aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndroid Build Coastguard Worker <android-build-coastguard-worker@google.com>2022-04-08 16:04:38 +0000
committerAndroid Build Coastguard Worker <android-build-coastguard-worker@google.com>2022-04-08 16:04:38 +0000
commitaf20b9ba3d3187aba73b86e61d14e60d54cb4c46 (patch)
treeb16b6085a42c68b75bcbaef66b259792ec9fb5c0
parented72843e9e1d40c7e42c1fae30d7b4d18fcbbeb9 (diff)
parent43fcfff5a381ac82e0a85065100eeaef96da7b85 (diff)
downloadbt-aml_tz2_305400100.tar.gz
Change-Id: Ic16096fdd7ed1c0ebcde050dcffd6c9bfad341f7
-rw-r--r--.gitignore5
-rw-r--r--.gn (renamed from gd/att/BUILD.gn)12
-rw-r--r--.style.yapf1
-rw-r--r--Android.bp32
-rw-r--r--BUILD.gn208
-rw-r--r--Cargo.toml24
-rw-r--r--METADATA3
-rw-r--r--OWNERS3
-rw-r--r--PREUPLOAD.cfg5
-rw-r--r--README.md141
-rwxr-xr-xTEST_MAPPING50
-rw-r--r--apex/Android.bp10
-rw-r--r--audio_a2dp_hw/Android.bp10
-rw-r--r--audio_a2dp_hw/src/audio_a2dp_hw.cc22
-rw-r--r--audio_bluetooth_hw/Android.bp10
-rw-r--r--audio_bluetooth_hw/device_port_proxy.cc210
-rw-r--r--audio_bluetooth_hw/device_port_proxy.h65
-rw-r--r--audio_bluetooth_hw/stream_apis.cc489
-rw-r--r--audio_bluetooth_hw/stream_apis.h21
-rw-r--r--audio_hal_interface/Android.bp40
-rw-r--r--audio_hal_interface/BUILD.gn36
-rw-r--r--audio_hal_interface/a2dp_encoding.cc36
-rw-r--r--audio_hal_interface/a2dp_encoding_host.cc53
-rw-r--r--audio_hal_interface/client_interface.cc562
-rw-r--r--audio_hal_interface/client_interface.h190
-rw-r--r--audio_hal_interface/client_interface_unittest.cc345
-rw-r--r--audio_hal_interface/codec_status.cc2
-rw-r--r--audio_hal_interface/hal_version_manager.h136
-rw-r--r--audio_hal_interface/hearing_aid_software_encoding.cc11
-rw-r--r--audio_hal_interface/hearing_aid_software_encoding_host.cc42
-rw-r--r--audio_hal_interface/le_audio_software.cc556
-rw-r--r--audio_hal_interface/le_audio_software.h109
-rw-r--r--audio_hearing_aid_hw/Android.bp19
-rw-r--r--audio_hearing_aid_hw/include/audio_hearing_aid_hw.h3
-rw-r--r--audio_hearing_aid_hw/src/audio_hearing_aid_hw.cc44
-rw-r--r--audio_hearing_aid_hw/src/audio_hearing_aid_hw_utils.cc2
-rw-r--r--binder/Android.bp18
-rw-r--r--binder/android/bluetooth/BufferConstraints.aidl3
-rw-r--r--binder/android/bluetooth/IBluetooth.aidl251
-rw-r--r--binder/android/bluetooth/IBluetoothA2dp.aidl67
-rw-r--r--binder/android/bluetooth/IBluetoothA2dpSink.aidl28
-rw-r--r--binder/android/bluetooth/IBluetoothAvrcpController.aidl19
-rw-r--r--binder/android/bluetooth/IBluetoothAvrcpTarget.aidl1
-rw-r--r--binder/android/bluetooth/IBluetoothConnectionCallback.aidl27
-rw-r--r--binder/android/bluetooth/IBluetoothGatt.aidl168
-rw-r--r--binder/android/bluetooth/IBluetoothGattCallback.aidl1
-rw-r--r--binder/android/bluetooth/IBluetoothHeadset.aidl90
-rw-r--r--binder/android/bluetooth/IBluetoothHeadsetClient.aidl82
-rw-r--r--binder/android/bluetooth/IBluetoothHeadsetPhone.aidl (renamed from binder/android/bluetooth/IBluetoothOobDataCallback.aidl)25
-rw-r--r--binder/android/bluetooth/IBluetoothHearingAid.aidl40
-rw-r--r--binder/android/bluetooth/IBluetoothHidDevice.aidl42
-rw-r--r--binder/android/bluetooth/IBluetoothHidHost.aidl70
-rw-r--r--binder/android/bluetooth/IBluetoothLeAudio.aidl57
-rw-r--r--binder/android/bluetooth/IBluetoothManager.aidl37
-rw-r--r--binder/android/bluetooth/IBluetoothMap.aidl28
-rw-r--r--binder/android/bluetooth/IBluetoothMapClient.aidl37
-rw-r--r--binder/android/bluetooth/IBluetoothMetadataListener.aidl1
-rw-r--r--binder/android/bluetooth/IBluetoothPan.aidl25
-rw-r--r--binder/android/bluetooth/IBluetoothPbap.aidl16
-rw-r--r--binder/android/bluetooth/IBluetoothPbapClient.aidl22
-rw-r--r--binder/android/bluetooth/IBluetoothProfileServiceConnection.aidl2
-rw-r--r--binder/android/bluetooth/IBluetoothSap.aidl31
-rw-r--r--binder/android/bluetooth/IBluetoothSocketManager.aidl3
-rw-r--r--binder/android/bluetooth/IBluetoothVolumeControl.aidl49
-rwxr-xr-x[-rw-r--r--]bta/Android.bp125
-rw-r--r--bta/BUILD.gn102
-rw-r--r--bta/ag/bta_ag_act.cc23
-rw-r--r--bta/ag/bta_ag_api.cc24
-rw-r--r--bta/ag/bta_ag_at.cc28
-rw-r--r--bta/ag/bta_ag_at.h4
-rw-r--r--bta/ag/bta_ag_cfg.cc10
-rw-r--r--bta/ag/bta_ag_cmd.cc146
-rw-r--r--bta/ag/bta_ag_int.h40
-rw-r--r--bta/ag/bta_ag_main.cc441
-rw-r--r--bta/ag/bta_ag_rfc.cc36
-rw-r--r--bta/ag/bta_ag_sco.cc264
-rw-r--r--bta/ag/bta_ag_sdp.cc52
-rw-r--r--bta/ar/bta_ar.cc121
-rw-r--r--bta/ar/bta_ar_int.h6
-rw-r--r--bta/av/bta_av_aact.cc375
-rw-r--r--bta/av/bta_av_act.cc126
-rw-r--r--bta/av/bta_av_api.cc55
-rw-r--r--bta/av/bta_av_cfg.cc89
-rw-r--r--bta/av/bta_av_ci.cc21
-rw-r--r--bta/av/bta_av_int.h127
-rw-r--r--bta/av/bta_av_main.cc531
-rw-r--r--bta/av/bta_av_ssm.cc860
-rw-r--r--bta/dm/bta_dm_act.cc2491
-rw-r--r--bta/dm/bta_dm_api.cc411
-rw-r--r--bta/dm/bta_dm_cfg.cc96
-rw-r--r--bta/dm/bta_dm_ci.cc29
-rw-r--r--bta/dm/bta_dm_int.h266
-rw-r--r--bta/dm/bta_dm_main.cc292
-rw-r--r--bta/dm/bta_dm_pm.cc370
-rw-r--r--bta/gatt/bta_gattc_act.cc381
-rw-r--r--bta/gatt/bta_gattc_api.cc57
-rw-r--r--bta/gatt/bta_gattc_cache.cc283
-rw-r--r--bta/gatt/bta_gattc_int.h175
-rw-r--r--bta/gatt/bta_gattc_main.cc69
-rw-r--r--bta/gatt/bta_gattc_queue.cc41
-rw-r--r--bta/gatt/bta_gattc_utils.cc73
-rw-r--r--bta/gatt/bta_gatts_act.cc81
-rw-r--r--bta/gatt/bta_gatts_api.cc36
-rw-r--r--bta/gatt/bta_gatts_int.h37
-rw-r--r--bta/gatt/bta_gatts_main.cc9
-rw-r--r--bta/gatt/bta_gatts_utils.cc9
-rw-r--r--bta/gatt/database.cc125
-rw-r--r--bta/gatt/database.h12
-rw-r--r--bta/gatt/database_builder.cc65
-rw-r--r--bta/gatt/database_builder.h17
-rw-r--r--bta/hd/bta_hd_act.cc32
-rw-r--r--bta/hd/bta_hd_api.cc23
-rw-r--r--bta/hd/bta_hd_int.h32
-rw-r--r--bta/hd/bta_hd_main.cc396
-rw-r--r--bta/hearing_aid/hearing_aid.cc125
-rw-r--r--bta/hearing_aid/hearing_aid_audio_source.cc41
-rw-r--r--bta/hf_client/bta_hf_client_act.cc23
-rw-r--r--bta/hf_client/bta_hf_client_api.cc26
-rw-r--r--bta/hf_client/bta_hf_client_at.cc174
-rw-r--r--bta/hf_client/bta_hf_client_at.h3
-rwxr-xr-xbta/hf_client/bta_hf_client_int.h52
-rw-r--r--bta/hf_client/bta_hf_client_main.cc59
-rw-r--r--bta/hf_client/bta_hf_client_rfc.cc33
-rw-r--r--bta/hf_client/bta_hf_client_sco.cc47
-rwxr-xr-xbta/hf_client/bta_hf_client_sdp.cc31
-rw-r--r--bta/hh/bta_hh_act.cc243
-rw-r--r--bta/hh/bta_hh_api.cc81
-rw-r--r--bta/hh/bta_hh_cfg.cc5
-rw-r--r--bta/hh/bta_hh_int.h170
-rwxr-xr-x[-rw-r--r--]bta/hh/bta_hh_le.cc443
-rw-r--r--bta/hh/bta_hh_main.cc364
-rw-r--r--bta/hh/bta_hh_utils.cc262
-rw-r--r--bta/include/bta_ag_api.h206
-rw-r--r--bta/include/bta_api.h840
-rw-r--r--bta/include/bta_ar_api.h25
-rw-r--r--bta/include/bta_av_api.h30
-rw-r--r--bta/include/bta_av_ci.h4
-rw-r--r--bta/include/bta_av_co.h20
-rw-r--r--bta/include/bta_dm_acl.h31
-rw-r--r--bta/include/bta_dm_api.h2
-rw-r--r--bta/include/bta_dm_ci.h18
-rw-r--r--bta/include/bta_dm_co.h37
-rw-r--r--bta/include/bta_gatt_api.h123
-rw-r--r--bta/include/bta_gatt_queue.h14
-rw-r--r--bta/include/bta_gatts_co.h2
-rw-r--r--bta/include/bta_hd_api.h7
-rw-r--r--bta/include/bta_hearing_aid_api.h6
-rwxr-xr-xbta/include/bta_hf_client_api.h18
-rw-r--r--bta/include/bta_hfp_api.h39
-rw-r--r--bta/include/bta_hh_api.h98
-rw-r--r--bta/include/bta_hh_co.h9
-rw-r--r--bta/include/bta_jv_api.h113
-rw-r--r--bta/include/bta_jv_co.h4
-rw-r--r--bta/include/bta_mce_api.h121
-rw-r--r--bta/include/bta_op_api.h2
-rw-r--r--bta/include/bta_pan_api.h9
-rw-r--r--bta/include/bta_pan_ci.h4
-rw-r--r--bta/include/bta_pan_co.h38
-rw-r--r--bta/include/bta_sdp_api.h13
-rw-r--r--bta/include/bta_vc_api.h40
-rw-r--r--bta/include/utl.h3
-rw-r--r--bta/jv/bta_jv_act.cc585
-rw-r--r--bta/jv/bta_jv_api.cc152
-rw-r--r--bta/jv/bta_jv_cfg.cc9
-rw-r--r--bta/jv/bta_jv_int.h34
-rw-r--r--bta/mce/bta_mce_act.cc189
-rw-r--r--bta/mce/bta_mce_api.cc107
-rw-r--r--bta/mce/bta_mce_cfg.cc45
-rw-r--r--bta/mce/bta_mce_int.h86
-rw-r--r--bta/mce/bta_mce_main.cc75
-rw-r--r--bta/pan/bta_pan_act.cc76
-rw-r--r--bta/pan/bta_pan_api.cc45
-rw-r--r--bta/pan/bta_pan_ci.cc18
-rw-r--r--bta/pan/bta_pan_int.h33
-rw-r--r--bta/pan/bta_pan_main.cc17
-rw-r--r--bta/pb/bta_pbs_int.h4
-rw-r--r--bta/sdp/bta_sdp.cc47
-rw-r--r--bta/sdp/bta_sdp_act.cc135
-rw-r--r--bta/sdp/bta_sdp_api.cc74
-rw-r--r--bta/sdp/bta_sdp_cfg.cc7
-rw-r--r--bta/sdp/bta_sdp_int.h61
-rw-r--r--bta/sys/bta_sys.h203
-rw-r--r--bta/sys/bta_sys_conn.cc168
-rw-r--r--bta/sys/bta_sys_int.h34
-rw-r--r--bta/sys/bta_sys_main.cc449
-rw-r--r--bta/sys/utl.cc9
-rw-r--r--bta/test/bta_dip_test.cc124
-rw-r--r--bta/test/bta_dm_cust_uuid_test.cc76
-rw-r--r--bta/test/bta_dm_test.cc114
-rw-r--r--bta/test/bta_gatt_test.cc295
-rw-r--r--bta/test/bta_hf_client_add_record_test.cc36
-rw-r--r--bta/test/bta_hf_client_test.cc3
-rw-r--r--bta/test/common/bta_gatt_api_mock.cc86
-rw-r--r--bta/test/common/bta_gatt_api_mock.h95
-rw-r--r--bta/test/common/bta_gatt_queue_mock.cc46
-rw-r--r--bta/test/common/bta_gatt_queue_mock.h49
-rw-r--r--bta/test/common/btm_api_mock.cc40
-rw-r--r--bta/test/common/btm_api_mock.h60
-rw-r--r--bta/test/common/fake_osi.h26
-rw-r--r--bta/test/gatt/database_builder_test.cc79
-rw-r--r--bta/test/gatt/database_test.cc85
-rw-r--r--bta/vc/device.cc245
-rw-r--r--bta/vc/devices.h192
-rw-r--r--bta/vc/devices_test.cc470
-rw-r--r--bta/vc/types.h47
-rw-r--r--bta/vc/vc.cc574
-rw-r--r--bta/vc/vc_test.cc643
-rw-r--r--btcore/Android.bp12
-rw-r--r--btcore/BUILD.gn59
-rw-r--r--btcore/include/module.h22
-rw-r--r--btcore/src/hal_util.cc10
-rw-r--r--btcore/src/module.cc77
-rwxr-xr-x[-rw-r--r--]btif/Android.bp135
-rw-r--r--btif/BUILD.gn101
-rw-r--r--btif/avrcp/avrcp_service.cc124
-rw-r--r--btif/avrcp/avrcp_service.h15
-rw-r--r--btif/co/bta_av_co.cc41
-rw-r--r--btif/co/bta_dm_co.cc224
-rw-r--r--btif/co/bta_hh_co.cc34
-rw-r--r--btif/co/bta_pan_co.cc68
-rw-r--r--btif/include/btif_a2dp_sink.h8
-rw-r--r--btif/include/btif_a2dp_source.h11
-rw-r--r--btif/include/btif_acl.h21
-rw-r--r--btif/include/btif_activity_attribution.h25
-rw-r--r--btif/include/btif_api.h181
-rw-r--r--btif/include/btif_av.h16
-rw-r--r--btif/include/btif_bqr.h5
-rw-r--r--btif/include/btif_common.h86
-rw-r--r--btif/include/btif_config.h43
-rw-r--r--btif/include/btif_config_cache.h5
-rw-r--r--btif/include/btif_dm.h29
-rw-r--r--btif/include/btif_gatt.h2
-rw-r--r--btif/include/btif_gatt_util.h3
-rw-r--r--btif/include/btif_hd.h2
-rw-r--r--btif/include/btif_hh.h27
-rw-r--r--btif/include/btif_mce.h (renamed from stack/test/common/mock_btif_storage.cc)26
-rw-r--r--btif/include/btif_metrics_logging.h69
-rw-r--r--btif/include/btif_pan_internal.h6
-rw-r--r--btif/include/btif_sock_l2cap.h2
-rw-r--r--btif/include/btif_sock_sdp.h2
-rw-r--r--btif/include/btif_sock_thread.h2
-rw-r--r--btif/include/btif_storage.h42
-rw-r--r--btif/include/btif_util.h2
-rw-r--r--btif/src/bluetooth.cc533
-rw-r--r--btif/src/btif_a2dp.cc22
-rw-r--r--btif/src/btif_a2dp_audio_interface.cc105
-rw-r--r--btif/src/btif_a2dp_sink.cc140
-rw-r--r--btif/src/btif_a2dp_source.cc200
-rw-r--r--btif/src/btif_av.cc323
-rw-r--r--btif/src/btif_avrcp_audio_track.cc24
-rw-r--r--btif/src/btif_ble_advertiser.cc14
-rw-r--r--btif/src/btif_ble_scanner.cc40
-rw-r--r--btif/src/btif_bqr.cc30
-rw-r--r--btif/src/btif_config.cc250
-rw-r--r--btif/src/btif_config_cache.cc13
-rw-r--r--btif/src/btif_config_transcode.cc7
-rw-r--r--btif/src/btif_core.cc852
-rw-r--r--btif/src/btif_debug_btsnoop.cc31
-rw-r--r--btif/src/btif_dm.cc1937
-rw-r--r--btif/src/btif_gatt.cc14
-rw-r--r--btif/src/btif_gatt_client.cc230
-rw-r--r--btif/src/btif_gatt_server.cc51
-rw-r--r--btif/src/btif_gatt_test.cc114
-rw-r--r--btif/src/btif_gatt_util.cc23
-rw-r--r--btif/src/btif_hd.cc31
-rw-r--r--btif/src/btif_hearing_aid.cc8
-rw-r--r--btif/src/btif_hf.cc139
-rwxr-xr-x[-rw-r--r--]btif/src/btif_hf_client.cc22
-rw-r--r--btif/src/btif_hh.cc155
-rw-r--r--btif/src/btif_keystore.cc4
-rw-r--r--btif/src/btif_le_audio.cc102
-rw-r--r--btif/src/btif_mce.cc161
-rw-r--r--btif/src/btif_metrics_logging.cc166
-rw-r--r--btif/src/btif_pan.cc73
-rw-r--r--btif/src/btif_profile_queue.cc24
-rwxr-xr-x[-rw-r--r--]btif/src/btif_rc.cc319
-rw-r--r--btif/src/btif_sdp_server.cc52
-rw-r--r--btif/src/btif_sock.cc82
-rw-r--r--btif/src/btif_sock_l2cap.cc391
-rw-r--r--btif/src/btif_sock_rfc.cc130
-rw-r--r--btif/src/btif_sock_sco.cc46
-rw-r--r--btif/src/btif_sock_sdp.cc50
-rw-r--r--btif/src/btif_sock_thread.cc60
-rw-r--r--btif/src/btif_sock_util.cc15
-rw-r--r--btif/src/btif_storage.cc312
-rw-r--r--btif/src/btif_util.cc10
-rw-r--r--btif/src/btif_vc.cc125
-rw-r--r--btif/src/stack_manager.cc257
-rw-r--r--btif/test/btif_config_cache_test.cc5
-rwxr-xr-x[-rw-r--r--]btif/test/btif_hf_client_service_test.cc21
-rw-r--r--btif/test/btif_rc_test.cc2
-rw-r--r--btif/test/btif_stack_test.cc206
-rwxr-xr-xbuild.py458
-rw-r--r--build/Android.bp50
-rw-r--r--build/dpkg/README.txt25
-rw-r--r--build/dpkg/libchrome-822064/debian/README.Debian1
-rw-r--r--build/dpkg/libchrome-822064/debian/changelog5
-rw-r--r--build/dpkg/libchrome-822064/debian/compat1
-rw-r--r--build/dpkg/libchrome-822064/debian/control28
-rwxr-xr-xbuild/dpkg/libchrome-822064/debian/install_headers.sh48
-rw-r--r--build/dpkg/libchrome-822064/debian/libchrome.install4
-rw-r--r--build/dpkg/libchrome-822064/debian/patches/0001-Add-missing-includes.patch37
-rw-r--r--build/dpkg/libchrome-822064/debian/patches/0001-Remove-absl-from-pkgconfig.patch33
-rw-r--r--build/dpkg/libchrome-822064/debian/patches/0001-rebase_path-for-write_args.patch34
-rw-r--r--build/dpkg/libchrome-822064/debian/patches/series3
-rwxr-xr-xbuild/dpkg/libchrome-822064/debian/rules38
-rwxr-xr-xbuild/dpkg/libchrome-822064/gen-src-pkg.sh60
-rw-r--r--build/dpkg/libchrome/debian/README.Debian1
-rw-r--r--build/dpkg/libchrome/debian/changelog5
-rw-r--r--build/dpkg/libchrome/debian/compat1
-rw-r--r--build/dpkg/libchrome/debian/control27
-rwxr-xr-xbuild/dpkg/libchrome/debian/install_headers.sh48
-rw-r--r--build/dpkg/libchrome/debian/libchrome.install4
-rw-r--r--build/dpkg/libchrome/debian/patches/0001-Add-missing-includes.patch37
-rw-r--r--build/dpkg/libchrome/debian/patches/0001-common-mk-rebase_path-output-location-of-generate-pc.patch36
-rw-r--r--build/dpkg/libchrome/debian/patches/0001-rebase_path-for-write_args.patch34
-rw-r--r--build/dpkg/libchrome/debian/patches/series3
-rwxr-xr-xbuild/dpkg/libchrome/debian/rules38
-rwxr-xr-xbuild/dpkg/libchrome/gen-src-pkg.sh60
-rw-r--r--build/dpkg/modp_b64/debian/README.Debian1
-rw-r--r--build/dpkg/modp_b64/debian/changelog5
-rw-r--r--build/dpkg/modp_b64/debian/compat1
-rw-r--r--build/dpkg/modp_b64/debian/control18
-rw-r--r--build/dpkg/modp_b64/debian/modp-b64.install3
-rw-r--r--build/dpkg/modp_b64/debian/patches/0001-common-mk-rebase_path-output-location-of-generate-pc.patch36
-rw-r--r--build/dpkg/modp_b64/debian/patches/series1
-rwxr-xr-xbuild/dpkg/modp_b64/debian/rules31
-rwxr-xr-xbuild/dpkg/modp_b64/gen-src-pkg.sh57
-rwxr-xr-xbuild/install_deps.sh25
-rw-r--r--build/toolchain/clang/get_clang_suffix.py3
-rw-r--r--common/Android.bp16
-rw-r--r--common/BUILD.gn64
-rw-r--r--common/benchmark/thread_performance_benchmark.cc5
-rw-r--r--common/benchmark/timer_performance_benchmark.cc3
-rw-r--r--common/lru.h10
-rw-r--r--common/lru_unittest.cc34
-rw-r--r--common/message_loop_thread.cc57
-rw-r--r--common/message_loop_thread.h38
-rw-r--r--common/metric_id_allocator.h4
-rw-r--r--common/metrics.cc43
-rw-r--r--common/metrics.h20
-rw-r--r--common/metrics_linux.cc66
-rw-r--r--common/os_utils.cc28
-rw-r--r--common/os_utils.h17
-rw-r--r--common/stop_watch_legacy.cc105
-rw-r--r--common/stop_watch_legacy.h46
-rw-r--r--common/test/thread_performance_test.cc5
-rw-r--r--conf/Android.bp9
-rw-r--r--device/Android.bp9
-rw-r--r--device/BUILD.gn57
-rw-r--r--device/include/controller.h51
-rw-r--r--device/include/esco_parameters.h6
-rw-r--r--device/include/interop.h22
-rw-r--r--device/include/interop_database.h21
-rw-r--r--device/src/controller.cc332
-rw-r--r--device/src/esco_parameters.cc286
-rw-r--r--device/src/interop.cc13
-rw-r--r--doc/btsnoop_net.md7
-rw-r--r--doc/power_management.md2
-rw-r--r--doc/supported_features.md4
-rw-r--r--embdrv/g722/Android.bp12
-rw-r--r--embdrv/g722/BUILD.gn3
-rw-r--r--embdrv/g722/fuzzer/Android.bp24
-rw-r--r--embdrv/g722/fuzzer/g722_enc_fuzzer.cc90
-rw-r--r--embdrv/sbc/Android.bp9
-rw-r--r--embdrv/sbc/BUILD.gn8
-rw-r--r--embdrv/sbc/decoder/Android.bp11
-rw-r--r--embdrv/sbc/decoder/include/oi_bt_spec.h4
-rw-r--r--embdrv/sbc/decoder/include/oi_status.h78
-rw-r--r--embdrv/sbc/encoder/Android.bp10
-rw-r--r--gd/.clang-format5
-rw-r--r--gd/Android.bp713
-rw-r--r--gd/Android.mk148
-rw-r--r--gd/BUILD.gn134
-rw-r--r--gd/README.md24
-rw-r--r--gd/TEST_MAPPING12
-rw-r--r--gd/att/Android.bp9
-rw-r--r--gd/att/att_module.cc35
-rw-r--r--gd/btaa/Android.bp32
-rw-r--r--gd/btaa/BUILD.gn22
-rw-r--r--gd/btaa/activity_attribution.fbs29
-rw-r--r--gd/btaa/activity_attribution.h78
-rw-r--r--gd/btaa/android/activity_attribution.cc211
-rw-r--r--gd/btaa/attribution_processor.h71
-rw-r--r--gd/btaa/cmd_evt_classification.h36
-rw-r--r--gd/btaa/hci_processor.h87
-rw-r--r--gd/btaa/host/activity_attribution.cc51
-rw-r--r--gd/btaa/linux/activity_attribution.cc53
-rw-r--r--gd/btaa/linux_generic/attribution_processor.cc181
-rw-r--r--gd/btaa/linux_generic/cmd_evt_classification.cc465
-rw-r--r--gd/btaa/linux_generic/hci_processor.cc268
-rw-r--r--gd/btaa/linux_generic/wakelock_processor.cc67
-rw-r--r--gd/btaa/wakelock_processor.h38
-rw-r--r--gd/cert/android_devices_config.json (renamed from gd/cert/devices_config.json)14
-rw-r--r--gd/cert/async_subprocess_logger.py90
-rw-r--r--gd/cert/behavior.py173
-rw-r--r--gd/cert/bluetooth_packets_python3_setup.py18
-rw-r--r--gd/cert/capture.py41
-rw-r--r--gd/cert/captures.py187
-rw-r--r--gd/cert/cert_self_test.py397
-rw-r--r--gd/cert/cert_self_test_lib.py604
-rw-r--r--gd/cert/cert_testcases_facade_only (renamed from gd/cert/all_cert_testcases)9
-rw-r--r--gd/cert/change_waiter.py18
-rw-r--r--gd/cert/closable.py39
-rw-r--r--gd/cert/event_asserts.py176
-rw-r--r--gd/cert/event_callback_stream.py147
-rw-r--r--gd/cert/event_stream.py294
-rw-r--r--gd/cert/gd_base_test.py148
-rw-r--r--gd/cert/gd_base_test_facade_only.py75
-rw-r--r--gd/cert/gd_base_test_lib.py163
-rw-r--r--gd/cert/gd_device.py656
-rw-r--r--gd/cert/gd_device_base.py164
-rwxr-xr-xgd/cert/gen_html_coverage.sh10
-rw-r--r--gd/cert/host_config.json50
-rw-r--r--gd/cert/host_only_config_facade_only.json (renamed from gd/cert/rust_host_config.json)16
-rwxr-xr-xgd/cert/irun10
-rw-r--r--gd/cert/logging_client_interceptor.py86
-rw-r--r--gd/cert/matchers.py729
-rw-r--r--gd/cert/metadata.py78
-rw-r--r--gd/cert/os_utils.py141
-rw-r--r--gd/cert/performance_test_logger.py71
-rw-r--r--gd/cert/pts.json1
-rw-r--r--gd/cert/pts_base_test.py7
-rw-r--r--gd/cert/py_acl_manager.py97
-rw-r--r--gd/cert/py_hal.py283
-rw-r--r--gd/cert/py_hci.py214
-rw-r--r--gd/cert/py_l2cap.py266
-rw-r--r--gd/cert/py_le_acl_manager.py138
-rw-r--r--gd/cert/py_le_iso.py180
-rw-r--r--gd/cert/py_le_security.py87
-rw-r--r--gd/cert/py_security.py279
-rwxr-xr-xgd/cert/python3.8-gd2
-rwxr-xr-xgd/cert/run490
-rwxr-xr-xgd/cert/run_cert_facade_only.sh13
-rwxr-xr-xgd/cert/run_device_cert.sh6
-rwxr-xr-xgd/cert/run_pts_l2cap.sh7
-rw-r--r--gd/cert/rust_android_devices_config.json55
-rwxr-xr-xgd/cert/set_up_acts.sh109
-rwxr-xr-xgd/cert/set_up_and_run_device_cert.sh17
-rw-r--r--gd/cert/set_up_virtualenv.sh121
-rw-r--r--gd/cert/truth.py150
-rw-r--r--gd/common/Android.bp24
-rw-r--r--gd/common/BUILD.gn30
-rw-r--r--gd/common/bidi_queue.h10
-rw-r--r--gd/common/bidi_queue_unittest.cc35
-rw-r--r--gd/common/bind.h7
-rw-r--r--gd/common/blocking_queue_unittest.cc4
-rw-r--r--gd/common/byte_array.h99
-rw-r--r--gd/common/byte_array_test.cc53
-rw-r--r--gd/common/callback_list.h1
-rw-r--r--gd/common/circular_buffer.h130
-rw-r--r--gd/common/circular_buffer_test.cc106
-rw-r--r--gd/common/contextual_callback.h104
-rw-r--r--gd/common/init_flags.cc104
-rw-r--r--gd/common/init_flags.fbs17
-rw-r--r--gd/common/init_flags.h54
-rw-r--r--gd/common/init_flags_test.cc64
-rw-r--r--gd/common/link_key.cc (renamed from gd/common/multi_priority_queue_test.cc)58
-rw-r--r--gd/common/link_key.h (renamed from btif/src/btif_activity_attribution.cc)33
-rw-r--r--gd/common/link_key_unittest.cc50
-rw-r--r--gd/common/list_map.h220
-rw-r--r--gd/common/list_map_test.cc363
-rw-r--r--gd/common/lru_cache.h219
-rw-r--r--gd/common/lru_cache_test.cc461
-rw-r--r--gd/common/metric_id_manager.cc203
-rw-r--r--gd/common/metric_id_manager.h140
-rw-r--r--gd/common/metric_id_manager_unittest.cc500
-rw-r--r--gd/common/multi_priority_queue.h75
-rw-r--r--gd/common/numbers.h48
-rw-r--r--gd/common/numbers_test.cc37
-rw-r--r--gd/common/stop_watch.cc106
-rw-r--r--gd/common/stop_watch.h46
-rw-r--r--gd/common/strings.cc178
-rw-r--r--gd/common/strings.h138
-rw-r--r--gd/common/strings_test.cc249
-rw-r--r--gd/common/type_helper.h31
-rw-r--r--gd/crypto_toolbox/Android.bp12
-rw-r--r--gd/crypto_toolbox/BUILD.gn24
-rw-r--r--gd/crypto_toolbox/aes.cc260
-rw-r--r--gd/crypto_toolbox/aes.h54
-rw-r--r--gd/crypto_toolbox/aes_cmac.cc2
-rw-r--r--gd/crypto_toolbox/crypto_toolbox.cc38
-rw-r--r--gd/crypto_toolbox/crypto_toolbox.h23
-rw-r--r--gd/crypto_toolbox/crypto_toolbox_test.cc39
-rw-r--r--gd/docs/architecture/architecture.md313
-rw-r--r--gd/docs/architecture/data_flow_diagram.pngbin42362 -> 0 bytes
-rw-r--r--gd/docs/architecture/style_guide.md207
-rw-r--r--gd/docs/testing/cert_test.md254
-rw-r--r--gd/docs/testing/cert_test_architecture_drawing.pngbin54186 -> 0 bytes
-rw-r--r--gd/docs/testing/gtest.md283
-rw-r--r--gd/dumpsys/Android.bp151
-rw-r--r--gd/dumpsys/BUILD.gn37
-rw-r--r--gd/dumpsys/bluetooth_flatbuffer_test.cc71
-rw-r--r--gd/dumpsys/bluetooth_flatbuffer_test.fbs17
-rw-r--r--gd/dumpsys/bundler/Android.bp85
-rw-r--r--gd/dumpsys/bundler/BUILD.gn51
-rw-r--r--gd/dumpsys/bundler/bundler.cc335
-rw-r--r--gd/dumpsys/bundler/bundler.fbs19
-rw-r--r--gd/dumpsys/bundler/bundler.gni180
-rw-r--r--gd/dumpsys/bundler/bundler.h71
-rwxr-xr-xgd/dumpsys/bundler/extract_files_and_call.py58
-rw-r--r--gd/dumpsys/bundler/main.cc27
-rw-r--r--gd/dumpsys/bundler/test.bfbsbin456 -> 0 bytes
-rw-r--r--gd/dumpsys/bundler/test.cc85
-rw-r--r--gd/dumpsys/filter.cc200
-rw-r--r--gd/dumpsys/filter.h28
-rw-r--r--gd/dumpsys/filter_test.cc187
-rw-r--r--gd/dumpsys/init_flags.cc35
-rw-r--r--gd/dumpsys/init_flags.h31
-rw-r--r--gd/dumpsys/internal/filter_internal.cc247
-rw-r--r--gd/dumpsys/internal/filter_internal.h123
-rw-r--r--gd/dumpsys/internal/filter_internal_test.cc416
-rw-r--r--gd/dumpsys/internal/test_data/float.bfbsbin208 -> 0 bytes
-rw-r--r--gd/dumpsys/internal/test_data/float.fbs7
-rw-r--r--gd/dumpsys/internal/test_data/float_bfbs.h13
-rw-r--r--gd/dumpsys/internal/test_data/float_generated.h81
-rw-r--r--gd/dumpsys/internal/test_data/integer.bfbsbin212 -> 0 bytes
-rw-r--r--gd/dumpsys/internal/test_data/integer.fbs7
-rw-r--r--gd/dumpsys/internal/test_data/integer_bfbs.h14
-rw-r--r--gd/dumpsys/internal/test_data/integer_generated.h81
-rw-r--r--gd/dumpsys/internal/test_data/mkfiles9
-rw-r--r--gd/dumpsys/internal/test_data/root.h17
-rw-r--r--gd/dumpsys/internal/test_data/string.bfbsbin208 -> 0 bytes
-rw-r--r--gd/dumpsys/internal/test_data/string.fbs7
-rw-r--r--gd/dumpsys/internal/test_data/string_bfbs.h13
-rw-r--r--gd/dumpsys/internal/test_data/string_generated.h88
-rw-r--r--gd/dumpsys/internal/test_data/struct.bfbsbin320 -> 0 bytes
-rw-r--r--gd/dumpsys/internal/test_data/struct.fbs11
-rw-r--r--gd/dumpsys/internal/test_data/struct_bfbs.h19
-rw-r--r--gd/dumpsys/internal/test_data/struct_generated.h121
-rw-r--r--gd/dumpsys/reflection_schema.cc85
-rw-r--r--gd/dumpsys/reflection_schema.h46
-rw-r--r--gd/dumpsys/reflection_schema_test.cc64
-rw-r--r--gd/dumpsys/test_data/bar.fbs12
-rw-r--r--gd/dumpsys/test_data/bar.h17
-rw-r--r--gd/dumpsys/test_data/baz.fbs35
-rw-r--r--gd/dumpsys/test_data/baz.h32
-rw-r--r--gd/dumpsys/test_data/foo.fbs25
-rw-r--r--gd/dumpsys/test_data/foo.h40
-rw-r--r--gd/dumpsys/test_data/qux.fbs13
-rw-r--r--gd/dumpsys/test_data/qux.h26
-rw-r--r--gd/dumpsys/test_data/root.fbs27
-rw-r--r--gd/dumpsys/test_data/root.h17
-rw-r--r--gd/dumpsys_data.fbs25
-rw-r--r--gd/facade/common.proto11
-rw-r--r--gd/facade/facade_main.cc90
-rw-r--r--gd/facade/grpc_root_server.cc46
-rw-r--r--gd/facade/grpc_root_server.h4
-rw-r--r--gd/facade/read_only_property_server.cc9
-rw-r--r--gd/facade/read_only_property_server.h4
-rw-r--r--gd/fuzz/Android.bp15
-rw-r--r--gd/fuzz/helpers.cc46
-rw-r--r--gd/fuzz/helpers.h59
-rwxr-xr-xgd/fuzz/run34
-rw-r--r--gd/grpc/grpc_event_queue.h6
-rw-r--r--gd/grpc/grpc_module.cc8
-rw-r--r--gd/grpc/grpc_module.h9
-rw-r--r--gd/hal/Android.bp31
-rw-r--r--gd/hal/BUILD.gn29
-rw-r--r--gd/hal/cert/simple_hal_test.py480
-rw-r--r--gd/hal/facade.cc66
-rw-r--r--gd/hal/facade.h4
-rw-r--r--gd/hal/facade.proto31
-rw-r--r--gd/hal/fuzz/fuzz_hci_hal.cc121
-rw-r--r--gd/hal/fuzz/fuzz_hci_hal.h63
-rw-r--r--gd/hal/hal_facade.proto20
-rw-r--r--gd/hal/hci_hal.h15
-rw-r--r--gd/hal/hci_hal_android_hidl.cc141
-rw-r--r--gd/hal/hci_hal_android_hidl_test.cc5
-rw-r--r--gd/hal/hci_hal_host_rootcanal.cc (renamed from gd/hal/hci_hal_host.cc)272
-rw-r--r--gd/hal/hci_hal_host_rootcanal.h (renamed from gd/hal/hci_hal_host.h)0
-rw-r--r--gd/hal/hci_hal_host_rootcanal_test.cc (renamed from gd/hal/hci_hal_host_test.cc)34
-rw-r--r--gd/hal/snoop_logger.cc389
-rw-r--r--gd/hal/snoop_logger.h73
-rw-r--r--gd/hal/snoop_logger_test.cc302
-rw-r--r--gd/hci/Android.bp50
-rw-r--r--gd/hci/BUILD.gn45
-rw-r--r--gd/hci/acl_builder_test.cc20
-rw-r--r--gd/hci/acl_connection_interface.h47
-rw-r--r--gd/hci/acl_fragmenter.cc (renamed from gd/hci/acl_manager/acl_fragmenter.cc)4
-rw-r--r--gd/hci/acl_fragmenter.h (renamed from gd/hci/acl_manager/acl_fragmenter.h)2
-rw-r--r--gd/hci/acl_manager.cc2180
-rw-r--r--gd/hci/acl_manager.h303
-rw-r--r--gd/hci/acl_manager/acl_connection.cc29
-rw-r--r--gd/hci/acl_manager/acl_connection.h55
-rw-r--r--gd/hci/acl_manager/assembler.h131
-rw-r--r--gd/hci/acl_manager/classic_acl_connection.cc590
-rw-r--r--gd/hci/acl_manager/classic_acl_connection.h91
-rw-r--r--gd/hci/acl_manager/classic_impl.h703
-rw-r--r--gd/hci/acl_manager/connection_callbacks.h44
-rw-r--r--gd/hci/acl_manager/connection_management_callbacks.h99
-rw-r--r--gd/hci/acl_manager/event_checkers.h59
-rw-r--r--gd/hci/acl_manager/le_acl_connection.cc193
-rw-r--r--gd/hci/acl_manager/le_acl_connection.h86
-rw-r--r--gd/hci/acl_manager/le_connection_callbacks.h41
-rw-r--r--gd/hci/acl_manager/le_connection_management_callbacks.h46
-rw-r--r--gd/hci/acl_manager/le_impl.h707
-rw-r--r--gd/hci/acl_manager/round_robin_scheduler.cc256
-rw-r--r--gd/hci/acl_manager/round_robin_scheduler.h81
-rw-r--r--gd/hci/acl_manager/round_robin_scheduler_test.cc415
-rw-r--r--gd/hci/acl_manager_mock.h51
-rw-r--r--gd/hci/acl_manager_test.cc1194
-rw-r--r--gd/hci/address.cc79
-rw-r--r--gd/hci/address.h39
-rw-r--r--gd/hci/address_unittest.cc91
-rw-r--r--gd/hci/address_with_type.h13
-rw-r--r--gd/hci/cert/acl_manager_test.py393
-rw-r--r--gd/hci/cert/api.proto46
-rw-r--r--gd/hci/cert/cert.cc0
-rw-r--r--gd/hci/cert/controller_test.py73
-rw-r--r--gd/hci/cert/direct_hci_test.py927
-rw-r--r--gd/hci/cert/le_acl_manager_test.py629
-rw-r--r--gd/hci/cert/le_advertising_manager_test.py153
-rw-r--r--gd/hci/cert/le_scanning_manager_test.py95
-rw-r--r--gd/hci/cert/le_scanning_with_security_test.py86
-rw-r--r--gd/hci/class_of_device.cc82
-rw-r--r--gd/hci/class_of_device.h52
-rw-r--r--gd/hci/class_of_device_unittest.cc37
-rw-r--r--gd/hci/classic_device.h (renamed from stack/test/common/mock_btif_storage.h)33
-rw-r--r--gd/hci/command_interface.h41
-rw-r--r--gd/hci/controller.cc527
-rw-r--r--gd/hci/controller.h120
-rw-r--r--gd/hci/controller_mock.h133
-rw-r--r--gd/hci/controller_test.cc172
-rw-r--r--gd/hci/device.cc32
-rw-r--r--gd/hci/device.h136
-rw-r--r--gd/hci/device_database.cc276
-rw-r--r--gd/hci/device_database.h149
-rw-r--r--gd/hci/device_database_test.cc134
-rw-r--r--gd/hci/device_test.cc101
-rw-r--r--gd/hci/dual_device.h60
-rw-r--r--gd/hci/dual_device_test.cc81
-rw-r--r--gd/hci/enum_helper.h90
-rw-r--r--gd/hci/facade/acl_manager_facade.cc524
-rw-r--r--gd/hci/facade/acl_manager_facade.proto28
-rw-r--r--gd/hci/facade/controller_facade.cc13
-rw-r--r--gd/hci/facade/controller_facade.proto9
-rw-r--r--gd/hci/facade/facade.cc164
-rw-r--r--gd/hci/facade/facade.h6
-rw-r--r--gd/hci/facade/facade.proto43
-rw-r--r--gd/hci/facade/hci_facade.proto23
-rw-r--r--gd/hci/facade/le_acl_manager_facade.cc330
-rw-r--r--gd/hci/facade/le_acl_manager_facade.proto19
-rw-r--r--gd/hci/facade/le_advertising_manager_facade.cc19
-rw-r--r--gd/hci/facade/le_advertising_manager_facade.proto13
-rw-r--r--gd/hci/facade/le_initiator_address_facade.cc128
-rw-r--r--gd/hci/facade/le_initiator_address_facade.h45
-rw-r--r--gd/hci/facade/le_initiator_address_facade.proto28
-rw-r--r--gd/hci/facade/le_scanning_manager_facade.cc111
-rw-r--r--gd/hci/fuzz/acl_manager_fuzz_test.cc62
-rw-r--r--gd/hci/fuzz/fuzz_hci_layer.cc195
-rw-r--r--gd/hci/fuzz/fuzz_hci_layer.h195
-rw-r--r--gd/hci/fuzz/hci_layer_fuzz_client.cc124
-rw-r--r--gd/hci/fuzz/hci_layer_fuzz_client.h93
-rw-r--r--gd/hci/fuzz/hci_layer_fuzz_test.cc64
-rw-r--r--gd/hci/fuzz/status_vs_complete_commands.cc49
-rw-r--r--gd/hci/hci_acl_manager.fbs9
-rw-r--r--gd/hci/hci_layer.cc744
-rw-r--r--gd/hci/hci_layer.h106
-rw-r--r--gd/hci/hci_layer_test.cc337
-rw-r--r--gd/hci/hci_metrics_logging.cc877
-rw-r--r--gd/hci/hci_metrics_logging.h38
-rw-r--r--gd/hci/hci_packets.pdl2393
-rw-r--r--gd/hci/hci_packets_fuzz_test.cc10
-rw-r--r--gd/hci/hci_packets_test.cc375
-rw-r--r--gd/hci/le_acl_connection_interface.h37
-rw-r--r--gd/hci/le_address_manager.cc450
-rw-r--r--gd/hci/le_address_manager.h148
-rw-r--r--gd/hci/le_address_manager_test.cc463
-rw-r--r--gd/hci/le_advertising_interface.h24
-rw-r--r--gd/hci/le_advertising_manager.cc1175
-rw-r--r--gd/hci/le_advertising_manager.h88
-rw-r--r--gd/hci/le_advertising_manager_mock.h52
-rw-r--r--gd/hci/le_advertising_manager_test.cc993
-rw-r--r--gd/hci/le_device.h89
-rw-r--r--gd/hci/le_iso_interface.h37
-rw-r--r--gd/hci/le_report.h86
-rw-r--r--gd/hci/le_scanning_interface.h35
-rw-r--r--gd/hci/le_scanning_manager.cc1255
-rw-r--r--gd/hci/le_scanning_manager.h129
-rw-r--r--gd/hci/le_scanning_manager_test.cc355
-rw-r--r--gd/hci/le_security_interface.h26
-rw-r--r--gd/hci/link_key.cc25
-rw-r--r--gd/hci/link_key.h30
-rw-r--r--gd/hci/security_interface.h52
-rw-r--r--gd/hci/uuid.cc231
-rw-r--r--gd/hci/uuid.h153
-rw-r--r--gd/hci/uuid_unittest.cc144
-rw-r--r--gd/hci/vendor_specific_event_manager.cc132
-rw-r--r--gd/hci/vendor_specific_event_manager.h50
-rw-r--r--gd/iso/Android.bp30
-rw-r--r--gd/iso/cert/cert_le_iso.py59
-rw-r--r--gd/iso/cert/le_iso_test.py286
-rw-r--r--gd/iso/facade.cc232
-rw-r--r--gd/iso/facade.h41
-rw-r--r--gd/iso/facade.proto90
-rw-r--r--gd/iso/internal/iso_manager_impl.cc271
-rw-r--r--gd/iso/internal/iso_manager_impl.h118
-rw-r--r--gd/iso/iso_manager.cc104
-rw-r--r--gd/iso/iso_manager.h87
-rw-r--r--gd/iso/iso_module.cc66
-rw-r--r--gd/l2cap/Android.bp21
-rw-r--r--gd/l2cap/BUILD.gn60
-rw-r--r--gd/l2cap/cid.h2
-rw-r--r--gd/l2cap/classic/cert/cert_l2cap.py384
-rw-r--r--gd/l2cap/classic/cert/l2cap_performance_test.py187
-rw-r--r--gd/l2cap/classic/cert/l2cap_test.py3063
-rw-r--r--gd/l2cap/classic/cert/pts_l2cap_test.py363
-rw-r--r--gd/l2cap/classic/dynamic_channel_configuration_option.h6
-rw-r--r--gd/l2cap/classic/dynamic_channel_manager.cc37
-rw-r--r--gd/l2cap/classic/dynamic_channel_manager.h44
-rw-r--r--gd/l2cap/classic/dynamic_channel_service.cc7
-rw-r--r--gd/l2cap/classic/dynamic_channel_service.h6
-rw-r--r--gd/l2cap/classic/facade.cc420
-rw-r--r--gd/l2cap/classic/facade.proto61
-rw-r--r--gd/l2cap/classic/fixed_channel_manager.cc3
-rw-r--r--gd/l2cap/classic/fixed_channel_manager.h5
-rw-r--r--gd/l2cap/classic/fixed_channel_manager_mock.h2
-rw-r--r--gd/l2cap/classic/internal/channel_configuration_state.h2
-rw-r--r--gd/l2cap/classic/internal/dumpsys_helper.cc81
-rw-r--r--gd/l2cap/classic/internal/dumpsys_helper.h50
-rw-r--r--gd/l2cap/classic/internal/dynamic_channel_service_impl.h24
-rw-r--r--gd/l2cap/classic/internal/dynamic_channel_service_impl_mock.h39
-rw-r--r--gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.cc31
-rw-r--r--gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.h14
-rw-r--r--gd/l2cap/classic/internal/dynamic_channel_service_manager_impl_mock.h7
-rw-r--r--gd/l2cap/classic/internal/dynamic_channel_service_manager_test.cc13
-rw-r--r--gd/l2cap/classic/internal/fixed_channel_impl.cc5
-rw-r--r--gd/l2cap/classic/internal/fixed_channel_impl_test.cc63
-rw-r--r--gd/l2cap/classic/internal/fixed_channel_service_manager_test.cc2
-rw-r--r--gd/l2cap/classic/internal/link.cc327
-rw-r--r--gd/l2cap/classic/internal/link.h146
-rw-r--r--gd/l2cap/classic/internal/link_manager.cc330
-rw-r--r--gd/l2cap/classic/internal/link_manager.h74
-rw-r--r--gd/l2cap/classic/internal/link_manager_test.cc78
-rw-r--r--gd/l2cap/classic/internal/link_mock.h17
-rw-r--r--gd/l2cap/classic/internal/link_test.cc29
-rw-r--r--gd/l2cap/classic/internal/signalling_manager.cc489
-rw-r--r--gd/l2cap/classic/internal/signalling_manager.h15
-rw-r--r--gd/l2cap/classic/l2cap_classic_module.cc92
-rw-r--r--gd/l2cap/classic/l2cap_classic_module.fbs20
-rw-r--r--gd/l2cap/classic/l2cap_classic_module.h33
-rw-r--r--gd/l2cap/classic/link_property_listener.h95
-rw-r--r--gd/l2cap/classic/link_security_interface.h121
-rw-r--r--gd/l2cap/classic/security_enforcement_interface.h59
-rw-r--r--gd/l2cap/dynamic_channel.cc22
-rw-r--r--gd/l2cap/dynamic_channel.h16
-rwxr-xr-xgd/l2cap/fuzz/Android.bp44
-rwxr-xr-xgd/l2cap/fuzz/channel_fuzz_controller.cc40
-rwxr-xr-xgd/l2cap/fuzz/channel_fuzz_controller.h46
-rwxr-xr-xgd/l2cap/fuzz/fuzz_dynamic_channel_manager.h63
-rwxr-xr-xgd/l2cap/fuzz/fuzz_dynamic_channel_manager_impl.h109
-rwxr-xr-xgd/l2cap/fuzz/fuzz_l2cap.cc111
-rwxr-xr-xgd/l2cap/fuzz/fuzz_l2cap_classic_module.h54
-rwxr-xr-xgd/l2cap/fuzz/shim_l2cap.h106
-rw-r--r--gd/l2cap/internal/basic_mode_channel_data_controller.cc4
-rw-r--r--gd/l2cap/internal/basic_mode_channel_data_controller.h2
-rw-r--r--gd/l2cap/internal/data_pipeline_manager.cc11
-rw-r--r--gd/l2cap/internal/data_pipeline_manager.h3
-rw-r--r--gd/l2cap/internal/dynamic_channel_allocator.cc14
-rw-r--r--gd/l2cap/internal/dynamic_channel_allocator.h17
-rw-r--r--gd/l2cap/internal/dynamic_channel_allocator_fuzz_test.cc8
-rw-r--r--gd/l2cap/internal/dynamic_channel_allocator_test.cc4
-rw-r--r--gd/l2cap/internal/dynamic_channel_impl.cc28
-rw-r--r--gd/l2cap/internal/dynamic_channel_impl.h11
-rw-r--r--gd/l2cap/internal/dynamic_channel_impl_test.cc47
-rw-r--r--gd/l2cap/internal/enhanced_retransmission_mode_channel_data_controller.cc76
-rw-r--r--gd/l2cap/internal/enhanced_retransmission_mode_channel_data_controller.h5
-rw-r--r--gd/l2cap/internal/fixed_channel_allocator.h11
-rw-r--r--gd/l2cap/internal/fixed_channel_allocator_test.cc2
-rw-r--r--gd/l2cap/internal/ilink.h11
-rw-r--r--gd/l2cap/internal/ilink_mock.h2
-rw-r--r--gd/l2cap/internal/le_credit_based_channel_data_controller.cc4
-rw-r--r--gd/l2cap/internal/le_credit_based_channel_data_controller.h2
-rw-r--r--gd/l2cap/internal/le_credit_based_channel_data_controller_test.cc4
-rw-r--r--gd/l2cap/internal/parameter_provider.h2
-rw-r--r--gd/l2cap/internal/receiver.cc3
-rw-r--r--gd/l2cap/internal/scheduler.h11
-rw-r--r--gd/l2cap/internal/scheduler_fifo.cc37
-rw-r--r--gd/l2cap/internal/scheduler_fifo.h13
-rw-r--r--gd/l2cap/internal/scheduler_fifo_test.cc104
-rw-r--r--gd/l2cap/internal/sender.cc16
-rw-r--r--gd/l2cap/internal/sender.h3
-rw-r--r--gd/l2cap/internal/sender_test.cc4
-rw-r--r--gd/l2cap/l2cap_packet_fuzz_test.cc2
-rw-r--r--gd/l2cap/l2cap_packet_test.cc72
-rw-r--r--gd/l2cap/l2cap_packets.pdl110
-rw-r--r--gd/l2cap/le/cert/cert_le_l2cap.py201
-rw-r--r--gd/l2cap/le/cert/dual_l2cap_test.py187
-rw-r--r--gd/l2cap/le/cert/le_l2cap_test.py571
-rw-r--r--gd/l2cap/le/dynamic_channel.cc33
-rw-r--r--gd/l2cap/le/dynamic_channel.h28
-rw-r--r--gd/l2cap/le/dynamic_channel_manager.cc1
-rw-r--r--gd/l2cap/le/dynamic_channel_manager.h5
-rw-r--r--gd/l2cap/le/dynamic_channel_service.h1
-rw-r--r--gd/l2cap/le/facade.cc447
-rw-r--r--gd/l2cap/le/facade.h46
-rw-r--r--gd/l2cap/le/facade.proto85
-rw-r--r--gd/l2cap/le/fixed_channel.cc13
-rw-r--r--gd/l2cap/le/fixed_channel.h15
-rw-r--r--gd/l2cap/le/fixed_channel_manager.cc3
-rw-r--r--gd/l2cap/le/fixed_channel_manager.h8
-rw-r--r--gd/l2cap/le/internal/dynamic_channel_service_impl.h11
-rw-r--r--gd/l2cap/le/internal/dynamic_channel_service_impl_mock.h38
-rw-r--r--gd/l2cap/le/internal/dynamic_channel_service_manager_impl.cc15
-rw-r--r--gd/l2cap/le/internal/dynamic_channel_service_manager_impl.h11
-rw-r--r--gd/l2cap/le/internal/dynamic_channel_service_manager_test.cc30
-rw-r--r--gd/l2cap/le/internal/fixed_channel_impl.cc12
-rw-r--r--gd/l2cap/le/internal/fixed_channel_impl.h6
-rw-r--r--gd/l2cap/le/internal/fixed_channel_impl_test.cc63
-rw-r--r--gd/l2cap/le/internal/fixed_channel_service_manager_test.cc2
-rw-r--r--gd/l2cap/le/internal/link.cc176
-rw-r--r--gd/l2cap/le/internal/link.h86
-rw-r--r--gd/l2cap/le/internal/link_manager.cc122
-rw-r--r--gd/l2cap/le/internal/link_manager.h46
-rw-r--r--gd/l2cap/le/internal/link_manager_test.cc245
-rw-r--r--gd/l2cap/le/internal/link_mock.h8
-rw-r--r--gd/l2cap/le/internal/signalling_manager.cc227
-rw-r--r--gd/l2cap/le/internal/signalling_manager.h71
-rw-r--r--gd/l2cap/le/l2cap_le_module.cc51
-rw-r--r--gd/l2cap/le/l2cap_le_module.h34
-rw-r--r--gd/l2cap/le/link_options.cc68
-rw-r--r--gd/l2cap/le/link_options.h86
-rw-r--r--gd/l2cap/le/link_property_listener.h78
-rw-r--r--gd/l2cap/le/security_enforcement_interface.h45
-rw-r--r--gd/l2cap/le/security_policy.h46
-rw-r--r--gd/l2cap/security_policy.h (renamed from gd/l2cap/classic/security_policy.h)32
-rw-r--r--gd/module.cc61
-rw-r--r--gd/module.h96
-rw-r--r--gd/module_unittest.cc117
-rw-r--r--gd/module_unittest.fbs10
-rw-r--r--gd/module_unittest_generated.h84
-rw-r--r--gd/neighbor/Android.bp9
-rw-r--r--gd/neighbor/BUILD.gn30
-rw-r--r--gd/neighbor/cert/neighbor_test.py179
-rw-r--r--gd/neighbor/cert/py_neighbor.py84
-rw-r--r--gd/neighbor/connectability.cc3
-rw-r--r--gd/neighbor/connectability.h3
-rw-r--r--gd/neighbor/discoverability.cc27
-rw-r--r--gd/neighbor/discoverability.h4
-rw-r--r--gd/neighbor/facade/facade.cc82
-rw-r--r--gd/neighbor/facade/facade.proto5
-rw-r--r--gd/neighbor/inquiry.cc171
-rw-r--r--gd/neighbor/inquiry.h11
-rw-r--r--gd/neighbor/inquiry_mock.h60
-rw-r--r--gd/neighbor/inquiry_test.cc144
-rw-r--r--gd/neighbor/name.cc90
-rw-r--r--gd/neighbor/name.h13
-rw-r--r--gd/neighbor/name_db.cc42
-rw-r--r--gd/neighbor/name_db.h5
-rw-r--r--gd/neighbor/page.cc56
-rw-r--r--gd/neighbor/page.h3
-rw-r--r--gd/neighbor/scan.cc13
-rw-r--r--gd/neighbor/scan.h3
-rw-r--r--gd/os/Android.bp64
-rw-r--r--gd/os/BUILD.gn41
-rw-r--r--gd/os/alarm.h4
-rw-r--r--gd/os/alarm_benchmark.cc9
-rw-r--r--gd/os/android/metrics.cc430
-rw-r--r--gd/os/android/parameter_provider.cc80
-rw-r--r--gd/os/android/system_properties.cc51
-rw-r--r--gd/os/android/system_properties_test.cc58
-rw-r--r--gd/os/android/wakelock_native.cc118
-rw-r--r--gd/os/android/wakelock_native_test.cc273
-rw-r--r--gd/os/files.h49
-rw-r--r--gd/os/fuzz/dev_null_queue.h51
-rw-r--r--gd/os/fuzz/fake_timerfd.cc139
-rw-r--r--gd/os/fuzz/fake_timerfd.h41
-rw-r--r--gd/os/fuzz/fuzz_inject_queue.h46
-rw-r--r--gd/os/handler.h47
-rw-r--r--gd/os/host/metrics.cc106
-rw-r--r--gd/os/host/parameter_provider.cc100
-rw-r--r--gd/os/host/system_properties.cc52
-rw-r--r--gd/os/host/system_properties_test.cc44
-rw-r--r--gd/os/host/wakelock_native.cc53
-rw-r--r--gd/os/internal/wakelock_native.h51
-rw-r--r--gd/os/linux/metrics.cc106
-rw-r--r--gd/os/linux/parameter_provider.cc80
-rw-r--r--gd/os/linux/system_properties.cc52
-rw-r--r--gd/os/linux/system_properties_test.cc44
-rw-r--r--gd/os/linux/wakelock_native.cc53
-rw-r--r--gd/os/linux_generic/alarm.cc23
-rw-r--r--gd/os/linux_generic/alarm_unittest.cc8
-rw-r--r--gd/os/linux_generic/files.cc199
-rw-r--r--gd/os/linux_generic/files_test.cc89
-rw-r--r--gd/os/linux_generic/handler.cc7
-rw-r--r--gd/os/linux_generic/handler_unittest.cc10
-rw-r--r--gd/os/linux_generic/linux.h11
-rw-r--r--gd/os/linux_generic/queue.tpp50
-rw-r--r--gd/os/linux_generic/queue_unittest.cc146
-rw-r--r--gd/os/linux_generic/reactive_semaphore.cc2
-rw-r--r--gd/os/linux_generic/reactor.cc67
-rw-r--r--gd/os/linux_generic/reactor_unittest.cc52
-rw-r--r--gd/os/linux_generic/repeating_alarm.cc19
-rw-r--r--gd/os/linux_generic/repeating_alarm_unittest.cc42
-rw-r--r--gd/os/linux_generic/thread.cc7
-rw-r--r--gd/os/linux_generic/thread_unittest.cc7
-rw-r--r--gd/os/linux_generic/wakelock_manager.cc274
-rw-r--r--gd/os/linux_generic/wakelock_manager_unittest.cc192
-rw-r--r--gd/os/log.h88
-rw-r--r--gd/os/metrics.h268
-rw-r--r--gd/os/mock_queue.h100
-rw-r--r--gd/os/parameter_provider.h43
-rw-r--r--gd/os/queue.h36
-rw-r--r--gd/os/queue_benchmark.cc3
-rw-r--r--gd/os/rand.h40
-rw-r--r--gd/os/reactor.h16
-rw-r--r--gd/os/repeating_alarm.h4
-rw-r--r--gd/os/system_properties.h37
-rw-r--r--gd/os/thread_benchmark.cc5
-rw-r--r--gd/os/wakelock_manager.fbs26
-rw-r--r--gd/os/wakelock_manager.h94
-rw-r--r--gd/packet/Android.bp9
-rw-r--r--gd/packet/BUILD.gn32
-rw-r--r--gd/packet/base_packet_builder.h10
-rw-r--r--gd/packet/bit_inserter.h4
-rw-r--r--gd/packet/byte_inserter.h2
-rw-r--r--gd/packet/custom_field_fixed_size_interface.h42
-rw-r--r--gd/packet/endian_inserter.h18
-rw-r--r--gd/packet/iterator.cc18
-rw-r--r--gd/packet/iterator.h25
-rw-r--r--gd/packet/packet_view.h6
-rw-r--r--gd/packet/packet_view_unittest.cc54
-rw-r--r--gd/packet/parser/Android.bp19
-rw-r--r--gd/packet/parser/BUILD.gn87
-rw-r--r--gd/packet/parser/README16
-rw-r--r--gd/packet/parser/bison.gni75
-rw-r--r--gd/packet/parser/custom_field_def.cc8
-rw-r--r--gd/packet/parser/custom_field_def.h2
-rw-r--r--gd/packet/parser/custom_type_checker.h7
-rw-r--r--gd/packet/parser/declarations.h8
-rw-r--r--gd/packet/parser/enum_def.h2
-rw-r--r--gd/packet/parser/enum_gen.cc30
-rw-r--r--gd/packet/parser/enum_gen.h2
-rw-r--r--gd/packet/parser/fields/array_field.cc39
-rw-r--r--gd/packet/parser/fields/array_field.h8
-rw-r--r--gd/packet/parser/fields/body_field.cc26
-rw-r--r--gd/packet/parser/fields/body_field.h14
-rw-r--r--gd/packet/parser/fields/checksum_field.cc10
-rw-r--r--gd/packet/parser/fields/checksum_field.h6
-rw-r--r--gd/packet/parser/fields/checksum_start_field.cc13
-rw-r--r--gd/packet/parser/fields/checksum_start_field.h8
-rw-r--r--gd/packet/parser/fields/count_field.cc6
-rw-r--r--gd/packet/parser/fields/count_field.h2
-rw-r--r--gd/packet/parser/fields/custom_field.cc17
-rw-r--r--gd/packet/parser/fields/custom_field.h10
-rw-r--r--gd/packet/parser/fields/custom_field_fixed_size.cc43
-rw-r--r--gd/packet/parser/fields/custom_field_fixed_size.h10
-rw-r--r--gd/packet/parser/fields/enum_field.cc8
-rw-r--r--gd/packet/parser/fields/enum_field.h4
-rw-r--r--gd/packet/parser/fields/fixed_scalar_field.cc13
-rw-r--r--gd/packet/parser/fields/fixed_scalar_field.h9
-rw-r--r--gd/packet/parser/fields/group_field.cc9
-rw-r--r--gd/packet/parser/fields/group_field.h6
-rw-r--r--gd/packet/parser/fields/packet_field.cc44
-rw-r--r--gd/packet/parser/fields/packet_field.h22
-rw-r--r--gd/packet/parser/fields/padding_field.cc9
-rw-r--r--gd/packet/parser/fields/padding_field.h8
-rw-r--r--gd/packet/parser/fields/payload_field.cc21
-rw-r--r--gd/packet/parser/fields/payload_field.h10
-rw-r--r--gd/packet/parser/fields/reserved_field.cc9
-rw-r--r--gd/packet/parser/fields/reserved_field.h8
-rw-r--r--gd/packet/parser/fields/scalar_field.cc123
-rw-r--r--gd/packet/parser/fields/scalar_field.h17
-rw-r--r--gd/packet/parser/fields/size_field.cc4
-rw-r--r--gd/packet/parser/fields/size_field.h2
-rw-r--r--gd/packet/parser/fields/struct_field.cc26
-rw-r--r--gd/packet/parser/fields/struct_field.h10
-rw-r--r--gd/packet/parser/fields/variable_length_struct_field.cc12
-rw-r--r--gd/packet/parser/fields/variable_length_struct_field.h6
-rw-r--r--gd/packet/parser/fields/vector_field.cc158
-rw-r--r--gd/packet/parser/fields/vector_field.h10
-rw-r--r--gd/packet/parser/flex.gni70
-rw-r--r--gd/packet/parser/gen_cpp.cc411
-rw-r--r--gd/packet/parser/gen_rust.cc168
-rw-r--r--gd/packet/parser/language_l.ll9
-rw-r--r--gd/packet/parser/language_y.yy61
-rw-r--r--gd/packet/parser/main.cc416
-rw-r--r--gd/packet/parser/packet_def.cc771
-rw-r--r--gd/packet/parser/packet_def.h24
-rw-r--r--gd/packet/parser/packetgen.gni194
-rw-r--r--gd/packet/parser/parent_def.cc330
-rw-r--r--gd/packet/parser/parent_def.h30
-rw-r--r--gd/packet/parser/struct_def.cc177
-rw-r--r--gd/packet/parser/struct_def.h12
-rw-r--r--gd/packet/parser/struct_parser_generator.cc8
-rw-r--r--gd/packet/parser/test/Android.bp9
-rw-r--r--gd/packet/parser/test/generated_packet_test.cc134
-rw-r--r--gd/packet/parser/test/six_bytes.cc2
-rw-r--r--gd/packet/parser/test/six_bytes.h19
-rw-r--r--gd/packet/parser/test/test_packets.pdl4
-rw-r--r--gd/packet/parser/test/variable.h4
-rw-r--r--gd/packet/parser/util.h54
-rw-r--r--gd/packet/python3_module.cc32
-rw-r--r--gd/packet/raw_builder.h4
-rw-r--r--gd/proto/Android.bp59
-rw-r--r--gd/proto/BUILD.gn10
-rw-r--r--gd/rust/README.md17
-rw-r--r--gd/rust/common/Android.bp82
-rw-r--r--gd/rust/common/BUILD.gn43
-rw-r--r--gd/rust/common/Cargo.toml34
-rw-r--r--gd/rust/common/src/asserts.rs16
-rw-r--r--gd/rust/common/src/ffi/sys_prop.cc20
-rw-r--r--gd/rust/common/src/ffi/sys_prop.h12
-rw-r--r--gd/rust/common/src/init_flags.rs114
-rw-r--r--gd/rust/common/src/lib.rs52
-rw-r--r--gd/rust/common/src/ready.rs10
-rw-r--r--gd/rust/common/src/sys_prop.rs61
-rw-r--r--gd/rust/common/src/time.rs144
-rw-r--r--gd/rust/facade/Android.bp64
-rw-r--r--gd/rust/facade/BUILD.gn26
-rw-r--r--gd/rust/facade/Cargo.toml48
-rw-r--r--gd/rust/facade/helpers/Cargo.toml38
-rw-r--r--gd/rust/facade/helpers/lib.rs69
-rw-r--r--gd/rust/facade/src/lib.rs161
-rw-r--r--gd/rust/facade/src/main.rs108
-rw-r--r--gd/rust/facade_proto/Cargo.toml34
-rw-r--r--gd/rust/facade_proto/build.rs109
-rw-r--r--gd/rust/facade_proto/src/common.rs20
-rw-r--r--gd/rust/facade_proto/src/lib.rs25
-rw-r--r--gd/rust/gddi/Android.bp30
-rw-r--r--gd/rust/gddi/Cargo.toml31
-rw-r--r--gd/rust/gddi/macros/Cargo.toml28
-rw-r--r--gd/rust/gddi/macros/lib.rs209
-rw-r--r--gd/rust/gddi/src/lib.rs119
-rw-r--r--gd/rust/hal/Android.bp79
-rw-r--r--gd/rust/hal/BUILD.gn27
-rw-r--r--gd/rust/hal/Cargo.toml46
-rw-r--r--gd/rust/hal/src/facade.rs93
-rw-r--r--gd/rust/hal/src/ffi/hidl.cc128
-rw-r--r--gd/rust/hal/src/ffi/hidl.h15
-rw-r--r--gd/rust/hal/src/hidl_hal.rs115
-rw-r--r--gd/rust/hal/src/lib.rs112
-rw-r--r--gd/rust/hal/src/rootcanal_hal.rs163
-rw-r--r--gd/rust/hal/src/snoop.rs315
-rw-r--r--gd/rust/hci/Android.bp44
-rw-r--r--gd/rust/hci/BUILD.gn27
-rw-r--r--gd/rust/hci/Cargo.toml45
-rw-r--r--gd/rust/hci/custom_types/Cargo.toml23
-rw-r--r--gd/rust/hci/custom_types/lib.rs108
-rw-r--r--gd/rust/hci/src/controller.rs328
-rw-r--r--gd/rust/hci/src/controller_facade.rs72
-rw-r--r--gd/rust/hci/src/error.rs24
-rw-r--r--gd/rust/hci/src/facade.rs143
-rw-r--r--gd/rust/hci/src/lib.rs250
-rw-r--r--gd/rust/link/Android.bp37
-rw-r--r--gd/rust/link/Cargo.toml46
-rw-r--r--gd/rust/link/src/acl/classic/facade.rs91
-rw-r--r--gd/rust/link/src/acl/classic/mod.rs296
-rw-r--r--gd/rust/link/src/acl/core.rs182
-rw-r--r--gd/rust/link/src/acl/fragment.rs121
-rw-r--r--gd/rust/link/src/acl/mod.rs16
-rw-r--r--gd/rust/link/src/lib.rs13
-rw-r--r--gd/rust/linux/adapter/Cargo.toml37
-rw-r--r--gd/rust/linux/adapter/build.rs25
-rw-r--r--gd/rust/linux/adapter/src/main.rs182
-rw-r--r--gd/rust/linux/dbus_projection/Cargo.toml7
-rw-r--r--gd/rust/linux/dbus_projection/dbus_macros/Cargo.toml12
-rw-r--r--gd/rust/linux/dbus_projection/dbus_macros/src/lib.rs628
-rw-r--r--gd/rust/linux/dbus_projection/src/lib.rs102
-rw-r--r--gd/rust/linux/mgmt/Cargo.toml22
-rw-r--r--gd/rust/linux/mgmt/src/bin/btmanagerd/main.rs148
-rw-r--r--gd/rust/linux/mgmt/src/bin/btmanagerd/state_machine.rs572
-rw-r--r--gd/rust/linux/service/Cargo.toml26
-rw-r--r--gd/rust/linux/service/build.rs27
-rw-r--r--gd/rust/linux/service/src/dbus_arg.rs3
-rw-r--r--gd/rust/linux/service/src/iface_bluetooth.rs51
-rw-r--r--gd/rust/linux/service/src/iface_bluetooth_gatt.rs73
-rw-r--r--gd/rust/linux/service/src/main.rs100
-rw-r--r--gd/rust/linux/stack/Cargo.toml20
-rw-r--r--gd/rust/linux/stack/btif_macros/Cargo.toml12
-rw-r--r--gd/rust/linux/stack/btif_macros/src/lib.rs136
-rw-r--r--gd/rust/linux/stack/src/bluetooth.rs192
-rw-r--r--gd/rust/linux/stack/src/bluetooth_gatt.rs86
-rw-r--r--gd/rust/linux/stack/src/lib.rs110
-rw-r--r--gd/rust/main/Android.bp24
-rw-r--r--gd/rust/main/Cargo.toml33
-rw-r--r--gd/rust/main/src/lib.rs87
-rw-r--r--gd/rust/packets/Cargo.toml34
-rw-r--r--gd/rust/packets/build.rs60
-rw-r--r--gd/rust/packets/lib.rs11
-rw-r--r--gd/rust/shim/Android.bp158
-rw-r--r--gd/rust/shim/BUILD.gn70
-rw-r--r--gd/rust/shim/Cargo.toml56
-rw-r--r--gd/rust/shim/callbacks/callbacks.cc1
-rw-r--r--gd/rust/shim/callbacks/callbacks.h73
-rw-r--r--gd/rust/shim/src/bridge.rs113
-rw-r--r--gd/rust/shim/src/controller.rs149
-rw-r--r--gd/rust/shim/src/hci.rs89
-rw-r--r--gd/rust/shim/src/init_flags.rs22
-rw-r--r--gd/rust/shim/src/lib.rs10
-rw-r--r--gd/rust/shim/src/message_loop_thread.rs81
-rw-r--r--gd/rust/shim/src/stack.rs74
-rw-r--r--gd/rust/topshim/BUILD.gn56
-rw-r--r--gd/rust/topshim/Cargo.toml47
-rw-r--r--gd/rust/topshim/bindings/wrapper.h3
-rw-r--r--gd/rust/topshim/btif/btif_shim.cc338
-rw-r--r--gd/rust/topshim/btif/btif_shim.h87
-rw-r--r--gd/rust/topshim/src/btif.rs420
-rw-r--r--gd/rust/topshim/src/lib.rs8
-rw-r--r--gd/rust/topshim/src/topstack.rs23
-rw-r--r--gd/security/Android.bp23
-rw-r--r--gd/security/BUILD.gn57
-rw-r--r--gd/security/cert/cert_security.py364
-rw-r--r--gd/security/cert/le_security_test.py1097
-rw-r--r--gd/security/cert/security_test.py547
-rw-r--r--gd/security/cert/simple_security_test.py237
-rw-r--r--gd/security/channel/Android.bp9
-rw-r--r--gd/security/channel/security_manager_channel.cc98
-rw-r--r--gd/security/channel/security_manager_channel.h73
-rw-r--r--gd/security/channel/security_manager_channel_unittest.cc140
-rw-r--r--gd/security/ecdh_keys.cc1
-rw-r--r--gd/security/ecdh_keys.h1
-rw-r--r--gd/security/facade.cc419
-rw-r--r--gd/security/facade.proto132
-rw-r--r--gd/security/facade_configuration_api.cc91
-rw-r--r--gd/security/facade_configuration_api.h70
-rw-r--r--gd/security/initial_informations.h25
-rw-r--r--gd/security/internal/security_manager_impl.cc634
-rw-r--r--gd/security/internal/security_manager_impl.h152
-rw-r--r--gd/security/l2cap_security_module_interface.cc44
-rw-r--r--gd/security/l2cap_security_module_interface.h40
-rw-r--r--gd/security/pairing/Android.bp9
-rw-r--r--gd/security/pairing/classic_pairing_handler.cc473
-rw-r--r--gd/security/pairing/classic_pairing_handler.h87
-rw-r--r--gd/security/pairing/classic_pairing_handler_unittest.cc497
-rw-r--r--gd/security/pairing/oob_data.h52
-rw-r--r--gd/security/pairing/pairing_handler.h30
-rw-r--r--gd/security/pairing_failure.h4
-rw-r--r--gd/security/pairing_handler_le.cc130
-rw-r--r--gd/security/pairing_handler_le.h127
-rw-r--r--gd/security/pairing_handler_le_legacy.cc109
-rw-r--r--gd/security/pairing_handler_le_secure_connections.cc113
-rw-r--r--gd/security/pairing_handler_le_unittest.cc122
-rw-r--r--gd/security/record/Android.bp22
-rw-r--r--gd/security/record/security_record.h85
-rw-r--r--gd/security/record/security_record_database.h81
-rw-r--r--gd/security/record/security_record_storage.cc195
-rw-r--r--gd/security/record/security_record_storage.h76
-rw-r--r--gd/security/record/security_record_storage_test.cc206
-rw-r--r--gd/security/security_manager.cc41
-rw-r--r--gd/security/security_manager.h34
-rw-r--r--gd/security/security_manager_listener.h11
-rw-r--r--gd/security/security_module.cc74
-rw-r--r--gd/security/security_module.h8
-rw-r--r--gd/security/security_record_database.h63
-rw-r--r--gd/security/smp_packets.pdl4
-rw-r--r--gd/security/test/fake_hci_layer.h56
-rw-r--r--gd/security/test/fake_l2cap_test.cc4
-rw-r--r--gd/security/test/fake_name_db.h51
-rw-r--r--gd/security/test/fake_security_interface.h69
-rw-r--r--gd/security/test/fake_storage_module.h42
-rw-r--r--gd/security/test/mocks.h32
-rw-r--r--gd/security/test/pairing_handler_le_pair_test.cc451
-rw-r--r--gd/security/ui.h84
-rw-r--r--gd/setup.py113
-rw-r--r--gd/shim/Android.bp22
-rw-r--r--gd/shim/BUILD.gn31
-rw-r--r--gd/shim/cert/shim_test.py37
-rw-r--r--gd/shim/cert/stack_test.py20
-rw-r--r--gd/shim/dumpsys.cc158
-rw-r--r--gd/shim/dumpsys.fbs25
-rw-r--r--gd/shim/dumpsys.h15
-rw-r--r--gd/shim/dumpsys_args.cc41
-rw-r--r--gd/shim/dumpsys_args.h33
-rw-r--r--gd/shim/dumpsys_args_test.cc48
-rw-r--r--gd/shim/dumpsys_test.cc138
-rw-r--r--gd/shim/facade/facade.cc81
-rw-r--r--gd/shim/facade/facade.h45
-rw-r--r--gd/shim/facade/facade.proto13
-rw-r--r--gd/shim/l2cap.cc717
-rw-r--r--gd/shim/l2cap.h73
-rw-r--r--gd/shim/l2cap_test.cc459
-rw-r--r--gd/shim/only_include_this_file_into_legacy_stack___ever.h (renamed from main/shim/le_scanning_manager.h)21
-rw-r--r--gd/shim/stack.cc125
-rw-r--r--gd/shim/stack.h (renamed from gd/iso/iso_module.h)53
-rw-r--r--gd/shim/test_data/dumpsys_data.bfbsbin736 -> 0 bytes
-rw-r--r--gd/shim/test_data/dumpsys_test_data_binbin884 -> 0 bytes
-rw-r--r--gd/shim/test_data/dumpsys_test_data_bin.h67
-rw-r--r--gd/stack_manager.cc39
-rw-r--r--gd/stack_manager.h6
-rw-r--r--gd/stack_manager_unittest.cc3
-rw-r--r--gd/storage/Android.bp39
-rw-r--r--gd/storage/BUILD.gn32
-rw-r--r--gd/storage/adapter_config.cc26
-rw-r--r--gd/storage/adapter_config.h73
-rw-r--r--gd/storage/adapter_config_test.cc63
-rw-r--r--gd/storage/classic_device.cc55
-rw-r--r--gd/storage/classic_device.h108
-rw-r--r--gd/storage/classic_device_test.cc67
-rw-r--r--gd/storage/config_cache.cc459
-rw-r--r--gd/storage/config_cache.h147
-rw-r--r--gd/storage/config_cache_helper.cc124
-rw-r--r--gd/storage/config_cache_helper.h144
-rw-r--r--gd/storage/config_cache_helper_test.cc136
-rw-r--r--gd/storage/config_cache_test.cc340
-rw-r--r--gd/storage/device.cc121
-rw-r--r--gd/storage/device.h215
-rw-r--r--gd/storage/device_test.cc239
-rw-r--r--gd/storage/le_device.cc56
-rw-r--r--gd/storage/le_device.h107
-rw-r--r--gd/storage/le_device_test.cc67
-rw-r--r--gd/storage/legacy.cc120
-rw-r--r--gd/storage/legacy.h66
-rw-r--r--gd/storage/legacy_config_file.cc86
-rw-r--r--gd/storage/legacy_config_file.h42
-rw-r--r--gd/storage/legacy_config_file_test.cc187
-rw-r--r--gd/storage/legacy_osi_config.cc456
-rw-r--r--gd/storage/legacy_osi_config.h147
-rw-r--r--gd/storage/legacy_test.cc287
-rw-r--r--gd/storage/mutation.cc52
-rw-r--r--gd/storage/mutation.h42
-rw-r--r--gd/storage/mutation_entry.cc53
-rw-r--r--gd/storage/mutation_entry.h124
-rw-r--r--gd/storage/mutation_test.cc125
-rw-r--r--gd/storage/serializable.h55
-rw-r--r--gd/storage/storage_module.cc238
-rw-r--r--gd/storage/storage_module.h153
-rw-r--r--gd/storage/storage_module_test.cc321
-rw-r--r--hci/Android.bp30
-rw-r--r--hci/BUILD.gn75
-rw-r--r--hci/include/bt_hci_bdroid.h1
-rw-r--r--hci/include/btsnoop.h10
-rw-r--r--hci/include/btsnoop_mem.h7
-rw-r--r--hci/include/hci_internals.h30
-rw-r--r--hci/include/hci_layer.h6
-rw-r--r--hci/include/hci_packet_factory.h7
-rw-r--r--hci/include/hci_packet_parser.h16
-rw-r--r--hci/src/btsnoop.cc68
-rw-r--r--hci/src/btsnoop_mem.cc20
-rw-r--r--hci/src/btsnoop_net.cc23
-rw-r--r--hci/src/hci_inject.cc10
-rw-r--r--hci/src/hci_layer.cc112
-rw-r--r--hci/src/hci_layer_android.cc66
-rw-r--r--hci/src/hci_packet_factory.cc30
-rw-r--r--hci/src/hci_packet_parser.cc69
-rw-r--r--hci/src/packet_fragmenter.cc289
-rw-r--r--hci/test/other_stack_stub.cc3
-rw-r--r--hci/test/packet_fragmenter_test.cc409
-rw-r--r--include/Android.bp13
-rw-r--r--include/abstract_message_loop.h85
-rw-r--r--include/abstract_observer_list.h36
-rw-r--r--include/array_utils.h20
-rw-r--r--include/hardware/avrcp/avrcp.h6
-rw-r--r--include/hardware/ble_advertiser.h34
-rw-r--r--include/hardware/ble_scanner.h59
-rw-r--r--include/hardware/bluetooth.h135
-rw-r--r--include/hardware/bluetooth_headset_interface.h18
-rw-r--r--include/hardware/bt_activity_attribution.h76
-rw-r--r--include/hardware/bt_av.h13
-rw-r--r--include/hardware/bt_common_types.h3
-rw-r--r--include/hardware/bt_gatt_client.h7
-rw-r--r--include/hardware/bt_gatt_server.h3
-rw-r--r--include/hardware/bt_hearing_aid.h4
-rw-r--r--include/hardware/bt_hf_client.h2
-rw-r--r--include/hardware/bt_hh.h34
-rw-r--r--include/hardware/bt_le_audio.h94
-rw-r--r--include/hardware/bt_mce.h54
-rw-r--r--include/hardware/bt_sdp.h14
-rw-r--r--include/hardware/bt_sock.h6
-rw-r--r--include/hardware/bt_vc.h76
-rw-r--r--internal_include/Android.bp9
-rw-r--r--internal_include/bt_target.h250
-rw-r--r--internal_include/bt_trace.h53
-rw-r--r--internal_include/bte.h2
-rw-r--r--main/Android.bp126
-rw-r--r--main/BUILD.gn131
-rw-r--r--main/bte_conf.cc33
-rw-r--r--main/bte_init.cc103
-rw-r--r--main/bte_logmsg.cc32
-rw-r--r--main/bte_main.cc129
-rw-r--r--main/shim/Android.bp23
-rw-r--r--main/shim/BUILD.gn66
-rw-r--r--main/shim/acl.cc1471
-rw-r--r--main/shim/acl.h121
-rw-r--r--main/shim/acl_api.cc106
-rw-r--r--main/shim/acl_api.h43
-rw-r--r--main/shim/acl_legacy_interface.cc86
-rw-r--r--main/shim/acl_legacy_interface.h146
-rw-r--r--main/shim/activity_attribution.cc88
-rw-r--r--main/shim/activity_attribution.h34
-rw-r--r--main/shim/btm.cc747
-rw-r--r--main/shim/btm.h164
-rw-r--r--main/shim/btm_api.cc951
-rw-r--r--main/shim/btm_api.h594
-rw-r--r--main/shim/config.cc201
-rw-r--r--main/shim/config.h39
-rw-r--r--main/shim/controller.cc415
-rw-r--r--main/shim/dumpsys.cc37
-rw-r--r--main/shim/dumpsys.h33
-rw-r--r--main/shim/entry.cc152
-rw-r--r--main/shim/entry.h28
-rw-r--r--main/shim/hci_layer.cc784
-rw-r--r--main/shim/hci_layer.h6
-rw-r--r--main/shim/helpers.h241
-rw-r--r--main/shim/l2c_api.cc1683
-rw-r--r--main/shim/l2c_api.h301
-rw-r--r--main/shim/l2cap.cc420
-rw-r--r--main/shim/l2cap.h126
-rw-r--r--main/shim/le_advertising_manager.cc365
-rw-r--r--main/shim/le_advertising_manager.h32
-rw-r--r--main/shim/le_scanning_manager.cc513
-rw-r--r--main/shim/link_connection_interface.h48
-rw-r--r--main/shim/link_policy.cc290
-rw-r--r--main/shim/link_policy.h50
-rw-r--r--main/shim/link_policy_interface.h39
-rw-r--r--main/shim/metric_id_api.cc79
-rw-r--r--main/shim/metric_id_api.h90
-rw-r--r--main/shim/metrics_api.cc139
-rw-r--r--main/shim/metrics_api.h212
-rw-r--r--main/shim/shim.cc98
-rw-r--r--main/shim/shim.h19
-rw-r--r--main/shim/stack.cc275
-rw-r--r--main/shim/stack.h85
-rw-r--r--main/shim/timer.cc59
-rw-r--r--main/shim/timer.h74
-rw-r--r--main/stack_config.cc6
-rw-r--r--main/test/main_shim_test.cc420
-rw-r--r--osi/Android.bp10
-rw-r--r--osi/BUILD.gn88
-rw-r--r--osi/include/compat.h2
-rw-r--r--osi/include/log.h69
-rw-r--r--osi/include/osi.h4
-rw-r--r--osi/src/alarm.cc58
-rw-r--r--osi/src/allocation_tracker.cc5
-rw-r--r--osi/src/array.cc8
-rw-r--r--osi/src/compat.cc2
-rw-r--r--osi/src/future.cc3
-rw-r--r--osi/src/hash_map_utils.cc7
-rw-r--r--osi/src/osi.cc2
-rw-r--r--osi/src/properties.cc2
-rw-r--r--osi/src/reactor.cc27
-rw-r--r--osi/src/semaphore.cc19
-rw-r--r--osi/src/socket.cc15
-rw-r--r--osi/src/thread.cc19
-rw-r--r--osi/src/wakelock.cc35
-rw-r--r--osi/test/alarm_test.cc7
-rw-r--r--osi/test/fuzzers/Android.bp17
-rw-r--r--osi/test/fuzzers/alarm/Android.bp30
-rw-r--r--osi/test/fuzzers/alarm/fuzz_alarm.cc151
-rw-r--r--osi/test/fuzzers/allocation_tracker/Android.bp26
-rw-r--r--osi/test/fuzzers/allocation_tracker/corpus/checkfail-regression-1568055801
-rw-r--r--osi/test/fuzzers/allocation_tracker/fuzz_allocation_tracker.cc142
-rw-r--r--osi/test/fuzzers/allocator/Android.bp21
-rw-r--r--osi/test/fuzzers/allocator/fuzz_allocator.cc119
-rw-r--r--osi/test/fuzzers/array/Android.bp23
-rw-r--r--osi/test/fuzzers/array/fuzz_array.cc61
-rw-r--r--osi/test/fuzzers/buffer/Android.bp23
-rw-r--r--osi/test/fuzzers/buffer/fuzz_buffer.cc70
-rw-r--r--osi/test/fuzzers/compat/Android.bp24
-rw-r--r--osi/test/fuzzers/compat/fuzz_compat.cc62
-rw-r--r--osi/test/fuzzers/fixed_queue/Android.bp24
-rw-r--r--osi/test/fuzzers/fixed_queue/fuzz_fixed_queue.cc240
-rw-r--r--osi/test/fuzzers/future/Android.bp24
-rw-r--r--osi/test/fuzzers/future/fuzz_future.cc58
-rw-r--r--osi/test/fuzzers/include/libosiFuzzHelperFunctions.h45
-rw-r--r--osi/test/fuzzers/list/Android.bp21
-rw-r--r--osi/test/fuzzers/list/fuzz_list.cc277
-rw-r--r--osi/test/fuzzers/ringbuffer/Android.bp21
-rw-r--r--osi/test/fuzzers/ringbuffer/fuzz_ringbuffer.cc167
-rw-r--r--osi/test/properties_test.cc6
-rw-r--r--packet/Android.bp16
-rw-r--r--packet/BUILD.gn67
-rw-r--r--packet/avrcp/Android.bp13
-rw-r--r--packet/base/Android.bp13
-rw-r--r--packet/base/packet.h3
-rw-r--r--packet/tests/avrcp/avrcp_test_packets.h29
-rw-r--r--packet/tests/fuzzers/Android.bp757
-rw-r--r--packet/tests/fuzzers/avrcp_browse_packet_fuzzer.cc51
-rw-r--r--packet/tests/fuzzers/avrcp_packet_fuzzer.cc87
-rw-r--r--packet/tests/fuzzers/change_path_req_fuzzer.cc55
-rw-r--r--packet/tests/fuzzers/change_path_res_fuzzer.cc47
-rw-r--r--packet/tests/fuzzers/corpus/avrcp_browse_packet_corpus/validpacketbin25 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/avrcp_packet_corpus/validpacketbin10 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/avrcp_test_packets_corpus/validpacketbin14 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/change_path_packet_corpus/validpacketbin14 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/generate_corpus.sh52
-rw-r--r--packet/tests/fuzzers/corpus/get_capabilities_packet_corpus/validpacketbin14 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/get_item_attributes_packet_corpus/validpacketbin43 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/get_play_status_packet_corpus/validpacketbin10 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/get_total_number_of_items_corpus/validpacketbin3 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/pass_through_packet_corpus/validpacketbin5 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/play_item_packet_corpus/validpacketbin21 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/register_notification_packet_corpus/validpacketbin14 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/set_absolute_volume_packet_corpus/validpacketbin11 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/set_addressed_player_packet_corpus/validpacketbin10 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/set_browsed_player_packet_corpus/validpacketbin5 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/corpus/vendor_packet_corpus/validpacketbin10 -> 0 bytes
-rw-r--r--packet/tests/fuzzers/get_capabilities_req_fuzzer.cc52
-rw-r--r--packet/tests/fuzzers/get_capabilities_res_fuzzer.cc46
-rw-r--r--packet/tests/fuzzers/get_element_attributes_req_packet_fuzzer.cc49
-rw-r--r--packet/tests/fuzzers/get_element_attributes_res_packet_fuzzer.cc49
-rw-r--r--packet/tests/fuzzers/get_folder_items_req_fuzzer.cc52
-rw-r--r--packet/tests/fuzzers/get_folder_items_res_fuzzer.cc71
-rw-r--r--packet/tests/fuzzers/get_item_attributes_req_fuzzer.cc47
-rw-r--r--packet/tests/fuzzers/get_item_attributes_res_fuzzer.cc48
-rw-r--r--packet/tests/fuzzers/get_play_status_req_fuzzer.cc44
-rw-r--r--packet/tests/fuzzers/get_play_status_res_fuzzer.cc42
-rw-r--r--packet/tests/fuzzers/get_total_number_of_items_req_fuzzer.cc51
-rw-r--r--packet/tests/fuzzers/get_total_number_of_items_res_fuzzer.cc46
-rw-r--r--packet/tests/fuzzers/pass_through_packet_fuzzer.cc57
-rw-r--r--packet/tests/fuzzers/play_item_packet_fuzzer.cc55
-rw-r--r--packet/tests/fuzzers/register_notification_packet_fuzzer.cc58
-rw-r--r--packet/tests/fuzzers/reject_packet_fuzzer.cc49
-rw-r--r--packet/tests/fuzzers/set_absolute_volume_packet_fuzzer.cc52
-rw-r--r--packet/tests/fuzzers/set_addressed_player_packet_fuzzer.cc47
-rw-r--r--packet/tests/fuzzers/set_browsed_player_req_fuzzer.cc52
-rw-r--r--packet/tests/fuzzers/set_browsed_player_res_fuzzer.cc49
-rw-r--r--packet/tests/fuzzers/vendor_packet_fuzzer.cc65
-rw-r--r--profile/avrcp/Android.bp23
-rw-r--r--profile/avrcp/BUILD.gn49
-rw-r--r--profile/avrcp/avrcp_config.h52
-rw-r--r--profile/avrcp/avrcp_internal.h8
-rw-r--r--profile/avrcp/avrcp_message_converter.h4
-rw-r--r--profile/avrcp/connection_handler.cc66
-rw-r--r--profile/avrcp/connection_handler.h8
-rw-r--r--profile/avrcp/device.cc64
-rw-r--r--profile/avrcp/device.h11
-rw-r--r--profile/avrcp/tests/avrcp_connection_handler_test.cc1
-rw-r--r--profile/avrcp/tests/avrcp_device_test.cc236
-rw-r--r--profile/avrcp/tests/avrcp_test_helper.h6
-rw-r--r--profile/sdp/Android.bp9
-rw-r--r--proto/Android.bp24
-rw-r--r--proto/bluetooth/bluetoothKeystore/keystore.proto (renamed from gd/proto/bluetooth/bluetoothKeystore/keystore.proto)4
-rw-r--r--proto/bluetooth/metrics/bluetooth.proto (renamed from gd/proto/bluetooth/metrics/bluetooth.proto)11
-rw-r--r--rustfmt.toml1
-rw-r--r--service/Android.bp12
-rw-r--r--service/BUILD.gn170
-rw-r--r--service/adapter.cc14
-rw-r--r--service/avrcp_target.cc3
-rw-r--r--service/common/Android.bp9
-rw-r--r--service/common/BUILD.gn42
-rw-r--r--service/common/android/bluetooth/scan_filter.cc17
-rw-r--r--service/daemon.cc7
-rw-r--r--service/daemon.h4
-rw-r--r--service/example/heart_rate/server_main.cc4
-rw-r--r--service/gatt_client.cc3
-rw-r--r--service/gatt_server.cc3
-rw-r--r--service/gatt_server_old.cc98
-rw-r--r--service/hal/bluetooth_av_interface.cc24
-rw-r--r--service/hal/bluetooth_avrcp_interface.cc17
-rw-r--r--service/hal/bluetooth_gatt_interface.cc26
-rw-r--r--service/hal/bluetooth_interface.cc49
-rw-r--r--service/hal/bluetooth_interface.h7
-rw-r--r--service/hal/fake_bluetooth_av_interface.cc3
-rw-r--r--service/hal/fake_bluetooth_av_interface.h5
-rw-r--r--service/hal/fake_bluetooth_gatt_interface.cc12
-rw-r--r--service/hal/fake_bluetooth_gatt_interface.h13
-rw-r--r--service/hal/fake_bluetooth_interface.cc7
-rw-r--r--service/hal/fake_bluetooth_interface.h6
-rw-r--r--service/ipc/binder/ipc_handler_binder.cc4
-rw-r--r--service/ipc/dbus/bluetooth_adapter.cc28
-rw-r--r--service/ipc/dbus/ipc_handler_dbus.cc2
-rw-r--r--service/ipc/ipc_handler_linux.cc9
-rw-r--r--service/ipc/linux_ipc_host.cc23
-rw-r--r--service/logging_helpers.cc8
-rw-r--r--service/low_energy_client.cc8
-rw-r--r--service/low_energy_scanner.cc6
-rw-r--r--service/settings.cc9
-rw-r--r--service/test/adapter_unittest.cc9
-rw-r--r--service/test/advertise_data_unittest.cc12
-rw-r--r--service/test/gatt_client_unittest.cc7
-rw-r--r--service/test/gatt_server_unittest.cc9
-rw-r--r--service/test/ipc_linux_unittest.cc12
-rw-r--r--service/test/low_energy_advertiser_unittest.cc16
-rw-r--r--service/test/low_energy_client_unittest.cc10
-rw-r--r--service/test/low_energy_scanner_unittest.cc20
-rw-r--r--service/test/mock_daemon.h3
-rw-r--r--service/test/settings_unittest.cc17
-rw-r--r--stack/Android.bp588
-rw-r--r--stack/BUILD.gn427
-rw-r--r--stack/a2dp/a2dp_aac.cc195
-rw-r--r--stack/a2dp/a2dp_aac_decoder.cc6
-rw-r--r--stack/a2dp/a2dp_aac_encoder.cc267
-rw-r--r--stack/a2dp/a2dp_api.cc32
-rw-r--r--stack/a2dp/a2dp_codec_config.cc207
-rw-r--r--stack/a2dp/a2dp_sbc.cc142
-rw-r--r--stack/a2dp/a2dp_sbc_decoder.cc7
-rw-r--r--stack/a2dp/a2dp_sbc_encoder.cc227
-rw-r--r--stack/a2dp/a2dp_vendor_aptx.cc58
-rw-r--r--stack/a2dp/a2dp_vendor_aptx_encoder.cc52
-rw-r--r--stack/a2dp/a2dp_vendor_aptx_hd.cc60
-rw-r--r--stack/a2dp/a2dp_vendor_aptx_hd_encoder.cc54
-rw-r--r--stack/a2dp/a2dp_vendor_ldac.cc72
-rw-r--r--stack/a2dp/a2dp_vendor_ldac_abr.cc17
-rw-r--r--stack/a2dp/a2dp_vendor_ldac_decoder.cc28
-rw-r--r--stack/a2dp/a2dp_vendor_ldac_encoder.cc131
-rw-r--r--stack/acl/acl.cc72
-rw-r--r--stack/acl/acl.h423
-rw-r--r--stack/acl/ble_acl.cc173
-rw-r--r--stack/acl/btm_acl.cc2966
-rw-r--r--stack/acl/btm_pm.cc919
-rw-r--r--stack/acl/peer_packet_types.h71
-rw-r--r--stack/avct/avct_api.cc46
-rw-r--r--stack/avct/avct_bcb_act.cc17
-rw-r--r--stack/avct/avct_int.h12
-rw-r--r--stack/avct/avct_l2c.cc158
-rw-r--r--stack/avct/avct_l2c_br.cc210
-rw-r--r--stack/avct/avct_lcb.cc1
-rw-r--r--stack/avct/avct_lcb_act.cc17
-rw-r--r--stack/avdt/avdt_ad.cc35
-rw-r--r--stack/avdt/avdt_api.cc280
-rw-r--r--stack/avdt/avdt_ccb_act.cc19
-rw-r--r--stack/avdt/avdt_defs.h19
-rw-r--r--stack/avdt/avdt_int.h37
-rw-r--r--stack/avdt/avdt_l2c.cc221
-rw-r--r--stack/avdt/avdt_msg.cc8
-rw-r--r--stack/avdt/avdt_scb.cc77
-rw-r--r--stack/avdt/avdt_scb_act.cc48
-rw-r--r--stack/avrc/avrc_api.cc40
-rw-r--r--stack/avrc/avrc_bld_ct.cc2
-rw-r--r--stack/avrc/avrc_bld_tg.cc2
-rw-r--r--stack/avrc/avrc_int.h4
-rw-r--r--stack/avrc/avrc_opt.cc6
-rw-r--r--stack/avrc/avrc_pars_ct.cc8
-rw-r--r--stack/avrc/avrc_pars_tg.cc10
-rw-r--r--stack/avrc/avrc_sdp.cc96
-rw-r--r--stack/bnep/bnep_api.cc65
-rw-r--r--stack/bnep/bnep_int.h26
-rw-r--r--stack/bnep/bnep_main.cc196
-rw-r--r--stack/bnep/bnep_utils.cc69
-rw-r--r--stack/btm/ble_advertiser_hci_interface.cc3
-rw-r--r--stack/btm/ble_scanner_hci_interface.cc428
-rw-r--r--stack/btm/ble_scanner_hci_interface.h230
-rw-r--r--stack/btm/btm_acl.cc2594
-rw-r--r--stack/btm/btm_ble.cc796
-rw-r--r--stack/btm/btm_ble_addr.cc257
-rw-r--r--stack/btm/btm_ble_adv_filter.cc255
-rw-r--r--stack/btm/btm_ble_batchscan.cc25
-rw-r--r--stack/btm/btm_ble_bgconn.cc535
-rw-r--r--stack/btm/btm_ble_bgconn.h15
-rw-r--r--stack/btm/btm_ble_connection_establishment.cc (renamed from stack/acl/btm_ble_connection_establishment.cc)200
-rw-r--r--stack/btm/btm_ble_cont_energy.cc15
-rw-r--r--stack/btm/btm_ble_gap.cc925
-rw-r--r--stack/btm/btm_ble_int.h92
-rw-r--r--stack/btm/btm_ble_int_types.h207
-rw-r--r--stack/btm/btm_ble_multi_adv.cc10
-rw-r--r--stack/btm/btm_ble_privacy.cc157
-rw-r--r--stack/btm/btm_client_interface.cc183
-rw-r--r--stack/btm/btm_dev.cc119
-rw-r--r--stack/btm/btm_dev.h194
-rw-r--r--stack/btm/btm_devctl.cc382
-rw-r--r--stack/btm/btm_inq.cc838
-rw-r--r--stack/btm/btm_int.h288
-rw-r--r--stack/btm/btm_int_types.h954
-rw-r--r--stack/btm/btm_iso.cc144
-rw-r--r--stack/btm/btm_iso_impl.h706
-rw-r--r--stack/btm/btm_main.cc79
-rw-r--r--stack/btm/btm_pm.cc962
-rw-r--r--stack/btm/btm_scn.cc91
-rw-r--r--stack/btm/btm_scn.h23
-rw-r--r--stack/btm/btm_sco.cc622
-rw-r--r--stack/btm/btm_sco.h134
-rw-r--r--stack/btm/btm_sec.cc2363
-rw-r--r--stack/btm/btm_sec.h800
-rw-r--r--stack/btm/neighbor_inquiry.h257
-rw-r--r--stack/btm/security_device_record.h439
-rw-r--r--stack/btu/btu_hcif.cc881
-rw-r--r--stack/btu/btu_init.cc125
-rw-r--r--stack/btu/btu_task.cc64
-rw-r--r--stack/crypto_toolbox/crypto_toolbox.h3
-rw-r--r--stack/eatt/eatt.cc207
-rw-r--r--stack/eatt/eatt.h284
-rw-r--r--stack/eatt/eatt_impl.h672
-rw-r--r--stack/gap/gap_ble.cc56
-rw-r--r--stack/gap/gap_conn.cc279
-rw-r--r--stack/gatt/att_protocol.cc154
-rw-r--r--stack/gatt/connection_manager.cc86
-rw-r--r--stack/gatt/connection_manager.h2
-rw-r--r--stack/gatt/gatt_api.cc211
-rw-r--r--stack/gatt/gatt_attr.cc656
-rw-r--r--stack/gatt/gatt_auth.cc45
-rw-r--r--stack/gatt/gatt_cl.cc285
-rw-r--r--stack/gatt/gatt_db.cc102
-rw-r--r--stack/gatt/gatt_int.h254
-rw-r--r--stack/gatt/gatt_main.cc311
-rw-r--r--stack/gatt/gatt_sr.cc576
-rw-r--r--stack/gatt/gatt_sr_hash.cc128
-rw-r--r--stack/gatt/gatt_utils.cc423
-rw-r--r--stack/hcic/hciblecmds.cc544
-rw-r--r--stack/hcic/hcicmds.cc650
-rw-r--r--stack/hid/hid_conn.h44
-rw-r--r--stack/hid/hidd_api.cc45
-rw-r--r--stack/hid/hidd_conn.cc343
-rw-r--r--stack/hid/hidd_int.h9
-rw-r--r--stack/hid/hidh_api.cc100
-rw-r--r--stack/hid/hidh_conn.cc442
-rw-r--r--stack/hid/hidh_int.h12
-rw-r--r--stack/include/a2dp_aac_encoder.h21
-rw-r--r--stack/include/a2dp_sbc_constants.h1
-rw-r--r--stack/include/acl_api.h316
-rw-r--r--stack/include/acl_api_types.h91
-rw-r--r--stack/include/acl_client_callbacks.h36
-rw-r--r--stack/include/acl_hci_link_interface.h80
-rw-r--r--stack/include/avct_api.h2
-rw-r--r--stack/include/avdt_api.h139
-rw-r--r--stack/include/avrc_api.h61
-rw-r--r--stack/include/avrc_defs.h72
-rw-r--r--stack/include/ble_acl_interface.h41
-rw-r--r--stack/include/ble_hci_link_interface.h52
-rw-r--r--stack/include/bnep_api.h38
-rw-r--r--stack/include/bt_types.h564
-rw-r--r--stack/include/btm_api.h997
-rwxr-xr-x[-rw-r--r--]stack/include/btm_api_types.h1262
-rw-r--r--stack/include/btm_ble_api.h227
-rw-r--r--stack/include/btm_ble_api_types.h231
-rw-r--r--stack/include/btm_client_interface.h228
-rw-r--r--stack/include/btm_iso_api.h239
-rw-r--r--stack/include/btm_iso_api_types.h159
-rw-r--r--stack/include/btm_log_history.h31
-rw-r--r--stack/include/btm_status.h94
-rw-r--r--stack/include/btu.h11
-rw-r--r--stack/include/dev_hci_link_interface.h30
-rw-r--r--stack/include/gap_api.h120
-rw-r--r--stack/include/gatt_api.h367
-rw-r--r--stack/include/gattdefs.h7
-rw-r--r--stack/include/hci_error_code.h177
-rw-r--r--stack/include/hci_evt_length.h11
-rw-r--r--stack/include/hcidefs.h716
-rw-r--r--stack/include/hcimsgs.h688
-rw-r--r--stack/include/hidd_api.h11
-rw-r--r--stack/include/hiddefs.h41
-rw-r--r--stack/include/hidh_api.h27
-rw-r--r--stack/include/inq_hci_link_interface.h36
-rw-r--r--stack/include/l2c_api.h480
-rw-r--r--stack/include/l2cap_acl_interface.h49
-rw-r--r--stack/include/l2cap_controller_interface.h30
-rw-r--r--stack/include/l2cap_hci_link_interface.h62
-rw-r--r--stack/include/l2cap_security_interface.h38
-rw-r--r--stack/include/l2cdefs.h182
-rw-r--r--stack/include/ldacBT_bco_for_fluoride.h2
-rw-r--r--stack/include/pan_api.h7
-rw-r--r--stack/include/port_api.h9
-rw-r--r--stack/include/sco_client_callbacks.h25
-rw-r--r--stack/include/sco_hci_link_interface.h44
-rw-r--r--stack/include/sdp_api.h95
-rw-r--r--stack/include/sdpdefs.h100
-rw-r--r--stack/include/sec_hci_link_interface.h49
-rw-r--r--stack/include/security_client_callbacks.h78
-rw-r--r--stack/include/smp_api.h30
-rw-r--r--stack/include/smp_api_types.h242
-rw-r--r--stack/include/srvc_api.h5
-rw-r--r--stack/include/stack_metrics_logging.h49
-rw-r--r--stack/l2cap/l2c_api.cc1103
-rw-r--r--stack/l2cap/l2c_ble.cc756
-rw-r--r--stack/l2cap/l2c_csm.cc909
-rw-r--r--stack/l2cap/l2c_fcr.cc695
-rw-r--r--stack/l2cap/l2c_int.h549
-rw-r--r--stack/l2cap/l2c_link.cc987
-rw-r--r--stack/l2cap/l2c_main.cc258
-rw-r--r--stack/l2cap/l2c_utils.cc1267
-rw-r--r--stack/metrics/stack_metrics_logging.cc97
-rw-r--r--stack/pan/pan_api.cc89
-rw-r--r--stack/pan/pan_int.h11
-rw-r--r--stack/pan/pan_main.cc100
-rw-r--r--stack/pan/pan_utils.cc42
-rw-r--r--stack/rfcomm/port_api.cc22
-rw-r--r--stack/rfcomm/port_int.h16
-rw-r--r--stack/rfcomm/port_rfc.cc3
-rw-r--r--stack/rfcomm/port_utils.cc4
-rw-r--r--stack/rfcomm/rfc_int.h80
-rw-r--r--stack/rfcomm/rfc_l2cap_if.cc108
-rw-r--r--stack/rfcomm/rfc_mx_fsm.cc148
-rw-r--r--stack/rfcomm/rfc_port_fsm.cc40
-rw-r--r--stack/rfcomm/rfc_port_if.cc2
-rw-r--r--stack/rfcomm/rfc_ts_frames.cc3
-rw-r--r--stack/rfcomm/rfc_utils.cc3
-rw-r--r--stack/sdp/sdp_api.cc12
-rw-r--r--stack/sdp/sdp_db.cc68
-rw-r--r--stack/sdp/sdp_discovery.cc23
-rw-r--r--stack/sdp/sdp_main.cc326
-rw-r--r--stack/sdp/sdp_server.cc22
-rw-r--r--stack/sdp/sdp_utils.cc76
-rw-r--r--stack/sdp/sdpint.h16
-rw-r--r--stack/smp/smp_act.cc319
-rw-r--r--stack/smp/smp_api.cc131
-rw-r--r--stack/smp/smp_br_main.cc107
-rw-r--r--stack/smp/smp_int.h267
-rw-r--r--stack/smp/smp_keys.cc116
-rw-r--r--stack/smp/smp_l2c.cc82
-rw-r--r--stack/smp/smp_main.cc289
-rw-r--r--stack/smp/smp_utils.cc109
-rw-r--r--stack/srvc/srvc_dis.cc2
-rw-r--r--stack/srvc/srvc_eng.cc8
-rw-r--r--stack/test/ble_advertiser_test.cc6
-rw-r--r--stack/test/btm/peer_packet_types_test.cc86
-rw-r--r--stack/test/btm/stack_btm_test.cc185
-rw-r--r--stack/test/btm_iso_test.cc2314
-rw-r--r--stack/test/common/mock_acl.cc50
-rw-r--r--stack/test/common/mock_bta_dm_act.cc123
-rw-r--r--stack/test/common/mock_bta_sys_conn.cc96
-rw-r--r--stack/test/common/mock_btif_dm.cc163
-rw-r--r--stack/test/common/mock_btm_api_layer.cc33
-rw-r--r--stack/test/common/mock_btm_api_layer.h55
-rw-r--r--stack/test/common/mock_btm_layer.cc32
-rw-r--r--stack/test/common/mock_btm_layer.h5
-rw-r--r--stack/test/common/mock_btsnoop_module.cc12
-rw-r--r--stack/test/common/mock_btu_layer.cc4
-rw-r--r--stack/test/common/mock_controller.cc48
-rw-r--r--stack/test/common/mock_controller.h43
-rw-r--r--stack/test/common/mock_eatt.cc143
-rw-r--r--stack/test/common/mock_eatt.h70
-rw-r--r--stack/test/common/mock_gap_gap_ble.cc50
-rw-r--r--stack/test/common/mock_gatt_connection_manager.cc59
-rw-r--r--stack/test/common/mock_gatt_layer.cc39
-rw-r--r--stack/test/common/mock_gatt_layer.h54
-rw-r--r--stack/test/common/mock_gatt_main.cc111
-rw-r--r--stack/test/common/mock_hci_packet_parser.cc41
-rw-r--r--stack/test/common/mock_hcic_layer.cc114
-rw-r--r--stack/test/common/mock_hcic_layer.h121
-rw-r--r--stack/test/common/mock_l2cap_layer.cc40
-rw-r--r--stack/test/common/mock_l2cap_layer.h30
-rw-r--r--stack/test/common/mock_main_bte_main.cc48
-rw-r--r--stack/test/common/mock_main_shim.cc93
-rw-r--r--stack/test/common/mock_main_shim_btm_api.cc465
-rw-r--r--stack/test/common/mock_main_shim_controller.cc36
-rw-r--r--stack/test/common/mock_main_shim_l2c_api.cc230
-rw-r--r--stack/test/common/mock_main_shim_link_policy.cc45
-rw-r--r--stack/test/common/mock_smp_smp_act.cc252
-rw-r--r--stack/test/common/mock_smp_smp_api.cc88
-rw-r--r--stack/test/common/mock_stack_avdt_msg.cc81
-rw-r--r--stack/test/common/mock_stack_avdt_msg.h61
-rw-r--r--stack/test/common/mock_stack_l2cap_link.cc96
-rw-r--r--stack/test/eatt/eatt_test.cc443
-rw-r--r--stack/test/fuzzers/Android.bp62
-rw-r--r--stack/test/fuzzers/a2dp/Android.bp16
-rw-r--r--stack/test/fuzzers/a2dp/a2dpFuzzFunctions.h90
-rw-r--r--stack/test/fuzzers/a2dp/a2dpFuzzHelpers.h64
-rw-r--r--stack/test/fuzzers/a2dp/codec/Android.bp41
-rw-r--r--stack/test/fuzzers/a2dp/codec/a2dpCodecConfigFuzzFunctions.h227
-rw-r--r--stack/test/fuzzers/a2dp/codec/a2dpCodecConfigFuzzHelpers.h40
-rw-r--r--stack/test/fuzzers/a2dp/codec/a2dpCodecFuzzFunctions.h341
-rw-r--r--stack/test/fuzzers/a2dp/codec/a2dpCodecFuzzHelpers.h46
-rw-r--r--stack/test/fuzzers/a2dp/codec/a2dpCodecHelperFunctions.h171
-rw-r--r--stack/test/fuzzers/a2dp/codec/a2dpCodecInfoFuzzFunctions.h215
-rw-r--r--stack/test/fuzzers/a2dp/codec/a2dpCodecInfoFuzzHelpers.h63
-rw-r--r--stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec.cc34
-rw-r--r--stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec_config.cc34
-rw-r--r--stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec_info.cc34
-rw-r--r--stack/test/fuzzers/a2dp/fuzz_a2dp.cc38
-rw-r--r--stack/test/fuzzers/common/commonFuzzHelpers.h77
-rw-r--r--stack/test/fuzzers/sdp/Android.bp16
-rw-r--r--stack/test/fuzzers/sdp/fuzz_sdp.cc36
-rw-r--r--stack/test/fuzzers/sdp/sdpFuzzFunctions.h331
-rw-r--r--stack/test/fuzzers/sdp/sdpFuzzHelpers.h273
-rw-r--r--stack/test/gatt/gatt_sr_test.cc365
-rw-r--r--stack/test/gatt/mock_gatt_utils_ref.cc102
-rw-r--r--stack/test/gatt/stack_gatt_test.cc141
-rw-r--r--stack/test/gatt_connection_manager_test.cc148
-rw-r--r--stack/test/hci/stack_hci_test.cc133
-rw-r--r--stack/test/hid/stack_hid_test.cc77
-rw-r--r--stack/test/rfcomm/stack_rfcomm_test.cc11
-rw-r--r--stack/test/stack_a2dp_test.cc175
-rw-r--r--stack/test/stack_avdtp_test.cc182
-rw-r--r--stack/test/stack_btu_test.cc135
-rw-r--r--stack/test/stack_gatt_sr_hash_test.cc89
-rw-r--r--stack/test/stack_smp_test.cc13
-rw-r--r--test/Android.bp219
-rw-r--r--test/common/main_handler.cc63
-rw-r--r--test/common/main_handler.h36
-rwxr-xr-xtest/gen_coverage.py69
-rw-r--r--test/headless/Android.bp21
-rw-r--r--test/headless/README.md24
-rw-r--r--test/headless/connect/connect.cc134
-rw-r--r--test/headless/connect/connect.h35
-rw-r--r--test/headless/dumpsys/dumpsys.cc39
-rw-r--r--test/headless/dumpsys/dumpsys.h35
-rw-r--r--test/headless/get_options.cc68
-rw-r--r--test/headless/get_options.h11
-rw-r--r--test/headless/headless.cc101
-rw-r--r--test/headless/headless.h20
-rw-r--r--test/headless/interface.h36
-rw-r--r--test/headless/main.cc35
-rw-r--r--test/headless/pairing/pairing.cc11
-rw-r--r--test/headless/sdp/sdp.cc3
-rw-r--r--test/mock/mock_a2dp_api.cc67
-rw-r--r--test/mock/mock_a2dp_codec_config.cc351
-rw-r--r--test/mock/mock_activity_attribution.cc35
-rw-r--r--test/mock/mock_android_hardware_audio.cc61
-rw-r--r--test/mock/mock_bta_ag_api.cc67
-rw-r--r--test/mock/mock_bta_ar.cc55
-rw-r--r--test/mock/mock_bta_av_api.cc105
-rw-r--r--test/mock/mock_bta_av_ci.cc42
-rw-r--r--test/mock/mock_bta_av_main.cc102
-rw-r--r--test/mock/mock_bta_dm_act.cc164
-rw-r--r--test/mock/mock_bta_dm_api.cc145
-rw-r--r--test/mock/mock_bta_gattc_api.cc167
-rw-r--r--test/mock/mock_bta_gatts_api.cc85
-rw-r--r--test/mock/mock_bta_hd_api.cc60
-rw-r--r--test/mock/mock_bta_hearing_aid.cc74
-rw-r--r--test/mock/mock_bta_hf_client_api.cc62
-rw-r--r--test/mock/mock_bta_hh_api.cc82
-rw-r--r--test/mock/mock_bta_jv_api.cc146
-rw-r--r--test/mock/mock_bta_pan_api.cc48
-rw-r--r--test/mock/mock_bta_pan_ci.cc67
-rw-r--r--test/mock/mock_bta_sdp_api.cc54
-rw-r--r--test/mock/mock_bta_sys_conn.cc122
-rw-r--r--test/mock/mock_bta_sys_main.cc64
-rw-r--r--test/mock/mock_bta_sys_utl.cc63
-rw-r--r--test/mock/mock_bta_vc.cc60
-rw-r--r--test/mock/mock_bta_vc_device.cc92
-rw-r--r--test/mock/mock_btcore_module.cc61
-rw-r--r--test/mock/mock_btif_bqr.cc40
-rw-r--r--test/mock/mock_btif_co_bta_dm_co.cc38
-rw-r--r--test/mock/mock_btif_co_bta_hh_co.cc82
-rw-r--r--test/mock/mock_btif_config.cc162
-rw-r--r--test/mock/mock_btif_config.h265
-rw-r--r--test/mock/mock_btif_core.cc150
-rw-r--r--test/mock/mock_btif_debug_conn.cc40
-rw-r--r--test/mock/mock_btif_dm.cc175
-rw-r--r--test/mock/mock_btif_stack_manager.cc25
-rw-r--r--test/mock/mock_btif_storage.cc224
-rw-r--r--test/mock/mock_common_address_obfuscator.cc58
-rw-r--r--test/mock/mock_common_message_loop_thread.cc250
-rw-r--r--test/mock/mock_common_metric_id_allocator.cc104
-rw-r--r--test/mock/mock_common_metrics.cc207
-rw-r--r--test/mock/mock_common_repeating_timer.cc60
-rw-r--r--test/mock/mock_common_stop_watch_legacy.cc56
-rw-r--r--test/mock/mock_common_time_util.cc52
-rw-r--r--test/mock/mock_device_controller.cc460
-rw-r--r--test/mock/mock_device_controller.h101
-rw-r--r--test/mock/mock_device_interop.cc49
-rw-r--r--test/mock/mock_frameworks_libaudio.cc305
-rw-r--r--test/mock/mock_hci_btsnoop_mem.cc43
-rw-r--r--test/mock/mock_hci_layer.cc126
-rw-r--r--test/mock/mock_hci_layer.h169
-rw-r--r--test/mock/mock_hci_packet_factory.cc36
-rw-r--r--test/mock/mock_hci_packet_parser.cc41
-rw-r--r--test/mock/mock_hcic_hciblecmds.cc327
-rw-r--r--test/mock/mock_hcic_hcicmds.cc325
-rw-r--r--test/mock/mock_hcic_hcicmds.h55
-rw-r--r--test/mock/mock_main_bte.cc68
-rw-r--r--test/mock/mock_main_bte.h96
-rw-r--r--test/mock/mock_main_shim.cc93
-rw-r--r--test/mock/mock_main_shim_BtifConfigInterface.cc90
-rw-r--r--test/mock/mock_main_shim_acl.cc36
-rw-r--r--test/mock/mock_main_shim_acl_api.cc71
-rw-r--r--test/mock/mock_main_shim_activity_attribution.cc42
-rw-r--r--test/mock/mock_main_shim_btm_api.cc439
-rw-r--r--test/mock/mock_main_shim_controller.cc37
-rw-r--r--test/mock/mock_main_shim_dumpsys.cc44
-rw-r--r--test/mock/mock_main_shim_entry.cc75
-rw-r--r--test/mock/mock_main_shim_entry.h26
-rw-r--r--test/mock/mock_main_shim_l2cap_api.cc343
-rw-r--r--test/mock/mock_main_shim_l2cap_api.h590
-rw-r--r--test/mock/mock_main_shim_le_advertising_manager.cc45
-rw-r--r--test/mock/mock_main_shim_le_scanning_manager.cc40
-rw-r--r--test/mock/mock_main_shim_link_policy.cc121
-rw-r--r--test/mock/mock_main_shim_link_policy.h201
-rw-r--r--test/mock/mock_main_shim_metric_id_api.cc70
-rw-r--r--test/mock/mock_main_shim_metrics_api.cc180
-rw-r--r--test/mock/mock_main_shim_metrics_api.h287
-rw-r--r--test/mock/mock_stack_a2dp_api.cc67
-rw-r--r--test/mock/mock_stack_a2dp_codec_config.cc351
-rw-r--r--test/mock/mock_stack_acl.cc456
-rw-r--r--test/mock/mock_stack_acl_ble.cc76
-rw-r--r--test/mock/mock_stack_acl_btm_ble_connection_establishment.cc103
-rw-r--r--test/mock/mock_stack_acl_btm_ble_connection_establishment.h135
-rw-r--r--test/mock/mock_stack_acl_btm_pm.cc105
-rw-r--r--test/mock/mock_stack_avct_api.cc74
-rw-r--r--test/mock/mock_stack_avdt_api.cc147
-rw-r--r--test/mock/mock_stack_avrc_api.cc83
-rw-r--r--test/mock/mock_stack_avrc_bld_ct.cc40
-rw-r--r--test/mock/mock_stack_avrc_bld_tg.cc47
-rw-r--r--test/mock/mock_stack_avrc_pars.ct.cc54
-rw-r--r--test/mock/mock_stack_avrc_pars_tg.cc46
-rw-r--r--test/mock/mock_stack_avrc_sdp.cc58
-rw-r--r--test/mock/mock_stack_bnep_api.cc86
-rw-r--r--test/mock/mock_stack_btm.cc36
-rw-r--r--test/mock/mock_stack_btm_ble.cc256
-rw-r--r--test/mock/mock_stack_btm_ble_addr.cc128
-rw-r--r--test/mock/mock_stack_btm_ble_addr.h177
-rw-r--r--test/mock/mock_stack_btm_ble_adv_filter.cc66
-rw-r--r--test/mock/mock_stack_btm_ble_advertiser_hci_interface.cc75
-rw-r--r--test/mock/mock_stack_btm_ble_advertiser_hci_interface.h76
-rw-r--r--test/mock/mock_stack_btm_ble_batchscan.cc71
-rw-r--r--test/mock/mock_stack_btm_ble_bgconn.cc116
-rw-r--r--test/mock/mock_stack_btm_ble_bgconn.h167
-rw-r--r--test/mock/mock_stack_btm_ble_gap.cc213
-rw-r--r--test/mock/mock_stack_btm_ble_multi_adv.cc66
-rw-r--r--test/mock/mock_stack_btm_ble_privacy.cc140
-rw-r--r--test/mock/mock_stack_btm_ble_privacy.h180
-rw-r--r--test/mock/mock_stack_btm_ble_scanner_hci_interface.cc81
-rw-r--r--test/mock/mock_stack_btm_ble_scanner_hci_interface.h82
-rw-r--r--test/mock/mock_stack_btm_dev.cc112
-rw-r--r--test/mock/mock_stack_btm_devctl.cc123
-rw-r--r--test/mock/mock_stack_btm_inq.cc188
-rw-r--r--test/mock/mock_stack_btm_iso.cc45
-rw-r--r--test/mock/mock_stack_btm_main.cc57
-rw-r--r--test/mock/mock_stack_btm_scn.cc46
-rw-r--r--test/mock/mock_stack_btm_sco.cc125
-rw-r--r--test/mock/mock_stack_btm_sec.cc303
-rw-r--r--test/mock/mock_stack_btu_hcif.cc80
-rw-r--r--test/mock/mock_stack_btu_task.cc70
-rw-r--r--test/mock/mock_stack_crypto_toolbox.cc96
-rw-r--r--test/mock/mock_stack_crypto_toolbox.h169
-rw-r--r--test/mock/mock_stack_crypto_toolbox_aes_cmac.cc40
-rw-r--r--test/mock/mock_stack_gap_ble.cc51
-rw-r--r--test/mock/mock_stack_gap_conn.cc82
-rw-r--r--test/mock/mock_stack_gatt.cc159
-rw-r--r--test/mock/mock_stack_gatt_attr.cc84
-rw-r--r--test/mock/mock_stack_gatt_auth.cc66
-rw-r--r--test/mock/mock_stack_gatt_connection_manager.cc86
-rw-r--r--test/mock/mock_stack_gatt_main.cc111
-rw-r--r--test/mock/mock_stack_hidd_api.cc111
-rw-r--r--test/mock/mock_stack_hidh.cc81
-rw-r--r--test/mock/mock_stack_l2cap_api.cc271
-rw-r--r--test/mock/mock_stack_l2cap_api.h458
-rw-r--r--test/mock/mock_stack_l2cap_ble.cc201
-rw-r--r--test/mock/mock_stack_l2cap_ble.h321
-rw-r--r--test/mock/mock_stack_l2cap_link.cc96
-rw-r--r--test/mock/mock_stack_l2cap_main.cc60
-rw-r--r--test/mock/mock_stack_l2cap_utils.cc283
-rw-r--r--test/mock/mock_stack_metrics_logging.cc115
-rw-r--r--test/mock/mock_stack_metrics_logging.h166
-rw-r--r--test/mock/mock_stack_pan_api.cc92
-rw-r--r--test/mock/mock_stack_rfcomm_port_api.cc130
-rw-r--r--test/mock/mock_stack_sdp.cc113
-rw-r--r--test/mock/mock_stack_sdp_db.cc102
-rw-r--r--test/mock/mock_stack_sdp_main.cc51
-rw-r--r--test/mock/mock_stack_smp_act.cc430
-rw-r--r--test/mock/mock_stack_smp_act.h707
-rw-r--r--test/mock/mock_stack_smp_api.cc84
-rw-r--r--test/mock/mock_stack_srvc_dis.cc71
-rw-r--r--test/mock/mock_system_libfmq_eventflag.cc99
-rw-r--r--test/mock/mock_udrv_ulinux_uipc.cc100
-rw-r--r--test/rootcanal/Android.bp15
-rw-r--r--test/rootcanal/bluetooth_hci.cc64
-rw-r--r--test/rootcanal/bluetooth_hci.h26
-rwxr-xr-xtest/run_host_unit_tests.py29
-rwxr-xr-xtest/run_unit_tests.sh2
-rw-r--r--test/stub/legacy_trace.cc31
-rw-r--r--test/stub/osi.cc645
-rw-r--r--test/suite/Android.bp9
-rw-r--r--test/suite/BUILD.gn55
-rw-r--r--test/suite/adapter/adapter_unittest.cc3
-rw-r--r--test/suite/gatt/gatt_unittest.cc6
-rw-r--r--tools/scripts/btsnoop_live.py13
-rwxr-xr-xtools/scripts/btsnooz.py27
-rwxr-xr-xtools/scripts/dump_hearingaid_audio.py123
-rwxr-xr-xtools/scripts/dump_metrics_ascii.py18
-rwxr-xr-xtools/scripts/yapf_checker.py33
-rw-r--r--types/Android.bp9
-rw-r--r--types/BUILD.gn63
-rw-r--r--types/ble_address_with_type.h93
-rw-r--r--types/bluetooth/uuid.cc7
-rw-r--r--types/bluetooth/uuid.h3
-rw-r--r--types/bt_transport.h38
-rw-r--r--types/class_of_device.h3
-rw-r--r--types/hci_role.h49
-rw-r--r--types/raw_address.cc2
-rw-r--r--types/raw_address.h3
-rw-r--r--udrv/Android.bp13
-rw-r--r--udrv/BUILD.gn13
-rw-r--r--udrv/ulinux/uipc.cc4
-rw-r--r--utils/Android.bp10
-rw-r--r--utils/BUILD.gn14
-rw-r--r--utils/src/bt_utils.cc6
-rw-r--r--vendor_libs/Android.bp9
-rw-r--r--vendor_libs/linux/Android.bp9
-rw-r--r--vendor_libs/linux/interface/Android.bp32
-rw-r--r--vendor_libs/linux/interface/async_fd_watcher.cc3
-rw-r--r--vendor_libs/linux/interface/bluetooth_hci.cc9
-rw-r--r--vendor_libs/test_vendor_lib/Android.bp40
-rw-r--r--vendor_libs/test_vendor_lib/data/Android.bp14
-rw-r--r--vendor_libs/test_vendor_lib/desktop/root_canal_main.cc60
-rw-r--r--vendor_libs/test_vendor_lib/desktop/test_environment.cc46
-rw-r--r--vendor_libs/test_vendor_lib/desktop/test_environment.h39
-rw-r--r--vendor_libs/test_vendor_lib/include/acl.h42
-rw-r--r--vendor_libs/test_vendor_lib/include/hci.h (renamed from gd/hci/fuzz/status_vs_complete_commands.h)19
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/acl_connection_handler.cc231
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/acl_connection_handler.h51
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/connected_isochronous_group.h76
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/connected_isochronous_stream.h55
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/dual_mode_controller.cc1439
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/dual_mode_controller.h339
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/isochronous_connection_handler.cc101
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/isochronous_connection_handler.h57
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/le_advertiser.cc147
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/le_advertiser.h86
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/link_layer_controller.cc1790
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/link_layer_controller.h249
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/security_manager.cc60
-rw-r--r--vendor_libs/test_vendor_lib/model/controller/security_manager.h34
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/beacon.cc10
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/beacon_swarm.cc2
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/broken_adv.cc2
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/car_kit.cc11
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/car_kit.h4
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/classic.cc2
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/device.cc32
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/device.h7
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/device_properties.cc20
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/device_properties.h115
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/h4_packetizer.cc249
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/h4_packetizer.h60
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/h4_protocol.cc105
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/h4_protocol.h49
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/hci_packetizer.cc128
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/hci_packetizer.h68
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/hci_protocol.cc3
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/hci_protocol.h6
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/hci_socket_device.cc46
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/hci_socket_device.h20
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/keyboard.cc2
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/link_layer_socket_device.cc42
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/link_layer_socket_device.h6
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/loopback.cc7
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/remote_loopback_device.cc2
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/scripted_beacon.cc12
-rw-r--r--vendor_libs/test_vendor_lib/model/devices/sniffer.h2
-rw-r--r--vendor_libs/test_vendor_lib/model/setup/async_manager.cc134
-rw-r--r--vendor_libs/test_vendor_lib/model/setup/async_manager.h50
-rw-r--r--vendor_libs/test_vendor_lib/model/setup/phy_layer.h2
-rw-r--r--vendor_libs/test_vendor_lib/model/setup/phy_layer_factory.cc24
-rw-r--r--vendor_libs/test_vendor_lib/model/setup/phy_layer_factory.h20
-rw-r--r--vendor_libs/test_vendor_lib/model/setup/test_channel_transport.cc17
-rw-r--r--vendor_libs/test_vendor_lib/model/setup/test_command_handler.cc47
-rw-r--r--vendor_libs/test_vendor_lib/model/setup/test_command_handler.h5
-rw-r--r--vendor_libs/test_vendor_lib/model/setup/test_model.cc177
-rw-r--r--vendor_libs/test_vendor_lib/model/setup/test_model.h41
-rw-r--r--vendor_libs/test_vendor_lib/packets/link_layer_packets.pdl151
-rw-r--r--vendor_libs/test_vendor_lib/scripts/hci_socket.py87
-rw-r--r--vendor_libs/test_vendor_lib/scripts/link_layer_socket.py21
-rw-r--r--vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/Readme.txt11
-rw-r--r--vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/add_beacons10
-rw-r--r--vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/grant_permission.pb21
-rw-r--r--vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/no_permission.pb21
-rw-r--r--vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/run_test.sh17
-rw-r--r--vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/start_scan3
-rw-r--r--vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/test_events.pb21
-rw-r--r--vendor_libs/test_vendor_lib/scripts/send_simple_commands.py3
-rw-r--r--vendor_libs/test_vendor_lib/scripts/simple_link_layer_socket.py3
-rw-r--r--vendor_libs/test_vendor_lib/scripts/simple_stack.py3
-rw-r--r--vendor_libs/test_vendor_lib/scripts/test_channel.py73
-rw-r--r--vendor_libs/test_vendor_lib/test/async_manager_unittest.cc97
-rw-r--r--vendor_libs/test_vendor_lib/types/Android.bp9
-rw-r--r--vendor_libs/test_vendor_lib/types/BUILD.gn53
2038 files changed, 65391 insertions, 176681 deletions
diff --git a/.gitignore b/.gitignore
index 5acc85a88..92b837bfb 100644
--- a/.gitignore
+++ b/.gitignore
@@ -1,6 +1,3 @@
buildtools
out
-third_party/
-target/
-Cargo.lock
-tags
+third_party
diff --git a/gd/att/BUILD.gn b/.gn
index fd1693751..1c2396dfc 100644
--- a/gd/att/BUILD.gn
+++ b/.gn
@@ -1,5 +1,5 @@
#
-# Copyright 2021 Google, Inc.
+# Copyright 2015 Google, Inc.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
@@ -14,9 +14,9 @@
# limitations under the License.
#
-source_set("BluetoothAttSources") {
- sources = [ "att_module.cc" ]
+# This file is used by the GN meta build system to find the root of the source
+# tree and to set startup options. For documentation on the values set in this
+# file, run "gn help dotfile" at the command line.
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ "//bt/gd:gd_default_deps" ]
-}
+buildconfig = "//build/config/BUILDCONFIG.gn"
+secondary_source = "//build/secondary/"
diff --git a/.style.yapf b/.style.yapf
index 2b1192230..3c8af88e1 100644
--- a/.style.yapf
+++ b/.style.yapf
@@ -2,4 +2,3 @@
# http://google.github.io/styleguide/pyguide.html
based_on_style: google
indent_width: 4
-column_limit: 120
diff --git a/Android.bp b/Android.bp
index 2b4938061..113be7bbb 100644
--- a/Android.bp
+++ b/Android.bp
@@ -1,35 +1,3 @@
-package {
- default_applicable_licenses: ["system_bt_license"],
-}
-
-// Added automatically by a large-scale-change that took the approach of
-// 'apply every license found to every target'. While this makes sure we respect
-// every license restriction, it may not be entirely correct.
-//
-// e.g. GPL in an MIT project might only apply to the contrib/ directory.
-//
-// Please consider splitting the single license below into multiple licenses,
-// taking care not to lose any license_kind information, and overriding the
-// default license using the 'licenses: [...]' property on targets as needed.
-//
-// For unused files, consider creating a 'fileGroup' with "//visibility:private"
-// to attach the license to, and including a comment whether the files may be
-// used in the current project.
-// See: http://go/android-license-faq
-license {
- name: "system_bt_license",
- visibility: [":__subpackages__"],
- license_kinds: [
- "SPDX-license-identifier-Apache-2.0",
- "SPDX-license-identifier-BSD",
- "SPDX-license-identifier-MIT",
- "legacy_unencumbered",
- ],
- license_text: [
- "NOTICE",
- ],
-}
-
subdirs = [
"apex",
"binder",
diff --git a/BUILD.gn b/BUILD.gn
index 56ed7d85d..456fbeb8f 100644
--- a/BUILD.gn
+++ b/BUILD.gn
@@ -20,212 +20,22 @@
# you add a new build file, there must be some path of dependencies from this
# file to your new one or GN won't know about it.
-group("all") {
- deps = [ ":bluetooth" ]
-
- if (use.test) {
- deps += [ ":bluetooth_tests" ]
- }
-}
-
# This pulls in main/BUILD.gn and all of its dependencies.
group("bluetooth") {
deps = [
- "//bt/main:bluetooth",
- "//bt/main:bluetooth-static",
- #"//bt/service:bluetoothtbd",
+ "//main:bluetooth",
+ "//service:bluetoothtbd",
]
}
-if (use.test) {
- group("bluetooth_tests") {
- deps = [
- "//bt/btcore:net_test_btcore",
- "//bt/common:bluetooth_test_common",
- "//bt/profile/avrcp:net_test_avrcp",
- "//bt/service:bluetoothtbd_test",
- "//bt/stack:net_test_btm_iso",
- "//bt/types:net_test_types",
-
- #"//bt/packet:net_test_btpackets",
- ]
- }
-}
-
-if (host_cpu == target_cpu && host_os == target_os) {
- group("tools") {
- deps = [
- "//bt/gd/dumpsys/bundler:bluetooth_flatbuffer_bundler",
- "//bt/gd/packet/parser:bluetooth_packetgen",
- ]
- }
-}
+group("bluetooth_tests") {
+ testonly = true
-if (defined(use.android) && use.android) {
- group("android_bluetooth_tests") {
- deps = [
- "//bt/device:net_test_device",
- "//bt/hci:net_test_hci",
- "//bt/osi:net_test_osi",
- "//bt/test/suite:net_test_bluetooth",
- ]
- }
-}
-
-config("target_defaults") {
- include_dirs = [
- "//bt",
- "//bt/linux_include",
- "//bt/types",
- "//bt/include",
-
- # For flatbuffer generated headers
- "${root_gen_dir}/bt/gd/",
- "${root_gen_dir}/bt/gd/dumpsys/bundler",
- ]
-
- cflags = [
- "-fPIC",
- "-Wno-non-c-typedef-for-linkage",
- "-Wno-unreachable-code-return",
- "-Wno-defaulted-function-deleted",
- "-Wno-gnu-variable-sized-type-not-at-end",
- "-Wno-format-nonliteral",
- "-Wno-inconsistent-missing-override",
- "-Wno-unreachable-code",
- "-Wno-range-loop-construct",
- "-Wno-reorder-init-list",
- "-Wno-unused-function",
- "-Wno-unused-result",
- "-Wno-unused-variable",
- "-Wno-unused-const-variable",
- "-Wno-format",
- "-Wno-pessimizing-move",
- "-Wno-unknown-warning-option",
- "-Wno-final-dtor-non-final-class",
- ]
-
- cflags_cc = [
- "-std=c++17",
- ]
-
- defines = [
- "HAS_NO_BDROID_BUILDCFG",
- "OS_GENERIC",
- "OS_LINUX_GENERIC",
- "TARGET_FLOSS",
- "USE_LINUX_HCI_SOCKET",
- "EXPORT_SYMBOL=__attribute__((visibility(\"default\")))",
- "FALLTHROUGH_INTENDED=[[clang::fallthrough]]",
- ]
-
- # If not configured as a dynamic library, default to static library
- if (!(defined(use.bt_dynlib) && use.bt_dynlib)) {
- defines += [
- "STATIC_LIBBLUETOOTH",
- ]
- }
-
- if (!(defined(use.bt_nonstandard_codecs) && use.bt_nonstandard_codecs)) {
- defines += [ "EXCLUDE_NONSTANDARD_CODECS" ]
- }
-
- configs = [ ":external_libchrome" ]
-}
-
-group("libbt-platform-protos-lite") {
deps = [
- "//external/proto_logging/stats/enums/bluetooth:libbt-platform-protos-lite",
+ "//test/suite:net_test_bluetooth",
+ "//btcore:net_test_btcore",
+ "//hci:net_test_hci",
+ "//osi:net_test_osi",
+ "//device:net_test_device",
]
}
-
-# Configurations to use as dependencies for GN build
-config("external_gtest") {
- configs = [
- ":pkg_gtest",
- ":pkg_gmock",
- ]
-}
-
-config("external_gtest_main") {
- configs = [ ":pkg_gtest_main" ]
-}
-
-config("external_gmock_main") {
- configs = [ ":pkg_gmock_main" ]
-}
-
-config("external_libchrome") {
- configs = [ ":pkg_libchrome" ]
-}
-
-config("external_modp_b64") {
- configs = [ ":pkg_modp_b64" ]
-}
-
-config("external_tinyxml2") {
- configs = [ ":pkg_tinyxml2" ]
-}
-
-config("external_flatbuffers") {
- lib_dirs = [ "${libdir}" ]
-
- libs = [ "flatbuffers" ]
-}
-
-# Package configurations to extract dependencies from env
-pkg_config("pkg_gtest") {
- pkg_deps = [ "gtest" ]
-}
-
-pkg_config("pkg_gtest_main") {
- pkg_deps = [ "gtest_main" ]
-}
-
-pkg_config("pkg_gmock") {
- pkg_deps = [ "gmock" ]
-}
-
-pkg_config("pkg_gmock_main") {
- pkg_deps = [ "gmock_main" ]
-}
-
-pkg_config("pkg_libchrome") {
- pkg_deps = [ "libchrome" ]
-}
-
-pkg_config("pkg_modp_b64") {
- pkg_deps = [ "libmodp_b64" ]
-}
-
-pkg_config("pkg_tinyxml2") {
- pkg_deps = [ "tinyxml2" ]
-}
-
-# To use non-standard codecs (i.e. ldac, aac, aptx), set this use flag when
-# building. These codecs may have licensing issues that need to be resolved
-# first.
-if (defined(use.bt_nonstandard_codecs) && use.bt_nonstandard_codecs) {
- config("external_aac") {
- configs = [ ":pkg_aac" ]
- }
-
- pkg_config("pkg_aac") {
- pkg_deps = [ "fdk-aac" ]
- }
-
- config("external_libldac") {
- configs = [
- ":pkg_libldacBT_enc",
- ":pkg_libldacBT_abr",
- ]
- }
-
- pkg_config("pkg_libldacBT_enc") {
- pkg_deps = [ "ldacBT-enc" ]
- }
-
- pkg_config("pkg_libldacBT_abr") {
- pkg_deps = [ "ldacBT-abr" ]
- }
-}
diff --git a/Cargo.toml b/Cargo.toml
deleted file mode 100644
index aa507d10a..000000000
--- a/Cargo.toml
+++ /dev/null
@@ -1,24 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[workspace]
-
-members = [
- "gd/rust/shim",
- "gd/rust/topshim",
- "gd/rust/linux/mgmt",
- "gd/rust/linux/adapter",
- "gd/rust/linux/service",
-]
diff --git a/METADATA b/METADATA
deleted file mode 100644
index d97975ca3..000000000
--- a/METADATA
+++ /dev/null
@@ -1,3 +0,0 @@
-third_party {
- license_type: NOTICE
-}
diff --git a/OWNERS b/OWNERS
index df99fd302..ab11e8ce8 100644
--- a/OWNERS
+++ b/OWNERS
@@ -3,11 +3,10 @@ set noparent
# Project owners
zachoverflow@google.com
cmanton@google.com
-cncn@google.com
hsz@google.com
jpawlowski@google.com
mylesgw@google.com
optedoblivion@google.com
-qasimj@google.com
rahulsabnis@google.com
siyuanh@google.com
+stng@google.com
diff --git a/PREUPLOAD.cfg b/PREUPLOAD.cfg
index 04963df9d..a4730406c 100644
--- a/PREUPLOAD.cfg
+++ b/PREUPLOAD.cfg
@@ -3,11 +3,8 @@ ignore_merged_commits = true
[Builtin Hooks]
clang_format = true
-rustfmt = true
-
-[Builtin Hooks Options]
-rustfmt = --config-path=rustfmt.toml
[Hook Scripts]
aosp_first = ${REPO_ROOT}/frameworks/base/tools/aosp/aosp_sha.sh ${PREUPLOAD_COMMIT} ".*$"
yapf_hook = ./tools/scripts/yapf_checker.py
+
diff --git a/README.md b/README.md
index c7a6bccc4..869bc1fdc 100644
--- a/README.md
+++ b/README.md
@@ -5,29 +5,8 @@ Just build AOSP - Fluoride is there by default.
## Building and running on Linux
-Instructions for a Debian based distribution:
-* Debian Bullseye or newer
-* Ubuntu 20.10 or newer
-* Clang-11 or Clang-12
-* Flex 2.6.x
-* Bison 3.x.x (tested with 3.0.x, 3.2.x and 3.7.x)
-
-You'll want to download some pre-requisite packages as well. If you're currently
-configured for AOSP development, you should have all required packages.
-Otherwise, you can use the following apt-get list:
-
-```sh
-sudo apt-get install repo git-core gnupg flex bison gperf build-essential \
- zip curl zlib1g-dev gcc-multilib g++-multilib \
- x11proto-core-dev libx11-dev lib32z-dev libncurses5 \
- libgl1-mesa-dev libxml2-utils xsltproc unzip liblz4-tool libssl-dev \
- libc++-dev libevent-dev \
- flatbuffers-compiler libflatbuffers1 \
- openssl openssl-dev
-```
-
-You will also need a recent-ish version of Rust and Cargo. Please follow the
-instructions on [Rustup](https://rustup.rs/) to install a recent version.
+Instructions for Ubuntu, tested on 14.04 with Clang 3.5.0 and 16.10 with Clang
+ 3.8.0
### Download source
@@ -37,86 +16,96 @@ cd ~/fluoride
git clone https://android.googlesource.com/platform/system/bt
```
-Install dependencies (require sudo access). This adds some Ubuntu dependencies
-and also installs GN (which is the build tool we're using).
+Install dependencies (require sudo access):
```sh
cd ~/fluoride/bt
build/install_deps.sh
```
-The following third-party dependencies are necessary but currently unavailable
-via a package manager. You may have to build these from source and install them
-to your local environment.
+Then fetch third party dependencies:
+
+```sh
+cd ~/fluoride/bt
+mkdir third_party
+cd third_party
+git clone https://github.com/google/googletest.git
+git clone https://android.googlesource.com/platform/external/aac
+git clone https://android.googlesource.com/platform/external/libchrome
+git clone https://android.googlesource.com/platform/external/libldac
+git clone https://android.googlesource.com/platform/external/modp_b64
+git clone https://android.googlesource.com/platform/external/tinyxml2
+```
-* libchrome
-* modp_b64
+And third party dependencies of third party dependencies:
-We provide a script to produce debian packages for those components, please
-follow the instructions in build/dpkg/README.txt.
+```sh
+cd fluoride/bt/third_party/libchrome/base/third_party
+mkdir valgrind
+cd valgrind
+curl https://chromium.googlesource.com/chromium/src/base/+/master/third_party/valgrind/valgrind.h?format=TEXT | base64 -d > valgrind.h
+curl https://chromium.googlesource.com/chromium/src/base/+/master/third_party/valgrind/memcheck.h?format=TEXT | base64 -d > memcheck.h
+```
-The googletest packages provided by Debian/Ubuntu (libgmock-dev and
-libgtest-dev) do not provide pkg-config files, so you can build your own
-googletest using the steps below:
+NOTE: If system/bt is checked out under AOSP, then create symbolic links instead
+of downloading sources
```
-$ git clone https://github.com/google/googletest.git -b release-1.10.0
-$ cd googletest # Main directory of the cloned repository.
-$ mkdir build # Create a directory to hold the build output.
-$ cd build
-$ cmake .. # Generate native build scripts for GoogleTest.
-$ sudo make install -DCMAKE_INSTALL_PREFIX=/usr
+cd system/bt
+mkdir third_party
+cd third_party
+ln -s ../../../external/aac aac
+ln -s ../../../external/libchrome libchrome
+ln -s ../../../external/libldac libldac
+ln -s ../../../external/modp_b64 modp_b64
+ln -s ../../../external/tinyxml2 tinyxml2
+ln -s ../../../external/googletest googletest
```
-### Stage your build environment
-
-For host build, we depend on a few other repositories:
-* [Platform2](https://chromium.googlesource.com/chromiumos/platform2/)
-* [Rust crates](https://chromium.googlesource.com/chromiumos/third_party/rust_crates/)
-* [Proto logging](https://android.googlesource.com/platform/frameworks/proto_logging/)
+### Generate your build files
-Clone these all somewhere and create your staging environment.
```sh
-export STAGING_DIR=path/to/your/staging/dir
-mkdir ${STAGING_DIR}
-mkdir -p ${STAGING_DIR}/external
-ln -s $(readlink -f ${PLATFORM2_DIR}/common-mk) ${STAGING_DIR}/common-mk
-ln -s $(readlink -f ${PLATFORM2_DIR}/.gn) ${STAGING_DIR}/.gn
-ln -s $(readlink -f ${RUST_CRATE_DIR}) ${STAGING_DIR}/external/rust
-ln -s $(readlink -f ${PROTO_LOG_DIR}) ${STAGING_DIR}/external/proto_logging
+cd ~/fluoride/bt
+gn gen out/Default
```
### Build
-We provide a build script to automate building assuming you've staged your build
-environment already as above.
+```sh
+cd ~/fluoride/bt
+ninja -C out/Default all
+```
+
+This will build all targets (the shared library, executables, tests, etc) and
+ put them in out/Default. To build an individual target, replace "all" with the
+ target of your choice, e.g. ```ninja -C out/Default net_test_osi```.
+### Run
```sh
-./build.py --output ${OUTPUT_DIR} --platform-dir ${STAGING_DIR} --clang
+cd ~/fluoride/bt/out/Default
+LD_LIBRARY_PATH=./ ./bluetoothtbd -create-ipc-socket=fluoride
```
-This will build all targets to the output directory you've given. You can also
-build each stage separately (if you want to iterate on something specific):
+### Eclipse IDE Support
-* prepare - Generate the GN rules
-* tools - Generate host tools
-* rust - Build the rust portion of the build
-* main - Build all the C/C++ code
-* test - Build all targets and run the tests
-* clean - Clean the output directory
+1. Follows the Chromium project
+ [Eclipse Setup Instructions](https://chromium.googlesource.com/chromium/src/+/master/docs/linux_eclipse_dev.md)
+ until "Optional: Building inside Eclipse" section (don't do that section, we
+ will set it up differently)
-You can choose to run only a specific stage by passing an arg via `--target`.
+2. Generate Eclipse settings:
-Currently, Rust builds are a separate stage that uses Cargo to build. See
-[gd/rust/README.md](gd/rust/README.md) for more information.
+ ```sh
+ cd system/bt
+ gn gen --ide=eclipse out/Default
+ ```
-### Run
+3. In Eclipse, do File->Import->C/C++->C/C++ Project Settings, choose the XML
+ location under system/bt/out/Default
-By default on Linux, we statically link libbluetooth so you can just run the
-binary directly:
+4. Right click on the project. Go to Preferences->C/C++ Build->Builder Settings.
+ Uncheck "Use default build command", but instead using "ninja -C out/Default"
+
+5. Goto Behaviour tab, change clean command to "-t clean"
-```sh
-cd ~/fluoride/bt/out/Default
-./bluetoothtbd -create-ipc-socket=fluoride
-```
diff --git a/TEST_MAPPING b/TEST_MAPPING
index 69a0709ac..ccd894b33 100755
--- a/TEST_MAPPING
+++ b/TEST_MAPPING
@@ -28,9 +28,6 @@
"name" : "net_test_device"
},
{
- "name" : "net_test_eatt"
- },
- {
"name" : "net_test_hci"
},
{
@@ -57,13 +54,54 @@
],
"presubmit" : [
{
- "name" : "net_test_hf_client_add_record"
+ "name" : "bluetooth_test_common",
+ "host" : true
},
{
- "name" : "net_test_btif_hf_client_service"
+ "name" : "bluetoothtbd_test",
+ "host" : true
+ },
+ {
+ "name" : "net_test_avrcp",
+ "host" : true
+ },
+ {
+ "name" : "net_test_btcore",
+ "host" : true
+ },
+ {
+ "name" : "net_test_btpackets",
+ "host" : true
+ },
+ {
+ "name" : "net_test_types",
+ "host" : true
+ },
+ {
+ "name" : "net_test_btif_rc",
+ "host" : true
+ },
+ {
+ "name" : "net_test_stack_gatt_native",
+ "host" : true
+ },
+ {
+ "name" : "net_test_hci_fragmenter_native",
+ "host" : true
+ },
+ {
+ "name" : "net_test_stack_a2dp_native",
+ "host" : true
},
{
- "name" : "net_test_stack_btm"
+ "name" : "net_test_btif_config_cache",
+ "host" : true
+ },
+ {
+ "name" : "net_test_hf_client_add_record"
+ },
+ {
+ "name" : "net_test_btif_hf_client_service"
}
]
}
diff --git a/apex/Android.bp b/apex/Android.bp
index c206dca68..fc143ba3f 100644
--- a/apex/Android.bp
+++ b/apex/Android.bp
@@ -1,15 +1,5 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
apex {
name: "com.android.bluetooth.updatable",
- enabled: false,
manifest: "apex_manifest.json",
diff --git a/audio_a2dp_hw/Android.bp b/audio_a2dp_hw/Android.bp
index 708e1a609..fac3655b4 100644
--- a/audio_a2dp_hw/Android.bp
+++ b/audio_a2dp_hw/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_defaults {
name: "audio_a2dp_hw_defaults",
defaults: ["fluoride_defaults"],
@@ -40,7 +31,6 @@ cc_library_static {
srcs: [
"src/audio_a2dp_hw_utils.cc",
],
- host_supported: true,
}
// Audio A2DP library unit tests for target and host
diff --git a/audio_a2dp_hw/src/audio_a2dp_hw.cc b/audio_a2dp_hw/src/audio_a2dp_hw.cc
index 0387e4510..2fb139f89 100644
--- a/audio_a2dp_hw/src/audio_a2dp_hw.cc
+++ b/audio_a2dp_hw/src/audio_a2dp_hw.cc
@@ -70,11 +70,12 @@
// sockets
#define WRITE_POLL_MS 20
-#define FNLOG() LOG_VERBOSE("%s", __func__);
-#define DEBUG(fmt, ...) LOG_VERBOSE("%s: " fmt, __func__, ##__VA_ARGS__)
-#define INFO(fmt, ...) LOG_INFO("%s: " fmt, __func__, ##__VA_ARGS__)
-#define WARN(fmt, ...) LOG_WARN("%s: " fmt, __func__, ##__VA_ARGS__)
-#define ERROR(fmt, ...) LOG_ERROR("%s: " fmt, __func__, ##__VA_ARGS__)
+#define FNLOG() LOG_VERBOSE(LOG_TAG, "%s", __func__);
+#define DEBUG(fmt, ...) \
+ LOG_VERBOSE(LOG_TAG, "%s: " fmt, __func__, ##__VA_ARGS__)
+#define INFO(fmt, ...) LOG_INFO(LOG_TAG, "%s: " fmt, __func__, ##__VA_ARGS__)
+#define WARN(fmt, ...) LOG_WARN(LOG_TAG, "%s: " fmt, __func__, ##__VA_ARGS__)
+#define ERROR(fmt, ...) LOG_ERROR(LOG_TAG, "%s: " fmt, __func__, ##__VA_ARGS__)
#define ASSERTC(cond, msg, val) \
if (!(cond)) { \
@@ -110,7 +111,7 @@ struct a2dp_audio_device {
struct a2dp_config {
uint32_t rate;
- audio_channel_mask_t channel_mask;
+ uint32_t channel_mask;
bool is_stereo_to_mono; // True if fetching Stereo and mixing into Mono
int format;
};
@@ -1115,13 +1116,12 @@ size_t audio_a2dp_hw_stream_compute_buffer_size(
return buffer_sz;
}
-static audio_channel_mask_t out_get_channels(
- const struct audio_stream* stream) {
+static uint32_t out_get_channels(const struct audio_stream* stream) {
struct a2dp_stream_out* out = (struct a2dp_stream_out*)stream;
DEBUG("channels 0x%" PRIx32, out->common.cfg.channel_mask);
- return (audio_channel_mask_t)out->common.cfg.channel_mask;
+ return out->common.cfg.channel_mask;
}
static audio_format_t out_get_format(const struct audio_stream* stream) {
@@ -1440,11 +1440,11 @@ static size_t in_get_buffer_size(
return 320;
}
-static audio_channel_mask_t in_get_channels(const struct audio_stream* stream) {
+static uint32_t in_get_channels(const struct audio_stream* stream) {
struct a2dp_stream_in* in = (struct a2dp_stream_in*)stream;
FNLOG();
- return (audio_channel_mask_t)in->common.cfg.channel_mask;
+ return in->common.cfg.channel_mask;
}
static audio_format_t in_get_format(
diff --git a/audio_bluetooth_hw/Android.bp b/audio_bluetooth_hw/Android.bp
index e52f1dbca..de1effdb3 100644
--- a/audio_bluetooth_hw/Android.bp
+++ b/audio_bluetooth_hw/Android.bp
@@ -1,14 +1,5 @@
// The format of the name is audio.<type>.<hardware/etc>.so
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_shared {
name: "audio.bluetooth.default",
relative_install_path: "hw",
@@ -22,7 +13,6 @@ cc_library_shared {
header_libs: ["libhardware_headers"],
shared_libs: [
"android.hardware.bluetooth.audio@2.0",
- "android.hardware.bluetooth.audio@2.1",
"libaudioutils",
"libbase",
"libbluetooth_audio_session",
diff --git a/audio_bluetooth_hw/device_port_proxy.cc b/audio_bluetooth_hw/device_port_proxy.cc
index afa87426b..d3a9e82e5 100644
--- a/audio_bluetooth_hw/device_port_proxy.cc
+++ b/audio_bluetooth_hw/device_port_proxy.cc
@@ -23,7 +23,7 @@
#include <log/log.h>
#include <stdlib.h>
-#include "BluetoothAudioSessionControl_2_1.h"
+#include "BluetoothAudioSessionControl.h"
#include "device_port_proxy.h"
#include "stream_apis.h"
#include "utils.h"
@@ -33,12 +33,11 @@ namespace bluetooth {
namespace audio {
using ::android::base::StringPrintf;
-using ::android::bluetooth::audio::BluetoothAudioSessionControl_2_1;
+using ::android::bluetooth::audio::BluetoothAudioSessionControl;
using ::android::hardware::bluetooth::audio::V2_0::BitsPerSample;
using ::android::hardware::bluetooth::audio::V2_0::ChannelMode;
using ::android::hardware::bluetooth::audio::V2_0::PcmParameters;
-using SampleRate = ::android::hardware::bluetooth::audio::V2_0::SampleRate;
-using SampleRate_2_1 = ::android::hardware::bluetooth::audio::V2_1::SampleRate;
+using ::android::hardware::bluetooth::audio::V2_0::SampleRate;
using BluetoothAudioStatus =
::android::hardware::bluetooth::audio::V2_0::Status;
using ControlResultCallback = std::function<void(
@@ -47,33 +46,29 @@ using SessionChangedCallback = std::function<void(uint16_t cookie)>;
namespace {
-unsigned int SampleRateToAudioFormat(SampleRate_2_1 sample_rate) {
+unsigned int SampleRateToAudioFormat(SampleRate sample_rate) {
switch (sample_rate) {
- case SampleRate_2_1::RATE_8000:
- return 8000;
- case SampleRate_2_1::RATE_16000:
+ case SampleRate::RATE_16000:
return 16000;
- case SampleRate_2_1::RATE_24000:
+ case SampleRate::RATE_24000:
return 24000;
- case SampleRate_2_1::RATE_32000:
- return 32000;
- case SampleRate_2_1::RATE_44100:
+ case SampleRate::RATE_44100:
return 44100;
- case SampleRate_2_1::RATE_48000:
+ case SampleRate::RATE_48000:
return 48000;
- case SampleRate_2_1::RATE_88200:
+ case SampleRate::RATE_88200:
return 88200;
- case SampleRate_2_1::RATE_96000:
+ case SampleRate::RATE_96000:
return 96000;
- case SampleRate_2_1::RATE_176400:
+ case SampleRate::RATE_176400:
return 176400;
- case SampleRate_2_1::RATE_192000:
+ case SampleRate::RATE_192000:
return 192000;
default:
return kBluetoothDefaultSampleRate;
}
}
-audio_channel_mask_t OutputChannelModeToAudioFormat(ChannelMode channel_mode) {
+audio_channel_mask_t ChannelModeToAudioFormat(ChannelMode channel_mode) {
switch (channel_mode) {
case ChannelMode::MONO:
return AUDIO_CHANNEL_OUT_MONO;
@@ -84,17 +79,6 @@ audio_channel_mask_t OutputChannelModeToAudioFormat(ChannelMode channel_mode) {
}
}
-audio_channel_mask_t InputChannelModeToAudioFormat(ChannelMode channel_mode) {
- switch (channel_mode) {
- case ChannelMode::MONO:
- return AUDIO_CHANNEL_IN_MONO;
- case ChannelMode::STEREO:
- return AUDIO_CHANNEL_IN_STEREO;
- default:
- return kBluetoothDefaultInputChannelModeMask;
- }
-}
-
audio_format_t BitsPerSampleToAudioFormat(BitsPerSample bits_per_sample) {
switch (bits_per_sample) {
case BitsPerSample::BITS_16:
@@ -113,12 +97,12 @@ constexpr unsigned int kMaxWaitingTimeMs = 4500;
} // namespace
-BluetoothAudioPort::BluetoothAudioPort()
- : cookie_(android::bluetooth::audio::kObserversCookieUndefined),
- state_(BluetoothStreamState::DISABLED),
- session_type_(SessionType_2_1::UNKNOWN) {}
+BluetoothAudioPortOut::BluetoothAudioPortOut()
+ : state_(BluetoothStreamState::DISABLED),
+ session_type_(SessionType::UNKNOWN),
+ cookie_(android::bluetooth::audio::kObserversCookieUndefined) {}
-bool BluetoothAudioPort::SetUp(audio_devices_t devices) {
+bool BluetoothAudioPortOut::SetUp(audio_devices_t devices) {
if (!init_session_type(devices)) return false;
state_ = BluetoothStreamState::STANDBY;
@@ -126,7 +110,7 @@ bool BluetoothAudioPort::SetUp(audio_devices_t devices) {
auto control_result_cb = [port = this](uint16_t cookie, bool start_resp,
const BluetoothAudioStatus& status) {
if (!port->in_use()) {
- LOG(ERROR) << "control_result_cb: BluetoothAudioPort is not in use";
+ LOG(ERROR) << "control_result_cb: BluetoothAudioPortOut is not in use";
return;
}
if (port->cookie_ != cookie) {
@@ -138,7 +122,7 @@ bool BluetoothAudioPort::SetUp(audio_devices_t devices) {
};
auto session_changed_cb = [port = this](uint16_t cookie) {
if (!port->in_use()) {
- LOG(ERROR) << "session_changed_cb: BluetoothAudioPort is not in use";
+ LOG(ERROR) << "session_changed_cb: BluetoothAudioPortOut is not in use";
return;
}
if (port->cookie_ != cookie) {
@@ -151,51 +135,33 @@ bool BluetoothAudioPort::SetUp(audio_devices_t devices) {
::android::bluetooth::audio::PortStatusCallbacks cbacks = {
.control_result_cb_ = control_result_cb,
.session_changed_cb_ = session_changed_cb};
- cookie_ = BluetoothAudioSessionControl_2_1::RegisterControlResultCback(
+ cookie_ = BluetoothAudioSessionControl::RegisterControlResultCback(
session_type_, cbacks);
LOG(INFO) << __func__ << ": session_type=" << toString(session_type_) << ", cookie=" << StringPrintf("%#hx", cookie_);
return (cookie_ != android::bluetooth::audio::kObserversCookieUndefined);
}
-bool BluetoothAudioPort::init_session_type(audio_devices_t device) {
+bool BluetoothAudioPortOut::init_session_type(audio_devices_t device) {
switch (device) {
case AUDIO_DEVICE_OUT_BLUETOOTH_A2DP:
case AUDIO_DEVICE_OUT_BLUETOOTH_A2DP_HEADPHONES:
case AUDIO_DEVICE_OUT_BLUETOOTH_A2DP_SPEAKER:
LOG(VERBOSE) << __func__ << ": device=AUDIO_DEVICE_OUT_BLUETOOTH_A2DP (HEADPHONES/SPEAKER) ("
<< StringPrintf("%#x", device) << ")";
- session_type_ = SessionType_2_1::A2DP_SOFTWARE_ENCODING_DATAPATH;
+ session_type_ = SessionType::A2DP_SOFTWARE_ENCODING_DATAPATH;
break;
case AUDIO_DEVICE_OUT_HEARING_AID:
LOG(VERBOSE) << __func__ << ": device=AUDIO_DEVICE_OUT_HEARING_AID (MEDIA/VOICE) (" << StringPrintf("%#x", device)
<< ")";
- session_type_ = SessionType_2_1::HEARING_AID_SOFTWARE_ENCODING_DATAPATH;
- break;
- case AUDIO_DEVICE_OUT_BLE_HEADSET:
- LOG(VERBOSE) << __func__
- << ": device=AUDIO_DEVICE_OUT_BLE_HEADSET (MEDIA/VOICE) ("
- << StringPrintf("%#x", device) << ")";
- session_type_ = SessionType_2_1::LE_AUDIO_SOFTWARE_ENCODING_DATAPATH;
- break;
- case AUDIO_DEVICE_OUT_BLE_SPEAKER:
- LOG(VERBOSE) << __func__
- << ": device=AUDIO_DEVICE_OUT_BLE_SPEAKER (MEDIA) ("
- << StringPrintf("%#x", device) << ")";
- session_type_ = SessionType_2_1::LE_AUDIO_SOFTWARE_ENCODING_DATAPATH;
- break;
- case AUDIO_DEVICE_IN_BLE_HEADSET:
- LOG(VERBOSE) << __func__
- << ": device=AUDIO_DEVICE_IN_BLE_HEADSET (VOICE) ("
- << StringPrintf("%#x", device) << ")";
- session_type_ = SessionType_2_1::LE_AUDIO_SOFTWARE_DECODED_DATAPATH;
+ session_type_ = SessionType::HEARING_AID_SOFTWARE_ENCODING_DATAPATH;
break;
default:
LOG(ERROR) << __func__ << ": unknown device=" << StringPrintf("%#x", device);
return false;
}
- if (!BluetoothAudioSessionControl_2_1::IsSessionReady(session_type_)) {
+ if (!BluetoothAudioSessionControl::IsSessionReady(session_type_)) {
LOG(ERROR) << __func__ << ": device=" << StringPrintf("%#x", device) << ", session_type=" << toString(session_type_)
<< " is not ready";
return false;
@@ -203,7 +169,7 @@ bool BluetoothAudioPort::init_session_type(audio_devices_t device) {
return true;
}
-void BluetoothAudioPort::TearDown() {
+void BluetoothAudioPortOut::TearDown() {
if (!in_use()) {
LOG(ERROR) << __func__ << ": session_type=" << toString(session_type_)
<< ", cookie=" << StringPrintf("%#hx", cookie_) << " unknown monitor";
@@ -211,15 +177,15 @@ void BluetoothAudioPort::TearDown() {
}
LOG(INFO) << __func__ << ": session_type=" << toString(session_type_) << ", cookie=" << StringPrintf("%#hx", cookie_);
- BluetoothAudioSessionControl_2_1::UnregisterControlResultCback(session_type_,
- cookie_);
+ BluetoothAudioSessionControl::UnregisterControlResultCback(session_type_,
+ cookie_);
cookie_ = android::bluetooth::audio::kObserversCookieUndefined;
}
-void BluetoothAudioPort::ControlResultHandler(
+void BluetoothAudioPortOut::ControlResultHandler(
const BluetoothAudioStatus& status) {
if (!in_use()) {
- LOG(ERROR) << __func__ << ": BluetoothAudioPortis not in use";
+ LOG(ERROR) << __func__ << ": BluetoothAudioPortOut is not in use";
return;
}
std::unique_lock<std::mutex> port_lock(cv_mutex_);
@@ -262,9 +228,9 @@ void BluetoothAudioPort::ControlResultHandler(
internal_cv_.notify_all();
}
-void BluetoothAudioPort::SessionChangedHandler() {
+void BluetoothAudioPortOut::SessionChangedHandler() {
if (!in_use()) {
- LOG(ERROR) << __func__ << ": BluetoothAudioPort is not in use";
+ LOG(ERROR) << __func__ << ": BluetoothAudioPortOut is not in use";
return;
}
std::unique_lock<std::mutex> port_lock(cv_mutex_);
@@ -280,7 +246,7 @@ void BluetoothAudioPort::SessionChangedHandler() {
internal_cv_.notify_all();
}
-bool BluetoothAudioPort::in_use() const {
+bool BluetoothAudioPortOut::in_use() const {
return (cookie_ != android::bluetooth::audio::kObserversCookieUndefined);
}
@@ -293,75 +259,32 @@ bool BluetoothAudioPortOut::LoadAudioConfig(audio_config_t* audio_cfg) const {
return false;
}
- const ::android::hardware::bluetooth::audio::V2_1::AudioConfiguration&
- hal_audio_cfg =
- BluetoothAudioSessionControl_2_1::GetAudioConfig(session_type_);
+ const AudioConfiguration& hal_audio_cfg =
+ BluetoothAudioSessionControl::GetAudioConfig(session_type_);
if (hal_audio_cfg.getDiscriminator() !=
- ::android::hardware::bluetooth::audio::V2_1::AudioConfiguration::
- hidl_discriminator::pcmConfig) {
+ AudioConfiguration::hidl_discriminator::pcmConfig) {
audio_cfg->sample_rate = kBluetoothDefaultSampleRate;
audio_cfg->channel_mask = kBluetoothDefaultOutputChannelModeMask;
audio_cfg->format = kBluetoothDefaultAudioFormatBitsPerSample;
return false;
}
- const ::android::hardware::bluetooth::audio::V2_1::PcmParameters& pcm_cfg =
- hal_audio_cfg.pcmConfig();
+ const PcmParameters& pcm_cfg = hal_audio_cfg.pcmConfig();
LOG(VERBOSE) << __func__ << ": session_type=" << toString(session_type_)
<< ", cookie=" << StringPrintf("%#hx", cookie_) << ", state=" << state_ << ", PcmConfig=["
<< toString(pcm_cfg) << "]";
- if (pcm_cfg.sampleRate == SampleRate_2_1::RATE_UNKNOWN ||
+ if (pcm_cfg.sampleRate == SampleRate::RATE_UNKNOWN ||
pcm_cfg.channelMode == ChannelMode::UNKNOWN ||
pcm_cfg.bitsPerSample == BitsPerSample::BITS_UNKNOWN) {
return false;
}
audio_cfg->sample_rate = SampleRateToAudioFormat(pcm_cfg.sampleRate);
audio_cfg->channel_mask =
- (is_stereo_to_mono_
- ? AUDIO_CHANNEL_OUT_STEREO
- : OutputChannelModeToAudioFormat(pcm_cfg.channelMode));
+ (is_stereo_to_mono_ ? AUDIO_CHANNEL_OUT_STEREO : ChannelModeToAudioFormat(pcm_cfg.channelMode));
audio_cfg->format = BitsPerSampleToAudioFormat(pcm_cfg.bitsPerSample);
return true;
}
-bool BluetoothAudioPortIn::LoadAudioConfig(audio_config_t* audio_cfg) const {
- if (!in_use()) {
- LOG(ERROR) << __func__ << ": BluetoothAudioPortIn is not in use";
- audio_cfg->sample_rate = kBluetoothDefaultSampleRate;
- audio_cfg->channel_mask = kBluetoothDefaultInputChannelModeMask;
- audio_cfg->format = kBluetoothDefaultAudioFormatBitsPerSample;
- return false;
- }
-
- const ::android::hardware::bluetooth::audio::V2_1::AudioConfiguration&
- hal_audio_cfg =
- BluetoothAudioSessionControl_2_1::GetAudioConfig(session_type_);
- if (hal_audio_cfg.getDiscriminator() !=
- ::android::hardware::bluetooth::audio::V2_1::AudioConfiguration::
- hidl_discriminator::pcmConfig) {
- audio_cfg->sample_rate = kBluetoothDefaultSampleRate;
- audio_cfg->channel_mask = kBluetoothDefaultInputChannelModeMask;
- audio_cfg->format = kBluetoothDefaultAudioFormatBitsPerSample;
- return false;
- }
- const ::android::hardware::bluetooth::audio::V2_1::PcmParameters& pcm_cfg =
- hal_audio_cfg.pcmConfig();
- LOG(VERBOSE) << __func__ << ": session_type=" << toString(session_type_)
- << ", cookie=" << StringPrintf("%#hx", cookie_)
- << ", state=" << state_ << ", PcmConfig=[" << toString(pcm_cfg)
- << "]";
- if (pcm_cfg.sampleRate == SampleRate_2_1::RATE_UNKNOWN ||
- pcm_cfg.channelMode == ChannelMode::UNKNOWN ||
- pcm_cfg.bitsPerSample == BitsPerSample::BITS_UNKNOWN) {
- return false;
- }
-
- audio_cfg->sample_rate = SampleRateToAudioFormat(pcm_cfg.sampleRate);
- audio_cfg->channel_mask = InputChannelModeToAudioFormat(pcm_cfg.channelMode);
- audio_cfg->format = BitsPerSampleToAudioFormat(pcm_cfg.bitsPerSample);
- return true;
-}
-
-bool BluetoothAudioPort::CondwaitState(BluetoothStreamState state) {
+bool BluetoothAudioPortOut::CondwaitState(BluetoothStreamState state) {
bool retval;
std::unique_lock<std::mutex> port_lock(cv_mutex_);
switch (state) {
@@ -390,9 +313,9 @@ bool BluetoothAudioPort::CondwaitState(BluetoothStreamState state) {
return retval; // false if any failure like timeout
}
-bool BluetoothAudioPort::Start() {
+bool BluetoothAudioPortOut::Start() {
if (!in_use()) {
- LOG(ERROR) << __func__ << ": BluetoothAudioPort is not in use";
+ LOG(ERROR) << __func__ << ": BluetoothAudioPortOut is not in use";
return false;
}
@@ -401,7 +324,7 @@ bool BluetoothAudioPort::Start() {
bool retval = false;
if (state_ == BluetoothStreamState::STANDBY) {
state_ = BluetoothStreamState::STARTING;
- if (BluetoothAudioSessionControl_2_1::StartStream(session_type_)) {
+ if (BluetoothAudioSessionControl::StartStream(session_type_)) {
retval = CondwaitState(BluetoothStreamState::STARTING);
} else {
LOG(ERROR) << __func__ << ": session_type=" << toString(session_type_)
@@ -421,9 +344,9 @@ bool BluetoothAudioPort::Start() {
return retval; // false if any failure like timeout
}
-bool BluetoothAudioPort::Suspend() {
+bool BluetoothAudioPortOut::Suspend() {
if (!in_use()) {
- LOG(ERROR) << __func__ << ": BluetoothAudioPort is not in use";
+ LOG(ERROR) << __func__ << ": BluetoothAudioPortOut is not in use";
return false;
}
@@ -432,7 +355,7 @@ bool BluetoothAudioPort::Suspend() {
bool retval = false;
if (state_ == BluetoothStreamState::STARTED) {
state_ = BluetoothStreamState::SUSPENDING;
- if (BluetoothAudioSessionControl_2_1::SuspendStream(session_type_)) {
+ if (BluetoothAudioSessionControl::SuspendStream(session_type_)) {
retval = CondwaitState(BluetoothStreamState::SUSPENDING);
} else {
LOG(ERROR) << __func__ << ": session_type=" << toString(session_type_)
@@ -451,15 +374,15 @@ bool BluetoothAudioPort::Suspend() {
return retval; // false if any failure like timeout
}
-void BluetoothAudioPort::Stop() {
+void BluetoothAudioPortOut::Stop() {
if (!in_use()) {
- LOG(ERROR) << __func__ << ": BluetoothAudioPort is not in use";
+ LOG(ERROR) << __func__ << ": BluetoothAudioPortOut is not in use";
return;
}
LOG(INFO) << __func__ << ": session_type=" << toString(session_type_) << ", cookie=" << StringPrintf("%#hx", cookie_)
<< ", state=" << state_ << " request";
state_ = BluetoothStreamState::DISABLED;
- BluetoothAudioSessionControl_2_1::StopStream(session_type_);
+ BluetoothAudioSessionControl::StopStream(session_type_);
LOG(INFO) << __func__ << ": session_type=" << toString(session_type_) << ", cookie=" << StringPrintf("%#hx", cookie_)
<< ", state=" << state_ << " done";
}
@@ -467,8 +390,7 @@ void BluetoothAudioPort::Stop() {
size_t BluetoothAudioPortOut::WriteData(const void* buffer, size_t bytes) const {
if (!in_use()) return 0;
if (!is_stereo_to_mono_) {
- return BluetoothAudioSessionControl_2_1::OutWritePcmData(session_type_,
- buffer, bytes);
+ return BluetoothAudioSessionControl::OutWritePcmData(session_type_, buffer, bytes);
}
// WAR to mix the stereo into Mono (16 bits per sample)
@@ -478,25 +400,17 @@ size_t BluetoothAudioPortOut::WriteData(const void* buffer, size_t bytes) const
std::unique_ptr<int16_t[]> dst{new int16_t[write_frames]};
downmix_to_mono_i16_from_stereo_i16(dst.get(), src, write_frames);
// a frame is 16 bits, and the size of a mono frame is equal to half a stereo.
- return BluetoothAudioSessionControl_2_1::OutWritePcmData(
- session_type_, dst.get(), write_frames * 2) *
- 2;
+ return BluetoothAudioSessionControl::OutWritePcmData(session_type_, dst.get(), write_frames * 2) * 2;
}
-size_t BluetoothAudioPortIn::ReadData(void* buffer, size_t bytes) const {
- if (!in_use()) return 0;
- return BluetoothAudioSessionControl_2_1::InReadPcmData(session_type_, buffer,
- bytes);
-}
-
-bool BluetoothAudioPort::GetPresentationPosition(uint64_t* delay_ns,
- uint64_t* bytes,
- timespec* timestamp) const {
+bool BluetoothAudioPortOut::GetPresentationPosition(uint64_t* delay_ns,
+ uint64_t* bytes,
+ timespec* timestamp) const {
if (!in_use()) {
- LOG(ERROR) << __func__ << ": BluetoothAudioPort is not in use";
+ LOG(ERROR) << __func__ << ": BluetoothAudioPortOut is not in use";
return false;
}
- bool retval = BluetoothAudioSessionControl_2_1::GetPresentationPosition(
+ bool retval = BluetoothAudioSessionControl::GetPresentationPosition(
session_type_, delay_ns, bytes, timestamp);
LOG(VERBOSE) << __func__ << ": session_type=" << StringPrintf("%#hhx", session_type_)
<< ", cookie=" << StringPrintf("%#hx", cookie_) << ", state=" << state_ << ", delay=" << *delay_ns
@@ -506,22 +420,22 @@ bool BluetoothAudioPort::GetPresentationPosition(uint64_t* delay_ns,
return retval;
}
-void BluetoothAudioPort::UpdateMetadata(
+void BluetoothAudioPortOut::UpdateMetadata(
const source_metadata* source_metadata) const {
if (!in_use()) {
- LOG(ERROR) << __func__ << ": BluetoothAudioPort is not in use";
+ LOG(ERROR) << __func__ << ": BluetoothAudioPortOut is not in use";
return;
}
LOG(DEBUG) << __func__ << ": session_type=" << toString(session_type_) << ", cookie=" << StringPrintf("%#hx", cookie_)
<< ", state=" << state_ << ", " << source_metadata->track_count << " track(s)";
if (source_metadata->track_count == 0) return;
- BluetoothAudioSessionControl_2_1::UpdateTracksMetadata(session_type_,
- source_metadata);
+ BluetoothAudioSessionControl::UpdateTracksMetadata(session_type_,
+ source_metadata);
}
-BluetoothStreamState BluetoothAudioPort::GetState() const { return state_; }
+BluetoothStreamState BluetoothAudioPortOut::GetState() const { return state_; }
-void BluetoothAudioPort::SetState(BluetoothStreamState state) {
+void BluetoothAudioPortOut::SetState(BluetoothStreamState state) {
state_ = state;
}
diff --git a/audio_bluetooth_hw/device_port_proxy.h b/audio_bluetooth_hw/device_port_proxy.h
index 9e113926f..160df4ba7 100644
--- a/audio_bluetooth_hw/device_port_proxy.h
+++ b/audio_bluetooth_hw/device_port_proxy.h
@@ -16,7 +16,7 @@
#pragma once
-#include <android/hardware/bluetooth/audio/2.1/types.h>
+#include <android/hardware/bluetooth/audio/2.0/types.h>
#include <hardware/audio.h>
#include <condition_variable>
#include <mutex>
@@ -28,31 +28,30 @@ namespace android {
namespace bluetooth {
namespace audio {
-using SessionType_2_1 =
- ::android::hardware::bluetooth::audio::V2_1::SessionType;
+using ::android::hardware::bluetooth::audio::V2_0::SessionType;
// Proxy for Bluetooth Audio HW Module to communicate with Bluetooth Audio
// Session Control. All methods are not thread safe, so users must acquire a
// lock. Note: currently, in stream_apis.cc, if GetState() is only used for
// verbose logging, it is not locked, so the state may not be synchronized.
-class BluetoothAudioPort {
+class BluetoothAudioPortOut {
public:
- BluetoothAudioPort();
- virtual ~BluetoothAudioPort() = default;
+ BluetoothAudioPortOut();
+ ~BluetoothAudioPortOut() = default;
- // Fetch output control / data path of BluetoothAudioPort and setup
+ // Fetch output control / data path of BluetoothAudioPortOut and setup
// callbacks into BluetoothAudioProvider. If SetUp() returns false, the audio
- // HAL must delete this BluetoothAudioPort and return EINVAL to caller
+ // HAL must delete this BluetoothAudioPortOut and return EINVAL to caller
bool SetUp(audio_devices_t devices);
- // Unregister this BluetoothAudioPort from BluetoothAudioSessionControl.
- // Audio HAL must delete this BluetoothAudioPort after calling this.
+ // Unregister this BluetoothAudioPortOut from BluetoothAudioSessionControl.
+ // Audio HAL must delete this BluetoothAudioPortOut after calling this.
void TearDown();
// When the Audio framework / HAL tries to query audio config about format,
// channel mask and sample rate, it uses this function to fetch from the
// Bluetooth stack
- virtual bool LoadAudioConfig(audio_config_t* audio_cfg) const = 0;
+ bool LoadAudioConfig(audio_config_t* audio_cfg) const;
// WAR to support Mono mode / 16 bits per sample
void ForcePcmStereoToMono(bool force) {
@@ -69,8 +68,11 @@ class BluetoothAudioPort {
// Called by Audio framework / HAL to stop the stream
void Stop();
+ // The audio data path to the Bluetooth stack (Software encoding)
+ size_t WriteData(const void* buffer, size_t bytes) const;
+
// Called by the Audio framework / HAL to fetch informaiton about audio frames
- // presented to an external sink, or frames presented fror an internal sink
+ // presented to an external sink.
bool GetPresentationPosition(uint64_t* delay_ns, uint64_t* bytes,
timespec* timestamp) const;
@@ -85,26 +87,25 @@ class BluetoothAudioPort {
void SetState(BluetoothStreamState state);
bool IsA2dp() const {
- return session_type_ == SessionType_2_1::A2DP_SOFTWARE_ENCODING_DATAPATH ||
- session_type_ == SessionType_2_1::A2DP_HARDWARE_OFFLOAD_DATAPATH;
+ return session_type_ == SessionType::A2DP_SOFTWARE_ENCODING_DATAPATH ||
+ session_type_ == SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH;
}
- protected:
- uint16_t cookie_;
- BluetoothStreamState state_;
- SessionType_2_1 session_type_;
- // WR to support Mono: True if fetching Stereo and mixing into Mono
- bool is_stereo_to_mono_ = false;
- bool in_use() const;
-
private:
+ BluetoothStreamState state_;
+ SessionType session_type_;
+ uint16_t cookie_;
mutable std::mutex cv_mutex_;
std::condition_variable internal_cv_;
+ // WR to support Mono: True if fetching Stereo and mixing into Mono
+ bool is_stereo_to_mono_ = false;
// Check and initialize session type for |devices| If failed, this
- // BluetoothAudioPort is not initialized and must be deleted.
+ // BluetoothAudioPortOut is not initialized and must be deleted.
bool init_session_type(audio_devices_t device);
+ bool in_use() const;
+
bool CondwaitState(BluetoothStreamState state);
void ControlResultHandler(
@@ -112,24 +113,6 @@ class BluetoothAudioPort {
void SessionChangedHandler();
};
-class BluetoothAudioPortOut : public BluetoothAudioPort {
- public:
- ~BluetoothAudioPortOut() = default;
-
- // The audio data path to the Bluetooth stack (Software encoding)
- size_t WriteData(const void* buffer, size_t bytes) const;
- bool LoadAudioConfig(audio_config_t* audio_cfg) const;
-};
-
-class BluetoothAudioPortIn : public BluetoothAudioPort {
- public:
- ~BluetoothAudioPortIn() = default;
-
- // The audio data path from the Bluetooth stack (Software decoded)
- size_t ReadData(void* buffer, size_t bytes) const;
- bool LoadAudioConfig(audio_config_t* audio_cfg) const;
-};
-
} // namespace audio
} // namespace bluetooth
} // namespace android
diff --git a/audio_bluetooth_hw/stream_apis.cc b/audio_bluetooth_hw/stream_apis.cc
index aafe547f7..d809b57dc 100644
--- a/audio_bluetooth_hw/stream_apis.cc
+++ b/audio_bluetooth_hw/stream_apis.cc
@@ -127,53 +127,6 @@ void out_calculate_feeding_delay_ms(const BluetoothStreamOut* out,
}
}
-void in_calculate_starving_delay_ms(const BluetoothStreamIn* in,
- int64_t* frames, int64_t* time) {
- // delay_report is the audio delay from the remote headset receiving data to
- // the headset playing sound in units of nanoseconds
- uint64_t delay_report_ns = 0;
- uint64_t delay_report_ms = 0;
- // dispersed_bytes is the total number of bytes received by the Bluetooth
- // stack from a remote headset
- uint64_t dispersed_bytes = 0;
- struct timespec dispersed_timestamp = {};
-
- std::unique_lock<std::mutex> lock(in->mutex_);
- in->bluetooth_input_.GetPresentationPosition(
- &delay_report_ns, &dispersed_bytes, &dispersed_timestamp);
- delay_report_ms = delay_report_ns / 1000000;
-
- const uint64_t latency_frames = delay_report_ms * in->sample_rate_ / 1000;
- *frames = dispersed_bytes / audio_stream_in_frame_size(&in->stream_in_);
-
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", delay=" << delay_report_ms
- << "ms, data=" << dispersed_bytes
- << " bytes, timestamp=" << dispersed_timestamp.tv_sec << "."
- << StringPrintf("%09ld", dispersed_timestamp.tv_nsec) << "s";
-
- if (in->frames_presented_ < *frames) {
- // Was audio HAL reset?! The stack counter is obsoleted.
- *frames = in->frames_presented_;
- } else if ((in->frames_presented_ - *frames) > latency_frames) {
- // Is the Bluetooth input reset ?! Its counter was reset but could not be
- // used.
- *frames = in->frames_presented_;
- }
- // suppose frames would be queued in the headset buffer for delay_report
- // period, so those frames in buffers should not be included in the number
- // of presented frames at the timestamp.
- if (*frames > latency_frames) {
- *frames -= latency_frames;
- } else {
- *frames = 0;
- }
-
- *time = (dispersed_timestamp.tv_sec * 1000000000LL +
- dispersed_timestamp.tv_nsec) /
- 1000;
-}
-
} // namespace
std::ostream& operator<<(std::ostream& os, const BluetoothStreamState& state) {
@@ -341,12 +294,8 @@ static int out_set_parameters(struct audio_stream* stream,
if (params["A2dpSuspended"] == "true") {
LOG(INFO) << __func__ << ": state=" << out->bluetooth_output_.GetState()
<< " stream param stopped";
- out->frames_rendered_ = 0;
- if (out->bluetooth_output_.GetState() == BluetoothStreamState::STARTED) {
- out->bluetooth_output_.Suspend();
- out->bluetooth_output_.SetState(BluetoothStreamState::DISABLED);
- } else if (out->bluetooth_output_.GetState() !=
- BluetoothStreamState::DISABLED) {
+ if (out->bluetooth_output_.GetState() != BluetoothStreamState::DISABLED) {
+ out->frames_rendered_ = 0;
out->bluetooth_output_.Stop();
}
} else {
@@ -502,10 +451,6 @@ static ssize_t out_write(struct audio_stream_out* stream, const void* buffer,
if (stream->resume(stream)) {
LOG(ERROR) << __func__ << ": state=" << out->bluetooth_output_.GetState()
<< " failed to resume";
- if (out->bluetooth_output_.GetState() == BluetoothStreamState::DISABLED) {
- // drop data for cases of A2dpSuspended=true / closing=true
- totalWritten = bytes;
- }
usleep(kBluetoothDefaultOutputBufferMs * 1000);
return totalWritten;
}
@@ -774,368 +719,9 @@ void adev_close_output_stream(struct audio_hw_device* dev,
size_t adev_get_input_buffer_size(const struct audio_hw_device* dev,
const struct audio_config* config) {
- /* TODO: Adjust this value */
- LOG(VERBOSE) << __func__;
return 320;
}
-static uint32_t in_get_sample_rate(const struct audio_stream* stream) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
-
- return in->sample_rate_;
-}
-
-static int in_set_sample_rate(struct audio_stream* stream, uint32_t rate) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
-
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", sample_rate=" << in->sample_rate_;
- return (rate == in->sample_rate_ ? 0 : -ENOSYS);
-}
-
-static size_t in_get_buffer_size(const struct audio_stream* stream) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- size_t buffer_size =
- in->frames_count_ * audio_stream_in_frame_size(&in->stream_in_);
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", buffer_size=" << buffer_size;
- return buffer_size;
-}
-
-static audio_channel_mask_t in_get_channels(const struct audio_stream* stream) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- audio_config_t audio_cfg;
- if (in->bluetooth_input_.LoadAudioConfig(&audio_cfg)) {
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " audio_cfg=" << audio_cfg;
- return audio_cfg.channel_mask;
- } else {
- LOG(WARNING) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", channels=" << StringPrintf("%#x", in->channel_mask_)
- << " failure";
- return in->channel_mask_;
- }
-}
-
-static audio_format_t in_get_format(const struct audio_stream* stream) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- audio_config_t audio_cfg;
- if (in->bluetooth_input_.LoadAudioConfig(&audio_cfg)) {
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " audio_cfg=" << audio_cfg;
- return audio_cfg.format;
- } else {
- LOG(WARNING) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", format=" << in->format_ << " failure";
- return in->format_;
- }
-}
-
-static int in_set_format(struct audio_stream* stream, audio_format_t format) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", format=" << in->format_;
- return (format == in->format_ ? 0 : -ENOSYS);
-}
-
-static bool in_state_transition_timeout(BluetoothStreamIn* in,
- std::unique_lock<std::mutex>& lock,
- const BluetoothStreamState& state,
- uint16_t timeout_ms) {
- /* Don't loose suspend request, AF will not retry */
- while (in->bluetooth_input_.GetState() == state) {
- lock.unlock();
- usleep(1000);
- lock.lock();
-
- /* Don't block AF forever */
- if (--timeout_ms <= 0) {
- LOG(WARNING) << __func__
- << ", can't suspend - stucked in suspending"
- " state";
- return false;
- }
- }
-
- return true;
-}
-
-static int in_standby(struct audio_stream* stream) {
- auto* in = reinterpret_cast<BluetoothStreamIn*>(stream);
- std::unique_lock<std::mutex> lock(in->mutex_);
- int retval = 0;
-
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " being standby (suspend)";
-
- /* Give some time to start up */
- if (!in_state_transition_timeout(in, lock, BluetoothStreamState::STARTING,
- kBluetoothDefaultInputStateTimeoutMs)) {
- LOG(ERROR) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " NOT ready to by standby";
- return retval;
- }
-
- if (in->bluetooth_input_.GetState() == BluetoothStreamState::STARTED) {
- retval = (in->bluetooth_input_.Suspend() ? 0 : -EIO);
- } else if (in->bluetooth_input_.GetState() !=
- BluetoothStreamState::SUSPENDING) {
- LOG(DEBUG) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " standby already";
- return retval;
- }
-
- /* Give some time to suspend */
- if (!in_state_transition_timeout(in, lock, BluetoothStreamState::SUSPENDING,
- kBluetoothDefaultInputStateTimeoutMs)) {
- LOG(ERROR) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " NOT ready to by standby";
- return 0;
- }
-
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " standby (suspend) retval=" << retval;
-
- return retval;
-}
-
-static int in_dump(const struct audio_stream* stream, int fd) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState();
-
- return 0;
-}
-
-static int in_set_parameters(struct audio_stream* stream, const char* kvpairs) {
- auto* in = reinterpret_cast<BluetoothStreamIn*>(stream);
- std::unique_lock<std::mutex> lock(in->mutex_);
- int retval = 0;
-
- LOG(INFO) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState()
- << ", kvpairs=[" << kvpairs << "]";
-
- std::unordered_map<std::string, std::string> params =
- ParseAudioParams(kvpairs);
-
- if (params.empty()) return retval;
-
- LOG(INFO) << __func__ << ": ParamsMap=[" << GetAudioParamString(params)
- << "]";
-
- return retval;
-}
-
-static char* in_get_parameters(const struct audio_stream* stream,
- const char* keys) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- std::unique_lock<std::mutex> lock(in->mutex_);
-
- LOG(VERBOSE) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState()
- << ", keys=[" << keys << "]";
-
- std::unordered_map<std::string, std::string> params = ParseAudioParams(keys);
- if (params.empty()) return strdup("");
-
- audio_config_t audio_cfg;
- if (in->bluetooth_input_.LoadAudioConfig(&audio_cfg)) {
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " audio_cfg=" << audio_cfg;
- } else {
- LOG(ERROR) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " failed to get audio config";
- }
-
- std::unordered_map<std::string, std::string> return_params;
-
- /* TODO: Implement parameter getter */
-
- std::string result;
- for (const auto& ptr : return_params) {
- result += ptr.first + "=" + ptr.second + ";";
- }
-
- return strdup(result.c_str());
-}
-
-static int in_add_audio_effect(const struct audio_stream* stream,
- effect_handle_t effect) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", effect=" << effect;
- return 0;
-}
-
-static int in_remove_audio_effect(const struct audio_stream* stream,
- effect_handle_t effect) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", effect=" << effect;
- return 0;
-}
-
-static int in_set_gain(struct audio_stream_in* stream, float gain) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState();
-
- return 0;
-}
-
-static ssize_t in_read(struct audio_stream_in* stream, void* buffer,
- size_t bytes) {
- auto* in = reinterpret_cast<BluetoothStreamIn*>(stream);
- std::unique_lock<std::mutex> lock(in->mutex_);
- size_t totalRead = 0;
-
- /* Give some time to start up */
- if (!in_state_transition_timeout(in, lock, BluetoothStreamState::STARTING,
- kBluetoothDefaultInputStateTimeoutMs))
- return -EBUSY;
-
- if (in->bluetooth_input_.GetState() != BluetoothStreamState::STARTED) {
- LOG(INFO) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " first time bytes=" << bytes;
-
- int retval = 0;
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", starting";
- if (in->bluetooth_input_.GetState() == BluetoothStreamState::STANDBY) {
- retval = (in->bluetooth_input_.Start() ? 0 : -EIO);
- } else if (in->bluetooth_input_.GetState() ==
- BluetoothStreamState::SUSPENDING) {
- LOG(WARNING) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " NOT ready to start?!";
- retval = -EBUSY;
- } else if (in->bluetooth_input_.GetState() ==
- BluetoothStreamState::DISABLED) {
- LOG(WARNING) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " NOT allow to start?!";
- retval = -EINVAL;
- } else {
- LOG(DEBUG) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " started already";
- }
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", starting (start) retval=" << retval;
-
- if (retval) {
- LOG(ERROR) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " failed to start";
- return retval;
- }
- }
-
- lock.unlock();
- totalRead = in->bluetooth_input_.ReadData(buffer, bytes);
- lock.lock();
-
- struct timespec ts = {.tv_sec = 0, .tv_nsec = 0};
- clock_gettime(CLOCK_MONOTONIC, &ts);
- in->last_read_time_us_ = (ts.tv_sec * 1000000000LL + ts.tv_nsec) / 1000;
-
- const size_t frames = totalRead / audio_stream_in_frame_size(stream);
- in->frames_presented_ += frames;
-
- return totalRead;
-}
-
-static uint32_t in_get_input_frames_lost(struct audio_stream_in* stream) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState();
-
- return 0;
-}
-
-static int in_get_capture_position(const struct audio_stream_in* stream,
- int64_t* frames, int64_t* time) {
- if (stream == NULL || frames == NULL || time == NULL) {
- return -EINVAL;
- }
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
-
- if (in->bluetooth_input_.GetState() == BluetoothStreamState::STANDBY) {
- LOG(WARNING) << __func__ << ": state= " << in->bluetooth_input_.GetState();
- return -ENOSYS;
- }
-
- in_calculate_starving_delay_ms(in, frames, time);
-
- return 0;
-}
-
-static int in_start(const struct audio_stream_in* stream) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState();
-
- return 0;
-}
-
-static int in_stop(const struct audio_stream_in* stream) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState();
-
- return 0;
-}
-
-static int in_create_mmap_buffer(const struct audio_stream_in* stream,
- int32_t min_size_frames,
- struct audio_mmap_buffer_info* info) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState();
-
- return -ENOSYS;
-}
-
-static int in_get_mmap_position(const struct audio_stream_in* stream,
- struct audio_mmap_position* position) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState();
-
- return -ENOSYS;
-}
-
-static int in_get_active_microphones(
- const struct audio_stream_in* stream,
- struct audio_microphone_characteristic_t* mic_array, size_t* mic_count) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState();
-
- return -ENOSYS;
-}
-
-static int in_set_microphone_direction(const struct audio_stream_in* stream,
- audio_microphone_direction_t direction) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState();
-
- return -ENOSYS;
-}
-
-static int in_set_microphone_field_dimension(
- const struct audio_stream_in* stream, float zoom) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState();
-
- return -ENOSYS;
-}
-
-static void in_update_sink_metadata(struct audio_stream_in* stream,
- const struct sink_metadata* sink_metadata) {
- const auto* in = reinterpret_cast<const BluetoothStreamIn*>(stream);
- LOG(VERBOSE) << __func__
- << ": NOT HANDLED! state=" << in->bluetooth_input_.GetState();
-}
-
int adev_open_input_stream(struct audio_hw_device* dev,
audio_io_handle_t handle, audio_devices_t devices,
struct audio_config* config,
@@ -1143,75 +729,8 @@ int adev_open_input_stream(struct audio_hw_device* dev,
audio_input_flags_t flags __unused,
const char* address __unused,
audio_source_t source __unused) {
- *stream_in = nullptr;
- auto* in = new BluetoothStreamIn{};
- if (!in->bluetooth_input_.SetUp(devices)) {
- delete in;
- return -EINVAL;
- }
-
- LOG(INFO) << __func__ << ": device=" << StringPrintf("%#x", devices);
-
- in->stream_in_.common.get_sample_rate = in_get_sample_rate;
- in->stream_in_.common.set_sample_rate = in_set_sample_rate;
- in->stream_in_.common.get_buffer_size = in_get_buffer_size;
- in->stream_in_.common.get_channels = in_get_channels;
- in->stream_in_.common.get_format = in_get_format;
- in->stream_in_.common.set_format = in_set_format;
- in->stream_in_.common.standby = in_standby;
- in->stream_in_.common.dump = in_dump;
- in->stream_in_.common.set_parameters = in_set_parameters;
- in->stream_in_.common.get_parameters = in_get_parameters;
- in->stream_in_.common.add_audio_effect = in_add_audio_effect;
- in->stream_in_.common.remove_audio_effect = in_remove_audio_effect;
- in->stream_in_.set_gain = in_set_gain;
- in->stream_in_.read = in_read;
- in->stream_in_.get_input_frames_lost = in_get_input_frames_lost;
- in->stream_in_.get_capture_position = in_get_capture_position;
- in->stream_in_.start = in_start;
- in->stream_in_.stop = in_stop;
- in->stream_in_.create_mmap_buffer = in_create_mmap_buffer;
- in->stream_in_.get_mmap_position = in_get_mmap_position;
- in->stream_in_.get_active_microphones = in_get_active_microphones;
- in->stream_in_.set_microphone_direction = in_set_microphone_direction;
- in->stream_in_.set_microphone_field_dimension =
- in_set_microphone_field_dimension;
- in->stream_in_.update_sink_metadata = in_update_sink_metadata;
-
- if (!in->bluetooth_input_.LoadAudioConfig(config)) {
- LOG(ERROR) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << " failed to get audio config";
- return -EINVAL;
- }
-
- in->sample_rate_ = config->sample_rate;
- in->channel_mask_ = config->channel_mask;
- in->format_ = config->format;
- // frame is number of samples per channel
- in->frames_count_ =
- samples_per_ticks(kBluetoothDefaultInputBufferMs, in->sample_rate_, 1);
- in->frames_presented_ = 0;
-
- *stream_in = &in->stream_in_;
- LOG(INFO) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", sample_rate=" << in->sample_rate_
- << ", channels=" << StringPrintf("%#x", in->channel_mask_)
- << ", format=" << in->format_ << ", frames=" << in->frames_count_;
-
- return 0;
+ return -EINVAL;
}
void adev_close_input_stream(struct audio_hw_device* dev,
- struct audio_stream_in* stream) {
- auto* in = reinterpret_cast<BluetoothStreamIn*>(stream);
-
- if (in->bluetooth_input_.GetState() != BluetoothStreamState::DISABLED) {
- in->bluetooth_input_.Stop();
- }
-
- in->bluetooth_input_.TearDown();
- LOG(VERBOSE) << __func__ << ": state=" << in->bluetooth_input_.GetState()
- << ", stopped";
-
- delete in;
-}
+ struct audio_stream_in* stream_in) {}
diff --git a/audio_bluetooth_hw/stream_apis.h b/audio_bluetooth_hw/stream_apis.h
index 55512d7fb..c894d1e4b 100644
--- a/audio_bluetooth_hw/stream_apis.h
+++ b/audio_bluetooth_hw/stream_apis.h
@@ -27,13 +27,10 @@ constexpr audio_format_t kBluetoothDefaultAudioFormatBitsPerSample =
AUDIO_FORMAT_PCM_16_BIT;
constexpr unsigned int kBluetoothDefaultInputBufferMs = 20;
-constexpr unsigned int kBluetoothDefaultInputStateTimeoutMs = 20;
constexpr unsigned int kBluetoothDefaultOutputBufferMs = 10;
constexpr audio_channel_mask_t kBluetoothDefaultOutputChannelModeMask =
AUDIO_CHANNEL_OUT_STEREO;
-constexpr audio_channel_mask_t kBluetoothDefaultInputChannelModeMask =
- AUDIO_CHANNEL_IN_MONO;
enum class BluetoothStreamState : uint8_t {
DISABLED = 0, // This stream is closing or set param "suspend=true"
@@ -76,24 +73,6 @@ struct BluetoothAudioDevice {
std::list<BluetoothStreamOut*>(0);
};
-struct BluetoothStreamIn {
- // Must be the first member so it can be cast from audio_stream
- // or audio_stream_in pointer
- audio_stream_in stream_in_;
- ::android::bluetooth::audio::BluetoothAudioPortIn bluetooth_input_;
- int64_t last_read_time_us_;
- // Audio PCM Configs
- uint32_t sample_rate_;
- audio_channel_mask_t channel_mask_;
- audio_format_t format_;
- // frame is the number of samples per channel
- // frames count per tick
- size_t frames_count_;
- // total frames read after opened, never reset
- uint64_t frames_presented_;
- mutable std::mutex mutex_;
-};
-
int adev_open_output_stream(struct audio_hw_device* dev,
audio_io_handle_t handle, audio_devices_t devices,
audio_output_flags_t flags,
diff --git a/audio_hal_interface/Android.bp b/audio_hal_interface/Android.bp
index 8df759afc..92cf1b11d 100644
--- a/audio_hal_interface/Android.bp
+++ b/audio_hal_interface/Android.bp
@@ -1,14 +1,5 @@
// Bluetooth Audio library for target
// ========================================================
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "libbt-audio-hal-interface",
defaults: ["fluoride_defaults"],
@@ -18,38 +9,22 @@ cc_library_static {
"system/bt/bta/sys",
"system/bt/btif/include",
"system/bt/stack/include",
- "system/bt/gd/rust/shim",
+ ],
+ srcs: [
+ "a2dp_encoding.cc",
+ "client_interface.cc",
+ "codec_status.cc",
+ "hearing_aid_software_encoding.cc",
],
shared_libs: [
"android.hardware.bluetooth.audio@2.0",
- "android.hardware.bluetooth.audio@2.1",
+ "libfmq",
"libhidlbase",
],
static_libs: [
"libosi",
"libbt-common",
],
- target: {
- android: {
- shared_libs: [
- "libfmq",
- ],
- srcs: [
- "a2dp_encoding.cc",
- "client_interface.cc",
- "codec_status.cc",
- "hearing_aid_software_encoding.cc",
- "le_audio_software.cc",
- ],
- },
- host: {
- srcs: [
- "a2dp_encoding_host.cc",
- "hearing_aid_software_encoding_host.cc",
- ],
- },
- },
- host_supported: true,
cflags: [
"-DBUILDCFG",
],
@@ -69,7 +44,6 @@ cc_test {
],
shared_libs: [
"android.hardware.bluetooth.audio@2.0",
- "android.hardware.bluetooth.audio@2.1",
"libcutils",
"libfmq",
"libhidlbase",
diff --git a/audio_hal_interface/BUILD.gn b/audio_hal_interface/BUILD.gn
deleted file mode 100644
index 18abf77e3..000000000
--- a/audio_hal_interface/BUILD.gn
+++ /dev/null
@@ -1,36 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-static_library("audio_hal_interface") {
- sources = [
- "a2dp_encoding_host.cc",
- "hearing_aid_software_encoding_host.cc",
- ]
-
- include_dirs = [
- "//bt/bta/include",
- "//bt/btif/include",
- "//bt/stack/include",
- "//bt/gd/rust/shim",
- ]
-
- configs += [ "//bt:target_defaults" ]
-
- deps = [
- "//bt/common",
- "//bt/osi:osi",
- ]
-}
diff --git a/audio_hal_interface/a2dp_encoding.cc b/audio_hal_interface/a2dp_encoding.cc
index 44a4828fc..456ba60f1 100644
--- a/audio_hal_interface/a2dp_encoding.cc
+++ b/audio_hal_interface/a2dp_encoding.cc
@@ -13,18 +13,15 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-#define LOG_TAG "a2dp_encoding"
#include "a2dp_encoding.h"
#include "client_interface.h"
#include "codec_status.h"
-#include "a2dp_sbc_constants.h"
#include "btif_a2dp_source.h"
#include "btif_av.h"
#include "btif_av_co.h"
#include "btif_hf.h"
-#include "osi/include/log.h"
#include "osi/include/properties.h"
namespace {
@@ -38,7 +35,7 @@ using ::bluetooth::audio::PcmParameters;
using ::bluetooth::audio::SampleRate;
using ::bluetooth::audio::SessionType;
-using ::bluetooth::audio::BluetoothAudioSinkClientInterface;
+using ::bluetooth::audio::BluetoothAudioClientInterface;
using ::bluetooth::audio::codec::A2dpAacToHalConfig;
using ::bluetooth::audio::codec::A2dpAptxToHalConfig;
using ::bluetooth::audio::codec::A2dpCodecToHalBitsPerSample;
@@ -51,11 +48,10 @@ using ::bluetooth::audio::codec::CodecConfiguration;
BluetoothAudioCtrlAck a2dp_ack_to_bt_audio_ctrl_ack(tA2DP_CTRL_ACK ack);
// Provide call-in APIs for the Bluetooth Audio HAL
-class A2dpTransport
- : public ::bluetooth::audio::IBluetoothSinkTransportInstance {
+class A2dpTransport : public ::bluetooth::audio::IBluetoothTransportInstance {
public:
A2dpTransport(SessionType sessionType)
- : IBluetoothSinkTransportInstance(sessionType, {}),
+ : IBluetoothTransportInstance(sessionType, {}),
total_bytes_read_(0),
data_position_({}) {
a2dp_pending_cmd_ = A2DP_CTRL_CMD_NONE;
@@ -128,7 +124,6 @@ class A2dpTransport
void StopRequest() override {
if (btif_av_get_peer_sep() == AVDT_TSEP_SNK &&
!btif_av_stream_started_ready()) {
- btif_av_clear_remote_suspend_flag();
return;
}
LOG(INFO) << __func__ << ": handling";
@@ -195,9 +190,9 @@ tA2DP_CTRL_CMD A2dpTransport::a2dp_pending_cmd_ = A2DP_CTRL_CMD_NONE;
uint16_t A2dpTransport::remote_delay_report_ = 0;
// Common interface to call-out into Bluetooth Audio HAL
-BluetoothAudioSinkClientInterface* software_hal_interface = nullptr;
-BluetoothAudioSinkClientInterface* offloading_hal_interface = nullptr;
-BluetoothAudioSinkClientInterface* active_hal_interface = nullptr;
+BluetoothAudioClientInterface* software_hal_interface = nullptr;
+BluetoothAudioClientInterface* offloading_hal_interface = nullptr;
+BluetoothAudioClientInterface* active_hal_interface = nullptr;
// Save the value if the remote reports its delay before this interface is
// initialized
@@ -283,13 +278,6 @@ bool a2dp_get_selected_hal_codec_config(CodecConfiguration* codec_config) {
} else {
codec_config->peerMtu = peer_param.peer_mtu;
}
- if (current_codec.codec_type == BTAV_A2DP_CODEC_INDEX_SOURCE_SBC &&
- codec_config->config.sbcConfig().maxBitpool <=
- A2DP_SBC_BITPOOL_MIDDLE_QUALITY) {
- codec_config->peerMtu = MAX_2MBPS_AVDTP_MTU;
- } else if (codec_config->peerMtu > MAX_3MBPS_AVDTP_MTU) {
- codec_config->peerMtu = MAX_3MBPS_AVDTP_MTU;
- }
LOG(INFO) << __func__ << ": CodecConfiguration=" << toString(*codec_config);
return true;
}
@@ -299,7 +287,8 @@ bool a2dp_get_selected_hal_pcm_config(PcmParameters* pcm_config) {
A2dpCodecConfig* a2dp_codec_configs = bta_av_get_a2dp_current_codec();
if (a2dp_codec_configs == nullptr) {
LOG(WARNING) << __func__ << ": failure to get A2DP codec config";
- *pcm_config = BluetoothAudioSinkClientInterface::kInvalidPcmConfiguration;
+ *pcm_config = ::bluetooth::audio::BluetoothAudioClientInterface::
+ kInvalidPcmConfiguration;
return false;
}
@@ -355,8 +344,8 @@ bool init(bluetooth::common::MessageLoopThread* message_loop) {
auto a2dp_sink =
new A2dpTransport(SessionType::A2DP_SOFTWARE_ENCODING_DATAPATH);
- software_hal_interface =
- new BluetoothAudioSinkClientInterface(a2dp_sink, message_loop);
+ software_hal_interface = new bluetooth::audio::BluetoothAudioClientInterface(
+ a2dp_sink, message_loop);
if (!software_hal_interface->IsValid()) {
LOG(WARNING) << __func__ << ": BluetoothAudio HAL for A2DP is invalid?!";
delete software_hal_interface;
@@ -368,7 +357,8 @@ bool init(bluetooth::common::MessageLoopThread* message_loop) {
if (btif_av_is_a2dp_offload_enabled()) {
a2dp_sink = new A2dpTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
offloading_hal_interface =
- new BluetoothAudioSinkClientInterface(a2dp_sink, message_loop);
+ new bluetooth::audio::BluetoothAudioClientInterface(a2dp_sink,
+ message_loop);
if (!offloading_hal_interface->IsValid()) {
LOG(FATAL) << __func__
<< ": BluetoothAudio HAL for A2DP offloading is invalid?!";
@@ -475,8 +465,6 @@ void end_session() {
}
active_hal_interface->EndSession();
static_cast<A2dpTransport*>(active_hal_interface->GetTransportInstance())
- ->ResetPendingCmd();
- static_cast<A2dpTransport*>(active_hal_interface->GetTransportInstance())
->ResetPresentationPosition();
}
diff --git a/audio_hal_interface/a2dp_encoding_host.cc b/audio_hal_interface/a2dp_encoding_host.cc
deleted file mode 100644
index 60cc55544..000000000
--- a/audio_hal_interface/a2dp_encoding_host.cc
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "audio_hal_interface/a2dp_encoding.h"
-
-namespace bluetooth {
-namespace audio {
-namespace a2dp {
-
-bool update_codec_offloading_capabilities(
- const std::vector<btav_a2dp_codec_config_t>& framework_preference) {
- return false;
-}
-
-bool is_hal_2_0_enabled() { return false; }
-
-bool is_hal_2_0_offloading() { return false; }
-
-bool init(bluetooth::common::MessageLoopThread* message_loop) { return false; }
-
-void cleanup() {}
-
-// Set up the codec into BluetoothAudio HAL
-bool setup_codec() { return false; }
-
-void start_session() {}
-
-void end_session() {}
-
-void ack_stream_started(const tA2DP_CTRL_ACK& ack) {}
-
-void ack_stream_suspended(const tA2DP_CTRL_ACK& ack) {}
-
-size_t read(uint8_t* p_buf, uint32_t len) { return 0; }
-
-void set_remote_delay(uint16_t delay_report) {}
-
-} // namespace a2dp
-} // namespace audio
-} // namespace bluetooth
diff --git a/audio_hal_interface/client_interface.cc b/audio_hal_interface/client_interface.cc
index aa7412aed..e14a10220 100644
--- a/audio_hal_interface/client_interface.cc
+++ b/audio_hal_interface/client_interface.cc
@@ -17,14 +17,15 @@
#define LOG_TAG "BTAudioClientIf"
#include "client_interface.h"
-#include "hal_version_manager.h"
#include <android/hardware/bluetooth/audio/2.0/IBluetoothAudioPort.h>
+#include <android/hardware/bluetooth/audio/2.0/IBluetoothAudioProvidersFactory.h>
+#include <android/hidl/manager/1.2/IServiceManager.h>
#include <base/logging.h>
#include <hidl/MQDescriptor.h>
+#include <hidl/ServiceManagement.h>
#include <future>
-#include "common/stop_watch_legacy.h"
#include "osi/include/log.h"
namespace bluetooth {
@@ -35,18 +36,15 @@ using ::android::hardware::Return;
using ::android::hardware::Void;
using ::android::hardware::audio::common::V5_0::SourceMetadata;
using ::android::hardware::bluetooth::audio::V2_0::IBluetoothAudioPort;
-using ::bluetooth::common::StopWatchLegacy;
-
+using ::android::hardware::bluetooth::audio::V2_0::
+ IBluetoothAudioProvidersFactory;
using DataMQ = ::android::hardware::MessageQueue<
uint8_t, ::android::hardware::kSynchronizedReadWrite>;
static constexpr int kDefaultDataReadTimeoutMs = 10; // 10 ms
-static constexpr int kDefaultDataWriteTimeoutMs = 10; // 10 ms
static constexpr int kDefaultDataReadPollIntervalMs = 1; // non-blocking poll
-static constexpr int kDefaultDataWritePollIntervalMs = 1; // non-blocking poll
-
-std::unique_ptr<HalVersionManager> HalVersionManager::instance_ptr =
- std::unique_ptr<HalVersionManager>(new HalVersionManager());
+static constexpr char kFullyQualifiedInterfaceName[] =
+ "android.hardware.bluetooth.audio@2.0::IBluetoothAudioProvidersFactory";
std::ostream& operator<<(std::ostream& os, const BluetoothAudioCtrlAck& ack) {
switch (ack) {
@@ -67,53 +65,49 @@ std::ostream& operator<<(std::ostream& os, const BluetoothAudioCtrlAck& ack) {
}
}
+// Internal class within BluetoothAudioClientInterfaceace to implement
+// IBluetoothAudioPort (control interface used by Bluetooth Audio HAL)
class BluetoothAudioPortImpl : public IBluetoothAudioPort {
public:
- BluetoothAudioPortImpl(IBluetoothTransportInstance* transport_instance,
+ BluetoothAudioPortImpl(IBluetoothTransportInstance* sink,
const android::sp<IBluetoothAudioProvider>& provider)
- : transport_instance_(transport_instance), provider_(provider) {}
+ : sink_(sink), provider_(provider){};
Return<void> startStream() override {
- StopWatchLegacy(__func__);
- BluetoothAudioCtrlAck ack = transport_instance_->StartRequest();
+ BluetoothAudioCtrlAck ack = sink_->StartRequest();
if (ack != BluetoothAudioCtrlAck::PENDING) {
auto hidl_retval =
provider_->streamStarted(BluetoothAudioCtrlAckToHalStatus(ack));
if (!hidl_retval.isOk()) {
- LOG(ERROR) << __func__ << ": BluetoothAudioHal failure: "
- << hidl_retval.description();
+ LOG(ERROR) << __func__ << ": BluetoothAudioHal failure: " << hidl_retval.description();
}
}
return Void();
}
Return<void> suspendStream() override {
- StopWatchLegacy(__func__);
- BluetoothAudioCtrlAck ack = transport_instance_->SuspendRequest();
+ BluetoothAudioCtrlAck ack = sink_->SuspendRequest();
if (ack != BluetoothAudioCtrlAck::PENDING) {
auto hidl_retval =
provider_->streamSuspended(BluetoothAudioCtrlAckToHalStatus(ack));
if (!hidl_retval.isOk()) {
- LOG(ERROR) << __func__ << ": BluetoothAudioHal failure: "
- << hidl_retval.description();
+ LOG(ERROR) << __func__ << ": BluetoothAudioHal failure: " << hidl_retval.description();
}
}
return Void();
}
Return<void> stopStream() override {
- StopWatchLegacy(__func__);
- transport_instance_->StopRequest();
+ sink_->StopRequest();
return Void();
}
Return<void> getPresentationPosition(
getPresentationPosition_cb _hidl_cb) override {
- StopWatchLegacy(__func__);
uint64_t remote_delay_report_ns;
uint64_t total_bytes_read;
timespec data_position;
- bool retval = transport_instance_->GetPresentationPosition(
+ bool retval = sink_->GetPresentationPosition(
&remote_delay_report_ns, &total_bytes_read, &data_position);
TimeSpec transmittedOctetsTimeStamp;
@@ -136,7 +130,6 @@ class BluetoothAudioPortImpl : public IBluetoothAudioPort {
}
Return<void> updateMetadata(const SourceMetadata& sourceMetadata) override {
- StopWatchLegacy(__func__);
LOG(INFO) << __func__ << ": " << sourceMetadata.tracks.size()
<< " track(s)";
// refer to StreamOut.impl.h within Audio HAL (AUDIO_HAL_VERSION_5_0)
@@ -152,12 +145,12 @@ class BluetoothAudioPortImpl : public IBluetoothAudioPort {
}
const source_metadata_t source_metadata = {
.track_count = metadata_vec.size(), .tracks = metadata_vec.data()};
- transport_instance_->MetadataChanged(source_metadata);
+ sink_->MetadataChanged(source_metadata);
return Void();
}
private:
- IBluetoothTransportInstance* transport_instance_;
+ IBluetoothTransportInstance* sink_;
const android::sp<IBluetoothAudioProvider> provider_;
TimeSpec timespec_convert_to_hal(const timespec& ts) {
return {.tvSec = static_cast<uint64_t>(ts.tv_sec),
@@ -194,18 +187,24 @@ class BluetoothAudioDeathRecipient
bluetooth::common::MessageLoopThread* message_loop_;
};
-// Constructs an BluetoothAudioClientInterface to communicate to
-// BluetoothAudio HAL. |message_loop| is the thread where callbacks are
-// invoked.
-BluetoothAudioClientInterface::BluetoothAudioClientInterface(
- android::sp<BluetoothAudioDeathRecipient> death_recipient,
- IBluetoothTransportInstance* instance)
- : provider_(nullptr),
- provider_2_1_(nullptr),
- session_started_(false),
- mDataMQ(nullptr),
- transport_(instance) {
- death_recipient_ = death_recipient;
+BluetoothAudioClientInterface::BluetoothAudioClientInterface(IBluetoothTransportInstance* sink,
+ bluetooth::common::MessageLoopThread* message_loop)
+ : sink_(sink), provider_(nullptr), session_started_(false), mDataMQ(nullptr),
+ death_recipient_(new BluetoothAudioDeathRecipient(this, message_loop)) {
+ if (IsSupported()) {
+ FetchAudioProvider();
+ } else {
+ LOG(WARNING) << "IBluetoothAudioProvidersFactory not declared";
+ }
+}
+
+BluetoothAudioClientInterface::~BluetoothAudioClientInterface() {
+ if (provider_ != nullptr) {
+ auto hidl_retval = provider_->unlinkToDeath(death_recipient_);
+ if (!hidl_retval.isOk()) {
+ LOG(FATAL) << __func__ << ": BluetoothAudioDeathRecipient failure: " << hidl_retval.description();
+ }
+ }
}
std::vector<AudioCapabilities>
@@ -213,25 +212,39 @@ BluetoothAudioClientInterface::GetAudioCapabilities() const {
return capabilities_;
}
-std::vector<AudioCapabilities_2_1>
-BluetoothAudioClientInterface::GetAudioCapabilities_2_1() const {
- return capabilities_2_1_;
+bool BluetoothAudioClientInterface::IsSupported() {
+ auto service_manager = android::hardware::defaultServiceManager1_2();
+ CHECK(service_manager != nullptr);
+ size_t instance_count = 0;
+ auto listManifestByInterface_cb =
+ [&instance_count](
+ const hidl_vec<android::hardware::hidl_string>& instanceNames) {
+ instance_count = instanceNames.size();
+ LOG(INFO) << "listManifestByInterface_cb returns " << instance_count
+ << " instance(s)";
+ };
+ auto hidl_retval = service_manager->listManifestByInterface(
+ kFullyQualifiedInterfaceName, listManifestByInterface_cb);
+ if (!hidl_retval.isOk()) {
+ LOG(FATAL) << __func__ << ": IServiceManager::listByInterface failure: "
+ << hidl_retval.description();
+ return false;
+ }
+ return (instance_count > 0);
}
std::vector<AudioCapabilities>
BluetoothAudioClientInterface::GetAudioCapabilities(SessionType session_type) {
std::vector<AudioCapabilities> capabilities(0);
+ if (!IsSupported()) return capabilities;
- if (HalVersionManager::GetHalVersion() ==
- BluetoothAudioHalVersion::VERSION_UNAVAILABLE) {
- LOG(ERROR) << __func__ << ", can't get capability from unknown factory";
- return capabilities;
- }
-
- android::sp<IBluetoothAudioProvidersFactory_2_0> providersFactory =
- HalVersionManager::GetProvidersFactory_2_0();
+ android::sp<IBluetoothAudioProvidersFactory> providersFactory =
+ IBluetoothAudioProvidersFactory::getService();
CHECK(providersFactory != nullptr)
<< "IBluetoothAudioProvidersFactory::getService() failed";
+ LOG(INFO) << "IBluetoothAudioProvidersFactory::getService() returned "
+ << providersFactory.get()
+ << (providersFactory->isRemote() ? " (remote)" : " (local)");
auto getProviderCapabilities_cb =
[&capabilities](const hidl_vec<AudioCapabilities>& audioCapabilities) {
@@ -249,48 +262,17 @@ BluetoothAudioClientInterface::GetAudioCapabilities(SessionType session_type) {
return capabilities;
}
-std::vector<AudioCapabilities_2_1>
-BluetoothAudioClientInterface::GetAudioCapabilities_2_1(
- SessionType_2_1 session_type_2_1) {
- std::vector<AudioCapabilities_2_1> capabilities_2_1(0);
-
- if (HalVersionManager::GetHalVersion() !=
- BluetoothAudioHalVersion::VERSION_2_1) {
- LOG(ERROR) << __func__ << ", can't get capability for HAL 2.1";
- return capabilities_2_1;
- }
-
- android::sp<IBluetoothAudioProvidersFactory_2_1> providersFactory =
- HalVersionManager::GetProvidersFactory_2_1();
- CHECK(providersFactory != nullptr)
- << "IBluetoothAudioProvidersFactory::getService() failed";
-
- auto getProviderCapabilities_cb =
- [&capabilities_2_1](
- const hidl_vec<AudioCapabilities_2_1>& audioCapabilities_2_1) {
- for (auto capability_2_1 : audioCapabilities_2_1) {
- capabilities_2_1.push_back(capability_2_1);
- }
- };
- auto hidl_retval = providersFactory->getProviderCapabilities_2_1(
- session_type_2_1, getProviderCapabilities_cb);
- if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__
- << ": BluetoothAudioHal::getProviderCapabilities failure: "
- << hidl_retval.description();
- }
- return capabilities_2_1;
-}
-
void BluetoothAudioClientInterface::FetchAudioProvider() {
if (provider_ != nullptr) {
LOG(WARNING) << __func__ << ": reflash";
}
- android::sp<IBluetoothAudioProvidersFactory_2_0> providersFactory =
- HalVersionManager::GetProvidersFactory_2_0();
- CHECK(providersFactory != nullptr)
- << "IBluetoothAudioProvidersFactory::getService() failed";
+ android::sp<IBluetoothAudioProvidersFactory> providersFactory =
+ IBluetoothAudioProvidersFactory::getService();
+ CHECK(providersFactory != nullptr) << "IBluetoothAudioProvidersFactory::getService() failed";
+ LOG(INFO) << "IBluetoothAudioProvidersFactory::getService() returned "
+ << providersFactory.get()
+ << (providersFactory->isRemote() ? " (remote)" : " (local)");
auto getProviderCapabilities_cb =
[& capabilities = this->capabilities_](
@@ -301,21 +283,19 @@ void BluetoothAudioClientInterface::FetchAudioProvider() {
}
};
auto hidl_retval = providersFactory->getProviderCapabilities(
- transport_->GetSessionType(), getProviderCapabilities_cb);
+ sink_->GetSessionType(), getProviderCapabilities_cb);
if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__
- << ": BluetoothAudioHal::getProviderCapabilities failure: "
- << hidl_retval.description();
+ LOG(FATAL) << __func__ << ": BluetoothAudioHal::getProviderCapabilities failure: " << hidl_retval.description();
return;
}
if (capabilities_.empty()) {
LOG(WARNING) << __func__
- << ": SessionType=" << toString(transport_->GetSessionType())
+ << ": SessionType=" << toString(sink_->GetSessionType())
<< " Not supported by BluetoothAudioHal";
return;
}
LOG(INFO) << __func__ << ": BluetoothAudioHal SessionType="
- << toString(transport_->GetSessionType()) << " has "
+ << toString(sink_->GetSessionType()) << " has "
<< capabilities_.size() << " AudioCapabilities";
std::promise<void> openProvider_promise;
@@ -331,18 +311,16 @@ void BluetoothAudioClientInterface::FetchAudioProvider() {
ALOGE_IF(!provider_, "Failed to open BluetoothAudio provider");
openProvider_promise.set_value();
};
- hidl_retval = providersFactory->openProvider(transport_->GetSessionType(),
- openProvider_cb);
+ hidl_retval =
+ providersFactory->openProvider(sink_->GetSessionType(), openProvider_cb);
openProvider_future.get();
if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__ << ": BluetoothAudioHal::openProvider failure: "
- << hidl_retval.description();
+ LOG(FATAL) << __func__ << ": BluetoothAudioHal::openProvider failure: " << hidl_retval.description();
}
CHECK(provider_ != nullptr);
if (!provider_->linkToDeath(death_recipient_, 0).isOk()) {
- LOG(FATAL) << __func__ << ": BluetoothAudioDeathRecipient failure: "
- << hidl_retval.description();
+ LOG(FATAL) << __func__ << ": BluetoothAudioDeathRecipient failure: " << hidl_retval.description();
}
LOG(INFO) << "IBluetoothAudioProvidersFactory::openProvider() returned "
@@ -350,159 +328,15 @@ void BluetoothAudioClientInterface::FetchAudioProvider() {
<< (provider_->isRemote() ? " (remote)" : " (local)");
}
-void BluetoothAudioClientInterface::FetchAudioProvider_2_1() {
- if (provider_2_1_ != nullptr) {
- LOG(WARNING) << __func__ << ": reflash";
- }
-
- android::sp<IBluetoothAudioProvidersFactory_2_1> providersFactory =
- HalVersionManager::GetProvidersFactory_2_1();
- CHECK(providersFactory != nullptr)
- << "IBluetoothAudioProvidersFactory_2_1::getService() failed";
-
- auto getProviderCapabilities_cb =
- [&capabilities_2_1 = this->capabilities_2_1_](
- const hidl_vec<AudioCapabilities_2_1>& audioCapabilities_2_1) {
- capabilities_2_1.clear();
- for (auto capability_2_1 : audioCapabilities_2_1) {
- capabilities_2_1.push_back(capability_2_1);
- }
- };
- auto hidl_retval = providersFactory->getProviderCapabilities_2_1(
- transport_->GetSessionType_2_1(), getProviderCapabilities_cb);
- if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__
- << ": BluetoothAudioHal::getProviderCapabilities failure: "
- << hidl_retval.description();
- return;
- }
- if (capabilities_2_1_.empty()) {
- LOG(WARNING) << __func__ << ": SessionType="
- << toString(transport_->GetSessionType_2_1())
- << " Not supported by BluetoothAudioHal";
- return;
- }
- LOG(INFO) << __func__ << ": BluetoothAudioHal SessionType="
- << toString(transport_->GetSessionType_2_1()) << " has "
- << capabilities_2_1_.size() << " AudioCapabilities";
-
- std::promise<void> openProvider_promise;
- auto openProvider_future = openProvider_promise.get_future();
- auto openProvider_cb =
- [&provider_2_1_ = this->provider_2_1_, &openProvider_promise](
- BluetoothAudioStatus status,
- const android::sp<IBluetoothAudioProvider_2_1>& provider_2_1) {
- LOG(INFO) << "openProvider_cb(" << toString(status) << ")";
- if (status == BluetoothAudioStatus::SUCCESS) {
- provider_2_1_ = provider_2_1;
- }
- ALOGE_IF(!provider_2_1_, "Failed to open BluetoothAudio provider_2_1");
- openProvider_promise.set_value();
- };
- hidl_retval = providersFactory->openProvider_2_1(
- transport_->GetSessionType_2_1(), openProvider_cb);
- openProvider_future.get();
- if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__ << ": BluetoothAudioHal::openProvider failure: "
- << hidl_retval.description();
- }
- CHECK(provider_2_1_ != nullptr);
-
- if (!provider_2_1_->linkToDeath(death_recipient_, 0).isOk()) {
- LOG(FATAL) << __func__ << ": BluetoothAudioDeathRecipient failure: "
- << hidl_retval.description();
- }
-
- LOG(INFO) << "IBluetoothAudioProvidersFactory::openProvider() returned "
- << provider_2_1_.get()
- << (provider_2_1_->isRemote() ? " (remote)" : " (local)");
-}
-
-BluetoothAudioSinkClientInterface::BluetoothAudioSinkClientInterface(
- IBluetoothSinkTransportInstance* sink,
- bluetooth::common::MessageLoopThread* message_loop)
- : BluetoothAudioClientInterface{new BluetoothAudioDeathRecipient(
- this, message_loop),
- sink},
- sink_(sink) {
- if (HalVersionManager::GetHalVersion() ==
- BluetoothAudioHalVersion::VERSION_UNAVAILABLE) {
- return;
- }
-
- if ((HalVersionManager::GetHalVersion() ==
- BluetoothAudioHalVersion::VERSION_2_1) &&
- (sink_->GetSessionType_2_1() != SessionType_2_1::UNKNOWN)) {
- FetchAudioProvider_2_1();
- return;
- }
- FetchAudioProvider();
-}
-
-BluetoothAudioSinkClientInterface::~BluetoothAudioSinkClientInterface() {
- if (provider_ != nullptr) {
- auto hidl_retval = provider_->unlinkToDeath(death_recipient_);
- if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__ << ": BluetoothAudioDeathRecipient failure: "
- << hidl_retval.description();
- }
- }
- if (provider_2_1_ != nullptr) {
- auto hidl_retval = provider_2_1_->unlinkToDeath(death_recipient_);
- if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__ << ": BluetoothAudioDeathRecipient failure: "
- << hidl_retval.description();
- }
- }
-}
-
-BluetoothAudioSourceClientInterface::BluetoothAudioSourceClientInterface(
- IBluetoothSourceTransportInstance* source,
- bluetooth::common::MessageLoopThread* message_loop)
- : BluetoothAudioClientInterface{new BluetoothAudioDeathRecipient(
- this, message_loop),
- source},
- source_(source) {
- if (HalVersionManager::GetHalVersion() ==
- BluetoothAudioHalVersion::VERSION_UNAVAILABLE) {
- return;
- }
-
- if ((HalVersionManager::GetHalVersion() ==
- BluetoothAudioHalVersion::VERSION_2_1) &&
- (source_->GetSessionType_2_1() != SessionType_2_1::UNKNOWN)) {
- FetchAudioProvider_2_1();
- return;
- }
- FetchAudioProvider();
-}
-
-BluetoothAudioSourceClientInterface::~BluetoothAudioSourceClientInterface() {
- if (provider_ != nullptr) {
- auto hidl_retval = provider_->unlinkToDeath(death_recipient_);
- if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__ << ": BluetoothAudioDeathRecipient failure: "
- << hidl_retval.description();
- }
- }
- if (provider_2_1_ != nullptr) {
- auto hidl_retval = provider_2_1_->unlinkToDeath(death_recipient_);
- if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__ << ": BluetoothAudioDeathRecipient failure: "
- << hidl_retval.description();
- }
- }
-}
-
bool BluetoothAudioClientInterface::UpdateAudioConfig(
const AudioConfiguration& audio_config) {
bool is_software_session =
- (transport_->GetSessionType() ==
+ (sink_->GetSessionType() ==
SessionType::A2DP_SOFTWARE_ENCODING_DATAPATH ||
- transport_->GetSessionType() ==
+ sink_->GetSessionType() ==
SessionType::HEARING_AID_SOFTWARE_ENCODING_DATAPATH);
- bool is_offload_session = (transport_->GetSessionType() ==
- SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ bool is_offload_session =
+ (sink_->GetSessionType() == SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
auto audio_config_discriminator = audio_config.getDiscriminator();
bool is_software_audio_config =
(is_software_session &&
@@ -515,36 +349,7 @@ bool BluetoothAudioClientInterface::UpdateAudioConfig(
if (!is_software_audio_config && !is_offload_audio_config) {
return false;
}
- transport_->UpdateAudioConfiguration(audio_config);
- return true;
-}
-
-bool BluetoothAudioClientInterface::UpdateAudioConfig_2_1(
- const AudioConfiguration_2_1& audio_config_2_1) {
- bool is_software_session =
- (transport_->GetSessionType_2_1() ==
- SessionType_2_1::A2DP_SOFTWARE_ENCODING_DATAPATH ||
- transport_->GetSessionType_2_1() ==
- SessionType_2_1::HEARING_AID_SOFTWARE_ENCODING_DATAPATH ||
- transport_->GetSessionType_2_1() ==
- SessionType_2_1::LE_AUDIO_SOFTWARE_ENCODING_DATAPATH ||
- transport_->GetSessionType_2_1() ==
- SessionType_2_1::LE_AUDIO_SOFTWARE_DECODED_DATAPATH);
- bool is_offload_session = (transport_->GetSessionType_2_1() ==
- SessionType_2_1::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- auto audio_config_discriminator = audio_config_2_1.getDiscriminator();
- bool is_software_audio_config =
- (is_software_session &&
- audio_config_discriminator ==
- AudioConfiguration_2_1::hidl_discriminator::pcmConfig);
- bool is_offload_audio_config =
- (is_offload_session &&
- audio_config_discriminator ==
- AudioConfiguration_2_1::hidl_discriminator::codecConfig);
- if (!is_software_audio_config && !is_offload_audio_config) {
- return false;
- }
- transport_->UpdateAudioConfiguration_2_1(audio_config_2_1);
+ sink_->UpdateAudioConfiguration(audio_config);
return true;
}
@@ -561,8 +366,7 @@ int BluetoothAudioClientInterface::StartSession() {
}
android::sp<IBluetoothAudioPort> stack_if =
- new BluetoothAudioPortImpl(transport_, provider_);
-
+ new BluetoothAudioPortImpl(sink_, provider_);
std::unique_ptr<DataMQ> tempDataMQ;
BluetoothAudioStatus session_status;
@@ -579,85 +383,24 @@ int BluetoothAudioClientInterface::StartSession() {
hidl_startSession_promise.set_value();
};
auto hidl_retval = provider_->startSession(
- stack_if, transport_->GetAudioConfiguration(), hidl_cb);
+ stack_if, sink_->GetAudioConfiguration(), hidl_cb);
hidl_startSession_future.get();
if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__
- << ": BluetoothAudioHal failure: " << hidl_retval.description();
+ LOG(FATAL) << __func__ << ": BluetoothAudioHal failure: " << hidl_retval.description();
return -EPROTO;
}
if (tempDataMQ && tempDataMQ->isValid()) {
mDataMQ = std::move(tempDataMQ);
- } else if (transport_->GetSessionType() ==
+ } else if (sink_->GetSessionType() ==
SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH &&
session_status == BluetoothAudioStatus::SUCCESS) {
- transport_->ResetPresentationPosition();
- session_started_ = true;
- return 0;
- }
- if (mDataMQ && mDataMQ->isValid()) {
- transport_->ResetPresentationPosition();
- session_started_ = true;
- return 0;
- } else {
- ALOGE_IF(!mDataMQ, "Failed to obtain audio data path");
- ALOGE_IF(mDataMQ && !mDataMQ->isValid(), "Audio data path is invalid");
- session_started_ = false;
- return -EIO;
- }
-}
-
-int BluetoothAudioClientInterface::StartSession_2_1() {
- std::lock_guard<std::mutex> guard(internal_mutex_);
- if (provider_2_1_ == nullptr) {
- LOG(ERROR) << __func__ << ": BluetoothAudioHal nullptr";
- session_started_ = false;
- return -EINVAL;
- }
- if (session_started_) {
- LOG(ERROR) << __func__ << ": session started already";
- return -EBUSY;
- }
-
- android::sp<IBluetoothAudioPort> stack_if =
- new BluetoothAudioPortImpl(transport_, provider_2_1_);
-
- std::unique_ptr<DataMQ> tempDataMQ;
- BluetoothAudioStatus session_status;
-
- std::promise<void> hidl_startSession_promise;
- auto hidl_startSession_future = hidl_startSession_promise.get_future();
- auto hidl_cb = [&session_status, &tempDataMQ, &hidl_startSession_promise](
- BluetoothAudioStatus status,
- const DataMQ::Descriptor& dataMQ) {
- LOG(INFO) << "startSession_cb(" << toString(status) << ")";
- session_status = status;
- if (status == BluetoothAudioStatus::SUCCESS && dataMQ.isHandleValid()) {
- tempDataMQ.reset(new DataMQ(dataMQ));
- }
- hidl_startSession_promise.set_value();
- };
- auto hidl_retval = provider_2_1_->startSession_2_1(
- stack_if, transport_->GetAudioConfiguration_2_1(), hidl_cb);
- hidl_startSession_future.get();
- if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__
- << ": BluetoothAudioHal failure: " << hidl_retval.description();
- return -EPROTO;
- }
-
- if (tempDataMQ && tempDataMQ->isValid()) {
- mDataMQ = std::move(tempDataMQ);
- } else if (transport_->GetSessionType_2_1() ==
- SessionType_2_1::A2DP_HARDWARE_OFFLOAD_DATAPATH &&
- session_status == BluetoothAudioStatus::SUCCESS) {
- transport_->ResetPresentationPosition();
+ sink_->ResetPresentationPosition();
session_started_ = true;
return 0;
}
if (mDataMQ && mDataMQ->isValid()) {
- transport_->ResetPresentationPosition();
+ sink_->ResetPresentationPosition();
session_started_ = true;
return 0;
} else {
@@ -670,7 +413,7 @@ int BluetoothAudioClientInterface::StartSession_2_1() {
void BluetoothAudioClientInterface::StreamStarted(
const BluetoothAudioCtrlAck& ack) {
- if (provider_ == nullptr && provider_2_1_ == nullptr) {
+ if (provider_ == nullptr) {
LOG(ERROR) << __func__ << ": BluetoothAudioHal nullptr";
return;
}
@@ -679,16 +422,9 @@ void BluetoothAudioClientInterface::StreamStarted(
return;
}
BluetoothAudioStatus status = BluetoothAudioCtrlAckToHalStatus(ack);
-
- ::android::hardware::Return<void> hidl_retval;
- if (provider_2_1_ != nullptr)
- hidl_retval = provider_2_1_->streamStarted(status);
- else
- hidl_retval = provider_->streamStarted(status);
-
+ auto hidl_retval = provider_->streamStarted(status);
if (!hidl_retval.isOk()) {
- LOG(ERROR) << __func__
- << ": BluetoothAudioHal failure: " << hidl_retval.description();
+ LOG(ERROR) << __func__ << ": BluetoothAudioHal failure: " << hidl_retval.description();
}
}
@@ -703,59 +439,37 @@ void BluetoothAudioClientInterface::StreamSuspended(
return;
}
BluetoothAudioStatus status = BluetoothAudioCtrlAckToHalStatus(ack);
-
- ::android::hardware::Return<void> hidl_retval;
- if (provider_2_1_ != nullptr)
- hidl_retval = provider_2_1_->streamSuspended(status);
- else
- hidl_retval = provider_->streamSuspended(status);
-
+ auto hidl_retval = provider_->streamSuspended(status);
if (!hidl_retval.isOk()) {
- LOG(ERROR) << __func__
- << ": BluetoothAudioHal failure: " << hidl_retval.description();
+ LOG(ERROR) << __func__ << ": BluetoothAudioHal failure: " << hidl_retval.description();
}
}
int BluetoothAudioClientInterface::EndSession() {
std::lock_guard<std::mutex> guard(internal_mutex_);
if (!session_started_) {
- LOG(INFO) << __func__ << ": session ended already";
+ LOG(INFO) << __func__ << ": sessoin ended already";
return 0;
}
session_started_ = false;
- if (provider_2_1_ == nullptr && provider_ == nullptr) {
+ if (provider_ == nullptr) {
LOG(ERROR) << __func__ << ": BluetoothAudioHal nullptr";
return -EINVAL;
}
mDataMQ = nullptr;
-
- ::android::hardware::Return<void> hidl_retval;
- if (provider_2_1_ != nullptr)
- hidl_retval = provider_2_1_->endSession();
- else
- hidl_retval = provider_->endSession();
-
+ auto hidl_retval = provider_->endSession();
if (!hidl_retval.isOk()) {
- LOG(ERROR) << __func__
- << ": BluetoothAudioHal failure: " << hidl_retval.description();
+ LOG(ERROR) << __func__ << ": BluetoothAudioHal failure: " << hidl_retval.description();
return -EPROTO;
}
return 0;
}
-void BluetoothAudioClientInterface::FlushAudioData() {
- size_t size = mDataMQ->availableToRead();
- uint8_t p_buf[size];
-
- if (mDataMQ->read(p_buf, size) != size)
- LOG(WARNING) << __func__ << ", failed to flush data queue!";
-}
-
-size_t BluetoothAudioSinkClientInterface::ReadAudioData(uint8_t* p_buf,
- uint32_t len) {
- if (!IsValid()) {
- LOG(ERROR) << __func__ << ": BluetoothAudioHal is not valid";
+size_t BluetoothAudioClientInterface::ReadAudioData(uint8_t* p_buf,
+ uint32_t len) {
+ if (provider_ == nullptr) {
+ LOG(ERROR) << __func__ << ": BluetoothAudioHal nullptr";
return 0;
}
if (p_buf == nullptr || len == 0) return 0;
@@ -804,81 +518,21 @@ size_t BluetoothAudioSinkClientInterface::ReadAudioData(uint8_t* p_buf,
return total_read;
}
+size_t BluetoothAudioClientInterface::WriteAudioData(uint8_t* p_buf,
+ uint32_t len) {
+ // Not implemented!
+ return 0;
+}
+
void BluetoothAudioClientInterface::RenewAudioProviderAndSession() {
// NOTE: must be invoked on the same thread where this
// BluetoothAudioClientInterface is running
- if ((HalVersionManager::GetHalVersion() ==
- BluetoothAudioHalVersion::VERSION_2_1) &&
- (transport_->GetSessionType_2_1() != SessionType_2_1::UNKNOWN)) {
- FetchAudioProvider_2_1();
- } else if (transport_->GetSessionType() != SessionType::UNKNOWN) {
- FetchAudioProvider();
- } else {
- LOG(FATAL) << __func__ << ", cannot renew audio provider";
- return;
- }
-
+ FetchAudioProvider();
if (session_started_) {
LOG(INFO) << __func__ << ": Restart the session while audio HAL recovering";
session_started_ = false;
-
- if (provider_2_1_ != nullptr)
- StartSession_2_1();
- else
- StartSession();
- }
-}
-
-size_t BluetoothAudioSourceClientInterface::WriteAudioData(const uint8_t* p_buf,
- uint32_t len) {
- if (provider_ == nullptr) {
- LOG(ERROR) << __func__ << ": BluetoothAudioHal nullptr";
- return 0;
+ StartSession();
}
- if (p_buf == nullptr || len == 0) return 0;
-
- std::lock_guard<std::mutex> guard(internal_mutex_);
-
- size_t total_written = 0;
- int timeout_ms = kDefaultDataWriteTimeoutMs;
- do {
- if (mDataMQ == nullptr || !mDataMQ->isValid()) break;
-
- size_t avail_to_write = mDataMQ->availableToWrite();
- if (avail_to_write) {
- if (avail_to_write > len - total_written) {
- avail_to_write = len - total_written;
- }
- if (mDataMQ->write(p_buf + total_written, avail_to_write) == 0) {
- LOG(WARNING) << __func__ << ": len=" << len
- << " total_written=" << total_written << " failed";
- break;
- }
- total_written += avail_to_write;
- } else if (timeout_ms >= kDefaultDataWritePollIntervalMs) {
- std::this_thread::sleep_for(
- std::chrono::milliseconds(kDefaultDataWritePollIntervalMs));
- timeout_ms -= kDefaultDataWritePollIntervalMs;
- continue;
- } else {
- LOG(WARNING) << __func__ << ": " << (len - total_written) << "/" << len
- << " no data " << (kDefaultDataWriteTimeoutMs - timeout_ms)
- << " ms";
- break;
- }
- } while (total_written < len);
-
- if (timeout_ms <
- (kDefaultDataWriteTimeoutMs - kDefaultDataWritePollIntervalMs) &&
- timeout_ms >= kDefaultDataWritePollIntervalMs) {
- VLOG(1) << __func__ << ": underflow " << len << " -> " << total_written
- << " read " << (kDefaultDataWriteTimeoutMs - timeout_ms) << " ms";
- } else {
- VLOG(2) << __func__ << ": " << len << " -> " << total_written << " written";
- }
-
- source_->LogBytesWritten(total_written);
- return total_written;
}
} // namespace audio
diff --git a/audio_hal_interface/client_interface.h b/audio_hal_interface/client_interface.h
index b9f18b9ed..1484fc93d 100644
--- a/audio_hal_interface/client_interface.h
+++ b/audio_hal_interface/client_interface.h
@@ -20,8 +20,8 @@
#include <mutex>
#include <vector>
-#include <android/hardware/bluetooth/audio/2.1/IBluetoothAudioProvider.h>
-#include <android/hardware/bluetooth/audio/2.1/types.h>
+#include <android/hardware/bluetooth/audio/2.0/IBluetoothAudioProvider.h>
+#include <android/hardware/bluetooth/audio/2.0/types.h>
#include <fmq/MessageQueue.h>
#include <hardware/audio.h>
@@ -32,30 +32,14 @@
namespace bluetooth {
namespace audio {
-using ::android::hardware::bluetooth::audio::V2_0::IBluetoothAudioPort;
-using AudioCapabilities =
- ::android::hardware::bluetooth::audio::V2_0::AudioCapabilities;
-using AudioCapabilities_2_1 =
- ::android::hardware::bluetooth::audio::V2_1::AudioCapabilities;
-using AudioConfiguration =
- ::android::hardware::bluetooth::audio::V2_0::AudioConfiguration;
-using AudioConfiguration_2_1 =
- ::android::hardware::bluetooth::audio::V2_1::AudioConfiguration;
+using ::android::hardware::bluetooth::audio::V2_0::AudioCapabilities;
+using ::android::hardware::bluetooth::audio::V2_0::AudioConfiguration;
using ::android::hardware::bluetooth::audio::V2_0::BitsPerSample;
using ::android::hardware::bluetooth::audio::V2_0::ChannelMode;
-using IBluetoothAudioProvider =
- ::android::hardware::bluetooth::audio::V2_0::IBluetoothAudioProvider;
-using IBluetoothAudioProvider_2_1 =
- ::android::hardware::bluetooth::audio::V2_1::IBluetoothAudioProvider;
-using PcmParameters =
- ::android::hardware::bluetooth::audio::V2_0::PcmParameters;
-using PcmParameters_2_1 =
- ::android::hardware::bluetooth::audio::V2_1::PcmParameters;
-using SampleRate = ::android::hardware::bluetooth::audio::V2_0::SampleRate;
-using SampleRate_2_1 = ::android::hardware::bluetooth::audio::V2_1::SampleRate;
-using SessionType = ::android::hardware::bluetooth::audio::V2_0::SessionType;
-using SessionType_2_1 =
- ::android::hardware::bluetooth::audio::V2_1::SessionType;
+using ::android::hardware::bluetooth::audio::V2_0::IBluetoothAudioProvider;
+using ::android::hardware::bluetooth::audio::V2_0::PcmParameters;
+using ::android::hardware::bluetooth::audio::V2_0::SampleRate;
+using ::android::hardware::bluetooth::audio::V2_0::SessionType;
using ::android::hardware::bluetooth::audio::V2_0::TimeSpec;
using BluetoothAudioStatus =
::android::hardware::bluetooth::audio::V2_0::Status;
@@ -89,40 +73,22 @@ inline BluetoothAudioStatus BluetoothAudioCtrlAckToHalStatus(
}
}
-// An IBluetoothTransportInstance needs to be implemented by a Bluetooth
-// audio transport, such as A2DP or Hearing Aid, to handle callbacks from Audio
-// HAL.
+// An IBluetoothTransportInstance needs to be implemented by a Bluetooth audio
+// transport, such as A2DP or Hearing Aid, to handle callbacks from Audio HAL.
class IBluetoothTransportInstance {
public:
IBluetoothTransportInstance(SessionType sessionType,
AudioConfiguration audioConfig)
- : session_type_(sessionType),
- session_type_2_1_(SessionType_2_1::UNKNOWN),
- audio_config_(std::move(audioConfig)),
- audio_config_2_1_({}){};
- IBluetoothTransportInstance(SessionType_2_1 sessionType_2_1,
- AudioConfiguration_2_1 audioConfig_2_1)
- : session_type_(SessionType::UNKNOWN),
- session_type_2_1_(sessionType_2_1),
- audio_config_({}),
- audio_config_2_1_(std::move(audioConfig_2_1)){};
+ : session_type_(sessionType), audio_config_(std::move(audioConfig)){};
virtual ~IBluetoothTransportInstance() = default;
SessionType GetSessionType() const { return session_type_; }
- SessionType_2_1 GetSessionType_2_1() const { return session_type_2_1_; }
AudioConfiguration GetAudioConfiguration() const { return audio_config_; }
- AudioConfiguration_2_1 GetAudioConfiguration_2_1() const {
- return audio_config_2_1_;
- }
void UpdateAudioConfiguration(const AudioConfiguration& audio_config) {
audio_config_ = audio_config;
}
- void UpdateAudioConfiguration_2_1(
- const AudioConfiguration_2_1& audio_config_2_1) {
- audio_config_2_1_ = audio_config_2_1;
- }
virtual BluetoothAudioCtrlAck StartRequest() = 0;
@@ -139,42 +105,12 @@ class IBluetoothTransportInstance {
// Invoked when the transport is requested to reset presentation position
virtual void ResetPresentationPosition() = 0;
- private:
- const SessionType session_type_;
- const SessionType_2_1 session_type_2_1_;
- AudioConfiguration audio_config_;
- AudioConfiguration_2_1 audio_config_2_1_;
-};
-
-// An IBluetoothSinkTransportInstance needs to be implemented by a Bluetooth
-// audio transport, such as A2DP, Hearing Aid or LeAudio, to handle callbacks
-// from Audio HAL.
-class IBluetoothSinkTransportInstance : public IBluetoothTransportInstance {
- public:
- IBluetoothSinkTransportInstance(SessionType_2_1 sessionType_2_1,
- AudioConfiguration_2_1 audioConfig_2_1)
- : IBluetoothTransportInstance{sessionType_2_1, audioConfig_2_1} {}
- IBluetoothSinkTransportInstance(SessionType sessionType,
- AudioConfiguration audioConfig)
- : IBluetoothTransportInstance{sessionType, audioConfig} {}
- virtual ~IBluetoothSinkTransportInstance() = default;
-
// Invoked when the transport is requested to log bytes read
virtual void LogBytesRead(size_t bytes_readed) = 0;
-};
-class IBluetoothSourceTransportInstance : public IBluetoothTransportInstance {
- public:
- IBluetoothSourceTransportInstance(SessionType sessionType,
- AudioConfiguration audioConfig)
- : IBluetoothTransportInstance{sessionType, audioConfig} {}
- IBluetoothSourceTransportInstance(SessionType_2_1 sessionType_2_1,
- AudioConfiguration_2_1 audioConfig_2_1)
- : IBluetoothTransportInstance{sessionType_2_1, audioConfig_2_1} {}
- virtual ~IBluetoothSourceTransportInstance() = default;
-
- // Invoked when the transport is requested to log bytes written
- virtual void LogBytesWritten(size_t bytes_written) = 0;
+ private:
+ const SessionType session_type_;
+ AudioConfiguration audio_config_;
};
// common object is shared between different kind of SessionType
@@ -185,105 +121,65 @@ class BluetoothAudioDeathRecipient;
// IBluetoothTransportInstance
class BluetoothAudioClientInterface {
public:
+ // Constructs an BluetoothAudioClientInterface to communicate to
+ // BluetoothAudio HAL. |sink| is the implementation for the transport, and
+ // |message_loop| is the thread where callbacks are invoked.
BluetoothAudioClientInterface(
- android::sp<BluetoothAudioDeathRecipient> death_recipient,
- IBluetoothTransportInstance* instance);
- virtual ~BluetoothAudioClientInterface() = default;
+ IBluetoothTransportInstance* sink,
+ bluetooth::common::MessageLoopThread* message_loop);
+
+ ~BluetoothAudioClientInterface();
bool IsValid() const {
- return provider_ != nullptr || provider_2_1_ != nullptr;
+ return provider_ != nullptr;
}
+ IBluetoothTransportInstance* GetTransportInstance() const { return sink_; }
+
std::vector<AudioCapabilities> GetAudioCapabilities() const;
- std::vector<AudioCapabilities_2_1> GetAudioCapabilities_2_1() const;
static std::vector<AudioCapabilities> GetAudioCapabilities(
SessionType session_type);
- static std::vector<AudioCapabilities_2_1> GetAudioCapabilities_2_1(
- SessionType_2_1 session_type_2_1);
- void StreamStarted(const BluetoothAudioCtrlAck& ack);
-
- void StreamSuspended(const BluetoothAudioCtrlAck& ack);
+ bool UpdateAudioConfig(const AudioConfiguration& audioConfig);
int StartSession();
- int StartSession_2_1();
- // Renew the connection and usually is used when HIDL restarted
- void RenewAudioProviderAndSession();
+ void StreamStarted(const BluetoothAudioCtrlAck& ack);
+
+ void StreamSuspended(const BluetoothAudioCtrlAck& ack);
int EndSession();
- bool UpdateAudioConfig(const AudioConfiguration& audioConfig);
- bool UpdateAudioConfig_2_1(const AudioConfiguration_2_1& audioConfig_2_1);
+ // Read data from audio HAL through fmq
+ size_t ReadAudioData(uint8_t* p_buf, uint32_t len);
+
+ // Write data to audio HAL through fmq
+ size_t WriteAudioData(uint8_t* p_buf, uint32_t len);
- void FlushAudioData();
+ // Renew the connection and usually is used when HIDL restarted
+ void RenewAudioProviderAndSession();
static constexpr PcmParameters kInvalidPcmConfiguration = {
.sampleRate = SampleRate::RATE_UNKNOWN,
.channelMode = ChannelMode::UNKNOWN,
- .bitsPerSample = BitsPerSample::BITS_UNKNOWN};
+ .bitsPerSample = BitsPerSample::BITS_UNKNOWN,
+ };
+
+ private:
+ static bool IsSupported();
- protected:
- mutable std::mutex internal_mutex_;
// Helper function to connect to an IBluetoothAudioProvider
void FetchAudioProvider();
- // Helper function to connect to an IBluetoothAudioProvider 2.1
- void FetchAudioProvider_2_1();
+ mutable std::mutex internal_mutex_;
+ IBluetoothTransportInstance* sink_;
android::sp<IBluetoothAudioProvider> provider_;
- android::sp<IBluetoothAudioProvider_2_1> provider_2_1_;
+ std::vector<AudioCapabilities> capabilities_;
bool session_started_;
std::unique_ptr<::android::hardware::MessageQueue<
uint8_t, ::android::hardware::kSynchronizedReadWrite>>
mDataMQ;
android::sp<BluetoothAudioDeathRecipient> death_recipient_;
-
- private:
- IBluetoothTransportInstance* transport_;
- std::vector<AudioCapabilities> capabilities_;
- std::vector<AudioCapabilities_2_1> capabilities_2_1_;
-};
-
-// The client interface connects an IBluetoothTransportInstance to
-// IBluetoothAudioProvider and helps to route callbacks to
-// IBluetoothTransportInstance
-class BluetoothAudioSinkClientInterface : public BluetoothAudioClientInterface {
- public:
- // Constructs an BluetoothAudioSinkClientInterface to communicate to
- // BluetoothAudio HAL. |sink| is the implementation for the transport, and
- // |message_loop| is the thread where callbacks are invoked.
- BluetoothAudioSinkClientInterface(
- IBluetoothSinkTransportInstance* sink,
- bluetooth::common::MessageLoopThread* message_loop);
- virtual ~BluetoothAudioSinkClientInterface();
-
- IBluetoothSinkTransportInstance* GetTransportInstance() const {
- return sink_;
- }
-
- // Read data from audio HAL through fmq
- size_t ReadAudioData(uint8_t* p_buf, uint32_t len);
-
- private:
- IBluetoothSinkTransportInstance* sink_;
-};
-
-class BluetoothAudioSourceClientInterface
- : public BluetoothAudioClientInterface {
- public:
- // Constructs an BluetoothAudioSourceClientInterface to communicate to
- // BluetoothAudio HAL. |source| is the implementation for the transport, and
- // |message_loop| is the thread where callbacks are invoked.
- BluetoothAudioSourceClientInterface(
- IBluetoothSourceTransportInstance* source,
- bluetooth::common::MessageLoopThread* message_loop);
- virtual ~BluetoothAudioSourceClientInterface();
-
- // Write data to audio HAL through fmq
- size_t WriteAudioData(const uint8_t* p_buf, uint32_t len);
-
- private:
- IBluetoothSourceTransportInstance* source_;
};
} // namespace audio
diff --git a/audio_hal_interface/client_interface_unittest.cc b/audio_hal_interface/client_interface_unittest.cc
index 33954c720..f487f85a9 100644
--- a/audio_hal_interface/client_interface_unittest.cc
+++ b/audio_hal_interface/client_interface_unittest.cc
@@ -14,8 +14,6 @@
* limitations under the License.
*/
-#define LOG_TAG "bluetooth"
-
#include <gtest/gtest.h>
#include "client_interface.h"
@@ -39,19 +37,11 @@ using ::android::hardware::bluetooth::audio::V2_0::SbcNumSubbands;
using ::android::hardware::bluetooth::audio::V2_0::SbcParameters;
using ::bluetooth::audio::AudioCapabilities;
-using ::bluetooth::audio::AudioCapabilities_2_1;
using ::bluetooth::audio::AudioConfiguration;
-using ::bluetooth::audio::AudioConfiguration_2_1;
using ::bluetooth::audio::BluetoothAudioClientInterface;
-using ::bluetooth::audio::BluetoothAudioSinkClientInterface;
-using ::bluetooth::audio::BluetoothAudioSourceClientInterface;
using ::bluetooth::audio::BluetoothAudioStatus;
using ::bluetooth::audio::PcmParameters;
-using ::bluetooth::audio::PcmParameters_2_1;
-using ::bluetooth::audio::SampleRate;
-using ::bluetooth::audio::SampleRate_2_1;
using ::bluetooth::audio::SessionType;
-using ::bluetooth::audio::SessionType_2_1;
using ::bluetooth::audio::codec::A2dpCodecToHalBitsPerSample;
using ::bluetooth::audio::codec::A2dpCodecToHalChannelMode;
using ::bluetooth::audio::codec::A2dpCodecToHalSampleRate;
@@ -59,6 +49,7 @@ using ::bluetooth::audio::codec::BitsPerSample;
using ::bluetooth::audio::codec::ChannelMode;
using ::bluetooth::audio::codec::CodecConfiguration;
using ::bluetooth::audio::codec::IsCodecOffloadingEnabled;
+using ::bluetooth::audio::codec::SampleRate;
using ::bluetooth::audio::codec::UpdateOffloadingCapabilities;
using ::testing::Test;
@@ -86,15 +77,6 @@ constexpr SampleRatePair kSampleRatePairs[9] = {
{.hal_sample_rate_ = SampleRate::RATE_24000,
.btav_sample_rate_ = BTAV_A2DP_CODEC_SAMPLE_RATE_24000}};
-constexpr SampleRate_2_1 kSampleRates_2_1[] = {
- SampleRate_2_1::RATE_UNKNOWN, SampleRate_2_1::RATE_8000,
- SampleRate_2_1::RATE_16000, SampleRate_2_1::RATE_24000,
- SampleRate_2_1::RATE_32000, SampleRate_2_1::RATE_44100,
- SampleRate_2_1::RATE_48000};
-
-constexpr uint32_t kDataIntervalUs[] = {0 /* Invalid */,
- 10000 /* Valid 10ms */};
-
struct BitsPerSamplePair {
BitsPerSample hal_bits_per_sample_;
btav_a2dp_codec_bits_per_sample_t btav_bits_per_sample_;
@@ -128,17 +110,13 @@ constexpr btav_a2dp_codec_index_t codec_indexes[] = {
BTAV_A2DP_CODEC_INDEX_SINK_AAC, BTAV_A2DP_CODEC_INDEX_SINK_LDAC};
constexpr uint16_t kPeerMtus[5] = {660, 663, 883, 1005, 1500};
-class TestSinkTransport
- : public bluetooth::audio::IBluetoothSinkTransportInstance {
+class TestTransport : public bluetooth::audio::IBluetoothTransportInstance {
private:
static constexpr uint64_t kRemoteDelayReportMs = 200;
public:
- TestSinkTransport(SessionType session_type)
- : bluetooth::audio::IBluetoothSinkTransportInstance(session_type, {}){};
- TestSinkTransport(SessionType_2_1 session_type_2_1)
- : bluetooth::audio::IBluetoothSinkTransportInstance(session_type_2_1,
- {}){};
+ TestTransport(SessionType session_type)
+ : bluetooth::audio::IBluetoothTransportInstance(session_type, {}){};
bluetooth::audio::BluetoothAudioCtrlAck StartRequest() override {
return bluetooth::audio::BluetoothAudioCtrlAck::SUCCESS_FINISHED;
}
@@ -166,70 +144,25 @@ class TestSinkTransport
void LogBytesRead(size_t bytes_readed __unused) override{};
};
-class TestSourceTransport
- : public bluetooth::audio::IBluetoothSourceTransportInstance {
- private:
- static constexpr uint64_t kRemoteDelayReportMs = 200;
-
- public:
- TestSourceTransport(SessionType session_type)
- : bluetooth::audio::IBluetoothSourceTransportInstance(session_type, {}){};
- TestSourceTransport(SessionType_2_1 session_type_2_1)
- : bluetooth::audio::IBluetoothSourceTransportInstance(session_type_2_1,
- {}){};
- bluetooth::audio::BluetoothAudioCtrlAck StartRequest() override {
- return bluetooth::audio::BluetoothAudioCtrlAck::SUCCESS_FINISHED;
- }
- bluetooth::audio::BluetoothAudioCtrlAck SuspendRequest() override {
- return bluetooth::audio::BluetoothAudioCtrlAck::SUCCESS_FINISHED;
- }
- void StopRequest() override {}
- bool GetPresentationPosition(uint64_t* remote_delay_report_ns,
- uint64_t* total_bytes_written,
- timespec* data_position) override {
- if (remote_delay_report_ns) {
- *remote_delay_report_ns = kRemoteDelayReportMs * 1000000;
- }
- if (total_bytes_written) {
- *total_bytes_written = 0;
- }
- if (data_position) {
- clock_gettime(CLOCK_MONOTONIC, data_position);
- }
- return true;
- }
- void MetadataChanged(
- const source_metadata_t& source_metadata __unused) override {}
- void ResetPresentationPosition() override{};
- void LogBytesWritten(size_t bytes_written __unused) override{};
-};
-
class BluetoothAudioClientInterfaceTest : public Test {
protected:
- TestSinkTransport* test_sink_transport_ = nullptr;
- TestSourceTransport* test_source_transport_ = nullptr;
- BluetoothAudioSinkClientInterface* clientif_sink_ = nullptr;
- BluetoothAudioSourceClientInterface* clientif_source_ = nullptr;
+ TestTransport* test_transport_ = nullptr;
+ BluetoothAudioClientInterface* clientif_ = nullptr;
static constexpr int kClientIfReturnSuccess = 0;
void SetUp() override {}
void TearDown() override {
- if (clientif_sink_ != nullptr) delete clientif_sink_;
- clientif_sink_ = nullptr;
- if (test_sink_transport_ != nullptr) delete test_sink_transport_;
- test_sink_transport_ = nullptr;
-
- if (clientif_source_ != nullptr) delete clientif_source_;
- clientif_source_ = nullptr;
- if (test_source_transport_ != nullptr) delete test_source_transport_;
- test_source_transport_ = nullptr;
+ if (clientif_ != nullptr) delete clientif_;
+ clientif_ = nullptr;
+ if (test_transport_ != nullptr) delete test_transport_;
+ test_transport_ = nullptr;
}
bool IsSoftwarePcmParametersSupported(const PcmParameters& pcm_config) {
const std::vector<AudioCapabilities>& capabilities =
- clientif_sink_->GetAudioCapabilities();
+ clientif_->GetAudioCapabilities();
PcmParameters pcm_capabilities = capabilities[0].pcmCapabilities();
bool is_pcm_config_valid =
(pcm_config.sampleRate != SampleRate::RATE_UNKNOWN &&
@@ -242,19 +175,9 @@ class BluetoothAudioClientInterfaceTest : public Test {
return (is_pcm_config_valid && is_pcm_config_supported);
}
- bool IsSinkSoftwarePcmParameters_2_1_Supported(
- const PcmParameters_2_1& pcm_config) {
- return IsSoftwarePcmParameters_2_1_Supported(pcm_config, clientif_sink_);
- }
-
- bool IsSourceSoftwarePcmParameters_2_1_Supported(
- const PcmParameters_2_1& pcm_config) {
- return IsSoftwarePcmParameters_2_1_Supported(pcm_config, clientif_source_);
- }
-
bool IsCodecOffloadingSupported(const CodecConfiguration& codec_config) {
CodecCapabilities codec_capability = {};
- for (auto audio_capability : clientif_sink_->GetAudioCapabilities()) {
+ for (auto audio_capability : clientif_->GetAudioCapabilities()) {
if (audio_capability.codecCapabilities().codecType ==
codec_config.codecType) {
codec_capability = audio_capability.codecCapabilities();
@@ -323,25 +246,6 @@ class BluetoothAudioClientInterfaceTest : public Test {
return false;
}
}
-
- private:
- bool IsSoftwarePcmParameters_2_1_Supported(
- const PcmParameters_2_1& pcm_config,
- const BluetoothAudioClientInterface* clientif_) {
- const std::vector<AudioCapabilities_2_1>& capabilities =
- clientif_->GetAudioCapabilities_2_1();
- PcmParameters_2_1 pcm_capabilities = capabilities[0].pcmCapabilities();
- bool is_pcm_config_valid =
- (pcm_config.sampleRate != SampleRate_2_1::RATE_UNKNOWN &&
- pcm_config.bitsPerSample != BitsPerSample::BITS_UNKNOWN &&
- pcm_config.channelMode != ChannelMode::UNKNOWN &&
- pcm_config.dataIntervalUs != 0);
- bool is_pcm_config_supported =
- (pcm_config.sampleRate & pcm_capabilities.sampleRate &&
- pcm_config.bitsPerSample & pcm_capabilities.bitsPerSample &&
- pcm_config.channelMode & pcm_capabilities.channelMode);
- return (is_pcm_config_valid && is_pcm_config_supported);
- }
};
} // namespace
@@ -355,11 +259,11 @@ TEST_F(BluetoothAudioClientInterfaceTest, A2dpCodecToHalPcmConfig) {
bits_per_sample_pair.btav_bits_per_sample_;
for (auto channel_mode_pair : kChannelModePairs) {
a2dp_codec_config.channel_mode = channel_mode_pair.btav_channel_mode_;
- ASSERT_EQ(A2dpCodecToHalSampleRate(a2dp_codec_config),
+ EXPECT_EQ(A2dpCodecToHalSampleRate(a2dp_codec_config),
sample_rate_pair.hal_sample_rate_);
- ASSERT_EQ(A2dpCodecToHalBitsPerSample(a2dp_codec_config),
+ EXPECT_EQ(A2dpCodecToHalBitsPerSample(a2dp_codec_config),
bits_per_sample_pair.hal_bits_per_sample_);
- ASSERT_EQ(A2dpCodecToHalChannelMode(a2dp_codec_config),
+ EXPECT_EQ(A2dpCodecToHalChannelMode(a2dp_codec_config),
channel_mode_pair.hal_channel_mode_);
} // ChannelMode
} // BitsPerSampple
@@ -367,10 +271,9 @@ TEST_F(BluetoothAudioClientInterfaceTest, A2dpCodecToHalPcmConfig) {
}
TEST_F(BluetoothAudioClientInterfaceTest, StartAndEndA2dpSoftwareSession) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_SOFTWARE_ENCODING_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_SOFTWARE_ENCODING_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
AudioConfiguration audio_config = {};
PcmParameters pcm_config = {};
for (auto sample_rate_pair : kSampleRatePairs) {
@@ -380,13 +283,13 @@ TEST_F(BluetoothAudioClientInterfaceTest, StartAndEndA2dpSoftwareSession) {
for (auto channel_mode_pair : kChannelModePairs) {
pcm_config.channelMode = channel_mode_pair.hal_channel_mode_;
audio_config.pcmConfig(pcm_config);
- clientif_sink_->UpdateAudioConfig(audio_config);
+ clientif_->UpdateAudioConfig(audio_config);
if (IsSoftwarePcmParametersSupported(pcm_config)) {
- ASSERT_EQ(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->StartSession(), kClientIfReturnSuccess);
} else {
- ASSERT_NE(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_NE(clientif_->StartSession(), kClientIfReturnSuccess);
}
- ASSERT_EQ(clientif_sink_->EndSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->EndSession(), kClientIfReturnSuccess);
} // ChannelMode
} // BitsPerSampple
} // SampleRate
@@ -467,10 +370,9 @@ std::vector<CodecConfiguration> SbcCodecConfigurationsGenerator() {
}
TEST_F(BluetoothAudioClientInterfaceTest, A2dpSbcCodecOffloadingState) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
auto sbc_codec_configs = SbcCodecConfigurationsGenerator();
for (auto codec_offloading_preference :
CodecOffloadingPreferenceGenerator(BTAV_A2DP_CODEC_INDEX_SOURCE_SBC)) {
@@ -487,20 +389,19 @@ TEST_F(BluetoothAudioClientInterfaceTest, A2dpSbcCodecOffloadingState) {
}
TEST_F(BluetoothAudioClientInterfaceTest, StartAndEndA2dpOffloadSbcSession) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
AudioConfiguration audio_config = {};
for (CodecConfiguration codec_config : SbcCodecConfigurationsGenerator()) {
audio_config.codecConfig(codec_config);
- clientif_sink_->UpdateAudioConfig(audio_config);
+ clientif_->UpdateAudioConfig(audio_config);
if (IsCodecOffloadingSupported(codec_config)) {
- ASSERT_EQ(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->StartSession(), kClientIfReturnSuccess);
} else {
- ASSERT_NE(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_NE(clientif_->StartSession(), kClientIfReturnSuccess);
}
- ASSERT_EQ(clientif_sink_->EndSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->EndSession(), kClientIfReturnSuccess);
}
}
@@ -541,10 +442,9 @@ std::vector<CodecConfiguration> AacCodecConfigurationsGenerator() {
}
TEST_F(BluetoothAudioClientInterfaceTest, A2dpAacCodecOffloadingState) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
auto aac_codec_configs = AacCodecConfigurationsGenerator();
for (auto codec_offloading_preference :
CodecOffloadingPreferenceGenerator(BTAV_A2DP_CODEC_INDEX_SOURCE_AAC)) {
@@ -561,20 +461,19 @@ TEST_F(BluetoothAudioClientInterfaceTest, A2dpAacCodecOffloadingState) {
}
TEST_F(BluetoothAudioClientInterfaceTest, StartAndEndA2dpOffloadAacSession) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
AudioConfiguration audio_config = {};
for (CodecConfiguration codec_config : AacCodecConfigurationsGenerator()) {
audio_config.codecConfig(codec_config);
- clientif_sink_->UpdateAudioConfig(audio_config);
+ clientif_->UpdateAudioConfig(audio_config);
if (IsCodecOffloadingSupported(codec_config)) {
- ASSERT_EQ(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->StartSession(), kClientIfReturnSuccess);
} else {
- ASSERT_NE(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_NE(clientif_->StartSession(), kClientIfReturnSuccess);
}
- ASSERT_EQ(clientif_sink_->EndSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->EndSession(), kClientIfReturnSuccess);
}
}
@@ -612,10 +511,9 @@ std::vector<CodecConfiguration> LdacCodecConfigurationsGenerator() {
}
TEST_F(BluetoothAudioClientInterfaceTest, A2dpLdacCodecOffloadingState) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
auto ldac_codec_configs = LdacCodecConfigurationsGenerator();
for (auto codec_offloading_preference :
CodecOffloadingPreferenceGenerator(BTAV_A2DP_CODEC_INDEX_SOURCE_LDAC)) {
@@ -632,20 +530,19 @@ TEST_F(BluetoothAudioClientInterfaceTest, A2dpLdacCodecOffloadingState) {
}
TEST_F(BluetoothAudioClientInterfaceTest, StartAndEndA2dpOffloadLdacSession) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
AudioConfiguration audio_config = {};
for (CodecConfiguration codec_config : LdacCodecConfigurationsGenerator()) {
audio_config.codecConfig(codec_config);
- clientif_sink_->UpdateAudioConfig(audio_config);
+ clientif_->UpdateAudioConfig(audio_config);
if (IsCodecOffloadingSupported(codec_config)) {
- ASSERT_EQ(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->StartSession(), kClientIfReturnSuccess);
} else {
- ASSERT_NE(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_NE(clientif_->StartSession(), kClientIfReturnSuccess);
}
- ASSERT_EQ(clientif_sink_->EndSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->EndSession(), kClientIfReturnSuccess);
}
}
@@ -678,10 +575,9 @@ std::vector<CodecConfiguration> AptxCodecConfigurationsGenerator(
}
TEST_F(BluetoothAudioClientInterfaceTest, A2dpAptxCodecOffloadingState) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
auto aptx_codec_configs = AptxCodecConfigurationsGenerator(CodecType::APTX);
for (auto codec_offloading_preference :
CodecOffloadingPreferenceGenerator(BTAV_A2DP_CODEC_INDEX_SOURCE_APTX)) {
@@ -698,29 +594,27 @@ TEST_F(BluetoothAudioClientInterfaceTest, A2dpAptxCodecOffloadingState) {
}
TEST_F(BluetoothAudioClientInterfaceTest, StartAndEndA2dpOffloadAptxSession) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
AudioConfiguration audio_config = {};
for (CodecConfiguration codec_config :
AptxCodecConfigurationsGenerator(CodecType::APTX)) {
audio_config.codecConfig(codec_config);
- clientif_sink_->UpdateAudioConfig(audio_config);
+ clientif_->UpdateAudioConfig(audio_config);
if (IsCodecOffloadingSupported(codec_config)) {
- ASSERT_EQ(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->StartSession(), kClientIfReturnSuccess);
} else {
- ASSERT_NE(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_NE(clientif_->StartSession(), kClientIfReturnSuccess);
}
- ASSERT_EQ(clientif_sink_->EndSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->EndSession(), kClientIfReturnSuccess);
}
}
TEST_F(BluetoothAudioClientInterfaceTest, A2dpAptxHdCodecOffloadingState) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
auto aptx_hd_codec_configs =
AptxCodecConfigurationsGenerator(CodecType::APTX_HD);
for (auto codec_offloading_preference : CodecOffloadingPreferenceGenerator(
@@ -738,30 +632,28 @@ TEST_F(BluetoothAudioClientInterfaceTest, A2dpAptxHdCodecOffloadingState) {
}
TEST_F(BluetoothAudioClientInterfaceTest, StartAndEndA2dpOffloadAptxHdSession) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
AudioConfiguration audio_config = {};
for (CodecConfiguration codec_config :
AptxCodecConfigurationsGenerator(CodecType::APTX_HD)) {
audio_config.codecConfig(codec_config);
- clientif_sink_->UpdateAudioConfig(audio_config);
+ clientif_->UpdateAudioConfig(audio_config);
if (IsCodecOffloadingSupported(codec_config)) {
- ASSERT_EQ(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->StartSession(), kClientIfReturnSuccess);
} else {
- ASSERT_NE(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_NE(clientif_->StartSession(), kClientIfReturnSuccess);
}
- ASSERT_EQ(clientif_sink_->EndSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->EndSession(), kClientIfReturnSuccess);
}
}
TEST_F(BluetoothAudioClientInterfaceTest,
StartAndEndA2dpOffloadUnknownSession) {
- test_sink_transport_ =
- new TestSinkTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::A2DP_HARDWARE_OFFLOAD_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
AudioConfiguration audio_config = {};
CodecConfiguration codec_config = {};
codec_config.codecType = CodecType::UNKNOWN;
@@ -770,21 +662,20 @@ TEST_F(BluetoothAudioClientInterfaceTest,
codec_config.encodedAudioBitrate = 328000;
codec_config.config = {};
audio_config.codecConfig(codec_config);
- clientif_sink_->UpdateAudioConfig(audio_config);
+ clientif_->UpdateAudioConfig(audio_config);
if (IsCodecOffloadingSupported(codec_config)) {
- ASSERT_EQ(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->StartSession(), kClientIfReturnSuccess);
} else {
- ASSERT_NE(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_NE(clientif_->StartSession(), kClientIfReturnSuccess);
}
- ASSERT_EQ(clientif_sink_->EndSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->EndSession(), kClientIfReturnSuccess);
}
TEST_F(BluetoothAudioClientInterfaceTest,
StartAndEndHearingAidSoftwareSession) {
- test_sink_transport_ = new TestSinkTransport(
- SessionType::HEARING_AID_SOFTWARE_ENCODING_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
+ test_transport_ =
+ new TestTransport(SessionType::HEARING_AID_SOFTWARE_ENCODING_DATAPATH);
+ clientif_ = new BluetoothAudioClientInterface(test_transport_, nullptr);
AudioConfiguration audio_config = {};
PcmParameters pcm_config = {};
for (auto sample_rate_pair : kSampleRatePairs) {
@@ -794,78 +685,14 @@ TEST_F(BluetoothAudioClientInterfaceTest,
for (auto channel_mode_pair : kChannelModePairs) {
pcm_config.channelMode = channel_mode_pair.hal_channel_mode_;
audio_config.pcmConfig(pcm_config);
- clientif_sink_->UpdateAudioConfig(audio_config);
+ clientif_->UpdateAudioConfig(audio_config);
if (IsSoftwarePcmParametersSupported(pcm_config)) {
- ASSERT_EQ(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->StartSession(), kClientIfReturnSuccess);
} else {
- ASSERT_NE(clientif_sink_->StartSession(), kClientIfReturnSuccess);
+ EXPECT_NE(clientif_->StartSession(), kClientIfReturnSuccess);
}
- ASSERT_EQ(clientif_sink_->EndSession(), kClientIfReturnSuccess);
+ EXPECT_EQ(clientif_->EndSession(), kClientIfReturnSuccess);
} // ChannelMode
} // BitsPerSampple
} // SampleRate
}
-
-TEST_F(BluetoothAudioClientInterfaceTest,
- StartAndEndLeAudioEncodingSoftwareSession) {
- test_sink_transport_ = new TestSinkTransport(
- SessionType_2_1::LE_AUDIO_SOFTWARE_ENCODING_DATAPATH);
- clientif_sink_ =
- new BluetoothAudioSinkClientInterface(test_sink_transport_, nullptr);
- AudioConfiguration_2_1 audio_config = {};
- PcmParameters_2_1 pcm_config = {};
- for (auto sample_rate : kSampleRates_2_1) {
- pcm_config.sampleRate = sample_rate;
- for (auto bits_per_sample_pair : kBitsPerSamplePairs) {
- pcm_config.bitsPerSample = bits_per_sample_pair.hal_bits_per_sample_;
- for (auto channel_mode_pair : kChannelModePairs) {
- pcm_config.channelMode = channel_mode_pair.hal_channel_mode_;
- for (auto data_interval_us : kDataIntervalUs) {
- pcm_config.dataIntervalUs = data_interval_us;
- audio_config.pcmConfig(pcm_config);
- clientif_sink_->UpdateAudioConfig_2_1(audio_config);
- if (IsSinkSoftwarePcmParameters_2_1_Supported(pcm_config)) {
- ASSERT_EQ(clientif_sink_->StartSession_2_1(),
- kClientIfReturnSuccess);
- } else {
- ASSERT_NE(clientif_sink_->StartSession_2_1(),
- kClientIfReturnSuccess);
- }
- ASSERT_EQ(clientif_sink_->EndSession(), kClientIfReturnSuccess);
- } // dataIntervalUs
- } // ChannelMode
- } // BitsPerSampple
- } // SampleRate
-}
-
-TEST_F(BluetoothAudioClientInterfaceTest,
- StartAndEndLeAudioDecodedSoftwareSession) {
- test_source_transport_ = new TestSourceTransport(
- SessionType_2_1::LE_AUDIO_SOFTWARE_DECODED_DATAPATH);
- clientif_source_ =
- new BluetoothAudioSourceClientInterface(test_source_transport_, nullptr);
- AudioConfiguration_2_1 audio_config = {};
- PcmParameters_2_1 pcm_config = {};
- for (auto sample_rate : kSampleRates_2_1) {
- pcm_config.sampleRate = sample_rate;
- for (auto bits_per_sample_pair : kBitsPerSamplePairs) {
- pcm_config.bitsPerSample = bits_per_sample_pair.hal_bits_per_sample_;
- for (auto channel_mode_pair : kChannelModePairs) {
- pcm_config.channelMode = channel_mode_pair.hal_channel_mode_;
- for (auto data_interval_us : kDataIntervalUs) {
- pcm_config.dataIntervalUs = data_interval_us;
- audio_config.pcmConfig(pcm_config);
- clientif_source_->UpdateAudioConfig_2_1(audio_config);
- if (IsSourceSoftwarePcmParameters_2_1_Supported(pcm_config)) {
- ASSERT_EQ(clientif_source_->StartSession_2_1(),
- kClientIfReturnSuccess);
- } else {
- ASSERT_NE(clientif_source_->StartSession_2_1(),
- kClientIfReturnSuccess);
- }
- ASSERT_EQ(clientif_source_->EndSession(), kClientIfReturnSuccess);
- } // dataIntervalUs
- } // ChannelMode
- } // BitsPerSampple
- } // SampleRate
-}
diff --git a/audio_hal_interface/codec_status.cc b/audio_hal_interface/codec_status.cc
index cd9d88e05..0819e5c38 100644
--- a/audio_hal_interface/codec_status.cc
+++ b/audio_hal_interface/codec_status.cc
@@ -14,8 +14,6 @@
* limitations under the License.
*/
-#define LOG_TAG "bluetooth"
-
#include "codec_status.h"
#include "client_interface.h"
diff --git a/audio_hal_interface/hal_version_manager.h b/audio_hal_interface/hal_version_manager.h
deleted file mode 100644
index 779ea3ede..000000000
--- a/audio_hal_interface/hal_version_manager.h
+++ /dev/null
@@ -1,136 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <android/hardware/bluetooth/audio/2.1/IBluetoothAudioProvidersFactory.h>
-#include <android/hardware/bluetooth/audio/2.1/types.h>
-#include <android/hidl/manager/1.2/IServiceManager.h>
-#include <base/logging.h>
-#include <hidl/ServiceManagement.h>
-
-namespace bluetooth {
-namespace audio {
-
-using ::android::hardware::hidl_vec;
-
-using IBluetoothAudioProvidersFactory_2_0 = ::android::hardware::bluetooth::
- audio::V2_0::IBluetoothAudioProvidersFactory;
-using IBluetoothAudioProvidersFactory_2_1 = ::android::hardware::bluetooth::
- audio::V2_1::IBluetoothAudioProvidersFactory;
-
-constexpr char kFullyQualifiedInterfaceName_2_0[] =
- "android.hardware.bluetooth.audio@2.0::IBluetoothAudioProvidersFactory";
-constexpr char kFullyQualifiedInterfaceName_2_1[] =
- "android.hardware.bluetooth.audio@2.1::IBluetoothAudioProvidersFactory";
-
-enum class BluetoothAudioHalVersion : uint8_t {
- VERSION_2_0 = 0,
- VERSION_2_1,
- VERSION_UNAVAILABLE,
-};
-
-class HalVersionManager {
- public:
- static BluetoothAudioHalVersion GetHalVersion() {
- std::lock_guard<std::mutex> guard(instance_ptr->mutex_);
- return instance_ptr->hal_version_;
- }
-
- static android::sp<IBluetoothAudioProvidersFactory_2_1>
- GetProvidersFactory_2_1() {
- std::lock_guard<std::mutex> guard(instance_ptr->mutex_);
- if (instance_ptr->hal_version_ != BluetoothAudioHalVersion::VERSION_2_1) {
- return nullptr;
- }
- android::sp<IBluetoothAudioProvidersFactory_2_1> providers_factory =
- IBluetoothAudioProvidersFactory_2_1::getService();
- CHECK(providers_factory)
- << "V2_1::IBluetoothAudioProvidersFactory::getService() failed";
-
- LOG(INFO) << "V2_1::IBluetoothAudioProvidersFactory::getService() returned "
- << providers_factory.get()
- << (providers_factory->isRemote() ? " (remote)" : " (local)");
- return providers_factory;
- }
-
- static android::sp<IBluetoothAudioProvidersFactory_2_0>
- GetProvidersFactory_2_0() {
- std::unique_lock<std::mutex> guard(instance_ptr->mutex_);
- if (instance_ptr->hal_version_ == BluetoothAudioHalVersion::VERSION_2_1) {
- guard.unlock();
- return instance_ptr->GetProvidersFactory_2_1();
- }
- android::sp<IBluetoothAudioProvidersFactory_2_0> providers_factory =
- IBluetoothAudioProvidersFactory_2_0::getService();
- CHECK(providers_factory)
- << "V2_0::IBluetoothAudioProvidersFactory::getService() failed";
-
- LOG(INFO) << "V2_0::IBluetoothAudioProvidersFactory::getService() returned "
- << providers_factory.get()
- << (providers_factory->isRemote() ? " (remote)" : " (local)");
- guard.unlock();
- return providers_factory;
- }
-
- HalVersionManager() {
- auto service_manager = android::hardware::defaultServiceManager1_2();
- CHECK(service_manager != nullptr);
- size_t instance_count = 0;
- auto listManifestByInterface_cb =
- [&instance_count](
- const hidl_vec<android::hardware::hidl_string>& instanceNames) {
- instance_count = instanceNames.size();
- };
- auto hidl_retval = service_manager->listManifestByInterface(
- kFullyQualifiedInterfaceName_2_1, listManifestByInterface_cb);
- if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__ << ": IServiceManager::listByInterface failure: "
- << hidl_retval.description();
- return;
- }
-
- if (instance_count > 0) {
- hal_version_ = BluetoothAudioHalVersion::VERSION_2_1;
- return;
- }
-
- hidl_retval = service_manager->listManifestByInterface(
- kFullyQualifiedInterfaceName_2_0, listManifestByInterface_cb);
- if (!hidl_retval.isOk()) {
- LOG(FATAL) << __func__ << ": IServiceManager::listByInterface failure: "
- << hidl_retval.description();
- return;
- }
-
- if (instance_count > 0) {
- hal_version_ = BluetoothAudioHalVersion::VERSION_2_0;
- return;
- }
-
- hal_version_ = BluetoothAudioHalVersion::VERSION_UNAVAILABLE;
- LOG(ERROR) << __func__ << " No supported HAL version";
- }
-
- private:
- static std::unique_ptr<HalVersionManager> instance_ptr;
- std::mutex mutex_;
-
- BluetoothAudioHalVersion hal_version_;
-};
-
-} // namespace audio
-} // namespace bluetooth
diff --git a/audio_hal_interface/hearing_aid_software_encoding.cc b/audio_hal_interface/hearing_aid_software_encoding.cc
index 2482502c0..5107d46be 100644
--- a/audio_hal_interface/hearing_aid_software_encoding.cc
+++ b/audio_hal_interface/hearing_aid_software_encoding.cc
@@ -33,15 +33,14 @@ using ::bluetooth::audio::ChannelMode;
using ::bluetooth::audio::PcmParameters;
using ::bluetooth::audio::SampleRate;
using ::bluetooth::audio::SessionType;
-using ::bluetooth::audio::SessionType_2_1;
using ::bluetooth::audio::hearing_aid::StreamCallbacks;
// Transport implementation for Hearing Aids
class HearingAidTransport
- : public bluetooth::audio::IBluetoothSinkTransportInstance {
+ : public bluetooth::audio::IBluetoothTransportInstance {
public:
HearingAidTransport(StreamCallbacks stream_cb)
- : IBluetoothSinkTransportInstance(
+ : IBluetoothTransportInstance(
SessionType::HEARING_AID_SOFTWARE_ENCODING_DATAPATH, {}),
stream_cb_(std::move(stream_cb)),
remote_delay_report_ms_(0),
@@ -143,7 +142,7 @@ bool HearingAidGetSelectedHalPcmConfig(PcmParameters* hal_pcm_config) {
// Sink instance of Hearing Aids to provide call-in APIs for Bluetooth Audio Hal
HearingAidTransport* hearing_aid_sink = nullptr;
// Common interface to call-out into Bluetooth Audio Hal
-bluetooth::audio::BluetoothAudioSinkClientInterface*
+bluetooth::audio::BluetoothAudioClientInterface*
hearing_aid_hal_clientinterface = nullptr;
bool btaudio_hearing_aid_disabled = false;
bool is_configured = false;
@@ -179,8 +178,8 @@ bool init(StreamCallbacks stream_cb,
hearing_aid_sink = new HearingAidTransport(std::move(stream_cb));
hearing_aid_hal_clientinterface =
- new bluetooth::audio::BluetoothAudioSinkClientInterface(hearing_aid_sink,
- message_loop);
+ new bluetooth::audio::BluetoothAudioClientInterface(hearing_aid_sink,
+ message_loop);
if (!hearing_aid_hal_clientinterface->IsValid()) {
LOG(WARNING) << __func__ << ": BluetoothAudio HAL for Hearing Aid is invalid?!";
delete hearing_aid_hal_clientinterface;
diff --git a/audio_hal_interface/hearing_aid_software_encoding_host.cc b/audio_hal_interface/hearing_aid_software_encoding_host.cc
deleted file mode 100644
index 37d5bb2bd..000000000
--- a/audio_hal_interface/hearing_aid_software_encoding_host.cc
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "audio_hal_interface/hearing_aid_software_encoding.h"
-
-namespace bluetooth {
-namespace audio {
-namespace hearing_aid {
-
-bool is_hal_2_0_enabled() { return false; }
-
-bool init(StreamCallbacks stream_cb,
- bluetooth::common::MessageLoopThread* message_loop) {
- return false;
-}
-
-void cleanup() {}
-
-void start_session() {}
-
-void end_session() {}
-
-size_t read(uint8_t* p_buf, uint32_t len) { return 0; }
-
-void set_remote_delay(uint16_t delay_report_ms) {}
-
-} // namespace hearing_aid
-} // namespace audio
-} // namespace bluetooth
diff --git a/audio_hal_interface/le_audio_software.cc b/audio_hal_interface/le_audio_software.cc
deleted file mode 100644
index 7abac4009..000000000
--- a/audio_hal_interface/le_audio_software.cc
+++ /dev/null
@@ -1,556 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com. Represented by EHIMA -
- * www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "BTAudioClientLeAudio"
-
-#include "le_audio_software.h"
-
-#include "client_interface.h"
-#include "osi/include/log.h"
-#include "osi/include/properties.h"
-
-namespace {
-
-using ::android::hardware::bluetooth::audio::V2_0::BitsPerSample;
-using ::android::hardware::bluetooth::audio::V2_0::ChannelMode;
-using ::android::hardware::bluetooth::audio::V2_0::CodecType;
-using ::android::hardware::bluetooth::audio::V2_1::PcmParameters;
-using ::bluetooth::audio::BluetoothAudioCtrlAck;
-using ::bluetooth::audio::SampleRate_2_1;
-using ::bluetooth::audio::SessionType;
-using ::bluetooth::audio::SessionType_2_1;
-using ::bluetooth::audio::le_audio::LeAudioClientInterface;
-using ::bluetooth::audio::le_audio::StreamCallbacks;
-
-bluetooth::audio::BluetoothAudioSinkClientInterface*
- le_audio_sink_hal_clientinterface = nullptr;
-bluetooth::audio::BluetoothAudioSourceClientInterface*
- le_audio_source_hal_clientinterface = nullptr;
-
-static bool is_source_hal_enabled() {
- return le_audio_source_hal_clientinterface != nullptr;
-}
-
-static bool is_sink_hal_enabled() {
- return le_audio_sink_hal_clientinterface != nullptr;
-}
-
-class LeAudioTransport {
- public:
- LeAudioTransport(void (*flush)(void), StreamCallbacks stream_cb,
- PcmParameters pcm_config)
- : flush_(std::move(flush)),
- stream_cb_(std::move(stream_cb)),
- remote_delay_report_ms_(0),
- total_bytes_processed_(0),
- data_position_({}),
- pcm_config_(std::move(pcm_config)){};
-
- BluetoothAudioCtrlAck StartRequest() {
- LOG(INFO) << __func__;
- if (stream_cb_.on_resume_(true)) {
- return BluetoothAudioCtrlAck::SUCCESS_FINISHED;
- }
- return BluetoothAudioCtrlAck::FAILURE;
- }
-
- BluetoothAudioCtrlAck SuspendRequest() {
- LOG(INFO) << __func__;
- if (stream_cb_.on_suspend_()) {
- flush_();
- return BluetoothAudioCtrlAck::SUCCESS_FINISHED;
- } else {
- return BluetoothAudioCtrlAck::FAILURE;
- }
- }
-
- void StopRequest() {
- LOG(INFO) << __func__;
- if (stream_cb_.on_suspend_()) {
- flush_();
- }
- }
-
- bool GetPresentationPosition(uint64_t* remote_delay_report_ns,
- uint64_t* total_bytes_processed,
- timespec* data_position) {
- VLOG(2) << __func__ << ": data=" << total_bytes_processed_
- << " byte(s), timestamp=" << data_position_.tv_sec << "."
- << data_position_.tv_nsec
- << "s, delay report=" << remote_delay_report_ms_ << " msec.";
- if (remote_delay_report_ns != nullptr) {
- *remote_delay_report_ns = remote_delay_report_ms_ * 1000000u;
- }
- if (total_bytes_processed != nullptr)
- *total_bytes_processed = total_bytes_processed_;
- if (data_position != nullptr) *data_position = data_position_;
-
- return true;
- }
-
- void MetadataChanged(const source_metadata_t& source_metadata) {
- auto track_count = source_metadata.track_count;
- auto tracks = source_metadata.tracks;
- LOG(INFO) << __func__ << ": " << track_count << " track(s) received";
- while (track_count) {
- VLOG(1) << __func__ << ": usage=" << tracks->usage
- << ", content_type=" << tracks->content_type
- << ", gain=" << tracks->gain;
- --track_count;
- ++tracks;
- }
- }
-
- void ResetPresentationPosition() {
- VLOG(2) << __func__ << ": called.";
- remote_delay_report_ms_ = 0;
- total_bytes_processed_ = 0;
- data_position_ = {};
- }
-
- void LogBytesProcessed(size_t bytes_processed) {
- if (bytes_processed) {
- total_bytes_processed_ += bytes_processed;
- clock_gettime(CLOCK_MONOTONIC, &data_position_);
- }
- }
-
- void SetRemoteDelay(uint16_t delay_report_ms) {
- LOG(INFO) << __func__ << ": delay_report=" << delay_report_ms << " msec";
- remote_delay_report_ms_ = delay_report_ms;
- }
-
- const PcmParameters& LeAudioGetSelectedHalPcmConfig() { return pcm_config_; }
-
- void LeAudioSetSelectedHalPcmConfig(SampleRate_2_1 sample_rate,
- BitsPerSample bit_rate,
- ChannelMode channel_mode,
- uint32_t data_interval) {
- pcm_config_.sampleRate = sample_rate;
- pcm_config_.bitsPerSample = bit_rate;
- pcm_config_.channelMode = channel_mode;
- pcm_config_.dataIntervalUs = data_interval;
- }
-
- private:
- void (*flush_)(void);
- StreamCallbacks stream_cb_;
- uint16_t remote_delay_report_ms_;
- uint64_t total_bytes_processed_;
- timespec data_position_;
- PcmParameters pcm_config_;
-};
-
-static void flush_sink() {
- if (!is_sink_hal_enabled()) return;
-
- le_audio_sink_hal_clientinterface->FlushAudioData();
-}
-
-// Sink transport implementation for Le Audio
-class LeAudioSinkTransport
- : public bluetooth::audio::IBluetoothSinkTransportInstance {
- public:
- LeAudioSinkTransport(StreamCallbacks stream_cb)
- : IBluetoothSinkTransportInstance(
- SessionType_2_1::LE_AUDIO_SOFTWARE_ENCODING_DATAPATH, {}) {
- transport_ =
- new LeAudioTransport(flush_sink, std::move(stream_cb),
- {SampleRate_2_1::RATE_16000, ChannelMode::STEREO,
- BitsPerSample::BITS_16, 0});
- };
-
- ~LeAudioSinkTransport() { delete transport_; }
-
- BluetoothAudioCtrlAck StartRequest() override {
- return transport_->StartRequest();
- }
-
- BluetoothAudioCtrlAck SuspendRequest() override {
- return transport_->SuspendRequest();
- }
-
- void StopRequest() override { transport_->StopRequest(); }
-
- bool GetPresentationPosition(uint64_t* remote_delay_report_ns,
- uint64_t* total_bytes_read,
- timespec* data_position) override {
- return transport_->GetPresentationPosition(remote_delay_report_ns,
- total_bytes_read, data_position);
- }
-
- void MetadataChanged(const source_metadata_t& source_metadata) override {
- transport_->MetadataChanged(source_metadata);
- }
-
- void ResetPresentationPosition() override {
- transport_->ResetPresentationPosition();
- }
-
- void LogBytesRead(size_t bytes_read) override {
- transport_->LogBytesProcessed(bytes_read);
- }
-
- void SetRemoteDelay(uint16_t delay_report_ms) {
- transport_->SetRemoteDelay(delay_report_ms);
- }
-
- const PcmParameters& LeAudioGetSelectedHalPcmConfig() {
- return transport_->LeAudioGetSelectedHalPcmConfig();
- }
-
- void LeAudioSetSelectedHalPcmConfig(SampleRate_2_1 sample_rate,
- BitsPerSample bit_rate,
- ChannelMode channel_mode,
- uint32_t data_interval) {
- transport_->LeAudioSetSelectedHalPcmConfig(sample_rate, bit_rate,
- channel_mode, data_interval);
- }
-
- private:
- LeAudioTransport* transport_;
-};
-
-static void flush_source() {
- if (le_audio_source_hal_clientinterface == nullptr) return;
-
- le_audio_source_hal_clientinterface->FlushAudioData();
-}
-
-class LeAudioSourceTransport
- : public bluetooth::audio::IBluetoothSourceTransportInstance {
- public:
- LeAudioSourceTransport(StreamCallbacks stream_cb)
- : IBluetoothSourceTransportInstance(
- SessionType_2_1::LE_AUDIO_SOFTWARE_DECODED_DATAPATH, {}) {
- transport_ =
- new LeAudioTransport(flush_source, std::move(stream_cb),
- {SampleRate_2_1::RATE_16000, ChannelMode::MONO,
- BitsPerSample::BITS_16, 0});
- };
-
- ~LeAudioSourceTransport() { delete transport_; }
-
- BluetoothAudioCtrlAck StartRequest() override {
- return transport_->StartRequest();
- }
-
- BluetoothAudioCtrlAck SuspendRequest() override {
- return transport_->SuspendRequest();
- }
-
- void StopRequest() override { transport_->StopRequest(); }
-
- bool GetPresentationPosition(uint64_t* remote_delay_report_ns,
- uint64_t* total_bytes_written,
- timespec* data_position) override {
- return transport_->GetPresentationPosition(
- remote_delay_report_ns, total_bytes_written, data_position);
- }
-
- void MetadataChanged(const source_metadata_t& source_metadata) override {
- transport_->MetadataChanged(source_metadata);
- }
-
- void ResetPresentationPosition() override {
- transport_->ResetPresentationPosition();
- }
-
- void LogBytesWritten(size_t bytes_written) override {
- transport_->LogBytesProcessed(bytes_written);
- }
-
- void SetRemoteDelay(uint16_t delay_report_ms) {
- transport_->SetRemoteDelay(delay_report_ms);
- }
-
- const PcmParameters& LeAudioGetSelectedHalPcmConfig() {
- return transport_->LeAudioGetSelectedHalPcmConfig();
- }
-
- void LeAudioSetSelectedHalPcmConfig(SampleRate_2_1 sample_rate,
- BitsPerSample bit_rate,
- ChannelMode channel_mode,
- uint32_t data_interval) {
- transport_->LeAudioSetSelectedHalPcmConfig(sample_rate, bit_rate,
- channel_mode, data_interval);
- }
-
- private:
- LeAudioTransport* transport_;
-};
-
-// Instance of Le Audio to provide call-in APIs for Bluetooth Audio Hal
-LeAudioSinkTransport* le_audio_sink = nullptr;
-LeAudioSourceTransport* le_audio_source = nullptr;
-} // namespace
-
-namespace bluetooth {
-namespace audio {
-namespace le_audio {
-
-LeAudioClientInterface* LeAudioClientInterface::interface = nullptr;
-LeAudioClientInterface* LeAudioClientInterface::Get() {
- if (osi_property_get_bool(BLUETOOTH_AUDIO_HAL_PROP_DISABLED, false)) {
- LOG(ERROR) << __func__ << ": BluetoothAudio HAL is disabled";
- return nullptr;
- }
-
- if (LeAudioClientInterface::interface == nullptr)
- LeAudioClientInterface::interface = new LeAudioClientInterface();
-
- return LeAudioClientInterface::interface;
-}
-
-static SampleRate_2_1 le_audio_sample_rate2audio_hal(uint32_t sample_rate_2_1) {
- switch (sample_rate_2_1) {
- case 8000:
- return SampleRate_2_1::RATE_8000;
- case 16000:
- return SampleRate_2_1::RATE_16000;
- case 24000:
- return SampleRate_2_1::RATE_24000;
- case 32000:
- return SampleRate_2_1::RATE_32000;
- case 44100:
- return SampleRate_2_1::RATE_44100;
- case 48000:
- return SampleRate_2_1::RATE_48000;
- case 88200:
- return SampleRate_2_1::RATE_88200;
- case 96000:
- return SampleRate_2_1::RATE_96000;
- case 176400:
- return SampleRate_2_1::RATE_176400;
- case 192000:
- return SampleRate_2_1::RATE_192000;
- };
- return SampleRate_2_1::RATE_UNKNOWN;
-}
-
-static BitsPerSample le_audio_bit_rate2audio_hal(uint8_t bits_per_sample) {
- switch (bits_per_sample) {
- case 16:
- return BitsPerSample::BITS_16;
- case 24:
- return BitsPerSample::BITS_24;
- case 32:
- return BitsPerSample::BITS_32;
- };
- return BitsPerSample::BITS_UNKNOWN;
-}
-
-static ChannelMode le_audio_channel_mode2audio_hal(uint8_t channels_count) {
- switch (channels_count) {
- case 1:
- return ChannelMode::MONO;
- case 2:
- return ChannelMode::STEREO;
- }
- return ChannelMode::UNKNOWN;
-}
-
-void LeAudioClientInterface::Sink::Cleanup() {
- LOG(INFO) << __func__;
- StopSession();
- delete le_audio_sink_hal_clientinterface;
- le_audio_sink_hal_clientinterface = nullptr;
- delete le_audio_sink;
- le_audio_sink = nullptr;
-}
-
-void LeAudioClientInterface::Sink::SetPcmParameters(
- const PcmParameters& params) {
- le_audio_sink->LeAudioSetSelectedHalPcmConfig(
- le_audio_sample_rate2audio_hal(params.sample_rate),
- le_audio_bit_rate2audio_hal(params.bits_per_sample),
- le_audio_channel_mode2audio_hal(params.channels_count),
- params.data_interval_us);
-}
-
-// Update Le Audio delay report to BluetoothAudio HAL
-void LeAudioClientInterface::Sink::SetRemoteDelay(uint16_t delay_report_ms) {
- LOG(INFO) << __func__ << ": delay_report_ms=" << delay_report_ms << " ms";
- le_audio_sink->SetRemoteDelay(delay_report_ms);
-}
-
-void LeAudioClientInterface::Sink::StartSession() {
- LOG(INFO) << __func__;
- AudioConfiguration_2_1 audio_config;
- audio_config.pcmConfig(le_audio_sink->LeAudioGetSelectedHalPcmConfig());
- if (!le_audio_sink_hal_clientinterface->UpdateAudioConfig_2_1(audio_config)) {
- LOG(ERROR) << __func__ << ": cannot update audio config to HAL";
- return;
- }
- le_audio_sink_hal_clientinterface->StartSession_2_1();
-}
-
-void LeAudioClientInterface::Sink::StopSession() {
- LOG(INFO) << __func__;
- le_audio_sink_hal_clientinterface->EndSession();
-}
-
-size_t LeAudioClientInterface::Sink::Read(uint8_t* p_buf, uint32_t len) {
- return le_audio_sink_hal_clientinterface->ReadAudioData(p_buf, len);
-}
-
-void LeAudioClientInterface::Source::Cleanup() {
- LOG(INFO) << __func__;
- StopSession();
- delete le_audio_source_hal_clientinterface;
- le_audio_source_hal_clientinterface = nullptr;
- delete le_audio_source;
- le_audio_source = nullptr;
-}
-
-void LeAudioClientInterface::Source::SetPcmParameters(
- const PcmParameters& params) {
- le_audio_source->LeAudioSetSelectedHalPcmConfig(
- le_audio_sample_rate2audio_hal(params.sample_rate),
- le_audio_bit_rate2audio_hal(params.bits_per_sample),
- le_audio_channel_mode2audio_hal(params.channels_count),
- params.data_interval_us);
-}
-
-void LeAudioClientInterface::Source::SetRemoteDelay(uint16_t delay_report_ms) {
- LOG(INFO) << __func__ << ": delay_report_ms=" << delay_report_ms << " ms";
- le_audio_source->SetRemoteDelay(delay_report_ms);
-}
-
-void LeAudioClientInterface::Source::StartSession() {
- LOG(INFO) << __func__;
- if (!is_source_hal_enabled()) return;
- AudioConfiguration_2_1 audio_config;
- audio_config.pcmConfig(le_audio_source->LeAudioGetSelectedHalPcmConfig());
- if (!le_audio_source_hal_clientinterface->UpdateAudioConfig_2_1(
- audio_config)) {
- LOG(ERROR) << __func__ << ": cannot update audio config to HAL";
- return;
- }
- le_audio_source_hal_clientinterface->StartSession_2_1();
-}
-
-void LeAudioClientInterface::Source::StopSession() {
- LOG(INFO) << __func__;
- le_audio_source_hal_clientinterface->EndSession();
-}
-
-size_t LeAudioClientInterface::Source::Write(const uint8_t* p_buf,
- uint32_t len) {
- return le_audio_source_hal_clientinterface->WriteAudioData(p_buf, len);
-}
-
-LeAudioClientInterface::Sink* LeAudioClientInterface::GetSink(
- StreamCallbacks stream_cb,
- bluetooth::common::MessageLoopThread* message_loop) {
- if (sink_ == nullptr) {
- sink_ = new Sink();
- } else {
- LOG(WARNING) << __func__ << ", Sink is already acquired";
- return nullptr;
- }
-
- LOG(INFO) << __func__;
-
- le_audio_sink = new LeAudioSinkTransport(std::move(stream_cb));
- le_audio_sink_hal_clientinterface =
- new bluetooth::audio::BluetoothAudioSinkClientInterface(le_audio_sink,
- message_loop);
- if (!le_audio_sink_hal_clientinterface->IsValid()) {
- LOG(WARNING) << __func__
- << ": BluetoothAudio HAL for Le Audio is invalid?!";
- delete le_audio_sink_hal_clientinterface;
- le_audio_sink_hal_clientinterface = nullptr;
- delete le_audio_sink;
- le_audio_sink = nullptr;
- delete sink_;
- sink_ = nullptr;
-
- return nullptr;
- }
-
- return sink_;
-}
-
-bool LeAudioClientInterface::IsSinkAcquired() { return sink_ != nullptr; }
-
-bool LeAudioClientInterface::ReleaseSink(LeAudioClientInterface::Sink* sink) {
- if (sink != sink_) {
- LOG(WARNING) << __func__ << ", can't release not acquired sink";
- return false;
- }
-
- if (le_audio_sink_hal_clientinterface && le_audio_sink) sink->Cleanup();
-
- delete (sink_);
- sink_ = nullptr;
-
- return true;
-}
-
-LeAudioClientInterface::Source* LeAudioClientInterface::GetSource(
- StreamCallbacks stream_cb,
- bluetooth::common::MessageLoopThread* message_loop) {
- if (source_ == nullptr) {
- source_ = new Source();
- } else {
- LOG(WARNING) << __func__ << ", Source is already acquired";
- return nullptr;
- }
-
- LOG(INFO) << __func__;
-
- le_audio_source = new LeAudioSourceTransport(std::move(stream_cb));
- le_audio_source_hal_clientinterface =
- new bluetooth::audio::BluetoothAudioSourceClientInterface(le_audio_source,
- message_loop);
- if (!le_audio_source_hal_clientinterface->IsValid()) {
- LOG(WARNING) << __func__
- << ": BluetoothAudio HAL for Le Audio is invalid?!";
- delete le_audio_source_hal_clientinterface;
- le_audio_source_hal_clientinterface = nullptr;
- delete le_audio_source;
- le_audio_source = nullptr;
- delete source_;
- source_ = nullptr;
-
- return nullptr;
- }
-
- return source_;
-}
-
-bool LeAudioClientInterface::IsSourceAcquired() { return source_ != nullptr; }
-
-bool LeAudioClientInterface::ReleaseSource(
- LeAudioClientInterface::Source* source) {
- if (source != source_) {
- LOG(WARNING) << __func__ << ", can't release not acquired source";
- return false;
- }
-
- if (le_audio_source_hal_clientinterface && le_audio_source) source->Cleanup();
-
- delete (source_);
- source_ = nullptr;
-
- return true;
-}
-
-} // namespace le_audio
-} // namespace audio
-} // namespace bluetooth
diff --git a/audio_hal_interface/le_audio_software.h b/audio_hal_interface/le_audio_software.h
deleted file mode 100644
index 51584e6f5..000000000
--- a/audio_hal_interface/le_audio_software.h
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <functional>
-
-#include "common/message_loop_thread.h"
-
-namespace bluetooth {
-namespace audio {
-namespace le_audio {
-
-struct StreamCallbacks {
- std::function<bool(bool start_media_task)> on_resume_;
- std::function<bool(void)> on_suspend_;
-};
-
-class LeAudioClientInterface {
- public:
- struct PcmParameters {
- uint32_t data_interval_us;
- uint32_t sample_rate;
- uint8_t bits_per_sample;
- uint8_t channels_count;
- };
-
- private:
- class IClientInterfaceEndpoint {
- public:
- virtual ~IClientInterfaceEndpoint() = default;
- virtual void Cleanup() = 0;
- virtual void SetPcmParameters(const PcmParameters& params) = 0;
- virtual void SetRemoteDelay(uint16_t delay_report_ms) = 0;
- virtual void StartSession() = 0;
- virtual void StopSession() = 0;
- };
-
- public:
- class Sink : public IClientInterfaceEndpoint {
- public:
- virtual ~Sink() = default;
-
- void Cleanup() override;
- void SetPcmParameters(const PcmParameters& params) override;
- void SetRemoteDelay(uint16_t delay_report_ms) override;
- void StartSession() override;
- void StopSession() override;
-
- // Read the stream of bytes sinked to us by the upper layers
- size_t Read(uint8_t* p_buf, uint32_t len);
- };
- class Source : public IClientInterfaceEndpoint {
- public:
- virtual ~Source() = default;
-
- void Cleanup() override;
- void SetPcmParameters(const PcmParameters& params) override;
- void SetRemoteDelay(uint16_t delay_report_ms) override;
- void StartSession() override;
- void StopSession() override;
-
- // Source the given stream of bytes to be sinked into the upper layers
- size_t Write(const uint8_t* p_buf, uint32_t len);
- };
-
- // Get LE Audio sink client interface if it's not previously acquired and not
- // yet released.
- Sink* GetSink(StreamCallbacks stream_cb,
- bluetooth::common::MessageLoopThread* message_loop);
- // This should be called before trying to get sink interface
- bool IsSinkAcquired();
- // Release sink interface if belongs to LE audio client interface
- bool ReleaseSink(Sink* sink);
-
- // Get LE Audio source client interface if it's not previously acquired and
- // not yet released.
- Source* GetSource(StreamCallbacks stream_cb,
- bluetooth::common::MessageLoopThread* message_loop);
- // This should be called before trying to get source interface
- bool IsSourceAcquired();
- // Release source interface if belongs to LE audio client interface
- bool ReleaseSource(Source* source);
-
- // Get interface, if previously not initialized - it'll initialize singleton.
- static LeAudioClientInterface* Get();
-
- private:
- static LeAudioClientInterface* interface;
- Sink* sink_ = nullptr;
- Source* source_ = nullptr;
-};
-
-} // namespace le_audio
-} // namespace audio
-} // namespace bluetooth
diff --git a/audio_hearing_aid_hw/Android.bp b/audio_hearing_aid_hw/Android.bp
index 459807752..4ed9e7660 100644
--- a/audio_hearing_aid_hw/Android.bp
+++ b/audio_hearing_aid_hw/Android.bp
@@ -1,17 +1,10 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_defaults {
name: "audio_hearing_aid_hw_defaults",
defaults: ["fluoride_defaults"],
include_dirs: [
"system/bt",
+ "system/bt/include",
+ "system/bt/audio_hearing_aid_hw/include",
],
}
@@ -31,6 +24,14 @@ cc_library {
static_libs: ["libosi"],
}
+cc_library_static {
+ name: "libaudio-hearing-aid-hw-utils",
+ defaults: ["audio_hearing_aid_hw_defaults"],
+ srcs: [
+ "src/audio_hearing_aid_hw_utils.cc",
+ ],
+}
+
// Audio A2DP library unit tests for target and host
// ========================================================
cc_test {
diff --git a/audio_hearing_aid_hw/include/audio_hearing_aid_hw.h b/audio_hearing_aid_hw/include/audio_hearing_aid_hw.h
index 8e4f2559d..56d857669 100644
--- a/audio_hearing_aid_hw/include/audio_hearing_aid_hw.h
+++ b/audio_hearing_aid_hw/include/audio_hearing_aid_hw.h
@@ -144,4 +144,7 @@ extern size_t audio_ha_hw_stream_compute_buffer_size(
btav_a2dp_codec_bits_per_sample_t codec_bits_per_sample,
btav_a2dp_codec_channel_mode_t codec_channel_mode);
+// Returns a string representation of |event|.
+extern const char* audio_ha_hw_dump_ctrl_event(tHEARING_AID_CTRL_CMD event);
+
#endif /* AUDIO_HEARING_AID_HW_H */
diff --git a/audio_hearing_aid_hw/src/audio_hearing_aid_hw.cc b/audio_hearing_aid_hw/src/audio_hearing_aid_hw.cc
index 17b1e0f2d..cac73021a 100644
--- a/audio_hearing_aid_hw/src/audio_hearing_aid_hw.cc
+++ b/audio_hearing_aid_hw/src/audio_hearing_aid_hw.cc
@@ -42,7 +42,7 @@
#include "osi/include/osi.h"
#include "osi/include/socket_utils/sockets.h"
-#include "audio_hearing_aid_hw/include/audio_hearing_aid_hw.h"
+#include "audio_hearing_aid_hw.h"
/*****************************************************************************
* Constants & Macros
@@ -57,11 +57,12 @@
// sockets
#define WRITE_POLL_MS 20
-#define FNLOG() LOG_VERBOSE("%s", __func__);
-#define DEBUG(fmt, ...) LOG_VERBOSE("%s: " fmt, __func__, ##__VA_ARGS__)
-#define INFO(fmt, ...) LOG_INFO("%s: " fmt, __func__, ##__VA_ARGS__)
-#define WARN(fmt, ...) LOG_WARN("%s: " fmt, __func__, ##__VA_ARGS__)
-#define ERROR(fmt, ...) LOG_ERROR("%s: " fmt, __func__, ##__VA_ARGS__)
+#define FNLOG() LOG_VERBOSE(LOG_TAG, "%s", __func__);
+#define DEBUG(fmt, ...) \
+ LOG_VERBOSE(LOG_TAG, "%s: " fmt, __func__, ##__VA_ARGS__)
+#define INFO(fmt, ...) LOG_INFO(LOG_TAG, "%s: " fmt, __func__, ##__VA_ARGS__)
+#define WARN(fmt, ...) LOG_WARN(LOG_TAG, "%s: " fmt, __func__, ##__VA_ARGS__)
+#define ERROR(fmt, ...) LOG_ERROR(LOG_TAG, "%s: " fmt, __func__, ##__VA_ARGS__)
#define ASSERTC(cond, msg, val) \
if (!(cond)) { \
@@ -69,28 +70,6 @@
val); \
}
-#define CASE_RETURN_STR(const) \
- case const: \
- return #const;
-
-static const char* audio_ha_hw_dump_ctrl_event(tHEARING_AID_CTRL_CMD event) {
- switch (event) {
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_NONE)
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_CHECK_READY)
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_START)
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_STOP)
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_SUSPEND)
- CASE_RETURN_STR(HEARING_AID_CTRL_GET_INPUT_AUDIO_CONFIG)
- CASE_RETURN_STR(HEARING_AID_CTRL_GET_OUTPUT_AUDIO_CONFIG)
- CASE_RETURN_STR(HEARING_AID_CTRL_SET_OUTPUT_AUDIO_CONFIG)
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_OFFLOAD_START)
- default:
- break;
- }
-
- return "UNKNOWN HEARING_AID_CTRL_CMD";
-}
-
/*****************************************************************************
* Local type definitions
*****************************************************************************/
@@ -1098,13 +1077,12 @@ size_t audio_ha_hw_stream_compute_buffer_size(
return buffer_sz;
}
-static audio_channel_mask_t out_get_channels(
- const struct audio_stream* stream) {
+static uint32_t out_get_channels(const struct audio_stream* stream) {
struct ha_stream_out* out = (struct ha_stream_out*)stream;
DEBUG("channels 0x%" PRIx32, out->common.cfg.channel_mask);
- return (audio_channel_mask_t)out->common.cfg.channel_mask;
+ return out->common.cfg.channel_mask;
}
static audio_format_t out_get_format(const struct audio_stream* stream) {
@@ -1404,11 +1382,11 @@ static size_t in_get_buffer_size(
return 320;
}
-static audio_channel_mask_t in_get_channels(const struct audio_stream* stream) {
+static uint32_t in_get_channels(const struct audio_stream* stream) {
struct ha_stream_in* in = (struct ha_stream_in*)stream;
FNLOG();
- return (audio_channel_mask_t)in->common.cfg.channel_mask;
+ return in->common.cfg.channel_mask;
}
static audio_format_t in_get_format(
diff --git a/audio_hearing_aid_hw/src/audio_hearing_aid_hw_utils.cc b/audio_hearing_aid_hw/src/audio_hearing_aid_hw_utils.cc
index cb1eee772..235463289 100644
--- a/audio_hearing_aid_hw/src/audio_hearing_aid_hw_utils.cc
+++ b/audio_hearing_aid_hw/src/audio_hearing_aid_hw_utils.cc
@@ -16,7 +16,7 @@
*
******************************************************************************/
-#include "audio_hearing_aid_hw/include/audio_hearing_aid_hw.h"
+#include "audio_hearing_aid_hw.h"
#define CASE_RETURN_STR(const) \
case const: \
diff --git a/binder/Android.bp b/binder/Android.bp
index 20837b3bd..e4beadb00 100644
--- a/binder/Android.bp
+++ b/binder/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_shared {
name: "libbluetooth-binder",
product_variables: {
@@ -27,8 +18,8 @@ cc_library_shared {
"android/bluetooth/IBluetoothCallback.aidl",
"android/bluetooth/IBluetoothProfileServiceConnection.aidl",
"android/bluetooth/IBluetoothHeadset.aidl",
+ "android/bluetooth/IBluetoothHeadsetPhone.aidl",
"android/bluetooth/IBluetoothHearingAid.aidl",
- "android/bluetooth/IBluetoothVolumeControl.aidl",
"android/bluetooth/IBluetoothHidHost.aidl",
"android/bluetooth/IBluetoothPan.aidl",
"android/bluetooth/IBluetoothManager.aidl",
@@ -46,11 +37,9 @@ cc_library_shared {
"android/bluetooth/IBluetoothGattCallback.aidl",
"android/bluetooth/IBluetoothMetadataListener.aidl",
"android/bluetooth/IBluetoothGattServerCallback.aidl",
- "android/bluetooth/IBluetoothOobDataCallback.aidl",
"android/bluetooth/le/IAdvertisingSetCallback.aidl",
"android/bluetooth/le/IPeriodicAdvertisingCallback.aidl",
"android/bluetooth/le/IScannerCallback.aidl"
- "android/bluetooth/IBluetoothConnectionCallback.aidl",
*/
],
export_include_dirs: ["./"],
@@ -103,10 +92,9 @@ filegroup {
"android/bluetooth/IBluetoothCallback.aidl",
"android/bluetooth/IBluetoothProfileServiceConnection.aidl",
"android/bluetooth/IBluetoothHeadset.aidl",
+ "android/bluetooth/IBluetoothHeadsetPhone.aidl",
"android/bluetooth/IBluetoothHearingAid.aidl",
- "android/bluetooth/IBluetoothVolumeControl.aidl",
"android/bluetooth/IBluetoothHidHost.aidl",
- "android/bluetooth/IBluetoothLeAudio.aidl",
"android/bluetooth/IBluetoothPan.aidl",
"android/bluetooth/IBluetoothManager.aidl",
"android/bluetooth/IBluetoothManagerCallback.aidl",
@@ -124,10 +112,8 @@ filegroup {
"android/bluetooth/IBluetoothGattCallback.aidl",
"android/bluetooth/IBluetoothMetadataListener.aidl",
"android/bluetooth/IBluetoothGattServerCallback.aidl",
- "android/bluetooth/IBluetoothOobDataCallback.aidl",
"android/bluetooth/le/IAdvertisingSetCallback.aidl",
"android/bluetooth/le/IPeriodicAdvertisingCallback.aidl",
"android/bluetooth/le/IScannerCallback.aidl",
- "android/bluetooth/IBluetoothConnectionCallback.aidl",
],
}
diff --git a/binder/android/bluetooth/BufferConstraints.aidl b/binder/android/bluetooth/BufferConstraints.aidl
deleted file mode 100644
index 751f5acc9..000000000
--- a/binder/android/bluetooth/BufferConstraints.aidl
+++ /dev/null
@@ -1,3 +0,0 @@
-package android.bluetooth;
-
-parcelable BufferConstraints;
diff --git a/binder/android/bluetooth/IBluetooth.aidl b/binder/android/bluetooth/IBluetooth.aidl
index 88361eb33..0e554b7bb 100644
--- a/binder/android/bluetooth/IBluetooth.aidl
+++ b/binder/android/bluetooth/IBluetooth.aidl
@@ -17,16 +17,13 @@
package android.bluetooth;
import android.bluetooth.IBluetoothCallback;
-import android.bluetooth.IBluetoothConnectionCallback;
import android.bluetooth.IBluetoothMetadataListener;
-import android.bluetooth.IBluetoothOobDataCallback;
import android.bluetooth.IBluetoothSocketManager;
import android.bluetooth.IBluetoothStateChangeCallback;
import android.bluetooth.BluetoothActivityEnergyInfo;
import android.bluetooth.BluetoothClass;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.OobData;
-import android.content.AttributionSource;
import android.os.ParcelUuid;
import android.os.ParcelFileDescriptor;
import android.os.ResultReceiver;
@@ -38,178 +35,98 @@ import android.os.ResultReceiver;
*/
interface IBluetooth
{
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
int getState();
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean enable(boolean quietMode, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disable(in AttributionSource attributionSource);
+ boolean enable(boolean quietMode);
+ boolean disable();
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.LOCAL_MAC_ADDRESS})")
String getAddress();
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.LOCAL_MAC_ADDRESS})")
- String getAddressWithAttribution(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- ParcelUuid[] getUuids(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean setName(in String name, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- String getName(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_ADVERTISE)")
- int getNameLengthForAdvertise(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- BluetoothClass getBluetoothClass(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setBluetoothClass(in BluetoothClass bluetoothClass, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getIoCapability(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setIoCapability(int capability, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getLeIoCapability(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setLeIoCapability(int capability, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- int getScanMode(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- boolean setScanMode(int mode, int duration, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- int getDiscoverableTimeout(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- boolean setDiscoverableTimeout(int timeout, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- boolean startDiscovery(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- boolean cancelDiscovery(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- boolean isDiscovering(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- long getDiscoveryEndMillis(in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
+ ParcelUuid[] getUuids();
+ boolean setName(in String name);
+ String getName();
+ BluetoothClass getBluetoothClass();
+ boolean setBluetoothClass(in BluetoothClass bluetoothClass);
+
+ int getIoCapability();
+ boolean setIoCapability(int capability);
+ int getLeIoCapability();
+ boolean setLeIoCapability(int capability);
+
+ int getScanMode();
+ boolean setScanMode(int mode, int duration);
+
+ int getDiscoverableTimeout();
+ boolean setDiscoverableTimeout(int timeout);
+
+ boolean startDiscovery(String callingPackage, String callingFeatureId);
+ boolean cancelDiscovery();
+ boolean isDiscovering();
+ long getDiscoveryEndMillis();
+
int getAdapterConnectionState();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
int getProfileConnectionState(int profile);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- BluetoothDevice[] getBondedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean createBond(in BluetoothDevice device, in int transport, in OobData p192Data, in OobData p256Data, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean cancelBondProcess(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean removeBond(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getBondState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean isBondingInitiatedLocally(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
+ BluetoothDevice[] getBondedDevices();
+ boolean createBond(in BluetoothDevice device, in int transport, in OobData oobData);
+ boolean cancelBondProcess(in BluetoothDevice device);
+ boolean removeBond(in BluetoothDevice device);
+ int getBondState(in BluetoothDevice device);
+ boolean isBondingInitiatedLocally(in BluetoothDevice device);
long getSupportedProfiles();
- @UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
int getConnectionState(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionStateWithAttribution(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- String getRemoteName(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getRemoteType(in BluetoothDevice device, in AttributionSource attributionSource);
+
+ String getRemoteName(in BluetoothDevice device);
+ int getRemoteType(in BluetoothDevice device);
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
String getRemoteAlias(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- String getRemoteAliasWithAttribution(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int setRemoteAlias(in BluetoothDevice device, in String name, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getRemoteClass(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- ParcelUuid[] getRemoteUuids(in BluetoothDevice device, in AttributionSource attributionSource);
+ boolean setRemoteAlias(in BluetoothDevice device, in String name);
+ int getRemoteClass(in BluetoothDevice device);
+ ParcelUuid[] getRemoteUuids(in BluetoothDevice device);
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
boolean fetchRemoteUuids(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean fetchRemoteUuidsWithAttribution(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean sdpSearch(in BluetoothDevice device, in ParcelUuid uuid, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getBatteryLevel(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getMaxConnectedAudioDevices(in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean setPin(in BluetoothDevice device, boolean accept, int len, in byte[] pinCode, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean setPasskey(in BluetoothDevice device, boolean accept, int len, in byte[] passkey, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setPairingConfirmation(in BluetoothDevice device, boolean accept, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getPhonebookAccessPermission(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setSilenceMode(in BluetoothDevice device, boolean silence, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean getSilenceMode(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setPhonebookAccessPermission(in BluetoothDevice device, int value, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getMessageAccessPermission(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setMessageAccessPermission(in BluetoothDevice device, int value, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getSimAccessPermission(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setSimAccessPermission(in BluetoothDevice device, int value, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- void registerCallback(in IBluetoothCallback callback, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- void unregisterCallback(in IBluetoothCallback callback, in AttributionSource attributionSource);
+ boolean sdpSearch(in BluetoothDevice device, in ParcelUuid uuid);
+ int getBatteryLevel(in BluetoothDevice device);
+ int getMaxConnectedAudioDevices();
+
+ boolean setPin(in BluetoothDevice device, boolean accept, int len, in byte[] pinCode);
+ boolean setPasskey(in BluetoothDevice device, boolean accept, int len, in byte[]
+ passkey);
+ boolean setPairingConfirmation(in BluetoothDevice device, boolean accept);
+
+ int getPhonebookAccessPermission(in BluetoothDevice device);
+ boolean setSilenceMode(in BluetoothDevice device, boolean silence);
+ boolean getSilenceMode(in BluetoothDevice device);
+ boolean setPhonebookAccessPermission(in BluetoothDevice device, int value);
+ int getMessageAccessPermission(in BluetoothDevice device);
+ boolean setMessageAccessPermission(in BluetoothDevice device, int value);
+ int getSimAccessPermission(in BluetoothDevice device);
+ boolean setSimAccessPermission(in BluetoothDevice device, int value);
+
+ void registerCallback(in IBluetoothCallback callback);
+ void unregisterCallback(in IBluetoothCallback callback);
// For Socket
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
IBluetoothSocketManager getSocketManager();
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean factoryReset(in AttributionSource attributionSource);
+ boolean factoryReset();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
boolean isMultiAdvertisementSupported();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
boolean isOffloadedFilteringSupported();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
boolean isOffloadedScanBatchingSupported();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
boolean isActivityAndEnergyReportingSupported();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
boolean isLe2MPhySupported();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
boolean isLeCodedPhySupported();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
boolean isLeExtendedAdvertisingSupported();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
boolean isLePeriodicAdvertisingSupported();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
int getLeMaximumAdvertisingDataLength();
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- BluetoothActivityEnergyInfo reportActivityInfo(in AttributionSource attributionSource);
+ BluetoothActivityEnergyInfo reportActivityInfo();
// For Metadata
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean registerMetadataListener(in IBluetoothMetadataListener listener, in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean unregisterMetadataListener(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setMetadata(in BluetoothDevice device, in int key, in byte[] value, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- byte[] getMetadata(in BluetoothDevice device, in int key, in AttributionSource attributionSource);
+ boolean registerMetadataListener(in IBluetoothMetadataListener listener, in BluetoothDevice device);
+ boolean unregisterMetadataListener(in BluetoothDevice device);
+ boolean setMetadata(in BluetoothDevice device, in int key, in byte[] value);
+ byte[] getMetadata(in BluetoothDevice device, in int key);
+
/**
* Requests the controller activity info asynchronously.
@@ -218,33 +135,17 @@ interface IBluetooth
* key {@link android.os.BatteryStats#RESULT_RECEIVER_CONTROLLER_KEY}.
* The result code is ignored.
*/
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- oneway void requestActivityInfo(in ResultReceiver result, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- void onLeServiceUp(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- void onBrEdrDown(in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED,android.Manifest.permission.MODIFY_PHONE_STATE})")
- boolean connectAllEnabledProfiles(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean disconnectAllEnabledProfiles(in BluetoothDevice device, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED,android.Manifest.permission.MODIFY_PHONE_STATE})")
- boolean setActiveDevice(in BluetoothDevice device, in int profiles, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getMostRecentlyConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED,android.Manifest.permission.MODIFY_PHONE_STATE})")
- boolean removeActiveDevice(in int profiles, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean registerBluetoothConnectionCallback(in IBluetoothConnectionCallback callback, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean unregisterBluetoothConnectionCallback(in IBluetoothConnectionCallback callback, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean canBondWithoutDialog(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- void generateLocalOobData(in int transport, IBluetoothOobDataCallback callback, in AttributionSource attributionSource);
+ oneway void requestActivityInfo(in ResultReceiver result);
+
+ void onLeServiceUp();
+ void onBrEdrDown();
+
+ boolean connectAllEnabledProfiles(in BluetoothDevice device);
+ boolean disconnectAllEnabledProfiles(in BluetoothDevice device);
+
+ boolean setActiveDevice(in BluetoothDevice device, in int profiles);
+
+ List<BluetoothDevice> getMostRecentlyConnectedDevices();
+
+ boolean removeActiveDevice(in int profiles);
}
diff --git a/binder/android/bluetooth/IBluetoothA2dp.aidl b/binder/android/bluetooth/IBluetoothA2dp.aidl
index 94379af56..39157e5a2 100644
--- a/binder/android/bluetooth/IBluetoothA2dp.aidl
+++ b/binder/android/bluetooth/IBluetoothA2dp.aidl
@@ -19,8 +19,6 @@ package android.bluetooth;
import android.bluetooth.BluetoothCodecConfig;
import android.bluetooth.BluetoothCodecStatus;
import android.bluetooth.BluetoothDevice;
-import android.bluetooth.BufferConstraints;
-import android.content.AttributionSource;
/**
* APIs for Bluetooth A2DP service
@@ -30,64 +28,29 @@ import android.content.AttributionSource;
interface IBluetoothA2dp {
// Public API
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
boolean connect(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean connectWithAttribution(in BluetoothDevice device, in AttributionSource attributionSource);
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
boolean disconnect(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnectWithAttribution(in BluetoothDevice device, in AttributionSource attributionSource);
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
List<BluetoothDevice> getConnectedDevices();
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevicesWithAttribution(in AttributionSource attributionSource);
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStatesWithAttribution(in int[] states, in AttributionSource attributionSource);
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
int getConnectionState(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionStateWithAttribution(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean setActiveDevice(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- BluetoothDevice getActiveDevice(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
+ boolean setActiveDevice(in BluetoothDevice device);
+ BluetoothDevice getActiveDevice();
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
+ int getConnectionPolicy(in BluetoothDevice device);
boolean isAvrcpAbsoluteVolumeSupported();
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- oneway void setAvrcpAbsoluteVolume(int volume, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean isA2dpPlaying(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- BluetoothCodecStatus getCodecStatus(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- oneway void setCodecConfigPreference(in BluetoothDevice device, in BluetoothCodecConfig codecConfig, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- oneway void enableOptionalCodecs(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- oneway void disableOptionalCodecs(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int supportsOptionalCodecs(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getOptionalCodecsEnabled(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- oneway void setOptionalCodecsEnabled(in BluetoothDevice device, int value, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getDynamicBufferSupport(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- BufferConstraints getBufferConstraints(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setBufferLengthMillis(int codec, int size, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getPriority(in BluetoothDevice device, in AttributionSource attributionSource);
+ oneway void setAvrcpAbsoluteVolume(int volume);
+ boolean isA2dpPlaying(in BluetoothDevice device);
+ BluetoothCodecStatus getCodecStatus(in BluetoothDevice device);
+ oneway void setCodecConfigPreference(in BluetoothDevice device,
+ in BluetoothCodecConfig codecConfig);
+ oneway void enableOptionalCodecs(in BluetoothDevice device);
+ oneway void disableOptionalCodecs(in BluetoothDevice device);
+ int supportsOptionalCodecs(in BluetoothDevice device);
+ int getOptionalCodecsEnabled(in BluetoothDevice device);
+ oneway void setOptionalCodecsEnabled(in BluetoothDevice device, int value);
+ int getPriority(in BluetoothDevice device);
}
diff --git a/binder/android/bluetooth/IBluetoothA2dpSink.aidl b/binder/android/bluetooth/IBluetoothA2dpSink.aidl
index 53c12167b..946b8f418 100644
--- a/binder/android/bluetooth/IBluetoothA2dpSink.aidl
+++ b/binder/android/bluetooth/IBluetoothA2dpSink.aidl
@@ -18,7 +18,6 @@ package android.bluetooth;
import android.bluetooth.BluetoothAudioConfig;
import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
/**
* APIs for Bluetooth A2DP sink service
@@ -26,22 +25,13 @@ import android.content.AttributionSource;
* @hide
*/
interface IBluetoothA2dpSink {
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean connect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- BluetoothAudioConfig getAudioConfig(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean isA2dpPlaying(in BluetoothDevice device, in AttributionSource attributionSource);
+ boolean connect(in BluetoothDevice device);
+ boolean disconnect(in BluetoothDevice device);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ BluetoothAudioConfig getAudioConfig(in BluetoothDevice device);
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
+ int getConnectionPolicy(in BluetoothDevice device);
+ boolean isA2dpPlaying(in BluetoothDevice device);
}
diff --git a/binder/android/bluetooth/IBluetoothAvrcpController.aidl b/binder/android/bluetooth/IBluetoothAvrcpController.aidl
index 058ffcbb5..fc5ff2d0c 100644
--- a/binder/android/bluetooth/IBluetoothAvrcpController.aidl
+++ b/binder/android/bluetooth/IBluetoothAvrcpController.aidl
@@ -18,7 +18,6 @@ package android.bluetooth;
import android.bluetooth.BluetoothAvrcpPlayerSettings;
import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
import android.media.MediaMetadata;
import android.media.session.PlaybackState;
@@ -28,16 +27,10 @@ import android.media.session.PlaybackState;
* @hide
*/
interface IBluetoothAvrcpController {
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- BluetoothAvrcpPlayerSettings getPlayerSettings(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean setPlayerApplicationSetting(in BluetoothAvrcpPlayerSettings plAppSetting, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void sendGroupNavigationCmd(in BluetoothDevice device, int keyCode, int keyState, in AttributionSource attributionSource);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ BluetoothAvrcpPlayerSettings getPlayerSettings(in BluetoothDevice device);
+ boolean setPlayerApplicationSetting(in BluetoothAvrcpPlayerSettings plAppSetting);
+ void sendGroupNavigationCmd(in BluetoothDevice device, int keyCode, int keyState);
}
diff --git a/binder/android/bluetooth/IBluetoothAvrcpTarget.aidl b/binder/android/bluetooth/IBluetoothAvrcpTarget.aidl
index 64fbb7c51..23f36083a 100644
--- a/binder/android/bluetooth/IBluetoothAvrcpTarget.aidl
+++ b/binder/android/bluetooth/IBluetoothAvrcpTarget.aidl
@@ -25,6 +25,5 @@ interface IBluetoothAvrcpTarget {
/**
* @hide
*/
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
void sendVolumeChanged(in int volume);
}
diff --git a/binder/android/bluetooth/IBluetoothConnectionCallback.aidl b/binder/android/bluetooth/IBluetoothConnectionCallback.aidl
deleted file mode 100644
index 56de49c51..000000000
--- a/binder/android/bluetooth/IBluetoothConnectionCallback.aidl
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-package android.bluetooth;
-
-import android.bluetooth.BluetoothDevice;
-
-/**
- * Callback definitions for identifying when an ACL connection or disconnection happens
- * @hide
- */
-oneway interface IBluetoothConnectionCallback {
- void onDeviceConnected(in BluetoothDevice device);
- void onDeviceDisconnected(in BluetoothDevice device, in int hciReason);
-}
diff --git a/binder/android/bluetooth/IBluetoothGatt.aidl b/binder/android/bluetooth/IBluetoothGatt.aidl
index 7e18757ad..78d02610f 100644
--- a/binder/android/bluetooth/IBluetoothGatt.aidl
+++ b/binder/android/bluetooth/IBluetoothGatt.aidl
@@ -27,7 +27,6 @@ import android.bluetooth.le.ScanFilter;
import android.bluetooth.le.ScanResult;
import android.bluetooth.le.ScanSettings;
import android.bluetooth.le.ResultStorageDescriptor;
-import android.content.AttributionSource;
import android.os.ParcelUuid;
import android.os.WorkSource;
@@ -42,135 +41,80 @@ import android.bluetooth.le.IScannerCallback;
* @hide
*/
interface IBluetoothGatt {
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- void registerScanner(in IScannerCallback callback, in WorkSource workSource, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- void unregisterScanner(in int scannerId, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
+ void registerScanner(in IScannerCallback callback, in WorkSource workSource);
+ void unregisterScanner(in int scannerId);
void startScan(in int scannerId, in ScanSettings settings, in List<ScanFilter> filters,
- in List scanStorages, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
+ in List scanStorages, in String callingPackage, String callingFeatureId);
void startScanForIntent(in PendingIntent intent, in ScanSettings settings, in List<ScanFilter> filters,
- in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- void stopScanForIntent(in PendingIntent intent, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- void stopScan(in int scannerId, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- void flushPendingBatchResults(in int scannerId, in AttributionSource attributionSource);
+ in String callingPackage, String callingFeatureId);
+ void stopScanForIntent(in PendingIntent intent, in String callingPackage);
+ void stopScan(in int scannerId);
+ void flushPendingBatchResults(in int scannerId);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_ADVERTISE)")
void startAdvertisingSet(in AdvertisingSetParameters parameters, in AdvertiseData advertiseData,
in AdvertiseData scanResponse, in PeriodicAdvertisingParameters periodicParameters,
in AdvertiseData periodicData, in int duration, in int maxExtAdvEvents,
- in IAdvertisingSetCallback callback, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_ADVERTISE)")
- void stopAdvertisingSet(in IAdvertisingSetCallback callback, in AttributionSource attributionSource);
+ in IAdvertisingSetCallback callback);
+ void stopAdvertisingSet(in IAdvertisingSetCallback callback);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_ADVERTISE,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- void getOwnAddress(in int advertiserId, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_ADVERTISE)")
- void enableAdvertisingSet(in int advertiserId, in boolean enable, in int duration, in int maxExtAdvEvents, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_ADVERTISE)")
- void setAdvertisingData(in int advertiserId, in AdvertiseData data, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_ADVERTISE)")
- void setScanResponseData(in int advertiserId, in AdvertiseData data, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_ADVERTISE)")
- void setAdvertisingParameters(in int advertiserId, in AdvertisingSetParameters parameters, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_ADVERTISE)")
- void setPeriodicAdvertisingParameters(in int advertiserId, in PeriodicAdvertisingParameters parameters, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_ADVERTISE)")
- void setPeriodicAdvertisingData(in int advertiserId, in AdvertiseData data, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_ADVERTISE)")
- void setPeriodicAdvertisingEnable(in int advertiserId, in boolean enable, in AttributionSource attributionSource);
+ void getOwnAddress(in int advertiserId);
+ void enableAdvertisingSet(in int advertiserId, in boolean enable, in int duration, in int maxExtAdvEvents);
+ void setAdvertisingData(in int advertiserId, in AdvertiseData data);
+ void setScanResponseData(in int advertiserId, in AdvertiseData data);
+ void setAdvertisingParameters(in int advertiserId, in AdvertisingSetParameters parameters);
+ void setPeriodicAdvertisingParameters(in int advertiserId, in PeriodicAdvertisingParameters parameters);
+ void setPeriodicAdvertisingData(in int advertiserId, in AdvertiseData data);
+ void setPeriodicAdvertisingEnable(in int advertiserId, in boolean enable);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- void registerSync(in ScanResult scanResult, in int skip, in int timeout, in IPeriodicAdvertisingCallback callback, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_SCAN)")
- void unregisterSync(in IPeriodicAdvertisingCallback callback, in AttributionSource attributionSource);
+ void registerSync(in ScanResult scanResult, in int skip, in int timeout, in IPeriodicAdvertisingCallback callback);
+ void unregisterSync(in IPeriodicAdvertisingCallback callback);
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void registerClient(in ParcelUuid appId, in IBluetoothGattCallback callback, boolean eatt_support, in AttributionSource attributionSource);
+ void registerClient(in ParcelUuid appId, in IBluetoothGattCallback callback);
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void unregisterClient(in int clientIf, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void clientConnect(in int clientIf, in String address, in boolean isDirect, in int transport, in boolean opportunistic, in int phy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void clientDisconnect(in int clientIf, in String address, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void clientSetPreferredPhy(in int clientIf, in String address, in int txPhy, in int rxPhy, in int phyOptions, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void clientReadPhy(in int clientIf, in String addres, in AttributionSource attributionSources);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void refreshDevice(in int clientIf, in String address, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void discoverServices(in int clientIf, in String address, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void discoverServiceByUuid(in int clientIf, in String address, in ParcelUuid uuid, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void readCharacteristic(in int clientIf, in String address, in int handle, in int authReq, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
+ void unregisterClient(in int clientIf);
+ void clientConnect(in int clientIf, in String address, in boolean isDirect, in int transport, in boolean opportunistic, in int phy);
+ void clientDisconnect(in int clientIf, in String address);
+ void clientSetPreferredPhy(in int clientIf, in String address, in int txPhy, in int rxPhy, in int phyOptions);
+ void clientReadPhy(in int clientIf, in String address);
+ void refreshDevice(in int clientIf, in String address);
+ void discoverServices(in int clientIf, in String address);
+ void discoverServiceByUuid(in int clientIf, in String address, in ParcelUuid uuid);
+ void readCharacteristic(in int clientIf, in String address, in int handle, in int authReq);
void readUsingCharacteristicUuid(in int clientIf, in String address, in ParcelUuid uuid,
- in int startHandle, in int endHandle, in int authReq, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
+ in int startHandle, in int endHandle, in int authReq);
void writeCharacteristic(in int clientIf, in String address, in int handle,
- in int writeType, in int authReq, in byte[] value, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void readDescriptor(in int clientIf, in String address, in int handle, in int authReq, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
+ in int writeType, in int authReq, in byte[] value);
+ void readDescriptor(in int clientIf, in String address, in int handle, in int authReq);
void writeDescriptor(in int clientIf, in String address, in int handle,
- in int authReq, in byte[] value, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void registerForNotification(in int clientIf, in String address, in int handle, in boolean enable, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void beginReliableWrite(in int clientIf, in String address, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void endReliableWrite(in int clientIf, in String address, in boolean execute, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void readRemoteRssi(in int clientIf, in String address, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void configureMTU(in int clientIf, in String address, in int mtu, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void connectionParameterUpdate(in int clientIf, in String address, in int connectionPriority, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
+ in int authReq, in byte[] value);
+ void registerForNotification(in int clientIf, in String address, in int handle, in boolean enable);
+ void beginReliableWrite(in int clientIf, in String address);
+ void endReliableWrite(in int clientIf, in String address, in boolean execute);
+ void readRemoteRssi(in int clientIf, in String address);
+ void configureMTU(in int clientIf, in String address, in int mtu);
+ void connectionParameterUpdate(in int clientIf, in String address, in int connectionPriority);
void leConnectionUpdate(int clientIf, String address, int minInterval,
- int maxInterval, int peripheralLatency, int supervisionTimeout,
- int minConnectionEventLen, int maxConnectionEventLen, in AttributionSource attributionSource);
+ int maxInterval, int slaveLatency, int supervisionTimeout,
+ int minConnectionEventLen, int maxConnectionEventLen);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void registerServer(in ParcelUuid appId, in IBluetoothGattServerCallback callback, boolean eatt_support, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void unregisterServer(in int serverIf, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void serverConnect(in int serverIf, in String address, in boolean isDirect, in int transport, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void serverDisconnect(in int serverIf, in String address, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void serverSetPreferredPhy(in int clientIf, in String address, in int txPhy, in int rxPhy, in int phyOptions, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void serverReadPhy(in int clientIf, in String address, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void addService(in int serverIf, in BluetoothGattService service, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void removeService(in int serverIf, in int handle, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void clearServices(in int serverIf, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
+ void registerServer(in ParcelUuid appId, in IBluetoothGattServerCallback callback);
+ void unregisterServer(in int serverIf);
+ void serverConnect(in int serverIf, in String address, in boolean isDirect, in int transport);
+ void serverDisconnect(in int serverIf, in String address);
+ void serverSetPreferredPhy(in int clientIf, in String address, in int txPhy, in int rxPhy, in int phyOptions);
+ void serverReadPhy(in int clientIf, in String address);
+ void addService(in int serverIf, in BluetoothGattService service);
+ void removeService(in int serverIf, in int handle);
+ void clearServices(in int serverIf);
void sendResponse(in int serverIf, in String address, in int requestId,
- in int status, in int offset, in byte[] value, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
+ in int status, in int offset, in byte[] value);
void sendNotification(in int serverIf, in String address, in int handle,
- in boolean confirm, in byte[] value, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void disconnectAll(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void unregAll(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int numHwTrackFiltersAvailable(in AttributionSource attributionSource);
+ in boolean confirm, in byte[] value);
+ void disconnectAll();
+ void unregAll();
+ int numHwTrackFiltersAvailable();
}
diff --git a/binder/android/bluetooth/IBluetoothGattCallback.aidl b/binder/android/bluetooth/IBluetoothGattCallback.aidl
index 3f80043d2..123a85184 100644
--- a/binder/android/bluetooth/IBluetoothGattCallback.aidl
+++ b/binder/android/bluetooth/IBluetoothGattCallback.aidl
@@ -39,5 +39,4 @@ oneway interface IBluetoothGattCallback {
void onConfigureMTU(in String address, in int mtu, in int status);
void onConnectionUpdated(in String address, in int interval, in int latency,
in int timeout, in int status);
- void onServiceChanged(in String address);
}
diff --git a/binder/android/bluetooth/IBluetoothHeadset.aidl b/binder/android/bluetooth/IBluetoothHeadset.aidl
index e94ce5ab8..0edac1494 100644
--- a/binder/android/bluetooth/IBluetoothHeadset.aidl
+++ b/binder/android/bluetooth/IBluetoothHeadset.aidl
@@ -17,7 +17,6 @@
package android.bluetooth;
import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
/**
* API for Bluetooth Headset service
@@ -31,76 +30,39 @@ import android.content.AttributionSource;
interface IBluetoothHeadset {
// Public API
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
List<BluetoothDevice> getConnectedDevices();
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevicesWithAttribution(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
int getConnectionState(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionStateWithAttribution(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.MODIFY_PHONE_STATE})")
- boolean startVoiceRecognition(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean stopVoiceRecognition(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean isAudioConnected(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean sendVendorSpecificResultCode(in BluetoothDevice device, in String command, in String arg, in AttributionSource attributionSource);
+ boolean startVoiceRecognition(in BluetoothDevice device);
+ boolean stopVoiceRecognition(in BluetoothDevice device);
+ boolean isAudioConnected(in BluetoothDevice device);
+ boolean sendVendorSpecificResultCode(in BluetoothDevice device,
+ in String command,
+ in String arg);
// Hidden API
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.MODIFY_PHONE_STATE})")
boolean connect(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.MODIFY_PHONE_STATE})")
- boolean connectWithAttribution(in BluetoothDevice device, in AttributionSource attributionSource);
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
boolean disconnect(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnectWithAttribution(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED,android.Manifest.permission.MODIFY_PHONE_STATE})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getAudioState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean isAudioOn(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean connectAudio(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnectAudio(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void setAudioRouteAllowed(boolean allowed, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean getAudioRouteAllowed(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void setForceScoAudio(boolean forced, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.MODIFY_PHONE_STATE})")
- boolean startScoUsingVirtualVoiceCall(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.MODIFY_PHONE_STATE})")
- boolean stopScoUsingVirtualVoiceCall(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.MODIFY_PHONE_STATE})")
- oneway void phoneStateChanged(int numActive, int numHeld, int callState, String number, int type, String name, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.MODIFY_PHONE_STATE})")
- void clccResponse(int index, int direction, int status, int mode, boolean mpty, String number, int type, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.MODIFY_PHONE_STATE})")
- boolean setActiveDevice(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- BluetoothDevice getActiveDevice(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean isInbandRingingEnabled(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.MODIFY_PHONE_STATE})")
- boolean setPriority(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getPriority(in BluetoothDevice device, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean isNoiseReductionSupported(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean isVoiceRecognitionSupported(in BluetoothDevice device, in AttributionSource attributionSource);
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
+ int getConnectionPolicy(in BluetoothDevice device);
+ int getAudioState(in BluetoothDevice device);
+ boolean isAudioOn();
+ boolean connectAudio();
+ boolean disconnectAudio();
+ void setAudioRouteAllowed(boolean allowed);
+ boolean getAudioRouteAllowed();
+ void setForceScoAudio(boolean forced);
+ boolean startScoUsingVirtualVoiceCall();
+ boolean stopScoUsingVirtualVoiceCall();
+ oneway void phoneStateChanged(int numActive, int numHeld, int callState, String number, int type, String name);
+ void clccResponse(int index, int direction, int status, int mode, boolean mpty,
+ String number, int type);
+ boolean setActiveDevice(in BluetoothDevice device);
+ BluetoothDevice getActiveDevice();
+ boolean isInbandRingingEnabled();
+ boolean setPriority(in BluetoothDevice device, int connectionPolicy);
+ int getPriority(in BluetoothDevice device);
}
diff --git a/binder/android/bluetooth/IBluetoothHeadsetClient.aidl b/binder/android/bluetooth/IBluetoothHeadsetClient.aidl
index b22359075..f767b27b9 100644
--- a/binder/android/bluetooth/IBluetoothHeadsetClient.aidl
+++ b/binder/android/bluetooth/IBluetoothHeadsetClient.aidl
@@ -18,7 +18,6 @@ package android.bluetooth;
import android.bluetooth.BluetoothDevice;
import android.bluetooth.BluetoothHeadsetClientCall;
-import android.content.AttributionSource;
import android.os.Bundle;
/**
@@ -27,67 +26,40 @@ import android.os.Bundle;
* {@hide}
*/
interface IBluetoothHeadsetClient {
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean connect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
+ boolean connect(in BluetoothDevice device);
+ boolean disconnect(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
+ int getConnectionPolicy(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean startVoiceRecognition(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean stopVoiceRecognition(in BluetoothDevice device, in AttributionSource attributionSource);
+ boolean startVoiceRecognition(in BluetoothDevice device);
+ boolean stopVoiceRecognition(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothHeadsetClientCall> getCurrentCalls(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- Bundle getCurrentAgEvents(in BluetoothDevice device, in AttributionSource attributionSource);
+ List<BluetoothHeadsetClientCall> getCurrentCalls(in BluetoothDevice device);
+ Bundle getCurrentAgEvents(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean acceptCall(in BluetoothDevice device, int flag, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean holdCall(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean rejectCall(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean terminateCall(in BluetoothDevice device, in BluetoothHeadsetClientCall call, in AttributionSource attributionSource);
+ boolean acceptCall(in BluetoothDevice device, int flag);
+ boolean holdCall(in BluetoothDevice device);
+ boolean rejectCall(in BluetoothDevice device);
+ boolean terminateCall(in BluetoothDevice device, in BluetoothHeadsetClientCall call);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean enterPrivateMode(in BluetoothDevice device, int index, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean explicitCallTransfer(in BluetoothDevice device, in AttributionSource attributionSource);
+ boolean enterPrivateMode(in BluetoothDevice device, int index);
+ boolean explicitCallTransfer(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- BluetoothHeadsetClientCall dial(in BluetoothDevice device, String number, in AttributionSource attributionSource);
+ BluetoothHeadsetClientCall dial(in BluetoothDevice device, String number);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean sendDTMF(in BluetoothDevice device, byte code, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean getLastVoiceTagNumber(in BluetoothDevice device, in AttributionSource attributionSource);
+ boolean sendDTMF(in BluetoothDevice device, byte code);
+ boolean getLastVoiceTagNumber(in BluetoothDevice device);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getAudioState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean connectAudio(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnectAudio(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void setAudioRouteAllowed(in BluetoothDevice device, boolean allowed, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean getAudioRouteAllowed(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean sendVendorAtCommand(in BluetoothDevice device, int vendorId, String atCommand, in AttributionSource attributionSource);
+ int getAudioState(in BluetoothDevice device);
+ boolean connectAudio(in BluetoothDevice device);
+ boolean disconnectAudio(in BluetoothDevice device);
+ void setAudioRouteAllowed(in BluetoothDevice device, boolean allowed);
+ boolean getAudioRouteAllowed(in BluetoothDevice device);
+ boolean sendVendorAtCommand(in BluetoothDevice device, int vendorId, String atCommand);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- Bundle getCurrentAgFeatures(in BluetoothDevice device, in AttributionSource attributionSource);
+ Bundle getCurrentAgFeatures(in BluetoothDevice device);
}
diff --git a/binder/android/bluetooth/IBluetoothOobDataCallback.aidl b/binder/android/bluetooth/IBluetoothHeadsetPhone.aidl
index 00975b6bb..830978065 100644
--- a/binder/android/bluetooth/IBluetoothOobDataCallback.aidl
+++ b/binder/android/bluetooth/IBluetoothHeadsetPhone.aidl
@@ -1,5 +1,5 @@
/*
- * Copyright 2021 The Android Open Source Project
+ * Copyright 2012 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,15 +16,24 @@
package android.bluetooth;
-import android.bluetooth.IBluetooth;
-import android.bluetooth.OobData;
-
/**
- * API for receiving OobData from the host stack
+ * API for Bluetooth Headset Phone Service in phone app
*
* {@hide}
*/
-oneway interface IBluetoothOobDataCallback {
- void onOobData(int transport, in OobData oobData);
- void onError(int errorCode);
+interface IBluetoothHeadsetPhone {
+ // Internal functions, not be made public
+ boolean answerCall();
+ boolean hangupCall();
+ boolean sendDtmf(int dtmf);
+ boolean processChld(int chld);
+ String getNetworkOperator();
+ String getSubscriberNumber();
+ boolean listCurrentCalls();
+ boolean queryPhoneState();
+
+ // Internal for phone app to call
+ void updateBtHandsfreeAfterRadioTechnologyChange();
+ void cdmaSwapSecondCallState();
+ void cdmaSetSecondCallState(boolean state);
}
diff --git a/binder/android/bluetooth/IBluetoothHearingAid.aidl b/binder/android/bluetooth/IBluetoothHearingAid.aidl
index 211e3eebf..b6e02c1dd 100644
--- a/binder/android/bluetooth/IBluetoothHearingAid.aidl
+++ b/binder/android/bluetooth/IBluetoothHearingAid.aidl
@@ -17,7 +17,6 @@
package android.bluetooth;
import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
/**
* APIs for Bluetooth Hearing Aid service
@@ -26,38 +25,25 @@ import android.content.AttributionSource;
*/
interface IBluetoothHearingAid {
// Public API
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean connect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean setActiveDevice(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getActiveDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void setVolume(int volume, in AttributionSource attributionSource);
+ boolean connect(in BluetoothDevice device);
+ boolean disconnect(in BluetoothDevice device);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ boolean setActiveDevice(in BluetoothDevice device);
+ List<BluetoothDevice> getActiveDevices();
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
+ int getConnectionPolicy(in BluetoothDevice device);
+ void setVolume(int volume);
const int HI_SYNC_ID_INVALID = 0;
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- long getHiSyncId(in BluetoothDevice device, in AttributionSource attributionSource);
+ long getHiSyncId(in BluetoothDevice device);
const int SIDE_LEFT = 0;
const int SIDE_RIGHT = 1;
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getDeviceSide(in BluetoothDevice device, in AttributionSource attributionSource);
+ int getDeviceSide(in BluetoothDevice device);
const int MODE_MONAURAL = 0;
const int MODE_BINAURAL = 1;
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getDeviceMode(in BluetoothDevice device, in AttributionSource attributionSource);
+ int getDeviceMode(in BluetoothDevice device);
}
diff --git a/binder/android/bluetooth/IBluetoothHidDevice.aidl b/binder/android/bluetooth/IBluetoothHidDevice.aidl
index c53d1e63f..cefb324bb 100644
--- a/binder/android/bluetooth/IBluetoothHidDevice.aidl
+++ b/binder/android/bluetooth/IBluetoothHidDevice.aidl
@@ -20,34 +20,22 @@ import android.bluetooth.BluetoothDevice;
import android.bluetooth.IBluetoothHidDeviceCallback;
import android.bluetooth.BluetoothHidDeviceAppSdpSettings;
import android.bluetooth.BluetoothHidDeviceAppQosSettings;
-import android.content.AttributionSource;
/** @hide */
interface IBluetoothHidDevice {
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean registerApp(in BluetoothHidDeviceAppSdpSettings sdp, in BluetoothHidDeviceAppQosSettings inQos, in BluetoothHidDeviceAppQosSettings outQos, in IBluetoothHidDeviceCallback callback, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean unregisterApp(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean sendReport(in BluetoothDevice device, in int id, in byte[] data, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean replyReport(in BluetoothDevice device, in byte type, in byte id, in byte[] data, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean reportError(in BluetoothDevice device, byte error, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean unplug(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean connect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- String getUserAppName(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
+ boolean registerApp(in BluetoothHidDeviceAppSdpSettings sdp,
+ in BluetoothHidDeviceAppQosSettings inQos, in BluetoothHidDeviceAppQosSettings outQos,
+ in IBluetoothHidDeviceCallback callback);
+ boolean unregisterApp();
+ boolean sendReport(in BluetoothDevice device, in int id, in byte[] data);
+ boolean replyReport(in BluetoothDevice device, in byte type, in byte id, in byte[] data);
+ boolean reportError(in BluetoothDevice device, byte error);
+ boolean unplug(in BluetoothDevice device);
+ boolean connect(in BluetoothDevice device);
+ boolean disconnect(in BluetoothDevice device);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ String getUserAppName();
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
}
diff --git a/binder/android/bluetooth/IBluetoothHidHost.aidl b/binder/android/bluetooth/IBluetoothHidHost.aidl
index 23fbd60d8..ca3e33c7a 100644
--- a/binder/android/bluetooth/IBluetoothHidHost.aidl
+++ b/binder/android/bluetooth/IBluetoothHidHost.aidl
@@ -17,7 +17,6 @@
package android.bluetooth;
import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
/**
* API for Bluetooth HID service
@@ -26,34 +25,43 @@ import android.content.AttributionSource;
*/
interface IBluetoothHidHost {
// Public API
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean connect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean getProtocolMode(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean virtualUnplug(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean setProtocolMode(in BluetoothDevice device, int protocolMode, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean getReport(in BluetoothDevice device, byte reportType, byte reportId, int bufferSize, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean setReport(in BluetoothDevice device, byte reportType, String report, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean sendData(in BluetoothDevice device, String report, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean getIdleTime(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean setIdleTime(in BluetoothDevice device, byte idleTime, in AttributionSource attributionSource);
+ boolean connect(in BluetoothDevice device);
+ boolean disconnect(in BluetoothDevice device);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
+ int getConnectionPolicy(in BluetoothDevice device);
+ /**
+ * @hide
+ */
+ boolean getProtocolMode(in BluetoothDevice device);
+ /**
+ * @hide
+ */
+ boolean virtualUnplug(in BluetoothDevice device);
+ /**
+ * @hide
+ */
+ boolean setProtocolMode(in BluetoothDevice device, int protocolMode);
+ /**
+ * @hide
+ */
+ boolean getReport(in BluetoothDevice device, byte reportType, byte reportId, int bufferSize);
+ /**
+ * @hide
+ */
+ boolean setReport(in BluetoothDevice device, byte reportType, String report);
+ /**
+ * @hide
+ */
+ boolean sendData(in BluetoothDevice device, String report);
+ /**
+ * @hide
+ */
+ boolean getIdleTime(in BluetoothDevice device);
+ /**
+ * @hide
+ */
+ boolean setIdleTime(in BluetoothDevice device, byte idleTime);
}
diff --git a/binder/android/bluetooth/IBluetoothLeAudio.aidl b/binder/android/bluetooth/IBluetoothLeAudio.aidl
deleted file mode 100644
index 34240d134..000000000
--- a/binder/android/bluetooth/IBluetoothLeAudio.aidl
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package android.bluetooth;
-
-import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
-
-/**
- * APIs for Bluetooth LE Audio service
- *
- * @hide
- */
-interface IBluetoothLeAudio {
- // Public API
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean connect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean setActiveDevice(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getActiveDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
-
- const int LE_AUDIO_GROUP_ID_INVALID = -1;
-
- /**
- * Get device group id. Devices with same group id belong to same group (i.e left and right
- * earbud)
- */
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getGroupId(in BluetoothDevice device, in AttributionSource attributionSource);
-}
diff --git a/binder/android/bluetooth/IBluetoothManager.aidl b/binder/android/bluetooth/IBluetoothManager.aidl
index 76b7a4bc9..e94fe64b0 100644
--- a/binder/android/bluetooth/IBluetoothManager.aidl
+++ b/binder/android/bluetooth/IBluetoothManager.aidl
@@ -21,7 +21,6 @@ import android.bluetooth.IBluetoothGatt;
import android.bluetooth.IBluetoothManagerCallback;
import android.bluetooth.IBluetoothProfileServiceConnection;
import android.bluetooth.IBluetoothStateChangeCallback;
-import android.content.AttributionSource;
/**
* System private API for talking with the Bluetooth service.
@@ -30,50 +29,34 @@ import android.content.AttributionSource;
*/
interface IBluetoothManager
{
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
IBluetooth registerAdapter(in IBluetoothManagerCallback callback);
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
void unregisterAdapter(in IBluetoothManagerCallback callback);
@UnsupportedAppUsage
void registerStateChangeCallback(in IBluetoothStateChangeCallback callback);
@UnsupportedAppUsage
void unregisterStateChangeCallback(in IBluetoothStateChangeCallback callback);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean enable(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean enableNoAutoConnect(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disable(in AttributionSource attributionSource, boolean persist);
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
+ boolean isEnabled();
+ boolean enable(String packageName);
+ boolean enableNoAutoConnect(String packageName);
+ boolean disable(String packageName, boolean persist);
int getState();
@UnsupportedAppUsage
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
IBluetoothGatt getBluetoothGatt();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
boolean bindBluetoothProfileService(int profile, IBluetoothProfileServiceConnection proxy);
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
void unbindBluetoothProfileService(int profile, IBluetoothProfileServiceConnection proxy);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.LOCAL_MAC_ADDRESS})")
- String getAddress(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- String getName(in AttributionSource attributionSource);
+ String getAddress();
+ String getName();
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean onFactoryReset(in AttributionSource attributionSource);
+ boolean onFactoryReset();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
boolean isBleScanAlwaysAvailable();
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean enableBle(in AttributionSource attributionSource, IBinder b);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disableBle(in AttributionSource attributionSource, IBinder b);
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
+ boolean enableBle(String packageName, IBinder b);
+ boolean disableBle(String packageName, IBinder b);
boolean isBleAppPresent();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
boolean isHearingAidProfileSupported();
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
List<String> getSystemConfigEnabledProfilesForPackage(String packageName);
}
+
diff --git a/binder/android/bluetooth/IBluetoothMap.aidl b/binder/android/bluetooth/IBluetoothMap.aidl
index 2862005ae..4f221e4a3 100644
--- a/binder/android/bluetooth/IBluetoothMap.aidl
+++ b/binder/android/bluetooth/IBluetoothMap.aidl
@@ -17,7 +17,6 @@
package android.bluetooth;
import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
/**
* System private API for Bluetooth MAP service
@@ -25,22 +24,13 @@ import android.content.AttributionSource;
* {@hide}
*/
interface IBluetoothMap {
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getState(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- BluetoothDevice getClient(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean isConnected(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
+ int getState();
+ BluetoothDevice getClient();
+ boolean disconnect(in BluetoothDevice device);
+ boolean isConnected(in BluetoothDevice device);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
+ int getConnectionPolicy(in BluetoothDevice device);
}
diff --git a/binder/android/bluetooth/IBluetoothMapClient.aidl b/binder/android/bluetooth/IBluetoothMapClient.aidl
index 38aa2c4bd..3da40d3e2 100644
--- a/binder/android/bluetooth/IBluetoothMapClient.aidl
+++ b/binder/android/bluetooth/IBluetoothMapClient.aidl
@@ -18,7 +18,6 @@ package android.bluetooth;
import android.app.PendingIntent;
import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
import android.net.Uri;
/**
@@ -27,28 +26,16 @@ import android.net.Uri;
* {@hide}
*/
interface IBluetoothMapClient {
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf = { android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED })")
- boolean connect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf = { android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED })")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean isConnected(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf = { android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED })")
- boolean setConnectionPolicy(in BluetoothDevice device,in int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf = { android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.BLUETOOTH_PRIVILEGED })")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf = { android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.SEND_SMS })")
- boolean sendMessage(in BluetoothDevice device, in Uri[] contacts, in String message, in PendingIntent sentIntent, in PendingIntent deliveryIntent, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf = { android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.READ_SMS })")
- boolean getUnreadMessages(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getSupportedFeatures(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf = { android.Manifest.permission.BLUETOOTH_CONNECT, android.Manifest.permission.READ_SMS })")
- boolean setMessageStatus(in BluetoothDevice device, in String handle, in int status, in AttributionSource attributionSource);
+ boolean connect(in BluetoothDevice device);
+ boolean disconnect(in BluetoothDevice device);
+ boolean isConnected(in BluetoothDevice device);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ boolean setConnectionPolicy(in BluetoothDevice device,in int connectionPolicy);
+ int getConnectionPolicy(in BluetoothDevice device);
+ boolean sendMessage(in BluetoothDevice device, in Uri[] contacts, in String message,
+ in PendingIntent sentIntent, in PendingIntent deliveryIntent);
+ boolean getUnreadMessages(in BluetoothDevice device);
+ int getSupportedFeatures(in BluetoothDevice device);
}
diff --git a/binder/android/bluetooth/IBluetoothMetadataListener.aidl b/binder/android/bluetooth/IBluetoothMetadataListener.aidl
index e08919fed..765b12822 100644
--- a/binder/android/bluetooth/IBluetoothMetadataListener.aidl
+++ b/binder/android/bluetooth/IBluetoothMetadataListener.aidl
@@ -24,6 +24,5 @@ import android.bluetooth.BluetoothDevice;
* @hide
*/
oneway interface IBluetoothMetadataListener {
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
void onMetadataChanged(in BluetoothDevice devices, in int key, in byte[] value);
}
diff --git a/binder/android/bluetooth/IBluetoothPan.aidl b/binder/android/bluetooth/IBluetoothPan.aidl
index 4ee664e03..292c1278a 100644
--- a/binder/android/bluetooth/IBluetoothPan.aidl
+++ b/binder/android/bluetooth/IBluetoothPan.aidl
@@ -17,7 +17,6 @@
package android.bluetooth;
import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
/**
* API for Bluetooth Pan service
@@ -26,20 +25,12 @@ import android.content.AttributionSource;
*/
interface IBluetoothPan {
// Public API
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean isTetheringOn(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED,android.Manifest.permission.TETHER_PRIVILEGED})")
- void setBluetoothTethering(boolean value, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean connect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
+ boolean isTetheringOn();
+ void setBluetoothTethering(boolean value, String pkgName);
+ boolean connect(in BluetoothDevice device);
+ boolean disconnect(in BluetoothDevice device);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
}
diff --git a/binder/android/bluetooth/IBluetoothPbap.aidl b/binder/android/bluetooth/IBluetoothPbap.aidl
index 5d4f33431..3cb6a6f4f 100644
--- a/binder/android/bluetooth/IBluetoothPbap.aidl
+++ b/binder/android/bluetooth/IBluetoothPbap.aidl
@@ -17,7 +17,6 @@
package android.bluetooth;
import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
/**
* System private API for Bluetooth pbap service
@@ -25,14 +24,9 @@ import android.content.AttributionSource;
* {@hide}
*/
interface IBluetoothPbap {
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ void disconnect(in BluetoothDevice device);
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
}
diff --git a/binder/android/bluetooth/IBluetoothPbapClient.aidl b/binder/android/bluetooth/IBluetoothPbapClient.aidl
index 1512e44a6..e4bfc4e37 100644
--- a/binder/android/bluetooth/IBluetoothPbapClient.aidl
+++ b/binder/android/bluetooth/IBluetoothPbapClient.aidl
@@ -17,7 +17,6 @@
package android.bluetooth;
import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
/**
* API for Bluetooth Phone Book Access Provile Client Side
@@ -25,18 +24,11 @@ import android.content.AttributionSource;
* {@hide}
*/
interface IBluetoothPbapClient {
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean connect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
+ boolean connect(in BluetoothDevice device);
+ boolean disconnect(in BluetoothDevice device);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
+ int getConnectionPolicy(in BluetoothDevice device);
}
diff --git a/binder/android/bluetooth/IBluetoothProfileServiceConnection.aidl b/binder/android/bluetooth/IBluetoothProfileServiceConnection.aidl
index 5a048cf7e..e5c3de98c 100644
--- a/binder/android/bluetooth/IBluetoothProfileServiceConnection.aidl
+++ b/binder/android/bluetooth/IBluetoothProfileServiceConnection.aidl
@@ -25,8 +25,6 @@ import android.os.IBinder;
* {@hide}
*/
oneway interface IBluetoothProfileServiceConnection {
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
void onServiceConnected(in ComponentName comp, in IBinder service);
- @JavaPassthrough(annotation="@android.annotation.RequiresNoPermission")
void onServiceDisconnected(in ComponentName comp);
}
diff --git a/binder/android/bluetooth/IBluetoothSap.aidl b/binder/android/bluetooth/IBluetoothSap.aidl
index c97403e14..00f1f1a79 100644
--- a/binder/android/bluetooth/IBluetoothSap.aidl
+++ b/binder/android/bluetooth/IBluetoothSap.aidl
@@ -17,7 +17,6 @@
package android.bluetooth;
import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
/**
* System private API for Bluetooth SAP service
@@ -25,24 +24,14 @@ import android.content.AttributionSource;
* {@hide}
*/
interface IBluetoothSap {
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getState(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- BluetoothDevice getClient(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean connect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean isConnected(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
+ int getState();
+ BluetoothDevice getClient();
+ boolean connect(in BluetoothDevice device);
+ boolean disconnect(in BluetoothDevice device);
+ boolean isConnected(in BluetoothDevice device);
+ List<BluetoothDevice> getConnectedDevices();
+ List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states);
+ int getConnectionState(in BluetoothDevice device);
+ boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy);
+ int getConnectionPolicy(in BluetoothDevice device);
}
diff --git a/binder/android/bluetooth/IBluetoothSocketManager.aidl b/binder/android/bluetooth/IBluetoothSocketManager.aidl
index e895b4292..119988e9c 100644
--- a/binder/android/bluetooth/IBluetoothSocketManager.aidl
+++ b/binder/android/bluetooth/IBluetoothSocketManager.aidl
@@ -27,10 +27,7 @@ import android.os.ParcelFileDescriptor;
*/
interface IBluetoothSocketManager
{
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
@nullable ParcelFileDescriptor connectSocket(in BluetoothDevice device, int type, in @nullable ParcelUuid uuid, int port, int flag);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
@nullable ParcelFileDescriptor createSocketChannel(int type, in @nullable String serviceName, in @nullable ParcelUuid uuid, int port, int flag);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
void requestMaximumTxDataLength(in BluetoothDevice device);
}
diff --git a/binder/android/bluetooth/IBluetoothVolumeControl.aidl b/binder/android/bluetooth/IBluetoothVolumeControl.aidl
deleted file mode 100644
index d390bf05e..000000000
--- a/binder/android/bluetooth/IBluetoothVolumeControl.aidl
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package android.bluetooth;
-
-import android.bluetooth.BluetoothDevice;
-import android.content.AttributionSource;
-
-/**
- * APIs for Bluetooth Volume Control service
- *
- * @hide
- */
-interface IBluetoothVolumeControl {
- /* Public API */
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean connect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- boolean disconnect(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getConnectedDevices(in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- List<BluetoothDevice> getDevicesMatchingConnectionStates(in int[] states, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- int getConnectionState(in BluetoothDevice device, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- boolean setConnectionPolicy(in BluetoothDevice device, int connectionPolicy, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(allOf={android.Manifest.permission.BLUETOOTH_CONNECT,android.Manifest.permission.BLUETOOTH_PRIVILEGED})")
- int getConnectionPolicy(in BluetoothDevice device, in AttributionSource attributionSource);
-
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void setVolume(in BluetoothDevice device, int volume, in AttributionSource attributionSource);
- @JavaPassthrough(annotation="@android.annotation.RequiresPermission(android.Manifest.permission.BLUETOOTH_CONNECT)")
- void setVolumeGroup(int group_id, int volume, in AttributionSource attributionSource);
-}
diff --git a/bta/Android.bp b/bta/Android.bp
index 8e0d9bf9a..ac6b733ac 100644..100755
--- a/bta/Android.bp
+++ b/bta/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_defaults {
name: "fluoride_bta_defaults",
defaults: ["fluoride_defaults"],
@@ -30,7 +21,6 @@ cc_defaults {
"system/bt/udrv/include",
"system/bt/vnd/include",
"system/bt/utils/include",
- "system/bt/gd/rust/shim",
],
shared_libs: [
"libcutils",
@@ -80,8 +70,6 @@ cc_library_static {
"gatt/bta_gatts_utils.cc",
"gatt/database.cc",
"gatt/database_builder.cc",
- "vc/device.cc",
- "vc/vc.cc",
"hearing_aid/hearing_aid.cc",
"hearing_aid/hearing_aid_audio_source.cc",
"hf_client/bta_hf_client_act.cc",
@@ -103,6 +91,10 @@ cc_library_static {
"jv/bta_jv_act.cc",
"jv/bta_jv_api.cc",
"jv/bta_jv_cfg.cc",
+ "mce/bta_mce_act.cc",
+ "mce/bta_mce_api.cc",
+ "mce/bta_mce_cfg.cc",
+ "mce/bta_mce_main.cc",
"pan/bta_pan_act.cc",
"pan/bta_pan_api.cc",
"pan/bta_pan_ci.cc",
@@ -119,7 +111,9 @@ cc_library_static {
"avrcp-target-service",
"lib-bt-packets",
],
- host_supported: true,
+ whole_static_libs: [
+ "libaudio-hearing-aid-hw-utils",
+ ],
}
// bta unit tests for target
@@ -127,11 +121,8 @@ cc_library_static {
cc_test {
name: "net_test_bta",
defaults: ["fluoride_bta_defaults"],
- test_suites: ["device-tests"],
srcs: [
"test/bta_hf_client_test.cc",
- "test/bta_dm_cust_uuid_test.cc",
- "test/bta_dip_test.cc",
"test/gatt/database_builder_test.cc",
"test/gatt/database_builder_sample_device_test.cc",
"test/gatt/database_test.cc",
@@ -142,7 +133,6 @@ cc_test {
"libprotobuf-cpp-lite",
],
static_libs: [
- "crypto_toolbox_for_tests",
"libbtcore",
"libbt-bta",
"libbt-audio-hal-interface",
@@ -153,64 +143,6 @@ cc_test {
],
}
-cc_test {
- name: "bt_host_test_bta",
- defaults: ["fluoride_bta_defaults"],
- test_suites: ["device-tests"],
- host_supported: true,
- include_dirs: [
- "system/bt",
- "system/bt/gd",
- ],
- generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- "BluetoothGeneratedDumpsysDataSchema_h",
- "BluetoothGeneratedPackets_h",
- ],
- srcs: [
- ":TestMockBtif",
- ":TestMockDevice",
- ":TestMockMainShim",
- ":TestMockStack",
- ":TestStubOsi",
- "dm/bta_dm_act.cc",
- "dm/bta_dm_cfg.cc",
- "dm/bta_dm_ci.cc",
- "dm/bta_dm_main.cc",
- "dm/bta_dm_pm.cc",
- "gatt/bta_gattc_act.cc",
- "gatt/bta_gattc_api.cc",
- "gatt/bta_gattc_cache.cc",
- "gatt/bta_gattc_main.cc",
- "gatt/bta_gattc_queue.cc",
- "gatt/bta_gattc_utils.cc",
- "gatt/database.cc",
- "gatt/database_builder.cc",
- "hh/bta_hh_act.cc",
- "hh/bta_hh_cfg.cc",
- "hh/bta_hh_le.cc",
- "hh/bta_hh_main.cc",
- "hh/bta_hh_utils.cc",
- "sys/bta_sys_conn.cc",
- "sys/bta_sys_main.cc",
- "test/bta_dm_test.cc",
- "test/bta_gatt_test.cc",
- ],
- shared_libs: [
- "libcrypto",
- "libflatbuffers-cpp",
- "liblog",
- "libprotobuf-cpp-lite",
- ],
- static_libs: [
- "libbluetooth-types",
- "libbt-common",
- "libbt-protos-lite",
- "libbtcore",
- "libgmock",
- ],
-}
-
// bta hf client add record tests for target
// ========================================================
cc_test {
@@ -240,46 +172,3 @@ cc_test {
],
cflags: ["-DBUILDCFG"],
}
-
-
-// bta unit tests for host
-// ========================================================
-cc_test {
- name: "bluetooth_vc_test",
- test_suites: ["device-tests"],
- defaults: [
- "fluoride_bta_defaults",
- "clang_coverage_bin",
- ],
- host_supported: true,
- include_dirs: [
- "system/bt",
- "system/bt/bta/include",
- "system/bt/bta/test/common",
- "system/bt/stack/include",
- ],
- srcs : [
- "gatt/database.cc",
- "gatt/database_builder.cc",
- "test/common/bta_gatt_api_mock.cc",
- "test/common/bta_gatt_queue_mock.cc",
- "test/common/btm_api_mock.cc",
- "vc/devices_test.cc",
- "vc/device.cc",
- "vc/vc.cc",
- "vc/vc_test.cc",
- ],
- shared_libs: [
- "libprotobuf-cpp-lite",
- "libcrypto",
- ],
- static_libs : [
- "crypto_toolbox_for_tests",
- "libgmock",
- "libbt-common",
- "libbt-protos-lite",
- ],
- sanitize: {
- cfi: false,
- },
-}
diff --git a/bta/BUILD.gn b/bta/BUILD.gn
index 64bd53c21..0bf654413 100644
--- a/bta/BUILD.gn
+++ b/bta/BUILD.gn
@@ -72,6 +72,10 @@ static_library("bta") {
"jv/bta_jv_act.cc",
"jv/bta_jv_api.cc",
"jv/bta_jv_cfg.cc",
+ "mce/bta_mce_act.cc",
+ "mce/bta_mce_api.cc",
+ "mce/bta_mce_cfg.cc",
+ "mce/bta_mce_main.cc",
"pan/bta_pan_act.cc",
"pan/bta_pan_api.cc",
"pan/bta_pan_ci.cc",
@@ -83,8 +87,6 @@ static_library("bta") {
"sys/bta_sys_conn.cc",
"sys/bta_sys_main.cc",
"sys/utl.cc",
- "vc/device.cc",
- "vc/vc.cc",
]
include_dirs = [
@@ -94,64 +96,54 @@ static_library("bta") {
"hd",
"include",
"sys",
- "//bt/",
- "//bt/linux_include",
- "//bt/bta",
- "//bt/internal_include",
- "//bt/btcore/include",
- "//bt/hci/include",
- "//bt/internal_include",
- "//bt/stack/include",
- "//bt/stack/btm",
- "//bt/udrv/include",
- "//bt/utils/include",
- "//bt/vnd/include",
- "//bt/btif/include",
- "//bt/btif/avrcp",
- "//bt/include/hardware/avrcp",
- "//bt/profile/avrcp",
- "//bt/packet/avrcp",
- "//bt/packet/base",
- ]
-
- configs += [
- "//bt:target_defaults"
+ "//",
+ "//linux_include",
+ "//bta",
+ "//internal_include",
+ "//btcore/include",
+ "//hci/include",
+ "//internal_include",
+ "//stack/include",
+ "//stack/btm",
+ "//udrv/include",
+ "//utils/include",
+ "//vnd/include",
+ "//btif/include",
+ "//btif/avrcp",
+ "//include/hardware/avrcp",
+ "//profile/avrcp",
+ "//packet/avrcp",
+ "//packet/base",
]
deps = [
- "//bt/gd/rust/shim:shim_bridge_header",
- "//bt/gd/rust/shim:init_flags_bridge_header",
- "//bt/gd/rust/shim:message_loop_thread_bridge_header",
+ "//third_party/libchrome:base"
]
}
-if (use.test) {
- executable("net_test_bta") {
- sources = [
- "gatt/database_builder.cc",
- "test/gatt/database_builder_test.cc",
- "test/gatt/database_builder_sample_device_test.cc",
- "test/gatt/database_test.cc",
- ]
-
- include_dirs = [
- "include",
- "//bt/",
- "//bt/bta",
- "//bt/btcore/include",
- "//bt/hci/include",
- "//bt/internal_include",
- "//bt/stack/btm",
- ]
+executable("net_test_bta") {
+ testonly = true
+ sources = [
+ "gatt/database_builder.cc",
+ "test/gatt/database_builder_test.cc",
+ "test/gatt/database_builder_sample_device_test.cc",
+ "test/gatt/database_test.cc",
+ ]
- deps = [
- "//bt/bta",
- "//bt/types",
- ]
+ include_dirs = [
+ "include",
+ "//",
+ "//bta",
+ "//btcore/include",
+ "//hci/include",
+ "//internal_include",
+ "//stack/btm",
+ ]
- configs += [
- "//bt:external_gmock_main",
- "//bt:target_defaults",
- ]
- }
-}
+ deps = [
+ "//bta",
+ "//types",
+ "//third_party/googletest:gmock_main",
+ "//third_party/libchrome:base",
+ ]
+} \ No newline at end of file
diff --git a/bta/ag/bta_ag_act.cc b/bta/ag/bta_ag_act.cc
index 56a9d4f5c..5a3697aa2 100644
--- a/bta/ag/bta_ag_act.cc
+++ b/bta/ag/bta_ag_act.cc
@@ -22,15 +22,18 @@
*
******************************************************************************/
-#include <cstdint>
#include <cstring>
-#include "bta/ag/bta_ag_int.h"
-#include "bta/include/bta_dm_api.h"
-#include "btif/include/btif_config.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/include/l2c_api.h"
-#include "stack/include/port_api.h"
+#include "bta_ag_api.h"
+#include "bta_ag_int.h"
+#include "bta_api.h"
+#include "bta_dm_api.h"
+#include "bta_sys.h"
+#include "btif_config.h"
+#include "l2c_api.h"
+#include "osi/include/osi.h"
+#include "port_api.h"
+#include "utl.h"
/*****************************************************************************
* Constants
@@ -99,8 +102,8 @@ static void bta_ag_cback_open(tBTA_AG_SCB* p_scb, const RawAddress& bd_addr,
void bta_ag_register(tBTA_AG_SCB* p_scb, const tBTA_AG_DATA& data) {
/* initialize control block */
p_scb->reg_services = data.api_register.services;
+ p_scb->serv_sec_mask = data.api_register.sec_mask;
p_scb->features = data.api_register.features;
- p_scb->masked_features = data.api_register.features;
p_scb->app_id = data.api_register.app_id;
/* create SDP records */
@@ -172,6 +175,7 @@ void bta_ag_start_dereg(tBTA_AG_SCB* p_scb, const tBTA_AG_DATA& data) {
******************************************************************************/
void bta_ag_start_open(tBTA_AG_SCB* p_scb, const tBTA_AG_DATA& data) {
p_scb->peer_addr = data.api_open.bd_addr;
+ p_scb->cli_sec_mask = data.api_open.sec_mask;
p_scb->open_services = p_scb->reg_services;
/* Check if RFCOMM has any incoming connection to avoid collision. */
@@ -180,7 +184,7 @@ void bta_ag_start_open(tBTA_AG_SCB* p_scb, const tBTA_AG_DATA& data) {
/* Let the incoming connection goes through. */
/* Issue collision for this scb for now. */
/* We will decide what to do when we find incoming connetion later. */
- bta_ag_collision_cback(BTA_SYS_CONN_OPEN, BTA_ID_AG, 0, p_scb->peer_addr);
+ bta_ag_collision_cback(0, BTA_ID_AG, 0, p_scb->peer_addr);
return;
}
@@ -362,7 +366,6 @@ void bta_ag_rfc_close(tBTA_AG_SCB* p_scb,
/* reinitialize stuff */
p_scb->conn_service = 0;
p_scb->peer_features = 0;
- p_scb->masked_features = p_scb->features;
p_scb->peer_codecs = BTA_AG_CODEC_CVSD;
p_scb->sco_codec = BTA_AG_CODEC_CVSD;
/* Clear these flags upon SLC teardown */
diff --git a/bta/ag/bta_ag_api.cc b/bta/ag/bta_ag_api.cc
index a4010b63d..727ad0fa1 100644
--- a/bta/ag/bta_ag_api.cc
+++ b/bta/ag/bta_ag_api.cc
@@ -24,15 +24,14 @@
*
******************************************************************************/
+#include "bta_ag_api.h"
#include <base/bind.h>
-#include <base/location.h>
-#include <cstdint>
#include <cstring>
-#include <vector>
-
-#include "bta/ag/bta_ag_int.h"
-#include "bta/include/bta_ag_api.h"
-#include "stack/include/btu.h" // do_in_main_thread
+#include "bt_common.h"
+#include "bta_ag_int.h"
+#include "bta_api.h"
+#include "bta_sys.h"
+#include "stack/include/btu.h"
/*****************************************************************************
* Constants
@@ -91,11 +90,13 @@ void BTA_AgDisable() {
* Returns void
*
******************************************************************************/
-void BTA_AgRegister(tBTA_SERVICE_MASK services, tBTA_AG_FEAT features,
+void BTA_AgRegister(tBTA_SERVICE_MASK services, tBTA_SEC sec_mask,
+ tBTA_AG_FEAT features,
const std::vector<std::string>& service_names,
uint8_t app_id) {
- do_in_main_thread(FROM_HERE, base::Bind(&bta_ag_api_register, services,
- features, service_names, app_id));
+ do_in_main_thread(
+ FROM_HERE, base::Bind(&bta_ag_api_register, services, sec_mask, features,
+ service_names, app_id));
}
/*******************************************************************************
@@ -127,9 +128,10 @@ void BTA_AgDeregister(uint16_t handle) {
* Returns void
*
******************************************************************************/
-void BTA_AgOpen(uint16_t handle, const RawAddress& bd_addr) {
+void BTA_AgOpen(uint16_t handle, const RawAddress& bd_addr, tBTA_SEC sec_mask) {
tBTA_AG_DATA data = {};
data.api_open.bd_addr = bd_addr;
+ data.api_open.sec_mask = sec_mask;
do_in_main_thread(FROM_HERE, base::Bind(&bta_ag_sm_execute_by_handle, handle,
BTA_AG_API_OPEN_EVT, data));
}
diff --git a/bta/ag/bta_ag_at.cc b/bta/ag/bta_ag_at.cc
index 613a64b94..90c46ff4a 100644
--- a/bta/ag/bta_ag_at.cc
+++ b/bta/ag/bta_ag_at.cc
@@ -21,17 +21,13 @@
* BTA AG AT command interpreter.
*
******************************************************************************/
-#define LOG_TAG "bta_ag_at"
-#include <cstdint>
+#include <cstring>
-#include "bt_target.h" // Must be first to define build configuration:
-
-#include "bta/ag/bta_ag_at.h"
-#include "bta/ag/bta_ag_int.h"
-#include "bta/include/utl.h"
-#include "osi/include/allocator.h"
-#include "osi/include/log.h"
+#include "bt_common.h"
+#include "bta_ag_at.h"
+#include "log/log.h"
+#include "utl.h"
/*****************************************************************************
* Constants
@@ -139,7 +135,6 @@ void bta_ag_process_at(tBTA_AG_AT_CB* p_cb, char* p_end) {
if (int_arg < (int16_t)p_cb->p_at_tbl[idx].min ||
int_arg > (int16_t)p_cb->p_at_tbl[idx].max) {
/* arg out of range; error */
- LOG_WARN("arg out of range");
(*p_cb->p_err_cback)((tBTA_AG_SCB*)p_cb->p_user, false, nullptr);
} else {
(*p_cb->p_cmd_cback)((tBTA_AG_SCB*)p_cb->p_user,
@@ -151,15 +146,14 @@ void bta_ag_process_at(tBTA_AG_AT_CB* p_cb, char* p_end) {
p_cb->p_at_tbl[idx].command_id, arg_type, p_arg,
p_end, int_arg);
}
- } else {
- /* else error */
- LOG_WARN("Incoming arg type 0x%x does not match cmd arg type 0x%x",
- arg_type, p_cb->p_at_tbl[idx].arg_type);
+ }
+ /* else error */
+ else {
(*p_cb->p_err_cback)((tBTA_AG_SCB*)p_cb->p_user, false, nullptr);
}
- } else {
- /* else no match call error callback */
- LOG_WARN("Unmatched command index %d", idx);
+ }
+ /* else no match call error callback */
+ else {
(*p_cb->p_err_cback)((tBTA_AG_SCB*)p_cb->p_user, true, p_cb->p_cmd_buf);
}
}
diff --git a/bta/ag/bta_ag_at.h b/bta/ag/bta_ag_at.h
index e324e197f..c5b5d885c 100644
--- a/bta/ag/bta_ag_at.h
+++ b/bta/ag/bta_ag_at.h
@@ -24,10 +24,6 @@
#ifndef BTA_AG_AT_H
#define BTA_AG_AT_H
-#include <stddef.h>
-#include <cstddef>
-#include <cstdint>
-
/*****************************************************************************
* Constants
****************************************************************************/
diff --git a/bta/ag/bta_ag_cfg.cc b/bta/ag/bta_ag_cfg.cc
index fe75b6123..abb71b421 100644
--- a/bta/ag/bta_ag_cfg.cc
+++ b/bta/ag/bta_ag_cfg.cc
@@ -23,13 +23,9 @@
*
******************************************************************************/
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/ag/bta_ag_int.h"
-#include "bta/include/bta_ag_api.h"
-#include "osi/include/allocator.h"
-#include "osi/include/compat.h"
-#include "stack/include/bt_types.h"
+#include "bt_common.h"
+#include "bta_ag_api.h"
+#include "bta_ag_int.h"
#ifndef BTA_AG_CIND_INFO
#define BTA_AG_CIND_INFO \
diff --git a/bta/ag/bta_ag_cmd.cc b/bta/ag/bta_ag_cmd.cc
index a9ae83855..87b2a8254 100644
--- a/bta/ag/bta_ag_cmd.cc
+++ b/bta/ag/bta_ag_cmd.cc
@@ -18,18 +18,23 @@
#define LOG_TAG "bta_ag_cmd"
-#include <cstdint>
+#include <cctype>
+#include <cstdio>
#include <cstring>
-#include "bta/ag/bta_ag_at.h"
-#include "bta/ag/bta_ag_int.h"
-#include "bta/include/bta_ag_api.h"
-#include "bta/include/utl.h"
-#include "device/include/interop.h"
-#include "osi/include/compat.h"
+#include "bt_common.h"
+#include "bt_target.h"
+#include "bt_types.h"
+#include "bta_ag_api.h"
+#include "bta_ag_at.h"
+#include "bta_ag_int.h"
+#include "bta_api.h"
+#include "bta_sys.h"
+#include "log/log.h"
#include "osi/include/log.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/include/port_api.h"
+#include "osi/include/osi.h"
+#include "port_api.h"
+#include "utl.h"
/*****************************************************************************
* Constants
@@ -57,7 +62,7 @@ enum {
};
/* AT command interpreter table for HSP */
-static const tBTA_AG_AT_CMD bta_ag_hsp_cmd[] = {
+const tBTA_AG_AT_CMD bta_ag_hsp_cmd[] = {
{"+CKPD", BTA_AG_AT_CKPD_EVT, BTA_AG_AT_SET, BTA_AG_AT_INT, 200, 200},
{"+VGS", BTA_AG_SPK_EVT, BTA_AG_AT_SET, BTA_AG_AT_INT, 0, 15},
{"+VGM", BTA_AG_MIC_EVT, BTA_AG_AT_SET, BTA_AG_AT_INT, 0, 15},
@@ -65,7 +70,7 @@ static const tBTA_AG_AT_CMD bta_ag_hsp_cmd[] = {
{"", 0, 0, 0, 0, 0}};
/* AT command interpreter table for HFP */
-static const tBTA_AG_AT_CMD bta_ag_hfp_cmd[] = {
+const tBTA_AG_AT_CMD bta_ag_hfp_cmd[] = {
{"A", BTA_AG_AT_A_EVT, BTA_AG_AT_NONE, BTA_AG_AT_STR, 0, 0},
{"D", BTA_AG_AT_D_EVT, BTA_AG_AT_NONE | BTA_AG_AT_FREE, BTA_AG_AT_STR, 0,
0},
@@ -133,7 +138,7 @@ enum {
};
/* AT result code constant table */
-static const tBTA_AG_RESULT bta_ag_result_tbl[] = {
+const tBTA_AG_RESULT bta_ag_result_tbl[] = {
{"OK", BTA_AG_LOCAL_RES_OK, BTA_AG_RES_FMT_NONE},
{"ERROR", BTA_AG_LOCAL_RES_ERROR, BTA_AG_RES_FMT_NONE},
{"RING", BTA_AG_LOCAL_RES_RING, BTA_AG_RES_FMT_NONE},
@@ -174,7 +179,7 @@ typedef struct {
} tBTA_AG_INDICATOR_MAP;
/* callsetup indicator value lookup table */
-static const tBTA_AG_INDICATOR_MAP callsetup_indicator_map[] = {
+const tBTA_AG_INDICATOR_MAP callsetup_indicator_map[] = {
{BTA_AG_IN_CALL_RES, BTA_AG_CALLSETUP_INCOMING},
{BTA_AG_CALL_WAIT_RES, BTA_AG_CALLSETUP_INCOMING},
{BTA_AG_OUT_CALL_ORIG_RES, BTA_AG_CALLSETUP_OUTGOING},
@@ -205,7 +210,8 @@ static void bta_ag_send_result(tBTA_AG_SCB* p_scb, size_t code,
const char* p_arg, int16_t int_arg) {
const tBTA_AG_RESULT* result = bta_ag_result_by_code(code);
if (result == nullptr) {
- LOG_ERROR("%s Unable to lookup result for code %zu", __func__, code);
+ LOG_ERROR(LOG_TAG, "%s Unable to lookup result for code %zu", __func__,
+ code);
return;
}
@@ -599,11 +605,7 @@ void bta_ag_at_hsp_cback(tBTA_AG_SCB* p_scb, uint16_t command_id,
strlcpy(val.str, p_arg, sizeof(val.str));
/* call callback with event */
- if (command_id & 0xff00) {
- LOG_WARN("Received value that exceeds data type - lost information");
- }
- tBTA_AG_EVT event = static_cast<tBTA_AG_EVT>(command_id);
- (*bta_ag_cb.p_cback)(event, (tBTA_AG*)&val);
+ (*bta_ag_cb.p_cback)(command_id, (tBTA_AG*)&val);
}
static void remove_spaces(char* str) {
@@ -823,21 +825,6 @@ static bool bta_ag_parse_biev_response(tBTA_AG_SCB* p_scb, tBTA_AG_VAL* val) {
/*******************************************************************************
*
- * Function bta_ag_bind_timer_cback
- *
- * Description Handles bind timer callback
- *
- *
- * Returns void
- *
- ******************************************************************************/
-static void bta_ag_bind_timer_cback(void* data) {
- tBTA_AG_SCB* p_scb = (tBTA_AG_SCB*)data;
- bta_ag_svc_conn_open(p_scb, tBTA_AG_DATA::kEmpty);
-}
-
-/*******************************************************************************
- *
* Function bta_ag_at_hfp_cback
*
* Description AT command processing callback for HFP.
@@ -853,7 +840,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
uint32_t i, ind_id;
uint32_t bia_masked_out;
if (p_arg == nullptr) {
- LOG_WARN("p_arg is null for cmd 0x%x, send error and return", cmd);
+ APPL_TRACE_ERROR("%s: p_arg is null, send error and return", __func__);
bta_ag_send_error(p_scb, BTA_AG_ERR_INV_CHAR_IN_TSTR);
return;
}
@@ -868,7 +855,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
val.bd_addr = p_scb->peer_addr;
if ((p_end - p_arg + 1) >= (long)sizeof(val.str)) {
- LOG_ERROR("p_arg is too long for cmd 0x%x, send error and return", cmd);
+ APPL_TRACE_ERROR("%s: p_arg is too long, send error and return", __func__);
bta_ag_send_error(p_scb, BTA_AG_ERR_TEXT_TOO_LONG);
android_errorWriteLog(0x534e4554, "112860487");
return;
@@ -881,7 +868,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
* If |event| is 0 at the end of this function, the application
* callback is NOT invoked.
*/
- tBTA_AG_EVT event = BTA_AG_ENABLE_EVT;
+ tBTA_AG_EVT event = 0;
if (cmd < BTA_AG_LOCAL_EVT_FIRST) {
event = static_cast<tBTA_AG_EVT>(cmd);
}
@@ -899,7 +886,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
if (!bta_ag_sco_is_active_device(p_scb->peer_addr)) {
LOG(WARNING) << __func__ << ": AT+CHUP rejected as " << p_scb->peer_addr
<< " is not the active device";
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_OP_NOT_ALLOWED);
} else {
bta_ag_send_ok(p_scb);
@@ -922,7 +909,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
remove_spaces(val.str + 1);
if (!utl_isintstr(val.str + 1)) {
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_INV_CHAR_IN_DSTR);
}
} else if (val.str[0] == 'V') /* ATDV : Dial VoIP Call */
@@ -930,7 +917,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
/* We do not check string. Code will be added later if needed. */
if (!((p_scb->peer_features & BTA_AG_PEER_FEAT_VOIP) &&
(p_scb->features & BTA_AG_FEAT_VOIP))) {
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_OP_NOT_SUPPORTED);
}
}
@@ -942,7 +929,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
remove_spaces(val.str);
if (!utl_isdialstr(val.str)) {
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_INV_CHAR_IN_DSTR);
}
}
@@ -959,7 +946,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
case BTA_AG_AT_CHLD_EVT:
if (arg_type == BTA_AG_AT_TEST) {
/* don't call callback */
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
/* send CHLD string */
/* Form string based on supported 1.5 feature */
@@ -975,26 +962,13 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
/* send OK */
bta_ag_send_ok(p_scb);
- /* if service level conn. not already open and our features and
- ** peer features do not have HF Indicators, service level conn. now open
- */
- if (!p_scb->svc_conn &&
- !((p_scb->masked_features & BTA_AG_FEAT_HF_IND) &&
- (p_scb->peer_features & BTA_AG_PEER_FEAT_HF_IND))) {
- bta_ag_svc_conn_open(p_scb, tBTA_AG_DATA::kEmpty);
- } else {
- if (p_scb->peer_version >= HFP_VERSION_1_7 &&
- interop_match_addr(INTEROP_SLC_SKIP_BIND_COMMAND,
- &p_scb->peer_addr)) {
- alarm_set_on_mloop(p_scb->bind_timer, BTA_AG_BIND_TIMEOUT_MS,
- bta_ag_bind_timer_cback, p_scb);
- }
- }
+ /* if service level conn. not already open, now it's open */
+ bta_ag_svc_conn_open(p_scb, tBTA_AG_DATA::kEmpty);
} else {
val.idx = bta_ag_parse_chld(p_scb, val.str);
if (val.idx == BTA_AG_INVALID_CHLD) {
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_OP_NOT_SUPPORTED);
break;
}
@@ -1003,7 +977,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
(p_scb->peer_features & BTA_AG_PEER_FEAT_ECC))) {
/* we do not support ECC, but HF is sending us a CHLD with call
* index*/
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_OP_NOT_SUPPORTED);
} else {
@@ -1031,12 +1005,11 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
case BTA_AG_AT_BIND_EVT:
APPL_TRACE_DEBUG("%s BTA_AG_AT_BIND_EVT arg_type: %d", __func__,
arg_type);
- alarm_cancel(p_scb->bind_timer);
if (arg_type == BTA_AG_AT_SET) {
if (bta_ag_parse_bind_set(p_scb, val)) {
bta_ag_send_ok(p_scb);
} else {
- event = BTA_AG_ENABLE_EVT; /* don't call callback */
+ event = 0; /* don't call callback */
bta_ag_send_error(p_scb, BTA_AG_ERR_INVALID_INDEX);
}
} else {
@@ -1044,7 +1017,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
/* Need not pass this command beyond BTIF.*/
/* Stack handles it internally */
- event = BTA_AG_ENABLE_EVT; /* don't call callback */
+ event = 0; /* don't call callback */
}
break;
@@ -1054,14 +1027,14 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
} else {
bta_ag_send_error(p_scb, BTA_AG_ERR_INVALID_INDEX);
/* don't call callback receiving invalid indicator */
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
}
break;
case BTA_AG_AT_CIND_EVT:
if (arg_type == BTA_AG_AT_TEST) {
/* don't call callback */
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
/* send CIND string, send OK */
bta_ag_send_result(p_scb, BTA_AG_CIND_RES, p_bta_ag_cfg->cind_info, 0);
@@ -1081,13 +1054,11 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
bta_ag_send_ok(p_scb);
/* if service level conn. not already open and our features and
- * peer features do not have 3-way or HF Indicators, service level conn.
- * now open */
+ ** peer features do not have 3-way, service level conn. now open
+ */
if (!p_scb->svc_conn &&
- !((p_scb->masked_features & BTA_AG_FEAT_3WAY) &&
- (p_scb->peer_features & BTA_AG_PEER_FEAT_3WAY)) &&
- !((p_scb->masked_features & BTA_AG_FEAT_HF_IND) &&
- (p_scb->peer_features & BTA_AG_PEER_FEAT_HF_IND))) {
+ !((p_scb->features & BTA_AG_FEAT_3WAY) &&
+ (p_scb->peer_features & BTA_AG_PEER_FEAT_3WAY))) {
bta_ag_svc_conn_open(p_scb, tBTA_AG_DATA::kEmpty);
}
} else {
@@ -1100,7 +1071,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
if (strlen(p_arg) == 1) {
bta_ag_send_ok(p_scb);
} else {
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_INV_CHAR_IN_TSTR);
}
break;
@@ -1108,7 +1079,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
case BTA_AG_AT_BINP_EVT:
/* if feature not set don't call callback, send ERROR */
if (!(p_scb->features & BTA_AG_FEAT_VTAG)) {
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_OP_NOT_SUPPORTED);
}
break;
@@ -1117,7 +1088,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
/* if feature not supported don't call callback, send ERROR. App will send
* OK */
if (!(p_scb->features & BTA_AG_FEAT_VREC)) {
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_OP_NOT_SUPPORTED);
}
break;
@@ -1126,16 +1097,17 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
/* store peer features */
p_scb->peer_features = (uint16_t)int_arg;
+ tBTA_AG_FEAT features = p_scb->features;
if (p_scb->peer_version < HFP_VERSION_1_7) {
- p_scb->masked_features &= HFP_1_6_FEAT_MASK;
+ features &= HFP_1_6_FEAT_MASK;
}
APPL_TRACE_DEBUG("%s BRSF HF: 0x%x, phone: 0x%x", __func__,
- p_scb->peer_features, p_scb->masked_features);
+ p_scb->peer_features, features);
/* send BRSF, send OK */
bta_ag_send_result(p_scb, BTA_AG_LOCAL_RES_BRSF, nullptr,
- (int16_t)p_scb->masked_features);
+ (int16_t)features);
bta_ag_send_ok(p_scb);
break;
}
@@ -1145,7 +1117,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
if (p_scb->features & BTA_AG_FEAT_ECNR) {
bta_ag_send_ok(p_scb);
} else {
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_OP_NOT_SUPPORTED);
}
break;
@@ -1167,7 +1139,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
val.num = BTA_AG_BTRH_READ;
}
} else {
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_OP_NOT_SUPPORTED);
}
break;
@@ -1175,7 +1147,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
case BTA_AG_AT_COPS_EVT:
if (arg_type == BTA_AG_AT_SET) {
/* don't call callback */
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
/* send OK */
bta_ag_send_ok(p_scb);
@@ -1193,7 +1165,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
bta_ag_send_error(p_scb, BTA_AG_ERR_OP_NOT_SUPPORTED);
}
/* don't call callback */
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
break;
case BTA_AG_AT_BIA_EVT:
@@ -1224,7 +1196,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
val.num = bia_masked_out;
bta_ag_send_ok(p_scb);
} else {
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_INVALID_INDEX);
}
break;
@@ -1234,7 +1206,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
case BTA_AG_AT_CLCC_EVT:
if (!(p_scb->features & BTA_AG_FEAT_ECS)) {
- event = BTA_AG_ENABLE_EVT;
+ event = 0;
bta_ag_send_error(p_scb, BTA_AG_ERR_OP_NOT_SUPPORTED);
}
break;
@@ -1321,7 +1293,7 @@ void bta_ag_at_hfp_cback(tBTA_AG_SCB* p_scb, uint16_t cmd, uint8_t arg_type,
}
/* call callback */
- if (event != BTA_AG_ENABLE_EVT) {
+ if (event != 0) {
(*bta_ag_cb.p_cback)(event, (tBTA_AG*)&val);
}
}
@@ -1367,8 +1339,7 @@ void bta_ag_at_err_cback(tBTA_AG_SCB* p_scb, bool unknown, const char* p_arg) {
* Returns void
*
******************************************************************************/
-static void bta_ag_hsp_result(tBTA_AG_SCB* p_scb,
- const tBTA_AG_API_RESULT& result) {
+void bta_ag_hsp_result(tBTA_AG_SCB* p_scb, const tBTA_AG_API_RESULT& result) {
APPL_TRACE_DEBUG("bta_ag_hsp_result : res = %d", result.result);
switch (result.result) {
@@ -1463,9 +1434,8 @@ static void bta_ag_hsp_result(tBTA_AG_SCB* p_scb,
* Returns void
*
******************************************************************************/
-static void bta_ag_hfp_result(tBTA_AG_SCB* p_scb,
- const tBTA_AG_API_RESULT& result) {
- LOG_DEBUG("HFP connection result:%s", result.ToString().c_str());
+void bta_ag_hfp_result(tBTA_AG_SCB* p_scb, const tBTA_AG_API_RESULT& result) {
+ APPL_TRACE_DEBUG("bta_ag_hfp_result : res = %d", result.result);
switch (result.result) {
case BTA_AG_SPK_RES:
diff --git a/bta/ag/bta_ag_int.h b/bta/ag/bta_ag_int.h
index bf96fd41a..63934506a 100644
--- a/bta/ag/bta_ag_int.h
+++ b/bta/ag/bta_ag_int.h
@@ -24,12 +24,10 @@
#ifndef BTA_AG_INT_H
#define BTA_AG_INT_H
-#include <cstdint>
-
-#include "bta/ag/bta_ag_at.h"
-#include "bta/include/bta_ag_api.h"
-#include "bta/include/bta_api.h"
-#include "bta/sys/bta_sys.h"
+#include "bta_ag_api.h"
+#include "bta_ag_at.h"
+#include "bta_api.h"
+#include "bta_sys.h"
/*****************************************************************************
* Constants
@@ -59,9 +57,6 @@
(BTA_AG_FEAT_3WAY | BTA_AG_FEAT_ECNR | BTA_AG_FEAT_VREC | \
BTA_AG_FEAT_INBAND | BTA_AG_FEAT_VTAG)
-/* Timeout for alarm in 2018 toyota camry carkit workaround */
-#define BTA_AG_BIND_TIMEOUT_MS 500
-
enum {
/* these events are handled by the state machine */
BTA_AG_API_REGISTER_EVT = BTA_SYS_EVT_START(BTA_ID_AG),
@@ -101,7 +96,7 @@ enum {
};
/* sco states */
-typedef enum : uint8_t {
+enum {
BTA_AG_SCO_SHUTDOWN_ST, /* no sco listening, all sco connections closed */
BTA_AG_SCO_LISTEN_ST, /* sco listening */
BTA_AG_SCO_CODEC_ST, /* sco codec negotiation */
@@ -113,7 +108,7 @@ typedef enum : uint8_t {
BTA_AG_SCO_CLOSE_OP_ST, /* closing sco being opened */
BTA_AG_SCO_CLOSE_XFER_ST, /* closing sco being transferred */
BTA_AG_SCO_SHUTTING_ST /* sco shutting down */
-} tBTA_AG_SCO;
+};
/*****************************************************************************
* Data types
@@ -123,6 +118,7 @@ typedef enum : uint8_t {
typedef struct {
char p_name[2][BTA_SERVICE_NAME_LEN + 1];
tBTA_SERVICE_MASK services;
+ tBTA_SEC sec_mask;
tBTA_AG_FEAT features;
uint8_t app_id;
} tBTA_AG_API_REGISTER;
@@ -130,15 +126,13 @@ typedef struct {
/* data type for BTA_AG_API_OPEN_EVT */
typedef struct {
RawAddress bd_addr;
+ tBTA_SEC sec_mask;
} tBTA_AG_API_OPEN;
/* data type for BTA_AG_API_RESULT_EVT */
typedef struct {
tBTA_AG_RES result;
tBTA_AG_RES_DATA data;
- std::string ToString() const {
- return base::StringPrintf("result:%s", bta_ag_result_text(result).c_str());
- }
} tBTA_AG_API_RESULT;
/* data type for BTA_AG_API_SETCODEC_EVT */
@@ -205,8 +199,9 @@ struct tBTA_AG_SCB {
tBTA_SERVICE_MASK reg_services; /* services specified in register API */
tBTA_SERVICE_MASK open_services; /* services specified in open API */
uint16_t conn_handle; /* RFCOMM handle of connected service */
+ tBTA_SEC serv_sec_mask; /* server security mask */
+ tBTA_SEC cli_sec_mask; /* client security mask */
tBTA_AG_FEAT features; /* features registered by application */
- tBTA_AG_FEAT masked_features; /* local BRSF features for this connection */
tBTA_AG_PEER_FEAT peer_features; /* peer device features */
uint16_t peer_sdp_features; /* peer device SDP features */
uint16_t peer_version; /* profile version of peer device */
@@ -234,7 +229,6 @@ struct tBTA_AG_SCB {
uint8_t battchg_ind; /* CIEV battery charge indicator value */
uint8_t callheld_ind; /* CIEV call held indicator value */
uint32_t bia_masked_out; /* indicators HF does not want us to send */
- alarm_t* bind_timer; /* Timer for toyota camry 2018 carkit workaround */
alarm_t* collision_timer;
alarm_t* ring_timer;
alarm_t* codec_negotiation_timer;
@@ -254,14 +248,6 @@ struct tBTA_AG_SCB {
tBTA_AG_HF_IND
local_hf_indicators[BTA_AG_MAX_NUM_LOCAL_HF_IND]; /* Local supported
HF indicators */
-
- std::string ToString() const {
- return base::StringPrintf(
- "codec_updated=%d, codec_fallback=%d, "
- "sco_codec=%d, peer_codec=%d, msbc_settings=%d, device=%s",
- codec_updated, codec_fallback, sco_codec, peer_codecs,
- codec_msbc_settings, peer_addr.ToString().c_str());
- }
};
/* type for sco data */
@@ -270,7 +256,7 @@ typedef struct {
tBTA_AG_SCB* p_curr_scb; /* SCB associated with SCO connection */
tBTA_AG_SCB* p_xfer_scb; /* SCB associated with SCO transfer */
uint16_t cur_idx; /* SCO handle */
- tBTA_AG_SCO state; /* SCO state variable */
+ uint8_t state; /* SCO state variable */
bool is_local; /* SCO connection initiated locally or remotely */
} tBTA_AG_SCO_CB;
@@ -301,13 +287,13 @@ extern const tBTA_AG_HF_IND bta_ag_local_hf_ind_cfg[];
/*****************************************************************************
* Function prototypes
****************************************************************************/
-bool bta_ag_hdl_event(BT_HDR_RIGID* p_msg);
+bool bta_ag_hdl_event(BT_HDR* p_msg);
/* API functions */
extern void bta_ag_api_enable(tBTA_AG_CBACK* p_cback);
extern void bta_ag_api_disable();
extern void bta_ag_api_set_active_device(const RawAddress& new_active_device);
-extern void bta_ag_api_register(tBTA_SERVICE_MASK services,
+extern void bta_ag_api_register(tBTA_SERVICE_MASK services, tBTA_SEC sec_mask,
tBTA_AG_FEAT features,
const std::vector<std::string>& service_names,
uint8_t app_id);
diff --git a/bta/ag/bta_ag_main.cc b/bta/ag/bta_ag_main.cc
index 583102fa8..f7bb8be2e 100644
--- a/bta/ag/bta_ag_main.cc
+++ b/bta/ag/bta_ag_main.cc
@@ -22,16 +22,14 @@
*
******************************************************************************/
-#include <string>
-#include <vector>
-
-#include "bta/ag/bta_ag_int.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/alarm.h"
-#include "osi/include/compat.h"
-#include "osi/include/log.h"
+#include <stack/include/bt_types.h>
+#include <string.h>
+
+#include "bta_ag_int.h"
+#include "bta_api.h"
+#include "bta_sys.h"
#include "osi/include/osi.h"
-#include "stack/include/btm_api.h"
+#include "utl.h"
/*****************************************************************************
* Constants and types
@@ -39,6 +37,46 @@
/* state machine states */
enum { BTA_AG_INIT_ST, BTA_AG_OPENING_ST, BTA_AG_OPEN_ST, BTA_AG_CLOSING_ST };
+/* state machine action enumeration list */
+enum {
+ BTA_AG_REGISTER,
+ BTA_AG_DEREGISTER,
+ BTA_AG_START_OPEN,
+ BTA_AG_RFC_DO_OPEN,
+ BTA_AG_RFC_DO_CLOSE,
+ BTA_AG_START_DEREG,
+ BTA_AG_START_CLOSE,
+ BTA_AG_RFC_OPEN,
+ BTA_AG_OPEN_FAIL,
+ BTA_AG_RFC_ACP_OPEN,
+ BTA_AG_RFC_CLOSE,
+ BTA_AG_RFC_FAIL,
+ BTA_AG_RFC_DATA,
+ BTA_AG_DISC_INT_RES,
+ BTA_AG_DISC_FAIL,
+ BTA_AG_DISC_ACP_RES,
+ BTA_AG_FREE_DB,
+ BTA_AG_SCO_CONN_OPEN,
+ BTA_AG_SCO_CONN_CLOSE,
+ BTA_AG_SCO_LISTEN,
+ BTA_AG_SCO_OPEN,
+ BTA_AG_SCO_CLOSE,
+ BTA_AG_SCO_SHUTDOWN,
+ BTA_AG_POST_SCO_OPEN,
+ BTA_AG_POST_SCO_CLOSE,
+ BTA_AG_SVC_CONN_OPEN,
+ BTA_AG_RESULT,
+ BTA_AG_SETCODEC,
+ BTA_AG_SEND_RING,
+ BTA_AG_HANDLE_COLLISION,
+ BTA_AG_NUM_ACTIONS
+};
+
+#define BTA_AG_IGNORE BTA_AG_NUM_ACTIONS
+
+/* type for action functions */
+typedef void (*tBTA_AG_ACTION)(tBTA_AG_SCB* p_scb, const tBTA_AG_DATA& data);
+
#define CASE_RETURN_STR(const) \
case const: \
return #const;
@@ -113,6 +151,155 @@ static const char* bta_ag_state_str(uint8_t state) {
}
}
+/* action functions */
+const tBTA_AG_ACTION bta_ag_action[] = {
+ bta_ag_register, bta_ag_deregister, bta_ag_start_open,
+ bta_ag_rfc_do_open, bta_ag_rfc_do_close, bta_ag_start_dereg,
+ bta_ag_start_close, bta_ag_rfc_open, bta_ag_open_fail,
+ bta_ag_rfc_acp_open, bta_ag_rfc_close, bta_ag_rfc_fail,
+ bta_ag_rfc_data, bta_ag_disc_int_res, bta_ag_disc_fail,
+ bta_ag_disc_acp_res, bta_ag_free_db, bta_ag_sco_conn_open,
+ bta_ag_sco_conn_close, bta_ag_sco_listen, bta_ag_sco_open,
+ bta_ag_sco_close, bta_ag_sco_shutdown, bta_ag_post_sco_open,
+ bta_ag_post_sco_close, bta_ag_svc_conn_open, bta_ag_result,
+ bta_ag_setcodec, bta_ag_send_ring, bta_ag_handle_collision};
+
+static_assert(sizeof(bta_ag_action) / sizeof(tBTA_AG_ACTION) ==
+ BTA_AG_NUM_ACTIONS,
+ "bta_ag_action must handle all actions");
+
+/* state table information */
+#define BTA_AG_ACTIONS 2 /* number of actions */
+#define BTA_AG_NEXT_STATE 2 /* position of next state */
+#define BTA_AG_NUM_COLS 3 /* number of columns in state tables */
+
+/* state table for init state */
+const uint8_t bta_ag_st_init[][BTA_AG_NUM_COLS] = {
+ /* Event Action 1 Action 2 Next state */
+ /* API_REGISTER_EVT */ {BTA_AG_REGISTER, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* API_DEREGISTER_EVT */ {BTA_AG_DEREGISTER, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* API_OPEN_EVT */ {BTA_AG_START_OPEN, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* API_CLOSE_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* API_AUDIO_OPEN_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* API_AUDIO_CLOSE_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* API_RESULT_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* API_SETCODEC_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* RFC_OPEN_EVT */ {BTA_AG_RFC_ACP_OPEN, BTA_AG_SCO_LISTEN, BTA_AG_OPEN_ST},
+ /* RFC_CLOSE_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* RFC_SRV_CLOSE_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* RFC_DATA_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* SCO_OPEN_EVT */ {BTA_AG_SCO_CONN_OPEN, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* SCO_CLOSE_EVT */ {BTA_AG_SCO_CONN_CLOSE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* DISC_ACP_RES_EVT */ {BTA_AG_FREE_DB, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* DISC_INT_RES_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* DISC_OK_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* DISC_FAIL_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* RING_TOUT_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* SVC_TOUT_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* COLLISION_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_INIT_ST}};
+
+/* state table for opening state */
+const uint8_t bta_ag_st_opening[][BTA_AG_NUM_COLS] = {
+ /* Event Action 1 Action 2 Next state */
+ /* API_REGISTER_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* API_DEREGISTER_EVT */
+ {BTA_AG_RFC_DO_CLOSE, BTA_AG_START_DEREG, BTA_AG_CLOSING_ST},
+ /* API_OPEN_EVT */ {BTA_AG_OPEN_FAIL, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* API_CLOSE_EVT */ {BTA_AG_RFC_DO_CLOSE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* API_AUDIO_OPEN_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* API_AUDIO_CLOSE_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* API_RESULT_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* API_SETCODEC_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* RFC_OPEN_EVT */ {BTA_AG_RFC_OPEN, BTA_AG_SCO_LISTEN, BTA_AG_OPEN_ST},
+ /* RFC_CLOSE_EVT */ {BTA_AG_RFC_FAIL, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* RFC_SRV_CLOSE_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* RFC_DATA_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* SCO_OPEN_EVT */ {BTA_AG_SCO_CONN_OPEN, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* SCO_CLOSE_EVT */
+ {BTA_AG_SCO_CONN_CLOSE, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* DISC_ACP_RES_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* DISC_INT_RES_EVT */
+ {BTA_AG_DISC_INT_RES, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* DISC_OK_EVT */ {BTA_AG_RFC_DO_OPEN, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* DISC_FAIL_EVT */ {BTA_AG_DISC_FAIL, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* RING_TOUT_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* SVC_TOUT_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPENING_ST},
+ /* COLLISION_EVT */
+ {BTA_AG_HANDLE_COLLISION, BTA_AG_IGNORE, BTA_AG_INIT_ST}};
+
+/* state table for open state */
+const uint8_t bta_ag_st_open[][BTA_AG_NUM_COLS] = {
+ /* Event Action 1 Action 2 Next state */
+ /* API_REGISTER_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* API_DEREGISTER_EVT */
+ {BTA_AG_START_CLOSE, BTA_AG_START_DEREG, BTA_AG_CLOSING_ST},
+ /* API_OPEN_EVT */ {BTA_AG_OPEN_FAIL, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* API_CLOSE_EVT */ {BTA_AG_START_CLOSE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* API_AUDIO_OPEN_EVT */ {BTA_AG_SCO_OPEN, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* API_AUDIO_CLOSE_EVT */ {BTA_AG_SCO_CLOSE, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* API_RESULT_EVT */ {BTA_AG_RESULT, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* API_SETCODEC_EVT */ {BTA_AG_SETCODEC, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* RFC_OPEN_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* RFC_CLOSE_EVT */ {BTA_AG_RFC_CLOSE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* RFC_SRV_CLOSE_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* RFC_DATA_EVT */ {BTA_AG_RFC_DATA, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* SCO_OPEN_EVT */
+ {BTA_AG_SCO_CONN_OPEN, BTA_AG_POST_SCO_OPEN, BTA_AG_OPEN_ST},
+ /* SCO_CLOSE_EVT */
+ {BTA_AG_SCO_CONN_CLOSE, BTA_AG_POST_SCO_CLOSE, BTA_AG_OPEN_ST},
+ /* DISC_ACP_RES_EVT */ {BTA_AG_DISC_ACP_RES, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* DISC_INT_RES_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* DISC_OK_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* DISC_FAIL_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* RING_TOUT_EVT */ {BTA_AG_SEND_RING, BTA_AG_IGNORE, BTA_AG_OPEN_ST},
+ /* SVC_TOUT_EVT */ {BTA_AG_START_CLOSE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* COLLISION_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_OPEN_ST}};
+
+/* state table for closing state */
+const uint8_t bta_ag_st_closing[][BTA_AG_NUM_COLS] = {
+ /* Event Action 1 Action 2 Next state */
+ /* API_REGISTER_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* API_DEREGISTER_EVT */
+ {BTA_AG_START_DEREG, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* API_OPEN_EVT */ {BTA_AG_OPEN_FAIL, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* API_CLOSE_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* API_AUDIO_OPEN_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* API_AUDIO_CLOSE_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* API_RESULT_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* API_SETCODEC_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* RFC_OPEN_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* RFC_CLOSE_EVT */ {BTA_AG_RFC_CLOSE, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* RFC_SRV_CLOSE_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* RFC_DATA_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* SCO_OPEN_EVT */ {BTA_AG_SCO_CONN_OPEN, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* SCO_CLOSE_EVT */
+ {BTA_AG_SCO_CONN_CLOSE, BTA_AG_POST_SCO_CLOSE, BTA_AG_CLOSING_ST},
+ /* DISC_ACP_RES_EVT */ {BTA_AG_FREE_DB, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* DISC_INT_RES_EVT */ {BTA_AG_FREE_DB, BTA_AG_IGNORE, BTA_AG_INIT_ST},
+ /* DISC_OK_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* DISC_FAIL_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* RING_TOUT_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* SVC_TOUT_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST},
+ /* COLLISION_EVT */ {BTA_AG_IGNORE, BTA_AG_IGNORE, BTA_AG_CLOSING_ST}};
+
+constexpr size_t BTA_AG_NUM_EVENTS =
+ BTA_AG_MAX_EVT - BTA_SYS_EVT_START(BTA_ID_AG);
+static_assert(sizeof(bta_ag_st_init) / BTA_AG_NUM_COLS == BTA_AG_NUM_EVENTS,
+ "bta_ag_st_init must handle all AG events");
+static_assert(sizeof(bta_ag_st_opening) / BTA_AG_NUM_COLS == BTA_AG_NUM_EVENTS,
+ "bta_ag_st_opening must handle all AG events");
+static_assert(sizeof(bta_ag_st_open) / BTA_AG_NUM_COLS == BTA_AG_NUM_EVENTS,
+ "bta_ag_st_open must handle all AG events");
+static_assert(sizeof(bta_ag_st_closing) / BTA_AG_NUM_COLS == BTA_AG_NUM_EVENTS,
+ "bta_ag_st_closing must handle all AG events");
+
+/* type for state table */
+typedef const uint8_t (*tBTA_AG_ST_TBL)[BTA_AG_NUM_COLS];
+
+/* state table */
+const tBTA_AG_ST_TBL bta_ag_st_tbl[] = {bta_ag_st_init, bta_ag_st_opening,
+ bta_ag_st_open, bta_ag_st_closing};
+
/*****************************************************************************
* Global data
****************************************************************************/
@@ -377,7 +564,8 @@ void bta_ag_resume_open(tBTA_AG_SCB* p_scb) {
if (p_scb->state == BTA_AG_INIT_ST) {
LOG(INFO) << __func__ << ": Resume connection to " << p_scb->peer_addr
<< ", handle" << bta_ag_scb_to_idx(p_scb);
- tBTA_AG_DATA open_data = {.api_open = {.bd_addr = p_scb->peer_addr}};
+ tBTA_AG_DATA open_data = {.api_open = {.bd_addr = p_scb->peer_addr,
+ .sec_mask = p_scb->cli_sec_mask}};
bta_ag_sm_execute(p_scb, BTA_AG_API_OPEN_EVT, open_data);
} else {
VLOG(1) << __func__ << ": device " << p_scb->peer_addr
@@ -465,7 +653,8 @@ void bta_ag_api_disable() {
* Returns void
*
******************************************************************************/
-void bta_ag_api_register(tBTA_SERVICE_MASK services, tBTA_AG_FEAT features,
+void bta_ag_api_register(tBTA_SERVICE_MASK services, tBTA_SEC sec_mask,
+ tBTA_AG_FEAT features,
const std::vector<std::string>& service_names,
uint8_t app_id) {
tBTA_AG_SCB* p_scb = bta_ag_scb_alloc();
@@ -473,6 +662,7 @@ void bta_ag_api_register(tBTA_SERVICE_MASK services, tBTA_AG_FEAT features,
APPL_TRACE_DEBUG("bta_ag_api_register: p_scb 0x%08x ", p_scb);
tBTA_AG_DATA data = {};
data.api_register.features = features;
+ data.api_register.sec_mask = sec_mask;
data.api_register.services = services;
data.api_register.app_id = app_id;
for (int i = 0; i < BTA_AG_NUM_IDX; i++) {
@@ -510,23 +700,16 @@ void bta_ag_api_result(uint16_t handle, tBTA_AG_RES result,
if (handle != BTA_AG_HANDLE_ALL) {
p_scb = bta_ag_scb_by_idx(handle);
if (p_scb) {
- LOG_DEBUG("Audio gateway event for one client handle:%hu scb:%s", handle,
- p_scb->ToString().c_str());
+ APPL_TRACE_DEBUG("bta_ag_api_result: p_scb 0x%08x ", p_scb);
bta_ag_sm_execute(p_scb, static_cast<uint16_t>(BTA_AG_API_RESULT_EVT),
event_data);
- } else {
- LOG_WARN(
- "Received audio gateway event for unknown AG control block "
- "handle:%hu",
- handle);
}
} else {
int i;
for (i = 0, p_scb = &bta_ag_cb.scb[0]; i < BTA_AG_MAX_NUM_CLIENTS;
i++, p_scb++) {
if (p_scb->in_use && p_scb->svc_conn) {
- LOG_DEBUG("Audio gateway event for all clients scb:%s",
- p_scb->ToString().c_str());
+ APPL_TRACE_DEBUG("bta_ag_api_result p_scb 0x%08x ", p_scb);
bta_ag_sm_execute(p_scb, static_cast<uint16_t>(BTA_AG_API_RESULT_EVT),
event_data);
}
@@ -534,178 +717,6 @@ void bta_ag_api_result(uint16_t handle, tBTA_AG_RES result,
}
}
-static void bta_ag_better_state_machine(tBTA_AG_SCB* p_scb, uint16_t event,
- const tBTA_AG_DATA& data) {
- switch (p_scb->state) {
- case BTA_AG_INIT_ST:
- switch (event) {
- case BTA_AG_API_REGISTER_EVT:
- bta_ag_register(p_scb, data);
- break;
- case BTA_AG_API_DEREGISTER_EVT:
- bta_ag_deregister(p_scb, data);
- break;
- case BTA_AG_API_OPEN_EVT:
- p_scb->state = BTA_AG_OPENING_ST;
- bta_ag_start_open(p_scb, data);
- break;
- case BTA_AG_RFC_OPEN_EVT:
- p_scb->state = BTA_AG_OPEN_ST;
- bta_ag_rfc_acp_open(p_scb, data);
- bta_ag_sco_listen(p_scb, data);
- break;
- case BTA_AG_SCO_OPEN_EVT:
- bta_ag_sco_conn_open(p_scb, data);
- break;
- case BTA_AG_SCO_CLOSE_EVT:
- bta_ag_sco_conn_close(p_scb, data);
- break;
- case BTA_AG_DISC_ACP_RES_EVT:
- bta_ag_free_db(p_scb, data);
- break;
- default:
- LOG_ERROR("unknown event %d at state %d", event, p_scb->state);
- break;
- }
- break;
- case BTA_AG_OPENING_ST:
- switch (event) {
- case BTA_AG_API_DEREGISTER_EVT:
- p_scb->state = BTA_AG_CLOSING_ST;
- bta_ag_rfc_do_close(p_scb, data);
- bta_ag_start_dereg(p_scb, data);
- break;
- case BTA_AG_API_OPEN_EVT:
- bta_ag_open_fail(p_scb, data);
- break;
- case BTA_AG_API_CLOSE_EVT:
- p_scb->state = BTA_AG_CLOSING_ST;
- bta_ag_rfc_do_close(p_scb, data);
- break;
- case BTA_AG_RFC_OPEN_EVT:
- p_scb->state = BTA_AG_OPEN_ST;
- bta_ag_rfc_open(p_scb, data);
- bta_ag_sco_listen(p_scb, data);
- break;
- case BTA_AG_RFC_CLOSE_EVT:
- p_scb->state = BTA_AG_INIT_ST;
- bta_ag_rfc_fail(p_scb, data);
- break;
- case BTA_AG_SCO_OPEN_EVT:
- bta_ag_sco_conn_open(p_scb, data);
- break;
- case BTA_AG_SCO_CLOSE_EVT:
- bta_ag_sco_conn_close(p_scb, data);
- break;
- case BTA_AG_DISC_INT_RES_EVT:
- bta_ag_disc_int_res(p_scb, data);
- break;
- case BTA_AG_DISC_OK_EVT:
- bta_ag_rfc_do_open(p_scb, data);
- break;
- case BTA_AG_DISC_FAIL_EVT:
- p_scb->state = BTA_AG_INIT_ST;
- bta_ag_disc_fail(p_scb, data);
- break;
- case BTA_AG_COLLISION_EVT:
- p_scb->state = BTA_AG_INIT_ST;
- bta_ag_handle_collision(p_scb, data);
- break;
- default:
- LOG_ERROR("unknown event %d at state %d", event, p_scb->state);
- break;
- }
- break;
- case BTA_AG_OPEN_ST:
- switch (event) {
- case BTA_AG_API_DEREGISTER_EVT:
- p_scb->state = BTA_AG_CLOSING_ST;
- bta_ag_start_close(p_scb, data);
- bta_ag_start_dereg(p_scb, data);
- break;
- case BTA_AG_API_OPEN_EVT:
- bta_ag_open_fail(p_scb, data);
- break;
- case BTA_AG_API_CLOSE_EVT:
- p_scb->state = BTA_AG_CLOSING_ST;
- bta_ag_start_close(p_scb, data);
- break;
- case BTA_AG_API_AUDIO_OPEN_EVT:
- bta_ag_sco_open(p_scb, data);
- break;
- case BTA_AG_API_AUDIO_CLOSE_EVT:
- bta_ag_sco_close(p_scb, data);
- break;
- case BTA_AG_API_RESULT_EVT:
- bta_ag_result(p_scb, data);
- break;
- case BTA_AG_API_SETCODEC_EVT:
- bta_ag_setcodec(p_scb, data);
- break;
- case BTA_AG_RFC_CLOSE_EVT:
- p_scb->state = BTA_AG_INIT_ST;
- bta_ag_rfc_close(p_scb, data);
- break;
- case BTA_AG_RFC_DATA_EVT:
- bta_ag_rfc_data(p_scb, data);
- break;
- case BTA_AG_SCO_OPEN_EVT:
- bta_ag_sco_conn_open(p_scb, data);
- bta_ag_post_sco_open(p_scb, data);
- break;
- case BTA_AG_SCO_CLOSE_EVT:
- bta_ag_sco_conn_close(p_scb, data);
- bta_ag_post_sco_close(p_scb, data);
- break;
- case BTA_AG_DISC_ACP_RES_EVT:
- bta_ag_disc_acp_res(p_scb, data);
- break;
- case BTA_AG_RING_TIMEOUT_EVT:
- bta_ag_send_ring(p_scb, data);
- break;
- case BTA_AG_SVC_TIMEOUT_EVT:
- p_scb->state = BTA_AG_CLOSING_ST;
- bta_ag_start_close(p_scb, data);
- break;
- default:
- LOG_ERROR("unknown event %d at state %d", event, p_scb->state);
- break;
- }
- break;
- case BTA_AG_CLOSING_ST:
- switch (event) {
- case BTA_AG_API_DEREGISTER_EVT:
- bta_ag_start_dereg(p_scb, data);
- break;
- case BTA_AG_API_OPEN_EVT:
- bta_ag_open_fail(p_scb, data);
- break;
- case BTA_AG_RFC_CLOSE_EVT:
- p_scb->state = BTA_AG_INIT_ST;
- bta_ag_rfc_close(p_scb, data);
- break;
- case BTA_AG_SCO_OPEN_EVT:
- bta_ag_sco_conn_open(p_scb, data);
- break;
- case BTA_AG_SCO_CLOSE_EVT:
- bta_ag_sco_conn_close(p_scb, data);
- bta_ag_post_sco_close(p_scb, data);
- break;
- case BTA_AG_DISC_ACP_RES_EVT:
- bta_ag_free_db(p_scb, data);
- break;
- case BTA_AG_DISC_INT_RES_EVT:
- p_scb->state = BTA_AG_INIT_ST;
- bta_ag_free_db(p_scb, data);
- break;
- default:
- LOG_ERROR("unknown event %d at state %d", event, p_scb->state);
- break;
- }
- break;
- }
-}
-
/*******************************************************************************
*
* Function bta_ag_sm_execute
@@ -718,24 +729,45 @@ static void bta_ag_better_state_machine(tBTA_AG_SCB* p_scb, uint16_t event,
******************************************************************************/
void bta_ag_sm_execute(tBTA_AG_SCB* p_scb, uint16_t event,
const tBTA_AG_DATA& data) {
+ tBTA_AG_ST_TBL state_table;
+ uint8_t action;
+ int i;
uint16_t previous_event = event;
uint8_t previous_state = p_scb->state;
- LOG_DEBUG(
- "Execute AG event handle:0x%04x bd_addr:%s state:%s[0x%02x]"
- " event:%s[0x%04x] result:%s[0x%02x]",
- bta_ag_scb_to_idx(p_scb), PRIVATE_ADDRESS(p_scb->peer_addr),
+ APPL_TRACE_EVENT(
+ "%s: handle=0x%04x, bd_addr=%s, state=%s(0x%02x), "
+ "event=%s(0x%04x), result=%s(0x%02x)",
+ __func__, bta_ag_scb_to_idx(p_scb), p_scb->peer_addr.ToString().c_str(),
bta_ag_state_str(p_scb->state), p_scb->state, bta_ag_evt_str(event),
event, bta_ag_res_str(data.api_result.result), data.api_result.result);
- bta_ag_better_state_machine(p_scb, event, data);
+ event &= 0x00FF;
+ if (event >= (BTA_AG_MAX_EVT & 0x00FF)) {
+ APPL_TRACE_ERROR("%s: event out of range, ignored", __func__);
+ return;
+ }
+
+ /* look up the state table for the current state */
+ state_table = bta_ag_st_tbl[p_scb->state];
+
+ /* set next state */
+ p_scb->state = state_table[event][BTA_AG_NEXT_STATE];
+ /* execute action functions */
+ for (i = 0; i < BTA_AG_ACTIONS; i++) {
+ action = state_table[event][i];
+ if (action != BTA_AG_IGNORE) {
+ (*bta_ag_action[action])(p_scb, data);
+ } else {
+ break;
+ }
+ }
if (p_scb->state != previous_state) {
- LOG_DEBUG(
- "State changed handle:0x%04x bd_addr:%s "
- "state_change:%s[0x%02x]->%s[0x%02x]"
- " event:%s[0x%04x] result:%s[0x%02x]",
- bta_ag_scb_to_idx(p_scb), PRIVATE_ADDRESS(p_scb->peer_addr),
+ APPL_TRACE_EVENT(
+ "%s: handle=0x%04x, bd_addr=%s, state_change[%s(0x%02x)]->[%s(0x%02x)],"
+ " event[%s(0x%04x)], result[%s(0x%02x)]",
+ __func__, bta_ag_scb_to_idx(p_scb), p_scb->peer_addr.ToString().c_str(),
bta_ag_state_str(previous_state), previous_state,
bta_ag_state_str(p_scb->state), p_scb->state,
bta_ag_evt_str(previous_event), previous_event,
@@ -747,8 +779,7 @@ void bta_ag_sm_execute_by_handle(uint16_t handle, uint16_t event,
const tBTA_AG_DATA& data) {
tBTA_AG_SCB* p_scb = bta_ag_scb_by_idx(handle);
if (p_scb) {
- LOG_DEBUG("AG state machine event:%s[0x%04x] handle:0x%04x",
- bta_ag_evt_str(event), event, handle);
+ APPL_TRACE_DEBUG("%s: p_scb 0x%08x ", __func__, p_scb);
bta_ag_sm_execute(p_scb, event, data);
}
}
@@ -760,7 +791,7 @@ void bta_ag_sm_execute_by_handle(uint16_t handle, uint16_t event,
* @param p_msg event message
* @return True to free p_msg, or False if p_msg is freed within this function
*/
-bool bta_ag_hdl_event(BT_HDR_RIGID* p_msg) {
+bool bta_ag_hdl_event(BT_HDR* p_msg) {
switch (p_msg->event) {
case BTA_AG_RING_TIMEOUT_EVT:
case BTA_AG_SVC_TIMEOUT_EVT:
diff --git a/bta/ag/bta_ag_rfc.cc b/bta/ag/bta_ag_rfc.cc
index 7767739a9..d878afe34 100644
--- a/bta/ag/bta_ag_rfc.cc
+++ b/bta/ag/bta_ag_rfc.cc
@@ -23,13 +23,19 @@
*
******************************************************************************/
-#include <base/bind.h>
#include <cstring>
-#include "bta/ag/bta_ag_int.h"
+#include <base/bind.h>
+
+#include "bt_common.h"
+#include "bta_ag_api.h"
+#include "bta_ag_int.h"
+#include "btm_api.h"
#include "osi/include/osi.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "stack/include/port_api.h"
+#include "port_api.h"
+#include "rfcdefs.h"
+#include "stack/include/btu.h"
+#include "utl.h"
/* Event mask for RfCOMM port callback */
#define BTA_AG_PORT_EV_MASK PORT_EV_RXCHAR
@@ -241,6 +247,9 @@ void bta_ag_start_servers(tBTA_AG_SCB* p_scb, tBTA_SERVICE_MASK services) {
for (int i = 0; i < BTA_AG_NUM_IDX && services != 0; i++, services >>= 1) {
/* if service is set in mask */
if (services & 1) {
+ BTM_SetSecurityLevel(false, "", bta_ag_sec_id[i], p_scb->serv_sec_mask,
+ BT_PSM_RFCOMM, BTM_SEC_PROTO_RFCOMM,
+ bta_ag_cb.profile[i].scn);
int management_callback_index = bta_ag_scb_to_idx(p_scb) - 1;
CHECK_GE(management_callback_index, 0)
<< "invalid callback index, services=" << loghex(services)
@@ -250,18 +259,16 @@ void bta_ag_start_servers(tBTA_AG_SCB* p_scb, tBTA_SERVICE_MASK services) {
sizeof(bta_ag_mgmt_cback_tbl[0])))
<< "callback index out of bound, services=" << loghex(services)
<< ", bd_addr" << p_scb->peer_addr;
- int status = RFCOMM_CreateConnectionWithSecurity(
+ int status = RFCOMM_CreateConnection(
bta_ag_uuid[i], bta_ag_cb.profile[i].scn, true, BTA_AG_MTU,
RawAddress::kAny, &(p_scb->serv_handle[i]),
- bta_ag_mgmt_cback_tbl[management_callback_index],
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT);
+ bta_ag_mgmt_cback_tbl[management_callback_index]);
if (status == PORT_SUCCESS) {
bta_ag_setup_port(p_scb, p_scb->serv_handle[i]);
} else {
/* TODO: CR#137125 to handle to error properly */
- LOG(ERROR) << __func__ << ": RFCOMM_CreateConnectionWithSecurity ERROR "
- << status << ", p_scb=" << p_scb
- << ", services=" << loghex(services)
+ LOG(ERROR) << __func__ << ": RFCOMM_CreateConnection ERROR " << status
+ << ", p_scb=" << p_scb << ", services=" << loghex(services)
<< ", mgmt_cback_index=" << management_callback_index;
}
APPL_TRACE_DEBUG("%s: p_scb=0x%08x, services=0x%04x, mgmt_cback_index=%d",
@@ -323,12 +330,15 @@ bool bta_ag_is_server_closed(tBTA_AG_SCB* p_scb) {
*
******************************************************************************/
void bta_ag_rfc_do_open(tBTA_AG_SCB* p_scb, const tBTA_AG_DATA& data) {
+ BTM_SetSecurityLevel(true, "", bta_ag_sec_id[p_scb->conn_service],
+ p_scb->cli_sec_mask, BT_PSM_RFCOMM, BTM_SEC_PROTO_RFCOMM,
+ p_scb->peer_scn);
+
int management_callback_index = bta_ag_scb_to_idx(p_scb) - 1;
- int status = RFCOMM_CreateConnectionWithSecurity(
+ int status = RFCOMM_CreateConnection(
bta_ag_uuid[p_scb->conn_service], p_scb->peer_scn, false, BTA_AG_MTU,
p_scb->peer_addr, &(p_scb->conn_handle),
- bta_ag_mgmt_cback_tbl[management_callback_index],
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT);
+ bta_ag_mgmt_cback_tbl[management_callback_index]);
APPL_TRACE_DEBUG(
"%s: p_scb=0x%08x, conn_handle=%d, mgmt_cback_index=%d,"
" status=%d",
diff --git a/bta/ag/bta_ag_sco.cc b/bta/ag/bta_ag_sco.cc
index bb35c566e..297d93ddd 100644
--- a/bta/ag/bta_ag_sco.cc
+++ b/bta/ag/bta_ag_sco.cc
@@ -22,22 +22,18 @@
*
******************************************************************************/
-#include <base/bind.h>
-#include <cstdint>
+#include <cstddef>
-#include "bt_target.h" // Must be first to define build configuration
-#include "bt_trace.h" // Legacy trace logging
-
-#include "bta/ag/bta_ag_int.h"
+#include "bt_common.h"
+#include "bta_ag_api.h"
+#include "bta_ag_int.h"
+#include "bta_api.h"
+#include "btm_api.h"
#include "device/include/controller.h"
#include "device/include/esco_parameters.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/btm/btm_sco.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "types/raw_address.h"
+#include "osi/include/osi.h"
+#include "stack/include/btu.h"
+#include "utl.h"
/* Codec negotiation timeout */
#ifndef BTA_AG_CODEC_NEGOTIATION_TIMEOUT_MS
@@ -49,11 +45,11 @@ static RawAddress active_device_addr = {};
/* sco events */
enum {
- BTA_AG_SCO_LISTEN_E, /* listen request */
- BTA_AG_SCO_OPEN_E, /* open request */
- BTA_AG_SCO_XFER_E, /* transfer request */
- BTA_AG_SCO_CN_DONE_E, /* codec negotiation done */
- BTA_AG_SCO_REOPEN_E, /* Retry with other codec when failed */
+ BTA_AG_SCO_LISTEN_E, /* listen request */
+ BTA_AG_SCO_OPEN_E, /* open request */
+ BTA_AG_SCO_XFER_E, /* transfer request */
+ BTA_AG_SCO_CN_DONE_E, /* codec negotiation done */
+ BTA_AG_SCO_REOPEN_E, /* Retry with other codec when failed */
BTA_AG_SCO_CLOSE_E, /* close request */
BTA_AG_SCO_SHUTDOWN_E, /* shutdown request */
BTA_AG_SCO_CONN_OPEN_E, /* sco open */
@@ -162,17 +158,21 @@ static void bta_ag_sco_conn_cback(uint16_t sco_idx) {
static void bta_ag_sco_disc_cback(uint16_t sco_idx) {
uint16_t handle = 0;
- LOG_DEBUG(
- "sco_idx: 0x%x sco.state:%s", sco_idx,
- sco_state_text(static_cast<tSCO_STATE>(bta_ag_cb.sco.state)).c_str());
- LOG_DEBUG(
- " scb[0] in_use:%s sco_idx: 0x%x sco state:%s",
- logbool(bta_ag_cb.scb[0].in_use).c_str(), bta_ag_cb.scb[0].sco_idx,
- sco_state_text(static_cast<tSCO_STATE>(bta_ag_cb.scb[0].state)).c_str());
- LOG_DEBUG(
- " scb[1] in_use:%s sco_idx:0x%x sco state:%s",
- logbool(bta_ag_cb.scb[1].in_use).c_str(), bta_ag_cb.scb[1].sco_idx,
- sco_state_text(static_cast<tSCO_STATE>(bta_ag_cb.scb[1].state)).c_str());
+ APPL_TRACE_DEBUG(
+ "bta_ag_sco_disc_cback(): sco_idx: 0x%x p_cur_scb: 0x%08x sco.state: "
+ "%d",
+ sco_idx, bta_ag_cb.sco.p_curr_scb, bta_ag_cb.sco.state);
+
+ APPL_TRACE_DEBUG(
+ "bta_ag_sco_disc_cback(): scb[0] addr: 0x%08x in_use: %u sco_idx: 0x%x "
+ " sco state: %u",
+ &bta_ag_cb.scb[0], bta_ag_cb.scb[0].in_use, bta_ag_cb.scb[0].sco_idx,
+ bta_ag_cb.scb[0].state);
+ APPL_TRACE_DEBUG(
+ "bta_ag_sco_disc_cback(): scb[1] addr: 0x%08x in_use: %u sco_idx: 0x%x "
+ " sco state: %u",
+ &bta_ag_cb.scb[1], bta_ag_cb.scb[1].in_use, bta_ag_cb.scb[1].sco_idx,
+ bta_ag_cb.scb[1].state);
/* match callback to scb */
if (bta_ag_cb.sco.p_curr_scb != nullptr && bta_ag_cb.sco.p_curr_scb->in_use) {
@@ -184,6 +184,7 @@ static void bta_ag_sco_disc_cback(uint16_t sco_idx) {
}
if (handle != 0) {
+
/* Restore settings */
if (bta_ag_cb.sco.p_curr_scb->inuse_codec == BTA_AG_CODEC_MSBC) {
/* Bypass vendor specific and voice settings if enhanced eSCO supported */
@@ -247,8 +248,8 @@ static bool bta_ag_remove_sco(tBTA_AG_SCB* p_scb, bool only_active) {
if (p_scb->sco_idx != BTM_INVALID_SCO_INDEX) {
if (!only_active || p_scb->sco_idx == bta_ag_cb.sco.cur_idx) {
tBTM_STATUS status = BTM_RemoveSco(p_scb->sco_idx);
- LOG_DEBUG("Removed SCO index:0x%04x status:%s", p_scb->sco_idx,
- btm_status_text(status).c_str());
+ APPL_TRACE_DEBUG("%s: SCO index 0x%04x, status %d", __func__,
+ p_scb->sco_idx, status);
if (status == BTM_CMD_STARTED) {
/* SCO is connected; set current control block */
bta_ag_cb.sco.p_curr_scb = p_scb;
@@ -339,12 +340,12 @@ static void bta_ag_esco_connreq_cback(tBTM_ESCO_EVT event,
* Returns void
*
******************************************************************************/
-static void bta_ag_cback_sco(tBTA_AG_SCB* p_scb, tBTA_AG_EVT event) {
+static void bta_ag_cback_sco(tBTA_AG_SCB* p_scb, uint8_t event) {
tBTA_AG_HDR sco = {};
sco.handle = bta_ag_scb_to_idx(p_scb);
sco.app_id = p_scb->app_id;
/* call close cback */
- (*bta_ag_cb.p_cback)(static_cast<tBTA_AG_EVT>(event), (tBTA_AG*)&sco);
+ (*bta_ag_cb.p_cback)(event, (tBTA_AG*)&sco);
}
/*******************************************************************************
@@ -359,7 +360,12 @@ static void bta_ag_cback_sco(tBTA_AG_SCB* p_scb, tBTA_AG_EVT event) {
*
******************************************************************************/
static void bta_ag_create_sco(tBTA_AG_SCB* p_scb, bool is_orig) {
- LOG_DEBUG("BEFORE %s", p_scb->ToString().c_str());
+ APPL_TRACE_DEBUG(
+ "%s: BEFORE codec_updated=%d, codec_fallback=%d, "
+ "sco_codec=%d, peer_codec=%d, msbc_settings=%d, device=%s",
+ __func__, p_scb->codec_updated, p_scb->codec_fallback, p_scb->sco_codec,
+ p_scb->peer_codecs, p_scb->codec_msbc_settings,
+ p_scb->peer_addr.ToString().c_str());
tBTA_AG_PEER_CODEC esco_codec = BTA_AG_CODEC_CVSD;
if (!bta_ag_sco_is_active_device(p_scb->peer_addr)) {
@@ -393,24 +399,29 @@ static void bta_ag_create_sco(tBTA_AG_SCB* p_scb, bool is_orig) {
p_scb->codec_msbc_settings = BTA_AG_SCO_MSBC_SETTINGS_T2;
}
- /* Initialize eSCO parameters */
- enh_esco_params_t params = {};
+ esco_codec_t codec_index = ESCO_CODEC_CVSD;
/* If WBS included, use CVSD by default, index is 0 for CVSD by
* initialization. If eSCO codec is mSBC, index is T2 or T1 */
if (esco_codec == BTA_AG_CODEC_MSBC) {
if (p_scb->codec_msbc_settings == BTA_AG_SCO_MSBC_SETTINGS_T2) {
- params = esco_parameters_for_codec(ESCO_CODEC_MSBC_T2);
+ codec_index = ESCO_CODEC_MSBC_T2;
} else {
- params = esco_parameters_for_codec(ESCO_CODEC_MSBC_T1);
+ codec_index = ESCO_CODEC_MSBC_T1;
}
- } else {
- if (p_scb->features & BTA_AG_PEER_FEAT_ESCO_S4 &&
- (p_scb->peer_features & BTA_AG_PEER_FEAT_ESCO_S4)) {
- // HFP >=1.7 eSCO
- params = esco_parameters_for_codec(ESCO_CODEC_CVSD_S4);
- } else {
- // HFP <=1.6 eSCO
- params = esco_parameters_for_codec(ESCO_CODEC_CVSD_S3);
+ }
+
+ /* Initialize eSCO parameters */
+ enh_esco_params_t params = esco_parameters_for_codec(codec_index);
+ /* For CVSD */
+ if (esco_codec == BTM_SCO_CODEC_CVSD) {
+ /* Use the applicable packet types
+ (3-EV3 not allowed due to errata 2363) */
+ params.packet_types =
+ p_bta_ag_cfg->sco_pkt_types | ESCO_PKT_TYPES_MASK_NO_3_EV3;
+ if ((!(p_scb->features & BTA_AG_FEAT_ESCO)) ||
+ (!(p_scb->peer_features & BTA_AG_PEER_FEAT_ESCO))) {
+ params.max_latency_ms = 10;
+ params.retransmission_effort = ESCO_RETRANSMISSION_POWER;
}
}
@@ -428,21 +439,27 @@ static void bta_ag_create_sco(tBTA_AG_SCB* p_scb, bool is_orig) {
/* Send pending commands to create SCO connection to peer */
bta_ag_create_pending_sco(p_scb, bta_ag_cb.sco.is_local);
- LOG_DEBUG("Initiating AG SCO inx 0x%04x, pkt types 0x%04x", p_scb->sco_idx,
- params.packet_types);
+ APPL_TRACE_API("%s: orig %d, inx 0x%04x, pkt types 0x%04x", __func__,
+ is_orig, p_scb->sco_idx, params.packet_types);
} else {
/* Not initiating, go to listen mode */
- tBTM_STATUS btm_status = BTM_CreateSco(
+ tBTM_STATUS status = BTM_CreateSco(
&p_scb->peer_addr, false, params.packet_types, &p_scb->sco_idx,
bta_ag_sco_conn_cback, bta_ag_sco_disc_cback);
- if (btm_status == BTM_CMD_STARTED) {
+ if (status == BTM_CMD_STARTED) {
BTM_RegForEScoEvts(p_scb->sco_idx, bta_ag_esco_connreq_cback);
}
- LOG_DEBUG("Listening AG SCO inx 0x%04x status:%s pkt types 0x%04x",
- p_scb->sco_idx, btm_status_text(btm_status).c_str(),
- params.packet_types);
+
+ APPL_TRACE_API("%s: orig %d, inx 0x%04x, status 0x%x, pkt types 0x%04x",
+ __func__, is_orig, p_scb->sco_idx, status,
+ params.packet_types);
}
- LOG_DEBUG("AFTER %s", p_scb->ToString().c_str());
+ APPL_TRACE_DEBUG(
+ "%s: AFTER codec_updated=%d, codec_fallback=%d, "
+ "sco_codec=%d, peer_codec=%d, msbc_settings=%d, device=%s",
+ __func__, p_scb->codec_updated, p_scb->codec_fallback, p_scb->sco_codec,
+ p_scb->peer_codecs, p_scb->codec_msbc_settings,
+ p_scb->peer_addr.ToString().c_str());
}
/*******************************************************************************
@@ -468,17 +485,14 @@ static void bta_ag_create_pending_sco(tBTA_AG_SCB* p_scb, bool is_local) {
if (esco_codec == BTA_AG_CODEC_MSBC) {
if (p_scb->codec_msbc_settings == BTA_AG_SCO_MSBC_SETTINGS_T2) {
params = esco_parameters_for_codec(ESCO_CODEC_MSBC_T2);
- } else {
+ } else
params = esco_parameters_for_codec(ESCO_CODEC_MSBC_T1);
- }
} else {
- if (p_scb->features & BTA_AG_PEER_FEAT_ESCO_S4 &&
- (p_scb->peer_features & BTA_AG_PEER_FEAT_ESCO_S4)) {
- // HFP >=1.7 eSCO
- params = esco_parameters_for_codec(ESCO_CODEC_CVSD_S4);
- } else {
- // HFP <=1.6 eSCO
- params = esco_parameters_for_codec(ESCO_CODEC_CVSD_S3);
+ params = esco_parameters_for_codec(ESCO_CODEC_CVSD);
+ if ((!(p_scb->features & BTA_AG_FEAT_ESCO)) ||
+ (!(p_scb->peer_features & BTA_AG_PEER_FEAT_ESCO))) {
+ params.max_latency_ms = 10;
+ params.retransmission_effort = ESCO_RETRANSMISSION_POWER;
}
}
@@ -500,18 +514,12 @@ static void bta_ag_create_pending_sco(tBTA_AG_SCB* p_scb, bool is_local) {
}
APPL_TRACE_DEBUG("%s: initiated SCO connection", __func__);
} else {
- // Local device accepted SCO connection from peer(HF)
- // Because HF devices usually do not send AT+BAC and +BCS command,
- // and there is no plan to implement corresponding command handlers,
- // so we only accept CVSD connection from HF no matter what's
- // requested.
- if (p_scb->features & BTA_AG_PEER_FEAT_ESCO_S4 &&
- (p_scb->peer_features & BTA_AG_PEER_FEAT_ESCO_S4)) {
- // HFP >=1.7 eSCO
- params = esco_parameters_for_codec(ESCO_CODEC_CVSD_S4);
- } else {
- // HFP <=1.6 eSCO
- params = esco_parameters_for_codec(ESCO_CODEC_CVSD_S3);
+ /* Local device accepted SCO connection from peer */
+ params = esco_parameters_for_codec(ESCO_CODEC_CVSD);
+ if ((!(p_scb->features & BTA_AG_FEAT_ESCO)) ||
+ (!(p_scb->peer_features & BTA_AG_PEER_FEAT_ESCO))) {
+ params.max_latency_ms = 10;
+ params.retransmission_effort = ESCO_RETRANSMISSION_POWER;
}
BTM_EScoConnRsp(p_scb->sco_idx, HCI_SUCCESS, &params);
@@ -530,7 +538,7 @@ static void bta_ag_create_pending_sco(tBTA_AG_SCB* p_scb, bool is_local) {
*
******************************************************************************/
static void bta_ag_codec_negotiation_timer_cback(void* data) {
- LOG_WARN("Codec negotiation timeout");
+ APPL_TRACE_DEBUG("%s", __func__);
tBTA_AG_SCB* p_scb = (tBTA_AG_SCB*)data;
/* Announce that codec negotiation failed. */
@@ -551,12 +559,14 @@ static void bta_ag_codec_negotiation_timer_cback(void* data) {
*
******************************************************************************/
void bta_ag_codec_negotiate(tBTA_AG_SCB* p_scb) {
+ APPL_TRACE_DEBUG("%s", __func__);
bta_ag_cb.sco.p_curr_scb = p_scb;
uint8_t* p_rem_feat = BTM_ReadRemoteFeatures(p_scb->peer_addr);
bool sdp_wbs_support = p_scb->peer_sdp_features & BTA_AG_FEAT_WBS_SUPPORT;
if (p_rem_feat == nullptr) {
- LOG_WARN("Skip codec negotiation, failed to read remote features");
+ LOG(WARNING) << __func__
+ << ": Fail to read remote feature, skip codec negotiation";
bta_ag_sco_codec_nego(p_scb, false);
return;
}
@@ -572,13 +582,11 @@ void bta_ag_codec_negotiate(tBTA_AG_SCB* p_scb) {
// SCO setup fail by Firmware reject.
if (!HCI_LMP_TRANSPNT_SUPPORTED(p_rem_feat) || !sdp_wbs_support ||
!(p_scb->peer_features & BTA_AG_PEER_FEAT_CODEC)) {
- LOG_INFO("Assume CVSD by default due to mask mismatch");
p_scb->sco_codec = UUID_CODEC_CVSD;
}
if ((p_scb->codec_updated || p_scb->codec_fallback) &&
(p_scb->peer_features & BTA_AG_PEER_FEAT_CODEC)) {
- LOG_INFO("Starting codec negotiation");
/* Change the power mode to Active until SCO open is completed. */
bta_sys_busy(BTA_ID_AG, p_scb->app_id, p_scb->peer_addr);
@@ -591,18 +599,31 @@ void bta_ag_codec_negotiate(tBTA_AG_SCB* p_scb) {
bta_ag_codec_negotiation_timer_cback, p_scb);
} else {
/* use same codec type as previous SCO connection, skip codec negotiation */
- LOG_INFO("Skip codec negotiation, using the same codec");
+ APPL_TRACE_DEBUG(
+ "use same codec type as previous SCO connection,skip codec "
+ "negotiation");
bta_ag_sco_codec_nego(p_scb, true);
}
}
+/*******************************************************************************
+ *
+ * Function bta_ag_sco_event
+ *
+ * Description
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
tBTA_AG_SCO_CB* p_sco = &bta_ag_cb.sco;
uint8_t previous_state = p_sco->state;
- LOG_INFO("device:%s index:0x%04x state:%s[%d] event:%s[%d]",
- PRIVATE_ADDRESS(p_scb->peer_addr), p_scb->sco_idx,
- bta_ag_sco_state_str(p_sco->state), p_sco->state,
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_EVENT("%s: index=0x%04x, device=%s, state=%s[%d], event=%s[%d]",
+ __func__, p_scb->sco_idx,
+ p_scb->peer_addr.ToString().c_str(),
+ bta_ag_sco_state_str(p_sco->state), p_sco->state,
+ bta_ag_sco_evt_str(event), event);
switch (p_sco->state) {
case BTA_AG_SCO_SHUTDOWN_ST:
@@ -614,8 +635,9 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
break;
default:
- LOG_WARN("BTA_AG_SCO_SHUTDOWN_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_WARNING(
+ "%s: BTA_AG_SCO_SHUTDOWN_ST: Ignoring event %s[%d]", __func__,
+ bta_ag_sco_evt_str(event), event);
break;
}
break;
@@ -655,9 +677,10 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
case BTA_AG_SCO_CLOSE_E:
/* remove listening connection */
- /* Ignore the event. Keep listening SCO for the active SLC */
- LOG_WARN("BTA_AG_SCO_LISTEN_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ /* Ignore the event. Keep listening SCO for the active SLC
+ */
+ APPL_TRACE_WARNING("%s: BTA_AG_SCO_LISTEN_ST: Ignoring event %s[%d]",
+ __func__, bta_ag_sco_evt_str(event), event);
break;
case BTA_AG_SCO_CONN_CLOSE_E:
@@ -667,8 +690,8 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
break;
default:
- LOG_WARN("BTA_AG_SCO_LISTEN_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_WARNING("%s: BTA_AG_SCO_LISTEN_ST: Ignoring event %s[%d]",
+ __func__, bta_ag_sco_evt_str(event), event);
break;
}
break;
@@ -716,8 +739,8 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
break;
default:
- LOG_WARN("BTA_AG_SCO_CODEC_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_WARNING("%s: BTA_AG_SCO_CODEC_ST: Ignoring event %s[%d]",
+ __func__, bta_ag_sco_evt_str(event), event);
break;
}
break;
@@ -771,8 +794,8 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
break;
default:
- LOG_WARN("BTA_AG_SCO_OPENING_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_WARNING("%s: BTA_AG_SCO_OPENING_ST: Ignoring event %s[%d]",
+ __func__, bta_ag_sco_evt_str(event), event);
break;
}
break;
@@ -814,8 +837,8 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
break;
default:
- LOG_WARN("BTA_AG_SCO_OPEN_CL_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_WARNING("%s: BTA_AG_SCO_OPEN_CL_ST: Ignoring event %s[%d]",
+ __func__, bta_ag_sco_evt_str(event), event);
break;
}
break;
@@ -850,8 +873,9 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
break;
default:
- LOG_WARN("BTA_AG_SCO_OPEN_XFER_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_WARNING(
+ "%s: BTA_AG_SCO_OPEN_XFER_ST: Ignoring event %s[%d]", __func__,
+ bta_ag_sco_evt_str(event), event);
break;
}
break;
@@ -900,8 +924,8 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
break;
default:
- LOG_WARN("BTA_AG_SCO_OPEN_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_WARNING("%s: BTA_AG_SCO_OPEN_ST: Ignoring event %s[%d]",
+ __func__, bta_ag_sco_evt_str(event), event);
break;
}
break;
@@ -944,8 +968,8 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
break;
default:
- LOG_WARN("BTA_AG_SCO_CLOSING_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_WARNING("%s: BTA_AG_SCO_CLOSING_ST: Ignoring event %s[%d]",
+ __func__, bta_ag_sco_evt_str(event), event);
break;
}
break;
@@ -974,8 +998,9 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
break;
default:
- LOG_WARN("BTA_AG_SCO_CLOSE_OP_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_WARNING(
+ "%s: BTA_AG_SCO_CLOSE_OP_ST: Ignoring event %s[%d]", __func__,
+ bta_ag_sco_evt_str(event), event);
break;
}
break;
@@ -1025,8 +1050,9 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
}
default:
- LOG_WARN(" BTA_AG_SCO_CLOSE_XFER_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_WARNING(
+ "%s: BTA_AG_SCO_CLOSE_XFER_ST: Ignoring event %s[%d]", __func__,
+ bta_ag_sco_evt_str(event), event);
break;
}
break;
@@ -1082,8 +1108,9 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
break;
default:
- LOG_WARN("BTA_AG_SCO_SHUTTING_ST: Ignoring event %s[%d]",
- bta_ag_sco_evt_str(event), event);
+ APPL_TRACE_WARNING(
+ "%s: BTA_AG_SCO_SHUTTING_ST: Ignoring event %s[%d]", __func__,
+ bta_ag_sco_evt_str(event), event);
break;
}
break;
@@ -1092,10 +1119,10 @@ static void bta_ag_sco_event(tBTA_AG_SCB* p_scb, uint8_t event) {
break;
}
if (p_sco->state != previous_state) {
- LOG_WARN(
- "SCO_state_change: [%s(0x%02x)]->[%s(0x%02x)] "
+ APPL_TRACE_EVENT(
+ "%s: SCO_state_change: [%s(0x%02x)]->[%s(0x%02x)] "
"after event [%s(0x%02x)]",
- bta_ag_sco_state_str(previous_state), previous_state,
+ __func__, bta_ag_sco_state_str(previous_state), previous_state,
bta_ag_sco_state_str(p_sco->state), p_sco->state,
bta_ag_sco_evt_str(event), event);
}
@@ -1165,9 +1192,8 @@ void bta_ag_sco_open(tBTA_AG_SCB* p_scb, UNUSED_ATTR const tBTA_AG_DATA& data) {
}
/* if another scb using sco, this is a transfer */
if (bta_ag_cb.sco.p_curr_scb && bta_ag_cb.sco.p_curr_scb != p_scb) {
- LOG(INFO) << __func__ << ": transfer "
- << bta_ag_cb.sco.p_curr_scb->peer_addr << " -> "
- << p_scb->peer_addr;
+ LOG(INFO) << __func__ << ": tranfer " << bta_ag_cb.sco.p_curr_scb->peer_addr
+ << " -> " << p_scb->peer_addr;
bta_ag_sco_event(p_scb, BTA_AG_SCO_XFER_E);
} else {
/* else it is an open */
@@ -1211,14 +1237,14 @@ void bta_ag_sco_close(tBTA_AG_SCB* p_scb,
void bta_ag_sco_codec_nego(tBTA_AG_SCB* p_scb, bool result) {
if (result) {
/* Subsequent SCO connection will skip codec negotiation */
- LOG_INFO("Succeeded for index 0x%04x, device %s", p_scb->sco_idx,
- p_scb->peer_addr.ToString().c_str());
+ APPL_TRACE_DEBUG("%s: Succeeded for index 0x%04x, device %s", __func__,
+ p_scb->sco_idx, p_scb->peer_addr.ToString().c_str());
p_scb->codec_updated = false;
bta_ag_sco_event(p_scb, BTA_AG_SCO_CN_DONE_E);
} else {
/* codec negotiation failed */
- LOG_INFO("Failed for index 0x%04x, device %s", p_scb->sco_idx,
- p_scb->peer_addr.ToString().c_str());
+ APPL_TRACE_ERROR("%s: Failed for index 0x%04x, device %s", __func__,
+ p_scb->sco_idx, p_scb->peer_addr.ToString().c_str());
bta_ag_sco_event(p_scb, BTA_AG_SCO_CLOSE_E);
}
}
diff --git a/bta/ag/bta_ag_sdp.cc b/bta/ag/bta_ag_sdp.cc
index a37a7c8ab..dd9ec3c8c 100644
--- a/bta/ag/bta_ag_sdp.cc
+++ b/bta/ag/bta_ag_sdp.cc
@@ -23,18 +23,22 @@
*
******************************************************************************/
-#include <base/bind.h>
-#include <base/location.h>
+#include <cstring>
-#include "bt_target.h" // Legacy stack config
-#include "bt_trace.h" // Legacy trace logging
+#include <base/bind.h>
-#include "bta/ag/bta_ag_int.h"
-#include "btif/include/btif_config.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "stack/include/port_api.h"
-#include "types/bluetooth/uuid.h"
+#include "bt_common.h"
+#include "bta_ag_api.h"
+#include "bta_ag_int.h"
+#include "bta_api.h"
+#include "bta_sys.h"
+#include "btif_config.h"
+#include "btm_api.h"
+#include "osi/include/log.h"
+#include "osi/include/osi.h"
+#include "sdp_api.h"
+#include "stack/include/btu.h"
+#include "utl.h"
using bluetooth::Uuid;
@@ -50,12 +54,12 @@ using bluetooth::Uuid;
#endif
/* declare sdp callback functions */
-void bta_ag_sdp_cback_1(tSDP_RESULT);
-void bta_ag_sdp_cback_2(tSDP_RESULT);
-void bta_ag_sdp_cback_3(tSDP_RESULT);
-void bta_ag_sdp_cback_4(tSDP_RESULT);
-void bta_ag_sdp_cback_5(tSDP_RESULT);
-void bta_ag_sdp_cback_6(tSDP_RESULT);
+void bta_ag_sdp_cback_1(uint16_t status);
+void bta_ag_sdp_cback_2(uint16_t status);
+void bta_ag_sdp_cback_3(uint16_t status);
+void bta_ag_sdp_cback_4(uint16_t status);
+void bta_ag_sdp_cback_5(uint16_t status);
+void bta_ag_sdp_cback_6(uint16_t status);
/* SDP callback function table */
typedef tSDP_DISC_CMPL_CB* tBTA_AG_SDP_CBACK;
@@ -102,12 +106,12 @@ static void bta_ag_sdp_cback(uint16_t status, uint8_t idx) {
* Returns void
*
******************************************************************************/
-void bta_ag_sdp_cback_1(tSDP_STATUS status) { bta_ag_sdp_cback(status, 1); }
-void bta_ag_sdp_cback_2(tSDP_STATUS status) { bta_ag_sdp_cback(status, 2); }
-void bta_ag_sdp_cback_3(tSDP_STATUS status) { bta_ag_sdp_cback(status, 3); }
-void bta_ag_sdp_cback_4(tSDP_STATUS status) { bta_ag_sdp_cback(status, 4); }
-void bta_ag_sdp_cback_5(tSDP_STATUS status) { bta_ag_sdp_cback(status, 5); }
-void bta_ag_sdp_cback_6(tSDP_STATUS status) { bta_ag_sdp_cback(status, 6); }
+void bta_ag_sdp_cback_1(uint16_t status) { bta_ag_sdp_cback(status, 1); }
+void bta_ag_sdp_cback_2(uint16_t status) { bta_ag_sdp_cback(status, 2); }
+void bta_ag_sdp_cback_3(uint16_t status) { bta_ag_sdp_cback(status, 3); }
+void bta_ag_sdp_cback_4(uint16_t status) { bta_ag_sdp_cback(status, 4); }
+void bta_ag_sdp_cback_5(uint16_t status) { bta_ag_sdp_cback(status, 5); }
+void bta_ag_sdp_cback_6(uint16_t status) { bta_ag_sdp_cback(status, 6); }
/******************************************************************************
*
@@ -269,7 +273,7 @@ void bta_ag_del_records(tBTA_AG_SCB* p_scb) {
bta_ag_cb.profile[i].sdp_handle = 0;
}
BTM_FreeSCN(bta_ag_cb.profile[i].scn);
- RFCOMM_ClearSecurityRecord(bta_ag_cb.profile[i].scn);
+ BTM_SecClrService(bta_ag_sec_id[i]);
bta_sys_remove_uuid(bta_ag_uuid[i]);
}
}
@@ -476,7 +480,7 @@ void bta_ag_do_disc(tBTA_AG_SCB* p_scb, tBTA_SERVICE_MASK service) {
if (p_scb->p_disc_db != nullptr) {
android_errorWriteLog(0x534e4554, "174052148");
- LOG_ERROR("Discovery already in progress... returning.");
+ APPL_TRACE_ERROR("Discovery already in progress... returning.");
return;
}
diff --git a/bta/ar/bta_ar.cc b/bta/ar/bta_ar.cc
index 4dda718c5..8e02aa45b 100644
--- a/bta/ar/bta_ar.cc
+++ b/bta/ar/bta_ar.cc
@@ -22,18 +22,36 @@
*
******************************************************************************/
-#include <cstdint>
+#include <string.h>
-#include "bta/ar/bta_ar_int.h"
-#include "bta/sys/bta_sys.h"
-#include "stack/include/avct_api.h"
-#include "stack/include/avrc_api.h"
+#include "bta_ar_api.h"
+#include "bta_ar_int.h"
/* AV control block */
tBTA_AR_CB bta_ar_cb;
/*******************************************************************************
*
+ * Function bta_ar_id
+ *
+ * Description This function maps sys_id to ar id mask.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static uint8_t bta_ar_id(tBTA_SYS_ID sys_id) {
+ uint8_t mask = 0;
+ if (sys_id == BTA_ID_AV) {
+ mask = BTA_AR_AV_MASK;
+ } else if (sys_id == BTA_ID_AVK) {
+ mask = BTA_AR_AVK_MASK;
+ }
+
+ return mask;
+}
+
+/*******************************************************************************
+ *
* Function bta_ar_init
*
* Description This function is called to register to AVDTP.
@@ -61,6 +79,8 @@ static void bta_ar_avdt_cback(uint8_t handle, const RawAddress& bd_addr,
/* route the AVDT registration callback to av or avk */
if (bta_ar_cb.p_av_conn_cback)
(*bta_ar_cb.p_av_conn_cback)(handle, bd_addr, event, p_data, scb_index);
+ if (bta_ar_cb.p_avk_conn_cback)
+ (*bta_ar_cb.p_avk_conn_cback)(handle, bd_addr, event, p_data, scb_index);
}
/*******************************************************************************
@@ -72,15 +92,30 @@ static void bta_ar_avdt_cback(uint8_t handle, const RawAddress& bd_addr,
* Returns void
*
******************************************************************************/
-void bta_ar_reg_avdt(AvdtpRcb* p_reg, tAVDT_CTRL_CBACK* p_cback) {
- bta_ar_cb.p_av_conn_cback = p_cback;
- if (bta_ar_cb.avdt_registered == 0) {
- AVDT_Register(p_reg, bta_ar_avdt_cback);
+void bta_ar_reg_avdt(AvdtpRcb* p_reg, tAVDT_CTRL_CBACK* p_cback,
+ tBTA_SYS_ID sys_id) {
+ uint8_t mask = 0;
+
+ if (sys_id == BTA_ID_AV) {
+ bta_ar_cb.p_av_conn_cback = p_cback;
+ mask = BTA_AR_AV_MASK;
+ } else if (sys_id == BTA_ID_AVK) {
+ bta_ar_cb.p_avk_conn_cback = p_cback;
+ mask = BTA_AR_AVK_MASK;
} else {
- APPL_TRACE_WARNING("%s: doesn't register again (registered:%d)", __func__,
- bta_ar_cb.avdt_registered);
+ APPL_TRACE_ERROR("%s: the registration is from wrong sys_id:%d", __func__,
+ sys_id);
+ }
+
+ if (mask) {
+ if (bta_ar_cb.avdt_registered == 0) {
+ AVDT_Register(p_reg, bta_ar_avdt_cback);
+ } else {
+ APPL_TRACE_WARNING("%s: sys_id:%d doesn't register again (registered:%d)",
+ __func__, sys_id, bta_ar_cb.avdt_registered);
+ }
+ bta_ar_cb.avdt_registered |= mask;
}
- bta_ar_cb.avdt_registered |= BTA_AR_AV_MASK;
}
/*******************************************************************************
@@ -92,9 +127,17 @@ void bta_ar_reg_avdt(AvdtpRcb* p_reg, tAVDT_CTRL_CBACK* p_cback) {
* Returns void
*
******************************************************************************/
-void bta_ar_dereg_avdt() {
- bta_ar_cb.p_av_conn_cback = NULL;
- bta_ar_cb.avdt_registered &= ~BTA_AR_AV_MASK;
+void bta_ar_dereg_avdt(tBTA_SYS_ID sys_id) {
+ uint8_t mask = 0;
+
+ if (sys_id == BTA_ID_AV) {
+ bta_ar_cb.p_av_conn_cback = NULL;
+ mask = BTA_AR_AV_MASK;
+ } else if (sys_id == BTA_ID_AVK) {
+ bta_ar_cb.p_avk_conn_cback = NULL;
+ mask = BTA_AR_AVK_MASK;
+ }
+ bta_ar_cb.avdt_registered &= ~mask;
if (bta_ar_cb.avdt_registered == 0) AVDT_Deregister();
}
@@ -113,6 +156,18 @@ void bta_ar_dereg_avdt() {
******************************************************************************/
void bta_ar_avdt_conn(tBTA_SYS_ID sys_id, const RawAddress& bd_addr,
uint8_t scb_index) {
+ uint8_t event = BTA_AR_AVDT_CONN_EVT;
+ tAVDT_CTRL data;
+
+ if (sys_id == BTA_ID_AV) {
+ if (bta_ar_cb.p_avk_conn_cback) {
+ (*bta_ar_cb.p_avk_conn_cback)(0, bd_addr, event, &data, scb_index);
+ }
+ } else if (sys_id == BTA_ID_AVK) {
+ if (bta_ar_cb.p_av_conn_cback) {
+ (*bta_ar_cb.p_av_conn_cback)(0, bd_addr, event, &data, scb_index);
+ }
+ }
}
/*******************************************************************************
@@ -124,11 +179,16 @@ void bta_ar_avdt_conn(tBTA_SYS_ID sys_id, const RawAddress& bd_addr,
* Returns void
*
******************************************************************************/
-void bta_ar_reg_avct() {
- if (bta_ar_cb.avct_registered == 0) {
- AVCT_Register();
+void bta_ar_reg_avct(uint16_t mtu, uint16_t mtu_br, uint8_t sec_mask,
+ tBTA_SYS_ID sys_id) {
+ uint8_t mask = bta_ar_id(sys_id);
+
+ if (mask) {
+ if (bta_ar_cb.avct_registered == 0) {
+ AVCT_Register(mtu, mtu_br, sec_mask);
+ }
+ bta_ar_cb.avct_registered |= mask;
}
- bta_ar_cb.avct_registered |= BTA_AR_AV_MASK;
}
/*******************************************************************************
@@ -140,8 +200,10 @@ void bta_ar_reg_avct() {
* Returns void
*
******************************************************************************/
-void bta_ar_dereg_avct() {
- bta_ar_cb.avct_registered &= ~BTA_AR_AV_MASK;
+void bta_ar_dereg_avct(tBTA_SYS_ID sys_id) {
+ uint8_t mask = bta_ar_id(sys_id);
+
+ bta_ar_cb.avct_registered &= ~mask;
if (bta_ar_cb.avct_registered == 0) AVCT_Deregister();
}
@@ -157,11 +219,12 @@ void bta_ar_dereg_avct() {
*****************************************************************************/
void bta_ar_reg_avrc(uint16_t service_uuid, const char* service_name,
const char* provider_name, uint16_t categories,
- bool browse_supported, uint16_t profile_version) {
- uint8_t mask = BTA_AR_AV_MASK;
+ tBTA_SYS_ID sys_id, bool browse_supported,
+ uint16_t profile_version) {
+ uint8_t mask = bta_ar_id(sys_id);
uint8_t temp[8], *p;
- if (!categories) return;
+ if (!mask || !categories) return;
if (service_uuid == UUID_SERVCLASS_AV_REM_CTRL_TARGET) {
if (bta_ar_cb.sdp_tg_handle == 0) {
@@ -169,7 +232,7 @@ void bta_ar_reg_avrc(uint16_t service_uuid, const char* service_name,
bta_ar_cb.sdp_tg_handle = SDP_CreateRecord();
AVRC_AddRecord(service_uuid, service_name, provider_name, categories,
bta_ar_cb.sdp_tg_handle, browse_supported,
- profile_version, 0);
+ profile_version);
bta_sys_add_uuid(service_uuid);
}
/* only one TG is allowed (first-come, first-served).
@@ -182,7 +245,7 @@ void bta_ar_reg_avrc(uint16_t service_uuid, const char* service_name,
bta_ar_cb.sdp_ct_handle = SDP_CreateRecord();
AVRC_AddRecord(service_uuid, service_name, provider_name, categories,
bta_ar_cb.sdp_ct_handle, browse_supported,
- profile_version, 0);
+ profile_version);
bta_sys_add_uuid(service_uuid);
} else {
/* multiple CTs are allowed.
@@ -205,11 +268,13 @@ void bta_ar_reg_avrc(uint16_t service_uuid, const char* service_name,
* Returns void
*
*****************************************************************************/
-void bta_ar_dereg_avrc(uint16_t service_uuid) {
- uint8_t mask = BTA_AR_AV_MASK;
+void bta_ar_dereg_avrc(uint16_t service_uuid, tBTA_SYS_ID sys_id) {
+ uint8_t mask = bta_ar_id(sys_id);
uint16_t categories = 0;
uint8_t temp[8], *p;
+ if (!mask) return;
+
if (service_uuid == UUID_SERVCLASS_AV_REM_CTRL_TARGET) {
if (bta_ar_cb.sdp_tg_handle && mask == bta_ar_cb.tg_registered) {
bta_ar_cb.tg_registered = 0;
diff --git a/bta/ar/bta_ar_int.h b/bta/ar/bta_ar_int.h
index c2676a7d6..320fee979 100644
--- a/bta/ar/bta_ar_int.h
+++ b/bta/ar/bta_ar_int.h
@@ -25,10 +25,7 @@
#ifndef BTA_AR_INT_H
#define BTA_AR_INT_H
-#include <cstdint>
-
-#include "bta/include/bta_av_api.h"
-#include "stack/include/avdt_api.h"
+#include "bta_av_api.h"
#define BTA_AR_AV_MASK 0x01
#define BTA_AR_AVK_MASK 0x02
@@ -36,6 +33,7 @@
/* data associated with BTA_AR */
typedef struct {
tAVDT_CTRL_CBACK* p_av_conn_cback; /* av connection callback function */
+ tAVDT_CTRL_CBACK* p_avk_conn_cback; /* avk connection callback function */
uint8_t avdt_registered;
uint8_t avct_registered;
uint32_t sdp_tg_handle;
diff --git a/bta/av/bta_av_aact.cc b/bta/av/bta_av_aact.cc
index 5c78afb67..29dcea07b 100644
--- a/bta/av/bta_av_aact.cc
+++ b/bta/av/bta_av_aact.cc
@@ -26,37 +26,34 @@
#define LOG_TAG "bt_bta_av"
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <cstring>
-#include <vector>
+#include "bt_target.h"
-#include "bt_target.h" // Must be first to define build configuration
+#include <base/logging.h>
+#include <string.h>
+#include <vector>
-#include "bta/av/bta_av_int.h"
-#include "bta/include/bta_ar_api.h"
-#include "bta/include/bta_av_co.h"
-#include "btif/avrcp/avrcp_service.h"
+#include "a2dp_sbc.h"
+#include "avdt_api.h"
+#include "avrcp_service.h"
+#include "bt_utils.h"
+#include "bta_av_int.h"
#include "btif/include/btif_av_co.h"
#include "btif/include/btif_config.h"
#include "btif/include/btif_storage.h"
+#include "btm_int.h"
+#include "device/include/controller.h"
#include "device/include/interop.h"
-#include "main/shim/dumpsys.h"
+#include "l2c_api.h"
+#include "l2cdefs.h"
#include "osi/include/log.h"
#include "osi/include/osi.h"
#include "osi/include/properties.h"
-#include "stack/include/a2dp_sbc.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_client_interface.h"
-#include "stack/include/l2c_api.h"
-#include "types/hci_role.h"
-
-namespace {
-
-constexpr char kBtmLogTag[] = "A2DP";
-
-}
+#include "utl.h"
+#if (BTA_AR_INCLUDED == TRUE)
+#include "bta_ar_api.h"
+#endif
+#include "btif/include/btif_av.h"
+#include "btif/include/btif_hf.h"
/*****************************************************************************
* Constants
@@ -82,8 +79,12 @@ constexpr char kBtmLogTag[] = "A2DP";
/* ACL quota we are letting FW use for A2DP Offload Tx. */
#define BTA_AV_A2DP_OFFLOAD_XMIT_QUOTA 4
+#define BTIF_A2DP_MAX_BITPOOL_MQ 35
+
static void bta_av_offload_codec_builder(tBTA_AV_SCB* p_scb,
tBT_A2DP_OFFLOAD* p_a2dp_offload);
+static void bta_av_st_rc_timer(tBTA_AV_SCB* p_scb,
+ UNUSED_ATTR tBTA_AV_DATA* p_data);
/* state machine states */
enum {
@@ -107,7 +108,61 @@ const tBTA_AV_CO_FUNCTS bta_av_a2dp_cos = {bta_av_co_audio_init,
bta_av_co_audio_source_data_path,
bta_av_co_audio_delay,
bta_av_co_audio_update_mtu,
- bta_av_co_get_scmst_info};
+ bta_av_co_content_protect_is_active};
+
+/* ssm action functions for audio stream */
+const tBTA_AV_SACT bta_av_a2dp_action[] = {
+ bta_av_do_disc_a2dp, /* BTA_AV_DO_DISC */
+ bta_av_cleanup, /* BTA_AV_CLEANUP */
+ bta_av_free_sdb, /* BTA_AV_FREE_SDB */
+ bta_av_config_ind, /* BTA_AV_CONFIG_IND */
+ bta_av_disconnect_req, /* BTA_AV_DISCONNECT_REQ */
+ bta_av_security_req, /* BTA_AV_SECURITY_REQ */
+ bta_av_security_rsp, /* BTA_AV_SECURITY_RSP */
+ bta_av_setconfig_rsp, /* BTA_AV_SETCONFIG_RSP */
+ bta_av_st_rc_timer, /* BTA_AV_ST_RC_TIMER */
+ bta_av_str_opened, /* BTA_AV_STR_OPENED */
+ bta_av_security_ind, /* BTA_AV_SECURITY_IND */
+ bta_av_security_cfm, /* BTA_AV_SECURITY_CFM */
+ bta_av_do_close, /* BTA_AV_DO_CLOSE */
+ bta_av_connect_req, /* BTA_AV_CONNECT_REQ */
+ bta_av_sdp_failed, /* BTA_AV_SDP_FAILED */
+ bta_av_disc_results, /* BTA_AV_DISC_RESULTS */
+ bta_av_disc_res_as_acp, /* BTA_AV_DISC_RES_AS_ACP */
+ bta_av_open_failed, /* BTA_AV_OPEN_FAILED */
+ bta_av_getcap_results, /* BTA_AV_GETCAP_RESULTS */
+ bta_av_setconfig_rej, /* BTA_AV_SETCONFIG_REJ */
+ bta_av_discover_req, /* BTA_AV_DISCOVER_REQ */
+ bta_av_conn_failed, /* BTA_AV_CONN_FAILED */
+ bta_av_do_start, /* BTA_AV_DO_START */
+ bta_av_str_stopped, /* BTA_AV_STR_STOPPED */
+ bta_av_reconfig, /* BTA_AV_RECONFIG */
+ bta_av_data_path, /* BTA_AV_DATA_PATH */
+ bta_av_start_ok, /* BTA_AV_START_OK */
+ bta_av_start_failed, /* BTA_AV_START_FAILED */
+ bta_av_str_closed, /* BTA_AV_STR_CLOSED */
+ bta_av_clr_cong, /* BTA_AV_CLR_CONG */
+ bta_av_suspend_cfm, /* BTA_AV_SUSPEND_CFM */
+ bta_av_rcfg_str_ok, /* BTA_AV_RCFG_STR_OK */
+ bta_av_rcfg_failed, /* BTA_AV_RCFG_FAILED */
+ bta_av_rcfg_connect, /* BTA_AV_RCFG_CONNECT */
+ bta_av_rcfg_discntd, /* BTA_AV_RCFG_DISCNTD */
+ bta_av_suspend_cont, /* BTA_AV_SUSPEND_CONT */
+ bta_av_rcfg_cfm, /* BTA_AV_RCFG_CFM */
+ bta_av_rcfg_open, /* BTA_AV_RCFG_OPEN */
+ bta_av_security_rej, /* BTA_AV_SECURITY_REJ */
+ bta_av_open_rc, /* BTA_AV_OPEN_RC */
+ bta_av_chk_2nd_start, /* BTA_AV_CHK_2ND_START */
+ bta_av_save_caps, /* BTA_AV_SAVE_CAPS */
+ bta_av_set_use_rc, /* BTA_AV_SET_USE_RC */
+ bta_av_cco_close, /* BTA_AV_CCO_CLOSE */
+ bta_av_switch_role, /* BTA_AV_SWITCH_ROLE */
+ bta_av_role_res, /* BTA_AV_ROLE_RES */
+ bta_av_delay_co, /* BTA_AV_DELAY_CO */
+ bta_av_open_at_inc, /* BTA_AV_OPEN_AT_INC */
+ bta_av_offload_req, /* BTA_AV_OFFLOAD_REQ */
+ bta_av_offload_rsp, /* BTA_AV_OFFLOAD_RSP */
+ NULL};
/* these tables translate AVDT events to SSM events */
static const uint16_t bta_av_stream_evt_ok[] = {
@@ -132,7 +187,7 @@ static const uint16_t bta_av_stream_evt_ok[] = {
BTA_AV_AVDT_RPT_CONN_EVT, /* AVDT_REPORT_CONN_EVT */
BTA_AV_AVDT_RPT_CONN_EVT, /* AVDT_REPORT_DISCONN_EVT */
BTA_AV_AVDT_DELAY_RPT_EVT, /* AVDT_DELAY_REPORT_EVT */
- BTA_AV_AVDT_DELAY_RPT_CFM_EVT, /* AVDT_DELAY_REPORT_CFM_EVT */
+ 0 /* AVDT_DELAY_REPORT_CFM_EVT */
};
static const uint16_t bta_av_stream_evt_fail[] = {
@@ -157,7 +212,7 @@ static const uint16_t bta_av_stream_evt_fail[] = {
BTA_AV_AVDT_RPT_CONN_EVT, /* AVDT_REPORT_CONN_EVT */
BTA_AV_AVDT_RPT_CONN_EVT, /* AVDT_REPORT_DISCONN_EVT */
BTA_AV_AVDT_DELAY_RPT_EVT, /* AVDT_DELAY_REPORT_EVT */
- BTA_AV_AVDT_DELAY_RPT_CFM_EVT, /* AVDT_DELAY_REPORT_CFM_EVT */
+ 0 /* AVDT_DELAY_REPORT_CFM_EVT */
};
/***********************************************
@@ -214,7 +269,7 @@ static void bta_av_save_addr(tBTA_AV_SCB* p_scb, const RawAddress& bd_addr) {
bd_addr.ToString().c_str(), p_scb->recfg_sup,
p_scb->suspend_sup);
if (p_scb->PeerAddress() != bd_addr) {
- LOG_INFO("%s: reset flags old_addr=%s new_addr=%s", __func__,
+ LOG_INFO(LOG_TAG, "%s: reset flags old_addr=%s new_addr=%s", __func__,
p_scb->PeerAddress().ToString().c_str(),
bd_addr.ToString().c_str());
/* a new addr, reset the supported flags */
@@ -238,9 +293,9 @@ static void bta_av_save_addr(tBTA_AV_SCB* p_scb, const RawAddress& bd_addr) {
*
******************************************************************************/
static void notify_start_failed(tBTA_AV_SCB* p_scb) {
- LOG_ERROR("%s: peer %s role:0x%x bta_channel:%d bta_handle:0x%x", __func__,
- p_scb->PeerAddress().ToString().c_str(), p_scb->role, p_scb->chnl,
- p_scb->hndl);
+ LOG_ERROR(LOG_TAG, "%s: peer %s role:0x%x bta_channel:%d bta_handle:0x%x",
+ __func__, p_scb->PeerAddress().ToString().c_str(), p_scb->role,
+ p_scb->chnl, p_scb->hndl);
tBTA_AV_START start;
/* if start failed, clear role */
p_scb->role &= ~BTA_AV_ROLE_START_INT;
@@ -265,7 +320,8 @@ static void notify_start_failed(tBTA_AV_SCB* p_scb) {
* Returns void
*
******************************************************************************/
-void bta_av_st_rc_timer(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
+static void bta_av_st_rc_timer(tBTA_AV_SCB* p_scb,
+ UNUSED_ATTR tBTA_AV_DATA* p_data) {
APPL_TRACE_DEBUG("%s: rc_handle:%d, use_rc: %d", __func__, p_scb->rc_handle,
p_scb->use_rc);
/* for outgoing RC connection as INT/CT */
@@ -787,8 +843,17 @@ void bta_av_do_disc_a2dp(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
BTA_AV_AVRC_TIMER_EVT, p_scb->hndl);
}
+ if (bta_av_cb.features & BTA_AV_FEAT_MASTER) {
+ L2CA_SetDesireRole(L2CAP_ROLE_DISALLOW_SWITCH);
+
+ if (bta_av_cb.audio_open_cnt == 1) {
+ /* there's already an A2DP connection. do not allow switch */
+ bta_sys_clear_default_policy(BTA_ID_AV, HCI_ENABLE_MASTER_SLAVE_SWITCH);
+ }
+ }
/* store peer addr other parameters */
bta_av_save_addr(p_scb, p_data->api_open.bd_addr);
+ p_scb->sec_mask = p_data->api_open.sec_mask;
p_scb->use_rc = p_data->api_open.use_rc;
bta_sys_app_open(BTA_ID_AV, p_scb->app_id, p_scb->PeerAddress());
@@ -837,7 +902,8 @@ void bta_av_cleanup(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
tBTA_AV_CONN_CHG msg;
uint8_t role = BTA_AV_ROLE_AD_INT;
- LOG_INFO("%s peer %s", __func__, p_scb->PeerAddress().ToString().c_str());
+ LOG_INFO(LOG_TAG, "%s peer %s", __func__,
+ p_scb->PeerAddress().ToString().c_str());
/* free any buffers */
p_scb->sdp_discovery_started = false;
@@ -858,8 +924,6 @@ void bta_av_cleanup(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
p_scb->num_disc_snks = 0;
p_scb->coll_mask = 0;
alarm_cancel(p_scb->avrc_ct_timer);
- alarm_cancel(p_scb->link_signalling_timer);
- alarm_cancel(p_scb->accept_signalling_timer);
/* TODO(eisenbach): RE-IMPLEMENT USING VSC OR HAL EXTENSION
vendor_get_interface()->send_command(
@@ -935,7 +999,7 @@ void bta_av_config_ind(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
/* Clear collision mask */
p_scb->coll_mask = 0;
- alarm_cancel(p_scb->accept_signalling_timer);
+ alarm_cancel(bta_av_cb.accept_signalling_timer);
/* if no codec parameters in configuration, fail */
if ((p_evt_cfg->num_codec == 0) ||
@@ -1001,8 +1065,7 @@ void bta_av_disconnect_req(tBTA_AV_SCB* p_scb,
APPL_TRACE_API("%s: conn_lcb: 0x%x peer_addr: %s", __func__,
bta_av_cb.conn_lcb, p_scb->PeerAddress().ToString().c_str());
- alarm_cancel(p_scb->link_signalling_timer);
- alarm_cancel(p_scb->accept_signalling_timer);
+ alarm_cancel(bta_av_cb.link_signalling_timer);
alarm_cancel(p_scb->avrc_ct_timer);
// conn_lcb is the index bitmask of all used LCBs, and since LCB and SCB use
@@ -1074,7 +1137,8 @@ void bta_av_setconfig_rsp(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
/* we like this codec_type. find the sep_idx */
local_sep = bta_av_get_scb_sep_type(p_scb, avdt_handle);
bta_av_adjust_seps_idx(p_scb, avdt_handle);
- LOG_INFO(
+ LOG_DEBUG(
+ LOG_TAG,
"%s: peer %s bta_handle=0x%x avdt_handle=%d sep_idx=%d cur_psc_mask:0x%x",
__func__, p_scb->PeerAddress().ToString().c_str(), p_scb->hndl,
p_scb->avdt_handle, p_scb->sep_idx, p_scb->cur_psc_mask);
@@ -1092,7 +1156,7 @@ void bta_av_setconfig_rsp(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
AVDT_ConfigRsp(p_scb->avdt_handle, p_scb->avdt_label,
p_data->ci_setconfig.err_code, p_data->ci_setconfig.category);
- alarm_cancel(p_scb->link_signalling_timer);
+ alarm_cancel(bta_av_cb.link_signalling_timer);
if (p_data->ci_setconfig.err_code == AVDT_SUCCESS) {
p_scb->wait = BTA_AV_WAIT_ACP_CAPS_ON;
@@ -1155,7 +1219,6 @@ void bta_av_setconfig_rsp(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
******************************************************************************/
void bta_av_str_opened(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
tBTA_AV_CONN_CHG msg;
- char remote_name[BTM_MAX_REM_BD_NAME_LEN] = "";
uint8_t* p;
APPL_TRACE_DEBUG("%s: peer %s bta_handle: 0x%x", __func__,
@@ -1169,15 +1232,6 @@ void bta_av_str_opened(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
/* set the congestion flag, so AV would not send media packets by accident */
p_scb->cong = true;
p_scb->offload_start_pending = false;
- // Don't use AVDTP SUSPEND for restrict listed devices
- btif_storage_get_stored_remote_name(p_scb->PeerAddress(), remote_name);
- if (interop_match_name(INTEROP_DISABLE_AVDTP_SUSPEND, remote_name) ||
- interop_match_addr(INTEROP_DISABLE_AVDTP_SUSPEND,
- &p_scb->PeerAddress())) {
- LOG_INFO("%s: disable AVDTP SUSPEND: interop matched name %s address %s",
- __func__, remote_name, p_scb->PeerAddress().ToString().c_str());
- p_scb->suspend_sup = false;
- }
p_scb->stream_mtu =
p_data->str_msg.msg.open_ind.peer_mtu - AVDT_MEDIA_HDR_SIZE;
@@ -1221,7 +1275,9 @@ void bta_av_str_opened(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
}
}
}
+#if (BTA_AR_INCLUDED == TRUE)
bta_ar_avdt_conn(BTA_ID_AV, open.bd_addr, p_scb->hdi);
+#endif
if (p_scb->seps[p_scb->sep_idx].tsep == AVDT_TSEP_SRC) {
open.starting = false;
open.sep = AVDT_TSEP_SNK;
@@ -1317,7 +1373,7 @@ void bta_av_do_close(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
if (p_scb->co_started) {
bta_av_str_stopped(p_scb, NULL);
}
- alarm_cancel(p_scb->link_signalling_timer);
+ alarm_cancel(bta_av_cb.link_signalling_timer);
/* close stream */
p_scb->started = false;
@@ -1360,7 +1416,8 @@ void bta_av_connect_req(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
return;
}
- AVDT_ConnectReq(p_scb->PeerAddress(), p_scb->hdi, &bta_av_proc_stream_evt);
+ AVDT_ConnectReq(p_scb->PeerAddress(), p_scb->hdi, p_scb->sec_mask,
+ &bta_av_proc_stream_evt);
}
/*******************************************************************************
@@ -1694,8 +1751,8 @@ void bta_av_getcap_results(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
else if (uuid_int == UUID_SERVCLASS_AUDIO_SINK)
bta_av_adjust_seps_idx(p_scb,
bta_av_get_scb_handle(p_scb, AVDT_TSEP_SNK));
- LOG_INFO("%s: sep_idx=%d avdt_handle=%d bta_handle=0x%x", __func__,
- p_scb->sep_idx, p_scb->avdt_handle, p_scb->hndl);
+ LOG_DEBUG(LOG_TAG, "%s: sep_idx=%d avdt_handle=%d bta_handle=0x%x",
+ __func__, p_scb->sep_idx, p_scb->avdt_handle, p_scb->hndl);
/* use only the services peer supports */
cfg.psc_mask &= p_scb->peer_cap.psc_mask;
@@ -1744,8 +1801,8 @@ void bta_av_setconfig_rej(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
uint8_t avdt_handle = p_data->ci_setconfig.avdt_handle;
bta_av_adjust_seps_idx(p_scb, avdt_handle);
- LOG_INFO("%s: sep_idx=%d avdt_handle=%d bta_handle=0x%x", __func__,
- p_scb->sep_idx, p_scb->avdt_handle, p_scb->hndl);
+ LOG_DEBUG(LOG_TAG, "%s: sep_idx=%d avdt_handle=%d bta_handle=0x%x", __func__,
+ p_scb->sep_idx, p_scb->avdt_handle, p_scb->hndl);
AVDT_ConfigRsp(p_scb->avdt_handle, p_scb->avdt_label, AVDT_ERR_UNSUP_CFG, 0);
reject.bd_addr = p_data->str_msg.bd_addr;
@@ -1799,32 +1856,34 @@ void bta_av_conn_failed(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
*
******************************************************************************/
void bta_av_do_start(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
- LOG_INFO(
- "A2dp stream start peer:%s sco_occupied:%s av_role:0x%x started:%s "
- "wait:0x%x",
- PRIVATE_ADDRESS(p_scb->PeerAddress()),
- logbool(bta_av_cb.sco_occupied).c_str(), p_scb->role,
- logbool(p_scb->started).c_str(), p_scb->wait);
+ uint8_t clear_policy = 0;
+ uint8_t cur_role;
+
+ LOG_INFO(LOG_TAG,
+ "%s: peer %s sco_occupied:%s role:0x%x started:%s wait:0x%x",
+ __func__, p_scb->PeerAddress().ToString().c_str(),
+ logbool(bta_av_cb.sco_occupied).c_str(), p_scb->role,
+ logbool(p_scb->started).c_str(), p_scb->wait);
if (bta_av_cb.sco_occupied) {
- LOG_WARN("A2dp stream start failed");
bta_av_start_failed(p_scb, p_data);
return;
}
- /* disallow role switch during streaming, only if we are the central role
- * i.e. allow role switch, if we are peripheral.
- * It would not hurt us, if the peer device wants us to be central */
- tHCI_ROLE cur_role;
+ /* disallow role switch during streaming, only if we are the master role
+ * i.e. allow role switch, if we are slave.
+ * It would not hurt us, if the peer device wants us to be master */
if ((BTM_GetRole(p_scb->PeerAddress(), &cur_role) == BTM_SUCCESS) &&
- (cur_role == HCI_ROLE_CENTRAL)) {
- BTM_block_role_switch_for(p_scb->PeerAddress());
+ (cur_role == BTM_ROLE_MASTER)) {
+ clear_policy |= HCI_ENABLE_MASTER_SLAVE_SWITCH;
}
- BTM_block_sniff_mode_for(p_scb->PeerAddress());
+
+ bta_sys_clear_policy(BTA_ID_AV, clear_policy, p_scb->PeerAddress());
if (p_scb->started) {
p_scb->role |= BTA_AV_ROLE_START_INT;
if (p_scb->wait != 0) {
LOG_WARN(
+ LOG_TAG,
"%s: peer %s start stream request ignored: "
"already waiting: sco_occupied:%s role:0x%x started:%s wait:0x%x",
__func__, p_scb->PeerAddress().ToString().c_str(),
@@ -1842,6 +1901,7 @@ void bta_av_do_start(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
if ((p_scb->role & BTA_AV_ROLE_START_INT) != 0) {
LOG_WARN(
+ LOG_TAG,
"%s: peer %s start stream request ignored: "
"already initiated: sco_occupied:%s role:0x%x started:%s wait:0x%x",
__func__, p_scb->PeerAddress().ToString().c_str(),
@@ -1854,16 +1914,16 @@ void bta_av_do_start(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
bta_sys_busy(BTA_ID_AV, bta_av_cb.audio_open_cnt, p_scb->PeerAddress());
uint16_t result = AVDT_StartReq(&p_scb->avdt_handle, 1);
if (result != AVDT_SUCCESS) {
- LOG_ERROR("%s: AVDT_StartReq failed for peer %s result:%d", __func__,
- p_scb->PeerAddress().ToString().c_str(), result);
+ LOG_ERROR(LOG_TAG, "%s: AVDT_StartReq failed for peer %s result:%d",
+ __func__, p_scb->PeerAddress().ToString().c_str(), result);
bta_av_start_failed(p_scb, p_data);
}
- LOG_INFO(
- "%s: peer %s start requested: sco_occupied:%s role:0x%x "
- "started:%s wait:0x%x",
- __func__, p_scb->PeerAddress().ToString().c_str(),
- logbool(bta_av_cb.sco_occupied).c_str(), p_scb->role,
- logbool(p_scb->started).c_str(), p_scb->wait);
+ LOG_INFO(LOG_TAG,
+ "%s: peer %s start requested: sco_occupied:%s role:0x%x "
+ "started:%s wait:0x%x",
+ __func__, p_scb->PeerAddress().ToString().c_str(),
+ logbool(bta_av_cb.sco_occupied).c_str(), p_scb->role,
+ logbool(p_scb->started).c_str(), p_scb->wait);
}
/*******************************************************************************
@@ -1880,6 +1940,7 @@ void bta_av_str_stopped(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
uint8_t start = p_scb->started;
bool sus_evt = true;
BT_HDR* p_buf;
+ uint8_t set_policy = HCI_ENABLE_SNIFF_MODE;
APPL_TRACE_ERROR(
"%s: peer %s bta_handle:0x%x audio_open_cnt:%d, p_data %p start:%d",
@@ -1887,8 +1948,11 @@ void bta_av_str_stopped(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
bta_av_cb.audio_open_cnt, p_data, start);
bta_sys_idle(BTA_ID_AV, bta_av_cb.audio_open_cnt, p_scb->PeerAddress());
- BTM_unblock_role_switch_for(p_scb->PeerAddress());
- BTM_unblock_sniff_mode_for(p_scb->PeerAddress());
+ if ((bta_av_cb.features & BTA_AV_FEAT_MASTER) == 0 ||
+ bta_av_cb.audio_open_cnt == 1) {
+ set_policy |= HCI_ENABLE_MASTER_SLAVE_SWITCH;
+ }
+ bta_sys_set_policy(BTA_ID_AV, set_policy, p_scb->PeerAddress());
if (p_scb->co_started) {
if (p_scb->offload_started) {
@@ -1900,6 +1964,7 @@ void bta_av_str_stopped(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
p_scb->co_started = false;
p_scb->p_cos->stop(p_scb->hndl, p_scb->PeerAddress());
+ L2CA_SetFlushTimeout(p_scb->PeerAddress(), L2CAP_DEFAULT_FLUSH_TO);
}
/* if q_info.a2dp_list is not empty, drop it now */
@@ -1979,19 +2044,15 @@ void bta_av_reconfig(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
alarm_cancel(p_scb->avrc_ct_timer);
- LOG_DEBUG("p_scb->sep_info_idx=%d p_scb->rcfg_idx=%d p_rcfg->sep_info_idx=%d",
- p_scb->sep_info_idx, p_scb->rcfg_idx, p_rcfg->sep_info_idx);
- LOG_DEBUG("Peer capable codec: %s",
- A2DP_CodecInfoString(p_scb->peer_cap.codec_info).c_str());
- LOG_DEBUG("Current codec: %s",
- A2DP_CodecInfoString(p_scb->cfg.codec_info).c_str());
- LOG_DEBUG("Reconfig codec: %s",
- A2DP_CodecInfoString(p_rcfg->codec_info).c_str());
-
- BTM_LogHistory(
- kBtmLogTag, p_scb->PeerAddress(), "Codec reconfig",
- base::StringPrintf("%s => %s", A2DP_CodecName(p_scb->cfg.codec_info),
- A2DP_CodecName(p_rcfg->codec_info)));
+ APPL_TRACE_DEBUG(
+ "%s: p_scb->sep_info_idx=%d p_scb->rcfg_idx=%d p_rcfg->sep_info_idx=%d",
+ __func__, p_scb->sep_info_idx, p_scb->rcfg_idx, p_rcfg->sep_info_idx);
+ APPL_TRACE_DEBUG("%s: codec: %s", __func__,
+ A2DP_CodecInfoString(p_scb->peer_cap.codec_info).c_str());
+ APPL_TRACE_DEBUG("%s: codec: %s", __func__,
+ A2DP_CodecInfoString(p_scb->cfg.codec_info).c_str());
+ APPL_TRACE_DEBUG("%s: codec: %s", __func__,
+ A2DP_CodecInfoString(p_rcfg->codec_info).c_str());
p_cfg->num_protect = p_rcfg->num_protect;
memcpy(p_cfg->codec_info, p_rcfg->codec_info, AVDT_CODEC_SIZE);
@@ -2185,12 +2246,15 @@ void bta_av_data_path(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
void bta_av_start_ok(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
bool initiator = false;
bool suspend = false;
+ uint16_t flush_to;
uint8_t new_role = p_scb->role;
- BT_HDR_RIGID hdr;
- tHCI_ROLE cur_role;
+ BT_HDR hdr;
+ uint8_t clear_policy = 0;
+ uint8_t cur_role;
uint8_t local_tsep = p_scb->seps[p_scb->sep_idx].tsep;
- LOG_INFO("%s: peer %s bta_handle:0x%x wait:0x%x role:0x%x local_tsep:%d",
+ LOG_INFO(LOG_TAG,
+ "%s: peer %s bta_handle:0x%x wait:0x%x role:0x%x local_tsep:%d",
__func__, p_scb->PeerAddress().ToString().c_str(), p_scb->hndl,
p_scb->wait, p_scb->role, local_tsep);
@@ -2251,10 +2315,10 @@ void bta_av_start_ok(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
if (!bta_av_link_role_ok(p_scb, A2DP_SET_ONE_BIT))
p_scb->q_tag = BTA_AV_Q_TAG_START;
else {
- /* The wait flag may be set here while we are already central on the link */
+ /* The wait flag may be set here while we are already master on the link */
/* this could happen if a role switch complete event occurred during
* reconfig */
- /* if we are now central on the link, there is no need to wait for the role
+ /* if we are now master on the link, there is no need to wait for the role
* switch, */
/* complete anymore so we can clear the wait for role switch flag */
p_scb->wait &= ~BTA_AV_WAIT_ROLE_SW_BITS;
@@ -2293,7 +2357,11 @@ void bta_av_start_ok(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
* to be changed
*/
p_scb->co_started = bta_av_cb.audio_open_cnt;
+ flush_to = p_bta_av_cfg->p_audio_flush_to[p_scb->co_started - 1];
+ } else {
+ flush_to = 0;
}
+ L2CA_SetFlushTimeout(p_scb->PeerAddress(), flush_to);
/* clear the congestion flag */
p_scb->cong = false;
@@ -2313,14 +2381,16 @@ void bta_av_start_ok(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
{
/* If sink starts stream, disable sniff mode here */
if (!initiator) {
- /* If souce is the central role, disable role switch during streaming.
- * Otherwise allow role switch, if source is peripheral.
+ /* If souce is the master role, disable role switch during streaming.
+ * Otherwise allow role switch, if source is slave.
* Because it would not hurt source, if the peer device wants source to be
- * central */
+ * master */
if ((BTM_GetRole(p_scb->PeerAddress(), &cur_role) == BTM_SUCCESS) &&
- (cur_role == HCI_ROLE_CENTRAL)) {
- BTM_block_role_switch_for(p_scb->PeerAddress());
+ (cur_role == BTM_ROLE_MASTER)) {
+ clear_policy |= HCI_ENABLE_MASTER_SLAVE_SWITCH;
}
+
+ bta_sys_clear_policy(BTA_ID_AV, clear_policy, p_scb->PeerAddress());
}
p_scb->role = new_role;
@@ -2371,6 +2441,8 @@ void bta_av_start_ok(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
*
******************************************************************************/
void bta_av_start_failed(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
+ uint8_t set_policy = (HCI_ENABLE_SNIFF_MODE | HCI_ENABLE_MASTER_SLAVE_SWITCH);
+
APPL_TRACE_ERROR(
"%s: peer %s bta_handle:0x%x audio_open_cnt:%d started:%s co_started:%d",
__func__, p_scb->PeerAddress().ToString().c_str(), p_scb->hndl,
@@ -2382,8 +2454,7 @@ void bta_av_start_failed(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
notify_start_failed(p_scb);
}
- BTM_unblock_role_switch_for(p_scb->PeerAddress());
- BTM_unblock_sniff_mode_for(p_scb->PeerAddress());
+ bta_sys_set_policy(BTA_ID_AV, set_policy, p_scb->PeerAddress());
p_scb->sco_suspend = false;
}
@@ -2399,16 +2470,21 @@ void bta_av_start_failed(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
void bta_av_str_closed(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
tBTA_AV data;
tBTA_AV_EVT event;
+ uint8_t set_policy = HCI_ENABLE_SNIFF_MODE;
APPL_TRACE_WARNING(
"%s: peer %s bta_handle:0x%x open_status:%d chnl:%d co_started:%d",
__func__, p_scb->PeerAddress().ToString().c_str(), p_scb->hndl,
p_scb->open_status, p_scb->chnl, p_scb->co_started);
- BTM_unblock_role_switch_for(p_scb->PeerAddress());
- BTM_unblock_sniff_mode_for(p_scb->PeerAddress());
+ if ((bta_av_cb.features & BTA_AV_FEAT_MASTER) == 0 ||
+ bta_av_cb.audio_open_cnt == 1) {
+ set_policy |= HCI_ENABLE_MASTER_SLAVE_SWITCH;
+ }
+ bta_sys_set_policy(BTA_ID_AV, set_policy, p_scb->PeerAddress());
if (bta_av_cb.audio_open_cnt <= 1) {
- BTM_default_unblock_role_switch();
+ /* last connection - restore the allow switch flag */
+ L2CA_SetDesireRole(L2CAP_ROLE_ALLOW_SWITCH);
}
if (p_scb->open_status != BTA_AV_SUCCESS) {
@@ -2476,6 +2552,7 @@ void bta_av_clr_cong(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
void bta_av_suspend_cfm(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
tBTA_AV_SUSPEND suspend_rsp;
uint8_t err_code = p_data->str_msg.msg.hdr.err_code;
+ uint8_t set_policy = HCI_ENABLE_SNIFF_MODE;
APPL_TRACE_DEBUG("%s: peer %s bta_handle:0x%x audio_open_cnt:%d err_code:%d",
__func__, p_scb->PeerAddress().ToString().c_str(),
@@ -2493,6 +2570,10 @@ void bta_av_suspend_cfm(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
suspend_rsp.status = BTA_AV_SUCCESS;
if (err_code && (err_code != AVDT_ERR_BAD_STATE)) {
+ /* Disable suspend feature only with explicit rejection(not with timeout) */
+ if (err_code != AVDT_ERR_TIMEOUT) {
+ p_scb->suspend_sup = false;
+ }
suspend_rsp.status = BTA_AV_FAIL;
APPL_TRACE_ERROR("%s: suspend failed, closing connection", __func__);
@@ -2510,8 +2591,11 @@ void bta_av_suspend_cfm(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
}
bta_sys_idle(BTA_ID_AV, bta_av_cb.audio_open_cnt, p_scb->PeerAddress());
- BTM_unblock_role_switch_for(p_scb->PeerAddress());
- BTM_unblock_sniff_mode_for(p_scb->PeerAddress());
+ if ((bta_av_cb.features & BTA_AV_FEAT_MASTER) == 0 ||
+ bta_av_cb.audio_open_cnt == 1) {
+ set_policy |= HCI_ENABLE_MASTER_SLAVE_SWITCH;
+ }
+ bta_sys_set_policy(BTA_ID_AV, set_policy, p_scb->PeerAddress());
/* in case that we received suspend_ind, we may need to call co_stop here */
if (p_scb->co_started) {
@@ -2525,6 +2609,7 @@ void bta_av_suspend_cfm(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
p_scb->co_started = false;
p_scb->p_cos->stop(p_scb->hndl, p_scb->PeerAddress());
}
+ L2CA_SetFlushTimeout(p_scb->PeerAddress(), L2CAP_DEFAULT_FLUSH_TO);
}
{
@@ -2642,7 +2727,8 @@ void bta_av_rcfg_connect(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
/* let bta_av_rcfg_failed report fail */
bta_av_rcfg_failed(p_scb, NULL);
} else {
- AVDT_ConnectReq(p_scb->PeerAddress(), p_scb->hdi, &bta_av_proc_stream_evt);
+ AVDT_ConnectReq(p_scb->PeerAddress(), p_scb->hdi, p_scb->sec_mask,
+ &bta_av_proc_stream_evt);
}
}
@@ -2673,7 +2759,8 @@ void bta_av_rcfg_discntd(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
/* report close event & go to init state */
bta_av_ssm_execute(p_scb, BTA_AV_STR_DISC_FAIL_EVT, NULL);
} else {
- AVDT_ConnectReq(p_scb->PeerAddress(), p_scb->hdi, &bta_av_proc_stream_evt);
+ AVDT_ConnectReq(p_scb->PeerAddress(), p_scb->hdi, p_scb->sec_mask,
+ &bta_av_proc_stream_evt);
}
}
@@ -2707,6 +2794,11 @@ void bta_av_suspend_cont(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
bta_av_ssm_execute(p_scb, BTA_AV_STR_DISC_FAIL_EVT, NULL);
} else {
APPL_TRACE_ERROR("%s: suspend rejected, try close", __func__);
+ /* Disable suspend feature only with explicit rejection(not with timeout)
+ */
+ if (err_code != AVDT_ERR_TIMEOUT) {
+ p_scb->suspend_sup = false;
+ }
/* drop the buffers queued in L2CAP */
L2CA_FlushChannel(p_scb->l2c_cid, L2CAP_FLUSH_CHANS_ALL);
@@ -2738,7 +2830,7 @@ void bta_av_rcfg_cfm(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
APPL_TRACE_DEBUG("%s: err_code = %d", __func__, err_code);
- // Disable AVDTP RECONFIGURE for rejectlisted devices
+ // Disable AVDTP RECONFIGURE for blacklisted devices
bool disable_avdtp_reconfigure = false;
{
char remote_name[BTM_MAX_REM_BD_NAME_LEN] = "";
@@ -2747,10 +2839,11 @@ void bta_av_rcfg_cfm(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data) {
if (interop_match_name(INTEROP_DISABLE_AVDTP_RECONFIGURE, remote_name) ||
interop_match_addr(INTEROP_DISABLE_AVDTP_RECONFIGURE,
(const RawAddress*)&p_scb->PeerAddress())) {
- LOG_INFO(
- "%s: disable AVDTP RECONFIGURE: interop matched "
- "name %s address %s",
- __func__, remote_name, p_scb->PeerAddress().ToString().c_str());
+ LOG_INFO(LOG_TAG,
+ "%s: disable AVDTP RECONFIGURE: interop matched "
+ "name %s address %s",
+ __func__, remote_name,
+ p_scb->PeerAddress().ToString().c_str());
disable_avdtp_reconfigure = true;
}
}
@@ -2810,8 +2903,8 @@ void bta_av_rcfg_open(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
/* we may choose to use a different SEP at reconfig.
* adjust the sep_idx now */
bta_av_adjust_seps_idx(p_scb, bta_av_get_scb_handle(p_scb, AVDT_TSEP_SRC));
- LOG_INFO("%s: sep_idx=%d avdt_handle=%d bta_handle=0x%x", __func__,
- p_scb->sep_idx, p_scb->avdt_handle, p_scb->hndl);
+ LOG_DEBUG(LOG_TAG, "%s: sep_idx=%d avdt_handle=%d bta_handle=0x%x",
+ __func__, p_scb->sep_idx, p_scb->avdt_handle, p_scb->hndl);
/* open the stream with the new config */
p_scb->sep_info_idx = p_scb->rcfg_idx;
@@ -2847,11 +2940,11 @@ void bta_av_security_rej(tBTA_AV_SCB* p_scb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
******************************************************************************/
void bta_av_chk_2nd_start(tBTA_AV_SCB* p_scb,
UNUSED_ATTR tBTA_AV_DATA* p_data) {
- LOG_INFO(
- "%s: peer %s channel:%d bta_av_cb.audio_open_cnt:%d role:0x%x "
- "features:0x%x",
- __func__, p_scb->PeerAddress().ToString().c_str(), p_scb->chnl,
- bta_av_cb.audio_open_cnt, p_scb->role, bta_av_cb.features);
+ LOG_INFO(LOG_TAG,
+ "%s: peer %s channel:%d bta_av_cb.audio_open_cnt:%d role:0x%x "
+ "features:0x%x",
+ __func__, p_scb->PeerAddress().ToString().c_str(), p_scb->chnl,
+ bta_av_cb.audio_open_cnt, p_scb->role, bta_av_cb.features);
if ((p_scb->chnl == BTA_AV_CHNL_AUDIO) && (bta_av_cb.audio_open_cnt >= 2) &&
(((p_scb->role & BTA_AV_ROLE_AD_ACP) == 0) || // Outgoing connection or
@@ -2870,16 +2963,19 @@ void bta_av_chk_2nd_start(tBTA_AV_SCB* p_scb,
if (!new_started) {
// Start the new stream
new_started = true;
- LOG_INFO(
- "%s: starting new stream for peer %s because peer %s "
- "already started",
- __func__, p_scb->PeerAddress().ToString().c_str(),
- p_scbi->PeerAddress().ToString().c_str());
+ LOG_INFO(LOG_TAG,
+ "%s: starting new stream for peer %s because peer %s "
+ "already started",
+ __func__, p_scb->PeerAddress().ToString().c_str(),
+ p_scbi->PeerAddress().ToString().c_str());
bta_av_ssm_execute(p_scb, BTA_AV_AP_START_EVT, NULL);
}
// May need to update the flush timeout of this already started stream
if (p_scbi->co_started != bta_av_cb.audio_open_cnt) {
p_scbi->co_started = bta_av_cb.audio_open_cnt;
+ L2CA_SetFlushTimeout(
+ p_scbi->PeerAddress(),
+ p_bta_av_cfg->p_audio_flush_to[p_scbi->co_started - 1]);
}
}
}
@@ -2998,7 +3094,7 @@ void offload_vendor_callback(tBTM_VSC_CMPL* param) {
if (param->param_len) {
APPL_TRACE_DEBUG("%s: param_len = %d status = %d", __func__,
param->param_len, param->p_param_buf[0]);
- value.status = static_cast<tBTA_AV_STATUS>(param->p_param_buf[0]);
+ value.status = param->p_param_buf[0];
}
if (value.status == 0) {
sub_opcode = param->p_param_buf[1];
@@ -3031,8 +3127,7 @@ void bta_av_vendor_offload_start(tBTA_AV_SCB* p_scb,
UINT32_TO_STREAM(p_param, offload_start->codec_type);
UINT16_TO_STREAM(p_param, offload_start->max_latency);
- ARRAY_TO_STREAM(p_param, offload_start->scms_t_enable,
- static_cast<int>(offload_start->scms_t_enable.size()));
+ UINT16_TO_STREAM(p_param, offload_start->scms_t_enable);
UINT32_TO_STREAM(p_param, offload_start->sample_rate);
UINT8_TO_STREAM(p_param, offload_start->bits_per_sample);
UINT8_TO_STREAM(p_param, offload_start->ch_mode);
@@ -3162,7 +3257,7 @@ static void bta_av_offload_codec_builder(tBTA_AV_SCB* p_scb,
case BTAV_A2DP_CODEC_INDEX_SOURCE_SBC:
codec_type = BTA_AV_CODEC_TYPE_SBC;
if (A2DP_GetMaxBitpoolSbc(p_scb->cfg.codec_info) <=
- A2DP_SBC_BITPOOL_MIDDLE_QUALITY) {
+ BTIF_A2DP_MAX_BITPOOL_MQ) {
APPL_TRACE_WARNING("%s: Restricting streaming MTU size for MQ Bitpool",
__func__);
mtu = MAX_2MBPS_AVDTP_MTU;
@@ -3189,16 +3284,11 @@ static void bta_av_offload_codec_builder(tBTA_AV_SCB* p_scb,
p_a2dp_offload->max_latency = 0;
p_a2dp_offload->mtu = mtu;
p_a2dp_offload->acl_hdl =
- get_btm_client_interface().lifecycle.BTM_GetHCIConnHandle(
- p_scb->PeerAddress(), BT_TRANSPORT_BR_EDR);
- btav_a2dp_scmst_info_t scmst_info =
- p_scb->p_cos->get_scmst_info(p_scb->PeerAddress());
- p_a2dp_offload->scms_t_enable[0] = scmst_info.enable_status;
- p_a2dp_offload->scms_t_enable[1] = scmst_info.cp_header;
- APPL_TRACE_DEBUG(
- "%s: SCMS-T_enable status: %d, "
- "SCMS-T header (if it's enabled): 0x%02x",
- __func__, scmst_info.enable_status, scmst_info.cp_header);
+ BTM_GetHCIConnHandle(p_scb->PeerAddress(), BT_TRANSPORT_BR_EDR);
+ p_a2dp_offload->scms_t_enable =
+ p_scb->p_cos->cp_is_active(p_scb->PeerAddress());
+ APPL_TRACE_DEBUG("%s: scms_t_enable =%d", __func__,
+ p_a2dp_offload->scms_t_enable);
switch (A2DP_GetTrackSampleRate(p_scb->cfg.codec_info)) {
case 44100:
@@ -3214,7 +3304,8 @@ static void bta_av_offload_codec_builder(tBTA_AV_SCB* p_scb,
p_a2dp_offload->sample_rate = BTAV_A2DP_CODEC_SAMPLE_RATE_96000;
break;
}
- if (L2CA_GetRemoteCid(p_scb->l2c_cid, &p_a2dp_offload->l2c_rcid) == false) {
+ if (L2CA_GetIdentifiers(p_scb->l2c_cid, &p_a2dp_offload->l2c_rcid, NULL) ==
+ false) {
APPL_TRACE_ERROR("%s: Failed to fetch l2c rcid", __func__);
return;
}
diff --git a/bta/av/bta_av_act.cc b/bta/av/bta_av_act.cc
index dcbb18a7b..827cdbb5b 100644
--- a/bta/av/bta_av_act.cc
+++ b/bta/av/bta_av_act.cc
@@ -25,21 +25,26 @@
#define LOG_TAG "bt_bta_av"
-#include <cstdint>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/av/bta_av_int.h"
-#include "bta/include/bta_ar_api.h"
-#include "bta/include/utl.h"
-#include "btif/avrcp/avrcp_service.h"
-#include "osi/include/allocator.h"
+#include "bt_target.h"
+
+#include <base/logging.h>
+#include <string.h>
+
+#include "avdt_api.h"
+#include "avrcp_service.h"
+#include "bta_av_api.h"
+#include "bta_av_int.h"
+#include "l2c_api.h"
+#include "log/log.h"
+#include "osi/include/list.h"
#include "osi/include/log.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
+#include "osi/include/osi.h"
#include "osi/include/properties.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/l2c_api.h"
-#include "types/raw_address.h"
+#include "utl.h"
+
+#if (BTA_AR_INCLUDED == TRUE)
+#include "bta_ar_api.h"
+#endif
/*****************************************************************************
* Constants
@@ -183,7 +188,7 @@ static void bta_av_del_sdp_rec(uint32_t* p_sdp_handle) {
*
******************************************************************************/
static void bta_av_avrc_sdp_cback(UNUSED_ATTR uint16_t status) {
- BT_HDR_RIGID* p_msg = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_msg = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_msg->event = BTA_AV_SDP_AVRC_DISC_EVT;
@@ -301,7 +306,8 @@ static void bta_av_rc_msg_cback(uint8_t handle, uint8_t label, uint8_t opcode,
uint8_t bta_av_rc_create(tBTA_AV_CB* p_cb, uint8_t role, uint8_t shdl,
uint8_t lidx) {
if (is_new_avrcp_enabled()) {
- LOG_INFO("Skipping RC creation for the old AVRCP profile");
+ APPL_TRACE_WARNING("%s: Skipping RC creation for the old AVRCP profile",
+ __func__);
return BTA_AV_RC_HANDLE_NONE;
}
@@ -495,7 +501,7 @@ void bta_av_rc_opened(tBTA_AV_CB* p_cb, tBTA_AV_DATA* p_data) {
APPL_TRACE_DEBUG("%s: shdl:%d, srch %d", __func__, i + 1,
p_scb->rc_handle);
shdl = i + 1;
- LOG_INFO("%s: allow incoming AVRCP connections:%d", __func__,
+ LOG_INFO(LOG_TAG, "%s: allow incoming AVRCP connections:%d", __func__,
p_scb->use_rc);
alarm_cancel(p_scb->avrc_ct_timer);
disc = p_scb->hndl;
@@ -1091,9 +1097,11 @@ void bta_av_stream_chg(tBTA_AV_SCB* p_scb, bool started) {
logbool(started).c_str(), started_msk);
if (started) {
+ bta_av_cb.audio_streams |= started_msk;
/* Let L2CAP know this channel is processed with high priority */
L2CA_SetAclPriority(p_scb->PeerAddress(), L2CAP_PRIORITY_HIGH);
} else {
+ bta_av_cb.audio_streams &= ~started_msk;
/* Let L2CAP know this channel is processed with low priority */
L2CA_SetAclPriority(p_scb->PeerAddress(), L2CAP_PRIORITY_NORMAL);
}
@@ -1165,8 +1173,8 @@ void bta_av_conn_chg(tBTA_AV_DATA* p_data) {
"p_lcb_rc->conn_msk:x%x",
__func__, p_lcb_rc->conn_msk);
/* check if the RC is connected to the scb addr */
- LOG_INFO("%s: p_lcb_rc->addr: %s conn_chg.peer_addr: %s", __func__,
- p_lcb_rc->addr.ToString().c_str(),
+ LOG_INFO(LOG_TAG, "%s: p_lcb_rc->addr: %s conn_chg.peer_addr: %s",
+ __func__, p_lcb_rc->addr.ToString().c_str(),
p_data->conn_chg.peer_addr.ToString().c_str());
if (p_lcb_rc->conn_msk &&
@@ -1262,7 +1270,8 @@ void bta_av_conn_chg(tBTA_AV_DATA* p_data) {
if (p_cb->audio_open_cnt == 1) {
/* one audio channel goes down and there's one audio channel remains open.
* restore the switch role in default link policy */
- BTM_default_unblock_role_switch();
+ bta_sys_set_default_policy(BTA_ID_AV, HCI_ENABLE_MASTER_SLAVE_SWITCH);
+ /* allow role switch, if this is the last connection */
bta_av_restore_switch();
}
if (p_cb->audio_open_cnt) {
@@ -1274,6 +1283,9 @@ void bta_av_conn_chg(tBTA_AV_DATA* p_data) {
*/
if (p_scbi->co_started != bta_av_cb.audio_open_cnt) {
p_scbi->co_started = bta_av_cb.audio_open_cnt;
+ L2CA_SetFlushTimeout(
+ p_scbi->PeerAddress(),
+ p_bta_av_cfg->p_audio_flush_to[p_scbi->co_started - 1]);
}
}
}
@@ -1291,7 +1303,7 @@ void bta_av_conn_chg(tBTA_AV_DATA* p_data) {
*
******************************************************************************/
void bta_av_disable(tBTA_AV_CB* p_cb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
bool disabling_in_progress = false;
uint16_t xx;
@@ -1305,12 +1317,6 @@ void bta_av_disable(tBTA_AV_CB* p_cb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
* expect BTA_AV_DEREG_COMP_EVT when deregister is complete */
for (xx = 0; xx < BTA_AV_NUM_STRS; xx++) {
if (p_cb->p_scb[xx] != NULL) {
- // Free signalling timers
- alarm_free(p_cb->p_scb[xx]->link_signalling_timer);
- p_cb->p_scb[xx]->link_signalling_timer = NULL;
- alarm_free(p_cb->p_scb[xx]->accept_signalling_timer);
- p_cb->p_scb[xx]->accept_signalling_timer = NULL;
-
hdr.layer_specific = xx + 1;
bta_av_api_deregister((tBTA_AV_DATA*)&hdr);
disabling_in_progress = true;
@@ -1321,6 +1327,10 @@ void bta_av_disable(tBTA_AV_CB* p_cb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
// no needed to setup this disabling flag.
p_cb->disabling = disabling_in_progress;
+ alarm_free(p_cb->link_signalling_timer);
+ p_cb->link_signalling_timer = NULL;
+ alarm_free(p_cb->accept_signalling_timer);
+ p_cb->accept_signalling_timer = NULL;
}
/*******************************************************************************
@@ -1333,10 +1343,8 @@ void bta_av_disable(tBTA_AV_CB* p_cb, UNUSED_ATTR tBTA_AV_DATA* p_data) {
*
******************************************************************************/
void bta_av_api_disconnect(tBTA_AV_DATA* p_data) {
- tBTA_AV_SCB* p_scb =
- bta_av_hndl_to_scb(p_data->api_discnt.hdr.layer_specific);
- AVDT_DisconnectReq(p_scb->PeerAddress(), bta_av_conn_cback);
- alarm_cancel(p_scb->link_signalling_timer);
+ AVDT_DisconnectReq(p_data->api_discnt.bd_addr, bta_av_conn_cback);
+ alarm_cancel(bta_av_cb.link_signalling_timer);
}
/**
@@ -1424,7 +1432,8 @@ void bta_av_sig_chg(tBTA_AV_DATA* p_data) {
AVDT_DisconnectReq(p_data->str_msg.bd_addr, NULL);
return;
}
- LOG_INFO("%s: AVDT_CONNECT_IND_EVT: peer %s selected lcb_index %d",
+ LOG_INFO(LOG_TAG,
+ "%s: AVDT_CONNECT_IND_EVT: peer %s selected lcb_index %d",
__func__, p_data->str_msg.bd_addr.ToString().c_str(), xx);
tBTA_AV_SCB* p_scb = p_cb->p_scb[xx];
@@ -1454,31 +1463,24 @@ void bta_av_sig_chg(tBTA_AV_DATA* p_data) {
* The following function shall send the event and start the
* recurring timer
*/
- if (!p_scb->link_signalling_timer) {
- p_scb->link_signalling_timer = alarm_new("link_signalling_timer");
- }
- BT_HDR hdr;
- hdr.layer_specific = p_scb->hndl;
- bta_av_signalling_timer((tBTA_AV_DATA*)&hdr);
+ bta_av_signalling_timer(NULL);
APPL_TRACE_DEBUG("%s: Re-start timer for AVDTP service", __func__);
bta_sys_conn_open(BTA_ID_AV, p_scb->app_id, p_scb->PeerAddress());
/* Possible collision : need to avoid outgoing processing while the
* timer is running */
p_scb->coll_mask = BTA_AV_COLL_INC_TMR;
- if (!p_scb->accept_signalling_timer) {
- p_scb->accept_signalling_timer = alarm_new("accept_signalling_timer");
- }
alarm_set_on_mloop(
- p_scb->accept_signalling_timer, BTA_AV_ACCEPT_SIGNALLING_TIMEOUT_MS,
+ p_cb->accept_signalling_timer, BTA_AV_ACCEPT_SIGNALLING_TIMEOUT_MS,
bta_av_accept_signalling_timer_cback, UINT_TO_PTR(xx));
}
}
}
+#if (BTA_AR_INCLUDED == TRUE)
else if (event == BTA_AR_AVDT_CONN_EVT) {
- uint8_t scb_index = p_data->str_msg.scb_index;
- alarm_cancel(p_cb->p_scb[scb_index]->link_signalling_timer);
+ alarm_cancel(bta_av_cb.link_signalling_timer);
}
+#endif
else {
/* disconnected. */
APPL_TRACE_DEBUG("%s: bta_av_cb.conn_lcb=0x%x", __func__,
@@ -1524,9 +1526,6 @@ void bta_av_sig_chg(tBTA_AV_DATA* p_data) {
*
******************************************************************************/
void bta_av_signalling_timer(UNUSED_ATTR tBTA_AV_DATA* p_data) {
- tBTA_AV_HNDL hndl = p_data->hdr.layer_specific;
- tBTA_AV_SCB* p_scb = bta_av_hndl_to_scb(hndl);
-
tBTA_AV_CB* p_cb = &bta_av_cb;
int xx;
uint8_t mask;
@@ -1543,10 +1542,9 @@ void bta_av_signalling_timer(UNUSED_ATTR tBTA_AV_DATA* p_data) {
if (mask & p_cb->conn_lcb) {
/* this entry is used. check if it is connected */
if (!p_lcb->conn_msk) {
- APPL_TRACE_DEBUG("%s hndl 0x%x", __func__, p_scb->hndl);
- bta_sys_start_timer(p_scb->link_signalling_timer,
+ bta_sys_start_timer(p_cb->link_signalling_timer,
BTA_AV_SIGNALLING_TIMEOUT_MS,
- BTA_AV_SIGNALLING_TIMER_EVT, hndl);
+ BTA_AV_SIGNALLING_TIMER_EVT, 0);
tBTA_AV_PEND pend;
pend.bd_addr = p_lcb->addr;
tBTA_AV bta_av_data;
@@ -1591,7 +1589,7 @@ static void bta_av_accept_signalling_timer_cback(void* data) {
/* We are still doing SDP. Run the timer again. */
p_scb->coll_mask |= BTA_AV_COLL_INC_TMR;
- alarm_set_on_mloop(p_scb->accept_signalling_timer,
+ alarm_set_on_mloop(p_cb->accept_signalling_timer,
BTA_AV_ACCEPT_SIGNALLING_TIMEOUT_MS,
bta_av_accept_signalling_timer_cback,
UINT_TO_PTR(inx));
@@ -2082,7 +2080,7 @@ void bta_av_rc_closed(tBTA_AV_DATA* p_data) {
/* if the RCB uses the extra LCB, use the addr for event and clean it */
p_lcb = &p_cb->lcb[BTA_AV_NUM_LINKS];
rc_close.peer_addr = p_msg->peer_addr;
- LOG_INFO("%s: rc_only closed bd_addr: %s", __func__,
+ LOG_INFO(LOG_TAG, "%s: rc_only closed bd_addr: %s", __func__,
p_msg->peer_addr.ToString().c_str());
p_lcb->conn_msk = 0;
p_lcb->lidx = 0;
@@ -2135,7 +2133,7 @@ void bta_av_rc_browse_opened(tBTA_AV_DATA* p_data) {
tBTA_AV_RC_CONN_CHG* p_msg = (tBTA_AV_RC_CONN_CHG*)p_data;
tBTA_AV_RC_BROWSE_OPEN rc_browse_open;
- LOG_INFO("%s: peer_addr: %s rc_handle:%d", __func__,
+ LOG_INFO(LOG_TAG, "%s: peer_addr: %s rc_handle:%d", __func__,
p_msg->peer_addr.ToString().c_str(), p_msg->handle);
rc_browse_open.status = BTA_AV_SUCCESS;
@@ -2161,7 +2159,7 @@ void bta_av_rc_browse_closed(tBTA_AV_DATA* p_data) {
tBTA_AV_RC_CONN_CHG* p_msg = (tBTA_AV_RC_CONN_CHG*)p_data;
tBTA_AV_RC_BROWSE_CLOSE rc_browse_close;
- LOG_INFO("%s: peer_addr: %s rc_handle:%d", __func__,
+ LOG_INFO(LOG_TAG, "%s: peer_addr: %s rc_handle:%d", __func__,
p_msg->peer_addr.ToString().c_str(), p_msg->handle);
rc_browse_close.rc_handle = p_msg->handle;
@@ -2275,17 +2273,9 @@ void bta_av_dereg_comp(tBTA_AV_DATA* p_data) {
/* remove the A2DP SDP record, if no more audio stream is left */
if (!p_cb->reg_audio) {
-
- /* Only remove the SDP record if we're the ones that created it */
- if (is_new_avrcp_enabled()) {
- APPL_TRACE_DEBUG("%s: newavrcp is the owner of the AVRCP Target SDP "
- "record. Don't dereg the SDP record", __func__);
- } else {
- APPL_TRACE_DEBUG("%s: newavrcp is not enabled. Remove SDP record",
- __func__);
- bta_ar_dereg_avrc(UUID_SERVCLASS_AV_REMOTE_CONTROL);
- }
-
+#if (BTA_AR_INCLUDED == TRUE)
+ bta_ar_dereg_avrc(UUID_SERVCLASS_AV_REMOTE_CONTROL, BTA_ID_AV);
+#endif
if (p_cb->sdp_a2dp_handle) {
bta_av_del_sdp_rec(&p_cb->sdp_a2dp_handle);
p_cb->sdp_a2dp_handle = 0;
@@ -2308,12 +2298,14 @@ void bta_av_dereg_comp(tBTA_AV_DATA* p_data) {
p_cb->disabling);
/* if no stream control block is active */
if (p_cb->reg_audio == 0) {
+#if (BTA_AR_INCLUDED == TRUE)
/* deregister from AVDT */
- bta_ar_dereg_avdt();
+ bta_ar_dereg_avdt(BTA_ID_AV);
/* deregister from AVCT */
- bta_ar_dereg_avrc(UUID_SERVCLASS_AV_REM_CTRL_TARGET);
- bta_ar_dereg_avct();
+ bta_ar_dereg_avrc(UUID_SERVCLASS_AV_REM_CTRL_TARGET, BTA_ID_AV);
+ bta_ar_dereg_avct(BTA_ID_AV);
+#endif
if (p_cb->disabling) {
p_cb->disabling = false;
diff --git a/bta/av/bta_av_api.cc b/bta/av/bta_av_api.cc
index 23362e4c3..aed5b122b 100644
--- a/bta/av/bta_av_api.cc
+++ b/bta/av/bta_av_api.cc
@@ -26,11 +26,18 @@
#define LOG_TAG "bt_bta_av"
-#include "bt_target.h" // Must be first to define build configuration
+#include <base/logging.h>
+
+#include "bt_target.h"
+
+#include <string.h>
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_av_api.h"
+#include "bta_av_int.h"
+#include "bta_sys.h"
-#include "bta/av/bta_av_int.h"
#include "osi/include/allocator.h"
-#include "osi/include/compat.h"
#include "osi/include/log.h"
/*****************************************************************************
@@ -52,7 +59,8 @@ static const tBTA_SYS_REG bta_av_reg = {bta_av_hdl_event, BTA_AvDisable};
* Returns void
*
******************************************************************************/
-void BTA_AvEnable(tBTA_AV_FEAT features, tBTA_AV_CBACK* p_cback) {
+void BTA_AvEnable(tBTA_SEC sec_mask, tBTA_AV_FEAT features,
+ tBTA_AV_CBACK* p_cback) {
tBTA_AV_API_ENABLE* p_buf =
(tBTA_AV_API_ENABLE*)osi_malloc(sizeof(tBTA_AV_API_ENABLE));
@@ -62,6 +70,7 @@ void BTA_AvEnable(tBTA_AV_FEAT features, tBTA_AV_CBACK* p_cback) {
p_buf->hdr.event = BTA_AV_API_ENABLE_EVT;
p_buf->p_cback = p_cback;
p_buf->features = features;
+ p_buf->sec_mask = sec_mask;
bta_sys_sendmsg(p_buf);
}
@@ -76,7 +85,7 @@ void BTA_AvEnable(tBTA_AV_FEAT features, tBTA_AV_CBACK* p_cback) {
*
******************************************************************************/
void BTA_AvDisable(void) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
bta_sys_deregister(BTA_ID_AV);
p_buf->event = BTA_AV_API_DISABLE_EVT;
@@ -126,7 +135,7 @@ void BTA_AvRegister(tBTA_AV_CHNL chnl, const char* p_service_name,
*
******************************************************************************/
void BTA_AvDeregister(tBTA_AV_HNDL hndl) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->layer_specific = hndl;
p_buf->event = BTA_AV_API_DEREGISTER_EVT;
@@ -146,10 +155,11 @@ void BTA_AvDeregister(tBTA_AV_HNDL hndl) {
*
******************************************************************************/
void BTA_AvOpen(const RawAddress& bd_addr, tBTA_AV_HNDL handle, bool use_rc,
- uint16_t uuid) {
- LOG_INFO("%s: peer %s bta_handle:0x%x use_rc=%s uuid=0x%x", __func__,
- bd_addr.ToString().c_str(), handle, (use_rc) ? "true" : "false",
- uuid);
+ tBTA_SEC sec_mask, uint16_t uuid) {
+ LOG_INFO(LOG_TAG,
+ "%s: peer %s bta_handle:0x%x use_rc=%s sec_mask=0x%x uuid=0x%x",
+ __func__, bd_addr.ToString().c_str(), handle,
+ (use_rc) ? "true" : "false", sec_mask, uuid);
tBTA_AV_API_OPEN* p_buf =
(tBTA_AV_API_OPEN*)osi_malloc(sizeof(tBTA_AV_API_OPEN));
@@ -158,6 +168,7 @@ void BTA_AvOpen(const RawAddress& bd_addr, tBTA_AV_HNDL handle, bool use_rc,
p_buf->hdr.layer_specific = handle;
p_buf->bd_addr = bd_addr;
p_buf->use_rc = use_rc;
+ p_buf->sec_mask = sec_mask;
p_buf->switch_res = BTA_AV_RS_NONE;
p_buf->uuid = uuid;
@@ -174,9 +185,9 @@ void BTA_AvOpen(const RawAddress& bd_addr, tBTA_AV_HNDL handle, bool use_rc,
*
******************************************************************************/
void BTA_AvClose(tBTA_AV_HNDL handle) {
- LOG_INFO("%s: bta_handle:0x%x", __func__, handle);
+ LOG_INFO(LOG_TAG, "%s: bta_handle:0x%x", __func__, handle);
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_AV_API_CLOSE_EVT;
p_buf->layer_specific = handle;
@@ -193,14 +204,14 @@ void BTA_AvClose(tBTA_AV_HNDL handle) {
* Returns void
*
******************************************************************************/
-void BTA_AvDisconnect(tBTA_AV_HNDL handle) {
- LOG_INFO("%s: bta_handle=0x%x", __func__, handle);
+void BTA_AvDisconnect(const RawAddress& bd_addr) {
+ LOG_INFO(LOG_TAG, "%s: peer %s", __func__, bd_addr.ToString().c_str());
tBTA_AV_API_DISCNT* p_buf =
(tBTA_AV_API_DISCNT*)osi_malloc(sizeof(tBTA_AV_API_DISCNT));
p_buf->hdr.event = BTA_AV_API_DISCONNECT_EVT;
- p_buf->hdr.layer_specific = handle;
+ p_buf->bd_addr = bd_addr;
bta_sys_sendmsg(p_buf);
}
@@ -215,9 +226,9 @@ void BTA_AvDisconnect(tBTA_AV_HNDL handle) {
*
******************************************************************************/
void BTA_AvStart(tBTA_AV_HNDL handle) {
- LOG_INFO("Starting audio/video stream data transfer bta_handle:%hhu", handle);
+ LOG_INFO(LOG_TAG, "%s: bta_handle=0x%x", __func__, handle);
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_AV_API_START_EVT;
p_buf->layer_specific = handle;
@@ -235,9 +246,9 @@ void BTA_AvStart(tBTA_AV_HNDL handle) {
*
******************************************************************************/
void BTA_AvOffloadStart(tBTA_AV_HNDL hndl) {
- LOG_INFO("%s: bta_handle=0x%x", __func__, hndl);
+ LOG_INFO(LOG_TAG, "%s: bta_handle=0x%x", __func__, hndl);
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_AV_API_OFFLOAD_START_EVT;
p_buf->layer_specific = hndl;
@@ -277,7 +288,7 @@ void BTA_AvOffloadStartRsp(tBTA_AV_HNDL hndl, tBTA_AV_STATUS status) {
*
******************************************************************************/
void BTA_AvStop(tBTA_AV_HNDL handle, bool suspend) {
- LOG_INFO("%s: bta_handle=0x%x suspend=%s", __func__, handle,
+ LOG_INFO(LOG_TAG, "%s: bta_handle=0x%x suspend=%s", __func__, handle,
logbool(suspend).c_str());
tBTA_AV_API_STOP* p_buf =
@@ -308,8 +319,8 @@ void BTA_AvStop(tBTA_AV_HNDL handle, bool suspend) {
void BTA_AvReconfig(tBTA_AV_HNDL hndl, bool suspend, uint8_t sep_info_idx,
uint8_t* p_codec_info, uint8_t num_protect,
const uint8_t* p_protect_info) {
- LOG_INFO("%s: bta_handle=0x%x suspend=%s sep_info_idx=%d", __func__, hndl,
- logbool(suspend).c_str(), sep_info_idx);
+ LOG_INFO(LOG_TAG, "%s: bta_handle=0x%x suspend=%s sep_info_idx=%d", __func__,
+ hndl, logbool(suspend).c_str(), sep_info_idx);
tBTA_AV_API_RCFG* p_buf =
(tBTA_AV_API_RCFG*)osi_malloc(sizeof(tBTA_AV_API_RCFG) + num_protect);
diff --git a/bta/av/bta_av_cfg.cc b/bta/av/bta_av_cfg.cc
index d2a7d8aaa..858349660 100644
--- a/bta/av/bta_av_cfg.cc
+++ b/bta/av/bta_av_cfg.cc
@@ -23,12 +23,12 @@
*
******************************************************************************/
-#include <cstdint>
+#include <stddef.h>
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_av_api.h"
-#include "stack/include/avrc_api.h"
+#include "bt_common.h"
+#include "bt_target.h"
+#include "bta_api.h"
+#include "bta_av_int.h"
#ifndef BTA_AV_RC_COMP_ID
#define BTA_AV_RC_COMP_ID AVRC_CO_GOOGLE
@@ -63,6 +63,15 @@ const uint32_t bta_av_meta_caps_co_ids[] = {AVRC_CO_METADATA, AVRC_CO_BROADCOM};
* 3. GetCapabilities supported event_ids list
* 4. GetCapabilities supported event_ids count
*/
+/* Flushing partial avdtp packets can cause some headsets to disconnect the link
+ if receiving partial a2dp frames */
+const uint16_t bta_av_audio_flush_to[] = {
+ 0, /* 1 stream */
+ 0, /* 2 streams */
+ 0, /* 3 streams */
+ 0, /* 4 streams */
+ 0 /* 5 streams */
+}; /* AVDTP audio transport channel flush timeout */
/* Note: Android doesnt support AVRC_SUPF_TG_GROUP_NAVI */
/* Note: if AVRC_SUPF_TG_GROUP_NAVI is set, bta_av_cfg.avrc_group should be true
@@ -115,14 +124,25 @@ const uint8_t bta_av_meta_caps_evt_ids_avrcp13[] = {
sizeof(bta_av_meta_caps_evt_ids_avrcp13[0]))
#endif /* BTA_AVK_NUM_RC_EVT_IDS_AVRCP13 */
+/* the MTU for the AVRCP browsing channel */
+#ifndef BTA_AV_MAX_RC_BR_MTU
+#define BTA_AV_MAX_RC_BR_MTU 1008
+#endif
+
/* This configuration to be used when we are Src + TG + CT( only for abs vol) */
-extern const tBTA_AV_CFG bta_av_cfg = {
- BTA_AV_RC_COMP_ID, /* AVRCP Company ID */
- BTA_AV_RC_SUPF_CT, /* AVRCP controller categories */
- BTA_AV_RC_SUPF_TG, /* AVRCP target categories */
- 6, /* AVDTP audio channel max data queue size */
- false, /* true, to accept AVRC 1.3 group nevigation command */
- 2, /* company id count in p_meta_co_ids */
+const tBTA_AV_CFG bta_av_cfg = {
+ BTA_AV_RC_COMP_ID, /* AVRCP Company ID */
+ 512, /* AVRCP MTU at L2CAP for control channel */
+ BTA_AV_MAX_RC_BR_MTU, /* AVRCP MTU at L2CAP for browsing channel */
+ BTA_AV_RC_SUPF_CT, /* AVRCP controller categories */
+ BTA_AV_RC_SUPF_TG, /* AVRCP target categories */
+ 672, /* AVDTP signaling channel MTU at L2CAP */
+ MAX_3MBPS_AVDTP_MTU, /* AVDTP audio transport channel MTU at L2CAP */
+ bta_av_audio_flush_to, /* AVDTP audio transport channel flush
+ timeout */
+ 6, /* AVDTP audio channel max data queue size */
+ false, /* true, to accept AVRC 1.3 group nevigation command */
+ 2, /* company id count in p_meta_co_ids */
BTA_AV_NUM_RC_EVT_IDS, /* event id count in p_meta_evt_ids */
BTA_AV_RC_PASS_RSP_CODE, /* the default response code for pass
through commands */
@@ -130,19 +150,25 @@ extern const tBTA_AV_CFG bta_av_cfg = {
for company id */
bta_av_meta_caps_evt_ids, /* the the metadata Get Capabilities
response for event id */
+ NULL, /* the action function table for audio stream */
BTA_AV_RC_CT_NAME, /* Default AVRCP controller name */
BTA_AV_RC_TG_NAME /* Default AVRCP target name */
};
/* This configuration to be used when we are Sink + CT + TG( only for abs vol)
*/
-extern const tBTA_AV_CFG bta_avk_cfg = {
- AVRC_CO_METADATA, /* AVRCP Company ID */
- BTA_AVK_RC_SUPF_CT, /* AVRCP controller categories */
- BTA_AVK_RC_SUPF_TG, /* AVRCP target categories */
- 6, /* AVDTP audio channel max data queue size */
- false, /* true, to accept AVRC 1.3 group nevigation command */
- 2, /* company id count in p_meta_co_ids */
+const tBTA_AV_CFG bta_avk_cfg = {
+ AVRC_CO_METADATA, /* AVRCP Company ID */
+ 512, /* AVRCP MTU at L2CAP for control channel */
+ BTA_AV_MAX_RC_BR_MTU, /* AVRCP MTU at L2CAP for browsing channel */
+ BTA_AVK_RC_SUPF_CT, /* AVRCP controller categories */
+ BTA_AVK_RC_SUPF_TG, /* AVRCP target categories */
+ 672, /* AVDTP signaling channel MTU at L2CAP */
+ MAX_3MBPS_AVDTP_MTU, /* AVDTP audio transport channel MTU at L2CAP */
+ bta_av_audio_flush_to, /* AVDTP audio transport channel flush timeout */
+ 6, /* AVDTP audio channel max data queue size */
+ false, /* true, to accept AVRC 1.3 group nevigation command */
+ 2, /* company id count in p_meta_co_ids */
BTA_AVK_NUM_RC_EVT_IDS, /* event id count in p_meta_evt_ids */
BTA_AV_RC_PASS_RSP_CODE, /* the default response code for pass
through commands */
@@ -150,18 +176,24 @@ extern const tBTA_AV_CFG bta_avk_cfg = {
for company id */
bta_avk_meta_caps_evt_ids, /* the the metadata Get Capabilities
response for event id */
+ NULL, /* the action function table for audio stream */
{0}, /* Default AVRCP controller name */
{0}, /* Default AVRCP target name */
};
/* This configuration to be used when we are using AVRCP1.3 */
-extern const tBTA_AV_CFG bta_av_cfg_compatibility = {
- BTA_AV_RC_COMP_ID, /* AVRCP Company ID */
- BTA_AV_RC_SUPF_CT, /* AVRCP controller categories */
- AVRC_SUPF_TG_CAT1, /* Only support CAT1 for AVRCP1.3 */
- 6, /* AVDTP audio channel max data queue size */
- false, /* true, to accept AVRC 1.3 group nevigation command */
- 2, /* company id count in p_meta_co_ids */
+const tBTA_AV_CFG bta_av_cfg_compatibility = {
+ BTA_AV_RC_COMP_ID, /* AVRCP Company ID */
+ 512, /* AVRCP MTU at L2CAP for control channel */
+ BTA_AV_MAX_RC_BR_MTU, /* AVRCP MTU at L2CAP for browsing channel */
+ BTA_AV_RC_SUPF_CT, /* AVRCP controller categories */
+ AVRC_SUPF_TG_CAT1, /* Only support CAT1 for AVRCP1.3 */
+ 672, /* AVDTP signaling channel MTU at L2CAP */
+ MAX_3MBPS_AVDTP_MTU, /* AVDTP audio transport channel MTU at L2CAP */
+ bta_av_audio_flush_to, /* AVDTP audio transport channel flush timeout */
+ 6, /* AVDTP audio channel max data queue size */
+ false, /* true, to accept AVRC 1.3 group nevigation command */
+ 2, /* company id count in p_meta_co_ids */
BTA_AV_NUM_RC_EVT_IDS_AVRCP13, /* event id count for AVRCP1.3 */
BTA_AV_RC_PASS_RSP_CODE, /* the default response code for pass
through commands */
@@ -170,8 +202,9 @@ extern const tBTA_AV_CFG bta_av_cfg_compatibility = {
bta_av_meta_caps_evt_ids_avrcp13, /* the the metadata Get Capabilities
response for event id, compatible
with AVRCP1.3 */
- BTA_AV_RC_CT_NAME, /* Default AVRCP controller name */
- BTA_AV_RC_TG_NAME /* Default AVRCP target name */
+ NULL, /* the action function table for audio stream */
+ BTA_AV_RC_CT_NAME, /* Default AVRCP controller name */
+ BTA_AV_RC_TG_NAME /* Default AVRCP target name */
};
const tBTA_AV_CFG* p_bta_av_cfg = NULL;
diff --git a/bta/av/bta_av_ci.cc b/bta/av/bta_av_ci.cc
index b191e8216..e92c8d61a 100644
--- a/bta/av/bta_av_ci.cc
+++ b/bta/av/bta_av_ci.cc
@@ -25,10 +25,15 @@
#define LOG_TAG "bt_bta_av"
-#include "bta/av/bta_av_int.h"
-#include "osi/include/allocator.h"
#include "osi/include/log.h"
+#include "bta_av_ci.h"
+#include "bta_api.h"
+#include "bta_av_int.h"
+#include "bta_sys.h"
+
+#include <string.h>
+
/*******************************************************************************
*
* Function bta_av_ci_src_data_ready
@@ -41,7 +46,7 @@
*
******************************************************************************/
void bta_av_ci_src_data_ready(tBTA_AV_CHNL chnl) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->layer_specific = chnl;
p_buf->event = BTA_AV_CI_SRC_DATA_READY_EVT;
@@ -65,11 +70,11 @@ void bta_av_ci_src_data_ready(tBTA_AV_CHNL chnl) {
void bta_av_ci_setconfig(tBTA_AV_HNDL bta_av_handle, uint8_t err_code,
uint8_t category, uint8_t num_seid, uint8_t* p_seid,
bool recfg_needed, uint8_t avdt_handle) {
- LOG_INFO(
- "%s: bta_av_handle=0x%x err_code=%d category=%d "
- "num_seid=%d recfg_needed=%s avdt_handle=%d",
- __func__, bta_av_handle, err_code, category, num_seid,
- recfg_needed ? "true" : "false", avdt_handle);
+ LOG_DEBUG(LOG_TAG,
+ "%s: bta_av_handle=0x%x err_code=%d category=%d "
+ "num_seid=%d recfg_needed=%s avdt_handle=%d",
+ __func__, bta_av_handle, err_code, category, num_seid,
+ recfg_needed ? "true" : "false", avdt_handle);
tBTA_AV_CI_SETCONFIG* p_buf =
(tBTA_AV_CI_SETCONFIG*)osi_malloc(sizeof(tBTA_AV_CI_SETCONFIG));
diff --git a/bta/av/bta_av_int.h b/bta/av/bta_av_int.h
index 2f49a7743..3925e55c5 100644
--- a/bta/av/bta_av_int.h
+++ b/bta/av/bta_av_int.h
@@ -24,20 +24,13 @@
#ifndef BTA_AV_INT_H
#define BTA_AV_INT_H
-#include <cstdint>
-#include <string>
-
-#include "bta/av/bta_av_int.h"
-#include "bta/include/bta_av_api.h"
-#include "bta/include/bta_av_co.h"
-#include "bta/sys/bta_sys.h"
+#include "avdt_api.h"
+#include "bta_api.h"
+#include "bta_av_api.h"
+#include "bta_av_co.h"
+#include "bta_sys.h"
#include "osi/include/list.h"
-#include "stack/include/avdt_api.h"
-#include "stack/include/bt_types.h"
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
+#include "stack/include/a2dp_api.h"
/*****************************************************************************
* Constants
@@ -90,7 +83,6 @@ enum {
BTA_AV_AVDT_DISCONNECT_EVT,
BTA_AV_ROLE_CHANGE_EVT,
BTA_AV_AVDT_DELAY_RPT_EVT,
- BTA_AV_AVDT_DELAY_RPT_CFM_EVT,
BTA_AV_ACP_CONNECT_EVT,
BTA_AV_API_OFFLOAD_START_EVT,
BTA_AV_API_OFFLOAD_START_RSP_EVT,
@@ -199,7 +191,7 @@ typedef void (*tBTA_AV_CO_UPDATE_MTU)(tBTA_AV_HNDL bta_av_handle,
const RawAddress& peer_addr,
uint16_t mtu);
-typedef btav_a2dp_scmst_info_t (*tBTA_AV_CO_GET_SCMST_INFO)(
+typedef bool (*tBTA_AV_CO_CONTENT_PROTECT_IS_ACTIVE)(
const RawAddress& peer_addr);
/* the call-out functions for one stream */
@@ -215,56 +207,46 @@ typedef struct {
tBTA_AV_CO_DATAPATH data;
tBTA_AV_CO_DELAY delay;
tBTA_AV_CO_UPDATE_MTU update_mtu;
- tBTA_AV_CO_GET_SCMST_INFO get_scmst_info;
+ tBTA_AV_CO_CONTENT_PROTECT_IS_ACTIVE cp_is_active;
} tBTA_AV_CO_FUNCTS;
/* data type for BTA_AV_API_ENABLE_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_AV_CBACK* p_cback;
tBTA_AV_FEAT features;
+ tBTA_SEC sec_mask;
} tBTA_AV_API_ENABLE;
/* data type for BTA_AV_API_REGISTER_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
char p_service_name[BTA_SERVICE_NAME_LEN + 1];
uint8_t app_id;
tBTA_AV_SINK_DATA_CBACK* p_app_sink_data_cback;
uint16_t service_uuid;
} tBTA_AV_API_REG;
-typedef enum : uint8_t {
+enum {
BTA_AV_RS_NONE, /* straight API call */
BTA_AV_RS_OK, /* the role switch result - successful */
BTA_AV_RS_FAIL, /* the role switch result - failed */
BTA_AV_RS_DONE /* the role switch is done - continue */
-} tBTA_AV_RS_RES;
-
-inline std::string bta_av_role_switch_result_text(
- const tBTA_AV_RS_RES& result) {
- switch (result) {
- CASE_RETURN_TEXT(BTA_AV_RS_NONE);
- CASE_RETURN_TEXT(BTA_AV_RS_OK);
- CASE_RETURN_TEXT(BTA_AV_RS_FAIL);
- CASE_RETURN_TEXT(BTA_AV_RS_DONE);
- default:
- return std::string("UNKNOWN");
- }
-}
-
+};
+typedef uint8_t tBTA_AV_RS_RES;
/* data type for BTA_AV_API_OPEN_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress bd_addr;
bool use_rc;
+ tBTA_SEC sec_mask;
tBTA_AV_RS_RES switch_res;
uint16_t uuid; /* uuid of initiator */
} tBTA_AV_API_OPEN;
/* data type for BTA_AV_API_STOP_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
bool suspend;
bool flush;
bool reconfig_stop; // True if the stream is stopped for reconfiguration
@@ -272,19 +254,20 @@ typedef struct {
/* data type for BTA_AV_API_DISCONNECT_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
+ RawAddress bd_addr;
} tBTA_AV_API_DISCNT;
/* data type for BTA_AV_API_PROTECT_REQ_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint8_t* p_data;
uint16_t len;
} tBTA_AV_API_PROTECT_REQ;
/* data type for BTA_AV_API_PROTECT_RSP_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint8_t* p_data;
uint16_t len;
uint8_t error_code;
@@ -292,31 +275,27 @@ typedef struct {
/* data type for BTA_AV_API_REMOTE_CMD_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tAVRC_MSG_PASS msg;
uint8_t label;
} tBTA_AV_API_REMOTE_CMD;
/* data type for BTA_AV_API_VENDOR_CMD_EVT and RSP */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tAVRC_MSG_VENDOR msg;
uint8_t label;
} tBTA_AV_API_VENDOR;
/* data type for BTA_AV_API_RC_OPEN_EVT */
-typedef struct {
- BT_HDR_RIGID hdr;
-} tBTA_AV_API_OPEN_RC;
+typedef struct { BT_HDR hdr; } tBTA_AV_API_OPEN_RC;
/* data type for BTA_AV_API_RC_CLOSE_EVT */
-typedef struct {
- BT_HDR_RIGID hdr;
-} tBTA_AV_API_CLOSE_RC;
+typedef struct { BT_HDR hdr; } tBTA_AV_API_CLOSE_RC;
/* data type for BTA_AV_API_META_RSP_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
bool is_rsp;
uint8_t label;
tBTA_AV_CODE rsp_code;
@@ -325,7 +304,7 @@ typedef struct {
/* data type for BTA_AV_API_RECONFIG_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint8_t codec_info[AVDT_CODEC_SIZE]; /* codec configuration */
uint8_t* p_protect_info;
uint8_t num_protect;
@@ -335,7 +314,7 @@ typedef struct {
/* data type for BTA_AV_CI_SETCONFIG_OK_EVT and BTA_AV_CI_SETCONFIG_FAIL_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_AV_HNDL hndl;
uint8_t err_code;
uint8_t category;
@@ -347,7 +326,7 @@ typedef struct {
/* data type for all stream events from AVDTP */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
AvdtpSepConfig cfg; /* configuration/capabilities parameters */
tAVDT_CTRL msg; /* AVDTP callback message parameters */
RawAddress bd_addr; /* bd address */
@@ -359,7 +338,7 @@ typedef struct {
/* data type for BTA_AV_AVRC_MSG_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tAVRC_MSG msg;
uint8_t handle;
uint8_t label;
@@ -368,33 +347,33 @@ typedef struct {
/* data type for BTA_AV_AVRC_OPEN_EVT, BTA_AV_AVRC_CLOSE_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress peer_addr;
uint8_t handle;
} tBTA_AV_RC_CONN_CHG;
/* data type for BTA_AV_CONN_CHG_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress peer_addr;
bool is_up;
} tBTA_AV_CONN_CHG;
/* data type for BTA_AV_ROLE_CHANGE_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint8_t new_role;
uint8_t hci_status;
} tBTA_AV_ROLE_RES;
/* data type for BTA_AV_SDP_DISC_OK_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
} tBTA_AV_SDP_RES;
/* data type for BTA_AV_API_OFFLOAD_RSP_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_AV_STATUS status;
} tBTA_AV_API_STATUS_RSP;
@@ -407,23 +386,20 @@ typedef struct {
p_app_sink_data_cback; /* Sink application callback for media packets */
} tBTA_AV_SEP;
-enum : uint8_t {
- /* initiator/acceptor role for adaption */
- BTA_AV_ROLE_AD_INT = 0x00, /* initiator */
- BTA_AV_ROLE_AD_ACP = 0x01, /* acceptor */
+/* initiator/acceptor role for adaption */
+#define BTA_AV_ROLE_AD_INT 0x00 /* initiator */
+#define BTA_AV_ROLE_AD_ACP 0x01 /* acceptor */
- /* initiator/acceptor signaling roles */
- BTA_AV_ROLE_START_ACP = 0x00,
- BTA_AV_ROLE_START_INT = 0x10, /* do not change this value */
+/* initiator/acceptor signaling roles */
+#define BTA_AV_ROLE_START_ACP 0x00
+#define BTA_AV_ROLE_START_INT 0x10 /* do not change this value */
- BTA_AV_ROLE_SUSPEND = 0x20, /* suspending on start */
- BTA_AV_ROLE_SUSPEND_OPT = 0x40, /* Suspend on Start option is set */
-};
-typedef uint8_t tBTA_AV_ROLE;
+#define BTA_AV_ROLE_SUSPEND 0x20 /* suspending on start */
+#define BTA_AV_ROLE_SUSPEND_OPT 0x40 /* Suspend on Start option is set */
/* union of all event datatypes */
union tBTA_AV_DATA {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_AV_API_ENABLE api_enable;
tBTA_AV_API_REG api_reg;
tBTA_AV_API_OPEN api_open;
@@ -482,6 +458,7 @@ typedef union {
// TODO: This should be renamed and changed to a proper class
struct tBTA_AV_SCB final {
public:
+ const tBTA_AV_ACT* p_act_tbl; /* the action table for stream state machine */
const tBTA_AV_CO_FUNCTS* p_cos; /* the associated callout functions */
bool sdp_discovery_started; /* variable to determine whether SDP is started */
tBTA_AV_SEP seps[BTAV_A2DP_CODEC_INDEX_MAX];
@@ -491,11 +468,9 @@ struct tBTA_AV_SCB final {
tAVDT_SEP_INFO sep_info[BTA_AV_NUM_SEPS]; /* stream discovery results */
AvdtpSepConfig cfg; /* local SEP configuration */
alarm_t* avrc_ct_timer; /* delay timer for AVRC CT */
- alarm_t* link_signalling_timer;
- alarm_t*
- accept_signalling_timer; /* timer to monitor signalling when accepting */
uint16_t l2c_cid; /* L2CAP channel ID */
uint16_t stream_mtu; /* MTU of stream */
+ tBTA_SEC sec_mask; /* security mask */
uint8_t media_type; /* Media type: AVDT_MEDIA_TYPE_* */
bool cong; /* true if AVDTP congested */
tBTA_AV_STATUS open_status; /* open failure status */
@@ -619,6 +594,9 @@ typedef struct {
tBTA_AV_CBACK* p_cback; /* application callback function */
tBTA_AV_RCB rcb[BTA_AV_NUM_RCB]; /* RCB control block */
tBTA_AV_LCB lcb[BTA_AV_NUM_LINKS + 1]; /* link control block */
+ alarm_t* link_signalling_timer;
+ alarm_t*
+ accept_signalling_timer; /* timer to monitor signalling when accepting */
uint32_t sdp_a2dp_handle; /* SDP record handle for audio src */
uint32_t sdp_a2dp_snk_handle; /* SDP record handle for audio snk */
tBTA_AV_FEAT features; /* features mask */
@@ -637,6 +615,7 @@ typedef struct {
uint8_t rc_acp_idx; /* (index + 1) to RCB */
uint8_t rs_idx; /* (index + 1) to SCB for the one waiting for RS on open */
bool sco_occupied; /* true if SCO is being used or call is in progress */
+ uint8_t audio_streams; /* handle mask of streaming audio channels */
} tBTA_AV_CB;
// total attempts are half seconds
@@ -648,7 +627,7 @@ class tBT_A2DP_OFFLOAD {
public:
uint32_t codec_type; /* codec types ex: SBC/AAC/LDAC/APTx */
uint16_t max_latency; /* maximum latency */
- std::array<uint8_t, 2> scms_t_enable; /* SCMS-T enable */
+ uint16_t scms_t_enable; /* content protection enable */
uint32_t sample_rate; /* Sample rates ex: 44.1/48/88.2/96 Khz */
uint8_t bits_per_sample; /* bits per sample ex: 16/24/32 */
uint8_t ch_mode; /* None:0 Left:1 Right:2 */
@@ -681,6 +660,7 @@ extern const tBTA_AV_CFG bta_av_cfg_compatibility;
extern uint16_t* p_bta_av_rc_id;
extern uint16_t* p_bta_av_rc_id_ac;
+extern const tBTA_AV_SACT bta_av_a2dp_action[];
extern const tBTA_AV_CO_FUNCTS bta_av_a2dp_cos;
extern void bta_av_sink_data_cback(uint8_t handle, BT_HDR* p_pkt,
uint32_t time_stamp, uint8_t m_pt);
@@ -715,7 +695,7 @@ extern void bta_av_sm_execute(tBTA_AV_CB* p_cb, uint16_t event,
tBTA_AV_DATA* p_data);
extern void bta_av_ssm_execute(tBTA_AV_SCB* p_scb, uint16_t event,
tBTA_AV_DATA* p_data);
-extern bool bta_av_hdl_event(BT_HDR_RIGID* p_msg);
+extern bool bta_av_hdl_event(BT_HDR* p_msg);
extern const char* bta_av_evt_code(uint16_t evt_code);
extern bool bta_av_switch_if_needed(tBTA_AV_SCB* p_scb);
extern bool bta_av_link_role_ok(tBTA_AV_SCB* p_scb, uint8_t bits);
@@ -804,6 +784,5 @@ extern void bta_av_open_at_inc(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data);
extern void bta_av_offload_req(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data);
extern void bta_av_offload_rsp(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data);
extern void bta_av_vendor_offload_stop(void);
-extern void bta_av_st_rc_timer(tBTA_AV_SCB* p_scb, tBTA_AV_DATA* p_data);
#endif /* BTA_AV_INT_H */
diff --git a/bta/av/bta_av_main.cc b/bta/av/bta_av_main.cc
index 887171853..61e4b4e89 100644
--- a/bta/av/bta_av_main.cc
+++ b/bta/av/bta_av_main.cc
@@ -24,22 +24,25 @@
#define LOG_TAG "bt_bta_av"
-#include <cstdint>
+#include <base/logging.h>
+#include <string.h>
-#include "bt_target.h" // Must be first to define build configuration
+#include "bt_target.h"
+#include "osi/include/log.h"
+#include "osi/include/osi.h"
+#include "osi/include/properties.h"
-#include "bta/av/bta_av_int.h"
-#include "bta/include/bta_ar_api.h"
-#include "bta/include/utl.h"
-#include "btif/avrcp/avrcp_service.h"
+#include "bta_av_co.h"
+#include "bta_av_int.h"
#include "btif/include/btif_av_co.h"
#include "btif/include/btif_config.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "osi/include/properties.h"
-#include "stack/include/acl_api.h"
-#include "types/hci_role.h"
+#include "l2c_api.h"
+#include "l2cdefs.h"
+#include "utl.h"
+
+#if (BTA_AR_INCLUDED == TRUE)
+#include "bta_ar_api.h"
+#endif
/*****************************************************************************
* Constants and types
@@ -83,12 +86,86 @@
#endif
#ifndef AVRCP_DEFAULT_VERSION
-#define AVRCP_DEFAULT_VERSION AVRCP_1_5_STRING
+#define AVRCP_DEFAULT_VERSION AVRCP_1_4_STRING
#endif
/* state machine states */
enum { BTA_AV_INIT_ST, BTA_AV_OPEN_ST };
+/* state machine action enumeration list */
+enum {
+ BTA_AV_DISABLE,
+ BTA_AV_RC_OPENED,
+ BTA_AV_RC_REMOTE_CMD,
+ BTA_AV_RC_VENDOR_CMD,
+ BTA_AV_RC_VENDOR_RSP,
+ BTA_AV_RC_FREE_RSP,
+ BTA_AV_RC_FREE_BROWSE_MSG,
+ BTA_AV_RC_META_RSP,
+ BTA_AV_RC_MSG,
+ BTA_AV_RC_CLOSE,
+ BTA_AV_RC_BROWSE_CLOSE,
+ BTA_AV_NUM_ACTIONS
+};
+
+#define BTA_AV_IGNORE BTA_AV_NUM_ACTIONS
+
+/* type for action functions */
+typedef void (*tBTA_AV_ACTION)(tBTA_AV_CB* p_cb, tBTA_AV_DATA* p_data);
+
+/* action functions */
+const tBTA_AV_ACTION bta_av_action[] = {
+ bta_av_disable,
+ bta_av_rc_opened,
+ bta_av_rc_remote_cmd,
+ bta_av_rc_vendor_cmd,
+ bta_av_rc_vendor_rsp,
+ bta_av_rc_free_rsp,
+ bta_av_rc_free_browse_msg,
+ bta_av_rc_meta_rsp,
+ bta_av_rc_msg,
+ bta_av_rc_close,
+};
+
+/* state table information */
+#define BTA_AV_ACTION_COL 0 /* position of actions */
+#define BTA_AV_NEXT_STATE 1 /* position of next state */
+#define BTA_AV_NUM_COLS 2 /* number of columns in state tables */
+
+/* state table for init state */
+static const uint8_t bta_av_st_init[][BTA_AV_NUM_COLS] = {
+ /* Event Action 1 Next state */
+ /* API_DISABLE_EVT */ {BTA_AV_DISABLE, BTA_AV_INIT_ST},
+ /* API_REMOTE_CMD_EVT */ {BTA_AV_IGNORE, BTA_AV_INIT_ST},
+ /* API_VENDOR_CMD_EVT */ {BTA_AV_IGNORE, BTA_AV_INIT_ST},
+ /* API_VENDOR_RSP_EVT */ {BTA_AV_IGNORE, BTA_AV_INIT_ST},
+ /* API_META_RSP_EVT */ {BTA_AV_RC_FREE_RSP, BTA_AV_INIT_ST},
+ /* API_RC_CLOSE_EVT */ {BTA_AV_IGNORE, BTA_AV_INIT_ST},
+ /* AVRC_OPEN_EVT */ {BTA_AV_RC_OPENED, BTA_AV_OPEN_ST},
+ /* AVRC_MSG_EVT */ {BTA_AV_RC_FREE_BROWSE_MSG, BTA_AV_INIT_ST},
+ /* AVRC_NONE_EVT */ {BTA_AV_IGNORE, BTA_AV_INIT_ST},
+};
+
+/* state table for open state */
+static const uint8_t bta_av_st_open[][BTA_AV_NUM_COLS] = {
+ /* Event Action 1 Next state */
+ /* API_DISABLE_EVT */ {BTA_AV_DISABLE, BTA_AV_INIT_ST},
+ /* API_REMOTE_CMD_EVT */ {BTA_AV_RC_REMOTE_CMD, BTA_AV_OPEN_ST},
+ /* API_VENDOR_CMD_EVT */ {BTA_AV_RC_VENDOR_CMD, BTA_AV_OPEN_ST},
+ /* API_VENDOR_RSP_EVT */ {BTA_AV_RC_VENDOR_RSP, BTA_AV_OPEN_ST},
+ /* API_META_RSP_EVT */ {BTA_AV_RC_META_RSP, BTA_AV_OPEN_ST},
+ /* API_RC_CLOSE_EVT */ {BTA_AV_RC_CLOSE, BTA_AV_OPEN_ST},
+ /* AVRC_OPEN_EVT */ {BTA_AV_RC_OPENED, BTA_AV_OPEN_ST},
+ /* AVRC_MSG_EVT */ {BTA_AV_RC_MSG, BTA_AV_OPEN_ST},
+ /* AVRC_NONE_EVT */ {BTA_AV_IGNORE, BTA_AV_INIT_ST},
+};
+
+/* type for state table */
+typedef const uint8_t (*tBTA_AV_ST_TBL)[BTA_AV_NUM_COLS];
+
+/* state table */
+static const tBTA_AV_ST_TBL bta_av_st_tbl[] = {bta_av_st_init, bta_av_st_open};
+
typedef void (*tBTA_AV_NSM_ACT)(tBTA_AV_DATA* p_data);
static void bta_av_api_enable(tBTA_AV_DATA* p_data);
static void bta_av_api_register(tBTA_AV_DATA* p_data);
@@ -101,6 +178,26 @@ static void bta_av_sco_chg_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
static void bta_av_sys_rs_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
uint8_t app_id, const RawAddress& peer_addr);
+/* action functions */
+const tBTA_AV_NSM_ACT bta_av_nsm_act[] = {
+ bta_av_api_enable, /* BTA_AV_API_ENABLE_EVT */
+ bta_av_api_register, /* BTA_AV_API_REGISTER_EVT */
+ bta_av_api_deregister, /* BTA_AV_API_DEREGISTER_EVT */
+ bta_av_api_disconnect, /* BTA_AV_API_DISCONNECT_EVT */
+ bta_av_ci_data, /* BTA_AV_CI_SRC_DATA_READY_EVT */
+ bta_av_sig_chg, /* BTA_AV_SIG_CHG_EVT */
+ bta_av_signalling_timer, /* BTA_AV_SIGNALLING_TIMER_EVT */
+ bta_av_rc_disc_done, /* BTA_AV_SDP_AVRC_DISC_EVT */
+ bta_av_rc_closed, /* BTA_AV_AVRC_CLOSE_EVT */
+ bta_av_rc_browse_opened, /* BTA_AV_AVRC_BROWSE_OPEN_EVT */
+ bta_av_rc_browse_closed, /* BTA_AV_AVRC_BROWSE_CLOSE_EVT */
+ bta_av_conn_chg, /* BTA_AV_CONN_CHG_EVT */
+ bta_av_dereg_comp, /* BTA_AV_DEREG_COMP_EVT */
+ bta_av_rpc_conn, /* BTA_AV_AVDT_RPT_CONN_EVT */
+ bta_av_api_to_ssm, /* BTA_AV_API_START_EVT */
+ bta_av_api_to_ssm, /* BTA_AV_API_STOP_EVT */
+};
+
/*****************************************************************************
* Global data
****************************************************************************/
@@ -143,13 +240,15 @@ static void bta_av_api_enable(tBTA_AV_DATA* p_data) {
bta_sys_remove_uuid(UUID_SERVCLASS_AUDIO_SINK);
}
#endif
+#if (BTA_AR_INCLUDED == TRUE)
// deregister from AVDT
- bta_ar_dereg_avdt();
+ bta_ar_dereg_avdt(BTA_ID_AV);
// deregister from AVCT
- bta_ar_dereg_avrc(UUID_SERVCLASS_AV_REMOTE_CONTROL);
- bta_ar_dereg_avrc(UUID_SERVCLASS_AV_REM_CTRL_TARGET);
- bta_ar_dereg_avct();
+ bta_ar_dereg_avrc(UUID_SERVCLASS_AV_REMOTE_CONTROL, BTA_ID_AV);
+ bta_ar_dereg_avrc(UUID_SERVCLASS_AV_REM_CTRL_TARGET, BTA_ID_AV);
+ bta_ar_dereg_avct(BTA_ID_AV);
+#endif
}
/* initialize control block */
@@ -160,9 +259,18 @@ static void bta_av_api_enable(tBTA_AV_DATA* p_data) {
bta_av_cb.rc_acp_handle = BTA_AV_RC_HANDLE_NONE;
+ /*
+ * TODO: The "disable" event handling is missing - there we need
+ * to alarm_free() the alarms below.
+ */
+ bta_av_cb.link_signalling_timer = alarm_new("bta_av.link_signalling_timer");
+ bta_av_cb.accept_signalling_timer =
+ alarm_new("bta_av.accept_signalling_timer");
+
/* store parameters */
bta_av_cb.p_cback = p_data->api_enable.p_cback;
bta_av_cb.features = p_data->api_enable.features;
+ bta_av_cb.sec_mask = p_data->api_enable.sec_mask;
tBTA_AV_ENABLE enable;
enable.features = bta_av_cb.features;
@@ -294,7 +402,7 @@ void tBTA_AV_SCB::OnConnected(const RawAddress& peer_address) {
peer_address_ = peer_address;
if (peer_address.IsEmpty()) {
- LOG_ERROR("%s: Invalid peer address: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s: Invalid peer address: %s", __func__,
peer_address.ToString().c_str());
return;
}
@@ -304,8 +412,8 @@ void tBTA_AV_SCB::OnConnected(const RawAddress& peer_address) {
size_t version_value_size = sizeof(avdtp_version);
if (!btif_config_get_bin(peer_address_.ToString(), AVDTP_VERSION_CONFIG_KEY,
(uint8_t*)&avdtp_version, &version_value_size)) {
- LOG_WARN("%s: Failed to read cached peer AVDTP version for %s", __func__,
- peer_address_.ToString().c_str());
+ LOG_WARN(LOG_TAG, "%s: Failed to read cached peer AVDTP version for %s",
+ __func__, peer_address_.ToString().c_str());
} else {
SetAvdtpVersion(avdtp_version);
}
@@ -318,8 +426,8 @@ void tBTA_AV_SCB::OnDisconnected() {
void tBTA_AV_SCB::SetAvdtpVersion(uint16_t avdtp_version) {
avdtp_version_ = avdtp_version;
- LOG_INFO("%s: AVDTP version for %s set to 0x%x", __func__,
- peer_address_.ToString().c_str(), avdtp_version_);
+ LOG_DEBUG(LOG_TAG, "%s: AVDTP version for %s set to 0x%x", __func__,
+ peer_address_.ToString().c_str(), avdtp_version_);
}
/*******************************************************************************
@@ -329,8 +437,12 @@ void bta_av_conn_cback(UNUSED_ATTR uint8_t handle, const RawAddress& bd_addr,
uint16_t evt = 0;
tBTA_AV_SCB* p_scb = NULL;
+#if (BTA_AR_INCLUDED == TRUE)
if (event == BTA_AR_AVDT_CONN_EVT || event == AVDT_CONNECT_IND_EVT ||
event == AVDT_DISCONNECT_IND_EVT)
+#else
+ if (event == AVDT_CONNECT_IND_EVT || event == AVDT_DISCONNECT_IND_EVT)
+#endif
{
evt = BTA_AV_SIG_CHG_EVT;
if (event == AVDT_DISCONNECT_IND_EVT) {
@@ -351,7 +463,7 @@ void bta_av_conn_cback(UNUSED_ATTR uint8_t handle, const RawAddress& bd_addr,
APPL_TRACE_DEBUG("%s: bta_handle x%x, role x%x", __func__, p_scb->hndl,
p_scb->role);
}
- LOG_INFO("%s: conn_cback bd_addr: %s", __func__,
+ LOG_INFO(LOG_TAG, "%s: conn_cback bd_addr: %s", __func__,
bd_addr.ToString().c_str());
bta_sys_sendmsg(p_msg);
}
@@ -392,11 +504,12 @@ static void bta_av_api_register(tBTA_AV_DATA* p_data) {
char* p_service_name;
tBTA_UTL_COD cod;
- if (bta_av_cb.disabling || (bta_av_cb.features == 0)) {
+ if (bta_av_cb.disabling ||
+ (bta_av_cb.features == 0 && bta_av_cb.sec_mask == 0)) {
APPL_TRACE_WARNING(
- "%s: AV instance (features=%#x, reg_audio=%#x) is not "
+ "%s: AV instance (features=%#x, sec_mask=%#x, reg_audio=%#x) is not "
"ready for app_id %d",
- __func__, bta_av_cb.features, bta_av_cb.reg_audio,
+ __func__, bta_av_cb.features, bta_av_cb.sec_mask, bta_av_cb.reg_audio,
p_data->api_reg.app_id);
tBTA_AV_API_REG* p_buf =
(tBTA_AV_API_REG*)osi_malloc(sizeof(tBTA_AV_API_REG));
@@ -415,7 +528,8 @@ static void bta_av_api_register(tBTA_AV_DATA* p_data) {
char avrcp_version[PROPERTY_VALUE_MAX] = {0};
osi_property_get(AVRCP_VERSION_PROPERTY, avrcp_version,
AVRCP_DEFAULT_VERSION);
- LOG_INFO("%s: AVRCP version used for sdp: \"%s\"", __func__, avrcp_version);
+ LOG_INFO(LOG_TAG, "%s: AVRCP version used for sdp: \"%s\"", __func__,
+ avrcp_version);
uint16_t profile_initialized = p_data->api_reg.service_uuid;
if (profile_initialized == UUID_SERVCLASS_AUDIO_SINK) {
@@ -424,7 +538,7 @@ static void bta_av_api_register(tBTA_AV_DATA* p_data) {
p_bta_av_cfg = &bta_av_cfg;
if (!strncmp(AVRCP_1_3_STRING, avrcp_version, sizeof(AVRCP_1_3_STRING))) {
- LOG_INFO("%s: AVRCP 1.3 capabilites used", __func__);
+ LOG_INFO(LOG_TAG, "%s: AVRCP 1.3 capabilites used", __func__);
p_bta_av_cfg = &bta_av_cfg_compatibility;
}
}
@@ -450,49 +564,53 @@ static void bta_av_api_register(tBTA_AV_DATA* p_data) {
if (bta_av_cb.reg_audio == 0) {
/* the first channel registered. register to AVDTP */
- reg.ctrl_mtu = 672;
+ reg.ctrl_mtu = p_bta_av_cfg->sig_mtu;
reg.ret_tout = BTA_AV_RET_TOUT;
reg.sig_tout = BTA_AV_SIG_TOUT;
reg.idle_tout = BTA_AV_IDLE_TOUT;
+ reg.sec_mask = bta_av_cb.sec_mask;
reg.scb_index = p_scb->hdi;
- bta_ar_reg_avdt(&reg, bta_av_conn_cback);
+#if (BTA_AR_INCLUDED == TRUE)
+ bta_ar_reg_avdt(&reg, bta_av_conn_cback, BTA_ID_AV);
+#endif
bta_sys_role_chg_register(&bta_av_sys_rs_cback);
/* create remote control TG service if required */
if (bta_av_cb.features & (BTA_AV_FEAT_RCTG)) {
- /* register with no authorization; let AVDTP use authorization instead
- */
- bta_ar_reg_avct();
+/* register with no authorization; let AVDTP use authorization instead */
+#if (BTA_AR_INCLUDED == TRUE)
+#if (BTA_AV_WITH_AVCTP_AUTHORIZATION == TRUE)
+ bta_ar_reg_avct(p_bta_av_cfg->avrc_mtu, p_bta_av_cfg->avrc_br_mtu,
+ bta_av_cb.sec_mask, BTA_ID_AV);
+#else
+ bta_ar_reg_avct(p_bta_av_cfg->avrc_mtu, p_bta_av_cfg->avrc_br_mtu,
+ (uint8_t)(bta_av_cb.sec_mask & (~BTA_SEC_AUTHORIZE)),
+ BTA_ID_AV);
+#endif
/* For the Audio Sink role we support additional TG to support
* absolute volume.
*/
- if (is_new_avrcp_enabled()) {
- APPL_TRACE_DEBUG("%s: newavrcp is the owner of the AVRCP Target SDP "
- "record. Don't create the SDP record", __func__);
+ uint16_t profile_version = AVRC_REV_1_0;
+
+ if (!strncmp(AVRCP_1_6_STRING, avrcp_version,
+ sizeof(AVRCP_1_6_STRING))) {
+ profile_version = AVRC_REV_1_6;
+ } else if (!strncmp(AVRCP_1_5_STRING, avrcp_version,
+ sizeof(AVRCP_1_5_STRING))) {
+ profile_version = AVRC_REV_1_5;
+ } else if (!strncmp(AVRCP_1_3_STRING, avrcp_version,
+ sizeof(AVRCP_1_3_STRING))) {
+ profile_version = AVRC_REV_1_3;
} else {
- APPL_TRACE_DEBUG("%s: newavrcp is not enabled. Create SDP record",
- __func__);
-
- uint16_t profile_version = AVRC_REV_1_0;
- if (!strncmp(AVRCP_1_6_STRING, avrcp_version,
- sizeof(AVRCP_1_6_STRING))) {
- profile_version = AVRC_REV_1_6;
- } else if (!strncmp(AVRCP_1_5_STRING, avrcp_version,
- sizeof(AVRCP_1_5_STRING))) {
- profile_version = AVRC_REV_1_5;
- } else if (!strncmp(AVRCP_1_3_STRING, avrcp_version,
- sizeof(AVRCP_1_3_STRING))) {
- profile_version = AVRC_REV_1_3;
- } else {
- profile_version = AVRC_REV_1_4;
- }
-
- bta_ar_reg_avrc(
- UUID_SERVCLASS_AV_REM_CTRL_TARGET, "AV Remote Control Target", NULL,
- p_bta_av_cfg->avrc_tg_cat,
- (bta_av_cb.features & BTA_AV_FEAT_BROWSE), profile_version);
+ profile_version = AVRC_REV_1_4;
}
+
+ bta_ar_reg_avrc(
+ UUID_SERVCLASS_AV_REM_CTRL_TARGET, "AV Remote Control Target", NULL,
+ p_bta_av_cfg->avrc_tg_cat, BTA_ID_AV,
+ (bta_av_cb.features & BTA_AV_FEAT_BROWSE), profile_version);
+#endif
}
/* Set the Capturing service class bit */
@@ -525,11 +643,13 @@ static void bta_av_api_register(tBTA_AV_DATA* p_data) {
avdtp_stream_config.p_avdt_ctrl_cback = &bta_av_proc_stream_evt;
/* set up the audio stream control block */
+ p_scb->p_act_tbl = (const tBTA_AV_ACT*)bta_av_a2dp_action;
p_scb->p_cos = &bta_av_a2dp_cos;
p_scb->media_type = AVDT_MEDIA_TYPE_AUDIO;
avdtp_stream_config.cfg.psc_mask = AVDT_PSC_TRANS;
avdtp_stream_config.media_type = AVDT_MEDIA_TYPE_AUDIO;
- avdtp_stream_config.mtu = MAX_3MBPS_AVDTP_MTU;
+ avdtp_stream_config.mtu = p_bta_av_cfg->audio_mtu;
+ avdtp_stream_config.flush_to = L2CAP_DEFAULT_FLUSH_TO;
btav_a2dp_codec_index_t codec_index_min = BTAV_A2DP_CODEC_INDEX_SOURCE_MIN;
btav_a2dp_codec_index_t codec_index_max = BTAV_A2DP_CODEC_INDEX_SOURCE_MAX;
@@ -615,9 +735,19 @@ static void bta_av_api_register(tBTA_AV_DATA* p_data) {
if (bta_av_cb.features & (BTA_AV_FEAT_RCCT)) {
/* if TG is not supported, we need to register to AVCT now */
if ((bta_av_cb.features & (BTA_AV_FEAT_RCTG)) == 0) {
- bta_ar_reg_avct();
+#if (BTA_AR_INCLUDED == TRUE)
+#if (BTA_AV_WITH_AVCTP_AUTHORIZATION == TRUE)
+ bta_ar_reg_avct(p_bta_av_cfg->avrc_mtu, p_bta_av_cfg->avrc_br_mtu,
+ bta_av_cb.sec_mask, BTA_ID_AV);
+#else
+ bta_ar_reg_avct(p_bta_av_cfg->avrc_mtu, p_bta_av_cfg->avrc_br_mtu,
+ (uint8_t)(bta_av_cb.sec_mask & (~BTA_SEC_AUTHORIZE)),
+ BTA_ID_AV);
+#endif
+#endif
bta_av_rc_create(&bta_av_cb, AVCT_ACP, 0, BTA_AV_NUM_LINKS + 1);
}
+#if (BTA_AR_INCLUDED == TRUE)
/* create an SDP record as AVRC CT. We create 1.3 for SOURCE
* because we rely on feature bits being scanned by external
* devices more than the profile version itself.
@@ -626,15 +756,16 @@ static void bta_av_api_register(tBTA_AV_DATA* p_data) {
*/
if (profile_initialized == UUID_SERVCLASS_AUDIO_SOURCE) {
bta_ar_reg_avrc(UUID_SERVCLASS_AV_REMOTE_CONTROL, NULL, NULL,
- p_bta_av_cfg->avrc_ct_cat,
+ p_bta_av_cfg->avrc_ct_cat, BTA_ID_AV,
(bta_av_cb.features & BTA_AV_FEAT_BROWSE),
AVRC_REV_1_3);
} else if (profile_initialized == UUID_SERVCLASS_AUDIO_SINK) {
bta_ar_reg_avrc(UUID_SERVCLASS_AV_REMOTE_CONTROL, NULL, NULL,
- p_bta_av_cfg->avrc_ct_cat,
+ p_bta_av_cfg->avrc_ct_cat, BTA_ID_AV,
(bta_av_cb.features & BTA_AV_FEAT_BROWSE),
AVRC_REV_1_6);
}
+#endif
}
}
bta_av_cb.reg_audio |= BTA_AV_HNDL_TO_MSK(p_scb->hdi);
@@ -753,17 +884,20 @@ bool bta_av_chk_start(tBTA_AV_SCB* p_scb) {
// May need to update the flush timeout of this already started stream
if (p_scbi->co_started != bta_av_cb.audio_open_cnt) {
p_scbi->co_started = bta_av_cb.audio_open_cnt;
+ L2CA_SetFlushTimeout(
+ p_scbi->PeerAddress(),
+ p_bta_av_cfg->p_audio_flush_to[p_scbi->co_started - 1]);
}
}
}
}
- LOG_INFO(
- "%s: peer %s channel:%d bta_av_cb.audio_open_cnt:%d role:0x%x "
- "features:0x%x start:%s",
- __func__, p_scb->PeerAddress().ToString().c_str(), p_scb->chnl,
- bta_av_cb.audio_open_cnt, p_scb->role, bta_av_cb.features,
- logbool(start).c_str());
+ LOG_INFO(LOG_TAG,
+ "%s: peer %s channel:%d bta_av_cb.audio_open_cnt:%d role:0x%x "
+ "features:0x%x start:%s",
+ __func__, p_scb->PeerAddress().ToString().c_str(), p_scb->chnl,
+ bta_av_cb.audio_open_cnt, p_scb->role, bta_av_cb.features,
+ logbool(start).c_str());
return start;
}
@@ -781,13 +915,15 @@ void bta_av_restore_switch(void) {
tBTA_AV_CB* p_cb = &bta_av_cb;
int i;
uint8_t mask;
+ uint8_t set_policy = (HCI_ENABLE_SNIFF_MODE | HCI_ENABLE_MASTER_SLAVE_SWITCH);
APPL_TRACE_DEBUG("%s: reg_audio: 0x%x", __func__, bta_av_cb.reg_audio);
for (i = 0; i < BTA_AV_NUM_STRS; i++) {
mask = BTA_AV_HNDL_TO_MSK(i);
if (p_cb->conn_audio == mask) {
if (p_cb->p_scb[i]) {
- BTM_unblock_role_switch_for(p_cb->p_scb[i]->PeerAddress());
+ bta_sys_set_policy(BTA_ID_AV, set_policy,
+ p_cb->p_scb[i]->PeerAddress());
}
break;
}
@@ -808,8 +944,9 @@ static void bta_av_sys_rs_cback(UNUSED_ATTR tBTA_SYS_CONN_STATUS status,
const RawAddress& peer_addr) {
int i;
tBTA_AV_SCB* p_scb = NULL;
- tHCI_ROLE cur_role;
+ uint8_t cur_role;
uint8_t peer_idx = 0;
+ uint8_t set_policy = (HCI_ENABLE_SNIFF_MODE | HCI_ENABLE_MASTER_SLAVE_SWITCH);
APPL_TRACE_DEBUG(
"%s: peer %s new_role:%d hci_status:0x%x bta_av_cb.rs_idx:%d", __func__,
@@ -826,6 +963,12 @@ static void bta_av_sys_rs_cback(UNUSED_ATTR tBTA_SYS_CONN_STATUS status,
APPL_TRACE_DEBUG(
"%s: peer %s found: new_role:%d, hci_status:0x%x bta_handle:0x%x",
__func__, peer_addr.ToString().c_str(), id, app_id, p_scb->hndl);
+ /*
+ if ((id != BTM_ROLE_MASTER) && (app_id != HCI_SUCCESS))
+ {
+ bta_sys_set_policy(BTA_ID_AV, set_policy, p_scb->PeerAddress());
+ }
+ */
p_buf->hdr.event = BTA_AV_ROLE_CHANGE_EVT;
p_buf->hdr.layer_specific = p_scb->hndl;
p_buf->new_role = id;
@@ -839,8 +982,8 @@ static void bta_av_sys_rs_cback(UNUSED_ATTR tBTA_SYS_CONN_STATUS status,
/* restore role switch policy, if role switch failed */
if ((HCI_SUCCESS != app_id) &&
(BTM_GetRole(peer_addr, &cur_role) == BTM_SUCCESS) &&
- (cur_role == HCI_ROLE_PERIPHERAL)) {
- BTM_unblock_role_switch_for(peer_addr);
+ (cur_role == BTM_ROLE_SLAVE)) {
+ bta_sys_set_policy(BTA_ID_AV, set_policy, peer_addr);
}
/* if BTA_AvOpen() was called for other device, which caused the role switch
@@ -892,12 +1035,9 @@ static void bta_av_sco_chg_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
int i;
tBTA_AV_API_STOP stop;
- LOG(INFO) << __func__ << ": status=" << bta_sys_conn_status_text(status)
- << ", num_links=" << +id;
+ LOG(INFO) << __func__ << ": status=" << +status << ", num_links=" << +id;
if (id) {
bta_av_cb.sco_occupied = true;
- LOG_DEBUG("SCO occupied peer:%s status:%s", PRIVATE_ADDRESS(peer_addr),
- bta_sys_conn_status_text(status).c_str());
if (bta_av_cb.features & BTA_AV_FEAT_NO_SCO_SSPD) {
return;
@@ -919,8 +1059,6 @@ static void bta_av_sco_chg_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
}
} else {
bta_av_cb.sco_occupied = false;
- LOG_DEBUG("SCO unoccupied peer:%s status:%s", PRIVATE_ADDRESS(peer_addr),
- bta_sys_conn_status_text(status).c_str());
if (bta_av_cb.features & BTA_AV_FEAT_NO_SCO_SSPD) {
return;
@@ -943,7 +1081,7 @@ static void bta_av_sco_chg_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
* Function bta_av_switch_if_needed
*
* Description This function checks if there is another existing AV
- * channel that is local as peripheral role.
+ * channel that is local as slave role.
* If so, role switch and remove it from link policy.
*
* Returns true, if role switch is done
@@ -951,7 +1089,7 @@ static void bta_av_sco_chg_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
******************************************************************************/
bool bta_av_switch_if_needed(tBTA_AV_SCB* p_scb) {
// TODO: A workaround for devices that are connected first, become
- // Central, and block follow-up role changes - b/72122792 .
+ // Master, and block follow-up role changes - b/72122792 .
return false;
#if 0
uint8_t role;
@@ -969,11 +1107,12 @@ bool bta_av_switch_if_needed(tBTA_AV_SCB* p_scb) {
BTM_GetRole(p_scbi->PeerAddress(), &role);
/* this channel is open - clear the role switch link policy for this link
*/
- if (HCI_ROLE_CENTRAL != role) {
- if (bta_av_cb.features & BTA_AV_FEAT_CENTRAL)
- BTM_block_role_switch_for(p_scbi->PeerAddress());
+ if (BTM_ROLE_MASTER != role) {
+ if (bta_av_cb.features & BTA_AV_FEAT_MASTER)
+ bta_sys_clear_policy(BTA_ID_AV, HCI_ENABLE_MASTER_SLAVE_SWITCH,
+ p_scbi->PeerAddress());
if (BTM_CMD_STARTED !=
- BTM_SwitchRole(p_scbi->PeerAddress(), HCI_ROLE_CENTRAL)) {
+ BTM_SwitchRole(p_scbi->PeerAddress(), BTM_ROLE_MASTER, NULL)) {
/* can not switch role on SCBI
* start the timer on SCB - because this function is ONLY called when
* SCB gets API_OPEN */
@@ -1002,41 +1141,38 @@ bool bta_av_switch_if_needed(tBTA_AV_SCB* p_scb) {
*
******************************************************************************/
bool bta_av_link_role_ok(tBTA_AV_SCB* p_scb, uint8_t bits) {
- tHCI_ROLE role;
- if (BTM_GetRole(p_scb->PeerAddress(), &role) != BTM_SUCCESS) {
- LOG_WARN("Unable to find link role for device:%s",
- PRIVATE_ADDRESS(p_scb->PeerAddress()));
- return true;
- }
-
- if (role != HCI_ROLE_CENTRAL && (A2DP_BitsSet(bta_av_cb.conn_audio) > bits)) {
- LOG_INFO(
- "Switch link role to central peer:%s bta_handle:0x%x current_role:%s"
- " conn_audio:0x%x bits:%d features:0x%x",
- PRIVATE_ADDRESS(p_scb->PeerAddress()), p_scb->hndl,
- RoleText(role).c_str(), bta_av_cb.conn_audio, bits, bta_av_cb.features);
- const tBTM_STATUS status = BTM_SwitchRoleToCentral(p_scb->PeerAddress());
- switch (status) {
- case BTM_CMD_STARTED:
- break;
- case BTM_MODE_UNSUPPORTED:
- case BTM_DEV_RESTRICT_LISTED:
- // Role switch can never happen, but indicate to caller
- // a result such that a timer will not start to repeatedly
- // try something not possible.
- LOG_ERROR("Link can never role switch to central device:%s",
- PRIVATE_ADDRESS(p_scb->PeerAddress()));
- break;
- default:
+ uint8_t role;
+ bool is_ok = true;
+
+ if (BTM_GetRole(p_scb->PeerAddress(), &role) == BTM_SUCCESS) {
+ LOG_INFO(LOG_TAG,
+ "%s: peer %s bta_handle:0x%x role:%d conn_audio:0x%x bits:%d "
+ "features:0x%x",
+ __func__, p_scb->PeerAddress().ToString().c_str(), p_scb->hndl,
+ role, bta_av_cb.conn_audio, bits, bta_av_cb.features);
+ if (BTM_ROLE_MASTER != role &&
+ (A2DP_BitsSet(bta_av_cb.conn_audio) > bits ||
+ (bta_av_cb.features & BTA_AV_FEAT_MASTER))) {
+ if (bta_av_cb.features & BTA_AV_FEAT_MASTER)
+ bta_sys_clear_policy(BTA_ID_AV, HCI_ENABLE_MASTER_SLAVE_SWITCH,
+ p_scb->PeerAddress());
+
+ tBTM_STATUS status =
+ BTM_SwitchRole(p_scb->PeerAddress(), BTM_ROLE_MASTER, NULL);
+ if (status != BTM_CMD_STARTED) {
/* can not switch role on SCB - start the timer on SCB */
+ LOG_ERROR(LOG_TAG,
+ "%s: peer %s BTM_SwitchRole(BTM_ROLE_MASTER) error: %d",
+ __func__, p_scb->PeerAddress().ToString().c_str(), status);
+ }
+ if (status != BTM_MODE_UNSUPPORTED && status != BTM_DEV_BLACKLISTED) {
+ is_ok = false;
p_scb->wait |= BTA_AV_WAIT_ROLE_SW_RES_START;
- LOG_ERROR("Unable to switch role to central device:%s error:%s",
- PRIVATE_ADDRESS(p_scb->PeerAddress()),
- btm_status_text(status).c_str());
- return false;
+ }
}
}
- return true;
+
+ return is_ok;
}
/*******************************************************************************
@@ -1078,120 +1214,40 @@ void bta_av_dup_audio_buf(tBTA_AV_SCB* p_scb, BT_HDR* p_buf) {
}
}
-static void bta_av_non_state_machine_event(uint16_t event,
- tBTA_AV_DATA* p_data) {
- switch (event) {
- case BTA_AV_API_ENABLE_EVT:
- bta_av_api_enable(p_data);
- break;
- case BTA_AV_API_REGISTER_EVT:
- bta_av_api_register(p_data);
- break;
- case BTA_AV_API_DEREGISTER_EVT:
- bta_av_api_deregister(p_data);
- break;
- case BTA_AV_API_DISCONNECT_EVT:
- bta_av_api_disconnect(p_data);
- break;
- case BTA_AV_CI_SRC_DATA_READY_EVT:
- bta_av_ci_data(p_data);
- break;
- case BTA_AV_SIG_CHG_EVT:
- bta_av_sig_chg(p_data);
- break;
- case BTA_AV_SIGNALLING_TIMER_EVT:
- bta_av_signalling_timer(p_data);
- break;
- case BTA_AV_SDP_AVRC_DISC_EVT:
- bta_av_rc_disc_done(p_data);
- break;
- case BTA_AV_AVRC_CLOSE_EVT:
- bta_av_rc_closed(p_data);
- break;
- case BTA_AV_AVRC_BROWSE_OPEN_EVT:
- bta_av_rc_browse_opened(p_data);
- break;
- case BTA_AV_AVRC_BROWSE_CLOSE_EVT:
- bta_av_rc_browse_closed(p_data);
- break;
- case BTA_AV_CONN_CHG_EVT:
- bta_av_conn_chg(p_data);
- break;
- case BTA_AV_DEREG_COMP_EVT:
- bta_av_dereg_comp(p_data);
- break;
- case BTA_AV_AVDT_RPT_CONN_EVT:
- bta_av_rpc_conn(p_data);
- break;
- case BTA_AV_API_START_EVT:
- bta_av_api_to_ssm(p_data);
- break;
- case BTA_AV_API_STOP_EVT:
- bta_av_api_to_ssm(p_data);
- break;
- }
-}
-
-static void bta_av_better_state_machine(tBTA_AV_CB* p_cb, uint16_t event,
- tBTA_AV_DATA* p_data) {
- switch (p_cb->state) {
- case BTA_AV_INIT_ST:
- switch (event) {
- case BTA_AV_API_DISABLE_EVT:
- bta_av_disable(p_cb, p_data);
- break;
- case BTA_AV_API_META_RSP_EVT:
- bta_av_rc_free_rsp(p_cb, p_data);
- break;
- case BTA_AV_AVRC_OPEN_EVT:
- p_cb->state = BTA_AV_OPEN_ST;
- bta_av_rc_opened(p_cb, p_data);
- break;
- case BTA_AV_AVRC_MSG_EVT:
- bta_av_rc_free_browse_msg(p_cb, p_data);
- break;
- }
- break;
- case BTA_AV_OPEN_ST:
- switch (event) {
- case BTA_AV_API_DISABLE_EVT:
- p_cb->state = BTA_AV_INIT_ST;
- bta_av_disable(p_cb, p_data);
- break;
- case BTA_AV_API_REMOTE_CMD_EVT:
- bta_av_rc_remote_cmd(p_cb, p_data);
- break;
- case BTA_AV_API_VENDOR_CMD_EVT:
- bta_av_rc_vendor_cmd(p_cb, p_data);
- break;
- case BTA_AV_API_VENDOR_RSP_EVT:
- bta_av_rc_vendor_rsp(p_cb, p_data);
- break;
- case BTA_AV_API_META_RSP_EVT:
- bta_av_rc_meta_rsp(p_cb, p_data);
- break;
- case BTA_AV_API_RC_CLOSE_EVT:
- bta_av_rc_close(p_cb, p_data);
- break;
- case BTA_AV_AVRC_OPEN_EVT:
- bta_av_rc_opened(p_cb, p_data);
- break;
- case BTA_AV_AVRC_MSG_EVT:
- bta_av_rc_msg(p_cb, p_data);
- break;
- case BTA_AV_AVRC_NONE_EVT:
- p_cb->state = BTA_AV_INIT_ST;
- break;
- }
- break;
- }
-}
-
+/*******************************************************************************
+ *
+ * Function bta_av_sm_execute
+ *
+ * Description State machine event handling function for AV
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
void bta_av_sm_execute(tBTA_AV_CB* p_cb, uint16_t event, tBTA_AV_DATA* p_data) {
+ tBTA_AV_ST_TBL state_table;
+ uint8_t action;
+
APPL_TRACE_EVENT("%s: AV event=0x%x(%s) state=%d(%s)", __func__, event,
bta_av_evt_code(event), p_cb->state,
bta_av_st_code(p_cb->state));
- bta_av_better_state_machine(p_cb, event, p_data);
+
+ /* look up the state table for the current state */
+ state_table = bta_av_st_tbl[p_cb->state];
+
+ event &= 0x00FF;
+
+ /* set next state */
+ p_cb->state = state_table[event][BTA_AV_NEXT_STATE];
+ APPL_TRACE_EVENT("%s: next state=%d event offset:%d", __func__, p_cb->state,
+ event);
+
+ /* execute action functions */
+ action = state_table[event][BTA_AV_ACTION_COL];
+ if (action != BTA_AV_IGNORE) {
+ APPL_TRACE_EVENT("%s: action executed %d", __func__, action);
+ (*bta_av_action[action])(p_cb, p_data);
+ }
}
/*******************************************************************************
@@ -1204,14 +1260,16 @@ void bta_av_sm_execute(tBTA_AV_CB* p_cb, uint16_t event, tBTA_AV_DATA* p_data) {
* Returns bool
*
******************************************************************************/
-bool bta_av_hdl_event(BT_HDR_RIGID* p_msg) {
+bool bta_av_hdl_event(BT_HDR* p_msg) {
if (p_msg->event > BTA_AV_LAST_EVT) {
return true; /* to free p_msg */
}
if (p_msg->event >= BTA_AV_FIRST_NSM_EVT) {
APPL_TRACE_VERBOSE("%s: AV nsm event=0x%x(%s)", __func__, p_msg->event,
bta_av_evt_code(p_msg->event));
- bta_av_non_state_machine_event(p_msg->event, (tBTA_AV_DATA*)p_msg);
+ /* non state machine events */
+ (*bta_av_nsm_act[p_msg->event - BTA_AV_FIRST_NSM_EVT])(
+ (tBTA_AV_DATA*)p_msg);
} else if (p_msg->event >= BTA_AV_FIRST_SM_EVT &&
p_msg->event <= BTA_AV_LAST_SM_EVT) {
APPL_TRACE_VERBOSE("%s: AV sm event=0x%x(%s)", __func__, p_msg->event,
@@ -1394,15 +1452,26 @@ void bta_debug_av_dump(int fd) {
dprintf(fd, "\nBTA AV State:\n");
dprintf(fd, " State Machine State: %s\n", bta_av_st_code(bta_av_cb.state));
+ dprintf(fd, " Link signalling timer: %s\n",
+ alarm_is_scheduled(bta_av_cb.link_signalling_timer)
+ ? "Scheduled"
+ : "Not scheduled");
+ dprintf(fd, " Accept signalling timer: %s\n",
+ alarm_is_scheduled(bta_av_cb.accept_signalling_timer)
+ ? "Scheduled"
+ : "Not scheduled");
dprintf(fd, " SDP A2DP source handle: %d\n", bta_av_cb.sdp_a2dp_handle);
dprintf(fd, " SDP A2DP sink handle: %d\n", bta_av_cb.sdp_a2dp_snk_handle);
dprintf(fd, " Features: 0x%x\n", bta_av_cb.features);
+ dprintf(fd, " Security mask: 0x%x\n", bta_av_cb.sec_mask);
dprintf(fd, " SDP handle: %d\n", bta_av_cb.handle);
dprintf(fd, " Disabling: %s\n", bta_av_cb.disabling ? "true" : "false");
dprintf(fd, " SCO occupied: %s\n",
bta_av_cb.sco_occupied ? "true" : "false");
dprintf(fd, " Connected audio channels: %d\n", bta_av_cb.audio_open_cnt);
dprintf(fd, " Connected audio channels mask: 0x%x\n", bta_av_cb.conn_audio);
+ dprintf(fd, " Streaming audio channels mask: 0x%x\n",
+ bta_av_cb.audio_streams);
dprintf(fd, " Registered audio channels mask: 0x%x\n", bta_av_cb.reg_audio);
dprintf(fd, " Connected LCBs mask: 0x%x\n", bta_av_cb.conn_lcb);
@@ -1444,25 +1513,21 @@ void bta_debug_av_dump(int fd) {
p_scb->q_info.open.bd_addr.ToString().c_str());
dprintf(fd, " Use AVRCP: %s\n",
p_scb->q_info.open.use_rc ? "true" : "false");
+ dprintf(fd, " Security mask: 0x%x\n", p_scb->q_info.open.sec_mask);
dprintf(fd, " Switch result: %d\n", p_scb->q_info.open.switch_res);
dprintf(fd, " Initiator UUID: 0x%x\n", p_scb->q_info.open.uuid);
dprintf(fd, " Saved API Open peer: %s\n",
p_scb->open_api.bd_addr.ToString().c_str());
dprintf(fd, " Use AVRCP: %s\n",
p_scb->open_api.use_rc ? "true" : "false");
+ dprintf(fd, " Security mask: 0x%x\n", p_scb->open_api.sec_mask);
dprintf(fd, " Switch result: %d\n", p_scb->open_api.switch_res);
dprintf(fd, " Initiator UUID: 0x%x\n", p_scb->open_api.uuid);
- dprintf(fd, " Link signalling timer: %s\n",
- alarm_is_scheduled(p_scb->link_signalling_timer) ? "Scheduled"
- : "Not scheduled");
- dprintf(fd, " Accept signalling timer: %s\n",
- alarm_is_scheduled(p_scb->accept_signalling_timer)
- ? "Scheduled"
- : "Not scheduled");
// TODO: Print p_scb->sep_info[], cfg, avrc_ct_timer, current_codec ?
dprintf(fd, " L2CAP Channel ID: %d\n", p_scb->l2c_cid);
dprintf(fd, " Stream MTU: %d\n", p_scb->stream_mtu);
dprintf(fd, " AVDTP version: 0x%x\n", p_scb->AvdtpVersion());
+ dprintf(fd, " Security mask: 0x%x\n", p_scb->sec_mask);
dprintf(fd, " Media type: %d\n", p_scb->media_type);
dprintf(fd, " Congested: %s\n", p_scb->cong ? "true" : "false");
dprintf(fd, " Open status: %d\n", p_scb->open_status);
diff --git a/bta/av/bta_av_ssm.cc b/bta/av/bta_av_ssm.cc
index 1a6922c42..c9fc37e54 100644
--- a/bta/av/bta_av_ssm.cc
+++ b/bta/av/bta_av_ssm.cc
@@ -21,11 +21,11 @@
* This is the stream state machine for the BTA advanced audio/video.
*
******************************************************************************/
+#include <string.h>
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/av/bta_av_int.h"
-#include "osi/include/log.h"
+#include "bt_target.h"
+#include "bta_av_co.h"
+#include "bta_av_int.h"
/*****************************************************************************
* Constants and types
@@ -41,402 +41,432 @@ enum {
BTA_AV_CLOSING_SST
};
-static void bta_av_better_stream_state_machine(tBTA_AV_SCB* p_scb,
- uint16_t event,
- tBTA_AV_DATA* p_data) {
- uint8_t previous_state = p_scb->state;
- tBTA_AV_ACT event_handler1 = nullptr;
- tBTA_AV_ACT event_handler2 = nullptr;
- switch (p_scb->state) {
- case BTA_AV_INIT_SST:
- switch (event) {
- case BTA_AV_API_OPEN_EVT:
- p_scb->state = BTA_AV_OPENING_SST;
- event_handler1 = &bta_av_do_disc_a2dp;
- break;
- case BTA_AV_API_CLOSE_EVT:
- event_handler1 = &bta_av_cleanup;
- break;
- case BTA_AV_SDP_DISC_OK_EVT:
- event_handler1 = &bta_av_free_sdb;
- break;
- case BTA_AV_SDP_DISC_FAIL_EVT:
- event_handler1 = &bta_av_free_sdb;
- break;
- case BTA_AV_STR_CONFIG_IND_EVT:
- p_scb->state = BTA_AV_INCOMING_SST;
- event_handler1 = &bta_av_config_ind;
- break;
- case BTA_AV_ACP_CONNECT_EVT:
- p_scb->state = BTA_AV_INCOMING_SST;
- break;
- case BTA_AV_API_OFFLOAD_START_EVT:
- event_handler1 = &bta_av_offload_req;
- break;
- case BTA_AV_API_OFFLOAD_START_RSP_EVT:
- event_handler1 = &bta_av_offload_rsp;
- break;
- }
- break;
- case BTA_AV_INCOMING_SST:
- switch (event) {
- case BTA_AV_API_OPEN_EVT:
- event_handler1 = &bta_av_open_at_inc;
- break;
- case BTA_AV_API_CLOSE_EVT:
- p_scb->state = BTA_AV_CLOSING_SST;
- event_handler1 = &bta_av_cco_close;
- event_handler2 = &bta_av_disconnect_req;
- break;
- case BTA_AV_API_PROTECT_REQ_EVT:
- event_handler1 = &bta_av_security_req;
- break;
- case BTA_AV_API_PROTECT_RSP_EVT:
- event_handler1 = &bta_av_security_rsp;
- break;
- case BTA_AV_CI_SETCONFIG_OK_EVT:
- event_handler1 = &bta_av_setconfig_rsp;
- event_handler2 = &bta_av_st_rc_timer;
- break;
- case BTA_AV_CI_SETCONFIG_FAIL_EVT:
- p_scb->state = BTA_AV_INIT_SST;
- event_handler1 = &bta_av_setconfig_rej;
- event_handler2 = &bta_av_cleanup;
- break;
- case BTA_AV_SDP_DISC_OK_EVT:
- event_handler1 = &bta_av_free_sdb;
- break;
- case BTA_AV_SDP_DISC_FAIL_EVT:
- event_handler1 = &bta_av_free_sdb;
- break;
- case BTA_AV_STR_DISC_OK_EVT:
- event_handler1 = &bta_av_disc_res_as_acp;
- break;
- case BTA_AV_STR_GETCAP_OK_EVT:
- event_handler1 = &bta_av_save_caps;
- break;
- case BTA_AV_STR_OPEN_OK_EVT:
- p_scb->state = BTA_AV_OPEN_SST;
- event_handler1 = &bta_av_str_opened;
- break;
- case BTA_AV_STR_CLOSE_EVT:
- p_scb->state = BTA_AV_INIT_SST;
- event_handler1 = &bta_av_cco_close;
- event_handler2 = &bta_av_cleanup;
- break;
- case BTA_AV_STR_CONFIG_IND_EVT:
- event_handler1 = &bta_av_config_ind;
- break;
- case BTA_AV_STR_SECURITY_IND_EVT:
- event_handler1 = &bta_av_security_ind;
- break;
- case BTA_AV_STR_SECURITY_CFM_EVT:
- event_handler1 = &bta_av_security_cfm;
- break;
- case BTA_AV_AVDT_DISCONNECT_EVT:
- p_scb->state = BTA_AV_CLOSING_SST;
- event_handler1 = &bta_av_cco_close;
- event_handler2 = &bta_av_disconnect_req;
- break;
- case BTA_AV_AVDT_DELAY_RPT_EVT:
- event_handler1 = &bta_av_delay_co;
- break;
- case BTA_AV_API_OFFLOAD_START_EVT:
- event_handler1 = &bta_av_offload_req;
- break;
- case BTA_AV_API_OFFLOAD_START_RSP_EVT:
- event_handler1 = &bta_av_offload_rsp;
- break;
- }
- break;
- case BTA_AV_OPENING_SST:
- switch (event) {
- case BTA_AV_API_CLOSE_EVT:
- p_scb->state = BTA_AV_CLOSING_SST;
- event_handler1 = &bta_av_do_close;
- break;
- case BTA_AV_API_PROTECT_REQ_EVT:
- event_handler1 = &bta_av_security_req;
- break;
- case BTA_AV_API_PROTECT_RSP_EVT:
- event_handler1 = &bta_av_security_rsp;
- break;
- case BTA_AV_SDP_DISC_OK_EVT:
- event_handler1 = &bta_av_connect_req;
- break;
- case BTA_AV_SDP_DISC_FAIL_EVT:
- event_handler1 = &bta_av_connect_req;
- break;
- case BTA_AV_STR_DISC_OK_EVT:
- event_handler1 = &bta_av_disc_results;
- break;
- case BTA_AV_STR_DISC_FAIL_EVT:
- p_scb->state = BTA_AV_CLOSING_SST;
- event_handler1 = &bta_av_open_failed;
- break;
- case BTA_AV_STR_GETCAP_OK_EVT:
- event_handler1 = &bta_av_getcap_results;
- break;
- case BTA_AV_STR_GETCAP_FAIL_EVT:
- p_scb->state = BTA_AV_CLOSING_SST;
- event_handler1 = &bta_av_open_failed;
- break;
- case BTA_AV_STR_OPEN_OK_EVT:
- p_scb->state = BTA_AV_OPEN_SST;
- event_handler1 = &bta_av_st_rc_timer;
- event_handler2 = &bta_av_str_opened;
- break;
- case BTA_AV_STR_OPEN_FAIL_EVT:
- p_scb->state = BTA_AV_CLOSING_SST;
- event_handler1 = &bta_av_open_failed;
- break;
- case BTA_AV_STR_CONFIG_IND_EVT:
- p_scb->state = BTA_AV_INCOMING_SST;
- event_handler1 = &bta_av_config_ind;
- break;
- case BTA_AV_STR_SECURITY_IND_EVT:
- event_handler1 = &bta_av_security_ind;
- break;
- case BTA_AV_STR_SECURITY_CFM_EVT:
- event_handler1 = &bta_av_security_cfm;
- break;
- case BTA_AV_AVRC_TIMER_EVT:
- event_handler1 = &bta_av_switch_role;
- break;
- case BTA_AV_AVDT_CONNECT_EVT:
- event_handler1 = &bta_av_discover_req;
- break;
- case BTA_AV_AVDT_DISCONNECT_EVT:
- p_scb->state = BTA_AV_INIT_SST;
- event_handler1 = &bta_av_conn_failed;
- break;
- case BTA_AV_ROLE_CHANGE_EVT:
- event_handler1 = &bta_av_role_res;
- break;
- case BTA_AV_AVDT_DELAY_RPT_EVT:
- event_handler1 = &bta_av_delay_co;
- break;
- case BTA_AV_API_OFFLOAD_START_EVT:
- event_handler1 = &bta_av_offload_req;
- break;
- case BTA_AV_API_OFFLOAD_START_RSP_EVT:
- event_handler1 = &bta_av_offload_rsp;
- break;
- }
- break;
- case BTA_AV_OPEN_SST:
- switch (event) {
- case BTA_AV_API_CLOSE_EVT:
- p_scb->state = BTA_AV_CLOSING_SST;
- event_handler1 = &bta_av_do_close;
- break;
- case BTA_AV_AP_START_EVT:
- event_handler1 = &bta_av_do_start;
- break;
- case BTA_AV_AP_STOP_EVT:
- event_handler1 = &bta_av_str_stopped;
- break;
- case BTA_AV_API_RECONFIG_EVT:
- p_scb->state = BTA_AV_RCFG_SST;
- event_handler1 = &bta_av_reconfig;
- break;
- case BTA_AV_API_PROTECT_REQ_EVT:
- event_handler1 = &bta_av_security_req;
- break;
- case BTA_AV_API_PROTECT_RSP_EVT:
- event_handler1 = &bta_av_security_rsp;
- break;
- case BTA_AV_API_RC_OPEN_EVT:
- event_handler1 = &bta_av_set_use_rc;
- break;
- case BTA_AV_SRC_DATA_READY_EVT:
- event_handler1 = &bta_av_data_path;
- break;
- case BTA_AV_SDP_DISC_OK_EVT:
- event_handler1 = &bta_av_free_sdb;
- break;
- case BTA_AV_SDP_DISC_FAIL_EVT:
- event_handler1 = &bta_av_free_sdb;
- break;
- case BTA_AV_STR_GETCAP_OK_EVT:
- event_handler1 = &bta_av_save_caps;
- break;
- case BTA_AV_STR_START_OK_EVT:
- event_handler1 = &bta_av_start_ok;
- break;
- case BTA_AV_STR_START_FAIL_EVT:
- event_handler1 = &bta_av_start_failed;
- break;
- case BTA_AV_STR_CLOSE_EVT:
- p_scb->state = BTA_AV_INIT_SST;
- event_handler1 = &bta_av_str_closed;
- break;
- case BTA_AV_STR_CONFIG_IND_EVT:
- event_handler1 = &bta_av_setconfig_rej;
- break;
- case BTA_AV_STR_SECURITY_IND_EVT:
- event_handler1 = &bta_av_security_ind;
- break;
- case BTA_AV_STR_SECURITY_CFM_EVT:
- event_handler1 = &bta_av_security_cfm;
- break;
- case BTA_AV_STR_WRITE_CFM_EVT:
- event_handler1 = &bta_av_clr_cong;
- event_handler2 = &bta_av_data_path;
- break;
- case BTA_AV_STR_SUSPEND_CFM_EVT:
- event_handler1 = &bta_av_suspend_cfm;
- break;
- case BTA_AV_AVRC_TIMER_EVT:
- event_handler1 = &bta_av_open_rc;
- break;
- case BTA_AV_AVDT_DISCONNECT_EVT:
- p_scb->state = BTA_AV_INIT_SST;
- event_handler1 = &bta_av_str_closed;
- break;
- case BTA_AV_ROLE_CHANGE_EVT:
- event_handler1 = &bta_av_role_res;
- break;
- case BTA_AV_AVDT_DELAY_RPT_EVT:
- event_handler1 = &bta_av_delay_co;
- break;
- case BTA_AV_API_OFFLOAD_START_EVT:
- event_handler1 = &bta_av_offload_req;
- break;
- case BTA_AV_API_OFFLOAD_START_RSP_EVT:
- event_handler1 = &bta_av_offload_rsp;
- break;
- }
- break;
- case BTA_AV_RCFG_SST:
- switch (event) {
- case BTA_AV_API_CLOSE_EVT:
- p_scb->state = BTA_AV_CLOSING_SST;
- event_handler1 = &bta_av_disconnect_req;
- break;
- case BTA_AV_API_RECONFIG_EVT:
- event_handler1 = &bta_av_reconfig;
- break;
- case BTA_AV_SDP_DISC_OK_EVT:
- event_handler1 = &bta_av_free_sdb;
- break;
- case BTA_AV_SDP_DISC_FAIL_EVT:
- event_handler1 = &bta_av_free_sdb;
- break;
- case BTA_AV_STR_DISC_OK_EVT:
- event_handler1 = &bta_av_disc_results;
- break;
- case BTA_AV_STR_DISC_FAIL_EVT:
- p_scb->state = BTA_AV_INIT_SST;
- event_handler1 = &bta_av_str_closed;
- break;
- case BTA_AV_STR_GETCAP_OK_EVT:
- event_handler1 = &bta_av_getcap_results;
- break;
- case BTA_AV_STR_GETCAP_FAIL_EVT:
- p_scb->state = BTA_AV_INIT_SST;
- event_handler1 = &bta_av_str_closed;
- break;
- case BTA_AV_STR_OPEN_OK_EVT:
- p_scb->state = BTA_AV_OPEN_SST;
- event_handler1 = &bta_av_rcfg_str_ok;
- break;
- case BTA_AV_STR_OPEN_FAIL_EVT:
- event_handler1 = &bta_av_rcfg_failed;
- break;
- case BTA_AV_STR_CLOSE_EVT:
- event_handler1 = &bta_av_rcfg_connect;
- break;
- case BTA_AV_STR_CONFIG_IND_EVT:
- event_handler1 = &bta_av_setconfig_rej;
- break;
- case BTA_AV_STR_SUSPEND_CFM_EVT:
- event_handler1 = &bta_av_suspend_cfm;
- event_handler2 = &bta_av_suspend_cont;
- break;
- case BTA_AV_STR_RECONFIG_CFM_EVT:
- event_handler1 = &bta_av_rcfg_cfm;
- break;
- case BTA_AV_AVDT_CONNECT_EVT:
- event_handler1 = &bta_av_rcfg_open;
- break;
- case BTA_AV_AVDT_DISCONNECT_EVT:
- event_handler1 = &bta_av_rcfg_discntd;
- break;
- case BTA_AV_AVDT_DELAY_RPT_EVT:
- event_handler1 = &bta_av_delay_co;
- break;
- case BTA_AV_API_OFFLOAD_START_EVT:
- event_handler1 = &bta_av_offload_req;
- break;
- case BTA_AV_API_OFFLOAD_START_RSP_EVT:
- event_handler1 = &bta_av_offload_rsp;
- break;
- }
- break;
- case BTA_AV_CLOSING_SST:
- switch (event) {
- case BTA_AV_API_CLOSE_EVT:
- event_handler1 = &bta_av_disconnect_req;
- break;
- case BTA_AV_SDP_DISC_OK_EVT:
- p_scb->state = BTA_AV_INIT_SST;
- event_handler1 = &bta_av_sdp_failed;
- break;
- case BTA_AV_SDP_DISC_FAIL_EVT:
- p_scb->state = BTA_AV_INIT_SST;
- event_handler1 = &bta_av_sdp_failed;
- break;
- case BTA_AV_STR_OPEN_OK_EVT:
- event_handler1 = &bta_av_do_close;
- break;
- case BTA_AV_STR_OPEN_FAIL_EVT:
- event_handler1 = &bta_av_disconnect_req;
- break;
- case BTA_AV_STR_CLOSE_EVT:
- event_handler1 = &bta_av_disconnect_req;
- break;
- case BTA_AV_STR_CONFIG_IND_EVT:
- event_handler1 = &bta_av_setconfig_rej;
- break;
- case BTA_AV_STR_SECURITY_IND_EVT:
- event_handler1 = &bta_av_security_rej;
- break;
- case BTA_AV_AVDT_DISCONNECT_EVT:
- p_scb->state = BTA_AV_INIT_SST;
- event_handler1 = &bta_av_str_closed;
- break;
- case BTA_AV_API_OFFLOAD_START_EVT:
- event_handler1 = &bta_av_offload_req;
- break;
- case BTA_AV_API_OFFLOAD_START_RSP_EVT:
- event_handler1 = &bta_av_offload_rsp;
- break;
- }
- break;
- }
+/* state machine action enumeration list */
+enum {
+ BTA_AV_DO_DISC,
+ BTA_AV_CLEANUP,
+ BTA_AV_FREE_SDB,
+ BTA_AV_CONFIG_IND,
+ BTA_AV_DISCONNECT_REQ,
+ BTA_AV_SECURITY_REQ,
+ BTA_AV_SECURITY_RSP,
+ BTA_AV_SETCONFIG_RSP,
+ BTA_AV_ST_RC_TIMER,
+ BTA_AV_STR_OPENED,
+ BTA_AV_SECURITY_IND,
+ BTA_AV_SECURITY_CFM,
+ BTA_AV_DO_CLOSE,
+ BTA_AV_CONNECT_REQ,
+ BTA_AV_SDP_FAILED,
+ BTA_AV_DISC_RESULTS,
+ BTA_AV_DISC_RES_AS_ACP,
+ BTA_AV_OPEN_FAILED,
+ BTA_AV_GETCAP_RESULTS,
+ BTA_AV_SETCONFIG_REJ,
+ BTA_AV_DISCOVER_REQ,
+ BTA_AV_CONN_FAILED,
+ BTA_AV_DO_START,
+ BTA_AV_STR_STOPPED,
+ BTA_AV_RECONFIG,
+ BTA_AV_DATA_PATH,
+ BTA_AV_START_OK,
+ BTA_AV_START_FAILED,
+ BTA_AV_STR_CLOSED,
+ BTA_AV_CLR_CONG,
+ BTA_AV_SUSPEND_CFM,
+ BTA_AV_RCFG_STR_OK,
+ BTA_AV_RCFG_FAILED,
+ BTA_AV_RCFG_CONNECT,
+ BTA_AV_RCFG_DISCNTD,
+ BTA_AV_SUSPEND_CONT,
+ BTA_AV_RCFG_CFM,
+ BTA_AV_RCFG_OPEN,
+ BTA_AV_SECURITY_REJ,
+ BTA_AV_OPEN_RC,
+ BTA_AV_CHK_2ND_START,
+ BTA_AV_SAVE_CAPS,
+ BTA_AV_SET_USE_RC,
+ BTA_AV_CCO_CLOSE,
+ BTA_AV_SWITCH_ROLE,
+ BTA_AV_ROLE_RES,
+ BTA_AV_DELAY_CO,
+ BTA_AV_OPEN_AT_INC,
+ BTA_AV_OFFLOAD_REQ,
+ BTA_AV_OFFLOAD_RSP,
+ BTA_AV_NUM_SACTIONS
+};
- if (previous_state != p_scb->state) {
- LOG_INFO("peer %s p_scb=%#x(%p) AV event=0x%x(%s) state=%d(%s) -> %d(%s)",
- p_scb->PeerAddress().ToString().c_str(), p_scb->hndl, p_scb, event,
- bta_av_evt_code(event), previous_state,
- bta_av_sst_code(previous_state), p_scb->state,
- bta_av_sst_code(p_scb->state));
+#define BTA_AV_SIGNORE BTA_AV_NUM_SACTIONS
- } else {
- LOG_DEBUG("peer %s p_scb=%#x(%p) AV event=0x%x(%s) state=%d(%s)",
- p_scb->PeerAddress().ToString().c_str(), p_scb->hndl, p_scb,
- event, bta_av_evt_code(event), p_scb->state,
- bta_av_sst_code(p_scb->state));
- }
+/* state table information */
+/* #define BTA_AV_SACTION_COL 0 position of actions */
+#define BTA_AV_SACTIONS 2 /* number of actions */
+#define BTA_AV_SNEXT_STATE 2 /* position of next state */
+#define BTA_AV_NUM_COLS 3 /* number of columns in state tables */
+
+/* state table for init state */
+static const uint8_t bta_av_sst_init[][BTA_AV_NUM_COLS] = {
+ /* Event Action 1 Action 2 Next state */
+ /* API_OPEN_EVT */ {BTA_AV_DO_DISC, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* API_CLOSE_EVT */ {BTA_AV_CLEANUP, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* AP_START_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* AP_STOP_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* API_RECONFIG_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* API_PROTECT_REQ_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* API_PROTECT_RSP_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* API_RC_OPEN_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* SRC_DATA_READY_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* CI_SETCONFIG_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* CI_SETCONFIG_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* SDP_DISC_OK_EVT */ {BTA_AV_FREE_SDB, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* SDP_DISC_FAIL_EVT */ {BTA_AV_FREE_SDB, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_DISC_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_DISC_FAIL_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_GETCAP_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_GETCAP_FAIL_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_OPEN_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_OPEN_FAIL_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_START_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_START_FAIL_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_CLOSE_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_CONFIG_IND_EVT */
+ {BTA_AV_CONFIG_IND, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_SECURITY_IND_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_SECURITY_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_WRITE_CFM_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_SUSPEND_CFM_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_RECONFIG_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* AVRC_TIMER_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* AVDT_CONNECT_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* AVDT_DISCONNECT_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* ROLE_CHANGE_EVT*/ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* AVDT_DELAY_RPT_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* ACP_CONNECT_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* API_OFFLOAD_START_EVT */
+ {BTA_AV_OFFLOAD_REQ, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* API_OFFLOAD_START_RSP_EVT */
+ {BTA_AV_OFFLOAD_RSP, BTA_AV_SIGNORE, BTA_AV_INIT_SST}};
+
+/* state table for incoming state */
+static const uint8_t bta_av_sst_incoming[][BTA_AV_NUM_COLS] = {
+ /* Event Action 1 Action 2 Next state */
+ /* API_OPEN_EVT */ {BTA_AV_OPEN_AT_INC, BTA_AV_SIGNORE,
+ BTA_AV_INCOMING_SST},
+ /* API_CLOSE_EVT */
+ {BTA_AV_CCO_CLOSE, BTA_AV_DISCONNECT_REQ, BTA_AV_CLOSING_SST},
+ /* AP_START_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* AP_STOP_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* API_RECONFIG_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* API_PROTECT_REQ_EVT */
+ {BTA_AV_SECURITY_REQ, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* API_PROTECT_RSP_EVT */
+ {BTA_AV_SECURITY_RSP, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* API_RC_OPEN_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* SRC_DATA_READY_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* CI_SETCONFIG_OK_EVT */
+ {BTA_AV_SETCONFIG_RSP, BTA_AV_ST_RC_TIMER, BTA_AV_INCOMING_SST},
+ /* CI_SETCONFIG_FAIL_EVT */
+ {BTA_AV_SETCONFIG_REJ, BTA_AV_CLEANUP, BTA_AV_INIT_SST},
+ /* SDP_DISC_OK_EVT */
+ {BTA_AV_FREE_SDB, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* SDP_DISC_FAIL_EVT */
+ {BTA_AV_FREE_SDB, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_DISC_OK_EVT */
+ {BTA_AV_DISC_RES_AS_ACP, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_DISC_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_GETCAP_OK_EVT */
+ {BTA_AV_SAVE_CAPS, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_GETCAP_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_OPEN_OK_EVT */ {BTA_AV_STR_OPENED, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_OPEN_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_START_OK_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_START_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_CLOSE_EVT */ {BTA_AV_CCO_CLOSE, BTA_AV_CLEANUP, BTA_AV_INIT_SST},
+ /* STR_CONFIG_IND_EVT */
+ {BTA_AV_CONFIG_IND, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_SECURITY_IND_EVT */
+ {BTA_AV_SECURITY_IND, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_SECURITY_CFM_EVT */
+ {BTA_AV_SECURITY_CFM, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_WRITE_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_SUSPEND_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_RECONFIG_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* AVRC_TIMER_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* AVDT_CONNECT_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* AVDT_DISCONNECT_EVT */
+ {BTA_AV_CCO_CLOSE, BTA_AV_DISCONNECT_REQ, BTA_AV_CLOSING_SST},
+ /* ROLE_CHANGE_EVT*/ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* AVDT_DELAY_RPT_EVT */
+ {BTA_AV_DELAY_CO, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* ACP_CONNECT_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* API_OFFLOAD_START_EVT */
+ {BTA_AV_OFFLOAD_REQ, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* API_OFFLOAD_START_RSP_EVT */
+ {BTA_AV_OFFLOAD_RSP, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST}};
+
+/* state table for opening state */
+static const uint8_t bta_av_sst_opening[][BTA_AV_NUM_COLS] = {
+ /* Event Action 1 Action 2 Next state */
+ /* API_OPEN_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* API_CLOSE_EVT */ {BTA_AV_DO_CLOSE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* AP_START_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* AP_STOP_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* API_RECONFIG_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* API_PROTECT_REQ_EVT */
+ {BTA_AV_SECURITY_REQ, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* API_PROTECT_RSP_EVT */
+ {BTA_AV_SECURITY_RSP, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* API_RC_OPEN_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* SRC_DATA_READY_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* CI_SETCONFIG_OK_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* CI_SETCONFIG_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* SDP_DISC_OK_EVT */
+ {BTA_AV_CONNECT_REQ, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* SDP_DISC_FAIL_EVT */
+ {BTA_AV_CONNECT_REQ, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* STR_DISC_OK_EVT */
+ {BTA_AV_DISC_RESULTS, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* STR_DISC_FAIL_EVT */
+ {BTA_AV_OPEN_FAILED, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_GETCAP_OK_EVT */
+ {BTA_AV_GETCAP_RESULTS, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* STR_GETCAP_FAIL_EVT */
+ {BTA_AV_OPEN_FAILED, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_OPEN_OK_EVT */
+ {BTA_AV_ST_RC_TIMER, BTA_AV_STR_OPENED, BTA_AV_OPEN_SST},
+ /* STR_OPEN_FAIL_EVT */
+ {BTA_AV_OPEN_FAILED, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_START_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* STR_START_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* STR_CLOSE_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* STR_CONFIG_IND_EVT */
+ {BTA_AV_CONFIG_IND, BTA_AV_SIGNORE, BTA_AV_INCOMING_SST},
+ /* STR_SECURITY_IND_EVT */
+ {BTA_AV_SECURITY_IND, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* STR_SECURITY_CFM_EVT */
+ {BTA_AV_SECURITY_CFM, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* STR_WRITE_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* STR_SUSPEND_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* STR_RECONFIG_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* AVRC_TIMER_EVT */
+ {BTA_AV_SWITCH_ROLE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* AVDT_CONNECT_EVT */
+ {BTA_AV_DISCOVER_REQ, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* AVDT_DISCONNECT_EVT */
+ {BTA_AV_CONN_FAILED, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* ROLE_CHANGE_EVT*/ {BTA_AV_ROLE_RES, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* AVDT_DELAY_RPT_EVT */
+ {BTA_AV_DELAY_CO, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* ACP_CONNECT_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* API_OFFLOAD_START_EVT */
+ {BTA_AV_OFFLOAD_REQ, BTA_AV_SIGNORE, BTA_AV_OPENING_SST},
+ /* API_OFFLOAD_START_RSP_EVT */
+ {BTA_AV_OFFLOAD_RSP, BTA_AV_SIGNORE, BTA_AV_OPENING_SST}};
+
+/* state table for open state */
+static const uint8_t bta_av_sst_open[][BTA_AV_NUM_COLS] = {
+ /* Event Action 1 Action 2 Next state */
+ /* API_OPEN_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* API_CLOSE_EVT */ {BTA_AV_DO_CLOSE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* AP_START_EVT */ {BTA_AV_DO_START, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* AP_STOP_EVT */ {BTA_AV_STR_STOPPED, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* API_RECONFIG_EVT */ {BTA_AV_RECONFIG, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* API_PROTECT_REQ_EVT */
+ {BTA_AV_SECURITY_REQ, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* API_PROTECT_RSP_EVT */
+ {BTA_AV_SECURITY_RSP, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* API_RC_OPEN_EVT */ {BTA_AV_SET_USE_RC, BTA_AV_OPEN_RC, BTA_AV_OPEN_SST},
+ /* SRC_DATA_READY_EVT */
+ {BTA_AV_DATA_PATH, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* CI_SETCONFIG_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* CI_SETCONFIG_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* SDP_DISC_OK_EVT */ {BTA_AV_FREE_SDB, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* SDP_DISC_FAIL_EVT */ {BTA_AV_FREE_SDB, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_DISC_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_DISC_FAIL_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_GETCAP_OK_EVT */ {BTA_AV_SAVE_CAPS, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_GETCAP_FAIL_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_OPEN_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_OPEN_FAIL_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_START_OK_EVT */ {BTA_AV_START_OK, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_START_FAIL_EVT */
+ {BTA_AV_START_FAILED, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_CLOSE_EVT */ {BTA_AV_STR_CLOSED, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_CONFIG_IND_EVT */
+ {BTA_AV_SETCONFIG_REJ, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_SECURITY_IND_EVT */
+ {BTA_AV_SECURITY_IND, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_SECURITY_CFM_EVT */
+ {BTA_AV_SECURITY_CFM, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_WRITE_CFM_EVT */
+ {BTA_AV_CLR_CONG, BTA_AV_DATA_PATH, BTA_AV_OPEN_SST},
+ /* STR_SUSPEND_CFM_EVT */
+ {BTA_AV_SUSPEND_CFM, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_RECONFIG_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* AVRC_TIMER_EVT */
+ {BTA_AV_OPEN_RC, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* AVDT_CONNECT_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* AVDT_DISCONNECT_EVT */
+ {BTA_AV_STR_CLOSED, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* ROLE_CHANGE_EVT*/ {BTA_AV_ROLE_RES, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* AVDT_DELAY_RPT_EVT */ {BTA_AV_DELAY_CO, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* ACP_CONNECT_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* API_OFFLOAD_START_EVT */
+ {BTA_AV_OFFLOAD_REQ, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* API_OFFLOAD_START_RSP_EVT */
+ {BTA_AV_OFFLOAD_RSP, BTA_AV_SIGNORE, BTA_AV_OPEN_SST}};
+
+/* state table for reconfig state */
+static const uint8_t bta_av_sst_rcfg[][BTA_AV_NUM_COLS] = {
+ /* Event Action 1 Action 2 Next state */
+ /* API_OPEN_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* API_CLOSE_EVT */
+ {BTA_AV_DISCONNECT_REQ, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* AP_START_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* AP_STOP_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* API_RECONFIG_EVT */ {BTA_AV_RECONFIG, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* API_PROTECT_REQ_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* API_PROTECT_RSP_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* API_RC_OPEN_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* SRC_DATA_READY_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* CI_SETCONFIG_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* CI_SETCONFIG_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* SDP_DISC_OK_EVT */ {BTA_AV_FREE_SDB, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* SDP_DISC_FAIL_EVT */ {BTA_AV_FREE_SDB, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* STR_DISC_OK_EVT */
+ {BTA_AV_DISC_RESULTS, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* STR_DISC_FAIL_EVT */
+ {BTA_AV_STR_CLOSED, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_GETCAP_OK_EVT */
+ {BTA_AV_GETCAP_RESULTS, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* STR_GETCAP_FAIL_EVT */
+ {BTA_AV_STR_CLOSED, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_OPEN_OK_EVT */ {BTA_AV_RCFG_STR_OK, BTA_AV_SIGNORE, BTA_AV_OPEN_SST},
+ /* STR_OPEN_FAIL_EVT */
+ {BTA_AV_RCFG_FAILED, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* STR_START_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* STR_START_FAIL_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* STR_CLOSE_EVT */ {BTA_AV_RCFG_CONNECT, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* STR_CONFIG_IND_EVT */
+ {BTA_AV_SETCONFIG_REJ, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* STR_SECURITY_IND_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* STR_SECURITY_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* STR_WRITE_CFM_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* STR_SUSPEND_CFM_EVT */
+ {BTA_AV_SUSPEND_CFM, BTA_AV_SUSPEND_CONT, BTA_AV_RCFG_SST},
+ /* STR_RECONFIG_CFM_EVT */
+ {BTA_AV_RCFG_CFM, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* AVRC_TIMER_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* AVDT_CONNECT_EVT */ {BTA_AV_RCFG_OPEN, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* AVDT_DISCONNECT_EVT */
+ {BTA_AV_RCFG_DISCNTD, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* ROLE_CHANGE_EVT*/ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* AVDT_DELAY_RPT_EVT */ {BTA_AV_DELAY_CO, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* ACP_CONNECT_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* API_OFFLOAD_START_EVT */
+ {BTA_AV_OFFLOAD_REQ, BTA_AV_SIGNORE, BTA_AV_RCFG_SST},
+ /* API_OFFLOAD_START_RSP_EVT */
+ {BTA_AV_OFFLOAD_RSP, BTA_AV_SIGNORE, BTA_AV_RCFG_SST}};
+
+/* state table for closing state */
+static const uint8_t bta_av_sst_closing[][BTA_AV_NUM_COLS] = {
+ /* Event Action 1 Action 2 Next state */
+ /* API_OPEN_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* API_CLOSE_EVT */
+ {BTA_AV_DISCONNECT_REQ, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* AP_START_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* AP_STOP_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* API_RECONFIG_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* API_PROTECT_REQ_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* API_PROTECT_RSP_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* API_RC_OPEN_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* SRC_DATA_READY_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* CI_SETCONFIG_OK_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* CI_SETCONFIG_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* SDP_DISC_OK_EVT */ {BTA_AV_SDP_FAILED, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* SDP_DISC_FAIL_EVT */
+ {BTA_AV_SDP_FAILED, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* STR_DISC_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_DISC_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_GETCAP_OK_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_GETCAP_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_OPEN_OK_EVT */ {BTA_AV_DO_CLOSE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_OPEN_FAIL_EVT */
+ {BTA_AV_DISCONNECT_REQ, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_START_OK_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_START_FAIL_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_CLOSE_EVT */
+ {BTA_AV_DISCONNECT_REQ, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_CONFIG_IND_EVT */
+ {BTA_AV_SETCONFIG_REJ, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_SECURITY_IND_EVT */
+ {BTA_AV_SECURITY_REJ, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_SECURITY_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_WRITE_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_SUSPEND_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* STR_RECONFIG_CFM_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* AVRC_TIMER_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* AVDT_CONNECT_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* AVDT_DISCONNECT_EVT */
+ {BTA_AV_STR_CLOSED, BTA_AV_SIGNORE, BTA_AV_INIT_SST},
+ /* ROLE_CHANGE_EVT*/ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* AVDT_DELAY_RPT_EVT */
+ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* ACP_CONNECT_EVT */ {BTA_AV_SIGNORE, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* API_OFFLOAD_START_EVT */
+ {BTA_AV_OFFLOAD_REQ, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST},
+ /* API_OFFLOAD_START_RSP_EVT */
+ {BTA_AV_OFFLOAD_RSP, BTA_AV_SIGNORE, BTA_AV_CLOSING_SST}};
+
+/* type for state table */
+typedef const uint8_t (*tBTA_AV_SST_TBL)[BTA_AV_NUM_COLS];
+
+/* state table */
+static const tBTA_AV_SST_TBL bta_av_sst_tbl[] = {
+ bta_av_sst_init, bta_av_sst_incoming, bta_av_sst_opening,
+ bta_av_sst_open, bta_av_sst_rcfg, bta_av_sst_closing};
- if (event_handler1 != nullptr) {
- event_handler1(p_scb, p_data);
- }
- if (event_handler2 != nullptr) {
- event_handler2(p_scb, p_data);
- }
-}
/*******************************************************************************
*
@@ -456,7 +486,41 @@ void bta_av_ssm_execute(tBTA_AV_SCB* p_scb, uint16_t event,
return;
}
- bta_av_better_stream_state_machine(p_scb, event, p_data);
+ /* look up the state table for the current state */
+ tBTA_AV_SST_TBL state_table = bta_av_sst_tbl[p_scb->state];
+
+ /* set next state */
+ auto new_state =
+ state_table[event - BTA_AV_FIRST_SSM_EVT][BTA_AV_SNEXT_STATE];
+ if (p_scb->state != new_state) {
+ APPL_TRACE_WARNING(
+ "%s: peer %s AV event(0x%x)=0x%x(%s) state=%d(%s) -> %d(%s) p_scb=%p",
+ __func__, p_scb->PeerAddress().ToString().c_str(), p_scb->hndl, event,
+ bta_av_evt_code(event), p_scb->state, bta_av_sst_code(p_scb->state),
+ new_state, bta_av_sst_code(new_state), p_scb);
+ } else {
+ APPL_TRACE_VERBOSE(
+ "%s: peer %s AV event(0x%x)=0x%x(%s) state=%d(%s) p_scb=%p", __func__,
+ p_scb->PeerAddress().ToString().c_str(), p_scb->hndl, event,
+ bta_av_evt_code(event), p_scb->state, bta_av_sst_code(p_scb->state),
+ p_scb);
+ }
+ event -= BTA_AV_FIRST_SSM_EVT;
+ p_scb->state = state_table[event][BTA_AV_SNEXT_STATE];
+
+ APPL_TRACE_VERBOSE("%s: peer %s AV next state=%d(%s) p_scb=%p(0x%x)",
+ __func__, p_scb->PeerAddress().ToString().c_str(),
+ p_scb->state, bta_av_sst_code(p_scb->state), p_scb,
+ p_scb->hndl);
+
+ /* execute action functions */
+ for (int i = 0; i < BTA_AV_SACTIONS; i++) {
+ uint8_t action = state_table[event][i];
+ if (action != BTA_AV_SIGNORE) {
+ (*p_scb->p_act_tbl[action])(p_scb, p_data);
+ } else
+ break;
+ }
}
/*******************************************************************************
diff --git a/bta/dm/bta_dm_act.cc b/bta/dm/bta_dm_act.cc
index 8f9e26e52..3900594bf 100644
--- a/bta/dm/bta_dm_act.cc
+++ b/bta/dm/bta_dm_act.cc
@@ -25,31 +25,34 @@
#define LOG_TAG "bt_bta_dm"
-#include <cstdint>
-
-#include "bta/dm/bta_dm_int.h"
-#include "bta/gatt/bta_gattc_int.h"
-#include "bta/include/bta_dm_ci.h"
-#include "btif/include/btif_dm.h"
-#include "btif/include/btif_storage.h"
-#include "btif/include/stack_manager.h"
-#include "device/include/controller.h"
+#include <base/bind.h>
+#include <base/callback.h>
+#include <base/logging.h>
+#include <string.h>
+
+#include "bt_common.h"
+#include "bt_target.h"
+#include "bt_types.h"
+#include "bta_api.h"
+#include "bta_dm_api.h"
+#include "bta_dm_co.h"
+#include "bta_dm_int.h"
+#include "bta_sys.h"
+#include "btif_storage.h"
+#include "btif_config.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
#include "device/include/interop.h"
-#include "main/shim/acl_api.h"
-#include "main/shim/btm_api.h"
-#include "main/shim/dumpsys.h"
-#include "main/shim/shim.h"
-#include "osi/include/fixed_queue.h"
+#include "gap_api.h" /* For GAP_BleReadPeerPrefConnParams */
+#include "l2c_api.h"
#include "osi/include/log.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/btm/neighbor_inquiry.h"
+#include "sdp_api.h"
+#include "stack/btm/btm_ble_int.h"
#include "stack/gatt/connection_manager.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_client_interface.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "types/raw_address.h"
+#include "stack/include/gatt_api.h"
+#include "utl.h"
#if (GAP_INCLUDED == TRUE)
#include "gap_api.h"
@@ -57,10 +60,6 @@
using bluetooth::Uuid;
-void BTIF_dm_disable();
-void BTIF_dm_enable();
-void btm_ble_adv_init(void);
-
static void bta_dm_inq_results_cb(tBTM_INQ_RESULTS* p_inq, uint8_t* p_eir,
uint16_t eir_len);
static void bta_dm_inq_cmpl_cb(void* p_result);
@@ -69,31 +68,40 @@ static void bta_dm_service_search_remname_cback(const RawAddress& bd_addr,
static void bta_dm_remname_cback(void* p);
static void bta_dm_find_services(const RawAddress& bd_addr);
static void bta_dm_discover_next_device(void);
-static void bta_dm_sdp_callback(tSDP_STATUS sdp_status);
+static void bta_dm_sdp_callback(uint16_t sdp_status);
+static uint8_t bta_dm_authorize_cback(const RawAddress& bd_addr,
+ DEV_CLASS dev_class, BD_NAME bd_name,
+ uint8_t* service_name, uint8_t service_id,
+ bool is_originator);
static uint8_t bta_dm_pin_cback(const RawAddress& bd_addr, DEV_CLASS dev_class,
BD_NAME bd_name, bool min_16_digit);
static uint8_t bta_dm_new_link_key_cback(const RawAddress& bd_addr,
DEV_CLASS dev_class, BD_NAME bd_name,
const LinkKey& key, uint8_t key_type);
-static void bta_dm_authentication_complete_cback(const RawAddress& bd_addr,
- DEV_CLASS dev_class,
- BD_NAME bd_name,
- tHCI_REASON result);
+static uint8_t bta_dm_authentication_complete_cback(const RawAddress& bd_addr,
+ DEV_CLASS dev_class,
+ BD_NAME bd_name,
+ int result);
static void bta_dm_local_name_cback(void* p_name);
-static void bta_dm_check_av();
+static bool bta_dm_check_av(uint16_t event);
+static void bta_dm_bl_change_cback(tBTM_BL_EVENT_DATA* p_data);
-void BTA_dm_update_policy(tBTA_SYS_CONN_STATUS status, uint8_t id,
- uint8_t app_id, const RawAddress& peer_addr);
+static void bta_dm_policy_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
+ uint8_t app_id, const RawAddress& peer_addr);
/* Extended Inquiry Response */
-static tBTM_STATUS bta_dm_sp_cback(tBTM_SP_EVT event, tBTM_SP_EVT_DATA* p_data);
+static uint8_t bta_dm_sp_cback(tBTM_SP_EVT event, tBTM_SP_EVT_DATA* p_data);
static void bta_dm_set_eir(char* local_name);
+static void bta_dm_eir_search_services(tBTM_INQ_RESULTS* p_result,
+ tBTA_SERVICE_MASK* p_services_to_search,
+ tBTA_SERVICE_MASK* p_services_found);
+
static void bta_dm_search_timer_cback(void* data);
static void bta_dm_disable_conn_down_timer_cback(void* data);
-void bta_dm_rm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr);
+static void bta_dm_rm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
+ uint8_t app_id, const RawAddress& peer_addr);
static void bta_dm_adjust_roles(bool delay_role_switch);
static char* bta_dm_get_remname(void);
static void bta_dm_bond_cancel_complete_cback(tBTM_STATUS result);
@@ -102,6 +110,7 @@ static bool bta_dm_read_remote_device_name(const RawAddress& bd_addr,
tBT_TRANSPORT transport);
static void bta_dm_discover_device(const RawAddress& remote_bd_addr);
+static void bta_dm_sys_hw_cback(tBTA_SYS_HW_EVT status);
static void bta_dm_disable_search_and_disc(void);
static uint8_t bta_dm_ble_smp_cback(tBTM_LE_EVT event, const RawAddress& bda,
@@ -113,8 +122,9 @@ static void btm_dm_start_gatt_discovery(const RawAddress& bd_addr);
static void bta_dm_cancel_gatt_discovery(const RawAddress& bd_addr);
static void bta_dm_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data);
extern tBTA_DM_CONTRL_STATE bta_dm_pm_obtain_controller_state(void);
+
#if (BLE_VND_INCLUDED == TRUE)
-static void bta_dm_ctrl_features_rd_cmpl_cback(tHCI_STATUS result);
+static void bta_dm_ctrl_features_rd_cmpl_cback(tBTM_STATUS result);
#endif
#ifndef BTA_DM_BLE_ADV_CHNL_MAP
@@ -124,7 +134,7 @@ static void bta_dm_ctrl_features_rd_cmpl_cback(tHCI_STATUS result);
/* Disable timer interval (in milliseconds) */
#ifndef BTA_DM_DISABLE_TIMER_MS
-#define BTA_DM_DISABLE_TIMER_MS (2000)
+#define BTA_DM_DISABLE_TIMER_MS 5000
#endif
/* Disable timer retrial interval (in milliseconds) */
@@ -142,58 +152,13 @@ static void bta_dm_ctrl_features_rd_cmpl_cback(tHCI_STATUS result);
#define BTA_DM_SWITCH_DELAY_TIMER_MS 500
#endif
-namespace {
-
-// Time to wait after receiving shutdown request to delay the actual shutdown
-// process. This time may be zero which invokes immediate shutdown.
-#ifndef BTA_DISABLE_DELAY
-constexpr uint64_t kDisableDelayTimerInMs = 0;
-#else
-constexpr uint64_t kDisableDelayTimerInMs =
- static_cast<uint64_t>(BTA_DISABLE_DELAY);
-#endif
-
-struct WaitForAllAclConnectionsToDrain {
- uint64_t time_to_wait_in_ms;
- unsigned long TimeToWaitInMs() const {
- return static_cast<unsigned long>(time_to_wait_in_ms);
- }
- void* AlarmCallbackData() const {
- return const_cast<void*>(static_cast<const void*>(this));
- }
-
- static const WaitForAllAclConnectionsToDrain* FromAlarmCallbackData(
- void* data);
- static bool IsFirstPass(const WaitForAllAclConnectionsToDrain*);
-} first_pass =
- {
- .time_to_wait_in_ms = static_cast<uint64_t>(BTA_DM_DISABLE_TIMER_MS),
-},
- second_pass = {
- .time_to_wait_in_ms =
- static_cast<uint64_t>(BTA_DM_DISABLE_TIMER_RETRIAL_MS),
-};
-
-bool WaitForAllAclConnectionsToDrain::IsFirstPass(
- const WaitForAllAclConnectionsToDrain* pass) {
- return pass == &first_pass;
-}
-
-const WaitForAllAclConnectionsToDrain*
-WaitForAllAclConnectionsToDrain::FromAlarmCallbackData(void* data) {
- return const_cast<const WaitForAllAclConnectionsToDrain*>(
- static_cast<WaitForAllAclConnectionsToDrain*>(data));
-}
-
-} // namespace
-
static void bta_dm_reset_sec_dev_pending(const RawAddress& remote_bd_addr);
static void bta_dm_remove_sec_dev_entry(const RawAddress& remote_bd_addr);
static void bta_dm_observe_results_cb(tBTM_INQ_RESULTS* p_inq, uint8_t* p_eir,
uint16_t eir_len);
static void bta_dm_observe_cmpl_cb(void* p_result);
static void bta_dm_delay_role_switch_cback(void* data);
-static void bta_dm_wait_for_acl_to_drain_cback(void* data);
+static void bta_dm_disable_timer_cback(void* data);
const uint16_t bta_service_id_to_uuid_lkup_tbl[BTA_MAX_SERVICE_ID] = {
UUID_SERVCLASS_PNP_INFORMATION, /* Reserved */
@@ -228,15 +193,56 @@ const uint16_t bta_service_id_to_uuid_lkup_tbl[BTA_MAX_SERVICE_ID] = {
UUID_PROTOCOL_ATT /* BTA_GATT_SERVICE_ID */
};
+/*
+ * NOTE : The number of element in bta_service_id_to_btm_srv_id_lkup_tbl should
+ * be matching with the value BTA_MAX_SERVICE_ID in bta_api.h
+ *
+ * i.e., If you add new Service ID for BTA, the correct security ID of the new
+ * service from Security service definitions (btm_api.h) should be added to
+ * this lookup table.
+ */
+const uint32_t bta_service_id_to_btm_srv_id_lkup_tbl[BTA_MAX_SERVICE_ID] = {
+ 0, /* Reserved */
+ BTM_SEC_SERVICE_SERIAL_PORT, /* BTA_SPP_SERVICE_ID */
+ BTM_SEC_SERVICE_DUN, /* BTA_DUN_SERVICE_ID */
+ BTM_SEC_SERVICE_AVDTP, /* BTA_AUDIO_SOURCE_SERVICE_ID */
+ BTM_SEC_SERVICE_LAN_ACCESS, /* BTA_LAP_SERVICE_ID */
+ BTM_SEC_SERVICE_HEADSET_AG, /* BTA_HSP_SERVICE_ID */
+ BTM_SEC_SERVICE_AG_HANDSFREE, /* BTA_HFP_SERVICE_ID */
+ BTM_SEC_SERVICE_OBEX, /* BTA_OPP_SERVICE_ID */
+ BTM_SEC_SERVICE_OBEX_FTP, /* BTA_FTP_SERVICE_ID */
+ BTM_SEC_SERVICE_CORDLESS, /* BTA_CTP_SERVICE_ID */
+ BTM_SEC_SERVICE_INTERCOM, /* BTA_ICP_SERVICE_ID */
+ BTM_SEC_SERVICE_IRMC_SYNC, /* BTA_SYNC_SERVICE_ID */
+ BTM_SEC_SERVICE_BPP_JOB, /* BTA_BPP_SERVICE_ID */
+ BTM_SEC_SERVICE_BIP, /* BTA_BIP_SERVICE_ID */
+ BTM_SEC_SERVICE_BNEP_PANU, /* BTA_PANU_SERVICE_ID */
+ BTM_SEC_SERVICE_BNEP_NAP, /* BTA_NAP_SERVICE_ID */
+ BTM_SEC_SERVICE_BNEP_GN, /* BTA_GN_SERVICE_ID */
+ BTM_SEC_SERVICE_SAP, /* BTA_SAP_SERVICE_ID */
+ BTM_SEC_SERVICE_AVDTP, /* BTA_A2DP_SERVICE_ID */
+ BTM_SEC_SERVICE_AVCTP, /* BTA_AVRCP_SERVICE_ID */
+ BTM_SEC_SERVICE_HIDH_SEC_CTRL, /* BTA_HID_SERVICE_ID */
+ BTM_SEC_SERVICE_AVDTP, /* BTA_VDP_SERVICE_ID */
+ BTM_SEC_SERVICE_PBAP, /* BTA_PBAP_SERVICE_ID */
+ BTM_SEC_SERVICE_HEADSET, /* BTA_HSP_HS_SERVICE_ID */
+ BTM_SEC_SERVICE_HF_HANDSFREE, /* BTA_HFP_HS_SERVICE_ID */
+ BTM_SEC_SERVICE_MAP, /* BTA_MAP_SERVICE_ID */
+ BTM_SEC_SERVICE_MAP, /* BTA_MN_SERVICE_ID */
+ BTM_SEC_SERVICE_HDP_SNK, /* BTA_HDP_SERVICE_ID */
+ BTM_SEC_SERVICE_PBAP, /* BTA_PCE_SERVICE_ID */
+ BTM_SEC_SERVICE_ATT /* BTA_GATT_SERVICE_ID */
+};
+
/* bta security callback */
-const tBTM_APPL_INFO bta_security = {
- .p_pin_callback = &bta_dm_pin_cback,
- .p_link_key_callback = &bta_dm_new_link_key_cback,
- .p_auth_complete_callback = &bta_dm_authentication_complete_cback,
- .p_bond_cancel_cmpl_callback = &bta_dm_bond_cancel_complete_cback,
- .p_sp_callback = &bta_dm_sp_cback,
- .p_le_callback = &bta_dm_ble_smp_cback,
- .p_le_key_callback = &bta_dm_ble_id_key_cback};
+const tBTM_APPL_INFO bta_security = {&bta_dm_authorize_cback,
+ &bta_dm_pin_cback,
+ &bta_dm_new_link_key_cback,
+ &bta_dm_authentication_complete_cback,
+ &bta_dm_bond_cancel_complete_cback,
+ &bta_dm_sp_cback,
+ &bta_dm_ble_smp_cback,
+ &bta_dm_ble_id_key_cback};
#define MAX_DISC_RAW_DATA_BUF (4096)
uint8_t g_disc_raw_data_buf[MAX_DISC_RAW_DATA_BUF];
@@ -248,6 +254,20 @@ static uint8_t btm_local_io_caps;
/** Initialises the BT device manager */
void bta_dm_enable(tBTA_DM_SEC_CBACK* p_sec_cback) {
+ /* if already in use, return an error */
+ if (bta_dm_cb.is_bta_dm_active) {
+ tBTA_DM_SEC enable_event;
+ APPL_TRACE_WARNING("%s Device already started by another application",
+ __func__);
+ memset(&enable_event, 0, sizeof(tBTA_DM_SEC));
+ enable_event.enable.status = BTA_FAILURE;
+ if (p_sec_cback != NULL) p_sec_cback(BTA_DM_ENABLE_EVT, &enable_event);
+ return;
+ }
+
+ /* first, register our callback to SYS HW manager */
+ bta_sys_hw_register(BTA_SYS_HW_BLUETOOTH, bta_dm_sys_hw_cback);
+
/* make sure security callback is saved - if no callback, do not erase the
previous one,
it could be an error recovery mechanism */
@@ -255,6 +275,14 @@ void bta_dm_enable(tBTA_DM_SEC_CBACK* p_sec_cback) {
/* notify BTA DM is now active */
bta_dm_cb.is_bta_dm_active = true;
+ /* send a message to BTA SYS */
+ tBTA_SYS_HW_MSG* sys_enable_event =
+ (tBTA_SYS_HW_MSG*)osi_malloc(sizeof(tBTA_SYS_HW_MSG));
+ sys_enable_event->hdr.event = BTA_SYS_API_ENABLE_EVT;
+ sys_enable_event->hw_module = BTA_SYS_HW_BLUETOOTH;
+
+ bta_sys_sendmsg(sys_enable_event);
+
btm_local_io_caps = btif_storage_get_local_io_caps();
}
@@ -304,111 +332,135 @@ void bta_dm_deinit_cb(void) {
memset(&bta_dm_cb, 0, sizeof(bta_dm_cb));
}
-void BTA_dm_on_hw_off() {
- BTIF_dm_disable();
-
- /* reinitialize the control block */
- bta_dm_deinit_cb();
-
- /* hw is ready, go on with BTA DM initialization */
- alarm_free(bta_dm_search_cb.search_timer);
- alarm_free(bta_dm_search_cb.gatt_close_timer);
- osi_free(bta_dm_search_cb.p_pending_search);
- fixed_queue_free(bta_dm_search_cb.pending_discovery_queue, osi_free);
- memset(&bta_dm_search_cb, 0, sizeof(bta_dm_search_cb));
-
- /* notify BTA DM is now unactive */
- bta_dm_cb.is_bta_dm_active = false;
-}
-
-void BTA_dm_on_hw_on() {
+/*******************************************************************************
+ *
+ * Function bta_dm_sys_hw_cback
+ *
+ * Description callback register to SYS to get HW status updates
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void bta_dm_sys_hw_cback(tBTA_SYS_HW_EVT status) {
DEV_CLASS dev_class;
tBTA_DM_SEC_CBACK* temp_cback;
uint8_t key_mask = 0;
tBTA_BLE_LOCAL_ID_KEYS id_key;
- /* save security callback */
- temp_cback = bta_dm_cb.p_sec_cback;
- /* make sure the control block is properly initialized */
- bta_dm_init_cb();
- /* and retrieve the callback */
- bta_dm_cb.p_sec_cback = temp_cback;
- bta_dm_cb.is_bta_dm_active = true;
+ APPL_TRACE_DEBUG("%s with event: %i", __func__, status);
- /* hw is ready, go on with BTA DM initialization */
- alarm_free(bta_dm_search_cb.search_timer);
- alarm_free(bta_dm_search_cb.gatt_close_timer);
- osi_free(bta_dm_search_cb.p_pending_search);
- fixed_queue_free(bta_dm_search_cb.pending_discovery_queue, osi_free);
- memset(&bta_dm_search_cb, 0, sizeof(bta_dm_search_cb));
- /*
- * TODO: Should alarm_free() the bta_dm_search_cb timers during
- * graceful shutdown.
- */
- bta_dm_search_cb.search_timer = alarm_new("bta_dm_search.search_timer");
- bta_dm_search_cb.gatt_close_timer =
- alarm_new("bta_dm_search.gatt_close_timer");
- bta_dm_search_cb.pending_discovery_queue = fixed_queue_new(SIZE_MAX);
+ /* On H/W error evt, report to the registered DM application callback */
+ if (status == BTA_SYS_HW_ERROR_EVT) {
+ if (bta_dm_cb.p_sec_cback != NULL)
+ bta_dm_cb.p_sec_cback(BTA_DM_HW_ERROR_EVT, NULL);
+ return;
+ }
+
+ if (status == BTA_SYS_HW_OFF_EVT) {
+ if (bta_dm_cb.p_sec_cback != NULL)
+ bta_dm_cb.p_sec_cback(BTA_DM_DISABLE_EVT, NULL);
+
+ /* reinitialize the control block */
+ bta_dm_deinit_cb();
+
+ /* hw is ready, go on with BTA DM initialization */
+ alarm_free(bta_dm_search_cb.search_timer);
+ alarm_free(bta_dm_search_cb.gatt_close_timer);
+ memset(&bta_dm_search_cb, 0, sizeof(bta_dm_search_cb));
+
+ /* unregister from SYS */
+ bta_sys_hw_unregister(BTA_SYS_HW_BLUETOOTH);
+ /* notify BTA DM is now unactive */
+ bta_dm_cb.is_bta_dm_active = false;
+ } else if (status == BTA_SYS_HW_ON_EVT) {
+ /* FIXME: We should not unregister as the SYS shall invoke this callback on
+ * a H/W error.
+ * We need to revisit when this platform has more than one BLuetooth H/W
+ * chip
+ */
+ // bta_sys_hw_unregister( BTA_SYS_HW_BLUETOOTH);
+
+ /* save security callback */
+ temp_cback = bta_dm_cb.p_sec_cback;
+ /* make sure the control block is properly initialized */
+ bta_dm_init_cb();
+ /* and retrieve the callback */
+ bta_dm_cb.p_sec_cback = temp_cback;
+ bta_dm_cb.is_bta_dm_active = true;
+
+ /* hw is ready, go on with BTA DM initialization */
+ alarm_free(bta_dm_search_cb.search_timer);
+ alarm_free(bta_dm_search_cb.gatt_close_timer);
+ memset(&bta_dm_search_cb, 0, sizeof(bta_dm_search_cb));
+ /*
+ * TODO: Should alarm_free() the bta_dm_search_cb timers during
+ * graceful shutdown.
+ */
+ bta_dm_search_cb.search_timer = alarm_new("bta_dm_search.search_timer");
+ bta_dm_search_cb.gatt_close_timer =
+ alarm_new("bta_dm_search.gatt_close_timer");
- memset(&bta_dm_conn_srvcs, 0, sizeof(bta_dm_conn_srvcs));
- memset(&bta_dm_di_cb, 0, sizeof(tBTA_DM_DI_CB));
+ memset(&bta_dm_conn_srvcs, 0, sizeof(bta_dm_conn_srvcs));
+ memset(&bta_dm_di_cb, 0, sizeof(tBTA_DM_DI_CB));
- memcpy(dev_class, p_bta_dm_cfg->dev_class, sizeof(dev_class));
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_SetDeviceClass(dev_class);
- } else {
+ memcpy(dev_class, p_bta_dm_cfg->dev_class, sizeof(dev_class));
BTM_SetDeviceClass(dev_class);
- }
- /* load BLE local information: ID keys, ER if available */
- Octet16 er;
- btif_dm_get_ble_local_keys(&key_mask, &er, &id_key);
+ /* load BLE local information: ID keys, ER if available */
+ Octet16 er;
+ bta_dm_co_ble_load_local_keys(&key_mask, &er, &id_key);
- if (key_mask & BTA_BLE_LOCAL_KEY_TYPE_ER) {
- get_btm_client_interface().ble.BTM_BleLoadLocalKeys(
- BTA_BLE_LOCAL_KEY_TYPE_ER, (tBTM_BLE_LOCAL_KEYS*)&er);
- }
- if (key_mask & BTA_BLE_LOCAL_KEY_TYPE_ID) {
- get_btm_client_interface().ble.BTM_BleLoadLocalKeys(
- BTA_BLE_LOCAL_KEY_TYPE_ID, (tBTM_BLE_LOCAL_KEYS*)&id_key);
- }
- bta_dm_search_cb.conn_id = GATT_INVALID_CONN_ID;
-
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_SecRegister(&bta_security);
- } else {
- get_btm_client_interface().security.BTM_SecRegister(&bta_security);
- }
+ if (key_mask & BTA_BLE_LOCAL_KEY_TYPE_ER) {
+ BTM_BleLoadLocalKeys(BTA_BLE_LOCAL_KEY_TYPE_ER,
+ (tBTM_BLE_LOCAL_KEYS*)&er);
+ }
+ if (key_mask & BTA_BLE_LOCAL_KEY_TYPE_ID) {
+ BTM_BleLoadLocalKeys(BTA_BLE_LOCAL_KEY_TYPE_ID,
+ (tBTM_BLE_LOCAL_KEYS*)&id_key);
+ }
+ bta_dm_search_cb.conn_id = GATT_INVALID_CONN_ID;
- BTM_WritePageTimeout(p_bta_dm_cfg->page_timeout);
+ BTM_SecRegister(&bta_security);
+ BTM_SetDefaultLinkSuperTout(p_bta_dm_cfg->link_timeout);
+ BTM_WritePageTimeout(p_bta_dm_cfg->page_timeout);
+ bta_dm_cb.cur_policy = p_bta_dm_cfg->policy_settings;
+ BTM_SetDefaultLinkPolicy(bta_dm_cb.cur_policy);
+ BTM_RegBusyLevelNotif(bta_dm_bl_change_cback, NULL,
+ BTM_BL_UPDATE_MASK | BTM_BL_ROLE_CHG_MASK);
#if (BLE_VND_INCLUDED == TRUE)
- BTM_BleReadControllerFeatures(bta_dm_ctrl_features_rd_cmpl_cback);
+ BTM_BleReadControllerFeatures(bta_dm_ctrl_features_rd_cmpl_cback);
#else
- /* If VSC multi adv commands are available, advertising will be initialized
- * when capabilities are read. If they are not available, initialize
- * advertising here */
- btm_ble_adv_init();
+ /* If VSC multi adv commands are available, advertising will be initialized
+ * when capabilities are read. If they are not avaliable, initialize
+ * advertising here */
+ btm_ble_adv_init();
#endif
- /* Earlier, we used to invoke BTM_ReadLocalAddr which was just copying the
- bd_addr
- from the control block and invoking the callback which was sending the
- DM_ENABLE_EVT.
- But then we have a few HCI commands being invoked above which were still
- in progress
- when the ENABLE_EVT was sent. So modified this to fetch the local name
- which forces
- the DM_ENABLE_EVT to be sent only after all the init steps are complete
- */
- BTM_ReadLocalDeviceNameFromController(bta_dm_local_name_cback);
+ /* Earlier, we used to invoke BTM_ReadLocalAddr which was just copying the
+ bd_addr
+ from the control block and invoking the callback which was sending the
+ DM_ENABLE_EVT.
+ But then we have a few HCI commands being invoked above which were still
+ in progress
+ when the ENABLE_EVT was sent. So modified this to fetch the local name
+ which forces
+ the DM_ENABLE_EVT to be sent only after all the init steps are complete
+ */
+ BTM_ReadLocalDeviceNameFromController(bta_dm_local_name_cback);
- bta_sys_rm_register(bta_dm_rm_cback);
+ bta_sys_rm_register(bta_dm_rm_cback);
- /* initialize bluetooth low power manager */
- bta_dm_init_pm();
+ /* initialize bluetooth low power manager */
+ bta_dm_init_pm();
- bta_dm_gattc_register();
+ bta_sys_policy_register(bta_dm_policy_cback);
+
+ bta_dm_gattc_register();
+
+ } else
+ APPL_TRACE_DEBUG(" --- ignored event");
}
/** Disables the BT device manager */
@@ -419,10 +471,10 @@ void bta_dm_disable() {
L2CA_SetIdleTimeoutByBdAddr(RawAddress::kAny, 0, BT_TRANSPORT_LE);
/* disable all active subsystems */
- bta_sys_disable();
+ bta_sys_disable(BTA_SYS_HW_BLUETOOTH);
- BTM_SetDiscoverability(BTM_NON_DISCOVERABLE);
- BTM_SetConnectability(BTM_NON_CONNECTABLE);
+ BTM_SetDiscoverability(BTM_NON_DISCOVERABLE, 0, 0);
+ BTM_SetConnectability(BTM_NON_CONNECTABLE, 0, 0);
bta_dm_disable_pm();
bta_dm_disable_search_and_disc();
@@ -431,30 +483,27 @@ void bta_dm_disable() {
connection_manager::reset(false);
if (BTM_GetNumAclLinks() == 0) {
- // We can shut down faster if there are no ACL links
- switch (kDisableDelayTimerInMs) {
- case 0:
- LOG_DEBUG("Immediately disabling device manager");
- bta_dm_disable_conn_down_timer_cback(nullptr);
- break;
- default:
- LOG_DEBUG("Set timer to delay disable initiation:%lu ms",
- static_cast<unsigned long>(kDisableDelayTimerInMs));
- alarm_set_on_mloop(bta_dm_cb.disable_timer, kDisableDelayTimerInMs,
- bta_dm_disable_conn_down_timer_cback, nullptr);
- }
+#if (BTA_DISABLE_DELAY > 0)
+ /* If BTA_DISABLE_DELAY is defined and greater than zero, then delay the
+ * shutdown by
+ * BTA_DISABLE_DELAY milliseconds
+ */
+ APPL_TRACE_WARNING("%s BTA_DISABLE_DELAY set to %d ms", __func__,
+ BTA_DISABLE_DELAY);
+ alarm_set_on_mloop(bta_dm_cb.disable_timer, BTA_DISABLE_DELAY,
+ bta_dm_disable_conn_down_timer_cback, NULL);
+#else
+ bta_dm_disable_conn_down_timer_cback(NULL);
+#endif
} else {
- LOG_DEBUG("Set timer to wait for all ACL connections to close:%lu ms",
- first_pass.TimeToWaitInMs());
- alarm_set_on_mloop(bta_dm_cb.disable_timer, first_pass.time_to_wait_in_ms,
- bta_dm_wait_for_acl_to_drain_cback,
- first_pass.AlarmCallbackData());
+ alarm_set_on_mloop(bta_dm_cb.disable_timer, BTA_DM_DISABLE_TIMER_MS,
+ bta_dm_disable_timer_cback, UINT_TO_PTR(0));
}
}
/*******************************************************************************
*
- * Function bta_dm_wait_for_all_acl_to_drain
+ * Function bta_dm_disable_timer_cback
*
* Description Called if the disable timer expires
* Used to close ACL connections which are still active
@@ -464,45 +513,35 @@ void bta_dm_disable() {
* Returns void
*
******************************************************************************/
-static bool force_disconnect_all_acl_connections() {
- const bool is_force_disconnect_needed = (bta_dm_cb.device_list.count > 0);
+static void bta_dm_disable_timer_cback(void* data) {
+ uint8_t i;
+ tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
+ bool trigger_disc = false;
+ uint32_t param = PTR_TO_UINT(data);
- for (auto i = 0; i < bta_dm_cb.device_list.count; i++) {
- btm_remove_acl(bta_dm_cb.device_list.peer_device[i].peer_bdaddr,
- bta_dm_cb.device_list.peer_device[i].transport);
- }
- return is_force_disconnect_needed;
-}
+ APPL_TRACE_EVENT("%s trial %u", __func__, param);
-static void bta_dm_wait_for_acl_to_drain_cback(void* data) {
- ASSERT(data != nullptr);
- const WaitForAllAclConnectionsToDrain* pass =
- WaitForAllAclConnectionsToDrain::FromAlarmCallbackData(data);
+ if (BTM_GetNumAclLinks() && (param == 0)) {
+ for (i = 0; i < bta_dm_cb.device_list.count; i++) {
+ transport = bta_dm_cb.device_list.peer_device[i].transport;
+ btm_remove_acl(bta_dm_cb.device_list.peer_device[i].peer_bdaddr,
+ transport);
+ trigger_disc = true;
+ }
- if (BTM_GetNumAclLinks() &&
- WaitForAllAclConnectionsToDrain::IsFirstPass(pass)) {
- /* DISABLE_EVT still need to be sent out to avoid java layer disable timeout
- */
- if (force_disconnect_all_acl_connections()) {
- LOG_DEBUG(
- "Set timer for second pass to wait for all ACL connections to "
- "close:%lu ms ",
- second_pass.TimeToWaitInMs());
- alarm_set_on_mloop(
- bta_dm_cb.disable_timer, second_pass.time_to_wait_in_ms,
- bta_dm_wait_for_acl_to_drain_cback, second_pass.AlarmCallbackData());
+ /* Retrigger disable timer in case ACL disconnect failed, DISABLE_EVT still
+ need
+ to be sent out to avoid jave layer disable timeout */
+ if (trigger_disc) {
+ alarm_set_on_mloop(bta_dm_cb.disable_timer,
+ BTA_DM_DISABLE_TIMER_RETRIAL_MS,
+ bta_dm_disable_timer_cback, UINT_TO_PTR(1));
}
} else {
- // No ACL links were up or is second pass at ACL closure
- if (bluetooth::shim::is_gd_acl_enabled()) {
- LOG_INFO("Ensuring all ACL connections have been properly flushed");
- bluetooth::shim::ACL_Shutdown();
- }
-
bta_dm_cb.disabling = false;
bta_sys_remove_uuid(UUID_SERVCLASS_PNP_INFORMATION);
- BTIF_dm_disable();
+ bta_dm_cb.p_sec_cback(BTA_DM_DISABLE_EVT, NULL);
}
}
@@ -513,56 +552,80 @@ void bta_dm_set_dev_name(const std::vector<uint8_t>& name) {
}
/** Sets discoverability, connectability and pairability */
-bool BTA_DmSetVisibility(bt_scan_mode_t mode) {
- tBTA_DM_DISC disc_mode_param;
- tBTA_DM_CONN conn_mode_param;
-
- switch (mode) {
- case BT_SCAN_MODE_NONE:
- disc_mode_param = BTA_DM_NON_DISC;
- conn_mode_param = BTA_DM_NON_CONN;
- break;
+void bta_dm_set_visibility(tBTA_DM_DISC disc_mode_param,
+ tBTA_DM_CONN conn_mode_param, uint8_t pairable_mode,
+ uint8_t conn_paired_only) {
+ uint16_t window, interval;
+ uint16_t le_disc_mode = BTM_BleReadDiscoverability();
+ uint16_t le_conn_mode = BTM_BleReadConnectability();
+ uint16_t disc_mode = BTM_ReadDiscoverability(&window, &interval);
+ uint16_t conn_mode = BTM_ReadConnectability(&window, &interval);
+
+ /* set modes for Discoverability and connectability if not ignore */
+ if (disc_mode_param != (BTA_DM_IGNORE | BTA_DM_LE_IGNORE)) {
+ if ((disc_mode_param & BTA_DM_LE_IGNORE) == BTA_DM_LE_IGNORE)
+ disc_mode_param = ((disc_mode_param & ~BTA_DM_LE_IGNORE) | le_disc_mode);
+ if ((disc_mode_param & BTA_DM_IGNORE) == BTA_DM_IGNORE)
+ disc_mode_param = ((disc_mode_param & ~BTA_DM_IGNORE) | disc_mode);
+
+ BTM_SetDiscoverability(disc_mode_param, bta_dm_cb.inquiry_scan_window,
+ bta_dm_cb.inquiry_scan_interval);
+ }
- case BT_SCAN_MODE_CONNECTABLE:
- disc_mode_param = BTA_DM_NON_DISC;
- conn_mode_param = BTA_DM_CONN;
- break;
+ if (conn_mode_param != (BTA_DM_IGNORE | BTA_DM_LE_IGNORE)) {
+ if ((conn_mode_param & BTA_DM_LE_IGNORE) == BTA_DM_LE_IGNORE)
+ conn_mode_param = ((conn_mode_param & ~BTA_DM_LE_IGNORE) | le_conn_mode);
+ if ((conn_mode_param & BTA_DM_IGNORE) == BTA_DM_IGNORE)
+ conn_mode_param = ((conn_mode_param & ~BTA_DM_IGNORE) | conn_mode);
- case BT_SCAN_MODE_CONNECTABLE_DISCOVERABLE:
- disc_mode_param = BTA_DM_GENERAL_DISC;
- conn_mode_param = BTA_DM_CONN;
- break;
+ BTM_SetConnectability(conn_mode_param, bta_dm_cb.page_scan_window,
+ bta_dm_cb.page_scan_interval);
+ }
- default:
- return false;
+ /* Send False or True if not ignore */
+ if (pairable_mode != BTA_DM_IGNORE) {
+ if (pairable_mode == BTA_DM_NON_PAIRABLE)
+ bta_dm_cb.disable_pair_mode = true;
+ else
+ bta_dm_cb.disable_pair_mode = false;
}
- BTM_SetDiscoverability(disc_mode_param);
- BTM_SetConnectability(conn_mode_param);
- return true;
+ /* Send False or True if not ignore */
+ if (conn_paired_only != BTA_DM_IGNORE) {
+ if (conn_paired_only == BTA_DM_CONN_ALL)
+ bta_dm_cb.conn_paired_only = false;
+ else
+ bta_dm_cb.conn_paired_only = true;
+ }
+
+ /* Change mode if either mode is not ignore */
+ if (pairable_mode != BTA_DM_IGNORE || conn_paired_only != BTA_DM_IGNORE)
+ BTM_SetPairableMode((bool)(!(bta_dm_cb.disable_pair_mode)),
+ bta_dm_cb.conn_paired_only);
}
-static void bta_dm_process_remove_device_no_callback(
- const RawAddress& bd_addr) {
+/*******************************************************************************
+ *
+ * Function bta_dm_process_remove_device
+ *
+ * Description Removes device, Disconnects ACL link if required.
+ ***
+ ******************************************************************************/
+void bta_dm_process_remove_device(const RawAddress& bd_addr) {
/* need to remove all pending background connection before unpair */
BTA_GATTC_CancelOpen(0, bd_addr, false);
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_SecDeleteDevice(bd_addr);
- } else {
- BTM_SecDeleteDevice(bd_addr);
- }
+ BTM_SecDeleteDevice(bd_addr);
/* remove all cached GATT information */
BTA_GATTC_Refresh(bd_addr);
-}
-
-void bta_dm_process_remove_device(const RawAddress& bd_addr) {
- bta_dm_process_remove_device_no_callback(bd_addr);
if (bta_dm_cb.p_sec_cback) {
tBTA_DM_SEC sec_event;
sec_event.link_down.bd_addr = bd_addr;
+ ;
+ /* No connection, set status to success (acl disc code not valid) */
+ sec_event.link_down.status = HCI_SUCCESS;
bta_dm_cb.p_sec_cback(BTA_DM_DEV_UNPAIRED_EVT, &sec_event);
}
}
@@ -586,7 +649,7 @@ void bta_dm_remove_device(const RawAddress& bd_addr) {
if (peer_device.peer_bdaddr == bd_addr) {
peer_device.conn_state = BTA_DM_UNPAIRING;
- /* Make sure device is not in acceptlist before we disconnect */
+ /* Make sure device is not in white list before we disconnect */
GATT_CancelConnect(0, bd_addr, false);
btm_remove_acl(bd_addr, peer_device.transport);
@@ -623,11 +686,10 @@ void bta_dm_remove_device(const RawAddress& bd_addr) {
* disconnected */
for (int i = 0; i < bta_dm_cb.device_list.count; i++) {
auto& peer_device = bta_dm_cb.device_list.peer_device[i];
- if (peer_device.peer_bdaddr == other_address &&
- peer_device.transport == other_transport) {
+ if (peer_device.peer_bdaddr == other_address) {
peer_device.conn_state = BTA_DM_UNPAIRING;
- /* Make sure device is not in acceptlist before we disconnect */
+ /* Make sure device is not in white list before we disconnect */
GATT_CancelConnect(0, bd_addr, false);
btm_remove_acl(other_address, peer_device.transport);
@@ -645,6 +707,12 @@ void bta_dm_remove_device(const RawAddress& bd_addr) {
if (!other_address_connected && !other_address.IsEmpty()) {
bta_dm_process_remove_device(other_address);
}
+
+ /* Check the length of the paired devices, and if 0 then reset IRK */
+ if (btif_storage_get_num_bonded_devices() < 1) {
+ LOG(INFO) << "Last paired device removed, resetting IRK";
+ btm_ble_reset_id();
+ }
}
/*******************************************************************************
@@ -658,29 +726,44 @@ void bta_dm_remove_device(const RawAddress& bd_addr) {
void bta_dm_add_device(std::unique_ptr<tBTA_DM_API_ADD_DEVICE> msg) {
uint8_t* p_dc = NULL;
LinkKey* p_lc = NULL;
+ uint32_t trusted_services_mask[BTM_SEC_SERVICE_ARRAY_SIZE];
+ uint8_t index = 0;
+ uint8_t btm_mask_index = 0;
+
+ memset(trusted_services_mask, 0, sizeof(trusted_services_mask));
/* If not all zeros, the device class has been specified */
if (msg->dc_known) p_dc = (uint8_t*)msg->dc;
if (msg->link_key_known) p_lc = &msg->link_key;
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_SecAddDevice(msg->bd_addr, p_dc, msg->bd_name, nullptr,
- p_lc, msg->key_type, msg->pin_length);
- } else {
- auto add_result =
- BTM_SecAddDevice(msg->bd_addr, p_dc, msg->bd_name, nullptr, p_lc,
- msg->key_type, msg->pin_length);
- if (!add_result) {
- LOG(ERROR) << "BTA_DM: Error adding device " << msg->bd_addr;
+ if (msg->is_trusted) {
+ /* covert BTA service mask to BTM mask */
+ while (msg->tm && (index < BTA_MAX_SERVICE_ID)) {
+ if (msg->tm & (uint32_t)(1 << index)) {
+ btm_mask_index =
+ bta_service_id_to_btm_srv_id_lkup_tbl[index] / BTM_SEC_ARRAY_BITS;
+ trusted_services_mask[btm_mask_index] |=
+ (uint32_t)(1 << (bta_service_id_to_btm_srv_id_lkup_tbl[index] -
+ (uint32_t)(btm_mask_index * 32)));
+
+ msg->tm &= (uint32_t)(~(1 << index));
+ }
+ index++;
}
}
+
+ if (!BTM_SecAddDevice(msg->bd_addr, p_dc, msg->bd_name, msg->features,
+ trusted_services_mask, p_lc, msg->key_type, msg->io_cap,
+ msg->pin_length)) {
+ LOG(ERROR) << "BTA_DM: Error adding device " << msg->bd_addr;
+ }
}
/** This function forces to close the connection to a remote device and
* optionaly remove the device from security database if required. */
void bta_dm_close_acl(const RawAddress& bd_addr, bool remove_dev,
- tBT_TRANSPORT transport) {
+ tBTA_TRANSPORT transport) {
uint8_t index;
APPL_TRACE_DEBUG("bta_dm_close_acl");
@@ -697,7 +780,7 @@ void bta_dm_close_acl(const RawAddress& bd_addr, bool remove_dev,
APPL_TRACE_ERROR("unknown device, remove ACL failed");
}
- /* Make sure device is not in acceptlist before we disconnect */
+ /* Make sure device is not in white list before we disconnect */
GATT_CancelConnect(0, bd_addr, false);
/* Disconnect the ACL link */
@@ -705,32 +788,53 @@ void bta_dm_close_acl(const RawAddress& bd_addr, bool remove_dev,
}
/* if to remove the device from security database ? do it now */
else if (remove_dev) {
- bta_dm_process_remove_device_no_callback(bd_addr);
+ if (!BTM_SecDeleteDevice(bd_addr)) {
+ APPL_TRACE_ERROR("delete device from security database failed.");
+ }
+ /* need to remove all pending background connection if any */
+ BTA_GATTC_CancelOpen(0, bd_addr, false);
+ /* remove all cached GATT information */
+ BTA_GATTC_Refresh(bd_addr);
}
/* otherwise, no action needed */
}
+// TODO: this is unused. remove?
+/** This function forces to close all the ACL links specified by link type */
+void bta_dm_remove_all_acl(const tBTA_DM_LINK_TYPE link_type) {
+ tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
+
+ APPL_TRACE_DEBUG("%s link type = %d", __func__, link_type);
+
+ for (uint8_t i = 0; i < bta_dm_cb.device_list.count; i++) {
+ transport = bta_dm_cb.device_list.peer_device[i].transport;
+ if ((link_type == BTA_DM_LINK_TYPE_ALL) ||
+ ((link_type == BTA_DM_LINK_TYPE_LE) &&
+ (transport == BT_TRANSPORT_LE)) ||
+ ((link_type == BTA_DM_LINK_TYPE_BR_EDR) &&
+ (transport == BT_TRANSPORT_BR_EDR))) {
+ /* Disconnect the ACL link */
+ btm_remove_acl(bta_dm_cb.device_list.peer_device[i].peer_bdaddr,
+ transport);
+ }
+ }
+}
+
/** Bonds with peer device */
void bta_dm_bond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type) {
+ tBTA_TRANSPORT transport) {
tBTA_DM_SEC sec_event;
char* p_name;
- tBTM_STATUS status =
- (bluetooth::shim::is_gd_security_enabled())
- ? bluetooth::shim::BTM_SecBond(bd_addr, addr_type, transport,
- device_type)
- : BTM_SecBond(bd_addr, addr_type, transport, device_type, 0, NULL);
+ tBTM_STATUS status = BTM_SecBond(bd_addr, addr_type, transport, 0, NULL, 0);
if (bta_dm_cb.p_sec_cback && (status != BTM_CMD_STARTED)) {
memset(&sec_event, 0, sizeof(tBTA_DM_SEC));
sec_event.auth_cmpl.bd_addr = bd_addr;
- p_name = (bluetooth::shim::is_gd_security_enabled())
- ? bluetooth::shim::BTM_SecReadDevName(bd_addr)
- : BTM_SecReadDevName(bd_addr);
+ p_name = BTM_SecReadDevName(bd_addr);
if (p_name != NULL) {
- memcpy(sec_event.auth_cmpl.bd_name, p_name, BD_NAME_LEN);
- sec_event.auth_cmpl.bd_name[BD_NAME_LEN] = 0;
+ memcpy(sec_event.auth_cmpl.bd_name, p_name, (BD_NAME_LEN - 1));
+ sec_event.auth_cmpl.bd_name[BD_NAME_LEN - 1] = 0;
}
/* taken care of by memset [above]
@@ -754,10 +858,7 @@ void bta_dm_bond_cancel(const RawAddress& bd_addr) {
tBTA_DM_SEC sec_event;
APPL_TRACE_EVENT(" bta_dm_bond_cancel ");
-
- status = (bluetooth::shim::is_gd_security_enabled())
- ? bluetooth::shim::BTM_SecBondCancel(bd_addr)
- : BTM_SecBondCancel(bd_addr);
+ status = BTM_SecBondCancel(bd_addr);
if (bta_dm_cb.p_sec_cback &&
(status != BTM_CMD_STARTED && status != BTM_SUCCESS)) {
@@ -769,43 +870,98 @@ void bta_dm_bond_cancel(const RawAddress& bd_addr) {
/** Send the pin_reply to a request from BTM */
void bta_dm_pin_reply(std::unique_ptr<tBTA_DM_API_PIN_REPLY> msg) {
+ uint32_t trusted_mask[BTM_SEC_SERVICE_ARRAY_SIZE];
+
+ uint32_t* current_trusted_mask = BTM_ReadTrustedMask(msg->bd_addr);
+ if (current_trusted_mask) {
+ memcpy(trusted_mask, current_trusted_mask, sizeof(trusted_mask));
+ } else {
+ memset(trusted_mask, 0, sizeof(trusted_mask));
+ }
+
if (msg->accept) {
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_PINCodeReply(msg->bd_addr, BTM_SUCCESS, msg->pin_len,
- msg->p_pin);
- } else {
- BTM_PINCodeReply(msg->bd_addr, BTM_SUCCESS, msg->pin_len, msg->p_pin);
- }
+ BTM_PINCodeReply(msg->bd_addr, BTM_SUCCESS, msg->pin_len, msg->p_pin,
+ trusted_mask);
} else {
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_PINCodeReply(msg->bd_addr, BTM_NOT_AUTHORIZED, 0,
- NULL);
- } else {
- BTM_PINCodeReply(msg->bd_addr, BTM_NOT_AUTHORIZED, 0, NULL);
- }
+ BTM_PINCodeReply(msg->bd_addr, BTM_NOT_AUTHORIZED, 0, NULL, trusted_mask);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_policy_cback
+ *
+ * Description process the link policy changes
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void bta_dm_policy_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
+ uint8_t app_id, const RawAddress& peer_addr) {
+ tBTA_DM_PEER_DEVICE* p_dev = NULL;
+ uint16_t policy = app_id;
+ uint32_t mask = (uint32_t)(1 << id);
+
+ if (peer_addr != RawAddress::kEmpty) {
+ p_dev = bta_dm_find_peer_device(peer_addr);
+ }
+
+ APPL_TRACE_DEBUG(" bta_dm_policy_cback cmd:%d, policy:0x%x", status, policy);
+ switch (status) {
+ case BTA_SYS_PLCY_SET:
+ if (!p_dev) return;
+ /* restore the default link policy */
+ p_dev->link_policy |= policy;
+ BTM_SetLinkPolicy(p_dev->peer_bdaddr, &(p_dev->link_policy));
+ break;
+
+ case BTA_SYS_PLCY_CLR:
+ if (!p_dev) return;
+ /* clear the policy from the default link policy */
+ p_dev->link_policy &= (~policy);
+ BTM_SetLinkPolicy(p_dev->peer_bdaddr, &(p_dev->link_policy));
+
+ if (policy & (HCI_ENABLE_SNIFF_MODE | HCI_ENABLE_PARK_MODE)) {
+ /* if clearing sniff/park, wake the link */
+ bta_dm_pm_active(p_dev->peer_bdaddr);
+ }
+ break;
+
+ case BTA_SYS_PLCY_DEF_SET:
+ /* want to restore/set the role switch policy */
+ bta_dm_cb.role_policy_mask &= ~mask;
+ if (0 == bta_dm_cb.role_policy_mask) {
+ /* if nobody wants to insist on the role */
+ bta_dm_cb.cur_policy |= HCI_ENABLE_MASTER_SLAVE_SWITCH;
+ BTM_SetDefaultLinkPolicy(bta_dm_cb.cur_policy);
+ }
+ break;
+
+ case BTA_SYS_PLCY_DEF_CLR:
+ /* want to remove the role switch policy */
+ bta_dm_cb.role_policy_mask |= mask;
+ bta_dm_cb.cur_policy &= ~HCI_ENABLE_MASTER_SLAVE_SWITCH;
+ BTM_SetDefaultLinkPolicy(bta_dm_cb.cur_policy);
+ break;
}
}
/** Send the user confirm request reply in response to a request from BTM */
void bta_dm_confirm(const RawAddress& bd_addr, bool accept) {
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_ConfirmReqReply(
- accept ? BTM_SUCCESS : BTM_NOT_AUTHORIZED, bd_addr);
- } else {
- BTM_ConfirmReqReply(accept ? BTM_SUCCESS : BTM_NOT_AUTHORIZED, bd_addr);
- }
+ BTM_ConfirmReqReply(accept ? BTM_SUCCESS : BTM_NOT_AUTHORIZED, bd_addr);
+}
+
+/** respond to the IO capabilities request from BTM */
+void bta_dm_ci_io_req_act(const RawAddress& bd_addr, tBTA_IO_CAP io_cap,
+ tBTA_OOB_DATA oob_data, tBTA_AUTH_REQ auth_req) {
+ BTM_IoCapRsp(bd_addr, io_cap, oob_data,
+ auth_req ? BTM_AUTH_AP_YES : BTM_AUTH_AP_NO);
}
/** respond to the OOB data request for the remote device from BTM */
void bta_dm_ci_rmt_oob_act(std::unique_ptr<tBTA_DM_CI_RMT_OOB> msg) {
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_RemoteOobDataReply(
- msg->accept ? BTM_SUCCESS : BTM_NOT_AUTHORIZED, msg->bd_addr, msg->c,
- msg->r);
- } else {
- BTM_RemoteOobDataReply(msg->accept ? BTM_SUCCESS : BTM_NOT_AUTHORIZED,
- msg->bd_addr, msg->c, msg->r);
- }
+ BTM_RemoteOobDataReply(msg->accept ? BTM_SUCCESS : BTM_NOT_AUTHORIZED,
+ msg->bd_addr, msg->c, msg->r);
}
/*******************************************************************************
@@ -821,17 +977,34 @@ void bta_dm_ci_rmt_oob_act(std::unique_ptr<tBTA_DM_CI_RMT_OOB> msg) {
void bta_dm_search_start(tBTA_DM_MSG* p_data) {
tBTM_INQUIRY_CMPL result = {};
+ size_t len = sizeof(Uuid) * p_data->search.num_uuid;
bta_dm_gattc_register();
APPL_TRACE_DEBUG("%s avoid_scatter=%d", __func__,
p_bta_dm_cfg->avoid_scatter);
+ if (p_bta_dm_cfg->avoid_scatter &&
+ (p_data->search.rs_res == BTA_DM_RS_NONE) &&
+ bta_dm_check_av(BTA_DM_API_SEARCH_EVT)) {
+ LOG(INFO) << __func__ << ": delay search to avoid scatter";
+ memcpy(&bta_dm_cb.search_msg, &p_data->search, sizeof(tBTA_DM_API_SEARCH));
+ return;
+ }
+
BTM_ClearInqDb(nullptr);
/* save search params */
bta_dm_search_cb.p_search_cback = p_data->search.p_cback;
bta_dm_search_cb.services = p_data->search.services;
- result.status = BTM_StartInquiry(bta_dm_inq_results_cb, bta_dm_inq_cmpl_cb);
+ osi_free_and_reset((void**)&bta_dm_search_cb.p_srvc_uuid);
+
+ if ((bta_dm_search_cb.num_uuid = p_data->search.num_uuid) != 0 &&
+ p_data->search.p_uuid != nullptr) {
+ bta_dm_search_cb.p_srvc_uuid = (Uuid*)osi_malloc(len);
+ *bta_dm_search_cb.p_srvc_uuid = *p_data->search.p_uuid;
+ }
+ result.status = BTM_StartInquiry((tBTM_INQ_PARMS*)&p_data->search.inq_params,
+ bta_dm_inq_results_cb, bta_dm_inq_cmpl_cb);
APPL_TRACE_EVENT("%s status=%d", __func__, result.status);
if (result.status != BTM_CMD_STARTED) {
@@ -852,19 +1025,35 @@ void bta_dm_search_start(tBTA_DM_MSG* p_data) {
* Returns void
*
******************************************************************************/
-void bta_dm_search_cancel() {
+void bta_dm_search_cancel(UNUSED_ATTR tBTA_DM_MSG* p_data) {
+ tBTA_DM_MSG* p_msg;
+
if (BTM_IsInquiryActive()) {
- BTM_CancelInquiry();
- bta_dm_search_cancel_notify();
- bta_dm_search_cmpl();
+ if (BTM_CancelInquiry() == BTM_SUCCESS) {
+ bta_dm_search_cancel_notify(NULL);
+ p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
+ p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
+ p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
+ bta_sys_sendmsg(p_msg);
+ } else {
+ /* flag a search cancel is pending */
+ bta_dm_search_cb.cancel_pending = true;
+ }
}
/* If no Service Search going on then issue cancel remote name in case it is
active */
else if (!bta_dm_search_cb.name_discover_done) {
BTM_CancelRemoteDeviceName();
- bta_dm_search_cmpl();
+
+ p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
+ p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
+ p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
+ bta_sys_sendmsg(p_msg);
} else {
- bta_dm_inq_cmpl(0);
+ p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
+ p_msg->hdr.event = BTA_DM_INQUIRY_CMPL_EVT;
+ p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
+ bta_sys_sendmsg(p_msg);
}
if (bta_dm_search_cb.gatt_disc_active) {
@@ -883,25 +1072,85 @@ void bta_dm_search_cancel() {
*
******************************************************************************/
void bta_dm_discover(tBTA_DM_MSG* p_data) {
+ size_t len = sizeof(Uuid) * p_data->discover.num_uuid;
+ APPL_TRACE_EVENT("%s services_to_search=0x%04X, sdp_search=%d", __func__,
+ p_data->discover.services, p_data->discover.sdp_search);
+
/* save the search condition */
- bta_dm_search_cb.services = BTA_ALL_SERVICE_MASK;
+ bta_dm_search_cb.services = p_data->discover.services;
bta_dm_gattc_register();
+ osi_free_and_reset((void**)&bta_dm_search_cb.p_srvc_uuid);
+ if ((bta_dm_search_cb.num_uuid = p_data->discover.num_uuid) != 0 &&
+ p_data->discover.p_uuid != NULL) {
+ bta_dm_search_cb.p_srvc_uuid = (Uuid*)osi_malloc(len);
+ *bta_dm_search_cb.p_srvc_uuid = *p_data->discover.p_uuid;
+ }
+ bta_dm_search_cb.uuid_to_search = bta_dm_search_cb.num_uuid;
bta_dm_search_cb.p_search_cback = p_data->discover.p_cback;
+ bta_dm_search_cb.sdp_search = p_data->discover.sdp_search;
bta_dm_search_cb.services_to_search = bta_dm_search_cb.services;
bta_dm_search_cb.service_index = 0;
bta_dm_search_cb.services_found = 0;
bta_dm_search_cb.peer_name[0] = 0;
+ bta_dm_search_cb.sdp_search = p_data->discover.sdp_search;
bta_dm_search_cb.p_btm_inq_info = BTM_InqDbRead(p_data->discover.bd_addr);
bta_dm_search_cb.transport = p_data->discover.transport;
bta_dm_search_cb.name_discover_done = false;
+ bta_dm_search_cb.uuid = p_data->discover.uuid;
bta_dm_discover_device(p_data->discover.bd_addr);
}
/*******************************************************************************
*
+ * Function bta_dm_di_disc_cmpl
+ *
+ * Description Sends event to application when DI discovery complete
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_dm_di_disc_cmpl(tBTA_DM_MSG* p_data) {
+ tBTA_DM_DI_DISC_CMPL di_disc;
+
+ memset(&di_disc, 0, sizeof(tBTA_DM_DI_DISC_CMPL));
+ di_disc.bd_addr = bta_dm_search_cb.peer_bdaddr;
+
+ if ((p_data->hdr.offset == SDP_SUCCESS) ||
+ (p_data->hdr.offset == SDP_DB_FULL)) {
+ di_disc.num_record = SDP_GetNumDiRecords(bta_dm_di_cb.p_di_db);
+ } else
+ di_disc.result = BTA_FAILURE;
+
+ bta_dm_di_cb.p_di_db = NULL;
+ bta_dm_search_cb.p_search_cback(BTA_DM_DI_DISC_CMPL_EVT,
+ (tBTA_DM_SEARCH*)&di_disc);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_di_disc_callback
+ *
+ * Description This function queries a remote device for DI information.
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void bta_dm_di_disc_callback(uint16_t result) {
+ tBTA_DM_MSG* p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
+
+ p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
+ p_msg->hdr.layer_specific = BTA_DM_API_DI_DISCOVER_EVT;
+ p_msg->hdr.offset = result;
+
+ bta_sys_sendmsg(p_msg);
+}
+
+/*******************************************************************************
+ *
* Function bta_dm_disable_search_and_disc
*
* Description Cancels an ongoing search or discovery for devices in case
@@ -912,7 +1161,53 @@ void bta_dm_discover(tBTA_DM_MSG* p_data) {
*
******************************************************************************/
static void bta_dm_disable_search_and_disc(void) {
- if (bta_dm_search_cb.state != BTA_DM_SEARCH_IDLE) bta_dm_search_cancel();
+ tBTA_DM_DI_DISC_CMPL di_disc;
+
+ if (bta_dm_search_cb.state != BTA_DM_SEARCH_IDLE) bta_dm_search_cancel(NULL);
+
+ if (bta_dm_di_cb.p_di_db != NULL) {
+ memset(&di_disc, 0, sizeof(tBTA_DM_DI_DISC_CMPL));
+ di_disc.bd_addr = bta_dm_search_cb.peer_bdaddr;
+ di_disc.result = BTA_FAILURE;
+
+ bta_dm_di_cb.p_di_db = NULL;
+ bta_dm_search_cb.p_search_cback(BTA_DM_DI_DISC_CMPL_EVT, NULL);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_di_disc
+ *
+ * Description This function queries a remote device for DI information.
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_dm_di_disc(tBTA_DM_MSG* p_data) {
+ uint16_t result = BTA_FAILURE;
+
+ bta_dm_search_cb.p_search_cback = p_data->di_disc.p_cback;
+ bta_dm_search_cb.peer_bdaddr = p_data->di_disc.bd_addr;
+ bta_dm_di_cb.p_di_db = p_data->di_disc.p_sdp_db;
+
+ bta_dm_search_cb.p_sdp_db =
+ (tSDP_DISCOVERY_DB*)osi_malloc(BTA_DM_SDP_DB_SIZE);
+ if (SDP_DiDiscover(bta_dm_search_cb.peer_bdaddr, p_data->di_disc.p_sdp_db,
+ p_data->di_disc.len,
+ bta_dm_di_disc_callback) == SDP_SUCCESS) {
+ result = BTA_SUCCESS;
+ }
+
+ if (result == BTA_FAILURE) {
+ tBTA_DM_MSG* p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
+
+ p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
+ p_msg->hdr.layer_specific = BTA_DM_API_DI_DISCOVER_EVT;
+ p_data->hdr.offset = result;
+ bta_sys_sendmsg(p_msg);
+ }
}
/*******************************************************************************
@@ -933,12 +1228,8 @@ static bool bta_dm_read_remote_device_name(const RawAddress& bd_addr,
bta_dm_search_cb.peer_bdaddr = bd_addr;
bta_dm_search_cb.peer_name[0] = 0;
- btm_status =
- (bluetooth::shim::is_gd_security_enabled())
- ? bluetooth::shim::BTM_ReadRemoteDeviceName(
- bta_dm_search_cb.peer_bdaddr, bta_dm_remname_cback, transport)
- : BTM_ReadRemoteDeviceName(bta_dm_search_cb.peer_bdaddr,
- bta_dm_remname_cback, transport);
+ btm_status = BTM_ReadRemoteDeviceName(bta_dm_search_cb.peer_bdaddr,
+ bta_dm_remname_cback, transport);
if (btm_status == BTM_CMD_STARTED) {
APPL_TRACE_DEBUG("%s: BTM_ReadRemoteDeviceName is started", __func__);
@@ -950,13 +1241,7 @@ static bool bta_dm_read_remote_device_name(const RawAddress& bd_addr,
/* Remote name discovery is on going now so BTM cannot notify through
* "bta_dm_remname_cback" */
/* adding callback to get notified that current reading remore name done */
-
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_SecAddRmtNameNotifyCallback(
- &bta_dm_service_search_remname_cback);
- } else {
- BTM_SecAddRmtNameNotifyCallback(&bta_dm_service_search_remname_cback);
- }
+ BTM_SecAddRmtNameNotifyCallback(&bta_dm_service_search_remname_cback);
return (true);
} else {
@@ -976,22 +1261,12 @@ static bool bta_dm_read_remote_device_name(const RawAddress& bd_addr,
* Returns void
*
******************************************************************************/
-void bta_dm_inq_cmpl(uint8_t num) {
- if (bta_dm_search_get_state() == BTA_DM_SEARCH_CANCELLING) {
- bta_dm_search_set_state(BTA_DM_SEARCH_IDLE);
- bta_dm_search_cancel_cmpl();
- return;
- }
-
- if (bta_dm_search_get_state() != BTA_DM_SEARCH_ACTIVE) {
- return;
- }
-
+void bta_dm_inq_cmpl(tBTA_DM_MSG* p_data) {
tBTA_DM_SEARCH data;
APPL_TRACE_DEBUG("bta_dm_inq_cmpl");
- data.inq_cmpl.num_resps = num;
+ data.inq_cmpl.num_resps = p_data->inq_cmpl.num;
bta_dm_search_cb.p_search_cback(BTA_DM_INQ_CMPL_EVT, &data);
bta_dm_search_cb.p_btm_inq_info = BTM_InqDbFirst();
@@ -1003,8 +1278,14 @@ void bta_dm_inq_cmpl(uint8_t num) {
bta_dm_discover_device(
bta_dm_search_cb.p_btm_inq_info->results.remote_bd_addr);
} else {
+ tBTA_DM_MSG* p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
+
+ /* no devices, search complete */
bta_dm_search_cb.services = 0;
- bta_dm_search_cmpl();
+
+ p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
+ p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
+ bta_sys_sendmsg(p_msg);
}
}
@@ -1069,6 +1350,9 @@ void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
uint16_t service = 0xFFFF;
tSDP_PROTOCOL_ELEM pe;
+ Uuid* p_uuid = bta_dm_search_cb.p_srvc_uuid;
+ tBTA_DM_SEARCH result;
+
std::vector<Uuid> uuid_list;
if ((p_data->sdp_event.sdp_result == SDP_SUCCESS) ||
@@ -1078,6 +1362,11 @@ void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
do {
p_sdp_rec = NULL;
if (bta_dm_search_cb.service_index == (BTA_USER_SERVICE_ID + 1)) {
+ if (!bta_dm_search_cb.uuid.IsEmpty()) {
+ p_sdp_rec = SDP_FindServiceUUIDInDb(bta_dm_search_cb.p_sdp_db,
+ bta_dm_search_cb.uuid, p_sdp_rec);
+ }
+
if (p_sdp_rec && SDP_FindProtocolListElemInRec(
p_sdp_rec, UUID_PROTOCOL_RFCOMM, &pe)) {
bta_dm_search_cb.peer_scn = (uint8_t)pe.params[0];
@@ -1092,10 +1381,13 @@ void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
/* finished with BR/EDR services, now we check the result for GATT based
* service UUID */
if (bta_dm_search_cb.service_index == BTA_MAX_SERVICE_ID) {
+ if (bta_dm_search_cb.uuid_to_search != 0 && p_uuid != NULL) {
+ p_uuid +=
+ (bta_dm_search_cb.num_uuid - bta_dm_search_cb.uuid_to_search);
+ /* only support 16 bits UUID for now */
+ service = p_uuid->As16Bit();
+ }
/* all GATT based services */
-
- std::vector<Uuid> gatt_uuids;
-
do {
/* find a service record, report it */
p_sdp_rec =
@@ -1103,23 +1395,19 @@ void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
if (p_sdp_rec) {
Uuid service_uuid;
if (SDP_FindServiceUUIDInRec(p_sdp_rec, &service_uuid)) {
- gatt_uuids.push_back(service_uuid);
+ /* send result back to app now, one by one */
+ result.disc_ble_res.bd_addr = bta_dm_search_cb.peer_bdaddr;
+ strlcpy((char*)result.disc_ble_res.bd_name, bta_dm_get_remname(),
+ BD_NAME_LEN);
+
+ result.disc_ble_res.service = service_uuid;
+ bta_dm_search_cb.p_search_cback(BTA_DM_DISC_BLE_RES_EVT, &result);
}
}
- } while (p_sdp_rec);
-
- if (!gatt_uuids.empty()) {
- LOG_INFO("GATT services discovered using SDP");
- // send all result back to app
- tBTA_DM_SEARCH result;
- result.disc_ble_res.bd_addr = bta_dm_search_cb.peer_bdaddr;
- strlcpy((char*)result.disc_ble_res.bd_name, bta_dm_get_remname(),
- BD_NAME_LEN + 1);
+ if (bta_dm_search_cb.uuid_to_search > 0) break;
- result.disc_ble_res.services = &gatt_uuids;
- bta_dm_search_cb.p_search_cback(BTA_DM_DISC_BLE_RES_EVT, &result);
- }
+ } while (p_sdp_rec);
} else {
/* SDP_DB_FULL means some records with the
required attributes were received */
@@ -1141,7 +1429,13 @@ void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
if (bta_dm_search_cb.services == BTA_ALL_SERVICE_MASK &&
bta_dm_search_cb.services_to_search == 0) {
- bta_dm_search_cb.service_index++;
+ if (bta_dm_search_cb.service_index == BTA_BLE_SERVICE_ID &&
+ bta_dm_search_cb.uuid_to_search > 0)
+ bta_dm_search_cb.uuid_to_search--;
+
+ if (bta_dm_search_cb.uuid_to_search == 0 ||
+ bta_dm_search_cb.service_index != BTA_BLE_SERVICE_ID)
+ bta_dm_search_cb.service_index++;
} else /* regular one service per search or PNP search */
break;
@@ -1169,23 +1463,19 @@ void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
/* if there are more services to search for */
if (bta_dm_search_cb.services_to_search) {
/* Free up the p_sdp_db before checking the next one */
- bta_dm_free_sdp_db();
+ bta_dm_free_sdp_db(NULL);
bta_dm_find_services(bta_dm_search_cb.peer_bdaddr);
} else {
/* callbacks */
/* start next bd_addr if necessary */
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_SecDeleteRmtNameNotifyCallback(
- &bta_dm_service_search_remname_cback);
- } else {
- BTM_SecDeleteRmtNameNotifyCallback(
- &bta_dm_service_search_remname_cback);
- }
+ BTM_SecDeleteRmtNameNotifyCallback(&bta_dm_service_search_remname_cback);
p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
p_msg->hdr.event = BTA_DM_DISCOVERY_RESULT_EVT;
p_msg->disc_result.result.disc_res.result = BTA_SUCCESS;
+ p_msg->disc_result.result.disc_res.p_raw_data = NULL;
+ p_msg->disc_result.result.disc_res.raw_data_size = 0;
p_msg->disc_result.result.disc_res.num_uuids = uuid_list.size();
p_msg->disc_result.result.disc_res.p_uuid_list = NULL;
if (uuid_list.size() > 0) {
@@ -1204,6 +1494,15 @@ void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
__func__, bta_dm_search_cb.p_sdp_db->raw_used,
bta_dm_search_cb.p_sdp_db->raw_data);
+ p_msg->disc_result.result.disc_res.p_raw_data =
+ (uint8_t*)osi_malloc(bta_dm_search_cb.p_sdp_db->raw_used);
+ memcpy(p_msg->disc_result.result.disc_res.p_raw_data,
+ bta_dm_search_cb.p_sdp_db->raw_data,
+ bta_dm_search_cb.p_sdp_db->raw_used);
+
+ p_msg->disc_result.result.disc_res.raw_data_size =
+ bta_dm_search_cb.p_sdp_db->raw_used;
+
bta_dm_search_cb.p_sdp_db->raw_data =
NULL; // no need to free this - it is a global assigned.
bta_dm_search_cb.p_sdp_db->raw_used = 0;
@@ -1213,14 +1512,14 @@ void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
__func__);
}
/* Done with p_sdp_db. Free it */
- bta_dm_free_sdp_db();
+ bta_dm_free_sdp_db(NULL);
p_msg->disc_result.result.disc_res.services =
bta_dm_search_cb.services_found;
// Piggy back the SCN over result field
if (scn_found) {
p_msg->disc_result.result.disc_res.result =
- static_cast<tBTA_STATUS>((3 + bta_dm_search_cb.peer_scn));
+ (3 + bta_dm_search_cb.peer_scn);
p_msg->disc_result.result.disc_res.services |= BTA_USER_SERVICE_MASK;
APPL_TRACE_EVENT(" Piggy back the SCN over result field SCN=%d",
@@ -1228,25 +1527,22 @@ void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
}
p_msg->disc_result.result.disc_res.bd_addr = bta_dm_search_cb.peer_bdaddr;
strlcpy((char*)p_msg->disc_result.result.disc_res.bd_name,
- bta_dm_get_remname(), BD_NAME_LEN + 1);
+ bta_dm_get_remname(), BD_NAME_LEN);
bta_sys_sendmsg(p_msg);
}
} else {
/* conn failed. No need for timer */
- if (p_data->sdp_event.sdp_result == SDP_CONN_FAILED)
+ if (p_data->sdp_event.sdp_result == SDP_CONN_FAILED ||
+ p_data->sdp_event.sdp_result == SDP_CONN_REJECTED ||
+ p_data->sdp_event.sdp_result == SDP_SECURITY_ERR)
bta_dm_search_cb.wait_disc = false;
/* not able to connect go to next device */
if (bta_dm_search_cb.p_sdp_db)
osi_free_and_reset((void**)&bta_dm_search_cb.p_sdp_db);
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_SecDeleteRmtNameNotifyCallback(
- &bta_dm_service_search_remname_cback);
- } else {
- BTM_SecDeleteRmtNameNotifyCallback(&bta_dm_service_search_remname_cback);
- }
+ BTM_SecDeleteRmtNameNotifyCallback(&bta_dm_service_search_remname_cback);
p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
p_msg->hdr.event = BTA_DM_DISCOVERY_RESULT_EVT;
@@ -1255,7 +1551,7 @@ void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
bta_dm_search_cb.services_found;
p_msg->disc_result.result.disc_res.bd_addr = bta_dm_search_cb.peer_bdaddr;
strlcpy((char*)p_msg->disc_result.result.disc_res.bd_name,
- bta_dm_get_remname(), BD_NAME_LEN + 1);
+ bta_dm_get_remname(), BD_NAME_LEN);
bta_sys_sendmsg(p_msg);
}
@@ -1270,50 +1566,15 @@ void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
* Returns void
*
******************************************************************************/
-void bta_dm_search_cmpl() {
- bta_dm_search_set_state(BTA_DM_SEARCH_IDLE);
-
- uint16_t conn_id = bta_dm_search_cb.conn_id;
-
- /* no BLE connection, i.e. Classic service discovery end */
- if (conn_id == GATT_INVALID_CONN_ID) {
- bta_dm_search_cb.p_search_cback(BTA_DM_DISC_CMPL_EVT, nullptr);
- return;
- }
-
- btgatt_db_element_t* db = NULL;
- int count = 0;
- BTA_GATTC_GetGattDb(conn_id, 0x0000, 0xFFFF, &db, &count);
-
- if (count == 0) {
- LOG_INFO("Empty GATT database - no BLE services discovered");
- bta_dm_search_cb.p_search_cback(BTA_DM_DISC_CMPL_EVT, nullptr);
- return;
- }
-
- std::vector<Uuid> gatt_services;
-
- for (int i = 0; i < count; i++) {
- // we process service entries only
- if (db[i].type == BTGATT_DB_PRIMARY_SERVICE) {
- gatt_services.push_back(db[i].uuid);
- }
- }
- osi_free(db);
-
- tBTA_DM_SEARCH result;
- result.disc_ble_res.services = &gatt_services;
- result.disc_ble_res.bd_addr = bta_dm_search_cb.peer_bdaddr;
- strlcpy((char*)result.disc_ble_res.bd_name, (char*)bta_dm_search_cb.peer_name,
- BD_NAME_LEN + 1);
-
- LOG_INFO("GATT services discovered using LE Transport");
- // send all result back to app
- bta_dm_search_cb.p_search_cback(BTA_DM_DISC_BLE_RES_EVT, &result);
+void bta_dm_search_cmpl(tBTA_DM_MSG* p_data) {
+ APPL_TRACE_EVENT("%s", __func__);
- bta_dm_search_cb.p_search_cback(BTA_DM_DISC_CMPL_EVT, nullptr);
+ osi_free_and_reset((void**)&bta_dm_search_cb.p_srvc_uuid);
- bta_dm_execute_queued_request();
+ if (p_data->hdr.layer_specific == BTA_DM_API_DI_DISCOVER_EVT)
+ bta_dm_di_disc_cmpl(p_data);
+ else
+ bta_dm_search_cb.p_search_cback(BTA_DM_DISC_CMPL_EVT, NULL);
}
/*******************************************************************************
@@ -1336,7 +1597,12 @@ void bta_dm_disc_result(tBTA_DM_MSG* p_data) {
bta_dm_search_cb.p_search_cback(BTA_DM_DISC_RES_EVT,
&p_data->disc_result.result);
- bta_dm_search_cmpl();
+ tBTA_DM_MSG* p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
+
+ /* send a message to change state */
+ p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
+ p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
+ bta_sys_sendmsg(p_msg);
}
/*******************************************************************************
@@ -1402,7 +1668,7 @@ static void bta_dm_search_timer_cback(UNUSED_ATTR void* data) {
* Returns void
*
******************************************************************************/
-void bta_dm_free_sdp_db() {
+void bta_dm_free_sdp_db(UNUSED_ATTR tBTA_DM_MSG* p_data) {
osi_free_and_reset((void**)&bta_dm_search_cb.p_sdp_db);
}
@@ -1410,104 +1676,77 @@ void bta_dm_free_sdp_db() {
*
* Function bta_dm_queue_search
*
- * Description Queues search command
+ * Description Queues search command while search is being cancelled
*
* Returns void
*
******************************************************************************/
void bta_dm_queue_search(tBTA_DM_MSG* p_data) {
- osi_free_and_reset((void**)&bta_dm_search_cb.p_pending_search);
- bta_dm_search_cb.p_pending_search =
+ osi_free(bta_dm_search_cb.p_search_queue);
+ bta_dm_search_cb.p_search_queue =
(tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_API_SEARCH));
- memcpy(bta_dm_search_cb.p_pending_search, p_data, sizeof(tBTA_DM_API_SEARCH));
+ memcpy(bta_dm_search_cb.p_search_queue, p_data, sizeof(tBTA_DM_API_SEARCH));
}
/*******************************************************************************
*
* Function bta_dm_queue_disc
*
- * Description Queues discovery command
+ * Description Queues discovery command while search is being cancelled
*
* Returns void
*
******************************************************************************/
void bta_dm_queue_disc(tBTA_DM_MSG* p_data) {
- tBTA_DM_MSG* p_pending_discovery =
+ osi_free(bta_dm_search_cb.p_search_queue);
+ bta_dm_search_cb.p_search_queue =
(tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_API_DISCOVER));
- memcpy(p_pending_discovery, p_data, sizeof(tBTA_DM_API_DISCOVER));
- fixed_queue_enqueue(bta_dm_search_cb.pending_discovery_queue,
- p_pending_discovery);
+ memcpy(bta_dm_search_cb.p_search_queue, p_data, sizeof(tBTA_DM_API_DISCOVER));
}
/*******************************************************************************
*
- * Function bta_dm_execute_queued_request
+ * Function bta_dm_search_clear_queue
*
- * Description Executes queued request if one exists
+ * Description Clears the queue if API search cancel is called
*
* Returns void
*
******************************************************************************/
-void bta_dm_execute_queued_request() {
- if (bta_dm_search_cb.p_pending_search) {
- // Updated queued event to search event to trigger start search
- if (bta_dm_search_cb.p_pending_search->hdr.event ==
- BTA_DM_API_QUEUE_SEARCH_EVT) {
- bta_dm_search_cb.p_pending_search->hdr.event = BTA_DM_API_SEARCH_EVT;
- }
- LOG_INFO("%s Start pending search", __func__);
- bta_sys_sendmsg(bta_dm_search_cb.p_pending_search);
- bta_dm_search_cb.p_pending_search = NULL;
- } else {
- tBTA_DM_MSG* p_pending_discovery = (tBTA_DM_MSG*)fixed_queue_try_dequeue(
- bta_dm_search_cb.pending_discovery_queue);
- if (p_pending_discovery) {
- if (p_pending_discovery->hdr.event == BTA_DM_API_QUEUE_DISCOVER_EVT) {
- p_pending_discovery->hdr.event = BTA_DM_API_DISCOVER_EVT;
- }
- LOG_INFO("%s Start pending discovery", __func__);
- bta_sys_sendmsg(p_pending_discovery);
- }
- }
+void bta_dm_search_clear_queue(UNUSED_ATTR tBTA_DM_MSG* p_data) {
+ osi_free_and_reset((void**)&bta_dm_search_cb.p_search_queue);
}
/*******************************************************************************
*
- * Function bta_dm_is_search_request_queued
- *
- * Description Checks if there is a queued search request
- *
- * Returns bool
- *
- ******************************************************************************/
-bool bta_dm_is_search_request_queued() {
- return bta_dm_search_cb.p_pending_search != NULL;
-}
-
-/*******************************************************************************
- *
- * Function bta_dm_search_clear_queue
+ * Function bta_dm_search_cancel_cmpl
*
- * Description Clears the queue if API search cancel is called
+ * Description Search cancel is complete
*
* Returns void
*
******************************************************************************/
-void bta_dm_search_clear_queue() {
- osi_free_and_reset((void**)&bta_dm_search_cb.p_pending_search);
- fixed_queue_flush(bta_dm_search_cb.pending_discovery_queue, osi_free);
+void bta_dm_search_cancel_cmpl(UNUSED_ATTR tBTA_DM_MSG* p_data) {
+ if (bta_dm_search_cb.p_search_queue) {
+ bta_sys_sendmsg(bta_dm_search_cb.p_search_queue);
+ bta_dm_search_cb.p_search_queue = NULL;
+ }
}
/*******************************************************************************
*
- * Function bta_dm_search_cancel_cmpl
+ * Function bta_dm_search_cancel_transac_cmpl
*
- * Description Search cancel is complete
+ * Description Current Service Discovery or remote name procedure is
+ * completed after search cancellation
*
* Returns void
*
******************************************************************************/
-void bta_dm_search_cancel_cmpl() { bta_dm_execute_queued_request(); }
+void bta_dm_search_cancel_transac_cmpl(UNUSED_ATTR tBTA_DM_MSG* p_data) {
+ osi_free_and_reset((void**)&bta_dm_search_cb.p_sdp_db);
+ bta_dm_search_cancel_notify(NULL);
+}
/*******************************************************************************
*
@@ -1518,7 +1757,7 @@ void bta_dm_search_cancel_cmpl() { bta_dm_execute_queued_request(); }
* Returns void
*
******************************************************************************/
-void bta_dm_search_cancel_notify() {
+void bta_dm_search_cancel_notify(UNUSED_ATTR tBTA_DM_MSG* p_data) {
if (bta_dm_search_cb.p_search_cback) {
bta_dm_search_cb.p_search_cback(BTA_DM_SEARCH_CANCEL_CMPL_EVT, NULL);
}
@@ -1553,7 +1792,7 @@ static void bta_dm_find_services(const RawAddress& bd_addr) {
bta_dm_search_cb.services);
/* try to search all services by search based on L2CAP UUID */
if (bta_dm_search_cb.services == BTA_ALL_SERVICE_MASK) {
- LOG_INFO("%s services_to_search=%08x", __func__,
+ LOG_INFO(LOG_TAG, "%s services_to_search=%08x", __func__,
bta_dm_search_cb.services_to_search);
if (bta_dm_search_cb.services_to_search & BTA_RES_SERVICE_MASK) {
uuid = Uuid::From16Bit(bta_service_id_to_uuid_lkup_tbl[0]);
@@ -1565,11 +1804,25 @@ static void bta_dm_find_services(const RawAddress& bd_addr) {
} else {
/* for LE only profile */
if (bta_dm_search_cb.service_index == BTA_BLE_SERVICE_ID) {
- uuid = Uuid::From16Bit(
- bta_service_id_to_uuid_lkup_tbl[bta_dm_search_cb.service_index]);
+ if (bta_dm_search_cb.uuid_to_search > 0 &&
+ bta_dm_search_cb.p_srvc_uuid) {
+ uuid = *(bta_dm_search_cb.p_srvc_uuid + bta_dm_search_cb.num_uuid -
+ bta_dm_search_cb.uuid_to_search);
+
+ bta_dm_search_cb.uuid_to_search--;
+ } else {
+ uuid = Uuid::From16Bit(
+ bta_service_id_to_uuid_lkup_tbl[bta_dm_search_cb
+ .service_index]);
+ }
+
+ /* last one? clear the BLE service bit if all discovery has been done
+ */
+ if (bta_dm_search_cb.uuid_to_search == 0)
+ bta_dm_search_cb.services_to_search &=
+ (tBTA_SERVICE_MASK)(~(BTA_SERVICE_ID_TO_SERVICE_MASK(
+ bta_dm_search_cb.service_index)));
- bta_dm_search_cb.services_to_search &= (tBTA_SERVICE_MASK)(~(
- BTA_SERVICE_ID_TO_SERVICE_MASK(bta_dm_search_cb.service_index)));
} else {
/* remove the service from services to be searched */
bta_dm_search_cb.services_to_search &= (tBTA_SERVICE_MASK)(~(
@@ -1579,7 +1832,12 @@ static void bta_dm_find_services(const RawAddress& bd_addr) {
}
}
- LOG_INFO("%s search UUID = %s", __func__, uuid.ToString().c_str());
+ if (bta_dm_search_cb.service_index == BTA_USER_SERVICE_ID) {
+ uuid = bta_dm_search_cb.uuid;
+ }
+
+ LOG_INFO(LOG_TAG, "%s search UUID = %s", __func__,
+ uuid.ToString().c_str());
SDP_InitDiscoveryDb(bta_dm_search_cb.p_sdp_db, BTA_DM_SDP_DB_SIZE, 1,
&uuid, 0, NULL);
@@ -1598,7 +1856,10 @@ static void bta_dm_find_services(const RawAddress& bd_addr) {
bta_dm_search_cb.service_index = BTA_MAX_SERVICE_ID;
} else {
- bta_dm_search_cb.service_index++;
+ if ((bta_dm_search_cb.service_index == BTA_BLE_SERVICE_ID &&
+ bta_dm_search_cb.uuid_to_search == 0) ||
+ bta_dm_search_cb.service_index != BTA_BLE_SERVICE_ID)
+ bta_dm_search_cb.service_index++;
return;
}
}
@@ -1609,14 +1870,14 @@ static void bta_dm_find_services(const RawAddress& bd_addr) {
/* no more services to be discovered */
if (bta_dm_search_cb.service_index >= BTA_MAX_SERVICE_ID) {
tBTA_DM_MSG* p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
- /* initialize the data structure */
+ /* initialize the data structure - includes p_raw_data and raw_data_size */
memset(&(p_msg->disc_result.result), 0, sizeof(tBTA_DM_DISC_RES));
p_msg->hdr.event = BTA_DM_DISCOVERY_RESULT_EVT;
p_msg->disc_result.result.disc_res.services =
bta_dm_search_cb.services_found;
p_msg->disc_result.result.disc_res.bd_addr = bta_dm_search_cb.peer_bdaddr;
strlcpy((char*)p_msg->disc_result.result.disc_res.bd_name,
- bta_dm_get_remname(), BD_NAME_LEN + 1);
+ bta_dm_get_remname(), BD_NAME_LEN);
bta_sys_sendmsg(p_msg);
}
@@ -1649,6 +1910,8 @@ static void bta_dm_discover_next_device(void) {
bta_dm_search_cb.services = 0;
p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
+ p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
+
bta_sys_sendmsg(p_msg);
}
}
@@ -1664,7 +1927,7 @@ static void bta_dm_discover_next_device(void) {
******************************************************************************/
static void bta_dm_discover_device(const RawAddress& remote_bd_addr) {
tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
- if (bta_dm_search_cb.transport == BT_TRANSPORT_UNKNOWN) {
+ if (bta_dm_search_cb.transport == BTA_TRANSPORT_UNKNOWN) {
tBT_DEVICE_TYPE dev_type;
tBLE_ADDR_TYPE addr_type;
@@ -1675,6 +1938,9 @@ static void bta_dm_discover_device(const RawAddress& remote_bd_addr) {
transport = bta_dm_search_cb.transport;
}
+ /* Reset transport state for next discovery */
+ bta_dm_search_cb.transport = BTA_TRANSPORT_UNKNOWN;
+
VLOG(1) << __func__ << " BDA: " << remote_bd_addr;
bta_dm_search_cb.peer_bdaddr = remote_bd_addr;
@@ -1703,28 +1969,28 @@ static void bta_dm_discover_device(const RawAddress& remote_bd_addr) {
((bta_dm_search_cb.p_btm_inq_info == NULL) ||
(bta_dm_search_cb.p_btm_inq_info &&
(!bta_dm_search_cb.p_btm_inq_info->appl_knows_rem_name)))) {
- if (bta_dm_read_remote_device_name(bta_dm_search_cb.peer_bdaddr,
- transport)) {
- if (bta_dm_search_cb.state != BTA_DM_DISCOVER_ACTIVE) {
- /* Reset transport state for next discovery */
- bta_dm_search_cb.transport = BT_TRANSPORT_UNKNOWN;
- }
+ if (bta_dm_read_remote_device_name(bta_dm_search_cb.peer_bdaddr, transport))
return;
- }
/* starting name discovery failed */
bta_dm_search_cb.name_discover_done = true;
}
- /* Reset transport state for next discovery */
- bta_dm_search_cb.transport = BT_TRANSPORT_UNKNOWN;
-
/* if application wants to discover service */
if (bta_dm_search_cb.services) {
/* initialize variables */
bta_dm_search_cb.service_index = 0;
bta_dm_search_cb.services_found = 0;
bta_dm_search_cb.services_to_search = bta_dm_search_cb.services;
+ bta_dm_search_cb.uuid_to_search = bta_dm_search_cb.num_uuid;
+ if ((bta_dm_search_cb.p_btm_inq_info != NULL) &&
+ bta_dm_search_cb.services != BTA_USER_SERVICE_MASK &&
+ (!bta_dm_search_cb.sdp_search)) {
+ /* check if EIR provides the information of supported services */
+ bta_dm_eir_search_services(&bta_dm_search_cb.p_btm_inq_info->results,
+ &bta_dm_search_cb.services_to_search,
+ &bta_dm_search_cb.services_found);
+ }
/* if seaching with EIR is not completed */
if (bta_dm_search_cb.services_to_search) {
@@ -1751,6 +2017,11 @@ static void bta_dm_discover_device(const RawAddress& remote_bd_addr) {
if (bta_dm_search_cb.services_to_search & BTA_BLE_SERVICE_MASK) {
// set the raw data buffer here
memset(g_disc_raw_data_buf, 0, sizeof(g_disc_raw_data_buf));
+ bta_dm_search_cb.p_ble_rawdata = g_disc_raw_data_buf;
+
+ bta_dm_search_cb.ble_raw_size = MAX_DISC_RAW_DATA_BUF;
+ bta_dm_search_cb.ble_raw_used = 0;
+
/* start GATT for service discovery */
btm_dm_start_gatt_discovery(bta_dm_search_cb.peer_bdaddr);
return;
@@ -1766,13 +2037,13 @@ static void bta_dm_discover_device(const RawAddress& remote_bd_addr) {
/* name discovery and service discovery are done for this device */
tBTA_DM_MSG* p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
p_msg->hdr.event = BTA_DM_DISCOVERY_RESULT_EVT;
- /* initialize the data structure */
+ /* initialize the data structure - includes p_raw_data and raw_data_size */
memset(&(p_msg->disc_result.result), 0, sizeof(tBTA_DM_DISC_RES));
p_msg->disc_result.result.disc_res.result = BTA_SUCCESS;
p_msg->disc_result.result.disc_res.services = bta_dm_search_cb.services_found;
p_msg->disc_result.result.disc_res.bd_addr = bta_dm_search_cb.peer_bdaddr;
strlcpy((char*)p_msg->disc_result.result.disc_res.bd_name,
- (char*)bta_dm_search_cb.peer_name, BD_NAME_LEN + 1);
+ (char*)bta_dm_search_cb.peer_name, BD_NAME_LEN);
bta_sys_sendmsg(p_msg);
}
@@ -1786,12 +2057,12 @@ static void bta_dm_discover_device(const RawAddress& remote_bd_addr) {
* Returns void
*
******************************************************************************/
-static void bta_dm_sdp_callback(tSDP_STATUS sdp_status) {
+static void bta_dm_sdp_callback(uint16_t sdp_status) {
tBTA_DM_SDP_RESULT* p_msg =
(tBTA_DM_SDP_RESULT*)osi_malloc(sizeof(tBTA_DM_SDP_RESULT));
p_msg->hdr.event = BTA_DM_SDP_RESULT_EVT;
- p_msg->sdp_result = static_cast<uint16_t>(sdp_status);
+ p_msg->sdp_result = sdp_status;
bta_sys_sendmsg(p_msg);
}
@@ -1855,9 +2126,21 @@ static void bta_dm_inq_results_cb(tBTM_INQ_RESULTS* p_inq, uint8_t* p_eir,
*
******************************************************************************/
static void bta_dm_inq_cmpl_cb(void* p_result) {
+ tBTA_DM_MSG* p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
+
APPL_TRACE_DEBUG("%s", __func__);
- bta_dm_inq_cmpl(((tBTM_INQUIRY_CMPL*)p_result)->num_resp);
+ if (!bta_dm_search_cb.cancel_pending) {
+ p_msg->inq_cmpl.hdr.event = BTA_DM_INQUIRY_CMPL_EVT;
+ p_msg->inq_cmpl.num = ((tBTM_INQUIRY_CMPL*)p_result)->num_resp;
+ } else {
+ bta_dm_search_cb.cancel_pending = false;
+ bta_dm_search_cancel_notify(NULL);
+ p_msg->hdr.event = BTA_DM_SEARCH_CMPL_EVT;
+ p_msg->hdr.layer_specific = BTA_DM_API_DISCOVER_EVT;
+ }
+
+ bta_sys_sendmsg(p_msg);
}
/*******************************************************************************
@@ -1879,11 +2162,12 @@ static void bta_dm_service_search_remname_cback(const RawAddress& bd_addr,
/* if this is what we are looking for */
if (bta_dm_search_cb.peer_bdaddr == bd_addr) {
- rem_name.length = strlcpy((char*)rem_name.remote_bd_name, (char*)bd_name,
- BD_NAME_LEN + 1);
- if (rem_name.length > BD_NAME_LEN) {
- rem_name.length = BD_NAME_LEN;
+ rem_name.length = strlen((char*)bd_name);
+ if (rem_name.length > (BD_NAME_LEN - 1)) {
+ rem_name.length = (BD_NAME_LEN - 1);
+ rem_name.remote_bd_name[(BD_NAME_LEN - 1)] = 0;
}
+ strlcpy((char*)rem_name.remote_bd_name, (char*)bd_name, BD_NAME_LEN);
rem_name.status = BTM_SUCCESS;
bta_dm_remname_cback(&rem_name);
@@ -1925,14 +2209,9 @@ static void bta_dm_remname_cback(void* p) {
/* remote name discovery is done but it could be failed */
bta_dm_search_cb.name_discover_done = true;
strlcpy((char*)bta_dm_search_cb.peer_name,
- (char*)p_remote_name->remote_bd_name, BD_NAME_LEN + 1);
+ (char*)p_remote_name->remote_bd_name, BD_NAME_LEN);
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_SecDeleteRmtNameNotifyCallback(
- &bta_dm_service_search_remname_cback);
- } else {
- BTM_SecDeleteRmtNameNotifyCallback(&bta_dm_service_search_remname_cback);
- }
+ BTM_SecDeleteRmtNameNotifyCallback(&bta_dm_service_search_remname_cback);
if (bta_dm_search_cb.transport == BT_TRANSPORT_LE) {
GAP_BleReadPeerPrefConnParams(bta_dm_search_cb.peer_bdaddr);
@@ -1942,7 +2221,7 @@ static void bta_dm_remname_cback(void* p) {
(tBTA_DM_REM_NAME*)osi_malloc(sizeof(tBTA_DM_REM_NAME));
p_msg->result.disc_res.bd_addr = bta_dm_search_cb.peer_bdaddr;
strlcpy((char*)p_msg->result.disc_res.bd_name,
- (char*)p_remote_name->remote_bd_name, BD_NAME_LEN + 1);
+ (char*)p_remote_name->remote_bd_name, BD_NAME_LEN);
p_msg->hdr.event = BTA_DM_REMT_NAME_EVT;
bta_sys_sendmsg(p_msg);
@@ -1950,6 +2229,55 @@ static void bta_dm_remname_cback(void* p) {
/*******************************************************************************
*
+ * Function bta_dm_authorize_cback
+ *
+ * Description cback requesting authorization
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static uint8_t bta_dm_authorize_cback(const RawAddress& bd_addr,
+ DEV_CLASS dev_class, BD_NAME bd_name,
+ UNUSED_ATTR uint8_t* service_name,
+ uint8_t service_id,
+ UNUSED_ATTR bool is_originator) {
+ tBTA_DM_SEC sec_event;
+ uint8_t index = 1;
+
+ sec_event.authorize.bd_addr = bd_addr;
+ memcpy(sec_event.authorize.dev_class, dev_class, DEV_CLASS_LEN);
+ strlcpy((char*)sec_event.authorize.bd_name, (char*)bd_name, BD_NAME_LEN);
+
+#if (BTA_JV_INCLUDED == TRUE)
+ sec_event.authorize.service = service_id;
+#endif
+
+ while (index < BTA_MAX_SERVICE_ID) {
+ /* get the BTA service id corresponding to BTM id */
+ if (bta_service_id_to_btm_srv_id_lkup_tbl[index] == service_id) {
+ sec_event.authorize.service = index;
+ break;
+ }
+ index++;
+ }
+
+ /* if supported service callback otherwise not authorized */
+ if (bta_dm_cb.p_sec_cback && (index < BTA_MAX_SERVICE_ID
+#if (BTA_JV_INCLUDED == TRUE)
+ /* pass through JV service ID */
+ || (service_id >= BTA_FIRST_JV_SERVICE_ID &&
+ service_id <= BTA_LAST_JV_SERVICE_ID)
+#endif
+ )) {
+ bta_dm_cb.p_sec_cback(BTA_DM_AUTHORIZE_EVT, &sec_event);
+ return BTM_CMD_STARTED;
+ } else {
+ return BTM_NOT_AUTHORIZED;
+ }
+}
+
+/*******************************************************************************
+ *
* Function bta_dm_pinname_cback
*
* Description Callback requesting pin_key
@@ -1969,11 +2297,12 @@ static void bta_dm_pinname_cback(void* p_data) {
BTA_COPY_DEVICE_CLASS(sec_event.cfm_req.dev_class, bta_dm_cb.pin_dev_class);
if (p_result && p_result->status == BTM_SUCCESS) {
- bytes_to_copy =
- (p_result->length < BD_NAME_LEN) ? p_result->length : BD_NAME_LEN;
+ bytes_to_copy = (p_result->length < (BD_NAME_LEN - 1))
+ ? p_result->length
+ : (BD_NAME_LEN - 1);
memcpy(sec_event.cfm_req.bd_name, p_result->remote_bd_name,
bytes_to_copy);
- sec_event.pin_req.bd_name[BD_NAME_LEN] = 0;
+ sec_event.pin_req.bd_name[BD_NAME_LEN - 1] = 0;
} else /* No name found */
sec_event.cfm_req.bd_name[0] = 0;
@@ -1994,11 +2323,12 @@ static void bta_dm_pinname_cback(void* p_data) {
BTA_COPY_DEVICE_CLASS(sec_event.pin_req.dev_class, bta_dm_cb.pin_dev_class);
if (p_result && p_result->status == BTM_SUCCESS) {
- bytes_to_copy = (p_result->length < BD_NAME_LEN) ? p_result->length
- : (BD_NAME_LEN - 1);
+ bytes_to_copy = (p_result->length < (BD_NAME_LEN - 1))
+ ? p_result->length
+ : (BD_NAME_LEN - 1);
memcpy(sec_event.pin_req.bd_name, p_result->remote_bd_name,
bytes_to_copy);
- sec_event.pin_req.bd_name[BD_NAME_LEN] = 0;
+ sec_event.pin_req.bd_name[BD_NAME_LEN - 1] = 0;
} else /* No name found */
sec_event.pin_req.bd_name[0] = 0;
@@ -2041,7 +2371,7 @@ static uint8_t bta_dm_pin_cback(const RawAddress& bd_addr, DEV_CLASS dev_class,
sec_event.pin_req.bd_addr = bd_addr;
BTA_COPY_DEVICE_CLASS(sec_event.pin_req.dev_class, dev_class);
- strlcpy((char*)sec_event.pin_req.bd_name, (char*)bd_name, BD_NAME_LEN + 1);
+ strlcpy((char*)sec_event.pin_req.bd_name, (char*)bd_name, BD_NAME_LEN);
sec_event.pin_req.min_16_digit = min_16_digit;
bta_dm_cb.p_sec_cback(BTA_DM_PIN_REQ_EVT, &sec_event);
@@ -2067,30 +2397,35 @@ static uint8_t bta_dm_new_link_key_cback(const RawAddress& bd_addr,
memset(&sec_event, 0, sizeof(tBTA_DM_SEC));
- event = BTA_DM_AUTH_CMPL_EVT;
- p_auth_cmpl = &sec_event.auth_cmpl;
-
- p_auth_cmpl->bd_addr = bd_addr;
-
- memcpy(p_auth_cmpl->bd_name, bd_name, BD_NAME_LEN);
- p_auth_cmpl->bd_name[BD_NAME_LEN] = 0;
- p_auth_cmpl->key_present = true;
- p_auth_cmpl->key_type = key_type;
- p_auth_cmpl->success = true;
- p_auth_cmpl->key = key;
- sec_event.auth_cmpl.fail_reason = HCI_SUCCESS;
-
- // Report the BR link key based on the BR/EDR address and type
- BTM_ReadDevInfo(bd_addr, &sec_event.auth_cmpl.dev_type,
- &sec_event.auth_cmpl.addr_type);
- if (bta_dm_cb.p_sec_cback) bta_dm_cb.p_sec_cback(event, &sec_event);
-
- // Setting remove_dev_pending flag to false, where it will avoid deleting
- // the
- // security device record when the ACL connection link goes down in case of
- // reconnection.
- if (bta_dm_cb.device_list.count)
- bta_dm_reset_sec_dev_pending(p_auth_cmpl->bd_addr);
+ /* Not AMP Key type */
+ if (key_type != HCI_LKEY_TYPE_AMP_WIFI && key_type != HCI_LKEY_TYPE_AMP_UWB) {
+ event = BTA_DM_AUTH_CMPL_EVT;
+ p_auth_cmpl = &sec_event.auth_cmpl;
+
+ p_auth_cmpl->bd_addr = bd_addr;
+
+ memcpy(p_auth_cmpl->bd_name, bd_name, (BD_NAME_LEN - 1));
+ p_auth_cmpl->bd_name[BD_NAME_LEN - 1] = 0;
+ p_auth_cmpl->key_present = true;
+ p_auth_cmpl->key_type = key_type;
+ p_auth_cmpl->success = true;
+ p_auth_cmpl->key = key;
+ sec_event.auth_cmpl.fail_reason = HCI_SUCCESS;
+
+ // Report the BR link key based on the BR/EDR address and type
+ BTM_ReadDevInfo(bd_addr, &sec_event.auth_cmpl.dev_type,
+ &sec_event.auth_cmpl.addr_type);
+ if (bta_dm_cb.p_sec_cback) bta_dm_cb.p_sec_cback(event, &sec_event);
+
+ // Setting remove_dev_pending flag to false, where it will avoid deleting
+ // the
+ // security device record when the ACL connection link goes down in case of
+ // reconnection.
+ if (bta_dm_cb.device_list.count)
+ bta_dm_reset_sec_dev_pending(p_auth_cmpl->bd_addr);
+ } else {
+ APPL_TRACE_WARNING("%s() Received AMP Key", __func__);
+ }
return BTM_CMD_STARTED;
}
@@ -2104,44 +2439,36 @@ static uint8_t bta_dm_new_link_key_cback(const RawAddress& bd_addr,
* Returns void
*
******************************************************************************/
-static void bta_dm_authentication_complete_cback(
+static uint8_t bta_dm_authentication_complete_cback(
const RawAddress& bd_addr, UNUSED_ATTR DEV_CLASS dev_class, BD_NAME bd_name,
- tHCI_REASON reason) {
- if (reason != HCI_SUCCESS) {
- if (bta_dm_cb.p_sec_cback) {
- // Build out the security event data structure
- tBTA_DM_SEC sec_event = {
- .auth_cmpl =
- {
- .bd_addr = bd_addr,
- },
- };
- memcpy(sec_event.auth_cmpl.bd_name, bd_name, BD_NAME_LEN);
- sec_event.auth_cmpl.bd_name[BD_NAME_LEN] = 0;
-
- // Report the BR link key based on the BR/EDR address and type
- BTM_ReadDevInfo(bd_addr, &sec_event.auth_cmpl.dev_type,
- &sec_event.auth_cmpl.addr_type);
- sec_event.auth_cmpl.fail_reason = reason;
+ int result) {
+ tBTA_DM_SEC sec_event;
- bta_dm_cb.p_sec_cback(BTA_DM_AUTH_CMPL_EVT, &sec_event);
- }
+ if (result != BTM_SUCCESS) {
+ memset(&sec_event, 0, sizeof(tBTA_DM_SEC));
+ sec_event.auth_cmpl.bd_addr = bd_addr;
- switch (reason) {
- case HCI_ERR_AUTH_FAILURE:
- case HCI_ERR_KEY_MISSING:
- case HCI_ERR_HOST_REJECT_SECURITY:
- case HCI_ERR_ENCRY_MODE_NOT_ACCEPTABLE:
- LOG_WARN(
- "Deleting device record as authentication failed entry:%s "
- "reason:%s",
- PRIVATE_ADDRESS(bd_addr), hci_reason_code_text(reason).c_str());
- break;
+ memcpy(sec_event.auth_cmpl.bd_name, bd_name, (BD_NAME_LEN - 1));
+ sec_event.auth_cmpl.bd_name[BD_NAME_LEN - 1] = 0;
- default:
- break;
+ // Report the BR link key based on the BR/EDR address and type
+ BTM_ReadDevInfo(bd_addr, &sec_event.auth_cmpl.dev_type,
+ &sec_event.auth_cmpl.addr_type);
+ sec_event.auth_cmpl.fail_reason = (uint8_t)result;
+
+ if (bta_dm_cb.p_sec_cback)
+ bta_dm_cb.p_sec_cback(BTA_DM_AUTH_CMPL_EVT, &sec_event);
+
+ if (result == HCI_ERR_AUTH_FAILURE || result == HCI_ERR_KEY_MISSING ||
+ result == HCI_ERR_HOST_REJECT_SECURITY ||
+ result == HCI_ERR_ENCRY_MODE_NOT_ACCEPTABLE) {
+ APPL_TRACE_WARNING("%s deleting %s - result: 0x%02x", __func__,
+ bd_addr.ToString().c_str(), result);
+ bta_dm_remove_sec_dev_entry(bd_addr);
}
}
+
+ return BTM_SUCCESS;
}
/*******************************************************************************
@@ -2153,8 +2480,7 @@ static void bta_dm_authentication_complete_cback(
* Returns void
*
******************************************************************************/
-static tBTM_STATUS bta_dm_sp_cback(tBTM_SP_EVT event,
- tBTM_SP_EVT_DATA* p_data) {
+static uint8_t bta_dm_sp_cback(tBTM_SP_EVT event, tBTM_SP_EVT_DATA* p_data) {
tBTM_STATUS status = BTM_CMD_STARTED;
tBTA_DM_SEC sec_event;
tBTA_DM_SEC_EVT pin_evt = BTA_DM_SP_KEY_NOTIF_EVT;
@@ -2162,22 +2488,22 @@ static tBTM_STATUS bta_dm_sp_cback(tBTM_SP_EVT event,
APPL_TRACE_EVENT("bta_dm_sp_cback: %d", event);
if (!bta_dm_cb.p_sec_cback) return BTM_NOT_AUTHORIZED;
- bool sp_rmt_result = false;
/* TODO_SP */
switch (event) {
case BTM_SP_IO_REQ_EVT:
if (btm_local_io_caps != BTM_IO_CAP_NONE) {
/* translate auth_req */
- btif_dm_set_oob_for_io_req(&p_data->io_req.oob_data);
- btif_dm_proc_io_req(&p_data->io_req.auth_req, p_data->io_req.is_orig);
+ bta_dm_co_io_req(p_data->io_req.bd_addr, &p_data->io_req.io_cap,
+ &p_data->io_req.oob_data, &p_data->io_req.auth_req,
+ p_data->io_req.is_orig);
}
APPL_TRACE_EVENT("io mitm: %d oob_data:%d", p_data->io_req.auth_req,
p_data->io_req.oob_data);
break;
case BTM_SP_IO_RSP_EVT:
if (btm_local_io_caps != BTM_IO_CAP_NONE) {
- btif_dm_proc_io_rsp(p_data->io_rsp.bd_addr, p_data->io_rsp.io_cap,
- p_data->io_rsp.oob_data, p_data->io_rsp.auth_req);
+ bta_dm_co_io_rsp(p_data->io_rsp.bd_addr, p_data->io_rsp.io_cap,
+ p_data->io_rsp.oob_data, p_data->io_rsp.auth_req);
}
break;
@@ -2231,7 +2557,7 @@ static tBTM_STATUS bta_dm_sp_cback(tBTM_SP_EVT event,
BTA_COPY_DEVICE_CLASS(sec_event.key_notif.dev_class,
p_data->cfm_req.dev_class);
strlcpy((char*)sec_event.key_notif.bd_name,
- (char*)p_data->cfm_req.bd_name, BD_NAME_LEN + 1);
+ (char*)p_data->cfm_req.bd_name, BD_NAME_LEN);
}
}
@@ -2254,8 +2580,8 @@ static tBTM_STATUS bta_dm_sp_cback(tBTM_SP_EVT event,
BTA_COPY_DEVICE_CLASS(sec_event.key_notif.dev_class,
p_data->key_notif.dev_class);
strlcpy((char*)sec_event.key_notif.bd_name,
- (char*)p_data->key_notif.bd_name, BD_NAME_LEN + 1);
- sec_event.key_notif.bd_name[BD_NAME_LEN] = 0;
+ (char*)p_data->key_notif.bd_name, BD_NAME_LEN);
+ sec_event.key_notif.bd_name[BD_NAME_LEN - 1] = 0;
}
}
@@ -2264,24 +2590,51 @@ static tBTM_STATUS bta_dm_sp_cback(tBTM_SP_EVT event,
break;
case BTM_SP_LOC_OOB_EVT:
-#ifdef BTIF_DM_OOB_TEST
- btif_dm_proc_loc_oob(BT_TRANSPORT_BR_EDR,
- (bool)(p_data->loc_oob.status == BTM_SUCCESS),
- p_data->loc_oob.c, p_data->loc_oob.r);
-#endif
+ bta_dm_co_loc_oob((bool)(p_data->loc_oob.status == BTM_SUCCESS),
+ p_data->loc_oob.c, p_data->loc_oob.r);
break;
- case BTM_SP_RMT_OOB_EVT: {
- Octet16 c;
- Octet16 r;
- sp_rmt_result = false;
-#ifdef BTIF_DM_OOB_TEST
- sp_rmt_result = btif_dm_proc_rmt_oob(p_data->rmt_oob.bd_addr, &c, &r);
-#endif
- BTIF_TRACE_DEBUG("bta_dm_ci_rmt_oob: result=%d", sp_rmt_result);
- bta_dm_ci_rmt_oob(sp_rmt_result, p_data->rmt_oob.bd_addr, c, r);
+ case BTM_SP_RMT_OOB_EVT:
+ /* If the device name is not known, save bdaddr and devclass and initiate
+ * a name request */
+ if (p_data->rmt_oob.bd_name[0] == 0) {
+ bta_dm_cb.pin_evt = BTA_DM_SP_RMT_OOB_EVT;
+ bta_dm_cb.pin_bd_addr = p_data->rmt_oob.bd_addr;
+ BTA_COPY_DEVICE_CLASS(bta_dm_cb.pin_dev_class,
+ p_data->rmt_oob.dev_class);
+ if ((BTM_ReadRemoteDeviceName(p_data->rmt_oob.bd_addr,
+ bta_dm_pinname_cback,
+ BT_TRANSPORT_BR_EDR)) == BTM_CMD_STARTED)
+ return BTM_CMD_STARTED;
+ APPL_TRACE_WARNING(
+ " bta_dm_sp_cback() -> Failed to start Remote Name Request ");
+ }
+
+ sec_event.rmt_oob.bd_addr = p_data->rmt_oob.bd_addr;
+ BTA_COPY_DEVICE_CLASS(sec_event.rmt_oob.dev_class,
+ p_data->rmt_oob.dev_class);
+ strlcpy((char*)sec_event.rmt_oob.bd_name, (char*)p_data->rmt_oob.bd_name,
+ BD_NAME_LEN);
+
+ bta_dm_cb.p_sec_cback(BTA_DM_SP_RMT_OOB_EVT, &sec_event);
+
+ bta_dm_co_rmt_oob(p_data->rmt_oob.bd_addr);
+ break;
+
+ case BTM_SP_COMPLT_EVT:
+ /* do not report this event - handled by link_key_callback or
+ * auth_complete_callback */
+ break;
+
+ case BTM_SP_KEYPRESS_EVT:
+ memcpy(&sec_event.key_press, &p_data->key_press,
+ sizeof(tBTM_SP_KEYPRESS));
+ bta_dm_cb.p_sec_cback(BTA_DM_SP_KEYPRESS_EVT, &sec_event);
+ break;
+
+ case BTM_SP_UPGRADE_EVT:
+ bta_dm_co_lk_upgrade(p_data->upgrade.bd_addr, &p_data->upgrade.upgrade);
break;
- }
default:
status = BTM_NOT_AUTHORIZED;
@@ -2302,229 +2655,258 @@ static tBTM_STATUS bta_dm_sp_cback(tBTM_SP_EVT event,
*
******************************************************************************/
static void bta_dm_local_name_cback(UNUSED_ATTR void* p_name) {
- BTIF_dm_enable();
+ tBTA_DM_SEC sec_event;
+
+ sec_event.enable.status = BTA_SUCCESS;
+
+ if (bta_dm_cb.p_sec_cback)
+ bta_dm_cb.p_sec_cback(BTA_DM_ENABLE_EVT, &sec_event);
}
-static void handle_role_change(const RawAddress& bd_addr, tHCI_ROLE new_role,
- tHCI_STATUS hci_status) {
- tBTA_DM_PEER_DEVICE* p_dev = bta_dm_find_peer_device(bd_addr);
- if (!p_dev) {
- LOG_WARN(
- "Unable to find device for role change peer:%s new_role:%s "
- "hci_status:%s",
- PRIVATE_ADDRESS(bd_addr), RoleText(new_role).c_str(),
- hci_error_code_text(hci_status).c_str());
- return;
- }
+static void send_busy_level_update(uint8_t busy_level,
+ uint8_t busy_level_flags) {
+ if (!bta_dm_cb.p_sec_cback) return;
+
+ tBTA_DM_SEC conn;
+ memset(&conn, 0, sizeof(tBTA_DM_SEC));
+ conn.busy_level.level = busy_level;
+ conn.busy_level.level_flags = busy_level_flags;
+ bta_dm_cb.p_sec_cback(BTA_DM_BUSY_LEVEL_EVT, &conn);
+}
- LOG_INFO(
- "Role change callback peer:%s info:0x%x new_role:%s dev count:%d "
- "hci_status:%s",
- PRIVATE_ADDRESS(bd_addr), p_dev->Info(), RoleText(new_role).c_str(),
- bta_dm_cb.device_list.count, hci_error_code_text(hci_status).c_str());
+static void handle_role_change(const RawAddress& bd_addr, uint8_t new_role,
+ uint8_t hci_status) {
+ tBTA_DM_SEC conn;
+ memset(&conn, 0, sizeof(tBTA_DM_SEC));
- if (p_dev->Info() & BTA_DM_DI_AV_ACTIVE) {
+ tBTA_DM_PEER_DEVICE* p_dev = bta_dm_find_peer_device(bd_addr);
+ if (!p_dev) return;
+ LOG_INFO(LOG_TAG,
+ "%s: peer %s info:0x%x new_role:0x%x dev count:%d hci_status=%d",
+ __func__, bd_addr.ToString().c_str(), p_dev->info, new_role,
+ bta_dm_cb.device_list.count, hci_status);
+ if (p_dev->info & BTA_DM_DI_AV_ACTIVE) {
bool need_policy_change = false;
/* there's AV activity on this link */
- if (new_role == HCI_ROLE_PERIPHERAL && bta_dm_cb.device_list.count > 1 &&
+ if (new_role == HCI_ROLE_SLAVE && bta_dm_cb.device_list.count > 1 &&
hci_status == HCI_SUCCESS) {
/* more than one connections and the AV connection is role switched
- * to peripheral
- * switch it back to central and remove the switch policy */
- BTM_SwitchRoleToCentral(bd_addr);
+ * to slave
+ * switch it back to master and remove the switch policy */
+ BTM_SwitchRole(bd_addr, BTM_ROLE_MASTER, NULL);
need_policy_change = true;
- } else if (p_bta_dm_cfg->avoid_scatter && (new_role == HCI_ROLE_CENTRAL)) {
- /* if the link updated to be central include AV activities, remove
+ } else if (p_bta_dm_cfg->avoid_scatter && (new_role == HCI_ROLE_MASTER)) {
+ /* if the link updated to be master include AV activities, remove
* the switch policy */
need_policy_change = true;
}
if (need_policy_change) {
- BTM_block_role_switch_for(p_dev->peer_bdaddr);
+ bta_dm_policy_cback(BTA_SYS_PLCY_CLR, 0, HCI_ENABLE_MASTER_SLAVE_SWITCH,
+ p_dev->peer_bdaddr);
}
} else {
/* there's AV no activity on this link and role switch happened
* check if AV is active
- * if so, make sure the AV link is central */
- bta_dm_check_av();
+ * if so, make sure the AV link is master */
+ bta_dm_check_av(0);
}
bta_sys_notify_role_chg(bd_addr, new_role, hci_status);
+ conn.role_chg.bd_addr = bd_addr;
+ conn.role_chg.new_role = (uint8_t)new_role;
+ if (bta_dm_cb.p_sec_cback) bta_dm_cb.p_sec_cback(BTA_DM_ROLE_CHG_EVT, &conn);
}
-void BTA_dm_report_role_change(const RawAddress bd_addr, tHCI_ROLE new_role,
- tHCI_STATUS hci_status) {
- do_in_main_thread(
- FROM_HERE, base::Bind(handle_role_change, bd_addr, new_role, hci_status));
-}
-
-void handle_remote_features_complete(const RawAddress& bd_addr) {
- tBTA_DM_PEER_DEVICE* p_dev = bta_dm_find_peer_device(bd_addr);
- if (!p_dev) {
- LOG_WARN("Unable to find device peer:%s", PRIVATE_ADDRESS(bd_addr));
- return;
- }
-
- if (controller_get_interface()->supports_sniff_subrating() &&
- acl_peer_supports_sniff_subrating(bd_addr)) {
- LOG_DEBUG("Device supports sniff subrating peer:%s",
- PRIVATE_ADDRESS(bd_addr));
- p_dev->info = BTA_DM_DI_USE_SSR;
- } else {
- LOG_DEBUG("Device does NOT support sniff subrating peer:%s",
- PRIVATE_ADDRESS(bd_addr));
- }
-}
+static void bta_dm_acl_change(bool is_new, const RawAddress& bd_addr,
+ tBT_TRANSPORT transport, uint16_t handle) {
+ bool issue_unpair_cb = false;
-void BTA_dm_notify_remote_features_complete(const RawAddress bd_addr) {
- do_in_main_thread(FROM_HERE,
- base::Bind(handle_remote_features_complete, bd_addr));
-}
+ tBTA_DM_SEC conn;
+ memset(&conn, 0, sizeof(tBTA_DM_SEC));
-static tBTA_DM_PEER_DEVICE* allocate_device_for(const RawAddress& bd_addr,
- tBT_TRANSPORT transport) {
- for (uint8_t i = 0; i < bta_dm_cb.device_list.count; i++) {
- auto device = &bta_dm_cb.device_list.peer_device[i];
- if (device->peer_bdaddr == bd_addr && device->transport == transport) {
- return device;
+ if (is_new) {
+ uint8_t i;
+ for (i = 0; i < bta_dm_cb.device_list.count; i++) {
+ if (bta_dm_cb.device_list.peer_device[i].peer_bdaddr == bd_addr &&
+ bta_dm_cb.device_list.peer_device[i].conn_handle == handle)
+ break;
}
- }
- if (bta_dm_cb.device_list.count < BTA_DM_NUM_PEER_DEVICE) {
- auto device =
- &bta_dm_cb.device_list.peer_device[bta_dm_cb.device_list.count];
- device->peer_bdaddr = bd_addr;
- bta_dm_cb.device_list.count++;
- if (transport == BT_TRANSPORT_LE) {
- bta_dm_cb.device_list.le_count++;
+ if (i == bta_dm_cb.device_list.count) {
+ if (bta_dm_cb.device_list.count < BTA_DM_NUM_PEER_DEVICE) {
+ bta_dm_cb.device_list.peer_device[bta_dm_cb.device_list.count]
+ .peer_bdaddr = bd_addr;
+ bta_dm_cb.device_list.peer_device[bta_dm_cb.device_list.count]
+ .link_policy = bta_dm_cb.cur_policy;
+ bta_dm_cb.device_list.count++;
+ bta_dm_cb.device_list.peer_device[i].conn_handle = handle;
+ if (transport == BT_TRANSPORT_LE) bta_dm_cb.device_list.le_count++;
+ } else {
+ APPL_TRACE_ERROR("%s max active connection reached, no resources",
+ __func__);
+ return;
+ }
}
- return device;
- }
- return nullptr;
-}
-void bta_dm_acl_up(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- auto device = allocate_device_for(bd_addr, transport);
- if (device == nullptr) {
- LOG_WARN("Unable to allocate device resources for new connection");
- return;
- }
- device->conn_state = BTA_DM_CONNECTED;
- device->pref_role = BTA_ANY_ROLE;
- device->info = BTA_DM_DI_NONE;
- device->transport = transport;
+ bta_dm_cb.device_list.peer_device[i].conn_state = BTA_DM_CONNECTED;
+ bta_dm_cb.device_list.peer_device[i].pref_role = BTA_ANY_ROLE;
+ conn.link_up.bd_addr = bd_addr;
+ bta_dm_cb.device_list.peer_device[i].info = BTA_DM_DI_NONE;
+ conn.link_up.link_type = transport;
+ bta_dm_cb.device_list.peer_device[i].transport = transport;
+
+ uint8_t* p;
+ if (((NULL != (p = BTM_ReadLocalFeatures())) &&
+ HCI_SNIFF_SUB_RATE_SUPPORTED(p)) &&
+ ((NULL != (p = BTM_ReadRemoteFeatures(bd_addr))) &&
+ HCI_SNIFF_SUB_RATE_SUPPORTED(p))) {
+ /* both local and remote devices support SSR */
+ bta_dm_cb.device_list.peer_device[i].info = BTA_DM_DI_USE_SSR;
+ }
+ APPL_TRACE_WARNING("%s info: 0x%x", __func__,
+ bta_dm_cb.device_list.peer_device[i].info);
- if (controller_get_interface()->supports_sniff_subrating() &&
- acl_peer_supports_sniff_subrating(bd_addr)) {
- // NOTE: This callback assumes upon ACL connection that
- // the read remote features has completed and is valid.
- // The only guaranteed contract for valid read remote features
- // data is when the BTA_dm_notify_remote_features_complete()
- // callback has completed. The below assignment is kept for
- // transitional informational purposes only.
- device->info = BTA_DM_DI_USE_SSR;
- }
+ if (bta_dm_cb.p_sec_cback) bta_dm_cb.p_sec_cback(BTA_DM_LINK_UP_EVT, &conn);
+ } else {
+ for (uint8_t i = 0; i < bta_dm_cb.device_list.count; i++) {
+ if (bta_dm_cb.device_list.peer_device[i].peer_bdaddr != bd_addr ||
+ bta_dm_cb.device_list.peer_device[i].transport != transport)
+ continue;
- if (bta_dm_cb.p_sec_cback) {
- tBTA_DM_SEC conn;
- memset(&conn, 0, sizeof(tBTA_DM_SEC));
- conn.link_up.bd_addr = bd_addr;
+ if (bta_dm_cb.device_list.peer_device[i].conn_state == BTA_DM_UNPAIRING) {
+ if (BTM_SecDeleteDevice(
+ bta_dm_cb.device_list.peer_device[i].peer_bdaddr))
+ issue_unpair_cb = true;
- bta_dm_cb.p_sec_cback(BTA_DM_LINK_UP_EVT, &conn);
- LOG_DEBUG("Executed security callback for new connection available");
- }
- bta_dm_adjust_roles(true);
-}
+ /* remove all cached GATT information */
+ BTA_GATTC_Refresh(bd_addr);
-void BTA_dm_acl_up(const RawAddress bd_addr, tBT_TRANSPORT transport) {
- do_in_main_thread(FROM_HERE, base::Bind(bta_dm_acl_up, bd_addr, transport));
-}
+ APPL_TRACE_DEBUG("%s: Unpairing: issue unpair CB = %d ", __func__,
+ issue_unpair_cb);
+ }
-static void bta_dm_acl_down(const RawAddress& bd_addr,
- tBT_TRANSPORT transport) {
- bool issue_unpair_cb = false;
- bool remove_device = false;
+ conn.link_down.is_removed =
+ bta_dm_cb.device_list.peer_device[i].remove_dev_pending;
- for (uint8_t i = 0; i < bta_dm_cb.device_list.count; i++) {
- auto device = &bta_dm_cb.device_list.peer_device[i];
- if (device->peer_bdaddr != bd_addr || device->transport != transport)
- continue;
+ // Iterate to the one before the last when shrinking the list,
+ // otherwise we memcpy garbage data into the record.
+ // Then clear out the last item in the list since we are shrinking.
+ for (; i < bta_dm_cb.device_list.count - 1; i++) {
+ memcpy(&bta_dm_cb.device_list.peer_device[i],
+ &bta_dm_cb.device_list.peer_device[i + 1],
+ sizeof(bta_dm_cb.device_list.peer_device[i]));
+ }
+ if (bta_dm_cb.device_list.count > 0) {
+ int clear_index = bta_dm_cb.device_list.count - 1;
+ memset(&bta_dm_cb.device_list.peer_device[clear_index], 0,
+ sizeof(bta_dm_cb.device_list.peer_device[clear_index]));
+ }
+ break;
+ }
+ if (bta_dm_cb.device_list.count) bta_dm_cb.device_list.count--;
+ if ((transport == BT_TRANSPORT_LE) && (bta_dm_cb.device_list.le_count))
+ bta_dm_cb.device_list.le_count--;
+ conn.link_down.link_type = transport;
+
+ if ((transport == BT_TRANSPORT_BR_EDR) &&
+ (bta_dm_search_cb.wait_disc &&
+ bta_dm_search_cb.peer_bdaddr == bd_addr)) {
+ bta_dm_search_cb.wait_disc = false;
- if (device->conn_state == BTA_DM_UNPAIRING) {
- issue_unpair_cb =
- (bluetooth::shim::is_gd_security_enabled())
- ? bluetooth::shim::BTM_SecDeleteDevice(device->peer_bdaddr)
- : BTM_SecDeleteDevice(device->peer_bdaddr);
+ if (bta_dm_search_cb.sdp_results) {
+ APPL_TRACE_EVENT(" timer stopped ");
+ alarm_cancel(bta_dm_search_cb.search_timer);
+ bta_dm_discover_next_device();
+ }
+ }
+ if (bta_dm_cb.disabling) {
+ if (!BTM_GetNumAclLinks()) {
+ /*
+ * Start a timer to make sure that the profiles
+ * get the disconnect event.
+ */
+ alarm_set_on_mloop(bta_dm_cb.disable_timer,
+ BTA_DM_DISABLE_CONN_DOWN_TIMER_MS,
+ bta_dm_disable_conn_down_timer_cback, NULL);
+ }
+ }
+ if (conn.link_down.is_removed) {
+ BTM_SecDeleteDevice(bd_addr);
+ /* need to remove all pending background connection */
+ BTA_GATTC_CancelOpen(0, bd_addr, false);
/* remove all cached GATT information */
BTA_GATTC_Refresh(bd_addr);
-
- APPL_TRACE_DEBUG("%s: Unpairing: issue unpair CB = %d ", __func__,
- issue_unpair_cb);
}
- remove_device = device->remove_dev_pending;
-
- // Iterate to the one before the last when shrinking the list,
- // otherwise we memcpy garbage data into the record.
- // Then clear out the last item in the list since we are shrinking.
- for (; i < bta_dm_cb.device_list.count - 1; i++) {
- memcpy(&bta_dm_cb.device_list.peer_device[i],
- &bta_dm_cb.device_list.peer_device[i + 1],
- sizeof(bta_dm_cb.device_list.peer_device[i]));
- }
- if (bta_dm_cb.device_list.count > 0) {
- int clear_index = bta_dm_cb.device_list.count - 1;
- memset(&bta_dm_cb.device_list.peer_device[clear_index], 0,
- sizeof(bta_dm_cb.device_list.peer_device[clear_index]));
+ conn.link_down.bd_addr = bd_addr;
+ conn.link_down.status = (uint8_t)btm_get_acl_disc_reason_code();
+ if (bta_dm_cb.p_sec_cback) {
+ bta_dm_cb.p_sec_cback(BTA_DM_LINK_DOWN_EVT, &conn);
+ if (issue_unpair_cb)
+ bta_dm_cb.p_sec_cback(BTA_DM_DEV_UNPAIRED_EVT, &conn);
}
- break;
- }
- if (bta_dm_cb.device_list.count) bta_dm_cb.device_list.count--;
- if ((transport == BT_TRANSPORT_LE) && (bta_dm_cb.device_list.le_count)) {
- bta_dm_cb.device_list.le_count--;
}
- if ((transport == BT_TRANSPORT_BR_EDR) &&
- (bta_dm_search_cb.wait_disc && bta_dm_search_cb.peer_bdaddr == bd_addr)) {
- bta_dm_search_cb.wait_disc = false;
+ bta_dm_adjust_roles(true);
+}
- if (bta_dm_search_cb.sdp_results) {
- APPL_TRACE_EVENT(" timer stopped ");
- alarm_cancel(bta_dm_search_cb.search_timer);
- bta_dm_discover_next_device();
- }
- }
+/** Callback from btm when acl connection goes up or down */
+static void bta_dm_bl_change_cback(tBTM_BL_EVENT_DATA* p_data) {
+ switch (p_data->event) {
+ case BTM_BL_CONN_EVT:
+ /* connection up */
+ do_in_main_thread(
+ FROM_HERE, base::Bind(bta_dm_acl_change, true, *p_data->conn.p_bda,
+ p_data->conn.transport, p_data->conn.handle));
+ break;
+ case BTM_BL_DISCN_EVT:
+ /* connection down */
+ do_in_main_thread(
+ FROM_HERE, base::Bind(bta_dm_acl_change, false, *p_data->discn.p_bda,
+ p_data->discn.transport, p_data->discn.handle));
+ break;
- if (bta_dm_cb.disabling) {
- if (!BTM_GetNumAclLinks()) {
- /*
- * Start a timer to make sure that the profiles
- * get the disconnect event.
- */
- alarm_set_on_mloop(bta_dm_cb.disable_timer,
- BTA_DM_DISABLE_CONN_DOWN_TIMER_MS,
- bta_dm_disable_conn_down_timer_cback, NULL);
+ case BTM_BL_UPDATE_EVT: {
+ /* busy level update */
+ do_in_main_thread(FROM_HERE, base::Bind(send_busy_level_update,
+ p_data->update.busy_level,
+ p_data->update.busy_level_flags));
+ return;
+ }
+ case BTM_BL_ROLE_CHG_EVT: {
+ const auto& tmp = p_data->role_chg;
+ do_in_main_thread(FROM_HERE, base::Bind(handle_role_change, *tmp.p_bda,
+ tmp.new_role, tmp.hci_status));
+ return;
}
- }
- if (remove_device) {
- bta_dm_process_remove_device_no_callback(bd_addr);
- }
-
- if (bta_dm_cb.p_sec_cback) {
- tBTA_DM_SEC conn;
- memset(&conn, 0, sizeof(tBTA_DM_SEC));
- conn.link_down.bd_addr = bd_addr;
- bta_dm_cb.p_sec_cback(BTA_DM_LINK_DOWN_EVT, &conn);
- if (issue_unpair_cb) bta_dm_cb.p_sec_cback(BTA_DM_DEV_UNPAIRED_EVT, &conn);
+ case BTM_BL_COLLISION_EVT:
+ /* Collision report from Stack: Notify profiles */
+ do_in_main_thread(
+ FROM_HERE, base::Bind(bta_sys_notify_collision, *p_data->conn.p_bda));
+ return;
}
-
- bta_dm_adjust_roles(true);
}
-void BTA_dm_acl_down(const RawAddress bd_addr, tBT_TRANSPORT transport) {
- do_in_main_thread(FROM_HERE, base::Bind(bta_dm_acl_down, bd_addr, transport));
+/*******************************************************************************
+ *
+ * Function bta_dm_rs_cback
+ *
+ * Description Receives the role switch complete event
+ *
+ * Returns
+ *
+ ******************************************************************************/
+static void bta_dm_rs_cback(UNUSED_ATTR void* p1) {
+ APPL_TRACE_WARNING("bta_dm_rs_cback:%d", bta_dm_cb.rs_event);
+ if (bta_dm_cb.rs_event == BTA_DM_API_SEARCH_EVT) {
+ bta_dm_cb.search_msg.rs_res =
+ BTA_DM_RS_OK; /* do not care about the result for now */
+ bta_dm_cb.rs_event = 0;
+ bta_dm_search_start((tBTA_DM_MSG*)&bta_dm_cb.search_msg);
+ }
}
/*******************************************************************************
@@ -2532,29 +2914,50 @@ void BTA_dm_acl_down(const RawAddress bd_addr, tBT_TRANSPORT transport) {
* Function bta_dm_check_av
*
* Description This function checks if AV is active
- * if yes, make sure the AV link is central
+ * if yes, make sure the AV link is master
+ *
+ * Returns bool - true, if switch is in progress
*
******************************************************************************/
-static void bta_dm_check_av() {
+static bool bta_dm_check_av(uint16_t event) {
+ bool avoid_roleswitch = false;
+ bool switching = false;
uint8_t i;
tBTA_DM_PEER_DEVICE* p_dev;
+#if (BTA_DM_AVOID_A2DP_ROLESWITCH_ON_INQUIRY == TRUE)
+
+ /* avoid role switch upon inquiry if a2dp is actively streaming as it
+ introduces an audioglitch due to FW scheduling delays (unavoidable) */
+ if (event == BTA_DM_API_SEARCH_EVT) {
+ avoid_roleswitch = true;
+ }
+#endif
+
+ APPL_TRACE_WARNING("bta_dm_check_av:%d", bta_dm_cb.cur_av_count);
if (bta_dm_cb.cur_av_count) {
- LOG_INFO("av_count:%d", bta_dm_cb.cur_av_count);
for (i = 0; i < bta_dm_cb.device_list.count; i++) {
p_dev = &bta_dm_cb.device_list.peer_device[i];
- APPL_TRACE_WARNING("[%d]: state:%d, info:x%x", i, p_dev->conn_state,
- p_dev->Info());
+ APPL_TRACE_WARNING("[%d]: state:%d, info:x%x, avoid_rs %d", i,
+ p_dev->conn_state, p_dev->info, avoid_roleswitch);
if ((p_dev->conn_state == BTA_DM_CONNECTED) &&
- (p_dev->Info() & BTA_DM_DI_AV_ACTIVE)) {
- /* make central and take away the role switch policy */
- BTM_SwitchRoleToCentral(p_dev->peer_bdaddr);
- /* else either already central or can not switch for some reasons */
- BTM_block_role_switch_for(p_dev->peer_bdaddr);
+ (p_dev->info & BTA_DM_DI_AV_ACTIVE) && (!avoid_roleswitch)) {
+ /* make master and take away the role switch policy */
+ if (BTM_CMD_STARTED == BTM_SwitchRole(p_dev->peer_bdaddr,
+ HCI_ROLE_MASTER,
+ bta_dm_rs_cback)) {
+ /* the role switch command is actually sent */
+ bta_dm_cb.rs_event = event;
+ switching = true;
+ }
+ /* else either already master or can not switch for some reasons */
+ bta_dm_policy_cback(BTA_SYS_PLCY_CLR, 0, HCI_ENABLE_MASTER_SLAVE_SWITCH,
+ p_dev->peer_bdaddr);
break;
}
}
}
+ return switching;
}
/*******************************************************************************
@@ -2568,12 +2971,21 @@ static void bta_dm_check_av() {
*
******************************************************************************/
static void bta_dm_disable_conn_down_timer_cback(UNUSED_ATTR void* data) {
+ tBTA_SYS_HW_MSG* sys_enable_event =
+ (tBTA_SYS_HW_MSG*)osi_malloc(sizeof(tBTA_SYS_HW_MSG));
+
/* disable the power managment module */
bta_dm_disable_pm();
+ /* register our callback to SYS HW manager */
+ bta_sys_hw_register(BTA_SYS_HW_BLUETOOTH, bta_dm_sys_hw_cback);
+
+ /* send a message to BTA SYS */
+ sys_enable_event->hdr.event = BTA_SYS_API_DISABLE_EVT;
+ sys_enable_event->hw_module = BTA_SYS_HW_BLUETOOTH;
+ bta_sys_sendmsg(sys_enable_event);
+
bta_dm_cb.disabling = false;
- LOG_INFO("Stack device manager shutdown completed");
- future_ready(stack_manager_get_hack_future(), FUTURE_SUCCESS);
}
/*******************************************************************************
@@ -2586,16 +2998,12 @@ static void bta_dm_disable_conn_down_timer_cback(UNUSED_ATTR void* data) {
* Returns void
*
******************************************************************************/
-void bta_dm_rm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
+static void bta_dm_rm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
+ uint8_t app_id, const RawAddress& peer_addr) {
uint8_t j;
tBTA_PREF_ROLES role;
tBTA_DM_PEER_DEVICE* p_dev;
- LOG_DEBUG("BTA Role management callback count:%d status:%s peer:%s",
- bta_dm_cb.cur_av_count, bta_sys_conn_status_text(status).c_str(),
- PRIVATE_ADDRESS(peer_addr));
-
p_dev = bta_dm_find_peer_device(peer_addr);
if (status == BTA_SYS_CONN_OPEN) {
if (p_dev) {
@@ -2612,11 +3020,8 @@ void bta_dm_rm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id, uint8_t app_id,
if (((p_bta_dm_rm_cfg[j].app_id == app_id) ||
(p_bta_dm_rm_cfg[j].app_id == BTA_ALL_APP_ID)) &&
(p_bta_dm_rm_cfg[j].id == id)) {
- ASSERT_LOG(p_bta_dm_rm_cfg[j].cfg <= BTA_PERIPHERAL_ROLE_ONLY,
- "Passing illegal preferred role:0x%02x [0x%02x<=>0x%02x]",
- p_bta_dm_rm_cfg[j].cfg, BTA_ANY_ROLE,
- BTA_PERIPHERAL_ROLE_ONLY);
- role = static_cast<tBTA_PREF_ROLES>(p_bta_dm_rm_cfg[j].cfg);
+ role = p_bta_dm_rm_cfg[j].cfg;
+
if (role > p_dev->pref_role) p_dev->pref_role = role;
break;
}
@@ -2624,7 +3029,7 @@ void bta_dm_rm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id, uint8_t app_id,
}
}
- if (BTA_ID_AV == id) {
+ if ((BTA_ID_AV == id) || (BTA_ID_AVK == id)) {
if (status == BTA_SYS_CONN_BUSY) {
if (p_dev) p_dev->info |= BTA_DM_DI_AV_ACTIVE;
/* AV calls bta_sys_conn_open with the A2DP stream count as app_id */
@@ -2635,6 +3040,8 @@ void bta_dm_rm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id, uint8_t app_id,
/* get cur_av_count from connected services */
if (BTA_ID_AV == id) bta_dm_cb.cur_av_count = bta_dm_get_av_count();
}
+ APPL_TRACE_WARNING("bta_dm_rm_cback:%d, status:%d", bta_dm_cb.cur_av_count,
+ status);
}
/* Don't adjust roles for each busy/idle state transition to avoid
@@ -2697,11 +3104,7 @@ static void bta_dm_remove_sec_dev_entry(const RawAddress& remote_bd_addr) {
APPL_TRACE_DEBUG(
"%s ACL is not down. Schedule for Dev Removal when ACL closes",
__func__);
- if (bluetooth::shim::is_gd_security_enabled()) {
- bluetooth::shim::BTM_SecClearSecurityFlags(remote_bd_addr);
- } else {
- BTM_SecClearSecurityFlags(remote_bd_addr);
- }
+ BTM_SecClearSecurityFlags(remote_bd_addr);
for (int i = 0; i < bta_dm_cb.device_list.count; i++) {
if (bta_dm_cb.device_list.peer_device[i].peer_bdaddr == remote_bd_addr) {
bta_dm_cb.device_list.peer_device[i].remove_dev_pending = TRUE;
@@ -2712,7 +3115,11 @@ static void bta_dm_remove_sec_dev_entry(const RawAddress& remote_bd_addr) {
// remote_bd_addr comes from security record, which is removed in
// BTM_SecDeleteDevice.
RawAddress addr_copy = remote_bd_addr;
- bta_dm_process_remove_device_no_callback(addr_copy);
+ BTM_SecDeleteDevice(addr_copy);
+ /* need to remove all pending background connection */
+ BTA_GATTC_CancelOpen(0, addr_copy, false);
+ /* remove all cached GATT information */
+ BTA_GATTC_Refresh(addr_copy);
}
}
@@ -2728,30 +3135,46 @@ static void bta_dm_remove_sec_dev_entry(const RawAddress& remote_bd_addr) {
******************************************************************************/
static void bta_dm_adjust_roles(bool delay_role_switch) {
uint8_t i;
+ bool set_master_role = false;
uint8_t br_count =
bta_dm_cb.device_list.count - bta_dm_cb.device_list.le_count;
if (br_count) {
+ /* the configuration is no scatternet
+ * or AV connection exists and there are more than one ACL link */
+ if ((p_bta_dm_rm_cfg[0].cfg == BTA_DM_NO_SCATTERNET) ||
+ (bta_dm_cb.cur_av_count && br_count > 1)) {
+ L2CA_SetDesireRole(HCI_ROLE_MASTER);
+ set_master_role = true;
+ }
+
for (i = 0; i < bta_dm_cb.device_list.count; i++) {
if (bta_dm_cb.device_list.peer_device[i].conn_state == BTA_DM_CONNECTED &&
bta_dm_cb.device_list.peer_device[i].transport ==
BT_TRANSPORT_BR_EDR) {
+ if (!set_master_role &&
+ (bta_dm_cb.device_list.peer_device[i].pref_role != BTA_ANY_ROLE) &&
+ (p_bta_dm_rm_cfg[0].cfg == BTA_DM_PARTIAL_SCATTERNET)) {
+ L2CA_SetDesireRole(HCI_ROLE_MASTER);
+ set_master_role = true;
+ }
+
if ((bta_dm_cb.device_list.peer_device[i].pref_role ==
- BTA_CENTRAL_ROLE_ONLY) ||
+ BTA_MASTER_ROLE_ONLY) ||
(br_count > 1)) {
/* Initiating immediate role switch with certain remote devices
has caused issues due to role switch colliding with link encryption
setup and
causing encryption (and in turn the link) to fail . These device .
Firmware
- versions are stored in a rejectlist and role switch with these
+ versions are stored in a blacklist and role switch with these
devices are
delayed to avoid the collision with link encryption setup */
if (bta_dm_cb.device_list.peer_device[i].pref_role !=
- BTA_PERIPHERAL_ROLE_ONLY &&
+ BTA_SLAVE_ROLE_ONLY &&
!delay_role_switch) {
- BTM_SwitchRoleToCentral(
- bta_dm_cb.device_list.peer_device[i].peer_bdaddr);
+ BTM_SwitchRole(bta_dm_cb.device_list.peer_device[i].peer_bdaddr,
+ HCI_ROLE_MASTER, NULL);
} else {
alarm_set_on_mloop(bta_dm_cb.switch_delay_timer,
BTA_DM_SWITCH_DELAY_TIMER_MS,
@@ -2760,6 +3183,13 @@ static void bta_dm_adjust_roles(bool delay_role_switch) {
}
}
}
+
+ if (!set_master_role) {
+ L2CA_SetDesireRole(L2CAP_DESIRED_LINK_ROLE);
+ }
+
+ } else {
+ L2CA_SetDesireRole(L2CAP_DESIRED_LINK_ROLE);
}
}
@@ -2778,10 +3208,7 @@ static char* bta_dm_get_remname(void) {
/* If the name isn't already stored, try retrieving from BTM */
if (*p_name == '\0') {
- p_temp =
- (bluetooth::shim::is_gd_security_enabled())
- ? bluetooth::shim::BTM_SecReadDevName(bta_dm_search_cb.peer_bdaddr)
- : BTM_SecReadDevName(bta_dm_search_cb.peer_bdaddr);
+ p_temp = BTM_SecReadDevName(bta_dm_search_cb.peer_bdaddr);
if (p_temp != NULL) p_name = p_temp;
}
@@ -2883,7 +3310,7 @@ static void bta_dm_set_eir(char* local_name) {
memset(p, 0x00, HCI_EXT_INQ_RESPONSE_LEN);
- LOG_INFO("Generating extended inquiry response packet EIR");
+ APPL_TRACE_DEBUG("BTA is generating EIR");
if (local_name)
local_name_len = strlen(local_name);
@@ -2968,7 +3395,7 @@ static void bta_dm_set_eir(char* local_name) {
for (custom_uuid_idx = 0;
custom_uuid_idx < BTA_EIR_SERVER_NUM_CUSTOM_UUID;
custom_uuid_idx++) {
- const Uuid& curr = bta_dm_cb.bta_custom_uuid[custom_uuid_idx].custom_uuid;
+ const Uuid& curr = bta_dm_cb.custom_uuid[custom_uuid_idx];
if (curr.GetShortestRepresentationSize() == Uuid::kNumBytes16) {
if (num_uuid < max_num_uuid) {
UINT16_TO_STREAM(p, curr.As16Bit());
@@ -3001,7 +3428,7 @@ static void bta_dm_set_eir(char* local_name) {
for (custom_uuid_idx = 0; custom_uuid_idx < BTA_EIR_SERVER_NUM_CUSTOM_UUID;
custom_uuid_idx++) {
- const Uuid& curr = bta_dm_cb.bta_custom_uuid[custom_uuid_idx].custom_uuid;
+ const Uuid& curr = bta_dm_cb.custom_uuid[custom_uuid_idx];
if (curr.GetShortestRepresentationSize() == Uuid::kNumBytes32) {
if (num_uuid < max_num_uuid) {
UINT32_TO_STREAM(p, curr.As32Bit());
@@ -3030,7 +3457,7 @@ static void bta_dm_set_eir(char* local_name) {
for (custom_uuid_idx = 0; custom_uuid_idx < BTA_EIR_SERVER_NUM_CUSTOM_UUID;
custom_uuid_idx++) {
- const Uuid& curr = bta_dm_cb.bta_custom_uuid[custom_uuid_idx].custom_uuid;
+ const Uuid& curr = bta_dm_cb.custom_uuid[custom_uuid_idx];
if (curr.GetShortestRepresentationSize() == Uuid::kNumBytes128) {
if (num_uuid < max_num_uuid) {
ARRAY16_TO_STREAM(p, curr.To128BitBE().data());
@@ -3069,7 +3496,7 @@ static void bta_dm_set_eir(char* local_name) {
p_length = p;
UINT8_TO_STREAM(p, p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec_len + 1);
- UINT8_TO_STREAM(p, HCI_EIR_MANUFACTURER_SPECIFIC_TYPE);
+ UINT8_TO_STREAM(p, BTM_EIR_MANUFACTURER_SPECIFIC_TYPE);
memcpy(p, p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec,
p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec_len);
p += p_bta_dm_eir_cfg->bta_dm_eir_manufac_spec_len;
@@ -3093,83 +3520,69 @@ static void bta_dm_set_eir(char* local_name) {
BTM_WriteEIR(p_buf);
}
-#if (BTA_EIR_CANNED_UUID_LIST != TRUE)
/*******************************************************************************
*
- * Function bta_dm_get_cust_uuid_index
- *
- * Description Get index of custom uuid from list
- * Note, handle equals to 0 means to find a vacant
- * from list.
+ * Function bta_dm_eir_search_services
*
- * Returns Index of array
- * bta_dm_cb.bta_custom_uuid[BTA_EIR_SERVER_NUM_CUSTOM_UUID]
- *
- ******************************************************************************/
-static uint8_t bta_dm_get_cust_uuid_index(uint32_t handle) {
-#if (BTA_EIR_SERVER_NUM_CUSTOM_UUID > 0)
- uint8_t c_uu_idx = 0;
-
- while(c_uu_idx < BTA_EIR_SERVER_NUM_CUSTOM_UUID &&
- bta_dm_cb.bta_custom_uuid[c_uu_idx].handle != handle) {
- c_uu_idx++;
- }
-
- return c_uu_idx;
-#else
- return 0;
-#endif
-}
-
-/*******************************************************************************
- *
- * Function bta_dm_update_cust_uuid
- *
- * Description Update custom uuid with given value
+ * Description This function searches services in received EIR
*
* Returns None
*
******************************************************************************/
-static void bta_dm_update_cust_uuid(uint8_t c_uu_idx, const Uuid& uuid, uint32_t handle) {
-#if (BTA_EIR_SERVER_NUM_CUSTOM_UUID > 0)
- if (c_uu_idx < BTA_EIR_SERVER_NUM_CUSTOM_UUID) {
- tBTA_CUSTOM_UUID& curr = bta_dm_cb.bta_custom_uuid[c_uu_idx];
- curr.custom_uuid.UpdateUuid(uuid);
- curr.handle = handle;
- } else {
- APPL_TRACE_ERROR("%s invalid uuid index %d", __func__, c_uu_idx);
- }
-#endif
-}
+static void bta_dm_eir_search_services(tBTM_INQ_RESULTS* p_result,
+ tBTA_SERVICE_MASK* p_services_to_search,
+ tBTA_SERVICE_MASK* p_services_found) {
+ tBTA_SERVICE_MASK service_index = 0;
+ tBTM_EIR_SEARCH_RESULT result;
+
+ VLOG(1) << "BTA searching services in EIR of BDA:"
+ << p_result->remote_bd_addr;
+
+ APPL_TRACE_DEBUG(" with services_to_search=0x%08X", *p_services_to_search);
+
+ /* always do GATT based service discovery by SDP instead of from EIR */
+ /* if GATT based service is also to be put in EIR, need to modify this */
+ while (service_index < (BTA_MAX_SERVICE_ID - 1)) {
+ if (*p_services_to_search &
+ (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(service_index))) {
+ result = BTM_HasInquiryEirService(
+ p_result, bta_service_id_to_uuid_lkup_tbl[service_index]);
+
+ /* Searching for HSP v1.2 only device */
+ if ((result != BTM_EIR_FOUND) &&
+ (bta_service_id_to_uuid_lkup_tbl[service_index] ==
+ UUID_SERVCLASS_HEADSET)) {
+ result = BTM_HasInquiryEirService(p_result, UUID_SERVCLASS_HEADSET_HS);
+ }
-/*******************************************************************************
- *
- * Function bta_dm_eir_update_cust_uuid
- *
- * Description This function adds or removes custom service UUID in EIR database.
- *
- * Returns None
- *
- ******************************************************************************/
-void bta_dm_eir_update_cust_uuid(const tBTA_CUSTOM_UUID& curr, bool adding) {
- APPL_TRACE_DEBUG("%s", __func__);
-#if (BTA_EIR_SERVER_NUM_CUSTOM_UUID > 0)
- uint8_t c_uu_idx = 0;
- if (adding) {
- c_uu_idx = bta_dm_get_cust_uuid_index(0); /* find a vacant from uuid list */
- bta_dm_update_cust_uuid(c_uu_idx, curr.custom_uuid, curr.handle);
- } else {
- c_uu_idx = bta_dm_get_cust_uuid_index(curr.handle); /* find the uuid from uuid list */
- bta_dm_update_cust_uuid(c_uu_idx, curr.custom_uuid, 0);
- }
+ if (result == BTM_EIR_FOUND) {
+ /* If Plug and Play service record, need to check to see if Broadcom
+ * stack */
+ /* However, EIR data doesn't have EXT_BRCM_VERSION so just skip it */
+ if (bta_service_id_to_uuid_lkup_tbl[service_index] !=
+ UUID_SERVCLASS_PNP_INFORMATION) {
+ *p_services_found |= (tBTA_SERVICE_MASK)(
+ BTA_SERVICE_ID_TO_SERVICE_MASK(service_index));
+ /* remove the service from services to be searched */
+ *p_services_to_search &= (tBTA_SERVICE_MASK)(
+ ~(BTA_SERVICE_ID_TO_SERVICE_MASK(service_index)));
+ }
+ } else if (result == BTM_EIR_NOT_FOUND) {
+ /* remove the service from services to be searched */
+ *p_services_to_search &= (tBTA_SERVICE_MASK)(
+ ~(BTA_SERVICE_ID_TO_SERVICE_MASK(service_index)));
+ }
+ }
- /* Update EIR when UUIDs are changed */
- if (c_uu_idx <= BTA_EIR_SERVER_NUM_CUSTOM_UUID) {
- bta_dm_set_eir(NULL);
+ service_index++;
}
-#endif
+
+ APPL_TRACE_ERROR(
+ "BTA EIR search result, services_to_search=0x%08X, services_found=0x%08X",
+ *p_services_to_search, *p_services_found);
}
+#if (BTA_EIR_CANNED_UUID_LIST != TRUE)
/*******************************************************************************
*
* Function bta_dm_eir_update_uuid
@@ -3184,16 +3597,19 @@ void bta_dm_eir_update_uuid(uint16_t uuid16, bool adding) {
if (!BTM_HasEirService(p_bta_dm_eir_cfg->uuid_mask, uuid16)) return;
if (adding) {
- LOG_INFO("EIR Adding UUID=0x%04X into extended inquiry response", uuid16);
+ APPL_TRACE_EVENT("Adding UUID=0x%04X into EIR", uuid16);
BTM_AddEirService(bta_dm_cb.eir_uuid, uuid16);
} else {
- LOG_INFO("EIR Removing UUID=0x%04X from extended inquiry response", uuid16);
+ APPL_TRACE_EVENT("Removing UUID=0x%04X from EIR", uuid16);
BTM_RemoveEirService(bta_dm_cb.eir_uuid, uuid16);
}
bta_dm_set_eir(NULL);
+
+ APPL_TRACE_EVENT("bta_dm_eir_update_uuid UUID bit mask=0x%08X %08X",
+ bta_dm_cb.eir_uuid[1], bta_dm_cb.eir_uuid[0]);
}
#endif
@@ -3249,9 +3665,9 @@ void bta_dm_encrypt_cback(const RawAddress* bd_addr, tBT_TRANSPORT transport,
}
/**This function to encrypt the link */
-void bta_dm_set_encryption(const RawAddress& bd_addr, tBT_TRANSPORT transport,
+void bta_dm_set_encryption(const RawAddress& bd_addr, tBTA_TRANSPORT transport,
tBTA_DM_ENCRYPT_CBACK* p_callback,
- tBTM_BLE_SEC_ACT sec_act) {
+ tBTA_DM_BLE_SEC_ACT sec_act) {
uint8_t i;
APPL_TRACE_DEBUG("bta_dm_set_encryption"); // todo
@@ -3366,46 +3782,6 @@ static void bta_dm_observe_cmpl_cb(void* p_result) {
}
}
-static void ble_io_req(const RawAddress& bd_addr, tBTM_IO_CAP* p_io_cap,
- tBTM_OOB_DATA* p_oob_data, tBTM_LE_AUTH_REQ* p_auth_req,
- uint8_t* p_max_key_size, tBTM_LE_KEY_TYPE* p_init_key,
- tBTM_LE_KEY_TYPE* p_resp_key) {
- bte_appl_cfg.ble_io_cap = btif_storage_get_local_io_caps_ble();
-
- /* Retrieve the properties from file system if possible */
- tBTE_APPL_CFG nv_config;
- if (btif_dm_get_smp_config(&nv_config)) bte_appl_cfg = nv_config;
-
- /* *p_auth_req by default is false for devices with NoInputNoOutput; true for
- * other devices. */
-
- if (bte_appl_cfg.ble_auth_req)
- *p_auth_req = bte_appl_cfg.ble_auth_req |
- (bte_appl_cfg.ble_auth_req & 0x04) | ((*p_auth_req) & 0x04);
-
- /* if OOB is not supported, this call-out function does not need to do
- * anything
- * otherwise, look for the OOB data associated with the address and set
- * *p_oob_data accordingly.
- * If the answer can not be obtained right away,
- * set *p_oob_data to BTA_OOB_UNKNOWN and call bta_dm_ci_io_req() when the
- * answer is available.
- */
-
- btif_dm_set_oob_for_le_io_req(bd_addr, p_oob_data, p_auth_req);
-
- if (bte_appl_cfg.ble_io_cap <= 4) *p_io_cap = bte_appl_cfg.ble_io_cap;
-
- if (bte_appl_cfg.ble_init_key <= BTM_BLE_INITIATOR_KEY_SIZE)
- *p_init_key = bte_appl_cfg.ble_init_key;
-
- if (bte_appl_cfg.ble_resp_key <= BTM_BLE_RESPONDER_KEY_SIZE)
- *p_resp_key = bte_appl_cfg.ble_resp_key;
-
- if (bte_appl_cfg.ble_max_key_size > 7 && bte_appl_cfg.ble_max_key_size <= 16)
- *p_max_key_size = bte_appl_cfg.ble_max_key_size;
-}
-
/*******************************************************************************
*
* Function bta_dm_ble_smp_cback
@@ -3427,11 +3803,13 @@ static uint8_t bta_dm_ble_smp_cback(tBTM_LE_EVT event, const RawAddress& bda,
memset(&sec_event, 0, sizeof(tBTA_DM_SEC));
switch (event) {
case BTM_LE_IO_REQ_EVT:
- ble_io_req(bda, &p_data->io_req.io_cap, &p_data->io_req.oob_data,
- &p_data->io_req.auth_req, &p_data->io_req.max_key_size,
- &p_data->io_req.init_keys, &p_data->io_req.resp_keys);
+ bta_dm_co_ble_io_req(
+ bda, &p_data->io_req.io_cap, &p_data->io_req.oob_data,
+ &p_data->io_req.auth_req, &p_data->io_req.max_key_size,
+ &p_data->io_req.init_keys, &p_data->io_req.resp_keys);
APPL_TRACE_EVENT("io mitm: %d oob_data:%d", p_data->io_req.auth_req,
p_data->io_req.oob_data);
+
break;
case BTM_LE_CONSENT_REQ_EVT:
@@ -3446,11 +3824,9 @@ static uint8_t bta_dm_ble_smp_cback(tBTM_LE_EVT event, const RawAddress& bda,
case BTM_LE_SEC_REQUEST_EVT:
sec_event.ble_req.bd_addr = bda;
- p_name = (bluetooth::shim::is_gd_security_enabled())
- ? bluetooth::shim::BTM_SecReadDevName(bda)
- : BTM_SecReadDevName(bda);
+ p_name = BTM_SecReadDevName(bda);
if (p_name != NULL)
- strlcpy((char*)sec_event.ble_req.bd_name, p_name, BD_NAME_LEN + 1);
+ strlcpy((char*)sec_event.ble_req.bd_name, p_name, BD_NAME_LEN);
else
sec_event.ble_req.bd_name[0] = 0;
bta_dm_cb.p_sec_cback(BTA_DM_BLE_SEC_REQ_EVT, &sec_event);
@@ -3458,11 +3834,9 @@ static uint8_t bta_dm_ble_smp_cback(tBTM_LE_EVT event, const RawAddress& bda,
case BTM_LE_KEY_NOTIF_EVT:
sec_event.key_notif.bd_addr = bda;
- p_name = (bluetooth::shim::is_gd_security_enabled())
- ? bluetooth::shim::BTM_SecReadDevName(bda)
- : BTM_SecReadDevName(bda);
+ p_name = BTM_SecReadDevName(bda);
if (p_name != NULL)
- strlcpy((char*)sec_event.key_notif.bd_name, p_name, BD_NAME_LEN + 1);
+ strlcpy((char*)sec_event.key_notif.bd_name, p_name, BD_NAME_LEN);
else
sec_event.key_notif.bd_name[0] = 0;
sec_event.key_notif.passkey = p_data->key_notif;
@@ -3482,7 +3856,7 @@ static uint8_t bta_dm_ble_smp_cback(tBTM_LE_EVT event, const RawAddress& bda,
case BTM_LE_NC_REQ_EVT:
sec_event.key_notif.bd_addr = bda;
strlcpy((char*)sec_event.key_notif.bd_name, bta_dm_get_remname(),
- (BD_NAME_LEN + 1));
+ (BD_NAME_LEN));
sec_event.key_notif.passkey = p_data->key_notif;
bta_dm_cb.p_sec_cback(BTA_DM_BLE_NC_REQ_EVT, &sec_event);
break;
@@ -3492,14 +3866,6 @@ static uint8_t bta_dm_ble_smp_cback(tBTM_LE_EVT event, const RawAddress& bda,
bta_dm_cb.p_sec_cback(BTA_DM_BLE_SC_OOB_REQ_EVT, &sec_event);
break;
- case BTM_LE_SC_LOC_OOB_EVT:
- tBTA_DM_LOC_OOB_DATA local_oob_data;
- local_oob_data.local_oob_c = p_data->local_oob_data.commitment;
- local_oob_data.local_oob_r = p_data->local_oob_data.randomizer;
- sec_event.local_oob_data = local_oob_data;
- bta_dm_cb.p_sec_cback(BTA_DM_BLE_SC_CR_LOC_OOB_EVT, &sec_event);
- break;
-
case BTM_LE_KEY_EVT:
sec_event.ble_key.bd_addr = bda;
sec_event.ble_key.key_type = p_data->key.key_type;
@@ -3511,19 +3877,15 @@ static uint8_t bta_dm_ble_smp_cback(tBTM_LE_EVT event, const RawAddress& bda,
sec_event.auth_cmpl.bd_addr = bda;
BTM_ReadDevInfo(bda, &sec_event.auth_cmpl.dev_type,
&sec_event.auth_cmpl.addr_type);
- p_name = (bluetooth::shim::is_gd_security_enabled())
- ? bluetooth::shim::BTM_SecReadDevName(bda)
- : BTM_SecReadDevName(bda);
+ p_name = BTM_SecReadDevName(bda);
if (p_name != NULL)
- strlcpy((char*)sec_event.auth_cmpl.bd_name, p_name, (BD_NAME_LEN + 1));
+ strlcpy((char*)sec_event.auth_cmpl.bd_name, p_name, (BD_NAME_LEN));
else
sec_event.auth_cmpl.bd_name[0] = 0;
- if (p_data->complt.reason != HCI_SUCCESS) {
- // TODO This is not a proper use of this type
+ if (p_data->complt.reason != 0) {
sec_event.auth_cmpl.fail_reason =
- static_cast<tHCI_STATUS>(BTA_DM_AUTH_CONVERT_SMP_CODE(
- (static_cast<uint8_t>(p_data->complt.reason))));
+ BTA_DM_AUTH_CONVERT_SMP_CODE(((uint8_t)p_data->complt.reason));
if (btm_sec_is_a_bonded_dev(bda) &&
p_data->complt.reason == SMP_CONN_TOUT) {
@@ -3605,8 +3967,10 @@ static void bta_dm_ble_id_key_cback(uint8_t key_type,
*
******************************************************************************/
void bta_dm_add_blekey(const RawAddress& bd_addr, tBTA_LE_KEY_VALUE blekey,
- tBTM_LE_KEY_TYPE key_type) {
- BTM_SecAddBleKey(bd_addr, (tBTM_LE_KEY_VALUE*)&blekey, key_type);
+ tBTA_LE_KEY_TYPE key_type) {
+ if (!BTM_SecAddBleKey(bd_addr, (tBTM_LE_KEY_VALUE*)&blekey, key_type)) {
+ LOG(ERROR) << "BTA_DM: Error adding BLE Key for device " << bd_addr;
+ }
}
/*******************************************************************************
@@ -3623,7 +3987,9 @@ void bta_dm_add_blekey(const RawAddress& bd_addr, tBTA_LE_KEY_VALUE blekey,
******************************************************************************/
void bta_dm_add_ble_device(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
tBT_DEVICE_TYPE dev_type) {
- BTM_SecAddBleDevice(bd_addr, dev_type, addr_type);
+ if (!BTM_SecAddBleDevice(bd_addr, NULL, dev_type, addr_type)) {
+ LOG(ERROR) << "BTA_DM: Error adding BLE Device for device " << bd_addr;
+ }
}
/*******************************************************************************
@@ -3653,13 +4019,19 @@ void bta_dm_ble_confirm_reply(const RawAddress& bd_addr, bool accept) {
/** This function set the preferred connection parameters */
void bta_dm_ble_set_conn_params(const RawAddress& bd_addr,
uint16_t conn_int_min, uint16_t conn_int_max,
- uint16_t peripheral_latency,
+ uint16_t slave_latency,
uint16_t supervision_tout) {
L2CA_AdjustConnectionIntervals(&conn_int_min, &conn_int_max,
BTM_BLE_CONN_INT_MIN);
- BTM_BleSetPrefConnParams(bd_addr, conn_int_min, conn_int_max,
- peripheral_latency, supervision_tout);
+ BTM_BleSetPrefConnParams(bd_addr, conn_int_min, conn_int_max, slave_latency,
+ supervision_tout);
+}
+
+/** This function set the preferred connection scan parameters */
+void bta_dm_ble_set_conn_scan_params(uint32_t scan_interval,
+ uint32_t scan_window) {
+ BTM_BleSetConnScanParams(scan_interval, scan_window);
}
/** This function update LE connection parameters */
@@ -3706,12 +4078,10 @@ void bta_dm_ble_observe(bool start, uint8_t duration,
}
/** This function set the maximum transmission packet size */
-void bta_dm_ble_set_data_length(const RawAddress& bd_addr) {
- const controller_t* controller = controller_get_interface();
- uint16_t max_len = controller->get_ble_maximum_tx_data_length();
-
- if (BTM_SetBleDataLength(bd_addr, max_len) != BTM_SUCCESS) {
- LOG_INFO("Unable to set ble data length:%hu", max_len);
+void bta_dm_ble_set_data_length(const RawAddress& bd_addr,
+ uint16_t tx_data_length) {
+ if (BTM_SetBleDataLength(bd_addr, tx_data_length) != BTM_SUCCESS) {
+ APPL_TRACE_ERROR("%s failed", __func__);
}
}
@@ -3729,8 +4099,8 @@ static void bta_ble_energy_info_cmpl(tBTM_BLE_TX_TIME_MS tx_time,
tBTM_BLE_RX_TIME_MS rx_time,
tBTM_BLE_IDLE_TIME_MS idle_time,
tBTM_BLE_ENERGY_USED energy_used,
- tHCI_STATUS status) {
- tBTA_STATUS st = (status == HCI_SUCCESS) ? BTA_SUCCESS : BTA_FAILURE;
+ tBTM_STATUS status) {
+ tBTA_STATUS st = (status == BTM_SUCCESS) ? BTA_SUCCESS : BTA_FAILURE;
tBTA_DM_CONTRL_STATE ctrl_state = 0;
if (BTA_SUCCESS == st) ctrl_state = bta_dm_pm_obtain_controller_state();
@@ -3745,8 +4115,8 @@ void bta_dm_ble_get_energy_info(
tBTA_BLE_ENERGY_INFO_CBACK* p_energy_info_cback) {
bta_dm_cb.p_energy_info_cback = p_energy_info_cback;
tBTM_STATUS btm_status = BTM_BleGetEnergyInfo(bta_ble_energy_info_cmpl);
- if (btm_status != BTM_CMD_STARTED)
- bta_ble_energy_info_cmpl(0, 0, 0, 0, HCI_ERR_UNSPECIFIED);
+ if (BTM_CMD_STARTED != btm_status)
+ bta_ble_energy_info_cmpl(0, 0, 0, 0, btm_status);
}
#ifndef BTA_DM_GATT_CLOSE_DELAY_TOUT
@@ -3772,7 +4142,81 @@ static void bta_dm_gattc_register(void) {
else
bta_dm_search_cb.client_if = BTA_GATTS_INVALID_IF;
- }), false);
+ }));
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_dm_start_disc_gatt_services
+ *
+ * Description This function starts a GATT service search request.
+ *
+ * Parameters:
+ *
+ ******************************************************************************/
+static void btm_dm_start_disc_gatt_services(uint16_t conn_id) {
+ Uuid* p_uuid = bta_dm_search_cb.p_srvc_uuid + bta_dm_search_cb.num_uuid -
+ bta_dm_search_cb.uuid_to_search;
+
+ /* always search for all services */
+ BTA_GATTC_ServiceSearchRequest(conn_id, p_uuid);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_gatt_disc_result
+ *
+ * Description This function process the GATT service search result.
+ *
+ * Parameters:
+ *
+ ******************************************************************************/
+static void bta_dm_gatt_disc_result(tBTA_GATT_ID service_id) {
+ tBTA_DM_SEARCH result;
+
+ /*
+ * This logic will not work for gatt case. We are checking against the
+ * bluetooth profiles here
+ * just copy the GATTID in raw data field and send it across.
+ */
+
+ if (bta_dm_search_cb.ble_raw_used + sizeof(tBTA_GATT_ID) <
+ bta_dm_search_cb.ble_raw_size) {
+ APPL_TRACE_DEBUG(
+ "ADDING BLE SERVICE uuid=%s, ble_ptr = 0x%x, ble_raw_used = 0x%x",
+ service_id.uuid.ToString().c_str(), bta_dm_search_cb.p_ble_rawdata,
+ bta_dm_search_cb.ble_raw_used);
+
+ if (bta_dm_search_cb.p_ble_rawdata) {
+ // TODO(jpawlowski): the p_ble_raw data is only sent to btif_dm.cc, but is
+ // never used there. Get rid of this code completly, or implement the
+ // TODOs from btif_dm.cc
+ memcpy((bta_dm_search_cb.p_ble_rawdata + bta_dm_search_cb.ble_raw_used),
+ &service_id, sizeof(service_id));
+
+ bta_dm_search_cb.ble_raw_used += sizeof(service_id);
+ } else {
+ APPL_TRACE_ERROR("p_ble_rawdata is NULL");
+ }
+
+ } else {
+ APPL_TRACE_ERROR(
+ "%s out of room to accomodate more service ids ble_raw_size = %d "
+ "ble_raw_used = %d",
+ __func__, bta_dm_search_cb.ble_raw_size, bta_dm_search_cb.ble_raw_used);
+ }
+
+ LOG_INFO(LOG_TAG, "%s service_id_uuid_len=%zu", __func__,
+ service_id.uuid.GetShortestRepresentationSize());
+ if (bta_dm_search_cb.state != BTA_DM_SEARCH_IDLE) {
+ /* send result back to app now, one by one */
+ result.disc_ble_res.bd_addr = bta_dm_search_cb.peer_bdaddr;
+ strlcpy((char*)result.disc_ble_res.bd_name, bta_dm_get_remname(),
+ BD_NAME_LEN);
+ result.disc_ble_res.service = service_id.uuid;
+
+ bta_dm_search_cb.p_search_cback(BTA_DM_DISC_BLE_RES_EVT, &result);
}
}
@@ -3788,33 +4232,55 @@ static void bta_dm_gattc_register(void) {
static void bta_dm_gatt_disc_complete(uint16_t conn_id, tGATT_STATUS status) {
APPL_TRACE_DEBUG("%s conn_id = %d", __func__, conn_id);
- tBTA_DM_MSG* p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
+ if (bta_dm_search_cb.uuid_to_search > 0) bta_dm_search_cb.uuid_to_search--;
- /* no more services to be discovered */
- p_msg->hdr.event = BTA_DM_DISCOVERY_RESULT_EVT;
- p_msg->disc_result.result.disc_res.result =
- (status == GATT_SUCCESS) ? BTA_SUCCESS : BTA_FAILURE;
- APPL_TRACE_DEBUG("%s service found: 0x%08x", __func__,
- bta_dm_search_cb.services_found);
- p_msg->disc_result.result.disc_res.services = bta_dm_search_cb.services_found;
- p_msg->disc_result.result.disc_res.num_uuids = 0;
- p_msg->disc_result.result.disc_res.p_uuid_list = NULL;
- p_msg->disc_result.result.disc_res.bd_addr = bta_dm_search_cb.peer_bdaddr;
- strlcpy((char*)p_msg->disc_result.result.disc_res.bd_name,
- bta_dm_get_remname(), BD_NAME_LEN + 1);
+ if (status == GATT_SUCCESS && bta_dm_search_cb.uuid_to_search > 0) {
+ btm_dm_start_disc_gatt_services(conn_id);
+ } else {
+ tBTA_DM_MSG* p_msg = (tBTA_DM_MSG*)osi_malloc(sizeof(tBTA_DM_MSG));
- p_msg->disc_result.result.disc_res.device_type |= BT_DEVICE_TYPE_BLE;
+ bta_dm_search_cb.uuid_to_search = 0;
- bta_sys_sendmsg(p_msg);
+ /* no more services to be discovered */
+ p_msg->hdr.event = BTA_DM_DISCOVERY_RESULT_EVT;
+ p_msg->disc_result.result.disc_res.result =
+ (status == GATT_SUCCESS) ? BTA_SUCCESS : BTA_FAILURE;
+ APPL_TRACE_DEBUG("%s service found: 0x%08x", __func__,
+ bta_dm_search_cb.services_found);
+ p_msg->disc_result.result.disc_res.services =
+ bta_dm_search_cb.services_found;
+ p_msg->disc_result.result.disc_res.num_uuids = 0;
+ p_msg->disc_result.result.disc_res.p_uuid_list = NULL;
+ p_msg->disc_result.result.disc_res.bd_addr = bta_dm_search_cb.peer_bdaddr;
+ strlcpy((char*)p_msg->disc_result.result.disc_res.bd_name,
+ bta_dm_get_remname(), BD_NAME_LEN);
+
+ p_msg->disc_result.result.disc_res.device_type |= BT_DEVICE_TYPE_BLE;
+ if (bta_dm_search_cb.ble_raw_used > 0) {
+ p_msg->disc_result.result.disc_res.p_raw_data =
+ (uint8_t*)osi_malloc(bta_dm_search_cb.ble_raw_used);
+
+ memcpy(p_msg->disc_result.result.disc_res.p_raw_data,
+ bta_dm_search_cb.p_ble_rawdata, bta_dm_search_cb.ble_raw_used);
- if (conn_id != GATT_INVALID_CONN_ID) {
- /* start a GATT channel close delay timer */
- bta_sys_start_timer(bta_dm_search_cb.gatt_close_timer,
- BTA_DM_GATT_CLOSE_DELAY_TOUT,
- BTA_DM_DISC_CLOSE_TOUT_EVT, 0);
- bta_dm_search_cb.pending_close_bda = bta_dm_search_cb.peer_bdaddr;
+ p_msg->disc_result.result.disc_res.raw_data_size =
+ bta_dm_search_cb.ble_raw_used;
+ } else {
+ p_msg->disc_result.result.disc_res.p_raw_data = NULL;
+ bta_dm_search_cb.p_ble_rawdata = 0;
+ }
+
+ bta_sys_sendmsg(p_msg);
+
+ if (conn_id != GATT_INVALID_CONN_ID) {
+ /* start a GATT channel close delay timer */
+ bta_sys_start_timer(bta_dm_search_cb.gatt_close_timer,
+ BTA_DM_GATT_CLOSE_DELAY_TOUT,
+ BTA_DM_DISC_CLOSE_TOUT_EVT, 0);
+ bta_dm_search_cb.pending_close_bda = bta_dm_search_cb.peer_bdaddr;
+ }
+ bta_dm_search_cb.gatt_disc_active = false;
}
- bta_dm_search_cb.gatt_disc_active = false;
}
/*******************************************************************************
@@ -3852,12 +4318,14 @@ void btm_dm_start_gatt_discovery(const RawAddress& bd_addr) {
bta_dm_search_cb.conn_id != GATT_INVALID_CONN_ID) {
bta_dm_search_cb.pending_close_bda = RawAddress::kEmpty;
alarm_cancel(bta_dm_search_cb.gatt_close_timer);
- BTA_GATTC_ServiceSearchRequest(bta_dm_search_cb.conn_id, nullptr);
+ btm_dm_start_disc_gatt_services(bta_dm_search_cb.conn_id);
} else {
if (BTM_IsAclConnectionUp(bd_addr, BT_TRANSPORT_LE)) {
- BTA_GATTC_Open(bta_dm_search_cb.client_if, bd_addr, true, true);
+ BTA_GATTC_Open(bta_dm_search_cb.client_if, bd_addr, true,
+ GATT_TRANSPORT_LE, true);
} else {
- BTA_GATTC_Open(bta_dm_search_cb.client_if, bd_addr, true, false);
+ BTA_GATTC_Open(bta_dm_search_cb.client_if, bd_addr, true,
+ GATT_TRANSPORT_LE, false);
}
}
}
@@ -3899,7 +4367,7 @@ void bta_dm_proc_open_evt(tBTA_GATTC_OPEN* p_data) {
bta_dm_search_cb.conn_id = p_data->conn_id;
if (p_data->status == GATT_SUCCESS) {
- BTA_GATTC_ServiceSearchRequest(p_data->conn_id, nullptr);
+ btm_dm_start_disc_gatt_services(p_data->conn_id);
} else {
bta_dm_gatt_disc_complete(GATT_INVALID_CONN_ID, p_data->status);
}
@@ -3923,6 +4391,7 @@ static void bta_dm_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
break;
case BTA_GATTC_SEARCH_RES_EVT:
+ bta_dm_gatt_disc_result(p_data->srvc_res.service_uuid);
break;
case BTA_GATTC_SEARCH_CMPL_EVT:
@@ -3957,9 +4426,9 @@ static void bta_dm_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
* Parameters:
*
******************************************************************************/
-static void bta_dm_ctrl_features_rd_cmpl_cback(tHCI_STATUS result) {
+static void bta_dm_ctrl_features_rd_cmpl_cback(tBTM_STATUS result) {
APPL_TRACE_DEBUG("%s status = %d ", __func__, result);
- if (result == HCI_SUCCESS) {
+ if (result == BTM_SUCCESS) {
if (bta_dm_cb.p_sec_cback)
bta_dm_cb.p_sec_cback(BTA_DM_LE_FEATURES_READ, NULL);
} else {
diff --git a/bta/dm/bta_dm_api.cc b/bta/dm/bta_dm_api.cc
index 8e9e4c1e6..165017222 100644
--- a/bta/dm/bta_dm_api.cc
+++ b/bta/dm/bta_dm_api.cc
@@ -21,19 +21,19 @@
* This is the API implementation file for the BTA device manager.
*
******************************************************************************/
-
-#include <base/bind.h>
-#include <vector>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/dm/bta_dm_int.h"
-#include "osi/include/allocator.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
+#include <base/bind_helpers.h>
+#include <string.h>
+
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_dm_int.h"
+#include "bta_sys.h"
+#include "bta_sys_int.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "osi/include/osi.h"
+#include "stack/include/btu.h"
+#include "utl.h"
using bluetooth::Uuid;
@@ -44,11 +44,43 @@ using bluetooth::Uuid;
static const tBTA_SYS_REG bta_dm_search_reg = {bta_dm_search_sm_execute,
bta_dm_search_sm_disable};
-void BTA_dm_init() {
+/*******************************************************************************
+ *
+ * Function BTA_EnableBluetooth
+ *
+ * Description Enables bluetooth service. This function must be
+ * called before any other functions in the BTA API are called.
+ *
+ *
+ * Returns tBTA_STATUS
+ *
+ ******************************************************************************/
+tBTA_STATUS BTA_EnableBluetooth(tBTA_DM_SEC_CBACK* p_cback) {
+ /* Bluetooth disabling is in progress */
+ if (bta_dm_cb.disabling) return BTA_FAILURE;
+
bta_sys_register(BTA_ID_DM_SEARCH, &bta_dm_search_reg);
+
/* if UUID list is not provided as static data */
bta_sys_eir_register(bta_dm_eir_update_uuid);
- bta_sys_cust_eir_register(bta_dm_eir_update_cust_uuid);
+
+ do_in_main_thread(FROM_HERE, base::Bind(bta_dm_enable, p_cback));
+ return BTA_SUCCESS;
+}
+
+/*******************************************************************************
+ *
+ * Function BTA_DisableBluetooth
+ *
+ * Description Disables bluetooth service. This function is called when
+ * the application no longer needs bluetooth service
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+tBTA_STATUS BTA_DisableBluetooth(void) {
+ do_in_main_thread(FROM_HERE, base::Bind(bta_dm_disable));
+ return BTA_SUCCESS;
}
/** Enables bluetooth device under test mode */
@@ -57,14 +89,29 @@ void BTA_EnableTestMode(void) {
base::Bind(base::IgnoreResult(BTM_EnableTestMode)));
}
+/** Disable bluetooth device under test mode */
+void BTA_DisableTestMode(void) {
+ do_in_main_thread(FROM_HERE, base::Bind(BTM_DeviceReset, nullptr));
+}
+
/** This function sets the Bluetooth name of local device */
void BTA_DmSetDeviceName(char* p_name) {
- std::vector<uint8_t> name(BD_NAME_LEN + 1);
- strlcpy((char*)name.data(), p_name, BD_NAME_LEN + 1);
+ std::vector<uint8_t> name(BD_NAME_LEN);
+ strlcpy((char*)name.data(), p_name, BD_NAME_LEN);
do_in_main_thread(FROM_HERE, base::Bind(bta_dm_set_dev_name, name));
}
+/** This function sets the Bluetooth connectable, discoverable, pairable and
+ * conn paired only modes of local device
+ */
+void BTA_DmSetVisibility(tBTA_DM_DISC disc_mode, tBTA_DM_CONN conn_mode,
+ uint8_t pairable_mode, uint8_t conn_paired_only) {
+ do_in_main_thread(FROM_HERE,
+ base::Bind(bta_dm_set_visibility, disc_mode, conn_mode,
+ pairable_mode, conn_paired_only));
+}
+
/*******************************************************************************
*
* Function BTA_DmSearch
@@ -77,17 +124,16 @@ void BTA_DmSetDeviceName(char* p_name) {
* Returns void
*
******************************************************************************/
-void BTA_DmSearch(tBTA_DM_SEARCH_CBACK* p_cback, bool is_bonding_or_sdp) {
+void BTA_DmSearch(tBTA_DM_INQ* p_dm_inq, tBTA_SERVICE_MASK services,
+ tBTA_DM_SEARCH_CBACK* p_cback) {
tBTA_DM_API_SEARCH* p_msg =
(tBTA_DM_API_SEARCH*)osi_calloc(sizeof(tBTA_DM_API_SEARCH));
- /* Queue request if a device is bonding or performing service discovery */
- if (is_bonding_or_sdp) {
- p_msg->hdr.event = BTA_DM_API_QUEUE_SEARCH_EVT;
- } else {
- p_msg->hdr.event = BTA_DM_API_SEARCH_EVT;
- }
+ p_msg->hdr.event = BTA_DM_API_SEARCH_EVT;
+ memcpy(&p_msg->inq_params, p_dm_inq, sizeof(tBTA_DM_INQ));
+ p_msg->services = services;
p_msg->p_cback = p_cback;
+ p_msg->rs_res = BTA_DM_RS_NONE;
bta_sys_sendmsg(p_msg);
}
@@ -103,23 +149,10 @@ void BTA_DmSearch(tBTA_DM_SEARCH_CBACK* p_cback, bool is_bonding_or_sdp) {
*
******************************************************************************/
void BTA_DmSearchCancel(void) {
- switch (bta_dm_search_get_state()) {
- case BTA_DM_SEARCH_IDLE:
- bta_dm_search_cancel_notify();
- break;
- case BTA_DM_SEARCH_ACTIVE:
- bta_dm_search_set_state(BTA_DM_SEARCH_CANCELLING);
- bta_dm_search_cancel();
- break;
- case BTA_DM_SEARCH_CANCELLING:
- bta_dm_search_clear_queue();
- bta_dm_search_cancel_notify();
- break;
- case BTA_DM_DISCOVER_ACTIVE:
- bta_dm_search_set_state(BTA_DM_SEARCH_CANCELLING);
- bta_dm_search_cancel_notify();
- break;
- }
+ BT_HDR* p_msg = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
+
+ p_msg->event = BTA_DM_API_SEARCH_CANCEL_EVT;
+ bta_sys_sendmsg(p_msg);
}
/*******************************************************************************
@@ -133,28 +166,54 @@ void BTA_DmSearchCancel(void) {
* Returns void
*
******************************************************************************/
-void BTA_DmDiscover(const RawAddress& bd_addr, tBTA_DM_SEARCH_CBACK* p_cback,
- tBT_TRANSPORT transport, bool is_bonding_or_sdp) {
+void BTA_DmDiscover(const RawAddress& bd_addr, tBTA_SERVICE_MASK services,
+ tBTA_DM_SEARCH_CBACK* p_cback, bool sdp_search) {
tBTA_DM_API_DISCOVER* p_msg =
(tBTA_DM_API_DISCOVER*)osi_calloc(sizeof(tBTA_DM_API_DISCOVER));
- if (is_bonding_or_sdp) {
- p_msg->hdr.event = BTA_DM_API_QUEUE_DISCOVER_EVT;
- } else {
- p_msg->hdr.event = BTA_DM_API_DISCOVER_EVT;
- }
+ p_msg->hdr.event = BTA_DM_API_DISCOVER_EVT;
p_msg->bd_addr = bd_addr;
- p_msg->transport = transport;
+ p_msg->services = services;
+ p_msg->p_cback = p_cback;
+ p_msg->sdp_search = sdp_search;
+
+ bta_sys_sendmsg(p_msg);
+}
+
+/*******************************************************************************
+ *
+ * Function BTA_DmDiscoverUUID
+ *
+ * Description This function does service discovery for services of a
+ * peer device
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTA_DmDiscoverUUID(const RawAddress& bd_addr, const Uuid& uuid,
+ tBTA_DM_SEARCH_CBACK* p_cback, bool sdp_search) {
+ tBTA_DM_API_DISCOVER* p_msg =
+ (tBTA_DM_API_DISCOVER*)osi_malloc(sizeof(tBTA_DM_API_DISCOVER));
+
+ p_msg->hdr.event = BTA_DM_API_DISCOVER_EVT;
+ p_msg->bd_addr = bd_addr;
+ p_msg->services = BTA_USER_SERVICE_MASK; // Not exposed at API level
p_msg->p_cback = p_cback;
+ p_msg->sdp_search = sdp_search;
+
+ p_msg->num_uuid = 0;
+ p_msg->p_uuid = NULL;
+ p_msg->uuid = uuid;
bta_sys_sendmsg(p_msg);
}
/** This function initiates a bonding procedure with a peer device */
void BTA_DmBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type) {
- do_in_main_thread(FROM_HERE, base::Bind(bta_dm_bond, bd_addr, addr_type,
- transport, device_type));
+ tBTA_TRANSPORT transport) {
+ do_in_main_thread(FROM_HERE,
+ base::Bind(bta_dm_bond, bd_addr, addr_type, transport));
}
/** This function cancels the bonding procedure with a peer device
@@ -233,12 +292,16 @@ void BTA_DmConfirm(const RawAddress& bd_addr, bool accept) {
*
******************************************************************************/
void BTA_DmAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
- const LinkKey& link_key, uint8_t key_type,
+ const LinkKey& link_key, tBTA_SERVICE_MASK trusted_mask,
+ bool is_trusted, uint8_t key_type, tBTA_IO_CAP io_cap,
uint8_t pin_length) {
std::unique_ptr<tBTA_DM_API_ADD_DEVICE> msg =
std::make_unique<tBTA_DM_API_ADD_DEVICE>();
msg->bd_addr = bd_addr;
+ msg->tm = trusted_mask;
+ msg->is_trusted = is_trusted;
+ msg->io_cap = io_cap;
msg->link_key_known = true;
msg->key_type = key_type;
msg->link_key = link_key;
@@ -250,6 +313,7 @@ void BTA_DmAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
}
memset(msg->bd_name, 0, BD_NAME_LEN + 1);
+ memset(msg->features, 0, sizeof(msg->features));
msg->pin_length = pin_length;
do_in_main_thread(FROM_HERE,
@@ -310,40 +374,6 @@ void BTA_GetEirService(uint8_t* p_eir, size_t eir_len,
/*******************************************************************************
*
- * Function BTA_AddEirUuid
- *
- * Description Request to add a service class UID to the local
- * device's EIR data.
- *
- * Parameters uuid16 - The service class UUID you wish to add
- *
- * Returns void
- *
- ******************************************************************************/
-void BTA_AddEirUuid(uint16_t uuid16) {
- APPL_TRACE_API("%s: %d", __func__, uuid16);
- bta_sys_add_uuid(uuid16);
-}
-
-/*******************************************************************************
- *
- * Function BTA_RemoveEirUuid
- *
- * Description Request to remove a service class UID from the local
- * device's EIR data.
- *
- * Parameters uuid16 - The service class UUID you wish to remove
- *
- * Returns void
- *
- ******************************************************************************/
-void BTA_RemoveEirUuid(uint16_t uuid16) {
- APPL_TRACE_API("%s: %d", __func__, uuid16);
- bta_sys_remove_uuid(uuid16);
-}
-
-/*******************************************************************************
- *
* Function BTA_DmGetConnectionState
*
* Description Returns whether the remote device is currently connected.
@@ -351,7 +381,7 @@ void BTA_RemoveEirUuid(uint16_t uuid16) {
* Returns 0 if the device is NOT connected.
*
******************************************************************************/
-bool BTA_DmGetConnectionState(const RawAddress& bd_addr) {
+uint16_t BTA_DmGetConnectionState(const RawAddress& bd_addr) {
tBTA_DM_PEER_DEVICE* p_dev = bta_dm_find_peer_device(bd_addr);
return (p_dev && p_dev->conn_state == BTA_DM_CONNECTED);
}
@@ -368,7 +398,7 @@ bool BTA_DmGetConnectionState(const RawAddress& bd_addr) {
* Returns BTA_SUCCESS if record set sucessfully, otherwise error code.
*
******************************************************************************/
-tBTA_STATUS BTA_DmSetLocalDiRecord(tSDP_DI_RECORD* p_device_info,
+tBTA_STATUS BTA_DmSetLocalDiRecord(tBTA_DI_RECORD* p_device_info,
uint32_t* p_handle) {
tBTA_STATUS status = BTA_FAILURE;
@@ -405,7 +435,7 @@ tBTA_STATUS BTA_DmSetLocalDiRecord(tSDP_DI_RECORD* p_device_info,
*
******************************************************************************/
void BTA_DmAddBleKey(const RawAddress& bd_addr, tBTA_LE_KEY_VALUE* p_le_key,
- tBTM_LE_KEY_TYPE key_type) {
+ tBTA_LE_KEY_TYPE key_type) {
do_in_main_thread(
FROM_HERE, base::Bind(bta_dm_add_blekey, bd_addr, *p_le_key, key_type));
}
@@ -498,7 +528,7 @@ void BTA_DmBleSecurityGrant(const RawAddress& bd_addr,
* scan_window - scan window
* min_conn_int - minimum preferred connection interval
* max_conn_int - maximum preferred connection interval
- * peripheral_latency - preferred peripheral latency
+ * slave_latency - preferred slave latency
* supervision_tout - preferred supervision timeout
*
*
@@ -507,12 +537,162 @@ void BTA_DmBleSecurityGrant(const RawAddress& bd_addr,
******************************************************************************/
void BTA_DmSetBlePrefConnParams(const RawAddress& bd_addr,
uint16_t min_conn_int, uint16_t max_conn_int,
- uint16_t peripheral_latency,
+ uint16_t slave_latency,
uint16_t supervision_tout) {
do_in_main_thread(
- FROM_HERE,
- base::Bind(bta_dm_ble_set_conn_params, bd_addr, min_conn_int,
- max_conn_int, peripheral_latency, supervision_tout));
+ FROM_HERE, base::Bind(bta_dm_ble_set_conn_params, bd_addr, min_conn_int,
+ max_conn_int, slave_latency, supervision_tout));
+}
+
+/*******************************************************************************
+ *
+ * Function BTA_DmSetBleConnScanParams
+ *
+ * Description This function is called to set scan parameters used in
+ * BLE connection request
+ *
+ * Parameters: scan_interval - scan interval
+ * scan_window - scan window
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTA_DmSetBleConnScanParams(uint32_t scan_interval, uint32_t scan_window) {
+ do_in_main_thread(FROM_HERE, base::Bind(bta_dm_ble_set_conn_scan_params,
+ scan_interval, scan_window));
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_discover_send_msg
+ *
+ * Description This function send discover message to BTA task.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void bta_dm_discover_send_msg(const RawAddress& bd_addr,
+ tBTA_SERVICE_MASK_EXT* p_services,
+ tBTA_DM_SEARCH_CBACK* p_cback,
+ bool sdp_search,
+ tBTA_TRANSPORT transport) {
+ const size_t len =
+ p_services
+ ? (sizeof(tBTA_DM_API_DISCOVER) + sizeof(Uuid) * p_services->num_uuid)
+ : sizeof(tBTA_DM_API_DISCOVER);
+ tBTA_DM_API_DISCOVER* p_msg = (tBTA_DM_API_DISCOVER*)osi_calloc(len);
+
+ p_msg->hdr.event = BTA_DM_API_DISCOVER_EVT;
+ p_msg->bd_addr = bd_addr;
+ p_msg->p_cback = p_cback;
+ p_msg->sdp_search = sdp_search;
+ p_msg->transport = transport;
+
+ if (p_services != NULL) {
+ p_msg->services = p_services->srvc_mask;
+ p_msg->num_uuid = p_services->num_uuid;
+ if (p_services->num_uuid != 0) {
+ p_msg->p_uuid = (Uuid*)(p_msg + 1);
+ memcpy(p_msg->p_uuid, p_services->p_uuid,
+ sizeof(Uuid) * p_services->num_uuid);
+ }
+ }
+
+ bta_sys_sendmsg(p_msg);
+}
+
+/*******************************************************************************
+ *
+ * Function BTA_DmDiscoverByTransport
+ *
+ * Description This function does service discovery on particular transport
+ * for services of a
+ * peer device. When services.num_uuid is 0, it indicates all
+ * GATT based services are to be searched; otherwise a list of
+ * UUID of interested services should be provided through
+ * p_services->p_uuid.
+ *
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTA_DmDiscoverByTransport(const RawAddress& bd_addr,
+ tBTA_SERVICE_MASK_EXT* p_services,
+ tBTA_DM_SEARCH_CBACK* p_cback, bool sdp_search,
+ tBTA_TRANSPORT transport) {
+ bta_dm_discover_send_msg(bd_addr, p_services, p_cback, sdp_search, transport);
+}
+
+/*******************************************************************************
+ *
+ * Function BTA_DmDiscoverExt
+ *
+ * Description This function does service discovery for services of a
+ * peer device. When services.num_uuid is 0, it indicates all
+ * GATT based services are to be searched; other wise a list of
+ * UUID of interested services should be provided through
+ * p_services->p_uuid.
+ *
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTA_DmDiscoverExt(const RawAddress& bd_addr,
+ tBTA_SERVICE_MASK_EXT* p_services,
+ tBTA_DM_SEARCH_CBACK* p_cback, bool sdp_search) {
+ bta_dm_discover_send_msg(bd_addr, p_services, p_cback, sdp_search,
+ BTA_TRANSPORT_UNKNOWN);
+}
+
+/*******************************************************************************
+ *
+ * Function BTA_DmSearchExt
+ *
+ * Description This function searches for peer Bluetooth devices. It
+ * performs an inquiry and gets the remote name for devices.
+ * Service discovery is done if services is non zero
+ *
+ * Parameters p_dm_inq: inquiry conditions
+ * p_services: if service is not empty, service discovery will
+ * be done. For all GATT based service conditions,
+ * put num_uuid, and p_uuid is the pointer to the
+ * list of UUID values.
+ * p_cback: callback function when search is completed.
+ *
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTA_DmSearchExt(tBTA_DM_INQ* p_dm_inq, tBTA_SERVICE_MASK_EXT* p_services,
+ tBTA_DM_SEARCH_CBACK* p_cback) {
+ const size_t len =
+ p_services
+ ? (sizeof(tBTA_DM_API_SEARCH) + sizeof(Uuid) * p_services->num_uuid)
+ : sizeof(tBTA_DM_API_SEARCH);
+ tBTA_DM_API_SEARCH* p_msg = (tBTA_DM_API_SEARCH*)osi_calloc(len);
+
+ p_msg->hdr.event = BTA_DM_API_SEARCH_EVT;
+ memcpy(&p_msg->inq_params, p_dm_inq, sizeof(tBTA_DM_INQ));
+ p_msg->p_cback = p_cback;
+ p_msg->rs_res = BTA_DM_RS_NONE;
+
+ if (p_services != NULL) {
+ p_msg->services = p_services->srvc_mask;
+ p_msg->num_uuid = p_services->num_uuid;
+
+ if (p_services->num_uuid != 0) {
+ p_msg->p_uuid = (Uuid*)(p_msg + 1);
+ memcpy(p_msg->p_uuid, p_services->p_uuid,
+ sizeof(Uuid) * p_services->num_uuid);
+ } else {
+ p_msg->p_uuid = NULL;
+ }
+ }
+
+ bta_sys_sendmsg(p_msg);
}
/*******************************************************************************
@@ -527,7 +707,7 @@ void BTA_DmSetBlePrefConnParams(const RawAddress& bd_addr,
* [0x0004 ~ 0x4000]
* max_int - maximum connection interval,
* [0x0004 ~ 0x4000]
- * latency - peripheral latency [0 ~ 500]
+ * latency - slave latency [0 ~ 500]
* timeout - supervision timeout [0x000a ~ 0xc80]
*
* Returns void
@@ -579,9 +759,10 @@ void BTA_DmBleGetEnergyInfo(tBTA_BLE_ENERGY_INFO_CBACK* p_cmpl_cback) {
}
/** This function is to set maximum LE data packet size */
-void BTA_DmBleRequestMaxTxDataLength(const RawAddress& remote_device) {
- do_in_main_thread(FROM_HERE,
- base::Bind(bta_dm_ble_set_data_length, remote_device));
+void BTA_DmBleSetDataLength(const RawAddress& remote_device,
+ uint16_t tx_data_length) {
+ do_in_main_thread(FROM_HERE, base::Bind(bta_dm_ble_set_data_length,
+ remote_device, tx_data_length));
}
/*******************************************************************************
@@ -606,9 +787,9 @@ void BTA_DmBleRequestMaxTxDataLength(const RawAddress& remote_device) {
* Returns void
*
******************************************************************************/
-void BTA_DmSetEncryption(const RawAddress& bd_addr, tBT_TRANSPORT transport,
+void BTA_DmSetEncryption(const RawAddress& bd_addr, tBTA_TRANSPORT transport,
tBTA_DM_ENCRYPT_CBACK* p_callback,
- tBTM_BLE_SEC_ACT sec_act) {
+ tBTA_DM_BLE_SEC_ACT sec_act) {
APPL_TRACE_API("%s", __func__);
do_in_main_thread(FROM_HERE, base::Bind(bta_dm_set_encryption, bd_addr,
transport, p_callback, sec_act));
@@ -628,7 +809,7 @@ void BTA_DmSetEncryption(const RawAddress& bd_addr, tBT_TRANSPORT transport,
*
******************************************************************************/
void BTA_DmCloseACL(const RawAddress& bd_addr, bool remove_dev,
- tBT_TRANSPORT transport) {
+ tBTA_TRANSPORT transport) {
do_in_main_thread(
FROM_HERE, base::Bind(bta_dm_close_acl, bd_addr, remove_dev, transport));
}
@@ -665,3 +846,29 @@ extern void BTA_DmBleObserve(bool start, uint8_t duration,
*
******************************************************************************/
void BTA_VendorInit(void) { APPL_TRACE_API("BTA_VendorInit"); }
+
+/*******************************************************************************
+ *
+ * Function BTA_VendorCleanup
+ *
+ * Description This function frees up Broadcom specific VS specific dynamic
+ * memory
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTA_VendorCleanup(void) {
+ tBTM_BLE_VSC_CB cmn_ble_vsc_cb;
+ BTM_BleGetVendorCapabilities(&cmn_ble_vsc_cb);
+
+ if (cmn_ble_vsc_cb.max_filter > 0) {
+ btm_ble_adv_filter_cleanup();
+#if (BLE_PRIVACY_SPT == TRUE)
+ btm_ble_resolving_list_cleanup();
+#endif
+ }
+
+ if (cmn_ble_vsc_cb.tot_scan_results_strg > 0) btm_ble_batchscan_cleanup();
+
+ if (cmn_ble_vsc_cb.adv_inst_max > 0) btm_ble_multi_adv_cleanup();
+}
diff --git a/bta/dm/bta_dm_cfg.cc b/bta/dm/bta_dm_cfg.cc
index d5c757519..e1e2cadfb 100644
--- a/bta/dm/bta_dm_cfg.cc
+++ b/bta/dm/bta_dm_cfg.cc
@@ -23,23 +23,32 @@
*
******************************************************************************/
-#include <cstdint>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/dm/bta_dm_int.h"
-#include "bta/include/bta_api.h"
-#include "bta/include/bta_hh_api.h"
-#include "bta/include/bta_jv_api.h"
-#include "bta/sys/bta_sys.h"
-#include "types/raw_address.h"
+#include <stddef.h>
+
+#include "bt_target.h"
+#include "bta_api.h"
+#include "bta_dm_int.h"
+#include "bta_hh_api.h"
+#include "bta_jv_api.h"
+#include "bta_sys.h"
+
+#ifndef BTA_DM_LINK_POLICY_SETTINGS
+#define BTA_DM_LINK_POLICY_SETTINGS \
+ (HCI_ENABLE_MASTER_SLAVE_SWITCH | HCI_ENABLE_HOLD_MODE | \
+ HCI_ENABLE_SNIFF_MODE | HCI_ENABLE_PARK_MODE)
+#endif
/* page timeout in 625uS */
#ifndef BTA_DM_PAGE_TIMEOUT
#define BTA_DM_PAGE_TIMEOUT 8192
#endif
-/* TRUE to avoid scatternet when av is streaming (be the central) */
+/* link supervision timeout in 625uS (5 secs) */
+#ifndef BTA_DM_LINK_TIMEOUT
+#define BTA_DM_LINK_TIMEOUT 8000
+#endif
+
+/* TRUE to avoid scatternet when av is streaming (be the master) */
#ifndef BTA_DM_AVOID_SCATTER_A2DP
#define BTA_DM_AVOID_SCATTER_A2DP TRUE
#endif
@@ -55,9 +64,13 @@
const tBTA_DM_CFG bta_dm_cfg = {
/* mobile phone COD */
BTA_DM_COD,
+ /* link policy settings */
+ BTA_DM_LINK_POLICY_SETTINGS,
/* page timeout in 625uS */
BTA_DM_PAGE_TIMEOUT,
- /* true to avoid scatternet when av is streaming (be the central) */
+ /* link supervision timeout in 625uS*/
+ BTA_DM_LINK_TIMEOUT,
+ /* true to avoid scatternet when av is streaming (be the master) */
BTA_DM_AVOID_SCATTER_A2DP};
#ifndef BTA_DM_SCATTERNET
@@ -70,9 +83,14 @@ const tBTA_DM_CFG bta_dm_cfg = {
#define BTA_HH_ROLE BTA_ANY_ROLE
#endif
+#ifndef BTA_AV_ROLE
+/* By default, AV role (backward BTA_MASTER_ROLE_PREF) */
+#define BTA_AV_ROLE BTA_MASTER_ROLE_PREF
+#endif
+
#ifndef BTA_PANU_ROLE
-/* By default, AV role (backward BTA_CENTRAL_ROLE_PREF) */
-#define BTA_PANU_ROLE BTA_PERIPHERAL_ROLE_ONLY
+/* By default, AV role (backward BTA_MASTER_ROLE_PREF) */
+#define BTA_PANU_ROLE BTA_SLAVE_ROLE_ONLY
#endif
#define BTA_DM_NUM_RM_ENTRY 6
@@ -89,10 +107,10 @@ const tBTA_DM_RM bta_dm_rm_cfg[] = {
{BTA_ID_SYS, BTA_DM_NUM_RM_ENTRY, BTA_DM_SCATTERNET},
{BTA_ID_PAN, BTUI_PAN_ID_NAP, BTA_ANY_ROLE},
{BTA_ID_PAN, BTUI_PAN_ID_GN, BTA_ANY_ROLE},
- {BTA_ID_PAN, BTA_APP_ID_PAN_MULTI, BTA_CENTRAL_ROLE_ONLY},
+ {BTA_ID_PAN, BTA_APP_ID_PAN_MULTI, BTA_MASTER_ROLE_ONLY},
{BTA_ID_PAN, BTUI_PAN_ID_PANU, BTA_PANU_ROLE},
{BTA_ID_HH, BTA_ALL_APP_ID, BTA_HH_ROLE},
- {BTA_ID_AV, BTA_ALL_APP_ID, BTA_CENTRAL_ROLE_PREF}};
+ {BTA_ID_AV, BTA_ALL_APP_ID, BTA_AV_ROLE}};
const tBTA_DM_CFG* p_bta_dm_cfg = &bta_dm_cfg;
@@ -112,6 +130,7 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_CFG
{BTA_ID_CG, BTA_ALL_APP_ID, 1}, /* cg resue ct spec table */
{BTA_ID_DG, BTA_ALL_APP_ID, 2}, /* dg spec table */
{BTA_ID_AV, BTA_ALL_APP_ID, 4}, /* av spec table */
+ {BTA_ID_AVK, BTA_ALL_APP_ID, 13}, /* avk spec table */
{BTA_ID_FTC, BTA_ALL_APP_ID, 7}, /* ftc spec table */
{BTA_ID_FTS, BTA_ALL_APP_ID, 8}, /* fts spec table */
{BTA_ID_HD, BTA_ALL_APP_ID, 3}, /* hd spec table */
@@ -139,7 +158,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_CFG
tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* AG : 0 */
{(BTA_DM_PM_SNIFF | BTA_DM_PM_PARK), /* allow park & sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_SNIFF_A2DP_IDX, 7000},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open sniff */
@@ -159,7 +180,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* CT, CG : 1 */
{(BTA_DM_PM_SNIFF | BTA_DM_PM_PARK), /* allow park & sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_PARK, 5000},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open park */
@@ -178,7 +201,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* DG, PBC : 2 */
{(BTA_DM_PM_ACTIVE), /* no power saving mode allowed */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_SNIFF, 5000},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open active */
@@ -195,7 +220,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* HD : 3 */
{(BTA_DM_PM_SNIFF | BTA_DM_PM_PARK), /* allow park & sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR3), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_SNIFF_HD_ACTIVE_IDX, 5000},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open sniff */
@@ -214,7 +241,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* AV : 4 */
{(BTA_DM_PM_SNIFF), /* allow sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_SNIFF_A2DP_IDX, 7000},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open sniff */
@@ -232,7 +261,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* HH for joysticks and gamepad : 5 */
{(BTA_DM_PM_SNIFF | BTA_DM_PM_PARK), /* allow park & sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR1), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_SNIFF6, BTA_DM_PM_HH_OPEN_DELAY},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open sniff */
@@ -252,7 +283,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* HH : 6 */
{(BTA_DM_PM_SNIFF | BTA_DM_PM_PARK), /* allow park & sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR1), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_SNIFF_HH_OPEN_IDX, BTA_DM_PM_HH_OPEN_DELAY},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open sniff */
@@ -272,7 +305,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* FTC, OPC, JV : 7 */
{(BTA_DM_PM_SNIFF), /* allow sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_ACTIVE, 0},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open active */
@@ -290,7 +325,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* FTS, PBS, OPS, MSE, BTA_JV_PM_ID_1 : 8 */
{(BTA_DM_PM_SNIFF), /* allow sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_ACTIVE, 0},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open active */
@@ -308,7 +345,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* HL : 9 */
{(BTA_DM_PM_SNIFF), /* allow sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_SNIFF_A2DP_IDX, 5000},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open sniff */
@@ -327,7 +366,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* PANU : 10 */
{(BTA_DM_PM_SNIFF), /* allow sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_ACTIVE, 0},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open active */
@@ -345,7 +386,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* NAP : 11 */
{(BTA_DM_PM_SNIFF), /* allow sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_ACTIVE, 0},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open active */
@@ -364,7 +407,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* HS : 12 */
{(BTA_DM_PM_SNIFF | BTA_DM_PM_PARK), /* allow park & sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_SNIFF, 7000},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open sniff */
@@ -383,7 +428,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* AVK : 13 */
{(BTA_DM_PM_SNIFF), /* allow sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_SNIFF, 3000},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open sniff */
@@ -401,7 +448,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* GATTC : 14 */
,
{(BTA_DM_PM_SNIFF | BTA_DM_PM_PARK), /* allow park & sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_SNIFF_A2DP_IDX, 10000},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open active */
@@ -419,7 +468,9 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTA_DM_PM_SPEC bta_dm_pm_spec[BTA_DM_NUM_PM_SPEC] = {
/* GATTS : 15 */
,
{(BTA_DM_PM_SNIFF | BTA_DM_PM_PARK), /* allow park & sniff */
+#if (BTM_SSR_INCLUDED == TRUE)
(BTA_DM_PM_SSR2), /* the SSR entry */
+#endif
{
{{BTA_DM_PM_NO_PREF, 0},
{BTA_DM_PM_NO_ACTION, 0}}, /* conn open active */
@@ -527,20 +578,21 @@ tBTA_DM_PM_TYPE_QUALIFIER tBTM_PM_PWR_MD bta_dm_pm_md[] = {
/* the smaller of the SSR max latency wins.
* the entries in this table must be from highest latency (biggest interval) to
* lowest latency */
+#if (BTM_SSR_INCLUDED == TRUE)
tBTA_DM_SSR_SPEC bta_dm_ssr_spec[] = {
/*max_lat, min_rmt_to, min_loc_to*/
- {0, 0, 0, "no_ssr"}, /* BTA_DM_PM_SSR0 - do not use SSR */
+ {0, 0, 0}, /* BTA_DM_PM_SSR0 - do not use SSR */
/* BTA_DM_PM_SSR1 - HH, can NOT share entry with any other profile, seting
default max latency and min remote timeout as 0, and always read
individual device preference from HH module */
- {0, 0, 2, "hid_host"},
- {1200, 2, 2, "sniff_capable"}, /* BTA_DM_PM_SSR2 - others (as long as sniff
- is allowed)*/
- {360, 160, 1600, "hid_device"}, /* BTA_DM_PM_SSR3 - HD */
- {1200, 65534, 65534, "a2dp"} /* BTA_DM_PM_SSR4 - A2DP streaming */
+ {0, 0, 2},
+ {1200, 2, 2}, /* BTA_DM_PM_SSR2 - others (as long as sniff is allowed)*/
+ {360, 160, 1600}, /* BTA_DM_PM_SSR3 - HD */
+ {1200, 65534, 65534} /* BTA_DM_PM_SSR4 - A2DP streaming */
};
tBTA_DM_SSR_SPEC* p_bta_dm_ssr_spec = &bta_dm_ssr_spec[0];
+#endif
const tBTA_DM_PM_CFG* p_bta_dm_pm_cfg = &bta_dm_pm_cfg[0];
const tBTA_DM_PM_SPEC* p_bta_dm_pm_spec = &bta_dm_pm_spec[0];
diff --git a/bta/dm/bta_dm_ci.cc b/bta/dm/bta_dm_ci.cc
index ea815247a..45784c1e4 100644
--- a/bta/dm/bta_dm_ci.cc
+++ b/bta/dm/bta_dm_ci.cc
@@ -21,13 +21,34 @@
* This is the API implementation file for the BTA device manager.
*
******************************************************************************/
+#include "bta_dm_ci.h"
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_dm_int.h"
+#include "bta_sys.h"
+#include "stack/include/btu.h"
+
#include <base/bind.h>
#include <memory>
-#include "bta/dm/bta_dm_int.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "types/raw_address.h"
+/*******************************************************************************
+ *
+ * Function bta_dm_ci_io_req
+ *
+ * Description This function must be called in response to function
+ * bta_dm_co_io_req(), if *p_oob_data to BTA_OOB_UNKNOWN
+ * by bta_dm_co_io_req().
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_dm_ci_io_req(const RawAddress& bd_addr, tBTA_IO_CAP io_cap,
+ tBTA_OOB_DATA oob_data, tBTA_AUTH_REQ auth_req)
+
+{
+ do_in_main_thread(FROM_HERE, base::Bind(bta_dm_ci_io_req_act, bd_addr, io_cap,
+ oob_data, auth_req));
+}
/*******************************************************************************
*
diff --git a/bta/dm/bta_dm_int.h b/bta/dm/bta_dm_int.h
index 1f5952e7b..05abd8f94 100644
--- a/bta/dm/bta_dm_int.h
+++ b/bta/dm/bta_dm_int.h
@@ -24,22 +24,11 @@
#ifndef BTA_DM_INT_H
#define BTA_DM_INT_H
-#include <base/strings/stringprintf.h>
#include <memory>
-#include <string>
+#include "bt_target.h"
+#include "bta_sys.h"
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_api.h"
-#include "bta/include/bta_gatt_api.h"
-#include "bta/sys/bta_sys.h"
-#include "main/shim/dumpsys.h"
-
-#ifndef CASE_RETURN_TEXT
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-#endif
+#include "bta_gatt_api.h"
/*****************************************************************************
* Constants and data types
@@ -60,32 +49,58 @@
enum {
/* DM search API events */
BTA_DM_API_SEARCH_EVT = BTA_SYS_EVT_START(BTA_ID_DM_SEARCH),
+ BTA_DM_API_SEARCH_CANCEL_EVT,
BTA_DM_API_DISCOVER_EVT,
BTA_DM_INQUIRY_CMPL_EVT,
BTA_DM_REMT_NAME_EVT,
BTA_DM_SDP_RESULT_EVT,
BTA_DM_SEARCH_CMPL_EVT,
BTA_DM_DISCOVERY_RESULT_EVT,
- BTA_DM_DISC_CLOSE_TOUT_EVT,
- BTA_DM_API_QUEUE_SEARCH_EVT,
- BTA_DM_API_QUEUE_DISCOVER_EVT
+ BTA_DM_API_DI_DISCOVER_EVT,
+ BTA_DM_DISC_CLOSE_TOUT_EVT
+
};
-/* data type for BTA_DM_API_SEARCH_EVT and BTA_DM_API_QUEUE_SEARCH_EVT */
+enum {
+ BTA_DM_RS_NONE, /* straight API call */
+ BTA_DM_RS_OK, /* the role switch result - successful */
+ BTA_DM_RS_FAIL /* the role switch result - failed */
+};
+typedef uint8_t tBTA_DM_RS_RES;
+
+/* data type for BTA_DM_API_SEARCH_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
+ tBTA_DM_INQ inq_params;
tBTA_SERVICE_MASK services;
tBTA_DM_SEARCH_CBACK* p_cback;
+ tBTA_DM_RS_RES rs_res;
+ uint8_t num_uuid;
+ bluetooth::Uuid* p_uuid;
} tBTA_DM_API_SEARCH;
-/* data type for BTA_DM_API_DISCOVER_EVT and BTA_DM_API_QUEUE_DISCOVER_EVT */
+/* data type for BTA_DM_API_DISCOVER_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress bd_addr;
+ tBTA_SERVICE_MASK services;
tBTA_DM_SEARCH_CBACK* p_cback;
- tBT_TRANSPORT transport;
+ bool sdp_search;
+ tBTA_TRANSPORT transport;
+ uint8_t num_uuid;
+ bluetooth::Uuid* p_uuid;
+ bluetooth::Uuid uuid;
} tBTA_DM_API_DISCOVER;
+/* data type for BTA_DM_API_DI_DISC_EVT */
+typedef struct {
+ BT_HDR hdr;
+ RawAddress bd_addr;
+ tBTA_DISCOVERY_DB* p_sdp_db;
+ uint32_t len;
+ tBTA_DM_SEARCH_CBACK* p_cback;
+} tBTA_DM_API_DI_DISC;
+
typedef struct {
RawAddress bd_addr;
bool accept;
@@ -94,11 +109,11 @@ typedef struct {
} tBTA_DM_API_PIN_REPLY;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress bd_addr;
- tBTM_IO_CAP io_cap;
- tBTM_OOB_DATA oob_data;
- tBTM_AUTH_REQ auth_req;
+ tBTA_IO_CAP io_cap;
+ tBTA_OOB_DATA oob_data;
+ tBTA_AUTH_REQ auth_req;
} tBTA_DM_CI_IO_REQ;
typedef struct {
@@ -110,25 +125,25 @@ typedef struct {
/* data type for BTA_DM_REMT_NAME_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_DM_SEARCH result;
} tBTA_DM_REM_NAME;
/* data type for tBTA_DM_DISC_RESULT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_DM_SEARCH result;
} tBTA_DM_DISC_RESULT;
/* data type for BTA_DM_INQUIRY_CMPL_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint8_t num;
} tBTA_DM_INQUIRY_CMPL;
/* data type for BTA_DM_SDP_RESULT_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint16_t sdp_result;
} tBTA_DM_SDP_RESULT;
@@ -136,22 +151,27 @@ typedef struct {
RawAddress bd_addr;
DEV_CLASS dc;
LinkKey link_key;
+ tBTA_SERVICE_MASK tm;
+ bool is_trusted;
uint8_t key_type;
+ tBTA_IO_CAP io_cap;
bool link_key_known;
bool dc_known;
BD_NAME bd_name;
+ uint8_t
+ features[BTA_FEATURE_BYTES_PER_PAGE * (BTA_EXT_FEATURES_PAGE_MAX + 1)];
uint8_t pin_length;
} tBTA_DM_API_ADD_DEVICE;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
bool enable;
} tBTA_DM_API_BLE_FEATURE;
/* union of all data types */
typedef union {
/* GKI event buffer header */
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_DM_API_SEARCH search;
@@ -165,88 +185,52 @@ typedef union {
tBTA_DM_SDP_RESULT sdp_event;
+ tBTA_DM_API_DI_DISC di_disc;
+
} tBTA_DM_MSG;
#define BTA_DM_NUM_PEER_DEVICE 7
-typedef enum : uint8_t {
- BTA_DM_NOT_CONNECTED = 0,
- BTA_DM_CONNECTED = 1,
- BTA_DM_UNPAIRING = 2,
-} tBTA_DM_CONN_STATE;
-
-inline std::string bta_conn_state_text(tBTA_DM_CONN_STATE state) {
- switch (state) {
- CASE_RETURN_TEXT(BTA_DM_NOT_CONNECTED);
- CASE_RETURN_TEXT(BTA_DM_CONNECTED);
- CASE_RETURN_TEXT(BTA_DM_UNPAIRING);
- default:
- return std::string("UNKNOWN");
- }
-}
-
-typedef enum : uint8_t {
- BTA_DM_DI_NONE = 0x00, /* nothing special */
- BTA_DM_DI_SET_SNIFF = 0x01, /* set this bit if call BTM_SetPowerMode(sniff) */
- BTA_DM_DI_INT_SNIFF = 0x02, /* set this bit if call BTM_SetPowerMode(sniff) &
- enter sniff mode */
- BTA_DM_DI_ACP_SNIFF = 0x04, /* set this bit if peer init sniff */
- BTA_DM_DI_UNUSED = 0x08,
- BTA_DM_DI_USE_SSR = 0x10, /* set this bit if ssr is supported for this link */
- BTA_DM_DI_AV_ACTIVE = 0x20, /* set this bit if AV is active for this link */
-} tBTA_DM_DEV_INFO_BITMASK;
+#define BTA_DM_NOT_CONNECTED 0
+#define BTA_DM_CONNECTED 1
+#define BTA_DM_UNPAIRING 2
+typedef uint8_t tBTA_DM_CONN_STATE;
+
+#define BTA_DM_DI_NONE 0x00 /* nothing special */
+#define BTA_DM_DI_USE_SSR \
+ 0x10 /* set this bit if ssr is supported for this link */
+#define BTA_DM_DI_AV_ACTIVE \
+ 0x20 /* set this bit if AV is active for this link */
+#define BTA_DM_DI_SET_SNIFF \
+ 0x01 /* set this bit if call BTM_SetPowerMode(sniff) */
+#define BTA_DM_DI_INT_SNIFF \
+ 0x02 /* set this bit if call BTM_SetPowerMode(sniff) & enter sniff mode */
+#define BTA_DM_DI_ACP_SNIFF 0x04 /* set this bit if peer init sniff */
typedef uint8_t tBTA_DM_DEV_INFO;
-inline std::string device_info_text(tBTA_DM_DEV_INFO info) {
- const char* const device_info_text[] = {
- ":set_sniff", ":int_sniff", ":acp_sniff",
- ":unused", ":use_ssr", ":av_active",
- };
-
- std::string s = base::StringPrintf("0x%02x", info);
- if (info == BTA_DM_DI_NONE) return s + std::string(":none");
- for (size_t i = 0; i < sizeof(device_info_text) / sizeof(device_info_text[0]);
- i++) {
- if (info & (1u << i)) s += std::string(device_info_text[i]);
- }
- return s;
-}
-
/* set power mode request type */
#define BTA_DM_PM_RESTART 1
#define BTA_DM_PM_NEW_REQ 2
#define BTA_DM_PM_EXECUTE 3
typedef uint8_t tBTA_DM_PM_REQ;
-struct sBTA_DM_PEER_DEVICE {
+typedef struct {
RawAddress peer_bdaddr;
+ uint16_t link_policy;
tBTA_DM_CONN_STATE conn_state;
tBTA_PREF_ROLES pref_role;
bool in_use;
-
- private:
- friend void bta_dm_acl_up(const RawAddress& bd_addr, tBT_TRANSPORT transport);
- friend void bta_dm_pm_btm_status(const RawAddress& bd_addr,
- tBTM_PM_STATUS status, uint16_t value,
- tHCI_STATUS hci_status);
- friend void bta_dm_pm_sniff(struct sBTA_DM_PEER_DEVICE* p_peer_dev,
- uint8_t index);
- friend void bta_dm_rm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
- uint8_t app_id, const RawAddress& peer_addr);
- friend void handle_remote_features_complete(const RawAddress& bd_addr);
tBTA_DM_DEV_INFO info;
-
- public:
- tBTA_DM_DEV_INFO Info() const { return info; }
-
tBTA_DM_ENCRYPT_CBACK* p_encrypt_cback;
+#if (BTM_SSR_INCLUDED == TRUE)
tBTM_PM_STATUS prev_low; /* previous low power mode used */
+#endif
tBTA_DM_PM_ACTION pm_mode_attempted;
tBTA_DM_PM_ACTION pm_mode_failed;
bool remove_dev_pending;
+ uint16_t conn_handle;
tBT_TRANSPORT transport;
-};
-typedef struct sBTA_DM_PEER_DEVICE tBTA_DM_PEER_DEVICE;
+} tBTA_DM_PEER_DEVICE;
/* structure to store list of
active connections */
@@ -263,13 +247,6 @@ typedef struct {
tBTA_SYS_CONN_STATUS state;
bool new_request;
- std::string ToString() const {
- return base::StringPrintf(
- "peer:%s sys_name:%s app_id:%hhu state:%s new:request:%s",
- PRIVATE_ADDRESS(peer_bdaddr), BtaIdSysText(id).c_str(), app_id,
- bta_sys_conn_status_text(state).c_str(), logbool(new_request).c_str());
- }
-
} tBTA_DM_SRVCS;
#ifndef BTA_DM_NUM_CONN_SRVS
@@ -316,22 +293,31 @@ typedef struct {
alarm_t* disable_timer;
uint32_t wbt_sdp_handle; /* WIDCOMM Extensions SDP record handle */
uint8_t wbt_scn; /* WIDCOMM Extensions SCN */
- uint8_t num_central_only;
+ uint8_t num_master_only;
uint8_t pm_id;
tBTA_PM_TIMER pm_timer[BTA_DM_NUM_PM_TIMER];
+ uint32_t
+ role_policy_mask; /* the bits set indicates the modules that wants to
+ remove role switch from the default link policy */
+ uint16_t cur_policy; /* current default link policy */
+ uint16_t rs_event; /* the event waiting for role switch */
uint8_t cur_av_count; /* current AV connecions */
bool disable_pair_mode; /* disable pair mode or not */
bool conn_paired_only; /* allow connectable to paired device only or not */
tBTA_DM_API_SEARCH search_msg;
+ uint16_t page_scan_interval;
+ uint16_t page_scan_window;
+ uint16_t inquiry_scan_interval;
+ uint16_t inquiry_scan_window;
/* Storage for pin code request parameters */
RawAddress pin_bd_addr;
DEV_CLASS pin_dev_class;
tBTA_DM_SEC_EVT pin_evt;
- tBTM_IO_CAP loc_io_caps; /* IO Capabilities of local device */
- tBTM_IO_CAP rmt_io_caps; /* IO Capabilities of remote device */
- tBTM_AUTH_REQ loc_auth_req; /* Authentication required for local device */
- tBTM_AUTH_REQ rmt_auth_req;
+ tBTA_IO_CAP loc_io_caps; /* IO Capabilities of local device */
+ tBTA_IO_CAP rmt_io_caps; /* IO Capabilities of remote device */
+ tBTA_AUTH_REQ loc_auth_req; /* Authentication required for local device */
+ tBTA_AUTH_REQ rmt_auth_req;
uint32_t num_val; /* the numeric value for comparison. If just_works, do not
show this number to UI */
bool just_works; /* true, if "Just Works" association model */
@@ -339,7 +325,7 @@ typedef struct {
/* store UUID list for EIR */
uint32_t eir_uuid[BTM_EIR_SERVICE_ARRAY_SIZE];
#if (BTA_EIR_SERVER_NUM_CUSTOM_UUID > 0)
- tBTA_CUSTOM_UUID bta_custom_uuid[BTA_EIR_SERVER_NUM_CUSTOM_UUID];
+ bluetooth::Uuid custom_uuid[BTA_EIR_SERVER_NUM_CUSTOM_UUID];
#endif
#endif
@@ -363,18 +349,25 @@ typedef struct {
BD_NAME peer_name;
alarm_t* search_timer;
uint8_t service_index;
- tBTA_DM_MSG* p_pending_search;
- fixed_queue_t* pending_discovery_queue;
+ tBTA_DM_MSG* p_search_queue; /* search or discover commands during search
+ cancel stored here */
bool wait_disc;
bool sdp_results;
bluetooth::Uuid uuid;
uint8_t peer_scn;
- tBT_TRANSPORT transport;
+ bool sdp_search;
+ bool cancel_pending; /* inquiry cancel is pending */
+ tBTA_TRANSPORT transport;
tBTA_DM_SEARCH_CBACK* p_scan_cback;
tGATT_IF client_if;
+ uint8_t num_uuid;
+ bluetooth::Uuid* p_srvc_uuid;
uint8_t uuid_to_search;
bool gatt_disc_active;
uint16_t conn_id;
+ uint8_t* p_ble_rawdata;
+ uint32_t ble_raw_size;
+ uint32_t ble_raw_used;
alarm_t* gatt_close_timer; /* GATT channel close delay timer */
RawAddress pending_close_bda; /* pending GATT channel remote device address */
@@ -382,6 +375,7 @@ typedef struct {
/* DI control block */
typedef struct {
+ tSDP_DISCOVERY_DB* p_di_db; /* pointer to the DI discovery database */
uint8_t di_num; /* total local DI record number */
uint32_t di_handle[BTA_DI_NUM_MAX]; /* local DI record handle, the first one
is primary record */
@@ -399,9 +393,12 @@ enum {
typedef struct {
DEV_CLASS dev_class; /* local device class */
+ uint16_t
+ policy_settings; /* link policy setting hold, sniff, park, MS switch */
uint16_t page_timeout; /* timeout for page in slots */
+ uint16_t link_timeout; /* link supervision timeout in slots */
bool avoid_scatter; /* true to avoid scatternet when av is streaming (be the
- central) */
+ master) */
} tBTA_DM_CFG;
@@ -432,7 +429,9 @@ typedef struct {
typedef struct {
uint8_t allow_mask; /* mask of sniff/hold/park modes to allow */
+#if (BTM_SSR_INCLUDED == TRUE)
uint8_t ssr; /* set SSR on conn open/unpark */
+#endif
tBTA_DM_PM_ACTN actn_tbl[BTA_DM_PM_NUM_EVTS][2];
} tBTA_DM_PM_SPEC;
@@ -441,7 +440,6 @@ typedef struct {
uint16_t max_lat;
uint16_t min_rmt_to;
uint16_t min_loc_to;
- const char* name{nullptr};
} tBTA_DM_SSR_SPEC;
typedef struct {
@@ -455,7 +453,9 @@ extern const uint16_t bta_service_id_to_uuid_lkup_tbl[];
extern const tBTA_DM_PM_CFG* p_bta_dm_pm_cfg;
extern const tBTA_DM_PM_SPEC* p_bta_dm_pm_spec;
extern const tBTM_PM_PWR_MD* p_bta_dm_pm_md;
+#if (BTM_SSR_INCLUDED == TRUE)
extern tBTA_DM_SSR_SPEC* p_bta_dm_ssr_spec;
+#endif
/* update dynamic BRCM Aware EIR data */
extern const tBTA_DM_EIR_CONF bta_dm_eir_cfg;
@@ -470,32 +470,31 @@ extern tBTA_DM_SEARCH_CB bta_dm_search_cb;
/* DI control block */
extern tBTA_DM_DI_CB bta_dm_di_cb;
-extern bool bta_dm_search_sm_execute(BT_HDR_RIGID* p_msg);
+extern bool bta_dm_search_sm_execute(BT_HDR* p_msg);
extern void bta_dm_search_sm_disable(void);
extern void bta_dm_enable(tBTA_DM_SEC_CBACK*);
extern void bta_dm_disable();
extern void bta_dm_init_cb(void);
-extern void bta_dm_deinit_cb(void);
extern void bta_dm_set_dev_name(const std::vector<uint8_t>&);
-extern void bta_dm_set_visibility(tBTA_DM_DISC, tBTA_DM_CONN);
+extern void bta_dm_set_visibility(tBTA_DM_DISC, tBTA_DM_CONN, uint8_t, uint8_t);
extern void bta_dm_set_scan_config(tBTA_DM_MSG* p_data);
extern void bta_dm_vendor_spec_command(tBTA_DM_MSG* p_data);
-extern void bta_dm_bond(const RawAddress&, tBLE_ADDR_TYPE, tBT_TRANSPORT, int);
+extern void bta_dm_bond(const RawAddress&, tBLE_ADDR_TYPE, tBTA_TRANSPORT);
extern void bta_dm_bond_cancel(const RawAddress&);
extern void bta_dm_pin_reply(std::unique_ptr<tBTA_DM_API_PIN_REPLY> msg);
extern void bta_dm_add_device(std::unique_ptr<tBTA_DM_API_ADD_DEVICE> msg);
extern void bta_dm_remove_device(const RawAddress& bd_addr);
-extern void bta_dm_close_acl(const RawAddress&, bool, tBT_TRANSPORT);
+extern void bta_dm_close_acl(const RawAddress&, bool, tBTA_TRANSPORT);
extern void bta_dm_pm_btm_status(const RawAddress&, tBTM_PM_STATUS, uint16_t,
- tHCI_STATUS);
+ uint8_t);
extern void bta_dm_pm_timer(const RawAddress&, tBTA_DM_PM_ACTION);
extern void bta_dm_add_ampkey(tBTA_DM_MSG* p_data);
extern void bta_dm_add_blekey(const RawAddress& bd_addr,
tBTA_LE_KEY_VALUE blekey,
- tBTM_LE_KEY_TYPE key_type);
+ tBTA_LE_KEY_TYPE key_type);
extern void bta_dm_add_ble_device(const RawAddress& bd_addr,
tBLE_ADDR_TYPE addr_type,
tBT_DEVICE_TYPE dev_type);
@@ -504,6 +503,7 @@ extern void bta_dm_ble_passkey_reply(const RawAddress& bd_addr, bool accept,
extern void bta_dm_ble_confirm_reply(const RawAddress&, bool);
extern void bta_dm_ble_set_conn_params(const RawAddress&, uint16_t, uint16_t,
uint16_t, uint16_t);
+extern void bta_dm_ble_set_conn_scan_params(uint32_t, uint32_t);
extern void bta_dm_close_gatt_conn(tBTA_DM_MSG* p_data);
extern void bta_dm_ble_observe(bool, uint8_t, tBTA_DM_SEARCH_CBACK*);
extern void bta_dm_ble_update_conn_params(const RawAddress&, uint16_t, uint16_t,
@@ -511,14 +511,16 @@ extern void bta_dm_ble_update_conn_params(const RawAddress&, uint16_t, uint16_t,
uint16_t);
extern void bta_dm_ble_config_local_privacy(bool);
-extern void bta_dm_ble_set_data_length(const RawAddress& bd_addr);
+extern void bta_dm_ble_set_data_length(const RawAddress&, uint16_t);
extern void bta_dm_ble_get_energy_info(tBTA_BLE_ENERGY_INFO_CBACK*);
-extern void bta_dm_set_encryption(const RawAddress&, tBT_TRANSPORT,
- tBTA_DM_ENCRYPT_CBACK*, tBTM_BLE_SEC_ACT);
+extern void bta_dm_set_encryption(const RawAddress&, tBTA_TRANSPORT,
+ tBTA_DM_ENCRYPT_CBACK*, tBTA_DM_BLE_SEC_ACT);
extern void bta_dm_confirm(const RawAddress&, bool);
-
+extern void bta_dm_ci_io_req_act(const RawAddress& bd_addr, tBTA_IO_CAP io_cap,
+ tBTA_OOB_DATA oob_data,
+ tBTA_AUTH_REQ auth_req);
extern void bta_dm_ci_rmt_oob_act(std::unique_ptr<tBTA_DM_CI_RMT_OOB> msg);
extern void bta_dm_init_pm(void);
@@ -526,32 +528,28 @@ extern void bta_dm_disable_pm(void);
extern uint8_t bta_dm_get_av_count(void);
extern void bta_dm_search_start(tBTA_DM_MSG* p_data);
-extern void bta_dm_search_cancel();
+extern void bta_dm_search_cancel(tBTA_DM_MSG* p_data);
extern void bta_dm_discover(tBTA_DM_MSG* p_data);
-extern void bta_dm_inq_cmpl(uint8_t num);
+extern void bta_dm_di_disc(tBTA_DM_MSG* p_data);
+extern void bta_dm_inq_cmpl(tBTA_DM_MSG* p_data);
extern void bta_dm_rmt_name(tBTA_DM_MSG* p_data);
extern void bta_dm_sdp_result(tBTA_DM_MSG* p_data);
-extern void bta_dm_search_cmpl();
-extern void bta_dm_free_sdp_db();
+extern void bta_dm_search_cmpl(tBTA_DM_MSG* p_data);
+extern void bta_dm_free_sdp_db(tBTA_DM_MSG* p_data);
extern void bta_dm_disc_result(tBTA_DM_MSG* p_data);
extern void bta_dm_search_result(tBTA_DM_MSG* p_data);
extern void bta_dm_discovery_cmpl(tBTA_DM_MSG* p_data);
extern void bta_dm_queue_search(tBTA_DM_MSG* p_data);
extern void bta_dm_queue_disc(tBTA_DM_MSG* p_data);
-extern void bta_dm_execute_queued_request();
-extern bool bta_dm_is_search_request_queued();
-extern void bta_dm_search_clear_queue();
-extern void bta_dm_search_cancel_cmpl();
-extern void bta_dm_search_cancel_notify();
+extern void bta_dm_search_clear_queue(tBTA_DM_MSG* p_data);
+extern void bta_dm_search_cancel_cmpl(tBTA_DM_MSG* p_data);
+extern void bta_dm_search_cancel_notify(tBTA_DM_MSG* p_data);
+extern void bta_dm_search_cancel_transac_cmpl(tBTA_DM_MSG* p_data);
extern void bta_dm_disc_rmt_name(tBTA_DM_MSG* p_data);
extern tBTA_DM_PEER_DEVICE* bta_dm_find_peer_device(
const RawAddress& peer_addr);
-uint8_t bta_dm_search_get_state();
-void bta_dm_search_set_state(uint8_t state);
-
void bta_dm_eir_update_uuid(uint16_t uuid16, bool adding);
-void bta_dm_eir_update_cust_uuid(const tBTA_CUSTOM_UUID &curr, bool adding);
-#undef CASE_RETURN_TEXT
+extern void bta_dm_remove_all_acl(const tBTA_DM_LINK_TYPE);
#endif /* BTA_DM_INT_H */
diff --git a/bta/dm/bta_dm_main.cc b/bta/dm/bta_dm_main.cc
index 3b84f9d98..f9bffe66b 100644
--- a/bta/dm/bta_dm_main.cc
+++ b/bta/dm/bta_dm_main.cc
@@ -22,9 +22,9 @@
*
******************************************************************************/
-#include "bt_trace.h"
-#include "bta/dm/bta_dm_int.h"
-#include "stack/include/bt_types.h"
+#include "bta_api.h"
+#include "bta_dm_int.h"
+#include "bta_sys.h"
/*****************************************************************************
* Constants and types
@@ -34,6 +34,177 @@ tBTA_DM_CB bta_dm_cb;
tBTA_DM_SEARCH_CB bta_dm_search_cb;
tBTA_DM_DI_CB bta_dm_di_cb;
+#define BTA_DM_NUM_ACTIONS (BTA_DM_MAX_EVT & 0x00ff)
+
+/* type for action functions */
+typedef void (*tBTA_DM_ACTION)(tBTA_DM_MSG* p_data);
+
+/* state machine action enumeration list */
+enum {
+ BTA_DM_API_SEARCH, /* 0 bta_dm_search_start */
+ BTA_DM_API_SEARCH_CANCEL, /* 1 bta_dm_search_cancel */
+ BTA_DM_API_DISCOVER, /* 2 bta_dm_discover */
+ BTA_DM_INQUIRY_CMPL, /* 3 bta_dm_inq_cmpl */
+ BTA_DM_REMT_NAME, /* 4 bta_dm_rmt_name */
+ BTA_DM_SDP_RESULT, /* 5 bta_dm_sdp_result */
+ BTA_DM_SEARCH_CMPL, /* 6 bta_dm_search_cmpl*/
+ BTA_DM_FREE_SDP_DB, /* 7 bta_dm_free_sdp_db */
+ BTA_DM_DISC_RESULT, /* 8 bta_dm_disc_result */
+ BTA_DM_SEARCH_RESULT, /* 9 bta_dm_search_result */
+ BTA_DM_QUEUE_SEARCH, /* 10 bta_dm_queue_search */
+ BTA_DM_QUEUE_DISC, /* 11 bta_dm_queue_disc */
+ BTA_DM_SEARCH_CLEAR_QUEUE, /* 12 bta_dm_search_clear_queue */
+ BTA_DM_SEARCH_CANCEL_CMPL, /* 13 bta_dm_search_cancel_cmpl */
+ BTA_DM_SEARCH_CANCEL_NOTIFY, /* 14 bta_dm_search_cancel_notify */
+ BTA_DM_SEARCH_CANCEL_TRANSAC_CMPL, /* 15 bta_dm_search_cancel_transac_cmpl */
+ BTA_DM_DISC_RMT_NAME, /* 16 bta_dm_disc_rmt_name */
+ BTA_DM_API_DI_DISCOVER, /* 17 bta_dm_di_disc */
+ BTA_DM_CLOSE_GATT_CONN, /* 18 bta_dm_close_gatt_conn */
+ BTA_DM_SEARCH_NUM_ACTIONS /* 19 */
+};
+
+/* action function list */
+const tBTA_DM_ACTION bta_dm_search_action[] = {
+
+ bta_dm_search_start, /* 0 BTA_DM_API_SEARCH */
+ bta_dm_search_cancel, /* 1 BTA_DM_API_SEARCH_CANCEL */
+ bta_dm_discover, /* 2 BTA_DM_API_DISCOVER */
+ bta_dm_inq_cmpl, /* 3 BTA_DM_INQUIRY_CMPL */
+ bta_dm_rmt_name, /* 4 BTA_DM_REMT_NAME */
+ bta_dm_sdp_result, /* 5 BTA_DM_SDP_RESULT */
+ bta_dm_search_cmpl, /* 6 BTA_DM_SEARCH_CMPL */
+ bta_dm_free_sdp_db, /* 7 BTA_DM_FREE_SDP_DB */
+ bta_dm_disc_result, /* 8 BTA_DM_DISC_RESULT */
+ bta_dm_search_result, /* 9 BTA_DM_SEARCH_RESULT */
+ bta_dm_queue_search, /* 10 BTA_DM_QUEUE_SEARCH */
+ bta_dm_queue_disc, /* 11 BTA_DM_QUEUE_DISC */
+ bta_dm_search_clear_queue, /* 12 BTA_DM_SEARCH_CLEAR_QUEUE */
+ bta_dm_search_cancel_cmpl, /* 13 BTA_DM_SEARCH_CANCEL_CMPL */
+ bta_dm_search_cancel_notify, /* 14 BTA_DM_SEARCH_CANCEL_NOTIFY */
+ bta_dm_search_cancel_transac_cmpl, /* 15 BTA_DM_SEARCH_CANCEL_TRANSAC_CMPL
+ */
+ bta_dm_disc_rmt_name, /* 16 BTA_DM_DISC_RMT_NAME */
+ bta_dm_di_disc, /* 17 BTA_DM_API_DI_DISCOVER */
+ bta_dm_close_gatt_conn};
+
+#define BTA_DM_SEARCH_IGNORE BTA_DM_SEARCH_NUM_ACTIONS
+/* state table information */
+#define BTA_DM_SEARCH_ACTIONS 2 /* number of actions */
+#define BTA_DM_SEARCH_NEXT_STATE 2 /* position of next state */
+#define BTA_DM_SEARCH_NUM_COLS 3 /* number of columns in state tables */
+
+/* state table for listen state */
+const uint8_t bta_dm_search_idle_st_table[][BTA_DM_SEARCH_NUM_COLS] = {
+
+ /* Event Action 1
+ Action 2 Next State */
+ /* API_SEARCH */ {BTA_DM_API_SEARCH, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_ACTIVE},
+ /* API_SEARCH_CANCEL */ {BTA_DM_SEARCH_CANCEL_NOTIFY, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_IDLE},
+ /* API_SEARCH_DISC */ {BTA_DM_API_DISCOVER, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_DISCOVER_ACTIVE},
+ /* INQUIRY_CMPL */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_IDLE},
+ /* REMT_NAME_EVT */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_IDLE},
+ /* SDP_RESULT_EVT */ {BTA_DM_FREE_SDP_DB, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_IDLE},
+ /* SEARCH_CMPL_EVT */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_IDLE},
+ /* DISCV_RES_EVT */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_IDLE},
+ /* API_DI_DISCOVER_EVT */ {BTA_DM_API_DI_DISCOVER, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_ACTIVE},
+ /* DISC_CLOSE_TOUT_EVT */
+ {BTA_DM_CLOSE_GATT_CONN, BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IDLE}};
+const uint8_t bta_dm_search_search_active_st_table[][BTA_DM_SEARCH_NUM_COLS] = {
+
+ /* Event Action 1
+ Action 2 Next State */
+ /* API_SEARCH */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_ACTIVE},
+ /* API_SEARCH_CANCEL */ {BTA_DM_API_SEARCH_CANCEL, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_CANCELLING},
+ /* API_SEARCH_DISC */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_ACTIVE},
+ /* INQUIRY_CMPL */ {BTA_DM_INQUIRY_CMPL, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_ACTIVE},
+ /* REMT_NAME_EVT */ {BTA_DM_REMT_NAME, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_ACTIVE},
+ /* SDP_RESULT_EVT */ {BTA_DM_SDP_RESULT, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_ACTIVE},
+ /* SEARCH_CMPL_EVT */ {BTA_DM_SEARCH_CMPL, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_IDLE},
+ /* DISCV_RES_EVT */ {BTA_DM_SEARCH_RESULT, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_ACTIVE},
+ /* API_DI_DISCOVER_EVT */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_ACTIVE},
+ /* DISC_CLOSE_TOUT_EVT */
+ {BTA_DM_CLOSE_GATT_CONN, BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_ACTIVE}
+
+};
+
+const uint8_t
+ bta_dm_search_search_cancelling_st_table[][BTA_DM_SEARCH_NUM_COLS] = {
+
+ /* Event Action 1
+ Action 2 Next State */
+ /* API_SEARCH */ {BTA_DM_QUEUE_SEARCH, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_CANCELLING},
+ /* API_SEARCH_CANCEL */ {BTA_DM_SEARCH_CLEAR_QUEUE,
+ BTA_DM_SEARCH_CANCEL_NOTIFY,
+ BTA_DM_SEARCH_CANCELLING},
+ /* API_SEARCH_DISC */ {BTA_DM_QUEUE_DISC, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_CANCELLING},
+ /* INQUIRY_CMPL */ {BTA_DM_SEARCH_CANCEL_CMPL, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_IDLE},
+ /* REMT_NAME_EVT */ {BTA_DM_SEARCH_CANCEL_TRANSAC_CMPL,
+ BTA_DM_SEARCH_CANCEL_CMPL, BTA_DM_SEARCH_IDLE},
+ /* SDP_RESULT_EVT */ {BTA_DM_SEARCH_CANCEL_TRANSAC_CMPL,
+ BTA_DM_SEARCH_CANCEL_CMPL, BTA_DM_SEARCH_IDLE},
+ /* SEARCH_CMPL_EVT */ {BTA_DM_SEARCH_CANCEL_TRANSAC_CMPL,
+ BTA_DM_SEARCH_CANCEL_CMPL, BTA_DM_SEARCH_IDLE},
+ /* DISCV_RES_EVT */ {BTA_DM_SEARCH_CANCEL_TRANSAC_CMPL,
+ BTA_DM_SEARCH_CANCEL_CMPL, BTA_DM_SEARCH_IDLE},
+ /* API_DI_DISCOVER_EVT */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_CANCELLING},
+ /* DISC_CLOSE_TOUT_EVT */
+ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_CANCELLING}};
+
+const uint8_t bta_dm_search_disc_active_st_table[][BTA_DM_SEARCH_NUM_COLS] = {
+
+ /* Event Action 1
+ Action 2 Next State */
+ /* API_SEARCH */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_DISCOVER_ACTIVE},
+ /* API_SEARCH_CANCEL */ {BTA_DM_SEARCH_CANCEL_NOTIFY, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_CANCELLING},
+ /* API_SEARCH_DISC */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_DISCOVER_ACTIVE},
+ /* INQUIRY_CMPL */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_DISCOVER_ACTIVE},
+ /* REMT_NAME_EVT */ {BTA_DM_DISC_RMT_NAME, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_DISCOVER_ACTIVE},
+ /* SDP_RESULT_EVT */ {BTA_DM_SDP_RESULT, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_DISCOVER_ACTIVE},
+ /* SEARCH_CMPL_EVT */ {BTA_DM_SEARCH_CMPL, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_SEARCH_IDLE},
+ /* DISCV_RES_EVT */ {BTA_DM_DISC_RESULT, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_DISCOVER_ACTIVE},
+ /* API_DI_DISCOVER_EVT */ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE,
+ BTA_DM_DISCOVER_ACTIVE},
+ /* DISC_CLOSE_TOUT_EVT */
+ {BTA_DM_SEARCH_IGNORE, BTA_DM_SEARCH_IGNORE, BTA_DM_DISCOVER_ACTIVE}};
+
+typedef const uint8_t (*tBTA_DM_ST_TBL)[BTA_DM_SEARCH_NUM_COLS];
+
+/* state table */
+const tBTA_DM_ST_TBL bta_dm_search_st_tbl[] = {
+ bta_dm_search_idle_st_table, bta_dm_search_search_active_st_table,
+ bta_dm_search_search_cancelling_st_table,
+ bta_dm_search_disc_active_st_table};
+
/*******************************************************************************
*
* Function bta_dm_sm_search_disable
@@ -46,9 +217,6 @@ tBTA_DM_DI_CB bta_dm_di_cb;
******************************************************************************/
void bta_dm_search_sm_disable() { bta_sys_deregister(BTA_ID_DM_SEARCH); }
-void bta_dm_search_set_state(uint8_t state) { bta_dm_search_cb.state = state; }
-uint8_t bta_dm_search_get_state() { return bta_dm_search_cb.state; }
-
/*******************************************************************************
*
* Function bta_dm_search_sm_execute
@@ -59,104 +227,28 @@ uint8_t bta_dm_search_get_state() { return bta_dm_search_cb.state; }
* Returns void
*
******************************************************************************/
-bool bta_dm_search_sm_execute(BT_HDR_RIGID* p_msg) {
+bool bta_dm_search_sm_execute(BT_HDR* p_msg) {
+ tBTA_DM_ST_TBL state_table;
+ uint8_t action;
+ int i;
+
APPL_TRACE_EVENT("bta_dm_search_sm_execute state:%d, event:0x%x",
bta_dm_search_cb.state, p_msg->event);
- tBTA_DM_MSG* message = (tBTA_DM_MSG*)p_msg;
- switch (bta_dm_search_cb.state) {
- case BTA_DM_SEARCH_IDLE:
- switch (p_msg->event) {
- case BTA_DM_API_SEARCH_EVT:
- bta_dm_search_set_state(BTA_DM_SEARCH_ACTIVE);
- bta_dm_search_start(message);
- break;
- case BTA_DM_API_DISCOVER_EVT:
- bta_dm_search_set_state(BTA_DM_DISCOVER_ACTIVE);
- bta_dm_discover(message);
- break;
- case BTA_DM_SDP_RESULT_EVT:
- bta_dm_free_sdp_db();
- break;
- case BTA_DM_DISC_CLOSE_TOUT_EVT:
- bta_dm_close_gatt_conn(message);
- break;
- case BTA_DM_API_QUEUE_SEARCH_EVT:
- bta_dm_queue_search(message);
- break;
- case BTA_DM_API_QUEUE_DISCOVER_EVT:
- bta_dm_queue_disc(message);
- break;
- }
- break;
- case BTA_DM_SEARCH_ACTIVE:
- switch (p_msg->event) {
- case BTA_DM_REMT_NAME_EVT:
- bta_dm_rmt_name(message);
- break;
- case BTA_DM_SDP_RESULT_EVT:
- bta_dm_sdp_result(message);
- break;
- case BTA_DM_SEARCH_CMPL_EVT:
- bta_dm_search_cmpl();
- break;
- case BTA_DM_DISCOVERY_RESULT_EVT:
- bta_dm_search_result(message);
- break;
- case BTA_DM_DISC_CLOSE_TOUT_EVT:
- bta_dm_close_gatt_conn(message);
- break;
- case BTA_DM_API_DISCOVER_EVT:
- case BTA_DM_API_QUEUE_DISCOVER_EVT:
- bta_dm_queue_disc(message);
- break;
- }
- break;
- case BTA_DM_SEARCH_CANCELLING:
- switch (p_msg->event) {
- case BTA_DM_API_SEARCH_EVT:
- case BTA_DM_API_QUEUE_SEARCH_EVT:
- bta_dm_queue_search(message);
- break;
- case BTA_DM_API_DISCOVER_EVT:
- case BTA_DM_API_QUEUE_DISCOVER_EVT:
- bta_dm_queue_disc(message);
- break;
- case BTA_DM_SDP_RESULT_EVT:
- case BTA_DM_REMT_NAME_EVT:
- case BTA_DM_SEARCH_CMPL_EVT:
- case BTA_DM_DISCOVERY_RESULT_EVT:
- bta_dm_search_set_state(BTA_DM_SEARCH_IDLE);
- bta_dm_free_sdp_db();
- bta_dm_search_cancel_notify();
- bta_dm_search_cancel_cmpl();
- break;
- }
- break;
- case BTA_DM_DISCOVER_ACTIVE:
- switch (p_msg->event) {
- case BTA_DM_REMT_NAME_EVT:
- bta_dm_disc_rmt_name(message);
- break;
- case BTA_DM_SDP_RESULT_EVT:
- bta_dm_sdp_result(message);
- break;
- case BTA_DM_SEARCH_CMPL_EVT:
- bta_dm_search_cmpl();
- break;
- case BTA_DM_DISCOVERY_RESULT_EVT:
- bta_dm_disc_result(message);
- break;
- case BTA_DM_API_SEARCH_EVT:
- case BTA_DM_API_QUEUE_SEARCH_EVT:
- bta_dm_queue_search(message);
- break;
- case BTA_DM_API_DISCOVER_EVT:
- case BTA_DM_API_QUEUE_DISCOVER_EVT:
- bta_dm_queue_disc(message);
- break;
- }
+ /* look up the state table for the current state */
+ state_table = bta_dm_search_st_tbl[bta_dm_search_cb.state];
+
+ bta_dm_search_cb.state =
+ state_table[p_msg->event & 0x00ff][BTA_DM_SEARCH_NEXT_STATE];
+
+ /* execute action functions */
+ for (i = 0; i < BTA_DM_SEARCH_ACTIONS; i++) {
+ action = state_table[p_msg->event & 0x00ff][i];
+ if (action != BTA_DM_SEARCH_IGNORE) {
+ (*bta_dm_search_action[action])((tBTA_DM_MSG*)p_msg);
+ } else {
break;
+ }
}
return true;
}
diff --git a/bta/dm/bta_dm_pm.cc b/bta/dm/bta_dm_pm.cc
index f819c8846..51be1b6ec 100644
--- a/bta/dm/bta_dm_pm.cc
+++ b/bta/dm/bta_dm_pm.cc
@@ -24,19 +24,18 @@
******************************************************************************/
#include <base/bind.h>
-#include <cstdint>
+#include <base/logging.h>
+#include <string.h>
+
#include <mutex>
-#include "bta/dm/bta_dm_int.h"
-#include "bta/include/bta_api.h"
-#include "bta/include/bta_dm_api.h"
-#include "bta/sys/bta_sys.h"
-#include "device/include/controller.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "types/raw_address.h"
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_dm_api.h"
+#include "bta_dm_int.h"
+#include "bta_sys.h"
+#include "btm_api.h"
+#include "stack/include/btu.h"
static void bta_dm_pm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
uint8_t app_id, const RawAddress& peer_addr);
@@ -46,15 +45,20 @@ static void bta_dm_pm_set_mode(const RawAddress& peer_addr,
static void bta_dm_pm_timer_cback(void* data);
static void bta_dm_pm_btm_cback(const RawAddress& bd_addr,
tBTM_PM_STATUS status, uint16_t value,
- tHCI_STATUS hci_status);
+ uint8_t hci_status);
static bool bta_dm_pm_park(const RawAddress& peer_addr);
-void bta_dm_pm_sniff(tBTA_DM_PEER_DEVICE* p_peer_dev, uint8_t index);
+static bool bta_dm_pm_sniff(tBTA_DM_PEER_DEVICE* p_peer_dev, uint8_t index);
static bool bta_dm_pm_is_sco_active();
+#if (BTM_SSR_INCLUDED == TRUE)
static int bta_dm_get_sco_index();
+#endif
static void bta_dm_pm_hid_check(bool bScoActive);
+static void bta_dm_pm_set_sniff_policy(tBTA_DM_PEER_DEVICE* p_dev,
+ bool bDisable);
static void bta_dm_pm_stop_timer_by_index(tBTA_PM_TIMER* p_timer,
uint8_t timer_idx);
+#if (BTM_SSR_INCLUDED == TRUE)
#if (BTA_HH_INCLUDED == TRUE)
#include "../hh/bta_hh_int.h"
/* BTA_DM_PM_SSR1 will be dedicated for HH SSR setting entry, no other profile
@@ -62,6 +66,7 @@ static void bta_dm_pm_stop_timer_by_index(tBTA_PM_TIMER* p_timer,
#define BTA_DM_PM_SSR_HH BTA_DM_PM_SSR1
#endif
static void bta_dm_pm_ssr(const RawAddress& peer_addr, int ssr);
+#endif
tBTA_DM_CONNECTED_SRVCS bta_dm_conn_srvcs;
static std::recursive_mutex pm_timer_schedule_mutex;
@@ -84,7 +89,8 @@ void bta_dm_init_pm(void) {
if (p_bta_dm_pm_cfg[0].app_id != 0) {
bta_sys_pm_register(bta_dm_pm_cback);
- BTM_PmRegister((BTM_PM_REG_SET), &bta_dm_cb.pm_id, bta_dm_pm_btm_cback);
+ BTM_PmRegister((BTM_PM_REG_SET | BTM_PM_REG_NOTIF), &bta_dm_cb.pm_id,
+ bta_dm_pm_btm_cback);
}
/* Need to initialize all PM timer service IDs */
@@ -105,7 +111,7 @@ void bta_dm_init_pm(void) {
*
******************************************************************************/
void bta_dm_disable_pm(void) {
- BTM_PmRegister(BTM_PM_DEREG, &bta_dm_cb.pm_id, bta_dm_pm_btm_cback);
+ BTM_PmRegister(BTM_PM_DEREG, &bta_dm_cb.pm_id, NULL);
/*
* Deregister the PM callback from the system handling to prevent
@@ -301,12 +307,10 @@ static void bta_dm_pm_stop_timer_by_index(tBTA_PM_TIMER* p_timer,
std::unique_lock<std::recursive_mutex> schedule_lock(pm_timer_schedule_mutex);
std::unique_lock<std::recursive_mutex> state_lock(pm_timer_state_mutex);
- if (p_timer->srvc_id[timer_idx] == BTA_ID_MAX) {
- return;
- } /* The timer was not scheduled */
+ if (p_timer->srvc_id[timer_idx] == BTA_ID_MAX)
+ return; /* The timer was not scheduled */
- CHECK(p_timer->in_use);
- CHECK(p_timer->active > 0);
+ CHECK(p_timer->in_use && (p_timer->active > 0));
p_timer->srvc_id[timer_idx] = BTA_ID_MAX;
/* NOTE: pm_action[timer_idx] intentionally not reset */
@@ -334,9 +338,10 @@ static void bta_dm_pm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
tBTA_DM_PEER_DEVICE* p_dev;
tBTA_DM_PM_REQ pm_req = BTA_DM_PM_NEW_REQ;
- LOG_DEBUG("Power management callback status:%s[%hhu] id:%s[%d], app:%hhu",
- bta_sys_conn_status_text(status).c_str(), status,
- BtaIdSysText(id).c_str(), id, app_id);
+ APPL_TRACE_DEBUG("bta_dm_pm_cback: st(%d), id(%d), app(%d)", status, id,
+ app_id);
+
+ p_dev = bta_dm_find_peer_device(peer_addr);
/* find if there is an power mode entry for the service */
for (i = 1; i <= p_bta_dm_pm_cfg[0].app_id; i++) {
@@ -347,26 +352,16 @@ static void bta_dm_pm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
}
/* if no entries are there for the app_id and subsystem in p_bta_dm_pm_spec*/
- if (i > p_bta_dm_pm_cfg[0].app_id) {
- LOG_DEBUG("Ignoring power management callback as no service entries exist");
- return;
- }
+ if (i > p_bta_dm_pm_cfg[0].app_id) return;
- LOG_DEBUG("Stopped all timers for service to device:%s id:%hhu",
- PRIVATE_ADDRESS(peer_addr), id);
bta_dm_pm_stop_timer_by_srvc_id(peer_addr, id);
+/*p_dev = bta_dm_find_peer_device(peer_addr);*/
- p_dev = bta_dm_find_peer_device(peer_addr);
- if (p_dev) {
- LOG_DEBUG("Device info:%s", device_info_text(p_dev->Info()).c_str());
- } else {
- LOG_ERROR("Unable to find peer device...yet soldiering on...");
- }
-
+#if (BTM_SSR_INCLUDED == TRUE)
/* set SSR parameters on SYS CONN OPEN */
int index = BTA_DM_PM_SSR0;
if ((BTA_SYS_CONN_OPEN == status) && p_dev &&
- (p_dev->Info() & BTA_DM_DI_USE_SSR)) {
+ (p_dev->info & BTA_DM_DI_USE_SSR)) {
index = p_bta_dm_pm_spec[p_bta_dm_pm_cfg[i].spec_idx].ssr;
} else if (BTA_ID_AV == id) {
if (BTA_SYS_CONN_BUSY == status) {
@@ -376,12 +371,15 @@ static void bta_dm_pm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
index = p_bta_dm_pm_spec[p_bta_dm_pm_cfg[i].spec_idx].ssr;
}
}
+#endif
/* if no action for the event */
if (p_bta_dm_pm_spec[p_bta_dm_pm_cfg[i].spec_idx]
.actn_tbl[status][0]
.power_mode == BTA_DM_PM_NO_ACTION) {
+#if (BTM_SSR_INCLUDED == TRUE)
if (BTA_DM_PM_SSR0 == index) /* and do not need to set SSR, return. */
+#endif
return;
}
@@ -415,7 +413,7 @@ static void bta_dm_pm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
} else if (j == bta_dm_conn_srvcs.count) {
/* check if we have more connected service that cbs */
if (bta_dm_conn_srvcs.count == BTA_DM_NUM_CONN_SRVS) {
- LOG_WARN("bta_dm_act no more connected service cbs");
+ APPL_TRACE_WARNING("bta_dm_act no more connected service cbs");
return;
}
@@ -425,8 +423,7 @@ static void bta_dm_pm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
bta_dm_conn_srvcs.conn_srvc[j].new_request = true;
bta_dm_conn_srvcs.conn_srvc[j].peer_bdaddr = peer_addr;
- LOG_INFO("New connection service:%s[%hhu] app_id:%d",
- BtaIdSysText(id).c_str(), id, app_id);
+ APPL_TRACE_WARNING("new conn_srvc id:%d, app_id:%d", id, app_id);
bta_dm_conn_srvcs.count++;
bta_dm_conn_srvcs.conn_srvc[j].state = status;
@@ -450,12 +447,17 @@ static void bta_dm_pm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
p_dev->pm_mode_failed = 0;
}
- if (p_bta_dm_ssr_spec[index].max_lat || index == BTA_DM_PM_SSR_HH) {
+#if (BTM_SSR_INCLUDED == TRUE)
+ if (p_bta_dm_ssr_spec[index].max_lat
+#if (BTA_HH_INCLUDED == TRUE)
+ || index == BTA_DM_PM_SSR_HH
+#endif
+ ) {
bta_dm_pm_ssr(peer_addr, index);
} else {
- const controller_t* controller = controller_get_interface();
uint8_t* p = NULL;
- if (controller->supports_sniff_subrating() &&
+ if (((NULL != (p = BTM_ReadLocalFeatures())) &&
+ HCI_SNIFF_SUB_RATE_SUPPORTED(p)) &&
((NULL != (p = BTM_ReadRemoteFeatures(peer_addr))) &&
HCI_SNIFF_SUB_RATE_SUPPORTED(p)) &&
(index == BTA_DM_PM_SSR0)) {
@@ -468,6 +470,7 @@ static void bta_dm_pm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id,
}
}
}
+#endif
bta_dm_pm_set_mode(peer_addr, BTA_DM_PM_NO_ACTION, pm_req);
@@ -520,18 +523,12 @@ static void bta_dm_pm_set_mode(const RawAddress& peer_addr,
uint8_t timer_idx, available_timer = BTA_DM_PM_MODE_TIMER_MAX;
uint64_t remaining_ms = 0;
- if (!bta_dm_cb.device_list.count) {
- LOG_INFO("Device list count is zero");
- return;
- }
+ if (!bta_dm_cb.device_list.count) return;
/* see if any attempt to put device in low power mode failed */
p_peer_device = bta_dm_find_peer_device(peer_addr);
/* if no peer device found return */
- if (p_peer_device == NULL) {
- LOG_INFO("No peer device found");
- return;
- }
+ if (p_peer_device == NULL) return;
failed_pm = p_peer_device->pm_mode_failed;
@@ -551,13 +548,9 @@ static void bta_dm_pm_set_mode(const RawAddress& peer_addr,
p_act0 = &p_pm_spec->actn_tbl[p_srvcs->state][0];
p_act1 = &p_pm_spec->actn_tbl[p_srvcs->state][1];
+ APPL_TRACE_DEBUG("bta_dm_pm_set_mode: srvcsid: %d, state: %d, j: %d",
+ p_srvcs->id, p_srvcs->state, j);
allowed_modes |= p_pm_spec->allow_mask;
- LOG_DEBUG(
- "Service:%s[%hhu] state:%s[%hhu] allowed_modes:0x%02x "
- "service_index:%hhu ",
- BtaIdSysText(p_srvcs->id).c_str(), p_srvcs->id,
- bta_sys_conn_status_text(p_srvcs->state).c_str(), p_srvcs->state,
- allowed_modes, j);
/* PM actions are in the order of strictness */
@@ -626,6 +619,7 @@ static void bta_dm_pm_set_mode(const RawAddress& peer_addr,
}
break;
} else if (!bta_dm_cb.pm_timer[i].in_use) {
+ APPL_TRACE_DEBUG("%s dm_pm_timer:%d, %d ms", __func__, i, timeout_ms);
if (available_timer == BTA_DM_PM_MODE_TIMER_MAX) available_timer = i;
}
}
@@ -639,8 +633,10 @@ static void bta_dm_pm_set_mode(const RawAddress& peer_addr,
timeout_ms, p_srvcs->id, pm_action);
timer_started = true;
}
- } else {
- LOG_WARN("no more timers");
+ }
+ /* no more timers */
+ else {
+ APPL_TRACE_WARNING("bta_dm_act dm_pm_timer no more");
}
}
return;
@@ -648,30 +644,22 @@ static void bta_dm_pm_set_mode(const RawAddress& peer_addr,
/* if pending power mode timer expires, and currecnt link is in a
lower power mode than current profile requirement, igonre it */
if (pm_req == BTA_DM_PM_EXECUTE && pm_request < pm_action) {
- LOG_ERROR("Ignore the power mode request: %d", pm_request);
+ APPL_TRACE_ERROR("Ignore the power mode request: %d", pm_request)
return;
}
if (pm_action == BTA_DM_PM_PARK) {
p_peer_device->pm_mode_attempted = BTA_DM_PM_PARK;
bta_dm_pm_park(peer_addr);
- LOG_WARN("DEPRECATED Setting link to park mode peer:%s",
- PRIVATE_ADDRESS(peer_addr));
} else if (pm_action & BTA_DM_PM_SNIFF) {
/* dont initiate SNIFF, if link_policy has it disabled */
- if (BTM_is_sniff_allowed_for(peer_addr)) {
- LOG_DEBUG(
- "Link policy allows sniff mode so setting mode "
- "peer:%s",
- PRIVATE_ADDRESS(peer_addr));
+ if (p_peer_device->link_policy & HCI_ENABLE_SNIFF_MODE) {
p_peer_device->pm_mode_attempted = BTA_DM_PM_SNIFF;
bta_dm_pm_sniff(p_peer_device, (uint8_t)(pm_action & 0x0F));
} else {
- LOG_DEBUG("Link policy disallows sniff mode, ignore request peer:%s",
- PRIVATE_ADDRESS(peer_addr));
+ APPL_TRACE_DEBUG(
+ "bta_dm_pm_set_mode: Link policy disallows SNIFF, ignore request");
}
} else if (pm_action == BTA_DM_PM_ACTIVE) {
- LOG_DEBUG("Setting link to active mode peer:%s",
- PRIVATE_ADDRESS(peer_addr));
bta_dm_pm_active(peer_addr);
}
}
@@ -689,18 +677,11 @@ static bool bta_dm_pm_park(const RawAddress& peer_addr) {
tBTM_PM_MODE mode = BTM_PM_STS_ACTIVE;
/* if not in park mode, switch to park */
- if (!BTM_ReadPowerMode(peer_addr, &mode)) {
- LOG_WARN("Unable to read power mode for peer:%s",
- PRIVATE_ADDRESS(peer_addr));
- }
+ BTM_ReadPowerMode(peer_addr, &mode);
if (mode != BTM_PM_MD_PARK) {
- tBTM_STATUS status = BTM_SetPowerMode(bta_dm_cb.pm_id, peer_addr,
- &p_bta_dm_pm_md[BTA_DM_PM_PARK_IDX]);
- if (status == BTM_CMD_STORED || status == BTM_CMD_STARTED) {
- return true;
- }
- LOG_WARN("Unable to set park power mode");
+ BTM_SetPowerMode(bta_dm_cb.pm_id, peer_addr,
+ &p_bta_dm_pm_md[BTA_DM_PM_PARK_IDX]);
}
return true;
}
@@ -715,60 +696,57 @@ static bool bta_dm_pm_park(const RawAddress& peer_addr) {
* Returns true if sniff attempted, false otherwise.
*
******************************************************************************/
-void bta_dm_pm_sniff(tBTA_DM_PEER_DEVICE* p_peer_dev, uint8_t index) {
- tBTM_PM_MODE mode = BTM_PM_MD_ACTIVE;
+static bool bta_dm_pm_sniff(tBTA_DM_PEER_DEVICE* p_peer_dev, uint8_t index) {
+ tBTM_PM_MODE mode = BTM_PM_STS_ACTIVE;
tBTM_PM_PWR_MD pwr_md;
tBTM_STATUS status;
- if (!BTM_ReadPowerMode(p_peer_dev->peer_bdaddr, &mode)) {
- LOG_WARN("Unable to read power mode for peer:%s",
- PRIVATE_ADDRESS(p_peer_dev->peer_bdaddr));
- }
- tBTM_PM_STATUS mode_status = static_cast<tBTM_PM_STATUS>(mode);
- LOG_DEBUG("Current power mode:%s[0x%x] peer_info:%s[0x%02x]",
- power_mode_status_text(mode_status).c_str(), mode_status,
- device_info_text(p_peer_dev->Info()).c_str(), p_peer_dev->Info());
-
+ BTM_ReadPowerMode(p_peer_dev->peer_bdaddr, &mode);
+#if (BTM_SSR_INCLUDED == TRUE)
uint8_t* p_rem_feat = BTM_ReadRemoteFeatures(p_peer_dev->peer_bdaddr);
-
- const controller_t* controller = controller_get_interface();
+ APPL_TRACE_DEBUG("bta_dm_pm_sniff cur:%d, idx:%d, info:x%x", mode, index,
+ p_peer_dev->info);
if (mode != BTM_PM_MD_SNIFF ||
- (controller->supports_sniff_subrating() && p_rem_feat &&
+ (HCI_SNIFF_SUB_RATE_SUPPORTED(BTM_ReadLocalFeatures()) && p_rem_feat &&
HCI_SNIFF_SUB_RATE_SUPPORTED(p_rem_feat) &&
- !(p_peer_dev->Info() & BTA_DM_DI_USE_SSR))) {
+ !(p_peer_dev->info & BTA_DM_DI_USE_SSR))) {
/* Dont initiate Sniff if controller has alreay accepted
* remote sniff params. This avoid sniff loop issue with
* some agrresive headsets who use sniff latencies more than
* DUT supported range of Sniff intervals.*/
- if ((mode == BTM_PM_MD_SNIFF) &&
- (p_peer_dev->Info() & BTA_DM_DI_ACP_SNIFF)) {
- LOG_DEBUG("Link already in sniff mode peer:%s",
- PRIVATE_ADDRESS(p_peer_dev->peer_bdaddr));
- return;
+ if ((mode == BTM_PM_MD_SNIFF) && (p_peer_dev->info & BTA_DM_DI_ACP_SNIFF)) {
+ APPL_TRACE_DEBUG("%s: already in remote initiate sniff", __func__);
+ return true;
+ }
+#else
+ APPL_TRACE_DEBUG("bta_dm_pm_sniff cur:%d, idx:%d", mode, index);
+ if (mode != BTM_PM_MD_SNIFF) {
+#endif
+ /* if the current mode is not sniff, issue the sniff command.
+ * If sniff, but SSR is not used in this link, still issue the command */
+ memcpy(&pwr_md, &p_bta_dm_pm_md[index], sizeof(tBTM_PM_PWR_MD));
+ if (p_peer_dev->info & BTA_DM_DI_INT_SNIFF) {
+ pwr_md.mode |= BTM_PM_MD_FORCE;
+ }
+ status =
+ BTM_SetPowerMode(bta_dm_cb.pm_id, p_peer_dev->peer_bdaddr, &pwr_md);
+ if (status == BTM_CMD_STORED || status == BTM_CMD_STARTED) {
+ p_peer_dev->info &= ~(BTA_DM_DI_INT_SNIFF | BTA_DM_DI_ACP_SNIFF);
+ p_peer_dev->info |= BTA_DM_DI_SET_SNIFF;
+ } else if (status == BTM_SUCCESS) {
+ APPL_TRACE_DEBUG(
+ "bta_dm_pm_sniff BTM_SetPowerMode() returns BTM_SUCCESS");
+ p_peer_dev->info &=
+ ~(BTA_DM_DI_INT_SNIFF | BTA_DM_DI_ACP_SNIFF | BTA_DM_DI_SET_SNIFF);
+ } else /* error */
+ {
+ APPL_TRACE_ERROR(
+ "bta_dm_pm_sniff BTM_SetPowerMode() returns ERROR status=%d", status);
+ p_peer_dev->info &=
+ ~(BTA_DM_DI_INT_SNIFF | BTA_DM_DI_ACP_SNIFF | BTA_DM_DI_SET_SNIFF);
}
}
- /* if the current mode is not sniff, issue the sniff command.
- * If sniff, but SSR is not used in this link, still issue the command */
- memcpy(&pwr_md, &p_bta_dm_pm_md[index], sizeof(tBTM_PM_PWR_MD));
- if (p_peer_dev->Info() & BTA_DM_DI_INT_SNIFF) {
- LOG_DEBUG("Trying to force power mode");
- pwr_md.mode |= BTM_PM_MD_FORCE;
- }
- status = BTM_SetPowerMode(bta_dm_cb.pm_id, p_peer_dev->peer_bdaddr, &pwr_md);
- if (status == BTM_CMD_STORED || status == BTM_CMD_STARTED) {
- p_peer_dev->info &= ~(BTA_DM_DI_INT_SNIFF | BTA_DM_DI_ACP_SNIFF);
- p_peer_dev->info |= BTA_DM_DI_SET_SNIFF;
- } else if (status == BTM_SUCCESS) {
- APPL_TRACE_DEBUG("bta_dm_pm_sniff BTM_SetPowerMode() returns BTM_SUCCESS");
- p_peer_dev->info &=
- ~(BTA_DM_DI_INT_SNIFF | BTA_DM_DI_ACP_SNIFF | BTA_DM_DI_SET_SNIFF);
- } else {
- LOG_ERROR("Unable to set power mode peer:%s status:%s",
- PRIVATE_ADDRESS(p_peer_dev->peer_bdaddr),
- btm_status_text(status).c_str());
- p_peer_dev->info &=
- ~(BTA_DM_DI_INT_SNIFF | BTA_DM_DI_ACP_SNIFF | BTA_DM_DI_SET_SNIFF);
- }
+ return true;
}
/*******************************************************************************
*
@@ -779,13 +757,12 @@ void bta_dm_pm_sniff(tBTA_DM_PEER_DEVICE* p_peer_dev, uint8_t index) {
* Returns void
*
******************************************************************************/
+#if (BTM_SSR_INCLUDED == TRUE)
static void bta_dm_pm_ssr(const RawAddress& peer_addr, int ssr) {
int current_ssr_index;
int ssr_index = ssr;
tBTA_DM_SSR_SPEC* p_spec = &p_bta_dm_ssr_spec[ssr_index];
- LOG_DEBUG("Request to put link to device:%s into power_mode:%s",
- PRIVATE_ADDRESS(peer_addr), p_spec->name);
/* go through the connected services */
for (int i = 0; i < bta_dm_conn_srvcs.count; i++) {
const tBTA_DM_SRVCS& service = bta_dm_conn_srvcs.conn_srvc[i];
@@ -799,10 +776,8 @@ static void bta_dm_pm_ssr(const RawAddress& peer_addr, int ssr) {
current_ssr_index = p_bta_dm_pm_spec[config.spec_idx].ssr;
if ((config.id == service.id) && ((config.app_id == BTA_ALL_APP_ID) ||
(config.app_id == service.app_id))) {
- LOG_INFO("Found connected service:%s app_id:%d peer:%s spec_name:%s",
- BtaIdSysText(service.id).c_str(), service.app_id,
- PRIVATE_ADDRESS(peer_addr),
- p_bta_dm_ssr_spec[current_ssr_index].name);
+ APPL_TRACE_WARNING("%s: conn_srvc id:%d, app_id:%d", __func__,
+ service.id, service.app_id);
break;
}
}
@@ -820,80 +795,56 @@ static void bta_dm_pm_ssr(const RawAddress& peer_addr, int ssr) {
#endif
if (p_spec_cur->max_lat < p_spec->max_lat ||
(ssr_index == BTA_DM_PM_SSR0 && current_ssr_index != BTA_DM_PM_SSR0)) {
- LOG_DEBUG(
- "Changing sniff subrating specification for %s from %s[%d] ==> "
- "%s[%d]",
- PRIVATE_ADDRESS(peer_addr), p_spec->name, ssr_index, p_spec_cur->name,
- current_ssr_index);
ssr_index = current_ssr_index;
p_spec = &p_bta_dm_ssr_spec[ssr_index];
}
}
+ APPL_TRACE_WARNING("%s ssr:%d, lat:%d", __func__, ssr_index, p_spec->max_lat);
+
if (p_spec->max_lat) {
/* Avoid SSR reset on device which has SCO connected */
if (bta_dm_pm_is_sco_active()) {
int idx = bta_dm_get_sco_index();
if (idx != -1) {
if (bta_dm_conn_srvcs.conn_srvc[idx].peer_bdaddr == peer_addr) {
- LOG_WARN("SCO is active on device, ignore SSR");
+ APPL_TRACE_WARNING("%s SCO is active on device, ignore SSR",
+ __func__);
return;
}
}
}
- LOG_DEBUG(
- "Setting sniff subrating for device:%s spec_name:%s max_latency(s):%.2f"
- " min_local_timeout(s):%.2f min_remote_timeout(s):%.2f",
- PRIVATE_ADDRESS(peer_addr), p_spec->name,
- ticks_to_seconds(p_spec->max_lat), ticks_to_seconds(p_spec->min_loc_to),
- ticks_to_seconds(p_spec->min_rmt_to));
/* set the SSR parameters. */
BTM_SetSsrParams(peer_addr, p_spec->max_lat, p_spec->min_rmt_to,
p_spec->min_loc_to);
}
}
-
+#endif
/*******************************************************************************
*
* Function bta_dm_pm_active
*
* Description Brings connection to active mode
*
+ *
* Returns void
*
******************************************************************************/
void bta_dm_pm_active(const RawAddress& peer_addr) {
- tBTM_PM_PWR_MD pm{
- .mode = BTM_PM_MD_ACTIVE,
- };
+ tBTM_PM_PWR_MD pm;
+
+ memset((void*)&pm, 0, sizeof(pm));
/* switch to active mode */
- tBTM_STATUS status = BTM_SetPowerMode(bta_dm_cb.pm_id, peer_addr, &pm);
- switch (status) {
- case BTM_CMD_STORED:
- LOG_DEBUG("Active power mode stored for execution later for remote:%s",
- PRIVATE_ADDRESS(peer_addr));
- break;
- case BTM_CMD_STARTED:
- LOG_DEBUG("Active power mode started for remote:%s",
- PRIVATE_ADDRESS(peer_addr));
- break;
- case BTM_SUCCESS:
- LOG_INFO("Active power mode already set for device:%s",
- PRIVATE_ADDRESS(peer_addr));
- break;
- default:
- LOG_WARN("Unable to set active power mode for device:%s status:%s",
- PRIVATE_ADDRESS(peer_addr), btm_status_text(status).c_str());
- break;
- }
+ pm.mode = BTM_PM_MD_ACTIVE;
+ BTM_SetPowerMode(bta_dm_cb.pm_id, peer_addr, &pm);
}
/** BTM power manager callback */
static void bta_dm_pm_btm_cback(const RawAddress& bd_addr,
tBTM_PM_STATUS status, uint16_t value,
- tHCI_STATUS hci_status) {
+ uint8_t hci_status) {
do_in_main_thread(FROM_HERE, base::Bind(bta_dm_pm_btm_status, bd_addr, status,
value, hci_status));
}
@@ -942,21 +893,13 @@ static void bta_dm_pm_timer_cback(void* data) {
/** Process pm status event from btm */
void bta_dm_pm_btm_status(const RawAddress& bd_addr, tBTM_PM_STATUS status,
- uint16_t interval, tHCI_STATUS hci_status) {
- LOG_DEBUG(
- "Power mode notification event status:%s peer:%s interval:%hu "
- "hci_status:%s",
- power_mode_status_text(status).c_str(), PRIVATE_ADDRESS(bd_addr),
- interval, hci_error_code_text(hci_status).c_str());
+ uint16_t value, uint8_t hci_status) {
+ APPL_TRACE_DEBUG("%s status: %d", __func__, status);
tBTA_DM_PEER_DEVICE* p_dev = bta_dm_find_peer_device(bd_addr);
- if (p_dev == nullptr) {
- LOG_INFO("Unable to process power event for peer:%s",
- PRIVATE_ADDRESS(bd_addr));
- return;
- }
+ if (NULL == p_dev) return;
- tBTA_DM_DEV_INFO info = p_dev->Info();
+ tBTA_DM_DEV_INFO info = p_dev->info;
/* check new mode */
switch (status) {
case BTM_PM_STS_ACTIVE:
@@ -974,11 +917,13 @@ void bta_dm_pm_btm_status(const RawAddress& bd_addr, tBTM_PM_STATUS status,
bta_dm_pm_set_mode(bd_addr, BTA_DM_PM_NO_ACTION, BTA_DM_PM_RESTART);
}
} else {
+#if (BTM_SSR_INCLUDED == TRUE)
if (p_dev->prev_low) {
/* need to send the SSR paramaters to controller again */
bta_dm_pm_ssr(p_dev->peer_bdaddr, BTA_DM_PM_SSR0);
}
p_dev->prev_low = BTM_PM_STS_ACTIVE;
+#endif
/* link to active mode, need to restart the timer for next low power
* mode if needed */
bta_dm_pm_stop_timer(bd_addr);
@@ -986,6 +931,7 @@ void bta_dm_pm_btm_status(const RawAddress& bd_addr, tBTM_PM_STATUS status,
}
break;
+#if (BTM_SSR_INCLUDED == TRUE)
case BTM_PM_STS_PARK:
case BTM_PM_STS_HOLD:
/* save the previous low power mode - for SSR.
@@ -995,19 +941,12 @@ void bta_dm_pm_btm_status(const RawAddress& bd_addr, tBTM_PM_STATUS status,
break;
case BTM_PM_STS_SSR:
- if (hci_status != 0) {
- LOG_WARN("Received error when attempting to set sniff subrating mode");
- }
- if (interval) {
+ if (value)
p_dev->info |= BTA_DM_DI_USE_SSR;
- LOG_DEBUG("Enabling sniff subrating mode for peer:%s",
- PRIVATE_ADDRESS(bd_addr));
- } else {
+ else
p_dev->info &= ~BTA_DM_DI_USE_SSR;
- LOG_DEBUG("Disabling sniff subrating mode for peer:%s",
- PRIVATE_ADDRESS(bd_addr));
- }
break;
+#endif
case BTM_PM_STS_SNIFF:
if (hci_status == 0) {
/* Stop PM timer now if already active for
@@ -1032,9 +971,8 @@ void bta_dm_pm_btm_status(const RawAddress& bd_addr, tBTM_PM_STATUS status,
break;
default:
- LOG_ERROR("Received unknown power mode status event:%hhu", status);
break;
- }
+ }
}
/** Process pm timer event from btm */
@@ -1085,9 +1023,12 @@ static bool bta_dm_pm_is_sco_active() {
break;
}
}
+
+ APPL_TRACE_DEBUG("bta_dm_is_sco_active: SCO active: %d", bScoActive);
return bScoActive;
}
+#if (BTM_SSR_INCLUDED == TRUE)
/*******************************************************************************
*
* Function bta_dm_get_sco_index
@@ -1107,6 +1048,7 @@ static int bta_dm_get_sco_index() {
}
return -1;
}
+#endif
/*******************************************************************************
*
@@ -1127,20 +1069,54 @@ static void bta_dm_pm_hid_check(bool bScoActive) {
APPL_TRACE_DEBUG(
"SCO status change(Active: %d), modify HID link policy. state: %d",
bScoActive, bta_dm_conn_srvcs.conn_srvc[j].state);
- auto peer_addr = bta_dm_conn_srvcs.conn_srvc[j].peer_bdaddr;
- if (bScoActive) {
- BTM_block_sniff_mode_for(peer_addr);
- bta_dm_pm_active(peer_addr);
- } else {
- BTM_unblock_sniff_mode_for(peer_addr);
- bta_dm_pm_set_mode(peer_addr, BTA_DM_PM_NO_ACTION, BTA_DM_PM_RESTART);
- }
+ bta_dm_pm_set_sniff_policy(
+ bta_dm_find_peer_device(bta_dm_conn_srvcs.conn_srvc[j].peer_bdaddr),
+ bScoActive);
+
+ /* if we had disabled link policy, seems like the hid device stop retrying
+ * SNIFF after a few tries. force sniff if needed */
+ if (!bScoActive)
+ bta_dm_pm_set_mode(bta_dm_conn_srvcs.conn_srvc[j].peer_bdaddr,
+ BTA_DM_PM_NO_ACTION, BTA_DM_PM_RESTART);
}
}
}
/*******************************************************************************
*
+ * Function bta_dm_pm_set_sniff_policy
+ *
+ * Description Disables/Enables sniff in link policy for the give device
+ *
+ * Returns None
+ *
+ ******************************************************************************/
+static void bta_dm_pm_set_sniff_policy(tBTA_DM_PEER_DEVICE* p_dev,
+ bool bDisable) {
+ uint16_t policy_setting;
+
+ if (!p_dev) return;
+
+ if (bDisable) {
+ policy_setting =
+ bta_dm_cb.cur_policy & (HCI_ENABLE_MASTER_SLAVE_SWITCH |
+ HCI_ENABLE_HOLD_MODE | HCI_ENABLE_PARK_MODE);
+
+ } else {
+ /* allow sniff after sco is closed */
+ policy_setting = bta_dm_cb.cur_policy;
+ }
+
+ /* if disabling SNIFF, make sure link is Active */
+ if (bDisable) bta_dm_pm_active(p_dev->peer_bdaddr);
+
+ /* update device record and set link policy */
+ p_dev->link_policy = policy_setting;
+ BTM_SetLinkPolicy(p_dev->peer_bdaddr, &policy_setting);
+}
+
+/*******************************************************************************
+ *
* Function bta_dm_pm_obtain_controller_state
*
* Description This function obtains the consolidated controller power
diff --git a/bta/gatt/bta_gattc_act.cc b/bta/gatt/bta_gattc_act.cc
index 800e6e255..3ff55b19c 100644
--- a/bta/gatt/bta_gattc_act.cc
+++ b/bta/gatt/bta_gattc_act.cc
@@ -25,22 +25,24 @@
#define LOG_TAG "bt_bta_gattc"
-#include <base/bind.h>
-#include <base/strings/stringprintf.h>
+#include <string.h>
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/gatt/bta_gattc_int.h"
-#include "bta/hh/bta_hh_int.h"
+#include <base/callback.h>
+#include "bt_common.h"
+#include "bt_target.h"
+#include "bta_gattc_int.h"
+#include "bta_sys.h"
#include "btif/include/btif_debug_conn.h"
-#include "device/include/controller.h"
+#include "l2c_api.h"
#include "osi/include/log.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/include/btm_ble_api_types.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "stack/include/l2c_api.h"
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
+#include "osi/include/osi.h"
+#include "stack/include/btu.h"
+#include "stack/l2cap/l2c_int.h"
+#include "utl.h"
+
+#if (BTA_HH_LE_INCLUDED == TRUE)
+#include "bta_hh_int.h"
+#endif
using base::StringPrintf;
using bluetooth::Uuid;
@@ -65,21 +67,20 @@ static void bta_gattc_enc_cmpl_cback(tGATT_IF gattc_if, const RawAddress& bda);
static void bta_gattc_cong_cback(uint16_t conn_id, bool congested);
static void bta_gattc_phy_update_cback(tGATT_IF gatt_if, uint16_t conn_id,
uint8_t tx_phy, uint8_t rx_phy,
- tGATT_STATUS status);
+ uint8_t status);
static void bta_gattc_conn_update_cback(tGATT_IF gatt_if, uint16_t conn_id,
uint16_t interval, uint16_t latency,
- uint16_t timeout, tGATT_STATUS status);
-
-static tGATT_CBACK bta_gattc_cl_cback = {
- .p_conn_cb = bta_gattc_conn_cback,
- .p_cmpl_cb = bta_gattc_cmpl_cback,
- .p_disc_res_cb = bta_gattc_disc_res_cback,
- .p_disc_cmpl_cb = bta_gattc_disc_cmpl_cback,
- .p_req_cb = nullptr,
- .p_enc_cmpl_cb = bta_gattc_enc_cmpl_cback,
- .p_congestion_cb = bta_gattc_cong_cback,
- .p_phy_update_cb = bta_gattc_phy_update_cback,
- .p_conn_update_cb = bta_gattc_conn_update_cback};
+ uint16_t timeout, uint8_t status);
+
+static tGATT_CBACK bta_gattc_cl_cback = {bta_gattc_conn_cback,
+ bta_gattc_cmpl_cback,
+ bta_gattc_disc_res_cback,
+ bta_gattc_disc_cmpl_cback,
+ NULL,
+ bta_gattc_enc_cmpl_cback,
+ bta_gattc_cong_cback,
+ bta_gattc_phy_update_cback,
+ bta_gattc_conn_update_cback};
/* opcode(tGATTC_OPTYPE) order has to be comply with internal event order */
static uint16_t bta_gattc_opcode_to_int_evt[] = {
@@ -139,9 +140,13 @@ void bta_gattc_disable() {
bta_gattc_cb.state = BTA_GATTC_STATE_DISABLING;
/* don't deregister HH GATT IF */
/* HH GATT IF will be deregistered by bta_hh_le_deregister when disable HH */
+#if (BTA_HH_LE_INCLUDED == TRUE)
if (!bta_hh_le_is_hh_gatt_if(bta_gattc_cb.cl_rcb[i].client_if)) {
+#endif
bta_gattc_deregister(&bta_gattc_cb.cl_rcb[i]);
+#if (BTA_HH_LE_INCLUDED == TRUE)
}
+#endif
}
/* no registered apps, indicate disable completed */
@@ -163,7 +168,7 @@ void bta_gattc_start_if(uint8_t client_if) {
/** Register a GATT client application with BTA */
void bta_gattc_register(const Uuid& app_uuid, tBTA_GATTC_CBACK* p_cback,
- BtaAppRegisterCallback cb, bool eatt_suppport) {
+ BtaAppRegisterCallback cb) {
tGATT_STATUS status = GATT_NO_RESOURCES;
uint8_t client_if = 0;
VLOG(1) << __func__ << ": state:" << +bta_gattc_cb.state;
@@ -175,9 +180,8 @@ void bta_gattc_register(const Uuid& app_uuid, tBTA_GATTC_CBACK* p_cback,
/* todo need to check duplicate uuid */
for (uint8_t i = 0; i < BTA_GATTC_CL_MAX; i++) {
if (!bta_gattc_cb.cl_rcb[i].in_use) {
- if ((bta_gattc_cb.cl_rcb[i].client_if = GATT_Register(
- app_uuid, "GattClient", &bta_gattc_cl_cback, eatt_suppport)) ==
- 0) {
+ if ((bta_gattc_cb.cl_rcb[i].client_if =
+ GATT_Register(app_uuid, &bta_gattc_cl_cback)) == 0) {
LOG(ERROR) << "Register with GATT stack failed.";
status = GATT_ERROR;
} else {
@@ -208,13 +212,8 @@ void bta_gattc_deregister(tBTA_GATTC_RCB* p_clreg) {
return;
}
- uint8_t accept_list_size = 0;
- if (controller_get_interface()->supports_ble()) {
- accept_list_size = controller_get_interface()->get_ble_acceptlist_size();
- }
-
/* remove bg connection associated with this rcb */
- for (uint8_t i = 0; i < accept_list_size; i++) {
+ for (uint8_t i = 0; i < BTM_GetWhiteListSize(); i++) {
if (!bta_gattc_cb.bg_track[i].in_use) continue;
if (bta_gattc_cb.bg_track[i].cif_mask & (1 << (p_clreg->client_if - 1))) {
@@ -237,7 +236,7 @@ void bta_gattc_deregister(tBTA_GATTC_RCB* p_clreg) {
p_clreg->dereg_pending = true;
- BT_HDR_RIGID buf;
+ BT_HDR buf;
buf.event = BTA_GATTC_API_CLOSE_EVT;
buf.layer_specific = bta_gattc_cb.clcb[i].bta_conn_id;
bta_gattc_close(&bta_gattc_cb.clcb[i], (tBTA_GATTC_DATA*)&buf);
@@ -245,8 +244,8 @@ void bta_gattc_deregister(tBTA_GATTC_RCB* p_clreg) {
}
/** process connect API request */
-void bta_gattc_process_api_open(const tBTA_GATTC_DATA* p_msg) {
- uint16_t event = ((BT_HDR_RIGID*)p_msg)->event;
+void bta_gattc_process_api_open(tBTA_GATTC_DATA* p_msg) {
+ uint16_t event = ((BT_HDR*)p_msg)->event;
tBTA_GATTC_RCB* p_clreg = bta_gattc_cl_get_regcb(p_msg->api_conn.client_if);
if (!p_clreg) {
@@ -275,21 +274,17 @@ void bta_gattc_process_api_open(const tBTA_GATTC_DATA* p_msg) {
}
/** process connect API request */
-void bta_gattc_process_api_open_cancel(const tBTA_GATTC_DATA* p_msg) {
- CHECK(p_msg != nullptr);
-
- uint16_t event = ((BT_HDR_RIGID*)p_msg)->event;
+void bta_gattc_process_api_open_cancel(tBTA_GATTC_DATA* p_msg) {
+ uint16_t event = ((BT_HDR*)p_msg)->event;
if (!p_msg->api_cancel_conn.is_direct) {
- LOG_DEBUG("Cancel GATT client background connection");
bta_gattc_cancel_bk_conn(&p_msg->api_cancel_conn);
return;
}
- LOG_DEBUG("Cancel GATT client direct connection");
tBTA_GATTC_CLCB* p_clcb = bta_gattc_find_clcb_by_cif(
p_msg->api_cancel_conn.client_if, p_msg->api_cancel_conn.remote_bda,
- BT_TRANSPORT_LE);
+ GATT_TRANSPORT_LE);
if (p_clcb != NULL) {
bta_gattc_sm_execute(p_clcb, event, p_msg);
return;
@@ -323,7 +318,7 @@ void bta_gattc_process_enc_cmpl(tGATT_IF client_if, const RawAddress& bda) {
}
void bta_gattc_cancel_open_error(tBTA_GATTC_CLCB* p_clcb,
- UNUSED_ATTR const tBTA_GATTC_DATA* p_data) {
+ UNUSED_ATTR tBTA_GATTC_DATA* p_data) {
tBTA_GATTC cb_data;
cb_data.status = GATT_ERROR;
@@ -333,7 +328,7 @@ void bta_gattc_cancel_open_error(tBTA_GATTC_CLCB* p_clcb,
}
void bta_gattc_open_error(tBTA_GATTC_CLCB* p_clcb,
- UNUSED_ATTR const tBTA_GATTC_DATA* p_data) {
+ UNUSED_ATTR tBTA_GATTC_DATA* p_data) {
LOG(ERROR) << "Connection already opened. wrong state";
bta_gattc_send_open_cback(p_clcb->p_rcb, GATT_SUCCESS, p_clcb->bda,
@@ -341,7 +336,7 @@ void bta_gattc_open_error(tBTA_GATTC_CLCB* p_clcb,
}
void bta_gattc_open_fail(tBTA_GATTC_CLCB* p_clcb,
- UNUSED_ATTR const tBTA_GATTC_DATA* p_data) {
+ UNUSED_ATTR tBTA_GATTC_DATA* p_data) {
LOG(WARNING) << __func__ << ": Cannot establish Connection. conn_id="
<< loghex(p_clcb->bta_conn_id) << ". Return GATT_ERROR("
<< +GATT_ERROR << ")";
@@ -353,7 +348,7 @@ void bta_gattc_open_fail(tBTA_GATTC_CLCB* p_clcb,
}
/** Process API connection function */
-void bta_gattc_open(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_open(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
tBTA_GATTC_DATA gattc_data;
/* open/hold a connection */
@@ -378,11 +373,11 @@ void bta_gattc_open(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
}
/** Process API Open for a background connection */
-void bta_gattc_init_bk_conn(const tBTA_GATTC_API_OPEN* p_data,
+void bta_gattc_init_bk_conn(tBTA_GATTC_API_OPEN* p_data,
tBTA_GATTC_RCB* p_clreg) {
if (!bta_gattc_mark_bg_conn(p_data->client_if, p_data->remote_bda, true)) {
bta_gattc_send_open_cback(p_clreg, GATT_NO_RESOURCES, p_data->remote_bda,
- GATT_INVALID_CONN_ID, BT_TRANSPORT_LE, 0);
+ GATT_INVALID_CONN_ID, GATT_TRANSPORT_LE, 0);
return;
}
@@ -392,7 +387,7 @@ void bta_gattc_init_bk_conn(const tBTA_GATTC_API_OPEN* p_data,
LOG(ERROR) << __func__
<< " unable to connect to remote bd_addr=" << p_data->remote_bda;
bta_gattc_send_open_cback(p_clreg, GATT_ERROR, p_data->remote_bda,
- GATT_INVALID_CONN_ID, BT_TRANSPORT_LE, 0);
+ GATT_INVALID_CONN_ID, GATT_TRANSPORT_LE, 0);
return;
}
@@ -404,19 +399,18 @@ void bta_gattc_init_bk_conn(const tBTA_GATTC_API_OPEN* p_data,
}
tBTA_GATTC_CLCB* p_clcb = bta_gattc_find_alloc_clcb(
- p_data->client_if, p_data->remote_bda, BT_TRANSPORT_LE);
+ p_data->client_if, p_data->remote_bda, GATT_TRANSPORT_LE);
if (!p_clcb) return;
tBTA_GATTC_DATA gattc_data;
gattc_data.hdr.layer_specific = p_clcb->bta_conn_id = conn_id;
/* open connection */
- bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CONN_EVT,
- static_cast<const tBTA_GATTC_DATA*>(&gattc_data));
+ bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_CONN_EVT, &gattc_data);
}
/** Process API Cancel Open for a background connection */
-void bta_gattc_cancel_bk_conn(const tBTA_GATTC_API_CANCEL_OPEN* p_data) {
+void bta_gattc_cancel_bk_conn(tBTA_GATTC_API_CANCEL_OPEN* p_data) {
tBTA_GATTC_RCB* p_clreg;
tBTA_GATTC cb_data;
cb_data.status = GATT_ERROR;
@@ -437,7 +431,7 @@ void bta_gattc_cancel_bk_conn(const tBTA_GATTC_API_CANCEL_OPEN* p_data) {
}
void bta_gattc_cancel_open_ok(tBTA_GATTC_CLCB* p_clcb,
- UNUSED_ATTR const tBTA_GATTC_DATA* p_data) {
+ UNUSED_ATTR tBTA_GATTC_DATA* p_data) {
tBTA_GATTC cb_data;
if (p_clcb->p_rcb->p_cback) {
@@ -448,8 +442,7 @@ void bta_gattc_cancel_open_ok(tBTA_GATTC_CLCB* p_clcb,
bta_gattc_clcb_dealloc(p_clcb);
}
-void bta_gattc_cancel_open(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_cancel_open(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
tBTA_GATTC cb_data;
if (GATT_CancelConnect(p_clcb->p_rcb->client_if,
@@ -464,7 +457,7 @@ void bta_gattc_cancel_open(tBTA_GATTC_CLCB* p_clcb,
}
/** receive connection callback from stack */
-void bta_gattc_conn(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_conn(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
tGATT_IF gatt_if;
VLOG(1) << __func__ << ": server cache state=" << +p_clcb->p_srcb->state;
@@ -501,12 +494,6 @@ void bta_gattc_conn(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
/* a pending service handle change indication */
if (p_clcb->p_srcb->srvc_hdl_chg) {
p_clcb->p_srcb->srvc_hdl_chg = false;
-
- /* set true to read database hash before service discovery */
- if (bta_gattc_is_robust_caching_enabled()) {
- p_clcb->p_srcb->srvc_hdl_db_hash = true;
- }
-
/* start discovery */
bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL);
}
@@ -514,7 +501,7 @@ void bta_gattc_conn(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
if (p_clcb->p_rcb) {
/* there is no RM for GATT */
- if (p_clcb->transport == BT_TRANSPORT_BR_EDR)
+ if (p_clcb->transport == BTA_TRANSPORT_BR_EDR)
bta_sys_conn_open(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda);
bta_gattc_send_open_cback(p_clcb->p_rcb, GATT_SUCCESS, p_clcb->bda,
@@ -524,8 +511,7 @@ void bta_gattc_conn(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
}
/** close a connection */
-void bta_gattc_close_fail(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_close_fail(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
tBTA_GATTC cb_data;
if (p_clcb->p_rcb->p_cback) {
@@ -533,6 +519,7 @@ void bta_gattc_close_fail(tBTA_GATTC_CLCB* p_clcb,
cb_data.close.client_if = p_clcb->p_rcb->client_if;
cb_data.close.conn_id = p_data->hdr.layer_specific;
cb_data.close.remote_bda = p_clcb->bda;
+ cb_data.close.status = GATT_ERROR;
cb_data.close.reason = BTA_GATT_CONN_NONE;
LOG(WARNING) << __func__ << ": conn_id=" << loghex(cb_data.close.conn_id)
@@ -543,39 +530,29 @@ void bta_gattc_close_fail(tBTA_GATTC_CLCB* p_clcb,
}
/** close a GATTC connection */
-void bta_gattc_close(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_close(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
tBTA_GATTC_CBACK* p_cback = p_clcb->p_rcb->p_cback;
tBTA_GATTC_RCB* p_clreg = p_clcb->p_rcb;
- tBTA_GATTC cb_data = {
- .close =
- {
- .client_if = p_clcb->p_rcb->client_if,
- .conn_id = p_clcb->bta_conn_id,
- .reason = GATT_CONN_OK,
- .remote_bda = p_clcb->bda,
- .status = GATT_SUCCESS,
- },
- };
-
- if (p_clcb->transport == BT_TRANSPORT_BR_EDR)
+ tBTA_GATTC cb_data;
+
+ VLOG(1) << __func__ << ": conn_id=" << loghex(p_clcb->bta_conn_id);
+
+ cb_data.close.client_if = p_clcb->p_rcb->client_if;
+ cb_data.close.conn_id = p_clcb->bta_conn_id;
+ cb_data.close.reason = p_clcb->reason;
+ cb_data.close.status = p_clcb->status;
+ cb_data.close.remote_bda = p_clcb->bda;
+
+ if (p_clcb->transport == BTA_TRANSPORT_BR_EDR)
bta_sys_conn_close(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda);
bta_gattc_clcb_dealloc(p_clcb);
if (p_data->hdr.event == BTA_GATTC_API_CLOSE_EVT) {
- GATT_Disconnect(p_data->hdr.layer_specific);
- LOG_DEBUG("Local close event client_if:%hu conn_id:%hu reason:%s",
- cb_data.close.client_if, cb_data.close.conn_id,
- gatt_disconnection_reason_text(
- static_cast<tGATT_DISCONN_REASON>(cb_data.close.reason))
- .c_str());
+ cb_data.close.status = GATT_Disconnect(p_data->hdr.layer_specific);
} else if (p_data->hdr.event == BTA_GATTC_INT_DISCONN_EVT) {
+ cb_data.close.status = p_data->int_conn.reason;
cb_data.close.reason = p_data->int_conn.reason;
- LOG_DEBUG("Peer close disconnect event client_if:%hu conn_id:%hu reason:%s",
- cb_data.close.client_if, cb_data.close.conn_id,
- gatt_disconnection_reason_text(
- static_cast<tGATT_DISCONN_REASON>(cb_data.close.reason))
- .c_str());
}
if (p_cback) (*p_cback)(BTA_GATTC_CLOSE_EVT, &cb_data);
@@ -597,8 +574,7 @@ void bta_gattc_reset_discover_st(tBTA_GATTC_SERV* p_srcb, tGATT_STATUS status) {
}
/** close a GATTC connection while in discovery state */
-void bta_gattc_disc_close(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_disc_close(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
VLOG(1) << __func__
<< ": Discovery cancel conn_id=" << loghex(p_clcb->bta_conn_id);
@@ -624,8 +600,6 @@ void bta_gattc_set_discover_st(tBTA_GATTC_SERV* p_srcb) {
if (bta_gattc_cb.clcb[i].p_srcb == p_srcb) {
bta_gattc_cb.clcb[i].status = GATT_SUCCESS;
bta_gattc_cb.clcb[i].state = BTA_GATTC_DISCOVER_ST;
- bta_gattc_cb.clcb[i].request_during_discovery =
- BTA_GATTC_DISCOVER_REQ_NONE;
}
}
}
@@ -634,13 +608,13 @@ void bta_gattc_set_discover_st(tBTA_GATTC_SERV* p_srcb) {
* set status to be discovery cancel for current discovery.
*/
void bta_gattc_restart_discover(tBTA_GATTC_CLCB* p_clcb,
- UNUSED_ATTR const tBTA_GATTC_DATA* p_data) {
+ UNUSED_ATTR tBTA_GATTC_DATA* p_data) {
p_clcb->status = GATT_CANCEL;
p_clcb->auto_update = BTA_GATTC_DISC_WAITING;
}
/** Configure MTU size on the GATT connection */
-void bta_gattc_cfg_mtu(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_cfg_mtu(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
if (!bta_gattc_enqueue(p_clcb, p_data)) return;
tGATT_STATUS status =
@@ -656,23 +630,9 @@ void bta_gattc_cfg_mtu(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
}
}
-void bta_gattc_start_discover_internal(tBTA_GATTC_CLCB* p_clcb) {
- if (p_clcb->transport == BT_TRANSPORT_LE)
- L2CA_EnableUpdateBleConnParams(p_clcb->p_srcb->server_bda, false);
-
- bta_gattc_init_cache(p_clcb->p_srcb);
- p_clcb->status = bta_gattc_discover_pri_service(
- p_clcb->bta_conn_id, p_clcb->p_srcb, GATT_DISC_SRVC_ALL);
- if (p_clcb->status != GATT_SUCCESS) {
- LOG(ERROR) << "discovery on server failed";
- bta_gattc_reset_discover_st(p_clcb->p_srcb, p_clcb->status);
- } else
- p_clcb->disc_active = true;
-}
-
/** Start a discovery on server */
void bta_gattc_start_discover(tBTA_GATTC_CLCB* p_clcb,
- UNUSED_ATTR const tBTA_GATTC_DATA* p_data) {
+ UNUSED_ATTR tBTA_GATTC_DATA* p_data) {
VLOG(1) << __func__ << ": conn_id:" << loghex(p_clcb->bta_conn_id)
<< " p_clcb->p_srcb->state:" << +p_clcb->p_srcb->state;
@@ -685,24 +645,25 @@ void bta_gattc_start_discover(tBTA_GATTC_CLCB* p_clcb,
p_clcb->auto_update = BTA_GATTC_NO_SCHEDULE;
if (p_clcb->p_srcb != NULL) {
- /* set all srcb related clcb into discovery ST */
- bta_gattc_set_discover_st(p_clcb->p_srcb);
-
/* clear the service change mask */
p_clcb->p_srcb->srvc_hdl_chg = false;
p_clcb->p_srcb->update_count = 0;
p_clcb->p_srcb->state = BTA_GATTC_SERV_DISC_ACT;
- /* read db hash if db hash characteristic exists */
- if (bta_gattc_is_robust_caching_enabled() &&
- p_clcb->p_srcb->srvc_hdl_db_hash && bta_gattc_read_db_hash(p_clcb)) {
- LOG(INFO) << __func__
- << ": pending service discovery, read db hash first";
- p_clcb->p_srcb->srvc_hdl_db_hash = false;
- return;
- }
+ if (p_clcb->transport == BTA_TRANSPORT_LE)
+ L2CA_EnableUpdateBleConnParams(p_clcb->p_srcb->server_bda, false);
+
+ /* set all srcb related clcb into discovery ST */
+ bta_gattc_set_discover_st(p_clcb->p_srcb);
- bta_gattc_start_discover_internal(p_clcb);
+ bta_gattc_init_cache(p_clcb->p_srcb);
+ p_clcb->status = bta_gattc_discover_pri_service(
+ p_clcb->bta_conn_id, p_clcb->p_srcb, GATT_DISC_SRVC_ALL);
+ if (p_clcb->status != GATT_SUCCESS) {
+ LOG(ERROR) << "discovery on server failed";
+ bta_gattc_reset_discover_st(p_clcb->p_srcb, p_clcb->status);
+ } else
+ p_clcb->disc_active = true;
} else {
LOG(ERROR) << "unknown device, can not start discovery";
}
@@ -718,12 +679,12 @@ void bta_gattc_start_discover(tBTA_GATTC_CLCB* p_clcb,
/** discovery on server is finished */
void bta_gattc_disc_cmpl(tBTA_GATTC_CLCB* p_clcb,
- UNUSED_ATTR const tBTA_GATTC_DATA* p_data) {
- const tBTA_GATTC_DATA* p_q_cmd = p_clcb->p_q_cmd;
+ UNUSED_ATTR tBTA_GATTC_DATA* p_data) {
+ tBTA_GATTC_DATA* p_q_cmd = p_clcb->p_q_cmd;
VLOG(1) << __func__ << ": conn_id=" << loghex(p_clcb->bta_conn_id);
- if (p_clcb->transport == BT_TRANSPORT_LE)
+ if (p_clcb->transport == BTA_TRANSPORT_LE)
L2CA_EnableUpdateBleConnParams(p_clcb->p_srcb->server_bda, true);
p_clcb->p_srcb->state = BTA_GATTC_SERV_IDLE;
p_clcb->disc_active = false;
@@ -751,7 +712,8 @@ void bta_gattc_disc_cmpl(tBTA_GATTC_CLCB* p_clcb,
else if (p_q_cmd != NULL) {
p_clcb->p_q_cmd = NULL;
/* execute pending operation of link block still present */
- if (L2CA_IsLinkEstablished(p_clcb->p_srcb->server_bda, p_clcb->transport)) {
+ if (l2cu_find_lcb_by_bd_addr(p_clcb->p_srcb->server_bda,
+ p_clcb->transport)) {
bta_gattc_sm_execute(p_clcb, p_q_cmd->hdr.event, p_q_cmd);
}
/* if the command executed requeued the cmd, we don't
@@ -769,7 +731,7 @@ void bta_gattc_disc_cmpl(tBTA_GATTC_CLCB* p_clcb,
}
/** Read an attribute */
-void bta_gattc_read(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_read(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
if (!bta_gattc_enqueue(p_clcb, p_data)) return;
tGATT_STATUS status;
@@ -801,8 +763,7 @@ void bta_gattc_read(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
}
/** read multiple */
-void bta_gattc_read_multi(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_read_multi(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
if (!bta_gattc_enqueue(p_clcb, p_data)) return;
tGATT_READ_PARAM read_param;
@@ -826,7 +787,7 @@ void bta_gattc_read_multi(tBTA_GATTC_CLCB* p_clcb,
}
/** Write an attribute */
-void bta_gattc_write(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_write(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
if (!bta_gattc_enqueue(p_clcb, p_data)) return;
tGATT_STATUS status = GATT_SUCCESS;
@@ -855,7 +816,7 @@ void bta_gattc_write(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
}
/** send execute write */
-void bta_gattc_execute(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_execute(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
if (!bta_gattc_enqueue(p_clcb, p_data)) return;
tGATT_STATUS status =
@@ -870,15 +831,15 @@ void bta_gattc_execute(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
}
/** send handle value confirmation */
-void bta_gattc_confirm(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
- uint16_t cid = p_data->api_confirm.cid;
+void bta_gattc_confirm(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
+ uint16_t handle = p_data->api_confirm.handle;
if (GATTC_SendHandleValueConfirm(p_data->api_confirm.hdr.layer_specific,
- cid) != GATT_SUCCESS) {
- LOG(ERROR) << __func__ << ": to cid=" << loghex(cid) << " failed";
+ handle) != GATT_SUCCESS) {
+ LOG(ERROR) << __func__ << ": to handle=" << loghex(handle) << " failed";
} else {
/* if over BR_EDR, inform PM for mode change */
- if (p_clcb->transport == BT_TRANSPORT_BR_EDR) {
+ if (p_clcb->transport == BTA_TRANSPORT_BR_EDR) {
bta_sys_busy(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda);
bta_sys_idle(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda);
}
@@ -886,8 +847,7 @@ void bta_gattc_confirm(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
}
/** read complete */
-static void bta_gattc_read_cmpl(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_OP_CMPL* p_data) {
+void bta_gattc_read_cmpl(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_OP_CMPL* p_data) {
GATT_READ_OP_CB cb = p_clcb->p_q_cmd->api_read.read_cb;
void* my_cb_data = p_clcb->p_q_cmd->api_read.read_cb_data;
@@ -907,8 +867,7 @@ static void bta_gattc_read_cmpl(tBTA_GATTC_CLCB* p_clcb,
}
/** write complete */
-static void bta_gattc_write_cmpl(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_OP_CMPL* p_data) {
+void bta_gattc_write_cmpl(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_OP_CMPL* p_data) {
GATT_WRITE_OP_CB cb = p_clcb->p_q_cmd->api_write.write_cb;
void* my_cb_data = p_clcb->p_q_cmd->api_write.write_cb_data;
@@ -921,8 +880,7 @@ static void bta_gattc_write_cmpl(tBTA_GATTC_CLCB* p_clcb,
}
/** execute write complete */
-static void bta_gattc_exec_cmpl(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_OP_CMPL* p_data) {
+void bta_gattc_exec_cmpl(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_OP_CMPL* p_data) {
tBTA_GATTC cb_data;
osi_free_and_reset((void**)&p_clcb->p_q_cmd);
@@ -936,10 +894,8 @@ static void bta_gattc_exec_cmpl(tBTA_GATTC_CLCB* p_clcb,
}
/** configure MTU operation complete */
-static void bta_gattc_cfg_mtu_cmpl(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_OP_CMPL* p_data) {
- GATT_CONFIGURE_MTU_OP_CB cb = p_clcb->p_q_cmd->api_mtu.mtu_cb;
- void* my_cb_data = p_clcb->p_q_cmd->api_mtu.mtu_cb_data;
+void bta_gattc_cfg_mtu_cmpl(tBTA_GATTC_CLCB* p_clcb,
+ tBTA_GATTC_OP_CMPL* p_data) {
tBTA_GATTC cb_data;
osi_free_and_reset((void**)&p_clcb->p_q_cmd);
@@ -953,40 +909,31 @@ static void bta_gattc_cfg_mtu_cmpl(tBTA_GATTC_CLCB* p_clcb,
cb_data.cfg_mtu.status = p_data->status;
cb_data.cfg_mtu.mtu = p_clcb->p_srcb->mtu;
- if (cb) {
- cb(p_clcb->bta_conn_id, p_data->status, my_cb_data);
- }
-
(*p_clcb->p_rcb->p_cback)(BTA_GATTC_CFG_MTU_EVT, &cb_data);
}
/** operation completed */
-void bta_gattc_op_cmpl(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
- if (p_clcb->p_q_cmd == NULL) {
- LOG_ERROR("No pending command gatt client command");
+void bta_gattc_op_cmpl(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
+ uint8_t op = (uint8_t)p_data->op_cmpl.op_code;
+ uint8_t mapped_op = 0;
+
+ VLOG(1) << __func__ << ": op:" << +op;
+
+ if (op == GATTC_OPTYPE_INDICATION || op == GATTC_OPTYPE_NOTIFICATION) {
+ LOG(ERROR) << "unexpected operation, ignored";
return;
}
- const tGATTC_OPTYPE op = p_data->op_cmpl.op_code;
- switch (op) {
- case GATTC_OPTYPE_READ:
- case GATTC_OPTYPE_WRITE:
- case GATTC_OPTYPE_EXE_WRITE:
- case GATTC_OPTYPE_CONFIG:
- break;
+ if (op < GATTC_OPTYPE_READ) return;
- case GATTC_OPTYPE_NONE:
- case GATTC_OPTYPE_DISCOVERY:
- case GATTC_OPTYPE_NOTIFICATION:
- case GATTC_OPTYPE_INDICATION:
- default:
- LOG(ERROR) << "unexpected operation, ignored";
- return;
+ if (p_clcb->p_q_cmd == NULL) {
+ LOG(ERROR) << "No pending command";
+ return;
}
if (p_clcb->p_q_cmd->hdr.event !=
bta_gattc_opcode_to_int_evt[op - GATTC_OPTYPE_READ]) {
- uint8_t mapped_op =
+ mapped_op =
p_clcb->p_q_cmd->hdr.event - BTA_GATTC_API_READ_EVT + GATTC_OPTYPE_READ;
if (mapped_op > GATTC_OPTYPE_INDICATION) mapped_op = 0;
@@ -1004,8 +951,7 @@ void bta_gattc_op_cmpl(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
p_clcb->p_srcb->srvc_hdl_chg && op != GATTC_OPTYPE_CONFIG) {
VLOG(1) << "Discard all responses when service change indication is "
"received.";
- // TODO Fix constness
- const_cast<tBTA_GATTC_DATA*>(p_data)->op_cmpl.status = GATT_ERROR;
+ p_data->op_cmpl.status = GATT_ERROR;
}
/* service handle change void the response, discard it */
@@ -1021,32 +967,22 @@ void bta_gattc_op_cmpl(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
else if (op == GATTC_OPTYPE_CONFIG)
bta_gattc_cfg_mtu_cmpl(p_clcb, &p_data->op_cmpl);
- // If receive DATABASE_OUT_OF_SYNC error code, bta_gattc should start service
- // discovery immediately
- if (bta_gattc_is_robust_caching_enabled() &&
- p_data->op_cmpl.status == GATT_DATABASE_OUT_OF_SYNC) {
- LOG(INFO) << __func__ << ": DATABASE_OUT_OF_SYNC, re-discover service";
- p_clcb->auto_update = BTA_GATTC_REQ_WAITING;
- /* request read db hash first */
- p_clcb->p_srcb->srvc_hdl_db_hash = true;
- bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL);
- return;
- }
-
if (p_clcb->auto_update == BTA_GATTC_DISC_WAITING) {
p_clcb->auto_update = BTA_GATTC_REQ_WAITING;
-
- /* request read db hash first */
- if (bta_gattc_is_robust_caching_enabled()) {
- p_clcb->p_srcb->srvc_hdl_db_hash = true;
- }
-
bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL);
}
}
+/** operation completed */
+void bta_gattc_ignore_op_cmpl(UNUSED_ATTR tBTA_GATTC_CLCB* p_clcb,
+ tBTA_GATTC_DATA* p_data) {
+ /* receive op complete when discovery is started, ignore the response,
+ and wait for discovery finish and resent */
+ VLOG(1) << __func__ << ": op = " << +p_data->hdr.layer_specific;
+}
+
/** start a search in the local server cache */
-void bta_gattc_search(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_search(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
tGATT_STATUS status = GATT_INTERNAL_ERROR;
tBTA_GATTC cb_data;
VLOG(1) << __func__ << ": conn_id=" << loghex(p_clcb->bta_conn_id);
@@ -1064,13 +1000,13 @@ void bta_gattc_search(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
/** enqueue a command into control block, usually because discovery operation is
* busy */
-void bta_gattc_q_cmd(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
+void bta_gattc_q_cmd(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
bta_gattc_enqueue(p_clcb, p_data);
}
/** report API call failure back to apps */
void bta_gattc_fail(tBTA_GATTC_CLCB* p_clcb,
- UNUSED_ATTR const tBTA_GATTC_DATA* p_data) {
+ UNUSED_ATTR tBTA_GATTC_DATA* p_data) {
if (p_clcb->status == GATT_SUCCESS) {
LOG(ERROR) << "operation not supported at current state " << +p_clcb->state;
}
@@ -1104,18 +1040,17 @@ static void bta_gattc_conn_cback(tGATT_IF gattc_if, const RawAddress& bdaddr,
uint16_t conn_id, bool connected,
tGATT_DISCONN_REASON reason,
tBT_TRANSPORT transport) {
- if (connected) {
- LOG_INFO("Connected att_id:%hhu transport:%s reason:%s", gattc_if,
- bt_transport_text(transport).c_str(),
- gatt_disconnection_reason_text(reason).c_str());
- btif_debug_conn_state(bdaddr, BTIF_DEBUG_CONNECTED, GATT_CONN_UNKNOWN);
- } else {
- LOG_INFO("Disconnected att_id:%hhu transport:%s reason:%s", gattc_if,
- bt_transport_text(transport).c_str(),
- gatt_disconnection_reason_text(reason).c_str());
- btif_debug_conn_state(bdaddr, BTIF_DEBUG_DISCONNECTED, GATT_CONN_UNKNOWN);
+ if (reason != 0) {
+ LOG(WARNING) << __func__ << ": cif=" << +gattc_if
+ << " connected=" << connected << " conn_id=" << loghex(conn_id)
+ << " reason=" << loghex(reason);
}
+ if (connected)
+ btif_debug_conn_state(bdaddr, BTIF_DEBUG_CONNECTED, GATT_CONN_UNKNOWN);
+ else
+ btif_debug_conn_state(bdaddr, BTIF_DEBUG_DISCONNECTED, reason);
+
tBTA_GATTC_DATA* p_buf =
(tBTA_GATTC_DATA*)osi_calloc(sizeof(tBTA_GATTC_DATA));
p_buf->int_conn.hdr.event =
@@ -1133,10 +1068,11 @@ static void bta_gattc_conn_cback(tGATT_IF gattc_if, const RawAddress& bdaddr,
/** encryption complete callback function to GATT client stack */
static void bta_gattc_enc_cmpl_cback(tGATT_IF gattc_if, const RawAddress& bda) {
tBTA_GATTC_CLCB* p_clcb =
- bta_gattc_find_clcb_by_cif(gattc_if, bda, BT_TRANSPORT_LE);
+ bta_gattc_find_clcb_by_cif(gattc_if, bda, GATT_TRANSPORT_LE);
if (p_clcb == NULL) return;
+#if (BTA_HH_LE_INCLUDED == TRUE)
/* filter this event just for BTA HH LE GATT client,
* In the future, if we want to enable encryption complete event
* for all GATT clients, we can remove this code
@@ -1144,6 +1080,7 @@ static void bta_gattc_enc_cmpl_cback(tGATT_IF gattc_if, const RawAddress& bda) {
if (!bta_hh_le_is_hh_gatt_if(gattc_if)) {
return;
}
+#endif
VLOG(1) << __func__ << ": cif:" << +gattc_if;
@@ -1235,23 +1172,16 @@ bool bta_gattc_process_srvc_chg_ind(uint16_t conn_id, tBTA_GATTC_RCB* p_clrcb,
}
}
/* send confirmation here if this is an indication, it should always be */
- GATTC_SendHandleValueConfirm(conn_id, p_notify->cid);
+ GATTC_SendHandleValueConfirm(conn_id, att_value->handle);
/* if connection available, refresh cache by doing discovery now */
- if (p_clcb) {
- /* request read db hash first */
- if (bta_gattc_is_robust_caching_enabled()) {
- p_srcb->srvc_hdl_db_hash = true;
- }
- bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL);
- }
+ if (p_clcb) bta_gattc_sm_execute(p_clcb, BTA_GATTC_INT_DISCOVER_EVT, NULL);
}
/* notify applicationf or service change */
if (p_clrcb->p_cback) {
tBTA_GATTC bta_gattc;
- bta_gattc.service_changed.remote_bda = p_srcb->server_bda;
- bta_gattc.service_changed.conn_id = conn_id;
+ bta_gattc.remote_bda = p_srcb->server_bda;
(*p_clrcb->p_cback)(BTA_GATTC_SRVC_CHG_EVT, &bta_gattc);
}
@@ -1288,12 +1218,12 @@ void bta_gattc_process_indicate(uint16_t conn_id, tGATTC_OPTYPE op,
tBTA_GATTC_NOTIFY notify;
RawAddress remote_bda;
tGATT_IF gatt_if;
- tBT_TRANSPORT transport;
+ tBTA_TRANSPORT transport;
if (!GATT_GetConnectionInfor(conn_id, &gatt_if, remote_bda, &transport)) {
LOG(ERROR) << __func__ << ": indication/notif for unknown app";
if (op == GATTC_OPTYPE_INDICATION)
- GATTC_SendHandleValueConfirm(conn_id, p_data->cid);
+ GATTC_SendHandleValueConfirm(conn_id, handle);
return;
}
@@ -1301,7 +1231,7 @@ void bta_gattc_process_indicate(uint16_t conn_id, tGATTC_OPTYPE op,
if (p_clrcb == NULL) {
LOG(ERROR) << __func__ << ": indication/notif for unregistered app";
if (op == GATTC_OPTYPE_INDICATION)
- GATTC_SendHandleValueConfirm(conn_id, p_data->cid);
+ GATTC_SendHandleValueConfirm(conn_id, handle);
return;
}
@@ -1309,14 +1239,13 @@ void bta_gattc_process_indicate(uint16_t conn_id, tGATTC_OPTYPE op,
if (p_srcb == NULL) {
LOG(ERROR) << __func__ << ": indication/notif for unknown device, ignore";
if (op == GATTC_OPTYPE_INDICATION)
- GATTC_SendHandleValueConfirm(conn_id, p_data->cid);
+ GATTC_SendHandleValueConfirm(conn_id, handle);
return;
}
tBTA_GATTC_CLCB* p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id);
notify.handle = handle;
- notify.cid = p_data->cid;
/* if service change indication/notification, don't forward to application */
if (bta_gattc_process_srvc_chg_ind(conn_id, p_clrcb, p_srcb, p_clcb, &notify,
@@ -1346,7 +1275,7 @@ void bta_gattc_process_indicate(uint16_t conn_id, tGATTC_OPTYPE op,
/* no one intersted and need ack? */
else if (op == GATTC_OPTYPE_INDICATION) {
VLOG(1) << __func__ << " no one interested, ack now";
- GATTC_SendHandleValueConfirm(conn_id, p_data->cid);
+ GATTC_SendHandleValueConfirm(conn_id, handle);
}
}
@@ -1371,7 +1300,7 @@ static void bta_gattc_cmpl_cback(uint16_t conn_id, tGATTC_OPTYPE op,
}
/* if over BR_EDR, inform PM for mode change */
- if (p_clcb->transport == BT_TRANSPORT_BR_EDR) {
+ if (p_clcb->transport == BTA_TRANSPORT_BR_EDR) {
bta_sys_busy(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda);
bta_sys_idle(BTA_ID_GATTC, BTA_ALL_APP_ID, p_clcb->bda);
}
@@ -1413,7 +1342,7 @@ static void bta_gattc_cong_cback(uint16_t conn_id, bool congested) {
static void bta_gattc_phy_update_cback(tGATT_IF gatt_if, uint16_t conn_id,
uint8_t tx_phy, uint8_t rx_phy,
- tGATT_STATUS status) {
+ uint8_t status) {
tBTA_GATTC_RCB* p_clreg = bta_gattc_cl_get_regcb(gatt_if);
if (!p_clreg || !p_clreg->p_cback) {
@@ -1432,7 +1361,7 @@ static void bta_gattc_phy_update_cback(tGATT_IF gatt_if, uint16_t conn_id,
static void bta_gattc_conn_update_cback(tGATT_IF gatt_if, uint16_t conn_id,
uint16_t interval, uint16_t latency,
- uint16_t timeout, tGATT_STATUS status) {
+ uint16_t timeout, uint8_t status) {
tBTA_GATTC_RCB* p_clreg = bta_gattc_cl_get_regcb(gatt_if);
if (!p_clreg || !p_clreg->p_cback) {
diff --git a/bta/gatt/bta_gattc_api.cc b/bta/gatt/bta_gattc_api.cc
index 93af8c159..829084c5b 100644
--- a/bta/gatt/bta_gattc_api.cc
+++ b/bta/gatt/bta_gattc_api.cc
@@ -22,19 +22,19 @@
*
******************************************************************************/
-#include <base/bind.h>
-#include <ios>
-#include <list>
-#include <memory>
-#include <vector>
+#include "bt_target.h"
-#include "bt_target.h" // Must be first to define build configuration
+#include <string.h>
-#include "bta/gatt/bta_gattc_int.h"
+#include <base/bind.h>
+#include <base/bind_helpers.h>
+#include <base/callback.h>
+#include "bt_common.h"
+#include "bta_gatt_api.h"
+#include "bta_gattc_int.h"
+#include "bta_sys.h"
#include "device/include/controller.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "types/bluetooth/uuid.h"
-#include "types/bt_transport.h"
+#include "stack/include/btu.h"
using bluetooth::Uuid;
@@ -72,13 +72,13 @@ void BTA_GATTC_Disable(void) {
* |cb| one time callback when registration is finished
*/
void BTA_GATTC_AppRegister(tBTA_GATTC_CBACK* p_client_cb,
- BtaAppRegisterCallback cb, bool eatt_support) {
+ BtaAppRegisterCallback cb) {
if (!bta_sys_is_register(BTA_ID_GATTC))
bta_sys_register(BTA_ID_GATTC, &bta_gattc_reg);
do_in_main_thread(
FROM_HERE, base::Bind(&bta_gattc_register, Uuid::GetRandom(), p_client_cb,
- std::move(cb), eatt_support));
+ std::move(cb)));
}
static void app_deregister_impl(tGATT_IF client_if) {
@@ -118,15 +118,16 @@ void BTA_GATTC_AppDeregister(tGATT_IF client_if) {
*
******************************************************************************/
void BTA_GATTC_Open(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct, bool opportunistic) {
+ bool is_direct, tGATT_TRANSPORT transport,
+ bool opportunistic) {
uint8_t phy = controller_get_interface()->get_le_all_initiating_phys();
- BTA_GATTC_Open(client_if, remote_bda, is_direct, BT_TRANSPORT_LE,
- opportunistic, phy);
+ BTA_GATTC_Open(client_if, remote_bda, is_direct, transport, opportunistic,
+ phy);
}
void BTA_GATTC_Open(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct, tBT_TRANSPORT transport, bool opportunistic,
- uint8_t initiating_phys) {
+ bool is_direct, tGATT_TRANSPORT transport,
+ bool opportunistic, uint8_t initiating_phys) {
tBTA_GATTC_API_OPEN* p_buf =
(tBTA_GATTC_API_OPEN*)osi_malloc(sizeof(tBTA_GATTC_API_OPEN));
@@ -181,7 +182,7 @@ void BTA_GATTC_CancelOpen(tGATT_IF client_if, const RawAddress& remote_bda,
*
******************************************************************************/
void BTA_GATTC_Close(uint16_t conn_id) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_GATTC_API_CLOSE_EVT;
p_buf->layer_specific = conn_id;
@@ -202,21 +203,13 @@ void BTA_GATTC_Close(uint16_t conn_id) {
* Returns void
*
******************************************************************************/
-
void BTA_GATTC_ConfigureMTU(uint16_t conn_id, uint16_t mtu) {
- BTA_GATTC_ConfigureMTU(conn_id, mtu, NULL, NULL);
-}
-
-void BTA_GATTC_ConfigureMTU(uint16_t conn_id, uint16_t mtu,
- GATT_CONFIGURE_MTU_OP_CB callback, void* cb_data) {
tBTA_GATTC_API_CFG_MTU* p_buf =
(tBTA_GATTC_API_CFG_MTU*)osi_malloc(sizeof(tBTA_GATTC_API_CFG_MTU));
p_buf->hdr.event = BTA_GATTC_API_CFG_MTU_EVT;
p_buf->hdr.layer_specific = conn_id;
p_buf->mtu = mtu;
- p_buf->mtu_cb = callback;
- p_buf->mtu_cb_data = cb_data;
bta_sys_sendmsg(p_buf);
}
@@ -238,7 +231,7 @@ void BTA_GATTC_ConfigureMTU(uint16_t conn_id, uint16_t mtu,
* Returns None
*
******************************************************************************/
-void BTA_GATTC_ServiceSearchRequest(uint16_t conn_id, const Uuid* p_srvc_uuid) {
+void BTA_GATTC_ServiceSearchRequest(uint16_t conn_id, Uuid* p_srvc_uuid) {
const size_t len = sizeof(tBTA_GATTC_API_SEARCH) + sizeof(Uuid);
tBTA_GATTC_API_SEARCH* p_buf = (tBTA_GATTC_API_SEARCH*)osi_calloc(len);
@@ -605,21 +598,21 @@ void BTA_GATTC_ExecuteWrite(uint16_t conn_id, bool is_execute) {
* Description This function is called to send handle value confirmation.
*
* Parameters conn_id - connection ID.
- * cid
+ * p_char_id - characteristic ID to confirm.
*
* Returns None
*
******************************************************************************/
-void BTA_GATTC_SendIndConfirm(uint16_t conn_id, uint16_t cid) {
+void BTA_GATTC_SendIndConfirm(uint16_t conn_id, uint16_t handle) {
tBTA_GATTC_API_CONFIRM* p_buf =
(tBTA_GATTC_API_CONFIRM*)osi_calloc(sizeof(tBTA_GATTC_API_CONFIRM));
- VLOG(1) << __func__ << ": conn_id=" << +conn_id << " cid=0x" << std::hex
- << +cid;
+ VLOG(1) << __func__ << ": conn_id=" << +conn_id << " handle=0x" << std::hex
+ << +handle;
p_buf->hdr.event = BTA_GATTC_API_CONFIRM_EVT;
p_buf->hdr.layer_specific = conn_id;
- p_buf->cid = cid;
+ p_buf->handle = handle;
bta_sys_sendmsg(p_buf);
}
diff --git a/bta/gatt/bta_gattc_cache.cc b/bta/gatt/bta_gattc_cache.cc
index 9e4d44324..eed1d67b1 100644
--- a/bta/gatt/bta_gattc_cache.cc
+++ b/bta/gatt/bta_gattc_cache.cc
@@ -25,19 +25,27 @@
#define LOG_TAG "bt_bta_gattc"
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <cstdio>
-#include <sstream>
+#include "bt_target.h"
-#include "bt_target.h" // Must be first to define build configuration
+#include <errno.h>
+#include <stdio.h>
+#include <string.h>
+#include <unistd.h>
+#include <sstream>
-#include "bta/gatt/bta_gattc_int.h"
-#include "bta/gatt/database.h"
+#include "bt_common.h"
+#include "bta_gattc_int.h"
+#include "bta_sys.h"
+#include "btm_api.h"
+#include "btm_ble_api.h"
+#include "btm_int.h"
+#include "database.h"
+#include "database_builder.h"
#include "osi/include/log.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/gatt_api.h"
-#include "types/bluetooth/uuid.h"
+#include "osi/include/osi.h"
+#include "sdp_api.h"
+#include "sdpdefs.h"
+#include "utl.h"
using base::StringPrintf;
using bluetooth::Uuid;
@@ -60,19 +68,10 @@ const Characteristic* bta_gattc_get_characteristic_srcb(tBTA_GATTC_SERV* p_srcb,
static void bta_gattc_explore_srvc_finished(uint16_t conn_id,
tBTA_GATTC_SERV* p_srvc_cb);
-static void bta_gattc_read_db_hash_cmpl(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_OP_CMPL* p_data);
-
-static void bta_gattc_read_ext_prop_desc_cmpl(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_OP_CMPL* p_data);
-
-// define the max retry count for DATABASE_OUT_OF_SYNC
-#define BTA_GATTC_DISCOVER_RETRY_COUNT 2
-
#define BTA_GATT_SDP_DB_SIZE 4096
#define GATT_CACHE_PREFIX "/data/misc/bluetooth/gatt_cache_"
-#define GATT_CACHE_VERSION 6
+#define GATT_CACHE_VERSION 5
static void bta_gattc_generate_cache_file_name(char* buffer, size_t buffer_len,
const RawAddress& bda) {
@@ -133,11 +132,11 @@ const Service* bta_gattc_find_matching_service(
/** Start primary service discovery */
tGATT_STATUS bta_gattc_discover_pri_service(uint16_t conn_id,
tBTA_GATTC_SERV* p_server_cb,
- tGATT_DISC_TYPE disc_type) {
+ uint8_t disc_type) {
tBTA_GATTC_CLCB* p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id);
if (!p_clcb) return GATT_ERROR;
- if (p_clcb->transport == BT_TRANSPORT_LE) {
+ if (p_clcb->transport == BTA_TRANSPORT_LE) {
return GATTC_Discover(conn_id, disc_type, 0x0001, 0xFFFF);
}
@@ -155,56 +154,16 @@ static void bta_gattc_explore_next_service(uint16_t conn_id,
return;
}
- if (p_srvc_cb->pending_discovery.StartNextServiceExploration()) {
- const auto& service =
- p_srvc_cb->pending_discovery.CurrentlyExploredService();
- VLOG(1) << "Start service discovery";
-
- /* start discovering included services */
- GATTC_Discover(conn_id, GATT_DISC_INC_SRVC, service.first, service.second);
+ if (!p_srvc_cb->pending_discovery.StartNextServiceExploration()) {
+ bta_gattc_explore_srvc_finished(conn_id, p_srvc_cb);
return;
}
- // No more services to discover
-
- // As part of service discovery, read the values of "Characteristic Extended
- // Properties" descriptor
- const auto& descriptors =
- p_srvc_cb->pending_discovery.DescriptorHandlesToRead();
- if (!descriptors.empty()) {
- // set request field to READ_EXT_PROP_DESC
- p_clcb->request_during_discovery =
- BTA_GATTC_DISCOVER_REQ_READ_EXT_PROP_DESC;
-
- if (p_srvc_cb->read_multiple_not_supported || descriptors.size() == 1) {
- tGATT_READ_PARAM read_param{
- .by_handle = {.handle = descriptors.front(),
- .auth_req = GATT_AUTH_REQ_NONE}};
- GATTC_Read(conn_id, GATT_READ_BY_HANDLE, &read_param);
- // asynchronous continuation in bta_gattc_op_cmpl_during_discovery
- return;
- }
-
- // TODO(jpawlowski): as a limit we should use MTU/2 rather than
- // GATT_MAX_READ_MULTI_HANDLES
- /* each descriptor contains just 2 bytes, so response size is same as
- * request size */
- size_t num_handles =
- std::min(descriptors.size(), (size_t)GATT_MAX_READ_MULTI_HANDLES);
-
- tGATT_READ_PARAM read_param;
- memset(&read_param, 0, sizeof(tGATT_READ_PARAM));
- read_param.read_multiple.num_handles = num_handles;
- read_param.read_multiple.auth_req = GATT_AUTH_REQ_NONE;
- memcpy(&read_param.read_multiple.handles, descriptors.data(),
- sizeof(uint16_t) * num_handles);
- GATTC_Read(conn_id, GATT_READ_MULTIPLE, &read_param);
+ const auto& service = p_srvc_cb->pending_discovery.CurrentlyExploredService();
+ VLOG(1) << "Start service discovery";
- // asynchronous continuation in bta_gattc_op_cmpl_during_discovery
- return;
- }
-
- bta_gattc_explore_srvc_finished(conn_id, p_srvc_cb);
+ /* start discovering included services */
+ GATTC_Discover(conn_id, GATT_DISC_INC_SRVC, service.first, service.second);
}
static void bta_gattc_explore_srvc_finished(uint16_t conn_id,
@@ -231,14 +190,6 @@ static void bta_gattc_explore_srvc_finished(uint16_t conn_id,
p_clcb->p_srcb->gatt_database.Serialize());
}
- // After success, reset the count.
- if (bta_gattc_is_robust_caching_enabled()) {
- LOG(INFO) << __func__
- << ": service discovery succeed, reset count to zero, conn_id="
- << loghex(conn_id);
- p_srvc_cb->srvc_disc_count = 0;
- }
-
bta_gattc_reset_discover_st(p_clcb->p_srcb, GATT_SUCCESS);
}
@@ -268,7 +219,7 @@ descriptor_discovery_done:
}
/* Process the discovery result from sdp */
-void bta_gattc_sdp_callback(tSDP_STATUS sdp_status, void* user_data) {
+void bta_gattc_sdp_callback(uint16_t sdp_status, void* user_data) {
tBTA_GATTC_CB_DATA* cb_data = (tBTA_GATTC_CB_DATA*)user_data;
tBTA_GATTC_SERV* p_srvc_cb = bta_gattc_find_scb_by_cid(cb_data->sdp_conn_id);
@@ -365,30 +316,6 @@ static tGATT_STATUS bta_gattc_sdp_service_disc(uint16_t conn_id,
return GATT_SUCCESS;
}
-/** operation completed */
-void bta_gattc_op_cmpl_during_discovery(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data) {
- // Currently, there are two cases needed to be handled.
- // 1. Read ext prop descriptor value after service discovery
- // 2. Read db hash before starting service discovery
- switch (p_clcb->request_during_discovery) {
- case BTA_GATTC_DISCOVER_REQ_READ_EXT_PROP_DESC:
- bta_gattc_read_ext_prop_desc_cmpl(p_clcb, &p_data->op_cmpl);
- break;
- case BTA_GATTC_DISCOVER_REQ_READ_DB_HASH:
- if (bta_gattc_is_robust_caching_enabled()) {
- bta_gattc_read_db_hash_cmpl(p_clcb, &p_data->op_cmpl);
- } else {
- // it is not possible here if flag is off, but just in case
- p_clcb->request_during_discovery = BTA_GATTC_DISCOVER_REQ_NONE;
- }
- break;
- case BTA_GATTC_DISCOVER_REQ_NONE:
- default:
- break;
- }
-}
-
/** callback function to GATT client stack */
void bta_gattc_disc_res_cback(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
tGATT_DISC_RES* p_data) {
@@ -422,40 +349,20 @@ void bta_gattc_disc_res_cback(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
case GATT_DISC_CHAR_DSCPT:
p_srvc_cb->pending_discovery.AddDescriptor(p_data->handle, p_data->type);
break;
-
- case GATT_DISC_MAX:
- default:
- LOG_ERROR("Received illegal discovery item");
- break;
}
}
void bta_gattc_disc_cmpl_cback(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
tGATT_STATUS status) {
tBTA_GATTC_CLCB* p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id);
- tBTA_GATTC_SERV* p_srvc_cb = bta_gattc_find_scb_by_cid(conn_id);
if (p_clcb && (status != GATT_SUCCESS || p_clcb->status != GATT_SUCCESS)) {
if (status == GATT_SUCCESS) p_clcb->status = status;
-
- // if db out of sync is received, try to start service discovery if possible
- if (bta_gattc_is_robust_caching_enabled() &&
- status == GATT_DATABASE_OUT_OF_SYNC) {
- if (p_srvc_cb &&
- p_srvc_cb->srvc_disc_count < BTA_GATTC_DISCOVER_RETRY_COUNT) {
- p_srvc_cb->srvc_disc_count++;
- p_clcb->auto_update = BTA_GATTC_DISC_WAITING;
- } else {
- LOG(ERROR) << __func__
- << ": retry limit exceeds for db out of sync, conn_id="
- << conn_id;
- }
- }
-
bta_gattc_sm_execute(p_clcb, BTA_GATTC_DISCOVER_CMPL_EVT, NULL);
return;
}
+ tBTA_GATTC_SERV* p_srvc_cb = bta_gattc_find_scb_by_cid(conn_id);
if (!p_srvc_cb) return;
switch (disc_type) {
@@ -488,11 +395,6 @@ void bta_gattc_disc_cmpl_cback(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
/* start discovering next characteristic for char descriptor */
bta_gattc_start_disc_char_dscp(conn_id, p_srvc_cb);
break;
-
- case GATT_DISC_MAX:
- default:
- LOG_ERROR("Received illegal discovery item");
- break;
}
}
@@ -623,125 +525,6 @@ const Characteristic* bta_gattc_get_owning_characteristic(uint16_t conn_id,
return bta_gattc_get_owning_characteristic_srcb(p_clcb->p_srcb, handle);
}
-/* request reading database hash */
-bool bta_gattc_read_db_hash(tBTA_GATTC_CLCB* p_clcb) {
- tGATT_READ_PARAM read_param;
- memset(&read_param, 0, sizeof(tGATT_READ_BY_TYPE));
-
- read_param.char_type.s_handle = 0x0001;
- read_param.char_type.e_handle = 0xFFFF;
- read_param.char_type.uuid = Uuid::From16Bit(GATT_UUID_DATABASE_HASH);
- read_param.char_type.auth_req = GATT_AUTH_REQ_NONE;
- tGATT_STATUS status =
- GATTC_Read(p_clcb->bta_conn_id, GATT_READ_BY_TYPE, &read_param);
-
- if (status != GATT_SUCCESS) return false;
- p_clcb->request_during_discovery = BTA_GATTC_DISCOVER_REQ_READ_DB_HASH;
-
- return true;
-}
-
-/* handle response of reading database hash */
-static void bta_gattc_read_db_hash_cmpl(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_OP_CMPL* p_data) {
- uint8_t op = (uint8_t)p_data->op_code;
- if (op != GATTC_OPTYPE_READ) {
- VLOG(1) << __func__ << ": op = " << +p_data->hdr.layer_specific;
- return;
- }
- p_clcb->request_during_discovery = BTA_GATTC_DISCOVER_REQ_NONE;
-
- // run match flow only if the status is success
- bool matched = false;
- if (p_data->status == GATT_SUCCESS) {
- // start to compare local hash and remote hash
- uint16_t len = p_data->p_cmpl->att_value.len;
- uint8_t* data = p_data->p_cmpl->att_value.value;
-
- Octet16 remote_hash;
- if (len == remote_hash.size()) {
- uint8_t idx = 0;
- auto it = remote_hash.begin();
- for (; idx < len; idx++, data++, it++) *it = *data;
-
- Octet16 local_hash = p_clcb->p_srcb->gatt_database.Hash();
- matched = (local_hash == remote_hash);
- }
- }
-
- if (matched) {
- LOG(INFO) << __func__ << ": hash is the same, skip service discovery";
- p_clcb->p_srcb->state = BTA_GATTC_SERV_IDLE;
- bta_gattc_reset_discover_st(p_clcb->p_srcb, GATT_SUCCESS);
- } else {
- LOG(INFO) << __func__ << ": hash is not the same, start service discovery";
- bta_gattc_start_discover_internal(p_clcb);
- }
-}
-
-/* handle response of reading extended properties descriptor */
-static void bta_gattc_read_ext_prop_desc_cmpl(
- tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_OP_CMPL* p_data) {
- uint8_t op = (uint8_t)p_data->op_code;
- if (op != GATTC_OPTYPE_READ) {
- VLOG(1) << __func__ << ": op = " << +p_data->hdr.layer_specific;
- return;
- }
-
- if (!p_clcb->disc_active) {
- VLOG(1) << __func__ << ": not active in discover state";
- return;
- }
- p_clcb->request_during_discovery = BTA_GATTC_DISCOVER_REQ_NONE;
-
- tBTA_GATTC_SERV* p_srvc_cb = p_clcb->p_srcb;
- const uint8_t status = p_data->status;
-
- if (status == GATT_REQ_NOT_SUPPORTED &&
- !p_srvc_cb->read_multiple_not_supported) {
- // can't do "read multiple request", fall back to "read request"
- p_srvc_cb->read_multiple_not_supported = true;
- bta_gattc_explore_next_service(p_clcb->bta_conn_id, p_srvc_cb);
- return;
- }
-
- if (status != GATT_SUCCESS) {
- LOG(WARNING) << "Discovery on server failed: " << loghex(status);
- bta_gattc_reset_discover_st(p_clcb->p_srcb, GATT_ERROR);
- return;
- }
-
- const tGATT_VALUE& att_value = p_data->p_cmpl->att_value;
- if (p_srvc_cb->read_multiple_not_supported && att_value.len != 2) {
- // Just one Characteristic Extended Properties value at a time in Read
- // Response
- LOG(WARNING) << __func__ << " Read Response should be just 2 bytes!";
- bta_gattc_reset_discover_st(p_clcb->p_srcb, GATT_ERROR);
- return;
- }
-
- // Parsing is same for "Read Multiple Response", and for "Read Response"
- const uint8_t* p = att_value.value;
- std::vector<uint16_t> value_of_descriptors;
- while (p < att_value.value + att_value.len) {
- uint16_t extended_properties;
- STREAM_TO_UINT16(extended_properties, p);
- value_of_descriptors.push_back(extended_properties);
- }
-
- bool ret =
- p_srvc_cb->pending_discovery.SetValueOfDescriptors(value_of_descriptors);
- if (!ret) {
- LOG(WARNING) << __func__
- << " Problem setting Extended Properties descriptors values";
- bta_gattc_reset_discover_st(p_clcb->p_srcb, GATT_ERROR);
- return;
- }
-
- // Continue service discovery
- bta_gattc_explore_next_service(p_clcb->bta_conn_id, p_srvc_cb);
-}
-
/*******************************************************************************
*
* Function bta_gattc_fill_gatt_db_el
@@ -851,18 +634,12 @@ static void bta_gattc_get_gatt_db_impl(tBTA_GATTC_SERV* p_srvc_cb,
charac.value_handle, 0 /* s_handle */,
0 /* e_handle */, charac.value_handle,
charac.uuid, charac.properties);
- btgatt_db_element_t* characteristic = curr_db_attr;
curr_db_attr++;
for (const Descriptor& desc : charac.descriptors) {
bta_gattc_fill_gatt_db_el(
curr_db_attr, BTGATT_DB_DESCRIPTOR, desc.handle, 0 /* s_handle */,
0 /* e_handle */, desc.handle, desc.uuid, 0 /* property */);
-
- if (desc.uuid == Uuid::From16Bit(GATT_UUID_CHAR_EXT_PROP)) {
- characteristic->extended_properties =
- desc.characteristic_extended_properties;
- }
curr_db_attr++;
}
}
@@ -899,7 +676,7 @@ void bta_gattc_get_gatt_db(uint16_t conn_id, uint16_t start_handle,
int* count) {
tBTA_GATTC_CLCB* p_clcb = bta_gattc_find_clcb_by_conn_id(conn_id);
- LOG_INFO("%s", __func__);
+ LOG_DEBUG(LOG_TAG, "%s", __func__);
if (p_clcb == NULL) {
LOG(ERROR) << "Unknown conn_id=" << loghex(conn_id);
return;
diff --git a/bta/gatt/bta_gattc_int.h b/bta/gatt/bta_gattc_int.h
index bfde5aba7..45a54c30c 100644
--- a/bta/gatt/bta_gattc_int.h
+++ b/bta/gatt/bta_gattc_int.h
@@ -24,16 +24,17 @@
#ifndef BTA_GATTC_INT_H
#define BTA_GATTC_INT_H
-#include <cstdint>
+#include "bt_target.h"
-#include "bt_target.h" // Must be first to define build configuration
+#include "bta_gatt_api.h"
+#include "bta_sys.h"
+#include "database_builder.h"
+#include "osi/include/fixed_queue.h"
-#include "bta/gatt/database.h"
-#include "bta/gatt/database_builder.h"
-#include "bta/include/bta_gatt_api.h"
-#include "bta/sys/bta_sys.h"
-#include "stack/include/gatt_api.h"
-#include "types/bt_transport.h"
+#include "bt_common.h"
+
+#include <base/logging.h>
+#include <base/strings/stringprintf.h>
/*****************************************************************************
* Constants and data types
@@ -75,6 +76,8 @@ typedef uint16_t tBTA_GATTC_INT_EVT;
#define BTA_GATTC_KNOWN_SR_MAX 255
#endif
+#define BTA_GATTC_CONN_MAX GATT_MAX_PHY_CHANNEL
+
#ifndef BTA_GATTC_CLCB_MAX
#define BTA_GATTC_CLCB_MAX GATT_CL_MAX_LCB
#endif
@@ -83,11 +86,11 @@ typedef uint16_t tBTA_GATTC_INT_EVT;
/* internal strucutre for GATTC register API */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress remote_bda;
tGATT_IF client_if;
bool is_direct;
- tBT_TRANSPORT transport;
+ tBTA_TRANSPORT transport;
uint8_t initiating_phys;
bool opportunistic;
} tBTA_GATTC_API_OPEN;
@@ -95,7 +98,7 @@ typedef struct {
typedef tBTA_GATTC_API_OPEN tBTA_GATTC_API_CANCEL_OPEN;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tGATT_AUTH_REQ auth_req;
// read by handle data
@@ -112,7 +115,7 @@ typedef struct {
} tBTA_GATTC_API_READ;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tGATT_AUTH_REQ auth_req;
uint16_t handle;
tGATT_WRITE_TYPE write_type;
@@ -124,43 +127,43 @@ typedef struct {
} tBTA_GATTC_API_WRITE;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
bool is_execute;
} tBTA_GATTC_API_EXEC;
typedef struct {
- BT_HDR_RIGID hdr;
- uint16_t cid;
+ BT_HDR hdr;
+ uint16_t handle;
} tBTA_GATTC_API_CONFIRM;
+typedef tGATT_CL_COMPLETE tBTA_GATTC_CMPL;
+
typedef struct {
- BT_HDR_RIGID hdr;
- tGATTC_OPTYPE op_code;
+ BT_HDR hdr;
+ uint8_t op_code;
tGATT_STATUS status;
- tGATT_CL_COMPLETE* p_cmpl;
+ tBTA_GATTC_CMPL* p_cmpl;
} tBTA_GATTC_OP_CMPL;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
bluetooth::Uuid* p_srvc_uuid;
} tBTA_GATTC_API_SEARCH;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tGATT_AUTH_REQ auth_req;
uint8_t num_attr;
uint16_t handles[GATT_MAX_READ_MULTI_HANDLES];
} tBTA_GATTC_API_READ_MULTI;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint16_t mtu;
- GATT_CONFIGURE_MTU_OP_CB mtu_cb;
- void* mtu_cb_data;
} tBTA_GATTC_API_CFG_MTU;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress remote_bda;
tGATT_IF client_if;
uint8_t role;
@@ -169,7 +172,7 @@ typedef struct {
} tBTA_GATTC_INT_CONN;
typedef union {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_GATTC_API_OPEN api_conn;
tBTA_GATTC_API_CANCEL_OPEN api_cancel_conn;
tBTA_GATTC_API_READ api_read;
@@ -210,20 +213,14 @@ typedef struct {
gatt::DatabaseBuilder pending_discovery;
- /* used only during service discovery, when reading Extended Characteristic
- * Properties */
- bool read_multiple_not_supported;
-
uint8_t srvc_hdl_chg; /* service handle change indication pending */
- bool srvc_hdl_db_hash; /* read db hash pending */
- uint8_t srvc_disc_count; /* current discovery retry count */
uint16_t attr_index; /* cahce NV saving/loading attribute index */
uint16_t mtu;
} tBTA_GATTC_SERV;
#ifndef BTA_GATTC_NOTIF_REG_MAX
-#define BTA_GATTC_NOTIF_REG_MAX 64
+#define BTA_GATTC_NOTIF_REG_MAX 15
#endif
typedef struct {
@@ -247,17 +244,10 @@ typedef struct {
typedef struct {
uint16_t bta_conn_id; /* client channel ID, unique for clcb */
RawAddress bda;
- tBT_TRANSPORT transport; /* channel transport */
+ tBTA_TRANSPORT transport; /* channel transport */
tBTA_GATTC_RCB* p_rcb; /* pointer to the registration CB */
tBTA_GATTC_SERV* p_srcb; /* server cache CB */
- const tBTA_GATTC_DATA* p_q_cmd; /* command in queue waiting for execution */
-
-// request during discover state
-#define BTA_GATTC_DISCOVER_REQ_NONE 0
-#define BTA_GATTC_DISCOVER_REQ_READ_EXT_PROP_DESC 1
-#define BTA_GATTC_DISCOVER_REQ_READ_DB_HASH 2
-
- uint8_t request_during_discovery; /* request during discover state */
+ tBTA_GATTC_DATA* p_q_cmd; /* command in queue waiting for execution */
#define BTA_GATTC_NO_SCHEDULE 0
#define BTA_GATTC_DISC_WAITING 0x01
@@ -268,6 +258,7 @@ typedef struct {
bool in_use;
tBTA_GATTC_STATE state;
tGATT_STATUS status;
+ uint16_t reason;
} tBTA_GATTC_CLCB;
/* back ground connection tracking information */
@@ -301,7 +292,7 @@ enum {
typedef struct {
uint8_t state;
- tBTA_GATTC_CONN conn_track[GATT_MAX_PHY_CHANNEL];
+ tBTA_GATTC_CONN conn_track[BTA_GATTC_CONN_MAX];
tBTA_GATTC_BG_TCK bg_track[BTA_GATTC_KNOWN_SR_MAX];
tBTA_GATTC_RCB cl_rcb[BTA_GATTC_CL_MAX];
@@ -319,101 +310,87 @@ extern tBTA_GATTC_CB bta_gattc_cb;
/*****************************************************************************
* Function prototypes
****************************************************************************/
-extern bool bta_gattc_hdl_event(BT_HDR_RIGID* p_msg);
+extern bool bta_gattc_hdl_event(BT_HDR* p_msg);
extern bool bta_gattc_sm_execute(tBTA_GATTC_CLCB* p_clcb, uint16_t event,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
/* function processed outside SM */
extern void bta_gattc_disable();
extern void bta_gattc_register(const bluetooth::Uuid& app_uuid,
tBTA_GATTC_CBACK* p_data,
- BtaAppRegisterCallback cb, bool eatt_support);
-extern void bta_gattc_process_api_open(const tBTA_GATTC_DATA* p_msg);
-extern void bta_gattc_process_api_open_cancel(const tBTA_GATTC_DATA* p_msg);
+ BtaAppRegisterCallback cb);
+extern void bta_gattc_process_api_open(tBTA_GATTC_DATA* p_msg);
+extern void bta_gattc_process_api_open_cancel(tBTA_GATTC_DATA* p_msg);
extern void bta_gattc_deregister(tBTA_GATTC_RCB* p_clreg);
/* function within state machine */
-extern void bta_gattc_open(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_open(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
extern void bta_gattc_open_fail(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
extern void bta_gattc_open_error(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
extern void bta_gattc_cancel_open(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
extern void bta_gattc_cancel_open_ok(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
extern void bta_gattc_cancel_open_error(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_conn(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_conn(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_close(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_close(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
extern void bta_gattc_close_fail(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
extern void bta_gattc_disc_close(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
extern void bta_gattc_start_discover(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_start_discover_internal(tBTA_GATTC_CLCB* p_clcb);
+ tBTA_GATTC_DATA* p_data);
extern void bta_gattc_disc_cmpl(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_read(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_write(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_op_cmpl(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_q_cmd(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_search(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_fail(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_confirm(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_execute(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_read(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_write(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_op_cmpl(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_q_cmd(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_search(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_fail(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_confirm(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_execute(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
extern void bta_gattc_read_multi(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_ci_open(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_ci_open(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
extern void bta_gattc_ci_close(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
-extern void bta_gattc_op_cmpl_during_discovery(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_ignore_op_cmpl(tBTA_GATTC_CLCB* p_clcb,
+ tBTA_GATTC_DATA* p_data);
extern void bta_gattc_restart_discover(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_msg);
-extern void bta_gattc_init_bk_conn(const tBTA_GATTC_API_OPEN* p_data,
+ tBTA_GATTC_DATA* p_msg);
+extern void bta_gattc_init_bk_conn(tBTA_GATTC_API_OPEN* p_data,
tBTA_GATTC_RCB* p_clreg);
-extern void bta_gattc_cancel_bk_conn(const tBTA_GATTC_API_CANCEL_OPEN* p_data);
+extern void bta_gattc_cancel_bk_conn(tBTA_GATTC_API_CANCEL_OPEN* p_data);
extern void bta_gattc_send_open_cback(tBTA_GATTC_RCB* p_clreg,
tGATT_STATUS status,
const RawAddress& remote_bda,
- uint16_t conn_id, tBT_TRANSPORT transport,
- uint16_t mtu);
+ uint16_t conn_id,
+ tBTA_TRANSPORT transport, uint16_t mtu);
extern void bta_gattc_process_api_refresh(const RawAddress& remote_bda);
-extern void bta_gattc_cfg_mtu(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+extern void bta_gattc_cfg_mtu(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
extern void bta_gattc_listen(tBTA_GATTC_DATA* p_msg);
extern void bta_gattc_broadcast(tBTA_GATTC_DATA* p_msg);
/* utility functions */
extern tBTA_GATTC_CLCB* bta_gattc_find_clcb_by_cif(uint8_t client_if,
const RawAddress& remote_bda,
- tBT_TRANSPORT transport);
+ tBTA_TRANSPORT transport);
extern tBTA_GATTC_CLCB* bta_gattc_find_clcb_by_conn_id(uint16_t conn_id);
extern tBTA_GATTC_CLCB* bta_gattc_clcb_alloc(tGATT_IF client_if,
const RawAddress& remote_bda,
- tBT_TRANSPORT transport);
+ tBTA_TRANSPORT transport);
extern void bta_gattc_clcb_dealloc(tBTA_GATTC_CLCB* p_clcb);
extern tBTA_GATTC_CLCB* bta_gattc_find_alloc_clcb(tGATT_IF client_if,
const RawAddress& remote_bda,
- tBT_TRANSPORT transport);
+ tBTA_TRANSPORT transport);
extern tBTA_GATTC_RCB* bta_gattc_cl_get_regcb(uint8_t client_if);
extern tBTA_GATTC_SERV* bta_gattc_find_srcb(const RawAddress& bda);
extern tBTA_GATTC_SERV* bta_gattc_srcb_alloc(const RawAddress& bda);
@@ -421,8 +398,7 @@ extern tBTA_GATTC_SERV* bta_gattc_find_scb_by_cid(uint16_t conn_id);
extern tBTA_GATTC_CLCB* bta_gattc_find_int_conn_clcb(tBTA_GATTC_DATA* p_msg);
extern tBTA_GATTC_CLCB* bta_gattc_find_int_disconn_clcb(tBTA_GATTC_DATA* p_msg);
-extern bool bta_gattc_enqueue(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+extern bool bta_gattc_enqueue(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data);
extern bool bta_gattc_check_notif_registry(tBTA_GATTC_RCB* p_clreg,
tBTA_GATTC_SERV* p_srcb,
@@ -437,7 +413,6 @@ extern void bta_gattc_clear_notif_registration(tBTA_GATTC_SERV* p_srcb,
uint16_t start_handle,
uint16_t end_handle);
extern tBTA_GATTC_SERV* bta_gattc_find_srvr_cache(const RawAddress& bda);
-extern bool bta_gattc_is_robust_caching_enabled();
/* discovery functions */
extern void bta_gattc_disc_res_cback(uint16_t conn_id,
@@ -448,7 +423,7 @@ extern void bta_gattc_disc_cmpl_cback(uint16_t conn_id,
tGATT_STATUS status);
extern tGATT_STATUS bta_gattc_discover_pri_service(uint16_t conn_id,
tBTA_GATTC_SERV* p_server_cb,
- tGATT_DISC_TYPE disc_type);
+ uint8_t disc_type);
extern void bta_gattc_search_service(tBTA_GATTC_CLCB* p_clcb,
bluetooth::Uuid* p_uuid);
extern const std::list<gatt::Service>* bta_gattc_get_services(uint16_t conn_id);
@@ -479,6 +454,4 @@ extern bool bta_gattc_conn_dealloc(const RawAddress& remote_bda);
extern bool bta_gattc_cache_load(tBTA_GATTC_SERV* p_srcb);
extern void bta_gattc_cache_reset(const RawAddress& server_bda);
-extern bool bta_gattc_read_db_hash(tBTA_GATTC_CLCB* p_clcb);
-
#endif /* BTA_GATTC_INT_H */
diff --git a/bta/gatt/bta_gattc_main.cc b/bta/gatt/bta_gattc_main.cc
index b93881e24..afc3e51c9 100644
--- a/bta/gatt/bta_gattc_main.cc
+++ b/bta/gatt/bta_gattc_main.cc
@@ -22,11 +22,12 @@
*
******************************************************************************/
-#include <base/strings/stringprintf.h>
+#include "bt_target.h"
-#include "bt_target.h" // Must be first to define build configuration"
+#include <string.h>
-#include "bta/gatt/bta_gattc_int.h"
+#include "bt_common.h"
+#include "bta_gattc_int.h"
using base::StringPrintf;
@@ -56,7 +57,7 @@ enum {
BTA_GATTC_CONFIRM,
BTA_GATTC_EXEC,
BTA_GATTC_READ_MULTI,
- BTA_GATTC_OP_CMPL_DURING_DISCOVERY,
+ BTA_GATTC_IGNORE_OP_CMPL,
BTA_GATTC_DISC_CLOSE,
BTA_GATTC_RESTART_DISCOVER,
BTA_GATTC_CFG_MTU,
@@ -65,34 +66,34 @@ enum {
};
/* type for action functions */
typedef void (*tBTA_GATTC_ACTION)(tBTA_GATTC_CLCB* p_clcb,
- const tBTA_GATTC_DATA* p_data);
+ tBTA_GATTC_DATA* p_data);
/* action function list */
const tBTA_GATTC_ACTION bta_gattc_action[] = {
- bta_gattc_open, /* BTA_GATTC_OPEN */
- bta_gattc_open_fail, /* BTA_GATTC_OPEN_FAIL */
- bta_gattc_open_error, /* BTA_GATTC_OPEN_ERROR */
- bta_gattc_cancel_open, /* BTA_GATTC_CANCEL_OPEN */
- bta_gattc_cancel_open_ok, /* BTA_GATTC_CANCEL_OPEN_OK */
- bta_gattc_cancel_open_error, /* BTA_GATTC_CANCEL_OPEN_ERROR */
- bta_gattc_conn, /* BTA_GATTC_CONN */
- bta_gattc_start_discover, /* BTA_GATTC_START_DISCOVER */
- bta_gattc_disc_cmpl, /* BTA_GATTC_DISC_CMPL */
- bta_gattc_q_cmd, /* BTA_GATTC_Q_CMD */
- bta_gattc_close, /* BTA_GATTC_CLOSE */
- bta_gattc_close_fail, /* BTA_GATTC_CLOSE_FAIL */
- bta_gattc_read, /* BTA_GATTC_READ */
- bta_gattc_write, /* BTA_GATTC_WRITE */
- bta_gattc_op_cmpl, /* BTA_GATTC_OP_CMPL */
- bta_gattc_search, /* BTA_GATTC_SEARCH */
- bta_gattc_fail, /* BTA_GATTC_FAIL */
- bta_gattc_confirm, /* BTA_GATTC_CONFIRM */
- bta_gattc_execute, /* BTA_GATTC_EXEC */
- bta_gattc_read_multi, /* BTA_GATTC_READ_MULTI */
- bta_gattc_op_cmpl_during_discovery, /* BTA_GATTC_OP_CMPL_DURING_DISCOVERY */
- bta_gattc_disc_close, /* BTA_GATTC_DISC_CLOSE */
- bta_gattc_restart_discover, /* BTA_GATTC_RESTART_DISCOVER */
- bta_gattc_cfg_mtu /* BTA_GATTC_CFG_MTU */
+ bta_gattc_open, /* BTA_GATTC_OPEN */
+ bta_gattc_open_fail, /* BTA_GATTC_OPEN_FAIL */
+ bta_gattc_open_error, /* BTA_GATTC_OPEN_ERROR */
+ bta_gattc_cancel_open, /* BTA_GATTC_CANCEL_OPEN */
+ bta_gattc_cancel_open_ok, /* BTA_GATTC_CANCEL_OPEN_OK */
+ bta_gattc_cancel_open_error, /* BTA_GATTC_CANCEL_OPEN_ERROR */
+ bta_gattc_conn, /* BTA_GATTC_CONN */
+ bta_gattc_start_discover, /* BTA_GATTC_START_DISCOVER */
+ bta_gattc_disc_cmpl, /* BTA_GATTC_DISC_CMPL */
+ bta_gattc_q_cmd, /* BTA_GATTC_Q_CMD */
+ bta_gattc_close, /* BTA_GATTC_CLOSE */
+ bta_gattc_close_fail, /* BTA_GATTC_CLOSE_FAIL */
+ bta_gattc_read, /* BTA_GATTC_READ */
+ bta_gattc_write, /* BTA_GATTC_WRITE */
+ bta_gattc_op_cmpl, /* BTA_GATTC_OP_CMPL */
+ bta_gattc_search, /* BTA_GATTC_SEARCH */
+ bta_gattc_fail, /* BTA_GATTC_FAIL */
+ bta_gattc_confirm, /* BTA_GATTC_CONFIRM */
+ bta_gattc_execute, /* BTA_GATTC_EXEC */
+ bta_gattc_read_multi, /* BTA_GATTC_READ_MULTI */
+ bta_gattc_ignore_op_cmpl, /* BTA_GATTC_IGNORE_OP_CMPL */
+ bta_gattc_disc_close, /* BTA_GATTC_DISC_CLOSE */
+ bta_gattc_restart_discover, /* BTA_GATTC_RESTART_DISCOVER */
+ bta_gattc_cfg_mtu /* BTA_GATTC_CFG_MTU */
};
/* state table information */
@@ -255,7 +256,7 @@ static const uint8_t bta_gattc_st_discover[][BTA_GATTC_NUM_COLS] = {
BTA_GATTC_DISCOVER_ST},
/* BTA_GATTC_DISCOVER_CMPL_EVT */ {BTA_GATTC_DISC_CMPL,
BTA_GATTC_CONN_ST},
- /* BTA_GATTC_OP_CMPL_EVT */ {BTA_GATTC_OP_CMPL_DURING_DISCOVERY,
+ /* BTA_GATTC_OP_CMPL_EVT */ {BTA_GATTC_IGNORE_OP_CMPL,
BTA_GATTC_DISCOVER_ST},
/* BTA_GATTC_INT_DISCONN_EVT */ {BTA_GATTC_CLOSE, BTA_GATTC_IDLE_ST},
@@ -296,7 +297,7 @@ static const char* gattc_state_code(tBTA_GATTC_STATE state_code);
*
******************************************************************************/
bool bta_gattc_sm_execute(tBTA_GATTC_CLCB* p_clcb, uint16_t event,
- const tBTA_GATTC_DATA* p_data) {
+ tBTA_GATTC_DATA* p_data) {
tBTA_GATTC_ST_TBL state_table;
uint8_t action;
int i;
@@ -361,7 +362,7 @@ bool bta_gattc_sm_execute(tBTA_GATTC_CLCB* p_clcb, uint16_t event,
* Returns bool
*
******************************************************************************/
-bool bta_gattc_hdl_event(BT_HDR_RIGID* p_msg) {
+bool bta_gattc_hdl_event(BT_HDR* p_msg) {
tBTA_GATTC_CLCB* p_clcb = NULL;
bool rt = true;
#if (BTA_GATT_DEBUG == TRUE)
@@ -386,8 +387,8 @@ bool bta_gattc_hdl_event(BT_HDR_RIGID* p_msg) {
p_clcb = bta_gattc_find_clcb_by_conn_id(p_msg->layer_specific);
if (p_clcb != NULL) {
- rt = bta_gattc_sm_execute(p_clcb, p_msg->event,
- (const tBTA_GATTC_DATA*)p_msg);
+ rt =
+ bta_gattc_sm_execute(p_clcb, p_msg->event, (tBTA_GATTC_DATA*)p_msg);
} else {
VLOG(1) << "Ignore unknown conn ID: " << +p_msg->layer_specific;
}
diff --git a/bta/gatt/bta_gattc_queue.cc b/bta/gatt/bta_gattc_queue.cc
index 0058741b4..6d8f57c3f 100644
--- a/bta/gatt/bta_gattc_queue.cc
+++ b/bta/gatt/bta_gattc_queue.cc
@@ -26,7 +26,6 @@ constexpr uint8_t GATT_READ_CHAR = 1;
constexpr uint8_t GATT_READ_DESC = 2;
constexpr uint8_t GATT_WRITE_CHAR = 3;
constexpr uint8_t GATT_WRITE_DESC = 4;
-constexpr uint8_t GATT_CONFIG_MTU = 5;
struct gatt_read_op_data {
GATT_READ_OP_CB cb;
@@ -81,29 +80,6 @@ void BtaGattQueue::gatt_write_op_finished(uint16_t conn_id, tGATT_STATUS status,
}
}
-struct gatt_configure_mtu_op_data {
- GATT_CONFIGURE_MTU_OP_CB cb;
- void* cb_data;
-};
-
-void BtaGattQueue::gatt_configure_mtu_op_finished(uint16_t conn_id,
- tGATT_STATUS status,
- void* data) {
- gatt_configure_mtu_op_data* tmp = (gatt_configure_mtu_op_data*)data;
- GATT_CONFIGURE_MTU_OP_CB tmp_cb = tmp->cb;
- void* tmp_cb_data = tmp->cb_data;
-
- osi_free(data);
-
- mark_as_not_executing(conn_id);
- gatt_execute_next_op(conn_id);
-
- if (tmp_cb) {
- tmp_cb(conn_id, status, tmp_cb_data);
- return;
- }
-}
-
void BtaGattQueue::gatt_execute_next_op(uint16_t conn_id) {
APPL_TRACE_DEBUG("%s: conn_id=0x%x", __func__, conn_id);
if (gatt_op_queue.empty()) {
@@ -161,14 +137,6 @@ void BtaGattQueue::gatt_execute_next_op(uint16_t conn_id) {
data->cb_data = op.write_cb_data;
BTA_GATTC_WriteCharDescr(conn_id, op.handle, std::move(op.value),
GATT_AUTH_REQ_NONE, gatt_write_op_finished, data);
- } else if (op.type == GATT_CONFIG_MTU) {
- gatt_configure_mtu_op_data* data =
- (gatt_configure_mtu_op_data*)osi_malloc(sizeof(gatt_configure_mtu_op_data));
- data->cb = op.mtu_cb;
- data->cb_data = op.mtu_cb_data;
- BTA_GATTC_ConfigureMTU(conn_id, static_cast<uint16_t>(op.value[0] |
- (op.value[1] << 8)),
- gatt_configure_mtu_op_finished, data);
}
gatt_ops.pop_front();
@@ -222,12 +190,3 @@ void BtaGattQueue::WriteDescriptor(uint16_t conn_id, uint16_t handle,
.value = std::move(value)});
gatt_execute_next_op(conn_id);
}
-
-void BtaGattQueue::ConfigureMtu(uint16_t conn_id, uint16_t mtu) {
- LOG(INFO) << __func__ << ", mtu: " << static_cast<int>(mtu);
- std::vector<uint8_t> value = {static_cast<uint8_t>(mtu & 0xff),
- static_cast<uint8_t>(mtu >> 8)};
- gatt_op_queue[conn_id].push_back({.type = GATT_CONFIG_MTU,
- .value = std::move(value)});
- gatt_execute_next_op(conn_id);
-}
diff --git a/bta/gatt/bta_gattc_utils.cc b/bta/gatt/bta_gattc_utils.cc
index 2da0739d9..d0b45c10b 100644
--- a/bta/gatt/bta_gattc_utils.cc
+++ b/bta/gatt/bta_gattc_utils.cc
@@ -24,24 +24,16 @@
#define LOG_TAG "bt_bta_gattc"
-#include <cstdint>
+#include "bt_target.h"
-#include "bt_target.h" // Must be first to define build configuration
+#include <base/logging.h>
+#include <string.h>
-#include "bta/gatt/bta_gattc_int.h"
-#include "device/include/controller.h"
-#include "gd/common/init_flags.h"
-#include "types/bt_transport.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
-
-static uint8_t ble_acceptlist_size() {
- const controller_t* controller = controller_get_interface();
- if (!controller->supports_ble()) {
- return 0;
- }
- return controller->get_ble_acceptlist_size();
-}
+#include "bt_common.h"
+#include "bta_gattc_int.h"
+#include "bta_sys.h"
+#include "l2c_api.h"
+#include "utl.h"
/*******************************************************************************
*
@@ -89,7 +81,7 @@ uint8_t bta_gattc_num_reg_app(void) {
******************************************************************************/
tBTA_GATTC_CLCB* bta_gattc_find_clcb_by_cif(uint8_t client_if,
const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
+ tBTA_TRANSPORT transport) {
tBTA_GATTC_CLCB* p_clcb = &bta_gattc_cb.clcb[0];
uint8_t i;
@@ -130,7 +122,7 @@ tBTA_GATTC_CLCB* bta_gattc_find_clcb_by_conn_id(uint16_t conn_id) {
******************************************************************************/
tBTA_GATTC_CLCB* bta_gattc_clcb_alloc(tGATT_IF client_if,
const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
+ tBTA_TRANSPORT transport) {
uint8_t i_clcb = 0;
tBTA_GATTC_CLCB* p_clcb = NULL;
@@ -175,7 +167,7 @@ tBTA_GATTC_CLCB* bta_gattc_clcb_alloc(tGATT_IF client_if,
******************************************************************************/
tBTA_GATTC_CLCB* bta_gattc_find_alloc_clcb(tGATT_IF client_if,
const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
+ tBTA_TRANSPORT transport) {
tBTA_GATTC_CLCB* p_clcb;
p_clcb = bta_gattc_find_clcb_by_cif(client_if, remote_bda, transport);
@@ -232,7 +224,7 @@ tBTA_GATTC_SERV* bta_gattc_find_srcb(const RawAddress& bda) {
tBTA_GATTC_SERV* p_srcb = &bta_gattc_cb.known_server[0];
uint8_t i;
- for (i = 0; i < ble_acceptlist_size(); i++, p_srcb++) {
+ for (i = 0; i < BTM_GetWhiteListSize(); i++, p_srcb++) {
if (p_srcb->in_use && p_srcb->server_bda == bda) return p_srcb;
}
return NULL;
@@ -251,7 +243,7 @@ tBTA_GATTC_SERV* bta_gattc_find_srvr_cache(const RawAddress& bda) {
tBTA_GATTC_SERV* p_srcb = &bta_gattc_cb.known_server[0];
uint8_t i;
- for (i = 0; i < ble_acceptlist_size(); i++, p_srcb++) {
+ for (i = 0; i < BTM_GetWhiteListSize(); i++, p_srcb++) {
if (p_srcb->server_bda == bda) return p_srcb;
}
return NULL;
@@ -287,7 +279,7 @@ tBTA_GATTC_SERV* bta_gattc_srcb_alloc(const RawAddress& bda) {
bool found = false;
uint8_t i;
- for (i = 0; i < ble_acceptlist_size(); i++, p_tcb++) {
+ for (i = 0; i < BTM_GetWhiteListSize(); i++, p_tcb++) {
if (!p_tcb->in_use) {
found = true;
break;
@@ -322,7 +314,7 @@ tBTA_GATTC_SERV* bta_gattc_srcb_alloc(const RawAddress& bda) {
* Returns success or failure.
*
******************************************************************************/
-bool bta_gattc_enqueue(tBTA_GATTC_CLCB* p_clcb, const tBTA_GATTC_DATA* p_data) {
+bool bta_gattc_enqueue(tBTA_GATTC_CLCB* p_clcb, tBTA_GATTC_DATA* p_data) {
if (p_clcb->p_q_cmd == NULL) {
p_clcb->p_q_cmd = p_data;
return true;
@@ -377,7 +369,7 @@ void bta_gattc_clear_notif_registration(tBTA_GATTC_SERV* p_srcb,
tGATT_IF gatt_if;
tBTA_GATTC_RCB* p_clrcb;
uint8_t i;
- tBT_TRANSPORT transport;
+ tGATT_TRANSPORT transport;
uint16_t handle;
if (GATT_GetConnectionInfor(conn_id, &gatt_if, remote_bda, &transport)) {
@@ -417,7 +409,7 @@ bool bta_gattc_mark_bg_conn(tGATT_IF client_if,
uint8_t i = 0;
tBTA_GATTC_CIF_MASK* p_cif_mask;
- for (i = 0; i < ble_acceptlist_size(); i++, p_bg_tck++) {
+ for (i = 0; i < BTM_GetWhiteListSize(); i++, p_bg_tck++) {
if (p_bg_tck->in_use && ((p_bg_tck->remote_bda == remote_bda_ptr) ||
(p_bg_tck->remote_bda.IsEmpty()))) {
p_cif_mask = &p_bg_tck->cif_mask;
@@ -444,8 +436,8 @@ bool bta_gattc_mark_bg_conn(tGATT_IF client_if,
return false;
} else /* adding a new device mask */
{
- for (i = 0, p_bg_tck = &bta_gattc_cb.bg_track[0]; i < ble_acceptlist_size();
- i++, p_bg_tck++) {
+ for (i = 0, p_bg_tck = &bta_gattc_cb.bg_track[0];
+ i < BTM_GetWhiteListSize(); i++, p_bg_tck++) {
if (!p_bg_tck->in_use) {
p_bg_tck->in_use = true;
p_bg_tck->remote_bda = remote_bda_ptr;
@@ -476,11 +468,11 @@ bool bta_gattc_check_bg_conn(tGATT_IF client_if, const RawAddress& remote_bda,
uint8_t i = 0;
bool is_bg_conn = false;
- for (i = 0; i < ble_acceptlist_size() && !is_bg_conn; i++, p_bg_tck++) {
+ for (i = 0; i < BTM_GetWhiteListSize() && !is_bg_conn; i++, p_bg_tck++) {
if (p_bg_tck->in_use && (p_bg_tck->remote_bda == remote_bda ||
p_bg_tck->remote_bda.IsEmpty())) {
if (((p_bg_tck->cif_mask & (1 << (client_if - 1))) != 0) &&
- role == HCI_ROLE_CENTRAL)
+ role == HCI_ROLE_MASTER)
is_bg_conn = true;
}
}
@@ -497,7 +489,7 @@ bool bta_gattc_check_bg_conn(tGATT_IF client_if, const RawAddress& remote_bda,
******************************************************************************/
void bta_gattc_send_open_cback(tBTA_GATTC_RCB* p_clreg, tGATT_STATUS status,
const RawAddress& remote_bda, uint16_t conn_id,
- tBT_TRANSPORT transport, uint16_t mtu) {
+ tBTA_TRANSPORT transport, uint16_t mtu) {
tBTA_GATTC cb_data;
if (p_clreg->p_cback) {
@@ -526,7 +518,7 @@ tBTA_GATTC_CONN* bta_gattc_conn_alloc(const RawAddress& remote_bda) {
uint8_t i_conn = 0;
tBTA_GATTC_CONN* p_conn = &bta_gattc_cb.conn_track[0];
- for (i_conn = 0; i_conn < GATT_MAX_PHY_CHANNEL; i_conn++, p_conn++) {
+ for (i_conn = 0; i_conn < BTA_GATTC_CONN_MAX; i_conn++, p_conn++) {
if (!p_conn->in_use) {
#if (BTA_GATT_DEBUG == TRUE)
VLOG(1) << __func__ << ": found conn_track:" << +i_conn << " available";
@@ -552,7 +544,7 @@ tBTA_GATTC_CONN* bta_gattc_conn_find(const RawAddress& remote_bda) {
uint8_t i_conn = 0;
tBTA_GATTC_CONN* p_conn = &bta_gattc_cb.conn_track[0];
- for (i_conn = 0; i_conn < GATT_MAX_PHY_CHANNEL; i_conn++, p_conn++) {
+ for (i_conn = 0; i_conn < BTA_GATTC_CONN_MAX; i_conn++, p_conn++) {
if (p_conn->in_use && remote_bda == p_conn->remote_bda) {
#if (BTA_GATT_DEBUG == TRUE)
VLOG(1) << __func__ << ": found conn_track:" << +i_conn << " matched";
@@ -614,7 +606,7 @@ bool bta_gattc_conn_dealloc(const RawAddress& remote_bda) {
tBTA_GATTC_CLCB* bta_gattc_find_int_conn_clcb(tBTA_GATTC_DATA* p_msg) {
tBTA_GATTC_CLCB* p_clcb = NULL;
- if (p_msg->int_conn.role == HCI_ROLE_PERIPHERAL)
+ if (p_msg->int_conn.role == HCI_ROLE_SLAVE)
bta_gattc_conn_find_alloc(p_msg->int_conn.remote_bda);
/* try to locate a logic channel */
@@ -623,7 +615,7 @@ tBTA_GATTC_CLCB* bta_gattc_find_int_conn_clcb(tBTA_GATTC_DATA* p_msg) {
p_msg->int_conn.transport);
if (p_clcb == NULL) {
/* for a background connection or listening connection */
- if (/*p_msg->int_conn.role == HCI_ROLE_PERIPHERAL || */
+ if (/*p_msg->int_conn.role == HCI_ROLE_SLAVE || */
bta_gattc_check_bg_conn(p_msg->int_conn.client_if,
p_msg->int_conn.remote_bda,
p_msg->int_conn.role)) {
@@ -663,16 +655,3 @@ tBTA_GATTC_CLCB* bta_gattc_find_int_disconn_clcb(tBTA_GATTC_DATA* p_msg) {
}
return p_clcb;
}
-
-/*******************************************************************************
- *
- * Function bta_gattc_is_robust_caching_enabled
- *
- * Description check if robust caching is enabled
- *
- * Returns true if enabled; otherwise false
- *
- ******************************************************************************/
-bool bta_gattc_is_robust_caching_enabled() {
- return bluetooth::common::init_flags::gatt_robust_caching_is_enabled();
-}
diff --git a/bta/gatt/bta_gatts_act.cc b/bta/gatt/bta_gatts_act.cc
index 03895f094..8e3d589c4 100644
--- a/bta/gatt/bta_gatts_act.cc
+++ b/bta/gatt/bta_gatts_act.cc
@@ -23,16 +23,20 @@
*
******************************************************************************/
-#include <cstdint>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/gatt/bta_gatts_int.h"
-#include "bta/include/bta_api.h"
-#include "bta/include/bta_gatts_co.h"
+#include "bt_target.h"
+
+#include <base/logging.h>
+#include <string.h>
+#include "bt_common.h"
+#include "bta_gatts_co.h"
+#include "bta_gatts_int.h"
+#include "bta_sys.h"
#include "btif/include/btif_debug_conn.h"
+#include "btm_ble_api.h"
#include "osi/include/osi.h"
-#include "stack/include/gatt_api.h"
+#include "utl.h"
+
+using base::StringPrintf;
static void bta_gatts_nv_save_cback(bool is_saved,
tGATTS_HNDL_RANGE* p_hndl_range);
@@ -43,29 +47,27 @@ static bool bta_gatts_nv_srv_chg_cback(tGATTS_SRV_CHG_CMD cmd,
static void bta_gatts_conn_cback(tGATT_IF gatt_if, const RawAddress& bda,
uint16_t conn_id, bool connected,
tGATT_DISCONN_REASON reason,
- tBT_TRANSPORT transport);
+ tGATT_TRANSPORT transport);
static void bta_gatts_send_request_cback(uint16_t conn_id, uint32_t trans_id,
tGATTS_REQ_TYPE req_type,
tGATTS_DATA* p_data);
static void bta_gatts_cong_cback(uint16_t conn_id, bool congested);
static void bta_gatts_phy_update_cback(tGATT_IF gatt_if, uint16_t conn_id,
uint8_t tx_phy, uint8_t rx_phy,
- tGATT_STATUS status);
+ uint8_t status);
static void bta_gatts_conn_update_cback(tGATT_IF gatt_if, uint16_t conn_id,
uint16_t interval, uint16_t latency,
- uint16_t timeout, tGATT_STATUS status);
-
-static tGATT_CBACK bta_gatts_cback = {
- .p_conn_cb = bta_gatts_conn_cback,
- .p_cmpl_cb = nullptr,
- .p_disc_res_cb = nullptr,
- .p_disc_cmpl_cb = nullptr,
- .p_req_cb = bta_gatts_send_request_cback,
- .p_enc_cmpl_cb = nullptr,
- .p_congestion_cb = bta_gatts_cong_cback,
- .p_phy_update_cb = bta_gatts_phy_update_cback,
- .p_conn_update_cb = bta_gatts_conn_update_cback,
-};
+ uint16_t timeout, uint8_t status);
+
+static tGATT_CBACK bta_gatts_cback = {bta_gatts_conn_cback,
+ NULL,
+ NULL,
+ NULL,
+ bta_gatts_send_request_cback,
+ NULL,
+ bta_gatts_cong_cback,
+ bta_gatts_phy_update_cback,
+ bta_gatts_conn_update_cback};
tGATT_APPL_INFO bta_gatts_nv_cback = {bta_gatts_nv_save_cback,
bta_gatts_nv_srv_chg_cback};
@@ -209,8 +211,7 @@ void bta_gatts_register(tBTA_GATTS_CB* p_cb, tBTA_GATTS_DATA* p_msg) {
p_cb->rcb[first_unuse].p_cback = p_msg->api_reg.p_cback;
p_cb->rcb[first_unuse].app_uuid = p_msg->api_reg.app_uuid;
cb_data.reg_oper.server_if = p_cb->rcb[first_unuse].gatt_if =
- GATT_Register(p_msg->api_reg.app_uuid, "GattServer", &bta_gatts_cback,
- p_msg->api_reg.eatt_support);
+ GATT_Register(p_msg->api_reg.app_uuid, &bta_gatts_cback);
if (!p_cb->rcb[first_unuse].gatt_if) {
status = GATT_NO_RESOURCES;
} else {
@@ -371,7 +372,7 @@ void bta_gatts_indicate_handle(tBTA_GATTS_CB* p_cb, tBTA_GATTS_DATA* p_msg) {
tGATT_STATUS status = GATT_ILLEGAL_PARAMETER;
tGATT_IF gatt_if;
RawAddress remote_bda;
- tBT_TRANSPORT transport;
+ tBTA_TRANSPORT transport;
tBTA_GATTS cb_data;
p_srvc_cb =
@@ -393,7 +394,7 @@ void bta_gatts_indicate_handle(tBTA_GATTS_CB* p_cb, tBTA_GATTS_DATA* p_msg) {
p_msg->api_indicate.len, p_msg->api_indicate.value);
/* if over BR_EDR, inform PM for mode change */
- if (transport == BT_TRANSPORT_BR_EDR) {
+ if (transport == BTA_TRANSPORT_BR_EDR) {
bta_sys_busy(BTA_ID_GATTS, BTA_ALL_APP_ID, remote_bda);
bta_sys_idle(BTA_ID_GATTS, BTA_ALL_APP_ID, remote_bda);
}
@@ -499,7 +500,7 @@ void bta_gatts_close(UNUSED_ATTR tBTA_GATTS_CB* p_cb, tBTA_GATTS_DATA* p_msg) {
tGATT_STATUS status = GATT_ERROR;
tGATT_IF gatt_if;
RawAddress remote_bda;
- tBT_TRANSPORT transport;
+ tGATT_TRANSPORT transport;
if (GATT_GetConnectionInfor(p_msg->hdr.layer_specific, &gatt_if, remote_bda,
&transport)) {
@@ -513,7 +514,7 @@ void bta_gatts_close(UNUSED_ATTR tBTA_GATTS_CB* p_cb, tBTA_GATTS_DATA* p_msg) {
p_rcb = bta_gatts_find_app_rcb_by_app_if(gatt_if);
if (p_rcb && p_rcb->p_cback) {
- if (transport == BT_TRANSPORT_BR_EDR)
+ if (transport == BTA_TRANSPORT_BR_EDR)
bta_sys_conn_close(BTA_ID_GATTS, BTA_ALL_APP_ID, remote_bda);
tBTA_GATTS bta_gatts;
@@ -540,7 +541,7 @@ static void bta_gatts_send_request_cback(uint16_t conn_id, uint32_t trans_id,
tBTA_GATTS cb_data;
tBTA_GATTS_RCB* p_rcb;
tGATT_IF gatt_if;
- tBT_TRANSPORT transport;
+ tGATT_TRANSPORT transport;
memset(&cb_data, 0, sizeof(tBTA_GATTS));
@@ -553,7 +554,7 @@ static void bta_gatts_send_request_cback(uint16_t conn_id, uint32_t trans_id,
if (p_rcb && p_rcb->p_cback) {
/* if over BR_EDR, inform PM for mode change */
- if (transport == BT_TRANSPORT_BR_EDR) {
+ if (transport == BTA_TRANSPORT_BR_EDR) {
bta_sys_busy(BTA_ID_GATTS, BTA_ALL_APP_ID, cb_data.req_data.remote_bda);
bta_sys_idle(BTA_ID_GATTS, BTA_ALL_APP_ID, cb_data.req_data.remote_bda);
}
@@ -583,25 +584,26 @@ static void bta_gatts_send_request_cback(uint16_t conn_id, uint32_t trans_id,
******************************************************************************/
static void bta_gatts_conn_cback(tGATT_IF gatt_if, const RawAddress& bdaddr,
uint16_t conn_id, bool connected,
- tGATT_DISCONN_REASON,
- tBT_TRANSPORT transport) {
+ tGATT_DISCONN_REASON reason,
+ tGATT_TRANSPORT transport) {
tBTA_GATTS cb_data;
uint8_t evt = connected ? BTA_GATTS_CONNECT_EVT : BTA_GATTS_DISCONNECT_EVT;
tBTA_GATTS_RCB* p_reg;
VLOG(1) << __func__ << " bda=" << bdaddr << " gatt_if= " << gatt_if
- << ", conn_id=" << loghex(conn_id) << " connected=" << connected;
+ << ", conn_id=" << loghex(conn_id) << " connected=" << connected
+ << ", reason=" << loghex(reason);
if (connected)
btif_debug_conn_state(bdaddr, BTIF_DEBUG_CONNECTED, GATT_CONN_UNKNOWN);
else
- btif_debug_conn_state(bdaddr, BTIF_DEBUG_DISCONNECTED, GATT_CONN_UNKNOWN);
+ btif_debug_conn_state(bdaddr, BTIF_DEBUG_DISCONNECTED, reason);
p_reg = bta_gatts_find_app_rcb_by_app_if(gatt_if);
if (p_reg && p_reg->p_cback) {
/* there is no RM for GATT */
- if (transport == BT_TRANSPORT_BR_EDR) {
+ if (transport == BTA_TRANSPORT_BR_EDR) {
if (connected)
bta_sys_conn_open(BTA_ID_GATTS, BTA_ALL_APP_ID, bdaddr);
else
@@ -610,6 +612,7 @@ static void bta_gatts_conn_cback(tGATT_IF gatt_if, const RawAddress& bdaddr,
cb_data.conn.conn_id = conn_id;
cb_data.conn.server_if = gatt_if;
+ cb_data.conn.reason = reason;
cb_data.conn.transport = transport;
cb_data.conn.remote_bda = bdaddr;
(*p_reg->p_cback)(evt, &cb_data);
@@ -620,7 +623,7 @@ static void bta_gatts_conn_cback(tGATT_IF gatt_if, const RawAddress& bdaddr,
static void bta_gatts_phy_update_cback(tGATT_IF gatt_if, uint16_t conn_id,
uint8_t tx_phy, uint8_t rx_phy,
- tGATT_STATUS status) {
+ uint8_t status) {
tBTA_GATTS_RCB* p_reg = bta_gatts_find_app_rcb_by_app_if(gatt_if);
if (!p_reg || !p_reg->p_cback) {
LOG(ERROR) << __func__ << ": server_if=" << +gatt_if << " not found";
@@ -638,7 +641,7 @@ static void bta_gatts_phy_update_cback(tGATT_IF gatt_if, uint16_t conn_id,
static void bta_gatts_conn_update_cback(tGATT_IF gatt_if, uint16_t conn_id,
uint16_t interval, uint16_t latency,
- uint16_t timeout, tGATT_STATUS status) {
+ uint16_t timeout, uint8_t status) {
tBTA_GATTS_RCB* p_reg = bta_gatts_find_app_rcb_by_app_if(gatt_if);
if (!p_reg || !p_reg->p_cback) {
LOG(ERROR) << __func__ << ": server_if=" << +gatt_if << " not found";
@@ -667,7 +670,7 @@ static void bta_gatts_conn_update_cback(tGATT_IF gatt_if, uint16_t conn_id,
static void bta_gatts_cong_cback(uint16_t conn_id, bool congested) {
tBTA_GATTS_RCB* p_rcb;
tGATT_IF gatt_if;
- tBT_TRANSPORT transport;
+ tGATT_TRANSPORT transport;
tBTA_GATTS cb_data;
if (GATT_GetConnectionInfor(conn_id, &gatt_if, cb_data.req_data.remote_bda,
diff --git a/bta/gatt/bta_gatts_api.cc b/bta/gatt/bta_gatts_api.cc
index 5e49a7c93..ef002692c 100644
--- a/bta/gatt/bta_gatts_api.cc
+++ b/bta/gatt/bta_gatts_api.cc
@@ -22,20 +22,16 @@
*
******************************************************************************/
-#include <base/bind.h>
-#include <base/location.h>
-#include <cstdint>
-#include <memory>
-#include <vector>
+#include "bt_target.h"
-#include "bt_target.h" // Must be first to define build configuration
+#include <base/bind.h>
+#include <string.h>
-#include "bta/gatt/bta_gatts_int.h"
-#include "osi/include/allocator.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "types/bluetooth/uuid.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
+#include "bt_common.h"
+#include "bta_gatt_api.h"
+#include "bta_gatts_int.h"
+#include "bta_sys.h"
+#include "stack/include/btu.h"
/*****************************************************************************
* Constants
@@ -61,7 +57,7 @@ void BTA_GATTS_Disable(void) {
return;
}
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_GATTS_API_DISABLE_EVT;
bta_sys_sendmsg(p_buf);
bta_sys_deregister(BTA_ID_GATTS);
@@ -81,7 +77,7 @@ void BTA_GATTS_Disable(void) {
*
******************************************************************************/
void BTA_GATTS_AppRegister(const bluetooth::Uuid& app_uuid,
- tBTA_GATTS_CBACK* p_cback, bool eatt_support) {
+ tBTA_GATTS_CBACK* p_cback) {
tBTA_GATTS_API_REG* p_buf =
(tBTA_GATTS_API_REG*)osi_malloc(sizeof(tBTA_GATTS_API_REG));
@@ -92,7 +88,6 @@ void BTA_GATTS_AppRegister(const bluetooth::Uuid& app_uuid,
p_buf->hdr.event = BTA_GATTS_API_REG_EVT;
p_buf->app_uuid = app_uuid;
p_buf->p_cback = p_cback;
- p_buf->eatt_support = eatt_support;
bta_sys_sendmsg(p_buf);
}
@@ -137,8 +132,7 @@ void bta_gatts_add_service_impl(tGATT_IF server_if,
return;
}
- tGATT_STATUS status =
- GATTS_AddService(server_if, service.data(), service.size());
+ uint16_t status = GATTS_AddService(server_if, service.data(), service.size());
if (status != GATT_SERVICE_STARTED) {
memset(&bta_gatts_cb.srvc_cb[srvc_idx], 0, sizeof(tBTA_GATTS_SRVC_CB));
LOG(ERROR) << __func__ << ": service creation failed.";
@@ -193,7 +187,7 @@ extern void BTA_GATTS_AddService(tGATT_IF server_if,
*
******************************************************************************/
void BTA_GATTS_DeleteService(uint16_t service_id) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_GATTS_API_DEL_SRVC_EVT;
p_buf->layer_specific = service_id;
@@ -213,7 +207,7 @@ void BTA_GATTS_DeleteService(uint16_t service_id) {
*
******************************************************************************/
void BTA_GATTS_StopService(uint16_t service_id) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_GATTS_API_STOP_SRVC_EVT;
p_buf->layer_specific = service_id;
@@ -303,7 +297,7 @@ void BTA_GATTS_SendRsp(uint16_t conn_id, uint32_t trans_id, tGATT_STATUS status,
*
******************************************************************************/
void BTA_GATTS_Open(tGATT_IF server_if, const RawAddress& remote_bda,
- bool is_direct, tBT_TRANSPORT transport) {
+ bool is_direct, tGATT_TRANSPORT transport) {
tBTA_GATTS_API_OPEN* p_buf =
(tBTA_GATTS_API_OPEN*)osi_malloc(sizeof(tBTA_GATTS_API_OPEN));
@@ -355,7 +349,7 @@ void BTA_GATTS_CancelOpen(tGATT_IF server_if, const RawAddress& remote_bda,
*
******************************************************************************/
void BTA_GATTS_Close(uint16_t conn_id) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_GATTS_API_CLOSE_EVT;
p_buf->layer_specific = conn_id;
diff --git a/bta/gatt/bta_gatts_int.h b/bta/gatt/bta_gatts_int.h
index 25cdf4923..adecf30b8 100644
--- a/bta/gatt/bta_gatts_int.h
+++ b/bta/gatt/bta_gatts_int.h
@@ -24,15 +24,13 @@
#ifndef BTA_GATTS_INT_H
#define BTA_GATTS_INT_H
-#include <cstdint>
+#include "bt_target.h"
+#include "bta_gatt_api.h"
+#include "bta_sys.h"
+#include "gatt_api.h"
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_gatt_api.h"
-#include "bta/sys/bta_sys.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_ble_api_types.h"
-#include "stack/include/gatt_api.h"
+#include <base/strings/stringprintf.h>
+#include "bt_common.h"
/*****************************************************************************
* Constants and data types
@@ -61,28 +59,27 @@ typedef uint16_t tBTA_GATTS_INT_EVT;
/* internal strucutre for GATTC register API */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
bluetooth::Uuid app_uuid;
tBTA_GATTS_CBACK* p_cback;
- bool eatt_support;
} tBTA_GATTS_API_REG;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tGATT_IF server_if;
} tBTA_GATTS_INT_START_IF;
typedef tBTA_GATTS_INT_START_IF tBTA_GATTS_API_DEREG;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tGATT_IF server_if;
btgatt_db_element_t* service;
uint16_t count;
} tBTA_GATTS_API_ADD_SERVICE;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint16_t attr_id;
uint16_t len;
bool need_confirm;
@@ -90,30 +87,30 @@ typedef struct {
} tBTA_GATTS_API_INDICATION;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint32_t trans_id;
tGATT_STATUS status;
tGATTS_RSP* p_rsp;
} tBTA_GATTS_API_RSP;
typedef struct {
- BT_HDR_RIGID hdr;
- tBT_TRANSPORT transport;
+ BT_HDR hdr;
+ tGATT_TRANSPORT transport;
} tBTA_GATTS_API_START;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress remote_bda;
tGATT_IF server_if;
bool is_direct;
- tBT_TRANSPORT transport;
+ tGATT_TRANSPORT transport;
} tBTA_GATTS_API_OPEN;
typedef tBTA_GATTS_API_OPEN tBTA_GATTS_API_CANCEL_OPEN;
typedef union {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_GATTS_API_REG api_reg;
tBTA_GATTS_API_DEREG api_dereg;
tBTA_GATTS_API_ADD_SERVICE api_add_service;
@@ -159,7 +156,7 @@ extern tBTA_GATTS_CB bta_gatts_cb;
/*****************************************************************************
* Function prototypes
****************************************************************************/
-extern bool bta_gatts_hdl_event(BT_HDR_RIGID* p_msg);
+extern bool bta_gatts_hdl_event(BT_HDR* p_msg);
extern void bta_gatts_api_disable(tBTA_GATTS_CB* p_cb);
extern void bta_gatts_api_enable(tBTA_GATTS_CB* p_cb, tBTA_GATTS_DATA* p_data);
diff --git a/bta/gatt/bta_gatts_main.cc b/bta/gatt/bta_gatts_main.cc
index 497f31558..1dc0aa22e 100644
--- a/bta/gatt/bta_gatts_main.cc
+++ b/bta/gatt/bta_gatts_main.cc
@@ -22,9 +22,12 @@
*
******************************************************************************/
-#include "bt_target.h" // Must be first to define build configuration
+#include "bt_target.h"
-#include "bta/gatt/bta_gatts_int.h"
+#include <string.h>
+
+#include "bt_common.h"
+#include "bta_gatts_int.h"
/* GATTS control block */
tBTA_GATTS_CB bta_gatts_cb;
@@ -39,7 +42,7 @@ tBTA_GATTS_CB bta_gatts_cb;
* Returns void
*
******************************************************************************/
-bool bta_gatts_hdl_event(BT_HDR_RIGID* p_msg) {
+bool bta_gatts_hdl_event(BT_HDR* p_msg) {
tBTA_GATTS_CB* p_cb = &bta_gatts_cb;
switch (p_msg->event) {
diff --git a/bta/gatt/bta_gatts_utils.cc b/bta/gatt/bta_gatts_utils.cc
index 27ef521d8..173d4f305 100644
--- a/bta/gatt/bta_gatts_utils.cc
+++ b/bta/gatt/bta_gatts_utils.cc
@@ -22,11 +22,14 @@
*
******************************************************************************/
-#include <cstdint>
+#include "bt_target.h"
-#include "bt_target.h" // Must be first to define build configuration
+#include <string.h>
-#include "bta/gatt/bta_gatts_int.h"
+#include "bt_common.h"
+#include "bta_gatts_int.h"
+#include "bta_sys.h"
+#include "utl.h"
/*******************************************************************************
*
diff --git a/bta/gatt/database.cc b/bta/gatt/database.cc
index 4e93078ac..58f70566f 100644
--- a/bta/gatt/database.cc
+++ b/bta/gatt/database.cc
@@ -18,7 +18,6 @@
#include "database.h"
#include "bt_trace.h"
-#include "stack/crypto_toolbox/crypto_toolbox.h"
#include "stack/include/gattdefs.h"
#include <base/logging.h>
@@ -35,19 +34,12 @@ const Uuid PRIMARY_SERVICE = Uuid::From16Bit(GATT_UUID_PRI_SERVICE);
const Uuid SECONDARY_SERVICE = Uuid::From16Bit(GATT_UUID_SEC_SERVICE);
const Uuid INCLUDE = Uuid::From16Bit(GATT_UUID_INCLUDE_SERVICE);
const Uuid CHARACTERISTIC = Uuid::From16Bit(GATT_UUID_CHAR_DECLARE);
-const Uuid CHARACTERISTIC_EXTENDED_PROPERTIES =
- Uuid::From16Bit(GATT_UUID_CHAR_EXT_PROP);
bool HandleInRange(const Service& svc, uint16_t handle) {
return handle >= svc.handle && handle <= svc.end_handle;
}
} // namespace
-static size_t UuidSize(const Uuid& uuid) {
- size_t len = uuid.GetShortestRepresentationSize();
- return (len == Uuid::kNumBytes32) ? Uuid::kNumBytes128 : len;
-}
-
Service* FindService(std::list<Service>& services, uint16_t handle) {
for (Service& service : services) {
if (handle >= service.handle && handle <= service.end_handle)
@@ -118,14 +110,7 @@ std::vector<StoredAttribute> Database::Serialize() const {
.uuid = charac.uuid}}});
for (const Descriptor& desc : charac.descriptors) {
- if (desc.uuid == CHARACTERISTIC_EXTENDED_PROPERTIES) {
- nv_attr.push_back({desc.handle,
- desc.uuid,
- {.characteristic_extended_properties =
- desc.characteristic_extended_properties}});
- } else {
- nv_attr.push_back({desc.handle, desc.uuid, {}});
- }
+ nv_attr.push_back({desc.handle, desc.uuid, {}});
}
}
}
@@ -192,116 +177,12 @@ Database Database::Deserialize(const std::vector<StoredAttribute>& nv_attr,
});
} else {
- if (attr.type == CHARACTERISTIC_EXTENDED_PROPERTIES) {
- current_service_it->characteristics.back().descriptors.emplace_back(
- Descriptor{.handle = attr.handle,
- .uuid = attr.type,
- .characteristic_extended_properties =
- attr.value.characteristic_extended_properties});
-
- } else {
- current_service_it->characteristics.back().descriptors.emplace_back(
- Descriptor{.handle = attr.handle, .uuid = attr.type});
- }
+ current_service_it->characteristics.back().descriptors.emplace_back(
+ Descriptor{.handle = attr.handle, .uuid = attr.type});
}
}
*success = true;
return result;
}
-Octet16 Database::Hash() const {
- int len = 0;
- // Compute how much space we need to actually hold the data.
- for (const Service& service : services) {
- len += 4 + UuidSize(service.uuid);
-
- for (const auto& is : service.included_services) {
- len += 8 + UuidSize(is.uuid);
- }
-
- for (const Characteristic& c : service.characteristics) {
- len += 7 + UuidSize(c.uuid);
-
- for (const Descriptor& d : c.descriptors) {
- if (UuidSize(d.uuid) != Uuid::kNumBytes16) {
- continue;
- }
- uint16_t value = d.uuid.As16Bit();
- if (value == GATT_UUID_CHAR_DESCRIPTION ||
- value == GATT_UUID_CHAR_CLIENT_CONFIG ||
- value == GATT_UUID_CHAR_SRVR_CONFIG ||
- value == GATT_UUID_CHAR_PRESENT_FORMAT ||
- value == GATT_UUID_CHAR_AGG_FORMAT) {
- len += 2 + UuidSize(d.uuid);
- } else if (value == GATT_UUID_CHAR_EXT_PROP) {
- len += 4 + UuidSize(d.uuid);
- }
- }
- }
- }
-
- std::vector<uint8_t> serialized(len);
- uint8_t* p = serialized.data();
- for (const Service& service : services) {
- UINT16_TO_STREAM(p, service.handle);
- if (service.is_primary) {
- UINT16_TO_STREAM(p, GATT_UUID_PRI_SERVICE);
- } else {
- UINT16_TO_STREAM(p, GATT_UUID_SEC_SERVICE);
- }
-
- if (UuidSize(service.uuid) == Uuid::kNumBytes16) {
- UINT16_TO_STREAM(p, service.uuid.As16Bit());
- } else {
- ARRAY_TO_STREAM(p, service.uuid.To128BitLE(), (int)Uuid::kNumBytes128);
- }
-
- for (const auto& is : service.included_services) {
- UINT16_TO_STREAM(p, is.handle);
- UINT16_TO_STREAM(p, GATT_UUID_INCLUDE_SERVICE);
- UINT16_TO_STREAM(p, is.start_handle);
- UINT16_TO_STREAM(p, is.end_handle);
-
- if (UuidSize(is.uuid) == Uuid::kNumBytes16) {
- UINT16_TO_STREAM(p, is.uuid.As16Bit());
- } else {
- ARRAY_TO_STREAM(p, is.uuid.To128BitLE(), (int)Uuid::kNumBytes128);
- }
- }
-
- for (const Characteristic& c : service.characteristics) {
- UINT16_TO_STREAM(p, c.declaration_handle);
- UINT16_TO_STREAM(p, GATT_UUID_CHAR_DECLARE);
- UINT8_TO_STREAM(p, c.properties);
- UINT16_TO_STREAM(p, c.value_handle);
-
- if (UuidSize(c.uuid) == Uuid::kNumBytes16) {
- UINT16_TO_STREAM(p, c.uuid.As16Bit());
- } else {
- ARRAY_TO_STREAM(p, c.uuid.To128BitLE(), (int)Uuid::kNumBytes128);
- }
-
- for (const Descriptor& d : c.descriptors) {
- if (UuidSize(d.uuid) != Uuid::kNumBytes16) continue;
- uint16_t value = d.uuid.As16Bit();
- if (value == GATT_UUID_CHAR_DESCRIPTION ||
- value == GATT_UUID_CHAR_CLIENT_CONFIG ||
- value == GATT_UUID_CHAR_SRVR_CONFIG ||
- value == GATT_UUID_CHAR_PRESENT_FORMAT ||
- value == GATT_UUID_CHAR_AGG_FORMAT) {
- UINT16_TO_STREAM(p, d.handle);
- UINT16_TO_STREAM(p, d.uuid.As16Bit());
- } else if (value == GATT_UUID_CHAR_EXT_PROP) {
- UINT16_TO_STREAM(p, d.handle);
- UINT16_TO_STREAM(p, d.uuid.As16Bit());
- UINT16_TO_STREAM(p, d.characteristic_extended_properties);
- }
- }
- }
- }
-
- std::reverse(serialized.begin(), serialized.end());
- return crypto_toolbox::aes_cmac(Octet16{0}, serialized.data(),
- serialized.size());
-}
} // namespace gatt
diff --git a/bta/gatt/database.h b/bta/gatt/database.h
index 53c03e5db..d1ba836e5 100644
--- a/bta/gatt/database.h
+++ b/bta/gatt/database.h
@@ -24,7 +24,6 @@
#include <utility>
#include <vector>
-#include "stack/include/bt_types.h" /* for Octet16 */
#include "types/bluetooth/uuid.h"
namespace gatt {
@@ -50,16 +49,14 @@ struct StoredAttribute {
bluetooth::Uuid uuid;
} included_service;
- /* characteristic definition */
+ /* characteristic deifnition */
struct {
uint8_t properties;
uint16_t value_handle;
bluetooth::Uuid uuid;
} characteristic;
- /* for descriptor we store value only for
- * «Characteristic Extended Properties» */
- uint16_t characteristic_extended_properties;
+ /* for descriptor definition we don't store value*/
} value;
};
@@ -94,8 +91,6 @@ struct Characteristic {
struct Descriptor {
uint16_t handle;
bluetooth::Uuid uuid;
- /* set and used for «Characteristic Extended Properties» only */
- uint16_t characteristic_extended_properties;
};
class DatabaseBuilder;
@@ -119,9 +114,6 @@ class Database {
static Database Deserialize(const std::vector<gatt::StoredAttribute>& nv_attr,
bool* success);
- /* Return 128 bit unique identifier of this GATT database */
- Octet16 Hash() const;
-
friend class DatabaseBuilder;
private:
diff --git a/bta/gatt/database_builder.cc b/bta/gatt/database_builder.cc
index a35cd35fd..98c0a2712 100644
--- a/bta/gatt/database_builder.cc
+++ b/bta/gatt/database_builder.cc
@@ -16,19 +16,12 @@
*
******************************************************************************/
-#include <algorithm>
-#include <cstdint>
-#include <list>
-#include <string>
-#include <utility>
-#include <vector>
+#include "database_builder.h"
-#include "bt_target.h" // Must be first to define build configuration
+#include "bt_trace.h"
-#include "bta/gatt/database.h"
-#include "bta/gatt/database_builder.h"
-#include "stack/include/gattdefs.h"
-#include "types/bluetooth/uuid.h"
+#include <base/logging.h>
+#include <algorithm>
using bluetooth::Uuid;
@@ -132,11 +125,6 @@ void DatabaseBuilder::AddDescriptor(uint16_t handle, const Uuid& uuid) {
char_node->descriptors.emplace_back(
gatt::Descriptor{.handle = handle, .uuid = uuid});
-
- // We must read value for Characteristic Extended Properties
- if (uuid == Uuid::From16Bit(GATT_UUID_CHAR_EXT_PROP)) {
- descriptor_handles_to_read.emplace_back(handle);
- }
}
bool DatabaseBuilder::StartNextServiceExploration() {
@@ -192,51 +180,6 @@ std::pair<uint16_t, uint16_t> DatabaseBuilder::NextDescriptorRangeToExplore() {
return {HANDLE_MAX, HANDLE_MAX};
}
-Descriptor* FindDescriptorByHandle(std::list<Service>& services,
- uint16_t handle) {
- Service* service = FindService(services, handle);
- if (!service) return nullptr;
-
- Characteristic* char_node = &service->characteristics.front();
- for (auto it = service->characteristics.begin();
- it != service->characteristics.end(); it++) {
- if (it->declaration_handle > handle) break;
- char_node = &(*it);
- }
-
- for (auto& descriptor : char_node->descriptors) {
- if (descriptor.handle == handle) return &descriptor;
- }
-
- return nullptr;
-}
-
-bool DatabaseBuilder::SetValueOfDescriptors(
- const std::vector<uint16_t>& values) {
- if (values.size() > descriptor_handles_to_read.size()) {
- LOG(ERROR) << "values.size() <= descriptors.size() expected";
- descriptor_handles_to_read.clear();
- return false;
- }
-
- for (size_t i = 0; i < values.size(); i++) {
- Descriptor* d = FindDescriptorByHandle(database.services,
- descriptor_handles_to_read[i]);
- if (!d) {
- LOG(ERROR) << __func__ << "non-existing descriptor!";
- descriptor_handles_to_read.clear();
- return false;
- }
-
- d->characteristic_extended_properties = values[i];
- }
-
- descriptor_handles_to_read.erase(
- descriptor_handles_to_read.begin(),
- descriptor_handles_to_read.begin() + values.size());
- return true;
-}
-
bool DatabaseBuilder::InProgress() const { return !database.services.empty(); }
Database DatabaseBuilder::Build() {
diff --git a/bta/gatt/database_builder.h b/bta/gatt/database_builder.h
index e9ae03097..d2cc72054 100644
--- a/bta/gatt/database_builder.h
+++ b/bta/gatt/database_builder.h
@@ -18,7 +18,7 @@
#pragma once
-#include "bta/gatt/database.h"
+#include "gatt/database.h"
#include <utility>
@@ -50,17 +50,6 @@ class DatabaseBuilder {
*/
std::pair<uint16_t, uint16_t> NextDescriptorRangeToExplore();
- /* Return vector of "Characteristic Extended Properties" descriptors that must
- * be read as part of service discovery process */
- std::vector<uint16_t> DescriptorHandlesToRead() {
- return descriptor_handles_to_read;
- }
-
- /* Assign value to descriptors from |DescriptorHandlesToRead()|. Values must
- * be in same order. Returns |true| if all goes well, |false| if there is
- * problem mapping values to descriptors. */
- bool SetValueOfDescriptors(const std::vector<uint16_t>& values);
-
/* Returns true, if GATT discovery is in progress, false if discovery was not
* started, or is already finished.
*/
@@ -89,10 +78,6 @@ class DatabaseBuilder {
/* sorted, unique set of start_handle, end_handle pair of all services that
* have not yet been discovered */
std::set<std::pair<uint16_t, uint16_t>> services_to_discover;
-
- /* handles of "Characteristic Extended Properties" descriptors that must be
- * read as part of service discovery process */
- std::vector<uint16_t> descriptor_handles_to_read;
};
} // namespace gatt
diff --git a/bta/hd/bta_hd_act.cc b/bta/hd/bta_hd_act.cc
index 089f7bbbf..a37a05167 100644
--- a/bta/hd/bta_hd_act.cc
+++ b/bta/hd/bta_hd_act.cc
@@ -23,19 +23,21 @@
*
******************************************************************************/
-#include <cstdint>
-#include <string>
+#include "bt_target.h"
-// BTA_HD_INCLUDED
-#include "bt_target.h" // Must be first to define build configuration
#if defined(BTA_HD_INCLUDED) && (BTA_HD_INCLUDED == TRUE)
-#include "bta/hd/bta_hd_int.h"
-#include "include/hardware/bt_hd.h"
-#include "osi/include/allocator.h"
-#include "osi/include/log.h"
-#include "stack/include/hidd_api.h"
-#include "types/raw_address.h"
+#include <hardware/bluetooth.h>
+#include <hardware/bt_hd.h>
+#include <string.h>
+
+#include "bt_utils.h"
+#include "bta_hd_int.h"
+#include "bta_sys.h"
+#include "btm_api.h"
+
+#include "log/log.h"
+#include "osi/include/osi.h"
static void bta_hd_cback(const RawAddress& bd_addr, uint8_t event,
uint32_t data, BT_HDR* pdata);
@@ -89,6 +91,8 @@ void bta_hd_api_enable(tBTA_HD_DATA* p_data) {
memset(&bta_hd_cb, 0, sizeof(tBTA_HD_CB));
+ HID_DevSetSecurityLevel(BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT);
+
/* store parameters */
bta_hd_cb.p_cback = p_data->api_enable.p_cback;
@@ -217,7 +221,7 @@ void bta_hd_register_act(tBTA_HD_DATA* p_data) {
* Returns void
*
******************************************************************************/
-void bta_hd_unregister_act() {
+void bta_hd_unregister_act(UNUSED_ATTR tBTA_HD_DATA* p_data) {
tBTA_HD_STATUS status = BTA_HD_OK;
APPL_TRACE_API("%s", __func__);
@@ -253,7 +257,7 @@ void bta_hd_unregister2_act(tBTA_HD_DATA* p_data) {
bta_hd_close_act(p_data);
// then unregister
- bta_hd_unregister_act();
+ bta_hd_unregister_act(p_data);
if (bta_hd_cb.disable_w4_close) {
bta_hd_api_disable();
@@ -303,7 +307,7 @@ extern void bta_hd_connect_act(tBTA_HD_DATA* p_data) {
* Returns void
*
******************************************************************************/
-extern void bta_hd_disconnect_act() {
+extern void bta_hd_disconnect_act(UNUSED_ATTR tBTA_HD_DATA* p_data) {
tHID_STATUS ret;
tBTA_HD cback_data;
@@ -415,7 +419,7 @@ extern void bta_hd_report_error_act(tBTA_HD_DATA* p_data) {
* Returns void
*
******************************************************************************/
-extern void bta_hd_vc_unplug_act() {
+extern void bta_hd_vc_unplug_act(UNUSED_ATTR tBTA_HD_DATA* p_data) {
tHID_STATUS ret;
APPL_TRACE_API("%s", __func__);
diff --git a/bta/hd/bta_hd_api.cc b/bta/hd/bta_hd_api.cc
index 4b33cd3ab..40963cce2 100644
--- a/bta/hd/bta_hd_api.cc
+++ b/bta/hd/bta_hd_api.cc
@@ -23,16 +23,17 @@
*
******************************************************************************/
-#define LOG_TAG "bluetooth"
+#include "bt_target.h"
-// BTA_HD_INCLUDED
-#include "bt_target.h" // Must be first to define build configuration
#if defined(BTA_HD_INCLUDED) && (BTA_HD_INCLUDED == TRUE)
-#include "bta/hd/bta_hd_int.h"
-#include "osi/include/allocator.h"
-#include "osi/include/compat.h"
-#include "osi/include/log.h"
+#include <log/log.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "bta_hd_api.h"
+#include "bta_hd_int.h"
/*****************************************************************************
* Constants
@@ -79,7 +80,7 @@ void BTA_HdDisable(void) {
bta_sys_deregister(BTA_ID_HD);
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_HD_API_DISABLE_EVT;
bta_sys_sendmsg(p_buf);
}
@@ -152,7 +153,7 @@ extern void BTA_HdRegisterApp(tBTA_HD_APP_INFO* p_app_info,
extern void BTA_HdUnregisterApp(void) {
APPL_TRACE_API("%s", __func__);
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_HD_API_UNREGISTER_APP_EVT;
bta_sys_sendmsg(p_buf);
@@ -203,7 +204,7 @@ extern void BTA_HdSendReport(tBTA_HD_REPORT* p_report) {
extern void BTA_HdVirtualCableUnplug(void) {
APPL_TRACE_API("%s", __func__);
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_HD_API_VC_UNPLUG_EVT;
bta_sys_sendmsg(p_buf);
@@ -242,7 +243,7 @@ extern void BTA_HdConnect(const RawAddress& addr) {
******************************************************************************/
extern void BTA_HdDisconnect(void) {
APPL_TRACE_API("%s", __func__);
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_HD_API_DISCONNECT_EVT;
bta_sys_sendmsg(p_buf);
diff --git a/bta/hd/bta_hd_int.h b/bta/hd/bta_hd_int.h
index 67f282bc0..0748b677e 100644
--- a/bta/hd/bta_hd_int.h
+++ b/bta/hd/bta_hd_int.h
@@ -26,13 +26,9 @@
#ifndef BTA_HD_INT_H
#define BTA_HD_INT_H
-#include <cstdint>
-
-#include "bta/include/bta_hd_api.h"
-#include "bta/sys/bta_sys.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/hiddefs.h"
-#include "types/raw_address.h"
+#include "bta_hd_api.h"
+#include "bta_sys.h"
+#include "hiddefs.h"
enum {
BTA_HD_API_REGISTER_APP_EVT = BTA_SYS_EVT_START(BTA_ID_HD),
@@ -63,7 +59,7 @@ typedef uint16_t tBTA_HD_INT_EVT;
#define BTA_HD_INVALID_EVT (BTA_HD_API_DISABLE_EVT + 1)
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_HD_CBACK* p_cback;
} tBTA_HD_API_ENABLE;
@@ -80,7 +76,7 @@ typedef struct {
#define BTA_HD_STATE_REMOVING 0x05
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
char name[BTA_HD_APP_NAME_LEN];
char description[BTA_HD_APP_DESCRIPTION_LEN];
char provider[BTA_HD_APP_PROVIDER_LEN];
@@ -95,7 +91,7 @@ typedef struct {
#define BTA_HD_REPORT_LEN HID_DEV_MTU_SIZE
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
bool use_intr;
uint8_t type;
uint8_t id;
@@ -104,18 +100,18 @@ typedef struct {
} tBTA_HD_SEND_REPORT;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress addr;
} tBTA_HD_DEVICE_CTRL;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint8_t error;
} tBTA_HD_REPORT_ERR;
/* union of all event data types */
typedef union {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_HD_API_ENABLE api_enable;
tBTA_HD_REGISTER_APP register_app;
tBTA_HD_SEND_REPORT send_report;
@@ -124,7 +120,7 @@ typedef union {
} tBTA_HD_DATA;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress addr;
uint32_t data;
BT_HDR* p_data;
@@ -150,21 +146,21 @@ extern tBTA_HD_CB bta_hd_cb;
/*****************************************************************************
* Function prototypes
****************************************************************************/
-extern bool bta_hd_hdl_event(BT_HDR_RIGID* p_msg);
+extern bool bta_hd_hdl_event(BT_HDR* p_msg);
extern void bta_hd_api_enable(tBTA_HD_DATA* p_data);
extern void bta_hd_api_disable(void);
extern void bta_hd_register_act(tBTA_HD_DATA* p_data);
-extern void bta_hd_unregister_act();
+extern void bta_hd_unregister_act(tBTA_HD_DATA* p_data);
extern void bta_hd_unregister2_act(tBTA_HD_DATA* p_data);
extern void bta_hd_connect_act(tBTA_HD_DATA* p_data);
-extern void bta_hd_disconnect_act();
+extern void bta_hd_disconnect_act(tBTA_HD_DATA* p_data);
extern void bta_hd_add_device_act(tBTA_HD_DATA* p_data);
extern void bta_hd_remove_device_act(tBTA_HD_DATA* p_data);
extern void bta_hd_send_report_act(tBTA_HD_DATA* p_data);
extern void bta_hd_report_error_act(tBTA_HD_DATA* p_data);
-extern void bta_hd_vc_unplug_act();
+extern void bta_hd_vc_unplug_act(tBTA_HD_DATA* p_data);
extern void bta_hd_open_act(tBTA_HD_DATA* p_data);
extern void bta_hd_close_act(tBTA_HD_DATA* p_data);
diff --git a/bta/hd/bta_hd_main.cc b/bta/hd/bta_hd_main.cc
index 022f8fe6c..84784b1af 100644
--- a/bta/hd/bta_hd_main.cc
+++ b/bta/hd/bta_hd_main.cc
@@ -23,13 +23,14 @@
*
******************************************************************************/
-#include <cstdint>
+#include "bt_target.h"
-// BTA_HD_INCLUDED
-#include "bt_target.h" // Must be first to define build configuration
#if defined(BTA_HD_INCLUDED) && (BTA_HD_INCLUDED == TRUE)
-#include "bta/hd/bta_hd_int.h"
+#include <string.h>
+
+#include "bta_hd_api.h"
+#include "bta_hd_int.h"
/*****************************************************************************
* Constants and types
@@ -45,126 +46,224 @@ enum {
};
typedef uint8_t tBTA_HD_STATE;
+/* state machine actions */
+enum {
+ BTA_HD_REGISTER_ACT,
+ BTA_HD_UNREGISTER_ACT,
+ BTA_HD_UNREGISTER2_ACT,
+ BTA_HD_CONNECT_ACT,
+ BTA_HD_DISCONNECT_ACT,
+ BTA_HD_ADD_DEVICE_ACT,
+ BTA_HD_REMOVE_DEVICE_ACT,
+ BTA_HD_SEND_REPORT_ACT,
+ BTA_HD_REPORT_ERROR_ACT,
+ BTA_HD_VC_UNPLUG_ACT,
+
+ BTA_HD_OPEN_ACT,
+ BTA_HD_CLOSE_ACT,
+ BTA_HD_INTR_DATA_ACT,
+ BTA_HD_GET_REPORT_ACT,
+ BTA_HD_SET_REPORT_ACT,
+ BTA_HD_SET_PROTOCOL_ACT,
+ BTA_HD_VC_UNPLUG_DONE_ACT,
+ BTA_HD_SUSPEND_ACT,
+ BTA_HD_EXIT_SUSPEND_ACT,
+
+ BTA_HD_NUM_ACTIONS
+};
+
+#define BTA_HD_IGNORE BTA_HD_NUM_ACTIONS
+
+typedef void (*tBTA_HD_ACTION)(tBTA_HD_DATA* p_data);
+
+/* action functions */
+const tBTA_HD_ACTION bta_hd_action[] = {
+ bta_hd_register_act, bta_hd_unregister_act, bta_hd_unregister2_act,
+ bta_hd_connect_act, bta_hd_disconnect_act, bta_hd_add_device_act,
+ bta_hd_remove_device_act, bta_hd_send_report_act, bta_hd_report_error_act,
+ bta_hd_vc_unplug_act,
+
+ bta_hd_open_act, bta_hd_close_act, bta_hd_intr_data_act,
+ bta_hd_get_report_act, bta_hd_set_report_act, bta_hd_set_protocol_act,
+ bta_hd_vc_unplug_done_act, bta_hd_suspend_act, bta_hd_exit_suspend_act,
+};
+
+/* state table information */
+#define BTA_HD_ACTION 0 /* position of action */
+#define BTA_HD_NEXT_STATE 1 /* position of next state */
+#define BTA_HD_NUM_COLS 2 /* number of columns */
+
+const uint8_t bta_hd_st_init[][BTA_HD_NUM_COLS] = {
+ /* Event Action Next state
+ */
+ /* BTA_HD_API_REGISTER_APP_EVT */ {BTA_HD_REGISTER_ACT, BTA_HD_IDLE_ST},
+ /* BTA_HD_API_UNREGISTER_APP_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_API_CONNECT_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_API_DISCONNECT_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_API_ADD_DEVICE_EVT */ {BTA_HD_ADD_DEVICE_ACT, BTA_HD_INIT_ST},
+ /* BTA_HD_API_REMOVE_DEVICE_EVT */ {BTA_HD_REMOVE_DEVICE_ACT, BTA_HD_INIT_ST},
+ /* BTA_HD_API_SEND_REPORT_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_API_REPORT_ERROR_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_API_VC_UNPLUG_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_INT_OPEN_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_INT_CLOSE_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_INT_INTR_DATA_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_INT_GET_REPORT_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_INT_SET_REPORT_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_INT_SET_PROTOCOL_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_INT_VC_UNPLUG_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_INT_SUSPEND_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+ /* BTA_HD_INT_EXIT_SUSPEND_EVT */ {BTA_HD_IGNORE, BTA_HD_INIT_ST},
+};
+
+const uint8_t bta_hd_st_idle[][BTA_HD_NUM_COLS] = {
+ /* Event Action Next state
+ */
+ /* BTA_HD_API_REGISTER_APP_EVT */ {BTA_HD_IGNORE, BTA_HD_IDLE_ST},
+ /* BTA_HD_API_UNREGISTER_APP_EVT */ {BTA_HD_UNREGISTER_ACT, BTA_HD_INIT_ST},
+ /* BTA_HD_API_CONNECT_EVT */ {BTA_HD_CONNECT_ACT, BTA_HD_IDLE_ST},
+ /* BTA_HD_API_DISCONNECT_EVT */ {BTA_HD_DISCONNECT_ACT, BTA_HD_IDLE_ST},
+ /* BTA_HD_API_ADD_DEVICE_EVT */ {BTA_HD_ADD_DEVICE_ACT, BTA_HD_IDLE_ST},
+ /* BTA_HD_API_REMOVE_DEVICE_EVT */ {BTA_HD_REMOVE_DEVICE_ACT, BTA_HD_IDLE_ST},
+ /* BTA_HD_API_SEND_REPORT_EVT */ {BTA_HD_SEND_REPORT_ACT, BTA_HD_IDLE_ST},
+ /* BTA_HD_API_REPORT_ERROR_EVT */ {BTA_HD_IGNORE, BTA_HD_IDLE_ST},
+ /* BTA_HD_API_VC_UNPLUG_EVT */ {BTA_HD_IGNORE, BTA_HD_IDLE_ST},
+ /* BTA_HD_INT_OPEN_EVT */ {BTA_HD_OPEN_ACT, BTA_HD_CONN_ST},
+ /* BTA_HD_INT_CLOSE_EVT */ {BTA_HD_CLOSE_ACT, BTA_HD_IDLE_ST},
+ /* BTA_HD_INT_INTR_DATA_EVT */ {BTA_HD_IGNORE, BTA_HD_IDLE_ST},
+ /* BTA_HD_INT_GET_REPORT_EVT */ {BTA_HD_IGNORE, BTA_HD_IDLE_ST},
+ /* BTA_HD_INT_SET_REPORT_EVT */ {BTA_HD_IGNORE, BTA_HD_IDLE_ST},
+ /* BTA_HD_INT_SET_PROTOCOL_EVT */ {BTA_HD_IGNORE, BTA_HD_IDLE_ST},
+ /* BTA_HD_INT_VC_UNPLUG_EVT */ {BTA_HD_IGNORE, BTA_HD_IDLE_ST},
+ /* BTA_HD_INT_SUSPEND_EVT */ {BTA_HD_IGNORE, BTA_HD_IDLE_ST},
+ /* BTA_HD_INT_EXIT_SUSPEND_EVT */ {BTA_HD_IGNORE, BTA_HD_IDLE_ST},
+};
+
+const uint8_t bta_hd_st_conn[][BTA_HD_NUM_COLS] = {
+ /* Event Action Next state */
+ /* BTA_HD_API_REGISTER_APP_EVT */ {BTA_HD_IGNORE, BTA_HD_CONN_ST},
+ /* BTA_HD_API_UNREGISTER_APP_EVT */ {BTA_HD_DISCONNECT_ACT,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_API_CONNECT_EVT */ {BTA_HD_IGNORE, BTA_HD_CONN_ST},
+ /* BTA_HD_API_DISCONNECT_EVT */ {BTA_HD_DISCONNECT_ACT, BTA_HD_CONN_ST},
+ /* BTA_HD_API_ADD_DEVICE_EVT */ {BTA_HD_ADD_DEVICE_ACT, BTA_HD_CONN_ST},
+ /* BTA_HD_API_REMOVE_DEVICE_EVT */ {BTA_HD_REMOVE_DEVICE_ACT,
+ BTA_HD_CONN_ST},
+ /* BTA_HD_API_SEND_REPORT_EVT */ {BTA_HD_SEND_REPORT_ACT,
+ BTA_HD_CONN_ST},
+ /* BTA_HD_API_REPORT_ERROR_EVT */ {BTA_HD_REPORT_ERROR_ACT,
+ BTA_HD_CONN_ST},
+ /* BTA_HD_API_VC_UNPLUG_EVT */ {BTA_HD_VC_UNPLUG_ACT, BTA_HD_CONN_ST},
+ /* BTA_HD_INT_OPEN_EVT */ {BTA_HD_IGNORE, BTA_HD_CONN_ST},
+ /* BTA_HD_INT_CLOSE_EVT */ {BTA_HD_CLOSE_ACT, BTA_HD_IDLE_ST},
+ /* BTA_HD_INT_INTR_DATA_EVT */ {BTA_HD_INTR_DATA_ACT, BTA_HD_CONN_ST},
+ /* BTA_HD_INT_GET_REPORT_EVT */ {BTA_HD_GET_REPORT_ACT, BTA_HD_CONN_ST},
+ /* BTA_HD_INT_SET_REPORT_EVT */ {BTA_HD_SET_REPORT_ACT, BTA_HD_CONN_ST},
+ /* BTA_HD_INT_SET_PROTOCOL_EVT */ {BTA_HD_SET_PROTOCOL_ACT,
+ BTA_HD_CONN_ST},
+ /* BTA_HD_INT_VC_UNPLUG_EVT */ {BTA_HD_VC_UNPLUG_DONE_ACT,
+ BTA_HD_IDLE_ST},
+ /* BTA_HD_INT_SUSPEND_EVT */ {BTA_HD_SUSPEND_ACT, BTA_HD_CONN_ST},
+ /* BTA_HD_INT_EXIT_SUSPEND_EVT */ {BTA_HD_EXIT_SUSPEND_ACT,
+ BTA_HD_CONN_ST},
+};
+
+const uint8_t bta_hd_st_transient_to_init[][BTA_HD_NUM_COLS] = {
+ /* Event Action Next state */
+ /* BTA_HD_API_REGISTER_APP_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_API_UNREGISTER_APP_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_API_CONNECT_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_API_DISCONNECT_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_API_ADD_DEVICE_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_API_REMOVE_DEVICE_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_API_SEND_REPORT_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_API_REPORT_ERROR_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_API_VC_UNPLUG_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_INT_OPEN_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_INT_CLOSE_EVT */ {BTA_HD_UNREGISTER2_ACT,
+ BTA_HD_INIT_ST},
+ /* BTA_HD_INT_INTR_DATA_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_INT_GET_REPORT_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_INT_SET_REPORT_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_INT_SET_PROTOCOL_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_INT_VC_UNPLUG_EVT */ {BTA_HD_UNREGISTER2_ACT,
+ BTA_HD_INIT_ST},
+ /* BTA_HD_INT_SUSPEND_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+ /* BTA_HD_INT_EXIT_SUSPEND_EVT */ {BTA_HD_IGNORE,
+ BTA_HD_TRANSIENT_TO_INIT_ST},
+};
+
+/* type for state table */
+typedef const uint8_t (*tBTA_HD_ST_TBL)[BTA_HD_NUM_COLS];
+
+/* state table */
+const tBTA_HD_ST_TBL bta_hd_st_tbl[] = {bta_hd_st_init, bta_hd_st_idle,
+ bta_hd_st_conn,
+ bta_hd_st_transient_to_init};
+
/*****************************************************************************
* Global data
****************************************************************************/
tBTA_HD_CB bta_hd_cb;
-static tBTA_HD_STATE get_state() { return bta_hd_cb.state; }
+static const char* bta_hd_evt_code(tBTA_HD_INT_EVT evt_code);
+static const char* bta_hd_state_code(tBTA_HD_STATE state_code);
-static void set_state(tBTA_HD_STATE state) { bta_hd_cb.state = state; }
+/*******************************************************************************
+ *
+ * Function bta_hd_sm_execute
+ *
+ * Description State machine event handling function for HID Device
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_hd_sm_execute(uint16_t event, tBTA_HD_DATA* p_data) {
+ tBTA_HD_ST_TBL state_table;
+ tBTA_HD_STATE prev_state;
+ uint8_t action;
+ tBTA_HD cback_data;
-static void bta_hd_better_state_machine(uint16_t event, tBTA_HD_DATA* p_data) {
- switch (get_state()) {
- case BTA_HD_INIT_ST:
- switch (event) {
- case BTA_HD_API_REGISTER_APP_EVT:
- set_state(BTA_HD_IDLE_ST);
- bta_hd_register_act(p_data);
- break;
- case BTA_HD_API_ADD_DEVICE_EVT:
- bta_hd_add_device_act(p_data);
- break;
- case BTA_HD_API_REMOVE_DEVICE_EVT:
- bta_hd_remove_device_act(p_data);
- break;
- }
- break;
- case BTA_HD_IDLE_ST:
- switch (event) {
- case BTA_HD_API_UNREGISTER_APP_EVT:
- set_state(BTA_HD_INIT_ST);
- bta_hd_unregister_act();
- break;
- case BTA_HD_API_CONNECT_EVT:
- bta_hd_connect_act(p_data);
- break;
- case BTA_HD_API_DISCONNECT_EVT:
- bta_hd_disconnect_act();
- break;
- case BTA_HD_API_ADD_DEVICE_EVT:
- bta_hd_add_device_act(p_data);
- break;
- case BTA_HD_API_REMOVE_DEVICE_EVT:
- bta_hd_remove_device_act(p_data);
- break;
- case BTA_HD_API_SEND_REPORT_EVT:
- bta_hd_send_report_act(p_data);
- break;
- case BTA_HD_INT_OPEN_EVT:
- set_state(BTA_HD_CONN_ST);
- bta_hd_open_act(p_data);
- break;
- case BTA_HD_INT_CLOSE_EVT:
- bta_hd_close_act(p_data);
- break;
- }
- break;
- case BTA_HD_CONN_ST:
- switch (event) {
- case BTA_HD_API_UNREGISTER_APP_EVT:
- set_state(BTA_HD_TRANSIENT_TO_INIT_ST);
- bta_hd_disconnect_act();
- break;
- case BTA_HD_API_DISCONNECT_EVT:
- bta_hd_disconnect_act();
- break;
- case BTA_HD_API_ADD_DEVICE_EVT:
- bta_hd_add_device_act(p_data);
- break;
- case BTA_HD_API_REMOVE_DEVICE_EVT:
- bta_hd_remove_device_act(p_data);
- break;
- case BTA_HD_API_SEND_REPORT_EVT:
- bta_hd_send_report_act(p_data);
- break;
- case BTA_HD_API_REPORT_ERROR_EVT:
- bta_hd_report_error_act(p_data);
- break;
- case BTA_HD_API_VC_UNPLUG_EVT:
- bta_hd_vc_unplug_act();
- break;
- case BTA_HD_INT_CLOSE_EVT:
- set_state(BTA_HD_IDLE_ST);
- bta_hd_close_act(p_data);
- break;
- case BTA_HD_INT_INTR_DATA_EVT:
- bta_hd_intr_data_act(p_data);
- break;
- case BTA_HD_INT_GET_REPORT_EVT:
- bta_hd_get_report_act(p_data);
- break;
- case BTA_HD_INT_SET_REPORT_EVT:
- bta_hd_set_report_act(p_data);
- break;
- case BTA_HD_INT_SET_PROTOCOL_EVT:
- bta_hd_set_protocol_act(p_data);
- break;
- case BTA_HD_INT_VC_UNPLUG_EVT:
- set_state(BTA_HD_IDLE_ST);
- bta_hd_vc_unplug_done_act(p_data);
- break;
- case BTA_HD_INT_SUSPEND_EVT:
- bta_hd_suspend_act(p_data);
- break;
- case BTA_HD_INT_EXIT_SUSPEND_EVT:
- bta_hd_exit_suspend_act(p_data);
- break;
- }
- break;
- case BTA_HD_TRANSIENT_TO_INIT_ST:
- switch (event) {
- case BTA_HD_INT_CLOSE_EVT:
- set_state(BTA_HD_INIT_ST);
- bta_hd_unregister2_act(p_data);
- break;
- case BTA_HD_INT_VC_UNPLUG_EVT:
- set_state(BTA_HD_INIT_ST);
- bta_hd_unregister2_act(p_data);
- break;
- }
- break;
+ APPL_TRACE_EVENT("%s: state=%s (%d) event=%s (%d)", __func__,
+ bta_hd_state_code(bta_hd_cb.state), bta_hd_cb.state,
+ bta_hd_evt_code(event), event);
+
+ prev_state = bta_hd_cb.state;
+
+ memset(&cback_data, 0, sizeof(tBTA_HD));
+
+ state_table = bta_hd_st_tbl[bta_hd_cb.state];
+
+ event &= 0xff;
+
+ action = state_table[event][BTA_HD_ACTION];
+ if (action < BTA_HD_IGNORE) {
+ (*bta_hd_action[action])(p_data);
}
+
+ bta_hd_cb.state = state_table[event][BTA_HD_NEXT_STATE];
+
+ if (bta_hd_cb.state != prev_state) {
+ APPL_TRACE_EVENT("%s: [new] state=%s (%d)", __func__,
+ bta_hd_state_code(bta_hd_cb.state), bta_hd_cb.state);
+ }
+
+ return;
}
/*******************************************************************************
@@ -176,7 +275,7 @@ static void bta_hd_better_state_machine(uint16_t event, tBTA_HD_DATA* p_data) {
* Returns void
*
******************************************************************************/
-bool bta_hd_hdl_event(BT_HDR_RIGID* p_msg) {
+bool bta_hd_hdl_event(BT_HDR* p_msg) {
APPL_TRACE_API("%s: p_msg->event=%d", __func__, p_msg->event);
switch (p_msg->event) {
@@ -191,17 +290,74 @@ bool bta_hd_hdl_event(BT_HDR_RIGID* p_msg) {
// unregister (and disconnect)
bta_hd_cb.disable_w4_close = TRUE;
- bta_hd_better_state_machine(BTA_HD_API_UNREGISTER_APP_EVT,
- (tBTA_HD_DATA*)p_msg);
+ bta_hd_sm_execute(BTA_HD_API_UNREGISTER_APP_EVT, (tBTA_HD_DATA*)p_msg);
} else {
bta_hd_api_disable();
}
break;
default:
- bta_hd_better_state_machine(p_msg->event, (tBTA_HD_DATA*)p_msg);
+ bta_hd_sm_execute(p_msg->event, (tBTA_HD_DATA*)p_msg);
}
return (TRUE);
}
+static const char* bta_hd_evt_code(tBTA_HD_INT_EVT evt_code) {
+ switch (evt_code) {
+ case BTA_HD_API_REGISTER_APP_EVT:
+ return "BTA_HD_API_REGISTER_APP_EVT";
+ case BTA_HD_API_UNREGISTER_APP_EVT:
+ return "BTA_HD_API_UNREGISTER_APP_EVT";
+ case BTA_HD_API_CONNECT_EVT:
+ return "BTA_HD_API_CONNECT_EVT";
+ case BTA_HD_API_DISCONNECT_EVT:
+ return "BTA_HD_API_DISCONNECT_EVT";
+ case BTA_HD_API_ADD_DEVICE_EVT:
+ return "BTA_HD_API_ADD_DEVICE_EVT";
+ case BTA_HD_API_REMOVE_DEVICE_EVT:
+ return "BTA_HD_API_REMOVE_DEVICE_EVT";
+ case BTA_HD_API_SEND_REPORT_EVT:
+ return "BTA_HD_API_SEND_REPORT_EVT";
+ case BTA_HD_API_REPORT_ERROR_EVT:
+ return "BTA_HD_API_REPORT_ERROR_EVT";
+ case BTA_HD_API_VC_UNPLUG_EVT:
+ return "BTA_HD_API_VC_UNPLUG_EVT";
+ case BTA_HD_INT_OPEN_EVT:
+ return "BTA_HD_INT_OPEN_EVT";
+ case BTA_HD_INT_CLOSE_EVT:
+ return "BTA_HD_INT_CLOSE_EVT";
+ case BTA_HD_INT_INTR_DATA_EVT:
+ return "BTA_HD_INT_INTR_DATA_EVT";
+ case BTA_HD_INT_GET_REPORT_EVT:
+ return "BTA_HD_INT_GET_REPORT_EVT";
+ case BTA_HD_INT_SET_REPORT_EVT:
+ return "BTA_HD_INT_SET_REPORT_EVT";
+ case BTA_HD_INT_SET_PROTOCOL_EVT:
+ return "BTA_HD_INT_SET_PROTOCOL_EVT";
+ case BTA_HD_INT_VC_UNPLUG_EVT:
+ return "BTA_HD_INT_VC_UNPLUG_EVT";
+ case BTA_HD_INT_SUSPEND_EVT:
+ return "BTA_HD_INT_SUSPEND_EVT";
+ case BTA_HD_INT_EXIT_SUSPEND_EVT:
+ return "BTA_HD_INT_EXIT_SUSPEND_EVT";
+ default:
+ return "<unknown>";
+ }
+}
+
+static const char* bta_hd_state_code(tBTA_HD_STATE state_code) {
+ switch (state_code) {
+ case BTA_HD_INIT_ST:
+ return "BTA_HD_INIT_ST";
+ case BTA_HD_IDLE_ST:
+ return "BTA_HD_IDLE_ST";
+ case BTA_HD_CONN_ST:
+ return "BTA_HD_CONN_ST";
+ case BTA_HD_TRANSIENT_TO_INIT_ST:
+ return "BTA_HD_TRANSIENT_TO_INIT_ST";
+ default:
+ return "<unknown>";
+ }
+}
+
#endif /* BTA_HD_INCLUDED */
diff --git a/bta/hearing_aid/hearing_aid.cc b/bta/hearing_aid/hearing_aid.cc
index f863d69a7..5c50c1aa3 100644
--- a/bta/hearing_aid/hearing_aid.cc
+++ b/bta/hearing_aid/hearing_aid.cc
@@ -18,29 +18,20 @@
#include "bta_hearing_aid_api.h"
-#define LOG_TAG "bluetooth"
-
-#include <base/bind.h>
-#include <base/callback.h>
-#include <base/strings/string_number_conversions.h> // HexEncode
-#include <cstdint>
-#include <vector>
-
-#include "bta/include/bta_gatt_api.h"
-#include "bta/include/bta_gatt_queue.h"
-#include "bta/include/bta_hearing_aid_api.h"
+#include "bta_gatt_api.h"
+#include "bta_gatt_queue.h"
+#include "btm_int.h"
#include "device/include/controller.h"
#include "embdrv/g722/g722_enc_dec.h"
-#include "osi/include/log.h"
+#include "gap_api.h"
+#include "gatt_api.h"
#include "osi/include/properties.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/acl_api.h" // BTM_ReadRSSI
-#include "stack/include/acl_api_types.h" // tBTM_RSSI_RESULT
-#include "stack/include/gap_api.h"
-#include "stack/include/l2c_api.h" // L2CAP_MIN_OFFSET
-#include "types/bluetooth/uuid.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
+
+#include <base/bind.h>
+#include <base/logging.h>
+#include <base/strings/string_number_conversions.h>
+#include <hardware/bt_hearing_aid.h>
+#include <vector>
using base::Closure;
using bluetooth::Uuid;
@@ -100,7 +91,8 @@ Uuid LE_PSM_UUID = Uuid::FromString("2d410339-82b6-42aa-b34e-e2e01
// clang-format on
void hearingaid_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data);
-void encryption_callback(const RawAddress*, tBT_TRANSPORT, void*, tBTM_STATUS);
+void encryption_callback(const RawAddress*, tGATT_TRANSPORT, void*,
+ tBTM_STATUS);
void read_rssi_cb(void* p_void);
inline BT_HDR* malloc_l2cap_buf(uint16_t len) {
@@ -207,7 +199,7 @@ static void write_rpt_ctl_cfg_cb(uint16_t conn_id, tGATT_STATUS status,
uint16_t handle, void* data) {
if (status != GATT_SUCCESS) {
LOG(ERROR) << __func__ << ": handle=" << handle << ", conn_id=" << conn_id
- << ", status=" << loghex(static_cast<uint8_t>(status));
+ << ", status=" << loghex(status);
}
}
@@ -282,7 +274,7 @@ class HearingAidImpl : public HearingAid {
instance->gatt_if = client_id;
initCb.Run();
},
- initCb), false);
+ initCb));
}
uint16_t UpdateBleConnParams(const RawAddress& address) {
@@ -320,20 +312,20 @@ class HearingAidImpl : public HearingAid {
void Connect(const RawAddress& address) override {
DVLOG(2) << __func__ << " " << address;
hearingDevices.Add(HearingDevice(address, true));
- BTA_GATTC_Open(gatt_if, address, true, false);
+ BTA_GATTC_Open(gatt_if, address, true, GATT_TRANSPORT_LE, false);
}
- void AddToAcceptlist(const RawAddress& address) override {
+ void AddToWhiteList(const RawAddress& address) override {
VLOG(2) << __func__ << " address: " << address;
hearingDevices.Add(HearingDevice(address, true));
- BTA_GATTC_Open(gatt_if, address, false, false);
+ BTA_GATTC_Open(gatt_if, address, false, GATT_TRANSPORT_LE, false);
}
- void AddFromStorage(const HearingDevice& dev_info, uint16_t is_acceptlisted) {
+ void AddFromStorage(const HearingDevice& dev_info, uint16_t is_white_listed) {
DVLOG(2) << __func__ << " " << dev_info.address
<< ", hiSyncId=" << loghex(dev_info.hi_sync_id)
- << ", isAcceptlisted=" << is_acceptlisted;
- if (is_acceptlisted) {
+ << ", isWhiteListed=" << is_white_listed;
+ if (is_white_listed) {
hearingDevices.Add(dev_info);
// TODO: we should increase the scanning window for few seconds, to get
@@ -341,7 +333,8 @@ class HearingAidImpl : public HearingAid {
// BTM_BleSetConnScanParams(2048, 1024);
/* add device into BG connection to accept remote initiated connection */
- BTA_GATTC_Open(gatt_if, dev_info.address, false, false);
+ BTA_GATTC_Open(gatt_if, dev_info.address, false, GATT_TRANSPORT_LE,
+ false);
}
callbacks->OnDeviceAvailable(dev_info.capabilities, dev_info.hi_sync_id,
@@ -352,7 +345,7 @@ class HearingAidImpl : public HearingAid {
void OnGattConnected(tGATT_STATUS status, uint16_t conn_id,
tGATT_IF client_if, RawAddress address,
- tBT_TRANSPORT transport, uint16_t mtu) {
+ tBTA_TRANSPORT transport, uint16_t mtu) {
VLOG(2) << __func__ << ": address=" << address << ", conn_id=" << conn_id;
HearingDevice* hearingDevice = hearingDevices.FindByAddress(address);
@@ -367,7 +360,7 @@ class HearingAidImpl : public HearingAid {
if (status != GATT_SUCCESS) {
if (!hearingDevice->connecting_actively) {
- // acceptlist connection failed, that's ok.
+ // whitelist connection failed, that's ok.
return;
}
@@ -397,7 +390,9 @@ class HearingAidImpl : public HearingAid {
hearingDevice->connection_update_status = AWAITING;
}
- if (controller_get_interface()->supports_ble_2m_phy()) {
+ tACL_CONN* p_acl = btm_bda_to_acl(address, BT_TRANSPORT_LE);
+ if (p_acl != nullptr && controller_get_interface()->supports_ble_2m_phy() &&
+ HCI_LE_2M_PHY_SUPPORTED(p_acl->peer_le_features)) {
LOG(INFO) << address << " set preferred PHY to 2M";
BTM_BleSetPhy(address, PHY_LE_2M, PHY_LE_2M, 0);
}
@@ -406,23 +401,31 @@ class HearingAidImpl : public HearingAid {
// TODO(jpawlowski: for 16khz only 87 is required, optimize
BTM_SetBleDataLength(address, 167);
- if (BTM_SecIsSecurityPending(address)) {
- /* if security collision happened, wait for encryption done
- * (BTA_GATTC_ENC_CMPL_CB_EVT) */
- return;
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(address);
+ if (p_dev_rec) {
+ if (p_dev_rec->sec_state == BTM_SEC_STATE_ENCRYPTING ||
+ p_dev_rec->sec_state == BTM_SEC_STATE_AUTHENTICATING) {
+ /* if security collision happened, wait for encryption done
+ * (BTA_GATTC_ENC_CMPL_CB_EVT) */
+ return;
+ }
}
/* verify bond */
- if (BTM_IsEncrypted(address, BT_TRANSPORT_LE)) {
+ uint8_t sec_flag = 0;
+ BTM_GetSecurityFlagsByTransport(address, &sec_flag, BT_TRANSPORT_LE);
+
+ if (sec_flag & BTM_SEC_FLAG_ENCRYPTED) {
/* if link has been encrypted */
OnEncryptionComplete(address, true);
return;
}
- if (BTM_IsLinkKeyKnown(address, BT_TRANSPORT_LE)) {
+ if (sec_flag & BTM_SEC_FLAG_LKEY_KNOWN) {
/* if bonded and link not encrypted */
- BTM_SetEncryption(address, BT_TRANSPORT_LE, encryption_callback, nullptr,
- BTM_BLE_SEC_ENCRYPT);
+ sec_flag = BTM_BLE_SEC_ENCRYPT;
+ BTM_SetEncryption(address, BTA_TRANSPORT_LE, encryption_callback, nullptr,
+ sec_flag);
return;
}
@@ -488,8 +491,8 @@ class HearingAidImpl : public HearingAid {
send_state_change_to_other_side(hearingDevice, conn_update);
send_state_change(hearingDevice, conn_update);
} else {
- LOG(INFO) << __func__ << ": error status="
- << loghex(static_cast<uint8_t>(p_data->conn_update.status))
+ LOG(INFO) << __func__
+ << ": error status=" << loghex(p_data->conn_update.status)
<< ", conn_id=" << conn_id
<< ", device=" << hearingDevice->address
<< ", connection_update_status="
@@ -876,7 +879,8 @@ class HearingAidImpl : public HearingAid {
uint16_t gap_handle = GAP_ConnOpen(
"", service_id, false, &hearingDevice->address, psm, 514 /* MPS */,
&cfg_info, nullptr, BTM_SEC_NONE /* TODO: request security ? */,
- HearingAidImpl::GapCallbackStatic, BT_TRANSPORT_LE);
+ L2CAP_FCR_LE_COC_MODE, HearingAidImpl::GapCallbackStatic,
+ BT_TRANSPORT_LE);
if (gap_handle == GAP_INVALID_HANDLE) {
LOG(ERROR) << "UNABLE TO GET gap_handle";
return;
@@ -934,7 +938,7 @@ class HearingAidImpl : public HearingAid {
if (register_status != GATT_SUCCESS) {
LOG(ERROR) << __func__
<< ": BTA_GATTC_RegisterForNotifications failed, status="
- << loghex(static_cast<uint8_t>(register_status));
+ << loghex(register_status);
return;
}
std::vector<uint8_t> value(2);
@@ -1362,6 +1366,14 @@ class HearingAidImpl : public HearingAid {
case GAP_EVT_CONN_UNCONGESTED:
DVLOG(2) << "GAP_EVT_CONN_UNCONGESTED";
break;
+
+ case GAP_EVT_LE_COC_CREDITS: {
+ auto& tmp = data->coc_credits;
+ DVLOG(2) << "GAP_EVT_LE_COC_CREDITS, for device: "
+ << hearingDevice->address << " added" << tmp.credits_received
+ << " credit_count: " << tmp.credit_count;
+ break;
+ }
}
}
@@ -1473,8 +1485,9 @@ class HearingAidImpl : public HearingAid {
DoDisconnectAudioStop();
}
- void OnGattDisconnected(uint16_t conn_id, tGATT_IF client_if,
- RawAddress remote_bda) {
+ void OnGattDisconnected(tGATT_STATUS status, uint16_t conn_id,
+ tGATT_IF client_if, RawAddress remote_bda,
+ tBTA_GATT_REASON reason) {
HearingDevice* hearingDevice = hearingDevices.FindByConnId(conn_id);
if (!hearingDevice) {
VLOG(2) << "Skipping unknown device disconnect, conn_id="
@@ -1482,7 +1495,7 @@ class HearingAidImpl : public HearingAid {
return;
}
VLOG(2) << __func__ << ": conn_id=" << loghex(conn_id)
- << ", remote_bda=" << remote_bda;
+ << ", reason=" << loghex(reason) << ", remote_bda=" << remote_bda;
// Inform the other side (if any) of this disconnection
std::vector<uint8_t> inform_disconn_state(
@@ -1492,8 +1505,9 @@ class HearingAidImpl : public HearingAid {
DoDisconnectCleanUp(hearingDevice);
// This is needed just for the first connection. After stack is restarted,
- // code that loads device will add them to acceptlist.
- BTA_GATTC_Open(gatt_if, hearingDevice->address, false, false);
+ // code that loads device will add them to whitelist.
+ BTA_GATTC_Open(gatt_if, hearingDevice->address, false, GATT_TRANSPORT_LE,
+ false);
callbacks->OnConnectionState(ConnectionState::DISCONNECTED, remote_bda);
@@ -1692,7 +1706,8 @@ void hearingaid_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
case BTA_GATTC_CLOSE_EVT: {
if (!instance) return;
tBTA_GATTC_CLOSE& c = p_data->close;
- instance->OnGattDisconnected(c.conn_id, c.client_if, c.remote_bda);
+ instance->OnGattDisconnected(c.status, c.conn_id, c.client_if,
+ c.remote_bda, c.reason);
} break;
case BTA_GATTC_SEARCH_CMPL_EVT:
@@ -1731,7 +1746,7 @@ void hearingaid_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
case BTA_GATTC_SRVC_DISC_DONE_EVT:
if (!instance) return;
- instance->OnServiceDiscDoneEvent(p_data->service_changed.remote_bda);
+ instance->OnServiceDiscDoneEvent(p_data->remote_bda);
break;
default:
@@ -1739,7 +1754,7 @@ void hearingaid_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
}
}
-void encryption_callback(const RawAddress* address, tBT_TRANSPORT, void*,
+void encryption_callback(const RawAddress* address, tGATT_TRANSPORT, void*,
tBTM_STATUS status) {
if (instance) {
instance->OnEncryptionComplete(*address,
@@ -1783,12 +1798,12 @@ HearingAid* HearingAid::Get() {
};
void HearingAid::AddFromStorage(const HearingDevice& dev_info,
- uint16_t is_acceptlisted) {
+ uint16_t is_white_listed) {
if (!instance) {
LOG(ERROR) << "Not initialized yet";
}
- instance->AddFromStorage(dev_info, is_acceptlisted);
+ instance->AddFromStorage(dev_info, is_white_listed);
};
int HearingAid::GetDeviceCount() {
diff --git a/bta/hearing_aid/hearing_aid_audio_source.cc b/bta/hearing_aid/hearing_aid_audio_source.cc
index 9ab4d13e1..0896e2bb3 100644
--- a/bta/hearing_aid/hearing_aid_audio_source.cc
+++ b/bta/hearing_aid/hearing_aid_audio_source.cc
@@ -16,46 +16,23 @@
*
******************************************************************************/
-#include <base/files/file_util.h>
-#include <cstdint>
-#include <memory>
-#include <sstream>
-#include <vector>
-
#include "audio_hal_interface/hearing_aid_software_encoding.h"
#include "audio_hearing_aid_hw/include/audio_hearing_aid_hw.h"
-#include "bta/include/bta_hearing_aid_api.h"
+#include "bta_hearing_aid_api.h"
+#include "btu.h"
+#include "osi/include/wakelock.h"
+#include "uipc.h"
+
+#include <base/files/file_util.h>
+#include <include/hardware/bt_av.h>
+
#include "common/repeating_timer.h"
#include "common/time_util.h"
-#include "osi/include/wakelock.h"
-#include "stack/include/btu.h" // get_main_thread
-#include "udrv/include/uipc.h"
using base::FilePath;
+extern const char* audio_ha_hw_dump_ctrl_event(tHEARING_AID_CTRL_CMD event);
namespace {
-#define CASE_RETURN_STR(const) \
- case const: \
- return #const;
-
-const char* audio_ha_hw_dump_ctrl_event(tHEARING_AID_CTRL_CMD event) {
- switch (event) {
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_NONE)
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_CHECK_READY)
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_START)
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_STOP)
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_SUSPEND)
- CASE_RETURN_STR(HEARING_AID_CTRL_GET_INPUT_AUDIO_CONFIG)
- CASE_RETURN_STR(HEARING_AID_CTRL_GET_OUTPUT_AUDIO_CONFIG)
- CASE_RETURN_STR(HEARING_AID_CTRL_SET_OUTPUT_AUDIO_CONFIG)
- CASE_RETURN_STR(HEARING_AID_CTRL_CMD_OFFLOAD_START)
- default:
- break;
- }
-
- return "UNKNOWN HEARING_AID_CTRL_CMD";
-}
-
int bit_rate = -1;
int sample_rate = -1;
int data_interval_ms = -1;
diff --git a/bta/hf_client/bta_hf_client_act.cc b/bta/hf_client/bta_hf_client_act.cc
index 66252c4f0..e3f25f61c 100644
--- a/bta/hf_client/bta_hf_client_act.cc
+++ b/bta/hf_client/bta_hf_client_act.cc
@@ -23,13 +23,18 @@
*
******************************************************************************/
-#include "bt_trace.h" // Legacy trace logging
-
-#include "bta/hf_client/bta_hf_client_int.h"
-#include "bta/include/bta_dm_api.h"
-#include "stack/include/l2c_api.h"
-#include "stack/include/port_api.h"
-#include "types/raw_address.h"
+#include <string.h>
+#include "bt_utils.h"
+#include "bta_api.h"
+#include "bta_dm_api.h"
+#include "bta_hf_client_api.h"
+#include "bta_hf_client_int.h"
+#include "bta_sys.h"
+#include "l2c_api.h"
+#include "osi/include/compat.h"
+#include "osi/include/osi.h"
+#include "port_api.h"
+#include "utl.h"
/*****************************************************************************
* Constants
@@ -94,6 +99,7 @@ void bta_hf_client_start_open(tBTA_HF_CLIENT_DATA* p_data) {
/* store parameters */
if (p_data) {
client_cb->peer_addr = p_data->api_open.bd_addr;
+ client_cb->cli_sec_mask = p_data->api_open.sec_mask;
}
/* Check if RFCOMM has any incoming connection to avoid collision. */
@@ -102,8 +108,7 @@ void bta_hf_client_start_open(tBTA_HF_CLIENT_DATA* p_data) {
/* Let the incoming connection goes through. */
/* Issue collision for now. */
/* We will decide what to do when we find incoming connection later.*/
- bta_hf_client_collision_cback(BTA_SYS_CONN_OPEN, BTA_ID_HS, 0,
- client_cb->peer_addr);
+ bta_hf_client_collision_cback(0, BTA_ID_HS, 0, client_cb->peer_addr);
return;
}
diff --git a/bta/hf_client/bta_hf_client_api.cc b/bta/hf_client/bta_hf_client_api.cc
index 53083655b..38c5594c8 100644
--- a/bta/hf_client/bta_hf_client_api.cc
+++ b/bta/hf_client/bta_hf_client_api.cc
@@ -24,17 +24,11 @@
*
******************************************************************************/
-#include <cstdint>
+#include <string.h>
-#include "bt_trace.h" // Legacy trace logging
-
-#include "bta/hf_client/bta_hf_client_int.h"
-#include "bta/include/bta_hf_client_api.h"
-#include "bta/sys/bta_sys.h"
-#include "osi/include/allocator.h"
+#include "bta_hf_client_api.h"
+#include "bta_hf_client_int.h"
#include "osi/include/compat.h"
-#include "stack/include/bt_types.h"
-#include "types/raw_address.h"
/*****************************************************************************
* External Function Declarations
@@ -55,10 +49,10 @@
* Returns BTA_SUCCESS if OK, BTA_FAILURE otherwise.
*
******************************************************************************/
-tBTA_STATUS BTA_HfClientEnable(tBTA_HF_CLIENT_CBACK* p_cback,
+tBTA_STATUS BTA_HfClientEnable(tBTA_HF_CLIENT_CBACK* p_cback, tBTA_SEC sec_mask,
tBTA_HF_CLIENT_FEAT features,
const char* p_service_name) {
- return bta_hf_client_api_enable(p_cback, features, p_service_name);
+ return bta_hf_client_api_enable(p_cback, sec_mask, features, p_service_name);
}
/*******************************************************************************
@@ -82,7 +76,8 @@ void BTA_HfClientDisable(void) { bta_hf_client_api_disable(); }
* Returns void
*
******************************************************************************/
-void BTA_HfClientOpen(const RawAddress& bd_addr, uint16_t* p_handle) {
+void BTA_HfClientOpen(const RawAddress& bd_addr, tBTA_SEC sec_mask,
+ uint16_t* p_handle) {
APPL_TRACE_DEBUG("%s", __func__);
tBTA_HF_CLIENT_API_OPEN* p_buf =
(tBTA_HF_CLIENT_API_OPEN*)osi_malloc(sizeof(tBTA_HF_CLIENT_API_OPEN));
@@ -95,6 +90,7 @@ void BTA_HfClientOpen(const RawAddress& bd_addr, uint16_t* p_handle) {
p_buf->hdr.event = BTA_HF_CLIENT_API_OPEN_EVT;
p_buf->hdr.layer_specific = *p_handle;
p_buf->bd_addr = bd_addr;
+ p_buf->sec_mask = sec_mask;
bta_sys_sendmsg(p_buf);
}
@@ -111,7 +107,7 @@ void BTA_HfClientOpen(const RawAddress& bd_addr, uint16_t* p_handle) {
*
******************************************************************************/
void BTA_HfClientClose(uint16_t handle) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_HF_CLIENT_API_CLOSE_EVT;
p_buf->layer_specific = handle;
@@ -131,7 +127,7 @@ void BTA_HfClientClose(uint16_t handle) {
*
******************************************************************************/
void BTA_HfClientAudioOpen(uint16_t handle) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_HF_CLIENT_API_AUDIO_OPEN_EVT;
p_buf->layer_specific = handle;
@@ -151,7 +147,7 @@ void BTA_HfClientAudioOpen(uint16_t handle) {
*
******************************************************************************/
void BTA_HfClientAudioClose(uint16_t handle) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_HF_CLIENT_API_AUDIO_CLOSE_EVT;
p_buf->layer_specific = handle;
diff --git a/bta/hf_client/bta_hf_client_at.cc b/bta/hf_client/bta_hf_client_at.cc
index 721bbbcf7..6e4fe2696 100644
--- a/bta/hf_client/bta_hf_client_at.cc
+++ b/bta/hf_client/bta_hf_client_at.cc
@@ -19,13 +19,15 @@
#define LOG_TAG "bt_hf_client"
-#include "bt_trace.h" // Legacy trace logging
+#include <errno.h>
+#include <stdio.h>
+#include <string.h>
-#include "bta/hf_client/bta_hf_client_int.h"
-#include "osi/include/allocator.h"
-#include "osi/include/compat.h"
+#include "bta_hf_client_api.h"
+#include "bta_hf_client_int.h"
#include "osi/include/log.h"
-#include "stack/include/port_api.h"
+#include "osi/include/osi.h"
+#include "port_api.h"
/* Uncomment to enable AT traffic dumping */
/* #define BTA_HF_CLIENT_AT_DUMP 1 */
@@ -52,10 +54,6 @@
#define BTA_HF_CLIENT_INDICATOR_CALLSETUP "callsetup"
#define BTA_HF_CLIENT_INDICATOR_CALLHELD "callheld"
-/* BIND parse mode */
-#define BTA_HF_CLIENT_BIND_PARSE_READ_ENABLED_IND 0
-#define BTA_HF_CLIENT_BIND_PARSE_READ_SUPPOETED_IND 1
-
#define MIN(a, b) \
({ \
__typeof__(a) _a = (a); \
@@ -145,13 +143,14 @@ static void bta_hf_client_queue_at(tBTA_HF_CLIENT_CB* client_cb,
static void bta_hf_client_at_resp_timer_cback(void* data) {
tBTA_HF_CLIENT_CB* client_cb = (tBTA_HF_CLIENT_CB*)data;
if (client_cb->at_cb.current_cmd == BTA_HF_CLIENT_AT_CNUM) {
- LOG_INFO("%s: timed out waiting for AT+CNUM response; spoofing OK.",
+ LOG_INFO(LOG_TAG,
+ "%s: timed out waiting for AT+CNUM response; spoofing OK.",
__func__);
bta_hf_client_handle_ok(client_cb);
} else {
APPL_TRACE_ERROR("HFPClient: AT response timeout, disconnecting");
- tBTA_HF_CLIENT_DATA msg = {};
+ tBTA_HF_CLIENT_DATA msg;
msg.hdr.layer_specific = client_cb->handle;
bta_hf_client_sm_execute(BTA_HF_CLIENT_API_CLOSE_EVT, &msg);
}
@@ -395,24 +394,6 @@ static void bta_hf_client_handle_chld(tBTA_HF_CLIENT_CB* client_cb,
client_cb->chld_features |= mask;
}
-static void bta_hf_client_handle_bind_read_supported_ind(
- tBTA_HF_CLIENT_CB* client_cb, int indicator_id) {
- APPL_TRACE_DEBUG("%s: %d", __func__, indicator_id);
-
- client_cb->peer_hf_indicators.insert(indicator_id);
-}
-
-static void bta_hf_client_handle_bind_read_enabled_ind(
- tBTA_HF_CLIENT_CB* client_cb, int indicator_id, bool enable) {
- APPL_TRACE_DEBUG("%s: %d", __func__, indicator_id);
-
- if (enable) {
- client_cb->enabled_hf_indicators.insert(indicator_id);
- } else {
- client_cb->enabled_hf_indicators.erase(indicator_id);
- }
-}
-
static void bta_hf_client_handle_ciev(tBTA_HF_CLIENT_CB* client_cb,
uint32_t index, uint32_t value) {
int8_t realind = -1;
@@ -1005,46 +986,6 @@ static char* bta_hf_client_parse_chld(tBTA_HF_CLIENT_CB* client_cb,
return buffer;
}
-static char* bta_hf_client_parse_bind(tBTA_HF_CLIENT_CB* client_cb,
- char* buffer) {
- AT_CHECK_EVENT(buffer, "+BIND:");
-
- uint8_t mode = BTA_HF_CLIENT_BIND_PARSE_READ_ENABLED_IND;
-
- int idx = -1;
-
- while (*buffer != 0) {
- switch (*buffer) {
- case '(':
- mode = BTA_HF_CLIENT_BIND_PARSE_READ_SUPPOETED_IND;
- break;
- case ')':
- break;
- case '0':
- case '1':
- case '2':
- if (mode == BTA_HF_CLIENT_BIND_PARSE_READ_SUPPOETED_IND) {
- // +BIND: (id0, id1, ...)
- bta_hf_client_handle_bind_read_supported_ind(client_cb,
- (*buffer - '0'));
- } else if (idx == -1) {
- // +BIND: [id]...
- idx = *buffer - '0';
- } else {
- // +BIND: ...[status]
- bta_hf_client_handle_bind_read_enabled_ind(client_cb, idx,
- *buffer - '0');
- }
- break;
- default:
- break;
- }
- buffer++;
- }
-
- return buffer;
-}
-
static char* bta_hf_client_parse_ciev(tBTA_HF_CLIENT_CB* client_cb,
char* buffer) {
uint32_t index, value;
@@ -1470,13 +1411,12 @@ static char* bta_hf_client_parse_no_answer(tBTA_HF_CLIENT_CB* client_cb,
return buffer;
}
-static char* bta_hf_client_parse_rejectlisted(tBTA_HF_CLIENT_CB* client_cb,
- char* buffer) {
- AT_CHECK_EVENT(buffer, "REJECTLISTED");
+static char* bta_hf_client_parse_blacklisted(tBTA_HF_CLIENT_CB* client_cb,
+ char* buffer) {
+ AT_CHECK_EVENT(buffer, "BLACKLISTED");
AT_CHECK_RN(buffer);
- bta_hf_client_handle_error(client_cb, BTA_HF_CLIENT_AT_RESULT_REJECTLISTED,
- 0);
+ bta_hf_client_handle_error(client_cb, BTA_HF_CLIENT_AT_RESULT_BLACKLISTED, 0);
return buffer;
}
@@ -1548,21 +1488,20 @@ static char* bta_hf_client_process_unknown(tBTA_HF_CLIENT_CB* client_cb,
typedef char* (*tBTA_HF_CLIENT_PARSER_CALLBACK)(tBTA_HF_CLIENT_CB*, char*);
static const tBTA_HF_CLIENT_PARSER_CALLBACK bta_hf_client_parser_cb[] = {
- bta_hf_client_parse_ok, bta_hf_client_parse_error,
- bta_hf_client_parse_ring, bta_hf_client_parse_brsf,
- bta_hf_client_parse_cind, bta_hf_client_parse_ciev,
- bta_hf_client_parse_chld, bta_hf_client_parse_bcs,
- bta_hf_client_parse_bsir, bta_hf_client_parse_cmeerror,
- bta_hf_client_parse_vgm, bta_hf_client_parse_vgme,
- bta_hf_client_parse_vgs, bta_hf_client_parse_vgse,
- bta_hf_client_parse_bvra, bta_hf_client_parse_clip,
- bta_hf_client_parse_ccwa, bta_hf_client_parse_cops,
- bta_hf_client_parse_binp, bta_hf_client_parse_clcc,
- bta_hf_client_parse_cnum, bta_hf_client_parse_btrh,
- bta_hf_client_parse_bind, bta_hf_client_parse_busy,
- bta_hf_client_parse_delayed, bta_hf_client_parse_no_carrier,
- bta_hf_client_parse_no_answer, bta_hf_client_parse_rejectlisted,
- bta_hf_client_process_unknown};
+ bta_hf_client_parse_ok, bta_hf_client_parse_error,
+ bta_hf_client_parse_ring, bta_hf_client_parse_brsf,
+ bta_hf_client_parse_cind, bta_hf_client_parse_ciev,
+ bta_hf_client_parse_chld, bta_hf_client_parse_bcs,
+ bta_hf_client_parse_bsir, bta_hf_client_parse_cmeerror,
+ bta_hf_client_parse_vgm, bta_hf_client_parse_vgme,
+ bta_hf_client_parse_vgs, bta_hf_client_parse_vgse,
+ bta_hf_client_parse_bvra, bta_hf_client_parse_clip,
+ bta_hf_client_parse_ccwa, bta_hf_client_parse_cops,
+ bta_hf_client_parse_binp, bta_hf_client_parse_clcc,
+ bta_hf_client_parse_cnum, bta_hf_client_parse_btrh,
+ bta_hf_client_parse_busy, bta_hf_client_parse_delayed,
+ bta_hf_client_parse_no_carrier, bta_hf_client_parse_no_answer,
+ bta_hf_client_parse_blacklisted, bta_hf_client_process_unknown};
/* calculate supported event list length */
static const uint16_t bta_hf_client_parser_cb_count =
@@ -1631,7 +1570,7 @@ static void bta_hf_client_at_parse_start(tBTA_HF_CLIENT_CB* client_cb) {
"HFPCient: could not skip unknown AT event, disconnecting");
bta_hf_client_at_reset(client_cb);
- tBTA_HF_CLIENT_DATA msg = {};
+ tBTA_HF_CLIENT_DATA msg;
msg.hdr.layer_specific = client_cb->handle;
bta_hf_client_sm_execute(BTA_HF_CLIENT_API_CLOSE_EVT, &msg);
return;
@@ -1694,7 +1633,7 @@ void bta_hf_client_at_parse(tBTA_HF_CLIENT_CB* client_cb, char* buf,
bta_hf_client_at_reset(client_cb);
- tBTA_HF_CLIENT_DATA msg = {};
+ tBTA_HF_CLIENT_DATA msg;
msg.hdr.layer_specific = client_cb->handle;
bta_hf_client_sm_execute(BTA_HF_CLIENT_API_CLOSE_EVT, &msg);
return;
@@ -1818,54 +1757,6 @@ void bta_hf_client_send_at_chld(tBTA_HF_CLIENT_CB* client_cb, char cmd,
bta_hf_client_send_at(client_cb, BTA_HF_CLIENT_AT_CHLD, buf, at_len);
}
-void bta_hf_client_send_at_bind(tBTA_HF_CLIENT_CB* client_cb, int step) {
- std::string buf;
- tBTA_HF_CLIENT_AT_CMD cmd = BTA_HF_CLIENT_AT_BIND_SET_IND;
-
- APPL_TRACE_DEBUG("%s", __func__);
-
- switch (step) {
- case 0: // List HF supported indicators
- // TODO: Add flags to determine enabled HF features
- buf = "AT+BIND=1,2\r";
- cmd = BTA_HF_CLIENT_AT_BIND_SET_IND;
- break;
- case 1: // Read AG supported indicators
- buf = "AT+BIND=?\r";
- cmd = BTA_HF_CLIENT_AT_BIND_READ_SUPPORTED_IND;
- break;
- case 2: // Read AG enabled/disabled status of indicators
- buf = "AT+BIND?\r";
- cmd = BTA_HF_CLIENT_AT_BIND_READ_ENABLED_IND;
- break;
- default:
- break;
- }
- bta_hf_client_send_at(client_cb, cmd, buf.c_str(), buf.size());
-}
-
-void bta_hf_client_send_at_biev(tBTA_HF_CLIENT_CB* client_cb, int indicator_id,
- int indicator_value) {
- char buf[32];
- tBTA_HF_CLIENT_AT_CMD cmd = BTA_HF_CLIENT_AT_BIEV;
-
- if ((client_cb->peer_features & BTA_HF_CLIENT_FEAT_HF_IND) == 0) {
- APPL_TRACE_ERROR("%s peer does not support HF Indicators", __func__);
- return;
- }
-
- if (client_cb->enabled_hf_indicators.count(indicator_id) <= 0) {
- APPL_TRACE_ERROR("%s HF indicators %d is disabled", __func__, indicator_id);
- return;
- }
-
- APPL_TRACE_DEBUG("%s", __func__);
-
- int len = sprintf(buf, "AT+BIEV=%d,%d\r", indicator_id, indicator_value);
-
- bta_hf_client_send_at(client_cb, cmd, buf, len);
-}
-
void bta_hf_client_send_at_clip(tBTA_HF_CLIENT_CB* client_cb, bool activate) {
const char* buf;
@@ -2218,11 +2109,6 @@ void bta_hf_client_send_at_cmd(tBTA_HF_CLIENT_DATA* p_data) {
bta_hf_client_send_at_chld(client_cb, '0' + p_val->uint32_val1,
p_val->uint32_val2);
break;
- case BTA_HF_CLIENT_AT_CMD_BIEV:
- /* expects ascii code for command */
- bta_hf_client_send_at_biev(client_cb, p_val->uint32_val1,
- p_val->uint32_val2);
- break;
case BTA_HF_CLIENT_AT_CMD_BCC:
bta_hf_client_send_at_bcc(client_cb);
break;
diff --git a/bta/hf_client/bta_hf_client_at.h b/bta/hf_client/bta_hf_client_at.h
index 11a0d0b0d..132817536 100644
--- a/bta/hf_client/bta_hf_client_at.h
+++ b/bta/hf_client/bta_hf_client_at.h
@@ -21,9 +21,6 @@
* Data types
****************************************************************************/
-#include <cstdint>
-#include "osi/include/alarm.h"
-
/* ASCII character string of arguments to the AT command */
#define BTA_HF_CLIENT_AT_MAX_LEN 512
diff --git a/bta/hf_client/bta_hf_client_int.h b/bta/hf_client/bta_hf_client_int.h
index 8354eadb5..4cd16fa5e 100755
--- a/bta/hf_client/bta_hf_client_int.h
+++ b/bta/hf_client/bta_hf_client_int.h
@@ -17,19 +17,18 @@
*
******************************************************************************/
-#include <cstdint>
-#include <unordered_set>
-
-#include "bta/hf_client/bta_hf_client_at.h"
-#include "bta/include/bta_hf_client_api.h"
-#include "bta/sys/bta_sys.h"
-#include "osi/include/alarm.h"
-#include "stack/include/bt_types.h"
-#include "types/raw_address.h"
+#include "bta_api.h"
+#include "bta_hf_client_api.h"
+#include "bta_hf_client_at.h"
+#include "bta_sys.h"
/*****************************************************************************
* Constants
****************************************************************************/
+#define HFP_VERSION_1_1 0x0101
+#define HFP_VERSION_1_5 0x0105
+#define HFP_VERSION_1_6 0x0106
+#define HFP_VERSION_1_7 0x0107
/* RFCOMM MTU SIZE */
#define BTA_HF_CLIENT_MTU 256
@@ -99,10 +98,6 @@ enum {
BTA_HF_CLIENT_AT_CNUM,
BTA_HF_CLIENT_AT_NREC,
BTA_HF_CLIENT_AT_BINP,
- BTA_HF_CLIENT_AT_BIND_SET_IND,
- BTA_HF_CLIENT_AT_BIND_READ_SUPPORTED_IND,
- BTA_HF_CLIENT_AT_BIND_READ_ENABLED_IND,
- BTA_HF_CLIENT_AT_BIEV,
BTA_HF_CLIENT_AT_VENDOR_SPECIFIC,
};
@@ -111,26 +106,27 @@ enum {
****************************************************************************/
/* data type for BTA_HF_CLIENT_API_OPEN_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress bd_addr;
uint16_t* handle;
+ tBTA_SEC sec_mask;
} tBTA_HF_CLIENT_API_OPEN;
/* data type for BTA_HF_CLIENT_DISC_RESULT_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint16_t status;
} tBTA_HF_CLIENT_DISC_RESULT;
/* data type for RFCOMM events */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint16_t port_handle;
} tBTA_HF_CLIENT_RFC;
/* generic purpose data type for other events */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
bool bool_val;
uint8_t uint8_val;
uint32_t uint32_val1;
@@ -140,7 +136,7 @@ typedef struct {
/* union of all event datatypes */
typedef union {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_HF_CLIENT_API_OPEN api_open;
tBTA_HF_CLIENT_DISC_RESULT disc_result;
tBTA_HF_CLIENT_RFC rfc;
@@ -171,6 +167,7 @@ typedef struct {
RawAddress peer_addr; /* peer bd address */
tSDP_DISCOVERY_DB* p_disc_db; /* pointer to discovery database */
uint16_t conn_handle; /* RFCOMM handle of connected service */
+ tBTA_SEC cli_sec_mask; /* client security mask */
tBTA_HF_CLIENT_PEER_FEAT peer_features; /* peer device features */
tBTA_HF_CLIENT_CHLD_FEAT chld_features; /* call handling features */
uint16_t peer_version; /* profile version of peer device */
@@ -182,14 +179,10 @@ typedef struct {
tBTM_SCO_CODEC_TYPE negotiated_codec; /* negotiated codec */
bool svc_conn; /* set to true when service level connection is up */
bool send_at_reply; /* set to true to notify framework about AT results */
- tBTA_HF_CLIENT_AT_CB at_cb; /* AT Parser control block */
- uint8_t state; /* state machine state */
- bool is_allocated; /* if the control block is already allocated */
- alarm_t* collision_timer; /* Collision timer */
- std::unordered_set<int>
- peer_hf_indicators; /* peer supported hf indicator indices (HFP1.7) */
- std::unordered_set<int>
- enabled_hf_indicators; /* enabled hf indicator indices (HFP1.7) */
+ tBTA_HF_CLIENT_AT_CB at_cb; /* AT Parser control block */
+ uint8_t state; /* state machine state */
+ bool is_allocated; /* if the control block is already allocated */
+ alarm_t* collision_timer; /* Collision timer */
} tBTA_HF_CLIENT_CB;
typedef struct {
@@ -198,6 +191,7 @@ typedef struct {
uint8_t scn;
tBTA_HF_CLIENT_CBACK* p_cback; /* application callback */
tBTA_HF_CLIENT_FEAT features; /* features registered by application */
+ tBTA_SEC serv_sec_mask; /* server security mask */
uint16_t serv_handle; /* RFCOMM server handle */
bool deregister; /* true if service shutting down */
@@ -217,7 +211,7 @@ extern tBTA_HF_CLIENT_CB* bta_hf_client_find_cb_by_bda(
const RawAddress& bd_addr);
extern tBTA_HF_CLIENT_CB* bta_hf_client_find_cb_by_rfc_handle(uint16_t handle);
extern tBTA_HF_CLIENT_CB* bta_hf_client_find_cb_by_sco_handle(uint16_t handle);
-extern bool bta_hf_client_hdl_event(BT_HDR_RIGID* p_msg);
+extern bool bta_hf_client_hdl_event(BT_HDR* p_msg);
extern void bta_hf_client_sm_execute(uint16_t event,
tBTA_HF_CLIENT_DATA* p_data);
extern void bta_hf_client_slc_seq(tBTA_HF_CLIENT_CB* client_cb, bool error);
@@ -229,6 +223,7 @@ extern void bta_hf_client_collision_cback(tBTA_SYS_CONN_STATUS status,
const RawAddress& peer_addr);
extern void bta_hf_client_resume_open(tBTA_HF_CLIENT_CB* client_cb);
extern tBTA_STATUS bta_hf_client_api_enable(tBTA_HF_CLIENT_CBACK* p_cback,
+ tBTA_SEC sec_mask,
tBTA_HF_CLIENT_FEAT features,
const char* p_service_name);
@@ -276,9 +271,6 @@ extern void bta_hf_client_send_at_cmer(tBTA_HF_CLIENT_CB* client_cb,
bool activate);
extern void bta_hf_client_send_at_chld(tBTA_HF_CLIENT_CB* client_cb, char cmd,
uint32_t idx);
-extern void bta_hf_client_send_at_bind(tBTA_HF_CLIENT_CB* client_cb, int step);
-extern void bta_hf_client_send_at_biev(tBTA_HF_CLIENT_CB* client_cb, int ind_id,
- int value);
extern void bta_hf_client_send_at_clip(tBTA_HF_CLIENT_CB* client_cb,
bool activate);
extern void bta_hf_client_send_at_ccwa(tBTA_HF_CLIENT_CB* client_cb,
diff --git a/bta/hf_client/bta_hf_client_main.cc b/bta/hf_client/bta_hf_client_main.cc
index 902af1323..fac61c78a 100644
--- a/bta/hf_client/bta_hf_client_main.cc
+++ b/bta/hf_client/bta_hf_client_main.cc
@@ -17,14 +17,19 @@
*
******************************************************************************/
-#include <cstdint>
-#include <cstdio>
-
-#include "bta/hf_client/bta_hf_client_int.h"
-#include "bta/include/utl.h"
-#include "osi/include/allocator.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/include/btm_api.h"
+#include <base/logging.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "bt_utils.h"
+#include "bta_api.h"
+#include "bta_hf_client_api.h"
+#include "bta_hf_client_int.h"
+#include "bta_sys.h"
+#include "osi/include/osi.h"
+#include "osi/include/properties.h"
+#include "utl.h"
static const char* bta_hf_client_evt_str(uint16_t event);
static const char* bta_hf_client_state_str(uint8_t state);
@@ -297,13 +302,8 @@ void bta_hf_client_cb_init(tBTA_HF_CLIENT_CB* client_cb, uint16_t handle) {
// Free any memory we need to explicity release
alarm_free(client_cb->collision_timer);
- // release unique pointers
- client_cb->enabled_hf_indicators.clear();
- client_cb->peer_hf_indicators.clear();
-
// Memset the rest of the block
- // memset(client_cb, 0, sizeof(tBTA_HF_CLIENT_CB));
- *client_cb = {};
+ memset(client_cb, 0, sizeof(tBTA_HF_CLIENT_CB));
// Re allocate any variables required
client_cb->collision_timer = alarm_new("bta_hf_client.scb_collision_timer");
@@ -330,6 +330,7 @@ void bta_hf_client_resume_open(tBTA_HF_CLIENT_CB* client_cb) {
tBTA_HF_CLIENT_DATA msg;
msg.hdr.layer_specific = client_cb->handle;
msg.api_open.bd_addr = client_cb->peer_addr;
+ msg.api_open.sec_mask = client_cb->cli_sec_mask;
bta_hf_client_start_open(&msg);
}
}
@@ -407,6 +408,7 @@ void bta_hf_client_collision_cback(UNUSED_ATTR tBTA_SYS_CONN_STATUS status,
*
******************************************************************************/
tBTA_STATUS bta_hf_client_api_enable(tBTA_HF_CLIENT_CBACK* p_cback,
+ tBTA_SEC sec_mask,
tBTA_HF_CLIENT_FEAT features,
const char* p_service_name) {
/* If already registered then return error */
@@ -422,6 +424,7 @@ tBTA_STATUS bta_hf_client_api_enable(tBTA_HF_CLIENT_CBACK* p_cback,
bta_hf_client_cb_arr_init();
bta_hf_client_cb_arr.p_cback = p_cback;
+ bta_hf_client_cb_arr.serv_sec_mask = sec_mask;
bta_hf_client_cb_arr.features = features;
/* create SDP records */
@@ -675,7 +678,7 @@ void bta_hf_client_api_disable() {
* Returns bool
*
******************************************************************************/
-bool bta_hf_client_hdl_event(BT_HDR_RIGID* p_msg) {
+bool bta_hf_client_hdl_event(BT_HDR* p_msg) {
APPL_TRACE_DEBUG("%s: %s (0x%x)", __func__,
bta_hf_client_evt_str(p_msg->event), p_msg->event);
bta_hf_client_sm_execute(p_msg->event, (tBTA_HF_CLIENT_DATA*)p_msg);
@@ -839,9 +842,6 @@ void bta_hf_client_slc_seq(tBTA_HF_CLIENT_CB* client_cb, bool error) {
if (client_cb->peer_features & BTA_HF_CLIENT_PEER_FEAT_3WAY &&
bta_hf_client_cb_arr.features & BTA_HF_CLIENT_FEAT_3WAY) {
bta_hf_client_send_at_chld(client_cb, '?', 0);
- } else if (bta_hf_client_cb_arr.features & BTA_HF_CLIENT_FEAT_HF_IND &&
- client_cb->peer_features & BTA_HF_CLIENT_PEER_HF_IND) {
- bta_hf_client_send_at_bind(client_cb, 0);
} else {
tBTA_HF_CLIENT_DATA msg;
msg.hdr.layer_specific = client_cb->handle;
@@ -850,32 +850,13 @@ void bta_hf_client_slc_seq(tBTA_HF_CLIENT_CB* client_cb, bool error) {
}
break;
- case BTA_HF_CLIENT_AT_CHLD:
- if (bta_hf_client_cb_arr.features & BTA_HF_CLIENT_FEAT_HF_IND &&
- client_cb->peer_features & BTA_HF_CLIENT_PEER_HF_IND) {
- bta_hf_client_send_at_bind(client_cb, 0);
- } else {
- tBTA_HF_CLIENT_DATA msg;
- msg.hdr.layer_specific = client_cb->handle;
- bta_hf_client_svc_conn_open(&msg);
- send_post_slc_cmd(client_cb);
- }
- break;
-
- case BTA_HF_CLIENT_AT_BIND_SET_IND:
- bta_hf_client_send_at_bind(client_cb, 1);
- break;
-
- case BTA_HF_CLIENT_AT_BIND_READ_SUPPORTED_IND:
- bta_hf_client_send_at_bind(client_cb, 2);
- break;
-
- case BTA_HF_CLIENT_AT_BIND_READ_ENABLED_IND:
+ case BTA_HF_CLIENT_AT_CHLD: {
tBTA_HF_CLIENT_DATA msg;
msg.hdr.layer_specific = client_cb->handle;
bta_hf_client_svc_conn_open(&msg);
send_post_slc_cmd(client_cb);
break;
+ }
default: {
/* If happen there is a bug in SLC creation procedure... */
diff --git a/bta/hf_client/bta_hf_client_rfc.cc b/bta/hf_client/bta_hf_client_rfc.cc
index 42c3d3ab8..535371f6b 100644
--- a/bta/hf_client/bta_hf_client_rfc.cc
+++ b/bta/hf_client/bta_hf_client_rfc.cc
@@ -24,13 +24,14 @@
*
******************************************************************************/
-#include <cstdint>
+#include <base/logging.h>
+#include <string.h>
-#include "bta/hf_client/bta_hf_client_int.h"
-#include "osi/include/allocator.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/include/port_api.h"
-#include "stack/include/sdp_api.h"
+#include "bt_utils.h"
+#include "bta_api.h"
+#include "bta_hf_client_int.h"
+#include "osi/include/osi.h"
+#include "port_api.h"
/*******************************************************************************
*
@@ -180,10 +181,14 @@ void bta_hf_client_start_server() {
return;
}
- port_status = RFCOMM_CreateConnectionWithSecurity(
+ BTM_SetSecurityLevel(false, "", BTM_SEC_SERVICE_HF_HANDSFREE,
+ bta_hf_client_cb_arr.serv_sec_mask, BT_PSM_RFCOMM,
+ BTM_SEC_PROTO_RFCOMM, bta_hf_client_cb_arr.scn);
+
+ port_status = RFCOMM_CreateConnection(
UUID_SERVCLASS_HF_HANDSFREE, bta_hf_client_cb_arr.scn, true,
BTA_HF_CLIENT_MTU, RawAddress::kAny, &(bta_hf_client_cb_arr.serv_handle),
- bta_hf_client_mgmt_cback, BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT);
+ bta_hf_client_mgmt_cback);
APPL_TRACE_DEBUG("%s: started rfcomm server with handle %d", __func__,
bta_hf_client_cb_arr.serv_handle);
@@ -237,11 +242,13 @@ void bta_hf_client_rfc_do_open(tBTA_HF_CLIENT_DATA* p_data) {
return;
}
- if (RFCOMM_CreateConnectionWithSecurity(
- UUID_SERVCLASS_HF_HANDSFREE, client_cb->peer_scn, false,
- BTA_HF_CLIENT_MTU, client_cb->peer_addr, &(client_cb->conn_handle),
- bta_hf_client_mgmt_cback,
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT) == PORT_SUCCESS) {
+ BTM_SetSecurityLevel(true, "", BTM_SEC_SERVICE_HF_HANDSFREE,
+ client_cb->cli_sec_mask, BT_PSM_RFCOMM,
+ BTM_SEC_PROTO_RFCOMM, client_cb->peer_scn);
+ if (RFCOMM_CreateConnection(UUID_SERVCLASS_HF_HANDSFREE, client_cb->peer_scn,
+ false, BTA_HF_CLIENT_MTU, client_cb->peer_addr,
+ &(client_cb->conn_handle),
+ bta_hf_client_mgmt_cback) == PORT_SUCCESS) {
bta_hf_client_setup_port(client_cb->conn_handle);
APPL_TRACE_DEBUG("bta_hf_client_rfc_do_open : conn_handle = %d",
client_cb->conn_handle);
diff --git a/bta/hf_client/bta_hf_client_sco.cc b/bta/hf_client/bta_hf_client_sco.cc
index ee906ec1d..956b6d61c 100644
--- a/bta/hf_client/bta_hf_client_sco.cc
+++ b/bta/hf_client/bta_hf_client_sco.cc
@@ -16,14 +16,14 @@
* limitations under the License.
*
******************************************************************************/
+#include <string.h>
-#include <cstdint>
-
-#include "bta/hf_client/bta_hf_client_int.h"
-#include "bta/include/bta_ag_api.h"
+#include "bt_trace.h"
+#include "bt_utils.h"
+#include "bta_ag_api.h"
+#include "bta_hf_client_int.h"
#include "device/include/esco_parameters.h"
-#include "osi/include/allocator.h"
-#include "stack/include/btm_api.h"
+#include "osi/include/osi.h"
#define BTA_HF_CLIENT_NO_EDR_ESCO \
(ESCO_PKT_TYPES_MASK_NO_2_EV3 | ESCO_PKT_TYPES_MASK_NO_3_EV3 | \
@@ -109,17 +109,14 @@ static void bta_hf_client_sco_conn_rsp(tBTA_HF_CLIENT_CB* client_cb,
if (client_cb->sco_state == BTA_HF_CLIENT_SCO_LISTEN_ST) {
if (p_data->link_type == BTM_LINK_TYPE_SCO) {
- // SCO
- resp = esco_parameters_for_codec(SCO_CODEC_CVSD_D1);
- } else if (client_cb->negotiated_codec == BTA_AG_CODEC_MSBC) {
- // eSCO mSBC
- resp = esco_parameters_for_codec(ESCO_CODEC_MSBC_T2);
- } else if (bta_hf_client_cb_arr.features & BTA_HF_CLIENT_FEAT_ESCO_S4) {
- // eSCO CVSD, HFP 1.7 requires S4
- resp = esco_parameters_for_codec(ESCO_CODEC_CVSD_S4);
+ resp = esco_parameters_for_codec(ESCO_CODEC_CVSD);
} else {
- // eSCO CVSD, S3 is preferred by default(before HFP 1.7)
- resp = esco_parameters_for_codec(ESCO_CODEC_CVSD_S3);
+ if (client_cb->negotiated_codec == BTA_AG_CODEC_MSBC) {
+ resp = esco_parameters_for_codec(ESCO_CODEC_MSBC_T2);
+ } else {
+ // default codec
+ resp = esco_parameters_for_codec(ESCO_CODEC_CVSD);
+ }
}
/* tell sys to stop av if any */
@@ -182,7 +179,7 @@ static void bta_hf_client_sco_conn_cback(uint16_t sco_idx) {
return;
}
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_HF_CLIENT_SCO_OPEN_EVT;
p_buf->layer_specific = client_cb->handle;
bta_sys_sendmsg(p_buf);
@@ -207,7 +204,7 @@ static void bta_hf_client_sco_disc_cback(uint16_t sco_idx) {
return;
}
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_HF_CLIENT_SCO_CLOSE_EVT;
p_buf->layer_specific = client_cb->handle;
bta_sys_sendmsg(p_buf);
@@ -236,19 +233,7 @@ static void bta_hf_client_sco_create(tBTA_HF_CLIENT_CB* client_cb,
return;
}
- // codec parameters
- enh_esco_params_t params;
- // Since HF device is not expected to receive AT+BAC send +BCS command,
- // codec support of the connected AG device will be unknown,
- // so HF device will always establish only CVSD connection.
- if ((bta_hf_client_cb_arr.features & BTA_HF_CLIENT_FEAT_ESCO_S4) &&
- (client_cb->peer_features & BTA_HF_CLIENT_PEER_ESCO_S4)) {
- // eSCO CVSD, HFP 1.7 requires S4
- params = esco_parameters_for_codec(ESCO_CODEC_CVSD_S4);
- } else {
- // eSCO CVSD, S3 is preferred by default(before HFP 1.7)
- params = esco_parameters_for_codec(ESCO_CODEC_CVSD_S3);
- }
+ enh_esco_params_t params = esco_parameters_for_codec(ESCO_CODEC_CVSD);
/* if initiating set current scb and peer bd addr */
if (is_orig) {
diff --git a/bta/hf_client/bta_hf_client_sdp.cc b/bta/hf_client/bta_hf_client_sdp.cc
index db3348179..359f7acc1 100755
--- a/bta/hf_client/bta_hf_client_sdp.cc
+++ b/bta/hf_client/bta_hf_client_sdp.cc
@@ -24,19 +24,16 @@
*
******************************************************************************/
-#include <cstdint>
-
-#include "bta/hf_client/bta_hf_client_int.h"
-#include "bta/include/bta_ag_api.h"
-#include "bta/include/bta_hf_client_api.h"
-#include "bta/sys/bta_sys.h"
-#include "osi/include/allocator.h"
+#include <string.h>
+#include <base/logging.h>
+
+#include "bt_utils.h"
+#include "bta_api.h"
+#include "bta_hf_client_api.h"
+#include "bta_hf_client_int.h"
+#include "bta_sys.h"
+#include "osi/include/osi.h"
#include "osi/include/properties.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/port_api.h"
-#include "stack/include/sdpdefs.h"
-#include "types/bluetooth/uuid.h"
using bluetooth::Uuid;
@@ -56,7 +53,7 @@ using bluetooth::Uuid;
* Returns void
*
******************************************************************************/
-static void bta_hf_client_sdp_cback(tSDP_STATUS status, void* data) {
+static void bta_hf_client_sdp_cback(uint16_t status, void* data) {
uint16_t event;
tBTA_HF_CLIENT_DISC_RESULT* p_buf = (tBTA_HF_CLIENT_DISC_RESULT*)osi_malloc(
sizeof(tBTA_HF_CLIENT_DISC_RESULT));
@@ -124,7 +121,11 @@ bool bta_hf_client_add_record(const char* p_service_name, uint8_t scn,
/* add profile descriptor list */
profile_uuid = UUID_SERVCLASS_HF_HANDSFREE;
- version = BTA_HFP_VERSION;
+ version = HFP_VERSION_1_6;
+
+ if (osi_property_get_bool("persist.bluetooth.hfpclient.sco_s4_supported",
+ false))
+ version = HFP_VERSION_1_7;
result &= SDP_AddProfileDescriptorList(sdp_handle, profile_uuid, version);
@@ -204,7 +205,7 @@ void bta_hf_client_del_record(tBTA_HF_CLIENT_CB_ARR* client_cb) {
SDP_DeleteRecord(client_cb->sdp_handle);
client_cb->sdp_handle = 0;
BTM_FreeSCN(client_cb->scn);
- RFCOMM_ClearSecurityRecord(client_cb->scn);
+ BTM_SecClrService(BTM_SEC_SERVICE_HF_HANDSFREE);
bta_sys_remove_uuid(UUID_SERVCLASS_HF_HANDSFREE);
}
}
diff --git a/bta/hh/bta_hh_act.cc b/bta/hh/bta_hh_act.cc
index bc092b68c..81163c755 100644
--- a/bta/hh/bta_hh_act.cc
+++ b/bta/hh/bta_hh_act.cc
@@ -22,36 +22,25 @@
*
******************************************************************************/
-#define LOG_TAG "bluetooth"
+#include "bt_target.h"
-// BTA_HH_INCLUDED
-#include "bt_target.h" // Must be first to define build configuration
#if (BTA_HH_INCLUDED == TRUE)
-#include <cstdint>
-#include <string>
+#include <log/log.h>
+#include <string.h>
-#include "bta/hh/bta_hh_int.h"
-#include "bta/include/bta_hh_api.h"
-#include "bta/include/bta_hh_co.h"
-#include "bta/sys/bta_sys.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/include/hiddefs.h"
-#include "stack/include/hidh_api.h"
-#include "types/raw_address.h"
+#include "bta_hh_co.h"
+#include "bta_hh_int.h"
+#include "bta_sys.h"
+#include "btm_api.h"
+#include "l2c_api.h"
+#include "osi/include/osi.h"
+#include "utl.h"
/*****************************************************************************
* Constants
****************************************************************************/
-namespace {
-
-constexpr char kBtmLogTag[] = "HIDH";
-
-}
-
/*****************************************************************************
* Local Function prototypes
****************************************************************************/
@@ -59,8 +48,10 @@ static void bta_hh_cback(uint8_t dev_handle, const RawAddress& addr,
uint8_t event, uint32_t data, BT_HDR* pdata);
static tBTA_HH_STATUS bta_hh_get_trans_status(uint32_t result);
+#if (BTA_HH_DEBUG == TRUE)
static const char* bta_hh_get_w4_event(uint16_t event);
static const char* bta_hh_hid_event_name(uint16_t event);
+#endif
/*****************************************************************************
* Action Functions
@@ -84,6 +75,8 @@ void bta_hh_api_enable(tBTA_HH_DATA* p_data) {
memset(&bta_hh_cb, 0, sizeof(tBTA_HH_CB));
+ HID_HostSetSecurityLevel("", p_data->api_enable.sec_mask);
+
/* Register with L2CAP */
if (HID_HostRegister(bta_hh_cback) == HID_SUCCESS) {
/* store parameters */
@@ -102,9 +95,11 @@ void bta_hh_api_enable(tBTA_HH_DATA* p_data) {
bta_hh_cb.cb_index[xx] = BTA_HH_IDX_INVALID;
}
+#if (BTA_HH_LE_INCLUDED == TRUE)
if (status == BTA_HH_OK) {
bta_hh_le_enable();
} else
+#endif
{
/* signal BTA call back event */
tBTA_HH bta_hh;
@@ -158,10 +153,10 @@ void bta_hh_api_disable(void) {
*
******************************************************************************/
void bta_hh_disc_cmpl(void) {
- LOG_DEBUG("Disconnect complete");
-
+#if (BTA_HH_LE_INCLUDED == TRUE)
HID_HostDeregister();
bta_hh_le_deregister();
+#else
tBTA_HH_STATUS status = BTA_HH_OK;
/* Deregister with lower layer */
@@ -189,10 +184,12 @@ static void bta_hh_sdp_cback(uint16_t result, uint16_t attr_mask,
/* make sure sdp succeeded and hh has not been disabled */
if ((result == SDP_SUCCESS) && (p_cb != NULL)) {
/* security is required for the connection, add attr_mask bit*/
- attr_mask |= HID_SEC_REQUIRED;
+ if (p_cb->sec_mask) attr_mask |= HID_SEC_REQUIRED;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_EVENT("%s: p_cb: %d result 0x%02x, attr_mask 0x%02x, handle %x",
__func__, p_cb, result, attr_mask, p_cb->hid_handle);
+#endif
/* check to see type of device is supported , and should not been added
* before */
@@ -247,12 +244,14 @@ static void bta_hh_sdp_cback(uint16_t result, uint16_t attr_mask,
* Returns void
*
******************************************************************************/
-static void bta_hh_di_sdp_cback(tSDP_RESULT result) {
+static void bta_hh_di_sdp_cback(uint16_t result) {
tBTA_HH_DEV_CB* p_cb = bta_hh_cb.p_cur;
tBTA_HH_STATUS status = BTA_HH_ERR_SDP;
tSDP_DI_GET_RECORD di_rec;
tHID_STATUS ret;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_EVENT("%s: p_cb: %d result 0x%02x", __func__, p_cb, result);
+#endif
/* if DI record does not exist on remote device, vendor_id in
* tBTA_HH_DEV_DSCP_INFO will be set to 0xffff and we will allow the
@@ -280,8 +279,10 @@ static void bta_hh_di_sdp_cback(tSDP_RESULT result) {
if (ret == HID_SUCCESS) {
status = BTA_HH_OK;
} else {
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("%s: HID_HostGetSDPRecord failed: Status 0x%2x",
__func__, ret);
+#endif
}
}
@@ -307,23 +308,27 @@ static void bta_hh_di_sdp_cback(tSDP_RESULT result) {
* Returns void
*
******************************************************************************/
-void bta_hh_start_sdp(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_start_sdp(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
tBTA_HH_STATUS status = BTA_HH_ERR_SDP;
uint8_t hdl;
+ p_cb->sec_mask = p_data->api_conn.sec_mask;
p_cb->mode = p_data->api_conn.mode;
bta_hh_cb.p_cur = p_cb;
- if (BTM_UseLeLink(p_data->api_conn.bd_addr)) {
- p_cb->is_le_device = true;
+#if (BTA_HH_LE_INCLUDED == TRUE)
+ if (bta_hh_is_le_device(p_cb, p_data->api_conn.bd_addr)) {
bta_hh_le_open_conn(p_cb, p_data->api_conn.bd_addr);
return;
}
+#endif
/* if previously virtually cabled device, skip SDP */
if (p_cb->app_id) {
status = BTA_HH_OK;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("%s: skip SDP for known devices", __func__);
+#endif
if (p_cb->hid_handle == BTA_HH_INVALID_HANDLE) {
if (HID_HostAddDev(p_cb->addr, p_cb->attr_mask, &hdl) == HID_SUCCESS) {
/* update device CB with newly register device handle */
@@ -351,8 +356,10 @@ void bta_hh_start_sdp(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
if (SDP_DiDiscover(p_data->api_conn.bd_addr, bta_hh_cb.p_disc_db,
p_bta_hh_cfg->sdp_db_size,
bta_hh_di_sdp_cback) != SDP_SUCCESS) {
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("%s: SDP_DiDiscover failed: Status 0x%2X", __func__,
status);
+#endif
status = BTA_HH_ERR_SDP;
osi_free_and_reset((void**)&bta_hh_cb.p_disc_db);
} else {
@@ -389,13 +396,13 @@ void bta_hh_start_sdp(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
* Returns void
*
******************************************************************************/
-void bta_hh_sdp_cmpl(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
- CHECK(p_data != nullptr);
-
+void bta_hh_sdp_cmpl(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
tBTA_HH_CONN conn_dat;
tBTA_HH_STATUS status = p_data->status;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("%s: status 0x%2X", __func__, p_data->status);
+#endif
/* initialize call back data */
memset((void*)&conn_dat, 0, sizeof(tBTA_HH_CONN));
@@ -407,6 +414,8 @@ void bta_hh_sdp_cmpl(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
/* not incoming connection doing SDP, initiate a HID connection */
if (!p_cb->incoming_conn) {
tHID_STATUS ret;
+ /* set security level */
+ HID_HostSetSecurityLevel("", p_cb->sec_mask);
/* open HID connection */
ret = HID_HostOpenDev(p_cb->hid_handle);
@@ -420,8 +429,10 @@ void bta_hh_sdp_cmpl(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
APPL_TRACE_DEBUG("%s: connection already in progress", __func__);
return;
} else {
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("%s: HID_HostOpenDev failed: Status 0x%2X", __func__,
ret);
+#endif
/* open fail, remove device from management device list */
HID_HostRemoveDev(p_cb->hid_handle);
status = BTA_HH_ERR;
@@ -455,7 +466,9 @@ void bta_hh_sdp_cmpl(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
/* clean up device control block */
bta_hh_clean_up_kdev(p_cb);
}
+#if (BTA_HH_DEBUG == TRUE)
bta_hh_trace_dev_db();
+#endif
}
p_cb->incoming_conn = false;
p_cb->incoming_hid_handle = BTA_HH_INVALID_HANDLE;
@@ -472,37 +485,32 @@ void bta_hh_sdp_cmpl(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
* Returns void
*
******************************************************************************/
-extern void btif_hh_remove_device(RawAddress bd_addr);
-void bta_hh_api_disc_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
- CHECK(p_cb != nullptr);
-
- if (p_cb->is_le_device) {
- LOG_DEBUG("Host initiating close to le device:%s",
- PRIVATE_ADDRESS(p_cb->addr));
+void bta_hh_api_disc_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
+ tBTA_HH_CBDATA disc_dat;
+ tHID_STATUS status;
+#if (BTA_HH_LE_INCLUDED == TRUE)
+ if (p_cb->is_le_device)
bta_hh_le_api_disc_act(p_cb);
+ else
+#endif
+ {
+ /* found an active connection */
+ disc_dat.handle =
+ p_data ? (uint8_t)p_data->hdr.layer_specific : p_cb->hid_handle;
+ disc_dat.status = BTA_HH_ERR;
- } else {
- const uint8_t hid_handle =
- (p_data != nullptr) ? static_cast<uint8_t>(p_data->hdr.layer_specific)
- : p_cb->hid_handle;
- tHID_STATUS status = HID_HostCloseDev(hid_handle);
- if (status != HID_SUCCESS) {
- LOG_WARN("Failed closing classic device:%s status:%s",
- PRIVATE_ADDRESS(p_cb->addr), hid_status_text(status).c_str());
- } else {
- LOG_DEBUG("Host initiated close to classic device:%s",
- PRIVATE_ADDRESS(p_cb->addr));
+ status = HID_HostCloseDev(disc_dat.handle);
+
+ if (status) {
+ tBTA_HH bta_hh;
+ bta_hh.dev_status = disc_dat;
+ (*bta_hh_cb.p_cback)(BTA_HH_CLOSE_EVT, &bta_hh);
}
- tBTA_HH bta_hh = {
- .dev_status = {.status =
- (status == HID_SUCCESS) ? BTA_HH_OK : BTA_HH_ERR,
- .handle = hid_handle},
- };
- (*bta_hh_cb.p_cback)(BTA_HH_CLOSE_EVT, &bta_hh);
}
-}
+ return;
+}
/*******************************************************************************
*
* Function bta_hh_open_cmpl_act
@@ -513,7 +521,7 @@ void bta_hh_api_disc_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
* Returns void
*
******************************************************************************/
-void bta_hh_open_cmpl_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_open_cmpl_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
tBTA_HH_CONN conn;
uint8_t dev_handle =
p_data ? (uint8_t)p_data->hid_cback.hdr.layer_specific : p_cb->hid_handle;
@@ -529,23 +537,22 @@ void bta_hh_open_cmpl_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
bta_hh_co_open(p_cb->hid_handle, p_cb->sub_class, p_cb->attr_mask,
p_cb->app_id);
+#if (BTA_HH_LE_INCLUDED == TRUE)
conn.status = p_cb->status;
conn.le_hid = p_cb->is_le_device;
conn.scps_supported = p_cb->scps_supported;
- BTM_LogHistory(kBtmLogTag, p_cb->addr, "Opened",
- base::StringPrintf(
- "%s initiator:%s", (p_cb->is_le_device) ? "le" : "classic",
- (p_cb->incoming_conn) ? "remote" : "local"));
-
if (!p_cb->is_le_device)
+#endif
{
/* inform role manager */
bta_sys_conn_open(BTA_ID_HH, p_cb->app_id, p_cb->addr);
}
/* set protocol mode when not default report mode */
if (p_cb->mode != BTA_HH_PROTO_RPT_MODE
+#if (BTA_HH_LE_INCLUDED == TRUE)
&& !p_cb->is_le_device
+#endif
) {
if ((HID_HostWriteDev(dev_handle, HID_TRANS_SET_PROTOCOL,
HID_PAR_PROTOCOL_BOOT_MODE, 0, 0, NULL)) !=
@@ -573,13 +580,15 @@ void bta_hh_open_cmpl_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
* Returns void
*
******************************************************************************/
-void bta_hh_open_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_open_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
tBTA_HH_API_CONN conn_data;
uint8_t dev_handle =
p_data ? (uint8_t)p_data->hid_cback.hdr.layer_specific : p_cb->hid_handle;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_EVENT("%s: Device[%d] connected", __func__, dev_handle);
+#endif
/* SDP has been done */
if (p_cb->app_id != 0) {
@@ -611,7 +620,7 @@ void bta_hh_open_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
* Returns void
*
******************************************************************************/
-void bta_hh_data_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_data_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
BT_HDR* pdata = p_data->hid_cback.p_data;
uint8_t* p_rpt = (uint8_t*)(pdata + 1) + pdata->offset;
@@ -632,9 +641,11 @@ void bta_hh_data_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
* Returns void
*
******************************************************************************/
-void bta_hh_handsk_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_handsk_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("HANDSHAKE received for: event = %s data= %d",
bta_hh_get_w4_event(p_cb->w4_evt), p_data->hid_cback.data);
+#endif
tBTA_HH bta_hh;
memset(&bta_hh, 0, sizeof(tBTA_HH));
@@ -679,7 +690,9 @@ void bta_hh_handsk_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
bta_hh.conn.handle = p_cb->hid_handle;
bta_hh.conn.bda = p_cb->addr;
(*bta_hh_cb.p_cback)(p_cb->w4_evt, &bta_hh);
+#if (BTA_HH_DEBUG == TRUE)
bta_hh_trace_dev_db();
+#endif
p_cb->w4_evt = 0;
break;
@@ -703,13 +716,15 @@ void bta_hh_handsk_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
* Returns void
*
******************************************************************************/
-void bta_hh_ctrl_dat_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_ctrl_dat_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
BT_HDR* pdata = p_data->hid_cback.p_data;
uint8_t* data = (uint8_t*)(pdata + 1) + pdata->offset;
tBTA_HH_HSDATA hs_data;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("Ctrl DATA received w4: event[%s]",
bta_hh_get_w4_event(p_cb->w4_evt));
+#endif
if (pdata->len == 0) {
android_errorWriteLog(0x534e4554, "116108738");
p_cb->w4_evt = 0;
@@ -733,10 +748,12 @@ void bta_hh_ctrl_dat_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
hs_data.rsp_data.proto_mode = ((*data) == HID_PAR_PROTOCOL_REPORT)
? BTA_HH_PROTO_RPT_MODE
: BTA_HH_PROTO_BOOT_MODE;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("GET_PROTOCOL Mode = [%s]",
(hs_data.rsp_data.proto_mode == BTA_HH_PROTO_RPT_MODE)
? "Report"
: "Boot");
+#endif
break;
/* should not expect control DATA for SET_ transaction */
case BTA_HH_SET_PROTO_EVT:
@@ -746,8 +763,10 @@ void bta_hh_ctrl_dat_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
case BTA_HH_SET_IDLE_EVT:
FALLTHROUGH_INTENDED; /* FALLTHROUGH */
default:
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("invalid transaction type for DATA payload: 4_evt[%s]",
bta_hh_get_w4_event(p_cb->w4_evt));
+#endif
break;
}
@@ -772,7 +791,7 @@ void bta_hh_ctrl_dat_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
* Returns void
*
******************************************************************************/
-void bta_hh_open_failure(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_open_failure(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
tBTA_HH_CONN conn_dat;
uint32_t reason = p_data->hid_cback.data; /* Reason for closing (32-bit) */
@@ -786,7 +805,9 @@ void bta_hh_open_failure(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
/* Report OPEN fail event */
(*bta_hh_cb.p_cback)(BTA_HH_OPEN_EVT, (tBTA_HH*)&conn_dat);
+#if (BTA_HH_DEBUG == TRUE)
bta_hh_trace_dev_db();
+#endif
/* clean up control block, but retain SDP info and device handle */
p_cb->vp = false;
p_cb->w4_evt = 0;
@@ -811,31 +832,16 @@ void bta_hh_open_failure(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
* Returns void
*
******************************************************************************/
-void bta_hh_close_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_close_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
tBTA_HH_CONN conn_dat;
tBTA_HH_CBDATA disc_dat = {BTA_HH_OK, 0};
-
uint32_t reason = p_data->hid_cback.data; /* Reason for closing (32-bit) */
- const bool l2cap_conn_fail = reason & HID_L2CAP_CONN_FAIL;
- const bool l2cap_req_fail = reason & HID_L2CAP_REQ_FAIL;
- const bool l2cap_cfg_fail = reason & HID_L2CAP_CFG_FAIL;
- const tHID_STATUS hid_status = static_cast<tHID_STATUS>(reason & 0xff);
/* if HID_HDEV_EVT_VC_UNPLUG was received, report BTA_HH_VC_UNPLUG_EVT */
uint16_t event = p_cb->vp ? BTA_HH_VC_UNPLUG_EVT : BTA_HH_CLOSE_EVT;
disc_dat.handle = p_cb->hid_handle;
- disc_dat.status = to_bta_hh_status(p_data->hid_cback.data);
-
- std::string overlay_fail =
- base::StringPrintf("%s %s %s", (l2cap_conn_fail) ? "l2cap_conn_fail" : "",
- (l2cap_req_fail) ? "l2cap_req_fail" : "",
- (l2cap_cfg_fail) ? "l2cap_cfg_fail" : "");
- BTM_LogHistory(kBtmLogTag, p_cb->addr, "Closed",
- base::StringPrintf("%s reason %s %s",
- (p_cb->is_le_device) ? "le" : "classic",
- hid_status_text(hid_status).c_str(),
- overlay_fail.c_str()));
+ disc_dat.status = p_data->hid_cback.data;
/* Check reason for closing */
if ((reason & (HID_L2CAP_CONN_FAIL |
@@ -855,7 +861,9 @@ void bta_hh_close_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
/* Report OPEN fail event */
(*bta_hh_cb.p_cback)(BTA_HH_OPEN_EVT, (tBTA_HH*)&conn_dat);
+#if (BTA_HH_DEBUG == TRUE)
bta_hh_trace_dev_db();
+#endif
return;
}
/* otherwise report CLOSE/VC_UNPLUG event */
@@ -877,7 +885,9 @@ void bta_hh_close_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
bta_hh_clean_up_kdev(p_cb);
}
+#if (BTA_HH_DEBUG == TRUE)
bta_hh_trace_dev_db();
+#endif
}
/* clean up control block, but retain SDP info and device handle */
@@ -903,10 +913,12 @@ void bta_hh_close_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
*
******************************************************************************/
void bta_hh_get_dscp_act(tBTA_HH_DEV_CB* p_cb,
- UNUSED_ATTR const tBTA_HH_DATA* p_data) {
+ UNUSED_ATTR tBTA_HH_DATA* p_data) {
+#if (BTA_HH_LE_INCLUDED == TRUE)
if (p_cb->is_le_device) {
bta_hh_le_get_dscp_act(p_cb);
} else
+#endif
(*bta_hh_cb.p_cback)(BTA_HH_GET_DSCP_EVT, (tBTA_HH*)&p_cb->dscp_info);
}
@@ -920,8 +932,8 @@ void bta_hh_get_dscp_act(tBTA_HH_DEV_CB* p_cb,
* Returns void
*
******************************************************************************/
-void bta_hh_maint_dev_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
- const tBTA_HH_MAINT_DEV* p_dev_info = &p_data->api_maintdev;
+void bta_hh_maint_dev_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
+ tBTA_HH_MAINT_DEV* p_dev_info = &p_data->api_maintdev;
tBTA_HH_DEV_INFO dev_info;
uint8_t dev_handle;
@@ -933,23 +945,31 @@ void bta_hh_maint_dev_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
dev_info.bda = p_dev_info->bda;
/* initialize callback data */
if (p_cb->hid_handle == BTA_HH_INVALID_HANDLE) {
- if (BTM_UseLeLink(p_data->api_conn.bd_addr)) {
- p_cb->is_le_device = true;
+#if (BTA_HH_LE_INCLUDED == TRUE)
+ if (bta_hh_is_le_device(p_cb, p_data->api_conn.bd_addr)) {
dev_info.handle = bta_hh_le_add_device(p_cb, p_dev_info);
if (dev_info.handle != BTA_HH_INVALID_HANDLE)
dev_info.status = BTA_HH_OK;
} else
+#endif
if (HID_HostAddDev(p_dev_info->bda, p_dev_info->attr_mask,
&dev_handle) == HID_SUCCESS) {
dev_info.handle = dev_handle;
dev_info.status = BTA_HH_OK;
+#if (BTA_HH_LE_INCLUDED == TRUE)
/* update DI information */
bta_hh_update_di_info(p_cb, p_dev_info->dscp_info.vendor_id,
p_dev_info->dscp_info.product_id,
p_dev_info->dscp_info.version,
p_dev_info->dscp_info.flag);
+#else
+ bta_hh_update_di_info(p_cb, p_dev_info->dscp_info.vendor_id,
+ p_dev_info->dscp_info.product_id,
+ p_dev_info->dscp_info.version, 0);
+
+#endif
/* add to BTA device list */
bta_hh_add_device_to_list(
p_cb, dev_handle, p_dev_info->attr_mask,
@@ -964,18 +984,22 @@ void bta_hh_maint_dev_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
dev_info.handle = p_cb->hid_handle;
dev_info.status = BTA_HH_OK;
}
+#if (BTA_HH_DEBUG == TRUE)
bta_hh_trace_dev_db();
+#endif
break;
case BTA_HH_RMV_DEV_EVT: /* remove device */
dev_info.handle = (uint8_t)p_dev_info->hdr.layer_specific;
dev_info.bda = p_cb->addr;
+#if (BTA_HH_LE_INCLUDED == TRUE)
if (p_cb->is_le_device) {
bta_hh_le_remove_dev_bg_conn(p_cb);
bta_hh_sm_execute(p_cb, BTA_HH_API_CLOSE_EVT, NULL);
bta_hh_clean_up_kdev(p_cb);
} else
+#endif
{
if (HID_HostRemoveDev(dev_info.handle) == HID_SUCCESS) {
dev_info.status = BTA_HH_OK;
@@ -1002,34 +1026,30 @@ void bta_hh_maint_dev_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
* Returns void
*
******************************************************************************/
-static uint8_t convert_api_sndcmd_param(const tBTA_HH_CMD_DATA& api_sndcmd) {
- uint8_t api_sndcmd_param = api_sndcmd.param;
- if (api_sndcmd.t_type == HID_TRANS_SET_PROTOCOL) {
- api_sndcmd_param = (api_sndcmd.param == BTA_HH_PROTO_RPT_MODE)
- ? HID_PAR_PROTOCOL_REPORT
- : HID_PAR_PROTOCOL_BOOT_MODE;
- }
- return api_sndcmd_param;
-}
-
-void bta_hh_write_dev_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_write_dev_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
tBTA_HH_CBDATA cbdata = {BTA_HH_OK, 0};
- uint16_t event =
- (p_data->api_sndcmd.t_type - HID_TRANS_GET_REPORT) + BTA_HH_GET_RPT_EVT;
+ uint16_t event = (p_data->api_sndcmd.t_type - BTA_HH_FST_BTE_TRANS_EVT) +
+ BTA_HH_FST_TRANS_CB_EVT;
+#if (BTA_HH_LE_INCLUDED == TRUE)
if (p_cb->is_le_device)
bta_hh_le_write_dev_act(p_cb, p_data);
else
+#endif
{
cbdata.handle = p_cb->hid_handle;
/* match up BTE/BTA report/boot mode def */
- const uint8_t api_sndcmd_param =
- convert_api_sndcmd_param(p_data->api_sndcmd);
+ if (p_data->api_sndcmd.t_type == HID_TRANS_SET_PROTOCOL) {
+ p_data->api_sndcmd.param =
+ (p_data->api_sndcmd.param == BTA_HH_PROTO_RPT_MODE)
+ ? HID_PAR_PROTOCOL_REPORT
+ : HID_PAR_PROTOCOL_BOOT_MODE;
+ }
if (HID_HostWriteDev(p_cb->hid_handle, p_data->api_sndcmd.t_type,
- api_sndcmd_param, p_data->api_sndcmd.data,
+ p_data->api_sndcmd.param, p_data->api_sndcmd.data,
p_data->api_sndcmd.rpt_id,
p_data->api_sndcmd.p_data) != HID_SUCCESS) {
APPL_TRACE_ERROR("HID_HostWriteDev Error ");
@@ -1038,7 +1058,7 @@ void bta_hh_write_dev_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
if (p_data->api_sndcmd.t_type != HID_TRANS_CONTROL &&
p_data->api_sndcmd.t_type != HID_TRANS_DATA)
(*bta_hh_cb.p_cback)(event, (tBTA_HH*)&cbdata);
- else if (api_sndcmd_param == BTA_HH_CTRL_VIRTUAL_CABLE_UNPLUG)
+ else if (p_data->api_sndcmd.param == BTA_HH_CTRL_VIRTUAL_CABLE_UNPLUG)
(*bta_hh_cb.p_cback)(BTA_HH_VC_UNPLUG_EVT, (tBTA_HH*)&cbdata);
} else {
switch (p_data->api_sndcmd.t_type) {
@@ -1061,7 +1081,7 @@ void bta_hh_write_dev_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
case HID_TRANS_CONTROL:
/* no handshake event will be generated */
/* if VC_UNPLUG is issued, set flag */
- if (api_sndcmd_param == BTA_HH_CTRL_VIRTUAL_CABLE_UNPLUG)
+ if (p_data->api_sndcmd.param == BTA_HH_CTRL_VIRTUAL_CABLE_UNPLUG)
p_cb->vp = true;
break;
@@ -1078,9 +1098,9 @@ void bta_hh_write_dev_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
/* inform PM for mode change */
bta_sys_busy(BTA_ID_HH, p_cb->app_id, p_cb->addr);
bta_sys_idle(BTA_ID_HH, p_cb->app_id, p_cb->addr);
- } else if (api_sndcmd_param == BTA_HH_CTRL_SUSPEND) {
+ } else if (p_data->api_sndcmd.param == BTA_HH_CTRL_SUSPEND) {
bta_sys_sco_close(BTA_ID_HH, p_cb->app_id, p_cb->addr);
- } else if (api_sndcmd_param == BTA_HH_CTRL_EXIT_SUSPEND) {
+ } else if (p_data->api_sndcmd.param == BTA_HH_CTRL_EXIT_SUSPEND) {
bta_sys_busy(BTA_ID_HH, p_cb->app_id, p_cb->addr);
}
}
@@ -1106,8 +1126,10 @@ static void bta_hh_cback(uint8_t dev_handle, const RawAddress& addr,
uint16_t sm_event = BTA_HH_INVALID_EVT;
uint8_t xx = 0;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("%s::HID_event [%s]", __func__,
bta_hh_hid_event_name(event));
+#endif
switch (event) {
case HID_HDEV_EVT_OPEN:
@@ -1183,6 +1205,7 @@ static tBTA_HH_STATUS bta_hh_get_trans_status(uint32_t result) {
* Debug Functions
****************************************************************************/
+#if (BTA_HH_DEBUG == TRUE)
static const char* bta_hh_get_w4_event(uint16_t event) {
switch (event) {
case BTA_HH_GET_RPT_EVT:
@@ -1228,3 +1251,5 @@ static const char* bta_hh_hid_event_name(uint16_t event) {
return "Unknown HID event";
}
}
+#endif
+#endif /* BTA_HH_INCLUDED */
diff --git a/bta/hh/bta_hh_api.cc b/bta/hh/bta_hh_api.cc
index bd9994a50..cd32ede47 100644
--- a/bta/hh/bta_hh_api.cc
+++ b/bta/hh/bta_hh_api.cc
@@ -24,17 +24,21 @@
#define LOG_TAG "bt_bta_hh"
-#include <cstdint>
+#include "bta_hh_api.h"
+
+#include "bt_target.h"
-// BTA_HH_INCLUDED
-#include "bt_target.h" // Must be first to define build configuration
#if (BTA_HH_INCLUDED == TRUE)
-#include "bta/hh/bta_hh_int.h"
-#include "bta/sys/bta_sys.h"
-#include "osi/include/allocator.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "types/raw_address.h"
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "bta_hh_int.h"
+#include "l2c_api.h"
+#include "osi/include/log.h"
+#include "osi/include/osi.h"
+#include "utl.h"
/*****************************************************************************
* Constants
@@ -55,15 +59,18 @@ static const tBTA_SYS_REG bta_hh_reg = {bta_hh_hdl_event, BTA_HhDisable};
* Returns void
*
******************************************************************************/
-void BTA_HhEnable(tBTA_HH_CBACK* p_cback) {
+void BTA_HhEnable(tBTA_SEC sec_mask, tBTA_HH_CBACK* p_cback) {
tBTA_HH_API_ENABLE* p_buf =
(tBTA_HH_API_ENABLE*)osi_calloc(sizeof(tBTA_HH_API_ENABLE));
+ LOG_INFO(LOG_TAG, "%s sec_mask:0x%x p_cback:%p", __func__, sec_mask, p_cback);
+
/* register with BTA system manager */
bta_sys_register(BTA_ID_HH, &bta_hh_reg);
p_buf->hdr.event = BTA_HH_API_ENABLE_EVT;
p_buf->p_cback = p_cback;
+ p_buf->sec_mask = sec_mask;
bta_sys_sendmsg(p_buf);
}
@@ -115,13 +122,14 @@ void BTA_HhClose(uint8_t dev_handle) {
* Returns void
*
******************************************************************************/
-void BTA_HhOpen(const RawAddress& dev_bda) {
+void BTA_HhOpen(const RawAddress& dev_bda, tBTA_HH_PROTO_MODE mode,
+ tBTA_SEC sec_mask) {
tBTA_HH_API_CONN* p_buf =
(tBTA_HH_API_CONN*)osi_calloc(sizeof(tBTA_HH_API_CONN));
- tBTA_HH_PROTO_MODE mode = BTA_HH_PROTO_RPT_MODE;
p_buf->hdr.event = BTA_HH_API_OPEN_EVT;
p_buf->hdr.layer_specific = BTA_HH_INVALID_HANDLE;
+ p_buf->sec_mask = sec_mask;
p_buf->mode = mode;
p_buf->bd_addr = dev_bda;
@@ -164,7 +172,13 @@ static void bta_hh_snd_write_dev(uint8_t dev_handle, uint8_t t_type,
******************************************************************************/
void BTA_HhSetReport(uint8_t dev_handle, tBTA_HH_RPT_TYPE r_type,
BT_HDR* p_data) {
- bta_hh_snd_write_dev(dev_handle, HID_TRANS_SET_REPORT, r_type, 0, 0, p_data);
+ /* send feature report on control channel */
+ if (r_type == BTA_HH_RPTT_FEATURE)
+ bta_hh_snd_write_dev(dev_handle, HID_TRANS_SET_REPORT, r_type, 0, 0,
+ p_data);
+ /* send output data report on interrupt channel */
+ else
+ bta_hh_snd_write_dev(dev_handle, HID_TRANS_DATA, r_type, 0, 0, p_data);
}
/*******************************************************************************
*
@@ -266,12 +280,14 @@ void BTA_HhSendCtrl(uint8_t dev_handle, tBTA_HH_TRANS_CTRL_TYPE c_type) {
******************************************************************************/
void BTA_HhSendData(uint8_t dev_handle, UNUSED_ATTR const RawAddress& dev_bda,
BT_HDR* p_data) {
+#if (BTA_HH_LE_INCLUDED == TRUE)
if (p_data->layer_specific != BTA_HH_RPTT_OUTPUT) {
APPL_TRACE_ERROR(
"ERROR! Wrong report type! Write Command only valid for output "
"report!");
return;
}
+#endif
bta_hh_snd_write_dev(dev_handle, HID_TRANS_DATA,
(uint8_t)p_data->layer_specific, 0, 0, p_data);
}
@@ -359,4 +375,45 @@ void BTA_HhRemoveDev(uint8_t dev_handle) {
/* Utility Function */
/******************************************************************************/
+/*******************************************************************************
+ *
+ * Function BTA_HhParseBootRpt
+ *
+ * Description This utility function parse a boot mode report.
+ * For keyboard report, report data will carry the keycode max
+ * up to 6 key press in one report. Application need to convert
+ * the keycode into keypress character according to keyboard
+ * language.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTA_HhParseBootRpt(tBTA_HH_BOOT_RPT* p_data, uint8_t* p_report,
+ uint16_t report_len) {
+ p_data->dev_type = BTA_HH_DEVT_UNKNOWN;
+
+ if (p_report) {
+ /* first byte is report ID */
+ switch (p_report[0]) {
+ case BTA_HH_KEYBD_RPT_ID: /* key board report ID */
+ p_data->dev_type = p_report[0];
+ bta_hh_parse_keybd_rpt(p_data, p_report + 1,
+ (uint16_t)(report_len - 1));
+ break;
+
+ case BTA_HH_MOUSE_RPT_ID: /* mouse report ID */
+ p_data->dev_type = p_report[0];
+ bta_hh_parse_mice_rpt(p_data, p_report + 1, (uint16_t)(report_len - 1));
+ break;
+
+ default:
+ APPL_TRACE_DEBUG("Unknown boot report: %d", p_report[0]);
+ ;
+ break;
+ }
+ }
+
+ return;
+}
+
#endif /* BTA_HH_INCLUDED */
diff --git a/bta/hh/bta_hh_cfg.cc b/bta/hh/bta_hh_cfg.cc
index 483ce1c9e..debe3e59e 100644
--- a/bta/hh/bta_hh_cfg.cc
+++ b/bta/hh/bta_hh_cfg.cc
@@ -23,9 +23,8 @@
*
******************************************************************************/
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_hh_api.h"
+#include "bt_target.h"
+#include "bta_hh_api.h"
/* max number of device types supported by BTA */
#define BTA_HH_MAX_DEVT_SPT 9
diff --git a/bta/hh/bta_hh_int.h b/bta/hh/bta_hh_int.h
index 8a350ad8f..74bcffc60 100644
--- a/bta/hh/bta_hh_int.h
+++ b/bta/hh/bta_hh_int.h
@@ -25,16 +25,19 @@
#ifndef BTA_HH_INT_H
#define BTA_HH_INT_H
-#include <cstdint>
+#include "bta_hh_api.h"
+#include "bta_sys.h"
+#include "utl.h"
-#include "bta/include/bta_api.h"
-#include "bta/include/bta_gatt_api.h"
-#include "bta/include/bta_hh_api.h"
-#include "bta/sys/bta_sys.h"
-#include "stack/include/bt_types.h"
+#if (BTA_HH_LE_INCLUDED == TRUE)
+#include "bta_gatt_api.h"
+#endif
+
+/* can be moved to bta_api.h */
+#define BTA_HH_MAX_RPT_CHARS 8
/* state machine events, these events are handled by the state machine */
-enum tBTA_HH_INT_EVT : uint16_t {
+enum {
BTA_HH_API_OPEN_EVT = BTA_SYS_EVT_START(BTA_ID_HH),
BTA_HH_API_CLOSE_EVT,
BTA_HH_INT_OPEN_EVT,
@@ -47,66 +50,86 @@ enum tBTA_HH_INT_EVT : uint16_t {
BTA_HH_API_GET_DSCP_EVT,
BTA_HH_API_MAINT_DEV_EVT,
BTA_HH_OPEN_CMPL_EVT,
+#if (BTA_HH_LE_INCLUDED == TRUE)
BTA_HH_GATT_CLOSE_EVT,
BTA_HH_GATT_OPEN_EVT,
BTA_HH_START_ENC_EVT,
BTA_HH_ENC_CMPL_EVT,
BTA_HH_GATT_ENC_CMPL_EVT,
+#endif
/* not handled by execute state machine */
BTA_HH_API_ENABLE_EVT,
BTA_HH_API_DISABLE_EVT,
BTA_HH_DISC_CMPL_EVT
-}; /* HID host internal events */
+};
+typedef uint16_t tBTA_HH_INT_EVT; /* HID host internal events */
#define BTA_HH_INVALID_EVT (BTA_HH_DISC_CMPL_EVT + 1)
+/* event used to map between BTE event and BTA event */
+#define BTA_HH_FST_TRANS_CB_EVT BTA_HH_GET_RPT_EVT
+#define BTA_HH_FST_BTE_TRANS_EVT HID_TRANS_GET_REPORT
+
+/* sub event code used for device maintainence API call */
+#define BTA_HH_ADD_DEV 0
+#define BTA_HH_REMOVE_DEV 1
+
/* state machine states */
enum {
BTA_HH_NULL_ST,
BTA_HH_IDLE_ST,
BTA_HH_W4_CONN_ST,
- BTA_HH_CONN_ST,
- BTA_HH_W4_SEC,
+ BTA_HH_CONN_ST
+#if (BTA_HH_LE_INCLUDED == TRUE)
+ ,
+ BTA_HH_W4_SEC
+#endif
+ ,
BTA_HH_INVALID_ST /* Used to check invalid states before executing SM function
- */
+ */
};
typedef uint8_t tBTA_HH_STATE;
/* data structure used to send a command/data to HID device */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint8_t t_type;
uint8_t param;
uint8_t rpt_id;
+#if (BTA_HH_LE_INCLUDED == TRUE)
+ uint8_t srvc_id;
+#endif
uint16_t data;
BT_HDR* p_data;
} tBTA_HH_CMD_DATA;
/* data type for BTA_HH_API_ENABLE_EVT */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
+ uint8_t sec_mask;
uint8_t service_name[BTA_SERVICE_NAME_LEN + 1];
tBTA_HH_CBACK* p_cback;
} tBTA_HH_API_ENABLE;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress bd_addr;
+ uint8_t sec_mask;
tBTA_HH_PROTO_MODE mode;
} tBTA_HH_API_CONN;
/* internal event data from BTE HID callback */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress addr;
uint32_t data;
BT_HDR* p_data;
} tBTA_HH_CBACK_DATA;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress bda;
uint16_t attr_mask;
uint16_t sub_event;
@@ -115,38 +138,44 @@ typedef struct {
tBTA_HH_DEV_DSCP_INFO dscp_info;
} tBTA_HH_MAINT_DEV;
+#if (BTA_HH_LE_INCLUDED == TRUE)
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint16_t conn_id;
- tGATT_DISCONN_REASON reason;
+ tBTA_GATT_REASON reason; /* disconnect reason code, not useful when connect
+ event is reported */
+
} tBTA_HH_LE_CLOSE;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint16_t scan_int;
uint16_t scan_win;
} tBTA_HH_SCPP_UPDATE;
-
+#endif
/* union of all event data types */
typedef union {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_HH_API_ENABLE api_enable;
tBTA_HH_API_CONN api_conn;
tBTA_HH_CMD_DATA api_sndcmd;
tBTA_HH_CBACK_DATA hid_cback;
tBTA_HH_STATUS status;
tBTA_HH_MAINT_DEV api_maintdev;
+#if (BTA_HH_LE_INCLUDED == TRUE)
tBTA_HH_LE_CLOSE le_close;
tBTA_GATTC_OPEN le_open;
tBTA_HH_SCPP_UPDATE le_scpp_update;
tBTA_GATTC_ENC_CMPL_CB le_enc_cmpl;
+#endif
} tBTA_HH_DATA;
+#if (BTA_HH_LE_INCLUDED == TRUE)
typedef struct {
uint8_t index;
bool in_use;
uint8_t srvc_inst_id;
- uint16_t char_inst_id;
+ uint8_t char_inst_id;
tBTA_HH_RPT_TYPE rpt_type;
uint16_t uuid;
uint8_t rpt_id;
@@ -183,6 +212,7 @@ typedef struct {
/* check to see if th edevice handle is a LE device handle */
#define BTA_HH_IS_LE_DEV_HDL(x) ((x)&0xf0)
#define BTA_HH_IS_LE_DEV_HDL_VALID(x) (((x) >> 4) <= BTA_HH_LE_MAX_KNOWN)
+#endif
/* device control block */
typedef struct {
@@ -192,6 +222,7 @@ typedef struct {
uint16_t w4_evt; /* W4_handshake event name */
uint8_t index; /* index number referenced to handle index */
uint8_t sub_class; /* Cod sub class */
+ uint8_t sec_mask; /* security mask */
uint8_t app_id; /* application ID for this connection */
uint8_t hid_handle; /* device handle : low 4 bits for regular HID:
HID_HOST_MAX_DEVICES can not exceed 15;
@@ -201,9 +232,11 @@ typedef struct {
bool in_use; /* control block currently in use */
bool incoming_conn; /* is incoming connection? */
uint8_t incoming_hid_handle; /* temporary handle for incoming connection? */
+ bool opened; /* true if device successfully opened HID connection */
tBTA_HH_PROTO_MODE mode; /* protocol mode */
tBTA_HH_STATE state; /* CB state */
+#if (BTA_HH_LE_INCLUDED == TRUE)
#define BTA_HH_LE_DISC_NONE 0x00
#define BTA_HH_LE_DISC_HIDS 0x01
#define BTA_HH_LE_DISC_DIS 0x02
@@ -211,35 +244,53 @@ typedef struct {
uint8_t disc_active;
tBTA_HH_STATUS status;
- tBTM_STATUS btm_status;
+ tBTA_GATT_REASON reason;
bool is_le_device;
tBTA_HH_LE_HID_SRVC hid_srvc;
uint16_t conn_id;
bool in_bg_conn;
uint8_t clt_cfg_idx;
+ uint16_t scan_refresh_char_handle;
bool scps_supported;
#define BTA_HH_LE_SCPS_NOTIFY_NONE 0
#define BTA_HH_LE_SCPS_NOTIFY_SPT 0x01
#define BTA_HH_LE_SCPS_NOTIFY_ENB 0x02
uint8_t scps_notify; /* scan refresh supported/notification enabled */
+#endif
+
bool security_pending;
} tBTA_HH_DEV_CB;
+/* key board parsing control block */
+typedef struct {
+ bool mod_key[4]; /* ctrl, shift(upper), Alt, GUI */
+ bool num_lock;
+ bool caps_lock;
+ uint8_t last_report[BTA_HH_MAX_RPT_CHARS];
+} tBTA_HH_KB_CB;
+
/******************************************************************************
* Main Control Block
******************************************************************************/
typedef struct {
+ tBTA_HH_KB_CB kb_cb; /* key board control block,
+ suppose BTA will connect
+ to only one keyboard at
+ the same time */
tBTA_HH_DEV_CB kdev[BTA_HH_MAX_DEVICE]; /* device control block */
tBTA_HH_DEV_CB* p_cur; /* current device control
block idx, used in sdp */
uint8_t cb_index[BTA_HH_MAX_KNOWN]; /* maintain a CB index
map to dev handle */
+#if (BTA_HH_LE_INCLUDED == TRUE)
uint8_t le_cb_index[BTA_HH_LE_MAX_KNOWN]; /* maintain a CB index map to LE dev
handle */
tGATT_IF gatt_if;
+#endif
tBTA_HH_CBACK* p_cback; /* Application callbacks */
tSDP_DISCOVERY_DB* p_disc_db;
+ uint8_t trace_level; /* tracing level */
uint8_t cnt_num; /* connected device number */
bool w4_disable; /* w4 disable flag */
} tBTA_HH_CB;
@@ -252,41 +303,37 @@ extern tBTA_HH_CFG* p_bta_hh_cfg;
/*****************************************************************************
* Function prototypes
****************************************************************************/
-extern bool bta_hh_hdl_event(BT_HDR_RIGID* p_msg);
+extern bool bta_hh_hdl_event(BT_HDR* p_msg);
extern void bta_hh_sm_execute(tBTA_HH_DEV_CB* p_cb, uint16_t event,
- const tBTA_HH_DATA* p_data);
+ tBTA_HH_DATA* p_data);
/* action functions */
-extern void bta_hh_api_disc_act(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_data);
-extern void bta_hh_open_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data);
-extern void bta_hh_close_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data);
-extern void bta_hh_data_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data);
-extern void bta_hh_ctrl_dat_act(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_data);
-extern void bta_hh_start_sdp(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data);
-extern void bta_hh_sdp_cmpl(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data);
-extern void bta_hh_write_dev_act(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_data);
-extern void bta_hh_get_dscp_act(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_data);
-extern void bta_hh_handsk_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data);
-extern void bta_hh_maint_dev_act(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_data);
-extern void bta_hh_open_cmpl_act(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_data);
-extern void bta_hh_open_failure(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_data);
+extern void bta_hh_api_disc_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_open_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_close_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_data_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_ctrl_dat_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_start_sdp(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_sdp_cmpl(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_write_dev_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_get_dscp_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_handsk_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_maint_dev_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_open_cmpl_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_open_failure(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
/* utility functions */
extern uint8_t bta_hh_find_cb(const RawAddress& bda);
-extern tBTA_HH_DEV_CB* bta_hh_get_cb(const RawAddress& bda);
+extern void bta_hh_parse_keybd_rpt(tBTA_HH_BOOT_RPT* p_kb_data,
+ uint8_t* p_report, uint16_t report_len);
+extern void bta_hh_parse_mice_rpt(tBTA_HH_BOOT_RPT* p_kb_data,
+ uint8_t* p_report, uint16_t report_len);
extern bool bta_hh_tod_spt(tBTA_HH_DEV_CB* p_cb, uint8_t sub_class);
extern void bta_hh_clean_up_kdev(tBTA_HH_DEV_CB* p_cb);
extern void bta_hh_add_device_to_list(tBTA_HH_DEV_CB* p_cb, uint8_t handle,
uint16_t attr_mask,
- const tHID_DEV_DSCP_INFO* p_dscp_info,
+ tHID_DEV_DSCP_INFO* p_dscp_info,
uint8_t sub_class, uint16_t max_latency,
uint16_t min_tout, uint8_t app_id);
extern void bta_hh_update_di_info(tBTA_HH_DEV_CB* p_cb, uint16_t vendor_id,
@@ -309,28 +356,27 @@ extern tBTA_HH_STATUS bta_hh_read_ssr_param(const RawAddress& bd_addr,
extern void bta_hh_le_enable(void);
extern bool bta_hh_le_is_hh_gatt_if(tGATT_IF client_if);
extern void bta_hh_le_deregister(void);
+extern bool bta_hh_is_le_device(tBTA_HH_DEV_CB* p_cb,
+ const RawAddress& remote_bda);
extern void bta_hh_le_open_conn(tBTA_HH_DEV_CB* p_cb,
const RawAddress& remote_bda);
extern void bta_hh_le_api_disc_act(tBTA_HH_DEV_CB* p_cb);
extern void bta_hh_le_get_dscp_act(tBTA_HH_DEV_CB* p_cb);
-extern void bta_hh_le_write_dev_act(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_data);
+extern void bta_hh_le_write_dev_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
extern uint8_t bta_hh_le_add_device(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_MAINT_DEV* p_dev_info);
+ tBTA_HH_MAINT_DEV* p_dev_info);
extern void bta_hh_le_remove_dev_bg_conn(tBTA_HH_DEV_CB* p_cb);
-extern void bta_hh_le_open_fail(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_data);
-extern void bta_hh_gatt_open(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data);
-extern void bta_hh_gatt_close(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data);
-extern void bta_hh_start_security(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_buf);
-
-extern void bta_hh_start_security(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_buf);
-extern void bta_hh_security_cmpl(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_buf);
+extern void bta_hh_le_open_fail(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_gatt_open(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_gatt_close(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+extern void bta_hh_start_security(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_buf);
+extern void bta_hh_start_srvc_discovery(tBTA_HH_DEV_CB* p_cb,
+ tBTA_HH_DATA* p_buf);
+extern void bta_hh_start_security(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_buf);
+extern void bta_hh_security_cmpl(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_buf);
extern void bta_hh_le_notify_enc_cmpl(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_data);
+ tBTA_HH_DATA* p_data);
+extern void bta_hh_ci_load_rpt(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_buf);
#if (BTA_HH_DEBUG == TRUE)
extern void bta_hh_trace_dev_db(void);
diff --git a/bta/hh/bta_hh_le.cc b/bta/hh/bta_hh_le.cc
index 093fe5ab8..ba95af1f6 100644..100755
--- a/bta/hh/bta_hh_le.cc
+++ b/bta/hh/bta_hh_le.cc
@@ -18,40 +18,41 @@
#define LOG_TAG "bt_bta_hh"
+#include "bta_api.h"
+#include "bta_hh_int.h"
+#include "osi/include/osi.h"
+
+#if (BTA_HH_LE_INCLUDED == TRUE)
+
+#include <string.h>
+
#include <base/bind.h>
#include <base/callback.h>
-#include <cstdint>
-#include <vector>
-#include "bta/hh/bta_hh_int.h"
-#include "bta/include/bta_gatt_queue.h"
-#include "bta/include/bta_hh_co.h"
+#include "bta_gatt_api.h"
+#include "bta_gatt_queue.h"
+#include "bta_hh_co.h"
+#include "btm_api.h"
+#include "btm_ble_api.h"
+#include "btm_int.h"
#include "device/include/interop.h"
-#include "main/shim/dumpsys.h"
#include "osi/include/log.h"
-#include "osi/include/osi.h" // ARRAY_SIZE
-#include "stack/btm/btm_sec.h" // BTM_
-#include "stack/include/btu.h" // post_on_bt_main
-#include "stack/include/l2c_api.h" // L2CA_
-#include "stack/include/srvc_api.h" // tDIS_VALUE
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
+#include "srvc_api.h"
+#include "stack/include/l2c_api.h"
+#include "utl.h"
using bluetooth::Uuid;
using std::vector;
-namespace {
-
#ifndef BTA_HH_LE_RECONN
-constexpr bool kBTA_HH_LE_RECONN = true;
-#else
-constexpr bool kBTA_HH_LE_RECONN = false;
+#define BTA_HH_LE_RECONN TRUE
#endif
-} // namespace
-
#define BTA_HH_APP_ID_LE 0xff
+#define BTA_HH_LE_RPT_TYPE_VALID(x) \
+ ((x) <= BTA_LE_HID_RPT_FEATURE && (x) >= BTA_LE_HID_RPT_INPUT)
+
#define BTA_HH_LE_PROTO_BOOT_MODE 0x00
#define BTA_HH_LE_PROTO_REPORT_MODE 0x01
@@ -69,6 +70,7 @@ static void bta_hh_process_cache_rpt(tBTA_HH_DEV_CB* p_cb,
tBTA_HH_RPT_CACHE_ENTRY* p_rpt_cache,
uint8_t num_rpt);
+#if (BTA_HH_DEBUG == TRUE)
static const char* bta_hh_le_rpt_name[4] = {"UNKNOWN", "INPUT", "OUTPUT",
"FEATURE"};
@@ -148,6 +150,7 @@ static const char* bta_hh_uuid_to_str(uint16_t uuid) {
}
}
+#endif
/*******************************************************************************
*
* Function bta_hh_le_enable
@@ -184,7 +187,7 @@ void bta_hh_le_enable(void) {
/* signal BTA call back event */
(*bta_hh_cb.p_cback)(BTA_HH_ENABLE_EVT, &bta_hh);
}
- }), false);
+ }));
}
/*******************************************************************************
@@ -213,6 +216,21 @@ bool bta_hh_le_is_hh_gatt_if(tGATT_IF client_if) {
******************************************************************************/
void bta_hh_le_deregister(void) { BTA_GATTC_AppDeregister(bta_hh_cb.gatt_if); }
+/*******************************************************************************
+ *
+ * Function bta_hh_is_le_device
+ *
+ * Description Check to see if the remote device is a LE only device
+ *
+ * Parameters:
+ *
+ ******************************************************************************/
+bool bta_hh_is_le_device(tBTA_HH_DEV_CB* p_cb, const RawAddress& remote_bda) {
+ p_cb->is_le_device = BTM_UseLeLink(remote_bda);
+
+ return p_cb->is_le_device;
+}
+
/******************************************************************************
*
* Function bta_hh_le_get_le_cb
@@ -222,7 +240,7 @@ void bta_hh_le_deregister(void) { BTA_GATTC_AppDeregister(bta_hh_cb.gatt_if); }
* Parameters:
*
******************************************************************************/
-static uint8_t bta_hh_le_get_le_dev_hdl(uint8_t cb_index) {
+uint8_t bta_hh_le_get_le_dev_hdl(uint8_t cb_index) {
uint8_t i;
for (i = 0; i < ARRAY_SIZE(bta_hh_cb.le_cb_index); i++) {
if (bta_hh_cb.le_cb_index[i] == cb_index) return BTA_HH_GET_LE_DEV_HDL(i);
@@ -258,7 +276,7 @@ void bta_hh_le_open_conn(tBTA_HH_DEV_CB* p_cb, const RawAddress& remote_bda) {
bta_hh_cb.le_cb_index[BTA_HH_GET_LE_CB_IDX(p_cb->hid_handle)] = p_cb->index;
p_cb->in_use = true;
- BTA_GATTC_Open(bta_hh_cb.gatt_if, remote_bda, true, false);
+ BTA_GATTC_Open(bta_hh_cb.gatt_if, remote_bda, true, GATT_TRANSPORT_LE, false);
}
/*******************************************************************************
@@ -269,7 +287,7 @@ void bta_hh_le_open_conn(tBTA_HH_DEV_CB* p_cb, const RawAddress& remote_bda) {
* ID.
*
******************************************************************************/
-static tBTA_HH_DEV_CB* bta_hh_le_find_dev_cb_by_conn_id(uint16_t conn_id) {
+tBTA_HH_DEV_CB* bta_hh_le_find_dev_cb_by_conn_id(uint16_t conn_id) {
uint8_t i;
tBTA_HH_DEV_CB* p_dev_cb = &bta_hh_cb.kdev[0];
@@ -286,7 +304,7 @@ static tBTA_HH_DEV_CB* bta_hh_le_find_dev_cb_by_conn_id(uint16_t conn_id) {
* Description Utility function find a device control block by BD address.
*
******************************************************************************/
-static tBTA_HH_DEV_CB* bta_hh_le_find_dev_cb_by_bda(const RawAddress& bda) {
+tBTA_HH_DEV_CB* bta_hh_le_find_dev_cb_by_bda(const RawAddress& bda) {
uint8_t i;
tBTA_HH_DEV_CB* p_dev_cb = &bta_hh_cb.kdev[0];
@@ -303,8 +321,8 @@ static tBTA_HH_DEV_CB* bta_hh_le_find_dev_cb_by_bda(const RawAddress& bda) {
* Description find HID service instance ID by battery service instance ID
*
******************************************************************************/
-static uint8_t bta_hh_le_find_service_inst_by_battery_inst_id(
- tBTA_HH_DEV_CB* p_cb, uint8_t ba_inst_id) {
+uint8_t bta_hh_le_find_service_inst_by_battery_inst_id(tBTA_HH_DEV_CB* p_cb,
+ uint8_t ba_inst_id) {
if (p_cb->hid_srvc.in_use && p_cb->hid_srvc.incl_srvc_inst == ba_inst_id) {
return p_cb->hid_srvc.srvc_inst_id;
}
@@ -319,9 +337,9 @@ static uint8_t bta_hh_le_find_service_inst_by_battery_inst_id(
* and instance ID
*
******************************************************************************/
-static tBTA_HH_LE_RPT* bta_hh_le_find_report_entry(
+tBTA_HH_LE_RPT* bta_hh_le_find_report_entry(
tBTA_HH_DEV_CB* p_cb, uint8_t srvc_inst_id, /* service instance ID */
- uint16_t rpt_uuid, uint16_t char_inst_id) {
+ uint16_t rpt_uuid, uint8_t char_inst_id) {
uint8_t i;
uint8_t hid_inst_id = srvc_inst_id;
tBTA_HH_LE_RPT* p_rpt;
@@ -353,15 +371,17 @@ static tBTA_HH_LE_RPT* bta_hh_le_find_report_entry(
* Returns void
*
******************************************************************************/
-static tBTA_HH_LE_RPT* bta_hh_le_find_rpt_by_idtype(tBTA_HH_LE_RPT* p_head,
- uint8_t mode,
- tBTA_HH_RPT_TYPE r_type,
- uint8_t rpt_id) {
+tBTA_HH_LE_RPT* bta_hh_le_find_rpt_by_idtype(tBTA_HH_LE_RPT* p_head,
+ uint8_t mode,
+ tBTA_HH_RPT_TYPE r_type,
+ uint8_t rpt_id) {
tBTA_HH_LE_RPT* p_rpt = p_head;
uint8_t i;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("bta_hh_le_find_rpt_by_idtype: r_type: %d rpt_id: %d",
r_type, rpt_id);
+#endif
for (i = 0; i < BTA_HH_LE_RPT_MAX; i++, p_rpt++) {
if (p_rpt->in_use && p_rpt->rpt_id == rpt_id && r_type == p_rpt->rpt_type) {
@@ -388,10 +408,10 @@ static tBTA_HH_LE_RPT* bta_hh_le_find_rpt_by_idtype(tBTA_HH_LE_RPT* p_head,
* list.
*
******************************************************************************/
-static tBTA_HH_LE_RPT* bta_hh_le_find_alloc_report_entry(tBTA_HH_DEV_CB* p_cb,
- uint8_t srvc_inst_id,
- uint16_t rpt_uuid,
- uint16_t inst_id) {
+tBTA_HH_LE_RPT* bta_hh_le_find_alloc_report_entry(tBTA_HH_DEV_CB* p_cb,
+ uint8_t srvc_inst_id,
+ uint16_t rpt_uuid,
+ uint8_t inst_id) {
uint8_t i, hid_inst_id = srvc_inst_id;
tBTA_HH_LE_RPT* p_rpt;
@@ -442,7 +462,7 @@ static const gatt::Descriptor* find_descriptor_by_short_uuid(
BTA_GATTC_GetCharacteristic(conn_id, char_handle);
if (!p_char) {
- LOG_WARN("%s No such characteristic: %d", __func__, char_handle);
+ LOG_WARN(LOG_TAG, "%s No such characteristic: %d", __func__, char_handle);
return NULL;
}
@@ -482,10 +502,9 @@ static tBTA_HH_STATUS bta_hh_le_read_char_descriptor(tBTA_HH_DEV_CB* p_cb,
* Parameters:
*
******************************************************************************/
-static void bta_hh_le_save_report_ref(tBTA_HH_DEV_CB* p_dev_cb,
- tBTA_HH_LE_RPT* p_rpt,
- tGATT_STATUS status, uint8_t* value,
- uint16_t len) {
+void bta_hh_le_save_report_ref(tBTA_HH_DEV_CB* p_dev_cb, tBTA_HH_LE_RPT* p_rpt,
+ tGATT_STATUS status, uint8_t* value,
+ uint16_t len) {
if (status == GATT_INSUF_AUTHENTICATION) {
/* close connection right away */
p_dev_cb->status = BTA_HH_ERR_AUTH_FAILED;
@@ -504,7 +523,9 @@ static void bta_hh_le_save_report_ref(tBTA_HH_DEV_CB* p_dev_cb,
if (p_rpt->rpt_type > BTA_HH_RPTT_FEATURE) /* invalid report type */
p_rpt->rpt_type = BTA_HH_RPTT_RESRV;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("%s: report ID: %d", __func__, p_rpt->rpt_id);
+#endif
tBTA_HH_RPT_CACHE_ENTRY rpt_entry;
rpt_entry.rpt_id = p_rpt->rpt_id;
rpt_entry.rpt_type = p_rpt->rpt_type;
@@ -531,13 +552,14 @@ static void bta_hh_le_save_report_ref(tBTA_HH_DEV_CB* p_dev_cb,
* Parameters:
*
******************************************************************************/
-static void bta_hh_le_register_input_notif(tBTA_HH_DEV_CB* p_dev_cb,
- uint8_t proto_mode,
- bool register_ba) {
+void bta_hh_le_register_input_notif(tBTA_HH_DEV_CB* p_dev_cb,
+ uint8_t proto_mode, bool register_ba) {
tBTA_HH_LE_RPT* p_rpt = &p_dev_cb->hid_srvc.report[0];
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("%s: bta_hh_le_register_input_notif mode: %d", __func__,
proto_mode);
+#endif
for (int i = 0; i < BTA_HH_LE_RPT_MAX; i++, p_rpt++) {
if (p_rpt->rpt_type == BTA_HH_RPTT_INPUT) {
@@ -591,7 +613,7 @@ static void bta_hh_le_register_input_notif(tBTA_HH_DEV_CB* p_dev_cb,
* Description Deregister all notifications
*
******************************************************************************/
-static void bta_hh_le_deregister_input_notif(tBTA_HH_DEV_CB* p_dev_cb) {
+void bta_hh_le_deregister_input_notif(tBTA_HH_DEV_CB* p_dev_cb) {
tBTA_HH_LE_RPT* p_rpt = &p_dev_cb->hid_srvc.report[0];
for (uint8_t i = 0; i < BTA_HH_LE_RPT_MAX; i++, p_rpt++) {
@@ -621,15 +643,19 @@ static void bta_hh_le_deregister_input_notif(tBTA_HH_DEV_CB* p_dev_cb) {
* Description HID over GATT connection sucessfully opened
*
******************************************************************************/
-static void bta_hh_le_open_cmpl(tBTA_HH_DEV_CB* p_cb) {
+void bta_hh_le_open_cmpl(tBTA_HH_DEV_CB* p_cb) {
if (p_cb->disc_active == BTA_HH_LE_DISC_NONE) {
+#if (BTA_HH_DEBUG == TRUE)
bta_hh_le_hid_report_dbg(p_cb);
+#endif
bta_hh_le_register_input_notif(p_cb, p_cb->mode, true);
bta_hh_sm_execute(p_cb, BTA_HH_OPEN_CMPL_EVT, NULL);
- if (kBTA_HH_LE_RECONN && p_cb->status == BTA_HH_OK) {
+#if (BTA_HH_LE_RECONN == TRUE)
+ if (p_cb->status == BTA_HH_OK) {
bta_hh_le_add_dev_bg_conn(p_cb, true);
}
+#endif
}
}
@@ -641,9 +667,9 @@ static void bta_hh_le_open_cmpl(tBTA_HH_DEV_CB* p_cb) {
* a characteristic
*
******************************************************************************/
-static bool bta_hh_le_write_ccc(tBTA_HH_DEV_CB* p_cb, uint16_t char_handle,
- uint16_t clt_cfg_value, GATT_WRITE_OP_CB cb,
- void* cb_data) {
+bool bta_hh_le_write_ccc(tBTA_HH_DEV_CB* p_cb, uint8_t char_handle,
+ uint16_t clt_cfg_value, GATT_WRITE_OP_CB cb,
+ void* cb_data) {
const gatt::Descriptor* p_desc = find_descriptor_by_short_uuid(
p_cb->conn_id, char_handle, GATT_UUID_CHAR_CLIENT_CONFIG);
if (!p_desc) return false;
@@ -657,7 +683,7 @@ static bool bta_hh_le_write_ccc(tBTA_HH_DEV_CB* p_cb, uint16_t char_handle,
return true;
}
-static bool bta_hh_le_write_rpt_clt_cfg(tBTA_HH_DEV_CB* p_cb);
+bool bta_hh_le_write_rpt_clt_cfg(tBTA_HH_DEV_CB* p_cb);
static void write_rpt_ctl_cfg_cb(uint16_t conn_id, tGATT_STATUS status,
uint16_t handle, void* data) {
@@ -697,7 +723,7 @@ static void write_rpt_ctl_cfg_cb(uint16_t conn_id, tGATT_STATUS status,
* enable all input notification upon connection open.
*
******************************************************************************/
-static bool bta_hh_le_write_rpt_clt_cfg(tBTA_HH_DEV_CB* p_cb) {
+bool bta_hh_le_write_rpt_clt_cfg(tBTA_HH_DEV_CB* p_cb) {
uint8_t i;
tBTA_HH_LE_RPT* p_rpt = &p_cb->hid_srvc.report[p_cb->clt_cfg_idx];
@@ -759,8 +785,8 @@ static void write_proto_mode_cb(uint16_t conn_id, tGATT_STATUS status,
* Description Set remote device protocol mode.
*
******************************************************************************/
-static bool bta_hh_le_set_protocol_mode(tBTA_HH_DEV_CB* p_cb,
- tBTA_HH_PROTO_MODE mode) {
+bool bta_hh_le_set_protocol_mode(tBTA_HH_DEV_CB* p_cb,
+ tBTA_HH_PROTO_MODE mode) {
tBTA_HH_CBDATA cback_data;
APPL_TRACE_DEBUG("%s attempt mode: %s", __func__,
@@ -830,10 +856,12 @@ static void get_protocol_mode_cb(uint16_t conn_id, tGATT_STATUS status,
p_dev_cb->mode = hs_data.rsp_data.proto_mode;
}
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("LE GET_PROTOCOL Mode = [%s]",
(hs_data.rsp_data.proto_mode == BTA_HH_PROTO_RPT_MODE)
? "Report"
: "Boot");
+#endif
p_dev_cb->w4_evt = 0;
(*bta_hh_cb.p_cback)(BTA_HH_GET_PROTO_EVT, (tBTA_HH*)&hs_data);
@@ -846,7 +874,7 @@ static void get_protocol_mode_cb(uint16_t conn_id, tGATT_STATUS status,
* Description Get remote device protocol mode.
*
******************************************************************************/
-static void bta_hh_le_get_protocol_mode(tBTA_HH_DEV_CB* p_cb) {
+void bta_hh_le_get_protocol_mode(tBTA_HH_DEV_CB* p_cb) {
tBTA_HH_HSDATA hs_data;
p_cb->w4_evt = BTA_HH_GET_PROTO_EVT;
@@ -874,8 +902,7 @@ static void bta_hh_le_get_protocol_mode(tBTA_HH_DEV_CB* p_cb) {
* Parameters:
*
******************************************************************************/
-static void bta_hh_le_dis_cback(const RawAddress& addr,
- tDIS_VALUE* p_dis_value) {
+void bta_hh_le_dis_cback(const RawAddress& addr, tDIS_VALUE* p_dis_value) {
tBTA_HH_DEV_CB* p_cb = bta_hh_le_find_dev_cb_by_bda(addr);
if (p_cb == NULL || p_dis_value == NULL) {
@@ -886,10 +913,12 @@ static void bta_hh_le_dis_cback(const RawAddress& addr,
p_cb->disc_active &= ~BTA_HH_LE_DISC_DIS;
/* plug in the PnP info for this device */
if (p_dis_value->attr_mask & DIS_ATTR_PNP_ID_BIT) {
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG(
"Plug in PnP info: product_id = %02x, vendor_id = %04x, version = %04x",
p_dis_value->pnp_id.product_id, p_dis_value->pnp_id.vendor_id,
p_dis_value->pnp_id.product_version);
+#endif
p_cb->dscp_info.product_id = p_dis_value->pnp_id.product_id;
p_cb->dscp_info.vendor_id = p_dis_value->pnp_id.vendor_id;
p_cb->dscp_info.version = p_dis_value->pnp_id.product_version;
@@ -907,7 +936,7 @@ static void bta_hh_le_dis_cback(const RawAddress& addr,
* Parameters:
*
******************************************************************************/
-static void bta_hh_le_pri_service_discovery(tBTA_HH_DEV_CB* p_cb) {
+void bta_hh_le_pri_service_discovery(tBTA_HH_DEV_CB* p_cb) {
bta_hh_le_co_reset_rpt_cache(p_cb->addr, p_cb->app_id);
p_cb->disc_active |= (BTA_HH_LE_DISC_HIDS | BTA_HH_LE_DISC_DIS);
@@ -934,19 +963,20 @@ static void bta_hh_le_pri_service_discovery(tBTA_HH_DEV_CB* p_cb) {
* Returns None
*
******************************************************************************/
-static void bta_hh_le_encrypt_cback(const RawAddress* bd_addr,
- UNUSED_ATTR tBT_TRANSPORT transport,
- UNUSED_ATTR void* p_ref_data,
- tBTM_STATUS result) {
- tBTA_HH_DEV_CB* p_dev_cb = bta_hh_get_cb(*bd_addr);
- if (p_dev_cb == nullptr) {
- LOG_ERROR("unexpected encryption callback, ignore");
+void bta_hh_le_encrypt_cback(const RawAddress* bd_addr,
+ UNUSED_ATTR tGATT_TRANSPORT transport,
+ UNUSED_ATTR void* p_ref_data, tBTM_STATUS result) {
+ uint8_t idx = bta_hh_find_cb(*bd_addr);
+ tBTA_HH_DEV_CB* p_dev_cb;
+
+ if (idx != BTA_HH_IDX_INVALID)
+ p_dev_cb = &bta_hh_cb.kdev[idx];
+ else {
+ APPL_TRACE_ERROR("unexpected encryption callback, ignore");
return;
}
-
- // TODO Collapse the duplicated status values
p_dev_cb->status = (result == BTM_SUCCESS) ? BTA_HH_OK : BTA_HH_ERR_SEC;
- p_dev_cb->btm_status = result;
+ p_dev_cb->reason = result;
bta_hh_sm_execute(p_dev_cb, BTA_HH_ENC_CMPL_EVT, NULL);
}
@@ -963,7 +993,7 @@ static void bta_hh_le_encrypt_cback(const RawAddress* bd_addr,
*
******************************************************************************/
void bta_hh_security_cmpl(tBTA_HH_DEV_CB* p_cb,
- UNUSED_ATTR const tBTA_HH_DATA* p_buf) {
+ UNUSED_ATTR tBTA_HH_DATA* p_buf) {
APPL_TRACE_DEBUG("%s", __func__);
if (p_cb->status == BTA_HH_OK) {
if (!p_cb->hid_srvc.in_use) {
@@ -991,11 +1021,9 @@ void bta_hh_security_cmpl(tBTA_HH_DEV_CB* p_cb,
bta_hh_le_pri_service_discovery(p_cb);
}
} else {
- LOG_ERROR("Encryption failed status:%s btm_status:%s",
- bta_hh_status_text(p_cb->status).c_str(),
- btm_status_text(p_cb->btm_status).c_str());
- if (!(p_cb->status == BTA_HH_ERR_SEC &&
- p_cb->btm_status == BTM_ERR_PROCESSING))
+ APPL_TRACE_ERROR("%s() - encryption failed; status=0x%04x, reason=0x%04x",
+ __func__, p_cb->status, p_cb->reason);
+ if (!(p_cb->status == BTA_HH_ERR_SEC && p_cb->reason == BTM_ERR_PROCESSING))
bta_hh_le_api_disc_act(p_cb);
}
}
@@ -1009,8 +1037,7 @@ void bta_hh_security_cmpl(tBTA_HH_DEV_CB* p_cb,
* Returns
*
******************************************************************************/
-void bta_hh_le_notify_enc_cmpl(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_DATA* p_buf) {
+void bta_hh_le_notify_enc_cmpl(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_buf) {
if (p_cb == NULL || !p_cb->security_pending || p_buf == NULL ||
p_buf->le_enc_cmpl.client_if != bta_hh_cb.gatt_if) {
return;
@@ -1029,7 +1056,7 @@ void bta_hh_le_notify_enc_cmpl(tBTA_HH_DEV_CB* p_cb,
* Parameters:
*
******************************************************************************/
-static void bta_hh_clear_service_cache(tBTA_HH_DEV_CB* p_cb) {
+void bta_hh_clear_service_cache(tBTA_HH_DEV_CB* p_cb) {
tBTA_HH_LE_HID_SRVC* p_hid_srvc = &p_cb->hid_srvc;
p_cb->app_id = 0;
@@ -1049,30 +1076,46 @@ static void bta_hh_clear_service_cache(tBTA_HH_DEV_CB* p_cb) {
*
******************************************************************************/
void bta_hh_start_security(tBTA_HH_DEV_CB* p_cb,
- UNUSED_ATTR const tBTA_HH_DATA* p_buf) {
- if (BTM_SecIsSecurityPending(p_cb->addr)) {
- /* if security collision happened, wait for encryption done */
- p_cb->security_pending = true;
- return;
+ UNUSED_ATTR tBTA_HH_DATA* p_buf) {
+ uint8_t sec_flag = 0;
+ tBTM_SEC_DEV_REC* p_dev_rec;
+
+ p_dev_rec = btm_find_dev(p_cb->addr);
+ if (p_dev_rec) {
+ if (p_dev_rec->sec_state == BTM_SEC_STATE_ENCRYPTING ||
+ p_dev_rec->sec_state == BTM_SEC_STATE_AUTHENTICATING) {
+ /* if security collision happened, wait for encryption done */
+ p_cb->security_pending = true;
+ return;
+ }
}
+ /* verify bond */
+ BTM_GetSecurityFlagsByTransport(p_cb->addr, &sec_flag, BT_TRANSPORT_LE);
+
/* if link has been encrypted */
- if (BTM_IsEncrypted(p_cb->addr, BT_TRANSPORT_LE)) {
+ if (sec_flag & BTM_SEC_FLAG_ENCRYPTED) {
p_cb->status = BTA_HH_OK;
bta_hh_sm_execute(p_cb, BTA_HH_ENC_CMPL_EVT, NULL);
}
/* if bonded and link not encrypted */
- else if (BTM_IsLinkKeyKnown(p_cb->addr, BT_TRANSPORT_LE)) {
+ else if (sec_flag & BTM_SEC_FLAG_LKEY_KNOWN) {
+ sec_flag = BTM_BLE_SEC_ENCRYPT;
p_cb->status = BTA_HH_ERR_AUTH_FAILED;
- BTM_SetEncryption(p_cb->addr, BT_TRANSPORT_LE, bta_hh_le_encrypt_cback,
- NULL, BTM_BLE_SEC_ENCRYPT);
+ BTM_SetEncryption(p_cb->addr, BTA_TRANSPORT_LE, bta_hh_le_encrypt_cback,
+ NULL, sec_flag);
}
/* unbonded device, report security error here */
- else {
+ else if (p_cb->sec_mask != BTA_SEC_NONE) {
+ sec_flag = BTM_BLE_SEC_ENCRYPT_NO_MITM;
p_cb->status = BTA_HH_ERR_AUTH_FAILED;
bta_hh_clear_service_cache(p_cb);
- BTM_SetEncryption(p_cb->addr, BT_TRANSPORT_LE, bta_hh_le_encrypt_cback,
- NULL, BTM_BLE_SEC_ENCRYPT_NO_MITM);
+ BTM_SetEncryption(p_cb->addr, BTA_TRANSPORT_LE, bta_hh_le_encrypt_cback,
+ NULL, sec_flag);
+ }
+ /* otherwise let it go through */
+ else {
+ bta_hh_sm_execute(p_cb, BTA_HH_ENC_CMPL_EVT, NULL);
}
}
@@ -1085,9 +1128,9 @@ void bta_hh_start_security(tBTA_HH_DEV_CB* p_cb,
* Parameters:
*
******************************************************************************/
-void bta_hh_gatt_open(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_buf) {
- const tBTA_GATTC_OPEN* p_data = &p_buf->le_open;
- const uint8_t* p2;
+void bta_hh_gatt_open(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_buf) {
+ tBTA_GATTC_OPEN* p_data = &p_buf->le_open;
+ uint8_t* p2;
/* if received invalid callback data , ignore it */
if (p_cb == NULL || p_data == NULL) return;
@@ -1114,8 +1157,10 @@ void bta_hh_gatt_open(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_buf) {
BtaGattQueue::Clean(p_cb->conn_id);
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("hid_handle = %2x conn_id = %04x cb_index = %d",
p_cb->hid_handle, p_cb->conn_id, p_cb->index);
+#endif
bta_hh_sm_execute(p_cb, BTA_HH_START_ENC_EVT, NULL);
@@ -1131,36 +1176,28 @@ void bta_hh_gatt_open(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_buf) {
*
* Function bta_hh_le_close
*
- * Description This function converts the GATT close event and post it as a
- * BTA HH internal event.
+ * Description This function process the GATT close event and post it as a
+ * BTA HH internal event
+ *
+ * Parameters:
*
******************************************************************************/
-static void bta_hh_le_close(const tBTA_GATTC_CLOSE& gattc_data) {
- tBTA_HH_DEV_CB* p_cb = bta_hh_le_find_dev_cb_by_bda(gattc_data.remote_bda);
- if (p_cb == nullptr) {
- LOG_WARN("Received close event with unknown device:%s",
- PRIVATE_ADDRESS(gattc_data.remote_bda));
- return;
+void bta_hh_le_close(tBTA_GATTC_CLOSE* p_data) {
+ tBTA_HH_DEV_CB* p_dev_cb = bta_hh_le_find_dev_cb_by_bda(p_data->remote_bda);
+ uint16_t sm_event = BTA_HH_GATT_CLOSE_EVT;
+
+ if (p_dev_cb != NULL) {
+ tBTA_HH_LE_CLOSE* p_buf =
+ (tBTA_HH_LE_CLOSE*)osi_malloc(sizeof(tBTA_HH_LE_CLOSE));
+ p_buf->hdr.event = sm_event;
+ p_buf->hdr.layer_specific = (uint16_t)p_dev_cb->hid_handle;
+ p_buf->conn_id = p_data->conn_id;
+ p_buf->reason = p_data->reason;
+
+ p_dev_cb->conn_id = GATT_INVALID_CONN_ID;
+ p_dev_cb->security_pending = false;
+ bta_sys_sendmsg(p_buf);
}
- p_cb->conn_id = GATT_INVALID_CONN_ID;
- p_cb->security_pending = false;
-
- post_on_bt_main([=]() {
- const tBTA_HH_DATA data = {
- .le_close =
- {
- .conn_id = gattc_data.conn_id,
- .reason = gattc_data.reason,
- .hdr =
- {
- .event = BTA_HH_GATT_CLOSE_EVT,
- .layer_specific =
- static_cast<uint16_t>(p_cb->hid_handle),
- },
- },
- };
- bta_hh_sm_execute(p_cb, BTA_HH_GATT_CLOSE_EVT, &data);
- });
}
/*******************************************************************************
@@ -1172,8 +1209,7 @@ static void bta_hh_le_close(const tBTA_GATTC_CLOSE& gattc_data) {
* Parameters:
*
******************************************************************************/
-static void bta_hh_le_gatt_disc_cmpl(tBTA_HH_DEV_CB* p_cb,
- tBTA_HH_STATUS status) {
+void bta_hh_le_gatt_disc_cmpl(tBTA_HH_DEV_CB* p_cb, tBTA_HH_STATUS status) {
APPL_TRACE_DEBUG("bta_hh_le_gatt_disc_cmpl ");
/* if open sucessful or protocol mode not desired, keep the connection open
@@ -1256,8 +1292,10 @@ static void read_ext_rpt_ref_desc_cb(uint16_t conn_id, tGATT_STATUS status,
STREAM_TO_UINT16(p_dev_cb->hid_srvc.ext_rpt_ref, pp);
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("%s: External Report Reference UUID 0x%04x", __func__,
p_dev_cb->hid_srvc.ext_rpt_ref);
+#endif
}
static void read_report_ref_desc_cb(uint16_t conn_id, tGATT_STATUS status,
@@ -1288,9 +1326,9 @@ static void read_report_ref_desc_cb(uint16_t conn_id, tGATT_STATUS status,
if (p_rpt) bta_hh_le_save_report_ref(p_dev_cb, p_rpt, status, value, len);
}
-static void read_pref_conn_params_cb(uint16_t conn_id, tGATT_STATUS status,
- uint16_t handle, uint16_t len,
- uint8_t* value, void* data) {
+void read_pref_conn_params_cb(uint16_t conn_id, tGATT_STATUS status,
+ uint16_t handle, uint16_t len, uint8_t* value,
+ void* data) {
if (status != GATT_SUCCESS) {
APPL_TRACE_ERROR("%s: error: %d", __func__, status);
return;
@@ -1342,7 +1380,7 @@ static void read_pref_conn_params_cb(uint16_t conn_id, tGATT_STATUS status,
BTM_BleSetPrefConnParams(p_dev_cb->addr, min_interval, max_interval, latency,
timeout);
L2CA_UpdateBleConnParams(p_dev_cb->addr, min_interval, max_interval, latency,
- timeout, 0, 0);
+ timeout);
}
/*******************************************************************************
@@ -1363,8 +1401,8 @@ static void bta_hh_le_search_hid_chars(tBTA_HH_DEV_CB* p_dev_cb,
if (!charac.uuid.Is16Bit()) continue;
uint16_t uuid16 = charac.uuid.As16Bit();
- LOG_INFO("%s: %s %s", __func__, bta_hh_uuid_to_str(uuid16),
- charac.uuid.ToString().c_str());
+ LOG_DEBUG(LOG_TAG, "%s: %s %s", __func__, bta_hh_uuid_to_str(uuid16),
+ charac.uuid.ToString().c_str());
switch (uuid16) {
case GATT_UUID_HID_CONTROL_POINT:
@@ -1436,7 +1474,7 @@ static void bta_hh_le_search_hid_chars(tBTA_HH_DEV_CB* p_dev_cb,
* Parameters:
*
******************************************************************************/
-static void bta_hh_le_srvc_search_cmpl(tBTA_GATTC_SEARCH_CMPL* p_data) {
+void bta_hh_le_srvc_search_cmpl(tBTA_GATTC_SEARCH_CMPL* p_data) {
tBTA_HH_DEV_CB* p_dev_cb = bta_hh_le_find_dev_cb_by_conn_id(p_data->conn_id);
/* service search exception or no HID service is supported on remote */
@@ -1469,9 +1507,11 @@ static void bta_hh_le_srvc_search_cmpl(tBTA_GATTC_SEARCH_CMPL* p_data) {
APPL_TRACE_DEBUG("%s: have HID service inst_id= %d", __func__,
p_dev_cb->hid_srvc.srvc_inst_id);
} else if (service.uuid == Uuid::From16Bit(UUID_SERVCLASS_SCAN_PARAM)) {
+ p_dev_cb->scan_refresh_char_handle = 0;
for (const gatt::Characteristic& charac : service.characteristics) {
if (charac.uuid == Uuid::From16Bit(GATT_UUID_SCAN_REFRESH)) {
+ p_dev_cb->scan_refresh_char_handle = charac.value_handle;
if (charac.properties & GATT_CHAR_PROP_BIT_NOTIFY)
p_dev_cb->scps_notify |= BTA_HH_LE_SCPS_NOTIFY_SPT;
@@ -1508,7 +1548,7 @@ static void bta_hh_le_srvc_search_cmpl(tBTA_GATTC_SEARCH_CMPL* p_data) {
* Parameters:
*
******************************************************************************/
-static void bta_hh_le_input_rpt_notify(tBTA_GATTC_NOTIFY* p_data) {
+void bta_hh_le_input_rpt_notify(tBTA_GATTC_NOTIFY* p_data) {
tBTA_HH_DEV_CB* p_dev_cb = bta_hh_le_find_dev_cb_by_conn_id(p_data->conn_id);
uint8_t app_id;
uint8_t* p_buf;
@@ -1580,7 +1620,7 @@ static void bta_hh_le_input_rpt_notify(tBTA_GATTC_NOTIFY* p_data) {
* Returns void
*
******************************************************************************/
-void bta_hh_le_open_fail(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_le_open_fail(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
tBTA_HH_CONN conn_dat;
/* open failure in the middle of service discovery, clear all services */
@@ -1594,10 +1634,13 @@ void bta_hh_le_open_fail(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
conn_dat.bda = p_cb->addr;
conn_dat.le_hid = true;
conn_dat.scps_supported = p_cb->scps_supported;
- conn_dat.status = p_cb->status;
- if (p_data->le_close.reason != GATT_CONN_OK) {
- conn_dat.status = BTA_HH_ERR;
- }
+
+ if (p_cb->status == BTA_HH_OK)
+ conn_dat.status = (p_data->le_close.reason == GATT_CONN_UNKNOWN)
+ ? p_cb->status
+ : BTA_HH_ERR;
+ else
+ conn_dat.status = p_cb->status;
/* Report OPEN fail event */
(*bta_hh_cb.p_cback)(BTA_HH_OPEN_EVT, (tBTA_HH*)&conn_dat);
@@ -1607,13 +1650,14 @@ void bta_hh_le_open_fail(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
*
* Function bta_hh_gatt_close
*
- * Description action function to process the GATT close in the state
+ * Description action function to process the GATT close int he state
* machine.
*
* Returns void
*
******************************************************************************/
-void bta_hh_gatt_close(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_gatt_close(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
+ tBTA_HH_CBDATA disc_dat = {BTA_HH_OK, 0};
/* deregister all notification */
bta_hh_le_deregister_input_notif(p_cb);
@@ -1622,19 +1666,23 @@ void bta_hh_gatt_close(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
/* update total conn number */
bta_hh_cb.cnt_num--;
- tBTA_HH_CBDATA disc_dat = {
- .status = p_cb->status,
- .handle = p_cb->hid_handle,
- };
+ disc_dat.handle = p_cb->hid_handle;
+ disc_dat.status = p_cb->status;
+
(*bta_hh_cb.p_cback)(BTA_HH_CLOSE_EVT, (tBTA_HH*)&disc_dat);
/* if no connection is active and HH disable is signaled, disable service */
if (bta_hh_cb.cnt_num == 0 && bta_hh_cb.w4_disable) {
bta_hh_disc_cmpl();
- } else if (kBTA_HH_LE_RECONN &&
- p_data->le_close.reason == GATT_CONN_TIMEOUT) {
- bta_hh_le_add_dev_bg_conn(p_cb, false);
+ } else {
+#if (BTA_HH_LE_RECONN == TRUE)
+ if (p_data->le_close.reason == GATT_CONN_TIMEOUT) {
+ bta_hh_le_add_dev_bg_conn(p_cb, false);
+ }
+#endif
}
+
+ return;
}
/*******************************************************************************
@@ -1647,16 +1695,13 @@ void bta_hh_gatt_close(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
*
******************************************************************************/
void bta_hh_le_api_disc_act(tBTA_HH_DEV_CB* p_cb) {
- if (p_cb->conn_id == GATT_INVALID_CONN_ID) {
- LOG_ERROR("Tried to disconnect HID device with invalid id");
- return;
+ if (p_cb->conn_id != GATT_INVALID_CONN_ID) {
+ BtaGattQueue::Clean(p_cb->conn_id);
+ BTA_GATTC_Close(p_cb->conn_id);
+ /* remove device from background connection if intended to disconnect,
+ do not allow reconnection */
+ bta_hh_le_remove_dev_bg_conn(p_cb);
}
-
- BtaGattQueue::Clean(p_cb->conn_id);
- BTA_GATTC_Close(p_cb->conn_id);
- /* remove device from background connection if intended to disconnect,
- do not allow reconnection */
- bta_hh_le_remove_dev_bg_conn(p_cb);
}
/*******************************************************************************
@@ -1744,8 +1789,8 @@ static void read_report_cb(uint16_t conn_id, tGATT_STATUS status,
* Returns void
*
******************************************************************************/
-static void bta_hh_le_get_rpt(tBTA_HH_DEV_CB* p_cb, tBTA_HH_RPT_TYPE r_type,
- uint8_t rpt_id) {
+void bta_hh_le_get_rpt(tBTA_HH_DEV_CB* p_cb, tBTA_HH_RPT_TYPE r_type,
+ uint8_t rpt_id) {
tBTA_HH_LE_RPT* p_rpt = bta_hh_le_find_rpt_by_idtype(
p_cb->hid_srvc.report, p_cb->mode, r_type, rpt_id);
@@ -1767,13 +1812,12 @@ static void write_report_cb(uint16_t conn_id, tGATT_STATUS status,
if (cb_evt == 0) return;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("bta_hh_le_write_cmpl w4_evt: %d", p_dev_cb->w4_evt);
+#endif
const gatt::Characteristic* p_char =
BTA_GATTC_GetCharacteristic(conn_id, handle);
-
- if (p_char == nullptr) return;
-
uint16_t uuid = p_char->uuid.As16Bit();
if (uuid != GATT_UUID_HID_REPORT && uuid != GATT_UUID_HID_BT_KB_INPUT &&
uuid != GATT_UUID_HID_BT_MOUSE_INPUT &&
@@ -1796,8 +1840,8 @@ static void write_report_cb(uint16_t conn_id, tGATT_STATUS status,
* Returns void
*
******************************************************************************/
-static void bta_hh_le_write_rpt(tBTA_HH_DEV_CB* p_cb, tBTA_HH_RPT_TYPE r_type,
- BT_HDR* p_buf, uint16_t w4_evt) {
+void bta_hh_le_write_rpt(tBTA_HH_DEV_CB* p_cb, tBTA_HH_RPT_TYPE r_type,
+ BT_HDR* p_buf, uint16_t w4_evt) {
tBTA_HH_LE_RPT* p_rpt;
uint8_t rpt_id;
@@ -1842,8 +1886,8 @@ static void bta_hh_le_write_rpt(tBTA_HH_DEV_CB* p_cb, tBTA_HH_RPT_TYPE r_type,
* Returns void
*
******************************************************************************/
-static void bta_hh_le_suspend(tBTA_HH_DEV_CB* p_cb,
- tBTA_HH_TRANS_CTRL_TYPE ctrl_type) {
+void bta_hh_le_suspend(tBTA_HH_DEV_CB* p_cb,
+ tBTA_HH_TRANS_CTRL_TYPE ctrl_type) {
ctrl_type -= BTA_HH_CTRL_SUSPEND;
// We don't care about response
@@ -1861,7 +1905,7 @@ static void bta_hh_le_suspend(tBTA_HH_DEV_CB* p_cb,
* Returns void
*
******************************************************************************/
-void bta_hh_le_write_dev_act(tBTA_HH_DEV_CB* p_cb, const tBTA_HH_DATA* p_data) {
+void bta_hh_le_write_dev_act(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data) {
switch (p_data->api_sndcmd.t_type) {
case HID_TRANS_SET_PROTOCOL:
p_cb->w4_evt = BTA_HH_SET_PROTO_EVT;
@@ -1933,16 +1977,22 @@ void bta_hh_le_get_dscp_act(tBTA_HH_DEV_CB* p_cb) {
*
******************************************************************************/
static void bta_hh_le_add_dev_bg_conn(tBTA_HH_DEV_CB* p_cb, bool check_bond) {
+ uint8_t sec_flag = 0;
bool to_add = true;
if (check_bond) {
/* start reconnection if remote is a bonded device */
- if (!BTM_IsLinkKeyKnown(p_cb->addr, BT_TRANSPORT_LE)) to_add = false;
+ /* verify bond */
+ BTM_GetSecurityFlagsByTransport(p_cb->addr, &sec_flag, BT_TRANSPORT_LE);
+
+ if ((sec_flag & BTM_SEC_FLAG_LKEY_KNOWN) == 0) to_add = false;
}
- if (!p_cb->in_bg_conn && to_add) {
+ if (/*p_cb->dscp_info.flag & BTA_HH_LE_NORMAL_CONN &&*/
+ !p_cb->in_bg_conn && to_add) {
/* add device into BG connection to accept remote initiated connection */
- BTA_GATTC_Open(bta_hh_cb.gatt_if, p_cb->addr, false, false);
+ BTA_GATTC_Open(bta_hh_cb.gatt_if, p_cb->addr, false, GATT_TRANSPORT_LE,
+ false);
p_cb->in_bg_conn = true;
}
return;
@@ -1960,7 +2010,7 @@ static void bta_hh_le_add_dev_bg_conn(tBTA_HH_DEV_CB* p_cb, bool check_bond) {
*
******************************************************************************/
uint8_t bta_hh_le_add_device(tBTA_HH_DEV_CB* p_cb,
- const tBTA_HH_MAINT_DEV* p_dev_info) {
+ tBTA_HH_MAINT_DEV* p_dev_info) {
p_cb->hid_handle = bta_hh_le_get_le_dev_hdl(p_cb->index);
if (p_cb->hid_handle == BTA_HH_INVALID_HANDLE) return BTA_HH_INVALID_HANDLE;
bta_hh_cb.le_cb_index[BTA_HH_GET_LE_CB_IDX(p_cb->hid_handle)] = p_cb->index;
@@ -1994,8 +2044,6 @@ uint8_t bta_hh_le_add_device(tBTA_HH_DEV_CB* p_cb,
******************************************************************************/
void bta_hh_le_remove_dev_bg_conn(tBTA_HH_DEV_CB* p_dev_cb) {
if (p_dev_cb->in_bg_conn) {
- LOG_DEBUG("Removing from background connection device:%s",
- PRIVATE_ADDRESS(p_dev_cb->addr));
p_dev_cb->in_bg_conn = false;
BTA_GATTC_CancelOpen(bta_hh_cb.gatt_if, p_dev_cb->addr, false);
@@ -2016,13 +2064,14 @@ void bta_hh_le_remove_dev_bg_conn(tBTA_HH_DEV_CB* p_dev_cb) {
******************************************************************************/
static void bta_hh_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
tBTA_HH_DEV_CB* p_dev_cb;
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("bta_hh_gattc_callback event = %d", event);
+#endif
if (p_data == NULL) return;
switch (event) {
case BTA_GATTC_DEREG_EVT: /* 1 */
- bta_hh_cleanup_disable(
- static_cast<tBTA_HH_STATUS>(p_data->reg_oper.status));
+ bta_hh_cleanup_disable(p_data->reg_oper.status);
break;
case BTA_GATTC_OPEN_EVT: /* 2 */
@@ -2034,7 +2083,7 @@ static void bta_hh_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
break;
case BTA_GATTC_CLOSE_EVT: /* 5 */
- bta_hh_le_close(p_data->close);
+ bta_hh_le_close(&p_data->close);
break;
case BTA_GATTC_SEARCH_CMPL_EVT: /* 6 */
@@ -2058,6 +2107,54 @@ static void bta_hh_gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
}
}
+static void read_report_descriptor_ccc_cb(uint16_t conn_id, tGATT_STATUS status,
+ uint16_t handle, uint16_t len,
+ uint8_t* value, void* data) {
+ tBTA_HH_LE_RPT* p_rpt = (tBTA_HH_LE_RPT*)data;
+ uint8_t* pp = value;
+ STREAM_TO_UINT16(p_rpt->client_cfg_value, pp);
+
+ APPL_TRACE_DEBUG("Read Client Configuration: 0x%04x",
+ p_rpt->client_cfg_value);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_hh_le_hid_read_rpt_clt_cfg
+ *
+ * Description a test command to read report descriptor client
+ * configuration
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_hh_le_hid_read_rpt_clt_cfg(const RawAddress& bd_addr, uint8_t rpt_id) {
+ tBTA_HH_DEV_CB* p_cb = NULL;
+ tBTA_HH_LE_RPT* p_rpt;
+ uint8_t index = BTA_HH_IDX_INVALID;
+
+ index = bta_hh_find_cb(bd_addr);
+ if (index == BTA_HH_IDX_INVALID) {
+ APPL_TRACE_ERROR("%s: unknown device", __func__);
+ return;
+ }
+
+ p_cb = &bta_hh_cb.kdev[index];
+
+ p_rpt = bta_hh_le_find_rpt_by_idtype(p_cb->hid_srvc.report, p_cb->mode,
+ BTA_HH_RPTT_INPUT, rpt_id);
+
+ if (p_rpt == NULL) {
+ APPL_TRACE_ERROR("%s: no matching report", __func__);
+ return;
+ }
+
+ bta_hh_le_read_char_descriptor(p_cb, p_rpt->char_inst_id,
+ GATT_UUID_CHAR_CLIENT_CONFIG,
+ read_report_descriptor_ccc_cb, p_rpt);
+ return;
+}
+
/*******************************************************************************
*
* Function bta_hh_process_cache_rpt
@@ -2102,3 +2199,5 @@ static void bta_hh_process_cache_rpt(tBTA_HH_DEV_CB* p_cb,
}
}
}
+
+#endif
diff --git a/bta/hh/bta_hh_main.cc b/bta/hh/bta_hh_main.cc
index f704fe65c..2528391bb 100644
--- a/bta/hh/bta_hh_main.cc
+++ b/bta/hh/bta_hh_main.cc
@@ -22,14 +22,187 @@
*
******************************************************************************/
-#include <string.h> // memset
-#include <cstdint>
-
-#include "bt_target.h" // Must be first to define build configuration
+#include "bt_target.h"
#if (BTA_HH_INCLUDED == TRUE)
-#include "bta/hh/bta_hh_int.h"
+#include <string.h>
+
+#include "bt_common.h"
+#include "bta_hh_api.h"
+#include "bta_hh_int.h"
+
+/*****************************************************************************
+ * Constants and types
+ ****************************************************************************/
+
+/* state machine action enumeration list */
+enum {
+ BTA_HH_API_DISC_ACT, /* HID host process API close action */
+ BTA_HH_OPEN_ACT, /* HID host process BTA_HH_EVT_OPEN */
+ BTA_HH_CLOSE_ACT, /* HID host process BTA_HH_EVT_CLOSE */
+ BTA_HH_DATA_ACT, /* HID host receive data report */
+ BTA_HH_CTRL_DAT_ACT,
+ BTA_HH_HANDSK_ACT,
+ BTA_HH_START_SDP, /* HID host inquery */
+ BTA_HH_SDP_CMPL,
+ BTA_HH_WRITE_DEV_ACT,
+ BTA_HH_GET_DSCP_ACT,
+ BTA_HH_MAINT_DEV_ACT,
+ BTA_HH_OPEN_CMPL_ACT,
+ BTA_HH_OPEN_FAILURE,
+#if (BTA_HH_LE_INCLUDED == TRUE)
+ BTA_HH_GATT_CLOSE,
+ BTA_HH_LE_OPEN_FAIL,
+ BTA_HH_GATT_OPEN,
+ BTA_HH_START_SEC,
+ BTA_HH_SEC_CMPL,
+ BTA_HH_GATT_ENC_CMPL,
+#endif
+ BTA_HH_NUM_ACTIONS
+};
+
+#define BTA_HH_IGNORE BTA_HH_NUM_ACTIONS
+
+/* type for action functions */
+typedef void (*tBTA_HH_ACTION)(tBTA_HH_DEV_CB* p_cb, tBTA_HH_DATA* p_data);
+
+/* action functions */
+const tBTA_HH_ACTION bta_hh_action[] = {
+ bta_hh_api_disc_act, bta_hh_open_act, bta_hh_close_act, bta_hh_data_act,
+ bta_hh_ctrl_dat_act, bta_hh_handsk_act, bta_hh_start_sdp, bta_hh_sdp_cmpl,
+ bta_hh_write_dev_act, bta_hh_get_dscp_act, bta_hh_maint_dev_act,
+ bta_hh_open_cmpl_act, bta_hh_open_failure
+#if (BTA_HH_LE_INCLUDED == TRUE)
+ ,
+ bta_hh_gatt_close, bta_hh_le_open_fail, bta_hh_gatt_open,
+ bta_hh_start_security, bta_hh_security_cmpl, bta_hh_le_notify_enc_cmpl
+#endif
+};
+
+/* state table information */
+#define BTA_HH_ACTION 0 /* position of action */
+#define BTA_HH_NEXT_STATE 1 /* position of next state */
+#define BTA_HH_NUM_COLS 2 /* number of columns */
+
+/* state table for idle state */
+const uint8_t bta_hh_st_idle[][BTA_HH_NUM_COLS] = {
+ /* Event Action Next state */
+ /* BTA_HH_API_OPEN_EVT */ {BTA_HH_START_SDP, BTA_HH_W4_CONN_ST},
+ /* BTA_HH_API_CLOSE_EVT */ {BTA_HH_IGNORE, BTA_HH_IDLE_ST},
+ /* BTA_HH_INT_OPEN_EVT */ {BTA_HH_OPEN_ACT, BTA_HH_W4_CONN_ST},
+ /* BTA_HH_INT_CLOSE_EVT */ {BTA_HH_CLOSE_ACT, BTA_HH_IDLE_ST},
+ /* BTA_HH_INT_DATA_EVT */ {BTA_HH_IGNORE, BTA_HH_IDLE_ST},
+ /* BTA_HH_INT_CTRL_DATA */ {BTA_HH_IGNORE, BTA_HH_IDLE_ST},
+ /* BTA_HH_INT_HANDSK_EVT */ {BTA_HH_IGNORE, BTA_HH_IDLE_ST},
+ /* BTA_HH_SDP_CMPL_EVT */ {BTA_HH_IGNORE, BTA_HH_IDLE_ST},
+ /* BTA_HH_API_WRITE_DEV_EVT */ {BTA_HH_IGNORE, BTA_HH_IDLE_ST},
+ /* BTA_HH_API_GET_DSCP_EVT */ {BTA_HH_IGNORE, BTA_HH_IDLE_ST},
+ /* BTA_HH_API_MAINT_DEV_EVT */ {BTA_HH_MAINT_DEV_ACT, BTA_HH_IDLE_ST},
+ /* BTA_HH_OPEN_CMPL_EVT */ {BTA_HH_OPEN_CMPL_ACT, BTA_HH_CONN_ST}
+#if (BTA_HH_LE_INCLUDED == TRUE)
+ /* BTA_HH_GATT_CLOSE_EVT */,
+ {BTA_HH_IGNORE, BTA_HH_IDLE_ST}
+ /* BTA_HH_GATT_OPEN_EVT */,
+ {BTA_HH_GATT_OPEN, BTA_HH_W4_CONN_ST}
+ /* BTA_HH_START_ENC_EVT */,
+ {BTA_HH_IGNORE, BTA_HH_IDLE_ST}
+ /* BTA_HH_ENC_CMPL_EVT */,
+ {BTA_HH_IGNORE, BTA_HH_IDLE_ST}
+ /* BTA_HH_GATT_ENC_CMPL_EVT */,
+ {BTA_HH_IGNORE, BTA_HH_IDLE_ST}
+#endif
+
+};
+
+const uint8_t bta_hh_st_w4_conn[][BTA_HH_NUM_COLS] = {
+ /* Event Action Next state */
+ /* BTA_HH_API_OPEN_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_CONN_ST},
+ /* BTA_HH_API_CLOSE_EVT */ {BTA_HH_IGNORE, BTA_HH_IDLE_ST},
+ /* BTA_HH_INT_OPEN_EVT */ {BTA_HH_OPEN_ACT, BTA_HH_W4_CONN_ST},
+ /* BTA_HH_INT_CLOSE_EVT */ {BTA_HH_OPEN_FAILURE, BTA_HH_IDLE_ST},
+ /* BTA_HH_INT_DATA_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_CONN_ST},
+ /* BTA_HH_INT_CTRL_DATA */ {BTA_HH_IGNORE, BTA_HH_W4_CONN_ST},
+ /* BTA_HH_INT_HANDSK_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_CONN_ST},
+ /* BTA_HH_SDP_CMPL_EVT */ {BTA_HH_SDP_CMPL, BTA_HH_W4_CONN_ST},
+ /* BTA_HH_API_WRITE_DEV_EVT */ {BTA_HH_WRITE_DEV_ACT, BTA_HH_W4_CONN_ST},
+ /* BTA_HH_API_GET_DSCP_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_CONN_ST},
+ /* BTA_HH_API_MAINT_DEV_EVT */ {BTA_HH_MAINT_DEV_ACT, BTA_HH_IDLE_ST},
+ /* BTA_HH_OPEN_CMPL_EVT */ {BTA_HH_OPEN_CMPL_ACT, BTA_HH_CONN_ST}
+#if (BTA_HH_LE_INCLUDED == TRUE)
+ /* BTA_HH_GATT_CLOSE_EVT */,
+ {BTA_HH_LE_OPEN_FAIL, BTA_HH_IDLE_ST}
+ /* BTA_HH_GATT_OPEN_EVT */,
+ {BTA_HH_GATT_OPEN, BTA_HH_W4_CONN_ST}
+ /* BTA_HH_START_ENC_EVT */,
+ {BTA_HH_START_SEC, BTA_HH_W4_SEC}
+ /* BTA_HH_ENC_CMPL_EVT */,
+ {BTA_HH_IGNORE, BTA_HH_W4_CONN_ST}
+ /* BTA_HH_GATT_ENC_CMPL_EVT */,
+ {BTA_HH_IGNORE, BTA_HH_W4_CONN_ST}
+#endif
+};
+
+const uint8_t bta_hh_st_connected[][BTA_HH_NUM_COLS] = {
+ /* Event Action Next state */
+ /* BTA_HH_API_OPEN_EVT */ {BTA_HH_IGNORE, BTA_HH_CONN_ST},
+ /* BTA_HH_API_CLOSE_EVT */ {BTA_HH_API_DISC_ACT, BTA_HH_CONN_ST},
+ /* BTA_HH_INT_OPEN_EVT */ {BTA_HH_OPEN_ACT, BTA_HH_CONN_ST},
+ /* BTA_HH_INT_CLOSE_EVT */ {BTA_HH_CLOSE_ACT, BTA_HH_IDLE_ST},
+ /* BTA_HH_INT_DATA_EVT */ {BTA_HH_DATA_ACT, BTA_HH_CONN_ST},
+ /* BTA_HH_INT_CTRL_DATA */ {BTA_HH_CTRL_DAT_ACT, BTA_HH_CONN_ST},
+ /* BTA_HH_INT_HANDSK_EVT */ {BTA_HH_HANDSK_ACT, BTA_HH_CONN_ST},
+ /* BTA_HH_SDP_CMPL_EVT */ {BTA_HH_IGNORE, BTA_HH_CONN_ST},
+ /* BTA_HH_API_WRITE_DEV_EVT */ {BTA_HH_WRITE_DEV_ACT, BTA_HH_CONN_ST},
+ /* BTA_HH_API_GET_DSCP_EVT */ {BTA_HH_GET_DSCP_ACT, BTA_HH_CONN_ST},
+ /* BTA_HH_API_MAINT_DEV_EVT */ {BTA_HH_MAINT_DEV_ACT, BTA_HH_CONN_ST},
+ /* BTA_HH_OPEN_CMPL_EVT */ {BTA_HH_IGNORE, BTA_HH_CONN_ST}
+#if (BTA_HH_LE_INCLUDED == TRUE)
+ /* BTA_HH_GATT_CLOSE_EVT */,
+ {BTA_HH_GATT_CLOSE, BTA_HH_IDLE_ST}
+ /* BTA_HH_GATT_OPEN_EVT */,
+ {BTA_HH_IGNORE, BTA_HH_CONN_ST}
+ /* BTA_HH_START_ENC_EVT */,
+ {BTA_HH_IGNORE, BTA_HH_CONN_ST}
+ /* BTA_HH_ENC_CMPL_EVT */,
+ {BTA_HH_IGNORE, BTA_HH_CONN_ST}
+ /* BTA_HH_GATT_ENC_CMPL_EVT */,
+ {BTA_HH_IGNORE, BTA_HH_CONN_ST}
+#endif
+};
+#if (BTA_HH_LE_INCLUDED == TRUE)
+const uint8_t bta_hh_st_w4_sec[][BTA_HH_NUM_COLS] = {
+ /* Event Action Next state */
+ /* BTA_HH_API_OPEN_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_SEC},
+ /* BTA_HH_API_CLOSE_EVT */ {BTA_HH_API_DISC_ACT, BTA_HH_W4_SEC},
+ /* BTA_HH_INT_OPEN_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_SEC},
+ /* BTA_HH_INT_CLOSE_EVT */ {BTA_HH_OPEN_FAILURE, BTA_HH_IDLE_ST},
+ /* BTA_HH_INT_DATA_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_SEC},
+ /* BTA_HH_INT_CTRL_DATA */ {BTA_HH_IGNORE, BTA_HH_W4_SEC},
+ /* BTA_HH_INT_HANDSK_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_SEC},
+ /* BTA_HH_SDP_CMPL_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_SEC},
+ /* BTA_HH_API_WRITE_DEV_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_SEC},
+ /* BTA_HH_API_GET_DSCP_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_SEC},
+ /* BTA_HH_API_MAINT_DEV_EVT */ {BTA_HH_MAINT_DEV_ACT, BTA_HH_W4_SEC},
+ /* BTA_HH_OPEN_CMPL_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_SEC},
+ /* BTA_HH_GATT_CLOSE_EVT */ {BTA_HH_LE_OPEN_FAIL, BTA_HH_IDLE_ST},
+ /* BTA_HH_GATT_OPEN_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_SEC},
+ /* BTA_HH_START_ENC_EVT */ {BTA_HH_IGNORE, BTA_HH_W4_SEC},
+ /* BTA_HH_ENC_CMPL_EVT */ {BTA_HH_SEC_CMPL, BTA_HH_W4_CONN_ST},
+ /* BTA_HH_GATT_ENC_CMPL_EVT */ {BTA_HH_GATT_ENC_CMPL, BTA_HH_W4_SEC}};
+#endif
+
+/* type for state table */
+typedef const uint8_t (*tBTA_HH_ST_TBL)[BTA_HH_NUM_COLS];
+
+/* state table */
+const tBTA_HH_ST_TBL bta_hh_st_tbl[] = {bta_hh_st_idle, bta_hh_st_w4_conn,
+ bta_hh_st_connected
+#if (BTA_HH_LE_INCLUDED == TRUE)
+ ,
+ bta_hh_st_w4_sec
+#endif
+};
/*****************************************************************************
* Global data
@@ -39,140 +212,10 @@ tBTA_HH_CB bta_hh_cb;
/*****************************************************************************
* Static functions
****************************************************************************/
+#if (BTA_HH_DEBUG == TRUE)
static const char* bta_hh_evt_code(tBTA_HH_INT_EVT evt_code);
static const char* bta_hh_state_code(tBTA_HH_STATE state_code);
-
-static void bta_hh_better_state_machine(tBTA_HH_DEV_CB* p_cb, uint16_t event,
- const tBTA_HH_DATA* p_data) {
- switch (p_cb->state) {
- case BTA_HH_IDLE_ST:
- switch (event) {
- case BTA_HH_API_OPEN_EVT:
- p_cb->state = BTA_HH_W4_CONN_ST;
- bta_hh_start_sdp(p_cb, p_data);
- break;
- case BTA_HH_INT_OPEN_EVT:
- p_cb->state = BTA_HH_W4_CONN_ST;
- bta_hh_open_act(p_cb, p_data);
- break;
- case BTA_HH_INT_CLOSE_EVT:
- bta_hh_close_act(p_cb, p_data);
- break;
- case BTA_HH_API_MAINT_DEV_EVT:
- bta_hh_maint_dev_act(p_cb, p_data);
- break;
- case BTA_HH_OPEN_CMPL_EVT:
- p_cb->state = BTA_HH_CONN_ST;
- bta_hh_open_cmpl_act(p_cb, p_data);
- break;
- case BTA_HH_GATT_OPEN_EVT:
- p_cb->state = BTA_HH_W4_CONN_ST;
- bta_hh_gatt_open(p_cb, p_data);
- break;
- }
- break;
- case BTA_HH_W4_CONN_ST:
- switch (event) {
- case BTA_HH_API_CLOSE_EVT:
- p_cb->state = BTA_HH_IDLE_ST;
- break;
- case BTA_HH_INT_OPEN_EVT:
- bta_hh_open_act(p_cb, p_data);
- break;
- case BTA_HH_INT_CLOSE_EVT:
- p_cb->state = BTA_HH_IDLE_ST;
- bta_hh_open_failure(p_cb, p_data);
- break;
- case BTA_HH_SDP_CMPL_EVT:
- bta_hh_sdp_cmpl(p_cb, p_data);
- break;
- case BTA_HH_API_WRITE_DEV_EVT:
- bta_hh_write_dev_act(p_cb, p_data);
- break;
- case BTA_HH_API_MAINT_DEV_EVT:
- p_cb->state = BTA_HH_IDLE_ST;
- bta_hh_maint_dev_act(p_cb, p_data);
- break;
- case BTA_HH_OPEN_CMPL_EVT:
- p_cb->state = BTA_HH_CONN_ST;
- bta_hh_open_cmpl_act(p_cb, p_data);
- break;
- case BTA_HH_GATT_CLOSE_EVT:
- p_cb->state = BTA_HH_IDLE_ST;
- bta_hh_le_open_fail(p_cb, p_data);
- break;
- case BTA_HH_GATT_OPEN_EVT:
- bta_hh_gatt_open(p_cb, p_data);
- break;
- case BTA_HH_START_ENC_EVT:
- p_cb->state = BTA_HH_W4_SEC;
- bta_hh_start_security(p_cb, p_data);
- break;
- }
- break;
- case BTA_HH_CONN_ST:
- switch (event) {
- case BTA_HH_API_CLOSE_EVT:
- bta_hh_api_disc_act(p_cb, p_data);
- break;
- case BTA_HH_INT_OPEN_EVT:
- bta_hh_open_act(p_cb, p_data);
- break;
- case BTA_HH_INT_CLOSE_EVT:
- p_cb->state = BTA_HH_IDLE_ST;
- bta_hh_close_act(p_cb, p_data);
- break;
- case BTA_HH_INT_DATA_EVT:
- bta_hh_data_act(p_cb, p_data);
- break;
- case BTA_HH_INT_CTRL_DATA:
- bta_hh_ctrl_dat_act(p_cb, p_data);
- break;
- case BTA_HH_INT_HANDSK_EVT:
- bta_hh_handsk_act(p_cb, p_data);
- break;
- case BTA_HH_API_WRITE_DEV_EVT:
- bta_hh_write_dev_act(p_cb, p_data);
- break;
- case BTA_HH_API_GET_DSCP_EVT:
- bta_hh_get_dscp_act(p_cb, p_data);
- break;
- case BTA_HH_API_MAINT_DEV_EVT:
- bta_hh_maint_dev_act(p_cb, p_data);
- break;
- case BTA_HH_GATT_CLOSE_EVT:
- p_cb->state = BTA_HH_IDLE_ST;
- bta_hh_gatt_close(p_cb, p_data);
- break;
- }
- break;
- case BTA_HH_W4_SEC:
- switch (event) {
- case BTA_HH_API_CLOSE_EVT:
- bta_hh_api_disc_act(p_cb, p_data);
- break;
- case BTA_HH_INT_CLOSE_EVT:
- p_cb->state = BTA_HH_IDLE_ST;
- bta_hh_open_failure(p_cb, p_data);
- break;
- case BTA_HH_API_MAINT_DEV_EVT:
- bta_hh_maint_dev_act(p_cb, p_data);
- break;
- case BTA_HH_GATT_CLOSE_EVT:
- p_cb->state = BTA_HH_IDLE_ST;
- bta_hh_le_open_fail(p_cb, p_data);
- break;
- case BTA_HH_ENC_CMPL_EVT:
- p_cb->state = BTA_HH_W4_CONN_ST;
- bta_hh_security_cmpl(p_cb, p_data);
- break;
- case BTA_HH_GATT_ENC_CMPL_EVT:
- bta_hh_le_notify_enc_cmpl(p_cb, p_data);
- break;
- }
- break;
- }
-}
+#endif
/*******************************************************************************
*
@@ -185,11 +228,15 @@ static void bta_hh_better_state_machine(tBTA_HH_DEV_CB* p_cb, uint16_t event,
*
******************************************************************************/
void bta_hh_sm_execute(tBTA_HH_DEV_CB* p_cb, uint16_t event,
- const tBTA_HH_DATA* p_data) {
+ tBTA_HH_DATA* p_data) {
+ tBTA_HH_ST_TBL state_table;
+ uint8_t action;
tBTA_HH cback_data;
tBTA_HH_EVT cback_event = 0;
+#if (BTA_HH_DEBUG == TRUE)
tBTA_HH_STATE in_state;
- tBTA_HH_INT_EVT debug_event = static_cast<tBTA_HH_INT_EVT>(event);
+ uint16_t debug_event = event;
+#endif
memset(&cback_data, 0, sizeof(tBTA_HH));
@@ -221,8 +268,8 @@ void bta_hh_sm_execute(tBTA_HH_DEV_CB* p_cb, uint16_t event,
}
break;
case BTA_HH_API_WRITE_DEV_EVT:
- cback_event = (p_data->api_sndcmd.t_type - HID_TRANS_GET_REPORT) +
- BTA_HH_GET_RPT_EVT;
+ cback_event = (p_data->api_sndcmd.t_type - BTA_HH_FST_BTE_TRANS_EVT) +
+ BTA_HH_FST_TRANS_CB_EVT;
osi_free_and_reset((void**)&p_data->api_sndcmd.p_data);
if (p_data->api_sndcmd.t_type == HID_TRANS_SET_PROTOCOL ||
p_data->api_sndcmd.t_type == HID_TRANS_SET_REPORT ||
@@ -267,10 +314,12 @@ void bta_hh_sm_execute(tBTA_HH_DEV_CB* p_cb, uint16_t event,
}
/* corresponding CB is found, go to state machine */
else {
+#if (BTA_HH_DEBUG == TRUE)
in_state = p_cb->state;
APPL_TRACE_EVENT("bta_hh_sm_execute: State 0x%02x [%s], Event [%s]",
in_state, bta_hh_state_code(in_state),
bta_hh_evt_code(debug_event));
+#endif
if ((p_cb->state == BTA_HH_NULL_ST) || (p_cb->state >= BTA_HH_INVALID_ST)) {
APPL_TRACE_ERROR(
@@ -278,17 +327,29 @@ void bta_hh_sm_execute(tBTA_HH_DEV_CB* p_cb, uint16_t event,
p_cb->state, event);
return;
}
+ state_table = bta_hh_st_tbl[p_cb->state - 1];
+
+ event &= 0xff;
- bta_hh_better_state_machine(p_cb, event, p_data);
+ p_cb->state = state_table[event][BTA_HH_NEXT_STATE];
+ action = state_table[event][BTA_HH_ACTION];
+ if (action != BTA_HH_IGNORE) {
+ (*bta_hh_action[action])(p_cb, p_data);
+ }
+
+#if (BTA_HH_DEBUG == TRUE)
if (in_state != p_cb->state) {
- LOG_DEBUG("HHID State Change: [%s] -> [%s] after Event [%s]",
- bta_hh_state_code(in_state), bta_hh_state_code(p_cb->state),
- bta_hh_evt_code(debug_event));
+ APPL_TRACE_DEBUG("HH State Change: [%s] -> [%s] after Event [%s]",
+ bta_hh_state_code(in_state),
+ bta_hh_state_code(p_cb->state),
+ bta_hh_evt_code(debug_event));
}
+#endif
}
-}
+ return;
+}
/*******************************************************************************
*
* Function bta_hh_hdl_event
@@ -299,7 +360,7 @@ void bta_hh_sm_execute(tBTA_HH_DEV_CB* p_cb, uint16_t event,
* Returns void
*
******************************************************************************/
-bool bta_hh_hdl_event(BT_HDR_RIGID* p_msg) {
+bool bta_hh_hdl_event(BT_HDR* p_msg) {
uint8_t index = BTA_HH_IDX_INVALID;
tBTA_HH_DEV_CB* p_cb = NULL;
@@ -350,8 +411,10 @@ bool bta_hh_hdl_event(BT_HDR_RIGID* p_msg) {
if (index != BTA_HH_IDX_INVALID) p_cb = &bta_hh_cb.kdev[index];
+#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("bta_hh_hdl_event:: handle = %d dev_cb[%d] ",
p_msg->layer_specific, index);
+#endif
bta_hh_sm_execute(p_cb, p_msg->event, (tBTA_HH_DATA*)p_msg);
}
return (true);
@@ -360,6 +423,7 @@ bool bta_hh_hdl_event(BT_HDR_RIGID* p_msg) {
/*****************************************************************************
* Debug Functions
****************************************************************************/
+#if (BTA_HH_DEBUG == TRUE)
/*******************************************************************************
*
* Function bta_hh_evt_code
@@ -401,6 +465,7 @@ static const char* bta_hh_evt_code(tBTA_HH_INT_EVT evt_code) {
return "BTA_HH_API_GET_DSCP_EVT";
case BTA_HH_OPEN_CMPL_EVT:
return "BTA_HH_OPEN_CMPL_EVT";
+#if (BTA_HH_LE_INCLUDED == TRUE)
case BTA_HH_GATT_CLOSE_EVT:
return "BTA_HH_GATT_CLOSE_EVT";
case BTA_HH_GATT_OPEN_EVT:
@@ -409,6 +474,7 @@ static const char* bta_hh_evt_code(tBTA_HH_INT_EVT evt_code) {
return "BTA_HH_START_ENC_EVT";
case BTA_HH_ENC_CMPL_EVT:
return "BTA_HH_ENC_CMPL_EVT";
+#endif
default:
return "unknown HID Host event code";
}
@@ -433,11 +499,15 @@ static const char* bta_hh_state_code(tBTA_HH_STATE state_code) {
return "BTA_HH_W4_CONN_ST";
case BTA_HH_CONN_ST:
return "BTA_HH_CONN_ST";
+#if (BTA_HH_LE_INCLUDED == TRUE)
case BTA_HH_W4_SEC:
return "BTA_HH_W4_SEC";
+#endif
default:
return "unknown HID Host state";
}
}
+#endif /* Debug Functions */
+
#endif /* BTA_HH_INCLUDED */
diff --git a/bta/hh/bta_hh_utils.cc b/bta/hh/bta_hh_utils.cc
index 1310b0312..f3cb1b31f 100644
--- a/bta/hh/bta_hh_utils.cc
+++ b/bta/hh/bta_hh_utils.cc
@@ -15,20 +15,15 @@
* limitations under the License.
*
******************************************************************************/
-#include <string.h> // memset
-#include <cstring>
+#include <string.h>
-#include "bt_target.h" // Must be first to define build configuration
+#include "bt_target.h"
#if (BTA_HH_INCLUDED == TRUE)
-#include "bt_trace.h" // Legacy trace logging
-#include "bta/hh/bta_hh_int.h"
+#include "bta_hh_int.h"
#include "btif/include/btif_storage.h"
#include "device/include/interop.h"
#include "osi/include/osi.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/btm_client_interface.h"
-#include "types/raw_address.h"
/* if SSR max latency is not defined by remote device, set the default value
as half of the link supervision timeout */
@@ -37,12 +32,19 @@
/*****************************************************************************
* Constants
****************************************************************************/
+#define BTA_HH_KB_CTRL_MASK 0x11
+#define BTA_HH_KB_SHIFT_MASK 0x22
+#define BTA_HH_KB_ALT_MASK 0x44
+#define BTA_HH_KB_GUI_MASK 0x88
-namespace {
+#define BTA_HH_KB_CAPS_LOCK 0x39 /* caps lock */
+#define BTA_HH_KB_NUM_LOCK 0x53 /* num lock */
-constexpr uint16_t kSsrMaxLatency = 18; /* slots * 0.625ms */
+#define BTA_HH_MAX_RPT_CHARS 8
-} // namespace
+static const uint8_t bta_hh_mod_key_mask[BTA_HH_MOD_MAX_KEY] = {
+ BTA_HH_KB_CTRL_MASK, BTA_HH_KB_SHIFT_MASK, BTA_HH_KB_ALT_MASK,
+ BTA_HH_KB_GUI_MASK};
/*******************************************************************************
*
@@ -93,14 +95,6 @@ uint8_t bta_hh_find_cb(const RawAddress& bda) {
return xx;
}
-tBTA_HH_DEV_CB* bta_hh_get_cb(const RawAddress& bda) {
- uint8_t idx = bta_hh_find_cb(bda);
- if (idx == BTA_HH_IDX_INVALID) {
- return nullptr;
- }
- return &bta_hh_cb.kdev[idx];
-}
-
/*******************************************************************************
*
* Function bta_hh_clean_up_kdev
@@ -115,10 +109,12 @@ void bta_hh_clean_up_kdev(tBTA_HH_DEV_CB* p_cb) {
uint8_t index;
if (p_cb->hid_handle != BTA_HH_INVALID_HANDLE) {
+#if (BTA_HH_LE_INCLUDED == TRUE)
if (p_cb->is_le_device)
bta_hh_cb.le_cb_index[BTA_HH_GET_LE_CB_IDX(p_cb->hid_handle)] =
BTA_HH_IDX_INVALID;
else
+#endif
bta_hh_cb.cb_index[p_cb->hid_handle] = BTA_HH_IDX_INVALID;
}
@@ -145,7 +141,11 @@ void bta_hh_clean_up_kdev(tBTA_HH_DEV_CB* p_cb) {
******************************************************************************/
void bta_hh_update_di_info(tBTA_HH_DEV_CB* p_cb, uint16_t vendor_id,
uint16_t product_id, uint16_t version,
+#if (BTA_HH_LE_INCLUDED == TRUE)
uint8_t flag)
+#else
+ UNUSED_ATTR uint8_t flag)
+#endif
{
#if (BTA_HH_DEBUG == TRUE)
APPL_TRACE_DEBUG("vendor_id = 0x%2x product_id = 0x%2x version = 0x%2x",
@@ -154,7 +154,9 @@ void bta_hh_update_di_info(tBTA_HH_DEV_CB* p_cb, uint16_t vendor_id,
p_cb->dscp_info.vendor_id = vendor_id;
p_cb->dscp_info.product_id = product_id;
p_cb->dscp_info.version = version;
+#if (BTA_HH_LE_INCLUDED == TRUE)
p_cb->dscp_info.flag = flag;
+#endif
}
/*******************************************************************************
*
@@ -167,7 +169,7 @@ void bta_hh_update_di_info(tBTA_HH_DEV_CB* p_cb, uint16_t vendor_id,
******************************************************************************/
void bta_hh_add_device_to_list(tBTA_HH_DEV_CB* p_cb, uint8_t handle,
uint16_t attr_mask,
- const tHID_DEV_DSCP_INFO* p_dscp_info,
+ tHID_DEV_DSCP_INFO* p_dscp_info,
uint8_t sub_class, uint16_t ssr_max_latency,
uint16_t ssr_min_tout, uint8_t app_id) {
#if (BTA_HH_DEBUG == TRUE)
@@ -226,6 +228,140 @@ bool bta_hh_tod_spt(tBTA_HH_DEV_CB* p_cb, uint8_t sub_class) {
return false;
}
+/*******************************************************************************
+ *
+ * Function bta_hh_parse_keybd_rpt
+ *
+ * Description This utility function parse a boot mode keyboard report.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_hh_parse_keybd_rpt(tBTA_HH_BOOT_RPT* p_kb_data, uint8_t* p_report,
+ uint16_t report_len) {
+ tBTA_HH_KB_CB* p_kb = &bta_hh_cb.kb_cb;
+ tBTA_HH_KEYBD_RPT* p_data = &p_kb_data->data_rpt.keybd_rpt;
+
+ uint8_t this_char, ctl_shift;
+ uint16_t xx, yy, key_idx = 0;
+ uint8_t this_report[BTA_HH_MAX_RPT_CHARS];
+
+#if (BTA_HH_DEBUG == TRUE)
+ APPL_TRACE_DEBUG("bta_hh_parse_keybd_rpt: (report=%p, report_len=%d) called",
+ p_report, report_len);
+#endif
+
+ if (report_len < 2) return;
+
+ ctl_shift = *p_report++;
+ report_len--;
+
+ if (report_len > BTA_HH_MAX_RPT_CHARS) report_len = BTA_HH_MAX_RPT_CHARS;
+
+ memset(this_report, 0, BTA_HH_MAX_RPT_CHARS);
+ memset(p_data, 0, sizeof(tBTA_HH_KEYBD_RPT));
+ memcpy(this_report, p_report, report_len);
+
+ /* Take care of shift, control, GUI and alt, modifier keys */
+ for (xx = 0; xx < BTA_HH_MOD_MAX_KEY; xx++) {
+ if (ctl_shift & bta_hh_mod_key_mask[xx]) {
+ APPL_TRACE_DEBUG("Mod Key[%02x] pressed", bta_hh_mod_key_mask[xx]);
+ p_kb->mod_key[xx] = true;
+ } else if (p_kb->mod_key[xx]) {
+ p_kb->mod_key[xx] = false;
+ }
+ /* control key flag is set */
+ p_data->mod_key[xx] = p_kb->mod_key[xx];
+ }
+
+ /***************************************************************************/
+ /* First step is to remove all characters we saw in the last report */
+ /***************************************************************************/
+ for (xx = 0; xx < report_len; xx++) {
+ for (yy = 0; yy < BTA_HH_MAX_RPT_CHARS; yy++) {
+ if (this_report[xx] == p_kb->last_report[yy]) {
+ this_report[xx] = 0;
+ }
+ }
+ }
+ /***************************************************************************/
+ /* Now, process all the characters in the report, up to 6 keycodes */
+ /***************************************************************************/
+ for (xx = 0; xx < report_len; xx++) {
+#if (BTA_HH_DEBUG == TRUE)
+ APPL_TRACE_DEBUG("this_char = %02x", this_report[xx]);
+#endif
+ this_char = this_report[xx];
+ if (this_char == 0) continue;
+ /* take the key code as the report data */
+ if (this_report[xx] == BTA_HH_KB_CAPS_LOCK)
+ p_kb->caps_lock = p_kb->caps_lock ? false : true;
+ else if (this_report[xx] == BTA_HH_KB_NUM_LOCK)
+ p_kb->num_lock = p_kb->num_lock ? false : true;
+ else
+ p_data->this_char[key_idx++] = this_char;
+
+#if (BTA_HH_DEBUG == TRUE)
+ APPL_TRACE_DEBUG("found keycode %02x ", this_report[xx]);
+#endif
+ p_data->caps_lock = p_kb->caps_lock;
+ p_data->num_lock = p_kb->num_lock;
+ }
+
+ memset(p_kb->last_report, 0, BTA_HH_MAX_RPT_CHARS);
+ memcpy(p_kb->last_report, p_report, report_len);
+
+ return;
+}
+
+/*******************************************************************************
+ *
+ * Function bta_hh_parse_mice_rpt
+ *
+ * Description This utility function parse a boot mode mouse report.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_hh_parse_mice_rpt(tBTA_HH_BOOT_RPT* p_mice_data, uint8_t* p_report,
+ uint16_t report_len) {
+ tBTA_HH_MICE_RPT* p_data = &p_mice_data->data_rpt.mice_rpt;
+#if (BTA_HH_DEBUG == TRUE)
+ uint8_t xx;
+
+ APPL_TRACE_DEBUG(
+ "bta_hh_parse_mice_rpt: bta_keybd_rpt_rcvd(report=%p, \
+ report_len=%d) called",
+ p_report, report_len);
+#endif
+
+ if (report_len < 3) return;
+
+ if (report_len > BTA_HH_MAX_RPT_CHARS) report_len = BTA_HH_MAX_RPT_CHARS;
+
+#if (BTA_HH_DEBUG == TRUE)
+ for (xx = 0; xx < report_len; xx++) {
+ APPL_TRACE_DEBUG("this_char = %02x", p_report[xx]);
+ }
+#endif
+
+ /* only first bytes lower 3 bits valid */
+ p_data->mouse_button = (p_report[0] & 0x07);
+
+ /* x displacement */
+ p_data->delta_x = p_report[1];
+
+ /* y displacement */
+ p_data->delta_y = p_report[2];
+
+#if (BTA_HH_DEBUG == TRUE)
+ APPL_TRACE_DEBUG("mice button: 0x%2x", p_data->mouse_button);
+ APPL_TRACE_DEBUG("mice move: x = %d y = %d", p_data->delta_x,
+ p_data->delta_y);
+#endif
+
+ return;
+}
/*******************************************************************************
*
@@ -239,52 +375,52 @@ bool bta_hh_tod_spt(tBTA_HH_DEV_CB* p_cb, uint8_t sub_class) {
tBTA_HH_STATUS bta_hh_read_ssr_param(const RawAddress& bd_addr,
uint16_t* p_max_ssr_lat,
uint16_t* p_min_ssr_tout) {
- tBTA_HH_DEV_CB* p_cb = bta_hh_get_cb(bd_addr);
- if (p_cb == nullptr) {
- LOG_WARN("Unable to find device:%s", PRIVATE_ADDRESS(bd_addr));
- return BTA_HH_ERR;
- }
-
- /* if remote device does not have HIDSSRHostMaxLatency attribute in SDP,
- set SSR max latency default value here. */
- if (p_cb->dscp_info.ssr_max_latency == HID_SSR_PARAM_INVALID) {
- /* The default is calculated as half of link supervision timeout.*/
-
- uint16_t ssr_max_latency;
- if (get_btm_client_interface().link_controller.BTM_GetLinkSuperTout(
- p_cb->addr, &ssr_max_latency) != BTM_SUCCESS) {
- LOG_WARN("Unable to get supervision timeout for peer:%s",
- PRIVATE_ADDRESS(p_cb->addr));
- return BTA_HH_ERR;
- }
- ssr_max_latency = BTA_HH_GET_DEF_SSR_MAX_LAT(ssr_max_latency);
-
- /* per 1.1 spec, if the newly calculated max latency is greater than
- BTA_HH_SSR_MAX_LATENCY_DEF which is 500ms, use
- BTA_HH_SSR_MAX_LATENCY_DEF */
- if (ssr_max_latency > BTA_HH_SSR_MAX_LATENCY_DEF)
- ssr_max_latency = BTA_HH_SSR_MAX_LATENCY_DEF;
-
- char remote_name[BTM_MAX_REM_BD_NAME_LEN] = "";
- if (btif_storage_get_stored_remote_name(bd_addr, remote_name)) {
- if (interop_match_name(INTEROP_HID_HOST_LIMIT_SNIFF_INTERVAL,
- remote_name)) {
- if (ssr_max_latency > kSsrMaxLatency /* slots * 0.625ms */) {
- ssr_max_latency = kSsrMaxLatency;
+ tBTA_HH_STATUS status = BTA_HH_ERR;
+ tBTA_HH_CB* p_cb = &bta_hh_cb;
+ uint8_t i;
+ uint16_t ssr_max_latency;
+ for (i = 0; i < BTA_HH_MAX_KNOWN; i++) {
+ if (p_cb->kdev[i].addr == bd_addr) {
+ /* if remote device does not have HIDSSRHostMaxLatency attribute in SDP,
+ set SSR max latency default value here. */
+ if (p_cb->kdev[i].dscp_info.ssr_max_latency == HID_SSR_PARAM_INVALID) {
+ /* The default is calculated as half of link supervision timeout.*/
+
+ BTM_GetLinkSuperTout(p_cb->kdev[i].addr, &ssr_max_latency);
+ ssr_max_latency = BTA_HH_GET_DEF_SSR_MAX_LAT(ssr_max_latency);
+
+ /* per 1.1 spec, if the newly calculated max latency is greater than
+ BTA_HH_SSR_MAX_LATENCY_DEF which is 500ms, use
+ BTA_HH_SSR_MAX_LATENCY_DEF */
+ if (ssr_max_latency > BTA_HH_SSR_MAX_LATENCY_DEF)
+ ssr_max_latency = BTA_HH_SSR_MAX_LATENCY_DEF;
+
+ char remote_name[BTM_MAX_REM_BD_NAME_LEN] = "";
+ if (btif_storage_get_stored_remote_name(bd_addr, remote_name)) {
+ if (interop_match_name(INTEROP_HID_HOST_LIMIT_SNIFF_INTERVAL,
+ remote_name)) {
+ if (ssr_max_latency > 18 /* slots * 0.625ms */) {
+ ssr_max_latency = 18;
+ }
+ }
}
- }
- }
- *p_max_ssr_lat = ssr_max_latency;
- } else
- *p_max_ssr_lat = p_cb->dscp_info.ssr_max_latency;
+ *p_max_ssr_lat = ssr_max_latency;
+ } else
+ *p_max_ssr_lat = p_cb->kdev[i].dscp_info.ssr_max_latency;
- if (p_cb->dscp_info.ssr_min_tout == HID_SSR_PARAM_INVALID)
- *p_min_ssr_tout = BTA_HH_SSR_MIN_TOUT_DEF;
- else
- *p_min_ssr_tout = p_cb->dscp_info.ssr_min_tout;
+ if (p_cb->kdev[i].dscp_info.ssr_min_tout == HID_SSR_PARAM_INVALID)
+ *p_min_ssr_tout = BTA_HH_SSR_MIN_TOUT_DEF;
+ else
+ *p_min_ssr_tout = p_cb->kdev[i].dscp_info.ssr_min_tout;
- return BTA_HH_OK;
+ status = BTA_HH_OK;
+
+ break;
+ }
+ }
+
+ return status;
}
/*******************************************************************************
@@ -335,6 +471,7 @@ void bta_hh_cleanup_disable(tBTA_HH_STATUS status) {
uint8_t bta_hh_dev_handle_to_cb_idx(uint8_t dev_handle) {
uint8_t index = BTA_HH_IDX_INVALID;
+#if (BTA_HH_LE_INCLUDED == TRUE)
if (BTA_HH_IS_LE_DEV_HDL(dev_handle)) {
if (BTA_HH_IS_LE_DEV_HDL_VALID(dev_handle))
index = bta_hh_cb.le_cb_index[BTA_HH_GET_LE_CB_IDX(dev_handle)];
@@ -343,6 +480,7 @@ uint8_t bta_hh_dev_handle_to_cb_idx(uint8_t dev_handle) {
dev_handle, index);
#endif
} else
+#endif
/* regular HID device checking */
if (dev_handle < BTA_HH_MAX_KNOWN)
index = bta_hh_cb.cb_index[dev_handle];
diff --git a/bta/include/bta_ag_api.h b/bta/include/bta_ag_api.h
index 5ce8ed1b9..c5d4f3619 100644
--- a/bta/include/bta_ag_api.h
+++ b/bta/include/bta_ag_api.h
@@ -26,21 +26,35 @@
#define BTA_AG_API_H
#include "bta_api.h"
-#include "bta_hfp_api.h"
#include <string>
#include <vector>
-#include "bta/include/bta_ag_api.h"
-#include "bta/include/bta_api.h"
-#include "types/raw_address.h"
-
/*****************************************************************************
* Constants and data types
****************************************************************************/
/* Number of SCBs (AG service instances that can be registered) */
#define BTA_AG_MAX_NUM_CLIENTS 6
+#define HFP_HSP_VERSION_UNKNOWN 0x0000
+#define HFP_VERSION_1_1 0x0101
+#define HFP_VERSION_1_5 0x0105
+#define HFP_VERSION_1_6 0x0106
+#define HFP_VERSION_1_7 0x0107
+
+#define HSP_VERSION_1_0 0x0100
+#define HSP_VERSION_1_2 0x0102
+
+#define HFP_VERSION_CONFIG_KEY "HfpVersion"
+#define HFP_SDP_FEATURES_CONFIG_KEY "HfpSdpFeatures"
+
+/* Note, if you change the default version here, please also change the one in
+ * bta_hs_api.h, they are meant to be the same.
+ */
+#ifndef BTA_HFP_VERSION
+#define BTA_HFP_VERSION HFP_VERSION_1_7
+#endif
+
/* AG feature masks */
#define BTA_AG_FEAT_3WAY 0x00000001 /* Three-way calling */
#define BTA_AG_FEAT_ECNR 0x00000002 /* Echo cancellation/noise reduction */
@@ -64,7 +78,7 @@
/* HFP 1.7+ */
#define BTA_AG_FEAT_HF_IND 0x00000400 /* HF Indicators */
-#define BTA_AG_FEAT_ESCO_S4 0x00000800 /* eSCO S4 setting supported */
+#define BTA_AG_FEAT_ESCO 0x00000800 /* eSCO S4 (and T2) setting supported */
/* Proprietary features: using 31 ~ 16 bits */
#define BTA_AG_FEAT_BTRH 0x00010000 /* CCAP incoming call hold */
@@ -106,74 +120,37 @@ typedef uint8_t tBTA_AG_STATUS;
#define BTA_AG_HANDLE_SCO_NO_CHANGE 0xFFFF
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-typedef enum : uint8_t {
- /* AG result codes used with BTA_AgResult */
- BTA_AG_SPK_RES = 0, /* Update speaker volume */
- BTA_AG_MIC_RES = 1, /* Update microphone volume */
- BTA_AG_INBAND_RING_RES = 2, /* Update inband ring state */
- BTA_AG_CIND_RES = 3, /* Send indicator response for AT+CIND */
- BTA_AG_BINP_RES = 4, /* Send phone number for voice tag for AT+BINP */
- BTA_AG_IND_RES = 5, /* Update an indicator value */
- BTA_AG_BVRA_RES = 6, /* Update voice recognition state */
- BTA_AG_CNUM_RES = 7, /* Send subscriber number response for AT+CNUM */
- BTA_AG_BTRH_RES = 8, /* Send CCAP incoming call hold */
- BTA_AG_CLCC_RES = 9, /* Query list of calls */
- BTA_AG_COPS_RES = 10, /* Read network operator */
- BTA_AG_IN_CALL_RES = 11, /* Indicate incoming phone call */
- BTA_AG_IN_CALL_CONN_RES = 12, /* Incoming phone call connected */
- BTA_AG_CALL_WAIT_RES = 13, /* Call waiting notification */
- BTA_AG_OUT_CALL_ORIG_RES = 14, /* Outgoing phone call origination */
-
- /* Outgoing phone call alerting remote party */
- BTA_AG_OUT_CALL_ALERT_RES = 15,
- BTA_AG_OUT_CALL_CONN_RES = 16, /* Outgoing phone call connected */
-
- /* Incoming/outgoing = 3,-way canceled before connected */
- BTA_AG_CALL_CANCEL_RES = 17,
- BTA_AG_END_CALL_RES = 18, /* End call */
- BTA_AG_IN_CALL_HELD_RES = 19, /* Incoming call held */
- BTA_AG_UNAT_RES = 20, /* Response to unknown AT command event */
- BTA_AG_MULTI_CALL_RES = 21, /* SLC at three way call */
- BTA_AG_BIND_RES = 22, /* Activate/Deactivate HF indicator */
- BTA_AG_IND_RES_ON_DEMAND = 33, /* Update an indicator value forcible */
- BTA_AG_UNKNOWN = 0xff, // Should be unset
-} tBTA_AG_RES;
-
-inline std::string bta_ag_result_text(const tBTA_AG_RES& result) {
- switch (result) {
- CASE_RETURN_TEXT(BTA_AG_SPK_RES);
- CASE_RETURN_TEXT(BTA_AG_MIC_RES);
- CASE_RETURN_TEXT(BTA_AG_INBAND_RING_RES);
- CASE_RETURN_TEXT(BTA_AG_CIND_RES);
- CASE_RETURN_TEXT(BTA_AG_BINP_RES);
- CASE_RETURN_TEXT(BTA_AG_IND_RES);
- CASE_RETURN_TEXT(BTA_AG_BVRA_RES);
- CASE_RETURN_TEXT(BTA_AG_CNUM_RES);
- CASE_RETURN_TEXT(BTA_AG_BTRH_RES);
- CASE_RETURN_TEXT(BTA_AG_CLCC_RES);
- CASE_RETURN_TEXT(BTA_AG_COPS_RES);
- CASE_RETURN_TEXT(BTA_AG_IN_CALL_RES);
- CASE_RETURN_TEXT(BTA_AG_IN_CALL_CONN_RES);
- CASE_RETURN_TEXT(BTA_AG_CALL_WAIT_RES);
- CASE_RETURN_TEXT(BTA_AG_OUT_CALL_ORIG_RES);
- CASE_RETURN_TEXT(BTA_AG_OUT_CALL_ALERT_RES);
- CASE_RETURN_TEXT(BTA_AG_OUT_CALL_CONN_RES);
- CASE_RETURN_TEXT(BTA_AG_CALL_CANCEL_RES);
- CASE_RETURN_TEXT(BTA_AG_END_CALL_RES);
- CASE_RETURN_TEXT(BTA_AG_IN_CALL_HELD_RES);
- CASE_RETURN_TEXT(BTA_AG_UNAT_RES);
- CASE_RETURN_TEXT(BTA_AG_MULTI_CALL_RES);
- CASE_RETURN_TEXT(BTA_AG_BIND_RES);
- CASE_RETURN_TEXT(BTA_AG_IND_RES_ON_DEMAND);
- CASE_RETURN_TEXT(BTA_AG_UNKNOWN);
- default:
- return std::string("UNKNOWN");
- }
-}
+/* AG result codes used with BTA_AgResult */
+#define BTA_AG_SPK_RES 0 /* Update speaker volume */
+#define BTA_AG_MIC_RES 1 /* Update microphone volume */
+#define BTA_AG_INBAND_RING_RES 2 /* Update inband ring state */
+#define BTA_AG_CIND_RES 3 /* Send indicator response for AT+CIND */
+#define BTA_AG_BINP_RES 4 /* Send phone number for voice tag for AT+BINP */
+#define BTA_AG_IND_RES 5 /* Update an indicator value */
+#define BTA_AG_BVRA_RES 6 /* Update voice recognition state */
+#define BTA_AG_CNUM_RES 7 /* Send subscriber number response for AT+CNUM */
+#define BTA_AG_BTRH_RES 8 /* Send CCAP incoming call hold */
+#define BTA_AG_CLCC_RES 9 /* Query list of calls */
+#define BTA_AG_COPS_RES 10 /* Read network operator */
+#define BTA_AG_IN_CALL_RES 11 /* Indicate incoming phone call */
+#define BTA_AG_IN_CALL_CONN_RES 12 /* Incoming phone call connected */
+#define BTA_AG_CALL_WAIT_RES 13 /* Call waiting notification */
+#define BTA_AG_OUT_CALL_ORIG_RES 14 /* Outgoing phone call origination */
+
+/* Outgoing phone call alerting remote party */
+#define BTA_AG_OUT_CALL_ALERT_RES 15
+#define BTA_AG_OUT_CALL_CONN_RES 16 /* Outgoing phone call connected */
+
+/* Incoming/outgoing 3-way canceled before connected */
+#define BTA_AG_CALL_CANCEL_RES 17
+#define BTA_AG_END_CALL_RES 18 /* End call */
+#define BTA_AG_IN_CALL_HELD_RES 19 /* Incoming call held */
+#define BTA_AG_UNAT_RES 20 /* Response to unknown AT command event */
+#define BTA_AG_MULTI_CALL_RES 21 /* SLC at three way call */
+#define BTA_AG_BIND_RES 22 /* Activate/Deactivate HF indicator */
+#define BTA_AG_IND_RES_ON_DEMAND 33 /* Update an indicator value forcible */
+
+typedef uint8_t tBTA_AG_RES;
/* HFP peer features */
#define BTA_AG_PEER_FEAT_ECNR 0x0001 /* Echo cancellation/noise reduction */
@@ -185,7 +162,7 @@ inline std::string bta_ag_result_text(const tBTA_AG_RES& result) {
#define BTA_AG_PEER_FEAT_ECC 0x0040 /* Enhanced Call Control */
#define BTA_AG_PEER_FEAT_CODEC 0x0080 /* Codec Negotiation */
#define BTA_AG_PEER_FEAT_HF_IND 0x0100 /* HF Indicators */
-#define BTA_AG_PEER_FEAT_ESCO_S4 0x0200 /* eSCO S4 setting supported */
+#define BTA_AG_PEER_FEAT_ESCO 0x0200 /* eSCO S4 (and T2) setting supported */
/* Proprietary features: using bits after 12 */
@@ -318,43 +295,43 @@ struct tBTA_AG_RES_DATA {
static const tBTA_AG_RES_DATA kEmpty;
};
-typedef enum : uint8_t {
- /* AG callback events */
- BTA_AG_ENABLE_EVT = 0, /* AG enabled */
- BTA_AG_REGISTER_EVT = 1, /* AG registered */
- BTA_AG_OPEN_EVT = 2, /* AG connection open */
- BTA_AG_CLOSE_EVT = 3, /* AG connection closed */
- BTA_AG_CONN_EVT = 4, /* Service level connection opened */
- BTA_AG_AUDIO_OPEN_EVT = 5, /* Audio connection open */
- BTA_AG_AUDIO_CLOSE_EVT = 6, /* Audio connection closed */
- BTA_AG_SPK_EVT = 7, /* Speaker volume changed */
- BTA_AG_MIC_EVT = 8, /* Microphone volume changed */
- BTA_AG_AT_CKPD_EVT = 9, /* CKPD from the HS */
- BTA_AG_DISABLE_EVT = 30, /* AG disabled */
- BTA_AG_WBS_EVT = 31, /* SCO codec info */
- /* Values below are for HFP only */
- BTA_AG_AT_A_EVT = 10, /* Answer a call */
- BTA_AG_AT_D_EVT = 11, /* Place a call using number or memory dial */
- BTA_AG_AT_CHLD_EVT = 12, /* Call hold */
- BTA_AG_AT_CHUP_EVT = 13, /* Hang up a call */
- BTA_AG_AT_CIND_EVT = 14, /* Read indicator settings */
- BTA_AG_AT_VTS_EVT = 15, /* Transmit DTMF tone */
- BTA_AG_AT_BINP_EVT = 16, /* Retrieve number from voice tag */
- BTA_AG_AT_BLDN_EVT = 17, /* Place call to last dialed number */
- BTA_AG_AT_BVRA_EVT = 18, /* Enable/disable voice recognition */
- BTA_AG_AT_NREC_EVT = 19, /* Disable echo canceling */
- BTA_AG_AT_CNUM_EVT = 20, /* Retrieve subscriber number */
- BTA_AG_AT_BTRH_EVT = 21, /* CCAP-style incoming call hold */
- BTA_AG_AT_CLCC_EVT = 22, /* Query list of current calls */
- BTA_AG_AT_COPS_EVT = 23, /* Query list of current calls */
- BTA_AG_AT_UNAT_EVT = 24, /* Unknown AT command */
- BTA_AG_AT_CBC_EVT = 25, /* Battery Level report from HF */
- BTA_AG_AT_BAC_EVT = 26, /* avablable codec */
- BTA_AG_AT_BCS_EVT = 27, /* Codec select */
- BTA_AG_AT_BIND_EVT = 28, /* HF indicator */
- BTA_AG_AT_BIEV_EVT = 29, /* HF indicator updates from peer */
- BTA_AG_AT_BIA_EVT = 32, /* AG indicator activation event from peer */
-} tBTA_AG_EVT;
+/* AG callback events */
+#define BTA_AG_ENABLE_EVT 0 /* AG enabled */
+#define BTA_AG_REGISTER_EVT 1 /* AG registered */
+#define BTA_AG_OPEN_EVT 2 /* AG connection open */
+#define BTA_AG_CLOSE_EVT 3 /* AG connection closed */
+#define BTA_AG_CONN_EVT 4 /* Service level connection opened */
+#define BTA_AG_AUDIO_OPEN_EVT 5 /* Audio connection open */
+#define BTA_AG_AUDIO_CLOSE_EVT 6 /* Audio connection closed */
+#define BTA_AG_SPK_EVT 7 /* Speaker volume changed */
+#define BTA_AG_MIC_EVT 8 /* Microphone volume changed */
+#define BTA_AG_AT_CKPD_EVT 9 /* CKPD from the HS */
+#define BTA_AG_DISABLE_EVT 30 /* AG disabled */
+#define BTA_AG_WBS_EVT 31 /* SCO codec info */
+/* Values below are for HFP only */
+#define BTA_AG_AT_A_EVT 10 /* Answer a call */
+#define BTA_AG_AT_D_EVT 11 /* Place a call using number or memory dial */
+#define BTA_AG_AT_CHLD_EVT 12 /* Call hold */
+#define BTA_AG_AT_CHUP_EVT 13 /* Hang up a call */
+#define BTA_AG_AT_CIND_EVT 14 /* Read indicator settings */
+#define BTA_AG_AT_VTS_EVT 15 /* Transmit DTMF tone */
+#define BTA_AG_AT_BINP_EVT 16 /* Retrieve number from voice tag */
+#define BTA_AG_AT_BLDN_EVT 17 /* Place call to last dialed number */
+#define BTA_AG_AT_BVRA_EVT 18 /* Enable/disable voice recognition */
+#define BTA_AG_AT_NREC_EVT 19 /* Disable echo canceling */
+#define BTA_AG_AT_CNUM_EVT 20 /* Retrieve subscriber number */
+#define BTA_AG_AT_BTRH_EVT 21 /* CCAP-style incoming call hold */
+#define BTA_AG_AT_CLCC_EVT 22 /* Query list of current calls */
+#define BTA_AG_AT_COPS_EVT 23 /* Query list of current calls */
+#define BTA_AG_AT_UNAT_EVT 24 /* Unknown AT command */
+#define BTA_AG_AT_CBC_EVT 25 /* Battery Level report from HF */
+#define BTA_AG_AT_BAC_EVT 26 /* avablable codec */
+#define BTA_AG_AT_BCS_EVT 27 /* Codec select */
+#define BTA_AG_AT_BIND_EVT 28 /* HF indicator */
+#define BTA_AG_AT_BIEV_EVT 29 /* HF indicator updates from peer */
+#define BTA_AG_AT_BIA_EVT 32 /* AG indicator activation event from peer */
+
+typedef uint8_t tBTA_AG_EVT;
/* data associated with most non-AT events */
typedef struct {
@@ -523,7 +500,8 @@ void BTA_AgDisable();
* Returns void
*
******************************************************************************/
-void BTA_AgRegister(tBTA_SERVICE_MASK services, tBTA_AG_FEAT features,
+void BTA_AgRegister(tBTA_SERVICE_MASK services, tBTA_SEC sec_mask,
+ tBTA_AG_FEAT features,
const std::vector<std::string>& service_names,
uint8_t app_id);
@@ -552,7 +530,7 @@ void BTA_AgDeregister(uint16_t handle);
* Returns void
*
******************************************************************************/
-void BTA_AgOpen(uint16_t handle, const RawAddress& bd_addr);
+void BTA_AgOpen(uint16_t handle, const RawAddress& bd_addr, tBTA_SEC sec_mask);
/*******************************************************************************
*
diff --git a/bta/include/bta_api.h b/bta/include/bta_api.h
index 8e3eb8d4f..b7d7d3051 100644
--- a/bta/include/bta_api.h
+++ b/bta/include/bta_api.h
@@ -25,47 +25,65 @@
#ifndef BTA_API_H
#define BTA_API_H
-#include <cstdint>
-#include <vector>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "osi/include/log.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/btm_ble_api_types.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/sdp_api.h"
-#include "types/ble_address_with_type.h"
-#include "types/bluetooth/uuid.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
+#include <hardware/bt_common_types.h>
+#include <memory>
+#include "bt_target.h"
+#include "bt_types.h"
+#include "btm_api.h"
+#include "btm_ble_api.h"
/*****************************************************************************
* Constants and data types
****************************************************************************/
/* Status Return Value */
-typedef enum : uint8_t {
- BTA_SUCCESS = 0, /* Successful operation. */
- BTA_FAILURE = 1, /* Generic failure. */
- BTA_PENDING = 2, /* API cannot be completed right now */
- BTA_BUSY = 3,
- BTA_NO_RESOURCES = 4,
- BTA_WRONG_MODE = 5,
-} tBTA_STATUS;
+#define BTA_SUCCESS 0 /* Successful operation. */
+#define BTA_FAILURE 1 /* Generic failure. */
+#define BTA_PENDING 2 /* API cannot be completed right now */
+#define BTA_BUSY 3
+#define BTA_NO_RESOURCES 4
+#define BTA_WRONG_MODE 5
+
+typedef uint8_t tBTA_STATUS;
/*
* Service ID
+ *
+ * NOTES: When you add a new Service ID for BTA AND require to change the value
+ * of BTA_MAX_SERVICE_ID, make sure that the correct security ID of the new
+ * service from Security service definitions (btm_api.h) should be added to
+ * bta_service_id_to_btm_srv_id_lkup_tbl table in bta_dm_act.cc
*/
+#define BTA_RES_SERVICE_ID 0 /* Reserved */
+#define BTA_SPP_SERVICE_ID 1 /* Serial port profile. */
+#define BTA_DUN_SERVICE_ID 2 /* Dial-up networking profile. */
#define BTA_A2DP_SOURCE_SERVICE_ID 3 /* A2DP Source profile. */
+#define BTA_LAP_SERVICE_ID 4 /* LAN access profile. */
#define BTA_HSP_SERVICE_ID 5 /* Headset profile. */
#define BTA_HFP_SERVICE_ID 6 /* Hands-free profile. */
+#define BTA_OPP_SERVICE_ID 7 /* Object push */
+#define BTA_FTP_SERVICE_ID 8 /* File transfer */
+#define BTA_CTP_SERVICE_ID 9 /* Cordless Terminal */
+#define BTA_ICP_SERVICE_ID 10 /* Intercom Terminal */
+#define BTA_SYNC_SERVICE_ID 11 /* Synchronization */
+#define BTA_BPP_SERVICE_ID 12 /* Basic printing profile */
#define BTA_BIP_SERVICE_ID 13 /* Basic Imaging profile */
+#define BTA_PANU_SERVICE_ID 14 /* PAN User */
+#define BTA_NAP_SERVICE_ID 15 /* PAN Network access point */
+#define BTA_GN_SERVICE_ID 16 /* PAN Group Ad-hoc networks */
+#define BTA_SAP_SERVICE_ID 17 /* SIM Access profile */
#define BTA_A2DP_SINK_SERVICE_ID 18 /* A2DP Sink */
+#define BTA_AVRCP_SERVICE_ID 19 /* A/V remote control */
#define BTA_HID_SERVICE_ID 20 /* HID */
+#define BTA_VDP_SERVICE_ID 21 /* Video distribution */
+#define BTA_PBAP_SERVICE_ID 22 /* PhoneBook Access Server*/
+#define BTA_HSP_HS_SERVICE_ID 23 /* HFP HS role */
#define BTA_HFP_HS_SERVICE_ID 24 /* HSP HS role */
+#define BTA_MAP_SERVICE_ID 25 /* Message Access Profile */
+#define BTA_MN_SERVICE_ID 26 /* Message Notification Service */
+#define BTA_HDP_SERVICE_ID 27 /* Health Device Profile */
+#define BTA_PCE_SERVICE_ID 28 /* PhoneBook Access Client */
#define BTA_SDP_SERVICE_ID 29 /* SDP Search */
#define BTA_HIDD_SERVICE_ID 30 /* HID Device */
@@ -83,9 +101,35 @@ typedef uint8_t tBTA_SERVICE_ID;
/* Service ID Mask */
#define BTA_RES_SERVICE_MASK 0x00000001 /* Reserved */
+#define BTA_SPP_SERVICE_MASK 0x00000002 /* Serial port profile. */
+#define BTA_DUN_SERVICE_MASK 0x00000004 /* Dial-up networking profile. */
+#define BTA_FAX_SERVICE_MASK 0x00000008 /* Fax profile. */
+#define BTA_LAP_SERVICE_MASK 0x00000010 /* LAN access profile. */
#define BTA_HSP_SERVICE_MASK 0x00000020 /* HSP AG role. */
#define BTA_HFP_SERVICE_MASK 0x00000040 /* HFP AG role */
+#define BTA_OPP_SERVICE_MASK 0x00000080 /* Object push */
+#define BTA_FTP_SERVICE_MASK 0x00000100 /* File transfer */
+#define BTA_CTP_SERVICE_MASK 0x00000200 /* Cordless Terminal */
+#define BTA_ICP_SERVICE_MASK 0x00000400 /* Intercom Terminal */
+#define BTA_SYNC_SERVICE_MASK 0x00000800 /* Synchronization */
+#define BTA_BPP_SERVICE_MASK 0x00001000 /* Print server */
+#define BTA_BIP_SERVICE_MASK 0x00002000 /* Basic Imaging */
+#define BTA_PANU_SERVICE_MASK 0x00004000 /* PAN User */
+#define BTA_NAP_SERVICE_MASK 0x00008000 /* PAN Network access point */
+#define BTA_GN_SERVICE_MASK 0x00010000 /* PAN Group Ad-hoc networks */
+#define BTA_SAP_SERVICE_MASK 0x00020000 /* PAN Group Ad-hoc networks */
+#define BTA_A2DP_SERVICE_MASK 0x00040000 /* Advanced audio distribution */
+#define BTA_AVRCP_SERVICE_MASK 0x00080000 /* A/V remote control */
+#define BTA_HID_SERVICE_MASK 0x00100000 /* HID */
+#define BTA_VDP_SERVICE_MASK 0x00200000 /* Video distribution */
+#define BTA_PBAP_SERVICE_MASK 0x00400000 /* Phone Book Server */
+#define BTA_HSP_HS_SERVICE_MASK 0x00800000 /* HFP HS role */
+#define BTA_HFP_HS_SERVICE_MASK 0x01000000 /* HSP HS role */
+#define BTA_MAS_SERVICE_MASK 0x02000000 /* Message Access Profile */
+#define BTA_MN_SERVICE_MASK 0x04000000 /* Message Notification Profile */
#define BTA_HL_SERVICE_MASK 0x08000000 /* Health Device Profile */
+#define BTA_PCE_SERVICE_MASK 0x10000000 /* Phone Book Client */
+#define BTA_HIDD_SERVICE_MASK 0x20000000 /* HID Device */
#define BTA_BLE_SERVICE_MASK 0x40000000 /* GATT based service */
#define BTA_ALL_SERVICE_MASK 0x7FFFFFFF /* All services supported by BTA. */
@@ -93,7 +137,18 @@ typedef uint8_t tBTA_SERVICE_ID;
typedef uint32_t tBTA_SERVICE_MASK;
+/* extended service mask, including mask with one or more GATT UUID */
+typedef struct {
+ tBTA_SERVICE_MASK srvc_mask;
+ uint8_t num_uuid;
+ bluetooth::Uuid* p_uuid;
+} tBTA_SERVICE_MASK_EXT;
+
/* Security Setting Mask */
+#define BTA_SEC_NONE BTM_SEC_NONE /* No security. */
+#define BTA_SEC_AUTHORIZE \
+ (BTM_SEC_IN_AUTHORIZE) /* Authorization required (only needed for out \
+ going connection )*/
#define BTA_SEC_AUTHENTICATE \
(BTM_SEC_IN_AUTHENTICATE | \
BTM_SEC_OUT_AUTHENTICATE) /* Authentication required. */
@@ -102,6 +157,13 @@ typedef uint32_t tBTA_SERVICE_MASK;
typedef uint16_t tBTA_SEC;
+/* Ignore for Discoverable, Connectable, Pairable and Connectable Paired only
+ * device modes */
+#define BTA_DM_IGNORE 0x00FF
+
+/* Ignore for Discoverable, Connectable only for LE modes */
+#define BTA_DM_LE_IGNORE 0xFF00
+
#define BTA_APP_ID_PAN_MULTI 0xFE /* app id for pan multiple connection */
#define BTA_ALL_APP_ID 0xFF
@@ -110,6 +172,12 @@ typedef uint16_t tBTA_SEC;
#define BTA_DM_GENERAL_DISC \
BTM_GENERAL_DISCOVERABLE /* General discoverable. \
*/
+#define BTA_DM_BLE_NON_DISCOVERABLE \
+ BTM_BLE_NON_DISCOVERABLE /* Device is not LE discoverable */
+#define BTA_DM_BLE_GENERAL_DISCOVERABLE \
+ BTM_BLE_GENERAL_DISCOVERABLE /* Device is LE General discoverable */
+#define BTA_DM_BLE_LIMITED_DISCOVERABLE \
+ BTM_BLE_LIMITED_DISCOVERABLE /* Device is LE Limited discoverable */
typedef uint16_t
tBTA_DM_DISC; /* this discoverability mode is a bit mask among BR mode and
LE mode */
@@ -117,55 +185,105 @@ typedef uint16_t
/* Connectable Modes */
#define BTA_DM_NON_CONN BTM_NON_CONNECTABLE /* Device is not connectable. */
#define BTA_DM_CONN BTM_CONNECTABLE /* Device is connectable. */
+#define BTA_DM_BLE_NON_CONNECTABLE \
+ BTM_BLE_NON_CONNECTABLE /* Device is LE non-connectable. */
+#define BTA_DM_BLE_CONNECTABLE \
+ BTM_BLE_CONNECTABLE /* Device is LE connectable. */
typedef uint16_t tBTA_DM_CONN;
-/* Central/peripheral preferred roles */
-typedef enum : uint8_t {
- BTA_ANY_ROLE = 0x00,
- BTA_CENTRAL_ROLE_PREF = 0x01,
- BTA_CENTRAL_ROLE_ONLY = 0x02,
- /* Used for PANU only, skip role switch to central */
- BTA_PERIPHERAL_ROLE_ONLY = 0x03,
-} tBTA_PREF_ROLES;
-
-inline tBTA_PREF_ROLES toBTA_PREF_ROLES(uint8_t role) {
- ASSERT_LOG(role <= BTA_PERIPHERAL_ROLE_ONLY,
- "Passing illegal preferred role:0x%02x [0x%02x<=>0x%02x]", role,
- BTA_ANY_ROLE, BTA_PERIPHERAL_ROLE_ONLY);
- return static_cast<tBTA_PREF_ROLES>(role);
-}
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string preferred_role_text(const tBTA_PREF_ROLES& role) {
- switch (role) {
- CASE_RETURN_TEXT(BTA_ANY_ROLE);
- CASE_RETURN_TEXT(BTA_CENTRAL_ROLE_PREF);
- CASE_RETURN_TEXT(BTA_CENTRAL_ROLE_ONLY);
- CASE_RETURN_TEXT(BTA_PERIPHERAL_ROLE_ONLY);
- default:
- return std::string("UNKNOWN:%hhu", role);
- }
-}
-#undef CASE_RETURN_TEXT
+#define BTA_TRANSPORT_UNKNOWN 0
+#define BTA_TRANSPORT_BR_EDR BT_TRANSPORT_BR_EDR
+#define BTA_TRANSPORT_LE BT_TRANSPORT_LE
+typedef tBT_TRANSPORT tBTA_TRANSPORT;
+
+/* Pairable Modes */
+#define BTA_DM_PAIRABLE 1
+#define BTA_DM_NON_PAIRABLE 0
+
+/* Connectable Paired Only Mode */
+#define BTA_DM_CONN_ALL 0
+#define BTA_DM_CONN_PAIRED 1
+
+/* Inquiry Modes */
+#define BTA_DM_INQUIRY_NONE BTM_INQUIRY_NONE /*No BR inquiry. */
+#define BTA_DM_GENERAL_INQUIRY \
+ BTM_GENERAL_INQUIRY /* Perform general inquiry. */
+#define BTA_DM_LIMITED_INQUIRY \
+ BTM_LIMITED_INQUIRY /* Perform limited inquiry. */
+
+#define BTA_BLE_INQUIRY_NONE BTM_BLE_INQUIRY_NONE
+#define BTA_BLE_GENERAL_INQUIRY \
+ BTM_BLE_GENERAL_INQUIRY /* Perform LE general inquiry. */
+#define BTA_BLE_LIMITED_INQUIRY \
+ BTM_BLE_LIMITED_INQUIRY /* Perform LE limited inquiry. */
+typedef uint8_t tBTA_DM_INQ_MODE;
+
+/* Inquiry Filter Type */
+#define BTA_DM_INQ_CLR BTM_CLR_INQUIRY_FILTER /* Clear inquiry filter. */
+#define BTA_DM_INQ_DEV_CLASS \
+ BTM_FILTER_COND_DEVICE_CLASS /* Filter on device class. */
+#define BTA_DM_INQ_BD_ADDR \
+ BTM_FILTER_COND_BD_ADDR /* Filter on a specific BD address. */
+
+typedef uint8_t tBTA_DM_INQ_FILT;
+
+/* Authorize Response */
+#define BTA_DM_AUTH_PERM \
+ 0 /* Authorized for future connections to the service */
+#define BTA_DM_AUTH_TEMP 1 /* Authorized for current connection only */
+#define BTA_DM_NOT_AUTH 2 /* Not authorized for the service */
+
+typedef uint8_t tBTA_AUTH_RESP;
+
+/* M/S preferred roles */
+#define BTA_ANY_ROLE 0x00
+#define BTA_MASTER_ROLE_PREF 0x01
+#define BTA_MASTER_ROLE_ONLY 0x02
+#define BTA_SLAVE_ROLE_ONLY \
+ 0x03 /* Used for PANU only, skip role switch to master */
+
+typedef uint8_t tBTA_PREF_ROLES;
enum {
BTA_DM_NO_SCATTERNET, /* Device doesn't support scatternet, it might
support "role switch during connection" for
an incoming connection, when it already has
- another connection in central role */
+ another connection in master role */
BTA_DM_PARTIAL_SCATTERNET, /* Device supports partial scatternet. It can have
- simultaneous connection in Central and
- Peripheral roles for short period of time */
- BTA_DM_FULL_SCATTERNET /* Device can have simultaneous connection in central
- and peripheral roles */
+ simulateous connection in Master and Slave roles
+ for short period of time */
+ BTA_DM_FULL_SCATTERNET /* Device can have simultaneous connection in master
+ and slave roles */
};
+/* Inquiry filter device class condition */
+typedef struct {
+ DEV_CLASS dev_class; /* device class of interest */
+ DEV_CLASS dev_class_mask; /* mask to determine the bits of device class of
+ interest */
+} tBTA_DM_COD_COND;
+
+/* Inquiry Filter Condition */
+typedef union {
+ RawAddress bd_addr; /* BD address of device to filter. */
+ tBTA_DM_COD_COND dev_class_cond; /* Device class filter condition */
+} tBTA_DM_INQ_COND;
+
+/* Inquiry Parameters */
+typedef struct {
+ tBTA_DM_INQ_MODE mode; /* Inquiry mode, limited or general. */
+ uint8_t duration; /* Inquiry duration in 1.28 sec units. */
+ uint8_t max_resps; /* Maximum inquiry responses. Set to zero for unlimited
+ responses. */
+ bool report_dup; /* report duplicated inquiry response with higher RSSI value
+ */
+ tBTA_DM_INQ_FILT filter_type; /* Filter condition type. */
+ tBTA_DM_INQ_COND filter_cond; /* Filter condition data. */
+} tBTA_DM_INQ;
+
typedef struct {
uint8_t bta_dm_eir_min_name_len; /* minimum length of local name when it is
shortened */
@@ -185,19 +303,65 @@ typedef struct {
uint8_t* bta_dm_eir_additional; /* additional data */
} tBTA_DM_EIR_CONF;
+/* advertising filter policy */
+typedef tBTM_BLE_AFP tBTA_BLE_AFP;
+
+enum {
+ BTA_BLE_BATCH_SCAN_MODE_PASS = 1,
+ BTA_BLE_BATCH_SCAN_MODE_ACTI = 2,
+ BTA_BLE_BATCH_SCAN_MODE_PASS_ACTI = 3
+};
+typedef uint8_t tBTA_BLE_BATCH_SCAN_MODE;
+
+enum { BTA_BLE_DISCARD_OLD_ITEMS = 0, BTA_BLE_DISCARD_LOWER_RSSI_ITEMS = 1 };
+typedef uint8_t tBTA_BLE_DISCARD_RULE;
+
+enum { BTA_BLE_ADV_SEEN_FIRST_TIME = 0, BTA_BLE_ADV_TRACKING_TIMEOUT = 1 };
+typedef uint8_t tBTA_BLE_ADV_CHANGE_REASON;
+
+/* BLE customer specific feature function type definitions */
+/* data type used on customer specific feature for RSSI monitoring */
+#define BTA_BLE_RSSI_ALERT_HI 0
+#define BTA_BLE_RSSI_ALERT_RANGE 1
+#define BTA_BLE_RSSI_ALERT_LO 2
typedef uint8_t tBTA_DM_BLE_RSSI_ALERT_TYPE;
+#define BTA_BLE_RSSI_ALERT_NONE BTM_BLE_RSSI_ALERT_NONE /* (0) */
+#define BTA_BLE_RSSI_ALERT_HI_BIT BTM_BLE_RSSI_ALERT_HI_BIT /* (1) */
+#define BTA_BLE_RSSI_ALERT_RANGE_BIT \
+ BTM_BLE_RSSI_ALERT_RANGE_BIT /* (1 << 1) */
+#define BTA_BLE_RSSI_ALERT_LO_BIT BTM_BLE_RSSI_ALERT_LO_BIT /* (1 << 2) */
+typedef uint8_t tBTA_DM_BLE_RSSI_ALERT_MASK;
+
+typedef void(tBTA_DM_BLE_RSSI_CBACK)(const RawAddress& bd_addr,
+ tBTA_DM_BLE_RSSI_ALERT_TYPE alert_type,
+ int8_t rssi);
+
+typedef int8_t tBTA_DM_RSSI_VALUE;
+typedef uint8_t tBTA_DM_LINK_QUALITY_VALUE;
+
+typedef uint8_t tBTA_SIG_STRENGTH_MASK;
+
/* Security Callback Events */
+#define BTA_DM_ENABLE_EVT 0 /* Enable Event */
+#define BTA_DM_DISABLE_EVT 1 /* Disable Event */
#define BTA_DM_PIN_REQ_EVT 2 /* PIN request. */
#define BTA_DM_AUTH_CMPL_EVT 3 /* Authentication complete indication. */
#define BTA_DM_AUTHORIZE_EVT 4 /* Authorization request. */
#define BTA_DM_LINK_UP_EVT 5 /* Connection UP event */
#define BTA_DM_LINK_DOWN_EVT 6 /* Connection DOWN event */
+#define BTA_DM_SIG_STRENGTH_EVT \
+ 7 /* Signal strength for bluetooth connection \
+ */
+#define BTA_DM_BUSY_LEVEL_EVT 8 /* System busy level */
#define BTA_DM_BOND_CANCEL_CMPL_EVT 9 /* Bond cancel complete indication */
#define BTA_DM_SP_CFM_REQ_EVT \
10 /* Simple Pairing User Confirmation request. \
*/
#define BTA_DM_SP_KEY_NOTIF_EVT 11 /* Simple Pairing Passkey Notification */
+#define BTA_DM_SP_RMT_OOB_EVT 12 /* Simple Pairing Remote OOB Data request. */
+#define BTA_DM_SP_KEYPRESS_EVT 13 /* Key press notification event. */
+#define BTA_DM_ROLE_CHG_EVT 14 /* Role Change event. */
#define BTA_DM_BLE_KEY_EVT 15 /* BLE SMP key event for peer device keys */
#define BTA_DM_BLE_SEC_REQ_EVT 16 /* BLE SMP security request */
#define BTA_DM_BLE_PASSKEY_NOTIF_EVT 17 /* SMP passkey notification event */
@@ -210,16 +374,18 @@ typedef uint8_t tBTA_DM_BLE_RSSI_ALERT_TYPE;
23 /* Simple Pairing Remote OOB Extended Data request. */
#define BTA_DM_BLE_AUTH_CMPL_EVT 24 /* BLE Auth complete */
#define BTA_DM_DEV_UNPAIRED_EVT 25
+#define BTA_DM_HW_ERROR_EVT 26 /* BT Chip H/W error */
#define BTA_DM_LE_FEATURES_READ \
27 /* Cotroller specific LE features are read \
*/
#define BTA_DM_ENER_INFO_READ 28 /* Energy info read */
#define BTA_DM_BLE_SC_OOB_REQ_EVT 29 /* SMP SC OOB request event */
#define BTA_DM_BLE_CONSENT_REQ_EVT 30 /* SMP consent request event */
-#define BTA_DM_BLE_SC_CR_LOC_OOB_EVT \
- 31 /* SMP SC Create Local OOB request event */
typedef uint8_t tBTA_DM_SEC_EVT;
+/* Structure associated with BTA_DM_ENABLE_EVT */
+typedef struct { tBTA_STATUS status; } tBTA_DM_ENABLE;
+
/* Structure associated with BTA_DM_PIN_REQ_EVT */
typedef struct {
/* Note: First 3 data members must be, bd_addr, dev_class, and bd_name in
@@ -238,26 +404,72 @@ typedef struct {
*/
#define BTA_DM_AUTH_CONVERT_SMP_CODE(x) (BTA_DM_AUTH_FAIL_BASE + (x))
+#define BTA_DM_AUTH_SMP_PASSKEY_FAIL \
+ (BTA_DM_AUTH_FAIL_BASE + SMP_PASSKEY_ENTRY_FAIL)
+#define BTA_DM_AUTH_SMP_OOB_FAIL (BTA_DM_AUTH_FAIL_BASE + SMP_OOB_FAIL)
#define BTA_DM_AUTH_SMP_PAIR_AUTH_FAIL \
(BTA_DM_AUTH_FAIL_BASE + SMP_PAIR_AUTH_FAIL)
#define BTA_DM_AUTH_SMP_CONFIRM_VALUE_FAIL \
(BTA_DM_AUTH_FAIL_BASE + SMP_CONFIRM_VALUE_ERR)
#define BTA_DM_AUTH_SMP_PAIR_NOT_SUPPORT \
(BTA_DM_AUTH_FAIL_BASE + SMP_PAIR_NOT_SUPPORT)
+#define BTA_DM_AUTH_SMP_ENC_KEY_SIZE (BTA_DM_AUTH_FAIL_BASE + SMP_ENC_KEY_SIZE)
+#define BTA_DM_AUTH_SMP_INVALID_CMD (BTA_DM_AUTH_FAIL_BASE + SMP_INVALID_CMD)
#define BTA_DM_AUTH_SMP_UNKNOWN_ERR \
(BTA_DM_AUTH_FAIL_BASE + SMP_PAIR_FAIL_UNKNOWN)
+#define BTA_DM_AUTH_SMP_REPEATED_ATTEMPT \
+ (BTA_DM_AUTH_FAIL_BASE + SMP_REPEATED_ATTEMPTS)
+#define BTA_DM_AUTH_SMP_INVALID_PARAMETERS \
+ (BTA_DM_AUTH_FAIL_BASE + SMP_INVALID_PARAMETERS)
+#define BTA_DM_AUTH_SMP_INTERNAL_ERR \
+ (BTA_DM_AUTH_FAIL_BASE + SMP_PAIR_INTERNAL_ERR)
+#define BTA_DM_AUTH_SMP_UNKNOWN_IO (BTA_DM_AUTH_FAIL_BASE + SMP_UNKNOWN_IO_CAP)
+#define BTA_DM_AUTH_SMP_INIT_FAIL (BTA_DM_AUTH_FAIL_BASE + SMP_INIT_FAIL)
+#define BTA_DM_AUTH_SMP_CONFIRM_FAIL (BTA_DM_AUTH_FAIL_BASE + SMP_CONFIRM_FAIL)
+#define BTA_DM_AUTH_SMP_BUSY (BTA_DM_AUTH_FAIL_BASE + SMP_BUSY)
+#define BTA_DM_AUTH_SMP_ENC_FAIL (BTA_DM_AUTH_FAIL_BASE + SMP_ENC_FAIL)
+#define BTA_DM_AUTH_SMP_RSP_TIMEOUT (BTA_DM_AUTH_FAIL_BASE + SMP_RSP_TIMEOUT)
#define BTA_DM_AUTH_SMP_CONN_TOUT (BTA_DM_AUTH_FAIL_BASE + SMP_CONN_TOUT)
+/* connection parameter boundary value and dummy value */
+#define BTA_DM_BLE_SCAN_INT_MIN BTM_BLE_SCAN_INT_MIN
+#define BTA_DM_BLE_SCAN_INT_MAX BTM_BLE_SCAN_INT_MAX
+#define BTA_DM_BLE_SCAN_WIN_MIN BTM_BLE_SCAN_WIN_MIN
+#define BTA_DM_BLE_SCAN_WIN_MAX BTM_BLE_SCAN_WIN_MAX
+#define BTA_DM_BLE_CONN_INT_MIN BTM_BLE_CONN_INT_MIN
+#define BTA_DM_BLE_CONN_INT_MAX BTM_BLE_CONN_INT_MAX
+#define BTA_DM_BLE_CONN_LATENCY_MAX BTM_BLE_CONN_LATENCY_MAX
+#define BTA_DM_BLE_CONN_SUP_TOUT_MIN BTM_BLE_CONN_SUP_TOUT_MIN
+#define BTA_DM_BLE_CONN_SUP_TOUT_MAX BTM_BLE_CONN_SUP_TOUT_MAX
+#define BTA_DM_BLE_CONN_PARAM_UNDEF \
+ BTM_BLE_CONN_PARAM_UNDEF /* use this value when a specific value not to be \
+ overwritten */
+
+#define BTA_LE_KEY_PENC \
+ BTM_LE_KEY_PENC /* encryption information of peer device */
+#define BTA_LE_KEY_PID BTM_LE_KEY_PID /* identity key of the peer device */
+#define BTA_LE_KEY_PCSRK BTM_LE_KEY_PCSRK /* peer SRK */
+#define BTA_LE_KEY_LENC \
+ BTM_LE_KEY_LENC /* master role security information:div */
+#define BTA_LE_KEY_LID BTM_LE_KEY_LID /* master device ID key */
+#define BTA_LE_KEY_LCSRK \
+ BTM_LE_KEY_LCSRK /* local CSRK has been deliver to peer */
typedef uint8_t tBTA_LE_KEY_TYPE; /* can be used as a bit mask */
+typedef tBTM_LE_PENC_KEYS tBTA_LE_PENC_KEYS;
+typedef tBTM_LE_PCSRK_KEYS tBTA_LE_PCSRK_KEYS;
+typedef tBTM_LE_LENC_KEYS tBTA_LE_LENC_KEYS;
+typedef tBTM_LE_LCSRK_KEYS tBTA_LE_LCSRK_KEYS;
+typedef tBTM_LE_PID_KEYS tBTA_LE_PID_KEYS;
+
typedef union {
- tBTM_LE_PENC_KEYS penc_key; /* received peer encryption key */
- tBTM_LE_PCSRK_KEYS psrk_key; /* received peer device SRK */
- tBTM_LE_PID_KEYS pid_key; /* peer device ID key */
- tBTM_LE_LENC_KEYS
+ tBTA_LE_PENC_KEYS penc_key; /* received peer encryption key */
+ tBTA_LE_PCSRK_KEYS psrk_key; /* received peer device SRK */
+ tBTA_LE_PID_KEYS pid_key; /* peer device ID key */
+ tBTA_LE_LENC_KEYS
lenc_key; /* local encryption reproduction keys LTK = = d1(ER,DIV,0)*/
- tBTM_LE_LCSRK_KEYS lcsrk_key; /* local device CSRK = d1(ER,DIV,1)*/
- tBTM_LE_PID_KEYS lid_key; /* local device ID key for the particular remote */
+ tBTA_LE_LCSRK_KEYS lcsrk_key; /* local device CSRK = d1(ER,DIV,1)*/
+ tBTA_LE_PID_KEYS lid_key; /* local device ID key for the particular remote */
} tBTA_LE_KEY_VALUE;
#define BTA_BLE_LOCAL_KEY_TYPE_ID 1
@@ -272,6 +484,7 @@ typedef struct {
#define BTA_DM_SEC_GRANTED BTA_SUCCESS
#define BTA_DM_SEC_PAIR_NOT_SPT BTA_DM_AUTH_SMP_PAIR_NOT_SUPPORT
+#define BTA_DM_SEC_REP_ATTEMPTS BTA_DM_AUTH_SMP_REPEATED_ATTEMPT
typedef uint8_t tBTA_DM_BLE_SEC_GRANT;
/* Structure associated with BTA_DM_BLE_SEC_REQ_EVT */
@@ -294,26 +507,80 @@ typedef struct {
LinkKey key; /* Link key associated with peer device. */
uint8_t key_type; /* The type of Link Key */
bool success; /* true of authentication succeeded, false if failed. */
- tHCI_REASON
- fail_reason; /* The HCI reason/error code for when success=false */
+ uint8_t fail_reason; /* The HCI reason/error code for when success=false */
tBLE_ADDR_TYPE addr_type; /* Peer device address type */
tBT_DEVICE_TYPE dev_type;
} tBTA_DM_AUTH_CMPL;
+/* Structure associated with BTA_DM_AUTHORIZE_EVT */
+typedef struct {
+ RawAddress bd_addr; /* BD address peer device. */
+ BD_NAME bd_name; /* Name of peer device. */
+ tBTA_SERVICE_ID service; /* Service ID to authorize. */
+ DEV_CLASS dev_class;
+} tBTA_DM_AUTHORIZE;
+
/* Structure associated with BTA_DM_LINK_UP_EVT */
typedef struct {
RawAddress bd_addr; /* BD address peer device. */
+ tBTA_TRANSPORT link_type;
} tBTA_DM_LINK_UP;
/* Structure associated with BTA_DM_LINK_DOWN_EVT */
typedef struct {
RawAddress bd_addr; /* BD address peer device. */
+ uint8_t status; /* connection open/closed */
+ bool is_removed; /* true if device is removed when link is down */
+ tBTA_TRANSPORT link_type;
} tBTA_DM_LINK_DOWN;
+/* Structure associated with BTA_DM_ROLE_CHG_EVT */
+typedef struct {
+ RawAddress bd_addr; /* BD address peer device. */
+ uint8_t new_role; /* the new connection role */
+} tBTA_DM_ROLE_CHG;
+
+/* Structure associated with BTA_DM_BUSY_LEVEL_EVT */
+typedef struct {
+ uint8_t level; /* when paging or inquiring, level is 10.
+ Otherwise, the number of ACL links */
+ uint8_t level_flags; /* indicates individual flags */
+} tBTA_DM_BUSY_LEVEL;
+
+#define BTA_IO_CAP_OUT BTM_IO_CAP_OUT /* 0 DisplayOnly */
+#define BTA_IO_CAP_IO BTM_IO_CAP_IO /* 1 DisplayYesNo */
+#define BTA_IO_CAP_IN BTM_IO_CAP_IN /* 2 KeyboardOnly */
+#define BTA_IO_CAP_NONE BTM_IO_CAP_NONE /* 3 NoInputNoOutput */
+#define BTA_IO_CAP_KBDISP BTM_IO_CAP_KBDISP /* 4 Keyboard display */
+typedef tBTM_IO_CAP tBTA_IO_CAP;
+
+#define BTA_AUTH_SP_NO \
+ BTM_AUTH_SP_NO /* 0 MITM Protection Not Required - Single \
+ Profile/non-bonding \
+ Numeric comparison with automatic accept allowed */
#define BTA_AUTH_SP_YES \
BTM_AUTH_SP_YES /* 1 MITM Protection Required - Single Profile/non-bonding \
Use IO Capabilities to determine authentication procedure \
*/
+#define BTA_AUTH_AP_NO \
+ BTM_AUTH_AP_NO /* 2 MITM Protection Not Required - All Profiles/dedicated \
+ bonding \
+ Numeric comparison with automatic accept allowed */
+#define BTA_AUTH_AP_YES \
+ BTM_AUTH_AP_YES /* 3 MITM Protection Required - All Profiles/dedicated \
+ bonding \
+ Use IO Capabilities to determine authentication procedure \
+ */
+#define BTA_AUTH_SPGB_NO \
+ BTM_AUTH_SPGB_NO /* 4 MITM Protection Not Required - Single Profiles/general \
+ bonding \
+ Numeric comparison with automatic accept allowed */
+#define BTA_AUTH_SPGB_YES \
+ BTM_AUTH_SPGB_YES /* 5 MITM Protection Required - Single Profiles/general \
+ bonding \
+ Use IO Capabilities to determine authentication \
+ procedure */
+typedef tBTM_AUTH_REQ tBTA_AUTH_REQ;
#define BTA_AUTH_DD_BOND \
BTM_AUTH_DD_BOND /* 2 this bit is set for dedicated bonding */
@@ -322,7 +589,22 @@ typedef struct {
#define BTA_AUTH_BONDS \
BTM_AUTH_BONDS /* 6 the general/dedicated bonding bits */
+#define BTA_LE_AUTH_NO_BOND BTM_LE_AUTH_REQ_NO_BOND /* 0*/
+#define BTA_LE_AUTH_BOND BTM_LE_AUTH_REQ_BOND /* 1 << 0 */
+#define BTA_LE_AUTH_REQ_MITM BTM_LE_AUTH_REQ_MITM /* 1 << 2 */
+
+#define BTA_LE_AUTH_REQ_SC_ONLY BTM_LE_AUTH_REQ_SC_ONLY /* 1 << 3 */
+#define BTA_LE_AUTH_REQ_SC_BOND BTM_LE_AUTH_REQ_SC_BOND /* 1001 */
+#define BTA_LE_AUTH_REQ_SC_MITM BTM_LE_AUTH_REQ_SC_MITM /* 1100 */
#define BTA_LE_AUTH_REQ_SC_MITM_BOND BTM_LE_AUTH_REQ_SC_MITM_BOND /* 1101 */
+typedef tBTM_LE_AUTH_REQ
+ tBTA_LE_AUTH_REQ; /* combination of the above bit pattern */
+
+#define BTA_OOB_NONE BTM_OOB_NONE
+#define BTA_OOB_PRESENT BTM_OOB_PRESENT
+#define BTA_OOB_UNKNOWN BTM_OOB_UNKNOWN
+
+typedef tBTM_OOB_DATA tBTA_OOB_DATA;
/* Structure associated with BTA_DM_SP_CFM_REQ_EVT */
typedef struct {
@@ -334,12 +616,27 @@ typedef struct {
uint32_t num_val; /* the numeric value for comparison. If just_works, do not
show this number to UI */
bool just_works; /* true, if "Just Works" association model */
- tBTM_AUTH_REQ loc_auth_req; /* Authentication required for local device */
- tBTM_AUTH_REQ rmt_auth_req; /* Authentication required for peer device */
- tBTM_IO_CAP loc_io_caps; /* IO Capabilities of local device */
- tBTM_AUTH_REQ rmt_io_caps; /* IO Capabilities of remote device */
+ tBTA_AUTH_REQ loc_auth_req; /* Authentication required for local device */
+ tBTA_AUTH_REQ rmt_auth_req; /* Authentication required for peer device */
+ tBTA_IO_CAP loc_io_caps; /* IO Capabilities of local device */
+ tBTA_AUTH_REQ rmt_io_caps; /* IO Capabilities of remote device */
} tBTA_DM_SP_CFM_REQ;
+enum {
+ BTA_SP_KEY_STARTED, /* passkey entry started */
+ BTA_SP_KEY_ENTERED, /* passkey digit entered */
+ BTA_SP_KEY_ERASED, /* passkey digit erased */
+ BTA_SP_KEY_CLEARED, /* passkey cleared */
+ BTA_SP_KEY_COMPLT /* passkey entry completed */
+};
+typedef uint8_t tBTA_SP_KEY_TYPE;
+
+/* Structure associated with BTA_DM_SP_KEYPRESS_EVT */
+typedef struct {
+ RawAddress bd_addr; /* peer address */
+ tBTA_SP_KEY_TYPE notif_type;
+} tBTA_DM_SP_KEY_PRESS;
+
/* Structure associated with BTA_DM_SP_KEY_NOTIF_EVT */
typedef struct {
/* Note: First 3 data members must be, bd_addr, dev_class, and bd_name in
@@ -365,27 +662,26 @@ typedef struct {
tBTA_STATUS result; /* true of bond cancel succeeded, false if failed. */
} tBTA_DM_BOND_CANCEL_CMPL;
-typedef struct {
- Octet16 local_oob_c; /* Local OOB Data Confirmation/Commitment */
- Octet16 local_oob_r; /* Local OOB Data Randomizer */
-} tBTA_DM_LOC_OOB_DATA;
-
/* Union of all security callback structures */
typedef union {
+ tBTA_DM_ENABLE enable; /* BTA enabled */
tBTA_DM_PIN_REQ pin_req; /* PIN request. */
tBTA_DM_AUTH_CMPL auth_cmpl; /* Authentication complete indication. */
+ tBTA_DM_AUTHORIZE authorize; /* Authorization request. */
tBTA_DM_LINK_UP link_up; /* ACL connection down event */
tBTA_DM_LINK_DOWN link_down; /* ACL connection down event */
+ tBTA_DM_BUSY_LEVEL busy_level; /* System busy level */
tBTA_DM_SP_CFM_REQ cfm_req; /* user confirm request */
tBTA_DM_SP_KEY_NOTIF key_notif; /* passkey notification */
tBTA_DM_SP_RMT_OOB rmt_oob; /* remote oob */
tBTA_DM_BOND_CANCEL_CMPL
bond_cancel_cmpl; /* Bond Cancel Complete indication */
+ tBTA_DM_SP_KEY_PRESS key_press; /* key press notification event */
+ tBTA_DM_ROLE_CHG role_chg; /* role change event */
tBTA_DM_BLE_SEC_REQ ble_req; /* BLE SMP related request */
tBTA_DM_BLE_KEY ble_key; /* BLE SMP keys used when pairing */
tBTA_BLE_LOCAL_ID_KEYS ble_id_keys; /* IR event */
Octet16 ble_er; /* ER event data */
- tBTA_DM_LOC_OOB_DATA local_oob_data; /* Local OOB data generated by us */
} tBTA_DM_SEC;
/* Security callback */
@@ -401,10 +697,14 @@ typedef void(tBTA_DM_SEC_CBACK)(tBTA_DM_SEC_EVT event, tBTA_DM_SEC* p_data);
#define BTA_DM_DISC_BLE_RES_EVT \
3 /* Discovery result for BLE GATT based servoce on a peer device. */
#define BTA_DM_DISC_CMPL_EVT 4 /* Discovery complete. */
+#define BTA_DM_DI_DISC_CMPL_EVT 5 /* Discovery complete. */
#define BTA_DM_SEARCH_CANCEL_CMPL_EVT 6 /* Search cancelled */
typedef uint8_t tBTA_DM_SEARCH_EVT;
+#define BTA_DM_INQ_RES_IGNORE_RSSI \
+ BTM_INQ_RES_IGNORE_RSSI /* 0x7f RSSI value not supplied (ignore it) */
+
/* Structure associated with BTA_DM_INQ_RES_EVT */
typedef struct {
RawAddress bd_addr; /* BD address peer device. */
@@ -418,7 +718,7 @@ typedef struct {
uint8_t* p_eir; /* received EIR */
uint16_t eir_len; /* received EIR length */
uint8_t inq_result_type;
- tBLE_ADDR_TYPE ble_addr_type;
+ uint8_t ble_addr_type;
uint16_t ble_evt_type;
uint8_t ble_primary_phy;
uint8_t ble_secondary_phy;
@@ -434,11 +734,20 @@ typedef struct {
uint8_t num_resps; /* Number of inquiry responses. */
} tBTA_DM_INQ_CMPL;
+/* Structure associated with BTA_DM_DI_DISC_CMPL_EVT */
+typedef struct {
+ RawAddress bd_addr; /* BD address peer device. */
+ uint8_t num_record; /* Number of DI record */
+ tBTA_STATUS result;
+} tBTA_DM_DI_DISC_CMPL;
+
/* Structure associated with BTA_DM_DISC_RES_EVT */
typedef struct {
RawAddress bd_addr; /* BD address peer device. */
BD_NAME bd_name; /* Name of peer device. */
tBTA_SERVICE_MASK services; /* Services found on peer device. */
+ uint8_t* p_raw_data; /* Raw data for discovery DB */
+ uint32_t raw_data_size; /* size of raw data */
tBT_DEVICE_TYPE device_type; /* device type in case it is BLE device */
uint32_t num_uuids;
bluetooth::Uuid* p_uuid_list;
@@ -449,8 +758,7 @@ typedef struct {
typedef struct {
RawAddress bd_addr; /* BD address peer device. */
BD_NAME bd_name; /* Name of peer device. */
- std::vector<bluetooth::Uuid>*
- services; /* GATT based Services UUID found on peer device. */
+ bluetooth::Uuid service; /* GATT based Services UUID found on peer device. */
} tBTA_DM_DISC_BLE_RES;
/* Union of all search callback structures */
@@ -460,6 +768,8 @@ typedef union {
tBTA_DM_DISC_RES disc_res; /* Discovery result for a peer device. */
tBTA_DM_DISC_BLE_RES
disc_ble_res; /* discovery result for GATT based service */
+ tBTA_DM_DI_DISC_CMPL di_disc; /* DI discovery result for a peer device */
+
} tBTA_DM_SEARCH;
/* Search callback */
@@ -471,58 +781,89 @@ typedef void(tBTA_DM_EXEC_CBACK)(void* p_param);
/* Encryption callback*/
typedef void(tBTA_DM_ENCRYPT_CBACK)(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
+ tBTA_TRANSPORT transport,
tBTA_STATUS result);
+#define BTA_DM_BLE_SEC_NONE BTM_BLE_SEC_NONE
+#define BTA_DM_BLE_SEC_ENCRYPT BTM_BLE_SEC_ENCRYPT
+#define BTA_DM_BLE_SEC_NO_MITM BTM_BLE_SEC_ENCRYPT_NO_MITM
+#define BTA_DM_BLE_SEC_MITM BTM_BLE_SEC_ENCRYPT_MITM
+typedef tBTM_BLE_SEC_ACT tBTA_DM_BLE_SEC_ACT;
+
+typedef tBTM_BLE_TX_TIME_MS tBTA_DM_BLE_TX_TIME_MS;
+typedef tBTM_BLE_RX_TIME_MS tBTA_DM_BLE_RX_TIME_MS;
+typedef tBTM_BLE_IDLE_TIME_MS tBTA_DM_BLE_IDLE_TIME_MS;
+typedef tBTM_BLE_ENERGY_USED tBTA_DM_BLE_ENERGY_USED;
+
#define BTA_DM_CONTRL_UNKNOWN 0 /* Unknown state */
+#define BTA_DM_CONTRL_ACTIVE 1 /* ACL link on, SCO link ongoing, sniff mode */
+#define BTA_DM_CONTRL_SCAN \
+ 2 /* Scan state - paging/inquiry/trying to \
+ connect*/
+#define BTA_DM_CONTRL_IDLE \
+ 3 /* Idle state - page scan, LE advt, inquiry scan \
+ */
typedef uint8_t tBTA_DM_CONTRL_STATE;
-typedef void(tBTA_BLE_ENERGY_INFO_CBACK)(tBTM_BLE_TX_TIME_MS tx_time,
- tBTM_BLE_RX_TIME_MS rx_time,
- tBTM_BLE_IDLE_TIME_MS idle_time,
- tBTM_BLE_ENERGY_USED energy_used,
+typedef uint8_t tBTA_DM_BLE_ADV_STATE;
+typedef uint8_t tBTA_DM_BLE_ADV_INFO_PRESENT;
+typedef uint8_t tBTA_DM_BLE_RSSI_VALUE;
+typedef uint16_t tBTA_DM_BLE_ADV_INFO_TIMESTAMP;
+
+typedef void(tBTA_BLE_ENERGY_INFO_CBACK)(tBTA_DM_BLE_TX_TIME_MS tx_time,
+ tBTA_DM_BLE_RX_TIME_MS rx_time,
+ tBTA_DM_BLE_IDLE_TIME_MS idle_time,
+ tBTA_DM_BLE_ENERGY_USED energy_used,
tBTA_DM_CONTRL_STATE ctrl_state,
tBTA_STATUS status);
/* Maximum service name length */
#define BTA_SERVICE_NAME_LEN 35
+#define BTA_SERVICE_DESP_LEN BTA_SERVICE_NAME_LEN
+#define BTA_PROVIDER_NAME_LEN BTA_SERVICE_NAME_LEN
+
+/* link policy masks */
+#define BTA_DM_LP_SWITCH HCI_ENABLE_MASTER_SLAVE_SWITCH
+#define BTA_DM_LP_HOLD HCI_ENABLE_HOLD_MODE
+#define BTA_DM_LP_SNIFF HCI_ENABLE_SNIFF_MODE
+#define BTA_DM_LP_PARK HCI_ENABLE_PARK_MODE
+typedef uint16_t tBTA_DM_LP_MASK;
+
+/* power mode actions */
+#define BTA_DM_PM_NO_ACTION 0x00 /* no change to the current pm setting */
+#define BTA_DM_PM_PARK 0x10 /* prefers park mode */
+#define BTA_DM_PM_SNIFF 0x20 /* prefers sniff mode */
+#define BTA_DM_PM_SNIFF1 0x21 /* prefers sniff1 mode */
+#define BTA_DM_PM_SNIFF2 0x22 /* prefers sniff2 mode */
+#define BTA_DM_PM_SNIFF3 0x23 /* prefers sniff3 mode */
+#define BTA_DM_PM_SNIFF4 0x24 /* prefers sniff4 mode */
+#define BTA_DM_PM_SNIFF5 0x25 /* prefers sniff5 mode */
+#define BTA_DM_PM_SNIFF6 0x26 /* prefers sniff6 mode */
+#define BTA_DM_PM_SNIFF7 0x27 /* prefers sniff7 mode */
+#define BTA_DM_PM_SNIFF_USER0 \
+ 0x28 /* prefers user-defined sniff0 mode (testtool only) */
+#define BTA_DM_PM_SNIFF_USER1 \
+ 0x29 /* prefers user-defined sniff1 mode (testtool only) */
+#define BTA_DM_PM_ACTIVE 0x40 /* prefers active mode */
+#define BTA_DM_PM_RETRY 0x80 /* retry power mode based on current settings */
+#define BTA_DM_PM_SUSPEND 0x04 /* prefers suspend mode */
+#define BTA_DM_PM_NO_PREF \
+ 0x01 /* service has no prefernce on power mode setting. eg. connection to \
+ service got closed */
-typedef enum : uint8_t {
- /* power mode actions */
- BTA_DM_PM_NO_ACTION = 0x00, /* no change to the current pm setting */
- BTA_DM_PM_PARK = 0x10, /* prefers park mode */
- BTA_DM_PM_SNIFF = 0x20, /* prefers sniff mode */
- BTA_DM_PM_SNIFF1 = 0x21, /* prefers sniff1 mode */
- BTA_DM_PM_SNIFF2 = 0x22, /* prefers sniff2 mode */
- BTA_DM_PM_SNIFF3 = 0x23, /* prefers sniff3 mode */
- BTA_DM_PM_SNIFF4 = 0x24, /* prefers sniff4 mode */
- BTA_DM_PM_SNIFF5 = 0x25, /* prefers sniff5 mode */
- BTA_DM_PM_SNIFF6 = 0x26, /* prefers sniff6 mode */
- BTA_DM_PM_SNIFF7 = 0x27, /* prefers sniff7 mode */
- BTA_DM_PM_SNIFF_USER0 =
- 0x28, /* prefers user-defined sniff0 mode (testtool only) */
- BTA_DM_PM_SNIFF_USER1 =
- 0x29, /* prefers user-defined sniff1 mode (testtool only) */
- BTA_DM_PM_ACTIVE = 0x40, /* prefers active mode */
- BTA_DM_PM_RETRY = 0x80, /* retry power mode based on current settings */
- BTA_DM_PM_SUSPEND = 0x04, /* prefers suspend mode */
- BTA_DM_PM_NO_PREF = 0x01, /* service has no preference on power mode setting.
- eg. connection to \ service got closed */
- BTA_DM_PM_SNIFF_MASK = 0x0f, // Masks the sniff submode
-} tBTA_DM_PM_ACTION_BITMASK;
typedef uint8_t tBTA_DM_PM_ACTION;
/* index to bta_dm_ssr_spec */
-enum {
- BTA_DM_PM_SSR0 = 0,
- /* BTA_DM_PM_SSR1 will be dedicated for \
- HH SSR setting entry, no other profile can use it */
- BTA_DM_PM_SSR1 = 1,
- BTA_DM_PM_SSR2 = 2,
- BTA_DM_PM_SSR3 = 3,
- BTA_DM_PM_SSR4 = 4,
-};
+#define BTA_DM_PM_SSR0 0
+#define BTA_DM_PM_SSR1 \
+ 1 /* BTA_DM_PM_SSR1 will be dedicated for \
+ HH SSR setting entry, no other profile can use it */
+#define BTA_DM_PM_SSR2 2
+#define BTA_DM_PM_SSR3 3
+#define BTA_DM_PM_SSR4 4
+#define BTA_DM_PM_SSR5 5
+#define BTA_DM_PM_SSR6 6
#define BTA_DM_PM_NUM_EVTS 9
@@ -633,14 +974,52 @@ enum {
#define BTA_DM_PM_PARK_TIMEOUT 0
#endif
+/* Switch callback events */
+#define BTA_DM_SWITCH_CMPL_EVT 0 /* Completion of the Switch API */
+
+typedef uint8_t tBTA_DM_SWITCH_EVT;
+typedef void(tBTA_DM_SWITCH_CBACK)(tBTA_DM_SWITCH_EVT event,
+ tBTA_STATUS status);
+
+/* Audio routing out configuration */
+#define BTA_DM_ROUTE_NONE 0x00 /* No Audio output */
+#define BTA_DM_ROUTE_DAC 0x01 /* routing over analog output */
+#define BTA_DM_ROUTE_I2S 0x02 /* routing over digital (I2S) output */
+#define BTA_DM_ROUTE_BT_MONO 0x04 /* routing over SCO */
+#define BTA_DM_ROUTE_BT_STEREO 0x08 /* routing over BT Stereo */
+#define BTA_DM_ROUTE_HOST 0x10 /* routing over Host */
+#define BTA_DM_ROUTE_FMTX 0x20 /* routing over FMTX */
+#define BTA_DM_ROUTE_FMRX 0x40 /* routing over FMRX */
+#define BTA_DM_ROUTE_BTSNK 0x80 /* routing over BT SNK */
+
+typedef uint8_t tBTA_DM_ROUTE_PATH;
+
/* Device Identification (DI) data structure
*/
+/* Used to set the DI record */
+typedef tSDP_DI_RECORD tBTA_DI_RECORD;
+/* Used to get the DI record */
+typedef tSDP_DI_GET_RECORD tBTA_DI_GET_RECORD;
+/* SDP discovery database */
+typedef tSDP_DISCOVERY_DB tBTA_DISCOVERY_DB;
#ifndef BTA_DI_NUM_MAX
#define BTA_DI_NUM_MAX 3
#endif
+/* Device features mask definitions */
+#define BTA_FEATURE_BYTES_PER_PAGE BTM_FEATURE_BYTES_PER_PAGE
+#define BTA_EXT_FEATURES_PAGE_MAX BTM_EXT_FEATURES_PAGE_MAX
+/* ACL type
+*/
+#define BTA_DM_LINK_TYPE_BR_EDR 0x01
+#define BTA_DM_LINK_TYPE_LE 0x02
+#define BTA_DM_LINK_TYPE_ALL 0xFF
+typedef uint8_t tBTA_DM_LINK_TYPE;
+
#define IMMEDIATE_DELY_MODE 0x00
+#define ONFOUND_DELY_MODE 0x01
+#define BATCH_DELY_MODE 0x02
#define ALLOW_ALL_FILTER 0x00
#define LOWEST_RSSI_VALUE 129
@@ -648,7 +1027,36 @@ enum {
* External Function Declarations
****************************************************************************/
-void BTA_dm_init();
+/*******************************************************************************
+ *
+ * Function BTA_EnableBluetooth
+ *
+ * Description This function initializes BTA and prepares BTA and the
+ * Bluetooth protocol stack for use. This function is
+ * typically called at startup or when Bluetooth services
+ * are required by the phone. This function must be called
+ * before calling any other API function.
+ *
+ *
+ * Returns BTA_SUCCESS if successful.
+ * BTA_FAIL if internal failure.
+ *
+ ******************************************************************************/
+extern tBTA_STATUS BTA_EnableBluetooth(tBTA_DM_SEC_CBACK* p_cback);
+
+/*******************************************************************************
+ *
+ * Function BTA_DisableBluetooth
+ *
+ * Description This function disables BTA and the Bluetooth protocol
+ * stack. It is called when BTA is no longer being used
+ * by any application in the system.
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern tBTA_STATUS BTA_DisableBluetooth(void);
/*******************************************************************************
*
@@ -664,6 +1072,18 @@ extern void BTA_EnableTestMode(void);
/*******************************************************************************
*
+ * Function BTA_DisableTestMode
+ *
+ * Description Disable bluetooth device under test mode
+ *
+ *
+ * Returns None
+ *
+ ******************************************************************************/
+extern void BTA_DisableTestMode(void);
+
+/*******************************************************************************
+ *
* Function BTA_DmSetDeviceName
*
* Description This function sets the Bluetooth name of the local device.
@@ -688,7 +1108,8 @@ extern void BTA_DmSetDeviceName(char* p_name);
* Returns void
*
******************************************************************************/
-extern bool BTA_DmSetVisibility(bt_scan_mode_t mode);
+extern void BTA_DmSetVisibility(tBTA_DM_DISC disc_mode, tBTA_DM_CONN conn_mode,
+ uint8_t pairable_mode, uint8_t conn_filter);
/*******************************************************************************
*
@@ -698,15 +1119,14 @@ extern bool BTA_DmSetVisibility(bt_scan_mode_t mode);
* first performs an inquiry; for each device found from the
* inquiry it gets the remote name of the device. If
* parameter services is nonzero, service discovery will be
- * performed on each device for the services specified. If the
- * parameter is_bonding_or_sdp is true, the request will be
- * queued until bonding or sdp completes
+ * performed on each device for the services specified.
*
*
* Returns void
*
******************************************************************************/
-extern void BTA_DmSearch(tBTA_DM_SEARCH_CBACK* p_cback, bool is_bonding_or_sdp);
+extern void BTA_DmSearch(tBTA_DM_INQ* p_dm_inq, tBTA_SERVICE_MASK services,
+ tBTA_DM_SEARCH_CBACK* p_cback);
/*******************************************************************************
*
@@ -733,8 +1153,23 @@ extern void BTA_DmSearchCancel(void);
*
******************************************************************************/
extern void BTA_DmDiscover(const RawAddress& bd_addr,
- tBTA_DM_SEARCH_CBACK* p_cback,
- tBT_TRANSPORT transport, bool is_bonding_or_sdp);
+ tBTA_SERVICE_MASK services,
+ tBTA_DM_SEARCH_CBACK* p_cback, bool sdp_search);
+
+/*******************************************************************************
+ *
+ * Function BTA_DmDiscoverUUID
+ *
+ * Description This function performs service discovery for the services
+ * of a particular peer device.
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTA_DmDiscoverUUID(const RawAddress& bd_addr,
+ const bluetooth::Uuid& uuid,
+ tBTA_DM_SEARCH_CBACK* p_cback, bool sdp_search);
/*******************************************************************************
*
@@ -763,7 +1198,7 @@ tBTA_STATUS BTA_DmGetCachedRemoteName(const RawAddress& remote_device,
*
******************************************************************************/
extern void BTA_DmBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type);
+ tBTA_TRANSPORT transport);
/*******************************************************************************
*
@@ -832,7 +1267,9 @@ extern void BTA_DmConfirm(const RawAddress& bd_addr, bool accept);
*
******************************************************************************/
extern void BTA_DmAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
- const LinkKey& link_key, uint8_t key_type,
+ const LinkKey& link_key,
+ tBTA_SERVICE_MASK trusted_mask, bool is_trusted,
+ uint8_t key_type, tBTA_IO_CAP io_cap,
uint8_t pin_length);
/*******************************************************************************
@@ -868,42 +1305,14 @@ extern void BTA_GetEirService(uint8_t* p_eir, size_t eir_len,
/*******************************************************************************
*
- * Function BTA_AddEirUuid
- *
- * Description Request to add a new service class UUID to the local
- * device's EIR data.
- *
- * Parameters uuid16 - The service class UUID you wish to add
- *
- * Returns void
- *
- ******************************************************************************/
-extern void BTA_AddEirUuid(uint16_t uuid16);
-
-/*******************************************************************************
- *
- * Function BTA_RemoveEirUuid
- *
- * Description Request to remove a service class UID from the local
- * device's EIR data.
- *
- * Parameters uuid16 - The service class UUID you wish to remove
- *
- * Returns void
- *
- ******************************************************************************/
-extern void BTA_RemoveEirUuid(uint16_t uuid16);
-
-/*******************************************************************************
- *
* Function BTA_DmGetConnectionState
*
* Description Returns whether the remote device is currently connected.
*
- * Returns true if the device is NOT connected, false otherwise.
+ * Returns 0 if the device is NOT connected.
*
******************************************************************************/
-extern bool BTA_DmGetConnectionState(const RawAddress& bd_addr);
+extern uint16_t BTA_DmGetConnectionState(const RawAddress& bd_addr);
/*******************************************************************************
*
@@ -914,7 +1323,7 @@ extern bool BTA_DmGetConnectionState(const RawAddress& bd_addr);
* Returns BTA_SUCCESS if record set sucessfully, otherwise error code.
*
******************************************************************************/
-extern tBTA_STATUS BTA_DmSetLocalDiRecord(tSDP_DI_RECORD* p_device_info,
+extern tBTA_STATUS BTA_DmSetLocalDiRecord(tBTA_DI_RECORD* p_device_info,
uint32_t* p_handle);
/*******************************************************************************
@@ -935,7 +1344,7 @@ extern tBTA_STATUS BTA_DmSetLocalDiRecord(tSDP_DI_RECORD* p_device_info,
*
******************************************************************************/
extern void BTA_DmCloseACL(const RawAddress& bd_addr, bool remove_dev,
- tBT_TRANSPORT transport);
+ tBTA_TRANSPORT transport);
/* BLE related API functions */
/*******************************************************************************
@@ -1021,7 +1430,7 @@ extern void BTA_DmAddBleDevice(const RawAddress& bd_addr,
******************************************************************************/
extern void BTA_DmAddBleKey(const RawAddress& bd_addr,
tBTA_LE_KEY_VALUE* p_le_key,
- tBTM_LE_KEY_TYPE key_type);
+ tBTA_LE_KEY_TYPE key_type);
/*******************************************************************************
*
@@ -1033,7 +1442,7 @@ extern void BTA_DmAddBleKey(const RawAddress& bd_addr,
* Parameters: bd_addr - BD address of the peripheral
* min_conn_int - minimum preferred connection interval
* max_conn_int - maximum preferred connection interval
- * peripheral_latency - preferred peripheral latency
+ * slave_latency - preferred slave latency
* supervision_tout - preferred supervision timeout
*
*
@@ -1043,11 +1452,93 @@ extern void BTA_DmAddBleKey(const RawAddress& bd_addr,
extern void BTA_DmSetBlePrefConnParams(const RawAddress& bd_addr,
uint16_t min_conn_int,
uint16_t max_conn_int,
- uint16_t peripheral_latency,
+ uint16_t slave_latency,
uint16_t supervision_tout);
/*******************************************************************************
*
+ * Function BTA_DmSetBleConnScanParams
+ *
+ * Description This function is called to set scan parameters used in
+ * BLE connection request
+ *
+ * Parameters: scan_interval - scan interval
+ * scan_window - scan window
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTA_DmSetBleConnScanParams(uint32_t scan_interval,
+ uint32_t scan_window);
+
+/*******************************************************************************
+ *
+ * Function BTA_DmSearchExt
+ *
+ * Description This function searches for peer Bluetooth devices. It
+ * performs an inquiry and gets the remote name for devices.
+ * Service discovery is done if services is non zero
+ *
+ * Parameters p_dm_inq: inquiry conditions
+ * services: if service is not empty, service discovery will be
+ * done.
+ * for all GATT based service condition, put
+ * num_uuid, and p_uuid is the pointer to the list of
+ * UUID values.
+ * p_cback: callback functino when search is completed.
+ *
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTA_DmSearchExt(tBTA_DM_INQ* p_dm_inq,
+ tBTA_SERVICE_MASK_EXT* p_services,
+ tBTA_DM_SEARCH_CBACK* p_cback);
+
+/*******************************************************************************
+ *
+ * Function BTA_DmDiscoverExt
+ *
+ * Description This function does service discovery for services of a
+ * peer device. When services.num_uuid is 0, it indicates all
+ * GATT based services are to be searched; other wise a list of
+ * UUID of interested services should be provided through
+ * services.p_uuid.
+ *
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTA_DmDiscoverExt(const RawAddress& bd_addr,
+ tBTA_SERVICE_MASK_EXT* p_services,
+ tBTA_DM_SEARCH_CBACK* p_cback, bool sdp_search);
+
+/*******************************************************************************
+ *
+ * Function BTA_DmDiscoverByTransport
+ *
+ * Description This function does service discovery on particular transport
+ * for services of a
+ * peer device. When services.num_uuid is 0, it indicates all
+ * GATT based services are to be searched; other wise a list of
+ * UUID of interested services should be provided through
+ * p_services->p_uuid.
+ *
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTA_DmDiscoverByTransport(const RawAddress& bd_addr,
+ tBTA_SERVICE_MASK_EXT* p_services,
+ tBTA_DM_SEARCH_CBACK* p_cback,
+ bool sdp_search,
+ tBTA_TRANSPORT transport);
+
+/*******************************************************************************
+ *
* Function BTA_DmSetEncryption
*
* Description This function is called to ensure that connection is
@@ -1070,9 +1561,9 @@ extern void BTA_DmSetBlePrefConnParams(const RawAddress& bd_addr,
*
******************************************************************************/
extern void BTA_DmSetEncryption(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
+ tBTA_TRANSPORT transport,
tBTA_DM_ENCRYPT_CBACK* p_callback,
- tBTM_BLE_SEC_ACT sec_act);
+ tBTA_DM_BLE_SEC_ACT sec_act);
/*******************************************************************************
*
@@ -1130,7 +1621,7 @@ extern void BTA_DmBleEnableRemotePrivacy(const RawAddress& bd_addr,
* Parameters: bd_addr - BD address of the peer
* min_int - minimum connection interval, [0x0004 ~ 0x4000]
* max_int - maximum connection interval, [0x0004 ~ 0x4000]
- * latency - peripheral latency [0 ~ 500]
+ * latency - slave latency [0 ~ 500]
* timeout - supervision timeout [0x000a ~ 0xc80]
*
* Returns void
@@ -1151,7 +1642,8 @@ extern void BTA_DmBleUpdateConnectionParams(const RawAddress& bd_addr,
* Returns void
*
******************************************************************************/
-extern void BTA_DmBleRequestMaxTxDataLength(const RawAddress& remote_device);
+extern void BTA_DmBleSetDataLength(const RawAddress& remote_device,
+ uint16_t tx_data_length);
/*******************************************************************************
*
@@ -1178,4 +1670,16 @@ extern void BTA_DmBleGetEnergyInfo(tBTA_BLE_ENERGY_INFO_CBACK* p_cmpl_cback);
******************************************************************************/
extern void BTA_VendorInit(void);
+/*******************************************************************************
+ *
+ * Function BTA_BrcmCleanup
+ *
+ * Description This function frees up Broadcom specific VS specific dynamic
+ * memory
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTA_VendorCleanup(void);
+
#endif /* BTA_API_H */
diff --git a/bta/include/bta_ar_api.h b/bta/include/bta_ar_api.h
index 6b57096e8..b2a875322 100644
--- a/bta/include/bta_ar_api.h
+++ b/bta/include/bta_ar_api.h
@@ -26,10 +26,12 @@
#ifndef BTA_AR_API_H
#define BTA_AR_API_H
-#include <cstdint>
-
-#include "bta/sys/bta_sys.h"
-#include "stack/include/avdt_api.h"
+#include "avct_api.h"
+#include "avdt_api.h"
+#include "avrc_api.h"
+#include "bta_av_api.h"
+#include "bta_sys.h"
+#include "sdp_api.h"
/*****************************************************************************
* Constants and data types
@@ -58,7 +60,8 @@ extern void bta_ar_init(void);
* Returns void
*
******************************************************************************/
-extern void bta_ar_reg_avdt(AvdtpRcb* p_reg, tAVDT_CTRL_CBACK* p_cback);
+extern void bta_ar_reg_avdt(AvdtpRcb* p_reg, tAVDT_CTRL_CBACK* p_cback,
+ tBTA_SYS_ID sys_id);
/*******************************************************************************
*
@@ -69,7 +72,7 @@ extern void bta_ar_reg_avdt(AvdtpRcb* p_reg, tAVDT_CTRL_CBACK* p_cback);
* Returns void
*
******************************************************************************/
-extern void bta_ar_dereg_avdt();
+extern void bta_ar_dereg_avdt(tBTA_SYS_ID sys_id);
/*******************************************************************************
*
@@ -95,7 +98,8 @@ extern void bta_ar_avdt_conn(tBTA_SYS_ID sys_id, const RawAddress& bd_addr,
* Returns void
*
******************************************************************************/
-extern void bta_ar_reg_avct();
+extern void bta_ar_reg_avct(uint16_t mtu, uint16_t mtu_br, uint8_t sec_mask,
+ tBTA_SYS_ID sys_id);
/*******************************************************************************
*
@@ -106,7 +110,7 @@ extern void bta_ar_reg_avct();
* Returns void
*
******************************************************************************/
-extern void bta_ar_dereg_avct();
+extern void bta_ar_dereg_avct(tBTA_SYS_ID sys_id);
/******************************************************************************
*
@@ -119,7 +123,8 @@ extern void bta_ar_dereg_avct();
*****************************************************************************/
extern void bta_ar_reg_avrc(uint16_t service_uuid, const char* p_service_name,
const char* p_provider_name, uint16_t categories,
- bool browse_supported, uint16_t profile_version);
+ tBTA_SYS_ID sys_id, bool browse_supported,
+ uint16_t profile_version);
/******************************************************************************
*
@@ -131,6 +136,6 @@ extern void bta_ar_reg_avrc(uint16_t service_uuid, const char* p_service_name,
* Returns void
*
*****************************************************************************/
-extern void bta_ar_dereg_avrc(uint16_t service_uuid);
+extern void bta_ar_dereg_avrc(uint16_t service_uuid, tBTA_SYS_ID sys_id);
#endif /* BTA_AR_API_H */
diff --git a/bta/include/bta_av_api.h b/bta/include/bta_av_api.h
index 4591bbaef..82be54d34 100644
--- a/bta/include/bta_av_api.h
+++ b/bta/include/bta_av_api.h
@@ -26,15 +26,20 @@
#ifndef BTA_AV_API_H
#define BTA_AV_API_H
-#include <cstdint>
-
-#include "bta/include/bta_api.h"
-#include "stack/include/avrc_defs.h"
-#include "stack/include/bt_types.h"
+#include "a2dp_codec_api.h"
+#include "avdt_api.h"
+#include "avrc_api.h"
+#include "bta_api.h"
/*****************************************************************************
* Constants and data types
****************************************************************************/
+/* Set to TRUE if seperate authorization prompt desired for AVCTP besides A2DP
+ * authorization */
+/* Typically FALSE when AVRCP is used in conjunction with A2DP */
+#ifndef BTA_AV_WITH_AVCTP_AUTHORIZATION
+#define BTA_AV_WITH_AVCTP_AUTHORIZATION FALSE
+#endif
/* AV status values */
#define BTA_AV_SUCCESS 0 /* successful operation */
@@ -61,6 +66,7 @@ typedef uint8_t tBTA_AV_STATUS;
#define BTA_AV_FEAT_MULTI_AV \
0x0080 /* use multi-av, if controller supports it */
#define BTA_AV_FEAT_BROWSE 0x0010 /* use browsing channel */
+#define BTA_AV_FEAT_MASTER 0x0100 /* stream only as master role */
#define BTA_AV_FEAT_ADV_CTRL \
0x0200 /* remote control Advanced Control command/response */
#define BTA_AV_FEAT_DELAY_RPT 0x0400 /* allow delay reporting */
@@ -376,8 +382,14 @@ typedef void (*tBTA_AV_ACT)(tBTA_AV_SCB* p_cb, tBTA_AV_DATA* p_data);
/* AV configuration structure */
typedef struct {
uint32_t company_id; /* AVRCP Company ID */
+ uint16_t avrc_mtu; /* AVRCP MTU at L2CAP for control channel */
+ uint16_t avrc_br_mtu; /* AVRCP MTU at L2CAP for browsing channel */
uint16_t avrc_ct_cat; /* AVRCP controller categories */
uint16_t avrc_tg_cat; /* AVRCP target categories */
+ uint16_t sig_mtu; /* AVDTP signaling channel MTU at L2CAP */
+ uint16_t audio_mtu; /* AVDTP audio transport channel MTU at L2CAP */
+ const uint16_t*
+ p_audio_flush_to; /* AVDTP audio transport channel flush timeout */
uint16_t audio_mqs; /* AVDTP audio channel max data queue size */
bool avrc_group; /* true, to accept AVRC 1.3 group nevigation command */
uint8_t num_co_ids; /* company id count in p_meta_co_ids */
@@ -388,6 +400,7 @@ typedef struct {
p_meta_co_ids; /* the metadata Get Capabilities response for company id */
const uint8_t* p_meta_evt_ids; /* the the metadata Get Capabilities response
for event id */
+ const tBTA_AV_ACT* p_act_tbl; /* action function table for audio stream */
char avrc_controller_name[BTA_SERVICE_NAME_LEN]; /* Default AVRCP controller
name */
char avrc_target_name[BTA_SERVICE_NAME_LEN]; /* Default AVRCP target name*/
@@ -410,7 +423,8 @@ typedef struct {
* Returns void
*
******************************************************************************/
-void BTA_AvEnable(tBTA_AV_FEAT features, tBTA_AV_CBACK* p_cback);
+void BTA_AvEnable(tBTA_SEC sec_mask, tBTA_AV_FEAT features,
+ tBTA_AV_CBACK* p_cback);
/*******************************************************************************
*
@@ -464,7 +478,7 @@ void BTA_AvDeregister(tBTA_AV_HNDL hndl);
*
******************************************************************************/
void BTA_AvOpen(const RawAddress& bd_addr, tBTA_AV_HNDL handle, bool use_rc,
- uint16_t uuid);
+ tBTA_SEC sec_mask, uint16_t uuid);
/*******************************************************************************
*
@@ -486,7 +500,7 @@ void BTA_AvClose(tBTA_AV_HNDL handle);
* Returns void
*
******************************************************************************/
-void BTA_AvDisconnect(tBTA_AV_HNDL handle);
+void BTA_AvDisconnect(const RawAddress& bd_addr);
/*******************************************************************************
*
diff --git a/bta/include/bta_av_ci.h b/bta/include/bta_av_ci.h
index fedba46a3..07b59e6fa 100644
--- a/bta/include/bta_av_ci.h
+++ b/bta/include/bta_av_ci.h
@@ -24,9 +24,7 @@
#ifndef BTA_AV_CI_H
#define BTA_AV_CI_H
-#include <cstdint>
-
-#include "bta/include/bta_av_api.h"
+#include "bta_av_api.h"
/*****************************************************************************
* Function Declarations
diff --git a/bta/include/bta_av_co.h b/bta/include/bta_av_co.h
index 28ed5c4c6..f83ff23b0 100644
--- a/bta/include/bta_av_co.h
+++ b/bta/include/bta_av_co.h
@@ -24,13 +24,8 @@
#ifndef BTA_AV_CO_H
#define BTA_AV_CO_H
-#include <cstdint>
-
-#include "bta/include/bta_av_api.h"
-#include "include/hardware/bt_av.h"
-#include "stack/include/a2dp_error_codes.h"
-#include "stack/include/avdt_api.h"
-#include "types/raw_address.h"
+#include "bta_av_api.h"
+#include "l2c_api.h"
/*****************************************************************************
* Constants and data types
@@ -231,16 +226,13 @@ void bta_av_co_audio_update_mtu(tBTA_AV_HNDL bta_av_handle,
/*******************************************************************************
**
- ** Function bta_av_co_get_scmst_info
+ ** Function bta_av_co_content_protect_is_active
**
- ** Description Get the SCMS-T information for the specific peer
+ ** Description Get the current configuration of content protection
**
- ** Returns btav_a2dp_scmst_info_t.
- ** It contains the information of SCMS-T which are the SCMS-T
- ** enable status for the specific peer and the SCMS-T header
- ** if SCMS-T is enabled.
+ ** Returns TRUE if the current streaming has CP, FALSE otherwise
**
******************************************************************************/
-btav_a2dp_scmst_info_t bta_av_co_get_scmst_info(const RawAddress& peer_address);
+bool bta_av_co_content_protect_is_active(const RawAddress& peer_address);
#endif /* BTA_AV_CO_H */
diff --git a/bta/include/bta_dm_acl.h b/bta/include/bta_dm_acl.h
deleted file mode 100644
index aaaa94eb3..000000000
--- a/bta/include/bta_dm_acl.h
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include "stack/include/bt_types.h"
-#include "stack/include/hci_error_code.h"
-#include "types/bt_transport.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
-
-void BTA_dm_acl_up(const RawAddress bd_addr, tBT_TRANSPORT transport);
-void BTA_dm_acl_down(const RawAddress bd_addr, tBT_TRANSPORT transport);
-void BTA_dm_report_role_change(const RawAddress bd_addr, tHCI_ROLE new_role,
- tHCI_STATUS hci_status);
-void BTA_dm_notify_remote_features_complete(const RawAddress bd_addr);
diff --git a/bta/include/bta_dm_api.h b/bta/include/bta_dm_api.h
index 1ad4fd6ea..8fdff7697 100644
--- a/bta/include/bta_dm_api.h
+++ b/bta/include/bta_dm_api.h
@@ -24,7 +24,7 @@
#ifndef BTA_DM_API_H
#define BTA_DM_API_H
-#include "types/raw_address.h"
+#include "stack/include/bt_types.h"
// Brings connection to active mode
void bta_dm_pm_active(const RawAddress& peer_addr);
diff --git a/bta/include/bta_dm_ci.h b/bta/include/bta_dm_ci.h
index a7b621092..a89854a37 100644
--- a/bta/include/bta_dm_ci.h
+++ b/bta/include/bta_dm_ci.h
@@ -24,14 +24,24 @@
#ifndef BTA_DM_CI_H
#define BTA_DM_CI_H
-#include <cstdint>
-
-#include "stack/include/bt_types.h"
-#include "types/raw_address.h"
+#include "bta_api.h"
/*****************************************************************************
* Function Declarations
****************************************************************************/
+/*******************************************************************************
+ *
+ * Function bta_dm_ci_io_req
+ *
+ * Description This function must be called in response to function
+ * bta_dm_co_io_req(), if *p_oob_data is set to BTA_OOB_UNKNOWN
+ * by bta_dm_co_io_req().
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void bta_dm_ci_io_req(const RawAddress& bd_addr, tBTA_IO_CAP io_cap,
+ tBTA_OOB_DATA oob_data, tBTA_AUTH_REQ auth_req);
/*******************************************************************************
*
diff --git a/bta/include/bta_dm_co.h b/bta/include/bta_dm_co.h
index 49a821076..4561cbf46 100644
--- a/bta/include/bta_dm_co.h
+++ b/bta/include/bta_dm_co.h
@@ -24,10 +24,8 @@
#ifndef BTA_DM_CO_H
#define BTA_DM_CO_H
-#include "bta/include/bta_api.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_api_types.h"
-#include "types/raw_address.h"
+#include "bta_sys.h"
+#include "btm_api.h"
#ifndef BTA_SCO_OUT_PKT_SIZE
#define BTA_SCO_OUT_PKT_SIZE BTM_SCO_DATA_SIZE_MAX
@@ -54,9 +52,9 @@
* Returns void.
*
******************************************************************************/
-extern void bta_dm_co_io_req(const RawAddress& bd_addr, tBTM_IO_CAP* p_io_cap,
- tBTM_OOB_DATA* p_oob_data,
- tBTM_AUTH_REQ* p_auth_req, bool is_orig);
+extern void bta_dm_co_io_req(const RawAddress& bd_addr, tBTA_IO_CAP* p_io_cap,
+ tBTA_OOB_DATA* p_oob_data,
+ tBTA_AUTH_REQ* p_auth_req, bool is_orig);
/*******************************************************************************
*
@@ -75,8 +73,23 @@ extern void bta_dm_co_io_req(const RawAddress& bd_addr, tBTM_IO_CAP* p_io_cap,
* Returns void.
*
******************************************************************************/
-extern void bta_dm_co_io_rsp(const RawAddress& bd_addr, tBTM_IO_CAP io_cap,
- tBTM_OOB_DATA oob_data, tBTM_AUTH_REQ auth_req);
+extern void bta_dm_co_io_rsp(const RawAddress& bd_addr, tBTA_IO_CAP io_cap,
+ tBTA_OOB_DATA oob_data, tBTA_AUTH_REQ auth_req);
+
+/*******************************************************************************
+ *
+ * Function bta_dm_co_lk_upgrade
+ *
+ * Description This callout function is executed by DM to check if the
+ * platform wants allow link key upgrade
+ *
+ * Parameters bd_addr - The peer device
+ * *p_upgrade - true, if link key upgrade is desired.
+ *
+ * Returns void.
+ *
+ ******************************************************************************/
+extern void bta_dm_co_lk_upgrade(const RawAddress& bd_addr, bool* p_upgrade);
/*******************************************************************************
*
@@ -177,9 +190,9 @@ extern void bta_dm_sco_co_in_data(BT_HDR* p_buf, tBTM_SCO_DATA_FLAG status);
*
******************************************************************************/
extern void bta_dm_co_ble_io_req(
- const RawAddress& bd_addr, tBTM_IO_CAP* p_io_cap, tBTM_OOB_DATA* p_oob_data,
- tBTM_LE_AUTH_REQ* p_auth_req, uint8_t* p_max_key_size,
- tBTM_LE_KEY_TYPE* p_init_key, tBTM_LE_KEY_TYPE* p_resp_key);
+ const RawAddress& bd_addr, tBTA_IO_CAP* p_io_cap, tBTA_OOB_DATA* p_oob_data,
+ tBTA_LE_AUTH_REQ* p_auth_req, uint8_t* p_max_key_size,
+ tBTA_LE_KEY_TYPE* p_init_key, tBTA_LE_KEY_TYPE* p_resp_key);
/*******************************************************************************
*
diff --git a/bta/include/bta_gatt_api.h b/bta/include/bta_gatt_api.h
index 7027741d8..41151f813 100644
--- a/bta/include/bta_gatt_api.h
+++ b/bta/include/bta_gatt_api.h
@@ -25,15 +25,13 @@
#ifndef BTA_GATT_API_H
#define BTA_GATT_API_H
+#include "bta/gatt/database.h"
+#include "bta_api.h"
+#include "gatt_api.h"
+
#include <base/callback_forward.h>
-#include <list>
-#include <string>
#include <vector>
-#include "bta/gatt/database.h"
-#include "stack/include/gatt_api.h"
-#include "types/raw_address.h"
-
#ifndef BTA_GATT_DEBUG
#define BTA_GATT_DEBUG false
#endif
@@ -51,52 +49,24 @@ typedef struct {
} __attribute__((packed)) tBTA_GATT_ID;
/* Client callback function events */
-typedef enum : uint8_t {
- BTA_GATTC_DEREG_EVT = 1, /* GATT client deregistered event */
- BTA_GATTC_OPEN_EVT = 2, /* GATTC open request status event */
- BTA_GATTC_CLOSE_EVT = 5, /* GATTC close request status event */
- BTA_GATTC_SEARCH_CMPL_EVT = 6, /* GATT discovery complete event */
- BTA_GATTC_SEARCH_RES_EVT = 7, /* GATT discovery result event */
- BTA_GATTC_SRVC_DISC_DONE_EVT = 8, /* GATT service discovery done event */
- BTA_GATTC_NOTIF_EVT = 10, /* GATT attribute notification event */
- BTA_GATTC_EXEC_EVT = 12, /* execute write complete event */
- BTA_GATTC_ACL_EVT = 13, /* ACL up event */
- BTA_GATTC_CANCEL_OPEN_EVT = 14, /* cancel open event */
- BTA_GATTC_SRVC_CHG_EVT = 15, /* service change event */
- BTA_GATTC_ENC_CMPL_CB_EVT = 17, /* encryption complete callback event */
- BTA_GATTC_CFG_MTU_EVT = 18, /* configure MTU complete event */
- BTA_GATTC_CONGEST_EVT = 24, /* Congestion event */
- BTA_GATTC_PHY_UPDATE_EVT = 25, /* PHY change event */
- BTA_GATTC_CONN_UPDATE_EVT = 26, /* Connection parameters update event */
-} tBTA_GATTC_EVT;
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string gatt_client_event_text(const tBTA_GATTC_EVT& event) {
- switch (event) {
- CASE_RETURN_TEXT(BTA_GATTC_DEREG_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_OPEN_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_CLOSE_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_SEARCH_CMPL_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_SEARCH_RES_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_SRVC_DISC_DONE_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_NOTIF_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_EXEC_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_ACL_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_CANCEL_OPEN_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_SRVC_CHG_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_ENC_CMPL_CB_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_CFG_MTU_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_CONGEST_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_PHY_UPDATE_EVT);
- CASE_RETURN_TEXT(BTA_GATTC_CONN_UPDATE_EVT);
- default:
- return std::string("UNKNOWN[%hhu]", event);
- }
-}
-#undef CASE_RETURN_TEXT
+#define BTA_GATTC_DEREG_EVT 1 /* GATT client deregistered event */
+#define BTA_GATTC_OPEN_EVT 2 /* GATTC open request status event */
+#define BTA_GATTC_CLOSE_EVT 5 /* GATTC close request status event */
+#define BTA_GATTC_SEARCH_CMPL_EVT 6 /* GATT discovery complete event */
+#define BTA_GATTC_SEARCH_RES_EVT 7 /* GATT discovery result event */
+#define BTA_GATTC_SRVC_DISC_DONE_EVT 8 /* GATT service discovery done event */
+#define BTA_GATTC_NOTIF_EVT 10 /* GATT attribute notification event */
+#define BTA_GATTC_EXEC_EVT 12 /* execute write complete event */
+#define BTA_GATTC_ACL_EVT 13 /* ACL up event */
+#define BTA_GATTC_CANCEL_OPEN_EVT 14 /* cancel open event */
+#define BTA_GATTC_SRVC_CHG_EVT 15 /* service change event */
+#define BTA_GATTC_ENC_CMPL_CB_EVT 17 /* encryption complete callback event */
+#define BTA_GATTC_CFG_MTU_EVT 18 /* configure MTU complete event */
+#define BTA_GATTC_CONGEST_EVT 24 /* Congestion event */
+#define BTA_GATTC_PHY_UPDATE_EVT 25 /* PHY change event */
+#define BTA_GATTC_CONN_UPDATE_EVT 26 /* Connection parameters update event */
+
+typedef uint8_t tBTA_GATTC_EVT;
typedef struct {
uint16_t unit; /* as UUIUD defined by SIG */
@@ -119,9 +89,14 @@ typedef struct {
uint8_t* p_value;
} tBTA_GATT_UNFMT;
+#define BTA_GATT_CONN_NONE 0x0101 /* 0x0101 no connection to cancel */
+typedef uint16_t tBTA_GATT_REASON;
+
+#define BTA_GATTC_MULTI_MAX GATT_MAX_READ_MULTI_HANDLES
+
typedef struct {
uint8_t num_attr;
- uint16_t handles[GATT_MAX_READ_MULTI_HANDLES];
+ uint16_t handles[BTA_GATTC_MULTI_MAX];
} tBTA_GATTC_MULTI;
/* callback data structure */
@@ -170,16 +145,17 @@ typedef struct {
uint16_t conn_id;
tGATT_IF client_if;
RawAddress remote_bda;
- tBT_TRANSPORT transport;
+ tBTA_TRANSPORT transport;
uint16_t mtu;
} tBTA_GATTC_OPEN;
typedef struct {
- uint16_t conn_id;
tGATT_STATUS status;
+ uint16_t conn_id;
tGATT_IF client_if;
RawAddress remote_bda;
- tGATT_DISCONN_REASON reason;
+ tBTA_GATT_REASON reason; /* disconnect reason code, not useful when connect
+ event is reported */
} tBTA_GATTC_CLOSE;
typedef struct {
@@ -189,7 +165,6 @@ typedef struct {
uint16_t len;
uint8_t value[GATT_MAX_ATTR_LEN];
bool is_notify;
- uint16_t cid;
} tBTA_GATTC_NOTIFY;
typedef struct {
@@ -226,11 +201,6 @@ typedef struct {
tGATT_STATUS status;
} tBTA_GATTC_CONN_UPDATE;
-typedef struct {
- RawAddress remote_bda;
- uint16_t conn_id;
-} tBTA_GATTC_SERVICE_CHANGED;
-
typedef union {
tGATT_STATUS status;
@@ -249,7 +219,6 @@ typedef union {
tBTA_GATTC_CONGEST congest;
tBTA_GATTC_PHY_UPDATE phy_update;
tBTA_GATTC_CONN_UPDATE conn_update;
- tBTA_GATTC_SERVICE_CHANGED service_changed;
} tBTA_GATTC;
/* GATTC enable callback function */
@@ -336,7 +305,8 @@ typedef struct {
tGATT_IF server_if;
RawAddress remote_bda;
uint16_t conn_id;
- tBT_TRANSPORT transport;
+ tBTA_GATT_REASON reason; /* report disconnect reason */
+ tGATT_TRANSPORT transport;
} tBTA_GATTS_CONN;
typedef struct {
@@ -417,7 +387,7 @@ using BtaAppRegisterCallback =
* p_client_cb - pointer to the application callback function.
**/
extern void BTA_GATTC_AppRegister(tBTA_GATTC_CBACK* p_client_cb,
- BtaAppRegisterCallback cb, bool eatt_support);
+ BtaAppRegisterCallback cb);
/*******************************************************************************
*
@@ -447,9 +417,10 @@ extern void BTA_GATTC_AppDeregister(tGATT_IF client_if);
*
******************************************************************************/
extern void BTA_GATTC_Open(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct, bool opportunistic);
+ bool is_direct, tGATT_TRANSPORT transport,
+ bool opportunistic);
extern void BTA_GATTC_Open(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct, tBT_TRANSPORT transport,
+ bool is_direct, tGATT_TRANSPORT transport,
bool opportunistic, uint8_t initiating_phys);
/*******************************************************************************
@@ -499,7 +470,7 @@ extern void BTA_GATTC_Close(uint16_t conn_id);
*
******************************************************************************/
extern void BTA_GATTC_ServiceSearchRequest(uint16_t conn_id,
- const bluetooth::Uuid* p_srvc_uuid);
+ bluetooth::Uuid* p_srvc_uuid);
/**
* This function is called to send "Find service by UUID" request. Used only for
@@ -585,8 +556,6 @@ typedef void (*GATT_READ_OP_CB)(uint16_t conn_id, tGATT_STATUS status,
void* data);
typedef void (*GATT_WRITE_OP_CB)(uint16_t conn_id, tGATT_STATUS status,
uint16_t handle, void* data);
-typedef void (*GATT_CONFIGURE_MTU_OP_CB)(uint16_t conn_id, tGATT_STATUS status,
- void* data);
/*******************************************************************************
*
@@ -674,12 +643,12 @@ void BTA_GATTC_WriteCharDescr(uint16_t conn_id, uint16_t handle,
* Description This function is called to send handle value confirmation.
*
* Parameters conn_id - connection ID.
- * cid - channel id
+ * handle - characteristic handle to confirm.
*
* Returns None
*
******************************************************************************/
-extern void BTA_GATTC_SendIndConfirm(uint16_t conn_id, uint16_t cid);
+extern void BTA_GATTC_SendIndConfirm(uint16_t conn_id, uint16_t handle);
/*******************************************************************************
*
@@ -794,9 +763,6 @@ extern void BTA_GATTC_Refresh(const RawAddress& remote_bda);
*
******************************************************************************/
extern void BTA_GATTC_ConfigureMTU(uint16_t conn_id, uint16_t mtu);
-extern void BTA_GATTC_ConfigureMTU(uint16_t conn_id, uint16_t mtu,
- GATT_CONFIGURE_MTU_OP_CB callback,
- void* cb_data);
/*******************************************************************************
* BTA GATT Server API
@@ -837,13 +803,12 @@ extern void BTA_GATTS_Disable(void);
*
* Parameters p_app_uuid - applicaiton UUID
* p_cback - pointer to the application callback function.
- * eatt_support: indicate eatt support.
*
* Returns None
*
******************************************************************************/
extern void BTA_GATTS_AppRegister(const bluetooth::Uuid& app_uuid,
- tBTA_GATTS_CBACK* p_cback, bool eatt_support);
+ tBTA_GATTS_CBACK* p_cback);
/*******************************************************************************
*
@@ -873,7 +838,7 @@ extern void BTA_GATTS_AppDeregister(tGATT_IF server_if);
* service cannot be added.
*
******************************************************************************/
-typedef base::Callback<void(tGATT_STATUS status, int server_if,
+typedef base::Callback<void(uint8_t status, int server_if,
std::vector<btgatt_db_element_t> service)>
BTA_GATTS_AddServiceCb;
@@ -961,7 +926,7 @@ extern void BTA_GATTS_SendRsp(uint16_t conn_id, uint32_t trans_id,
*
******************************************************************************/
extern void BTA_GATTS_Open(tGATT_IF server_if, const RawAddress& remote_bda,
- bool is_direct, tBT_TRANSPORT transport);
+ bool is_direct, tGATT_TRANSPORT transport);
/*******************************************************************************
*
diff --git a/bta/include/bta_gatt_queue.h b/bta/include/bta_gatt_queue.h
index 5e2a3a917..963fc138a 100644
--- a/bta/include/bta_gatt_queue.h
+++ b/bta/include/bta_gatt_queue.h
@@ -14,13 +14,12 @@
* limitations under the License.
*/
-#include <cstdint>
+#include <vector>
+
#include <list>
#include <unordered_map>
#include <unordered_set>
-#include <vector>
-
-#include "bta/include/bta_gatt_api.h"
+#include "bta_gatt_api.h"
/* BTA GATTC implementation does not allow for multiple commands queuing. So one
* client making calls to BTA_GATTC_ReadCharacteristic, BTA_GATTC_ReadCharDescr,
@@ -48,7 +47,6 @@ class BtaGattQueue {
std::vector<uint8_t> value,
tGATT_WRITE_TYPE write_type, GATT_WRITE_OP_CB cb,
void* cb_data);
- static void ConfigureMtu(uint16_t conn_id, uint16_t mtu);
/* Holds pending GATT operations */
struct gatt_operation {
@@ -58,8 +56,6 @@ class BtaGattQueue {
void* read_cb_data;
GATT_WRITE_OP_CB write_cb;
void* write_cb_data;
- GATT_CONFIGURE_MTU_OP_CB mtu_cb;
- void* mtu_cb_data;
/* write-specific fields */
tGATT_WRITE_TYPE write_type;
@@ -74,11 +70,9 @@ class BtaGattQueue {
uint8_t* value, void* data);
static void gatt_write_op_finished(uint16_t conn_id, tGATT_STATUS status,
uint16_t handle, void* data);
- static void gatt_configure_mtu_op_finished(uint16_t conn_id,
- tGATT_STATUS status, void* data);
// maps connection id to operations waiting for execution
static std::unordered_map<uint16_t, std::list<gatt_operation>> gatt_op_queue;
// contain connection ids that currently execute operations
static std::unordered_set<uint16_t> gatt_op_queue_executing;
-};
+}; \ No newline at end of file
diff --git a/bta/include/bta_gatts_co.h b/bta/include/bta_gatts_co.h
index 4ab5cbd52..eb820f7bb 100644
--- a/bta/include/bta_gatts_co.h
+++ b/bta/include/bta_gatts_co.h
@@ -24,7 +24,7 @@
#ifndef BTA_GATTS_CO_H
#define BTA_GATTS_CO_H
-#include "bta/include/bta_gatt_api.h"
+#include "bta_gatt_api.h"
/*******************************************************************************
*
diff --git a/bta/include/bta_hd_api.h b/bta/include/bta_hd_api.h
index 4d89a0ecd..2bb78f12d 100644
--- a/bta/include/bta_hd_api.h
+++ b/bta/include/bta_hd_api.h
@@ -19,11 +19,8 @@
#ifndef BTA_HD_API_H
#define BTA_HD_API_H
-#include <cstdint>
-
-#include "bta/include/bta_api.h"
-#include "stack/include/hiddefs.h"
-#include "types/raw_address.h"
+#include "bta_api.h"
+#include "hidd_api.h"
/*****************************************************************************
* Constants and Type Definitions
diff --git a/bta/include/bta_hearing_aid_api.h b/bta/include/bta_hearing_aid_api.h
index 613802a21..6c4954b09 100644
--- a/bta/include/bta_hearing_aid_api.h
+++ b/bta/include/bta_hearing_aid_api.h
@@ -20,9 +20,7 @@
#include <base/callback_forward.h>
#include <hardware/bt_hearing_aid.h>
-#include <cstdint>
#include <deque>
-#include <functional>
#include <vector>
constexpr uint16_t HEARINGAID_MAX_NUM_UUIDS = 1;
@@ -220,13 +218,13 @@ class HearingAid {
static void DebugDump(int fd);
static void AddFromStorage(const HearingDevice& dev_info,
- uint16_t is_acceptlisted);
+ uint16_t is_white_listed);
static int GetDeviceCount();
virtual void Connect(const RawAddress& address) = 0;
virtual void Disconnect(const RawAddress& address) = 0;
- virtual void AddToAcceptlist(const RawAddress& address) = 0;
+ virtual void AddToWhiteList(const RawAddress& address) = 0;
virtual void SetVolume(int8_t volume) = 0;
};
diff --git a/bta/include/bta_hf_client_api.h b/bta/include/bta_hf_client_api.h
index 32822c2ed..7f460798e 100755
--- a/bta/include/bta_hf_client_api.h
+++ b/bta/include/bta_hf_client_api.h
@@ -25,11 +25,7 @@
#ifndef BTA_HF_CLIENT_API_H
#define BTA_HF_CLIENT_API_H
-#include <cstdint>
-
#include "bta_api.h"
-#include "bta_hfp_api.h"
-#include "types/raw_address.h"
/*****************************************************************************
* Constants and data types
@@ -49,8 +45,7 @@
#define BTA_HF_CLIENT_PEER_ECC 0x00000080 /* Enhanced Call Control */
#define BTA_HF_CLIENT_PEER_EXTERR 0x00000100 /* Extended error codes */
#define BTA_HF_CLIENT_PEER_CODEC 0x00000200 /* Codec Negotiation */
-#define BTA_HF_CLIENT_PEER_HF_IND 0x00000400 /* HF Indicators */
-#define BTA_HF_CLIENT_PEER_ESCO_S4 0x00000800 /* ESCO S4 link setting */
+#define BTA_HF_CLIENT_PEER_S4 0x00000800 /* ESCO S4 link setting */
typedef uint16_t tBTA_HF_CLIENT_PEER_FEAT;
@@ -66,8 +61,7 @@ typedef uint16_t tBTA_HF_CLIENT_PEER_FEAT;
#define BTA_HF_CLIENT_FEAT_ECS 0x00000020 /* Enhanced Call Status */
#define BTA_HF_CLIENT_FEAT_ECC 0x00000040 /* Enhanced Call Control */
#define BTA_HF_CLIENT_FEAT_CODEC 0x00000080 /* Codec Negotiation */
-#define BTA_HF_CLIENT_FEAT_HF_IND 0x00000100 /* HF Indicators */
-#define BTA_HF_CLIENT_FEAT_ESCO_S4 0x00000200 /* ESCO S4 link setting */
+#define BTA_HF_CLIENT_FEAT_S4 0x00000200 /* ESCO S4 link setting */
/* HFP HF extended call handling - masks not related to any spec */
#define BTA_HF_CLIENT_CHLD_REL \
@@ -95,7 +89,7 @@ typedef uint16_t tBTA_HF_CLIENT_CHLD_FEAT;
#define BTA_HF_CLIENT_AT_RESULT_BUSY 3
#define BTA_HF_CLIENT_AT_RESULT_NO_ANSWER 4
#define BTA_HF_CLIENT_AT_RESULT_DELAY 5
-#define BTA_HF_CLIENT_AT_RESULT_REJECTLISTED 6
+#define BTA_HF_CLIENT_AT_RESULT_BLACKLISTED 6
#define BTA_HF_CLIENT_AT_RESULT_CME 7
typedef uint8_t tBTA_HF_CLIENT_AT_RESULT_TYPE;
@@ -171,7 +165,6 @@ typedef uint8_t tBTA_HF_CLIENT_IND_TYPE;
#define BTA_HF_CLIENT_AT_CMD_BLDN 14
#define BTA_HF_CLIENT_AT_CMD_NREC 15
#define BTA_HF_CLIENT_AT_CMD_VENDOR_SPECIFIC_CMD 16
-#define BTA_HF_CLIENT_AT_CMD_BIEV 17
typedef uint8_t tBTA_HF_CLIENT_AT_CMD_TYPE;
@@ -294,7 +287,7 @@ typedef void(tBTA_HF_CLIENT_CBACK)(tBTA_HF_CLIENT_EVT event,
* Returns BTA_SUCCESS if OK, BTA_FAILURE otherwise.
*
******************************************************************************/
-tBTA_STATUS BTA_HfClientEnable(tBTA_HF_CLIENT_CBACK* p_cback,
+tBTA_STATUS BTA_HfClientEnable(tBTA_HF_CLIENT_CBACK* p_cback, tBTA_SEC sec_mask,
tBTA_HF_CLIENT_FEAT features,
const char* p_service_name);
@@ -324,7 +317,8 @@ void BTA_HfClientDisable(void);
* Returns void
*
******************************************************************************/
-void BTA_HfClientOpen(const RawAddress& bd_addr, uint16_t* p_handle);
+void BTA_HfClientOpen(const RawAddress& bd_addr, tBTA_SEC sec_mask,
+ uint16_t* p_handle);
/*******************************************************************************
*
diff --git a/bta/include/bta_hfp_api.h b/bta/include/bta_hfp_api.h
deleted file mode 100644
index a3dd3a97a..000000000
--- a/bta/include/bta_hfp_api.h
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BTA_HFP_API_H
-#define BTA_HFP_API_H
-
-/* HFP Versions */
-#define HFP_HSP_VERSION_UNKNOWN 0x0000
-#define HFP_HSP_VERSION_DONT_CARE 0xFFFF
-#define HFP_VERSION_1_1 0x0101
-#define HFP_VERSION_1_5 0x0105
-#define HFP_VERSION_1_6 0x0106
-#define HFP_VERSION_1_7 0x0107
-
-#define HSP_VERSION_1_0 0x0100
-#define HSP_VERSION_1_2 0x0102
-
-#define HFP_VERSION_CONFIG_KEY "HfpVersion"
-#define HFP_SDP_FEATURES_CONFIG_KEY "HfpSdpFeatures"
-
-/* Default HFP Version */
-#ifndef BTA_HFP_VERSION
-#define BTA_HFP_VERSION HFP_VERSION_1_7
-#endif
-
-#endif /* BTA_HFP_API_H */ \ No newline at end of file
diff --git a/bta/include/bta_hh_api.h b/bta/include/bta_hh_api.h
index 2df707f77..9198b4647 100644
--- a/bta/include/bta_hh_api.h
+++ b/bta/include/bta_hh_api.h
@@ -18,12 +18,12 @@
#ifndef BTA_HH_API_H
#define BTA_HH_API_H
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <string>
+#include "bta_api.h"
+#include "hidh_api.h"
-#include "bta/include/bta_api.h"
-#include "stack/include/hiddefs.h"
+#if (BTA_HH_LE_INCLUDED == TRUE)
+#include "gatt_api.h"
+#endif
/*****************************************************************************
* Constants and Type Definitions
@@ -40,12 +40,6 @@
#define BTA_HH_SSR_MIN_TOUT_DEF 2
#endif
-#ifndef CASE_RETURN_TEXT
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-#endif
-
/* BTA HID Host callback events */
#define BTA_HH_ENABLE_EVT 0 /* HH enabled */
#define BTA_HH_DISABLE_EVT 1 /* HH disabled */
@@ -83,6 +77,7 @@ typedef uint16_t tBTA_HH_EVT;
#define BTA_HH_IDX_INVALID 0xff
#define BTA_HH_MAX_KNOWN HID_HOST_MAX_DEVICES
+#if (BTA_HH_LE_INCLUDED == TRUE)
/* GATT_MAX_PHY_CHANNEL can not exceed 14 for the design of BTA HH */
#if GATT_MAX_PHY_CHANNEL > 14
#define BTA_HH_LE_MAX_KNOWN 14
@@ -91,6 +86,9 @@ typedef uint16_t tBTA_HH_EVT;
#endif
#define BTA_HH_MAX_DEVICE (HID_HOST_MAX_DEVICES + BTA_HH_LE_MAX_KNOWN)
+#else
+#define BTA_HH_MAX_DEVICE HID_HOST_MAX_DEVICES
+#endif
/* invalid device handle */
#define BTA_HH_INVALID_HANDLE 0xff
@@ -117,8 +115,8 @@ typedef uint8_t tBTA_HH_BOOT_RPT_ID;
#define BTA_HH_DEVT_OTHER 0x80
typedef uint8_t tBTA_HH_DEVT;
-typedef enum : uint8_t {
- BTA_HH_OK = 0,
+enum {
+ BTA_HH_OK,
BTA_HH_HS_HID_NOT_READY, /* handshake error : device not ready */
BTA_HH_HS_INVALID_RPT_ID, /* handshake error : invalid report ID */
BTA_HH_HS_TRANS_NOT_SPT, /* handshake error : transaction not spt */
@@ -136,34 +134,17 @@ typedef enum : uint8_t {
BTA_HH_ERR_AUTH_FAILED, /* authentication fail */
BTA_HH_ERR_HDL,
BTA_HH_ERR_SEC
-} tBTA_HH_STATUS;
-
-inline tBTA_HH_STATUS to_bta_hh_status(uint32_t status) {
- return static_cast<tBTA_HH_STATUS>(status);
-}
-
-inline std::string bta_hh_status_text(const tBTA_HH_STATUS& status) {
- switch (status) {
- CASE_RETURN_TEXT(BTA_HH_OK);
- CASE_RETURN_TEXT(BTA_HH_HS_HID_NOT_READY);
- CASE_RETURN_TEXT(BTA_HH_HS_INVALID_RPT_ID);
- CASE_RETURN_TEXT(BTA_HH_HS_TRANS_NOT_SPT);
- CASE_RETURN_TEXT(BTA_HH_HS_INVALID_PARAM);
- CASE_RETURN_TEXT(BTA_HH_HS_ERROR);
- CASE_RETURN_TEXT(BTA_HH_ERR);
- CASE_RETURN_TEXT(BTA_HH_ERR_SDP);
- CASE_RETURN_TEXT(BTA_HH_ERR_PROTO);
- CASE_RETURN_TEXT(BTA_HH_ERR_DB_FULL);
- CASE_RETURN_TEXT(BTA_HH_ERR_TOD_UNSPT);
- CASE_RETURN_TEXT(BTA_HH_ERR_NO_RES);
- CASE_RETURN_TEXT(BTA_HH_ERR_AUTH_FAILED);
- CASE_RETURN_TEXT(BTA_HH_ERR_HDL);
- CASE_RETURN_TEXT(BTA_HH_ERR_SEC);
- default:
- return std::string("UNKNOWN[%hhu]", status);
- }
-}
-
+};
+typedef uint8_t tBTA_HH_STATUS;
+
+#define BTA_HH_VIRTUAL_CABLE HID_VIRTUAL_CABLE
+#define BTA_HH_NORMALLY_CONNECTABLE HID_NORMALLY_CONNECTABLE
+#define BTA_HH_RECONN_INIT HID_RECONN_INIT
+#define BTA_HH_SDP_DISABLE HID_SDP_DISABLE
+#define BTA_HH_BATTERY_POWER HID_BATTERY_POWER
+#define BTA_HH_REMOTE_WAKE HID_REMOTE_WAKE
+#define BTA_HH_SUP_TOUT_AVLBL HID_SUP_TOUT_AVLBL
+#define BTA_HH_SEC_REQUIRED HID_SEC_REQUIRED
typedef uint16_t tBTA_HH_ATTR_MASK;
/* supported type of device and corresponding application ID */
@@ -217,16 +198,13 @@ typedef struct {
uint16_t
ssr_min_tout; /* SSR min timeout, BTA_HH_SSR_PARAM_INVALID if unknown */
uint8_t ctry_code; /*Country Code.*/
+#if (BTA_HH_LE_INCLUDED == TRUE)
#define BTA_HH_LE_REMOTE_WAKE 0x01
#define BTA_HH_LE_NORMAL_CONN 0x02
uint8_t flag;
+#endif
tBTA_HH_DEV_DESCR descriptor;
-
- std::string ToString() const {
- return base::StringPrintf("%04x::%04x::%04x", vendor_id, product_id,
- version);
- }
} tBTA_HH_DEV_DSCP_INFO;
/* callback event data for BTA_HH_OPEN_EVT */
@@ -234,8 +212,10 @@ typedef struct {
RawAddress bda; /* HID device bd address */
tBTA_HH_STATUS status; /* operation status */
uint8_t handle; /* device handle */
+#if (BTA_HH_LE_INCLUDED == TRUE)
bool le_hid; /* is LE devices? */
bool scps_supported; /* scan parameter service supported */
+#endif
} tBTA_HH_CONN;
@@ -331,7 +311,7 @@ typedef void(tBTA_HH_CBACK)(tBTA_HH_EVT event, tBTA_HH* p_data);
* Returns void
*
******************************************************************************/
-extern void BTA_HhEnable(tBTA_HH_CBACK* p_cback);
+extern void BTA_HhEnable(tBTA_SEC sec_mask, tBTA_HH_CBACK* p_cback);
/*******************************************************************************
*
@@ -355,7 +335,8 @@ extern void BTA_HhDisable(void);
* Returns void
*
******************************************************************************/
-extern void BTA_HhOpen(const RawAddress& dev_bda);
+extern void BTA_HhOpen(const RawAddress& dev_bda, tBTA_HH_PROTO_MODE mode,
+ tBTA_SEC sec_mask);
/*******************************************************************************
*
@@ -516,4 +497,25 @@ extern void BTA_HhAddDev(const RawAddress& bda, tBTA_HH_ATTR_MASK attr_mask,
******************************************************************************/
extern void BTA_HhRemoveDev(uint8_t dev_handle);
+/*******************************************************************************
+ *
+ * Parsing Utility Functions
+ *
+ ******************************************************************************/
+/*******************************************************************************
+ *
+ * Function BTA_HhParseBootRpt
+ *
+ * Description This utility function parse a boot mode report.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTA_HhParseBootRpt(tBTA_HH_BOOT_RPT* p_data, uint8_t* p_report,
+ uint16_t report_len);
+
+/* test commands */
+extern void bta_hh_le_hid_read_rpt_clt_cfg(const RawAddress& bd_addr,
+ uint8_t rpt_id);
+
#endif /* BTA_HH_API_H */
diff --git a/bta/include/bta_hh_co.h b/bta/include/bta_hh_co.h
index 13141fe45..44e5a9f68 100644
--- a/bta/include/bta_hh_co.h
+++ b/bta/include/bta_hh_co.h
@@ -24,16 +24,14 @@
#ifndef BTA_HH_CO_H
#define BTA_HH_CO_H
-#include <cstdint>
-
-#include "bta/include/bta_hh_api.h"
+#include "bta_hh_api.h"
typedef struct {
uint16_t rpt_uuid;
uint8_t rpt_id;
tBTA_HH_RPT_TYPE rpt_type;
uint8_t srvc_inst_id;
- uint16_t char_inst_id;
+ uint8_t char_inst_id;
} tBTA_HH_RPT_CACHE_ENTRY;
/*******************************************************************************
@@ -104,6 +102,7 @@ extern void bta_hh_co_set_rpt_rsp(uint8_t dev_handle, uint8_t status);
extern void bta_hh_co_get_rpt_rsp(uint8_t dev_handle, uint8_t status,
uint8_t* p_rpt, uint16_t len);
+#if (BTA_HH_LE_INCLUDED == TRUE)
/*******************************************************************************
*
* Function bta_hh_le_co_rpt_info
@@ -157,4 +156,6 @@ extern tBTA_HH_RPT_CACHE_ENTRY* bta_hh_le_co_cache_load(
extern void bta_hh_le_co_reset_rpt_cache(const RawAddress& remote_bda,
uint8_t app_id);
+#endif /* #if (BTA_HH_LE_INCLUDED == TRUE) */
+
#endif /* BTA_HH_CO_H */
diff --git a/bta/include/bta_jv_api.h b/bta/include/bta_jv_api.h
index 73105aaac..39f72fd8c 100644
--- a/bta/include/bta_jv_api.h
+++ b/bta/include/bta_jv_api.h
@@ -24,13 +24,11 @@
#ifndef BTA_JV_API_H
#define BTA_JV_API_H
-#include <cstdint>
-#include <memory>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_api.h"
-#include "stack/include/l2c_api.h"
+#include "bt_target.h"
+#include "bt_types.h"
+#include "bta_api.h"
+#include "btm_api.h"
+#include "l2c_api.h"
/*****************************************************************************
* Constants and data types
@@ -78,6 +76,8 @@ typedef uint8_t tBTA_JV_STATUS;
enum { BTA_JV_DISC_NONE, BTA_JV_DISC_LIMITED, BTA_JV_DISC_GENERAL };
typedef uint16_t tBTA_JV_DISC;
+#define BTA_JV_ROLE_SLAVE BTM_ROLE_SLAVE
+#define BTA_JV_ROLE_MASTER BTM_ROLE_MASTER
typedef uint32_t tBTA_JV_ROLE;
#define BTA_JV_SERVICE_LMTD_DISCOVER \
@@ -144,6 +144,8 @@ typedef uint8_t tBTA_JV_CONN_STATE;
21 /* L2CAP connection congestion status changed */
#define BTA_JV_L2CAP_READ_EVT 22 /* the result for BTA_JvL2capRead */
#define BTA_JV_L2CAP_WRITE_EVT 24 /* the result for BTA_JvL2capWrite*/
+#define BTA_JV_L2CAP_WRITE_FIXED_EVT \
+ 25 /* the result for BTA_JvL2capWriteFixed */
/* events received by tBTA_JV_RFCOMM_CBACK */
#define BTA_JV_RFCOMM_OPEN_EVT \
@@ -247,6 +249,16 @@ typedef struct {
bool cong; /* congestion status */
} tBTA_JV_L2CAP_WRITE;
+/* data associated with BTA_JV_L2CAP_WRITE_FIXED_EVT */
+typedef struct {
+ tBTA_JV_STATUS status; /* Whether the operation succeeded or failed. */
+ uint16_t channel; /* The connection channel */
+ RawAddress addr; /* The peer address */
+ uint32_t req_id; /* The req_id in the associated BTA_JvL2capWrite() */
+ uint16_t len; /* The length of the data written. */
+ bool cong; /* congestion status */
+} tBTA_JV_L2CAP_WRITE_FIXED;
+
/* data associated with BTA_JV_RFCOMM_OPEN_EVT */
typedef struct {
tBTA_JV_STATUS status; /* Whether the operation succeeded or failed. */
@@ -350,6 +362,7 @@ typedef union {
BTA_JV_RFCOMM_DATA_IND_EVT */
tBTA_JV_LE_DATA_IND le_data_ind; /* BTA_JV_L2CAP_LE_DATA_IND_EVT */
tBTA_JV_L2CAP_LE_OPEN l2c_le_open; /* BTA_JV_L2CAP_OPEN_EVT */
+ tBTA_JV_L2CAP_WRITE_FIXED l2c_write_fixed; /* BTA_JV_L2CAP_WRITE_FIXED_EVT */
} tBTA_JV;
/* JAVA DM Interface callback */
@@ -400,6 +413,18 @@ void BTA_JvDisable(void);
/*******************************************************************************
*
+ * Function BTA_JvIsEncrypted
+ *
+ * Description This function checks if the link to peer device is encrypted
+ *
+ * Returns true if encrypted.
+ * false if not.
+ *
+ ******************************************************************************/
+bool BTA_JvIsEncrypted(const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
* Function BTA_JvGetChannelId
*
* Description This function reserves a SCN/PSM for applications running
@@ -478,6 +503,22 @@ tBTA_JV_STATUS BTA_JvDeleteRecord(uint32_t handle);
/*******************************************************************************
*
+ * Function BTA_JvL2capConnectLE
+ *
+ * Description Initiate a connection as an LE L2CAP client to the given BD
+ * Address.
+ * When the connection is initiated or failed to initiate,
+ * tBTA_JV_L2CAP_CBACK is called with BTA_JV_L2CAP_CL_INIT_EVT
+ * When the connection is established or failed,
+ * tBTA_JV_L2CAP_CBACK is called with BTA_JV_L2CAP_OPEN_EVT
+ *
+ ******************************************************************************/
+void BTA_JvL2capConnectLE(uint16_t remote_chan, const RawAddress& peer_bd_addr,
+ tBTA_JV_L2CAP_CBACK* p_cback,
+ uint32_t l2cap_socket_id);
+
+/*******************************************************************************
+ *
* Function BTA_JvL2capConnect
*
* Description Initiate a connection as a L2CAP client to the given BD
@@ -509,6 +550,19 @@ tBTA_JV_STATUS BTA_JvL2capClose(uint32_t handle);
/*******************************************************************************
*
+ * Function BTA_JvL2capCloseLE
+ *
+ * Description This function closes an L2CAP client connection for Fixed
+ * Channels Function is idempotent and no callbacks are called!
+ *
+ * Returns BTA_JV_SUCCESS, if the request is being processed.
+ * BTA_JV_FAILURE, otherwise.
+ *
+ ******************************************************************************/
+tBTA_JV_STATUS BTA_JvL2capCloseLE(uint32_t handle);
+
+/*******************************************************************************
+ *
* Function BTA_JvL2capStartServer
*
* Description This function starts an L2CAP server and listens for an
@@ -530,6 +584,37 @@ void BTA_JvL2capStartServer(int conn_type, tBTA_SEC sec_mask, tBTA_JV_ROLE role,
/*******************************************************************************
*
+ * Function BTA_JvL2capStartServerLE
+ *
+ * Description This function starts an LE L2CAP server and listens for an
+ * L2CAP connection from a remote Bluetooth device on a fixed
+ * channel over an LE link. When the server
+ * is started successfully, tBTA_JV_L2CAP_CBACK is called with
+ * BTA_JV_L2CAP_START_EVT. When the connection is established,
+ * tBTA_JV_L2CAP_CBACK is called with BTA_JV_L2CAP_OPEN_EVT.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTA_JvL2capStartServerLE(uint16_t local_chan, tBTA_JV_L2CAP_CBACK* p_cback,
+ uint32_t l2cap_socket_id);
+
+/*******************************************************************************
+ *
+ * Function BTA_JvL2capStopServerLE
+ *
+ * Description This function stops the LE L2CAP server. If the server has
+ * an active connection, it would be closed.
+ *
+ * Returns BTA_JV_SUCCESS, if the request is being processed.
+ * BTA_JV_FAILURE, otherwise.
+ *
+ ******************************************************************************/
+tBTA_JV_STATUS BTA_JvL2capStopServerLE(uint16_t local_chan,
+ uint32_t l2cap_socket_id);
+
+/*******************************************************************************
+ *
* Function BTA_JvL2capStopServer
*
* Description This function stops the L2CAP server. If the server has
@@ -588,6 +673,20 @@ tBTA_JV_STATUS BTA_JvL2capWrite(uint32_t handle, uint32_t req_id, BT_HDR* msg,
/*******************************************************************************
*
+ * Function BTA_JvL2capWriteFixed
+ *
+ * Description This function writes data to an L2CAP connection
+ * When the operation is complete, tBTA_JV_L2CAP_CBACK is
+ * called with BTA_JV_L2CAP_WRITE_FIXED_EVT. Works for
+ * fixed-channel connections
+ *
+ ******************************************************************************/
+void BTA_JvL2capWriteFixed(uint16_t channel, const RawAddress& addr,
+ uint32_t req_id, tBTA_JV_L2CAP_CBACK* p_cback,
+ BT_HDR* msg, uint32_t user_id);
+
+/*******************************************************************************
+ *
* Function BTA_JvRfcommConnect
*
* Description This function makes an RFCOMM conection to a remote BD
diff --git a/bta/include/bta_jv_co.h b/bta/include/bta_jv_co.h
index 7ab63c91f..fdee4ef2f 100644
--- a/bta/include/bta_jv_co.h
+++ b/bta/include/bta_jv_co.h
@@ -24,9 +24,7 @@
#ifndef BTA_JV_CO_H
#define BTA_JV_CO_H
-#include <cstdint>
-
-#include "stack/include/bt_types.h"
+#include "bta_jv_api.h"
/*****************************************************************************
* Function Declarations
diff --git a/bta/include/bta_mce_api.h b/bta/include/bta_mce_api.h
new file mode 100644
index 000000000..182e5da72
--- /dev/null
+++ b/bta/include/bta_mce_api.h
@@ -0,0 +1,121 @@
+/******************************************************************************
+ *
+ * Copyright 2014 The Android Open Source Project
+ * Copyright 2006-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+/******************************************************************************
+ *
+ * This is the public interface file the BTA MCE I/F
+ *
+ ******************************************************************************/
+#ifndef BTA_MCE_API_H
+#define BTA_MCE_API_H
+
+#include "bt_target.h"
+#include "bt_types.h"
+#include "bta_api.h"
+#include "btm_api.h"
+
+/*****************************************************************************
+ * Constants and data types
+ ****************************************************************************/
+/* status values */
+#define BTA_MCE_SUCCESS 0 /* Successful operation. */
+#define BTA_MCE_FAILURE 1 /* Generic failure. */
+#define BTA_MCE_BUSY 2 /* Temporarily can not handle this request. */
+
+typedef uint8_t tBTA_MCE_STATUS;
+
+/* MCE I/F callback events */
+/* events received by tBTA_MCE_DM_CBACK */
+#define BTA_MCE_ENABLE_EVT 0 /* MCE enabled */
+#define BTA_MCE_MAS_DISCOVERY_COMP_EVT 1 /* SDP MAS discovery complete */
+#define BTA_MCE_MAX_EVT 2 /* max number of MCE events */
+
+#define BTA_MCE_MAX_MAS_INSTANCES 12
+
+typedef uint16_t tBTA_MCE_EVT;
+
+typedef struct {
+ uint8_t scn;
+ char* p_srv_name;
+ uint16_t srv_name_len;
+ uint8_t instance_id;
+ uint8_t msg_type;
+} tBTA_MCE_MAS_INFO;
+
+/* data associated with BTA_MCE_MAS_DISCOVERY_COMP_EVT */
+typedef struct {
+ tBTA_MCE_STATUS status;
+ RawAddress remote_addr;
+ int num_mas;
+ tBTA_MCE_MAS_INFO mas[BTA_MCE_MAX_MAS_INSTANCES];
+} tBTA_MCE_MAS_DISCOVERY_COMP;
+
+/* union of data associated with MCE callback */
+typedef union {
+ tBTA_MCE_STATUS status; /* BTA_MCE_ENABLE_EVT */
+ tBTA_MCE_MAS_DISCOVERY_COMP
+ mas_disc_comp; /* BTA_MCE_MAS_DISCOVERY_COMP_EVT */
+} tBTA_MCE;
+
+/* MCE DM Interface callback */
+typedef void(tBTA_MCE_DM_CBACK)(tBTA_MCE_EVT event, tBTA_MCE* p_data,
+ void* user_data);
+
+/* MCE configuration structure */
+typedef struct {
+ uint16_t sdp_db_size; /* The size of p_sdp_db */
+ tSDP_DISCOVERY_DB* p_sdp_db; /* The data buffer to keep SDP database */
+} tBTA_MCE_CFG;
+
+/*****************************************************************************
+ * External Function Declarations
+ ****************************************************************************/
+
+/*******************************************************************************
+ *
+ * Function BTA_MceEnable
+ *
+ * Description Enable the MCE I/F service. When the enable
+ * operation is complete the callback function will be
+ * called with a BTA_MCE_ENABLE_EVT. This function must
+ * be called before other functions in the MCE API are
+ * called.
+ *
+ * Returns BTA_MCE_SUCCESS if successful.
+ * BTA_MCE_FAIL if internal failure.
+ *
+ ******************************************************************************/
+extern tBTA_MCE_STATUS BTA_MceEnable(tBTA_MCE_DM_CBACK* p_cback);
+
+/*******************************************************************************
+ *
+ * Function BTA_MceGetRemoteMasInstances
+ *
+ * Description This function performs service discovery for the MAS service
+ * by the given peer device. When the operation is completed
+ * the tBTA_MCE_DM_CBACK callback function will be called with
+ * a BTA_MCE_MAS_DISCOVERY_COMP_EVT.
+ *
+ * Returns BTA_MCE_SUCCESS, if the request is being processed.
+ * BTA_MCE_FAILURE, otherwise.
+ *
+ ******************************************************************************/
+extern tBTA_MCE_STATUS BTA_MceGetRemoteMasInstances(const RawAddress& bd_addr);
+
+#endif /* BTA_MCE_API_H */
diff --git a/bta/include/bta_op_api.h b/bta/include/bta_op_api.h
index aa9fd740e..bab96ff4c 100644
--- a/bta/include/bta_op_api.h
+++ b/bta/include/bta_op_api.h
@@ -26,7 +26,7 @@
#ifndef BTA_OP_API_H
#define BTA_OP_API_H
-#include <cstdint>
+#include "bta_api.h"
/*****************************************************************************
* Constants and data types
diff --git a/bta/include/bta_pan_api.h b/bta/include/bta_pan_api.h
index 48f2ae4e2..ce8a3c85a 100644
--- a/bta/include/bta_pan_api.h
+++ b/bta/include/bta_pan_api.h
@@ -26,9 +26,8 @@
#ifndef BTA_PAN_API_H
#define BTA_PAN_API_H
-#include <cstdint>
-
-#include "types/raw_address.h"
+#include "bta_api.h"
+#include "pan_api.h"
/*****************************************************************************
* Constants and data types
@@ -49,6 +48,7 @@ typedef uint8_t tBTA_PAN_EVT;
/* pan roles */
#define BTA_PAN_ROLE_PANU PAN_ROLE_CLIENT
+#define BTA_PAN_ROLE_GN PAN_ROLE_GN_SERVER
#define BTA_PAN_ROLE_NAP PAN_ROLE_NAP_SERVER
typedef uint8_t tBTA_PAN_ROLE;
@@ -57,6 +57,8 @@ typedef uint8_t tBTA_PAN_ROLE;
typedef struct {
const char* p_srv_name; /* service name for the PAN role */
uint8_t app_id; /* application id */
+ tBTA_SEC sec_mask; /* security setting for the role */
+
} tBTA_PAN_ROLE_INFO;
/* Event associated with BTA_PAN_SET_ROLE_EVT */
@@ -144,6 +146,7 @@ extern void BTA_PanDisable(void);
*
******************************************************************************/
void BTA_PanSetRole(tBTA_PAN_ROLE role, tBTA_PAN_ROLE_INFO* p_user_info,
+ tBTA_PAN_ROLE_INFO* p_gn_info,
tBTA_PAN_ROLE_INFO* p_nap_info);
/*******************************************************************************
diff --git a/bta/include/bta_pan_ci.h b/bta/include/bta_pan_ci.h
index 670188914..afc63771c 100644
--- a/bta/include/bta_pan_ci.h
+++ b/bta/include/bta_pan_ci.h
@@ -24,9 +24,7 @@
#ifndef BTA_PAN_CI_H
#define BTA_PAN_CI_H
-#include <cstdint>
-
-#include "bta/include/bta_pan_api.h"
+#include "bta_pan_api.h"
/*****************************************************************************
* Function Declarations
diff --git a/bta/include/bta_pan_co.h b/bta/include/bta_pan_co.h
index 86baff01d..6dc5435fc 100644
--- a/bta/include/bta_pan_co.h
+++ b/bta/include/bta_pan_co.h
@@ -24,9 +24,7 @@
#ifndef BTA_PAN_CO_H
#define BTA_PAN_CO_H
-#include <cstdint>
-
-#include "bta/include/bta_pan_api.h"
+#include "bta_pan_api.h"
/*****************************************************************************
* Constants
@@ -64,6 +62,22 @@ extern uint8_t bta_pan_co_init(uint8_t* q_level);
/*******************************************************************************
*
+ * Function bta_pan_co_open
+ *
+ * Description This function is executed by PAN when a connection
+ * is opened. The phone can use this function to set
+ * up data paths or perform any required initialization.
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void bta_pan_co_open(uint16_t handle, uint8_t app_id,
+ tBTA_PAN_ROLE local_role, tBTA_PAN_ROLE peer_role,
+ const RawAddress& peer_addr);
+
+/*******************************************************************************
+ *
* Function bta_pan_co_close
*
* Description This function is called by PAN when a connection to a
@@ -107,6 +121,24 @@ extern void bta_pan_co_rx_path(uint16_t handle, uint8_t app_id);
/*******************************************************************************
*
+ * Function bta_pan_co_tx_write
+ *
+ * Description This function is called by PAN to send data to the phone
+ * when the TX path is configured to use a push interface.
+ * The implementation of this function must copy the data to
+ * the phone's memory.
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void bta_pan_co_tx_write(uint16_t handle, uint8_t app_id,
+ const RawAddress& src, const RawAddress& dst,
+ uint16_t protocol, uint8_t* p_data,
+ uint16_t len, bool ext, bool forward);
+
+/*******************************************************************************
+ *
* Function bta_pan_co_rx_flow
*
* Description This function is called by PAN to enable or disable
diff --git a/bta/include/bta_sdp_api.h b/bta/include/bta_sdp_api.h
index ea4737fb9..078167a34 100644
--- a/bta/include/bta_sdp_api.h
+++ b/bta/include/bta_sdp_api.h
@@ -24,15 +24,12 @@
#ifndef BTA_SDP_API_H
#define BTA_SDP_API_H
-#include <cstdint>
+#include <hardware/bt_sdp.h>
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_api.h"
-#include "bta/include/bta_sdp_api.h"
-#include "include/hardware/bt_sdp.h" // bluetooth_sdp_record
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
+#include "bt_target.h"
+#include "bt_types.h"
+#include "bta_api.h"
+#include "btm_api.h"
using bluetooth::Uuid;
diff --git a/bta/include/bta_vc_api.h b/bta/include/bta_vc_api.h
deleted file mode 100644
index 66a47cd11..000000000
--- a/bta/include/bta_vc_api.h
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <hardware/bt_vc.h>
-
-class VolumeControl {
- public:
- virtual ~VolumeControl() = default;
-
- static void Initialize(bluetooth::vc::VolumeControlCallbacks* callbacks);
- static void CleanUp();
- static VolumeControl* Get();
- static void DebugDump(int fd);
-
- static void AddFromStorage(const RawAddress& address, bool auto_connect);
-
- static bool IsVolumeControlRunning();
-
- /* Volume Control Server (VCS) */
- virtual void Connect(const RawAddress& address) = 0;
- virtual void Disconnect(const RawAddress& address) = 0;
- virtual void SetVolume(std::variant<RawAddress, int> addr_or_group_id,
- uint8_t volume) = 0;
-};
diff --git a/bta/include/utl.h b/bta/include/utl.h
index 362a35eda..10afd251c 100644
--- a/bta/include/utl.h
+++ b/bta/include/utl.h
@@ -24,7 +24,8 @@
#ifndef UTL_H
#define UTL_H
-#include <cstdint>
+#include "bt_types.h"
+#include "bt_utils.h"
/*****************************************************************************
* Constants
diff --git a/bta/jv/bta_jv_act.cc b/bta/jv/bta_jv_act.cc
index 13fa89953..27bc7fb20 100644
--- a/bta/jv/bta_jv_act.cc
+++ b/bta/jv/bta_jv_act.cc
@@ -21,30 +21,72 @@
* This file contains action functions for BTA JV APIs.
*
******************************************************************************/
-
-#define LOG_TAG "bluetooth"
-
-#include <cstdint>
-#include <unordered_set>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_jv_co.h"
-#include "bta/jv/bta_jv_int.h"
-#include "bta/sys/bta_sys.h"
+#include <arpa/inet.h>
+#include <bluetooth/uuid.h>
+#include <hardware/bluetooth.h>
+#include <pthread.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "avct_api.h"
+#include "avdt_api.h"
+#include "bt_common.h"
+#include "bt_types.h"
+#include "bta_api.h"
+#include "bta_jv_api.h"
+#include "bta_jv_co.h"
+#include "bta_jv_int.h"
+#include "bta_sys.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "device/include/controller.h"
+#include "gap_api.h"
+#include "l2c_api.h"
#include "osi/include/allocator.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/avct_api.h" // AVCT_PSM
-#include "stack/include/avdt_api.h" // AVDT_PSM
-#include "stack/include/gap_api.h"
-#include "stack/include/port_api.h"
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
+#include "port_api.h"
+#include "rfcdefs.h"
+#include "sdp_api.h"
+#include "stack/l2cap/l2c_int.h"
+#include "utl.h"
+
+#include "osi/include/osi.h"
using bluetooth::Uuid;
tBTA_JV_CB bta_jv_cb;
-std::unordered_set<uint16_t> used_l2cap_classic_dynamic_psm;
+
+/* one of these exists for each client */
+struct fc_client {
+ struct fc_client* next_all_list;
+ struct fc_client* next_chan_list;
+ RawAddress remote_addr;
+ uint32_t id;
+ tBTA_JV_L2CAP_CBACK* p_cback;
+ uint32_t l2cap_socket_id;
+ uint16_t handle;
+ uint16_t chan;
+ uint8_t sec_id;
+ unsigned server : 1;
+ unsigned init_called : 1;
+};
+
+/* one of these exists for each channel we're dealing with */
+struct fc_channel {
+ struct fc_channel* next;
+ struct fc_client* clients;
+ uint8_t has_server : 1;
+ uint16_t chan;
+};
+
+static struct fc_client* fc_clients;
+static struct fc_channel* fc_channels;
+static uint32_t fc_next_id;
+
+static void fcchan_conn_chng_cbk(uint16_t chan, const RawAddress& bd_addr,
+ bool connected, uint16_t reason,
+ tBT_TRANSPORT);
+static void fcchan_data_cbk(uint16_t chan, const RawAddress& bd_addr,
+ BT_HDR* p_buf);
static tBTA_JV_PCB* bta_jv_add_rfc_port(tBTA_JV_RFC_CB* p_cb,
tBTA_JV_PCB* p_pcb_open);
@@ -286,14 +328,14 @@ static tBTA_JV_STATUS bta_jv_free_rfc_cb(tBTA_JV_RFC_CB* p_cb,
p_pcb->handle = 0;
p_cb->curr_sess--;
if (p_cb->curr_sess == 0) {
- RFCOMM_ClearSecurityRecord(p_cb->scn);
p_cb->scn = 0;
+ bta_jv_free_sec_id(&p_cb->sec_id);
p_cb->p_cback = NULL;
p_cb->handle = 0;
p_cb->curr_sess = -1;
}
if (remove_server) {
- RFCOMM_ClearSecurityRecord(p_cb->scn);
+ bta_jv_free_sec_id(&p_cb->sec_id);
}
}
return status;
@@ -510,13 +552,13 @@ bool bta_jv_check_psm(uint16_t psm) {
if (psm < 0x1001) {
/* see if this is defined by spec */
switch (psm) {
- case BT_PSM_SDP:
+ case SDP_PSM: /* 1 */
case BT_PSM_RFCOMM: /* 3 */
/* do not allow java app to use these 2 PSMs */
break;
- case BT_PSM_TCS:
- case BT_PSM_CTP:
+ case TCS_PSM_INTERCOM: /* 5 */
+ case TCS_PSM_CORDLESS: /* 7 */
if (!bta_sys_is_register(BTA_ID_CT) &&
!bta_sys_is_register(BTA_ID_CG))
ret = true;
@@ -526,8 +568,8 @@ bool bta_jv_check_psm(uint16_t psm) {
if (!bta_sys_is_register(BTA_ID_PAN)) ret = true;
break;
- case BT_PSM_HIDC:
- case BT_PSM_HIDI:
+ case HID_PSM_CONTROL: /* 0x11 */
+ case HID_PSM_INTERRUPT: /* 0x13 */
// FIX: allow HID Device and HID Host to coexist
if (!bta_sys_is_register(BTA_ID_HD) ||
!bta_sys_is_register(BTA_ID_HH))
@@ -536,7 +578,9 @@ bool bta_jv_check_psm(uint16_t psm) {
case AVCT_PSM: /* 0x17 */
case AVDT_PSM: /* 0x19 */
- if (!bta_sys_is_register(BTA_ID_AV)) ret = true;
+ if ((!bta_sys_is_register(BTA_ID_AV)) &&
+ (!bta_sys_is_register(BTA_ID_AVK)))
+ ret = true;
break;
default:
@@ -603,31 +647,6 @@ static void bta_jv_set_free_psm(uint16_t psm) {
}
}
-static uint16_t bta_jv_allocate_l2cap_classic_psm() {
- bool done = false;
- uint16_t psm = bta_jv_cb.dyn_psm;
-
- while (!done) {
- psm += 2;
- if (psm > 0xfeff) {
- psm = 0x1001;
- } else if (psm & 0x0100) {
- /* the upper byte must be even */
- psm += 0x0100;
- }
-
- /* if psm is in range of reserved BRCM Aware features */
- if ((BRCM_RESERVED_PSM_START <= psm) && (psm <= BRCM_RESERVED_PSM_END))
- continue;
-
- /* make sure the newlly allocated psm is not used right now */
- if (used_l2cap_classic_dynamic_psm.count(psm) == 0) done = true;
- }
- bta_jv_cb.dyn_psm = psm;
-
- return (psm);
-}
-
/** Obtain a free SCN (Server Channel Number) (RFCOMM channel or L2CAP PSM) */
void bta_jv_get_channel_id(
int32_t type /* One of BTA_JV_CONN_TYPE_ */,
@@ -665,7 +684,7 @@ void bta_jv_get_channel_id(
case BTA_JV_CONN_TYPE_L2CAP:
psm = bta_jv_get_free_psm();
if (psm == 0) {
- psm = bta_jv_allocate_l2cap_classic_psm();
+ psm = L2CA_AllocatePSM();
VLOG(2) << __func__ << ": returned PSM=" << loghex(psm);
}
break;
@@ -719,11 +738,11 @@ void bta_jv_free_scn(int32_t type /* One of BTA_JV_CONN_TYPE_ */,
* Returns void
*
******************************************************************************/
-static void bta_jv_start_discovery_cback(tSDP_RESULT result, void* user_data) {
+static void bta_jv_start_discovery_cback(uint16_t result, void* user_data) {
tBTA_JV_STATUS status;
uint32_t* p_rfcomm_slot_id = static_cast<uint32_t*>(user_data);
- VLOG(2) << __func__ << ": res=" << loghex(static_cast<uint16_t>(result));
+ VLOG(2) << __func__ << ": res=" << loghex(result);
bta_jv_cb.sdp_active = BTA_JV_SDP_ACT_NONE;
if (bta_jv_cb.p_dm_cback) {
@@ -893,11 +912,15 @@ void bta_jv_l2cap_connect(int32_t type, tBTA_SEC sec_mask, tBTA_JV_ROLE role,
tBTA_JV_L2CAP_CBACK* p_cback,
uint32_t l2cap_socket_id) {
uint16_t handle = GAP_INVALID_HANDLE;
+ uint8_t chan_mode_mask = GAP_FCR_CHAN_OPT_BASIC;
tL2CAP_CFG_INFO cfg;
memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
if (cfg_param) {
cfg = *cfg_param;
+ if (cfg.fcr_present && cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) {
+ chan_mode_mask = GAP_FCR_CHAN_OPT_ERTM;
+ }
}
/* We need to use this value for MTU to be able to handle cases where cfg is
@@ -905,6 +928,10 @@ void bta_jv_l2cap_connect(int32_t type, tBTA_SEC sec_mask, tBTA_JV_ROLE role,
cfg.mtu_present = true;
cfg.mtu = rx_mtu;
+ /* TODO: DM role manager
+ L2CA_SetDesireRole(role);
+ */
+
uint8_t sec_id = bta_jv_alloc_sec_id();
tBTA_JV_L2CAP_CL_INIT evt_data;
evt_data.sec_id = sec_id;
@@ -917,7 +944,7 @@ void bta_jv_l2cap_connect(int32_t type, tBTA_SEC sec_mask, tBTA_JV_ROLE role,
{
uint16_t max_mps = 0xffff; // Let GAP_ConnOpen set the max_mps.
handle = GAP_ConnOpen("", sec_id, 0, &peer_bd_addr, remote_psm, max_mps,
- &cfg, ertm_info.get(), sec_mask,
+ &cfg, ertm_info.get(), sec_mask, chan_mode_mask,
bta_jv_l2cap_client_cback, type);
if (handle != GAP_INVALID_HANDLE) {
evt_data.status = BTA_JV_SUCCESS;
@@ -1038,11 +1065,15 @@ void bta_jv_l2cap_start_server(int32_t type, tBTA_SEC sec_mask,
uint32_t l2cap_socket_id) {
uint16_t handle;
tBTA_JV_L2CAP_START evt_data;
+ uint8_t chan_mode_mask = GAP_FCR_CHAN_OPT_BASIC;
tL2CAP_CFG_INFO cfg;
memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
if (cfg_param) {
cfg = *cfg_param;
+ if (cfg.fcr_present && cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) {
+ chan_mode_mask = GAP_FCR_CHAN_OPT_ERTM;
+ }
}
// FIX: MTU=0 means not present
@@ -1054,13 +1085,17 @@ void bta_jv_l2cap_start_server(int32_t type, tBTA_SEC sec_mask,
cfg.mtu = 0;
}
+ /* TODO DM role manager
+ L2CA_SetDesireRole(role);
+ */
+
uint8_t sec_id = bta_jv_alloc_sec_id();
uint16_t max_mps = 0xffff; // Let GAP_ConnOpen set the max_mps.
/* PSM checking is not required for LE COC */
if (0 == sec_id ||
((type == BTA_JV_CONN_TYPE_L2CAP) && (!bta_jv_check_psm(local_psm))) ||
(handle = GAP_ConnOpen("JV L2CAP", sec_id, 1, nullptr, local_psm, max_mps,
- &cfg, ertm_info.get(), sec_mask,
+ &cfg, ertm_info.get(), sec_mask, chan_mode_mask,
bta_jv_l2cap_server_cback, type)) ==
GAP_INVALID_HANDLE) {
bta_jv_free_sec_id(&sec_id);
@@ -1156,6 +1191,24 @@ void bta_jv_l2cap_write(uint32_t handle, uint32_t req_id, BT_HDR* msg,
p_cb->p_cback(BTA_JV_L2CAP_WRITE_EVT, &bta_jv, user_id);
}
+/* Write data to an L2CAP connection using Fixed channels */
+void bta_jv_l2cap_write_fixed(uint16_t channel, const RawAddress& addr,
+ uint32_t req_id, BT_HDR* msg, uint32_t user_id,
+ tBTA_JV_L2CAP_CBACK* p_cback) {
+ tBTA_JV_L2CAP_WRITE_FIXED evt_data;
+ evt_data.status = BTA_JV_FAILURE;
+ evt_data.channel = channel;
+ evt_data.addr = addr;
+ evt_data.req_id = req_id;
+ evt_data.len = 0;
+
+ L2CA_SendFixedChnlData(channel, addr, msg);
+
+ tBTA_JV bta_jv;
+ bta_jv.l2c_write_fixed = evt_data;
+ p_cback(BTA_JV_L2CAP_WRITE_FIXED_EVT, &bta_jv, user_id);
+}
+
/*******************************************************************************
*
* Function bta_jv_port_data_co_cback
@@ -1274,22 +1327,37 @@ static void bta_jv_port_event_cl_cback(uint32_t code, uint16_t port_handle) {
}
/* Client initiates an RFCOMM connection */
-void bta_jv_rfcomm_connect(tBTA_SEC sec_mask, uint8_t remote_scn,
- const RawAddress& peer_bd_addr,
+void bta_jv_rfcomm_connect(tBTA_SEC sec_mask, tBTA_JV_ROLE role,
+ uint8_t remote_scn, const RawAddress& peer_bd_addr,
tBTA_JV_RFCOMM_CBACK* p_cback,
uint32_t rfcomm_slot_id) {
uint16_t handle = 0;
uint32_t event_mask = BTA_JV_RFC_EV_MASK;
tPORT_STATE port_state;
+ /* TODO DM role manager
+ L2CA_SetDesireRole(role);
+ */
+
+ uint8_t sec_id = bta_jv_alloc_sec_id();
+
tBTA_JV_RFCOMM_CL_INIT evt_data;
memset(&evt_data, 0, sizeof(evt_data));
+ evt_data.sec_id = sec_id;
evt_data.status = BTA_JV_SUCCESS;
+ if (0 == sec_id ||
+ !BTM_SetSecurityLevel(true, "", sec_id, sec_mask, BT_PSM_RFCOMM,
+ BTM_SEC_PROTO_RFCOMM, remote_scn)) {
+ evt_data.status = BTA_JV_FAILURE;
+ LOG(ERROR) << __func__ << ": sec_id=" << +sec_id
+ << " is zero or BTM_SetSecurityLevel failed, remote_scn:"
+ << +remote_scn;
+ }
+
if (evt_data.status == BTA_JV_SUCCESS &&
- RFCOMM_CreateConnectionWithSecurity(
- UUID_SERVCLASS_SERIAL_PORT, remote_scn, false, BTA_JV_DEF_RFC_MTU,
- peer_bd_addr, &handle, bta_jv_port_mgmt_cl_cback,
- sec_mask) != PORT_SUCCESS) {
+ RFCOMM_CreateConnection(UUID_SERVCLASS_SERIAL_PORT, remote_scn, false,
+ BTA_JV_DEF_RFC_MTU, peer_bd_addr, &handle,
+ bta_jv_port_mgmt_cl_cback) != PORT_SUCCESS) {
LOG(ERROR) << __func__ << ": RFCOMM_CreateConnection failed";
evt_data.status = BTA_JV_FAILURE;
}
@@ -1298,6 +1366,7 @@ void bta_jv_rfcomm_connect(tBTA_SEC sec_mask, uint8_t remote_scn,
tBTA_JV_RFC_CB* p_cb = bta_jv_alloc_rfc_cb(handle, &p_pcb);
if (p_cb) {
p_cb->p_cback = p_cback;
+ p_cb->sec_id = sec_id;
p_cb->scn = 0;
p_pcb->state = BTA_JV_ST_CL_OPENING;
p_pcb->rfcomm_slot_id = rfcomm_slot_id;
@@ -1323,7 +1392,7 @@ void bta_jv_rfcomm_connect(tBTA_SEC sec_mask, uint8_t remote_scn,
bta_jv.rfc_cl_init = evt_data;
p_cback(BTA_JV_RFCOMM_CL_INIT_EVT, &bta_jv, rfcomm_slot_id);
if (bta_jv.rfc_cl_init.status == BTA_JV_FAILURE) {
- RFCOMM_ClearSecurityRecord(remote_scn);
+ if (sec_id) bta_jv_free_sec_id(&sec_id);
if (handle) RFCOMM_RemoveConnection(handle);
}
}
@@ -1365,6 +1434,8 @@ void bta_jv_rfcomm_close(uint32_t handle, uint32_t rfcomm_slot_id) {
if (!find_rfc_pcb(rfcomm_slot_id, &p_cb, &p_pcb)) return;
bta_jv_free_rfc_cb(p_cb, p_pcb);
+ VLOG(2) << __func__ << ": sec id in use=" << get_sec_id_used()
+ << ", rfc_cb in use=" << get_rfc_cb_used();
}
/*******************************************************************************
@@ -1566,24 +1637,39 @@ static tBTA_JV_PCB* bta_jv_add_rfc_port(tBTA_JV_RFC_CB* p_cb,
}
/* waits for an RFCOMM client to connect */
-void bta_jv_rfcomm_start_server(tBTA_SEC sec_mask, uint8_t local_scn,
- uint8_t max_session,
+void bta_jv_rfcomm_start_server(tBTA_SEC sec_mask, tBTA_JV_ROLE role,
+ uint8_t local_scn, uint8_t max_session,
tBTA_JV_RFCOMM_CBACK* p_cback,
uint32_t rfcomm_slot_id) {
uint16_t handle = 0;
uint32_t event_mask = BTA_JV_RFC_EV_MASK;
tPORT_STATE port_state;
+ uint8_t sec_id = 0;
tBTA_JV_RFC_CB* p_cb = NULL;
tBTA_JV_PCB* p_pcb;
tBTA_JV_RFCOMM_START evt_data;
+ /* TODO DM role manager
+ L2CA_SetDesireRole(role);
+ */
memset(&evt_data, 0, sizeof(evt_data));
evt_data.status = BTA_JV_FAILURE;
+ VLOG(2) << __func__ << ": sec id in use=" << get_sec_id_used()
+ << ", rfc_cb in use=" << get_rfc_cb_used();
do {
- if (RFCOMM_CreateConnectionWithSecurity(
- 0, local_scn, true, BTA_JV_DEF_RFC_MTU, RawAddress::kAny, &handle,
- bta_jv_port_mgmt_sr_cback, sec_mask) != PORT_SUCCESS) {
+ sec_id = bta_jv_alloc_sec_id();
+
+ if (0 == sec_id ||
+ !BTM_SetSecurityLevel(false, "JV PORT", sec_id, sec_mask, BT_PSM_RFCOMM,
+ BTM_SEC_PROTO_RFCOMM, local_scn)) {
+ LOG(ERROR) << __func__ << ": run out of sec_id";
+ break;
+ }
+
+ if (RFCOMM_CreateConnection(sec_id, local_scn, true, BTA_JV_DEF_RFC_MTU,
+ RawAddress::kAny, &handle,
+ bta_jv_port_mgmt_sr_cback) != PORT_SUCCESS) {
LOG(ERROR) << __func__ << ": RFCOMM_CreateConnection failed";
break;
}
@@ -1596,11 +1682,13 @@ void bta_jv_rfcomm_start_server(tBTA_SEC sec_mask, uint8_t local_scn,
p_cb->max_sess = max_session;
p_cb->p_cback = p_cback;
+ p_cb->sec_id = sec_id;
p_cb->scn = local_scn;
p_pcb->state = BTA_JV_ST_SR_LISTEN;
p_pcb->rfcomm_slot_id = rfcomm_slot_id;
evt_data.status = BTA_JV_SUCCESS;
evt_data.handle = p_cb->handle;
+ evt_data.sec_id = sec_id;
evt_data.use_co = true;
PORT_ClearKeepHandleFlag(handle);
@@ -1619,7 +1707,7 @@ void bta_jv_rfcomm_start_server(tBTA_SEC sec_mask, uint8_t local_scn,
if (bta_jv.rfc_start.status == BTA_JV_SUCCESS) {
PORT_SetDataCOCallback(handle, bta_jv_port_data_co_cback);
} else {
- RFCOMM_ClearSecurityRecord(local_scn);
+ if (sec_id) bta_jv_free_sec_id(&sec_id);
if (handle) RFCOMM_RemoveConnection(handle);
}
}
@@ -1639,6 +1727,8 @@ void bta_jv_rfcomm_stop_server(uint32_t handle, uint32_t rfcomm_slot_id) {
VLOG(2) << __func__ << ": p_pcb=" << p_pcb
<< ", p_pcb->port_handle=" << p_pcb->port_handle;
bta_jv_free_rfc_cb(p_cb, p_pcb);
+ VLOG(2) << __func__ << ": sec id in use=" << get_sec_id_used()
+ << ", rfc_cb in use=" << get_rfc_cb_used();
}
/* write data to an RFCOMM connection */
@@ -1794,3 +1884,358 @@ static void bta_jv_pm_state_change(tBTA_JV_PM_CB* p_cb,
}
}
/******************************************************************************/
+
+static struct fc_channel* fcchan_get(uint16_t chan, char create) {
+ struct fc_channel* t = fc_channels;
+ static tL2CAP_FIXED_CHNL_REG fcr = {
+ .pL2CA_FixedConn_Cb = fcchan_conn_chng_cbk,
+ .pL2CA_FixedData_Cb = fcchan_data_cbk,
+ .fixed_chnl_opts =
+ {
+ .mode = L2CAP_FCR_BASIC_MODE,
+ .tx_win_sz = 1,
+ .max_transmit = 0xFF,
+ .rtrans_tout = 2000,
+ .mon_tout = 12000,
+ .mps = 670,
+ },
+ .default_idle_tout = 0xffff,
+ };
+
+ while (t && t->chan != chan) t = t->next;
+
+ if (t)
+ return t;
+ else if (!create)
+ return NULL; /* we cannot alloc a struct if not asked to */
+
+ t = static_cast<struct fc_channel*>(osi_calloc(sizeof(*t)));
+ t->chan = chan;
+
+ if (!L2CA_RegisterFixedChannel(chan, &fcr)) {
+ osi_free(t);
+ return NULL;
+ }
+
+ // link it in
+ t->next = fc_channels;
+ fc_channels = t;
+
+ return t;
+}
+
+/* pass NULL to find servers */
+static struct fc_client* fcclient_find_by_addr(struct fc_client* start,
+ const RawAddress* addr) {
+ struct fc_client* t = start;
+
+ while (t) {
+ /* match client if have addr */
+ if (addr && addr == &t->remote_addr) break;
+
+ /* match server if do not have addr */
+ if (!addr && t->server) break;
+
+ t = t->next_all_list;
+ }
+
+ return t;
+}
+
+static struct fc_client* fcclient_find_by_id(uint32_t id) {
+ struct fc_client* t = fc_clients;
+
+ while (t && t->id != id) t = t->next_all_list;
+
+ return t;
+}
+
+static struct fc_client* fcclient_alloc(uint16_t chan, char server,
+ const uint8_t* sec_id_to_use) {
+ struct fc_channel* fc = fcchan_get(chan, true);
+ struct fc_client* t;
+ uint8_t sec_id;
+
+ if (!fc) return NULL;
+
+ if (fc->has_server && server)
+ return NULL; /* no way to have multiple servers on same channel */
+
+ if (sec_id_to_use)
+ sec_id = *sec_id_to_use;
+ else
+ sec_id = bta_jv_alloc_sec_id();
+
+ t = static_cast<fc_client*>(osi_calloc(sizeof(*t)));
+ // Allocate it a unique ID
+ do {
+ t->id = ++fc_next_id;
+ } while (!t->id || fcclient_find_by_id(t->id));
+
+ // Populate some params
+ t->chan = chan;
+ t->server = server;
+
+ // Get a security id
+ t->sec_id = sec_id;
+
+ // Link it in to global list
+ t->next_all_list = fc_clients;
+ fc_clients = t;
+
+ // Link it in to channel list
+ t->next_chan_list = fc->clients;
+ fc->clients = t;
+
+ // Update channel if needed
+ if (server) fc->has_server = true;
+
+ return t;
+}
+
+static void fcclient_free(struct fc_client* fc) {
+ struct fc_client* t = fc_clients;
+ struct fc_channel* tc = fcchan_get(fc->chan, false);
+
+ // remove from global list
+ while (t && t->next_all_list != fc) t = t->next_all_list;
+
+ if (!t && fc != fc_clients) return; /* prevent double-free */
+
+ if (t)
+ t->next_all_list = fc->next_all_list;
+ else
+ fc_clients = fc->next_all_list;
+
+ // remove from channel list
+ if (tc) {
+ t = tc->clients;
+
+ while (t && t->next_chan_list != fc) t = t->next_chan_list;
+
+ if (t)
+ t->next_chan_list = fc->next_chan_list;
+ else
+ tc->clients = fc->next_chan_list;
+
+ // if was server then channel no longer has a server
+ if (fc->server) tc->has_server = false;
+ }
+
+ // free security id
+ bta_jv_free_sec_id(&fc->sec_id);
+
+ osi_free(fc);
+}
+
+static void fcchan_conn_chng_cbk(uint16_t chan, const RawAddress& bd_addr,
+ bool connected, uint16_t reason,
+ tBT_TRANSPORT transport) {
+ tBTA_JV init_evt;
+ tBTA_JV open_evt;
+ struct fc_channel* tc;
+ struct fc_client *t = NULL, *new_conn;
+ tBTA_JV_L2CAP_CBACK* p_cback = NULL;
+ char call_init = false;
+ uint32_t l2cap_socket_id;
+
+ tc = fcchan_get(chan, false);
+ if (tc) {
+ t = fcclient_find_by_addr(
+ tc->clients,
+ &bd_addr); // try to find an open socked for that addr
+ if (t) {
+ p_cback = t->p_cback;
+ l2cap_socket_id = t->l2cap_socket_id;
+ } else {
+ t = fcclient_find_by_addr(
+ tc->clients,
+ NULL); // try to find a listening socked for that channel
+ if (t) {
+ // found: create a normal connection socket and assign the connection to
+ // it
+ new_conn = fcclient_alloc(chan, false, &t->sec_id);
+ if (new_conn) {
+ new_conn->remote_addr = bd_addr;
+ new_conn->p_cback = NULL; // for now
+ new_conn->init_called = true; /*nop need to do it again */
+
+ p_cback = t->p_cback;
+ l2cap_socket_id = t->l2cap_socket_id;
+
+ t = new_conn;
+ }
+ } else {
+ // drop it
+ return;
+ }
+ }
+ }
+
+ if (t) {
+ if (!t->init_called) {
+ call_init = true;
+ t->init_called = true;
+
+ init_evt.l2c_cl_init.handle = t->id;
+ init_evt.l2c_cl_init.status = BTA_JV_SUCCESS;
+ init_evt.l2c_cl_init.sec_id = t->sec_id;
+ }
+
+ open_evt.l2c_open.handle = t->id;
+ open_evt.l2c_open.tx_mtu = 23; /* 23, why not ?*/
+ memcpy(&open_evt.l2c_le_open.rem_bda, &t->remote_addr,
+ sizeof(open_evt.l2c_le_open.rem_bda));
+ // TODO: (apanicke) Change the way these functions work so that casting
+ // isn't needed
+ open_evt.l2c_le_open.p_p_cback = (void**)&t->p_cback;
+ open_evt.l2c_le_open.p_user_data = (void**)&t->l2cap_socket_id;
+ open_evt.l2c_le_open.status = BTA_JV_SUCCESS;
+
+ if (connected) {
+ open_evt.l2c_open.status = BTA_JV_SUCCESS;
+ } else {
+ fcclient_free(t);
+ open_evt.l2c_open.status = BTA_JV_FAILURE;
+ }
+ }
+
+ if (call_init) p_cback(BTA_JV_L2CAP_CL_INIT_EVT, &init_evt, l2cap_socket_id);
+
+ // call this with lock taken so socket does not disappear from under us */
+ if (p_cback) {
+ p_cback(BTA_JV_L2CAP_OPEN_EVT, &open_evt, l2cap_socket_id);
+ if (!t->p_cback) /* no callback set, means they do not want this one... */
+ fcclient_free(t);
+ }
+}
+
+static void fcchan_data_cbk(uint16_t chan, const RawAddress& bd_addr,
+ BT_HDR* p_buf) {
+ tBTA_JV evt_data;
+ struct fc_channel* tc;
+ struct fc_client* t = NULL;
+ tBTA_JV_L2CAP_CBACK* sock_cback = NULL;
+ uint32_t sock_id;
+
+ tc = fcchan_get(chan, false);
+ if (tc) {
+ // try to find an open socked for that addr and channel
+ t = fcclient_find_by_addr(tc->clients, &bd_addr);
+ }
+ if (!t) {
+ // no socket -> drop it
+ return;
+ }
+
+
+ sock_cback = t->p_cback;
+ sock_id = t->l2cap_socket_id;
+ evt_data.le_data_ind.handle = t->id;
+ evt_data.le_data_ind.p_buf = p_buf;
+
+ if (sock_cback) sock_cback(BTA_JV_L2CAP_DATA_IND_EVT, &evt_data, sock_id);
+}
+
+/** makes an le l2cap client connection */
+void bta_jv_l2cap_connect_le(uint16_t remote_chan,
+ const RawAddress& peer_bd_addr,
+ tBTA_JV_L2CAP_CBACK* p_cback,
+ uint32_t l2cap_socket_id) {
+ tBTA_JV evt;
+ uint32_t id;
+ char call_init_f = true;
+ struct fc_client* t;
+
+ evt.l2c_cl_init.handle = GAP_INVALID_HANDLE;
+ evt.l2c_cl_init.status = BTA_JV_FAILURE;
+
+ t = fcclient_alloc(remote_chan, false, NULL);
+ if (!t) {
+ p_cback(BTA_JV_L2CAP_CL_INIT_EVT, &evt, l2cap_socket_id);
+ return;
+ }
+
+ t->p_cback = p_cback;
+ t->l2cap_socket_id = l2cap_socket_id;
+ t->remote_addr = peer_bd_addr;
+ id = t->id;
+ t->init_called = false;
+
+ if (L2CA_ConnectFixedChnl(t->chan, t->remote_addr)) {
+ evt.l2c_cl_init.status = BTA_JV_SUCCESS;
+ evt.l2c_cl_init.handle = id;
+ }
+
+ // it could have been deleted/moved from under us, so re-find it */
+ t = fcclient_find_by_id(id);
+ if (t) {
+ if (evt.l2c_cl_init.status == BTA_JV_SUCCESS) {
+ call_init_f = !t->init_called;
+ } else {
+ fcclient_free(t);
+ t = NULL;
+ }
+ }
+ if (call_init_f) p_cback(BTA_JV_L2CAP_CL_INIT_EVT, &evt, l2cap_socket_id);
+ if (t) {
+ t->init_called = true;
+ }
+}
+
+/* stops an LE L2CAP server */
+void bta_jv_l2cap_stop_server_le(uint16_t local_chan) {
+ struct fc_client* fcclient;
+
+ tBTA_JV evt;
+ evt.l2c_close.status = BTA_JV_FAILURE;
+ evt.l2c_close.async = false;
+ evt.l2c_close.handle = GAP_INVALID_HANDLE;
+
+ struct fc_channel* fcchan = fcchan_get(local_chan, false);
+ if (fcchan) {
+ while ((fcclient = fcchan->clients)) {
+ tBTA_JV_L2CAP_CBACK* p_cback = fcclient->p_cback;
+ uint32_t l2cap_socket_id = fcclient->l2cap_socket_id;
+
+ evt.l2c_close.handle = fcclient->id;
+ evt.l2c_close.status = BTA_JV_SUCCESS;
+ evt.l2c_close.async = false;
+
+ fcclient_free(fcclient);
+
+ if (p_cback) p_cback(BTA_JV_L2CAP_CLOSE_EVT, &evt, l2cap_socket_id);
+ }
+ }
+}
+
+/** starts an LE L2CAP server */
+void bta_jv_l2cap_start_server_le(uint16_t local_chan,
+ tBTA_JV_L2CAP_CBACK* p_cback,
+ uint32_t l2cap_socket_id) {
+ tBTA_JV_L2CAP_START evt_data;
+ evt_data.handle = GAP_INVALID_HANDLE;
+ evt_data.status = BTA_JV_FAILURE;
+
+ struct fc_client* t = fcclient_alloc(local_chan, true, NULL);
+ if (!t) goto out;
+
+ t->p_cback = p_cback;
+ t->l2cap_socket_id = l2cap_socket_id;
+
+ // if we got here, we're registered...
+ evt_data.status = BTA_JV_SUCCESS;
+ evt_data.handle = t->id;
+ evt_data.sec_id = t->sec_id;
+
+out:
+ tBTA_JV bta_jv;
+ bta_jv.l2c_start = evt_data;
+ p_cback(BTA_JV_L2CAP_START_EVT, &bta_jv, l2cap_socket_id);
+}
+
+/* close a fixed channel connection. calls no callbacks. idempotent */
+extern void bta_jv_l2cap_close_fixed(uint32_t handle) {
+ struct fc_client* t = fcclient_find_by_id(handle);
+ if (t) fcclient_free(t);
+}
diff --git a/bta/jv/bta_jv_api.cc b/bta/jv/bta_jv_api.cc
index 3d25824db..6702e0d89 100644
--- a/bta/jv/bta_jv_api.cc
+++ b/bta/jv/bta_jv_api.cc
@@ -22,20 +22,21 @@
* Technology (JABWT) as specified by the JSR82 specificiation
*
******************************************************************************/
-
#include <base/bind.h>
-#include <base/location.h>
+#include <base/bind_helpers.h>
#include <base/logging.h>
-#include <cstdint>
-#include <memory>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/jv/bta_jv_int.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "stack/include/gap_api.h"
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
+#include <string.h>
+
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_jv_api.h"
+#include "bta_jv_int.h"
+#include "bta_sys.h"
+#include "gap_api.h"
+#include "port_api.h"
+#include "sdp_api.h"
+#include "stack/include/btu.h"
+#include "utl.h"
using base::Bind;
using bluetooth::Uuid;
@@ -71,8 +72,6 @@ tBTA_JV_STATUS BTA_JvEnable(tBTA_JV_DM_CBACK* p_cback) {
for (int i = 0; i < BTA_JV_PM_MAX_NUM; i++) {
bta_jv_cb.pm_cb[i].handle = BTA_JV_PM_HANDLE_CLEAR;
}
- bta_jv_cb.dyn_psm = 0xfff;
- used_l2cap_classic_dynamic_psm = {};
bta_jv_enabled = true;
@@ -91,6 +90,27 @@ void BTA_JvDisable(void) {
/*******************************************************************************
*
+ * Function BTA_JvIsEncrypted
+ *
+ * Description This function checks if the link to peer device is encrypted
+ *
+ * Returns true if encrypted.
+ * false if not.
+ *
+ ******************************************************************************/
+bool BTA_JvIsEncrypted(const RawAddress& bd_addr) {
+ bool is_encrypted = false;
+ uint8_t sec_flags, le_flags;
+
+ if (BTM_GetSecurityFlags(bd_addr, &sec_flags) &&
+ BTM_GetSecurityFlagsByTransport(bd_addr, &le_flags, BT_TRANSPORT_LE)) {
+ if (sec_flags & BTM_SEC_FLAG_ENCRYPTED || le_flags & BTM_SEC_FLAG_ENCRYPTED)
+ is_encrypted = true;
+ }
+ return is_encrypted;
+}
+/*******************************************************************************
+ *
* Function BTA_JvGetChannelId
*
* Description This function reserves a SCN (server channel number) for
@@ -210,6 +230,27 @@ tBTA_JV_STATUS BTA_JvDeleteRecord(uint32_t handle) {
/*******************************************************************************
*
+ * Function BTA_JvL2capConnectLE
+ *
+ * Description Initiate an LE connection as a L2CAP client to the given BD
+ * Address.
+ * When the connection is initiated or failed to initiate,
+ * tBTA_JV_L2CAP_CBACK is called with BTA_JV_L2CAP_CL_INIT_EVT
+ * When the connection is established or failed,
+ * tBTA_JV_L2CAP_CBACK is called with BTA_JV_L2CAP_OPEN_EVT
+ *
+ ******************************************************************************/
+void BTA_JvL2capConnectLE(uint16_t remote_chan, const RawAddress& peer_bd_addr,
+ tBTA_JV_L2CAP_CBACK* p_cback,
+ uint32_t l2cap_socket_id) {
+ VLOG(2) << __func__;
+ CHECK(p_cback);
+ do_in_main_thread(FROM_HERE, Bind(&bta_jv_l2cap_connect_le, remote_chan,
+ peer_bd_addr, p_cback, l2cap_socket_id));
+}
+
+/*******************************************************************************
+ *
* Function BTA_JvL2capConnect
*
* Description Initiate a connection as a L2CAP client to the given BD
@@ -259,6 +300,24 @@ tBTA_JV_STATUS BTA_JvL2capClose(uint32_t handle) {
/*******************************************************************************
*
+ * Function BTA_JvL2capCloseLE
+ *
+ * Description This function closes an L2CAP client connection for Fixed
+ * Channels Function is idempotent and no callbacks are called!
+ *
+ * Returns BTA_JV_SUCCESS, if the request is being processed.
+ * BTA_JV_FAILURE, otherwise.
+ *
+ ******************************************************************************/
+tBTA_JV_STATUS BTA_JvL2capCloseLE(uint32_t handle) {
+ VLOG(2) << __func__;
+
+ do_in_main_thread(FROM_HERE, Bind(&bta_jv_l2cap_close_fixed, handle));
+ return BTA_JV_SUCCESS;
+}
+
+/*******************************************************************************
+ *
* Function BTA_JvL2capStartServer
*
* Description This function starts an L2CAP server and listens for an
@@ -288,6 +347,28 @@ void BTA_JvL2capStartServer(int conn_type, tBTA_SEC sec_mask, tBTA_JV_ROLE role,
/*******************************************************************************
*
+ * Function BTA_JvL2capStartServerLE
+ *
+ * Description This function starts an LE L2CAP server and listens for an
+ * L2CAP connection from a remote Bluetooth device. When the
+ * server is started successfully, tBTA_JV_L2CAP_CBACK is
+ * called with BTA_JV_L2CAP_START_EVT. When the connection is
+ * established, tBTA_JV_L2CAP_CBACK is called with
+ * BTA_JV_L2CAP_OPEN_EVT.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTA_JvL2capStartServerLE(uint16_t local_chan, tBTA_JV_L2CAP_CBACK* p_cback,
+ uint32_t l2cap_socket_id) {
+ VLOG(2) << __func__;
+ CHECK(p_cback);
+ do_in_main_thread(FROM_HERE, Bind(&bta_jv_l2cap_start_server_le, local_chan,
+ p_cback, l2cap_socket_id));
+}
+
+/*******************************************************************************
+ *
* Function BTA_JvL2capStopServer
*
* Description This function stops the L2CAP server. If the server has an
@@ -308,6 +389,25 @@ tBTA_JV_STATUS BTA_JvL2capStopServer(uint16_t local_psm,
/*******************************************************************************
*
+ * Function BTA_JvL2capStopServerLE
+ *
+ * Description This function stops the LE L2CAP server. If the server has
+ * an active connection, it would be closed.
+ *
+ * Returns BTA_JV_SUCCESS, if the request is being processed.
+ * BTA_JV_FAILURE, otherwise.
+ *
+ ******************************************************************************/
+tBTA_JV_STATUS BTA_JvL2capStopServerLE(uint16_t local_chan,
+ uint32_t l2cap_socket_id) {
+ VLOG(2) << __func__;
+
+ do_in_main_thread(FROM_HERE, Bind(&bta_jv_l2cap_stop_server_le, local_chan));
+ return BTA_JV_SUCCESS;
+}
+
+/*******************************************************************************
+ *
* Function BTA_JvL2capRead
*
* Description This function reads data from an L2CAP connection
@@ -398,6 +498,26 @@ tBTA_JV_STATUS BTA_JvL2capWrite(uint32_t handle, uint32_t req_id, BT_HDR* msg,
/*******************************************************************************
*
+ * Function BTA_JvL2capWriteFixed
+ *
+ * Description This function writes data to an L2CAP connection
+ * When the operation is complete, tBTA_JV_L2CAP_CBACK is
+ * called with BTA_JV_L2CAP_WRITE_EVT. Works for
+ * fixed-channel connections. This function takes ownership of
+ * p_data, and will osi_free it.
+ *
+ ******************************************************************************/
+void BTA_JvL2capWriteFixed(uint16_t channel, const RawAddress& addr,
+ uint32_t req_id, tBTA_JV_L2CAP_CBACK* p_cback,
+ BT_HDR* msg, uint32_t user_id) {
+ VLOG(2) << __func__;
+
+ do_in_main_thread(FROM_HERE, Bind(&bta_jv_l2cap_write_fixed, channel, addr,
+ req_id, msg, user_id, p_cback));
+}
+
+/*******************************************************************************
+ *
* Function BTA_JvRfcommConnect
*
* Description This function makes an RFCOMM conection to a remote BD
@@ -422,7 +542,7 @@ tBTA_JV_STATUS BTA_JvRfcommConnect(tBTA_SEC sec_mask, tBTA_JV_ROLE role,
if (!p_cback) return BTA_JV_FAILURE; /* Nothing to do */
do_in_main_thread(FROM_HERE,
- Bind(&bta_jv_rfcomm_connect, sec_mask, remote_scn,
+ Bind(&bta_jv_rfcomm_connect, sec_mask, role, remote_scn,
peer_bd_addr, p_cback, rfcomm_slot_id));
return BTA_JV_SUCCESS;
}
@@ -483,7 +603,7 @@ tBTA_JV_STATUS BTA_JvRfcommStartServer(tBTA_SEC sec_mask, tBTA_JV_ROLE role,
}
do_in_main_thread(FROM_HERE,
- Bind(&bta_jv_rfcomm_start_server, sec_mask, local_scn,
+ Bind(&bta_jv_rfcomm_start_server, sec_mask, role, local_scn,
max_session, p_cback, rfcomm_slot_id));
return BTA_JV_SUCCESS;
}
diff --git a/bta/jv/bta_jv_cfg.cc b/bta/jv/bta_jv_cfg.cc
index baec991d4..c01445e87 100644
--- a/bta/jv/bta_jv_cfg.cc
+++ b/bta/jv/bta_jv_cfg.cc
@@ -24,12 +24,9 @@
*
******************************************************************************/
-#include <cstdint>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_jv_api.h"
-#include "stack/include/sdp_api.h"
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_jv_api.h"
#ifndef BTA_JV_SDP_DB_SIZE
#define BTA_JV_SDP_DB_SIZE 4500
diff --git a/bta/jv/bta_jv_int.h b/bta/jv/bta_jv_int.h
index 8bd206bf0..fa7158042 100644
--- a/bta/jv/bta_jv_int.h
+++ b/bta/jv/bta_jv_int.h
@@ -24,11 +24,13 @@
#ifndef BTA_JV_INT_H
#define BTA_JV_INT_H
-#include <memory>
-#include <unordered_set>
+#include "bta_api.h"
+#include "bta_jv_api.h"
+#include "bta_sys.h"
+#include "port_api.h"
+#include "rfcdefs.h"
-#include "bta/include/bta_jv_api.h"
-#include "stack/include/rfcdefs.h"
+#include <memory>
/*****************************************************************************
* Constants
@@ -123,8 +125,6 @@ typedef struct {
uint8_t sdp_active; /* see BTA_JV_SDP_ACT_* */
bluetooth::Uuid uuid; /* current uuid of sdp discovery*/
tBTA_JV_PM_CB pm_cb[BTA_JV_PM_MAX_NUM]; /* PM on a per JV handle bases */
-
- uint16_t dyn_psm; /* Next dynamic PSM value to try to assign */
} tBTA_JV_CB;
enum {
@@ -136,8 +136,6 @@ enum {
/* JV control block */
extern tBTA_JV_CB bta_jv_cb;
-extern std::unordered_set<uint16_t> used_l2cap_classic_dynamic_psm;
-
/* config struct */
extern tBTA_JV_CFG* p_bta_jv_cfg;
@@ -170,13 +168,14 @@ extern void bta_jv_l2cap_stop_server(uint16_t local_psm,
uint32_t l2cap_socket_id);
extern void bta_jv_l2cap_write(uint32_t handle, uint32_t req_id, BT_HDR* msg,
uint32_t user_id, tBTA_JV_L2C_CB* p_cb);
-extern void bta_jv_rfcomm_connect(tBTA_SEC sec_mask, uint8_t remote_scn,
+extern void bta_jv_rfcomm_connect(tBTA_SEC sec_mask, tBTA_JV_ROLE role,
+ uint8_t remote_scn,
const RawAddress& peer_bd_addr,
tBTA_JV_RFCOMM_CBACK* p_cback,
uint32_t rfcomm_slot_id);
extern void bta_jv_rfcomm_close(uint32_t handle, uint32_t rfcomm_slot_id);
-extern void bta_jv_rfcomm_start_server(tBTA_SEC sec_mask, uint8_t local_scn,
- uint8_t max_session,
+extern void bta_jv_rfcomm_start_server(tBTA_SEC sec_mask, tBTA_JV_ROLE role,
+ uint8_t local_scn, uint8_t max_session,
tBTA_JV_RFCOMM_CBACK* p_cback,
uint32_t rfcomm_slot_id);
extern void bta_jv_rfcomm_stop_server(uint32_t handle, uint32_t rfcomm_slot_id);
@@ -184,7 +183,18 @@ extern void bta_jv_rfcomm_write(uint32_t handle, uint32_t req_id,
tBTA_JV_RFC_CB* p_cb, tBTA_JV_PCB* p_pcb);
extern void bta_jv_set_pm_profile(uint32_t handle, tBTA_JV_PM_ID app_id,
tBTA_JV_CONN_STATE init_st);
-
+extern void bta_jv_l2cap_connect_le(uint16_t remote_chan,
+ const RawAddress& peer_bd_addr,
+ tBTA_JV_L2CAP_CBACK* p_cback,
+ uint32_t l2cap_socket_id);
+extern void bta_jv_l2cap_start_server_le(uint16_t local_chan,
+ tBTA_JV_L2CAP_CBACK* p_cback,
+ uint32_t l2cap_socket_id);
extern void bta_jv_l2cap_stop_server_le(uint16_t local_chan);
+extern void bta_jv_l2cap_write_fixed(uint16_t channel, const RawAddress& addr,
+ uint32_t req_id, BT_HDR* msg,
+ uint32_t user_id,
+ tBTA_JV_L2CAP_CBACK* p_cback);
+extern void bta_jv_l2cap_close_fixed(uint32_t handle);
#endif /* BTA_JV_INT_H */
diff --git a/bta/mce/bta_mce_act.cc b/bta/mce/bta_mce_act.cc
new file mode 100644
index 000000000..0d9bbf38c
--- /dev/null
+++ b/bta/mce/bta_mce_act.cc
@@ -0,0 +1,189 @@
+/******************************************************************************
+ *
+ * Copyright 2014 The Android Open Source Project
+ * Copyright 2003-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+/******************************************************************************
+ *
+ * This file contains action functions for MCE.
+ *
+ ******************************************************************************/
+
+#include <arpa/inet.h>
+#include <hardware/bluetooth.h>
+
+#include <string.h>
+#include "bt_common.h"
+#include "bt_types.h"
+#include "bta_api.h"
+#include "bta_mce_api.h"
+#include "bta_mce_int.h"
+#include "bta_sys.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "sdp_api.h"
+#include "utl.h"
+
+using bluetooth::Uuid;
+
+/*****************************************************************************
+ * Constants
+ ****************************************************************************/
+
+static const Uuid bta_mce_mas_uuid =
+ Uuid::From16Bit(UUID_SERVCLASS_MESSAGE_ACCESS);
+
+/*******************************************************************************
+ *
+ * Function bta_mce_search_cback
+ *
+ * Description Callback from btm after search is completed
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+
+static void bta_mce_search_cback(uint16_t result, void* user_data) {
+ tSDP_DISC_REC* p_rec = NULL;
+ tBTA_MCE_MAS_DISCOVERY_COMP evt_data;
+ int found = 0;
+
+ APPL_TRACE_DEBUG("bta_mce_start_discovery_cback res: 0x%x", result);
+
+ bta_mce_cb.sdp_active = BTA_MCE_SDP_ACT_NONE;
+
+ if (bta_mce_cb.p_dm_cback == NULL) return;
+
+ evt_data.status = BTA_MCE_FAILURE;
+ evt_data.remote_addr = bta_mce_cb.remote_addr;
+ evt_data.num_mas = 0;
+
+ if (result == SDP_SUCCESS || result == SDP_DB_FULL) {
+ do {
+ tSDP_DISC_ATTR* p_attr;
+ tSDP_PROTOCOL_ELEM pe;
+
+ p_rec = SDP_FindServiceUUIDInDb(p_bta_mce_cfg->p_sdp_db, bta_mce_mas_uuid,
+ p_rec);
+
+ APPL_TRACE_DEBUG("p_rec:%p", p_rec);
+
+ if (p_rec == NULL) break;
+
+ if (!SDP_FindProtocolListElemInRec(p_rec, UUID_PROTOCOL_RFCOMM, &pe))
+ continue;
+
+ evt_data.mas[found].scn = pe.params[0];
+
+ p_attr = SDP_FindAttributeInRec(p_rec, ATTR_ID_SERVICE_NAME);
+ if (p_attr == NULL) continue;
+
+ evt_data.mas[found].p_srv_name = (char*)p_attr->attr_value.v.array;
+ evt_data.mas[found].srv_name_len =
+ SDP_DISC_ATTR_LEN(p_attr->attr_len_type);
+
+ p_attr = SDP_FindAttributeInRec(p_rec, ATTR_ID_MAS_INSTANCE_ID);
+ if (p_attr == NULL) break;
+
+ evt_data.mas[found].instance_id = p_attr->attr_value.v.u8;
+
+ p_attr = SDP_FindAttributeInRec(p_rec, ATTR_ID_SUPPORTED_MSG_TYPE);
+ if (p_attr == NULL) break;
+
+ evt_data.mas[found].msg_type = p_attr->attr_value.v.u8;
+
+ found++;
+ } while (p_rec != NULL && found < BTA_MCE_MAX_MAS_INSTANCES);
+
+ evt_data.num_mas = found;
+ evt_data.status = BTA_MCE_SUCCESS;
+ }
+
+ tBTA_MCE bta_mce;
+ bta_mce.mas_disc_comp = evt_data;
+ bta_mce_cb.p_dm_cback(BTA_MCE_MAS_DISCOVERY_COMP_EVT, &bta_mce, user_data);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_mce_enable
+ *
+ * Description Initializes the MCE I/F
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_mce_enable(tBTA_MCE_MSG* p_data) {
+ tBTA_MCE_STATUS status = BTA_MCE_SUCCESS;
+ bta_mce_cb.p_dm_cback = p_data->enable.p_cback;
+ tBTA_MCE bta_mce;
+ bta_mce.status = status;
+ bta_mce_cb.p_dm_cback(BTA_MCE_ENABLE_EVT, &bta_mce, NULL);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_mce_get_remote_mas_instances
+ *
+ * Description Discovers MAS instances on remote device
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_mce_get_remote_mas_instances(tBTA_MCE_MSG* p_data) {
+ if (p_data == NULL) {
+ APPL_TRACE_DEBUG("MCE control block handle is null");
+ return;
+ }
+ tBTA_MCE_STATUS status = BTA_MCE_FAILURE;
+
+ APPL_TRACE_DEBUG("%s in, sdp_active:%d", __func__, bta_mce_cb.sdp_active);
+
+ if (bta_mce_cb.sdp_active != BTA_MCE_SDP_ACT_NONE) {
+ /* SDP is still in progress */
+ status = BTA_MCE_BUSY;
+ if (bta_mce_cb.p_dm_cback) {
+ tBTA_MCE bta_mce;
+ bta_mce.status = status;
+ bta_mce_cb.p_dm_cback(BTA_MCE_MAS_DISCOVERY_COMP_EVT, &bta_mce, NULL);
+ }
+
+ return;
+ }
+
+ bta_mce_cb.sdp_active = BTA_MCE_SDP_ACT_YES;
+ bta_mce_cb.remote_addr = p_data->get_rmt_mas.bd_addr;
+
+ SDP_InitDiscoveryDb(p_bta_mce_cfg->p_sdp_db, p_bta_mce_cfg->sdp_db_size, 1,
+ &bta_mce_mas_uuid, 0, NULL);
+
+ if (!SDP_ServiceSearchAttributeRequest2(p_data->get_rmt_mas.bd_addr,
+ p_bta_mce_cfg->p_sdp_db,
+ bta_mce_search_cback, NULL)) {
+ bta_mce_cb.sdp_active = BTA_MCE_SDP_ACT_NONE;
+
+ /* failed to start SDP. report the failure right away */
+ if (bta_mce_cb.p_dm_cback) {
+ tBTA_MCE bta_mce;
+ bta_mce.status = status;
+ bta_mce_cb.p_dm_cback(BTA_MCE_MAS_DISCOVERY_COMP_EVT, &bta_mce, NULL);
+ }
+ }
+ /*
+ else report the result when the cback is called
+ */
+}
diff --git a/bta/mce/bta_mce_api.cc b/bta/mce/bta_mce_api.cc
new file mode 100644
index 000000000..7ab10dae8
--- /dev/null
+++ b/bta/mce/bta_mce_api.cc
@@ -0,0 +1,107 @@
+/******************************************************************************
+ *
+ * Copyright 2014 The Android Open Source Project
+ * Copyright 2003-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+/******************************************************************************
+ *
+ * This is the implementation of the API for MCE subsystem
+ *
+ ******************************************************************************/
+
+#include <string.h>
+
+#include "bt_common.h"
+#include "bt_types.h"
+#include "bta_api.h"
+#include "bta_mce_api.h"
+#include "bta_mce_int.h"
+#include "bta_sys.h"
+#include "port_api.h"
+#include "sdp_api.h"
+
+/*****************************************************************************
+ * Constants
+ ****************************************************************************/
+
+static const tBTA_SYS_REG bta_mce_reg = {bta_mce_sm_execute, NULL};
+
+/*******************************************************************************
+ *
+ * Function BTA_MceEnable
+ *
+ * Description Enable the MCE I/F service. When the enable
+ * operation is complete the callback function will be
+ * called with a BTA_MCE_ENABLE_EVT. This function must
+ * be called before other functions in the MCE API are
+ * called.
+ *
+ * Returns BTA_MCE_SUCCESS if successful.
+ * BTA_MCE_FAIL if internal failure.
+ *
+ ******************************************************************************/
+tBTA_MCE_STATUS BTA_MceEnable(tBTA_MCE_DM_CBACK* p_cback) {
+ tBTA_MCE_STATUS status = BTA_MCE_FAILURE;
+
+ APPL_TRACE_API("%", __func__);
+
+ if (p_cback && !bta_sys_is_register(BTA_ID_MCE)) {
+ memset(&bta_mce_cb, 0, sizeof(tBTA_MCE_CB));
+
+ /* register with BTA system manager */
+ bta_sys_register(BTA_ID_MCE, &bta_mce_reg);
+
+ if (p_cback) {
+ tBTA_MCE_API_ENABLE* p_buf =
+ (tBTA_MCE_API_ENABLE*)osi_malloc(sizeof(tBTA_MCE_API_ENABLE));
+ p_buf->hdr.event = BTA_MCE_API_ENABLE_EVT;
+ p_buf->p_cback = p_cback;
+ bta_sys_sendmsg(p_buf);
+ status = BTA_MCE_SUCCESS;
+ }
+ }
+
+ return status;
+}
+
+/*******************************************************************************
+ *
+ * Function BTA_MceGetRemoteMasInstances
+ *
+ * Description This function performs service discovery for the MAS service
+ * by the given peer device. When the operation is completed
+ * the tBTA_MCE_DM_CBACK callback function will be called with
+ * a BTA_MCE_MAS_DISCOVERY_COMP_EVT.
+ *
+ * Returns BTA_MCE_SUCCESS, if the request is being processed.
+ * BTA_MCE_FAILURE, otherwise.
+ *
+ ******************************************************************************/
+tBTA_MCE_STATUS BTA_MceGetRemoteMasInstances(const RawAddress& bd_addr) {
+ tBTA_MCE_API_GET_REMOTE_MAS_INSTANCES* p_msg =
+ (tBTA_MCE_API_GET_REMOTE_MAS_INSTANCES*)osi_malloc(
+ sizeof(tBTA_MCE_API_GET_REMOTE_MAS_INSTANCES));
+
+ APPL_TRACE_API("%s", __func__);
+
+ p_msg->hdr.event = BTA_MCE_API_GET_REMOTE_MAS_INSTANCES_EVT;
+ p_msg->bd_addr = bd_addr;
+
+ bta_sys_sendmsg(p_msg);
+
+ return BTA_MCE_SUCCESS;
+}
diff --git a/bta/mce/bta_mce_cfg.cc b/bta/mce/bta_mce_cfg.cc
new file mode 100644
index 000000000..ede80ba67
--- /dev/null
+++ b/bta/mce/bta_mce_cfg.cc
@@ -0,0 +1,45 @@
+/******************************************************************************
+ *
+ * Copyright 2014 The Android Open Source Project
+ * Copyright 2003-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+/******************************************************************************
+ *
+ * This file contains compile-time configurable constants for MCE
+ *
+ ******************************************************************************/
+
+#include "bt_common.h"
+#include "bt_types.h"
+#include "bta_api.h"
+#include "bta_mce_api.h"
+
+#ifndef BTA_MCE_SDP_DB_SIZE
+#define BTA_MCE_SDP_DB_SIZE 4500
+#endif
+
+static tSDP_DISCOVERY_DB
+ bta_mce_sdp_db_data[BTA_MCE_SDP_DB_SIZE / sizeof(tSDP_DISCOVERY_DB)];
+
+/* MCE configuration structure */
+const tBTA_MCE_CFG bta_mce_cfg = {
+ (BTA_MCE_SDP_DB_SIZE / sizeof(tSDP_DISCOVERY_DB)) *
+ sizeof(tSDP_DISCOVERY_DB),
+ bta_mce_sdp_db_data /* The data buffer to keep SDP database */
+};
+
+const tBTA_MCE_CFG* p_bta_mce_cfg = &bta_mce_cfg;
diff --git a/bta/mce/bta_mce_int.h b/bta/mce/bta_mce_int.h
new file mode 100644
index 000000000..4e1058fd4
--- /dev/null
+++ b/bta/mce/bta_mce_int.h
@@ -0,0 +1,86 @@
+/******************************************************************************
+ *
+ * Copyright 2014 The Android Open Source Project
+ * Copyright 2003-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+/******************************************************************************
+ *
+ * This is the private interface file for the BTA MCE I/F
+ *
+ ******************************************************************************/
+#ifndef BTA_MCE_INT_H
+#define BTA_MCE_INT_H
+
+#include "bta_api.h"
+#include "bta_mce_api.h"
+#include "bta_sys.h"
+
+/*****************************************************************************
+ * Constants
+ ****************************************************************************/
+
+enum {
+ /* these events are handled by the state machine */
+ BTA_MCE_API_ENABLE_EVT = BTA_SYS_EVT_START(BTA_ID_MCE),
+ BTA_MCE_API_GET_REMOTE_MAS_INSTANCES_EVT,
+ BTA_MCE_MAX_INT_EVT
+};
+
+/* data type for BTA_MCE_API_ENABLE_EVT */
+typedef struct {
+ BT_HDR hdr;
+ tBTA_MCE_DM_CBACK* p_cback;
+} tBTA_MCE_API_ENABLE;
+
+/* data type for BTA_MCE_API_GET_REMOTE_MAS_INSTANCES_EVT */
+typedef struct {
+ BT_HDR hdr;
+ RawAddress bd_addr;
+} tBTA_MCE_API_GET_REMOTE_MAS_INSTANCES;
+
+/* union of all data types */
+typedef union {
+ /* GKI event buffer header */
+ BT_HDR hdr;
+ tBTA_MCE_API_ENABLE enable;
+ tBTA_MCE_API_GET_REMOTE_MAS_INSTANCES get_rmt_mas;
+} tBTA_MCE_MSG;
+
+/* MCE control block */
+typedef struct {
+ uint8_t sdp_active; /* see BTA_MCE_SDP_ACT_* */
+ RawAddress remote_addr;
+ tBTA_MCE_DM_CBACK* p_dm_cback;
+} tBTA_MCE_CB;
+
+enum {
+ BTA_MCE_SDP_ACT_NONE = 0,
+ BTA_MCE_SDP_ACT_YES /* waiting for SDP result */
+};
+
+/* MCE control block */
+extern tBTA_MCE_CB bta_mce_cb;
+
+/* config struct */
+extern tBTA_MCE_CFG* p_bta_mce_cfg;
+
+extern bool bta_mce_sm_execute(BT_HDR* p_msg);
+
+extern void bta_mce_enable(tBTA_MCE_MSG* p_data);
+extern void bta_mce_get_remote_mas_instances(tBTA_MCE_MSG* p_data);
+
+#endif /* BTA_MCE_INT_H */
diff --git a/bta/mce/bta_mce_main.cc b/bta/mce/bta_mce_main.cc
new file mode 100644
index 000000000..d2a2ca172
--- /dev/null
+++ b/bta/mce/bta_mce_main.cc
@@ -0,0 +1,75 @@
+/******************************************************************************
+ *
+ * Copyright 2014 The Android Open Source Project
+ * Copyright 2003-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+/******************************************************************************
+ *
+ * This is the main implementation file for the BTA MCE I/F
+ *
+ ******************************************************************************/
+
+#include <stddef.h>
+
+#include "bta_api.h"
+#include "bta_mce_api.h"
+#include "bta_mce_int.h"
+#include "bta_sys.h"
+
+/*****************************************************************************
+ * Constants and types
+ ****************************************************************************/
+
+tBTA_MCE_CB bta_mce_cb;
+
+/* state machine action enumeration list */
+#define BTA_MCE_NUM_ACTIONS (BTA_MCE_MAX_INT_EVT & 0x00ff)
+
+/* type for action functions */
+typedef void (*tBTA_MCE_ACTION)(tBTA_MCE_MSG* p_data);
+
+/* action function list */
+const tBTA_MCE_ACTION bta_mce_action[] = {
+ bta_mce_enable, /* BTA_MCE_API_ENABLE_EVT */
+ bta_mce_get_remote_mas_instances, /* BTA_MCE_API_GET_REMOTE_MAS_INSTANCES_EVT
+ */
+};
+
+/*******************************************************************************
+ *
+ * Function bta_mce_sm_execute
+ *
+ * Description State machine event handling function for MCE
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+bool bta_mce_sm_execute(BT_HDR* p_msg) {
+ if (p_msg == NULL) return false;
+
+ bool ret = false;
+ uint16_t action = (p_msg->event & 0x00ff);
+
+ /* execute action functions */
+ if (action < BTA_MCE_NUM_ACTIONS) {
+ (*bta_mce_action[action])((tBTA_MCE_MSG*)p_msg);
+ ret = true;
+ }
+
+ return (ret);
+}
diff --git a/bta/pan/bta_pan_act.cc b/bta/pan/bta_pan_act.cc
index 3543ea1e1..f887cbac4 100644
--- a/bta/pan/bta_pan_act.cc
+++ b/bta/pan/bta_pan_act.cc
@@ -22,23 +22,23 @@
*
******************************************************************************/
-#define LOG_TAG "bluetooth"
+#include "bt_target.h"
-#include <cstdint>
-
-// PAN_INCLUDED
-#include "bt_target.h" // Must be first to define build configuration
#if (PAN_INCLUDED == TRUE)
-#include "bta/include/bta_pan_co.h"
-#include "bta/pan/bta_pan_int.h"
-#include "osi/include/allocator.h"
-#include "osi/include/fixed_queue.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/include/bt_types.h"
-#include "stack/include/pan_api.h"
-#include "types/raw_address.h"
+#include <string.h>
+
+#include <log/log.h>
+
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_pan_api.h"
+#include "bta_pan_co.h"
+#include "bta_pan_int.h"
+#include "bta_sys.h"
+#include "osi/include/osi.h"
+#include "pan_api.h"
+#include "utl.h"
/* RX and TX data flow mask */
#define BTA_PAN_RX_MASK 0x0F
@@ -114,6 +114,8 @@ static void bta_pan_conn_state_cback(uint16_t handle, const RawAddress& bd_addr,
if (src_role == PAN_ROLE_CLIENT)
p_scb->app_id = bta_pan_cb.app_id[0];
+ else if (src_role == PAN_ROLE_GN_SERVER)
+ p_scb->app_id = bta_pan_cb.app_id[1];
else if (src_role == PAN_ROLE_NAP_SERVER)
p_scb->app_id = bta_pan_cb.app_id[2];
} else if ((state != PAN_SUCCESS) && !is_role_change) {
@@ -145,7 +147,7 @@ static void bta_pan_data_flow_cb(uint16_t handle, tPAN_RESULT result) {
if (p_scb == NULL) return;
if (result == PAN_TX_FLOW_ON) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->layer_specific = handle;
p_buf->event = BTA_PAN_BNEP_FLOW_ENABLE_EVT;
bta_sys_sendmsg(p_buf);
@@ -196,7 +198,7 @@ static void bta_pan_data_buf_ind_cback(uint16_t handle, const RawAddress& src,
((tBTA_PAN_DATA_PARAMS*)p_new_buf)->forward = forward;
fixed_queue_enqueue(p_scb->data_queue, p_new_buf);
- BT_HDR_RIGID* p_event = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_event = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_event->layer_specific = handle;
p_event->event = BTA_PAN_RX_FROM_BNEP_READY_EVT;
bta_sys_sendmsg(p_event);
@@ -297,6 +299,12 @@ static bool bta_pan_has_multiple_connections(uint8_t app_id) {
******************************************************************************/
void bta_pan_enable(tBTA_PAN_DATA* p_data) {
tPAN_REGISTER reg_data;
+ uint16_t initial_discoverability;
+ uint16_t initial_connectability;
+ uint16_t d_window;
+ uint16_t d_interval;
+ uint16_t c_window;
+ uint16_t c_interval;
bta_pan_cb.p_cback = p_data->api_enable.p_cback;
@@ -308,8 +316,18 @@ void bta_pan_enable(tBTA_PAN_DATA* p_data) {
reg_data.pan_mfilt_ind_cb = bta_pan_mfilt_ind_cback;
reg_data.pan_tx_data_flow_cb = bta_pan_data_flow_cb;
+ /* read connectability and discoverability settings.
+ Pan profile changes the settings. We have to change it back to
+ be consistent with other bta subsystems */
+ initial_connectability = BTM_ReadConnectability(&c_window, &c_interval);
+ initial_discoverability = BTM_ReadDiscoverability(&d_window, &d_interval);
+
PAN_Register(&reg_data);
+ /* set it back to original value */
+ BTM_SetDiscoverability(initial_discoverability, d_window, d_interval);
+ BTM_SetConnectability(initial_connectability, c_window, c_interval);
+
bta_pan_cb.flow_mask = bta_pan_co_init(&bta_pan_cb.q_level);
bta_pan_cb.p_cback(BTA_PAN_ENABLE_EVT, NULL);
}
@@ -326,14 +344,20 @@ void bta_pan_enable(tBTA_PAN_DATA* p_data) {
void bta_pan_set_role(tBTA_PAN_DATA* p_data) {
tPAN_RESULT status;
tBTA_PAN bta_pan;
+ uint8_t sec[3];
bta_pan_cb.app_id[0] = p_data->api_set_role.user_app_id;
+ bta_pan_cb.app_id[1] = p_data->api_set_role.gn_app_id;
bta_pan_cb.app_id[2] = p_data->api_set_role.nap_app_id;
+ sec[0] = p_data->api_set_role.user_sec_mask;
+ sec[1] = p_data->api_set_role.gn_sec_mask;
+ sec[2] = p_data->api_set_role.nap_sec_mask;
+
/* set security correctly in api and here */
- status =
- PAN_SetRole(p_data->api_set_role.role, p_data->api_set_role.user_name,
- p_data->api_set_role.nap_name);
+ status = PAN_SetRole(
+ p_data->api_set_role.role, sec, p_data->api_set_role.user_name,
+ p_data->api_set_role.gn_name, p_data->api_set_role.nap_name);
bta_pan.set_role.role = p_data->api_set_role.role;
if (status == PAN_SUCCESS) {
@@ -342,6 +366,11 @@ void bta_pan_set_role(tBTA_PAN_DATA* p_data) {
else
bta_sys_remove_uuid(UUID_SERVCLASS_NAP);
+ if (p_data->api_set_role.role & PAN_ROLE_GN_SERVER)
+ bta_sys_add_uuid(UUID_SERVCLASS_GN);
+ else
+ bta_sys_remove_uuid(UUID_SERVCLASS_GN);
+
if (p_data->api_set_role.role & PAN_ROLE_CLIENT)
bta_sys_add_uuid(UUID_SERVCLASS_PANU);
else
@@ -351,7 +380,7 @@ void bta_pan_set_role(tBTA_PAN_DATA* p_data) {
}
/* if status is not success clear everything */
else {
- PAN_SetRole(0, NULL, NULL);
+ PAN_SetRole(0, 0, NULL, NULL, NULL);
bta_sys_remove_uuid(UUID_SERVCLASS_NAP);
bta_sys_remove_uuid(UUID_SERVCLASS_GN);
bta_sys_remove_uuid(UUID_SERVCLASS_PANU);
@@ -377,7 +406,7 @@ void bta_pan_disable(void) {
uint8_t i;
/* close all connections */
- PAN_SetRole(0, NULL, NULL);
+ PAN_SetRole(0, NULL, NULL, NULL, NULL);
#if (BTA_EIR_CANNED_UUID_LIST != TRUE)
bta_sys_remove_uuid(UUID_SERVCLASS_NAP);
@@ -493,9 +522,10 @@ void bta_pan_conn_open(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data) {
p_scb->app_flow_enable = true;
/* If app_id is NAP/GN, check whether there are multiple connections.
- If there are, provide a special app_id to dm to enforce central role only.
+ If there are, provide a special app_id to dm to enforce master role only.
*/
- if (p_scb->app_id == bta_pan_cb.app_id[2] &&
+ if ((p_scb->app_id == bta_pan_cb.app_id[1] ||
+ p_scb->app_id == bta_pan_cb.app_id[2]) &&
bta_pan_has_multiple_connections(p_scb->app_id)) {
p_scb->app_id = BTA_APP_ID_PAN_MULTI;
}
diff --git a/bta/pan/bta_pan_api.cc b/bta/pan/bta_pan_api.cc
index a119125e8..9f2573565 100644
--- a/bta/pan/bta_pan_api.cc
+++ b/bta/pan/bta_pan_api.cc
@@ -22,25 +22,23 @@
* Broadcom's Bluetooth application layer for mobile phones.
*
******************************************************************************/
+#include <string.h>
-#include <cstdint>
+#include "bt_target.h"
-#include "bt_target.h" // Must be first to define build configuration
-#if (BTA_PAN_INCLUDED == TRUE)
+#include "bt_common.h"
+#include "bt_utils.h"
+#include "bta_api.h"
+#include "bta_pan_api.h"
+#include "bta_pan_int.h"
+#include "bta_sys.h"
+#include "osi/include/osi.h"
+#include "pan_api.h"
-#include "bta/pan/bta_pan_int.h"
-#include "osi/include/allocator.h"
-#include "osi/include/compat.h"
-#include "types/raw_address.h"
+#if (BTA_PAN_INCLUDED == TRUE)
static const tBTA_SYS_REG bta_pan_reg = {bta_pan_hdl_event, BTA_PanDisable};
-#ifndef PAN_SECURITY
-#define PAN_SECURITY \
- (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_IN_ENCRYPT | \
- BTM_SEC_OUT_ENCRYPT)
-#endif
-
/*******************************************************************************
*
* Function BTA_PanEnable
@@ -77,7 +75,7 @@ void BTA_PanEnable(tBTA_PAN_CBACK p_cback) {
*
******************************************************************************/
void BTA_PanDisable(void) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
bta_sys_deregister(BTA_ID_PAN);
p_buf->event = BTA_PAN_API_DISABLE_EVT;
@@ -97,6 +95,7 @@ void BTA_PanDisable(void) {
*
******************************************************************************/
void BTA_PanSetRole(tBTA_PAN_ROLE role, tBTA_PAN_ROLE_INFO* p_user_info,
+ tBTA_PAN_ROLE_INFO* p_gn_info,
tBTA_PAN_ROLE_INFO* p_nap_info) {
tBTA_PAN_API_SET_ROLE* p_buf =
(tBTA_PAN_API_SET_ROLE*)osi_calloc(sizeof(tBTA_PAN_API_SET_ROLE));
@@ -104,18 +103,28 @@ void BTA_PanSetRole(tBTA_PAN_ROLE role, tBTA_PAN_ROLE_INFO* p_user_info,
p_buf->hdr.event = BTA_PAN_API_SET_ROLE_EVT;
p_buf->role = role;
- if (role & BTA_PAN_ROLE_PANU) {
+ if (p_user_info && (role & BTA_PAN_ROLE_PANU)) {
if (p_user_info->p_srv_name)
strlcpy(p_buf->user_name, p_user_info->p_srv_name, BTA_SERVICE_NAME_LEN);
p_buf->user_app_id = p_user_info->app_id;
+ p_buf->user_sec_mask = p_user_info->sec_mask;
+ }
+
+ if (p_gn_info && (role & BTA_PAN_ROLE_GN)) {
+ if (p_gn_info->p_srv_name)
+ strlcpy(p_buf->gn_name, p_gn_info->p_srv_name, BTA_SERVICE_NAME_LEN);
+
+ p_buf->gn_app_id = p_gn_info->app_id;
+ p_buf->gn_sec_mask = p_gn_info->sec_mask;
}
- if (role & BTA_PAN_ROLE_NAP) {
+ if (p_nap_info && (role & BTA_PAN_ROLE_NAP)) {
if (p_nap_info->p_srv_name)
strlcpy(p_buf->nap_name, p_nap_info->p_srv_name, BTA_SERVICE_NAME_LEN);
p_buf->nap_app_id = p_nap_info->app_id;
+ p_buf->nap_sec_mask = p_nap_info->sec_mask;
}
bta_sys_sendmsg(p_buf);
@@ -157,7 +166,7 @@ void BTA_PanOpen(const RawAddress& bd_addr, tBTA_PAN_ROLE local_role,
*
******************************************************************************/
void BTA_PanClose(uint16_t handle) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = BTA_PAN_API_CLOSE_EVT;
p_buf->layer_specific = handle;
@@ -165,8 +174,6 @@ void BTA_PanClose(uint16_t handle) {
bta_sys_sendmsg(p_buf);
}
#else
-#include "bta/pan/bta_pan_int.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
void BTA_PanEnable(UNUSED_ATTR tBTA_PAN_CBACK p_cback) {}
diff --git a/bta/pan/bta_pan_ci.cc b/bta/pan/bta_pan_ci.cc
index 4365fe728..7ebb0ad52 100644
--- a/bta/pan/bta_pan_ci.cc
+++ b/bta/pan/bta_pan_ci.cc
@@ -22,11 +22,18 @@
*
******************************************************************************/
-#include "bt_target.h" // Must be first to define build configuration
+#include "bt_target.h"
-#include "bta/pan/bta_pan_int.h"
-#include "osi/include/allocator.h"
-#include "types/raw_address.h"
+#include <string.h>
+
+#include "bt_common.h"
+#include "bt_utils.h"
+#include "bta_api.h"
+#include "bta_pan_api.h"
+#include "bta_pan_ci.h"
+#include "bta_pan_int.h"
+#include "osi/include/osi.h"
+#include "pan_api.h"
#if (BTA_PAN_INCLUDED == TRUE)
@@ -67,7 +74,7 @@ void bta_pan_ci_tx_ready(uint16_t handle) {
*
******************************************************************************/
void bta_pan_ci_rx_ready(uint16_t handle) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->layer_specific = handle;
p_buf->event = BTA_PAN_CI_RX_READY_EVT;
@@ -224,7 +231,6 @@ void bta_pan_ci_set_pfilters(uint16_t handle, uint16_t num_filters,
PAN_SetProtocolFilters(handle, num_filters, p_start_array, p_end_array);
}
#else
-#include "osi/include/osi.h" // UNUSED_ATTR
void bta_pan_ci_tx_ready(UNUSED_ATTR uint16_t handle) {}
diff --git a/bta/pan/bta_pan_int.h b/bta/pan/bta_pan_int.h
index 52270719a..df79fcb47 100644
--- a/bta/pan/bta_pan_int.h
+++ b/bta/pan/bta_pan_int.h
@@ -24,14 +24,9 @@
#ifndef BTA_PAN_INT_H
#define BTA_PAN_INT_H
-#include <cstdint>
-
-#include "bta/include/bta_api.h"
-#include "bta/include/bta_pan_api.h"
-#include "bta/sys/bta_sys.h"
+#include "bta_pan_api.h"
+#include "bta_sys.h"
#include "osi/include/fixed_queue.h"
-#include "stack/include/pan_api.h"
-#include "types/raw_address.h"
/*****************************************************************************
* Constants
@@ -67,23 +62,29 @@ enum { BTA_PAN_IDLE_ST, BTA_PAN_OPEN_ST, BTA_PAN_CLOSING_ST };
/* data type for BTA_PAN_API_ENABLE_EVT */
typedef struct {
- BT_HDR_RIGID hdr; /* Event header */
+ BT_HDR hdr; /* Event header */
tBTA_PAN_CBACK* p_cback; /* PAN callback function */
} tBTA_PAN_API_ENABLE;
/* data type for BTA_PAN_API_REG_ROLE_EVT */
typedef struct {
- BT_HDR_RIGID hdr; /* Event header */
+ BT_HDR hdr; /* Event header */
char user_name[BTA_SERVICE_NAME_LEN + 1]; /* Service name */
+ char gn_name[BTA_SERVICE_NAME_LEN + 1]; /* Service name */
char nap_name[BTA_SERVICE_NAME_LEN + 1]; /* Service name */
tBTA_PAN_ROLE role;
uint8_t user_app_id;
+ uint8_t gn_app_id;
uint8_t nap_app_id;
+ tBTA_SEC user_sec_mask; /* Security mask */
+ tBTA_SEC gn_sec_mask; /* Security mask */
+ tBTA_SEC nap_sec_mask; /* Security mask */
+
} tBTA_PAN_API_SET_ROLE;
/* data type for BTA_PAN_API_OPEN_EVT */
typedef struct {
- BT_HDR_RIGID hdr; /* Event header */
+ BT_HDR hdr; /* Event header */
tBTA_PAN_ROLE local_role; /* local role */
tBTA_PAN_ROLE peer_role; /* peer role */
RawAddress bd_addr; /* peer bdaddr */
@@ -91,20 +92,20 @@ typedef struct {
/* data type for BTA_PAN_CI_TX_FLOW_EVT */
typedef struct {
- BT_HDR_RIGID hdr; /* Event header */
+ BT_HDR hdr; /* Event header */
bool enable; /* Flow control setting */
} tBTA_PAN_CI_TX_FLOW;
/* data type for BTA_PAN_CONN_OPEN_EVT */
typedef struct {
- BT_HDR_RIGID hdr; /* Event header */
+ BT_HDR hdr; /* Event header */
tPAN_RESULT result;
} tBTA_PAN_CONN;
/* union of all data types */
typedef union {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTA_PAN_API_ENABLE api_enable;
tBTA_PAN_API_SET_ROLE api_set_role;
tBTA_PAN_API_OPEN api_open;
@@ -141,7 +142,7 @@ typedef struct {
/* pan data param */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
RawAddress src;
RawAddress dst;
uint16_t protocol;
@@ -164,7 +165,7 @@ extern tBTA_PAN_SCB* bta_pan_scb_alloc(void);
extern void bta_pan_scb_dealloc(tBTA_PAN_SCB* p_scb);
extern uint8_t bta_pan_scb_to_idx(tBTA_PAN_SCB* p_scb);
extern tBTA_PAN_SCB* bta_pan_scb_by_handle(uint16_t handle);
-extern bool bta_pan_hdl_event(BT_HDR_RIGID* p_msg);
+extern bool bta_pan_hdl_event(BT_HDR* p_msg);
/* action functions */
extern void bta_pan_enable(tBTA_PAN_DATA* p_data);
@@ -172,11 +173,13 @@ extern void bta_pan_disable(void);
extern void bta_pan_set_role(tBTA_PAN_DATA* p_data);
extern void bta_pan_open(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data);
extern void bta_pan_api_close(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data);
+extern void bta_pan_set_shutdown(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data);
extern void bta_pan_rx_path(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data);
extern void bta_pan_tx_path(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data);
extern void bta_pan_tx_flow(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data);
extern void bta_pan_conn_open(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data);
extern void bta_pan_conn_close(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data);
+extern void bta_pan_writebuf(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data);
extern void bta_pan_write_buf(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data);
extern void bta_pan_free_buf(tBTA_PAN_SCB* p_scb, tBTA_PAN_DATA* p_data);
diff --git a/bta/pan/bta_pan_main.cc b/bta/pan/bta_pan_main.cc
index 779a8a234..09df88f2e 100644
--- a/bta/pan/bta_pan_main.cc
+++ b/bta/pan/bta_pan_main.cc
@@ -21,14 +21,21 @@
* This file contains the PAN main functions and state machine.
*
******************************************************************************/
-#include <cstdint>
-#include "bt_target.h" // Must be first to define build configuration
+#include "bt_target.h"
#if (BTA_PAN_INCLUDED == TRUE)
-#include "bta/pan/bta_pan_int.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
+#include <string.h>
+
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_pan_api.h"
+#include "bta_pan_int.h"
+#include "bta_sys.h"
+#include "osi/include/osi.h"
+#include "pan_api.h"
+#include "utl.h"
/*****************************************************************************
* Constants and types
@@ -307,7 +314,7 @@ tBTA_PAN_SCB* bta_pan_scb_by_handle(uint16_t handle) {
* Returns void
*
******************************************************************************/
-bool bta_pan_hdl_event(BT_HDR_RIGID* p_msg) {
+bool bta_pan_hdl_event(BT_HDR* p_msg) {
tBTA_PAN_SCB* p_scb;
bool freebuf = true;
diff --git a/bta/pb/bta_pbs_int.h b/bta/pb/bta_pbs_int.h
index 546a5f906..cf597f80e 100644
--- a/bta/pb/bta_pbs_int.h
+++ b/bta/pb/bta_pbs_int.h
@@ -24,8 +24,8 @@
#ifndef BTA_PBS_INT_H
#define BTA_PBS_INT_H
-#include <cstdint>
-#include "bt_target.h" // Must be first to define build configuration
+#include "bt_target.h"
+#include "bta_sys.h"
/*****************************************************************************
* Constants and data types
diff --git a/bta/sdp/bta_sdp.cc b/bta/sdp/bta_sdp.cc
index eaf5c7fa3..1729db856 100644
--- a/bta/sdp/bta_sdp.cc
+++ b/bta/sdp/bta_sdp.cc
@@ -22,6 +22,51 @@
*
******************************************************************************/
-#include "bta/sdp/bta_sdp_int.h"
+#include <stdlib.h>
+
+#include "bta_api.h"
+#include "bta_sdp_api.h"
+#include "bta_sdp_int.h"
+#include "bta_sys.h"
+
+/*****************************************************************************
+ * Constants and types
+ ****************************************************************************/
tBTA_SDP_CB bta_sdp_cb;
+
+/* state machine action enumeration list */
+#define BTA_SDP_NUM_ACTIONS (BTA_SDP_MAX_INT_EVT & 0x00ff)
+
+/* type for action functions */
+typedef void (*tBTA_SDP_ACTION)(tBTA_SDP_MSG* p_data);
+
+/* action function list */
+const tBTA_SDP_ACTION bta_sdp_action[] = {
+ bta_sdp_enable, /* BTA_SDP_API_ENABLE_EVT */
+ bta_sdp_search, /* BTA_SDP_API_SEARCH_EVT */
+ bta_sdp_create_record, /* BTA_SDP_API_CREATE_RECORD_USER_EVT */
+ bta_sdp_remove_record, /* BTA_SDP_API_REMOVE_RECORD_USER_EVT */
+};
+
+/*******************************************************************************
+ * Function bta_sdp_sm_execute
+ *
+ * Description State machine event handling function for SDP search
+ *
+ * Returns void
+ ******************************************************************************/
+bool bta_sdp_sm_execute(BT_HDR* p_msg) {
+ if (p_msg == NULL) return false;
+
+ bool ret = false;
+ uint16_t action = (p_msg->event & 0x00ff);
+
+ /* execute action functions */
+ if (action < BTA_SDP_NUM_ACTIONS) {
+ (*bta_sdp_action[action])((tBTA_SDP_MSG*)p_msg);
+ ret = true;
+ }
+
+ return (ret);
+}
diff --git a/bta/sdp/bta_sdp_act.cc b/bta/sdp/bta_sdp_act.cc
index 296f84f31..80baed7d4 100644
--- a/bta/sdp/bta_sdp_act.cc
+++ b/bta/sdp/bta_sdp_act.cc
@@ -20,16 +20,33 @@
* This file contains action functions for SDP search.
******************************************************************************/
+#include <arpa/inet.h>
+#include <hardware/bluetooth.h>
#include <hardware/bt_sdp.h>
-#include <cstdint>
-
-#include "bta/include/bta_sdp_api.h"
-#include "bta/sdp/bta_sdp_int.h"
-#include "btif/include/btif_sock_sdp.h"
+#include <stdlib.h>
+#include <string.h>
+
+#include "bt_common.h"
+#include "bt_types.h"
+#include "bta_api.h"
+#include "bta_sdp_api.h"
+#include "bta_sdp_int.h"
+#include "bta_sys.h"
+#include "btm_api.h"
+#include "btm_int.h"
#include "osi/include/allocator.h"
-#include "stack/include/sdp_api.h"
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
+#include "sdp_api.h"
+#include "utl.h"
+
+/*****************************************************************************
+ * Constants
+ ****************************************************************************/
+
+static const Uuid UUID_OBEX_OBJECT_PUSH = Uuid::From16Bit(0x1105);
+static const Uuid UUID_PBAP_PSE = Uuid::From16Bit(0x112F);
+static const Uuid UUID_MAP_MAS = Uuid::From16Bit(0x1132);
+static const Uuid UUID_MAP_MNS = Uuid::From16Bit(0x1133);
+static const Uuid UUID_SAP = Uuid::From16Bit(0x112D);
static void bta_create_mns_sdp_record(bluetooth_sdp_record* record,
tSDP_DISC_REC* p_rec) {
@@ -284,60 +301,6 @@ static void bta_create_sap_sdp_record(bluetooth_sdp_record* record,
}
}
-static void bta_create_dip_sdp_record(bluetooth_sdp_record* record,
- tSDP_DISC_REC* p_rec) {
- tSDP_DISC_ATTR* p_attr;
-
- APPL_TRACE_DEBUG("%s()", __func__);
-
- /* hdr is redundancy in dip */
- record->dip.hdr.type = SDP_TYPE_DIP;
- record->dip.hdr.service_name_length = 0;
- record->dip.hdr.service_name = nullptr;
- record->dip.hdr.rfcomm_channel_number = 0;
- record->dip.hdr.l2cap_psm = -1;
- record->dip.hdr.profile_version = 0;
-
- p_attr =
- SDP_FindAttributeInRec(p_rec, ATTR_ID_SPECIFICATION_ID);
- if (p_attr != nullptr)
- record->dip.spec_id = p_attr->attr_value.v.u16;
- else
- APPL_TRACE_ERROR("%s() ATTR_ID_SPECIFICATION_ID not found", __func__);
-
- p_attr = SDP_FindAttributeInRec(p_rec, ATTR_ID_VENDOR_ID);
- if (p_attr != nullptr)
- record->dip.vendor = p_attr->attr_value.v.u16;
- else
- APPL_TRACE_ERROR("%s() ATTR_ID_VENDOR_ID not found", __func__);
-
- p_attr =
- SDP_FindAttributeInRec(p_rec, ATTR_ID_VENDOR_ID_SOURCE);
- if (p_attr != nullptr)
- record->dip.vendor_id_source = p_attr->attr_value.v.u16;
- else
- APPL_TRACE_ERROR("%s() ATTR_ID_VENDOR_ID_SOURCE not found", __func__);
-
- p_attr = SDP_FindAttributeInRec(p_rec, ATTR_ID_PRODUCT_ID);
- if (p_attr != nullptr)
- record->dip.product = p_attr->attr_value.v.u16;
- else
- APPL_TRACE_ERROR("%s() ATTR_ID_PRODUCT_ID not found", __func__);
-
- p_attr =
- SDP_FindAttributeInRec(p_rec, ATTR_ID_PRODUCT_VERSION);
- if (p_attr != nullptr)
- record->dip.version = p_attr->attr_value.v.u16;
- else
- APPL_TRACE_ERROR("%s() ATTR_ID_PRODUCT_VERSION not found", __func__);
-
- p_attr = SDP_FindAttributeInRec(p_rec, ATTR_ID_PRIMARY_RECORD);
- if (p_attr != nullptr)
- record->dip.primary_record = !(!p_attr->attr_value.v.u8);
- else
- APPL_TRACE_ERROR("%s() ATTR_ID_PRIMARY_RECORD not found", __func__);
-}
-
static void bta_create_raw_sdp_record(bluetooth_sdp_record* record,
tSDP_DISC_REC* p_rec) {
tSDP_DISC_ATTR* p_attr;
@@ -367,12 +330,12 @@ static void bta_create_raw_sdp_record(bluetooth_sdp_record* record,
}
/** Callback from btm after search is completed */
-static void bta_sdp_search_cback(tSDP_RESULT result, void* user_data) {
+static void bta_sdp_search_cback(uint16_t result, void* user_data) {
tBTA_SDP_STATUS status = BTA_SDP_FAILURE;
int count = 0;
APPL_TRACE_DEBUG("%s() - res: 0x%x", __func__, result);
- bta_sdp_cb.sdp_active = false;
+ bta_sdp_cb.sdp_active = BTA_SDP_ACTIVE_NONE;
if (bta_sdp_cb.p_dm_cback == NULL) return;
@@ -410,9 +373,6 @@ static void bta_sdp_search_cback(tSDP_RESULT result, void* user_data) {
} else if (uuid == UUID_SAP) {
APPL_TRACE_DEBUG("%s() - found SAP uuid", __func__);
bta_create_sap_sdp_record(&evt_data.records[count], p_rec);
- } else if (uuid == UUID_DIP) {
- APPL_TRACE_DEBUG("%s() - found DIP uuid", __func__);
- bta_create_dip_sdp_record(&evt_data.records[count], p_rec);
} else {
/* we do not have specific structure for this */
APPL_TRACE_DEBUG("%s() - profile not identified. using raw data",
@@ -447,10 +407,10 @@ static void bta_sdp_search_cback(tSDP_RESULT result, void* user_data) {
* Returns void
*
******************************************************************************/
-void bta_sdp_enable(tBTA_SDP_DM_CBACK* p_cback) {
+void bta_sdp_enable(tBTA_SDP_MSG* p_data) {
APPL_TRACE_DEBUG("%s in, sdp_active:%d", __func__, bta_sdp_cb.sdp_active);
tBTA_SDP_STATUS status = BTA_SDP_SUCCESS;
- bta_sdp_cb.p_dm_cback = p_cback;
+ bta_sdp_cb.p_dm_cback = p_data->enable.p_cback;
tBTA_SDP bta_sdp;
bta_sdp.status = status;
bta_sdp_cb.p_dm_cback(BTA_SDP_ENABLE_EVT, &bta_sdp, NULL);
@@ -465,19 +425,24 @@ void bta_sdp_enable(tBTA_SDP_DM_CBACK* p_cback) {
* Returns void
*
******************************************************************************/
-void bta_sdp_search(const RawAddress bd_addr, const bluetooth::Uuid uuid) {
+void bta_sdp_search(tBTA_SDP_MSG* p_data) {
+ if (p_data == NULL) {
+ APPL_TRACE_DEBUG("SDP control block handle is null");
+ return;
+ }
tBTA_SDP_STATUS status = BTA_SDP_FAILURE;
APPL_TRACE_DEBUG("%s in, sdp_active:%d", __func__, bta_sdp_cb.sdp_active);
- if (bta_sdp_cb.sdp_active) {
+ const Uuid& uuid = p_data->get_search.uuid;
+ if (bta_sdp_cb.sdp_active != BTA_SDP_ACTIVE_NONE) {
/* SDP is still in progress */
status = BTA_SDP_BUSY;
if (bta_sdp_cb.p_dm_cback) {
tBTA_SDP_SEARCH_COMP result;
memset(&result, 0, sizeof(result));
result.uuid = uuid;
- result.remote_addr = bd_addr;
+ result.remote_addr = p_data->get_search.bd_addr;
result.status = status;
tBTA_SDP bta_sdp;
bta_sdp.sdp_search_comp = result;
@@ -486,8 +451,8 @@ void bta_sdp_search(const RawAddress bd_addr, const bluetooth::Uuid uuid) {
return;
}
- bta_sdp_cb.sdp_active = true;
- bta_sdp_cb.remote_addr = bd_addr;
+ bta_sdp_cb.sdp_active = BTA_SDP_ACTIVE_YES;
+ bta_sdp_cb.remote_addr = p_data->get_search.bd_addr;
/* initialize the search for the uuid */
APPL_TRACE_DEBUG("%s init discovery with UUID: %s", __func__,
@@ -497,17 +462,17 @@ void bta_sdp_search(const RawAddress bd_addr, const bluetooth::Uuid uuid) {
Uuid* bta_sdp_search_uuid = (Uuid*)osi_malloc(sizeof(Uuid));
*bta_sdp_search_uuid = uuid;
- if (!SDP_ServiceSearchAttributeRequest2(bd_addr, p_bta_sdp_cfg->p_sdp_db,
- bta_sdp_search_cback,
- (void*)bta_sdp_search_uuid)) {
- bta_sdp_cb.sdp_active = false;
+ if (!SDP_ServiceSearchAttributeRequest2(
+ p_data->get_search.bd_addr, p_bta_sdp_cfg->p_sdp_db,
+ bta_sdp_search_cback, (void*)bta_sdp_search_uuid)) {
+ bta_sdp_cb.sdp_active = BTA_SDP_ACTIVE_NONE;
/* failed to start SDP. report the failure right away */
if (bta_sdp_cb.p_dm_cback) {
tBTA_SDP_SEARCH_COMP result;
memset(&result, 0, sizeof(result));
result.uuid = uuid;
- result.remote_addr = bd_addr;
+ result.remote_addr = p_data->get_search.bd_addr;
result.status = status;
tBTA_SDP bta_sdp;
bta_sdp.sdp_search_comp = result;
@@ -528,9 +493,11 @@ void bta_sdp_search(const RawAddress bd_addr, const bluetooth::Uuid uuid) {
* Returns void
*
******************************************************************************/
-void bta_sdp_create_record(void* user_data) {
+void bta_sdp_create_record(tBTA_SDP_MSG* p_data) {
+ APPL_TRACE_DEBUG("%s() event: %d", __func__, p_data->record.hdr.event);
if (bta_sdp_cb.p_dm_cback)
- bta_sdp_cb.p_dm_cback(BTA_SDP_CREATE_RECORD_USER_EVT, NULL, user_data);
+ bta_sdp_cb.p_dm_cback(BTA_SDP_CREATE_RECORD_USER_EVT, NULL,
+ p_data->record.user_data);
}
/*******************************************************************************
@@ -542,7 +509,9 @@ void bta_sdp_create_record(void* user_data) {
* Returns void
*
******************************************************************************/
-void bta_sdp_remove_record(void* user_data) {
+void bta_sdp_remove_record(tBTA_SDP_MSG* p_data) {
+ APPL_TRACE_DEBUG("%s() event: %d", __func__, p_data->record.hdr.event);
if (bta_sdp_cb.p_dm_cback)
- bta_sdp_cb.p_dm_cback(BTA_SDP_REMOVE_RECORD_USER_EVT, NULL, user_data);
+ bta_sdp_cb.p_dm_cback(BTA_SDP_REMOVE_RECORD_USER_EVT, NULL,
+ p_data->record.user_data);
}
diff --git a/bta/sdp/bta_sdp_api.cc b/bta/sdp/bta_sdp_api.cc
index c33471994..17e449cc9 100644
--- a/bta/sdp/bta_sdp_api.cc
+++ b/bta/sdp/bta_sdp_api.cc
@@ -22,18 +22,22 @@
*
******************************************************************************/
-#include <base/bind.h>
-#include <base/location.h>
+#include <string.h>
-#include "bt_target.h" // Must be first to define build configuration
-#include "bta/include/bta_sdp_api.h"
-#include "bta/sdp/bta_sdp_int.h"
-#include "stack/include/btu.h" // do_in_main_thread
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_sdp_api.h"
+#include "bta_sdp_int.h"
+#include "bta_sys.h"
+#include "port_api.h"
+#include "sdp_api.h"
/*****************************************************************************
* Constants
****************************************************************************/
+static const tBTA_SYS_REG bta_sdp_reg = {bta_sdp_sm_execute, NULL};
+
/*******************************************************************************
*
* Function BTA_SdpEnable
@@ -49,13 +53,25 @@
*
******************************************************************************/
tBTA_SDP_STATUS BTA_SdpEnable(tBTA_SDP_DM_CBACK* p_cback) {
- if (!p_cback) {
- return BTA_SDP_FAILURE;
- }
+ tBTA_SDP_STATUS status = BTA_SDP_FAILURE;
- memset(&bta_sdp_cb, 0, sizeof(tBTA_SDP_CB));
- do_in_main_thread(FROM_HERE, base::Bind(bta_sdp_enable, p_cback));
- return BTA_SDP_SUCCESS;
+ APPL_TRACE_API(__func__);
+ if (p_cback && !bta_sys_is_register(BTA_ID_SDP)) {
+ memset(&bta_sdp_cb, 0, sizeof(tBTA_SDP_CB));
+
+ /* register with BTA system manager */
+ bta_sys_register(BTA_ID_SDP, &bta_sdp_reg);
+
+ if (p_cback) {
+ tBTA_SDP_API_ENABLE* p_buf =
+ (tBTA_SDP_API_ENABLE*)osi_malloc(sizeof(tBTA_SDP_API_ENABLE));
+ p_buf->hdr.event = BTA_SDP_API_ENABLE_EVT;
+ p_buf->p_cback = p_cback;
+ bta_sys_sendmsg(p_buf);
+ status = BTA_SDP_SUCCESS;
+ }
+ }
+ return status;
}
/*******************************************************************************
@@ -73,7 +89,17 @@ tBTA_SDP_STATUS BTA_SdpEnable(tBTA_SDP_DM_CBACK* p_cback) {
******************************************************************************/
tBTA_SDP_STATUS BTA_SdpSearch(const RawAddress& bd_addr,
const bluetooth::Uuid& uuid) {
- do_in_main_thread(FROM_HERE, base::Bind(bta_sdp_search, bd_addr, uuid));
+ tBTA_SDP_API_SEARCH* p_msg =
+ (tBTA_SDP_API_SEARCH*)osi_malloc(sizeof(tBTA_SDP_API_SEARCH));
+
+ APPL_TRACE_API("%s", __func__);
+
+ p_msg->hdr.event = BTA_SDP_API_SEARCH_EVT;
+ p_msg->bd_addr = bd_addr;
+ p_msg->uuid = uuid;
+
+ bta_sys_sendmsg(p_msg);
+
return BTA_SDP_SUCCESS;
}
@@ -90,7 +116,16 @@ tBTA_SDP_STATUS BTA_SdpSearch(const RawAddress& bd_addr,
*
******************************************************************************/
tBTA_SDP_STATUS BTA_SdpCreateRecordByUser(void* user_data) {
- do_in_main_thread(FROM_HERE, base::Bind(bta_sdp_create_record, user_data));
+ tBTA_SDP_API_RECORD_USER* p_msg =
+ (tBTA_SDP_API_RECORD_USER*)osi_malloc(sizeof(tBTA_SDP_API_RECORD_USER));
+
+ APPL_TRACE_API("%s", __func__);
+
+ p_msg->hdr.event = BTA_SDP_API_CREATE_RECORD_USER_EVT;
+ p_msg->user_data = user_data;
+
+ bta_sys_sendmsg(p_msg);
+
return BTA_SDP_SUCCESS;
}
@@ -107,6 +142,15 @@ tBTA_SDP_STATUS BTA_SdpCreateRecordByUser(void* user_data) {
*
******************************************************************************/
tBTA_SDP_STATUS BTA_SdpRemoveRecordByUser(void* user_data) {
- do_in_main_thread(FROM_HERE, base::Bind(bta_sdp_remove_record, user_data));
+ tBTA_SDP_API_RECORD_USER* p_msg =
+ (tBTA_SDP_API_RECORD_USER*)osi_malloc(sizeof(tBTA_SDP_API_RECORD_USER));
+
+ APPL_TRACE_API("%s", __func__);
+
+ p_msg->hdr.event = BTA_SDP_API_REMOVE_RECORD_USER_EVT;
+ p_msg->user_data = user_data;
+
+ bta_sys_sendmsg(p_msg);
+
return BTA_SDP_SUCCESS;
}
diff --git a/bta/sdp/bta_sdp_cfg.cc b/bta/sdp/bta_sdp_cfg.cc
index 36e745d19..beec3b520 100644
--- a/bta/sdp/bta_sdp_cfg.cc
+++ b/bta/sdp/bta_sdp_cfg.cc
@@ -20,10 +20,9 @@
* This file contains compile-time configurable constants for SDP Search
******************************************************************************/
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_sdp_api.h"
-#include "stack/include/sdp_api.h"
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_sdp_api.h"
#ifndef BTA_SDP_DB_SIZE
#define BTA_SDP_DB_SIZE 4500
diff --git a/bta/sdp/bta_sdp_int.h b/bta/sdp/bta_sdp_int.h
index 03c888f99..b6b68faf2 100644
--- a/bta/sdp/bta_sdp_int.h
+++ b/bta/sdp/bta_sdp_int.h
@@ -27,17 +27,59 @@
#ifndef BTA_SDP_INT_H
#define BTA_SDP_INT_H
-#include "bta/include/bta_sdp_api.h"
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
+#include "bta_api.h"
+#include "bta_sdp_api.h"
+#include "bta_sys.h"
/*****************************************************************************
* Constants
****************************************************************************/
+enum {
+ /* these events are handled by the state machine */
+ BTA_SDP_API_ENABLE_EVT = BTA_SYS_EVT_START(BTA_ID_SDP),
+ BTA_SDP_API_SEARCH_EVT,
+ BTA_SDP_API_CREATE_RECORD_USER_EVT,
+ BTA_SDP_API_REMOVE_RECORD_USER_EVT,
+ BTA_SDP_MAX_INT_EVT
+};
+
+enum {
+ BTA_SDP_ACTIVE_NONE = 0,
+ BTA_SDP_ACTIVE_YES /* waiting for SDP result */
+};
+
+/* data type for BTA_SDP_API_ENABLE_EVT */
+typedef struct {
+ BT_HDR hdr;
+ tBTA_SDP_DM_CBACK* p_cback;
+} tBTA_SDP_API_ENABLE;
+
+/* data type for BTA_SDP_API_SEARCH_EVT */
+typedef struct {
+ BT_HDR hdr;
+ RawAddress bd_addr;
+ bluetooth::Uuid uuid;
+} tBTA_SDP_API_SEARCH;
+
+/* data type for BTA_SDP_API_SEARCH_EVT */
+typedef struct {
+ BT_HDR hdr;
+ void* user_data;
+} tBTA_SDP_API_RECORD_USER;
+
+/* union of all data types */
+typedef union {
+ /* GKI event buffer header */
+ BT_HDR hdr;
+ tBTA_SDP_API_ENABLE enable;
+ tBTA_SDP_API_SEARCH get_search;
+ tBTA_SDP_API_RECORD_USER record;
+} tBTA_SDP_MSG;
+
/* SDP control block */
typedef struct {
- bool sdp_active;
+ uint8_t sdp_active; /* see BTA_SDP_SDP_ACT_* */
RawAddress remote_addr;
tBTA_SDP_DM_CBACK* p_dm_cback;
} tBTA_SDP_CB;
@@ -48,10 +90,11 @@ extern tBTA_SDP_CB bta_sdp_cb;
/* config struct */
extern tBTA_SDP_CFG* p_bta_sdp_cfg;
-extern void bta_sdp_enable(tBTA_SDP_DM_CBACK* p_cback);
-extern void bta_sdp_search(const RawAddress bd_addr,
- const bluetooth::Uuid uuid);
-extern void bta_sdp_create_record(void* user_data);
-extern void bta_sdp_remove_record(void* user_data);
+extern bool bta_sdp_sm_execute(BT_HDR* p_msg);
+
+extern void bta_sdp_enable(tBTA_SDP_MSG* p_data);
+extern void bta_sdp_search(tBTA_SDP_MSG* p_data);
+extern void bta_sdp_create_record(tBTA_SDP_MSG* p_data);
+extern void bta_sdp_remove_record(tBTA_SDP_MSG* p_data);
#endif /* BTA_SDP_INT_H */
diff --git a/bta/sys/bta_sys.h b/bta/sys/bta_sys.h
index fa3c03aee..3ceefc112 100644
--- a/bta/sys/bta_sys.h
+++ b/bta/sys/bta_sys.h
@@ -24,14 +24,12 @@
#ifndef BTA_SYS_H
#define BTA_SYS_H
-#include <base/time/time.h>
-#include <cstdint>
-
-#include "bt_target.h" // Must be first to define build configuration
-
+#include "bt_common.h"
+#include "bt_target.h"
#include "osi/include/alarm.h"
-#include "stack/include/hci_error_code.h"
-#include "types/hci_role.h"
+
+#include <base/logging.h>
+#include <base/threading/thread.h>
/*****************************************************************************
* Constants and data types
@@ -41,18 +39,20 @@
typedef bool(tBTA_SYS_VS_EVT_HDLR)(uint16_t evt, void* p);
/* event handler function type */
-typedef bool(tBTA_SYS_EVT_HDLR)(BT_HDR_RIGID* p_msg);
-static_assert(
- sizeof(BT_HDR) == sizeof(BT_HDR_RIGID),
- "Rigid replacement should be same size struct with flexible member");
+typedef bool(tBTA_SYS_EVT_HDLR)(BT_HDR* p_msg);
/* disable function type */
typedef void(tBTA_SYS_DISABLE)(void);
-template <typename T, typename U>
-inline const T* Specialize(U* u) {
- return const_cast<const T*>(reinterpret_cast<T*>(u));
-}
+/* HW modules */
+enum {
+ BTA_SYS_HW_BLUETOOTH,
+ BTA_SYS_HW_RT,
+
+ BTA_SYS_MAX_HW_MODULES
+};
+
+typedef uint16_t tBTA_SYS_HW_MODULE;
#ifndef BTA_DM_NUM_JV_ID
#define BTA_DM_NUM_JV_ID 2
@@ -78,6 +78,7 @@ inline const T* Specialize(U* u) {
#define BTA_ID_ACC 16 /* Advanced Camera Client */
#define BTA_ID_SC 17 /* SIM Card Access server */
#define BTA_ID_AV 18 /* Advanced audio/video */
+#define BTA_ID_AVK 19 /* Audio/video sink */
#define BTA_ID_HD 20 /* HID Device */
#define BTA_ID_CG 21 /* Cordless Gateway */
#define BTA_ID_BP 22 /* Basic Printing Client */
@@ -94,69 +95,46 @@ inline const T* Specialize(U* u) {
#define BTA_ID_SDP 33 /* SDP Client */
#define BTA_ID_BLUETOOTH_MAX 34 /* last BT profile */
+/* GENERIC */
+#define BTA_ID_PRM 38
+#define BTA_ID_SYSTEM 39 /* platform-specific */
+#define BTA_ID_SWRAP 40 /* Insight script wrapper */
+#define BTA_ID_MIP 41 /* Multicase Individual Polling */
+#define BTA_ID_RT 42 /* Audio Routing module: This module is always on. */
+#define BTA_ID_CLOSURE 43 /* Generic C++ closure */
+
+/* JV */
+#define BTA_ID_JV1 44 /* JV1 */
+#define BTA_ID_JV2 45 /* JV2 */
+
#define BTA_ID_MAX (44 + BTA_DM_NUM_JV_ID)
typedef uint8_t tBTA_SYS_ID;
-inline std::string BtaIdSysText(tBTA_SYS_ID sys_id) {
- switch (sys_id) {
- case BTA_ID_DM_SEARCH: // 2
- return std::string("Scanner");
- case BTA_ID_AG: // 5
- return std::string("Audio gateway");
- case BTA_ID_PAN: // 14
- return std::string("PAN Personal area network");
- case BTA_ID_AV: // 18
- return std::string("Advanced audio/video");
- case BTA_ID_HD: // 20
- return std::string("HID Human interface device");
- case BTA_ID_HH: // 23
- return std::string("HID Human interface host");
- case BTA_ID_GATTC: // 31
- return std::string("GATT client");
- case BTA_ID_GATTS: // 32
- return std::string("GATT server");
- default:
- return std::string("Unknown");
- }
-}
-
-typedef enum : uint8_t {
- BTA_SYS_CONN_OPEN = 0x00,
- BTA_SYS_CONN_CLOSE = 0x01,
- BTA_SYS_APP_OPEN = 0x02,
- BTA_SYS_APP_CLOSE = 0x03,
- BTA_SYS_SCO_OPEN = 0x04,
- BTA_SYS_SCO_CLOSE = 0x05,
- BTA_SYS_CONN_IDLE = 0x06,
- BTA_SYS_CONN_BUSY = 0x07,
- BTA_SYS_ROLE_CHANGE = 0x14, /* role change */
-} tBTA_SYS_CONN_STATUS;
-
-inline std::string bta_sys_conn_status_text(tBTA_SYS_CONN_STATUS status) {
- switch (status) {
- case BTA_SYS_CONN_OPEN:
- return std::string("BTA_SYS_CONN_OPEN");
- case BTA_SYS_CONN_CLOSE:
- return std::string("BTA_SYS_CONN_CLOSE");
- case BTA_SYS_APP_OPEN:
- return std::string("BTA_SYS_APP_OPEN");
- case BTA_SYS_APP_CLOSE:
- return std::string("BTA_SYS_APP_CLOSE");
- case BTA_SYS_SCO_OPEN:
- return std::string("BTA_SYS_SCO_OPEN");
- case BTA_SYS_SCO_CLOSE:
- return std::string("BTA_SYS_SCO_CLOSE");
- case BTA_SYS_CONN_IDLE:
- return std::string("BTA_SYS_CONN_IDLE");
- case BTA_SYS_CONN_BUSY:
- return std::string("BTA_SYS_CONN_BUSY");
- case BTA_SYS_ROLE_CHANGE:
- return std::string("BTA_SYS_ROLE_CHANGE");
- default:
- return std::string("UNKNOWN");
- }
-}
+#define BTA_SYS_CONN_OPEN 0x00
+#define BTA_SYS_CONN_CLOSE 0x01
+#define BTA_SYS_APP_OPEN 0x02
+#define BTA_SYS_APP_CLOSE 0x03
+#define BTA_SYS_SCO_OPEN 0x04
+#define BTA_SYS_SCO_CLOSE 0x05
+#define BTA_SYS_CONN_IDLE 0x06
+#define BTA_SYS_CONN_BUSY 0x07
+
+/* for link policy */
+#define BTA_SYS_PLCY_SET 0x10 /* set the link policy to the given addr */
+#define BTA_SYS_PLCY_CLR 0x11 /* clear the link policy to the given addr */
+#define BTA_SYS_PLCY_DEF_SET 0x12 /* set the default link policy */
+#define BTA_SYS_PLCY_DEF_CLR 0x13 /* clear the default link policy */
+#define BTA_SYS_ROLE_CHANGE 0x14 /* role change */
+
+typedef uint8_t tBTA_SYS_CONN_STATUS;
+
+/* Bitmask of sys features */
+#define BTA_SYS_FEAT_PCM2 0x0001
+#define BTA_SYS_FEAT_PCM2_MASTER 0x0002
+
+/* tBTA_PREF_ROLES */
+typedef uint8_t tBTA_SYS_PREF_ROLES;
/* conn callback for role / low power manager*/
typedef void(tBTA_SYS_CONN_CBACK)(tBTA_SYS_CONN_STATUS status, uint8_t id,
@@ -166,15 +144,9 @@ typedef void(tBTA_SYS_CONN_CBACK)(tBTA_SYS_CONN_STATUS status, uint8_t id,
typedef void(tBTA_SYS_SSR_CFG_CBACK)(uint8_t id, uint8_t app_id,
uint16_t latency, uint16_t tout);
-typedef struct {
- bluetooth::Uuid custom_uuid;
- uint32_t handle;
-} tBTA_CUSTOM_UUID;
-
#if (BTA_EIR_CANNED_UUID_LIST != TRUE)
/* eir callback for adding/removeing UUID */
typedef void(tBTA_SYS_EIR_CBACK)(uint16_t uuid16, bool adding);
-typedef void(tBTA_SYS_CUST_EIR_CBACK)(const tBTA_CUSTOM_UUID &curr, bool adding);
#endif
/* registration structure */
@@ -183,6 +155,14 @@ typedef struct {
tBTA_SYS_DISABLE* disable;
} tBTA_SYS_REG;
+/* data type to send events to BTA SYS HW manager */
+typedef struct {
+ BT_HDR hdr;
+ tBTA_SYS_HW_MODULE hw_module;
+} tBTA_SYS_HW_MSG;
+
+typedef void (*tBTA_SYS_REGISTER)(uint8_t id, const tBTA_SYS_REG* p_reg);
+
/*****************************************************************************
* Global data
****************************************************************************/
@@ -193,28 +173,68 @@ extern uint8_t appl_trace_level;
/*****************************************************************************
* Macros
****************************************************************************/
+
/* Calculate start of event enumeration; id is top 8 bits of event */
#define BTA_SYS_EVT_START(id) ((id) << 8)
/*****************************************************************************
+ * events for BTA SYS HW manager
+ ****************************************************************************/
+
+/* events sent to SYS HW manager - must be kept synchronized with tables in
+ * bta_sys_main.cc */
+enum {
+ /* device manager local device API events */
+ BTA_SYS_API_ENABLE_EVT = BTA_SYS_EVT_START(BTA_ID_SYS),
+ BTA_SYS_EVT_ENABLED_EVT,
+ BTA_SYS_EVT_STACK_ENABLED_EVT,
+ BTA_SYS_API_DISABLE_EVT,
+ BTA_SYS_EVT_DISABLED_EVT,
+ BTA_SYS_ERROR_EVT,
+
+ BTA_SYS_MAX_EVT
+};
+
+/* SYS HW status events - returned by SYS HW manager to other modules. */
+enum {
+ BTA_SYS_HW_OFF_EVT,
+ BTA_SYS_HW_ON_EVT,
+ BTA_SYS_HW_STARTING_EVT,
+ BTA_SYS_HW_STOPPING_EVT,
+ BTA_SYS_HW_ERROR_EVT
+
+};
+typedef uint8_t tBTA_SYS_HW_EVT;
+
+/* HW enable callback type */
+typedef void(tBTA_SYS_HW_CBACK)(tBTA_SYS_HW_EVT status);
+
+/*****************************************************************************
* Function declarations
****************************************************************************/
-void bta_set_forward_hw_failures(bool value);
-void BTA_sys_signal_hw_error();
extern void bta_sys_init(void);
+extern void bta_sys_free(void);
+extern void bta_sys_event(BT_HDR* p_msg);
+extern void bta_sys_set_trace_level(uint8_t level);
extern void bta_sys_register(uint8_t id, const tBTA_SYS_REG* p_reg);
extern void bta_sys_deregister(uint8_t id);
extern bool bta_sys_is_register(uint8_t id);
+extern uint16_t bta_sys_get_sys_features(void);
extern void bta_sys_sendmsg(void* p_msg);
extern void bta_sys_sendmsg_delayed(void* p_msg, const base::TimeDelta& delay);
extern void bta_sys_start_timer(alarm_t* alarm, uint64_t interval_ms,
uint16_t event, uint16_t layer_specific);
-extern void bta_sys_disable();
+extern void bta_sys_disable(tBTA_SYS_HW_MODULE module);
+
+extern void bta_sys_hw_register(tBTA_SYS_HW_MODULE module,
+ tBTA_SYS_HW_CBACK* cback);
+extern void bta_sys_hw_unregister(tBTA_SYS_HW_MODULE module);
extern void bta_sys_rm_register(tBTA_SYS_CONN_CBACK* p_cback);
extern void bta_sys_pm_register(tBTA_SYS_CONN_CBACK* p_cback);
+extern void bta_sys_policy_register(tBTA_SYS_CONN_CBACK* p_cback);
extern void bta_sys_sco_register(tBTA_SYS_CONN_CBACK* p_cback);
extern void bta_sys_conn_open(uint8_t id, uint8_t app_id,
@@ -238,13 +258,15 @@ extern void bta_sys_idle(uint8_t id, uint8_t app_id,
extern void bta_sys_busy(uint8_t id, uint8_t app_id,
const RawAddress& peer_addr);
+#if (BTM_SSR_INCLUDED == TRUE)
extern void bta_sys_ssr_cfg_register(tBTA_SYS_SSR_CFG_CBACK* p_cback);
extern void bta_sys_chg_ssr_config(uint8_t id, uint8_t app_id,
uint16_t max_latency, uint16_t min_tout);
+#endif
extern void bta_sys_role_chg_register(tBTA_SYS_CONN_CBACK* p_cback);
extern void bta_sys_notify_role_chg(const RawAddress& peer_addr,
- tHCI_ROLE new_role, tHCI_STATUS hci_status);
+ uint8_t new_role, uint8_t hci_status);
extern void bta_sys_collision_register(uint8_t bta_id,
tBTA_SYS_CONN_CBACK* p_cback);
extern void bta_sys_notify_collision(const RawAddress& peer_addr);
@@ -253,16 +275,17 @@ extern void bta_sys_notify_collision(const RawAddress& peer_addr);
extern void bta_sys_eir_register(tBTA_SYS_EIR_CBACK* p_cback);
extern void bta_sys_add_uuid(uint16_t uuid16);
extern void bta_sys_remove_uuid(uint16_t uuid16);
-extern void bta_sys_cust_eir_register(tBTA_SYS_CUST_EIR_CBACK* p_cback);
-extern void bta_sys_add_cust_uuid(const tBTA_CUSTOM_UUID& curr);
-extern void bta_sys_remove_cust_uuid(const tBTA_CUSTOM_UUID& curr);
#else
#define bta_sys_eir_register(ut)
#define bta_sys_add_uuid(ut)
#define bta_sys_remove_uuid(ut)
-#define bta_sys_cust_eir_register(ut)
-#define bta_sys_add_cust_uuid(ut)
-#define bta_sys_remove_cust_uuid(ut)
#endif
+extern void bta_sys_set_policy(uint8_t id, uint8_t policy,
+ const RawAddress& peer_addr);
+extern void bta_sys_clear_policy(uint8_t id, uint8_t policy,
+ const RawAddress& peer_addr);
+extern void bta_sys_set_default_policy(uint8_t id, uint8_t policy);
+extern void bta_sys_clear_default_policy(uint8_t id, uint8_t policy);
+
#endif /* BTA_SYS_H */
diff --git a/bta/sys/bta_sys_conn.cc b/bta/sys/bta_sys_conn.cc
index 4496f8662..ef9649b79 100644
--- a/bta/sys/bta_sys_conn.cc
+++ b/bta/sys/bta_sys_conn.cc
@@ -22,18 +22,14 @@
*
******************************************************************************/
-#include <cstdint>
+#include <stddef.h>
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/sys/bta_sys.h"
-#include "bta/sys/bta_sys_int.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/include/btm_api.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_sys.h"
+#include "bta_sys_int.h"
+#include "osi/include/osi.h"
+#include "utl.h"
/*******************************************************************************
*
@@ -51,6 +47,20 @@ void bta_sys_rm_register(tBTA_SYS_CONN_CBACK* p_cback) {
/*******************************************************************************
*
+ * Function bta_sys_policy_register
+ *
+ * Description Called by BTA DM to register link policy change callbacks
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_sys_policy_register(tBTA_SYS_CONN_CBACK* p_cback) {
+ bta_sys_cb.p_policy_cb = p_cback;
+}
+
+/*******************************************************************************
+ *
* Function bta_sys_role_chg_register
*
* Description Called by BTA AV to register role change callbacks
@@ -72,10 +82,11 @@ void bta_sys_role_chg_register(tBTA_SYS_CONN_CBACK* p_cback) {
* Returns void
*
******************************************************************************/
+#if (BTM_SSR_INCLUDED == TRUE)
void bta_sys_ssr_cfg_register(tBTA_SYS_SSR_CFG_CBACK* p_cback) {
bta_sys_cb.p_ssr_cb = p_cback;
}
-
+#endif
/*******************************************************************************
*
* Function bta_sys_role_chg_register
@@ -86,11 +97,10 @@ void bta_sys_ssr_cfg_register(tBTA_SYS_SSR_CFG_CBACK* p_cback) {
* Returns void
*
******************************************************************************/
-void bta_sys_notify_role_chg(const RawAddress& peer_addr, tHCI_ROLE new_role,
- tHCI_STATUS hci_status) {
- LOG_DEBUG("Role changed peer:%s new_role:%s hci_status:%s",
- PRIVATE_ADDRESS(peer_addr), RoleText(new_role).c_str(),
- hci_error_code_text(hci_status).c_str());
+void bta_sys_notify_role_chg(const RawAddress& peer_addr, uint8_t new_role,
+ uint8_t hci_status) {
+ APPL_TRACE_DEBUG("%s: peer %s new_role:%d hci_status:0x%x", __func__,
+ peer_addr.ToString().c_str(), new_role, hci_status);
if (bta_sys_cb.p_role_cb) {
bta_sys_cb.p_role_cb(BTA_SYS_ROLE_CHANGE, new_role, hci_status, peer_addr);
}
@@ -135,8 +145,7 @@ void bta_sys_notify_collision(const RawAddress& peer_addr) {
for (index = 0; index < MAX_COLLISION_REG; index++) {
if ((bta_sys_cb.colli_reg.id[index] != 0) &&
(bta_sys_cb.colli_reg.p_coll_cback[index] != NULL)) {
- bta_sys_cb.colli_reg.p_coll_cback[index](BTA_SYS_CONN_OPEN, BTA_ID_SYS, 0,
- peer_addr);
+ bta_sys_cb.colli_reg.p_coll_cback[index](0, BTA_ID_SYS, 0, peer_addr);
}
}
}
@@ -339,12 +348,87 @@ void bta_sys_sco_unuse(uint8_t id, uint8_t app_id,
* Returns void
*
******************************************************************************/
+#if (BTM_SSR_INCLUDED == TRUE)
void bta_sys_chg_ssr_config(uint8_t id, uint8_t app_id, uint16_t max_latency,
uint16_t min_tout) {
if (bta_sys_cb.p_ssr_cb) {
bta_sys_cb.p_ssr_cb(id, app_id, max_latency, min_tout);
}
}
+#endif
+/*******************************************************************************
+ *
+ * Function bta_sys_set_policy
+ *
+ * Description Called by BTA subsystems to indicate that the given link
+ * policy to peer device should be set
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_sys_set_policy(uint8_t id, uint8_t policy,
+ const RawAddress& peer_addr) {
+ APPL_TRACE_DEBUG("%s: peer %s id:%d policy:0x%x", __func__,
+ peer_addr.ToString().c_str(), id, policy);
+ if (bta_sys_cb.p_policy_cb) {
+ bta_sys_cb.p_policy_cb(BTA_SYS_PLCY_SET, id, policy, peer_addr);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function bta_sys_clear_policy
+ *
+ * Description Called by BTA subsystems to indicate that the given link
+ * policy to peer device should be clear
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_sys_clear_policy(uint8_t id, uint8_t policy,
+ const RawAddress& peer_addr) {
+ APPL_TRACE_DEBUG("%s: peer %s id:%d policy:0x%x", __func__,
+ peer_addr.ToString().c_str(), id, policy);
+ if (bta_sys_cb.p_policy_cb) {
+ bta_sys_cb.p_policy_cb(BTA_SYS_PLCY_CLR, id, policy, peer_addr);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function bta_sys_set_default_policy
+ *
+ * Description Called by BTA subsystems to indicate that the given default
+ * link policy should be set
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_sys_set_default_policy(uint8_t id, uint8_t policy) {
+ APPL_TRACE_DEBUG("%s: id:%d policy:0x%x", __func__, id, policy);
+ if (bta_sys_cb.p_policy_cb) {
+ bta_sys_cb.p_policy_cb(BTA_SYS_PLCY_DEF_SET, id, policy,
+ RawAddress::kEmpty);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function bta_sys_clear_default_policy
+ *
+ * Description Called by BTA subsystems to indicate that the given default
+ * link policy should be clear
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_sys_clear_default_policy(uint8_t id, uint8_t policy) {
+ APPL_TRACE_DEBUG("%s: id:%d policy:0x%x", __func__, id, policy);
+ if (bta_sys_cb.p_policy_cb) {
+ bta_sys_cb.p_policy_cb(BTA_SYS_PLCY_DEF_CLR, id, policy,
+ RawAddress::kEmpty);
+ }
+}
/*******************************************************************************
*
@@ -403,20 +487,6 @@ void bta_sys_eir_register(tBTA_SYS_EIR_CBACK* p_cback) {
/*******************************************************************************
*
- * Function bta_sys_cust_eir_register
- *
- * Description Called by BTA DM to register EIR utility function that can
- * be used by the other BTA modules to add/remove custom UUID.
- *
- * Returns void
- *
- ******************************************************************************/
-void bta_sys_cust_eir_register(tBTA_SYS_CUST_EIR_CBACK* p_cback) {
- bta_sys_cb.cust_eir_cb = p_cback;
-}
-
-/*******************************************************************************
- *
* Function bta_sys_add_uuid
*
* Description Called by BTA subsystems to indicate to DM that new service
@@ -446,36 +516,4 @@ void bta_sys_remove_uuid(uint16_t uuid16) {
bta_sys_cb.eir_cb(uuid16, false);
}
}
-
-/*******************************************************************************
- *
- * Function bta_sys_add_cust_uuid
- *
- * Description Called by BTA subsystems to indicate to DM that the custom service
- * class UUID is removed.
- *
- * Returns void
- *
- ******************************************************************************/
-void bta_sys_add_cust_uuid(const tBTA_CUSTOM_UUID& curr) {
- if (bta_sys_cb.cust_eir_cb) {
- bta_sys_cb.cust_eir_cb(curr, true);
- }
-}
-
-/*******************************************************************************
- *
- * Function bta_sys_remove_cust_uuid
- *
- * Description Called by BTA subsystems to indicate to DM that the service
- * class UUID is removed.
- *
- * Returns void
- *
- ******************************************************************************/
-void bta_sys_remove_cust_uuid(const tBTA_CUSTOM_UUID& curr) {
- if (bta_sys_cb.cust_eir_cb) {
- bta_sys_cb.cust_eir_cb(curr, false);
- }
-}
#endif
diff --git a/bta/sys/bta_sys_int.h b/bta/sys/bta_sys_int.h
index 7487f4d5d..fcf219950 100644
--- a/bta/sys/bta_sys_int.h
+++ b/bta/sys/bta_sys_int.h
@@ -24,9 +24,6 @@
#ifndef BTA_SYS_INT_H
#define BTA_SYS_INT_H
-#include <cstdint>
-#include "bta/sys/bta_sys.h"
-
/*****************************************************************************
* Constants and data types
****************************************************************************/
@@ -35,6 +32,15 @@
* state table
****************************************************************************/
+/* SYS HW state */
+enum {
+ BTA_SYS_HW_OFF,
+ BTA_SYS_HW_STARTING,
+ BTA_SYS_HW_ON,
+ BTA_SYS_HW_STOPPING
+};
+typedef uint8_t tBTA_SYS_HW_STATE;
+
/* Collision callback */
#define MAX_COLLISION_REG 5
@@ -47,21 +53,28 @@ typedef struct {
typedef struct {
tBTA_SYS_REG* reg[BTA_ID_MAX]; /* registration structures */
bool is_reg[BTA_ID_MAX]; /* registration structures */
- bool forward_hw_failures;
+ tBTA_SYS_HW_STATE state;
+ tBTA_SYS_HW_CBACK* sys_hw_cback[BTA_SYS_MAX_HW_MODULES]; /* enable callback
+ for each HW
+ modules */
+ uint32_t sys_hw_module_active; /* bitmask of all active modules */
uint16_t sys_features; /* Bitmask of sys features */
tBTA_SYS_CONN_CBACK* prm_cb; /* role management callback registered by DM */
tBTA_SYS_CONN_CBACK*
ppm_cb; /* low power management callback registered by DM */
tBTA_SYS_CONN_CBACK*
+ p_policy_cb; /* link policy change callback registered by DM */
+ tBTA_SYS_CONN_CBACK*
p_sco_cb; /* SCO connection change callback registered by AV */
tBTA_SYS_CONN_CBACK* p_role_cb; /* role change callback registered by AV */
tBTA_SYS_COLLISION colli_reg; /* collision handling module */
#if (BTA_EIR_CANNED_UUID_LIST != TRUE)
tBTA_SYS_EIR_CBACK* eir_cb; /* add/remove UUID into EIR */
- tBTA_SYS_CUST_EIR_CBACK* cust_eir_cb; /* add/remove customer UUID into EIR */
#endif
+#if (BTM_SSR_INCLUDED == TRUE)
tBTA_SYS_SSR_CFG_CBACK* p_ssr_cb;
+#endif
/* VS event handler */
tBTA_SYS_VS_EVT_HDLR* p_vs_evt_hdlr;
@@ -74,4 +87,15 @@ typedef struct {
/* system manager control block */
extern tBTA_SYS_CB bta_sys_cb;
+/* functions used for BTA SYS HW state machine */
+void bta_sys_hw_btm_cback(tBTM_DEV_STATUS status);
+void bta_sys_hw_error(tBTA_SYS_HW_MSG* p_sys_hw_msg);
+void bta_sys_hw_api_enable(tBTA_SYS_HW_MSG* p_sys_hw_msg);
+void bta_sys_hw_api_disable(tBTA_SYS_HW_MSG* p_sys_hw_msg);
+void bta_sys_hw_evt_enabled(tBTA_SYS_HW_MSG* p_sys_hw_msg);
+void bta_sys_hw_evt_disabled(tBTA_SYS_HW_MSG* p_sys_hw_msg);
+void bta_sys_hw_evt_stack_enabled(tBTA_SYS_HW_MSG* p_sys_hw_msg);
+
+bool bta_sys_sm_execute(BT_HDR* p_msg);
+
#endif /* BTA_SYS_INT_H */
diff --git a/bta/sys/bta_sys_main.cc b/bta/sys/bta_sys_main.cc
index 944860661..e81320d72 100644
--- a/bta/sys/bta_sys_main.cc
+++ b/bta/sys/bta_sys_main.cc
@@ -25,29 +25,142 @@
#define LOG_TAG "bt_bta_sys_main"
#include <base/bind.h>
-#include <cstring>
+#include <base/logging.h>
+#include <string.h>
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/sys/bta_sys.h"
-#include "bta/sys/bta_sys_int.h"
-#include "include/hardware/bluetooth.h"
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_sys.h"
+#include "bta_sys_int.h"
+#include "btm_api.h"
+#include "btu.h"
#include "osi/include/alarm.h"
-#include "osi/include/allocator.h"
+#include "osi/include/fixed_queue.h"
#include "osi/include/log.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btu.h" // do_in_main_thread
+#include "osi/include/osi.h"
+#include "utl.h"
-void BTIF_dm_on_hw_error();
+#if (defined BTA_AR_INCLUDED) && (BTA_AR_INCLUDED == TRUE)
+#include "bta_ar_api.h"
+#endif
/* system manager control block definition */
tBTA_SYS_CB bta_sys_cb;
/* trace level */
/* TODO Hard-coded trace levels - Needs to be configurable */
-uint8_t appl_trace_level = APPL_INITIAL_TRACE_LEVEL;
+uint8_t appl_trace_level = BT_TRACE_LEVEL_WARNING; // APPL_INITIAL_TRACE_LEVEL;
uint8_t btif_trace_level = BT_TRACE_LEVEL_WARNING;
+static const tBTA_SYS_REG bta_sys_hw_reg = {bta_sys_sm_execute, NULL};
+
+/* type for action functions */
+typedef void (*tBTA_SYS_ACTION)(tBTA_SYS_HW_MSG* p_data);
+
+/* action function list */
+const tBTA_SYS_ACTION bta_sys_action[] = {
+ /* device manager local device API events - cf bta_sys.h for events */
+ bta_sys_hw_api_enable, /* 0 BTA_SYS_HW_API_ENABLE_EVT */
+ bta_sys_hw_evt_enabled, /* 1 BTA_SYS_HW_EVT_ENABLED_EVT */
+ bta_sys_hw_evt_stack_enabled, /* 2 BTA_SYS_HW_EVT_STACK_ENABLED_EVT */
+ bta_sys_hw_api_disable, /* 3 BTA_SYS_HW_API_DISABLE_EVT */
+ bta_sys_hw_evt_disabled, /* 4 BTA_SYS_HW_EVT_DISABLED_EVT */
+ bta_sys_hw_error /* 5 BTA_SYS_HW_ERROR_EVT */
+};
+
+/* state machine action enumeration list */
+enum {
+ /* device manager local device API events */
+ BTA_SYS_HW_API_ENABLE,
+ BTA_SYS_HW_EVT_ENABLED,
+ BTA_SYS_HW_EVT_STACK_ENABLED,
+ BTA_SYS_HW_API_DISABLE,
+ BTA_SYS_HW_EVT_DISABLED,
+ BTA_SYS_HW_ERROR
+};
+
+#define BTA_SYS_NUM_ACTIONS (BTA_SYS_MAX_EVT & 0x00ff)
+#define BTA_SYS_IGNORE BTA_SYS_NUM_ACTIONS
+
+/* state table information */
+#define BTA_SYS_ACTIONS 2 /* number of actions */
+#define BTA_SYS_NEXT_STATE 2 /* position of next state */
+#define BTA_SYS_NUM_COLS 3 /* number of columns in state tables */
+
+/* state table for OFF state */
+const uint8_t bta_sys_hw_off[][BTA_SYS_NUM_COLS] = {
+ /* Event Action 1 Action 2
+ Next State */
+ /* API_ENABLE */ {BTA_SYS_HW_API_ENABLE, BTA_SYS_IGNORE,
+ BTA_SYS_HW_STARTING},
+ /* EVT_ENABLED */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_STARTING},
+ /* STACK_ENABLED */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_ON},
+ /* API_DISABLE */ {BTA_SYS_HW_EVT_DISABLED, BTA_SYS_IGNORE,
+ BTA_SYS_HW_OFF},
+ /* EVT_DISABLED */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_OFF},
+ /* EVT_ERROR */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_OFF}};
+
+const uint8_t bta_sys_hw_starting[][BTA_SYS_NUM_COLS] = {
+ /* Event Action 1 Action 2
+ Next State */
+ /* API_ENABLE */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE,
+ BTA_SYS_HW_STARTING}, /* wait for completion event */
+ /* EVT_ENABLED */ {BTA_SYS_HW_EVT_ENABLED, BTA_SYS_IGNORE,
+ BTA_SYS_HW_STARTING},
+ /* STACK_ENABLED */ {BTA_SYS_HW_EVT_STACK_ENABLED, BTA_SYS_IGNORE,
+ BTA_SYS_HW_ON},
+ /* API_DISABLE */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE,
+ BTA_SYS_HW_STOPPING}, /* successive disable/enable:
+ change state wait for
+ completion to disable */
+ /* EVT_DISABLED */ {BTA_SYS_HW_EVT_DISABLED, BTA_SYS_HW_API_ENABLE,
+ BTA_SYS_HW_STARTING}, /* successive enable/disable:
+ notify, then restart HW */
+ /* EVT_ERROR */ {BTA_SYS_HW_ERROR, BTA_SYS_IGNORE, BTA_SYS_HW_ON}};
+
+const uint8_t bta_sys_hw_on[][BTA_SYS_NUM_COLS] = {
+ /* Event Action 1 Action 2
+ Next State */
+ /* API_ENABLE */ {BTA_SYS_HW_API_ENABLE, BTA_SYS_IGNORE, BTA_SYS_HW_ON},
+ /* EVT_ENABLED */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_ON},
+ /* STACK_ENABLED */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE, BTA_SYS_HW_ON},
+ /* API_DISABLE */
+ {BTA_SYS_HW_API_DISABLE, BTA_SYS_IGNORE,
+ BTA_SYS_HW_ON}, /* don't change the state here, as some
+ other modules might be active */
+ /* EVT_DISABLED */ {BTA_SYS_HW_ERROR, BTA_SYS_IGNORE, BTA_SYS_HW_ON},
+ /* EVT_ERROR */ {BTA_SYS_HW_ERROR, BTA_SYS_IGNORE, BTA_SYS_HW_ON}};
+
+const uint8_t bta_sys_hw_stopping[][BTA_SYS_NUM_COLS] = {
+ /* Event Action 1 Action 2
+ Next State */
+ /* API_ENABLE */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE,
+ BTA_SYS_HW_STARTING}, /* change state, and wait for
+ completion event to enable */
+ /* EVT_ENABLED */ {BTA_SYS_HW_EVT_ENABLED, BTA_SYS_IGNORE,
+ BTA_SYS_HW_STOPPING}, /* successive enable/disable:
+ finish the enable before
+ disabling */
+ /* STACK_ENABLED */ {BTA_SYS_HW_EVT_STACK_ENABLED, BTA_SYS_HW_API_DISABLE,
+ BTA_SYS_HW_STOPPING}, /* successive enable/disable:
+ notify, then stop */
+ /* API_DISABLE */ {BTA_SYS_IGNORE, BTA_SYS_IGNORE,
+ BTA_SYS_HW_STOPPING}, /* wait for completion event */
+ /* EVT_DISABLED */ {BTA_SYS_HW_EVT_DISABLED, BTA_SYS_IGNORE,
+ BTA_SYS_HW_OFF},
+ /* EVT_ERROR */ {BTA_SYS_HW_API_DISABLE, BTA_SYS_IGNORE,
+ BTA_SYS_HW_STOPPING}};
+
+typedef const uint8_t (*tBTA_SYS_ST_TBL)[BTA_SYS_NUM_COLS];
+
+/* state table */
+const tBTA_SYS_ST_TBL bta_sys_st_tbl[] = {
+ bta_sys_hw_off, /* BTA_SYS_HW_OFF */
+ bta_sys_hw_starting, /* BTA_SYS_HW_STARTING */
+ bta_sys_hw_on, /* BTA_SYS_HW_ON */
+ bta_sys_hw_stopping /* BTA_SYS_HW_STOPPING */
+};
+
/*******************************************************************************
*
* Function bta_sys_init
@@ -60,15 +173,266 @@ uint8_t btif_trace_level = BT_TRACE_LEVEL_WARNING;
******************************************************************************/
void bta_sys_init(void) {
memset(&bta_sys_cb, 0, sizeof(tBTA_SYS_CB));
+
+ appl_trace_level = APPL_INITIAL_TRACE_LEVEL;
+
+ /* register BTA SYS message handler */
+ bta_sys_register(BTA_ID_SYS, &bta_sys_hw_reg);
+
+ /* register for BTM notifications */
+ BTM_RegisterForDeviceStatusNotif(&bta_sys_hw_btm_cback);
+
+#if (defined BTA_AR_INCLUDED) && (BTA_AR_INCLUDED == TRUE)
+ bta_ar_init();
+#endif
+}
+
+void bta_sys_free(void) {
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_sm_execute
+ *
+ * Description State machine event handling function for DM
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+bool bta_sys_sm_execute(BT_HDR* p_msg) {
+ bool freebuf = true;
+ tBTA_SYS_ST_TBL state_table;
+ uint8_t action;
+ int i;
+
+ APPL_TRACE_EVENT("bta_sys_sm_execute state:%d, event:0x%x", bta_sys_cb.state,
+ p_msg->event);
+
+ /* look up the state table for the current state */
+ state_table = bta_sys_st_tbl[bta_sys_cb.state];
+ /* update state */
+ bta_sys_cb.state = state_table[p_msg->event & 0x00ff][BTA_SYS_NEXT_STATE];
+
+ /* execute action functions */
+ for (i = 0; i < BTA_SYS_ACTIONS; i++) {
+ action = state_table[p_msg->event & 0x00ff][i];
+ if (action != BTA_SYS_IGNORE) {
+ (*bta_sys_action[action])((tBTA_SYS_HW_MSG*)p_msg);
+ } else {
+ break;
+ }
+ }
+ return freebuf;
+}
+
+void bta_sys_hw_register(tBTA_SYS_HW_MODULE module, tBTA_SYS_HW_CBACK* cback) {
+ bta_sys_cb.sys_hw_cback[module] = cback;
+}
+
+void bta_sys_hw_unregister(tBTA_SYS_HW_MODULE module) {
+ bta_sys_cb.sys_hw_cback[module] = NULL;
}
-void bta_set_forward_hw_failures(bool value) {
- bta_sys_cb.forward_hw_failures = value;
+/*******************************************************************************
+ *
+ * Function bta_sys_hw_btm_cback
+ *
+ * Description This function is registered by BTA SYS to BTM in order to get
+ * status notifications
+ *
+ *
+ * Returns
+ *
+ ******************************************************************************/
+void bta_sys_hw_btm_cback(tBTM_DEV_STATUS status) {
+ tBTA_SYS_HW_MSG* sys_event =
+ (tBTA_SYS_HW_MSG*)osi_malloc(sizeof(tBTA_SYS_HW_MSG));
+
+ APPL_TRACE_DEBUG("%s was called with parameter: %i", __func__, status);
+
+ /* send a message to BTA SYS */
+ if (status == BTM_DEV_STATUS_UP) {
+ sys_event->hdr.event = BTA_SYS_EVT_STACK_ENABLED_EVT;
+ } else if (status == BTM_DEV_STATUS_DOWN) {
+ sys_event->hdr.event = BTA_SYS_ERROR_EVT;
+ } else {
+ /* BTM_DEV_STATUS_CMD_TOUT is ignored for now. */
+ osi_free_and_reset((void**)&sys_event);
+ }
+
+ if (sys_event) bta_sys_sendmsg(sys_event);
}
-void BTA_sys_signal_hw_error() {
- if (bta_sys_cb.forward_hw_failures) {
- BTIF_dm_on_hw_error();
+/*******************************************************************************
+ *
+ * Function bta_sys_hw_error
+ *
+ * Description In case the HW device stops answering... Try to turn it off,
+ * then re-enable all
+ * previously active SW modules.
+ *
+ * Returns success or failure
+ *
+ ******************************************************************************/
+void bta_sys_hw_error(UNUSED_ATTR tBTA_SYS_HW_MSG* p_sys_hw_msg) {
+ uint8_t module_index;
+
+ APPL_TRACE_DEBUG("%s", __func__);
+
+ for (module_index = 0; module_index < BTA_SYS_MAX_HW_MODULES;
+ module_index++) {
+ if (bta_sys_cb.sys_hw_module_active & ((uint32_t)1 << module_index)) {
+ switch (module_index) {
+ case BTA_SYS_HW_BLUETOOTH:
+ /* Send BTA_SYS_HW_ERROR_EVT to DM */
+ if (bta_sys_cb.sys_hw_cback[module_index] != NULL)
+ bta_sys_cb.sys_hw_cback[module_index](BTA_SYS_HW_ERROR_EVT);
+ break;
+ default:
+ /* not yet supported */
+ break;
+ }
+ }
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function bta_sys_hw_enable
+ *
+ * Description this function is called after API enable and HW has been
+ * turned on
+ *
+ *
+ * Returns success or failure
+ *
+ ******************************************************************************/
+
+void bta_sys_hw_api_enable(tBTA_SYS_HW_MSG* p_sys_hw_msg) {
+ if ((!bta_sys_cb.sys_hw_module_active) &&
+ (bta_sys_cb.state != BTA_SYS_HW_ON)) {
+ /* register which HW module was turned on */
+ bta_sys_cb.sys_hw_module_active |= ((uint32_t)1 << p_sys_hw_msg->hw_module);
+
+ tBTA_SYS_HW_MSG* p_msg =
+ (tBTA_SYS_HW_MSG*)osi_malloc(sizeof(tBTA_SYS_HW_MSG));
+ p_msg->hdr.event = BTA_SYS_EVT_ENABLED_EVT;
+ p_msg->hw_module = p_sys_hw_msg->hw_module;
+
+ bta_sys_sendmsg(p_msg);
+ } else {
+ /* register which HW module was turned on */
+ bta_sys_cb.sys_hw_module_active |= ((uint32_t)1 << p_sys_hw_msg->hw_module);
+
+ /* HW already in use, so directly notify the caller */
+ if (bta_sys_cb.sys_hw_cback[p_sys_hw_msg->hw_module] != NULL)
+ bta_sys_cb.sys_hw_cback[p_sys_hw_msg->hw_module](BTA_SYS_HW_ON_EVT);
+ }
+
+ APPL_TRACE_EVENT("bta_sys_hw_api_enable for %d, active modules 0x%04X",
+ p_sys_hw_msg->hw_module, bta_sys_cb.sys_hw_module_active);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_sys_hw_disable
+ *
+ * Description if no other module is using the HW, this function will call
+ * (if defined) a user-macro to turn off the HW
+ *
+ *
+ * Returns success or failure
+ *
+ ******************************************************************************/
+void bta_sys_hw_api_disable(tBTA_SYS_HW_MSG* p_sys_hw_msg) {
+ APPL_TRACE_DEBUG("bta_sys_hw_api_disable for %d, active modules: 0x%04X",
+ p_sys_hw_msg->hw_module, bta_sys_cb.sys_hw_module_active);
+
+ /* make sure the related SW blocks were stopped */
+ bta_sys_disable(p_sys_hw_msg->hw_module);
+
+ /* register which module we turn off */
+ bta_sys_cb.sys_hw_module_active &= ~((uint32_t)1 << p_sys_hw_msg->hw_module);
+
+ /* if there are still some SW modules using the HW, just provide an answer to
+ * the calling */
+ if (bta_sys_cb.sys_hw_module_active != 0) {
+ /* if there are still some SW modules using the HW, directly notify the
+ * caller */
+ if (bta_sys_cb.sys_hw_cback[p_sys_hw_msg->hw_module] != NULL)
+ bta_sys_cb.sys_hw_cback[p_sys_hw_msg->hw_module](BTA_SYS_HW_OFF_EVT);
+ } else {
+ /* manually update the state of our system */
+ bta_sys_cb.state = BTA_SYS_HW_STOPPING;
+
+ tBTA_SYS_HW_MSG* p_msg =
+ (tBTA_SYS_HW_MSG*)osi_malloc(sizeof(tBTA_SYS_HW_MSG));
+ p_msg->hdr.event = BTA_SYS_EVT_DISABLED_EVT;
+ p_msg->hw_module = p_sys_hw_msg->hw_module;
+
+ bta_sys_sendmsg(p_msg);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function bta_sys_hw_event_enabled
+ *
+ * Description
+ *
+ *
+ * Returns success or failure
+ *
+ ******************************************************************************/
+void bta_sys_hw_evt_enabled(tBTA_SYS_HW_MSG* p_sys_hw_msg) {
+ APPL_TRACE_EVENT("bta_sys_hw_evt_enabled for %i", p_sys_hw_msg->hw_module);
+ BTM_DeviceReset(NULL);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_sys_hw_event_disabled
+ *
+ * Description
+ *
+ *
+ * Returns success or failure
+ *
+ ******************************************************************************/
+void bta_sys_hw_evt_disabled(tBTA_SYS_HW_MSG* p_sys_hw_msg) {
+ uint8_t hw_module_index;
+
+ APPL_TRACE_DEBUG("bta_sys_hw_evt_disabled - module 0x%X",
+ p_sys_hw_msg->hw_module);
+
+ for (hw_module_index = 0; hw_module_index < BTA_SYS_MAX_HW_MODULES;
+ hw_module_index++) {
+ if (bta_sys_cb.sys_hw_cback[hw_module_index] != NULL)
+ bta_sys_cb.sys_hw_cback[hw_module_index](BTA_SYS_HW_OFF_EVT);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function bta_sys_hw_event_stack_enabled
+ *
+ * Description we receive this event once the SW side is ready (stack, FW
+ * download,... ), i.e. we can really start using the device. So
+ * notify the app.
+ *
+ * Returns success or failure
+ *
+ ******************************************************************************/
+void bta_sys_hw_evt_stack_enabled(UNUSED_ATTR tBTA_SYS_HW_MSG* p_sys_hw_msg) {
+ uint8_t hw_module_index;
+
+ APPL_TRACE_DEBUG(" bta_sys_hw_evt_stack_enabled!notify the callers");
+
+ for (hw_module_index = 0; hw_module_index < BTA_SYS_MAX_HW_MODULES;
+ hw_module_index++) {
+ if (bta_sys_cb.sys_hw_cback[hw_module_index] != NULL)
+ bta_sys_cb.sys_hw_cback[hw_module_index](BTA_SYS_HW_ON_EVT);
}
}
@@ -82,7 +446,7 @@ void BTA_sys_signal_hw_error() {
* Returns void
*
******************************************************************************/
-static void bta_sys_event(BT_HDR_RIGID* p_msg) {
+void bta_sys_event(BT_HDR* p_msg) {
uint8_t id;
bool freebuf = true;
@@ -95,8 +459,7 @@ static void bta_sys_event(BT_HDR_RIGID* p_msg) {
if ((id < BTA_ID_MAX) && (bta_sys_cb.reg[id] != NULL)) {
freebuf = (*bta_sys_cb.reg[id]->evt_hdlr)(p_msg);
} else {
- LOG_INFO("Ignoring receipt of unregistered event id:%s",
- BtaIdSysText(id).c_str());
+ APPL_TRACE_WARNING("%s: Received unregistered event id %d", __func__, id);
}
if (freebuf) {
@@ -163,8 +526,7 @@ bool bta_sys_is_register(uint8_t id) { return bta_sys_cb.is_reg[id]; }
******************************************************************************/
void bta_sys_sendmsg(void* p_msg) {
if (do_in_main_thread(
- FROM_HERE,
- base::Bind(&bta_sys_event, static_cast<BT_HDR_RIGID*>(p_msg))) !=
+ FROM_HERE, base::Bind(&bta_sys_event, static_cast<BT_HDR*>(p_msg))) !=
BT_STATUS_SUCCESS) {
LOG(ERROR) << __func__ << ": do_in_main_thread failed";
}
@@ -172,8 +534,7 @@ void bta_sys_sendmsg(void* p_msg) {
void bta_sys_sendmsg_delayed(void* p_msg, const base::TimeDelta& delay) {
if (do_in_main_thread_delayed(
- FROM_HERE,
- base::Bind(&bta_sys_event, static_cast<BT_HDR_RIGID*>(p_msg)),
+ FROM_HERE, base::Bind(&bta_sys_event, static_cast<BT_HDR*>(p_msg)),
delay) != BT_STATUS_SUCCESS) {
LOG(ERROR) << __func__ << ": do_in_main_thread_delayed failed";
}
@@ -191,7 +552,7 @@ void bta_sys_sendmsg_delayed(void* p_msg, const base::TimeDelta& delay) {
******************************************************************************/
void bta_sys_start_timer(alarm_t* alarm, uint64_t interval_ms, uint16_t event,
uint16_t layer_specific) {
- BT_HDR_RIGID* p_buf = (BT_HDR_RIGID*)osi_malloc(sizeof(BT_HDR_RIGID));
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR));
p_buf->event = event;
p_buf->layer_specific = layer_specific;
@@ -208,9 +569,21 @@ void bta_sys_start_timer(alarm_t* alarm, uint64_t interval_ms, uint16_t event,
* Returns void
*
******************************************************************************/
-void bta_sys_disable() {
- int bta_id = BTA_ID_DM_SEARCH;
- int bta_id_max = BTA_ID_BLUETOOTH_MAX;
+void bta_sys_disable(tBTA_SYS_HW_MODULE module) {
+ int bta_id = 0;
+ int bta_id_max = 0;
+
+ APPL_TRACE_DEBUG("bta_sys_disable: module %i", module);
+
+ switch (module) {
+ case BTA_SYS_HW_BLUETOOTH:
+ bta_id = BTA_ID_DM_SEARCH;
+ bta_id_max = BTA_ID_BLUETOOTH_MAX;
+ break;
+ default:
+ APPL_TRACE_WARNING("bta_sys_disable: unkown module");
+ return;
+ }
for (; bta_id <= bta_id_max; bta_id++) {
if (bta_sys_cb.reg[bta_id] != NULL) {
@@ -221,3 +594,25 @@ void bta_sys_disable() {
}
}
}
+
+/*******************************************************************************
+ *
+ * Function bta_sys_set_trace_level
+ *
+ * Description Set trace level for BTA
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_sys_set_trace_level(uint8_t level) { appl_trace_level = level; }
+
+/*******************************************************************************
+ *
+ * Function bta_sys_get_sys_features
+ *
+ * Description Returns sys_features to other BTA modules.
+ *
+ * Returns sys_features
+ *
+ ******************************************************************************/
+uint16_t bta_sys_get_sys_features(void) { return bta_sys_cb.sys_features; }
diff --git a/bta/sys/utl.cc b/bta/sys/utl.cc
index e4d9034db..544f91e8c 100644
--- a/bta/sys/utl.cc
+++ b/bta/sys/utl.cc
@@ -21,12 +21,11 @@
* This file contains utility functions.
*
******************************************************************************/
-#include <cstdint>
+#include <stddef.h>
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/utl.h"
-#include "stack/include/btm_api.h"
+#include "bt_common.h"
+#include "btm_api.h"
+#include "utl.h"
/*******************************************************************************
*
diff --git a/bta/test/bta_dip_test.cc b/bta/test/bta_dip_test.cc
deleted file mode 100644
index 9b010e59e..000000000
--- a/bta/test/bta_dip_test.cc
+++ /dev/null
@@ -1,124 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#include <gtest/gtest.h>
-#include "bta/sdp/bta_sdp_act.cc"
-#include "stack/sdp/sdp_api.cc"
-
-namespace {
-const RawAddress bdaddr({0x11, 0x22, 0x33, 0x44, 0x55, 0x66});
-} // namespace
-
-extern tBTA_SDP_CB bta_sdp_cb;
-extern tBTA_SDP_CFG* p_bta_sdp_cfg;
-
-static tSDP_DISC_ATTR g_attr_service_class_id_list;
-static tSDP_DISC_ATTR g_sub_attr;
-static tSDP_DISC_ATTR g_attr_spec_id;
-static tSDP_DISC_ATTR g_attr_vendor_id;
-static tSDP_DISC_ATTR g_attr_vendor_id_src;
-static tSDP_DISC_ATTR g_attr_vendor_product_id;
-static tSDP_DISC_ATTR g_attr_vendor_product_version;
-static tSDP_DISC_ATTR g_attr_vendor_product_primary_record;
-static tSDP_DISC_REC g_rec;
-
-bool sdpu_compare_uuid_with_attr(const Uuid& uuid, tSDP_DISC_ATTR* p_attr) {
- return true;
-}
-
-static void sdp_dm_cback(tBTA_SDP_EVT event, tBTA_SDP* p_data,
- void* user_data) {
- return;
-}
-
-class BtaDipTest : public ::testing::Test {
- protected:
- void SetUp() override {
- g_attr_service_class_id_list.p_next_attr = &g_attr_spec_id;
- g_attr_service_class_id_list.attr_id = ATTR_ID_SERVICE_CLASS_ID_LIST;
- g_attr_service_class_id_list.attr_len_type = (DATA_ELE_SEQ_DESC_TYPE<<12)|2;
- g_attr_service_class_id_list.attr_value.v.p_sub_attr = &g_sub_attr;
- g_sub_attr.attr_len_type = (UUID_DESC_TYPE<<12)|2;
- g_sub_attr.attr_value.v.u16 = 0x1200;
-
- g_attr_spec_id.p_next_attr = &g_attr_vendor_id;
- g_attr_spec_id.attr_id = ATTR_ID_SPECIFICATION_ID;
- g_attr_spec_id.attr_len_type = (UINT_DESC_TYPE<<12)|2;
- g_attr_spec_id.attr_value.v.u16 = 0x0103;
-
- g_attr_vendor_id.p_next_attr = &g_attr_vendor_id_src;
- g_attr_vendor_id.attr_id = ATTR_ID_VENDOR_ID;
- g_attr_vendor_id.attr_len_type = (UINT_DESC_TYPE<<12)|2;
- g_attr_vendor_id.attr_value.v.u16 = 0x18d1;
-
- // Allocation should succeed
- g_attr_vendor_id_src.p_next_attr = &g_attr_vendor_product_id;
- g_attr_vendor_id_src.attr_id = ATTR_ID_VENDOR_ID_SOURCE;
- g_attr_vendor_id_src.attr_len_type = (UINT_DESC_TYPE<<12)|2;
- g_attr_vendor_id_src.attr_value.v.u16 = 1;
-
- g_attr_vendor_product_id.p_next_attr = &g_attr_vendor_product_version;
- g_attr_vendor_product_id.attr_id = ATTR_ID_PRODUCT_ID;
- g_attr_vendor_product_id.attr_len_type = (UINT_DESC_TYPE<<12)|2;
- g_attr_vendor_product_id.attr_value.v.u16 = 0x1234;
-
- g_attr_vendor_product_version.p_next_attr = &g_attr_vendor_product_primary_record;
- g_attr_vendor_product_version.attr_id = ATTR_ID_PRODUCT_VERSION;
- g_attr_vendor_product_version.attr_len_type = (UINT_DESC_TYPE<<12)|2;
- g_attr_vendor_product_version.attr_value.v.u16 = 0x0100;
-
- g_attr_vendor_product_primary_record.p_next_attr = &g_attr_vendor_product_primary_record;
- g_attr_vendor_product_primary_record.attr_id = ATTR_ID_PRIMARY_RECORD;
- g_attr_vendor_product_primary_record.attr_len_type = (BOOLEAN_DESC_TYPE<<12);
- g_attr_vendor_product_primary_record.attr_value.v.u8 = 1;
-
- g_rec.p_first_attr = &g_attr_service_class_id_list;
- g_rec.p_next_rec = nullptr;
- g_rec.remote_bd_addr = bdaddr;
- g_rec.time_read = 0;
-
- bta_sdp_cb.p_dm_cback = sdp_dm_cback;
- bta_sdp_cb.remote_addr = bdaddr;
-
- p_bta_sdp_cfg->p_sdp_db->p_first_rec = &g_rec;
- }
-
- void TearDown() override {}
-};
-
-// Test that bta_create_dip_sdp_record can parse sdp record to bluetooth_sdp_record correctly
-TEST_F(BtaDipTest, test_bta_create_dip_sdp_record) {
- bluetooth_sdp_record record;
-
- bta_create_dip_sdp_record(&record, &g_rec);
-
- ASSERT_EQ(record.dip.spec_id, 0x0103);
- ASSERT_EQ(record.dip.vendor, 0x18d1);
- ASSERT_EQ(record.dip.vendor_id_source, 1);
- ASSERT_EQ(record.dip.product, 0x1234);
- ASSERT_EQ(record.dip.version, 0x0100);
- ASSERT_EQ(record.dip.primary_record, true);
-}
-
-TEST_F(BtaDipTest, test_bta_sdp_search_cback) {
- Uuid* userdata = (Uuid*)malloc(sizeof(Uuid));
-
- memcpy(userdata, &UUID_DIP, sizeof(UUID_DIP));
- bta_sdp_search_cback(SDP_SUCCESS, userdata);
-}
-
diff --git a/bta/test/bta_dm_cust_uuid_test.cc b/bta/test/bta_dm_cust_uuid_test.cc
deleted file mode 100644
index 5667546b5..000000000
--- a/bta/test/bta_dm_cust_uuid_test.cc
+++ /dev/null
@@ -1,76 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#include <gtest/gtest.h>
-
-#include "bta/dm/bta_dm_int.h"
-#include "types/bluetooth/uuid.h"
-
-using bluetooth::Uuid;
-
-// NOTE:
-// Local re-implementation of functions to avoid testing of
-// unrelated functions/features.
-tBTM_STATUS BTM_ReadLocalDeviceName(char** p_name) { return BTM_SUCCESS; }
-uint8_t BTM_GetEirSupportedServices(uint32_t* p_eir_uuid, uint8_t** p,
- uint8_t max_num_uuid16,
- uint8_t* p_num_uuid16) {
- return BT_EIR_FLAGS_TYPE;
-}
-tBTM_STATUS BTM_WriteEIR(BT_HDR* p_buff) { return BTM_SUCCESS; }
-
-class BtaCustUuid : public testing::Test {
- protected:
- void SetUp() override {
- memset(&bta_dm_cb, 0, sizeof(bta_dm_cb));
- }
-};
-
-namespace {
- uint32_t handle1 = 1;
- uint32_t handle2 = 2;
- static const Uuid uuid1 = Uuid::From128BitBE(
- Uuid::UUID128Bit{{0x00, 0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88,
- 0x99, 0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff}});
- static const Uuid uuid2 = Uuid::From128BitBE(
- Uuid::UUID128Bit{{0x00, 0x00, 0x00, 0x00, 0x22, 0x22, 0x22, 0x22, 0x33,
- 0x33, 0x55, 0x55, 0x55, 0x55, 0x55, 0x59}});
-}
-
-// Test we can remove/add 128 bit custom UUID from/to bta_dm_cb.bta_custom_uuid
-TEST_F(BtaCustUuid, test_add_remove_cust_uuid) {
- tBTA_CUSTOM_UUID& curr0 = bta_dm_cb.bta_custom_uuid[0];
- tBTA_CUSTOM_UUID& curr1 = bta_dm_cb.bta_custom_uuid[1];
- tBTA_CUSTOM_UUID curr0_expect = {uuid1, handle1};
- tBTA_CUSTOM_UUID curr1_expect = {uuid2, handle2};
- // Add first 128 bit custom UUID
- bta_dm_eir_update_cust_uuid(curr0_expect, true);
- ASSERT_STREQ(uuid1.ToString().c_str(), curr0.custom_uuid.ToString().c_str());
- // Add second 128 bit custom UUID
- bta_dm_eir_update_cust_uuid(curr1_expect, true);
- ASSERT_STREQ(uuid2.ToString().c_str(), curr1.custom_uuid.ToString().c_str());
-
- curr0_expect.custom_uuid.UpdateUuid(Uuid::kEmpty);
- curr1_expect.custom_uuid.UpdateUuid(Uuid::kEmpty);
- // Remove first 128 bit custom UUID
- bta_dm_eir_update_cust_uuid(curr0_expect, false);
- ASSERT_STREQ(Uuid::kEmpty.ToString().c_str(), curr0.custom_uuid.ToString().c_str());
- // Remove second 128 bit custom UUID
- bta_dm_eir_update_cust_uuid(curr1_expect, false);
- ASSERT_STREQ(Uuid::kEmpty.ToString().c_str(), curr1.custom_uuid.ToString().c_str());
-}
diff --git a/bta/test/bta_dm_test.cc b/bta/test/bta_dm_test.cc
deleted file mode 100644
index d440a5c2f..000000000
--- a/bta/test/bta_dm_test.cc
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <base/bind.h>
-#include <base/location.h>
-#include <gtest/gtest.h>
-
-#include "bta/dm/bta_dm_int.h"
-#include "bta/hf_client/bta_hf_client_int.h"
-#include "bta/include/bta_hf_client_api.h"
-#include "bta/test/common/fake_osi.h"
-#include "common/message_loop_thread.h"
-
-std::map<std::string, int> mock_function_count_map;
-
-void LogMsg(uint32_t trace_set_mask, const char* fmt_str, ...) {}
-
-namespace base {
-class MessageLoop;
-} // namespace base
-
-namespace {
-constexpr uint8_t kUnusedTimer = BTA_ID_MAX;
-} // namespace
-
-class BtaDmTest : public testing::Test {
- protected:
- void SetUp() override {
- mock_function_count_map.clear();
-
- bta_dm_init_cb();
-
- for (int i = 0; i < BTA_DM_NUM_PM_TIMER; i++) {
- for (int j = 0; j < BTA_DM_PM_MODE_TIMER_MAX; j++) {
- bta_dm_cb.pm_timer[i].srvc_id[j] = kUnusedTimer;
- }
- }
- }
- void TearDown() override { bta_dm_deinit_cb(); }
-};
-
-TEST_F(BtaDmTest, nop) {
- bool status = true;
- ASSERT_EQ(true, status);
-}
-
-extern struct fake_osi_alarm_set_on_mloop fake_osi_alarm_set_on_mloop_;
-
-TEST_F(BtaDmTest, disable_no_acl_links) {
- bta_dm_cb.disabling = true;
-
- bta_dm_disable(); // Waiting for all ACL connections to drain
- ASSERT_EQ(0, mock_function_count_map["btm_remove_acl"]);
- ASSERT_EQ(1, mock_function_count_map["alarm_set_on_mloop"]);
-
- // Execute timer callback
- fake_osi_alarm_set_on_mloop_.cb(fake_osi_alarm_set_on_mloop_.data);
- ASSERT_EQ(1, mock_function_count_map["alarm_set_on_mloop"]);
- ASSERT_EQ(0, mock_function_count_map["BTIF_dm_disable"]);
- ASSERT_EQ(1, mock_function_count_map["future_ready"]);
- ASSERT_TRUE(!bta_dm_cb.disabling);
-}
-
-extern uint16_t mock_stack_acl_num_links;
-TEST_F(BtaDmTest, disable_first_pass_with_acl_links) {
- bta_dm_cb.disabling = true;
- // ACL link is open
- mock_stack_acl_num_links = bta_dm_cb.device_list.count = 1;
-
- bta_dm_disable(); // Waiting for all ACL connections to drain
- mock_stack_acl_num_links = 0; // ACL link has closed
- ASSERT_EQ(1, mock_function_count_map["alarm_set_on_mloop"]);
- ASSERT_EQ(0, mock_function_count_map["BTIF_dm_disable"]);
-
- // First disable pass
- fake_osi_alarm_set_on_mloop_.cb(fake_osi_alarm_set_on_mloop_.data);
- ASSERT_EQ(1, mock_function_count_map["alarm_set_on_mloop"]);
- ASSERT_EQ(1, mock_function_count_map["BTIF_dm_disable"]);
- ASSERT_TRUE(!bta_dm_cb.disabling);
-}
-
-TEST_F(BtaDmTest, disable_second_pass_with_acl_links) {
- bta_dm_cb.disabling = true;
- // ACL link is open
- mock_stack_acl_num_links = bta_dm_cb.device_list.count = 1;
-
- bta_dm_disable(); // Waiting for all ACL connections to drain
- ASSERT_EQ(1, mock_function_count_map["alarm_set_on_mloop"]);
- ASSERT_EQ(0, mock_function_count_map["BTIF_dm_disable"]);
-
- // First disable pass
- fake_osi_alarm_set_on_mloop_.cb(fake_osi_alarm_set_on_mloop_.data);
- ASSERT_EQ(2, mock_function_count_map["alarm_set_on_mloop"]);
- ASSERT_EQ(0, mock_function_count_map["BTIF_dm_disable"]);
- ASSERT_EQ(1, mock_function_count_map["btm_remove_acl"]);
-
- // Second disable pass
- fake_osi_alarm_set_on_mloop_.cb(fake_osi_alarm_set_on_mloop_.data);
- ASSERT_EQ(1, mock_function_count_map["BTIF_dm_disable"]);
- ASSERT_TRUE(!bta_dm_cb.disabling);
-}
diff --git a/bta/test/bta_gatt_test.cc b/bta/test/bta_gatt_test.cc
deleted file mode 100644
index a95ae46a5..000000000
--- a/bta/test/bta_gatt_test.cc
+++ /dev/null
@@ -1,295 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gtest/gtest.h>
-#include <string.h>
-
-#include <cstdint>
-#include <map>
-#include <memory>
-#include <string>
-
-#include "bta/gatt/bta_gattc_int.h"
-#include "common/message_loop_thread.h"
-#include "stack/gatt/gatt_int.h"
-
-// TODO put this in common place
-extern std::map<std::string, int> mock_function_count_map;
-
-namespace param {
-struct {
- uint16_t conn_id;
- tGATT_STATUS status;
- uint16_t handle;
- uint16_t len;
- uint8_t* value;
- void* data;
-} bta_gatt_read_complete_callback;
-} // namespace param
-void bta_gatt_read_complete_callback(uint16_t conn_id, tGATT_STATUS status,
- uint16_t handle, uint16_t len,
- uint8_t* value, void* data) {
- param::bta_gatt_read_complete_callback.conn_id = conn_id;
- param::bta_gatt_read_complete_callback.status = status;
- param::bta_gatt_read_complete_callback.handle = handle;
- param::bta_gatt_read_complete_callback.len = len;
- param::bta_gatt_read_complete_callback.value = value;
- param::bta_gatt_read_complete_callback.data = data;
-}
-
-namespace param {
-struct {
- uint16_t conn_id;
- tGATT_STATUS status;
- uint16_t handle;
- void* data;
-} bta_gatt_write_complete_callback;
-} // namespace param
-
-void bta_gatt_write_complete_callback(uint16_t conn_id, tGATT_STATUS status,
- uint16_t handle, void* data) {
- param::bta_gatt_write_complete_callback.conn_id = conn_id;
- param::bta_gatt_write_complete_callback.status = status;
- param::bta_gatt_write_complete_callback.handle = handle;
- param::bta_gatt_write_complete_callback.data = data;
-}
-
-namespace param {
-struct {
- uint16_t conn_id;
- tGATT_STATUS status;
- void* data;
-} bta_gatt_configure_mtu_complete_callback;
-} // namespace param
-
-void bta_gatt_configure_mtu_complete_callback(uint16_t conn_id,
- tGATT_STATUS status, void* data) {
- param::bta_gatt_configure_mtu_complete_callback.conn_id = conn_id;
- param::bta_gatt_configure_mtu_complete_callback.status = status;
- param::bta_gatt_configure_mtu_complete_callback.data = data;
-}
-
-namespace param {
-struct {
- tBTA_GATTC_EVT event;
- tBTA_GATTC* p_data;
-} bta_gattc_event_complete_callback;
-} // namespace param
-
-void bta_gattc_event_complete_callback(tBTA_GATTC_EVT event,
- tBTA_GATTC* p_data) {
- param::bta_gattc_event_complete_callback.event = event;
- param::bta_gattc_event_complete_callback.p_data = p_data;
-}
-
-class BtaGattTest : public ::testing::Test {
- protected:
- void SetUp() override {
- mock_function_count_map.clear();
- param::bta_gatt_read_complete_callback = {};
- param::bta_gatt_write_complete_callback = {};
- param::bta_gatt_configure_mtu_complete_callback = {};
- param::bta_gattc_event_complete_callback = {};
- }
-
- void TearDown() override {}
-
- tBTA_GATTC_RCB app_control_block = {
- .p_cback = bta_gattc_event_complete_callback,
- };
-
- tGATT_CL_COMPLETE gatt_cl_complete = {
- .att_value =
- {
- .conn_id = 1,
- .handle = 2,
- .offset = 3,
- .auth_req = GATT_AUTH_REQ_NONE,
- .value = {10, 11, 12, 13},
- .len = 4, // length of value above
- },
- };
-
- tBTA_GATTC_SERV service_control_block = {
- .mtu = 456,
- };
- tBTA_GATTC_DATA command_queue;
-
- tBTA_GATTC_CLCB client_channel_control_block = {
- .p_q_cmd = &command_queue,
- .p_rcb = &app_control_block,
- .p_srcb = &service_control_block,
- .bta_conn_id = 456,
- };
-};
-
-TEST_F(BtaGattTest, bta_gattc_op_cmpl_read) {
- command_queue = {
- .api_read = // tBTA_GATTC_API_READ
- {
- .hdr =
- {
- .event = BTA_GATTC_API_READ_EVT,
- },
- .handle = 123,
- .read_cb = bta_gatt_read_complete_callback,
- .read_cb_data = static_cast<void*>(this),
- },
- };
-
- client_channel_control_block.p_q_cmd = &command_queue;
-
- tBTA_GATTC_DATA data = {
- .op_cmpl =
- {
- .op_code = GATTC_OPTYPE_READ,
- .status = GATT_OUT_OF_RANGE,
- .p_cmpl = &gatt_cl_complete,
- },
- };
-
- bta_gattc_op_cmpl(&client_channel_control_block, &data);
- ASSERT_EQ(1, mock_function_count_map["osi_free_and_reset"]);
- ASSERT_EQ(456, param::bta_gatt_read_complete_callback.conn_id);
- ASSERT_EQ(GATT_OUT_OF_RANGE, param::bta_gatt_read_complete_callback.status);
- ASSERT_EQ(123, param::bta_gatt_read_complete_callback.handle);
- ASSERT_EQ(4, param::bta_gatt_read_complete_callback.len);
- ASSERT_EQ(10, param::bta_gatt_read_complete_callback.value[0]);
- ASSERT_EQ(this, param::bta_gatt_read_complete_callback.data);
-}
-
-TEST_F(BtaGattTest, bta_gattc_op_cmpl_write) {
- command_queue = {
- .api_write = // tBTA_GATTC_API_WRITE
- {
- .hdr =
- {
- .event = BTA_GATTC_API_WRITE_EVT,
- },
- .handle = 123,
- .write_cb = bta_gatt_write_complete_callback,
- .write_cb_data = static_cast<void*>(this),
- },
- };
-
- client_channel_control_block.p_q_cmd = &command_queue;
-
- tBTA_GATTC_DATA data = {
- .op_cmpl =
- {
- .op_code = GATTC_OPTYPE_WRITE,
- .status = GATT_OUT_OF_RANGE,
- .p_cmpl = &gatt_cl_complete,
- },
- };
-
- bta_gattc_op_cmpl(&client_channel_control_block, &data);
- ASSERT_EQ(1, mock_function_count_map["osi_free_and_reset"]);
- ASSERT_EQ(456, param::bta_gatt_write_complete_callback.conn_id);
- ASSERT_EQ(2, param::bta_gatt_write_complete_callback.handle);
- ASSERT_EQ(GATT_OUT_OF_RANGE, param::bta_gatt_write_complete_callback.status);
- ASSERT_EQ(this, param::bta_gatt_write_complete_callback.data);
-}
-
-TEST_F(BtaGattTest, bta_gattc_op_cmpl_config) {
- command_queue = {
- .api_mtu = // tBTA_GATTC_API_CFG_MTU
- {
- .hdr =
- {
- .event = BTA_GATTC_API_CFG_MTU_EVT,
- },
- .mtu_cb = bta_gatt_configure_mtu_complete_callback,
- .mtu_cb_data = static_cast<void*>(this),
- },
- };
-
- client_channel_control_block.p_q_cmd = &command_queue;
-
- tBTA_GATTC_DATA data = {
- .op_cmpl =
- {
- .op_code = GATTC_OPTYPE_CONFIG,
- .status = GATT_PRC_IN_PROGRESS,
- },
- };
-
- bta_gattc_op_cmpl(&client_channel_control_block, &data);
- ASSERT_EQ(1, mock_function_count_map["osi_free_and_reset"]);
- ASSERT_EQ(456, param::bta_gatt_configure_mtu_complete_callback.conn_id);
-
- ASSERT_EQ(GATT_PRC_IN_PROGRESS,
- param::bta_gatt_configure_mtu_complete_callback.status);
- ASSERT_EQ(this, param::bta_gatt_configure_mtu_complete_callback.data);
-}
-
-TEST_F(BtaGattTest, bta_gattc_op_cmpl_execute) {
- command_queue = {
- .api_exec = // tBTA_GATTC_API_EXEC
- {
- .hdr =
- {
- .event = BTA_GATTC_API_EXEC_EVT,
- },
- },
- };
-
- client_channel_control_block.p_q_cmd = &command_queue;
-
- tBTA_GATTC_DATA data = {
- .op_cmpl =
- {
- .op_code = GATTC_OPTYPE_EXE_WRITE,
- },
- };
-
- bta_gattc_op_cmpl(&client_channel_control_block, &data);
- ASSERT_EQ(BTA_GATTC_EXEC_EVT, param::bta_gattc_event_complete_callback.event);
- ASSERT_EQ(1, mock_function_count_map["osi_free_and_reset"]);
-}
-
-TEST_F(BtaGattTest, bta_gattc_op_cmpl_read_interrupted) {
- command_queue = {
- .api_read = // tBTA_GATTC_API_READ
- {
- .hdr =
- {
- .event = BTA_GATTC_API_READ_EVT,
- },
- .handle = 123,
- .read_cb = bta_gatt_read_complete_callback,
- .read_cb_data = static_cast<void*>(this),
- },
- };
-
- client_channel_control_block.p_q_cmd = &command_queue;
-
- // Create interrupt condition
- client_channel_control_block.auto_update = BTA_GATTC_DISC_WAITING;
- client_channel_control_block.p_srcb->srvc_hdl_chg = 1;
-
- tBTA_GATTC_DATA data = {
- .op_cmpl =
- {
- .op_code = GATTC_OPTYPE_READ,
- .status = GATT_OUT_OF_RANGE,
- .p_cmpl = &gatt_cl_complete,
- },
- };
-
- bta_gattc_op_cmpl(&client_channel_control_block, &data);
- ASSERT_EQ(GATT_ERROR, param::bta_gatt_read_complete_callback.status);
-}
diff --git a/bta/test/bta_hf_client_add_record_test.cc b/bta/test/bta_hf_client_add_record_test.cc
index 240d17b70..e975b567a 100644
--- a/bta/test/bta_hf_client_add_record_test.cc
+++ b/bta/test/bta_hf_client_add_record_test.cc
@@ -1,34 +1,11 @@
-/******************************************************************************
- *
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
#include <base/logging.h>
#include <gtest/gtest.h>
#include "bta/hf_client/bta_hf_client_sdp.cc"
-#include "bta/include/bta_hf_client_api.h"
#include "btif/src/btif_hf_client.cc"
static uint16_t gVersion;
-// Define appl_trace_level even though LogMsg is trivial. This is required when
-// coverage is enabled because the compiler is unable to eliminate the `if`
-// checks against appl_trace_level in APPL_TRACE_* macros.
-uint8_t appl_trace_level = 0;
void LogMsg(uint32_t trace_set_mask, const char* fmt_str, ...) {}
bool SDP_AddProtocolList(uint32_t handle, uint16_t num_elem,
tSDP_PROTOCOL_ELEM* p_elem_list) {
@@ -54,9 +31,7 @@ bool SDP_AddUuidSequence(uint32_t handle, uint16_t attr_id, uint16_t num_uuids,
class BtaHfClientAddRecordTest : public ::testing::Test {
protected:
- void SetUp() override {
- gVersion = 0;
- }
+ void SetUp() override { gVersion = 0; }
void TearDown() override {}
};
@@ -66,7 +41,12 @@ TEST_F(BtaHfClientAddRecordTest, test_hf_client_add_record) {
uint32_t sdp_handle = 0;
uint8_t scn = 0;
+ osi_property_set("persist.bluetooth.hfpclient.sco_s4_supported", "true");
+ bta_hf_client_add_record("Handsfree", scn, features, sdp_handle);
+ EXPECT_EQ(gVersion, 0x0107);
+ sdp_handle++;
+ scn++;
+ osi_property_set("persist.bluetooth.hfpclient.sco_s4_supported", "false");
bta_hf_client_add_record("Handsfree", scn, features, sdp_handle);
- ASSERT_EQ(gVersion, BTA_HFP_VERSION);
+ EXPECT_EQ(gVersion, 0x0106);
}
-
diff --git a/bta/test/bta_hf_client_test.cc b/bta/test/bta_hf_client_test.cc
index d906a9dd1..9b9ade25b 100644
--- a/bta/test/bta_hf_client_test.cc
+++ b/bta/test/bta_hf_client_test.cc
@@ -20,13 +20,12 @@
#include "bta/hf_client/bta_hf_client_int.h"
#include "bta/include/bta_hf_client_api.h"
-#include "common/message_loop_thread.h"
namespace base {
class MessageLoop;
} // namespace base
-bluetooth::common::MessageLoopThread* get_main_thread() { return nullptr; }
+base::MessageLoop* get_main_message_loop() { return NULL; }
namespace {
const RawAddress bdaddr1({0x11, 0x22, 0x33, 0x44, 0x55, 0x66});
diff --git a/bta/test/common/bta_gatt_api_mock.cc b/bta/test/common/bta_gatt_api_mock.cc
deleted file mode 100644
index 628c4d51c..000000000
--- a/bta/test/common/bta_gatt_api_mock.cc
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "bta_gatt_api_mock.h"
-
-static gatt::MockBtaGattInterface* gatt_interface = nullptr;
-
-void gatt::SetMockBtaGattInterface(
- MockBtaGattInterface* mock_bta_gatt_interface) {
- gatt_interface = mock_bta_gatt_interface;
-}
-
-void BTA_GATTC_AppRegister(tBTA_GATTC_CBACK* p_client_cb,
- BtaAppRegisterCallback cb, bool eatt_support) {
- gatt_interface->AppRegister(p_client_cb, cb, eatt_support);
-}
-
-void BTA_GATTC_AppDeregister(tGATT_IF client_if) {
- gatt_interface->AppDeregister(client_if);
-}
-
-void BTA_GATTC_Open(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct, tBT_TRANSPORT transport,
- bool opportunistic) {
- gatt_interface->Open(client_if, remote_bda, is_direct, transport,
- opportunistic);
-}
-
-void BTA_GATTC_Open(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct, bool opportunistic) {
- gatt_interface->Open(client_if, remote_bda, is_direct, opportunistic);
-}
-
-void BTA_GATTC_CancelOpen(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct) {
- gatt_interface->CancelOpen(client_if, remote_bda, is_direct);
-}
-
-void BTA_GATTC_Close(uint16_t conn_id) { gatt_interface->Close(conn_id); }
-
-void BTA_GATTC_ServiceSearchRequest(uint16_t conn_id,
- const bluetooth::Uuid* p_srvc_uuid) {
- gatt_interface->ServiceSearchRequest(conn_id, p_srvc_uuid);
-}
-
-const std::list<gatt::Service>* BTA_GATTC_GetServices(uint16_t conn_id) {
- return gatt_interface->GetServices(conn_id);
-}
-
-const gatt::Characteristic* BTA_GATTC_GetCharacteristic(uint16_t conn_id,
- uint16_t handle) {
- return gatt_interface->GetCharacteristic(conn_id, handle);
-}
-
-const gatt::Service* BTA_GATTC_GetOwningService(uint16_t conn_id,
- uint16_t handle) {
- return gatt_interface->GetOwningService(conn_id, handle);
-}
-
-tGATT_STATUS BTA_GATTC_RegisterForNotifications(tGATT_IF client_if,
- const RawAddress& remote_bda,
- uint16_t handle) {
- return gatt_interface->RegisterForNotifications(client_if, remote_bda,
- handle);
-}
-
-tGATT_STATUS BTA_GATTC_DeregisterForNotifications(tGATT_IF client_if,
- const RawAddress& remote_bda,
- uint16_t handle) {
- return gatt_interface->DeregisterForNotifications(client_if, remote_bda,
- handle);
-}
diff --git a/bta/test/common/bta_gatt_api_mock.h b/bta/test/common/bta_gatt_api_mock.h
deleted file mode 100644
index 3ddd6da76..000000000
--- a/bta/test/common/bta_gatt_api_mock.h
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <base/callback.h>
-#include <gmock/gmock.h>
-
-#include "bta_gatt_api.h"
-
-namespace gatt {
-
-class BtaGattInterface {
- public:
- virtual void AppRegister(tBTA_GATTC_CBACK* p_client_cb,
- BtaAppRegisterCallback cb, bool eatt_support) = 0;
- virtual void AppDeregister(tGATT_IF client_if) = 0;
- virtual void Open(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct, tBT_TRANSPORT transport,
- bool opportunistic) = 0;
- virtual void Open(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct, bool opportunistic) = 0;
- virtual void CancelOpen(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct) = 0;
- virtual void Close(uint16_t conn_id) = 0;
- virtual void ServiceSearchRequest(uint16_t conn_id,
- const bluetooth::Uuid* p_srvc_uuid) = 0;
- virtual const std::list<Service>* GetServices(uint16_t conn_id) = 0;
- virtual const Characteristic* GetCharacteristic(uint16_t conn_id,
- uint16_t handle) = 0;
- virtual const Service* GetOwningService(uint16_t conn_id,
- uint16_t handle) = 0;
- virtual tGATT_STATUS RegisterForNotifications(tGATT_IF client_if,
- const RawAddress& remote_bda,
- uint16_t handle) = 0;
- virtual tGATT_STATUS DeregisterForNotifications(tGATT_IF client_if,
- const RawAddress& remote_bda,
- uint16_t handle) = 0;
- virtual ~BtaGattInterface() = default;
-};
-
-class MockBtaGattInterface : public BtaGattInterface {
- public:
- MOCK_METHOD((void), AppRegister,
- (tBTA_GATTC_CBACK * p_client_cb, BtaAppRegisterCallback cb,
- bool eatt_support),
- (override));
- MOCK_METHOD((void), AppDeregister, (tGATT_IF client_if), (override));
- MOCK_METHOD((void), Open,
- (tGATT_IF client_if, const RawAddress& remote_bda, bool is_direct,
- tBT_TRANSPORT transport, bool opportunistic));
- MOCK_METHOD((void), Open,
- (tGATT_IF client_if, const RawAddress& remote_bda, bool is_direct,
- bool opportunistic));
- MOCK_METHOD((void), CancelOpen,
- (tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct));
- MOCK_METHOD((void), Close, (uint16_t conn_id));
- MOCK_METHOD((void), ServiceSearchRequest,
- (uint16_t conn_id, const bluetooth::Uuid* p_srvc_uuid));
- MOCK_METHOD((std::list<Service>*), GetServices, (uint16_t conn_id));
- MOCK_METHOD((const Characteristic*), GetCharacteristic,
- (uint16_t conn_id, uint16_t handle));
- MOCK_METHOD((const Service*), GetOwningService,
- (uint16_t conn_id, uint16_t handle));
- MOCK_METHOD((tGATT_STATUS), RegisterForNotifications,
- (tGATT_IF client_if, const RawAddress& remote_bda,
- uint16_t handle));
- MOCK_METHOD((tGATT_STATUS), DeregisterForNotifications,
- (tGATT_IF client_if, const RawAddress& remote_bda,
- uint16_t handle));
-};
-
-/**
- * Set the {@link MockBtaGattInterface} for testing
- *
- * @param mock_bta_gatt_interface pointer to mock bta gatt interface,
- * could be null
- */
-void SetMockBtaGattInterface(MockBtaGattInterface* mock_bta_gatt_interface);
-
-} // namespace gatt
diff --git a/bta/test/common/bta_gatt_queue_mock.cc b/bta/test/common/bta_gatt_queue_mock.cc
deleted file mode 100644
index 737b341c3..000000000
--- a/bta/test/common/bta_gatt_queue_mock.cc
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "bta_gatt_queue_mock.h"
-
-static gatt::MockBtaGattQueue* gatt_queue = nullptr;
-
-void gatt::SetMockBtaGattQueue(MockBtaGattQueue* mock_bta_gatt_queue) {
- gatt_queue = mock_bta_gatt_queue;
-}
-
-void BtaGattQueue::Clean(uint16_t conn_id) { gatt_queue->Clean(conn_id); }
-
-void BtaGattQueue::ReadCharacteristic(uint16_t conn_id, uint16_t handle,
- GATT_READ_OP_CB cb, void* cb_data) {
- gatt_queue->ReadCharacteristic(conn_id, handle, cb, cb_data);
-}
-
-void BtaGattQueue::WriteCharacteristic(uint16_t conn_id, uint16_t handle,
- std::vector<uint8_t> value,
- tGATT_WRITE_TYPE write_type,
- GATT_WRITE_OP_CB cb, void* cb_data) {
- gatt_queue->WriteCharacteristic(conn_id, handle, value, write_type, cb,
- cb_data);
-}
-
-void BtaGattQueue::WriteDescriptor(uint16_t conn_id, uint16_t handle,
- std::vector<uint8_t> value,
- tGATT_WRITE_TYPE write_type,
- GATT_WRITE_OP_CB cb, void* cb_data) {
- gatt_queue->WriteDescriptor(conn_id, handle, value, write_type, cb, cb_data);
-}
diff --git a/bta/test/common/bta_gatt_queue_mock.h b/bta/test/common/bta_gatt_queue_mock.h
deleted file mode 100644
index 127bdc8b7..000000000
--- a/bta/test/common/bta_gatt_queue_mock.h
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <gmock/gmock.h>
-
-#include "bta_gatt_queue.h"
-
-namespace gatt {
-
-class MockBtaGattQueue {
- public:
- MOCK_METHOD((void), Clean, (uint16_t conn_id));
- MOCK_METHOD((void), ReadCharacteristic,
- (uint16_t conn_id, uint16_t handle, GATT_READ_OP_CB cb,
- void* cb_data));
- MOCK_METHOD((void), WriteCharacteristic,
- (uint16_t conn_id, uint16_t handle, std::vector<uint8_t> value,
- tGATT_WRITE_TYPE write_type, GATT_WRITE_OP_CB cb,
- void* cb_data));
- MOCK_METHOD((void), WriteDescriptor,
- (uint16_t conn_id, uint16_t handle, std::vector<uint8_t> value,
- tGATT_WRITE_TYPE write_type, GATT_WRITE_OP_CB cb,
- void* cb_data));
-};
-
-/**
- * Set the {@link MockBtaGattQueue} for testing
- *
- * @param mock_bta_gatt_queue pointer to mock bta gatt queue, could be null
- */
-void SetMockBtaGattQueue(MockBtaGattQueue* mock_bta_gatt_queue);
-
-} // namespace gatt
diff --git a/bta/test/common/btm_api_mock.cc b/bta/test/common/btm_api_mock.cc
deleted file mode 100644
index 88d511a2d..000000000
--- a/bta/test/common/btm_api_mock.cc
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "btm_api_mock.h"
-
-static bluetooth::manager::MockBtmInterface* btm_interface = nullptr;
-
-void bluetooth::manager::SetMockBtmInterface(
- MockBtmInterface* mock_btm_interface) {
- btm_interface = mock_btm_interface;
-}
-
-bool BTM_GetSecurityFlagsByTransport(const RawAddress& bd_addr,
- uint8_t* p_sec_flags,
- tBT_TRANSPORT transport) {
- return btm_interface->GetSecurityFlagsByTransport(bd_addr, p_sec_flags,
- transport);
-}
-
-tBTM_STATUS BTM_SetEncryption(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback, void* p_ref_data,
- tBTM_BLE_SEC_ACT sec_act) {
- return btm_interface->SetEncryption(bd_addr, transport, p_callback,
- p_ref_data, sec_act);
-}
diff --git a/bta/test/common/btm_api_mock.h b/bta/test/common/btm_api_mock.h
deleted file mode 100644
index d337b85f5..000000000
--- a/bta/test/common/btm_api_mock.h
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <gmock/gmock.h>
-
-#include "btm_api.h"
-
-namespace bluetooth {
-namespace manager {
-
-class BtmInterface {
- public:
- virtual bool GetSecurityFlagsByTransport(const RawAddress& bd_addr,
- uint8_t* p_sec_flags,
- tBT_TRANSPORT transport) = 0;
- virtual tBTM_STATUS SetEncryption(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data,
- tBTM_BLE_SEC_ACT sec_act) = 0;
- virtual ~BtmInterface() = default;
-};
-
-class MockBtmInterface : public BtmInterface {
- public:
- MOCK_METHOD((bool), GetSecurityFlagsByTransport,
- (const RawAddress& bd_addr, uint8_t* p_sec_flags,
- tBT_TRANSPORT transport),
- (override));
- MOCK_METHOD((tBTM_STATUS), SetEncryption,
- (const RawAddress& bd_addr, tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback, void* p_ref_data,
- tBTM_BLE_SEC_ACT sec_act),
- (override));
-};
-
-/**
- * Set the {@link MockBtmInterface} for testing
- *
- * @param mock_btm_interface pointer to mock btm interface, could be null
- */
-void SetMockBtmInterface(MockBtmInterface* mock_btm_interface);
-
-} // namespace manager
-} // namespace bluetooth
diff --git a/bta/test/common/fake_osi.h b/bta/test/common/fake_osi.h
deleted file mode 100644
index 9056d583e..000000000
--- a/bta/test/common/fake_osi.h
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include "osi/include/alarm.h"
-
-struct fake_osi_alarm_set_on_mloop {
- uint64_t interval_ms{0};
- alarm_callback_t cb{};
- void* data{nullptr};
-};
diff --git a/bta/test/gatt/database_builder_test.cc b/bta/test/gatt/database_builder_test.cc
index de84d5f70..0a7e9280d 100644
--- a/bta/test/gatt/database_builder_test.cc
+++ b/bta/test/gatt/database_builder_test.cc
@@ -29,7 +29,7 @@ using bluetooth::Uuid;
namespace gatt {
namespace {
-/* make_pair doesn't work well with ASSERT_EQ, have own helper instead */
+/* make_pair doesn't work well with EXPECT_EQ, have own helper instead */
inline std::pair<uint16_t, uint16_t> make_pair_u16(uint16_t first,
uint16_t second) {
return std::make_pair(first, second);
@@ -61,10 +61,10 @@ TEST(DatabaseBuilderTest, EmptyServiceAddTest) {
// verify that the returned database matches what was discovered
auto service = result.Services().begin();
- ASSERT_EQ(service->handle, 0x0001);
- ASSERT_EQ(service->end_handle, 0x0001);
- ASSERT_EQ(service->is_primary, true);
- ASSERT_EQ(service->uuid, SERVICE_1_UUID);
+ EXPECT_EQ(service->handle, 0x0001);
+ EXPECT_EQ(service->end_handle, 0x0001);
+ EXPECT_EQ(service->is_primary, true);
+ EXPECT_EQ(service->uuid, SERVICE_1_UUID);
}
/* Verify adding service, characteristic and descriptor work */
@@ -82,19 +82,19 @@ TEST(DatabaseBuilderTest, DescriptorAddTest) {
// verify that the returned database matches what was discovered
auto service = result.Services().begin();
- ASSERT_EQ(service->handle, 0x0001);
- ASSERT_EQ(service->end_handle, 0x000f);
- ASSERT_EQ(service->is_primary, true);
- ASSERT_EQ(service->uuid, SERVICE_1_UUID);
+ EXPECT_EQ(service->handle, 0x0001);
+ EXPECT_EQ(service->end_handle, 0x000f);
+ EXPECT_EQ(service->is_primary, true);
+ EXPECT_EQ(service->uuid, SERVICE_1_UUID);
- ASSERT_EQ(service->characteristics[0].uuid, SERVICE_1_CHAR_1_UUID);
- ASSERT_EQ(service->characteristics[0].declaration_handle, 0x0002);
- ASSERT_EQ(service->characteristics[0].value_handle, 0x0003);
- ASSERT_EQ(service->characteristics[0].properties, 0x02);
+ EXPECT_EQ(service->characteristics[0].uuid, SERVICE_1_CHAR_1_UUID);
+ EXPECT_EQ(service->characteristics[0].declaration_handle, 0x0002);
+ EXPECT_EQ(service->characteristics[0].value_handle, 0x0003);
+ EXPECT_EQ(service->characteristics[0].properties, 0x02);
- ASSERT_EQ(service->characteristics[0].descriptors[0].uuid,
+ EXPECT_EQ(service->characteristics[0].descriptors[0].uuid,
SERVICE_1_CHAR_1_DESC_1_UUID);
- ASSERT_EQ(service->characteristics[0].descriptors[0].handle, 0x0004);
+ EXPECT_EQ(service->characteristics[0].descriptors[0].handle, 0x0004);
}
/* This test verifies that DatabaseBuilder properly handle discovery of
@@ -113,64 +113,59 @@ TEST(DatabaseBuilderTest, SecondaryServiceOutOfOrderTest) {
// First service skipped, no place for handles
EXPECT_TRUE(builder.StartNextServiceExploration());
- ASSERT_EQ(builder.CurrentlyExploredService(), make_pair_u16(0x0001, 0x000f));
+ EXPECT_EQ(builder.CurrentlyExploredService(), make_pair_u16(0x0001, 0x000f));
// For this test, content of first service is irrevelant
EXPECT_TRUE(builder.StartNextServiceExploration());
// Grabbing first service, to start Included Service and Characteristic
// discovery
- ASSERT_EQ(builder.CurrentlyExploredService(), make_pair_u16(0x0030, 0x003f));
+ EXPECT_EQ(builder.CurrentlyExploredService(), make_pair_u16(0x0030, 0x003f));
builder.AddIncludedService(0x0031, SERVICE_4_UUID, 0x0040, 0x004f);
builder.AddIncludedService(0x0032, SERVICE_2_UUID, 0x0020, 0x002f);
/* Secondary service exploration */
EXPECT_TRUE(builder.StartNextServiceExploration());
- ASSERT_EQ(builder.CurrentlyExploredService(), make_pair_u16(0x0020, 0x002f));
+ EXPECT_EQ(builder.CurrentlyExploredService(), make_pair_u16(0x0020, 0x002f));
/* Secondary service exploration */
EXPECT_TRUE(builder.StartNextServiceExploration());
- ASSERT_EQ(builder.CurrentlyExploredService(), make_pair_u16(0x0040, 0x004f));
+ EXPECT_EQ(builder.CurrentlyExploredService(), make_pair_u16(0x0040, 0x004f));
/* Back to primary service exploration */
EXPECT_TRUE(builder.StartNextServiceExploration());
- ASSERT_EQ(builder.CurrentlyExploredService(), make_pair_u16(0x0050, 0x005f));
+ EXPECT_EQ(builder.CurrentlyExploredService(), make_pair_u16(0x0050, 0x005f));
Database result = builder.Build();
// verify that the returned database matches what was discovered
auto service = result.Services().begin();
- ASSERT_EQ(service->handle, 0x0001);
- ASSERT_EQ(service->is_primary, true);
- ASSERT_EQ(service->uuid, SERVICE_1_UUID);
+ EXPECT_EQ(service->handle, 0x0001);
+ EXPECT_EQ(service->is_primary, true);
+ EXPECT_EQ(service->uuid, SERVICE_1_UUID);
service++;
- ASSERT_EQ(service->handle, 0x0020);
- ASSERT_EQ(service->end_handle, 0x002f);
- ASSERT_EQ(service->uuid, SERVICE_2_UUID);
- ASSERT_EQ(service->is_primary, false);
+ EXPECT_EQ(service->handle, 0x0020);
+ EXPECT_EQ(service->end_handle, 0x002f);
+ EXPECT_EQ(service->uuid, SERVICE_2_UUID);
+ EXPECT_EQ(service->is_primary, false);
service++;
- ASSERT_EQ(service->handle, 0x0030);
- ASSERT_EQ(service->end_handle, 0x003f);
- ASSERT_EQ(service->uuid, SERVICE_3_UUID);
- ASSERT_EQ(service->is_primary, true);
- ASSERT_EQ(service->included_services.size(), (size_t)2);
- ASSERT_EQ(service->included_services[0].start_handle, 0x0040);
- ASSERT_EQ(service->included_services[0].end_handle, 0x004f);
- ASSERT_EQ(service->included_services[1].start_handle, 0x0020);
- ASSERT_EQ(service->included_services[1].end_handle, 0x002f);
+ EXPECT_EQ(service->handle, 0x0030);
+ EXPECT_EQ(service->end_handle, 0x003f);
+ EXPECT_EQ(service->uuid, SERVICE_3_UUID);
+ EXPECT_EQ(service->is_primary, true);
service++;
- ASSERT_EQ(service->handle, 0x0040);
- ASSERT_EQ(service->uuid, SERVICE_4_UUID);
- ASSERT_EQ(service->is_primary, false);
+ EXPECT_EQ(service->handle, 0x0040);
+ EXPECT_EQ(service->uuid, SERVICE_4_UUID);
+ EXPECT_EQ(service->is_primary, false);
service++;
- ASSERT_EQ(service->handle, 0x0050);
- ASSERT_EQ(service->uuid, SERVICE_5_UUID);
- ASSERT_EQ(service->is_primary, true);
+ EXPECT_EQ(service->handle, 0x0050);
+ EXPECT_EQ(service->uuid, SERVICE_5_UUID);
+ EXPECT_EQ(service->is_primary, true);
service++;
ASSERT_EQ(service, result.Services().end());
diff --git a/bta/test/gatt/database_test.cc b/bta/test/gatt/database_test.cc
index 822f3ca4c..78250ecd7 100644
--- a/bta/test/gatt/database_test.cc
+++ b/bta/test/gatt/database_test.cc
@@ -33,8 +33,6 @@ const Uuid PRIMARY_SERVICE = Uuid::From16Bit(GATT_UUID_PRI_SERVICE);
const Uuid SECONDARY_SERVICE = Uuid::From16Bit(GATT_UUID_SEC_SERVICE);
const Uuid INCLUDE = Uuid::From16Bit(GATT_UUID_INCLUDE_SERVICE);
const Uuid CHARACTERISTIC = Uuid::From16Bit(GATT_UUID_CHAR_DECLARE);
-const Uuid CHARACTERISTIC_EXTENDED_PROPERTIES =
- Uuid::From16Bit(GATT_UUID_CHAR_EXT_PROP);
Uuid SERVICE_1_UUID = Uuid::FromString("1800");
Uuid SERVICE_2_UUID = Uuid::FromString("1801");
@@ -51,10 +49,6 @@ TEST(GattDatabaseTest, serialize_deserialize_binary_test) {
builder.AddIncludedService(0x0002, SERVICE_2_UUID, 0x0010, 0x001f);
builder.AddCharacteristic(0x0003, 0x0004, SERVICE_1_CHAR_1_UUID, 0x02);
builder.AddDescriptor(0x0005, SERVICE_1_CHAR_1_DESC_1_UUID);
- builder.AddDescriptor(0x0006, CHARACTERISTIC_EXTENDED_PROPERTIES);
-
- // Set value of only «Characteristic Extended Properties» descriptor
- builder.SetValueOfDescriptors({0x0001});
Database db = builder.Build();
std::vector<StoredAttribute> serialized = db.Serialize();
@@ -88,11 +82,6 @@ TEST(GattDatabaseTest, serialize_deserialize_binary_test) {
// Descriptor
EXPECT_EQ(serialized[4].handle, 0x0005);
EXPECT_EQ(serialized[4].type, SERVICE_1_CHAR_1_DESC_1_UUID);
-
- // Characteristic Extended Properties Descriptor
- EXPECT_EQ(serialized[5].handle, 0x0006);
- EXPECT_EQ(serialized[5].type, CHARACTERISTIC_EXTENDED_PROPERTIES);
- EXPECT_EQ(serialized[5].value.characteristic_extended_properties, 0x0001);
}
/* This test makes sure that Service represented in StoredAttribute have proper
@@ -159,8 +148,8 @@ TEST(GattCacheTest, stored_attribute_to_binary_included_service_test) {
EXPECT_EQ(memcmp(binary_form, &attr, len), 0);
}
-/* This test makes sure that «Characteristic Extended Properties» descriptor
- * represented in StoredAttribute have proper binary format. */
+/* This test makes sure that Characteristic represented in StoredAttribute have
+ * proper binary format. */
TEST(GattCacheTest, stored_attribute_to_binary_characteristic_test) {
StoredAttribute attr;
@@ -215,72 +204,4 @@ TEST(GattCacheTest, stored_attribute_to_binary_descriptor_test) {
// LOG(ERROR) << " " << base::HexEncode(&attr, len);
EXPECT_EQ(memcmp(binary_form, &attr, len), 0);
}
-
-// Example from Bluetooth SPEC V5.2, Vol 3, Part G, APPENDIX B
-TEST(GattDatabaseTest, hash_test) {
- DatabaseBuilder builder;
- builder.AddService(0x0001, 0x0005, Uuid::From16Bit(0x1800), true);
- builder.AddService(0x0006, 0x000D, Uuid::From16Bit(0x1801), true);
- builder.AddService(0x000E, 0x0013, Uuid::From16Bit(0x1808), true);
- builder.AddService(0x0014, 0xFFFF, Uuid::From16Bit(0x180F), false);
-
- builder.AddCharacteristic(0x0002, 0x0003, Uuid::From16Bit(0x2A00), 0x0A);
- builder.AddCharacteristic(0x0004, 0x0005, Uuid::From16Bit(0x2A01), 0x02);
-
- builder.AddCharacteristic(0x0007, 0x0008, Uuid::From16Bit(0x2A05), 0x20);
- builder.AddDescriptor(0x0009, Uuid::From16Bit(0x2902));
- builder.AddCharacteristic(0x000A, 0x000B, Uuid::From16Bit(0x2B29), 0x0A);
- builder.AddCharacteristic(0x000C, 0x000D, Uuid::From16Bit(0x2B2A), 0x02);
-
- builder.AddIncludedService(0x000F, Uuid::From16Bit(0x180F), 0x0014, 0x0016);
- builder.AddCharacteristic(0x0010, 0x0011, Uuid::From16Bit(0x2A18), 0xA2);
- builder.AddDescriptor(0x0012, Uuid::From16Bit(0x2902));
- builder.AddDescriptor(0x0013, Uuid::From16Bit(0x2900));
-
- builder.AddCharacteristic(0x0015, 0x0016, Uuid::From16Bit(0x2A19), 0x02);
-
- // set characteristic extended properties descriptor values
- std::vector<uint16_t> descriptorValues = {0x0000};
- builder.SetValueOfDescriptors(descriptorValues);
-
- Database db = builder.Build();
-
- // Big endian example from Bluetooth SPEC V5.2, Vol 3, Part G, APPENDIX B
- Octet16 expected_hash{0xF1, 0xCA, 0x2D, 0x48, 0xEC, 0xF5, 0x8B, 0xAC,
- 0x8A, 0x88, 0x30, 0xBB, 0xB9, 0xFB, 0xA9, 0x90};
-
- Octet16 hash = db.Hash();
- // Convert output hash from little endian to big endian
- std::reverse(hash.begin(), hash.end());
-
- EXPECT_EQ(hash, expected_hash);
-}
-
-/* This test makes sure that Descriptor represented in StoredAttribute have
- * proper binary format. */
-TEST(GattCacheTest,
- stored_attribute_to_binary_characteristic_extended_properties_test) {
- StoredAttribute attr;
-
- /* make sure padding at end of union is cleared */
- memset(&attr, 0, sizeof(attr));
-
- attr = {.handle = 0x0003,
- .type = Uuid::FromString("2900"),
- .value = {.characteristic_extended_properties = 0x0001}};
-
- constexpr size_t len = sizeof(StoredAttribute);
- // clang-format off
- uint8_t binary_form[len] = {
- /*handle */ 0x03, 0x00,
- /* type */ 0x00, 0x00, 0x29, 0x00, 0x00, 0x00, 0x10, 0x00, 0x80, 0x00, 0x00, 0x80, 0x5F, 0x9B, 0x34, 0xFB,
- /* characteristic extended properties */ 0x01, 0x00,
- /* clear padding */ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00};
- // clang-format on
-
- // useful for debugging:
- // LOG(ERROR) << " " << base::HexEncode(&attr, len);
- EXPECT_EQ(memcmp(binary_form, &attr, len), 0);
-}
-} // namespace gatt
+} // namespace gatt \ No newline at end of file
diff --git a/bta/vc/device.cc b/bta/vc/device.cc
deleted file mode 100644
index 9e059e781..000000000
--- a/bta/vc/device.cc
+++ /dev/null
@@ -1,245 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <map>
-#include <vector>
-
-#include "bta_gatt_api.h"
-#include "bta_gatt_queue.h"
-#include "devices.h"
-#include "gatt_api.h"
-#include "stack/btm/btm_sec.h"
-
-using namespace bluetooth::vc::internal;
-
-void VolumeControlDevice::Disconnect(tGATT_IF gatt_if) {
- LOG(INFO) << __func__ << ": " << this->ToString();
-
- if (IsConnected()) {
- if (volume_state_handle != 0)
- BTA_GATTC_DeregisterForNotifications(gatt_if, address,
- volume_state_handle);
-
- if (volume_flags_handle != 0)
- BTA_GATTC_DeregisterForNotifications(gatt_if, address,
- volume_flags_handle);
-
- BtaGattQueue::Clean(connection_id);
- BTA_GATTC_Close(connection_id);
- connection_id = GATT_INVALID_CONN_ID;
- } else {
- BTA_GATTC_CancelOpen(gatt_if, address, false);
- }
-
- device_ready = false;
- handles_pending.clear();
-}
-
-/*
- * Find the handle for the client characteristics configuration of a given
- * characteristics
- */
-uint16_t VolumeControlDevice::find_ccc_handle(uint16_t chrc_handle) {
- const gatt::Characteristic* p_char =
- BTA_GATTC_GetCharacteristic(connection_id, chrc_handle);
- if (!p_char) {
- LOG(WARNING) << __func__ << ": no such handle=" << loghex(chrc_handle);
- return 0;
- }
-
- for (const gatt::Descriptor& desc : p_char->descriptors) {
- if (desc.uuid == Uuid::From16Bit(GATT_UUID_CHAR_CLIENT_CONFIG))
- return desc.handle;
- }
-
- return 0;
-}
-
-bool VolumeControlDevice::set_volume_control_service_handles(
- const gatt::Service& service) {
- uint16_t state_handle = 0, state_ccc_handle = 0, control_point_handle = 0,
- flags_handle = 0, flags_ccc_handle = 0;
-
- for (const gatt::Characteristic& chrc : service.characteristics) {
- if (chrc.uuid == kVolumeControlStateUuid) {
- state_handle = chrc.value_handle;
- state_ccc_handle = find_ccc_handle(chrc.value_handle);
- } else if (chrc.uuid == kVolumeControlPointUuid) {
- control_point_handle = chrc.value_handle;
- } else if (chrc.uuid == kVolumeFlagsUuid) {
- flags_handle = chrc.value_handle;
- flags_ccc_handle = find_ccc_handle(chrc.value_handle);
- } else {
- LOG(WARNING) << __func__ << ": unknown characteristic=" << chrc.uuid;
- }
- }
-
- // Validate service handles
- if (GATT_HANDLE_IS_VALID(state_handle) &&
- GATT_HANDLE_IS_VALID(state_ccc_handle) &&
- GATT_HANDLE_IS_VALID(control_point_handle) &&
- GATT_HANDLE_IS_VALID(flags_handle)
- /* volume_flags_ccc_handle is optional */) {
- volume_state_handle = state_handle;
- volume_state_ccc_handle = state_ccc_handle;
- volume_control_point_handle = control_point_handle;
- volume_flags_handle = flags_handle;
- volume_flags_ccc_handle = flags_ccc_handle;
- return true;
- }
-
- return false;
-}
-
-bool VolumeControlDevice::UpdateHandles(void) {
- ResetHandles();
-
- bool vcs_found = false;
- const std::list<gatt::Service>* services =
- BTA_GATTC_GetServices(connection_id);
- if (services == nullptr) {
- LOG(ERROR) << "No services found";
- return false;
- }
-
- for (auto const& service : *services) {
- if (service.uuid == kVolumeControlUuid) {
- LOG(INFO) << "Found VCS, handle=" << loghex(service.handle);
- vcs_found = set_volume_control_service_handles(service);
- if (!vcs_found) break;
- }
- }
-
- return vcs_found;
-}
-
-void VolumeControlDevice::ResetHandles(void) {
- device_ready = false;
-
- // the handles are not valid, so discard pending GATT operations
- BtaGattQueue::Clean(connection_id);
-
- volume_state_handle = 0;
- volume_state_ccc_handle = 0;
- volume_control_point_handle = 0;
- volume_flags_handle = 0;
- volume_flags_ccc_handle = 0;
-}
-
-void VolumeControlDevice::ControlPointOperation(uint8_t opcode,
- const std::vector<uint8_t>* arg,
- GATT_WRITE_OP_CB cb,
- void* cb_data) {
- std::vector<uint8_t> set_value({opcode, change_counter});
- if (arg != nullptr)
- set_value.insert(set_value.end(), (*arg).begin(), (*arg).end());
-
- BtaGattQueue::WriteCharacteristic(connection_id, volume_control_point_handle,
- set_value, GATT_WRITE, cb, cb_data);
-}
-
-bool VolumeControlDevice::subscribe_for_notifications(tGATT_IF gatt_if,
- uint16_t handle,
- uint16_t ccc_handle,
- GATT_WRITE_OP_CB cb) {
- tGATT_STATUS status =
- BTA_GATTC_RegisterForNotifications(gatt_if, address, handle);
- if (status != GATT_SUCCESS) {
- LOG(ERROR) << __func__ << ": failed, status=" << loghex(+status);
- return false;
- }
-
- std::vector<uint8_t> value(2);
- uint8_t* ptr = value.data();
- UINT16_TO_STREAM(ptr, GATT_CHAR_CLIENT_CONFIG_NOTIFICATION);
- BtaGattQueue::WriteDescriptor(connection_id, ccc_handle, std::move(value),
- GATT_WRITE, cb, nullptr);
-
- return true;
-}
-
-/**
- * Enqueue GATT requests that are required by the Volume Control to be
- * functional. This includes State characteristics read and subscription.
- * Those characteristics contain the change counter needed to send any request
- * via Control Point. Once completed successfully, the device can be stored
- * and reported as connected. In each case we subscribe first to be sure we do
- * not miss any value change.
- */
-bool VolumeControlDevice::EnqueueInitialRequests(
- tGATT_IF gatt_if, GATT_READ_OP_CB chrc_read_cb,
- GATT_WRITE_OP_CB cccd_write_cb) {
- handles_pending.clear();
- handles_pending.insert(volume_state_handle);
- handles_pending.insert(volume_state_ccc_handle);
- if (!subscribe_for_notifications(gatt_if, volume_state_handle,
- volume_state_ccc_handle, cccd_write_cb)) {
- return false;
- }
-
- BtaGattQueue::ReadCharacteristic(connection_id, volume_state_handle,
- chrc_read_cb, nullptr);
-
- return true;
-}
-
-/**
- * Enqueue the remaining requests. Those are not so crucial and can be done
- * once Volume Control instance indicates it's readiness to profile.
- * This includes characteristics read and subscription.
- * In each case we subscribe first to be sure we do not miss any value change.
- */
-void VolumeControlDevice::EnqueueRemainingRequests(
- tGATT_IF gatt_if, GATT_READ_OP_CB chrc_read_cb,
- GATT_WRITE_OP_CB cccd_write_cb) {
- std::map<uint16_t, uint16_t> handle_pairs{
- {volume_flags_handle, volume_flags_ccc_handle},
- };
-
- for (auto const& handles : handle_pairs) {
- if (GATT_HANDLE_IS_VALID(handles.second)) {
- subscribe_for_notifications(gatt_if, handles.first, handles.second,
- cccd_write_cb);
- }
-
- BtaGattQueue::ReadCharacteristic(connection_id, handles.first, chrc_read_cb,
- nullptr);
- }
-}
-
-bool VolumeControlDevice::VerifyReady(uint16_t handle) {
- handles_pending.erase(handle);
- device_ready = handles_pending.size() == 0;
- return device_ready;
-}
-
-bool VolumeControlDevice::IsEncryptionEnabled() {
- uint8_t sec_flag = 0;
- bool device_found =
- BTM_GetSecurityFlagsByTransport(address, &sec_flag, BT_TRANSPORT_LE);
- LOG(INFO) << __func__ << ": found=" << static_cast<int>(device_found)
- << " sec_flag=" << loghex(sec_flag);
- return device_found && (sec_flag & BTM_SEC_FLAG_ENCRYPTED);
-}
-
-bool VolumeControlDevice::EnableEncryption(tBTM_SEC_CALLBACK* callback) {
- int result = BTM_SetEncryption(address, BT_TRANSPORT_LE, callback, nullptr,
- BTM_BLE_SEC_ENCRYPT);
- LOG(INFO) << __func__ << ": result=" << +result;
- // TODO: should we care about the result??
- return true;
-}
diff --git a/bta/vc/devices.h b/bta/vc/devices.h
deleted file mode 100644
index 71dc6c9e0..000000000
--- a/bta/vc/devices.h
+++ /dev/null
@@ -1,192 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include <unordered_set>
-#include <vector>
-
-#include "bta/include/bta_gatt_api.h"
-#include "bta/vc/types.h"
-#include "include/hardware/bt_vc.h"
-#include "types/raw_address.h"
-
-namespace bluetooth {
-namespace vc {
-namespace internal {
-
-class VolumeControlDevice {
- public:
- RawAddress address;
- /* This is true only during first connection to profile, until we store the
- * device
- */
- bool first_connection;
-
- /* we are making active attempt to connect to this device, 'direct connect'.
- * This is true only during initial phase of first connection. */
- bool connecting_actively;
-
- bool service_changed_rcvd;
-
- uint8_t volume;
- uint8_t change_counter;
- bool mute;
- uint8_t flags;
-
- uint16_t connection_id;
-
- /* Volume Control Service */
- uint16_t volume_state_handle;
- uint16_t volume_state_ccc_handle;
- uint16_t volume_control_point_handle;
- uint16_t volume_flags_handle;
- uint16_t volume_flags_ccc_handle;
-
- bool device_ready; /* Set when device read server status and registgered for
- notifications */
-
- VolumeControlDevice(const RawAddress& address, bool first_connection)
- : address(address),
- first_connection(first_connection),
- connecting_actively(first_connection),
- service_changed_rcvd(false),
- volume(0),
- change_counter(0),
- mute(false),
- flags(0),
- connection_id(GATT_INVALID_CONN_ID),
- volume_state_handle(0),
- volume_state_ccc_handle(0),
- volume_control_point_handle(0),
- volume_flags_handle(0),
- volume_flags_ccc_handle(0),
- device_ready(false) {}
-
- ~VolumeControlDevice() = default;
-
- inline std::string ToString() { return address.ToString(); }
-
- void DebugDump(int fd) { dprintf(fd, "%s\n", this->ToString().c_str()); }
-
- bool IsConnected() { return connection_id != GATT_INVALID_CONN_ID; }
-
- void Disconnect(tGATT_IF gatt_if);
-
- bool UpdateHandles(void);
-
- void ResetHandles(void);
-
- bool HasHandles(void) { return GATT_HANDLE_IS_VALID(volume_state_handle); }
-
- void ControlPointOperation(uint8_t opcode, const std::vector<uint8_t>* arg,
- GATT_WRITE_OP_CB cb, void* cb_data);
- bool IsEncryptionEnabled();
-
- bool EnableEncryption(tBTM_SEC_CALLBACK* callback);
-
- bool EnqueueInitialRequests(tGATT_IF gatt_if, GATT_READ_OP_CB chrc_read_cb,
- GATT_WRITE_OP_CB cccd_write_cb);
- void EnqueueRemainingRequests(tGATT_IF gatt_if, GATT_READ_OP_CB chrc_read_cb,
- GATT_WRITE_OP_CB cccd_write_cb);
- bool VerifyReady(uint16_t handle);
-
- private:
- /*
- * This is used to track the pending GATT operation handles. Once the list is
- * empty the device is assumed ready and connected. We are doing it because we
- * want to make sure all the required characteristics and descritors are
- * available on server side.
- */
- std::unordered_set<uint16_t> handles_pending;
-
- uint16_t find_ccc_handle(uint16_t chrc_handle);
- bool set_volume_control_service_handles(const gatt::Service& service);
- bool subscribe_for_notifications(tGATT_IF gatt_if, uint16_t handle,
- uint16_t ccc_handle, GATT_WRITE_OP_CB cb);
-};
-
-class VolumeControlDevices {
- public:
- void Add(const RawAddress& address, bool first_connection) {
- if (FindByAddress(address) != nullptr) return;
-
- devices_.emplace_back(address, first_connection);
- }
-
- void Remove(const RawAddress& address) {
- for (auto it = devices_.begin(); it != devices_.end(); it++) {
- if (it->address == address) {
- it = devices_.erase(it);
- break;
- }
- }
- }
-
- VolumeControlDevice* FindByAddress(const RawAddress& address) {
- auto iter = std::find_if(devices_.begin(), devices_.end(),
- [&address](const VolumeControlDevice& device) {
- return device.address == address;
- });
-
- return (iter == devices_.end()) ? nullptr : &(*iter);
- }
-
- VolumeControlDevice* FindByConnId(uint16_t connection_id) {
- auto iter =
- std::find_if(devices_.begin(), devices_.end(),
- [&connection_id](const VolumeControlDevice& device) {
- return device.connection_id == connection_id;
- });
-
- return (iter == devices_.end()) ? nullptr : &(*iter);
- }
-
- size_t Size() { return (devices_.size()); }
-
- void Clear() { devices_.clear(); }
-
- void DebugDump(int fd) {
- for (auto& device : devices_) {
- device.DebugDump(fd);
- }
- }
-
- void Disconnect(tGATT_IF gatt_if) {
- for (auto& device : devices_) {
- device.Disconnect(gatt_if);
- }
- }
-
- void ControlPointOperation(std::vector<RawAddress>& devices, uint8_t opcode,
- const std::vector<uint8_t>* arg,
- GATT_WRITE_OP_CB cb, void* cb_data) {
- for (auto& addr : devices) {
- VolumeControlDevice* device = FindByAddress(addr);
- if (device && device->IsConnected())
- device->ControlPointOperation(opcode, arg, cb, cb_data);
- }
- }
-
- private:
- std::vector<VolumeControlDevice> devices_;
-};
-
-} // namespace internal
-} // namespace vc
-} // namespace bluetooth
diff --git a/bta/vc/devices_test.cc b/bta/vc/devices_test.cc
deleted file mode 100644
index e1fb3d4ec..000000000
--- a/bta/vc/devices_test.cc
+++ /dev/null
@@ -1,470 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "devices.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include <map>
-
-#include "bta_gatt_api_mock.h"
-#include "bta_gatt_queue_mock.h"
-#include "btm_api_mock.h"
-#include "gatt/database_builder.h"
-
-namespace bluetooth {
-namespace vc {
-namespace internal {
-
-using ::testing::_;
-using ::testing::DoAll;
-using ::testing::Invoke;
-using ::testing::Mock;
-using ::testing::Return;
-using ::testing::SetArgPointee;
-using ::testing::Test;
-
-RawAddress GetTestAddress(int index) {
- CHECK_LT(index, UINT8_MAX);
- RawAddress result = {
- {0xC0, 0xDE, 0xC0, 0xDE, 0x00, static_cast<uint8_t>(index)}};
- return result;
-}
-
-class VolumeControlDevicesTest : public ::testing::Test {
- protected:
- void SetUp() override {
- devices_ = new VolumeControlDevices();
- gatt::SetMockBtaGattInterface(&gatt_interface);
- gatt::SetMockBtaGattQueue(&gatt_queue);
- }
-
- void TearDown() override {
- gatt::SetMockBtaGattQueue(nullptr);
- gatt::SetMockBtaGattInterface(nullptr);
- delete devices_;
- }
-
- VolumeControlDevices* devices_ = nullptr;
- gatt::MockBtaGattInterface gatt_interface;
- gatt::MockBtaGattQueue gatt_queue;
-};
-
-TEST_F(VolumeControlDevicesTest, test_add) {
- RawAddress test_address_0 = GetTestAddress(0);
- ASSERT_EQ((size_t)0, devices_->Size());
- devices_->Add(test_address_0, true);
- ASSERT_EQ((size_t)1, devices_->Size());
-}
-
-TEST_F(VolumeControlDevicesTest, test_add_twice) {
- RawAddress test_address_0 = GetTestAddress(0);
- ASSERT_EQ((size_t)0, devices_->Size());
- devices_->Add(test_address_0, true);
- devices_->Add(test_address_0, true);
- ASSERT_EQ((size_t)1, devices_->Size());
-}
-
-TEST_F(VolumeControlDevicesTest, test_remove) {
- RawAddress test_address_0 = GetTestAddress(0);
- RawAddress test_address_1 = GetTestAddress(1);
- devices_->Add(test_address_0, true);
- devices_->Add(test_address_1, true);
- ASSERT_EQ((size_t)2, devices_->Size());
- devices_->Remove(test_address_0);
- ASSERT_EQ((size_t)1, devices_->Size());
-}
-
-TEST_F(VolumeControlDevicesTest, test_clear) {
- RawAddress test_address_0 = GetTestAddress(0);
- ASSERT_EQ((size_t)0, devices_->Size());
- devices_->Add(test_address_0, true);
- ASSERT_EQ((size_t)1, devices_->Size());
- devices_->Clear();
- ASSERT_EQ((size_t)0, devices_->Size());
-}
-
-TEST_F(VolumeControlDevicesTest, test_find_by_address) {
- RawAddress test_address_0 = GetTestAddress(0);
- RawAddress test_address_1 = GetTestAddress(1);
- RawAddress test_address_2 = GetTestAddress(2);
- devices_->Add(test_address_0, true);
- devices_->Add(test_address_1, false);
- devices_->Add(test_address_2, true);
- VolumeControlDevice* device = devices_->FindByAddress(test_address_1);
- ASSERT_NE(nullptr, device);
- ASSERT_EQ(test_address_1, device->address);
-}
-
-TEST_F(VolumeControlDevicesTest, test_find_by_conn_id) {
- RawAddress test_address_0 = GetTestAddress(0);
- devices_->Add(test_address_0, true);
- VolumeControlDevice* test_device = devices_->FindByAddress(test_address_0);
- test_device->connection_id = 0x0005;
- ASSERT_NE(nullptr, devices_->FindByConnId(test_device->connection_id));
-}
-
-TEST_F(VolumeControlDevicesTest, test_disconnect) {
- RawAddress test_address_0 = GetTestAddress(0);
- RawAddress test_address_1 = GetTestAddress(1);
- devices_->Add(test_address_0, true);
- devices_->Add(test_address_1, true);
- VolumeControlDevice* test_device_0 = devices_->FindByAddress(test_address_0);
- test_device_0->connection_id = 0x0005;
- tGATT_IF gatt_if = 8;
- EXPECT_CALL(gatt_interface, Close(test_device_0->connection_id));
- EXPECT_CALL(gatt_interface, CancelOpen(gatt_if, test_address_1, _));
- devices_->Disconnect(gatt_if);
-}
-
-TEST_F(VolumeControlDevicesTest, test_control_point_operation) {
- uint8_t opcode = 50;
- std::vector<RawAddress> devices;
-
- for (int i = 5; i > 0; i--) {
- RawAddress test_address = GetTestAddress(i);
- devices.push_back(test_address);
- uint8_t change_counter = 10 * i;
- uint16_t control_point_handle = 0x0020 + i;
- uint16_t connection_id = i;
- devices_->Add(test_address, true);
- VolumeControlDevice* device = devices_->FindByAddress(test_address);
- device->connection_id = connection_id;
- device->change_counter = change_counter;
- device->volume_control_point_handle = control_point_handle;
- std::vector<uint8_t> data_expected({opcode, change_counter});
-
- EXPECT_CALL(gatt_queue,
- WriteCharacteristic(connection_id, control_point_handle,
- data_expected, GATT_WRITE, _, _));
- }
-
- const std::vector<uint8_t>* arg = nullptr;
- GATT_WRITE_OP_CB cb = nullptr;
- void* cb_data = nullptr;
- devices_->ControlPointOperation(devices, opcode, arg, cb, cb_data);
-}
-
-TEST_F(VolumeControlDevicesTest, test_control_point_operation_args) {
- uint8_t opcode = 60;
- uint8_t arg_1 = 0x02;
- uint8_t arg_2 = 0x05;
- std::vector<RawAddress> devices;
-
- for (int i = 5; i > 0; i--) {
- RawAddress test_address = GetTestAddress(i);
- devices.push_back(test_address);
- uint8_t change_counter = 10 * i;
- uint16_t control_point_handle = 0x0020 + i;
- uint16_t connection_id = i;
- devices_->Add(test_address, true);
- VolumeControlDevice* device = devices_->FindByAddress(test_address);
- device->connection_id = connection_id;
- device->change_counter = change_counter;
- device->volume_control_point_handle = control_point_handle;
- std::vector<uint8_t> data_expected({opcode, change_counter, arg_1, arg_2});
-
- EXPECT_CALL(gatt_queue,
- WriteCharacteristic(connection_id, control_point_handle,
- data_expected, GATT_WRITE, _, _));
- }
-
- std::vector<uint8_t> arg({arg_1, arg_2});
- GATT_WRITE_OP_CB cb = nullptr;
- void* cb_data = nullptr;
- devices_->ControlPointOperation(devices, opcode, &arg, cb, cb_data);
-}
-
-TEST_F(VolumeControlDevicesTest, test_control_point_skip_not_connected) {
- RawAddress test_address = GetTestAddress(1);
- devices_->Add(test_address, true);
- VolumeControlDevice* device = devices_->FindByAddress(test_address);
- device->connection_id = GATT_INVALID_CONN_ID;
- uint16_t control_point_handle = 0x0020;
- device->volume_control_point_handle = control_point_handle;
-
- EXPECT_CALL(gatt_queue,
- WriteCharacteristic(_, control_point_handle, _, _, _, _))
- .Times(0);
-
- uint8_t opcode = 5;
- std::vector<RawAddress> devices = {test_address};
- const std::vector<uint8_t>* arg = nullptr;
- GATT_WRITE_OP_CB cb = nullptr;
- void* cb_data = nullptr;
- devices_->ControlPointOperation(devices, opcode, arg, cb, cb_data);
-}
-
-class VolumeControlDeviceTest : public ::testing::Test {
- protected:
- void SetUp() override {
- device = new VolumeControlDevice(GetTestAddress(1), true);
- gatt::SetMockBtaGattInterface(&gatt_interface);
- gatt::SetMockBtaGattQueue(&gatt_queue);
- bluetooth::manager::SetMockBtmInterface(&btm_interface);
-
- ON_CALL(gatt_interface, GetCharacteristic(_, _))
- .WillByDefault(
- Invoke([&](uint16_t conn_id,
- uint16_t handle) -> const gatt::Characteristic* {
- for (auto const& service : services) {
- for (auto const& characteristic : service.characteristics) {
- if (characteristic.value_handle == handle) {
- return &characteristic;
- }
- }
- }
-
- return nullptr;
- }));
-
- ON_CALL(gatt_interface, GetOwningService(_, _))
- .WillByDefault(Invoke(
- [&](uint16_t conn_id, uint16_t handle) -> const gatt::Service* {
- for (auto const& service : services) {
- if (service.handle <= handle && service.end_handle >= handle) {
- return &service;
- }
- }
-
- return nullptr;
- }));
-
- ON_CALL(gatt_interface, GetServices(_)).WillByDefault(Return(&services));
- }
-
- void TearDown() override {
- bluetooth::manager::SetMockBtmInterface(nullptr);
- gatt::SetMockBtaGattQueue(nullptr);
- gatt::SetMockBtaGattInterface(nullptr);
- delete device;
- }
-
- /* sample database 1xVCS, 2xAICS, 2xVOCS */
- void SetSampleDatabase1(void) {
- gatt::DatabaseBuilder builder;
- builder.AddService(0x0001, 0x0016, kVolumeControlUuid, true);
- builder.AddCharacteristic(
- 0x0010, 0x0011, kVolumeControlStateUuid,
- GATT_CHAR_PROP_BIT_READ | GATT_CHAR_PROP_BIT_NOTIFY);
- builder.AddDescriptor(0x0012,
- Uuid::From16Bit(GATT_UUID_CHAR_CLIENT_CONFIG));
- builder.AddCharacteristic(0x0013, 0x0014, kVolumeControlPointUuid,
- GATT_CHAR_PROP_BIT_WRITE);
- builder.AddCharacteristic(0x0015, 0x0016, kVolumeFlagsUuid,
- GATT_CHAR_PROP_BIT_READ);
- builder.AddService(0x00a0, 0x00a3,
- Uuid::From16Bit(UUID_SERVCLASS_GATT_SERVER), true);
- builder.AddCharacteristic(0x00a1, 0x00a2,
- Uuid::From16Bit(GATT_UUID_GATT_SRV_CHGD),
- GATT_CHAR_PROP_BIT_NOTIFY);
- builder.AddDescriptor(0x00a3,
- Uuid::From16Bit(GATT_UUID_CHAR_CLIENT_CONFIG));
- services = builder.Build().Services();
- ASSERT_EQ(true, device->UpdateHandles());
- }
-
- /* sample database no VCS */
- void SetSampleDatabase2(void) {
- gatt::DatabaseBuilder builder;
- builder.AddService(0x0001, 0x0003, Uuid::From16Bit(0x1800), true);
- builder.AddCharacteristic(0x0002, 0x0003, Uuid::From16Bit(0x2a00),
- GATT_CHAR_PROP_BIT_READ);
- services = builder.Build().Services();
- ASSERT_EQ(false, device->UpdateHandles());
- }
-
- VolumeControlDevice* device = nullptr;
- gatt::MockBtaGattInterface gatt_interface;
- gatt::MockBtaGattQueue gatt_queue;
- bluetooth::manager::MockBtmInterface btm_interface;
- std::list<gatt::Service> services;
-};
-
-TEST_F(VolumeControlDeviceTest, test_service_volume_control_not_found) {
- SetSampleDatabase2();
- ASSERT_EQ(false, device->HasHandles());
-}
-
-TEST_F(VolumeControlDeviceTest, test_service_volume_control_incomplete) {
- gatt::DatabaseBuilder builder;
- builder.AddService(0x0001, 0x0006, kVolumeControlUuid, true);
- builder.AddCharacteristic(
- 0x0002, 0x0003, kVolumeControlStateUuid,
- GATT_CHAR_PROP_BIT_READ | GATT_CHAR_PROP_BIT_NOTIFY);
- builder.AddDescriptor(0x0004, Uuid::From16Bit(GATT_UUID_CHAR_CLIENT_CONFIG));
- builder.AddCharacteristic(0x0005, 0x0006, kVolumeControlPointUuid,
- GATT_CHAR_PROP_BIT_WRITE);
- /* no Volume Control Flags characteristic */
- services = builder.Build().Services();
- ASSERT_EQ(false, device->UpdateHandles());
- ASSERT_EQ(0x0000, device->volume_state_handle);
- ASSERT_EQ(0x0000, device->volume_state_ccc_handle);
- ASSERT_EQ(0x0000, device->volume_control_point_handle);
- ASSERT_EQ(0x0000, device->volume_flags_handle);
- ASSERT_EQ(0x0000, device->volume_flags_ccc_handle);
- ASSERT_EQ(false, device->HasHandles());
-}
-
-TEST_F(VolumeControlDeviceTest, test_services_changed) {
- SetSampleDatabase1();
- ASSERT_NE(0, device->volume_state_handle);
- ASSERT_NE(0, device->volume_control_point_handle);
- ASSERT_NE(0, device->volume_flags_handle);
- ASSERT_EQ(true, device->HasHandles());
- SetSampleDatabase2();
- ASSERT_EQ(0, device->volume_state_handle);
- ASSERT_EQ(0, device->volume_control_point_handle);
- ASSERT_EQ(0, device->volume_flags_handle);
- ASSERT_EQ(false, device->HasHandles());
-}
-
-TEST_F(VolumeControlDeviceTest, test_enqueue_initial_requests) {
- SetSampleDatabase1();
-
- tGATT_IF gatt_if = 0x0001;
- std::vector<uint8_t> register_for_notification_data({0x01, 0x00});
-
- std::map<uint16_t, uint16_t> expected_to_read_write{
- {0x0011, 0x0012} /* volume control state */};
-
- for (auto const& handle_pair : expected_to_read_write) {
- EXPECT_CALL(gatt_queue, ReadCharacteristic(_, handle_pair.first, _, _));
- EXPECT_CALL(gatt_queue, WriteDescriptor(_, handle_pair.second,
- register_for_notification_data,
- GATT_WRITE, _, _));
- EXPECT_CALL(gatt_interface,
- RegisterForNotifications(gatt_if, _, handle_pair.first));
- }
-
- auto chrc_read_cb = [](uint16_t conn_id, tGATT_STATUS status, uint16_t handle,
- uint16_t len, uint8_t* value, void* data) {};
- auto cccd_write_cb = [](uint16_t conn_id, tGATT_STATUS status,
- uint16_t handle, void* data) {};
- ASSERT_EQ(true, device->EnqueueInitialRequests(gatt_if, chrc_read_cb,
- cccd_write_cb));
-};
-
-TEST_F(VolumeControlDeviceTest, test_device_ready) {
- SetSampleDatabase1();
-
- // grab all the handles requested
- std::vector<uint16_t> requested_handles;
- ON_CALL(gatt_queue, WriteDescriptor(_, _, _, _, _, _))
- .WillByDefault(Invoke(
- [&requested_handles](
- uint16_t conn_id, uint16_t handle, std::vector<uint8_t> value,
- tGATT_WRITE_TYPE write_type, GATT_WRITE_OP_CB cb,
- void* cb_data) -> void { requested_handles.push_back(handle); }));
- ON_CALL(gatt_queue, ReadCharacteristic(_, _, _, _))
- .WillByDefault(Invoke(
- [&requested_handles](uint16_t conn_id, uint16_t handle,
- GATT_READ_OP_CB cb, void* cb_data) -> void {
- requested_handles.push_back(handle);
- }));
-
- auto chrc_read_cb = [](uint16_t conn_id, tGATT_STATUS status, uint16_t handle,
- uint16_t len, uint8_t* value, void* data) {};
- auto cccd_write_cb = [](uint16_t conn_id, tGATT_STATUS status,
- uint16_t handle, void* data) {};
- ASSERT_EQ(true, device->EnqueueInitialRequests(0x0001, chrc_read_cb,
- cccd_write_cb));
- ASSERT_NE((size_t)0, requested_handles.size());
-
- // indicate non-pending requests
- ASSERT_EQ(false, device->device_ready);
- device->VerifyReady(0xffff);
-
- for (uint16_t handle : requested_handles) {
- ASSERT_EQ(false, device->device_ready);
- device->VerifyReady(handle);
- }
-
- ASSERT_EQ(true, device->device_ready);
-}
-
-TEST_F(VolumeControlDeviceTest, test_enqueue_remaining_requests) {
- SetSampleDatabase1();
-
- tGATT_IF gatt_if = 0x0001;
- std::vector<uint8_t> register_for_notification_data({0x01, 0x00});
-
- std::vector<uint16_t> expected_to_read{0x0016 /* volume flags */};
-
- std::map<uint16_t, uint16_t> expected_to_write_value_ccc_handle_map{};
-
- for (uint16_t handle : expected_to_read) {
- EXPECT_CALL(gatt_queue, ReadCharacteristic(_, handle, _, _));
- }
-
- for (auto const& handle_pair : expected_to_write_value_ccc_handle_map) {
- EXPECT_CALL(gatt_queue, WriteDescriptor(_, handle_pair.second,
- register_for_notification_data,
- GATT_WRITE, _, _));
- EXPECT_CALL(gatt_interface,
- RegisterForNotifications(gatt_if, _, handle_pair.first));
- }
-
- auto chrc_read_cb = [](uint16_t conn_id, tGATT_STATUS status, uint16_t handle,
- uint16_t len, uint8_t* value, void* data) {};
- auto cccd_write_cb = [](uint16_t conn_id, tGATT_STATUS status,
- uint16_t handle, void* data) {};
- device->EnqueueRemainingRequests(gatt_if, chrc_read_cb, cccd_write_cb);
-}
-
-TEST_F(VolumeControlDeviceTest, test_check_link_encrypted) {
- ON_CALL(btm_interface, GetSecurityFlagsByTransport(_, _, _))
- .WillByDefault(
- DoAll(SetArgPointee<1>(BTM_SEC_FLAG_ENCRYPTED), Return(true)));
- ASSERT_EQ(true, device->IsEncryptionEnabled());
-
- ON_CALL(btm_interface, GetSecurityFlagsByTransport(_, _, _))
- .WillByDefault(DoAll(SetArgPointee<1>(0), Return(false)));
- ASSERT_NE(true, device->IsEncryptionEnabled());
-
- ON_CALL(btm_interface, GetSecurityFlagsByTransport(_, _, _))
- .WillByDefault(DoAll(SetArgPointee<1>(0), Return(true)));
- ASSERT_NE(true, device->IsEncryptionEnabled());
-}
-
-TEST_F(VolumeControlDeviceTest, test_control_point_operation) {
- GATT_WRITE_OP_CB write_cb = [](uint16_t conn_id, tGATT_STATUS status,
- uint16_t handle, void* data) {};
- SetSampleDatabase1();
- device->change_counter = 0x01;
- std::vector<uint8_t> expected_data({0x03, 0x01});
- EXPECT_CALL(gatt_queue, WriteCharacteristic(_, 0x0014, expected_data,
- GATT_WRITE, write_cb, nullptr));
- device->ControlPointOperation(0x03, nullptr, write_cb, nullptr);
-}
-
-TEST_F(VolumeControlDeviceTest, test_control_point_operation_arg) {
- GATT_WRITE_OP_CB write_cb = [](uint16_t conn_id, tGATT_STATUS status,
- uint16_t handle, void* data) {};
- SetSampleDatabase1();
- device->change_counter = 0x55;
- std::vector<uint8_t> expected_data({0x01, 0x55, 0x02, 0x03});
- EXPECT_CALL(gatt_queue, WriteCharacteristic(_, 0x0014, expected_data,
- GATT_WRITE, write_cb, nullptr));
- std::vector<uint8_t> arg({0x02, 0x03});
- device->ControlPointOperation(0x01, &arg, write_cb, nullptr);
-}
-
-} // namespace internal
-} // namespace vc
-} // namespace bluetooth
diff --git a/bta/vc/types.h b/bta/vc/types.h
deleted file mode 100644
index 808df9ffa..000000000
--- a/bta/vc/types.h
+++ /dev/null
@@ -1,47 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <queue>
-#include <vector>
-
-#include "raw_address.h"
-
-namespace bluetooth {
-namespace vc {
-namespace internal {
-
-/* clang-format off */
-/* Volume control point opcodes */
-static constexpr uint8_t kControlPointOpcodeVolumeDown = 0x00;
-static constexpr uint8_t kControlPointOpcodeVolumeUp = 0x01;
-static constexpr uint8_t kControlPointOpcodeUnmuteVolumeDown = 0x02;
-static constexpr uint8_t kControlPointOpcodeUnmuteVolumeUp = 0x03;
-static constexpr uint8_t kControlPointOpcodeSetAbsoluteVolume = 0x04;
-static constexpr uint8_t kControlPointOpcodeUnmute = 0x05;
-static constexpr uint8_t kControlPointOpcodeMute = 0x06;
-
-static const Uuid kVolumeControlUuid = Uuid::From16Bit(0x1844);
-static const Uuid kVolumeControlStateUuid = Uuid::From16Bit(0x2B7D);
-static const Uuid kVolumeControlPointUuid = Uuid::From16Bit(0x2B7E);
-static const Uuid kVolumeFlagsUuid = Uuid::From16Bit(0x2B7F);
-/* clang-format on */
-
-} // namespace internal
-} // namespace vc
-} // namespace bluetooth
diff --git a/bta/vc/vc.cc b/bta/vc/vc.cc
deleted file mode 100644
index ee9461395..000000000
--- a/bta/vc/vc.cc
+++ /dev/null
@@ -1,574 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <base/bind.h>
-#include <base/bind_helpers.h>
-#include <base/logging.h>
-#include <base/strings/string_number_conversions.h>
-#include <hardware/bt_vc.h>
-
-#include <string>
-#include <vector>
-
-#include "bta_gatt_api.h"
-#include "bta_gatt_queue.h"
-#include "bta_vc_api.h"
-#include "btif_storage.h"
-#include "devices.h"
-
-using base::Closure;
-using bluetooth::Uuid;
-using bluetooth::vc::ConnectionState;
-using namespace bluetooth::vc::internal;
-
-namespace {
-class VolumeControlImpl;
-VolumeControlImpl* instance;
-
-/**
- * Overview:
- *
- * This is Volume Control Implementation class which realize Volume Control
- * Profile (VCP)
- *
- * Each connected peer device supporting Volume Control Service (VCS) is on the
- * list of devices (volume_control_devices_).
- *
- * Once all the mandatory characteristis for all the services are discovered,
- * Fluoride calls ON_CONNECTED callback.
- *
- * It is assumed that whenever application changes general audio options in this
- * profile e.g. Volume up/down, mute/unmute etc, profile configures all the
- * devices which are active Le Audio devices.
- *
- *
- */
-class VolumeControlImpl : public VolumeControl {
- public:
- ~VolumeControlImpl() override = default;
-
- VolumeControlImpl(bluetooth::vc::VolumeControlCallbacks* callbacks)
- : gatt_if_(0), callbacks_(callbacks) {
- BTA_GATTC_AppRegister(
- gattc_callback_static,
- base::Bind([](uint8_t client_id, uint8_t status) {
- if (status != GATT_SUCCESS) {
- LOG(ERROR) << "Can't start Volume Control profile - no gatt "
- "clients left!";
- return;
- }
- instance->gatt_if_ = client_id;
- }),
- true);
- }
-
- void Connect(const RawAddress& address) override {
- LOG(INFO) << __func__ << " " << address;
-
- auto device = volume_control_devices_.FindByAddress(address);
- if (!device) {
- volume_control_devices_.Add(address, true);
- } else {
- device->connecting_actively = true;
- }
-
- BTA_GATTC_Open(gatt_if_, address, true, false);
- }
-
- void AddFromStorage(const RawAddress& address, bool auto_connect) {
- LOG(INFO) << __func__ << " " << address
- << ", auto_connect=" << auto_connect;
-
- if (auto_connect) {
- volume_control_devices_.Add(address, false);
-
- /* Add device into BG connection to accept remote initiated connection */
- BTA_GATTC_Open(gatt_if_, address, false, false);
- }
- }
-
- void OnGattConnected(tGATT_STATUS status, uint16_t connection_id,
- tGATT_IF /*client_if*/, RawAddress address,
- tBT_TRANSPORT /*transport*/, uint16_t /*mtu*/) {
- LOG(INFO) << __func__ << ": address=" << address
- << ", connection_id=" << connection_id;
-
- VolumeControlDevice* device =
- volume_control_devices_.FindByAddress(address);
- if (!device) {
- LOG(ERROR) << __func__ << "Skipping unknown device, address=" << address;
- return;
- }
-
- if (status != GATT_SUCCESS) {
- LOG(INFO) << "Failed to connect to Volume Control device";
- device_cleanup_helper(device, device->connecting_actively);
- return;
- }
-
- device->connection_id = connection_id;
-
- if (device->IsEncryptionEnabled()) {
- OnEncryptionComplete(address, BTM_SUCCESS);
- return;
- }
-
- if (!device->EnableEncryption(enc_callback_static)) {
- device_cleanup_helper(device, device->connecting_actively);
- }
- }
-
- void OnEncryptionComplete(const RawAddress& address, uint8_t success) {
- VolumeControlDevice* device =
- volume_control_devices_.FindByAddress(address);
- if (!device) {
- LOG(ERROR) << __func__ << "Skipping unknown device" << address;
- return;
- }
-
- if (success != BTM_SUCCESS) {
- LOG(ERROR) << "encryption failed "
- << "status: " << int{success};
- // If the encryption failed, do not remove the device.
- // Disconnect only, since the Android will try to re-enable encryption
- // after disconnection
- device->Disconnect(gatt_if_);
- if (device->connecting_actively)
- callbacks_->OnConnectionState(ConnectionState::DISCONNECTED,
- device->address);
- return;
- }
-
- LOG(INFO) << __func__ << " " << address << "status: " << success;
-
- if (device->HasHandles()) {
- device->EnqueueInitialRequests(gatt_if_, chrc_read_callback_static,
- OnGattWriteCccStatic);
-
- } else {
- device->first_connection = true;
- BTA_GATTC_ServiceSearchRequest(device->connection_id,
- &kVolumeControlUuid);
- }
- }
-
- void OnServiceChangeEvent(const RawAddress& address) {
- VolumeControlDevice* device =
- volume_control_devices_.FindByAddress(address);
- if (!device) {
- LOG(ERROR) << __func__ << "Skipping unknown device" << address;
- return;
- }
- LOG(INFO) << __func__ << ": address=" << address;
- device->first_connection = true;
- device->service_changed_rcvd = true;
- BtaGattQueue::Clean(device->connection_id);
- }
-
- void OnServiceDiscDoneEvent(const RawAddress& address) {
- VolumeControlDevice* device =
- volume_control_devices_.FindByAddress(address);
- if (!device) {
- LOG(ERROR) << __func__ << "Skipping unknown device" << address;
- return;
- }
-
- if (device->service_changed_rcvd)
- BTA_GATTC_ServiceSearchRequest(device->connection_id,
- &kVolumeControlUuid);
- }
-
- void OnServiceSearchComplete(uint16_t connection_id, tGATT_STATUS status) {
- VolumeControlDevice* device =
- volume_control_devices_.FindByConnId(connection_id);
- if (!device) {
- LOG(ERROR) << __func__ << "Skipping unknown device, connection_id="
- << loghex(connection_id);
- return;
- }
-
- /* Known device, nothing to do */
- if (!device->first_connection) return;
-
- if (status != GATT_SUCCESS) {
- /* close connection and report service discovery complete with error */
- LOG(ERROR) << "Service discovery failed";
- device_cleanup_helper(device, device->first_connection);
- return;
- }
-
- bool success = device->UpdateHandles();
- if (!success) {
- LOG(ERROR) << "Incomplete service database";
- device_cleanup_helper(device, true);
- return;
- }
-
- device->EnqueueInitialRequests(gatt_if_, chrc_read_callback_static,
- OnGattWriteCccStatic);
- }
-
- void OnCharacteristicValueChanged(uint16_t conn_id, tGATT_STATUS status,
- uint16_t handle, uint16_t len,
- uint8_t* value, void* /* data */) {
- VolumeControlDevice* device = volume_control_devices_.FindByConnId(conn_id);
- if (!device) {
- LOG(INFO) << __func__ << ": unknown conn_id=" << loghex(conn_id);
- return;
- }
-
- if (status != GATT_SUCCESS) {
- LOG(INFO) << __func__ << ": status=" << static_cast<int>(status);
- return;
- }
-
- if (handle == device->volume_state_handle) {
- OnVolumeControlStateChanged(device, len, value);
- verify_device_ready(device, handle);
- return;
- }
- if (handle == device->volume_flags_handle) {
- OnVolumeControlFlagsChanged(device, len, value);
- verify_device_ready(device, handle);
- return;
- }
-
- LOG(ERROR) << __func__ << ": unknown handle=" << loghex(handle);
- }
-
- void OnNotificationEvent(uint16_t conn_id, uint16_t handle, uint16_t len,
- uint8_t* value) {
- LOG(INFO) << __func__ << ": handle=" << loghex(handle);
- OnCharacteristicValueChanged(conn_id, GATT_SUCCESS, handle, len, value,
- nullptr);
- }
-
- void VolumeControlReadCommon(uint16_t conn_id, uint16_t handle) {
- BtaGattQueue::ReadCharacteristic(conn_id, handle, chrc_read_callback_static,
- nullptr);
- }
-
- void OnVolumeControlStateChanged(VolumeControlDevice* device, uint16_t len,
- uint8_t* value) {
- if (len != 3) {
- LOG(INFO) << __func__ << ": malformed len=" << loghex(len);
- return;
- }
-
- uint8_t* pp = value;
- STREAM_TO_UINT8(device->volume, pp);
- STREAM_TO_UINT8(device->mute, pp);
- STREAM_TO_UINT8(device->change_counter, pp);
-
- LOG(INFO) << __func__ << " " << base::HexEncode(value, len);
- LOG(INFO) << __func__ << "volume " << loghex(device->volume) << "mute"
- << loghex(device->mute) << "change_counter"
- << loghex(device->change_counter);
-
- if (!device->device_ready) return;
-
- callbacks_->OnVolumeStateChanged(device->address, device->volume,
- device->mute);
- }
-
- void OnVolumeControlFlagsChanged(VolumeControlDevice* device, uint16_t len,
- uint8_t* value) {
- device->flags = *value;
-
- LOG(INFO) << __func__ << " " << base::HexEncode(value, len);
- LOG(INFO) << __func__ << "flags " << loghex(device->flags);
- }
-
- void OnGattWriteCcc(uint16_t connection_id, tGATT_STATUS status,
- uint16_t handle, void* /*data*/) {
- VolumeControlDevice* device =
- volume_control_devices_.FindByConnId(connection_id);
- if (!device) {
- LOG(INFO) << __func__
- << "unknown connection_id=" << loghex(connection_id);
- BtaGattQueue::Clean(connection_id);
- return;
- }
-
- if (status != GATT_SUCCESS) {
- LOG(ERROR) << __func__
- << "Failed to register for notification: " << loghex(handle)
- << " status: " << status;
- device_cleanup_helper(device, true);
- return;
- }
-
- LOG(INFO) << __func__
- << "Successfully register for indications: " << loghex(handle);
-
- verify_device_ready(device, handle);
- }
-
- static void OnGattWriteCccStatic(uint16_t connection_id, tGATT_STATUS status,
- uint16_t handle, void* data) {
- if (!instance) {
- LOG(ERROR) << __func__ << "No instance=" << handle;
- return;
- }
-
- instance->OnGattWriteCcc(connection_id, status, handle, data);
- }
-
- void Dump(int fd) { volume_control_devices_.DebugDump(fd); }
-
- void Disconnect(const RawAddress& address) override {
- VolumeControlDevice* device =
- volume_control_devices_.FindByAddress(address);
- if (!device) {
- LOG(INFO) << "Device not connected to profile" << address;
- return;
- }
-
- LOG(INFO) << __func__ << ": " << address;
- LOG(INFO) << "GAP_EVT_CONN_CLOSED: " << device->address;
- device_cleanup_helper(device, true);
- }
-
- void OnGattDisconnected(uint16_t connection_id, tGATT_IF /*client_if*/,
- RawAddress remote_bda,
- tGATT_DISCONN_REASON /*reason*/) {
- VolumeControlDevice* device =
- volume_control_devices_.FindByConnId(connection_id);
- if (!device) {
- LOG(ERROR) << __func__
- << " Skipping unknown device disconnect, connection_id="
- << loghex(connection_id);
- return;
- }
-
- // If we get here, it means, device has not been exlicitly disconnected.
- bool device_ready = device->device_ready;
-
- device_cleanup_helper(device, device->connecting_actively);
-
- if (device_ready) {
- volume_control_devices_.Add(remote_bda, true);
-
- /* Add device into BG connection to accept remote initiated connection */
- BTA_GATTC_Open(gatt_if_, remote_bda, false, false);
- }
- }
-
- void OnWriteControlResponse(uint16_t connection_id, tGATT_STATUS status,
- uint16_t handle, void* /*data*/) {
- VolumeControlDevice* device =
- volume_control_devices_.FindByConnId(connection_id);
- if (!device) {
- LOG(ERROR) << __func__
- << "Skipping unknown device disconnect, connection_id="
- << loghex(connection_id);
- return;
- }
-
- LOG(INFO) << "Write response handle: " << loghex(handle)
- << " status: " << loghex((int)(status));
- }
-
- void SetVolume(std::variant<RawAddress, int> addr_or_group_id,
- uint8_t volume) override {
- LOG(INFO) << __func__ << "vol: " << +volume;
-
- if (std::holds_alternative<RawAddress>(addr_or_group_id)) {
- std::vector<RawAddress> devices = {
- std::get<RawAddress>(addr_or_group_id)};
- std::vector<uint8_t> arg({volume});
- devices_control_point_helper(devices,
- kControlPointOpcodeSetAbsoluteVolume, &arg);
- return;
- }
-
- /* TODO implement handling group request */
- }
-
- void CleanUp() {
- LOG(INFO) << __func__;
- volume_control_devices_.Disconnect(gatt_if_);
- volume_control_devices_.Clear();
- BTA_GATTC_AppDeregister(gatt_if_);
- }
-
- private:
- tGATT_IF gatt_if_;
- bluetooth::vc::VolumeControlCallbacks* callbacks_;
- VolumeControlDevices volume_control_devices_;
-
- void verify_device_ready(VolumeControlDevice* device, uint16_t handle) {
- if (device->device_ready) return;
-
- // VerifyReady sets the device_ready flag if all remaining GATT operations
- // are completed
- if (device->VerifyReady(handle)) {
- LOG(INFO) << __func__ << "Outstanding reads completed ";
-
- callbacks_->OnConnectionState(ConnectionState::CONNECTED,
- device->address);
-
- device->connecting_actively = true;
-
- device->first_connection = false;
-
- // once profile connected we can notify current states
- callbacks_->OnVolumeStateChanged(device->address, device->volume,
- device->mute);
-
- device->EnqueueRemainingRequests(gatt_if_, chrc_read_callback_static,
- OnGattWriteCccStatic);
- }
- }
-
- void device_cleanup_helper(VolumeControlDevice* device, bool notify) {
- device->Disconnect(gatt_if_);
- if (notify)
- callbacks_->OnConnectionState(ConnectionState::DISCONNECTED,
- device->address);
- volume_control_devices_.Remove(device->address);
- }
-
- void devices_control_point_helper(std::vector<RawAddress>& devices,
- uint8_t opcode,
- const std::vector<uint8_t>* arg) {
- volume_control_devices_.ControlPointOperation(
- devices, opcode, arg,
- [](uint16_t connection_id, tGATT_STATUS status, uint16_t handle,
- void* data) {
- if (instance)
- instance->OnWriteControlResponse(connection_id, status, handle,
- data);
- },
- nullptr);
- }
-
- void gattc_callback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
- LOG(INFO) << __func__ << " event = " << static_cast<int>(event);
-
- if (p_data == nullptr) return;
-
- switch (event) {
- case BTA_GATTC_OPEN_EVT: {
- tBTA_GATTC_OPEN& o = p_data->open;
- OnGattConnected(o.status, o.conn_id, o.client_if, o.remote_bda,
- o.transport, o.mtu);
-
- } break;
-
- case BTA_GATTC_CLOSE_EVT: {
- tBTA_GATTC_CLOSE& c = p_data->close;
- OnGattDisconnected(c.conn_id, c.client_if, c.remote_bda, c.reason);
- } break;
-
- case BTA_GATTC_SEARCH_CMPL_EVT:
- OnServiceSearchComplete(p_data->search_cmpl.conn_id,
- p_data->search_cmpl.status);
- break;
-
- case BTA_GATTC_NOTIF_EVT: {
- tBTA_GATTC_NOTIFY& n = p_data->notify;
- if (!n.is_notify || n.len > GATT_MAX_ATTR_LEN) {
- LOG(ERROR) << __func__ << ": rejected BTA_GATTC_NOTIF_EVT. is_notify="
- << n.is_notify << ", len=" << static_cast<int>(n.len);
- break;
- }
- OnNotificationEvent(n.conn_id, n.handle, n.len, n.value);
- } break;
-
- case BTA_GATTC_ENC_CMPL_CB_EVT:
- OnEncryptionComplete(p_data->enc_cmpl.remote_bda, true);
- break;
-
- case BTA_GATTC_SRVC_CHG_EVT:
- OnServiceChangeEvent(p_data->remote_bda);
- break;
-
- case BTA_GATTC_SRVC_DISC_DONE_EVT:
- OnServiceDiscDoneEvent(p_data->remote_bda);
- break;
-
- default:
- break;
- }
- }
-
- static void gattc_callback_static(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
- if (instance) instance->gattc_callback(event, p_data);
- }
-
- static void enc_callback_static(const RawAddress* address, tBT_TRANSPORT,
- void*, tBTM_STATUS status) {
- if (instance) instance->OnEncryptionComplete(*address, status);
- }
-
- static void chrc_read_callback_static(uint16_t conn_id, tGATT_STATUS status,
- uint16_t handle, uint16_t len,
- uint8_t* value, void* data) {
- if (instance)
- instance->OnCharacteristicValueChanged(conn_id, status, handle, len,
- value, data);
- }
-};
-} // namespace
-
-void VolumeControl::Initialize(
- bluetooth::vc::VolumeControlCallbacks* callbacks) {
- if (instance) {
- LOG(ERROR) << "Already initialized!";
- return;
- }
-
- instance = new VolumeControlImpl(callbacks);
-}
-
-bool VolumeControl::IsVolumeControlRunning() { return instance; }
-
-VolumeControl* VolumeControl::Get(void) {
- CHECK(instance);
- return instance;
-};
-
-void VolumeControl::AddFromStorage(const RawAddress& address,
- bool auto_connect) {
- if (!instance) {
- LOG(ERROR) << "Not initialized yet";
- return;
- }
-
- instance->AddFromStorage(address, auto_connect);
-};
-
-void VolumeControl::CleanUp() {
- if (!instance) {
- LOG(ERROR) << "not initialized!";
- return;
- }
-
- VolumeControlImpl* ptr = instance;
- instance = nullptr;
-
- ptr->CleanUp();
-
- delete ptr;
-};
-
-void VolumeControl::DebugDump(int fd) {
- dprintf(fd, "Volume Control Manager:\n");
- if (instance) instance->Dump(fd);
- dprintf(fd, "\n");
-}
diff --git a/bta/vc/vc_test.cc b/bta/vc/vc_test.cc
deleted file mode 100644
index 1d45fa881..000000000
--- a/bta/vc/vc_test.cc
+++ /dev/null
@@ -1,643 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <base/bind.h>
-#include <base/bind_helpers.h>
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "bta_gatt_api_mock.h"
-#include "bta_gatt_queue_mock.h"
-#include "bta_vc_api.h"
-#include "btm_api_mock.h"
-#include "gatt/database_builder.h"
-#include "hardware/bt_gatt_types.h"
-#include "types.h"
-
-void btif_storage_add_volume_control(const RawAddress& addr, bool auto_conn) {}
-
-namespace bluetooth {
-namespace vc {
-namespace internal {
-namespace {
-
-using base::Bind;
-using base::Unretained;
-
-using bluetooth::vc::ConnectionState;
-using bluetooth::vc::VolumeControlCallbacks;
-
-using testing::_;
-using testing::DoAll;
-using testing::DoDefault;
-using testing::Invoke;
-using testing::Mock;
-using testing::NotNull;
-using testing::Return;
-using testing::SaveArg;
-using testing::SetArgPointee;
-using testing::WithArg;
-
-RawAddress GetTestAddress(int index) {
- CHECK_LT(index, UINT8_MAX);
- RawAddress result = {
- {0xC0, 0xDE, 0xC0, 0xDE, 0x00, static_cast<uint8_t>(index)}};
- return result;
-}
-
-class MockVolumeControlCallbacks : public VolumeControlCallbacks {
- public:
- MockVolumeControlCallbacks() = default;
- ~MockVolumeControlCallbacks() override = default;
-
- MOCK_METHOD((void), OnConnectionState,
- (ConnectionState state, const RawAddress& address), (override));
- MOCK_METHOD((void), OnVolumeStateChanged,
- (const RawAddress& address, uint8_t volume, bool mute),
- (override));
- MOCK_METHOD((void), OnGroupVolumeStateChanged,
- (int group_id, uint8_t volume, bool mute), (override));
-
- private:
- DISALLOW_COPY_AND_ASSIGN(MockVolumeControlCallbacks);
-};
-
-class VolumeControlTest : public ::testing::Test {
- private:
- void set_sample_database(uint16_t conn_id, bool vcs, bool vcs_broken,
- bool aics, bool aics_broken, bool vocs,
- bool vocs_broken) {
- gatt::DatabaseBuilder builder;
- builder.AddService(0x0001, 0x0003, Uuid::From16Bit(0x1800), true);
- builder.AddCharacteristic(0x0002, 0x0003, Uuid::From16Bit(0x2a00),
- GATT_CHAR_PROP_BIT_READ);
- /* 0x0004-0x000f RFU */
- if (vcs) {
- /* VCS */
- builder.AddService(0x0010, 0x0026, kVolumeControlUuid, true);
- if (aics) {
- /* TODO Place holder */
- }
- if (vocs) {
- /* TODO Place holder */
- }
- /* 0x0015-0x001f RFU */
- builder.AddCharacteristic(
- 0x0020, 0x0021, kVolumeControlStateUuid,
- GATT_CHAR_PROP_BIT_READ | GATT_CHAR_PROP_BIT_NOTIFY);
- builder.AddDescriptor(0x0022,
- Uuid::From16Bit(GATT_UUID_CHAR_CLIENT_CONFIG));
- if (!vcs_broken) {
- builder.AddCharacteristic(0x0023, 0x0024, kVolumeControlPointUuid,
- GATT_CHAR_PROP_BIT_WRITE);
- }
- builder.AddCharacteristic(0x0025, 0x0026, kVolumeFlagsUuid,
- GATT_CHAR_PROP_BIT_READ);
- /* 0x0027-0x002f RFU */
- if (aics) {
- /* TODO Place holder for AICS */
- }
- if (vocs) {
- /* TODO Place holder for VOCS */
- }
- }
- /* 0x008c-0x008f RFU */
-
- /* GATTS */
- builder.AddService(0x0090, 0x0093,
- Uuid::From16Bit(UUID_SERVCLASS_GATT_SERVER), true);
- builder.AddCharacteristic(0x0091, 0x0092,
- Uuid::From16Bit(GATT_UUID_GATT_SRV_CHGD),
- GATT_CHAR_PROP_BIT_NOTIFY);
- builder.AddDescriptor(0x0093,
- Uuid::From16Bit(GATT_UUID_CHAR_CLIENT_CONFIG));
- services_map[conn_id] = builder.Build().Services();
-
- ON_CALL(gatt_queue, ReadCharacteristic(conn_id, _, _, _))
- .WillByDefault(Invoke([&](uint16_t conn_id, uint16_t handle,
- GATT_READ_OP_CB cb, void* cb_data) -> void {
- std::vector<uint8_t> value;
-
- switch (handle) {
- case 0x0003:
- /* device name */
- value.resize(20);
- break;
-
- case 0x0021:
- /* volume state */
- value.resize(3);
- break;
-
- case 0x0026:
- /* volume flags */
- value.resize(1);
- break;
-
- default:
- ASSERT_TRUE(false);
- return;
- }
-
- cb(conn_id, GATT_SUCCESS, handle, value.size(), value.data(),
- cb_data);
- }));
- }
-
- protected:
- void SetUp(void) override {
- bluetooth::manager::SetMockBtmInterface(&btm_interface);
- gatt::SetMockBtaGattInterface(&gatt_interface);
- gatt::SetMockBtaGattQueue(&gatt_queue);
- callbacks.reset(new MockVolumeControlCallbacks());
-
- // default action for GetCharacteristic function call
- ON_CALL(gatt_interface, GetCharacteristic(_, _))
- .WillByDefault(
- Invoke([&](uint16_t conn_id,
- uint16_t handle) -> const gatt::Characteristic* {
- std::list<gatt::Service>& services = services_map[conn_id];
- for (auto const& service : services) {
- for (auto const& characteristic : service.characteristics) {
- if (characteristic.value_handle == handle) {
- return &characteristic;
- }
- }
- }
-
- return nullptr;
- }));
-
- // default action for GetOwningService function call
- ON_CALL(gatt_interface, GetOwningService(_, _))
- .WillByDefault(Invoke(
- [&](uint16_t conn_id, uint16_t handle) -> const gatt::Service* {
- std::list<gatt::Service>& services = services_map[conn_id];
- for (auto const& service : services) {
- if (service.handle <= handle && service.end_handle >= handle) {
- return &service;
- }
- }
-
- return nullptr;
- }));
-
- // default action for GetServices function call
- ON_CALL(gatt_interface, GetServices(_))
- .WillByDefault(WithArg<0>(
- Invoke([&](uint16_t conn_id) -> std::list<gatt::Service>* {
- return &services_map[conn_id];
- })));
-
- // default action for RegisterForNotifications function call
- ON_CALL(gatt_interface, RegisterForNotifications(gatt_if, _, _))
- .WillByDefault(Return(GATT_SUCCESS));
-
- // default action for DeregisterForNotifications function call
- ON_CALL(gatt_interface, DeregisterForNotifications(gatt_if, _, _))
- .WillByDefault(Return(GATT_SUCCESS));
-
- // default action for WriteDescriptor function call
- ON_CALL(gatt_queue, WriteDescriptor(_, _, _, _, _, _))
- .WillByDefault(
- Invoke([](uint16_t conn_id, uint16_t handle,
- std::vector<uint8_t> value, tGATT_WRITE_TYPE write_type,
- GATT_WRITE_OP_CB cb, void* cb_data) -> void {
- if (cb) cb(conn_id, GATT_SUCCESS, handle, cb_data);
- }));
- }
-
- void TearDown(void) override {
- services_map.clear();
- callbacks.reset();
- gatt::SetMockBtaGattQueue(nullptr);
- gatt::SetMockBtaGattInterface(nullptr);
- bluetooth::manager::SetMockBtmInterface(nullptr);
- }
-
- void TestAppRegister(void) {
- BtaAppRegisterCallback app_register_callback;
- EXPECT_CALL(gatt_interface, AppRegister(_, _, _))
- .WillOnce(DoAll(SaveArg<0>(&gatt_callback),
- SaveArg<1>(&app_register_callback)));
- VolumeControl::Initialize(callbacks.get());
- ASSERT_TRUE(gatt_callback);
- ASSERT_TRUE(app_register_callback);
- app_register_callback.Run(gatt_if, GATT_SUCCESS);
- ASSERT_TRUE(VolumeControl::IsVolumeControlRunning());
- }
-
- void TestAppUnregister(void) {
- EXPECT_CALL(gatt_interface, AppDeregister(gatt_if));
- VolumeControl::CleanUp();
- ASSERT_FALSE(VolumeControl::IsVolumeControlRunning());
- gatt_callback = nullptr;
- }
-
- void TestConnect(const RawAddress& address) {
- // by default indicate link as encrypted
- ON_CALL(btm_interface, GetSecurityFlagsByTransport(address, NotNull(), _))
- .WillByDefault(
- DoAll(SetArgPointee<1>(BTM_SEC_FLAG_ENCRYPTED), Return(true)));
-
- EXPECT_CALL(gatt_interface, Open(gatt_if, address, true, _));
- VolumeControl::Get()->Connect(address);
- }
-
- void TestDisconnect(const RawAddress& address, uint16_t conn_id) {
- if (conn_id) {
- EXPECT_CALL(gatt_interface, Close(conn_id));
- } else {
- EXPECT_CALL(gatt_interface, CancelOpen(gatt_if, address, _));
- }
- VolumeControl::Get()->Disconnect(address);
- }
-
- void TestAddFromStorage(const RawAddress& address, bool auto_connect) {
- // by default indicate link as encrypted
- ON_CALL(btm_interface, GetSecurityFlagsByTransport(address, NotNull(), _))
- .WillByDefault(
- DoAll(SetArgPointee<1>(BTM_SEC_FLAG_ENCRYPTED), Return(true)));
-
- if (auto_connect) {
- EXPECT_CALL(gatt_interface, Open(gatt_if, address, false, _));
- } else {
- EXPECT_CALL(gatt_interface, Open(gatt_if, address, _, _)).Times(0);
- }
- VolumeControl::Get()->AddFromStorage(address, auto_connect);
- }
-
- void TestSubscribeNotifications(const RawAddress& address, uint16_t conn_id,
- std::map<uint16_t, uint16_t>& handle_pairs) {
- SetSampleDatabase(conn_id);
- TestAppRegister();
- TestConnect(address);
- GetConnectedEvent(address, conn_id);
-
- EXPECT_CALL(gatt_queue, WriteDescriptor(_, _, _, _, _, _))
- .WillRepeatedly(DoDefault());
- EXPECT_CALL(gatt_interface, RegisterForNotifications(_, _, _))
- .WillRepeatedly(DoDefault());
-
- std::vector<uint8_t> notify_value({0x01, 0x00});
- for (auto const& handles : handle_pairs) {
- EXPECT_CALL(gatt_queue, WriteDescriptor(conn_id, handles.second,
- notify_value, GATT_WRITE, _, _))
- .WillOnce(DoDefault());
- EXPECT_CALL(gatt_interface,
- RegisterForNotifications(gatt_if, address, handles.first))
- .WillOnce(DoDefault());
- }
-
- GetSearchCompleteEvent(conn_id);
- TestAppUnregister();
- }
-
- void TestReadCharacteristic(const RawAddress& address, uint16_t conn_id,
- std::vector<uint16_t> handles) {
- SetSampleDatabase(conn_id);
- TestAppRegister();
- TestConnect(address);
- GetConnectedEvent(address, conn_id);
-
- EXPECT_CALL(gatt_queue, ReadCharacteristic(conn_id, _, _, _))
- .WillRepeatedly(DoDefault());
- for (auto const& handle : handles) {
- EXPECT_CALL(gatt_queue, ReadCharacteristic(conn_id, handle, _, _))
- .WillOnce(DoDefault());
- }
-
- GetSearchCompleteEvent(conn_id);
- TestAppUnregister();
- }
-
- void GetConnectedEvent(const RawAddress& address, uint16_t conn_id) {
- tBTA_GATTC_OPEN event_data = {
- .status = GATT_SUCCESS,
- .conn_id = conn_id,
- .client_if = gatt_if,
- .remote_bda = address,
- .transport = GATT_TRANSPORT_LE,
- .mtu = 240,
- };
-
- gatt_callback(BTA_GATTC_OPEN_EVT, (tBTA_GATTC*)&event_data);
- }
-
- void GetDisconnectedEvent(const RawAddress& address, uint16_t conn_id) {
- tBTA_GATTC_CLOSE event_data = {
- .status = GATT_SUCCESS,
- .conn_id = conn_id,
- .client_if = gatt_if,
- .remote_bda = address,
- .reason = GATT_CONN_TERMINATE_PEER_USER,
- };
-
- gatt_callback(BTA_GATTC_CLOSE_EVT, (tBTA_GATTC*)&event_data);
- }
-
- void GetSearchCompleteEvent(uint16_t conn_id) {
- tBTA_GATTC_SEARCH_CMPL event_data = {
- .status = GATT_SUCCESS,
- .conn_id = conn_id,
- };
-
- gatt_callback(BTA_GATTC_SEARCH_CMPL_EVT, (tBTA_GATTC*)&event_data);
- }
-
- void SetEncryptionResult(const RawAddress& address, bool success) {
- ON_CALL(btm_interface, GetSecurityFlagsByTransport(address, NotNull(), _))
- .WillByDefault(DoAll(SetArgPointee<1>(0), Return(true)));
- EXPECT_CALL(btm_interface,
- SetEncryption(address, _, NotNull(), _, BTM_BLE_SEC_ENCRYPT))
- .WillOnce(Invoke(
- [&success](const RawAddress& bd_addr, tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback, void* p_ref_data,
- tBTM_BLE_SEC_ACT sec_act) -> tBTM_STATUS {
- p_callback(&bd_addr, transport, p_ref_data,
- success ? BTM_SUCCESS : BTM_FAILED_ON_SECURITY);
- return BTM_SUCCESS;
- }));
- }
-
- void SetSampleDatabaseVCS(uint16_t conn_id) {
- set_sample_database(conn_id, true, false, false, false, false, false);
- }
-
- void SetSampleDatabaseNoVCS(uint16_t conn_id) {
- set_sample_database(conn_id, false, false, true, false, true, false);
- }
-
- void SetSampleDatabaseVCSBroken(uint16_t conn_id) {
- set_sample_database(conn_id, true, true, true, false, true, false);
- }
-
- void SetSampleDatabase(uint16_t conn_id) {
- set_sample_database(conn_id, true, false, true, false, true, false);
- }
-
- std::unique_ptr<MockVolumeControlCallbacks> callbacks;
- bluetooth::manager::MockBtmInterface btm_interface;
- gatt::MockBtaGattInterface gatt_interface;
- gatt::MockBtaGattQueue gatt_queue;
- tBTA_GATTC_CBACK* gatt_callback;
- const uint8_t gatt_if = 0xff;
- std::map<uint16_t, std::list<gatt::Service>> services_map;
-};
-
-TEST_F(VolumeControlTest, test_get_uninitialized) {
- ASSERT_DEATH(VolumeControl::Get(), "");
-}
-
-TEST_F(VolumeControlTest, test_initialize) {
- VolumeControl::Initialize(callbacks.get());
- ASSERT_TRUE(VolumeControl::IsVolumeControlRunning());
- VolumeControl::CleanUp();
-}
-
-TEST_F(VolumeControlTest, test_initialize_twice) {
- VolumeControl::Initialize(callbacks.get());
- VolumeControl* volume_control_p = VolumeControl::Get();
- VolumeControl::Initialize(callbacks.get());
- ASSERT_EQ(volume_control_p, VolumeControl::Get());
- VolumeControl::CleanUp();
-}
-
-TEST_F(VolumeControlTest, test_cleanup_initialized) {
- VolumeControl::Initialize(callbacks.get());
- VolumeControl::CleanUp();
- ASSERT_FALSE(VolumeControl::IsVolumeControlRunning());
-}
-
-TEST_F(VolumeControlTest, test_cleanup_uninitialized) {
- VolumeControl::CleanUp();
- ASSERT_FALSE(VolumeControl::IsVolumeControlRunning());
-}
-
-TEST_F(VolumeControlTest, test_app_registration) {
- TestAppRegister();
- TestAppUnregister();
-}
-
-TEST_F(VolumeControlTest, test_connect) {
- TestAppRegister();
- TestConnect(GetTestAddress(0));
- TestAppUnregister();
-}
-
-TEST_F(VolumeControlTest, test_add_from_storage) {
- TestAppRegister();
- TestAddFromStorage(GetTestAddress(0), true);
- TestAddFromStorage(GetTestAddress(1), false);
- TestAppUnregister();
-}
-
-TEST_F(VolumeControlTest, test_disconnect_non_connected) {
- const RawAddress test_address = GetTestAddress(0);
- TestAppRegister();
- TestConnect(test_address);
- EXPECT_CALL(*callbacks,
- OnConnectionState(ConnectionState::DISCONNECTED, test_address));
- TestDisconnect(test_address, 0);
- TestAppUnregister();
-}
-
-TEST_F(VolumeControlTest, test_disconnect_connected) {
- const RawAddress test_address = GetTestAddress(0);
- TestAppRegister();
- TestConnect(test_address);
- GetConnectedEvent(test_address, 1);
- EXPECT_CALL(*callbacks,
- OnConnectionState(ConnectionState::DISCONNECTED, test_address));
- TestDisconnect(test_address, 1);
- TestAppUnregister();
-}
-
-TEST_F(VolumeControlTest, test_disconnected) {
- const RawAddress test_address = GetTestAddress(0);
- TestAppRegister();
- TestConnect(test_address);
- GetConnectedEvent(test_address, 1);
- EXPECT_CALL(*callbacks,
- OnConnectionState(ConnectionState::DISCONNECTED, test_address));
- GetDisconnectedEvent(test_address, 1);
- TestAppUnregister();
-}
-
-TEST_F(VolumeControlTest, test_disconnected_while_autoconnect) {
- const RawAddress test_address = GetTestAddress(0);
- TestAppRegister();
- TestAddFromStorage(test_address, true);
- GetConnectedEvent(test_address, 1);
- // autoconnect - don't indicate disconnection
- EXPECT_CALL(*callbacks,
- OnConnectionState(ConnectionState::DISCONNECTED, test_address))
- .Times(0);
- GetDisconnectedEvent(test_address, 1);
- TestAppUnregister();
-}
-
-TEST_F(VolumeControlTest, test_reconnect_after_encryption_failed) {
- const RawAddress test_address = GetTestAddress(0);
- TestAppRegister();
- TestAddFromStorage(test_address, true);
- SetEncryptionResult(test_address, false);
- // autoconnect - don't indicate disconnection
- EXPECT_CALL(*callbacks,
- OnConnectionState(ConnectionState::DISCONNECTED, test_address))
- .Times(0);
- GetConnectedEvent(test_address, 1);
- Mock::VerifyAndClearExpectations(&btm_interface);
- SetEncryptionResult(test_address, true);
- GetConnectedEvent(test_address, 1);
- TestAppUnregister();
-}
-
-TEST_F(VolumeControlTest, test_discovery_vcs_found) {
- const RawAddress test_address = GetTestAddress(0);
- SetSampleDatabaseVCS(1);
- TestAppRegister();
- TestConnect(test_address);
- EXPECT_CALL(*callbacks,
- OnConnectionState(ConnectionState::CONNECTED, test_address));
- GetConnectedEvent(test_address, 1);
- GetSearchCompleteEvent(1);
- Mock::VerifyAndClearExpectations(callbacks.get());
- TestAppUnregister();
-}
-
-TEST_F(VolumeControlTest, test_discovery_vcs_not_found) {
- const RawAddress test_address = GetTestAddress(0);
- SetSampleDatabaseNoVCS(1);
- TestAppRegister();
- TestConnect(test_address);
- EXPECT_CALL(*callbacks,
- OnConnectionState(ConnectionState::DISCONNECTED, test_address));
- GetConnectedEvent(test_address, 1);
-
- GetSearchCompleteEvent(1);
- Mock::VerifyAndClearExpectations(callbacks.get());
- TestAppUnregister();
-}
-
-TEST_F(VolumeControlTest, test_discovery_vcs_broken) {
- const RawAddress test_address = GetTestAddress(0);
- SetSampleDatabaseVCSBroken(1);
- TestAppRegister();
- TestConnect(test_address);
- EXPECT_CALL(*callbacks,
- OnConnectionState(ConnectionState::DISCONNECTED, test_address));
- GetConnectedEvent(test_address, 1);
- GetSearchCompleteEvent(1);
- Mock::VerifyAndClearExpectations(callbacks.get());
- TestAppUnregister();
-}
-
-TEST_F(VolumeControlTest, test_subscribe_vcs_volume_state) {
- std::map<uint16_t, uint16_t> handles({{0x0021, 0x0022}});
- TestSubscribeNotifications(GetTestAddress(0), 1, handles);
-}
-
-TEST_F(VolumeControlTest, test_read_vcs_volume_state) {
- const RawAddress test_address = GetTestAddress(0);
- EXPECT_CALL(*callbacks, OnVolumeStateChanged(test_address, _, _));
- std::vector<uint16_t> handles({0x0021});
- TestReadCharacteristic(test_address, 1, handles);
-}
-
-TEST_F(VolumeControlTest, test_read_vcs_volume_flags) {
- std::vector<uint16_t> handles({0x0026});
- TestReadCharacteristic(GetTestAddress(0), 1, handles);
-}
-
-class VolumeControlCallbackTest : public VolumeControlTest {
- protected:
- const RawAddress test_address = GetTestAddress(0);
- uint16_t conn_id = 22;
-
- void SetUp(void) override {
- VolumeControlTest::SetUp();
- SetSampleDatabase(conn_id);
- TestAppRegister();
- TestConnect(test_address);
- GetConnectedEvent(test_address, conn_id);
- GetSearchCompleteEvent(conn_id);
- }
-
- void TearDown(void) override {
- TestAppUnregister();
- VolumeControlTest::TearDown();
- }
-
- void GetNotificationEvent(uint16_t handle, std::vector<uint8_t>& value) {
- tBTA_GATTC_NOTIFY event_data = {
- .conn_id = conn_id,
- .bda = test_address,
- .handle = handle,
- .len = (uint8_t)value.size(),
- .is_notify = true,
- };
-
- std::copy(value.begin(), value.end(), event_data.value);
- gatt_callback(BTA_GATTC_NOTIF_EVT, (tBTA_GATTC*)&event_data);
- }
-};
-
-TEST_F(VolumeControlCallbackTest, test_volume_state_changed) {
- std::vector<uint8_t> value({0x03, 0x01, 0x02});
- EXPECT_CALL(*callbacks, OnVolumeStateChanged(test_address, 0x03, true));
- GetNotificationEvent(0x0021, value);
-}
-
-TEST_F(VolumeControlCallbackTest, test_volume_state_changed_malformed) {
- EXPECT_CALL(*callbacks, OnVolumeStateChanged(test_address, _, _)).Times(0);
- std::vector<uint8_t> too_short({0x03, 0x01});
- GetNotificationEvent(0x0021, too_short);
- std::vector<uint8_t> too_long({0x03, 0x01, 0x02, 0x03});
- GetNotificationEvent(0x0021, too_long);
-}
-
-class VolumeControlValueSetTest : public VolumeControlTest {
- protected:
- const RawAddress test_address = GetTestAddress(0);
- uint16_t conn_id = 22;
-
- void SetUp(void) override {
- VolumeControlTest::SetUp();
- SetSampleDatabase(conn_id);
- TestAppRegister();
- TestConnect(test_address);
- GetConnectedEvent(test_address, conn_id);
- GetSearchCompleteEvent(conn_id);
- }
-
- void TearDown(void) override {
- TestAppUnregister();
- VolumeControlTest::TearDown();
- }
-};
-
-TEST_F(VolumeControlValueSetTest, test_set_volume) {
- std::vector<uint8_t> expected_data({0x04, 0x00, 0x10});
- EXPECT_CALL(gatt_queue, WriteCharacteristic(conn_id, 0x0024, expected_data,
- GATT_WRITE, _, _));
- VolumeControl::Get()->SetVolume(test_address, 0x10);
-}
-} // namespace
-} // namespace internal
-} // namespace vc
-} // namespace bluetooth
diff --git a/btcore/Android.bp b/btcore/Android.bp
index fc2cd4e94..6f5b0adae 100644
--- a/btcore/Android.bp
+++ b/btcore/Android.bp
@@ -1,14 +1,5 @@
// libbtcore static library for target and host
// ========================================================
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "libbtcore",
defaults: ["fluoride_defaults"],
@@ -56,7 +47,4 @@ cc_test {
"libosi",
],
host_supported: true,
- test_options: {
- unit_test: true,
- },
}
diff --git a/btcore/BUILD.gn b/btcore/BUILD.gn
index 1b8ba7ec8..01b9cf7e3 100644
--- a/btcore/BUILD.gn
+++ b/btcore/BUILD.gn
@@ -19,51 +19,44 @@ static_library("btcore") {
"src/device_class.cc",
"src/hal_util.cc",
"src/module.cc",
- "src/osi_module.cc",
"src/property.cc",
+ "src/osi_module.cc",
]
include_dirs = [
"include",
- "//bt",
+ "//",
]
- configs += [ "//bt:target_defaults" ]
-
deps = [
- "//bt/gd/rust/shim:init_flags_bridge_header",
- "//bt/gd/rust/shim:message_loop_thread_bridge_header",
+ "//third_party/libchrome:base",
]
}
-if (use.test) {
- executable("net_test_btcore") {
- sources = [
- "//bt/osi/test/AllocationTestHarness.cc",
- "test/device_class_test.cc",
- "test/property_test.cc",
- ]
-
- include_dirs = [
- "include",
- "//bt",
- ]
+executable("net_test_btcore") {
+ testonly = true
+ sources = [
+ "test/device_class_test.cc",
+ "test/property_test.cc",
+ "//osi/test/AllocationTestHarness.cc",
+ ]
- deps = [
- "//bt/btcore",
- "//bt/osi",
- "//bt/types",
- ]
+ include_dirs = [
+ "include",
+ "//",
+ ]
- configs += [
- "//bt:external_gtest_main",
- "//bt:target_defaults",
- ]
+ deps = [
+ "//btcore",
+ "//osi",
+ "//types",
+ "//third_party/googletest:gtest_main",
+ "//third_party/libchrome:base",
+ ]
- libs = [
- "pthread",
- "rt",
- "dl",
- ]
- }
+ libs = [
+ "-lpthread",
+ "-lrt",
+ "-ldl",
+ ]
}
diff --git a/btcore/include/module.h b/btcore/include/module.h
index a6f5fd272..ca1d8b41f 100644
--- a/btcore/include/module.h
+++ b/btcore/include/module.h
@@ -29,12 +29,12 @@ typedef future_t* (*module_lifecycle_fn)(void);
#define BTCORE_MAX_MODULE_DEPENDENCIES 10
typedef struct {
- const char* name{nullptr};
- module_lifecycle_fn init{nullptr};
- module_lifecycle_fn start_up{nullptr};
- module_lifecycle_fn shut_down{nullptr};
- module_lifecycle_fn clean_up{nullptr};
- const char* dependencies[BTCORE_MAX_MODULE_DEPENDENCIES]{nullptr};
+ const char* name;
+ module_lifecycle_fn init;
+ module_lifecycle_fn start_up;
+ module_lifecycle_fn shut_down;
+ module_lifecycle_fn clean_up;
+ const char* dependencies[BTCORE_MAX_MODULE_DEPENDENCIES];
} module_t;
// Prepares module management. Must be called before doing anything with
@@ -57,3 +57,13 @@ void module_shut_down(const module_t* module);
// Clean up the provided module. |module| may not be NULL.
// If not initialized, does nothing.
void module_clean_up(const module_t* module);
+
+// Temporary callbacked wrapper for module start up, so real modules can be
+// spliced into the current janky startup sequence. Runs on a separate thread,
+// which terminates when the module start up has finished. When module startup
+// has finished, |callback| is called within the context of |callback_thread|
+// with |FUTURE_SUCCESS| or |FUTURE_FAIL| depending on whether startup succeeded
+// or not.
+void module_start_up_callbacked_wrapper(
+ const module_t* module,
+ bluetooth::common::MessageLoopThread* callback_thread, thread_fn callback);
diff --git a/btcore/src/hal_util.cc b/btcore/src/hal_util.cc
index 616bd2b46..d0433486f 100644
--- a/btcore/src/hal_util.cc
+++ b/btcore/src/hal_util.cc
@@ -31,7 +31,6 @@ using base::StringPrintf;
#define BLUETOOTH_LIBRARY_NAME "libbluetooth.so"
-#if !defined(STATIC_LIBBLUETOOTH)
int hal_util_load_bt_library(const bt_interface_t** interface) {
const char* sym = BLUETOOTH_INTERFACE_STRING;
bt_interface_t* itf = nullptr;
@@ -66,12 +65,3 @@ error:
return -EINVAL;
}
-#else
-extern bt_interface_t bluetoothInterface;
-
-int hal_util_load_bt_library(const bt_interface_t** interface) {
- *interface = &bluetoothInterface;
-
- return 0;
-}
-#endif
diff --git a/btcore/src/module.cc b/btcore/src/module.cc
index aba223422..d22600656 100644
--- a/btcore/src/module.cc
+++ b/btcore/src/module.cc
@@ -18,8 +18,6 @@
#define LOG_TAG "bt_core_module"
-#include "btcore/include/module.h"
-
#include <base/logging.h>
#include <dlfcn.h>
#include <string.h>
@@ -27,6 +25,7 @@
#include <mutex>
#include <unordered_map>
+#include "btcore/include/module.h"
#include "common/message_loop_thread.h"
#include "osi/include/allocator.h"
#include "osi/include/log.h"
@@ -51,7 +50,9 @@ static void set_module_state(const module_t* module, module_state_t state);
void module_management_start(void) {}
-void module_management_stop(void) { metadata.clear(); }
+void module_management_stop(void) {
+ metadata.clear();
+}
const module_t* get_module(const char* name) {
module_t* module = (module_t*)dlsym(RTLD_DEFAULT, name);
@@ -64,7 +65,8 @@ bool module_init(const module_t* module) {
CHECK(get_module_state(module) == MODULE_STATE_NONE);
if (!call_lifecycle_function(module->init)) {
- LOG_ERROR("%s Failed to initialize module \"%s\"", __func__, module->name);
+ LOG_ERROR(LOG_TAG, "%s Failed to initialize module \"%s\"", __func__,
+ module->name);
return false;
}
@@ -82,12 +84,13 @@ bool module_start_up(const module_t* module) {
CHECK(get_module_state(module) == MODULE_STATE_INITIALIZED ||
module->init == NULL);
- LOG_INFO("%s Starting module \"%s\"", __func__, module->name);
+ LOG_INFO(LOG_TAG, "%s Starting module \"%s\"", __func__, module->name);
if (!call_lifecycle_function(module->start_up)) {
- LOG_ERROR("%s Failed to start up module \"%s\"", __func__, module->name);
+ LOG_ERROR(LOG_TAG, "%s Failed to start up module \"%s\"", __func__,
+ module->name);
return false;
}
- LOG_INFO("%s Started module \"%s\"", __func__, module->name);
+ LOG_INFO(LOG_TAG, "%s Started module \"%s\"", __func__, module->name);
set_module_state(module, MODULE_STATE_STARTED);
return true;
@@ -101,12 +104,14 @@ void module_shut_down(const module_t* module) {
// Only something to do if the module was actually started
if (state < MODULE_STATE_STARTED) return;
- LOG_INFO("%s Shutting down module \"%s\"", __func__, module->name);
+ LOG_INFO(LOG_TAG, "%s Shutting down module \"%s\"", __func__, module->name);
if (!call_lifecycle_function(module->shut_down)) {
- LOG_ERROR("%s Failed to shutdown module \"%s\". Continuing anyway.",
+ LOG_ERROR(LOG_TAG,
+ "%s Failed to shutdown module \"%s\". Continuing anyway.",
__func__, module->name);
}
- LOG_INFO("%s Shutdown of module \"%s\" completed", __func__, module->name);
+ LOG_INFO(LOG_TAG, "%s Shutdown of module \"%s\" completed", __func__,
+ module->name);
set_module_state(module, MODULE_STATE_INITIALIZED);
}
@@ -119,12 +124,13 @@ void module_clean_up(const module_t* module) {
// Only something to do if the module was actually initialized
if (state < MODULE_STATE_INITIALIZED) return;
- LOG_INFO("%s Cleaning up module \"%s\"", __func__, module->name);
+ LOG_INFO(LOG_TAG, "%s Cleaning up module \"%s\"", __func__, module->name);
if (!call_lifecycle_function(module->clean_up)) {
- LOG_ERROR("%s Failed to cleanup module \"%s\". Continuing anyway.",
+ LOG_ERROR(LOG_TAG, "%s Failed to cleanup module \"%s\". Continuing anyway.",
__func__, module->name);
}
- LOG_INFO("%s Cleanup of module \"%s\" completed", __func__, module->name);
+ LOG_INFO(LOG_TAG, "%s Cleanup of module \"%s\" completed", __func__,
+ module->name);
set_module_state(module, MODULE_STATE_NONE);
}
@@ -153,3 +159,48 @@ static void set_module_state(const module_t* module, module_state_t state) {
std::lock_guard<std::mutex> lock(metadata_mutex);
metadata[module] = state;
}
+
+// TODO(zachoverflow): remove when everything modulized
+// Temporary callback-wrapper-related code
+class CallbackWrapper {
+ public:
+ explicit CallbackWrapper(const module_t* module,
+ MessageLoopThread* callback_thread,
+ thread_fn callback)
+ : module(module),
+ lifecycle_thread("bt_module_lifecycle_thread"),
+ callback_thread(callback_thread),
+ callback(callback),
+ success(false) {}
+ const module_t* module;
+ MessageLoopThread lifecycle_thread;
+ // we don't own this thread
+ MessageLoopThread* callback_thread;
+ thread_fn callback;
+ bool success;
+};
+
+static void post_result_to_callback(std::shared_ptr<CallbackWrapper> wrapper) {
+ CHECK(wrapper);
+ wrapper->lifecycle_thread.ShutDown();
+ wrapper->callback(wrapper->success ? FUTURE_SUCCESS : FUTURE_FAIL);
+}
+
+static void run_wrapped_start_up(std::shared_ptr<CallbackWrapper> wrapper) {
+ CHECK(wrapper);
+ wrapper->success = module_start_up(wrapper->module);
+ // Post the result back to the callback
+ wrapper->callback_thread->DoInThread(
+ FROM_HERE, base::BindOnce(post_result_to_callback, wrapper));
+}
+
+void module_start_up_callbacked_wrapper(const module_t* module,
+ MessageLoopThread* callback_thread,
+ thread_fn callback) {
+ std::shared_ptr<CallbackWrapper> wrapper =
+ std::make_shared<CallbackWrapper>(module, callback_thread, callback);
+ wrapper->lifecycle_thread.StartUp();
+ // Run the actual module start up
+ wrapper->lifecycle_thread.DoInThread(
+ FROM_HERE, base::BindOnce(run_wrapped_start_up, wrapper));
+}
diff --git a/btif/Android.bp b/btif/Android.bp
index d1110520f..dd2412139 100644..100755
--- a/btif/Android.bp
+++ b/btif/Android.bp
@@ -1,14 +1,5 @@
// Common variables
// ========================================================
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
btifCommonIncludes = [
"system/bt",
"system/bt/bta/include",
@@ -58,8 +49,8 @@ cc_library_static {
"src/btif_a2dp_control.cc",
"src/btif_a2dp_sink.cc",
"src/btif_a2dp_source.cc",
- "src/btif_activity_attribution.cc",
"src/btif_av.cc",
+ "src/btif_avrcp_audio_track.cc",
"src/btif_ble_advertiser.cc",
"src/btif_ble_scanner.cc",
"src/btif_bqr.cc",
@@ -76,14 +67,12 @@ cc_library_static {
"src/btif_gatt_server.cc",
"src/btif_gatt_test.cc",
"src/btif_gatt_util.cc",
- "src/btif_vc.cc",
"src/btif_hearing_aid.cc",
"src/btif_hf.cc",
"src/btif_hf_client.cc",
"src/btif_hh.cc",
"src/btif_hd.cc",
- "src/btif_le_audio.cc",
- "src/btif_metrics_logging.cc",
+ "src/btif_mce.cc",
"src/btif_pan.cc",
"src/btif_profile_queue.cc",
"src/btif_rc.cc",
@@ -102,40 +91,32 @@ cc_library_static {
"src/btif_keystore.cc",
"src/stack_manager.cc",
],
+ header_libs: [
+ "libmedia_headers",
+ ],
shared_libs: [
- "android.hardware.bluetooth.a2dp@1.0",
- "android.hardware.bluetooth.audio@2.0",
- "android.hardware.bluetooth.audio@2.1",
- "libcrypto",
+ "libaaudio",
"libcutils",
- "libhidlbase",
+ "libfmq",
"liblog",
+ "libz",
"libtinyxml2",
+ "android.hardware.bluetooth.a2dp@1.0",
+ "android.hardware.bluetooth.audio@2.0",
+ "libhidlbase",
"libutils",
- "libz",
+ "libcrypto",
],
- target: {
- android: {
- shared_libs: [
- "libaaudio",
- "libfmq",
- ],
- srcs: ["src/btif_avrcp_audio_track.cc"],
- },
- host: {
- srcs: ["src/btif_avrcp_audio_track_linux.cc"],
- },
- },
whole_static_libs: [
"avrcp-target-service",
+ "libaudio-a2dp-hw-utils",
"lib-bt-packets",
"libbt-audio-hal-interface",
- "libaudio-a2dp-hw-utils",
],
cflags: [
"-DBUILDCFG",
],
- host_supported: true,
+
}
// btif unit tests for target
@@ -152,12 +133,8 @@ cc_test {
shared_libs: [
"libaaudio",
"android.hardware.bluetooth@1.0",
- "android.hardware.bluetooth@1.1",
"android.hardware.bluetooth.a2dp@1.0",
"android.hardware.bluetooth.audio@2.0",
- "android.hardware.bluetooth.audio@2.1",
- "android.system.suspend.control-V1-ndk",
- "libbinder_ndk",
"libfmq",
"libhidlbase",
"liblog",
@@ -224,9 +201,6 @@ cc_test {
defaults: ["fluoride_defaults"],
test_suites: ["device-tests"],
host_supported: true,
- test_options: {
- unit_test: true,
- },
include_dirs: btifCommonIncludes,
srcs: [
"test/btif_rc_test.cc",
@@ -260,9 +234,6 @@ cc_test {
defaults: ["fluoride_defaults"],
test_suites: ["device-tests"],
host_supported: true,
- test_options: {
- unit_test: true,
- },
include_dirs: btifCommonIncludes,
srcs: [
"src/btif_config_cache.cc",
@@ -303,81 +274,3 @@ cc_test {
],
cflags: ["-DBUILDCFG"],
}
-
-// Cycle stack test
-// ========================================================
-cc_test {
- name: "net_test_btif_stack",
- host_supported: true,
- defaults: ["fluoride_defaults"],
- test_suites: ["device-tests"],
- include_dirs: [
- "frameworks/av/media/libaaudio/include",
- "system/bt",
- "system/bt/bta/dm",
- "system/bt/bta/include",
- "system/bt/bta/sys",
- "system/bt/btif/avrcp",
- "system/bt/btif/co",
- "system/bt/btif/include",
- "system/bt/device/include",
- "system/bt/embdrv/sbc/decoder/include",
- "system/bt/embdrv/sbc/encoder/include",
- "system/bt/gd",
- "system/bt/hci/include",
- "system/bt/include",
- "system/bt/internal_include",
- "system/bt/stack/a2dp",
- "system/bt/stack/avdt",
- "system/bt/stack/btm",
- "system/bt/stack/include",
- "system/bt/stack/l2cap",
- "system/bt/udrv/include",
- "system/bt/utils/include",
- "system/bt/vnd/include",
- "system/libfmq/include",
- "system/libhwbinder/include",
- ],
- srcs: [
- ":LibBluetoothSources",
- ":TestMockAndroidHardware",
- ":TestMockBta",
- ":TestMockBtcore",
- ":TestMockCommon",
- ":TestMockFrameworks",
- ":TestMockHci",
- ":TestMockMainShim",
- ":TestMockStack",
- ":TestMockSystemLibfmq",
- ":TestMockUdrv",
- "test/btif_stack_test.cc",
- ],
- generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- "BluetoothGeneratedDumpsysDataSchema_h",
- "BluetoothGeneratedDumpsysTestData_h",
- "BluetoothGeneratedPackets_h",
- ],
- header_libs: ["libbluetooth_headers"],
- shared_libs: [
- "android.hardware.bluetooth.a2dp@1.0",
- "android.hardware.bluetooth.audio@2.0",
- "android.hardware.bluetooth.audio@2.1",
- "libcrypto",
- "libcutils",
- "libflatbuffers-cpp",
- "libhidlbase",
- "liblog",
- "libtinyxml2",
- ],
- whole_static_libs: [
- "libbtif",
- ],
- static_libs: [
- "libbluetooth-types",
- "libbtdevice",
- "libgmock",
- "libosi",
- ],
- cflags: ["-DBUILDCFG"],
-}
diff --git a/btif/BUILD.gn b/btif/BUILD.gn
index 9d1bc6c3a..5e78d7da2 100644
--- a/btif/BUILD.gn
+++ b/btif/BUILD.gn
@@ -16,43 +16,22 @@
static_library("btif") {
sources = [
- # TODO(abps) - Do we need this?
- "//bt/audio_a2dp_hw/src/audio_a2dp_hw_utils.cc",
- "//bt/audio_hearing_aid_hw/src/audio_hearing_aid_hw_utils.cc",
-
- # AVRCP Target Service
- "avrcp/avrcp_service.cc",
- "co/bta_av_co.cc",
-
- # Callouts
- "co/bta_dm_co.cc",
- "co/bta_gatts_co.cc",
- "co/bta_hh_co.cc",
- "co/bta_pan_co.cc",
-
- # HAL layer
- "src/bluetooth.cc",
-
- # BTIF implementation
+ "//audio_a2dp_hw/src/audio_a2dp_hw_utils.cc",
+ "//audio_hearing_aid_hw/src/audio_hearing_aid_hw_utils.cc",
"src/btif_a2dp.cc",
-
- # "TODO(abps) - Move this abstraction elsewhere
- # "src/btif_a2dp_audio_interface.cc",
"src/btif_a2dp_audio_interface_linux.cc",
"src/btif_a2dp_control.cc",
"src/btif_a2dp_sink.cc",
"src/btif_a2dp_source.cc",
- "src/btif_activity_attribution.cc",
"src/btif_av.cc",
+ "avrcp/avrcp_service.cc",
- # TODO(abps) - Move this abstraction elsewhere
- # "src/btif_avrcp_audio_track.cc",
+ #TODO(jpawlowski): heavily depends on Android,
+ # "src/btif_avrcp_audio_track.cc",
"src/btif_avrcp_audio_track_linux.cc",
"src/btif_ble_advertiser.cc",
"src/btif_ble_scanner.cc",
- "src/btif_bqr.cc",
"src/btif_config.cc",
- "src/btif_config_cache.cc",
"src/btif_config_transcode.cc",
"src/btif_core.cc",
"src/btif_debug.cc",
@@ -64,15 +43,12 @@ static_library("btif") {
"src/btif_gatt_server.cc",
"src/btif_gatt_test.cc",
"src/btif_gatt_util.cc",
- "src/btif_hd.cc",
- "src/btif_vc.cc",
"src/btif_hearing_aid.cc",
"src/btif_hf.cc",
"src/btif_hf_client.cc",
"src/btif_hh.cc",
- "src/btif_keystore.cc",
- "src/btif_le_audio.cc",
- "src/btif_metrics_logging.cc",
+ "src/btif_hd.cc",
+ "src/btif_mce.cc",
"src/btif_pan.cc",
"src/btif_profile_queue.cc",
"src/btif_rc.cc",
@@ -91,40 +67,43 @@ static_library("btif") {
"src/stack_manager.cc",
]
+ # BTIF callouts
+ sources += [
+ "co/bta_dm_co.cc",
+ "co/bta_av_co.cc",
+ "co/bta_hh_co.cc",
+ "co/bta_pan_co.cc",
+ "co/bta_gatts_co.cc",
+ ]
+
include_dirs = [
"include",
- "//bt/",
- "//bt/bta/dm",
- "//bt/linux_include",
- "//bt/audio_a2dp_hw/include",
- "//bt/audio_hearing_aid_hw/include",
- "//bt/bta/include",
- "//bt/bta/sys",
- "//bt/btcore/include",
- "//bt/device/include",
- "//bt/embdrv/sbc/encoder/include",
- "//bt/embdrv/sbc/decoder/include",
- "//bt/hci/include",
- "//bt/stack/a2dp",
- "//bt/stack/btm",
- "//bt/stack/l2cap",
- "//bt/stack/include",
- "//bt/internal_include",
- "//bt/udrv/include",
- "//bt/utils/include",
- "//bt/vnd/include",
- "//bt/profile/avrcp",
+ "//",
+ "//linux_include",
+ "//audio_a2dp_hw/include",
+ "//audio_hearing_aid_hw/include",
+ "//bta/include",
+ "//bta/sys",
+ "//btcore/include",
+ "//device/include",
+ "//embdrv/sbc/encoder/include",
+ "//embdrv/sbc/decoder/include",
+ "//hci/include",
+ "//stack/a2dp",
+ "//stack/btm",
+ "//stack/l2cap",
+ "//stack/include",
+ "//third_party/tinyxml2",
+ "//internal_include",
+ "//udrv/include",
+ "//utils/include",
+ "//vnd/include",
+ "//profile/avrcp",
]
deps = [
- "//bt:libbt-platform-protos-lite",
- "//bt/common",
- "//bt/gd/rust/shim:init_flags_bridge_header",
- "//bt/profile/avrcp:profile_avrcp",
- ]
-
- configs += [
- "//bt:target_defaults",
- "//bt:external_tinyxml2",
+ "//common",
+ "//third_party/libchrome:base",
+ "//profile/avrcp:profile_avrcp"
]
}
diff --git a/btif/avrcp/avrcp_service.cc b/btif/avrcp/avrcp_service.cc
index 51d66feac..1308461f1 100644
--- a/btif/avrcp/avrcp_service.cc
+++ b/btif/avrcp/avrcp_service.cc
@@ -23,10 +23,8 @@
#include <mutex>
#include <sstream>
-#include "abstract_message_loop.h"
#include "btif_av.h"
#include "btif_common.h"
-#include "btif_dm.h"
#include "device.h"
#include "stack/include/btu.h"
@@ -36,8 +34,20 @@ namespace avrcp {
AvrcpService* AvrcpService::instance_ = nullptr;
AvrcpService::ServiceInterfaceImpl* AvrcpService::service_interface_ = nullptr;
+std::mutex jni_mutex_;
+base::MessageLoop* jni_message_loop_ = nullptr;
+base::CancelableTaskTracker task_tracker_;
+
void do_in_avrcp_jni(const base::Closure& task) {
- do_in_jni_thread(FROM_HERE, task);
+ std::lock_guard<std::mutex> lock(jni_mutex_);
+
+ if (jni_message_loop_ == nullptr) {
+ LOG(WARNING) << __func__ << ": jni_message_loop_ is null";
+ return;
+ }
+
+ task_tracker_.PostTask(jni_message_loop_->task_runner().get(), FROM_HERE,
+ task);
}
class A2dpInterfaceImpl : public A2dpInterface {
@@ -50,22 +60,13 @@ class A2dpInterfaceImpl : public A2dpInterface {
class AvrcpInterfaceImpl : public AvrcpInterface {
public:
- uint16_t GetAvrcpVersion() {
- return AVRC_GetProfileVersion();
- }
-
uint16_t AddRecord(uint16_t service_uuid, const char* p_service_name,
const char* p_provider_name, uint16_t categories,
uint32_t sdp_handle, bool browse_supported,
- uint16_t profile_version,
- uint16_t cover_art_psm) override {
+ uint16_t profile_version) override {
return AVRC_AddRecord(service_uuid, p_service_name, p_provider_name,
categories, sdp_handle, browse_supported,
- profile_version, cover_art_psm);
- }
-
- uint16_t RemoveRecord(uint32_t sdp_handle) {
- return AVRC_RemoveRecord(sdp_handle);
+ profile_version);
}
uint16_t FindService(uint16_t service_uuid, const RawAddress& bd_addr,
@@ -286,16 +287,8 @@ void AvrcpService::Init(MediaInterface* media_interface,
VolumeInterface* volume_interface) {
LOG(INFO) << "AVRCP Target Service started";
- profile_version = avrcp_interface_.GetAvrcpVersion();
-
- uint16_t supported_features = GetSupportedFeatures(profile_version);
- sdp_record_handle = SDP_CreateRecord();
-
- avrcp_interface_.AddRecord(UUID_SERVCLASS_AV_REM_CTRL_TARGET,
- "AV Remote Control Target", NULL,
- supported_features, sdp_record_handle, true,
- profile_version, 0);
- btif_dm_add_uuid_to_eir(UUID_SERVCLASS_AV_REM_CTRL_TARGET);
+ // TODO (apanicke): Add a function that sets up the SDP records once we
+ // remove the AVRCP SDP setup in AVDTP (bta_av_main.cc)
media_interface_ = new MediaInterfaceWrapper(media_interface);
media_interface->RegisterUpdateCallback(instance_);
@@ -313,27 +306,9 @@ void AvrcpService::Init(MediaInterface* media_interface,
connection_handler_ = ConnectionHandler::Get();
}
-uint16_t AvrcpService::GetSupportedFeatures(uint16_t profile_version) {
- switch (profile_version) {
- case AVRC_REV_1_6:
- return AVRCP_SUPF_TG_1_6;
- case AVRC_REV_1_5:
- return AVRCP_SUPF_TG_1_5;
- case AVRC_REV_1_4:
- return AVRCP_SUPF_TG_1_4;
- case AVRC_REV_1_3:
- return AVRCP_SUPF_TG_1_3;
- }
- return AVRCP_SUPF_TG_DEFAULT;
-}
-
void AvrcpService::Cleanup() {
LOG(INFO) << "AVRCP Target Service stopped";
- avrcp_interface_.RemoveRecord(sdp_record_handle);
- btif_dm_remove_uuid_from_eir(UUID_SERVCLASS_AV_REM_CTRL_TARGET);
- sdp_record_handle = -1;
-
connection_handler_->CleanUp();
connection_handler_ = nullptr;
if (volume_interface_ != nullptr) {
@@ -342,30 +317,6 @@ void AvrcpService::Cleanup() {
delete media_interface_;
}
-void AvrcpService::RegisterBipServer(int psm) {
- LOG(INFO) << "AVRCP Target Service has registered a BIP OBEX server, psm="
- << psm;
- avrcp_interface_.RemoveRecord(sdp_record_handle);
- uint16_t supported_features
- = GetSupportedFeatures(profile_version) | AVRC_SUPF_TG_PLAYER_COVER_ART;
- sdp_record_handle = SDP_CreateRecord();
- avrcp_interface_.AddRecord(UUID_SERVCLASS_AV_REM_CTRL_TARGET,
- "AV Remote Control Target", NULL,
- supported_features, sdp_record_handle, true,
- profile_version, psm);
-}
-
-void AvrcpService::UnregisterBipServer() {
- LOG(INFO) << "AVRCP Target Service has unregistered a BIP OBEX server";
- avrcp_interface_.RemoveRecord(sdp_record_handle);
- uint16_t supported_features = GetSupportedFeatures(profile_version);
- sdp_record_handle = SDP_CreateRecord();
- avrcp_interface_.AddRecord(UUID_SERVCLASS_AV_REM_CTRL_TARGET,
- "AV Remote Control Target", NULL,
- supported_features, sdp_record_handle, true,
- profile_version, 0);
-}
-
AvrcpService* AvrcpService::Get() {
CHECK(instance_);
return instance_;
@@ -390,13 +341,6 @@ void AvrcpService::DisconnectDevice(const RawAddress& bdaddr) {
connection_handler_->DisconnectDevice(bdaddr);
}
-void AvrcpService::SetBipClientStatus(const RawAddress& bdaddr,
- bool connected) {
- LOG(INFO) << __PRETTY_FUNCTION__ << ": address=" << bdaddr.ToString()
- << ", connected=" << connected;
- connection_handler_->SetBipClientStatus(bdaddr, connected);
-}
-
void AvrcpService::SendMediaUpdate(bool track_changed, bool play_state,
bool queue) {
LOG(INFO) << __PRETTY_FUNCTION__ << " track_changed=" << track_changed
@@ -454,25 +398,16 @@ void AvrcpService::ServiceInterfaceImpl::Init(
CHECK(instance_ == nullptr);
instance_ = new AvrcpService();
+ {
+ std::lock_guard<std::mutex> jni_lock(jni_mutex_);
+ jni_message_loop_ = get_jni_message_loop();
+ }
+
do_in_main_thread(FROM_HERE,
base::Bind(&AvrcpService::Init, base::Unretained(instance_),
media_interface, volume_interface));
}
-void AvrcpService::ServiceInterfaceImpl::RegisterBipServer(int psm) {
- std::lock_guard<std::mutex> lock(service_interface_lock_);
- CHECK(instance_ != nullptr);
- do_in_main_thread(FROM_HERE, base::Bind(&AvrcpService::RegisterBipServer,
- base::Unretained(instance_), psm));
-}
-
-void AvrcpService::ServiceInterfaceImpl::UnregisterBipServer() {
- std::lock_guard<std::mutex> lock(service_interface_lock_);
- CHECK(instance_ != nullptr);
- do_in_main_thread(FROM_HERE, base::Bind(&AvrcpService::UnregisterBipServer,
- base::Unretained(instance_)));
-}
-
bool AvrcpService::ServiceInterfaceImpl::ConnectDevice(
const RawAddress& bdaddr) {
std::lock_guard<std::mutex> lock(service_interface_lock_);
@@ -491,20 +426,17 @@ bool AvrcpService::ServiceInterfaceImpl::DisconnectDevice(
return true;
}
-void AvrcpService::ServiceInterfaceImpl::SetBipClientStatus(
- const RawAddress& bdaddr, bool connected) {
- std::lock_guard<std::mutex> lock(service_interface_lock_);
- CHECK(instance_ != nullptr);
- do_in_main_thread(FROM_HERE, base::Bind(&AvrcpService::SetBipClientStatus,
- base::Unretained(instance_), bdaddr,
- connected));
-}
-
bool AvrcpService::ServiceInterfaceImpl::Cleanup() {
std::lock_guard<std::mutex> lock(service_interface_lock_);
if (instance_ == nullptr) return false;
+ {
+ std::lock_guard<std::mutex> jni_lock(jni_mutex_);
+ task_tracker_.TryCancelAll();
+ jni_message_loop_ = nullptr;
+ }
+
do_in_main_thread(FROM_HERE,
base::Bind(&AvrcpService::Cleanup, base::Owned(instance_)));
diff --git a/btif/avrcp/avrcp_service.h b/btif/avrcp/avrcp_service.h
index 067631ecd..e19899ded 100644
--- a/btif/avrcp/avrcp_service.h
+++ b/btif/avrcp/avrcp_service.h
@@ -18,7 +18,6 @@
#include <map>
#include <memory>
-#include <mutex>
#include "hardware/avrcp/avrcp.h"
#include "osi/include/properties.h"
@@ -57,14 +56,9 @@ class AvrcpService : public MediaCallbacks {
void Init(MediaInterface* media_interface, VolumeInterface* volume_interface);
void Cleanup();
- void RegisterBipServer(int psm);
- void UnregisterBipServer();
-
void ConnectDevice(const RawAddress& bdaddr);
void DisconnectDevice(const RawAddress& bdaddr);
- void SetBipClientStatus(const RawAddress& bdaddr, bool connected);
-
// Functions inherited from MediaCallbacks in order to receive updates
void SendMediaUpdate(bool track_changed, bool play_state,
bool queue) override;
@@ -76,11 +70,8 @@ class AvrcpService : public MediaCallbacks {
public:
void Init(MediaInterface* media_interface,
VolumeInterface* volume_interface) override;
- void RegisterBipServer(int psm) override;
- void UnregisterBipServer() override;
bool ConnectDevice(const RawAddress& bdaddr) override;
bool DisconnectDevice(const RawAddress& bdaddr) override;
- void SetBipClientStatus(const RawAddress& bdaddr, bool connected) override;
bool Cleanup() override;
private:
@@ -91,15 +82,11 @@ class AvrcpService : public MediaCallbacks {
protected:
void DeviceCallback(std::shared_ptr<Device> device);
- uint16_t GetSupportedFeatures(uint16_t profile_version);
private:
static AvrcpService* instance_;
static ServiceInterfaceImpl* service_interface_;
- uint32_t sdp_record_handle = -1;
- uint16_t profile_version = -1;
-
MediaInterface* media_interface_ = nullptr;
VolumeInterface* volume_interface_ = nullptr;
@@ -111,4 +98,4 @@ class AvrcpService : public MediaCallbacks {
inline bool is_new_avrcp_enabled() {
return osi_property_get_bool("persist.bluetooth.enablenewavrcp", true);
-}
+} \ No newline at end of file
diff --git a/btif/co/bta_av_co.cc b/btif/co/bta_av_co.cc
index 463612011..708bb4076 100644
--- a/btif/co/bta_av_co.cc
+++ b/btif/co/bta_av_co.cc
@@ -24,19 +24,25 @@
******************************************************************************/
#include <mutex>
-#include <vector>
-#include "bt_target.h" // Must be first to define build configuration
+#include <base/bind.h>
+#include <base/logging.h>
+#include <string.h>
-#include "bta/include/bta_av_api.h"
-#include "bta/include/bta_av_ci.h"
-#include "btif/include/btif_a2dp_source.h"
-#include "btif/include/btif_av.h"
-#include "include/hardware/bt_av.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/include/a2dp_codec_api.h"
-#include "stack/include/a2dp_error_codes.h"
-#include "stack/include/avdt_api.h"
+#include "bt_target.h"
+
+#include "a2dp_api.h"
+#include "a2dp_sbc.h"
+#include "bta_av_api.h"
+#include "bta_av_ci.h"
+#include "bta_av_co.h"
+#include "bta_sys.h"
+
+#include "btif_av.h"
+#include "btif_av_co.h"
+#include "btif_util.h"
+#include "osi/include/osi.h"
+#include "osi/include/properties.h"
// Macro to retrieve the number of elements in a statically allocated array
#define BTA_AV_CO_NUM_ELEMENTS(__a) (sizeof(__a) / sizeof((__a)[0]))
@@ -2201,19 +2207,10 @@ bool bta_av_co_set_codec_audio_config(
return bta_av_co_cb.SetCodecAudioConfig(codec_audio_config);
}
-btav_a2dp_scmst_info_t bta_av_co_get_scmst_info(
- const RawAddress& peer_address) {
+bool bta_av_co_content_protect_is_active(const RawAddress& peer_address) {
BtaAvCoPeer* p_peer = bta_av_co_cb.FindPeer(peer_address);
CHECK(p_peer != nullptr);
- btav_a2dp_scmst_info_t scmst_info{};
- scmst_info.enable_status = BTAV_A2DP_SCMST_DISABLED;
-
- if (p_peer->ContentProtectActive()) {
- scmst_info.enable_status = BTAV_A2DP_SCMST_ENABLED;
- scmst_info.cp_header = bta_av_co_cb.ContentProtectFlag();
- }
-
- return scmst_info;
+ return p_peer->ContentProtectActive();
}
void btif_a2dp_codec_debug_dump(int fd) { bta_av_co_cb.DebugDump(fd); }
diff --git a/btif/co/bta_dm_co.cc b/btif/co/bta_dm_co.cc
index 34664819e..200ce556c 100644
--- a/btif/co/bta_dm_co.cc
+++ b/btif/co/bta_dm_co.cc
@@ -57,3 +57,227 @@ bool bta_dm_co_get_compress_memory(UNUSED_ATTR tBTA_SYS_ID id,
return true;
}
+/*******************************************************************************
+ *
+ * Function bta_dm_co_io_req
+ *
+ * Description This callout function is executed by DM to get IO
+ * capabilities of the local device for the Simple Pairing
+ * process.
+ *
+ * Parameters bd_addr - The peer device
+ * *p_io_cap - The local Input/Output capabilities
+ * *p_oob_data - true, if OOB data is available for the peer
+ * device.
+ * *p_auth_req - true, if MITM protection is required.
+ *
+ * Returns void.
+ *
+ ******************************************************************************/
+void bta_dm_co_io_req(UNUSED_ATTR const RawAddress& bd_addr,
+ tBTA_IO_CAP* p_io_cap, tBTA_OOB_DATA* p_oob_data,
+ tBTA_AUTH_REQ* p_auth_req, bool is_orig) {
+ btif_dm_set_oob_for_io_req(p_oob_data);
+ btif_dm_proc_io_req(bd_addr, p_io_cap, p_oob_data, p_auth_req, is_orig);
+ BTIF_TRACE_DEBUG("bta_dm_co_io_req *p_oob_data = %d", *p_oob_data);
+ BTIF_TRACE_DEBUG("bta_dm_co_io_req *p_io_cap = %d", *p_io_cap);
+ BTIF_TRACE_DEBUG("bta_dm_co_io_req *p_auth_req = %d", *p_auth_req);
+ BTIF_TRACE_DEBUG("bta_dm_co_io_req is_orig = %d", is_orig);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_co_io_rsp
+ *
+ * Description This callout function is executed by DM to report IO
+ * capabilities of the peer device for the Simple Pairing
+ * process.
+ *
+ * Parameters bd_addr - The peer device
+ * io_cap - The remote Input/Output capabilities
+ * oob_data - true, if OOB data is available for the peer
+ * device.
+ * auth_req - true, if MITM protection is required.
+ *
+ * Returns void.
+ *
+ ******************************************************************************/
+void bta_dm_co_io_rsp(const RawAddress& bd_addr, tBTA_IO_CAP io_cap,
+ tBTA_OOB_DATA oob_data, tBTA_AUTH_REQ auth_req) {
+ btif_dm_proc_io_rsp(bd_addr, io_cap, oob_data, auth_req);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_co_lk_upgrade
+ *
+ * Description This callout function is executed by DM to check if the
+ * platform wants allow link key upgrade
+ *
+ * Parameters bd_addr - The peer device
+ * *p_upgrade - true, if link key upgrade is desired.
+ *
+ * Returns void.
+ *
+ ******************************************************************************/
+void bta_dm_co_lk_upgrade(UNUSED_ATTR const RawAddress& bd_addr,
+ UNUSED_ATTR bool* p_upgrade) {}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_co_loc_oob
+ *
+ * Description This callout function is executed by DM to report the OOB
+ * data of the local device for the Simple Pairing process
+ *
+ * Parameters valid - true, if the local OOB data is retrieved from LM
+ * c - Simple Pairing Hash C
+ * r - Simple Pairing Randomnizer R
+ *
+ * Returns void.
+ *
+ ******************************************************************************/
+void bta_dm_co_loc_oob(bool valid, const Octet16& c, const Octet16& r) {
+ BTIF_TRACE_DEBUG("bta_dm_co_loc_oob, valid = %d", valid);
+#ifdef BTIF_DM_OOB_TEST
+ btif_dm_proc_loc_oob(valid, c, r);
+#endif
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_co_rmt_oob
+ *
+ * Description This callout function is executed by DM to request the OOB
+ * data for the remote device for the Simple Pairing process
+ * Need to call bta_dm_ci_rmt_oob() in response
+ *
+ * Parameters bd_addr - The peer device
+ *
+ * Returns void.
+ *
+ ******************************************************************************/
+void bta_dm_co_rmt_oob(const RawAddress& bd_addr) {
+ Octet16 c;
+ Octet16 r;
+ bool result = false;
+
+#ifdef BTIF_DM_OOB_TEST
+ result = btif_dm_proc_rmt_oob(bd_addr, &c, &r);
+#endif
+
+ BTIF_TRACE_DEBUG("bta_dm_co_rmt_oob: result=%d", result);
+ bta_dm_ci_rmt_oob(result, bd_addr, c, r);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_co_le_io_key_req
+ *
+ * Description This callout function is executed by DM to get BLE key
+ * information
+ * before SMP pairing gets going.
+ *
+ * Parameters bd_addr - The peer device
+ * *p_max_key_size - max key size local device supported.
+ * *p_init_key - initiator keys.
+ * *p_resp_key - responder keys.
+ *
+ * Returns void.
+ *
+ ******************************************************************************/
+void bta_dm_co_le_io_key_req(UNUSED_ATTR const RawAddress& bd_addr,
+ uint8_t* p_max_key_size,
+ tBTA_LE_KEY_TYPE* p_init_key,
+ tBTA_LE_KEY_TYPE* p_resp_key) {
+ BTIF_TRACE_ERROR("##################################");
+ BTIF_TRACE_ERROR("bta_dm_co_le_io_key_req: only setting max size to 16");
+ BTIF_TRACE_ERROR("##################################");
+ *p_max_key_size = 16;
+ *p_init_key = *p_resp_key =
+ (BTA_LE_KEY_PENC | BTA_LE_KEY_PID | BTA_LE_KEY_PCSRK | BTA_LE_KEY_LENC |
+ BTA_LE_KEY_LID | BTA_LE_KEY_LCSRK);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_co_ble_local_key_reload
+ *
+ * Description This callout function is to load the local BLE keys if
+ * available on the device.
+ *
+ * Parameters none
+ *
+ * Returns void.
+ *
+ ******************************************************************************/
+void bta_dm_co_ble_load_local_keys(tBTA_DM_BLE_LOCAL_KEY_MASK* p_key_mask,
+ Octet16* p_er,
+ tBTA_BLE_LOCAL_ID_KEYS* p_id_keys) {
+ BTIF_TRACE_DEBUG("##################################");
+ BTIF_TRACE_DEBUG(
+ "bta_dm_co_ble_load_local_keys: Load local keys if any are persisted");
+ BTIF_TRACE_DEBUG("##################################");
+ btif_dm_get_ble_local_keys(p_key_mask, p_er, p_id_keys);
+}
+
+/*******************************************************************************
+ *
+ * Function bta_dm_co_ble_io_req
+ *
+ * Description This callout function is executed by DM to get BLE IO
+ * capabilities before SMP pairing gets going.
+ *
+ * Parameters bd_addr - The peer device
+ * *p_io_cap - The local Input/Output capabilities
+ * *p_oob_data - true, if OOB data is available for the peer
+ * device.
+ * *p_auth_req - Auth request setting (Bonding and MITM
+ * required or not)
+ * *p_max_key_size - max key size local device supported.
+ * *p_init_key - initiator keys.
+ * *p_resp_key - responder keys.
+ *
+ * Returns void.
+ *
+ ******************************************************************************/
+void bta_dm_co_ble_io_req(const RawAddress& bd_addr, tBTA_IO_CAP* p_io_cap,
+ tBTA_OOB_DATA* p_oob_data,
+ tBTA_LE_AUTH_REQ* p_auth_req, uint8_t* p_max_key_size,
+ tBTA_LE_KEY_TYPE* p_init_key,
+ tBTA_LE_KEY_TYPE* p_resp_key) {
+ bte_appl_cfg.ble_io_cap = btif_storage_get_local_io_caps_ble();
+
+ /* Retrieve the properties from file system if possible */
+ tBTE_APPL_CFG nv_config;
+ if (btif_dm_get_smp_config(&nv_config)) bte_appl_cfg = nv_config;
+
+ /* *p_auth_req by default is false for devices with NoInputNoOutput; true for
+ * other devices. */
+
+ if (bte_appl_cfg.ble_auth_req)
+ *p_auth_req = bte_appl_cfg.ble_auth_req |
+ (bte_appl_cfg.ble_auth_req & 0x04) | ((*p_auth_req) & 0x04);
+
+ /* if OOB is not supported, this call-out function does not need to do
+ * anything
+ * otherwise, look for the OOB data associated with the address and set
+ * *p_oob_data accordingly.
+ * If the answer can not be obtained right away,
+ * set *p_oob_data to BTA_OOB_UNKNOWN and call bta_dm_ci_io_req() when the
+ * answer is available.
+ */
+
+ btif_dm_set_oob_for_le_io_req(bd_addr, p_oob_data, p_auth_req);
+
+ if (bte_appl_cfg.ble_io_cap <= 4) *p_io_cap = bte_appl_cfg.ble_io_cap;
+
+ if (bte_appl_cfg.ble_init_key <= BTM_BLE_INITIATOR_KEY_SIZE)
+ *p_init_key = bte_appl_cfg.ble_init_key;
+
+ if (bte_appl_cfg.ble_resp_key <= BTM_BLE_RESPONDER_KEY_SIZE)
+ *p_resp_key = bte_appl_cfg.ble_resp_key;
+
+ if (bte_appl_cfg.ble_max_key_size > 7 && bte_appl_cfg.ble_max_key_size <= 16)
+ *p_max_key_size = bte_appl_cfg.ble_max_key_size;
+}
diff --git a/btif/co/bta_hh_co.cc b/btif/co/bta_hh_co.cc
index c5aba4425..cec3f6927 100644
--- a/btif/co/bta_hh_co.cc
+++ b/btif/co/bta_hh_co.cc
@@ -37,11 +37,12 @@
const char* dev_path = "/dev/uhid";
+#if (BTA_HH_LE_INCLUDED == TRUE)
#include "btif_config.h"
#define BTA_HH_NV_LOAD_MAX 16
static tBTA_HH_RPT_CACHE_ENTRY sReportCache[BTA_HH_NV_LOAD_MAX];
+#endif
#define GET_RPT_RSP_OFFSET 9
-#define BTA_HH_CACHE_REPORT_VERSION 1
#define THREAD_NORMAL_PRIORITY 0
#define BT_HH_THREAD "bt_hh_thread"
@@ -127,7 +128,8 @@ static int uhid_read_event(btif_hh_device_t* p_dev) {
btif_hh_setreport(p_dev, BTHH_FEATURE_REPORT, ev.u.output.size,
ev.u.output.data);
else if (ev.u.output.rtype == UHID_OUTPUT_REPORT)
- btif_hh_senddata(p_dev, ev.u.output.size, ev.u.output.data);
+ btif_hh_setreport(p_dev, BTHH_OUTPUT_REPORT, ev.u.output.size,
+ ev.u.output.data);
else
APPL_TRACE_ERROR("%s: UHID_OUTPUT: Invalid report type = %d", __func__,
ev.u.output.rtype);
@@ -161,7 +163,6 @@ static int uhid_read_event(btif_hh_device_t* p_dev) {
APPL_TRACE_ERROR("%s: UHID_FEATURE: Invalid report type = %d", __func__,
ev.u.feature.rtype);
break;
-#ifdef OS_ANDROID // Host kernel does not support UHID_SET_REPORT
case UHID_SET_REPORT:
if (ret < (ssize_t)(sizeof(ev.type) + sizeof(ev.u.set_report))) {
APPL_TRACE_ERROR("%s: Invalid size read from uhid-dev: %zd < %zu",
@@ -185,7 +186,6 @@ static int uhid_read_event(btif_hh_device_t* p_dev) {
APPL_TRACE_ERROR("%s:UHID_SET_REPORT: Invalid Report type = %d"
, __func__, ev.u.set_report.rtype);
break;
-#endif // ifdef OS_ANDROID
default:
APPL_TRACE_DEBUG("Invalid event from uhid-dev: %u\n", ev.type);
}
@@ -229,6 +229,7 @@ static inline pthread_t create_thread(void* (*start_routine)(void*),
******************************************************************************/
static void* btif_hh_poll_event_thread(void* arg) {
btif_hh_device_t* p_dev = (btif_hh_device_t*)arg;
+ APPL_TRACE_DEBUG("%s: Thread created fd = %d", __func__, p_dev->fd);
struct pollfd pfds[1];
// This thread is created by bt_main_thread with RT priority. Lower the thread
@@ -240,10 +241,7 @@ static void* btif_hh_poll_event_thread(void* arg) {
p_dev->hh_poll_thread_id = -1;
return 0;
}
- p_dev->pid = gettid();
pthread_setname_np(pthread_self(), BT_HH_THREAD);
- LOG_DEBUG("Host hid polling thread created name:%s pid:%d fd:%d",
- BT_HH_THREAD, p_dev->pid, p_dev->fd);
pfds[0].fd = p_dev->fd;
pfds[0].events = POLLIN;
@@ -267,7 +265,6 @@ static void* btif_hh_poll_event_thread(void* arg) {
}
p_dev->hh_poll_thread_id = -1;
- p_dev->pid = -1;
return 0;
}
@@ -617,6 +614,7 @@ void bta_hh_co_get_rpt_rsp(uint8_t dev_handle, uint8_t status, uint8_t* p_rpt,
}
}
+#if (BTA_HH_LE_INCLUDED == TRUE)
/*******************************************************************************
*
* Function bta_hh_le_co_rpt_info
@@ -651,7 +649,6 @@ void bta_hh_le_co_rpt_info(const RawAddress& remote_bda,
memcpy(&sReportCache[idx++], p_entry, sizeof(tBTA_HH_RPT_CACHE_ENTRY));
btif_config_set_bin(bdstr, "HidReport", (const uint8_t*)sReportCache,
idx * sizeof(tBTA_HH_RPT_CACHE_ENTRY));
- btif_config_set_int(bdstr, "HidReportVersion", BTA_HH_CACHE_REPORT_VERSION);
BTIF_TRACE_DEBUG("%s() - Saving report; dev=%s, idx=%d", __func__, bdstr,
idx);
}
@@ -663,14 +660,14 @@ void bta_hh_le_co_rpt_info(const RawAddress& remote_bda,
*
* Description This callout function is to request the application to load
* the cached HOGP report if there is any. When cache reading
- * is completed, bta_hh_le_co_cache_load() is called by the
+ * is completed, bta_hh_le_ci_cache_load() is called by the
* application.
*
* Parameters remote_bda - remote device address
- * p_num_rpt - number of cached report
+ * p_num_rpt: number of cached report
* app_id - application id
*
- * Returns the cached report array
+ * Returns the acched report array
*
******************************************************************************/
tBTA_HH_RPT_CACHE_ENTRY* bta_hh_le_co_cache_load(const RawAddress& remote_bda,
@@ -684,15 +681,6 @@ tBTA_HH_RPT_CACHE_ENTRY* bta_hh_le_co_cache_load(const RawAddress& remote_bda,
if (len > sizeof(sReportCache)) len = sizeof(sReportCache);
btif_config_get_bin(bdstr, "HidReport", (uint8_t*)sReportCache, &len);
-
- int cache_version = -1;
- btif_config_get_int(bdstr, "HidReportVersion", &cache_version);
-
- if (cache_version != BTA_HH_CACHE_REPORT_VERSION) {
- bta_hh_le_co_reset_rpt_cache(remote_bda, app_id);
- return NULL;
- }
-
*p_num_rpt = len / sizeof(tBTA_HH_RPT_CACHE_ENTRY);
BTIF_TRACE_DEBUG("%s() - Loaded %d reports; dev=%s", __func__, *p_num_rpt,
@@ -718,6 +706,8 @@ void bta_hh_le_co_reset_rpt_cache(const RawAddress& remote_bda,
const char* bdstr = addrstr.c_str();
btif_config_remove(bdstr, "HidReport");
- btif_config_remove(bdstr, "HidReportVersion");
+
BTIF_TRACE_DEBUG("%s() - Reset cache for bda %s", __func__, bdstr);
}
+
+#endif // (BTA_HH_LE_INCLUDED == TRUE)
diff --git a/btif/co/bta_pan_co.cc b/btif/co/bta_pan_co.cc
index 112c1a714..86499f3a1 100644
--- a/btif/co/bta_pan_co.cc
+++ b/btif/co/bta_pan_co.cc
@@ -59,6 +59,51 @@ uint8_t bta_pan_co_init(uint8_t* q_level) {
return (BTA_PAN_RX_PUSH_BUF | BTA_PAN_RX_PUSH | BTA_PAN_TX_PULL);
}
+/******************************************************************************
+ *
+ * Function bta_pan_co_open
+ *
+ * Description
+ *
+ *
+ *
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_pan_co_open(uint16_t handle, uint8_t app_id, tBTA_PAN_ROLE local_role,
+ tBTA_PAN_ROLE peer_role, const RawAddress& peer_addr) {
+ BTIF_TRACE_API(
+ "bta_pan_co_open:app_id:%d, local_role:%d, peer_role:%d, "
+ "handle:%d",
+ app_id, local_role, peer_role, handle);
+ btpan_conn_t* conn = btpan_find_conn_addr(peer_addr);
+ if (conn == NULL)
+ conn = btpan_new_conn(handle, peer_addr, local_role, peer_role);
+ if (conn) {
+ BTIF_TRACE_DEBUG(
+ "bta_pan_co_open:tap_fd:%d, open_count:%d, "
+ "conn->handle:%d should = handle:%d, local_role:%d, remote_role:%d",
+ btpan_cb.tap_fd, btpan_cb.open_count, conn->handle, handle,
+ conn->local_role, conn->remote_role);
+ // refresh the role & bt address
+
+ btpan_cb.open_count++;
+ conn->handle = handle;
+ // conn->peer = peer_addr;
+ if (btpan_cb.tap_fd < 0) {
+ btpan_cb.tap_fd = btpan_tap_open();
+ if (btpan_cb.tap_fd >= 0) create_tap_read_thread(btpan_cb.tap_fd);
+ }
+ if (btpan_cb.tap_fd >= 0) {
+ btpan_cb.flow = 1;
+ conn->state = PAN_STATE_OPEN;
+ bta_pan_ci_rx_ready(handle);
+ }
+ }
+}
+
/*******************************************************************************
*
* Function bta_pan_co_close
@@ -167,6 +212,29 @@ void bta_pan_co_rx_path(UNUSED_ATTR uint16_t handle,
/*******************************************************************************
*
+ * Function bta_pan_co_tx_write
+ *
+ * Description This function is called by PAN to send data to the phone
+ * when the TX path is configured to use a push interface.
+ * The implementation of this function must copy the data to
+ * the phone's memory.
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void bta_pan_co_tx_write(UNUSED_ATTR uint16_t handle,
+ UNUSED_ATTR uint8_t app_id,
+ UNUSED_ATTR const RawAddress& src,
+ UNUSED_ATTR const RawAddress& dst,
+ UNUSED_ATTR uint16_t protocol,
+ UNUSED_ATTR uint8_t* p_data, UNUSED_ATTR uint16_t len,
+ UNUSED_ATTR bool ext, UNUSED_ATTR bool forward) {
+ BTIF_TRACE_API("bta_pan_co_tx_write not used");
+}
+
+/*******************************************************************************
+ *
* Function bta_pan_co_rx_flow
*
* Description This function is called by PAN to enable or disable
diff --git a/btif/include/btif_a2dp_sink.h b/btif/include/btif_a2dp_sink.h
index f5f2a0c39..b972c79f9 100644
--- a/btif/include/btif_a2dp_sink.h
+++ b/btif/include/btif_a2dp_sink.h
@@ -20,12 +20,12 @@
#ifndef BTIF_A2DP_SINK_H
#define BTIF_A2DP_SINK_H
-#include <cstdint>
+#include <inttypes.h>
+#include <stdbool.h>
#include <future>
-#include "audio_a2dp_hw/include/audio_a2dp_hw.h"
-#include "bta/include/bta_av_api.h"
-#include "types/raw_address.h"
+#include "bt_types.h"
+#include "bta_av_api.h"
//
// Audio focus state for audio track.
diff --git a/btif/include/btif_a2dp_source.h b/btif/include/btif_a2dp_source.h
index 60e5e0d3d..6d2cbb1d9 100644
--- a/btif/include/btif_a2dp_source.h
+++ b/btif/include/btif_a2dp_source.h
@@ -20,13 +20,10 @@
#ifndef BTIF_A2DP_SOURCE_H
#define BTIF_A2DP_SOURCE_H
-#include <cstdint>
+#include <stdbool.h>
#include <future>
-#include <vector>
-#include "bta/include/bta_av_api.h"
-#include "include/hardware/bt_av.h"
-#include "types/raw_address.h"
+#include "bta_av_api.h"
// Initialize the A2DP Source module.
// This function should be called by the BTIF state machine prior to using the
@@ -129,8 +126,4 @@ BT_HDR* btif_a2dp_source_audio_readbuf(void);
// information.
void btif_a2dp_source_debug_dump(int fd);
-// Set the dynamic audio buffer size
-void btif_a2dp_source_set_dynamic_audio_buffer_size(
- uint8_t dynamic_audio_buffer_size);
-
#endif /* BTIF_A2DP_SOURCE_H */
diff --git a/btif/include/btif_acl.h b/btif/include/btif_acl.h
deleted file mode 100644
index 0fa6d93bb..000000000
--- a/btif/include/btif_acl.h
+++ /dev/null
@@ -1,21 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-
-void BTIF_dm_report_inquiry_status_change(uint8_t busy_level_flags);
diff --git a/btif/include/btif_activity_attribution.h b/btif/include/btif_activity_attribution.h
deleted file mode 100644
index 44b585575..000000000
--- a/btif/include/btif_activity_attribution.h
+++ /dev/null
@@ -1,25 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <hardware/bt_activity_attribution.h>
-
-namespace bluetooth {
-namespace activity_attribution {
-
-ActivityAttributionInterface* get_activity_attribution_instance();
-
-}
-} // namespace bluetooth
diff --git a/btif/include/btif_api.h b/btif/include/btif_api.h
index 3a7c2d7f7..f9b888691 100644
--- a/btif/include/btif_api.h
+++ b/btif/include/btif_api.h
@@ -63,6 +63,19 @@ bt_status_t btif_enable_bluetooth(void);
/*******************************************************************************
*
+ * Function btif_disable_bluetooth
+ *
+ * Description Inititates shutdown of Bluetooth system.
+ * Any active links will be dropped and device entering
+ * non connectable/discoverable mode
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+bt_status_t btif_disable_bluetooth(void);
+
+/*******************************************************************************
+ *
* Function btif_cleanup_bluetooth
*
* Description Cleanup BTIF state.
@@ -92,23 +105,24 @@ bool is_restricted_mode(void);
/*******************************************************************************
*
- * Function is_common_criteria_mode
+ * Function is_niap_mode_
*
- * Description Check if BT is enabled in common criteria mode. In this
- * mode, will use the LTK from the keystore to authenticate.
+ * Description Checks if BT was enabled in single user mode. In this
+ * mode, use of keystore for key attestation of LTK is limitee
+ * to this mode defined by UserManager.
*
* Returns bool
*
******************************************************************************/
-bool is_common_criteria_mode(void);
+bool is_niap_mode(void);
/*******************************************************************************
*
- * Function get_common_criteria_config_compare_result
+ * Function get_niap_config_compare_result
*
- * Description Get the common criteria config compare result for confirming
- * the config checksum compare result. When the common criteria
- * mode doesn't enable, it should be all pass (0b11).
+ * Description Get the niap config compare result for confirming the config
+ * checksum compare result. When the niap mode doesn't enable,
+ * it should be all pass (0b11).
* Bit define:
* CONFIG_FILE_COMPARE_PASS = 0b01
* CONFIG_BACKUP_COMPARE_PASS = 0b10
@@ -116,7 +130,7 @@ bool is_common_criteria_mode(void);
* Returns int
*
******************************************************************************/
-int get_common_criteria_config_compare_result(void);
+int get_niap_config_compare_result(void);
/*******************************************************************************
*
@@ -136,10 +150,10 @@ bool is_atv_device(void);
*
* Description Fetches all local adapter properties
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_get_adapter_properties(void);
-
-bt_property_t* property_deep_copy(const bt_property_t* prop);
+bt_status_t btif_get_adapter_properties(void);
/*******************************************************************************
*
@@ -147,8 +161,10 @@ bt_property_t* property_deep_copy(const bt_property_t* prop);
*
* Description Fetches property value from local cache
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_get_adapter_property(bt_property_type_t type);
+bt_status_t btif_get_adapter_property(bt_property_type_t type);
/*******************************************************************************
*
@@ -157,8 +173,10 @@ void btif_get_adapter_property(bt_property_type_t type);
* Description Updates core stack with property value and stores it in
* local cache
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_set_adapter_property(bt_property_t* property);
+bt_status_t btif_set_adapter_property(const bt_property_t* property);
/*******************************************************************************
*
@@ -166,9 +184,11 @@ void btif_set_adapter_property(bt_property_t* property);
*
* Description Fetches the remote device property from the NVRAM
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_get_remote_device_property(RawAddress remote_addr,
- bt_property_type_t type);
+bt_status_t btif_get_remote_device_property(RawAddress* remote_addr,
+ bt_property_type_t type);
/*******************************************************************************
*
@@ -176,8 +196,10 @@ void btif_get_remote_device_property(RawAddress remote_addr,
*
* Description Fetches all the remote device properties from NVRAM
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_get_remote_device_properties(RawAddress remote_addr);
+bt_status_t btif_get_remote_device_properties(RawAddress* remote_addr);
/*******************************************************************************
*
@@ -187,9 +209,24 @@ void btif_get_remote_device_properties(RawAddress remote_addr);
* Currently, BT_PROPERTY_REMOTE_FRIENDLY_NAME is the only
* remote device property that can be set
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_set_remote_device_property(RawAddress* remote_addr,
- bt_property_t* property);
+bt_status_t btif_set_remote_device_property(RawAddress* remote_addr,
+ const bt_property_t* property);
+
+/*******************************************************************************
+ *
+ * Function btif_get_remote_service_record
+ *
+ * Description Looks up the service matching uuid on the remote device
+ * and fetches the SCN and service_name if the UUID is found
+ *
+ * Returns bt_status_t
+ *
+ ******************************************************************************/
+bt_status_t btif_get_remote_service_record(const RawAddress& remote_addr,
+ const bluetooth::Uuid& uuid);
/*******************************************************************************
* BTIF DM API
@@ -201,8 +238,11 @@ void btif_set_remote_device_property(RawAddress* remote_addr,
*
* Description Start device discovery/inquiry
*
+ *
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_start_discovery(void);
+bt_status_t btif_dm_start_discovery(void);
/*******************************************************************************
*
@@ -210,18 +250,21 @@ void btif_dm_start_discovery(void);
*
* Description Cancels search
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_cancel_discovery(void);
+bt_status_t btif_dm_cancel_discovery(void);
-bool btif_dm_pairing_is_busy();
/*******************************************************************************
*
* Function btif_dm_create_bond
*
* Description Initiate bonding with the specified device
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_create_bond(const RawAddress bd_addr, int transport);
+bt_status_t btif_dm_create_bond(const RawAddress* bd_addr, int transport);
/*******************************************************************************
*
@@ -229,11 +272,12 @@ void btif_dm_create_bond(const RawAddress bd_addr, int transport);
*
* Description Initiate bonding with the specified device using OOB data.
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_create_bond_out_of_band(const RawAddress bd_addr,
- tBT_TRANSPORT transport,
- const bt_oob_data_t p192_data,
- const bt_oob_data_t p256_data);
+bt_status_t btif_dm_create_bond_out_of_band(
+ const RawAddress* bd_addr, int transport,
+ const bt_out_of_band_data_t* oob_data);
/*******************************************************************************
*
@@ -241,8 +285,10 @@ void btif_dm_create_bond_out_of_band(const RawAddress bd_addr,
*
* Description Initiate bonding with the specified device
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_cancel_bond(const RawAddress bd_addr);
+bt_status_t btif_dm_cancel_bond(const RawAddress* bd_addr);
/*******************************************************************************
*
@@ -250,8 +296,10 @@ void btif_dm_cancel_bond(const RawAddress bd_addr);
*
* Description Removes bonding with the specified device
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_remove_bond(const RawAddress bd_addr);
+bt_status_t btif_dm_remove_bond(const RawAddress* bd_addr);
/*******************************************************************************
*
@@ -270,9 +318,11 @@ uint16_t btif_dm_get_connection_state(const RawAddress* bd_addr);
*
* Description BT legacy pairing - PIN code reply
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_pin_reply(const RawAddress bd_addr, uint8_t accept,
- uint8_t pin_len, bt_pin_code_t pin_code);
+bt_status_t btif_dm_pin_reply(const RawAddress* bd_addr, uint8_t accept,
+ uint8_t pin_len, bt_pin_code_t* pin_code);
/*******************************************************************************
*
@@ -293,9 +343,12 @@ bt_status_t btif_dm_passkey_reply(const RawAddress* bd_addr, uint8_t accept,
* Description BT SSP Reply - Just Works, Numeric Comparison & Passkey
* Entry
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_ssp_reply(const RawAddress bd_addr, bt_ssp_variant_t variant,
- uint8_t accept);
+bt_status_t btif_dm_ssp_reply(const RawAddress* bd_addr,
+ bt_ssp_variant_t variant, uint8_t accept,
+ uint32_t passkey);
/*******************************************************************************
*
@@ -317,7 +370,31 @@ bt_status_t btif_dm_get_adapter_property(bt_property_t* prop);
* Returns bt_status_t
*
******************************************************************************/
-void btif_dm_get_remote_services(const RawAddress remote_addr, int transport);
+bt_status_t btif_dm_get_remote_service_record(const RawAddress& remote_addr,
+ const bluetooth::Uuid& uuid);
+
+/*******************************************************************************
+ *
+ * Function btif_dm_get_remote_services
+ *
+ * Description Start SDP to get remote services
+ *
+ * Returns bt_status_t
+ *
+ ******************************************************************************/
+bt_status_t btif_dm_get_remote_services(const RawAddress& remote_addr);
+
+/*******************************************************************************
+ *
+ * Function btif_dm_get_remote_services_by_transport
+ *
+ * Description Start SDP to get remote services by transport
+ *
+ * Returns bt_status_t
+ *
+ ******************************************************************************/
+bt_status_t btif_dm_get_remote_services_by_transport(RawAddress* remote_addr,
+ int transport);
/*******************************************************************************
*
@@ -326,10 +403,10 @@ void btif_dm_get_remote_services(const RawAddress remote_addr, int transport);
* Description Configure Test Mode - 'enable' to 1 puts the device in test
* mode and 0 exits test mode
*
+ * Returns BT_STATUS_SUCCESS on success
+ *
******************************************************************************/
-void btif_dut_mode_configure(uint8_t enable);
-
-bool btif_is_dut_mode();
+bt_status_t btif_dut_mode_configure(uint8_t enable);
/*******************************************************************************
*
@@ -337,14 +414,21 @@ bool btif_is_dut_mode();
*
* Description Sends a HCI Vendor specific command to the controller
*
+ * Returns BT_STATUS_SUCCESS on success
+ *
******************************************************************************/
-void btif_dut_mode_send(uint16_t opcode, uint8_t* buf, uint8_t len);
-
-void btif_ble_transmitter_test(uint8_t tx_freq, uint8_t test_data_len,
- uint8_t packet_payload);
+bt_status_t btif_dut_mode_send(uint16_t opcode, uint8_t* buf, uint8_t len);
-void btif_ble_receiver_test(uint8_t rx_freq);
-void btif_ble_test_end();
+/*******************************************************************************
+ *
+ * Function btif_le_test_mode
+ *
+ * Description Sends a HCI BLE Test command to the Controller
+ *
+ * Returns BT_STATUS_SUCCESS on success
+ *
+ ******************************************************************************/
+bt_status_t btif_le_test_mode(uint16_t opcode, uint8_t* buf, uint8_t len);
/*******************************************************************************
*
@@ -379,15 +463,4 @@ bt_status_t btif_config_hci_snoop_log(uint8_t enable);
******************************************************************************/
void btif_debug_bond_event_dump(int fd);
-/*******************************************************************************
- *
- * Function btif_set_dynamic_audio_buffer_size
- *
- * Description Set dynamic audio buffer size
- *
- * Returns BT_STATUS_SUCCESS on success
- *
- ******************************************************************************/
-bt_status_t btif_set_dynamic_audio_buffer_size(int codec, int size);
-
#endif /* BTIF_API_H */
diff --git a/btif/include/btif_av.h b/btif/include/btif_av.h
index 0a3095ee5..8ddfc6ae8 100644
--- a/btif/include/btif_av.h
+++ b/btif/include/btif_av.h
@@ -23,13 +23,8 @@
#ifndef BTIF_AV_H
#define BTIF_AV_H
-#include <cstdint>
-
-#include "include/hardware/bt_av.h"
-#include "types/raw_address.h"
-
-// #include "bta/include/bta_av_api.h"
-// #include "btif/include/btif_common.h"
+#include "bta_av_api.h"
+#include "btif_common.h"
/**
* When the local device is A2DP source, get the address of the active peer.
@@ -221,11 +216,4 @@ bool btif_av_is_a2dp_offload_running(void);
*/
bool btif_av_is_peer_silenced(const RawAddress& peer_address);
-/**
- * Set the dynamic audio buffer size
- *
- * @param dynamic_audio_buffer_size to set
- */
-void btif_av_set_dynamic_audio_buffer_size(uint8_t dynamic_audio_buffer_size);
-
#endif /* BTIF_AV_H */
diff --git a/btif/include/btif_bqr.h b/btif/include/btif_bqr.h
index 7dcff600b..f22544b84 100644
--- a/btif/include/btif_bqr.h
+++ b/btif/include/btif_bqr.h
@@ -27,7 +27,8 @@ namespace bqr {
// Bluetooth Quality Report (BQR)
//
// It is a feature to start the mechanism in the Bluetooth controller to report
-// Bluetooth Quality event to the host and the following options can be enabled:
+// Bluetooth Quality event to the host and there are four options could be
+// enabled:
// [Quality Monitoring Mode]
// The controller shall periodically send Bluetooth Quality Report sub-event
// to the host.
@@ -203,7 +204,7 @@ typedef struct {
uint8_t connection_role;
// Current Transmit Power Level for the connection. This value is the same as
// the controller's response to the HCI_Read_Transmit_Power_Level HCI command.
- int8_t tx_power_level;
+ uint8_t tx_power_level;
// Received Signal Strength Indication (RSSI) value for the connection. This
// value is an absolute receiver signal strength value.
int8_t rssi;
diff --git a/btif/include/btif_common.h b/btif/include/btif_common.h
index 3ce8db6da..67e8e1152 100644
--- a/btif/include/btif_common.h
+++ b/btif/include/btif_common.h
@@ -24,9 +24,9 @@
#include <base/bind.h>
#include <base/location.h>
+#include <base/message_loop/message_loop.h>
#include <hardware/bluetooth.h>
-#include "abstract_message_loop.h"
#include "bt_types.h"
#include "bta/include/bta_api.h"
#include "osi/include/log.h"
@@ -36,12 +36,12 @@
* Constants & Macros
******************************************************************************/
-#define ASSERTC(cond, msg, val) \
- do { \
- if (!(cond)) { \
- LOG_ERROR("### ASSERT : %s %s line %d %s (%d) ###", __FILE__, __func__, \
- __LINE__, (msg), (val)); \
- } \
+#define ASSERTC(cond, msg, val) \
+ do { \
+ if (!(cond)) { \
+ LOG_ERROR(LOG_TAG, "### ASSERT : %s %s line %d %s (%d) ###", __FILE__, \
+ __func__, __LINE__, (msg), (val)); \
+ } \
} while (0)
/* Calculate start of event enumeration; id is top 8 bits of event */
@@ -76,6 +76,8 @@
#define BTIF_PAN 4
#define BTIF_HF_CLIENT 5
+extern bt_callbacks_t* bt_hal_cbacks;
+
#define HAL_CBACK(P_CB, P_CBACK, ...) \
do { \
if ((P_CB) && (P_CB)->P_CBACK) { \
@@ -91,6 +93,18 @@
* on downstreams path
*/
enum {
+ BTIF_CORE_API_START = BTIF_SIG_START(BTIF_CORE),
+ BTIF_CORE_STORAGE_NO_ACTION,
+ BTIF_CORE_STORAGE_ADAPTER_WRITE,
+ BTIF_CORE_STORAGE_ADAPTER_READ,
+ BTIF_CORE_STORAGE_ADAPTER_READ_ALL,
+ BTIF_CORE_STORAGE_REMOTE_WRITE,
+ BTIF_CORE_STORAGE_REMOTE_READ,
+ BTIF_CORE_STORAGE_REMOTE_READ_ALL,
+ BTIF_CORE_STORAGE_READ_ALL,
+ BTIF_CORE_STORAGE_NOTIFY_STATUS,
+ /* add here */
+
BTIF_DM_API_START = BTIF_SIG_START(BTIF_DM),
BTIF_DM_ENABLE_SERVICE,
BTIF_DM_DISABLE_SERVICE,
@@ -112,6 +126,16 @@ enum {
BTIF_CORE_CB_START = BTIF_SIG_CB_START(BTIF_CORE),
/* add here */
+ BTIF_DM_CB_START = BTIF_SIG_CB_START(BTIF_DM),
+ BTIF_DM_CB_DISCOVERY_STARTED, /* Discovery has started */
+ BTIF_DM_CB_CREATE_BOND, /* Create bond */
+ BTIF_DM_CB_REMOVE_BOND, /*Remove bond */
+ BTIF_DM_CB_HID_REMOTE_NAME, /* Remote name callback for HID device */
+ BTIF_DM_CB_BOND_STATE_BONDING,
+ BTIF_DM_CB_LE_TX_TEST, /* BLE Tx Test command complete callback */
+ BTIF_DM_CB_LE_RX_TEST, /* BLE Rx Test command complete callback */
+ BTIF_DM_CB_LE_TEST_END, /* BLE Test mode end callback */
+
BTIF_HFP_CB_START = BTIF_SIG_CB_START(BTIF_HFP),
BTIF_HFP_CB_AUDIO_CONNECTING, /* HF AUDIO connect has been sent to BTA
successfully */
@@ -138,7 +162,7 @@ typedef void(tBTIF_COPY_CBACK)(uint16_t event, char* p_dest, char* p_src);
/* this type handles all btif context switches between BTU and HAL */
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tBTIF_CBACK* p_cb; /* context switch callback */
/* parameters passed to callback */
@@ -154,7 +178,7 @@ extern bt_status_t do_in_jni_thread(base::OnceClosure task);
extern bt_status_t do_in_jni_thread(const base::Location& from_here,
base::OnceClosure task);
extern bool is_on_jni_thread();
-extern btbase::AbstractMessageLoop* get_jni_message_loop();
+extern base::MessageLoop* get_jni_message_loop();
/**
* This template wraps callback into callback that will be executed on jni
* thread
@@ -172,55 +196,31 @@ base::Callback<R(Args...)> jni_thread_wrapper(const base::Location& from_here,
}
tBTA_SERVICE_MASK btif_get_enabled_services_mask(void);
-void btif_enable_service(tBTA_SERVICE_ID service_id);
-void btif_disable_service(tBTA_SERVICE_ID service_id);
+bt_status_t btif_enable_service(tBTA_SERVICE_ID service_id);
+bt_status_t btif_disable_service(tBTA_SERVICE_ID service_id);
int btif_is_enabled(void);
/**
* BTIF_Events
*/
-void btif_enable_bluetooth_evt();
+void btif_enable_bluetooth_evt(tBTA_STATUS status);
+void btif_disable_bluetooth_evt(void);
void btif_adapter_properties_evt(bt_status_t status, uint32_t num_props,
bt_property_t* p_props);
void btif_remote_properties_evt(bt_status_t status, RawAddress* remote_addr,
uint32_t num_props, bt_property_t* p_props);
void bte_load_did_conf(const char* p_path);
-void bte_main_init(void);
+void bte_main_boot_entry(void);
+void bte_main_enable(void);
+void bte_main_disable(void);
+void bte_main_cleanup(void);
+void bte_main_postload_cfg(void);
bt_status_t btif_transfer_context(tBTIF_CBACK* p_cback, uint16_t event,
char* p_params, int param_len,
tBTIF_COPY_CBACK* p_copy_cback);
-void btif_init_ok();
-
-void invoke_adapter_state_changed_cb(bt_state_t state);
-void invoke_adapter_properties_cb(bt_status_t status, int num_properties,
- bt_property_t* properties);
-void invoke_remote_device_properties_cb(bt_status_t status, RawAddress bd_addr,
- int num_properties,
- bt_property_t* properties);
-void invoke_device_found_cb(int num_properties, bt_property_t* properties);
-void invoke_discovery_state_changed_cb(bt_discovery_state_t state);
-void invoke_pin_request_cb(RawAddress bd_addr, bt_bdname_t bd_name,
- uint32_t cod, bool min_16_digit);
-void invoke_ssp_request_cb(RawAddress bd_addr, bt_bdname_t bd_name,
- uint32_t cod, bt_ssp_variant_t pairing_variant,
- uint32_t pass_key);
-void invoke_oob_data_request_cb(tBT_TRANSPORT t, bool valid, Octet16 c,
- Octet16 r, RawAddress raw_address,
- uint8_t address_type);
-void invoke_bond_state_changed_cb(bt_status_t status, RawAddress bd_addr,
- bt_bond_state_t state);
-void invoke_acl_state_changed_cb(bt_status_t status, RawAddress bd_addr,
- bt_acl_state_t state, bt_hci_error_code_t hci_reason);
-void invoke_thread_evt_cb(bt_cb_thread_evt event);
-void invoke_le_test_mode_cb(bt_status_t status, uint16_t count);
-void invoke_energy_info_cb(bt_activity_energy_info energy_info,
- bt_uid_traffic_t* uid_data);
-void invoke_link_quality_report_cb(
- uint64_t timestamp, int report_id, int rssi, int snr,
- int retransmission_count, int packets_not_receive_count,
- int negative_acknowledgement_count);
+void btif_init_ok(UNUSED_ATTR uint16_t event, UNUSED_ATTR char* p_param);
#endif /* BTIF_COMMON_H */
diff --git a/btif/include/btif_config.h b/btif/include/btif_config.h
index 57a4f1e33..d1678cd7e 100644
--- a/btif/include/btif_config.h
+++ b/btif/include/btif_config.h
@@ -26,7 +26,6 @@
#include <list>
#include <string>
#include "osi/include/config.h"
-#include "types/ble_address_with_type.h"
static const char BTIF_CONFIG_MODULE[] = "btif_config_module";
@@ -42,6 +41,7 @@ static const std::string BT_CONFIG_KEY_REMOTE_VER_MFCT = "Manufacturer";
static const std::string BT_CONFIG_KEY_REMOTE_VER_VER = "LmpVer";
static const std::string BT_CONFIG_KEY_REMOTE_VER_SUBVER = "LmpSubVer";
+bool btif_config_has_section(const char* section);
bool btif_config_exist(const std::string& section, const std::string& key);
bool btif_config_get_int(const std::string& section, const std::string& key,
int* value);
@@ -64,7 +64,7 @@ bool btif_config_remove(const std::string& section, const std::string& key);
size_t btif_config_get_bin_length(const std::string& section,
const std::string& key);
-std::vector<RawAddress> btif_config_get_paired_devices();
+const std::list<section_t>& btif_config_sections();
void btif_config_save(void);
void btif_config_flush(void);
@@ -72,8 +72,43 @@ bool btif_config_clear(void);
// TODO(zachoverflow): Eww...we need to move these out. These are peer specific,
// not config general.
-bool btif_get_address_type(const RawAddress& bd_addr,
- tBLE_ADDR_TYPE* p_addr_type);
+bool btif_get_address_type(const RawAddress& bd_addr, int* p_addr_type);
bool btif_get_device_type(const RawAddress& bd_addr, int* p_device_type);
void btif_debug_config_dump(int fd);
+
+typedef struct {
+ std::string (*checksum_read)(const char* filename);
+ bool (*checksum_save)(const std::string& checksum,
+ const std::string& filename);
+ bool (*config_get_bool)(const config_t& config, const std::string& section,
+ const std::string& key, bool def_value);
+ int (*config_get_int)(const config_t& config, const std::string& section,
+ const std::string& key, int def_value);
+ const std::string* (*config_get_string)(const config_t& config,
+ const std::string& section,
+ const std::string& key,
+ const std::string* def_value);
+ uint64_t (*config_get_uint64)(const config_t& config,
+ const std::string& section,
+ const std::string& key, uint64_t def_value);
+ bool (*config_has_key)(const config_t& config, const std::string& section,
+ const std::string& key);
+ bool (*config_has_section)(const config_t& config,
+ const std::string& section);
+ std::unique_ptr<config_t> (*config_new)(const char* filename);
+ std::unique_ptr<config_t> (*config_new_clone)(const config_t& src);
+ std::unique_ptr<config_t> (*config_new_empty)(void);
+ bool (*config_remove_key)(config_t* config, const std::string& section,
+ const std::string& key);
+ bool (*config_remove_section)(config_t* config, const std::string& section);
+ bool (*config_save)(const config_t& config, const std::string& filename);
+ void (*config_set_bool)(config_t* config, const std::string& section,
+ const std::string& key, bool value);
+ void (*config_set_int)(config_t* config, const std::string& section,
+ const std::string& key, int value);
+ void (*config_set_string)(config_t* config, const std::string& section,
+ const std::string& key, const std::string& value);
+ void (*config_set_uint64)(config_t* config, const std::string& section,
+ const std::string& key, uint64_t value);
+} storage_config_t;
diff --git a/btif/include/btif_config_cache.h b/btif/include/btif_config_cache.h
index 212d8298e..aedcd4eb4 100644
--- a/btif/include/btif_config_cache.h
+++ b/btif/include/btif_config_cache.h
@@ -31,7 +31,7 @@ class BtifConfigCache {
void Clear();
void Init(std::unique_ptr<config_t> source);
- std::vector<std::string> GetPersistentSectionNames();
+ const std::list<section_t>& GetPersistentSections();
config_t PersistentSectionCopy();
bool HasSection(const std::string& section_name);
bool HasUnpairedSection(const std::string& section_name);
@@ -55,7 +55,6 @@ class BtifConfigCache {
const std::string& key);
private:
- bluetooth::common::LegacyLruCache<std::string, section_t>
- unpaired_devices_cache_;
+ bluetooth::common::LruCache<std::string, section_t> unpaired_devices_cache_;
config_t paired_devices_list_;
};
diff --git a/btif/include/btif_dm.h b/btif/include/btif_dm.h
index 6c2a5947f..fae8929d2 100644
--- a/btif/include/btif_dm.h
+++ b/btif/include/btif_dm.h
@@ -43,36 +43,32 @@ void btif_dm_on_disable(void);
/**
* Callout for handling io_capabilities request
*/
-void btif_dm_proc_io_req(tBTM_AUTH_REQ* p_auth_req, bool is_orig);
+void btif_dm_proc_io_req(const RawAddress& bd_addr, tBTA_IO_CAP* p_io_cap,
+ tBTA_OOB_DATA* p_oob_data, tBTA_AUTH_REQ* p_auth_req,
+ bool is_orig);
/**
* Callout for handling io_capabilities response
*/
-void btif_dm_proc_io_rsp(const RawAddress& bd_addr, tBTM_IO_CAP io_cap,
- tBTM_OOB_DATA oob_data, tBTM_AUTH_REQ auth_req);
+void btif_dm_proc_io_rsp(const RawAddress& bd_addr, tBTA_IO_CAP io_cap,
+ tBTA_OOB_DATA oob_data, tBTA_AUTH_REQ auth_req);
/**
* Out-of-band functions
*/
-void btif_dm_set_oob_for_io_req(tBTM_OOB_DATA* p_oob_data);
+void btif_dm_set_oob_for_io_req(tBTA_OOB_DATA* p_oob_data);
void btif_dm_set_oob_for_le_io_req(const RawAddress& bd_addr,
- tBTM_OOB_DATA* p_oob_data,
- tBTM_LE_AUTH_REQ* p_auth_req);
+ tBTA_OOB_DATA* p_oob_data,
+ tBTA_LE_AUTH_REQ* p_auth_req);
#ifdef BTIF_DM_OOB_TEST
void btif_dm_load_local_oob(void);
-void btif_dm_proc_loc_oob(tBT_TRANSPORT transport, bool is_valid,
- const Octet16& c, const Octet16& r);
+void btif_dm_proc_loc_oob(bool valid, const Octet16& c, const Octet16& r);
bool btif_dm_proc_rmt_oob(const RawAddress& bd_addr, Octet16* p_c,
Octet16* p_r);
-void btif_dm_generate_local_oob_data(tBT_TRANSPORT transport);
#endif /* BTIF_DM_OOB_TEST */
/*callout for reading SMP properties from Text file*/
bool btif_dm_get_smp_config(tBTE_APPL_CFG* p_cfg);
-/* EIR functions */
-void btif_dm_add_uuid_to_eir(uint16_t uuid16);
-void btif_dm_remove_uuid_from_eir(uint16_t uuid16);
-
typedef struct {
bool is_penc_key_rcvd;
tBTM_LE_PENC_KEYS penc_key; /* received peer encryption key */
@@ -88,6 +84,13 @@ typedef struct {
bool is_lidk_key_rcvd; /* local identity key received */
} btif_dm_ble_cb_t;
+#define BTIF_DM_LE_KEY_PENC BTA_LE_KEY_PENC
+#define BTIF_DM_LE_KEY_PID BTA_LE_KEY_PID
+#define BTIF_DM_LE_KEY_PCSRK BTA_LE_KEY_PCSRK
+#define BTIF_DM_LE_KEY_LENC BTA_LE_KEY_LENC
+#define BTIF_DM_LE_KEY_LID BTA_LE_KEY_LID
+#define BTIF_DM_LE_KEY_LCSRK BTA_LE_KEY_LCSRK
+
#define BTIF_DM_LE_LOCAL_KEY_IR (1 << 0)
#define BTIF_DM_LE_LOCAL_KEY_IRK (1 << 1)
#define BTIF_DM_LE_LOCAL_KEY_DHK (1 << 2)
diff --git a/btif/include/btif_gatt.h b/btif/include/btif_gatt.h
index 7391e6dbe..88f18a7b9 100644
--- a/btif/include/btif_gatt.h
+++ b/btif/include/btif_gatt.h
@@ -27,8 +27,6 @@
#ifndef BTIF_GATT_H
#define BTIF_GATT_H
-#include "include/hardware/bt_gatt.h"
-
extern const btgatt_client_interface_t btgattClientInterface;
extern const btgatt_server_interface_t btgattServerInterface;
diff --git a/btif/include/btif_gatt_util.h b/btif/include/btif_gatt_util.h
index e53bc260b..284a45c70 100644
--- a/btif/include/btif_gatt_util.h
+++ b/btif/include/btif_gatt_util.h
@@ -23,12 +23,11 @@
#include <hardware/bt_gatt.h>
#include "bta/include/bta_gatt_api.h"
-#include "types/bt_transport.h"
void btif_to_bta_response(tGATTS_RSP* p_dest, btgatt_response_t* p_src);
void btif_gatt_check_encrypted_link(RawAddress bd_addr,
- tBT_TRANSPORT transport);
+ tGATT_TRANSPORT transport);
extern void btif_gatt_move_track_adv_data(btgatt_track_adv_info_t* p_dest,
btgatt_track_adv_info_t* p_src);
diff --git a/btif/include/btif_hd.h b/btif/include/btif_hd.h
index 10efbb719..7ed7d5633 100644
--- a/btif/include/btif_hd.h
+++ b/btif/include/btif_hd.h
@@ -23,7 +23,7 @@
#include <hardware/bluetooth.h>
#include <hardware/bt_hd.h>
#include <stdint.h>
-#include "bta/include/bta_hd_api.h"
+#include "bta_hd_api.h"
typedef enum {
BTIF_HD_DISABLED = 0,
diff --git a/btif/include/btif_hh.h b/btif/include/btif_hh.h
index 1d4bc93e2..b71d347c1 100644
--- a/btif/include/btif_hh.h
+++ b/btif/include/btif_hh.h
@@ -23,7 +23,7 @@
#include <hardware/bt_hh.h>
#include <pthread.h>
#include <stdint.h>
-#include "bta/include/bta_hh_api.h"
+#include "bta_hh_api.h"
#include "btu.h"
#include "osi/include/fixed_queue.h"
@@ -46,7 +46,7 @@
* Type definitions and return values
******************************************************************************/
-typedef enum : unsigned {
+typedef enum {
BTIF_HH_DISABLED = 0,
BTIF_HH_ENABLED,
BTIF_HH_DISABLING,
@@ -56,26 +56,6 @@ typedef enum : unsigned {
BTIF_HH_DEV_DISCONNECTED
} BTIF_HH_STATUS;
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string btif_hh_status_text(const BTIF_HH_STATUS& status) {
- switch (status) {
- CASE_RETURN_TEXT(BTIF_HH_DISABLED);
- CASE_RETURN_TEXT(BTIF_HH_ENABLED);
- CASE_RETURN_TEXT(BTIF_HH_DISABLING);
- CASE_RETURN_TEXT(BTIF_HH_DEV_UNKNOWN);
- CASE_RETURN_TEXT(BTIF_HH_DEV_CONNECTING);
- CASE_RETURN_TEXT(BTIF_HH_DEV_CONNECTED);
- CASE_RETURN_TEXT(BTIF_HH_DEV_DISCONNECTED);
- default:
- return std::string("UNKNOWN[%hhu]", status);
- }
-}
-#undef CASE_RETURN_TEXT
-
-// Shared with uhid polling thread
typedef struct {
bthh_connection_state_t dev_status;
uint8_t dev_handle;
@@ -86,7 +66,6 @@ typedef struct {
int fd;
bool ready_for_data;
pthread_t hh_poll_thread_id;
- pid_t pid{-1};
uint8_t hh_keep_polling;
alarm_t* vup_timer;
fixed_queue_t* get_rpt_id_queue;
@@ -130,8 +109,6 @@ extern void btif_hh_disconnect(RawAddress* bd_addr);
extern void btif_hh_setreport(btif_hh_device_t* p_dev,
bthh_report_type_t r_type, uint16_t size,
uint8_t* report);
-extern void btif_hh_senddata(btif_hh_device_t* p_dev, uint16_t size,
- uint8_t* report);
extern void btif_hh_getreport(btif_hh_device_t* p_dev,
bthh_report_type_t r_type, uint8_t reportId,
uint16_t bufferSize);
diff --git a/stack/test/common/mock_btif_storage.cc b/btif/include/btif_mce.h
index b65d89ac2..1eea20668 100644
--- a/stack/test/common/mock_btif_storage.cc
+++ b/btif/include/btif_mce.h
@@ -1,6 +1,7 @@
/******************************************************************************
*
- * Copyright 2020 The Android Open Source Project
+ * Copyright 2014 The Android Open Source Project
+ * Copyright 2009-2012 Broadcom Corporation
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,18 +17,19 @@
*
******************************************************************************/
-#include "mock_btif_storage.h"
+/*******************************************************************************
+ *
+ * Filename: btif_mce.h
+ *
+ * Description: Bluetooth MCE Interface
+ *
+ ******************************************************************************/
-static bluetooth::manager::MockBtifStorageInterface* btif_storage_interface =
- nullptr;
+#ifndef BTIF_MCE_H
+#define BTIF_MCE_H
-void bluetooth::manager::SetMockBtifStorageInterface(
- MockBtifStorageInterface* mock_btif_storage_interface) {
- btif_storage_interface = mock_btif_storage_interface;
-}
+#include <hardware/bt_mce.h>
-void btif_storage_load_bonded_eatt(void) {
- btif_storage_interface->LoadBondedEatt();
-}
+btmce_interface_t* btif_mce_get_interface();
-uint8_t btif_storage_get_local_io_caps() { return 0; }
+#endif
diff --git a/btif/include/btif_metrics_logging.h b/btif/include/btif_metrics_logging.h
deleted file mode 100644
index c24c907f2..000000000
--- a/btif/include/btif_metrics_logging.h
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
-
-#include "main/shim/metric_id_api.h"
-#include "types/raw_address.h"
-
-void log_a2dp_audio_underrun_event(const RawAddress& address,
- uint64_t encoding_interval_millis,
- int num_missing_pcm_bytes);
-
-void log_a2dp_audio_overrun_event(const RawAddress& address,
- uint64_t encoding_interval_millis,
- int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes);
-
-void log_a2dp_playback_event(const RawAddress& address, int playback_state,
- int audio_coding_mode);
-
-void log_read_rssi_result(const RawAddress& address, uint16_t handle,
- uint32_t cmd_status, int8_t rssi);
-
-void log_read_failed_contact_counter_result(const RawAddress& address,
- uint16_t handle,
- uint32_t cmd_status,
- int32_t failed_contact_counter);
-
-void log_read_tx_power_level_result(const RawAddress& address, uint16_t handle,
- uint32_t cmd_status,
- int32_t transmit_power_level);
-
-void log_socket_connection_state(
- const RawAddress& address, int port, int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes, int64_t rx_bytes, int uid, int server_port,
- android::bluetooth::SocketRoleEnum socket_role);
-
-bool init_metric_id_allocator(
- const std::unordered_map<RawAddress, int>& paired_device_map,
- bluetooth::shim::CallbackLegacy save_id_callback,
- bluetooth::shim::CallbackLegacy forget_device_callback);
-
-bool close_metric_id_allocator();
-
-int allocate_metric_id_from_metric_id_allocator(const RawAddress&);
-
-int save_metric_id_from_metric_id_allocator(const RawAddress&);
-
-void forget_device_from_metric_id_allocator(const RawAddress&);
-
-bool is_valid_id_from_metric_id_allocator(const int id); \ No newline at end of file
diff --git a/btif/include/btif_pan_internal.h b/btif/include/btif_pan_internal.h
index 37630dbe0..5b536afe3 100644
--- a/btif/include/btif_pan_internal.h
+++ b/btif/include/btif_pan_internal.h
@@ -38,7 +38,13 @@
#define PANU_SERVICE_NAME "Android Network User"
#define TAP_IF_NAME "bt-pan"
#define TAP_MAX_PKT_WRITE_LEN 2000
+#ifndef PAN_SECURITY
+#define PAN_SECURITY \
+ (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_IN_ENCRYPT | \
+ BTM_SEC_OUT_ENCRYPT)
+#endif
+#define PAN_STATE_UNKNOWN 0
#define PAN_STATE_OPEN 1
#define PAN_STATE_CLOSE 2
#ifndef PAN_ROLE_INACTIVE
diff --git a/btif/include/btif_sock_l2cap.h b/btif/include/btif_sock_l2cap.h
index 0c867c5c4..f92127931 100644
--- a/btif/include/btif_sock_l2cap.h
+++ b/btif/include/btif_sock_l2cap.h
@@ -9,6 +9,8 @@
#include <hardware/bluetooth.h>
+#define L2CAP_MASK_FIXED_CHANNEL 0x10000
+
bt_status_t btsock_l2cap_init(int handle, uid_set_t* set);
bt_status_t btsock_l2cap_cleanup();
bt_status_t btsock_l2cap_listen(const char* name, int channel, int* sock_fd,
diff --git a/btif/include/btif_sock_sdp.h b/btif/include/btif_sock_sdp.h
index 7a9da8448..5421cd161 100644
--- a/btif/include/btif_sock_sdp.h
+++ b/btif/include/btif_sock_sdp.h
@@ -30,8 +30,6 @@ static const bluetooth::Uuid UUID_PBAP_PSE = bluetooth::Uuid::From16Bit(0x112F);
static const bluetooth::Uuid UUID_MAP_MAS = bluetooth::Uuid::From16Bit(0x1132);
static const bluetooth::Uuid UUID_SAP = bluetooth::Uuid::From16Bit(0x112D);
static const bluetooth::Uuid UUID_SPP = bluetooth::Uuid::From16Bit(0x1101);
-static const bluetooth::Uuid UUID_DIP = bluetooth::Uuid::From16Bit(0x1200);
-static const bluetooth::Uuid UUID_MAP_MNS = bluetooth::Uuid::From16Bit(0x1133);
int add_rfc_sdp_rec(const char* name, bluetooth::Uuid uuid, int scn);
void del_rfc_sdp_rec(int handle);
diff --git a/btif/include/btif_sock_thread.h b/btif/include/btif_sock_thread.h
index 6e9317bc0..4b111a48f 100644
--- a/btif/include/btif_sock_thread.h
+++ b/btif/include/btif_sock_thread.h
@@ -43,7 +43,7 @@ typedef void (*btsock_signaled_cb)(int fd, int type, int flags,
uint32_t user_id);
typedef void (*btsock_cmd_cb)(int cmd_fd, int type, int size, uint32_t user_id);
-void btsock_thread_init();
+int btsock_thread_init();
int btsock_thread_add_fd(int handle, int fd, int type, int flags,
uint32_t user_id);
bool btsock_thread_remove_fd_and_close(int thread_handle, int fd);
diff --git a/btif/include/btif_storage.h b/btif/include/btif_storage.h
index 7e970ec4d..1c1163d14 100644
--- a/btif/include/btif_storage.h
+++ b/btif/include/btif_storage.h
@@ -24,7 +24,6 @@
#include "bt_target.h"
#include "bt_types.h"
-#include "types/ble_address_with_type.h"
/*******************************************************************************
* Constants & Macros
@@ -220,7 +219,7 @@ bt_status_t btif_storage_load_bonded_hid_info(void);
* BT_STATUS_FAIL otherwise
*
******************************************************************************/
-bt_status_t btif_storage_remove_hid_info(const RawAddress& remote_bd_addr);
+bt_status_t btif_storage_remove_hid_info(RawAddress* remote_bd_addr);
/** Loads information about bonded hearing aid devices */
void btif_storage_load_bonded_hearing_aids();
@@ -228,34 +227,9 @@ void btif_storage_load_bonded_hearing_aids();
/** Deletes the bonded hearing aid device info from NVRAM */
void btif_storage_remove_hearing_aid(const RawAddress& address);
-/** Set/Unset the hearing aid device HEARING_AID_IS_ACCEPTLISTED flag. */
-void btif_storage_set_hearing_aid_acceptlist(const RawAddress& address,
- bool add_to_acceptlist);
-
-/** Stores information about GATT Client supported features support */
-void btif_storage_set_gatt_cl_supp_feat(const RawAddress& bd_addr,
- uint8_t feat);
-
-/** Get client supported features */
-uint8_t btif_storage_get_gatt_cl_supp_feat(const RawAddress& bd_addr);
-
-/** Remove client supported features */
-void btif_storage_remove_gatt_cl_supp_feat(const RawAddress& bd_addr);
-
-/** Stores information about GATT server supported features */
-void btif_storage_set_gatt_sr_supp_feat(const RawAddress& addr, uint8_t feat);
-
-/** Gets information about GATT server supported features */
-uint8_t btif_storage_get_sr_supp_feat(const RawAddress& bd_addr);
-
-/** Store last server database hash for remote client */
-void btif_storage_set_gatt_cl_db_hash(const RawAddress& bd_addr, Octet16 hash);
-
-/** Get last server database hash for remote client */
-Octet16 btif_storage_get_gatt_cl_db_hash(const RawAddress& bd_addr);
-
-/** Remove last server database hash for remote client */
-void btif_storage_remove_gatt_cl_db_hash(const RawAddress& bd_addr);
+/** Set/Unset the hearing aid device HEARING_AID_IS_WHITE_LISTED flag. */
+void btif_storage_set_hearing_aid_white_list(const RawAddress& address,
+ bool add_to_whitelist);
/** Get the hearing aid device properties. */
bool btif_storage_get_hearing_aid_prop(
@@ -281,7 +255,7 @@ bt_status_t btif_storage_add_ble_bonding_key(RawAddress* remote_bd_addr,
const uint8_t* key,
uint8_t key_type,
uint8_t key_length);
-bt_status_t btif_storage_get_ble_bonding_key(const RawAddress& remote_bd_addr,
+bt_status_t btif_storage_get_ble_bonding_key(RawAddress* remote_bd_addr,
uint8_t key_type,
uint8_t* key_value,
int key_length);
@@ -295,10 +269,10 @@ bt_status_t btif_storage_get_ble_local_key(uint8_t key_type,
Octet16* key_value);
bt_status_t btif_storage_get_remote_addr_type(const RawAddress* remote_bd_addr,
- tBLE_ADDR_TYPE* addr_type);
+ int* addr_type);
bt_status_t btif_storage_set_remote_addr_type(const RawAddress* remote_bd_addr,
- tBLE_ADDR_TYPE addr_type);
+ uint8_t addr_type);
/*******************************************************************************
* Function btif_storage_load_hidd
@@ -320,7 +294,7 @@ bt_status_t btif_storage_load_hidd(void);
*
******************************************************************************/
-bt_status_t btif_storage_set_hidd(const RawAddress& remote_bd_addr);
+bt_status_t btif_storage_set_hidd(RawAddress* remote_bd_addr);
/*******************************************************************************
*
diff --git a/btif/include/btif_util.h b/btif/include/btif_util.h
index 725cf34f5..007cfa5b9 100644
--- a/btif/include/btif_util.h
+++ b/btif/include/btif_util.h
@@ -25,7 +25,7 @@
#include <sys/time.h>
#include "bt_types.h"
-#include "utils/include/bt_utils.h"
+#include "bt_utils.h"
/*******************************************************************************
* Constants & Macros
diff --git a/btif/src/bluetooth.cc b/btif/src/bluetooth.cc
index a72f787f5..a00c0c662 100644
--- a/btif/src/bluetooth.cc
+++ b/btif/src/bluetooth.cc
@@ -27,6 +27,11 @@
#define LOG_TAG "bt_btif"
#include <base/logging.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+
#include <hardware/bluetooth.h>
#include <hardware/bluetooth_headset_interface.h>
#include <hardware/bt_av.h>
@@ -35,23 +40,17 @@
#include <hardware/bt_hearing_aid.h>
#include <hardware/bt_hf_client.h>
#include <hardware/bt_hh.h>
-#include <hardware/bt_le_audio.h>
+#include <hardware/bt_mce.h>
#include <hardware/bt_pan.h>
#include <hardware/bt_rc.h>
#include <hardware/bt_sdp.h>
#include <hardware/bt_sock.h>
-#include <hardware/bt_vc.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <unistd.h>
#include "bt_utils.h"
#include "bta/include/bta_hearing_aid_api.h"
#include "bta/include/bta_hf_client_api.h"
#include "btif/avrcp/avrcp_service.h"
#include "btif_a2dp.h"
-#include "btif_activity_attribution.h"
#include "btif_api.h"
#include "btif_av.h"
#include "btif_bqr.h"
@@ -61,16 +60,13 @@
#include "btif_debug_conn.h"
#include "btif_hf.h"
#include "btif_keystore.h"
-#include "btif_metrics_logging.h"
#include "btif_storage.h"
#include "btsnoop.h"
#include "btsnoop_mem.h"
#include "common/address_obfuscator.h"
#include "common/metric_id_allocator.h"
#include "common/metrics.h"
-#include "common/os_utils.h"
#include "device/include/interop.h"
-#include "gd/common/init_flags.h"
#include "main/shim/dumpsys.h"
#include "main/shim/shim.h"
#include "osi/include/alarm.h"
@@ -79,24 +75,19 @@
#include "osi/include/osi.h"
#include "osi/include/wakelock.h"
#include "stack/gatt/connection_manager.h"
-#include "stack/include/avdt_api.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btu.h"
#include "stack_manager.h"
using bluetooth::hearing_aid::HearingAidInterface;
-using bluetooth::le_audio::LeAudioClientInterface;
-using bluetooth::vc::VolumeControlInterface;
/*******************************************************************************
* Static variables
******************************************************************************/
-static bt_callbacks_t* bt_hal_cbacks = NULL;
+bt_callbacks_t* bt_hal_cbacks = NULL;
bool restricted_mode = false;
-bool common_criteria_mode = false;
+bool niap_mode = false;
const int CONFIG_COMPARE_ALL_PASS = 0b11;
-int common_criteria_config_compare_result = CONFIG_COMPARE_ALL_PASS;
+int niap_config_compare_result = CONFIG_COMPARE_ALL_PASS;
bool is_local_device_atv = false;
/*******************************************************************************
@@ -118,6 +109,8 @@ extern const bthh_interface_t* btif_hh_get_interface();
extern const bthd_interface_t* btif_hd_get_interface();
/*pan*/
extern const btpan_interface_t* btif_pan_get_interface();
+/*map client*/
+extern const btmce_interface_t* btif_mce_get_interface();
/* gatt */
extern const btgatt_interface_t* btif_gatt_get_interface();
/* avrc target */
@@ -128,17 +121,12 @@ extern const btrc_ctrl_interface_t* btif_rc_ctrl_get_interface();
extern const btsdp_interface_t* btif_sdp_get_interface();
/*Hearing Aid client*/
extern HearingAidInterface* btif_hearing_aid_get_interface();
-/* LeAudio testi client */
-extern LeAudioClientInterface* btif_le_audio_get_interface();
-/* Volume Control client */
-extern VolumeControlInterface* btif_volume_control_get_interface();
/*******************************************************************************
* Functions
******************************************************************************/
static bool interface_ready(void) { return bt_hal_cbacks != NULL; }
-void set_hal_cbacks(bt_callbacks_t* callbacks) { bt_hal_cbacks = callbacks; }
static bool is_profile(const char* p1, const char* p2) {
CHECK(p1);
@@ -153,15 +141,16 @@ static bool is_profile(const char* p1, const char* p2) {
****************************************************************************/
static int init(bt_callbacks_t* callbacks, bool start_restricted,
- bool is_common_criteria_mode, int config_compare_result,
- const char** init_flags, bool is_atv) {
- LOG_INFO(
- "%s: start restricted = %d ; common criteria mode = %d, config compare "
- "result = %d",
- __func__, start_restricted, is_common_criteria_mode,
- config_compare_result);
+ bool is_niap_mode, int config_compare_result, bool is_atv) {
+ LOG_INFO(LOG_TAG,
+ "%s: start restricted = %d ; niap = %d, config compare result = %d",
+ __func__, start_restricted, is_niap_mode, config_compare_result);
- bluetooth::common::InitFlags::Load(init_flags);
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ LOG_INFO(LOG_TAG, "%s Enable Gd bluetooth functionality", __func__);
+ } else {
+ LOG_INFO(LOG_TAG, "%s Preserving legacy bluetooth functionality", __func__);
+ }
if (interface_ready()) return BT_STATUS_DONE;
@@ -169,11 +158,10 @@ static int init(bt_callbacks_t* callbacks, bool start_restricted,
allocation_tracker_init();
#endif
- set_hal_cbacks(callbacks);
-
+ bt_hal_cbacks = callbacks;
restricted_mode = start_restricted;
- common_criteria_mode = is_common_criteria_mode;
- common_criteria_config_compare_result = config_compare_result;
+ niap_mode = is_niap_mode;
+ niap_config_compare_result = config_compare_result;
is_local_device_atv = is_atv;
stack_manager_get_interface()->init_stack();
@@ -198,160 +186,122 @@ static int disable(void) {
static void cleanup(void) { stack_manager_get_interface()->clean_up_stack(); }
bool is_restricted_mode() { return restricted_mode; }
-bool is_common_criteria_mode() {
- return is_bluetooth_uid() && common_criteria_mode;
-}
-// if common criteria mode disable, will always return
-// CONFIG_COMPARE_ALL_PASS(0b11) indicate don't check config checksum.
-int get_common_criteria_config_compare_result() {
- return is_common_criteria_mode() ? common_criteria_config_compare_result
- : CONFIG_COMPARE_ALL_PASS;
+bool is_niap_mode() { return niap_mode; }
+// if niap mode disable, will always return CONFIG_COMPARE_ALL_PASS(0b11)
+// indicate don't check config checksum.
+int get_niap_config_compare_result() {
+ return niap_mode ? niap_config_compare_result : CONFIG_COMPARE_ALL_PASS;
}
bool is_atv_device() { return is_local_device_atv; }
static int get_adapter_properties(void) {
- if (!btif_is_enabled()) return BT_STATUS_NOT_READY;
+ /* sanity check */
+ if (!interface_ready()) return BT_STATUS_NOT_READY;
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_get_adapter_properties));
- return BT_STATUS_SUCCESS;
+ return btif_get_adapter_properties();
}
static int get_adapter_property(bt_property_type_t type) {
- /* Allow get_adapter_property only for BDADDR and BDNAME if BT is disabled */
- if (!btif_is_enabled() && (type != BT_PROPERTY_BDADDR) &&
- (type != BT_PROPERTY_BDNAME) && (type != BT_PROPERTY_CLASS_OF_DEVICE))
- return BT_STATUS_NOT_READY;
+ /* sanity check */
+ if (!interface_ready()) return BT_STATUS_NOT_READY;
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_get_adapter_property, type));
- return BT_STATUS_SUCCESS;
+ return btif_get_adapter_property(type);
}
static int set_adapter_property(const bt_property_t* property) {
- if (!btif_is_enabled()) return BT_STATUS_NOT_READY;
-
- switch (property->type) {
- case BT_PROPERTY_BDNAME:
- case BT_PROPERTY_ADAPTER_SCAN_MODE:
- case BT_PROPERTY_ADAPTER_DISCOVERY_TIMEOUT:
- case BT_PROPERTY_CLASS_OF_DEVICE:
- case BT_PROPERTY_LOCAL_IO_CAPS:
- case BT_PROPERTY_LOCAL_IO_CAPS_BLE:
- break;
- default:
- return BT_STATUS_FAIL;
- }
+ /* sanity check */
+ if (!interface_ready()) return BT_STATUS_NOT_READY;
- do_in_main_thread(FROM_HERE, base::BindOnce(
- [](bt_property_t* property) {
- btif_set_adapter_property(property);
- osi_free(property);
- },
- property_deep_copy(property)));
- return BT_STATUS_SUCCESS;
+ return btif_set_adapter_property(property);
}
int get_remote_device_properties(RawAddress* remote_addr) {
- if (!btif_is_enabled()) return BT_STATUS_NOT_READY;
+ /* sanity check */
+ if (!interface_ready()) return BT_STATUS_NOT_READY;
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_get_remote_device_properties,
- *remote_addr));
- return BT_STATUS_SUCCESS;
+ return btif_get_remote_device_properties(remote_addr);
}
int get_remote_device_property(RawAddress* remote_addr,
bt_property_type_t type) {
- if (!btif_is_enabled()) return BT_STATUS_NOT_READY;
+ /* sanity check */
+ if (!interface_ready()) return BT_STATUS_NOT_READY;
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_get_remote_device_property,
- *remote_addr, type));
- return BT_STATUS_SUCCESS;
+ return btif_get_remote_device_property(remote_addr, type);
}
int set_remote_device_property(RawAddress* remote_addr,
const bt_property_t* property) {
- if (!btif_is_enabled()) return BT_STATUS_NOT_READY;
-
- do_in_main_thread(
- FROM_HERE, base::BindOnce(
- [](RawAddress remote_addr, bt_property_t* property) {
- btif_set_remote_device_property(&remote_addr, property);
- osi_free(property);
- },
- *remote_addr, property_deep_copy(property)));
- return BT_STATUS_SUCCESS;
+ /* sanity check */
+ if (!interface_ready()) return BT_STATUS_NOT_READY;
+
+ return btif_set_remote_device_property(remote_addr, property);
+}
+
+int get_remote_service_record(const RawAddress& remote_addr,
+ const bluetooth::Uuid& uuid) {
+ /* sanity check */
+ if (!interface_ready()) return BT_STATUS_NOT_READY;
+
+ return btif_get_remote_service_record(remote_addr, uuid);
}
int get_remote_services(RawAddress* remote_addr) {
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- do_in_main_thread(FROM_HERE,
- base::BindOnce(btif_dm_get_remote_services, *remote_addr,
- BT_TRANSPORT_UNKNOWN));
- return BT_STATUS_SUCCESS;
+ return btif_dm_get_remote_services(*remote_addr);
}
static int start_discovery(void) {
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_dm_start_discovery));
- return BT_STATUS_SUCCESS;
+ return btif_dm_start_discovery();
}
static int cancel_discovery(void) {
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_dm_cancel_discovery));
- return BT_STATUS_SUCCESS;
+ return btif_dm_cancel_discovery();
}
static int create_bond(const RawAddress* bd_addr, int transport) {
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- if (btif_dm_pairing_is_busy()) return BT_STATUS_BUSY;
- do_in_main_thread(FROM_HERE,
- base::BindOnce(btif_dm_create_bond, *bd_addr, transport));
- return BT_STATUS_SUCCESS;
+ return btif_dm_create_bond(bd_addr, transport);
}
static int create_bond_out_of_band(const RawAddress* bd_addr, int transport,
- const bt_oob_data_t* p192_data,
- const bt_oob_data_t* p256_data) {
- if (!interface_ready()) return BT_STATUS_NOT_READY;
- if (btif_dm_pairing_is_busy()) return BT_STATUS_BUSY;
-
- do_in_main_thread(FROM_HERE,
- base::BindOnce(btif_dm_create_bond_out_of_band, *bd_addr,
- transport, *p192_data, *p256_data));
- return BT_STATUS_SUCCESS;
-}
-
-static int generate_local_oob_data(tBT_TRANSPORT transport) {
- LOG_INFO("%s", __func__);
+ const bt_out_of_band_data_t* oob_data) {
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- return do_in_main_thread(
- FROM_HERE, base::BindOnce(btif_dm_generate_local_oob_data, transport));
+ return btif_dm_create_bond_out_of_band(bd_addr, transport, oob_data);
}
static int cancel_bond(const RawAddress* bd_addr) {
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_dm_cancel_bond, *bd_addr));
- return BT_STATUS_SUCCESS;
+ return btif_dm_cancel_bond(bd_addr);
}
static int remove_bond(const RawAddress* bd_addr) {
if (is_restricted_mode() && !btif_storage_is_restricted_device(bd_addr))
return BT_STATUS_SUCCESS;
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_dm_remove_bond, *bd_addr));
- return BT_STATUS_SUCCESS;
+ return btif_dm_remove_bond(bd_addr);
}
static int get_connection_state(const RawAddress* bd_addr) {
+ /* sanity check */
if (!interface_ready()) return 0;
return btif_dm_get_connection_state(bd_addr);
@@ -359,28 +309,23 @@ static int get_connection_state(const RawAddress* bd_addr) {
static int pin_reply(const RawAddress* bd_addr, uint8_t accept, uint8_t pin_len,
bt_pin_code_t* pin_code) {
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- if (pin_code == nullptr || pin_len > PIN_CODE_LEN) return BT_STATUS_FAIL;
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_dm_pin_reply, *bd_addr,
- accept, pin_len, *pin_code));
- return BT_STATUS_SUCCESS;
+ return btif_dm_pin_reply(bd_addr, accept, pin_len, pin_code);
}
static int ssp_reply(const RawAddress* bd_addr, bt_ssp_variant_t variant,
uint8_t accept, uint32_t passkey) {
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- if (variant == BT_SSP_VARIANT_PASSKEY_ENTRY) return BT_STATUS_FAIL;
- do_in_main_thread(
- FROM_HERE, base::BindOnce(btif_dm_ssp_reply, *bd_addr, variant, accept));
- return BT_STATUS_SUCCESS;
+ return btif_dm_ssp_reply(bd_addr, variant, accept, passkey);
}
static int read_energy_info() {
if (!interface_ready()) return BT_STATUS_NOT_READY;
-
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_dm_read_energy_info));
+ btif_dm_read_energy_info();
return BT_STATUS_SUCCESS;
}
@@ -400,8 +345,8 @@ static void dump(int fd, const char** arguments) {
HearingAid::DebugDump(fd);
connection_manager::dump(fd);
bluetooth::bqr::DebugDump(fd);
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::Dump(fd, arguments);
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ bluetooth::shim::Dump(fd);
} else {
#if (BTSNOOP_MEM == TRUE)
btif_debug_btsnoop_dump(fd);
@@ -414,7 +359,7 @@ static void dumpMetrics(std::string* output) {
}
static const void* get_profile_interface(const char* profile_id) {
- LOG_INFO("%s: id = %s", __func__, profile_id);
+ LOG_INFO(LOG_TAG, "%s: id = %s", __func__, profile_id);
/* sanity check */
if (!interface_ready()) return NULL;
@@ -461,67 +406,34 @@ static const void* get_profile_interface(const char* profile_id) {
if (is_profile(profile_id, BT_KEYSTORE_ID))
return bluetooth::bluetooth_keystore::getBluetoothKeystoreInterface();
-
- if (is_profile(profile_id, BT_ACTIVITY_ATTRIBUTION_ID)) {
- return bluetooth::activity_attribution::get_activity_attribution_instance();
- }
-
- if (is_profile(profile_id, BT_PROFILE_LE_AUDIO_ID))
- return btif_le_audio_get_interface();
-
- if (is_profile(profile_id, BT_PROFILE_VC_ID))
- return btif_volume_control_get_interface();
-
return NULL;
}
int dut_mode_configure(uint8_t enable) {
+ LOG_INFO(LOG_TAG, "%s", __func__);
+
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- if (!stack_manager_get_interface()->get_stack_is_running())
- return BT_STATUS_NOT_READY;
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_dut_mode_configure, enable));
- return BT_STATUS_SUCCESS;
+ return btif_dut_mode_configure(enable);
}
int dut_mode_send(uint16_t opcode, uint8_t* buf, uint8_t len) {
+ LOG_INFO(LOG_TAG, "%s", __func__);
+
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- if (!btif_is_dut_mode()) return BT_STATUS_FAIL;
-
- uint8_t* copy = (uint8_t*)osi_calloc(len);
- memcpy(copy, buf, len);
-
- do_in_main_thread(FROM_HERE,
- base::BindOnce(
- [](uint16_t opcode, uint8_t* buf, uint8_t len) {
- btif_dut_mode_send(opcode, buf, len);
- osi_free(buf);
- },
- opcode, copy, len));
- return BT_STATUS_SUCCESS;
+
+ return btif_dut_mode_send(opcode, buf, len);
}
int le_test_mode(uint16_t opcode, uint8_t* buf, uint8_t len) {
+ LOG_INFO(LOG_TAG, "%s", __func__);
+
+ /* sanity check */
if (!interface_ready()) return BT_STATUS_NOT_READY;
- switch (opcode) {
- case HCI_BLE_TRANSMITTER_TEST:
- if (len != 3) return BT_STATUS_PARM_INVALID;
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_ble_transmitter_test,
- buf[0], buf[1], buf[2]));
- break;
- case HCI_BLE_RECEIVER_TEST:
- if (len != 1) return BT_STATUS_PARM_INVALID;
- do_in_main_thread(FROM_HERE,
- base::BindOnce(btif_ble_receiver_test, buf[0]));
- break;
- case HCI_BLE_TEST_END:
- do_in_main_thread(FROM_HERE, base::BindOnce(btif_ble_test_end));
- break;
- default:
- return BT_STATUS_UNSUPPORTED;
- }
- return BT_STATUS_SUCCESS;
+ return btif_le_test_mode(opcode, buf, len);
}
static bt_os_callouts_t* wakelock_os_callouts_saved = nullptr;
@@ -554,7 +466,7 @@ static int set_os_callouts(bt_os_callouts_t* callouts) {
}
static int config_clear(void) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
return btif_config_clear() ? BT_STATUS_SUCCESS : BT_STATUS_FAIL;
}
@@ -568,11 +480,8 @@ static std::string obfuscate_address(const RawAddress& address) {
}
static int get_metric_id(const RawAddress& address) {
- return allocate_metric_id_from_metric_id_allocator(address);
-}
-
-static int set_dynamic_audio_buffer_size(int codec, int size) {
- return btif_set_dynamic_audio_buffer_size(codec, size);
+ return bluetooth::common::MetricIdAllocator::GetInstance().AllocateId(
+ address);
}
EXPORT_SYMBOL bt_interface_t bluetoothInterface = {
@@ -587,7 +496,7 @@ EXPORT_SYMBOL bt_interface_t bluetoothInterface = {
get_remote_device_properties,
get_remote_device_property,
set_remote_device_property,
- nullptr,
+ get_remote_service_record,
get_remote_services,
start_discovery,
cancel_discovery,
@@ -612,252 +521,4 @@ EXPORT_SYMBOL bt_interface_t bluetoothInterface = {
get_avrcp_service,
obfuscate_address,
get_metric_id,
- set_dynamic_audio_buffer_size,
- generate_local_oob_data};
-
-// callback reporting helpers
-
-bt_property_t* property_deep_copy_array(int num_properties,
- bt_property_t* properties) {
- bt_property_t* copy = nullptr;
- if (num_properties > 0) {
- size_t content_len = 0;
- for (int i = 0; i < num_properties; i++) {
- auto len = properties[i].len;
- if (len > 0) {
- content_len += len;
- }
- }
-
- copy = (bt_property_t*)osi_calloc((sizeof(bt_property_t) * num_properties) +
- content_len);
- uint8_t* content = (uint8_t*)(copy + num_properties);
-
- for (int i = 0; i < num_properties; i++) {
- auto len = properties[i].len;
- copy[i].type = properties[i].type;
- copy[i].len = len;
- if (len <= 0) {
- continue;
- }
- copy[i].val = content;
- memcpy(content, properties[i].val, len);
- content += len;
- }
- }
- return copy;
-}
-
-void invoke_adapter_state_changed_cb(bt_state_t state) {
- do_in_jni_thread(FROM_HERE, base::BindOnce(
- [](bt_state_t state) {
- HAL_CBACK(bt_hal_cbacks,
- adapter_state_changed_cb, state);
- },
- state));
-}
-
-void invoke_adapter_properties_cb(bt_status_t status, int num_properties,
- bt_property_t* properties) {
- do_in_jni_thread(FROM_HERE,
- base::BindOnce(
- [](bt_status_t status, int num_properties,
- bt_property_t* properties) {
- HAL_CBACK(bt_hal_cbacks, adapter_properties_cb, status,
- num_properties, properties);
- if (properties) {
- osi_free(properties);
- }
- },
- status, num_properties,
- property_deep_copy_array(num_properties, properties)));
-}
-
-void invoke_remote_device_properties_cb(bt_status_t status, RawAddress bd_addr,
- int num_properties,
- bt_property_t* properties) {
- do_in_jni_thread(
- FROM_HERE, base::BindOnce(
- [](bt_status_t status, RawAddress bd_addr,
- int num_properties, bt_property_t* properties) {
- HAL_CBACK(bt_hal_cbacks, remote_device_properties_cb,
- status, &bd_addr, num_properties, properties);
- if (properties) {
- osi_free(properties);
- }
- },
- status, bd_addr, num_properties,
- property_deep_copy_array(num_properties, properties)));
-}
-
-void invoke_device_found_cb(int num_properties, bt_property_t* properties) {
- do_in_jni_thread(FROM_HERE,
- base::BindOnce(
- [](int num_properties, bt_property_t* properties) {
- HAL_CBACK(bt_hal_cbacks, device_found_cb,
- num_properties, properties);
- if (properties) {
- osi_free(properties);
- }
- },
- num_properties,
- property_deep_copy_array(num_properties, properties)));
-}
-
-void invoke_discovery_state_changed_cb(bt_discovery_state_t state) {
- do_in_jni_thread(FROM_HERE, base::BindOnce(
- [](bt_discovery_state_t state) {
- HAL_CBACK(bt_hal_cbacks,
- discovery_state_changed_cb,
- state);
- },
- state));
-}
-
-void invoke_pin_request_cb(RawAddress bd_addr, bt_bdname_t bd_name,
- uint32_t cod, bool min_16_digit) {
- do_in_jni_thread(FROM_HERE, base::BindOnce(
- [](RawAddress bd_addr, bt_bdname_t bd_name,
- uint32_t cod, bool min_16_digit) {
- HAL_CBACK(bt_hal_cbacks, pin_request_cb,
- &bd_addr, &bd_name, cod,
- min_16_digit);
- },
- bd_addr, bd_name, cod, min_16_digit));
-}
-
-void invoke_ssp_request_cb(RawAddress bd_addr, bt_bdname_t bd_name,
- uint32_t cod, bt_ssp_variant_t pairing_variant,
- uint32_t pass_key) {
- do_in_jni_thread(FROM_HERE,
- base::BindOnce(
- [](RawAddress bd_addr, bt_bdname_t bd_name, uint32_t cod,
- bt_ssp_variant_t pairing_variant, uint32_t pass_key) {
- HAL_CBACK(bt_hal_cbacks, ssp_request_cb, &bd_addr,
- &bd_name, cod, pairing_variant, pass_key);
- },
- bd_addr, bd_name, cod, pairing_variant, pass_key));
-}
-
-void invoke_oob_data_request_cb(tBT_TRANSPORT t, bool valid, Octet16 c,
- Octet16 r, RawAddress raw_address,
- uint8_t address_type) {
- LOG_INFO("%s", __func__);
- bt_oob_data_t oob_data = {};
- char* local_name;
- BTM_ReadLocalDeviceName(&local_name);
- for (int i = 0; i < BTM_MAX_LOC_BD_NAME_LEN; i++) {
- oob_data.device_name[i] = local_name[i];
- }
-
- // Set the local address
- int j = 5;
- for (int i = 0; i < 6; i++) {
- oob_data.address[i] = raw_address.address[j];
- j--;
- }
- oob_data.address[6] = address_type;
-
- // Each value (for C and R) is 16 octets in length
- bool c_empty = true;
- for (int i = 0; i < 16; i++) {
- // C cannot be all 0s, if so then we want to fail
- if (c[i] != 0) c_empty = false;
- oob_data.c[i] = c[i];
- // R is optional and may be empty
- oob_data.r[i] = r[i];
- }
- oob_data.is_valid = valid && !c_empty;
- // The oob_data_length is 2 octects in length. The value includes the length
- // of itself. 16 + 16 + 2 = 34 Data 0x0022 Little Endian order 0x2200
- oob_data.oob_data_length[0] = 0;
- oob_data.oob_data_length[1] = 34;
- bt_status_t status = do_in_jni_thread(
- FROM_HERE, base::BindOnce(
- [](tBT_TRANSPORT t, bt_oob_data_t oob_data) {
- HAL_CBACK(bt_hal_cbacks, generate_local_oob_data_cb, t,
- oob_data);
- },
- t, oob_data));
- if (status != BT_STATUS_SUCCESS) {
- LOG_ERROR("%s: Failed to call callback!", __func__);
- }
-}
-
-void invoke_bond_state_changed_cb(bt_status_t status, RawAddress bd_addr,
- bt_bond_state_t state) {
- do_in_jni_thread(
- FROM_HERE,
- base::BindOnce(
- [](bt_status_t status, RawAddress bd_addr, bt_bond_state_t state) {
- HAL_CBACK(bt_hal_cbacks, bond_state_changed_cb, status, &bd_addr,
- state);
- },
- status, bd_addr, state));
-}
-
-void invoke_acl_state_changed_cb(bt_status_t status, RawAddress bd_addr,
- bt_acl_state_t state, bt_hci_error_code_t hci_reason) {
- do_in_jni_thread(
- FROM_HERE,
- base::BindOnce(
- [](bt_status_t status, RawAddress bd_addr, bt_acl_state_t state,
- bt_hci_error_code_t hci_reason) {
- HAL_CBACK(bt_hal_cbacks, acl_state_changed_cb, status, &bd_addr,
- state, hci_reason);
- },
- status, bd_addr, state, hci_reason));
-}
-
-void invoke_thread_evt_cb(bt_cb_thread_evt event) {
- do_in_jni_thread(FROM_HERE, base::BindOnce(
- [](bt_cb_thread_evt event) {
- HAL_CBACK(bt_hal_cbacks, thread_evt_cb,
- event);
- if (event == DISASSOCIATE_JVM) {
- bt_hal_cbacks = NULL;
- }
- },
- event));
-}
-
-void invoke_le_test_mode_cb(bt_status_t status, uint16_t count) {
- do_in_jni_thread(FROM_HERE, base::BindOnce(
- [](bt_status_t status, uint16_t count) {
- HAL_CBACK(bt_hal_cbacks, le_test_mode_cb,
- status, count);
- },
- status, count));
-}
-
-// takes ownership of |uid_data|
-void invoke_energy_info_cb(bt_activity_energy_info energy_info,
- bt_uid_traffic_t* uid_data) {
- do_in_jni_thread(
- FROM_HERE,
- base::BindOnce(
- [](bt_activity_energy_info energy_info, bt_uid_traffic_t* uid_data) {
- HAL_CBACK(bt_hal_cbacks, energy_info_cb, &energy_info, uid_data);
- osi_free(uid_data);
- },
- energy_info, uid_data));
-}
-
-void invoke_link_quality_report_cb(
- uint64_t timestamp, int report_id, int rssi, int snr,
- int retransmission_count, int packets_not_receive_count,
- int negative_acknowledgement_count) {
- do_in_jni_thread(
- FROM_HERE,
- base::BindOnce(
- [](uint64_t timestamp, int report_id, int rssi, int snr,
- int retransmission_count, int packets_not_receive_count,
- int negative_acknowledgement_count) {
- HAL_CBACK(bt_hal_cbacks, link_quality_report_cb,
- timestamp, report_id, rssi, snr, retransmission_count,
- packets_not_receive_count,
- negative_acknowledgement_count);
- },
- timestamp, report_id, rssi, snr, retransmission_count,
- packets_not_receive_count, negative_acknowledgement_count));
-}
+};
diff --git a/btif/src/btif_a2dp.cc b/btif/src/btif_a2dp.cc
index 83cd10341..c9f45928f 100644
--- a/btif/src/btif_a2dp.cc
+++ b/btif/src/btif_a2dp.cc
@@ -37,8 +37,8 @@
#include "osi/include/log.h"
void btif_a2dp_on_idle(void) {
- LOG_VERBOSE("Peer stream endpoint type:%s",
- peer_stream_endpoint_text(btif_av_get_peer_sep()).c_str());
+ LOG_INFO(LOG_TAG, "%s: ## ON A2DP IDLE ## peer_sep = %d", __func__,
+ btif_av_get_peer_sep());
if (btif_av_get_peer_sep() == AVDT_TSEP_SNK) {
btif_a2dp_source_on_idle();
} else if (btif_av_get_peer_sep() == AVDT_TSEP_SRC) {
@@ -61,8 +61,7 @@ bool btif_a2dp_on_started(const RawAddress& peer_addr, tBTA_AV_START* p_av_start
bluetooth::audio::a2dp::ack_stream_started(status);
} else if (btif_av_is_a2dp_offload_enabled()) {
// TODO: BluetoothA2dp@1.0 is deprecated
- btif_a2dp_audio_on_started(
- (status == A2DP_CTRL_ACK_SUCCESS) ? BTA_AV_SUCCESS : BTA_AV_FAIL_SDP);
+ btif_a2dp_audio_on_started(status);
} else {
btif_a2dp_command_ack(status);
}
@@ -111,7 +110,8 @@ bool btif_a2dp_on_started(const RawAddress& peer_addr, tBTA_AV_START* p_av_start
}
void btif_a2dp_on_stopped(tBTA_AV_SUSPEND* p_av_suspend) {
- LOG_INFO("%s: ## ON A2DP STOPPED ## p_av_suspend=%p", __func__, p_av_suspend);
+ LOG_INFO(LOG_TAG, "%s: ## ON A2DP STOPPED ## p_av_suspend=%p", __func__,
+ p_av_suspend);
if (btif_av_get_peer_sep() == AVDT_TSEP_SRC) {
btif_a2dp_sink_on_stopped(p_av_suspend);
@@ -127,7 +127,7 @@ void btif_a2dp_on_stopped(tBTA_AV_SUSPEND* p_av_suspend) {
}
void btif_a2dp_on_suspended(tBTA_AV_SUSPEND* p_av_suspend) {
- LOG_INFO("%s: ## ON A2DP SUSPENDED ## p_av_suspend=%p", __func__,
+ LOG_INFO(LOG_TAG, "%s: ## ON A2DP SUSPENDED ## p_av_suspend=%p", __func__,
p_av_suspend);
if (btif_av_get_peer_sep() == AVDT_TSEP_SRC) {
btif_a2dp_sink_on_suspended(p_av_suspend);
@@ -145,20 +145,20 @@ void btif_a2dp_on_suspended(tBTA_AV_SUSPEND* p_av_suspend) {
void btif_a2dp_on_offload_started(const RawAddress& peer_addr,
tBTA_AV_STATUS status) {
tA2DP_CTRL_ACK ack;
- LOG_INFO("%s: peer %s status %d", __func__, peer_addr.ToString().c_str(),
- status);
+ LOG_INFO(LOG_TAG, "%s: peer %s status %d", __func__,
+ peer_addr.ToString().c_str(), status);
switch (status) {
case BTA_AV_SUCCESS:
ack = A2DP_CTRL_ACK_SUCCESS;
break;
case BTA_AV_FAIL_RESOURCES:
- LOG_ERROR("%s: peer %s FAILED UNSUPPORTED", __func__,
+ LOG_ERROR(LOG_TAG, "%s: peer %s FAILED UNSUPPORTED", __func__,
peer_addr.ToString().c_str());
ack = A2DP_CTRL_ACK_UNSUPPORTED;
break;
default:
- LOG_ERROR("%s: peer %s FAILED: status = %d", __func__,
+ LOG_ERROR(LOG_TAG, "%s: peer %s FAILED: status = %d", __func__,
peer_addr.ToString().c_str(), status);
ack = A2DP_CTRL_ACK_FAILURE;
break;
@@ -168,7 +168,7 @@ void btif_a2dp_on_offload_started(const RawAddress& peer_addr,
// Offload request will return with failure from btif_av sm if
// suspend is triggered for remote start. Disconnect only if SoC
// returned failure for offload VSC
- LOG_ERROR("%s: peer %s offload start failed", __func__,
+ LOG_ERROR(LOG_TAG, "%s: peer %s offload start failed", __func__,
peer_addr.ToString().c_str());
btif_av_src_disconnect_sink(peer_addr);
}
diff --git a/btif/src/btif_a2dp_audio_interface.cc b/btif/src/btif_a2dp_audio_interface.cc
index 7d7a083a3..026baa15a 100644
--- a/btif/src/btif_a2dp_audio_interface.cc
+++ b/btif/src/btif_a2dp_audio_interface.cc
@@ -18,28 +18,32 @@
#define LOG_TAG "btif_a2dp_audio_interface"
+#include "btif_a2dp_audio_interface.h"
+
+#include <mutex>
+
+#include <a2dp_vendor.h>
+#include <a2dp_vendor_ldac_constants.h>
#include <android/hardware/bluetooth/a2dp/1.0/IBluetoothAudioHost.h>
#include <android/hardware/bluetooth/a2dp/1.0/IBluetoothAudioOffload.h>
#include <android/hardware/bluetooth/a2dp/1.0/types.h>
-#include <base/bind.h>
-#include <base/callback.h>
-#include <base/location.h>
+#include <base/logging.h>
#include <hwbinder/ProcessState.h>
-#include <mutex>
-
-#include "audio_a2dp_hw/include/audio_a2dp_hw.h"
+#include <utils/RefBase.h>
+#include "a2dp_sbc.h"
+#include "bt_common.h"
#include "bta/av/bta_av_int.h"
-#include "bta/include/bta_av_api.h"
-#include "btif/include/btif_a2dp_source.h"
-#include "btif/include/btif_av.h"
-#include "btif/include/btif_av_co.h"
-#include "btif/include/btif_hf.h"
+#include "btif_a2dp.h"
+#include "btif_a2dp_control.h"
+#include "btif_a2dp_sink.h"
+#include "btif_a2dp_source.h"
+#include "btif_av.h"
+#include "btif_av_co.h"
+#include "btif_hf.h"
#include "common/metrics.h"
#include "common/time_util.h"
-#include "osi/include/log.h"
-#include "stack/include/a2dp_codec_api.h"
-#include "stack/include/avdt_api.h"
-#include "stack/include/btu.h" // do_in_main_thread
+#include "osi/include/osi.h"
+#include "stack/include/btu.h"
using bluetooth::common::A2dpSessionMetrics;
using bluetooth::common::BluetoothMetricsLogger;
@@ -148,7 +152,7 @@ class BluetoothAudioHost : public IBluetoothAudioHost {
// TODO : Delay reporting
/* Return<void> a2dp_get_sink_latency() {
- LOG_INFO("%s:start ", __func__);
+ LOG_INFO(LOG_TAG,"%s:start ", __func__);
btif_a2dp_audio_send_sink_latency();
return Void();
}*/
@@ -159,7 +163,7 @@ class BluetoothAudioDeathRecipient : public hidl_death_recipient {
void serviceDied(
uint64_t /*cookie*/,
const wp<::android::hidl::base::V1_0::IBase>& /*who*/) override {
- LOG_ERROR("%s", __func__);
+ LOG_ERROR(LOG_TAG, "%s", __func__);
// Restart the session on the correct thread
do_in_main_thread(FROM_HERE,
base::Bind(&btif_a2dp_audio_interface_restart_session));
@@ -189,7 +193,7 @@ static Status mapToStatus(uint8_t resp) {
static void btif_a2dp_get_codec_configuration(
CodecConfiguration* p_codec_info) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
tBT_A2DP_OFFLOAD a2dp_offload;
A2dpCodecConfig* a2dpCodecConfig = bta_av_get_a2dp_current_codec();
a2dpCodecConfig->getCodecSpecificConfig(&a2dp_offload);
@@ -203,7 +207,7 @@ static void btif_a2dp_get_codec_configuration(
BTA_AV_CODEC_TYPE_SBC;
p_codec_info->codecSpecific.sbcData.codecParameters =
a2dp_offload.codec_info[0];
- LOG_INFO(" %s: codec parameters =%d", __func__,
+ LOG_INFO(LOG_TAG, " %s: codec parameters =%d", __func__,
a2dp_offload.codec_info[0]);
p_codec_info->codecSpecific.sbcData.minBitpool =
a2dp_offload.codec_info[1];
@@ -247,8 +251,8 @@ static void btif_a2dp_get_codec_configuration(
} else {
p_codec_info->peerMtu = peer_param.peer_mtu;
}
- LOG_INFO("%s: peer MTU: %d effective MTU: %d result MTU: %d", __func__,
- peer_param.peer_mtu, effectiveMtu, p_codec_info->peerMtu);
+ LOG_INFO(LOG_TAG, "%s: peer MTU: %d effective MTU: %d result MTU: %d",
+ __func__, peer_param.peer_mtu, effectiveMtu, p_codec_info->peerMtu);
p_codec_info->sampleRate =
(::android::hardware::bluetooth::a2dp::V1_0::SampleRate)
@@ -263,28 +267,31 @@ static void btif_a2dp_get_codec_configuration(
}
static void btif_a2dp_audio_interface_init() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
btAudio = IBluetoothAudioOffload::getService();
CHECK(btAudio != nullptr);
auto death_link = btAudio->linkToDeath(bluetoothAudioDeathRecipient, 0);
if (!death_link.isOk()) {
- LOG_ERROR("%s: Cannot observe the Bluetooth Audio HAL's death", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Cannot observe the Bluetooth Audio HAL's death",
+ __func__);
}
- LOG_INFO("%s: IBluetoothAudioOffload::getService() returned %p (%s)",
- __func__, btAudio.get(), (btAudio->isRemote() ? "remote" : "local"));
+ LOG_DEBUG(
+ LOG_TAG, "%s: IBluetoothAudioOffload::getService() returned %p (%s)",
+ __func__, btAudio.get(), (btAudio->isRemote() ? "remote" : "local"));
- LOG_INFO("%s:Init returned", __func__);
+ LOG_INFO(LOG_TAG, "%s:Init returned", __func__);
}
static void btif_a2dp_audio_interface_deinit() {
- LOG_INFO("%s: start", __func__);
+ LOG_INFO(LOG_TAG, "%s: start", __func__);
if (btAudio != nullptr) {
auto death_unlink = btAudio->unlinkToDeath(bluetoothAudioDeathRecipient);
if (!death_unlink.isOk()) {
- LOG_ERROR("%s: Error unlinking death observer from Bluetooth Audio HAL",
+ LOG_ERROR(LOG_TAG,
+ "%s: Error unlinking death observer from Bluetooth Audio HAL",
__func__);
}
}
@@ -292,7 +299,7 @@ static void btif_a2dp_audio_interface_deinit() {
}
void btif_a2dp_audio_interface_start_session() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
BluetoothMetricsLogger::GetInstance()->LogBluetoothSessionStart(
bluetooth::common::CONNECTION_TECHNOLOGY_TYPE_BREDR, 0);
a2dp_offload_audio_stats.Reset();
@@ -305,7 +312,7 @@ void btif_a2dp_audio_interface_start_session() {
}
void btif_a2dp_audio_interface_end_session() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
a2dp_offload_audio_stats.LogAudioStopMetricsAndReset();
BluetoothMetricsLogger::GetInstance()->LogBluetoothSessionEnd(
bluetooth::common::DISCONNECT_REASON_UNKNOWN, 0);
@@ -313,16 +320,17 @@ void btif_a2dp_audio_interface_end_session() {
if (btAudio == nullptr) return;
auto ret = btAudio->endSession();
if (!ret.isOk()) {
- LOG_ERROR("HAL server is dead");
+ LOG_ERROR(LOG_TAG, "HAL server is dead");
}
btif_a2dp_audio_interface_deinit();
}
// Conditionally restart the session only if it was started before
static void btif_a2dp_audio_interface_restart_session() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
if (btAudio == nullptr) {
- LOG_INFO("%s: nothing to restart - session was not started", __func__);
+ LOG_INFO(LOG_TAG, "%s: nothing to restart - session was not started",
+ __func__);
return;
}
btAudio = nullptr;
@@ -330,13 +338,13 @@ static void btif_a2dp_audio_interface_restart_session() {
}
void btif_a2dp_audio_on_started(tBTA_AV_STATUS status) {
- LOG_INFO("%s: status = %d", __func__, status);
+ LOG_INFO(LOG_TAG, "%s: status = %d", __func__, status);
if (btAudio != nullptr) {
if (a2dp_cmd_pending == A2DP_CTRL_CMD_START) {
if (status != A2DP_CTRL_ACK_PENDING) {
a2dp_cmd_pending = A2DP_CTRL_CMD_NONE;
}
- LOG_INFO("%s: calling method onStarted", __func__);
+ LOG_INFO(LOG_TAG, "%s: calling method onStarted", __func__);
auto hal_status = mapToStatus(status);
btAudio->streamStarted(hal_status);
if (hal_status == Status::SUCCESS) {
@@ -347,13 +355,13 @@ void btif_a2dp_audio_on_started(tBTA_AV_STATUS status) {
}
void btif_a2dp_audio_on_suspended(tBTA_AV_STATUS status) {
- LOG_INFO("%s: status = %d", __func__, status);
+ LOG_INFO(LOG_TAG, "%s: status = %d", __func__, status);
if (btAudio != nullptr) {
if (a2dp_cmd_pending == A2DP_CTRL_CMD_SUSPEND) {
if (status != A2DP_CTRL_ACK_PENDING) {
a2dp_cmd_pending = A2DP_CTRL_CMD_NONE;
}
- LOG_INFO("calling method onSuspended");
+ LOG_INFO(LOG_TAG, "calling method onSuspended");
auto hal_status = mapToStatus(status);
btAudio->streamSuspended(hal_status);
if (hal_status == Status::SUCCESS) {
@@ -364,16 +372,17 @@ void btif_a2dp_audio_on_suspended(tBTA_AV_STATUS status) {
}
void btif_a2dp_audio_on_stopped(tBTA_AV_STATUS status) {
- LOG_INFO("%s: status = %d", __func__, status);
+ LOG_INFO(LOG_TAG, "%s: status = %d", __func__, status);
if (btAudio != nullptr && a2dp_cmd_pending == A2DP_CTRL_CMD_START) {
a2dp_cmd_pending = A2DP_CTRL_CMD_NONE;
- LOG_INFO("%s: Remote disconnected when start under progress", __func__);
+ LOG_INFO(LOG_TAG, "%s: Remote disconnected when start under progress",
+ __func__);
btAudio->streamStarted(mapToStatus(A2DP_CTRL_ACK_DISCONNECT_IN_PROGRESS));
a2dp_offload_audio_stats.LogAudioStopMetricsAndReset();
}
}
void btif_a2dp_audio_send_start_req() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
uint8_t resp;
resp = btif_a2dp_audio_process_request(A2DP_CTRL_CMD_START);
if (btAudio != nullptr) {
@@ -382,11 +391,11 @@ void btif_a2dp_audio_send_start_req() {
if (status == Status::SUCCESS) {
a2dp_offload_audio_stats.LogAudioStart();
}
- if (!ret.isOk()) LOG_ERROR("HAL server died");
+ if (!ret.isOk()) LOG_ERROR(LOG_TAG, "HAL server died");
}
}
void btif_a2dp_audio_send_suspend_req() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
uint8_t resp;
resp = btif_a2dp_audio_process_request(A2DP_CTRL_CMD_SUSPEND);
if (btAudio != nullptr) {
@@ -395,28 +404,28 @@ void btif_a2dp_audio_send_suspend_req() {
if (status == Status::SUCCESS) {
a2dp_offload_audio_stats.LogAudioStopMetricsAndReset();
}
- if (!ret.isOk()) LOG_ERROR("HAL server died");
+ if (!ret.isOk()) LOG_ERROR(LOG_TAG, "HAL server died");
}
}
void btif_a2dp_audio_send_stop_req() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
btif_a2dp_audio_process_request(A2DP_CTRL_CMD_STOP);
a2dp_offload_audio_stats.LogAudioStopMetricsAndReset();
}
/*void btif_a2dp_audio_send_sink_latency()
{
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
uint16_t sink_latency = btif_av_get_sink_latency();
if (btAudio != nullptr) {
auto ret = btAudio->a2dp_on_get_sink_latency(sink_latency);
- if (!ret.isOk()) LOG_ERROR("server died");
+ if (!ret.isOk()) LOG_ERROR(LOG_TAG, "server died");
}
}*/
uint8_t btif_a2dp_audio_process_request(uint8_t cmd) {
- LOG_INFO("%s: cmd: %s", __func__,
+ LOG_INFO(LOG_TAG, "%s: cmd: %s", __func__,
audio_a2dp_hw_dump_ctrl_event((tA2DP_CTRL_CMD)cmd));
uint8_t status;
switch (cmd) {
@@ -499,7 +508,7 @@ uint8_t btif_a2dp_audio_process_request(uint8_t cmd) {
status = A2DP_CTRL_ACK_FAILURE;
break;
}
- LOG_INFO("a2dp-ctrl-cmd : %s DONE returning status %d",
+ LOG_INFO(LOG_TAG, "a2dp-ctrl-cmd : %s DONE returning status %d",
audio_a2dp_hw_dump_ctrl_event((tA2DP_CTRL_CMD)cmd), status);
if (status == A2DP_CTRL_ACK_PENDING) {
a2dp_cmd_pending = cmd;
diff --git a/btif/src/btif_a2dp_sink.cc b/btif/src/btif_a2dp_sink.cc
index fa02a8682..0d96f16c1 100644
--- a/btif/src/btif_a2dp_sink.cc
+++ b/btif/src/btif_a2dp_sink.cc
@@ -19,25 +19,25 @@
#define LOG_TAG "bt_btif_a2dp_sink"
-#include <base/bind.h>
#include <atomic>
+#include <cstdio>
+#include <cstring>
#include <mutex>
#include <string>
-#include "bt_target.h" // Must be first to define build configuration
+#include <base/bind.h>
-#include "btif/include/btif_a2dp_sink.h"
-#include "btif/include/btif_av.h"
-#include "btif/include/btif_av_co.h"
-#include "btif/include/btif_avrcp_audio_track.h"
-#include "btif/include/btif_util.h" // CASE_RETURN_STR
+#include "bt_common.h"
+#include "btif_a2dp.h"
+#include "btif_a2dp_sink.h"
+#include "btif_av.h"
+#include "btif_av_co.h"
+#include "btif_avrcp_audio_track.h"
+#include "btif_util.h"
#include "common/message_loop_thread.h"
-#include "osi/include/alarm.h"
-#include "osi/include/allocator.h"
#include "osi/include/fixed_queue.h"
#include "osi/include/log.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/include/bt_types.h"
+#include "osi/include/osi.h"
using bluetooth::common::MessageLoopThread;
using LockGuard = std::lock_guard<std::mutex>;
@@ -70,12 +70,12 @@ enum {
};
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
uint8_t codec_info[AVDT_CODEC_SIZE];
} tBTIF_MEDIA_SINK_DECODER_UPDATE;
typedef struct {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
btif_a2dp_sink_focus_state_t focus_state;
} tBTIF_MEDIA_SINK_FOCUS_UPDATE;
@@ -136,7 +136,7 @@ static void btif_a2dp_sink_start_session_delayed(
static void btif_a2dp_sink_end_session_delayed();
static void btif_a2dp_sink_shutdown_delayed();
static void btif_a2dp_sink_cleanup_delayed();
-static void btif_a2dp_sink_command_ready(BT_HDR_RIGID* p_msg);
+static void btif_a2dp_sink_command_ready(BT_HDR* p_msg);
static void btif_a2dp_sink_audio_handle_stop_decoding();
static void btif_decode_alarm_cb(void* context);
static void btif_a2dp_sink_audio_handle_start_decoding();
@@ -169,11 +169,11 @@ UNUSED_ATTR static const char* dump_media_event(uint16_t event) {
}
bool btif_a2dp_sink_init() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
LockGuard lock(g_mutex);
if (btif_a2dp_sink_state != BTIF_A2DP_SINK_STATE_OFF) {
- LOG_ERROR("%s: A2DP Sink media task already running", __func__);
+ LOG_ERROR(LOG_TAG, "%s: A2DP Sink media task already running", __func__);
return false;
}
@@ -183,7 +183,7 @@ bool btif_a2dp_sink_init() {
/* Start A2DP Sink media task */
btif_a2dp_sink_cb.worker_thread.StartUp();
if (!btif_a2dp_sink_cb.worker_thread.IsRunning()) {
- LOG_ERROR("%s: unable to start up media thread", __func__);
+ LOG_ERROR(LOG_TAG, "%s: unable to start up media thread", __func__);
btif_a2dp_sink_state = BTIF_A2DP_SINK_STATE_OFF;
return false;
}
@@ -201,19 +201,19 @@ bool btif_a2dp_sink_init() {
}
static void btif_a2dp_sink_init_delayed() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
btif_a2dp_sink_state = BTIF_A2DP_SINK_STATE_RUNNING;
}
bool btif_a2dp_sink_startup() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
btif_a2dp_sink_cb.worker_thread.DoInThread(
FROM_HERE, base::BindOnce(btif_a2dp_sink_startup_delayed));
return true;
}
static void btif_a2dp_sink_startup_delayed() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
LockGuard lock(g_mutex);
// Nothing to do
}
@@ -270,32 +270,33 @@ bool btif_a2dp_sink_restart_session(const RawAddress& old_peer_address,
}
bool btif_a2dp_sink_end_session(const RawAddress& peer_address) {
- LOG_INFO("%s: peer_address=%s", __func__, peer_address.ToString().c_str());
+ LOG_INFO(LOG_TAG, "%s: peer_address=%s", __func__,
+ peer_address.ToString().c_str());
btif_a2dp_sink_cb.worker_thread.DoInThread(
FROM_HERE, base::BindOnce(btif_a2dp_sink_end_session_delayed));
return true;
}
static void btif_a2dp_sink_end_session_delayed() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
LockGuard lock(g_mutex);
// Nothing to do
}
void btif_a2dp_sink_shutdown() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
btif_a2dp_sink_cb.worker_thread.DoInThread(
FROM_HERE, base::BindOnce(btif_a2dp_sink_shutdown_delayed));
}
static void btif_a2dp_sink_shutdown_delayed() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
LockGuard lock(g_mutex);
// Nothing to do
}
void btif_a2dp_sink_cleanup() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
alarm_t* decode_alarm;
@@ -325,7 +326,7 @@ void btif_a2dp_sink_cleanup() {
}
static void btif_a2dp_sink_cleanup_delayed() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
LockGuard lock(g_mutex);
fixed_queue_free(btif_a2dp_sink_cb.rx_audio_queue, nullptr);
@@ -348,8 +349,8 @@ tA2DP_CHANNEL_COUNT btif_a2dp_sink_get_channel_count() {
return btif_a2dp_sink_cb.channel_count;
}
-static void btif_a2dp_sink_command_ready(BT_HDR_RIGID* p_msg) {
- LOG_VERBOSE("%s: event %d %s", __func__, p_msg->event,
+static void btif_a2dp_sink_command_ready(BT_HDR* p_msg) {
+ LOG_VERBOSE(LOG_TAG, "%s: event %d %s", __func__, p_msg->event,
dump_media_event(p_msg->event));
switch (p_msg->event) {
@@ -376,16 +377,16 @@ static void btif_a2dp_sink_command_ready(BT_HDR_RIGID* p_msg) {
btif_a2dp_sink_on_suspend_event();
break;
default:
- LOG_ERROR("%s: unknown event %d", __func__, p_msg->event);
+ LOG_ERROR(LOG_TAG, "%s: unknown event %d", __func__, p_msg->event);
break;
}
osi_free(p_msg);
- LOG_VERBOSE("%s: %s DONE", __func__, dump_media_event(p_msg->event));
+ LOG_VERBOSE(LOG_TAG, "%s: %s DONE", __func__, dump_media_event(p_msg->event));
}
void btif_a2dp_sink_update_decoder(const uint8_t* p_codec_info) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
tBTIF_MEDIA_SINK_DECODER_UPDATE* p_buf =
reinterpret_cast<tBTIF_MEDIA_SINK_DECODER_UPDATE*>(
osi_malloc(sizeof(tBTIF_MEDIA_SINK_DECODER_UPDATE)));
@@ -398,14 +399,12 @@ void btif_a2dp_sink_update_decoder(const uint8_t* p_codec_info) {
p_buf->hdr.event = BTIF_MEDIA_SINK_DECODER_UPDATE;
btif_a2dp_sink_cb.worker_thread.DoInThread(
- FROM_HERE,
- base::BindOnce(btif_a2dp_sink_command_ready, (BT_HDR_RIGID*)p_buf));
+ FROM_HERE, base::BindOnce(btif_a2dp_sink_command_ready, (BT_HDR*)p_buf));
}
void btif_a2dp_sink_on_idle() {
- LOG_INFO("%s", __func__);
- BT_HDR_RIGID* p_buf =
- reinterpret_cast<BT_HDR_RIGID*>(osi_malloc(sizeof(BT_HDR_RIGID)));
+ LOG_INFO(LOG_TAG, "%s", __func__);
+ BT_HDR* p_buf = reinterpret_cast<BT_HDR*>(osi_malloc(sizeof(BT_HDR)));
p_buf->event = BTIF_MEDIA_SINK_SUSPEND;
btif_a2dp_sink_cb.worker_thread.DoInThread(
FROM_HERE, base::BindOnce(btif_a2dp_sink_command_ready, p_buf));
@@ -416,9 +415,8 @@ void btif_a2dp_sink_on_idle() {
}
void btif_a2dp_sink_on_stopped(UNUSED_ATTR tBTA_AV_SUSPEND* p_av_suspend) {
- LOG_INFO("%s", __func__);
- BT_HDR_RIGID* p_buf =
- reinterpret_cast<BT_HDR_RIGID*>(osi_malloc(sizeof(BT_HDR_RIGID)));
+ LOG_INFO(LOG_TAG, "%s", __func__);
+ BT_HDR* p_buf = reinterpret_cast<BT_HDR*>(osi_malloc(sizeof(BT_HDR)));
p_buf->event = BTIF_MEDIA_SINK_SUSPEND;
btif_a2dp_sink_cb.worker_thread.DoInThread(
FROM_HERE, base::BindOnce(btif_a2dp_sink_command_ready, p_buf));
@@ -428,9 +426,8 @@ void btif_a2dp_sink_on_stopped(UNUSED_ATTR tBTA_AV_SUSPEND* p_av_suspend) {
}
void btif_a2dp_sink_on_suspended(UNUSED_ATTR tBTA_AV_SUSPEND* p_av_suspend) {
- LOG_INFO("%s", __func__);
- BT_HDR_RIGID* p_buf =
- reinterpret_cast<BT_HDR_RIGID*>(osi_malloc(sizeof(BT_HDR_RIGID)));
+ LOG_INFO(LOG_TAG, "%s", __func__);
+ BT_HDR* p_buf = reinterpret_cast<BT_HDR*>(osi_malloc(sizeof(BT_HDR)));
p_buf->event = BTIF_MEDIA_SINK_SUSPEND;
btif_a2dp_sink_cb.worker_thread.DoInThread(
FROM_HERE, base::BindOnce(btif_a2dp_sink_command_ready, p_buf));
@@ -440,10 +437,9 @@ void btif_a2dp_sink_on_suspended(UNUSED_ATTR tBTA_AV_SUSPEND* p_av_suspend) {
}
bool btif_a2dp_sink_on_start() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
- BT_HDR_RIGID* p_buf =
- reinterpret_cast<BT_HDR_RIGID*>(osi_malloc(sizeof(BT_HDR_RIGID)));
+ BT_HDR* p_buf = reinterpret_cast<BT_HDR*>(osi_malloc(sizeof(BT_HDR)));
p_buf->event = BTIF_MEDIA_SINK_START;
btif_a2dp_sink_cb.worker_thread.DoInThread(
FROM_HERE, base::BindOnce(btif_a2dp_sink_command_ready, p_buf));
@@ -452,7 +448,7 @@ bool btif_a2dp_sink_on_start() {
}
static void btif_a2dp_sink_audio_handle_stop_decoding() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
alarm_t* old_alarm;
{
LockGuard lock(g_mutex);
@@ -483,7 +479,7 @@ static void btif_decode_alarm_cb(UNUSED_ATTR void* context) {
}
static void btif_a2dp_sink_clear_track_event() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
LockGuard lock(g_mutex);
#ifndef OS_GENERIC
@@ -495,7 +491,7 @@ static void btif_a2dp_sink_clear_track_event() {
// Must be called while locked.
static void btif_a2dp_sink_audio_handle_start_decoding() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
if (btif_a2dp_sink_cb.decode_alarm != nullptr)
return; // Already started decoding
@@ -505,7 +501,7 @@ static void btif_a2dp_sink_audio_handle_start_decoding() {
btif_a2dp_sink_cb.decode_alarm = alarm_new_periodic("btif.a2dp_sink_decode");
if (btif_a2dp_sink_cb.decode_alarm == nullptr) {
- LOG_ERROR("%s: unable to allocate decode alarm", __func__);
+ LOG_ERROR(LOG_TAG, "%s: unable to allocate decode alarm", __func__);
return;
}
alarm_set(btif_a2dp_sink_cb.decode_alarm, BTIF_SINK_MEDIA_TIME_TICK_MS,
@@ -529,7 +525,7 @@ static void btif_a2dp_sink_handle_inc_media(BT_HDR* p_msg) {
CHECK(btif_a2dp_sink_cb.decoder_interface != nullptr);
if (!btif_a2dp_sink_cb.decoder_interface->decode_packet(p_msg)) {
- LOG_ERROR("%s: decoding failed", __func__);
+ LOG_ERROR(LOG_TAG, "%s: decoding failed", __func__);
}
}
@@ -572,14 +568,14 @@ static void btif_a2dp_sink_avk_handle_timer() {
/* when true media task discards any rx frames */
void btif_a2dp_sink_set_rx_flush(bool enable) {
- LOG_INFO("%s: enable=%s", __func__, (enable) ? "true" : "false");
+ LOG_INFO(LOG_TAG, "%s: enable=%s", __func__, (enable) ? "true" : "false");
LockGuard lock(g_mutex);
btif_a2dp_sink_cb.rx_flush = enable;
}
static void btif_a2dp_sink_audio_rx_flush_event() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
LockGuard lock(g_mutex);
// Flush all received encoded audio buffers
fixed_queue_flush(btif_a2dp_sink_cb.rx_audio_queue, osi_free);
@@ -587,7 +583,7 @@ static void btif_a2dp_sink_audio_rx_flush_event() {
static void btif_a2dp_sink_decoder_update_event(
tBTIF_MEDIA_SINK_DECODER_UPDATE* p_buf) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
LockGuard lock(g_mutex);
APPL_TRACE_DEBUG("%s: p_codec_info[%x:%x:%x:%x:%x:%x]", __func__,
p_buf->codec_info[1], p_buf->codec_info[2],
@@ -596,22 +592,22 @@ static void btif_a2dp_sink_decoder_update_event(
int sample_rate = A2DP_GetTrackSampleRate(p_buf->codec_info);
if (sample_rate == -1) {
- LOG_ERROR("%s: cannot get the track frequency", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot get the track frequency", __func__);
return;
}
int bits_per_sample = A2DP_GetTrackBitsPerSample(p_buf->codec_info);
if (bits_per_sample == -1) {
- LOG_ERROR("%s: cannot get the bits per sample", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot get the bits per sample", __func__);
return;
}
int channel_count = A2DP_GetTrackChannelCount(p_buf->codec_info);
if (channel_count == -1) {
- LOG_ERROR("%s: cannot get the channel count", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot get the channel count", __func__);
return;
}
int channel_type = A2DP_GetSinkTrackChannelType(p_buf->codec_info);
if (channel_type == -1) {
- LOG_ERROR("%s: cannot get the Sink channel type", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot get the Sink channel type", __func__);
return;
}
btif_a2dp_sink_cb.sample_rate = sample_rate;
@@ -623,13 +619,14 @@ static void btif_a2dp_sink_decoder_update_event(
btif_a2dp_sink_cb.decoder_interface = bta_av_co_get_decoder_interface();
if (btif_a2dp_sink_cb.decoder_interface == nullptr) {
- LOG_ERROR("%s: cannot stream audio: no source decoder interface", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot stream audio: no source decoder interface",
+ __func__);
return;
}
if (!btif_a2dp_sink_cb.decoder_interface->decoder_init(
btif_a2dp_sink_on_decode_complete)) {
- LOG_ERROR("%s: failed to initialize decoder", __func__);
+ LOG_ERROR(LOG_TAG, "%s: failed to initialize decoder", __func__);
return;
}
@@ -645,7 +642,7 @@ static void btif_a2dp_sink_decoder_update_event(
NULL;
#endif
if (btif_a2dp_sink_cb.audio_track == nullptr) {
- LOG_ERROR("%s: track creation failed", __func__);
+ LOG_ERROR(LOG_TAG, "%s: track creation failed", __func__);
return;
}
}
@@ -680,14 +677,13 @@ uint8_t btif_a2dp_sink_enqueue_buf(BT_HDR* p_pkt) {
}
void btif_a2dp_sink_audio_rx_flush_req() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
if (fixed_queue_is_empty(btif_a2dp_sink_cb.rx_audio_queue)) {
/* Queue is already empty */
return;
}
- BT_HDR_RIGID* p_buf =
- reinterpret_cast<BT_HDR_RIGID*>(osi_malloc(sizeof(BT_HDR_RIGID)));
+ BT_HDR* p_buf = reinterpret_cast<BT_HDR*>(osi_malloc(sizeof(BT_HDR)));
p_buf->event = BTIF_MEDIA_SINK_AUDIO_RX_FLUSH;
btif_a2dp_sink_cb.worker_thread.DoInThread(
FROM_HERE, base::BindOnce(btif_a2dp_sink_command_ready, p_buf));
@@ -698,20 +694,19 @@ void btif_a2dp_sink_debug_dump(UNUSED_ATTR int fd) {
}
void btif_a2dp_sink_set_focus_state_req(btif_a2dp_sink_focus_state_t state) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
tBTIF_MEDIA_SINK_FOCUS_UPDATE* p_buf =
reinterpret_cast<tBTIF_MEDIA_SINK_FOCUS_UPDATE*>(
osi_malloc(sizeof(tBTIF_MEDIA_SINK_FOCUS_UPDATE)));
p_buf->focus_state = state;
p_buf->hdr.event = BTIF_MEDIA_SINK_SET_FOCUS_STATE;
btif_a2dp_sink_cb.worker_thread.DoInThread(
- FROM_HERE,
- base::BindOnce(btif_a2dp_sink_command_ready, (BT_HDR_RIGID*)p_buf));
+ FROM_HERE, base::BindOnce(btif_a2dp_sink_command_ready, (BT_HDR*)p_buf));
}
static void btif_a2dp_sink_set_focus_state_event(
btif_a2dp_sink_focus_state_t state) {
- LOG_INFO("%s: state=%d", __func__, state);
+ LOG_INFO(LOG_TAG, "%s: state=%d", __func__, state);
LockGuard lock(g_mutex);
APPL_TRACE_DEBUG("%s: setting focus state to %d", __func__, state);
@@ -725,7 +720,7 @@ static void btif_a2dp_sink_set_focus_state_event(
}
void btif_a2dp_sink_set_audio_track_gain(float gain) {
- LOG_INFO("%s: set gain to %f", __func__, gain);
+ LOG_INFO(LOG_TAG, "%s: set gain to %f", __func__, gain);
LockGuard lock(g_mutex);
#ifndef OS_GENERIC
@@ -734,9 +729,8 @@ void btif_a2dp_sink_set_audio_track_gain(float gain) {
}
static void btif_a2dp_sink_clear_track_event_req() {
- LOG_INFO("%s", __func__);
- BT_HDR_RIGID* p_buf =
- reinterpret_cast<BT_HDR_RIGID*>(osi_malloc(sizeof(BT_HDR_RIGID)));
+ LOG_INFO(LOG_TAG, "%s", __func__);
+ BT_HDR* p_buf = reinterpret_cast<BT_HDR*>(osi_malloc(sizeof(BT_HDR)));
p_buf->event = BTIF_MEDIA_SINK_CLEAR_TRACK;
btif_a2dp_sink_cb.worker_thread.DoInThread(
@@ -744,7 +738,7 @@ static void btif_a2dp_sink_clear_track_event_req() {
}
static void btif_a2dp_sink_on_start_event() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
if ((btif_a2dp_sink_cb.decoder_interface != nullptr) &&
(btif_a2dp_sink_cb.decoder_interface->decoder_start != nullptr)) {
@@ -755,7 +749,7 @@ static void btif_a2dp_sink_on_start_event() {
}
static void btif_a2dp_sink_on_suspend_event() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
if ((btif_a2dp_sink_cb.decoder_interface != nullptr) &&
(btif_a2dp_sink_cb.decoder_interface->decoder_suspend != nullptr)) {
diff --git a/btif/src/btif_a2dp_source.cc b/btif/src/btif_a2dp_source.cc
index 19bf998ab..cd06a1219 100644
--- a/btif/src/btif_a2dp_source.cc
+++ b/btif/src/btif_a2dp_source.cc
@@ -39,7 +39,6 @@
#include "btif_a2dp_source.h"
#include "btif_av.h"
#include "btif_av_co.h"
-#include "btif_metrics_logging.h"
#include "btif_util.h"
#include "common/message_loop_thread.h"
#include "common/metrics.h"
@@ -49,8 +48,6 @@
#include "osi/include/log.h"
#include "osi/include/osi.h"
#include "osi/include/wakelock.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/acl_api_types.h"
#include "uipc.h"
using bluetooth::common::A2dpSessionMetrics;
@@ -230,9 +227,6 @@ static bluetooth::common::MessageLoopThread btif_a2dp_source_thread(
"bt_a2dp_source_worker_thread");
static BtifA2dpSource btif_a2dp_source_cb;
-static uint8_t btif_a2dp_source_dynamic_audio_buffer_size =
- MAX_OUTPUT_A2DP_FRAME_QUEUE_SZ;
-
static void btif_a2dp_source_init_delayed(void);
static void btif_a2dp_source_startup_delayed(void);
static void btif_a2dp_source_start_session_delayed(
@@ -269,6 +263,7 @@ static void update_scheduling_stats(SchedulingStats* stats, uint64_t now_us,
static void btif_a2dp_source_update_metrics(void);
static void btm_read_rssi_cb(void* data);
static void btm_read_failed_contact_counter_cb(void* data);
+static void btm_read_automatic_flush_timeout_cb(void* data);
static void btm_read_tx_power_cb(void* data);
void btif_a2dp_source_accumulate_scheduling_stats(SchedulingStats* src,
@@ -322,7 +317,7 @@ void btif_a2dp_source_accumulate_stats(BtifMediaStats* src,
}
bool btif_a2dp_source_init(void) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
// Start A2DP Source media task
btif_a2dp_source_thread.StartUp();
@@ -332,15 +327,16 @@ bool btif_a2dp_source_init(void) {
}
static void btif_a2dp_source_init_delayed(void) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
// Nothing to do
}
bool btif_a2dp_source_startup(void) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
if (btif_a2dp_source_cb.State() != BtifA2dpSource::kStateOff) {
- LOG_ERROR("%s: A2DP Source media task already running", __func__);
+ LOG_ERROR(LOG_TAG, "%s: A2DP Source media task already running", __func__);
return false;
}
@@ -356,7 +352,8 @@ bool btif_a2dp_source_startup(void) {
}
static void btif_a2dp_source_startup_delayed() {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
if (!btif_a2dp_source_thread.EnableRealTimeScheduling()) {
LOG(FATAL) << __func__ << ": unable to enable real time scheduling";
}
@@ -448,7 +445,7 @@ bool btif_a2dp_source_restart_session(const RawAddress& old_peer_address,
}
bool btif_a2dp_source_end_session(const RawAddress& peer_address) {
- LOG_INFO("%s: peer_address=%s state=%s", __func__,
+ LOG_INFO(LOG_TAG, "%s: peer_address=%s state=%s", __func__,
peer_address.ToString().c_str(),
btif_a2dp_source_cb.StateStr().c_str());
btif_a2dp_source_thread.DoInThread(
@@ -459,14 +456,14 @@ bool btif_a2dp_source_end_session(const RawAddress& peer_address) {
static void btif_a2dp_source_end_session_delayed(
const RawAddress& peer_address) {
- LOG_INFO("%s: peer_address=%s state=%s", __func__,
+ LOG_INFO(LOG_TAG, "%s: peer_address=%s state=%s", __func__,
peer_address.ToString().c_str(),
btif_a2dp_source_cb.StateStr().c_str());
if ((btif_a2dp_source_cb.State() == BtifA2dpSource::kStateRunning) ||
(btif_a2dp_source_cb.State() == BtifA2dpSource::kStateShuttingDown)) {
btif_av_stream_stop(peer_address);
} else {
- LOG_ERROR("%s: A2DP Source media task is not running", __func__);
+ LOG_ERROR(LOG_TAG, "%s: A2DP Source media task is not running", __func__);
}
if (bluetooth::audio::a2dp::is_hal_2_0_enabled()) {
bluetooth::audio::a2dp::end_session();
@@ -482,7 +479,8 @@ static void btif_a2dp_source_end_session_delayed(
}
void btif_a2dp_source_shutdown(void) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
if ((btif_a2dp_source_cb.State() == BtifA2dpSource::kStateOff) ||
(btif_a2dp_source_cb.State() == BtifA2dpSource::kStateShuttingDown)) {
@@ -497,7 +495,8 @@ void btif_a2dp_source_shutdown(void) {
}
static void btif_a2dp_source_shutdown_delayed(void) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
// Stop the timer
btif_a2dp_source_cb.media_alarm.CancelAndWait();
@@ -518,7 +517,8 @@ static void btif_a2dp_source_shutdown_delayed(void) {
}
void btif_a2dp_source_cleanup(void) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
// Make sure the source is shutdown
btif_a2dp_source_shutdown();
@@ -531,7 +531,8 @@ void btif_a2dp_source_cleanup(void) {
}
static void btif_a2dp_source_cleanup_delayed(void) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
// Nothing to do
}
@@ -548,7 +549,7 @@ bool btif_a2dp_source_is_streaming(void) {
}
static void btif_a2dp_source_setup_codec(const RawAddress& peer_address) {
- LOG_INFO("%s: peer_address=%s state=%s", __func__,
+ LOG_INFO(LOG_TAG, "%s: peer_address=%s state=%s", __func__,
peer_address.ToString().c_str(),
btif_a2dp_source_cb.StateStr().c_str());
@@ -564,7 +565,7 @@ static void btif_a2dp_source_setup_codec(const RawAddress& peer_address) {
static void btif_a2dp_source_setup_codec_delayed(
const RawAddress& peer_address) {
- LOG_INFO("%s: peer_address=%s state=%s", __func__,
+ LOG_INFO(LOG_TAG, "%s: peer_address=%s state=%s", __func__,
peer_address.ToString().c_str(),
btif_a2dp_source_cb.StateStr().c_str());
@@ -572,19 +573,21 @@ static void btif_a2dp_source_setup_codec_delayed(
bta_av_co_get_peer_params(peer_address, &peer_params);
if (!bta_av_co_set_active_peer(peer_address)) {
- LOG_ERROR("%s: Cannot stream audio: cannot set active peer to %s", __func__,
- peer_address.ToString().c_str());
+ LOG_ERROR(LOG_TAG, "%s: Cannot stream audio: cannot set active peer to %s",
+ __func__, peer_address.ToString().c_str());
return;
}
btif_a2dp_source_cb.encoder_interface = bta_av_co_get_encoder_interface();
if (btif_a2dp_source_cb.encoder_interface == nullptr) {
- LOG_ERROR("%s: Cannot stream audio: no source encoder interface", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Cannot stream audio: no source encoder interface",
+ __func__);
return;
}
A2dpCodecConfig* a2dp_codec_config = bta_av_get_a2dp_current_codec();
if (a2dp_codec_config == nullptr) {
- LOG_ERROR("%s: Cannot stream audio: current codec is not set", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Cannot stream audio: current codec is not set",
+ __func__);
return;
}
@@ -602,14 +605,16 @@ static void btif_a2dp_source_setup_codec_delayed(
}
void btif_a2dp_source_start_audio_req(void) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
btif_a2dp_source_thread.DoInThread(
FROM_HERE, base::Bind(&btif_a2dp_source_audio_tx_start_event));
}
void btif_a2dp_source_stop_audio_req(void) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
btif_a2dp_source_thread.DoInThread(
FROM_HERE, base::Bind(&btif_a2dp_source_audio_tx_stop_event));
@@ -673,7 +678,8 @@ static void btif_a2dp_source_encoder_user_config_update_event(
void btif_a2dp_source_feeding_update_req(
const btav_a2dp_codec_config_t& codec_audio_config) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
btif_a2dp_source_thread.DoInThread(
FROM_HERE, base::Bind(&btif_a2dp_source_audio_feeding_update_event,
codec_audio_config));
@@ -681,14 +687,17 @@ void btif_a2dp_source_feeding_update_req(
static void btif_a2dp_source_audio_feeding_update_event(
const btav_a2dp_codec_config_t& codec_audio_config) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
if (!bta_av_co_set_codec_audio_config(codec_audio_config)) {
- LOG_ERROR("%s: cannot update codec audio feeding parameters", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot update codec audio feeding parameters",
+ __func__);
}
}
void btif_a2dp_source_on_idle(void) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
if (btif_a2dp_source_cb.State() == BtifA2dpSource::kStateOff) return;
/* Make sure media task is stopped */
@@ -696,15 +705,16 @@ void btif_a2dp_source_on_idle(void) {
}
void btif_a2dp_source_on_stopped(tBTA_AV_SUSPEND* p_av_suspend) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
if (btif_a2dp_source_cb.State() == BtifA2dpSource::kStateOff) return;
// allow using this API for other (acknowledgement and stopping media task)
// than suspend
if (p_av_suspend != nullptr && p_av_suspend->status != BTA_AV_SUCCESS) {
- LOG_ERROR("%s: A2DP stop failed: status=%d, initiator=%s", __func__,
- p_av_suspend->status,
+ LOG_ERROR(LOG_TAG, "%s: A2DP stop failed: status=%d, initiator=%s",
+ __func__, p_av_suspend->status,
(p_av_suspend->initiator ? "true" : "false"));
if (p_av_suspend->initiator) {
if (bluetooth::audio::a2dp::is_hal_2_0_enabled()) {
@@ -730,7 +740,8 @@ void btif_a2dp_source_on_stopped(tBTA_AV_SUSPEND* p_av_suspend) {
}
void btif_a2dp_source_on_suspended(tBTA_AV_SUSPEND* p_av_suspend) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
if (btif_a2dp_source_cb.State() == BtifA2dpSource::kStateOff) return;
@@ -738,8 +749,8 @@ void btif_a2dp_source_on_suspended(tBTA_AV_SUSPEND* p_av_suspend) {
// check for status failures
if (p_av_suspend->status != BTA_AV_SUCCESS) {
- LOG_WARN("%s: A2DP suspend failed: status=%d, initiator=%s", __func__,
- p_av_suspend->status,
+ LOG_WARN(LOG_TAG, "%s: A2DP suspend failed: status=%d, initiator=%s",
+ __func__, p_av_suspend->status,
(p_av_suspend->initiator ? "true" : "false"));
if (p_av_suspend->initiator) {
if (bluetooth::audio::a2dp::is_hal_2_0_enabled()) {
@@ -764,14 +775,14 @@ void btif_a2dp_source_on_suspended(tBTA_AV_SUSPEND* p_av_suspend) {
/* when true media task discards any tx frames */
void btif_a2dp_source_set_tx_flush(bool enable) {
- LOG_INFO("%s: enable=%s state=%s", __func__, (enable) ? "true" : "false",
- btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: enable=%s state=%s", __func__,
+ (enable) ? "true" : "false", btif_a2dp_source_cb.StateStr().c_str());
btif_a2dp_source_cb.tx_flush = enable;
}
static void btif_a2dp_source_audio_tx_start_event(void) {
LOG_INFO(
- "%s: media_alarm is %s, streaming %s state=%s", __func__,
+ LOG_TAG, "%s: media_alarm is %s, streaming %s state=%s", __func__,
btif_a2dp_source_cb.media_alarm.IsScheduled() ? "running" : "stopped",
btif_a2dp_source_is_streaming() ? "true" : "false",
btif_a2dp_source_cb.StateStr().c_str());
@@ -814,7 +825,7 @@ static void btif_a2dp_source_audio_tx_start_event(void) {
static void btif_a2dp_source_audio_tx_stop_event(void) {
LOG_INFO(
- "%s: media_alarm is %s, streaming %s state=%s", __func__,
+ LOG_TAG, "%s: media_alarm is %s, streaming %s state=%s", __func__,
btif_a2dp_source_cb.media_alarm.IsScheduled() ? "running" : "stopped",
btif_a2dp_source_is_streaming() ? "true" : "false",
btif_a2dp_source_cb.StateStr().c_str());
@@ -879,7 +890,8 @@ static void btif_a2dp_source_audio_handle_timer(void) {
log_tstamps_us("A2DP Source tx timer", timestamp_us);
if (!btif_a2dp_source_cb.media_alarm.IsScheduled()) {
- LOG_ERROR("%s: ERROR Media task Scheduled after Suspend", __func__);
+ LOG_ERROR(LOG_TAG, "%s: ERROR Media task Scheduled after Suspend",
+ __func__);
return;
}
CHECK(btif_a2dp_source_cb.encoder_interface != nullptr);
@@ -911,16 +923,16 @@ static uint32_t btif_a2dp_source_read_callback(uint8_t* p_buf, uint32_t len) {
}
if (bytes_read < len) {
- LOG_WARN("%s: UNDERFLOW: ONLY READ %d BYTES OUT OF %d", __func__,
+ LOG_WARN(LOG_TAG, "%s: UNDERFLOW: ONLY READ %d BYTES OUT OF %d", __func__,
bytes_read, len);
btif_a2dp_source_cb.stats.media_read_total_underflow_bytes +=
(len - bytes_read);
btif_a2dp_source_cb.stats.media_read_total_underflow_count++;
btif_a2dp_source_cb.stats.media_read_last_underflow_us =
bluetooth::common::time_get_os_boottime_us();
- log_a2dp_audio_underrun_event(btif_av_source_active_peer(),
- btif_a2dp_source_cb.encoder_interval_ms,
- len - bytes_read);
+ bluetooth::common::LogA2dpAudioUnderrunEvent(
+ btif_av_source_active_peer(), btif_a2dp_source_cb.encoder_interval_ms,
+ len - bytes_read);
}
return bytes_read;
@@ -939,7 +951,7 @@ static bool btif_a2dp_source_enqueue_callback(BT_HDR* p_buf, size_t frames_n,
/* Check if the transmission queue has been flushed */
if (btif_a2dp_source_cb.tx_flush) {
- LOG_VERBOSE("%s: tx suspended, discarded frame", __func__);
+ LOG_VERBOSE(LOG_TAG, "%s: tx suspended, discarded frame", __func__);
btif_a2dp_source_cb.stats.tx_queue_total_flushed_messages +=
fixed_queue_length(btif_a2dp_source_cb.tx_audio_queue);
@@ -953,10 +965,11 @@ static bool btif_a2dp_source_enqueue_callback(BT_HDR* p_buf, size_t frames_n,
// Check for TX queue overflow
// TODO: Using frames_n here is probably wrong: should be "+ 1" instead.
if (fixed_queue_length(btif_a2dp_source_cb.tx_audio_queue) + frames_n >
- btif_a2dp_source_dynamic_audio_buffer_size) {
- LOG_WARN("%s: TX queue buffer size now=%u adding=%u max=%d", __func__,
+ MAX_OUTPUT_A2DP_FRAME_QUEUE_SZ) {
+ LOG_WARN(LOG_TAG, "%s: TX queue buffer size now=%u adding=%u max=%d",
+ __func__,
(uint32_t)fixed_queue_length(btif_a2dp_source_cb.tx_audio_queue),
- (uint32_t)frames_n, btif_a2dp_source_dynamic_audio_buffer_size);
+ (uint32_t)frames_n, MAX_OUTPUT_A2DP_FRAME_QUEUE_SZ);
// Keep track of drop-outs
btif_a2dp_source_cb.stats.tx_queue_dropouts++;
btif_a2dp_source_cb.stats.tx_queue_last_dropouts_us = now_us;
@@ -978,27 +991,34 @@ static bool btif_a2dp_source_enqueue_callback(BT_HDR* p_buf, size_t frames_n,
osi_free(p_data);
}
}
- log_a2dp_audio_overrun_event(btif_av_source_active_peer(), drop_n,
- btif_a2dp_source_cb.encoder_interval_ms,
- num_dropped_encoded_frames,
- num_dropped_encoded_bytes);
+ bluetooth::common::LogA2dpAudioOverrunEvent(
+ btif_av_source_active_peer(), drop_n,
+ btif_a2dp_source_cb.encoder_interval_ms, num_dropped_encoded_frames,
+ num_dropped_encoded_bytes);
// Request additional debug info if we had to flush buffers
RawAddress peer_bda = btif_av_source_active_peer();
tBTM_STATUS status = BTM_ReadRSSI(peer_bda, btm_read_rssi_cb);
if (status != BTM_CMD_STARTED) {
- LOG_WARN("%s: Cannot read RSSI: status %d", __func__, status);
+ LOG_WARN(LOG_TAG, "%s: Cannot read RSSI: status %d", __func__, status);
}
status = BTM_ReadFailedContactCounter(peer_bda,
btm_read_failed_contact_counter_cb);
if (status != BTM_CMD_STARTED) {
- LOG_WARN("%s: Cannot read Failed Contact Counter: status %d", __func__,
- status);
+ LOG_WARN(LOG_TAG, "%s: Cannot read Failed Contact Counter: status %d",
+ __func__, status);
+ }
+ status = BTM_ReadAutomaticFlushTimeout(peer_bda,
+ btm_read_automatic_flush_timeout_cb);
+ if (status != BTM_CMD_STARTED) {
+ LOG_WARN(LOG_TAG, "%s: Cannot read Automatic Flush Timeout: status %d",
+ __func__, status);
}
status =
BTM_ReadTxPower(peer_bda, BT_TRANSPORT_BR_EDR, btm_read_tx_power_cb);
if (status != BTM_CMD_STARTED) {
- LOG_WARN("%s: Cannot read Tx Power: status %d", __func__, status);
+ LOG_WARN(LOG_TAG, "%s: Cannot read Tx Power: status %d", __func__,
+ status);
}
}
@@ -1015,7 +1035,8 @@ static bool btif_a2dp_source_enqueue_callback(BT_HDR* p_buf, size_t frames_n,
static void btif_a2dp_source_audio_tx_flush_event(void) {
/* Flush all enqueued audio buffers (encoded) */
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
if (btif_av_is_a2dp_offload_running()) return;
if (btif_a2dp_source_cb.encoder_interface != nullptr)
@@ -1033,7 +1054,8 @@ static void btif_a2dp_source_audio_tx_flush_event(void) {
}
static bool btif_a2dp_source_audio_tx_flush_req(void) {
- LOG_INFO("%s: state=%s", __func__, btif_a2dp_source_cb.StateStr().c_str());
+ LOG_INFO(LOG_TAG, "%s: state=%s", __func__,
+ btif_a2dp_source_cb.StateStr().c_str());
btif_a2dp_source_thread.DoInThread(
FROM_HERE, base::Bind(&btif_a2dp_source_audio_tx_flush_event));
@@ -1317,69 +1339,83 @@ static void btif_a2dp_source_update_metrics(void) {
BluetoothMetricsLogger::GetInstance()->LogA2dpSession(metrics);
}
-void btif_a2dp_source_set_dynamic_audio_buffer_size(
- uint8_t dynamic_audio_buffer_size) {
- btif_a2dp_source_dynamic_audio_buffer_size = dynamic_audio_buffer_size;
-}
-
static void btm_read_rssi_cb(void* data) {
if (data == nullptr) {
- LOG_ERROR("%s: Read RSSI request timed out", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Read RSSI request timed out", __func__);
return;
}
tBTM_RSSI_RESULT* result = (tBTM_RSSI_RESULT*)data;
if (result->status != BTM_SUCCESS) {
- LOG_ERROR("%s: unable to read remote RSSI (status %d)", __func__,
+ LOG_ERROR(LOG_TAG, "%s: unable to read remote RSSI (status %d)", __func__,
result->status);
return;
}
+ bluetooth::common::LogReadRssiResult(
+ result->rem_bda, bluetooth::common::kUnknownConnectionHandle,
+ result->hci_status, result->rssi);
- log_read_rssi_result(result->rem_bda,
- bluetooth::common::kUnknownConnectionHandle,
- result->hci_status, result->rssi);
-
- LOG_WARN("%s: device: %s, rssi: %d", __func__,
+ LOG_WARN(LOG_TAG, "%s: device: %s, rssi: %d", __func__,
result->rem_bda.ToString().c_str(), result->rssi);
}
static void btm_read_failed_contact_counter_cb(void* data) {
if (data == nullptr) {
- LOG_ERROR("%s: Read Failed Contact Counter request timed out", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Read Failed Contact Counter request timed out",
+ __func__);
return;
}
tBTM_FAILED_CONTACT_COUNTER_RESULT* result =
(tBTM_FAILED_CONTACT_COUNTER_RESULT*)data;
if (result->status != BTM_SUCCESS) {
- LOG_ERROR("%s: unable to read Failed Contact Counter (status %d)", __func__,
- result->status);
+ LOG_ERROR(LOG_TAG, "%s: unable to read Failed Contact Counter (status %d)",
+ __func__, result->status);
return;
}
- log_read_failed_contact_counter_result(
+ bluetooth::common::LogReadFailedContactCounterResult(
result->rem_bda, bluetooth::common::kUnknownConnectionHandle,
result->hci_status, result->failed_contact_counter);
- LOG_WARN("%s: device: %s, Failed Contact Counter: %u", __func__,
+ LOG_WARN(LOG_TAG, "%s: device: %s, Failed Contact Counter: %u", __func__,
result->rem_bda.ToString().c_str(), result->failed_contact_counter);
}
+static void btm_read_automatic_flush_timeout_cb(void* data) {
+ if (data == nullptr) {
+ LOG_ERROR(LOG_TAG, "%s: Read Automatic Flush Timeout request timed out",
+ __func__);
+ return;
+ }
+
+ tBTM_AUTOMATIC_FLUSH_TIMEOUT_RESULT* result =
+ (tBTM_AUTOMATIC_FLUSH_TIMEOUT_RESULT*)data;
+ if (result->status != BTM_SUCCESS) {
+ LOG_ERROR(LOG_TAG, "%s: unable to read Automatic Flush Timeout (status %d)",
+ __func__, result->status);
+ return;
+ }
+
+ LOG_WARN(LOG_TAG, "%s: device: %s, Automatic Flush Timeout: %u", __func__,
+ result->rem_bda.ToString().c_str(), result->automatic_flush_timeout);
+}
+
static void btm_read_tx_power_cb(void* data) {
if (data == nullptr) {
- LOG_ERROR("%s: Read Tx Power request timed out", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Read Tx Power request timed out", __func__);
return;
}
tBTM_TX_POWER_RESULT* result = (tBTM_TX_POWER_RESULT*)data;
if (result->status != BTM_SUCCESS) {
- LOG_ERROR("%s: unable to read Tx Power (status %d)", __func__,
+ LOG_ERROR(LOG_TAG, "%s: unable to read Tx Power (status %d)", __func__,
result->status);
return;
}
- log_read_tx_power_level_result(result->rem_bda,
- bluetooth::common::kUnknownConnectionHandle,
- result->hci_status, result->tx_power);
+ bluetooth::common::LogReadTxPowerLevelResult(
+ result->rem_bda, bluetooth::common::kUnknownConnectionHandle,
+ result->hci_status, result->tx_power);
- LOG_WARN("%s: device: %s, Tx Power: %d", __func__,
+ LOG_WARN(LOG_TAG, "%s: device: %s, Tx Power: %d", __func__,
result->rem_bda.ToString().c_str(), result->tx_power);
}
diff --git a/btif/src/btif_av.cc b/btif/src/btif_av.cc
index 50717d9eb..679ec5ef5 100644
--- a/btif/src/btif_av.cc
+++ b/btif/src/btif_av.cc
@@ -18,37 +18,38 @@
#define LOG_TAG "btif_av"
+#include "btif_av.h"
+
#include <base/bind.h>
+#include <base/logging.h>
#include <base/strings/stringprintf.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/a2dp/enums.pb.h>
-#include <cstdint>
-#include <future>
-#include <memory>
-#include <string>
-#include <vector>
+#include <string.h>
+#include <map>
+#include <mutex>
+
+#include <hardware/bluetooth.h>
+#include <hardware/bt_av.h>
+#include <hardware/bt_rc.h>
+#include "audio_a2dp_hw/include/audio_a2dp_hw.h"
#include "audio_hal_interface/a2dp_encoding.h"
-#include "bta/av/bta_av_int.h"
-#include "btif/include/btif_a2dp.h"
-#include "btif/include/btif_a2dp_control.h"
-#include "btif/include/btif_a2dp_sink.h"
+#include "bt_common.h"
+#include "bt_utils.h"
+#include "bta/include/bta_api.h"
#include "btif/include/btif_a2dp_source.h"
-#include "btif/include/btif_av.h"
-#include "btif/include/btif_av_co.h"
-#include "btif/include/btif_common.h"
-#include "btif/include/btif_profile_queue.h"
-#include "btif/include/btif_rc.h"
-#include "btif/include/btif_util.h"
-#include "btif_metrics_logging.h"
-#include "common/metrics.h"
+#include "btif_a2dp.h"
+#include "btif_a2dp_audio_interface.h"
+#include "btif_a2dp_control.h"
+#include "btif_a2dp_sink.h"
+#include "btif_av_co.h"
+#include "btif_profile_queue.h"
+#include "btif_rc.h"
+#include "btif_util.h"
+#include "btu.h"
#include "common/state_machine.h"
-#include "hardware/bt_av.h"
-#include "include/hardware/bt_rc.h"
-#include "main/shim/dumpsys.h"
+#include "osi/include/allocator.h"
+#include "osi/include/osi.h"
#include "osi/include/properties.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "types/raw_address.h"
/*****************************************************************************
* Constants & Macros
@@ -58,10 +59,6 @@ static const std::string kBtifAvSinkServiceName = "Advanced Audio Sink";
static constexpr int kDefaultMaxConnectedAudioDevices = 1;
static constexpr tBTA_AV_HNDL kBtaHandleUnknown = 0;
-namespace {
-constexpr char kBtmLogHistoryTag[] = "A2DP";
-}
-
/*****************************************************************************
* Local type definitions
*****************************************************************************/
@@ -439,7 +436,7 @@ class BtifAvSource {
if (peer_address.IsEmpty()) {
return false;
}
- LOG_INFO("%s: peer: %s", __PRETTY_FUNCTION__,
+ LOG_INFO(LOG_TAG, "%s: peer: %s", __PRETTY_FUNCTION__,
peer_address.ToString().c_str());
BtifAvPeer* peer = FindPeer(peer_address);
if (peer == nullptr) {
@@ -536,6 +533,7 @@ class BtifAvSource {
std::set<RawAddress> silenced_peers_;
RawAddress active_peer_;
std::map<uint8_t, tBTA_AV_HNDL> peer_id2bta_handle_;
+ std::mutex mutex_;
};
class BtifAvSink {
@@ -550,8 +548,7 @@ class BtifAvSink {
max_connected_peers_(kDefaultMaxConnectedAudioDevices) {}
~BtifAvSink();
- bt_status_t Init(btav_sink_callbacks_t* callbacks,
- int max_connected_audio_devices);
+ bt_status_t Init(btav_sink_callbacks_t* callbacks);
void Cleanup();
btav_sink_callbacks_t* Callbacks() { return callbacks_; }
@@ -654,6 +651,7 @@ class BtifAvSink {
std::map<RawAddress, BtifAvPeer*> peers_;
RawAddress active_peer_;
std::map<uint8_t, tBTA_AV_HNDL> peer_id2bta_handle_;
+ std::mutex mutex_;
};
/*****************************************************************************
@@ -961,7 +959,7 @@ bt_status_t BtifAvSource::Init(
btav_source_callbacks_t* callbacks, int max_connected_audio_devices,
const std::vector<btav_a2dp_codec_config_t>& codec_priorities,
const std::vector<btav_a2dp_codec_config_t>& offloading_preference) {
- LOG_INFO("%s: max_connected_audio_devices=%d", __PRETTY_FUNCTION__,
+ LOG_INFO(LOG_TAG, "%s: max_connected_audio_devices=%d", __PRETTY_FUNCTION__,
max_connected_audio_devices);
if (enabled_) return BT_STATUS_SUCCESS;
CleanupAllPeers();
@@ -993,7 +991,7 @@ bt_status_t BtifAvSource::Init(
}
void BtifAvSource::Cleanup() {
- LOG_INFO("%s", __PRETTY_FUNCTION__);
+ LOG_INFO(LOG_TAG, "%s", __PRETTY_FUNCTION__);
if (!enabled_) return;
btif_queue_cleanup(UUID_SERVCLASS_AUDIO_SOURCE);
@@ -1041,6 +1039,7 @@ BtifAvPeer* BtifAvSource::FindPeerByPeerId(uint8_t peer_id) {
BtifAvPeer* BtifAvSource::FindOrCreatePeer(const RawAddress& peer_address,
tBTA_AV_HNDL bta_handle) {
+ std::unique_lock<std::mutex> lock(mutex_);
BTIF_TRACE_DEBUG("%s: peer_address=%s bta_handle=0x%x", __PRETTY_FUNCTION__,
peer_address.ToString().c_str(), bta_handle);
@@ -1073,7 +1072,8 @@ BtifAvPeer* BtifAvSource::FindOrCreatePeer(const RawAddress& peer_address,
bta_handle = it->second;
}
- LOG_INFO("%s: Create peer: peer_address=%s bta_handle=0x%x peer_id=%d",
+ LOG_INFO(LOG_TAG,
+ "%s: Create peer: peer_address=%s bta_handle=0x%x peer_id=%d",
__PRETTY_FUNCTION__, peer_address.ToString().c_str(), bta_handle,
peer_id);
peer = new BtifAvPeer(peer_address, AVDT_TSEP_SNK, bta_handle, peer_id);
@@ -1119,7 +1119,7 @@ void BtifAvSource::DeleteIdlePeers() {
BtifAvPeer* peer = it->second;
auto prev_it = it++;
if (!peer->CanBeDeleted()) continue;
- LOG_INFO("%s: Deleting idle peer: %s bta_handle=0x%x", __func__,
+ LOG_INFO(LOG_TAG, "%s: Deleting idle peer: %s bta_handle=0x%x", __func__,
peer->PeerAddress().ToString().c_str(), peer->BtaHandle());
peer->Cleanup();
peers_.erase(prev_it);
@@ -1145,6 +1145,7 @@ void BtifAvSource::RegisterAllBtaHandles() {
}
void BtifAvSource::DeregisterAllBtaHandles() {
+ std::unique_lock<std::mutex> lock(mutex_);
for (auto it : peer_id2bta_handle_) {
tBTA_AV_HNDL bta_handle = it.second;
BTA_AvDeregister(bta_handle);
@@ -1154,6 +1155,7 @@ void BtifAvSource::DeregisterAllBtaHandles() {
void BtifAvSource::BtaHandleRegistered(uint8_t peer_id,
tBTA_AV_HNDL bta_handle) {
+ std::unique_lock<std::mutex> lock(mutex_);
peer_id2bta_handle_.insert(std::make_pair(peer_id, bta_handle));
// Set the BTA Handle for the Peer (if exists)
@@ -1176,14 +1178,12 @@ void BtifAvSource::BtaHandleRegistered(uint8_t peer_id,
BtifAvSink::~BtifAvSink() { CleanupAllPeers(); }
-bt_status_t BtifAvSink::Init(btav_sink_callbacks_t* callbacks,
- int max_connected_audio_devices) {
- LOG_INFO("%s(max_connected_audio_devices=%d)", __PRETTY_FUNCTION__,
- max_connected_audio_devices);
+bt_status_t BtifAvSink::Init(btav_sink_callbacks_t* callbacks) {
+ LOG_INFO(LOG_TAG, "%s", __PRETTY_FUNCTION__);
if (enabled_) return BT_STATUS_SUCCESS;
CleanupAllPeers();
- max_connected_peers_ = max_connected_audio_devices;
+ max_connected_peers_ = kDefaultMaxConnectedAudioDevices;
callbacks_ = callbacks;
std::vector<btav_a2dp_codec_config_t> codec_priorities; // Default priorities
@@ -1198,7 +1198,7 @@ bt_status_t BtifAvSink::Init(btav_sink_callbacks_t* callbacks,
}
void BtifAvSink::Cleanup() {
- LOG_INFO("%s", __PRETTY_FUNCTION__);
+ LOG_INFO(LOG_TAG, "%s", __PRETTY_FUNCTION__);
if (!enabled_) return;
btif_queue_cleanup(UUID_SERVCLASS_AUDIO_SINK);
@@ -1246,6 +1246,7 @@ BtifAvPeer* BtifAvSink::FindPeerByPeerId(uint8_t peer_id) {
BtifAvPeer* BtifAvSink::FindOrCreatePeer(const RawAddress& peer_address,
tBTA_AV_HNDL bta_handle) {
+ std::unique_lock<std::mutex> lock(mutex_);
BTIF_TRACE_DEBUG("%s: peer_address=%s bta_handle=0x%x", __PRETTY_FUNCTION__,
peer_address.ToString().c_str(), bta_handle);
@@ -1278,7 +1279,8 @@ BtifAvPeer* BtifAvSink::FindOrCreatePeer(const RawAddress& peer_address,
bta_handle = it->second;
}
- LOG_INFO("%s: Create peer: peer_address=%s bta_handle=0x%x peer_id=%d",
+ LOG_INFO(LOG_TAG,
+ "%s: Create peer: peer_address=%s bta_handle=0x%x peer_id=%d",
__PRETTY_FUNCTION__, peer_address.ToString().c_str(), bta_handle,
peer_id);
peer = new BtifAvPeer(peer_address, AVDT_TSEP_SRC, bta_handle, peer_id);
@@ -1327,7 +1329,7 @@ void BtifAvSink::DeleteIdlePeers() {
BtifAvPeer* peer = it->second;
auto prev_it = it++;
if (!peer->CanBeDeleted()) continue;
- LOG_INFO("%s: Deleting idle peer: %s bta_handle=0x%x", __func__,
+ LOG_INFO(LOG_TAG, "%s: Deleting idle peer: %s bta_handle=0x%x", __func__,
peer->PeerAddress().ToString().c_str(), peer->BtaHandle());
peer->Cleanup();
peers_.erase(prev_it);
@@ -1353,6 +1355,7 @@ void BtifAvSink::RegisterAllBtaHandles() {
}
void BtifAvSink::DeregisterAllBtaHandles() {
+ std::unique_lock<std::mutex> lock(mutex_);
for (auto it : peer_id2bta_handle_) {
tBTA_AV_HNDL bta_handle = it.second;
BTA_AvDeregister(bta_handle);
@@ -1361,6 +1364,7 @@ void BtifAvSink::DeregisterAllBtaHandles() {
}
void BtifAvSink::BtaHandleRegistered(uint8_t peer_id, tBTA_AV_HNDL bta_handle) {
+ std::unique_lock<std::mutex> lock(mutex_);
peer_id2bta_handle_.insert(std::make_pair(peer_id, bta_handle));
// Set the BTA Handle for the Peer (if exists)
@@ -1474,7 +1478,7 @@ bool BtifAvStateMachine::StateIdle::ProcessEvent(uint32_t event, void* p_data) {
}
btif_av_query_mandatory_codec_priority(peer_.PeerAddress());
BTA_AvOpen(peer_.PeerAddress(), peer_.BtaHandle(), true,
- peer_.LocalUuidServiceClass());
+ BTA_SEC_AUTHENTICATE, peer_.LocalUuidServiceClass());
peer_.StateMachine().TransitionTo(BtifAvStateMachine::kStateOpening);
} break;
case BTIF_AV_AVRCP_OPEN_EVT:
@@ -1545,12 +1549,12 @@ bool BtifAvStateMachine::StateIdle::ProcessEvent(uint32_t event, void* p_data) {
tBTA_AV_STATUS status = p_bta_data->open.status;
bool can_connect = true;
- LOG_INFO("%s: Peer %s : event=%s flags=%s status=%d(%s) edr=0x%x",
- __PRETTY_FUNCTION__, peer_.PeerAddress().ToString().c_str(),
- BtifAvEvent::EventName(event).c_str(),
- peer_.FlagsToString().c_str(), status,
- (status == BTA_AV_SUCCESS) ? "SUCCESS" : "FAILED",
- p_bta_data->open.edr);
+ LOG_INFO(
+ LOG_TAG, "%s: Peer %s : event=%s flags=%s status=%d(%s) edr=0x%x",
+ __PRETTY_FUNCTION__, peer_.PeerAddress().ToString().c_str(),
+ BtifAvEvent::EventName(event).c_str(), peer_.FlagsToString().c_str(),
+ status, (status == BTA_AV_SUCCESS) ? "SUCCESS" : "FAILED",
+ p_bta_data->open.edr);
if (p_bta_data->open.status == BTA_AV_SUCCESS) {
state = BTAV_CONNECTION_STATE_CONNECTED;
@@ -1696,12 +1700,12 @@ bool BtifAvStateMachine::StateOpening::ProcessEvent(uint32_t event,
int av_state;
tBTA_AV_STATUS status = p_bta_data->open.status;
- LOG_INFO("%s: Peer %s : event=%s flags=%s status=%d(%s) edr=0x%x",
- __PRETTY_FUNCTION__, peer_.PeerAddress().ToString().c_str(),
- BtifAvEvent::EventName(event).c_str(),
- peer_.FlagsToString().c_str(), status,
- (status == BTA_AV_SUCCESS) ? "SUCCESS" : "FAILED",
- p_bta_data->open.edr);
+ LOG_INFO(
+ LOG_TAG, "%s: Peer %s : event=%s flags=%s status=%d(%s) edr=0x%x",
+ __PRETTY_FUNCTION__, peer_.PeerAddress().ToString().c_str(),
+ BtifAvEvent::EventName(event).c_str(), peer_.FlagsToString().c_str(),
+ status, (status == BTA_AV_SUCCESS) ? "SUCCESS" : "FAILED",
+ p_bta_data->open.edr);
if (p_bta_data->open.status == BTA_AV_SUCCESS) {
state = BTAV_CONNECTION_STATE_CONNECTED;
@@ -1871,7 +1875,7 @@ bool BtifAvStateMachine::StateOpened::ProcessEvent(uint32_t event,
break; // Ignore
case BTIF_AV_START_STREAM_REQ_EVT:
- LOG_INFO("%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
+ LOG_INFO(LOG_TAG, "%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
peer_.PeerAddress().ToString().c_str(),
BtifAvEvent::EventName(event).c_str(),
peer_.FlagsToString().c_str());
@@ -1880,13 +1884,13 @@ bool BtifAvStateMachine::StateOpened::ProcessEvent(uint32_t event,
break;
case BTA_AV_START_EVT: {
- LOG_INFO(
- "%s: Peer %s : event=%s status=%d suspending=%d "
- "initiator=%d flags=%s",
- __PRETTY_FUNCTION__, peer_.PeerAddress().ToString().c_str(),
- BtifAvEvent::EventName(event).c_str(), p_av->start.status,
- p_av->start.suspending, p_av->start.initiator,
- peer_.FlagsToString().c_str());
+ LOG_INFO(LOG_TAG,
+ "%s: Peer %s : event=%s status=%d suspending=%d "
+ "initiator=%d flags=%s",
+ __PRETTY_FUNCTION__, peer_.PeerAddress().ToString().c_str(),
+ BtifAvEvent::EventName(event).c_str(), p_av->start.status,
+ p_av->start.suspending, p_av->start.initiator,
+ peer_.FlagsToString().c_str());
if ((p_av->start.status == BTA_SUCCESS) && p_av->start.suspending)
return true;
@@ -2076,7 +2080,7 @@ bool BtifAvStateMachine::StateStarted::ProcessEvent(uint32_t event,
break; // Ignore
case BTIF_AV_START_STREAM_REQ_EVT:
- LOG_INFO("%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
+ LOG_INFO(LOG_TAG, "%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
peer_.PeerAddress().ToString().c_str(),
BtifAvEvent::EventName(event).c_str(),
peer_.FlagsToString().c_str());
@@ -2087,7 +2091,7 @@ bool BtifAvStateMachine::StateStarted::ProcessEvent(uint32_t event,
// FIXME -- use suspend = true always to work around issue with BTA AV
case BTIF_AV_STOP_STREAM_REQ_EVT:
case BTIF_AV_SUSPEND_STREAM_REQ_EVT:
- LOG_INFO("%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
+ LOG_INFO(LOG_TAG, "%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
peer_.PeerAddress().ToString().c_str(),
BtifAvEvent::EventName(event).c_str(),
peer_.FlagsToString().c_str());
@@ -2115,7 +2119,7 @@ bool BtifAvStateMachine::StateStarted::ProcessEvent(uint32_t event,
break;
case BTIF_AV_DISCONNECT_REQ_EVT:
- LOG_INFO("%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
+ LOG_INFO(LOG_TAG, "%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
peer_.PeerAddress().ToString().c_str(),
BtifAvEvent::EventName(event).c_str(),
peer_.FlagsToString().c_str());
@@ -2135,7 +2139,8 @@ bool BtifAvStateMachine::StateStarted::ProcessEvent(uint32_t event,
break;
case BTA_AV_SUSPEND_EVT: {
- LOG_INFO("%s: Peer %s : event=%s status=%d initiator=%d flags=%s",
+ LOG_INFO(LOG_TAG,
+ "%s: Peer %s : event=%s status=%d initiator=%d flags=%s",
__PRETTY_FUNCTION__, peer_.PeerAddress().ToString().c_str(),
BtifAvEvent::EventName(event).c_str(), p_av->suspend.status,
p_av->suspend.initiator, peer_.FlagsToString().c_str());
@@ -2175,7 +2180,7 @@ bool BtifAvStateMachine::StateStarted::ProcessEvent(uint32_t event,
} break;
case BTA_AV_STOP_EVT:
- LOG_INFO("%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
+ LOG_INFO(LOG_TAG, "%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
peer_.PeerAddress().ToString().c_str(),
BtifAvEvent::EventName(event).c_str(),
peer_.FlagsToString().c_str());
@@ -2198,7 +2203,7 @@ bool BtifAvStateMachine::StateStarted::ProcessEvent(uint32_t event,
break;
case BTA_AV_CLOSE_EVT:
- LOG_INFO("%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
+ LOG_INFO(LOG_TAG, "%s: Peer %s : event=%s flags=%s", __PRETTY_FUNCTION__,
peer_.PeerAddress().ToString().c_str(),
BtifAvEvent::EventName(event).c_str(),
peer_.FlagsToString().c_str());
@@ -2377,7 +2382,7 @@ static void btif_av_sink_initiate_av_open_timer_timeout(void* data) {
*/
static void btif_report_connection_state(const RawAddress& peer_address,
btav_connection_state_t state) {
- LOG_INFO("%s: peer_address=%s state=%d", __func__,
+ LOG_INFO(LOG_TAG, "%s: peer_address=%s state=%d", __func__,
peer_address.ToString().c_str(), state);
if (btif_av_source.Enabled()) {
@@ -2402,7 +2407,7 @@ static void btif_report_connection_state(const RawAddress& peer_address,
*/
static void btif_report_audio_state(const RawAddress& peer_address,
btav_audio_state_t state) {
- LOG_INFO("%s: peer_address=%s state=%d", __func__,
+ LOG_INFO(LOG_TAG, "%s: peer_address=%s state=%d", __func__,
peer_address.ToString().c_str(), state);
if (btif_av_source.Enabled()) {
@@ -2414,26 +2419,6 @@ static void btif_report_audio_state(const RawAddress& peer_address,
base::Bind(btif_av_sink.Callbacks()->audio_state_cb,
peer_address, state));
}
-
- using android::bluetooth::a2dp::AudioCodingModeEnum;
- using android::bluetooth::a2dp::PlaybackStateEnum;
- PlaybackStateEnum playback_state = PlaybackStateEnum::PLAYBACK_STATE_UNKNOWN;
- switch (state) {
- case BTAV_AUDIO_STATE_STARTED:
- playback_state = PlaybackStateEnum::PLAYBACK_STATE_PLAYING;
- break;
- case BTAV_AUDIO_STATE_STOPPED:
- playback_state = PlaybackStateEnum::PLAYBACK_STATE_NOT_PLAYING;
- break;
- default:
- break;
- }
- AudioCodingModeEnum audio_coding_mode =
- btif_av_is_a2dp_offload_running()
- ? AudioCodingModeEnum::AUDIO_CODING_MODE_HARDWARE
- : AudioCodingModeEnum::AUDIO_CODING_MODE_SOFTWARE;
-
- log_a2dp_playback_event(peer_address, playback_state, audio_coding_mode);
}
void btif_av_report_source_codec_state(
@@ -2462,7 +2447,7 @@ void btif_av_report_source_codec_state(
*/
static void btif_av_report_sink_audio_config_state(
const RawAddress& peer_address, int sample_rate, int channel_count) {
- LOG_INFO("%s: Peer %s : sample_rate=%d channel_count=%d", __func__,
+ LOG_INFO(LOG_TAG, "%s: Peer %s : sample_rate=%d channel_count=%d", __func__,
peer_address.ToString().c_str(), sample_rate, channel_count);
if (btif_av_sink.Enabled()) {
do_in_jni_thread(FROM_HERE,
@@ -2480,23 +2465,18 @@ static void btif_av_report_sink_audio_config_state(
static void btif_av_query_mandatory_codec_priority(
const RawAddress& peer_address) {
auto query_priority = [](const RawAddress& peer_address) {
- if (!btif_av_source.Enabled()) {
- LOG_WARN("BTIF AV Source is not enabled");
- return;
- }
- btav_source_callbacks_t* callbacks = btif_av_source.Callbacks();
- bool preferred = callbacks != nullptr &&
- callbacks->mandatory_codec_preferred_cb(peer_address);
+ auto apply_priority = [](const RawAddress& peer_address, bool preferred) {
+ BtifAvPeer* peer = btif_av_source_find_peer(peer_address);
+ if (peer == nullptr) {
+ BTIF_TRACE_WARNING(
+ "btif_av_query_mandatory_codec_priority: peer is null");
+ return;
+ }
+ peer->SetMandatoryCodecPreferred(preferred);
+ };
+ bool preferred =
+ btif_av_source.Callbacks()->mandatory_codec_preferred_cb(peer_address);
if (preferred) {
- auto apply_priority = [](const RawAddress& peer_address, bool preferred) {
- BtifAvPeer* peer = btif_av_find_peer(peer_address);
- if (peer == nullptr) {
- BTIF_TRACE_WARNING(
- "btif_av_query_mandatory_codec_priority: peer is null");
- return;
- }
- peer->SetMandatoryCodecPreferred(preferred);
- };
do_in_main_thread(
FROM_HERE, base::BindOnce(apply_priority, peer_address, preferred));
}
@@ -2521,10 +2501,12 @@ static void btif_av_handle_event(uint8_t peer_sep,
const RawAddress& peer_address,
tBTA_AV_HNDL bta_handle,
const BtifAvEvent& btif_av_event) {
- LOG_DEBUG("Handle event peer_address=%s bta_handle=0x%x",
- PRIVATE_ADDRESS(peer_address), bta_handle);
-
BtifAvPeer* peer = nullptr;
+ BTIF_TRACE_EVENT(
+ "%s: peer_sep=%s (%d) peer_address=%s bta_handle=0x%x event=%s", __func__,
+ (peer_sep == AVDT_TSEP_SRC) ? "Source" : "Sink", peer_sep,
+ peer_address.ToString().c_str(), bta_handle,
+ btif_av_event.ToString().c_str());
// Find the peer
if (peer_address != RawAddress::kEmpty) {
@@ -2541,10 +2523,10 @@ static void btif_av_handle_event(uint8_t peer_sep,
}
}
if (peer == nullptr) {
- LOG_ERROR(
- "jni_thread: Cannot find or create %s peer for peer_address=%s "
- " bta_handle=0x%x : event dropped: %s",
- peer_stream_endpoint_text(peer_sep).c_str(),
+ BTIF_TRACE_ERROR(
+ "%s: Cannot find or create %s peer for peer_address=%s bta_handle=0x%x "
+ ": event dropped: %s",
+ __func__, (peer_sep == AVDT_TSEP_SRC) ? "Source" : "Sink",
peer_address.ToString().c_str(), bta_handle,
btif_av_event.ToString().c_str());
return;
@@ -2568,25 +2550,23 @@ static void btif_av_handle_bta_av_event(uint8_t peer_sep,
tBTA_AV_HNDL bta_handle = kBtaHandleUnknown;
tBTA_AV_EVT event = btif_av_event.Event();
tBTA_AV* p_data = (tBTA_AV*)btif_av_event.Data();
- std::string msg;
- LOG_DEBUG(
- "jni_thread: Handle BTA AV or AVRCP event %s: peer_sep=%hhu event=%s",
- peer_stream_endpoint_text(peer_sep).c_str(), peer_sep,
- btif_av_event.ToString().c_str());
+ BTIF_TRACE_DEBUG("%s: peer_sep=%s (%d) event=%s", __func__,
+ (peer_sep == AVDT_TSEP_SRC) ? "Source" : "Sink", peer_sep,
+ btif_av_event.ToString().c_str());
switch (event) {
case BTA_AV_ENABLE_EVT: {
const tBTA_AV_ENABLE& enable = p_data->enable;
- LOG_DEBUG("Enable features=0x%x", enable.features);
+ BTIF_TRACE_DEBUG("%s: features=0x%x", __func__, enable.features);
return; // Nothing to do
}
case BTA_AV_REGISTER_EVT: {
const tBTA_AV_REGISTER& registr = p_data->registr;
bta_handle = registr.hndl;
uint8_t peer_id = registr.app_id; // The PeerId is used as AppId
- LOG_DEBUG("Register bta_handle=0x%x app_id=%d", bta_handle,
- registr.app_id);
+ BTIF_TRACE_DEBUG("%s: bta_handle=0x%x app_id=%d", __func__, bta_handle,
+ registr.app_id);
if (peer_sep == AVDT_TSEP_SNK) {
btif_av_source.BtaHandleRegistered(peer_id, bta_handle);
} else if (peer_sep == AVDT_TSEP_SRC) {
@@ -2598,26 +2578,22 @@ static void btif_av_handle_bta_av_event(uint8_t peer_sep,
const tBTA_AV_OPEN& open = p_data->open;
peer_address = open.bd_addr;
bta_handle = open.hndl;
- msg = "Stream opened";
break;
}
case BTA_AV_CLOSE_EVT: {
const tBTA_AV_CLOSE& close = p_data->close;
bta_handle = close.hndl;
- msg = "Stream closed";
break;
}
case BTA_AV_START_EVT: {
const tBTA_AV_START& start = p_data->start;
bta_handle = start.hndl;
- msg = "Stream started";
break;
}
case BTA_AV_SUSPEND_EVT:
case BTA_AV_STOP_EVT: {
const tBTA_AV_SUSPEND& suspend = p_data->suspend;
bta_handle = suspend.hndl;
- msg = "Stream stopped";
break;
}
case BTA_AV_PROTECT_REQ_EVT: {
@@ -2660,10 +2636,8 @@ static void btif_av_handle_bta_av_event(uint8_t peer_sep,
// events are received from the AVRCP module.
if (peer_sep == AVDT_TSEP_SNK) {
peer_address = btif_av_source.ActivePeer();
- msg = "Stream sink offloaded";
} else if (peer_sep == AVDT_TSEP_SRC) {
peer_address = btif_av_sink.ActivePeer();
- msg = "Stream source offloaded";
}
break;
}
@@ -2694,11 +2668,9 @@ static void btif_av_handle_bta_av_event(uint8_t peer_sep,
break;
}
}
+ BTIF_TRACE_DEBUG("%s: peer_address=%s bta_handle=0x%x", __func__,
+ peer_address.ToString().c_str(), bta_handle);
- if (!msg.empty()) {
- BTM_LogHistory(kBtmLogHistoryTag, peer_address, msg,
- btif_av_event.ToString());
- }
btif_av_handle_event(peer_sep, peer_address, bta_handle, btif_av_event);
}
@@ -2783,10 +2755,9 @@ static bt_status_t init_src(
}
// Initializes the AV interface for sink mode
-static bt_status_t init_sink(btav_sink_callbacks_t* callbacks,
- int max_connected_audio_devices) {
+static bt_status_t init_sink(btav_sink_callbacks_t* callbacks) {
BTIF_TRACE_EVENT("%s", __func__);
- return btif_av_sink.Init(callbacks, max_connected_audio_devices);
+ return btif_av_sink.Init(callbacks);
}
// Updates the final focus state reported by components calling this module
@@ -2870,21 +2841,20 @@ static void set_active_peer_int(uint8_t peer_sep,
}
static bt_status_t src_connect_sink(const RawAddress& peer_address) {
+ BTIF_TRACE_EVENT("%s: Peer %s", __func__, peer_address.ToString().c_str());
+
if (!btif_av_source.Enabled()) {
- LOG_WARN("BTIF AV Source is not enabled");
+ BTIF_TRACE_WARNING("%s: BTIF AV Source is not enabled", __func__);
return BT_STATUS_NOT_READY;
}
RawAddress peer_address_copy(peer_address);
- LOG_DEBUG("Connecting to AV sink peer:%s",
- PRIVATE_ADDRESS(peer_address_copy));
-
return btif_queue_connect(UUID_SERVCLASS_AUDIO_SOURCE, &peer_address_copy,
connect_int);
}
static bt_status_t sink_connect_src(const RawAddress& peer_address) {
- LOG_INFO("%s: Peer %s", __func__, peer_address.ToString().c_str());
+ LOG_INFO(LOG_TAG, "%s: Peer %s", __func__, peer_address.ToString().c_str());
if (!btif_av_sink.Enabled()) {
BTIF_TRACE_WARNING("%s: BTIF AV Sink is not enabled", __func__);
@@ -2897,7 +2867,7 @@ static bt_status_t sink_connect_src(const RawAddress& peer_address) {
}
static bt_status_t src_disconnect_sink(const RawAddress& peer_address) {
- LOG_INFO("%s: Peer %s", __func__, peer_address.ToString().c_str());
+ LOG_INFO(LOG_TAG, "%s: Peer %s", __func__, peer_address.ToString().c_str());
if (!btif_av_source.Enabled()) {
BTIF_TRACE_WARNING("%s: BTIF AV Source is not enabled", __func__);
@@ -2913,7 +2883,7 @@ static bt_status_t src_disconnect_sink(const RawAddress& peer_address) {
}
static bt_status_t sink_disconnect_src(const RawAddress& peer_address) {
- LOG_INFO("%s: Peer %s", __func__, peer_address.ToString().c_str());
+ LOG_INFO(LOG_TAG, "%s: Peer %s", __func__, peer_address.ToString().c_str());
if (!btif_av_sink.Enabled()) {
BTIF_TRACE_WARNING("%s: BTIF AV Sink is not enabled", __func__);
@@ -3055,7 +3025,7 @@ RawAddress btif_av_sink_active_peer(void) { return btif_av_sink.ActivePeer(); }
bool btif_av_is_sink_enabled(void) { return btif_av_sink.Enabled(); }
void btif_av_stream_start(void) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
btif_av_source_dispatch_sm_event(btif_av_source_active_peer(),
BTIF_AV_START_STREAM_REQ_EVT);
}
@@ -3082,7 +3052,7 @@ void src_do_suspend_in_main_thread(btif_av_sm_event_t event) {
}
void btif_av_stream_stop(const RawAddress& peer_address) {
- LOG_INFO("%s peer %s", __func__, peer_address.ToString().c_str());
+ LOG_INFO(LOG_TAG, "%s peer %s", __func__, peer_address.ToString().c_str());
if (!peer_address.IsEmpty()) {
btif_av_source_dispatch_sm_event(peer_address, BTIF_AV_STOP_STREAM_REQ_EVT);
@@ -3095,20 +3065,20 @@ void btif_av_stream_stop(const RawAddress& peer_address) {
}
void btif_av_stream_suspend(void) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
// The active peer might have changed and we might be in the process
// of reconfiguring the stream. We need to suspend the appropriate peer(s).
src_do_suspend_in_main_thread(BTIF_AV_SUSPEND_STREAM_REQ_EVT);
}
void btif_av_stream_start_offload(void) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
btif_av_source_dispatch_sm_event(btif_av_source_active_peer(),
BTIF_AV_OFFLOAD_START_REQ_EVT);
}
void btif_av_src_disconnect_sink(const RawAddress& peer_address) {
- LOG_INFO("%s: peer %s", __func__, peer_address.ToString().c_str());
+ LOG_INFO(LOG_TAG, "%s: peer %s", __func__, peer_address.ToString().c_str());
src_disconnect_sink(peer_address);
}
@@ -3126,7 +3096,7 @@ bool btif_av_stream_ready(void) {
}
int state = peer->StateMachine().StateId();
- LOG_INFO("%s: Peer %s : state=%d, flags=%s", __func__,
+ LOG_INFO(LOG_TAG, "%s: Peer %s : state=%d, flags=%s", __func__,
peer->PeerAddress().ToString().c_str(), state,
peer->FlagsToString().c_str());
// check if we are remotely suspended or stop is pending
@@ -3155,7 +3125,7 @@ bool btif_av_stream_started_ready(void) {
} else {
ready = (state == BtifAvStateMachine::kStateStarted);
}
- LOG_INFO("%s: Peer %s : state=%d flags=%s ready=%d", __func__,
+ LOG_INFO(LOG_TAG, "%s: Peer %s : state=%d flags=%s ready=%d", __func__,
peer->PeerAddress().ToString().c_str(), state,
peer->FlagsToString().c_str(), ready);
@@ -3193,6 +3163,10 @@ bt_status_t btif_av_source_execute_service(bool enable) {
(enable) ? "enable" : "disable");
if (enable) {
+ // TODO: Removed BTA_SEC_AUTHORIZE since the Java/App does not
+ // handle this request in order to allow incoming connections to succeed.
+ // We need to put this back once support for this is added.
+
// Added BTA_AV_FEAT_NO_SCO_SSPD - this ensures that the BTA does not
// auto-suspend av streaming on AG events(SCO or Call). The suspend shall
// be initiated by the app/audioflinger layers.
@@ -3208,7 +3182,7 @@ bt_status_t btif_av_source_execute_service(bool enable) {
#if (AVRC_ADV_CTRL_INCLUDED == TRUE)
features |= BTA_AV_FEAT_RCCT | BTA_AV_FEAT_ADV_CTRL | BTA_AV_FEAT_BROWSE;
#endif
- BTA_AvEnable(features, bta_av_source_callback);
+ BTA_AvEnable(BTA_SEC_AUTHENTICATE, features, bta_av_source_callback);
btif_av_source.RegisterAllBtaHandles();
return BT_STATUS_SUCCESS;
}
@@ -3231,12 +3205,7 @@ bt_status_t btif_av_sink_execute_service(bool enable) {
BTA_AV_FEAT_METADATA | BTA_AV_FEAT_VENDOR |
BTA_AV_FEAT_ADV_CTRL | BTA_AV_FEAT_RCTG |
BTA_AV_FEAT_BROWSE | BTA_AV_FEAT_COVER_ARTWORK;
-
- if (delay_reporting_enabled()) {
- features |= BTA_AV_FEAT_DELAY_RPT;
- }
-
- BTA_AvEnable(features, bta_av_sink_callback);
+ BTA_AvEnable(BTA_SEC_AUTHENTICATE, features, bta_av_sink_callback);
btif_av_sink.RegisterAllBtaHandles();
return BT_STATUS_SUCCESS;
}
@@ -3276,30 +3245,28 @@ bool btif_av_is_connected(void) {
uint8_t btif_av_get_peer_sep(void) {
BtifAvPeer* peer = btif_av_find_active_peer();
if (peer == nullptr) {
- LOG_INFO("No active sink or source peer found");
+ BTIF_TRACE_WARNING("%s: No active peer found", __func__);
return AVDT_TSEP_SNK;
}
uint8_t peer_sep = peer->PeerSep();
- LOG_INFO("Peer %s SEP is %s (%d)", peer->PeerAddress().ToString().c_str(),
- (peer_sep == AVDT_TSEP_SRC) ? "Source" : "Sink", peer_sep);
+ BTIF_TRACE_DEBUG("%s: Peer %s SEP is %s (%d)", __func__,
+ peer->PeerAddress().ToString().c_str(),
+ (peer_sep == AVDT_TSEP_SRC) ? "Source" : "Sink", peer_sep);
return peer_sep;
}
void btif_av_clear_remote_suspend_flag(void) {
- auto clear_remote_suspend_flag = []() {
- BtifAvPeer* peer = btif_av_find_active_peer();
- if (peer == nullptr) {
- BTIF_TRACE_WARNING("%s: No active peer found", __func__);
- return;
- }
- BTIF_TRACE_DEBUG("%s: Peer %s : flags=%s are cleared", __func__,
- peer->PeerAddress().ToString().c_str(),
- peer->FlagsToString().c_str());
- peer->ClearFlags(BtifAvPeer::kFlagRemoteSuspend);
- };
- // switch to main thread to prevent a race condition of accessing peers
- do_in_main_thread(FROM_HERE, base::Bind(clear_remote_suspend_flag));
+ BtifAvPeer* peer = btif_av_find_active_peer();
+ if (peer == nullptr) {
+ BTIF_TRACE_WARNING("%s: No active peer found", __func__);
+ return;
+ }
+
+ BTIF_TRACE_DEBUG("%s: Peer %s : flags=%s are cleared", __func__,
+ peer->PeerAddress().ToString().c_str(),
+ peer->FlagsToString().c_str());
+ peer->ClearFlags(BtifAvPeer::kFlagRemoteSuspend);
}
bool btif_av_is_peer_edr(const RawAddress& peer_address) {
@@ -3348,7 +3315,7 @@ bool btif_av_peer_prefers_mandatory_codec(const RawAddress& peer_address) {
void btif_av_acl_disconnected(const RawAddress& peer_address) {
// Inform the application that ACL is disconnected and move to idle state
- LOG_INFO("%s: Peer %s : ACL Disconnected", __func__,
+ LOG_INFO(LOG_TAG, "%s: Peer %s : ACL Disconnected", __func__,
peer_address.ToString().c_str());
if (btif_av_source.Enabled()) {
@@ -3398,7 +3365,7 @@ static void btif_debug_av_peer_dump(int fd, const BtifAvPeer& peer) {
dprintf(fd, " Support 3Mbps: %s\n", peer.Is3Mbps() ? "true" : "false");
dprintf(fd, " Self Initiated Connection: %s\n",
peer.SelfInitiatedConnection() ? "true" : "false");
- dprintf(fd, " Delay Reporting: %u (in 1/10 milliseconds) \n", peer.GetDelayReport());
+ dprintf(fd, " Delay Reporting: %u\n", peer.GetDelayReport());
dprintf(fd, " Codec Preferred: %s\n",
peer.IsMandatoryCodecPreferred() ? "Mandatory" : "Optional");
}
@@ -3475,7 +3442,3 @@ bool btif_av_is_a2dp_offload_running() {
bool btif_av_is_peer_silenced(const RawAddress& peer_address) {
return btif_av_source.IsPeerSilenced(peer_address);
}
-
-void btif_av_set_dynamic_audio_buffer_size(uint8_t dynamic_audio_buffer_size) {
- btif_a2dp_source_set_dynamic_audio_buffer_size(dynamic_audio_buffer_size);
-}
diff --git a/btif/src/btif_avrcp_audio_track.cc b/btif/src/btif_avrcp_audio_track.cc
index 8ca5c9798..5cf94e2ec 100644
--- a/btif/src/btif_avrcp_audio_track.cc
+++ b/btif/src/btif_avrcp_audio_track.cc
@@ -43,7 +43,7 @@ char outputFilename[50] = "/data/misc/bluedroid/output_sample.pcm";
void* BtifAvrcpAudioTrackCreate(int trackFreq, int bitsPerSample,
int channelCount) {
- LOG_VERBOSE("%s Track.cpp: btCreateTrack freq %d bps %d channel %d ",
+ LOG_VERBOSE(LOG_TAG, "%s Track.cpp: btCreateTrack freq %d bps %d channel %d ",
__func__, trackFreq, bitsPerSample, channelCount);
AAudioStreamBuilder* builder;
@@ -76,36 +76,36 @@ void* BtifAvrcpAudioTrackCreate(int trackFreq, int bitsPerSample,
void BtifAvrcpAudioTrackStart(void* handle) {
if (handle == NULL) {
- LOG_ERROR("%s: handle is null!", __func__);
+ LOG_ERROR(LOG_TAG, "%s: handle is null!", __func__);
return;
}
BtifAvrcpAudioTrack* trackHolder = static_cast<BtifAvrcpAudioTrack*>(handle);
CHECK(trackHolder != NULL);
CHECK(trackHolder->stream != NULL);
- LOG_VERBOSE("%s Track.cpp: btStartTrack", __func__);
+ LOG_VERBOSE(LOG_TAG, "%s Track.cpp: btStartTrack", __func__);
AAudioStream_requestStart(trackHolder->stream);
}
void BtifAvrcpAudioTrackStop(void* handle) {
if (handle == NULL) {
- LOG_INFO("%s handle is null.", __func__);
+ LOG_DEBUG(LOG_TAG, "%s handle is null.", __func__);
return;
}
BtifAvrcpAudioTrack* trackHolder = static_cast<BtifAvrcpAudioTrack*>(handle);
if (trackHolder != NULL && trackHolder->stream != NULL) {
- LOG_VERBOSE("%s Track.cpp: btStartTrack", __func__);
+ LOG_VERBOSE(LOG_TAG, "%s Track.cpp: btStartTrack", __func__);
AAudioStream_requestStop(trackHolder->stream);
}
}
void BtifAvrcpAudioTrackDelete(void* handle) {
if (handle == NULL) {
- LOG_INFO("%s handle is null.", __func__);
+ LOG_DEBUG(LOG_TAG, "%s handle is null.", __func__);
return;
}
BtifAvrcpAudioTrack* trackHolder = static_cast<BtifAvrcpAudioTrack*>(handle);
if (trackHolder != NULL && trackHolder->stream != NULL) {
- LOG_VERBOSE("%s Track.cpp: btStartTrack", __func__);
+ LOG_VERBOSE(LOG_TAG, "%s Track.cpp: btStartTrack", __func__);
AAudioStream_close(trackHolder->stream);
delete trackHolder->buffer;
delete trackHolder;
@@ -121,12 +121,12 @@ void BtifAvrcpAudioTrackDelete(void* handle) {
void BtifAvrcpAudioTrackPause(void* handle) {
if (handle == NULL) {
- LOG_INFO("%s handle is null.", __func__);
+ LOG_DEBUG(LOG_TAG, "%s handle is null.", __func__);
return;
}
BtifAvrcpAudioTrack* trackHolder = static_cast<BtifAvrcpAudioTrack*>(handle);
if (trackHolder != NULL && trackHolder->stream != NULL) {
- LOG_VERBOSE("%s Track.cpp: btPauseTrack", __func__);
+ LOG_VERBOSE(LOG_TAG, "%s Track.cpp: btPauseTrack", __func__);
AAudioStream_requestPause(trackHolder->stream);
AAudioStream_requestFlush(trackHolder->stream);
}
@@ -134,7 +134,7 @@ void BtifAvrcpAudioTrackPause(void* handle) {
void BtifAvrcpSetAudioTrackGain(void* handle, float gain) {
if (handle == NULL) {
- LOG_INFO("%s handle is null.", __func__);
+ LOG_DEBUG(LOG_TAG, "%s handle is null.", __func__);
return;
}
// Does nothing right now
@@ -218,8 +218,8 @@ int BtifAvrcpAudioTrackWriteData(void* handle, void* audioBuffer,
trackHolder->stream, trackHolder->buffer,
transcodedCount / (sampleSize * trackHolder->channelCount),
kTimeoutNanos);
- LOG_VERBOSE("%s Track.cpp: btWriteData len = %d ret = %d", __func__,
- bufferLength, retval);
+ LOG_VERBOSE(LOG_TAG, "%s Track.cpp: btWriteData len = %d ret = %d",
+ __func__, bufferLength, retval);
} while (transcodedCount < bufferLength);
return transcodedCount;
diff --git a/btif/src/btif_ble_advertiser.cc b/btif/src/btif_ble_advertiser.cc
index e6bfe20cf..d1923bdd3 100644
--- a/btif/src/btif_ble_advertiser.cc
+++ b/btif/src/btif_ble_advertiser.cc
@@ -26,8 +26,6 @@
#include "ble_advertiser.h"
#include "btif_common.h"
-#include "main/shim/le_advertising_manager.h"
-#include "main/shim/shim.h"
#include "stack/include/btu.h"
using base::Bind;
@@ -182,7 +180,7 @@ class BleAdvertiserInterfaceImpl : public BleAdvertiserInterface {
timeout_s * 100, jni_thread_wrapper(FROM_HERE, timeout_cb)));
}
- void StartAdvertisingSet(int reg_id, IdTxPowerStatusCallback cb,
+ void StartAdvertisingSet(IdTxPowerStatusCallback cb,
AdvertiseParameters params,
std::vector<uint8_t> advertise_data,
std::vector<uint8_t> scan_response_data,
@@ -248,10 +246,6 @@ class BleAdvertiserInterfaceImpl : public BleAdvertiserInterface {
BleAdvertisingManager::Get(), advertiser_id, enable,
jni_thread_wrapper(FROM_HERE, cb)));
}
-
- void RegisterCallbacks(AdvertisingCallbacks* callbacks) {
- // For GD only
- }
};
BleAdvertiserInterface* btLeAdvertiserInstance = nullptr;
@@ -259,12 +253,8 @@ BleAdvertiserInterface* btLeAdvertiserInstance = nullptr;
} // namespace
BleAdvertiserInterface* get_ble_advertiser_instance() {
- if (bluetooth::shim::is_gd_advertising_enabled()) {
- LOG(INFO) << __func__ << " use gd le advertiser";
- return bluetooth::shim::get_ble_advertiser_instance();
- } else if (btLeAdvertiserInstance == nullptr) {
+ if (btLeAdvertiserInstance == nullptr)
btLeAdvertiserInstance = new BleAdvertiserInterfaceImpl();
- }
return btLeAdvertiserInstance;
}
diff --git a/btif/src/btif_ble_scanner.cc b/btif/src/btif_ble_scanner.cc
index badae4ed3..b3149938f 100644
--- a/btif/src/btif_ble_scanner.cc
+++ b/btif/src/btif_ble_scanner.cc
@@ -30,8 +30,6 @@
#include "btif_common.h"
#include "btif_util.h"
-#include "main/shim/le_scanning_manager.h"
-#include "main/shim/shim.h"
#include <hardware/bt_gatt.h>
@@ -96,7 +94,7 @@ void bta_batch_scan_threshold_cb(tBTM_BLE_REF_VALUE ref_value) {
SCAN_CBACK_IN_JNI(batchscan_threshold_cb, ref_value);
}
-void bta_batch_scan_reports_cb(int client_id, tBTM_STATUS status,
+void bta_batch_scan_reports_cb(int client_id, tBTA_STATUS status,
uint8_t report_format, uint8_t num_records,
std::vector<uint8_t> data) {
SCAN_CBACK_IN_JNI(batchscan_reports_cb, client_id, status, report_format,
@@ -104,7 +102,7 @@ void bta_batch_scan_reports_cb(int client_id, tBTM_STATUS status,
}
void bta_scan_results_cb_impl(RawAddress bd_addr, tBT_DEVICE_TYPE device_type,
- int8_t rssi, tBLE_ADDR_TYPE addr_type,
+ int8_t rssi, uint8_t addr_type,
uint16_t ble_evt_type, uint8_t ble_primary_phy,
uint8_t ble_secondary_phy,
uint8_t ble_advertising_sid, int8_t ble_tx_power,
@@ -130,7 +128,8 @@ void bta_scan_results_cb_impl(RawAddress bd_addr, tBT_DEVICE_TYPE device_type,
if (remote_name_len > BD_NAME_LEN + 1 ||
(remote_name_len == BD_NAME_LEN + 1 &&
p_eir_remote_name[BD_NAME_LEN] != '\0')) {
- LOG_INFO("%s dropping invalid packet - device name too long: %d",
+ LOG_INFO(LOG_TAG,
+ "%s dropping invalid packet - device name too long: %d",
__func__, remote_name_len);
return;
}
@@ -140,8 +139,8 @@ void bta_scan_results_cb_impl(RawAddress bd_addr, tBT_DEVICE_TYPE device_type,
if (remote_name_len < BD_NAME_LEN + 1)
bdname.name[remote_name_len] = '\0';
- LOG_VERBOSE("%s BLE device name=%s len=%d dev_type=%d", __func__,
- bdname.name, remote_name_len, device_type);
+ LOG_VERBOSE(LOG_TAG, "%s BLE device name=%s len=%d dev_type=%d",
+ __func__, bdname.name, remote_name_len, device_type);
btif_dm_update_ble_remote_properties(bd_addr, bdname.name, device_type);
}
}
@@ -206,15 +205,13 @@ void bta_cback(tBTA_GATTC_EVT, tBTA_GATTC*) {}
class BleScannerInterfaceImpl : public BleScannerInterface {
~BleScannerInterfaceImpl() override{};
- void RegisterScanner(const bluetooth::Uuid& app_uuid,
- RegisterCallback cb) override {
+ void RegisterScanner(RegisterCallback cb) override {
do_in_main_thread(FROM_HERE,
Bind(
[](RegisterCallback cb) {
BTA_GATTC_AppRegister(
bta_cback,
- jni_thread_wrapper(FROM_HERE, std::move(cb)),
- false);
+ jni_thread_wrapper(FROM_HERE, std::move(cb)));
},
std::move(cb)));
}
@@ -313,8 +310,7 @@ class BleScannerInterfaceImpl : public BleScannerInterface {
int addr_type, int discard_rule, Callback cb) override {
do_in_main_thread(
FROM_HERE, base::Bind(&BTM_BleEnableBatchScan, scan_mode, scan_interval,
- scan_window, discard_rule,
- static_cast<tBLE_ADDR_TYPE>(addr_type),
+ scan_window, discard_rule, addr_type,
jni_thread_wrapper(FROM_HERE, cb)));
}
@@ -324,10 +320,9 @@ class BleScannerInterfaceImpl : public BleScannerInterface {
}
void BatchscanReadReports(int client_if, int scan_mode) override {
- do_in_main_thread(
- FROM_HERE,
- base::Bind(&BTM_BleReadScanReports, (tBLE_SCAN_MODE)scan_mode,
- Bind(bta_batch_scan_reports_cb, client_if)));
+ do_in_main_thread(FROM_HERE,
+ base::Bind(&BTM_BleReadScanReports, (uint8_t)scan_mode,
+ Bind(bta_batch_scan_reports_cb, client_if)));
}
void StartSync(uint8_t sid, RawAddress address, uint16_t skip,
@@ -335,10 +330,6 @@ class BleScannerInterfaceImpl : public BleScannerInterface {
SyncLostCb lost_cb) override {}
void StopSync(uint16_t handle) override {}
-
- void RegisterCallbacks(ScanningCallbacks* callbacks) {
- // For GD only
- }
};
BleScannerInterface* btLeScannerInstance = nullptr;
@@ -346,11 +337,8 @@ BleScannerInterface* btLeScannerInstance = nullptr;
} // namespace
BleScannerInterface* get_ble_scanner_instance() {
- if (bluetooth::shim::is_gd_scanning_enabled()) {
- LOG_INFO("Use gd le scanner");
- return bluetooth::shim::get_ble_scanner_instance();
- } else if (btLeScannerInstance == nullptr) {
+ if (btLeScannerInstance == nullptr)
btLeScannerInstance = new BleScannerInterfaceImpl();
- }
+
return btLeScannerInstance;
}
diff --git a/btif/src/btif_bqr.cc b/btif/src/btif_bqr.cc
index c437b2c1b..848d8863f 100644
--- a/btif/src/btif_bqr.cc
+++ b/btif/src/btif_bqr.cc
@@ -17,18 +17,15 @@
#include <base/logging.h>
#include <errno.h>
#include <fcntl.h>
-#ifdef OS_ANDROID
#include <statslog.h>
-#endif
#include <stdio.h>
#include <sys/stat.h>
#include "btif_bqr.h"
-#include "btif_common.h"
-#include "btm_api.h"
+#include "btif_dm.h"
#include "common/leaky_bonded_queue.h"
-#include "common/time_util.h"
#include "osi/include/properties.h"
+#include "stack/btm/btm_int.h"
namespace bluetooth {
namespace bqr {
@@ -54,7 +51,7 @@ void BqrVseSubEvt::ParseBqrLinkQualityEvt(uint8_t length,
STREAM_TO_UINT8(bqr_link_quality_event_.packet_types, p_param_buf);
STREAM_TO_UINT16(bqr_link_quality_event_.connection_handle, p_param_buf);
STREAM_TO_UINT8(bqr_link_quality_event_.connection_role, p_param_buf);
- STREAM_TO_INT8(bqr_link_quality_event_.tx_power_level, p_param_buf);
+ STREAM_TO_UINT8(bqr_link_quality_event_.tx_power_level, p_param_buf);
STREAM_TO_INT8(bqr_link_quality_event_.rssi, p_param_buf);
STREAM_TO_UINT8(bqr_link_quality_event_.snr, p_param_buf);
STREAM_TO_UINT8(bqr_link_quality_event_.unused_afh_channel_count,
@@ -126,9 +123,8 @@ std::string BqrVseSubEvt::ToString() const {
ss << QualityReportIdToString(bqr_link_quality_event_.quality_report_id)
<< ", Handle: " << loghex(bqr_link_quality_event_.connection_handle)
<< ", " << PacketTypeToString(bqr_link_quality_event_.packet_types) << ", "
- << ((bqr_link_quality_event_.connection_role == 0) ? "Central"
- : "Peripheral ")
- << ", PwLv: " << std::to_string(bqr_link_quality_event_.tx_power_level)
+ << ((bqr_link_quality_event_.connection_role == 0) ? "Master" : "Slave ")
+ << ", PwLv: " << loghex(bqr_link_quality_event_.tx_power_level)
<< ", RSSI: " << std::to_string(bqr_link_quality_event_.rssi)
<< ", SNR: " << std::to_string(bqr_link_quality_event_.snr)
<< ", UnusedCh: "
@@ -271,8 +267,7 @@ void ConfigureBqr(const BqrConfiguration& bqr_config) {
return;
}
- LOG(INFO) << __func__ << ": Action: "
- << loghex(static_cast<uint8_t>(bqr_config.report_action))
+ LOG(INFO) << __func__ << ": Action: " << bqr_config.report_action
<< ", Mask: " << loghex(bqr_config.quality_event_mask)
<< ", Interval: " << bqr_config.minimum_report_interval_ms;
@@ -388,16 +383,6 @@ void AddLinkQualityEventToQueue(uint8_t length, uint8_t* p_link_quality_event) {
p_bqr_event->ParseBqrLinkQualityEvt(length, p_link_quality_event);
LOG(WARNING) << *p_bqr_event;
- invoke_link_quality_report_cb(
- bluetooth::common::time_get_os_boottime_ms(),
- p_bqr_event->bqr_link_quality_event_.quality_report_id,
- p_bqr_event->bqr_link_quality_event_.rssi,
- p_bqr_event->bqr_link_quality_event_.snr,
- p_bqr_event->bqr_link_quality_event_.retransmission_count,
- p_bqr_event->bqr_link_quality_event_.no_rx_count,
- p_bqr_event->bqr_link_quality_event_.nak_count);
-
-#ifdef OS_ANDROID
int ret = android::util::stats_write(
android::util::BLUETOOTH_QUALITY_REPORT_REPORTED,
p_bqr_event->bqr_link_quality_event_.quality_report_id,
@@ -423,9 +408,6 @@ void AddLinkQualityEventToQueue(uint8_t length, uint8_t* p_link_quality_event) {
LOG(WARNING) << __func__ << ": failed to log BQR event to statsd, error "
<< ret;
}
-#else
- // TODO(abps) Metrics for non-Android build
-#endif
kpBqrEventQueue->Enqueue(p_bqr_event.release());
}
diff --git a/btif/src/btif_config.cc b/btif/src/btif_config.cc
index 95e9baa9c..49cb19fb6 100644
--- a/btif/src/btif_config.cc
+++ b/btif/src/btif_config.cc
@@ -21,26 +21,28 @@
#include "btif_config.h"
#include <base/logging.h>
+#include <ctype.h>
#include <openssl/rand.h>
+#include <openssl/sha.h>
+#include <private/android_filesystem_config.h>
+#include <stdio.h>
+#include <string.h>
+#include <time.h>
#include <unistd.h>
-
-#include <cctype>
-#include <cstdio>
-#include <cstring>
-#include <ctime>
#include <functional>
#include <mutex>
#include <sstream>
#include <string>
#include <unordered_map>
+#include <btif_keystore.h>
+#include "bt_types.h"
#include "btcore/include/module.h"
#include "btif_api.h"
#include "btif_common.h"
#include "btif_config_cache.h"
#include "btif_config_transcode.h"
-#include "btif_keystore.h"
-#include "btif_metrics_logging.h"
+#include "btif_util.h"
#include "common/address_obfuscator.h"
#include "common/metric_id_allocator.h"
#include "main/shim/config.h"
@@ -93,8 +95,10 @@ static std::unique_ptr<config_t> btif_config_open(const char* filename);
// Key attestation
static bool config_checksum_pass(int check_bit) {
- return ((get_common_criteria_config_compare_result() & check_bit) ==
- check_bit);
+ return ((get_niap_config_compare_result() & check_bit) == check_bit);
+}
+static bool btif_is_niap_mode() {
+ return getuid() == AID_BLUETOOTH && is_niap_mode();
}
static bool btif_in_encrypt_key_name_list(std::string key);
@@ -119,6 +123,23 @@ static enum ConfigSource {
static char btif_config_time_created[TIME_STRING_LENGTH];
+static const storage_config_t interface = {
+ checksum_read, checksum_save, config_get_bool,
+ config_get_int, config_get_string, config_get_uint64,
+ config_has_key, config_has_section, config_new,
+ config_new_clone, config_new_empty, config_remove_key,
+ config_remove_section, config_save, config_set_bool,
+ config_set_int, config_set_string, config_set_uint64,
+};
+
+static const storage_config_t* storage_config_get_interface() {
+ if (bluetooth::shim::is_gd_stack_started_up()) {
+ return bluetooth::shim::storage_config_get_interface();
+ } else {
+ return &interface;
+ }
+}
+
static BluetoothKeystoreInterface* get_bluetooth_keystore_interface() {
return bluetooth::bluetooth_keystore::getBluetoothKeystoreInterface();
}
@@ -134,22 +155,21 @@ bool btif_get_device_type(const RawAddress& bda, int* p_device_type) {
if (!btif_config_get_int(bd_addr_str, "DevType", p_device_type)) return false;
- LOG_INFO("Device [%s] device type %d", bd_addr_str, *p_device_type);
+ LOG_DEBUG(LOG_TAG, "%s: Device [%s] type %d", __func__, bd_addr_str,
+ *p_device_type);
return true;
}
-bool btif_get_address_type(const RawAddress& bda, tBLE_ADDR_TYPE* p_addr_type) {
+bool btif_get_address_type(const RawAddress& bda, int* p_addr_type) {
if (p_addr_type == NULL) return false;
std::string addrstr = bda.ToString();
const char* bd_addr_str = addrstr.c_str();
- int val = 0;
- if (!btif_config_get_int(bd_addr_str, "AddrType", &val)) return false;
- *p_addr_type = static_cast<tBLE_ADDR_TYPE>(val);
+ if (!btif_config_get_int(bd_addr_str, "AddrType", p_addr_type)) return false;
- LOG_DEBUG("Device [%s] address type %s", bd_addr_str,
- AddressTypeText(*p_addr_type).c_str());
+ LOG_DEBUG(LOG_TAG, "%s: Device [%s] address type %d", __func__, bd_addr_str,
+ *p_addr_type);
return true;
}
@@ -199,15 +219,19 @@ static void init_metric_id_allocator() {
// version of android without a metric id.
std::vector<RawAddress> addresses_without_id;
- for (const auto& mac_address : btif_config_get_paired_devices()) {
- auto addr_str = mac_address.ToString();
+ for (auto& section : btif_config_sections()) {
+ auto& section_name = section.name;
+ RawAddress mac_address;
+ if (!RawAddress::FromString(section_name, mac_address)) {
+ continue;
+ }
// if the section name is a mac address
bool is_valid_id_found = false;
- if (btif_config_exist(addr_str, BT_CONFIG_METRICS_ID_KEY)) {
+ if (btif_config_exist(section_name, BT_CONFIG_METRICS_ID_KEY)) {
// there is one metric id under this mac_address
int id = 0;
- btif_config_get_int(addr_str, BT_CONFIG_METRICS_ID_KEY, &id);
- if (is_valid_id_from_metric_id_allocator(id)) {
+ btif_config_get_int(section_name, BT_CONFIG_METRICS_ID_KEY, &id);
+ if (MetricIdAllocator::IsValidId(id)) {
paired_device_map[mac_address] = id;
is_valid_id_found = true;
}
@@ -227,16 +251,16 @@ static void init_metric_id_allocator() {
[](const RawAddress& address, const int id) {
return btif_config_remove(address.ToString(), BT_CONFIG_METRICS_ID_KEY);
};
- if (!init_metric_id_allocator(paired_device_map,
- std::move(save_device_callback),
- std::move(forget_device_callback))) {
+ if (!MetricIdAllocator::GetInstance().Init(
+ paired_device_map, std::move(save_device_callback),
+ std::move(forget_device_callback))) {
LOG(FATAL) << __func__ << "Failed to initialize MetricIdAllocator";
}
// Add device_without_id
for (auto& address : addresses_without_id) {
- allocate_metric_id_from_metric_id_allocator(address);
- save_metric_id_from_metric_id_allocator(address);
+ MetricIdAllocator::GetInstance().AllocateId(address);
+ MetricIdAllocator::GetInstance().SaveDevice(address);
}
}
@@ -249,13 +273,6 @@ static BtifConfigCache btif_config_cache(TEMPORARY_SECTION_CAPACITY);
// Module lifecycle functions
static future_t* init(void) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- // TODO (b/158035889) Migrate metrics module to GD
- read_or_set_metrics_salt();
- init_metric_id_allocator();
- return future_new_immediate(FUTURE_SUCCESS);
- }
std::unique_lock<std::recursive_mutex> lock(config_lock);
std::unique_ptr<config_t> config;
@@ -268,8 +285,8 @@ static future_t* init(void) {
btif_config_source = ORIGINAL;
}
if (!config) {
- LOG_WARN("%s unable to load config file: %s; using backup.", __func__,
- CONFIG_FILE_PATH);
+ LOG_WARN(LOG_TAG, "%s unable to load config file: %s; using backup.",
+ __func__, CONFIG_FILE_PATH);
if (config_checksum_pass(CONFIG_BACKUP_COMPARE_PASS)) {
config = btif_config_open(CONFIG_BACKUP_PATH);
btif_config_source = BACKUP;
@@ -277,16 +294,18 @@ static future_t* init(void) {
}
}
if (!config) {
- LOG_WARN("%s unable to load backup; attempting to transcode legacy file.",
+ LOG_WARN(LOG_TAG,
+ "%s unable to load backup; attempting to transcode legacy file.",
__func__);
config = btif_config_transcode(CONFIG_LEGACY_FILE_PATH);
btif_config_source = LEGACY;
file_source = "Legacy";
}
if (!config) {
- LOG_ERROR("%s unable to transcode legacy file; creating empty config.",
+ LOG_ERROR(LOG_TAG,
+ "%s unable to transcode legacy file; creating empty config.",
__func__);
- config = config_new_empty();
+ config = storage_config_get_interface()->config_new_empty();
btif_config_source = NEW_FILE;
file_source = "Empty";
}
@@ -327,7 +346,7 @@ static future_t* init(void) {
// write back to disk.
config_timer = alarm_new("btif.config");
if (!config_timer) {
- LOG_ERROR("%s unable to create alarm.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to create alarm.", __func__);
goto error;
}
@@ -345,11 +364,12 @@ error:
}
static std::unique_ptr<config_t> btif_config_open(const char* filename) {
- std::unique_ptr<config_t> config = config_new(filename);
+ std::unique_ptr<config_t> config =
+ storage_config_get_interface()->config_new(filename);
if (!config) return nullptr;
if (!config_has_section(*config, "Adapter")) {
- LOG_ERROR("Config is missing adapter section");
+ LOG_ERROR(LOG_TAG, "Config is missing adapter section");
return nullptr;
}
@@ -362,13 +382,6 @@ static future_t* shut_down(void) {
}
static future_t* clean_up(void) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- // GD storage module cleanup by itself
- std::unique_lock<std::recursive_mutex> lock(config_lock);
- close_metric_id_allocator();
- return future_new_immediate(FUTURE_SUCCESS);
- }
btif_config_flush();
alarm_free(config_timer);
@@ -376,7 +389,7 @@ static future_t* clean_up(void) {
std::unique_lock<std::recursive_mutex> lock(config_lock);
get_bluetooth_keystore_interface()->clear_map();
- close_metric_id_allocator();
+ MetricIdAllocator::GetInstance().Close();
btif_config_cache.Clear();
return future_new_immediate(FUTURE_SUCCESS);
}
@@ -387,21 +400,20 @@ EXPORT_SYMBOL module_t btif_config_module = {.name = BTIF_CONFIG_MODULE,
.shut_down = shut_down,
.clean_up = clean_up};
+bool btif_config_has_section(const char* section) {
+ CHECK(section != NULL);
+
+ std::unique_lock<std::recursive_mutex> lock(config_lock);
+ return btif_config_cache.HasSection(section);
+}
+
bool btif_config_exist(const std::string& section, const std::string& key) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- return bluetooth::shim::BtifConfigInterface::HasProperty(section, key);
- }
std::unique_lock<std::recursive_mutex> lock(config_lock);
return btif_config_cache.HasKey(section, key);
}
bool btif_config_get_int(const std::string& section, const std::string& key,
int* value) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- return bluetooth::shim::BtifConfigInterface::GetInt(section, key, value);
- }
CHECK(value != NULL);
std::unique_lock<std::recursive_mutex> lock(config_lock);
auto ret = btif_config_cache.GetInt(section, key);
@@ -414,10 +426,6 @@ bool btif_config_get_int(const std::string& section, const std::string& key,
bool btif_config_set_int(const std::string& section, const std::string& key,
int value) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- return bluetooth::shim::BtifConfigInterface::SetInt(section, key, value);
- }
std::unique_lock<std::recursive_mutex> lock(config_lock);
btif_config_cache.SetInt(section, key, value);
return true;
@@ -425,10 +433,6 @@ bool btif_config_set_int(const std::string& section, const std::string& key,
bool btif_config_get_uint64(const std::string& section, const std::string& key,
uint64_t* value) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- return bluetooth::shim::BtifConfigInterface::GetUint64(section, key, value);
- }
CHECK(value != NULL);
std::unique_lock<std::recursive_mutex> lock(config_lock);
auto ret = btif_config_cache.GetUint64(section, key);
@@ -441,41 +445,13 @@ bool btif_config_get_uint64(const std::string& section, const std::string& key,
bool btif_config_set_uint64(const std::string& section, const std::string& key,
uint64_t value) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- return bluetooth::shim::BtifConfigInterface::SetUint64(section, key, value);
- }
std::unique_lock<std::recursive_mutex> lock(config_lock);
btif_config_cache.SetUint64(section, key, value);
return true;
}
-/*******************************************************************************
- *
- * Function btif_config_get_str
- *
- * Description Get the string value associated with a particular section
- * and key.
- *
- * section : The section name (i.e "Adapter")
- * key : The key name (i.e "Address")
- * value : A pointer to a buffer where we will store the value
- * size_bytes : The size of the buffer we have available to
- * write the value into. Will be updated upon
- * returning to contain the number of bytes
- * written.
- *
- * Returns True if a value was found, False otherwise.
- *
- ******************************************************************************/
-
bool btif_config_get_str(const std::string& section, const std::string& key,
char* value, int* size_bytes) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- return bluetooth::shim::BtifConfigInterface::GetStr(section, key, value,
- size_bytes);
- }
CHECK(value != NULL);
CHECK(size_bytes != NULL);
@@ -491,10 +467,6 @@ bool btif_config_get_str(const std::string& section, const std::string& key,
bool btif_config_set_str(const std::string& section, const std::string& key,
const std::string& value) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- return bluetooth::shim::BtifConfigInterface::SetStr(section, key, value);
- }
std::unique_lock<std::recursive_mutex> lock(config_lock);
btif_config_cache.SetString(section, key, value);
return true;
@@ -508,11 +480,6 @@ static bool btif_in_encrypt_key_name_list(std::string key) {
bool btif_config_get_bin(const std::string& section, const std::string& key,
uint8_t* value, size_t* length) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- return bluetooth::shim::BtifConfigInterface::GetBin(section, key, value,
- length);
- }
CHECK(value != NULL);
CHECK(length != NULL);
@@ -555,7 +522,7 @@ bool btif_config_get_bin(const std::string& section, const std::string& key,
sscanf(ptr, "%02hhx", &value[*length]);
}
- if (is_common_criteria_mode()) {
+ if (btif_is_niap_mode()) {
if (!value_str_from_config->empty() && in_encrypt_key_name_list &&
!is_key_encrypted) {
get_bluetooth_keystore_interface()->set_encrypt_key_or_remove_key(
@@ -573,10 +540,6 @@ bool btif_config_get_bin(const std::string& section, const std::string& key,
size_t btif_config_get_bin_length(const std::string& section,
const std::string& key) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- return bluetooth::shim::BtifConfigInterface::GetBinLength(section, key);
- }
std::unique_lock<std::recursive_mutex> lock(config_lock);
auto value_str = btif_config_cache.GetString(section, key);
if (!value_str) return 0;
@@ -586,11 +549,6 @@ size_t btif_config_get_bin_length(const std::string& section,
bool btif_config_set_bin(const std::string& section, const std::string& key,
const uint8_t* value, size_t length) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- return bluetooth::shim::BtifConfigInterface::SetBin(section, key, value,
- length);
- }
const char* lookup = "0123456789abcdef";
if (length > 0) CHECK(value != NULL);
@@ -608,7 +566,7 @@ bool btif_config_set_bin(const std::string& section, const std::string& key,
}
std::string value_str;
- if ((length > 0) && is_common_criteria_mode() &&
+ if ((length > 0) && btif_is_niap_mode() &&
btif_in_encrypt_key_name_list(key)) {
get_bluetooth_keystore_interface()->set_encrypt_key_or_remove_key(
section + "-" + key, str);
@@ -626,33 +584,12 @@ bool btif_config_set_bin(const std::string& section, const std::string& key,
return true;
}
-std::vector<RawAddress> btif_config_get_paired_devices() {
- std::vector<std::string> names;
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- names = bluetooth::shim::BtifConfigInterface::GetPersistentDevices();
- } else {
- std::unique_lock<std::recursive_mutex> lock(config_lock);
- names = btif_config_cache.GetPersistentSectionNames();
- }
- std::vector<RawAddress> result;
- result.reserve(names.size());
- for (const auto& name : names) {
- RawAddress addr = {};
- // Gather up known devices from configuration section names
- if (RawAddress::FromString(name, addr)) {
- result.emplace_back(addr);
- }
- }
- return result;
+const std::list<section_t>& btif_config_sections() {
+ return btif_config_cache.GetPersistentSections();
}
bool btif_config_remove(const std::string& section, const std::string& key) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- return bluetooth::shim::BtifConfigInterface::RemoveProperty(section, key);
- }
- if (is_common_criteria_mode() && btif_in_encrypt_key_name_list(key)) {
+ if (is_niap_mode() && btif_in_encrypt_key_name_list(key)) {
get_bluetooth_keystore_interface()->set_encrypt_key_or_remove_key(
section + "-" + key, "");
}
@@ -661,22 +598,12 @@ bool btif_config_remove(const std::string& section, const std::string& key) {
}
void btif_config_save(void) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- bluetooth::shim::BtifConfigInterface::Save();
- return;
- }
CHECK(config_timer != NULL);
alarm_set(config_timer, CONFIG_SETTLE_PERIOD_MS, timer_config_save_cb, NULL);
}
void btif_config_flush(void) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- bluetooth::shim::BtifConfigInterface::Flush();
- return;
- }
CHECK(config_timer != NULL);
alarm_cancel(config_timer);
@@ -684,12 +611,6 @@ void btif_config_flush(void) {
}
bool btif_config_clear(void) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- CHECK(bluetooth::shim::is_gd_stack_started_up());
- bluetooth::shim::BtifConfigInterface::Clear();
- bluetooth::shim::BtifConfigInterface::Save();
- return true;
- }
CHECK(config_timer != NULL);
alarm_cancel(config_timer);
@@ -697,8 +618,8 @@ bool btif_config_clear(void) {
std::unique_lock<std::recursive_mutex> lock(config_lock);
btif_config_cache.Clear();
- bool ret =
- config_save(btif_config_cache.PersistentSectionCopy(), CONFIG_FILE_PATH);
+ bool ret = storage_config_get_interface()->config_save(
+ btif_config_cache.PersistentSectionCopy(), CONFIG_FILE_PATH);
btif_config_source = RESET;
return ret;
@@ -717,8 +638,9 @@ static void btif_config_write(UNUSED_ATTR uint16_t event,
std::unique_lock<std::recursive_mutex> lock(config_lock);
rename(CONFIG_FILE_PATH, CONFIG_BACKUP_PATH);
- config_save(btif_config_cache.PersistentSectionCopy(), CONFIG_FILE_PATH);
- if (is_common_criteria_mode()) {
+ storage_config_get_interface()->config_save(
+ btif_config_cache.PersistentSectionCopy(), CONFIG_FILE_PATH);
+ if (btif_is_niap_mode()) {
get_bluetooth_keystore_interface()->set_encrypt_key_or_remove_key(
CONFIG_FILE_PREFIX, CONFIG_FILE_HASH);
}
@@ -749,19 +671,13 @@ void btif_debug_config_dump(int fd) {
break;
}
- std::optional<std::string> file_source;
- if (bluetooth::shim::is_gd_stack_started_up()) {
- CHECK(bluetooth::shim::is_any_gd_enabled());
- file_source =
- bluetooth::shim::BtifConfigInterface::GetStr(INFO_SECTION, FILE_SOURCE);
- } else {
- file_source = btif_config_cache.GetString(INFO_SECTION, FILE_SOURCE);
- }
+ auto file_source = btif_config_cache.GetString(INFO_SECTION, FILE_SOURCE);
if (!file_source) {
file_source.emplace("Original");
}
- auto devices = btif_config_cache.GetPersistentSectionNames();
- dprintf(fd, " Devices loaded: %zu\n", devices.size());
+
+ dprintf(fd, " Devices loaded: %zu\n",
+ btif_config_cache.GetPersistentSections().size());
dprintf(fd, " File created/tagged: %s\n", btif_config_time_created);
dprintf(fd, " File source: %s\n", file_source->c_str());
}
diff --git a/btif/src/btif_config_cache.cc b/btif/src/btif_config_cache.cc
index dc4ae4d96..c5562aa86 100644
--- a/btif/src/btif_config_cache.cc
+++ b/btif/src/btif_config_cache.cc
@@ -148,21 +148,16 @@ bool BtifConfigCache::RemoveKey(const std::string& section_name,
}
}
-std::vector<std::string> BtifConfigCache::GetPersistentSectionNames() {
- std::vector<std::string> result;
- result.reserve(paired_devices_list_.sections.size());
- for (const auto& section : paired_devices_list_.sections) {
- result.emplace_back(section.name);
- }
- return result;
-}
-
/* clone persistent sections (Local Adapter sections, remote paired devices
* section,..) */
config_t BtifConfigCache::PersistentSectionCopy() {
return paired_devices_list_;
}
+const std::list<section_t>& BtifConfigCache::GetPersistentSections() {
+ return paired_devices_list_.sections;
+}
+
void BtifConfigCache::SetString(std::string section_name, std::string key,
std::string value) {
if (trim_new_line(section_name) || trim_new_line(key) ||
diff --git a/btif/src/btif_config_transcode.cc b/btif/src/btif_config_transcode.cc
index 090b4e15a..75ebd7738 100644
--- a/btif/src/btif_config_transcode.cc
+++ b/btif/src/btif_config_transcode.cc
@@ -29,14 +29,15 @@ std::unique_ptr<config_t> btif_config_transcode(const char* xml_filename) {
XMLDocument document;
int error = document.LoadFile(xml_filename);
if (error != XML_SUCCESS) {
- LOG_ERROR("%s unable to load XML file '%s': %d", __func__, xml_filename,
- error);
+ LOG_ERROR(LOG_TAG, "%s unable to load XML file '%s': %d", __func__,
+ xml_filename, error);
return NULL;
}
XMLElement* rootElement = document.RootElement();
if (!rootElement) {
- LOG_ERROR("%s unable to find root element; assuming corrupted config file.",
+ LOG_ERROR(LOG_TAG,
+ "%s unable to find root element; assuming corrupted config file.",
__func__);
return NULL;
}
diff --git a/btif/src/btif_core.cc b/btif/src/btif_core.cc
index 62e201338..aa77979ac 100644
--- a/btif/src/btif_core.cc
+++ b/btif/src/btif_core.cc
@@ -28,58 +28,91 @@
#define LOG_TAG "bt_btif_core"
-#include <signal.h>
-#include <sys/types.h>
-
#include <base/at_exit.h>
#include <base/bind.h>
+#include <base/run_loop.h>
#include <base/threading/platform_thread.h>
-#include <cstdint>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "btif/include/btif_av.h"
-#include "btif/include/btif_common.h"
-#include "btif/include/btif_config.h"
-#include "btif/include/btif_dm.h"
-#include "btif/include/btif_pan.h"
-#include "btif/include/btif_profile_queue.h"
-#include "btif/include/btif_sock.h"
-#include "btif/include/btif_storage.h"
-#include "btif/include/stack_manager.h"
+#include <base/threading/thread.h>
+#include <ctype.h>
+#include <dirent.h>
+#include <fcntl.h>
+#include <hardware/bluetooth.h>
+#include <stdlib.h>
+#include <string.h>
+#include <sys/stat.h>
+#include <sys/types.h>
+#include <unistd.h>
+
+#include "bt_common.h"
+#include "bt_utils.h"
+#include "bta_api.h"
+#include "bte.h"
+#include "btif_api.h"
+#include "btif_av.h"
+#include "btif_config.h"
+#include "btif_pan.h"
+#include "btif_profile_queue.h"
+#include "btif_sock.h"
+#include "btif_storage.h"
+#include "btif_uid.h"
+#include "btif_util.h"
+#include "btu.h"
#include "common/message_loop_thread.h"
#include "device/include/controller.h"
+#include "osi/include/fixed_queue.h"
#include "osi/include/future.h"
#include "osi/include/log.h"
+#include "osi/include/osi.h"
#include "osi/include/properties.h"
-#include "stack/include/a2dp_api.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_ble_api.h"
-#include "types/bluetooth/uuid.h"
+#include "stack_manager.h"
using base::PlatformThread;
using bluetooth::Uuid;
using bluetooth::common::MessageLoopThread;
-static void bt_jni_msg_ready(void* context);
-
/*******************************************************************************
* Constants & Macros
******************************************************************************/
#ifndef BTE_DID_CONF_FILE
// TODO(armansito): Find a better way than searching by a hardcoded path.
-#if defined(OS_GENERIC) && !defined(TARGET_FLOSS)
+#if defined(OS_GENERIC)
#define BTE_DID_CONF_FILE "bt_did.conf"
#else // !defined(OS_GENERIC)
#define BTE_DID_CONF_FILE "/etc/bluetooth/bt_did.conf"
#endif // defined(OS_GENERIC)
#endif // BTE_DID_CONF_FILE
-#define CODEC_TYPE_NUMBER 32
-#define DEFAULT_BUFFER_TIME (MAX_PCM_FRAME_NUM_PER_TICK * 2)
-#define MAXIMUM_BUFFER_TIME (MAX_PCM_FRAME_NUM_PER_TICK * 2)
-#define MINIMUM_BUFFER_TIME MAX_PCM_FRAME_NUM_PER_TICK
+/*******************************************************************************
+ * Local type definitions
+ ******************************************************************************/
+
+/* These type definitions are used when passing data from the HAL to BTIF
+ * context in the downstream path for the adapter and remote_device property
+ * APIs
+ */
+
+typedef struct {
+ RawAddress bd_addr;
+ bt_property_type_t type;
+} btif_storage_read_t;
+
+typedef struct {
+ RawAddress bd_addr;
+ bt_property_t prop;
+} btif_storage_write_t;
+
+typedef union {
+ btif_storage_read_t read_req;
+ btif_storage_write_t write_req;
+} btif_storage_req_t;
+
+typedef enum {
+ BTIF_CORE_STATE_DISABLED = 0,
+ BTIF_CORE_STATE_ENABLING,
+ BTIF_CORE_STATE_ENABLED,
+ BTIF_CORE_STATE_DISABLING
+} btif_core_state_t;
/*******************************************************************************
* Static variables
@@ -100,15 +133,47 @@ static base::AtExitManager* exit_manager;
static uid_set_t* uid_set;
/*******************************************************************************
+ * Static functions
+ ******************************************************************************/
+static void btif_jni_associate();
+static void btif_jni_disassociate();
+
+/* sends message to btif task */
+static void btif_sendmsg(void* p_msg);
+
+/*******************************************************************************
* Externs
******************************************************************************/
-void btif_dm_enable_service(tBTA_SERVICE_ID service_id, bool enable);
+extern fixed_queue_t* btu_hci_msg_queue;
+
+void btif_dm_execute_service_request(uint16_t event, char* p_param);
#ifdef BTIF_DM_OOB_TEST
void btif_dm_load_local_oob(void);
#endif
/*******************************************************************************
*
+ * Function btif_context_switched
+ *
+ * Description Callback used to execute transferred context callback
+ *
+ * p_msg : message to be executed in btif context
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+
+static void btif_context_switched(void* p_msg) {
+ BTIF_TRACE_VERBOSE("btif_context_switched");
+
+ tBTIF_CONTEXT_SWITCH_CBACK* p = (tBTIF_CONTEXT_SWITCH_CBACK*)p_msg;
+
+ /* each callback knows how to parse the data */
+ if (p->p_cb) p->p_cb(p->event, p->p_param);
+}
+
+/*******************************************************************************
+ *
* Function btif_transfer_context
*
* Description This function switches context to btif task
@@ -146,7 +211,8 @@ bt_status_t btif_transfer_context(tBTIF_CBACK* p_cback, uint16_t event,
memcpy(p_msg->p_param, p_params, param_len); /* callback parameter data */
}
- do_in_jni_thread(base::Bind(&bt_jni_msg_ready, p_msg));
+ btif_sendmsg(p_msg);
+
return BT_STATUS_SUCCESS;
}
@@ -171,9 +237,7 @@ bool is_on_jni_thread() {
return jni_thread.GetThreadId() == PlatformThread::CurrentId();
}
-btbase::AbstractMessageLoop* get_jni_message_loop() {
- return jni_thread.message_loop();
-}
+base::MessageLoop* get_jni_message_loop() { return jni_thread.message_loop(); }
/*******************************************************************************
*
@@ -202,8 +266,10 @@ int btif_is_enabled(void) {
(stack_manager_get_interface()->get_stack_is_running()));
}
-void btif_init_ok() {
+void btif_init_ok(UNUSED_ATTR uint16_t event, UNUSED_ATTR char* p_param) {
+ BTIF_TRACE_DEBUG("btif_task: received trigger stack init event");
btif_dm_load_ble_local_keys();
+ BTA_EnableBluetooth(bte_dm_evt);
}
/*******************************************************************************
@@ -217,9 +283,33 @@ void btif_init_ok() {
*
******************************************************************************/
static void bt_jni_msg_ready(void* context) {
- tBTIF_CONTEXT_SWITCH_CBACK* p = (tBTIF_CONTEXT_SWITCH_CBACK*)context;
- if (p->p_cb) p->p_cb(p->event, p->p_param);
- osi_free(p);
+ BT_HDR* p_msg = (BT_HDR*)context;
+
+ BTIF_TRACE_VERBOSE("btif task fetched event %x", p_msg->event);
+
+ switch (p_msg->event) {
+ case BT_EVT_CONTEXT_SWITCH_EVT:
+ btif_context_switched(p_msg);
+ break;
+ default:
+ BTIF_TRACE_ERROR("unhandled btif event (%d)", p_msg->event & BT_EVT_MASK);
+ break;
+ }
+ osi_free(p_msg);
+}
+
+/*******************************************************************************
+ *
+ * Function btif_sendmsg
+ *
+ * Description Sends msg to BTIF task
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+
+void btif_sendmsg(void* p_msg) {
+ do_in_jni_thread(base::Bind(&bt_jni_msg_ready, p_msg));
}
/*******************************************************************************
@@ -232,29 +322,15 @@ static void bt_jni_msg_ready(void* context) {
*
******************************************************************************/
bt_status_t btif_init_bluetooth() {
- LOG_INFO("%s entered", __func__);
+ LOG_INFO(LOG_TAG, "%s entered", __func__);
exit_manager = new base::AtExitManager();
+ bte_main_boot_entry();
jni_thread.StartUp();
- invoke_thread_evt_cb(ASSOCIATE_JVM);
- LOG_INFO("%s finished", __func__);
+ jni_thread.DoInThread(FROM_HERE, base::Bind(btif_jni_associate));
+ LOG_INFO(LOG_TAG, "%s finished", __func__);
return BT_STATUS_SUCCESS;
}
-static bool btif_is_a2dp_offload_enabled() {
- char value_sup[PROPERTY_VALUE_MAX] = {'\0'};
- char value_dis[PROPERTY_VALUE_MAX] = {'\0'};
- bool a2dp_offload_enabled_;
-
- osi_property_get("ro.bluetooth.a2dp_offload.supported", value_sup, "false");
- osi_property_get("persist.bluetooth.a2dp_offload.disabled", value_dis,
- "false");
- a2dp_offload_enabled_ =
- (strcmp(value_sup, "true") == 0) && (strcmp(value_dis, "false") == 0);
- BTIF_TRACE_DEBUG("a2dp_offload.enable = %d", a2dp_offload_enabled_);
-
- return a2dp_offload_enabled_;
-}
-
/*******************************************************************************
*
* Function btif_enable_bluetooth_evt
@@ -266,19 +342,20 @@ static bool btif_is_a2dp_offload_enabled() {
*
******************************************************************************/
-void btif_enable_bluetooth_evt() {
+void btif_enable_bluetooth_evt(tBTA_STATUS status) {
+ LOG_INFO(LOG_TAG, "%s entered: status %d", __func__, status);
+
/* Fetch the local BD ADDR */
RawAddress local_bd_addr = *controller_get_interface()->get_address();
std::string bdstr = local_bd_addr.ToString();
char val[PROPERTY_VALUE_MAX] = "";
- int val_size = PROPERTY_VALUE_MAX;
- if (!btif_config_get_str("Adapter", "Address", val, &val_size) ||
- strcmp(bdstr.c_str(), val) != 0) {
- // We failed to get an address or the one in the config file does not match
- // the address given by the controller interface. Update the config cache
- LOG_INFO("%s: Storing '%s' into the config file", __func__, bdstr.c_str());
+ int val_size = 0;
+ if ((btif_config_get_str("Adapter", "Address", val, &val_size) == 0) ||
+ strcmp(bdstr.c_str(), val) == 0) {
+ // This address is not present in the config file, save it there.
+ BTIF_TRACE_WARNING("%s: Saving the Adapter Address", __func__);
btif_config_set_str("Adapter", "Address", bdstr.c_str());
btif_config_save();
@@ -287,29 +364,94 @@ void btif_enable_bluetooth_evt() {
prop.type = BT_PROPERTY_BDADDR;
prop.val = (void*)&local_bd_addr;
prop.len = sizeof(RawAddress);
- invoke_adapter_properties_cb(BT_STATUS_SUCCESS, 1, &prop);
+ HAL_CBACK(bt_hal_cbacks, adapter_properties_cb, BT_STATUS_SUCCESS, 1,
+ &prop);
}
+ bte_main_postload_cfg();
+
/* callback to HAL */
- uid_set = uid_set_create();
+ if (status == BTA_SUCCESS) {
+ uid_set = uid_set_create();
- btif_dm_init(uid_set);
+ btif_dm_init(uid_set);
- /* init rfcomm & l2cap api */
- btif_sock_init(uid_set);
+ /* init rfcomm & l2cap api */
+ btif_sock_init(uid_set);
- /* init pan */
- btif_pan_init();
+ /* init pan */
+ btif_pan_init();
- /* load did configuration */
- bte_load_did_conf(BTE_DID_CONF_FILE);
+ /* load did configuration */
+ bte_load_did_conf(BTE_DID_CONF_FILE);
#ifdef BTIF_DM_OOB_TEST
- btif_dm_load_local_oob();
+ btif_dm_load_local_oob();
#endif
+ future_ready(stack_manager_get_hack_future(), FUTURE_SUCCESS);
+ } else {
+ /* cleanup rfcomm & l2cap api */
+ btif_sock_cleanup();
+
+ btif_pan_cleanup();
+
+ future_ready(stack_manager_get_hack_future(), FUTURE_FAIL);
+ }
+
+ LOG_INFO(LOG_TAG, "%s finished", __func__);
+}
+
+/*******************************************************************************
+ *
+ * Function btif_disable_bluetooth
+ *
+ * Description Inititates shutdown of Bluetooth system.
+ * Any active links will be dropped and device entering
+ * non connectable/discoverable mode
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+bt_status_t btif_disable_bluetooth() {
+ LOG_INFO(LOG_TAG, "%s entered", __func__);
+
+ do_in_main_thread(FROM_HERE, base::Bind(&btm_ble_multi_adv_cleanup));
+ // TODO(jpawlowski): this should do whole BTA_VendorCleanup(), but it would
+ // kill the stack now.
+
+ btif_dm_on_disable();
+ /* cleanup rfcomm & l2cap api */
+ btif_sock_cleanup();
+ btif_pan_cleanup();
+ BTA_DisableBluetooth();
+
+ LOG_INFO(LOG_TAG, "%s finished", __func__);
+
+ return BT_STATUS_SUCCESS;
+}
+
+/*******************************************************************************
+ *
+ * Function btif_disable_bluetooth_evt
+ *
+ * Description Event notifying BT disable is now complete.
+ * Terminates main stack tasks and notifies HAL
+ * user with updated BT state.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+
+void btif_disable_bluetooth_evt() {
+ LOG_INFO(LOG_TAG, "%s entered", __func__);
+
+ bte_main_disable();
+
+ /* callback to HAL */
future_ready(stack_manager_get_hack_future(), FUTURE_SUCCESS);
- LOG_INFO("Bluetooth enable event completed");
+
+ LOG_INFO(LOG_TAG, "%s finished", __func__);
}
/*******************************************************************************
@@ -323,15 +465,17 @@ void btif_enable_bluetooth_evt() {
******************************************************************************/
bt_status_t btif_cleanup_bluetooth() {
- LOG_INFO("%s entered", __func__);
+ LOG_INFO(LOG_TAG, "%s entered", __func__);
+ do_in_main_thread(FROM_HERE, base::Bind(&BTA_VendorCleanup));
btif_dm_cleanup();
- invoke_thread_evt_cb(DISASSOCIATE_JVM);
+ jni_thread.DoInThread(FROM_HERE, base::BindOnce(btif_jni_disassociate));
btif_queue_release();
jni_thread.ShutDown();
+ bte_main_cleanup();
delete exit_manager;
exit_manager = nullptr;
btif_dut_mode = 0;
- LOG_INFO("%s finished", __func__);
+ LOG_INFO(LOG_TAG, "%s finished", __func__);
return BT_STATUS_SUCCESS;
}
@@ -356,17 +500,24 @@ static void btif_dut_mode_cback(UNUSED_ATTR tBTM_VSC_CMPL* p) {
* Description Configure Test Mode - 'enable' to 1 puts the device in test
* mode and 0 exits test mode
*
+ * Returns BT_STATUS_SUCCESS on success
+ *
******************************************************************************/
-void btif_dut_mode_configure(uint8_t enable) {
+bt_status_t btif_dut_mode_configure(uint8_t enable) {
BTIF_TRACE_DEBUG("%s", __func__);
+ if (!stack_manager_get_interface()->get_stack_is_running()) {
+ BTIF_TRACE_ERROR("btif_dut_mode_configure : Bluetooth not enabled");
+ return BT_STATUS_NOT_READY;
+ }
+
btif_dut_mode = enable;
if (enable == 1) {
BTA_EnableTestMode();
} else {
- // Can't do in process reset anyways - just quit
- kill(getpid(), SIGKILL);
+ BTA_DisableTestMode();
}
+ return BT_STATUS_SUCCESS;
}
/*******************************************************************************
@@ -375,10 +526,18 @@ void btif_dut_mode_configure(uint8_t enable) {
*
* Description Sends a HCI Vendor specific command to the controller
*
+ * Returns BT_STATUS_SUCCESS on success
+ *
******************************************************************************/
-void btif_dut_mode_send(uint16_t opcode, uint8_t* buf, uint8_t len) {
+bt_status_t btif_dut_mode_send(uint16_t opcode, uint8_t* buf, uint8_t len) {
+ /* TODO: Check that opcode is a vendor command group */
BTIF_TRACE_DEBUG("%s", __func__);
+ if (!btif_is_dut_mode()) {
+ BTIF_TRACE_ERROR("Bluedroid HAL needs to be init with test_mode set to 1.");
+ return BT_STATUS_FAIL;
+ }
BTM_VendorSpecificCommand(opcode, len, buf, btif_dut_mode_cback);
+ return BT_STATUS_SUCCESS;
}
/*****************************************************************************
@@ -457,7 +616,9 @@ static bt_status_t btif_in_get_adapter_properties(void) {
btif_storage_get_adapter_property(&properties[num_props]);
num_props++;
- invoke_adapter_properties_cb(BT_STATUS_SUCCESS, num_props, properties);
+ HAL_CBACK(bt_hal_cbacks, adapter_properties_cb, BT_STATUS_SUCCESS, num_props,
+ properties);
+
return BT_STATUS_SUCCESS;
}
@@ -502,29 +663,166 @@ static bt_status_t btif_in_get_remote_device_properties(RawAddress* bd_addr) {
&remote_properties[num_props]);
num_props++;
- invoke_remote_device_properties_cb(BT_STATUS_SUCCESS, *bd_addr, num_props,
- remote_properties);
+ HAL_CBACK(bt_hal_cbacks, remote_device_properties_cb, BT_STATUS_SUCCESS,
+ bd_addr, num_props, remote_properties);
return BT_STATUS_SUCCESS;
}
-static void btif_core_storage_adapter_notify_empty_success() {
- invoke_adapter_properties_cb(BT_STATUS_SUCCESS, 0, NULL);
+/*******************************************************************************
+ *
+ * Function execute_storage_request
+ *
+ * Description Executes adapter storage request in BTIF context
+ *
+ * Returns bt_status_t
+ *
+ ******************************************************************************/
+
+static void execute_storage_request(uint16_t event, char* p_param) {
+ bt_status_t status = BT_STATUS_SUCCESS;
+
+ BTIF_TRACE_EVENT("execute storage request event : %d", event);
+
+ switch (event) {
+ case BTIF_CORE_STORAGE_ADAPTER_WRITE: {
+ btif_storage_req_t* p_req = (btif_storage_req_t*)p_param;
+ bt_property_t* p_prop = &(p_req->write_req.prop);
+ BTIF_TRACE_EVENT("type: %d, len %d, 0x%x", p_prop->type, p_prop->len,
+ p_prop->val);
+
+ status = btif_storage_set_adapter_property(p_prop);
+ HAL_CBACK(bt_hal_cbacks, adapter_properties_cb, status, 1, p_prop);
+ } break;
+
+ case BTIF_CORE_STORAGE_ADAPTER_READ: {
+ btif_storage_req_t* p_req = (btif_storage_req_t*)p_param;
+ char buf[512];
+ bt_property_t prop;
+ prop.type = p_req->read_req.type;
+ prop.val = (void*)buf;
+ prop.len = sizeof(buf);
+ if (prop.type == BT_PROPERTY_LOCAL_LE_FEATURES) {
+ tBTM_BLE_VSC_CB cmn_vsc_cb;
+ bt_local_le_features_t local_le_features;
+
+ /* LE features are not stored in storage. Should be retrived from stack
+ */
+ BTM_BleGetVendorCapabilities(&cmn_vsc_cb);
+ local_le_features.local_privacy_enabled = BTM_BleLocalPrivacyEnabled();
+
+ prop.len = sizeof(bt_local_le_features_t);
+ if (cmn_vsc_cb.filter_support == 1)
+ local_le_features.max_adv_filter_supported = cmn_vsc_cb.max_filter;
+ else
+ local_le_features.max_adv_filter_supported = 0;
+ local_le_features.max_adv_instance = cmn_vsc_cb.adv_inst_max;
+ local_le_features.max_irk_list_size = cmn_vsc_cb.max_irk_list_sz;
+ local_le_features.rpa_offload_supported = cmn_vsc_cb.rpa_offloading;
+ local_le_features.scan_result_storage_size =
+ cmn_vsc_cb.tot_scan_results_strg;
+ local_le_features.activity_energy_info_supported =
+ cmn_vsc_cb.energy_support;
+ local_le_features.version_supported = cmn_vsc_cb.version_supported;
+ local_le_features.total_trackable_advertisers =
+ cmn_vsc_cb.total_trackable_advertisers;
+
+ local_le_features.extended_scan_support =
+ cmn_vsc_cb.extended_scan_support > 0;
+ local_le_features.debug_logging_supported =
+ cmn_vsc_cb.debug_logging_supported > 0;
+ memcpy(prop.val, &local_le_features, prop.len);
+ } else {
+ status = btif_storage_get_adapter_property(&prop);
+ }
+ HAL_CBACK(bt_hal_cbacks, adapter_properties_cb, status, 1, &prop);
+ } break;
+
+ case BTIF_CORE_STORAGE_ADAPTER_READ_ALL: {
+ status = btif_in_get_adapter_properties();
+ } break;
+
+ case BTIF_CORE_STORAGE_NOTIFY_STATUS: {
+ HAL_CBACK(bt_hal_cbacks, adapter_properties_cb, status, 0, NULL);
+ } break;
+
+ default:
+ BTIF_TRACE_ERROR("%s invalid event id (%d)", __func__, event);
+ break;
+ }
}
-static void btif_core_storage_adapter_write(bt_property_t* prop) {
- BTIF_TRACE_EVENT("type: %d, len %d, 0x%x", prop->type, prop->len, prop->val);
- bt_status_t status = btif_storage_set_adapter_property(prop);
- invoke_adapter_properties_cb(status, 1, prop);
+static void execute_storage_remote_request(uint16_t event, char* p_param) {
+ bt_status_t status = BT_STATUS_FAIL;
+ bt_property_t prop;
+
+ BTIF_TRACE_EVENT("execute storage remote request event : %d", event);
+
+ switch (event) {
+ case BTIF_CORE_STORAGE_REMOTE_READ: {
+ char buf[1024];
+ btif_storage_req_t* p_req = (btif_storage_req_t*)p_param;
+ prop.type = p_req->read_req.type;
+ prop.val = (void*)buf;
+ prop.len = sizeof(buf);
+
+ status = btif_storage_get_remote_device_property(
+ &(p_req->read_req.bd_addr), &prop);
+ HAL_CBACK(bt_hal_cbacks, remote_device_properties_cb, status,
+ &(p_req->read_req.bd_addr), 1, &prop);
+ } break;
+ case BTIF_CORE_STORAGE_REMOTE_WRITE: {
+ btif_storage_req_t* p_req = (btif_storage_req_t*)p_param;
+ status = btif_storage_set_remote_device_property(
+ &(p_req->write_req.bd_addr), &(p_req->write_req.prop));
+ } break;
+ case BTIF_CORE_STORAGE_REMOTE_READ_ALL: {
+ btif_storage_req_t* p_req = (btif_storage_req_t*)p_param;
+ btif_in_get_remote_device_properties(&p_req->read_req.bd_addr);
+ } break;
+ }
}
void btif_adapter_properties_evt(bt_status_t status, uint32_t num_props,
bt_property_t* p_props) {
- invoke_adapter_properties_cb(status, num_props, p_props);
+ HAL_CBACK(bt_hal_cbacks, adapter_properties_cb, status, num_props, p_props);
}
void btif_remote_properties_evt(bt_status_t status, RawAddress* remote_addr,
uint32_t num_props, bt_property_t* p_props) {
- invoke_remote_device_properties_cb(status, *remote_addr, num_props, p_props);
+ HAL_CBACK(bt_hal_cbacks, remote_device_properties_cb, status, remote_addr,
+ num_props, p_props);
+}
+
+/*******************************************************************************
+ *
+ * Function btif_in_storage_request_copy_cb
+ *
+ * Description Switch context callback function to perform the deep copy for
+ * both the adapter and remote_device property API
+ *
+ * Returns None
+ *
+ ******************************************************************************/
+static void btif_in_storage_request_copy_cb(uint16_t event, char* p_new_buf,
+ char* p_old_buf) {
+ btif_storage_req_t* new_req = (btif_storage_req_t*)p_new_buf;
+ btif_storage_req_t* old_req = (btif_storage_req_t*)p_old_buf;
+
+ BTIF_TRACE_EVENT("%s", __func__);
+ switch (event) {
+ case BTIF_CORE_STORAGE_REMOTE_WRITE:
+ case BTIF_CORE_STORAGE_ADAPTER_WRITE: {
+ new_req->write_req.bd_addr = old_req->write_req.bd_addr;
+ /* Copy the member variables one at a time */
+ new_req->write_req.prop.type = old_req->write_req.prop.type;
+ new_req->write_req.prop.len = old_req->write_req.prop.len;
+
+ new_req->write_req.prop.val =
+ (uint8_t*)(p_new_buf + sizeof(btif_storage_req_t));
+ memcpy(new_req->write_req.prop.val, old_req->write_req.prop.val,
+ old_req->write_req.prop.len);
+ } break;
+ }
}
/*******************************************************************************
@@ -533,12 +831,18 @@ void btif_remote_properties_evt(bt_status_t status, RawAddress* remote_addr,
*
* Description Fetch all available properties (local & remote)
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_get_adapter_properties(void) {
+bt_status_t btif_get_adapter_properties(void) {
BTIF_TRACE_EVENT("%s", __func__);
- btif_in_get_adapter_properties();
+ if (!btif_is_enabled()) return BT_STATUS_NOT_READY;
+
+ return btif_transfer_context(execute_storage_request,
+ BTIF_CORE_STORAGE_ADAPTER_READ_ALL, NULL, 0,
+ NULL);
}
/*******************************************************************************
@@ -547,99 +851,26 @@ void btif_get_adapter_properties(void) {
*
* Description Fetches property value from local cache
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_get_adapter_property(bt_property_type_t type) {
+bt_status_t btif_get_adapter_property(bt_property_type_t type) {
+ btif_storage_req_t req;
+
BTIF_TRACE_EVENT("%s %d", __func__, type);
- bt_status_t status = BT_STATUS_SUCCESS;
- char buf[512];
- bt_property_t prop;
- prop.type = type;
- prop.val = (void*)buf;
- prop.len = sizeof(buf);
- if (prop.type == BT_PROPERTY_LOCAL_LE_FEATURES) {
- tBTM_BLE_VSC_CB cmn_vsc_cb;
- bt_local_le_features_t local_le_features;
-
- /* LE features are not stored in storage. Should be retrived from stack
- */
- BTM_BleGetVendorCapabilities(&cmn_vsc_cb);
- local_le_features.local_privacy_enabled = BTM_BleLocalPrivacyEnabled();
-
- prop.len = sizeof(bt_local_le_features_t);
- if (cmn_vsc_cb.filter_support == 1)
- local_le_features.max_adv_filter_supported = cmn_vsc_cb.max_filter;
- else
- local_le_features.max_adv_filter_supported = 0;
- local_le_features.max_adv_instance = cmn_vsc_cb.adv_inst_max;
- local_le_features.max_irk_list_size = cmn_vsc_cb.max_irk_list_sz;
- local_le_features.rpa_offload_supported = cmn_vsc_cb.rpa_offloading;
- local_le_features.scan_result_storage_size =
- cmn_vsc_cb.tot_scan_results_strg;
- local_le_features.activity_energy_info_supported =
- cmn_vsc_cb.energy_support;
- local_le_features.version_supported = cmn_vsc_cb.version_supported;
- local_le_features.total_trackable_advertisers =
- cmn_vsc_cb.total_trackable_advertisers;
-
- local_le_features.extended_scan_support =
- cmn_vsc_cb.extended_scan_support > 0;
- local_le_features.debug_logging_supported =
- cmn_vsc_cb.debug_logging_supported > 0;
- memcpy(prop.val, &local_le_features, prop.len);
- } else if (prop.type == BT_PROPERTY_DYNAMIC_AUDIO_BUFFER) {
- tBTM_BLE_VSC_CB cmn_vsc_cb;
- bt_dynamic_audio_buffer_item_t dynamic_audio_buffer_item;
-
- BTM_BleGetVendorCapabilities(&cmn_vsc_cb);
-
- prop.len = sizeof(bt_dynamic_audio_buffer_item_t);
- if (btif_is_a2dp_offload_enabled() == false) {
- BTIF_TRACE_DEBUG("%s Get buffer millis for A2DP software encoding",
- __func__);
- for (int i = 0; i < CODEC_TYPE_NUMBER; i++) {
- dynamic_audio_buffer_item.dab_item[i] = {
- .default_buffer_time = DEFAULT_BUFFER_TIME,
- .maximum_buffer_time = MAXIMUM_BUFFER_TIME,
- .minimum_buffer_time = MINIMUM_BUFFER_TIME};
- }
- memcpy(prop.val, &dynamic_audio_buffer_item, prop.len);
- } else {
- if (cmn_vsc_cb.dynamic_audio_buffer_support != 0) {
- BTIF_TRACE_DEBUG("%s Get buffer millis for A2DP Offload", __func__);
- tBTM_BT_DYNAMIC_AUDIO_BUFFER_CB
- bt_dynamic_audio_buffer_cb[CODEC_TYPE_NUMBER];
- BTM_BleGetDynamicAudioBuffer(bt_dynamic_audio_buffer_cb);
-
- for (int i = 0; i < CODEC_TYPE_NUMBER; i++) {
- dynamic_audio_buffer_item.dab_item[i] = {
- .default_buffer_time =
- bt_dynamic_audio_buffer_cb[i].default_buffer_time,
- .maximum_buffer_time =
- bt_dynamic_audio_buffer_cb[i].maximum_buffer_time,
- .minimum_buffer_time =
- bt_dynamic_audio_buffer_cb[i].minimum_buffer_time};
- }
- memcpy(prop.val, &dynamic_audio_buffer_item, prop.len);
- } else {
- BTIF_TRACE_DEBUG("%s Don't support Dynamic Audio Buffer", __func__);
- }
- }
- } else {
- status = btif_storage_get_adapter_property(&prop);
- }
- invoke_adapter_properties_cb(status, 1, &prop);
-}
+ /* Allow get_adapter_property only for BDADDR and BDNAME if BT is disabled */
+ if (!btif_is_enabled() && (type != BT_PROPERTY_BDADDR) &&
+ (type != BT_PROPERTY_BDNAME) && (type != BT_PROPERTY_CLASS_OF_DEVICE))
+ return BT_STATUS_NOT_READY;
+
+ req.read_req.bd_addr = RawAddress::kEmpty;
+ req.read_req.type = type;
-bt_property_t* property_deep_copy(const bt_property_t* prop) {
- bt_property_t* copy =
- (bt_property_t*)osi_calloc(sizeof(bt_property_t) + prop->len);
- copy->type = prop->type;
- copy->len = prop->len;
- copy->val = (uint8_t*)(copy + 1);
- memcpy(copy->val, prop->val, prop->len);
- return copy;
+ return btif_transfer_context(execute_storage_request,
+ BTIF_CORE_STORAGE_ADAPTER_READ, (char*)&req,
+ sizeof(btif_storage_req_t), NULL);
}
/*******************************************************************************
@@ -653,16 +884,23 @@ bt_property_t* property_deep_copy(const bt_property_t* prop) {
*
******************************************************************************/
-void btif_set_adapter_property(bt_property_t* property) {
+bt_status_t btif_set_adapter_property(const bt_property_t* property) {
+ btif_storage_req_t req;
+ bt_status_t status = BT_STATUS_SUCCESS;
+ int storage_req_id = BTIF_CORE_STORAGE_NOTIFY_STATUS; /* default */
+ char bd_name[BTM_MAX_LOC_BD_NAME_LEN + 1];
+ uint16_t name_len = 0;
+
BTIF_TRACE_EVENT("btif_set_adapter_property type: %d, len %d, 0x%x",
property->type, property->len, property->val);
+ if (!btif_is_enabled()) return BT_STATUS_NOT_READY;
+
switch (property->type) {
case BT_PROPERTY_BDNAME: {
- char bd_name[BTM_MAX_LOC_BD_NAME_LEN + 1];
- uint16_t name_len = property->len > BTM_MAX_LOC_BD_NAME_LEN
- ? BTM_MAX_LOC_BD_NAME_LEN
- : property->len;
+ name_len = property->len > BTM_MAX_LOC_BD_NAME_LEN
+ ? BTM_MAX_LOC_BD_NAME_LEN
+ : property->len;
memcpy(bd_name, property->val, name_len);
bd_name[name_len] = '\0';
@@ -670,22 +908,46 @@ void btif_set_adapter_property(bt_property_t* property) {
BTA_DmSetDeviceName((char*)bd_name);
- btif_core_storage_adapter_write(property);
+ storage_req_id = BTIF_CORE_STORAGE_ADAPTER_WRITE;
} break;
case BT_PROPERTY_ADAPTER_SCAN_MODE: {
bt_scan_mode_t mode = *(bt_scan_mode_t*)property->val;
+ tBTA_DM_DISC disc_mode;
+ tBTA_DM_CONN conn_mode;
+
+ switch (mode) {
+ case BT_SCAN_MODE_NONE:
+ disc_mode = BTA_DM_NON_DISC;
+ conn_mode = BTA_DM_NON_CONN;
+ break;
+
+ case BT_SCAN_MODE_CONNECTABLE:
+ disc_mode = BTA_DM_NON_DISC;
+ conn_mode = BTA_DM_CONN;
+ break;
+
+ case BT_SCAN_MODE_CONNECTABLE_DISCOVERABLE:
+ disc_mode = BTA_DM_GENERAL_DISC;
+ conn_mode = BTA_DM_CONN;
+ break;
+
+ default:
+ BTIF_TRACE_ERROR("invalid scan mode (0x%x)", mode);
+ return BT_STATUS_PARM_INVALID;
+ }
+
BTIF_TRACE_EVENT("set property scan mode : %x", mode);
- if (BTA_DmSetVisibility(mode)) {
- btif_core_storage_adapter_write(property);
- }
+ BTA_DmSetVisibility(disc_mode, conn_mode, BTA_DM_IGNORE, BTA_DM_IGNORE);
+
+ storage_req_id = BTIF_CORE_STORAGE_ADAPTER_WRITE;
} break;
case BT_PROPERTY_ADAPTER_DISCOVERY_TIMEOUT: {
/* Nothing to do beside store the value in NV. Java
will change the SCAN_MODE property after setting timeout,
if required */
- btif_core_storage_adapter_write(property);
+ storage_req_id = BTIF_CORE_STORAGE_ADAPTER_WRITE;
} break;
case BT_PROPERTY_CLASS_OF_DEVICE: {
DEV_CLASS dev_class;
@@ -695,18 +957,42 @@ void btif_set_adapter_property(bt_property_t* property) {
dev_class[1], dev_class[2]);
BTM_SetDeviceClass(dev_class);
- btif_core_storage_adapter_notify_empty_success();
} break;
+ case BT_PROPERTY_BDADDR:
+ case BT_PROPERTY_UUIDS:
+ case BT_PROPERTY_ADAPTER_BONDED_DEVICES:
+ case BT_PROPERTY_REMOTE_FRIENDLY_NAME:
+ /* no write support through HAL, these properties are only populated from
+ * BTA events */
+ status = BT_STATUS_FAIL;
+ break;
case BT_PROPERTY_LOCAL_IO_CAPS:
case BT_PROPERTY_LOCAL_IO_CAPS_BLE: {
// Changing IO Capability of stack at run-time is not currently supported.
// This call changes the stored value which will affect the stack next
// time it starts up.
- btif_core_storage_adapter_write(property);
+ storage_req_id = BTIF_CORE_STORAGE_ADAPTER_WRITE;
} break;
default:
+ BTIF_TRACE_ERROR("btif_get_adapter_property : invalid type %d",
+ property->type);
+ status = BT_STATUS_FAIL;
break;
}
+
+ if (storage_req_id != BTIF_CORE_STORAGE_NO_ACTION) {
+ /* pass on to storage for updating local database */
+
+ req.write_req.bd_addr = RawAddress::kEmpty;
+ memcpy(&(req.write_req.prop), property, sizeof(bt_property_t));
+
+ return btif_transfer_context(execute_storage_request, storage_req_id,
+ (char*)&req,
+ sizeof(btif_storage_req_t) + property->len,
+ btif_in_storage_request_copy_cb);
+ }
+
+ return status;
}
/*******************************************************************************
@@ -715,18 +1001,20 @@ void btif_set_adapter_property(bt_property_t* property) {
*
* Description Fetches the remote device property from the NVRAM
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_get_remote_device_property(RawAddress remote_addr,
- bt_property_type_t type) {
- char buf[1024];
- bt_property_t prop;
- prop.type = type;
- prop.val = (void*)buf;
- prop.len = sizeof(buf);
+bt_status_t btif_get_remote_device_property(RawAddress* remote_addr,
+ bt_property_type_t type) {
+ btif_storage_req_t req;
- bt_status_t status =
- btif_storage_get_remote_device_property(&remote_addr, &prop);
- invoke_remote_device_properties_cb(status, remote_addr, 1, &prop);
+ if (!btif_is_enabled()) return BT_STATUS_NOT_READY;
+
+ req.read_req.bd_addr = *remote_addr;
+ req.read_req.type = type;
+ return btif_transfer_context(execute_storage_remote_request,
+ BTIF_CORE_STORAGE_REMOTE_READ, (char*)&req,
+ sizeof(btif_storage_req_t), NULL);
}
/*******************************************************************************
@@ -735,9 +1023,18 @@ void btif_get_remote_device_property(RawAddress remote_addr,
*
* Description Fetches all the remote device properties from NVRAM
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_get_remote_device_properties(RawAddress remote_addr) {
- btif_in_get_remote_device_properties(&remote_addr);
+bt_status_t btif_get_remote_device_properties(RawAddress* remote_addr) {
+ btif_storage_req_t req;
+
+ if (!btif_is_enabled()) return BT_STATUS_NOT_READY;
+
+ req.read_req.bd_addr = *remote_addr;
+ return btif_transfer_context(execute_storage_remote_request,
+ BTIF_CORE_STORAGE_REMOTE_READ_ALL, (char*)&req,
+ sizeof(btif_storage_req_t), NULL);
}
/*******************************************************************************
@@ -748,10 +1045,39 @@ void btif_get_remote_device_properties(RawAddress remote_addr) {
* Currently, BT_PROPERTY_REMOTE_FRIENDLY_NAME is the only
* remote device property that can be set
*
+ * Returns bt_status_t
+ *
+ ******************************************************************************/
+bt_status_t btif_set_remote_device_property(RawAddress* remote_addr,
+ const bt_property_t* property) {
+ btif_storage_req_t req;
+
+ if (!btif_is_enabled()) return BT_STATUS_NOT_READY;
+
+ req.write_req.bd_addr = *remote_addr;
+ memcpy(&(req.write_req.prop), property, sizeof(bt_property_t));
+
+ return btif_transfer_context(execute_storage_remote_request,
+ BTIF_CORE_STORAGE_REMOTE_WRITE, (char*)&req,
+ sizeof(btif_storage_req_t) + property->len,
+ btif_in_storage_request_copy_cb);
+}
+
+/*******************************************************************************
+ *
+ * Function btif_get_remote_service_record
+ *
+ * Description Looks up the service matching uuid on the remote device
+ * and fetches the SCN and service_name if the UUID is found
+ *
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_set_remote_device_property(RawAddress* remote_addr,
- bt_property_t* property) {
- btif_storage_set_remote_device_property(remote_addr, property);
+bt_status_t btif_get_remote_service_record(const RawAddress& remote_addr,
+ const Uuid& uuid) {
+ if (!btif_is_enabled()) return BT_STATUS_NOT_READY;
+
+ return btif_dm_get_remote_service_record(remote_addr, uuid);
}
/*******************************************************************************
@@ -776,16 +1102,30 @@ tBTA_SERVICE_MASK btif_get_enabled_services_mask(void) {
* Upon BT enable, BTIF core shall invoke the BTA APIs to
* enable the profiles
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_enable_service(tBTA_SERVICE_ID service_id) {
+bt_status_t btif_enable_service(tBTA_SERVICE_ID service_id) {
+ tBTA_SERVICE_ID* p_id = &service_id;
+
+ /* If BT is enabled, we need to switch to BTIF context and trigger the
+ * enable for that profile
+ *
+ * Otherwise, we just set the flag. On BT_Enable, the DM will trigger
+ * enable for the profiles that have been enabled */
+
btif_enabled_services |= (1 << service_id);
BTIF_TRACE_DEBUG("%s: current services:0x%x", __func__,
btif_enabled_services);
if (btif_is_enabled()) {
- btif_dm_enable_service(service_id, true);
+ btif_transfer_context(btif_dm_execute_service_request,
+ BTIF_DM_ENABLE_SERVICE, (char*)p_id,
+ sizeof(tBTA_SERVICE_ID), NULL);
}
+
+ return BT_STATUS_SUCCESS;
}
/*******************************************************************************
*
@@ -795,88 +1135,38 @@ void btif_enable_service(tBTA_SERVICE_ID service_id) {
* Upon BT disable, BTIF core shall invoke the BTA APIs to
* disable the profiles
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_disable_service(tBTA_SERVICE_ID service_id) {
+bt_status_t btif_disable_service(tBTA_SERVICE_ID service_id) {
+ tBTA_SERVICE_ID* p_id = &service_id;
+
+ /* If BT is enabled, we need to switch to BTIF context and trigger the
+ * disable for that profile so that the appropriate uuid_property_changed will
+ * be triggerred. Otherwise, we just need to clear the service_id in the mask
+ */
+
btif_enabled_services &= (tBTA_SERVICE_MASK)(~(1 << service_id));
BTIF_TRACE_DEBUG("%s: Current Services:0x%x", __func__,
btif_enabled_services);
if (btif_is_enabled()) {
- btif_dm_enable_service(service_id, false);
- }
-}
-
-void DynamicAudiobufferSizeCompleteCallback(tBTM_VSC_CMPL* p_vsc_cmpl_params) {
- LOG(INFO) << __func__;
-
- if (p_vsc_cmpl_params->param_len < 1) {
- LOG(ERROR) << __func__
- << ": The length of returned parameters is less than 1";
- return;
- }
- uint8_t* p_event_param_buf = p_vsc_cmpl_params->p_param_buf;
- uint8_t status = 0xff;
- uint8_t opcode = 0xff;
- uint16_t respond_buffer_time = 0xffff;
-
- // [Return Parameter] | [Size] | [Purpose]
- // Status | 1 octet | Command complete status
- // Dynamic_Audio_Buffer_opcode| 1 octet | 0x02 - Set buffer time
- // Audio_Codec_Buffer_Time | 2 octet | Current buffer time
- STREAM_TO_UINT8(status, p_event_param_buf);
- if (status != HCI_SUCCESS) {
- LOG(ERROR) << __func__
- << ": Fail to configure DFTB. status: " << loghex(status);
- return;
- }
-
- if (p_vsc_cmpl_params->param_len != 4) {
- LOG(FATAL) << __func__
- << ": The length of returned parameters is not equal to 4: "
- << std::to_string(p_vsc_cmpl_params->param_len);
- return;
+ btif_transfer_context(btif_dm_execute_service_request,
+ BTIF_DM_DISABLE_SERVICE, (char*)p_id,
+ sizeof(tBTA_SERVICE_ID), NULL);
}
- STREAM_TO_UINT8(opcode, p_event_param_buf);
- LOG(INFO) << __func__ << ": opcode = " << loghex(opcode);
-
- if (opcode == 0x02) {
- STREAM_TO_UINT16(respond_buffer_time, p_event_param_buf);
- LOG(INFO) << __func__
- << ": Succeed to configure Media Tx Buffer, used_buffer_time = "
- << loghex(respond_buffer_time);
- }
+ return BT_STATUS_SUCCESS;
}
-bt_status_t btif_set_dynamic_audio_buffer_size(int codec, int size) {
- BTIF_TRACE_DEBUG("%s", __func__);
-
- tBTM_BLE_VSC_CB cmn_vsc_cb;
- BTM_BleGetVendorCapabilities(&cmn_vsc_cb);
-
- if (!btif_av_is_a2dp_offload_enabled()) {
- BTIF_TRACE_DEBUG("%s Set buffer size (%d) for A2DP software encoding",
- __func__, size);
- btif_av_set_dynamic_audio_buffer_size((uint8_t(size)));
- } else {
- if (cmn_vsc_cb.dynamic_audio_buffer_support != 0) {
- BTIF_TRACE_DEBUG("%s Set buffer size (%d) for A2DP offload", __func__,
- size);
- uint16_t firmware_tx_buffer_length_byte;
- uint8_t param[3] = {0};
- uint8_t* p_param = param;
-
- firmware_tx_buffer_length_byte = static_cast<uint16_t>(size);
- LOG(INFO) << __func__ << "firmware_tx_buffer_length_byte: "
- << firmware_tx_buffer_length_byte;
-
- UINT8_TO_STREAM(p_param, HCI_CONTROLLER_DAB_SET_BUFFER_TIME);
- UINT16_TO_STREAM(p_param, firmware_tx_buffer_length_byte);
- BTM_VendorSpecificCommand(HCI_CONTROLLER_DAB, p_param - param, param,
- DynamicAudiobufferSizeCompleteCallback);
- }
- }
+static void btif_jni_associate() {
+ BTIF_TRACE_DEBUG("%s Associating thread to JVM", __func__);
+ HAL_CBACK(bt_hal_cbacks, thread_evt_cb, ASSOCIATE_JVM);
+}
- return BT_STATUS_SUCCESS;
+static void btif_jni_disassociate() {
+ BTIF_TRACE_DEBUG("%s Disassociating thread from JVM", __func__);
+ HAL_CBACK(bt_hal_cbacks, thread_evt_cb, DISASSOCIATE_JVM);
+ bt_hal_cbacks = NULL;
}
diff --git a/btif/src/btif_debug_btsnoop.cc b/btif/src/btif_debug_btsnoop.cc
index 5ebfdae7b..45fcade8b 100644
--- a/btif/src/btif_debug_btsnoop.cc
+++ b/btif/src/btif_debug_btsnoop.cc
@@ -35,6 +35,12 @@
static const size_t BTSNOOP_MEM_BUFFER_SIZE = (256 * 1024);
#endif
+// Block size for copying buffers (for compression/encoding etc.)
+static const size_t BLOCK_SIZE = 16384;
+
+// Maximum line length in bugreport (should be multiple of 4 for base64 output)
+static const uint8_t MAX_LINE_LENGTH = 128;
+
static std::mutex buffer_mutex;
static ringbuffer_t* buffer = NULL;
static uint64_t last_timestamp_ms = 0;
@@ -114,10 +120,6 @@ static size_t btsnoop_calculate_packet_length(uint16_t type,
return len_hci_acl < length ? len_hci_acl : length;
}
- case BT_EVT_TO_LM_HCI_ISO:
- case BT_EVT_TO_BTU_HCI_ISO:
- return length;
-
case BT_EVT_TO_LM_HCI_SCO:
case BT_EVT_TO_BTU_HCI_SCO:
// We're not logging SCO packets at this time since they are not currently
@@ -128,18 +130,6 @@ static size_t btsnoop_calculate_packet_length(uint16_t type,
}
}
-void btif_debug_btsnoop_init(void) {
- if (buffer == NULL) buffer = ringbuffer_init(BTSNOOP_MEM_BUFFER_SIZE);
- btsnoop_mem_set_callback(btsnoop_cb);
-}
-
-#ifndef OS_ANDROID
-void btif_debug_btsnoop_dump(int fd) {}
-#else
-
-// Block size for copying buffers (for compression/encoding etc.)
-static constexpr size_t BLOCK_SIZE = 16384;
-
static bool btsnoop_compress(ringbuffer_t* rb_dst, ringbuffer_t* rb_src) {
CHECK(rb_dst != NULL);
CHECK(rb_src != NULL);
@@ -181,6 +171,11 @@ static bool btsnoop_compress(ringbuffer_t* rb_dst, ringbuffer_t* rb_src) {
return rc;
}
+void btif_debug_btsnoop_init(void) {
+ if (buffer == NULL) buffer = ringbuffer_init(BTSNOOP_MEM_BUFFER_SIZE);
+ btsnoop_mem_set_callback(btsnoop_cb);
+}
+
void btif_debug_btsnoop_dump(int fd) {
ringbuffer_t* ringbuffer = ringbuffer_init(BTSNOOP_MEM_BUFFER_SIZE);
if (ringbuffer == NULL) {
@@ -220,9 +215,6 @@ void btif_debug_btsnoop_dump(int fd) {
while (ringbuffer_size(ringbuffer) > 0) {
size_t read = ringbuffer_pop(ringbuffer, b64_in, 3);
- // Maximum line length in bugreport (should be multiple of 4 for base64
- // output)
- constexpr uint8_t MAX_LINE_LENGTH = 128;
if (line_length >= MAX_LINE_LENGTH) {
dprintf(fd, "\n");
line_length = 0;
@@ -236,4 +228,3 @@ void btif_debug_btsnoop_dump(int fd) {
error:
ringbuffer_free(ringbuffer);
}
-#endif
diff --git a/btif/src/btif_dm.cc b/btif/src/btif_dm.cc
index 49be64145..48d32909e 100644
--- a/btif/src/btif_dm.cc
+++ b/btif/src/btif_dm.cc
@@ -47,43 +47,38 @@
#include "advertise_data_parser.h"
#include "bt_common.h"
-#include "bta_dm_int.h"
#include "bta_gatt_api.h"
-#include "btif/include/stack_manager.h"
#include "btif_api.h"
#include "btif_av.h"
#include "btif_bqr.h"
#include "btif_config.h"
#include "btif_dm.h"
-#include "btif_gatt.h"
#include "btif_hd.h"
#include "btif_hf.h"
#include "btif_hh.h"
-#include "btif_metrics_logging.h"
#include "btif_sdp.h"
#include "btif_storage.h"
#include "btif_util.h"
#include "btu.h"
+#include "common/metric_id_allocator.h"
#include "common/metrics.h"
#include "device/include/controller.h"
#include "device/include/interop.h"
#include "internal_include/stack_config.h"
-#include "main/shim/shim.h"
#include "osi/include/allocator.h"
#include "osi/include/log.h"
#include "osi/include/osi.h"
#include "osi/include/properties.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_sec.h"
+#include "stack/btm/btm_int.h"
#include "stack_config.h"
using bluetooth::Uuid;
+using bluetooth::common::MetricIdAllocator;
/******************************************************************************
* Constants & Macros
*****************************************************************************/
const Uuid UUID_HEARING_AID = Uuid::FromString("FDF0");
-const Uuid UUID_VC = Uuid::FromString("1844");
#define COD_MASK 0x07FF
@@ -99,6 +94,8 @@ const Uuid UUID_VC = Uuid::FromString("1844");
#define COD_AV_PORTABLE_AUDIO 0x041C
#define COD_AV_HIFI_AUDIO 0x0428
+#define BTIF_DM_DEFAULT_INQ_MAX_RESULTS 0
+#define BTIF_DM_DEFAULT_INQ_MAX_DURATION 10
#define BTIF_DM_MAX_SDP_ATTEMPTS_AFTER_PAIRING 2
#define NUM_TIMEOUT_RETRIES 5
@@ -117,7 +114,7 @@ typedef struct {
bt_bond_state_t state;
RawAddress static_bdaddr;
RawAddress bd_addr;
- tBTM_SEC_DEV_REC::tBTM_BOND_TYPE bond_type;
+ tBTM_BOND_TYPE bond_type;
uint8_t pin_code_len;
uint8_t is_ssp;
uint8_t auth_req;
@@ -147,15 +144,31 @@ typedef struct {
} btif_dm_local_key_cb_t;
+typedef struct {
+ RawAddress bd_addr;
+ BD_NAME bd_name;
+} btif_dm_remote_name_t;
+
/* this structure holds optional OOB data for remote device */
typedef struct {
- RawAddress bdaddr; /* peer bdaddr */
- tBT_TRANSPORT transport; /* BR/EDR or LE */
- int data_present; /* What type(s) of OOB Data present */
- bt_oob_data_t p192_data; /* P192 Data or empty */
- bt_oob_data_t p256_data; /* P256 Data or empty */
+ RawAddress bdaddr; /* peer bdaddr */
+ bt_out_of_band_data_t oob_data;
} btif_dm_oob_cb_t;
+typedef struct {
+ RawAddress bdaddr;
+ uint8_t transport; /* 0=Unknown, 1=BR/EDR, 2=LE */
+} btif_dm_create_bond_cb_t;
+
+typedef struct {
+ uint8_t status;
+ uint8_t ctrl_state;
+ uint64_t tx_time;
+ uint64_t rx_time;
+ uint64_t idle_time;
+ uint64_t energy_used;
+} btif_activity_energy_info_cb_t;
+
typedef struct { unsigned int manufact_id; } skip_sdp_entry_t;
typedef enum {
@@ -176,7 +189,7 @@ typedef struct {
#define MAX_BTIF_BOND_EVENT_ENTRIES 15
-static skip_sdp_entry_t sdp_rejectlist[] = {{76}}; // Apple Mouse and Keyboard
+static skip_sdp_entry_t sdp_blacklist[] = {{76}}; // Apple Mouse and Keyboard
/* This flag will be true if HCI_Inquiry is in progress */
static bool btif_dm_inquiry_in_progress = false;
@@ -203,8 +216,10 @@ static size_t btif_events_end_index = 0;
*****************************************************************************/
static btif_dm_pairing_cb_t pairing_cb;
static btif_dm_oob_cb_t oob_cb;
-static void btif_dm_cb_create_bond(const RawAddress bd_addr,
- tBT_TRANSPORT transport);
+static void btif_dm_generic_evt(uint16_t event, char* p_param);
+static void btif_dm_cb_create_bond(const RawAddress& bd_addr,
+ tBTA_TRANSPORT transport);
+static void btif_dm_cb_hid_remote_name(tBTM_REMOTE_DEV_NAME* p_remote_name);
static void btif_update_remote_properties(const RawAddress& bd_addr,
BD_NAME bd_name, DEV_CLASS dev_class,
tBT_DEVICE_TYPE dev_type);
@@ -217,7 +232,7 @@ static void btif_dm_ble_oob_req_evt(tBTA_DM_SP_RMT_OOB* req_oob_type);
static void btif_dm_ble_sc_oob_req_evt(tBTA_DM_SP_RMT_OOB* req_oob_type);
static void bte_scan_filt_param_cfg_evt(uint8_t action_type, uint8_t avbl_space,
- uint8_t ref_value, uint8_t btm_status);
+ uint8_t ref_value, uint8_t status);
static char* btif_get_default_local_name();
@@ -228,6 +243,7 @@ static void btif_stats_add_bond_event(const RawAddress& bd_addr,
/******************************************************************************
* Externs
*****************************************************************************/
+extern bt_status_t btif_av_execute_service(bool b_enable);
extern bt_status_t btif_av_sink_execute_service(bool b_enable);
extern bt_status_t btif_hh_execute_service(bool b_enable);
extern bt_status_t btif_hf_client_execute_service(bool b_enable);
@@ -251,10 +267,31 @@ static bool is_bonding_or_sdp() {
(pairing_cb.state == BT_BOND_STATE_BONDED && pairing_cb.sdp_attempts);
}
-void btif_dm_init(uid_set_t* set) {
- uid_set = set;
+static void btif_dm_data_copy(uint16_t event, char* dst, char* src) {
+ tBTA_DM_SEC* dst_dm_sec = (tBTA_DM_SEC*)dst;
+ tBTA_DM_SEC* src_dm_sec = (tBTA_DM_SEC*)src;
+
+ if (!src_dm_sec) return;
+
+ CHECK(dst_dm_sec);
+ maybe_non_aligned_memcpy(dst_dm_sec, src_dm_sec, sizeof(*src_dm_sec));
+
+ if (event == BTA_DM_BLE_KEY_EVT) {
+ dst_dm_sec->ble_key.p_key_value =
+ (tBTM_LE_KEY_VALUE*)osi_malloc(sizeof(tBTM_LE_KEY_VALUE));
+ CHECK(src_dm_sec->ble_key.p_key_value);
+ memcpy(dst_dm_sec->ble_key.p_key_value, src_dm_sec->ble_key.p_key_value,
+ sizeof(tBTM_LE_KEY_VALUE));
+ }
}
+static void btif_dm_data_free(uint16_t event, tBTA_DM_SEC* dm_sec) {
+ if (event == BTA_DM_BLE_KEY_EVT)
+ osi_free_and_reset((void**)&dm_sec->ble_key.p_key_value);
+}
+
+void btif_dm_init(uid_set_t* set) { uid_set = set; }
+
void btif_dm_cleanup(void) {
if (uid_set) {
uid_set_destroy(uid_set);
@@ -381,7 +418,7 @@ static uint32_t get_cod(const RawAddress* remote_bdaddr) {
sizeof(uint32_t), &remote_cod);
if (btif_storage_get_remote_device_property(
(RawAddress*)remote_bdaddr, &prop_name) == BT_STATUS_SUCCESS) {
- LOG_INFO("%s remote_cod = 0x%08x", __func__, remote_cod);
+ LOG_INFO(LOG_TAG, "%s remote_cod = 0x%08x", __func__, remote_cod);
return remote_cod & COD_MASK;
}
@@ -396,23 +433,46 @@ bool check_cod_hid(const RawAddress* remote_bdaddr) {
return (get_cod(remote_bdaddr) & COD_HID_MASK) == COD_HID_MAJOR;
}
+bool check_hid_le(const RawAddress* remote_bdaddr) {
+ uint32_t remote_dev_type;
+ bt_property_t prop_name;
+
+ /* check if we already have it in our btif_storage cache */
+ BTIF_STORAGE_FILL_PROPERTY(&prop_name, BT_PROPERTY_TYPE_OF_DEVICE,
+ sizeof(uint32_t), &remote_dev_type);
+ if (btif_storage_get_remote_device_property(
+ (RawAddress*)remote_bdaddr, &prop_name) == BT_STATUS_SUCCESS) {
+ if (remote_dev_type == BT_DEVICE_DEVTYPE_BLE) {
+ if (btif_config_exist(remote_bdaddr->ToString().c_str(), "HidAppId"))
+ return true;
+ }
+ }
+ return false;
+}
+
/*****************************************************************************
*
* Function check_sdp_bl
*
- * Description Checks if a given device is rejectlisted to skip sdp
+ * Description Checks if a given device is blacklisted to skip sdp
*
* Parameters skip_sdp_entry
*
- * Returns true if the device is present in rejectlist, else false
+ * Returns true if the device is present in blacklist, else false
*
******************************************************************************/
bool check_sdp_bl(const RawAddress* remote_bdaddr) {
+ uint16_t manufacturer = 0;
+ uint8_t lmp_ver = 0;
+ uint16_t lmp_subver = 0;
bt_property_t prop_name;
bt_remote_version_t info;
if (remote_bdaddr == NULL) return false;
+ /* fetch additional info about remote device used in iop query */
+ BTM_ReadRemoteVersion(*remote_bdaddr, &lmp_ver, &manufacturer, &lmp_subver);
+
/* if not available yet, try fetching from config database */
BTIF_STORAGE_FILL_PROPERTY(&prop_name, BT_PROPERTY_REMOTE_VERSION_INFO,
sizeof(bt_remote_version_t), &info);
@@ -421,10 +481,10 @@ bool check_sdp_bl(const RawAddress* remote_bdaddr) {
BT_STATUS_SUCCESS) {
return false;
}
- uint16_t manufacturer = info.manufacturer;
+ manufacturer = info.manufacturer;
- for (unsigned int i = 0; i < ARRAY_SIZE(sdp_rejectlist); i++) {
- if (manufacturer == sdp_rejectlist[i].manufact_id) return true;
+ for (unsigned int i = 0; i < ARRAY_SIZE(sdp_blacklist); i++) {
+ if (manufacturer == sdp_blacklist[i].manufact_id) return true;
}
return false;
}
@@ -436,30 +496,28 @@ static void bond_state_changed(bt_status_t status, const RawAddress& bd_addr,
if ((pairing_cb.state == state) && (state == BT_BOND_STATE_BONDING)) {
// Cross key pairing so send callback for static address
if (!pairing_cb.static_bdaddr.IsEmpty()) {
- invoke_bond_state_changed_cb(status, bd_addr, state);
+ auto tmp = bd_addr;
+ HAL_CBACK(bt_hal_cbacks, bond_state_changed_cb, status, &tmp, state);
}
return;
}
- if (pairing_cb.bond_type == tBTM_SEC_DEV_REC::BOND_TYPE_TEMPORARY) {
- state = BT_BOND_STATE_NONE;
- }
+ if (pairing_cb.bond_type == BOND_TYPE_TEMPORARY) state = BT_BOND_STATE_NONE;
- LOG_INFO(
- "Bond state changed to state=%d [0:none, 1:bonding, 2:bonded],"
- " prev_state=%d, sdp_attempts = %d",
- state, pairing_cb.state, pairing_cb.sdp_attempts);
+ BTIF_TRACE_DEBUG("%s: state=%d, prev_state=%d, sdp_attempts = %d", __func__,
+ state, pairing_cb.state, pairing_cb.sdp_attempts);
if (state == BT_BOND_STATE_NONE) {
- forget_device_from_metric_id_allocator(bd_addr);
+ MetricIdAllocator::GetInstance().ForgetDevice(bd_addr);
} else if (state == BT_BOND_STATE_BONDED) {
- allocate_metric_id_from_metric_id_allocator(bd_addr);
- if (!save_metric_id_from_metric_id_allocator(bd_addr)) {
+ MetricIdAllocator::GetInstance().AllocateId(bd_addr);
+ if (!MetricIdAllocator::GetInstance().SaveDevice(bd_addr)) {
LOG(FATAL) << __func__ << ": Fail to save metric id for device "
<< bd_addr;
}
}
- invoke_bond_state_changed_cb(status, bd_addr, state);
+ auto tmp = bd_addr;
+ HAL_CBACK(bt_hal_cbacks, bond_state_changed_cb, status, &tmp, state);
int dev_type;
if (!btif_get_device_type(bd_addr, &dev_type)) {
@@ -473,7 +531,6 @@ static void bond_state_changed(bt_status_t status, const RawAddress& bd_addr,
pairing_cb.bd_addr = bd_addr;
} else {
pairing_cb = {};
- bta_dm_execute_queued_request();
}
}
@@ -484,19 +541,16 @@ static void btif_update_remote_version_property(RawAddress* p_bd) {
uint8_t lmp_ver = 0;
uint16_t lmp_subver = 0;
uint16_t mfct_set = 0;
+ tBTM_STATUS btm_status;
bt_remote_version_t info;
bt_status_t status;
- CHECK(p_bd != nullptr);
-
- const bool version_info_valid =
- BTM_ReadRemoteVersion(*p_bd, &lmp_ver, &mfct_set, &lmp_subver);
+ btm_status = BTM_ReadRemoteVersion(*p_bd, &lmp_ver, &mfct_set, &lmp_subver);
- LOG_INFO("Remote version info valid:%s [%s]: %x, %x, %x",
- logbool(version_info_valid).c_str(), PRIVATE_ADDRESS((*p_bd)),
- lmp_ver, mfct_set, lmp_subver);
+ LOG_DEBUG(LOG_TAG, "remote version info [%s]: %x, %x, %x",
+ p_bd->ToString().c_str(), lmp_ver, mfct_set, lmp_subver);
- if (version_info_valid) {
+ if (btm_status == BTM_SUCCESS) {
// Always update cache to ensure we have availability whenever BTM API is
// not populated
info.manufacturer = mfct_set;
@@ -515,7 +569,7 @@ static void btif_update_remote_properties(const RawAddress& bdaddr,
tBT_DEVICE_TYPE device_type) {
int num_properties = 0;
bt_property_t properties[3];
- bt_status_t status = BT_STATUS_UNHANDLED;
+ bt_status_t status;
uint32_t cod;
bt_device_type_t dev_type;
@@ -525,42 +579,36 @@ static void btif_update_remote_properties(const RawAddress& bdaddr,
if (strlen((const char*)bd_name)) {
BTIF_STORAGE_FILL_PROPERTY(&properties[num_properties], BT_PROPERTY_BDNAME,
strlen((char*)bd_name), bd_name);
- if (!bluetooth::shim::is_gd_security_enabled()) {
- status = btif_storage_set_remote_device_property(
- &bdaddr, &properties[num_properties]);
- ASSERTC(status == BT_STATUS_SUCCESS, "failed to save remote device name",
- status);
- }
+ status = btif_storage_set_remote_device_property(
+ &bdaddr, &properties[num_properties]);
+ ASSERTC(status == BT_STATUS_SUCCESS, "failed to save remote device name",
+ status);
num_properties++;
}
/* class of device */
cod = devclass2uint(dev_class);
+ BTIF_TRACE_DEBUG("%s cod is 0x%06x", __func__, cod);
if (cod == 0) {
/* Try to retrieve cod from storage */
- LOG_VERBOSE("class of device (cod) is unclassified, checking storage");
+ BTIF_TRACE_DEBUG("%s cod is 0, checking cod from storage", __func__);
BTIF_STORAGE_FILL_PROPERTY(&properties[num_properties],
BT_PROPERTY_CLASS_OF_DEVICE, sizeof(cod), &cod);
status = btif_storage_get_remote_device_property(
&bdaddr, &properties[num_properties]);
- LOG_VERBOSE("cod retrieved from storage is 0x%06x", cod);
+ BTIF_TRACE_DEBUG("%s cod retrieved from storage is 0x%06x", __func__, cod);
if (cod == 0) {
- LOG_INFO("cod from storage is also unclassified");
+ BTIF_TRACE_DEBUG("%s cod is again 0, set as unclassified", __func__);
cod = COD_UNCLASSIFIED;
}
- } else {
- LOG_INFO("class of device (cod) is 0x%06x", cod);
}
BTIF_STORAGE_FILL_PROPERTY(&properties[num_properties],
BT_PROPERTY_CLASS_OF_DEVICE, sizeof(cod), &cod);
-
- if (!bluetooth::shim::is_gd_security_enabled()) {
- status = btif_storage_set_remote_device_property(
- &bdaddr, &properties[num_properties]);
- ASSERTC(status == BT_STATUS_SUCCESS, "failed to save remote device class",
- status);
- }
+ status = btif_storage_set_remote_device_property(&bdaddr,
+ &properties[num_properties]);
+ ASSERTC(status == BT_STATUS_SUCCESS, "failed to save remote device class",
+ status);
num_properties++;
/* device type */
@@ -569,25 +617,46 @@ static void btif_update_remote_properties(const RawAddress& bdaddr,
BTIF_STORAGE_FILL_PROPERTY(&prop_name, BT_PROPERTY_TYPE_OF_DEVICE,
sizeof(uint8_t), &remote_dev_type);
if (btif_storage_get_remote_device_property(&bdaddr, &prop_name) ==
- BT_STATUS_SUCCESS) {
+ BT_STATUS_SUCCESS)
dev_type = (bt_device_type_t)(remote_dev_type | device_type);
- } else {
+ else
dev_type = (bt_device_type_t)device_type;
- }
BTIF_STORAGE_FILL_PROPERTY(&properties[num_properties],
BT_PROPERTY_TYPE_OF_DEVICE, sizeof(dev_type),
&dev_type);
- if (!bluetooth::shim::is_gd_security_enabled()) {
- status = btif_storage_set_remote_device_property(
- &bdaddr, &properties[num_properties]);
- ASSERTC(status == BT_STATUS_SUCCESS, "failed to save remote device type",
- status);
- }
+ status = btif_storage_set_remote_device_property(&bdaddr,
+ &properties[num_properties]);
+ ASSERTC(status == BT_STATUS_SUCCESS, "failed to save remote device type",
+ status);
num_properties++;
- invoke_remote_device_properties_cb(status, bdaddr, num_properties,
- properties);
+ auto tmp = bdaddr;
+ HAL_CBACK(bt_hal_cbacks, remote_device_properties_cb, status, &tmp,
+ num_properties, properties);
+}
+
+/*******************************************************************************
+ *
+ * Function btif_dm_cb_hid_remote_name
+ *
+ * Description Remote name callback for HID device. Called in btif context
+ * Special handling for HID devices
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btif_dm_cb_hid_remote_name(tBTM_REMOTE_DEV_NAME* p_remote_name) {
+ BTIF_TRACE_DEBUG("%s: status=%d pairing_cb.state=%d", __func__,
+ p_remote_name->status, pairing_cb.state);
+ if (pairing_cb.state == BT_BOND_STATE_BONDING) {
+ if (p_remote_name->status == BTM_SUCCESS) {
+ bond_state_changed(BT_STATUS_SUCCESS, pairing_cb.bd_addr,
+ BT_BOND_STATE_BONDED);
+ } else
+ bond_state_changed(BT_STATUS_FAIL, pairing_cb.bd_addr,
+ BT_BOND_STATE_NONE);
+ }
}
/*******************************************************************************
@@ -600,13 +669,13 @@ static void btif_update_remote_properties(const RawAddress& bdaddr,
* Returns void
*
******************************************************************************/
-static void btif_dm_cb_create_bond(const RawAddress bd_addr,
- tBT_TRANSPORT transport) {
+static void btif_dm_cb_create_bond(const RawAddress& bd_addr,
+ tBTA_TRANSPORT transport) {
bool is_hid = check_cod(&bd_addr, COD_HID_POINTING);
bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_BONDING);
int device_type = 0;
- tBLE_ADDR_TYPE addr_type = BLE_ADDR_PUBLIC;
+ int addr_type;
std::string addrstr = bd_addr.ToString();
const char* bdstr = addrstr.c_str();
if (transport == BT_TRANSPORT_LE) {
@@ -618,7 +687,7 @@ static void btif_dm_cb_create_bond(const RawAddress bd_addr,
// Try to read address type. OOB pairing might have set it earlier, but
// didn't store it, it defaults to BLE_ADDR_PUBLIC
uint8_t tmp_dev_type;
- tBLE_ADDR_TYPE tmp_addr_type = BLE_ADDR_PUBLIC;
+ uint8_t tmp_addr_type;
BTM_ReadDevInfo(bd_addr, &tmp_dev_type, &tmp_addr_type);
addr_type = tmp_addr_type;
@@ -639,7 +708,7 @@ static void btif_dm_cb_create_bond(const RawAddress bd_addr,
if (status != BT_STATUS_SUCCESS)
bond_state_changed(status, bd_addr, BT_BOND_STATE_NONE);
} else {
- BTA_DmBond(bd_addr, addr_type, transport, device_type);
+ BTA_DmBond(bd_addr, addr_type, transport);
}
/* Track originator of bond creation */
pairing_cb.is_local_initiated = true;
@@ -647,6 +716,30 @@ static void btif_dm_cb_create_bond(const RawAddress bd_addr,
/*******************************************************************************
*
+ * Function btif_dm_cb_remove_bond
+ *
+ * Description remove bond initiated from the BTIF thread context
+ * Special handling for HID devices
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btif_dm_cb_remove_bond(const RawAddress* bd_addr) {
+/*special handling for HID devices */
+/* VUP needs to be sent if its a HID Device. The HID HOST module will check if
+there
+is a valid hid connection with this bd_addr. If yes VUP will be issued.*/
+#if (BTA_HH_INCLUDED == TRUE)
+ if (btif_hh_virtual_unplug(bd_addr) != BT_STATUS_SUCCESS)
+#endif
+ {
+ BTIF_TRACE_DEBUG("%s: Removing HH device", __func__);
+ BTA_DmRemoveDevice(*bd_addr);
+ }
+}
+
+/*******************************************************************************
+ *
* Function btif_dm_get_connection_state
*
* Description Returns whether the remote device is currently connected
@@ -660,17 +753,83 @@ uint16_t btif_dm_get_connection_state(const RawAddress* bd_addr) {
uint16_t rc = BTA_DmGetConnectionState(*bd_addr);
if (rc != 0) {
- if (BTM_IsEncrypted(*bd_addr, BT_TRANSPORT_BR_EDR)) {
- rc |= ENCRYPTED_BREDR;
- }
- if (BTM_IsEncrypted(*bd_addr, BT_TRANSPORT_LE)) {
- rc |= ENCRYPTED_LE;
- }
+ uint8_t flags = 0;
+
+ BTM_GetSecurityFlagsByTransport(*bd_addr, &flags, BT_TRANSPORT_BR_EDR);
+ BTIF_TRACE_DEBUG("%s: security flags (BR/EDR)=0x%02x", __func__, flags);
+ if (flags & BTM_SEC_FLAG_ENCRYPTED) rc |= ENCRYPTED_BREDR;
+
+ BTM_GetSecurityFlagsByTransport(*bd_addr, &flags, BT_TRANSPORT_LE);
+ BTIF_TRACE_DEBUG("%s: security flags (LE)=0x%02x", __func__, flags);
+ if (flags & BTM_SEC_FLAG_ENCRYPTED) rc |= ENCRYPTED_LE;
}
return rc;
}
+/*******************************************************************************
+ *
+ * Function search_devices_copy_cb
+ *
+ * Description Deep copy callback for search devices event
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void search_devices_copy_cb(uint16_t event, char* p_dest, char* p_src) {
+ tBTA_DM_SEARCH* p_dest_data = (tBTA_DM_SEARCH*)p_dest;
+ tBTA_DM_SEARCH* p_src_data = (tBTA_DM_SEARCH*)p_src;
+
+ if (!p_src) return;
+
+ BTIF_TRACE_DEBUG("%s: event=%s", __func__, dump_dm_search_event(event));
+ maybe_non_aligned_memcpy(p_dest_data, p_src_data, sizeof(*p_src_data));
+ switch (event) {
+ case BTA_DM_INQ_RES_EVT: {
+ if (p_src_data->inq_res.p_eir) {
+ p_dest_data->inq_res.p_eir =
+ (uint8_t*)(p_dest + sizeof(tBTA_DM_SEARCH));
+ memcpy(p_dest_data->inq_res.p_eir, p_src_data->inq_res.p_eir,
+ p_src_data->inq_res.eir_len);
+ p_dest_data->inq_res.eir_len = p_src_data->inq_res.eir_len;
+ }
+ } break;
+
+ case BTA_DM_DISC_RES_EVT: {
+ if (p_src_data->disc_res.raw_data_size &&
+ p_src_data->disc_res.p_raw_data) {
+ p_dest_data->disc_res.p_raw_data =
+ (uint8_t*)(p_dest + sizeof(tBTA_DM_SEARCH));
+ memcpy(p_dest_data->disc_res.p_raw_data,
+ p_src_data->disc_res.p_raw_data,
+ p_src_data->disc_res.raw_data_size);
+ }
+ } break;
+ }
+}
+
+static void search_services_copy_cb(uint16_t event, char* p_dest, char* p_src) {
+ tBTA_DM_SEARCH* p_dest_data = (tBTA_DM_SEARCH*)p_dest;
+ tBTA_DM_SEARCH* p_src_data = (tBTA_DM_SEARCH*)p_src;
+
+ if (!p_src) return;
+ maybe_non_aligned_memcpy(p_dest_data, p_src_data, sizeof(*p_src_data));
+ switch (event) {
+ case BTA_DM_DISC_RES_EVT: {
+ if (p_src_data->disc_res.result == BTA_SUCCESS) {
+ if (p_src_data->disc_res.num_uuids > 0) {
+ p_dest_data->disc_res.p_uuid_list =
+ (Uuid*)(p_dest + sizeof(tBTA_DM_SEARCH));
+ memcpy(p_dest_data->disc_res.p_uuid_list,
+ p_src_data->disc_res.p_uuid_list,
+ p_src_data->disc_res.num_uuids * sizeof(Uuid));
+ osi_free_and_reset((void**)&p_src_data->disc_res.p_uuid_list);
+ }
+ osi_free_and_reset((void**)&p_src_data->disc_res.p_raw_data);
+ }
+ } break;
+ }
+}
/******************************************************************************
*
* BTIF DM callback events
@@ -693,11 +852,7 @@ static void btif_dm_pin_req_evt(tBTA_DM_PIN_REQ* p_pin_req) {
int dev_type;
/* Remote properties update */
- if (BTM_GetPeerDeviceTypeFromFeatures(p_pin_req->bd_addr) ==
- BT_DEVICE_TYPE_DUMO) {
- dev_type = BT_DEVICE_TYPE_DUMO;
- } else if (!btif_get_device_type(p_pin_req->bd_addr, &dev_type)) {
- // Failed to get device type, defaulting to BR/EDR.
+ if (!btif_get_device_type(p_pin_req->bd_addr, &dev_type)) {
dev_type = BT_DEVICE_TYPE_BREDR;
}
btif_update_remote_properties(p_pin_req->bd_addr, p_pin_req->bd_name,
@@ -706,12 +861,12 @@ static void btif_dm_pin_req_evt(tBTA_DM_PIN_REQ* p_pin_req) {
const RawAddress& bd_addr = p_pin_req->bd_addr;
memcpy(bd_name.name, p_pin_req->bd_name, BD_NAME_LEN);
- bd_name.name[BD_NAME_LEN] = '\0';
if (pairing_cb.state == BT_BOND_STATE_BONDING &&
bd_addr != pairing_cb.bd_addr) {
BTIF_TRACE_WARNING("%s(): already in bonding state, reject request",
__FUNCTION__);
+ btif_dm_pin_reply(&bd_addr, 0, 0, NULL);
return;
}
@@ -764,7 +919,10 @@ static void btif_dm_pin_req_evt(tBTA_DM_PIN_REQ* p_pin_req) {
}
}
}
- invoke_pin_request_cb(bd_addr, bd_name, cod, p_pin_req->min_16_digit);
+ // TODO: make cback accept const and get rid of tmp!
+ auto tmp = bd_addr;
+ HAL_CBACK(bt_hal_cbacks, pin_request_cb, &tmp, &bd_name, cod,
+ p_pin_req->min_16_digit);
}
/*******************************************************************************
@@ -785,11 +943,7 @@ static void btif_dm_ssp_cfm_req_evt(tBTA_DM_SP_CFM_REQ* p_ssp_cfm_req) {
BTIF_TRACE_DEBUG("%s", __func__);
/* Remote properties update */
- if (BTM_GetPeerDeviceTypeFromFeatures(p_ssp_cfm_req->bd_addr) ==
- BT_DEVICE_TYPE_DUMO) {
- dev_type = BT_DEVICE_TYPE_DUMO;
- } else if (!btif_get_device_type(p_ssp_cfm_req->bd_addr, &dev_type)) {
- // Failed to get device type, defaulting to BR/EDR.
+ if (!btif_get_device_type(p_ssp_cfm_req->bd_addr, &dev_type)) {
dev_type = BT_DEVICE_TYPE_BREDR;
}
btif_update_remote_properties(p_ssp_cfm_req->bd_addr, p_ssp_cfm_req->bd_name,
@@ -803,7 +957,7 @@ static void btif_dm_ssp_cfm_req_evt(tBTA_DM_SP_CFM_REQ* p_ssp_cfm_req) {
bd_addr != pairing_cb.bd_addr) {
BTIF_TRACE_WARNING("%s(): already in bonding state, reject request",
__FUNCTION__);
- btif_dm_ssp_reply(bd_addr, BT_SSP_VARIANT_PASSKEY_CONFIRMATION, 0);
+ btif_dm_ssp_reply(&bd_addr, BT_SSP_VARIANT_PASSKEY_CONFIRMATION, 0, 0);
return;
}
@@ -820,9 +974,9 @@ static void btif_dm_ssp_cfm_req_evt(tBTA_DM_SP_CFM_REQ* p_ssp_cfm_req) {
!(p_ssp_cfm_req->loc_auth_req & BTM_AUTH_BONDS) &&
!(p_ssp_cfm_req->rmt_auth_req & BTM_AUTH_BONDS) &&
!(check_cod((RawAddress*)&p_ssp_cfm_req->bd_addr, COD_HID_POINTING)))
- pairing_cb.bond_type = tBTM_SEC_DEV_REC::BOND_TYPE_TEMPORARY;
+ pairing_cb.bond_type = BOND_TYPE_TEMPORARY;
else
- pairing_cb.bond_type = tBTM_SEC_DEV_REC::BOND_TYPE_PERSISTENT;
+ pairing_cb.bond_type = BOND_TYPE_PERSISTENT;
btm_set_bond_type_dev(p_ssp_cfm_req->bd_addr, pairing_cb.bond_type);
@@ -833,11 +987,10 @@ static void btif_dm_ssp_cfm_req_evt(tBTA_DM_SP_CFM_REQ* p_ssp_cfm_req) {
/* Pairing consent for JustWorks NOT needed if:
* 1. Incoming temporary pairing is detected
*/
- if (is_incoming &&
- pairing_cb.bond_type == tBTM_SEC_DEV_REC::BOND_TYPE_TEMPORARY) {
+ if (is_incoming && pairing_cb.bond_type == BOND_TYPE_TEMPORARY) {
BTIF_TRACE_EVENT(
"%s: Auto-accept JustWorks pairing for temporary incoming", __func__);
- btif_dm_ssp_reply(bd_addr, BT_SSP_VARIANT_CONSENT, true);
+ btif_dm_ssp_reply(&bd_addr, BT_SSP_VARIANT_CONSENT, true, 0);
return;
}
}
@@ -845,16 +998,15 @@ static void btif_dm_ssp_cfm_req_evt(tBTA_DM_SP_CFM_REQ* p_ssp_cfm_req) {
cod = devclass2uint(p_ssp_cfm_req->dev_class);
if (cod == 0) {
- LOG_INFO("%s cod is 0, set as unclassified", __func__);
+ LOG_DEBUG(LOG_TAG, "%s cod is 0, set as unclassified", __func__);
cod = COD_UNCLASSIFIED;
}
pairing_cb.sdp_attempts = 0;
- invoke_ssp_request_cb(
- bd_addr, bd_name, cod,
- (p_ssp_cfm_req->just_works ? BT_SSP_VARIANT_CONSENT
- : BT_SSP_VARIANT_PASSKEY_CONFIRMATION),
- p_ssp_cfm_req->num_val);
+ HAL_CBACK(bt_hal_cbacks, ssp_request_cb, &bd_addr, &bd_name, cod,
+ (p_ssp_cfm_req->just_works ? BT_SSP_VARIANT_CONSENT
+ : BT_SSP_VARIANT_PASSKEY_CONFIRMATION),
+ p_ssp_cfm_req->num_val);
}
static void btif_dm_ssp_key_notif_evt(tBTA_DM_SP_KEY_NOTIF* p_ssp_key_notif) {
@@ -865,11 +1017,7 @@ static void btif_dm_ssp_key_notif_evt(tBTA_DM_SP_KEY_NOTIF* p_ssp_key_notif) {
BTIF_TRACE_DEBUG("%s", __func__);
/* Remote properties update */
- if (BTM_GetPeerDeviceTypeFromFeatures(p_ssp_key_notif->bd_addr) ==
- BT_DEVICE_TYPE_DUMO) {
- dev_type = BT_DEVICE_TYPE_DUMO;
- } else if (!btif_get_device_type(p_ssp_key_notif->bd_addr, &dev_type)) {
- // Failed to get device type, defaulting to BR/EDR.
+ if (!btif_get_device_type(p_ssp_key_notif->bd_addr, &dev_type)) {
dev_type = BT_DEVICE_TYPE_BREDR;
}
btif_update_remote_properties(
@@ -878,20 +1026,18 @@ static void btif_dm_ssp_key_notif_evt(tBTA_DM_SP_KEY_NOTIF* p_ssp_key_notif) {
RawAddress bd_addr = p_ssp_key_notif->bd_addr;
memcpy(bd_name.name, p_ssp_key_notif->bd_name, BD_NAME_LEN);
- bd_name.name[BD_NAME_LEN] = '\0';
bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_BONDING);
pairing_cb.is_ssp = true;
cod = devclass2uint(p_ssp_key_notif->dev_class);
if (cod == 0) {
- LOG_INFO("%s cod is 0, set as unclassified", __func__);
+ LOG_DEBUG(LOG_TAG, "%s cod is 0, set as unclassified", __func__);
cod = COD_UNCLASSIFIED;
}
- invoke_ssp_request_cb(bd_addr, bd_name, cod,
- BT_SSP_VARIANT_PASSKEY_NOTIFICATION,
- p_ssp_key_notif->passkey);
+ HAL_CBACK(bt_hal_cbacks, ssp_request_cb, &bd_addr, &bd_name, cod,
+ BT_SSP_VARIANT_PASSKEY_NOTIFICATION, p_ssp_key_notif->passkey);
}
/*******************************************************************************
*
@@ -913,31 +1059,29 @@ static void btif_dm_auth_cmpl_evt(tBTA_DM_AUTH_CMPL* p_auth_cmpl) {
p_auth_cmpl->key_present);
RawAddress bd_addr = p_auth_cmpl->bd_addr;
- if (!bluetooth::shim::is_gd_security_enabled()) {
- if ((p_auth_cmpl->success) && (p_auth_cmpl->key_present)) {
- if ((p_auth_cmpl->key_type < HCI_LKEY_TYPE_DEBUG_COMB) ||
- (p_auth_cmpl->key_type == HCI_LKEY_TYPE_AUTH_COMB) ||
- (p_auth_cmpl->key_type == HCI_LKEY_TYPE_CHANGED_COMB) ||
- (p_auth_cmpl->key_type == HCI_LKEY_TYPE_AUTH_COMB_P_256) ||
- pairing_cb.bond_type == tBTM_SEC_DEV_REC::BOND_TYPE_PERSISTENT) {
- bt_status_t ret;
- BTIF_TRACE_DEBUG("%s: Storing link key. key_type=0x%x, bond_type=%d",
- __func__, p_auth_cmpl->key_type, pairing_cb.bond_type);
- ret = btif_storage_add_bonded_device(&bd_addr, p_auth_cmpl->key,
- p_auth_cmpl->key_type,
- pairing_cb.pin_code_len);
- ASSERTC(ret == BT_STATUS_SUCCESS, "storing link key failed", ret);
- } else {
- BTIF_TRACE_DEBUG(
- "%s: Temporary key. Not storing. key_type=0x%x, bond_type=%d",
- __func__, p_auth_cmpl->key_type, pairing_cb.bond_type);
- if (pairing_cb.bond_type == tBTM_SEC_DEV_REC::BOND_TYPE_TEMPORARY) {
- BTIF_TRACE_DEBUG("%s: sending BT_BOND_STATE_NONE for Temp pairing",
- __func__);
- btif_storage_remove_bonded_device(&bd_addr);
- bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_NONE);
- return;
- }
+ if ((p_auth_cmpl->success) && (p_auth_cmpl->key_present)) {
+ if ((p_auth_cmpl->key_type < HCI_LKEY_TYPE_DEBUG_COMB) ||
+ (p_auth_cmpl->key_type == HCI_LKEY_TYPE_AUTH_COMB) ||
+ (p_auth_cmpl->key_type == HCI_LKEY_TYPE_CHANGED_COMB) ||
+ (p_auth_cmpl->key_type == HCI_LKEY_TYPE_AUTH_COMB_P_256) ||
+ pairing_cb.bond_type == BOND_TYPE_PERSISTENT) {
+ bt_status_t ret;
+ BTIF_TRACE_DEBUG("%s: Storing link key. key_type=0x%x, bond_type=%d",
+ __func__, p_auth_cmpl->key_type, pairing_cb.bond_type);
+ ret = btif_storage_add_bonded_device(&bd_addr, p_auth_cmpl->key,
+ p_auth_cmpl->key_type,
+ pairing_cb.pin_code_len);
+ ASSERTC(ret == BT_STATUS_SUCCESS, "storing link key failed", ret);
+ } else {
+ BTIF_TRACE_DEBUG(
+ "%s: Temporary key. Not storing. key_type=0x%x, bond_type=%d",
+ __func__, p_auth_cmpl->key_type, pairing_cb.bond_type);
+ if (pairing_cb.bond_type == BOND_TYPE_TEMPORARY) {
+ BTIF_TRACE_DEBUG("%s: sending BT_BOND_STATE_NONE for Temp pairing",
+ __func__);
+ btif_storage_remove_bonded_device(&bd_addr);
+ bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_NONE);
+ return;
}
}
}
@@ -958,31 +1102,22 @@ static void btif_dm_auth_cmpl_evt(tBTA_DM_AUTH_CMPL* p_auth_cmpl) {
return;
}
- if (!bluetooth::shim::is_gd_security_enabled()) {
- btif_storage_set_remote_addr_type(&bd_addr, p_auth_cmpl->addr_type);
- }
-
- int dev_type;
- if (BTM_GetPeerDeviceTypeFromFeatures(bd_addr) == BT_DEVICE_TYPE_DUMO) {
- dev_type = BT_DEVICE_TYPE_DUMO;
- } else {
- dev_type = p_auth_cmpl->dev_type;
- }
+ btif_storage_set_remote_addr_type(&bd_addr, p_auth_cmpl->addr_type);
btif_update_remote_properties(p_auth_cmpl->bd_addr, p_auth_cmpl->bd_name,
- NULL, dev_type);
+ NULL, p_auth_cmpl->dev_type);
pairing_cb.timeout_retries = 0;
status = BT_STATUS_SUCCESS;
state = BT_BOND_STATE_BONDED;
bd_addr = p_auth_cmpl->bd_addr;
if (check_sdp_bl(&bd_addr) && check_cod_hid(&bd_addr)) {
- LOG_WARN("%s:skip SDP", __func__);
+ LOG_WARN(LOG_TAG, "%s:skip SDP", __func__);
skip_sdp = true;
}
if (!pairing_cb.is_local_initiated && skip_sdp) {
bond_state_changed(status, bd_addr, state);
- LOG_WARN("%s: Incoming HID Connection", __func__);
+ LOG_WARN(LOG_TAG, "%s: Incoming HID Connection", __func__);
bt_property_t prop;
Uuid uuid = Uuid::From16Bit(UUID_SERVCLASS_HUMAN_INTERFACE);
@@ -990,7 +1125,9 @@ static void btif_dm_auth_cmpl_evt(tBTA_DM_AUTH_CMPL* p_auth_cmpl) {
prop.val = &uuid;
prop.len = Uuid::kNumBytes128;
- invoke_remote_device_properties_cb(BT_STATUS_SUCCESS, bd_addr, 1, &prop);
+ /* Send the event to the BTIF */
+ HAL_CBACK(bt_hal_cbacks, remote_device_properties_cb, BT_STATUS_SUCCESS,
+ &bd_addr, 1, &prop);
} else {
bool is_crosskey = false;
/* If bonded due to cross-key, save the static address too*/
@@ -1013,13 +1150,14 @@ static void btif_dm_auth_cmpl_evt(tBTA_DM_AUTH_CMPL* p_auth_cmpl) {
if (is_crosskey) {
// If bonding occurred due to cross-key pairing, send bonding callback
// for static address now
- LOG_INFO("%s: send bonding state update for static address %s",
+ LOG_INFO(LOG_TAG,
+ "%s: send bonding state update for static address %s",
__func__, bd_addr.ToString().c_str());
bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_BONDING);
}
bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_BONDED);
- btif_dm_get_remote_services(bd_addr, BT_TRANSPORT_UNKNOWN);
+ btif_dm_get_remote_services(bd_addr);
}
}
// Do not call bond_state_changed_cb yet. Wait until remote service
@@ -1035,7 +1173,7 @@ static void btif_dm_auth_cmpl_evt(tBTA_DM_AUTH_CMPL* p_auth_cmpl) {
BTIF_TRACE_WARNING("%s() - Pairing timeout; retrying (%d) ...",
__func__, pairing_cb.timeout_retries);
--pairing_cb.timeout_retries;
- btif_dm_cb_create_bond(bd_addr, BT_TRANSPORT_UNKNOWN);
+ btif_dm_cb_create_bond(bd_addr, BTA_TRANSPORT_UNKNOWN);
return;
}
FALLTHROUGH_INTENDED; /* FALLTHROUGH */
@@ -1044,22 +1182,16 @@ static void btif_dm_auth_cmpl_evt(tBTA_DM_AUTH_CMPL* p_auth_cmpl) {
break;
case HCI_ERR_PAIRING_NOT_ALLOWED:
- if (!bluetooth::shim::is_gd_security_enabled()) {
- is_bonded_device_removed = (btif_storage_remove_bonded_device(
- &bd_addr) == BT_STATUS_SUCCESS);
- } else {
- is_bonded_device_removed = true;
- }
+ is_bonded_device_removed =
+ (btif_storage_remove_bonded_device(&bd_addr) == BT_STATUS_SUCCESS);
status = BT_STATUS_AUTH_REJECTED;
break;
/* map the auth failure codes, so we can retry pairing if necessary */
case HCI_ERR_AUTH_FAILURE:
case HCI_ERR_KEY_MISSING:
- is_bonded_device_removed = (bluetooth::shim::is_gd_security_enabled())
- ? true
- : (btif_storage_remove_bonded_device(
- &bd_addr) == BT_STATUS_SUCCESS);
+ is_bonded_device_removed =
+ (btif_storage_remove_bonded_device(&bd_addr) == BT_STATUS_SUCCESS);
[[fallthrough]];
case HCI_ERR_HOST_REJECT_SECURITY:
case HCI_ERR_ENCRY_MODE_NOT_ACCEPTABLE:
@@ -1074,7 +1206,7 @@ static void btif_dm_auth_cmpl_evt(tBTA_DM_AUTH_CMPL* p_auth_cmpl) {
/* Create the Bond once again */
BTIF_TRACE_WARNING("%s() auto pair failed. Reinitiate Bond",
__func__);
- btif_dm_cb_create_bond(bd_addr, BT_TRANSPORT_UNKNOWN);
+ btif_dm_cb_create_bond(bd_addr, BTA_TRANSPORT_UNKNOWN);
return;
} else {
/* if autopair attempts are more than 1, or not attempted */
@@ -1090,10 +1222,8 @@ static void btif_dm_auth_cmpl_evt(tBTA_DM_AUTH_CMPL* p_auth_cmpl) {
/* Remove Device as bonded in nvram as authentication failed */
BTIF_TRACE_DEBUG("%s(): removing hid pointing device from nvram",
__func__);
- is_bonded_device_removed = (bluetooth::shim::is_gd_security_enabled())
- ? true
- : (btif_storage_remove_bonded_device(
- &bd_addr) == BT_STATUS_SUCCESS);
+ is_bonded_device_removed =
+ (btif_storage_remove_bonded_device(&bd_addr) == BT_STATUS_SUCCESS);
}
// Report bond state change to java only if we are bonding to a device or
// a device is removed from the pairing list.
@@ -1112,12 +1242,13 @@ static void btif_dm_auth_cmpl_evt(tBTA_DM_AUTH_CMPL* p_auth_cmpl) {
* Returns void
*
*****************************************************************************/
-static void btif_dm_search_devices_evt(tBTA_DM_SEARCH_EVT event,
- tBTA_DM_SEARCH* p_search_data) {
+static void btif_dm_search_devices_evt(uint16_t event, char* p_param) {
+ tBTA_DM_SEARCH* p_search_data;
BTIF_TRACE_EVENT("%s event=%s", __func__, dump_dm_search_event(event));
switch (event) {
case BTA_DM_DISC_RES_EVT: {
+ p_search_data = (tBTA_DM_SEARCH*)p_param;
/* Remote name update */
if (strlen((const char*)p_search_data->disc_res.bd_name)) {
bt_property_t properties[1];
@@ -1132,7 +1263,8 @@ static void btif_dm_search_devices_evt(tBTA_DM_SEARCH_EVT event,
btif_storage_set_remote_device_property(&bdaddr, &properties[0]);
ASSERTC(status == BT_STATUS_SUCCESS,
"failed to save remote device property", status);
- invoke_remote_device_properties_cb(status, bdaddr, 1, properties);
+ HAL_CBACK(bt_hal_cbacks, remote_device_properties_cb, status, &bdaddr,
+ 1, properties);
}
/* TODO: Services? */
} break;
@@ -1143,8 +1275,7 @@ static void btif_dm_search_devices_evt(tBTA_DM_SEARCH_EVT event,
uint8_t remote_name_len;
tBTA_SERVICE_MASK services = 0;
- p_search_data->inq_res.remt_name_not_required =
- check_eir_remote_name(p_search_data, NULL, NULL);
+ p_search_data = (tBTA_DM_SEARCH*)p_param;
RawAddress& bdaddr = p_search_data->inq_res.bd_addr;
BTIF_TRACE_DEBUG("%s() %s device_type = 0x%x\n", __func__,
@@ -1170,7 +1301,7 @@ static void btif_dm_search_devices_evt(tBTA_DM_SEARCH_EVT event,
bt_device_type_t dev_type;
uint32_t num_properties = 0;
bt_status_t status;
- tBLE_ADDR_TYPE addr_type = BLE_ADDR_PUBLIC;
+ int addr_type = 0;
memset(properties, 0, sizeof(properties));
/* RawAddress */
@@ -1231,19 +1362,19 @@ static void btif_dm_search_devices_evt(tBTA_DM_SEARCH_EVT event,
ASSERTC(status == BT_STATUS_SUCCESS,
"failed to save remote addr type (inquiry)", status);
/* Callback to notify upper layer of device */
- invoke_device_found_cb(num_properties, properties);
+ HAL_CBACK(bt_hal_cbacks, device_found_cb, num_properties, properties);
}
} break;
case BTA_DM_INQ_CMPL_EVT: {
- BTM_BleAdvFilterParamSetup(BTM_BLE_SCAN_COND_DELETE,
- static_cast<tBTM_BLE_PF_FILT_INDEX>(0),
- nullptr,
- base::Bind(&bte_scan_filt_param_cfg_evt,
- btm_status_value(BTM_SUCCESS)));
+ do_in_main_thread(
+ FROM_HERE,
+ base::Bind(&BTM_BleAdvFilterParamSetup, BTM_BLE_SCAN_COND_DELETE, 0,
+ nullptr, base::Bind(&bte_scan_filt_param_cfg_evt, 0)));
} break;
case BTA_DM_DISC_CMPL_EVT: {
- invoke_discovery_state_changed_cb(BT_DISCOVERY_STOPPED);
+ HAL_CBACK(bt_hal_cbacks, discovery_state_changed_cb,
+ BT_DISCOVERY_STOPPED);
} break;
case BTA_DM_SEARCH_CANCEL_CMPL_EVT: {
/* if inquiry is not in progress and we get a cancel event, then
@@ -1258,21 +1389,17 @@ static void btif_dm_search_devices_evt(tBTA_DM_SEARCH_EVT event,
if (!btif_dm_inquiry_in_progress) {
btgatt_filt_param_setup_t adv_filt_param;
memset(&adv_filt_param, 0, sizeof(btgatt_filt_param_setup_t));
- BTM_BleAdvFilterParamSetup(BTM_BLE_SCAN_COND_DELETE, 0, nullptr,
- base::Bind(&bte_scan_filt_param_cfg_evt,
- btm_status_value(BTM_SUCCESS)));
- invoke_discovery_state_changed_cb(BT_DISCOVERY_STOPPED);
+ do_in_main_thread(
+ FROM_HERE,
+ base::Bind(&BTM_BleAdvFilterParamSetup, BTM_BLE_SCAN_COND_DELETE, 0,
+ nullptr, base::Bind(&bte_scan_filt_param_cfg_evt, 0)));
+ HAL_CBACK(bt_hal_cbacks, discovery_state_changed_cb,
+ BT_DISCOVERY_STOPPED);
}
} break;
}
}
-/* Returns true if |uuid| should be passed as device property */
-static bool btif_is_interesting_le_service(bluetooth::Uuid uuid) {
- return (uuid.As16Bit() == UUID_SERVCLASS_LE_HID || uuid == UUID_HEARING_AID ||
- uuid == UUID_VC);
-}
-
/*******************************************************************************
*
* Function btif_dm_search_services_evt
@@ -1282,8 +1409,10 @@ static bool btif_is_interesting_le_service(bluetooth::Uuid uuid) {
* Returns void
*
******************************************************************************/
-static void btif_dm_search_services_evt(tBTA_DM_SEARCH_EVT event,
- tBTA_DM_SEARCH* p_data) {
+static void btif_dm_search_services_evt(uint16_t event, char* p_param) {
+ tBTA_DM_SEARCH* p_data = (tBTA_DM_SEARCH*)p_param;
+
+ BTIF_TRACE_EVENT("%s: event = %d", __func__, event);
switch (event) {
case BTA_DM_DISC_RES_EVT: {
bt_property_t prop;
@@ -1292,17 +1421,19 @@ static void btif_dm_search_services_evt(tBTA_DM_SEARCH_EVT event,
RawAddress& bd_addr = p_data->disc_res.bd_addr;
- LOG_VERBOSE("result=0x%x, services 0x%x", p_data->disc_res.result,
- p_data->disc_res.services);
+ BTIF_TRACE_DEBUG("%s:(result=0x%x, services 0x%x)", __func__,
+ p_data->disc_res.result, p_data->disc_res.services);
if (p_data->disc_res.result != BTA_SUCCESS &&
pairing_cb.state == BT_BOND_STATE_BONDED &&
pairing_cb.sdp_attempts < BTIF_DM_MAX_SDP_ATTEMPTS_AFTER_PAIRING) {
if (pairing_cb.sdp_attempts) {
- LOG_WARN("SDP failed after bonding re-attempting");
+ BTIF_TRACE_WARNING("%s: SDP failed after bonding re-attempting",
+ __func__);
pairing_cb.sdp_attempts++;
- btif_dm_get_remote_services(bd_addr, BT_TRANSPORT_UNKNOWN);
+ btif_dm_get_remote_services(bd_addr);
} else {
- LOG_WARN("SDP triggered by someone failed when bonding");
+ BTIF_TRACE_WARNING("%s: SDP triggered by someone failed when bonding",
+ __func__);
}
return;
}
@@ -1314,7 +1445,7 @@ static void btif_dm_search_services_evt(tBTA_DM_SEARCH_EVT event,
prop.len = p_data->disc_res.num_uuids * Uuid::kNumBytes128;
for (i = 0; i < p_data->disc_res.num_uuids; i++) {
std::string temp = ((p_data->disc_res.p_uuid_list + i))->ToString();
- LOG_INFO("index:%d uuid:%s", i, temp.c_str());
+ LOG_INFO(LOG_TAG, "%s index:%d uuid:%s", __func__, i, temp.c_str());
}
}
@@ -1324,30 +1455,31 @@ static void btif_dm_search_services_evt(tBTA_DM_SEARCH_EVT event,
if (pairing_cb.state == BT_BOND_STATE_BONDED && pairing_cb.sdp_attempts &&
(p_data->disc_res.bd_addr == pairing_cb.bd_addr ||
p_data->disc_res.bd_addr == pairing_cb.static_bdaddr)) {
- LOG_INFO("SDP search done for %s", bd_addr.ToString().c_str());
+ LOG_INFO(LOG_TAG, "%s: SDP search done for %s", __func__,
+ bd_addr.ToString().c_str());
pairing_cb.sdp_attempts = 0;
// Both SDP and bonding are done, clear pairing control block in case
// it is not already cleared
pairing_cb = {};
- bta_dm_execute_queued_request();
// Send one empty UUID to Java to unblock pairing intent when SDP failed
// or no UUID is discovered
if (p_data->disc_res.result != BTA_SUCCESS ||
p_data->disc_res.num_uuids == 0) {
- LOG_INFO("SDP failed, send empty UUID to unblock bonding %s",
- bd_addr.ToString().c_str());
- bt_property_t prop_uuids;
+ LOG_INFO(LOG_TAG,
+ "%s: SDP failed, send empty UUID to unblock bonding %s",
+ __func__, bd_addr.ToString().c_str());
+ bt_property_t prop;
Uuid uuid = {};
- prop_uuids.type = BT_PROPERTY_UUIDS;
- prop_uuids.val = &uuid;
- prop_uuids.len = Uuid::kNumBytes128;
+ prop.type = BT_PROPERTY_UUIDS;
+ prop.val = &uuid;
+ prop.len = Uuid::kNumBytes128;
/* Send the event to the BTIF */
- invoke_remote_device_properties_cb(BT_STATUS_SUCCESS, bd_addr, 1,
- &prop_uuids);
+ HAL_CBACK(bt_hal_cbacks, remote_device_properties_cb,
+ BT_STATUS_SUCCESS, &bd_addr, 1, &prop);
break;
}
}
@@ -1358,8 +1490,8 @@ static void btif_dm_search_services_evt(tBTA_DM_SEARCH_EVT event,
ASSERTC(ret == BT_STATUS_SUCCESS, "storing remote services failed",
ret);
/* Send the event to the BTIF */
- invoke_remote_device_properties_cb(BT_STATUS_SUCCESS, bd_addr, 1,
- &prop);
+ HAL_CBACK(bt_hal_cbacks, remote_device_properties_cb, BT_STATUS_SUCCESS,
+ &bd_addr, 1, &prop);
}
} break;
@@ -1372,133 +1504,93 @@ static void btif_dm_search_services_evt(tBTA_DM_SEARCH_EVT event,
break;
case BTA_DM_DISC_BLE_RES_EVT: {
+ BTIF_TRACE_DEBUG("%s: service %s", __func__,
+ p_data->disc_ble_res.service.ToString().c_str());
int num_properties = 0;
- bt_property_t prop[2];
- std::vector<uint8_t> property_value;
- int num_uuids = 0;
-
- for (Uuid uuid : *p_data->disc_ble_res.services) {
- LOG_VERBOSE("service %s", uuid.ToString().c_str());
- if (btif_is_interesting_le_service(uuid)) {
- num_uuids++;
- auto valAsBe = uuid.To128BitBE();
- property_value.insert(property_value.end(), valAsBe.begin(),
- valAsBe.end());
- }
- }
-
- if (num_uuids == 0) {
- LOG_INFO("No well known BLE services discovered");
- return;
- }
+ if (p_data->disc_ble_res.service.As16Bit() == UUID_SERVCLASS_LE_HID ||
+ p_data->disc_ble_res.service == UUID_HEARING_AID) {
+ BTIF_TRACE_DEBUG("%s: Found HOGP or HEARING AID UUID", __func__);
+ bt_property_t prop[2];
+ bt_status_t ret;
- RawAddress& bd_addr = p_data->disc_ble_res.bd_addr;
- prop[0].type = BT_PROPERTY_UUIDS;
- prop[0].val = (void*)property_value.data();
- prop[0].len = Uuid::kNumBytes128 * num_uuids;
+ const auto& arr = p_data->disc_ble_res.service.To128BitBE();
- /* Also write this to the NVRAM */
- bt_status_t ret =
- btif_storage_set_remote_device_property(&bd_addr, &prop[0]);
- ASSERTC(ret == BT_STATUS_SUCCESS, "storing remote services failed", ret);
- num_properties++;
+ RawAddress& bd_addr = p_data->disc_ble_res.bd_addr;
+ prop[0].type = BT_PROPERTY_UUIDS;
+ prop[0].val = (void*)arr.data();
+ prop[0].len = Uuid::kNumBytes128;
- /* Remote name update */
- if (strnlen((const char*)p_data->disc_ble_res.bd_name, BD_NAME_LEN)) {
- prop[1].type = BT_PROPERTY_BDNAME;
- prop[1].val = p_data->disc_ble_res.bd_name;
- prop[1].len = strnlen((char*)p_data->disc_ble_res.bd_name, BD_NAME_LEN);
-
- ret = btif_storage_set_remote_device_property(&bd_addr, &prop[1]);
- ASSERTC(ret == BT_STATUS_SUCCESS,
- "failed to save remote device property", ret);
+ /* Also write this to the NVRAM */
+ ret = btif_storage_set_remote_device_property(&bd_addr, &prop[0]);
+ ASSERTC(ret == BT_STATUS_SUCCESS, "storing remote services failed",
+ ret);
num_properties++;
- }
- /* Send the event to the BTIF */
- invoke_remote_device_properties_cb(BT_STATUS_SUCCESS, bd_addr,
- num_properties, prop);
+ /* Remote name update */
+ if (strnlen((const char*)p_data->disc_ble_res.bd_name, BD_NAME_LEN)) {
+ prop[1].type = BT_PROPERTY_BDNAME;
+ prop[1].val = p_data->disc_ble_res.bd_name;
+ prop[1].len =
+ strnlen((char*)p_data->disc_ble_res.bd_name, BD_NAME_LEN);
+
+ ret = btif_storage_set_remote_device_property(&bd_addr, &prop[1]);
+ ASSERTC(ret == BT_STATUS_SUCCESS,
+ "failed to save remote device property", ret);
+ num_properties++;
+ }
+
+ /* Send the event to the BTIF */
+ HAL_CBACK(bt_hal_cbacks, remote_device_properties_cb, BT_STATUS_SUCCESS,
+ &bd_addr, num_properties, prop);
+ }
} break;
default: { ASSERTC(0, "unhandled search services event", event); } break;
}
}
-void BTIF_dm_report_inquiry_status_change(uint8_t status) {
- if (status == BTM_INQUIRY_STARTED) {
- invoke_discovery_state_changed_cb(BT_DISCOVERY_STARTED);
- btif_dm_inquiry_in_progress = true;
- } else if (status == BTM_INQUIRY_CANCELLED) {
- invoke_discovery_state_changed_cb(BT_DISCOVERY_STOPPED);
- btif_dm_inquiry_in_progress = false;
- } else if (status == BTM_INQUIRY_COMPLETE) {
- btif_dm_inquiry_in_progress = false;
- }
-}
-
-void BTIF_dm_on_hw_error() {
- BTIF_TRACE_ERROR("Received H/W Error. ");
- /* Flush storage data */
- btif_config_flush();
- usleep(100000); /* 100milliseconds */
- /* Killing the process to force a restart as part of fault tolerance */
- kill(getpid(), SIGKILL);
-}
-
-void BTIF_dm_enable() {
- BD_NAME bdname;
- bt_status_t status;
- bt_property_t prop;
- prop.type = BT_PROPERTY_BDNAME;
- prop.len = BD_NAME_LEN;
- prop.val = (void*)bdname;
+/*******************************************************************************
+ *
+ * Function btif_dm_remote_service_record_evt
+ *
+ * Description Executes search service record event in btif context
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btif_dm_remote_service_record_evt(uint16_t event, char* p_param) {
+ tBTA_DM_SEARCH* p_data = (tBTA_DM_SEARCH*)p_param;
- status = btif_storage_get_adapter_property(&prop);
- if (status == BT_STATUS_SUCCESS) {
- /* A name exists in the storage. Make this the device name */
- BTA_DmSetDeviceName((char*)prop.val);
- } else {
- /* Storage does not have a name yet.
- * Use the default name and write it to the chip
- */
- BTA_DmSetDeviceName(btif_get_default_local_name());
- }
+ BTIF_TRACE_EVENT("%s: event = %d", __func__, event);
+ switch (event) {
+ case BTA_DM_DISC_RES_EVT: {
+ bt_service_record_t rec;
+ bt_property_t prop;
- /* Enable local privacy */
- BTA_DmBleConfigLocalPrivacy(BLE_LOCAL_PRIVACY_ENABLED);
+ memset(&rec, 0, sizeof(bt_service_record_t));
+ RawAddress& bd_addr = p_data->disc_res.bd_addr;
- /* for each of the enabled services in the mask, trigger the profile
- * enable */
- tBTA_SERVICE_MASK service_mask = btif_get_enabled_services_mask();
- for (uint32_t i = 0; i <= BTA_MAX_SERVICE_ID; i++) {
- if (service_mask & (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(i))) {
- btif_in_execute_service_request(i, true);
- }
- }
- /* clear control blocks */
- memset(&pairing_cb, 0, sizeof(btif_dm_pairing_cb_t));
- pairing_cb.bond_type = tBTM_SEC_DEV_REC::BOND_TYPE_PERSISTENT;
+ BTIF_TRACE_DEBUG("%s:(result=0x%x, services 0x%x)", __func__,
+ p_data->disc_res.result, p_data->disc_res.services);
+ prop.type = BT_PROPERTY_SERVICE_RECORD;
+ prop.val = (void*)&rec;
+ prop.len = sizeof(rec);
+
+ /* disc_res.result is overloaded with SCN. Cannot check result */
+ p_data->disc_res.services &= ~BTA_USER_SERVICE_MASK;
+ /* TODO: Get the UUID as well */
+ rec.channel = p_data->disc_res.result - 3;
+ /* TODO: Need to get the service name using p_raw_data */
+ rec.name[0] = 0;
+
+ HAL_CBACK(bt_hal_cbacks, remote_device_properties_cb, BT_STATUS_SUCCESS,
+ &bd_addr, 1, &prop);
+ } break;
- /* This function will also trigger the adapter_properties_cb
- ** and bonded_devices_info_cb
- */
- btif_storage_load_bonded_devices();
- bluetooth::bqr::EnableBtQualityReport(true);
- btif_enable_bluetooth_evt();
-}
-
-void BTIF_dm_disable() {
- /* for each of the enabled services in the mask, trigger the profile
- * disable */
- tBTA_SERVICE_MASK service_mask = btif_get_enabled_services_mask();
- for (uint32_t i = 0; i <= BTA_MAX_SERVICE_ID; i++) {
- if (service_mask & (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(i))) {
- btif_in_execute_service_request(i, false);
- }
+ default: {
+ ASSERTC(0, "unhandled remote service record event", event);
+ } break;
}
- bluetooth::bqr::EnableBtQualityReport(false);
- LOG_INFO("Stack device manager shutdown finished");
- future_ready(stack_manager_get_hack_future(), FUTURE_SUCCESS);
}
/*******************************************************************************
@@ -1512,11 +1604,70 @@ void BTIF_dm_disable() {
******************************************************************************/
static void btif_dm_upstreams_evt(uint16_t event, char* p_param) {
tBTA_DM_SEC* p_data = (tBTA_DM_SEC*)p_param;
+ tBTA_SERVICE_MASK service_mask;
+ uint32_t i;
RawAddress bd_addr;
BTIF_TRACE_EVENT("%s: ev: %s", __func__, dump_dm_event(event));
switch (event) {
+ case BTA_DM_ENABLE_EVT: {
+ BD_NAME bdname;
+ bt_status_t status;
+ bt_property_t prop;
+ prop.type = BT_PROPERTY_BDNAME;
+ prop.len = BD_NAME_LEN;
+ prop.val = (void*)bdname;
+
+ status = btif_storage_get_adapter_property(&prop);
+ if (status == BT_STATUS_SUCCESS) {
+ /* A name exists in the storage. Make this the device name */
+ BTA_DmSetDeviceName((char*)prop.val);
+ } else {
+ /* Storage does not have a name yet.
+ * Use the default name and write it to the chip
+ */
+ BTA_DmSetDeviceName(btif_get_default_local_name());
+ }
+
+ /* Enable local privacy */
+ BTA_DmBleConfigLocalPrivacy(BLE_LOCAL_PRIVACY_ENABLED);
+
+ /* for each of the enabled services in the mask, trigger the profile
+ * enable */
+ service_mask = btif_get_enabled_services_mask();
+ for (i = 0; i <= BTA_MAX_SERVICE_ID; i++) {
+ if (service_mask &
+ (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(i))) {
+ btif_in_execute_service_request(i, true);
+ }
+ }
+ /* clear control blocks */
+ memset(&pairing_cb, 0, sizeof(btif_dm_pairing_cb_t));
+ pairing_cb.bond_type = BOND_TYPE_PERSISTENT;
+
+ /* This function will also trigger the adapter_properties_cb
+ ** and bonded_devices_info_cb
+ */
+ btif_storage_load_bonded_devices();
+ bluetooth::bqr::EnableBtQualityReport(true);
+ btif_enable_bluetooth_evt(p_data->enable.status);
+ } break;
+
+ case BTA_DM_DISABLE_EVT:
+ /* for each of the enabled services in the mask, trigger the profile
+ * disable */
+ service_mask = btif_get_enabled_services_mask();
+ for (i = 0; i <= BTA_MAX_SERVICE_ID; i++) {
+ if (service_mask &
+ (tBTA_SERVICE_MASK)(BTA_SERVICE_ID_TO_SERVICE_MASK(i))) {
+ btif_in_execute_service_request(i, false);
+ }
+ }
+ bluetooth::bqr::EnableBtQualityReport(false);
+ btif_disable_bluetooth_evt();
+ break;
+
case BTA_DM_PIN_REQ_EVT:
btif_dm_pin_req_evt(&p_data->pin_req);
break;
@@ -1528,8 +1679,7 @@ static void btif_dm_upstreams_evt(uint16_t event, char* p_param) {
case BTA_DM_BOND_CANCEL_CMPL_EVT:
if (is_bonding_or_sdp()) {
bd_addr = pairing_cb.bd_addr;
- btm_set_bond_type_dev(pairing_cb.bd_addr,
- tBTM_SEC_DEV_REC::BOND_TYPE_UNKNOWN);
+ btm_set_bond_type_dev(pairing_cb.bd_addr, BOND_TYPE_UNKNOWN);
bond_state_changed((bt_status_t)p_data->bond_cancel_cmpl.result,
bd_addr, BT_BOND_STATE_NONE);
}
@@ -1544,8 +1694,7 @@ static void btif_dm_upstreams_evt(uint16_t event, char* p_param) {
case BTA_DM_DEV_UNPAIRED_EVT:
bd_addr = p_data->link_down.bd_addr;
- btm_set_bond_type_dev(p_data->link_down.bd_addr,
- tBTM_SEC_DEV_REC::BOND_TYPE_UNKNOWN);
+ btm_set_bond_type_dev(p_data->link_down.bd_addr, BOND_TYPE_UNKNOWN);
/*special handling for HID devices */
#if (defined(BTA_HH_INCLUDED) && (BTA_HH_INCLUDED == TRUE))
@@ -1559,31 +1708,49 @@ static void btif_dm_upstreams_evt(uint16_t event, char* p_param) {
bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_NONE);
break;
+ case BTA_DM_BUSY_LEVEL_EVT: {
+ if (p_data->busy_level.level_flags & BTM_BL_INQUIRY_PAGING_MASK) {
+ if (p_data->busy_level.level_flags == BTM_BL_INQUIRY_STARTED) {
+ HAL_CBACK(bt_hal_cbacks, discovery_state_changed_cb,
+ BT_DISCOVERY_STARTED);
+ btif_dm_inquiry_in_progress = true;
+ } else if (p_data->busy_level.level_flags == BTM_BL_INQUIRY_CANCELLED) {
+ HAL_CBACK(bt_hal_cbacks, discovery_state_changed_cb,
+ BT_DISCOVERY_STOPPED);
+ btif_dm_inquiry_in_progress = false;
+ } else if (p_data->busy_level.level_flags == BTM_BL_INQUIRY_COMPLETE) {
+ btif_dm_inquiry_in_progress = false;
+ }
+ }
+ } break;
+
case BTA_DM_LINK_UP_EVT:
bd_addr = p_data->link_up.bd_addr;
BTIF_TRACE_DEBUG("BTA_DM_LINK_UP_EVT. Sending BT_ACL_STATE_CONNECTED");
btif_update_remote_version_property(&bd_addr);
- invoke_acl_state_changed_cb(BT_STATUS_SUCCESS, bd_addr,
- BT_ACL_STATE_CONNECTED, HCI_SUCCESS);
+ HAL_CBACK(bt_hal_cbacks, acl_state_changed_cb, BT_STATUS_SUCCESS,
+ &bd_addr, BT_ACL_STATE_CONNECTED);
break;
case BTA_DM_LINK_DOWN_EVT:
bd_addr = p_data->link_down.bd_addr;
- btm_set_bond_type_dev(p_data->link_down.bd_addr,
- tBTM_SEC_DEV_REC::BOND_TYPE_UNKNOWN);
+ btm_set_bond_type_dev(p_data->link_down.bd_addr, BOND_TYPE_UNKNOWN);
btif_av_acl_disconnected(bd_addr);
- invoke_acl_state_changed_cb(BT_STATUS_SUCCESS, bd_addr,
- BT_ACL_STATE_DISCONNECTED,
- static_cast<bt_hci_error_code_t>(btm_get_acl_disc_reason_code()));
- LOG_DEBUG(
- "Sent BT_ACL_STATE_DISCONNECTED upward as ACL link down event "
- "device:%s reason:%s",
- PRIVATE_ADDRESS(bd_addr),
- hci_reason_code_text(
- static_cast<tHCI_REASON>(btm_get_acl_disc_reason_code()))
- .c_str());
+ BTIF_TRACE_DEBUG(
+ "BTA_DM_LINK_DOWN_EVT. Sending BT_ACL_STATE_DISCONNECTED");
+ HAL_CBACK(bt_hal_cbacks, acl_state_changed_cb, BT_STATUS_SUCCESS,
+ &bd_addr, BT_ACL_STATE_DISCONNECTED);
+ break;
+
+ case BTA_DM_HW_ERROR_EVT:
+ BTIF_TRACE_ERROR("Received H/W Error. ");
+ /* Flush storage data */
+ btif_config_flush();
+ usleep(100000); /* 100milliseconds */
+ /* Killing the process to force a restart as part of fault tolerance */
+ kill(getpid(), SIGKILL);
break;
case BTA_DM_BLE_KEY_EVT:
@@ -1608,38 +1775,38 @@ static void btif_dm_upstreams_evt(uint16_t event, char* p_param) {
}
switch (p_data->ble_key.key_type) {
- case BTM_LE_KEY_PENC:
- BTIF_TRACE_DEBUG("Rcv BTM_LE_KEY_PENC");
+ case BTA_LE_KEY_PENC:
+ BTIF_TRACE_DEBUG("Rcv BTA_LE_KEY_PENC");
pairing_cb.ble.is_penc_key_rcvd = true;
pairing_cb.ble.penc_key = p_data->ble_key.p_key_value->penc_key;
break;
- case BTM_LE_KEY_PID:
- BTIF_TRACE_DEBUG("Rcv BTM_LE_KEY_PID");
+ case BTA_LE_KEY_PID:
+ BTIF_TRACE_DEBUG("Rcv BTA_LE_KEY_PID");
pairing_cb.ble.is_pid_key_rcvd = true;
pairing_cb.ble.pid_key = p_data->ble_key.p_key_value->pid_key;
break;
- case BTM_LE_KEY_PCSRK:
- BTIF_TRACE_DEBUG("Rcv BTM_LE_KEY_PCSRK");
+ case BTA_LE_KEY_PCSRK:
+ BTIF_TRACE_DEBUG("Rcv BTA_LE_KEY_PCSRK");
pairing_cb.ble.is_pcsrk_key_rcvd = true;
pairing_cb.ble.pcsrk_key = p_data->ble_key.p_key_value->pcsrk_key;
break;
- case BTM_LE_KEY_LENC:
- BTIF_TRACE_DEBUG("Rcv BTM_LE_KEY_LENC");
+ case BTA_LE_KEY_LENC:
+ BTIF_TRACE_DEBUG("Rcv BTA_LE_KEY_LENC");
pairing_cb.ble.is_lenc_key_rcvd = true;
pairing_cb.ble.lenc_key = p_data->ble_key.p_key_value->lenc_key;
break;
- case BTM_LE_KEY_LCSRK:
- BTIF_TRACE_DEBUG("Rcv BTM_LE_KEY_LCSRK");
+ case BTA_LE_KEY_LCSRK:
+ BTIF_TRACE_DEBUG("Rcv BTA_LE_KEY_LCSRK");
pairing_cb.ble.is_lcsrk_key_rcvd = true;
pairing_cb.ble.lcsrk_key = p_data->ble_key.p_key_value->lcsrk_key;
break;
- case BTM_LE_KEY_LID:
- BTIF_TRACE_DEBUG("Rcv BTM_LE_KEY_LID");
+ case BTA_LE_KEY_LID:
+ BTIF_TRACE_DEBUG("Rcv BTA_LE_KEY_LID");
pairing_cb.ble.is_lidk_key_rcvd = true;
break;
@@ -1677,13 +1844,6 @@ static void btif_dm_upstreams_evt(uint16_t event, char* p_param) {
BTIF_TRACE_DEBUG("BTA_DM_BLE_SC_OOB_REQ_EVT. ");
btif_dm_ble_sc_oob_req_evt(&p_data->rmt_oob);
break;
- case BTA_DM_BLE_SC_CR_LOC_OOB_EVT:
- BTIF_TRACE_DEBUG("BTA_DM_BLE_SC_CR_LOC_OOB_EVT");
- btif_dm_proc_loc_oob(BT_TRANSPORT_LE, true,
- p_data->local_oob_data.local_oob_c,
- p_data->local_oob_data.local_oob_r);
- break;
-
case BTA_DM_BLE_LOCAL_IR_EVT:
BTIF_TRACE_DEBUG("BTA_DM_BLE_LOCAL_IR_EVT. ");
ble_local_key_cb.is_id_keys_rcvd = true;
@@ -1713,15 +1873,17 @@ static void btif_dm_upstreams_evt(uint16_t event, char* p_param) {
case BTA_DM_LE_FEATURES_READ: {
tBTM_BLE_VSC_CB cmn_vsc_cb;
bt_local_le_features_t local_le_features;
+ char buf[512];
bt_property_t prop;
prop.type = BT_PROPERTY_LOCAL_LE_FEATURES;
- prop.val = (void*)&local_le_features;
- prop.len = sizeof(bt_local_le_features_t);
+ prop.val = (void*)buf;
+ prop.len = sizeof(buf);
/* LE features are not stored in storage. Should be retrived from stack */
BTM_BleGetVendorCapabilities(&cmn_vsc_cb);
local_le_features.local_privacy_enabled = BTM_BleLocalPrivacyEnabled();
+ prop.len = sizeof(bt_local_le_features_t);
if (cmn_vsc_cb.filter_support == 1)
local_le_features.max_adv_filter_supported = cmn_vsc_cb.max_filter;
else
@@ -1754,17 +1916,98 @@ static void btif_dm_upstreams_evt(uint16_t event, char* p_param) {
local_le_features.le_maximum_advertising_data_length =
controller->get_ble_maxium_advertising_data_length();
- local_le_features.dynamic_audio_buffer_supported =
- cmn_vsc_cb.dynamic_audio_buffer_support;
+ memcpy(prop.val, &local_le_features, prop.len);
+ HAL_CBACK(bt_hal_cbacks, adapter_properties_cb, BT_STATUS_SUCCESS, 1,
+ &prop);
+ break;
+ }
- invoke_adapter_properties_cb(BT_STATUS_SUCCESS, 1, &prop);
+ case BTA_DM_ENER_INFO_READ: {
+ btif_activity_energy_info_cb_t* p_ener_data =
+ (btif_activity_energy_info_cb_t*)p_param;
+ bt_activity_energy_info energy_info;
+ energy_info.status = p_ener_data->status;
+ energy_info.ctrl_state = p_ener_data->ctrl_state;
+ energy_info.rx_time = p_ener_data->rx_time;
+ energy_info.tx_time = p_ener_data->tx_time;
+ energy_info.idle_time = p_ener_data->idle_time;
+ energy_info.energy_used = p_ener_data->energy_used;
+
+ bt_uid_traffic_t* data = uid_set_read_and_clear(uid_set);
+ HAL_CBACK(bt_hal_cbacks, energy_info_cb, &energy_info, data);
+ osi_free(data);
break;
}
+ case BTA_DM_AUTHORIZE_EVT:
+ case BTA_DM_SIG_STRENGTH_EVT:
+ case BTA_DM_SP_RMT_OOB_EVT:
+ case BTA_DM_SP_KEYPRESS_EVT:
+ case BTA_DM_ROLE_CHG_EVT:
+
default:
BTIF_TRACE_WARNING("%s: unhandled event (%d)", __func__, event);
break;
}
+
+ btif_dm_data_free(event, p_data);
+}
+
+/*******************************************************************************
+ *
+ * Function btif_dm_generic_evt
+ *
+ * Description Executes non-BTA upstream events in BTIF context
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btif_dm_generic_evt(uint16_t event, char* p_param) {
+ BTIF_TRACE_EVENT("%s: event=%d", __func__, event);
+ switch (event) {
+ case BTIF_DM_CB_DISCOVERY_STARTED: {
+ HAL_CBACK(bt_hal_cbacks, discovery_state_changed_cb,
+ BT_DISCOVERY_STARTED);
+ } break;
+
+ case BTIF_DM_CB_CREATE_BOND: {
+ pairing_cb.timeout_retries = NUM_TIMEOUT_RETRIES;
+ btif_dm_create_bond_cb_t* create_bond_cb =
+ (btif_dm_create_bond_cb_t*)p_param;
+ btif_dm_cb_create_bond(create_bond_cb->bdaddr, create_bond_cb->transport);
+ } break;
+
+ case BTIF_DM_CB_REMOVE_BOND: {
+ btif_dm_cb_remove_bond((RawAddress*)p_param);
+ } break;
+
+ case BTIF_DM_CB_HID_REMOTE_NAME: {
+ btif_dm_cb_hid_remote_name((tBTM_REMOTE_DEV_NAME*)p_param);
+ } break;
+
+ case BTIF_DM_CB_BOND_STATE_BONDING: {
+ bond_state_changed(BT_STATUS_SUCCESS, *((RawAddress*)p_param),
+ BT_BOND_STATE_BONDING);
+ } break;
+ case BTIF_DM_CB_LE_TX_TEST:
+ case BTIF_DM_CB_LE_RX_TEST: {
+ uint8_t status;
+ STREAM_TO_UINT8(status, p_param);
+ HAL_CBACK(bt_hal_cbacks, le_test_mode_cb,
+ (status == 0) ? BT_STATUS_SUCCESS : BT_STATUS_FAIL, 0);
+ } break;
+ case BTIF_DM_CB_LE_TEST_END: {
+ uint8_t status;
+ uint16_t count = 0;
+ STREAM_TO_UINT8(status, p_param);
+ if (status == 0) STREAM_TO_UINT16(count, p_param);
+ HAL_CBACK(bt_hal_cbacks, le_test_mode_cb,
+ (status == 0) ? BT_STATUS_SUCCESS : BT_STATUS_FAIL, count);
+ } break;
+ default: {
+ BTIF_TRACE_WARNING("%s : Unknown event 0x%x", __func__, event);
+ } break;
+ }
}
/*******************************************************************************
@@ -1778,7 +2021,102 @@ static void btif_dm_upstreams_evt(uint16_t event, char* p_param) {
******************************************************************************/
void bte_dm_evt(tBTA_DM_SEC_EVT event, tBTA_DM_SEC* p_data) {
- btif_dm_upstreams_evt(event, (char*)p_data);
+ /* switch context to btif task context (copy full union size for convenience)
+ */
+ bt_status_t status = btif_transfer_context(
+ btif_dm_upstreams_evt, (uint16_t)event, (char*)p_data,
+ sizeof(tBTA_DM_SEC), btif_dm_data_copy);
+
+ /* catch any failed context transfers */
+ ASSERTC(status == BT_STATUS_SUCCESS, "context transfer failed", status);
+}
+
+/*******************************************************************************
+ *
+ * Function bte_search_devices_evt
+ *
+ * Description Switches context from BTE to BTIF for DM search events
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void bte_search_devices_evt(tBTA_DM_SEARCH_EVT event,
+ tBTA_DM_SEARCH* p_data) {
+ uint16_t param_len = 0;
+
+ if (p_data) param_len += sizeof(tBTA_DM_SEARCH);
+ /* Allocate buffer to hold the pointers (deep copy). The pointers will point
+ * to the end of the tBTA_DM_SEARCH */
+ switch (event) {
+ case BTA_DM_INQ_RES_EVT: {
+ if (p_data->inq_res.p_eir) param_len += p_data->inq_res.eir_len;
+ } break;
+
+ case BTA_DM_DISC_RES_EVT: {
+ if (p_data->disc_res.raw_data_size && p_data->disc_res.p_raw_data)
+ param_len += p_data->disc_res.raw_data_size;
+ } break;
+ }
+ BTIF_TRACE_DEBUG("%s event=%s param_len=%d", __func__,
+ dump_dm_search_event(event), param_len);
+
+ /* if remote name is available in EIR, set teh flag so that stack doesnt
+ * trigger RNR */
+ if (event == BTA_DM_INQ_RES_EVT)
+ p_data->inq_res.remt_name_not_required =
+ check_eir_remote_name(p_data, NULL, NULL);
+
+ btif_transfer_context(
+ btif_dm_search_devices_evt, (uint16_t)event, (char*)p_data, param_len,
+ (param_len > sizeof(tBTA_DM_SEARCH)) ? search_devices_copy_cb : NULL);
+}
+
+/*******************************************************************************
+ *
+ * Function bte_dm_search_services_evt
+ *
+ * Description Switches context from BTE to BTIF for DM search services
+ * event
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void bte_dm_search_services_evt(tBTA_DM_SEARCH_EVT event,
+ tBTA_DM_SEARCH* p_data) {
+ uint16_t param_len = 0;
+ if (p_data) param_len += sizeof(tBTA_DM_SEARCH);
+ switch (event) {
+ case BTA_DM_DISC_RES_EVT: {
+ if ((p_data->disc_res.result == BTA_SUCCESS) &&
+ (p_data->disc_res.num_uuids > 0)) {
+ param_len += (p_data->disc_res.num_uuids * Uuid::kNumBytes128);
+ }
+ } break;
+ }
+ /* TODO: The only other member that needs a deep copy is the p_raw_data. But
+ * not sure
+ * if raw_data is needed. */
+ btif_transfer_context(
+ btif_dm_search_services_evt, event, (char*)p_data, param_len,
+ (param_len > sizeof(tBTA_DM_SEARCH)) ? search_services_copy_cb : NULL);
+}
+
+/*******************************************************************************
+ *
+ * Function bte_dm_remote_service_record_evt
+ *
+ * Description Switches context from BTE to BTIF for DM search service
+ * record event
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void bte_dm_remote_service_record_evt(tBTA_DM_SEARCH_EVT event,
+ tBTA_DM_SEARCH* p_data) {
+ /* TODO: The only member that needs a deep copy is the p_raw_data. But not
+ * sure yet if this is needed. */
+ btif_transfer_context(btif_dm_remote_service_record_evt, event, (char*)p_data,
+ sizeof(tBTA_DM_SEARCH), NULL);
}
/*******************************************************************************
@@ -1790,10 +2128,10 @@ void bte_dm_evt(tBTA_DM_SEC_EVT event, tBTA_DM_SEC* p_data) {
* Returns void
*
******************************************************************************/
-static void bta_energy_info_cb(tBTM_BLE_TX_TIME_MS tx_time,
- tBTM_BLE_RX_TIME_MS rx_time,
- tBTM_BLE_IDLE_TIME_MS idle_time,
- tBTM_BLE_ENERGY_USED energy_used,
+static void bta_energy_info_cb(tBTA_DM_BLE_TX_TIME_MS tx_time,
+ tBTA_DM_BLE_RX_TIME_MS rx_time,
+ tBTA_DM_BLE_IDLE_TIME_MS idle_time,
+ tBTA_DM_BLE_ENERGY_USED energy_used,
tBTA_DM_CONTRL_STATE ctrl_state,
tBTA_STATUS status) {
BTIF_TRACE_DEBUG(
@@ -1801,27 +2139,26 @@ static void bta_energy_info_cb(tBTM_BLE_TX_TIME_MS tx_time,
"idle_time=%ld,used=%ld",
status, ctrl_state, tx_time, rx_time, idle_time, energy_used);
- bt_activity_energy_info energy_info;
- energy_info.status = status;
- energy_info.ctrl_state = ctrl_state;
- energy_info.rx_time = rx_time;
- energy_info.tx_time = tx_time;
- energy_info.idle_time = idle_time;
- energy_info.energy_used = energy_used;
-
- bt_uid_traffic_t* data = uid_set_read_and_clear(uid_set);
- invoke_energy_info_cb(energy_info, data);
+ btif_activity_energy_info_cb_t btif_cb;
+ btif_cb.status = status;
+ btif_cb.ctrl_state = ctrl_state;
+ btif_cb.tx_time = (uint64_t)tx_time;
+ btif_cb.rx_time = (uint64_t)rx_time;
+ btif_cb.idle_time = (uint64_t)idle_time;
+ btif_cb.energy_used = (uint64_t)energy_used;
+ btif_transfer_context(btif_dm_upstreams_evt, BTA_DM_ENER_INFO_READ,
+ (char*)&btif_cb, sizeof(btif_activity_energy_info_cb_t),
+ NULL);
}
/* Scan filter param config event */
static void bte_scan_filt_param_cfg_evt(uint8_t ref_value, uint8_t avbl_space,
- uint8_t action_type,
- uint8_t btm_status) {
+ uint8_t action_type, uint8_t status) {
/* This event occurs on calling BTA_DmBleCfgFilterCondition internally,
** and that is why there is no HAL callback
*/
- if (btm_status != btm_status_value(BTM_SUCCESS)) {
- BTIF_TRACE_ERROR("%s, %d", __func__, btm_status);
+ if (BTA_SUCCESS != status) {
+ BTIF_TRACE_ERROR("%s, %d", __func__, status);
} else {
BTIF_TRACE_DEBUG("%s", __func__);
}
@@ -1839,20 +2176,20 @@ static void bte_scan_filt_param_cfg_evt(uint8_t ref_value, uint8_t avbl_space,
*
* Description Start device discovery/inquiry
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_start_discovery(void) {
- BTIF_TRACE_EVENT("%s", __func__);
+bt_status_t btif_dm_start_discovery(void) {
+ tBTA_DM_INQ inq_params;
+ tBTA_SERVICE_MASK services = 0;
- if (bta_dm_is_search_request_queued()) {
- LOG_INFO("%s skipping start discovery because a request is queued",
- __func__);
- return;
- }
+ BTIF_TRACE_EVENT("%s", __func__);
/* Cleanup anything remaining on index 0 */
- BTM_BleAdvFilterParamSetup(
- BTM_BLE_SCAN_COND_DELETE, static_cast<tBTM_BLE_PF_FILT_INDEX>(0), nullptr,
- base::Bind(&bte_scan_filt_param_cfg_evt, btm_status_value(BTM_SUCCESS)));
+ do_in_main_thread(
+ FROM_HERE,
+ base::Bind(&BTM_BleAdvFilterParamSetup, BTM_BLE_SCAN_COND_DELETE, 0,
+ nullptr, base::Bind(&bte_scan_filt_param_cfg_evt, 0)));
auto adv_filt_param = std::make_unique<btgatt_filt_param_setup_t>();
/* Add an allow-all filter on index 0*/
@@ -1862,15 +2199,29 @@ void btif_dm_start_discovery(void) {
adv_filt_param->list_logic_type = BTA_DM_BLE_PF_LIST_LOGIC_OR;
adv_filt_param->rssi_low_thres = LOWEST_RSSI_VALUE;
adv_filt_param->rssi_high_thres = LOWEST_RSSI_VALUE;
- BTM_BleAdvFilterParamSetup(
- BTM_BLE_SCAN_COND_ADD, static_cast<tBTM_BLE_PF_FILT_INDEX>(0),
- std::move(adv_filt_param),
- base::Bind(&bte_scan_filt_param_cfg_evt, btm_status_value(BTM_SUCCESS)));
+ do_in_main_thread(
+ FROM_HERE, base::Bind(&BTM_BleAdvFilterParamSetup, BTM_BLE_SCAN_COND_ADD,
+ 0, base::Passed(&adv_filt_param),
+ base::Bind(&bte_scan_filt_param_cfg_evt, 0)));
+
+ /* TODO: Do we need to handle multiple inquiries at the same time? */
+
+ /* Set inquiry params and call API */
+ inq_params.mode = BTA_DM_GENERAL_INQUIRY | BTA_BLE_GENERAL_INQUIRY;
+ inq_params.duration = BTIF_DM_DEFAULT_INQ_MAX_DURATION;
+
+ inq_params.max_resps = BTIF_DM_DEFAULT_INQ_MAX_RESULTS;
+ inq_params.report_dup = true;
+
+ inq_params.filter_type = BTA_DM_INQ_CLR;
+ /* TODO: Filter device by BDA needs to be implemented here */
/* Will be enabled to true once inquiry busy level has been received */
btif_dm_inquiry_in_progress = false;
/* find nearby devices */
- BTA_DmSearch(btif_dm_search_devices_evt, is_bonding_or_sdp());
+ BTA_DmSearch(&inq_params, services, bte_search_devices_evt);
+
+ return BT_STATUS_SUCCESS;
}
/*******************************************************************************
@@ -1879,14 +2230,13 @@ void btif_dm_start_discovery(void) {
*
* Description Cancels search
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_cancel_discovery(void) {
- LOG_INFO("Cancel search");
+bt_status_t btif_dm_cancel_discovery(void) {
+ BTIF_TRACE_EVENT("%s", __func__);
BTA_DmSearchCancel();
-}
-
-bool btif_dm_pairing_is_busy() {
- return pairing_cb.state != BT_BOND_STATE_NONE;
+ return BT_STATUS_SUCCESS;
}
/*******************************************************************************
@@ -1895,15 +2245,26 @@ bool btif_dm_pairing_is_busy() {
*
* Description Initiate bonding with the specified device
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_create_bond(const RawAddress bd_addr, int transport) {
+bt_status_t btif_dm_create_bond(const RawAddress* bd_addr, int transport) {
+ btif_dm_create_bond_cb_t create_bond_cb;
+ create_bond_cb.transport = transport;
+ create_bond_cb.bdaddr = *bd_addr;
+
BTIF_TRACE_EVENT("%s: bd_addr=%s, transport=%d", __func__,
- bd_addr.ToString().c_str(), transport);
- btif_stats_add_bond_event(bd_addr, BTIF_DM_FUNC_CREATE_BOND,
+ bd_addr->ToString().c_str(), transport);
+ if (pairing_cb.state != BT_BOND_STATE_NONE) return BT_STATUS_BUSY;
+
+ btif_stats_add_bond_event(*bd_addr, BTIF_DM_FUNC_CREATE_BOND,
pairing_cb.state);
- pairing_cb.timeout_retries = NUM_TIMEOUT_RETRIES;
- btif_dm_cb_create_bond(bd_addr, transport);
+ btif_transfer_context(btif_dm_generic_evt, BTIF_DM_CB_CREATE_BOND,
+ (char*)&create_bond_cb,
+ sizeof(btif_dm_create_bond_cb_t), NULL);
+
+ return BT_STATUS_SUCCESS;
}
/*******************************************************************************
@@ -1913,97 +2274,31 @@ void btif_dm_create_bond(const RawAddress bd_addr, int transport) {
* Description Initiate bonding with the specified device using out of band
* data
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_create_bond_out_of_band(const RawAddress bd_addr,
- tBT_TRANSPORT transport,
- const bt_oob_data_t p192_data,
- const bt_oob_data_t p256_data) {
- bt_oob_data_t empty_data;
- memset(&empty_data, 0, sizeof(empty_data));
-
- oob_cb.bdaddr = bd_addr;
- oob_cb.transport = transport;
- oob_cb.data_present = (int)BTM_OOB_NONE;
- if (memcmp(&p192_data, &empty_data, sizeof(p192_data)) != 0) {
- memcpy(&oob_cb.p192_data, &p192_data, sizeof(bt_oob_data_t));
- oob_cb.data_present = (int)BTM_OOB_PRESENT_192;
- }
-
- if (memcmp(&p256_data, &empty_data, sizeof(p256_data)) != 0) {
- memcpy(&oob_cb.p256_data, &p256_data, sizeof(bt_oob_data_t));
- if (oob_cb.data_present == (int)BTM_OOB_PRESENT_192) {
- oob_cb.data_present = (int)BTM_OOB_PRESENT_192_AND_256;
- } else {
- oob_cb.data_present = (int)BTM_OOB_PRESENT_256;
- }
- }
+bt_status_t btif_dm_create_bond_out_of_band(
+ const RawAddress* bd_addr, int transport,
+ const bt_out_of_band_data_t* oob_data) {
+ oob_cb.bdaddr = *bd_addr;
+ memcpy(&oob_cb.oob_data, oob_data, sizeof(bt_out_of_band_data_t));
uint8_t empty[] = {0, 0, 0, 0, 0, 0, 0};
- switch (transport) {
- case BT_TRANSPORT_BR_EDR:
- // TODO(182162589): Flesh out classic impl in legacy BTMSec
- // Nothing to do yet, but not an error
-
- // The controller only supports P192
- switch (oob_cb.data_present) {
- case BTM_OOB_PRESENT_192_AND_256:
- LOG_INFO("Have both P192 and P256");
- [[fallthrough]];
- case BTM_OOB_PRESENT_192:
- LOG_INFO("Using P192");
- break;
- case BTM_OOB_PRESENT_256:
- LOG_INFO("Using P256");
- [[fallthrough]];
- default:
- // TODO(181889116):
- // Upgrade to support p256 (for now we just ignore P256)
- // because the controllers do not yet support it.
- LOG_ERROR("Invalid data present for controller: %d",
- oob_cb.data_present);
- bond_state_changed(BT_STATUS_FAIL, bd_addr, BT_BOND_STATE_NONE);
- return;
- }
- pairing_cb.is_local_initiated = true;
- LOG_ERROR("Classic not implemented yet");
- bond_state_changed(BT_STATUS_FAIL, bd_addr, BT_BOND_STATE_NONE);
- return;
- case BT_TRANSPORT_LE: {
- // Guess default RANDOM for address type for LE
- tBLE_ADDR_TYPE address_type = BLE_ADDR_RANDOM;
- LOG_INFO("Using LE Transport");
- switch (oob_cb.data_present) {
- case BTM_OOB_PRESENT_192_AND_256:
- LOG_INFO("Have both P192 and P256");
- [[fallthrough]];
- // Always prefer 256 for LE
- case BTM_OOB_PRESENT_256:
- LOG_INFO("Using P256");
- // If we have an address, lets get the type
- if (memcmp(p256_data.address, empty, 7) != 0) {
- /* byte no 7 is address type in LE Bluetooth Address OOB data */
- address_type = static_cast<tBLE_ADDR_TYPE>(p256_data.address[6]);
- }
- break;
- case BTM_OOB_PRESENT_192:
- LOG_INFO("Using P192");
- // If we have an address, lets get the type
- if (memcmp(p192_data.address, empty, 7) != 0) {
- /* byte no 7 is address type in LE Bluetooth Address OOB data */
- address_type = static_cast<tBLE_ADDR_TYPE>(p192_data.address[6]);
- }
- break;
- }
- pairing_cb.is_local_initiated = true;
- BTM_SecAddBleDevice(bd_addr, BT_DEVICE_TYPE_BLE, address_type);
- BTA_DmBond(bd_addr, address_type, transport, BT_DEVICE_TYPE_BLE);
- break;
+ // If LE Bluetooth Device Address is provided, use provided address type
+ // value.
+ if (memcmp(oob_data->le_bt_dev_addr, empty, 7) != 0) {
+ /* byte no 7 is address type in LE Bluetooth Address OOB data */
+ uint8_t address_type = oob_data->le_bt_dev_addr[6];
+ if (address_type == BLE_ADDR_PUBLIC || address_type == BLE_ADDR_RANDOM) {
+ // bd_addr->address is already reversed, so use it instead of
+ // oob_data->le_bt_dev_addr
+ BTM_SecAddBleDevice(*bd_addr, NULL, BT_DEVICE_TYPE_BLE, address_type);
}
- default:
- LOG_ERROR("Invalid transport: %d", transport);
- bond_state_changed(BT_STATUS_FAIL, bd_addr, BT_BOND_STATE_NONE);
- return;
}
+
+ BTIF_TRACE_EVENT("%s: bd_addr=%s, transport=%d", __func__,
+ bd_addr->ToString().c_str(), transport);
+ return btif_dm_create_bond(bd_addr, transport);
}
/*******************************************************************************
@@ -2012,11 +2307,14 @@ void btif_dm_create_bond_out_of_band(const RawAddress bd_addr,
*
* Description Initiate bonding with the specified device
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_cancel_bond(const RawAddress bd_addr) {
- BTIF_TRACE_EVENT("%s: bd_addr=%s", __func__, bd_addr.ToString().c_str());
- btif_stats_add_bond_event(bd_addr, BTIF_DM_FUNC_CANCEL_BOND,
+bt_status_t btif_dm_cancel_bond(const RawAddress* bd_addr) {
+ BTIF_TRACE_EVENT("%s: bd_addr=%s", __func__, bd_addr->ToString().c_str());
+
+ btif_stats_add_bond_event(*bd_addr, BTIF_DM_FUNC_CANCEL_BOND,
pairing_cb.state);
/* TODO:
@@ -2026,22 +2324,24 @@ void btif_dm_cancel_bond(const RawAddress bd_addr) {
if (is_bonding_or_sdp()) {
if (pairing_cb.is_ssp) {
if (pairing_cb.is_le_only) {
- BTA_DmBleSecurityGrant(bd_addr, BTA_DM_SEC_PAIR_NOT_SPT);
+ BTA_DmBleSecurityGrant(*bd_addr, BTA_DM_SEC_PAIR_NOT_SPT);
} else {
- BTA_DmConfirm(bd_addr, false);
- BTA_DmBondCancel(bd_addr);
- btif_storage_remove_bonded_device(&bd_addr);
+ BTA_DmConfirm(*bd_addr, false);
+ BTA_DmBondCancel(*bd_addr);
+ btif_storage_remove_bonded_device(bd_addr);
}
} else {
if (pairing_cb.is_le_only) {
- BTA_DmBondCancel(bd_addr);
+ BTA_DmBondCancel(*bd_addr);
} else {
- BTA_DmPinReply(bd_addr, false, 0, NULL);
+ BTA_DmPinReply(*bd_addr, false, 0, NULL);
}
/* Cancel bonding, in case it is in ACL connection setup state */
- BTA_DmBondCancel(bd_addr);
+ BTA_DmBondCancel(*bd_addr);
}
}
+
+ return BT_STATUS_SUCCESS;
}
/*******************************************************************************
@@ -2068,25 +2368,20 @@ void btif_dm_hh_open_failed(RawAddress* bdaddr) {
*
* Description Removes bonding with the specified device
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_remove_bond(const RawAddress bd_addr) {
- BTIF_TRACE_EVENT("%s: bd_addr=%s", __func__, bd_addr.ToString().c_str());
+bt_status_t btif_dm_remove_bond(const RawAddress* bd_addr) {
+ BTIF_TRACE_EVENT("%s: bd_addr=%s", __func__, bd_addr->ToString().c_str());
- btif_stats_add_bond_event(bd_addr, BTIF_DM_FUNC_REMOVE_BOND,
+ btif_stats_add_bond_event(*bd_addr, BTIF_DM_FUNC_REMOVE_BOND,
pairing_cb.state);
- // special handling for HID devices
- // VUP needs to be sent if its a HID Device. The HID HOST module will check if
- // there is a valid hid connection with this bd_addr. If yes VUP will be
- // issued.
-#if (BTA_HH_INCLUDED == TRUE)
- if (btif_hh_virtual_unplug(&bd_addr) != BT_STATUS_SUCCESS)
-#endif
- {
- BTIF_TRACE_DEBUG("%s: Removing HH device", __func__);
- BTA_DmRemoveDevice(bd_addr);
- }
+ btif_transfer_context(btif_dm_generic_evt, BTIF_DM_CB_REMOVE_BOND,
+ (char*)bd_addr, sizeof(RawAddress), NULL);
+
+ return BT_STATUS_SUCCESS;
}
/*******************************************************************************
@@ -2095,26 +2390,29 @@ void btif_dm_remove_bond(const RawAddress bd_addr) {
*
* Description BT legacy pairing - PIN code reply
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_pin_reply(const RawAddress bd_addr, uint8_t accept,
- uint8_t pin_len, bt_pin_code_t pin_code) {
+bt_status_t btif_dm_pin_reply(const RawAddress* bd_addr, uint8_t accept,
+ uint8_t pin_len, bt_pin_code_t* pin_code) {
BTIF_TRACE_EVENT("%s: accept=%d", __func__, accept);
-
+ if (pin_code == NULL || pin_len > PIN_CODE_LEN) return BT_STATUS_FAIL;
if (pairing_cb.is_le_only) {
int i;
uint32_t passkey = 0;
int multi[] = {100000, 10000, 1000, 100, 10, 1};
for (i = 0; i < 6; i++) {
- passkey += (multi[i] * (pin_code.pin[i] - '0'));
+ passkey += (multi[i] * (pin_code->pin[i] - '0'));
}
BTIF_TRACE_DEBUG("btif_dm_pin_reply: passkey: %d", passkey);
- BTA_DmBlePasskeyReply(bd_addr, accept, passkey);
+ BTA_DmBlePasskeyReply(*bd_addr, accept, passkey);
} else {
- BTA_DmPinReply(bd_addr, accept, pin_len, pin_code.pin);
+ BTA_DmPinReply(*bd_addr, accept, pin_len, pin_code->pin);
if (accept) pairing_cb.pin_code_len = pin_len;
}
+ return BT_STATUS_SUCCESS;
}
/*******************************************************************************
@@ -2124,22 +2422,34 @@ void btif_dm_pin_reply(const RawAddress bd_addr, uint8_t accept,
* Description BT SSP Reply - Just Works, Numeric Comparison & Passkey
* Entry
*
+ * Returns bt_status_t
+ *
******************************************************************************/
-void btif_dm_ssp_reply(const RawAddress bd_addr, bt_ssp_variant_t variant,
- uint8_t accept) {
+bt_status_t btif_dm_ssp_reply(const RawAddress* bd_addr,
+ bt_ssp_variant_t variant, uint8_t accept,
+ UNUSED_ATTR uint32_t passkey) {
+ if (variant == BT_SSP_VARIANT_PASSKEY_ENTRY) {
+ /* This is not implemented in the stack.
+ * For devices with display, this is not needed
+ */
+ BTIF_TRACE_WARNING("%s: Not implemented", __func__);
+ return BT_STATUS_FAIL;
+ }
+ /* BT_SSP_VARIANT_CONSENT & BT_SSP_VARIANT_PASSKEY_CONFIRMATION supported */
BTIF_TRACE_EVENT("%s: accept=%d", __func__, accept);
if (pairing_cb.is_le_only) {
if (pairing_cb.is_le_nc) {
- BTA_DmBleConfirmReply(bd_addr, accept);
+ BTA_DmBleConfirmReply(*bd_addr, accept);
} else {
if (accept)
- BTA_DmBleSecurityGrant(bd_addr, BTA_DM_SEC_GRANTED);
+ BTA_DmBleSecurityGrant(*bd_addr, BTA_DM_SEC_GRANTED);
else
- BTA_DmBleSecurityGrant(bd_addr, BTA_DM_SEC_PAIR_NOT_SPT);
+ BTA_DmBleSecurityGrant(*bd_addr, BTA_DM_SEC_PAIR_NOT_SPT);
}
} else {
- BTA_DmConfirm(bd_addr, accept);
+ BTA_DmConfirm(*bd_addr, accept);
}
+ return BT_STATUS_SUCCESS;
}
/*******************************************************************************
@@ -2207,21 +2517,71 @@ bt_status_t btif_dm_get_adapter_property(bt_property_t* prop) {
*
* Function btif_dm_get_remote_services
*
+ * Description Start SDP to get remote services
+ *
+ * Returns bt_status_t
+ *
+ ******************************************************************************/
+bt_status_t btif_dm_get_remote_services(const RawAddress& remote_addr) {
+ BTIF_TRACE_EVENT("%s: bd_addr=%s", __func__, remote_addr.ToString().c_str());
+
+ BTA_DmDiscover(remote_addr, BTA_ALL_SERVICE_MASK, bte_dm_search_services_evt,
+ true);
+
+ return BT_STATUS_SUCCESS;
+}
+
+/*******************************************************************************
+ *
+ * Function btif_dm_get_remote_services_by_transport
+ *
* Description Start SDP to get remote services by transport
*
* Returns bt_status_t
*
******************************************************************************/
-void btif_dm_get_remote_services(RawAddress remote_addr, const int transport) {
+bt_status_t btif_dm_get_remote_services_by_transport(RawAddress* remote_addr,
+ const int transport) {
BTIF_TRACE_EVENT("%s: transport=%d, remote_addr=%s", __func__, transport,
- remote_addr.ToString().c_str());
+ remote_addr->ToString().c_str());
+
+ /* Set the mask extension */
+ tBTA_SERVICE_MASK_EXT mask_ext;
+ mask_ext.num_uuid = 0;
+ mask_ext.p_uuid = NULL;
+ mask_ext.srvc_mask = BTA_ALL_SERVICE_MASK;
- BTA_DmDiscover(remote_addr, btif_dm_search_services_evt, transport,
- remote_addr != pairing_cb.bd_addr && is_bonding_or_sdp());
+ BTA_DmDiscoverByTransport(*remote_addr, &mask_ext, bte_dm_search_services_evt,
+ true, transport);
+
+ return BT_STATUS_SUCCESS;
}
-void btif_dm_enable_service(tBTA_SERVICE_ID service_id, bool enable) {
- bt_status_t status = btif_in_execute_service_request(service_id, enable);
+/*******************************************************************************
+ *
+ * Function btif_dm_get_remote_service_record
+ *
+ * Description Start SDP to get remote service record
+ *
+ *
+ * Returns bt_status_t
+ ******************************************************************************/
+bt_status_t btif_dm_get_remote_service_record(const RawAddress& remote_addr,
+ const Uuid& uuid) {
+ BTIF_TRACE_EVENT("%s: bd_addr=%s", __func__, remote_addr.ToString().c_str());
+ BTA_DmDiscoverUUID(remote_addr, uuid, bte_dm_remote_service_record_evt, true);
+
+ return BT_STATUS_SUCCESS;
+}
+
+void btif_dm_execute_service_request(uint16_t event, char* p_param) {
+ bool b_enable = false;
+ bt_status_t status;
+ if (event == BTIF_DM_ENABLE_SERVICE) {
+ b_enable = true;
+ }
+ status =
+ btif_in_execute_service_request(*((tBTA_SERVICE_ID*)p_param), b_enable);
if (status == BT_STATUS_SUCCESS) {
bt_property_t property;
Uuid local_uuids[BT_MAX_NUM_UUIDS];
@@ -2230,12 +2590,16 @@ void btif_dm_enable_service(tBTA_SERVICE_ID service_id, bool enable) {
BTIF_STORAGE_FILL_PROPERTY(&property, BT_PROPERTY_UUIDS,
sizeof(local_uuids), local_uuids);
btif_storage_get_adapter_property(&property);
- invoke_adapter_properties_cb(BT_STATUS_SUCCESS, 1, &property);
+ HAL_CBACK(bt_hal_cbacks, adapter_properties_cb, BT_STATUS_SUCCESS, 1,
+ &property);
}
return;
}
-void btif_dm_proc_io_req(tBTM_AUTH_REQ* p_auth_req, bool is_orig) {
+void btif_dm_proc_io_req(UNUSED_ATTR const RawAddress& bd_addr,
+ UNUSED_ATTR tBTA_IO_CAP* p_io_cap,
+ UNUSED_ATTR tBTA_OOB_DATA* p_oob_data,
+ tBTA_AUTH_REQ* p_auth_req, bool is_orig) {
uint8_t yes_no_bit = BTA_AUTH_SP_YES & *p_auth_req;
/* if local initiated:
** 1. set DD + MITM
@@ -2270,8 +2634,8 @@ void btif_dm_proc_io_req(tBTM_AUTH_REQ* p_auth_req, bool is_orig) {
}
void btif_dm_proc_io_rsp(UNUSED_ATTR const RawAddress& bd_addr,
- tBTM_IO_CAP io_cap, UNUSED_ATTR tBTM_OOB_DATA oob_data,
- tBTM_AUTH_REQ auth_req) {
+ tBTA_IO_CAP io_cap, UNUSED_ATTR tBTA_OOB_DATA oob_data,
+ tBTA_AUTH_REQ auth_req) {
if (auth_req & BTA_AUTH_BONDS) {
BTIF_TRACE_DEBUG("%s auth_req:%d", __func__, auth_req);
pairing_cb.auth_req = auth_req;
@@ -2279,8 +2643,8 @@ void btif_dm_proc_io_rsp(UNUSED_ATTR const RawAddress& bd_addr,
}
}
-void btif_dm_set_oob_for_io_req(tBTM_OOB_DATA* p_has_oob_data) {
- if (is_empty_128bit(oob_cb.p192_data.c)) {
+void btif_dm_set_oob_for_io_req(tBTA_OOB_DATA* p_has_oob_data) {
+ if (is_empty_128bit(oob_cb.oob_data.c192)) {
*p_has_oob_data = false;
} else {
*p_has_oob_data = true;
@@ -2289,71 +2653,38 @@ void btif_dm_set_oob_for_io_req(tBTM_OOB_DATA* p_has_oob_data) {
}
void btif_dm_set_oob_for_le_io_req(const RawAddress& bd_addr,
- tBTM_OOB_DATA* p_has_oob_data,
- tBTM_LE_AUTH_REQ* p_auth_req) {
- switch (oob_cb.data_present) {
- case BTM_OOB_PRESENT_192_AND_256:
- LOG_INFO("Have both P192 and P256");
- [[fallthrough]];
- // Always prefer 256 for LE
- case BTM_OOB_PRESENT_256:
- LOG_INFO("Using P256");
- if (!is_empty_128bit(oob_cb.p256_data.c) &&
- !is_empty_128bit(oob_cb.p256_data.r)) {
- /* make sure OOB data is for this particular device */
- if (bd_addr == oob_cb.bdaddr) {
- *p_auth_req = ((*p_auth_req) | BTM_LE_AUTH_REQ_SC_ONLY);
- *p_has_oob_data = true;
- } else {
- *p_has_oob_data = false;
- LOG_WARN("P256-1: Remote address didn't match OOB data address");
- }
- } else if (!is_empty_128bit(oob_cb.p256_data.sm_tk)) {
- /* We have security manager TK */
-
- /* make sure OOB data is for this particular device */
- if (bd_addr == oob_cb.bdaddr) {
- // When using OOB with TK, SC Secure Connections bit must be disabled.
- tBTM_LE_AUTH_REQ mask = ~BTM_LE_AUTH_REQ_SC_ONLY;
- *p_auth_req = ((*p_auth_req) & mask);
- *p_has_oob_data = true;
- } else {
- *p_has_oob_data = false;
- LOG_WARN("P256-2: Remote address didn't match OOB data address");
- }
- } else {
- *p_has_oob_data = false;
- }
- break;
- case BTM_OOB_PRESENT_192:
- LOG_INFO("Using P192");
- if (!is_empty_128bit(oob_cb.p192_data.c) &&
- !is_empty_128bit(oob_cb.p192_data.r)) {
- /* make sure OOB data is for this particular device */
- if (bd_addr == oob_cb.bdaddr) {
- *p_auth_req = ((*p_auth_req) | BTM_LE_AUTH_REQ_SC_ONLY);
- *p_has_oob_data = true;
- } else {
- *p_has_oob_data = false;
- LOG_WARN("P192-1: Remote address didn't match OOB data address");
- }
- } else if (!is_empty_128bit(oob_cb.p192_data.sm_tk)) {
- /* We have security manager TK */
-
- /* make sure OOB data is for this particular device */
- if (bd_addr == oob_cb.bdaddr) {
- // When using OOB with TK, SC Secure Connections bit must be disabled.
- tBTM_LE_AUTH_REQ mask = ~BTM_LE_AUTH_REQ_SC_ONLY;
- *p_auth_req = ((*p_auth_req) & mask);
- *p_has_oob_data = true;
- } else {
- *p_has_oob_data = false;
- LOG_WARN("P192-2: Remote address didn't match OOB data address");
- }
- } else {
- *p_has_oob_data = false;
- }
- break;
+ tBTA_OOB_DATA* p_has_oob_data,
+ tBTA_LE_AUTH_REQ* p_auth_req) {
+ if (!is_empty_128bit(oob_cb.oob_data.le_sc_c) &&
+ !is_empty_128bit(oob_cb.oob_data.le_sc_r)) {
+ /* We have LE SC OOB data */
+
+ /* make sure OOB data is for this particular device */
+ if (bd_addr == oob_cb.bdaddr) {
+ *p_auth_req = ((*p_auth_req) | BTM_LE_AUTH_REQ_SC_ONLY);
+ *p_has_oob_data = true;
+ } else {
+ *p_has_oob_data = false;
+ BTIF_TRACE_WARNING("%s: remote address didn't match OOB data address",
+ __func__);
+ }
+ } else if (!is_empty_128bit(oob_cb.oob_data.sm_tk)) {
+ /* We have security manager TK */
+
+ /* make sure OOB data is for this particular device */
+ if (bd_addr == oob_cb.bdaddr) {
+ // When using OOB with TK, SC Secure Connections bit must be disabled.
+ tBTA_LE_AUTH_REQ mask = ~BTM_LE_AUTH_REQ_SC_ONLY;
+ *p_auth_req = ((*p_auth_req) & mask);
+
+ *p_has_oob_data = true;
+ } else {
+ *p_has_oob_data = false;
+ BTIF_TRACE_WARNING("%s: remote address didn't match OOB data address",
+ __func__);
+ }
+ } else {
+ *p_has_oob_data = false;
}
BTIF_TRACE_DEBUG("%s *p_has_oob_data=%d", __func__, *p_has_oob_data);
}
@@ -2364,144 +2695,46 @@ void btif_dm_load_local_oob(void) {
osi_property_get("service.brcm.bt.oob", prop_oob, "3");
BTIF_TRACE_DEBUG("%s: prop_oob = %s", __func__, prop_oob);
if (prop_oob[0] != '3') {
- if (is_empty_128bit(oob_cb.p192_data.c)) {
+ if (is_empty_128bit(oob_cb.oob_data.c192)) {
BTIF_TRACE_DEBUG("%s: read OOB, call BTA_DmLocalOob()", __func__);
BTA_DmLocalOob();
}
}
}
-static bool waiting_on_oob_advertiser_start = false;
-static uint8_t oob_advertiser_id = 0;
-static void stop_oob_advertiser() {
- auto advertiser = get_ble_advertiser_instance();
- advertiser->Unregister(oob_advertiser_id);
- oob_advertiser_id = 0;
-}
-
-/*******************************************************************************
- *
- * Function btif_dm_generate_local_oob_data
- *
- * Description Initiate oob data fetch from controller
- *
- * Parameters transport; Classic or LE
- *
- ******************************************************************************/
-void btif_dm_generate_local_oob_data(tBT_TRANSPORT transport) {
- LOG_DEBUG("Transport %s", bt_transport_text(transport).c_str());
- if (transport == BT_TRANSPORT_BR_EDR) {
- BTM_ReadLocalOobData();
- } else if (transport == BT_TRANSPORT_LE) {
- // Call create data first, so we don't have to hold on to the address for
- // the state machine lifecycle. Rather, lets create the data, then start
- // advertising then request the address.
- if (!waiting_on_oob_advertiser_start) {
- if (oob_advertiser_id != 0) {
- stop_oob_advertiser();
+void btif_dm_proc_loc_oob(bool valid, const Octet16& c, const Octet16& r) {
+ FILE* fp;
+ const char* path_a = "/data/misc/bluedroid/LOCAL/a.key";
+ const char* path_b = "/data/misc/bluedroid/LOCAL/b.key";
+ const char* path = NULL;
+ char prop_oob[PROPERTY_VALUE_MAX];
+ BTIF_TRACE_DEBUG("%s: valid=%d", __func__, valid);
+ if (is_empty_128bit(oob_cb.oob_data.c192) && valid) {
+ BTIF_TRACE_DEBUG("save local OOB data in memory");
+ memcpy(oob_cb.oob_data.c192, c.data(), OCTET16_LEN);
+ memcpy(oob_cb.oob_data.r192, r.data(), OCTET16_LEN);
+ osi_property_get("service.brcm.bt.oob", prop_oob, "3");
+ BTIF_TRACE_DEBUG("%s: prop_oob = %s", __func__, prop_oob);
+ if (prop_oob[0] == '1')
+ path = path_a;
+ else if (prop_oob[0] == '2')
+ path = path_b;
+ if (path) {
+ fp = fopen(path, "wb+");
+ if (fp == NULL) {
+ BTIF_TRACE_DEBUG("%s: failed to save local OOB data to %s", __func__,
+ path);
+ } else {
+ BTIF_TRACE_DEBUG("%s: save local OOB data into file %s", __func__,
+ path);
+ fwrite(c.data(), 1, OCTET16_LEN, fp);
+ fwrite(r.data(), 1, OCTET16_LEN, fp);
+ fclose(fp);
}
- waiting_on_oob_advertiser_start = true;
- SMP_CrLocScOobData();
- } else {
- invoke_oob_data_request_cb(transport, false, Octet16{}, Octet16{},
- RawAddress{}, 0x00);
}
}
}
-// Step Four: CallBack from Step Three
-static void get_address_callback(tBT_TRANSPORT transport, bool is_valid,
- const Octet16& c, const Octet16& r,
- uint8_t address_type, RawAddress address) {
- invoke_oob_data_request_cb(transport, is_valid, c, r, address, address_type);
- waiting_on_oob_advertiser_start = false;
-}
-
-// Step Three: CallBack from Step Two, advertise and get address
-static void start_advertising_callback(uint8_t id, tBT_TRANSPORT transport,
- bool is_valid, const Octet16& c,
- const Octet16& r, uint8_t status) {
- if (status != 0) {
- LOG_INFO("OOB get advertiser ID failed with status %hhd", status);
- invoke_oob_data_request_cb(transport, false, c, r, RawAddress{}, 0x00);
- SMP_ClearLocScOobData();
- waiting_on_oob_advertiser_start = false;
- oob_advertiser_id = 0;
- return;
- }
- LOG_DEBUG("OOB advertiser with id %hhd", id);
- auto advertiser = get_ble_advertiser_instance();
- advertiser->GetOwnAddress(
- id, base::Bind(&get_address_callback, transport, is_valid, c, r));
-}
-
-static void timeout_cb(uint8_t id, uint8_t status) {
- LOG_INFO("OOB advertiser with id %hhd timed out with status %hhd", id,
- status);
- auto advertiser = get_ble_advertiser_instance();
- advertiser->Unregister(id);
- SMP_ClearLocScOobData();
- waiting_on_oob_advertiser_start = false;
- oob_advertiser_id = 0;
-}
-
-// Step Two: CallBack from Step One, advertise and get address
-static void id_status_callback(tBT_TRANSPORT transport, bool is_valid,
- const Octet16& c, const Octet16& r, uint8_t id,
- uint8_t status) {
- if (status != 0) {
- LOG_INFO("OOB get advertiser ID failed with status %hhd", status);
- invoke_oob_data_request_cb(transport, false, c, r, RawAddress{}, 0x00);
- SMP_ClearLocScOobData();
- waiting_on_oob_advertiser_start = false;
- oob_advertiser_id = 0;
- return;
- }
-
- oob_advertiser_id = id;
-
- auto advertiser = get_ble_advertiser_instance();
- AdvertiseParameters parameters;
- parameters.advertising_event_properties = 0x0041 /* connectable, tx power */;
- parameters.min_interval = 0xa0; // 100 ms
- parameters.max_interval = 0x500; // 800 ms
- parameters.channel_map = 0x7; // Use all the channels
- parameters.tx_power = 0; // 0 dBm
- parameters.primary_advertising_phy = 1;
- parameters.secondary_advertising_phy = 2;
- parameters.scan_request_notification_enable = 0;
-
- std::vector<uint8_t> advertisement{0x02, 0x01 /* Flags */,
- 0x02 /* Connectable */};
- std::vector<uint8_t> scan_data{};
-
- advertiser->StartAdvertising(
- id,
- base::Bind(&start_advertising_callback, id, transport, is_valid, c, r),
- parameters, advertisement, scan_data, 3600 /* timeout_s */,
- base::Bind(&timeout_cb, id));
-}
-
-// Step One: Start the advertiser
-static void start_oob_advertiser(tBT_TRANSPORT transport, bool is_valid,
- const Octet16& c, const Octet16& r) {
- auto advertiser = get_ble_advertiser_instance();
- advertiser->RegisterAdvertiser(
- base::Bind(&id_status_callback, transport, is_valid, c, r));
-}
-
-void btif_dm_proc_loc_oob(tBT_TRANSPORT transport, bool is_valid,
- const Octet16& c, const Octet16& r) {
- // is_valid is important for deciding which OobDataCallback function to use
- if (!is_valid) {
- invoke_oob_data_request_cb(transport, false, c, r, RawAddress{}, 0x00);
- waiting_on_oob_advertiser_start = false;
- return;
- }
- // Now that we have the data, lets start advertising and get the address.
- start_oob_advertiser(transport, is_valid, c, r);
-}
-
/*******************************************************************************
*
* Function btif_dm_get_smp_config
@@ -2521,7 +2754,7 @@ void btif_dm_proc_loc_oob(tBT_TRANSPORT transport, bool is_valid,
bool btif_dm_get_smp_config(tBTE_APPL_CFG* p_cfg) {
const std::string* recv = stack_config_get_interface()->get_pts_smp_options();
if (!recv) {
- LOG_DEBUG("SMP pairing options not found in stack configuration");
+ BTIF_TRACE_DEBUG("%s: SMP options not found in configuration", __func__);
return false;
}
@@ -2589,11 +2822,13 @@ bool btif_dm_proc_rmt_oob(const RawAddress& bd_addr, Octet16* p_c,
}
BTIF_TRACE_DEBUG("%s: read OOB data from %s", __func__, path);
- (void)fread(p_c->data(), 1, OCTET16_LEN, fp);
- (void)fread(p_r->data(), 1, OCTET16_LEN, fp);
+ fread(p_c->data(), 1, OCTET16_LEN, fp);
+ fread(p_r->data(), 1, OCTET16_LEN, fp);
fclose(fp);
- bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_BONDING);
+ RawAddress bt_bd_addr = bd_addr;
+ btif_transfer_context(btif_dm_generic_evt, BTIF_DM_CB_BOND_STATE_BONDING,
+ (char*)&bt_bd_addr, sizeof(RawAddress), NULL);
return true;
}
#endif /* BTIF_DM_OOB_TEST */
@@ -2615,15 +2850,13 @@ static void btif_dm_ble_key_notif_evt(tBTA_DM_SP_KEY_NOTIF* p_ssp_key_notif) {
(tBT_DEVICE_TYPE)dev_type);
bd_addr = p_ssp_key_notif->bd_addr;
memcpy(bd_name.name, p_ssp_key_notif->bd_name, BD_NAME_LEN);
- bd_name.name[BD_NAME_LEN] = '\0';
bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_BONDING);
pairing_cb.is_ssp = false;
cod = COD_UNCLASSIFIED;
- invoke_ssp_request_cb(bd_addr, bd_name, cod,
- BT_SSP_VARIANT_PASSKEY_NOTIFICATION,
- p_ssp_key_notif->passkey);
+ HAL_CBACK(bt_hal_cbacks, ssp_request_cb, &bd_addr, &bd_name, cod,
+ BT_SSP_VARIANT_PASSKEY_NOTIFICATION, p_ssp_key_notif->passkey);
}
/*******************************************************************************
@@ -2651,28 +2884,25 @@ static void btif_dm_ble_auth_cmpl_evt(tBTA_DM_AUTH_CMPL* p_auth_cmpl) {
if (p_auth_cmpl->success) {
status = BT_STATUS_SUCCESS;
state = BT_BOND_STATE_BONDED;
- tBLE_ADDR_TYPE addr_type;
+ int addr_type;
RawAddress bdaddr = p_auth_cmpl->bd_addr;
if (btif_storage_get_remote_addr_type(&bdaddr, &addr_type) !=
BT_STATUS_SUCCESS)
btif_storage_set_remote_addr_type(&bdaddr, p_auth_cmpl->addr_type);
/* Test for temporary bonding */
- if (btm_get_bond_type_dev(p_auth_cmpl->bd_addr) ==
- tBTM_SEC_DEV_REC::BOND_TYPE_TEMPORARY) {
+ if (btm_get_bond_type_dev(p_auth_cmpl->bd_addr) == BOND_TYPE_TEMPORARY) {
BTIF_TRACE_DEBUG("%s: sending BT_BOND_STATE_NONE for Temp pairing",
__func__);
btif_storage_remove_bonded_device(&bdaddr);
state = BT_BOND_STATE_NONE;
} else {
btif_dm_save_ble_bonding_keys(bdaddr);
- btif_dm_get_remote_services(bd_addr, BT_TRANSPORT_LE);
+ btif_dm_get_remote_services_by_transport(&bd_addr, GATT_TRANSPORT_LE);
}
} else {
/*Map the HCI fail reason to bt status */
- // TODO This is not a proper use of the type
- uint8_t fail_reason = static_cast<uint8_t>(p_auth_cmpl->fail_reason);
- switch (fail_reason) {
+ switch (p_auth_cmpl->fail_reason) {
case BTA_DM_AUTH_SMP_PAIR_AUTH_FAIL:
case BTA_DM_AUTH_SMP_CONFIRM_VALUE_FAIL:
case BTA_DM_AUTH_SMP_UNKNOWN_ERR:
@@ -2702,8 +2932,7 @@ static void btif_dm_ble_auth_cmpl_evt(tBTA_DM_AUTH_CMPL* p_auth_cmpl) {
break;
}
}
- if (state == BT_BOND_STATE_BONDED && !pairing_cb.static_bdaddr.IsEmpty() &&
- bd_addr != pairing_cb.static_bdaddr) {
+ if (state == BT_BOND_STATE_BONDED && bd_addr != pairing_cb.static_bdaddr) {
// Report RPA bonding state to Java in crosskey paring
bond_state_changed(status, bd_addr, BT_BOND_STATE_BONDING);
}
@@ -2754,37 +2983,36 @@ void btif_dm_save_ble_bonding_keys(RawAddress& bd_addr) {
if (pairing_cb.ble.is_penc_key_rcvd) {
btif_storage_add_ble_bonding_key(
- &bd_addr, (uint8_t*)&pairing_cb.ble.penc_key, BTM_LE_KEY_PENC,
+ &bd_addr, (uint8_t*)&pairing_cb.ble.penc_key, BTIF_DM_LE_KEY_PENC,
sizeof(tBTM_LE_PENC_KEYS));
}
if (pairing_cb.ble.is_pid_key_rcvd) {
- btif_storage_add_ble_bonding_key(&bd_addr,
- (uint8_t*)&pairing_cb.ble.pid_key,
- BTM_LE_KEY_PID, sizeof(tBTM_LE_PID_KEYS));
+ btif_storage_add_ble_bonding_key(
+ &bd_addr, (uint8_t*)&pairing_cb.ble.pid_key, BTIF_DM_LE_KEY_PID,
+ sizeof(tBTM_LE_PID_KEYS));
}
if (pairing_cb.ble.is_pcsrk_key_rcvd) {
btif_storage_add_ble_bonding_key(
- &bd_addr, (uint8_t*)&pairing_cb.ble.pcsrk_key, BTM_LE_KEY_PCSRK,
+ &bd_addr, (uint8_t*)&pairing_cb.ble.pcsrk_key, BTIF_DM_LE_KEY_PCSRK,
sizeof(tBTM_LE_PCSRK_KEYS));
}
if (pairing_cb.ble.is_lenc_key_rcvd) {
btif_storage_add_ble_bonding_key(
- &bd_addr, (uint8_t*)&pairing_cb.ble.lenc_key, BTM_LE_KEY_LENC,
+ &bd_addr, (uint8_t*)&pairing_cb.ble.lenc_key, BTIF_DM_LE_KEY_LENC,
sizeof(tBTM_LE_LENC_KEYS));
}
if (pairing_cb.ble.is_lcsrk_key_rcvd) {
btif_storage_add_ble_bonding_key(
- &bd_addr, (uint8_t*)&pairing_cb.ble.lcsrk_key, BTM_LE_KEY_LCSRK,
+ &bd_addr, (uint8_t*)&pairing_cb.ble.lcsrk_key, BTIF_DM_LE_KEY_LCSRK,
sizeof(tBTM_LE_LCSRK_KEYS));
}
if (pairing_cb.ble.is_lidk_key_rcvd) {
- uint8_t empty[] = {};
- btif_storage_add_ble_bonding_key(&bd_addr, empty, BTM_LE_KEY_LID, 0);
+ btif_storage_add_ble_bonding_key(&bd_addr, NULL, BTIF_DM_LE_KEY_LID, 0);
}
}
@@ -2825,11 +3053,10 @@ void btif_dm_ble_sec_req_evt(tBTA_DM_BLE_SEC_REQ* p_ble_req, bool is_consent) {
RawAddress bd_addr = p_ble_req->bd_addr;
memcpy(bd_name.name, p_ble_req->bd_name, BD_NAME_LEN);
- bd_name.name[BD_NAME_LEN] = '\0';
bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_BONDING);
- pairing_cb.bond_type = tBTM_SEC_DEV_REC::BOND_TYPE_PERSISTENT;
+ pairing_cb.bond_type = BOND_TYPE_PERSISTENT;
pairing_cb.is_le_only = true;
pairing_cb.is_le_nc = false;
pairing_cb.is_ssp = true;
@@ -2837,7 +3064,8 @@ void btif_dm_ble_sec_req_evt(tBTA_DM_BLE_SEC_REQ* p_ble_req, bool is_consent) {
cod = COD_UNCLASSIFIED;
- invoke_ssp_request_cb(bd_addr, bd_name, cod, BT_SSP_VARIANT_CONSENT, 0);
+ HAL_CBACK(bt_hal_cbacks, ssp_request_cb, &bd_addr, &bd_name, cod,
+ BT_SSP_VARIANT_CONSENT, 0);
}
/*******************************************************************************
@@ -2863,14 +3091,13 @@ static void btif_dm_ble_passkey_req_evt(tBTA_DM_PIN_REQ* p_pin_req) {
RawAddress bd_addr = p_pin_req->bd_addr;
memcpy(bd_name.name, p_pin_req->bd_name, BD_NAME_LEN);
- bd_name.name[BD_NAME_LEN] = '\0';
bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_BONDING);
pairing_cb.is_le_only = true;
cod = COD_UNCLASSIFIED;
- invoke_pin_request_cb(bd_addr, bd_name, cod, false);
+ HAL_CBACK(bt_hal_cbacks, pin_request_cb, &bd_addr, &bd_name, cod, false);
}
static void btif_dm_ble_key_nc_req_evt(tBTA_DM_SP_KEY_NOTIF* p_notif_req) {
/* TODO implement key notification for numeric comparison */
@@ -2884,16 +3111,14 @@ static void btif_dm_ble_key_nc_req_evt(tBTA_DM_SP_KEY_NOTIF* p_notif_req) {
bt_bdname_t bd_name;
memcpy(bd_name.name, p_notif_req->bd_name, BD_NAME_LEN);
- bd_name.name[BD_NAME_LEN] = '\0';
bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_BONDING);
pairing_cb.is_ssp = false;
pairing_cb.is_le_only = true;
pairing_cb.is_le_nc = true;
- invoke_ssp_request_cb(bd_addr, bd_name, COD_UNCLASSIFIED,
- BT_SSP_VARIANT_PASSKEY_CONFIRMATION,
- p_notif_req->passkey);
+ HAL_CBACK(bt_hal_cbacks, ssp_request_cb, &bd_addr, &bd_name, COD_UNCLASSIFIED,
+ BT_SSP_VARIANT_PASSKEY_CONFIRMATION, p_notif_req->passkey);
}
static void btif_dm_ble_oob_req_evt(tBTA_DM_SP_RMT_OOB* req_oob_type) {
@@ -2904,7 +3129,7 @@ static void btif_dm_ble_oob_req_evt(tBTA_DM_SP_RMT_OOB* req_oob_type) {
* btif_dm_set_oob_for_le_io_req, but check here again. If it's not present
* do nothing, pairing will timeout.
*/
- if (is_empty_128bit(oob_cb.p192_data.sm_tk)) {
+ if (is_empty_128bit(oob_cb.oob_data.sm_tk)) {
return;
}
@@ -2924,65 +3149,43 @@ static void btif_dm_ble_oob_req_evt(tBTA_DM_SP_RMT_OOB* req_oob_type) {
pairing_cb.is_le_only = true;
pairing_cb.is_le_nc = false;
- BTM_BleOobDataReply(req_oob_type->bd_addr, 0, 16, oob_cb.p192_data.sm_tk);
+ BTM_BleOobDataReply(req_oob_type->bd_addr, 0, 16, oob_cb.oob_data.sm_tk);
}
static void btif_dm_ble_sc_oob_req_evt(tBTA_DM_SP_RMT_OOB* req_oob_type) {
BTIF_TRACE_DEBUG("%s", __func__);
RawAddress bd_addr = req_oob_type->bd_addr;
- BTIF_TRACE_DEBUG("%s: bd_addr: %s", __func__, bd_addr.ToString().c_str());
- BTIF_TRACE_DEBUG("%s: oob_cb.bdaddr: %s", __func__,
- oob_cb.bdaddr.ToString().c_str());
-
- /* make sure OOB data is for this particular device */
- if (req_oob_type->bd_addr != oob_cb.bdaddr) {
- LOG_ERROR("remote address didn't match OOB data address");
- return;
- }
/* We already checked if OOB data is present in
* btif_dm_set_oob_for_le_io_req, but check here again. If it's not present
* do nothing, pairing will timeout.
*/
- bt_oob_data_t oob_data_to_use = {};
- switch (oob_cb.data_present) {
- case BTM_OOB_PRESENT_192_AND_256:
- LOG_INFO("Have both P192 and P256");
- [[fallthrough]];
- // Always prefer 256 for LE
- case BTM_OOB_PRESENT_256:
- LOG_INFO("Using P256");
- if (is_empty_128bit(oob_cb.p256_data.c) &&
- is_empty_128bit(oob_cb.p256_data.r)) {
- LOG_WARN("P256 LE SC OOB data is empty");
- return;
- }
- oob_data_to_use = oob_cb.p256_data;
- break;
- case BTM_OOB_PRESENT_192:
- LOG_INFO("Using P192");
- if (is_empty_128bit(oob_cb.p192_data.c) &&
- is_empty_128bit(oob_cb.p192_data.r)) {
- LOG_WARN("P192 LE SC OOB data is empty");
- return;
- }
- oob_data_to_use = oob_cb.p192_data;
- break;
+ if (is_empty_128bit(oob_cb.oob_data.le_sc_c) &&
+ is_empty_128bit(oob_cb.oob_data.le_sc_r)) {
+ BTIF_TRACE_WARNING("%s: LE SC OOB data is empty", __func__);
+ return;
+ }
+
+ /* make sure OOB data is for this particular device */
+ if (req_oob_type->bd_addr != oob_cb.bdaddr) {
+ BTIF_TRACE_WARNING("%s: remote address didn't match OOB data address",
+ __func__);
+ return;
}
/* Remote name update */
- btif_update_remote_properties(req_oob_type->bd_addr,
- oob_data_to_use.device_name, NULL,
- BT_DEVICE_TYPE_BLE);
+ btif_update_remote_properties(req_oob_type->bd_addr, req_oob_type->bd_name,
+ NULL, BT_DEVICE_TYPE_BLE);
bond_state_changed(BT_STATUS_SUCCESS, bd_addr, BT_BOND_STATE_BONDING);
pairing_cb.is_ssp = false;
- // TODO: we can derive classic pairing from this one
- pairing_cb.is_le_only = true;
+ pairing_cb.is_le_only =
+ true; // TODO: we can derive classic pairing from this one
pairing_cb.is_le_nc = false;
- BTM_BleSecureConnectionOobDataReply(req_oob_type->bd_addr, oob_data_to_use.c,
- oob_data_to_use.r);
+
+ BTM_BleSecureConnectionOobDataReply(
+ req_oob_type->bd_addr, oob_cb.oob_data.le_sc_c, oob_cb.oob_data.le_sc_r);
}
void btif_dm_update_ble_remote_properties(const RawAddress& bd_addr,
@@ -2992,46 +3195,54 @@ void btif_dm_update_ble_remote_properties(const RawAddress& bd_addr,
}
static void btif_dm_ble_tx_test_cback(void* p) {
- char* p_param = (char*)p;
- uint8_t status;
- STREAM_TO_UINT8(status, p_param);
- invoke_le_test_mode_cb((status == 0) ? BT_STATUS_SUCCESS : BT_STATUS_FAIL, 0);
+ btif_transfer_context(btif_dm_generic_evt, BTIF_DM_CB_LE_TX_TEST, (char*)p, 1,
+ NULL);
}
static void btif_dm_ble_rx_test_cback(void* p) {
- char* p_param = (char*)p;
- uint8_t status;
- STREAM_TO_UINT8(status, p_param);
- invoke_le_test_mode_cb((status == 0) ? BT_STATUS_SUCCESS : BT_STATUS_FAIL, 0);
+ btif_transfer_context(btif_dm_generic_evt, BTIF_DM_CB_LE_RX_TEST, (char*)p, 1,
+ NULL);
}
static void btif_dm_ble_test_end_cback(void* p) {
- char* p_param = (char*)p;
- uint8_t status;
- uint16_t count = 0;
- STREAM_TO_UINT8(status, p_param);
- if (status == 0) STREAM_TO_UINT16(count, p_param);
- invoke_le_test_mode_cb((status == 0) ? BT_STATUS_SUCCESS : BT_STATUS_FAIL,
- count);
+ btif_transfer_context(btif_dm_generic_evt, BTIF_DM_CB_LE_TEST_END, (char*)p,
+ 3, NULL);
}
-
-void btif_ble_transmitter_test(uint8_t tx_freq, uint8_t test_data_len,
- uint8_t packet_payload) {
- BTM_BleTransmitterTest(tx_freq, test_data_len, packet_payload,
- btif_dm_ble_tx_test_cback);
-}
-
-void btif_ble_receiver_test(uint8_t rx_freq) {
- BTM_BleReceiverTest(rx_freq, btif_dm_ble_rx_test_cback);
+/*******************************************************************************
+ *
+ * Function btif_le_test_mode
+ *
+ * Description Sends a HCI BLE Test command to the Controller
+ *
+ * Returns BT_STATUS_SUCCESS on success
+ *
+ ******************************************************************************/
+bt_status_t btif_le_test_mode(uint16_t opcode, uint8_t* buf, uint8_t len) {
+ switch (opcode) {
+ case HCI_BLE_TRANSMITTER_TEST:
+ if (len != 3) return BT_STATUS_PARM_INVALID;
+ BTM_BleTransmitterTest(buf[0], buf[1], buf[2], btif_dm_ble_tx_test_cback);
+ break;
+ case HCI_BLE_RECEIVER_TEST:
+ if (len != 1) return BT_STATUS_PARM_INVALID;
+ BTM_BleReceiverTest(buf[0], btif_dm_ble_rx_test_cback);
+ break;
+ case HCI_BLE_TEST_END:
+ BTM_BleTestEnd(btif_dm_ble_test_end_cback);
+ break;
+ default:
+ BTIF_TRACE_ERROR("%s: Unknown LE Test Mode Command 0x%x", __func__,
+ opcode);
+ return BT_STATUS_UNSUPPORTED;
+ }
+ return BT_STATUS_SUCCESS;
}
-void btif_ble_test_end() { BTM_BleTestEnd(btif_dm_ble_test_end_cback); }
-
void btif_dm_on_disable() {
/* cancel any pending pairing requests */
if (is_bonding_or_sdp()) {
BTIF_TRACE_DEBUG("%s: Cancel pending pairing request", __func__);
- btif_dm_cancel_bond(pairing_cb.bd_addr);
+ btif_dm_cancel_bond(&pairing_cb.bd_addr);
}
}
@@ -3046,34 +3257,6 @@ void btif_dm_on_disable() {
******************************************************************************/
void btif_dm_read_energy_info() { BTA_DmBleGetEnergyInfo(bta_energy_info_cb); }
-/*******************************************************************************
- *
- * Function btif_dm_add_uuid_to_eir
- *
- * Description Add a service class uuid to the local device's EIR data
- *
- * Returns void
- *
- ******************************************************************************/
-void btif_dm_add_uuid_to_eir(uint16_t uuid16) {
- BTIF_TRACE_DEBUG("%s: %d", __func__, uuid16);
- BTA_AddEirUuid(uuid16);
-}
-
-/*******************************************************************************
- *
- * Function btif_dm_remove_uuid_from_eir
- *
- * Description Remove a service class uuid from the local device's EIR data
- *
- * Returns void
- *
- ******************************************************************************/
-void btif_dm_remove_uuid_from_eir(uint16_t uuid16) {
- BTIF_TRACE_DEBUG("%s: %d", __func__, uuid16);
- BTA_RemoveEirUuid(uuid16);
-}
-
static char* btif_get_default_local_name() {
if (btif_default_local_name[0] == '\0') {
int max_len = sizeof(btif_default_local_name) - 1;
diff --git a/btif/src/btif_gatt.cc b/btif/src/btif_gatt.cc
index d8076b07e..b4d0b10c5 100644
--- a/btif/src/btif_gatt.cc
+++ b/btif/src/btif_gatt.cc
@@ -75,15 +75,15 @@ static void btif_gatt_cleanup(void) {
}
static btgatt_interface_t btgattInterface = {
- .size = sizeof(btgattInterface),
+ sizeof(btgattInterface),
- .init = btif_gatt_init,
- .cleanup = btif_gatt_cleanup,
+ btif_gatt_init,
+ btif_gatt_cleanup,
- .client = &btgattClientInterface,
- .server = &btgattServerInterface,
- .scanner = nullptr, // filled in btif_gatt_get_interface
- .advertiser = nullptr // filled in btif_gatt_get_interface
+ &btgattClientInterface,
+ &btgattServerInterface,
+ nullptr, // filled in btif_gatt_get_interface
+ nullptr // filled in btif_gatt_get_interface
};
/*******************************************************************************
diff --git a/btif/src/btif_gatt_client.cc b/btif/src/btif_gatt_client.cc
index 9fb09c6fe..14433d397 100644
--- a/btif/src/btif_gatt_client.cc
+++ b/btif/src/btif_gatt_client.cc
@@ -31,25 +31,24 @@
#include <base/threading/thread.h>
#include <errno.h>
#include <hardware/bluetooth.h>
-#include <hardware/bt_gatt.h>
+#include <stdlib.h>
+#include <string.h>
+#include "device/include/controller.h"
+
+#include "btif_common.h"
+#include "btif_util.h"
-#include <string>
+#include <hardware/bt_gatt.h>
#include "bta_api.h"
#include "bta_gatt_api.h"
-#include "btif_common.h"
#include "btif_config.h"
#include "btif_dm.h"
#include "btif_gatt.h"
#include "btif_gatt_util.h"
#include "btif_storage.h"
-#include "btif_util.h"
-#include "device/include/controller.h"
#include "osi/include/log.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/acl_api_types.h"
#include "stack/include/btu.h"
-#include "types/bt_transport.h"
#include "vendor_api.h"
using base::Bind;
@@ -75,64 +74,35 @@ extern const btgatt_callbacks_t* bt_gatt_callbacks;
} \
} while (0)
-#define CHECK_BTGATT_INIT() \
- do { \
- if (bt_gatt_callbacks == NULL) { \
- LOG_WARN("%s: BTGATT not initialized", __func__); \
- return BT_STATUS_NOT_READY; \
- } else { \
- LOG_VERBOSE("%s", __func__); \
- } \
+#define CHECK_BTGATT_INIT() \
+ do { \
+ if (bt_gatt_callbacks == NULL) { \
+ LOG_WARN(LOG_TAG, "%s: BTGATT not initialized", __func__); \
+ return BT_STATUS_NOT_READY; \
+ } else { \
+ LOG_VERBOSE(LOG_TAG, "%s", __func__); \
+ } \
} while (0)
+#define BLE_RESOLVE_ADDR_MSB \
+ 0x40 /* bit7, bit6 is 01 to be resolvable random \
+ */
+#define BLE_RESOLVE_ADDR_MASK 0xc0 /* bit 6, and bit7 */
+inline bool BTM_BLE_IS_RESOLVE_BDA(const RawAddress& x) {
+ return ((x.address)[0] & BLE_RESOLVE_ADDR_MASK) == BLE_RESOLVE_ADDR_MSB;
+}
namespace {
uint8_t rssi_request_client_if;
-std::string bta_gattc_event_text(const tBTA_GATTC_EVT& event) {
- switch (event) {
- case BTA_GATTC_DEREG_EVT:
- return std::string("GATT client deregistered");
- case BTA_GATTC_OPEN_EVT:
- return std::string("GATTC open request status");
- case BTA_GATTC_CLOSE_EVT:
- return std::string("GATTC close request status");
- case BTA_GATTC_SEARCH_CMPL_EVT:
- return std::string("GATT discovery complete");
- case BTA_GATTC_SEARCH_RES_EVT:
- return std::string("GATT discovery result");
- case BTA_GATTC_SRVC_DISC_DONE_EVT:
- return std::string("GATT service discovery done");
- case BTA_GATTC_NOTIF_EVT:
- return std::string("GATT attribute notification");
- case BTA_GATTC_EXEC_EVT:
- return std::string("execute write complete");
- case BTA_GATTC_ACL_EVT:
- return std::string("ACL up");
- case BTA_GATTC_CANCEL_OPEN_EVT:
- return std::string("cancel open");
- case BTA_GATTC_SRVC_CHG_EVT:
- return std::string("service change");
- case BTA_GATTC_ENC_CMPL_CB_EVT:
- return std::string("encryption complete callback");
- case BTA_GATTC_CFG_MTU_EVT:
- return std::string("configure MTU complete");
- case BTA_GATTC_CONGEST_EVT:
- return std::string("congestion");
- case BTA_GATTC_PHY_UPDATE_EVT:
- return std::string("PHY change");
- case BTA_GATTC_CONN_UPDATE_EVT:
- return std::string("connection parameters update");
- }
-}
-
-static void btif_gattc_upstreams_evt(uint16_t event, char* p_param) {
- LOG_DEBUG("Event %s [%d]",
- bta_gattc_event_text(static_cast<tBTA_GATTC_EVT>(event)).c_str(),
- event);
+void btif_gattc_upstreams_evt(uint16_t event, char* p_param) {
+ LOG_VERBOSE(LOG_TAG, "%s: Event %d", __func__, event);
tBTA_GATTC* p_data = (tBTA_GATTC*)p_param;
switch (event) {
+ case BTA_GATTC_DEREG_EVT:
+ break;
+
case BTA_GATTC_EXEC_EVT: {
HAL_CBACK(bt_gatt_callbacks, client->execute_write_cb,
p_data->exec_cmpl.conn_id, p_data->exec_cmpl.status);
@@ -159,7 +129,7 @@ static void btif_gattc_upstreams_evt(uint16_t event, char* p_param) {
data);
if (!p_data->notify.is_notify)
- BTA_GATTC_SendIndConfirm(p_data->notify.conn_id, p_data->notify.cid);
+ BTA_GATTC_SendIndConfirm(p_data->notify.conn_id, p_data->notify.handle);
break;
}
@@ -183,17 +153,20 @@ static void btif_gattc_upstreams_evt(uint16_t event, char* p_param) {
case BTA_GATTC_CLOSE_EVT: {
HAL_CBACK(bt_gatt_callbacks, client->close_cb, p_data->close.conn_id,
- p_data->close.status, p_data->close.client_if,
+ p_data->status, p_data->close.client_if,
p_data->close.remote_bda);
break;
}
case BTA_GATTC_ACL_EVT:
- case BTA_GATTC_DEREG_EVT:
+ LOG_DEBUG(LOG_TAG, "BTA_GATTC_ACL_EVT: status = %d", p_data->status);
+ /* Ignore for now */
+ break;
+
case BTA_GATTC_SEARCH_RES_EVT:
+ break;
+
case BTA_GATTC_CANCEL_OPEN_EVT:
- case BTA_GATTC_SRVC_DISC_DONE_EVT:
- LOG_DEBUG("Ignoring event (%d)", event);
break;
case BTA_GATTC_CFG_MTU_EVT: {
@@ -221,20 +194,13 @@ static void btif_gattc_upstreams_evt(uint16_t event, char* p_param) {
p_data->conn_update.status);
break;
- case BTA_GATTC_SRVC_CHG_EVT:
- HAL_CBACK(bt_gatt_callbacks, client->service_changed_cb,
- p_data->service_changed.conn_id);
- break;
-
default:
- LOG_ERROR("Unhandled event (%d)!", event);
+ LOG_ERROR(LOG_TAG, "%s: Unhandled event (%d)!", __func__, event);
break;
}
}
-static void bta_gattc_cback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
- LOG_DEBUG(" gatt client callback event:%s [%d]",
- gatt_client_event_text(event).c_str(), event);
+void bta_gattc_cback(tBTA_GATTC_EVT event, tBTA_GATTC* p_data) {
bt_status_t status =
btif_transfer_context(btif_gattc_upstreams_evt, (uint16_t)event,
(char*)p_data, sizeof(tBTA_GATTC), NULL);
@@ -254,12 +220,11 @@ void btm_read_rssi_cb(void* p_void) {
* Client API Functions
******************************************************************************/
-static bt_status_t btif_gattc_register_app(const Uuid& uuid,
- bool eatt_support) {
+bt_status_t btif_gattc_register_app(const Uuid& uuid) {
CHECK_BTGATT_INIT();
return do_in_jni_thread(Bind(
- [](const Uuid& uuid, bool eatt_support) {
+ [](const Uuid& uuid) {
BTA_GATTC_AppRegister(
bta_gattc_cback,
base::Bind(
@@ -271,17 +236,16 @@ static bt_status_t btif_gattc_register_app(const Uuid& uuid,
},
uuid, client_id, status));
},
- uuid),
- eatt_support);
+ uuid));
},
- uuid, eatt_support));
+ uuid));
}
-static void btif_gattc_unregister_app_impl(int client_if) {
+void btif_gattc_unregister_app_impl(int client_if) {
BTA_GATTC_AppDeregister(client_if);
}
-static bt_status_t btif_gattc_unregister_app(int client_if) {
+bt_status_t btif_gattc_unregister_app(int client_if) {
CHECK_BTGATT_INIT();
return do_in_jni_thread(Bind(&btif_gattc_unregister_app_impl, client_if));
}
@@ -290,9 +254,9 @@ void btif_gattc_open_impl(int client_if, RawAddress address, bool is_direct,
int transport_p, bool opportunistic,
int initiating_phys) {
// Ensure device is in inquiry database
- tBLE_ADDR_TYPE addr_type = BLE_ADDR_PUBLIC;
+ int addr_type = 0;
int device_type = 0;
- tBT_TRANSPORT transport = (tBT_TRANSPORT)BT_TRANSPORT_LE;
+ tGATT_TRANSPORT transport = (tGATT_TRANSPORT)GATT_TRANSPORT_LE;
if (btif_get_address_type(address, &addr_type) &&
btif_get_device_type(address, &device_type) &&
@@ -318,23 +282,23 @@ void btif_gattc_open_impl(int client_if, RawAddress address, bool is_direct,
}
// Determine transport
- if (transport_p != BT_TRANSPORT_AUTO) {
+ if (transport_p != GATT_TRANSPORT_AUTO) {
transport = transport_p;
} else {
switch (device_type) {
case BT_DEVICE_TYPE_BREDR:
- transport = BT_TRANSPORT_BR_EDR;
+ transport = GATT_TRANSPORT_BR_EDR;
break;
case BT_DEVICE_TYPE_BLE:
- transport = BT_TRANSPORT_LE;
+ transport = GATT_TRANSPORT_LE;
break;
case BT_DEVICE_TYPE_DUMO:
- if (transport_p == BT_TRANSPORT_LE)
- transport = BT_TRANSPORT_LE;
+ if (transport_p == GATT_TRANSPORT_LE)
+ transport = GATT_TRANSPORT_LE;
else
- transport = BT_TRANSPORT_BR_EDR;
+ transport = GATT_TRANSPORT_BR_EDR;
break;
}
}
@@ -346,9 +310,9 @@ void btif_gattc_open_impl(int client_if, RawAddress address, bool is_direct,
initiating_phys);
}
-static bt_status_t btif_gattc_open(int client_if, const RawAddress& bd_addr,
- bool is_direct, int transport,
- bool opportunistic, int initiating_phys) {
+bt_status_t btif_gattc_open(int client_if, const RawAddress& bd_addr,
+ bool is_direct, int transport, bool opportunistic,
+ int initiating_phys) {
CHECK_BTGATT_INIT();
// Closure will own this value and free it.
return do_in_jni_thread(Bind(&btif_gattc_open_impl, client_if, bd_addr,
@@ -363,25 +327,23 @@ void btif_gattc_close_impl(int client_if, RawAddress address, int conn_id) {
else
BTA_GATTC_CancelOpen(client_if, address, true);
- // Cancel pending background connections (remove from acceptlist)
+ // Cancel pending background connections (remove from whitelist)
BTA_GATTC_CancelOpen(client_if, address, false);
}
-static bt_status_t btif_gattc_close(int client_if, const RawAddress& bd_addr,
- int conn_id) {
+bt_status_t btif_gattc_close(int client_if, const RawAddress& bd_addr,
+ int conn_id) {
CHECK_BTGATT_INIT();
return do_in_jni_thread(
Bind(&btif_gattc_close_impl, client_if, bd_addr, conn_id));
}
-static bt_status_t btif_gattc_refresh(int client_if,
- const RawAddress& bd_addr) {
+bt_status_t btif_gattc_refresh(int client_if, const RawAddress& bd_addr) {
CHECK_BTGATT_INIT();
return do_in_jni_thread(Bind(&BTA_GATTC_Refresh, bd_addr));
}
-static bt_status_t btif_gattc_search_service(int conn_id,
- const Uuid* filter_uuid) {
+bt_status_t btif_gattc_search_service(int conn_id, const Uuid* filter_uuid) {
CHECK_BTGATT_INIT();
if (filter_uuid) {
@@ -394,7 +356,7 @@ static bt_status_t btif_gattc_search_service(int conn_id,
}
}
-static void btif_gattc_discover_service_by_uuid(int conn_id, const Uuid& uuid) {
+void btif_gattc_discover_service_by_uuid(int conn_id, const Uuid& uuid) {
do_in_jni_thread(Bind(&BTA_GATTC_DiscoverServiceByUuid, conn_id, uuid));
}
@@ -407,7 +369,7 @@ void btif_gattc_get_gatt_db_impl(int conn_id) {
osi_free(db);
}
-static bt_status_t btif_gattc_get_gatt_db(int conn_id) {
+bt_status_t btif_gattc_get_gatt_db(int conn_id) {
CHECK_BTGATT_INIT();
return do_in_jni_thread(Bind(&btif_gattc_get_gatt_db_impl, conn_id));
}
@@ -428,8 +390,7 @@ void read_char_cb(uint16_t conn_id, tGATT_STATUS status, uint16_t handle,
base::Owned(params));
}
-static bt_status_t btif_gattc_read_char(int conn_id, uint16_t handle,
- int auth_req) {
+bt_status_t btif_gattc_read_char(int conn_id, uint16_t handle, int auth_req) {
CHECK_BTGATT_INIT();
return do_in_jni_thread(Bind(&BTA_GATTC_ReadCharacteristic, conn_id, handle,
auth_req, read_char_cb, nullptr));
@@ -452,11 +413,9 @@ void read_using_char_uuid_cb(uint16_t conn_id, tGATT_STATUS status,
base::Owned(params));
}
-static bt_status_t btif_gattc_read_using_char_uuid(int conn_id,
- const Uuid& uuid,
- uint16_t s_handle,
- uint16_t e_handle,
- int auth_req) {
+bt_status_t btif_gattc_read_using_char_uuid(int conn_id, const Uuid& uuid,
+ uint16_t s_handle,
+ uint16_t e_handle, int auth_req) {
CHECK_BTGATT_INIT();
return do_in_jni_thread(Bind(&BTA_GATTC_ReadUsingCharUuid, conn_id, uuid,
s_handle, e_handle, auth_req,
@@ -476,8 +435,8 @@ void read_desc_cb(uint16_t conn_id, tGATT_STATUS status, uint16_t handle,
CLI_CBACK_IN_JNI(read_descriptor_cb, conn_id, status, params);
}
-static bt_status_t btif_gattc_read_char_descr(int conn_id, uint16_t handle,
- int auth_req) {
+bt_status_t btif_gattc_read_char_descr(int conn_id, uint16_t handle,
+ int auth_req) {
CHECK_BTGATT_INIT();
return do_in_jni_thread(Bind(&BTA_GATTC_ReadCharDescr, conn_id, handle,
auth_req, read_desc_cb, nullptr));
@@ -488,9 +447,8 @@ void write_char_cb(uint16_t conn_id, tGATT_STATUS status, uint16_t handle,
CLI_CBACK_IN_JNI(write_characteristic_cb, conn_id, status, handle);
}
-static bt_status_t btif_gattc_write_char(int conn_id, uint16_t handle,
- int write_type, int auth_req,
- vector<uint8_t> value) {
+bt_status_t btif_gattc_write_char(int conn_id, uint16_t handle, int write_type,
+ int auth_req, vector<uint8_t> value) {
CHECK_BTGATT_INIT();
if (value.size() > BTGATT_MAX_ATTR_LEN) value.resize(BTGATT_MAX_ATTR_LEN);
@@ -505,9 +463,8 @@ void write_descr_cb(uint16_t conn_id, tGATT_STATUS status, uint16_t handle,
CLI_CBACK_IN_JNI(write_descriptor_cb, conn_id, status, handle);
}
-static bt_status_t btif_gattc_write_char_descr(int conn_id, uint16_t handle,
- int auth_req,
- vector<uint8_t> value) {
+bt_status_t btif_gattc_write_char_descr(int conn_id, uint16_t handle,
+ int auth_req, vector<uint8_t> value) {
CHECK_BTGATT_INIT();
if (value.size() > BTGATT_MAX_ATTR_LEN) value.resize(BTGATT_MAX_ATTR_LEN);
@@ -517,15 +474,15 @@ static bt_status_t btif_gattc_write_char_descr(int conn_id, uint16_t handle,
nullptr));
}
-static bt_status_t btif_gattc_execute_write(int conn_id, int execute) {
+bt_status_t btif_gattc_execute_write(int conn_id, int execute) {
CHECK_BTGATT_INIT();
return do_in_jni_thread(
Bind(&BTA_GATTC_ExecuteWrite, conn_id, (uint8_t)execute));
}
-static void btif_gattc_reg_for_notification_impl(tGATT_IF client_if,
- const RawAddress& bda,
- uint16_t handle) {
+void btif_gattc_reg_for_notification_impl(tGATT_IF client_if,
+ const RawAddress& bda,
+ uint16_t handle) {
tGATT_STATUS status =
BTA_GATTC_RegisterForNotifications(client_if, bda, handle);
@@ -544,9 +501,9 @@ bt_status_t btif_gattc_reg_for_notification(int client_if,
bd_addr, handle));
}
-static void btif_gattc_dereg_for_notification_impl(tGATT_IF client_if,
- const RawAddress& bda,
- uint16_t handle) {
+void btif_gattc_dereg_for_notification_impl(tGATT_IF client_if,
+ const RawAddress& bda,
+ uint16_t handle) {
tGATT_STATUS status =
BTA_GATTC_DeregisterForNotifications(client_if, bda, handle);
@@ -565,8 +522,8 @@ bt_status_t btif_gattc_dereg_for_notification(int client_if,
client_if, bd_addr, handle));
}
-static bt_status_t btif_gattc_read_remote_rssi(int client_if,
- const RawAddress& bd_addr) {
+bt_status_t btif_gattc_read_remote_rssi(int client_if,
+ const RawAddress& bd_addr) {
CHECK_BTGATT_INIT();
rssi_request_client_if = client_if;
@@ -574,17 +531,16 @@ static bt_status_t btif_gattc_read_remote_rssi(int client_if,
Bind(base::IgnoreResult(&BTM_ReadRSSI), bd_addr, btm_read_rssi_cb));
}
-static bt_status_t btif_gattc_configure_mtu(int conn_id, int mtu) {
+bt_status_t btif_gattc_configure_mtu(int conn_id, int mtu) {
CHECK_BTGATT_INIT();
return do_in_jni_thread(
- Bind(base::IgnoreResult(
- static_cast<void (*)(uint16_t,uint16_t)>(&BTA_GATTC_ConfigureMTU)),
- conn_id, mtu));
+ Bind(base::IgnoreResult(&BTA_GATTC_ConfigureMTU), conn_id, mtu));
}
-static void btif_gattc_conn_parameter_update_impl(
- RawAddress addr, int min_interval, int max_interval, int latency,
- int timeout, uint16_t min_ce_len, uint16_t max_ce_len) {
+void btif_gattc_conn_parameter_update_impl(RawAddress addr, int min_interval,
+ int max_interval, int latency,
+ int timeout, uint16_t min_ce_len,
+ uint16_t max_ce_len) {
if (BTA_DmGetConnectionState(addr))
BTA_DmBleUpdateConnectionParams(addr, min_interval, max_interval, latency,
timeout, min_ce_len, max_ce_len);
@@ -604,16 +560,16 @@ bt_status_t btif_gattc_conn_parameter_update(const RawAddress& bd_addr,
min_interval, max_interval, latency, timeout, min_ce_len, max_ce_len));
}
-static bt_status_t btif_gattc_set_preferred_phy(const RawAddress& bd_addr,
- uint8_t tx_phy, uint8_t rx_phy,
- uint16_t phy_options) {
+bt_status_t btif_gattc_set_preferred_phy(const RawAddress& bd_addr,
+ uint8_t tx_phy, uint8_t rx_phy,
+ uint16_t phy_options) {
CHECK_BTGATT_INIT();
do_in_main_thread(FROM_HERE,
Bind(&BTM_BleSetPhy, bd_addr, tx_phy, rx_phy, phy_options));
return BT_STATUS_SUCCESS;
}
-static bt_status_t btif_gattc_read_phy(
+bt_status_t btif_gattc_read_phy(
const RawAddress& bd_addr,
base::Callback<void(uint8_t tx_phy, uint8_t rx_phy, uint8_t status)> cb) {
CHECK_BTGATT_INIT();
@@ -622,7 +578,7 @@ static bt_status_t btif_gattc_read_phy(
return BT_STATUS_SUCCESS;
}
-static int btif_gattc_get_device_type(const RawAddress& bd_addr) {
+int btif_gattc_get_device_type(const RawAddress& bd_addr) {
int device_type = 0;
if (btif_config_get_int(bd_addr.ToString().c_str(), "DevType", &device_type))
@@ -630,8 +586,8 @@ static int btif_gattc_get_device_type(const RawAddress& bd_addr) {
return 0;
}
-static bt_status_t btif_gattc_test_command(int command,
- const btgatt_test_params_t& params) {
+bt_status_t btif_gattc_test_command(int command,
+ const btgatt_test_params_t& params) {
return btif_gattc_test_command_impl(command, &params);
}
diff --git a/btif/src/btif_gatt_server.cc b/btif/src/btif_gatt_server.cc
index 00f9ea2e6..6dc5eb7ea 100644
--- a/btif/src/btif_gatt_server.cc
+++ b/btif/src/btif_gatt_server.cc
@@ -48,7 +48,6 @@
#include "btif_storage.h"
#include "osi/include/log.h"
#include "stack/include/btu.h"
-#include "types/bt_transport.h"
using base::Bind;
using base::Owned;
@@ -59,14 +58,14 @@ using std::vector;
* Constants & Macros
******************************************************************************/
-#define CHECK_BTGATT_INIT() \
- do { \
- if (bt_gatt_callbacks == NULL) { \
- LOG_WARN("%s: BTGATT not initialized", __func__); \
- return BT_STATUS_NOT_READY; \
- } else { \
- LOG_VERBOSE("%s", __func__); \
- } \
+#define CHECK_BTGATT_INIT() \
+ do { \
+ if (bt_gatt_callbacks == NULL) { \
+ LOG_WARN(LOG_TAG, "%s: BTGATT not initialized", __func__); \
+ return BT_STATUS_NOT_READY; \
+ } else { \
+ LOG_VERBOSE(LOG_TAG, "%s", __func__); \
+ } \
} while (0)
/*******************************************************************************
@@ -125,7 +124,7 @@ static void btapp_gatts_free_req_data(uint16_t event, tBTA_GATTS* p_data) {
}
static void btapp_gatts_handle_cback(uint16_t event, char* p_param) {
- LOG_VERBOSE("%s: Event %d", __func__, event);
+ LOG_VERBOSE(LOG_TAG, "%s: Event %d", __func__, event);
tBTA_GATTS* p_data = (tBTA_GATTS*)p_param;
switch (event) {
@@ -232,7 +231,7 @@ static void btapp_gatts_handle_cback(uint16_t event, char* p_param) {
case BTA_GATTS_OPEN_EVT:
case BTA_GATTS_CANCEL_OPEN_EVT:
case BTA_GATTS_CLOSE_EVT:
- LOG_INFO("%s: Empty event (%d)!", __func__, event);
+ LOG_DEBUG(LOG_TAG, "%s: Empty event (%d)!", __func__, event);
break;
case BTA_GATTS_PHY_UPDATE_EVT:
@@ -249,7 +248,7 @@ static void btapp_gatts_handle_cback(uint16_t event, char* p_param) {
break;
default:
- LOG_ERROR("%s: Unhandled event (%d)!", __func__, event);
+ LOG_ERROR(LOG_TAG, "%s: Unhandled event (%d)!", __func__, event);
break;
}
@@ -267,12 +266,11 @@ static void btapp_gatts_cback(tBTA_GATTS_EVT event, tBTA_GATTS* p_data) {
/*******************************************************************************
* Server API Functions
******************************************************************************/
-static bt_status_t btif_gatts_register_app(const Uuid& bt_uuid,
- bool eatt_support) {
+static bt_status_t btif_gatts_register_app(const Uuid& bt_uuid) {
CHECK_BTGATT_INIT();
return do_in_jni_thread(
- Bind(&BTA_GATTS_AppRegister, bt_uuid, &btapp_gatts_cback, eatt_support));
+ Bind(&BTA_GATTS_AppRegister, bt_uuid, &btapp_gatts_cback));
}
static bt_status_t btif_gatts_unregister_app(int server_if) {
@@ -283,9 +281,9 @@ static bt_status_t btif_gatts_unregister_app(int server_if) {
static void btif_gatts_open_impl(int server_if, const RawAddress& address,
bool is_direct, int transport_param) {
// Ensure device is in inquiry database
- tBLE_ADDR_TYPE addr_type = BLE_ADDR_PUBLIC;
+ int addr_type = 0;
int device_type = 0;
- tBT_TRANSPORT transport = BT_TRANSPORT_LE;
+ tGATT_TRANSPORT transport = GATT_TRANSPORT_LE;
if (btif_get_address_type(address, &addr_type) &&
btif_get_device_type(address, &device_type) &&
@@ -294,23 +292,23 @@ static void btif_gatts_open_impl(int server_if, const RawAddress& address,
}
// Determine transport
- if (transport_param != BT_TRANSPORT_AUTO) {
+ if (transport_param != GATT_TRANSPORT_AUTO) {
transport = transport_param;
} else {
switch (device_type) {
case BT_DEVICE_TYPE_BREDR:
- transport = BT_TRANSPORT_BR_EDR;
+ transport = GATT_TRANSPORT_BR_EDR;
break;
case BT_DEVICE_TYPE_BLE:
- transport = BT_TRANSPORT_LE;
+ transport = GATT_TRANSPORT_LE;
break;
case BT_DEVICE_TYPE_DUMO:
- if (transport_param == BT_TRANSPORT_LE)
- transport = BT_TRANSPORT_LE;
+ if (transport_param == GATT_TRANSPORT_LE)
+ transport = GATT_TRANSPORT_LE;
else
- transport = BT_TRANSPORT_BR_EDR;
+ transport = GATT_TRANSPORT_BR_EDR;
break;
}
}
@@ -345,7 +343,7 @@ static bt_status_t btif_gatts_close(int server_if, const RawAddress& bd_addr,
Bind(&btif_gatts_close_impl, server_if, bd_addr, conn_id));
}
-static void on_service_added_cb(tGATT_STATUS status, int server_if,
+static void on_service_added_cb(uint8_t status, int server_if,
vector<btgatt_db_element_t> service) {
HAL_CBACK(bt_gatt_callbacks, server->service_added_cb, status, server_if,
std::move(service));
@@ -358,7 +356,7 @@ static void add_service_impl(int server_if,
// refactored, and one can distinguish stack-internal aps from external apps
if (service[0].uuid == Uuid::From16Bit(UUID_SERVCLASS_GATT_SERVER) ||
service[0].uuid == Uuid::From16Bit(UUID_SERVCLASS_GAP_SERVER)) {
- LOG_ERROR("%s: Attept to register restricted service", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Attept to register restricted service", __func__);
HAL_CBACK(bt_gatt_callbacks, server->service_added_cb, BT_STATUS_FAIL,
server_if, std::move(service));
return;
@@ -406,8 +404,7 @@ static void btif_gatts_send_response_impl(int conn_id, int trans_id, int status,
tGATTS_RSP rsp_struct;
btif_to_bta_response(&rsp_struct, &response);
- BTA_GATTS_SendRsp(conn_id, trans_id, static_cast<tGATT_STATUS>(status),
- &rsp_struct);
+ BTA_GATTS_SendRsp(conn_id, trans_id, status, &rsp_struct);
HAL_CBACK(bt_gatt_callbacks, server->response_confirmation_cb, 0,
rsp_struct.attr_value.handle);
diff --git a/btif/src/btif_gatt_test.cc b/btif/src/btif_gatt_test.cc
index 02216c7bb..1c0af357e 100644
--- a/btif/src/btif_gatt_test.cc
+++ b/btif/src/btif_gatt_test.cc
@@ -69,15 +69,16 @@ static btif_test_cb_t test_cb;
static void btif_test_connect_cback(tGATT_IF, const RawAddress&,
uint16_t conn_id, bool connected,
tGATT_DISCONN_REASON, tBT_TRANSPORT) {
- LOG_INFO("%s: conn_id=%d, connected=%d", __func__, conn_id, connected);
+ LOG_DEBUG(LOG_TAG, "%s: conn_id=%d, connected=%d", __func__, conn_id,
+ connected);
test_cb.conn_id = connected ? conn_id : 0;
}
static void btif_test_command_complete_cback(uint16_t conn_id, tGATTC_OPTYPE op,
tGATT_STATUS status,
tGATT_CL_COMPLETE* p_data) {
- LOG_INFO("%s: op_code=0x%02x, conn_id=0x%x. status=0x%x", __func__, op,
- conn_id, status);
+ LOG_DEBUG(LOG_TAG, "%s: op_code=0x%02x, conn_id=0x%x. status=0x%x", __func__,
+ op, conn_id, status);
switch (op) {
case GATTC_OPTYPE_READ:
@@ -88,11 +89,11 @@ static void btif_test_command_complete_cback(uint16_t conn_id, tGATTC_OPTYPE op,
break;
case GATTC_OPTYPE_INDICATION:
- GATTC_SendHandleValueConfirm(conn_id, p_data->cid);
+ GATTC_SendHandleValueConfirm(conn_id, p_data->handle);
break;
default:
- LOG_INFO("%s: Unknown op_code (0x%02x)", __func__, op);
+ LOG_DEBUG(LOG_TAG, "%s: Unknown op_code (0x%02x)", __func__, op);
break;
}
}
@@ -100,61 +101,62 @@ static void btif_test_command_complete_cback(uint16_t conn_id, tGATTC_OPTYPE op,
static void btif_test_discovery_result_cback(UNUSED_ATTR uint16_t conn_id,
tGATT_DISC_TYPE disc_type,
tGATT_DISC_RES* p_data) {
- LOG_INFO("------ GATT Discovery result %-22s -------", disc_name[disc_type]);
- LOG_INFO(" Attribute handle: 0x%04x (%d)", p_data->handle,
- p_data->handle);
+ LOG_DEBUG(LOG_TAG, "------ GATT Discovery result %-22s -------",
+ disc_name[disc_type]);
+ LOG_DEBUG(LOG_TAG, " Attribute handle: 0x%04x (%d)", p_data->handle,
+ p_data->handle);
if (disc_type != GATT_DISC_CHAR_DSCPT) {
- LOG_INFO(" Attribute type: %s", p_data->type.ToString().c_str());
+ LOG_DEBUG(LOG_TAG, " Attribute type: %s",
+ p_data->type.ToString().c_str());
}
switch (disc_type) {
case GATT_DISC_SRVC_ALL:
- LOG_INFO(" Handle range: 0x%04x ~ 0x%04x (%d ~ %d)",
- p_data->handle, p_data->value.group_value.e_handle,
- p_data->handle, p_data->value.group_value.e_handle);
- LOG_INFO(" Service UUID: %s",
- p_data->value.group_value.service_type.ToString().c_str());
+ LOG_DEBUG(LOG_TAG, " Handle range: 0x%04x ~ 0x%04x (%d ~ %d)",
+ p_data->handle, p_data->value.group_value.e_handle,
+ p_data->handle, p_data->value.group_value.e_handle);
+ LOG_DEBUG(LOG_TAG, " Service UUID: %s",
+ p_data->value.group_value.service_type.ToString().c_str());
break;
case GATT_DISC_SRVC_BY_UUID:
- LOG_INFO(" Handle range: 0x%04x ~ 0x%04x (%d ~ %d)",
- p_data->handle, p_data->value.handle, p_data->handle,
- p_data->value.handle);
+ LOG_DEBUG(LOG_TAG, " Handle range: 0x%04x ~ 0x%04x (%d ~ %d)",
+ p_data->handle, p_data->value.handle, p_data->handle,
+ p_data->value.handle);
break;
case GATT_DISC_INC_SRVC:
- LOG_INFO(" Handle range: 0x%04x ~ 0x%04x (%d ~ %d)",
- p_data->value.incl_service.s_handle,
- p_data->value.incl_service.e_handle,
- p_data->value.incl_service.s_handle,
- p_data->value.incl_service.e_handle);
- LOG_INFO(" Service UUID: %s",
- p_data->value.incl_service.service_type.ToString().c_str());
+ LOG_DEBUG(LOG_TAG, " Handle range: 0x%04x ~ 0x%04x (%d ~ %d)",
+ p_data->value.incl_service.s_handle,
+ p_data->value.incl_service.e_handle,
+ p_data->value.incl_service.s_handle,
+ p_data->value.incl_service.e_handle);
+ LOG_DEBUG(LOG_TAG, " Service UUID: %s",
+ p_data->value.incl_service.service_type.ToString().c_str());
break;
case GATT_DISC_CHAR:
- LOG_INFO(" Properties: 0x%02x",
- p_data->value.dclr_value.char_prop);
- LOG_INFO(" Characteristic UUID: %s",
- p_data->value.dclr_value.char_uuid.ToString().c_str());
+ LOG_DEBUG(LOG_TAG, " Properties: 0x%02x",
+ p_data->value.dclr_value.char_prop);
+ LOG_DEBUG(LOG_TAG, " Characteristic UUID: %s",
+ p_data->value.dclr_value.char_uuid.ToString().c_str());
break;
case GATT_DISC_CHAR_DSCPT:
- LOG_INFO(" Descriptor UUID: %s", p_data->type.ToString().c_str());
- break;
- case GATT_DISC_MAX:
- LOG_ERROR(" Unknown discovery item");
+ LOG_DEBUG(LOG_TAG, " Descriptor UUID: %s",
+ p_data->type.ToString().c_str());
break;
}
- LOG_INFO("-----------------------------------------------------------");
+ LOG_DEBUG(LOG_TAG,
+ "-----------------------------------------------------------");
}
static void btif_test_discovery_complete_cback(
UNUSED_ATTR uint16_t conn_id, UNUSED_ATTR tGATT_DISC_TYPE disc_type,
tGATT_STATUS status) {
- LOG_INFO("%s: status=%d", __func__, status);
+ LOG_DEBUG(LOG_TAG, "%s: status=%d", __func__, status);
}
static tGATT_CBACK btif_test_callbacks = {btif_test_connect_cback,
@@ -176,13 +178,12 @@ bt_status_t btif_gattc_test_command_impl(int command,
switch (command) {
case 0x01: /* Enable */
{
- LOG_INFO("%s: ENABLE - enable=%d", __func__, params->u1);
+ LOG_DEBUG(LOG_TAG, "%s: ENABLE - enable=%d", __func__, params->u1);
if (params->u1) {
std::array<uint8_t, Uuid::kNumBytes128> tmp;
tmp.fill(0xAE);
- test_cb.gatt_if =
- GATT_Register(bluetooth::Uuid::From128BitBE(tmp),
- std::string("GattTest"), &btif_test_callbacks, false);
+ test_cb.gatt_if = GATT_Register(bluetooth::Uuid::From128BitBE(tmp),
+ &btif_test_callbacks);
GATT_StartIf(test_cb.gatt_if);
} else {
GATT_Deregister(test_cb.gatt_if);
@@ -193,23 +194,25 @@ bt_status_t btif_gattc_test_command_impl(int command,
case 0x02: /* Connect */
{
- LOG_INFO("%s: CONNECT - device=%s (dev_type=%d, addr_type=%d)", __func__,
- params->bda1->ToString().c_str(), params->u1, params->u2);
+ LOG_DEBUG(LOG_TAG, "%s: CONNECT - device=%s (dev_type=%d, addr_type=%d)",
+ __func__, params->bda1->ToString().c_str(), params->u1,
+ params->u2);
if (params->u1 == BT_DEVICE_TYPE_BLE)
- BTM_SecAddBleDevice(*params->bda1, BT_DEVICE_TYPE_BLE,
- static_cast<tBLE_ADDR_TYPE>(params->u2));
+ BTM_SecAddBleDevice(*params->bda1, NULL, BT_DEVICE_TYPE_BLE,
+ params->u2);
if (!GATT_Connect(test_cb.gatt_if, *params->bda1, true, BT_TRANSPORT_LE,
false)) {
- LOG_ERROR("%s: GATT_Connect failed!", __func__);
+ LOG_ERROR(LOG_TAG, "%s: GATT_Connect failed!", __func__);
}
break;
}
case 0x03: /* Disconnect */
{
- LOG_INFO("%s: DISCONNECT - conn_id=%d", __func__, test_cb.conn_id);
+ LOG_DEBUG(LOG_TAG, "%s: DISCONNECT - conn_id=%d", __func__,
+ test_cb.conn_id);
GATT_Disconnect(test_cb.conn_id);
break;
}
@@ -217,22 +220,25 @@ bt_status_t btif_gattc_test_command_impl(int command,
case 0x04: /* Discover */
{
if (params->u1 >= GATT_DISC_MAX) {
- LOG_ERROR("%s: DISCOVER - Invalid type (%d)!", __func__, params->u1);
+ LOG_ERROR(LOG_TAG, "%s: DISCOVER - Invalid type (%d)!", __func__,
+ params->u1);
return (bt_status_t)0;
}
- LOG_INFO("%s: DISCOVER (%s), conn_id=%d, uuid=%s, handles=0x%04x-0x%04x",
- __func__, disc_name[params->u1], test_cb.conn_id,
- params->uuid1->ToString().c_str(), params->u2, params->u3);
- GATTC_Discover(test_cb.conn_id, static_cast<tGATT_DISC_TYPE>(params->u1),
- params->u2, params->u3, *params->uuid1);
+ LOG_DEBUG(LOG_TAG,
+ "%s: DISCOVER (%s), conn_id=%d, uuid=%s, handles=0x%04x-0x%04x",
+ __func__, disc_name[params->u1], test_cb.conn_id,
+ params->uuid1->ToString().c_str(), params->u2, params->u3);
+ GATTC_Discover(test_cb.conn_id, params->u1, params->u2, params->u3,
+ *params->uuid1);
break;
}
case 0xF0: /* Pairing configuration */
- LOG_INFO("%s: Setting pairing config auth=%d, iocaps=%d, keys=%d/%d/%d",
- __func__, params->u1, params->u2, params->u3, params->u4,
- params->u5);
+ LOG_DEBUG(LOG_TAG,
+ "%s: Setting pairing config auth=%d, iocaps=%d, keys=%d/%d/%d",
+ __func__, params->u1, params->u2, params->u3, params->u4,
+ params->u5);
bte_appl_cfg.ble_auth_req = params->u1;
bte_appl_cfg.ble_io_cap = params->u2;
@@ -242,7 +248,7 @@ bt_status_t btif_gattc_test_command_impl(int command,
break;
default:
- LOG_ERROR("%s: UNKNOWN TEST COMMAND 0x%02x", __func__, command);
+ LOG_ERROR(LOG_TAG, "%s: UNKNOWN TEST COMMAND 0x%02x", __func__, command);
break;
}
return (bt_status_t)0;
diff --git a/btif/src/btif_gatt_util.cc b/btif/src/btif_gatt_util.cc
index e6bbf384d..16f227511 100644
--- a/btif/src/btif_gatt_util.cc
+++ b/btif/src/btif_gatt_util.cc
@@ -39,8 +39,6 @@
#include "btif_storage.h"
#include "btif_util.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_sec.h"
-#include "types/bt_transport.h"
using bluetooth::Uuid;
@@ -59,33 +57,38 @@ void btif_to_bta_response(tGATTS_RSP* p_dest, btgatt_response_t* p_src) {
* Encrypted link map handling
******************************************************************************/
+#if (BLE_DELAY_REQUEST_ENC == FALSE)
static bool btif_gatt_is_link_encrypted(const RawAddress& bd_addr) {
- return BTM_IsEncrypted(bd_addr, BT_TRANSPORT_BR_EDR) ||
- BTM_IsEncrypted(bd_addr, BT_TRANSPORT_LE);
+ return BTA_JvIsEncrypted(bd_addr);
}
static void btif_gatt_set_encryption_cb(UNUSED_ATTR const RawAddress& bd_addr,
- UNUSED_ATTR tBT_TRANSPORT transport,
+ UNUSED_ATTR tBTA_TRANSPORT transport,
tBTA_STATUS result) {
if (result != BTA_SUCCESS && result != BTA_BUSY) {
BTIF_TRACE_WARNING("%s() - Encryption failed (%d)", __func__, result);
}
}
+#endif
+#if (BLE_DELAY_REQUEST_ENC == FALSE)
void btif_gatt_check_encrypted_link(RawAddress bd_addr,
- tBT_TRANSPORT transport_link) {
+ tGATT_TRANSPORT transport_link) {
tBTM_LE_PENC_KEYS key;
if ((btif_storage_get_ble_bonding_key(
- bd_addr, BTM_LE_KEY_PENC, (uint8_t*)&key,
+ &bd_addr, BTIF_DM_LE_KEY_PENC, (uint8_t*)&key,
sizeof(tBTM_LE_PENC_KEYS)) == BT_STATUS_SUCCESS) &&
!btif_gatt_is_link_encrypted(bd_addr)) {
- LOG_DEBUG("Checking gatt link peer:%s transport:%s",
- PRIVATE_ADDRESS(bd_addr),
- bt_transport_text(transport_link).c_str());
+ BTIF_TRACE_DEBUG("%s: transport = %d", __func__, transport_link);
BTA_DmSetEncryption(bd_addr, transport_link, &btif_gatt_set_encryption_cb,
BTM_BLE_SEC_ENCRYPT);
}
}
+#else
+void btif_gatt_check_encrypted_link(UNUSED_ATTR RawAddress bd_addr,
+ UNUSED_ATTR tGATT_TRANSPORT
+ transport_link) {}
+#endif
void btif_gatt_move_track_adv_data(btgatt_track_adv_info_t* p_dest,
btgatt_track_adv_info_t* p_src) {
diff --git a/btif/src/btif_hd.cc b/btif/src/btif_hd.cc
index aa99d48c8..d580a19ef 100644
--- a/btif/src/btif_hd.cc
+++ b/btif/src/btif_hd.cc
@@ -27,19 +27,22 @@
***********************************************************************************/
#define LOG_TAG "BTIF_HD"
-#include <cstdint>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_hd_api.h"
-#include "btif/include/btif_common.h"
-#include "btif/include/btif_hd.h"
-#include "btif/include/btif_storage.h"
-#include "btif/include/btif_util.h"
-#include "include/hardware/bt_hd.h"
-#include "osi/include/allocator.h"
-#include "osi/include/compat.h"
-#include "types/raw_address.h"
+#include <errno.h>
+#include <hardware/bluetooth.h>
+#include <hardware/bt_hd.h>
+#include <log/log.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "bta_api.h"
+#include "bta_hd_api.h"
+#include "bta_hh_api.h"
+
+#include "btif_common.h"
+#include "btif_hd.h"
+#include "btif_storage.h"
+#include "btif_util.h"
#define BTIF_HD_APP_NAME_LEN 50
#define BTIF_HD_APP_DESCRIPTION_LEN 50
@@ -208,7 +211,7 @@ static void btif_hd_upstreams_evt(uint16_t event, char* p_param) {
BTA_HdDisconnect();
break;
}
- btif_storage_set_hidd(p_data->conn.bda);
+ btif_storage_set_hidd((RawAddress*)&p_data->conn.bda);
HAL_CBACK(bt_hd_callbacks, connection_state_cb,
(RawAddress*)&p_data->conn.bda, BTHD_CONN_STATE_CONNECTED);
diff --git a/btif/src/btif_hearing_aid.cc b/btif/src/btif_hearing_aid.cc
index 18d9f671a..52cce270a 100644
--- a/btif/src/btif_hearing_aid.cc
+++ b/btif/src/btif_hearing_aid.cc
@@ -92,15 +92,15 @@ class HearingAidInterfaceImpl
DVLOG(2) << __func__ << " address: " << address;
do_in_main_thread(FROM_HERE, Bind(&HearingAid::Disconnect,
Unretained(HearingAid::Get()), address));
- do_in_jni_thread(FROM_HERE, Bind(&btif_storage_set_hearing_aid_acceptlist,
+ do_in_jni_thread(FROM_HERE, Bind(&btif_storage_set_hearing_aid_white_list,
address, false));
}
- void AddToAcceptlist(const RawAddress& address) override {
+ void AddToWhiteList(const RawAddress& address) override {
VLOG(2) << __func__ << " address: " << address;
- do_in_main_thread(FROM_HERE, Bind(&HearingAid::AddToAcceptlist,
+ do_in_main_thread(FROM_HERE, Bind(&HearingAid::AddToWhiteList,
Unretained(HearingAid::Get()), address));
- do_in_jni_thread(FROM_HERE, Bind(&btif_storage_set_hearing_aid_acceptlist,
+ do_in_jni_thread(FROM_HERE, Bind(&btif_storage_set_hearing_aid_white_list,
address, true));
}
diff --git a/btif/src/btif_hf.cc b/btif/src/btif_hf.cc
index dd8bb26ab..ec4c13f47 100644
--- a/btif/src/btif_hf.cc
+++ b/btif/src/btif_hf.cc
@@ -27,26 +27,24 @@
#define LOG_TAG "bt_btif_hf"
-#include <cstdint>
-#include <string>
+#include <cstdlib>
+#include <cstring>
+#include <ctime>
+
+#include <bta/include/bta_ag_api.h>
+#include <hardware/bluetooth.h>
+#include <hardware/bluetooth_headset_callbacks.h>
+#include <hardware/bluetooth_headset_interface.h>
+#include <hardware/bt_hf.h>
+#include <log/log.h>
-#include "bta/include/bta_ag_api.h"
#include "bta/include/utl.h"
-#include "btif/include/btif_common.h"
-#include "btif/include/btif_profile_queue.h"
-#include "btif/include/btif_util.h"
+#include "bta_ag_api.h"
+#include "btif_common.h"
+#include "btif_hf.h"
+#include "btif_profile_queue.h"
+#include "btif_util.h"
#include "common/metrics.h"
-#include "include/hardware/bluetooth_headset_callbacks.h"
-#include "include/hardware/bluetooth_headset_interface.h"
-#include "include/hardware/bt_hf.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "stack/include/btm_api.h"
-#include "types/raw_address.h"
-
-namespace {
-constexpr char kBtmLogTag[] = "HFP";
-}
namespace bluetooth {
namespace headset {
@@ -71,11 +69,15 @@ namespace headset {
{ BTIF_HSAG_SERVICE_NAME, BTIF_HFAG_SERVICE_NAME }
#endif
+#ifndef BTIF_HF_SECURITY
+#define BTIF_HF_SECURITY (BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT)
+#endif
+
#ifndef BTIF_HF_FEATURES
-#define BTIF_HF_FEATURES \
- (BTA_AG_FEAT_3WAY | BTA_AG_FEAT_ECNR | BTA_AG_FEAT_REJECT | \
- BTA_AG_FEAT_ECS | BTA_AG_FEAT_EXTERR | BTA_AG_FEAT_VREC | \
- BTA_AG_FEAT_CODEC | BTA_AG_FEAT_HF_IND | BTA_AG_FEAT_ESCO_S4 | \
+#define BTIF_HF_FEATURES \
+ (BTA_AG_FEAT_3WAY | BTA_AG_FEAT_ECNR | BTA_AG_FEAT_REJECT | \
+ BTA_AG_FEAT_ECS | BTA_AG_FEAT_EXTERR | BTA_AG_FEAT_VREC | \
+ BTA_AG_FEAT_CODEC | BTA_AG_FEAT_HF_IND | BTA_AG_FEAT_ESCO | \
BTA_AG_FEAT_UNAT)
#endif
@@ -296,22 +298,22 @@ static void btif_hf_upstreams_evt(uint16_t event, char* p_param) {
tBTA_AG* p_data = (tBTA_AG*)p_param;
int idx = p_data->hdr.handle - 1;
- LOG_DEBUG("HF Upstream event:%s", dump_hf_event(event));
+ BTIF_TRACE_DEBUG("%s: event=%s", __func__, dump_hf_event(event));
if ((idx < 0) || (idx >= BTA_AG_MAX_NUM_CLIENTS)) {
- LOG_ERROR("%s Invalid client index:%d", dump_hf_event(event), idx);
+ BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx);
return;
}
if (!bt_hf_callbacks) {
- LOG_ERROR("%s Headset callback is not set", dump_hf_event(event));
+ BTIF_TRACE_ERROR("%s: Headset callback is NULL", __func__);
return;
}
switch (event) {
case BTA_AG_REGISTER_EVT:
btif_hf_cb[idx].handle = p_data->reg.hdr.handle;
- LOG_DEBUG("%s idx:%d btif_hf_cb.handle = %d", dump_hf_event(event), idx,
- btif_hf_cb[idx].handle);
+ BTIF_TRACE_DEBUG("%s: BTA_AG_REGISTER_EVT, btif_hf_cb.handle = %d",
+ __func__, btif_hf_cb[idx].handle);
break;
// RFCOMM connected or failed to connect
case BTA_AG_OPEN_EVT:
@@ -388,11 +390,10 @@ static void btif_hf_upstreams_evt(uint16_t event, char* p_param) {
btif_queue_advance();
}
break;
+ // SLC and RFCOMM both disconnected
case BTA_AG_CLOSE_EVT: {
- LOG_DEBUG(
- "SLC and RFCOMM both disconnected event:%s idx:%d"
- " btif_hf_cb.handle:%d",
- dump_hf_event(event), idx, btif_hf_cb[idx].handle);
+ BTIF_TRACE_DEBUG("%s: BTA_AG_CLOSE_EVT, idx = %d, btif_hf_cb.handle = %d",
+ __func__, idx, btif_hf_cb[idx].handle);
// If AG_OPEN was received but SLC was not connected in time, then
// AG_CLOSE may be received. We need to advance the queue here.
bool failed_to_setup_slc =
@@ -408,8 +409,9 @@ static void btif_hf_upstreams_evt(uint16_t event, char* p_param) {
}
break;
}
+ // SLC connected
case BTA_AG_CONN_EVT:
- LOG_DEBUG("SLC connected event:%s idx:%d", dump_hf_event(event), idx);
+ BTIF_TRACE_DEBUG("%s: BTA_AG_CONN_EVT, idx = %d ", __func__, idx);
btif_hf_cb[idx].peer_feat = p_data->conn.peer_feat;
btif_hf_cb[idx].state = BTHF_CONNECTION_STATE_SLC_CONNECTED;
bt_hf_callbacks->ConnectionStateCallback(btif_hf_cb[idx].state,
@@ -420,21 +422,18 @@ static void btif_hf_upstreams_evt(uint16_t event, char* p_param) {
break;
case BTA_AG_AUDIO_OPEN_EVT:
- LOG_DEBUG("Audio open event:%s", dump_hf_event(event));
bt_hf_callbacks->AudioStateCallback(BTHF_AUDIO_STATE_CONNECTED,
&btif_hf_cb[idx].connected_bda);
break;
case BTA_AG_AUDIO_CLOSE_EVT:
- LOG_DEBUG("Audio close event:%s", dump_hf_event(event));
bt_hf_callbacks->AudioStateCallback(BTHF_AUDIO_STATE_DISCONNECTED,
&btif_hf_cb[idx].connected_bda);
break;
+ /* BTA auto-responds, silently discard */
case BTA_AG_SPK_EVT:
case BTA_AG_MIC_EVT:
- LOG_DEBUG("BTA auto-responds, silently discard event:%s",
- dump_hf_event(event));
bt_hf_callbacks->VolumeControlCallback(
(event == BTA_AG_SPK_EVT) ? BTHF_VOLUME_TYPE_SPK
: BTHF_VOLUME_TYPE_MIC,
@@ -668,7 +667,7 @@ static bt_status_t connect_int(RawAddress* bd_addr, uint16_t uuid) {
hf_cb->connected_bda = *bd_addr;
hf_cb->is_initiator = true;
hf_cb->peer_feat = 0;
- BTA_AgOpen(hf_cb->handle, hf_cb->connected_bda);
+ BTA_AgOpen(hf_cb->handle, hf_cb->connected_bda, BTIF_HF_SECURITY);
return BT_STATUS_SUCCESS;
}
@@ -712,8 +711,6 @@ class HeadsetInterface : Interface {
bt_status_t Disconnect(RawAddress* bd_addr) override;
bt_status_t ConnectAudio(RawAddress* bd_addr) override;
bt_status_t DisconnectAudio(RawAddress* bd_addr) override;
- bt_status_t isNoiseReductionSupported(RawAddress* bd_addr) override;
- bt_status_t isVoiceRecognitionSupported(RawAddress* bd_addr) override;
bt_status_t StartVoiceRecognition(RawAddress* bd_addr) override;
bt_status_t StopVoiceRecognition(RawAddress* bd_addr) override;
bt_status_t VolumeControl(bthf_volume_type_t type, int volume,
@@ -838,32 +835,6 @@ bt_status_t HeadsetInterface::DisconnectAudio(RawAddress* bd_addr) {
return BT_STATUS_SUCCESS;
}
-bt_status_t HeadsetInterface::isNoiseReductionSupported(RawAddress* bd_addr) {
- CHECK_BTHF_INIT();
- int idx = btif_hf_idx_by_bdaddr(bd_addr);
- if ((idx < 0) || (idx >= BTA_AG_MAX_NUM_CLIENTS)) {
- BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx);
- return BT_STATUS_FAIL;
- }
- if (!(btif_hf_cb[idx].peer_feat & BTA_AG_PEER_FEAT_ECNR)) {
- return BT_STATUS_UNSUPPORTED;
- }
- return BT_STATUS_SUCCESS;
-}
-
-bt_status_t HeadsetInterface::isVoiceRecognitionSupported(RawAddress* bd_addr) {
- CHECK_BTHF_INIT();
- int idx = btif_hf_idx_by_bdaddr(bd_addr);
- if ((idx < 0) || (idx >= BTA_AG_MAX_NUM_CLIENTS)) {
- BTIF_TRACE_ERROR("%s: Invalid index %d", __func__, idx);
- return BT_STATUS_FAIL;
- }
- if (!(btif_hf_cb[idx].peer_feat & BTA_AG_PEER_FEAT_VREC)) {
- return BT_STATUS_UNSUPPORTED;
- }
- return BT_STATUS_SUCCESS;
-}
-
bt_status_t HeadsetInterface::StartVoiceRecognition(RawAddress* bd_addr) {
CHECK_BTHF_INIT();
int idx = btif_hf_idx_by_bdaddr(bd_addr);
@@ -1111,15 +1082,14 @@ bt_status_t HeadsetInterface::PhoneStateChange(
const char* number, bthf_call_addrtype_t type, const char* name,
RawAddress* bd_addr) {
CHECK_BTHF_INIT();
- if (bd_addr == nullptr) {
- LOG_WARN("bd_addr is null");
+ if (!bd_addr) {
+ BTIF_TRACE_WARNING("%s: bd_addr is null", __func__);
return BT_STATUS_FAIL;
}
-
- const RawAddress raw_address(*bd_addr);
int idx = btif_hf_idx_by_bdaddr(bd_addr);
if (idx < 0 || idx > BTA_AG_MAX_NUM_CLIENTS) {
- LOG_WARN("Invalid index %d for %s", idx, PRIVATE_ADDRESS(raw_address));
+ BTIF_TRACE_WARNING("%s: invalid index %d for %s", __func__, idx,
+ bd_addr->ToString().c_str());
return BT_STATUS_FAIL;
}
const btif_hf_cb_t& control_block = btif_hf_cb[idx];
@@ -1136,23 +1106,22 @@ bt_status_t HeadsetInterface::PhoneStateChange(
<< ", num_held=" << num_held;
return BT_STATUS_SUCCESS;
}
- LOG_DEBUG(
- "bd_addr:%s active_bda:%s num_active:%u prev_num_active:%u num_held:%u "
- "prev_num_held:%u call_state:%s prev_call_state:%s",
- PRIVATE_ADDRESS((*bd_addr)), PRIVATE_ADDRESS(active_bda), num_active,
- control_block.num_active, num_held, control_block.num_held,
- dump_hf_call_state(call_setup_state),
- dump_hf_call_state(control_block.call_setup_state));
- tBTA_AG_RES res = BTA_AG_UNKNOWN;
+ LOG(INFO) << __func__ << ": idx=" << idx << ", addr=" << *bd_addr
+ << ", active_bda=" << active_bda << ", num_active=" << num_active
+ << ", prev_num_active" << control_block.num_active
+ << ", num_held=" << num_held
+ << ", prev_num_held=" << control_block.num_held
+ << ", call_state=" << dump_hf_call_state(call_setup_state)
+ << ", prev_call_state="
+ << dump_hf_call_state(control_block.call_setup_state);
+ tBTA_AG_RES res = 0xFF;
bt_status_t status = BT_STATUS_SUCCESS;
bool active_call_updated = false;
/* if all indicators are 0, send end call and return */
if (num_active == 0 && num_held == 0 &&
call_setup_state == BTHF_CALL_STATE_IDLE) {
- if (control_block.num_active > 0) {
- BTM_LogHistory(kBtmLogTag, raw_address, "Call Ended");
- }
+ VLOG(1) << __func__ << ": call ended";
BTA_AgResult(control_block.handle, BTA_AG_END_CALL_RES,
tBTA_AG_RES_DATA::kEmpty);
/* if held call was present, reset that as well */
@@ -1291,13 +1260,6 @@ bt_status_t HeadsetInterface::PhoneStateChange(
snprintf(ag_res.str, sizeof(ag_res.str), "%s",
call_number_stream.str().c_str());
}
- {
- std::string cell_number(number);
- BTM_LogHistory(
- kBtmLogTag, raw_address, "Call Incoming",
- base::StringPrintf("number:%s", PRIVATE_CELL(cell_number)));
- }
- // base::StringPrintf("number:%s", PRIVATE_CELL(number)));
break;
case BTHF_CALL_STATE_DIALING:
if (!(num_active + num_held) && is_active_device(*bd_addr)) {
@@ -1465,7 +1427,8 @@ bt_status_t ExecuteService(bool b_enable) {
/* Enable and register with BTA-AG */
BTA_AgEnable(bte_hf_evt);
for (uint8_t app_id = 0; app_id < btif_max_hf_clients; app_id++) {
- BTA_AgRegister(BTIF_HF_SERVICES, btif_hf_features, service_names, app_id);
+ BTA_AgRegister(BTIF_HF_SERVICES, BTIF_HF_SECURITY, btif_hf_features,
+ service_names, app_id);
}
} else {
/* De-register AG */
diff --git a/btif/src/btif_hf_client.cc b/btif/src/btif_hf_client.cc
index 3a8e4ea72..06fe5e453 100644..100755
--- a/btif/src/btif_hf_client.cc
+++ b/btif/src/btif_hf_client.cc
@@ -42,15 +42,15 @@
*
******************************************************************************/
-#ifndef LOG_TAG
#define LOG_TAG "bt_btif_hfc"
-#endif
+#include <stdlib.h>
#include <string.h>
#include <hardware/bluetooth.h>
#include <hardware/bt_hf_client.h>
+#include "bt_utils.h"
#include "bta_hf_client_api.h"
#include "btif_common.h"
#include "btif_profile_queue.h"
@@ -66,6 +66,10 @@
#define BTIF_HF_CLIENT_SERVICE_NAME ("Handsfree")
#endif
+#ifndef BTIF_HF_CLIENT_SECURITY
+#define BTIF_HF_CLIENT_SECURITY (BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT)
+#endif
+
#ifndef BTIF_HF_CLIENT_FEATURES
#define BTIF_HF_CLIENT_FEATURES \
(BTA_HF_CLIENT_FEAT_ECNR | BTA_HF_CLIENT_FEAT_3WAY | \
@@ -310,7 +314,7 @@ static bt_status_t connect_int(RawAddress* bd_addr, uint16_t uuid) {
* The handle is valid until we have called BTA_HfClientClose or the LL
* has notified us of channel close due to remote closing, error etc.
*/
- BTA_HfClientOpen(cb->peer_bda, &cb->handle);
+ BTA_HfClientOpen(cb->peer_bda, BTIF_HF_CLIENT_SECURITY, &cb->handle);
return BT_STATUS_SUCCESS;
}
@@ -1041,16 +1045,14 @@ bt_status_t btif_hf_client_execute_service(bool b_enable) {
BTIF_TRACE_EVENT("%s: enable: %d", __func__, b_enable);
tBTA_HF_CLIENT_FEAT features = BTIF_HF_CLIENT_FEATURES;
- uint16_t hfp_version = BTA_HFP_VERSION;
- if (hfp_version >= HFP_VERSION_1_7) {
- features |= BTA_HF_CLIENT_FEAT_ESCO_S4;
- }
+ if (osi_property_get_bool("persist.bluetooth.hfpclient.sco_s4_supported",
+ false))
+ features |= BTA_HF_CLIENT_FEAT_S4;
if (b_enable) {
/* Enable and register with BTA-HFClient */
- BTIF_TRACE_EVENT("%s: support codec negotiation %d ", __func__,
- features);
- BTA_HfClientEnable(bta_hf_client_evt, features,
+ BTIF_TRACE_EVENT("%s: support codec negotiation %d ", __func__, features);
+ BTA_HfClientEnable(bta_hf_client_evt, BTIF_HF_CLIENT_SECURITY, features,
BTIF_HF_CLIENT_SERVICE_NAME);
} else {
BTA_HfClientDisable();
diff --git a/btif/src/btif_hh.cc b/btif/src/btif_hh.cc
index 9e5db0c1a..5380fa566 100644
--- a/btif/src/btif_hh.cc
+++ b/btif/src/btif_hh.cc
@@ -27,23 +27,34 @@
#define LOG_TAG "bt_btif_hh"
-#include <cstdint>
-
-#include "btif/include/btif_common.h"
-#include "btif/include/btif_hh.h"
-#include "btif/include/btif_storage.h"
-#include "btif/include/btif_util.h"
-#include "include/hardware/bt_hh.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/allocator.h"
+#include "btif_hh.h"
+
+#include <base/logging.h>
+#include <errno.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <unistd.h>
+
+#include "bt_common.h"
+#include "bta_api.h"
+#include "btif_common.h"
+#include "btif_storage.h"
+#include "btif_util.h"
+#include "l2c_api.h"
#include "osi/include/log.h"
-#include "stack/include/hidh_api.h"
-#include "stack/include/l2c_api.h"
+#include "osi/include/osi.h"
+
+#define BTIF_HH_APP_ID_MI 0x01
+#define BTIF_HH_APP_ID_KB 0x02
#define COD_HID_KEYBOARD 0x0540
#define COD_HID_POINTING 0x0580
#define COD_HID_COMBO 0x05C0
+#define KEYSTATE_FILEPATH \
+ "/data/misc/bluedroid/bt_hh_ks" // keep this in sync with HID host jni
+
#define HID_REPORT_CAPSLOCK 0x39
#define HID_REPORT_NUMLOCK 0x53
#define HID_REPORT_SCROLLLOCK 0x47
@@ -55,13 +66,19 @@
#define LOGITECH_KB_MX5500_VENDOR_ID 0x046D
#define LOGITECH_KB_MX5500_PRODUCT_ID 0xB30B
+extern const int BT_UID;
+extern const int BT_GID;
static int btif_hh_keylockstates = 0; // The current key state of each key
-// TODO This is duplicated in header file with different value
+#define BTIF_HH_ID_1 0
#define BTIF_HH_DEV_DISCONNECTED 3
#define BTIF_TIMEOUT_VUP_MS (3 * 1000)
+#ifndef BTUI_HH_SECURITY
+#define BTUI_HH_SECURITY (BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT)
+#endif
+
/* HH request events */
typedef enum {
BTIF_HH_CONNECT_REQ_EVT = 0,
@@ -72,6 +89,7 @@ typedef enum {
/*******************************************************************************
* Constants & Macros
******************************************************************************/
+#define BTIF_HH_SERVICES (BTA_HID_SERVICE_MASK)
/*******************************************************************************
* Local type definitions
@@ -112,19 +130,30 @@ static tHID_KB_LIST hid_kb_numlock_on_list[] = {{LOGITECH_KB_MX5500_PRODUCT_ID,
/*******************************************************************************
* Externs
******************************************************************************/
-extern bool check_cod(const RawAddress* remote_bdaddr, uint32_t cod);
-extern bool check_cod_hid(const RawAddress* remote_bdaddr);
extern void bta_hh_co_destroy(int fd);
+extern void bta_hh_co_write(int fd, uint8_t* rpt, uint16_t len);
+extern bt_status_t btif_dm_remove_bond(const RawAddress* bd_addr);
extern void bta_hh_co_send_hid_info(btif_hh_device_t* p_dev,
const char* dev_name, uint16_t vendor_id,
uint16_t product_id, uint16_t version,
uint8_t ctry_code, int dscp_len,
uint8_t* p_dscp);
-extern void bta_hh_co_write(int fd, uint8_t* rpt, uint16_t len);
-extern void bte_hh_evt(tBTA_HH_EVT event, tBTA_HH* p_data);
+extern bool check_cod(const RawAddress* remote_bdaddr, uint32_t cod);
+extern void btif_dm_cb_remove_bond(const RawAddress* bd_addr);
+extern bool check_cod_hid(const RawAddress* remote_bdaddr);
+extern int scru_ascii_2_hex(char* p_ascii, int len, uint8_t* p_hex);
extern void btif_dm_hh_open_failed(RawAddress* bdaddr);
extern void btif_hd_service_registration();
-extern void btif_hh_timer_timeout(void* data);
+
+/*****************************************************************************
+ * Local Function prototypes
+ ****************************************************************************/
+static void set_keylockstate(int keymask, bool isSet);
+static void toggle_os_keylockstates(int fd, int changedkeystates);
+static void sync_lockstate_on_connect(btif_hh_device_t* p_dev);
+// static void hh_update_keyboard_lockstates(btif_hh_device_t *p_dev);
+void btif_hh_timer_timeout(void* data);
+void bte_hh_evt(tBTA_HH_EVT event, tBTA_HH* p_data);
/*******************************************************************************
* Functions
@@ -431,7 +460,7 @@ void btif_hh_remove_device(RawAddress bd_addr) {
p_added_dev = &btif_hh_cb.added_devices[i];
if (p_added_dev->bd_addr == bd_addr) {
BTA_HhRemoveDev(p_added_dev->dev_handle);
- btif_storage_remove_hid_info(p_added_dev->bd_addr);
+ btif_storage_remove_hid_info(&(p_added_dev->bd_addr));
memset(&(p_added_dev->bd_addr), 0, 6);
p_added_dev->dev_handle = BTA_HH_INVALID_HANDLE;
break;
@@ -446,13 +475,8 @@ void btif_hh_remove_device(RawAddress bd_addr) {
/* need to notify up-layer device is disconnected to avoid state out of sync
* with up-layer */
-
- do_in_jni_thread(base::Bind(
- [](RawAddress bd_addr) {
- HAL_CBACK(bt_hh_callbacks, connection_state_cb, &bd_addr,
- BTHH_CONN_STATE_DISCONNECTED);
- },
- p_dev->bd_addr));
+ HAL_CBACK(bt_hh_callbacks, connection_state_cb, &(p_dev->bd_addr),
+ BTHH_CONN_STATE_DISCONNECTED);
p_dev->dev_status = BTHH_CONN_STATE_UNKNOWN;
p_dev->dev_handle = BTA_HH_INVALID_HANDLE;
@@ -587,7 +611,7 @@ bt_status_t btif_hh_connect(const RawAddress* bd_addr) {
pagescan mode, we will do 2 retries to connect before giving up */
btif_hh_cb.status = BTIF_HH_DEV_CONNECTING;
btif_hh_cb.pending_conn_address = *bd_addr;
- BTA_HhOpen(*bd_addr);
+ BTA_HhOpen(*bd_addr, BTA_HH_PROTO_RPT_MODE, BTUI_HH_SECURITY);
// TODO(jpawlowski); make cback accept const and remove tmp!
auto tmp = *bd_addr;
@@ -605,17 +629,14 @@ bt_status_t btif_hh_connect(const RawAddress* bd_addr) {
* Returns void
*
******************************************************************************/
+
void btif_hh_disconnect(RawAddress* bd_addr) {
- CHECK(bd_addr != nullptr);
- const btif_hh_device_t* p_dev = btif_hh_find_connected_dev_by_bda(*bd_addr);
- if (p_dev == nullptr) {
- LOG_DEBUG("Unable to disconnect unknown HID device:%s",
- PRIVATE_ADDRESS((*bd_addr)));
- return;
- }
- LOG_DEBUG("Disconnect and close request for HID device:%s",
- PRIVATE_ADDRESS((*bd_addr)));
- BTA_HhClose(p_dev->dev_handle);
+ btif_hh_device_t* p_dev;
+ p_dev = btif_hh_find_connected_dev_by_bda(*bd_addr);
+ if (p_dev != NULL) {
+ BTA_HhClose(p_dev->dev_handle);
+ } else
+ BTIF_TRACE_DEBUG("%s-- Error: device not connected:", __func__);
}
/*******************************************************************************
@@ -640,26 +661,6 @@ void btif_hh_setreport(btif_hh_device_t* p_dev, bthh_report_type_t r_type,
/*******************************************************************************
*
- * Function btif_btif_hh_senddata
- *
- * Description senddata initiated from the BTIF thread context
- *
- * Returns void
- *
- ******************************************************************************/
-void btif_hh_senddata(btif_hh_device_t* p_dev, uint16_t size, uint8_t* report) {
- BT_HDR* p_buf = create_pbuf(size, report);
- if (p_buf == NULL) {
- APPL_TRACE_ERROR("%s: Error, failed to allocate RPT buffer, size = %d",
- __func__, size);
- return;
- }
- p_buf->layer_specific = BTA_HH_RPTT_OUTPUT;
- BTA_HhSendData(p_dev->dev_handle, p_dev->bd_addr, p_buf);
-}
-
-/*******************************************************************************
- *
* Function btif_hh_service_registration
*
* Description Registers or derigisters the hid host service
@@ -679,7 +680,7 @@ void btif_hh_service_registration(bool enable) {
btif_hd_service_registration();
}
} else if (enable) {
- BTA_HhEnable(bte_hh_evt);
+ BTA_HhEnable(BTA_SEC_ENCRYPT, bte_hh_evt);
} else {
btif_hh_cb.service_dereg_active = TRUE;
BTA_HhDisable();
@@ -959,7 +960,7 @@ static void btif_hh_upstreams_evt(uint16_t event, char* p_param) {
}
if (p_dev->fd < 0) {
LOG_ERROR(
-
+ LOG_TAG,
"BTA_HH_GET_DSCP_EVT: Error, failed to find the uhid driver...");
return;
}
@@ -1083,7 +1084,7 @@ static void btif_hh_upstreams_evt(uint16_t event, char* p_param) {
break;
case BTA_HH_API_ERR_EVT:
- LOG_INFO("BTA_HH API_ERR");
+ LOG_INFO(LOG_TAG, "BTA_HH API_ERR");
break;
default:
@@ -1146,13 +1147,13 @@ void bte_hh_evt(tBTA_HH_EVT event, tBTA_HH* p_data) {
******************************************************************************/
static void btif_hh_handle_evt(uint16_t event, char* p_param) {
- CHECK(p_param != nullptr);
RawAddress* bd_addr = (RawAddress*)p_param;
+ BTIF_TRACE_EVENT("%s: event=%d", __func__, event);
+ int ret;
switch (event) {
case BTIF_HH_CONNECT_REQ_EVT: {
- LOG_DEBUG("Connect request received remote:%s",
- PRIVATE_ADDRESS((*bd_addr)));
- if (btif_hh_connect(bd_addr) == BT_STATUS_SUCCESS) {
+ ret = btif_hh_connect(bd_addr);
+ if (ret == BT_STATUS_SUCCESS) {
HAL_CBACK(bt_hh_callbacks, connection_state_cb, bd_addr,
BTHH_CONN_STATE_CONNECTING);
} else
@@ -1161,25 +1162,19 @@ static void btif_hh_handle_evt(uint16_t event, char* p_param) {
} break;
case BTIF_HH_DISCONNECT_REQ_EVT: {
- LOG_DEBUG("Disconnect request received remote:%s",
- PRIVATE_ADDRESS((*bd_addr)));
+ BTIF_TRACE_EVENT("%s: event=%d", __func__, event);
btif_hh_disconnect(bd_addr);
HAL_CBACK(bt_hh_callbacks, connection_state_cb, bd_addr,
BTHH_CONN_STATE_DISCONNECTING);
} break;
case BTIF_HH_VUP_REQ_EVT: {
- LOG_DEBUG("Virtual unplug request received remote:%s",
- PRIVATE_ADDRESS((*bd_addr)));
- if (btif_hh_virtual_unplug(bd_addr) != BT_STATUS_SUCCESS) {
- LOG_WARN("Unable to virtual unplug device remote:%s",
- PRIVATE_ADDRESS((*bd_addr)));
- }
+ BTIF_TRACE_EVENT("%s: event=%d", __func__, event);
+ ret = btif_hh_virtual_unplug(bd_addr);
} break;
default: {
- LOG_WARN("Unknown event received:%d remote:%s", event,
- PRIVATE_ADDRESS((*bd_addr)));
+ BTIF_TRACE_WARNING("%s : Unknown event 0x%x", __func__, event);
} break;
}
}
@@ -1202,7 +1197,7 @@ void btif_hh_timer_timeout(void* data) {
if (p_dev->dev_status != BTHH_CONN_STATE_CONNECTED) return;
memset(&p_data, 0, sizeof(tBTA_HH));
- p_data.dev_status.status = BTA_HH_ERR; // tBTA_HH_STATUS
+ p_data.dev_status.status = BTHH_ERR;
p_data.dev_status.handle = p_dev->dev_handle;
/* switch context to btif task context */
@@ -1248,12 +1243,8 @@ static bt_status_t connect(RawAddress* bd_addr) {
btif_transfer_context(btif_hh_handle_evt, BTIF_HH_CONNECT_REQ_EVT,
(char*)bd_addr, sizeof(RawAddress), NULL);
return BT_STATUS_SUCCESS;
- } else if ((btif_hh_cb.pending_conn_address == *bd_addr) &&
- (btif_hh_cb.status == BTIF_HH_DEV_CONNECTING)) {
- LOG(INFO) << __func__ << ": already connecting " << *bd_addr;
+ } else
return BT_STATUS_BUSY;
- }
- return BT_STATUS_FAIL;
}
/*******************************************************************************
@@ -1359,7 +1350,7 @@ static bt_status_t set_idle_time(RawAddress* bd_addr, uint8_t idle_time) {
return BT_STATUS_FAIL;
}
- btif_hh_device_t* p_dev = btif_hh_find_connected_dev_by_bda(*bd_addr);
+ btif_hh_device_t* p_dev = p_dev = btif_hh_find_connected_dev_by_bda(*bd_addr);
if (p_dev == NULL) {
BTIF_TRACE_WARNING("%s: addr = %s not opened", __func__,
bd_addr->ToString().c_str());
@@ -1559,7 +1550,7 @@ static bt_status_t set_report(RawAddress* bd_addr,
/* Build a SetReport data buffer */
// TODO
hex_bytes_filled = ascii_2_hex(report, len, hexbuf);
- LOG_INFO("Hex bytes filled, hex value: %d", hex_bytes_filled);
+ LOG_INFO(LOG_TAG, "Hex bytes filled, hex value: %d", hex_bytes_filled);
if (hex_bytes_filled) {
BT_HDR* p_buf = create_pbuf(hex_bytes_filled, hexbuf);
if (p_buf == NULL) {
@@ -1701,7 +1692,7 @@ static const bthh_interface_t bthhInterface = {
bt_status_t btif_hh_execute_service(bool b_enable) {
if (b_enable) {
/* Enable and register with BTA-HH */
- BTA_HhEnable(bte_hh_evt);
+ BTA_HhEnable(BTUI_HH_SECURITY, bte_hh_evt);
} else {
/* Disable HH */
BTA_HhDisable();
diff --git a/btif/src/btif_keystore.cc b/btif/src/btif_keystore.cc
index dcc816b62..86194b77c 100644
--- a/btif/src/btif_keystore.cc
+++ b/btif/src/btif_keystore.cc
@@ -18,7 +18,6 @@
#include <btif_common.h>
#include <btif_keystore.h>
-#include "btif_storage.h"
#include <base/bind.h>
#include <base/location.h>
@@ -44,9 +43,6 @@ class BluetoothKeystoreInterfaceImpl
void init(BluetoothKeystoreCallbacks* callbacks) override {
VLOG(2) << __func__;
this->callbacks = callbacks;
- // Get bonded devices number to get all bonded devices key.
- do_in_jni_thread(
- FROM_HERE, base::Bind([]() { btif_storage_get_num_bonded_devices(); }));
}
void set_encrypt_key_or_remove_key(std::string prefix,
diff --git a/btif/src/btif_le_audio.cc b/btif/src/btif_le_audio.cc
deleted file mode 100644
index 5143cb6e4..000000000
--- a/btif/src/btif_le_audio.cc
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- * Copyright 2019 HIMSA II K/S - www.himsa.com. Represented by EHIMA -
- * www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <hardware/bluetooth.h>
-#include <vector>
-
-#include "btif_common.h"
-#include "btif_storage.h"
-#include "hardware/bt_le_audio.h"
-#include "stack/include/btu.h"
-
-#include <hardware/bt_le_audio.h>
-
-using base::Bind;
-using base::Unretained;
-using bluetooth::le_audio::ConnectionState;
-
-using bluetooth::le_audio::GroupStatus;
-using bluetooth::le_audio::LeAudioClientCallbacks;
-using bluetooth::le_audio::LeAudioClientInterface;
-
-namespace {
-class LeAudioClientInterfaceImpl;
-std::unique_ptr<LeAudioClientInterface> lEAudioInstance;
-
-class LeAudioClientInterfaceImpl : public LeAudioClientInterface,
- public LeAudioClientCallbacks {
- ~LeAudioClientInterfaceImpl() = default;
-
- void OnConnectionState(ConnectionState state,
- const RawAddress& address) override {
- do_in_jni_thread(FROM_HERE, Bind(&LeAudioClientCallbacks::OnConnectionState,
- Unretained(callbacks), state, address));
- }
-
- void OnGroupStatus(uint8_t group_id, GroupStatus group_status,
- uint8_t group_flags) override {
- do_in_jni_thread(FROM_HERE, Bind(&LeAudioClientCallbacks::OnGroupStatus,
- Unretained(callbacks), group_id,
- group_status, group_flags));
- }
-
- void OnSetMemberAvailable(const RawAddress& address,
- uint8_t group_id) override {
- do_in_jni_thread(FROM_HERE,
- Bind(&LeAudioClientCallbacks::OnSetMemberAvailable,
- Unretained(callbacks), address, group_id));
- }
-
- void OnAudioConf(const RawAddress& addr, uint8_t direction, uint8_t group_id,
- uint32_t snk_audio_location,
- uint32_t src_audio_location) override {
- do_in_jni_thread(
- FROM_HERE,
- Bind(&LeAudioClientCallbacks::OnAudioConf, Unretained(callbacks), addr,
- direction, group_id, snk_audio_location, src_audio_location));
- }
-
- void Initialize(LeAudioClientCallbacks* callbacks) override {
- this->callbacks = callbacks;
- }
-
- void Cleanup(void) override {}
-
- void Connect(const RawAddress& address) override {}
-
- void Disconnect(const RawAddress& address) override {}
-
- void GroupStream(const uint8_t group_id,
- const uint16_t content_type) override {}
-
- void GroupSuspend(const uint8_t group_id) override {}
-
- void GroupStop(const uint8_t group_id) override {}
-
- private:
- LeAudioClientCallbacks* callbacks;
-};
-
-} /* namespace */
-
-LeAudioClientInterface* btif_le_audio_get_interface() {
- if (!lEAudioInstance) {
- lEAudioInstance.reset(new LeAudioClientInterfaceImpl());
- }
-
- return lEAudioInstance.get();
-}
diff --git a/btif/src/btif_mce.cc b/btif/src/btif_mce.cc
new file mode 100644
index 000000000..d9326dbdb
--- /dev/null
+++ b/btif/src/btif_mce.cc
@@ -0,0 +1,161 @@
+/******************************************************************************
+ *
+ * Copyright 2014 The Android Open Source Project
+ * Copyright 2009-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+/*******************************************************************************
+ *
+ * Filename: btif_mce.c
+ *
+ * Description: Message Access Profile (MCE role) Bluetooth Interface
+ *
+ *
+ ******************************************************************************/
+
+#define LOG_TAG "bt_btif_mce"
+
+#include <stdlib.h>
+#include <string.h>
+
+#include <hardware/bluetooth.h>
+#include <hardware/bt_mce.h>
+
+#include "bt_types.h"
+#include "bta_api.h"
+#include "bta_mce_api.h"
+#include "btif_common.h"
+#include "btif_util.h"
+
+/*****************************************************************************
+ * Static variables
+ *****************************************************************************/
+
+static btmce_callbacks_t* bt_mce_callbacks = NULL;
+
+static void btif_mce_mas_discovery_comp_evt(uint16_t event, char* p_param) {
+ tBTA_MCE_MAS_DISCOVERY_COMP* evt_data = (tBTA_MCE_MAS_DISCOVERY_COMP*)p_param;
+ btmce_mas_instance_t insts[BTA_MCE_MAX_MAS_INSTANCES];
+ int i;
+
+ BTIF_TRACE_EVENT("%s: event = %d", __func__, event);
+
+ if (event != BTA_MCE_MAS_DISCOVERY_COMP_EVT) return;
+
+ for (i = 0; i < evt_data->num_mas; i++) {
+ insts[i].id = evt_data->mas[i].instance_id;
+ insts[i].scn = evt_data->mas[i].scn;
+ insts[i].msg_types = evt_data->mas[i].msg_type;
+ insts[i].p_name = evt_data->mas[i].p_srv_name;
+ }
+
+ RawAddress addr = evt_data->remote_addr;
+ HAL_CBACK(bt_mce_callbacks, remote_mas_instances_cb,
+ (bt_status_t)evt_data->status, &addr, evt_data->num_mas, insts);
+}
+
+static void mas_discovery_comp_copy_cb(uint16_t event, char* p_dest,
+ char* p_src) {
+ tBTA_MCE_MAS_DISCOVERY_COMP* p_dest_data =
+ (tBTA_MCE_MAS_DISCOVERY_COMP*)p_dest;
+ tBTA_MCE_MAS_DISCOVERY_COMP* p_src_data = (tBTA_MCE_MAS_DISCOVERY_COMP*)p_src;
+ char* p_dest_str;
+ int i;
+
+ if (!p_src) return;
+
+ if (event != BTA_MCE_MAS_DISCOVERY_COMP_EVT) return;
+
+ maybe_non_aligned_memcpy(p_dest_data, p_src_data, sizeof(*p_src_data));
+
+ p_dest_str = p_dest + sizeof(tBTA_MCE_MAS_DISCOVERY_COMP);
+
+ for (i = 0; i < p_src_data->num_mas; i++) {
+ p_dest_data->mas[i].p_srv_name = p_dest_str;
+ memcpy(p_dest_str, p_src_data->mas[i].p_srv_name,
+ p_src_data->mas[i].srv_name_len);
+ p_dest_str += p_src_data->mas[i].srv_name_len;
+ *(p_dest_str++) = '\0';
+ }
+}
+
+static void mce_dm_cback(tBTA_MCE_EVT event, tBTA_MCE* p_data,
+ void* user_data) {
+ switch (event) {
+ case BTA_MCE_MAS_DISCOVERY_COMP_EVT: {
+ int i;
+ uint16_t param_len = sizeof(tBTA_MCE);
+
+ /* include space for all p_srv_name copies including null-termination */
+ for (i = 0; i < p_data->mas_disc_comp.num_mas; i++)
+ param_len += (p_data->mas_disc_comp.mas[i].srv_name_len + 1);
+
+ /* need to deepy copy p_srv_name and null-terminate */
+ btif_transfer_context(btif_mce_mas_discovery_comp_evt, event,
+ (char*)p_data, param_len,
+ mas_discovery_comp_copy_cb);
+
+ break;
+ }
+ }
+}
+
+static bt_status_t init(btmce_callbacks_t* callbacks) {
+ BTIF_TRACE_EVENT("%s", __func__);
+
+ bt_mce_callbacks = callbacks;
+
+ btif_enable_service(BTA_MAP_SERVICE_ID);
+
+ return BT_STATUS_SUCCESS;
+}
+
+static bt_status_t get_remote_mas_instances(RawAddress* bd_addr) {
+ VLOG(2) << __func__ << ": remote_addr=" << bd_addr;
+
+ BTA_MceGetRemoteMasInstances(*bd_addr);
+
+ return BT_STATUS_SUCCESS;
+}
+
+static const btmce_interface_t mce_if = {
+ sizeof(btmce_interface_t), init, get_remote_mas_instances,
+};
+
+const btmce_interface_t* btif_mce_get_interface(void) {
+ BTIF_TRACE_EVENT("%s", __func__);
+ return &mce_if;
+}
+
+/*******************************************************************************
+ *
+ * Function btif_mce_execute_service
+ *
+ * Description Initializes/Shuts down the service
+ *
+ * Returns BT_STATUS_SUCCESS on success, BT_STATUS_FAIL otherwise
+ *
+ ******************************************************************************/
+bt_status_t btif_mce_execute_service(bool b_enable) {
+ BTIF_TRACE_EVENT("%s enable:%d", __func__, b_enable);
+
+ if (b_enable) {
+ BTA_MceEnable(mce_dm_cback);
+ } else {
+ /* This is called on BT disable so no need to extra cleanup */
+ }
+ return BT_STATUS_SUCCESS;
+}
diff --git a/btif/src/btif_metrics_logging.cc b/btif/src/btif_metrics_logging.cc
deleted file mode 100644
index e177fd431..000000000
--- a/btif/src/btif_metrics_logging.cc
+++ /dev/null
@@ -1,166 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
-
-#include "btif/include/btif_metrics_logging.h"
-#include "common/metric_id_allocator.h"
-#include "common/metrics.h"
-#include "main/shim/metrics_api.h"
-#include "main/shim/shim.h"
-#include "types/raw_address.h"
-
-void log_a2dp_audio_underrun_event(const RawAddress& address,
- uint64_t encoding_interval_millis,
- int num_missing_pcm_bytes) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricA2dpAudioUnderrunEvent(
- address, encoding_interval_millis, num_missing_pcm_bytes);
- } else {
- bluetooth::common::LogA2dpAudioUnderrunEvent(
- address, encoding_interval_millis, num_missing_pcm_bytes);
- }
-}
-
-void log_a2dp_audio_overrun_event(const RawAddress& address,
- uint64_t encoding_interval_millis,
- int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricA2dpAudioOverrunEvent(
- address, encoding_interval_millis, num_dropped_buffers,
- num_dropped_encoded_frames, num_dropped_encoded_bytes);
- } else {
- bluetooth::common::LogA2dpAudioOverrunEvent(
- address, encoding_interval_millis, num_dropped_buffers,
- num_dropped_encoded_frames, num_dropped_encoded_bytes);
- }
-}
-
-void log_a2dp_playback_event(const RawAddress& address, int playback_state,
- int audio_coding_mode) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricA2dpPlaybackEvent(address, playback_state,
- audio_coding_mode);
- } else {
- bluetooth::common::LogA2dpPlaybackEvent(address, playback_state,
- audio_coding_mode);
- }
-}
-
-void log_read_rssi_result(const RawAddress& address, uint16_t handle,
- uint32_t cmd_status, int8_t rssi) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricReadRssiResult(address, handle, cmd_status, rssi);
- } else {
- bluetooth::common::LogReadRssiResult(address, handle, cmd_status, rssi);
- }
-}
-
-void log_read_failed_contact_counter_result(const RawAddress& address,
- uint16_t handle,
- uint32_t cmd_status,
- int32_t failed_contact_counter) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricReadFailedContactCounterResult(
- address, handle, cmd_status, failed_contact_counter);
- } else {
- bluetooth::common::LogReadFailedContactCounterResult(
- address, handle, cmd_status, failed_contact_counter);
- }
-}
-
-void log_read_tx_power_level_result(const RawAddress& address, uint16_t handle,
- uint32_t cmd_status,
- int32_t transmit_power_level) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricReadTxPowerLevelResult(
- address, handle, cmd_status, transmit_power_level);
- } else {
- bluetooth::common::LogReadTxPowerLevelResult(address, handle, cmd_status,
- transmit_power_level);
- }
-}
-
-void log_socket_connection_state(
- const RawAddress& address, int port, int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes, int64_t rx_bytes, int uid, int server_port,
- android::bluetooth::SocketRoleEnum socket_role) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricSocketConnectionState(
- address, port, type, connection_state, tx_bytes, rx_bytes, uid,
- server_port, socket_role);
- } else {
- bluetooth::common::LogSocketConnectionState(
- address, port, type, connection_state, tx_bytes, rx_bytes, uid,
- server_port, socket_role);
- }
-}
-
-bool init_metric_id_allocator(
- const std::unordered_map<RawAddress, int>& paired_device_map,
- bluetooth::shim::CallbackLegacy save_device_callback,
- bluetooth::shim::CallbackLegacy forget_device_callback) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- return bluetooth::shim::InitMetricIdAllocator(
- paired_device_map, std::move(save_device_callback),
- std::move(forget_device_callback));
- }
- return bluetooth::common::MetricIdAllocator::GetInstance().Init(
- paired_device_map, std::move(save_device_callback),
- std::move(forget_device_callback));
-}
-
-bool close_metric_id_allocator() {
- if (bluetooth::shim::is_any_gd_enabled()) {
- return bluetooth::shim::CloseMetricIdAllocator();
- }
- return bluetooth::common::MetricIdAllocator::GetInstance().Close();
-}
-
-int allocate_metric_id_from_metric_id_allocator(const RawAddress& address) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- return bluetooth::shim::AllocateIdFromMetricIdAllocator(address);
- }
- return bluetooth::common::MetricIdAllocator::GetInstance().AllocateId(
- address);
-}
-
-int save_metric_id_from_metric_id_allocator(const RawAddress& address) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- return bluetooth::shim::SaveDeviceOnMetricIdAllocator(address);
- }
- return bluetooth::common::MetricIdAllocator::GetInstance().SaveDevice(
- address);
-}
-
-void forget_device_from_metric_id_allocator(const RawAddress& address) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::ForgetDeviceFromMetricIdAllocator(address);
- } else {
- bluetooth::common::MetricIdAllocator::GetInstance().ForgetDevice(address);
- }
-}
-
-bool is_valid_id_from_metric_id_allocator(const int id) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- return bluetooth::shim::IsValidIdFromMetricIdAllocator(id);
- }
- return bluetooth::common::MetricIdAllocator::IsValidId(id);
-}
diff --git a/btif/src/btif_pan.cc b/btif/src/btif_pan.cc
index 95144bbb0..fe10b4958 100644
--- a/btif/src/btif_pan.cc
+++ b/btif/src/btif_pan.cc
@@ -27,35 +27,60 @@
#define LOG_TAG "bt_btif_pan"
-#include <arpa/inet.h>
#include <base/bind.h>
-#include <base/location.h>
+#include <base/logging.h>
+#include <ctype.h>
+#include <errno.h>
#include <fcntl.h>
#include <linux/if_ether.h>
#include <linux/if_tun.h>
+#include <linux/sockios.h>
#include <net/if.h>
+#include <netdb.h>
+#include <netinet/in.h>
+#include <signal.h>
+#include <stdio.h>
+#include <string.h>
#include <sys/ioctl.h>
#include <sys/poll.h>
+#include <sys/prctl.h>
+#include <sys/select.h>
+#include <sys/socket.h>
+#include <sys/wait.h>
#include <unistd.h>
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_pan_api.h"
-#include "btif/include/btif_common.h"
-#include "btif/include/btif_pan_internal.h"
-#include "btif/include/btif_sock_thread.h"
+#include <hardware/bluetooth.h>
+#include <hardware/bt_pan.h>
+
+#include "bt_common.h"
+#include "bta_api.h"
+#include "bta_pan_api.h"
+#include "btif_common.h"
+#include "btif_pan_internal.h"
+#include "btif_sock_thread.h"
+#include "btif_sock_util.h"
+#include "btif_util.h"
+#include "btm_api.h"
#include "device/include/controller.h"
-#include "include/hardware/bt_pan.h"
#include "osi/include/log.h"
#include "osi/include/osi.h"
-#include "stack/include/btu.h" // do_in_main_thread
-#include "stack/include/pan_api.h"
+#include "stack/include/btu.h"
#define FORWARD_IGNORE 1
#define FORWARD_SUCCESS 0
#define FORWARD_FAILURE (-1)
#define FORWARD_CONGEST (-2)
+#if (PAN_NAP_DISABLED == TRUE && PANU_DISABLED == TRUE)
+#define BTPAN_LOCAL_ROLE BTPAN_ROLE_NONE
+#elif PAN_NAP_DISABLED == TRUE
+#define BTPAN_LOCAL_ROLE BTPAN_ROLE_PANU
+#elif PANU_DISABLED == TRUE
+#define BTPAN_LOCAL_ROLE BTPAN_ROLE_PANNAP
+#else
+#define BTPAN_LOCAL_ROLE (BTPAN_ROLE_PANU | BTPAN_ROLE_PANNAP)
+#endif
+
#define asrt(s) \
do { \
if (!(s)) \
@@ -85,7 +110,7 @@ static void bta_pan_callback(tBTA_PAN_EVT event, tBTA_PAN* p_data);
static void btu_exec_tap_fd_read(const int fd);
static btpan_interface_t pan_if = {
- sizeof(pan_if), btpan_jni_init, nullptr, btpan_get_local_role,
+ sizeof(pan_if), btpan_jni_init, btpan_enable, btpan_get_local_role,
btpan_connect, btpan_disconnect, btpan_jni_cleanup};
const btpan_interface_t* btif_pan_get_interface() { return &pan_if; }
@@ -113,15 +138,7 @@ void btif_pan_init() {
btpan_cleanup_conn(&btpan_cb.conns[i]);
BTA_PanEnable(bta_pan_callback);
btpan_cb.enabled = 1;
-
- int role = BTPAN_ROLE_NONE;
-#if PAN_NAP_DISABLED == FALSE
- role |= BTPAN_ROLE_PANNAP;
-#endif
-#if PANU_DISABLED == FALSE
- role |= BTPAN_ROLE_PANU;
-#endif
- btpan_enable(role);
+ btpan_enable(BTPAN_LOCAL_ROLE);
}
}
@@ -180,15 +197,16 @@ static inline int btpan_role_to_bta(int btpan_role) {
static volatile int btpan_dev_local_role;
#if (BTA_PAN_INCLUDED == TRUE)
-static tBTA_PAN_ROLE_INFO bta_panu_info = {PANU_SERVICE_NAME, 0};
-static tBTA_PAN_ROLE_INFO bta_pan_nap_info = {PAN_NAP_SERVICE_NAME, 1};
+static tBTA_PAN_ROLE_INFO bta_panu_info = {PANU_SERVICE_NAME, 0, PAN_SECURITY};
+static tBTA_PAN_ROLE_INFO bta_pan_nap_info = {PAN_NAP_SERVICE_NAME, 1,
+ PAN_SECURITY};
#endif
static bt_status_t btpan_enable(int local_role) {
#if (BTA_PAN_INCLUDED == TRUE)
BTIF_TRACE_DEBUG("%s - local_role: %d", __func__, local_role);
int bta_pan_role = btpan_role_to_bta(local_role);
- BTA_PanSetRole(bta_pan_role, &bta_panu_info, &bta_pan_nap_info);
+ BTA_PanSetRole(bta_pan_role, &bta_panu_info, NULL, &bta_pan_nap_info);
btpan_dev_local_role = local_role;
return BT_STATUS_SUCCESS;
#else
@@ -402,7 +420,8 @@ int btpan_tap_send(int tap_fd, const RawAddress& src, const RawAddress& dst,
char packet[TAP_MAX_PKT_WRITE_LEN + sizeof(tETH_HDR)];
memcpy(packet, &eth_hdr, sizeof(tETH_HDR));
if (len > TAP_MAX_PKT_WRITE_LEN) {
- LOG_ERROR("btpan_tap_send eth packet size:%d is exceeded limit!", len);
+ LOG_ERROR(LOG_TAG, "btpan_tap_send eth packet size:%d is exceeded limit!",
+ len);
return -1;
}
memcpy(packet + sizeof(tETH_HDR), buf, len);
@@ -597,7 +616,7 @@ static void bta_pan_callback_transfer(uint16_t event, char* p_param) {
bt_status_t status;
btpan_conn_t* conn = btpan_find_conn_handle(p_data->open.handle);
- LOG_VERBOSE("%s pan connection open status: %d", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s pan connection open status: %d", __func__,
p_data->open.status);
if (p_data->open.status == BTA_PAN_SUCCESS) {
state = BTPAN_STATE_CONNECTED;
@@ -619,7 +638,7 @@ static void bta_pan_callback_transfer(uint16_t event, char* p_param) {
break;
}
case BTA_PAN_CLOSE_EVT: {
- LOG_INFO("%s: event = BTA_PAN_CLOSE_EVT handle %d", __func__,
+ LOG_INFO(LOG_TAG, "%s: event = BTA_PAN_CLOSE_EVT handle %d", __func__,
p_data->close.handle);
btpan_conn_t* conn = btpan_find_conn_handle(p_data->close.handle);
btpan_close_conn(conn);
diff --git a/btif/src/btif_profile_queue.cc b/btif/src/btif_profile_queue.cc
index e4243500b..900a6af52 100644
--- a/btif/src/btif_profile_queue.cc
+++ b/btif/src/btif_profile_queue.cc
@@ -37,7 +37,6 @@
#include "bt_common.h"
#include "btif_common.h"
-#include "main/shim/dumpsys.h"
#include "stack_manager.h"
/*******************************************************************************
@@ -53,7 +52,7 @@ class ConnectNode {
std::string ToString() const {
return base::StringPrintf("address=%s UUID=%04X busy=%s",
- PRIVATE_ADDRESS(address_), uuid_,
+ address_.ToString().c_str(), uuid_,
(busy_) ? "true" : "false");
}
@@ -100,13 +99,14 @@ static void queue_int_add(uint16_t uuid, const RawAddress& bda,
ConnectNode param(bda, uuid, connect_cb);
for (const auto& node : connect_queue) {
if (node.uuid() == param.uuid() && node.address() == param.address()) {
- LOG_ERROR("Dropping duplicate profile connection request:%s",
- param.ToString().c_str());
+ LOG_ERROR(LOG_TAG, "%s: dropping duplicate connection request: %s",
+ __func__, param.ToString().c_str());
return;
}
}
- LOG_INFO("Queueing profile connection request:%s", param.ToString().c_str());
+ LOG_INFO(LOG_TAG, "%s: adding connection request: %s", __func__,
+ param.ToString().c_str());
connect_queue.push_back(param);
btif_queue_connect_next();
@@ -116,7 +116,7 @@ static void queue_int_advance() {
if (connect_queue.empty()) return;
const ConnectNode& head = connect_queue.front();
- LOG_INFO("%s: removing connection request: %s", __func__,
+ LOG_INFO(LOG_TAG, "%s: removing connection request: %s", __func__,
head.ToString().c_str());
connect_queue.pop_front();
@@ -124,13 +124,13 @@ static void queue_int_advance() {
}
static void queue_int_cleanup(uint16_t uuid) {
- LOG_INFO("%s: UUID=%04X", __func__, uuid);
+ LOG_INFO(LOG_TAG, "%s: UUID=%04X", __func__, uuid);
for (auto it = connect_queue.begin(); it != connect_queue.end();) {
auto it_prev = it++;
const ConnectNode& node = *it_prev;
if (node.uuid() == uuid) {
- LOG_INFO("%s: removing connection request: %s", __func__,
+ LOG_INFO(LOG_TAG, "%s: removing connection request: %s", __func__,
node.ToString().c_str());
connect_queue.erase(it_prev);
}
@@ -193,10 +193,12 @@ bt_status_t btif_queue_connect_next(void) {
ConnectNode& head = connect_queue.front();
- LOG_INFO("Executing profile connection request:%s", head.ToString().c_str());
+ LOG_INFO(LOG_TAG, "%s: executing connection request: %s", __func__,
+ head.ToString().c_str());
bt_status_t b_status = head.connect();
if (b_status != BT_STATUS_SUCCESS) {
- LOG_INFO("%s: connect %s failed, advance to next scheduled connection.",
+ LOG_INFO(LOG_TAG,
+ "%s: connect %s failed, advance to next scheduled connection.",
__func__, head.ToString().c_str());
btif_queue_advance();
}
@@ -213,7 +215,7 @@ bt_status_t btif_queue_connect_next(void) {
*
******************************************************************************/
void btif_queue_release() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
if (do_in_jni_thread(FROM_HERE, base::Bind(&queue_int_release)) !=
BT_STATUS_SUCCESS) {
LOG(FATAL) << __func__ << ": Failed to schedule on JNI thread";
diff --git a/btif/src/btif_rc.cc b/btif/src/btif_rc.cc
index c77ba6f55..9fc221e03 100644..100755
--- a/btif/src/btif_rc.cc
+++ b/btif/src/btif_rc.cc
@@ -46,11 +46,10 @@
#include "btif_util.h"
#include "btu.h"
#include "device/include/interop.h"
+#include "log/log.h"
#include "osi/include/list.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
#include "osi/include/properties.h"
-#include "stack/include/avrc_api.h"
#define RC_INVALID_TRACK_ID (0xFFFFFFFFFFFFFFFFULL)
@@ -168,19 +167,6 @@ typedef struct {
btrc_player_app_ext_attr_t ext_attrs[AVRC_MAX_APP_ATTR_SIZE];
} btif_rc_player_app_settings_t;
-typedef struct {
- bool in_use;
- uint8_t lbl;
- uint8_t handle;
- btif_rc_timer_context_t txn_timer_context;
- alarm_t* txn_timer;
-} rc_transaction_t;
-
-typedef struct {
- std::recursive_mutex lbllock;
- rc_transaction_t transaction[MAX_TRANSACTIONS_PER_SESSION];
-} rc_transaction_set_t;
-
/* TODO : Merge btif_rc_reg_notifications_t and btif_rc_cmd_ctxt_t to a single
* struct */
typedef struct {
@@ -202,7 +188,6 @@ typedef struct {
bool rc_features_processed;
uint64_t rc_playing_uid;
bool rc_procedure_complete;
- rc_transaction_set_t transaction_set;
} btif_rc_device_cb_t;
typedef struct {
@@ -211,12 +196,27 @@ typedef struct {
} rc_cb_t;
typedef struct {
+ bool in_use;
+ uint8_t lbl;
+ uint8_t handle;
+ btif_rc_timer_context_t txn_timer_context;
+ alarm_t* txn_timer;
+} rc_transaction_t;
+
+typedef struct {
+ std::recursive_mutex lbllock;
+ rc_transaction_t transaction[MAX_TRANSACTIONS_PER_SESSION];
+} rc_device_t;
+
+typedef struct {
uint8_t label;
RawAddress rc_addr;
} rc_context_t;
typedef struct { uint8_t handle; } btif_rc_handle_t;
+rc_device_t device;
+
static void sleep_ms(uint64_t timeout_ms);
/* Response status code - Unknown Error - this is changed to "reserved" */
@@ -251,7 +251,6 @@ static const uint8_t status_code_map[] = {
AVRC_STS_ADDR_PLAYER_CHG, /* BTRC_STS_ADDR_PLAY_CHGD */
};
-void initialize_device(btif_rc_device_cb_t* p_dev);
static void send_reject_response(uint8_t rc_handle, uint8_t label, uint8_t pdu,
uint8_t status, uint8_t opcode);
static uint8_t opcode_from_pdu(uint8_t pdu);
@@ -259,12 +258,11 @@ static void send_metamsg_rsp(btif_rc_device_cb_t* p_dev, int index,
uint8_t label, tBTA_AV_CODE code,
tAVRC_RESPONSE* pmetamsg_resp);
static void register_volumechange(uint8_t label, btif_rc_device_cb_t* p_dev);
-static void init_all_transactions(btif_rc_device_cb_t* p_dev);
-static bt_status_t get_transaction(btif_rc_device_cb_t* p_dev,
- rc_transaction_t** ptransaction);
-static void release_transaction(btif_rc_device_cb_t* p_dev, uint8_t label);
-static rc_transaction_t* get_transaction_by_lbl(btif_rc_device_cb_t* p_dev,
- uint8_t label);
+static void lbl_init();
+static void init_all_transactions();
+static bt_status_t get_transaction(rc_transaction_t** ptransaction);
+static void release_transaction(uint8_t label);
+static rc_transaction_t* get_transaction_by_lbl(uint8_t label);
static void handle_rc_metamsg_rsp(tBTA_AV_META_MSG* pmeta_msg,
btif_rc_device_cb_t* p_dev);
@@ -398,41 +396,6 @@ static btif_rc_device_cb_t* alloc_device() {
return NULL;
}
-void initialize_device(btif_rc_device_cb_t* p_dev) {
- if (p_dev == nullptr) return;
-
- p_dev->rc_connected = false;
- p_dev->br_connected = false;
- p_dev->rc_handle = 0;
- p_dev->rc_features = 0;
- p_dev->rc_cover_art_psm = 0;
- p_dev->rc_state = BTRC_CONNECTION_STATE_DISCONNECTED;
- p_dev->rc_addr = RawAddress::kEmpty;
- p_dev->rc_pending_play = false;
- for (int i = 0; i < MAX_CMD_QUEUE_LEN; ++i) {
- p_dev->rc_pdu_info[i].ctype = 0;
- p_dev->rc_pdu_info[i].label = 0;
- p_dev->rc_pdu_info[i].is_rsp_pending = false;
- }
- if (p_dev->rc_supported_event_list != nullptr) {
- list_clear(p_dev->rc_supported_event_list);
- }
- p_dev->rc_supported_event_list = nullptr;
- p_dev->rc_volume = MAX_VOLUME;
- p_dev->rc_vol_label = MAX_LABEL;
- memset(&p_dev->rc_app_settings, 0, sizeof(btif_rc_player_app_settings_t));
- p_dev->rc_play_status_timer = nullptr;
- p_dev->rc_features_processed = false;
- p_dev->rc_playing_uid = 0;
- p_dev->rc_procedure_complete = false;
-
- // Leaving the value of the default constructor for the lbllock mutex is fine
- // but we still need to clear out the transaction label set
- memset(&p_dev->transaction_set.transaction, 0,
- sizeof(p_dev->transaction_set.transaction));
- init_all_transactions(p_dev);
-}
-
static btif_rc_device_cb_t* get_connected_device(int index) {
BTIF_TRACE_DEBUG("%s: index: %d", __func__, index);
if (index > BTIF_RC_NUM_CONN) {
@@ -448,6 +411,19 @@ static btif_rc_device_cb_t* get_connected_device(int index) {
return (&btif_rc_cb.rc_multi_cb[index]);
}
+static int get_num_connected_devices() {
+ int connected_devices = 0;
+ for (int idx = 0; idx < BTIF_RC_NUM_CONN; idx++) {
+ if (btif_rc_cb.rc_multi_cb[idx].rc_state ==
+ BTRC_CONNECTION_STATE_CONNECTED) {
+ connected_devices++;
+ }
+ }
+ BTIF_TRACE_DEBUG("%s: returning connected_devices: %d", __func__,
+ connected_devices);
+ return connected_devices;
+}
+
btif_rc_device_cb_t* btif_rc_get_device_by_bda(const RawAddress& bd_addr) {
VLOG(1) << __func__ << ": bd_addr: " << bd_addr;
@@ -620,16 +596,16 @@ void handle_rc_features(btif_rc_device_cb_t* p_dev) {
rc_transaction_t* p_transaction = NULL;
bt_status_t status = BT_STATUS_NOT_READY;
if (MAX_LABEL == p_dev->rc_vol_label) {
- status = get_transaction(p_dev, &p_transaction);
+ status = get_transaction(&p_transaction);
} else {
- p_transaction = get_transaction_by_lbl(p_dev, p_dev->rc_vol_label);
+ p_transaction = get_transaction_by_lbl(p_dev->rc_vol_label);
if (NULL != p_transaction) {
BTIF_TRACE_DEBUG(
"%s: register_volumechange already in progress for label: %d",
__func__, p_dev->rc_vol_label);
return;
}
- status = get_transaction(p_dev, &p_transaction);
+ status = get_transaction(&p_transaction);
}
if (BT_STATUS_SUCCESS == status && NULL != p_transaction) {
p_dev->rc_vol_label = p_transaction->lbl;
@@ -690,7 +666,6 @@ void handle_rc_connect(tBTA_AV_RC_OPEN* p_rc_open) {
BTIF_TRACE_ERROR("%s: Connect failed with error code: %d", __func__,
p_rc_open->status);
p_dev->rc_connected = false;
- return;
}
// check if already some RC is connected
@@ -761,17 +736,43 @@ void handle_rc_disconnect(tBTA_AV_RC_CLOSE* p_rc_close) {
BTIF_TRACE_ERROR("Got disconnect of unknown device");
return;
}
-
- /* Report connection state if device is AVRCP target */
+ /* report connection state if device is AVRCP target */
if (bt_rc_ctrl_callbacks != NULL) {
do_in_jni_thread(
FROM_HERE, base::Bind(bt_rc_ctrl_callbacks->connection_state_cb, false,
false, p_dev->rc_addr));
}
+ /* Clean up AVRCP procedure flags */
+ memset(&p_dev->rc_app_settings, 0, sizeof(btif_rc_player_app_settings_t));
+ p_dev->rc_features_processed = false;
+ p_dev->rc_procedure_complete = false;
+ /* Check and clear the notification event list */
+ if (p_dev->rc_supported_event_list != NULL) {
+ list_clear(p_dev->rc_supported_event_list);
+ p_dev->rc_supported_event_list = NULL;
+ }
+
+ /* check if there is another device connected */
+ if (p_dev->rc_state == BTRC_CONNECTION_STATE_CONNECTED) {
+ p_dev->rc_handle = 0;
+ p_dev->rc_connected = false;
+ p_dev->rc_state = BTRC_CONNECTION_STATE_DISCONNECTED;
+
+ memset(p_dev->rc_notif, 0, sizeof(p_dev->rc_notif));
+
+ p_dev->rc_features = 0;
+ p_dev->rc_cover_art_psm = 0;
+ p_dev->rc_vol_label = MAX_LABEL;
+ p_dev->rc_volume = MAX_VOLUME;
+
+ p_dev->rc_addr = RawAddress::kEmpty;
+ }
+ if (get_num_connected_devices() == 0) {
+ BTIF_TRACE_DEBUG("%s: Closing all handles", __func__);
+ init_all_transactions();
+ }
- // We'll re-initialize the device state back to what it looked like before
- // the connection
- initialize_device(p_dev);
+ p_dev->rc_addr = RawAddress::kEmpty;
}
/***************************************************************************
@@ -864,7 +865,7 @@ void handle_rc_passthrough_rsp(tBTA_AV_REMOTE_RSP* p_remote_rsp) {
BTIF_TRACE_DEBUG("%s: rc_id: %d state: %s", __func__, p_remote_rsp->rc_id,
status);
- release_transaction(p_dev, p_remote_rsp->label);
+ release_transaction(p_remote_rsp->label);
if (bt_rc_ctrl_callbacks != NULL) {
do_in_jni_thread(
FROM_HERE,
@@ -911,7 +912,7 @@ void handle_rc_vendorunique_rsp(tBTA_AV_REMOTE_RSP* p_remote_rsp) {
BTIF_TRACE_DEBUG("%s: vendor_id: %d status: %s", __func__, vendor_id,
status);
- release_transaction(p_dev, p_remote_rsp->label);
+ release_transaction(p_remote_rsp->label);
do_in_jni_thread(FROM_HERE,
base::Bind(bt_rc_ctrl_callbacks->groupnavigation_rsp_cb,
vendor_id, key_state));
@@ -970,7 +971,7 @@ void handle_rc_metamsg_cmd(tBTA_AV_META_MSG* pmeta_msg) {
if (pmeta_msg->code >= AVRC_RSP_NOT_IMPL) {
{
rc_transaction_t* transaction = NULL;
- transaction = get_transaction_by_lbl(p_dev, pmeta_msg->label);
+ transaction = get_transaction_by_lbl(pmeta_msg->label);
if (transaction != NULL) {
handle_rc_metamsg_rsp(pmeta_msg, p_dev);
} else {
@@ -1440,7 +1441,7 @@ static uint8_t opcode_from_pdu(uint8_t pdu) {
*
***************************************************************************/
static uint8_t fill_attribute_id_array(
- uint8_t cmd_attribute_number, const uint32_t* cmd_attribute_id_array,
+ uint8_t cmd_attribute_number, btrc_media_attr_t* cmd_attribute_id_array,
size_t out_array_size, btrc_media_attr_t* out_attribute_id_array) {
/* Default case for cmd_attribute_number == 0xFF, No attribute */
uint8_t out_attribute_number = 0;
@@ -1515,7 +1516,8 @@ static void btif_rc_upstreams_evt(uint16_t event, tAVRC_COMMAND* pavrc_cmd,
case AVRC_PDU_GET_ELEMENT_ATTR: {
btrc_media_attr_t element_attrs[BTRC_MAX_ELEM_ATTR_SIZE] = {};
uint8_t num_attr = fill_attribute_id_array(
- pavrc_cmd->get_elem_attrs.num_attr, pavrc_cmd->get_elem_attrs.attrs,
+ pavrc_cmd->get_elem_attrs.num_attr,
+ (btrc_media_attr_t*)pavrc_cmd->get_elem_attrs.attrs,
BTRC_MAX_ELEM_ATTR_SIZE, element_attrs);
if (num_attr == 0) {
BTIF_TRACE_ERROR(
@@ -1652,7 +1654,8 @@ static void btif_rc_upstreams_evt(uint16_t event, tAVRC_COMMAND* pavrc_cmd,
case AVRC_PDU_GET_ITEM_ATTRIBUTES: {
btrc_media_attr_t item_attrs[BTRC_MAX_ELEM_ATTR_SIZE] = {};
uint8_t num_attr = fill_attribute_id_array(
- pavrc_cmd->get_attrs.attr_count, pavrc_cmd->get_attrs.p_attr_list,
+ pavrc_cmd->get_attrs.attr_count,
+ (btrc_media_attr_t*)pavrc_cmd->get_attrs.p_attr_list,
BTRC_MAX_ELEM_ATTR_SIZE, item_attrs);
if (num_attr == 0) {
BTIF_TRACE_ERROR(
@@ -1793,8 +1796,13 @@ static bt_status_t init(btrc_callbacks_t* callbacks) {
bt_rc_callbacks = callbacks;
for (int idx = 0; idx < BTIF_RC_NUM_CONN; idx++) {
- initialize_device(&btif_rc_cb.rc_multi_cb[idx]);
+ memset(&btif_rc_cb.rc_multi_cb[idx], 0,
+ sizeof(btif_rc_cb.rc_multi_cb[idx]));
+ btif_rc_cb.rc_multi_cb[idx].rc_vol_label = MAX_LABEL;
+ btif_rc_cb.rc_multi_cb[idx].rc_volume = MAX_VOLUME;
+ btif_rc_cb.rc_multi_cb[idx].rc_state = BTRC_CONNECTION_STATE_DISCONNECTED;
}
+ lbl_init();
return result;
}
@@ -1816,8 +1824,13 @@ static bt_status_t init_ctrl(btrc_ctrl_callbacks_t* callbacks) {
bt_rc_ctrl_callbacks = callbacks;
for (int idx = 0; idx < BTIF_RC_NUM_CONN; idx++) {
- initialize_device(&btif_rc_cb.rc_multi_cb[idx]);
+ memset(&btif_rc_cb.rc_multi_cb[idx], 0,
+ sizeof(btif_rc_cb.rc_multi_cb[idx]));
+ btif_rc_cb.rc_multi_cb[idx].rc_vol_label = MAX_LABEL;
+ btif_rc_cb.rc_multi_cb[idx].rc_volume = MAX_VOLUME;
+ btif_rc_cb.rc_multi_cb[idx].rc_features_processed = FALSE;
}
+ lbl_init();
return result;
}
@@ -2579,28 +2592,27 @@ static bt_status_t set_volume(uint8_t volume) {
tAVRC_STS status = BT_STATUS_UNSUPPORTED;
for (int idx = 0; idx < BTIF_RC_NUM_CONN; idx++) {
- btif_rc_device_cb_t* p_dev = &btif_rc_cb.rc_multi_cb[idx];
- if (!p_dev->rc_connected) continue;
+ if (!btif_rc_cb.rc_multi_cb[idx].rc_connected) continue;
- if (p_dev->rc_volume == volume) {
+ if (btif_rc_cb.rc_multi_cb[idx].rc_volume == volume) {
status = BT_STATUS_DONE;
BTIF_TRACE_ERROR("%s: volume value already set earlier: 0x%02x", __func__,
volume);
continue;
}
- if ((p_dev->rc_volume == volume) ||
- p_dev->rc_state !=
+ if ((btif_rc_cb.rc_multi_cb[idx].rc_volume == volume) ||
+ btif_rc_cb.rc_multi_cb[idx].rc_state !=
BTRC_CONNECTION_STATE_CONNECTED) {
continue;
}
- if ((p_dev->rc_features & BTA_AV_FEAT_RCTG) == 0) {
+ if ((btif_rc_cb.rc_multi_cb[idx].rc_features & BTA_AV_FEAT_RCTG) == 0) {
status = BT_STATUS_NOT_READY;
continue;
}
- if (!(p_dev->rc_features & BTA_AV_FEAT_ADV_CTRL))
+ if (!(btif_rc_cb.rc_multi_cb[idx].rc_features & BTA_AV_FEAT_ADV_CTRL))
continue;
BTIF_TRACE_DEBUG("%s: Peer supports absolute volume. newVolume: %d",
@@ -2621,7 +2633,7 @@ static bt_status_t set_volume(uint8_t volume) {
}
rc_transaction_t* p_transaction = NULL;
- bt_status_t tran_status = get_transaction(p_dev, &p_transaction);
+ bt_status_t tran_status = get_transaction(&p_transaction);
if (tran_status != BT_STATUS_SUCCESS || !p_transaction) {
osi_free_and_reset((void**)&p_msg);
@@ -2634,7 +2646,8 @@ static bt_status_t set_volume(uint8_t volume) {
BTIF_TRACE_DEBUG("%s: msgreq being sent out with label: %d", __func__,
p_transaction->lbl);
- BTA_AvMetaCmd(p_dev->rc_handle, p_transaction->lbl, AVRC_CMD_CTRL, p_msg);
+ BTA_AvMetaCmd(btif_rc_cb.rc_multi_cb[idx].rc_handle, p_transaction->lbl,
+ AVRC_CMD_CTRL, p_msg);
status = BT_STATUS_SUCCESS;
}
return (bt_status_t)status;
@@ -2666,7 +2679,7 @@ static void register_volumechange(uint8_t lbl, btif_rc_device_cb_t* p_dev) {
BldResp = AVRC_BldCommand(&avrc_cmd, &p_msg);
if (AVRC_STS_NO_ERROR == BldResp && p_msg) {
- p_transaction = get_transaction_by_lbl(p_dev, lbl);
+ p_transaction = get_transaction_by_lbl(lbl);
if (p_transaction != NULL) {
BTA_AvMetaCmd(p_dev->rc_handle, p_transaction->lbl, AVRC_CMD_NOTIF,
p_msg);
@@ -2715,9 +2728,9 @@ static void handle_rc_metamsg_rsp(tBTA_AV_META_MSG* pmeta_msg,
AVRC_EVT_VOLUME_CHANGE == avrc_response.reg_notif.event_id &&
p_dev->rc_vol_label == pmeta_msg->label) {
p_dev->rc_vol_label = MAX_LABEL;
- release_transaction(p_dev, p_dev->rc_vol_label);
+ release_transaction(p_dev->rc_vol_label);
} else if (AVRC_PDU_SET_ABSOLUTE_VOLUME == avrc_response.rsp.pdu) {
- release_transaction(p_dev, pmeta_msg->label);
+ release_transaction(pmeta_msg->label);
}
return;
}
@@ -2758,7 +2771,7 @@ static void handle_rc_metamsg_rsp(tBTA_AV_META_MSG* pmeta_msg,
register_volumechange(p_dev->rc_vol_label, p_dev);
} else if (AVRC_PDU_SET_ABSOLUTE_VOLUME == avrc_response.rsp.pdu) {
/* free up the label here */
- release_transaction(p_dev, pmeta_msg->label);
+ release_transaction(pmeta_msg->label);
}
BTIF_TRACE_EVENT("%s: Passing received metamsg response to app. pdu: %s",
@@ -2826,12 +2839,6 @@ bool iterate_supported_event_list_for_timeout(void* data, void* cb_data) {
**************************************************************************/
static void rc_notification_interim_timout(uint8_t label,
btif_rc_device_cb_t* p_dev) {
- /* Device disconnections clear the event list but can't free the timer */
- if (p_dev == NULL || p_dev->rc_supported_event_list) {
- BTIF_TRACE_WARNING("%s: timeout for null device or event list", __func__);
- return;
- }
-
list_node_t* node;
rc_context_t cntxt;
memset(&cntxt, 0, sizeof(rc_context_t));
@@ -2928,7 +2935,7 @@ static void btif_rc_status_cmd_timeout_handler(UNUSED_ATTR uint16_t event,
handle_get_playstatus_response(&meta_msg, &avrc_response.get_play_status);
break;
}
- release_transaction(p_dev, p_context->rc_status_cmd.label);
+ release_transaction(p_context->rc_status_cmd.label);
}
/***************************************************************************
@@ -2976,7 +2983,7 @@ static void btif_rc_control_cmd_timeout_handler(UNUSED_ATTR uint16_t event,
handle_set_app_attr_val_response(&meta_msg, &avrc_response.set_app_val);
break;
}
- release_transaction(p_dev, p_context->rc_control_cmd.label);
+ release_transaction(p_context->rc_control_cmd.label);
}
/***************************************************************************
@@ -3009,7 +3016,7 @@ static void btif_rc_control_cmd_timer_timeout(void* data) {
static void register_for_event_notification(btif_rc_supported_event_t* p_event,
btif_rc_device_cb_t* p_dev) {
rc_transaction_t* p_transaction = NULL;
- bt_status_t status = get_transaction(p_dev, &p_transaction);
+ bt_status_t status = get_transaction(&p_transaction);
if (status != BT_STATUS_SUCCESS) {
BTIF_TRACE_ERROR("%s: no more transaction labels: %d", __func__, status);
return;
@@ -3024,7 +3031,7 @@ static void register_for_event_notification(btif_rc_supported_event_t* p_event,
if (status != BT_STATUS_SUCCESS) {
BTIF_TRACE_ERROR("%s: Error in Notification registration: %d", __func__,
status);
- release_transaction(p_dev, p_transaction->lbl);
+ release_transaction(p_transaction->lbl);
return;
}
@@ -3071,7 +3078,7 @@ bt_status_t build_and_send_vendor_cmd(tAVRC_COMMAND* avrc_cmd,
tBTA_AV_CODE cmd_code,
btif_rc_device_cb_t* p_dev) {
rc_transaction_t* p_transaction = NULL;
- bt_status_t tran_status = get_transaction(p_dev, &p_transaction);
+ bt_status_t tran_status = get_transaction(&p_transaction);
if (BT_STATUS_SUCCESS != tran_status) return BT_STATUS_FAIL;
BT_HDR* p_msg = NULL;
@@ -3119,7 +3126,7 @@ static bt_status_t build_and_send_browsing_cmd(tAVRC_COMMAND* avrc_cmd,
}
rc_transaction_t* p_transaction = NULL;
- bt_status_t tran_status = get_transaction(p_dev, &p_transaction);
+ bt_status_t tran_status = get_transaction(&p_transaction);
if (tran_status != BT_STATUS_SUCCESS || p_transaction == NULL) {
osi_free(p_msg);
@@ -4258,11 +4265,6 @@ static void handle_change_path_response(tBTA_AV_META_MSG* pmeta_msg,
btif_rc_device_cb_t* p_dev =
btif_rc_get_device_by_handle(pmeta_msg->rc_handle);
- if (p_dev == NULL) {
- BTIF_TRACE_ERROR("%s: Invalid rc handle", __func__);
- return;
- }
-
if (p_rsp->status == AVRC_STS_NO_ERROR) {
do_in_jni_thread(FROM_HERE,
base::Bind(bt_rc_ctrl_callbacks->change_folder_path_cb,
@@ -4287,11 +4289,6 @@ static void handle_set_browsed_player_response(tBTA_AV_META_MSG* pmeta_msg,
btif_rc_device_cb_t* p_dev =
btif_rc_get_device_by_handle(pmeta_msg->rc_handle);
- if (p_dev == NULL) {
- BTIF_TRACE_ERROR("%s: Invalid rc handle", __func__);
- return;
- }
-
if (p_rsp->status == AVRC_STS_NO_ERROR) {
do_in_jni_thread(
FROM_HERE,
@@ -4310,10 +4307,10 @@ static void handle_set_browsed_player_response(tBTA_AV_META_MSG* pmeta_msg,
* Returns None
*
**************************************************************************/
-static void clear_cmd_timeout(btif_rc_device_cb_t* p_dev, uint8_t label) {
+static void clear_cmd_timeout(uint8_t label) {
rc_transaction_t* p_txn;
- p_txn = get_transaction_by_lbl(p_dev, label);
+ p_txn = get_transaction_by_lbl(label);
if (p_txn == NULL) {
BTIF_TRACE_ERROR("%s: Error in transaction label lookup", __func__);
return;
@@ -4336,12 +4333,10 @@ static void handle_avk_rc_metamsg_rsp(tBTA_AV_META_MSG* pmeta_msg) {
uint8_t scratch_buf[512] = {0}; // this variable is unused
uint16_t buf_len;
tAVRC_STS status;
- btif_rc_device_cb_t* p_dev = NULL;
BTIF_TRACE_DEBUG("%s: opcode: %d rsp_code: %d ", __func__,
pmeta_msg->p_msg->hdr.opcode, pmeta_msg->code);
- p_dev = btif_rc_get_device_by_handle(pmeta_msg->rc_handle);
status = AVRC_Ctrl_ParsResponse(pmeta_msg->p_msg, &avrc_response, scratch_buf,
&buf_len);
if ((AVRC_OP_VENDOR == pmeta_msg->p_msg->hdr.opcode) &&
@@ -4356,7 +4351,7 @@ static void handle_avk_rc_metamsg_rsp(tBTA_AV_META_MSG* pmeta_msg) {
handle_notification_response(pmeta_msg, &avrc_response.reg_notif);
if (pmeta_msg->code == AVRC_RSP_INTERIM) {
/* Don't free the transaction Id */
- clear_cmd_timeout(p_dev, pmeta_msg->label);
+ clear_cmd_timeout(pmeta_msg->label);
return;
}
break;
@@ -4430,8 +4425,8 @@ static void handle_avk_rc_metamsg_rsp(tBTA_AV_META_MSG* pmeta_msg) {
__func__, pmeta_msg->code, pmeta_msg->len);
return;
}
- BTIF_TRACE_DEBUG("%s: release transaction %d", __func__, pmeta_msg->label);
- release_transaction(p_dev, pmeta_msg->label);
+ BTIF_TRACE_DEBUG("XX __func__ release transaction %d", pmeta_msg->label);
+ release_transaction(pmeta_msg->label);
}
/***************************************************************************
@@ -4955,7 +4950,8 @@ static bt_status_t play_item_cmd(const RawAddress& bd_addr, uint8_t scope,
memcpy(avrc_cmd.play_item.uid, uid, AVRC_UID_SIZE);
avrc_cmd.play_item.uid_counter = uid_counter;
- return build_and_send_vendor_cmd(&avrc_cmd, AVRC_CMD_CTRL, p_dev);
+ return build_and_send_browsing_cmd(&avrc_cmd, p_dev);
+ // return build_and_send_vendor_cmd(&avrc_cmd, AVRC_CMD_CTRL, p_dev);
}
/***************************************************************************
@@ -5239,7 +5235,7 @@ static bt_status_t send_groupnavigation_cmd(const RawAddress& bd_addr,
CHECK_RC_CONNECTED(p_dev);
if (p_dev->rc_features & BTA_AV_FEAT_RCTG) {
- bt_status_t tran_status = get_transaction(p_dev, &p_transaction);
+ bt_status_t tran_status = get_transaction(&p_transaction);
if ((BT_STATUS_SUCCESS == tran_status) && (NULL != p_transaction)) {
uint8_t buffer[AVRC_PASS_THRU_GROUP_LEN] = {0};
uint8_t* start = buffer;
@@ -5285,7 +5281,7 @@ static bt_status_t send_passthrough_cmd(const RawAddress& bd_addr,
BTIF_TRACE_DEBUG("%s: key-code: %d, key-state: %d", __func__, key_code,
key_state);
if (p_dev->rc_features & BTA_AV_FEAT_RCTG) {
- bt_status_t tran_status = get_transaction(p_dev, &p_transaction);
+ bt_status_t tran_status = get_transaction(&p_transaction);
if (BT_STATUS_SUCCESS == tran_status && NULL != p_transaction) {
BTA_AvRemoteCmd(p_dev->rc_handle, p_transaction->lbl,
(tBTA_AV_RC)key_code, (tBTA_AV_STATE)key_state);
@@ -5383,21 +5379,31 @@ const btrc_ctrl_interface_t* btif_rc_ctrl_get_interface(void) {
*
* Returns void
******************************************************************************/
-static void initialize_transaction(btif_rc_device_cb_t* p_dev, int lbl) {
- if (p_dev == nullptr) return;
- rc_transaction_set_t* transaction_set = &(p_dev->transaction_set);
- std::unique_lock<std::recursive_mutex> lock(transaction_set->lbllock);
+static void initialize_transaction(int lbl) {
+ std::unique_lock<std::recursive_mutex> lock(device.lbllock);
if (lbl < MAX_TRANSACTIONS_PER_SESSION) {
- if (alarm_is_scheduled(transaction_set->transaction[lbl].txn_timer)) {
- clear_cmd_timeout(p_dev, lbl);
+ if (alarm_is_scheduled(device.transaction[lbl].txn_timer)) {
+ clear_cmd_timeout(lbl);
}
- transaction_set->transaction[lbl].lbl = lbl;
- transaction_set->transaction[lbl].in_use = false;
- transaction_set->transaction[lbl].handle = 0;
+ device.transaction[lbl].lbl = lbl;
+ device.transaction[lbl].in_use = false;
+ device.transaction[lbl].handle = 0;
}
}
/*******************************************************************************
+ * Function lbl_init
+ *
+ * Description Initializes label structures and mutexes.
+ *
+ * Returns void
+ ******************************************************************************/
+void lbl_init() {
+ memset(&device.transaction, 0, sizeof(device.transaction));
+ init_all_transactions();
+}
+
+/*******************************************************************************
*
* Function init_all_transactions
*
@@ -5405,10 +5411,10 @@ static void initialize_transaction(btif_rc_device_cb_t* p_dev, int lbl) {
*
* Returns void
******************************************************************************/
-void init_all_transactions(btif_rc_device_cb_t* p_dev) {
- if (p_dev == nullptr) return;
- for (auto i = 0; i < MAX_TRANSACTIONS_PER_SESSION; ++i) {
- initialize_transaction(p_dev, i);
+void init_all_transactions() {
+ uint8_t txn_indx = 0;
+ for (txn_indx = 0; txn_indx < MAX_TRANSACTIONS_PER_SESSION; txn_indx++) {
+ initialize_transaction(txn_indx);
}
}
@@ -5421,22 +5427,20 @@ void init_all_transactions(btif_rc_device_cb_t* p_dev) {
*
* Returns bt_status_t
******************************************************************************/
-rc_transaction_t* get_transaction_by_lbl(btif_rc_device_cb_t* p_dev,
- uint8_t lbl) {
- if (p_dev == nullptr) return nullptr;
-
+rc_transaction_t* get_transaction_by_lbl(uint8_t lbl) {
rc_transaction_t* transaction = NULL;
- rc_transaction_set_t* transaction_set = &(p_dev->transaction_set);
- std::unique_lock<std::recursive_mutex> lock(transaction_set->lbllock);
+ std::unique_lock<std::recursive_mutex> lock(device.lbllock);
/* Determine if this is a valid label */
if (lbl < MAX_TRANSACTIONS_PER_SESSION) {
- if (!transaction_set->transaction[lbl].in_use) {
+ if (!device.transaction[lbl].in_use) {
transaction = NULL;
} else {
- transaction = &(transaction_set->transaction[lbl]);
+ transaction = &(device.transaction[lbl]);
+ BTIF_TRACE_DEBUG("%s: Got transaction.label: %d", __func__, lbl);
}
}
+
return transaction;
}
@@ -5448,24 +5452,20 @@ rc_transaction_t* get_transaction_by_lbl(btif_rc_device_cb_t* p_dev,
*
* Returns bt_status_t
******************************************************************************/
-static bt_status_t get_transaction(btif_rc_device_cb_t* p_dev,
- rc_transaction_t** ptransaction) {
- if (p_dev == NULL) return BT_STATUS_FAIL;
- rc_transaction_set_t* transaction_set = &(p_dev->transaction_set);
- std::unique_lock<std::recursive_mutex> lock(transaction_set->lbllock);
- // Check for unused transactions in the device's transaction set
+static bt_status_t get_transaction(rc_transaction_t** ptransaction) {
+ std::unique_lock<std::recursive_mutex> lock(device.lbllock);
+
+ // Check for unused transactions
for (uint8_t i = 0; i < MAX_TRANSACTIONS_PER_SESSION; i++) {
- if (!transaction_set->transaction[i].in_use) {
- BTIF_TRACE_DEBUG("%s: p_dev=%s, label=%d, got free transaction!",
- __func__, p_dev->rc_addr.ToString().c_str(), i);
- transaction_set->transaction[i].in_use = true;
- *ptransaction = &(transaction_set->transaction[i]);
+ if (!device.transaction[i].in_use) {
+ BTIF_TRACE_DEBUG("%s: Got transaction.label: %d", __func__,
+ device.transaction[i].lbl);
+ device.transaction[i].in_use = true;
+ *ptransaction = &(device.transaction[i]);
return BT_STATUS_SUCCESS;
}
}
- BTIF_TRACE_ERROR("%s: p_dev=%s, failed to find free transaction", __func__,
- p_dev->rc_addr.ToString().c_str());
return BT_STATUS_NOMEM;
}
@@ -5477,15 +5477,14 @@ static bt_status_t get_transaction(btif_rc_device_cb_t* p_dev,
*
* Returns bt_status_t
******************************************************************************/
-void release_transaction(btif_rc_device_cb_t* p_dev, uint8_t lbl) {
- BTIF_TRACE_DEBUG("%s: p_dev=%s, label=%d", __func__,
- p_dev == NULL ? "null" : p_dev->rc_addr.ToString().c_str(),
- lbl);
- rc_transaction_t* transaction = get_transaction_by_lbl(p_dev, lbl);
+void release_transaction(uint8_t lbl) {
+ BTIF_TRACE_DEBUG("%s %d", __func__, lbl);
+ rc_transaction_t* transaction = get_transaction_by_lbl(lbl);
/* If the transaction is in use... */
if (transaction != NULL) {
- initialize_transaction(p_dev, lbl);
+ BTIF_TRACE_DEBUG("%s: lbl: %d", __func__, lbl);
+ initialize_transaction(lbl);
}
}
diff --git a/btif/src/btif_sdp_server.cc b/btif/src/btif_sdp_server.cc
index 08f307d9d..ef1b02f4d 100644
--- a/btif/src/btif_sdp_server.cc
+++ b/btif/src/btif_sdp_server.cc
@@ -28,6 +28,7 @@
#define LOG_TAG "bt_btif_sdp_server"
+#include <log/log.h>
#include <pthread.h>
#include <stdlib.h>
#include <string.h>
@@ -267,6 +268,7 @@ static const sdp_slot_t* start_create_sdp(int id) {
static void set_sdp_handle(int id, int handle) {
std::unique_lock<std::recursive_mutex> lock(sdp_lock);
sdp_slots[id].sdp_handle = handle;
+ BTIF_TRACE_DEBUG("%s() id=%d to handle=0x%08x", __func__, id, handle);
}
bt_status_t create_sdp_record(bluetooth_sdp_record* record,
@@ -379,9 +381,17 @@ static int add_maps_sdp(const bluetooth_sdp_mas_record* rec) {
uint8_t temp[4];
uint8_t* p_temp = temp;
+ APPL_TRACE_DEBUG(
+ "%s(): MASID = 0x%02x, scn 0x%02x, psm = 0x%04x\n service name %s",
+ __func__, rec->mas_instance_id, rec->hdr.rfcomm_channel_number,
+ rec->hdr.l2cap_psm, rec->hdr.service_name);
+
+ APPL_TRACE_DEBUG(" msg_types: 0x%02x, feature_bits: 0x%08x",
+ rec->supported_message_types, rec->supported_features);
+
sdp_handle = SDP_CreateRecord();
if (sdp_handle == 0) {
- LOG_ERROR("Unable to register MAPS Service");
+ APPL_TRACE_ERROR("%s() - Unable to register MAPS Service", __func__);
return sdp_handle;
}
@@ -459,9 +469,16 @@ static int add_mapc_sdp(const bluetooth_sdp_mns_record* rec) {
uint8_t temp[4];
uint8_t* p_temp = temp;
+ APPL_TRACE_DEBUG("%s(): scn 0x%02x, psm = 0x%04x\n service name %s",
+ __func__, rec->hdr.rfcomm_channel_number, rec->hdr.l2cap_psm,
+ rec->hdr.service_name);
+
+ APPL_TRACE_DEBUG(" feature_bits: 0x%08x", rec->supported_features);
+
sdp_handle = SDP_CreateRecord();
if (sdp_handle == 0) {
- LOG_ERROR("Unable to register MAP Notification Service");
+ APPL_TRACE_ERROR("%s(): Unable to register MAP Notification Service",
+ __func__);
return sdp_handle;
}
@@ -526,9 +543,10 @@ static int add_pbapc_sdp(const bluetooth_sdp_pce_record* rec) {
bool status = true;
uint32_t sdp_handle = 0;
+ APPL_TRACE_DEBUG("%s(): service name %s", __func__, rec->hdr.service_name);
sdp_handle = SDP_CreateRecord();
if (sdp_handle == 0) {
- LOG_ERROR("Unable to register PBAP Client Service");
+ APPL_TRACE_ERROR("%s(): Unable to register PBAP Client Service", __func__);
return sdp_handle;
}
@@ -541,8 +559,8 @@ static int add_pbapc_sdp(const bluetooth_sdp_pce_record* rec) {
(uint8_t*)rec->hdr.service_name);
/* Add in the Bluetooth Profile Descriptor List */
- status &= SDP_AddProfileDescriptorList(
- sdp_handle, UUID_SERVCLASS_PHONE_ACCESS, rec->hdr.profile_version);
+ status &= SDP_AddProfileDescriptorList(sdp_handle, service,
+ rec->hdr.profile_version);
/* Make the service browseable */
status &=
@@ -571,9 +589,16 @@ static int add_pbaps_sdp(const bluetooth_sdp_pse_record* rec) {
uint8_t temp[4];
uint8_t* p_temp = temp;
+ APPL_TRACE_DEBUG("%s(): scn 0x%02x, psm = 0x%04x\n service name %s",
+ __func__, rec->hdr.rfcomm_channel_number, rec->hdr.l2cap_psm,
+ rec->hdr.service_name);
+
+ APPL_TRACE_DEBUG(" supported_repositories: 0x%08x, feature_bits: 0x%08x",
+ rec->supported_repositories, rec->supported_features);
+
sdp_handle = SDP_CreateRecord();
if (sdp_handle == 0) {
- LOG_ERROR("Unable to register PBAP Server Service");
+ APPL_TRACE_ERROR("%s(): Unable to register PBAP Server Service", __func__);
return sdp_handle;
}
@@ -651,9 +676,17 @@ static int add_opps_sdp(const bluetooth_sdp_ops_record* rec) {
tBTA_UTL_COD cod;
int i, j;
+ APPL_TRACE_DEBUG("%s(): scn 0x%02x, psm = 0x%04x\n service name %s",
+ __func__, rec->hdr.rfcomm_channel_number, rec->hdr.l2cap_psm,
+ rec->hdr.service_name);
+
+ APPL_TRACE_DEBUG(" supported formats count: %d",
+ rec->supported_formats_list_len);
+
sdp_handle = SDP_CreateRecord();
if (sdp_handle == 0) {
- LOG_ERROR("Unable to register Object Push Server Service");
+ APPL_TRACE_ERROR("%s(): Unable to register Object Push Server Service",
+ __func__);
return sdp_handle;
}
@@ -730,9 +763,12 @@ static int add_saps_sdp(const bluetooth_sdp_sap_record* rec) {
bool status = true;
uint32_t sdp_handle = 0;
+ APPL_TRACE_DEBUG("%s(): scn 0x%02x, service name %s", __func__,
+ rec->hdr.rfcomm_channel_number, rec->hdr.service_name);
+
sdp_handle = SDP_CreateRecord();
if (sdp_handle == 0) {
- LOG_ERROR("Unable to register SAPS Service");
+ APPL_TRACE_ERROR("%s(): Unable to register SAPS Service", __func__);
return sdp_handle;
}
diff --git a/btif/src/btif_sock.cc b/btif/src/btif_sock.cc
index e6a03f2da..ba701270e 100644
--- a/btif/src/btif_sock.cc
+++ b/btif/src/btif_sock.cc
@@ -29,7 +29,6 @@
#include "bta_api.h"
#include "btif_common.h"
#include "btif_config.h"
-#include "btif_metrics_logging.h"
#include "btif_sock_l2cap.h"
#include "btif_sock_rfc.h"
#include "btif_sock_sco.h"
@@ -37,6 +36,7 @@
#include "btif_sock_thread.h"
#include "btif_uid.h"
#include "btif_util.h"
+#include "common/metrics.h"
#include "device/include/controller.h"
#include "osi/include/thread.h"
@@ -74,32 +74,35 @@ bt_status_t btif_sock_init(uid_set_t* uid_set) {
btsock_thread_init();
thread_handle = btsock_thread_create(btsock_signaled, NULL);
if (thread_handle == -1) {
- LOG_ERROR("%s unable to create btsock_thread.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to create btsock_thread.", __func__);
goto error;
}
status = btsock_rfc_init(thread_handle, uid_set);
if (status != BT_STATUS_SUCCESS) {
- LOG_ERROR("%s error initializing RFCOMM sockets: %d", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s error initializing RFCOMM sockets: %d", __func__,
+ status);
goto error;
}
status = btsock_l2cap_init(thread_handle, uid_set);
if (status != BT_STATUS_SUCCESS) {
- LOG_ERROR("%s error initializing L2CAP sockets: %d", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s error initializing L2CAP sockets: %d", __func__,
+ status);
goto error;
}
thread = thread_new("btif_sock");
if (!thread) {
- LOG_ERROR("%s error creating new thread.", __func__);
+ LOG_ERROR(LOG_TAG, "%s error creating new thread.", __func__);
btsock_rfc_cleanup();
goto error;
}
status = btsock_sco_init(thread);
if (status != BT_STATUS_SUCCESS) {
- LOG_ERROR("%s error initializing SCO sockets: %d", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s error initializing SCO sockets: %d", __func__,
+ status);
btsock_rfc_cleanup();
goto error;
}
@@ -138,11 +141,11 @@ static bt_status_t btsock_listen(btsock_type_t type, const char* service_name,
bt_status_t status = BT_STATUS_FAIL;
int original_channel = channel;
- log_socket_connection_state(RawAddress::kEmpty, 0, type,
- android::bluetooth::SocketConnectionstateEnum::
- SOCKET_CONNECTION_STATE_LISTENING,
- 0, 0, app_uid, channel,
- android::bluetooth::SOCKET_ROLE_LISTEN);
+ bluetooth::common::LogSocketConnectionState(
+ RawAddress::kEmpty, 0, type,
+ android::bluetooth::SocketConnectionstateEnum::
+ SOCKET_CONNECTION_STATE_LISTENING,
+ 0, 0, app_uid, channel, android::bluetooth::SOCKET_ROLE_LISTEN);
switch (type) {
case BTSOCK_RFCOMM:
status = btsock_rfc_listen(service_name, service_uuid, channel, sock_fd,
@@ -157,13 +160,13 @@ static bt_status_t btsock_listen(btsock_type_t type, const char* service_name,
/* Set channel to zero so that it will be assigned */
channel = 0;
} else if (channel <= 0) {
- LOG_ERROR("%s: type BTSOCK_L2CAP_LE: invalid channel=%d", __func__,
- channel);
+ LOG_ERROR(LOG_TAG, "%s: type BTSOCK_L2CAP_LE: invalid channel=%d",
+ __func__, channel);
break;
}
flags |= BTSOCK_FLAG_LE_COC;
- LOG_INFO(
-
+ LOG_DEBUG(
+ LOG_TAG,
"%s: type=BTSOCK_L2CAP_LE, channel=0x%x, original=0x%x, flags=0x%x",
__func__, channel, original_channel, flags);
status =
@@ -174,16 +177,17 @@ static bt_status_t btsock_listen(btsock_type_t type, const char* service_name,
break;
default:
- LOG_ERROR("%s unknown/unsupported socket type: %d", __func__, type);
+ LOG_ERROR(LOG_TAG, "%s unknown/unsupported socket type: %d", __func__,
+ type);
status = BT_STATUS_UNSUPPORTED;
break;
}
if (status != BT_STATUS_SUCCESS) {
- log_socket_connection_state(RawAddress::kEmpty, 0, type,
- android::bluetooth::SocketConnectionstateEnum::
- SOCKET_CONNECTION_STATE_DISCONNECTED,
- 0, 0, app_uid, channel,
- android::bluetooth::SOCKET_ROLE_LISTEN);
+ bluetooth::common::LogSocketConnectionState(
+ RawAddress::kEmpty, 0, type,
+ android::bluetooth::SocketConnectionstateEnum::
+ SOCKET_CONNECTION_STATE_DISCONNECTED,
+ 0, 0, app_uid, channel, android::bluetooth::SOCKET_ROLE_LISTEN);
}
return status;
}
@@ -197,11 +201,11 @@ static bt_status_t btsock_connect(const RawAddress* bd_addr, btsock_type_t type,
*sock_fd = INVALID_FD;
bt_status_t status = BT_STATUS_FAIL;
- log_socket_connection_state(*bd_addr, 0, type,
- android::bluetooth::SocketConnectionstateEnum::
- SOCKET_CONNECTION_STATE_CONNECTING,
- 0, 0, app_uid, channel,
- android::bluetooth::SOCKET_ROLE_CONNECTION);
+ bluetooth::common::LogSocketConnectionState(
+ *bd_addr, 0, type,
+ android::bluetooth::SocketConnectionstateEnum::
+ SOCKET_CONNECTION_STATE_CONNECTING,
+ 0, 0, app_uid, channel, android::bluetooth::SOCKET_ROLE_CONNECTION);
switch (type) {
case BTSOCK_RFCOMM:
status =
@@ -216,7 +220,7 @@ static bt_status_t btsock_connect(const RawAddress* bd_addr, btsock_type_t type,
flags |= BTSOCK_FLAG_LE_COC;
// Ensure device is in inquiry database
- tBLE_ADDR_TYPE addr_type = BLE_ADDR_PUBLIC;
+ int addr_type = 0;
int device_type = 0;
if (btif_get_address_type(*bd_addr, &addr_type) &&
@@ -225,8 +229,8 @@ static bt_status_t btsock_connect(const RawAddress* bd_addr, btsock_type_t type,
BTA_DmAddBleDevice(*bd_addr, addr_type, device_type);
}
- LOG_INFO("%s: type=BTSOCK_L2CAP_LE, channel=0x%x, flags=0x%x", __func__,
- channel, flags);
+ LOG_DEBUG(LOG_TAG, "%s: type=BTSOCK_L2CAP_LE, channel=0x%x, flags=0x%x",
+ __func__, channel, flags);
status = btsock_l2cap_connect(bd_addr, channel, sock_fd, flags, app_uid);
break;
}
@@ -236,22 +240,28 @@ static bt_status_t btsock_connect(const RawAddress* bd_addr, btsock_type_t type,
break;
default:
- LOG_ERROR("%s unknown/unsupported socket type: %d", __func__, type);
+ LOG_ERROR(LOG_TAG, "%s unknown/unsupported socket type: %d", __func__,
+ type);
status = BT_STATUS_UNSUPPORTED;
break;
}
if (status != BT_STATUS_SUCCESS) {
- log_socket_connection_state(*bd_addr, 0, type,
- android::bluetooth::SocketConnectionstateEnum::
- SOCKET_CONNECTION_STATE_DISCONNECTED,
- 0, 0, app_uid, channel,
- android::bluetooth::SOCKET_ROLE_CONNECTION);
+ bluetooth::common::LogSocketConnectionState(
+ *bd_addr, 0, type,
+ android::bluetooth::SocketConnectionstateEnum::
+ SOCKET_CONNECTION_STATE_DISCONNECTED,
+ 0, 0, app_uid, channel, android::bluetooth::SOCKET_ROLE_CONNECTION);
}
return status;
}
static void btsock_request_max_tx_data_length(const RawAddress& remote_device) {
- BTA_DmBleRequestMaxTxDataLength(remote_device);
+ const controller_t* controller = controller_get_interface();
+ uint16_t max_len = controller->get_ble_maximum_tx_data_length();
+
+ DVLOG(2) << __func__ << ": max_len=" << max_len;
+
+ BTA_DmBleSetDataLength(remote_device, max_len);
}
static void btsock_signaled(int fd, int type, int flags, uint32_t user_id) {
diff --git a/btif/src/btif_sock_l2cap.cc b/btif/src/btif_sock_l2cap.cc
index a5a9857db..8def2af38 100644
--- a/btif/src/btif_sock_l2cap.cc
+++ b/btif/src/btif_sock_l2cap.cc
@@ -15,24 +15,45 @@
* limitations under the License.
*/
+#include "btif_sock_l2cap.h"
+
+#include <base/logging.h>
+#include <errno.h>
+#include <stdlib.h>
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <sys/types.h>
-#include <cstdint>
-#include <cstring>
-
-#include "bta/include/bta_jv_api.h"
-#include "btif/include/btif_metrics_logging.h"
-#include "btif/include/btif_sock_thread.h"
-#include "btif/include/btif_sock_util.h"
-#include "btif/include/btif_uid.h"
-#include "include/hardware/bluetooth.h"
-#include "internal_include/bt_target.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "stack/btm/security_device_record.h"
-#include "stack/include/bt_types.h"
-#include "types/raw_address.h"
+#include <unistd.h>
+#include <vector>
+
+#include <mutex>
+
+#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
+#include <hardware/bt_sock.h>
+
+#include "osi/include/allocator.h"
+
+#include "bt_common.h"
+#include "bt_target.h"
+#include "bta_api.h"
+#include "bta_jv_api.h"
+#include "bta_jv_co.h"
+#include "btif_common.h"
+#include "btif_sock_sdp.h"
+#include "btif_sock_thread.h"
+#include "btif_sock_util.h"
+#include "btif_uid.h"
+#include "btif_util.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
+#include "common/metrics.h"
+#include "hcimsgs.h"
+#include "l2c_api.h"
+#include "l2c_int.h"
+#include "l2cdefs.h"
+#include "port_api.h"
+#include "sdp_api.h"
struct packet {
struct packet *next, *prev;
@@ -49,7 +70,7 @@ typedef struct l2cap_socket {
int app_uid; // The UID of the app who requested this socket
int handle; // handle from lower layers
unsigned security; // security flags
- int channel; // PSM
+ int channel; // channel (fixed_chan) or PSM (!fixed_chan)
int our_fd; // fd from our side
int app_fd; // fd from app's side
@@ -57,6 +78,7 @@ typedef struct l2cap_socket {
struct packet* first_packet; // fist packet to be delivered to app
struct packet* last_packet; // last packet to be delivered to app
+ unsigned fixed_chan : 1; // fixed channel (or psm?)
unsigned server : 1; // is a server? (or connecting?)
unsigned connected : 1; // is connected?
unsigned outgoing_congest : 1; // should we hold?
@@ -159,8 +181,7 @@ static char packet_put_head_l(l2cap_socket* sock, const void* data,
static char packet_put_tail_l(l2cap_socket* sock, const void* data,
uint32_t len) {
if (sock->bytes_buffered >= L2CAP_MAX_RX_BUFFER) {
- LOG_ERROR("Unable to add to buffer due to buffer overflow socket_id:%u",
- sock->id);
+ LOG(ERROR) << __func__ << ": buffer overflow";
return false;
}
@@ -202,7 +223,7 @@ static void btsock_l2cap_free_l(l2cap_socket* sock) {
return;
// Whenever a socket is freed, the connection must be dropped
- log_socket_connection_state(
+ bluetooth::common::LogSocketConnectionState(
sock->addr, sock->id, sock->is_le_coc ? BTSOCK_L2CAP_LE : BTSOCK_L2CAP,
android::bluetooth::SOCKET_CONNECTION_STATE_DISCONNECTED, sock->tx_bytes,
sock->rx_bytes, sock->app_uid, sock->channel,
@@ -221,8 +242,7 @@ static void btsock_l2cap_free_l(l2cap_socket* sock) {
if (sock->app_fd != -1) {
close(sock->app_fd);
} else {
- LOG_INFO("Application has already closed l2cap socket socket_id:%u",
- sock->id);
+ LOG(ERROR) << "SOCK_LIST: free(id = " << sock->id << ") - NO app_fd!";
}
while (packet_get_head_l(sock, &buf, NULL)) osi_free(buf);
@@ -235,21 +255,35 @@ static void btsock_l2cap_free_l(l2cap_socket* sock) {
}
if ((sock->channel >= 0) && (sock->server)) {
BTA_JvFreeChannel(sock->channel, BTA_JV_CONN_TYPE_L2CAP_LE);
- LOG_INFO("Stopped L2CAP LE COC server socket_id:%u channel:%u", sock->id,
- sock->channel);
- BTA_JvL2capStopServer(sock->channel, sock->id);
+ if (!sock->fixed_chan) {
+ VLOG(2) << __func__ << ": stopping L2CAP LE COC server channel "
+ << sock->channel;
+ BTA_JvL2capStopServer(sock->channel, sock->id);
+ }
}
} else {
// Only call if we are non server connections
if ((sock->handle >= 0) && (!sock->server)) {
- BTA_JvL2capClose(sock->handle);
+ if (sock->fixed_chan)
+ BTA_JvL2capCloseLE(sock->handle);
+ else
+ BTA_JvL2capClose(sock->handle);
}
if ((sock->channel >= 0) && (sock->server)) {
- BTA_JvFreeChannel(sock->channel, BTA_JV_CONN_TYPE_L2CAP);
- BTA_JvL2capStopServer(sock->channel, sock->id);
+ if (sock->fixed_chan)
+ BTA_JvFreeChannel(sock->channel, BTA_JV_CONN_TYPE_L2CAP_LE);
+ else
+ BTA_JvFreeChannel(sock->channel, BTA_JV_CONN_TYPE_L2CAP);
+
+ if (!sock->fixed_chan) {
+ DVLOG(2) << __func__ << ": stopping L2CAP server channel "
+ << sock->channel;
+ BTA_JvL2capStopServer(sock->channel, sock->id);
+ }
}
}
+ DVLOG(2) << __func__ << ": free id:" << sock->id;
osi_free(sock);
}
@@ -270,7 +304,7 @@ static l2cap_socket* btsock_l2cap_alloc_l(const char* name,
security |= BTM_SEC_IN_MIN_16_DIGIT_PIN;
if (socketpair(AF_LOCAL, SOCK_SEQPACKET, 0, fds)) {
- LOG_ERROR("socketpair failed:%s", strerror(errno));
+ LOG(ERROR) << "socketpair failed, errno:" << errno;
goto fail_sockpair;
}
@@ -313,7 +347,7 @@ static l2cap_socket* btsock_l2cap_alloc_l(const char* name,
sock->id++;
}
last_sock_id = sock->id;
- LOG_INFO("Allocated l2cap socket structure socket_id:%u", sock->id);
+ DVLOG(2) << __func__ << " SOCK_LIST: alloc id:" << sock->id;
return sock;
fail_sockpair:
@@ -322,6 +356,7 @@ fail_sockpair:
}
bt_status_t btsock_l2cap_init(int handle, uid_set_t* set) {
+ DVLOG(2) << __func__ << ": handle: " << handle;
std::unique_lock<std::mutex> lock(state_lock);
pth = handle;
socks = NULL;
@@ -337,8 +372,7 @@ bt_status_t btsock_l2cap_cleanup() {
}
static inline bool send_app_psm_or_chan_l(l2cap_socket* sock) {
- LOG_INFO("Sending l2cap socket socket_id:%u channel:%d", sock->id,
- sock->channel);
+ DVLOG(2) << __func__ << ": channel: " << sock->channel;
return sock_send_all(sock->our_fd, (const uint8_t*)&sock->channel,
sizeof(sock->channel)) == sizeof(sock->channel);
}
@@ -357,11 +391,12 @@ static bool send_app_connect_signal(int fd, const RawAddress* addr, int channel,
if (sock_send_fd(fd, (const uint8_t*)&cs, sizeof(cs), send_fd) ==
sizeof(cs))
return true;
+ else
+ LOG(ERROR) << "sock_send_fd failed, fd: " << fd
+ << ", send_fd:" << send_fd;
} else if (sock_send_all(fd, (const uint8_t*)&cs, sizeof(cs)) == sizeof(cs)) {
return true;
}
-
- LOG_ERROR("Unable to send data to socket fd:%d send_fd:%d", fd, send_fd);
return false;
}
@@ -371,20 +406,20 @@ static void on_srv_l2cap_listen_started(tBTA_JV_L2CAP_START* p_start,
std::unique_lock<std::mutex> lock(state_lock);
sock = btsock_l2cap_find_by_id_l(id);
- if (!sock) {
- LOG_ERROR("Unable to find l2cap socket with socket_id:%u", id);
- return;
- }
+ if (!sock) return;
if (p_start->status != BTA_JV_SUCCESS) {
- LOG_ERROR("Unable to start l2cap server socket_id:%u", sock->id);
+ LOG(ERROR) << "Error starting l2cap_listen - status: "
+ << loghex(p_start->status);
btsock_l2cap_free_l(sock);
return;
}
sock->handle = p_start->handle;
+ DVLOG(2) << __func__ << ": sock->handle: " << sock->handle
+ << ", id: " << sock->id;
- log_socket_connection_state(
+ bluetooth::common::LogSocketConnectionState(
sock->addr, sock->id, sock->is_le_coc ? BTSOCK_L2CAP_LE : BTSOCK_L2CAP,
android::bluetooth::SocketConnectionstateEnum::
SOCKET_CONNECTION_STATE_LISTENING,
@@ -395,7 +430,7 @@ static void on_srv_l2cap_listen_started(tBTA_JV_L2CAP_START* p_start,
if (!sock->server_psm_sent) {
if (!send_app_psm_or_chan_l(sock)) {
// closed
- LOG_INFO("Unable to send socket to application socket_id:%u", sock->id);
+ DVLOG(2) << "send_app_psm() failed, close rs->id: " << sock->id;
btsock_l2cap_free_l(sock);
} else {
sock->server_psm_sent = true;
@@ -408,13 +443,9 @@ static void on_cl_l2cap_init(tBTA_JV_L2CAP_CL_INIT* p_init, uint32_t id) {
std::unique_lock<std::mutex> lock(state_lock);
sock = btsock_l2cap_find_by_id_l(id);
- if (!sock) {
- LOG_ERROR("Unable to find l2cap socket with socket_id:%u", id);
- return;
- }
+ if (!sock) return;
if (p_init->status != BTA_JV_SUCCESS) {
- LOG_ERROR("Initialization status failed socket_id:%u", id);
btsock_l2cap_free_l(sock);
return;
}
@@ -433,6 +464,7 @@ static void on_srv_l2cap_psm_connect_l(tBTA_JV_L2CAP_OPEN* p_open,
btsock_l2cap_alloc_l(sock->name, &p_open->rem_bda, false, 0);
accept_rs->connected = true;
accept_rs->security = sock->security;
+ accept_rs->fixed_chan = sock->fixed_chan;
accept_rs->channel = sock->channel;
accept_rs->handle = sock->handle;
accept_rs->app_uid = sock->app_uid;
@@ -447,7 +479,7 @@ static void on_srv_l2cap_psm_connect_l(tBTA_JV_L2CAP_OPEN* p_open,
accept_rs->id = sock->id;
sock->id = new_listen_id;
- log_socket_connection_state(
+ bluetooth::common::LogSocketConnectionState(
accept_rs->addr, accept_rs->id,
accept_rs->is_le_coc ? BTSOCK_L2CAP_LE : BTSOCK_L2CAP,
android::bluetooth::SOCKET_CONNECTION_STATE_CONNECTED, 0, 0,
@@ -460,6 +492,9 @@ static void on_srv_l2cap_psm_connect_l(tBTA_JV_L2CAP_OPEN* p_open,
SOCK_THREAD_FD_EXCEPTION, sock->id);
btsock_thread_add_fd(pth, accept_rs->our_fd, BTSOCK_L2CAP, SOCK_THREAD_FD_RD,
accept_rs->id);
+ DVLOG(2) << "sending connect signal & app fd: " << accept_rs->app_fd
+ << " to app server to accept() the connection";
+ DVLOG(2) << "server fd: << " << sock->our_fd << ", scn:" << sock->channel;
send_app_connect_signal(sock->our_fd, &accept_rs->addr, sock->channel, 0,
accept_rs->app_fd, sock->rx_mtu, p_open->tx_mtu);
accept_rs->app_fd =
@@ -469,25 +504,99 @@ static void on_srv_l2cap_psm_connect_l(tBTA_JV_L2CAP_OPEN* p_open,
btsock_l2cap_server_listen(sock);
}
+static void on_srv_l2cap_le_connect_l(tBTA_JV_L2CAP_LE_OPEN* p_open,
+ l2cap_socket* sock) {
+ // std::mutex locked by caller
+ l2cap_socket* accept_rs =
+ btsock_l2cap_alloc_l(sock->name, &p_open->rem_bda, false, 0);
+ if (!accept_rs) return;
+
+ // swap IDs
+ uint32_t new_listen_id = accept_rs->id;
+ accept_rs->id = sock->id;
+ sock->id = new_listen_id;
+
+ accept_rs->handle = p_open->handle;
+ accept_rs->connected = true;
+ accept_rs->security = sock->security;
+ accept_rs->fixed_chan = sock->fixed_chan;
+ accept_rs->channel = sock->channel;
+ accept_rs->app_uid = sock->app_uid;
+ accept_rs->tx_mtu = sock->tx_mtu = p_open->tx_mtu;
+
+ // if we do not set a callback, this socket will be dropped */
+ *(p_open->p_p_cback) = (void*)btsock_l2cap_cbk;
+ *(p_open->p_user_data) = UINT_TO_PTR(accept_rs->id);
+
+ bluetooth::common::LogSocketConnectionState(
+ accept_rs->addr, accept_rs->id,
+ accept_rs->is_le_coc ? BTSOCK_L2CAP_LE : BTSOCK_L2CAP,
+ android::bluetooth::SOCKET_CONNECTION_STATE_CONNECTED, 0, 0,
+ accept_rs->app_uid, accept_rs->channel,
+ accept_rs->server ? android::bluetooth::SOCKET_ROLE_LISTEN
+ : android::bluetooth::SOCKET_ROLE_CONNECTION);
+
+ // start monitor the socket
+ btsock_thread_add_fd(pth, sock->our_fd, BTSOCK_L2CAP,
+ SOCK_THREAD_FD_EXCEPTION, sock->id);
+ btsock_thread_add_fd(pth, accept_rs->our_fd, BTSOCK_L2CAP, SOCK_THREAD_FD_RD,
+ accept_rs->id);
+ DVLOG(2) << "sending connect signal & app fd: " << accept_rs->app_fd
+ << " to app server to accept() the connection";
+ DVLOG(2) << "server fd: << " << sock->our_fd << ", scn:" << sock->channel;
+ send_app_connect_signal(sock->our_fd, &accept_rs->addr, sock->channel, 0,
+ accept_rs->app_fd, sock->rx_mtu, p_open->tx_mtu);
+ accept_rs->app_fd = -1; // the fd is closed after sent to app
+}
+
static void on_cl_l2cap_psm_connect_l(tBTA_JV_L2CAP_OPEN* p_open,
l2cap_socket* sock) {
sock->addr = p_open->rem_bda;
sock->tx_mtu = p_open->tx_mtu;
if (!send_app_psm_or_chan_l(sock)) {
- LOG_ERROR("Unable to send l2cap socket to application socket_id:%u",
- sock->id);
+ LOG(ERROR) << "send_app_psm_or_chan_l failed";
+ return;
+ }
+
+ if (!send_app_connect_signal(sock->our_fd, &sock->addr, sock->channel, 0, -1,
+ sock->rx_mtu, p_open->tx_mtu)) {
+ LOG(ERROR) << "send_app_connect_signal failed";
+ return;
+ }
+
+ bluetooth::common::LogSocketConnectionState(
+ sock->addr, sock->id, sock->is_le_coc ? BTSOCK_L2CAP_LE : BTSOCK_L2CAP,
+ android::bluetooth::SOCKET_CONNECTION_STATE_CONNECTED, 0, 0,
+ sock->app_uid, sock->channel,
+ sock->server ? android::bluetooth::SOCKET_ROLE_LISTEN
+ : android::bluetooth::SOCKET_ROLE_CONNECTION);
+
+ // start monitoring the socketpair to get call back when app writing data
+ DVLOG(2) << " connect signal sent, slot id: " << sock->id
+ << ", chan: " << sock->channel << ", server: " << sock->server;
+ btsock_thread_add_fd(pth, sock->our_fd, BTSOCK_L2CAP, SOCK_THREAD_FD_RD,
+ sock->id);
+ sock->connected = true;
+}
+
+static void on_cl_l2cap_le_connect_l(tBTA_JV_L2CAP_LE_OPEN* p_open,
+ l2cap_socket* sock) {
+ sock->addr = p_open->rem_bda;
+ sock->tx_mtu = p_open->tx_mtu;
+
+ if (!send_app_psm_or_chan_l(sock)) {
+ LOG(ERROR) << "send_app_psm_or_chan_l failed";
return;
}
if (!send_app_connect_signal(sock->our_fd, &sock->addr, sock->channel, 0, -1,
sock->rx_mtu, p_open->tx_mtu)) {
- LOG_ERROR("Unable to connect l2cap socket to application socket_id:%u",
- sock->id);
+ LOG(ERROR) << "send_app_connect_signal failed";
return;
}
- log_socket_connection_state(
+ bluetooth::common::LogSocketConnectionState(
sock->addr, sock->id, sock->is_le_coc ? BTSOCK_L2CAP_LE : BTSOCK_L2CAP,
android::bluetooth::SOCKET_CONNECTION_STATE_CONNECTED, 0, 0,
sock->app_uid, sock->channel,
@@ -495,9 +604,10 @@ static void on_cl_l2cap_psm_connect_l(tBTA_JV_L2CAP_OPEN* p_open,
: android::bluetooth::SOCKET_ROLE_CONNECTION);
// start monitoring the socketpair to get call back when app writing data
+ DVLOG(2) << " connect signal sent, slot id: " << sock->id
+ << ", chan: " << sock->channel << ", server: " << sock->server;
btsock_thread_add_fd(pth, sock->our_fd, BTSOCK_L2CAP, SOCK_THREAD_FD_RD,
sock->id);
- LOG_INFO("Connected l2cap socket socket_id:%u", sock->id);
sock->connected = true;
}
@@ -509,20 +619,24 @@ static void on_l2cap_connect(tBTA_JV* p_data, uint32_t id) {
std::unique_lock<std::mutex> lock(state_lock);
sock = btsock_l2cap_find_by_id_l(id);
if (!sock) {
- LOG_ERROR("Unable to find l2cap socket with socket_id:%u", id);
+ LOG(ERROR) << __func__ << ": unknown socket";
return;
}
sock->tx_mtu = le_open->tx_mtu;
- if (psm_open->status == BTA_JV_SUCCESS) {
+ if (sock->fixed_chan && le_open->status == BTA_JV_SUCCESS) {
+ if (!sock->server) {
+ on_cl_l2cap_le_connect_l(le_open, sock);
+ } else {
+ on_srv_l2cap_le_connect_l(le_open, sock);
+ }
+ } else if (!sock->fixed_chan && psm_open->status == BTA_JV_SUCCESS) {
if (!sock->server) {
on_cl_l2cap_psm_connect_l(psm_open, sock);
} else {
on_srv_l2cap_psm_connect_l(psm_open, sock);
}
} else {
- LOG_ERROR("Unable to open socket after receiving connection socket_id:%u",
- sock->id);
btsock_l2cap_free_l(sock);
}
}
@@ -532,23 +646,21 @@ static void on_l2cap_close(tBTA_JV_L2CAP_CLOSE* p_close, uint32_t id) {
std::unique_lock<std::mutex> lock(state_lock);
sock = btsock_l2cap_find_by_id_l(id);
- if (!sock) {
- LOG_INFO(
- "Unable to find probably already closed l2cap socket with socket_id:%u",
- id);
- return;
- }
+ if (!sock) return;
- log_socket_connection_state(
+ bluetooth::common::LogSocketConnectionState(
sock->addr, sock->id, sock->is_le_coc ? BTSOCK_L2CAP_LE : BTSOCK_L2CAP,
android::bluetooth::SOCKET_CONNECTION_STATE_DISCONNECTING, 0, 0,
sock->app_uid, sock->channel,
sock->server ? android::bluetooth::SOCKET_ROLE_LISTEN
: android::bluetooth::SOCKET_ROLE_CONNECTION);
+ DVLOG(2) << __func__ << ": slot id: " << sock->id << ", fd: " << sock->our_fd
+ << (sock->fixed_chan ? ", fixed_chan:" : ", PSM: ") << sock->channel
+ << ", server:" << sock->server;
// TODO: This does not seem to be called...
// I'm not sure if this will be called for non-server sockets?
- if (sock->server) {
+ if (!sock->fixed_chan && (sock->server)) {
BTA_JvFreeChannel(sock->channel, BTA_JV_CONN_TYPE_L2CAP);
}
btsock_l2cap_free_l(sock);
@@ -559,16 +671,12 @@ static void on_l2cap_outgoing_congest(tBTA_JV_L2CAP_CONG* p, uint32_t id) {
std::unique_lock<std::mutex> lock(state_lock);
sock = btsock_l2cap_find_by_id_l(id);
- if (!sock) {
- LOG_ERROR("Unable to find l2cap socket with socket_id:%u", id);
- return;
- }
+ if (!sock) return;
sock->outgoing_congest = p->cong ? 1 : 0;
-
+ // mointer the fd for any outgoing data
if (!sock->outgoing_congest) {
- LOG_VERBOSE("Monitoring l2cap socket for outgoing data socket_id:%u",
- sock->id);
+ DVLOG(2) << __func__ << ": adding fd to btsock_thread...";
btsock_thread_add_fd(pth, sock->our_fd, BTSOCK_L2CAP, SOCK_THREAD_FD_RD,
sock->id);
}
@@ -577,17 +685,14 @@ static void on_l2cap_outgoing_congest(tBTA_JV_L2CAP_CONG* p, uint32_t id) {
static void on_l2cap_write_done(uint16_t len, uint32_t id) {
std::unique_lock<std::mutex> lock(state_lock);
l2cap_socket* sock = btsock_l2cap_find_by_id_l(id);
- if (!sock) {
- LOG_ERROR("Unable to find l2cap socket with socket_id:%u", id);
- return;
- }
+ if (!sock) return;
int app_uid = sock->app_uid;
if (!sock->outgoing_congest) {
+ // monitor the fd for any outgoing data
+ DVLOG(2) << __func__ << ": adding fd to btsock_thread...";
btsock_thread_add_fd(pth, sock->our_fd, BTSOCK_L2CAP, SOCK_THREAD_FD_RD,
sock->id);
- } else {
- LOG_INFO("Socket congestion on socket_id:%u", sock->id);
}
sock->tx_bytes += len;
@@ -602,29 +707,46 @@ static void on_l2cap_data_ind(tBTA_JV* evt, uint32_t id) {
std::unique_lock<std::mutex> lock(state_lock);
sock = btsock_l2cap_find_by_id_l(id);
- if (!sock) {
- LOG_ERROR("Unable to find l2cap socket with socket_id:%u", id);
- return;
- }
+ if (!sock) return;
app_uid = sock->app_uid;
- uint32_t count;
-
- if (BTA_JvL2capReady(sock->handle, &count) == BTA_JV_SUCCESS) {
- std::vector<uint8_t> buffer(count);
- if (BTA_JvL2capRead(sock->handle, sock->id, buffer.data(), count) ==
- BTA_JV_SUCCESS) {
- if (packet_put_tail_l(sock, buffer.data(), count)) {
- bytes_read = count;
- btsock_thread_add_fd(pth, sock->our_fd, BTSOCK_L2CAP, SOCK_THREAD_FD_WR,
- sock->id);
- } else { // connection must be dropped
- LOG_WARN("Closing socket as unable to push data to socket socket_id:%u",
- sock->id);
- BTA_JvL2capClose(sock->handle);
- btsock_l2cap_free_l(sock);
- return;
+ if (sock->fixed_chan) { /* we do these differently */
+
+ tBTA_JV_LE_DATA_IND* p_le_data_ind = &evt->le_data_ind;
+ BT_HDR* p_buf = p_le_data_ind->p_buf;
+ uint8_t* data = (uint8_t*)(p_buf + 1) + p_buf->offset;
+
+ if (packet_put_tail_l(sock, data, p_buf->len)) {
+ bytes_read = p_buf->len;
+ btsock_thread_add_fd(pth, sock->our_fd, BTSOCK_L2CAP, SOCK_THREAD_FD_WR,
+ sock->id);
+ } else { // connection must be dropped
+ DVLOG(2) << __func__
+ << ": unable to push data to socket - closing fixed channel";
+ BTA_JvL2capCloseLE(sock->handle);
+ btsock_l2cap_free_l(sock);
+ return;
+ }
+
+ } else {
+ uint32_t count;
+
+ if (BTA_JvL2capReady(sock->handle, &count) == BTA_JV_SUCCESS) {
+ std::vector<uint8_t> buffer(count);
+ if (BTA_JvL2capRead(sock->handle, sock->id, buffer.data(), count) ==
+ BTA_JV_SUCCESS) {
+ if (packet_put_tail_l(sock, buffer.data(), count)) {
+ bytes_read = count;
+ btsock_thread_add_fd(pth, sock->our_fd, BTSOCK_L2CAP,
+ SOCK_THREAD_FD_WR, sock->id);
+ } else { // connection must be dropped
+ DVLOG(2) << __func__
+ << ": unable to push data to socket - closing channel";
+ BTA_JvL2capClose(sock->handle);
+ btsock_l2cap_free_l(sock);
+ return;
+ }
}
}
}
@@ -651,17 +773,26 @@ static void btsock_l2cap_cbk(tBTA_JV_EVT event, tBTA_JV* p_data,
break;
case BTA_JV_L2CAP_CLOSE_EVT:
+ DVLOG(2) << "BTA_JV_L2CAP_CLOSE_EVT: id: " << l2cap_socket_id;
on_l2cap_close(&p_data->l2c_close, l2cap_socket_id);
break;
case BTA_JV_L2CAP_DATA_IND_EVT:
on_l2cap_data_ind(p_data, l2cap_socket_id);
+ DVLOG(2) << "BTA_JV_L2CAP_DATA_IND_EVT";
break;
case BTA_JV_L2CAP_READ_EVT:
+ DVLOG(2) << "BTA_JV_L2CAP_READ_EVT not used";
break;
case BTA_JV_L2CAP_WRITE_EVT:
+ DVLOG(2) << "BTA_JV_L2CAP_WRITE_EVT: id: " << l2cap_socket_id;
+ on_l2cap_write_done(p_data->l2c_write.len, l2cap_socket_id);
+ break;
+
+ case BTA_JV_L2CAP_WRITE_FIXED_EVT:
+ DVLOG(2) << "BTA_JV_L2CAP_WRITE_FIXED_EVT: id: " << l2cap_socket_id;
on_l2cap_write_done(p_data->l2c_write.len, l2cap_socket_id);
break;
@@ -670,14 +801,27 @@ static void btsock_l2cap_cbk(tBTA_JV_EVT event, tBTA_JV* p_data,
break;
default:
- LOG_ERROR("Unhandled event:%hu l2cap_socket_id:%u", event,
- l2cap_socket_id);
+ LOG(ERROR) << "unhandled event: " << event
+ << ", slot id: " << l2cap_socket_id;
break;
}
}
-const tL2CAP_ERTM_INFO obex_l2c_etm_opt = {L2CAP_FCR_ERTM_MODE,
- /* Mandatory for OBEX over l2cap */};
+/* L2CAP default options for OBEX socket connections */
+const tL2CAP_FCR_OPTS obex_l2c_fcr_opts_def = {
+ L2CAP_FCR_ERTM_MODE, /* Mandatory for OBEX over l2cap */
+ OBX_FCR_OPT_TX_WINDOW_SIZE_BR_EDR, /* Tx window size */
+ OBX_FCR_OPT_MAX_TX_B4_DISCNT, /* Maximum transmissions before
+ disconnecting */
+ OBX_FCR_OPT_RETX_TOUT, /* Retransmission timeout (2 secs) */
+ OBX_FCR_OPT_MONITOR_TOUT, /* Monitor timeout (12 secs) */
+ OBX_FCR_OPT_MAX_PDU_SIZE /* MPS segment size */
+};
+const tL2CAP_ERTM_INFO obex_l2c_etm_opt = {
+ L2CAP_FCR_ERTM_MODE, /* Mandatory for OBEX over l2cap */
+ L2CAP_FCR_CHAN_OPT_ERTM, /* Mandatory for OBEX over l2cap */
+ OBX_USER_RX_BUF_SIZE, OBX_USER_TX_BUF_SIZE,
+ OBX_FCR_RX_BUF_SIZE, OBX_FCR_TX_BUF_SIZE};
/**
* When using a dynamic PSM, a PSM allocation is requested from
@@ -692,7 +836,7 @@ void on_l2cap_psm_assigned(int id, int psm) {
std::unique_lock<std::mutex> lock(state_lock);
l2cap_socket* sock = btsock_l2cap_find_by_id_l(id);
if (!sock) {
- LOG_ERROR("Unable to find l2cap socket with socket_id:%u", id);
+ LOG(ERROR) << __func__ << ": sock is null";
return;
}
@@ -702,6 +846,15 @@ void on_l2cap_psm_assigned(int id, int psm) {
}
static void btsock_l2cap_server_listen(l2cap_socket* sock) {
+ DVLOG(2) << __func__ << ": fixed_chan: " << sock->fixed_chan
+ << ", channel: " << sock->channel
+ << ", is_le_coc: " << sock->is_le_coc;
+
+ if (sock->fixed_chan) {
+ BTA_JvL2capStartServerLE(sock->channel, btsock_l2cap_cbk, sock->id);
+ return;
+ }
+
int connection_type =
sock->is_le_coc ? BTA_JV_CONN_TYPE_L2CAP_LE : BTA_JV_CONN_TYPE_L2CAP;
@@ -714,7 +867,7 @@ static void btsock_l2cap_server_listen(l2cap_socket* sock) {
/* Setup ETM settings: mtu will be set below */
std::unique_ptr<tL2CAP_CFG_INFO> cfg = std::make_unique<tL2CAP_CFG_INFO>(
- tL2CAP_CFG_INFO{.fcr_present = true, .fcr = kDefaultErtmOptions});
+ tL2CAP_CFG_INFO{.fcr_present = true, .fcr = obex_l2c_fcr_opts_def});
std::unique_ptr<tL2CAP_ERTM_INFO> ertm_info;
if (!sock->is_le_coc) {
@@ -731,11 +884,18 @@ static bt_status_t btsock_l2cap_listen_or_connect(const char* name,
int channel, int* sock_fd,
int flags, char listen,
int app_uid) {
- bool is_le_coc = (flags & BTSOCK_FLAG_LE_COC) != 0;
+ int fixed_chan = 1;
+ bool is_le_coc = false;
- if (!sock_fd) {
- LOG_INFO("Invalid socket descriptor");
- return BT_STATUS_PARM_INVALID;
+ if (!sock_fd) return BT_STATUS_PARM_INVALID;
+
+ if (channel < 0) {
+ // We need to auto assign a PSM
+ fixed_chan = 0;
+ } else {
+ is_le_coc = (flags & BTSOCK_FLAG_LE_COC) != 0;
+ fixed_chan = (channel & L2CAP_MASK_FIXED_CHANNEL) != 0;
+ channel &= ~L2CAP_MASK_FIXED_CHANNEL;
}
if (!is_inited()) return BT_STATUS_NOT_READY;
@@ -748,6 +908,7 @@ static bt_status_t btsock_l2cap_listen_or_connect(const char* name,
return BT_STATUS_NOMEM;
}
+ sock->fixed_chan = fixed_chan;
sock->channel = channel;
sock->app_uid = app_uid;
sock->is_le_coc = is_le_coc;
@@ -757,12 +918,15 @@ static bt_status_t btsock_l2cap_listen_or_connect(const char* name,
if (listen) {
btsock_l2cap_server_listen(sock);
} else {
+ if (fixed_chan) {
+ BTA_JvL2capConnectLE(channel, sock->addr, btsock_l2cap_cbk, sock->id);
+ } else {
int connection_type =
sock->is_le_coc ? BTA_JV_CONN_TYPE_L2CAP_LE : BTA_JV_CONN_TYPE_L2CAP;
/* Setup ETM settings: mtu will be set below */
std::unique_ptr<tL2CAP_CFG_INFO> cfg = std::make_unique<tL2CAP_CFG_INFO>(
- tL2CAP_CFG_INFO{.fcr_present = true, .fcr = kDefaultErtmOptions});
+ tL2CAP_CFG_INFO{.fcr_present = true, .fcr = obex_l2c_fcr_opts_def});
std::unique_ptr<tL2CAP_ERTM_INFO> ertm_info;
if (!sock->is_le_coc) {
@@ -772,6 +936,7 @@ static bt_status_t btsock_l2cap_listen_or_connect(const char* name,
BTA_JvL2capConnect(
connection_type, sock->security, 0, std::move(ertm_info), channel,
sock->rx_mtu, std::move(cfg), sock->addr, btsock_l2cap_cbk, sock->id);
+ }
}
*sock_fd = sock->app_fd;
@@ -885,8 +1050,14 @@ void btsock_l2cap_signaled(int fd, int flags, uint32_t user_id) {
buffer->len = count;
DVLOG(2) << __func__ << ": bytes received from socket: " << count;
- // will take care of freeing buffer
- BTA_JvL2capWrite(sock->handle, PTR_TO_UINT(buffer), buffer, user_id);
+ if (sock->fixed_chan) {
+ // will take care of freeing buffer
+ BTA_JvL2capWriteFixed(sock->channel, sock->addr, PTR_TO_UINT(buffer),
+ btsock_l2cap_cbk, buffer, user_id);
+ } else {
+ // will take care of freeing buffer
+ BTA_JvL2capWrite(sock->handle, PTR_TO_UINT(buffer), buffer, user_id);
+ }
}
} else
drop_it = true;
diff --git a/btif/src/btif_sock_rfc.cc b/btif/src/btif_sock_rfc.cc
index 6a31dc217..b9ad3a8b5 100644
--- a/btif/src/btif_sock_rfc.cc
+++ b/btif/src/btif_sock_rfc.cc
@@ -18,35 +18,48 @@
#define LOG_TAG "bt_btif_sock_rfcomm"
-#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
+#include <base/logging.h>
+#include <errno.h>
+#include <features.h>
+#include <pthread.h>
+#include <string.h>
#include <sys/ioctl.h>
#include <sys/socket.h>
#include <sys/types.h>
-#include <cstdint>
-#include <mutex>
+#include <unistd.h>
-#include "bt_target.h" // Must be first to define build configuration
+#include <mutex>
-#include "bta/include/bta_jv_api.h"
-#include "btif/include/btif_metrics_logging.h"
-/* The JV interface can have only one user, hence we need to call a few
- * L2CAP functions from this file. */
-#include "btif/include/btif_sock_l2cap.h"
-#include "btif/include/btif_sock_sdp.h"
-#include "btif/include/btif_sock_thread.h"
-#include "btif/include/btif_sock_util.h"
-#include "btif/include/btif_uid.h"
-#include "include/hardware/bt_sock.h"
-#include "osi/include/allocator.h"
+#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
+#include <hardware/bluetooth.h>
+#include <hardware/bt_sock.h>
+
+#include "bt_common.h"
+#include "bt_target.h"
+#include "bta_api.h"
+#include "bta_jv_api.h"
+#include "bta_jv_co.h"
+#include "btif_common.h"
+#include "btif_sock_sdp.h"
+#include "btif_sock_thread.h"
+#include "btif_sock_util.h"
+#include "btif_uid.h"
+#include "btif_util.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
+#include "common/metrics.h"
+#include "hcimsgs.h"
#include "osi/include/compat.h"
#include "osi/include/list.h"
#include "osi/include/log.h"
-#include "osi/include/osi.h" // INVALID_FD
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/port_api.h"
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
+#include "osi/include/osi.h"
+#include "port_api.h"
+#include "sdp_api.h"
+
+/* The JV interface can have only one user, hence we need to call a few
+ * L2CAP functions from this file. */
+#include "btif_sock_l2cap.h"
using bluetooth::Uuid;
@@ -152,7 +165,7 @@ static rfc_slot_t* find_rfc_slot_by_id(uint32_t id) {
for (size_t i = 0; i < ARRAY_SIZE(rfc_slots); ++i)
if (rfc_slots[i].id == id) return &rfc_slots[i];
- LOG_ERROR("%s unable to find RFCOMM slot id: %u", __func__, id);
+ LOG_ERROR(LOG_TAG, "%s unable to find RFCOMM slot id: %u", __func__, id);
return NULL;
}
@@ -190,13 +203,14 @@ static rfc_slot_t* alloc_rfc_slot(const RawAddress* addr, const char* name,
rfc_slot_t* slot = find_free_slot();
if (!slot) {
- LOG_ERROR("%s unable to find free RFCOMM slot.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to find free RFCOMM slot.", __func__);
return NULL;
}
int fds[2] = {INVALID_FD, INVALID_FD};
if (socketpair(AF_LOCAL, SOCK_STREAM, 0, fds) == -1) {
- LOG_ERROR("%s error creating socketpair: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s error creating socketpair: %s", __func__,
+ strerror(errno));
return NULL;
}
@@ -236,7 +250,7 @@ static rfc_slot_t* create_srv_accept_rfc_slot(rfc_slot_t* srv_rs,
rfc_slot_t* accept_rs = alloc_rfc_slot(
addr, srv_rs->service_name, srv_rs->service_uuid, srv_rs->scn, 0, false);
if (!accept_rs) {
- LOG_ERROR("%s unable to allocate RFCOMM slot.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to allocate RFCOMM slot.", __func__);
return NULL;
}
@@ -280,6 +294,10 @@ bt_status_t btsock_rfc_listen(const char* service_name,
if ((flags & BTSOCK_FLAG_NO_SDP) == 0) {
if (!service_uuid || service_uuid->IsEmpty()) {
+ APPL_TRACE_DEBUG(
+ "%s: service_uuid not set AND BTSOCK_FLAG_NO_SDP is not set - "
+ "changing to SPP",
+ __func__);
// Use serial port profile to listen to specified channel
service_uuid = &UUID_SPP;
} else {
@@ -296,11 +314,11 @@ bt_status_t btsock_rfc_listen(const char* service_name,
rfc_slot_t* slot =
alloc_rfc_slot(NULL, service_name, *service_uuid, channel, flags, true);
if (!slot) {
- LOG_ERROR("unable to allocate RFCOMM slot");
+ LOG_ERROR(LOG_TAG, "%s unable to allocate RFCOMM slot.", __func__);
return BT_STATUS_FAIL;
}
- LOG_INFO("Adding listening socket service_name: %s - channel: %d",
- service_name, channel);
+ APPL_TRACE_DEBUG("BTA_JvGetChannelId: service_name: %s - channel: %d",
+ service_name, channel);
BTA_JvGetChannelId(BTA_JV_CONN_TYPE_RFCOMM, slot->id, channel);
*sock_fd = slot->app_fd; // Transfer ownership of fd to caller.
/*TODO:
@@ -338,7 +356,7 @@ bt_status_t btsock_rfc_connect(const RawAddress* bd_addr,
rfc_slot_t* slot =
alloc_rfc_slot(bd_addr, NULL, *service_uuid, channel, flags, false);
if (!slot) {
- LOG_ERROR("%s unable to allocate RFCOMM slot.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to allocate RFCOMM slot.", __func__);
return BT_STATUS_FAIL;
}
@@ -347,13 +365,14 @@ bt_status_t btsock_rfc_connect(const RawAddress* bd_addr,
BTA_JvRfcommConnect(slot->security, slot->role, slot->scn, slot->addr,
rfcomm_cback, slot->id);
if (ret != BTA_JV_SUCCESS) {
- LOG_ERROR("%s unable to initiate RFCOMM connection: %d", __func__, ret);
+ LOG_ERROR(LOG_TAG, "%s unable to initiate RFCOMM connection: %d",
+ __func__, ret);
cleanup_rfc_slot(slot);
return BT_STATUS_FAIL;
}
if (!send_app_scn(slot)) {
- LOG_ERROR("%s unable to send channel number.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to send channel number.", __func__);
cleanup_rfc_slot(slot);
return BT_STATUS_FAIL;
}
@@ -402,7 +421,7 @@ static void cleanup_rfc_slot(rfc_slot_t* slot) {
if (slot->fd != INVALID_FD) {
shutdown(slot->fd, SHUT_RDWR);
close(slot->fd);
- log_socket_connection_state(
+ bluetooth::common::LogSocketConnectionState(
slot->addr, slot->id, BTSOCK_RFCOMM,
android::bluetooth::SOCKET_CONNECTION_STATE_DISCONNECTED,
slot->tx_bytes, slot->rx_bytes, slot->app_uid, slot->scn,
@@ -483,7 +502,7 @@ static void on_srv_rfc_listen_started(tBTA_JV_RFCOMM_START* p_start,
if (p_start->status == BTA_JV_SUCCESS) {
slot->rfc_handle = p_start->handle;
- log_socket_connection_state(
+ bluetooth::common::LogSocketConnectionState(
slot->addr, slot->id, BTSOCK_RFCOMM,
android::bluetooth::SocketConnectionstateEnum::
SOCKET_CONNECTION_STATE_LISTENING,
@@ -506,7 +525,7 @@ static uint32_t on_srv_rfc_connect(tBTA_JV_RFCOMM_SRV_OPEN* p_open,
srv_rs, &p_open->rem_bda, p_open->handle, p_open->new_listen_handle);
if (!accept_rs) return 0;
- log_socket_connection_state(
+ bluetooth::common::LogSocketConnectionState(
accept_rs->addr, accept_rs->id, BTSOCK_RFCOMM,
android::bluetooth::SOCKET_CONNECTION_STATE_CONNECTED, 0, 0,
accept_rs->app_uid, accept_rs->scn,
@@ -538,7 +557,7 @@ static void on_cli_rfc_connect(tBTA_JV_RFCOMM_OPEN* p_open, uint32_t id) {
slot->rfc_port_handle = BTA_JvRfcommGetPortHdl(p_open->handle);
slot->addr = p_open->rem_bda;
- log_socket_connection_state(
+ bluetooth::common::LogSocketConnectionState(
slot->addr, slot->id, BTSOCK_RFCOMM,
android::bluetooth::SOCKET_CONNECTION_STATE_CONNECTED, 0, 0,
slot->app_uid, slot->scn,
@@ -548,7 +567,7 @@ static void on_cli_rfc_connect(tBTA_JV_RFCOMM_OPEN* p_open, uint32_t id) {
if (send_app_connect_signal(slot->fd, &slot->addr, slot->scn, 0, -1)) {
slot->f.connected = true;
} else {
- LOG_ERROR("%s unable to send connect completion signal to caller.",
+ LOG_ERROR(LOG_TAG, "%s unable to send connect completion signal to caller.",
__func__);
}
}
@@ -560,7 +579,7 @@ static void on_rfc_close(UNUSED_ATTR tBTA_JV_RFCOMM_CLOSE* p_close,
// rfc_handle already closed when receiving rfcomm close event from stack.
rfc_slot_t* slot = find_rfc_slot_by_id(id);
if (slot) {
- log_socket_connection_state(
+ bluetooth::common::LogSocketConnectionState(
slot->addr, slot->id, BTSOCK_RFCOMM,
android::bluetooth::SOCKET_CONNECTION_STATE_DISCONNECTING, 0, 0,
slot->app_uid, slot->scn,
@@ -572,8 +591,8 @@ static void on_rfc_close(UNUSED_ATTR tBTA_JV_RFCOMM_CLOSE* p_close,
static void on_rfc_write_done(tBTA_JV_RFCOMM_WRITE* p, uint32_t id) {
if (p->status != BTA_JV_SUCCESS) {
- LOG_ERROR("%s error writing to RFCOMM socket with slot %u.", __func__,
- p->req_id);
+ LOG_ERROR(LOG_TAG, "%s error writing to RFCOMM socket with slot %u.",
+ __func__, p->req_id);
return;
}
@@ -649,7 +668,7 @@ static uint32_t rfcomm_cback(tBTA_JV_EVT event, tBTA_JV* p_data,
break;
default:
- LOG_ERROR("%s unhandled event %d, slot id: %u", __func__, event,
+ LOG_ERROR(LOG_TAG, "%s unhandled event %d, slot id: %u", __func__, event,
rfcomm_slot_id);
break;
}
@@ -744,10 +763,10 @@ static void jv_dm_cback(tBTA_JV_EVT event, tBTA_JV* p_data, uint32_t id) {
} else if (slot) {
// TODO(sharvil): this is really a logic error and we should probably
// assert.
- LOG_ERROR(
- "%s SDP response returned but RFCOMM slot %d did not "
- "request SDP record.",
- __func__, id);
+ LOG_ERROR(LOG_TAG,
+ "%s SDP response returned but RFCOMM slot %d did not "
+ "request SDP record.",
+ __func__, id);
}
} else if (slot) {
cleanup_rfc_slot(slot);
@@ -785,7 +804,7 @@ static sent_status_t send_data_to_app(int fd, BT_HDR* p_buf) {
if (sent == -1) {
if (errno == EAGAIN || errno == EWOULDBLOCK) return SENT_NONE;
- LOG_ERROR("%s error writing RFCOMM data back to app: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s error writing RFCOMM data back to app: %s", __func__,
strerror(errno));
return SENT_FAILED;
}
@@ -845,10 +864,10 @@ void btsock_rfc_signaled(UNUSED_ATTR int fd, int flags, uint32_t user_id) {
BTA_JvRfcommWrite(slot->rfc_handle, slot->id);
}
} else {
- LOG_ERROR(
- "%s socket signaled for read while disconnected, slot: %d, "
- "channel: %d",
- __func__, slot->id, slot->scn);
+ LOG_ERROR(LOG_TAG,
+ "%s socket signaled for read while disconnected, slot: %d, "
+ "channel: %d",
+ __func__, slot->id, slot->scn);
need_close = true;
}
}
@@ -856,10 +875,10 @@ void btsock_rfc_signaled(UNUSED_ATTR int fd, int flags, uint32_t user_id) {
if (flags & SOCK_THREAD_FD_WR) {
// App is ready to receive more data, tell stack to enable data flow.
if (!slot->f.connected || !flush_incoming_que_on_wr_signal(slot)) {
- LOG_ERROR(
- "%s socket signaled for write while disconnected (or write "
- "failure), slot: %d, channel: %d",
- __func__, slot->id, slot->scn);
+ LOG_ERROR(LOG_TAG,
+ "%s socket signaled for write while disconnected (or write "
+ "failure), slot: %d, channel: %d",
+ __func__, slot->id, slot->scn);
need_close = true;
}
}
@@ -919,7 +938,8 @@ int bta_co_rfc_data_outgoing_size(uint32_t id, int* size) {
if (!slot) return false;
if (ioctl(slot->fd, FIONREAD, size) != 0) {
- LOG_ERROR("%s unable to determine bytes remaining to be read on fd %d: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s unable to determine bytes remaining to be read on fd %d: %s",
__func__, slot->fd, strerror(errno));
cleanup_rfc_slot(slot);
return false;
@@ -937,7 +957,7 @@ int bta_co_rfc_data_outgoing(uint32_t id, uint8_t* buf, uint16_t size) {
OSI_NO_INTR(received = recv(slot->fd, buf, size, 0));
if (received != size) {
- LOG_ERROR("%s error receiving RFCOMM data from app: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s error receiving RFCOMM data from app: %s", __func__,
strerror(errno));
cleanup_rfc_slot(slot);
return false;
diff --git a/btif/src/btif_sock_sco.cc b/btif/src/btif_sock_sco.cc
index bd07432c0..62831960c 100644
--- a/btif/src/btif_sock_sco.cc
+++ b/btif/src/btif_sock_sco.cc
@@ -18,22 +18,27 @@
#define LOG_TAG "bt_btif_sock_sco"
+#include <base/logging.h>
+#include <errno.h>
+#include <pthread.h>
+#include <string.h>
#include <sys/socket.h>
#include <sys/types.h>
+#include <unistd.h>
-#include <cstdint>
#include <mutex>
+#include <hardware/bluetooth.h>
+#include <hardware/bt_sock.h>
+
+#include "btif_common.h"
#include "device/include/esco_parameters.h"
-#include "include/hardware/bt_sock.h"
#include "osi/include/allocator.h"
#include "osi/include/list.h"
#include "osi/include/log.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
+#include "osi/include/osi.h"
#include "osi/include/socket.h"
#include "osi/include/thread.h"
-#include "stack/include/btm_api.h"
-#include "types/raw_address.h"
// This module provides a socket abstraction for SCO connections to a higher
// layer. It returns file descriptors representing two types of sockets:
@@ -85,7 +90,7 @@ bt_status_t btsock_sco_init(thread_t* thread_) {
if (!sco_sockets) return BT_STATUS_FAIL;
thread = thread_;
- enh_esco_params_t params = esco_parameters_for_codec(SCO_CODEC_CVSD_D1);
+ enh_esco_params_t params = esco_parameters_for_codec(ESCO_CODEC_CVSD);
BTM_SetEScoMode(&params);
return BT_STATUS_SUCCESS;
@@ -133,30 +138,30 @@ static sco_socket_t* sco_socket_establish_locked(bool is_listening,
tBTM_STATUS status;
enh_esco_params_t params;
if (socketpair(AF_LOCAL, SOCK_STREAM, 0, pair) == -1) {
- LOG_ERROR("%s unable to allocate socket pair: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s unable to allocate socket pair: %s", __func__,
strerror(errno));
goto error;
}
sco_socket = sco_socket_new();
if (!sco_socket) {
- LOG_ERROR("%s unable to allocate new SCO socket.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to allocate new SCO socket.", __func__);
goto error;
}
- params = esco_parameters_for_codec(SCO_CODEC_CVSD_D1);
+ params = esco_parameters_for_codec(ESCO_CODEC_CVSD);
status = BTM_CreateSco(bd_addr, !is_listening, params.packet_types,
&sco_socket->sco_handle, connect_completed_cb,
disconnect_completed_cb);
if (status != BTM_CMD_STARTED) {
- LOG_ERROR("%s unable to create SCO socket: %d", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s unable to create SCO socket: %d", __func__, status);
goto error;
}
socket = socket_new_from_fd(pair[1]);
if (!socket) {
- LOG_ERROR("%s unable to allocate socket from file descriptor %d.", __func__,
- pair[1]);
+ LOG_ERROR(LOG_TAG, "%s unable to allocate socket from file descriptor %d.",
+ __func__, pair[1]);
goto error;
}
@@ -221,14 +226,14 @@ static void connection_request_cb(tBTM_ESCO_EVT event,
sco_socket_t* new_sco_socket;
if (!sco_socket) {
- LOG_ERROR("%s unable to find sco_socket for handle: %hu", __func__,
+ LOG_ERROR(LOG_TAG, "%s unable to find sco_socket for handle: %hu", __func__,
conn_data->sco_inx);
goto error;
}
if (sco_socket != listen_sco_socket) {
LOG_ERROR(
-
+ LOG_TAG,
"%s received connection request on non-listening socket handle: %hu",
__func__, conn_data->sco_inx);
goto error;
@@ -236,7 +241,7 @@ static void connection_request_cb(tBTM_ESCO_EVT event,
new_sco_socket = sco_socket_establish_locked(true, NULL, &client_fd);
if (!new_sco_socket) {
- LOG_ERROR("%s unable to allocate new sco_socket.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to allocate new sco_socket.", __func__);
goto error;
}
@@ -254,7 +259,8 @@ static void connection_request_cb(tBTM_ESCO_EVT event,
if (socket_write_and_transfer_fd(sco_socket->socket, &connect_signal,
sizeof(connect_signal),
client_fd) != sizeof(connect_signal)) {
- LOG_ERROR("%s unable to send new file descriptor to listening socket.",
+ LOG_ERROR(LOG_TAG,
+ "%s unable to send new file descriptor to listening socket.",
__func__);
goto error;
}
@@ -274,8 +280,8 @@ static void connect_completed_cb(uint16_t sco_handle) {
sco_socket_t* sco_socket = sco_socket_find_locked(sco_handle);
if (!sco_socket) {
- LOG_ERROR("%s SCO socket not found on connect for handle: %hu", __func__,
- sco_handle);
+ LOG_ERROR(LOG_TAG, "%s SCO socket not found on connect for handle: %hu",
+ __func__, sco_handle);
return;
}
@@ -296,8 +302,8 @@ static void disconnect_completed_cb(uint16_t sco_handle) {
sco_socket_t* sco_socket = sco_socket_find_locked(sco_handle);
if (!sco_socket) {
- LOG_ERROR("%s SCO socket not found on disconnect for handle: %hu", __func__,
- sco_handle);
+ LOG_ERROR(LOG_TAG, "%s SCO socket not found on disconnect for handle: %hu",
+ __func__, sco_handle);
return;
}
diff --git a/btif/src/btif_sock_sdp.cc b/btif/src/btif_sock_sdp.cc
index 3fb36f058..d7993e5d8 100644
--- a/btif/src/btif_sock_sdp.cc
+++ b/btif/src/btif_sock_sdp.cc
@@ -18,17 +18,30 @@
#define LOG_TAG "bt_btif_sock_sdp"
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "bta/include/bta_jv_api.h"
-#include "bta/include/bta_op_api.h"
-#include "bta/include/utl.h"
-#include "bta/pb/bta_pbs_int.h"
-#include "bta/sys/bta_sys.h"
-#include "btif/include/btif_sock_sdp.h"
-#include "stack/include/sdp_api.h"
-#include "stack/include/sdpdefs.h"
-#include "types/bluetooth/uuid.h"
+#include "btif_sock_sdp.h"
+
+#include <errno.h>
+#include <sys/socket.h>
+#include <sys/types.h>
+
+#include <hardware/bluetooth.h>
+#include <hardware/bt_sock.h>
+
+#include "../bta/pb/bta_pbs_int.h"
+#include "../include/bta_op_api.h"
+#include "bt_common.h"
+#include "bt_target.h"
+#include "bta_api.h"
+#include "bta_jv_api.h"
+#include "btif_common.h"
+#include "btif_sock_util.h"
+#include "btif_util.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
+#include "hcimsgs.h"
+#include "sdp_api.h"
+#include "utl.h"
using bluetooth::Uuid;
@@ -184,13 +197,6 @@ static int add_sdp_by_uuid(const char* name, const Uuid& uuid,
APPL_TRACE_DEBUG(
"%s: service registered successfully, service_name: %s, handle: 0x%08x",
__func__, name, handle);
-
- {
- // Write the custom 128-bit UUID to EIR
- tBTA_CUSTOM_UUID curr = {uuid, handle};
- bta_sys_add_cust_uuid(curr);
- }
-
return handle;
error:
@@ -466,11 +472,5 @@ int add_rfc_sdp_rec(const char* name, Uuid uuid, const int channel) {
void del_rfc_sdp_rec(int handle) {
APPL_TRACE_DEBUG("del_rfc_sdp_rec: handle:0x%x", handle);
- if ((handle != -1) && (handle != 0)) {
- // Remove the custom 128-bit UUID from EIR
- const tBTA_CUSTOM_UUID curr = {Uuid::kEmpty, (uint32_t)handle};
- bta_sys_remove_cust_uuid(curr);
-
- BTA_JvDeleteRecord(handle);
- }
+ if ((handle != -1) && (handle != 0)) BTA_JvDeleteRecord(handle);
}
diff --git a/btif/src/btif_sock_thread.cc b/btif/src/btif_sock_thread.cc
index 96395e91c..a49568bf7 100644
--- a/btif/src/btif_sock_thread.cc
+++ b/btif/src/btif_sock_thread.cc
@@ -47,7 +47,6 @@
#include <unistd.h>
#include <mutex>
-#include <optional>
#include <string>
#include "bta_api.h"
@@ -77,22 +76,22 @@
#define CMD_REMOVE_FD 4
#define CMD_USER_PRIVATE 5
-struct poll_slot_t {
+typedef struct {
struct pollfd pfd;
uint32_t user_id;
int type;
int flags;
-};
-struct thread_slot_t {
+} poll_slot_t;
+typedef struct {
int cmd_fdr, cmd_fdw;
int poll_count;
poll_slot_t ps[MAX_POLL];
int psi[MAX_POLL]; // index of poll slot
- std::optional<pthread_t> thread_id;
+ pthread_t thread_id;
btsock_signaled_cb callback;
btsock_cmd_cb cmd_callback;
int used;
-};
+} thread_slot_t;
static thread_slot_t ts[MAX_THREAD];
static void* sock_poll_thread(void* arg);
@@ -134,6 +133,7 @@ static int alloc_thread_slot() {
int i;
// reversed order to save guard uninitialized access to 0 index
for (i = MAX_THREAD - 1; i >= 0; i--) {
+ APPL_TRACE_DEBUG("ts[%d].used:%d", i, ts[i].used);
if (!ts[i].used) {
ts[i].used = 1;
return i;
@@ -149,25 +149,28 @@ static void free_thread_slot(int h) {
} else
APPL_TRACE_ERROR("invalid thread handle:%d", h);
}
-void btsock_thread_init() {
+int btsock_thread_init() {
static int initialized;
+ APPL_TRACE_DEBUG("in initialized:%d", initialized);
if (!initialized) {
initialized = 1;
int h;
for (h = 0; h < MAX_THREAD; h++) {
ts[h].cmd_fdr = ts[h].cmd_fdw = -1;
ts[h].used = 0;
- ts[h].thread_id = std::nullopt;
+ ts[h].thread_id = -1;
ts[h].poll_count = 0;
ts[h].callback = NULL;
ts[h].cmd_callback = NULL;
}
}
+ return true;
}
int btsock_thread_create(btsock_signaled_cb callback,
btsock_cmd_cb cmd_callback) {
asrt(callback || cmd_callback);
int h = alloc_thread_slot();
+ APPL_TRACE_DEBUG("alloc_thread_slot ret:%d", h);
if (h >= 0) {
init_poll(h);
pthread_t thread;
@@ -179,6 +182,7 @@ int btsock_thread_create(btsock_signaled_cb callback,
}
ts[h].thread_id = thread;
+ APPL_TRACE_DEBUG("h:%d, thread id:%d", h, ts[h].thread_id);
ts[h].callback = callback;
ts[h].cmd_callback = cmd_callback;
}
@@ -192,6 +196,8 @@ static inline void init_cmd_fd(int h) {
APPL_TRACE_ERROR("socketpair failed: %s", strerror(errno));
return;
}
+ APPL_TRACE_DEBUG("h:%d, cmd_fdr:%d, cmd_fdw:%d", h, ts[h].cmd_fdr,
+ ts[h].cmd_fdw);
// add the cmd fd for read & write
add_poll(h, ts[h].cmd_fdr, 0, SOCK_THREAD_FD_RD, 0);
}
@@ -224,16 +230,17 @@ int btsock_thread_add_fd(int h, int fd, int type, int flags, uint32_t user_id) {
}
if (flags & SOCK_THREAD_ADD_FD_SYNC) {
// must executed in socket poll thread
- if (ts[h].thread_id.value() == pthread_self()) {
+ if (ts[h].thread_id == pthread_self()) {
// cleanup one-time flags
flags &= ~SOCK_THREAD_ADD_FD_SYNC;
add_poll(h, fd, type, flags, user_id);
return true;
}
- LOG_WARN(
+ APPL_TRACE_DEBUG(
"THREAD_ADD_FD_SYNC is not called in poll thread, fallback to async");
}
sock_cmd_t cmd = {CMD_ADD_FD, fd, type, flags, user_id};
+ APPL_TRACE_DEBUG("adding fd:%d, flags:0x%x", fd, flags);
ssize_t ret;
OSI_NO_INTR(ret = send(ts[h].cmd_fdw, &cmd, sizeof(cmd), 0));
@@ -271,6 +278,7 @@ int btsock_thread_post_cmd(int h, int type, const unsigned char* data, int size,
return false;
}
sock_cmd_t cmd = {CMD_USER_PRIVATE, 0, type, size, user_id};
+ APPL_TRACE_DEBUG("post cmd type:%d, size:%d, h:%d, ", type, size, h);
sock_cmd_t* cmd_send = &cmd;
int size_send = sizeof(cmd);
if (data && size) {
@@ -322,9 +330,9 @@ int btsock_thread_exit(int h) {
OSI_NO_INTR(ret = send(ts[h].cmd_fdw, &cmd, sizeof(cmd), 0));
if (ret == sizeof(cmd)) {
- if (ts[h].thread_id != std::nullopt) {
- pthread_join(ts[h].thread_id.value(), 0);
- ts[h].thread_id = std::nullopt;
+ if (ts[h].thread_id != -1) {
+ pthread_join(ts[h].thread_id, 0);
+ ts[h].thread_id = -1;
}
free_thread_slot(h);
return true;
@@ -334,7 +342,7 @@ int btsock_thread_exit(int h) {
static void init_poll(int h) {
int i;
ts[h].poll_count = 0;
- ts[h].thread_id = std::nullopt;
+ ts[h].thread_id = -1;
ts[h].callback = NULL;
ts[h].cmd_callback = NULL;
for (i = 0; i < MAX_POLL; i++) {
@@ -409,9 +417,10 @@ static int process_cmd_sock(int h) {
OSI_NO_INTR(ret = recv(fd, &cmd, sizeof(cmd), MSG_WAITALL));
if (ret != sizeof(cmd)) {
- LOG_ERROR("recv cmd errno:%d", errno);
+ APPL_TRACE_ERROR("recv cmd errno:%d", errno);
return false;
}
+ APPL_TRACE_DEBUG("cmd.id:%d", cmd.id);
switch (cmd.id) {
case CMD_ADD_FD:
add_poll(h, cmd.fd, cmd.type, cmd.flags, cmd.user_id);
@@ -436,12 +445,24 @@ static int process_cmd_sock(int h) {
case CMD_EXIT:
return false;
default:
- LOG_WARN("unknown cmd: %d", cmd.id);
+ APPL_TRACE_DEBUG("unknown cmd: %d", cmd.id);
break;
}
return true;
}
+static void print_events(short events) {
+ std::string flags("");
+ if ((events)&POLLIN) flags += " POLLIN";
+ if ((events)&POLLPRI) flags += " POLLPRI";
+ if ((events)&POLLOUT) flags += " POLLOUT";
+ if ((events)&POLLERR) flags += " POLLERR";
+ if ((events)&POLLHUP) flags += " POLLHUP ";
+ if ((events)&POLLNVAL) flags += " POLLNVAL";
+ if ((events)&POLLRDHUP) flags += " POLLRDHUP";
+ APPL_TRACE_DEBUG("print poll event:%x = %s", (events), flags.c_str());
+}
+
static void process_data_sock(int h, struct pollfd* pfds, int count) {
asrt(count <= ts[h].poll_count);
int i;
@@ -452,6 +473,7 @@ static void process_data_sock(int h, struct pollfd* pfds, int count) {
uint32_t user_id = ts[h].ps[ps_i].user_id;
int type = ts[h].ps[ps_i].type;
int flags = 0;
+ print_events(pfds[i].revents);
if (IS_READ(pfds[i].revents)) {
flags |= SOCK_THREAD_FD_RD;
}
@@ -512,7 +534,7 @@ static void* sock_poll_thread(void* arg) {
{
asrt(pfds[0].fd == ts[h].cmd_fdr);
if (!process_cmd_sock(h)) {
- LOG_INFO("h:%d, process_cmd_sock return false, exit...", h);
+ APPL_TRACE_DEBUG("h:%d, process_cmd_sock return false, exit...", h);
break;
}
if (ret == 1)
@@ -522,9 +544,9 @@ static void* sock_poll_thread(void* arg) {
}
if (need_process_data_fd) process_data_sock(h, pfds, ret);
} else {
- LOG_INFO("no data, select ret: %d", ret);
+ APPL_TRACE_DEBUG("no data, select ret: %d", ret)
};
}
- LOG_INFO("socket poll thread exiting, h:%d", h);
+ APPL_TRACE_DEBUG("socket poll thread exiting, h:%d", h);
return 0;
}
diff --git a/btif/src/btif_sock_util.cc b/btif/src/btif_sock_util.cc
index bf81522be..68afa2ad8 100644
--- a/btif/src/btif_sock_util.cc
+++ b/btif/src/btif_sock_util.cc
@@ -36,9 +36,22 @@
#include <hardware/bluetooth.h>
#include <hardware/bt_sock.h>
+#include "bt_common.h"
#include "bt_target.h"
+#include "bta_api.h"
+#include "bta_jv_api.h"
+#include "bta_jv_co.h"
+#include "btif_common.h"
+#include "btif_sock_sdp.h"
+#include "btif_sock_thread.h"
#include "btif_util.h"
-#include "osi/include/osi.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
+#include "hcimsgs.h"
+#include "osi/include/log.h"
+#include "port_api.h"
+#include "sdp_api.h"
#define asrt(s) \
do { \
diff --git a/btif/src/btif_storage.cc b/btif/src/btif_storage.cc
index 8a20518b5..95e4ef071 100644
--- a/btif/src/btif_storage.cc
+++ b/btif/src/btif_storage.cc
@@ -35,6 +35,7 @@
#include <alloca.h>
#include <base/logging.h>
#include <ctype.h>
+#include <log/log.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
@@ -81,9 +82,6 @@ using bluetooth::Uuid;
#define BTIF_STORAGE_KEY_LOCAL_IO_CAPS "LocalIOCaps"
#define BTIF_STORAGE_KEY_LOCAL_IO_CAPS_BLE "LocalIOCapsBLE"
#define BTIF_STORAGE_KEY_ADAPTER_DISC_TIMEOUT "DiscoveryTimeout"
-#define BTIF_STORAGE_KEY_GATT_CLIENT_SUPPORTED "GattClientSupportedFeatures"
-#define BTIF_STORAGE_KEY_GATT_CLIENT_DB_HASH "GattClientDatabaseHash"
-#define BTIF_STORAGE_KEY_GATT_SERVER_SUPPORTED "GattServerSupportedFeatures"
/* This is a local property to add a device found */
#define BT_PROPERTY_REMOTE_DEVICE_TIMESTAMP 0xFF
@@ -189,12 +187,12 @@ static int prop2cfg(const RawAddress* remote_bd_addr, bt_property_t* prop) {
bdstr = remote_bd_addr->ToString();
}
+ BTIF_TRACE_DEBUG("in, bd addr:%s, prop type:%d, len:%d", bdstr.c_str(),
+ prop->type, prop->len);
char value[1024];
if (prop->len <= 0 || prop->len > (int)sizeof(value) - 1) {
- LOG_WARN(
- "Unable to save property to configuration file type:%d, "
- " len:%d is invalid",
- prop->type, prop->len);
+ BTIF_TRACE_ERROR("property type:%d, len:%d is invalid", prop->type,
+ prop->len);
return false;
}
switch (prop->type) {
@@ -286,9 +284,11 @@ static int cfg2prop(const RawAddress* remote_bd_addr, bt_property_t* prop) {
if (remote_bd_addr) {
bdstr = remote_bd_addr->ToString();
}
+ BTIF_TRACE_DEBUG("in, bd addr:%s, prop type:%d, len:%d", bdstr.c_str(),
+ prop->type, prop->len);
if (prop->len <= 0) {
- LOG_WARN("Invalid property read from configuration file type:%d, len:%d",
- prop->type, prop->len);
+ BTIF_TRACE_ERROR("property type:%d, len:%d is invalid", prop->type,
+ prop->len);
return false;
}
int ret = false;
@@ -424,6 +424,8 @@ static bt_status_t btif_in_fetch_bonded_device(const std::string& bdstr) {
if ((btif_in_fetch_bonded_ble_device(bdstr, false, NULL) !=
BT_STATUS_SUCCESS) &&
(!bt_linkkey_file_found)) {
+ BTIF_TRACE_DEBUG("Remote device:%s, no link key or ble key found",
+ bdstr.c_str());
return BT_STATUS_FAIL;
}
return BT_STATUS_SUCCESS;
@@ -446,8 +448,11 @@ static bt_status_t btif_in_fetch_bonded_devices(
bool bt_linkkey_file_found = false;
int device_type;
- for (const auto& bd_addr : btif_config_get_paired_devices()) {
- auto name = bd_addr.ToString();
+ // TODO: this code is not thread safe, it can corrupt config content.
+ // b/67595284
+ for (const section_t& section : btif_config_sections()) {
+ const std::string& name = section.name;
+ if (!RawAddress::IsValidAddress(name)) continue;
BTIF_TRACE_DEBUG("Remote device:%s", name.c_str());
LinkKey link_key;
@@ -455,6 +460,8 @@ static bt_status_t btif_in_fetch_bonded_devices(
if (btif_config_get_bin(name, "LinkKey", link_key.data(), &size)) {
int linkkey_type;
if (btif_config_get_int(name, "LinkKeyType", &linkkey_type)) {
+ RawAddress bd_addr;
+ RawAddress::FromString(name, bd_addr);
if (add) {
DEV_CLASS dev_class = {0, 0, 0};
int cod;
@@ -462,8 +469,8 @@ static bt_status_t btif_in_fetch_bonded_devices(
if (btif_config_get_int(name, "DevClass", &cod))
uint2devclass((uint32_t)cod, dev_class);
btif_config_get_int(name, "PinLength", &pin_length);
- BTA_DmAddDevice(bd_addr, dev_class, link_key, (uint8_t)linkkey_type,
- pin_length);
+ BTA_DmAddDevice(bd_addr, dev_class, link_key, 0, 0,
+ (uint8_t)linkkey_type, 0, pin_length);
if (btif_config_get_int(name, "DevType", &device_type) &&
(device_type == BT_DEVICE_TYPE_DUMO)) {
@@ -477,14 +484,15 @@ static bt_status_t btif_in_fetch_bonded_devices(
}
}
if (!btif_in_fetch_bonded_ble_device(name, add, p_bonded_devices) && !bt_linkkey_file_found) {
- LOG_VERBOSE("No link key or ble key found for device:%s", name.c_str());
+ BTIF_TRACE_DEBUG("Remote device:%s, no link key or ble key found",
+ name.c_str());
}
}
return BT_STATUS_SUCCESS;
}
static void btif_read_le_key(const uint8_t key_type, const size_t key_len,
- RawAddress bd_addr, const tBLE_ADDR_TYPE addr_type,
+ RawAddress bd_addr, const uint8_t addr_type,
const bool add_key, bool* device_added,
bool* key_found) {
CHECK(device_added);
@@ -493,7 +501,7 @@ static void btif_read_le_key(const uint8_t key_type, const size_t key_len,
tBTA_LE_KEY_VALUE key;
memset(&key, 0, sizeof(key));
- if (btif_storage_get_ble_bonding_key(bd_addr, key_type, (uint8_t*)&key,
+ if (btif_storage_get_ble_bonding_key(&bd_addr, key_type, (uint8_t*)&key,
key_len) == BT_STATUS_SUCCESS) {
if (add_key) {
if (!*device_added) {
@@ -624,12 +632,13 @@ bt_status_t btif_storage_get_adapter_property(bt_property_t* property) {
/* Fetch the local BD ADDR */
const controller_t* controller = controller_get_interface();
if (!controller->get_is_ready()) {
- LOG_ERROR("%s: Controller not ready! Unable to return Bluetooth Address",
+ LOG_ERROR(LOG_TAG,
+ "%s: Controller not ready! Unable to return Bluetooth Address",
__func__);
*bd_addr = RawAddress::kEmpty;
return BT_STATUS_FAIL;
} else {
- LOG_ERROR("%s: Controller ready!", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Controller ready!", __func__);
*bd_addr = *controller->get_address();
}
property->len = RawAddress::kLength;
@@ -658,7 +667,7 @@ bt_status_t btif_storage_get_adapter_property(bt_property_t* property) {
uint32_t i;
tBTA_SERVICE_MASK service_mask = btif_get_enabled_services_mask();
- LOG_INFO("%s service_mask:0x%x", __func__, service_mask);
+ LOG_INFO(LOG_TAG, "%s service_mask:0x%x", __func__, service_mask);
for (i = 0; i < BTA_MAX_SERVICE_ID; i++) {
/* This should eventually become a function when more services are enabled
*/
@@ -836,7 +845,7 @@ bt_status_t btif_storage_add_bonded_device(RawAddress* remote_bd_addr,
bt_status_t btif_storage_remove_bonded_device(
const RawAddress* remote_bd_addr) {
std::string bdstr = remote_bd_addr->ToString();
- LOG_INFO("Removing bonded device addr:%s", bdstr.c_str());
+ BTIF_TRACE_DEBUG("in bd addr:%s", bdstr.c_str());
btif_storage_remove_ble_bonding_keys(remote_bd_addr);
@@ -850,16 +859,6 @@ bt_status_t btif_storage_remove_bonded_device(
if (btif_config_exist(bdstr, BTIF_STORAGE_PATH_REMOTE_ALIASE)) {
ret &= btif_config_remove(bdstr, BTIF_STORAGE_PATH_REMOTE_ALIASE);
}
- if (btif_config_exist(bdstr, BTIF_STORAGE_KEY_GATT_CLIENT_SUPPORTED)) {
- ret &= btif_config_remove(bdstr, BTIF_STORAGE_KEY_GATT_CLIENT_SUPPORTED);
- }
- if (btif_config_exist(bdstr, BTIF_STORAGE_KEY_GATT_CLIENT_DB_HASH)) {
- ret &= btif_config_remove(bdstr, BTIF_STORAGE_KEY_GATT_CLIENT_DB_HASH);
- }
- if (btif_config_exist(bdstr, BTIF_STORAGE_KEY_GATT_SERVER_SUPPORTED)) {
- ret &= btif_config_remove(bdstr, BTIF_STORAGE_KEY_GATT_SERVER_SUPPORTED);
- }
-
/* write bonded info immediately */
btif_config_flush();
return ret ? BT_STATUS_SUCCESS : BT_STATUS_FAIL;
@@ -874,14 +873,20 @@ bt_status_t btif_storage_remove_bonded_device(
*/
static void remove_devices_with_sample_ltk() {
std::vector<RawAddress> bad_ltk;
- for (const auto& bd_addr : btif_config_get_paired_devices()) {
- auto name = bd_addr.ToString();
+ for (const section_t& section : btif_config_sections()) {
+ const std::string& name = section.name;
+ if (!RawAddress::IsValidAddress(name)) {
+ continue;
+ }
+
+ RawAddress bd_addr;
+ RawAddress::FromString(name, bd_addr);
tBTA_LE_KEY_VALUE key;
memset(&key, 0, sizeof(key));
if (btif_storage_get_ble_bonding_key(
- bd_addr, BTM_LE_KEY_PENC, (uint8_t*)&key,
+ &bd_addr, BTIF_DM_LE_KEY_PENC, (uint8_t*)&key,
sizeof(tBTM_LE_PENC_KEYS)) == BT_STATUS_SUCCESS) {
if (is_sample_ltk(key.penc_key.ltk)) {
bad_ltk.push_back(bd_addr);
@@ -1052,22 +1057,22 @@ bt_status_t btif_storage_add_ble_bonding_key(RawAddress* remote_bd_addr,
uint8_t key_length) {
const char* name;
switch (key_type) {
- case BTM_LE_KEY_PENC:
+ case BTIF_DM_LE_KEY_PENC:
name = "LE_KEY_PENC";
break;
- case BTM_LE_KEY_PID:
+ case BTIF_DM_LE_KEY_PID:
name = "LE_KEY_PID";
break;
- case BTM_LE_KEY_PCSRK:
+ case BTIF_DM_LE_KEY_PCSRK:
name = "LE_KEY_PCSRK";
break;
- case BTM_LE_KEY_LENC:
+ case BTIF_DM_LE_KEY_LENC:
name = "LE_KEY_LENC";
break;
- case BTM_LE_KEY_LCSRK:
+ case BTIF_DM_LE_KEY_LCSRK:
name = "LE_KEY_LCSRK";
break;
- case BTM_LE_KEY_LID:
+ case BTIF_DM_LE_KEY_LID:
name = "LE_KEY_LID";
break;
default:
@@ -1089,28 +1094,28 @@ bt_status_t btif_storage_add_ble_bonding_key(RawAddress* remote_bd_addr,
* BT_STATUS_FAIL otherwise
*
******************************************************************************/
-bt_status_t btif_storage_get_ble_bonding_key(const RawAddress& remote_bd_addr,
+bt_status_t btif_storage_get_ble_bonding_key(RawAddress* remote_bd_addr,
uint8_t key_type,
uint8_t* key_value,
int key_length) {
const char* name;
switch (key_type) {
- case BTM_LE_KEY_PENC:
+ case BTIF_DM_LE_KEY_PENC:
name = "LE_KEY_PENC";
break;
- case BTM_LE_KEY_PID:
+ case BTIF_DM_LE_KEY_PID:
name = "LE_KEY_PID";
break;
- case BTM_LE_KEY_PCSRK:
+ case BTIF_DM_LE_KEY_PCSRK:
name = "LE_KEY_PCSRK";
break;
- case BTM_LE_KEY_LENC:
+ case BTIF_DM_LE_KEY_LENC:
name = "LE_KEY_LENC";
break;
- case BTM_LE_KEY_LCSRK:
+ case BTIF_DM_LE_KEY_LCSRK:
name = "LE_KEY_LCSRK";
break;
- case BTM_LE_KEY_LID:
+ case BTIF_DM_LE_KEY_LID:
name = "LE_KEY_LID";
break;
default:
@@ -1118,7 +1123,7 @@ bt_status_t btif_storage_get_ble_bonding_key(const RawAddress& remote_bd_addr,
}
size_t length = key_length;
int ret =
- btif_config_get_bin(remote_bd_addr.ToString(), name, key_value, &length);
+ btif_config_get_bin(remote_bd_addr->ToString(), name, key_value, &length);
return ret ? BT_STATUS_SUCCESS : BT_STATUS_FAIL;
}
@@ -1135,7 +1140,7 @@ bt_status_t btif_storage_get_ble_bonding_key(const RawAddress& remote_bd_addr,
bt_status_t btif_storage_remove_ble_bonding_keys(
const RawAddress* remote_bd_addr) {
std::string bdstr = remote_bd_addr->ToString();
- LOG_INFO("Removing bonding keys for bd addr:%s", bdstr.c_str());
+ BTIF_TRACE_DEBUG(" %s in bd addr:%s", __func__, bdstr.c_str());
int ret = 1;
if (btif_config_exist(bdstr, "LE_KEY_PENC"))
ret &= btif_config_remove(bdstr, "LE_KEY_PENC");
@@ -1241,7 +1246,7 @@ static bt_status_t btif_in_fetch_bonded_ble_device(
const std::string& remote_bd_addr, int add,
btif_bonded_devices_t* p_bonded_devices) {
int device_type;
- tBLE_ADDR_TYPE addr_type;
+ int addr_type;
bool device_added = false;
bool key_found = false;
@@ -1262,22 +1267,22 @@ static bt_status_t btif_in_fetch_bonded_ble_device(
btif_storage_set_remote_addr_type(&bd_addr, BLE_ADDR_PUBLIC);
}
- btif_read_le_key(BTM_LE_KEY_PENC, sizeof(tBTM_LE_PENC_KEYS), bd_addr,
+ btif_read_le_key(BTIF_DM_LE_KEY_PENC, sizeof(tBTM_LE_PENC_KEYS), bd_addr,
addr_type, add, &device_added, &key_found);
- btif_read_le_key(BTM_LE_KEY_PID, sizeof(tBTM_LE_PID_KEYS), bd_addr,
+ btif_read_le_key(BTIF_DM_LE_KEY_PID, sizeof(tBTM_LE_PID_KEYS), bd_addr,
addr_type, add, &device_added, &key_found);
- btif_read_le_key(BTM_LE_KEY_LID, sizeof(tBTM_LE_PID_KEYS), bd_addr,
+ btif_read_le_key(BTIF_DM_LE_KEY_LID, sizeof(tBTM_LE_PID_KEYS), bd_addr,
addr_type, add, &device_added, &key_found);
- btif_read_le_key(BTM_LE_KEY_PCSRK, sizeof(tBTM_LE_PCSRK_KEYS), bd_addr,
+ btif_read_le_key(BTIF_DM_LE_KEY_PCSRK, sizeof(tBTM_LE_PCSRK_KEYS), bd_addr,
addr_type, add, &device_added, &key_found);
- btif_read_le_key(BTM_LE_KEY_LENC, sizeof(tBTM_LE_LENC_KEYS), bd_addr,
+ btif_read_le_key(BTIF_DM_LE_KEY_LENC, sizeof(tBTM_LE_LENC_KEYS), bd_addr,
addr_type, add, &device_added, &key_found);
- btif_read_le_key(BTM_LE_KEY_LCSRK, sizeof(tBTM_LE_LCSRK_KEYS), bd_addr,
+ btif_read_le_key(BTIF_DM_LE_KEY_LCSRK, sizeof(tBTM_LE_LCSRK_KEYS), bd_addr,
addr_type, add, &device_added, &key_found);
// Fill in the bonded devices
@@ -1292,7 +1297,7 @@ static bt_status_t btif_in_fetch_bonded_ble_device(
}
bt_status_t btif_storage_set_remote_addr_type(const RawAddress* remote_bd_addr,
- tBLE_ADDR_TYPE addr_type) {
+ uint8_t addr_type) {
int ret = btif_config_set_int(remote_bd_addr->ToString(), "AddrType",
(int)addr_type);
return ret ? BT_STATUS_SUCCESS : BT_STATUS_FAIL;
@@ -1313,10 +1318,9 @@ bool btif_has_ble_keys(const std::string& bdstr) {
*
******************************************************************************/
bt_status_t btif_storage_get_remote_addr_type(const RawAddress* remote_bd_addr,
- tBLE_ADDR_TYPE* addr_type) {
- int val;
- int ret = btif_config_get_int(remote_bd_addr->ToString(), "AddrType", &val);
- *addr_type = static_cast<tBLE_ADDR_TYPE>(val);
+ int* addr_type) {
+ int ret =
+ btif_config_get_int(remote_bd_addr->ToString(), "AddrType", addr_type);
return ret ? BT_STATUS_SUCCESS : BT_STATUS_FAIL;
}
/*******************************************************************************
@@ -1363,8 +1367,11 @@ bt_status_t btif_storage_add_hid_device_info(
*
******************************************************************************/
bt_status_t btif_storage_load_bonded_hid_info(void) {
- for (const auto& bd_addr : btif_config_get_paired_devices()) {
- auto name = bd_addr.ToString();
+ // TODO: this code is not thread safe, it can corrupt config content.
+ // b/67595284
+ for (const section_t& section : btif_config_sections()) {
+ const std::string& name = section.name;
+ if (!RawAddress::IsValidAddress(name)) continue;
BTIF_TRACE_DEBUG("Remote device:%s", name.c_str());
@@ -1373,7 +1380,9 @@ bt_status_t btif_storage_load_bonded_hid_info(void) {
uint16_t attr_mask = (uint16_t)value;
if (btif_in_fetch_bonded_device(name) != BT_STATUS_SUCCESS) {
- btif_storage_remove_hid_info(bd_addr);
+ RawAddress bd_addr;
+ RawAddress::FromString(name, bd_addr);
+ btif_storage_remove_hid_info(&bd_addr);
continue;
}
@@ -1414,6 +1423,8 @@ bt_status_t btif_storage_load_bonded_hid_info(void) {
(uint8_t*)dscp_info.descriptor.dsc_list, &len);
}
+ RawAddress bd_addr;
+ RawAddress::FromString(name, bd_addr);
// add extracted information to BTA HH
if (btif_hh_add_added_dev(bd_addr, attr_mask)) {
BTA_HhAddDev(bd_addr, attr_mask, sub_class, app_id, dscp_info);
@@ -1434,8 +1445,8 @@ bt_status_t btif_storage_load_bonded_hid_info(void) {
* BT_STATUS_FAIL otherwise
*
******************************************************************************/
-bt_status_t btif_storage_remove_hid_info(const RawAddress& remote_bd_addr) {
- std::string bdstr = remote_bd_addr.ToString();
+bt_status_t btif_storage_remove_hid_info(RawAddress* remote_bd_addr) {
+ std::string bdstr = remote_bd_addr->ToString();
btif_config_remove(bdstr, "HidAttrMask");
btif_config_remove(bdstr, "HidSubClass");
@@ -1466,7 +1477,7 @@ constexpr char HEARING_AID_SERVICE_CHANGED_CCC_HANDLE[] =
constexpr char HEARING_AID_SYNC_ID[] = "HearingAidSyncId";
constexpr char HEARING_AID_RENDER_DELAY[] = "HearingAidRenderDelay";
constexpr char HEARING_AID_PREPARATION_DELAY[] = "HearingAidPreparationDelay";
-constexpr char HEARING_AID_IS_ACCEPTLISTED[] = "HearingAidIsAcceptlisted";
+constexpr char HEARING_AID_IS_WHITE_LISTED[] = "HearingAidIsWhiteListed";
void btif_storage_add_hearing_aid(const HearingDevice& dev_info) {
do_in_jni_thread(
@@ -1496,7 +1507,7 @@ void btif_storage_add_hearing_aid(const HearingDevice& dev_info) {
dev_info.render_delay);
btif_config_set_int(bdstr, HEARING_AID_PREPARATION_DELAY,
dev_info.preparation_delay);
- btif_config_set_int(bdstr, HEARING_AID_IS_ACCEPTLISTED, true);
+ btif_config_set_int(bdstr, HEARING_AID_IS_WHITE_LISTED, true);
btif_config_save();
},
dev_info));
@@ -1504,8 +1515,11 @@ void btif_storage_add_hearing_aid(const HearingDevice& dev_info) {
/** Loads information about bonded hearing aid devices */
void btif_storage_load_bonded_hearing_aids() {
- for (const auto& bd_addr : btif_config_get_paired_devices()) {
- const std::string& name = bd_addr.ToString();
+ // TODO: this code is not thread safe, it can corrupt config content.
+ // b/67595284
+ for (const section_t& section : btif_config_sections()) {
+ const std::string& name = section.name;
+ if (!RawAddress::IsValidAddress(name)) continue;
int size = STORAGE_UUID_STRING_SIZE * HEARINGAID_MAX_NUM_UUIDS;
char uuid_str[size];
@@ -1529,6 +1543,8 @@ void btif_storage_load_bonded_hearing_aids() {
BTIF_TRACE_DEBUG("Remote device:%s", name.c_str());
if (btif_in_fetch_bonded_device(name) != BT_STATUS_SUCCESS) {
+ RawAddress bd_addr;
+ RawAddress::FromString(name, bd_addr);
btif_storage_remove_hearing_aid(bd_addr);
continue;
}
@@ -1579,9 +1595,12 @@ void btif_storage_load_bonded_hearing_aids() {
if (btif_config_get_int(name, HEARING_AID_PREPARATION_DELAY, &value))
preparation_delay = value;
- uint16_t is_acceptlisted = 0;
- if (btif_config_get_int(name, HEARING_AID_IS_ACCEPTLISTED, &value))
- is_acceptlisted = value;
+ uint16_t is_white_listed = 0;
+ if (btif_config_get_int(name, HEARING_AID_IS_WHITE_LISTED, &value))
+ is_white_listed = value;
+
+ RawAddress bd_addr;
+ RawAddress::FromString(name, bd_addr);
// add extracted information to BTA Hearing Aid
do_in_main_thread(
@@ -1592,7 +1611,7 @@ void btif_storage_load_bonded_hearing_aids() {
audio_status_ccc_handle, service_changed_ccc_handle,
volume_handle, read_psm_handle, hi_sync_id,
render_delay, preparation_delay),
- is_acceptlisted));
+ is_white_listed));
}
}
@@ -1610,16 +1629,16 @@ void btif_storage_remove_hearing_aid(const RawAddress& address) {
btif_config_remove(addrstr, HEARING_AID_SYNC_ID);
btif_config_remove(addrstr, HEARING_AID_RENDER_DELAY);
btif_config_remove(addrstr, HEARING_AID_PREPARATION_DELAY);
- btif_config_remove(addrstr, HEARING_AID_IS_ACCEPTLISTED);
+ btif_config_remove(addrstr, HEARING_AID_IS_WHITE_LISTED);
btif_config_save();
}
-/** Set/Unset the hearing aid device HEARING_AID_IS_ACCEPTLISTED flag. */
-void btif_storage_set_hearing_aid_acceptlist(const RawAddress& address,
- bool add_to_acceptlist) {
+/** Set/Unset the hearing aid device HEARING_AID_IS_WHITE_LISTED flag. */
+void btif_storage_set_hearing_aid_white_list(const RawAddress& address,
+ bool add_to_whitelist) {
std::string addrstr = address.ToString();
- btif_config_set_int(addrstr, HEARING_AID_IS_ACCEPTLISTED, add_to_acceptlist);
+ btif_config_set_int(addrstr, HEARING_AID_IS_WHITE_LISTED, add_to_whitelist);
btif_config_save();
}
@@ -1664,34 +1683,6 @@ bool btif_storage_get_hearing_aid_prop(
return true;
}
-/** Stores information about GATT server supported features */
-void btif_storage_set_gatt_sr_supp_feat(const RawAddress& addr, uint8_t feat) {
- do_in_jni_thread(
- FROM_HERE, Bind(
- [](const RawAddress& addr, uint8_t feat) {
- std::string bdstr = addr.ToString();
- VLOG(2)
- << "GATT server supported features for: " << bdstr
- << " features: " << +feat;
- btif_config_set_int(
- bdstr, BTIF_STORAGE_KEY_GATT_SERVER_SUPPORTED, feat);
- btif_config_save();
- },
- addr, feat));
-}
-
-/** Gets information about GATT server supported features */
-uint8_t btif_storage_get_sr_supp_feat(const RawAddress& bd_addr) {
- auto name = bd_addr.ToString();
-
- int value = 0;
- btif_config_get_int(name, BTIF_STORAGE_KEY_GATT_SERVER_SUPPORTED, &value);
- BTIF_TRACE_DEBUG("Remote device: %s GATT server supported features 0x%02x",
- name.c_str(), value);
-
- return value;
-}
-
/*******************************************************************************
*
* Function btif_storage_is_restricted_device
@@ -1722,13 +1713,18 @@ int btif_storage_get_num_bonded_devices(void) {
*
******************************************************************************/
bt_status_t btif_storage_load_hidd(void) {
- for (const auto& bd_addr : btif_config_get_paired_devices()) {
- auto name = bd_addr.ToString();
+ // TODO: this code is not thread safe, it can corrupt config content.
+ // b/67595284
+ for (const section_t& section : btif_config_sections()) {
+ const std::string& name = section.name;
+ if (!RawAddress::IsValidAddress(name)) continue;
BTIF_TRACE_DEBUG("Remote device:%s", name.c_str());
int value;
if (btif_in_fetch_bonded_device(name) == BT_STATUS_SUCCESS) {
if (btif_config_get_int(name, "HidDeviceCabled", &value)) {
+ RawAddress bd_addr;
+ RawAddress::FromString(name, bd_addr);
BTA_HdAddDevice(bd_addr);
break;
}
@@ -1748,13 +1744,13 @@ bt_status_t btif_storage_load_hidd(void) {
* Returns BT_STATUS_SUCCESS
*
******************************************************************************/
-bt_status_t btif_storage_set_hidd(const RawAddress& remote_bd_addr) {
- std::string remote_device_address_string = remote_bd_addr.ToString();
- for (const auto& bd_addr : btif_config_get_paired_devices()) {
- auto name = bd_addr.ToString();
- if (bd_addr == remote_bd_addr) continue;
- if (btif_in_fetch_bonded_device(name) == BT_STATUS_SUCCESS) {
- btif_config_remove(name, "HidDeviceCabled");
+bt_status_t btif_storage_set_hidd(RawAddress* remote_bd_addr) {
+ std::string remote_device_address_string = remote_bd_addr->ToString();
+ for (const section_t& section : btif_config_sections()) {
+ if (!RawAddress::IsValidAddress(section.name)) continue;
+ if (section.name == remote_device_address_string) continue;
+ if (btif_in_fetch_bonded_device(section.name) == BT_STATUS_SUCCESS) {
+ btif_config_remove(section.name, "HidDeviceCabled");
}
}
@@ -1790,89 +1786,3 @@ bool btif_storage_get_stored_remote_name(const RawAddress& bd_addr,
return (btif_storage_get_remote_device_property(&bd_addr, &property) ==
BT_STATUS_SUCCESS);
}
-
-/** Stores information about GATT Client supported features support */
-void btif_storage_set_gatt_cl_supp_feat(const RawAddress& bd_addr,
- uint8_t feat) {
- do_in_jni_thread(
- FROM_HERE, Bind(
- [](const RawAddress& bd_addr, uint8_t feat) {
- std::string bdstr = bd_addr.ToString();
- VLOG(2)
- << "saving gatt client supported feat: " << bdstr;
- btif_config_set_int(
- bdstr, BTIF_STORAGE_KEY_GATT_CLIENT_SUPPORTED, feat);
- btif_config_save();
- },
- bd_addr, feat));
-}
-
-/** Get client supported features */
-uint8_t btif_storage_get_gatt_cl_supp_feat(const RawAddress& bd_addr) {
- auto name = bd_addr.ToString();
-
- int value = 0;
- btif_config_get_int(name, BTIF_STORAGE_KEY_GATT_CLIENT_SUPPORTED, &value);
- BTIF_TRACE_DEBUG("Remote device: %s GATT client supported features 0x%02x",
- name.c_str(), value);
-
- return value;
-}
-
-/** Remove client supported features */
-void btif_storage_remove_gatt_cl_supp_feat(const RawAddress& bd_addr) {
- do_in_jni_thread(
- FROM_HERE, Bind(
- [](const RawAddress& bd_addr) {
- auto bdstr = bd_addr.ToString();
- if (btif_config_exist(
- bdstr, BTIF_STORAGE_KEY_GATT_CLIENT_SUPPORTED)) {
- btif_config_remove(
- bdstr, BTIF_STORAGE_KEY_GATT_CLIENT_SUPPORTED);
- btif_config_save();
- }
- },
- bd_addr));
-}
-
-/** Store last server database hash for remote client */
-void btif_storage_set_gatt_cl_db_hash(const RawAddress& bd_addr, Octet16 hash) {
- do_in_jni_thread(FROM_HERE, Bind(
- [](const RawAddress& bd_addr, Octet16 hash) {
- auto bdstr = bd_addr.ToString();
- btif_config_set_bin(
- bdstr,
- BTIF_STORAGE_KEY_GATT_CLIENT_DB_HASH,
- hash.data(), hash.size());
- btif_config_save();
- },
- bd_addr, hash));
-}
-
-/** Get last server database hash for remote client */
-Octet16 btif_storage_get_gatt_cl_db_hash(const RawAddress& bd_addr) {
- auto bdstr = bd_addr.ToString();
-
- Octet16 hash;
- size_t size = hash.size();
- btif_config_get_bin(bdstr, BTIF_STORAGE_KEY_GATT_CLIENT_DB_HASH, hash.data(),
- &size);
-
- return hash;
-}
-
-/** Remove las server database hash for remote client */
-void btif_storage_remove_gatt_cl_db_hash(const RawAddress& bd_addr) {
- do_in_jni_thread(FROM_HERE,
- Bind(
- [](const RawAddress& bd_addr) {
- auto bdstr = bd_addr.ToString();
- if (btif_config_exist(
- bdstr, BTIF_STORAGE_KEY_GATT_CLIENT_DB_HASH)) {
- btif_config_remove(
- bdstr, BTIF_STORAGE_KEY_GATT_CLIENT_DB_HASH);
- btif_config_save();
- }
- },
- bd_addr));
-}
diff --git a/btif/src/btif_util.cc b/btif/src/btif_util.cc
index ae49edb59..0aa11428e 100644
--- a/btif/src/btif_util.cc
+++ b/btif/src/btif_util.cc
@@ -116,6 +116,7 @@ const char* dump_dm_search_event(uint16_t event) {
CASE_RETURN_STR(BTA_DM_DISC_RES_EVT)
CASE_RETURN_STR(BTA_DM_DISC_BLE_RES_EVT)
CASE_RETURN_STR(BTA_DM_DISC_CMPL_EVT)
+ CASE_RETURN_STR(BTA_DM_DI_DISC_CMPL_EVT)
CASE_RETURN_STR(BTA_DM_SEARCH_CANCEL_CMPL_EVT)
default:
@@ -143,13 +144,21 @@ const char* dump_property_type(bt_property_type_t type) {
const char* dump_dm_event(uint16_t event) {
switch (event) {
+ CASE_RETURN_STR(BTA_DM_ENABLE_EVT)
+ CASE_RETURN_STR(BTA_DM_DISABLE_EVT)
CASE_RETURN_STR(BTA_DM_PIN_REQ_EVT)
CASE_RETURN_STR(BTA_DM_AUTH_CMPL_EVT)
+ CASE_RETURN_STR(BTA_DM_AUTHORIZE_EVT)
CASE_RETURN_STR(BTA_DM_LINK_UP_EVT)
CASE_RETURN_STR(BTA_DM_LINK_DOWN_EVT)
+ CASE_RETURN_STR(BTA_DM_SIG_STRENGTH_EVT)
+ CASE_RETURN_STR(BTA_DM_BUSY_LEVEL_EVT)
CASE_RETURN_STR(BTA_DM_BOND_CANCEL_CMPL_EVT)
CASE_RETURN_STR(BTA_DM_SP_CFM_REQ_EVT)
CASE_RETURN_STR(BTA_DM_SP_KEY_NOTIF_EVT)
+ CASE_RETURN_STR(BTA_DM_SP_RMT_OOB_EVT)
+ CASE_RETURN_STR(BTA_DM_SP_KEYPRESS_EVT)
+ CASE_RETURN_STR(BTA_DM_ROLE_CHG_EVT)
CASE_RETURN_STR(BTA_DM_BLE_KEY_EVT)
CASE_RETURN_STR(BTA_DM_BLE_SEC_REQ_EVT)
CASE_RETURN_STR(BTA_DM_BLE_PASSKEY_NOTIF_EVT)
@@ -159,6 +168,7 @@ const char* dump_dm_event(uint16_t event) {
CASE_RETURN_STR(BTA_DM_BLE_LOCAL_ER_EVT)
CASE_RETURN_STR(BTA_DM_BLE_AUTH_CMPL_EVT)
CASE_RETURN_STR(BTA_DM_DEV_UNPAIRED_EVT)
+ CASE_RETURN_STR(BTA_DM_HW_ERROR_EVT)
CASE_RETURN_STR(BTA_DM_ENER_INFO_READ)
default:
diff --git a/btif/src/btif_vc.cc b/btif/src/btif_vc.cc
deleted file mode 100644
index bf51eb591..000000000
--- a/btif/src/btif_vc.cc
+++ /dev/null
@@ -1,125 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/* Volume Control Interface */
-
-#include <hardware/bluetooth.h>
-#include <hardware/bt_vc.h>
-
-#include <base/bind.h>
-#include <base/location.h>
-#include <base/logging.h>
-
-#include "bta_vc_api.h"
-#include "btif_common.h"
-#include "stack/include/btu.h"
-
-using base::Bind;
-using base::Unretained;
-using bluetooth::vc::ConnectionState;
-using bluetooth::vc::VolumeControlCallbacks;
-using bluetooth::vc::VolumeControlInterface;
-
-namespace {
-std::unique_ptr<VolumeControlInterface> vc_instance;
-
-class VolumeControlInterfaceImpl : public VolumeControlInterface,
- public VolumeControlCallbacks {
- ~VolumeControlInterfaceImpl() override = default;
-
- void Init(VolumeControlCallbacks* callbacks) override {
- DVLOG(2) << __func__;
- this->callbacks_ = callbacks;
- do_in_main_thread(FROM_HERE, Bind(&VolumeControl::Initialize, this));
- }
-
- void OnConnectionState(ConnectionState state,
- const RawAddress& address) override {
- DVLOG(2) << __func__ << " address: " << address;
- do_in_jni_thread(FROM_HERE, Bind(&VolumeControlCallbacks::OnConnectionState,
- Unretained(callbacks_), state, address));
- }
-
- void OnVolumeStateChanged(const RawAddress& address, uint8_t volume,
- bool mute) override {
- DVLOG(2) << __func__ << " address: " << address << "volume: " << volume
- << "mute: " << mute;
- do_in_jni_thread(FROM_HERE,
- Bind(&VolumeControlCallbacks::OnVolumeStateChanged,
- Unretained(callbacks_), address, volume, mute));
- }
-
- void OnGroupVolumeStateChanged(int group_id, uint8_t volume,
- bool mute) override {
- DVLOG(2) << __func__ << "group_id: " << group_id << "volume: " << volume
- << "mute: " << mute;
- do_in_jni_thread(FROM_HERE,
- Bind(&VolumeControlCallbacks::OnGroupVolumeStateChanged,
- Unretained(callbacks_), group_id, volume, mute));
- }
-
- void Connect(const RawAddress& address) override {
- DVLOG(2) << __func__ << " address: " << address;
- do_in_main_thread(FROM_HERE,
- Bind(&VolumeControl::Connect,
- Unretained(VolumeControl::Get()), address));
- }
-
- void Disconnect(const RawAddress& address) override {
- DVLOG(2) << __func__ << " address: " << address;
- do_in_main_thread(FROM_HERE,
- Bind(&VolumeControl::Disconnect,
- Unretained(VolumeControl::Get()), address));
- }
-
- void SetVolume(std::variant<RawAddress, int> addr_or_group_id,
- uint8_t volume) override {
- DVLOG(2) << __func__ << " volume: " << volume;
- do_in_main_thread(FROM_HERE, Bind(&VolumeControl::SetVolume,
- Unretained(VolumeControl::Get()),
- std::move(addr_or_group_id), volume));
- }
-
- void RemoveDevice(const RawAddress& address) override {
- DVLOG(2) << __func__ << " address: " << address;
-
- /* RemoveDevice can be called on devices that don't have HA enabled */
- if (VolumeControl::IsVolumeControlRunning()) {
- do_in_main_thread(FROM_HERE,
- Bind(&VolumeControl::Disconnect,
- Unretained(VolumeControl::Get()), address));
- }
-
- /* Placeholder: Remove things from storage here */
- }
-
- void Cleanup(void) override {
- DVLOG(2) << __func__;
- do_in_main_thread(FROM_HERE, Bind(&VolumeControl::CleanUp));
- }
-
- private:
- VolumeControlCallbacks* callbacks_;
-};
-
-} /* namespace */
-
-VolumeControlInterface* btif_volume_control_get_interface(void) {
- if (!vc_instance) vc_instance.reset(new VolumeControlInterfaceImpl());
-
- return vc_instance.get();
-}
diff --git a/btif/src/stack_manager.cc b/btif/src/stack_manager.cc
index ab247345d..60c2c0cc0 100644
--- a/btif/src/stack_manager.cc
+++ b/btif/src/stack_manager.cc
@@ -21,10 +21,6 @@
#include "stack_manager.h"
#include <hardware/bluetooth.h>
-#if defined(STATIC_LIBBLUETOOTH)
-#include <cstdlib>
-#include <cstring>
-#endif
#include "btcore/include/module.h"
#include "btcore/include/osi_module.h"
@@ -32,52 +28,14 @@
#include "btif_common.h"
#include "common/message_loop_thread.h"
#include "device/include/controller.h"
-#include "hci/include/btsnoop.h"
-#include "main/shim/shim.h"
#include "osi/include/log.h"
#include "osi/include/osi.h"
#include "osi/include/semaphore.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/btm_client_interface.h"
-#include "stack/include/btu.h"
// Temp includes
#include "bt_utils.h"
-#include "bta/sys/bta_sys.h"
#include "btif_config.h"
#include "btif_profile_queue.h"
-#include "internal_include/bt_target.h"
-#include "internal_include/bte.h"
-#include "stack/include/gatt_api.h"
-#include "stack/include/l2c_api.h"
-#include "stack/include/port_api.h"
-#include "stack/sdp/sdpint.h"
-#if (BNEP_INCLUDED == TRUE)
-#include "stack/include/bnep_api.h"
-#endif
-#include "stack/include/gap_api.h"
-#if (PAN_INCLUDED == TRUE)
-#include "stack/include/pan_api.h"
-#endif
-#include "stack/include/a2dp_api.h"
-#include "stack/include/avrc_api.h"
-#if (HID_HOST_INCLUDED == TRUE)
-#include "stack/include/hidh_api.h"
-#endif
-#include "stack/include/smp_api.h"
-#include "bta_ar_api.h"
-#include "bta/sys/bta_sys_int.h"
-#include "bta_dm_int.h"
-#include "btif/include/btif_pan.h"
-#include "btif/include/btif_sock.h"
-#include "device/include/interop.h"
-#include "internal_include/stack_config.h"
-#include "main/shim/controller.h"
-
-void main_thread_shut_down();
-void main_thread_start_up();
-void BTA_dm_on_hw_on();
-void BTA_dm_on_hw_off();
using bluetooth::common::MessageLoopThread;
@@ -141,93 +99,35 @@ static bool get_stack_is_running() { return stack_is_running; }
// Internal functions
-#ifdef STATIC_LIBBLUETOOTH
-extern const module_t bt_utils_module;
-extern const module_t bte_logmsg_module;
-extern const module_t btif_config_module;
-extern const module_t btsnoop_module;
-extern const module_t bt_utils_module;
-extern const module_t controller_module;
-extern const module_t gd_idle_module;
-extern const module_t gd_shim_module;
-extern const module_t hci_module;
-extern const module_t interop_module;
-extern const module_t osi_module;
-extern const module_t stack_config_module;
-
-struct module_lookup {
- const char* name;
- const module_t* module;
-};
-
-const struct module_lookup module_table[] = {
- {BTE_LOGMSG_MODULE, &bte_logmsg_module},
- {BTIF_CONFIG_MODULE, &btif_config_module},
- {BTSNOOP_MODULE, &btsnoop_module},
- {BT_UTILS_MODULE, &bt_utils_module},
- {CONTROLLER_MODULE, &controller_module},
- {GD_IDLE_MODULE, &gd_idle_module},
- {GD_SHIM_MODULE, &gd_shim_module},
- {HCI_MODULE, &hci_module},
- {INTEROP_MODULE, &interop_module},
- {OSI_MODULE, &osi_module},
- {STACK_CONFIG_MODULE, &stack_config_module},
- {NULL, NULL},
-};
-
-inline const module_t* get_local_module(const char* name) {
- size_t len = strlen(name);
-
- for (const struct module_lookup* l = module_table; l->module; l++) {
- if (strncmp(l->name, name, len) == 0) {
- return l->module;
- }
- }
-
- abort();
- return nullptr;
-}
-#else
-inline const module_t* get_local_module(const char* name) {
- return get_module(name);
-}
-#endif
-
// Synchronous function to initialize the stack
static void event_init_stack(void* context) {
semaphore_t* semaphore = (semaphore_t*)context;
- LOG_INFO("is initializing the stack");
+ LOG_INFO(LOG_TAG, "%s is initializing the stack", __func__);
if (stack_is_initialized) {
- LOG_INFO("found the stack already in initialized state");
+ LOG_INFO(LOG_TAG, "%s found the stack already in initialized state",
+ __func__);
} else {
module_management_start();
- module_init(get_local_module(OSI_MODULE));
- module_init(get_local_module(BT_UTILS_MODULE));
- if (bluetooth::shim::is_any_gd_enabled()) {
- module_start_up(get_local_module(GD_IDLE_MODULE));
- }
- module_init(get_local_module(BTIF_CONFIG_MODULE));
+ module_init(get_module(OSI_MODULE));
+ module_init(get_module(BT_UTILS_MODULE));
+ module_init(get_module(BTIF_CONFIG_MODULE));
btif_init_bluetooth();
- module_init(get_local_module(INTEROP_MODULE));
- bte_main_init();
- module_init(get_local_module(STACK_CONFIG_MODULE));
-
// stack init is synchronous, so no waiting necessary here
stack_is_initialized = true;
}
- LOG_INFO("finished");
+ LOG_INFO(LOG_TAG, "%s finished", __func__);
if (semaphore) semaphore_post(semaphore);
}
static void ensure_stack_is_initialized() {
if (!stack_is_initialized) {
- LOG_WARN("%s found the stack was uninitialized. Initializing now.",
+ LOG_WARN(LOG_TAG, "%s found the stack was uninitialized. Initializing now.",
__func__);
// No semaphore needed since we are calling it directly
event_init_stack(nullptr);
@@ -237,146 +137,62 @@ static void ensure_stack_is_initialized() {
// Synchronous function to start up the stack
static void event_start_up_stack(UNUSED_ATTR void* context) {
if (stack_is_running) {
- LOG_INFO("%s stack already brought up", __func__);
+ LOG_INFO(LOG_TAG, "%s stack already brought up", __func__);
return;
}
ensure_stack_is_initialized();
- LOG_INFO("%s is bringing up the stack", __func__);
+ LOG_INFO(LOG_TAG, "%s is bringing up the stack", __func__);
future_t* local_hack_future = future_new();
hack_future = local_hack_future;
- if (bluetooth::shim::is_any_gd_enabled()) {
- LOG_INFO("%s Gd shim module enabled", __func__);
- module_shut_down(get_local_module(GD_IDLE_MODULE));
- module_start_up(get_local_module(GD_SHIM_MODULE));
- module_start_up(get_local_module(BTIF_CONFIG_MODULE));
- } else {
- module_start_up(get_local_module(BTIF_CONFIG_MODULE));
- module_start_up(get_local_module(BTSNOOP_MODULE));
- module_start_up(get_local_module(HCI_MODULE));
- }
-
- get_btm_client_interface().lifecycle.btm_init();
- l2c_init();
- sdp_init();
- gatt_init();
- SMP_Init();
- get_btm_client_interface().lifecycle.btm_ble_init();
-
- RFCOMM_Init();
-#if (BNEP_INCLUDED == TRUE)
- BNEP_Init();
-#if (PAN_INCLUDED == TRUE)
- PAN_Init();
-#endif /* PAN */
-#endif /* BNEP Included */
- A2DP_Init();
- AVRC_Init();
- GAP_Init();
-#if (HID_HOST_INCLUDED == TRUE)
- HID_HostInit();
-#endif
-
- bta_sys_init();
- bta_ar_init();
- module_init(get_local_module(BTE_LOGMSG_MODULE));
-
- main_thread_start_up();
-
- btif_init_ok();
- BTA_dm_init();
- bta_dm_enable(bte_dm_evt);
-
- bta_set_forward_hw_failures(true);
- btm_acl_device_down();
- if (bluetooth::shim::is_gd_controller_enabled()) {
- CHECK(module_start_up(get_local_module(GD_CONTROLLER_MODULE)));
- } else {
- CHECK(module_start_up(get_local_module(CONTROLLER_MODULE)));
- }
- BTM_reset_complete();
-
- BTA_dm_on_hw_on();
+ // Include this for now to put btif config into a shutdown-able state
+ module_start_up(get_module(BTIF_CONFIG_MODULE));
+ bte_main_enable();
if (future_await(local_hack_future) != FUTURE_SUCCESS) {
- LOG_ERROR("%s failed to start up the stack", __func__);
+ LOG_ERROR(LOG_TAG, "%s failed to start up the stack", __func__);
stack_is_running = true; // So stack shutdown actually happens
event_shut_down_stack(nullptr);
return;
}
stack_is_running = true;
- LOG_INFO("%s finished", __func__);
+ LOG_INFO(LOG_TAG, "%s finished", __func__);
do_in_jni_thread(FROM_HERE, base::Bind(event_signal_stack_up, nullptr));
}
// Synchronous function to shut down the stack
static void event_shut_down_stack(UNUSED_ATTR void* context) {
if (!stack_is_running) {
- LOG_INFO("%s stack is already brought down", __func__);
+ LOG_INFO(LOG_TAG, "%s stack is already brought down", __func__);
return;
}
- LOG_INFO("%s is bringing down the stack", __func__);
+ LOG_INFO(LOG_TAG, "%s is bringing down the stack", __func__);
future_t* local_hack_future = future_new();
hack_future = local_hack_future;
stack_is_running = false;
- do_in_main_thread(FROM_HERE, base::Bind(&btm_ble_multi_adv_cleanup));
-
- btif_dm_on_disable();
- btif_sock_cleanup();
- btif_pan_cleanup();
-
- do_in_main_thread(FROM_HERE, base::Bind(bta_dm_disable));
+ btif_disable_bluetooth();
+ module_shut_down(get_module(BTIF_CONFIG_MODULE));
future_await(local_hack_future);
- local_hack_future = future_new();
- hack_future = local_hack_future;
-
- bta_sys_disable();
- bta_set_forward_hw_failures(false);
- BTA_dm_on_hw_off();
-
- module_shut_down(get_local_module(BTIF_CONFIG_MODULE));
-
- future_await(local_hack_future);
-
- main_thread_shut_down();
-
- module_clean_up(get_local_module(BTE_LOGMSG_MODULE));
-
- gatt_free();
- l2c_free();
- sdp_free();
- get_btm_client_interface().lifecycle.btm_ble_free();
- get_btm_client_interface().lifecycle.btm_free();
-
- if (bluetooth::shim::is_any_gd_enabled()) {
- LOG_INFO("%s Gd shim module disabled", __func__);
- module_shut_down(get_local_module(GD_SHIM_MODULE));
- module_start_up(get_local_module(GD_IDLE_MODULE));
- } else {
- module_shut_down(get_local_module(HCI_MODULE));
- module_shut_down(get_local_module(BTSNOOP_MODULE));
- }
-
- module_shut_down(
- get_local_module(CONTROLLER_MODULE)); // Doesn't do any work, just
- // puts it in a restartable
- // state
+ module_shut_down(get_module(CONTROLLER_MODULE)); // Doesn't do any work, just
+ // puts it in a restartable
+ // state
hack_future = future_new();
do_in_jni_thread(FROM_HERE, base::Bind(event_signal_stack_down, nullptr));
future_await(hack_future);
- LOG_INFO("%s finished", __func__);
+ LOG_INFO(LOG_TAG, "%s finished", __func__);
}
static void ensure_stack_is_not_running() {
if (stack_is_running) {
- LOG_WARN("%s found the stack was still running. Bringing it down now.",
+ LOG_WARN(LOG_TAG,
+ "%s found the stack was still running. Bringing it down now.",
__func__);
event_shut_down_stack(nullptr);
}
@@ -385,26 +201,21 @@ static void ensure_stack_is_not_running() {
// Synchronous function to clean up the stack
static void event_clean_up_stack(void* context) {
if (!stack_is_initialized) {
- LOG_INFO("%s found the stack already in a clean state", __func__);
+ LOG_INFO(LOG_TAG, "%s found the stack already in a clean state", __func__);
goto cleanup;
}
ensure_stack_is_not_running();
- LOG_INFO("%s is cleaning up the stack", __func__);
+ LOG_INFO(LOG_TAG, "%s is cleaning up the stack", __func__);
stack_is_initialized = false;
btif_cleanup_bluetooth();
-
- module_clean_up(get_local_module(STACK_CONFIG_MODULE));
- module_clean_up(get_local_module(INTEROP_MODULE));
-
- module_clean_up(get_local_module(BTIF_CONFIG_MODULE));
- module_clean_up(get_local_module(BT_UTILS_MODULE));
- module_clean_up(get_local_module(OSI_MODULE));
- module_shut_down(get_local_module(GD_IDLE_MODULE));
+ module_clean_up(get_module(BTIF_CONFIG_MODULE));
+ module_clean_up(get_module(BT_UTILS_MODULE));
+ module_clean_up(get_module(OSI_MODULE));
module_management_stop();
- LOG_INFO("%s finished", __func__);
+ LOG_INFO(LOG_TAG, "%s finished", __func__);
cleanup:;
semaphore_t* semaphore = (semaphore_t*)context;
@@ -415,11 +226,11 @@ static void event_signal_stack_up(UNUSED_ATTR void* context) {
// Notify BTIF connect queue that we've brought up the stack. It's
// now time to dispatch all the pending profile connect requests.
btif_queue_connect_next();
- invoke_adapter_state_changed_cb(BT_STATE_ON);
+ HAL_CBACK(bt_hal_cbacks, adapter_state_changed_cb, BT_STATE_ON);
}
static void event_signal_stack_down(UNUSED_ATTR void* context) {
- invoke_adapter_state_changed_cb(BT_STATE_OFF);
+ HAL_CBACK(bt_hal_cbacks, adapter_state_changed_cb, BT_STATE_OFF);
future_ready(stack_manager_get_hack_future(), FUTURE_SUCCESS);
}
@@ -428,7 +239,7 @@ static void ensure_manager_initialized() {
management_thread.StartUp();
if (!management_thread.IsRunning()) {
- LOG_ERROR("%s unable to start stack management thread", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to start stack management thread", __func__);
return;
}
}
diff --git a/btif/test/btif_config_cache_test.cc b/btif/test/btif_config_cache_test.cc
index b7c0e9b40..aaccf8c0c 100644
--- a/btif/test/btif_config_cache_test.cc
+++ b/btif/test/btif_config_cache_test.cc
@@ -483,9 +483,8 @@ TEST(BtifConfigCacheTest, test_PersistentSectionCopy_Init) {
// check GetPersistentSections
int num_of_paired_devices = 0;
- for (const auto& sec_name :
- test_btif_config_cache.GetPersistentSectionNames()) {
- EXPECT_TRUE(test_btif_config_cache.HasPersistentSection(sec_name));
+ for (const section_t& sec : test_btif_config_cache.GetPersistentSections()) {
+ EXPECT_TRUE(test_btif_config_cache.HasPersistentSection(sec.name));
num_of_paired_devices++;
}
EXPECT_EQ(num_of_paired_devices, 3);
diff --git a/btif/test/btif_hf_client_service_test.cc b/btif/test/btif_hf_client_service_test.cc
index db48af146..6844e86be 100644..100755
--- a/btif/test/btif_hf_client_service_test.cc
+++ b/btif/test/btif_hf_client_service_test.cc
@@ -1,37 +1,31 @@
#include <base/logging.h>
#include <gtest/gtest.h>
-#include "bta_hfp_api.h"
#undef LOG_TAG
#include "btif/src/btif_hf_client.cc"
static tBTA_HF_CLIENT_FEAT gFeatures;
-
uint8_t btif_trace_level = BT_TRACE_LEVEL_WARNING;
void LogMsg(uint32_t trace_set_mask, const char* fmt_str, ...) {}
-tBTA_STATUS BTA_HfClientEnable(tBTA_HF_CLIENT_CBACK* p_cback,
+tBTA_STATUS BTA_HfClientEnable(tBTA_HF_CLIENT_CBACK* p_cback, tBTA_SEC sec_mask,
tBTA_HF_CLIENT_FEAT features,
const char* p_service_name) {
gFeatures = features;
return BTA_SUCCESS;
}
-void BTA_HfClientDisable(void) { }
+void BTA_HfClientDisable(void) {}
bt_status_t btif_transfer_context(tBTIF_CBACK* p_cback, uint16_t event,
char* p_params, int param_len,
tBTIF_COPY_CBACK* p_copy_cback) {
return BT_STATUS_SUCCESS;
}
void btif_queue_advance() {}
-const char* dump_hf_client_event(uint16_t event) {
- return "UNKNOWN MSG ID";
-}
+const char* dump_hf_client_event(uint16_t event) { return "UNKNOWN MSG ID"; }
class BtifHfClientTest : public ::testing::Test {
protected:
- void SetUp() override {
- gFeatures = BTIF_HF_CLIENT_FEATURES;
- }
+ void SetUp() override { gFeatures = BTIF_HF_CLIENT_FEATURES; }
void TearDown() override {}
};
@@ -39,7 +33,10 @@ class BtifHfClientTest : public ::testing::Test {
TEST_F(BtifHfClientTest, test_btif_hf_cleint_service) {
bool enable = true;
+ osi_property_set("persist.bluetooth.hfpclient.sco_s4_supported", "true");
+ btif_hf_client_execute_service(enable);
+ EXPECT_TRUE(gFeatures & BTA_HF_CLIENT_FEAT_S4);
+ osi_property_set("persist.bluetooth.hfpclient.sco_s4_supported", "false");
btif_hf_client_execute_service(enable);
- ASSERT_EQ((gFeatures & BTA_HF_CLIENT_FEAT_ESCO_S4) > 0,
- BTA_HFP_VERSION >= HFP_VERSION_1_7);
+ EXPECT_FALSE(gFeatures & BTA_HF_CLIENT_FEAT_S4);
}
diff --git a/btif/test/btif_rc_test.cc b/btif/test/btif_rc_test.cc
index c90b424d6..6271881c9 100644
--- a/btif/test/btif_rc_test.cc
+++ b/btif/test/btif_rc_test.cc
@@ -92,7 +92,7 @@ bt_status_t do_in_jni_thread(const base::Location& from_here,
base::OnceClosure task) {
return BT_STATUS_SUCCESS;
}
-bluetooth::common::MessageLoopThread* get_main_thread() { return nullptr; }
+base::MessageLoop* get_main_message_loop() { return nullptr; }
bool interop_match_addr(const interop_feature_t feature,
const RawAddress* addr) {
return false;
diff --git a/btif/test/btif_stack_test.cc b/btif/test/btif_stack_test.cc
deleted file mode 100644
index 8b3cfae09..000000000
--- a/btif/test/btif_stack_test.cc
+++ /dev/null
@@ -1,206 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "btif/include/btif_profile_queue.h"
-
-#include <gtest/gtest.h>
-
-#include <base/bind.h>
-#include <base/callback.h>
-#include <base/location.h>
-#include "stack_manager.h"
-#include "types/raw_address.h"
-
-#include "bta/include/bta_ag_api.h" // tBTA_AG_RES_DATA::kEmpty
-#include "hci/include/hci_layer.h" // hci_t
-#include "test/mock/mock_hci_layer.h"
-
-std::map<std::string, int> mock_function_count_map;
-
-void set_hal_cbacks(bt_callbacks_t* callbacks); // btif/src/bluetooth.cc
-
-// tLEGACY_TRACE_LEVEL
-uint8_t btu_trace_level = 6;
-uint8_t appl_trace_level = 6;
-uint8_t btif_trace_level = 6;
-
-namespace {
-
-void dump_mock_function_count_map() {
- LOG_INFO("Mock function count map size:%zu", mock_function_count_map.size());
-
- for (auto it : mock_function_count_map) {
- LOG_INFO("function:%s: call_count:%d", it.first.c_str(), it.second);
- }
-}
-
-namespace _adapter_state_changed {
-bt_state_t state{BT_STATE_OFF};
-}
-void adapter_state_changed(bt_state_t state) {
- LOG_INFO("%u => %u", _adapter_state_changed::state, state);
-}
-
-void adapter_properties(bt_status_t status, int num_properties,
- bt_property_t* properties) {
- LOG_INFO("Callback rx");
-}
-
-void remote_device_properties(bt_status_t status, RawAddress* bd_addr,
- int num_properties, bt_property_t* properties) {
- LOG_INFO("Callback rx");
-}
-
-void device_found(int num_properties, bt_property_t* properties) {
- LOG_INFO("Callback rx");
-}
-
-void discovery_state_changed(bt_discovery_state_t state) {
- LOG_INFO("Callback rx");
-}
-
-/** Bluetooth Legacy PinKey Request callback */
-void pin_request(RawAddress* remote_bd_addr, bt_bdname_t* bd_name, uint32_t cod,
- bool min_16_digit) {
- LOG_INFO("Callback rx");
-}
-
-void ssp_request(RawAddress* remote_bd_addr, bt_bdname_t* bd_name, uint32_t cod,
- bt_ssp_variant_t pairing_variant, uint32_t pass_key) {
- LOG_INFO("Callback rx");
-}
-
-/** Bluetooth Bond state changed callback */
-/* Invoked in response to create_bond, cancel_bond or remove_bond */
-void bond_state_changed(bt_status_t status, RawAddress* remote_bd_addr,
- bt_bond_state_t state) {
- LOG_INFO("Callback rx");
-}
-
-/** Bluetooth ACL connection state changed callback */
-void acl_state_changed(bt_status_t status, RawAddress* remote_bd_addr,
- bt_acl_state_t state, bt_hci_error_code_t hci_reason) {
- LOG_INFO("status:%s device:%s state:%s", bt_status_text(status).c_str(),
- remote_bd_addr->ToString().c_str(),
- (state) ? "disconnected" : "connected");
-}
-
-/** Bluetooth Link Quality Report callback */
-void link_quality_report(uint64_t timestamp, int report_id, int rssi, int snr,
- int retransmission_count,
- int packets_not_receive_count,
- int negative_acknowledgement_count) {
- LOG_INFO("Callback rx");
-}
-
-void thread_event(bt_cb_thread_evt evt) { LOG_INFO("Callback rx"); }
-
-void dut_mode_recv(uint16_t opcode, uint8_t* buf, uint8_t len) {
- LOG_INFO("Callback rx");
-}
-
-void le_test_mode(bt_status_t status, uint16_t num_packets) {
- LOG_INFO("Callback rx");
-}
-
-void energy_info(bt_activity_energy_info* energy_info,
- bt_uid_traffic_t* uid_data) {
- LOG_INFO("Callback rx");
-}
-
-bt_callbacks_t bt_callbacks{
- /** set to sizeof(bt_callbacks_t) */
- .size = sizeof(bt_callbacks_t),
- .adapter_state_changed_cb = adapter_state_changed,
- .adapter_properties_cb = adapter_properties,
- .remote_device_properties_cb = remote_device_properties,
- .device_found_cb = device_found,
- .discovery_state_changed_cb = discovery_state_changed,
- .pin_request_cb = pin_request,
- .ssp_request_cb = ssp_request,
- .bond_state_changed_cb = bond_state_changed,
- .acl_state_changed_cb = acl_state_changed,
- .thread_evt_cb = thread_event,
- .dut_mode_recv_cb = dut_mode_recv,
- .le_test_mode_cb = le_test_mode,
- .energy_info_cb = energy_info,
- .link_quality_report_cb = link_quality_report,
-};
-
-void set_data_cb(
- base::Callback<void(const base::Location&, BT_HDR*)> send_data_cb) {
- mock_function_count_map[__func__]++;
-}
-
-void transmit_command(BT_HDR* command, command_complete_cb complete_callback,
- command_status_cb status_cb, void* context) {
- mock_function_count_map[__func__]++;
-}
-
-future_t* transmit_command_futured(BT_HDR* command) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-
-void transmit_downward(uint16_t type, void* data) {
- mock_function_count_map[__func__]++;
-}
-
-} // namespace
-
-hci_t mock_hci = {
- .set_data_cb = set_data_cb,
- .transmit_command = transmit_command,
- .transmit_command_futured = transmit_command_futured,
- .transmit_downward = transmit_downward,
-};
-
-bool is_bluetooth_uid() { return false; }
-const tBTA_AG_RES_DATA tBTA_AG_RES_DATA::kEmpty = {};
-
-namespace bluetooth {
-namespace common {
-
-class BluetoothMetricsLogger {};
-
-} // namespace common
-} // namespace bluetooth
-
-class StackCycleTest : public ::testing::Test {
- protected:
- void SetUp() override {
- test::mock::hci_layer::hci_layer_get_interface.hci = &mock_hci;
- stack_manager_ = stack_manager_get_interface();
- }
-
- void TearDown() override { stack_manager_ = nullptr; }
- const stack_manager_t* stack_manager_{nullptr};
-};
-
-TEST_F(StackCycleTest, stack_init) {
- // TODO load init flags
- // bluetooth::common::InitFlags::Load(init_flags);
-
- set_hal_cbacks(&bt_callbacks);
-
- stack_manager_get_interface()->init_stack();
-
- LOG_INFO("Initialized stack");
-
- ASSERT_EQ(1, mock_function_count_map["set_data_cb"]);
-
- dump_mock_function_count_map();
-}
diff --git a/build.py b/build.py
deleted file mode 100755
index c6cbabd36..000000000
--- a/build.py
+++ /dev/null
@@ -1,458 +0,0 @@
-#!/usr/bin/env python3
-
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-""" Build BT targets on the host system.
-
-For building, you will first have to stage a platform directory that has the
-following structure:
-|-common-mk
-|-bt
-|-external
-|-|-rust
-|-|-|-vendor
-
-The simplest way to do this is to check out platform2 to another directory (that
-is not a subdir of this bt directory), symlink bt there and symlink the rust
-vendor repository as well.
-"""
-import argparse
-import multiprocessing
-import os
-import shutil
-import six
-import subprocess
-import sys
-
-# Use flags required by common-mk (find -type f | grep -nE 'use[.]' {})
-COMMON_MK_USES = [
- 'asan',
- 'coverage',
- 'cros_host',
- 'fuzzer',
- 'fuzzer',
- 'msan',
- 'profiling',
- 'tcmalloc',
- 'test',
- 'ubsan',
-]
-
-# Default use flags.
-USE_DEFAULTS = {
- 'android': False,
- 'bt_nonstandard_codecs': False,
- 'test': False,
-}
-
-VALID_TARGETS = [
- 'prepare', # Prepare the output directory (gn gen + rust setup)
- 'tools', # Build the host tools (i.e. packetgen)
- 'rust', # Build only the rust components + copy artifacts to output dir
- 'main', # Build the main C++ codebase
- 'test', # Run the unit tests
- 'clean', # Clean up output directory
- 'all', # All targets except test and clean
-]
-
-HOST_TESTS = [
- 'bluetooth_test_common',
- 'bluetoothtbd_test',
- 'net_test_avrcp',
- 'net_test_btcore',
- 'net_test_types',
- 'net_test_btm_iso',
- 'net_test_btpackets',
-]
-
-
-class UseFlags():
-
- def __init__(self, use_flags):
- """ Construct the use flags.
-
- Args:
- use_flags: List of use flags parsed from the command.
- """
- self.flags = {}
-
- # Import use flags required by common-mk
- for use in COMMON_MK_USES:
- self.set_flag(use, False)
-
- # Set our defaults
- for use, value in USE_DEFAULTS.items():
- self.set_flag(use, value)
-
- # Set use flags - value is set to True unless the use starts with -
- # All given use flags always override the defaults
- for use in use_flags:
- value = not use.startswith('-')
- self.set_flag(use, value)
-
- def set_flag(self, key, value=True):
- setattr(self, key, value)
- self.flags[key] = value
-
-
-class HostBuild():
-
- def __init__(self, args):
- """ Construct the builder.
-
- Args:
- args: Parsed arguments from ArgumentParser
- """
- self.args = args
-
- # Set jobs to number of cpus unless explicitly set
- self.jobs = self.args.jobs
- if not self.jobs:
- self.jobs = multiprocessing.cpu_count()
- print("Number of jobs = {}".format(self.jobs))
-
- # Normalize all directories
- self.output_dir = os.path.abspath(self.args.output)
- self.platform_dir = os.path.abspath(self.args.platform_dir)
- self.sysroot = self.args.sysroot
- self.use_board = os.path.abspath(self.args.use_board) if self.args.use_board else None
- self.libdir = self.args.libdir
-
- # If default target isn't set, build everything
- self.target = 'all'
- if hasattr(self.args, 'target') and self.args.target:
- self.target = self.args.target
-
- target_use = self.args.use if self.args.use else []
-
- # Unless set, always build test code
- if not self.args.notest:
- target_use.append('test')
-
- self.use = UseFlags(target_use)
-
- # Validate platform directory
- assert os.path.isdir(self.platform_dir), 'Platform dir does not exist'
- assert os.path.isfile(os.path.join(self.platform_dir, '.gn')), 'Platform dir does not have .gn at root'
-
- # Make sure output directory exists (or create it)
- os.makedirs(self.output_dir, exist_ok=True)
-
- # Set some default attributes
- self.libbase_ver = None
-
- self.configure_environ()
-
- def _generate_rustflags(self):
- """ Rustflags to include for the build.
- """
- rust_flags = [
- '-L',
- '{}/out/Default/'.format(self.output_dir),
- '-C',
- 'link-arg=-Wl,--allow-multiple-definition',
- ]
-
- return ' '.join(rust_flags)
-
- def configure_environ(self):
- """ Configure environment variables for GN and Cargo.
- """
- self.env = os.environ.copy()
-
- # Make sure cargo home dir exists and has a bin directory
- cargo_home = os.path.join(self.output_dir, 'cargo_home')
- os.makedirs(cargo_home, exist_ok=True)
- os.makedirs(os.path.join(cargo_home, 'bin'), exist_ok=True)
-
- # Configure Rust env variables
- self.env['CARGO_TARGET_DIR'] = self.output_dir
- self.env['CARGO_HOME'] = os.path.join(self.output_dir, 'cargo_home')
- self.env['RUSTFLAGS'] = self._generate_rustflags()
-
- # Configure some GN variables
- if self.use_board:
- self.env['PKG_CONFIG_PATH'] = os.path.join(self.use_board, self.libdir, 'pkgconfig')
- libdir = os.path.join(self.use_board, self.libdir)
- if self.env.get('LIBRARY_PATH'):
- libpath = self.env['LIBRARY_PATH']
- self.env['LIBRARY_PATH'] = '{}:{}'.format(libdir, libpath)
- else:
- self.env['LIBRARY_PATH'] = libdir
-
- def run_command(self, target, args, cwd=None, env=None):
- """ Run command and stream the output.
- """
- # Set some defaults
- if not cwd:
- cwd = self.platform_dir
- if not env:
- env = self.env
-
- log_file = os.path.join(self.output_dir, '{}.log'.format(target))
- with open(log_file, 'wb') as lf:
- rc = 0
- process = subprocess.Popen(args, cwd=cwd, env=env, stdout=subprocess.PIPE)
- while True:
- line = process.stdout.readline()
- print(line.decode('utf-8'), end="")
- lf.write(line)
- if not line:
- rc = process.poll()
- if rc is not None:
- break
-
- time.sleep(0.1)
-
- if rc != 0:
- raise Exception("Return code is {}".format(rc))
-
- def _get_basever(self):
- if self.libbase_ver:
- return self.libbase_ver
-
- self.libbase_ver = os.environ.get('BASE_VER', '')
- if not self.libbase_ver:
- base_file = os.path.join(self.sysroot, 'usr/share/libchrome/BASE_VER')
- try:
- with open(base_file, 'r') as f:
- self.libbase_ver = f.read().strip('\n')
- except:
- self.libbase_ver = 'NOT-INSTALLED'
-
- return self.libbase_ver
-
- def _gn_default_output(self):
- return os.path.join(self.output_dir, 'out/Default')
-
- def _gn_configure(self):
- """ Configure all required parameters for platform2.
-
- Mostly copied from //common-mk/platform2.py
- """
- clang = self.args.clang
-
- def to_gn_string(s):
- return '"%s"' % s.replace('"', '\\"')
-
- def to_gn_list(strs):
- return '[%s]' % ','.join([to_gn_string(s) for s in strs])
-
- def to_gn_args_args(gn_args):
- for k, v in gn_args.items():
- if isinstance(v, bool):
- v = str(v).lower()
- elif isinstance(v, list):
- v = to_gn_list(v)
- elif isinstance(v, six.string_types):
- v = to_gn_string(v)
- else:
- raise AssertionError('Unexpected %s, %r=%r' % (type(v), k, v))
- yield '%s=%s' % (k.replace('-', '_'), v)
-
- gn_args = {
- 'platform_subdir': 'bt',
- 'cc': 'clang' if clang else 'gcc',
- 'cxx': 'clang++' if clang else 'g++',
- 'ar': 'llvm-ar' if clang else 'ar',
- 'pkg-config': 'pkg-config',
- 'clang_cc': clang,
- 'clang_cxx': clang,
- 'OS': 'linux',
- 'sysroot': self.sysroot,
- 'libdir': os.path.join(self.sysroot, self.libdir),
- 'build_root': self.output_dir,
- 'platform2_root': self.platform_dir,
- 'libbase_ver': self._get_basever(),
- 'enable_exceptions': os.environ.get('CXXEXCEPTIONS', 0) == '1',
- 'external_cflags': [],
- 'external_cxxflags': [],
- 'enable_werror': False,
- }
-
- if clang:
- # Make sure to mark the clang use flag as true
- self.use.set_flag('clang', True)
- gn_args['external_cxxflags'] += ['-I/usr/include/']
-
- # EXTREME HACK ALERT
- #
- # In my laziness, I am supporting building against an already built
- # sysroot path (i.e. chromeos board) so that I don't have to build
- # libchrome or modp_b64 locally.
- if self.use_board:
- includedir = os.path.join(self.use_board, 'usr/include')
- gn_args['external_cxxflags'] += [
- '-I{}'.format(includedir),
- '-I{}/libchrome'.format(includedir),
- '-I{}/gtest'.format(includedir),
- '-I{}/gmock'.format(includedir),
- '-I{}/modp_b64'.format(includedir),
- ]
- gn_args_args = list(to_gn_args_args(gn_args))
- use_args = ['%s=%s' % (k, str(v).lower()) for k, v in self.use.flags.items()]
- gn_args_args += ['use={%s}' % (' '.join(use_args))]
-
- gn_args = [
- 'gn',
- 'gen',
- ]
-
- if self.args.verbose:
- gn_args.append('-v')
-
- gn_args += [
- '--root=%s' % self.platform_dir,
- '--args=%s' % ' '.join(gn_args_args),
- self._gn_default_output(),
- ]
-
- if 'PKG_CONFIG_PATH' in self.env:
- print('DEBUG: PKG_CONFIG_PATH is', self.env['PKG_CONFIG_PATH'])
-
- self.run_command('configure', gn_args)
-
- def _gn_build(self, target):
- """ Generate the ninja command for the target and run it.
- """
- args = ['%s:%s' % ('bt', target)]
- ninja_args = ['ninja', '-C', self._gn_default_output()]
- if self.jobs:
- ninja_args += ['-j', str(self.jobs)]
- ninja_args += args
-
- if self.args.verbose:
- ninja_args.append('-v')
-
- self.run_command('build', ninja_args)
-
- def _rust_configure(self):
- """ Generate config file at cargo_home so we use vendored crates.
- """
- template = """
- [source.systembt]
- directory = "{}/external/rust/vendor"
-
- [source.crates-io]
- replace-with = "systembt"
- local-registry = "/nonexistent"
- """
-
- if self.args.vendored_rust:
- contents = template.format(self.platform_dir)
- with open(os.path.join(self.env['CARGO_HOME'], 'config'), 'w') as f:
- f.write(contents)
-
- def _rust_build(self):
- """ Run `cargo build` from platform2/bt directory.
- """
- self.run_command('rust', ['cargo', 'build'], cwd=os.path.join(self.platform_dir, 'bt'), env=self.env)
-
- def _target_prepare(self):
- """ Target to prepare the output directory for building.
-
- This runs gn gen to generate all rquired files and set up the Rust
- config properly. This will be run
- """
- self._gn_configure()
- self._rust_configure()
-
- def _target_tools(self):
- """ Build the tools target in an already prepared environment.
- """
- self._gn_build('tools')
-
- # Also copy bluetooth_packetgen to CARGO_HOME so it's available
- shutil.copy(
- os.path.join(self._gn_default_output(), 'bluetooth_packetgen'), os.path.join(self.env['CARGO_HOME'], 'bin'))
-
- def _target_rust(self):
- """ Build rust artifacts in an already prepared environment.
- """
- self._rust_build()
- rust_dir = os.path.join(self._gn_default_output(), 'rust')
- if os.path.exists(rust_dir):
- shutil.rmtree(rust_dir)
- shutil.copytree(os.path.join(self.output_dir, 'debug'), rust_dir)
-
- def _target_main(self):
- """ Build the main GN artifacts in an already prepared environment.
- """
- self._gn_build('all')
-
- def _target_test(self):
- """ Runs the host tests.
- """
- # Rust tests first
- self.run_command('test', ['cargo', 'test'], cwd=os.path.join(self.platform_dir, 'bt'), env=self.env)
-
- # Host tests second based on host test list
- for t in HOST_TESTS:
- self.run_command(
- 'test', [os.path.join(self.output_dir, 'out/Default', t)],
- cwd=os.path.join(self.output_dir),
- env=self.env)
-
- def _target_clean(self):
- """ Delete the output directory entirely.
- """
- shutil.rmtree(self.output_dir)
-
- def _target_all(self):
- """ Build all common targets (skipping test and clean).
- """
- self._target_prepare()
- self._target_tools()
- self._target_main()
- self._target_rust()
-
- def build(self):
- """ Builds according to self.target
- """
- print('Building target ', self.target)
-
- if self.target == 'prepare':
- self._target_prepare()
- elif self.target == 'tools':
- self._target_tools()
- elif self.target == 'rust':
- self._target_rust()
- elif self.target == 'main':
- self._target_main()
- elif self.target == 'test':
- self._target_test()
- elif self.target == 'clean':
- self._target_clean()
- elif self.target == 'all':
- self._target_all()
-
-
-if __name__ == '__main__':
- parser = argparse.ArgumentParser(description='Simple build for host.')
- parser.add_argument('--output', help='Output directory for the build.', required=True)
- parser.add_argument('--platform-dir', help='Directory where platform2 is staged.', required=True)
- parser.add_argument('--clang', help='Use clang compiler.', default=False, action='store_true')
- parser.add_argument('--use', help='Set a specific use flag.')
- parser.add_argument('--notest', help="Don't compile test code.", default=False, action='store_true')
- parser.add_argument('--target', help='Run specific build target')
- parser.add_argument('--sysroot', help='Set a specific sysroot path', default='/')
- parser.add_argument('--libdir', help='Libdir - default = usr/lib64', default='usr/lib64')
- parser.add_argument('--use-board', help='Use a built x86 board for dependencies. Provide path.')
- parser.add_argument('--jobs', help='Number of jobs to run', default=0, type=int)
- parser.add_argument('--vendored-rust', help='Use vendored rust crates', default=False, action='store_true')
- parser.add_argument('--verbose', help='Verbose logs for build.')
-
- args = parser.parse_args()
- build = HostBuild(args)
- build.build()
diff --git a/build/Android.bp b/build/Android.bp
index 9d423422d..32c0f31c0 100644
--- a/build/Android.bp
+++ b/build/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
bootstrap_go_package {
name: "soong-fluoride",
pkgPath: "android/soong/fluoride",
@@ -79,19 +70,10 @@ fluoride_defaults {
},
},
defaults: ["fluoride_types_defaults_fuzzable"],
- header_libs: ["libbluetooth_headers", "libbt_callbacks_cxx_headers"],
- generated_headers: [
- "libbt_shim_bridge_header",
- "libbt_message_loop_thread_bridge_header",
- "cxx-bridge-header"
- ],
- include_dirs: ["system/bt/gd/rust/shim"],
+ header_libs: ["libbluetooth_headers"],
static_libs: [
"libbluetooth-types",
"libbt-platform-protos-lite",
- "libbluetooth_rust_interop",
- "liblog",
- "libcutils",
],
cpp_std: "c++17",
sanitize: {
@@ -102,38 +84,10 @@ fluoride_defaults {
fluoride_defaults {
name: "fluoride_defaults",
defaults: ["fluoride_defaults_fuzzable", "fluoride_types_defaults"],
- shared_libs: [
- "libcutils",
- "libgrpc++",
- "libgrpc_wrap",
- "libhidlbase",
- "libstatslog",
- "libutils",
-
- ],
+ shared_libs: ["libstatslog"],
sanitize: {
misc_undefined: ["bounds"],
},
- static_libs: [
- "libbluetooth_gd",
- "libbluetooth_rust_interop",
- "libbt_shim_ffi",
- ],
- target: {
- darwin: {
- // libstatslog -> libbinder doesn't build on mac
- enabled: false,
- },
- android: {
- shared_libs: [
- "android.hardware.bluetooth@1.0",
- "android.hardware.bluetooth@1.1",
- ],
- cflags: [
- "-DOS_ANDROID",
- ],
- },
- },
}
// Enables code coverage for a set of source files. Must be combined with
diff --git a/build/dpkg/README.txt b/build/dpkg/README.txt
deleted file mode 100644
index 785079602..000000000
--- a/build/dpkg/README.txt
+++ /dev/null
@@ -1,25 +0,0 @@
-This directory contains scripts to build Debian packages as dependencies for
-building Fluoride on Linux.
-
-To generate the Debian packages, you need:
-
-* Debian 10 (Buster)
-* gn, get binary from https://chrome-infra-packages.appspot.com/dl/gn/gn/linux-amd64/+/latest
-* apt-get install git debmake
-* Other build dependencies are package dependent, you will get error message
- mentioning the list of missing packages
-
-Steps to build debian packages (modp_b64 first):
-```
-$ cd build/dpkg/modp_b64
-$ ./gen-src-pkg /tmp/modp_b64
-```
-
-If the above succeeded, there will be a .deb file in /tmp/modp_b64. You can
-install this binary package locally like:
-```
-$ sudo dpkg -i /tmp/modp_b64/modp-b64_0.0.1-1_amd64.deb
-```
-
-After installing modp_b64, you can do the same steps with libchrome in
-build/dpkg/libchrome.
diff --git a/build/dpkg/libchrome-822064/debian/README.Debian b/build/dpkg/libchrome-822064/debian/README.Debian
deleted file mode 100644
index 773bbf318..000000000
--- a/build/dpkg/libchrome-822064/debian/README.Debian
+++ /dev/null
@@ -1 +0,0 @@
-libchrome for Debian
diff --git a/build/dpkg/libchrome-822064/debian/changelog b/build/dpkg/libchrome-822064/debian/changelog
deleted file mode 100644
index 113a5e756..000000000
--- a/build/dpkg/libchrome-822064/debian/changelog
+++ /dev/null
@@ -1,5 +0,0 @@
-libchrome (822064-1) buster; urgency=low
-
- * Initial release.
-
- -- Sonny Sasaka <sonnysasaka@chromium.org> Fri, 30 Apr 2021 19:41:40 +0000
diff --git a/build/dpkg/libchrome-822064/debian/compat b/build/dpkg/libchrome-822064/debian/compat
deleted file mode 100644
index f599e28b8..000000000
--- a/build/dpkg/libchrome-822064/debian/compat
+++ /dev/null
@@ -1 +0,0 @@
-10
diff --git a/build/dpkg/libchrome-822064/debian/control b/build/dpkg/libchrome-822064/debian/control
deleted file mode 100644
index b11c23fbc..000000000
--- a/build/dpkg/libchrome-822064/debian/control
+++ /dev/null
@@ -1,28 +0,0 @@
-Source: libchrome
-Section: libs
-Priority: optional
-Maintainer: Sonny Sasaka <sonnysasaka@chromium.org>
-Standards-Version: 4.1.4
-Homepage: https://chromium.googlesource.com/aosp/platform/external/libchrome/
-Build-Depends:
- debhelper (>=11~),
- clang,
- python3,
- pkg-config,
- ninja-build,
- libglib2.0-dev,
- libevent-dev,
- libnss3-dev,
- libdbus-1-dev,
- libprotobuf-dev,
- googletest,
- libre2-dev,
- libdouble-conversion-dev,
- libssl-dev,
- libabsl-dev
-
-Package: libchrome
-Architecture: any
-Multi-Arch: foreign
-Depends: ${misc:Depends}, ${shlibs:Depends}
-Description: Chromium's base library
diff --git a/build/dpkg/libchrome-822064/debian/install_headers.sh b/build/dpkg/libchrome-822064/debian/install_headers.sh
deleted file mode 100755
index 19cb5efa8..000000000
--- a/build/dpkg/libchrome-822064/debian/install_headers.sh
+++ /dev/null
@@ -1,48 +0,0 @@
-#!/bin/bash
-
-destdir="$1"
-
-header_dirs=(
- base
- base/allocator
- base/containers
- base/debug
- base/files
- base/hash
- base/i18n
- base/json
- base/memory
- base/message_loop
- base/metrics
- base/numerics
- base/posix
- base/process
- base/strings
- base/synchronization
- base/system
- base/task
- base/task/common
- base/task/sequence_manager
- base/task/thread_pool
- base/test
- base/third_party/icu
- base/third_party/nspr
- base/third_party/valgrind
- base/threading
- base/time
- base/timer
- base/trace_event
- base/trace_event/common
- build
- components/policy
- components/policy/core/common
- testing/gmock/include/gmock
- testing/gtest/include/gtest
- dbus
- )
-
-# Install header files.
-for d in "${header_dirs[@]}" ; do
- mkdir -p "${destdir}/usr/include/libchrome/${d}"
- cp libchrome/"${d}"/*.h "${destdir}/usr/include/libchrome/${d}"
-done
diff --git a/build/dpkg/libchrome-822064/debian/libchrome.install b/build/dpkg/libchrome-822064/debian/libchrome.install
deleted file mode 100644
index 9d381c1e2..000000000
--- a/build/dpkg/libchrome-822064/debian/libchrome.install
+++ /dev/null
@@ -1,4 +0,0 @@
-out/Release/lib/libbase*.so /usr/lib
-out/Release/libbase*.a /usr/lib
-out/Release/obj/libchrome/libchrome*.pc /usr/lib/pkgconfig
-usr/include /usr
diff --git a/build/dpkg/libchrome-822064/debian/patches/0001-Add-missing-includes.patch b/build/dpkg/libchrome-822064/debian/patches/0001-Add-missing-includes.patch
deleted file mode 100644
index a2f2b4b9a..000000000
--- a/build/dpkg/libchrome-822064/debian/patches/0001-Add-missing-includes.patch
+++ /dev/null
@@ -1,37 +0,0 @@
-From 50a4636886c958717213856132fcbb57c3b8ea2a Mon Sep 17 00:00:00 2001
-From: Sonny Sasaka <sonnysasaka@chromium.org>
-Date: Fri, 19 Mar 2021 16:18:07 -0700
-Subject: [PATCH] Add missing includes
-
----
- base/hash/md5.cc | 1 +
- crypto/p224_spake.cc | 1 +
- 2 files changed, 2 insertions(+)
-
-diff --git a/libchrome/base/hash/md5.cc b/libchrome/base/hash/md5.cc
-index bdb9990a9..ef8954eaf 100644
---- a/libchrome/base/hash/md5.cc
-+++ b/libchrome/base/hash/md5.cc
-@@ -24,6 +24,7 @@
- #include "base/hash/md5.h"
-
- #include <stddef.h>
-+#include <string.h>
-
- namespace {
-
-diff --git a/libchrome/crypto/p224_spake.cc b/libchrome/crypto/p224_spake.cc
-index 157410537..de0af5466 100644
---- a/libchrome/crypto/p224_spake.cc
-+++ b/libchrome/crypto/p224_spake.cc
-@@ -8,6 +8,7 @@
- #include <crypto/p224_spake.h>
-
- #include <algorithm>
-+#include <string.h>
-
- #include <base/logging.h>
- #include <crypto/p224.h>
---
-2.20.1
-
diff --git a/build/dpkg/libchrome-822064/debian/patches/0001-Remove-absl-from-pkgconfig.patch b/build/dpkg/libchrome-822064/debian/patches/0001-Remove-absl-from-pkgconfig.patch
deleted file mode 100644
index 73b8c48cd..000000000
--- a/build/dpkg/libchrome-822064/debian/patches/0001-Remove-absl-from-pkgconfig.patch
+++ /dev/null
@@ -1,33 +0,0 @@
-From 9c93da57cc206ce3d301786b7ef733197ee92939 Mon Sep 17 00:00:00 2001
-From: Sonny Sasaka <sonnysasaka@chromium.org>
-Date: Fri, 30 Apr 2021 17:49:14 -0700
-Subject: [PATCH] Remove absl from pkgconfig
-
-Change-Id: Ia54bb1c58056b1d7adab668e77ef98ffb15f41c6
----
- BUILD.gn | 2 --
- 1 file changed, 2 deletions(-)
-
-diff --git a/libchrome/BUILD.gn b/libchrome/BUILD.gn
-index 402ed4c725..7778aa0163 100644
---- a/libchrome/BUILD.gn
-+++ b/libchrome/BUILD.gn
-@@ -90,7 +90,6 @@ libbase_sublibs = [
- "modp_b64",
- ]
- pkg_deps = [
-- "absl",
- "glib-2.0",
- "libevent",
- ]
-@@ -460,7 +459,6 @@ if (use.dbus) {
- name = "base-dbus"
- deps = [ ":base-core" ]
- pkg_deps = [
-- "absl",
- "dbus-1",
- ]
- if (use.fuzzer) {
---
-2.31.0
-
diff --git a/build/dpkg/libchrome-822064/debian/patches/0001-rebase_path-for-write_args.patch b/build/dpkg/libchrome-822064/debian/patches/0001-rebase_path-for-write_args.patch
deleted file mode 100644
index 9b359c0e8..000000000
--- a/build/dpkg/libchrome-822064/debian/patches/0001-rebase_path-for-write_args.patch
+++ /dev/null
@@ -1,34 +0,0 @@
-From 6875449497baf026fb8228668930a715ffcc7082 Mon Sep 17 00:00:00 2001
-From: Sonny Sasaka <sonnysasaka@chromium.org>
-Date: Fri, 19 Mar 2021 16:56:59 -0700
-Subject: [PATCH] rebase_path for write_args
-
----
- BUILD.gn | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
-diff --git a/libchrome/BUILD.gn b/libchrome/BUILD.gn
-index a846d8f52..66ac10a55 100644
---- a/libchrome/BUILD.gn
-+++ b/libchrome/BUILD.gn
-@@ -556,7 +556,7 @@ action("base") {
-
- script = "//common-mk/write_args.py"
- outputs = [ "${root_out_dir}/lib/lib${target_name}.so" ]
-- args = [ "--output" ] + outputs + [ "--" ] + [
-+ args = [ "--output" ] + rebase_path(outputs) + [ "--" ] + [
- "GROUP",
- "(",
- "AS_NEEDED",
-@@ -618,7 +618,7 @@ action("base-test") {
-
- script = "//common-mk/write_args.py"
- outputs = [ "${root_out_dir}/lib${target_name}.a" ]
-- args = [ "--output" ] + outputs + [ "--" ] + [
-+ args = [ "--output" ] + rebase_path(outputs) + [ "--" ] + [
- "GROUP",
- "(",
- "AS_NEEDED",
---
-2.20.1
-
diff --git a/build/dpkg/libchrome-822064/debian/patches/series b/build/dpkg/libchrome-822064/debian/patches/series
deleted file mode 100644
index 912858828..000000000
--- a/build/dpkg/libchrome-822064/debian/patches/series
+++ /dev/null
@@ -1,3 +0,0 @@
-0001-Add-missing-includes.patch
-0001-rebase_path-for-write_args.patch
-0001-Remove-absl-from-pkgconfig.patch
diff --git a/build/dpkg/libchrome-822064/debian/rules b/build/dpkg/libchrome-822064/debian/rules
deleted file mode 100755
index 7d23a54d0..000000000
--- a/build/dpkg/libchrome-822064/debian/rules
+++ /dev/null
@@ -1,38 +0,0 @@
-#!/usr/bin/make -f
-
-# gn args
-defines =
-defines += pkg_config=\"pkg-config\"
-defines += libbase_ver=\"822064\"
-defines += platform2_root=\"$(shell pwd)/\"
-defines += platform_subdir=\"libchrome\"
-defines += cxx=\"clang++\"
-defines += cc=\"clang\"
-defines += ar=\"ar\"
-defines += external_cxxflags=[\"-I/usr/src/googletest/googletest/include\", \"-I/usr/src/googletest/googlemock/include\"]
-defines += external_ldflags=[\"-latomic\", \"-labsl_base\", \"-labsl_bad_variant_access\"]
-defines += enable_werror=false
-defines += libdir=\"/usr/lib\"
-defines += use={mojo=false asan=false coverage=false crypto=true dbus=true fuzzer=false timers=true cros_host=false profiling=false tcmalloc=false}
-
-# handle parallel build options
-njobs=1
-ifneq (,$(filter parallel=%,$(DEB_BUILD_OPTIONS)))
-njobs=$(patsubst parallel=%,%,$(filter parallel=%,$(DEB_BUILD_OPTIONS)))
-endif
-
-%:
- dh $@ --parallel
-
-override_dh_auto_build-arch:
- gn gen out/Release --args="$(defines)"
- ninja -j$(njobs) -C out/Release
-
-override_dh_auto_clean:
- rm -rf out
- find . -name \*.pyc -execdir rm -f {} \;
- dh_auto_clean
-
-override_dh_auto_install-arch:
- dh_auto_install
- debian/install_headers.sh debian/tmp
diff --git a/build/dpkg/libchrome-822064/gen-src-pkg.sh b/build/dpkg/libchrome-822064/gen-src-pkg.sh
deleted file mode 100755
index cbb5dce54..000000000
--- a/build/dpkg/libchrome-822064/gen-src-pkg.sh
+++ /dev/null
@@ -1,60 +0,0 @@
-#!/bin/bash
-# Generates Debian source and binary packages of libchrome.
-
-if [ -z "$1" ]; then
- echo "Usage: gen-src-pkg.sh <output-dir>"
- exit 1
-fi
-
-outdir="$1"
-pkgdir=libchrome-822064
-origtar=libchrome_822064.orig.tar.gz
-scriptdir="$( cd "$( dirname "$0" )" && pwd )"
-branch=release-R91-13904.B
-
-tmpdir=$(mktemp -d)
-echo Generating source package in "${tmpdir}".
-
-# Download platform2 source.
-cd "${tmpdir}"
-git clone --branch "${branch}" https://chromium.googlesource.com/chromiumos/platform2 || exit 1
-mkdir "${pkgdir}"
-cd "${pkgdir}"
-# Trim platform2, only common-mk is needed.
-cp -a ../platform2/{common-mk,.gn} .
-
-# Download libchrome source and apply Chrome OS's patches.
-git clone --branch "${branch}" https://chromium.googlesource.com/aosp/platform/external/libchrome || exit 1
-cd libchrome
-rm -rf .git
-while read -r patch; do
- patch -p1 < "libchrome_tools/patches/${patch}"
-done < <(grep -E '^[^#]' "libchrome_tools/patches/patches")
-
-# Clean up temporary platform2 checkout.
-cd ../..
-rm -rf platform2
-
-# Debian requires creating .orig.tar.gz.
-tar czf "${origtar}" "${pkgdir}"
-
-# Debianize the source.
-cd "${pkgdir}"
-yes | debmake || exit 1
-cp -aT "${scriptdir}/debian/" "${tmpdir}/${pkgdir}/debian/"
-
-# Build source package and binary package.
-cd "${tmpdir}/${pkgdir}"
-dpkg-buildpackage --no-sign || exit 1
-
-# Copy the results to output dir.
-cd "${tmpdir}"
-mkdir -p "${outdir}/src"
-cp *.dsc *.orig.tar.gz *.debian.tar.xz "${outdir}/src"
-cp *.deb "${outdir}"
-cd /
-
-echo Removing temporary directory "${tmpdir}".
-rm -rf "${tmpdir}"
-
-echo Done. Check out Debian source package in "${outdir}".
diff --git a/build/dpkg/libchrome/debian/README.Debian b/build/dpkg/libchrome/debian/README.Debian
deleted file mode 100644
index 773bbf318..000000000
--- a/build/dpkg/libchrome/debian/README.Debian
+++ /dev/null
@@ -1 +0,0 @@
-libchrome for Debian
diff --git a/build/dpkg/libchrome/debian/changelog b/build/dpkg/libchrome/debian/changelog
deleted file mode 100644
index 3cdedf689..000000000
--- a/build/dpkg/libchrome/debian/changelog
+++ /dev/null
@@ -1,5 +0,0 @@
-libchrome (780652-1) buster; urgency=low
-
- * Initial release.
-
- -- Sonny Sasaka <sonnysasaka@chromium.org> Fri, 19 Mar 2021 19:41:40 +0000
diff --git a/build/dpkg/libchrome/debian/compat b/build/dpkg/libchrome/debian/compat
deleted file mode 100644
index f599e28b8..000000000
--- a/build/dpkg/libchrome/debian/compat
+++ /dev/null
@@ -1 +0,0 @@
-10
diff --git a/build/dpkg/libchrome/debian/control b/build/dpkg/libchrome/debian/control
deleted file mode 100644
index d804b4d88..000000000
--- a/build/dpkg/libchrome/debian/control
+++ /dev/null
@@ -1,27 +0,0 @@
-Source: libchrome
-Section: libs
-Priority: optional
-Maintainer: Sonny Sasaka <sonnysasaka@chromium.org>
-Standards-Version: 4.1.4
-Homepage: https://chromium.googlesource.com/aosp/platform/external/libchrome/
-Build-Depends:
- debhelper (>=11~),
- clang,
- python3,
- pkg-config,
- ninja-build,
- libglib2.0-dev,
- libevent-dev,
- libnss3-dev,
- libdbus-1-dev,
- libprotobuf-dev,
- googletest,
- libre2-dev,
- libdouble-conversion-dev,
- libssl-dev
-
-Package: libchrome
-Architecture: any
-Multi-Arch: foreign
-Depends: ${misc:Depends}, ${shlibs:Depends}
-Description: Chromium's base library
diff --git a/build/dpkg/libchrome/debian/install_headers.sh b/build/dpkg/libchrome/debian/install_headers.sh
deleted file mode 100755
index 19cb5efa8..000000000
--- a/build/dpkg/libchrome/debian/install_headers.sh
+++ /dev/null
@@ -1,48 +0,0 @@
-#!/bin/bash
-
-destdir="$1"
-
-header_dirs=(
- base
- base/allocator
- base/containers
- base/debug
- base/files
- base/hash
- base/i18n
- base/json
- base/memory
- base/message_loop
- base/metrics
- base/numerics
- base/posix
- base/process
- base/strings
- base/synchronization
- base/system
- base/task
- base/task/common
- base/task/sequence_manager
- base/task/thread_pool
- base/test
- base/third_party/icu
- base/third_party/nspr
- base/third_party/valgrind
- base/threading
- base/time
- base/timer
- base/trace_event
- base/trace_event/common
- build
- components/policy
- components/policy/core/common
- testing/gmock/include/gmock
- testing/gtest/include/gtest
- dbus
- )
-
-# Install header files.
-for d in "${header_dirs[@]}" ; do
- mkdir -p "${destdir}/usr/include/libchrome/${d}"
- cp libchrome/"${d}"/*.h "${destdir}/usr/include/libchrome/${d}"
-done
diff --git a/build/dpkg/libchrome/debian/libchrome.install b/build/dpkg/libchrome/debian/libchrome.install
deleted file mode 100644
index 9d381c1e2..000000000
--- a/build/dpkg/libchrome/debian/libchrome.install
+++ /dev/null
@@ -1,4 +0,0 @@
-out/Release/lib/libbase*.so /usr/lib
-out/Release/libbase*.a /usr/lib
-out/Release/obj/libchrome/libchrome*.pc /usr/lib/pkgconfig
-usr/include /usr
diff --git a/build/dpkg/libchrome/debian/patches/0001-Add-missing-includes.patch b/build/dpkg/libchrome/debian/patches/0001-Add-missing-includes.patch
deleted file mode 100644
index a2f2b4b9a..000000000
--- a/build/dpkg/libchrome/debian/patches/0001-Add-missing-includes.patch
+++ /dev/null
@@ -1,37 +0,0 @@
-From 50a4636886c958717213856132fcbb57c3b8ea2a Mon Sep 17 00:00:00 2001
-From: Sonny Sasaka <sonnysasaka@chromium.org>
-Date: Fri, 19 Mar 2021 16:18:07 -0700
-Subject: [PATCH] Add missing includes
-
----
- base/hash/md5.cc | 1 +
- crypto/p224_spake.cc | 1 +
- 2 files changed, 2 insertions(+)
-
-diff --git a/libchrome/base/hash/md5.cc b/libchrome/base/hash/md5.cc
-index bdb9990a9..ef8954eaf 100644
---- a/libchrome/base/hash/md5.cc
-+++ b/libchrome/base/hash/md5.cc
-@@ -24,6 +24,7 @@
- #include "base/hash/md5.h"
-
- #include <stddef.h>
-+#include <string.h>
-
- namespace {
-
-diff --git a/libchrome/crypto/p224_spake.cc b/libchrome/crypto/p224_spake.cc
-index 157410537..de0af5466 100644
---- a/libchrome/crypto/p224_spake.cc
-+++ b/libchrome/crypto/p224_spake.cc
-@@ -8,6 +8,7 @@
- #include <crypto/p224_spake.h>
-
- #include <algorithm>
-+#include <string.h>
-
- #include <base/logging.h>
- #include <crypto/p224.h>
---
-2.20.1
-
diff --git a/build/dpkg/libchrome/debian/patches/0001-common-mk-rebase_path-output-location-of-generate-pc.patch b/build/dpkg/libchrome/debian/patches/0001-common-mk-rebase_path-output-location-of-generate-pc.patch
deleted file mode 100644
index 418efcc47..000000000
--- a/build/dpkg/libchrome/debian/patches/0001-common-mk-rebase_path-output-location-of-generate-pc.patch
+++ /dev/null
@@ -1,36 +0,0 @@
-From 04fa5e1ade08696b5a2cc3b65bf0fd26c43251c7 Mon Sep 17 00:00:00 2001
-From: Sonny Sasaka <sonnysasaka@chromium.org>
-Date: Fri, 19 Mar 2021 11:17:43 -0700
-Subject: [PATCH] common-mk: rebase_path output location of generate-pc.py
-
-Without rebase_path, the generate-pc.py would be called like
-`generate-pc.py --output //out/Release` if the output is inside the
-source directory and this gn path isn't recognized as a generic
-filesystem path.
-
-BUG=b:183216216
-TEST=with modp_b64, call
-$ gn gen out/Release --args=...
-$ ninja
-
-Change-Id: Ic9d9b3d01d52d483e3d81ca2e8d514b47900f5bb
----
- common-mk/pkg_config.gni | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
-diff --git a/common-mk/pkg_config.gni b/common-mk/pkg_config.gni
-index 24e2cf1401..b2c58845d4 100644
---- a/common-mk/pkg_config.gni
-+++ b/common-mk/pkg_config.gni
-@@ -84,7 +84,7 @@ template("generate_pkg_config") {
- outputs = [ "${target_out_dir}/${output_name}.pc" ]
-
- script = "//common-mk/generate-pc.py"
-- args = [ "--output" ] + outputs + [ "--name=" + name ]
-+ args = [ "--output" ] + rebase_path(outputs) + [ "--name=" + name ]
- if (defined(description)) {
- args += [ "--description=" + description ]
- }
---
-2.29.2
-
diff --git a/build/dpkg/libchrome/debian/patches/0001-rebase_path-for-write_args.patch b/build/dpkg/libchrome/debian/patches/0001-rebase_path-for-write_args.patch
deleted file mode 100644
index 9b359c0e8..000000000
--- a/build/dpkg/libchrome/debian/patches/0001-rebase_path-for-write_args.patch
+++ /dev/null
@@ -1,34 +0,0 @@
-From 6875449497baf026fb8228668930a715ffcc7082 Mon Sep 17 00:00:00 2001
-From: Sonny Sasaka <sonnysasaka@chromium.org>
-Date: Fri, 19 Mar 2021 16:56:59 -0700
-Subject: [PATCH] rebase_path for write_args
-
----
- BUILD.gn | 4 ++--
- 1 file changed, 2 insertions(+), 2 deletions(-)
-
-diff --git a/libchrome/BUILD.gn b/libchrome/BUILD.gn
-index a846d8f52..66ac10a55 100644
---- a/libchrome/BUILD.gn
-+++ b/libchrome/BUILD.gn
-@@ -556,7 +556,7 @@ action("base") {
-
- script = "//common-mk/write_args.py"
- outputs = [ "${root_out_dir}/lib/lib${target_name}.so" ]
-- args = [ "--output" ] + outputs + [ "--" ] + [
-+ args = [ "--output" ] + rebase_path(outputs) + [ "--" ] + [
- "GROUP",
- "(",
- "AS_NEEDED",
-@@ -618,7 +618,7 @@ action("base-test") {
-
- script = "//common-mk/write_args.py"
- outputs = [ "${root_out_dir}/lib${target_name}.a" ]
-- args = [ "--output" ] + outputs + [ "--" ] + [
-+ args = [ "--output" ] + rebase_path(outputs) + [ "--" ] + [
- "GROUP",
- "(",
- "AS_NEEDED",
---
-2.20.1
-
diff --git a/build/dpkg/libchrome/debian/patches/series b/build/dpkg/libchrome/debian/patches/series
deleted file mode 100644
index 5a26f7be7..000000000
--- a/build/dpkg/libchrome/debian/patches/series
+++ /dev/null
@@ -1,3 +0,0 @@
-0001-common-mk-rebase_path-output-location-of-generate-pc.patch
-0001-Add-missing-includes.patch
-0001-rebase_path-for-write_args.patch
diff --git a/build/dpkg/libchrome/debian/rules b/build/dpkg/libchrome/debian/rules
deleted file mode 100755
index 6ac17835c..000000000
--- a/build/dpkg/libchrome/debian/rules
+++ /dev/null
@@ -1,38 +0,0 @@
-#!/usr/bin/make -f
-
-# gn args
-defines =
-defines += pkg_config=\"pkg-config\"
-defines += libbase_ver=\"780652\"
-defines += platform2_root=\"$(shell pwd)/\"
-defines += platform_subdir=\"libchrome\"
-defines += cxx=\"clang++\"
-defines += cc=\"clang\"
-defines += ar=\"ar\"
-defines += external_cxxflags=[\"-I/usr/src/googletest/googletest/include\", \"-I/usr/src/googletest/googlemock/include\"]
-defines += external_ldflags=[\"-latomic\"]
-defines += enable_werror=false
-defines += libdir=\"/usr/lib\"
-defines += use={mojo=false asan=false coverage=false crypto=true dbus=true fuzzer=false timers=true cros_host=false profiling=false tcmalloc=false}
-
-# handle parallel build options
-njobs=1
-ifneq (,$(filter parallel=%,$(DEB_BUILD_OPTIONS)))
-njobs=$(patsubst parallel=%,%,$(filter parallel=%,$(DEB_BUILD_OPTIONS)))
-endif
-
-%:
- dh $@ --parallel
-
-override_dh_auto_build-arch:
- gn gen out/Release --args="$(defines)"
- ninja -j$(njobs) -C out/Release
-
-override_dh_auto_clean:
- rm -rf out
- find . -name \*.pyc -execdir rm -f {} \;
- dh_auto_clean
-
-override_dh_auto_install-arch:
- dh_auto_install
- debian/install_headers.sh debian/tmp
diff --git a/build/dpkg/libchrome/gen-src-pkg.sh b/build/dpkg/libchrome/gen-src-pkg.sh
deleted file mode 100755
index 3cee0e461..000000000
--- a/build/dpkg/libchrome/gen-src-pkg.sh
+++ /dev/null
@@ -1,60 +0,0 @@
-#!/bin/bash
-# Generates Debian source and binary packages of libchrome.
-
-if [ -z "$1" ]; then
- echo "Usage: gen-src-pkg.sh <output-dir>"
- exit 1
-fi
-
-outdir="$1"
-pkgdir=libchrome-780652
-origtar=libchrome_780652.orig.tar.gz
-scriptdir="$( cd "$( dirname "$0" )" && pwd )"
-branch=release-R90-13816.B
-
-tmpdir=$(mktemp -d)
-echo Generating source package in "${tmpdir}".
-
-# Download platform2 source.
-cd "${tmpdir}"
-git clone --branch "${branch}" https://chromium.googlesource.com/chromiumos/platform2 || exit 1
-mkdir "${pkgdir}"
-cd "${pkgdir}"
-# Trim platform2, only common-mk is needed.
-cp -a ../platform2/{common-mk,.gn} .
-
-# Download libchrome source and apply Chrome OS's patches.
-git clone --branch "${branch}" https://chromium.googlesource.com/aosp/platform/external/libchrome || exit 1
-cd libchrome
-rm -rf .git
-while read -r patch; do
- patch -p1 < "libchrome_tools/patches/${patch}"
-done < <(grep -E '^[^#]' "libchrome_tools/patches/patches")
-
-# Clean up temporary platform2 checkout.
-cd ../..
-rm -rf platform2
-
-# Debian requires creating .orig.tar.gz.
-tar czf "${origtar}" "${pkgdir}"
-
-# Debianize the source.
-cd "${pkgdir}"
-yes | debmake || exit 1
-cp -aT "${scriptdir}/debian/" "${tmpdir}/${pkgdir}/debian/"
-
-# Build source package and binary package.
-cd "${tmpdir}/${pkgdir}"
-dpkg-buildpackage --no-sign || exit 1
-
-# Copy the results to output dir.
-cd "${tmpdir}"
-mkdir -p "${outdir}/src"
-cp *.dsc *.orig.tar.gz *.debian.tar.xz "${outdir}/src"
-cp *.deb "${outdir}"
-cd /
-
-echo Removing temporary directory "${tmpdir}".
-rm -rf "${tmpdir}"
-
-echo Done. Check out Debian source package in "${outdir}".
diff --git a/build/dpkg/modp_b64/debian/README.Debian b/build/dpkg/modp_b64/debian/README.Debian
deleted file mode 100644
index 2fb99bde8..000000000
--- a/build/dpkg/modp_b64/debian/README.Debian
+++ /dev/null
@@ -1 +0,0 @@
-modp-b64 for Debian
diff --git a/build/dpkg/modp_b64/debian/changelog b/build/dpkg/modp_b64/debian/changelog
deleted file mode 100644
index 034c8ef7c..000000000
--- a/build/dpkg/modp_b64/debian/changelog
+++ /dev/null
@@ -1,5 +0,0 @@
-modp-b64 (0.0.1-1) buster; urgency=low
-
- * Initial release.
-
- -- Sonny Sasaka <sonnysasaka@chromium.org> Fri, 19 Mar 2021 19:41:40 +0000
diff --git a/build/dpkg/modp_b64/debian/compat b/build/dpkg/modp_b64/debian/compat
deleted file mode 100644
index f599e28b8..000000000
--- a/build/dpkg/modp_b64/debian/compat
+++ /dev/null
@@ -1 +0,0 @@
-10
diff --git a/build/dpkg/modp_b64/debian/control b/build/dpkg/modp_b64/debian/control
deleted file mode 100644
index a1ef0d98f..000000000
--- a/build/dpkg/modp_b64/debian/control
+++ /dev/null
@@ -1,18 +0,0 @@
-Source: modp-b64
-Section: libs
-Priority: optional
-Maintainer: Sonny Sasaka <sonnysasaka@chromium.org>
-Standards-Version: 4.1.4
-Homepage: https://chromium.googlesource.com/aosp/platform/external/modp_b64/
-Build-Depends:
- debhelper (>=11~),
- clang,
- python3,
- pkg-config,
- ninja-build,
-
-Package: modp-b64
-Architecture: any
-Multi-Arch: foreign
-Depends: ${misc:Depends}, ${shlibs:Depends}
-Description: modp base64 decoder
diff --git a/build/dpkg/modp_b64/debian/modp-b64.install b/build/dpkg/modp_b64/debian/modp-b64.install
deleted file mode 100644
index 3bd28024e..000000000
--- a/build/dpkg/modp_b64/debian/modp-b64.install
+++ /dev/null
@@ -1,3 +0,0 @@
-modp_b64/modp_b64 /usr/include
-out/Release/libmodp_b64.a /usr/lib
-out/Release/obj/modp_b64/libmodp_b64.pc /usr/lib/pkgconfig
diff --git a/build/dpkg/modp_b64/debian/patches/0001-common-mk-rebase_path-output-location-of-generate-pc.patch b/build/dpkg/modp_b64/debian/patches/0001-common-mk-rebase_path-output-location-of-generate-pc.patch
deleted file mode 100644
index 418efcc47..000000000
--- a/build/dpkg/modp_b64/debian/patches/0001-common-mk-rebase_path-output-location-of-generate-pc.patch
+++ /dev/null
@@ -1,36 +0,0 @@
-From 04fa5e1ade08696b5a2cc3b65bf0fd26c43251c7 Mon Sep 17 00:00:00 2001
-From: Sonny Sasaka <sonnysasaka@chromium.org>
-Date: Fri, 19 Mar 2021 11:17:43 -0700
-Subject: [PATCH] common-mk: rebase_path output location of generate-pc.py
-
-Without rebase_path, the generate-pc.py would be called like
-`generate-pc.py --output //out/Release` if the output is inside the
-source directory and this gn path isn't recognized as a generic
-filesystem path.
-
-BUG=b:183216216
-TEST=with modp_b64, call
-$ gn gen out/Release --args=...
-$ ninja
-
-Change-Id: Ic9d9b3d01d52d483e3d81ca2e8d514b47900f5bb
----
- common-mk/pkg_config.gni | 2 +-
- 1 file changed, 1 insertion(+), 1 deletion(-)
-
-diff --git a/common-mk/pkg_config.gni b/common-mk/pkg_config.gni
-index 24e2cf1401..b2c58845d4 100644
---- a/common-mk/pkg_config.gni
-+++ b/common-mk/pkg_config.gni
-@@ -84,7 +84,7 @@ template("generate_pkg_config") {
- outputs = [ "${target_out_dir}/${output_name}.pc" ]
-
- script = "//common-mk/generate-pc.py"
-- args = [ "--output" ] + outputs + [ "--name=" + name ]
-+ args = [ "--output" ] + rebase_path(outputs) + [ "--name=" + name ]
- if (defined(description)) {
- args += [ "--description=" + description ]
- }
---
-2.29.2
-
diff --git a/build/dpkg/modp_b64/debian/patches/series b/build/dpkg/modp_b64/debian/patches/series
deleted file mode 100644
index 27086fc3b..000000000
--- a/build/dpkg/modp_b64/debian/patches/series
+++ /dev/null
@@ -1 +0,0 @@
-0001-common-mk-rebase_path-output-location-of-generate-pc.patch
diff --git a/build/dpkg/modp_b64/debian/rules b/build/dpkg/modp_b64/debian/rules
deleted file mode 100755
index 1bb93aee1..000000000
--- a/build/dpkg/modp_b64/debian/rules
+++ /dev/null
@@ -1,31 +0,0 @@
-#!/usr/bin/make -f
-
-# gn args
-defines =
-defines += pkg_config=\"pkg-config\"
-defines += platform2_root=\"$(shell pwd)/\"
-defines += platform_subdir=\"modp_b64\"
-defines += cxx=\"clang++\"
-defines += cc=\"clang\"
-defines += ar=\"ar\"
-defines += enable_werror=false
-defines += libdir=\"/usr/lib\"
-defines += use={mojo=false asan=false coverage=false crypto=true dbus=true fuzzer=false timers=true cros_host=false profiling=false tcmalloc=false}
-
-# handle parallel build options
-njobs=1
-ifneq (,$(filter parallel=%,$(DEB_BUILD_OPTIONS)))
-njobs=$(patsubst parallel=%,%,$(filter parallel=%,$(DEB_BUILD_OPTIONS)))
-endif
-
-%:
- dh $@
-
-override_dh_auto_build-arch:
- gn gen out/Release --args="$(defines)"
- ninja -j$(njobs) -C out/Release
-
-override_dh_auto_clean:
- rm -rf out
- find . -name \*.pyc -execdir rm -f {} \;
- dh_auto_clean
diff --git a/build/dpkg/modp_b64/gen-src-pkg.sh b/build/dpkg/modp_b64/gen-src-pkg.sh
deleted file mode 100755
index cc22f678f..000000000
--- a/build/dpkg/modp_b64/gen-src-pkg.sh
+++ /dev/null
@@ -1,57 +0,0 @@
-#!/bin/bash
-# Generates Debian source and binary packages of modp_b64.
-
-if [ -z "$1" ]; then
- echo "Usage: gen-src-pkg.sh <output-dir>"
- exit 1
-fi
-
-outdir="$1"
-pkgdir=modp-b64-0.0.1
-origtar=modp-b64_0.0.1.orig.tar.gz
-scriptdir="$( cd "$( dirname "$0" )" && pwd )"
-branch=release-R90-13816.B
-
-tmpdir=$(mktemp -d)
-echo Generating source package in "${tmpdir}".
-
-# Download platform2 source.
-cd "${tmpdir}"
-git clone --branch "${branch}" https://chromium.googlesource.com/chromiumos/platform2 || exit 1
-mkdir "${pkgdir}"
-cd "${pkgdir}"
-# Trim platform2, only common-mk is needed.
-cp -a ../platform2/{common-mk,.gn} .
-
-# Download modp_b64 source.
-git clone --branch "${branch}" https://chromium.googlesource.com/aosp/platform/external/modp_b64 || exit 1
-cd modp_b64
-rm -rf .git
-
-# Clean up temporary platform2 checkout.
-cd ../..
-rm -rf platform2
-
-# Debian requires creating .orig.tar.gz.
-tar czf "${origtar}" "${pkgdir}"
-
-# Debianize the source.
-cd "${pkgdir}"
-yes | debmake || exit 1
-cp -aT "${scriptdir}/debian/" "${tmpdir}/${pkgdir}/debian/"
-
-# Build source package and binary package.
-cd "${tmpdir}/${pkgdir}"
-dpkg-buildpackage --no-sign || exit 1
-
-# Copy the results to output dir.
-cd "${tmpdir}"
-mkdir -p "${outdir}/src"
-cp *.dsc *.orig.tar.gz *.debian.tar.xz "${outdir}/src"
-cp *.deb "${outdir}"
-cd /
-
-echo Removing temporary directory "${tmpdir}".
-rm -rf "${tmpdir}"
-
-echo Done. Check out Debian source package in "${outdir}".
diff --git a/build/install_deps.sh b/build/install_deps.sh
index 4826b385f..f1173a9ca 100755
--- a/build/install_deps.sh
+++ b/build/install_deps.sh
@@ -1,7 +1,7 @@
#!/bin/bash
CLANG_PACKAGE=clang
GNSHA1_URL="https://chromium.googlesource.com/chromium/buildtools/\
- +/central/linux64/gn.sha1?format=TEXT"
++/master/linux64/gn.sha1?format=TEXT"
# Check if clang is already installed on current system
clang_path=`which clang`
@@ -20,7 +20,7 @@ fi
if [ ! -z "$CLANG_PACKAGE" ]; then
# Try to find clang from a known list
- for clang_version in 12.0 11.0
+ for clang_version in 3.9 3.8 3.7 3.6 3.5
do
clang_path=`which clang-$clang_version`
if [ -f "$clang_path" ]; then
@@ -34,21 +34,20 @@ fi
if [ ! -z "$CLANG_PACKAGE" ]; then
echo "clang not found on current system, installing"
if [ -f /etc/lsb-release ]; then
- # Ubuntu
- ubuntu_version=$(lsb_release --release --short)
- IFS="." read -ra ubuntu_version_array <<< "$ubuntu_version"
- ubuntu_version_major=${ubuntu_version_array[0]}
- ubuntu_version_minor=${ubuntu_version_array[1]}
- if [ $ubuntu_version_major -lt 15 ]; then
- echo "Choose clang-3.8 for Ubuntu 14 and below"
- CLANG_PACKAGE=clang-3.8
- fi
+ # Ubuntu
+ ubuntu_version=$(lsb_release --release --short)
+ IFS="." read -ra ubuntu_version_array <<< "$ubuntu_version"
+ ubuntu_version_major=${ubuntu_version_array[0]}
+ ubuntu_version_minor=${ubuntu_version_array[1]}
+ if [ $ubuntu_version_major -lt 15 ]; then
+ echo "Choose clang-3.8 for Ubuntu 14 and below"
+ CLANG_PACKAGE=clang-3.8
+ fi
fi
fi
sudo apt-get -y install $CLANG_PACKAGE libevent-dev libc++-dev libc++abi-dev \
- ninja-build libflatbuffers-dev libtinyxml2-dev
-
+ ninja-build
gn_path=`which gn`
if [ -z $gn_path ]; then
gnsha1=$(curl $GNSHA1_URL | base64 -d)
diff --git a/build/toolchain/clang/get_clang_suffix.py b/build/toolchain/clang/get_clang_suffix.py
index 6bf7b9c8b..fbfe16c95 100644
--- a/build/toolchain/clang/get_clang_suffix.py
+++ b/build/toolchain/clang/get_clang_suffix.py
@@ -18,7 +18,8 @@ clang_version_major = 0
clang_version_minor = 0
if clang_path:
- clang_version_out = subprocess.Popen([clang_path, "--version"], stdout=subprocess.PIPE).communicate()[0]
+ clang_version_out = subprocess.Popen(
+ [clang_path, "--version"], stdout=subprocess.PIPE).communicate()[0]
clang_version_match = re.search(CLANG_VERSION_REGEX, clang_version_out)
clang_version_str = clang_version_match.group(1)
clang_version_array = clang_version_str.split('.')
diff --git a/common/Android.bp b/common/Android.bp
index b22109b3a..e05528c7e 100644
--- a/common/Android.bp
+++ b/common/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "libbt-common",
defaults: [
@@ -17,7 +8,6 @@ cc_library_static {
include_dirs: [
"system/bt",
"system/bt/stack/include",
- "system/bt/gd/rust/shim",
],
srcs: [
"address_obfuscator.cc",
@@ -25,10 +15,8 @@ cc_library_static {
"metric_id_allocator.cc",
"metrics.cc",
"once_timer.cc",
- "os_utils.cc",
"repeating_timer.cc",
"time_util.cc",
- "stop_watch_legacy.cc",
],
shared_libs: [
"libcrypto",
@@ -46,13 +34,9 @@ cc_test {
"clang_coverage_bin",
],
host_supported: true,
- test_options: {
- unit_test: true,
- },
include_dirs: [
"system/bt",
"system/bt/stack/include",
- "system/bt/gd/rust/shim",
],
srcs: [
"address_obfuscator_unittest.cc",
diff --git a/common/BUILD.gn b/common/BUILD.gn
index 0260fb212..76d70f8fb 100644
--- a/common/BUILD.gn
+++ b/common/BUILD.gn
@@ -16,55 +16,47 @@
static_library("common") {
sources = [
- "address_obfuscator.cc",
"message_loop_thread.cc",
- "metric_id_allocator.cc",
"metrics_linux.cc",
- "once_timer.cc",
- "os_utils.cc",
- "repeating_timer.cc",
"time_util.cc",
+ "timer.cc",
]
include_dirs = [
- "//bt/",
- "//bt/stack/include",
- "//bt/linux_include",
- "//bt/internal_include",
+ "//",
+ "//stack/include",
+ "//linux_include",
+ "//internal_include",
]
deps = [
- "//bt:libbt-platform-protos-lite",
- "//bt/gd/rust/shim:init_flags_bridge_header",
+ "//third_party/libchrome:base",
]
-
- configs += [ "//bt:target_defaults" ]
}
-if (use.test) {
- executable("bluetooth_test_common") {
- sources = [
- "leaky_bonded_queue_unittest.cc",
- "state_machine_unittest.cc",
- "time_util_unittest.cc",
- ]
-
- include_dirs = [
- "//bt/",
- "//bt/common",
- ]
+executable("bt_test_common") {
+ testonly = true
+ sources = [
+ "leaky_bonded_queue_unittest.cc",
+ "state_machine_unittest.cc",
+ "time_util_unittest.cc",
+ "timer_unittest.cc"
+ ]
- deps = [ "//bt/common" ]
+ include_dirs = [
+ "//",
+ "//common",
+ ]
- configs += [
- "//bt:external_gtest_main",
- "//bt:external_gmock_main",
- "//bt:target_defaults",
- ]
+ deps = [
+ "//common",
+ "//third_party/googletest:gtest_main",
+ "//third_party/googletest:gmock_main",
+ "//third_party/libchrome:base",
+ ]
- libs = [
- "pthread",
- "rt",
- ]
- }
+ libs = [
+ "-lpthread",
+ "-lrt",
+ ]
}
diff --git a/common/benchmark/thread_performance_benchmark.cc b/common/benchmark/thread_performance_benchmark.cc
index 8538dac05..74f157f85 100644
--- a/common/benchmark/thread_performance_benchmark.cc
+++ b/common/benchmark/thread_performance_benchmark.cc
@@ -23,7 +23,6 @@
#include <memory>
#include <thread>
-#include "abstract_message_loop.h"
#include "common/message_loop_thread.h"
#include "osi/include/fixed_queue.h"
#include "osi/include/thread.h"
@@ -94,7 +93,7 @@ class BM_MessageLoop : public BM_ThreadPerformance {
return nullptr;
}
void RunMessageLoop() {
- message_loop_ = new btbase::AbstractMessageLoop();
+ message_loop_ = new base::MessageLoop();
run_loop_ = new base::RunLoop();
message_loop_->task_runner()->PostTask(
FROM_HERE, base::BindOnce(&std::promise<void>::set_value,
@@ -107,7 +106,7 @@ class BM_MessageLoop : public BM_ThreadPerformance {
}
protected:
- btbase::AbstractMessageLoop* message_loop_ = nullptr;
+ base::MessageLoop* message_loop_ = nullptr;
base::RunLoop* run_loop_ = nullptr;
};
diff --git a/common/benchmark/timer_performance_benchmark.cc b/common/benchmark/timer_performance_benchmark.cc
index 8aaaf0207..deaaad866 100644
--- a/common/benchmark/timer_performance_benchmark.cc
+++ b/common/benchmark/timer_performance_benchmark.cc
@@ -32,7 +32,8 @@ using bluetooth::common::OnceTimer;
using bluetooth::common::RepeatingTimer;
using bluetooth::common::time_get_os_boottime_us;
-bluetooth::common::MessageLoopThread* get_main_thread() { return nullptr; }
+// fake get_main_message_loop implementation for alarm
+base::MessageLoop* get_main_message_loop() { return nullptr; }
namespace {
std::unordered_map<int, int> g_map;
diff --git a/common/lru.h b/common/lru.h
index 42636832d..36f8707dc 100644
--- a/common/lru.h
+++ b/common/lru.h
@@ -33,7 +33,7 @@ namespace bluetooth {
namespace common {
template <typename K, typename V>
-class LegacyLruCache {
+class LruCache {
public:
using Node = std::pair<K, V>;
/**
@@ -42,7 +42,7 @@ class LegacyLruCache {
* @param capacity maximum size of the cache
* @param log_tag, keyword to put at the head of log.
*/
- LegacyLruCache(const size_t& capacity, const std::string& log_tag)
+ LruCache(const size_t& capacity, const std::string& log_tag)
: capacity_(capacity) {
if (capacity_ == 0) {
// don't allow invalid capacity
@@ -51,10 +51,10 @@ class LegacyLruCache {
}
// delete copy constructor
- LegacyLruCache(LegacyLruCache const&) = delete;
- LegacyLruCache& operator=(LegacyLruCache const&) = delete;
+ LruCache(LruCache const&) = delete;
+ LruCache& operator=(LruCache const&) = delete;
- ~LegacyLruCache() { Clear(); }
+ ~LruCache() { Clear(); }
/**
* Clear the cache
diff --git a/common/lru_unittest.cc b/common/lru_unittest.cc
index b58f1dfd0..6e1d5e432 100644
--- a/common/lru_unittest.cc
+++ b/common/lru_unittest.cc
@@ -26,11 +26,11 @@
namespace testing {
-using bluetooth::common::LegacyLruCache;
+using bluetooth::common::LruCache;
-TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheMainTest1) {
+TEST(BluetoothLruCacheTest, LruCacheMainTest1) {
int* value = new int(0);
- LegacyLruCache<int, int> cache(3, "testing"); // capacity = 3;
+ LruCache<int, int> cache(3, "testing"); // capacity = 3;
cache.Put(1, 10);
EXPECT_EQ(cache.Size(), 1);
EXPECT_FALSE(cache.Put(2, 20));
@@ -74,9 +74,9 @@ TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheMainTest1) {
EXPECT_EQ(*value, 60);
}
-TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheMainTest2) {
+TEST(BluetoothLruCacheTest, LruCacheMainTest2) {
int* value = new int(0);
- LegacyLruCache<int, int> cache(2, "testing"); // size = 2;
+ LruCache<int, int> cache(2, "testing"); // size = 2;
EXPECT_FALSE(cache.Put(1, 10));
EXPECT_FALSE(cache.Put(2, 20));
EXPECT_THAT(cache.Put(3, 30), Optional(Pair(1, 10)));
@@ -126,8 +126,8 @@ TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheMainTest2) {
EXPECT_EQ(*value, 50);
}
-TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheFindTest) {
- LegacyLruCache<int, int> cache(10, "testing");
+TEST(BluetoothLruCacheTest, LruCacheFindTest) {
+ LruCache<int, int> cache(10, "testing");
cache.Put(1, 10);
cache.Put(2, 20);
int value = 0;
@@ -143,8 +143,8 @@ TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheFindTest) {
EXPECT_EQ(cache.Find(10), nullptr);
}
-TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheGetTest) {
- LegacyLruCache<int, int> cache(10, "testing");
+TEST(BluetoothLruCacheTest, LruCacheGetTest) {
+ LruCache<int, int> cache(10, "testing");
cache.Put(1, 10);
cache.Put(2, 20);
int value = 0;
@@ -157,8 +157,8 @@ TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheGetTest) {
EXPECT_EQ(value, 10);
}
-TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheRemoveTest) {
- LegacyLruCache<int, int> cache(10, "testing");
+TEST(BluetoothLruCacheTest, LruCacheRemoveTest) {
+ LruCache<int, int> cache(10, "testing");
for (int key = 0; key <= 30; key++) {
cache.Put(key, key * 100);
}
@@ -176,8 +176,8 @@ TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheRemoveTest) {
}
}
-TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheClearTest) {
- LegacyLruCache<int, int> cache(10, "testing");
+TEST(BluetoothLruCacheTest, LruCacheClearTest) {
+ LruCache<int, int> cache(10, "testing");
for (int key = 0; key < 10; key++) {
cache.Put(key, key * 100);
}
@@ -197,10 +197,10 @@ TEST(BluetoothLegacyLruCacheTest, LegacyLruCacheClearTest) {
}
}
-TEST(BluetoothLegacyLruCacheTest, LegacyLruCachePressureTest) {
+TEST(BluetoothLruCacheTest, LruCachePressureTest) {
auto started = std::chrono::high_resolution_clock::now();
int max_size = 0xFFFFF; // 2^20 = 1M
- LegacyLruCache<int, int> cache(static_cast<size_t>(max_size), "testing");
+ LruCache<int, int> cache(static_cast<size_t>(max_size), "testing");
// fill the cache
for (int key = 0; key < max_size; key++) {
@@ -239,8 +239,8 @@ TEST(BluetoothLegacyLruCacheTest, LegacyLruCachePressureTest) {
EXPECT_LT(execution_time, 10000);
}
-TEST(BluetoothLegacyLruCacheTest, BluetoothLruMultiThreadPressureTest) {
- LegacyLruCache<int, int> cache(100, "testing");
+TEST(BluetoothLruCacheTest, BluetoothLruMultiThreadPressureTest) {
+ LruCache<int, int> cache(100, "testing");
auto pointer = &cache;
// make sure no deadlock
std::vector<std::thread> workers;
diff --git a/common/message_loop_thread.cc b/common/message_loop_thread.cc
index 643de6442..e2c2e2d92 100644
--- a/common/message_loop_thread.cc
+++ b/common/message_loop_thread.cc
@@ -22,9 +22,6 @@
#include <base/strings/stringprintf.h>
-#include "gd/common/init_flags.h"
-#include "osi/include/log.h"
-
namespace bluetooth {
namespace common {
@@ -32,10 +29,6 @@ namespace common {
static constexpr int kRealTimeFifoSchedulingPriority = 1;
MessageLoopThread::MessageLoopThread(const std::string& thread_name)
- : MessageLoopThread(thread_name, false) {}
-
-MessageLoopThread::MessageLoopThread(const std::string& thread_name,
- bool is_main)
: thread_name_(thread_name),
message_loop_(nullptr),
run_loop_(nullptr),
@@ -43,23 +36,11 @@ MessageLoopThread::MessageLoopThread(const std::string& thread_name,
thread_id_(-1),
linux_tid_(-1),
weak_ptr_factory_(this),
- shutting_down_(false),
- is_main_(is_main),
- rust_thread_(nullptr) {}
+ shutting_down_(false) {}
MessageLoopThread::~MessageLoopThread() { ShutDown(); }
void MessageLoopThread::StartUp() {
- if (is_main_ && init_flags::gd_rust_is_enabled()) {
- rust_thread_ = new ::rust::Box<shim::rust::MessageLoopThread>(
- shim::rust::main_message_loop_thread_create());
- auto rust_id =
- bluetooth::shim::rust::main_message_loop_thread_start(**rust_thread_);
- thread_id_ = rust_id;
- linux_tid_ = rust_id;
- return;
- }
-
std::promise<void> start_up_promise;
std::future<void> start_up_future = start_up_promise.get_future();
{
@@ -84,20 +65,6 @@ bool MessageLoopThread::DoInThreadDelayed(const base::Location& from_here,
base::OnceClosure task,
const base::TimeDelta& delay) {
std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- if (is_main_ && init_flags::gd_rust_is_enabled()) {
- if (rust_thread_ == nullptr) {
- LOG(ERROR) << __func__ << ": rust thread is null for thread " << *this
- << ", from " << from_here.ToString();
- return false;
- }
-
- shim::rust::main_message_loop_thread_do_delayed(
- **rust_thread_,
- std::make_unique<shim::rust::OnceClosure>(std::move(task)),
- delay.InMilliseconds());
- return true;
- }
-
if (message_loop_ == nullptr) {
LOG(ERROR) << __func__ << ": message loop is null for thread " << *this
<< ", from " << from_here.ToString();
@@ -115,13 +82,6 @@ bool MessageLoopThread::DoInThreadDelayed(const base::Location& from_here,
void MessageLoopThread::ShutDown() {
{
- if (is_main_ && init_flags::gd_rust_is_enabled()) {
- delete rust_thread_;
- thread_id_ = -1;
- linux_tid_ = -1;
- return;
- }
-
std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
if (thread_ == nullptr) {
LOG(INFO) << __func__ << ": thread " << *this << " is already stopped";
@@ -171,7 +131,7 @@ std::string MessageLoopThread::ToString() const {
bool MessageLoopThread::IsRunning() const {
std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- return thread_id_ != -1;
+ return message_loop_ != nullptr;
}
// Non API method, should not be protected by API mutex
@@ -180,22 +140,17 @@ void MessageLoopThread::RunThread(MessageLoopThread* thread,
thread->Run(std::move(start_up_promise));
}
-btbase::AbstractMessageLoop* MessageLoopThread::message_loop() const {
- ASSERT_LOG(!is_main_,
- "you are not allowed to get the main thread's message loop");
-
+base::MessageLoop* MessageLoopThread::message_loop() const {
std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
return message_loop_;
}
bool MessageLoopThread::EnableRealTimeScheduling() {
std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
-
if (!IsRunning()) {
LOG(ERROR) << __func__ << ": thread " << *this << " is not running";
return false;
}
-
struct sched_param rt_params = {.sched_priority =
kRealTimeFifoSchedulingPriority};
int rc = sched_setscheduler(linux_tid_, SCHED_FIFO, &rt_params);
@@ -217,14 +172,10 @@ base::WeakPtr<MessageLoopThread> MessageLoopThread::GetWeakPtr() {
void MessageLoopThread::Run(std::promise<void> start_up_promise) {
{
std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- if (is_main_ && init_flags::gd_rust_is_enabled()) {
- return;
- }
-
LOG(INFO) << __func__ << ": message loop starting for thread "
<< thread_name_;
base::PlatformThread::SetName(thread_name_);
- message_loop_ = new btbase::AbstractMessageLoop();
+ message_loop_ = new base::MessageLoop();
run_loop_ = new base::RunLoop();
thread_id_ = base::PlatformThread::CurrentId();
linux_tid_ = static_cast<pid_t>(syscall(SYS_gettid));
diff --git a/common/message_loop_thread.h b/common/message_loop_thread.h
index 7420dbcb2..3984a9b58 100644
--- a/common/message_loop_thread.h
+++ b/common/message_loop_thread.h
@@ -24,11 +24,9 @@
#include <base/bind.h>
#include <base/location.h>
+#include <base/message_loop/message_loop.h>
#include <base/run_loop.h>
#include <base/threading/platform_thread.h>
-#include "src/message_loop_thread.rs.h"
-
-#include "abstract_message_loop.h"
namespace bluetooth {
@@ -46,7 +44,6 @@ class MessageLoopThread final {
* @param thread_name name of this worker thread
*/
explicit MessageLoopThread(const std::string& thread_name);
- explicit MessageLoopThread(const std::string& thread_name, bool is_main);
/**
* Destroys the message loop thread automatically when it goes out of scope
@@ -136,7 +133,20 @@ class MessageLoopThread final {
* @return message loop associated with this thread, nullptr if thread is not
* running
*/
- btbase::AbstractMessageLoop* message_loop() const;
+ base::MessageLoop* message_loop() const;
+
+ private:
+ /**
+ * Static method to run the thread
+ *
+ * This is used instead of a C++ lambda because of the use of std::shared_ptr
+ *
+ * @param context needs to be a pointer to an instance of MessageLoopThread
+ * @param start_up_promise a std::promise that is used to notify calling
+ * thread the completion of message loop start-up
+ */
+ static void RunThread(MessageLoopThread* context,
+ std::promise<void> start_up_promise);
/**
* Post a task to run on this thread after a specified delay. If the task
@@ -166,18 +176,8 @@ class MessageLoopThread final {
bool DoInThreadDelayed(const base::Location& from_here,
base::OnceClosure task, const base::TimeDelta& delay);
- private:
- /**
- * Static method to run the thread
- *
- * This is used instead of a C++ lambda because of the use of std::shared_ptr
- *
- * @param context needs to be a pointer to an instance of MessageLoopThread
- * @param start_up_promise a std::promise that is used to notify calling
- * thread the completion of message loop start-up
- */
- static void RunThread(MessageLoopThread* context,
- std::promise<void> start_up_promise);
+ friend class RepeatingTimer; // allow Timer to use DoInThreadDelayed()
+ friend class OnceTimer; // allow OnceTimer to use DoInThreadDelayed()
/**
* Actual method to run the thread, blocking until ShutDown() is called
@@ -189,7 +189,7 @@ class MessageLoopThread final {
mutable std::recursive_mutex api_mutex_;
const std::string thread_name_;
- btbase::AbstractMessageLoop* message_loop_;
+ base::MessageLoop* message_loop_;
base::RunLoop* run_loop_;
std::thread* thread_;
base::PlatformThreadId thread_id_;
@@ -197,8 +197,6 @@ class MessageLoopThread final {
pid_t linux_tid_;
base::WeakPtrFactory<MessageLoopThread> weak_ptr_factory_;
bool shutting_down_;
- bool is_main_;
- ::rust::Box<shim::rust::MessageLoopThread>* rust_thread_ = nullptr;
DISALLOW_COPY_AND_ASSIGN(MessageLoopThread);
};
diff --git a/common/metric_id_allocator.h b/common/metric_id_allocator.h
index cd18d5cfc..63236e49b 100644
--- a/common/metric_id_allocator.h
+++ b/common/metric_id_allocator.h
@@ -119,8 +119,8 @@ class MetricIdAllocator {
static const std::string LOGGING_TAG;
mutable std::mutex id_allocator_mutex_;
- LegacyLruCache<RawAddress, int> paired_device_cache_;
- LegacyLruCache<RawAddress, int> temporary_device_cache_;
+ LruCache<RawAddress, int> paired_device_cache_;
+ LruCache<RawAddress, int> temporary_device_cache_;
std::unordered_set<int> id_set_;
int next_id_{kMinId};
diff --git a/common/metrics.cc b/common/metrics.cc
index 9214dcbde..5d2365fb0 100644
--- a/common/metrics.cc
+++ b/common/metrics.cc
@@ -678,29 +678,6 @@ void LogA2dpAudioOverrunEvent(const RawAddress& address,
}
}
-void LogA2dpPlaybackEvent(const RawAddress& address, int playback_state,
- int audio_coding_mode) {
- std::string obfuscated_id;
- int metric_id = 0;
- if (!address.IsEmpty()) {
- obfuscated_id = AddressObfuscator::GetInstance()->Obfuscate(address);
- metric_id = MetricIdAllocator::GetInstance().AllocateId(address);
- }
- // nullptr and size 0 represent missing value for obfuscated_id
- android::util::BytesField bytes_field(
- address.IsEmpty() ? nullptr : obfuscated_id.c_str(),
- address.IsEmpty() ? 0 : obfuscated_id.size());
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_A2DP_PLAYBACK_STATE_CHANGED, bytes_field,
- playback_state, audio_coding_mode, metric_id);
- if (ret < 0) {
- LOG(WARNING) << __func__ << ": failed to log for " << address
- << ", playback_state " << playback_state
- << ", audio_coding_mode " << audio_coding_mode << ", error "
- << ret;
- }
-}
-
void LogReadRssiResult(const RawAddress& address, uint16_t handle,
uint32_t cmd_status, int8_t rssi) {
std::string obfuscated_id;
@@ -901,26 +878,6 @@ void LogManufacturerInfo(const RawAddress& address,
}
}
-void LogBluetoothHalCrashReason(const RawAddress& address, uint32_t error_code,
- uint32_t vendor_error_code) {
- std::string obfuscated_id;
- if (!address.IsEmpty()) {
- obfuscated_id = AddressObfuscator::GetInstance()->Obfuscate(address);
- }
- // nullptr and size 0 represent missing value for obfuscated_id
- android::util::BytesField obfuscated_id_field(
- address.IsEmpty() ? nullptr : obfuscated_id.c_str(),
- address.IsEmpty() ? 0 : obfuscated_id.size());
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_HAL_CRASH_REASON_REPORTED, 0,
- obfuscated_id_field, error_code, vendor_error_code);
- if (ret < 0) {
- LOG(WARNING) << __func__ << ": failed for " << address << ", error_code "
- << loghex(error_code) << ", vendor_error_code "
- << loghex(vendor_error_code) << ", error " << ret;
- }
-}
-
} // namespace common
} // namespace bluetooth
diff --git a/common/metrics.h b/common/metrics.h
index c8973f323..c4fd14fd7 100644
--- a/common/metrics.h
+++ b/common/metrics.h
@@ -360,16 +360,6 @@ void LogA2dpAudioOverrunEvent(const RawAddress& address,
int num_dropped_encoded_bytes);
/**
- * Log A2DP playback state changed event
- *
- * @param address A2DP device associated with this event
- * @param playback_state audio playback state
- * @param audio_coding_mode audio codec encoding mode
- */
-void LogA2dpPlaybackEvent(const RawAddress& address, int playback_state,
- int audio_coding_mode);
-
-/**
* Log read RSSI result
*
* @param address device associated with this event
@@ -489,16 +479,6 @@ void LogManufacturerInfo(const RawAddress& address,
const std::string& model,
const std::string& hardware_version,
const std::string& software_version);
-
-/**
- * Logs when received Bluetooth HAL crash reason report.
- *
- * @param address current connected address.
- * @param error_code the crash reason from bluetooth hal
- * @param vendor_error_code the vendor crash reason from bluetooth Firmware
- */
-void LogBluetoothHalCrashReason(const RawAddress& address, uint32_t error_code,
- uint32_t vendor_error_code);
} // namespace common
} // namespace bluetooth
diff --git a/common/metrics_linux.cc b/common/metrics_linux.cc
index f36382781..bf16960e0 100644
--- a/common/metrics_linux.cc
+++ b/common/metrics_linux.cc
@@ -88,72 +88,6 @@ void BluetoothMetricsLogger::ResetLog() {}
void BluetoothMetricsLogger::Reset() {}
-void LogClassicPairingEvent(const RawAddress& address, uint16_t handle,
- uint32_t hci_cmd, uint16_t hci_event,
- uint16_t cmd_status, uint16_t reason_code,
- int64_t event_value) {}
-
-void LogSocketConnectionState(
- const RawAddress& address, int port, int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes, int64_t rx_bytes, int uid, int server_port,
- android::bluetooth::SocketRoleEnum socket_role) {}
-
-void LogHciTimeoutEvent(uint32_t hci_cmd) {}
-
-void LogA2dpAudioUnderrunEvent(const RawAddress& address,
- uint64_t encoding_interval_millis,
- int num_missing_pcm_bytes) {}
-
-void LogA2dpAudioOverrunEvent(const RawAddress& address,
- uint64_t encoding_interval_millis,
- int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes) {}
-
-void LogA2dpPlaybackEvent(const RawAddress& address, int playback_state,
- int audio_coding_mode) {}
-
-void LogBluetoothHalCrashReason(const RawAddress& address, uint32_t error_code,
- uint32_t vendor_error_code) {}
-
-void LogReadRssiResult(const RawAddress& address, uint16_t handle,
- uint32_t cmd_status, int8_t rssi) {}
-
-void LogReadFailedContactCounterResult(const RawAddress& address,
- uint16_t handle, uint32_t cmd_status,
- int32_t failed_contact_counter) {}
-
-void LogReadTxPowerLevelResult(const RawAddress& address, uint16_t handle,
- uint32_t cmd_status,
- int32_t transmit_power_level) {}
-
-void LogRemoteVersionInfo(uint16_t handle, uint8_t status, uint8_t version,
- uint16_t manufacturer_name, uint16_t subversion) {}
-
-void LogLinkLayerConnectionEvent(const RawAddress* address,
- uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction,
- uint16_t link_type, uint32_t hci_cmd,
- uint16_t hci_event, uint16_t hci_ble_event,
- uint16_t cmd_status, uint16_t reason_code) {}
-
-void LogManufacturerInfo(const RawAddress& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer,
- const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version) {}
-
-void LogSdpAttribute(const RawAddress& address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value) {}
-
-void LogSmpPairingEvent(const RawAddress& address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason) {}
-
} // namespace common
} // namespace bluetooth
diff --git a/common/os_utils.cc b/common/os_utils.cc
deleted file mode 100644
index d6a0f322f..000000000
--- a/common/os_utils.cc
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifdef OS_ANDROID
-#include <private/android_filesystem_config.h>
-#include <unistd.h>
-#endif
-
-bool is_bluetooth_uid() {
-#ifdef OS_ANDROID
- return getuid() == AID_BLUETOOTH;
-#else
- return false;
-#endif
-}
diff --git a/common/os_utils.h b/common/os_utils.h
deleted file mode 100644
index cf9424367..000000000
--- a/common/os_utils.h
+++ /dev/null
@@ -1,17 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-bool is_bluetooth_uid();
diff --git a/common/stop_watch_legacy.cc b/common/stop_watch_legacy.cc
deleted file mode 100644
index a2bb562fa..000000000
--- a/common/stop_watch_legacy.cc
+++ /dev/null
@@ -1,105 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "BtStopWatchLegacy"
-
-#include "common/stop_watch_legacy.h"
-
-#include <iomanip>
-#include <mutex>
-#include <sstream>
-#include <utility>
-
-#include <base/logging.h>
-#include "osi/include/log.h"
-
-namespace bluetooth {
-namespace common {
-
-static const int LOG_BUFFER_LENGTH = 10;
-static std::array<StopWatchLog, LOG_BUFFER_LENGTH> stopwatch_logs;
-static int current_buffer_index;
-static std::recursive_mutex stopwatch_log_mutex;
-
-void StopWatchLegacy::RecordLog(StopWatchLog log) {
- std::unique_lock<std::recursive_mutex> lock(stopwatch_log_mutex, std::defer_lock);
- if (!lock.try_lock()) {
- LOG_INFO("try_lock fail. log content: %s, took %zu us", log.message.c_str(),
- static_cast<size_t>(
- std::chrono::duration_cast<std::chrono::microseconds>(
- stopwatch_logs[current_buffer_index].end_timestamp -
- stopwatch_logs[current_buffer_index].start_timestamp)
- .count()));
- return;
- }
- if (current_buffer_index >= LOG_BUFFER_LENGTH) {
- current_buffer_index = 0;
- }
- stopwatch_logs[current_buffer_index] = std::move(log);
- current_buffer_index++;
- lock.unlock();
-}
-
-void StopWatchLegacy::DumpStopWatchLog() {
- std::lock_guard<std::recursive_mutex> lock(stopwatch_log_mutex);
- LOG_INFO("=====================================");
- LOG_INFO("bluetooth stopwatch log history:");
- for (int i = 0; i < LOG_BUFFER_LENGTH; i++) {
- if (current_buffer_index >= LOG_BUFFER_LENGTH) {
- current_buffer_index = 0;
- }
- if (stopwatch_logs[current_buffer_index].message.empty()) {
- current_buffer_index++;
- continue;
- }
- std::stringstream ss;
- auto now = stopwatch_logs[current_buffer_index].timestamp;
- auto millis = std::chrono::duration_cast<std::chrono::milliseconds>(
- now.time_since_epoch()) %
- 1000;
- auto now_time_t = std::chrono::system_clock::to_time_t(now);
- ss << std::put_time(std::localtime(&now_time_t), "%Y-%m-%d %H:%M:%S");
- ss << '.' << std::setfill('0') << std::setw(3) << millis.count();
- std::string start_timestamp = ss.str();
- LOG_INFO("%s: %s: took %zu us", start_timestamp.c_str(),
- stopwatch_logs[current_buffer_index].message.c_str(),
- static_cast<size_t>(
- std::chrono::duration_cast<std::chrono::microseconds>(
- stopwatch_logs[current_buffer_index].end_timestamp -
- stopwatch_logs[current_buffer_index].start_timestamp)
- .count()));
- current_buffer_index++;
- }
- LOG_INFO("=====================================");
-}
-
-StopWatchLegacy::StopWatchLegacy(std::string text)
- : text_(std::move(text)),
- timestamp_(std::chrono::system_clock::now()),
- start_timestamp_(std::chrono::high_resolution_clock::now()) {}
-
-StopWatchLegacy::~StopWatchLegacy() {
- StopWatchLog sw_log;
- sw_log.timestamp = timestamp_;
- sw_log.start_timestamp = start_timestamp_;
- sw_log.end_timestamp = std::chrono::high_resolution_clock::now();
- sw_log.message = std::move(text_);
-
- RecordLog(std::move(sw_log));
-}
-
-} // namespace common
-} // namespace bluetooth
diff --git a/common/stop_watch_legacy.h b/common/stop_watch_legacy.h
deleted file mode 100644
index 2573d99cd..000000000
--- a/common/stop_watch_legacy.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <chrono>
-#include <string>
-
-namespace bluetooth {
-namespace common {
-
-typedef struct {
- std::chrono::system_clock::time_point timestamp;
- std::chrono::high_resolution_clock::time_point start_timestamp;
- std::chrono::high_resolution_clock::time_point end_timestamp;
- std::string message;
-} StopWatchLog;
-
-class StopWatchLegacy {
- public:
- static void DumpStopWatchLog(void);
- StopWatchLegacy(std::string text);
- ~StopWatchLegacy();
-
- private:
- std::string text_;
- std::chrono::system_clock::time_point timestamp_;
- std::chrono::high_resolution_clock::time_point start_timestamp_;
- void RecordLog(StopWatchLog log);
-};
-
-} // namespace common
-} // namespace bluetooth
diff --git a/common/test/thread_performance_test.cc b/common/test/thread_performance_test.cc
index b9ab10605..4c38feda9 100644
--- a/common/test/thread_performance_test.cc
+++ b/common/test/thread_performance_test.cc
@@ -26,7 +26,6 @@
#include <iostream>
#include <thread>
-#include "abstract_message_loop.h"
#include "common/message_loop_thread.h"
#include "osi/include/fixed_queue.h"
#include "osi/include/thread.h"
@@ -77,7 +76,7 @@ class MessageLoopPerformanceTest : public PerformanceTest {
return nullptr;
}
void RunMessageLoop() {
- message_loop_ = new btbase::AbstractMessageLoop();
+ message_loop_ = new base::MessageLoop();
run_loop_ = new base::RunLoop();
message_loop_->task_runner()->PostTask(
FROM_HERE, base::Bind(&std::promise<void>::set_value,
@@ -90,7 +89,7 @@ class MessageLoopPerformanceTest : public PerformanceTest {
}
protected:
- btbase::AbstractMessageLoop* message_loop_ = nullptr;
+ base::MessageLoop* message_loop_ = nullptr;
base::RunLoop* run_loop_ = nullptr;
};
diff --git a/conf/Android.bp b/conf/Android.bp
index 9fe5ab1f6..ecf492201 100644
--- a/conf/Android.bp
+++ b/conf/Android.bp
@@ -1,14 +1,5 @@
// Bluetooth bt_stack.conf config file
// ========================================================
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
prebuilt_etc {
name: "bt_stack.conf",
src: "bt_stack.conf",
diff --git a/device/Android.bp b/device/Android.bp
index 52db73317..0b7cda7a9 100644
--- a/device/Android.bp
+++ b/device/Android.bp
@@ -1,14 +1,5 @@
// Bluetooth device static library for target
// ========================================================
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "libbtdevice",
defaults: ["fluoride_defaults"],
diff --git a/device/BUILD.gn b/device/BUILD.gn
index b0c026146..5de439d30 100644
--- a/device/BUILD.gn
+++ b/device/BUILD.gn
@@ -22,46 +22,37 @@ static_library("device") {
]
include_dirs = [
- "//bt/",
- "//bt/btcore/include",
- "//bt/hci/include",
- "//bt/internal_include",
- "//bt/stack/include",
- ]
-
- configs += [
- "//bt:target_defaults",
+ "//",
+ "//btcore/include",
+ "//hci/include",
+ "//internal_include",
+ "//stack/include",
]
deps = [
- "//bt/gd/rust/shim:init_flags_bridge_header",
- "//bt/gd/rust/shim:message_loop_thread_bridge_header",
+ "//third_party/libchrome:base",
]
}
-if (use.test) {
- executable("net_test_device") {
- sources = [
- "//bt/osi/test/AllocationTestHarness.cc",
- ]
-
- include_dirs = [ "//bt" ]
+executable("net_test_device") {
+ testonly = true
+ sources = [
+ "//osi/test/AllocationTestHarness.cc",
+ ]
- deps = [
- "//bt/device",
- "//bt/btcore",
- "//bt/osi",
- ]
+ include_dirs = [ "//" ]
- configs += [
- "//bt:external_gtest_main",
- "//bt:target_defaults",
- ]
+ deps = [
+ "//device",
+ "//btcore",
+ "//osi",
+ "//third_party/googletest:gtest_main",
+ "//third_party/libchrome:base",
+ ]
- libs = [
- "pthread",
- "rt",
- "dl",
- ]
- }
+ libs = [
+ "-lpthread",
+ "-lrt",
+ "-ldl",
+ ]
}
diff --git a/device/include/controller.h b/device/include/controller.h
index 4d1fdf46b..2127b27ae 100644
--- a/device/include/controller.h
+++ b/device/include/controller.h
@@ -21,7 +21,7 @@
#include <stdbool.h>
#include <stdint.h>
-#include "btcore/include/device_features.h"
+#include "device_features.h"
#include "hci/include/hci_layer.h"
#include "hci/include/hci_packet_factory.h"
#include "hci/include/hci_packet_parser.h"
@@ -34,6 +34,10 @@ typedef struct controller_t {
const RawAddress* (*get_address)(void);
const bt_version_t* (*get_bt_version)(void);
+ const bt_device_features_t* (*get_features_classic)(int index);
+ uint8_t (*get_last_features_classic_index)(void);
+
+ const bt_device_features_t* (*get_features_ble)(void);
const uint8_t* (*get_ble_supported_states)(void);
bool (*supports_simple_pairing)(void);
@@ -43,31 +47,9 @@ typedef struct controller_t {
bool (*supports_interlaced_inquiry_scan)(void);
bool (*supports_rssi_with_inquiry_results)(void);
bool (*supports_extended_inquiry_response)(void);
- bool (*supports_central_peripheral_role_switch)(void);
+ bool (*supports_master_slave_role_switch)(void);
bool (*supports_enhanced_setup_synchronous_connection)(void);
bool (*supports_enhanced_accept_synchronous_connection)(void);
- bool (*supports_3_slot_packets)(void);
- bool (*supports_5_slot_packets)(void);
- bool (*supports_classic_2m_phy)(void);
- bool (*supports_classic_3m_phy)(void);
- bool (*supports_3_slot_edr_packets)(void);
- bool (*supports_5_slot_edr_packets)(void);
- bool (*supports_sco)(void);
- bool (*supports_hv2_packets)(void);
- bool (*supports_hv3_packets)(void);
- bool (*supports_ev3_packets)(void);
- bool (*supports_ev4_packets)(void);
- bool (*supports_ev5_packets)(void);
- bool (*supports_esco_2m_phy)(void);
- bool (*supports_esco_3m_phy)(void);
- bool (*supports_3_slot_esco_edr_packets)(void);
- bool (*supports_role_switch)(void);
- bool (*supports_hold_mode)(void);
- bool (*supports_sniff_mode)(void);
- bool (*supports_park_mode)(void);
- bool (*supports_non_flushable_pb)(void);
- bool (*supports_sniff_subrating)(void);
- bool (*supports_encryption_pause)(void);
bool (*supports_ble)(void);
bool (*supports_ble_packet_extension)(void);
@@ -78,40 +60,27 @@ typedef struct controller_t {
bool (*supports_ble_coded_phy)(void);
bool (*supports_ble_extended_advertising)(void);
bool (*supports_ble_periodic_advertising)(void);
- bool (*supports_ble_peripheral_initiated_feature_exchange)(void);
- bool (*supports_ble_connection_parameter_request)(void);
- bool (*supports_ble_periodic_advertising_sync_transfer_sender)(void);
- bool (*supports_ble_periodic_advertising_sync_transfer_recipient)(void);
- bool (*supports_ble_connected_isochronous_stream_central)(void);
- bool (*supports_ble_connected_isochronous_stream_peripheral)(void);
- bool (*supports_ble_isochronous_broadcaster)(void);
- bool (*supports_ble_synchronized_receiver)(void);
// Get the cached acl data sizes for the controller.
uint16_t (*get_acl_data_size_classic)(void);
uint16_t (*get_acl_data_size_ble)(void);
- uint16_t (*get_iso_data_size)(void);
// Get the cached acl packet sizes for the controller.
// This is a convenience function for the respective
// acl data size + size of the acl header.
uint16_t (*get_acl_packet_size_classic)(void);
uint16_t (*get_acl_packet_size_ble)(void);
- uint16_t (*get_iso_packet_size)(void);
uint16_t (*get_ble_default_data_packet_length)(void);
uint16_t (*get_ble_maximum_tx_data_length)(void);
- uint16_t (*get_ble_maximum_tx_time)(void);
uint16_t (*get_ble_maxium_advertising_data_length)(void);
uint8_t (*get_ble_number_of_supported_advertising_sets)(void);
- uint8_t (*get_ble_periodic_advertiser_list_size)(void);
// Get the number of acl packets the controller can buffer.
uint16_t (*get_acl_buffer_count_classic)(void);
uint8_t (*get_acl_buffer_count_ble)(void);
- uint8_t (*get_iso_buffer_count)(void);
- uint8_t (*get_ble_acceptlist_size)(void);
+ uint8_t (*get_ble_white_list_size)(void);
uint8_t (*get_ble_resolving_list_max_size)(void);
void (*set_ble_resolving_list_max_size)(int resolving_list_max_size);
@@ -120,6 +89,12 @@ typedef struct controller_t {
} controller_t;
+namespace bluetooth {
+namespace legacy {
+const controller_t* controller_get_interface();
+} // namespace legacy
+} // namespace bluetooth
+
const controller_t* controller_get_interface();
const controller_t* controller_get_test_interface(
diff --git a/device/include/esco_parameters.h b/device/include/esco_parameters.h
index 6df628949..b79948d00 100644
--- a/device/include/esco_parameters.h
+++ b/device/include/esco_parameters.h
@@ -30,14 +30,12 @@ typedef enum {
} sco_codec_t;
typedef enum {
- SCO_CODEC_CVSD_D1 = 0,
- ESCO_CODEC_CVSD_S3,
- ESCO_CODEC_CVSD_S4,
+ ESCO_CODEC_CVSD = 0,
ESCO_CODEC_MSBC_T1,
ESCO_CODEC_MSBC_T2,
} esco_codec_t;
-#define ESCO_NUM_CODECS 5
+#define ESCO_NUM_CODECS 3
// Coding Formats (BT 4.1 or later Assigned numbers)
#define ESCO_CODING_FORMAT_ULAW ((uint8_t)0x00) /* u-Law log */
diff --git a/device/include/interop.h b/device/include/interop.h
index 2e9a266fd..d7ca917bd 100644
--- a/device/include/interop.h
+++ b/device/include/interop.h
@@ -46,7 +46,7 @@ typedef enum {
// Disable automatic pairing with headsets/car-kits
// Some car kits do not react kindly to a failed pairing attempt and
- // do not allow immediate re-pairing. Rejectlist these so that the initial
+ // do not allow immediate re-pairing. Blacklist these so that the initial
// pairing attempt makes it to the user instead.
INTEROP_DISABLE_AUTO_PAIRING,
@@ -80,7 +80,7 @@ typedef enum {
// but fail to play the reconfigured audio stream.
INTEROP_DISABLE_AVDTP_RECONFIGURE,
- // Create dynamic rejectlist to disable role switch.
+ // Create dynamic blacklist to disable role switch.
// Some car kits indicate that role switch is supported, but then reject
// role switch attempts. After rejecting several role switch attempts,
// such car kits will go into bad state.
@@ -99,23 +99,7 @@ typedef enum {
// The public address of these devices are same as the Random address in ADV.
// Then will get name by LE_Create_connection, actually fails,
// but will block pairing.
- INTEROP_DISABLE_NAME_REQUEST,
-
- // Respond AVRCP profile version only 1.4 for some device.
- INTEROP_AVRCP_1_4_ONLY,
-
- // Disable sniff mode for headsets/car-kits
- // Some car kits supports sniff mode but when DUT initiates sniff req
- // Remote will go to bad state and its leads to LMP time out.
- INTEROP_DISABLE_SNIFF,
-
- // Do not send AVDTP SUSPEND while the playback is paused.
- // Some older A2DP Sink devices might not support to pause the streaming.
- INTEROP_DISABLE_AVDTP_SUSPEND,
-
- // Some car kits do not send the AT+BIND command while establishing the SLC
- // which causes an HFP profile connection failure
- INTEROP_SLC_SKIP_BIND_COMMAND
+ INTEROP_DISABLE_NAME_REQUEST
} interop_feature_t;
// Check if a given |addr| matches a known interoperability workaround as
diff --git a/device/include/interop_database.h b/device/include/interop_database.h
index 159cfacc5..b4b1b07d9 100644
--- a/device/include/interop_database.h
+++ b/device/include/interop_database.h
@@ -150,27 +150,6 @@ static const interop_addr_entry_t interop_addr_database[] = {
// for skip name request,
// because BR/EDR address and ADV random address are the same
{{{0xd4, 0x7a, 0xe2, 0, 0, 0}}, 3, INTEROP_DISABLE_NAME_REQUEST},
-
- // Lexus Carkit
- {{{0x64, 0xd4, 0xbd, 0, 0, 0}}, 3, INTEROP_AVRCP_1_4_ONLY},
-
- // Mazda Carkit
- {{{0xfc, 0x35, 0xe6, 0, 0, 0}}, 3, INTEROP_AVRCP_1_4_ONLY},
-
- // Toyota Car Audio
- {{{0x00, 0x17, 0x53, 0, 0, 0}}, 3, INTEROP_AVRCP_1_4_ONLY},
-
- // Honda High End Carkit
- {{{0x9c, 0x8d, 0x7c, 0, 0, 0}}, 3, INTEROP_AVRCP_1_4_ONLY},
-
- // Honda Civic Carkit
- {{{0x0c, 0xd9, 0xc1, 0, 0, 0}}, 3, INTEROP_AVRCP_1_4_ONLY},
-
- // KDDI Carkit
- {{{0x44, 0xea, 0xd8, 0, 0, 0}}, 3, INTEROP_DISABLE_SNIFF},
-
- // Toyota Camry 2018 Carkit HFP AT+BIND missing
- {{{0x94, 0xb2, 0xcc, 0x30, 0, 0}}, 4, INTEROP_SLC_SKIP_BIND_COMMAND}
};
typedef struct {
diff --git a/device/src/controller.cc b/device/src/controller.cc
index d312e36ad..a260b98c6 100644
--- a/device/src/controller.cc
+++ b/device/src/controller.cc
@@ -30,16 +30,15 @@
#include "main/shim/controller.h"
#include "main/shim/shim.h"
#include "osi/include/future.h"
-#include "osi/include/properties.h"
#include "stack/include/btm_ble_api.h"
-const bt_event_mask_t BLE_EVENT_MASK = {{0x00, 0x00, 0x00, 0x00, 0x7F, 0x02,
+const bt_event_mask_t BLE_EVENT_MASK = {{0x00, 0x00, 0x00, 0x00, 0x00, 0x02,
#if (BLE_PRIVACY_SPT == TRUE)
- 0xFE,
+ 0x1E,
#else
/* Disable "LE Enhanced Connection
Complete" when privacy is off */
- 0xFC,
+ 0x1C,
#endif
0x7f}};
@@ -53,7 +52,6 @@ const uint8_t SCO_HOST_BUFFER_SIZE = 0xff;
#define BLE_SUPPORTED_STATES_SIZE 8
#define BLE_SUPPORTED_FEATURES_SIZE 8
#define MAX_LOCAL_SUPPORTED_CODECS_SIZE 8
-#define LL_FEATURE_BIT_ISO_HOST_SUPPORT 32
static const hci_t* local_hci;
static const hci_packet_factory_t* packet_factory;
@@ -68,13 +66,10 @@ static uint8_t last_features_classic_page_index;
static uint16_t acl_data_size_classic;
static uint16_t acl_data_size_ble;
-static uint16_t iso_data_size;
-
static uint16_t acl_buffer_count_classic;
static uint8_t acl_buffer_count_ble;
-static uint8_t iso_buffer_count;
-static uint8_t ble_acceptlist_size;
+static uint8_t ble_white_list_size;
static uint8_t ble_resolving_list_max_size;
static uint8_t ble_supported_states[BLE_SUPPORTED_STATES_SIZE];
static bt_device_features_t features_ble;
@@ -86,13 +81,11 @@ static uint16_t ble_supported_max_rx_time;
static uint16_t ble_maxium_advertising_data_length;
static uint8_t ble_number_of_supported_advertising_sets;
-static uint8_t ble_periodic_advertiser_list_size;
static uint8_t local_supported_codecs[MAX_LOCAL_SUPPORTED_CODECS_SIZE];
static uint8_t number_of_local_supported_codecs = 0;
static bool readable;
static bool ble_supported;
-static bool iso_supported;
static bool simple_pairing_supported;
static bool secure_connections_supported;
@@ -202,34 +195,15 @@ static future_t* start_up(void) {
ble_supported = last_features_classic_page_index >= 1 &&
HCI_LE_HOST_SUPPORTED(features_classic[1].as_array);
if (ble_supported) {
- // Request the ble acceptlist size next
- response = AWAIT_COMMAND(packet_factory->make_ble_read_acceptlist_size());
- packet_parser->parse_ble_read_acceptlist_size_response(
- response, &ble_acceptlist_size);
-
- // Request the ble supported features next
- response =
- AWAIT_COMMAND(packet_factory->make_ble_read_local_supported_features());
- packet_parser->parse_ble_read_local_supported_features_response(
- response, &features_ble);
-
- iso_supported = HCI_LE_CIS_CENTRAL(features_ble.as_array) ||
- HCI_LE_CIS_PERIPHERAL(features_ble.as_array) ||
- HCI_LE_ISO_BROADCASTER(features_ble.as_array);
+ // Request the ble white list size next
+ response = AWAIT_COMMAND(packet_factory->make_ble_read_white_list_size());
+ packet_parser->parse_ble_read_white_list_size_response(
+ response, &ble_white_list_size);
- if (iso_supported) {
- // Request the ble buffer size next
- response = AWAIT_COMMAND(packet_factory->make_ble_read_buffer_size_v2());
- packet_parser->parse_ble_read_buffer_size_v2_response(
- response, &acl_data_size_ble, &acl_buffer_count_ble, &iso_data_size,
- &iso_buffer_count);
-
- } else {
- // Request the ble buffer size next
- response = AWAIT_COMMAND(packet_factory->make_ble_read_buffer_size());
- packet_parser->parse_ble_read_buffer_size_response(
- response, &acl_data_size_ble, &acl_buffer_count_ble);
- }
+ // Request the ble buffer size next
+ response = AWAIT_COMMAND(packet_factory->make_ble_read_buffer_size());
+ packet_parser->parse_ble_read_buffer_size_response(
+ response, &acl_data_size_ble, &acl_buffer_count_ble);
// Response of 0 indicates ble has the same buffer size as classic
if (acl_data_size_ble == 0) acl_data_size_ble = acl_data_size_classic;
@@ -239,6 +213,12 @@ static future_t* start_up(void) {
packet_parser->parse_ble_read_supported_states_response(
response, ble_supported_states, sizeof(ble_supported_states));
+ // Request the ble supported features next
+ response =
+ AWAIT_COMMAND(packet_factory->make_ble_read_local_supported_features());
+ packet_parser->parse_ble_read_local_supported_features_response(
+ response, &features_ble);
+
if (HCI_LE_ENHANCED_PRIVACY_SUPPORTED(features_ble.as_array)) {
response =
AWAIT_COMMAND(packet_factory->make_ble_read_resolving_list_size());
@@ -274,24 +254,10 @@ static future_t* start_up(void) {
ble_maxium_advertising_data_length = 31;
}
- if (HCI_LE_PERIODIC_ADVERTISING_SUPPORTED(features_ble.as_array)) {
- response = AWAIT_COMMAND(
- packet_factory->make_ble_read_periodic_advertiser_list_size());
-
- packet_parser->parse_ble_read_size_of_advertiser_list(
- response, &ble_periodic_advertiser_list_size);
- }
-
// Set the ble event mask next
response =
AWAIT_COMMAND(packet_factory->make_ble_set_event_mask(&BLE_EVENT_MASK));
packet_parser->parse_generic_command_complete(response);
-
- if (HCI_LE_SET_HOST_FEATURE_SUPPORTED(supported_commands)) {
- response = AWAIT_COMMAND(packet_factory->make_ble_set_host_features(
- LL_FEATURE_BIT_ISO_HOST_SUPPORT, 0x01));
- packet_parser->parse_generic_command_complete(response);
- }
}
if (simple_pairing_supported) {
@@ -343,6 +309,18 @@ static const bt_version_t* get_bt_version(void) {
return &bt_version;
}
+// TODO(zachoverflow): hide inside, move decoder inside too
+static const bt_device_features_t* get_features_classic(int index) {
+ CHECK(readable);
+ CHECK(index < MAX_FEATURES_CLASSIC_PAGE_COUNT);
+ return &features_classic[index];
+}
+
+static uint8_t get_last_features_classic_index(void) {
+ CHECK(readable);
+ return last_features_classic_page_index;
+}
+
static uint8_t* get_local_supported_codecs(uint8_t* number_of_codecs) {
CHECK(readable);
if (number_of_local_supported_codecs) {
@@ -352,6 +330,12 @@ static uint8_t* get_local_supported_codecs(uint8_t* number_of_codecs) {
return NULL;
}
+static const bt_device_features_t* get_features_ble(void) {
+ CHECK(readable);
+ CHECK(ble_supported);
+ return &features_ble;
+}
+
static const uint8_t* get_ble_supported_states(void) {
CHECK(readable);
CHECK(ble_supported);
@@ -393,7 +377,7 @@ static bool supports_extended_inquiry_response(void) {
return HCI_EXT_INQ_RSP_SUPPORTED(features_classic[0].as_array);
}
-static bool supports_central_peripheral_role_switch(void) {
+static bool supports_master_slave_role_switch(void) {
CHECK(readable);
return HCI_SWITCH_SUPPORTED(features_classic[0].as_array);
}
@@ -408,116 +392,6 @@ static bool supports_enhanced_accept_synchronous_connection(void) {
return HCI_ENH_ACCEPT_SYNCH_CONN_SUPPORTED(supported_commands);
}
-static bool supports_3_slot_packets(void) {
- CHECK(readable);
- return HCI_3_SLOT_PACKETS_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_5_slot_packets(void) {
- CHECK(readable);
- return HCI_5_SLOT_PACKETS_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_classic_2m_phy(void) {
- CHECK(readable);
- return HCI_EDR_ACL_2MPS_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_classic_3m_phy(void) {
- CHECK(readable);
- return HCI_EDR_ACL_3MPS_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_3_slot_edr_packets(void) {
- CHECK(readable);
- return HCI_3_SLOT_EDR_ACL_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_5_slot_edr_packets(void) {
- CHECK(readable);
- return HCI_5_SLOT_EDR_ACL_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_sco(void) {
- CHECK(readable);
- return HCI_SCO_LINK_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_hv2_packets(void) {
- CHECK(readable);
- return HCI_HV2_PACKETS_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_hv3_packets(void) {
- CHECK(readable);
- return HCI_HV3_PACKETS_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_ev3_packets(void) {
- CHECK(readable);
- return HCI_ESCO_EV3_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_ev4_packets(void) {
- CHECK(readable);
- return HCI_ESCO_EV4_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_ev5_packets(void) {
- CHECK(readable);
- return HCI_ESCO_EV5_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_esco_2m_phy(void) {
- CHECK(readable);
- return HCI_EDR_ESCO_2MPS_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_esco_3m_phy(void) {
- CHECK(readable);
- return HCI_EDR_ESCO_3MPS_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_3_slot_esco_edr_packets(void) {
- CHECK(readable);
- return HCI_3_SLOT_EDR_ESCO_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_role_switch(void) {
- CHECK(readable);
- return HCI_SWITCH_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_hold_mode(void) {
- CHECK(readable);
- return HCI_HOLD_MODE_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_sniff_mode(void) {
- CHECK(readable);
- return HCI_SNIFF_MODE_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_park_mode(void) {
- CHECK(readable);
- return HCI_PARK_MODE_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_non_flushable_pb(void) {
- CHECK(readable);
- return HCI_NON_FLUSHABLE_PB_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_sniff_subrating(void) {
- CHECK(readable);
- return HCI_SNIFF_SUB_RATE_SUPPORTED(features_classic[0].as_array);
-}
-
-static bool supports_encryption_pause(void) {
- CHECK(readable);
- return HCI_ATOMIC_ENCRYPT_SUPPORTED(features_classic[0].as_array);
-}
-
static bool supports_ble(void) {
CHECK(readable);
return ble_supported;
@@ -572,56 +446,6 @@ static bool supports_ble_periodic_advertising(void) {
return HCI_LE_PERIODIC_ADVERTISING_SUPPORTED(features_ble.as_array);
}
-static bool supports_ble_peripheral_initiated_feature_exchange(void) {
- CHECK(readable);
- CHECK(ble_supported);
- return HCI_LE_PERIPHERAL_INIT_FEAT_EXC_SUPPORTED(features_ble.as_array);
-}
-
-static bool supports_ble_connection_parameter_request(void) {
- CHECK(readable);
- CHECK(ble_supported);
- return HCI_LE_CONN_PARAM_REQ_SUPPORTED(features_ble.as_array);
-}
-
-static bool supports_ble_periodic_advertising_sync_transfer_sender(void) {
- CHECK(readable);
- CHECK(ble_supported);
- return HCI_LE_PERIODIC_ADVERTISING_SYNC_TRANSFER_SENDER(
- features_ble.as_array);
-}
-
-static bool supports_ble_periodic_advertising_sync_transfer_recipient(void) {
- CHECK(readable);
- CHECK(ble_supported);
- return HCI_LE_PERIODIC_ADVERTISING_SYNC_TRANSFER_RECIPIENT(
- features_ble.as_array);
-}
-
-static bool supports_ble_connected_isochronous_stream_central(void) {
- CHECK(readable);
- CHECK(ble_supported);
- return HCI_LE_CIS_CENTRAL(features_ble.as_array);
-}
-
-static bool supports_ble_connected_isochronous_stream_peripheral(void) {
- CHECK(readable);
- CHECK(ble_supported);
- return HCI_LE_CIS_PERIPHERAL(features_ble.as_array);
-}
-
-static bool supports_ble_isochronous_broadcaster(void) {
- CHECK(readable);
- CHECK(ble_supported);
- return HCI_LE_ISO_BROADCASTER(features_ble.as_array);
-}
-
-static bool supports_ble_synchronized_receiver(void) {
- CHECK(readable);
- CHECK(ble_supported);
- return HCI_LE_SYNCHRONIZED_RECEIVER(features_ble.as_array);
-}
-
static uint16_t get_acl_data_size_classic(void) {
CHECK(readable);
return acl_data_size_classic;
@@ -633,11 +457,6 @@ static uint16_t get_acl_data_size_ble(void) {
return acl_data_size_ble;
}
-static uint16_t get_iso_data_size(void) {
- CHECK(readable);
- return iso_data_size;
-}
-
static uint16_t get_acl_packet_size_classic(void) {
CHECK(readable);
return acl_data_size_classic + HCI_DATA_PREAMBLE_SIZE;
@@ -648,11 +467,6 @@ static uint16_t get_acl_packet_size_ble(void) {
return acl_data_size_ble + HCI_DATA_PREAMBLE_SIZE;
}
-static uint16_t get_iso_packet_size(void) {
- CHECK(readable);
- return iso_data_size + HCI_DATA_PREAMBLE_SIZE;
-}
-
static uint16_t get_ble_suggested_default_data_length(void) {
CHECK(readable);
CHECK(ble_supported);
@@ -665,12 +479,6 @@ static uint16_t get_ble_maximum_tx_data_length(void) {
return ble_supported_max_tx_octets;
}
-static uint16_t get_ble_maximum_tx_time(void) {
- CHECK(readable);
- CHECK(ble_supported);
- return ble_supported_max_tx_time;
-}
-
static uint16_t get_ble_maxium_advertising_data_length(void) {
CHECK(readable);
CHECK(ble_supported);
@@ -683,12 +491,6 @@ static uint8_t get_ble_number_of_supported_advertising_sets(void) {
return ble_number_of_supported_advertising_sets;
}
-static uint8_t get_ble_periodic_advertiser_list_size(void) {
- CHECK(readable);
- CHECK(ble_supported);
- return ble_periodic_advertiser_list_size;
-}
-
static uint16_t get_acl_buffer_count_classic(void) {
CHECK(readable);
return acl_buffer_count_classic;
@@ -700,16 +502,10 @@ static uint8_t get_acl_buffer_count_ble(void) {
return acl_buffer_count_ble;
}
-static uint8_t get_iso_buffer_count(void) {
+static uint8_t get_ble_white_list_size(void) {
CHECK(readable);
CHECK(ble_supported);
- return iso_buffer_count;
-}
-
-static uint8_t get_ble_acceptlist_size(void) {
- CHECK(readable);
- CHECK(ble_supported);
- return ble_acceptlist_size;
+ return ble_white_list_size;
}
static uint8_t get_ble_resolving_list_max_size(void) {
@@ -742,6 +538,10 @@ static const controller_t interface = {
get_address,
get_bt_version,
+ get_features_classic,
+ get_last_features_classic_index,
+
+ get_features_ble,
get_ble_supported_states,
supports_simple_pairing,
@@ -751,31 +551,9 @@ static const controller_t interface = {
supports_interlaced_inquiry_scan,
supports_rssi_with_inquiry_results,
supports_extended_inquiry_response,
- supports_central_peripheral_role_switch,
+ supports_master_slave_role_switch,
supports_enhanced_setup_synchronous_connection,
supports_enhanced_accept_synchronous_connection,
- supports_3_slot_packets,
- supports_5_slot_packets,
- supports_classic_2m_phy,
- supports_classic_3m_phy,
- supports_3_slot_edr_packets,
- supports_5_slot_edr_packets,
- supports_sco,
- supports_hv2_packets,
- supports_hv3_packets,
- supports_ev3_packets,
- supports_ev4_packets,
- supports_ev5_packets,
- supports_esco_2m_phy,
- supports_esco_3m_phy,
- supports_3_slot_esco_edr_packets,
- supports_role_switch,
- supports_hold_mode,
- supports_sniff_mode,
- supports_park_mode,
- supports_non_flushable_pb,
- supports_sniff_subrating,
- supports_encryption_pause,
supports_ble,
supports_ble_packet_extension,
@@ -786,42 +564,28 @@ static const controller_t interface = {
supports_ble_coded_phy,
supports_ble_extended_advertising,
supports_ble_periodic_advertising,
- supports_ble_peripheral_initiated_feature_exchange,
- supports_ble_connection_parameter_request,
- supports_ble_periodic_advertising_sync_transfer_sender,
- supports_ble_periodic_advertising_sync_transfer_recipient,
- supports_ble_connected_isochronous_stream_central,
- supports_ble_connected_isochronous_stream_peripheral,
- supports_ble_isochronous_broadcaster,
- supports_ble_synchronized_receiver,
get_acl_data_size_classic,
get_acl_data_size_ble,
- get_iso_data_size,
get_acl_packet_size_classic,
get_acl_packet_size_ble,
- get_iso_packet_size,
-
get_ble_suggested_default_data_length,
get_ble_maximum_tx_data_length,
- get_ble_maximum_tx_time,
get_ble_maxium_advertising_data_length,
get_ble_number_of_supported_advertising_sets,
- get_ble_periodic_advertiser_list_size,
get_acl_buffer_count_classic,
get_acl_buffer_count_ble,
- get_iso_buffer_count,
- get_ble_acceptlist_size,
+ get_ble_white_list_size,
get_ble_resolving_list_max_size,
set_ble_resolving_list_max_size,
get_local_supported_codecs,
get_le_all_initiating_phys};
-static const controller_t* controller_get_interface_legacy() {
+const controller_t* bluetooth::legacy::controller_get_interface() {
static bool loaded = false;
if (!loaded) {
loaded = true;
@@ -835,10 +599,10 @@ static const controller_t* controller_get_interface_legacy() {
}
const controller_t* controller_get_interface() {
- if (bluetooth::shim::is_gd_controller_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::controller_get_interface();
} else {
- return controller_get_interface_legacy();
+ return bluetooth::legacy::controller_get_interface();
}
}
diff --git a/device/src/esco_parameters.cc b/device/src/esco_parameters.cc
index e2a6eecce..7f550a142 100644
--- a/device/src/esco_parameters.cc
+++ b/device/src/esco_parameters.cc
@@ -21,193 +21,123 @@
#include "device/include/esco_parameters.h"
static const enh_esco_params_t default_esco_parameters[ESCO_NUM_CODECS] = {
- // CVSD D1
- {
- .transmit_bandwidth = TXRX_64KBITS_RATE,
- .receive_bandwidth = TXRX_64KBITS_RATE,
- .transmit_coding_format = {.coding_format = ESCO_CODING_FORMAT_CVSD,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .receive_coding_format = {.coding_format = ESCO_CODING_FORMAT_CVSD,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .transmit_codec_frame_size = 60,
- .receive_codec_frame_size = 60,
- .input_bandwidth = INPUT_OUTPUT_64K_RATE,
- .output_bandwidth = INPUT_OUTPUT_64K_RATE,
- .input_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
+ // CVSD
+ {.transmit_bandwidth = TXRX_64KBITS_RATE,
+ .receive_bandwidth = TXRX_64KBITS_RATE,
+ .transmit_coding_format = {.coding_format = ESCO_CODING_FORMAT_CVSD,
.company_id = 0x0000,
.vendor_specific_codec_id = 0x0000},
- .output_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .input_coded_data_size = 16,
- .output_coded_data_size = 16,
- .input_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
- .output_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
- .input_pcm_payload_msb_position = 0,
- .output_pcm_payload_msb_position = 0,
- .input_data_path = ESCO_DATA_PATH_PCM,
- .output_data_path = ESCO_DATA_PATH_PCM,
- .input_transport_unit_size = 0x00,
- .output_transport_unit_size = 0x00,
- .max_latency_ms = 0xFFFF, // Don't care
- .packet_types = (ESCO_PKT_TYPES_MASK_HV1 | ESCO_PKT_TYPES_MASK_HV2 |
- ESCO_PKT_TYPES_MASK_HV3),
- .retransmission_effort = ESCO_RETRANSMISSION_OFF,
- },
- // CVSD S3
- {
- .transmit_bandwidth = TXRX_64KBITS_RATE,
- .receive_bandwidth = TXRX_64KBITS_RATE,
- .transmit_coding_format = {.coding_format = ESCO_CODING_FORMAT_CVSD,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .receive_coding_format = {.coding_format = ESCO_CODING_FORMAT_CVSD,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .transmit_codec_frame_size = 60,
- .receive_codec_frame_size = 60,
- .input_bandwidth = INPUT_OUTPUT_64K_RATE,
- .output_bandwidth = INPUT_OUTPUT_64K_RATE,
- .input_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .output_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .input_coded_data_size = 16,
- .output_coded_data_size = 16,
- .input_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
- .output_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
- .input_pcm_payload_msb_position = 0,
- .output_pcm_payload_msb_position = 0,
- .input_data_path = ESCO_DATA_PATH_PCM,
- .output_data_path = ESCO_DATA_PATH_PCM,
- .input_transport_unit_size = 0x00,
- .output_transport_unit_size = 0x00,
- .max_latency_ms = 10,
- .packet_types =
- (ESCO_PKT_TYPES_MASK_HV1 | ESCO_PKT_TYPES_MASK_HV2 |
- ESCO_PKT_TYPES_MASK_HV3 | ESCO_PKT_TYPES_MASK_EV3 |
- ESCO_PKT_TYPES_MASK_EV4 | ESCO_PKT_TYPES_MASK_EV5 |
- ESCO_PKT_TYPES_MASK_NO_3_EV3 | ESCO_PKT_TYPES_MASK_NO_2_EV5 |
- ESCO_PKT_TYPES_MASK_NO_3_EV5),
- .retransmission_effort = ESCO_RETRANSMISSION_POWER,
- },
- // CVSD S4
- {
- .transmit_bandwidth = TXRX_64KBITS_RATE,
- .receive_bandwidth = TXRX_64KBITS_RATE,
- .transmit_coding_format = {.coding_format = ESCO_CODING_FORMAT_CVSD,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .receive_coding_format = {.coding_format = ESCO_CODING_FORMAT_CVSD,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .transmit_codec_frame_size = 60,
- .receive_codec_frame_size = 60,
- .input_bandwidth = INPUT_OUTPUT_64K_RATE,
- .output_bandwidth = INPUT_OUTPUT_64K_RATE,
- .input_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .output_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .input_coded_data_size = 16,
- .output_coded_data_size = 16,
- .input_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
- .output_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
- .input_pcm_payload_msb_position = 0,
- .output_pcm_payload_msb_position = 0,
- .input_data_path = ESCO_DATA_PATH_PCM,
- .output_data_path = ESCO_DATA_PATH_PCM,
- .input_transport_unit_size = 0x00,
- .output_transport_unit_size = 0x00,
- .max_latency_ms = 12,
- .packet_types =
- (ESCO_PKT_TYPES_MASK_HV1 | ESCO_PKT_TYPES_MASK_HV2 |
- ESCO_PKT_TYPES_MASK_HV3 | ESCO_PKT_TYPES_MASK_EV3 |
- ESCO_PKT_TYPES_MASK_EV4 | ESCO_PKT_TYPES_MASK_EV5 |
- ESCO_PKT_TYPES_MASK_NO_3_EV3 | ESCO_PKT_TYPES_MASK_NO_2_EV5 |
- ESCO_PKT_TYPES_MASK_NO_3_EV5),
- .retransmission_effort = ESCO_RETRANSMISSION_QUALITY,
+ .receive_coding_format = {.coding_format = ESCO_CODING_FORMAT_CVSD,
+ .company_id = 0x0000,
+ .vendor_specific_codec_id = 0x0000},
+ .transmit_codec_frame_size = 60,
+ .receive_codec_frame_size = 60,
+ .input_bandwidth = INPUT_OUTPUT_64K_RATE,
+ .output_bandwidth = INPUT_OUTPUT_64K_RATE,
+ .input_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
+ .company_id = 0x0000,
+ .vendor_specific_codec_id = 0x0000},
+ .output_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
+ .company_id = 0x0000,
+ .vendor_specific_codec_id = 0x0000},
+ .input_coded_data_size = 16,
+ .output_coded_data_size = 16,
+ .input_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
+ .output_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
+ .input_pcm_payload_msb_position = 0,
+ .output_pcm_payload_msb_position = 0,
+ .input_data_path = ESCO_DATA_PATH_PCM,
+ .output_data_path = ESCO_DATA_PATH_PCM,
+ .input_transport_unit_size = 0x00,
+ .output_transport_unit_size = 0x00,
+#if (BTA_HFP_VERSION >= HFP_VERSION_1_7)
+ .max_latency_ms = 12,
+#else
+ .max_latency_ms = 10,
+#endif
+
+ .packet_types =
+ (ESCO_PKT_TYPES_MASK_HV1 | ESCO_PKT_TYPES_MASK_HV2 |
+ ESCO_PKT_TYPES_MASK_HV3 | ESCO_PKT_TYPES_MASK_EV3 |
+ ESCO_PKT_TYPES_MASK_EV4 | ESCO_PKT_TYPES_MASK_EV5 |
+ ESCO_PKT_TYPES_MASK_NO_3_EV3 | ESCO_PKT_TYPES_MASK_NO_2_EV5 |
+ ESCO_PKT_TYPES_MASK_NO_3_EV5),
+#if (BTA_HFP_VERSION >= HFP_VERSION_1_7)
+ .retransmission_effort = ESCO_RETRANSMISSION_QUALITY
+#else
+ .retransmission_effort = ESCO_RETRANSMISSION_POWER
+#endif
+
},
// mSBC T1
- {
- .transmit_bandwidth = TXRX_64KBITS_RATE,
- .receive_bandwidth = TXRX_64KBITS_RATE,
- .transmit_coding_format = {.coding_format = ESCO_CODING_FORMAT_MSBC,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .receive_coding_format = {.coding_format = ESCO_CODING_FORMAT_MSBC,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .transmit_codec_frame_size = 60,
- .receive_codec_frame_size = 60,
- .input_bandwidth = INPUT_OUTPUT_128K_RATE,
- .output_bandwidth = INPUT_OUTPUT_128K_RATE,
- .input_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
+ {.transmit_bandwidth = TXRX_64KBITS_RATE,
+ .receive_bandwidth = TXRX_64KBITS_RATE,
+ .transmit_coding_format = {.coding_format = ESCO_CODING_FORMAT_MSBC,
.company_id = 0x0000,
.vendor_specific_codec_id = 0x0000},
- .output_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .input_coded_data_size = 16,
- .output_coded_data_size = 16,
- .input_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
- .output_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
- .input_pcm_payload_msb_position = 0,
- .output_pcm_payload_msb_position = 0,
- .input_data_path = ESCO_DATA_PATH_PCM,
- .output_data_path = ESCO_DATA_PATH_PCM,
- .input_transport_unit_size = 0x00,
- .output_transport_unit_size = 0x00,
- .max_latency_ms = 8,
- .packet_types =
- (ESCO_PKT_TYPES_MASK_EV3 | ESCO_PKT_TYPES_MASK_NO_3_EV3 |
- ESCO_PKT_TYPES_MASK_NO_2_EV5 | ESCO_PKT_TYPES_MASK_NO_3_EV5 |
- ESCO_PKT_TYPES_MASK_NO_2_EV3),
- .retransmission_effort = ESCO_RETRANSMISSION_QUALITY,
- },
+ .receive_coding_format = {.coding_format = ESCO_CODING_FORMAT_MSBC,
+ .company_id = 0x0000,
+ .vendor_specific_codec_id = 0x0000},
+ .transmit_codec_frame_size = 60,
+ .receive_codec_frame_size = 60,
+ .input_bandwidth = INPUT_OUTPUT_128K_RATE,
+ .output_bandwidth = INPUT_OUTPUT_128K_RATE,
+ .input_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
+ .company_id = 0x0000,
+ .vendor_specific_codec_id = 0x0000},
+ .output_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
+ .company_id = 0x0000,
+ .vendor_specific_codec_id = 0x0000},
+ .input_coded_data_size = 16,
+ .output_coded_data_size = 16,
+ .input_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
+ .output_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
+ .input_pcm_payload_msb_position = 0,
+ .output_pcm_payload_msb_position = 0,
+ .input_data_path = ESCO_DATA_PATH_PCM,
+ .output_data_path = ESCO_DATA_PATH_PCM,
+ .input_transport_unit_size = 0x00,
+ .output_transport_unit_size = 0x00,
+ .max_latency_ms = 8,
+ .packet_types =
+ (ESCO_PKT_TYPES_MASK_EV3 | ESCO_PKT_TYPES_MASK_NO_3_EV3 |
+ ESCO_PKT_TYPES_MASK_NO_2_EV5 | ESCO_PKT_TYPES_MASK_NO_3_EV5 |
+ ESCO_PKT_TYPES_MASK_NO_2_EV3),
+ .retransmission_effort = ESCO_RETRANSMISSION_QUALITY},
// mSBC T2
- {
- .transmit_bandwidth = TXRX_64KBITS_RATE,
- .receive_bandwidth = TXRX_64KBITS_RATE,
- .transmit_coding_format = {.coding_format = ESCO_CODING_FORMAT_MSBC,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .receive_coding_format = {.coding_format = ESCO_CODING_FORMAT_MSBC,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .transmit_codec_frame_size = 60,
- .receive_codec_frame_size = 60,
- .input_bandwidth = INPUT_OUTPUT_128K_RATE,
- .output_bandwidth = INPUT_OUTPUT_128K_RATE,
- .input_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
+ {.transmit_bandwidth = TXRX_64KBITS_RATE,
+ .receive_bandwidth = TXRX_64KBITS_RATE,
+ .transmit_coding_format = {.coding_format = ESCO_CODING_FORMAT_MSBC,
.company_id = 0x0000,
.vendor_specific_codec_id = 0x0000},
- .output_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
- .company_id = 0x0000,
- .vendor_specific_codec_id = 0x0000},
- .input_coded_data_size = 16,
- .output_coded_data_size = 16,
- .input_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
- .output_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
- .input_pcm_payload_msb_position = 0,
- .output_pcm_payload_msb_position = 0,
- .input_data_path = ESCO_DATA_PATH_PCM,
- .output_data_path = ESCO_DATA_PATH_PCM,
- .input_transport_unit_size = 0x00,
- .output_transport_unit_size = 0x00,
- .max_latency_ms = 13,
- .packet_types =
- (ESCO_PKT_TYPES_MASK_EV3 | ESCO_PKT_TYPES_MASK_NO_3_EV3 |
- ESCO_PKT_TYPES_MASK_NO_2_EV5 | ESCO_PKT_TYPES_MASK_NO_3_EV5),
- .retransmission_effort = ESCO_RETRANSMISSION_QUALITY,
- },
-};
+ .receive_coding_format = {.coding_format = ESCO_CODING_FORMAT_MSBC,
+ .company_id = 0x0000,
+ .vendor_specific_codec_id = 0x0000},
+ .transmit_codec_frame_size = 60,
+ .receive_codec_frame_size = 60,
+ .input_bandwidth = INPUT_OUTPUT_128K_RATE,
+ .output_bandwidth = INPUT_OUTPUT_128K_RATE,
+ .input_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
+ .company_id = 0x0000,
+ .vendor_specific_codec_id = 0x0000},
+ .output_coding_format = {.coding_format = ESCO_CODING_FORMAT_LINEAR,
+ .company_id = 0x0000,
+ .vendor_specific_codec_id = 0x0000},
+ .input_coded_data_size = 16,
+ .output_coded_data_size = 16,
+ .input_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
+ .output_pcm_data_format = ESCO_PCM_DATA_FORMAT_2_COMP,
+ .input_pcm_payload_msb_position = 0,
+ .output_pcm_payload_msb_position = 0,
+ .input_data_path = ESCO_DATA_PATH_PCM,
+ .output_data_path = ESCO_DATA_PATH_PCM,
+ .input_transport_unit_size = 0x00,
+ .output_transport_unit_size = 0x00,
+ .max_latency_ms = 13,
+ .packet_types =
+ (ESCO_PKT_TYPES_MASK_EV3 | ESCO_PKT_TYPES_MASK_NO_3_EV3 |
+ ESCO_PKT_TYPES_MASK_NO_2_EV5 | ESCO_PKT_TYPES_MASK_NO_3_EV5),
+ .retransmission_effort = ESCO_RETRANSMISSION_QUALITY}};
enh_esco_params_t esco_parameters_for_codec(esco_codec_t codec) {
CHECK(codec >= 0) << "codec index " << (int)codec << "< 0";
diff --git a/device/src/interop.cc b/device/src/interop.cc
index 4f4b5de27..9a701b1c0 100644
--- a/device/src/interop.cc
+++ b/device/src/interop.cc
@@ -50,8 +50,9 @@ bool interop_match_addr(const interop_feature_t feature,
if (interop_match_fixed_(feature, addr) ||
interop_match_dynamic_(feature, addr)) {
- LOG_INFO("%s() Device %s is a match for interop workaround %s.", __func__,
- addr->ToString().c_str(), interop_feature_string_(feature));
+ LOG_INFO(LOG_TAG, "%s() Device %s is a match for interop workaround %s.",
+ __func__, addr->ToString().c_str(),
+ interop_feature_string_(feature));
return true;
}
@@ -68,8 +69,8 @@ bool interop_match_name(const interop_feature_t feature, const char* name) {
strlen(name) >= interop_name_database[i].length &&
strncmp(name, interop_name_database[i].name,
interop_name_database[i].length) == 0) {
- LOG_INFO("%s() Device %s is a match for interop workaround %s.", __func__,
- name, interop_feature_string_(feature));
+ LOG_INFO(LOG_TAG, "%s() Device %s is a match for interop workaround %s.",
+ __func__, name, interop_feature_string_(feature));
return true;
}
}
@@ -131,10 +132,6 @@ static const char* interop_feature_string_(const interop_feature_t feature) {
CASE_RETURN_STR(INTEROP_DISABLE_ROLE_SWITCH)
CASE_RETURN_STR(INTEROP_HID_HOST_LIMIT_SNIFF_INTERVAL)
CASE_RETURN_STR(INTEROP_DISABLE_NAME_REQUEST)
- CASE_RETURN_STR(INTEROP_AVRCP_1_4_ONLY)
- CASE_RETURN_STR(INTEROP_DISABLE_SNIFF)
- CASE_RETURN_STR(INTEROP_DISABLE_AVDTP_SUSPEND)
- CASE_RETURN_STR(INTEROP_SLC_SKIP_BIND_COMMAND);
}
return "UNKNOWN";
diff --git a/doc/btsnoop_net.md b/doc/btsnoop_net.md
index 6964a9add..25009081a 100644
--- a/doc/btsnoop_net.md
+++ b/doc/btsnoop_net.md
@@ -3,14 +3,13 @@ btsnoop_net
btsnoop_net exposes Bluetooth snoop logs over a local TCP socket which enables
real-time debugging of HCI data with hcidump.
-This feature is enabled by enabling "Enable Bluetooth HCI snoop log" in the
-Developer options and setting BT_NET_DEBUG flag to TRUE in the btsnoop_net.cc.
+This feature is enabled by setting `BtSnoopLogOutput=true` in `bt_stack.conf`.
Once it has been enabled and the stack restarted, the stack will listen for
incoming TCP connections on port 8872.
-To use this feature with btmon on a Linux host, you can run:
+To use this feature with hcidump on a Linux host, you can run:
```
$ adb forward tcp:8872 tcp:8872
- $ nc localhost 8872 | btmon -P -r /dev/stdin
+ $ nc localhost 8872 | hcidump -r /dev/stdin
```
diff --git a/doc/power_management.md b/doc/power_management.md
index 7da31ee86..68032571c 100644
--- a/doc/power_management.md
+++ b/doc/power_management.md
@@ -136,7 +136,7 @@ seems to be used in the `bta_dm_act.cc` file, and only for reinitialization.
request to enable PARK for the given peer and connection.
- If the action chosen is `BTA_DM_PM_SNIFF`, the peer device's link policy
is checked to see if it's allowed. If so, then `bta_dm_pm_sniff` is
- called, which makes various calls to the local controller,
+ called, which makes various calls to `BTM_ReadLocalFeatures`,
`BTM_ReadRemoteFeatures` and `BTM_SetPowerMode` to ensure SNIFF mode is
enabled.
- If the action chosen is `BTA_DM_PM_ACTIVE`, a call to `bta_dm_pm_active`
diff --git a/doc/supported_features.md b/doc/supported_features.md
index 50ca84d02..6063d911b 100644
--- a/doc/supported_features.md
+++ b/doc/supported_features.md
@@ -5,12 +5,12 @@ Qualified Design ID: 83953
Protocol / Profile | Version | Roles
-------------------+---------+-------
-L2CAP | 4.2 | Initiator, Acceptor, LE Central, LE Peripheral
+L2CAP | 4.2 | Initiator, Acceptor, LE Master, LE Slave
SDP | 4.2 | Server, Client
GAP | 4.2 | BR/EDR, LE Central, LE Periperhal, LE Observer, LE Broadcaster
GATT | 4.2 | Client, Server; LE and BR/EDR
ATT | 4.2 | Client, Server; LE and BR/EDR
-SM | 4.2 | Central (Initiator), Peripheral (Responder)
+SM | 4.2 | Master (Initiator), Slave (Responder)
AVCTP | 1.4 | Controller, Target
AVDTP | 1.2 | Source, Initiator, Acceptor
BNEP | 1.0 |
diff --git a/embdrv/g722/Android.bp b/embdrv/g722/Android.bp
index 2cb813970..fbac14574 100644
--- a/embdrv/g722/Android.bp
+++ b/embdrv/g722/Android.bp
@@ -1,14 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- // SPDX-license-identifier-BSD
- // legacy_unencumbered
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "libg722codec",
defaults: ["fluoride_defaults"],
@@ -19,5 +8,4 @@ cc_library_static {
"g722_decode.cc",
"g722_encode.cc",
],
- host_supported: true,
}
diff --git a/embdrv/g722/BUILD.gn b/embdrv/g722/BUILD.gn
index aa5e06ea2..083e80b91 100644
--- a/embdrv/g722/BUILD.gn
+++ b/embdrv/g722/BUILD.gn
@@ -19,7 +19,4 @@ static_library("g722") {
"g722_decode.cc",
"g722_encode.cc",
]
-
- defines = [ "G722_SUPPORT_MALLOC" ]
- configs += [ "//bt:target_defaults" ]
}
diff --git a/embdrv/g722/fuzzer/Android.bp b/embdrv/g722/fuzzer/Android.bp
deleted file mode 100644
index fd7fad0be..000000000
--- a/embdrv/g722/fuzzer/Android.bp
+++ /dev/null
@@ -1,24 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "g722_enc_fuzzer",
- srcs: [
- "g722_enc_fuzzer.cc",
- ],
- host_supported: false,
- static_libs: [
- "libg722codec",
- ],
- fuzz_config: {
- cc: [
- "hsz@google.com",
- ],
- },
-}
diff --git a/embdrv/g722/fuzzer/g722_enc_fuzzer.cc b/embdrv/g722/fuzzer/g722_enc_fuzzer.cc
deleted file mode 100644
index 19df472a7..000000000
--- a/embdrv/g722/fuzzer/g722_enc_fuzzer.cc
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
- * Copyright (C) 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#include <fuzzer/FuzzedDataProvider.h>
-
-#include "../g722_enc_dec.h"
-
-uint32_t get_rate_from_fdp(FuzzedDataProvider* fdp) {
- uint32_t rate = fdp->ConsumeIntegralInRange<uint32_t>(
- 0, 3); // Currently 3 different bit rates are available in G.722 codec
- switch (rate) {
- case 0:
- return 48000;
- case 1:
- return 56000;
- default:
- return 64000;
- }
-}
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
- FuzzedDataProvider fdp(data, size);
-
- std::vector<uint8_t> buff;
- for (size_t i = 0; i < size; i++) {
- buff.push_back(data[i]);
- }
-
- int num_samples =
- buff.size() / (2 /*bytes_per_sample*/ * 2 /*number of channels*/);
-
- // The G.722 codec accept only even number of samples for encoding
- if (num_samples % 2 != 0) {
- num_samples--;
- }
-
- // Making channel data from buffer
- std::vector<uint16_t> channel_data;
-
- for (int i = 0; i < num_samples; i++) {
- const uint8_t* sample = buff.data() + i * 2;
- int16_t left = (int16_t)((*(sample + 1) << 8) + *sample) >> 1;
-
- sample += 2;
- int16_t right = (int16_t)((*(sample + 1) << 8) + *sample) >> 1;
-
- uint16_t mono_data = (int16_t)(((uint32_t)left + (uint32_t)right) >> 1);
- channel_data.push_back(mono_data);
- }
-
- uint32_t rate = get_rate_from_fdp(&fdp);
-
- // Encoder Initialization
- g722_encode_state_t* encoder_state = nullptr;
- encoder_state = g722_encode_init(nullptr, rate, G722_PACKED);
-
- // Encode
- std::vector<uint8_t> encoded_data;
- // Magic number is used in api, It should basically fit the number generated
- // by this formula : num_channels * sample_rate * data_interval_ms
- // * (bit_rate / 8)) / 1000 as mentioned in hearing_aid.cc And if we fit all
- // the values in the above formula, the max value we can get is 1920. And I
- // used "size" of the input that libfuzzer generates as the initial
- // parameter to resize
- encoded_data.resize(size);
- int encoded_size =
- g722_encode(encoder_state, encoded_data.data(),
- (const int16_t*)channel_data.data(), channel_data.size());
- encoded_data.resize(encoded_size);
-
- // Encoder release
- if (encoder_state != nullptr) {
- g722_encode_release(encoder_state);
- encoder_state = nullptr;
- }
-
- return 0;
-} \ No newline at end of file
diff --git a/embdrv/sbc/Android.bp b/embdrv/sbc/Android.bp
index 94bf443b2..5696377f6 100644
--- a/embdrv/sbc/Android.bp
+++ b/embdrv/sbc/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
subdirs = [
"decoder",
"encoder",
diff --git a/embdrv/sbc/BUILD.gn b/embdrv/sbc/BUILD.gn
index ce8524582..696080a07 100644
--- a/embdrv/sbc/BUILD.gn
+++ b/embdrv/sbc/BUILD.gn
@@ -33,8 +33,6 @@ source_set("sbc_decoder") {
]
include_dirs = [ "decoder/include" ]
-
- configs += [ "//bt:target_defaults" ]
}
source_set("sbc_encoder") {
@@ -51,11 +49,9 @@ source_set("sbc_encoder") {
include_dirs = [
"encoder/include",
- "//bt/internal_include",
- "//bt/stack/include",
+ "//internal_include",
+ "//stack/include",
]
-
- configs += [ "//bt:target_defaults" ]
}
static_library("sbc") {
diff --git a/embdrv/sbc/decoder/Android.bp b/embdrv/sbc/decoder/Android.bp
index a3e13ce28..65599d40b 100644
--- a/embdrv/sbc/decoder/Android.bp
+++ b/embdrv/sbc/decoder/Android.bp
@@ -1,14 +1,5 @@
// Bluetooth SBC decoder static library for target
// ========================================================
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "libbt-sbc-decoder",
defaults: ["fluoride_defaults"],
@@ -32,7 +23,6 @@ cc_library_static {
"include",
"srce",
],
- host_supported: true,
}
cc_fuzz {
@@ -48,3 +38,4 @@ cc_fuzz {
],
host_supported: false,
}
+
diff --git a/embdrv/sbc/decoder/include/oi_bt_spec.h b/embdrv/sbc/decoder/include/oi_bt_spec.h
index 939308f58..67d5217cd 100644
--- a/embdrv/sbc/decoder/include/oi_bt_spec.h
+++ b/embdrv/sbc/decoder/include/oi_bt_spec.h
@@ -39,8 +39,8 @@
extern "C" {
#endif
-/** The maximum number of active peripherals in a piconet. */
-#define OI_BT_MAX_ACTIVE_PERIPHERALS 7
+/** The maximum number of active slaves in a piconet. */
+#define OI_BT_MAX_ACTIVE_SLAVES 7
/**
* @name Data types for working with UUIDs
diff --git a/embdrv/sbc/decoder/include/oi_status.h b/embdrv/sbc/decoder/include/oi_status.h
index 7750758d2..8e6d20a5d 100644
--- a/embdrv/sbc/decoder/include/oi_status.h
+++ b/embdrv/sbc/decoder/include/oi_status.h
@@ -101,8 +101,9 @@ typedef enum {
OI_STATUS_LINK_TERMINATED = 143, /**< The link was terminated */
OI_STATUS_PIN_CODE_TOO_LONG =
144, /**< Application gave us a pin code that is too long */
- OI_STATUS_STILL_REGISTERED = 145, /**< The service cannot be shutdown because
- there are still active registrations. */
+ OI_STATUS_STILL_REGISTERED =
+ 145, /**< The service cannot be shutdown because there are still active
+ registrations. */
OI_STATUS_SPEC_VIOLATION =
146, /**< Some application behavior contrary to BT specifications */
@@ -323,7 +324,7 @@ typedef enum {
819, /**< SDP: Failed attempt to connect to an SDP server */
OI_SDP_SERVER_TOO_MANY_CONNECTIONS =
821, /**< SDP: Exceeded maximum number of simultaneous server connections
- */
+ */
OI_SDP_NO_MATCHING_SERVICE_RECORD =
823, /**< SDP: No service record matched the UUID list */
OI_SDP_PARTIAL_RESPONSE = 824, /**< SDP: Internal use only */
@@ -444,8 +445,9 @@ typedef enum {
OI_DEVMGR_ENUM_UNEXPECTED_INQ_RESULT = 1321, /**< DEVMGR: inquiry result event
in inappropriate enumeration
state */
- OI_DEVMGR_ENUM_DATABASE_FULL = 1322, /**< DEVMGR: device enumeration, database
- is full, couldn't add a new device */
+ OI_DEVMGR_ENUM_DATABASE_FULL =
+ 1322, /**< DEVMGR: device enumeration, database is full, couldn't add a
+ new device */
OI_DEVMGR_ENUM_INQUIRIES_OVERLAP = 1323, /**< DEVMGR: device enumeration,
periodic inquiries occurring too
close together */
@@ -459,8 +461,9 @@ typedef enum {
1327, /**< DEVMGR: only one application can use SCO */
OI_DEVMGR_SCO_NOT_REGISTERED =
1328, /**< DEVMGR: SCO applications must register before using the API */
- OI_DEVMGR_SCO_WITHOUT_ACL = 1329, /**< DEVMGR: Got SCO connection but there is
- no underlying ACL connection */
+ OI_DEVMGR_SCO_WITHOUT_ACL =
+ 1329, /**< DEVMGR: Got SCO connection but there is no underlying ACL
+ connection */
OI_DEVMGR_NO_SUPPORT =
1330, /**< DEVMGR: Request is not supported by the device */
OI_DEVMGR_WRITE_POLICY_FAILED = 1331, /**< DEVMGR: connection attempt failed -
@@ -468,8 +471,9 @@ typedef enum {
OI_DEVMGR_NOT_IN_MASTER_MODE = 1332, /**< DEVMGR: OI_DEVMGR EndMasterMode
without prior
OI_DEVMGR_BeginMasterMode */
- OI_DEVMGR_POLICY_VIOLATION = 1333, /**< DEVMGR: low-power request is rejected
- - link policy does not allow it */
+ OI_DEVMGR_POLICY_VIOLATION =
+ 1333, /**< DEVMGR: low-power request is rejected - link policy does not
+ allow it */
OI_DEVMGR_BUSY_TIMEOUT = 1334, /**< DEVMGR: queued operation timed out while
in the queue; \n
timeout configurable via @ref OI_CONFIG_DEVMGR::connectQueueTimeoutSecs
@@ -504,8 +508,9 @@ timeout configurable via @ref OI_CONFIG_DEVMGR::connectQueueTimeoutSecs
1408, /**< SECMGR: l2cap access denied - disconnected */
OI_SECMGR_ACCESS_PENDING =
1409, /**< SECMGR: l2cap access request is still pending */
- OI_SECMGR_PIN_CODE_TOO_SHORT = 1410, /**< SECMGR: Higher-layer process gave us
- a pin code that is too short */
+ OI_SECMGR_PIN_CODE_TOO_SHORT =
+ 1410, /**< SECMGR: Higher-layer process gave us a pin code that is too
+ short */
OI_SECMGR_UNKNOWN_ENCRYPT_VALUE = 1411, /**< SECMGR: got EncryptionChange
event, unknown encryption enable
value */
@@ -516,7 +521,7 @@ timeout configurable via @ref OI_CONFIG_DEVMGR::connectQueueTimeoutSecs
OI_SECMGR_ENCRYPTION_FAILED = 1414, /**< SECMGR: device encryption failed */
OI_SECMGR_UNIT_KEY_UNSUPPORTED =
1415, /**< SECMGR: authentication failed due to non-support of unit keys
- */
+ */
OI_SECMGR_NOT_REGISTERED =
1416, /**< SECMGR: required registrations have not yet occurred */
OI_SECMGR_ILLEGAL_WRITE_SSP_MODE =
@@ -635,8 +640,9 @@ timeout configurable via @ref OI_CONFIG_DEVMGR::connectQueueTimeoutSecs
feature not supported for
requested command */
- OI_HEADSET_SERVICE_NOT_STARTED = 1901, /**< HEADSET: Cannot connect to headset
- AG if headset service not started */
+ OI_HEADSET_SERVICE_NOT_STARTED =
+ 1901, /**< HEADSET: Cannot connect to headset AG if headset service not
+ started */
OI_HEADSET_AG_SERVICE_NOT_STARTED = 1902, /**< HEADSET: Cannot connect to
headset device if headset AG
service not started */
@@ -684,9 +690,8 @@ timeout configurable via @ref OI_CONFIG_DEVMGR::connectQueueTimeoutSecs
2033, /**< BNEP: multicast response code Max Limit Reached */
OI_BNEP_FILTER_MULTI_FAILED_SECURITY =
2034, /**< BNEP: multicast response code Security */
- OI_BNEP_LOCAL_DEVICE_MUST_BE_CENTRAL =
- 2040, /**< BNEP: Device must be central of the piconet for this function
- */
+ OI_BNEP_LOCAL_DEVICE_MUST_BE_MASTER =
+ 2040, /**< BNEP: Device must be master of the piconet for this function */
OI_BNEP_PACKET_FILTERED_OUT =
2041, /**< BNEP: Packet did not pass current filters */
@@ -705,8 +710,9 @@ timeout configurable via @ref OI_CONFIG_DEVMGR::connectQueueTimeoutSecs
2201, /**< PAN: This PAN role was already registered */
OI_PAN_ROLE_NOT_ALLOWED =
2202, /**< PAN: The PAN role is not currently allowed */
- OI_PAN_INCOMPATIBLE_ROLES = 2203, /**< PAN: Only certain local and remote role
- combinations are permitted */
+ OI_PAN_INCOMPATIBLE_ROLES =
+ 2203, /**< PAN: Only certain local and remote role combinations are
+ permitted */
OI_PAN_INVALID_ROLE =
2204, /**< PAN: Role specified is not one the defined PAN roles */
OI_PAN_CONNECTION_IN_PROGRESS =
@@ -745,19 +751,20 @@ timeout configurable via @ref OI_CONFIG_DEVMGR::connectQueueTimeoutSecs
*/
OI_HID_DEVICE_SERVICE_NOT_STARTED =
2602, /**< HID: Cannot connect to a HID host unless HID device is started
- */
-
- OI_AT_ERROR = 2701, /**< AT: ERROR response */
- OI_AT_NO_CARRIER = 2702, /**< AT: NO CARRIER response */
- OI_AT_BUSY = 2703, /**< AT: BUSY response */
- OI_AT_NO_ANSWER = 2704, /**< AT: NO ANSWER response */
- OI_AT_DELAYED = 2705, /**< AT: DELAYED response */
- OI_AT_REJECTLISTED = 2706, /**< AT: REJECTLISTED response */
- OI_AT_CME_ERROR = 2707, /**< AT: +CME ERROR response */
- OI_AT_CMS_ERROR = 2708, /**< AT: +CMS ERROR response */
-
- OI_BLST_CHARACTER_TIMEOUT = 2801, /**< BLST: Timeout expired while waiting for
- a character from the client. */
+ */
+
+ OI_AT_ERROR = 2701, /**< AT: ERROR response */
+ OI_AT_NO_CARRIER = 2702, /**< AT: NO CARRIER response */
+ OI_AT_BUSY = 2703, /**< AT: BUSY response */
+ OI_AT_NO_ANSWER = 2704, /**< AT: NO ANSWER response */
+ OI_AT_DELAYED = 2705, /**< AT: DELAYED response */
+ OI_AT_BLACKLISTED = 2706, /**< AT: BLACKLISTED response */
+ OI_AT_CME_ERROR = 2707, /**< AT: +CME ERROR response */
+ OI_AT_CMS_ERROR = 2708, /**< AT: +CMS ERROR response */
+
+ OI_BLST_CHARACTER_TIMEOUT =
+ 2801, /**< BLST: Timeout expired while waiting for a character from the
+ client. */
OI_BLST_ACKNOWLDGE_TIMEOUT =
2802, /**< BLST: Timeout expired while waiting for event acknowledgment
from the client */
@@ -771,8 +778,9 @@ timeout configurable via @ref OI_CONFIG_DEVMGR::connectQueueTimeoutSecs
OI_AVDTP_OUT_OF_RESOURCES = 2902, /**< AVDTP: Tried to allocate too many
endpoints or signalling channels. */
- OI_PBAP_REPOSITORY_NOT_SET = 3001, /**< PBAP: Phonebook repository must be set
- for operation to complete. */
+ OI_PBAP_REPOSITORY_NOT_SET =
+ 3001, /**< PBAP: Phonebook repository must be set for operation to
+ complete. */
OI_PBAP_PHONEBOOK_NOT_SET =
3002, /**< PBAP: Phonebook be set for operation to complete. */
@@ -818,7 +826,7 @@ timeout configurable via @ref OI_CONFIG_DEVMGR::connectQueueTimeoutSecs
OI_MAX_BM3_STATUS_VAL, /* Maximum BM3 status code */
/* Status code values reserved for BM3 SDK platform-specific implementations
- */
+ */
OI_STATUS_RESERVED_FOR_BCOT = 9000,
/* Status code values reserved for BHAPI products */
diff --git a/embdrv/sbc/encoder/Android.bp b/embdrv/sbc/encoder/Android.bp
index 9df8d2b37..8ca44de21 100644
--- a/embdrv/sbc/encoder/Android.bp
+++ b/embdrv/sbc/encoder/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "libbt-sbc-encoder",
defaults: ["fluoride_defaults"],
@@ -29,5 +20,4 @@ cc_library_static {
"system/bt/internal_include",
"system/bt/stack/include",
],
- host_supported: true,
}
diff --git a/gd/.clang-format b/gd/.clang-format
index edf31fec7..1f1f58618 100644
--- a/gd/.clang-format
+++ b/gd/.clang-format
@@ -24,8 +24,5 @@ CommentPragmas: NOLINT:.*
DerivePointerAlignment: false
ColumnLimit: 120
AllowShortFunctionsOnASingleLine: Empty
-ConstructorInitializerAllOnOneLineOrOnePerLine: true
+ConstructorInitializerAllOnOneLineOrOnePerLine: false
BreakConstructorInitializers: BeforeColon
-AlignAfterOpenBracket: AlwaysBreak
-BinPackArguments: false
-BinPackParameters: false
diff --git a/gd/Android.bp b/gd/Android.bp
index c9985a845..540001fb0 100644
--- a/gd/Android.bp
+++ b/gd/Android.bp
@@ -1,13 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- // SPDX-license-identifier-BSD
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_defaults {
name: "gd_defaults",
target: {
@@ -23,6 +13,7 @@ cc_defaults {
},
host: {
cflags: [
+ "-DOS_LINUX",
"-DOS_LINUX_GENERIC",
],
},
@@ -42,7 +33,6 @@ cc_defaults {
conlyflags: [
"-std=c99",
],
- header_libs: ["jni_headers"],
sanitize: {
misc_undefined: ["bounds"],
},
@@ -81,36 +71,8 @@ cc_defaults {
},
}
-cc_defaults {
- name: "gd_clang_tidy",
- tidy: true,
- tidy_checks: [
- "clang-analyzer-core.CallAndMessage",
- "clang-analyzer-optin.cplusplus.UninitializedObject",
- "-google*",
- "-performance*",
- "-bugprone*",
- ],
- tidy_checks_as_errors: [
- "cppcoreguidelines-pro-type-member-init",
- "clang-analyzer-core.CallAndMessage",
- "clang-analyzer-optin.cplusplus.UninitializedObject",
- ],
- tidy_flags: [
- "--header-filter=^.*system/bt/.*.h$",
- "--extra-arg-before=-Xclang",
- "--extra-arg-before=-analyzer-config",
- "--extra-arg-before=-Xclang",
- "--extra-arg-before=optin.cplusplus.UninitializedObject:Pedantic=true",
- "--extra-arg-before=-Xclang",
- "--extra-arg-before=-analyzer-config",
- "--extra-arg-before=-Xclang",
- "--extra-arg-before=optin.cplusplus.UninitializedObject:CheckPointeeInitialization=true",
- ],
-}
-
-cc_defaults {
- name: "libbluetooth_gd_defaults",
+cc_library {
+ name: "libbluetooth_gd",
defaults: [
"gd_defaults",
"gd_clang_file_coverage",
@@ -119,33 +81,22 @@ cc_defaults {
target: {
linux: {
srcs: [
- ":BluetoothBtaaSources_linux_generic",
":BluetoothOsSources_linux_generic",
],
},
host: {
srcs: [
- ":BluetoothBtaaSources_host",
- ":BluetoothHalSources_hci_host",
- ":BluetoothOsSources_host",
+ ":BluetoothHalSources_hci_rootcanal",
],
},
android: {
srcs: [
- ":BluetoothBtaaSources_android",
":BluetoothHalSources_hci_android_hidl",
- ":BluetoothOsSources_android",
],
shared_libs: [
"android.hardware.bluetooth@1.0",
- "android.hardware.bluetooth@1.1",
- "android.system.suspend.control-V1-ndk",
- "android.system.suspend@1.0",
- "libbinder_ndk",
- "libcutils",
"libhidlbase",
"libutils",
- "libstatslog",
],
},
},
@@ -155,10 +106,8 @@ cc_defaults {
":BluetoothAttSources",
":BluetoothCommonSources",
":BluetoothCryptoToolboxSources",
- ":BluetoothDumpsysSources",
":BluetoothHalSources",
":BluetoothHciSources",
- ":BluetoothIsoSources",
":BluetoothL2capSources",
":BluetoothNeighborSources",
":BluetoothPacketSources",
@@ -167,43 +116,10 @@ cc_defaults {
":BluetoothStorageSources",
],
generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- "BluetoothGeneratedDumpsysDataSchema_h",
- "BluetoothGeneratedDumpsysBundledSchema_h",
"BluetoothGeneratedPackets_h",
],
shared_libs: [
"libchrome",
- "libcrypto",
- "libflatbuffers-cpp",
- "libgrpc++",
- "libgrpc_wrap",
- ],
- static_libs: [
- "libbluetooth-protos",
- "libbluetooth_rust_interop",
- "libbt-platform-protos-lite",
- ],
- export_static_lib_headers: [ "libbluetooth_rust_interop" ],
-}
-
-cc_library {
- name: "libbluetooth_gd",
- defaults: [
- "libbluetooth_gd_defaults",
- ],
-}
-
-cc_library {
- name: "libbluetooth_gd_fuzzing",
- defaults: [
- "libbluetooth_gd_defaults",
- ],
- srcs: [
- ":BluetoothOsSources_fuzz",
- ],
- cflags: [
- "-DFUZZ_TARGET",
],
}
@@ -211,7 +127,6 @@ cc_binary {
name: "bluetooth_stack_with_facade",
defaults: [
"gd_defaults",
- "gd_clang_coverage_bin",
],
host_supported: true,
srcs: [
@@ -223,50 +138,29 @@ cc_binary {
":BluetoothFacade_hci_layer",
":BluetoothFacade_l2cap_layer",
":BluetoothFacade_neighbor",
- ":BluetoothFacade_iso_layer",
":BluetoothFacade_security_layer",
- ":BluetoothFacade_shim_layer",
],
generated_headers: [
- "BluetoothFacadeGeneratedStub_h",
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- "BluetoothGeneratedDumpsysDataSchema_h",
"BluetoothGeneratedPackets_h",
- // Needed here to guarantee that generated zip file is created before
- // bluetooth_cert_tests.zip is packaged
- "BluetoothFacadeAndCertGeneratedStub_py",
+ "BluetoothFacadeGeneratedStub_h",
],
generated_sources: [
"BluetoothFacadeGeneratedStub_cc",
],
static_libs: [
- "breakpad_client",
- "libbluetooth-protos",
"libbluetooth_gd",
- "libflatbuffers-cpp",
- "libbluetooth_rust_interop",
],
shared_libs: [
- "libbacktrace",
"libchrome",
- "libcrypto",
- "libgrpc++",
"libgrpc++_unsecure",
- "libgrpc_wrap",
"libprotobuf-cpp-full",
],
target: {
android: {
shared_libs: [
"android.hardware.bluetooth@1.0",
- "android.hardware.bluetooth@1.1",
- "android.system.suspend.control-V1-ndk",
- "android.system.suspend@1.0",
- "libbinder_ndk",
"libhidlbase",
"libutils",
- "libcutils",
- "libstatslog",
],
},
host: {
@@ -277,89 +171,6 @@ cc_binary {
},
sanitize: {
address: true,
- cfi: true,
- }
-}
-
-cc_test {
- name: "bluetooth_test_gd_unit",
- test_suites: ["device-tests"],
- defaults: [
- "gd_defaults",
- "gd_clang_coverage_bin",
- ],
- host_supported: true,
- test_options: {
- unit_test: true,
- },
- target: {
- linux: {
- srcs: [
- ":BluetoothOsTestSources_linux_generic",
- ],
- },
- host: {
- srcs: [
- ":BluetoothHalTestSources_hci_host",
- ":BluetoothOsTestSources_host",
- ],
- },
- android: {
- srcs: [
- ":BluetoothHalTestSources_hci_android_hidl",
- ":BluetoothOsTestSources_android",
- ],
- shared_libs: [
- "android.hardware.bluetooth@1.0",
- "android.hardware.bluetooth@1.1",
- "android.system.suspend.control-V1-ndk",
- "android.system.suspend@1.0",
- "libbinder_ndk",
- "libhidlbase",
- "libutils",
- "libcutils",
- "libstatslog",
- ],
- },
- },
- srcs: [
- "module_unittest.cc",
- "stack_manager_unittest.cc",
- ":BluetoothCommonTestSources",
- ":BluetoothCryptoToolboxTestSources",
- ":BluetoothDumpsysTestSources",
- ":BluetoothHalTestSources",
- ":BluetoothHciUnitTestSources",
- ":BluetoothL2capUnitTestSources",
- ":BluetoothPacketTestSources",
- ":BluetoothShimTestSources",
- ":BluetoothSecurityUnitTestSources",
- ":BluetoothStorageUnitTestSources",
- ],
- generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- "BluetoothGeneratedDumpsysBundledSchema_h",
- "BluetoothGeneratedDumpsysBundledTestSchema_h",
- "BluetoothGeneratedDumpsysDataSchema_h",
- "BluetoothGeneratedDumpsysTestData_h",
- "BluetoothGeneratedPackets_h",
- ],
- static_libs: [
- "libbluetooth-protos",
- "libbluetooth_gd",
- "libc++fs",
- "libflatbuffers-cpp",
- "libgmock",
- "libbluetooth_rust_interop",
- ],
- shared_libs: [
- "libchrome",
- "libcrypto",
- "libgrpc++",
- "libgrpc_wrap",
- ],
- sanitize: {
- address: true,
},
}
@@ -371,9 +182,6 @@ cc_test {
"gd_clang_coverage_bin",
],
host_supported: true,
- test_options: {
- unit_test: false,
- },
target: {
linux: {
srcs: [
@@ -382,25 +190,17 @@ cc_test {
},
host: {
srcs: [
- ":BluetoothHalTestSources_hci_host",
- ":BluetoothOsTestSources_host",
+ ":BluetoothHalTestSources_hci_rootcanal",
],
},
android: {
srcs: [
":BluetoothHalTestSources_hci_android_hidl",
- ":BluetoothOsTestSources_android",
],
shared_libs: [
"android.hardware.bluetooth@1.0",
- "android.hardware.bluetooth@1.1",
- "android.system.suspend.control-V1-ndk",
- "android.system.suspend@1.0",
- "libbinder_ndk",
"libhidlbase",
"libutils",
- "libcutils",
- "libstatslog",
],
},
},
@@ -410,37 +210,23 @@ cc_test {
":BluetoothAttTestSources",
":BluetoothCommonTestSources",
":BluetoothCryptoToolboxTestSources",
- ":BluetoothDumpsysTestSources",
- ":BluetoothHalTestSources",
":BluetoothHciTestSources",
- ":BluetoothIsoTestSources",
":BluetoothL2capTestSources",
":BluetoothNeighborTestSources",
":BluetoothPacketTestSources",
":BluetoothSecurityTestSources",
+ ":BluetoothShimTestSources",
":BluetoothStorageTestSources",
],
generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- "BluetoothGeneratedDumpsysBundledSchema_h",
- "BluetoothGeneratedDumpsysBundledTestSchema_h",
- "BluetoothGeneratedDumpsysDataSchema_h",
- "BluetoothGeneratedDumpsysTestData_h",
"BluetoothGeneratedPackets_h",
],
static_libs: [
- "libbluetooth-protos",
"libbluetooth_gd",
- "libc++fs",
- "libflatbuffers-cpp",
"libgmock",
- "libbluetooth_rust_interop",
],
shared_libs: [
"libchrome",
- "libcrypto",
- "libgrpc++",
- "libgrpc_wrap",
],
sanitize: {
address: true,
@@ -455,11 +241,7 @@ cc_test {
"gd_clang_coverage_bin",
],
host_supported: true,
- test_options: {
- unit_test: true,
- },
srcs: [
- "hci/address.cc",
":BluetoothPacketSources",
":BluetoothPacketParserTestPacketTestSources",
],
@@ -470,96 +252,35 @@ cc_test {
address: true,
cfi: true,
},
- static_libs: [
- "libchrome",
- ],
- shared_libs: [
- "libgrpc++",
- "libgrpc_wrap",
- ],
- target: {
- android: {
- shared_libs: [
- "android.hardware.bluetooth@1.0",
- "android.hardware.bluetooth@1.1",
- "libhidlbase",
- "libutils",
- "libcutils",
- ],
- },
- },
-}
-
-cc_defaults {
- name: "gd_fuzz_defaults",
- defaults: ["gd_defaults"],
- srcs: [
- ":BluetoothFuzzHelperSources",
- ":BluetoothHciFuzzHelperSources",
- ],
- static_libs: [
- "libbluetooth-protos",
- "libbluetooth_gd_fuzzing",
- "libchrome",
- "libgmock",
- "libgtest",
- "libbluetooth_rust_interop",
- ],
- host_supported: true,
- generated_headers: [
- "BluetoothGeneratedDumpsysDataSchema_h",
- "BluetoothGeneratedPackets_h",
- ],
- shared_libs: [
- "libcrypto",
- "libflatbuffers-cpp",
- "libgrpc++",
- "libgrpc_wrap",
- ],
- cflags: [
- "-DFUZZ_TARGET",
- ],
- target: {
- android: {
- shared_libs: [
- "android.hardware.bluetooth@1.0",
- "android.hardware.bluetooth@1.1",
- "android.system.suspend.control-V1-ndk",
- "libbinder_ndk",
- "libcutils",
- "libhidlbase",
- "libutils",
- "libstatslog",
- ],
- },
- },
-}
-
-cc_fuzz {
- name: "bluetooth_gd_fuzz_test",
- defaults: ["gd_fuzz_defaults"],
- srcs: [
- "fuzz_test.cc",
- ":BluetoothHciFuzzTestSources",
- ":BluetoothL2capFuzzTestSources",
- ],
}
cc_fuzz {
- name: "bluetooth_gd_hci_layer_fuzz_test",
- defaults: ["gd_fuzz_defaults"],
- srcs: [
- "hci/fuzz/hci_layer_fuzz_test.cc",
- ":BluetoothHalFuzzSources",
- ],
-}
-
-cc_fuzz {
- name: "bluetooth_gd_acl_manager_fuzz_test",
- defaults: ["gd_fuzz_defaults"],
- srcs: [
- "hci/fuzz/acl_manager_fuzz_test.cc",
- ],
+ name: "bluetooth_gd_fuzz_test",
+ defaults: ["gd_defaults"],
+ srcs: [
+ "fuzz_test.cc",
+ ":BluetoothHciFuzzTestSources",
+ ":BluetoothL2capFuzzTestSources",
+ ],
+ static_libs: [
+ "libbluetooth_gd",
+ "libchrome",
+ "libgmock",
+ "libgtest",
+ ],
+ host_supported: true,
+ generated_headers: [
+ "BluetoothGeneratedPackets_h",
+ ],
+ target: {
+ android: {
+ shared_libs: [
+ "android.hardware.bluetooth@1.0",
+ "libhidlbase",
+ "libutils",
+ ],
+ },
+ },
}
cc_benchmark {
@@ -583,7 +304,7 @@ filegroup {
srcs: [
"hci/address.cc",
"hci/class_of_device.cc",
- ],
+ ],
}
genrule {
@@ -605,111 +326,11 @@ genrule {
}
genrule {
- name: "BluetoothGeneratedPackets_rust",
- tools: [
- "bluetooth_packetgen",
- ],
- cmd: "$(location bluetooth_packetgen) --include=system/bt/gd --out=$(genDir) $(in) --rust",
- srcs: [
- "hci/hci_packets.pdl",
- ],
- out: [
- "hci/hci_packets.rs",
- ],
-}
-
-rust_library {
- name: "libbt_packets",
- defaults: ["gd_rust_defaults"],
- crate_name: "bt_packets",
- srcs: ["rust/packets/lib.rs", ":BluetoothGeneratedPackets_rust"],
- edition: "2018",
- host_supported: true,
- proc_macros: ["libnum_derive"],
- rustlibs: [
- "libbytes",
- "libnum_traits",
- "libthiserror",
- "libbt_hci_custom_types",
- "liblog_rust",
- ],
-}
-
-rust_test_host {
- name: "libbt_packets_test",
- defaults: ["gd_rust_defaults"],
- srcs: ["rust/packets/lib.rs", ":BluetoothGeneratedPackets_rust"],
- test_suites: ["general-tests"],
- edition: "2018",
- proc_macros: ["libnum_derive"],
- rustlibs: [
- "libbytes",
- "libnum_traits",
- "libthiserror",
- "libbt_hci_custom_types",
- "liblog_rust",
- ],
-}
-
-// Generates binary schema data to be bundled and source file generated
-genrule {
- name: "BluetoothGeneratedDumpsysBinarySchema_bfbs",
- tools: [
- "flatc",
- ],
- cmd: "$(location flatc) -I system/bt/gd -b --schema -o $(genDir) $(in) ",
- srcs: [
- "btaa/activity_attribution.fbs",
- "common/init_flags.fbs",
- "dumpsys_data.fbs",
- "hci/hci_acl_manager.fbs",
- "l2cap/classic/l2cap_classic_module.fbs",
- "shim/dumpsys.fbs",
- "os/wakelock_manager.fbs",
- ],
- out: [
- "activity_attribution.bfbs",
- "init_flags.bfbs",
- "dumpsys.bfbs",
- "dumpsys_data.bfbs",
- "hci_acl_manager.bfbs",
- "l2cap_classic_module.bfbs",
- "wakelock_manager.bfbs",
- ],
-}
-
-genrule {
- name: "BluetoothGeneratedDumpsysDataSchema_h",
- tools: [
- "flatc",
- ],
- cmd: "$(location flatc) -I system/bt/gd -o $(genDir) --cpp $(in) ",
- srcs: [
- "btaa/activity_attribution.fbs",
- "common/init_flags.fbs",
- "dumpsys_data.fbs",
- "hci/hci_acl_manager.fbs",
- "l2cap/classic/l2cap_classic_module.fbs",
- "shim/dumpsys.fbs",
- "os/wakelock_manager.fbs",
- ],
- out: [
- "activity_attribution_generated.h",
- "dumpsys_data_generated.h",
- "dumpsys_generated.h",
- "hci_acl_manager_generated.h",
- "init_flags_generated.h",
- "l2cap_classic_module_generated.h",
- "wakelock_manager_generated.h",
- ],
-}
-
-genrule {
name: "BluetoothGeneratedPackets_python3_cc",
tools: [
"bluetooth_packetgen",
],
- cmd: "$(location bluetooth_packetgen) --include=system/bt/gd --out=$(genDir) --num_shards=10 $(in)",
+ cmd: "$(location bluetooth_packetgen) --include=system/bt/gd --out=$(genDir) --num_shards=5 $(in)",
srcs: [
"hci/hci_packets.pdl",
"l2cap/l2cap_packets.pdl",
@@ -722,33 +343,18 @@ genrule {
"hci/hci_packets_python3_shard_2.cc",
"hci/hci_packets_python3_shard_3.cc",
"hci/hci_packets_python3_shard_4.cc",
- "hci/hci_packets_python3_shard_5.cc",
- "hci/hci_packets_python3_shard_6.cc",
- "hci/hci_packets_python3_shard_7.cc",
- "hci/hci_packets_python3_shard_8.cc",
- "hci/hci_packets_python3_shard_9.cc",
"l2cap/l2cap_packets_python3.cc",
"l2cap/l2cap_packets_python3_shard_0.cc",
"l2cap/l2cap_packets_python3_shard_1.cc",
"l2cap/l2cap_packets_python3_shard_2.cc",
"l2cap/l2cap_packets_python3_shard_3.cc",
"l2cap/l2cap_packets_python3_shard_4.cc",
- "l2cap/l2cap_packets_python3_shard_5.cc",
- "l2cap/l2cap_packets_python3_shard_6.cc",
- "l2cap/l2cap_packets_python3_shard_7.cc",
- "l2cap/l2cap_packets_python3_shard_8.cc",
- "l2cap/l2cap_packets_python3_shard_9.cc",
"security/smp_packets_python3.cc",
"security/smp_packets_python3_shard_0.cc",
"security/smp_packets_python3_shard_1.cc",
"security/smp_packets_python3_shard_2.cc",
"security/smp_packets_python3_shard_3.cc",
"security/smp_packets_python3_shard_4.cc",
- "security/smp_packets_python3_shard_5.cc",
- "security/smp_packets_python3_shard_6.cc",
- "security/smp_packets_python3_shard_7.cc",
- "security/smp_packets_python3_shard_8.cc",
- "security/smp_packets_python3_shard_9.cc",
],
}
@@ -757,20 +363,16 @@ filegroup {
srcs: [
"facade/common.proto",
"facade/rootservice.proto",
- "hal/hal_facade.proto",
- "hci/facade/hci_facade.proto",
+ "hal/facade.proto",
+ "hci/facade/facade.proto",
"hci/facade/acl_manager_facade.proto",
"hci/facade/controller_facade.proto",
"hci/facade/le_acl_manager_facade.proto",
"hci/facade/le_advertising_manager_facade.proto",
- "hci/facade/le_initiator_address_facade.proto",
"hci/facade/le_scanning_manager_facade.proto",
- "iso/facade.proto",
"neighbor/facade/facade.proto",
"l2cap/classic/facade.proto",
- "l2cap/le/facade.proto",
"security/facade.proto",
- "shim/facade/facade.proto",
],
}
@@ -789,10 +391,10 @@ genrule {
"facade/common.pb.h",
"facade/rootservice.grpc.pb.h",
"facade/rootservice.pb.h",
- "hal/hal_facade.grpc.pb.h",
- "hal/hal_facade.pb.h",
- "hci/facade/hci_facade.grpc.pb.h",
- "hci/facade/hci_facade.pb.h",
+ "hal/facade.grpc.pb.h",
+ "hal/facade.pb.h",
+ "hci/facade/facade.grpc.pb.h",
+ "hci/facade/facade.pb.h",
"hci/facade/acl_manager_facade.grpc.pb.h",
"hci/facade/acl_manager_facade.pb.h",
"hci/facade/controller_facade.grpc.pb.h",
@@ -801,22 +403,14 @@ genrule {
"hci/facade/le_acl_manager_facade.pb.h",
"hci/facade/le_advertising_manager_facade.grpc.pb.h",
"hci/facade/le_advertising_manager_facade.pb.h",
- "hci/facade/le_initiator_address_facade.grpc.pb.h",
- "hci/facade/le_initiator_address_facade.pb.h",
"hci/facade/le_scanning_manager_facade.grpc.pb.h",
"hci/facade/le_scanning_manager_facade.pb.h",
- "iso/facade.grpc.pb.h",
- "iso/facade.pb.h",
"l2cap/classic/facade.grpc.pb.h",
"l2cap/classic/facade.pb.h",
- "l2cap/le/facade.grpc.pb.h",
- "l2cap/le/facade.pb.h",
"neighbor/facade/facade.grpc.pb.h",
"neighbor/facade/facade.pb.h",
"security/facade.grpc.pb.h",
"security/facade.pb.h",
- "shim/facade/facade.grpc.pb.h",
- "shim/facade/facade.pb.h",
],
}
@@ -835,10 +429,10 @@ genrule {
"facade/common.pb.cc",
"facade/rootservice.grpc.pb.cc",
"facade/rootservice.pb.cc",
- "hal/hal_facade.grpc.pb.cc",
- "hal/hal_facade.pb.cc",
- "hci/facade/hci_facade.grpc.pb.cc",
- "hci/facade/hci_facade.pb.cc",
+ "hal/facade.grpc.pb.cc",
+ "hal/facade.pb.cc",
+ "hci/facade/facade.grpc.pb.cc",
+ "hci/facade/facade.pb.cc",
"hci/facade/acl_manager_facade.grpc.pb.cc",
"hci/facade/acl_manager_facade.pb.cc",
"hci/facade/controller_facade.grpc.pb.cc",
@@ -847,22 +441,14 @@ genrule {
"hci/facade/le_acl_manager_facade.pb.cc",
"hci/facade/le_advertising_manager_facade.grpc.pb.cc",
"hci/facade/le_advertising_manager_facade.pb.cc",
- "hci/facade/le_initiator_address_facade.grpc.pb.cc",
- "hci/facade/le_initiator_address_facade.pb.cc",
"hci/facade/le_scanning_manager_facade.grpc.pb.cc",
"hci/facade/le_scanning_manager_facade.pb.cc",
- "iso/facade.grpc.pb.cc",
- "iso/facade.pb.cc",
"l2cap/classic/facade.grpc.pb.cc",
"l2cap/classic/facade.pb.cc",
- "l2cap/le/facade.grpc.pb.cc",
- "l2cap/le/facade.pb.cc",
"neighbor/facade/facade.grpc.pb.cc",
"neighbor/facade/facade.pb.cc",
"security/facade.grpc.pb.cc",
"security/facade.pb.cc",
- "shim/facade/facade.grpc.pb.cc",
- "shim/facade/facade.pb.cc",
],
}
@@ -873,127 +459,110 @@ genrule {
"protoc-gen-grpc-python-plugin",
"soong_zip",
],
- cmd: "mkdir -p $(genDir)/files && " +
- "$(location aprotoc) -Isystem/bt/gd -Iexternal/protobuf/src --plugin=protoc-gen-grpc=$(location protoc-gen-grpc-python-plugin) $(in) --grpc_out=$(genDir)/files --python_out=$(genDir)/files && " +
- "mkdir -p $(genDir)/files/cert && " +
- "touch $(genDir)/files/cert/__init__.py && " +
- "touch $(genDir)/files/facade/__init__.py && " +
- "touch $(genDir)/files/hal/__init__.py && " +
- "touch $(genDir)/files/hci/__init__.py && " +
- "touch $(genDir)/files/hci/facade/__init__.py && " +
- "touch $(genDir)/files/iso/__init__.py && " +
- "touch $(genDir)/files/l2cap/classic/__init__.py && " +
- "touch $(genDir)/files/l2cap/le/__init__.py && " +
- "touch $(genDir)/files/neighbor/facade/__init__.py && " +
- "touch $(genDir)/files/security/__init__.py && " +
- "$(location soong_zip) -C $(genDir)/files -D $(genDir)/files -o $(out)",
+ cmd: "$(location aprotoc) -Isystem/bt/gd -Iexternal/protobuf/src --plugin=protoc-gen-grpc=$(location protoc-gen-grpc-python-plugin) $(in) --grpc_out=$(genDir) --python_out=$(genDir); " +
+ "touch $(genDir)/facade/__init__.py; " +
+ "touch $(genDir)/hal/__init__.py; " +
+ "touch $(genDir)/hci/__init__.py; " +
+ "touch $(genDir)/hci/facade/__init__.py; " +
+ "touch $(genDir)/l2cap/classic/__init__.py; " +
+ "touch $(genDir)/neighbor/facade/__init__.py; " +
+ "touch $(genDir)/security/__init__.py; " +
+ "$(location soong_zip) -C $(genDir) -D $(genDir) -o $(out)",
srcs: [
":BluetoothFacadeProto",
],
out: ["bluetooth_cert_generated_py.zip"],
+ dist: {
+ targets: ["bluetooth_stack_with_facade"],
+ },
+
}
cc_defaults {
- name: "bluetooth_py3_native_extension_defaults",
- include_dirs: [
- "external/python/cpython3/Include",
- ],
- target: {
- android: {
- include_dirs: ["external/python/cpython3/android/bionic/pyconfig"],
- },
- android_arm: {
- cflags: ["-DSOABI=\"cpython-38android-arm-android-bionic\""],
- suffix: ".cpython-38android-arm-android-bionic",
- },
- android_arm64: {
- cflags: ["-DSOABI=\"cpython-38android-arm64-android-bionic\""],
- suffix: ".cpython-38android-arm64-android-bionic",
- },
- android_x86: {
- cflags: ["-DSOABI=\"cpython-38android-x86-android-bionic\""],
- suffix: ".cpython-38android-x86-android-bionic",
- },
- android_x86_64: {
- cflags: ["-DSOABI=\"cpython-38android-x86_64-android-bionic\""],
- suffix: ".cpython-38android-x86_64-android-bionic",
- },
- // Regenerate include dirs with android_regen.sh
- darwin_x86_64: {
- include_dirs: ["external/python/cpython3/android/darwin_x86_64/pyconfig"],
- cflags: [
- "-Wno-deprecated-declarations",
- "-Wno-pointer-arith",
- "-DSOABI=\"cpython-38android-x86_64-darwin\"",
- ],
- suffix: ".cpython-38android-x86_64-darwin",
- },
- linux_bionic: {
- // NB linux_bionic is a 'host' architecture but it uses the bionic libc like 'android'
- // targets so use the android pyconfig.
- include_dirs: ["external/python/cpython3/android/bionic/pyconfig"],
- cflags: ["-DSOABI=\"cpython-38android-x86_64-linux-bionic\""],
- suffix: ".cpython-38android-x86_64-linux-bionic",
- },
- linux_glibc_x86: {
- enabled: false,
- },
- linux_glibc_x86_64: {
- include_dirs: ["external/python/cpython3/android/linux_x86_64/pyconfig"],
- cflags: ["-DSOABI=\"cpython-38android-x86_64-linux-gnu\""],
- // Commenting out the Linux suffix so that cpython-38-x86_64-linux-gnu
- // Python 3.8 can also import the untagged .so library per PEP 3149
- // Keep this change until Android py3-cmd can run ACTS, gRPC and can
- // Export Python native symbols such as PyType_Type
- // suffix: ".cpython-38android-x86_64-linux-gnu",
- },
- windows: {
- enabled: false,
- },
- },
- allow_undefined_symbols: true,
+ name: "bluetooth_py3_native_extension_defaults",
+ include_dirs: [
+ "external/python/cpython3/Include",
+ ],
+ target: {
+ android: {
+ include_dirs: ["external/python/cpython3/android/bionic/pyconfig"],
+ },
+ android_arm: {
+ cflags: ["-DSOABI=\"cpython-38android-arm-android-bionic\""],
+ suffix: ".cpython-38android-arm-android-bionic",
+ },
+ android_arm64: {
+ cflags: ["-DSOABI=\"cpython-38android-arm64-android-bionic\""],
+ suffix: ".cpython-38android-arm64-android-bionic",
+ },
+ android_x86: {
+ cflags: ["-DSOABI=\"cpython-38android-x86-android-bionic\""],
+ suffix: ".cpython-38android-x86-android-bionic",
+ },
+ android_x86_64: {
+ cflags: ["-DSOABI=\"cpython-38android-x86_64-android-bionic\""],
+ suffix: ".cpython-38android-x86_64-android-bionic",
+ },
+ // Regenerate include dirs with android_regen.sh
+ darwin_x86_64: {
+ include_dirs: ["external/python/cpython3/android/darwin_x86_64/pyconfig"],
+ cflags: [
+ "-Wno-deprecated-declarations",
+ "-Wno-pointer-arith",
+ "-DSOABI=\"cpython-38android-x86_64-darwin\"",
+ ],
+ suffix: ".cpython-38android-x86_64-darwin",
+ },
+ linux_bionic: {
+ // NB linux_bionic is a 'host' architecture but it uses the bionic libc like 'android'
+ // targets so use the android pyconfig.
+ include_dirs: ["external/python/cpython3/android/bionic/pyconfig"],
+ cflags: ["-DSOABI=\"cpython-38android-x86_64-linux-bionic\""],
+ suffix: ".cpython-38android-x86_64-linux-bionic",
+ },
+ linux_glibc_x86: {
+ enabled: false,
+ },
+ linux_glibc_x86_64: {
+ include_dirs: ["external/python/cpython3/android/linux_x86_64/pyconfig"],
+ cflags: ["-DSOABI=\"cpython-38android-x86_64-linux-gnu\""],
+ // Commenting out the Linux suffix so that cpython-38-x86_64-linux-gnu
+ // Python 3.8 can also import the untagged .so library per PEP 3149
+ // Keep this change until Android py3-cmd can run ACTS, gRPC and can
+ // Export Python native symbols such as PyType_Type
+ // suffix: ".cpython-38android-x86_64-linux-gnu",
+ },
+ windows: {
+ enabled: false,
+ },
+ },
+ allow_undefined_symbols: true,
}
cc_library_host_shared {
- name: "bluetooth_packets_python3",
- defaults: [
- "gd_defaults",
- "bluetooth_py3_native_extension_defaults",
- ],
- srcs: [
- "common/strings.cc",
- "packet/python3_module.cc",
- "l2cap/fcs.cc",
- ":BluetoothPacketSources",
- "hci/address.cc",
- "hci/class_of_device.cc",
-
- ],
- generated_headers: [
- "BluetoothGeneratedPackets_h",
- ],
- generated_sources: [
- "BluetoothGeneratedPackets_python3_cc",
- ],
- header_libs: [
- "pybind11_headers",
- ],
- cflags: [
- "-fexceptions",
- ],
- rtti: true,
-}
-
-rust_protobuf {
- name: "libbt_facade_proto",
- crate_name: "bt_facade_proto",
- protos: ["facade/common.proto"],
- grpc_protos: [
- "hci/facade/controller_facade.proto",
- "hci/facade/hci_facade.proto",
- "hal/hal_facade.proto",
- "facade/rootservice.proto",
- ],
- source_stem: "facade",
- host_supported: true,
+ name: "bluetooth_packets_python3",
+ defaults: [
+ "gd_defaults",
+ "bluetooth_py3_native_extension_defaults"
+ ],
+ srcs: [
+ "packet/python3_module.cc",
+ "l2cap/fcs.cc",
+ ":BluetoothPacketSources",
+ "hci/address.cc",
+ "hci/class_of_device.cc",
+ ],
+ generated_headers: [
+ "BluetoothGeneratedPackets_h",
+ ],
+ generated_sources: [
+ "BluetoothGeneratedPackets_python3_cc",
+ ],
+ header_libs: [
+ "pybind11_headers",
+ ],
+ cflags: [
+ "-fexceptions",
+ ],
+ rtti: true,
}
diff --git a/gd/Android.mk b/gd/Android.mk
index 0a41f6a79..60bcbcf02 100644
--- a/gd/Android.mk
+++ b/gd/Android.mk
@@ -1,106 +1,46 @@
LOCAL_PATH := $(call my-dir)
-#LINT.IfChange
-LOCAL_cert_test_sources := \
- $(call all-named-files-under,*.py,.) \
- cert/all_cert_testcases
-LOCAL_cert_test_sources := \
- $(filter-out gd_cert_venv% venv%, $(LOCAL_cert_test_sources))
-LOCAL_cert_test_sources := \
- $(addprefix $(LOCAL_PATH)/, $(LOCAL_cert_test_sources))
-
-LOCAL_host_executables := \
- $(HOST_OUT_EXECUTABLES)/bluetooth_stack_with_facade \
- $(HOST_OUT_EXECUTABLES)/bluetooth_with_facades \
- $(HOST_OUT_EXECUTABLES)/root-canal
-
-LOCAL_host_python_extension_libraries := \
- $(HOST_OUT_SHARED_LIBRARIES)/bluetooth_packets_python3.so
-
-LOCAL_host_libraries := \
- $(HOST_OUT_SHARED_LIBRARIES)/libbase.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libbluetooth_gd.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libc++.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libchrome.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libcrypto-host.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libevent-host.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libgrpc++_unsecure.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libgrpc++.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libgrpc_wrap.so \
- $(HOST_OUT_SHARED_LIBRARIES)/liblog.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libssl-host.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libz-host.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libprotobuf-cpp-full.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libunwindstack.so \
- $(HOST_OUT_SHARED_LIBRARIES)/liblzma.so \
- $(HOST_OUT_SHARED_LIBRARIES)/libbacktrace.so
-
-LOCAL_target_executables := \
- $(TARGET_OUT_EXECUTABLES)/bluetooth_stack_with_facade
-
-LOCAL_target_libraries := \
- $(TARGET_OUT_SHARED_LIBRARIES)/libcrypto.so \
- $(TARGET_OUT_SHARED_LIBRARIES)/libbluetooth_gd.so \
- $(TARGET_OUT_SHARED_LIBRARIES)/libgrpc++_unsecure.so
-#LINT.ThenChange(cert/run)
-
-bluetooth_cert_src_and_bin_zip := \
- $(call intermediates-dir-for,PACKAGING,bluetooth_cert_src_and_bin,HOST)/bluetooth_cert_src_and_bin.zip
-
-# Assume 64-bit OS
-$(bluetooth_cert_src_and_bin_zip): PRIVATE_cert_test_sources := $(LOCAL_cert_test_sources)
-$(bluetooth_cert_src_and_bin_zip): PRIVATE_host_executables := $(LOCAL_host_executables)
-$(bluetooth_cert_src_and_bin_zip): PRIVATE_host_python_extension_libraries := $(LOCAL_host_python_extension_libraries)
-$(bluetooth_cert_src_and_bin_zip): PRIVATE_host_libraries := $(LOCAL_host_libraries)
-$(bluetooth_cert_src_and_bin_zip): PRIVATE_target_executables := $(LOCAL_target_executables)
-$(bluetooth_cert_src_and_bin_zip): PRIVATE_target_libraries := $(LOCAL_target_libraries)
-$(bluetooth_cert_src_and_bin_zip): $(SOONG_ZIP) $(LOCAL_cert_test_sources) \
- $(LOCAL_host_executables) $(LOCAL_host_libraries) $(LOCAL_host_python_extension_libraries) \
- $(LOCAL_target_executables) $(LOCAL_target_libraries)
- $(hide) $(SOONG_ZIP) -d -o $@ \
- -C system/bt/gd $(addprefix -f ,$(PRIVATE_cert_test_sources)) \
- -C $(HOST_OUT_EXECUTABLES) $(addprefix -f ,$(PRIVATE_host_executables)) \
- -C $(HOST_OUT_SHARED_LIBRARIES) $(addprefix -f ,$(PRIVATE_host_python_extension_libraries)) \
- -P lib64 \
- -C $(HOST_OUT_SHARED_LIBRARIES) $(addprefix -f ,$(PRIVATE_host_libraries)) \
- -P target \
- -C $(TARGET_OUT_EXECUTABLES) $(addprefix -f ,$(PRIVATE_target_executables)) \
- -C $(TARGET_OUT_SHARED_LIBRARIES) $(addprefix -f ,$(PRIVATE_target_libraries))
-
-# TODO: Find a better way to locate output from SOONG genrule()
-LOCAL_cert_generated_py_zip := \
- $(SOONG_OUT_DIR)/.intermediates/system/bt/gd/BluetoothFacadeAndCertGeneratedStub_py/gen/bluetooth_cert_generated_py.zip
-
-LOCAL_acts_zip := $(HOST_OUT)/acts-dist/acts.zip
-
-bluetooth_cert_tests_py_package_zip := \
- $(call intermediates-dir-for,PACKAGING,bluetooth_cert_tests_py_package,HOST)/bluetooth_cert_tests.zip
-
-$(bluetooth_cert_tests_py_package_zip): PRIVATE_cert_src_and_bin_zip := $(bluetooth_cert_src_and_bin_zip)
-$(bluetooth_cert_tests_py_package_zip): PRIVATE_acts_zip := $(LOCAL_acts_zip)
-$(bluetooth_cert_tests_py_package_zip): PRIVATE_cert_generated_py_zip := $(LOCAL_cert_generated_py_zip)
-$(bluetooth_cert_tests_py_package_zip): $(SOONG_ZIP) $(LOCAL_acts_zip) \
- $(bluetooth_cert_src_and_bin_zip) $(bluetooth_cert_generated_py_zip)
- @echo "Packaging Bluetooth Cert Tests into $@"
- @rm -rf $(dir $@)bluetooth_cert_tests
- @rm -rf $(dir $@)acts
- @mkdir -p $(dir $@)bluetooth_cert_tests
- @mkdir -p $(dir $@)acts
- $(hide) unzip -o -q $(PRIVATE_acts_zip) "tools/test/connectivity/acts/framework/*" -d $(dir $@)acts
- $(hide) unzip -o -q $(PRIVATE_cert_src_and_bin_zip) -d $(dir $@)bluetooth_cert_tests
- $(hide) unzip -o -q $(PRIVATE_cert_generated_py_zip) -d $(dir $@)bluetooth_cert_tests
- # Make all subdirectory of gd Python pacakages except lib64 and target
- $(hide) for f in `find $(dir $@)bluetooth_cert_tests -type d -name "*" \
- -not -path "$(dir $@)bluetooth_cert_tests/target*" \
- -not -path "$(dir $@)bluetooth_cert_tests/lib64*"` \
- ; do (touch -a $$f/__init__.py) ; done
- $(hide) $(SOONG_ZIP) -d -o $@ -C $(dir $@)bluetooth_cert_tests -D $(dir $@)bluetooth_cert_tests \
- -P acts_framework \
- -C $(dir $@)acts/tools/test/connectivity/acts/framework -D $(dir $@)acts/tools/test/connectivity/acts/framework \
- -P llvm_binutils -C $(LLVM_PREBUILTS_BASE)/linux-x86/$(LLVM_PREBUILTS_VERSION) \
- -f $(LLVM_PREBUILTS_BASE)/linux-x86/$(LLVM_PREBUILTS_VERSION)/bin/llvm-cov \
- -f $(LLVM_PREBUILTS_BASE)/linux-x86/$(LLVM_PREBUILTS_VERSION)/bin/llvm-profdata \
- -f $(LLVM_PREBUILTS_BASE)/linux-x86/$(LLVM_PREBUILTS_VERSION)/bin/llvm-symbolizer \
- -f $(LLVM_PREBUILTS_BASE)/linux-x86/$(LLVM_PREBUILTS_VERSION)/lib64/libc++.so.1
-
-$(call dist-for-goals,bluetooth_stack_with_facade,$(bluetooth_cert_tests_py_package_zip):bluetooth_cert_tests.zip)
+bluetooth_cert_test_file_list := \
+ $(call all-named-files-under,*.py,cert) \
+ $(call all-named-files-under,*.sh,cert) \
+ $(call all-named-files-under,*.proto,cert facade hal hci/cert hci/facade l2cap/classic \
+ l2cap/classic/cert neighbor/facade security) \
+ cert/cert_testcases_facade_only \
+ cert/android_devices_config.json \
+ cert/host_only_config_facade_only.json \
+ hal/cert/simple_hal_test.py \
+ hci/cert/acl_manager_test.py \
+ hci/cert/controller_test.py \
+ hci/cert/direct_hci_test.py \
+ hci/cert/le_acl_manager_test.py \
+ hci/cert/le_advertising_manager_test.py \
+ hci/cert/le_scanning_manager_test.py \
+ l2cap/classic/cert/l2cap_test.py \
+ l2cap/classic/cert/pts_l2cap_test.py \
+ neighbor/cert/neighbor_test.py \
+ security/cert/simple_security_test.py \
+ shim/cert/stack_test.py
+
+
+bluetooth_cert_test_file_list := $(addprefix $(LOCAL_PATH)/,$(bluetooth_cert_test_file_list))
+
+bluetooth_cert_test_file_list += \
+ $(HOST_OUT_EXECUTABLES)/bluetooth_stack_with_facade \
+ $(HOST_OUT_SHARED_LIBRARIES)/bluetooth_packets_python3.so \
+ $(HOST_OUT_SHARED_LIBRARIES)/libbluetooth_gd.so \
+ $(HOST_OUT_SHARED_LIBRARIES)/libc++.so \
+ $(HOST_OUT_SHARED_LIBRARIES)/libgrpc++_unsecure.so \
+ $(TARGET_OUT_EXECUTABLES)/bluetooth_stack_with_facade \
+ $(TARGET_OUT_SHARED_LIBRARIES)/libbluetooth_gd.so \
+ $(TARGET_OUT_SHARED_LIBRARIES)/libgrpc++_unsecure.so \
+ $(HOST_OUT_NATIVE_TESTS)/root-canal/root-canal
+
+bluetooth_cert_zip_path := \
+ $(call intermediates-dir-for,PACKAGING,bluetooth_cert_test_package,HOST)/bluetooth_cert_test.zip
+
+$(bluetooth_cert_zip_path): PRIVATE_BLUETOOTH_CERT_TEST_FILE_LIST := $(bluetooth_cert_test_file_list)
+
+$(bluetooth_cert_zip_path) : $(SOONG_ZIP) $(bluetooth_cert_test_file_list)
+ $(hide) $(SOONG_ZIP) -d -o $@ $(addprefix -f ,$(PRIVATE_BLUETOOTH_CERT_TEST_FILE_LIST))
+
+$(call dist-for-goals,bluetooth_stack_with_facade,$(bluetooth_cert_zip_path):bluetooth_cert_test.zip)
diff --git a/gd/BUILD.gn b/gd/BUILD.gn
deleted file mode 100644
index 14ec30326..000000000
--- a/gd/BUILD.gn
+++ /dev/null
@@ -1,134 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import("//bt/gd/dumpsys/bundler/bundler.gni")
-import("//bt/gd/packet/parser/packetgen.gni")
-import("//common-mk/flatbuffer.gni")
-
-config("gd_defaults") {
- cflags_cc = [
- "-DGOOGLE_PROTOBUF_NO_RTTI",
- "-Wno-unused-parameter",
- "-Wno-unused-result",
- "-Wno-tautological-overlap-compare",
- ]
-
- defines = [
- "OS_LINUX_GENERIC",
- "OS_GENERIC",
- ]
-
- libs = [
- "ssl",
- "crypto",
- ]
-
- include_dirs = [ "//bt/gd" ]
- configs = [ "//bt:target_defaults" ]
-}
-
-config("rust_defaults") {
- # Empty for now
-}
-
-group("gd_default_deps") {
- deps = [
- "//bt/gd:BluetoothGeneratedDumpsysDataSchema_h",
- "//bt/gd:BluetoothGeneratedPackets_h",
- "//bt/gd/dumpsys:BluetoothGeneratedDumpsysBundledSchema_h",
- "//bt/gd/rust/shim:init_flags_bridge_header",
- ]
-}
-
-static_library("libbluetooth_gd") {
- sources = [
- "module.cc",
- "stack_manager.cc",
- ]
-
- include_dirs = [ "." ]
- configs += [ ":gd_defaults" ]
- deps = [
- "//bt/gd/rust/topshim:libbluetooth_topshim",
- "//bt/gd/rust/shim:libbluetooth_rust_interop",
- "//bt/gd:BluetoothGeneratedPackets_h",
- "//bt/gd/att:BluetoothAttSources",
- "//bt/gd/common:BluetoothCommonSources",
- "//bt/gd/crypto_toolbox:BluetoothCryptoToolboxSources",
- "//bt/gd/dumpsys:BluetoothDumpsysSources",
- "//bt/gd/btaa:BluetoothBtaaSources_linux",
- "//bt/gd/hal:BluetoothHalSources",
- "//bt/gd/hal:BluetoothHalSources_hci_host",
- "//bt/gd/l2cap:BluetoothL2capSources",
- "//bt/gd/neighbor:BluetoothNeighborSources",
- "//bt/gd/security:BluetoothSecuritySources",
- "//bt/gd/shim:BluetoothShimSources",
- "//bt/gd/storage:BluetoothStorageSources",
- ]
-}
-
-flatbuffer("BluetoothGeneratedDumpsysDataSchema_h") {
- sources = [
- "btaa/activity_attribution.fbs",
- "common/init_flags.fbs",
- "dumpsys_data.fbs",
- "hci/hci_acl_manager.fbs",
- "l2cap/classic/l2cap_classic_module.fbs",
- "shim/dumpsys.fbs",
- ]
-}
-
-bt_flatc_binary_schema("BluetoothGeneratedDumpsysBinarySchema_bfbs") {
- sources = [
- "btaa/activity_attribution.fbs",
- "common/init_flags.fbs",
- "dumpsys_data.fbs",
- "hci/hci_acl_manager.fbs",
- "l2cap/classic/l2cap_classic_module.fbs",
- "shim/dumpsys.fbs",
- ]
-
- include_dir = "bt/gd"
-}
-
-packetgen_py("BluetoothGeneratedPackets_python3_cc") {
- sources = [
- "hci/hci_packets.pdl",
- "l2cap/l2cap_packets.pdl",
- "security/smp_packets.pdl",
- ]
-
- include = "bt/gd"
- source_root = "../.."
- shards = 10
-}
-
-packetgen_headers("BluetoothGeneratedPackets_h") {
- sources = [
- "hci/hci_packets.pdl",
- "l2cap/l2cap_packets.pdl",
- "security/smp_packets.pdl",
- ]
-
- include = "bt/gd"
- source_root = "../.."
-}
-
-packetgen_rust("BluetoothGeneratedPackets_rust") {
- sources = [ "hci/hci_packets.pdl" ]
-
- include = "bt/gd"
- source_root = "../.."
-}
diff --git a/gd/README.md b/gd/README.md
index 18a021132..52b4e58a3 100644
--- a/gd/README.md
+++ b/gd/README.md
@@ -1,27 +1,3 @@
### Why is gabeldorsche plural?
Please see this [informative video we've prepared](https://www.youtube.com/watch?v=vLRyJ0dawjM).
-
-### Architecture
-
-Guidelines for developing the Gabeldorsche (GD) stack
-
-* [Architecture](./docs/architecture/architecture.md)
-* [Style Guide](./docs/architecture/style_guide.md)
-
-### Testing
-
-Gabeldorsche (GD) was built with test driven development in mind. Three types of
-tests are used in ensuring Gabeldorsche stack's stability, correctness and free
-from regression.
-
-If you are verifying something is glued or hooked up correctly inside the stack,
-use a unit test.
-
-* [GTest Unit Test](./docs/testing/gtest.md)
-
-If you are verifying correct behavior (especially interop problems) **DO NOT**
-write a unit test as this not a good use of your time. Write a [cert test](./cert_test.md) instead
-so it applies to any stack.
-
-* [GD Certification Tests](./docs/testing/cert_test.md)
diff --git a/gd/TEST_MAPPING b/gd/TEST_MAPPING
new file mode 100644
index 000000000..f0ddeafb4
--- /dev/null
+++ b/gd/TEST_MAPPING
@@ -0,0 +1,12 @@
+{
+ "presubmit" : [
+ {
+ "name" : "bluetooth_test_gd",
+ "host" : true
+ },
+ {
+ "name" : "bluetooth_packet_parser_test",
+ "host" : true
+ }
+ ]
+}
diff --git a/gd/att/Android.bp b/gd/att/Android.bp
index 6511df68c..b7af1efff 100644
--- a/gd/att/Android.bp
+++ b/gd/att/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothAttSources",
srcs: [
diff --git a/gd/att/att_module.cc b/gd/att/att_module.cc
index 7f411333c..2d1c3b1e0 100644
--- a/gd/att/att_module.cc
+++ b/gd/att/att_module.cc
@@ -16,25 +16,23 @@
#define LOG_TAG "att"
-#include "att/att_module.h"
-
#include <memory>
-
-#include "l2cap/classic/l2cap_classic_module.h"
-#include "l2cap/le/l2cap_le_module.h"
#include "module.h"
#include "os/handler.h"
#include "os/log.h"
+#include "att/att_module.h"
+#include "l2cap/classic/l2cap_classic_module.h"
+#include "l2cap/le/l2cap_le_module.h"
+
namespace bluetooth {
namespace att {
const ModuleFactory AttModule::Factory = ModuleFactory([]() { return new AttModule(); });
namespace {
-void OnAttRegistrationCompleteLe(
- l2cap::le::FixedChannelManager::RegistrationResult result,
- std::unique_ptr<l2cap::le::FixedChannelService> le_smp_service) {
+void OnAttRegistrationCompleteLe(l2cap::le::FixedChannelManager::RegistrationResult result,
+ std::unique_ptr<l2cap::le::FixedChannelService> le_smp_service) {
LOG_INFO("ATT channel registration complete");
}
@@ -44,22 +42,15 @@ void OnAttConnectionOpenLe(std::unique_ptr<l2cap::le::FixedChannel> channel) {
} // namespace
struct AttModule::impl {
- impl(
- os::Handler* att_handler,
- l2cap::le::L2capLeModule* l2cap_le_module,
- l2cap::classic::L2capClassicModule* l2cap_classic_module)
+ impl(os::Handler* att_handler, l2cap::le::L2capLeModule* l2cap_le_module,
+ l2cap::classic::L2capClassicModule* l2cap_classic_module)
: att_handler_(att_handler), l2cap_le_module_(l2cap_le_module), l2cap_classic_module_(l2cap_classic_module) {
// TODO: move that into a ATT manager, or other proper place
std::unique_ptr<bluetooth::l2cap::le::FixedChannelManager> l2cap_manager_le_(
l2cap_le_module_->GetFixedChannelManager());
- // TODO(b/161256497): CID 4 is taken by shim layer ATT module so far. When we migrate to GD ATT module, we use real
- // CID here.
- constexpr uint16_t kFakeLeAttributeCid = 50;
- l2cap_manager_le_->RegisterService(
- kFakeLeAttributeCid,
- common::BindOnce(&OnAttRegistrationCompleteLe),
- common::Bind(&OnAttConnectionOpenLe),
- att_handler_);
+ l2cap_manager_le_->RegisterService(bluetooth::l2cap::kLeAttributeCid, {},
+ common::BindOnce(&OnAttRegistrationCompleteLe),
+ common::Bind(&OnAttConnectionOpenLe), att_handler_);
}
os::Handler* att_handler_;
@@ -73,8 +64,8 @@ void AttModule::ListDependencies(ModuleList* list) {
}
void AttModule::Start() {
- pimpl_ = std::make_unique<impl>(
- GetHandler(), GetDependency<l2cap::le::L2capLeModule>(), GetDependency<l2cap::classic::L2capClassicModule>());
+ pimpl_ = std::make_unique<impl>(GetHandler(), GetDependency<l2cap::le::L2capLeModule>(),
+ GetDependency<l2cap::classic::L2capClassicModule>());
}
void AttModule::Stop() {
diff --git a/gd/btaa/Android.bp b/gd/btaa/Android.bp
deleted file mode 100644
index 2aea7eefb..000000000
--- a/gd/btaa/Android.bp
+++ /dev/null
@@ -1,32 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-filegroup {
- name: "BluetoothBtaaSources_android",
- srcs: [
- "android/activity_attribution.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothBtaaSources_host",
- srcs: [
- "host/activity_attribution.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothBtaaSources_linux_generic",
- srcs: [
- "linux_generic/attribution_processor.cc",
- "linux_generic/cmd_evt_classification.cc",
- "linux_generic/hci_processor.cc",
- "linux_generic/wakelock_processor.cc",
- ],
-}
diff --git a/gd/btaa/BUILD.gn b/gd/btaa/BUILD.gn
deleted file mode 100644
index 342a4e3dc..000000000
--- a/gd/btaa/BUILD.gn
+++ /dev/null
@@ -1,22 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-source_set("BluetoothBtaaSources_linux") {
- sources = [ "linux/activity_attribution.cc" ]
-
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ "//bt/gd:gd_default_deps" ]
-}
diff --git a/gd/btaa/activity_attribution.fbs b/gd/btaa/activity_attribution.fbs
deleted file mode 100644
index 9ff18cd3a..000000000
--- a/gd/btaa/activity_attribution.fbs
+++ /dev/null
@@ -1,29 +0,0 @@
-namespace bluetooth.activity_attribution;
-
-attribute "privacy";
-
-table WakeupEntry {
- wakeup_time:string;
- activity:string;
- address:string;
-}
-
-table DeviceActivityAggregationEntry {
- address:string;
- activity:string;
- wakeup_count:int;
- byte_count:int;
- wakelock_duration_ms:int;
- creation_time:string;
-}
-
-table ActivityAttributionData {
- title_wakeup:string;
- num_wakeup:int;
- wakeup_attribution:[WakeupEntry];
- title_activity:string;
- num_device_activity:int;
- device_activity_aggregation:[DeviceActivityAggregationEntry];
-}
-
-root_type ActivityAttributionData; \ No newline at end of file
diff --git a/gd/btaa/activity_attribution.h b/gd/btaa/activity_attribution.h
deleted file mode 100644
index 9bba347fe..000000000
--- a/gd/btaa/activity_attribution.h
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "hal/snoop_logger.h"
-#include "hci/address.h"
-#include "module.h"
-
-namespace bluetooth {
-namespace activity_attribution {
-
-enum class Activity : uint8_t { UNKNOWN = 0, ACL, ADVERTISE, CONNECT, CONTROL, HFP, ISO, SCAN, VENDOR };
-
-using CreationTime = std::chrono::time_point<std::chrono::system_clock>;
-
-struct BtaaAggregationEntry {
- hci::Address address;
- Activity activity;
- uint16_t wakeup_count;
- uint32_t byte_count;
- uint32_t wakelock_duration_ms;
- CreationTime creation_time;
-};
-
-class ActivityAttributionCallback {
- public:
- virtual ~ActivityAttributionCallback() = default;
-
- // Callback when Bluetooth woke up the system
- virtual void OnWakeup(const Activity activity, const hci::Address& address) = 0;
-
- // Callback when Bluetooth activity logs are ready to be moved
- virtual void OnActivityLogsReady(const std::vector<BtaaAggregationEntry> logs) = 0;
-};
-
-class ActivityAttribution : public bluetooth::Module {
- public:
- ActivityAttribution() = default;
- ~ActivityAttribution() = default;
-
- void Capture(const hal::HciPacket& packet, hal::SnoopLogger::PacketType type);
- void OnWakelockAcquired();
- void OnWakelockReleased();
- void OnWakeup();
- void RegisterActivityAttributionCallback(ActivityAttributionCallback* callback);
-
- static const ModuleFactory Factory;
-
- protected:
- std::string ToString() const override;
- void ListDependencies(ModuleList* list) override;
- void Start() override;
- void Stop() override;
- DumpsysDataFinisher GetDumpsysData(flatbuffers::FlatBufferBuilder* builder) const override; // Module
-
- private:
- struct impl;
- std::unique_ptr<impl> pimpl_;
-
- DISALLOW_COPY_AND_ASSIGN(ActivityAttribution);
-};
-
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/btaa/android/activity_attribution.cc b/gd/btaa/android/activity_attribution.cc
deleted file mode 100644
index 3b72feb3a..000000000
--- a/gd/btaa/android/activity_attribution.cc
+++ /dev/null
@@ -1,211 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "btaa"
-
-#include "btaa/activity_attribution.h"
-#include "activity_attribution_generated.h"
-
-#include <aidl/android/system/suspend/BnSuspendCallback.h>
-#include <aidl/android/system/suspend/BnWakelockCallback.h>
-#include <aidl/android/system/suspend/ISuspendControlService.h>
-#include <android/binder_manager.h>
-
-#include "btaa/attribution_processor.h"
-#include "btaa/hci_processor.h"
-#include "btaa/wakelock_processor.h"
-#include "module.h"
-#include "os/log.h"
-
-using aidl::android::system::suspend::BnSuspendCallback;
-using aidl::android::system::suspend::BnWakelockCallback;
-using aidl::android::system::suspend::ISuspendCallback;
-using aidl::android::system::suspend::ISuspendControlService;
-using Status = ::ndk::ScopedAStatus;
-using namespace ndk;
-
-namespace bluetooth {
-namespace activity_attribution {
-
-const ModuleFactory ActivityAttribution::Factory = ModuleFactory([]() { return new ActivityAttribution(); });
-
-static const std::string kBtWakelockName("hal_bluetooth_lock");
-static const std::string kBtWakeupReason("hs_uart_wakeup");
-static const size_t kHciAclHeaderSize = 4;
-
-struct wakelock_callback : public BnWakelockCallback {
- wakelock_callback(ActivityAttribution* module) : module_(module) {}
-
- Status notifyAcquired() override {
- module_->OnWakelockAcquired();
- return Status::ok();
- }
- Status notifyReleased() override {
- module_->OnWakelockReleased();
- return Status::ok();
- }
-
- ActivityAttribution* module_;
-};
-
-struct wakeup_callback : public BnSuspendCallback {
- wakeup_callback(ActivityAttribution* module) : module_(module) {}
-
- Status notifyWakeup(bool success, const std::vector<std::string>& wakeup_reasons) override {
- for (auto& wakeup_reason : wakeup_reasons) {
- if (wakeup_reason.find(kBtWakeupReason) != std::string::npos) {
- module_->OnWakeup();
- break;
- }
- }
- return Status::ok();
- }
-
- ActivityAttribution* module_;
-};
-
-struct ActivityAttribution::impl {
- impl(ActivityAttribution* module) {
- bool is_registered = false;
-
- auto control_service =
- ISuspendControlService::fromBinder(SpAIBinder(AServiceManager_getService("suspend_control")));
- if (!control_service) {
- LOG_ERROR("Fail to obtain suspend_control");
- return;
- }
-
- Status register_callback_status =
- control_service->registerCallback(SharedRefBase::make<wakeup_callback>(module), &is_registered);
- if (!is_registered || !register_callback_status.isOk()) {
- LOG_ERROR("Fail to register wakeup callback");
- return;
- }
-
- register_callback_status = control_service->registerWakelockCallback(
- SharedRefBase::make<wakelock_callback>(module), kBtWakelockName, &is_registered);
- if (!is_registered || !register_callback_status.isOk()) {
- LOG_ERROR("Fail to register wakelock callback");
- return;
- }
- }
-
- void on_hci_packet(hal::HciPacket packet, hal::SnoopLogger::PacketType type, uint16_t length) {
- attribution_processor_.OnBtaaPackets(std::move(hci_processor_.OnHciPacket(std::move(packet), type, length)));
- }
-
- void on_wakelock_acquired() {
- wakelock_processor_.OnWakelockAcquired();
- }
-
- void on_wakelock_released() {
- uint32_t wakelock_duration_ms = 0;
-
- wakelock_duration_ms = wakelock_processor_.OnWakelockReleased();
- if (wakelock_duration_ms != 0) {
- attribution_processor_.OnWakelockReleased(wakelock_duration_ms);
- }
- }
-
- void on_wakeup() {
- attribution_processor_.OnWakeup();
- }
-
- void register_callback(ActivityAttributionCallback* callback) {
- callback_ = callback;
- }
-
- void Dump(
- std::promise<flatbuffers::Offset<ActivityAttributionData>> promise, flatbuffers::FlatBufferBuilder* fb_builder) {
- attribution_processor_.Dump(std::move(promise), fb_builder);
- }
-
- ActivityAttributionCallback* callback_;
- AttributionProcessor attribution_processor_;
- HciProcessor hci_processor_;
- WakelockProcessor wakelock_processor_;
-};
-
-void ActivityAttribution::Capture(const hal::HciPacket& packet, hal::SnoopLogger::PacketType type) {
- uint16_t original_length = packet.size();
- uint16_t truncate_length;
-
- switch (type) {
- case hal::SnoopLogger::PacketType::CMD:
- case hal::SnoopLogger::PacketType::EVT:
- truncate_length = packet.size();
- break;
- case hal::SnoopLogger::PacketType::ACL:
- case hal::SnoopLogger::PacketType::SCO:
- case hal::SnoopLogger::PacketType::ISO:
- truncate_length = kHciAclHeaderSize;
- break;
- }
-
- if (!truncate_length) {
- return;
- }
-
- hal::HciPacket truncate_packet(packet.begin(), packet.begin() + truncate_length);
- CallOn(pimpl_.get(), &impl::on_hci_packet, truncate_packet, type, original_length);
-}
-
-void ActivityAttribution::OnWakelockAcquired() {
- CallOn(pimpl_.get(), &impl::on_wakelock_acquired);
-}
-
-void ActivityAttribution::OnWakelockReleased() {
- CallOn(pimpl_.get(), &impl::on_wakelock_released);
-}
-
-void ActivityAttribution::OnWakeup() {
- CallOn(pimpl_.get(), &impl::on_wakeup);
-}
-
-void ActivityAttribution::RegisterActivityAttributionCallback(ActivityAttributionCallback* callback) {
- CallOn(pimpl_.get(), &impl::register_callback, callback);
-}
-
-std::string ActivityAttribution::ToString() const {
- return "Btaa Module";
-}
-
-void ActivityAttribution::ListDependencies(ModuleList* list) {}
-
-void ActivityAttribution::Start() {
- pimpl_ = std::make_unique<impl>(this);
-}
-
-void ActivityAttribution::Stop() {
- pimpl_.reset();
-}
-
-DumpsysDataFinisher ActivityAttribution::GetDumpsysData(flatbuffers::FlatBufferBuilder* fb_builder) const {
- ASSERT(fb_builder != nullptr);
-
- std::promise<flatbuffers::Offset<ActivityAttributionData>> promise;
- auto future = promise.get_future();
- pimpl_->Dump(std::move(promise), fb_builder);
-
- auto dumpsys_data = future.get();
-
- return [dumpsys_data](DumpsysDataBuilder* dumpsys_builder) {
- dumpsys_builder->add_activity_attribution_dumpsys_data(dumpsys_data);
- };
-}
-
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/btaa/attribution_processor.h b/gd/btaa/attribution_processor.h
deleted file mode 100644
index 11bbc9cc4..000000000
--- a/gd/btaa/attribution_processor.h
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include <unordered_map>
-
-#include "hci_processor.h"
-
-namespace bluetooth {
-namespace activity_attribution {
-
-static constexpr size_t kWakeupAggregatorSize = 200;
-
-struct AddressActivityKey {
- hci::Address address;
- Activity activity;
-
- bool operator==(const AddressActivityKey& other) const {
- return (address == other.address && activity == other.activity);
- }
-};
-
-struct AddressActivityKeyHasher {
- std::size_t operator()(const AddressActivityKey& key) const {
- return (
- (std::hash<std::string>()(key.address.ToString()) ^
- (std::hash<unsigned char>()(static_cast<unsigned char>(key.activity)))));
- }
-};
-
-struct WakeupDescriptor {
- Activity activity_;
- const hci::Address address_;
- WakeupDescriptor(Activity activity, const hci::Address address) : activity_(activity), address_(address) {}
- virtual ~WakeupDescriptor() {}
-};
-
-class AttributionProcessor {
- public:
- void OnBtaaPackets(std::vector<BtaaHciPacket> btaa_packets);
- void OnWakelockReleased(uint32_t duration_ms);
- void OnWakeup();
- void Dump(
- std::promise<flatbuffers::Offset<ActivityAttributionData>> promise, flatbuffers::FlatBufferBuilder* fb_builder);
-
- private:
- bool wakeup_ = false;
- std::unordered_map<AddressActivityKey, BtaaAggregationEntry, AddressActivityKeyHasher> btaa_aggregator_;
- std::unordered_map<AddressActivityKey, BtaaAggregationEntry, AddressActivityKeyHasher> wakelock_duration_aggregator_;
- common::TimestampedCircularBuffer<WakeupDescriptor> wakeup_aggregator_ =
- common::TimestampedCircularBuffer<WakeupDescriptor>(kWakeupAggregatorSize);
- const char* ActivityToString(Activity activity);
-};
-
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/btaa/cmd_evt_classification.h b/gd/btaa/cmd_evt_classification.h
deleted file mode 100644
index 1aae6c224..000000000
--- a/gd/btaa/cmd_evt_classification.h
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "btaa/activity_attribution.h"
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace activity_attribution {
-
-struct CmdEvtActivityClassification {
- Activity activity;
- uint16_t connection_handle_pos;
- uint16_t address_pos;
-};
-
-CmdEvtActivityClassification lookup_cmd(hci::OpCode opcode);
-CmdEvtActivityClassification lookup_event(hci::EventCode event_code);
-CmdEvtActivityClassification lookup_le_event(hci::SubeventCode subevent_code);
-
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/btaa/hci_processor.h b/gd/btaa/hci_processor.h
deleted file mode 100644
index 47fbc68c3..000000000
--- a/gd/btaa/hci_processor.h
+++ /dev/null
@@ -1,87 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "btaa/activity_attribution.h"
-#include "btaa/cmd_evt_classification.h"
-#include "hal/snoop_logger.h"
-#include "hci/address.h"
-
-namespace bluetooth {
-namespace activity_attribution {
-
-struct BtaaHciPacket {
- Activity activity;
- hci::Address address;
- uint16_t byte_count;
-
- BtaaHciPacket() {}
- BtaaHciPacket(Activity activity, hci::Address address, uint16_t byte_count)
- : activity(activity), address(address), byte_count(byte_count) {}
-};
-
-class DeviceParser {
- public:
- void match_handle_with_address(uint16_t connection_handle, hci::Address& address);
-
- private:
- std::map<uint16_t, hci::Address> connection_lookup_table_;
-};
-
-struct PendingCommand {
- hci::OpCode opcode;
- BtaaHciPacket btaa_hci_packet;
-};
-
-class HciProcessor {
- public:
- std::vector<BtaaHciPacket> OnHciPacket(hal::HciPacket packet, hal::SnoopLogger::PacketType type, uint16_t length);
-
- private:
- void process_le_event(std::vector<BtaaHciPacket>& btaa_hci_packets, int16_t byte_count, hci::EventView& event);
- void process_special_event(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- hci::EventCode event_code,
- uint16_t byte_count,
- hci::EventView& event);
- void process_command(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- packet::PacketView<packet::kLittleEndian>& packet_view,
- uint16_t byte_count);
- void process_event(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- packet::PacketView<packet::kLittleEndian>& packet_view,
- uint16_t byte_count);
- void process_acl(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- packet::PacketView<packet::kLittleEndian>& packet_view,
- uint16_t byte_count);
- void process_sco(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- packet::PacketView<packet::kLittleEndian>& packet_view,
- uint16_t byte_count);
- void process_iso(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- packet::PacketView<packet::kLittleEndian>& packet_view,
- uint16_t byte_count);
-
- DeviceParser device_parser_;
- PendingCommand pending_command_;
-};
-
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/btaa/host/activity_attribution.cc b/gd/btaa/host/activity_attribution.cc
deleted file mode 100644
index a2f7d70a9..000000000
--- a/gd/btaa/host/activity_attribution.cc
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "btaa/activity_attribution.h"
-
-#include "module.h"
-
-namespace bluetooth {
-namespace activity_attribution {
-
-struct ActivityAttribution::impl {};
-
-void ActivityAttribution::OnWakelockAcquired() {}
-
-void ActivityAttribution::OnWakelockReleased() {}
-
-void ActivityAttribution::OnWakeup() {}
-
-void ActivityAttribution::RegisterActivityAttributionCallback(ActivityAttributionCallback* callback) {}
-
-std::string ActivityAttribution::ToString() const {
- return "Btaa Module";
-}
-
-void ActivityAttribution::ListDependencies(ModuleList* list) {}
-
-void ActivityAttribution::Start() {}
-
-void ActivityAttribution::Stop() {}
-
-const ModuleFactory ActivityAttribution::Factory = ModuleFactory([]() { return new ActivityAttribution(); });
-
-DumpsysDataFinisher EmptyDumpsysDataFinisher = [](DumpsysDataBuilder* dumpsys_data_builder) {};
-DumpsysDataFinisher ActivityAttribution::GetDumpsysData(flatbuffers::FlatBufferBuilder* builder) const {
- return EmptyDumpsysDataFinisher;
-}
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/btaa/linux/activity_attribution.cc b/gd/btaa/linux/activity_attribution.cc
deleted file mode 100644
index dd6a7db98..000000000
--- a/gd/btaa/linux/activity_attribution.cc
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "btaa/activity_attribution.h"
-
-// TODO: Implement for Linux.
-namespace bluetooth {
-namespace activity_attribution {
-
-const ModuleFactory ActivityAttribution::Factory = ModuleFactory([]() { return new ActivityAttribution(); });
-
-struct ActivityAttribution::impl {
- impl(ActivityAttribution* module) {}
-
- void on_hci_packet(hal::HciPacket packet, hal::SnoopLogger::PacketType type, uint16_t length) {}
-
- void register_callback(ActivityAttributionCallback* callback) {}
-};
-
-void ActivityAttribution::Capture(const hal::HciPacket& packet, hal::SnoopLogger::PacketType type) {}
-
-void ActivityAttribution::RegisterActivityAttributionCallback(ActivityAttributionCallback* callback) {}
-
-std::string ActivityAttribution::ToString() const {
- return "Btaa Module";
-}
-
-void ActivityAttribution::ListDependencies(ModuleList* list) {}
-
-void ActivityAttribution::Start() {}
-
-void ActivityAttribution::Stop() {}
-
-DumpsysDataFinisher EmptyDumpsysDataFinisher = [](DumpsysDataBuilder* dumpsys_data_builder) {};
-DumpsysDataFinisher ActivityAttribution::GetDumpsysData(flatbuffers::FlatBufferBuilder* builder) const {
- return EmptyDumpsysDataFinisher;
-}
-
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/btaa/linux_generic/attribution_processor.cc b/gd/btaa/linux_generic/attribution_processor.cc
deleted file mode 100644
index a55243a06..000000000
--- a/gd/btaa/linux_generic/attribution_processor.cc
+++ /dev/null
@@ -1,181 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "btaa/attribution_processor.h"
-#include "common/strings.h"
-
-#include "os/log.h"
-
-namespace bluetooth {
-namespace activity_attribution {
-
-constexpr char kActivityAttributionTimeFormat[] = "%Y-%m-%d %H:%M:%S";
-// A device-activity aggregation entry expires after two days (172800 seconds)
-static const int kDurationToKeepDeviceActivityEntrySecs = 172800;
-// A transient device-activity aggregation entry is defined as an entry with very few Byte count
-// (200 Bytes, this is about the size of 5 advertising packets) over a period of time (15 minutes)
-static const int kByteCountTransientDeviceActivityEntry = 200;
-static const int kDurationTransientDeviceActivityEntrySecs = 900;
-static const int kMapSizeTrimDownAggregationEntry = 200;
-
-void AttributionProcessor::OnBtaaPackets(std::vector<BtaaHciPacket> btaa_packets) {
- AddressActivityKey key;
-
- for (auto& btaa_packet : btaa_packets) {
- key.address = btaa_packet.address;
- key.activity = btaa_packet.activity;
-
- if (wakelock_duration_aggregator_.find(key) == wakelock_duration_aggregator_.end()) {
- wakelock_duration_aggregator_[key] = {};
- }
- wakelock_duration_aggregator_[key].byte_count += btaa_packet.byte_count;
-
- if (wakeup_) {
- wakelock_duration_aggregator_[key].wakeup_count += 1;
- wakeup_aggregator_.Push(std::move(WakeupDescriptor(btaa_packet.activity, btaa_packet.address)));
- }
- }
- wakeup_ = false;
-}
-
-void AttributionProcessor::OnWakelockReleased(uint32_t duration_ms) {
- uint32_t total_byte_count = 0;
- uint32_t ms_per_byte = 0;
-
- for (auto& it : wakelock_duration_aggregator_) {
- total_byte_count += it.second.byte_count;
- }
-
- if (total_byte_count == 0) {
- return;
- }
-
- ms_per_byte = duration_ms / total_byte_count;
- auto cur_time = std::chrono::system_clock::now();
- for (auto& it : wakelock_duration_aggregator_) {
- it.second.wakelock_duration_ms = ms_per_byte * it.second.byte_count;
- if (btaa_aggregator_.find(it.first) == btaa_aggregator_.end()) {
- btaa_aggregator_[it.first] = {};
- btaa_aggregator_[it.first].creation_time = cur_time;
- }
-
- auto elapsed_time_sec =
- std::chrono::duration_cast<std::chrono::seconds>(cur_time - btaa_aggregator_[it.first].creation_time).count();
- if (elapsed_time_sec > kDurationToKeepDeviceActivityEntrySecs) {
- btaa_aggregator_[it.first].wakeup_count = 0;
- btaa_aggregator_[it.first].byte_count = 0;
- btaa_aggregator_[it.first].wakelock_duration_ms = 0;
- btaa_aggregator_[it.first].creation_time = cur_time;
- }
-
- btaa_aggregator_[it.first].wakeup_count += it.second.wakeup_count;
- btaa_aggregator_[it.first].byte_count += it.second.byte_count;
- btaa_aggregator_[it.first].wakelock_duration_ms += it.second.wakelock_duration_ms;
- }
- wakelock_duration_aggregator_.clear();
-
- if (btaa_aggregator_.size() < kMapSizeTrimDownAggregationEntry) {
- return;
- }
- // Trim down the transient entries in the aggregator to avoid that it overgrows
- for (auto& it : btaa_aggregator_) {
- auto elapsed_time_sec =
- std::chrono::duration_cast<std::chrono::seconds>(cur_time - it.second.creation_time).count();
- if (elapsed_time_sec > kDurationTransientDeviceActivityEntrySecs &&
- it.second.byte_count < kByteCountTransientDeviceActivityEntry) {
- btaa_aggregator_.erase(it.first);
- }
- }
-}
-
-void AttributionProcessor::OnWakeup() {
- if (wakeup_) {
- LOG_INFO("Previous wakeup notification is not consumed.");
- }
- wakeup_ = true;
-}
-
-void AttributionProcessor::Dump(
- std::promise<flatbuffers::Offset<ActivityAttributionData>> promise, flatbuffers::FlatBufferBuilder* fb_builder) {
- // Dump wakeup attribution data
- auto title_wakeup = fb_builder->CreateString("----- Wakeup Attribution Dumpsys -----");
- std::vector<common::TimestampedEntry<WakeupDescriptor>> wakeup_aggregator = wakeup_aggregator_.Pull();
- std::vector<flatbuffers::Offset<WakeupEntry>> wakeup_entry_offsets;
- for (auto& it : wakeup_aggregator) {
- WakeupEntryBuilder wakeup_entry_builder(*fb_builder);
- std::chrono::milliseconds duration(it.timestamp);
- std::chrono::time_point<std::chrono::system_clock> wakeup_time(duration);
- wakeup_entry_builder.add_wakeup_time(fb_builder->CreateString(
- bluetooth::common::StringFormatTimeWithMilliseconds(kActivityAttributionTimeFormat, wakeup_time).c_str()));
- wakeup_entry_builder.add_activity(fb_builder->CreateString((ActivityToString(it.entry.activity_))));
- wakeup_entry_builder.add_address(fb_builder->CreateString(it.entry.address_.ToString()));
- wakeup_entry_offsets.push_back(wakeup_entry_builder.Finish());
- }
- auto wakeup_entries = fb_builder->CreateVector(wakeup_entry_offsets);
-
- // Dump device-based activity aggregation data
- auto title_device_activity = fb_builder->CreateString("----- Device-based Activity Attribution Dumpsys -----");
- std::vector<flatbuffers::Offset<DeviceActivityAggregationEntry>> aggregation_entry_offsets;
- for (auto& it : btaa_aggregator_) {
- DeviceActivityAggregationEntryBuilder device_entry_builder(*fb_builder);
- device_entry_builder.add_address(fb_builder->CreateString(it.first.address.ToString()));
- device_entry_builder.add_activity(fb_builder->CreateString((ActivityToString(it.first.activity))));
- device_entry_builder.add_wakeup_count(it.second.wakeup_count);
- device_entry_builder.add_byte_count(it.second.byte_count);
- device_entry_builder.add_wakelock_duration_ms(it.second.wakelock_duration_ms);
- device_entry_builder.add_creation_time(fb_builder->CreateString(
- bluetooth::common::StringFormatTimeWithMilliseconds(kActivityAttributionTimeFormat, it.second.creation_time)
- .c_str()));
- aggregation_entry_offsets.push_back(device_entry_builder.Finish());
- }
- auto aggregation_entries = fb_builder->CreateVector(aggregation_entry_offsets);
-
- ActivityAttributionDataBuilder builder(*fb_builder);
- builder.add_title_wakeup(title_wakeup);
- builder.add_num_wakeup(wakeup_aggregator.size());
- builder.add_wakeup_attribution(wakeup_entries);
- builder.add_title_activity(title_device_activity);
- builder.add_num_device_activity(btaa_aggregator_.size());
- builder.add_device_activity_aggregation(aggregation_entries);
- btaa_aggregator_.clear();
-
- flatbuffers::Offset<ActivityAttributionData> dumpsys_data = builder.Finish();
- promise.set_value(dumpsys_data);
-}
-
-#ifndef CASE_RETURN_TEXT
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-#endif
-
-const char* AttributionProcessor::ActivityToString(Activity activity) {
- switch (activity) {
- CASE_RETURN_TEXT(Activity::ACL);
- CASE_RETURN_TEXT(Activity::ADVERTISE);
- CASE_RETURN_TEXT(Activity::CONNECT);
- CASE_RETURN_TEXT(Activity::CONTROL);
- CASE_RETURN_TEXT(Activity::HFP);
- CASE_RETURN_TEXT(Activity::ISO);
- CASE_RETURN_TEXT(Activity::SCAN);
- CASE_RETURN_TEXT(Activity::VENDOR);
- default:
- return "UNKNOWN";
- }
-}
-
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/btaa/linux_generic/cmd_evt_classification.cc b/gd/btaa/linux_generic/cmd_evt_classification.cc
deleted file mode 100644
index a8b6151e6..000000000
--- a/gd/btaa/linux_generic/cmd_evt_classification.cc
+++ /dev/null
@@ -1,465 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "btaa/cmd_evt_classification.h"
-
-namespace bluetooth {
-namespace activity_attribution {
-
-CmdEvtActivityClassification lookup_cmd(hci::OpCode opcode) {
- CmdEvtActivityClassification classification = {};
- switch (opcode) {
- case hci::OpCode::INQUIRY:
- case hci::OpCode::INQUIRY_CANCEL:
- case hci::OpCode::PERIODIC_INQUIRY_MODE:
- case hci::OpCode::EXIT_PERIODIC_INQUIRY_MODE:
- classification = {.activity = Activity::SCAN, .connection_handle_pos = 0, .address_pos = 0};
- break;
-
- case hci::OpCode::CREATE_CONNECTION:
- case hci::OpCode::CREATE_CONNECTION_CANCEL:
- case hci::OpCode::ACCEPT_CONNECTION_REQUEST:
- case hci::OpCode::LINK_KEY_REQUEST_REPLY:
- case hci::OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY:
- case hci::OpCode::PIN_CODE_REQUEST_REPLY:
- case hci::OpCode::PIN_CODE_REQUEST_NEGATIVE_REPLY:
- case hci::OpCode::REJECT_CONNECTION_REQUEST:
- case hci::OpCode::REMOTE_NAME_REQUEST:
- case hci::OpCode::REMOTE_NAME_REQUEST_CANCEL:
- case hci::OpCode::ACCEPT_SYNCHRONOUS_CONNECTION:
- case hci::OpCode::REJECT_SYNCHRONOUS_CONNECTION:
- case hci::OpCode::IO_CAPABILITY_REQUEST_REPLY:
- case hci::OpCode::USER_CONFIRMATION_REQUEST_REPLY:
- case hci::OpCode::USER_CONFIRMATION_REQUEST_NEGATIVE_REPLY:
- case hci::OpCode::USER_PASSKEY_REQUEST_REPLY:
- case hci::OpCode::USER_PASSKEY_REQUEST_NEGATIVE_REPLY:
- case hci::OpCode::REMOTE_OOB_DATA_REQUEST_REPLY:
- case hci::OpCode::REMOTE_OOB_DATA_REQUEST_NEGATIVE_REPLY:
- case hci::OpCode::IO_CAPABILITY_REQUEST_NEGATIVE_REPLY:
- case hci::OpCode::ENHANCED_ACCEPT_SYNCHRONOUS_CONNECTION:
- case hci::OpCode::REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY:
- case hci::OpCode::SWITCH_ROLE:
- case hci::OpCode::READ_STORED_LINK_KEY:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 0, .address_pos = 3};
- break;
-
- case hci::OpCode::CENTRAL_LINK_KEY:
- case hci::OpCode::READ_DEFAULT_LINK_POLICY_SETTINGS:
- case hci::OpCode::WRITE_DEFAULT_LINK_POLICY_SETTINGS:
- case hci::OpCode::WRITE_SCAN_ENABLE:
- case hci::OpCode::READ_PAGE_SCAN_ACTIVITY:
- case hci::OpCode::WRITE_PAGE_SCAN_ACTIVITY:
- case hci::OpCode::READ_PAGE_SCAN_TYPE:
- case hci::OpCode::WRITE_PAGE_SCAN_TYPE:
- case hci::OpCode::READ_SIMPLE_PAIRING_MODE:
- case hci::OpCode::WRITE_SIMPLE_PAIRING_MODE:
- case hci::OpCode::READ_SCAN_ENABLE:
- case hci::OpCode::LE_CREATE_CONNECTION_CANCEL:
- case hci::OpCode::LE_READ_CONNECT_LIST_SIZE:
- case hci::OpCode::LE_CLEAR_CONNECT_LIST:
- case hci::OpCode::SEND_KEYPRESS_NOTIFICATION:
- case hci::OpCode::LE_CLEAR_RESOLVING_LIST:
- case hci::OpCode::LE_READ_RESOLVING_LIST_SIZE:
- case hci::OpCode::LE_SET_HOST_CHANNEL_CLASSIFICATION:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 0, .address_pos = 0};
- break;
-
- case hci::OpCode::DISCONNECT:
- case hci::OpCode::CHANGE_CONNECTION_PACKET_TYPE:
- case hci::OpCode::AUTHENTICATION_REQUESTED:
- case hci::OpCode::SET_CONNECTION_ENCRYPTION:
- case hci::OpCode::CHANGE_CONNECTION_LINK_KEY:
- case hci::OpCode::READ_REMOTE_SUPPORTED_FEATURES:
- case hci::OpCode::READ_REMOTE_EXTENDED_FEATURES:
- case hci::OpCode::READ_REMOTE_VERSION_INFORMATION:
- case hci::OpCode::READ_CLOCK_OFFSET:
- case hci::OpCode::READ_LMP_HANDLE:
- case hci::OpCode::SETUP_SYNCHRONOUS_CONNECTION:
- case hci::OpCode::ENHANCED_SETUP_SYNCHRONOUS_CONNECTION:
- case hci::OpCode::HOLD_MODE:
- case hci::OpCode::SNIFF_MODE:
- case hci::OpCode::EXIT_SNIFF_MODE:
- case hci::OpCode::QOS_SETUP:
- case hci::OpCode::ROLE_DISCOVERY:
- case hci::OpCode::READ_LINK_POLICY_SETTINGS:
- case hci::OpCode::WRITE_LINK_POLICY_SETTINGS:
- case hci::OpCode::FLOW_SPECIFICATION:
- case hci::OpCode::SNIFF_SUBRATING:
- case hci::OpCode::FLUSH:
- case hci::OpCode::READ_AUTOMATIC_FLUSH_TIMEOUT:
- case hci::OpCode::WRITE_AUTOMATIC_FLUSH_TIMEOUT:
- case hci::OpCode::READ_LINK_SUPERVISION_TIMEOUT:
- case hci::OpCode::WRITE_LINK_SUPERVISION_TIMEOUT:
- case hci::OpCode::REFRESH_ENCRYPTION_KEY:
- case hci::OpCode::READ_FAILED_CONTACT_COUNTER:
- case hci::OpCode::RESET_FAILED_CONTACT_COUNTER:
- case hci::OpCode::READ_LINK_QUALITY:
- case hci::OpCode::READ_RSSI:
- case hci::OpCode::READ_AFH_CHANNEL_MAP:
- case hci::OpCode::READ_CLOCK:
- case hci::OpCode::READ_ENCRYPTION_KEY_SIZE:
- // READ_LOOPBACK_MODE = 0x1801,
- // WRITE_LOOPBACK_MODE = 0x1802,
- // ENABLE_DEVICE_UNDER_TEST_MODE = 0x1803,
- // WRITE_SIMPLE_PAIRING_DEBUG_MODE = 0x1804,
- // WRITE_SECURE_CONNECTIONS_TEST_MODE = 0x180a,
- case hci::OpCode::ENHANCED_FLUSH:
- case hci::OpCode::LE_CONNECTION_UPDATE:
- case hci::OpCode::LE_START_ENCRYPTION:
- case hci::OpCode::LE_LONG_TERM_KEY_REQUEST_REPLY:
- case hci::OpCode::LE_LONG_TERM_KEY_REQUEST_NEGATIVE_REPLY:
- case hci::OpCode::LE_READ_PHY:
- case hci::OpCode::LE_SET_PHY:
- case hci::OpCode::LE_READ_REMOTE_FEATURES:
- case hci::OpCode::LE_REMOTE_CONNECTION_PARAMETER_REQUEST_REPLY:
- case hci::OpCode::LE_REMOTE_CONNECTION_PARAMETER_REQUEST_NEGATIVE_REPLY:
- case hci::OpCode::LE_SET_DATA_LENGTH:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 3, .address_pos = 0};
- break;
-
- case hci::OpCode::SET_EVENT_MASK:
- case hci::OpCode::RESET:
- case hci::OpCode::SET_EVENT_FILTER:
- case hci::OpCode::READ_PIN_TYPE:
- case hci::OpCode::WRITE_PIN_TYPE:
- case hci::OpCode::WRITE_LOCAL_NAME:
- case hci::OpCode::READ_LOCAL_NAME:
- case hci::OpCode::READ_CONNECTION_ACCEPT_TIMEOUT:
- case hci::OpCode::WRITE_CONNECTION_ACCEPT_TIMEOUT:
- case hci::OpCode::READ_PAGE_TIMEOUT:
- case hci::OpCode::WRITE_PAGE_TIMEOUT:
- case hci::OpCode::READ_AUTHENTICATION_ENABLE:
- case hci::OpCode::WRITE_AUTHENTICATION_ENABLE:
- case hci::OpCode::READ_CLASS_OF_DEVICE:
- case hci::OpCode::WRITE_CLASS_OF_DEVICE:
- case hci::OpCode::READ_VOICE_SETTING:
- case hci::OpCode::WRITE_VOICE_SETTING:
- case hci::OpCode::READ_NUM_BROADCAST_RETRANSMITS:
- case hci::OpCode::WRITE_NUM_BROADCAST_RETRANSMITS:
- case hci::OpCode::READ_HOLD_MODE_ACTIVITY:
- case hci::OpCode::WRITE_HOLD_MODE_ACTIVITY:
- case hci::OpCode::READ_SYNCHRONOUS_FLOW_CONTROL_ENABLE:
- case hci::OpCode::WRITE_SYNCHRONOUS_FLOW_CONTROL_ENABLE:
- case hci::OpCode::SET_CONTROLLER_TO_HOST_FLOW_CONTROL:
- case hci::OpCode::HOST_BUFFER_SIZE:
- case hci::OpCode::HOST_NUM_COMPLETED_PACKETS:
- case hci::OpCode::READ_NUMBER_OF_SUPPORTED_IAC:
- case hci::OpCode::READ_CURRENT_IAC_LAP:
- case hci::OpCode::WRITE_CURRENT_IAC_LAP:
- case hci::OpCode::SET_AFH_HOST_CHANNEL_CLASSIFICATION:
- case hci::OpCode::READ_AFH_CHANNEL_ASSESSMENT_MODE:
- case hci::OpCode::WRITE_AFH_CHANNEL_ASSESSMENT_MODE:
- case hci::OpCode::READ_LE_HOST_SUPPORT:
- case hci::OpCode::WRITE_LE_HOST_SUPPORT:
- case hci::OpCode::READ_SECURE_CONNECTIONS_HOST_SUPPORT:
- case hci::OpCode::WRITE_SECURE_CONNECTIONS_HOST_SUPPORT:
- case hci::OpCode::READ_LOCAL_OOB_EXTENDED_DATA:
- case hci::OpCode::SET_ECOSYSTEM_BASE_INTERVAL:
- case hci::OpCode::CONFIGURE_DATA_PATH:
- case hci::OpCode::READ_LOCAL_VERSION_INFORMATION:
- case hci::OpCode::READ_LOCAL_SUPPORTED_COMMANDS:
- case hci::OpCode::READ_LOCAL_SUPPORTED_FEATURES:
- case hci::OpCode::READ_LOCAL_EXTENDED_FEATURES:
- case hci::OpCode::READ_BUFFER_SIZE:
- case hci::OpCode::READ_BD_ADDR:
- case hci::OpCode::READ_DATA_BLOCK_SIZE:
- case hci::OpCode::READ_LOCAL_SUPPORTED_CODECS_V1:
- case hci::OpCode::READ_LOCAL_SUPPORTED_CODECS_V2:
- case hci::OpCode::READ_LOCAL_SUPPORTED_CODEC_CAPABILITIES:
- case hci::OpCode::READ_LOCAL_SUPPORTED_CONTROLLER_DELAY:
- case hci::OpCode::READ_LOCAL_OOB_DATA:
- case hci::OpCode::LE_GENERATE_DHKEY_COMMAND:
- case hci::OpCode::LE_MODIFY_SLEEP_CLOCK_ACCURACY:
- case hci::OpCode::LE_READ_BUFFER_SIZE_V2:
- case hci::OpCode::LE_READ_SUGGESTED_DEFAULT_DATA_LENGTH:
- case hci::OpCode::LE_WRITE_SUGGESTED_DEFAULT_DATA_LENGTH:
- case hci::OpCode::LE_READ_LOCAL_P_256_PUBLIC_KEY_COMMAND:
- case hci::OpCode::LE_GENERATE_DHKEY_COMMAND_V1:
- case hci::OpCode::LE_SET_EVENT_MASK:
- case hci::OpCode::LE_READ_BUFFER_SIZE_V1:
- case hci::OpCode::LE_READ_LOCAL_SUPPORTED_FEATURES:
- case hci::OpCode::LE_SET_RANDOM_ADDRESS:
- case hci::OpCode::LE_READ_TRANSMIT_POWER:
- case hci::OpCode::LE_READ_RF_PATH_COMPENSATION_POWER:
- case hci::OpCode::LE_WRITE_RF_PATH_COMPENSATION_POWER:
- case hci::OpCode::LE_SET_DEFAULT_PHY:
- case hci::OpCode::LE_ENCRYPT:
- case hci::OpCode::LE_RAND:
- case hci::OpCode::LE_SET_ADDRESS_RESOLUTION_ENABLE:
- case hci::OpCode::LE_SET_RESOLVABLE_PRIVATE_ADDRESS_TIMEOUT:
- case hci::OpCode::LE_READ_MAXIMUM_DATA_LENGTH:
- case hci::OpCode::LE_READ_SUPPORTED_STATES:
- classification = {.activity = Activity::CONTROL, .connection_handle_pos = 0, .address_pos = 0};
- break;
-
- case hci::OpCode::DELETE_STORED_LINK_KEY:
- classification = {.activity = Activity::CONTROL, .connection_handle_pos = 0, .address_pos = 3};
- break;
- case hci::OpCode::READ_TRANSMIT_POWER_LEVEL:
- classification = {.activity = Activity::CONTROL, .connection_handle_pos = 3, .address_pos = 0};
- break;
-
- case hci::OpCode::READ_INQUIRY_SCAN_ACTIVITY:
- case hci::OpCode::WRITE_INQUIRY_SCAN_ACTIVITY:
- case hci::OpCode::READ_INQUIRY_SCAN_TYPE:
- case hci::OpCode::WRITE_INQUIRY_SCAN_TYPE:
- case hci::OpCode::READ_INQUIRY_MODE:
- case hci::OpCode::WRITE_INQUIRY_MODE:
- case hci::OpCode::READ_EXTENDED_INQUIRY_RESPONSE:
- case hci::OpCode::WRITE_EXTENDED_INQUIRY_RESPONSE:
- case hci::OpCode::LE_SET_CIG_PARAMETERS:
- case hci::OpCode::LE_CREATE_CIS:
- case hci::OpCode::LE_REMOVE_CIG:
- case hci::OpCode::LE_ACCEPT_CIS_REQUEST:
- case hci::OpCode::LE_REJECT_CIS_REQUEST:
- case hci::OpCode::LE_CREATE_BIG:
- case hci::OpCode::LE_TERMINATE_BIG:
- case hci::OpCode::LE_BIG_CREATE_SYNC:
- case hci::OpCode::LE_BIG_TERMINATE_SYNC:
- case hci::OpCode::LE_REQUEST_PEER_SCA:
- case hci::OpCode::LE_SETUP_ISO_DATA_PATH:
- case hci::OpCode::LE_REMOVE_ISO_DATA_PATH:
- case hci::OpCode::LE_SET_HOST_FEATURE:
- case hci::OpCode::LE_READ_ISO_LINK_QUALITY:
- case hci::OpCode::LE_ENHANCED_READ_TRANSMIT_POWER_LEVEL:
- case hci::OpCode::LE_READ_REMOTE_TRANSMIT_POWER_LEVEL:
- case hci::OpCode::LE_SET_PATH_LOSS_REPORTING_PARAMETERS:
- case hci::OpCode::LE_SET_PATH_LOSS_REPORTING_ENABLE:
- case hci::OpCode::LE_SET_TRANSMIT_POWER_REPORTING_ENABLE:
- case hci::OpCode::LE_GET_VENDOR_CAPABILITIES:
- case hci::OpCode::LE_MULTI_ADVT:
- case hci::OpCode::LE_BATCH_SCAN:
- case hci::OpCode::LE_ADV_FILTER:
- case hci::OpCode::LE_ENERGY_INFO:
- case hci::OpCode::LE_EXTENDED_SCAN_PARAMS:
- case hci::OpCode::CONTROLLER_DEBUG_INFO:
- case hci::OpCode::CONTROLLER_A2DP_OPCODE:
- case hci::OpCode::CONTROLLER_BQR:
- case hci::OpCode::READ_INQUIRY_RESPONSE_TRANSMIT_POWER_LEVEL:
- case hci::OpCode::WRITE_INQUIRY_TRANSMIT_POWER_LEVEL:
- case hci::OpCode::LE_SET_EXTENDED_SCAN_PARAMETERS:
- case hci::OpCode::LE_SET_EXTENDED_SCAN_ENABLE:
- case hci::OpCode::LE_PERIODIC_ADVERTISING_CREATE_SYNC_CANCEL:
- case hci::OpCode::LE_SET_SCAN_PARAMETERS:
- case hci::OpCode::LE_SET_SCAN_ENABLE:
- case hci::OpCode::LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS:
- case hci::OpCode::LE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE:
- case hci::OpCode::LE_CLEAR_PERIODIC_ADVERTISING_LIST:
- case hci::OpCode::LE_READ_PERIODIC_ADVERTISING_LIST_SIZE:
- case hci::OpCode::LE_PERIODIC_ADVERTISING_TERMINATE_SYNC:
- classification = {.activity = Activity::SCAN, .connection_handle_pos = 0, .address_pos = 0};
- break;
-
- case hci::OpCode::LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER:
- case hci::OpCode::LE_SET_ADVERTISING_DATA:
- case hci::OpCode::LE_SET_SCAN_RESPONSE_DATA:
- case hci::OpCode::LE_SET_ADVERTISING_ENABLE:
- case hci::OpCode::LE_SET_EXTENDED_ADVERTISING_DATA:
- case hci::OpCode::LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE:
- case hci::OpCode::LE_SET_EXTENDED_ADVERTISING_ENABLE:
- case hci::OpCode::LE_READ_MAXIMUM_ADVERTISING_DATA_LENGTH:
- case hci::OpCode::LE_READ_NUMBER_OF_SUPPORTED_ADVERTISING_SETS:
- case hci::OpCode::LE_REMOVE_ADVERTISING_SET:
- case hci::OpCode::LE_CLEAR_ADVERTISING_SETS:
- case hci::OpCode::LE_SET_PERIODIC_ADVERTISING_PARAM:
- case hci::OpCode::LE_SET_PERIODIC_ADVERTISING_DATA:
- case hci::OpCode::LE_SET_PERIODIC_ADVERTISING_ENABLE:
- case hci::OpCode::LE_SET_EXTENDED_ADVERTISING_RANDOM_ADDRESS:
- classification = {.activity = Activity::ADVERTISE, .connection_handle_pos = 0, .address_pos = 0};
- break;
-
- case hci::OpCode::LE_SET_ADVERTISING_PARAMETERS:
- classification = {.activity = Activity::SCAN, .connection_handle_pos = 0, .address_pos = 10};
- break;
- case hci::OpCode::LE_CREATE_CONNECTION:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 0, .address_pos = 9};
- break;
- case hci::OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST:
- case hci::OpCode::LE_READ_CHANNEL_MAP:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 4, .address_pos = 0};
- break;
-
- case hci::OpCode::LE_REMOVE_DEVICE_FROM_CONNECT_LIST:
- case hci::OpCode::LE_ADD_DEVICE_TO_RESOLVING_LIST:
- case hci::OpCode::LE_REMOVE_DEVICE_FROM_RESOLVING_LIST:
- case hci::OpCode::LE_READ_PEER_RESOLVABLE_ADDRESS:
- case hci::OpCode::LE_READ_LOCAL_RESOLVABLE_ADDRESS:
- case hci::OpCode::LE_SET_PRIVACY_MODE:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 0, .address_pos = 4};
- break;
-
- case hci::OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS:
- classification = {.activity = Activity::ADVERTISE, .connection_handle_pos = 0, .address_pos = 15};
- break;
- case hci::OpCode::LE_EXTENDED_CREATE_CONNECTION:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 0, .address_pos = 6};
- break;
- case hci::OpCode::LE_PERIODIC_ADVERTISING_CREATE_SYNC:
- classification = {.activity = Activity::SCAN, .connection_handle_pos = 0, .address_pos = 6};
- break;
- case hci::OpCode::LE_ADD_DEVICE_TO_PERIODIC_ADVERTISING_LIST:
- case hci::OpCode::LE_REMOVE_DEVICE_FROM_PERIODIC_ADVERTISING_LIST:
- classification = {.activity = Activity::SCAN, .connection_handle_pos = 0, .address_pos = 4};
- break;
- case hci::OpCode::LE_PERIODIC_ADVERTISING_SYNC_TRANSFER:
- case hci::OpCode::LE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER:
- case hci::OpCode::LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS:
- classification = {.activity = Activity::SCAN, .connection_handle_pos = 3, .address_pos = 0};
- break;
-
- default:
- classification = {.activity = Activity::UNKNOWN, .connection_handle_pos = 0, .address_pos = 0};
- break;
- }
- return classification;
-}
-
-CmdEvtActivityClassification lookup_event(hci::EventCode event_code) {
- CmdEvtActivityClassification classification = {};
- switch (event_code) {
- case hci::EventCode::INQUIRY_COMPLETE:
- classification = {.activity = Activity::SCAN, .connection_handle_pos = 0, .address_pos = 0};
- break;
- case hci::EventCode::CONNECTION_COMPLETE:
- case hci::EventCode::SYNCHRONOUS_CONNECTION_COMPLETE:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 3, .address_pos = 5};
- break;
-
- case hci::EventCode::CONNECTION_REQUEST:
- case hci::EventCode::PIN_CODE_REQUEST:
- case hci::EventCode::LINK_KEY_REQUEST:
- case hci::EventCode::LINK_KEY_NOTIFICATION:
- case hci::EventCode::USER_PASSKEY_NOTIFICATION:
- case hci::EventCode::KEYPRESS_NOTIFICATION:
- case hci::EventCode::REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION:
- case hci::EventCode::IO_CAPABILITY_REQUEST:
- case hci::EventCode::IO_CAPABILITY_RESPONSE:
- case hci::EventCode::USER_CONFIRMATION_REQUEST:
- case hci::EventCode::USER_PASSKEY_REQUEST:
- case hci::EventCode::REMOTE_OOB_DATA_REQUEST:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 0, .address_pos = 2};
- break;
-
- case hci::EventCode::DISCONNECTION_COMPLETE:
- case hci::EventCode::AUTHENTICATION_COMPLETE:
- case hci::EventCode::ENCRYPTION_CHANGE:
- case hci::EventCode::ENCRYPTION_KEY_REFRESH_COMPLETE:
- case hci::EventCode::LINK_SUPERVISION_TIMEOUT_CHANGED:
- case hci::EventCode::CHANGE_CONNECTION_LINK_KEY_COMPLETE:
- case hci::EventCode::CENTRAL_LINK_KEY_COMPLETE:
- case hci::EventCode::READ_REMOTE_SUPPORTED_FEATURES_COMPLETE:
- case hci::EventCode::READ_REMOTE_VERSION_INFORMATION_COMPLETE:
- case hci::EventCode::QOS_SETUP_COMPLETE:
- case hci::EventCode::MODE_CHANGE:
- case hci::EventCode::READ_CLOCK_OFFSET_COMPLETE:
- case hci::EventCode::CONNECTION_PACKET_TYPE_CHANGED:
- case hci::EventCode::FLOW_SPECIFICATION_COMPLETE:
- case hci::EventCode::READ_REMOTE_EXTENDED_FEATURES_COMPLETE:
- case hci::EventCode::SYNCHRONOUS_CONNECTION_CHANGED:
- case hci::EventCode::SNIFF_SUBRATING:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 3, .address_pos = 0};
- break;
-
- case hci::EventCode::REMOTE_NAME_REQUEST_COMPLETE:
- case hci::EventCode::EXTENDED_INQUIRY_RESULT:
- classification = {.activity = Activity::SCAN, .connection_handle_pos = 0, .address_pos = 3};
- break;
- case hci::EventCode::FLUSH_OCCURRED:
- case hci::EventCode::MAX_SLOTS_CHANGE:
- case hci::EventCode::QOS_VIOLATION:
- case hci::EventCode::ENHANCED_FLUSH_COMPLETE:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 2, .address_pos = 0};
- break;
- case hci::EventCode::ROLE_CHANGE:
- case hci::EventCode::SIMPLE_PAIRING_COMPLETE:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 0, .address_pos = 3};
- break;
- case hci::EventCode::PAGE_SCAN_REPETITION_MODE_CHANGE:
- classification = {.activity = Activity::SCAN, .connection_handle_pos = 0, .address_pos = 2};
- break;
-
- default:
- classification = {.activity = Activity::UNKNOWN, .connection_handle_pos = 0, .address_pos = 0};
- }
- return classification;
-}
-
-CmdEvtActivityClassification lookup_le_event(hci::SubeventCode subevent_code) {
- CmdEvtActivityClassification classification = {};
- switch (subevent_code) {
- case hci::SubeventCode::CONNECTION_COMPLETE:
- case hci::SubeventCode::ENHANCED_CONNECTION_COMPLETE:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 4, .address_pos = 7};
- break;
-
- case hci::SubeventCode::CONNECTION_UPDATE_COMPLETE:
- case hci::SubeventCode::READ_REMOTE_FEATURES_COMPLETE:
- case hci::SubeventCode::PHY_UPDATE_COMPLETE:
- case hci::SubeventCode::CTE_REQUEST_FAILED:
- case hci::SubeventCode::TRANSMIT_POWER_REPORTING:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 4, .address_pos = 0};
- break;
-
- case hci::SubeventCode::LONG_TERM_KEY_REQUEST:
- case hci::SubeventCode::REMOTE_CONNECTION_PARAMETER_REQUEST:
- case hci::SubeventCode::DATA_LENGTH_CHANGE:
- case hci::SubeventCode::CHANNEL_SELECTION_ALGORITHM:
- case hci::SubeventCode::CONNECTION_IQ_REPORT:
- case hci::SubeventCode::PATH_LOSS_THRESHOLD:
- classification = {.activity = Activity::CONNECT, .connection_handle_pos = 3, .address_pos = 0};
- break;
-
- case hci::SubeventCode::READ_LOCAL_P256_PUBLIC_KEY_COMPLETE:
- case hci::SubeventCode::GENERATE_DHKEY_COMPLETE:
- classification = {.activity = Activity::CONTROL, .connection_handle_pos = 0, .address_pos = 0};
- break;
-
- case hci::SubeventCode::PERIODIC_ADVERTISING_SYNC_ESTABLISHED:
- case hci::SubeventCode::PERIODIC_ADVERTISING_REPORT:
- case hci::SubeventCode::PERIODIC_ADVERTISING_SYNC_LOST:
- case hci::SubeventCode::ADVERTISING_SET_TERMINATED:
- classification = {.activity = Activity::ADVERTISE, .connection_handle_pos = 0, .address_pos = 0};
- break;
-
- case hci::SubeventCode::SCAN_TIMEOUT:
- case hci::SubeventCode::BIG_INFO_ADVERTISING_REPORT:
- case hci::SubeventCode::CONNECTIONLESS_IQ_REPORT:
- case hci::SubeventCode::CREATE_BIG_COMPLETE:
- case hci::SubeventCode::TERMINATE_BIG_COMPLETE:
- case hci::SubeventCode::BIG_SYNC_ESTABLISHED:
- case hci::SubeventCode::BIG_SYNC_LOST:
- case hci::SubeventCode::REQUEST_PEER_SCA_COMPLETE:
- classification = {.activity = Activity::SCAN, .connection_handle_pos = 0, .address_pos = 0};
- break;
-
- case hci::SubeventCode::SCAN_REQUEST_RECEIVED:
- classification = {.activity = Activity::ADVERTISE, .connection_handle_pos = 0, .address_pos = 5};
- break;
-
- case hci::SubeventCode::PERIODIC_ADVERTISING_SYNC_TRANSFER_RECEIVED:
- case hci::SubeventCode::CIS_ESTABLISHED:
- case hci::SubeventCode::CIS_REQUEST:
- classification = {.activity = Activity::SCAN, .connection_handle_pos = 4, .address_pos = 0};
- break;
-
- default:
- classification = {.activity = Activity::UNKNOWN, .connection_handle_pos = 0, .address_pos = 0};
- }
- return classification;
-}
-
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/btaa/linux_generic/hci_processor.cc b/gd/btaa/linux_generic/hci_processor.cc
deleted file mode 100644
index 60c5969bc..000000000
--- a/gd/btaa/linux_generic/hci_processor.cc
+++ /dev/null
@@ -1,268 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "btaa/hci_processor.h"
-
-#include "os/log.h"
-
-namespace bluetooth {
-namespace activity_attribution {
-
-void DeviceParser::match_handle_with_address(uint16_t connection_handle, hci::Address& address) {
- if (connection_handle && !address.IsEmpty()) {
- connection_lookup_table_[connection_handle] = address;
- } else if (connection_handle) {
- if (connection_lookup_table_.find(connection_handle) != connection_lookup_table_.end()) {
- address = connection_lookup_table_[connection_handle];
- }
- }
-}
-
-void HciProcessor::process_le_event(
- std::vector<BtaaHciPacket>& btaa_hci_packets, int16_t byte_count, hci::EventView& event) {
- uint16_t connection_handle_value = 0;
- hci::Address address_value;
-
- auto le_packet_view = hci::LeMetaEventView::Create(event);
- if (!le_packet_view.IsValid()) {
- return;
- }
-
- auto subevent_code = le_packet_view.GetSubeventCode();
- auto le_event_info = lookup_le_event(subevent_code);
-
- if (le_event_info.activity != Activity::UNKNOWN) {
- // lookup_le_event returns all simple classic event which does not require additional processing.
- if (le_event_info.connection_handle_pos) {
- auto connection_handle_it = event.begin() + le_event_info.connection_handle_pos;
- connection_handle_value = connection_handle_it.extract<uint16_t>();
- }
- if (le_event_info.address_pos) {
- auto address_value_it = event.begin() + le_event_info.address_pos;
- address_value = address_value_it.extract<hci::Address>();
- }
- device_parser_.match_handle_with_address(connection_handle_value, address_value);
- btaa_hci_packets.push_back(BtaaHciPacket(le_event_info.activity, address_value, byte_count));
- }
-}
-
-void HciProcessor::process_special_event(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- hci::EventCode event_code,
- uint16_t byte_count,
- hci::EventView& event) {
- uint16_t avg_byte_count;
- hci::Address address_value;
-
- switch (event_code) {
- case hci::EventCode::INQUIRY_RESULT:
- case hci::EventCode::INQUIRY_RESULT_WITH_RSSI: {
- auto packet_view = hci::InquiryResultView::Create(event);
- if (!packet_view.IsValid()) {
- return;
- }
- auto inquiry_results = packet_view.GetInquiryResults();
- avg_byte_count = byte_count / inquiry_results.size();
- for (auto& inquiry_result : inquiry_results) {
- btaa_hci_packets.push_back(BtaaHciPacket(Activity::SCAN, inquiry_result.bd_addr_, avg_byte_count));
- }
- } break;
-
- case hci::EventCode::NUMBER_OF_COMPLETED_PACKETS: {
- auto packet_view = hci::NumberOfCompletedPacketsView::Create(event);
- if (!packet_view.IsValid()) {
- return;
- }
- auto completed_packets = packet_view.GetCompletedPackets();
- avg_byte_count = byte_count / completed_packets.size();
- for (auto& completed_packet : completed_packets) {
- device_parser_.match_handle_with_address(completed_packet.connection_handle_, address_value);
- btaa_hci_packets.push_back(BtaaHciPacket(Activity::CONNECT, address_value, avg_byte_count));
- }
- } break;
-
- case hci::EventCode::RETURN_LINK_KEYS: {
- auto packet_view = hci::ReturnLinkKeysView::Create(event);
- if (!packet_view.IsValid()) {
- return;
- }
- auto keys_and_addresses = packet_view.GetKeys();
- avg_byte_count = byte_count / keys_and_addresses.size();
- for (auto& key_and_address : keys_and_addresses) {
- btaa_hci_packets.push_back(BtaaHciPacket(Activity::CONNECT, key_and_address.address_, avg_byte_count));
- }
- } break;
-
- default: {
- btaa_hci_packets.push_back(BtaaHciPacket(Activity::UNKNOWN, address_value, byte_count));
- } break;
- }
-}
-
-void HciProcessor::process_command(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- packet::PacketView<packet::kLittleEndian>& packet_view,
- uint16_t byte_count) {
- hci::CommandView command = hci::CommandView::Create(packet_view);
- if (!command.IsValid()) {
- return;
- }
-
- uint16_t connection_handle_value = 0;
- hci::Address address_value;
- auto opcode = command.GetOpCode();
- auto cmd_info = lookup_cmd(opcode);
-
- if (cmd_info.connection_handle_pos) {
- auto connection_handle_it = command.begin() + cmd_info.connection_handle_pos;
- connection_handle_value = connection_handle_it.extract<uint16_t>();
- }
- if (cmd_info.address_pos) {
- auto address_value_it = command.begin() + cmd_info.address_pos;
- address_value = address_value_it.extract<hci::Address>();
- }
- device_parser_.match_handle_with_address(connection_handle_value, address_value);
- pending_command_.btaa_hci_packet = BtaaHciPacket(cmd_info.activity, address_value, byte_count);
-
- pending_command_.opcode = opcode;
-}
-
-void HciProcessor::process_event(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- packet::PacketView<packet::kLittleEndian>& packet_view,
- uint16_t byte_count) {
- hci::EventView event = hci::EventView::Create(packet_view);
- if (!event.IsValid()) {
- return;
- }
-
- uint16_t connection_handle_value = 0;
- hci::Address address_value;
- auto event_code = event.GetEventCode();
- auto event_info = lookup_event(event_code);
-
- if (event_info.activity != Activity::UNKNOWN) {
- // lookup_event returns all simple classic event which does not require additional processing.
- if (event_info.connection_handle_pos) {
- auto connection_handle_it = event.begin() + event_info.connection_handle_pos;
- connection_handle_value = connection_handle_it.extract<uint16_t>();
- }
- if (event_info.address_pos) {
- auto address_value_it = event.begin() + event_info.address_pos;
- address_value = address_value_it.extract<hci::Address>();
- }
- device_parser_.match_handle_with_address(connection_handle_value, address_value);
- btaa_hci_packets.push_back(BtaaHciPacket(event_info.activity, address_value, byte_count));
- } else {
- // The event requires additional processing.
- switch (event_code) {
- case hci::EventCode::COMMAND_COMPLETE: {
- auto packet_view = hci::CommandCompleteView::Create(event);
- if (packet_view.IsValid() && packet_view.GetCommandOpCode() == pending_command_.opcode) {
- pending_command_.btaa_hci_packet.byte_count += byte_count;
- btaa_hci_packets.push_back(std::move(pending_command_.btaa_hci_packet));
- } else {
- btaa_hci_packets.push_back(BtaaHciPacket(Activity::UNKNOWN, address_value, byte_count));
- }
- } break;
- case hci::EventCode::COMMAND_STATUS: {
- auto packet_view = hci::CommandStatusView::Create(event);
- if (packet_view.IsValid() && packet_view.GetCommandOpCode() == pending_command_.opcode) {
- pending_command_.btaa_hci_packet.byte_count += byte_count;
- btaa_hci_packets.push_back(std::move(pending_command_.btaa_hci_packet));
- } else {
- btaa_hci_packets.push_back(BtaaHciPacket(Activity::UNKNOWN, address_value, byte_count));
- }
- break;
- }
- case hci::EventCode::LE_META_EVENT:
- process_le_event(btaa_hci_packets, byte_count, event);
- break;
- case hci::EventCode::VENDOR_SPECIFIC:
- btaa_hci_packets.push_back(BtaaHciPacket(Activity::VENDOR, address_value, byte_count));
- break;
- default:
- process_special_event(btaa_hci_packets, event_code, byte_count, event);
- break;
- }
- }
-}
-
-void HciProcessor::process_acl(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- packet::PacketView<packet::kLittleEndian>& packet_view,
- uint16_t byte_count) {
- hci::AclView acl = hci::AclView::Create(packet_view);
- auto connection_handle = acl.begin();
- // Connection handle is extracted from the 12 least significant bit.
- uint16_t connection_handle_value = connection_handle.extract<uint16_t>() & 0xfff;
- hci::Address address_value;
- device_parser_.match_handle_with_address(connection_handle_value, address_value);
- btaa_hci_packets.push_back(BtaaHciPacket(Activity::ACL, address_value, byte_count));
-}
-
-void HciProcessor::process_sco(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- packet::PacketView<packet::kLittleEndian>& packet_view,
- uint16_t byte_count) {
- hci::ScoView sco = hci::ScoView::Create(packet_view);
- auto connection_handle = sco.begin();
- // Connection handle is extracted from the 12 least significant bit.
- uint16_t connection_handle_value = connection_handle.extract<uint16_t>() & 0xfff;
- hci::Address address_value;
- device_parser_.match_handle_with_address(connection_handle_value, address_value);
- btaa_hci_packets.push_back(BtaaHciPacket(Activity::HFP, address_value, byte_count));
-}
-
-void HciProcessor::process_iso(
- std::vector<BtaaHciPacket>& btaa_hci_packets,
- packet::PacketView<packet::kLittleEndian>& packet_view,
- uint16_t byte_count) {
- hci::IsoView iso = hci::IsoView::Create(packet_view);
- auto connection_handle = iso.begin();
- // Connection handle is extracted from the 12 least significant bit.
- uint16_t connection_handle_value = connection_handle.extract<uint16_t>() & 0xfff;
- hci::Address address_value;
- device_parser_.match_handle_with_address(connection_handle_value, address_value);
- btaa_hci_packets.push_back(BtaaHciPacket(Activity::ISO, address_value, byte_count));
-}
-
-std::vector<BtaaHciPacket> HciProcessor::OnHciPacket(
- hal::HciPacket packet, hal::SnoopLogger::PacketType type, uint16_t length) {
- std::vector<BtaaHciPacket> btaa_hci_packets;
- auto packet_view = packet::PacketView<packet::kLittleEndian>(std::make_shared<std::vector<uint8_t>>(packet));
- switch (type) {
- case hal::SnoopLogger::PacketType::CMD:
- process_command(btaa_hci_packets, packet_view, length);
- break;
- case hal::SnoopLogger::PacketType::EVT:
- process_event(btaa_hci_packets, packet_view, length);
- break;
- case hal::SnoopLogger::PacketType::ACL:
- process_acl(btaa_hci_packets, packet_view, length);
- break;
- case hal::SnoopLogger::PacketType::SCO:
- process_sco(btaa_hci_packets, packet_view, length);
- break;
- case hal::SnoopLogger::PacketType::ISO:
- process_iso(btaa_hci_packets, packet_view, length);
- break;
- }
- return btaa_hci_packets;
-}
-
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/btaa/linux_generic/wakelock_processor.cc b/gd/btaa/linux_generic/wakelock_processor.cc
deleted file mode 100644
index bd3b3edc8..000000000
--- a/gd/btaa/linux_generic/wakelock_processor.cc
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "btaa/wakelock_processor.h"
-
-#include "os/log.h"
-
-namespace bluetooth {
-namespace activity_attribution {
-
-static const int kWakelockMaxDurationMs(10000);
-
-WakelockProcessor::WakelockProcessor() {
- wakelock_net_count_ = 0;
- wakelock_acquired_time_ = {};
-}
-
-uint32_t WakelockProcessor::OnWakelockReleased() {
- auto cur_time = std::chrono::system_clock::now();
- uint32_t wakelock_duration_ms = 0;
-
- if (wakelock_net_count_ == 0) {
- LOG_INFO("Release a never acquired wakelock, ignored.");
- } else {
- wakelock_net_count_--;
- if (wakelock_net_count_ == 0) {
- wakelock_duration_ms = static_cast<uint32_t>(
- std::chrono::duration_cast<std::chrono::milliseconds>(cur_time - wakelock_acquired_time_).count());
- wakelock_acquired_time_ = {};
- }
- }
-
- return wakelock_duration_ms;
-}
-
-void WakelockProcessor::OnWakelockAcquired() {
- auto cur_time = std::chrono::system_clock::now();
-
- if (wakelock_net_count_ == 0) {
- if (wakelock_acquired_time_.time_since_epoch().count()) {
- LOG_INFO("Previous wakelock acquired time is not consumed, dropped.");
- }
- wakelock_acquired_time_ = cur_time;
- } else if (cur_time - wakelock_acquired_time_ > std::chrono::milliseconds(kWakelockMaxDurationMs)) {
- LOG_INFO("Wakelock held for too long, likely we missed a release notification. Resetting wakelock stats.");
- wakelock_net_count_ = 0;
- wakelock_acquired_time_ = cur_time;
- }
-
- wakelock_net_count_++;
-}
-
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/btaa/wakelock_processor.h b/gd/btaa/wakelock_processor.h
deleted file mode 100644
index 8b700d2d8..000000000
--- a/gd/btaa/wakelock_processor.h
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <chrono>
-#include <cstdint>
-
-namespace bluetooth {
-namespace activity_attribution {
-
-class WakelockProcessor {
- public:
- WakelockProcessor();
-
- uint32_t OnWakelockReleased();
- void OnWakelockAcquired();
-
- private:
- std::chrono::time_point<std::chrono::system_clock> wakelock_acquired_time_;
- uint8_t wakelock_net_count_;
-};
-
-} // namespace activity_attribution
-} // namespace bluetooth
diff --git a/gd/cert/devices_config.json b/gd/cert/android_devices_config.json
index 8bd257a19..7123c650d 100644
--- a/gd/cert/devices_config.json
+++ b/gd/cert/android_devices_config.json
@@ -10,9 +10,8 @@
"grpc_port": "8898",
"grpc_root_server_port": "8896",
"signal_port": "8894",
- "label": "cert",
+ "label": "cert_stack",
"serial_number": "CERT",
- "name": "Cert Device",
"cmd":
[
"adb",
@@ -22,9 +21,7 @@
"/system/bin/bluetooth_stack_with_facade",
"--grpc-port=$(grpc_port)",
"--root-server-port=$(grpc_root_server_port)",
- "--btsnoop=/data/misc/bluetooth/logs/btsnoop_hci.log",
- "--btsnooz=/data/misc/bluetooth/logs/btsnooz_hci.log",
- "--btconfig=/data/misc/bluedroid/bt_config.conf",
+ "--btsnoop=data/misc/bluetooth/logs/btsnoop_hci.log",
"--signal-port=$(signal_port)"
]
},
@@ -32,9 +29,8 @@
"grpc_port": "8899",
"grpc_root_server_port": "8897",
"signal_port": "8895",
- "label": "dut",
+ "label": "stack_under_test",
"serial_number": "DUT",
- "name": "DUT Device",
"cmd":
[
"adb",
@@ -44,9 +40,7 @@
"/system/bin/bluetooth_stack_with_facade",
"--grpc-port=$(grpc_port)",
"--root-server-port=$(grpc_root_server_port)",
- "--btsnoop=/data/misc/bluetooth/logs/btsnoop_hci.log",
- "--btsnooz=/data/misc/bluetooth/logs/btsnooz_hci.log",
- "--btconfig=/data/misc/bluedroid/bt_config.conf",
+ "--btsnoop=data/misc/bluetooth/logs/btsnoop_hci.log",
"--signal-port=$(signal_port)"
]
}
diff --git a/gd/cert/async_subprocess_logger.py b/gd/cert/async_subprocess_logger.py
deleted file mode 100644
index 00a5d6909..000000000
--- a/gd/cert/async_subprocess_logger.py
+++ /dev/null
@@ -1,90 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from contextlib import ExitStack
-import concurrent.futures
-import logging
-import re
-import subprocess
-from cert.os_utils import TerminalColor
-
-
-class AsyncSubprocessLogger:
- """
- An asynchronous logger for subprocesses.Popen object's STDOUT
-
- Contains threading functionality that allows asynchronous handling of lines
- from STDOUT from subprocess.Popen
- """
- WAIT_TIMEOUT_SECONDS = 10
- PROCESS_TAG_MIN_WIDTH = 24
-
- def __init__(self,
- process: subprocess.Popen,
- log_file_paths,
- log_to_stdout=False,
- tag=None,
- color: TerminalColor = None):
- """
- :param process: a subprocess.Popen object with STDOUT
- :param log_file_paths: list of log files to redirect log to
- :param log_to_stdout: whether to dump logs to stdout in the format of
- "[tag] logline"
- :param tag: tag to be used in above format
- :param color: when dumping to stdout, what color to use for tag
- """
- if not process:
- raise ValueError("process cannot be None")
- if not process.stdout:
- raise ValueError("process.stdout cannot be None")
- if log_to_stdout:
- if not tag or type(tag) is not str:
- raise ValueError("When logging to stdout, log tag must be set")
- self.log_file_paths = log_file_paths
- self.log_to_stdout = log_to_stdout
- self.tag = tag
- self.color = color
- self.process = process
- self.executor = concurrent.futures.ThreadPoolExecutor(max_workers=1)
- self.future = self.executor.submit(self.__logging_loop)
-
- def stop(self):
- """
- Stop this logger and this object can no longer be used after this call
- """
- try:
- result = self.future.result(timeout=self.WAIT_TIMEOUT_SECONDS)
- if result:
- logging.error("logging thread %s produced an error when executing: %s" % (self.tag, str(result)))
- except concurrent.futures.TimeoutError:
- logging.error("logging thread %s failed to finish after %d seconds" % (self.tag, self.WAIT_TIMEOUT_SECONDS))
- self.executor.shutdown(wait=False)
-
- def __logging_loop(self):
- if self.color:
- loggableTag = "[%s%s%s]" % (self.color, self.tag, TerminalColor.END)
- else:
- loggableTag = "[%s]" % self.tag
- tagLength = len(re.sub('[^\w\s]', '', loggableTag))
- if tagLength < self.PROCESS_TAG_MIN_WIDTH:
- loggableTag += " " * (self.PROCESS_TAG_MIN_WIDTH - tagLength)
- with ExitStack() as stack:
- log_files = [stack.enter_context(open(file_path, 'w')) for file_path in self.log_file_paths]
- for line in self.process.stdout:
- for log_file in log_files:
- log_file.write(line)
- if self.log_to_stdout:
- print("{}{}".format(loggableTag, line.strip()))
diff --git a/gd/cert/behavior.py b/gd/cert/behavior.py
deleted file mode 100644
index 8403dd6f2..000000000
--- a/gd/cert/behavior.py
+++ /dev/null
@@ -1,173 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from abc import ABC, abstractmethod
-from datetime import datetime, timedelta
-from mobly import signals
-from threading import Condition
-
-from cert.event_stream import static_remaining_time_delta
-from cert.truth import assertThat
-
-
-class IHasBehaviors(ABC):
-
- @abstractmethod
- def get_behaviors(self):
- pass
-
-
-def anything():
- return lambda obj: True
-
-
-def when(has_behaviors):
- assertThat(isinstance(has_behaviors, IHasBehaviors)).isTrue()
- return has_behaviors.get_behaviors()
-
-
-def IGNORE_UNHANDLED(obj):
- pass
-
-
-class SingleArgumentBehavior(object):
-
- def __init__(self, reply_stage_factory):
- self._reply_stage_factory = reply_stage_factory
- self._instances = []
- self._invoked_obj = []
- self._invoked_condition = Condition()
- self.set_default_to_crash()
-
- def begin(self, matcher):
- return PersistenceStage(self, matcher, self._reply_stage_factory)
-
- def append(self, behavior_instance):
- self._instances.append(behavior_instance)
-
- def set_default(self, fn):
- assertThat(fn).isNotNone()
- self._default_fn = fn
-
- def set_default_to_crash(self):
- self._default_fn = None
-
- def set_default_to_ignore(self):
- self._default_fn = IGNORE_UNHANDLED
-
- def run(self, obj):
- for instance in self._instances:
- if instance.try_run(obj):
- self.__obj_invoked(obj)
- return
- if self._default_fn is not None:
- # IGNORE_UNHANDLED is also a default fn
- self._default_fn(obj)
- self.__obj_invoked(obj)
- else:
- raise signals.TestFailure(
- "%s: behavior for %s went unhandled" % (self._reply_stage_factory().__class__.__name__, obj),
- extras=None)
-
- def __obj_invoked(self, obj):
- self._invoked_condition.acquire()
- self._invoked_obj.append(obj)
- self._invoked_condition.notify()
- self._invoked_condition.release()
-
- def wait_until_invoked(self, matcher, times, timeout):
- end_time = datetime.now() + timeout
- invoked_times = 0
- while datetime.now() < end_time and invoked_times < times:
- remaining = static_remaining_time_delta(end_time)
- invoked_times = sum((matcher(i) for i in self._invoked_obj))
- self._invoked_condition.acquire()
- self._invoked_condition.wait(remaining.total_seconds())
- self._invoked_condition.release()
- return invoked_times == times
-
-
-class PersistenceStage(object):
-
- def __init__(self, behavior, matcher, reply_stage_factory):
- self._behavior = behavior
- self._matcher = matcher
- self._reply_stage_factory = reply_stage_factory
-
- def then(self, times=1):
- reply_stage = self._reply_stage_factory()
- reply_stage.init(self._behavior, self._matcher, times)
- return reply_stage
-
- def always(self):
- return self.then(times=-1)
-
-
-class ReplyStage(object):
-
- def init(self, behavior, matcher, persistence):
- self._behavior = behavior
- self._matcher = matcher
- self._persistence = persistence
-
- def _commit(self, fn):
- self._behavior.append(BehaviorInstance(self._matcher, self._persistence, fn))
-
-
-class BehaviorInstance(object):
-
- def __init__(self, matcher, persistence, fn):
- self._matcher = matcher
- self._persistence = persistence
- self._fn = fn
- self._called_count = 0
-
- def try_run(self, obj):
- if not self._matcher(obj):
- return False
- if self._persistence >= 0:
- if self._called_count >= self._persistence:
- return False
- self._called_count += 1
- self._fn(obj)
- return True
-
-
-class BoundVerificationStage(object):
-
- def __init__(self, behavior, matcher, timeout):
- self._behavior = behavior
- self._matcher = matcher
- self._timeout = timeout
-
- def times(self, times=1):
- return self._behavior.wait_until_invoked(self._matcher, times, self._timeout)
-
-
-class WaitForBehaviorSubject(object):
-
- def __init__(self, behaviors, timeout):
- self._behaviors = behaviors
- self._timeout = timeout
-
- def __getattr__(self, item):
- behavior = getattr(self._behaviors, item + "_behavior")
- t = self._timeout
- return lambda matcher: BoundVerificationStage(behavior, matcher, t)
-
-
-def wait_until(i_has_behaviors, timeout=timedelta(seconds=3)):
- return WaitForBehaviorSubject(i_has_behaviors.get_behaviors(), timeout)
diff --git a/gd/cert/bluetooth_packets_python3_setup.py b/gd/cert/bluetooth_packets_python3_setup.py
index 0eac18b75..c9e25c216 100644
--- a/gd/cert/bluetooth_packets_python3_setup.py
+++ b/gd/cert/bluetooth_packets_python3_setup.py
@@ -29,12 +29,16 @@ import glob
from setuptools import setup, Extension
ANDROID_BUILD_TOP = os.getenv("ANDROID_BUILD_TOP")
-PYBIND11_INCLUDE_DIR = os.path.join(ANDROID_BUILD_TOP, "external/python/pybind11/include")
+PYBIND11_INCLUDE_DIR = os.path.join(ANDROID_BUILD_TOP,
+ "external/python/pybind11/include")
GD_DIR = os.path.join(ANDROID_BUILD_TOP, "system/bt/gd")
-BT_PACKETS_GEN_DIR = os.path.join(ANDROID_BUILD_TOP,
- "out/soong/.intermediates/system/bt/gd/BluetoothGeneratedPackets_h/gen")
-BT_PACKETS_PY3_GEN_DIR = os.path.join(ANDROID_BUILD_TOP,
- "out/soong/.intermediates/system/bt/gd/BluetoothGeneratedPackets_python3_cc/gen")
+BT_PACKETS_GEN_DIR = os.path.join(
+ ANDROID_BUILD_TOP,
+ "out/soong/.intermediates/system/bt/gd/BluetoothGeneratedPackets_h/gen")
+BT_PACKETS_PY3_GEN_DIR = os.path.join(
+ ANDROID_BUILD_TOP,
+ "out/soong/.intermediates/system/bt/gd/BluetoothGeneratedPackets_python3_cc/gen"
+)
BT_PACKETS_BASE_SRCS = [
os.path.join(GD_DIR, "l2cap/fcs.cc"),
@@ -57,7 +61,9 @@ BT_PACKETS_PY3_SRCs = \
bluetooth_packets_python3_module = Extension(
'bluetooth_packets_python3',
sources=BT_PACKETS_BASE_SRCS + BT_PACKETS_PY3_SRCs,
- include_dirs=[GD_DIR, BT_PACKETS_GEN_DIR, BT_PACKETS_PY3_GEN_DIR, PYBIND11_INCLUDE_DIR],
+ include_dirs=[
+ GD_DIR, BT_PACKETS_GEN_DIR, BT_PACKETS_PY3_GEN_DIR, PYBIND11_INCLUDE_DIR
+ ],
extra_compile_args=['-std=c++17'])
setup(
diff --git a/gd/cert/capture.py b/gd/cert/capture.py
deleted file mode 100644
index e37dc7dbb..000000000
--- a/gd/cert/capture.py
+++ /dev/null
@@ -1,41 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-
-class Capture(object):
- """
- Wrap a match function and use in its place, to capture the value
- that matched. Specify an optional |capture_fn| to transform the
- captured value.
- """
-
- def __init__(self, match_fn, capture_fn=None):
- self._match_fn = match_fn
- self._capture_fn = capture_fn
- self._value = None
-
- def __call__(self, obj):
- if self._match_fn(obj) != True:
- return False
-
- if self._capture_fn is not None:
- self._value = self._capture_fn(obj)
- else:
- self._value = obj
- return True
-
- def get(self):
- return self._value
diff --git a/gd/cert/captures.py b/gd/cert/captures.py
deleted file mode 100644
index cda5b68fd..000000000
--- a/gd/cert/captures.py
+++ /dev/null
@@ -1,187 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import bluetooth_packets_python3 as bt_packets
-from bluetooth_packets_python3 import hci_packets
-from bluetooth_packets_python3 import l2cap_packets
-from bluetooth_packets_python3.l2cap_packets import CommandCode, LeCommandCode
-from cert.capture import Capture
-from cert.matchers import HciMatchers
-from cert.matchers import L2capMatchers
-from cert.matchers import SecurityMatchers
-from security.facade_pb2 import UiMsgType
-
-
-class HalCaptures(object):
-
- @staticmethod
- def ReadBdAddrCompleteCapture():
- return Capture(
- lambda packet: packet.payload[0:5] == b'\x0e\x0a\x01\x09\x10', lambda packet: hci_packets.ReadBdAddrCompleteView(
- hci_packets.CommandCompleteView(
- hci_packets.EventView(bt_packets.PacketViewLittleEndian(list(packet.payload))))))
-
- @staticmethod
- def ConnectionRequestCapture():
- return Capture(
- lambda packet: packet.payload[0:2] == b'\x04\x0a', lambda packet: hci_packets.ConnectionRequestView(
- hci_packets.EventView(bt_packets.PacketViewLittleEndian(list(packet.payload)))))
-
- @staticmethod
- def ConnectionCompleteCapture():
- return Capture(
- lambda packet: packet.payload[0:3] == b'\x03\x0b\x00', lambda packet: hci_packets.ConnectionCompleteView(
- hci_packets.EventView(bt_packets.PacketViewLittleEndian(list(packet.payload)))))
-
- @staticmethod
- def DisconnectionCompleteCapture():
- return Capture(
- lambda packet: packet.payload[0:2] == b'\x05\x04', lambda packet: hci_packets.DisconnectionCompleteView(
- hci_packets.EventView(bt_packets.PacketViewLittleEndian(list(packet.payload)))))
-
- @staticmethod
- def LeConnectionCompleteCapture():
- return Capture(
- lambda packet: packet.payload[0] == 0x3e and (packet.payload[2] == 0x01 or packet.payload[2] == 0x0a),
- lambda packet: hci_packets.LeConnectionCompleteView(
- hci_packets.LeMetaEventView(
- hci_packets.EventView(bt_packets.PacketViewLittleEndian(list(packet.payload))))))
-
-
-class HciCaptures(object):
-
- @staticmethod
- def ReadLocalOobDataCompleteCapture():
- return Capture(
- HciMatchers.CommandComplete(hci_packets.OpCode.READ_LOCAL_OOB_DATA),
- lambda packet: HciMatchers.ExtractMatchingCommandComplete(packet.payload, hci_packets.OpCode.READ_LOCAL_OOB_DATA)
- )
-
- @staticmethod
- def ReadLocalOobExtendedDataCompleteCapture():
- return Capture(
- HciMatchers.CommandComplete(hci_packets.OpCode.READ_LOCAL_OOB_EXTENDED_DATA),
- lambda packet: HciMatchers.ExtractMatchingCommandComplete(packet.payload, hci_packets.OpCode.READ_LOCAL_OOB_EXTENDED_DATA)
- )
-
- @staticmethod
- def ReadBdAddrCompleteCapture():
- return Capture(
- HciMatchers.CommandComplete(hci_packets.OpCode.READ_BD_ADDR),
- lambda packet: hci_packets.ReadBdAddrCompleteView(HciMatchers.ExtractMatchingCommandComplete(packet.payload, hci_packets.OpCode.READ_BD_ADDR)))
-
- @staticmethod
- def ConnectionRequestCapture():
- return Capture(
- HciMatchers.EventWithCode(hci_packets.EventCode.CONNECTION_REQUEST),
- lambda packet: hci_packets.ConnectionRequestView(
- HciMatchers.ExtractEventWithCode(packet.payload, hci_packets.EventCode.CONNECTION_REQUEST)))
-
- @staticmethod
- def ConnectionCompleteCapture():
- return Capture(
- HciMatchers.EventWithCode(hci_packets.EventCode.CONNECTION_COMPLETE),
- lambda packet: hci_packets.ConnectionCompleteView(
- HciMatchers.ExtractEventWithCode(packet.payload, hci_packets.EventCode.CONNECTION_COMPLETE)))
-
- @staticmethod
- def DisconnectionCompleteCapture():
- return Capture(
- HciMatchers.EventWithCode(hci_packets.EventCode.DISCONNECTION_COMPLETE),
- lambda packet: hci_packets.DisconnectionCompleteView(
- HciMatchers.ExtractEventWithCode(packet.payload, hci_packets.EventCode.DISCONNECTION_COMPLETE)))
-
- @staticmethod
- def LeConnectionCompleteCapture():
- return Capture(HciMatchers.LeConnectionComplete(),
- lambda packet: HciMatchers.ExtractLeConnectionComplete(packet.payload))
-
- @staticmethod
- def SimplePairingCompleteCapture():
- return Capture(HciMatchers.EventWithCode(hci_packets.EventCode.SIMPLE_PAIRING_COMPLETE),
- lambda packet: hci_packets.SimplePairingCompleteView(
- HciMatchers.ExtractEventWithCode(packet.payload, hci_packets.EventCode.SIMPLE_PAIRING_COMPLETE)))
-
-
-class L2capCaptures(object):
-
- @staticmethod
- def ConnectionRequest(psm):
- return Capture(L2capMatchers.ConnectionRequest(psm), L2capCaptures._extract_connection_request)
-
- @staticmethod
- def _extract_connection_request(packet):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.CONNECTION_REQUEST)
- return l2cap_packets.ConnectionRequestView(frame)
-
- @staticmethod
- def ConnectionResponse(scid):
- return Capture(L2capMatchers.ConnectionResponse(scid), L2capCaptures._extract_connection_response)
-
- @staticmethod
- def _extract_connection_response(packet):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.CONNECTION_RESPONSE)
- return l2cap_packets.ConnectionResponseView(frame)
-
- @staticmethod
- def ConfigurationRequest(cid=None):
- return Capture(L2capMatchers.ConfigurationRequest(cid), L2capCaptures._extract_configuration_request)
-
- @staticmethod
- def _extract_configuration_request(packet):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.CONFIGURATION_REQUEST)
- return l2cap_packets.ConfigurationRequestView(frame)
-
- @staticmethod
- def CreditBasedConnectionRequest(psm):
- return Capture(
- L2capMatchers.CreditBasedConnectionRequest(psm), L2capCaptures._extract_credit_based_connection_request)
-
- @staticmethod
- def _extract_credit_based_connection_request(packet):
- frame = L2capMatchers.le_control_frame_with_code(packet, LeCommandCode.LE_CREDIT_BASED_CONNECTION_REQUEST)
- return l2cap_packets.LeCreditBasedConnectionRequestView(frame)
-
- @staticmethod
- def CreditBasedConnectionResponse():
- return Capture(L2capMatchers.CreditBasedConnectionResponse(),
- L2capCaptures._extract_credit_based_connection_response)
-
- @staticmethod
- def _extract_credit_based_connection_response(packet):
- frame = L2capMatchers.le_control_frame_with_code(packet, LeCommandCode.LE_CREDIT_BASED_CONNECTION_RESPONSE)
- return l2cap_packets.LeCreditBasedConnectionResponseView(frame)
-
- @staticmethod
- def LinkSecurityInterfaceCallbackEvent(type):
- return Capture(L2capMatchers.LinkSecurityInterfaceCallbackEvent(type), L2capCaptures._extract_address)
-
- @staticmethod
- def _extract_address(packet):
- return packet.address
-
-
-class SecurityCaptures(object):
-
- @staticmethod
- def DisplayPasskey():
- return Capture(SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PASSKEY), SecurityCaptures._extract_passkey)
-
- @staticmethod
- def _extract_passkey(event):
- if event is None:
- return None
- return event.numeric_value
diff --git a/gd/cert/cert_self_test.py b/gd/cert/cert_self_test.py
index c24305e00..86edb4c2c 100644
--- a/gd/cert/cert_self_test.py
+++ b/gd/cert/cert_self_test.py
@@ -14,278 +14,219 @@
# See the License for the specific language governing permissions and
# limitations under the License.
-from datetime import datetime, timedelta
import logging
-from threading import Timer
import time
-import traceback
from mobly import asserts
+from datetime import datetime, timedelta
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
+from cert.event_callback_stream import EventCallbackStream
+from cert.event_asserts import EventAsserts
-from acts import signals
-from acts.base_test import BaseTestClass
-
+# Test packet nesting
from bluetooth_packets_python3 import hci_packets
from bluetooth_packets_python3 import l2cap_packets
-from cert.event_stream import EventStream, FilteringEventStream
-from cert.truth import assertThat
-from cert.metadata import metadata
-from cert.behavior import when, wait_until
-from cert.behavior import IHasBehaviors
-from cert.behavior import anything
-from cert.behavior import SingleArgumentBehavior
-from cert.behavior import ReplyStage
-from cert.cert_self_test_lib import *
-
-
-class CertSelfTest(BaseTestClass):
-
- def setup_test(self):
- return True
-
- def teardown_test(self):
- return True
-
- def test_assert_occurs_at_least_passes(self):
- test_assert_occurs_at_least_passes_core()
-
- def test_assert_occurs_passes(self):
- test_assert_occurs_passes_core()
-
- def test_assert_occurs_fails(self):
- test_assert_occurs_fails_core()
- def test_assert_occurs_at_most_passes(self):
- test_assert_occurs_at_most_passes_core()
-
- def test_assert_occurs_at_most_fails(self):
- test_assert_occurs_at_most_fails_core()
-
- def test_skip_a_test(self):
- test_skip_a_test_core()
-
- def test_nested_packets(self):
- test_nested_packets_core()
-
- def test_l2cap_config_options(self):
- test_l2cap_config_options_core()
- def test_assertThat_boolean_success(self):
- test_assertThat_boolean_success_core()
+class BogusProto:
- def test_assertThat_boolean_falseIsTrue(self):
- test_assertThat_boolean_falseIsTrue_core()
+ class BogusType:
- def test_assertThat_boolean_trueIsFalse(self):
- test_assertThat_boolean_trueIsFalse_core()
+ def __init__(self):
+ self.name = "BogusProto"
+ self.is_extension = False
+ self.cpp_type = False
- def test_assertThat_object_success(self):
- test_assertThat_object_success_core()
+ def type(self):
+ return 'BogusRpc'
- def test_assertThat_object_isEqualToFails(self):
- test_assertThat_object_isEqualToFails_core()
+ def label(self):
+ return "label"
- def test_assertThat_object_isNotEqualToFails(self):
- test_assertThat_object_isNotEqualToFails_core()
+ class BogusDescriptor:
- def test_assertThat_object_isNoneFails(self):
- test_assertThat_object_isNoneFails_core()
+ def __init__(self, name):
+ self.full_name = name
- def test_assertThat_object_isNotNoneFails(self):
- test_assertThat_object_isNotNoneFails_core()
+ def __init__(self, value):
+ self.value_ = value
+ self.DESCRIPTOR = BogusProto.BogusDescriptor(str(value))
- def test_assertThat_eventStream_emits_passes(self):
- test_assertThat_eventStream_emits_passes_core()
+ def __str__(self):
+ return "BogusRpc value = " + str(self.value_)
- def test_assertThat_eventStream_emits_then_passes(self):
- test_assertThat_eventStream_emits_then_passes_core()
+ def ListFields(self):
+ for field in [BogusProto.BogusType()]:
+ yield [field, self.value_]
- def test_assertThat_eventStream_emits_fails(self):
- test_assertThat_eventStream_emits_fails_core()
- def test_assertThat_eventStream_emits_then_fails(self):
- test_assertThat_eventStream_emits_then_fails_core()
+class FetchEvents:
- def test_assertThat_eventStream_emitsInOrder_passes(self):
- test_assertThat_eventStream_emitsInOrder_passes_core()
+ def __init__(self, events, delay_ms):
+ self.events_ = events
+ self.sleep_time_ = (delay_ms * 1.0) / 1000
+ self.index_ = 0
+ self.done_ = False
+ self.then_ = datetime.now()
- def test_assertThat_eventStream_emitsInAnyOrder_passes(self):
- test_assertThat_eventStream_emitsInAnyOrder_passes_core()
+ def __iter__(self):
+ for event in self.events_:
+ time.sleep(self.sleep_time_)
+ if self.done_:
+ return
+ logging.debug("yielding %d" % event)
+ yield BogusProto(event)
- def test_assertThat_eventStream_emitsInOrder_fails(self):
- test_assertThat_eventStream_emitsInOrder_fails_core()
+ def done(self):
+ return self.done_
- def test_assertThat_eventStream_emitsInAnyOrder_fails(self):
- test_assertThat_eventStream_emitsInAnyOrder_fails_core()
+ def cancel(self):
+ logging.debug("cancel")
+ self.done_ = True
+ return None
- def test_assertThat_emitsNone_passes(self):
- test_assertThat_emitsNone_passes_core()
- def test_assertThat_emitsNone_passes_after_1_second(self):
- test_assertThat_emitsNone_passes_after_1_second_core()
+class CertSelfTest(GdFacadeOnlyBaseTestClass):
- def test_assertThat_emitsNone_fails(self):
- test_assertThat_emitsNone_fails_core()
-
- def test_assertThat_emitsNone_zero_passes(self):
- test_assertThat_emitsNone_zero_passes_core()
-
- def test_assertThat_emitsNone_zero_passes_after_one_second(self):
- test_assertThat_emitsNone_zero_passes_after_one_second_core()
-
- def test_assertThat_emitsNone_zero_fails(self):
- test_assertThat_emitsNone_zero_fails_core()
+ def setup_test(self):
+ return True
- def test_filtering_event_stream_none_filter_function(self):
- test_filtering_event_stream_none_filter_function_core()
+ def teardown_test(self):
+ return True
- def test_metadata_empty(self):
+ def test_assert_none_passes(self):
+ with EventCallbackStream(FetchEvents(events=[],
+ delay_ms=50)) as event_stream:
+ event_asserts = EventAsserts(event_stream)
+ event_asserts.assert_none(timeout=timedelta(milliseconds=10))
- @metadata()
- def simple_pass_test(arg):
- pass
+ def test_assert_none_passes_after_one_second(self):
+ with EventCallbackStream(FetchEvents([1],
+ delay_ms=1500)) as event_stream:
+ event_asserts = EventAsserts(event_stream)
+ event_asserts.assert_none(timeout=timedelta(seconds=1.0))
+ def test_assert_none_fails(self):
try:
- simple_pass_test(1)
- except signals.TestFailure:
- pass
+ with EventCallbackStream(FetchEvents(events=[17],
+ delay_ms=50)) as event_stream:
+ event_asserts = EventAsserts(event_stream)
+ event_asserts.assert_none(timeout=timedelta(seconds=1))
except Exception as e:
- asserts.fail("@metadata() should only raise signals.TestFailure, "
- "but raised %s with msg %s instead" % (e.__class__.__name__, str(e)))
- else:
- asserts.fail("@metadata() should not work")
-
- def test_metadata_empty_no_function_call(self):
-
- @metadata
- def simple_pass_test(arg):
- pass
-
+ logging.debug(e)
+ return True # Failed as expected
+ return False
+
+ def test_assert_none_matching_passes(self):
+ with EventCallbackStream(FetchEvents(events=[1, 2, 3],
+ delay_ms=50)) as event_stream:
+ event_asserts = EventAsserts(event_stream)
+ event_asserts.assert_none_matching(
+ lambda data: data.value_ == 4, timeout=timedelta(seconds=0.15))
+
+ def test_assert_none_matching_passes_after_1_second(self):
+ with EventCallbackStream(
+ FetchEvents(events=[1, 2, 3, 4], delay_ms=400)) as event_stream:
+ event_asserts = EventAsserts(event_stream)
+ event_asserts.assert_none_matching(
+ lambda data: data.value_ == 4, timeout=timedelta(seconds=1))
+
+ def test_assert_none_matching_fails(self):
try:
- simple_pass_test(1)
- except signals.TestFailure:
- pass
+ with EventCallbackStream(
+ FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
+ event_asserts = EventAsserts(event_stream)
+ event_asserts.assert_none_matching(
+ lambda data: data.value_ == 2, timeout=timedelta(seconds=1))
except Exception as e:
- asserts.fail("@metadata should only raise signals.TestFailure, "
- "but raised %s with msg %s instead" % (e.__class__.__name__, str(e)))
- else:
- asserts.fail("@metadata should not work")
+ logging.debug(e)
+ return True # Failed as expected
+ return False
- def test_metadata_pts_missing_id(self):
+ def test_assert_occurs_at_least_passes(self):
+ with EventCallbackStream(
+ FetchEvents(events=[1, 2, 3, 1, 2, 3],
+ delay_ms=40)) as event_stream:
+ event_asserts = EventAsserts(event_stream)
+ event_asserts.assert_event_occurs(
+ lambda data: data.value_ == 1,
+ timeout=timedelta(milliseconds=300),
+ at_least_times=2)
- @metadata(pts_test_name="Hello world")
- def simple_pass_test(arg):
- pass
+ def test_assert_occurs_passes(self):
+ with EventCallbackStream(FetchEvents(events=[1, 2, 3],
+ delay_ms=50)) as event_stream:
+ event_asserts = EventAsserts(event_stream)
+ event_asserts.assert_event_occurs(
+ lambda data: data.value_ == 1, timeout=timedelta(seconds=1))
+ def test_assert_occurs_fails(self):
try:
- simple_pass_test(1)
- except signals.TestFailure:
- pass
+ with EventCallbackStream(
+ FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
+ event_asserts = EventAsserts(event_stream)
+ event_asserts.assert_event_occurs(
+ lambda data: data.value_ == 4, timeout=timedelta(seconds=1))
except Exception as e:
- asserts.fail("should only raise signals.TestFailure, "
- "but raised %s with msg %s instead" % (e.__class__.__name__, str(e)))
- else:
- asserts.fail("missing pts_test_id should not work")
+ logging.debug(e)
+ return True # Failed as expected
+ return False
- def test_metadata_pts_missing_name(self):
-
- @metadata(pts_test_id="A/B/C")
- def simple_pass_test(arg):
- pass
+ def test_assert_occurs_at_most_passes(self):
+ with EventCallbackStream(FetchEvents(events=[1, 2, 3, 4],
+ delay_ms=50)) as event_stream:
+ event_asserts = EventAsserts(event_stream)
+ event_asserts.assert_event_occurs_at_most(
+ lambda data: data.value_ < 4,
+ timeout=timedelta(seconds=1),
+ at_most_times=3)
+ def test_assert_occurs_at_most_fails(self):
try:
- simple_pass_test(1)
- except signals.TestFailure:
- pass
+ with EventCallbackStream(
+ FetchEvents(events=[1, 2, 3, 4],
+ delay_ms=50)) as event_stream:
+ event_asserts = EventAsserts(event_stream)
+ event_asserts.assert_event_occurs_at_most(
+ lambda data: data.value_ > 1,
+ timeout=timedelta(seconds=1),
+ at_most_times=2)
except Exception as e:
- asserts.fail("should only raise signals.TestFailure, "
- "but raised %s with msg %s instead" % (e.__class__.__name__, str(e)))
- else:
- asserts.fail("missing pts_test_name should not work")
-
- def test_metadata_pts_test_id_and_description(self):
-
- @metadata(pts_test_id="A/B/C", pts_test_name="Hello world")
- def simple_pass_test(arg):
- pass
-
- try:
- simple_pass_test(1)
- except signals.TestPass as e:
- asserts.assert_true("pts_test_id" in e.extras, msg=("pts_test_id not in extra: %s" % str(e.extras)))
- asserts.assert_equal(e.extras["pts_test_id"], "A/B/C")
- asserts.assert_true("pts_test_name" in e.extras, msg=("pts_test_name not in extra: %s" % str(e.extras)))
- asserts.assert_equal(e.extras["pts_test_name"], "Hello world")
- else:
- asserts.fail("Must throw an exception using @metadata decorator")
-
- def test_metadata_test_with_exception_stacktrace(self):
-
- @metadata(pts_test_id="A/B/C", pts_test_name="Hello world")
- def simple_fail_test(failure_argument):
- raise ValueError(failure_argument)
-
- try:
- simple_fail_test("BEEFBEEF")
- except signals.TestError as e:
- asserts.assert_true("pts_test_id" in e.extras, msg=("pts_test_id not in extra: %s" % str(e.extras)))
- asserts.assert_equal(e.extras["pts_test_id"], "A/B/C")
- asserts.assert_true("pts_test_name" in e.extras, msg=("pts_test_name not in extra: %s" % str(e.extras)))
- asserts.assert_equal(e.extras["pts_test_name"], "Hello world")
- trace_str = traceback.format_exc()
- asserts.assert_true(
- "raise ValueError(failure_argument)" in trace_str,
- msg="Failed test method not in error stack trace: %s" % trace_str)
- else:
- asserts.fail("Must throw an exception using @metadata decorator")
-
- def test_fluent_behavior_simple(self):
- test_fluent_behavior_simple_core()
+ logging.debug(e)
+ return True # Failed as expected
+ return False
- def test_fluent_behavior__then_single__captures_one(self):
- test_fluent_behavior__then_single__captures_one_core()
-
- def test_fluent_behavior__then_times__captures_all(self):
- test_fluent_behavior__then_times__captures_all_core()
-
- def test_fluent_behavior__always__captures_all(self):
- test_fluent_behavior__always__captures_all_core()
-
- def test_fluent_behavior__matcher__captures_relevant(self):
- test_fluent_behavior__matcher__captures_relevant_core()
-
- def test_fluent_behavior__then_repeated__captures_relevant(self):
- test_fluent_behavior__then_repeated__captures_relevant_core()
-
- def test_fluent_behavior__fallback__captures_relevant(self):
- test_fluent_behavior__fallback__captures_relevant_core()
-
- def test_fluent_behavior__default_unhandled_crash(self):
- test_fluent_behavior__default_unhandled_crash_core()
-
- def test_fluent_behavior__set_default_works(self):
- test_fluent_behavior__set_default_works_core()
-
- def test_fluent_behavior__wait_until_done(self):
- test_fluent_behavior__wait_until_done_core()
-
- def test_fluent_behavior__wait_until_done_different_lambda(self):
- test_fluent_behavior__wait_until_done_different_lambda_core()
-
- def test_fluent_behavior__wait_until_done_anything(self):
- test_fluent_behavior__wait_until_done_anything_core()
-
- def test_fluent_behavior__wait_until_done_not_happened(self):
- test_fluent_behavior__wait_until_done_not_happened_core()
-
- def test_fluent_behavior__wait_until_done_with_default(self):
- test_fluent_behavior__wait_until_done_with_default_core()
-
- def test_fluent_behavior__wait_until_done_two_events_AA(self):
- test_fluent_behavior__wait_until_done_two_events_AA_core()
+ def test_skip_a_test(self):
+ asserts.skip("Skipping this test because it's blocked by b/xyz")
+ assert False
- def test_fluent_behavior__wait_until_done_two_events_AB(self):
- test_fluent_behavior__wait_until_done_two_events_AB_core()
+ def test_nested_packets(self):
+ handle = 123
+ inside = hci_packets.ReadScanEnableBuilder()
+ logging.debug(inside.Serialize())
+ logging.debug("building outside")
+ outside = hci_packets.AclPacketBuilder(
+ handle,
+ hci_packets.PacketBoundaryFlag.FIRST_NON_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT, inside)
+ logging.debug(outside.Serialize())
+ logging.debug("Done!")
- def test_fluent_behavior__wait_until_done_only_one_event_is_done(self):
- test_fluent_behavior__wait_until_done_only_one_event_is_done_core()
+ def test_l2cap_config_options(self):
+ mtu_opt = l2cap_packets.MtuConfigurationOption()
+ mtu_opt.mtu = 123
+ fcs_opt = l2cap_packets.FrameCheckSequenceOption()
+ fcs_opt.fcs_type = l2cap_packets.FcsType.DEFAULT
+ request = l2cap_packets.ConfigurationRequestBuilder(
+ 0x1d, # Command ID
+ 0xc1d, # Channel ID
+ l2cap_packets.Continuation.END,
+ [mtu_opt, fcs_opt])
+ request.Serialize()
+ handle = 123
+ wrapped = hci_packets.AclPacketBuilder(
+ handle,
+ hci_packets.PacketBoundaryFlag.FIRST_NON_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT, request)
+ asserts.assert_true(
+ len(wrapped.Serialize()) == 16, "Packet serialized incorrectly")
diff --git a/gd/cert/cert_self_test_lib.py b/gd/cert/cert_self_test_lib.py
deleted file mode 100644
index 82b63c623..000000000
--- a/gd/cert/cert_self_test_lib.py
+++ /dev/null
@@ -1,604 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2019 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from datetime import datetime, timedelta
-import logging
-from threading import Timer
-import time
-import traceback
-
-from mobly import asserts
-
-from bluetooth_packets_python3 import hci_packets
-from bluetooth_packets_python3 import l2cap_packets
-from cert.event_stream import EventStream, FilteringEventStream
-from cert.truth import assertThat
-from cert.metadata import metadata
-from cert.behavior import when, wait_until
-from cert.behavior import IHasBehaviors
-from cert.behavior import anything
-from cert.behavior import SingleArgumentBehavior
-from cert.behavior import ReplyStage
-
-
-class BogusProto:
-
- class BogusType:
-
- def __init__(self):
- self.name = "BogusProto"
- self.is_extension = False
- self.cpp_type = False
-
- def type(self):
- return 'BogusRpc'
-
- def label(self):
- return "label"
-
- class BogusDescriptor:
-
- def __init__(self, name):
- self.full_name = name
-
- def __init__(self, value):
- self.value_ = value
- self.DESCRIPTOR = BogusProto.BogusDescriptor(str(value))
-
- def __str__(self):
- return "BogusRpc value = " + str(self.value_)
-
- def ListFields(self):
- for field in [BogusProto.BogusType()]:
- yield [field, self.value_]
-
-
-class FetchEvents:
-
- def __init__(self, events, delay_ms):
- self.events_ = events
- self.sleep_time_ = (delay_ms * 1.0) / 1000
- self.index_ = 0
- self.done_ = False
- self.then_ = datetime.now()
-
- def __iter__(self):
- for event in self.events_:
- time.sleep(self.sleep_time_)
- if self.done_:
- return
- logging.debug("yielding %d" % event)
- yield BogusProto(event)
-
- def done(self):
- return self.done_
-
- def cancel(self):
- logging.debug("cancel")
- self.done_ = True
- return None
-
-
-class TestBehaviors(object):
-
- def __init__(self, parent):
- self.test_request_behavior = SingleArgumentBehavior(lambda: TestBehaviors.TestRequestReplyStage(parent))
-
- def test_request(self, matcher):
- return self.test_request_behavior.begin(matcher)
-
- class TestRequestReplyStage(ReplyStage):
-
- def __init__(self, parent):
- self._parent = parent
-
- def increment_count(self):
- self._commit(lambda obj: self._increment_count(obj))
- return self
-
- def _increment_count(self, obj):
- self._parent.count += 1
- self._parent.captured.append(obj)
-
-
-class ObjectWithBehaviors(IHasBehaviors):
-
- def __init__(self):
- self.behaviors = TestBehaviors(self)
- self.count = 0
- self.captured = []
- self.unhandled_count = 0
-
- def get_behaviors(self):
- return self.behaviors
-
- def increment_unhandled(self):
- self.unhandled_count += 1
-
-
-def test_assert_occurs_at_least_passes_core():
- with EventStream(FetchEvents(events=[1, 2, 3, 1, 2, 3], delay_ms=40)) as event_stream:
- event_stream.assert_event_occurs(
- lambda data: data.value_ == 1, timeout=timedelta(milliseconds=300), at_least_times=2)
-
-
-def test_assert_occurs_passes_core():
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- event_stream.assert_event_occurs(lambda data: data.value_ == 1, timeout=timedelta(seconds=1))
-
-
-def test_assert_occurs_fails_core():
- try:
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- event_stream.assert_event_occurs(lambda data: data.value_ == 4, timeout=timedelta(seconds=1))
- except Exception as e:
- logging.debug(e)
- return True # Failed as expected
- return False
-
-
-def test_assert_occurs_at_most_passes_core():
- with EventStream(FetchEvents(events=[1, 2, 3, 4], delay_ms=50)) as event_stream:
- event_stream.assert_event_occurs_at_most(
- lambda data: data.value_ < 4, timeout=timedelta(seconds=1), at_most_times=3)
-
-
-def test_assert_occurs_at_most_fails_core():
- try:
- with EventStream(FetchEvents(events=[1, 2, 3, 4], delay_ms=50)) as event_stream:
- event_stream.assert_event_occurs_at_most(
- lambda data: data.value_ > 1, timeout=timedelta(seconds=1), at_most_times=2)
- except Exception as e:
- logging.debug(e)
- return True # Failed as expected
- return False
-
-
-def test_skip_a_test_core():
- asserts.skip("Skipping this test because it's blocked by b/xyz")
- assert False
-
-
-def test_nested_packets_core():
- handle = 123
- inside = hci_packets.ReadScanEnableBuilder()
- logging.debug(inside.Serialize())
- logging.debug("building outside")
- outside = hci_packets.AclBuilder(handle, hci_packets.PacketBoundaryFlag.FIRST_NON_AUTOMATICALLY_FLUSHABLE,
- hci_packets.BroadcastFlag.POINT_TO_POINT, inside)
- logging.debug(outside.Serialize())
- logging.debug("Done!")
-
-
-def test_l2cap_config_options_core():
- mtu_opt = l2cap_packets.MtuConfigurationOption()
- mtu_opt.mtu = 123
- fcs_opt = l2cap_packets.FrameCheckSequenceOption()
- fcs_opt.fcs_type = l2cap_packets.FcsType.DEFAULT
- request = l2cap_packets.ConfigurationRequestBuilder(
- 0x1d, # Command ID
- 0xc1d, # Channel ID
- l2cap_packets.Continuation.END,
- [mtu_opt, fcs_opt])
- request_b_frame = l2cap_packets.BasicFrameBuilder(0x01, request)
- handle = 123
- wrapped = hci_packets.AclBuilder(handle, hci_packets.PacketBoundaryFlag.FIRST_NON_AUTOMATICALLY_FLUSHABLE,
- hci_packets.BroadcastFlag.POINT_TO_POINT, request_b_frame)
- # Size is ACL (4) + L2CAP (4) + Configure (8) + MTU (4) + FCS (3)
- asserts.assert_true(len(wrapped.Serialize()) == 23, "Packet serialized incorrectly")
-
-
-def test_assertThat_boolean_success_core():
- assertThat(True).isTrue()
- assertThat(False).isFalse()
-
-
-def test_assertThat_boolean_falseIsTrue_core():
- try:
- assertThat(False).isTrue()
- except Exception as e:
- return True
- return False
-
-
-def test_assertThat_boolean_trueIsFalse_core():
- try:
- assertThat(True).isFalse()
- except Exception as e:
- return True
- return False
-
-
-def test_assertThat_object_success_core():
- assertThat("this").isEqualTo("this")
- assertThat("this").isNotEqualTo("that")
- assertThat(None).isNone()
- assertThat("this").isNotNone()
-
-
-def test_assertThat_object_isEqualToFails_core():
- try:
- assertThat("this").isEqualTo("that")
- except Exception as e:
- return True
- return False
-
-
-def test_assertThat_object_isNotEqualToFails_core():
- try:
- assertThat("this").isNotEqualTo("this")
- except Exception as e:
- return True
- return False
-
-
-def test_assertThat_object_isNoneFails_core():
- try:
- assertThat("this").isNone()
- except Exception as e:
- return True
- return False
-
-
-def test_assertThat_object_isNotNoneFails_core():
- try:
- assertThat(None).isNotNone()
- except Exception as e:
- return True
- return False
-
-
-def test_assertThat_eventStream_emits_passes_core():
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- assertThat(event_stream).emits(lambda data: data.value_ == 1)
-
-
-def test_assertThat_eventStream_emits_then_passes_core():
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- assertThat(event_stream).emits(lambda data: data.value_ == 1).then(lambda data: data.value_ == 3)
-
-
-def test_assertThat_eventStream_emits_fails_core():
- try:
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- assertThat(event_stream).emits(lambda data: data.value_ == 4)
- except Exception as e:
- logging.debug(e)
- return True # Failed as expected
- return False
-
-
-def test_assertThat_eventStream_emits_then_fails_core():
- try:
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- assertThat(event_stream).emits(lambda data: data.value_ == 1).emits(lambda data: data.value_ == 4)
- except Exception as e:
- logging.debug(e)
- return True # Failed as expected
- return False
-
-
-def test_assertThat_eventStream_emitsInOrder_passes_core():
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- assertThat(event_stream).emits(lambda data: data.value_ == 1, lambda data: data.value_ == 2).inOrder()
-
-
-def test_assertThat_eventStream_emitsInAnyOrder_passes_core():
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- assertThat(event_stream).emits(lambda data: data.value_ == 2,
- lambda data: data.value_ == 1).inAnyOrder().then(lambda data: data.value_ == 3)
-
-
-def test_assertThat_eventStream_emitsInOrder_fails_core():
- try:
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- assertThat(event_stream).emits(lambda data: data.value_ == 2, lambda data: data.value_ == 1).inOrder()
- except Exception as e:
- logging.debug(e)
- return True # Failed as expected
- return False
-
-
-def test_assertThat_eventStream_emitsInAnyOrder_fails_core():
- try:
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- assertThat(event_stream).emits(lambda data: data.value_ == 4, lambda data: data.value_ == 1).inAnyOrder()
- except Exception as e:
- logging.debug(e)
- return True # Failed as expected
- return False
-
-
-def test_assertThat_emitsNone_passes_core():
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- assertThat(event_stream).emitsNone(
- lambda data: data.value_ == 4, timeout=timedelta(seconds=0.15)).thenNone(
- lambda data: data.value_ == 5, timeout=timedelta(seconds=0.15))
-
-
-def test_assertThat_emitsNone_passes_after_1_second_core():
- with EventStream(FetchEvents(events=[1, 2, 3, 4], delay_ms=400)) as event_stream:
- assertThat(event_stream).emitsNone(lambda data: data.value_ == 4, timeout=timedelta(seconds=1))
-
-
-def test_assertThat_emitsNone_fails_core():
- try:
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- assertThat(event_stream).emitsNone(lambda data: data.value_ == 2, timeout=timedelta(seconds=1))
- except Exception as e:
- logging.debug(e)
- return True # Failed as expected
- return False
-
-
-def test_assertThat_emitsNone_zero_passes_core():
- with EventStream(FetchEvents(events=[], delay_ms=50)) as event_stream:
- assertThat(event_stream).emitsNone(timeout=timedelta(milliseconds=10)).thenNone(
- timeout=timedelta(milliseconds=10))
-
-
-def test_assertThat_emitsNone_zero_passes_after_one_second_core():
- with EventStream(FetchEvents([1], delay_ms=1500)) as event_stream:
- assertThat(event_stream).emitsNone(timeout=timedelta(seconds=1.0))
-
-
-def test_assertThat_emitsNone_zero_fails_core():
- try:
- with EventStream(FetchEvents(events=[17], delay_ms=50)) as event_stream:
- assertThat(event_stream).emitsNone(timeout=timedelta(seconds=1))
- except Exception as e:
- logging.debug(e)
- return True # Failed as expected
- return False
-
-
-def test_filtering_event_stream_none_filter_function_core():
- with EventStream(FetchEvents(events=[1, 2, 3], delay_ms=50)) as event_stream:
- filtered_event_stream = FilteringEventStream(event_stream, None)
- assertThat(filtered_event_stream) \
- .emits(lambda data: data.value_ == 1) \
- .then(lambda data: data.value_ == 3)
-
-
-def test_fluent_behavior_simple_core():
- thing = ObjectWithBehaviors()
-
- when(thing).test_request(anything()).then().increment_count()
-
- thing.behaviors.test_request_behavior.run("A")
-
- assertThat(thing.count).isEqualTo(1)
- assertThat(thing.captured).isEqualTo(["A"])
-
-
-def test_fluent_behavior__then_single__captures_one_core():
- thing = ObjectWithBehaviors()
-
- thing.behaviors.test_request_behavior.set_default_to_ignore()
-
- when(thing).test_request(anything()).then().increment_count()
-
- thing.behaviors.test_request_behavior.run("A")
- thing.behaviors.test_request_behavior.run("A")
- thing.behaviors.test_request_behavior.run("A")
-
- assertThat(thing.count).isEqualTo(1)
- assertThat(thing.captured).isEqualTo(["A"])
-
-
-def test_fluent_behavior__then_times__captures_all_core():
- thing = ObjectWithBehaviors()
-
- when(thing).test_request(anything()).then(times=3).increment_count()
-
- thing.behaviors.test_request_behavior.run("A")
- thing.behaviors.test_request_behavior.run("B")
- thing.behaviors.test_request_behavior.run("C")
-
- assertThat(thing.count).isEqualTo(3)
- assertThat(thing.captured).isEqualTo(["A", "B", "C"])
-
-
-def test_fluent_behavior__always__captures_all_core():
- thing = ObjectWithBehaviors()
-
- when(thing).test_request(anything()).always().increment_count()
-
- thing.behaviors.test_request_behavior.run("A")
- thing.behaviors.test_request_behavior.run("B")
- thing.behaviors.test_request_behavior.run("C")
-
- assertThat(thing.count).isEqualTo(3)
- assertThat(thing.captured).isEqualTo(["A", "B", "C"])
-
-
-def test_fluent_behavior__matcher__captures_relevant_core():
- thing = ObjectWithBehaviors()
- thing.behaviors.test_request_behavior.set_default_to_ignore()
-
- when(thing).test_request(lambda obj: obj == "B").always().increment_count()
-
- thing.behaviors.test_request_behavior.run("A")
- thing.behaviors.test_request_behavior.run("B")
- thing.behaviors.test_request_behavior.run("C")
-
- assertThat(thing.count).isEqualTo(1)
- assertThat(thing.captured).isEqualTo(["B"])
-
-
-def test_fluent_behavior__then_repeated__captures_relevant_core():
- thing = ObjectWithBehaviors()
- thing.behaviors.test_request_behavior.set_default_to_ignore()
-
- when(thing).test_request(anything()).then().increment_count().increment_count()
-
- thing.behaviors.test_request_behavior.run("A")
- thing.behaviors.test_request_behavior.run("B")
- thing.behaviors.test_request_behavior.run("A")
-
- assertThat(thing.count).isEqualTo(2)
- assertThat(thing.captured).isEqualTo(["A", "B"])
-
-
-def test_fluent_behavior__fallback__captures_relevant_core():
- thing = ObjectWithBehaviors()
- thing.behaviors.test_request_behavior.set_default_to_ignore()
-
- when(thing).test_request(lambda obj: obj == "B").then(times=1).increment_count()
- when(thing).test_request(lambda obj: obj == "C").always().increment_count()
-
- thing.behaviors.test_request_behavior.run("A")
- thing.behaviors.test_request_behavior.run("B")
- thing.behaviors.test_request_behavior.run("A")
- thing.behaviors.test_request_behavior.run("C")
- thing.behaviors.test_request_behavior.run("B")
- thing.behaviors.test_request_behavior.run("C")
-
- assertThat(thing.count).isEqualTo(3)
- assertThat(thing.captured).isEqualTo(["B", "C", "C"])
-
-
-def test_fluent_behavior__default_unhandled_crash_core():
- thing = ObjectWithBehaviors()
-
- when(thing).test_request(anything()).then().increment_count()
-
- thing.behaviors.test_request_behavior.run("A")
- try:
- thing.behaviors.test_request_behavior.run("A")
- except Exception as e:
- logging.debug(e)
- return True # Failed as expected
- return False
-
-
-def test_fluent_behavior__set_default_works_core():
- thing = ObjectWithBehaviors()
- thing.behaviors.test_request_behavior.set_default(lambda obj: thing.increment_unhandled())
-
- when(thing).test_request(anything()).then().increment_count()
-
- thing.behaviors.test_request_behavior.run("A")
- thing.behaviors.test_request_behavior.run("A")
- assertThat(thing.unhandled_count).isEqualTo(1)
-
-
-def test_fluent_behavior__wait_until_done_core():
- thing = ObjectWithBehaviors()
- is_a = lambda obj: obj == "A"
- when(thing).test_request(is_a).then().increment_count()
-
- closure = lambda: thing.behaviors.test_request_behavior.run("A")
- t = Timer(0.5, closure)
- t.start()
-
- wait_until(thing).test_request(is_a).times(1)
- assertThat(thing.count).isEqualTo(1)
- assertThat(thing.captured).isEqualTo(["A"])
-
-
-def test_fluent_behavior__wait_until_done_different_lambda_core():
- thing = ObjectWithBehaviors()
- when(thing).test_request(lambda obj: obj == "A").then().increment_count()
-
- closure = lambda: thing.behaviors.test_request_behavior.run("A")
- t = Timer(0.5, closure)
- t.start()
-
- wait_until(thing).test_request(lambda obj: obj == "A").times(1)
- assertThat(thing.count).isEqualTo(1)
- assertThat(thing.captured).isEqualTo(["A"])
-
-
-def test_fluent_behavior__wait_until_done_anything_core():
- thing = ObjectWithBehaviors()
- when(thing).test_request(lambda obj: obj == "A").then().increment_count()
-
- closure = lambda: thing.behaviors.test_request_behavior.run("A")
- t = Timer(0.5, closure)
- t.start()
-
- wait_until(thing).test_request(anything()).times(1)
- assertThat(thing.count).isEqualTo(1)
- assertThat(thing.captured).isEqualTo(["A"])
-
-
-def test_fluent_behavior__wait_until_done_not_happened_core():
- thing = ObjectWithBehaviors()
- thing.behaviors.test_request_behavior.set_default_to_ignore()
- when(thing).test_request(lambda obj: obj == "A").then().increment_count()
-
- closure = lambda: thing.behaviors.test_request_behavior.run("B")
- t = Timer(0.5, closure)
- t.start()
- assertThat(wait_until(thing).test_request(lambda obj: obj == "A").times(1)).isFalse()
-
-
-def test_fluent_behavior__wait_until_done_with_default_core():
- thing = ObjectWithBehaviors()
- thing.behaviors.test_request_behavior.set_default(lambda obj: thing.increment_unhandled())
-
- closure = lambda: thing.behaviors.test_request_behavior.run("A")
- t = Timer(0.5, closure)
- t.start()
-
- wait_until(thing).test_request(anything()).times(1)
- assertThat(thing.unhandled_count).isEqualTo(1)
-
-
-def test_fluent_behavior__wait_until_done_two_events_AA_core():
- thing = ObjectWithBehaviors()
- when(thing).test_request(lambda obj: obj == "A").then().increment_count().increment_count()
-
- closure1 = lambda: thing.behaviors.test_request_behavior.run("A")
- t1 = Timer(0.5, closure1)
- t1.start()
- closure2 = lambda: thing.behaviors.test_request_behavior.run("A")
- t2 = Timer(0.5, closure2)
- t2.start()
-
- wait_until(thing).test_request(lambda obj: obj == "A").times(2)
- assertThat(thing.count).isEqualTo(2)
- assertThat(thing.captured).isEqualTo(["A", "A"])
-
-
-def test_fluent_behavior__wait_until_done_two_events_AB_core():
- thing = ObjectWithBehaviors()
- when(thing).test_request(anything()).always().increment_count()
-
- closure1 = lambda: thing.behaviors.test_request_behavior.run("A")
- t1 = Timer(0.5, closure1)
- t1.start()
- closure2 = lambda: thing.behaviors.test_request_behavior.run("B")
- t2 = Timer(1, closure2)
- t2.start()
-
- wait_until(thing).test_request(anything()).times(2)
- assertThat(thing.count).isEqualTo(2)
- assertThat(thing.captured).isEqualTo(["A", "B"])
-
-
-def test_fluent_behavior__wait_until_done_only_one_event_is_done_core():
- thing = ObjectWithBehaviors()
- when(thing).test_request(anything()).always().increment_count()
-
- closure1 = lambda: thing.behaviors.test_request_behavior.run("A")
- t1 = Timer(1, closure1)
- t1.start()
- closure2 = lambda: thing.behaviors.test_request_behavior.run("B")
- t2 = Timer(3, closure2)
- t2.start()
- assertThat(wait_until(thing).test_request(lambda obj: obj == "A").times(2)).isFalse()
diff --git a/gd/cert/all_cert_testcases b/gd/cert/cert_testcases_facade_only
index fbbcaeebd..a5bb929f5 100644
--- a/gd/cert/all_cert_testcases
+++ b/gd/cert/cert_testcases_facade_only
@@ -3,17 +3,10 @@ SimpleHalTest
DirectHciTest
LeAdvertisingManagerTest
LeScanningManagerTest
-LeScanningWithSecurityTest
+SimpleSecurityTest
NeighborTest
ControllerTest
AclManagerTest
LeAclManagerTest
StackTest
L2capTest
-LeL2capTest
-DualL2capTest
-LeSecurityTest
-L2capPerformanceTest
-SecurityTest
-ShimTest
-LeIsoTest
diff --git a/gd/cert/change_waiter.py b/gd/cert/change_waiter.py
deleted file mode 100644
index 30a72f967..000000000
--- a/gd/cert/change_waiter.py
+++ /dev/null
@@ -1,18 +0,0 @@
-import pyinotify
-import sys
-
-wm = pyinotify.WatchManager()
-mask = pyinotify.IN_DELETE | pyinotify.IN_CREATE | pyinotify.IN_MODIFY
-
-
-class EventHandler(pyinotify.ProcessEvent):
-
- def process_default(self, event):
- quit()
-
-
-handler = EventHandler()
-notifier = pyinotify.Notifier(wm, handler)
-wdd = wm.add_watch(sys.argv[1], mask, rec=True)
-
-notifier.loop()
diff --git a/gd/cert/closable.py b/gd/cert/closable.py
deleted file mode 100644
index a1c0737ae..000000000
--- a/gd/cert/closable.py
+++ /dev/null
@@ -1,39 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2019 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from abc import ABC, abstractmethod
-
-
-class Closable(ABC):
-
- def __enter__(self):
- return self
-
- def __exit__(self, type, value, traceback):
- self.close()
- return traceback is None
-
- def __del__(self):
- self.close()
-
- @abstractmethod
- def close(self):
- pass
-
-
-def safeClose(closable):
- if closable is not None:
- closable.close()
diff --git a/gd/cert/event_asserts.py b/gd/cert/event_asserts.py
new file mode 100644
index 000000000..ea2dedcc9
--- /dev/null
+++ b/gd/cert/event_asserts.py
@@ -0,0 +1,176 @@
+#!/usr/bin/env python3
+#
+# Copyright 2019 - The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+from datetime import datetime, timedelta
+import logging
+from queue import SimpleQueue, Empty
+
+from mobly import asserts
+
+from google.protobuf import text_format
+
+
+class EventAsserts(object):
+ """
+ A class that handles various asserts with respect to a gRPC unary stream
+
+ This class must be created before an event happens as events in a
+ EventCallbackStream is not sticky and will be lost if you don't subscribe
+ to them before generating those events.
+
+ When asserting on sequential events, a single EventAsserts object is enough
+
+ When asserting on simultaneous events, you would need multiple EventAsserts
+ objects as each EventAsserts object owns a separate queue that is actively
+ being popped as asserted events happen
+ """
+ DEFAULT_TIMEOUT_SECONDS = 3
+
+ def __init__(self, event_callback_stream):
+ if event_callback_stream is None:
+ raise ValueError("event_callback_stream cannot be None")
+ self.event_callback_stream = event_callback_stream
+ self.event_queue = SimpleQueue()
+ self.callback = lambda event: self.event_queue.put(event)
+ self.event_callback_stream.register_callback(self.callback)
+
+ def __del__(self):
+ self.event_callback_stream.unregister_callback(self.callback)
+
+ def remaining_time_delta(self, end_time):
+ remaining = end_time - datetime.now()
+ if remaining < timedelta(milliseconds=0):
+ remaining = timedelta(milliseconds=0)
+ return remaining
+
+ def assert_none(self, timeout=timedelta(seconds=DEFAULT_TIMEOUT_SECONDS)):
+ """
+ Assert no event happens within timeout period
+
+ :param timeout: a timedelta object
+ :return:
+ """
+ logging.debug("assert_none %fs" % (timeout.total_seconds()))
+ try:
+ event = self.event_queue.get(timeout=timeout.total_seconds())
+ asserts.assert_true(
+ event is None,
+ msg=("Expected None, but got %s" % text_format.MessageToString(
+ event, as_one_line=True)))
+ except Empty:
+ return
+
+ def assert_none_matching(
+ self, match_fn, timeout=timedelta(seconds=DEFAULT_TIMEOUT_SECONDS)):
+ """
+ Assert no events where match_fn(event) is True happen within timeout
+ period
+
+ :param match_fn: return True/False on match_fn(event)
+ :param timeout: a timedelta object
+ :return:
+ """
+ logging.debug("assert_none_matching %fs" % (timeout.total_seconds()))
+ event = None
+ end_time = datetime.now() + timeout
+ while event is None and datetime.now() < end_time:
+ remaining = self.remaining_time_delta(end_time)
+ logging.debug("Waiting for event (%fs remaining)" %
+ (remaining.total_seconds()))
+ try:
+ current_event = self.event_queue.get(
+ timeout=remaining.total_seconds())
+ if match_fn(current_event):
+ event = current_event
+ except Empty:
+ continue
+ logging.debug("Done waiting for an event")
+ if event is None:
+ return # Avoid an assert in MessageToString(None, ...)
+ asserts.assert_true(
+ event is None,
+ msg=("Expected None matching, but got %s" %
+ text_format.MessageToString(event, as_one_line=True)))
+
+ def assert_event_occurs(self,
+ match_fn,
+ at_least_times=1,
+ timeout=timedelta(seconds=DEFAULT_TIMEOUT_SECONDS)):
+ """
+ Assert at least |at_least_times| instances of events happen where
+ match_fn(event) returns True within timeout period
+
+ :param match_fn: returns True/False on match_fn(event)
+ :param timeout: a timedelta object
+ :param at_least_times: how many times at least a matching event should
+ happen
+ :return:
+ """
+ logging.debug("assert_event_occurs %d %fs" % (at_least_times,
+ timeout.total_seconds()))
+ event_list = []
+ end_time = datetime.now() + timeout
+ while len(event_list) < at_least_times and datetime.now() < end_time:
+ remaining = self.remaining_time_delta(end_time)
+ logging.debug("Waiting for event (%fs remaining)" %
+ (remaining.total_seconds()))
+ try:
+ current_event = self.event_queue.get(
+ timeout=remaining.total_seconds())
+ if match_fn(current_event):
+ event_list.append(current_event)
+ except Empty:
+ continue
+ logging.debug("Done waiting for event")
+ asserts.assert_true(
+ len(event_list) >= at_least_times,
+ msg=("Expected at least %d events, but got %d" % (at_least_times,
+ len(event_list))))
+
+ def assert_event_occurs_at_most(
+ self,
+ match_fn,
+ at_most_times,
+ timeout=timedelta(seconds=DEFAULT_TIMEOUT_SECONDS)):
+ """
+ Assert at most |at_most_times| instances of events happen where
+ match_fn(event) returns True within timeout period
+
+ :param match_fn: returns True/False on match_fn(event)
+ :param at_most_times: how many times at most a matching event should
+ happen
+ :param timeout:a timedelta object
+ :return:
+ """
+ logging.debug("assert_event_occurs_at_most")
+ event_list = []
+ end_time = datetime.now() + timeout
+ while len(event_list) <= at_most_times and datetime.now() < end_time:
+ remaining = self.remaining_time_delta(end_time)
+ logging.debug("Waiting for event iteration (%fs remaining)" %
+ (remaining.total_seconds()))
+ try:
+ current_event = self.event_queue.get(
+ timeout=remaining.total_seconds())
+ if match_fn(current_event):
+ event_list.append(current_event)
+ except Empty:
+ continue
+ logging.debug("Done waiting, got %d events" % len(event_list))
+ asserts.assert_true(
+ len(event_list) <= at_most_times,
+ msg=("Expected at most %d events, but got %d" % (at_most_times,
+ len(event_list))))
diff --git a/gd/cert/event_callback_stream.py b/gd/cert/event_callback_stream.py
new file mode 100644
index 000000000..00ea9cc83
--- /dev/null
+++ b/gd/cert/event_callback_stream.py
@@ -0,0 +1,147 @@
+#!/usr/bin/env python3
+#
+# Copyright 2019 - The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+from concurrent.futures import ThreadPoolExecutor
+from grpc import RpcError
+import logging
+
+
+class EventCallbackStream(object):
+ """
+ A an object that translate a gRPC stream of events to a Python stream of
+ callbacks.
+
+ All callbacks are non-sticky. This means that user will only receive callback
+ generated after EventCallbackStream is registered and will not receive any
+ callback after EventCallbackStream is unregistered
+
+ You would need a new EventCallbackStream and anything that depends on this
+ object once shutdown() is called
+ """
+
+ def __init__(self, server_stream_call):
+ """
+ Construct this object, call the |grpc_lambda| and trigger event_callback on
+ the thread used to create this object until |destroy| is called when this
+ object can no longer be used
+ :param server_stream_call: A server stream call object returned from
+ calling a gRPC server stream RPC API. The
+ object must support iterator interface (i.e.
+ next() method) and the grpc.Call interface
+ so that we can cancel it
+ :param event_callback: callback to be invoked with the only argument as
+ the generated event. The callback will be invoked
+ on a separate thread created within this object
+ """
+ if server_stream_call is None:
+ raise ValueError("server_stream_call must not be None")
+ self.server_stream_call = server_stream_call
+ self.handlers = []
+ self.executor = ThreadPoolExecutor()
+ self.future = self.executor.submit(EventCallbackStream._event_loop,
+ self)
+
+ def __enter__(self):
+ return self
+
+ def __exit__(self, type, value, traceback):
+ self.shutdown()
+ if traceback is None:
+ return True
+ else:
+ return False
+
+ def __del__(self):
+ self.shutdown()
+
+ def register_callback(self, callback, matcher_fn=None):
+ """
+ Register a callback to handle events. Event will be handled by callback
+ if matcher_fn(event) returns True
+
+ callback and matcher are registered as a tuple. Hence the same callback
+ with different matcher are considered two different handler units. Same
+ matcher, but different callback are also considered different handling
+ unit
+
+ Callback will be invoked on a ThreadPoolExecutor owned by this
+ EventCallbackStream
+
+ :param callback: Will be called as callback(event)
+ :param matcher_fn: A boolean function that returns True or False when
+ calling matcher_fn(event), if None, all event will
+ be matched
+ """
+ if callback is None:
+ raise ValueError("callback must not be None")
+ self.handlers.append((callback, matcher_fn))
+
+ def unregister_callback(self, callback, matcher_fn=None):
+ """
+ Unregister callback and matcher_fn from the event stream. Both objects
+ must match exactly the ones when calling register_callback()
+
+ :param callback: callback used in register_callback()
+ :param matcher_fn: matcher_fn used in register_callback()
+ :raises ValueError when (callback, matcher_fn) tuple is not found
+ """
+ if callback is None:
+ raise ValueError("callback must not be None")
+ self.handlers.remove((callback, matcher_fn))
+
+ def shutdown(self):
+ """
+ Stop the gRPC lambda so that event_callback will not be invoked after th
+ method returns.
+
+ This object will be useless after this call as there is no way to restart
+ the gRPC callback. You would have to create a new EventCallbackStream
+
+ :return: None on success, exception object on failure
+ """
+ while not self.server_stream_call.done():
+ self.server_stream_call.cancel()
+ exception_for_return = None
+ try:
+ result = self.future.result()
+ if result:
+ logging.warning("Inner loop error %s" % result)
+ raise result
+ except Exception as exp:
+ logging.warning("Exception: %s" % (exp))
+ exception_for_return = exp
+ self.executor.shutdown()
+ return exception_for_return
+
+ def _event_loop(self):
+ """
+ Main loop for consuming the gRPC stream events.
+ Blocks until computation is cancelled
+ :return: None on success, exception object on failure
+ """
+ try:
+ for event in self.server_stream_call:
+ for (callback, matcher_fn) in self.handlers:
+ if not matcher_fn or matcher_fn(event):
+ callback(event)
+ return None
+ except RpcError as exp:
+ if self.server_stream_call.cancelled():
+ logging.debug("Cancelled")
+ return None
+ else:
+ logging.warning("Some RPC error not due to cancellation")
+ return exp
diff --git a/gd/cert/event_stream.py b/gd/cert/event_stream.py
deleted file mode 100644
index ef7729c7d..000000000
--- a/gd/cert/event_stream.py
+++ /dev/null
@@ -1,294 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2019 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from abc import ABC, abstractmethod
-from concurrent.futures import ThreadPoolExecutor
-from datetime import datetime, timedelta
-import logging
-from queue import SimpleQueue, Empty
-
-from mobly import asserts
-
-from google.protobuf import text_format
-
-from grpc import RpcError
-
-from cert.closable import Closable
-
-
-class IEventStream(ABC):
-
- @abstractmethod
- def get_event_queue(self):
- pass
-
-
-class FilteringEventStream(IEventStream):
-
- def __init__(self, stream, filter_fn):
- self.filter_fn = filter_fn if filter_fn else lambda x: x
- self.event_queue = SimpleQueue()
- self.stream = stream
-
- self.stream.register_callback(self.__event_callback, lambda packet: self.filter_fn(packet) is not None)
-
- def __event_callback(self, event):
- self.event_queue.put(self.filter_fn(event))
-
- def get_event_queue(self):
- return self.event_queue
-
- def unregister(self):
- self.stream.unregister(self.__event_callback)
-
-
-def pretty_print(proto_event):
- return '{} {}'.format(type(proto_event).__name__, text_format.MessageToString(proto_event, as_one_line=True))
-
-
-DEFAULT_TIMEOUT_SECONDS = 3
-
-
-class EventStream(IEventStream, Closable):
- """
- A class that streams events from a gRPC stream, which you can assert on.
-
- Don't use these asserts directly, use the ones from cert.truth.
- """
-
- def __init__(self, server_stream_call):
- if server_stream_call is None:
- raise ValueError("server_stream_call cannot be None")
-
- self.server_stream_call = server_stream_call
- self.event_queue = SimpleQueue()
- self.handlers = []
- self.executor = ThreadPoolExecutor()
- self.future = self.executor.submit(EventStream.__event_loop, self)
-
- def get_event_queue(self):
- return self.event_queue
-
- def close(self):
- """
- Stop the gRPC lambda so that event_callback will not be invoked after
- the method returns.
-
- This object will be useless after this call as there is no way to
- restart the gRPC callback. You would have to create a new EventStream
-
- :raise None on success, or the same exception as __event_loop(), or
- concurrent.futures.TimeoutError if underlying stream failed to
- terminate within DEFAULT_TIMEOUT_SECONDS
- """
- # Try to cancel the execution, don't care the result, non-blocking
- self.server_stream_call.cancel()
- try:
- # cancelling gRPC stream should cause __event_loop() to quit
- # same exception will be raised by future.result() or
- # concurrent.futures.TimeoutError will be raised after timeout
- self.future.result(timeout=DEFAULT_TIMEOUT_SECONDS)
- finally:
- # Make sure we force shutdown the executor regardless of the result
- self.executor.shutdown(wait=False)
-
- def register_callback(self, callback, matcher_fn=None):
- """
- Register a callback to handle events. Event will be handled by callback
- if matcher_fn(event) returns True
-
- callback and matcher are registered as a tuple. Hence the same callback
- with different matcher are considered two different handler units. Same
- matcher, but different callback are also considered different handling
- unit
-
- Callback will be invoked on a ThreadPoolExecutor owned by this
- EventStream
-
- :param callback: Will be called as callback(event)
- :param matcher_fn: A boolean function that returns True or False when
- calling matcher_fn(event), if None, all event will
- be matched
- """
- if callback is None:
- raise ValueError("callback must not be None")
- self.handlers.append((callback, matcher_fn))
-
- def unregister_callback(self, callback, matcher_fn=None):
- """
- Unregister callback and matcher_fn from the event stream. Both objects
- must match exactly the ones when calling register_callback()
-
- :param callback: callback used in register_callback()
- :param matcher_fn: matcher_fn used in register_callback()
- :raises ValueError when (callback, matcher_fn) tuple is not found
- """
- if callback is None:
- raise ValueError("callback must not be None")
- self.handlers.remove((callback, matcher_fn))
-
- def __event_loop(self):
- """
- Main loop for consuming the gRPC stream events.
- Blocks until computation is cancelled
- :raise grpc.Error on failure
- """
- try:
- for event in self.server_stream_call:
- self.event_queue.put(event)
- for (callback, matcher_fn) in self.handlers:
- if not matcher_fn or matcher_fn(event):
- callback(event)
- except RpcError as exp:
- # Underlying gRPC stream should run indefinitely until cancelled
- # Hence any other reason besides CANCELLED is raised as an error
- if self.server_stream_call.cancelled():
- logging.debug("Cancelled")
- else:
- raise exp
-
- def assert_event_occurs(self, match_fn, at_least_times=1, timeout=timedelta(seconds=DEFAULT_TIMEOUT_SECONDS)):
- """
- Assert at least |at_least_times| instances of events happen where
- match_fn(event) returns True within timeout period
-
- :param match_fn: returns True/False on match_fn(event)
- :param timeout: a timedelta object
- :param at_least_times: how many times at least a matching event should
- happen
- :return:
- """
- NOT_FOR_YOU_assert_event_occurs(self, match_fn, at_least_times, timeout)
-
- def assert_event_occurs_at_most(self, match_fn, at_most_times, timeout=timedelta(seconds=DEFAULT_TIMEOUT_SECONDS)):
- """
- Assert at most |at_most_times| instances of events happen where
- match_fn(event) returns True within timeout period
-
- :param match_fn: returns True/False on match_fn(event)
- :param at_most_times: how many times at most a matching event should
- happen
- :param timeout:a timedelta object
- :return:
- """
- logging.debug("assert_event_occurs_at_most")
- event_list = []
- end_time = datetime.now() + timeout
- while len(event_list) <= at_most_times and datetime.now() < end_time:
- remaining = static_remaining_time_delta(end_time)
- logging.debug("Waiting for event iteration (%fs remaining)" % (remaining.total_seconds()))
- try:
- current_event = self.event_queue.get(timeout=remaining.total_seconds())
- if match_fn(current_event):
- event_list.append(current_event)
- except Empty:
- continue
- logging.debug("Done waiting, got %d events" % len(event_list))
- asserts.assert_true(
- len(event_list) <= at_most_times,
- msg=("Expected at most %d events, but got %d" % (at_most_times, len(event_list))))
-
-
-def static_remaining_time_delta(end_time):
- remaining = end_time - datetime.now()
- if remaining < timedelta(milliseconds=0):
- remaining = timedelta(milliseconds=0)
- return remaining
-
-
-def NOT_FOR_YOU_assert_event_occurs(istream,
- match_fn,
- at_least_times=1,
- timeout=timedelta(seconds=DEFAULT_TIMEOUT_SECONDS)):
- logging.debug("assert_event_occurs %d %fs" % (at_least_times, timeout.total_seconds()))
- event_list = []
- end_time = datetime.now() + timeout
- while len(event_list) < at_least_times and datetime.now() < end_time:
- remaining = static_remaining_time_delta(end_time)
- logging.debug("Waiting for event (%fs remaining)" % (remaining.total_seconds()))
- try:
- current_event = istream.get_event_queue().get(timeout=remaining.total_seconds())
- logging.debug("current_event: %s", current_event)
- if match_fn(current_event):
- event_list.append(current_event)
- except Empty:
- continue
- logging.debug("Done waiting for event, received %d", len(event_list))
- asserts.assert_true(
- len(event_list) >= at_least_times,
- msg=("Expected at least %d events, but got %d" % (at_least_times, len(event_list))))
-
-
-def NOT_FOR_YOU_assert_all_events_occur(istream,
- match_fns,
- order_matters,
- timeout=timedelta(seconds=DEFAULT_TIMEOUT_SECONDS)):
- logging.debug("assert_all_events_occur %fs" % timeout.total_seconds())
- pending_matches = list(match_fns)
- matched_order = []
- end_time = datetime.now() + timeout
- while len(pending_matches) > 0 and datetime.now() < end_time:
- remaining = static_remaining_time_delta(end_time)
- logging.debug("Waiting for event (%fs remaining)" % (remaining.total_seconds()))
- try:
- current_event = istream.get_event_queue().get(timeout=remaining.total_seconds())
- for match_fn in pending_matches:
- if match_fn(current_event):
- pending_matches.remove(match_fn)
- matched_order.append(match_fn)
- except Empty:
- continue
- logging.debug("Done waiting for event")
- asserts.assert_true(
- len(matched_order) == len(match_fns),
- msg=("Expected at least %d events, but got %d" % (len(match_fns), len(matched_order))))
- if order_matters:
- correct_order = True
- i = 0
- while i < len(match_fns):
- if match_fns[i] is not matched_order[i]:
- correct_order = False
- break
- i += 1
- asserts.assert_true(correct_order, "Events not received in correct order %s %s" % (match_fns, matched_order))
-
-
-def NOT_FOR_YOU_assert_none_matching(istream, match_fn, timeout=timedelta(seconds=DEFAULT_TIMEOUT_SECONDS)):
- logging.debug("assert_none_matching %fs" % (timeout.total_seconds()))
- event = None
- end_time = datetime.now() + timeout
- while event is None and datetime.now() < end_time:
- remaining = static_remaining_time_delta(end_time)
- logging.debug("Waiting for event (%fs remaining)" % (remaining.total_seconds()))
- try:
- current_event = istream.get_event_queue().get(timeout=remaining.total_seconds())
- if match_fn(current_event):
- event = current_event
- except Empty:
- continue
- logging.debug("Done waiting for an event")
- if event is None:
- return # Avoid an assert in MessageToString(None, ...)
- asserts.assert_true(event is None, msg='Expected None matching, but got {}'.format(pretty_print(event)))
-
-
-def NOT_FOR_YOU_assert_none(istream, timeout=timedelta(seconds=DEFAULT_TIMEOUT_SECONDS)):
- logging.debug("assert_none %fs" % (timeout.total_seconds()))
- try:
- event = istream.get_event_queue().get(timeout=timeout.total_seconds())
- asserts.assert_true(event is None, msg='Expected None, but got {}'.format(pretty_print(event)))
- except Empty:
- return
diff --git a/gd/cert/gd_base_test.py b/gd/cert/gd_base_test.py
index b382e6a22..ab19ba12e 100644
--- a/gd/cert/gd_base_test.py
+++ b/gd/cert/gd_base_test.py
@@ -14,120 +14,64 @@
# See the License for the specific language governing permissions and
# limitations under the License.
+from acts.base_test import BaseTestClass
+
import importlib
import logging
import os
import signal
import subprocess
-import traceback
-
-from functools import wraps
-from grpc import RpcError
-
-from acts import asserts, signals
-from acts.context import get_current_context
-from acts.base_test import BaseTestClass
-from cert.async_subprocess_logger import AsyncSubprocessLogger
-from cert.os_utils import get_gd_root
-from cert.os_utils import read_crash_snippet_and_log_tail
-from cert.os_utils import is_subprocess_alive
-from cert.os_utils import make_ports_available
-from cert.os_utils import TerminalColor
-from cert.gd_device import MOBLY_CONTROLLER_CONFIG_NAME as CONTROLLER_CONFIG_NAME
-from facade import rootservice_pb2 as facade_rootservice
-from cert.gd_base_test_lib import setup_class_core
-from cert.gd_base_test_lib import teardown_class_core
-from cert.gd_base_test_lib import setup_test_core
-from cert.gd_base_test_lib import teardown_test_core
-from cert.gd_base_test_lib import dump_crashes_core
+ANDROID_BUILD_TOP = os.environ.get('ANDROID_BUILD_TOP')
class GdBaseTestClass(BaseTestClass):
- SUBPROCESS_WAIT_TIMEOUT_SECONDS = 10
+ def __init__(self, configs):
+ BaseTestClass.__init__(self, configs)
- def setup_class(self, dut_module, cert_module):
- self.log_path_base = get_current_context().get_full_output_path()
- self.verbose_mode = bool(self.user_params.get('verbose_mode', False))
- for config in self.controller_configs[CONTROLLER_CONFIG_NAME]:
- config['verbose_mode'] = self.verbose_mode
-
- self.info = setup_class_core(
- dut_module=dut_module,
- cert_module=cert_module,
- verbose_mode=self.verbose_mode,
- log_path_base=self.log_path_base,
- controller_configs=self.controller_configs)
- self.dut_module = self.info['dut_module']
- self.cert_module = self.info['cert_module']
- self.rootcanal_running = self.info['rootcanal_running']
- self.rootcanal_logpath = self.info['rootcanal_logpath']
- self.rootcanal_process = self.info['rootcanal_process']
+ log_path_base = getattr(configs, "log_path", "/tmp/logs")
+ gd_devices = self.controller_configs.get("GdDevice")
+ gd_cert_devices = self.controller_configs.get("GdCertDevice")
+ self.rootcanal_running = False
if 'rootcanal' in self.controller_configs:
- asserts.assert_true(self.info['rootcanal_exist'],
- "Root canal does not exist at %s" % self.info['rootcanal'])
- asserts.assert_true(self.info['make_rootcanal_ports_available'],
- "Failed to make root canal ports available")
-
- self.log.debug("Running %s" % " ".join(self.info['rootcanal_cmd']))
- asserts.assert_true(
- self.info['is_rootcanal_process_started'],
- msg="Cannot start root-canal at " + str(self.info['rootcanal']))
- asserts.assert_true(self.info['is_subprocess_alive'], msg="root-canal stopped immediately after running")
-
- self.rootcanal_logger = self.info['rootcanal_logger']
- self.controller_configs = self.info['controller_configs']
-
- # Parse and construct GD device objects
- self.register_controller(importlib.import_module('cert.gd_device'), builtin=True)
- self.dut = self.gd_devices[1]
- self.cert = self.gd_devices[0]
+ self.rootcanal_running = True
+ rootcanal_logpath = os.path.join(log_path_base,
+ 'rootcanal_logs.txt')
+ self.rootcanal_logs = open(rootcanal_logpath, 'w')
+ rootcanal_config = self.controller_configs['rootcanal']
+ rootcanal_hci_port = str(rootcanal_config.get("hci_port", "6402"))
+ android_host_out = os.environ.get('ANDROID_HOST_OUT')
+ rootcanal = android_host_out + "/nativetest64/root-canal/root-canal"
+ self.rootcanal_process = subprocess.Popen(
+ [
+ rootcanal,
+ str(rootcanal_config.get("test_port", "6401")),
+ rootcanal_hci_port,
+ str(rootcanal_config.get("link_layer_port", "6403"))
+ ],
+ cwd=ANDROID_BUILD_TOP,
+ env=os.environ.copy(),
+ stdout=self.rootcanal_logs,
+ stderr=self.rootcanal_logs)
+ for gd_device in gd_devices:
+ gd_device["rootcanal_port"] = rootcanal_hci_port
+ for gd_cert_device in gd_cert_devices:
+ gd_cert_device["rootcanal_port"] = rootcanal_hci_port
+
+ self.register_controller(
+ importlib.import_module('cert.gd_device'), builtin=True)
+ self.register_controller(
+ importlib.import_module('cert.gd_cert_device'), builtin=True)
def teardown_class(self):
- teardown_class_core(
- rootcanal_running=self.rootcanal_running,
- rootcanal_process=self.rootcanal_process,
- rootcanal_logger=self.rootcanal_logger,
- subprocess_wait_timeout_seconds=self.SUBPROCESS_WAIT_TIMEOUT_SECONDS)
-
- def setup_test(self):
- setup_test_core(dut=self.dut, cert=self.cert, dut_module=self.dut_module, cert_module=self.cert_module)
-
- def teardown_test(self):
- teardown_test_core(cert=self.cert, dut=self.dut)
-
- def __getattribute__(self, name):
- attr = super().__getattribute__(name)
- if not callable(attr) or not GdBaseTestClass.__is_entry_function(name):
- return attr
-
- @wraps(attr)
- def __wrapped(*args, **kwargs):
- try:
- return attr(*args, **kwargs)
- except RpcError as e:
- exception_info = "".join(traceback.format_exception(e.__class__, e, e.__traceback__))
- raise signals.TestFailure(
- "RpcError during test\n\nRpcError:\n\n%s\n%s" % (exception_info, self.__dump_crashes()))
-
- return __wrapped
-
- __ENTRY_METHODS = {"setup_class", "teardown_class", "setup_test", "teardown_test"}
-
- @staticmethod
- def __is_entry_function(name):
- return name.startswith("test_") or name in GdBaseTestClass.__ENTRY_METHODS
-
- def __dump_crashes(self):
- """
- return: formatted stack traces if found, or last few lines of log
- """
- crash_detail = dump_crashes_core(
- dut=self.dut,
- cert=self.cert,
- rootcanal_running=self.rootcanal_running,
- rootcanal_process=self.rootcanal_process,
- rootcanal_logpath=self.rootcanal_logpath)
- return crash_detail
+ if self.rootcanal_running:
+ self.rootcanal_process.send_signal(signal.SIGINT)
+ rootcanal_return_code = self.rootcanal_process.wait()
+ self.rootcanal_logs.close()
+ if rootcanal_return_code != 0 and\
+ rootcanal_return_code != -signal.SIGINT:
+ logging.error(
+ "rootcanal stopped with code: %d" % rootcanal_return_code)
+ return False
diff --git a/gd/cert/gd_base_test_facade_only.py b/gd/cert/gd_base_test_facade_only.py
new file mode 100644
index 000000000..d79e20bb7
--- /dev/null
+++ b/gd/cert/gd_base_test_facade_only.py
@@ -0,0 +1,75 @@
+#!/usr/bin/env python3
+#
+# Copyright 2019 - The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+from acts.base_test import BaseTestClass
+from acts import context
+
+import importlib
+import logging
+import os
+import signal
+import subprocess
+
+ANDROID_BUILD_TOP = os.environ.get('ANDROID_BUILD_TOP')
+
+
+class GdFacadeOnlyBaseTestClass(BaseTestClass):
+
+ def setup_class(self):
+
+ log_path_base = context.get_current_context().get_full_output_path()
+ gd_devices = self.controller_configs.get("GdDevice")
+
+ self.rootcanal_running = False
+ if 'rootcanal' in self.controller_configs:
+ self.rootcanal_running = True
+ rootcanal_logpath = os.path.join(log_path_base,
+ 'rootcanal_logs.txt')
+ self.rootcanal_logs = open(rootcanal_logpath, 'w')
+ rootcanal_config = self.controller_configs['rootcanal']
+ rootcanal_hci_port = str(rootcanal_config.get("hci_port", "6402"))
+ android_host_out = os.environ.get('ANDROID_HOST_OUT')
+ rootcanal = android_host_out + "/nativetest64/root-canal/root-canal"
+ self.rootcanal_process = subprocess.Popen(
+ [
+ rootcanal,
+ str(rootcanal_config.get("test_port", "6401")),
+ rootcanal_hci_port,
+ str(rootcanal_config.get("link_layer_port", "6403"))
+ ],
+ cwd=ANDROID_BUILD_TOP,
+ env=os.environ.copy(),
+ stdout=self.rootcanal_logs,
+ stderr=self.rootcanal_logs)
+ for gd_device in gd_devices:
+ gd_device["rootcanal_port"] = rootcanal_hci_port
+
+ self.register_controller(
+ importlib.import_module('cert.gd_device'), builtin=True)
+
+ self.device_under_test = self.gd_devices[1]
+ self.cert_device = self.gd_devices[0]
+
+ def teardown_class(self):
+ if self.rootcanal_running:
+ self.rootcanal_process.send_signal(signal.SIGINT)
+ rootcanal_return_code = self.rootcanal_process.wait()
+ self.rootcanal_logs.close()
+ if rootcanal_return_code != 0 and\
+ rootcanal_return_code != -signal.SIGINT:
+ logging.error(
+ "rootcanal stopped with code: %d" % rootcanal_return_code)
+ return False
diff --git a/gd/cert/gd_base_test_lib.py b/gd/cert/gd_base_test_lib.py
deleted file mode 100644
index 19b83f1c9..000000000
--- a/gd/cert/gd_base_test_lib.py
+++ /dev/null
@@ -1,163 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2019 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import importlib
-import logging
-import os
-import signal
-import subprocess
-import traceback
-
-from functools import wraps
-from grpc import RpcError
-
-from cert.async_subprocess_logger import AsyncSubprocessLogger
-from cert.os_utils import get_gd_root
-from cert.os_utils import read_crash_snippet_and_log_tail
-from cert.os_utils import is_subprocess_alive
-from cert.os_utils import make_ports_available
-from cert.os_utils import TerminalColor
-from cert.gd_device import MOBLY_CONTROLLER_CONFIG_NAME as CONTROLLER_CONFIG_NAME
-from facade import rootservice_pb2 as facade_rootservice
-
-
-def setup_class_core(dut_module, cert_module, verbose_mode, log_path_base, controller_configs):
- info = {}
- info['dut_module'] = dut_module
- info['cert_module'] = cert_module
- info['controller_configs'] = controller_configs
-
- # Start root-canal if needed
- info['rootcanal_running'] = False
- if 'rootcanal' in info['controller_configs']:
- info['rootcanal_running'] = True
- # Get root canal binary
- rootcanal = os.path.join(get_gd_root(), "root-canal")
- info['rootcanal'] = rootcanal
- info['rootcanal_exist'] = os.path.isfile(rootcanal)
- if not os.path.isfile(rootcanal):
- return info
-
- # Get root canal log
- rootcanal_logpath = os.path.join(log_path_base, 'rootcanal_logs.txt')
- info['rootcanal_logpath'] = rootcanal_logpath
- # Make sure ports are available
- rootcanal_config = info['controller_configs']['rootcanal']
- rootcanal_test_port = int(rootcanal_config.get("test_port", "6401"))
- rootcanal_hci_port = int(rootcanal_config.get("hci_port", "6402"))
- rootcanal_link_layer_port = int(rootcanal_config.get("link_layer_port", "6403"))
-
- info['make_rootcanal_ports_available'] = make_ports_available((rootcanal_test_port, rootcanal_hci_port,
- rootcanal_link_layer_port))
- if not make_ports_available((rootcanal_test_port, rootcanal_hci_port, rootcanal_link_layer_port)):
- return info
-
- # Start root canal process
- rootcanal_cmd = [rootcanal, str(rootcanal_test_port), str(rootcanal_hci_port), str(rootcanal_link_layer_port)]
- info['rootcanal_cmd'] = rootcanal_cmd
-
- rootcanal_process = subprocess.Popen(
- rootcanal_cmd,
- cwd=get_gd_root(),
- env=os.environ.copy(),
- stdout=subprocess.PIPE,
- stderr=subprocess.STDOUT,
- universal_newlines=True)
-
- info['rootcanal_process'] = rootcanal_process
- if rootcanal_process:
- info['is_rootcanal_process_started'] = True
- else:
- info['is_rootcanal_process_started'] = False
- return info
- info['is_subprocess_alive'] = is_subprocess_alive(rootcanal_process)
- if not is_subprocess_alive(rootcanal_process):
- info['is_subprocess_alive'] = False
- return info
-
- info['rootcanal_logger'] = AsyncSubprocessLogger(
- rootcanal_process, [rootcanal_logpath],
- log_to_stdout=verbose_mode,
- tag="rootcanal",
- color=TerminalColor.MAGENTA)
-
- # Modify the device config to include the correct root-canal port
- for gd_device_config in info['controller_configs'].get("GdDevice"):
- gd_device_config["rootcanal_port"] = str(rootcanal_hci_port)
-
- return info
-
-
-def teardown_class_core(rootcanal_running, rootcanal_process, rootcanal_logger, subprocess_wait_timeout_seconds):
- if rootcanal_running:
- stop_signal = signal.SIGINT
- rootcanal_process.send_signal(stop_signal)
- try:
- return_code = rootcanal_process.wait(timeout=subprocess_wait_timeout_seconds)
- except subprocess.TimeoutExpired:
- logging.error("Failed to interrupt root canal via SIGINT, sending SIGKILL")
- stop_signal = signal.SIGKILL
- rootcanal_process.kill()
- try:
- return_code = rootcanal_process.wait(timeout=subprocess_wait_timeout_seconds)
- except subprocess.TimeoutExpired:
- logging.error("Failed to kill root canal")
- return_code = -65536
- if return_code != 0 and return_code != -stop_signal:
- logging.error("rootcanal stopped with code: %d" % return_code)
- rootcanal_logger.stop()
-
-
-def setup_test_core(dut, cert, dut_module, cert_module):
- dut.rootservice.StartStack(
- facade_rootservice.StartStackRequest(module_under_test=facade_rootservice.BluetoothModule.Value(dut_module),))
- cert.rootservice.StartStack(
- facade_rootservice.StartStackRequest(module_under_test=facade_rootservice.BluetoothModule.Value(cert_module),))
-
- dut.wait_channel_ready()
- cert.wait_channel_ready()
-
-
-def teardown_test_core(cert, dut):
- cert.rootservice.StopStack(facade_rootservice.StopStackRequest())
- dut.rootservice.StopStack(facade_rootservice.StopStackRequest())
-
-
-def dump_crashes_core(dut, cert, rootcanal_running, rootcanal_process, rootcanal_logpath):
- dut_crash, dut_log_tail = dut.get_crash_snippet_and_log_tail()
- cert_crash, cert_log_tail = cert.get_crash_snippet_and_log_tail()
- rootcanal_crash = None
- rootcanal_log_tail = None
- if rootcanal_running and not is_subprocess_alive(rootcanal_process):
- rootcanal_crash, roocanal_log_tail = read_crash_snippet_and_log_tail(rootcanal_logpath)
-
- crash_detail = ""
- if dut_crash or cert_crash or rootcanal_crash:
- if rootcanal_crash:
- crash_detail += "rootcanal crashed:\n\n%s\n\n" % rootcanal_crash
- if dut_crash:
- crash_detail += "dut stack crashed:\n\n%s\n\n" % dut_crash
- if cert_crash:
- crash_detail += "cert stack crashed:\n\n%s\n\n" % cert_crash
- else:
- if rootcanal_log_tail:
- crash_detail += "rootcanal log tail:\n\n%s\n\n" % rootcanal_log_tail
- if dut_log_tail:
- crash_detail += "dut log tail:\n\n%s\n\n" % dut_log_tail
- if cert_log_tail:
- crash_detail += "cert log tail:\n\n%s\n\n" % cert_log_tail
-
- return crash_detail
diff --git a/gd/cert/gd_device.py b/gd/cert/gd_device.py
index 65d85d216..a13298cb2 100644
--- a/gd/cert/gd_device.py
+++ b/gd/cert/gd_device.py
@@ -14,71 +14,39 @@
# See the License for the specific language governing permissions and
# limitations under the License.
-from abc import ABC
-from datetime import datetime
-import inspect
import logging
-import os
-import pathlib
-import shutil
-import signal
-import socket
-import subprocess
-import time
-from typing import List
-import grpc
-
-from acts import asserts
-from acts import utils
-from acts.context import get_current_context
-from acts.controllers.adb import AdbProxy
-from acts.controllers.adb import AdbError
-from acts.controllers.adb_lib.error import AdbCommandError
-
-from google.protobuf import empty_pb2 as empty_proto
-
-from cert.async_subprocess_logger import AsyncSubprocessLogger
-from cert.logging_client_interceptor import LoggingClientInterceptor
-from cert.os_utils import get_gd_root
-from cert.os_utils import read_crash_snippet_and_log_tail
-from cert.os_utils import is_subprocess_alive
-from cert.os_utils import make_ports_available
-from cert.os_utils import TerminalColor
from facade import rootservice_pb2_grpc as facade_rootservice_pb2_grpc
-from hal import hal_facade_pb2_grpc
-from hci.facade import hci_facade_pb2_grpc
+from cert.gd_device_base import GdDeviceBase, GdDeviceConfigError, replace_vars
+from hal import facade_pb2_grpc as hal_facade_pb2_grpc
+from hci.facade import facade_pb2_grpc as hci_facade_pb2_grpc
from hci.facade import acl_manager_facade_pb2_grpc
from hci.facade import controller_facade_pb2_grpc
from hci.facade import le_acl_manager_facade_pb2_grpc
from hci.facade import le_advertising_manager_facade_pb2_grpc
-from hci.facade import le_initiator_address_facade_pb2_grpc
from hci.facade import le_scanning_manager_facade_pb2_grpc
-from l2cap.classic import facade_pb2_grpc as l2cap_facade_pb2_grpc
-from l2cap.le import facade_pb2_grpc as l2cap_le_facade_pb2_grpc
-from iso import facade_pb2_grpc as iso_facade_pb2_grpc
from neighbor.facade import facade_pb2_grpc as neighbor_facade_pb2_grpc
+from l2cap.classic import facade_pb2_grpc as l2cap_facade_pb2_grpc
from security import facade_pb2_grpc as security_facade_pb2_grpc
-from shim.facade import facade_pb2_grpc as shim_facade_pb2_grpc
-MOBLY_CONTROLLER_CONFIG_NAME = "GdDevice"
+ACTS_CONTROLLER_CONFIG_NAME = "GdDevice"
ACTS_CONTROLLER_REFERENCE_NAME = "gd_devices"
def create(configs):
if not configs:
- raise Exception("Configuration is empty")
+ raise GdDeviceConfigError("Configuration is empty")
elif not isinstance(configs, list):
- raise Exception("Configuration should be a list")
+ raise GdDeviceConfigError("Configuration should be a list")
return get_instances_with_configs(configs)
def destroy(devices):
for device in devices:
try:
- device.teardown()
+ device.clean_up()
except:
- logging.exception("[%s] Failed to clean up properly due to" % device.label)
+ device.log.exception("Failed to clean up properly.")
def get_info(devices):
@@ -90,591 +58,43 @@ def get_instances_with_configs(configs):
devices = []
for config in configs:
resolved_cmd = []
- for arg in config["cmd"]:
- logging.debug(arg)
- resolved_cmd.append(replace_vars(arg, config))
- verbose_mode = bool(config.get('verbose_mode', False))
- if config.get("serial_number"):
- device = GdAndroidDevice(config["grpc_port"], config["grpc_root_server_port"], config["signal_port"],
- resolved_cmd, config["label"], MOBLY_CONTROLLER_CONFIG_NAME, config["name"],
- config["serial_number"], verbose_mode)
- else:
- device = GdHostOnlyDevice(config["grpc_port"], config["grpc_root_server_port"], config["signal_port"],
- resolved_cmd, config["label"], MOBLY_CONTROLLER_CONFIG_NAME, config["name"],
- verbose_mode)
- device.setup()
- devices.append(device)
+ for entry in config["cmd"]:
+ logging.debug(entry)
+ resolved_cmd.append(replace_vars(entry, config))
+ devices.append(
+ GdDevice(config["grpc_port"], config["grpc_root_server_port"],
+ config["signal_port"], resolved_cmd, config["label"],
+ config.get("serial_number", "")))
return devices
-def replace_vars(string, config):
- serial_number = config.get("serial_number")
- if serial_number is None:
- serial_number = ""
- rootcanal_port = config.get("rootcanal_port")
- if rootcanal_port is None:
- rootcanal_port = ""
- if serial_number == "DUT" or serial_number == "CERT":
- raise Exception("Did you forget to configure the serial number?")
- return string.replace("$GD_ROOT", get_gd_root()) \
- .replace("$(grpc_port)", config.get("grpc_port")) \
- .replace("$(grpc_root_server_port)", config.get("grpc_root_server_port")) \
- .replace("$(rootcanal_port)", rootcanal_port) \
- .replace("$(signal_port)", config.get("signal_port")) \
- .replace("$(serial_number)", serial_number)
-
-
-class GdDeviceBase(ABC):
- """
- Base GD device class that covers common traits which assumes that the
- device must be driven by a driver-like backing process that takes following
- command line arguments:
- --grpc-port: main entry port for facade services
- --root-server-port: management port for starting and stopping services
- --btsnoop: path to btsnoop HCI log
- --signal-port: signaling port to indicate that backing process is started
- --rootcanal-port: root-canal HCI port, optional
- """
-
- WAIT_CHANNEL_READY_TIMEOUT_SECONDS = 10
-
- def __init__(self, grpc_port: str, grpc_root_server_port: str, signal_port: str, cmd: List[str], label: str,
- type_identifier: str, name: str, verbose_mode: bool):
- """Base GD device, common traits for both device based and host only GD
- cert tests
- :param grpc_port: main gRPC service port
- :param grpc_root_server_port: gRPC root server port
- :param signal_port: signaling port for backing process start up
- :param cmd: list of arguments to run in backing process
- :param label: device label used in logs
- :param type_identifier: device type identifier used in logs
- :param name: name of device used in logs
- """
- # Must be at the first line of __init__ method
- values = locals()
- arguments = [values[arg] for arg in inspect.getfullargspec(GdDeviceBase.__init__).args if arg != "verbose_mode"]
- asserts.assert_true(all(arguments), "All arguments to GdDeviceBase must not be None nor empty")
- asserts.assert_true(all(cmd), "cmd list should not have None nor empty component")
- self.verbose_mode = verbose_mode
- self.grpc_root_server_port = int(grpc_root_server_port)
- self.grpc_port = int(grpc_port)
- self.signal_port = int(signal_port)
- self.name = name
- self.type_identifier = type_identifier
- self.label = label
- # logging.log_path only exists when this is used in an ACTS test run.
- self.log_path_base = get_current_context().get_full_output_path()
- self.test_runner_base_path = \
- get_current_context().get_base_output_path()
- self.backing_process_log_path = os.path.join(self.log_path_base,
- '%s_%s_backing_logs.txt' % (self.type_identifier, self.label))
- if "--btsnoop=" not in " ".join(cmd):
- cmd.append("--btsnoop=%s" % os.path.join(self.log_path_base, '%s_btsnoop_hci.log' % self.label))
- if "--btsnooz=" not in " ".join(cmd):
- cmd.append("--btsnooz=%s" % os.path.join(self.log_path_base, '%s_btsnooz_hci.log' % self.label))
- if "--btconfig=" not in " ".join(cmd):
- cmd.append("--btconfig=%s" % os.path.join(self.log_path_base, '%s_bt_config.conf' % self.label))
- self.cmd = cmd
- self.environment = os.environ.copy()
- if "cert" in self.label:
- self.terminal_color = TerminalColor.BLUE
- else:
- self.terminal_color = TerminalColor.YELLOW
-
- def setup(self):
- """Set up this device for test, must run before using this device
- - After calling this, teardown() must be called when test finishes
- - Should be executed after children classes' setup() methods
- :return:
- """
- # Ensure signal port is available
- # signal port is the only port that always listen on the host machine
- asserts.assert_true(
- make_ports_available([self.signal_port]), "[%s] Failed to make signal port available" % self.label)
- # Start backing process
- with socket.socket(socket.AF_INET, socket.SOCK_STREAM) as signal_socket:
- # Setup signaling socket
- signal_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
- signal_socket.bind(("localhost", self.signal_port))
- signal_socket.listen(1)
- signal_socket.settimeout(300) # 5 minute timeout for blocking socket operations
+class GdDevice(GdDeviceBase):
- # Start backing process
- logging.debug("Running %s" % " ".join(self.cmd))
- self.backing_process = subprocess.Popen(
- self.cmd,
- cwd=get_gd_root(),
- env=self.environment,
- stdout=subprocess.PIPE,
- stderr=subprocess.STDOUT,
- universal_newlines=True)
- asserts.assert_true(self.backing_process, msg="Cannot start backing_process at " + " ".join(self.cmd))
- asserts.assert_true(
- is_subprocess_alive(self.backing_process),
- msg="backing_process stopped immediately after running " + " ".join(self.cmd))
+ def __init__(self, grpc_port, grpc_root_server_port, signal_port, cmd,
+ label, serial_number):
+ super().__init__(grpc_port, grpc_root_server_port, signal_port, cmd,
+ label, ACTS_CONTROLLER_CONFIG_NAME, serial_number)
- # Wait for process to be ready
- logging.debug("Waiting for backing_process accept.")
- signal_socket.accept()
-
- self.backing_process_logger = AsyncSubprocessLogger(
- self.backing_process, [self.backing_process_log_path],
- log_to_stdout=self.verbose_mode,
- tag=self.label,
- color=self.terminal_color)
-
- # Setup gRPC management channels
- self.grpc_root_server_channel = grpc.insecure_channel("localhost:%d" % self.grpc_root_server_port)
- self.grpc_channel = grpc.insecure_channel("localhost:%d" % self.grpc_port)
-
- if self.verbose_mode:
- self.grpc_channel = grpc.intercept_channel(self.grpc_channel, LoggingClientInterceptor(self.label))
-
- # Establish services from facades
- self.rootservice = facade_rootservice_pb2_grpc.RootFacadeStub(self.grpc_root_server_channel)
+ # Facade stubs
+ self.rootservice = facade_rootservice_pb2_grpc.RootFacadeStub(
+ self.grpc_root_server_channel)
self.hal = hal_facade_pb2_grpc.HciHalFacadeStub(self.grpc_channel)
- self.controller_read_only_property = facade_rootservice_pb2_grpc.ReadOnlyPropertyStub(self.grpc_channel)
- self.hci = hci_facade_pb2_grpc.HciFacadeStub(self.grpc_channel)
- self.l2cap = l2cap_facade_pb2_grpc.L2capClassicModuleFacadeStub(self.grpc_channel)
- self.l2cap_le = l2cap_le_facade_pb2_grpc.L2capLeModuleFacadeStub(self.grpc_channel)
- self.iso = iso_facade_pb2_grpc.IsoModuleFacadeStub(self.grpc_channel)
- self.hci_acl_manager = acl_manager_facade_pb2_grpc.AclManagerFacadeStub(self.grpc_channel)
- self.hci_le_acl_manager = le_acl_manager_facade_pb2_grpc.LeAclManagerFacadeStub(self.grpc_channel)
- self.hci_le_initiator_address = le_initiator_address_facade_pb2_grpc.LeInitiatorAddressFacadeStub(
+ self.controller_read_only_property = facade_rootservice_pb2_grpc.ReadOnlyPropertyStub(
+ self.grpc_channel)
+ self.hci = hci_facade_pb2_grpc.HciLayerFacadeStub(self.grpc_channel)
+ self.l2cap = l2cap_facade_pb2_grpc.L2capClassicModuleFacadeStub(
+ self.grpc_channel)
+ self.hci_acl_manager = acl_manager_facade_pb2_grpc.AclManagerFacadeStub(
+ self.grpc_channel)
+ self.hci_le_acl_manager = le_acl_manager_facade_pb2_grpc.LeAclManagerFacadeStub(
+ self.grpc_channel)
+ self.hci_controller = controller_facade_pb2_grpc.ControllerFacadeStub(
self.grpc_channel)
- self.hci_controller = controller_facade_pb2_grpc.ControllerFacadeStub(self.grpc_channel)
- self.hci_controller.GetMacAddressSimple = lambda: self.hci_controller.GetMacAddress(empty_proto.Empty()).address
- self.hci_controller.GetLocalNameSimple = lambda: self.hci_controller.GetLocalName(empty_proto.Empty()).name
self.hci_le_advertising_manager = le_advertising_manager_facade_pb2_grpc.LeAdvertisingManagerFacadeStub(
self.grpc_channel)
self.hci_le_scanning_manager = le_scanning_manager_facade_pb2_grpc.LeScanningManagerFacadeStub(
self.grpc_channel)
- self.neighbor = neighbor_facade_pb2_grpc.NeighborFacadeStub(self.grpc_channel)
- self.security = security_facade_pb2_grpc.SecurityModuleFacadeStub(self.grpc_channel)
- self.shim = shim_facade_pb2_grpc.ShimFacadeStub(self.grpc_channel)
-
- def get_crash_snippet_and_log_tail(self):
- if is_subprocess_alive(self.backing_process):
- return None, None
-
- return read_crash_snippet_and_log_tail(self.backing_process_log_path)
-
- def teardown(self):
- """Tear down this device and clean up any resources.
- - Must be called after setup()
- - Should be executed before children classes' teardown()
- :return:
- """
- self.grpc_channel.close()
- self.grpc_root_server_channel.close()
- stop_signal = signal.SIGINT
- self.backing_process.send_signal(stop_signal)
- try:
- return_code = self.backing_process.wait(timeout=self.WAIT_CHANNEL_READY_TIMEOUT_SECONDS)
- except subprocess.TimeoutExpired:
- logging.error("[%s] Failed to interrupt backing process via SIGINT, sending SIGKILL" % self.label)
- stop_signal = signal.SIGKILL
- self.backing_process.kill()
- try:
- return_code = self.backing_process.wait(timeout=self.WAIT_CHANNEL_READY_TIMEOUT_SECONDS)
- except subprocess.TimeoutExpired:
- logging.error("Failed to kill backing process")
- return_code = -65536
- if return_code not in [-stop_signal, 0]:
- logging.error("backing process %s stopped with code: %d" % (self.label, return_code))
- self.backing_process_logger.stop()
-
- def wait_channel_ready(self):
- future = grpc.channel_ready_future(self.grpc_channel)
- try:
- future.result(timeout=self.WAIT_CHANNEL_READY_TIMEOUT_SECONDS)
- except grpc.FutureTimeoutError:
- asserts.fail("[%s] wait channel ready timeout" % self.label)
-
-
-class GdHostOnlyDevice(GdDeviceBase):
- """
- Host only device where the backing process is running on the host machine
- """
-
- def __init__(self, grpc_port: str, grpc_root_server_port: str, signal_port: str, cmd: List[str], label: str,
- type_identifier: str, name: str, verbose_mode: bool):
- super().__init__(grpc_port, grpc_root_server_port, signal_port, cmd, label, MOBLY_CONTROLLER_CONFIG_NAME, name,
- verbose_mode)
- # Enable LLVM code coverage output for host only tests
- self.backing_process_profraw_path = pathlib.Path(self.log_path_base).joinpath(
- "%s_%s_backing_coverage.profraw" % (self.type_identifier, self.label))
- self.environment["LLVM_PROFILE_FILE"] = str(self.backing_process_profraw_path)
- llvm_binutils = pathlib.Path(get_gd_root()).joinpath("llvm_binutils").joinpath("bin")
- llvm_symbolizer = llvm_binutils.joinpath("llvm-symbolizer")
- if llvm_symbolizer.is_file():
- self.environment["ASAN_SYMBOLIZER_PATH"] = llvm_symbolizer
- else:
- logging.warning("[%s] Cannot find LLVM symbolizer at %s" % (self.label, str(llvm_symbolizer)))
-
- def teardown(self):
- super().teardown()
- self.generate_coverage_report()
-
- def generate_coverage_report(self):
- if not self.backing_process_profraw_path.is_file():
- logging.info("[%s] Skip coverage report as there is no profraw file at %s" %
- (self.label, str(self.backing_process_profraw_path)))
- return
- try:
- if self.backing_process_profraw_path.stat().st_size <= 0:
- logging.info("[%s] Skip coverage report as profraw file is empty at %s" %
- (self.label, str(self.backing_process_profraw_path)))
- return
- except OSError:
- logging.info("[%s] Skip coverage report as profraw file is inaccessible at %s" %
- (self.label, str(self.backing_process_profraw_path)))
- return
- llvm_binutils = pathlib.Path(get_gd_root()).joinpath("llvm_binutils").joinpath("bin")
- llvm_profdata = llvm_binutils.joinpath("llvm-profdata")
- if not llvm_profdata.is_file():
- logging.info(
- "[%s] Skip coverage report as llvm-profdata is not found at %s" % (self.label, str(llvm_profdata)))
- return
- llvm_cov = llvm_binutils.joinpath("llvm-cov")
- if not llvm_cov.is_file():
- logging.info("[%s] Skip coverage report as llvm-cov is not found at %s" % (self.label, str(llvm_cov)))
- return
- logging.info("[%s] Generating coverage report" % self.label)
- profdata_path = pathlib.Path(self.test_runner_base_path).joinpath(
- "%s_%s_backing_process_coverage.profdata" % (self.type_identifier, self.label))
- profdata_path_tmp = pathlib.Path(self.test_runner_base_path).joinpath(
- "%s_%s_backing_process_coverage_tmp.profdata" % (self.type_identifier, self.label))
- # Merge with existing profdata if possible
- profdata_cmd = [str(llvm_profdata), "merge", "-sparse", str(self.backing_process_profraw_path)]
- if profdata_path.is_file():
- profdata_cmd.append(str(profdata_path))
- profdata_cmd += ["-o", str(profdata_path_tmp)]
- result = subprocess.run(profdata_cmd, stdout=subprocess.PIPE, stderr=subprocess.STDOUT)
- if result.returncode != 0:
- logging.warning("[%s] Failed to index profdata, cmd result: %r" % (self.label, result))
- profdata_path.unlink(missing_ok=True)
- return
- shutil.move(profdata_path_tmp, profdata_path)
- coverage_result_path = pathlib.Path(self.test_runner_base_path).joinpath(
- "%s_%s_backing_process_coverage.json" % (self.type_identifier, self.label))
- with coverage_result_path.open("w") as coverage_result_file:
- result = subprocess.run(
- [str(llvm_cov), "export", "--format=text", "--instr-profile", profdata_path, self.cmd[0]],
- stderr=subprocess.PIPE,
- stdout=coverage_result_file,
- cwd=os.path.join(get_gd_root()))
- if result.returncode != 0:
- logging.warning("[%s] Failed to generated coverage report, cmd result: %r" % (self.label, result))
- coverage_result_path.unlink(missing_ok=True)
- return
- coverage_summary_path = pathlib.Path(self.test_runner_base_path).joinpath(
- "%s_%s_backing_process_coverage_summary.txt" % (self.type_identifier, self.label))
- with coverage_summary_path.open("w") as coverage_summary_file:
- result = subprocess.run(
- [llvm_cov, "report", "--instr-profile", profdata_path, self.cmd[0]],
- stderr=subprocess.PIPE,
- stdout=coverage_summary_file,
- cwd=os.path.join(get_gd_root()))
- if result.returncode != 0:
- logging.warning("[%s] Failed to generated coverage summary, cmd result: %r" % (self.label, result))
- coverage_summary_path.unlink(missing_ok=True)
-
- def setup(self):
- # Ensure ports are available
- # Only check on host only test, for Android devices, these ports will
- # be opened on Android device and host machine ports will be occupied
- # by sshd or adb forwarding
- asserts.assert_true(
- make_ports_available((self.grpc_port, self.grpc_root_server_port)),
- "[%s] Failed to make backing process ports available" % self.label)
- super().setup()
-
-
-class GdAndroidDevice(GdDeviceBase):
- """Real Android device where the backing process is running on it
- """
-
- WAIT_FOR_DEVICE_TIMEOUT_SECONDS = 180
-
- def __init__(self, grpc_port: str, grpc_root_server_port: str, signal_port: str, cmd: List[str], label: str,
- type_identifier: str, name: str, serial_number: str, verbose_mode: bool):
- super().__init__(grpc_port, grpc_root_server_port, signal_port, cmd, label, type_identifier, name, verbose_mode)
- asserts.assert_true(serial_number, "serial_number must not be None nor empty")
- self.serial_number = serial_number
- self.adb = AdbProxy(serial_number)
-
- def setup(self):
- logging.info("Setting up device %s %s" % (self.label, self.serial_number))
- asserts.assert_true(self.adb.ensure_root(), "device %s cannot run as root", self.serial_number)
-
- # Try freeing ports and ignore results
- self.cleanup_port_forwarding()
- self.sync_device_time()
-
- # Set up port forwarding or reverse or die
- self.tcp_forward_or_die(self.grpc_port, self.grpc_port)
- self.tcp_forward_or_die(self.grpc_root_server_port, self.grpc_root_server_port)
- self.tcp_reverse_or_die(self.signal_port, self.signal_port)
-
- # Push test binaries
- self.ensure_verity_disabled()
- self.push_or_die(os.path.join(get_gd_root(), "target", "bluetooth_stack_with_facade"), "system/bin")
- self.push_or_die(os.path.join(get_gd_root(), "target", "libbluetooth_gd.so"), "system/lib64")
- self.push_or_die(os.path.join(get_gd_root(), "target", "libgrpc++_unsecure.so"), "system/lib64")
-
- try:
- self.adb.shell("rm /data/misc/bluetooth/logs/btsnoop_hci.log")
- except AdbCommandError as error:
- logging.error("Error during setup: " + str(error))
-
- try:
- self.adb.shell("rm /data/misc/bluetooth/logs/btsnooz_hci.log")
- except AdbCommandError as error:
- logging.error("Error during setup: " + str(error))
-
- try:
- self.adb.shell("rm /data/misc/bluedroid/bt_config.conf")
- except AdbCommandError as error:
- logging.error("Error during setup: " + str(error))
-
- try:
- self.adb.shell("rm /data/misc/bluedroid/bt_config.bak")
- except AdbCommandError as error:
- logging.error("Error during setup: " + str(error))
-
- self.ensure_no_output(self.adb.shell("svc bluetooth disable"))
-
- # Start logcat logging
- self.logcat_output_path = os.path.join(
- self.log_path_base, '%s_%s_%s_logcat_logs.txt' % (self.type_identifier, self.label, self.serial_number))
- self.logcat_cmd = ["adb", "-s", self.serial_number, "logcat", "-T", "1", "-v", "year", "-v", "uid"]
- logging.debug("Running %s", " ".join(self.logcat_cmd))
- self.logcat_process = subprocess.Popen(
- self.logcat_cmd, stdout=subprocess.PIPE, stderr=subprocess.STDOUT, universal_newlines=True)
- asserts.assert_true(self.logcat_process, msg="Cannot start logcat_process at " + " ".join(self.logcat_cmd))
- asserts.assert_true(
- is_subprocess_alive(self.logcat_process),
- msg="logcat_process stopped immediately after running " + " ".join(self.logcat_cmd))
- self.logcat_logger = AsyncSubprocessLogger(
- self.logcat_process, [self.logcat_output_path],
- log_to_stdout=self.verbose_mode,
- tag="%s_%s" % (self.label, self.serial_number),
- color=self.terminal_color)
-
- # Done run parent setup
- logging.info("Done preparation for %s, starting backing process" % self.serial_number)
- super().setup()
-
- def teardown(self):
- super().teardown()
- stop_signal = signal.SIGINT
- self.logcat_process.send_signal(stop_signal)
- try:
- return_code = self.logcat_process.wait(timeout=self.WAIT_CHANNEL_READY_TIMEOUT_SECONDS)
- except subprocess.TimeoutExpired:
- logging.error("[%s_%s] Failed to interrupt logcat process via SIGINT, sending SIGKILL" %
- (self.label, self.serial_number))
- stop_signal = signal.SIGKILL
- self.logcat_process.kill()
- try:
- return_code = self.logcat_process.wait(timeout=self.WAIT_CHANNEL_READY_TIMEOUT_SECONDS)
- except subprocess.TimeoutExpired:
- logging.error("Failed to kill logcat_process %s %s" % (self.label, self.serial_number))
- return_code = -65536
- if return_code not in [-stop_signal, 0]:
- logging.error("logcat_process %s_%s stopped with code: %d" % (self.label, self.serial_number, return_code))
- self.logcat_logger.stop()
- self.cleanup_port_forwarding()
- self.adb.pull("/data/misc/bluetooth/logs/btsnoop_hci.log %s" % os.path.join(self.log_path_base,
- "%s_btsnoop_hci.log" % self.label))
- self.adb.pull("/data/misc/bluedroid/bt_config.conf %s" % os.path.join(self.log_path_base,
- "%s_bt_config.conf" % self.label))
- self.adb.pull(
- "/data/misc/bluedroid/bt_config.bak %s" % os.path.join(self.log_path_base, "%s_bt_config.bak" % self.label))
-
- def cleanup_port_forwarding(self):
- try:
- self.adb.remove_tcp_forward(self.grpc_port)
- except AdbError as error:
- logging.error("Error during port forwarding cleanup: " + str(error))
-
- try:
- self.adb.remove_tcp_forward(self.grpc_root_server_port)
- except AdbError as error:
- logging.error("Error during port forwarding cleanup: " + str(error))
-
- try:
- self.adb.reverse("--remove tcp:%d" % self.signal_port)
- except AdbError as error:
- logging.error("Error during port forwarding cleanup: " + str(error))
-
- @staticmethod
- def ensure_no_output(result):
- """
- Ensure a command has not output
- """
- asserts.assert_true(
- result is None or len(result) == 0, msg="command returned something when it shouldn't: %s" % result)
-
- def sync_device_time(self):
- self.adb.shell("settings put global auto_time 0")
- self.adb.shell("settings put global auto_time_zone 0")
- device_tz = self.adb.shell("date +%z")
- asserts.assert_true(device_tz, "date +%z must return device timezone, "
- "but returned {} instead".format(device_tz))
- host_tz = time.strftime("%z")
- if device_tz != host_tz:
- target_timezone = utils.get_timezone_olson_id()
- logging.debug("Device timezone %s does not match host timezone %s, "
- "syncing them by setting timezone to %s" % (device_tz, host_tz, target_timezone))
- self.adb.shell("setprop persist.sys.timezone %s" % target_timezone)
- self.reboot()
- device_tz = self.adb.shell("date +%z")
- asserts.assert_equal(
- host_tz, device_tz, "Device timezone %s still does not match host "
- "timezone %s after reset" % (device_tz, host_tz))
- self.adb.shell("date %s" % time.strftime("%m%d%H%M%Y.%S"))
- datetime_format = "%Y-%m-%dT%H:%M:%S%z"
- try:
- device_time = datetime.strptime(self.adb.shell("date +'%s'" % datetime_format), datetime_format)
- except ValueError:
- asserts.fail("Failed to get time after sync")
- return
- # Include ADB delay that might be longer in SSH environment
- max_delta_seconds = 3
- host_time = datetime.now(tz=device_time.tzinfo)
- asserts.assert_almost_equal(
- (device_time - host_time).total_seconds(),
- 0,
- msg="Device time %s and host time %s off by >%dms after sync" %
- (device_time.isoformat(), host_time.isoformat(), int(max_delta_seconds * 1000)),
- delta=max_delta_seconds)
-
- def push_or_die(self, src_file_path, dst_file_path, push_timeout=300):
- """Pushes a file to the Android device
-
- Args:
- src_file_path: The path to the file to install.
- dst_file_path: The destination of the file.
- push_timeout: How long to wait for the push to finish in seconds
- """
- out = self.adb.push('%s %s' % (src_file_path, dst_file_path), timeout=push_timeout)
- if 'error' in out:
- asserts.fail('Unable to push file %s to %s due to %s' % (src_file_path, dst_file_path, out))
-
- def tcp_forward_or_die(self, host_port, device_port, num_retry=1):
- """
- Forward a TCP port from host to device or fail
- :param host_port: host port, int, 0 for adb to assign one
- :param device_port: device port, int
- :param num_retry: number of times to reboot and retry this before dying
- :return: host port int
- """
- error_or_port = self.adb.tcp_forward(host_port, device_port)
- if not error_or_port:
- logging.debug("host port %d was already forwarded" % host_port)
- return host_port
- if not isinstance(error_or_port, int):
- if num_retry > 0:
- # If requested, reboot an retry
- num_retry -= 1
- logging.warning(
- "[%s] Failed to TCP forward host port %d to "
- "device port %d, num_retries left is %d" % (self.label, host_port, device_port, num_retry))
- self.reboot()
- return self.tcp_forward_or_die(host_port, device_port, num_retry=num_retry)
- asserts.fail(
- 'Unable to forward host port %d to device port %d, error %s' % (host_port, device_port, error_or_port))
- return error_or_port
-
- def tcp_reverse_or_die(self, device_port, host_port, num_retry=1):
- """
- Forward a TCP port from device to host or fail
- :param device_port: device port, int, 0 for adb to assign one
- :param host_port: host port, int
- :param num_retry: number of times to reboot and retry this before dying
- :return: device port int
- """
- error_or_port = self.adb.reverse("tcp:%d tcp:%d" % (device_port, host_port))
- if not error_or_port:
- logging.debug("device port %d was already reversed" % device_port)
- return device_port
- try:
- error_or_port = int(error_or_port)
- except ValueError:
- if num_retry > 0:
- # If requested, reboot an retry
- num_retry -= 1
- logging.warning(
- "[%s] Failed to TCP reverse device port %d to "
- "host port %d, num_retries left is %d" % (self.label, device_port, host_port, num_retry))
- self.reboot()
- return self.tcp_reverse_or_die(device_port, host_port, num_retry=num_retry)
- asserts.fail(
- 'Unable to reverse device port %d to host port %d, error %s' % (device_port, host_port, error_or_port))
- return error_or_port
-
- def ensure_verity_disabled(self):
- """Ensures that verity is enabled.
-
- If verity is not enabled, this call will reboot the phone. Note that
- this only works on debuggable builds.
- """
- logging.debug("Disabling verity and remount for %s", self.serial_number)
- # The below properties will only exist if verity has been enabled.
- system_verity = self.adb.getprop('partition.system.verified')
- vendor_verity = self.adb.getprop('partition.vendor.verified')
- if system_verity or vendor_verity:
- self.adb.disable_verity()
- self.reboot()
- self.adb.remount()
- self.adb.wait_for_device(timeout=self.WAIT_FOR_DEVICE_TIMEOUT_SECONDS)
-
- def reboot(self, timeout_minutes=15.0):
- """Reboots the device.
-
- Reboot the device, wait for device to complete booting.
- """
- logging.debug("Rebooting %s", self.serial_number)
- self.adb.reboot()
-
- timeout_start = time.time()
- timeout = timeout_minutes * 60
- # Android sometimes return early after `adb reboot` is called. This
- # means subsequent calls may make it to the device before the reboot
- # goes through, return false positives for getprops such as
- # sys.boot_completed.
- while time.time() < timeout_start + timeout:
- try:
- self.adb.get_state()
- time.sleep(.1)
- except AdbError:
- # get_state will raise an error if the device is not found. We
- # want the device to be missing to prove the device has kicked
- # off the reboot.
- break
- minutes_left = timeout_minutes - (time.time() - timeout_start) / 60.0
- self.wait_for_boot_completion(timeout_minutes=minutes_left)
- asserts.assert_true(self.adb.ensure_root(), "device %s cannot run as root after reboot", self.serial_number)
-
- def wait_for_boot_completion(self, timeout_minutes=15.0):
- """
- Waits for Android framework to broadcast ACTION_BOOT_COMPLETED.
- :param timeout_minutes: number of minutes to wait
- """
- timeout_start = time.time()
- timeout = timeout_minutes * 60
-
- self.adb.wait_for_device(timeout=self.WAIT_FOR_DEVICE_TIMEOUT_SECONDS)
- while time.time() < timeout_start + timeout:
- try:
- completed = self.adb.getprop("sys.boot_completed")
- if completed == '1':
- return
- except AdbError:
- # adb shell calls may fail during certain period of booting
- # process, which is normal. Ignoring these errors.
- pass
- time.sleep(5)
- asserts.fail(msg='Device %s booting process timed out.' % self.serial_number)
+ self.neighbor = neighbor_facade_pb2_grpc.NeighborFacadeStub(
+ self.grpc_channel)
+ self.security = security_facade_pb2_grpc.SecurityModuleFacadeStub(
+ self.grpc_channel)
diff --git a/gd/cert/gd_device_base.py b/gd/cert/gd_device_base.py
new file mode 100644
index 000000000..40301c405
--- /dev/null
+++ b/gd/cert/gd_device_base.py
@@ -0,0 +1,164 @@
+#!/usr/bin/env python3
+#
+# Copyright 2019 - The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+import logging
+import os
+from builtins import open
+import json
+import signal
+import socket
+import subprocess
+import time
+
+from acts import context, error, tracelogger
+from acts.controllers.adb import AdbProxy
+
+import grpc
+
+ANDROID_BUILD_TOP = os.environ.get('ANDROID_BUILD_TOP')
+ANDROID_HOST_OUT = os.environ.get('ANDROID_HOST_OUT')
+ANDROID_PRODUCT_OUT = os.environ.get('ANDROID_PRODUCT_OUT')
+WAIT_CHANNEL_READY_TIMEOUT = 10
+
+
+def replace_vars(string, config):
+ serial_number = config.get("serial_number")
+ if serial_number is None:
+ serial_number = ""
+ rootcanal_port = config.get("rootcanal_port")
+ if rootcanal_port is None:
+ rootcanal_port = ""
+ if serial_number == "DUT" or serial_number == "CERT":
+ raise Exception("Did you forget to configure the serial number?")
+ return string.replace("$ANDROID_HOST_OUT", ANDROID_HOST_OUT) \
+ .replace("$(grpc_port)", config.get("grpc_port")) \
+ .replace("$(grpc_root_server_port)", config.get("grpc_root_server_port")) \
+ .replace("$(rootcanal_port)", rootcanal_port) \
+ .replace("$(signal_port)", config.get("signal_port")) \
+ .replace("$(serial_number)", serial_number)
+
+
+class GdDeviceBase:
+
+ def __init__(self, grpc_port, grpc_root_server_port, signal_port, cmd,
+ label, type_identifier, serial_number):
+ self.label = label if label is not None else grpc_port
+ # logging.log_path only exists when this is used in an ACTS test run.
+ self.log_path_base = context.get_current_context().get_full_output_path(
+ )
+ self.log = tracelogger.TraceLogger(
+ GdDeviceBaseLoggerAdapter(logging.getLogger(), {
+ 'device': label,
+ 'type_identifier': type_identifier
+ }))
+
+ backing_process_logpath = os.path.join(
+ self.log_path_base,
+ '%s_%s_backing_logs.txt' % (type_identifier, label))
+ self.backing_process_logs = open(backing_process_logpath, 'w')
+
+ cmd_str = json.dumps(cmd)
+ if "--btsnoop=" not in cmd_str:
+ btsnoop_path = os.path.join(self.log_path_base,
+ '%s_btsnoop_hci.log' % label)
+ cmd.append("--btsnoop=" + btsnoop_path)
+
+ self.serial_number = serial_number
+ if self.serial_number:
+ self.ad = AdbProxy(serial_number)
+ self.ad.shell("date " + time.strftime("%m%d%H%M%Y.%S"))
+ self.ad.tcp_forward(int(grpc_port), int(grpc_port))
+ self.ad.tcp_forward(
+ int(grpc_root_server_port), int(grpc_root_server_port))
+ self.ad.reverse("tcp:%s tcp:%s" % (signal_port, signal_port))
+ self.ad.push(
+ os.path.join(ANDROID_PRODUCT_OUT,
+ "system/bin/bluetooth_stack_with_facade"),
+ "system/bin")
+ self.ad.push(
+ os.path.join(ANDROID_PRODUCT_OUT,
+ "system/lib64/libbluetooth_gd.so"), "system/lib64")
+ self.ad.push(
+ os.path.join(ANDROID_PRODUCT_OUT,
+ "system/lib64/libgrpc++_unsecure.so"),
+ "system/lib64")
+ self.ad.shell("logcat -c")
+ self.ad.shell("rm /data/misc/bluetooth/logs/btsnoop_hci.log")
+ self.ad.shell("svc bluetooth disable")
+
+ tester_signal_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
+ tester_signal_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR,
+ 1)
+ socket_address = ('localhost', int(signal_port))
+ tester_signal_socket.bind(socket_address)
+ tester_signal_socket.listen(1)
+
+ self.backing_process = subprocess.Popen(
+ cmd,
+ cwd=ANDROID_BUILD_TOP,
+ env=os.environ.copy(),
+ stdout=self.backing_process_logs,
+ stderr=self.backing_process_logs)
+ tester_signal_socket.accept()
+ tester_signal_socket.close()
+
+ self.grpc_root_server_channel = grpc.insecure_channel(
+ "localhost:" + grpc_root_server_port)
+ self.grpc_port = int(grpc_port)
+ self.grpc_channel = grpc.insecure_channel("localhost:" + grpc_port)
+
+ def clean_up(self):
+ self.grpc_channel.close()
+ self.grpc_root_server_channel.close()
+ stop_signal = signal.SIGINT
+ self.backing_process.send_signal(stop_signal)
+ backing_process_return_code = self.backing_process.wait()
+ self.backing_process_logs.close()
+ if backing_process_return_code not in [-stop_signal, 0]:
+ logging.error("backing process %s stopped with code: %d" %
+ (self.label, backing_process_return_code))
+
+ if self.serial_number:
+ self.ad.shell("logcat -d -f /data/misc/bluetooth/logs/system_log")
+ self.ad.pull(
+ "/data/misc/bluetooth/logs/btsnoop_hci.log %s" % os.path.join(
+ self.log_path_base, "%s_btsnoop_hci.log" % self.label))
+ self.ad.pull(
+ "/data/misc/bluetooth/logs/system_log %s" % os.path.join(
+ self.log_path_base, "%s_system_log" % self.label))
+
+ def wait_channel_ready(self):
+ future = grpc.channel_ready_future(self.grpc_channel)
+ try:
+ future.result(timeout=WAIT_CHANNEL_READY_TIMEOUT)
+ except grpc.FutureTimeoutError:
+ logging.error("wait channel ready timeout")
+
+
+class GdDeviceBaseLoggerAdapter(logging.LoggerAdapter):
+
+ def process(self, msg, kwargs):
+ msg = "[%s|%s] %s" % (self.extra["type_identifier"],
+ self.extra["device"], msg)
+ return (msg, kwargs)
+
+
+class GdDeviceConfigError(Exception):
+ """Raised when GdDevice configs are malformatted."""
+
+
+class GdDeviceError(error.ActsError):
+ """Raised when there is an error in GdDevice."""
diff --git a/gd/cert/gen_html_coverage.sh b/gd/cert/gen_html_coverage.sh
deleted file mode 100755
index bfb1edb3b..000000000
--- a/gd/cert/gen_html_coverage.sh
+++ /dev/null
@@ -1,10 +0,0 @@
-#!/bin/bash
-
-pushd $ANDROID_BUILD_TOP
-
-llvm-cov show --format=html --summary-only --show-line-counts-or-regions --show-instantiation-summary --instr-profile=/tmp/logs/HostOnlyCert/latest/GdDevice_dut_backing_process_coverage.profdata --output-dir=/tmp/logs/HostOnlyCert/latest/GdDevice_dut_backing_process_coverage/ out/dist/bluetooth_venv/lib/python3.8/site-packages/bluetooth_stack_with_facade
-
-popd
-
-echo "point your browser to file:///tmp/logs/HostOnlyCert/latest/GdDevice_dut_backing_process_coverage/index.html"
-
diff --git a/gd/cert/host_config.json b/gd/cert/host_config.json
deleted file mode 100644
index 5b24dc7bb..000000000
--- a/gd/cert/host_config.json
+++ /dev/null
@@ -1,50 +0,0 @@
-
-{ "_description": "Bluetooth cert testing",
- "testbed":
- [
- {
- "_description": "Host only cert testbed",
- "name": "HostOnlyCert",
- "rootcanal":
- {
- "test_port": "6401",
- "hci_port": "6402",
- "link_layer_port": "6403"
- },
- "GdDevice":
- [
- {
- "grpc_port": "8998",
- "grpc_root_server_port": "8996",
- "signal_port": "8994",
- "label": "cert",
- "name": "Cert Device",
- "cmd":
- [
- "$GD_ROOT/bluetooth_stack_with_facade",
- "--grpc-port=$(grpc_port)",
- "--root-server-port=$(grpc_root_server_port)",
- "--rootcanal-port=$(rootcanal_port)",
- "--signal-port=$(signal_port)"
- ]
- },
- {
- "grpc_port": "8999",
- "grpc_root_server_port": "8997",
- "signal_port": "8995",
- "label": "dut",
- "name": "DUT Device",
- "cmd":
- [
- "$GD_ROOT/bluetooth_stack_with_facade",
- "--grpc-port=$(grpc_port)",
- "--root-server-port=$(grpc_root_server_port)",
- "--rootcanal-port=$(rootcanal_port)",
- "--signal-port=$(signal_port)"
- ]
- }
- ]
- }
- ],
- "logpath": "/tmp/logs"
-}
diff --git a/gd/cert/rust_host_config.json b/gd/cert/host_only_config_facade_only.json
index 2972a53e8..9de9d7052 100644
--- a/gd/cert/rust_host_config.json
+++ b/gd/cert/host_only_config_facade_only.json
@@ -7,9 +7,9 @@
"name": "HostOnlyCert",
"rootcanal":
{
- "test_port": "6401",
- "hci_port": "6402",
- "link_layer_port": "6403"
+ "test_port": 6401,
+ "hci_port": 6402,
+ "link_layer_port": 6403
},
"GdDevice":
[
@@ -17,11 +17,10 @@
"grpc_port": "8998",
"grpc_root_server_port": "8996",
"signal_port": "8994",
- "label": "cert",
- "name": "Cert Device",
+ "label": "cert_stack",
"cmd":
[
- "$GD_ROOT/bluetooth_with_facades",
+ "$ANDROID_HOST_OUT/bin/bluetooth_stack_with_facade",
"--grpc-port=$(grpc_port)",
"--root-server-port=$(grpc_root_server_port)",
"--rootcanal-port=$(rootcanal_port)",
@@ -32,11 +31,10 @@
"grpc_port": "8999",
"grpc_root_server_port": "8997",
"signal_port": "8995",
- "label": "dut",
- "name": "DUT Device",
+ "label": "stack_under_test",
"cmd":
[
- "$GD_ROOT/bluetooth_with_facades",
+ "$ANDROID_HOST_OUT/bin/bluetooth_stack_with_facade",
"--grpc-port=$(grpc_port)",
"--root-server-port=$(grpc_root_server_port)",
"--rootcanal-port=$(rootcanal_port)",
diff --git a/gd/cert/irun b/gd/cert/irun
deleted file mode 100755
index 30ab8778e..000000000
--- a/gd/cert/irun
+++ /dev/null
@@ -1,10 +0,0 @@
-#! /bin/bash
-# interactive version of run
-
-trap "exit;" SIGINT SIGTERM
-
-while true
-do
- ${ANDROID_BUILD_TOP}/system/bt/gd/cert/run "$@"
- python3 ${ANDROID_BUILD_TOP}/system/bt/gd/cert/change_waiter.py ${ANDROID_BUILD_TOP}/system/bt
-done
diff --git a/gd/cert/logging_client_interceptor.py b/gd/cert/logging_client_interceptor.py
deleted file mode 100644
index 5ab714962..000000000
--- a/gd/cert/logging_client_interceptor.py
+++ /dev/null
@@ -1,86 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import grpc
-import re
-
-from facade import common_pb2 as common
-from google.protobuf import text_format
-
-
-def custom_message_formatter(m, ident, as_one_line):
- if m.DESCRIPTOR == common.Data.DESCRIPTOR:
- return 'payload: (hex) "{}"'.format(m.payload.hex(" "))
- return None
-
-
-def pretty_print(request):
- return '{} {}'.format(
- type(request).__name__,
- text_format.MessageToString(request, as_one_line=True, message_formatter=custom_message_formatter))
-
-
-class LoggingRandezvousWrapper():
-
- def __init__(self, server_stream_call, logTag):
- if server_stream_call is None:
- raise ValueError("server_stream_call cannot be None")
- self.server_stream_call = server_stream_call
- self.logTag = logTag
-
- def cancel(self):
- self.server_stream_call.cancel()
-
- def cancelled(self):
- return self.server_stream_call.cancelled()
-
- def __iter__(self):
- return self
-
- def __next__(self):
- resp = self.server_stream_call.__next__()
- print("%s %s" % (self.logTag, pretty_print(resp)))
- return resp
-
-
-class LoggingClientInterceptor(grpc.UnaryUnaryClientInterceptor, grpc.UnaryStreamClientInterceptor):
-
- TAG_MIN_WIDTH = 24
-
- def __init__(self, name):
- self.name = name
- self.inLogTag = "[host ▶▶▶▶▶ %s]" % self.name
- self.outLogTag = "[host ◀◀◀◀◀ %s]" % self.name
- tagLength = len(re.sub('[^\w\s]', '', self.inLogTag)) + 11
- if tagLength < self.TAG_MIN_WIDTH:
- self.inLogTag += " " * (self.TAG_MIN_WIDTH - tagLength)
- self.outLogTag += " " * (self.TAG_MIN_WIDTH - tagLength)
-
- def intercept_unary_unary(self, continuation, client_call_details, request):
- """
- This interceptor logs the requests from host
- """
- print("%s%s %s" % (self.inLogTag, client_call_details.method, pretty_print(request)))
- return continuation(client_call_details, request)
-
- def intercept_unary_stream(self, continuation, client_call_details, request):
- """
- This interceptor wraps the server response, and logs all the messages coming to host
- """
- print("%s%s %s" % (self.inLogTag, client_call_details.method, pretty_print(request)))
- server_stream_call = continuation(client_call_details, request)
- retuningMsgLogTag = self.outLogTag + client_call_details.method
- return LoggingRandezvousWrapper(server_stream_call, retuningMsgLogTag)
diff --git a/gd/cert/matchers.py b/gd/cert/matchers.py
deleted file mode 100644
index 5d8fa1f8f..000000000
--- a/gd/cert/matchers.py
+++ /dev/null
@@ -1,729 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import logging
-import bluetooth_packets_python3 as bt_packets
-import logging
-
-from bluetooth_packets_python3 import hci_packets
-from bluetooth_packets_python3.hci_packets import EventCode
-from bluetooth_packets_python3 import l2cap_packets
-from bluetooth_packets_python3.l2cap_packets import CommandCode, LeCommandCode
-from bluetooth_packets_python3.l2cap_packets import ConfigurationResponseResult
-from bluetooth_packets_python3.l2cap_packets import ConnectionResponseResult
-from bluetooth_packets_python3.l2cap_packets import InformationRequestInfoType
-from bluetooth_packets_python3.l2cap_packets import LeCreditBasedConnectionResponseResult
-
-
-class HciMatchers(object):
-
- @staticmethod
- def CommandComplete(opcode):
- return lambda msg: HciMatchers._is_matching_command_complete(msg.payload, opcode)
-
- @staticmethod
- def ExtractMatchingCommandComplete(packet_bytes, opcode=None):
- return HciMatchers._extract_matching_command_complete(packet_bytes, opcode)
-
- @staticmethod
- def _is_matching_command_complete(packet_bytes, opcode=None):
- return HciMatchers._extract_matching_command_complete(packet_bytes, opcode) is not None
-
- @staticmethod
- def _extract_matching_command_complete(packet_bytes, opcode=None):
- event = HciMatchers._extract_matching_event(packet_bytes, EventCode.COMMAND_COMPLETE)
- if event is None:
- return None
- complete = hci_packets.CommandCompleteView(event)
- if opcode is None or complete is None:
- return complete
- else:
- if complete.GetCommandOpCode() != opcode:
- return None
- else:
- return complete
-
- @staticmethod
- def CommandStatus(opcode=None):
- return lambda msg: HciMatchers._is_matching_command_status(msg.payload, opcode)
-
- @staticmethod
- def ExtractMatchingCommandStatus(packet_bytes, opcode=None):
- return HciMatchers._extract_matching_command_complete(packet_bytes, opcode)
-
- @staticmethod
- def _is_matching_command_status(packet_bytes, opcode=None):
- return HciMatchers._extract_matching_command_status(packet_bytes, opcode) is not None
-
- @staticmethod
- def _extract_matching_command_status(packet_bytes, opcode=None):
- event = HciMatchers._extract_matching_event(packet_bytes, EventCode.COMMAND_STATUS)
- if event is None:
- return None
- complete = hci_packets.CommandStatusView(event)
- if opcode is None or complete is None:
- return complete
- else:
- if complete.GetCommandOpCode() != opcode:
- return None
- else:
- return complete
-
- @staticmethod
- def EventWithCode(event_code):
- return lambda msg: HciMatchers._is_matching_event(msg.payload, event_code)
-
- @staticmethod
- def ExtractEventWithCode(packet_bytes, event_code):
- return HciMatchers._extract_matching_event(packet_bytes, event_code)
-
- @staticmethod
- def _is_matching_event(packet_bytes, event_code):
- return HciMatchers._extract_matching_event(packet_bytes, event_code) is not None
-
- @staticmethod
- def _extract_matching_event(packet_bytes, event_code):
- event = hci_packets.EventView(bt_packets.PacketViewLittleEndian(list(packet_bytes)))
- if event is None:
- return None
- if event_code is not None and event.GetEventCode() != event_code:
- return None
- return event
-
- @staticmethod
- def LeEventWithCode(subevent_code):
- return lambda msg: HciMatchers._extract_matching_le_event(msg.payload, subevent_code) is not None
-
- @staticmethod
- def ExtractLeEventWithCode(packet_bytes, subevent_code):
- return HciMatchers._extract_matching_le_event(packet_bytes, subevent_code)
-
- @staticmethod
- def _extract_matching_le_event(packet_bytes, subevent_code):
- inner_event = HciMatchers._extract_matching_event(packet_bytes, hci_packets.EventCode.LE_META_EVENT)
- if inner_event is None:
- return None
- event = hci_packets.LeMetaEventView(inner_event)
- if event.GetSubeventCode() != subevent_code:
- return None
- return event
-
- @staticmethod
- def LeConnectionComplete():
- return lambda msg: HciMatchers._extract_le_connection_complete(msg.payload) is not None
-
- @staticmethod
- def ExtractLeConnectionComplete(packet_bytes):
- return HciMatchers._extract_le_connection_complete(packet_bytes)
-
- @staticmethod
- def _extract_le_connection_complete(packet_bytes):
- inner_event = HciMatchers._extract_matching_le_event(packet_bytes, hci_packets.SubeventCode.CONNECTION_COMPLETE)
- if inner_event is not None:
- return hci_packets.LeConnectionCompleteView(inner_event)
-
- inner_event = HciMatchers._extract_matching_le_event(packet_bytes,
- hci_packets.SubeventCode.ENHANCED_CONNECTION_COMPLETE)
- if inner_event is not None:
- return hci_packets.LeEnhancedConnectionCompleteView(inner_event)
-
- return None
-
- @staticmethod
- def LogEventCode():
- return lambda event: logging.info("Received event: %x" % hci_packets.EventView(bt_packets.PacketViewLittleEndian(list(event.payload))).GetEventCode())
-
- @staticmethod
- def LinkKeyRequest():
- return lambda event: HciMatchers.EventWithCode(EventCode.LINK_KEY_REQUEST)
-
- @staticmethod
- def IoCapabilityRequest():
- return lambda event: HciMatchers.EventWithCode(EventCode.IO_CAPABILITY_REQUEST)
-
- @staticmethod
- def IoCapabilityResponse():
- return lambda event: HciMatchers.EventWithCode(EventCode.IO_CAPABILITY_RESPONSE)
-
- @staticmethod
- def UserPasskeyNotification():
- return lambda event: HciMatchers.EventWithCode(EventCode.USER_PASSKEY_NOTIFICATION)
-
- @staticmethod
- def UserPasskeyRequest():
- return lambda event: HciMatchers.EventWithCode(EventCode.USER_PASSKEY_REQUEST)
-
- @staticmethod
- def UserConfirmationRequest():
- return lambda event: HciMatchers.EventWithCode(EventCode.USER_CONFIRMATION_REQUEST)
-
- @staticmethod
- def RemoteHostSupportedFeaturesNotification():
- return lambda event: HciMatchers.EventWithCode(EventCode.REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION)
-
- @staticmethod
- def LinkKeyNotification():
- return lambda event: HciMatchers.EventWithCode(EventCode.LINK_KEY_NOTIFICATION)
-
- @staticmethod
- def SimplePairingComplete():
- return lambda event: HciMatchers.EventWithCode(EventCode.SIMPLE_PAIRING_COMPLETE)
-
- @staticmethod
- def Disconnect():
- return lambda event: HciMatchers.EventWithCode(EventCode.DISCONNECT)
-
- @staticmethod
- def DisconnectionComplete():
- return lambda event: HciMatchers.EventWithCode(EventCode.DISCONNECTION_COMPLETE)
-
- @staticmethod
- def RemoteOobDataRequest():
- return lambda event: HciMatchers.EventWithCode(EventCode.REMOTE_OOB_DATA_REQUEST)
-
- @staticmethod
- def PinCodeRequest():
- return lambda event: HciMatchers.EventWithCode(EventCode.PIN_CODE_REQUEST)
-
- @staticmethod
- def LoopbackOf(packet):
- return HciMatchers.Exactly(hci_packets.LoopbackCommandBuilder(packet))
-
- @staticmethod
- def Exactly(packet):
- data = bytes(packet.Serialize())
- return lambda event: data == event.payload
-
-
-class NeighborMatchers(object):
-
- @staticmethod
- def InquiryResult(address):
- return lambda msg: NeighborMatchers._is_matching_inquiry_result(msg.packet, address)
-
- @staticmethod
- def _is_matching_inquiry_result(packet, address):
- hci_event = HciMatchers.ExtractEventWithCode(packet, EventCode.INQUIRY_RESULT)
- if hci_event is None:
- return False
- inquiry_view = hci_packets.InquiryResultView(hci_event)
- if inquiry_view is None:
- return False
- results = inquiry_view.GetInquiryResults()
- return any((address == result.bd_addr for result in results))
-
- @staticmethod
- def InquiryResultwithRssi(address):
- return lambda msg: NeighborMatchers._is_matching_inquiry_result_with_rssi(msg.packet, address)
-
- @staticmethod
- def _is_matching_inquiry_result_with_rssi(packet, address):
- hci_event = HciMatchers.ExtractEventWithCode(packet, EventCode.INQUIRY_RESULT_WITH_RSSI)
- if hci_event is None:
- return False
- inquiry_view = hci_packets.InquiryResultWithRssiView(hci_event)
- if inquiry_view is None:
- return False
- results = inquiry_view.GetInquiryResults()
- return any((address == result.address for result in results))
-
- @staticmethod
- def ExtendedInquiryResult(address):
- return lambda msg: NeighborMatchers._is_matching_extended_inquiry_result(msg.packet, address)
-
- @staticmethod
- def _is_matching_extended_inquiry_result(packet, address):
- hci_event = HciMatchers.ExtractEventWithCode(packet, EventCode.EXTENDED_INQUIRY_RESULT)
- if hci_event is None:
- return False
- extended_view = hci_packets.ExtendedInquiryResultView(hci_event)
- if extended_view is None:
- return False
- return address == extended_view.GetAddress()
-
-
-class L2capMatchers(object):
-
- @staticmethod
- def ConnectionRequest(psm):
- return lambda packet: L2capMatchers._is_matching_connection_request(packet, psm)
-
- @staticmethod
- def ConnectionResponse(scid):
- return lambda packet: L2capMatchers._is_matching_connection_response(packet, scid)
-
- @staticmethod
- def ConfigurationResponse(result=ConfigurationResponseResult.SUCCESS):
- return lambda packet: L2capMatchers._is_matching_configuration_response(packet, result)
-
- @staticmethod
- def ConfigurationRequest(cid=None):
- return lambda packet: L2capMatchers._is_matching_configuration_request_with_cid(packet, cid)
-
- @staticmethod
- def ConfigurationRequestWithErtm():
- return lambda packet: L2capMatchers._is_matching_configuration_request_with_ertm(packet)
-
- @staticmethod
- def ConfigurationRequestView(dcid):
- return lambda request_view: request_view.GetDestinationCid() == dcid
-
- @staticmethod
- def DisconnectionRequest(scid, dcid):
- return lambda packet: L2capMatchers._is_matching_disconnection_request(packet, scid, dcid)
-
- @staticmethod
- def DisconnectionResponse(scid, dcid):
- return lambda packet: L2capMatchers._is_matching_disconnection_response(packet, scid, dcid)
-
- @staticmethod
- def EchoResponse():
- return lambda packet: L2capMatchers._is_control_frame_with_code(packet, CommandCode.ECHO_RESPONSE)
-
- @staticmethod
- def CommandReject():
- return lambda packet: L2capMatchers._is_control_frame_with_code(packet, CommandCode.COMMAND_REJECT)
-
- @staticmethod
- def LeCommandReject():
- return lambda packet: L2capMatchers._is_le_control_frame_with_code(packet, LeCommandCode.COMMAND_REJECT)
-
- @staticmethod
- def LeConnectionParameterUpdateRequest():
- return lambda packet: L2capMatchers._is_le_control_frame_with_code(
- packet, LeCommandCode.CONNECTION_PARAMETER_UPDATE_REQUEST)
-
- @staticmethod
- def LeConnectionParameterUpdateResponse(result=l2cap_packets.ConnectionParameterUpdateResponseResult.ACCEPTED):
- return lambda packet: L2capMatchers._is_matching_connection_parameter_update_response(packet, result)
-
- @staticmethod
- def CreditBasedConnectionRequest(psm):
- return lambda packet: L2capMatchers._is_matching_credit_based_connection_request(packet, psm)
-
- @staticmethod
- def CreditBasedConnectionResponse(result=LeCreditBasedConnectionResponseResult.SUCCESS):
- return lambda packet: L2capMatchers._is_matching_credit_based_connection_response(packet, result)
-
- @staticmethod
- def CreditBasedConnectionResponseUsedCid():
- return lambda packet: L2capMatchers._is_matching_credit_based_connection_response(
- packet, LeCreditBasedConnectionResponseResult.SOURCE_CID_ALREADY_ALLOCATED
- ) or L2capMatchers._is_le_control_frame_with_code(packet, LeCommandCode.COMMAND_REJECT)
-
- @staticmethod
- def LeDisconnectionRequest(scid, dcid):
- return lambda packet: L2capMatchers._is_matching_le_disconnection_request(packet, scid, dcid)
-
- @staticmethod
- def LeDisconnectionResponse(scid, dcid):
- return lambda packet: L2capMatchers._is_matching_le_disconnection_response(packet, scid, dcid)
-
- @staticmethod
- def LeFlowControlCredit(cid):
- return lambda packet: L2capMatchers._is_matching_le_flow_control_credit(packet, cid)
-
- @staticmethod
- def SFrame(req_seq=None, f=None, s=None, p=None):
- return lambda packet: L2capMatchers._is_matching_supervisory_frame(packet, req_seq, f, s, p)
-
- @staticmethod
- def IFrame(tx_seq=None, payload=None, f=None):
- return lambda packet: L2capMatchers._is_matching_information_frame(packet, tx_seq, payload, f, fcs=False)
-
- @staticmethod
- def IFrameWithFcs(tx_seq=None, payload=None, f=None):
- return lambda packet: L2capMatchers._is_matching_information_frame(packet, tx_seq, payload, f, fcs=True)
-
- @staticmethod
- def IFrameStart(tx_seq=None, payload=None, f=None):
- return lambda packet: L2capMatchers._is_matching_information_start_frame(packet, tx_seq, payload, f, fcs=False)
-
- @staticmethod
- def Data(payload):
- return lambda packet: packet.GetPayload().GetBytes() == payload
-
- @staticmethod
- def FirstLeIFrame(payload, sdu_size):
- return lambda packet: L2capMatchers._is_matching_first_le_i_frame(packet, payload, sdu_size)
-
- # this is a hack - should be removed
- @staticmethod
- def PartialData(payload):
- return lambda packet: payload in packet.GetPayload().GetBytes()
-
- # this is a hack - should be removed
- @staticmethod
- def PacketPayloadRawData(payload):
- return lambda packet: payload in packet.payload
-
- # this is a hack - should be removed
- @staticmethod
- def PacketPayloadWithMatchingPsm(psm):
- return lambda packet: None if psm != packet.psm else packet
-
- # this is a hack - should be removed
- @staticmethod
- def PacketPayloadWithMatchingCid(cid):
- return lambda packet: None if cid != packet.fixed_cid else packet
-
- @staticmethod
- def ExtractBasicFrame(scid):
- return lambda packet: L2capMatchers._basic_frame_for(packet, scid)
-
- @staticmethod
- def ExtractBasicFrameWithFcs(scid):
- return lambda packet: L2capMatchers._basic_frame_with_fcs_for(packet, scid)
-
- @staticmethod
- def InformationRequestWithType(info_type):
- return lambda packet: L2capMatchers._information_request_with_type(packet, info_type)
-
- @staticmethod
- def InformationResponseExtendedFeatures(supports_ertm=None,
- supports_streaming=None,
- supports_fcs=None,
- supports_fixed_channels=None):
- return lambda packet: L2capMatchers._is_matching_information_response_extended_features(
- packet, supports_ertm, supports_streaming, supports_fcs, supports_fixed_channels)
-
- @staticmethod
- def _basic_frame(packet):
- if packet is None:
- return None
- return l2cap_packets.BasicFrameView(bt_packets.PacketViewLittleEndian(list(packet.payload)))
-
- @staticmethod
- def _basic_frame_with_fcs(packet):
- if packet is None:
- return None
- return l2cap_packets.BasicFrameWithFcsView(bt_packets.PacketViewLittleEndian(list(packet.payload)))
-
- @staticmethod
- def _basic_frame_for(packet, scid):
- frame = L2capMatchers._basic_frame(packet)
- if frame.GetChannelId() != scid:
- return None
- return frame
-
- @staticmethod
- def _basic_frame_with_fcs_for(packet, scid):
- frame = L2capMatchers._basic_frame(packet)
- if frame.GetChannelId() != scid:
- return None
- frame = L2capMatchers._basic_frame_with_fcs(packet)
- if frame is None:
- return None
- return frame
-
- @staticmethod
- def _information_frame(packet):
- standard_frame = l2cap_packets.StandardFrameView(packet)
- if standard_frame.GetFrameType() != l2cap_packets.FrameType.I_FRAME:
- return None
- return l2cap_packets.EnhancedInformationFrameView(standard_frame)
-
- @staticmethod
- def _information_frame_with_fcs(packet):
- standard_frame = l2cap_packets.StandardFrameWithFcsView(packet)
- if standard_frame is None:
- return None
- if standard_frame.GetFrameType() != l2cap_packets.FrameType.I_FRAME:
- return None
- return l2cap_packets.EnhancedInformationFrameWithFcsView(standard_frame)
-
- @staticmethod
- def _information_start_frame(packet):
- start_frame = L2capMatchers._information_frame(packet)
- if start_frame is None:
- return None
- return l2cap_packets.EnhancedInformationStartFrameView(start_frame)
-
- @staticmethod
- def _information_start_frame_with_fcs(packet):
- start_frame = L2capMatchers._information_frame_with_fcs(packet)
- if start_frame is None:
- return None
- return l2cap_packets.EnhancedInformationStartFrameWithFcsView(start_frame)
-
- @staticmethod
- def _supervisory_frame(packet):
- standard_frame = l2cap_packets.StandardFrameView(packet)
- if standard_frame.GetFrameType() != l2cap_packets.FrameType.S_FRAME:
- return None
- return l2cap_packets.EnhancedSupervisoryFrameView(standard_frame)
-
- @staticmethod
- def _is_matching_information_frame(packet, tx_seq, payload, f, fcs=False):
- if fcs:
- frame = L2capMatchers._information_frame_with_fcs(packet)
- else:
- frame = L2capMatchers._information_frame(packet)
- if frame is None:
- return False
- if tx_seq is not None and frame.GetTxSeq() != tx_seq:
- return False
- if payload is not None and frame.GetPayload().GetBytes() != payload:
- return False
- if f is not None and frame.GetF() != f:
- return False
- return True
-
- @staticmethod
- def _is_matching_information_start_frame(packet, tx_seq, payload, f, fcs=False):
- if fcs:
- frame = L2capMatchers._information_start_frame_with_fcs(packet)
- else:
- frame = L2capMatchers._information_start_frame(packet)
- if frame is None:
- return False
- if tx_seq is not None and frame.GetTxSeq() != tx_seq:
- return False
- if payload is not None and frame.GetPayload().GetBytes() != payload:
- return False
- if f is not None and frame.GetF() != f:
- return False
- return True
-
- @staticmethod
- def _is_matching_supervisory_frame(packet, req_seq, f, s, p):
- frame = L2capMatchers._supervisory_frame(packet)
- if frame is None:
- return False
- if req_seq is not None and frame.GetReqSeq() != req_seq:
- return False
- if f is not None and frame.GetF() != f:
- return False
- if s is not None and frame.GetS() != s:
- return False
- if p is not None and frame.GetP() != p:
- return False
- return True
-
- @staticmethod
- def _is_matching_first_le_i_frame(packet, payload, sdu_size):
- first_le_i_frame = l2cap_packets.FirstLeInformationFrameView(packet)
- return first_le_i_frame.GetPayload().GetBytes() == payload and first_le_i_frame.GetL2capSduLength() == sdu_size
-
- @staticmethod
- def _control_frame(packet):
- if packet.GetChannelId() != 1:
- return None
- return l2cap_packets.ControlView(packet.GetPayload())
-
- @staticmethod
- def _le_control_frame(packet):
- if packet.GetChannelId() != 5:
- return None
- return l2cap_packets.LeControlView(packet.GetPayload())
-
- @staticmethod
- def control_frame_with_code(packet, code):
- frame = L2capMatchers._control_frame(packet)
- if frame is None or frame.GetCode() != code:
- return None
- return frame
-
- @staticmethod
- def le_control_frame_with_code(packet, code):
- frame = L2capMatchers._le_control_frame(packet)
- if frame is None or frame.GetCode() != code:
- return None
- return frame
-
- @staticmethod
- def _is_control_frame_with_code(packet, code):
- return L2capMatchers.control_frame_with_code(packet, code) is not None
-
- @staticmethod
- def _is_le_control_frame_with_code(packet, code):
- return L2capMatchers.le_control_frame_with_code(packet, code) is not None
-
- @staticmethod
- def _is_matching_connection_request(packet, psm):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.CONNECTION_REQUEST)
- if frame is None:
- return False
- request = l2cap_packets.ConnectionRequestView(frame)
- return request.GetPsm() == psm
-
- @staticmethod
- def _is_matching_connection_response(packet, scid):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.CONNECTION_RESPONSE)
- if frame is None:
- return False
- response = l2cap_packets.ConnectionResponseView(frame)
- return response.GetSourceCid() == scid and response.GetResult(
- ) == ConnectionResponseResult.SUCCESS and response.GetDestinationCid() != 0
-
- @staticmethod
- def _is_matching_configuration_request_with_cid(packet, cid=None):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.CONFIGURATION_REQUEST)
- if frame is None:
- return False
- request = l2cap_packets.ConfigurationRequestView(frame)
- dcid = request.GetDestinationCid()
- return cid is None or cid == dcid
-
- @staticmethod
- def _is_matching_configuration_request_with_ertm(packet):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.CONFIGURATION_REQUEST)
- if frame is None:
- return False
- request = l2cap_packets.ConfigurationRequestView(frame)
- config_bytes = request.GetBytes()
- # TODO(b/153189503): Use packet struct parser.
- return b"\x04\x09\x03" in config_bytes
-
- @staticmethod
- def _is_matching_configuration_response(packet, result=ConfigurationResponseResult.SUCCESS):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.CONFIGURATION_RESPONSE)
- if frame is None:
- return False
- response = l2cap_packets.ConfigurationResponseView(frame)
- return response.GetResult() == result
-
- @staticmethod
- def _is_matching_disconnection_request(packet, scid, dcid):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.DISCONNECTION_REQUEST)
- if frame is None:
- return False
- request = l2cap_packets.DisconnectionRequestView(frame)
- return request.GetSourceCid() == scid and request.GetDestinationCid() == dcid
-
- @staticmethod
- def _is_matching_disconnection_response(packet, scid, dcid):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.DISCONNECTION_RESPONSE)
- if frame is None:
- return False
- response = l2cap_packets.DisconnectionResponseView(frame)
- return response.GetSourceCid() == scid and response.GetDestinationCid() == dcid
-
- @staticmethod
- def _is_matching_le_disconnection_response(packet, scid, dcid):
- frame = L2capMatchers.le_control_frame_with_code(packet, LeCommandCode.DISCONNECTION_RESPONSE)
- if frame is None:
- return False
- response = l2cap_packets.LeDisconnectionResponseView(frame)
- return response.GetSourceCid() == scid and response.GetDestinationCid() == dcid
-
- @staticmethod
- def _is_matching_le_disconnection_request(packet, scid, dcid):
- frame = L2capMatchers.le_control_frame_with_code(packet, LeCommandCode.DISCONNECTION_REQUEST)
- if frame is None:
- return False
- request = l2cap_packets.LeDisconnectionRequestView(frame)
- return request.GetSourceCid() == scid and request.GetDestinationCid() == dcid
-
- @staticmethod
- def _is_matching_le_flow_control_credit(packet, cid):
- frame = L2capMatchers.le_control_frame_with_code(packet, LeCommandCode.LE_FLOW_CONTROL_CREDIT)
- if frame is None:
- return False
- request = l2cap_packets.LeFlowControlCreditView(frame)
- return request.GetCid() == cid
-
- @staticmethod
- def _information_request_with_type(packet, info_type):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.INFORMATION_REQUEST)
- if frame is None:
- return None
- request = l2cap_packets.InformationRequestView(frame)
- if request.GetInfoType() != info_type:
- return None
- return request
-
- @staticmethod
- def _information_response_with_type(packet, info_type):
- frame = L2capMatchers.control_frame_with_code(packet, CommandCode.INFORMATION_RESPONSE)
- if frame is None:
- return None
- response = l2cap_packets.InformationResponseView(frame)
- if response.GetInfoType() != info_type:
- return None
- return response
-
- @staticmethod
- def _is_matching_information_response_extended_features(packet, supports_ertm, supports_streaming, supports_fcs,
- supports_fixed_channels):
- frame = L2capMatchers._information_response_with_type(packet,
- InformationRequestInfoType.EXTENDED_FEATURES_SUPPORTED)
- if frame is None:
- return False
- features = l2cap_packets.InformationResponseExtendedFeaturesView(frame)
- if supports_ertm is not None and features.GetEnhancedRetransmissionMode() != supports_ertm:
- return False
- if supports_streaming is not None and features.GetStreamingMode != supports_streaming:
- return False
- if supports_fcs is not None and features.GetFcsOption() != supports_fcs:
- return False
- if supports_fixed_channels is not None and features.GetFixedChannels() != supports_fixed_channels:
- return False
- return True
-
- @staticmethod
- def _is_matching_connection_parameter_update_response(packet, result):
- frame = L2capMatchers.le_control_frame_with_code(packet, LeCommandCode.CONNECTION_PARAMETER_UPDATE_RESPONSE)
- if frame is None:
- return False
- return l2cap_packets.ConnectionParameterUpdateResponseView(frame).GetResult() == result
-
- @staticmethod
- def _is_matching_credit_based_connection_request(packet, psm):
- frame = L2capMatchers.le_control_frame_with_code(packet, LeCommandCode.LE_CREDIT_BASED_CONNECTION_REQUEST)
- if frame is None:
- return False
- request = l2cap_packets.LeCreditBasedConnectionRequestView(frame)
- return request.GetLePsm() == psm
-
- @staticmethod
- def _is_matching_credit_based_connection_response(packet, result):
- frame = L2capMatchers.le_control_frame_with_code(packet, LeCommandCode.LE_CREDIT_BASED_CONNECTION_RESPONSE)
- if frame is None:
- return False
- response = l2cap_packets.LeCreditBasedConnectionResponseView(frame)
- return response.GetResult() == result and (result != LeCreditBasedConnectionResponseResult.SUCCESS or
- response.GetDestinationCid() != 0)
-
- @staticmethod
- def LinkSecurityInterfaceCallbackEvent(type):
- return lambda event: True if event.event_type == type else False
-
-
-class SecurityMatchers(object):
-
- @staticmethod
- def UiMsg(type, address=None):
- return lambda event: True if event.message_type == type and (address == None or address == event.peer) else False
-
- @staticmethod
- def BondMsg(type, address=None, reason=None):
- return lambda event: True if event.message_type == type and (address == None or address == event.peer) and (reason == None or reason == event.reason) else False
-
- @staticmethod
- def HelperMsg(type, address=None):
- return lambda event: True if event.message_type == type and (address == None or address == event.peer) else False
-
-
-class IsoMatchers(object):
-
- @staticmethod
- def Data(payload):
- return lambda packet: packet.payload == payload
-
- @staticmethod
- def PacketPayloadWithMatchingCisHandle(cis_handle):
- return lambda packet: None if cis_handle != packet.handle else packet
diff --git a/gd/cert/metadata.py b/gd/cert/metadata.py
deleted file mode 100644
index 17579ae28..000000000
--- a/gd/cert/metadata.py
+++ /dev/null
@@ -1,78 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2019 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-import functools
-import inspect
-
-from mobly import asserts
-
-from acts.test_decorators import test_info
-
-
-def _fail_decorator(msg):
-
- def fail_decorator(func):
-
- @functools.wraps(func)
- def fail(*args, **kwargs):
- asserts.fail(msg)
-
- return fail
-
- return fail_decorator
-
-
-def metadata(_do_not_use=None, pts_test_id=None, pts_test_name=None):
- """
- Record a piece of test metadata in the Extra section of the test Record in
- the test summary file. The metadata will come with a timestamp, but there
- is no guarantee on the order of when the metadata will be written
-
- Note:
- - Metadata is recorded per test case as key-value pairs.
- - Metadata is only guaranteed to be written when the test result is PASS,
- FAIL or SKIPPED. When there are test infrastructural errors, metadata
- might not be written successfully
- :param _do_not_use: a positional argument with default value. This argument
- is to ensure that @metadata(key=value) is used in a
- functional form instead of @metadata or @metadata(a)
- :param pts_test_id: A fully qualified PTS test ID such as
- L2CAP/COS/IEX/BV-01-C
- :param pts_test_name: A human readable test name such as
- "Request Connection" for the above example
- :return: decorated test case function object
- """
- if _do_not_use is not None:
-
- def fail(*args, **kwargs):
- asserts.fail("@metadata must be used in functional form such " "as @metadta(key=value)")
-
- return fail
-
- # Create a dictionary of optional parameters
- values = locals()
- args = {arg: values[arg] for arg in inspect.getfullargspec(metadata).args}
- del args["_do_not_use"]
-
- # Check if at least one optional parameter is valid
- if not any(args.values()):
- return _fail_decorator("at least one optional argument should be valid")
-
- # Validate pts_test_id and pts_test_name
- if any((pts_test_id, pts_test_name)) and \
- not all((pts_test_id, pts_test_name)):
- return _fail_decorator("pts_test_id and pts_test_name must both " "be valid if one of them is valid")
-
- return test_info(**args)
diff --git a/gd/cert/os_utils.py b/gd/cert/os_utils.py
deleted file mode 100644
index 6a2f74eaa..000000000
--- a/gd/cert/os_utils.py
+++ /dev/null
@@ -1,141 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import logging
-from pathlib import Path
-import psutil
-import re
-import subprocess
-from typing import Container
-from collections import deque
-
-
-class TerminalColor:
- RED = "\033[31;1m"
- BLUE = "\033[34;1m"
- YELLOW = "\033[33;1m"
- MAGENTA = "\033[35;1m"
- END = "\033[0m"
-
-
-def is_subprocess_alive(process, timeout_seconds=1):
- """
- Check if a process is alive for at least timeout_seconds
- :param process: a Popen object that represent a subprocess
- :param timeout_seconds: process needs to be alive for at least
- timeout_seconds
- :return: True if process is alive for at least timeout_seconds
- """
- try:
- process.wait(timeout=timeout_seconds)
- return False
- except subprocess.TimeoutExpired as exp:
- return True
-
-
-def get_gd_root():
- """
- Return the root of the GD test library
-
- GD root is the parent directory of cert
- :return: root directory string of gd test library
- """
- return str(Path(__file__).absolute().parents[1])
-
-
-def make_ports_available(ports: Container[int], timeout_seconds=10):
- """Make sure a list of ports are available
- kill occupying process if possible
- :param ports: list of target ports
- :param timeout_seconds: number of seconds to wait when killing processes
- :return: True on success, False on failure
- """
- if not ports:
- logging.warning("Empty ports is given to make_ports_available()")
- return True
- # Get connections whose state are in LISTEN only
- # Connections in other states won't affect binding as SO_REUSEADDR is used
- listening_conns_for_port = filter(
- lambda conn: (conn and conn.status == psutil.CONN_LISTEN and conn.laddr and conn.laddr.port in ports),
- psutil.net_connections())
- success = True
- for conn in listening_conns_for_port:
- logging.warning("Freeing port %d used by %s" % (conn.laddr.port, str(conn)))
- if not conn.pid:
- logging.error("Failed to kill process occupying port %d due to lack of pid" % conn.laddr.port)
- success = False
- continue
- logging.warning("Killing pid %d that is using port port %d" % (conn.pid, conn.laddr.port))
- process = psutil.Process(conn.pid)
- process.kill()
- try:
- process.wait(timeout=timeout_seconds)
- except psutil.TimeoutExpired:
- logging.error("SIGKILL timeout after %d seconds for pid %d" % (timeout_seconds, conn.pid))
- continue
- return success
-
-
-# e.g. 2020-05-06 16:02:04.216 bt - system/bt/gd/facade/facade_main.cc:79 - crash_callback: #03 pc 0000000000013520 /lib/x86_64-linux-gnu/libpthread-2.29.so
-HOST_CRASH_LINE_REGEX = re.compile(r"^.* - crash_callback: (?P<line>.*)$")
-HOST_ABORT_HEADER = "Process crashed, signal: Aborted"
-ASAN_OUTPUT_START_REGEX = re.compile(r"^==.*AddressSanitizer.*$")
-
-
-def read_crash_snippet_and_log_tail(logpath):
- """
- Get crash snippet if regex matched or last 20 lines of log
- :return: crash_snippet, log_tail_20
- 1) crash snippet without timestamp in one string;
- 2) last 20 lines of log in one string;
- """
- gd_root_prefix = get_gd_root() + "/"
- abort_line = None
- last_20_lines = deque(maxlen=20)
- crash_log_lines = []
- asan = False
- asan_lines = []
-
- with open(logpath) as f:
- for _, line in enumerate(f):
- last_20_lines.append(line)
- asan_match = ASAN_OUTPUT_START_REGEX.match(line)
- if asan or asan_match:
- asan_lines.append(line)
- asan = True
- continue
-
- host_crash_match = HOST_CRASH_LINE_REGEX.match(line)
- if host_crash_match:
- crash_line = host_crash_match.group("line").replace(gd_root_prefix, "")
- if HOST_ABORT_HEADER in crash_line \
- and len(last_20_lines) > 1:
- abort_line = last_20_lines[-2]
- crash_log_lines.append(crash_line)
-
- log_tail_20 = "".join(last_20_lines)
- crash_snippet = ""
- if abort_line is not None:
- crash_snippet += "abort log line:\n\n%s\n" % abort_line
- crash_snippet += "\n".join(crash_log_lines)
-
- if len(asan_lines) > 0:
- return "".join(asan_lines), log_tail_20
-
- if len(crash_log_lines) > 0:
- return crash_snippet, log_tail_20
-
- return None, log_tail_20
diff --git a/gd/cert/performance_test_logger.py b/gd/cert/performance_test_logger.py
deleted file mode 100644
index 006bbd6aa..000000000
--- a/gd/cert/performance_test_logger.py
+++ /dev/null
@@ -1,71 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from datetime import datetime
-
-
-class PerformanceTestLogger(object):
- """
- A helper class to log time points and intervals
- """
-
- def __init__(self):
- self.base_timepoint = datetime.now()
- # We use a dictionary of a list of timepoints
- self.start_interval_points = {}
- self.end_interval_points = {}
- self.single_points = {}
-
- def log_single_point(self, label=""):
- if label not in self.single_points:
- self.single_points[label] = []
- self.single_points[label].append(datetime.now())
-
- def start_interval(self, label=""):
- if label not in self.start_interval_points:
- self.start_interval_points[label] = []
- self.start_interval_points[label].append(datetime.now())
-
- def end_interval(self, label=""):
- if label not in self.end_interval_points:
- self.end_interval_points[label] = []
- self.end_interval_points[label].append(datetime.now())
-
- def _check_interval_label(self, label):
- if label not in self.start_interval_points or label not in self.end_interval_points:
- raise KeyError("label %s doesn't exist" % label)
- if len(self.start_interval_points[label]) != len(self.end_interval_points[label]):
- raise KeyError("label %s doesn't have correct start and end log" % label)
-
- def get_duration_of_intervals(self, label):
- """
- Return the list of duration of the intervals with specified label.
- """
- self._check_interval_label(label)
- intervals = []
- for i in range(len(self.start_interval_points[label])):
- interval = self.end_interval_points[label][i] - self.start_interval_points[label][i]
- intervals.append(interval)
- return intervals
-
- def dump_intervals(self):
- """
- Gives an iterator of (iterator of label, start, end) over all labels
- """
- for label in self.start_interval_points:
- self._check_interval_label(label)
- yield ((label, self.start_interval_points[label][i], self.end_interval_points[label][i])
- for i in range(len(self.start_interval_points[label])))
diff --git a/gd/cert/pts.json b/gd/cert/pts.json
index b266c5aa1..76a27bea3 100644
--- a/gd/cert/pts.json
+++ b/gd/cert/pts.json
@@ -13,7 +13,6 @@
"signal_port": "8895",
"label": "stack_under_test",
"serial_number": "DUT",
- "name": "Cert Device",
"cmd":
[
"adb",
diff --git a/gd/cert/pts_base_test.py b/gd/cert/pts_base_test.py
index 809940778..906bccf26 100644
--- a/gd/cert/pts_base_test.py
+++ b/gd/cert/pts_base_test.py
@@ -17,6 +17,10 @@
from acts.base_test import BaseTestClass
import importlib
+import logging
+import os
+import signal
+import subprocess
class PTSBaseTestClass(BaseTestClass):
@@ -26,4 +30,5 @@ class PTSBaseTestClass(BaseTestClass):
gd_devices = self.controller_configs.get("GdDevice")
- self.register_controller(importlib.import_module('cert.gd_device'), builtin=True)
+ self.register_controller(
+ importlib.import_module('cert.gd_device'), builtin=True)
diff --git a/gd/cert/py_acl_manager.py b/gd/cert/py_acl_manager.py
deleted file mode 100644
index bba58ad4c..000000000
--- a/gd/cert/py_acl_manager.py
+++ /dev/null
@@ -1,97 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from google.protobuf import empty_pb2 as empty_proto
-from cert.event_stream import EventStream
-from cert.event_stream import IEventStream
-from cert.captures import HciCaptures
-from cert.closable import Closable
-from cert.closable import safeClose
-from bluetooth_packets_python3 import hci_packets
-from cert.truth import assertThat
-from hci.facade import acl_manager_facade_pb2 as acl_manager_facade
-
-
-class PyAclManagerAclConnection(IEventStream, Closable):
-
- def __init__(self, acl_manager, remote_addr, handle, event_stream):
- self.acl_manager = acl_manager
- self.handle = handle
- self.remote_addr = remote_addr
- self.connection_event_stream = event_stream
- self.acl_stream = EventStream(self.acl_manager.FetchAclData(acl_manager_facade.HandleMsg(handle=self.handle)))
-
- def disconnect(self, reason):
- packet_bytes = bytes(hci_packets.DisconnectBuilder(self.handle, reason).Serialize())
- self.acl_manager.ConnectionCommand(acl_manager_facade.ConnectionCommandMsg(packet=packet_bytes))
-
- def close(self):
- safeClose(self.connection_event_stream)
- safeClose(self.acl_stream)
-
- def wait_for_disconnection_complete(self):
- disconnection_complete = HciCaptures.DisconnectionCompleteCapture()
- assertThat(self.connection_event_stream).emits(disconnection_complete)
- self.disconnect_reason = disconnection_complete.get().GetReason()
-
- def send(self, data):
- self.acl_manager.SendAclData(acl_manager_facade.AclData(handle=self.handle, payload=bytes(data)))
-
- def get_event_queue(self):
- return self.acl_stream.get_event_queue()
-
-
-class PyAclManager:
-
- def __init__(self, device):
- self.acl_manager = device.hci_acl_manager
- self.incoming_connection_event_stream = None
- self.outgoing_connection_event_stream = None
-
- def close(self):
- safeClose(self.incoming_connection_event_stream)
- safeClose(self.outgoing_connection_event_stream)
-
- def listen_for_an_incoming_connection(self):
- assertThat(self.incoming_connection_event_stream).isNone()
- self.incoming_connection_event_stream = EventStream(
- self.acl_manager.FetchIncomingConnection(empty_proto.Empty()))
-
- def initiate_connection(self, remote_addr):
- assertThat(self.outgoing_connection_event_stream).isNone()
- remote_addr_bytes = bytes(remote_addr, 'utf8') if type(remote_addr) is str else bytes(remote_addr)
- self.outgoing_connection_event_stream = EventStream(
- self.acl_manager.CreateConnection(acl_manager_facade.ConnectionMsg(address=remote_addr_bytes)))
-
- def complete_connection(self, event_stream):
- connection_complete = HciCaptures.ConnectionCompleteCapture()
- assertThat(event_stream).emits(connection_complete)
- complete = connection_complete.get()
- handle = complete.GetConnectionHandle()
- address = complete.GetBdAddr()
- return PyAclManagerAclConnection(self.acl_manager, address, handle, event_stream)
-
- def complete_incoming_connection(self):
- assertThat(self.incoming_connection_event_stream).isNotNone()
- event_stream = self.incoming_connection_event_stream
- self.incoming_connection_event_stream = None
- return self.complete_connection(event_stream)
-
- def complete_outgoing_connection(self):
- assertThat(self.outgoing_connection_event_stream).isNotNone()
- event_stream = self.outgoing_connection_event_stream
- self.outgoing_connection_event_stream = None
- return self.complete_connection(event_stream)
diff --git a/gd/cert/py_hal.py b/gd/cert/py_hal.py
deleted file mode 100644
index cba7b3084..000000000
--- a/gd/cert/py_hal.py
+++ /dev/null
@@ -1,283 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from google.protobuf import empty_pb2 as empty_proto
-from cert.event_stream import EventStream
-from cert.event_stream import FilteringEventStream
-from cert.event_stream import IEventStream
-from cert.closable import Closable
-from cert.closable import safeClose
-from cert.captures import HciCaptures
-from cert.truth import assertThat
-from bluetooth_packets_python3.hci_packets import WriteScanEnableBuilder
-from bluetooth_packets_python3.hci_packets import ScanEnable
-from bluetooth_packets_python3.hci_packets import AclBuilder
-from bluetooth_packets_python3 import RawBuilder
-from bluetooth_packets_python3.hci_packets import BroadcastFlag
-from bluetooth_packets_python3.hci_packets import PacketBoundaryFlag
-from bluetooth_packets_python3 import hci_packets
-from cert.matchers import HciMatchers
-from bluetooth_packets_python3.hci_packets import FilterDuplicates
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingLegacyParametersBuilder
-from bluetooth_packets_python3.hci_packets import LegacyAdvertisingProperties
-from bluetooth_packets_python3.hci_packets import PeerAddressType
-from bluetooth_packets_python3.hci_packets import AdvertisingFilterPolicy
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingRandomAddressBuilder
-from bluetooth_packets_python3.hci_packets import GapData
-from bluetooth_packets_python3.hci_packets import GapDataType
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingDataBuilder
-from bluetooth_packets_python3.hci_packets import Operation
-from bluetooth_packets_python3.hci_packets import OwnAddressType
-from bluetooth_packets_python3.hci_packets import LeScanningFilterPolicy
-from bluetooth_packets_python3.hci_packets import Enable
-from bluetooth_packets_python3.hci_packets import FragmentPreference
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingScanResponseBuilder
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingEnableBuilder
-from bluetooth_packets_python3.hci_packets import LeSetExtendedScanEnableBuilder
-from bluetooth_packets_python3.hci_packets import EnabledSet
-from bluetooth_packets_python3.hci_packets import OpCode
-from facade import common_pb2 as common
-
-
-class PyHalAclConnection(IEventStream):
-
- def __init__(self, handle, acl_stream, device):
- self.handle = int(handle)
- self.device = device
- self.our_acl_stream = FilteringEventStream(acl_stream, None)
-
- def send(self, pb_flag, b_flag, data):
- acl = AclBuilder(self.handle, pb_flag, b_flag, RawBuilder(data))
- self.device.hal.SendAcl(common.Data(payload=bytes(acl.Serialize())))
-
- def send_first(self, data):
- self.send(PacketBoundaryFlag.FIRST_NON_AUTOMATICALLY_FLUSHABLE, BroadcastFlag.POINT_TO_POINT, bytes(data))
-
- def get_event_queue(self):
- return self.our_acl_stream.get_event_queue()
-
-
-class PyHalAdvertisement(object):
-
- def __init__(self, handle, py_hal):
- self.handle = handle
- self.py_hal = py_hal
-
- def set_data(self, complete_name):
- data = GapData()
- data.data_type = GapDataType.COMPLETE_LOCAL_NAME
- data.data = list(bytes(complete_name))
- self.py_hal.send_hci_command(
- LeSetExtendedAdvertisingDataBuilder(self.handle, Operation.COMPLETE_ADVERTISEMENT,
- FragmentPreference.CONTROLLER_SHOULD_NOT, [data]))
- self.py_hal.wait_for_complete(OpCode.LE_SET_EXTENDED_ADVERTISING_DATA)
-
- def set_scan_response(self, shortened_name):
- data = GapData()
- data.data_type = GapDataType.SHORTENED_LOCAL_NAME
- data.data = list(bytes(shortened_name))
- self.py_hal.send_hci_command(
- LeSetExtendedAdvertisingScanResponseBuilder(self.handle, Operation.COMPLETE_ADVERTISEMENT,
- FragmentPreference.CONTROLLER_SHOULD_NOT, [data]))
- self.py_hal.wait_for_complete(OpCode.LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE)
-
- def start(self):
- enabled_set = EnabledSet()
- enabled_set.advertising_handle = self.handle
- enabled_set.duration = 0
- enabled_set.max_extended_advertising_events = 0
- self.py_hal.send_hci_command(LeSetExtendedAdvertisingEnableBuilder(Enable.ENABLED, [enabled_set]))
- self.py_hal.wait_for_complete(OpCode.LE_SET_EXTENDED_ADVERTISING_ENABLE)
-
- def stop(self):
- enabled_set = EnabledSet()
- enabled_set.advertising_handle = self.handle
- enabled_set.duration = 0
- enabled_set.max_extended_advertising_events = 0
- self.py_hal.send_hci_command(LeSetExtendedAdvertisingEnableBuilder(Enable.DISABLED, [enabled_set]))
- self.py_hal.wait_for_complete(OpCode.LE_SET_EXTENDED_ADVERTISING_ENABLE)
-
-
-class PyHal(Closable):
-
- def __init__(self, device):
- self.device = device
-
- self.hci_event_stream = EventStream(self.device.hal.StreamEvents(empty_proto.Empty()))
- self.acl_stream = EventStream(self.device.hal.StreamAcl(empty_proto.Empty()))
-
- # We don't deal with SCO for now
-
- def close(self):
- safeClose(self.hci_event_stream)
- safeClose(self.acl_stream)
-
- def get_hci_event_stream(self):
- return self.hci_event_stream
-
- def wait_for_complete(self, opcode):
- assertThat(self.hci_event_stream).emits(HciMatchers.CommandComplete(opcode))
-
- def wait_for_status(self, opcode):
- assertThat(self.hci_event_stream).emits(HciMatchers.CommandStatus(opcode))
-
- def get_acl_stream(self):
- return self.acl_stream
-
- def send_hci_command(self, command):
- self.device.hal.SendCommand(common.Data(payload=bytes(command.Serialize())))
-
- def send_acl(self, handle, pb_flag, b_flag, data):
- acl = AclBuilder(handle, pb_flag, b_flag, RawBuilder(data))
- self.device.hal.SendAcl(common.Data(payload=bytes(acl.Serialize())))
-
- def send_acl_first(self, handle, data):
- self.send_acl(handle, PacketBoundaryFlag.FIRST_NON_AUTOMATICALLY_FLUSHABLE, BroadcastFlag.POINT_TO_POINT, data)
-
- def read_own_address(self):
- self.send_hci_command(hci_packets.ReadBdAddrBuilder())
- read_bd_addr = HciCaptures.ReadBdAddrCompleteCapture()
- assertThat(self.hci_event_stream).emits(read_bd_addr)
- return read_bd_addr.get().GetBdAddr()
-
- def set_random_le_address(self, addr):
- self.send_hci_command(hci_packets.LeSetRandomAddressBuilder(addr))
- self.wait_for_complete(OpCode.LE_SET_RANDOM_ADDRESS)
-
- def set_scan_parameters(self):
- phy_scan_params = hci_packets.PhyScanParameters()
- phy_scan_params.le_scan_interval = 6553
- phy_scan_params.le_scan_window = 6553
- phy_scan_params.le_scan_type = hci_packets.LeScanType.ACTIVE
-
- self.send_hci_command(
- hci_packets.LeSetExtendedScanParametersBuilder(hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
- hci_packets.LeScanningFilterPolicy.ACCEPT_ALL, 1,
- [phy_scan_params]))
- self.wait_for_complete(OpCode.LE_SET_EXTENDED_SCAN_PARAMETERS)
-
- def start_scanning(self):
- self.send_hci_command(
- hci_packets.LeSetExtendedScanEnableBuilder(hci_packets.Enable.ENABLED,
- hci_packets.FilterDuplicates.DISABLED, 0, 0))
- self.wait_for_complete(OpCode.LE_SET_EXTENDED_SCAN_ENABLE)
-
- def stop_scanning(self):
- self.send_hci_command(
- hci_packets.LeSetExtendedScanEnableBuilder(hci_packets.Enable.DISABLED,
- hci_packets.FilterDuplicates.DISABLED, 0, 0))
- self.wait_for_complete(OpCode.LE_SET_EXTENDED_SCAN_ENABLE)
-
- def reset(self):
- self.send_hci_command(hci_packets.ResetBuilder())
- self.wait_for_complete(OpCode.RESET)
-
- def enable_inquiry_and_page_scan(self):
- self.send_hci_command(WriteScanEnableBuilder(ScanEnable.INQUIRY_AND_PAGE_SCAN))
-
- def initiate_connection(self, remote_addr):
- self.send_hci_command(
- hci_packets.CreateConnectionBuilder(
- remote_addr if isinstance(remote_addr, str) else remote_addr.decode('utf-8'),
- 0xcc18, # Packet Type
- hci_packets.PageScanRepetitionMode.R1,
- 0x0,
- hci_packets.ClockOffsetValid.INVALID,
- hci_packets.CreateConnectionRoleSwitch.ALLOW_ROLE_SWITCH))
-
- def accept_connection(self):
- connection_request = HciCaptures.ConnectionRequestCapture()
- assertThat(self.hci_event_stream).emits(connection_request)
-
- self.send_hci_command(
- hci_packets.AcceptConnectionRequestBuilder(connection_request.get().GetBdAddr(),
- hci_packets.AcceptConnectionRequestRole.REMAIN_PERIPHERAL))
- return self.complete_connection()
-
- def complete_connection(self):
- connection_complete = HciCaptures.ConnectionCompleteCapture()
- assertThat(self.hci_event_stream).emits(connection_complete)
-
- handle = connection_complete.get().GetConnectionHandle()
- return PyHalAclConnection(handle, self.acl_stream, self.device)
-
- def initiate_le_connection(self, remote_addr):
- phy_scan_params = hci_packets.LeCreateConnPhyScanParameters()
- phy_scan_params.scan_interval = 0x60
- phy_scan_params.scan_window = 0x30
- phy_scan_params.conn_interval_min = 0x18
- phy_scan_params.conn_interval_max = 0x28
- phy_scan_params.conn_latency = 0
- phy_scan_params.supervision_timeout = 0x1f4
- phy_scan_params.min_ce_length = 0
- phy_scan_params.max_ce_length = 0
- self.send_hci_command(
- hci_packets.LeExtendedCreateConnectionBuilder(
- hci_packets.InitiatorFilterPolicy.USE_PEER_ADDRESS, hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
- hci_packets.AddressType.RANDOM_DEVICE_ADDRESS, remote_addr, 1, [phy_scan_params]))
- self.wait_for_status(OpCode.LE_EXTENDED_CREATE_CONNECTION)
-
- def add_to_connect_list(self, remote_addr):
- self.send_hci_command(
- hci_packets.LeAddDeviceToConnectListBuilder(hci_packets.ConnectListAddressType.RANDOM, remote_addr))
-
- def initiate_le_connection_by_connect_list(self, remote_addr):
- phy_scan_params = hci_packets.LeCreateConnPhyScanParameters()
- phy_scan_params.scan_interval = 0x60
- phy_scan_params.scan_window = 0x30
- phy_scan_params.conn_interval_min = 0x18
- phy_scan_params.conn_interval_max = 0x28
- phy_scan_params.conn_latency = 0
- phy_scan_params.supervision_timeout = 0x1f4
- phy_scan_params.min_ce_length = 0
- phy_scan_params.max_ce_length = 0
- self.send_hci_command(
- hci_packets.LeExtendedCreateConnectionBuilder(
- hci_packets.InitiatorFilterPolicy.USE_CONNECT_LIST, hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
- hci_packets.AddressType.RANDOM_DEVICE_ADDRESS, remote_addr, 1, [phy_scan_params]))
-
- def complete_le_connection(self):
- connection_complete = HciCaptures.LeConnectionCompleteCapture()
- assertThat(self.hci_event_stream).emits(connection_complete)
-
- handle = connection_complete.get().GetConnectionHandle()
- return PyHalAclConnection(handle, self.acl_stream, self.device)
-
- def create_advertisement(self,
- handle,
- own_address,
- properties=LegacyAdvertisingProperties.ADV_IND,
- min_interval=400,
- max_interval=450,
- channel_map=7,
- own_address_type=OwnAddressType.RANDOM_DEVICE_ADDRESS,
- peer_address_type=PeerAddressType.PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
- peer_address='00:00:00:00:00:00',
- filter_policy=AdvertisingFilterPolicy.ALL_DEVICES,
- tx_power=0xF8,
- sid=1,
- scan_request_notification=Enable.DISABLED):
-
- self.send_hci_command(
- LeSetExtendedAdvertisingLegacyParametersBuilder(handle, properties, min_interval, max_interval, channel_map,
- own_address_type, peer_address_type, peer_address,
- filter_policy, tx_power, sid, scan_request_notification))
- self.wait_for_complete(OpCode.LE_SET_EXTENDED_ADVERTISING_PARAMETERS)
-
- self.send_hci_command(LeSetExtendedAdvertisingRandomAddressBuilder(handle, own_address))
- self.wait_for_complete(OpCode.LE_SET_EXTENDED_ADVERTISING_RANDOM_ADDRESS)
-
- return PyHalAdvertisement(handle, self)
diff --git a/gd/cert/py_hci.py b/gd/cert/py_hci.py
deleted file mode 100644
index 8312df68a..000000000
--- a/gd/cert/py_hci.py
+++ /dev/null
@@ -1,214 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from google.protobuf import empty_pb2 as empty_proto
-from cert.event_stream import EventStream
-from cert.event_stream import FilteringEventStream
-from cert.event_stream import IEventStream
-from cert.closable import Closable
-from cert.closable import safeClose
-from cert.captures import HciCaptures
-from bluetooth_packets_python3 import hci_packets
-from cert.truth import assertThat
-from hci.facade import hci_facade_pb2 as hci_facade
-from facade import common_pb2 as common
-from cert.matchers import HciMatchers
-from bluetooth_packets_python3.hci_packets import FilterDuplicates
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingLegacyParametersBuilder
-from bluetooth_packets_python3.hci_packets import LegacyAdvertisingProperties
-from bluetooth_packets_python3.hci_packets import PeerAddressType
-from bluetooth_packets_python3.hci_packets import AdvertisingFilterPolicy
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingRandomAddressBuilder
-from bluetooth_packets_python3.hci_packets import GapData
-from bluetooth_packets_python3.hci_packets import GapDataType
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingDataBuilder
-from bluetooth_packets_python3.hci_packets import Operation
-from bluetooth_packets_python3.hci_packets import OwnAddressType
-from bluetooth_packets_python3.hci_packets import LeScanningFilterPolicy
-from bluetooth_packets_python3.hci_packets import Enable
-from bluetooth_packets_python3.hci_packets import FragmentPreference
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingScanResponseBuilder
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingEnableBuilder
-from bluetooth_packets_python3.hci_packets import LeSetExtendedScanEnableBuilder
-from bluetooth_packets_python3.hci_packets import EnabledSet
-from bluetooth_packets_python3.hci_packets import OpCode
-from bluetooth_packets_python3.hci_packets import AclBuilder
-from bluetooth_packets_python3 import RawBuilder
-
-
-class PyHciAclConnection(IEventStream):
-
- def __init__(self, handle, acl_stream, device):
- self.handle = int(handle)
- self.device = device
- # todo, handle we got is 0, so doesn't match - fix before enabling filtering
- self.our_acl_stream = FilteringEventStream(acl_stream, None)
-
- def send(self, pb_flag, b_flag, data):
- acl = AclBuilder(self.handle, pb_flag, b_flag, RawBuilder(data))
- self.device.hci.SendAcl(common.Data(payload=bytes(acl.Serialize())))
-
- def send_first(self, data):
- self.send(hci_packets.PacketBoundaryFlag.FIRST_AUTOMATICALLY_FLUSHABLE,
- hci_packets.BroadcastFlag.POINT_TO_POINT, bytes(data))
-
- def send_continuing(self, data):
- self.send(hci_packets.PacketBoundaryFlag.CONTINUING_FRAGMENT, hci_packets.BroadcastFlag.POINT_TO_POINT,
- bytes(data))
-
- def get_event_queue(self):
- return self.our_acl_stream.get_event_queue()
-
-
-class PyHciAdvertisement(object):
-
- def __init__(self, handle, py_hci):
- self.handle = handle
- self.py_hci = py_hci
-
- def set_data(self, complete_name):
- data = GapData()
- data.data_type = GapDataType.COMPLETE_LOCAL_NAME
- data.data = list(bytes(complete_name))
- self.py_hci.send_command(
- LeSetExtendedAdvertisingDataBuilder(self.handle, Operation.COMPLETE_ADVERTISEMENT,
- FragmentPreference.CONTROLLER_SHOULD_NOT, [data]))
-
- def set_scan_response(self, shortened_name):
- data = GapData()
- data.data_type = GapDataType.SHORTENED_LOCAL_NAME
- data.data = list(bytes(shortened_name))
- self.py_hci.send_command(
- LeSetExtendedAdvertisingScanResponseBuilder(self.handle, Operation.COMPLETE_ADVERTISEMENT,
- FragmentPreference.CONTROLLER_SHOULD_NOT, [data]))
-
- def start(self):
- enabled_set = EnabledSet()
- enabled_set.advertising_handle = self.handle
- enabled_set.duration = 0
- enabled_set.max_extended_advertising_events = 0
- self.py_hci.send_command(LeSetExtendedAdvertisingEnableBuilder(Enable.ENABLED, [enabled_set]))
- assertThat(self.py_hci.get_event_stream()).emits(
- HciMatchers.CommandComplete(OpCode.LE_SET_EXTENDED_ADVERTISING_ENABLE))
-
-
-class PyHci(Closable):
-
- event_stream = None
- le_event_stream = None
- acl_stream = None
-
- def __init__(self, device, acl_streaming=False):
- """
- If you are planning on personally using the ACL data stream
- coming from HCI, specify acl_streaming=True. You probably only
- want this if you are testing HCI itself.
- """
- self.device = device
- self.event_stream = EventStream(self.device.hci.StreamEvents(empty_proto.Empty()))
- self.le_event_stream = EventStream(self.device.hci.StreamLeSubevents(empty_proto.Empty()))
- if acl_streaming:
- self.register_for_events(hci_packets.EventCode.ROLE_CHANGE, hci_packets.EventCode.CONNECTION_REQUEST,
- hci_packets.EventCode.CONNECTION_COMPLETE,
- hci_packets.EventCode.CONNECTION_PACKET_TYPE_CHANGED)
- self.acl_stream = EventStream(self.device.hci.StreamAcl(empty_proto.Empty()))
-
- def close(self):
- safeClose(self.event_stream)
- safeClose(self.le_event_stream)
- safeClose(self.acl_stream)
-
- def get_event_stream(self):
- return self.event_stream
-
- def get_le_event_stream(self):
- return self.le_event_stream
-
- def get_raw_acl_stream(self):
- if self.acl_stream is None:
- raise Exception("Please construct '%s' with acl_streaming=True!" % self.__class__.__name__)
- return self.acl_stream
-
- def register_for_events(self, *event_codes):
- for event_code in event_codes:
- self.device.hci.RequestEvent(hci_facade.EventRequest(code=int(event_code)))
-
- def register_for_le_events(self, *event_codes):
- for event_code in event_codes:
- self.device.hci.RequestLeSubevent(hci_facade.EventRequest(code=int(event_code)))
-
- def send_command(self, command):
- self.device.hci.SendCommand(common.Data(payload=bytes(command.Serialize())))
-
- def enable_inquiry_and_page_scan(self):
- self.send_command(hci_packets.WriteScanEnableBuilder(hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN))
-
- def read_own_address(self):
- self.send_command(hci_packets.ReadBdAddrBuilder())
- read_bd_addr = HciCaptures.ReadBdAddrCompleteCapture()
- assertThat(self.event_stream).emits(read_bd_addr)
- return read_bd_addr.get().GetBdAddr()
-
- def initiate_connection(self, remote_addr):
- self.send_command(
- hci_packets.CreateConnectionBuilder(
- remote_addr if isinstance(remote_addr, str) else remote_addr.decode('utf-8'),
- 0xcc18, # Packet Type
- hci_packets.PageScanRepetitionMode.R1,
- 0x0,
- hci_packets.ClockOffsetValid.INVALID,
- hci_packets.CreateConnectionRoleSwitch.ALLOW_ROLE_SWITCH))
-
- def accept_connection(self):
- connection_request = HciCaptures.ConnectionRequestCapture()
- assertThat(self.event_stream).emits(connection_request)
-
- self.send_command(
- hci_packets.AcceptConnectionRequestBuilder(connection_request.get().GetBdAddr(),
- hci_packets.AcceptConnectionRequestRole.REMAIN_PERIPHERAL))
- return self.complete_connection()
-
- def complete_connection(self):
- connection_complete = HciCaptures.ConnectionCompleteCapture()
- assertThat(self.event_stream).emits(connection_complete)
-
- handle = connection_complete.get().GetConnectionHandle()
- if self.acl_stream is None:
- raise Exception("Please construct '%s' with acl_streaming=True!" % self.__class__.__name__)
- return PyHciAclConnection(handle, self.acl_stream, self.device)
-
- def create_advertisement(self,
- handle,
- own_address,
- properties=LegacyAdvertisingProperties.ADV_IND,
- min_interval=400,
- max_interval=450,
- channel_map=7,
- own_address_type=OwnAddressType.RANDOM_DEVICE_ADDRESS,
- peer_address_type=PeerAddressType.PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
- peer_address='00:00:00:00:00:00',
- filter_policy=AdvertisingFilterPolicy.ALL_DEVICES,
- tx_power=0xF8,
- sid=1,
- scan_request_notification=Enable.DISABLED):
-
- self.send_command(
- LeSetExtendedAdvertisingLegacyParametersBuilder(handle, properties, min_interval, max_interval, channel_map,
- own_address_type, peer_address_type, peer_address,
- filter_policy, tx_power, sid, scan_request_notification))
-
- self.send_command(LeSetExtendedAdvertisingRandomAddressBuilder(handle, own_address))
- return PyHciAdvertisement(handle, self)
diff --git a/gd/cert/py_l2cap.py b/gd/cert/py_l2cap.py
deleted file mode 100644
index 8d1a230a9..000000000
--- a/gd/cert/py_l2cap.py
+++ /dev/null
@@ -1,266 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from google.protobuf import empty_pb2 as empty_proto
-
-from l2cap.classic import facade_pb2 as l2cap_facade_pb2
-from l2cap.classic.facade_pb2 import LinkSecurityInterfaceCallbackEventType
-from l2cap.le import facade_pb2 as l2cap_le_facade_pb2
-from l2cap.le.facade_pb2 import SecurityLevel
-from bluetooth_packets_python3 import hci_packets
-from bluetooth_packets_python3 import l2cap_packets
-from cert.event_stream import FilteringEventStream
-from cert.event_stream import EventStream, IEventStream
-from cert.closable import Closable, safeClose
-from cert.py_hci import PyHci
-from cert.matchers import HciMatchers
-from cert.matchers import L2capMatchers
-from cert.truth import assertThat
-from facade import common_pb2 as common
-
-
-class PyL2capChannel(IEventStream):
-
- def __init__(self, device, psm, l2cap_stream):
- self._device = device
- self._psm = psm
- self._le_l2cap_stream = l2cap_stream
- self._our_le_l2cap_view = FilteringEventStream(self._le_l2cap_stream,
- L2capMatchers.PacketPayloadWithMatchingPsm(self._psm))
-
- def get_event_queue(self):
- return self._our_le_l2cap_view.get_event_queue()
-
- def send(self, payload):
- self._device.l2cap.SendDynamicChannelPacket(
- l2cap_facade_pb2.DynamicChannelPacket(psm=self._psm, payload=payload))
-
- def close_channel(self):
- self._device.l2cap.CloseChannel(l2cap_facade_pb2.CloseChannelRequest(psm=self._psm))
-
- def set_traffic_paused(self, paused):
- self._device.l2cap.SetTrafficPaused(l2cap_facade_pb2.SetTrafficPausedRequest(psm=self._psm, paused=paused))
-
-
-class _ClassicConnectionResponseFutureWrapper(object):
- """
- The future object returned when we send a connection request from DUT. Can be used to get connection status and
- create the corresponding PyL2capDynamicChannel object later
- """
-
- def __init__(self, grpc_response_future, device, psm, l2cap_stream):
- self._grpc_response_future = grpc_response_future
- self._device = device
- self._psm = psm
- self._l2cap_stream = l2cap_stream
-
- def get_channel(self):
- return PyL2capChannel(self._device, self._psm, self._l2cap_stream)
-
-
-class PyL2cap(Closable):
-
- def __init__(self, device, cert_address, has_security=False):
- self._device = device
- self._cert_address = cert_address
- self._hci = PyHci(device)
- self._l2cap_stream = EventStream(self._device.l2cap.FetchL2capData(empty_proto.Empty()))
- self._security_connection_event_stream = EventStream(
- self._device.l2cap.FetchSecurityConnectionEvents(empty_proto.Empty()))
- if has_security == False:
- self._hci.register_for_events(hci_packets.EventCode.LINK_KEY_REQUEST)
-
- def close(self):
- safeClose(self._l2cap_stream)
- safeClose(self._security_connection_event_stream)
- safeClose(self._hci)
-
- def register_dynamic_channel(self, psm=0x33, mode=l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC):
- self._device.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=mode))
- return PyL2capChannel(self._device, psm, self._l2cap_stream)
-
- def connect_dynamic_channel_to_cert(self, psm=0x33, mode=l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC):
- """
- Send open Dynamic channel request to CERT.
- Get a future for connection result, to be used after CERT accepts request
- """
- self.register_dynamic_channel(psm, mode)
- response_future = self._device.l2cap.OpenChannel.future(
- l2cap_facade_pb2.OpenChannelRequest(psm=psm, remote=self._cert_address, mode=mode))
-
- return _ClassicConnectionResponseFutureWrapper(response_future, self._device, psm, self._l2cap_stream)
-
- def get_channel_queue_buffer_size(self):
- return self._device.l2cap.GetChannelQueueDepth(empty_proto.Empty()).size
-
- def initiate_connection_for_security(self):
- """
- Establish an ACL for the specific purpose of pairing devices
- """
- self._device.l2cap.InitiateConnectionForSecurity(self._cert_address)
-
- def get_security_connection_event_stream(self):
- """
- Stream of Link related events. Events are returned with an address.
- Events map to the LinkSecurityInterfaceListener callbacks
- """
- return self._security_connection_event_stream
-
- def security_link_hold(self):
- """
- Holds open the ACL indefinitely allowing for the security handshake
- to take place
- """
- self._device.l2cap.SecurityLinkHold(self._cert_address)
-
- def security_link_ensure_authenticated(self):
- """
- Triggers authentication process by sending HCI event AUTHENTICATION_REQUESTED
- """
- self._device.l2cap.SecurityLinkEnsureAuthenticated(self._cert_address)
-
- def security_link_release(self):
- """
- Releases a Held open ACL allowing for the ACL to time out after the default time
- """
- self._device.l2cap.SecurityLinkRelease(self._cert_address)
-
- def security_link_disconnect(self):
- """
- Immediately release and disconnect ACL
- """
- self._device.l2cap.SecurityLinkDisconnect(self._cert_address)
-
- def verify_security_connection(self):
- """
- Verify that we get a connection and a link key request
- """
- assertThat(self.get_security_connection_event_stream()).emits(
- lambda event: event.event_type == LinkSecurityInterfaceCallbackEventType.ON_CONNECTED)
- assertThat(self._hci.get_event_stream()).emits(HciMatchers.LinkKeyRequest())
-
-
-class PyLeL2capFixedChannel(IEventStream):
-
- def __init__(self, device, cid, l2cap_stream):
- self._device = device
- self._cid = cid
- self._le_l2cap_stream = l2cap_stream
- self._our_le_l2cap_view = FilteringEventStream(self._le_l2cap_stream,
- L2capMatchers.PacketPayloadWithMatchingCid(self._cid))
-
- def get_event_queue(self):
- return self._our_le_l2cap_view.get_event_queue()
-
- def send(self, payload):
- self._device.l2cap_le.SendFixedChannelPacket(
- l2cap_le_facade_pb2.FixedChannelPacket(cid=self._cid, payload=payload))
-
- def close_channel(self):
- self._device.l2cap_le.SetFixedChannel(
- l2cap_le_facade_pb2.SetEnableFixedChannelRequest(cid=self._cid, enable=False))
-
-
-class PyLeL2capDynamicChannel(IEventStream):
-
- def __init__(self, device, cert_address, psm, l2cap_stream):
- self._device = device
- self._cert_address = cert_address
- self._psm = psm
- self._le_l2cap_stream = l2cap_stream
- self._our_le_l2cap_view = FilteringEventStream(self._le_l2cap_stream,
- L2capMatchers.PacketPayloadWithMatchingPsm(self._psm))
-
- def get_event_queue(self):
- return self._our_le_l2cap_view.get_event_queue()
-
- def send(self, payload):
- self._device.l2cap_le.SendDynamicChannelPacket(
- l2cap_le_facade_pb2.DynamicChannelPacket(psm=self._psm, payload=payload))
-
- def close_channel(self):
- self._device.l2cap_le.CloseDynamicChannel(
- l2cap_le_facade_pb2.CloseDynamicChannelRequest(remote=self._cert_address, psm=self._psm))
-
-
-class _CreditBasedConnectionResponseFutureWrapper(object):
- """
- The future object returned when we send a connection request from DUT. Can be used to get connection status and
- create the corresponding PyLeL2capDynamicChannel object later
- """
-
- def __init__(self, grpc_response_future, device, cert_address, psm, le_l2cap_stream):
- self._grpc_response_future = grpc_response_future
- self._device = device
- self._cert_address = cert_address
- self._psm = psm
- self._le_l2cap_stream = le_l2cap_stream
-
- def get_status(self):
- return l2cap_packets.LeCreditBasedConnectionResponseResult(self._grpc_response_future.result().status)
-
- def get_channel(self):
- assertThat(self.get_status()).isEqualTo(l2cap_packets.LeCreditBasedConnectionResponseResult.SUCCESS)
- return PyLeL2capDynamicChannel(self._device, self._cert_address, self._psm, self._le_l2cap_stream)
-
-
-class PyLeL2cap(Closable):
-
- def __init__(self, device):
- self._device = device
- self._le_l2cap_stream = EventStream(self._device.l2cap_le.FetchL2capData(empty_proto.Empty()))
-
- def close(self):
- safeClose(self._le_l2cap_stream)
-
- def enable_fixed_channel(self, cid=4):
- self._device.l2cap_le.SetFixedChannel(l2cap_le_facade_pb2.SetEnableFixedChannelRequest(cid=cid, enable=True))
-
- def get_fixed_channel(self, cid=4):
- return PyLeL2capFixedChannel(self._device, cid, self._le_l2cap_stream)
-
- def register_coc(self, cert_address, psm=0x33, security_level=SecurityLevel.NO_SECURITY):
- self._device.l2cap_le.SetDynamicChannel(
- l2cap_le_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, enable=True, security_level=security_level))
- return PyLeL2capDynamicChannel(self._device, cert_address, psm, self._le_l2cap_stream)
-
- def connect_coc_to_cert(self, cert_address, psm=0x33):
- """
- Send open LE COC request to CERT. Get a future for connection result, to be used after CERT accepts request
- """
- self.register_coc(cert_address, psm)
- response_future = self._device.l2cap_le.OpenDynamicChannel.future(
- l2cap_le_facade_pb2.OpenDynamicChannelRequest(psm=psm, remote=cert_address))
-
- return _CreditBasedConnectionResponseFutureWrapper(response_future, self._device, cert_address, psm,
- self._le_l2cap_stream)
-
- def update_connection_parameter(self,
- conn_interval_min=0x10,
- conn_interval_max=0x10,
- conn_latency=0x0a,
- supervision_timeout=0x64,
- min_ce_length=12,
- max_ce_length=12):
- self._device.l2cap_le.SendConnectionParameterUpdate(
- l2cap_le_facade_pb2.ConnectionParameter(
- conn_interval_min=conn_interval_min,
- conn_interval_max=conn_interval_max,
- conn_latency=conn_latency,
- supervision_timeout=supervision_timeout,
- min_ce_length=min_ce_length,
- max_ce_length=max_ce_length))
diff --git a/gd/cert/py_le_acl_manager.py b/gd/cert/py_le_acl_manager.py
deleted file mode 100644
index c52a5abbc..000000000
--- a/gd/cert/py_le_acl_manager.py
+++ /dev/null
@@ -1,138 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from google.protobuf import empty_pb2 as empty_proto
-
-from cert.event_stream import EventStream
-from cert.event_stream import IEventStream
-from cert.captures import HciCaptures
-from cert.closable import Closable
-from cert.closable import safeClose
-from bluetooth_packets_python3 import hci_packets
-from cert.truth import assertThat
-from hci.facade import le_acl_manager_facade_pb2 as le_acl_manager_facade
-
-
-class PyLeAclManagerAclConnection(IEventStream, Closable):
-
- def __init__(self, le_acl_manager, address, remote_addr, handle, event_stream):
- """
- An abstract representation for an LE ACL connection in GD certification test
- :param le_acl_manager: The LeAclManager from this GD device
- :param address: The local device address
- :param remote_addr: Remote device address
- :param handle: Connection handle
- :param event_stream: The connection event stream for this connection
- """
- self.le_acl_manager = le_acl_manager
- # todo enable filtering after sorting out handles
- # self.our_acl_stream = FilteringEventStream(acl_stream, None)
- self.handle = handle
- self.connection_event_stream = event_stream
- self.acl_stream = EventStream(
- self.le_acl_manager.FetchAclData(le_acl_manager_facade.LeHandleMsg(handle=self.handle)))
- self.remote_address = remote_addr
- self.own_address = address
- self.disconnect_reason = None
-
- def close(self):
- safeClose(self.connection_event_stream)
- safeClose(self.acl_stream)
-
- def wait_for_disconnection_complete(self):
- disconnection_complete = HciCaptures.DisconnectionCompleteCapture()
- assertThat(self.connection_event_stream).emits(disconnection_complete)
- self.disconnect_reason = disconnection_complete.get().GetReason()
-
- def send(self, data):
- self.le_acl_manager.SendAclData(le_acl_manager_facade.LeAclData(handle=self.handle, payload=bytes(data)))
-
- def get_event_queue(self):
- return self.acl_stream.get_event_queue()
-
-
-class PyLeAclManager(Closable):
-
- def __init__(self, device):
- """
- LE ACL Manager for GD Certification test
- :param device: The GD device
- """
- self.le_acl_manager = device.hci_le_acl_manager
-
- self.incoming_connection_event_stream = None
- self.outgoing_connection_event_streams = {}
- self.active_connections = []
- self.next_token = 1
-
- def close(self):
- safeClose(self.incoming_connection_event_stream)
- for v in self.outgoing_connection_event_streams.values():
- safeClose(v[0])
- for connection in self.active_connections:
- safeClose(connection)
-
- def listen_for_incoming_connections(self):
- assertThat(self.incoming_connection_event_stream).isNone()
- self.incoming_connection_event_stream = EventStream(
- self.le_acl_manager.FetchIncomingConnection(empty_proto.Empty()))
-
- def connect_to_remote(self, remote_addr):
- token = self.initiate_connection(remote_addr)
- return self.complete_outgoing_connection(token)
-
- def wait_for_connection(self):
- self.listen_for_incoming_connections()
- return self.complete_incoming_connection()
-
- def cancel_connection(self, token):
- assertThat(token in self.outgoing_connection_event_streams).isTrue()
- pair = self.outgoing_connection_event_streams.pop(token)
- safeClose(pair[0])
- self.le_acl_manager.CancelConnection(pair[1])
-
- def initiate_connection(self, remote_addr):
- assertThat(self.next_token in self.outgoing_connection_event_streams).isFalse()
- self.outgoing_connection_event_streams[self.next_token] = EventStream(
- self.le_acl_manager.CreateConnection(remote_addr)), remote_addr
- token = self.next_token
- self.next_token += 1
- return token
-
- def complete_connection(self, event_stream):
- connection_complete = HciCaptures.LeConnectionCompleteCapture()
- assertThat(event_stream).emits(connection_complete)
- complete = connection_complete.get()
- handle = complete.GetConnectionHandle()
- remote = complete.GetPeerAddress()
- if complete.GetSubeventCode() == hci_packets.SubeventCode.ENHANCED_CONNECTION_COMPLETE:
- address = complete.GetLocalResolvablePrivateAddress()
- else:
- address = None
- connection = PyLeAclManagerAclConnection(self.le_acl_manager, address, remote, handle, event_stream)
- self.active_connections.append(connection)
- return connection
-
- def complete_incoming_connection(self):
- assertThat(self.incoming_connection_event_stream).isNotNone()
- event_stream = self.incoming_connection_event_stream
- self.incoming_connection_event_stream = None
- return self.complete_connection(event_stream)
-
- def complete_outgoing_connection(self, token):
- assertThat(self.outgoing_connection_event_streams[token]).isNotNone()
- event_stream = self.outgoing_connection_event_streams.pop(token)[0]
- return self.complete_connection(event_stream)
diff --git a/gd/cert/py_le_iso.py b/gd/cert/py_le_iso.py
deleted file mode 100644
index bc22f491c..000000000
--- a/gd/cert/py_le_iso.py
+++ /dev/null
@@ -1,180 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2021 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import logging
-
-from bluetooth_packets_python3 import hci_packets
-from cert.capture import Capture
-from cert.captures import SecurityCaptures
-from cert.closable import Closable
-from cert.closable import safeClose
-from cert.event_stream import EventStream, IEventStream
-from cert.event_stream import FilteringEventStream
-from cert.matchers import IsoMatchers
-from cert.truth import assertThat
-from datetime import timedelta
-from facade import common_pb2 as common
-from google.protobuf import empty_pb2 as empty_proto
-from iso import facade_pb2 as iso_facade_pb2
-
-
-class CisTestParameters():
-
- def __init__(self, cis_id, nse, max_sdu_m_to_s, max_sdu_s_to_m, max_pdu_m_to_s, max_pdu_s_to_m, phy_m_to_s,
- phy_s_to_m, bn_m_to_s, bn_s_to_m):
- self.cis_id = cis_id
- self.nse = nse
- self.max_sdu_m_to_s = max_sdu_m_to_s
- self.max_sdu_s_to_m = max_sdu_s_to_m
- self.max_pdu_m_to_s = max_pdu_m_to_s
- self.max_pdu_s_to_m = max_pdu_s_to_m
- self.phy_m_to_s = phy_m_to_s
- self.phy_s_to_m = phy_s_to_m
- self.bn_m_to_s = bn_m_to_s
- self.bn_s_to_m = bn_s_to_m
-
-
-class PyLeIsoStream(IEventStream):
-
- def __init__(self, device, cis_handle, iso_data_stream):
- self._device = device
- self._cis_handle = cis_handle
- self._le_iso_data_stream = iso_data_stream
- self._our_le_iso_cis_view = FilteringEventStream(
- self._le_iso_data_stream, IsoMatchers.PacketPayloadWithMatchingCisHandle(self._cis_handle))
-
- def get_event_queue(self):
- return self._our_le_iso_cis_view.get_event_queue()
-
- def send(self, payload):
- self._device.iso.SendIsoPacket(iso_facade_pb2.IsoPacket(handle=self._cis_handle, payload=payload))
-
-
-class PyLeIso(Closable):
- """
- Abstraction for iso tasks and GRPC calls
- """
-
- _iso_event_stream = None
-
- def __init__(self, device):
- logging.info("DUT: Init")
- self._device = device
- self._device.wait_channel_ready()
- self._iso_event_stream = EventStream(self._device.iso.FetchIsoEvents(empty_proto.Empty()))
- self._iso_data_stream = EventStream(self._device.iso.FetchIsoData(empty_proto.Empty()))
-
- def close(self):
- if self._iso_event_stream is not None:
- safeClose(self._iso_event_stream)
- else:
- logging.info("DUT: ISO Event Stream is None!")
- if self._iso_data_stream is not None:
- safeClose(self._iso_data_stream)
- else:
- logging.info("DUT: ISO Data Stream is None!")
-
- logging.info("DUT: close")
-
- def le_set_cig_parameters(self, cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, peripherals_clock_accuracy,
- packing, framing, max_transport_latency_m_to_s, max_transport_latency_s_to_m, cis_id,
- max_sdu_m_to_s, max_sdu_s_to_m, phy_m_to_s, phy_s_to_m, rtn_m_to_s, rtn_s_to_m):
-
- resp = self._device.iso.LeSetCigParameters(
- iso_facade_pb2.LeSetCigParametersRequest(
- cig_id=cig_id,
- sdu_interval_m_to_s=sdu_interval_m_to_s,
- sdu_interval_s_to_m=sdu_interval_s_to_m,
- peripherals_clock_accuracy=peripherals_clock_accuracy,
- packing=packing,
- framing=framing,
- max_transport_latency_m_to_s=max_transport_latency_m_to_s,
- max_transport_latency_s_to_m=max_transport_latency_s_to_m,
- cis_id=cis_id,
- max_sdu_m_to_s=max_sdu_m_to_s,
- max_sdu_s_to_m=max_sdu_s_to_m,
- phy_m_to_s=phy_m_to_s,
- phy_s_to_m=phy_s_to_m,
- rtn_m_to_s=rtn_m_to_s,
- rtn_s_to_m=rtn_s_to_m))
-
- def le_set_cig_parameters_test(self, cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, ft_m_to_s, ft_s_to_m,
- iso_interval, peripherals_clock_accuracy, packing, framing,
- max_transport_latency_m_to_s, max_transport_latency_s_to_m, cis_configs):
- configs = []
- for cc in cis_configs:
- configs.append(
- iso_facade_pb2.LeSetCigParametersTestRequest.LeCisParametersTestConfig(
- cis_id=cc.cis_id,
- nse=cc.nse,
- max_sdu_m_to_s=cc.max_sdu_m_to_s,
- max_sdu_s_to_m=cc.max_sdu_s_to_m,
- max_pdu_m_to_s=cc.max_pdu_m_to_s,
- max_pdu_s_to_m=cc.max_pdu_s_to_m,
- phy_m_to_s=cc.phy_m_to_s,
- phy_s_to_m=cc.phy_s_to_m,
- bn_m_to_s=cc.bn_m_to_s,
- bn_s_to_m=cc.bn_s_to_m,
- ))
-
- resp = self._device.iso.LeSetCigParameters(
- iso_facade_pb2.LeSetCigParametersTestRequest(
- cig_id=cig_id,
- sdu_interval_m_to_s=sdu_interval_m_to_s,
- sdu_interval_s_to_m=sdu_interval_s_to_m,
- ft_m_to_s=ft_m_to_s,
- ft_s_to_m=ft_s_to_m,
- iso_interval=iso_interval,
- peripherals_clock_accuracy=peripherals_clock_accuracy,
- packing=packing,
- framing=framing,
- max_transport_latency_m_to_s=max_transport_latency_m_to_s,
- max_transport_latency_s_to_m=max_transport_latency_s_to_m,
- cis_configs=configs))
-
- def wait_le_set_cig_parameters_complete(self):
- set_cig_params_complete_capture = PyLeIso.IsoCigComplete(iso_facade_pb2.IsoMsgType.ISO_PARAMETERS_SET_COMPLETE)
-
- assertThat(self._iso_event_stream).emits(set_cig_params_complete_capture, timeout=timedelta(seconds=5))
- return set_cig_params_complete_capture.get()
-
- @staticmethod
- def IsoCigComplete(type=None):
- return Capture(lambda event: True if event.message_type == type else False, PyLeIso._extract_cis_handles)
-
- @staticmethod
- def _extract_cis_handles(event):
- if event is None:
- return None
- return event.cis_handle
-
- def le_create_cis(self, cis_and_acl_handle_array):
- handles_pairs = []
- for hp_tmp in cis_and_acl_handle_array:
- handles_pairs.append(
- iso_facade_pb2.LeCreateCisRequest.HandlePair(cis_handle=hp_tmp[0], acl_handle=hp_tmp[1]))
-
- self._device.iso.LeCreateCis(iso_facade_pb2.LeCreateCisRequest(handle_pair=handles_pairs))
-
- def wait_le_cis_established(self):
- cis_establshed_capture = PyLeIso.IsoCigEstablished(iso_facade_pb2.IsoMsgType.ISO_CIS_ESTABLISHED)
- assertThat(self._iso_event_stream).emits(cis_establshed_capture, timeout=timedelta(seconds=5))
- cis_handle = cis_establshed_capture.get()[0]
- return PyLeIsoStream(self._device, cis_handle, self._iso_data_stream)
-
- @staticmethod
- def IsoCigEstablished(type):
- return Capture(lambda event: True if event.message_type == type else False, PyLeIso._extract_cis_handles)
diff --git a/gd/cert/py_le_security.py b/gd/cert/py_le_security.py
deleted file mode 100644
index 924ade935..000000000
--- a/gd/cert/py_le_security.py
+++ /dev/null
@@ -1,87 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import logging
-
-from bluetooth_packets_python3 import hci_packets
-from cert.captures import SecurityCaptures
-from cert.closable import Closable
-from cert.closable import safeClose
-from cert.event_stream import EventStream
-from cert.matchers import SecurityMatchers
-from cert.truth import assertThat
-from datetime import timedelta
-from facade import common_pb2 as common
-from google.protobuf import empty_pb2 as empty_proto
-from security.facade_pb2 import IoCapabilityMessage
-from security.facade_pb2 import AuthenticationRequirementsMessage
-from security.facade_pb2 import LeAuthRequirementsMessage
-from security.facade_pb2 import OobDataPresentMessage
-from security.facade_pb2 import UiCallbackMsg
-from security.facade_pb2 import UiCallbackType
-from security.facade_pb2 import HelperMsgType
-
-
-class PyLeSecurity(Closable):
- """
- Abstraction for security tasks and GRPC calls
- """
-
- _ui_event_stream = None
- _bond_event_stream = None
- _helper_event_stream = None
-
- def __init__(self, device):
- logging.info("DUT: Init")
- self._device = device
- self._device.wait_channel_ready()
- self._ui_event_stream = EventStream(self._device.security.FetchUiEvents(empty_proto.Empty()))
- self._bond_event_stream = EventStream(self._device.security.FetchBondEvents(empty_proto.Empty()))
- self._helper_event_stream = EventStream(self._device.security.FetchHelperEvents(empty_proto.Empty()))
-
- def get_ui_stream(self):
- return self._ui_event_stream
-
- def get_bond_stream(self):
- return self._bond_event_stream
-
- def wait_for_ui_event_passkey(self, timeout=timedelta(seconds=3)):
- display_passkey_capture = SecurityCaptures.DisplayPasskey()
- assertThat(self._ui_event_stream).emits(display_passkey_capture, timeout=timeout)
- return display_passkey_capture.get()
-
- def wait_device_disconnect(self, address):
- assertThat(self._helper_event_stream).emits(
- SecurityMatchers.HelperMsg(HelperMsgType.DEVICE_DISCONNECTED, address))
-
- def SetLeAuthRequirements(self, *args, **kwargs):
- return self._device.security.SetLeAuthRequirements(LeAuthRequirementsMessage(*args, **kwargs))
-
- def close(self):
- if self._ui_event_stream is not None:
- safeClose(self._ui_event_stream)
- else:
- logging.info("DUT: UI Event Stream is None!")
-
- if self._bond_event_stream is not None:
- safeClose(self._bond_event_stream)
- else:
- logging.info("DUT: Bond Event Stream is None!")
-
- if self._helper_event_stream is not None:
- safeClose(self._helper_event_stream)
- else:
- logging.info("DUT: Helper Event Stream is None!")
diff --git a/gd/cert/py_security.py b/gd/cert/py_security.py
deleted file mode 100644
index 21ee76f0b..000000000
--- a/gd/cert/py_security.py
+++ /dev/null
@@ -1,279 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import logging
-
-from bluetooth_packets_python3 import hci_packets
-from cert.closable import Closable
-from cert.closable import safeClose
-from cert.event_stream import EventStream
-from cert.truth import assertThat
-from facade import common_pb2 as common
-from google.protobuf import empty_pb2 as empty_proto
-
-from security.facade_pb2 import AuthenticationRequirements
-from security.facade_pb2 import AuthenticationRequirementsMessage
-from security.facade_pb2 import BondMsgType
-from security.facade_pb2 import SecurityPolicyMessage
-from security.facade_pb2 import IoCapabilities
-from security.facade_pb2 import IoCapabilityMessage
-from security.facade_pb2 import OobDataBondMessage
-from security.facade_pb2 import OobDataMessage
-from security.facade_pb2 import OobDataPresentMessage
-from security.facade_pb2 import UiMsgType
-from security.facade_pb2 import UiCallbackMsg
-from security.facade_pb2 import UiCallbackType
-
-
-class PySecurity(Closable):
- """
- Abstraction for security tasks and GRPC calls
- """
-
- _io_capabilities_name_lookup = {
- IoCapabilities.DISPLAY_ONLY: "DISPLAY_ONLY",
- IoCapabilities.DISPLAY_YES_NO_IO_CAP: "DISPLAY_YES_NO_IO_CAP",
- IoCapabilities.KEYBOARD_ONLY: "KEYBOARD_ONLY",
- IoCapabilities.NO_INPUT_NO_OUTPUT: "NO_INPUT_NO_OUTPUT",
- }
-
- _auth_reqs_name_lookup = {
- AuthenticationRequirements.NO_BONDING: "NO_BONDING",
- AuthenticationRequirements.NO_BONDING_MITM_PROTECTION: "NO_BONDING_MITM_PROTECTION",
- AuthenticationRequirements.DEDICATED_BONDING: "DEDICATED_BONDING",
- AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION: "DEDICATED_BONDING_MITM_PROTECTION",
- AuthenticationRequirements.GENERAL_BONDING: "GENERAL_BONDING",
- AuthenticationRequirements.GENERAL_BONDING_MITM_PROTECTION: "GENERAL_BONDING_MITM_PROTECTION",
- }
-
- _ui_event_stream = None
- _bond_event_stream = None
- _oob_data_event_stream = None
-
- def __init__(self, device):
- logging.info("DUT: Init")
- self._device = device
- self._device.wait_channel_ready()
- self._ui_event_stream = EventStream(self._device.security.FetchUiEvents(empty_proto.Empty()))
- self._bond_event_stream = EventStream(self._device.security.FetchBondEvents(empty_proto.Empty()))
- self._enforce_security_policy_stream = EventStream(
- self._device.security.FetchEnforceSecurityPolicyEvents(empty_proto.Empty()))
- self._disconnect_event_stream = EventStream(self._device.security.FetchDisconnectEvents(empty_proto.Empty()))
- self._oob_data_event_stream = EventStream(
- self._device.security.FetchGetOutOfBandDataEvents(empty_proto.Empty()))
-
- def create_bond(self, address, type):
- """
- Triggers stack under test to create bond
- """
- logging.info("DUT: Creating bond to '%s' from '%s'" % (str(address), str(self._device.address)))
- self._device.security.CreateBond(
- common.BluetoothAddressWithType(address=common.BluetoothAddress(address=address), type=type))
-
- def create_bond_out_of_band(self, address, type, p192_oob_data, p256_oob_data):
- """
- Triggers stack under test to create bond using Out of Band method
- """
-
- logging.info("DUT: Creating OOB bond to '%s' from '%s'" % (str(address), str(self._device.address)))
-
- self._device.security.CreateBondOutOfBand(
- OobDataBondMessage(
- address=common.BluetoothAddressWithType(address=common.BluetoothAddress(address=address), type=type),
- p192_data=OobDataMessage(
- address=common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=address), type=type),
- confirmation_value=bytes(bytearray(p192_oob_data[0])),
- random_value=bytes(bytearray(p192_oob_data[1]))),
- p256_data=OobDataMessage(
- address=common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=address), type=type),
- confirmation_value=bytes(bytearray(p256_oob_data[0])),
- random_value=bytes(bytearray(p256_oob_data[1])))))
-
- def remove_bond(self, address, type):
- """
- Removes bond from stack under test
- """
- self._device.security.RemoveBond(
- common.BluetoothAddressWithType(address=common.BluetoothAddress(address=address), type=type))
-
- def set_io_capabilities(self, io_capabilities):
- """
- Set the IO Capabilities used for the DUT
- """
- logging.info("DUT: setting IO Capabilities data to '%s'" % self._io_capabilities_name_lookup.get(
- io_capabilities, "ERROR"))
- self._device.security.SetIoCapability(IoCapabilityMessage(capability=io_capabilities))
-
- def set_authentication_requirements(self, auth_reqs):
- """
- Establish authentication requirements for the stack
- """
- logging.info("DUT: setting Authentication Requirements data to '%s'" % self._auth_reqs_name_lookup.get(
- auth_reqs, "ERROR"))
- self._device.security.SetAuthenticationRequirements(AuthenticationRequirementsMessage(requirement=auth_reqs))
-
- def __send_ui_callback(self, address, callback_type, b, uid, pin):
- """
- Send a callback from the UI as if the user pressed a button on the dialog
- """
- logging.info("DUT: Sending user input response uid: %d; response: %s" % (uid, b))
- self._device.security.SendUiCallback(
- UiCallbackMsg(
- message_type=callback_type,
- boolean=b,
- unique_id=uid,
- pin=bytes(pin),
- address=common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=address),
- type=common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)))
-
- def enable_secure_simple_pairing(self):
- """
- This is called when you want to enable SSP for testing
- Since the stack under test already enables it by default
- we do not need to do anything here for the time being
- """
- pass
-
- def enable_secure_connections(self):
- pass
-
- def accept_pairing(self, cert_address, reply_boolean):
- """
- Here we pass, but in cert we perform pairing flow tasks.
- This was added here in order to be more dynamic, but the stack
- under test will handle the pairing flow.
- """
- pass
-
- def accept_oob_pairing(self, cert_address, reply_boolean):
- """
- Here we pass, but in cert we perform pairing flow tasks.
- This was added here in order to be more dynamic, but the stack
- under test will handle the pairing flow.
- """
- pass
-
- def wait_for_passkey(self, cert_address):
- """
- Respond to the UI event
- """
- passkey = -1
-
- def get_passkey(event):
- if event.message_type == UiMsgType.DISPLAY_PASSKEY:
- nonlocal passkey
- passkey = event.numeric_value
- return True
- return False
-
- logging.info("DUT: Waiting for expected UI event")
- assertThat(self._ui_event_stream).emits(get_passkey)
- return passkey
-
- def input_pin(self, cert_address, pin):
- """
- Respond to the UI event
- """
- logging.info("DUT: Inputting pin code: %s" % str(pin))
- self.on_user_input(
- cert_address=cert_address, reply_boolean=True, expected_ui_event=UiMsgType.DISPLAY_PIN_ENTRY, pin=pin)
-
- def on_user_input(self, cert_address, reply_boolean, expected_ui_event, pin=[]):
- """
- Respond to the UI event
- """
- if expected_ui_event is None:
- return
-
- ui_id = -1
-
- def get_unique_id(event):
- if event.message_type == expected_ui_event:
- nonlocal ui_id
- ui_id = event.unique_id
- return True
- return False
-
- logging.info("DUT: Waiting for expected UI event")
- assertThat(self._ui_event_stream).emits(get_unique_id)
- callback_type = UiCallbackType.YES_NO if len(pin) == 0 else UiCallbackType.PIN
- self.__send_ui_callback(cert_address, callback_type, reply_boolean, ui_id, pin)
-
- def get_address(self):
- return self._device.address
-
- def wait_for_bond_event(self, expected_bond_event):
- """
- A bond event will be triggered once the bond process
- is complete. For the DUT we need to wait for it,
- for Cert it isn't needed.
- """
- logging.info("DUT: Waiting for Bond Event: %s " % expected_bond_event)
- assertThat(self._bond_event_stream).emits(
- lambda event: event.message_type == expected_bond_event or logging.info("DUT: Actual Bond Event: %s" % event.message_type)
- )
-
- def wait_for_enforce_security_event(self, expected_enforce_security_event):
- """
- We expect a 'True' or 'False' from the enforce security call
-
- This interface will allow the caller to wait for a callback
- result from enforcing security policy over the facade.
- """
- logging.info("DUT: Waiting for enforce security event")
- assertThat(self._enforce_security_policy_stream).emits(
- lambda event: event.result == expected_enforce_security_event or logging.info(event.result))
-
- def wait_for_disconnect_event(self):
- """
- The Address is expected to be returned
- """
- logging.info("DUT: Waiting for Disconnect Event")
- assertThat(self._disconnect_event_stream).emits(lambda event: logging.info("event: %s" % event.address) or True)
-
- def enforce_security_policy(self, address, type, policy):
- """
- Call to enforce classic security policy
- """
- self._device.security.EnforceSecurityPolicy(
- SecurityPolicyMessage(
- address=common.BluetoothAddressWithType(address=common.BluetoothAddress(address=address), type=type),
- policy=policy))
-
- def get_oob_data_from_controller(self, oob_data_present):
- self._device.security.GetOutOfBandData(empty_proto.Empty())
- oob_data = []
-
- def get_oob_data(event):
- nonlocal oob_data
- oob_data = [
- list(event.p192_data.confirmation_value),
- list(event.p192_data.random_value), [0 for i in range(0, 16)], [0 for i in range(0, 16)]
- ]
- return True
-
- assertThat(self._oob_data_event_stream).emits(get_oob_data)
- return oob_data
-
- def close(self):
- safeClose(self._ui_event_stream)
- safeClose(self._bond_event_stream)
- safeClose(self._enforce_security_policy_stream)
- safeClose(self._disconnect_event_stream)
- safeClose(self._oob_data_event_stream)
diff --git a/gd/cert/python3.8-gd b/gd/cert/python3.8-gd
new file mode 100755
index 000000000..2d9640ea6
--- /dev/null
+++ b/gd/cert/python3.8-gd
@@ -0,0 +1,2 @@
+#! /bin/bash
+PYTHONPATH=$PYTHONPATH:$ANDROID_BUILD_TOP/out/host/linux-x86/lib64:$ANDROID_BUILD_TOP/system/bt/gd:$ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py python3.8 "$@"
diff --git a/gd/cert/run b/gd/cert/run
deleted file mode 100755
index e666c5fbb..000000000
--- a/gd/cert/run
+++ /dev/null
@@ -1,490 +0,0 @@
-#! /bin/bash
-
-YELLOW="\033[1;33m"
-NOCOLOR="\033[0m"
-BLUE="\033[1;34m"
-RED="\033[1;91m"
-
-function happy_hedgehog {
- echo -e "\t${BLUE}"
- echo -e "\t ___------__"
- echo -e "\t |\__-- /\ _-"
- echo -e "\t |/_ __ -"
- echo -e "\t // \ / \ /__"
- echo -e "\t | 0 | 0 |__ --_ Gotta go fast!"
- echo -e "\t \\____-- __ \ ___-"
- echo -e "\t ( @ __/ / /_"
- echo -e "\t -_____--- --_"
- echo -e "\t // \ \\ ___-"
- echo -e "\t //|\__/ \\ \\"
- echo -e "\t \_-\_____/ \-\\"
- echo -e "\t // \\--\|"
- echo -e "\t ${RED}____${BLUE}// ||${RED}_"
- echo -e "\t${RED} /_____\ /___\\"
- echo -e "${NOCOLOR}"
-}
-
-function sad_hedgehog {
- echo -e "\t${BLUE}"
- echo -e "\t ___------__"
- echo -e "\t |\__-- /\ _-"
- echo -e "\t |/_ __ -"
- echo -e "\t // \ / \ /__"
- echo -e "\t | 0 | 0 |__ --_ Gotta go sllloowwww!"
- echo -e "\t \\____-- __ \ ___-"
- echo -e "\t ( @ __ / /_"
- echo -e "\t -_____--- --_"
- echo -e "\t // \ \\ ___-"
- echo -e "\t //|\__/ \\ \\"
- echo -e "\t \_-\_____/ \-\\"
- echo -e "\t // \\--\|"
- echo -e "\t ${RED} ____${BLUE}// ||${RED}_"
- echo -e "\t${RED} /_____\ /___\\"
- echo -e "{$NOCOLOR}"
-}
-
-function check_environment {
- if [[ -z "${ANDROID_BUILD_TOP}" ]] || [[ -z "${ANDROID_HOST_OUT}" ]] ; then
- echo -e "${RED}ANDROID_BUILD_TOP${NOCOLOR} or ${RED}ANDROID_HOST_OUT${NOCOLOR} is not set for host run"
- echo -e "Navigate to android root and run:"
- echo -e "${YELLOW}"
- echo -e ". build/envsetup.sh"
- echo -e "lunch <fish>"
- echo -e "${NOCOLOR}"
- echo
- exit 1
- fi
- if ! [ -x "$(command -v python3.9)" ] ; then
- echo -e "${RED}You must have python 3.9 installed${NOCOLOR}"
- exit 1
- fi
- python3.9 -m virtualenv --version
- if [[ $? -ne 0 ]] ; then
- echo "${RED}virtualenv not installed for python3.9${NOCOLOR}"
- echo "${RED}Please run 'python3.9 -m pip install virtualenv' to install it${NOCOLOR}"
- exit 1
- fi
-}
-
-ASHMEM_OUT="/dev/shm/out"
-ASHMEM_DIST="${ASHMEM_OUT}/dist"
-ASHMEM_VENV="${ASHMEM_DIST}/bluetooth_venv"
-ASHMEM_GOTTA_GO_FAST="/dev/shm/gottagofast"
-ASHMEM_HOST_LOGS="${ASHMEM_GOTTA_GO_FAST}/logs"
-ASHMEM_OUT_TARGET="${ASHMEM_GOTTA_GO_FAST}/target"
-ASHMEM_SOONG="${ASHMEM_GOTTA_GO_FAST}/out/soong"
-CERT_HOST_LOGS="/tmp/logs/HostOnlyCert"
-CERT_DEVICE_LOGS="TODO: Add this"
-CERT_TEST_VENV=${ANDROID_BUILD_TOP}/out/dist/bluetooth_venv
-OUT_TARGET="${ANDROID_BUILD_TOP}/out/target"
-TEST_CONFIG="${ANDROID_BUILD_TOP}/system/bt/gd/cert/host_config.json"
-TEST_FILTER="-tf ${ANDROID_BUILD_TOP}/system/bt/gd/cert/all_cert_testcases"
-CPP_BUILD_TARGET="bluetooth_stack_with_facade root-canal bluetooth_packets_python3"
-RUST_BUILD_TARGET="bluetooth_with_facades root-canal bluetooth_packets_python3"
-BUILD_TARGET=$CPP_BUILD_TARGET
-
-CLEAN_VENV=false
-GOTTA_GO_FAST=false
-NUM_REPETITIONS="1"
-SKIP_SOONG_BUILD=false
-USE_ASHMEM_VENV=true
-VERBOSE_MODE=false
-
-# Directory for test configs to modify
-CONFIG_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" >/dev/null 2>&1 && pwd )"
-
-## Verify devices connected and valid
-DUT_SERIAL="DUT Not Set"
-DUT_ADB="DUT Not Set"
-DUT_NAME="DUT Not Set"
-
-# Used for position arguments needed for later
-POSITIONAL=()
-function parse_options {
- while [[ $# -gt 0 ]]
- do
- key="$1"
- case $key in
- # This will delete the existing venv before running the test
- # If you updated external libraries such as ACTS, you need to add this flag
- --clean)
- CLEAN_VENV=true
- shift # past argument
- ;;
- --help)
- echo
- echo -e "${YELLOW}Help menu${NOCOLOR}"
- echo -e "==================================="
- echo -e "${BLUE} --clean${NOCOLOR}"
- echo -e " Clean the virtul environment; use if ACTS has been updated."
- echo -e "${BLUE} --disable-ashmem-venv${NOCOLOR}"
- echo -e " Places the virtual environment on disk rather than in ashmem which is default."
- echo -e "${BLUE} --gotta-go-fast${NOCOLOR}"
- echo -e " Makes use of ashmem as best as possible for targeted speed increases."
- echo -e "${BLUE} --device${NOCOLOR}"
- echo -e " Run the test on the 2 real devices."
- echo -e "${BLUE} --rust${NOCOLOR}"
- echo -e " Run the test using the rust implementation on the 2 real devices."
- echo -e "${BLUE} --rhost${NOCOLOR}"
- echo -e " Run the test using the rust implementation on the host."
- echo -e "${BLUE} --repeat=<N>${NOCOLOR}"
- echo -e " Repeat the test sequence N (int) number of times."
- echo -e "${BLUE} --skip-soong-build${NOCOLOR}"
- echo -e " Skips building soong targets. Use when you are just modifying simple python files."
- echo -e "${BLUE} --test_config=<configfile>${NOCOLOR}"
- echo -e " Override default test configuration."
- echo -e "${BLUE} --verbose${NOCOLOR}"
- echo -e " Displays device logs and test logs to output."
- echo
- echo -e "Usage: $0 [--clean|--host|--repeat=<N>|--test_config=<config>] [TestGroupName[:IndividualTestName]]"
- echo -e " ${YELLOW}e.g."
- echo -e " $0 --host --clean SecurityTest"
- echo -e " $0 --host --verbose SecurityTest:test_dut_initiated_display_only_display_only ${NOCOLOR}"
- echo
- shift
- exit 0
- ;;
- # This will cause the bluetooth_venv to NOT be created in ashmem
- # Using ashmem increases --clean build times by 40% (~21 seconds on my machine)
- --disable-ashmem-venv)
- USE_ASHMEM_VENV=false
- shift # past argument
- ;;
- --gotta-go-fast)
- GOTTA_GO_FAST=true
- shift # past argument
- ;;
- --device)
- TEST_CONFIG="${ANDROID_BUILD_TOP}/system/bt/gd/cert/devices_config.json"
- RR="$(cat ${TEST_CONFIG}|grep \"CERT\\\|DUT\")"
- if [ "$RR" != "" ]; then
- DUT_SERIAL="$(menu-adb DUT)"
- DUT_ADB="adb -s ${DUT_SERIAL}"
- DUT_NAME="$(adb devices -l | grep -v "List of device" | grep ${DUT_SERIAL} | awk '{ print $6 }' | cut -d ':' -f 2)"
- CERT_SERIAL="$(menu-adb CERT)"
- CERT_ADB="adb -s ${CERT_SERIAL}"
- CERT_NAME="$(adb devices -l | grep -v "List of device" | grep ${CERT_SERIAL} | awk '{ print $6 }' | cut -d ':' -f 2)"
-
- if [ "${CERT_SERIAL}" == "${DUT_SERIAL}" ]; then
- echo
- echo "ERROR: CERT and DUT cannot be the same device, or you only have one device connected!"
- echo
- exit 1
- fi
-
- ## Set android devices in config
- pushd .
- cd "${CONFIG_DIR}"
- popd
- sed -i "s/\"DUT\"/\"${DUT_SERIAL}\"/g" ${CONFIG_DIR}/devices_config.json
- sed -i "s/\"CERT\"/\"${CERT_SERIAL}\"/g" ${CONFIG_DIR}/devices_config.json
- fi
- shift # past argument
- ;;
- # Repeat running the specified test cases by N times in one single setup
- --repeat=*)
- NUM_REPETITIONS="${key#*=}"
- shift # past argument
- ;;
- --skip-soong-build)
- SKIP_SOONG_BUILD=true
- shift
- ;;
- --test_config=*)
- TEST_CONFIG="${key#*=}"
- shift # past argument
- ;;
- --rust)
- BUILD_TARGET=$RUST_BUILD_TARGET
- export RUST_BACKTRACE=1
- TEST_CONFIG=$ANDROID_BUILD_TOP/system/bt/gd/cert/rust_android_devices_config.json
- shift # past argument
- ;;
- --rhost)
- export RUST_BACKTRACE=1
- BUILD_TARGET=$RUST_BUILD_TARGET
- TEST_CONFIG=$ANDROID_BUILD_TOP/system/bt/gd/cert/rust_host_config.json
- shift # past argument
- ;;
- # This will log everything to both log file and stdout
- --verbose)
- VERBOSE_MODE=true
- shift # past argument
- ;;
- *) # unknown option
- POSITIONAL+=("$1") # save it in an array for later
- shift # past argument
- ;;
- esac
- done
- set -- "${POSITIONAL[@]}" # restore positional parameters
-
- # Set the test filter
- if [[ -n "$1" ]] ; then
- TEST_FILTER="-tc $1"
- fi
-
- INSTALL_ARGS="--reuse-acts"
- if [ "$CLEAN_VENV" == true ] ; then
- echo -e "${YELLOW}Cleaning up existing virtualenv${NOCOLOR}"
- rm -rf $CERT_TEST_VENV/*
- rm -rf $CERT_TEST_VENV
- mkdir -p ${CERT_TEST_VENV}
- INSTALL_ARGS=""
- else
- echo -e "${YELLOW}Try to reuse existing virtualenv at ${CERT_TEST_VENV}${NOCOLOR}"
- fi
-
-}
-
-function soong_build {
- if [ "$CLEAN_VENV" == true ] ; then
- $ANDROID_BUILD_TOP/build/soong/soong_ui.bash --build-mode --"modules-in-a-dir" --dir="${ANDROID_BUILD_TOP}/system/bt/gd" dist $BUILD_TARGET -j20
- if [[ $? -ne 0 ]] ; then
- echo "Failed to build ${BUILD_TARGET}"
- exit 1
- fi
- else
- $ANDROID_BUILD_TOP/build/soong/soong_ui.bash --build-mode --"all-modules" --dir="${ANDROID_BUILD_TOP}/system/bt/gd" $BUILD_TARGET -j20
- if [[ $? -ne 0 ]] ; then
- echo "Failed to build ${BUILD_TARGET}"
- exit 1
- fi
- fi
-}
-
-function setup_venv {
- # Make venv in memory, decreases --clean build times by 40%
- # Caveat is you lose the venv if the computer reboots
- if [ "${USE_ASHMEM_VENV}" == true ] ; then
- echo -e "${BLUE}Using ashmem virtual environment.${NOCOLOR}"
- if [[ ! -L ${CERT_TEST_VENV} ]] ; then
- echo -e "${BLUE}"
- echo -ne "Creating ashmem dist folder..."
- mkdir -p "${ASHMEM_VENV}"
- # Ensure the directory doesn't exist
- rm -rf "${CERT_TEST_VENV}"
- echo -e "Done"
- echo -ne "Sym linking ${ASHMEM_VENV} to ${CERT_TEST_VENV}..."
- ln -s "${ASHMEM_VENV}" "${CERT_TEST_VENV}"
- echo -e "Done"
- echo -e "${NOCOLOR}"
- fi
- else
- echo -e "${RED}Not using ashmem virtual environment.${NOCOLOR}"
- if [[ -L ${CERT_TEST_VENV} ]] ; then
- echo -e "${RED}"
- echo -en "Removing sym link from ${ASHMEM_VENV} to ${CERT_TEST_VENV}..."
- rm -rf ""${ASHMEM_VENV} "${CERT_TEST_VENV}"
- echo -e "Done"
- echo -en "Cleaning up memory..."
- rm -rf "${ASHMEM_VENV}"
- echo -e "Done"
- echo -e "${NOCOLOR}"
- fi
- fi
- python3.9 -m virtualenv --python `which python3.9` "${CERT_TEST_VENV}"
- if [[ $? -ne 0 ]] ; then
- echo "Error setting up virtualenv"
- exit 1
- fi
-
- unzip -o -q "${ANDROID_BUILD_TOP}/out/dist/bluetooth_cert_tests.zip" -d "${CERT_TEST_VENV}/acts"
- if [[ $? -ne 0 ]] ; then
- echo "Error unzipping bluetooth_cert_tests.zip"
- exit 1
- fi
-
- venv_common
-}
-
-function incremental_venv {
-#LINT.IfChange
- HOST_BIN="${ANDROID_BUILD_TOP}/out/host/linux-x86/bin"
- HOST_LIB="${ANDROID_BUILD_TOP}/out/host/linux-x86/lib64"
- DEST_DIR="${ANDROID_BUILD_TOP}/out/dist/bluetooth_venv/acts"
- DEST_LIB_DIR="${DEST_DIR}/lib64"
- cp {$HOST_BIN,$DEST_DIR}/bluetooth_stack_with_facade
- cp {$HOST_BIN,$DEST_DIR}/bluetooth_with_facades
- cp {$HOST_BIN,$DEST_DIR}/root-canal
-
- cp {$HOST_LIB,$DEST_DIR}/bluetooth_packets_python3.so
-
- cp {$HOST_LIB,$DEST_LIB_DIR}/libbase.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libbluetooth_gd.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libc++.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libchrome.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libcrypto-host.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libevent-host.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libgrpc++_unsecure.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libgrpc++.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libgrpc_wrap.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/liblog.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libssl-host.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libz-host.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libprotobuf-cpp-full.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libunwindstack.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/liblzma.so
- cp {$HOST_LIB,$DEST_LIB_DIR}/libbacktrace.so
-
- for i in `find ${ANDROID_BUILD_TOP}/system/bt/gd -name "*.py" -type f`; do
- cp {${ANDROID_BUILD_TOP}/system/bt/gd,$DEST_DIR}${i#${ANDROID_BUILD_TOP}/system/bt/gd}
- done
-#LINT.ThenChange(../Android.mk)
-
- venv_common
-}
-
-function venv_common {
- $(echo "${CERT_TEST_VENV}/bin/python" "${CERT_TEST_VENV}/acts/setup.py" --quiet build --force)
- if [[ $? -ne 0 ]] ; then
- echo "Error building GD Python libraries"
- echo -e "${YELLOW}NOTE:${NOCOLOR} To build external libraries the first time, please add --clean option."
- exit 1
- fi
-
- $(echo "${CERT_TEST_VENV}/bin/python" "${CERT_TEST_VENV}/acts/setup.py" --quiet install --skip-build --force "${INSTALL_ARGS}")
- if [[ $? -ne 0 ]] ; then
- echo "Error installing GD Python libraries"
- exit 1
- fi
-
-"${CERT_TEST_VENV}/bin/python" -c "
-import bluetooth_packets_python3 as bp3
-bp3.BaseStruct
-"
-if [[ $? -ne 0 ]] ; then
- echo "Setup failed as bluetooth_packets_python3 cannot be imported"
- exit 1
-fi
-
-if [ "${VERBOSE_MODE}" == true ] ; then
- TEMP_CONFIG=/tmp/temp_acts_config.json
- cat "${TEST_CONFIG}" | "${CERT_TEST_VENV}/bin/python" -c "
-import sys
-import json
-from acts import keys
-config = json.load(sys.stdin)
-config['verbose_mode'] = True
-print(json.dumps(config))
- " > "${TEMP_CONFIG}"
- TEST_CONFIG="${TEMP_CONFIG}"
- if [[ $? -ne 0 ]] ; then
- echo "Setup failed as verbose mode is chosen but cannot be enabled"
- exit 1
- fi
-fi
-}
-
-function gotta_go_fast {
- if [ "${GOTTA_GO_FAST}" == true ] ; then
- # Call here to explicitly note the flag is in use
- happy_hedgehog
- if [[ ! -L "${CERT_HOST_LOGS}" ]] ; then
- rm -rf "${CERT_HOST_LOGS}"
- mkdir -p "${ASHMEM_HOST_LOGS}"
- ln -s "${ASHMEM_HOST_LOGS}" "${CERT_HOST_LOGS}"
- fi
-
- if [[ ! -L "${OUT_TARGET}" ]] ; then
- rm -rf "${OUT_TARGET}"
- mkdir -p "${ASHMEM_OUT_TARGET}"
- ln -s "${ASHMEM_OUT_TARGET}" "${OUT_TARGET}"
- fi
- else
- if [[ -L "${CERT_HOST_LOGS}" ]] ; then
- # Call here so we don't spam anyone not using the flag
- sad_hedgehog
- rm -rf "${CERT_HOST_LOGS}"
- rm -rf "${ASHMEM_HOST_LOGS}"
- fi
-
- if [[ -L "${OUT_TARGET}" ]] ; then
- rm -rf "${OUT_TARGET}"
- rm -rf "${ASHMEM_OUT_TARGET}"
- fi
- fi
-}
-
-function run_tests {
- for n in $(seq "${NUM_REPETITIONS}"); do
- $(echo "${CERT_TEST_VENV}/bin/python" "${CERT_TEST_VENV}/bin/act.py" \
- -c "${TEST_CONFIG}" \
- "${TEST_FILTER}" \
- -tp "${CERT_TEST_VENV}"/acts)
- done
-
- if [ "${CLEAN_VENV}" != true ] ; then
- echo -e "${YELLOW}NOTE:${NOCOLOR} Completed tests using existing external libraries in virtualenv."
- echo -e "${YELLOW}NOTE:${NOCOLOR} To update external libraries, please add --clean option."
- fi
-}
-
-function menu-adb() {
- TMP=$(adb devices -l | grep -v "List of device" | awk '{ print $1 }')
- # TODO(optedoblivion): If the device doesn't have a name (offline), it misnames them
- NTMP=$(adb devices -l | grep -v "List of device" | awk '{ print $6 }' | cut -d ':' -f 2)
- SERIALS=($TMP)
- DEVICES=($NTMP)
- LEN=${#SERIALS[@]}
- result=0
- if [ $LEN -lt 1 ]; then
- echo "No devices connected!"
- return 1
- fi
-
- if [ "$LEN" == "" ]; then
- LEN=0
- fi
-
- answer=0
-
- DEVICE_NAME="$1 device"
-
- if [ $LEN -gt 1 ]; then
- echo "+-------------------------------------------------+" 1>&2
- echo "| Choose a ${DEVICE_NAME}: " 1>&2
- echo "+-------------------------------------------------+" 1>&2
- echo "| |" 1>&2
- let fixed_len=$LEN-1
- for i in `seq 0 $fixed_len`;
- do
- serial=${SERIALS[i]}
- device=${DEVICES[i]}
- echo "| $i) $serial $device" 1>&2
- ## TODO[MSB]: Find character count, fill with space and ending box wall
- done
- echo "| |" 1>&2
- echo "+-------------------------------------------------+" 1>&2
- echo 1>&2
- echo -n "Index number: " 1>&2
- read answer
- fi
-
- if [ $answer -ge $LEN ]; then
- echo
- echo "Please choose a correct index!" 1>&2
- echo
- return 1
- fi
-
- SERIAL=${SERIALS[$answer]}
- echo $SERIAL
-}
-
-function main {
- check_environment
- parse_options $@
- if [[ "${SKIP_SOONG_BUILD}" != true ]] ; then
- soong_build
- fi
- if [ "$CLEAN_VENV" == true ] ; then
- setup_venv
- else
- incremental_venv
- fi
- gotta_go_fast
- run_tests
-}
-
-main $@
diff --git a/gd/cert/run_cert_facade_only.sh b/gd/cert/run_cert_facade_only.sh
new file mode 100755
index 000000000..e7b011043
--- /dev/null
+++ b/gd/cert/run_cert_facade_only.sh
@@ -0,0 +1,13 @@
+#! /bin/bash
+
+if [[ -z "${ANDROID_BUILD_TOP}" ]]; then
+ echo "ANDROID_BUILD_TOP is not set"
+fi
+
+if [[ -z "${ANDROID_HOST_OUT}" ]]; then
+ echo "ANDROID_HOST_OUT is not set for host run"
+fi
+
+unzip -o -q $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py.zip -d $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py
+
+PYTHONPATH=$PYTHONPATH:$ANDROID_BUILD_TOP/out/host/linux-x86/lib64:$ANDROID_BUILD_TOP/system/bt/gd:$ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py python3.8 `which act.py` -c $ANDROID_BUILD_TOP/system/bt/gd/cert/host_only_config_facade_only.json -tf $ANDROID_BUILD_TOP/system/bt/gd/cert/cert_testcases_facade_only -tp $ANDROID_BUILD_TOP/system/bt/gd
diff --git a/gd/cert/run_device_cert.sh b/gd/cert/run_device_cert.sh
new file mode 100755
index 000000000..1da2bcc4c
--- /dev/null
+++ b/gd/cert/run_device_cert.sh
@@ -0,0 +1,6 @@
+#! /bin/bash
+
+unzip -q -o $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py.zip -d $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py
+
+# For bluetooth_packets_python3
+PYTHONPATH=$PYTHONPATH:$ANDROID_BUILD_TOP/out/host/linux-x86/lib64:$ANDROID_BUILD_TOP/system/bt/gd:$ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py python3.8 `which act.py` -c $ANDROID_BUILD_TOP/system/bt/gd/cert/android_devices_config.json -tf $ANDROID_BUILD_TOP/system/bt/gd/cert/cert_testcases_facade_only -tp $ANDROID_BUILD_TOP/system/bt/gd
diff --git a/gd/cert/run_pts_l2cap.sh b/gd/cert/run_pts_l2cap.sh
index 356b31f9b..313cbb72c 100755
--- a/gd/cert/run_pts_l2cap.sh
+++ b/gd/cert/run_pts_l2cap.sh
@@ -1,5 +1,6 @@
#! /bin/bash
-source $ANDROID_BUILD_TOP/system/bt/cert/run \
- --test_config=$ANDROID_BUILD_TOP/system/bt/gd/cert/pts.json \
- --test_file=$ANDROID_BUILD_TOP/system/bt/gd/cert/pts_l2cap_testcase \ No newline at end of file
+unzip -u $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py.zip -d $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py
+
+# For bluetooth_packets_python3
+PYTHONPATH=$PYTHONPATH:$ANDROID_BUILD_TOP/out/host/linux-x86/lib64:$ANDROID_BUILD_TOP/system/bt/gd:$ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py python3.8 `which act.py` -c $ANDROID_BUILD_TOP/system/bt/gd/cert/pts.json -tf $ANDROID_BUILD_TOP/system/bt/gd/cert/pts_l2cap_testcase -tp $ANDROID_BUILD_TOP/system/bt/gd
diff --git a/gd/cert/rust_android_devices_config.json b/gd/cert/rust_android_devices_config.json
deleted file mode 100644
index 6d76310dd..000000000
--- a/gd/cert/rust_android_devices_config.json
+++ /dev/null
@@ -1,55 +0,0 @@
-{ "_description": "Bluetooth cert testing",
- "testbed":
- [
- {
- "_description": "Two Android devices cert testbed",
- "name": "AndroidDeviceCert",
- "GdDevice":
- [
- {
- "grpc_port": "8898",
- "grpc_root_server_port": "8896",
- "signal_port": "8894",
- "label": "cert",
- "serial_number": "CERT",
- "name": "Cert Device",
- "cmd":
- [
- "adb",
- "-s",
- "$(serial_number)",
- "shell",
- "/system/bin/bluetooth_with_facadas",
- "--grpc-port=$(grpc_port)",
- "--root-server-port=$(grpc_root_server_port)",
- "--btsnoop=/data/misc/bluetooth/logs/btsnoop_hci.log",
- "--btconfig=/data/misc/bluedroid/bt_config.conf",
- "--signal-port=$(signal_port)"
- ]
- },
- {
- "grpc_port": "8899",
- "grpc_root_server_port": "8897",
- "signal_port": "8895",
- "label": "dut",
- "serial_number": "DUT",
- "name": "DUT Device",
- "cmd":
- [
- "adb",
- "-s",
- "$(serial_number)",
- "shell",
- "/system/bin/bluetooth_with_facades",
- "--grpc-port=$(grpc_port)",
- "--root-server-port=$(grpc_root_server_port)",
- "--btsnoop=/data/misc/bluetooth/logs/btsnoop_hci.log",
- "--btconfig=/data/misc/bluedroid/bt_config.conf",
- "--signal-port=$(signal_port)"
- ]
- }
- ]
- }
- ],
- "logpath": "/tmp/logs"
-}
diff --git a/gd/cert/set_up_acts.sh b/gd/cert/set_up_acts.sh
new file mode 100755
index 000000000..a902efce2
--- /dev/null
+++ b/gd/cert/set_up_acts.sh
@@ -0,0 +1,109 @@
+#! /bin/bash
+#
+# Script to setup environment to execute bluetooth certification stack
+#
+# for more info, see go/acts
+
+## Android build main build setup script relative to top level android source root
+BUILD_SETUP=./build/envsetup.sh
+
+function UsageAndroidTree {
+ cat<<EOF
+Ensure invoked from within the android source tree
+EOF
+}
+
+function UsageSourcedNotExecuted {
+ cat<<EOF
+Ensure script is SOURCED and not executed to persist the build setup
+e.g.
+source $0
+EOF
+}
+
+function UpFind {
+ while [[ $PWD != / ]] ; do
+ rc=$(find "$PWD" -maxdepth 1 "$@")
+ if [ -n "$rc" ]; then
+ echo $(dirname "$rc")
+ return
+ fi
+ cd ..
+ done
+}
+
+function SetUpAndroidBuild {
+ pushd .
+ android_root=$(UpFind -name out -type d)
+ if [[ -z $android_root ]] ; then
+ UsageAndroidTree
+ return
+ fi
+ echo "Found android root $android_root"
+ cd $android_root && . $BUILD_SETUP
+ echo "Sourced build setup rules"
+ cd $android_root && lunch
+ popd
+}
+
+function SetupPython38 {
+ echo "Setting up python3.8"
+ sudo apt-get install python3.8-dev
+}
+
+function CompileBluetoothPacketsPython3 {
+ echo "bluetooth_packets_python3 is not found, compiling"
+ croot
+ make -j bluetooth_packets_python3
+}
+
+if [[ "${BASH_SOURCE[0]}" == "${0}" ]] ; then
+ UsageSourcedNotExecuted
+ exit 1
+fi
+
+if [[ -z "$ANDROID_BUILD_TOP" ]] ; then
+ SetUpAndroidBuild
+fi
+
+## Check python3.8 is installed properly
+## Need Python 3.8 because bluetooth_packets_python3 is compiled against
+## Python 3.8 headers
+dpkg -l python3.8-dev > /dev/null 2>&1
+if [[ $? -ne 0 ]] ; then
+ SetupPython38
+fi
+
+## Check bluetooth_packets_python3 is compiled succssfully
+PYTHONPATH=$PYTHONPATH:$ANDROID_BUILD_TOP/out/host/linux-x86/lib64 python3.8 -c "
+import bluetooth_packets_python3 as bp3
+bp3.BaseStruct
+"
+if [[ $? -ne 0 ]] ; then
+ pushd .
+ CompileBluetoothPacketsPython3
+ popd
+ python3.8 -c "
+import bluetooth_packets_python3 as bp3
+bp3.BaseStruct
+"
+ if [[ $? -ne 0 ]] ; then
+ echo "Setup failed as bluetooth_packets_python3 cannot be found"
+ else
+ echo "Found bluetooth_packets_python3 after compilation"
+ fi
+else
+ echo "Found bluetooth_packets_python3"
+fi
+
+## All is good now so go ahead with the acts setup
+pushd .
+cd $ANDROID_BUILD_TOP/tools/test/connectivity/acts/framework/
+sudo python3.8 setup.py develop
+if [[ $? -eq 0 ]] ; then
+ echo "cert setup complete"
+else
+ echo "cert setup failed"
+fi
+popd
+
diff --git a/gd/cert/set_up_and_run_device_cert.sh b/gd/cert/set_up_and_run_device_cert.sh
index f768ae811..1a467080a 100755
--- a/gd/cert/set_up_and_run_device_cert.sh
+++ b/gd/cert/set_up_and_run_device_cert.sh
@@ -12,7 +12,7 @@ function menu-adb() {
result=0
if [ $LEN -lt 1 ]; then
echo "No devices connected!"
- return 1
+ exit 1
fi
if [ "$LEN" == "" ]; then
@@ -47,7 +47,7 @@ function menu-adb() {
echo
echo "Please choose a correct index!" 1>&2
echo
- return 1
+ exit 1
fi
SERIAL=${SERIALS[$answer]}
@@ -67,12 +67,12 @@ function UpFind {
function get-android-root() {
- android_root=$(UpFind -name dalvik -type d)
+ android_root=$(UpFind -name out -type d)
if [[ -z $android_root ]] ; then
echo
echo "Needs to be ran in the android tree"
echo
- return 1
+ exit 1
fi
echo "${android_root}"
}
@@ -88,7 +88,6 @@ banner
DRY_RUN=""
DO_BUILD=0
-echo "$@"
if [ $# -gt 0 ]; then
for var in "$@"
do
@@ -101,7 +100,7 @@ if [ $# -gt 0 ]; then
echo " -h | Help(this) Menu"
echo " -d | Dry run; just prints commands"
echo
- return 0
+ exit 0
elif [ "$var" == "-d" ]; then
DRY_RUN="echo"
elif [ "$var" == "-b" ]; then
@@ -123,7 +122,7 @@ if [ "${CERT_SERIAL}" == "${DUT_SERIAL}" ]; then
echo
echo "ERROR: CERT and DUT cannot be the same device, or you only have one device connected!"
echo
- return 1
+ exit 1
fi
## Start builds
@@ -146,7 +145,7 @@ fi
pushd .
cd "${DIR}"
# Reset in case user chooses different item in menu
-git checkout android_devices_config.json
+git co android_devices_config.json
popd
$DRY_RUN sed -i "s/\"DUT\"/\"${DUT_SERIAL}\"/g" ${DIR}/android_devices_config.json
$DRY_RUN sed -i "s/\"CERT\"/\"${CERT_SERIAL}\"/g" ${DIR}/android_devices_config.json
@@ -155,4 +154,4 @@ $DRY_RUN sed -i "s/\"CERT\"/\"${CERT_SERIAL}\"/g" ${DIR}/android_devices_config.
#$DRY_RUN source $(get-android-root)/system/bt/gd/cert/set_up_acts.sh
## Start test
-$DRY_RUN $(get-android-root)/system/bt/gd/cert/run
+$DRY_RUN $(get-android-root)/system/bt/gd/cert/run_device_cert.sh
diff --git a/gd/cert/set_up_virtualenv.sh b/gd/cert/set_up_virtualenv.sh
index 0c076916e..c730583f3 100644
--- a/gd/cert/set_up_virtualenv.sh
+++ b/gd/cert/set_up_virtualenv.sh
@@ -5,9 +5,9 @@
# Usage
# 1. cd system/bt/gd
# 2. source cert/set_up_virtualenv.sh
-# 4. [run tests, do development, hack] using vevn/bin/python
-#
-# Note: Just use the virtualized Python binary, no need to activate
+# 3. source gd_cert_venv/bin/activate
+# 4. [run tests, do development, hack]
+# 5. deactivate (or just close the terminal window)
## Android build main build setup script relative to top level android source root
BUILD_SETUP=./build/envsetup.sh
@@ -61,6 +61,12 @@ function SetupPip3 {
sudo apt-get install python3-pip
}
+function CompileBluetoothPacketsPython3 {
+ echo "bluetooth_packets_python3 is not found, compiling"
+ croot
+ make -j bluetooth_packets_python3
+}
+
# Deactivate existing virtual environment, if any, ignore errors
deactivate > /dev/null 2>&1
@@ -96,49 +102,118 @@ if [[ -z "$ANDROID_BUILD_TOP" ]] ; then
SetUpAndroidBuild
fi
+## Check bluetooth_packets_python3 is compiled succssfully
+$ANDROID_BUILD_TOP/system/bt/gd/cert/python3.8-gd -c "
+import bluetooth_packets_python3 as bp3
+bp3.BaseStruct
+"
+if [[ $? -ne 0 ]] ; then
+ pushd .
+ CompileBluetoothPacketsPython3
+ popd
+ $ANDROID_BUILD_TOP/system/bt/gd/cert/python3.8-gd -c "
+import bluetooth_packets_python3 as bp3
+bp3.BaseStruct
+"
+ if [[ $? -ne 0 ]] ; then
+ echo "Setup failed as bluetooth_packets_python3 cannot be found"
+ return 1
+ else
+ echo "Found bluetooth_packets_python3 after compilation"
+ fi
+else
+ echo "Found bluetooth_packets_python3"
+fi
+
## Compile and unzip test artifacts
-echo "Compiling bluetooth_stack_with_facade ..."
-$ANDROID_BUILD_TOP/build/soong/soong_ui.bash --build-mode --"all-modules" --dir="$(pwd)" dist bluetooth_stack_with_facade
+if [[ ! -f "$ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py.zip" || ! -f "$ANDROID_BUILD_TOP/out/dist/bluetooth_cert_test.zip" ]]; then
+ echo "bluetooth_cert_generated_py.zip OR bluetooth_cert_test.zip is not found, compiling"
+ m -j dist bluetooth_stack_with_facade
+ if [[ ! -f "$ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py.zip" || ! -f "$ANDROID_BUILD_TOP/out/dist/bluetooth_cert_test.zip" ]]; then
+ echo "Failed to compile bluetooth_stack_with_facade"
+ return 1
+ fi
+fi
+unzip -u $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py.zip -d $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py
if [[ $? -ne 0 ]] ; then
- echo "Failed to compile bluetooth_stack_with_facade"
+ echo "Failed to unzip bluetooth_cert_generated_py.zip"
return 1
fi
-if [[ ! -f "$ANDROID_BUILD_TOP/out/dist/bluetooth_cert_tests.zip" ]]; then
- echo "Cannot find bluetooth_cert_tests.zip after compilation"
+unzip -u $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_test.zip -d $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_test
+if [[ $? -ne 0 ]] ; then
+ echo "Failed to unzip bluetooth_cert_test.zip"
return 1
fi
-CERT_TEST_VENV=$ANDROID_BUILD_TOP/out/dist/bluetooth_venv
-
-rm -rf $CERT_TEST_VENV
-
-python3.8 -m virtualenv --python `which python3.8` $CERT_TEST_VENV
+# Set-up virtualenv
+pushd .
+cd $ANDROID_BUILD_TOP/system/bt/gd
+virtualenv -p python3.8 gd_cert_venv
+popd
if [[ $? -ne 0 ]] ; then
echo "Error setting up virtualenv"
return 1
fi
-unzip -o -q $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_tests.zip -d $CERT_TEST_VENV/acts
+# Set up artifacts
+pushd .
+cd $ANDROID_BUILD_TOP/system/bt/gd/gd_cert_venv/lib/python3.8/site-packages
+# Python generated code
+ln -sfT $ANDROID_BUILD_TOP/tools/test/connectivity/acts/framework/acts acts
+ln -sfT $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py/cert cert
+ln -sfT $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py/facade facade
+ln -sfT $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py/hal hal
+ln -sfT $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py/hci hci
+ln -sfT $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py/l2cap l2cap
+ln -sfT $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py/neighbor neighbor
+ln -sfT $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_generated_py/security security
+# Native libraries
+ln -sfT $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_test/out/host/linux-x86/lib64/bluetooth_packets_python3.so bluetooth_packets_python3.so
+# Per systrace, Python only load from python3.8/lib64 directory for plugin imported native libraries
+mkdir -p $ANDROID_BUILD_TOP/system/bt/gd/gd_cert_venv/lib/python3.8/lib64
+cd $ANDROID_BUILD_TOP/system/bt/gd/gd_cert_venv/lib/python3.8/lib64
+ln -sfT $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_test/out/host/linux-x86/lib64/libc++.so libc++.so
+ln -sfT $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_test/out/host/linux-x86/lib64/libbluetooth_gd.so libbluetooth_gd.so
+ln -sfT $ANDROID_BUILD_TOP/out/dist/bluetooth_cert_test/out/host/linux-x86/lib64/libgrpc++_unsecure.so libgrpc++_unsecure.so
+# Binaries
+cd $ANDROID_BUILD_TOP/system/bt/gd/gd_cert_venv/bin
+ln -sfT $ANDROID_BUILD_TOP/out/host/linux-x86/bin/bluetooth_stack_with_facade bluetooth_stack_with_facade
+ln -sfT $ANDROID_BUILD_TOP/out/host/linux-x86/nativetest64/root-canal/root-canal root-canal
+popd
+
+# Activate virtualenv
+pushd .
+source $ANDROID_BUILD_TOP/system/bt/gd/gd_cert_venv/bin/activate
+popd
if [[ $? -ne 0 ]] ; then
- echo "Error unzipping bluetooth_cert_tests.zip"
+ echo "Failed to activate virtualenv"
+ deactivate
+ return 1
+fi
+if [[ -z "$ANDROID_BUILD_TOP" ]] ; then
+ echo "Failed to inherit Android build environment"
+ deactivate
return 1
fi
-$CERT_TEST_VENV/bin/python $CERT_TEST_VENV/acts/setup.py install
+## Set up ACTS
+# sudo is no longer needed since we are in a virtual environment
+python3.8 $ANDROID_BUILD_TOP/tools/test/connectivity/acts/framework/setup.py develop
if [[ $? -ne 0 ]] ; then
- echo "Error installing GD libraries"
+ echo "ACTS setup failed"
+ deactivate
return 1
fi
-$CERT_TEST_VENV/bin/python -c "
-import bluetooth_packets_python3 as bp3
-bp3.BaseStruct
-"
+pip3 install protobuf
if [[ $? -ne 0 ]] ; then
- echo "Setup failed as bluetooth_packets_python3 cannot be imported"
- return 1
+ echo "Failed to install protobuf"
+ deactivate
+ return 1
fi
+deactivate
+
echo ""
echo "Please mark GD root directory as \"Project Sources and Headers\" in IDE"
echo "If still seeing errors, invalidate cached and restart"
diff --git a/gd/cert/truth.py b/gd/cert/truth.py
deleted file mode 100644
index eba6be343..000000000
--- a/gd/cert/truth.py
+++ /dev/null
@@ -1,150 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from datetime import timedelta
-
-from mobly.asserts import assert_true
-from mobly.asserts import assert_false
-from mobly import signals
-
-from cert.event_stream import IEventStream
-from cert.event_stream import NOT_FOR_YOU_assert_event_occurs
-from cert.event_stream import NOT_FOR_YOU_assert_all_events_occur
-from cert.event_stream import NOT_FOR_YOU_assert_none_matching
-from cert.event_stream import NOT_FOR_YOU_assert_none
-
-
-class ObjectSubject(object):
-
- def __init__(self, value):
- self._value = value
-
- def isEqualTo(self, other):
- if self._value != other:
- raise signals.TestFailure("Expected \"%s\" to be equal to \"%s\"" % (self._value, other), extras=None)
-
- def isNotEqualTo(self, other):
- if self._value == other:
- raise signals.TestFailure("Expected \"%s\" to not be equal to \"%s\"" % (self._value, other), extras=None)
-
- def isNone(self):
- if self._value is not None:
- raise signals.TestFailure("Expected \"%s\" to be None" % self._value, extras=None)
-
- def isNotNone(self):
- if self._value is None:
- raise signals.TestFailure("Expected \"%s\" to not be None" % self._value, extras=None)
-
-
-DEFAULT_TIMEOUT = timedelta(seconds=3)
-
-
-class EventStreamSubject(ObjectSubject):
-
- def __init__(self, value):
- super().__init__(value)
-
- def emits(self, *match_fns, at_least_times=1, timeout=DEFAULT_TIMEOUT):
- if len(match_fns) == 0:
- raise signals.TestFailure("Must specify a match function")
- elif len(match_fns) == 1:
- NOT_FOR_YOU_assert_event_occurs(self._value, match_fns[0], at_least_times=at_least_times, timeout=timeout)
- return EventStreamContinuationSubject(self._value)
- else:
- return MultiMatchStreamSubject(self._value, match_fns, timeout)
-
- def emitsNone(self, *match_fns, timeout=DEFAULT_TIMEOUT):
- if len(match_fns) == 0:
- NOT_FOR_YOU_assert_none(self._value, timeout=timeout)
- return EventStreamContinuationSubject(self._value)
- elif len(match_fns) == 1:
- NOT_FOR_YOU_assert_none_matching(self._value, match_fns[0], timeout=timeout)
- return EventStreamContinuationSubject(self._value)
- else:
- raise signals.TestFailure("Cannot specify multiple match functions")
-
-
-class MultiMatchStreamSubject(object):
-
- def __init__(self, stream, match_fns, timeout):
- self._stream = stream
- self._match_fns = match_fns
- self._timeout = timeout
-
- def inAnyOrder(self):
- NOT_FOR_YOU_assert_all_events_occur(self._stream, self._match_fns, order_matters=False, timeout=self._timeout)
- return EventStreamContinuationSubject(self._stream)
-
- def inOrder(self):
- NOT_FOR_YOU_assert_all_events_occur(self._stream, self._match_fns, order_matters=True, timeout=self._timeout)
- return EventStreamContinuationSubject(self._stream)
-
-
-class EventStreamContinuationSubject(ObjectSubject):
-
- def __init__(self, value):
- super().__init__(value)
-
- def then(self, *match_fns, at_least_times=1, timeout=DEFAULT_TIMEOUT):
- if len(match_fns) == 0:
- raise signals.TestFailure("Must specify a match function")
- elif len(match_fns) == 1:
- NOT_FOR_YOU_assert_event_occurs(self._value, match_fns[0], at_least_times=at_least_times, timeout=timeout)
- return EventStreamContinuationSubject(self._value)
- else:
- return MultiMatchStreamSubject(self._value, match_fns, timeout)
-
- def thenNone(self, *match_fns, timeout=DEFAULT_TIMEOUT):
- if len(match_fns) == 0:
- NOT_FOR_YOU_assert_none(self._value, timeout=timeout)
- return EventStreamContinuationSubject(self._value)
- elif len(match_fns) == 1:
- NOT_FOR_YOU_assert_none_matching(self._value, match_fns[0], timeout=timeout)
- return EventStreamContinuationSubject(self._value)
- else:
- raise signals.TestFailure("Cannot specify multiple match functions")
-
-
-class BooleanSubject(ObjectSubject):
-
- def __init__(self, value):
- super().__init__(value)
-
- def isTrue(self):
- assert_true(self._value, "")
-
- def isFalse(self):
- assert_false(self._value, "")
-
-
-class TimeDeltaSubject(ObjectSubject):
-
- def __init__(self, value):
- super().__init__(value)
-
- def isWithin(self, time_bound):
- assert_true(self._value < time_bound, "")
-
-
-def assertThat(subject):
- if type(subject) is bool:
- return BooleanSubject(subject)
- elif isinstance(subject, IEventStream):
- return EventStreamSubject(subject)
- elif isinstance(subject, timedelta):
- return TimeDeltaSubject(subject)
- else:
- return ObjectSubject(subject)
diff --git a/gd/common/Android.bp b/gd/common/Android.bp
index 27d559a59..c9234278c 100644
--- a/gd/common/Android.bp
+++ b/gd/common/Android.bp
@@ -1,19 +1,7 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothCommonSources",
srcs: [
- "init_flags.cc",
- "metric_id_manager.cc",
- "strings.cc",
- "stop_watch.cc",
+ "link_key.cc",
],
}
@@ -22,15 +10,7 @@ filegroup {
srcs: [
"blocking_queue_unittest.cc",
"bidi_queue_unittest.cc",
- "byte_array_test.cc",
- "circular_buffer_test.cc",
"observer_registry_test.cc",
- "init_flags_test.cc",
- "list_map_test.cc",
- "lru_cache_test.cc",
- "metric_id_manager_unittest.cc",
- "multi_priority_queue_test.cc",
- "numbers_test.cc",
- "strings_test.cc",
+ "link_key_unittest.cc",
],
}
diff --git a/gd/common/BUILD.gn b/gd/common/BUILD.gn
deleted file mode 100644
index fb4dad973..000000000
--- a/gd/common/BUILD.gn
+++ /dev/null
@@ -1,30 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-source_set("BluetoothCommonSources") {
- sources = [
- "init_flags.cc",
- "metric_id_manager.cc",
- "stop_watch.cc",
- "strings.cc",
- ]
-
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [
- "//bt/gd:gd_default_deps",
- "//bt:libbt-platform-protos-lite",
- ]
-}
diff --git a/gd/common/bidi_queue.h b/gd/common/bidi_queue.h
index 0fdf0858d..c108588b1 100644
--- a/gd/common/bidi_queue.h
+++ b/gd/common/bidi_queue.h
@@ -25,13 +25,16 @@ namespace bluetooth {
namespace common {
template <typename TENQUEUE, typename TDEQUEUE>
-class BidiQueueEnd : public ::bluetooth::os::IQueueEnqueue<TENQUEUE>, public ::bluetooth::os::IQueueDequeue<TDEQUEUE> {
+class BidiQueueEnd
+ : public ::bluetooth::os::IQueueEnqueue<TENQUEUE>,
+ public ::bluetooth::os::IQueueDequeue<TDEQUEUE> {
public:
using EnqueueCallback = Callback<std::unique_ptr<TENQUEUE>()>;
using DequeueCallback = Callback<void()>;
BidiQueueEnd(::bluetooth::os::IQueueEnqueue<TENQUEUE>* tx, ::bluetooth::os::IQueueDequeue<TDEQUEUE>* rx)
- : tx_(tx), rx_(rx) {}
+ : tx_(tx), rx_(rx) {
+ }
void RegisterEnqueue(::bluetooth::os::Handler* handler, EnqueueCallback callback) override {
tx_->RegisterEnqueue(handler, callback);
@@ -65,7 +68,8 @@ class BidiQueue {
: up_queue_(capacity),
down_queue_(capacity),
up_end_(&down_queue_, &up_queue_),
- down_end_(&up_queue_, &down_queue_) {}
+ down_end_(&up_queue_, &down_queue_) {
+ }
BidiQueueEnd<TDOWN, TUP>* GetUpEnd() {
return &up_end_;
diff --git a/gd/common/bidi_queue_unittest.cc b/gd/common/bidi_queue_unittest.cc
index 155927537..7a5503c80 100644
--- a/gd/common/bidi_queue_unittest.cc
+++ b/gd/common/bidi_queue_unittest.cc
@@ -23,8 +23,8 @@
#include "os/handler.h"
#include "os/thread.h"
-using ::bluetooth::os::Handler;
using ::bluetooth::os::Thread;
+using ::bluetooth::os::Handler;
namespace bluetooth {
namespace common {
@@ -52,14 +52,17 @@ class BidiQueueTest : public ::testing::Test {
Handler* down_handler_;
};
-class A {};
+class A {
+};
-class B {};
+class B {
+};
template <typename TA, typename TB>
class TestBidiQueueEnd {
public:
- explicit TestBidiQueueEnd(BidiQueueEnd<TA, TB>* end, Handler* handler) : handler_(handler), end_(end) {}
+ explicit TestBidiQueueEnd(BidiQueueEnd<TA, TB>* end, Handler* handler)
+ : handler_(handler), end_(end) {}
~TestBidiQueueEnd() {
handler_->Clear();
@@ -67,11 +70,8 @@ class TestBidiQueueEnd {
std::promise<void>* Send(TA* value) {
std::promise<void>* promise = new std::promise<void>();
- handler_->Post(BindOnce(
- &TestBidiQueueEnd<TA, TB>::handle_send,
- common::Unretained(this),
- common::Unretained(value),
- common::Unretained(promise)));
+ handler_->Post(BindOnce(&TestBidiQueueEnd<TA, TB>::handle_send, common::Unretained(this), common::Unretained(value),
+ common::Unretained(promise)));
return promise;
}
@@ -84,13 +84,8 @@ class TestBidiQueueEnd {
}
void handle_send(TA* value, std::promise<void>* promise) {
- end_->RegisterEnqueue(
- handler_,
- Bind(
- &TestBidiQueueEnd<TA, TB>::handle_register_enqueue,
- common::Unretained(this),
- common::Unretained(value),
- common::Unretained(promise)));
+ end_->RegisterEnqueue(handler_, Bind(&TestBidiQueueEnd<TA, TB>::handle_register_enqueue, common::Unretained(this),
+ common::Unretained(value), common::Unretained(promise)));
}
std::unique_ptr<TA> handle_register_enqueue(TA* value, std::promise<void>* promise) {
@@ -100,10 +95,8 @@ class TestBidiQueueEnd {
}
void handle_receive(std::promise<TB*>* promise) {
- end_->RegisterDequeue(
- handler_,
- Bind(
- &TestBidiQueueEnd<TA, TB>::handle_register_dequeue, common::Unretained(this), common::Unretained(promise)));
+ end_->RegisterDequeue(handler_, Bind(&TestBidiQueueEnd<TA, TB>::handle_register_dequeue, common::Unretained(this),
+ common::Unretained(promise)));
}
void handle_register_dequeue(std::promise<TB*>* promise) {
@@ -139,5 +132,5 @@ TEST_F(BidiQueueTest, simple_test) {
}
} // namespace
-} // namespace common
+} // namespace os
} // namespace bluetooth
diff --git a/gd/common/bind.h b/gd/common/bind.h
index e65d83032..1adf16c37 100644
--- a/gd/common/bind.h
+++ b/gd/common/bind.h
@@ -23,17 +23,12 @@ namespace common {
using base::Bind;
using base::BindOnce;
+using base::ConstRef;
using base::IgnoreResult;
-using base::MakeUnboundRunType;
using base::Owned;
using base::Passed;
using base::RetainedRef;
using base::Unretained;
-template <typename T, typename Functor, typename... Args>
-inline base::Callback<MakeUnboundRunType<Functor, T, Args...>> BindOn(T* obj, Functor&& functor, Args&&... args) {
- return common::Bind(std::forward<Functor>(functor), common::Unretained(obj), std::forward<Args>(args)...);
-}
-
} // namespace common
} // namespace bluetooth
diff --git a/gd/common/blocking_queue_unittest.cc b/gd/common/blocking_queue_unittest.cc
index b6c96321c..57a62459f 100644
--- a/gd/common/blocking_queue_unittest.cc
+++ b/gd/common/blocking_queue_unittest.cc
@@ -16,10 +16,10 @@
#include "common/blocking_queue.h"
-#include <gtest/gtest.h>
-
#include <thread>
+#include <gtest/gtest.h>
+
namespace bluetooth {
namespace common {
namespace {
diff --git a/gd/common/byte_array.h b/gd/common/byte_array.h
deleted file mode 100644
index 6f2f52944..000000000
--- a/gd/common/byte_array.h
+++ /dev/null
@@ -1,99 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <algorithm>
-#include <array>
-#include <cstdint>
-#include <initializer_list>
-#include <optional>
-#include <string>
-
-#include "common/strings.h"
-#include "packet/custom_field_fixed_size_interface.h"
-#include "storage/serializable.h"
-
-namespace bluetooth {
-namespace common {
-
-template <std::size_t LENGTH>
-class ByteArray : public packet::CustomFieldFixedSizeInterface<ByteArray<LENGTH>>,
- public storage::Serializable<ByteArray<LENGTH>> {
- public:
- static constexpr size_t kLength = LENGTH;
- ByteArray() = default;
- ByteArray(const uint8_t (&d)[kLength]) {
- std::copy(d, d + kLength, data());
- }
- ByteArray(std::array<uint8_t, kLength> a) : bytes(std::move(a)) {}
-
- std::array<uint8_t, kLength> bytes = {};
-
- uint8_t* data() override {
- return bytes.data();
- }
-
- const uint8_t* data() const override {
- return bytes.data();
- }
-
- // operators
- bool operator<(const ByteArray& rhs) const {
- return bytes < rhs.bytes;
- }
- bool operator==(const ByteArray& rhs) const {
- return bytes == rhs.bytes;
- }
- bool operator>(const ByteArray& rhs) const {
- return (rhs < *this);
- }
- bool operator<=(const ByteArray& rhs) const {
- return !(*this > rhs);
- }
- bool operator>=(const ByteArray& rhs) const {
- return !(*this < rhs);
- }
- bool operator!=(const ByteArray& rhs) const {
- return !(*this == rhs);
- }
-
- // storage::Serializable methods
- std::string ToString() const override {
- return common::ToHexString(bytes.begin(), bytes.end());
- }
- static std::optional<ByteArray<kLength>> FromString(const std::string& from) {
- if (from.length() != (kLength * 2)) {
- return std::nullopt;
- }
- auto vec = common::FromHexString(from);
- if (!vec) {
- return std::nullopt;
- }
- ByteArray<kLength> byte_array = {};
- std::move(vec->data(), vec->data() + vec->size(), byte_array.data());
- return byte_array;
- }
- std::string ToLegacyConfigString() const override {
- return ToString();
- }
- static std::optional<ByteArray<kLength>> FromLegacyConfigString(const std::string& from) {
- return FromString(from);
- }
-};
-
-} // namespace common
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/common/byte_array_test.cc b/gd/common/byte_array_test.cc
deleted file mode 100644
index f06b274ad..000000000
--- a/gd/common/byte_array_test.cc
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "common/byte_array.h"
-
-#include <gtest/gtest.h>
-
-#include "os/log.h"
-
-using bluetooth::common::ByteArray;
-
-static const char* test_bytes = "4c68384139f574d836bcf34e9dfb01bf\0";
-static uint8_t test_data[16] = {
- 0x4c, 0x68, 0x38, 0x41, 0x39, 0xf5, 0x74, 0xd8, 0x36, 0xbc, 0xf3, 0x4e, 0x9d, 0xfb, 0x01, 0xbf};
-static uint8_t data[16] = {
- 0x4c, 0x87, 0x49, 0xe1, 0x2e, 0x55, 0x0f, 0x7f, 0x60, 0x8b, 0x4f, 0x96, 0xd7, 0xc5, 0xbc, 0x2a};
-
-TEST(ByteArrayTest, test_constructor_array) {
- ByteArray<16> byte_array(data);
-
- for (int i = 0; i < ByteArray<16>::kLength; i++) {
- ASSERT_EQ(data[i], byte_array.bytes[i]);
- }
-}
-
-TEST(ByteArrayTest, test_from_str) {
- auto byte_array = ByteArray<16>::FromString(test_bytes);
- ASSERT_TRUE(byte_array);
-
- for (int i = 0; i < ByteArray<16>::kLength; i++) {
- ASSERT_EQ(test_data[i], byte_array->bytes[i]);
- }
-}
-
-TEST(ByteArrayTest, test_to_str) {
- ByteArray<16> byte_array = {
- {0x4C, 0x68, 0x38, 0x41, 0x39, 0xf5, 0x74, 0xd8, 0x36, 0xbc, 0xf3, 0x4e, 0x9d, 0xfb, 0x01, 0xbf}};
- std::string str = byte_array.ToString();
- ASSERT_STREQ(str.c_str(), test_bytes);
-} \ No newline at end of file
diff --git a/gd/common/callback_list.h b/gd/common/callback_list.h
index a3ad6b1f1..857b0c7a6 100644
--- a/gd/common/callback_list.h
+++ b/gd/common/callback_list.h
@@ -17,7 +17,6 @@
#pragma once
#include <utility>
-
#include "base/callback_list.h"
#include "os/handler.h"
diff --git a/gd/common/circular_buffer.h b/gd/common/circular_buffer.h
deleted file mode 100644
index 46d6972fe..000000000
--- a/gd/common/circular_buffer.h
+++ /dev/null
@@ -1,130 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstddef>
-#include <iterator>
-#include <memory>
-#include <mutex>
-#include <queue>
-
-namespace bluetooth {
-namespace common {
-
-template <typename T>
-class CircularBuffer {
- public:
- explicit CircularBuffer(size_t size);
-
- // Push one item to the circular buffer
- void Push(T item);
- // Take a snapshot of the circular buffer and return it as a vector
- std::vector<T> Pull() const;
- // Drain everything from the circular buffer and return them as a vector
- std::vector<T> Drain();
-
- private:
- const size_t size_;
- std::deque<T> queue_;
- mutable std::mutex mutex_;
-};
-
-class Timestamper {
- public:
- virtual long long GetTimestamp() const = 0;
- virtual ~Timestamper() {}
-};
-
-class TimestamperInMilliseconds : public Timestamper {
- public:
- long long GetTimestamp() const override {
- return std::chrono::duration_cast<std::chrono::milliseconds>(std::chrono::system_clock::now().time_since_epoch())
- .count();
- }
- virtual ~TimestamperInMilliseconds() {}
-};
-
-template <typename T>
-struct TimestampedEntry {
- long long timestamp;
- T entry;
-};
-
-template <typename T>
-class TimestampedCircularBuffer : public CircularBuffer<TimestampedEntry<T>> {
- public:
- explicit TimestampedCircularBuffer(
- size_t size, std::unique_ptr<Timestamper> timestamper = std::make_unique<TimestamperInMilliseconds>());
-
- void Push(T item);
- std::vector<TimestampedEntry<T>> Pull() const;
- std::vector<TimestampedEntry<T>> Drain();
-
- private:
- std::unique_ptr<Timestamper> timestamper_{std::make_unique<TimestamperInMilliseconds>()};
-};
-
-} // namespace common
-} // namespace bluetooth
-
-template <typename T>
-bluetooth::common::CircularBuffer<T>::CircularBuffer(size_t size) : size_(size) {}
-
-template <typename T>
-void bluetooth::common::CircularBuffer<T>::Push(const T item) {
- std::unique_lock<std::mutex> lock(mutex_);
- queue_.push_back(item);
- while (queue_.size() > size_) {
- queue_.pop_front();
- }
-}
-
-template <typename T>
-std::vector<T> bluetooth::common::CircularBuffer<T>::Pull() const {
- std::unique_lock<std::mutex> lock(mutex_);
- return std::vector<T>(queue_.cbegin(), queue_.cend());
-}
-
-template <typename T>
-std::vector<T> bluetooth::common::CircularBuffer<T>::Drain() {
- std::unique_lock<std::mutex> lock(mutex_);
- std::vector<T> items(std::make_move_iterator(queue_.begin()), std::make_move_iterator(queue_.end()));
- queue_.clear();
- return items;
-}
-
-template <typename T>
-bluetooth::common::TimestampedCircularBuffer<T>::TimestampedCircularBuffer(
- size_t size, std::unique_ptr<Timestamper> timestamper)
- : CircularBuffer<TimestampedEntry<T>>(size), timestamper_(std::move(timestamper)) {}
-
-template <typename T>
-void bluetooth::common::TimestampedCircularBuffer<T>::Push(const T item) {
- TimestampedEntry<T> timestamped_entry{timestamper_->GetTimestamp(), item};
- bluetooth::common::CircularBuffer<TimestampedEntry<T>>::Push(timestamped_entry);
-}
-
-template <typename T>
-std::vector<struct bluetooth::common::TimestampedEntry<T>> bluetooth::common::TimestampedCircularBuffer<T>::Pull()
- const {
- return bluetooth::common::CircularBuffer<TimestampedEntry<T>>::Pull();
-}
-
-template <typename T>
-std::vector<struct bluetooth::common::TimestampedEntry<T>> bluetooth::common::TimestampedCircularBuffer<T>::Drain() {
- return bluetooth::common::CircularBuffer<TimestampedEntry<T>>::Drain();
-}
diff --git a/gd/common/circular_buffer_test.cc b/gd/common/circular_buffer_test.cc
deleted file mode 100644
index bc6720794..000000000
--- a/gd/common/circular_buffer_test.cc
+++ /dev/null
@@ -1,106 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-#include <limits>
-#include <string>
-
-#include "common/circular_buffer.h"
-#include "os/log.h"
-
-namespace testing {
-
-long long timestamp_{0};
-struct TestTimestamper : public bluetooth::common::Timestamper {
- virtual long long GetTimestamp() const override {
- return timestamp_++;
- }
-};
-
-TEST(CircularBufferTest, simple) {
- bluetooth::common::TimestampedCircularBuffer<std::string> buffer(10);
-
- buffer.Push(std::string("One"));
- buffer.Push(std::string("Two"));
- buffer.Push(std::string("Three"));
-
- auto vec = buffer.Pull();
-
- ASSERT_STREQ("One", vec[0].entry.c_str());
- ASSERT_STREQ("Two", vec[1].entry.c_str());
- ASSERT_STREQ("Three", vec[2].entry.c_str());
-
- auto vec2 = buffer.Pull();
-
- ASSERT_FALSE(vec2.empty());
-}
-
-TEST(CircularBufferTest, simple_drain) {
- bluetooth::common::TimestampedCircularBuffer<std::string> buffer(10);
-
- buffer.Push(std::string("One"));
- buffer.Push(std::string("Two"));
- buffer.Push(std::string("Three"));
-
- auto vec = buffer.Drain();
-
- ASSERT_STREQ("One", vec[0].entry.c_str());
- ASSERT_STREQ("Two", vec[1].entry.c_str());
- ASSERT_STREQ("Three", vec[2].entry.c_str());
-
- auto vec2 = buffer.Pull();
-
- ASSERT_TRUE(vec2.empty());
-}
-
-TEST(CircularBufferTest, test_timestamps) {
- bluetooth::common::TimestampedCircularBuffer<std::string> buffer(10, std::make_unique<TestTimestamper>());
-
- buffer.Push(std::string("One"));
- buffer.Push(std::string("Two"));
- buffer.Push(std::string("Three"));
-
- auto vec = buffer.Pull();
- long long timestamp = 0;
- for (auto v : vec) {
- ASSERT_EQ(timestamp, v.timestamp);
- timestamp++;
- }
-}
-
-TEST(CircularBufferTest, max_timestamps) {
- bluetooth::common::TimestampedCircularBuffer<std::string> buffer(10);
-
- std::vector<std::string> test_data;
- for (int i = 0; i < 10 + 1; i++) {
- char buf[255];
- snprintf(buf, 255, "value:%d", i);
- test_data.push_back(std::string(buf));
- buffer.Push(std::string(buf));
- }
-
- auto vec = buffer.Pull();
- ASSERT_EQ(10, vec.size());
-
- int i = 0 + 1;
- for (auto v : vec) {
- ASSERT_EQ(test_data[i], v.entry.c_str());
- i++;
- }
-}
-
-} // namespace testing
diff --git a/gd/common/contextual_callback.h b/gd/common/contextual_callback.h
deleted file mode 100644
index 539352945..000000000
--- a/gd/common/contextual_callback.h
+++ /dev/null
@@ -1,104 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "common/bind.h"
-#include "common/callback.h"
-
-namespace bluetooth {
-namespace common {
-
-class IPostableContext {
- public:
- virtual ~IPostableContext(){};
- virtual void Post(OnceClosure closure) = 0;
-};
-
-template <typename R, typename... Args>
-class ContextualOnceCallback;
-
-// A callback bound to an execution context that can be invoked only once.
-template <typename R, typename... Args>
-class ContextualOnceCallback<R(Args...)> {
- public:
- ContextualOnceCallback(common::OnceCallback<R(Args...)>&& callback, IPostableContext* context)
- : callback_(std::move(callback)), context_(context) {}
-
- constexpr ContextualOnceCallback() = default;
-
- DISALLOW_COPY_AND_ASSIGN(ContextualOnceCallback);
-
- ContextualOnceCallback(ContextualOnceCallback&&) noexcept = default;
- ContextualOnceCallback& operator=(ContextualOnceCallback&&) noexcept = default;
-
- void Invoke(Args... args) {
- context_->Post(common::BindOnce(std::move(callback_), std::forward<Args>(args)...));
- }
-
- void InvokeIfNotEmpty(Args... args) {
- if (context_ != nullptr) {
- context_->Post(common::BindOnce(std::move(callback_), std::forward<Args>(args)...));
- }
- }
-
- bool IsEmpty() {
- return context_ == nullptr;
- }
-
- private:
- common::OnceCallback<R(Args...)> callback_;
- IPostableContext* context_;
-};
-
-template <typename R, typename... Args>
-class ContextualCallback;
-
-// A callback bound to an execution context that can be invoked multiple times.
-template <typename R, typename... Args>
-class ContextualCallback<R(Args...)> {
- public:
- ContextualCallback(common::Callback<R(Args...)>&& callback, IPostableContext* context)
- : callback_(std::move(callback)), context_(context) {}
-
- constexpr ContextualCallback() = default;
-
- ContextualCallback(const ContextualCallback&) = default;
- ContextualCallback& operator=(const ContextualCallback&) = default;
- ContextualCallback(ContextualCallback&&) noexcept = default;
- ContextualCallback& operator=(ContextualCallback&&) noexcept = default;
-
- void Invoke(Args... args) {
- context_->Post(common::BindOnce(callback_, std::forward<Args>(args)...));
- }
-
- void InvokeIfNotEmpty(Args... args) {
- if (context_ != nullptr) {
- context_->Post(common::BindOnce(callback_, std::forward<Args>(args)...));
- }
- }
-
- bool IsEmpty() {
- return context_ == nullptr;
- }
-
- private:
- common::Callback<R(Args...)> callback_;
- IPostableContext* context_;
-};
-
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/common/init_flags.cc b/gd/common/init_flags.cc
deleted file mode 100644
index a7569b80a..000000000
--- a/gd/common/init_flags.cc
+++ /dev/null
@@ -1,104 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#include "init_flags.h"
-
-#include <string>
-
-#include "common/strings.h"
-#include "os/log.h"
-
-namespace bluetooth {
-namespace common {
-
-bool InitFlags::logging_debug_enabled_for_all = false;
-std::unordered_map<std::string, bool> InitFlags::logging_debug_explicit_tag_settings = {};
-
-bool ParseBoolFlag(const std::vector<std::string>& flag_pair, const std::string& flag, bool* variable) {
- if (flag != flag_pair[0]) {
- return false;
- }
- auto value = BoolFromString(flag_pair[1]);
- if (!value) {
- return false;
- }
- *variable = *value;
- return true;
-}
-
-void InitFlags::Load(const char** flags) {
- const char** flags_copy = flags;
- SetAll(false);
- while (flags != nullptr && *flags != nullptr) {
- std::string flag_element = *flags;
- auto flag_pair = StringSplit(flag_element, "=", 2);
- if (flag_pair.size() != 2) {
- flags++;
- continue;
- }
-
- ParseBoolFlag(flag_pair, "INIT_logging_debug_enabled_for_all", &logging_debug_enabled_for_all);
- if ("INIT_logging_debug_enabled_for_tags" == flag_pair[0]) {
- auto tags = StringSplit(flag_pair[1], ",");
- for (const auto& tag : tags) {
- auto setting = logging_debug_explicit_tag_settings.find(tag);
- if (setting == logging_debug_explicit_tag_settings.end()) {
- logging_debug_explicit_tag_settings.insert_or_assign(tag, true);
- }
- }
- }
- if ("INIT_logging_debug_disabled_for_tags" == flag_pair[0]) {
- auto tags = StringSplit(flag_pair[1], ",");
- for (const auto& tag : tags) {
- logging_debug_explicit_tag_settings.insert_or_assign(tag, false);
- }
- }
- flags++;
- }
-
- std::vector<std::string> logging_debug_enabled_tags;
- std::vector<std::string> logging_debug_disabled_tags;
- for (const auto& tag_setting : logging_debug_explicit_tag_settings) {
- if (tag_setting.second) {
- logging_debug_enabled_tags.emplace_back(tag_setting.first);
- } else {
- logging_debug_disabled_tags.emplace_back(tag_setting.first);
- }
- }
-
- flags = flags_copy;
- rust::Vec<rust::String> rusted_flags = rust::Vec<rust::String>();
- while (flags != nullptr && *flags != nullptr) {
- rusted_flags.push_back(rust::String(*flags));
- flags++;
- }
- init_flags::load(std::move(rusted_flags));
-}
-
-void InitFlags::SetAll(bool value) {
- logging_debug_enabled_for_all = value;
- logging_debug_explicit_tag_settings.clear();
-}
-
-void InitFlags::SetAllForTesting() {
- init_flags::set_all_for_testing();
- SetAll(true);
-}
-
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/common/init_flags.fbs b/gd/common/init_flags.fbs
deleted file mode 100644
index 5e9d23d21..000000000
--- a/gd/common/init_flags.fbs
+++ /dev/null
@@ -1,17 +0,0 @@
-namespace bluetooth.common;
-
-attribute "privacy";
-
-table InitFlagsData {
- title:string;
- gd_advertising_enabled:bool;
- gd_scanning_enabled:bool;
- gd_security_enabled:bool;
- gd_acl_enabled:bool;
- gd_hci_enabled:bool;
- gd_controller_enabled:bool;
- gd_core_enabled:bool;
- btaa_hci_log_enabled:bool;
-}
-
-root_type InitFlagsData;
diff --git a/gd/common/init_flags.h b/gd/common/init_flags.h
deleted file mode 100644
index 11af2a177..000000000
--- a/gd/common/init_flags.h
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <stdexcept>
-#include <string>
-#include <unordered_map>
-
-#include "src/init_flags.rs.h"
-
-namespace bluetooth {
-namespace common {
-
-class InitFlags final {
- public:
- static void Load(const char** flags);
-
- inline static bool IsDebugLoggingEnabledForTag(const std::string& tag) {
- auto tag_setting = logging_debug_explicit_tag_settings.find(tag);
- if (tag_setting != logging_debug_explicit_tag_settings.end()) {
- return tag_setting->second;
- }
- return logging_debug_enabled_for_all;
- }
-
- inline static bool IsDebugLoggingEnabledForAll() {
- return logging_debug_enabled_for_all;
- }
-
- static void SetAllForTesting();
-
- private:
- static void SetAll(bool value);
- static bool logging_debug_enabled_for_all;
- // save both log allow list and block list in the map to save hashing time
- static std::unordered_map<std::string, bool> logging_debug_explicit_tag_settings;
-};
-
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/common/init_flags_test.cc b/gd/common/init_flags_test.cc
deleted file mode 100644
index 76babcc81..000000000
--- a/gd/common/init_flags_test.cc
+++ /dev/null
@@ -1,64 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#include "common/init_flags.h"
-
-#include <gtest/gtest.h>
-
-using bluetooth::common::InitFlags;
-
-TEST(InitFlagsTest, test_enable_debug_logging_for_all) {
- const char* input[] = {"INIT_logging_debug_enabled_for_all=true", nullptr};
- InitFlags::Load(input);
- ASSERT_TRUE(InitFlags::IsDebugLoggingEnabledForTag("foo"));
- ASSERT_TRUE(InitFlags::IsDebugLoggingEnabledForTag("bar"));
- ASSERT_TRUE(InitFlags::IsDebugLoggingEnabledForAll());
-}
-
-TEST(InitFlagsTest, test_enable_debug_logging_for_tags) {
- const char* input[] = {"INIT_logging_debug_enabled_for_tags=foo,bar,hello", nullptr};
- InitFlags::Load(input);
- ASSERT_TRUE(InitFlags::IsDebugLoggingEnabledForTag("foo"));
- ASSERT_TRUE(InitFlags::IsDebugLoggingEnabledForTag("bar"));
- ASSERT_TRUE(InitFlags::IsDebugLoggingEnabledForTag("hello"));
- ASSERT_FALSE(InitFlags::IsDebugLoggingEnabledForTag("Foo"));
- ASSERT_FALSE(InitFlags::IsDebugLoggingEnabledForAll());
-}
-
-TEST(InitFlagsTest, test_disable_debug_logging_for_tags) {
- const char* input[] = {"INIT_logging_debug_disabled_for_tags=foo,bar,hello", nullptr};
- InitFlags::Load(input);
- ASSERT_FALSE(InitFlags::IsDebugLoggingEnabledForTag("foo"));
- ASSERT_FALSE(InitFlags::IsDebugLoggingEnabledForTag("bar"));
- ASSERT_FALSE(InitFlags::IsDebugLoggingEnabledForTag("hello"));
- ASSERT_FALSE(InitFlags::IsDebugLoggingEnabledForTag("Foo"));
- ASSERT_FALSE(InitFlags::IsDebugLoggingEnabledForAll());
-}
-
-TEST(InitFlagsTest, test_debug_logging_multiple_flags) {
- const char* input[] = {"INIT_logging_debug_enabled_for_tags=foo,hello",
- "INIT_logging_debug_disabled_for_tags=foo,bar",
- "INIT_logging_debug_enabled_for_all=false",
- nullptr};
- InitFlags::Load(input);
- ASSERT_FALSE(InitFlags::IsDebugLoggingEnabledForTag("foo"));
- ASSERT_FALSE(InitFlags::IsDebugLoggingEnabledForTag("bar"));
- ASSERT_TRUE(InitFlags::IsDebugLoggingEnabledForTag("hello"));
- ASSERT_FALSE(InitFlags::IsDebugLoggingEnabledForTag("Foo"));
- ASSERT_FALSE(InitFlags::IsDebugLoggingEnabledForAll());
-}
diff --git a/gd/common/multi_priority_queue_test.cc b/gd/common/link_key.cc
index c0918adfe..12b60cdfd 100644
--- a/gd/common/multi_priority_queue_test.cc
+++ b/gd/common/link_key.cc
@@ -1,6 +1,6 @@
/******************************************************************************
*
- * Copyright 2021 The Android Open Source Project
+ * Copyright 2019 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,47 +16,41 @@
*
******************************************************************************/
-#include <gtest/gtest.h>
-
-#include "common/multi_priority_queue.h"
+#include "link_key.h"
namespace bluetooth {
namespace common {
-TEST(MultiPriorityQueueTest, without_high_priority_item) {
- common::MultiPriorityQueue<int, 2> q;
- ASSERT_TRUE(q.empty());
- q.push(0);
- q.push(1, 0);
- q.push(2);
- ASSERT_EQ(q.size(), 3);
- for (int i = 0; i < 3; i++) {
- ASSERT_EQ(q.front(), i);
- q.pop();
- }
- ASSERT_TRUE(q.empty());
+const LinkKey LinkKey::kExample{
+ {0x4C, 0x68, 0x38, 0x41, 0x39, 0xf5, 0x74, 0xd8, 0x36, 0xbc, 0xf3, 0x4e, 0x9d, 0xfb, 0x01, 0xbf}};
+
+LinkKey::LinkKey(const uint8_t (&data)[16]) {
+ std::copy(data, data + kLength, link_key);
}
-TEST(MultiPriorityQueueTest, with_high_priority_item) {
- common::MultiPriorityQueue<int, 2> q;
- q.push(1);
- q.push(2);
- q.push(0, 1);
- for (int i = 0; i < 3; i++) {
- ASSERT_EQ(q.front(), i);
- q.pop();
+std::string LinkKey::ToString() const {
+ char buffer[33] = "";
+ for (int i = 0; i < 16; i++) {
+ std::snprintf(&buffer[i * 2], 3, "%02x", link_key[i]);
}
+ std::string str(buffer);
+ return str;
}
-TEST(MultiPriorityQueueTest, with_multiple_priority_item) {
- common::MultiPriorityQueue<int, 3> q;
- q.push(1, 1);
- q.push(0, 2);
- q.push(2, 0);
- for (int i = 0; i < 3; i++) {
- ASSERT_EQ(q.front(), i);
- q.pop();
+bool LinkKey::FromString(const std::string& from, bluetooth::common::LinkKey& to) {
+ LinkKey new_link_key;
+
+ if (from.length() != 32) {
+ return false;
}
+
+ char* temp = nullptr;
+ for (int i = 0; i < 16; i++) {
+ new_link_key.link_key[i] = strtol(from.substr(i * 2, 2).c_str(), &temp, 16);
+ }
+
+ to = new_link_key;
+ return true;
}
} // namespace common
diff --git a/btif/src/btif_activity_attribution.cc b/gd/common/link_key.h
index 9f161cc91..b2bf3941d 100644
--- a/btif/src/btif_activity_attribution.cc
+++ b/gd/common/link_key.h
@@ -1,6 +1,6 @@
/******************************************************************************
*
- * Copyright 2020 The Android Open Source Project
+ * Copyright 2019 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,21 +16,26 @@
*
******************************************************************************/
-#define LOG_TAG "bt_btif_activity_attribution"
+#pragma once
-#include "btif_activity_attribution.h"
-#include "main/shim/activity_attribution.h"
-#include "main/shim/shim.h"
-
-using base::Bind;
-using base::Unretained;
+#include <string>
namespace bluetooth {
-namespace activity_attribution {
+namespace common {
+
+class LinkKey final {
+ public:
+ LinkKey() = default;
+ LinkKey(const uint8_t (&data)[16]);
+
+ static constexpr unsigned int kLength = 16;
+ uint8_t link_key[kLength];
+
+ std::string ToString() const;
+ static bool FromString(const std::string& from, LinkKey& to);
-ActivityAttributionInterface* get_activity_attribution_instance() {
- return bluetooth::shim::get_activity_attribution_instance();
-}
+ static const LinkKey kExample;
+};
-} // namespace activity_attribution
-} // namespace bluetooth
+} // namespace common
+} // namespace bluetooth \ No newline at end of file
diff --git a/gd/common/link_key_unittest.cc b/gd/common/link_key_unittest.cc
new file mode 100644
index 000000000..652956444
--- /dev/null
+++ b/gd/common/link_key_unittest.cc
@@ -0,0 +1,50 @@
+/******************************************************************************
+ *
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+#include "common/link_key.h"
+#include <gtest/gtest.h>
+#include "os/log.h"
+
+using bluetooth::common::LinkKey;
+
+static const char* test_link_key = "4c68384139f574d836bcf34e9dfb01bf\0";
+
+TEST(LinkKeyUnittest, test_constructor_array) {
+ uint8_t data[LinkKey::kLength] = {0x4c, 0x87, 0x49, 0xe1, 0x2e, 0x55, 0x0f, 0x7f,
+ 0x60, 0x8b, 0x4f, 0x96, 0xd7, 0xc5, 0xbc, 0x2a};
+
+ LinkKey link_key(data);
+
+ for (int i = 0; i < LinkKey::kLength; i++) {
+ ASSERT_EQ(data[i], link_key.link_key[i]);
+ }
+}
+
+TEST(LinkKeyUnittest, test_from_str) {
+ LinkKey link_key;
+ LinkKey::FromString(test_link_key, link_key);
+
+ for (int i = 0; i < LinkKey::kLength; i++) {
+ ASSERT_EQ(LinkKey::kExample.link_key[i], link_key.link_key[i]);
+ }
+}
+
+TEST(LinkKeyUnittest, test_to_str) {
+ std::string str = LinkKey::kExample.ToString();
+ ASSERT_STREQ(str.c_str(), test_link_key);
+} \ No newline at end of file
diff --git a/gd/common/list_map.h b/gd/common/list_map.h
deleted file mode 100644
index babf8697c..000000000
--- a/gd/common/list_map.h
+++ /dev/null
@@ -1,220 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <functional>
-#include <iterator>
-#include <list>
-#include <mutex>
-#include <optional>
-#include <thread>
-#include <type_traits>
-#include <unordered_map>
-
-namespace bluetooth {
-namespace common {
-
-// A map that maintains order of its element as a list. An element that is put earlier will appear before an element
-// that is put later when iterating through this map's entries. Keys must be unique.
-//
-// Performance:
-// - Key look-up and modification is O(1)
-// - Value operated by replacement, no in-place modification
-// - Memory consumption is:
-// O(2*capacity*sizeof(K) + capacity*(sizeof(nullptr)+sizeof(V)))
-// - NOT THREAD SAFE
-//
-// Template:
-// - Key key
-// - T value
-template <typename Key, typename T>
-class ListMap {
- public:
- using value_type = std::pair<const Key, T>;
- // different from c++17 node_type on purpose as we want node to be copyable
- using node_type = std::pair<Key, T>;
- using iterator = typename std::list<value_type>::iterator;
- using const_iterator = typename std::list<value_type>::const_iterator;
-
- // Constructor of the list map
- ListMap() = default;
-
- // for move
- ListMap(ListMap&& other) noexcept = default;
- ListMap& operator=(ListMap&& other) noexcept = default;
-
- // copy-constructor
- // iterators in key_map_ cannot be copied directly
- ListMap(const ListMap& other) : node_list_(other.node_list_) {
- for (auto iter = node_list_.begin(); iter != node_list_.end(); iter++) {
- key_map_.emplace(iter->first, iter);
- }
- }
-
- // copy-assignment
- // iterators in key_map_ cannot be copied directly
- ListMap& operator=(const ListMap& other) {
- if (&other == this) {
- return *this;
- }
- node_list_ = other.node_list_;
- key_map_.clear();
- for (auto iter = node_list_.begin(); iter != node_list_.end(); iter++) {
- key_map_.emplace(iter->first, iter);
- }
- return *this;
- }
-
- // comparison operators
- bool operator==(const ListMap& rhs) const {
- return node_list_ == rhs.node_list_;
- }
- bool operator!=(const ListMap& rhs) const {
- return !(*this == rhs);
- }
-
- ~ListMap() {
- clear();
- }
-
- // Clear the list map
- void clear() {
- key_map_.clear();
- node_list_.clear();
- }
-
- // const version of find()
- const_iterator find(const Key& key) const {
- return const_cast<ListMap*>(this)->find(key);
- }
-
- // Get the value of a key. Return iterator to the item if found, end() if not found
- iterator find(const Key& key) {
- auto map_iterator = key_map_.find(key);
- if (map_iterator == key_map_.end()) {
- return end();
- }
- return map_iterator->second;
- }
-
- // Check if key exist in the map. Return true if key exist in map, false if not.
- bool contains(const Key& key) const {
- return find(key) != end();
- }
-
- // Try emplace an element before a specific position |pos| of the list map. If the |key| already exists, does nothing.
- // Moved arguments won't be moved when key already exists. Return <iterator, true> when key does not exist, <iterator,
- // false> when key exist and iterator is the position where it was placed.
- template <class... Args>
- std::pair<iterator, bool> try_emplace(const_iterator pos, const Key& key, Args&&... args) {
- auto map_iterator = key_map_.find(key);
- if (map_iterator != key_map_.end()) {
- return std::make_pair(end(), false);
- }
- auto list_iterator = node_list_.emplace(pos, key, std::forward<Args>(args)...);
- key_map_.emplace(key, list_iterator);
- return std::make_pair(list_iterator, true);
- }
-
- // Try emplace an element before the end of the list map. If the key already exists, does nothing. Moved arguments
- // won't be moved when key already exists return <iterator, true> when key does not exist, <iterator, false> when key
- // exist and iterator is the position where it was placed
- template <class... Args>
- std::pair<iterator, bool> try_emplace_back(const Key& key, Args&&... args) {
- return try_emplace(end(), key, std::forward<Args>(args)...);
- }
-
- // Put a key-value pair to the map before position. If key already exist, |pos| will be ignored and existing value
- // will be replaced
- void insert_or_assign(const_iterator pos, const Key& key, T value) {
- auto map_iterator = key_map_.find(key);
- if (map_iterator != key_map_.end()) {
- map_iterator->second->second = std::move(value);
- return;
- }
- auto list_iterator = node_list_.emplace(pos, key, std::move(value));
- key_map_.emplace(key, list_iterator);
- }
-
- // Put a key-value pair to the tail of the map or replace the current value without moving the key if key exists
- void insert_or_assign(const Key& key, T value) {
- insert_or_assign(end(), key, std::move(value));
- }
-
- // STL splice, same as std::list::splice
- // - pos: element before which the content will be inserted
- // - other: another container to transfer the content from
- // - it: the element to transfer from other to *this
- void splice(const_iterator pos, ListMap<Key, T>& other, const_iterator it) {
- if (&other != this) {
- auto map_node = other.key_map_.extract(it->first);
- key_map_.insert(std::move(map_node));
- }
- node_list_.splice(pos, other.node_list_, it);
- }
-
- // Remove a key from the list map and return removed value if key exits, std::nullopt if not. The return value will be
- // evaluated to true in a boolean context if a value is contained by std::optional, false otherwise.
- std::optional<node_type> extract(const Key& key) {
- auto map_iterator = key_map_.find(key);
- if (map_iterator == key_map_.end()) {
- return std::nullopt;
- }
- std::optional<node_type> removed_node(std::move(*map_iterator->second));
- node_list_.erase(map_iterator->second);
- key_map_.erase(map_iterator);
- return removed_node;
- }
-
- // Remove an iterator pointed item from the list map and return the iterator immediately after the erased item
- iterator erase(const_iterator iter) {
- key_map_.erase(iter->first);
- return node_list_.erase(iter);
- }
-
- // Return size of the list map
- inline size_t size() const {
- return node_list_.size();
- }
-
- // Return iterator interface for begin
- inline iterator begin() {
- return node_list_.begin();
- }
-
- // Iterator interface for begin, const
- inline const_iterator begin() const {
- return node_list_.begin();
- }
-
- // Iterator interface for end
- inline iterator end() {
- return node_list_.end();
- }
-
- // Iterator interface for end, const
- inline const_iterator end() const {
- return node_list_.end();
- }
-
- private:
- std::list<value_type> node_list_;
- std::unordered_map<Key, iterator> key_map_;
-};
-
-} // namespace common
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/common/list_map_test.cc b/gd/common/list_map_test.cc
deleted file mode 100644
index e682eea50..000000000
--- a/gd/common/list_map_test.cc
+++ /dev/null
@@ -1,363 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <chrono>
-#include <memory>
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "common/list_map.h"
-
-namespace testing {
-
-using bluetooth::common::ListMap;
-
-TEST(ListMapTest, empty_test) {
- ListMap<int, int> list_map;
- EXPECT_EQ(list_map.size(), 0);
- EXPECT_EQ(list_map.find(42), list_map.end());
- list_map.clear(); // should not crash
- EXPECT_EQ(list_map.find(42), list_map.end());
- EXPECT_FALSE(list_map.contains(42));
- EXPECT_FALSE(list_map.extract(42));
-}
-
-TEST(ListMapTest, comparison_test) {
- ListMap<int, int> list_map_1;
- list_map_1.insert_or_assign(1, 10);
- list_map_1.insert_or_assign(2, 20);
- ListMap<int, int> list_map_2;
- list_map_2.insert_or_assign(1, 10);
- list_map_2.insert_or_assign(2, 20);
- EXPECT_EQ(list_map_1, list_map_2);
- // List map with different value should be different
- list_map_2.insert_or_assign(1, 11);
- EXPECT_NE(list_map_1, list_map_2);
- // List maps with different order should not be equal
- ListMap<int, int> list_map_3;
- list_map_3.insert_or_assign(2, 20);
- list_map_3.insert_or_assign(1, 10);
- EXPECT_NE(list_map_1, list_map_3);
- // Empty list map should not be equal to non-empty ones
- ListMap<int, int> list_map_4;
- EXPECT_NE(list_map_1, list_map_4);
- // Empty list maps should be equal
- ListMap<int, int> list_map_5;
- EXPECT_EQ(list_map_4, list_map_5);
-}
-
-TEST(ListMapTest, copy_test) {
- ListMap<int, std::shared_ptr<int>> list_map;
- list_map.insert_or_assign(1, std::make_shared<int>(100));
- auto iter = list_map.find(1);
- EXPECT_EQ(*iter->second, 100);
- ListMap<int, std::shared_ptr<int>> new_list_map = list_map;
- iter = new_list_map.find(1);
- EXPECT_EQ(*iter->second, 100);
- *iter->second = 300;
- iter = new_list_map.find(1);
- EXPECT_EQ(*iter->second, 300);
- // Since copy is used, shared_ptr should increase count
- EXPECT_EQ(iter->second.use_count(), 2);
-}
-
-TEST(ListMapTest, move_test) {
- ListMap<int, std::shared_ptr<int>> list_map;
- list_map.insert_or_assign(1, std::make_shared<int>(100));
- auto iter = list_map.find(1);
- EXPECT_EQ(*iter->second, 100);
- ListMap<int, std::shared_ptr<int>> new_list_map = std::move(list_map);
- iter = new_list_map.find(1);
- EXPECT_EQ(*iter->second, 100);
- *iter->second = 300;
- iter = new_list_map.find(1);
- EXPECT_EQ(*iter->second, 300);
- // Since move is used, shared_ptr should not increase count
- EXPECT_EQ(iter->second.use_count(), 1);
-}
-
-TEST(ListMapTest, move_insert_unique_ptr_test) {
- ListMap<int, std::unique_ptr<int>> list_map;
- list_map.insert_or_assign(1, std::make_unique<int>(100));
- auto iter = list_map.find(1);
- EXPECT_EQ(*iter->second, 100);
- list_map.insert_or_assign(1, std::make_unique<int>(400));
- iter = list_map.find(1);
- EXPECT_EQ(*iter->second, 400);
-}
-
-TEST(ListMapTest, move_insert_list_map_test) {
- ListMap<int, ListMap<int, int>> list_map;
- ListMap<int, int> m1;
- m1.insert_or_assign(1, 100);
- list_map.insert_or_assign(1, std::move(m1));
- auto iter = list_map.find(1);
- EXPECT_THAT(iter->second, ElementsAre(Pair(1, 100)));
- ListMap<int, int> m2;
- m2.insert_or_assign(2, 200);
- list_map.insert_or_assign(1, std::move(m2));
- iter = list_map.find(1);
- EXPECT_THAT(iter->second, ElementsAre(Pair(2, 200)));
-}
-
-TEST(ListMapTest, erase_one_item_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- list_map.insert_or_assign(3, 30);
- auto iter = list_map.find(2);
- iter = list_map.erase(iter);
- EXPECT_EQ(iter->first, 3);
- EXPECT_EQ(iter->second, 30);
-}
-
-TEST(ListMapTest, erase_in_for_loop_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- list_map.insert_or_assign(3, 30);
- for (auto iter = list_map.begin(); iter != list_map.end();) {
- if (iter->first == 2) {
- iter = list_map.erase(iter);
- } else {
- ++iter;
- }
- }
- EXPECT_THAT(list_map, ElementsAre(Pair(1, 10), Pair(3, 30)));
-}
-
-TEST(ListMapTest, splice_different_list_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- list_map.insert_or_assign(3, 30);
- ListMap<int, int> list_map_2;
- list_map_2.insert_or_assign(4, 40);
- list_map_2.insert_or_assign(5, 50);
- list_map.splice(list_map.find(2), list_map_2, list_map_2.find(4));
- EXPECT_EQ(list_map_2.find(4), list_map_2.end());
- auto iter = list_map.find(4);
- EXPECT_NE(iter, list_map.end());
- EXPECT_EQ(iter->second, 40);
- EXPECT_THAT(list_map, ElementsAre(Pair(1, 10), Pair(4, 40), Pair(2, 20), Pair(3, 30)));
-}
-
-TEST(ListMapTest, splice_same_list_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- list_map.insert_or_assign(3, 30);
- list_map.splice(list_map.find(2), list_map, list_map.find(3));
- EXPECT_THAT(list_map, ElementsAre(Pair(1, 10), Pair(3, 30), Pair(2, 20)));
- list_map.extract(2);
- list_map.insert_or_assign(list_map.begin(), 4, 40);
- EXPECT_THAT(list_map, ElementsAre(Pair(4, 40), Pair(1, 10), Pair(3, 30)));
- auto iter = list_map.find(4);
- EXPECT_EQ(iter->second, 40);
- list_map.splice(list_map.begin(), list_map, list_map.find(4));
- list_map.splice(list_map.begin(), list_map, list_map.find(3));
- list_map.splice(list_map.begin(), list_map, list_map.find(1));
- EXPECT_THAT(list_map, ElementsAre(Pair(1, 10), Pair(3, 30), Pair(4, 40)));
- iter = list_map.find(4);
- EXPECT_EQ(iter->second, 40);
- iter = list_map.find(3);
- EXPECT_EQ(iter->second, 30);
-}
-
-TEST(ListMapTest, put_get_and_contains_key_test) {
- ListMap<int, int> list_map;
- EXPECT_EQ(list_map.size(), 0);
- EXPECT_EQ(list_map.find(42), list_map.end());
- EXPECT_FALSE(list_map.contains(42));
- list_map.insert_or_assign(56, 200);
- EXPECT_EQ(list_map.find(42), list_map.end());
- EXPECT_FALSE(list_map.contains(42));
- auto iter = list_map.find(56);
- EXPECT_NE(iter, list_map.end());
- EXPECT_TRUE(list_map.contains(56));
- EXPECT_EQ(iter->second, 200);
- EXPECT_TRUE(list_map.extract(56));
- EXPECT_FALSE(list_map.contains(56));
-}
-
-TEST(ListMapTest, try_emplace_at_position_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- auto iter = list_map.find(2);
- EXPECT_EQ(iter->second, 20);
- auto result = list_map.try_emplace(iter, 42, 420);
- EXPECT_TRUE(result.second);
- iter = list_map.find(42);
- EXPECT_EQ(iter->second, 420);
- EXPECT_EQ(iter, result.first);
- ASSERT_THAT(list_map, ElementsAre(Pair(1, 10), Pair(42, 420), Pair(2, 20)));
- EXPECT_FALSE(list_map.try_emplace(result.first, 42, 420).second);
-}
-
-TEST(ListMapTest, try_emplace_back_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- auto result = list_map.try_emplace_back(42, 420);
- EXPECT_TRUE(result.second);
- auto iter = list_map.find(42);
- EXPECT_EQ(iter->second, 420);
- EXPECT_EQ(iter, result.first);
- ASSERT_THAT(list_map, ElementsAre(Pair(1, 10), Pair(2, 20), Pair(42, 420)));
- EXPECT_FALSE(list_map.try_emplace_back(42, 420).second);
-}
-
-TEST(ListMapTest, insert_at_position_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- auto iter = list_map.find(2);
- EXPECT_EQ(iter->second, 20);
- list_map.insert_or_assign(iter, 42, 420);
- iter = list_map.find(42);
- EXPECT_EQ(iter->second, 420);
- ASSERT_THAT(list_map, ElementsAre(Pair(1, 10), Pair(42, 420), Pair(2, 20)));
-}
-
-TEST(ListMapTest, in_place_modification_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- auto iter = list_map.find(2);
- iter->second = 200;
- ASSERT_THAT(list_map, ElementsAre(Pair(1, 10), Pair(2, 200)));
-}
-
-TEST(ListMapTest, get_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- auto iter = list_map.find(1);
- EXPECT_NE(iter, list_map.end());
- EXPECT_EQ(iter->second, 10);
-}
-
-TEST(ListMapTest, remove_test) {
- ListMap<int, int> list_map;
- for (int key = 0; key <= 30; key++) {
- list_map.insert_or_assign(key, key * 100);
- }
- for (int key = 0; key <= 30; key++) {
- EXPECT_TRUE(list_map.contains(key));
- }
- for (int key = 0; key <= 30; key++) {
- auto removed = list_map.extract(key);
- EXPECT_TRUE(removed);
- EXPECT_EQ(*removed, std::make_pair(key, key * 100));
- }
- for (int key = 0; key <= 30; key++) {
- EXPECT_FALSE(list_map.contains(key));
- }
-}
-
-TEST(ListMapTest, clear_test) {
- ListMap<int, int> list_map;
- for (int key = 0; key < 10; key++) {
- list_map.insert_or_assign(key, key * 100);
- }
- for (int key = 0; key < 10; key++) {
- EXPECT_TRUE(list_map.contains(key));
- }
- list_map.clear();
- for (int key = 0; key < 10; key++) {
- EXPECT_FALSE(list_map.contains(key));
- }
-
- for (int key = 0; key < 10; key++) {
- list_map.insert_or_assign(key, key * 1000);
- }
- for (int key = 0; key < 10; key++) {
- EXPECT_TRUE(list_map.contains(key));
- }
-}
-
-TEST(ListMapTest, container_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- ASSERT_THAT(list_map, ElementsAre(Pair(1, 10), Pair(2, 20)));
-}
-
-TEST(ListMapTest, iterator_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- std::list<std::pair<int, int>> list(list_map.begin(), list_map.end());
- ASSERT_THAT(list, ElementsAre(Pair(1, 10), Pair(2, 20)));
-}
-
-TEST(ListMapTest, for_loop_test) {
- ListMap<int, int> list_map;
- list_map.insert_or_assign(1, 10);
- list_map.insert_or_assign(2, 20);
- std::list<std::pair<int, int>> list;
- for (const auto& node : list_map) {
- list.emplace_back(node);
- }
- ASSERT_THAT(list, ElementsAre(Pair(1, 10), Pair(2, 20)));
- list.clear();
- for (auto& node : list_map) {
- list.emplace_back(node);
- node.second = node.second * 2;
- }
- ASSERT_THAT(list, ElementsAre(Pair(1, 10), Pair(2, 20)));
- list.clear();
- for (const auto& node : list_map) {
- list.emplace_back(node);
- }
- ASSERT_THAT(list, ElementsAre(Pair(1, 20), Pair(2, 40)));
-}
-
-TEST(ListMapTest, pressure_test) {
- auto started = std::chrono::high_resolution_clock::now();
- int num_entries = 0xFFFF; // 2^16 = 65535
- ListMap<int, int> list_map;
-
- // fill the list_map
- for (int key = 0; key < num_entries; key++) {
- list_map.insert_or_assign(key, key);
- }
-
- // make sure the list_map is full
- for (int key = 0; key < num_entries; key++) {
- EXPECT_TRUE(list_map.contains(key));
- }
-
- // clear the entire list_map
- for (int key = 0; key < num_entries; key++) {
- auto iter = list_map.find(key);
- EXPECT_NE(iter, list_map.end());
- EXPECT_EQ(iter->second, key);
- EXPECT_TRUE(list_map.extract(key));
- }
- EXPECT_EQ(list_map.size(), 0);
-
- // test execution time
- auto done = std::chrono::high_resolution_clock::now();
- int execution_time = std::chrono::duration_cast<std::chrono::microseconds>(done - started).count();
- // Shouldn't be more than 1000ms
- int execution_time_per_cycle_us = 10;
- EXPECT_LT(execution_time, execution_time_per_cycle_us * num_entries);
-}
-
-} // namespace testing
diff --git a/gd/common/lru_cache.h b/gd/common/lru_cache.h
deleted file mode 100644
index 632eaff06..000000000
--- a/gd/common/lru_cache.h
+++ /dev/null
@@ -1,219 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <functional>
-#include <iterator>
-#include <list>
-#include <mutex>
-#include <optional>
-#include <thread>
-#include <unordered_map>
-
-#include "common/list_map.h"
-#include "os/log.h"
-
-namespace bluetooth {
-namespace common {
-
-// An LRU map-cache the evict the oldest item when reaching capacity
-//
-// Usage:
-// - keys are sorted from warmest to coldest
-// - iterating through the cache won't warm up keys
-// - operations on iterators won't warm up keys
-// - find(), contains(), insert_or_assign() will warm up the key
-// - insert_or_assign() will evict coldest key when cache reaches capacity
-// - NOT THREAD SAFE
-//
-// Performance:
-// - Key look-up and modification is O(1)
-// - Memory consumption is:
-// O(2*capacity*sizeof(K) + capacity*(sizeof(nullptr)+sizeof(V)))
-//
-// Template:
-// - Key key type
-// - T value type
-// */
-template <typename Key, typename T>
-class LruCache {
- public:
- using value_type = typename ListMap<Key, T>::value_type;
- // different from c++17 node_type on purpose as we want node to be copyable
- using node_type = typename ListMap<Key, T>::node_type;
- using iterator = typename ListMap<Key, T>::iterator;
- using const_iterator = typename ListMap<Key, T>::const_iterator;
-
- // Constructor a LRU cache with |capacity|
- explicit LruCache(size_t capacity) : capacity_(capacity) {
- ASSERT_LOG(capacity_ != 0, "Unable to have 0 LRU Cache capacity");
- }
-
- // for move
- LruCache(LruCache&& other) noexcept = default;
- LruCache& operator=(LruCache&& other) noexcept = default;
-
- // copy-constructor
- // iterators in key_map_ cannot be copied directly
- LruCache(const LruCache& other) : capacity_(other.capacity_), list_map_(other.list_map_) {}
-
- // copy-assignment
- // iterators in key_map_ cannot be copied directly
- LruCache& operator=(const LruCache& other) {
- if (&other == this) {
- return *this;
- }
- capacity_ = other.capacity_;
- list_map_ = other.list_map_;
- return *this;
- }
-
- // comparison operators
- bool operator==(const LruCache& rhs) const {
- return capacity_ == rhs.capacity_ && list_map_ == rhs.list_map_;
- }
- bool operator!=(const LruCache& rhs) const {
- return !(*this == rhs);
- }
-
- ~LruCache() {
- clear();
- }
-
- // Clear the cache
- void clear() {
- list_map_.clear();
- }
-
- // Find the value of a key, and move the key to the head of cache, if there is one. Return iterator to value if key
- // exists, end() if not. Iterator might be invalidated when removed or evicted. Const version.
- //
- // LRU: Will warm up key
- // LRU: Access to returned iterator won't move key in LRU
- const_iterator find(const Key& key) const {
- return const_cast<LruCache*>(this)->find(key);
- }
-
- // Find the value of a key, and move the key to the head of cache, if there is one. Return iterator to value if key
- // exists, end() if not. Iterator might be invalidated when removed or evicted
- //
- // LRU: Will warm up key
- // LRU: Access to returned iterator won't move key in LRU
- iterator find(const Key& key) {
- auto iter = list_map_.find(key);
- if (iter == list_map_.end()) {
- return end();
- }
- // move to front
- list_map_.splice(list_map_.begin(), list_map_, iter);
- return iter;
- }
-
- // Check if key exist in the cache. Return true if key exist in cache, false, if not
- //
- // LRU: Will warm up key
- bool contains(const Key& key) const {
- return find(key) != list_map_.end();
- }
-
- // Put a key-value pair to the head of cache, evict the oldest key if cache is at capacity. Eviction is based on key
- // ONLY. Hence, updating a key will not evict the oldest key. Return evicted value if old value was evicted,
- // std::nullopt if not. The return value will be evaluated to true in a boolean context if a value is contained by
- // std::optional, false otherwise.
- //
- // LRU: Will warm up key
- std::optional<node_type> insert_or_assign(const Key& key, T value) {
- if (contains(key)) {
- // contains() calls find() that moved the node to the head
- list_map_.begin()->second = std::move(value);
- return std::nullopt;
- }
- // remove tail if at capacity
- std::optional<node_type> evicted_node = std::nullopt;
- if (list_map_.size() == capacity_) {
- evicted_node = list_map_.extract(std::prev(list_map_.end())->first);
- }
- // insert new one to front of list
- list_map_.insert_or_assign(list_map_.begin(), key, std::move(value));
- return evicted_node;
- }
-
- // Put a key-value pair to the head of cache, evict the oldest key if cache is at capacity. Eviction is based on key
- // ONLY. Hence, updating a key will not evict the oldest key. This method tries to construct the value in-place. If
- // the key already exist, this method only update the value. Return inserted iterator, whether insertion happens, and
- // evicted value if old value was evicted or std::nullopt
- //
- // LRU: Will warm up key
- template <class... Args>
- std::tuple<iterator, bool, std::optional<node_type>> try_emplace(const Key& key, Args&&... args) {
- if (contains(key)) {
- // contains() calls find() that moved the node to the head
- return std::make_tuple(end(), false, std::nullopt);
- }
- // remove tail if at capacity
- std::optional<node_type> evicted_node = std::nullopt;
- if (list_map_.size() == capacity_) {
- evicted_node = list_map_.extract(std::prev(list_map_.end())->first);
- }
- // insert new one to front of list
- auto pair = list_map_.try_emplace(list_map_.begin(), key, std::forward<Args>(args)...);
- return std::make_tuple(pair.first, pair.second, std::move(evicted_node));
- }
-
- // Delete a key from cache, return removed value if old value was evicted, std::nullopt if not. The return value will
- // be evaluated to true in a boolean context if a value is contained by std::optional, false otherwise.
- inline std::optional<node_type> extract(const Key& key) {
- return list_map_.extract(key);
- }
-
- /// Remove an iterator pointed item from the lru cache and return the iterator immediately after the erased item
- iterator erase(const_iterator iter) {
- return list_map_.erase(iter);
- }
-
- // Return size of the cache
- inline size_t size() const {
- return list_map_.size();
- }
-
- // Iterator interface for begin
- inline iterator begin() {
- return list_map_.begin();
- }
-
- // Return iterator interface for begin, const
- inline const_iterator begin() const {
- return list_map_.begin();
- }
-
- // Return iterator interface for end
- inline iterator end() {
- return list_map_.end();
- }
-
- // Iterator interface for end, const
- inline const_iterator end() const {
- return list_map_.end();
- }
-
- private:
- size_t capacity_;
- ListMap<Key, T> list_map_;
-};
-
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/common/lru_cache_test.cc b/gd/common/lru_cache_test.cc
deleted file mode 100644
index 62b03dd2e..000000000
--- a/gd/common/lru_cache_test.cc
+++ /dev/null
@@ -1,461 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <chrono>
-#include <limits>
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "common/lru_cache.h"
-
-namespace testing {
-
-using bluetooth::common::LruCache;
-
-TEST(LruCacheTest, empty_test) {
- LruCache<int, int> cache(3); // capacity = 3;
- EXPECT_EQ(cache.size(), 0);
- EXPECT_EQ(cache.find(42), cache.end());
- cache.clear(); // should not crash
- EXPECT_EQ(cache.find(42), cache.end());
- EXPECT_FALSE(cache.contains(42));
- EXPECT_FALSE(cache.extract(42));
-}
-
-TEST(LruCacheTest, comparison_test) {
- LruCache<int, int> cache_1(2);
- cache_1.insert_or_assign(1, 10);
- cache_1.insert_or_assign(2, 20);
- LruCache<int, int> cache_2(2);
- cache_2.insert_or_assign(1, 10);
- cache_2.insert_or_assign(2, 20);
- EXPECT_EQ(cache_1, cache_2);
- // Cache with different order should not be equal
- cache_2.find(1);
- EXPECT_NE(cache_1, cache_2);
- cache_1.find(1);
- EXPECT_EQ(cache_1, cache_2);
- // Cache with different value should be different
- cache_2.insert_or_assign(1, 11);
- EXPECT_NE(cache_1, cache_2);
- // Cache with different capacity should not be equal
- LruCache<int, int> cache_3(3);
- cache_3.insert_or_assign(1, 10);
- cache_3.insert_or_assign(2, 20);
- EXPECT_NE(cache_1, cache_3);
- // Empty cache should not be equal to non-empty ones
- LruCache<int, int> cache_4(2);
- EXPECT_NE(cache_1, cache_4);
- // Empty caches should be equal
- LruCache<int, int> cache_5(2);
- EXPECT_EQ(cache_4, cache_5);
- // Empty caches with different capacity should not be equal
- LruCache<int, int> cache_6(3);
- EXPECT_NE(cache_4, cache_6);
-}
-
-TEST(LruCacheTest, try_emplace_test) {
- LruCache<int, int> cache(2);
- cache.insert_or_assign(1, 10);
- cache.insert_or_assign(2, 20);
- auto result = cache.try_emplace(42, 420);
- // 1, 10 evicted
- EXPECT_EQ(std::get<2>(result), std::make_pair(1, 10));
- auto iter = cache.find(42);
- EXPECT_EQ(iter->second, 420);
- EXPECT_EQ(iter, std::get<0>(result));
- ASSERT_THAT(cache, ElementsAre(Pair(42, 420), Pair(2, 20)));
-}
-
-TEST(LruCacheTest, copy_test) {
- LruCache<int, std::shared_ptr<int>> cache(2);
- cache.insert_or_assign(1, std::make_shared<int>(100));
- auto iter = cache.find(1);
- EXPECT_EQ(*iter->second, 100);
- LruCache<int, std::shared_ptr<int>> new_cache = cache;
- iter = new_cache.find(1);
- EXPECT_EQ(*iter->second, 100);
- *iter->second = 300;
- iter = new_cache.find(1);
- EXPECT_EQ(*iter->second, 300);
- // Since copy is used, shared_ptr should increase count
- EXPECT_EQ(iter->second.use_count(), 2);
-}
-
-TEST(LruCacheTest, move_test) {
- LruCache<int, std::shared_ptr<int>> cache(2);
- cache.insert_or_assign(1, std::make_shared<int>(100));
- auto iter = cache.find(1);
- EXPECT_EQ(*iter->second, 100);
- LruCache<int, std::shared_ptr<int>> new_cache = std::move(cache);
- iter = new_cache.find(1);
- EXPECT_EQ(*iter->second, 100);
- *iter->second = 300;
- iter = new_cache.find(1);
- EXPECT_EQ(*iter->second, 300);
- // Since move is used, shared_ptr should not increase count
- EXPECT_EQ(iter->second.use_count(), 1);
-}
-
-TEST(LruCacheTest, move_insert_unique_ptr_test) {
- LruCache<int, std::unique_ptr<int>> cache(2);
- cache.insert_or_assign(1, std::make_unique<int>(100));
- auto iter = cache.find(1);
- EXPECT_EQ(*iter->second, 100);
- cache.insert_or_assign(1, std::make_unique<int>(400));
- iter = cache.find(1);
- EXPECT_EQ(*iter->second, 400);
-}
-
-TEST(LruCacheTest, move_insert_cache_test) {
- LruCache<int, LruCache<int, int>> cache(2);
- LruCache<int, int> m1(2);
- m1.insert_or_assign(1, 100);
- cache.insert_or_assign(1, std::move(m1));
- auto iter = cache.find(1);
- EXPECT_THAT(iter->second, ElementsAre(Pair(1, 100)));
- LruCache<int, int> m2(2);
- m2.insert_or_assign(2, 200);
- cache.insert_or_assign(1, std::move(m2));
- iter = cache.find(1);
- EXPECT_THAT(iter->second, ElementsAre(Pair(2, 200)));
-}
-
-TEST(LruCacheTest, erase_one_item_test) {
- LruCache<int, int> cache(3);
- cache.insert_or_assign(1, 10);
- cache.insert_or_assign(2, 20);
- cache.insert_or_assign(3, 30);
- auto iter = cache.find(2);
- // 2, 3, 1
- cache.find(3);
- // 3, 2, 1
- iter = cache.erase(iter);
- EXPECT_EQ(iter->first, 1);
- EXPECT_EQ(iter->second, 10);
- EXPECT_THAT(cache, ElementsAre(Pair(3, 30), Pair(1, 10)));
-}
-
-TEST(LruCacheTest, erase_in_for_loop_test) {
- LruCache<int, int> cache(3);
- cache.insert_or_assign(1, 10);
- cache.insert_or_assign(2, 20);
- cache.insert_or_assign(3, 30);
- for (auto iter = cache.begin(); iter != cache.end();) {
- if (iter->first == 2) {
- iter = cache.erase(iter);
- } else {
- ++iter;
- }
- }
- EXPECT_THAT(cache, ElementsAre(Pair(3, 30), Pair(1, 10)));
-}
-
-TEST(LruCacheTest, get_and_contains_key_test) {
- LruCache<int, int> cache(3); // capacity = 3;
- EXPECT_EQ(cache.size(), 0);
- EXPECT_EQ(cache.find(42), cache.end());
- EXPECT_FALSE(cache.contains(42));
- EXPECT_FALSE(cache.insert_or_assign(56, 200));
- EXPECT_EQ(cache.find(42), cache.end());
- EXPECT_FALSE(cache.contains(42));
- EXPECT_NE(cache.find(56), cache.end());
- EXPECT_TRUE(cache.contains(56));
- auto iter = cache.find(56);
- EXPECT_NE(iter, cache.end());
- EXPECT_EQ(iter->second, 200);
- EXPECT_TRUE(cache.extract(56));
- EXPECT_FALSE(cache.contains(56));
-}
-
-TEST(LruCacheTest, put_and_get_sequence_1) {
- // Section 1: Ordered put and ordered get
- LruCache<int, int> cache(3); // capacity = 3;
- EXPECT_FALSE(cache.insert_or_assign(1, 10));
- EXPECT_EQ(cache.size(), 1);
- EXPECT_FALSE(cache.insert_or_assign(2, 20));
- EXPECT_EQ(cache.size(), 2);
- EXPECT_FALSE(cache.insert_or_assign(3, 30));
- EXPECT_EQ(cache.size(), 3);
- // 3, 2, 1 after above operations
-
- auto evicted = cache.insert_or_assign(4, 40);
- // 4, 3, 2 after above operations, 1 is evicted
- EXPECT_TRUE(evicted);
- EXPECT_EQ(*evicted, std::make_pair(1, 10));
- EXPECT_EQ(cache.find(1), cache.end());
- LruCache<int, int>::const_iterator iter;
- EXPECT_NE(iter = cache.find(4), cache.end());
- EXPECT_EQ(iter->second, 40);
- EXPECT_NE(iter = cache.find(2), cache.end());
- EXPECT_EQ(iter->second, 20);
- EXPECT_NE(iter = cache.find(3), cache.end());
- EXPECT_EQ(iter->second, 30);
- // 3, 2, 4 after above operations
-
- // Section 2: Over capacity put and ordered get
- evicted = cache.insert_or_assign(5, 50);
- // 5, 3, 2 after above operations, 4 is evicted
- EXPECT_EQ(cache.size(), 3);
- EXPECT_TRUE(evicted);
- EXPECT_EQ(*evicted, std::make_pair(4, 40));
-
- EXPECT_TRUE(cache.extract(3));
- // 5, 2 should be in cache, 3 is removed
- EXPECT_FALSE(cache.insert_or_assign(6, 60));
- // 6, 5, 2 should be in cache
-
- // Section 3: Out of order get
- EXPECT_EQ(cache.find(3), cache.end());
- EXPECT_EQ(cache.find(4), cache.end());
- EXPECT_NE(iter = cache.find(2), cache.end());
- // 2, 6, 5 should be in cache
- EXPECT_EQ(iter->second, 20);
- EXPECT_NE(iter = cache.find(6), cache.end());
- // 6, 2, 5 should be in cache
- EXPECT_EQ(iter->second, 60);
- EXPECT_NE(iter = cache.find(5), cache.end());
- // 5, 6, 2 should be in cache
- EXPECT_EQ(iter->second, 50);
- evicted = cache.insert_or_assign(7, 70);
- // 7, 5, 6 should be in cache, 2 is evicted
- EXPECT_TRUE(evicted);
- EXPECT_EQ(*evicted, std::make_pair(2, 20));
-}
-
-TEST(LruCacheTest, put_and_get_sequence_2) {
- // Section 1: Replace item in cache
- LruCache<int, int> cache(2); // size = 2;
- EXPECT_FALSE(cache.insert_or_assign(1, 10));
- EXPECT_FALSE(cache.insert_or_assign(2, 20));
- // 2, 1 in cache
- auto evicted = cache.insert_or_assign(3, 30);
- // 3, 2 in cache, 1 is evicted
- EXPECT_TRUE(evicted);
- EXPECT_EQ(*evicted, std::make_pair(1, 10));
- EXPECT_FALSE(cache.insert_or_assign(2, 200));
- // 2, 3 in cache, nothing is evicted
- EXPECT_EQ(cache.size(), 2);
-
- EXPECT_FALSE(cache.contains(1));
- LruCache<int, int>::const_iterator iter;
- EXPECT_NE(iter = cache.find(2), cache.end());
- EXPECT_EQ(iter->second, 200);
- EXPECT_NE(iter = cache.find(3), cache.end());
- // 3, 2 in cache
- EXPECT_EQ(iter->second, 30);
-
- evicted = cache.insert_or_assign(4, 40);
- // 4, 3 in cache, 2 is evicted
- EXPECT_TRUE(evicted);
- EXPECT_EQ(*evicted, std::make_pair(2, 200));
-
- EXPECT_FALSE(cache.contains(2));
- EXPECT_NE(iter = cache.find(3), cache.end());
- EXPECT_EQ(iter->second, 30);
- EXPECT_NE(iter = cache.find(4), cache.end());
- EXPECT_EQ(iter->second, 40);
- // 4, 3 in cache
-
- EXPECT_TRUE(cache.extract(4));
- EXPECT_FALSE(cache.contains(4));
- // 3 in cache
- EXPECT_EQ(cache.size(), 1);
- EXPECT_FALSE(cache.insert_or_assign(2, 2000));
- // 2, 3 in cache
-
- EXPECT_FALSE(cache.contains(4));
- EXPECT_NE(iter = cache.find(3), cache.end());
- EXPECT_EQ(iter->second, 30);
- EXPECT_NE(iter = cache.find(2), cache.end());
- EXPECT_EQ(iter->second, 2000);
-
- EXPECT_TRUE(cache.extract(2));
- EXPECT_TRUE(cache.extract(3));
- EXPECT_FALSE(cache.insert_or_assign(5, 50));
- EXPECT_FALSE(cache.insert_or_assign(1, 100));
- EXPECT_FALSE(cache.insert_or_assign(5, 1000));
- EXPECT_EQ(cache.size(), 2);
- // 5, 1 in cache
-
- evicted = cache.insert_or_assign(6, 2000);
- // 6, 5 in cache
- EXPECT_TRUE(evicted);
- EXPECT_EQ(*evicted, std::make_pair(1, 100));
-
- EXPECT_FALSE(cache.contains(2));
- EXPECT_FALSE(cache.contains(3));
- EXPECT_NE(iter = cache.find(6), cache.end());
- EXPECT_EQ(iter->second, 2000);
- EXPECT_NE(iter = cache.find(5), cache.end());
- EXPECT_EQ(iter->second, 1000);
-}
-
-TEST(LruCacheTest, in_place_modification_test) {
- LruCache<int, int> cache(2);
- cache.insert_or_assign(1, 10);
- cache.insert_or_assign(2, 20);
- auto iter = cache.find(2);
- ASSERT_THAT(cache, ElementsAre(Pair(2, 20), Pair(1, 10)));
- iter->second = 200;
- ASSERT_THAT(cache, ElementsAre(Pair(2, 200), Pair(1, 10)));
- cache.insert_or_assign(1, 100);
- // 1, 2 in cache
- ASSERT_THAT(cache, ElementsAre(Pair(1, 100), Pair(2, 200)));
- // modifying iterator does not warm up key
- iter->second = 400;
- ASSERT_THAT(cache, ElementsAre(Pair(1, 100), Pair(2, 400)));
-}
-
-TEST(LruCacheTest, get_test) {
- LruCache<int, int> cache(2);
- EXPECT_FALSE(cache.insert_or_assign(1, 10));
- EXPECT_FALSE(cache.insert_or_assign(2, 20));
- EXPECT_TRUE(cache.contains(1));
- // 1, 2 in cache
- auto evicted = cache.insert_or_assign(3, 30);
- // 3, 1 in cache
- EXPECT_TRUE(evicted);
- EXPECT_EQ(*evicted, std::make_pair(2, 20));
-}
-
-TEST(LruCacheTest, remove_test) {
- LruCache<int, int> cache(10);
- for (int key = 0; key <= 30; key++) {
- cache.insert_or_assign(key, key * 100);
- }
- for (int key = 0; key <= 20; key++) {
- EXPECT_FALSE(cache.contains(key));
- }
- for (int key = 21; key <= 30; key++) {
- EXPECT_TRUE(cache.contains(key));
- }
- for (int key = 0; key <= 20; key++) {
- EXPECT_FALSE(cache.extract(key));
- }
- for (int key = 21; key <= 30; key++) {
- auto removed = cache.extract(key);
- EXPECT_TRUE(removed);
- EXPECT_EQ(*removed, std::make_pair(key, key * 100));
- }
- for (int key = 21; key <= 30; key++) {
- EXPECT_FALSE(cache.contains(key));
- }
-}
-
-TEST(LruCacheTest, clear_test) {
- LruCache<int, int> cache(10);
- for (int key = 0; key < 10; key++) {
- cache.insert_or_assign(key, key * 100);
- }
- for (int key = 0; key < 10; key++) {
- EXPECT_TRUE(cache.contains(key));
- }
- cache.clear();
- for (int key = 0; key < 10; key++) {
- EXPECT_FALSE(cache.contains(key));
- }
-
- for (int key = 0; key < 10; key++) {
- cache.insert_or_assign(key, key * 1000);
- }
- for (int key = 0; key < 10; key++) {
- EXPECT_TRUE(cache.contains(key));
- }
-}
-
-TEST(LruCacheTest, container_test) {
- LruCache<int, int> lru_cache(2);
- lru_cache.insert_or_assign(1, 10);
- lru_cache.insert_or_assign(2, 20);
- // Warm elements first
- ASSERT_THAT(lru_cache, ElementsAre(Pair(2, 20), Pair(1, 10)));
-}
-
-TEST(LruCacheTest, iterator_test) {
- LruCache<int, int> lru_cache(2);
- lru_cache.insert_or_assign(1, 10);
- lru_cache.insert_or_assign(2, 20);
- // Warm elements first
- std::list<std::pair<int, int>> list(lru_cache.begin(), lru_cache.end());
- ASSERT_THAT(list, ElementsAre(Pair(2, 20), Pair(1, 10)));
-}
-
-TEST(LruCacheTest, for_loop_test) {
- LruCache<int, int> lru_cache(2);
- lru_cache.insert_or_assign(1, 10);
- lru_cache.insert_or_assign(2, 20);
- // Warm elements first
- std::list<std::pair<int, int>> list;
- for (const auto& node : lru_cache) {
- list.emplace_back(node);
- }
- ASSERT_THAT(list, ElementsAre(Pair(2, 20), Pair(1, 10)));
- list.clear();
- for (auto& node : lru_cache) {
- list.emplace_back(node);
- node.second = node.second * 2;
- }
- ASSERT_THAT(list, ElementsAre(Pair(2, 20), Pair(1, 10)));
- list.clear();
- for (const auto& node : lru_cache) {
- list.emplace_back(node);
- }
- ASSERT_THAT(list, ElementsAre(Pair(2, 40), Pair(1, 20)));
-}
-
-TEST(LruCacheTest, pressure_test) {
- auto started = std::chrono::high_resolution_clock::now();
- int capacity = 0xFFFF; // 2^16 = 65535
- LruCache<int, int> cache(static_cast<size_t>(capacity));
-
- // fill the cache
- for (int key = 0; key < capacity; key++) {
- cache.insert_or_assign(key, key);
- }
-
- // make sure the cache is full
- for (int key = 0; key < capacity; key++) {
- EXPECT_TRUE(cache.contains(key));
- }
-
- // refresh the entire cache
- for (int key = 0; key < capacity; key++) {
- int new_key = key + capacity;
- cache.insert_or_assign(new_key, new_key);
- EXPECT_FALSE(cache.contains(key));
- EXPECT_TRUE(cache.contains(new_key));
- }
-
- // clear the entire cache
- LruCache<int, int>::const_iterator iter;
- for (int key = capacity; key < 2 * capacity; key++) {
- EXPECT_NE(iter = cache.find(key), cache.end());
- EXPECT_EQ(iter->second, key);
- EXPECT_TRUE(cache.extract(key));
- }
- EXPECT_EQ(cache.size(), 0);
-
- // test execution time
- auto done = std::chrono::high_resolution_clock::now();
- int execution_time = std::chrono::duration_cast<std::chrono::microseconds>(done - started).count();
- // Shouldn't be more than 1120ms
- int execution_time_per_cycle_us = 17;
- EXPECT_LT(execution_time, execution_time_per_cycle_us * capacity);
-}
-
-} // namespace testing
diff --git a/gd/common/metric_id_manager.cc b/gd/common/metric_id_manager.cc
deleted file mode 100644
index ef72097b0..000000000
--- a/gd/common/metric_id_manager.cc
+++ /dev/null
@@ -1,203 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2020 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-#define LOG_TAG "BluetoothMetricIdManager"
-
-#include <functional>
-#include <iterator>
-#include <mutex>
-#include <optional>
-#include <thread>
-
-#include "os/log.h"
-#include "common/metric_id_manager.h"
-
-namespace bluetooth {
-namespace common {
-
-using hci::Address;
-
-const size_t MetricIdManager::kMaxNumUnpairedDevicesInMemory = 200;
-const size_t MetricIdManager::kMaxNumPairedDevicesInMemory = 65000;
-const int MetricIdManager::kMinId = 1;
-const int MetricIdManager::kMaxId = 65534; // 2^16 - 2
-
-// id space should always be larger than kMaxNumPairedDevicesInMemory +
-// kMaxNumUnpairedDevicesInMemory
-static_assert((MetricIdManager::kMaxNumUnpairedDevicesInMemory +
- MetricIdManager::kMaxNumPairedDevicesInMemory) <
- (MetricIdManager::kMaxId - MetricIdManager::kMinId),
- "id space should always be larger than "
- "kMaxNumPairedDevicesInMemory + MaxNumUnpairedDevicesInMemory");
-
-MetricIdManager::MetricIdManager()
- : paired_device_cache_(kMaxNumPairedDevicesInMemory),
- temporary_device_cache_(kMaxNumUnpairedDevicesInMemory) {}
-
-bool MetricIdManager::Init(
- const std::unordered_map<Address, int>& paired_device_map,
- Callback save_id_callback, Callback forget_device_callback) {
- std::lock_guard<std::mutex> lock(id_allocator_mutex_);
- if (initialized_) {
- return false;
- }
-
- // init paired_devices_map
- if (paired_device_map.size() > kMaxNumPairedDevicesInMemory) {
- LOG_ALWAYS_FATAL(
- "Paired device map has size %zu, which is bigger than "
- "kMaxNumPairedDevicesInMemory %zu",
- paired_device_map.size(), kMaxNumPairedDevicesInMemory);
- // fail loudly to let caller know
- return false;
- }
-
- next_id_ = kMinId;
- for (const auto& p : paired_device_map) {
- if (p.second < kMinId || p.second > kMaxId) {
- LOG_ALWAYS_FATAL("Invalid Bluetooth Metric Id in config. "
- "Id %d of %s is out of range [%d, %d]",
- p.second, p.first.ToString().c_str(), kMinId, kMaxId);
- }
- auto evicted = paired_device_cache_.insert_or_assign(p.first, p.second);
- if (evicted) {
- ForgetDevicePostprocess(evicted->first, evicted->second);
- }
- id_set_.insert(p.second);
- next_id_ = std::max(next_id_, p.second + 1);
- }
- if (next_id_ > kMaxId) {
- next_id_ = kMinId;
- }
-
- // init callbacks
- save_id_callback_ = save_id_callback;
- forget_device_callback_ = forget_device_callback;
-
- return initialized_ = true;
-}
-
-MetricIdManager::~MetricIdManager() { Close(); }
-
-bool MetricIdManager::Close() {
- std::lock_guard<std::mutex> lock(id_allocator_mutex_);
- if (!initialized_) {
- return false;
- }
- paired_device_cache_.clear();
- temporary_device_cache_.clear();
- id_set_.clear();
- initialized_ = false;
- return true;
-}
-
-MetricIdManager& MetricIdManager::GetInstance() {
- static MetricIdManager metric_id_allocator;
- return metric_id_allocator;
-}
-
-bool MetricIdManager::IsEmpty() const {
- std::lock_guard<std::mutex> lock(id_allocator_mutex_);
- return paired_device_cache_.size() == 0 &&
- temporary_device_cache_.size() == 0;
-}
-
-// call this function when a new device is scanned
-int MetricIdManager::AllocateId(const Address& mac_address) {
- std::lock_guard<std::mutex> lock(id_allocator_mutex_);
- auto it = paired_device_cache_.find(mac_address);
- // if already have an id, return it
- if (it != paired_device_cache_.end()) {
- return it->second;
- }
- it = temporary_device_cache_.find(mac_address);
- if (it != temporary_device_cache_.end()) {
- return it->second;
- }
-
- // find next available id
- while (id_set_.count(next_id_) > 0) {
- next_id_++;
- if (next_id_ > kMaxId) {
- next_id_ = kMinId;
- LOG_WARN("Bluetooth metric id overflow.");
- }
- }
- int id = next_id_++;
- id_set_.insert(id);
- auto evicted = temporary_device_cache_.insert_or_assign(mac_address, id);
- if (evicted) {
- this->id_set_.extract(evicted->second);
- }
-
- if (next_id_ > kMaxId) {
- next_id_ = kMinId;
- }
- return id;
-}
-
-// call this function when a device is paired
-bool MetricIdManager::SaveDevice(const Address& mac_address) {
- std::lock_guard<std::mutex> lock(id_allocator_mutex_);
- if (paired_device_cache_.contains(mac_address)) {
- return true;
- }
- if (!temporary_device_cache_.contains(mac_address)) {
- LOG_ERROR("Failed to save device because device is not in "
- "temporary_device_cache_");
- return false;
- }
- auto opt = temporary_device_cache_.extract(mac_address);
- if (!opt) {
- LOG_ERROR("Failed to remove device from temporary_device_cache_");
- return false;
- }
- int id = opt->second;
- auto evicted = paired_device_cache_.insert_or_assign(mac_address, id);
- if (evicted) {
- ForgetDevicePostprocess(evicted->first, evicted->second);
- }
- if (!save_id_callback_(mac_address, id)) {
- LOG_ERROR("Callback returned false after saving the device");
- return false;
- }
- return true;
-}
-
-// call this function when a device is forgotten
-void MetricIdManager::ForgetDevice(const Address& mac_address) {
- std::lock_guard<std::mutex> lock(id_allocator_mutex_);
- auto opt = paired_device_cache_.extract(mac_address);
- if (!opt) {
- LOG_ERROR("Failed to remove device from paired_device_cache_");
- return;
- }
- ForgetDevicePostprocess(mac_address, opt->second);
-}
-
-bool MetricIdManager::IsValidId(const int id) {
- return id >= kMinId && id <= kMaxId;
-}
-
-void MetricIdManager::ForgetDevicePostprocess(const Address& mac_address,
- const int id) {
- id_set_.erase(id);
- forget_device_callback_(mac_address, id);
-}
-
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/common/metric_id_manager.h b/gd/common/metric_id_manager.h
deleted file mode 100644
index e238e22c8..000000000
--- a/gd/common/metric_id_manager.h
+++ /dev/null
@@ -1,140 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2020 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#pragma once
-
-#include <mutex>
-#include <string>
-#include <thread>
-#include <unordered_set>
-
-#include "common/lru_cache.h"
-#include "hci/address.h"
-
-namespace bluetooth {
-namespace common {
-
-class MetricIdManager {
- public:
- using Callback = std::function<bool(const hci::Address& address, const int id)>;
-
- static const size_t kMaxNumUnpairedDevicesInMemory;
- static const size_t kMaxNumPairedDevicesInMemory;
-
- static const int kMinId;
- static const int kMaxId;
-
- ~MetricIdManager();
-
- /**
- * Get the instance of singleton
- *
- * @return MetricIdManager&
- */
- static MetricIdManager& GetInstance();
-
- /**
- * Initialize the allocator
- *
- * @param paired_device_map map from mac_address to id already saved
- * in the disk before init
- * @param save_id_callback a callback that will be called after successfully
- * saving id for a paired device
- * @param forget_device_callback a callback that will be called after
- * successful id deletion for forgotten device,
- * @return true if successfully initialized
- */
- bool Init(
- const std::unordered_map<hci::Address, int>& paired_device_map,
- Callback save_id_callback,
- Callback forget_device_callback);
-
- /**
- * Close the allocator. should be called when Bluetooth process is killed
- *
- * @return true if successfully close
- */
- bool Close();
-
- /**
- * Check if no id saved in memory
- *
- * @return true if no id is saved
- */
- bool IsEmpty() const;
-
- /**
- * Allocate an id for a scanned device, or return the id if there is already
- * one
- *
- * @param mac_address mac address of Bluetooth device
- * @return the id of device
- */
- int AllocateId(const hci::Address& mac_address);
-
- /**
- * Save the id for a paired device
- *
- * @param mac_address mac address of Bluetooth device
- * @return true if save successfully
- */
- bool SaveDevice(const hci::Address& mac_address);
-
- /**
- * Delete the id for a device to be forgotten
- *
- * @param mac_address mac address of Bluetooth device
- */
- void ForgetDevice(const hci::Address& mac_address);
-
- /**
- * Check if an id is valid.
- * The id should be less than or equal to kMaxId and bigger than or equal to
- * kMinId
- *
- * @param mac_address mac address of Bluetooth device
- * @return true if delete successfully
- */
- static bool IsValidId(const int id);
-
- protected:
- // Singleton
- MetricIdManager();
-
- private:
- mutable std::mutex id_allocator_mutex_;
-
- LruCache<hci::Address, int> paired_device_cache_;
- LruCache<hci::Address, int> temporary_device_cache_;
- std::unordered_set<int> id_set_;
-
- int next_id_{kMinId};
- bool initialized_{false};
- Callback save_id_callback_;
- Callback forget_device_callback_;
-
- void ForgetDevicePostprocess(const hci::Address& mac_address,
- const int id);
-
- // delete copy constructor for singleton
- MetricIdManager(MetricIdManager const&) = delete;
- MetricIdManager& operator=(MetricIdManager const&) = delete;
-};
-
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/common/metric_id_manager_unittest.cc b/gd/common/metric_id_manager_unittest.cc
deleted file mode 100644
index a64002b0b..000000000
--- a/gd/common/metric_id_manager_unittest.cc
+++ /dev/null
@@ -1,500 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2020 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-#include <thread>
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "common/metric_id_manager.h"
-
-namespace testing {
-
-using bluetooth::common::MetricIdManager;
-
-bluetooth::hci::Address kthAddress(uint32_t k) {
- uint8_t array[6] = {0, 0, 0, 0, 0, 0};
- for (int i = 5; i >= 2; i--) {
- array[i] = k % 256;
- k = k / 256;
- }
- bluetooth::hci::Address addr(array);
- return addr;
-}
-
-std::unordered_map<bluetooth::hci::Address, int> generateAddresses(
- const uint32_t num) {
- // generate first num of mac address -> id pairs
- // input may is always valid 256^6 = 2^48 > 2^32
- std::unordered_map<bluetooth::hci::Address, int> device_map;
- for (size_t key = 0; key < num; key++) {
- device_map[kthAddress(key)] = key + MetricIdManager::kMinId;
- }
- return device_map;
-}
-
-TEST(BluetoothMetricIdManagerTest, MetricIdManagerInitCloseTest) {
- auto& manager = MetricIdManager::GetInstance();
- std::unordered_map<bluetooth::hci::Address, int> paired_device_map;
- MetricIdManager::Callback callback = [](
- const bluetooth::hci::Address&, const int) {
- return true;
- };
- ASSERT_TRUE(manager.Init(paired_device_map, callback, callback));
- ASSERT_FALSE(manager.Init(paired_device_map, callback, callback));
- ASSERT_TRUE(manager.Close());
-}
-
-TEST(BluetoothMetricIdManagerTest, MetricIdManagerNotCloseTest) {
- auto& manager = MetricIdManager::GetInstance();
- std::unordered_map<bluetooth::hci::Address, int> paired_device_map;
- MetricIdManager::Callback callback = [](
- const bluetooth::hci::Address&, const int) {
- return true;
- };
- ASSERT_TRUE(manager.Init(paired_device_map, callback, callback));
-
- // should fail because it isn't closed
- ASSERT_FALSE(manager.Init(paired_device_map, callback, callback));
- ASSERT_TRUE(manager.Close());
-}
-
-TEST(BluetoothMetricIdManagerTest, MetricIdManagerScanDeviceFromEmptyTest) {
- auto& manager = MetricIdManager::GetInstance();
- std::unordered_map<bluetooth::hci::Address, int> paired_device_map;
- MetricIdManager::Callback callback = [](
- const bluetooth::hci::Address&, const int) {
- return true;
- };
- // test empty map, next id should be kMinId
- ASSERT_TRUE(manager.Init(paired_device_map, callback, callback));
- ASSERT_EQ(manager.AllocateId(kthAddress(0)), MetricIdManager::kMinId);
- ASSERT_EQ(manager.AllocateId(kthAddress(1)), MetricIdManager::kMinId + 1);
- ASSERT_EQ(manager.AllocateId(kthAddress(0)), MetricIdManager::kMinId);
- ASSERT_EQ(manager.AllocateId(kthAddress(2)), MetricIdManager::kMinId + 2);
- ASSERT_TRUE(manager.Close());
-}
-
-TEST(BluetoothMetricIdManagerTest,
- MetricIdManagerScanDeviceFromFilledTest) {
- auto& manager = MetricIdManager::GetInstance();
- std::unordered_map<bluetooth::hci::Address, int> paired_device_map;
- MetricIdManager::Callback callback = [](
- const bluetooth::hci::Address&, const int) {
- return true;
- };
- int id = static_cast<int>(MetricIdManager::kMaxNumPairedDevicesInMemory) +
- MetricIdManager::kMinId;
- // next id should be MetricIdManager::kMaxNumPairedDevicesInMemory
- paired_device_map =
- generateAddresses(MetricIdManager::kMaxNumPairedDevicesInMemory);
- ASSERT_TRUE(manager.Init(paired_device_map, callback, callback));
- // try new values not in the map, should get new id.
- ASSERT_EQ(manager.AllocateId(kthAddress(INT_MAX)), id);
- ASSERT_EQ(manager.AllocateId(kthAddress(INT_MAX - 1)), id + 1);
- ASSERT_EQ(manager.AllocateId(kthAddress(INT_MAX)), id);
- ASSERT_EQ(manager.AllocateId(kthAddress(INT_MAX - 2)), id + 2);
- ASSERT_TRUE(manager.Close());
-}
-
-TEST(BluetoothMetricIdManagerTest, MetricIdManagerAllocateExistingTest) {
- auto& manager = MetricIdManager::GetInstance();
- std::unordered_map<bluetooth::hci::Address, int> paired_device_map =
- generateAddresses(MetricIdManager::kMaxNumPairedDevicesInMemory);
-
- MetricIdManager::Callback callback = [](
- const bluetooth::hci::Address&, const int) {
- return true;
- };
- int id = MetricIdManager::kMinId;
- // next id should be MetricIdManager::kMaxNumPairedDevicesInMemory
- ASSERT_TRUE(manager.Init(paired_device_map, callback, callback));
-
- // try values already in the map, should get new id.
- ASSERT_EQ(
- manager.AllocateId(bluetooth::hci::Address({0, 0, 0, 0, 0, 0})), id);
- ASSERT_EQ(
- manager.AllocateId(
- bluetooth::hci::Address({0, 0, 0, 0, 0, 1})), id + 1);
- ASSERT_EQ(
- manager.AllocateId(bluetooth::hci::Address({0, 0, 0, 0, 0, 0})), id);
- ASSERT_EQ(
- manager.AllocateId(
- bluetooth::hci::Address({0, 0, 0, 0, 0, 2})), id + 2);
- ASSERT_TRUE(manager.Close());
-}
-
-TEST(BluetoothMetricIdManagerTest, MetricIdManagerMainTest1) {
- auto& manager = MetricIdManager::GetInstance();
- std::unordered_map<bluetooth::hci::Address, int> paired_device_map;
- int placeholder = 22;
- int* pointer = &placeholder;
- MetricIdManager::Callback save_callback = [pointer](
- const bluetooth::hci::Address&,
- const int) {
- *pointer = *pointer * 2;
- return true;
- };
- MetricIdManager::Callback forget_callback = [pointer](
- const bluetooth::hci::Address&,
- const int) {
- *pointer = *pointer / 2;
- return true;
- };
-
- ASSERT_TRUE(
- manager.Init(paired_device_map, save_callback, forget_callback));
- ASSERT_EQ(manager.AllocateId(bluetooth::hci::Address({0, 0, 0, 0, 0, 0})),
- MetricIdManager::kMinId);
- // save it and make sure the callback is called
- ASSERT_TRUE(
- manager.SaveDevice(bluetooth::hci::Address({0, 0, 0, 0, 0, 0})));
- ASSERT_EQ(placeholder, 44);
-
- // should fail, since id of device is not allocated
- ASSERT_FALSE(
- manager.SaveDevice(bluetooth::hci::Address({0, 0, 0, 0, 0, 1})));
- ASSERT_EQ(placeholder, 44);
-
- // save it and make sure the callback is called
- ASSERT_EQ(manager.AllocateId(bluetooth::hci::Address({0, 0, 0, 0, 0, 2})),
- MetricIdManager::kMinId + 1);
- ASSERT_EQ(manager.AllocateId(bluetooth::hci::Address({0, 0, 0, 0, 0, 3})),
- MetricIdManager::kMinId + 2);
- ASSERT_TRUE(
- manager.SaveDevice(bluetooth::hci::Address({0, 0, 0, 0, 0, 2})));
- ASSERT_EQ(placeholder, 88);
- ASSERT_TRUE(
- manager.SaveDevice(bluetooth::hci::Address({0, 0, 0, 0, 0, 3})));
- ASSERT_EQ(placeholder, 176);
-
- // should be true but callback won't be called, since id had been saved
- ASSERT_TRUE(
- manager.SaveDevice(bluetooth::hci::Address({0, 0, 0, 0, 0, 0})));
- ASSERT_EQ(placeholder, 176);
-
- // forget
- manager.ForgetDevice(bluetooth::hci::Address({0, 0, 0, 0, 0, 1}));
- ASSERT_EQ(placeholder, 176);
- manager.ForgetDevice(bluetooth::hci::Address({0, 0, 0, 0, 0, 2}));
- ASSERT_EQ(placeholder, 88);
-
- ASSERT_TRUE(manager.Close());
-}
-
-TEST(BluetoothMetricIdManagerTest, MetricIdManagerFullPairedMap) {
- auto& manager = MetricIdManager::GetInstance();
- // preset a full map
- std::unordered_map<bluetooth::hci::Address, int> paired_device_map =
- generateAddresses(MetricIdManager::kMaxNumPairedDevicesInMemory);
- int placeholder = 243;
- int* pointer = &placeholder;
- MetricIdManager::Callback save_callback = [pointer](
- const bluetooth::hci::Address&,
- const int) {
- *pointer = *pointer * 2;
- return true;
- };
- MetricIdManager::Callback forget_callback = [pointer](
- const bluetooth::hci::Address&,
- const int) {
- *pointer = *pointer / 3;
- return true;
- };
-
- ASSERT_TRUE(
- manager.Init(paired_device_map, save_callback, forget_callback));
-
- // check if all preset ids are there.
- // comments based on kMaxNumPairedDevicesInMemory = 200. It can change.
- int key = 0;
- for (key = 0;
- key < static_cast<int>(MetricIdManager::kMaxNumPairedDevicesInMemory);
- key++) {
- ASSERT_EQ(manager.AllocateId(kthAddress(key)),
- key + MetricIdManager::kMinId);
- }
- // paired: 0, 1, 2 ... 199,
- // scanned:
-
- int id = static_cast<int>(MetricIdManager::kMaxNumPairedDevicesInMemory +
- MetricIdManager::kMinId);
- // next id should be MetricIdManager::kMaxNumPairedDevicesInMemory +
- // MetricIdManager::kMinId
-
- ASSERT_EQ(manager.AllocateId(kthAddress(key)), id++);
- // paired: 0, 1, 2 ... 199,
- // scanned: 200
-
- // save it and make sure the callback is called
- ASSERT_TRUE(manager.SaveDevice(kthAddress(key)));
- // one key is evicted, another key is saved so *2/3
- ASSERT_EQ(placeholder, 162);
-
- // paired: 1, 2 ... 199, 200,
- // scanned:
-
- ASSERT_EQ(manager.AllocateId(kthAddress(0)), id++);
- // paired: 1, 2 ... 199, 200
- // scanned: 0
-
- // key == 200
- // should fail, since id of device is not allocated
- ASSERT_FALSE(manager.SaveDevice(kthAddress(key + 1)));
- ASSERT_EQ(placeholder, 162);
- // paired: 1, 2 ... 199, 200,
- // scanned: 0
-
- ASSERT_EQ(manager.AllocateId(kthAddress(key + 1)), id++);
- ASSERT_TRUE(manager.SaveDevice(kthAddress(key + 1)));
- // one key is evicted, another key is saved so *2/3,
- ASSERT_EQ(placeholder, 108);
- // paired: 2 ... 199, 200, 201
- // scanned: 0
-
- ASSERT_EQ(manager.AllocateId(kthAddress(1)), id++);
- // paired: 2 ... 199, 200, 201,
- // scanned: 0, 1
-
- // save it and make sure the callback is called
- ASSERT_EQ(manager.AllocateId(kthAddress(key + 2)), id++);
- ASSERT_EQ(manager.AllocateId(kthAddress(key + 3)), id++);
- // paired: 2 ... 199, 200, 201,
- // scanned: 0, 1, 202, 203
-
- placeholder = 9;
- ASSERT_TRUE(manager.SaveDevice(kthAddress(key + 2)));
- // one key is evicted, another key is saved so *2/3,
- ASSERT_EQ(placeholder, 6);
- ASSERT_TRUE(manager.SaveDevice(kthAddress(key + 3)));
- // one key is evicted, another key is saved so *2/3,
- ASSERT_EQ(placeholder, 4);
- // paired: 4 ... 199, 200, 201, 202, 203
- // scanned: 0, 1
-
- // should be true but callback won't be called, since id had been saved
- ASSERT_TRUE(manager.SaveDevice(kthAddress(key + 2)));
- ASSERT_EQ(placeholder, 4);
-
- placeholder = 27;
- // forget
- manager.ForgetDevice(kthAddress(key + 200));
- ASSERT_EQ(placeholder, 27); // should fail, no such a key
- manager.ForgetDevice(kthAddress(key + 2));
- ASSERT_EQ(placeholder, 9);
- // paired: 4 ... 199, 200, 201, 203
- // scanned: 0, 1
-
- // save it and make sure the callback is called
- ASSERT_EQ(manager.AllocateId(kthAddress(key + 2)), id++);
- ASSERT_EQ(manager.AllocateId(kthAddress(key + 4)), id++);
- ASSERT_EQ(manager.AllocateId(kthAddress(key + 5)), id++);
- // paired: 4 ... 199, 200, 201, 203
- // scanned: 0, 1, 202, 204, 205
-
- ASSERT_TRUE(manager.SaveDevice(kthAddress(key + 2)));
- ASSERT_EQ(placeholder, 18); // no key is evicted, a key is saved so *2,
-
- // should be true but callback won't be called, since id had been saved
- ASSERT_TRUE(manager.SaveDevice(kthAddress(key + 3)));
- ASSERT_EQ(placeholder, 18); // no such a key in scanned
- ASSERT_TRUE(manager.SaveDevice(kthAddress(key + 4)));
- // one key is evicted, another key is saved so *2/3
- ASSERT_EQ(placeholder, 12);
- // paired: 5 6 ... 199, 200, 201, 203, 202, 204
- // scanned: 0, 1, 205
-
- // verify paired:
- for (key = 5; key <= 199; key++) {
- placeholder = 3;
- manager.ForgetDevice(kthAddress(key));
- ASSERT_EQ(placeholder, 1);
- }
- for (size_t k = MetricIdManager::kMaxNumPairedDevicesInMemory;
- k <= MetricIdManager::kMaxNumPairedDevicesInMemory + 4; k++) {
- placeholder = 3;
- manager.ForgetDevice(kthAddress(k));
- ASSERT_EQ(placeholder, 1);
- }
-
- // verify scanned
- placeholder = 4;
- ASSERT_TRUE(manager.SaveDevice(kthAddress(0)));
- ASSERT_TRUE(manager.SaveDevice(kthAddress(1)));
- ASSERT_TRUE(manager.SaveDevice(
- kthAddress(MetricIdManager::kMaxNumPairedDevicesInMemory + 5)));
- ASSERT_EQ(placeholder, 32);
-
- ASSERT_TRUE(manager.Close());
-}
-
-TEST(BluetoothMetricIdManagerTest, MetricIdManagerFullScannedMap) {
- auto& manager = MetricIdManager::GetInstance();
- std::unordered_map<bluetooth::hci::Address, int> paired_device_map;
- int placeholder = 22;
- int* pointer = &placeholder;
- MetricIdManager::Callback save_callback = [pointer](
- const bluetooth::hci::Address&,const int) {
- *pointer = *pointer * 2;
- return true;
- };
- MetricIdManager::Callback forget_callback = [pointer](
- const bluetooth::hci::Address&,const int) {
- *pointer = *pointer / 2;
- return true;
- };
-
- ASSERT_TRUE(
- manager.Init(paired_device_map, save_callback, forget_callback));
-
- // allocate kMaxNumUnpairedDevicesInMemory ids
- // comments based on kMaxNumUnpairedDevicesInMemory = 200
- for (int key = 0;
- key <
- static_cast<int>(MetricIdManager::kMaxNumUnpairedDevicesInMemory);
- key++) {
- ASSERT_EQ(manager.AllocateId(kthAddress(key)),
- key + MetricIdManager::kMinId);
- }
- // scanned: 0, 1, 2 ... 199,
- // paired:
-
- int id = MetricIdManager::kMaxNumUnpairedDevicesInMemory +
- MetricIdManager::kMinId;
- bluetooth::hci::Address addr =
- kthAddress(MetricIdManager::kMaxNumUnpairedDevicesInMemory);
- ASSERT_EQ(manager.AllocateId(addr), id);
- // scanned: 1, 2 ... 199, 200
-
- // save it and make sure the callback is called
- ASSERT_TRUE(manager.SaveDevice(addr));
- ASSERT_EQ(manager.AllocateId(addr), id);
- ASSERT_EQ(placeholder, 44);
- // paired: 200,
- // scanned: 1, 2 ... 199,
- id++;
-
- addr = kthAddress(MetricIdManager::kMaxNumUnpairedDevicesInMemory + 1);
- ASSERT_EQ(manager.AllocateId(addr), id++);
- // paired: 200,
- // scanned: 1, 2 ... 199, 201
-
- // try to allocate for device 0, 1, 2, 3, 4....199
- // we should have a new id every time,
- // since the scanned map is full at this point
- for (int key = 0;
- key <
- static_cast<int>(MetricIdManager::kMaxNumUnpairedDevicesInMemory);
- key++) {
- ASSERT_EQ(manager.AllocateId(kthAddress(key)), id++);
- }
- ASSERT_TRUE(manager.Close());
-}
-
-TEST(BluetoothMetricIdManagerTest, MetricIdManagerMultiThreadPressureTest) {
- std::unordered_map<bluetooth::hci::Address, int> paired_device_map;
- auto& manager = MetricIdManager::GetInstance();
- int placeholder = 22;
- int* pointer = &placeholder;
- MetricIdManager::Callback save_callback = [pointer](
- const bluetooth::hci::Address&, const int) {
- *pointer = *pointer + 1;
- return true;
- };
- MetricIdManager::Callback forget_callback = [pointer](
- const bluetooth::hci::Address&, const int) {
- *pointer = *pointer - 1;
- return true;
- };
- ASSERT_TRUE(
- manager.Init(paired_device_map, save_callback, forget_callback));
-
- // make sure no deadlock
- std::vector<std::thread> workers;
- for (int key = 0;
- key <
- static_cast<int>(MetricIdManager::kMaxNumUnpairedDevicesInMemory);
- key++) {
- workers.push_back(std::thread([key]() {
- auto& manager = MetricIdManager::GetInstance();
- bluetooth::hci::Address fake_mac_address = kthAddress(key);
- manager.AllocateId(fake_mac_address);
- ASSERT_TRUE(manager.SaveDevice(fake_mac_address));
- manager.ForgetDevice(fake_mac_address);
- }));
- }
- for (auto& worker : workers) {
- worker.join();
- }
- ASSERT_TRUE(manager.IsEmpty());
- ASSERT_TRUE(manager.Close());
-}
-
-TEST(BluetoothMetricIdManagerTest, MetricIdManagerWrapAroundTest1) {
- std::unordered_map<bluetooth::hci::Address, int> paired_device_map;
- auto& manager = MetricIdManager::GetInstance();
- MetricIdManager::Callback callback = [](
- const bluetooth::hci::Address&, const int) {
- return true;
- };
-
- // make a sparse paired_device_map
- int min_id = MetricIdManager::kMinId;
- paired_device_map[kthAddress(min_id)] = min_id;
- paired_device_map[kthAddress(min_id + 1)] = min_id + 1;
- paired_device_map[kthAddress(min_id + 3)] = min_id + 3;
- paired_device_map[kthAddress(min_id + 4)] = min_id + 4;
-
- int max_id = MetricIdManager::kMaxId;
- paired_device_map[kthAddress(max_id - 3)] = max_id - 3;
- paired_device_map[kthAddress(max_id - 4)] = max_id - 4;
-
- ASSERT_TRUE(manager.Init(paired_device_map, callback, callback));
-
- // next id should be max_id - 2, max_id - 1, max_id, min_id + 2, min_id + 5
- ASSERT_EQ(manager.AllocateId(kthAddress(max_id - 2)), max_id - 2);
- ASSERT_EQ(manager.AllocateId(kthAddress(max_id - 1)), max_id - 1);
- ASSERT_EQ(manager.AllocateId(kthAddress(max_id)), max_id);
- ASSERT_EQ(manager.AllocateId(kthAddress(min_id + 2)), min_id + 2);
- ASSERT_EQ(manager.AllocateId(kthAddress(min_id + 5)), min_id + 5);
-
- ASSERT_TRUE(manager.Close());
-}
-
-TEST(BluetoothMetricIdManagerTest, MetricIdManagerWrapAroundTest2) {
- std::unordered_map<bluetooth::hci::Address, int> paired_device_map;
- auto& manager = MetricIdManager::GetInstance();
- MetricIdManager::Callback callback = [](
- const bluetooth::hci::Address&, const int) {
- return true;
- };
-
- // make a sparse paired_device_map
- int min_id = MetricIdManager::kMinId;
- int max_id = MetricIdManager::kMaxId;
- paired_device_map[kthAddress(max_id)] = max_id;
-
- ASSERT_TRUE(manager.Init(paired_device_map, callback, callback));
-
- // next id should be min_id, min_id + 1
- ASSERT_EQ(manager.AllocateId(kthAddress(min_id)), min_id);
- ASSERT_EQ(manager.AllocateId(kthAddress(min_id + 1)), min_id + 1);
-
- ASSERT_TRUE(manager.Close());
-}
-
-} // namespace testing
diff --git a/gd/common/multi_priority_queue.h b/gd/common/multi_priority_queue.h
deleted file mode 100644
index 0546cd9c7..000000000
--- a/gd/common/multi_priority_queue.h
+++ /dev/null
@@ -1,75 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#pragma once
-
-#include <array>
-#include <queue>
-
-namespace bluetooth {
-namespace common {
-
-/**
- * A queue implementation which supports items with multiple priorities.
- * Items with greater priority value will be dequeued first.
- * When Enqueuing, the user can specify the priority (0 by default).
- * This can be used by ACL or L2CAP lower queue end sender to prioritize some link or channel, used by A2DP.
- */
-template <typename T, int NUM_PRIORITY_LEVELS = 2>
-class MultiPriorityQueue {
- static_assert(NUM_PRIORITY_LEVELS > 1);
-
- public:
- // Get the front item with the highest priority. Queue must be non-empty.
- T& front() {
- return queues_[next_to_dequeue_.top()].front();
- }
-
- [[nodiscard]] bool empty() const {
- return next_to_dequeue_.empty();
- }
-
- [[nodiscard]] size_t size() const {
- return next_to_dequeue_.size();
- }
-
- // Push the item with specified priority
- void push(const T& t, int priority = 0) {
- queues_[priority].push(t);
- next_to_dequeue_.push(priority);
- }
-
- // Push the item with specified priority
- void push(T&& t, int priority = 0) {
- queues_[priority].push(std::forward<T>(t));
- next_to_dequeue_.push(priority);
- }
-
- // Pop the item in the front
- void pop() {
- queues_[next_to_dequeue_.top()].pop();
- next_to_dequeue_.pop();
- }
-
- private:
- std::array<std::queue<T>, NUM_PRIORITY_LEVELS> queues_;
- std::priority_queue<int> next_to_dequeue_;
-};
-
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/common/numbers.h b/gd/common/numbers.h
deleted file mode 100644
index a2e9621e4..000000000
--- a/gd/common/numbers.h
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <limits>
-#include <type_traits>
-
-namespace bluetooth {
-namespace common {
-
-// Check if input is within numeric limits of RawType
-template <typename RawType, typename InputType>
-bool IsNumberInNumericLimits(InputType input) {
- // Only arithmetic types are supported
- static_assert(std::is_arithmetic_v<RawType> && std::is_arithmetic_v<InputType>);
- // Either both are signed or both are unsigned
- static_assert(
- (std::is_signed_v<RawType> && std::is_signed_v<InputType>) ||
- (std::is_unsigned_v<RawType> && std::is_unsigned_v<InputType>));
- if (std::numeric_limits<InputType>::max() > std::numeric_limits<RawType>::max()) {
- if (input > std::numeric_limits<RawType>::max()) {
- return false;
- }
- }
- if (std::numeric_limits<InputType>::lowest() < std::numeric_limits<RawType>::lowest()) {
- if (input < std::numeric_limits<RawType>::lowest()) {
- return false;
- }
- }
- return true;
-}
-
-} // namespace common
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/common/numbers_test.cc b/gd/common/numbers_test.cc
deleted file mode 100644
index ac4c3d708..000000000
--- a/gd/common/numbers_test.cc
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "common/numbers.h"
-
-#include <cstdint>
-
-#include <gtest/gtest.h>
-
-namespace testing {
-
-using bluetooth::common::IsNumberInNumericLimits;
-
-TEST(NumbersTest, test_is_number_in_numeric_limits) {
- // INT32_MAX+1
- int64_t n = 2147483648L;
- ASSERT_FALSE(IsNumberInNumericLimits<int32_t>(n));
- ASSERT_TRUE(IsNumberInNumericLimits<int64_t>(n));
- ASSERT_FALSE(IsNumberInNumericLimits<int8_t>(int32_t(128)));
- ASSERT_FALSE(IsNumberInNumericLimits<uint8_t>(uint32_t(256)));
- ASSERT_FALSE(IsNumberInNumericLimits<int8_t>(int32_t(-129)));
-}
-
-} // namespace testing \ No newline at end of file
diff --git a/gd/common/stop_watch.cc b/gd/common/stop_watch.cc
deleted file mode 100644
index 5c556c62d..000000000
--- a/gd/common/stop_watch.cc
+++ /dev/null
@@ -1,106 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "BtStopWatch"
-
-#include "common/stop_watch.h"
-
-#include <iomanip>
-#include <mutex>
-#include <sstream>
-#include <utility>
-
-#include "common/init_flags.h"
-#include "os/log.h"
-
-namespace bluetooth {
-namespace common {
-
-static const int LOG_BUFFER_LENGTH = 10;
-static std::array<StopWatchLog, LOG_BUFFER_LENGTH> stopwatch_logs;
-static int current_buffer_index;
-static std::recursive_mutex stopwatch_log_mutex;
-
-void StopWatch::RecordLog(StopWatchLog log) {
- std::unique_lock<std::recursive_mutex> lock(stopwatch_log_mutex, std::defer_lock);
- if (!lock.try_lock()) {
- LOG_INFO("try_lock fail. log content: %s, took %zu us", log.message.c_str(),
- static_cast<size_t>(
- std::chrono::duration_cast<std::chrono::microseconds>(
- stopwatch_logs[current_buffer_index].end_timestamp -
- stopwatch_logs[current_buffer_index].start_timestamp)
- .count()));
- return;
- }
- if (current_buffer_index >= LOG_BUFFER_LENGTH) {
- current_buffer_index = 0;
- }
- stopwatch_logs[current_buffer_index] = std::move(log);
- current_buffer_index++;
- lock.unlock();
-}
-
-void StopWatch::DumpStopWatchLog() {
- std::lock_guard<std::recursive_mutex> lock(stopwatch_log_mutex);
- LOG_INFO("=====================================");
- LOG_INFO("bluetooth stopwatch log history:");
- for (int i = 0; i < LOG_BUFFER_LENGTH; i++) {
- if (current_buffer_index >= LOG_BUFFER_LENGTH) {
- current_buffer_index = 0;
- }
- if (stopwatch_logs[current_buffer_index].message.empty()) {
- current_buffer_index++;
- continue;
- }
- std::stringstream ss;
- auto now = stopwatch_logs[current_buffer_index].timestamp;
- auto millis = std::chrono::duration_cast<std::chrono::milliseconds>(
- now.time_since_epoch()) %
- 1000;
- auto now_time_t = std::chrono::system_clock::to_time_t(now);
- ss << std::put_time(std::localtime(&now_time_t), "%Y-%m-%d %H:%M:%S");
- ss << '.' << std::setfill('0') << std::setw(3) << millis.count();
- std::string start_timestamp = ss.str();
- LOG_INFO(
- "%s: %s: took %zu us",
- start_timestamp.c_str(),
- stopwatch_logs[current_buffer_index].message.c_str(),
- static_cast<size_t>(std::chrono::duration_cast<std::chrono::microseconds>(
- stopwatch_logs[current_buffer_index].end_timestamp -
- stopwatch_logs[current_buffer_index].start_timestamp)
- .count()));
- current_buffer_index++;
- }
- LOG_INFO("=====================================");
-}
-
-StopWatch::StopWatch(std::string text)
- : text_(std::move(text)),
- timestamp_(std::chrono::system_clock::now()),
- start_timestamp_(std::chrono::high_resolution_clock::now()) {}
-
-StopWatch::~StopWatch() {
- StopWatchLog sw_log;
- sw_log.timestamp = timestamp_;
- sw_log.start_timestamp = start_timestamp_;
- sw_log.end_timestamp = std::chrono::high_resolution_clock::now();
- sw_log.message = std::move(text_);
-
- RecordLog(std::move(sw_log));
-}
-
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/common/stop_watch.h b/gd/common/stop_watch.h
deleted file mode 100644
index 4d7d54474..000000000
--- a/gd/common/stop_watch.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <chrono>
-#include <string>
-
-namespace bluetooth {
-namespace common {
-
-typedef struct {
- std::chrono::system_clock::time_point timestamp;
- std::chrono::high_resolution_clock::time_point start_timestamp;
- std::chrono::high_resolution_clock::time_point end_timestamp;
- std::string message;
-} StopWatchLog;
-
-class StopWatch {
- public:
- static void DumpStopWatchLog(void);
- StopWatch(std::string text);
- ~StopWatch();
-
- private:
- std::string text_;
- std::chrono::system_clock::time_point timestamp_;
- std::chrono::high_resolution_clock::time_point start_timestamp_;
- void RecordLog(StopWatchLog log);
-};
-
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/common/strings.cc b/gd/common/strings.cc
deleted file mode 100644
index 13c5c059c..000000000
--- a/gd/common/strings.cc
+++ /dev/null
@@ -1,178 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "common/strings.h"
-
-#include <charconv>
-#include <cstdlib>
-#include <functional>
-#include <iomanip>
-#include <iterator>
-#include <sstream>
-#include <system_error>
-
-namespace {
-
-struct IsSpace : std::unary_function<std::string::value_type, bool> {
- bool operator()(std::string::value_type v) {
- return isspace(static_cast<int>(v));
- }
-};
-
-struct IsHexDigit : std::unary_function<std::string::value_type, bool> {
- bool operator()(std::string::value_type v) {
- return isxdigit(static_cast<int>(v));
- }
-};
-
-} // namespace
-
-namespace bluetooth {
-namespace common {
-
-std::string ToHexString(const std::vector<uint8_t>& value) {
- return ToHexString(value.begin(), value.end());
-}
-
-bool IsValidHexString(const std::string& str) {
- return std::find_if_not(str.begin(), str.end(), IsHexDigit{}) == str.end();
-}
-
-std::optional<std::vector<uint8_t>> FromHexString(const std::string& str) {
- if (str.size() % 2 != 0) {
- LOG_INFO("str size is not divisible by 2, size is %zu", str.size());
- return std::nullopt;
- }
- if (std::find_if_not(str.begin(), str.end(), IsHexDigit{}) != str.end()) {
- LOG_INFO("value contains none hex digit");
- return std::nullopt;
- }
- std::vector<uint8_t> value;
- value.reserve(str.size() / 2);
- for (size_t i = 0; i < str.size(); i += 2) {
- uint8_t v = 0;
- auto ret = std::from_chars(str.c_str() + i, str.c_str() + i + 2, v, 16);
- if (std::make_error_code(ret.ec)) {
- LOG_INFO("failed to parse hex char at index %zu", i);
- return std::nullopt;
- }
- value.push_back(v);
- }
- return value;
-}
-
-std::string StringTrim(std::string str) {
- str.erase(str.begin(), std::find_if_not(str.begin(), str.end(), IsSpace{}));
- str.erase(std::find_if_not(str.rbegin(), str.rend(), IsSpace{}).base(), str.end());
- return str;
-}
-
-std::vector<std::string> StringSplit(const std::string& str, const std::string& delim, size_t max_token) {
- ASSERT_LOG(!delim.empty(), "delim cannot be empty");
- std::vector<std::string> tokens;
- // Use std::string::find and std::string::substr to avoid copying str into a stringstream
- std::string::size_type starting_index = 0;
- auto index_of_delim = str.find(delim);
- while ((max_token == 0 || tokens.size() < (max_token - 1)) && index_of_delim != std::string::npos) {
- tokens.push_back(str.substr(starting_index, index_of_delim - starting_index));
- starting_index = index_of_delim + delim.size();
- index_of_delim = str.find(delim, starting_index);
- }
- // Append last item to the vector if there are anything left
- if (starting_index < (str.size() + 1)) {
- tokens.push_back(str.substr(starting_index));
- }
- return tokens;
-}
-
-std::string StringJoin(const std::vector<std::string>& strings, const std::string& delim) {
- std::stringstream ss;
- for (auto it = strings.begin(); it != strings.end(); it++) {
- ss << *it;
- if (std::next(it) != strings.end()) {
- ss << delim;
- }
- }
- return ss.str();
-}
-
-std::optional<int64_t> Int64FromString(const std::string& str) {
- char* ptr = nullptr;
- errno = 0;
- int64_t value = std::strtoll(str.c_str(), &ptr, 10);
- if (errno != 0) {
- LOG_INFO("cannot parse string '%s' with error '%s'", str.c_str(), strerror(errno));
- return std::nullopt;
- }
- if (ptr == str.c_str()) {
- LOG_INFO("string '%s' is empty or has wrong format", str.c_str());
- return std::nullopt;
- }
- if (ptr != (str.c_str() + str.size())) {
- LOG_INFO("cannot parse whole string '%s'", str.c_str());
- return std::nullopt;
- }
- return value;
-}
-
-std::string ToString(int64_t value) {
- return std::to_string(value);
-}
-
-std::optional<uint64_t> Uint64FromString(const std::string& str) {
- if (str.find('-') != std::string::npos) {
- LOG_INFO("string '%s' contains minus sign, this function is for unsigned", str.c_str());
- return std::nullopt;
- }
- char* ptr = nullptr;
- errno = 0;
- uint64_t value = std::strtoull(str.c_str(), &ptr, 10);
- if (errno != 0) {
- LOG_INFO("cannot parse string '%s' with error '%s'", str.c_str(), strerror(errno));
- return std::nullopt;
- }
- if (ptr == str.c_str()) {
- LOG_INFO("string '%s' is empty or has wrong format", str.c_str());
- return std::nullopt;
- }
- if (ptr != (str.c_str() + str.size())) {
- LOG_INFO("cannot parse whole string '%s'", str.c_str());
- return std::nullopt;
- }
- return value;
-}
-
-std::string ToString(uint64_t value) {
- return std::to_string(value);
-}
-
-std::optional<bool> BoolFromString(const std::string& str) {
- if (str == "true") {
- return true;
- } else if (str == "false") {
- return false;
- } else {
- LOG_INFO("string '%s' is neither true nor false", str.c_str());
- return std::nullopt;
- }
-}
-
-std::string ToString(bool value) {
- return value ? "true" : "false";
-}
-
-} // namespace common
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/common/strings.h b/gd/common/strings.h
deleted file mode 100644
index c80d01eff..000000000
--- a/gd/common/strings.h
+++ /dev/null
@@ -1,138 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <limits.h>
-#include <string.h>
-#include <charconv>
-#include <iomanip>
-#include <iterator>
-#include <limits>
-#include <optional>
-#include <sstream>
-#include <string>
-#include <type_traits>
-#include <vector>
-
-#include "common/type_helper.h"
-#include "os/log.h"
-
-namespace bluetooth {
-namespace common {
-
-// Convert number into a hex string prefixed with 0x
-template <typename T>
-std::string ToHexString(T x) {
- if (x < 0) {
- if (x == INT_MIN) return "INT_MIN";
- return "-" + ToHexString(-x);
- }
- std::stringstream tmp;
- tmp << "0x" << std::internal << std::hex << std::setfill('0') << std::setw(sizeof(T) * 2) << (unsigned long)x;
- return tmp.str();
-}
-
-template <>
-inline std::string ToHexString<signed long>(signed long x) {
- if (x < 0) {
- if (x == LONG_MIN) return "LONG_MIN";
- return "-" + ToHexString<signed long>(-x);
- }
- std::stringstream tmp;
- tmp << "0x" << std::internal << std::hex << std::setfill('0') << std::setw(sizeof(signed long) * 2)
- << (unsigned long)x;
- return tmp.str();
-}
-
-// Convert value into a hex decimal formatted string in lower case, prefixed with 0s
-template <class InputIt>
-std::string ToHexString(InputIt first, InputIt last) {
- static_assert(
- std::is_same_v<typename std::iterator_traits<InputIt>::value_type, uint8_t>, "Must use uint8_t iterator");
- std::stringstream ss;
- for (InputIt it = first; it != last; ++it) {
- // +(byte) to prevent an uint8_t to be interpreted as a char
- ss << std::hex << std::setw(2) << std::setfill('0') << +(*it);
- }
- return ss.str();
-}
-// Convenience method for normal cases and initializer list, e.g. ToHexString({0x12, 0x34, 0x56, 0xab})
-std::string ToHexString(const std::vector<uint8_t>& value);
-
-// Return true if |str| is a valid hex demical strings contains only hex decimal chars [0-9a-fA-F]
-bool IsValidHexString(const std::string& str);
-
-// Parse |str| into a vector of uint8_t, |str| must contains only hex decimal
-std::optional<std::vector<uint8_t>> FromHexString(const std::string& str);
-
-// Remove whitespace from both ends of the |str|, returning a copy
-std::string StringTrim(std::string str);
-
-// Split |str| into at most |max_token| tokens delimited by |delim|, unlimited tokens when |max_token| is 0
-std::vector<std::string> StringSplit(const std::string& str, const std::string& delim, size_t max_token = 0);
-
-// Join |strings| into a single string using |delim|
-std::string StringJoin(const std::vector<std::string>& strings, const std::string& delim);
-
-// Various number comparison functions, only base 10 is supported
-std::optional<int64_t> Int64FromString(const std::string& str);
-std::string ToString(int64_t value);
-std::optional<uint64_t> Uint64FromString(const std::string& str);
-std::string ToString(uint64_t value);
-std::optional<bool> BoolFromString(const std::string& str);
-std::string ToString(bool value);
-
-// printf like formatting to std::string
-// format must contains format information, to print a string use StringFormat("%s", str)
-template <typename... Args>
-std::string StringFormat(const std::string& format, Args... args) {
- auto size = std::snprintf(nullptr, 0, format.c_str(), args...);
- ASSERT_LOG(size >= 0, "return value %d, error %d, text '%s'", size, errno, strerror(errno));
- // Add 1 for terminating null byte
- char buffer[size + 1];
- auto actual_size = std::snprintf(buffer, sizeof(buffer), format.c_str(), args...);
- ASSERT_LOG(
- size == actual_size,
- "asked size %d, actual size %d, error %d, text '%s'",
- size,
- actual_size,
- errno,
- strerror(errno));
- // Exclude the terminating null byte
- return std::string(buffer, size);
-}
-
-inline std::string StringFormatTime(const std::string& format, const struct std::tm& tm) {
- std::ostringstream os;
- os << std::put_time(&tm, format.c_str());
- return os.str();
-}
-
-inline std::string StringFormatTimeWithMilliseconds(
- const std::string& format,
- std::chrono::time_point<std::chrono::system_clock> time_point,
- struct tm* (*calendar_to_tm)(const time_t* timep) = localtime) {
- std::time_t epoch_time = std::chrono::system_clock::to_time_t(time_point);
- auto millis = time_point.time_since_epoch() / std::chrono::milliseconds(1) % 1000;
- std::tm tm = *calendar_to_tm(&epoch_time);
- std::ostringstream os;
- os << std::put_time(&tm, format.c_str()) << StringFormat(".%03u", millis);
- return os.str();
-}
-
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/common/strings_test.cc b/gd/common/strings_test.cc
deleted file mode 100644
index 8a9ff1a87..000000000
--- a/gd/common/strings_test.cc
+++ /dev/null
@@ -1,249 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "common/strings.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include <array>
-#include <memory>
-
-namespace testing {
-
-using bluetooth::common::BoolFromString;
-using bluetooth::common::FromHexString;
-using bluetooth::common::Int64FromString;
-using bluetooth::common::StringFormat;
-using bluetooth::common::StringFormatTime;
-using bluetooth::common::StringFormatTimeWithMilliseconds;
-using bluetooth::common::StringJoin;
-using bluetooth::common::StringSplit;
-using bluetooth::common::StringTrim;
-using bluetooth::common::ToHexString;
-using bluetooth::common::ToString;
-using bluetooth::common::Uint64FromString;
-
-static inline bool is_arch32() {
- return sizeof(long) == 4;
-}
-static inline bool is_arch64() {
- return sizeof(long) == 8;
-}
-
-TEST(StringsTest, to_hex_string_from_number) {
- ASSERT_EQ(ToHexString(0), "0x00000000");
- ASSERT_EQ(ToHexString(3), "0x00000003");
- ASSERT_EQ(ToHexString(25), "0x00000019");
- ASSERT_EQ(ToHexString(-25), "-0x00000019");
- ASSERT_EQ(ToHexString(INT_MIN + 1), "-0x7fffffff");
- ASSERT_EQ(ToHexString(INT_MAX), "0x7fffffff");
- ASSERT_EQ(ToHexString(INT_MIN), "INT_MIN");
- if (is_arch32()) {
- ASSERT_EQ(ToHexString(1 + INT_MAX), "INT_MIN");
- ASSERT_EQ(ToHexString(2 + INT_MAX), "-0x7fffffff"); // Rolled over
- ASSERT_EQ(ToHexString(-1 - INT_MIN), "0x7fffffff"); // Rolled over
- ASSERT_EQ(ToHexString(LONG_MAX), "0x7fffffff");
- ASSERT_EQ(ToHexString(LONG_MAX - 1L), "0x7ffffffe");
- ASSERT_EQ(ToHexString(LONG_MIN), "LONG_MIN");
- ASSERT_EQ(ToHexString(LONG_MIN + 1L), "-0x7fffffff");
- } else if (is_arch64()) {
- ASSERT_EQ(ToHexString((signed long)INT_MIN), "-0x0000000080000000");
- ASSERT_EQ(ToHexString(1 + INT_MAX), "INT_MIN"); // Rolled over
- ASSERT_EQ(ToHexString(2 + INT_MAX), "-0x7fffffff"); // Rolled over
- ASSERT_EQ(ToHexString(1L + INT_MAX), "0x0000000080000000");
- ASSERT_EQ(ToHexString(2L + INT_MAX), "0x0000000080000001");
- ASSERT_EQ(ToHexString(-1L + INT_MIN), "-0x0000000080000001");
- ASSERT_EQ(ToHexString(LONG_MAX), "0x7fffffffffffffff");
- ASSERT_EQ(ToHexString(LONG_MAX - 1L), "0x7ffffffffffffffe");
- ASSERT_EQ(ToHexString(LONG_MIN), "LONG_MIN");
- ASSERT_EQ(ToHexString(LONG_MIN + 1L), "-0x7fffffffffffffff");
- } else {
- LOG_ERROR("Unknown architecture");
- ASSERT_TRUE(false);
- }
- ASSERT_EQ(ToHexString('a'), "0x61");
-}
-
-TEST(StringsTest, trim_string_test) {
- ASSERT_EQ(StringTrim(" aa bb"), "aa bb");
- ASSERT_EQ(StringTrim("aa bb "), "aa bb");
- ASSERT_EQ(StringTrim(" aa bb "), "aa bb");
- ASSERT_EQ(StringTrim(" aa bb \n"), "aa bb");
- ASSERT_EQ(StringTrim(" \raa bb\t \n"), "aa bb");
-}
-
-TEST(StringsTest, split_string_test) {
- ASSERT_THAT(StringSplit("", ","), ElementsAre(""));
- ASSERT_THAT(StringSplit("1,2,3", ","), ElementsAre("1", "2", "3"));
- ASSERT_THAT(StringSplit("1,2,3", "!"), ElementsAre("1,2,3"));
- ASSERT_THAT(StringSplit("1,2,3", ",", 2), ElementsAre("1", "2,3"));
- ASSERT_THAT(StringSplit("a,b,", ","), ElementsAre("a", "b", ""));
- ASSERT_THAT(StringSplit("ab,", ",", 2), ElementsAre("ab", ""));
- ASSERT_THAT(StringSplit("ab,,", ",", 2), ElementsAre("ab", ","));
- ASSERT_THAT(StringSplit("ab,,", ",", 1), ElementsAre("ab,,"));
- ASSERT_THAT(StringSplit("1,,2,,3", ",,"), ElementsAre("1", "2", "3"));
- ASSERT_THAT(StringSplit("1,,2,,3,,", ",,"), ElementsAre("1", "2", "3", ""));
- ASSERT_THAT(StringSplit("1,,2,,3,,", ",,", 2), ElementsAre("1", "2,,3,,"));
- ASSERT_THAT(StringSplit("1", ",,", 2), ElementsAre("1"));
- ASSERT_DEATH({ StringSplit("1,2,3", ""); }, "delim cannot be empty");
-}
-
-TEST(StringsTest, join_string_test) {
- ASSERT_THAT(StringJoin({{"1", "2", "3"}}, ","), StrEq("1,2,3"));
- ASSERT_THAT(StringJoin({{}}, ","), StrEq(""));
- ASSERT_THAT(StringJoin({{"1"}}, ","), StrEq("1"));
- ASSERT_THAT(StringJoin({{"1", "2", "3"}}, ",,"), StrEq("1,,2,,3"));
- ASSERT_THAT(StringJoin({{"1", ",", "3"}}, ",,"), StrEq("1,,,,,3"));
-}
-
-TEST(StringsTest, to_hex_string_test) {
- // normal
- ASSERT_THAT(ToHexString({0x12, 0x34, 0x56, 0xab}), Eq("123456ab"));
- // empty
- ASSERT_THAT(ToHexString({}), Eq(""));
- // unary
- ASSERT_THAT(ToHexString({0x12}), Eq("12"));
- // half
- ASSERT_THAT(ToHexString({0x6, 0x5, 0x56, 0xb}), Eq("0605560b"));
- // other types
- std::array<uint8_t, 2> a = {0x12, 0x56};
- ASSERT_THAT(ToHexString(a.begin(), a.end()), Eq("1256"));
- std::vector<uint8_t> b = {0x34, 0x78};
- ASSERT_THAT(ToHexString(b.begin(), b.end()), Eq("3478"));
-}
-
-TEST(StringsTest, from_hex_string_test) {
- // normal
- ASSERT_THAT(FromHexString("aabbccdd1122"), Optional(ElementsAre(0xaa, 0xbb, 0xcc, 0xdd, 0x11, 0x22)));
- // empty
- ASSERT_THAT(FromHexString(""), Optional(IsEmpty()));
- // unary
- ASSERT_THAT(FromHexString("aa"), Optional(ElementsAre(0xaa)));
- // half
- ASSERT_THAT(FromHexString("0605560b"), Optional(ElementsAre(0x6, 0x5, 0x56, 0xb)));
- // upper case letter
- ASSERT_THAT(FromHexString("AABBCC"), Optional(ElementsAre(0xaa, 0xbb, 0xcc)));
- // upper and lower case letter mixed
- ASSERT_THAT(FromHexString("aAbbCC"), Optional(ElementsAre(0xaa, 0xbb, 0xcc)));
- // Error: odd length
- ASSERT_FALSE(FromHexString("0605560"));
- // Error: non hex char
- ASSERT_FALSE(FromHexString("060u560b"));
-}
-
-TEST(StringsTest, int64_from_and_to_string_test) {
- ASSERT_THAT(Int64FromString("42"), Optional(Eq(int64_t(42))));
- ASSERT_THAT(Int64FromString("-42"), Optional(Eq(int64_t(-42))));
- ASSERT_THAT(Int64FromString("0"), Optional(Eq(int64_t(0))));
- ASSERT_FALSE(Int64FromString(""));
- // only base 10 is supported
- ASSERT_FALSE(Int64FromString("0x42ab"));
- ASSERT_FALSE(Int64FromString("-0x42"));
- // floating point not supported
- ASSERT_FALSE(Int64FromString("42.0"));
- ASSERT_FALSE(Int64FromString("-42.0"));
- ASSERT_FALSE(Int64FromString("42abc"));
- ASSERT_FALSE(Int64FromString(""));
- // INT32_MAX + 1
- ASSERT_THAT(Int64FromString("2147483648"), Optional(Eq(int64_t(2147483648))));
- ASSERT_THAT(ToString(int64_t(2147483648)), StrEq("2147483648"));
- // INT32_MIN - 1
- ASSERT_THAT(Int64FromString("-2147483649"), Optional(Eq(int64_t(-2147483649))));
- ASSERT_THAT(ToString(int64_t(-2147483649)), StrEq("-2147483649"));
- // INT64_MAX
- ASSERT_THAT(Int64FromString("9223372036854775807"), Optional(Eq(int64_t(9223372036854775807))));
- ASSERT_THAT(ToString(int64_t(9223372036854775807)), StrEq("9223372036854775807"));
- // INT64_MAX+1
- ASSERT_FALSE(Int64FromString("9223372036854775808"));
- // INT64_MIN
- ASSERT_THAT(Int64FromString("-9223372036854775808"), Optional(Eq(int64_t(-9223372036854775807LL - 1))));
- ASSERT_THAT(ToString(int64_t(-9223372036854775807LL - 1)), StrEq("-9223372036854775808"));
- // INT64_MIN-1
- ASSERT_FALSE(Int64FromString("-9223372036854775809"));
-}
-
-TEST(StringsTest, uint64_from_and_to_string_test) {
- ASSERT_THAT(Uint64FromString("42"), Optional(Eq(uint64_t(42))));
- ASSERT_THAT(Uint64FromString("0"), Optional(Eq(uint64_t(0))));
- ASSERT_FALSE(Uint64FromString(""));
- // only base 10 is supported
- ASSERT_FALSE(Uint64FromString("0x42ab"));
- // only positive number is supported
- ASSERT_FALSE(Uint64FromString("-42"));
- // floating point not supported
- ASSERT_FALSE(Uint64FromString("42.0"));
- ASSERT_FALSE(Uint64FromString("-42.0"));
- ASSERT_FALSE(Uint64FromString("42abc"));
- ASSERT_FALSE(Uint64FromString(""));
- // UINT32_MAX + 1
- ASSERT_THAT(Uint64FromString("4294967295"), Optional(Eq(uint64_t(4294967295))));
- ASSERT_THAT(ToString(uint64_t(4294967295)), StrEq("4294967295"));
- // UINT64_MAX
- ASSERT_THAT(Uint64FromString("18446744073709551615"), Optional(Eq(uint64_t(18446744073709551615ULL))));
- ASSERT_THAT(ToString(uint64_t(18446744073709551615ULL)), StrEq("18446744073709551615"));
- // UINT64_MAX+1
- ASSERT_FALSE(Uint64FromString("18446744073709551616"));
-}
-
-TEST(StringsTest, bool_from_and_to_string_test) {
- ASSERT_THAT(BoolFromString("true"), Optional(IsTrue()));
- ASSERT_THAT(BoolFromString("false"), Optional(IsFalse()));
- ASSERT_FALSE(BoolFromString("abc"));
- ASSERT_FALSE(BoolFromString("FALSE"));
- ASSERT_FALSE(BoolFromString("TRUE"));
- ASSERT_FALSE(BoolFromString(""));
- ASSERT_THAT(ToString(true), StrEq("true"));
- ASSERT_THAT(ToString(false), StrEq("false"));
-}
-
-TEST(StringsTest, string_format_test) {
- ASSERT_THAT(StringFormat("%s", "hello"), StrEq("hello"));
- ASSERT_THAT(StringFormat("%d", 42), StrEq("42"));
- ASSERT_THAT(StringFormat("%s world", "hello"), StrEq("hello world"));
- ASSERT_THAT(StringFormat("%d %.1f 0x%02x", 42, 43.123, 0x8), StrEq("42 43.1 0x08"));
-}
-
-TEST(StringsTest, string_format_time_test) {
- std::string format("%Y-%m-%d %H:%M:%S");
- time_t then = 123456789;
- struct std::tm tm;
- gmtime_r(&then, &tm);
- ASSERT_THAT(StringFormatTime(format, tm), StrEq("1973-11-29 21:33:09"));
-}
-
-TEST(StringsTest, string_format_time_with_ms_in_the_beginning_test) {
- std::string format("%Y-%m-%d %H:%M:%S");
- std::time_t from_time = 0;
- std::chrono::time_point<std::chrono::system_clock> time_point = std::chrono::system_clock::from_time_t(from_time);
-
- ASSERT_THAT(StringFormatTimeWithMilliseconds(format, time_point, gmtime), StrEq("1970-01-01 00:00:00.000"));
-}
-
-TEST(StringsTest, string_format_time_with_ms_test) {
- std::string format("%Y-%m-%d %H:%M:%S");
- std::time_t from_time1 = 1234567890;
- std::chrono::time_point<std::chrono::system_clock> time_point1 = std::chrono::system_clock::from_time_t(from_time1);
- std::time_t from_time2 = 1234567890;
- std::chrono::time_point<std::chrono::system_clock> time_point2 = std::chrono::system_clock::from_time_t(from_time2);
-
- time_point2 += std::chrono::milliseconds(1);
-
- ASSERT_THAT(StringFormatTimeWithMilliseconds(format, time_point1, gmtime), StrEq("2009-02-13 23:31:30.000"));
- ASSERT_THAT(StringFormatTimeWithMilliseconds(format, time_point2, gmtime), StrEq("2009-02-13 23:31:30.001"));
-}
-
-} // namespace testing
diff --git a/gd/common/type_helper.h b/gd/common/type_helper.h
deleted file mode 100644
index 74991fbad..000000000
--- a/gd/common/type_helper.h
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <type_traits>
-
-namespace bluetooth {
-namespace common {
-
-// Check whether T is a specialization of TemplateType
-template <typename T, template <typename...> class TemplateType>
-struct is_specialization_of : std::false_type {};
-template <template <typename...> class TemplateType, typename... Args>
-struct is_specialization_of<TemplateType<Args...>, TemplateType> : std::true_type {};
-
-} // namespace common
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/crypto_toolbox/Android.bp b/gd/crypto_toolbox/Android.bp
index c89a0a9bc..fd2e6edae 100644
--- a/gd/crypto_toolbox/Android.bp
+++ b/gd/crypto_toolbox/Android.bp
@@ -1,13 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- // SPDX-license-identifier-BSD
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothCryptoToolboxSources",
srcs: [
@@ -22,4 +12,4 @@ filegroup {
srcs: [
"crypto_toolbox_test.cc",
]
-}
+} \ No newline at end of file
diff --git a/gd/crypto_toolbox/BUILD.gn b/gd/crypto_toolbox/BUILD.gn
deleted file mode 100644
index 4bca591f5..000000000
--- a/gd/crypto_toolbox/BUILD.gn
+++ /dev/null
@@ -1,24 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-source_set("BluetoothCryptoToolboxSources") {
- sources = [
- "aes.cc",
- "aes_cmac.cc",
- "crypto_toolbox.cc",
- ]
-
- configs += [ "//bt/gd:gd_defaults" ]
-}
diff --git a/gd/crypto_toolbox/aes.cc b/gd/crypto_toolbox/aes.cc
index 395642cd3..f53894e4a 100644
--- a/gd/crypto_toolbox/aes.cc
+++ b/gd/crypto_toolbox/aes.cc
@@ -77,8 +77,11 @@ typedef uint32_t uint_32t;
#define f1(x) (x)
#define f2(x) (((x) << 1) ^ ((((x) >> 7) & 1) * WPOLY))
-#define f4(x) (((x) << 2) ^ ((((x) >> 6) & 1) * WPOLY) ^ ((((x) >> 6) & 2) * WPOLY))
-#define f8(x) (((x) << 3) ^ ((((x) >> 5) & 1) * WPOLY) ^ ((((x) >> 5) & 2) * WPOLY) ^ ((((x) >> 5) & 4) * WPOLY))
+#define f4(x) \
+ (((x) << 2) ^ ((((x) >> 6) & 1) * WPOLY) ^ ((((x) >> 6) & 2) * WPOLY))
+#define f8(x) \
+ (((x) << 3) ^ ((((x) >> 5) & 1) * WPOLY) ^ ((((x) >> 5) & 2) * WPOLY) ^ \
+ ((((x) >> 5) & 4) * WPOLY))
#define d2(x) (((x) >> 1) ^ ((x)&1 ? DPOLY : 0))
#define f3(x) (f2(x) ^ (x))
@@ -89,82 +92,127 @@ typedef uint32_t uint_32t;
#if defined(USE_TABLES)
-#define sb_data(w) \
- { /* S Box data values */ \
- w(0x63), w(0x7c), w(0x77), w(0x7b), w(0xf2), w(0x6b), w(0x6f), w(0xc5), w(0x30), w(0x01), w(0x67), w(0x2b), \
- w(0xfe), w(0xd7), w(0xab), w(0x76), w(0xca), w(0x82), w(0xc9), w(0x7d), w(0xfa), w(0x59), w(0x47), w(0xf0), \
- w(0xad), w(0xd4), w(0xa2), w(0xaf), w(0x9c), w(0xa4), w(0x72), w(0xc0), w(0xb7), w(0xfd), w(0x93), w(0x26), \
- w(0x36), w(0x3f), w(0xf7), w(0xcc), w(0x34), w(0xa5), w(0xe5), w(0xf1), w(0x71), w(0xd8), w(0x31), w(0x15), \
- w(0x04), w(0xc7), w(0x23), w(0xc3), w(0x18), w(0x96), w(0x05), w(0x9a), w(0x07), w(0x12), w(0x80), w(0xe2), \
- w(0xeb), w(0x27), w(0xb2), w(0x75), w(0x09), w(0x83), w(0x2c), w(0x1a), w(0x1b), w(0x6e), w(0x5a), w(0xa0), \
- w(0x52), w(0x3b), w(0xd6), w(0xb3), w(0x29), w(0xe3), w(0x2f), w(0x84), w(0x53), w(0xd1), w(0x00), w(0xed), \
- w(0x20), w(0xfc), w(0xb1), w(0x5b), w(0x6a), w(0xcb), w(0xbe), w(0x39), w(0x4a), w(0x4c), w(0x58), w(0xcf), \
- w(0xd0), w(0xef), w(0xaa), w(0xfb), w(0x43), w(0x4d), w(0x33), w(0x85), w(0x45), w(0xf9), w(0x02), w(0x7f), \
- w(0x50), w(0x3c), w(0x9f), w(0xa8), w(0x51), w(0xa3), w(0x40), w(0x8f), w(0x92), w(0x9d), w(0x38), w(0xf5), \
- w(0xbc), w(0xb6), w(0xda), w(0x21), w(0x10), w(0xff), w(0xf3), w(0xd2), w(0xcd), w(0x0c), w(0x13), w(0xec), \
- w(0x5f), w(0x97), w(0x44), w(0x17), w(0xc4), w(0xa7), w(0x7e), w(0x3d), w(0x64), w(0x5d), w(0x19), w(0x73), \
- w(0x60), w(0x81), w(0x4f), w(0xdc), w(0x22), w(0x2a), w(0x90), w(0x88), w(0x46), w(0xee), w(0xb8), w(0x14), \
- w(0xde), w(0x5e), w(0x0b), w(0xdb), w(0xe0), w(0x32), w(0x3a), w(0x0a), w(0x49), w(0x06), w(0x24), w(0x5c), \
- w(0xc2), w(0xd3), w(0xac), w(0x62), w(0x91), w(0x95), w(0xe4), w(0x79), w(0xe7), w(0xc8), w(0x37), w(0x6d), \
- w(0x8d), w(0xd5), w(0x4e), w(0xa9), w(0x6c), w(0x56), w(0xf4), w(0xea), w(0x65), w(0x7a), w(0xae), w(0x08), \
- w(0xba), w(0x78), w(0x25), w(0x2e), w(0x1c), w(0xa6), w(0xb4), w(0xc6), w(0xe8), w(0xdd), w(0x74), w(0x1f), \
- w(0x4b), w(0xbd), w(0x8b), w(0x8a), w(0x70), w(0x3e), w(0xb5), w(0x66), w(0x48), w(0x03), w(0xf6), w(0x0e), \
- w(0x61), w(0x35), w(0x57), w(0xb9), w(0x86), w(0xc1), w(0x1d), w(0x9e), w(0xe1), w(0xf8), w(0x98), w(0x11), \
- w(0x69), w(0xd9), w(0x8e), w(0x94), w(0x9b), w(0x1e), w(0x87), w(0xe9), w(0xce), w(0x55), w(0x28), w(0xdf), \
- w(0x8c), w(0xa1), w(0x89), w(0x0d), w(0xbf), w(0xe6), w(0x42), w(0x68), w(0x41), w(0x99), w(0x2d), w(0x0f), \
- w(0xb0), w(0x54), w(0xbb), w(0x16) \
+#define sb_data(w) \
+ { /* S Box data values */ \
+ w(0x63), w(0x7c), w(0x77), w(0x7b), w(0xf2), w(0x6b), w(0x6f), w(0xc5), \
+ w(0x30), w(0x01), w(0x67), w(0x2b), w(0xfe), w(0xd7), w(0xab), \
+ w(0x76), w(0xca), w(0x82), w(0xc9), w(0x7d), w(0xfa), w(0x59), \
+ w(0x47), w(0xf0), w(0xad), w(0xd4), w(0xa2), w(0xaf), w(0x9c), \
+ w(0xa4), w(0x72), w(0xc0), w(0xb7), w(0xfd), w(0x93), w(0x26), \
+ w(0x36), w(0x3f), w(0xf7), w(0xcc), w(0x34), w(0xa5), w(0xe5), \
+ w(0xf1), w(0x71), w(0xd8), w(0x31), w(0x15), w(0x04), w(0xc7), \
+ w(0x23), w(0xc3), w(0x18), w(0x96), w(0x05), w(0x9a), w(0x07), \
+ w(0x12), w(0x80), w(0xe2), w(0xeb), w(0x27), w(0xb2), w(0x75), \
+ w(0x09), w(0x83), w(0x2c), w(0x1a), w(0x1b), w(0x6e), w(0x5a), \
+ w(0xa0), w(0x52), w(0x3b), w(0xd6), w(0xb3), w(0x29), w(0xe3), \
+ w(0x2f), w(0x84), w(0x53), w(0xd1), w(0x00), w(0xed), w(0x20), \
+ w(0xfc), w(0xb1), w(0x5b), w(0x6a), w(0xcb), w(0xbe), w(0x39), \
+ w(0x4a), w(0x4c), w(0x58), w(0xcf), w(0xd0), w(0xef), w(0xaa), \
+ w(0xfb), w(0x43), w(0x4d), w(0x33), w(0x85), w(0x45), w(0xf9), \
+ w(0x02), w(0x7f), w(0x50), w(0x3c), w(0x9f), w(0xa8), w(0x51), \
+ w(0xa3), w(0x40), w(0x8f), w(0x92), w(0x9d), w(0x38), w(0xf5), \
+ w(0xbc), w(0xb6), w(0xda), w(0x21), w(0x10), w(0xff), w(0xf3), \
+ w(0xd2), w(0xcd), w(0x0c), w(0x13), w(0xec), w(0x5f), w(0x97), \
+ w(0x44), w(0x17), w(0xc4), w(0xa7), w(0x7e), w(0x3d), w(0x64), \
+ w(0x5d), w(0x19), w(0x73), w(0x60), w(0x81), w(0x4f), w(0xdc), \
+ w(0x22), w(0x2a), w(0x90), w(0x88), w(0x46), w(0xee), w(0xb8), \
+ w(0x14), w(0xde), w(0x5e), w(0x0b), w(0xdb), w(0xe0), w(0x32), \
+ w(0x3a), w(0x0a), w(0x49), w(0x06), w(0x24), w(0x5c), w(0xc2), \
+ w(0xd3), w(0xac), w(0x62), w(0x91), w(0x95), w(0xe4), w(0x79), \
+ w(0xe7), w(0xc8), w(0x37), w(0x6d), w(0x8d), w(0xd5), w(0x4e), \
+ w(0xa9), w(0x6c), w(0x56), w(0xf4), w(0xea), w(0x65), w(0x7a), \
+ w(0xae), w(0x08), w(0xba), w(0x78), w(0x25), w(0x2e), w(0x1c), \
+ w(0xa6), w(0xb4), w(0xc6), w(0xe8), w(0xdd), w(0x74), w(0x1f), \
+ w(0x4b), w(0xbd), w(0x8b), w(0x8a), w(0x70), w(0x3e), w(0xb5), \
+ w(0x66), w(0x48), w(0x03), w(0xf6), w(0x0e), w(0x61), w(0x35), \
+ w(0x57), w(0xb9), w(0x86), w(0xc1), w(0x1d), w(0x9e), w(0xe1), \
+ w(0xf8), w(0x98), w(0x11), w(0x69), w(0xd9), w(0x8e), w(0x94), \
+ w(0x9b), w(0x1e), w(0x87), w(0xe9), w(0xce), w(0x55), w(0x28), \
+ w(0xdf), w(0x8c), w(0xa1), w(0x89), w(0x0d), w(0xbf), w(0xe6), \
+ w(0x42), w(0x68), w(0x41), w(0x99), w(0x2d), w(0x0f), w(0xb0), \
+ w(0x54), w(0xbb), w(0x16) \
}
-#define isb_data(w) \
- { /* inverse S Box data values */ \
- w(0x52), w(0x09), w(0x6a), w(0xd5), w(0x30), w(0x36), w(0xa5), w(0x38), w(0xbf), w(0x40), w(0xa3), w(0x9e), \
- w(0x81), w(0xf3), w(0xd7), w(0xfb), w(0x7c), w(0xe3), w(0x39), w(0x82), w(0x9b), w(0x2f), w(0xff), w(0x87), \
- w(0x34), w(0x8e), w(0x43), w(0x44), w(0xc4), w(0xde), w(0xe9), w(0xcb), w(0x54), w(0x7b), w(0x94), w(0x32), \
- w(0xa6), w(0xc2), w(0x23), w(0x3d), w(0xee), w(0x4c), w(0x95), w(0x0b), w(0x42), w(0xfa), w(0xc3), w(0x4e), \
- w(0x08), w(0x2e), w(0xa1), w(0x66), w(0x28), w(0xd9), w(0x24), w(0xb2), w(0x76), w(0x5b), w(0xa2), w(0x49), \
- w(0x6d), w(0x8b), w(0xd1), w(0x25), w(0x72), w(0xf8), w(0xf6), w(0x64), w(0x86), w(0x68), w(0x98), w(0x16), \
- w(0xd4), w(0xa4), w(0x5c), w(0xcc), w(0x5d), w(0x65), w(0xb6), w(0x92), w(0x6c), w(0x70), w(0x48), w(0x50), \
- w(0xfd), w(0xed), w(0xb9), w(0xda), w(0x5e), w(0x15), w(0x46), w(0x57), w(0xa7), w(0x8d), w(0x9d), w(0x84), \
- w(0x90), w(0xd8), w(0xab), w(0x00), w(0x8c), w(0xbc), w(0xd3), w(0x0a), w(0xf7), w(0xe4), w(0x58), w(0x05), \
- w(0xb8), w(0xb3), w(0x45), w(0x06), w(0xd0), w(0x2c), w(0x1e), w(0x8f), w(0xca), w(0x3f), w(0x0f), w(0x02), \
- w(0xc1), w(0xaf), w(0xbd), w(0x03), w(0x01), w(0x13), w(0x8a), w(0x6b), w(0x3a), w(0x91), w(0x11), w(0x41), \
- w(0x4f), w(0x67), w(0xdc), w(0xea), w(0x97), w(0xf2), w(0xcf), w(0xce), w(0xf0), w(0xb4), w(0xe6), w(0x73), \
- w(0x96), w(0xac), w(0x74), w(0x22), w(0xe7), w(0xad), w(0x35), w(0x85), w(0xe2), w(0xf9), w(0x37), w(0xe8), \
- w(0x1c), w(0x75), w(0xdf), w(0x6e), w(0x47), w(0xf1), w(0x1a), w(0x71), w(0x1d), w(0x29), w(0xc5), w(0x89), \
- w(0x6f), w(0xb7), w(0x62), w(0x0e), w(0xaa), w(0x18), w(0xbe), w(0x1b), w(0xfc), w(0x56), w(0x3e), w(0x4b), \
- w(0xc6), w(0xd2), w(0x79), w(0x20), w(0x9a), w(0xdb), w(0xc0), w(0xfe), w(0x78), w(0xcd), w(0x5a), w(0xf4), \
- w(0x1f), w(0xdd), w(0xa8), w(0x33), w(0x88), w(0x07), w(0xc7), w(0x31), w(0xb1), w(0x12), w(0x10), w(0x59), \
- w(0x27), w(0x80), w(0xec), w(0x5f), w(0x60), w(0x51), w(0x7f), w(0xa9), w(0x19), w(0xb5), w(0x4a), w(0x0d), \
- w(0x2d), w(0xe5), w(0x7a), w(0x9f), w(0x93), w(0xc9), w(0x9c), w(0xef), w(0xa0), w(0xe0), w(0x3b), w(0x4d), \
- w(0xae), w(0x2a), w(0xf5), w(0xb0), w(0xc8), w(0xeb), w(0xbb), w(0x3c), w(0x83), w(0x53), w(0x99), w(0x61), \
- w(0x17), w(0x2b), w(0x04), w(0x7e), w(0xba), w(0x77), w(0xd6), w(0x26), w(0xe1), w(0x69), w(0x14), w(0x63), \
- w(0x55), w(0x21), w(0x0c), w(0x7d) \
+#define isb_data(w) \
+ { /* inverse S Box data values */ \
+ w(0x52), w(0x09), w(0x6a), w(0xd5), w(0x30), w(0x36), w(0xa5), w(0x38), \
+ w(0xbf), w(0x40), w(0xa3), w(0x9e), w(0x81), w(0xf3), w(0xd7), \
+ w(0xfb), w(0x7c), w(0xe3), w(0x39), w(0x82), w(0x9b), w(0x2f), \
+ w(0xff), w(0x87), w(0x34), w(0x8e), w(0x43), w(0x44), w(0xc4), \
+ w(0xde), w(0xe9), w(0xcb), w(0x54), w(0x7b), w(0x94), w(0x32), \
+ w(0xa6), w(0xc2), w(0x23), w(0x3d), w(0xee), w(0x4c), w(0x95), \
+ w(0x0b), w(0x42), w(0xfa), w(0xc3), w(0x4e), w(0x08), w(0x2e), \
+ w(0xa1), w(0x66), w(0x28), w(0xd9), w(0x24), w(0xb2), w(0x76), \
+ w(0x5b), w(0xa2), w(0x49), w(0x6d), w(0x8b), w(0xd1), w(0x25), \
+ w(0x72), w(0xf8), w(0xf6), w(0x64), w(0x86), w(0x68), w(0x98), \
+ w(0x16), w(0xd4), w(0xa4), w(0x5c), w(0xcc), w(0x5d), w(0x65), \
+ w(0xb6), w(0x92), w(0x6c), w(0x70), w(0x48), w(0x50), w(0xfd), \
+ w(0xed), w(0xb9), w(0xda), w(0x5e), w(0x15), w(0x46), w(0x57), \
+ w(0xa7), w(0x8d), w(0x9d), w(0x84), w(0x90), w(0xd8), w(0xab), \
+ w(0x00), w(0x8c), w(0xbc), w(0xd3), w(0x0a), w(0xf7), w(0xe4), \
+ w(0x58), w(0x05), w(0xb8), w(0xb3), w(0x45), w(0x06), w(0xd0), \
+ w(0x2c), w(0x1e), w(0x8f), w(0xca), w(0x3f), w(0x0f), w(0x02), \
+ w(0xc1), w(0xaf), w(0xbd), w(0x03), w(0x01), w(0x13), w(0x8a), \
+ w(0x6b), w(0x3a), w(0x91), w(0x11), w(0x41), w(0x4f), w(0x67), \
+ w(0xdc), w(0xea), w(0x97), w(0xf2), w(0xcf), w(0xce), w(0xf0), \
+ w(0xb4), w(0xe6), w(0x73), w(0x96), w(0xac), w(0x74), w(0x22), \
+ w(0xe7), w(0xad), w(0x35), w(0x85), w(0xe2), w(0xf9), w(0x37), \
+ w(0xe8), w(0x1c), w(0x75), w(0xdf), w(0x6e), w(0x47), w(0xf1), \
+ w(0x1a), w(0x71), w(0x1d), w(0x29), w(0xc5), w(0x89), w(0x6f), \
+ w(0xb7), w(0x62), w(0x0e), w(0xaa), w(0x18), w(0xbe), w(0x1b), \
+ w(0xfc), w(0x56), w(0x3e), w(0x4b), w(0xc6), w(0xd2), w(0x79), \
+ w(0x20), w(0x9a), w(0xdb), w(0xc0), w(0xfe), w(0x78), w(0xcd), \
+ w(0x5a), w(0xf4), w(0x1f), w(0xdd), w(0xa8), w(0x33), w(0x88), \
+ w(0x07), w(0xc7), w(0x31), w(0xb1), w(0x12), w(0x10), w(0x59), \
+ w(0x27), w(0x80), w(0xec), w(0x5f), w(0x60), w(0x51), w(0x7f), \
+ w(0xa9), w(0x19), w(0xb5), w(0x4a), w(0x0d), w(0x2d), w(0xe5), \
+ w(0x7a), w(0x9f), w(0x93), w(0xc9), w(0x9c), w(0xef), w(0xa0), \
+ w(0xe0), w(0x3b), w(0x4d), w(0xae), w(0x2a), w(0xf5), w(0xb0), \
+ w(0xc8), w(0xeb), w(0xbb), w(0x3c), w(0x83), w(0x53), w(0x99), \
+ w(0x61), w(0x17), w(0x2b), w(0x04), w(0x7e), w(0xba), w(0x77), \
+ w(0xd6), w(0x26), w(0xe1), w(0x69), w(0x14), w(0x63), w(0x55), \
+ w(0x21), w(0x0c), w(0x7d) \
}
-#define mm_data(w) \
- { /* basic data for forming finite field tables */ \
- w(0x00), w(0x01), w(0x02), w(0x03), w(0x04), w(0x05), w(0x06), w(0x07), w(0x08), w(0x09), w(0x0a), w(0x0b), \
- w(0x0c), w(0x0d), w(0x0e), w(0x0f), w(0x10), w(0x11), w(0x12), w(0x13), w(0x14), w(0x15), w(0x16), w(0x17), \
- w(0x18), w(0x19), w(0x1a), w(0x1b), w(0x1c), w(0x1d), w(0x1e), w(0x1f), w(0x20), w(0x21), w(0x22), w(0x23), \
- w(0x24), w(0x25), w(0x26), w(0x27), w(0x28), w(0x29), w(0x2a), w(0x2b), w(0x2c), w(0x2d), w(0x2e), w(0x2f), \
- w(0x30), w(0x31), w(0x32), w(0x33), w(0x34), w(0x35), w(0x36), w(0x37), w(0x38), w(0x39), w(0x3a), w(0x3b), \
- w(0x3c), w(0x3d), w(0x3e), w(0x3f), w(0x40), w(0x41), w(0x42), w(0x43), w(0x44), w(0x45), w(0x46), w(0x47), \
- w(0x48), w(0x49), w(0x4a), w(0x4b), w(0x4c), w(0x4d), w(0x4e), w(0x4f), w(0x50), w(0x51), w(0x52), w(0x53), \
- w(0x54), w(0x55), w(0x56), w(0x57), w(0x58), w(0x59), w(0x5a), w(0x5b), w(0x5c), w(0x5d), w(0x5e), w(0x5f), \
- w(0x60), w(0x61), w(0x62), w(0x63), w(0x64), w(0x65), w(0x66), w(0x67), w(0x68), w(0x69), w(0x6a), w(0x6b), \
- w(0x6c), w(0x6d), w(0x6e), w(0x6f), w(0x70), w(0x71), w(0x72), w(0x73), w(0x74), w(0x75), w(0x76), w(0x77), \
- w(0x78), w(0x79), w(0x7a), w(0x7b), w(0x7c), w(0x7d), w(0x7e), w(0x7f), w(0x80), w(0x81), w(0x82), w(0x83), \
- w(0x84), w(0x85), w(0x86), w(0x87), w(0x88), w(0x89), w(0x8a), w(0x8b), w(0x8c), w(0x8d), w(0x8e), w(0x8f), \
- w(0x90), w(0x91), w(0x92), w(0x93), w(0x94), w(0x95), w(0x96), w(0x97), w(0x98), w(0x99), w(0x9a), w(0x9b), \
- w(0x9c), w(0x9d), w(0x9e), w(0x9f), w(0xa0), w(0xa1), w(0xa2), w(0xa3), w(0xa4), w(0xa5), w(0xa6), w(0xa7), \
- w(0xa8), w(0xa9), w(0xaa), w(0xab), w(0xac), w(0xad), w(0xae), w(0xaf), w(0xb0), w(0xb1), w(0xb2), w(0xb3), \
- w(0xb4), w(0xb5), w(0xb6), w(0xb7), w(0xb8), w(0xb9), w(0xba), w(0xbb), w(0xbc), w(0xbd), w(0xbe), w(0xbf), \
- w(0xc0), w(0xc1), w(0xc2), w(0xc3), w(0xc4), w(0xc5), w(0xc6), w(0xc7), w(0xc8), w(0xc9), w(0xca), w(0xcb), \
- w(0xcc), w(0xcd), w(0xce), w(0xcf), w(0xd0), w(0xd1), w(0xd2), w(0xd3), w(0xd4), w(0xd5), w(0xd6), w(0xd7), \
- w(0xd8), w(0xd9), w(0xda), w(0xdb), w(0xdc), w(0xdd), w(0xde), w(0xdf), w(0xe0), w(0xe1), w(0xe2), w(0xe3), \
- w(0xe4), w(0xe5), w(0xe6), w(0xe7), w(0xe8), w(0xe9), w(0xea), w(0xeb), w(0xec), w(0xed), w(0xee), w(0xef), \
- w(0xf0), w(0xf1), w(0xf2), w(0xf3), w(0xf4), w(0xf5), w(0xf6), w(0xf7), w(0xf8), w(0xf9), w(0xfa), w(0xfb), \
- w(0xfc), w(0xfd), w(0xfe), w(0xff) \
+#define mm_data(w) \
+ { /* basic data for forming finite field tables */ \
+ w(0x00), w(0x01), w(0x02), w(0x03), w(0x04), w(0x05), w(0x06), w(0x07), \
+ w(0x08), w(0x09), w(0x0a), w(0x0b), w(0x0c), w(0x0d), w(0x0e), \
+ w(0x0f), w(0x10), w(0x11), w(0x12), w(0x13), w(0x14), w(0x15), \
+ w(0x16), w(0x17), w(0x18), w(0x19), w(0x1a), w(0x1b), w(0x1c), \
+ w(0x1d), w(0x1e), w(0x1f), w(0x20), w(0x21), w(0x22), w(0x23), \
+ w(0x24), w(0x25), w(0x26), w(0x27), w(0x28), w(0x29), w(0x2a), \
+ w(0x2b), w(0x2c), w(0x2d), w(0x2e), w(0x2f), w(0x30), w(0x31), \
+ w(0x32), w(0x33), w(0x34), w(0x35), w(0x36), w(0x37), w(0x38), \
+ w(0x39), w(0x3a), w(0x3b), w(0x3c), w(0x3d), w(0x3e), w(0x3f), \
+ w(0x40), w(0x41), w(0x42), w(0x43), w(0x44), w(0x45), w(0x46), \
+ w(0x47), w(0x48), w(0x49), w(0x4a), w(0x4b), w(0x4c), w(0x4d), \
+ w(0x4e), w(0x4f), w(0x50), w(0x51), w(0x52), w(0x53), w(0x54), \
+ w(0x55), w(0x56), w(0x57), w(0x58), w(0x59), w(0x5a), w(0x5b), \
+ w(0x5c), w(0x5d), w(0x5e), w(0x5f), w(0x60), w(0x61), w(0x62), \
+ w(0x63), w(0x64), w(0x65), w(0x66), w(0x67), w(0x68), w(0x69), \
+ w(0x6a), w(0x6b), w(0x6c), w(0x6d), w(0x6e), w(0x6f), w(0x70), \
+ w(0x71), w(0x72), w(0x73), w(0x74), w(0x75), w(0x76), w(0x77), \
+ w(0x78), w(0x79), w(0x7a), w(0x7b), w(0x7c), w(0x7d), w(0x7e), \
+ w(0x7f), w(0x80), w(0x81), w(0x82), w(0x83), w(0x84), w(0x85), \
+ w(0x86), w(0x87), w(0x88), w(0x89), w(0x8a), w(0x8b), w(0x8c), \
+ w(0x8d), w(0x8e), w(0x8f), w(0x90), w(0x91), w(0x92), w(0x93), \
+ w(0x94), w(0x95), w(0x96), w(0x97), w(0x98), w(0x99), w(0x9a), \
+ w(0x9b), w(0x9c), w(0x9d), w(0x9e), w(0x9f), w(0xa0), w(0xa1), \
+ w(0xa2), w(0xa3), w(0xa4), w(0xa5), w(0xa6), w(0xa7), w(0xa8), \
+ w(0xa9), w(0xaa), w(0xab), w(0xac), w(0xad), w(0xae), w(0xaf), \
+ w(0xb0), w(0xb1), w(0xb2), w(0xb3), w(0xb4), w(0xb5), w(0xb6), \
+ w(0xb7), w(0xb8), w(0xb9), w(0xba), w(0xbb), w(0xbc), w(0xbd), \
+ w(0xbe), w(0xbf), w(0xc0), w(0xc1), w(0xc2), w(0xc3), w(0xc4), \
+ w(0xc5), w(0xc6), w(0xc7), w(0xc8), w(0xc9), w(0xca), w(0xcb), \
+ w(0xcc), w(0xcd), w(0xce), w(0xcf), w(0xd0), w(0xd1), w(0xd2), \
+ w(0xd3), w(0xd4), w(0xd5), w(0xd6), w(0xd7), w(0xd8), w(0xd9), \
+ w(0xda), w(0xdb), w(0xdc), w(0xdd), w(0xde), w(0xdf), w(0xe0), \
+ w(0xe1), w(0xe2), w(0xe3), w(0xe4), w(0xe5), w(0xe6), w(0xe7), \
+ w(0xe8), w(0xe9), w(0xea), w(0xeb), w(0xec), w(0xed), w(0xee), \
+ w(0xef), w(0xf0), w(0xf1), w(0xf2), w(0xf3), w(0xf4), w(0xf5), \
+ w(0xf6), w(0xf7), w(0xf8), w(0xf9), w(0xfa), w(0xfb), w(0xfc), \
+ w(0xfd), w(0xfe), w(0xff) \
}
static const uint_8t sbox[256] = sb_data(f1);
@@ -240,7 +288,8 @@ uint_8t fwd_affine(const uint_8t x) {
w ^= (w << 1) ^ (w << 2) ^ (w << 3) ^ (w << 4);
return 0x63 ^ ((w ^ (w >> 8)) & 0xff);
#else
- return 0x63 ^ x ^ (x << 1) ^ (x << 2) ^ (x << 3) ^ (x << 4) ^ (x >> 7) ^ (x >> 6) ^ (x >> 5) ^ (x >> 4);
+ return 0x63 ^ x ^ (x << 1) ^ (x << 2) ^ (x << 3) ^ (x << 4) ^ (x >> 7) ^
+ (x >> 6) ^ (x >> 5) ^ (x >> 4);
#endif
}
@@ -470,10 +519,12 @@ static void inv_mix_sub_columns(uint_8t dt[N_BLOCK], uint_8t st[N_BLOCK]) {
dt[2] = is_box(gfm_d(st[8]) ^ gfm_9(st[9]) ^ gfm_e(st[10]) ^ gfm_b(st[11]));
dt[7] = is_box(gfm_b(st[8]) ^ gfm_d(st[9]) ^ gfm_9(st[10]) ^ gfm_e(st[11]));
- dt[12] = is_box(gfm_e(st[12]) ^ gfm_b(st[13]) ^ gfm_d(st[14]) ^ gfm_9(st[15]));
+ dt[12] =
+ is_box(gfm_e(st[12]) ^ gfm_b(st[13]) ^ gfm_d(st[14]) ^ gfm_9(st[15]));
dt[1] = is_box(gfm_9(st[12]) ^ gfm_e(st[13]) ^ gfm_b(st[14]) ^ gfm_d(st[15]));
dt[6] = is_box(gfm_d(st[12]) ^ gfm_9(st[13]) ^ gfm_e(st[14]) ^ gfm_b(st[15]));
- dt[11] = is_box(gfm_b(st[12]) ^ gfm_d(st[13]) ^ gfm_9(st[14]) ^ gfm_e(st[15]));
+ dt[11] =
+ is_box(gfm_b(st[12]) ^ gfm_d(st[13]) ^ gfm_9(st[14]) ^ gfm_e(st[15]));
}
#if defined(AES_ENC_PREKEYED) || defined(AES_DEC_PREKEYED)
@@ -485,7 +536,8 @@ static void inv_mix_sub_columns(uint_8t dt[N_BLOCK], uint_8t st[N_BLOCK]) {
128, 192, 16, 24 and 32).
*/
-return_type aes_set_key(const unsigned char key[], length_type keylen, aes_context ctx[1]) {
+return_type aes_set_key(const unsigned char key[], length_type keylen,
+ aes_context ctx[1]) {
uint_8t cc, rc, hi;
switch (keylen) {
@@ -543,7 +595,8 @@ return_type aes_set_key(const unsigned char key[], length_type keylen, aes_conte
/* Encrypt a single block of 16 bytes */
-return_type aes_encrypt(const unsigned char in[N_BLOCK], unsigned char out[N_BLOCK], const aes_context ctx[1]) {
+return_type aes_encrypt(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK], const aes_context ctx[1]) {
if (ctx->rnd) {
uint_8t s1[N_BLOCK], r;
copy_and_key(s1, in, ctx->ksch);
@@ -570,8 +623,9 @@ return_type aes_encrypt(const unsigned char in[N_BLOCK], unsigned char out[N_BLO
/* CBC encrypt a number of blocks (input and return an IV) */
-return_type aes_cbc_encrypt(
- const unsigned char* in, unsigned char* out, int n_block, unsigned char iv[N_BLOCK], const aes_context ctx[1]) {
+return_type aes_cbc_encrypt(const unsigned char* in, unsigned char* out,
+ int n_block, unsigned char iv[N_BLOCK],
+ const aes_context ctx[1]) {
while (n_block--) {
xor_block(iv, in);
if (aes_encrypt(iv, iv, ctx) != EXIT_SUCCESS) return EXIT_FAILURE;
@@ -588,7 +642,8 @@ return_type aes_cbc_encrypt(
/* Decrypt a single block of 16 bytes */
-return_type aes_decrypt(const unsigned char in[N_BLOCK], unsigned char out[N_BLOCK], const aes_context ctx[1]) {
+return_type aes_decrypt(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK], const aes_context ctx[1]) {
if (ctx->rnd) {
uint_8t s1[N_BLOCK], r;
copy_and_key(s1, in, ctx->ksch + ctx->rnd * N_BLOCK);
@@ -615,8 +670,9 @@ return_type aes_decrypt(const unsigned char in[N_BLOCK], unsigned char out[N_BLO
/* CBC decrypt a number of blocks (input and return an IV) */
-return_type aes_cbc_decrypt(
- const unsigned char* in, unsigned char* out, int n_block, unsigned char iv[N_BLOCK], const aes_context ctx[1]) {
+return_type aes_cbc_decrypt(const unsigned char* in, unsigned char* out,
+ int n_block, unsigned char iv[N_BLOCK],
+ const aes_context ctx[1]) {
while (n_block--) {
uint_8t tmp[N_BLOCK];
@@ -655,11 +711,10 @@ static void update_encrypt_key_128(uint_8t k[N_BLOCK], uint_8t* rc) {
/* Encrypt a single block of 16 bytes with 'on the fly' 128 bit keying */
-void aes_encrypt_128(
- const unsigned char in[N_BLOCK],
- unsigned char out[N_BLOCK],
- const unsigned char key[N_BLOCK],
- unsigned char o_key[N_BLOCK]) {
+void aes_encrypt_128(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK],
+ const unsigned char key[N_BLOCK],
+ unsigned char o_key[N_BLOCK]) {
uint_8t s1[N_BLOCK], r, rc = 1;
if (o_key != key) block_copy(o_key, key);
@@ -710,11 +765,10 @@ static void update_decrypt_key_128(uint_8t k[N_BLOCK], uint_8t* rc) {
/* Decrypt a single block of 16 bytes with 'on the fly' 128 bit keying */
-void aes_decrypt_128(
- const unsigned char in[N_BLOCK],
- unsigned char out[N_BLOCK],
- const unsigned char key[N_BLOCK],
- unsigned char o_key[N_BLOCK]) {
+void aes_decrypt_128(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK],
+ const unsigned char key[N_BLOCK],
+ unsigned char o_key[N_BLOCK]) {
uint_8t s1[N_BLOCK], r, rc = 0x6c;
if (o_key != key) block_copy(o_key, key);
@@ -777,11 +831,10 @@ static void update_encrypt_key_256(uint_8t k[2 * N_BLOCK], uint_8t* rc) {
/* Encrypt a single block of 16 bytes with 'on the fly' 256 bit keying */
-void aes_encrypt_256(
- const unsigned char in[N_BLOCK],
- unsigned char out[N_BLOCK],
- const unsigned char key[2 * N_BLOCK],
- unsigned char o_key[2 * N_BLOCK]) {
+void aes_encrypt_256(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK],
+ const unsigned char key[2 * N_BLOCK],
+ unsigned char o_key[2 * N_BLOCK]) {
uint_8t s1[N_BLOCK], r, rc = 1;
if (o_key != key) {
block_copy(o_key, key);
@@ -856,11 +909,10 @@ static void update_decrypt_key_256(uint_8t k[2 * N_BLOCK], uint_8t* rc) {
/* Decrypt a single block of 16 bytes with 'on the fly'
256 bit keying
*/
-void aes_decrypt_256(
- const unsigned char in[N_BLOCK],
- unsigned char out[N_BLOCK],
- const unsigned char key[2 * N_BLOCK],
- unsigned char o_key[2 * N_BLOCK]) {
+void aes_decrypt_256(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK],
+ const unsigned char key[2 * N_BLOCK],
+ unsigned char o_key[2 * N_BLOCK]) {
uint_8t s1[N_BLOCK], r, rc = 0x80;
if (o_key != key) {
diff --git a/gd/crypto_toolbox/aes.h b/gd/crypto_toolbox/aes.h
index 6d59743b4..2ff6fbde0 100644
--- a/gd/crypto_toolbox/aes.h
+++ b/gd/crypto_toolbox/aes.h
@@ -80,23 +80,28 @@ typedef struct {
#if defined(AES_ENC_PREKEYED) || defined(AES_DEC_PREKEYED)
-return_type aes_set_key(const unsigned char key[], length_type keylen, aes_context ctx[1]);
+return_type aes_set_key(const unsigned char key[], length_type keylen,
+ aes_context ctx[1]);
#endif
#if defined(AES_ENC_PREKEYED)
-return_type aes_encrypt(const unsigned char in[N_BLOCK], unsigned char out[N_BLOCK], const aes_context ctx[1]);
+return_type aes_encrypt(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK], const aes_context ctx[1]);
-return_type aes_cbc_encrypt(
- const unsigned char* in, unsigned char* out, int n_block, unsigned char iv[N_BLOCK], const aes_context ctx[1]);
+return_type aes_cbc_encrypt(const unsigned char* in, unsigned char* out,
+ int n_block, unsigned char iv[N_BLOCK],
+ const aes_context ctx[1]);
#endif
#if defined(AES_DEC_PREKEYED)
-return_type aes_decrypt(const unsigned char in[N_BLOCK], unsigned char out[N_BLOCK], const aes_context ctx[1]);
+return_type aes_decrypt(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK], const aes_context ctx[1]);
-return_type aes_cbc_decrypt(
- const unsigned char* in, unsigned char* out, int n_block, unsigned char iv[N_BLOCK], const aes_context ctx[1]);
+return_type aes_cbc_decrypt(const unsigned char* in, unsigned char* out,
+ int n_block, unsigned char iv[N_BLOCK],
+ const aes_context ctx[1]);
#endif
/* The following calls are for 'on the fly' keying. In this case the
@@ -120,35 +125,30 @@ return_type aes_cbc_decrypt(
*/
#if defined(AES_ENC_128_OTFK)
-void aes_encrypt_128(
- const unsigned char in[N_BLOCK],
- unsigned char out[N_BLOCK],
- const unsigned char key[N_BLOCK],
- uint_8t o_key[N_BLOCK]);
+void aes_encrypt_128(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK],
+ const unsigned char key[N_BLOCK], uint_8t o_key[N_BLOCK]);
#endif
#if defined(AES_DEC_128_OTFK)
-void aes_decrypt_128(
- const unsigned char in[N_BLOCK],
- unsigned char out[N_BLOCK],
- const unsigned char key[N_BLOCK],
- unsigned char o_key[N_BLOCK]);
+void aes_decrypt_128(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK],
+ const unsigned char key[N_BLOCK],
+ unsigned char o_key[N_BLOCK]);
#endif
#if defined(AES_ENC_256_OTFK)
-void aes_encrypt_256(
- const unsigned char in[N_BLOCK],
- unsigned char out[N_BLOCK],
- const unsigned char key[2 * N_BLOCK],
- unsigned char o_key[2 * N_BLOCK]);
+void aes_encrypt_256(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK],
+ const unsigned char key[2 * N_BLOCK],
+ unsigned char o_key[2 * N_BLOCK]);
#endif
#if defined(AES_DEC_256_OTFK)
-void aes_decrypt_256(
- const unsigned char in[N_BLOCK],
- unsigned char out[N_BLOCK],
- const unsigned char key[2 * N_BLOCK],
- unsigned char o_key[2 * N_BLOCK]);
+void aes_decrypt_256(const unsigned char in[N_BLOCK],
+ unsigned char out[N_BLOCK],
+ const unsigned char key[2 * N_BLOCK],
+ unsigned char o_key[2 * N_BLOCK]);
#endif
#endif
diff --git a/gd/crypto_toolbox/aes_cmac.cc b/gd/crypto_toolbox/aes_cmac.cc
index 85fdd5930..752027e2f 100644
--- a/gd/crypto_toolbox/aes_cmac.cc
+++ b/gd/crypto_toolbox/aes_cmac.cc
@@ -22,8 +22,6 @@
*
******************************************************************************/
-#include <algorithm>
-
#include "crypto_toolbox/aes.h"
#include "crypto_toolbox/crypto_toolbox.h"
diff --git a/gd/crypto_toolbox/crypto_toolbox.cc b/gd/crypto_toolbox/crypto_toolbox.cc
index 67f1a7079..adb49561b 100644
--- a/gd/crypto_toolbox/crypto_toolbox.cc
+++ b/gd/crypto_toolbox/crypto_toolbox.cc
@@ -15,13 +15,11 @@
*/
#include "crypto_toolbox/crypto_toolbox.h"
+#include "crypto_toolbox/aes.h"
#include <endian.h>
-
#include <algorithm>
-#include "crypto_toolbox/aes.h"
-
namespace bluetooth {
namespace crypto_toolbox {
@@ -50,15 +48,8 @@ Octet16 f4(uint8_t* u, uint8_t* v, const Octet16& x, uint8_t z) {
}
/** helper for f5 */
-static Octet16 calculate_mac_key_or_ltk(
- const Octet16& t,
- uint8_t counter,
- uint8_t* key_id,
- const Octet16& n1,
- const Octet16& n2,
- uint8_t* a1,
- uint8_t* a2,
- uint8_t* length) {
+static Octet16 calculate_mac_key_or_ltk(const Octet16& t, uint8_t counter, uint8_t* key_id, const Octet16& n1,
+ const Octet16& n2, uint8_t* a1, uint8_t* a2, uint8_t* length) {
constexpr size_t msg_len = 1 /* Counter size */ + 4 /* keyID size */ + OCTET16_LEN /* N1 size */ +
OCTET16_LEN /* N2 size */ + 7 /* A1 size*/ + 7 /* A2 size*/ + 2 /* Length size */;
@@ -96,8 +87,8 @@ void f5(uint8_t* w, const Octet16& n1, const Octet16& n2, uint8_t* a1, uint8_t*
// DVLOG(2) << "ltk=" << HexEncode(ltk->data(), ltk->size());
}
-Octet16
-f6(const Octet16& w, const Octet16& n1, const Octet16& n2, const Octet16& r, uint8_t* iocap, uint8_t* a1, uint8_t* a2) {
+Octet16 f6(const Octet16& w, const Octet16& n1, const Octet16& n2, const Octet16& r, uint8_t* iocap, uint8_t* a1,
+ uint8_t* a2) {
const uint8_t msg_len = OCTET16_LEN /* N1 size */ + OCTET16_LEN /* N2 size */ + OCTET16_LEN /* R size */ +
3 /* IOcap size */ + 7 /* A1 size*/ + 7 /* A2 size*/;
@@ -139,8 +130,8 @@ uint32_t g2(uint8_t* u, uint8_t* v, const Octet16& x, const Octet16& y) {
Octet16 ltk_to_link_key(const Octet16& ltk, bool use_h7) {
Octet16 ilk; /* intermidiate link key */
if (use_h7) {
- constexpr Octet16 salt{
- 0x31, 0x70, 0x6D, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
+ constexpr Octet16 salt{0x31, 0x70, 0x6D, 0x74, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
ilk = h7(salt, ltk);
} else {
/* "tmp1" mapping to extended ASCII, little endian*/
@@ -156,8 +147,8 @@ Octet16 ltk_to_link_key(const Octet16& ltk, bool use_h7) {
Octet16 link_key_to_ltk(const Octet16& link_key, bool use_h7) {
Octet16 iltk; /* intermidiate long term key */
if (use_h7) {
- constexpr Octet16 salt{
- 0x32, 0x70, 0x6D, 0x74, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
+ constexpr Octet16 salt{0x32, 0x70, 0x6D, 0x74, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
iltk = h7(salt, link_key);
} else {
/* "tmp2" mapping to extended ASCII, little endian */
@@ -170,15 +161,8 @@ Octet16 link_key_to_ltk(const Octet16& link_key, bool use_h7) {
return h6(iltk, keyID_brle);
}
-Octet16 c1(
- const Octet16& k,
- const Octet16& r,
- const uint8_t* preq,
- const uint8_t* pres,
- const uint8_t iat,
- const uint8_t* ia,
- const uint8_t rat,
- const uint8_t* ra) {
+Octet16 c1(const Octet16& k, const Octet16& r, const uint8_t* preq, const uint8_t* pres, const uint8_t iat,
+ const uint8_t* ia, const uint8_t rat, const uint8_t* ra) {
Octet16 p1;
auto it = p1.begin();
it = std::copy(&iat, &iat + 1, it);
diff --git a/gd/crypto_toolbox/crypto_toolbox.h b/gd/crypto_toolbox/crypto_toolbox.h
index 65da0973e..25f7f699b 100644
--- a/gd/crypto_toolbox/crypto_toolbox.h
+++ b/gd/crypto_toolbox/crypto_toolbox.h
@@ -17,8 +17,6 @@
#pragma once
#include <array>
-#include <cstdint>
-#include <cstring>
namespace bluetooth {
namespace crypto_toolbox {
@@ -26,24 +24,17 @@ namespace crypto_toolbox {
constexpr int OCTET16_LEN = 16;
using Octet16 = std::array<uint8_t, OCTET16_LEN>;
-Octet16 c1(
- const Octet16& k,
- const Octet16& r,
- const uint8_t* pres,
- const uint8_t* preq,
- const uint8_t iat,
- const uint8_t* ia,
- const uint8_t rat,
- const uint8_t* ra);
+Octet16 c1(const Octet16& k, const Octet16& r, const uint8_t* pres, const uint8_t* preq, const uint8_t iat,
+ const uint8_t* ia, const uint8_t rat, const uint8_t* ra);
Octet16 s1(const Octet16& k, const Octet16& r1, const Octet16& r2);
extern Octet16 aes_128(const Octet16& key, const Octet16& message);
extern Octet16 aes_cmac(const Octet16& key, const uint8_t* message, uint16_t length);
extern Octet16 f4(uint8_t* u, uint8_t* v, const Octet16& x, uint8_t z);
-extern void f5(
- uint8_t* w, const Octet16& n1, const Octet16& n2, uint8_t* a1, uint8_t* a2, Octet16* mac_key, Octet16* ltk);
-extern Octet16 f6(
- const Octet16& w, const Octet16& n1, const Octet16& n2, const Octet16& r, uint8_t* iocap, uint8_t* a1, uint8_t* a2);
+extern void f5(uint8_t* w, const Octet16& n1, const Octet16& n2, uint8_t* a1, uint8_t* a2, Octet16* mac_key,
+ Octet16* ltk);
+extern Octet16 f6(const Octet16& w, const Octet16& n1, const Octet16& n2, const Octet16& r, uint8_t* iocap, uint8_t* a1,
+ uint8_t* a2);
extern Octet16 h6(const Octet16& w, std::array<uint8_t, 4> keyid);
extern Octet16 h7(const Octet16& salt, const Octet16& w);
extern uint32_t g2(uint8_t* u, uint8_t* v, const Octet16& x, const Octet16& y);
@@ -74,4 +65,4 @@ inline Octet16 aes_cmac(const Octet16& key, const Octet16& message) {
}
} // namespace crypto_toolbox
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/gd/crypto_toolbox/crypto_toolbox_test.cc b/gd/crypto_toolbox/crypto_toolbox_test.cc
index 5c21a5dfb..b5674c10b 100644
--- a/gd/crypto_toolbox/crypto_toolbox_test.cc
+++ b/gd/crypto_toolbox/crypto_toolbox_test.cc
@@ -16,13 +16,12 @@
*
******************************************************************************/
-#include "crypto_toolbox/crypto_toolbox.h"
-
#include <gtest/gtest.h>
-#include <vector>
-
#include "crypto_toolbox/aes.h"
+#include "crypto_toolbox/crypto_toolbox.h"
+
+#include <vector>
namespace bluetooth {
namespace crypto_toolbox {
@@ -33,8 +32,8 @@ TEST(CryptoToolboxTest, bt_spec_test_d_1_test) {
uint8_t m[] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
- uint8_t aes_cmac_k_m[] = {
- 0x7d, 0xf7, 0x6b, 0x0c, 0x1a, 0xb8, 0x99, 0xb3, 0x3e, 0x42, 0xf0, 0x47, 0xb9, 0x1b, 0x54, 0x6f};
+ uint8_t aes_cmac_k_m[] = {0x7d, 0xf7, 0x6b, 0x0c, 0x1a, 0xb8, 0x99, 0xb3,
+ 0x3e, 0x42, 0xf0, 0x47, 0xb9, 0x1b, 0x54, 0x6f};
uint8_t output[16];
aes_context ctx;
@@ -168,8 +167,8 @@ TEST(CryptoToolboxTest, bt_spec_example_d_3_test) {
std::array<uint8_t, 7> a2{0x00, 0xa7, 0x13, 0x70, 0x2d, 0xcf, 0xc1};
Octet16 expected_ltk{0x69, 0x86, 0x79, 0x11, 0x69, 0xd7, 0xcd, 0x23, 0x98, 0x05, 0x22, 0xb5, 0x94, 0x75, 0x0a, 0x38};
- Octet16 expected_mac_key{
- 0x29, 0x65, 0xf1, 0x76, 0xa1, 0x08, 0x4a, 0x02, 0xfd, 0x3f, 0x6a, 0x20, 0xce, 0x63, 0x6e, 0x20};
+ Octet16 expected_mac_key{0x29, 0x65, 0xf1, 0x76, 0xa1, 0x08, 0x4a, 0x02,
+ 0xfd, 0x3f, 0x6a, 0x20, 0xce, 0x63, 0x6e, 0x20};
// algorithm expect all input to be in little endian format, so reverse
std::reverse(std::begin(dhkey_w), std::end(dhkey_w));
@@ -198,8 +197,8 @@ TEST(CryptoToolboxTest, bt_spec_example_d_4_test) {
Octet16 MacKey{0x29, 0x65, 0xf1, 0x76, 0xa1, 0x08, 0x4a, 0x02, 0xfd, 0x3f, 0x6a, 0x20, 0xce, 0x63, 0x6e, 0x20};
- Octet16 expected_aes_cmac{
- 0xe3, 0xc4, 0x73, 0x98, 0x9c, 0xd0, 0xe8, 0xc5, 0xd2, 0x6c, 0x0b, 0x09, 0xda, 0x95, 0x8f, 0x61};
+ Octet16 expected_aes_cmac{0xe3, 0xc4, 0x73, 0x98, 0x9c, 0xd0, 0xe8, 0xc5,
+ 0xd2, 0x6c, 0x0b, 0x09, 0xda, 0x95, 0x8f, 0x61};
// algorithm expect all input to be in little endian format, so reverse
std::reverse(std::begin(n1), std::end(n1));
@@ -245,8 +244,8 @@ TEST(CryptoToolboxTest, bt_spec_example_d_5_test) {
TEST(CryptoToolboxTest, bt_spec_example_d_6_test) {
Octet16 key{0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05, 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
std::array<uint8_t, 4> keyID{0x6c, 0x65, 0x62, 0x72};
- Octet16 expected_aes_cmac{
- 0x2d, 0x9a, 0xe1, 0x02, 0xe7, 0x6d, 0xc9, 0x1c, 0xe8, 0xd3, 0xa9, 0xe2, 0x80, 0xb1, 0x63, 0x99};
+ Octet16 expected_aes_cmac{0x2d, 0x9a, 0xe1, 0x02, 0xe7, 0x6d, 0xc9, 0x1c,
+ 0xe8, 0xd3, 0xa9, 0xe2, 0x80, 0xb1, 0x63, 0x99};
// algorithm expect all input to be in little endian format, so reverse
std::reverse(std::begin(key), std::end(key));
@@ -261,8 +260,8 @@ TEST(CryptoToolboxTest, bt_spec_example_d_6_test) {
TEST(CryptoToolboxTest, bt_spec_example_d_7_test) {
Octet16 IRK{0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05, 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
Octet16 prand{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x70, 0x81, 0x94};
- Octet16 expected_aes_128{
- 0x15, 0x9d, 0x5f, 0xb7, 0x2e, 0xbe, 0x23, 0x11, 0xa4, 0x8c, 0x1b, 0xdc, 0xc4, 0x0d, 0xfb, 0xaa};
+ Octet16 expected_aes_128{0x15, 0x9d, 0x5f, 0xb7, 0x2e, 0xbe, 0x23, 0x11,
+ 0xa4, 0x8c, 0x1b, 0xdc, 0xc4, 0x0d, 0xfb, 0xaa};
std::array<uint8_t, 3> expected_ah{0x0d, 0xfb, 0xaa};
// algorithm expect all input to be in little endian format, so reverse
@@ -284,8 +283,8 @@ TEST(CryptoToolboxTest, bt_spec_example_d_7_test) {
TEST(CryptoToolboxTest, bt_spec_example_d_8_test) {
Octet16 Key{0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05, 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
Octet16 SALT{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x74, 0x6D, 0x70, 0x31};
- Octet16 expected_aes_cmac{
- 0xfb, 0x17, 0x35, 0x97, 0xc6, 0xa3, 0xc0, 0xec, 0xd2, 0x99, 0x8c, 0x2a, 0x75, 0xa5, 0x70, 0x11};
+ Octet16 expected_aes_cmac{0xfb, 0x17, 0x35, 0x97, 0xc6, 0xa3, 0xc0, 0xec,
+ 0xd2, 0x99, 0x8c, 0x2a, 0x75, 0xa5, 0x70, 0x11};
// algorithm expect all input to be in little endian format, so reverse
std::reverse(std::begin(Key), std::end(Key));
@@ -301,8 +300,8 @@ extern Octet16 smp_calculate_ltk_to_link_key(const Octet16& ltk, bool use_h7);
// BT Spec 5.0 | Vol 3, Part H D.9
TEST(CryptoToolboxTest, bt_spec_example_d_9_test) {
Octet16 LTK{0x36, 0x8d, 0xf9, 0xbc, 0xe3, 0x26, 0x4b, 0x58, 0xbd, 0x06, 0x6c, 0x33, 0x33, 0x4f, 0xbf, 0x64};
- Octet16 expected_link_key{
- 0x28, 0x7a, 0xd3, 0x79, 0xdc, 0xa4, 0x02, 0x53, 0x0a, 0x39, 0xf1, 0xf4, 0x30, 0x47, 0xb8, 0x35};
+ Octet16 expected_link_key{0x28, 0x7a, 0xd3, 0x79, 0xdc, 0xa4, 0x02, 0x53,
+ 0x0a, 0x39, 0xf1, 0xf4, 0x30, 0x47, 0xb8, 0x35};
// algorithm expect all input to be in little endian format, so reverse
std::reverse(std::begin(LTK), std::end(LTK));
@@ -315,8 +314,8 @@ TEST(CryptoToolboxTest, bt_spec_example_d_9_test) {
// BT Spec 5.0 | Vol 3, Part H D.10
TEST(CryptoToolboxTest, bt_spec_example_d_10_test) {
Octet16 LTK{0x36, 0x8d, 0xf9, 0xbc, 0xe3, 0x26, 0x4b, 0x58, 0xbd, 0x06, 0x6c, 0x33, 0x33, 0x4f, 0xbf, 0x64};
- Octet16 expected_link_key{
- 0xbc, 0x1c, 0xa4, 0xef, 0x63, 0x3f, 0xc1, 0xbd, 0x0d, 0x82, 0x30, 0xaf, 0xee, 0x38, 0x8f, 0xb0};
+ Octet16 expected_link_key{0xbc, 0x1c, 0xa4, 0xef, 0x63, 0x3f, 0xc1, 0xbd,
+ 0x0d, 0x82, 0x30, 0xaf, 0xee, 0x38, 0x8f, 0xb0};
// algorithm expect all input to be in little endian format, so reverse
std::reverse(std::begin(LTK), std::end(LTK));
diff --git a/gd/docs/architecture/architecture.md b/gd/docs/architecture/architecture.md
deleted file mode 100644
index 2a4ec8cdf..000000000
--- a/gd/docs/architecture/architecture.md
+++ /dev/null
@@ -1,313 +0,0 @@
-# Gabeldorsche Architecture
-
-[TOC]
-
-This document outlines some architectural considerations we've made when
-developing the Gabeldorsche (GD) Bluetooth stack.
-
-## Threading model
-
-First of all, the GD stack does not build on concepts of threads. Instead, it
-works with [`Handlers`](#handler). However, since GD ultimately runs on an OS,
-it still needs to interact with processes and threads before achieving the
-[`Handler`](#handler) abstraction.
-
-### Processes
-
-In general. three types of processes exist in the GD runtime environment:
-
-**Application processes**
-: include third-party apps, other system components such as audio and telecom
- services that interact with the _Bluetooth stack process_ APIs defined
- through various RPC/IPC methods such as Binder, Socket IPC, gRPC, DBUS. and
- so on, using languages such as AIDL or Protobuf. For Android applications,
- although APIs are defined in AIDL, some boiler plate code is wrapped in Java
- libraries exposed through code in
- [`frameworks/base/core/java/android/bluetooth`](https://android.googlesource.com/platform/frameworks/base/+/refs/heads/master/core/java/android/bluetooth/)
- that is released to developers as
- [Android SDK](https://developer.android.com/guide/topics/connectivity/bluetooth).
-
-**Hardware abstraction layer (HAL) processes**
-: one or many processes from the vendor partition, and hence is hardware
- depenedent. They interact with the _Bluetooth stack process_ via a set of
- hardware abstraction APIs defined through RPC/IPC methods such as Binder,
- Socket IPC, DBUS, and so on, using languages such as HIDL. On Android, this
- would be HAL processes that implement HIDL APIs such as
- [IBluetoothHci](https://android.googlesource.com/platform/hardware/interfaces/+/refs/heads/master/bluetooth/1.1/IBluetoothHci.hal)
- and
- [IBluetoothAudioProvider](https://android.googlesource.com/platform/hardware/interfaces/+/refs/heads/master/bluetooth/audio/2.0/IBluetoothAudioProvider.hal).
-
-**Bluetooth stack process**
-: typically one single process that implements various Bluetooth protocols and
- profiles above the Host Controller Interface (HCI) and below the Bluetooth
- SDK APIs. On one hand, it servces the requests from _Application processes_;
- on the other hand, it forwards these requests via interactions with _HAL
- processes_. On Android, this process typically runs under AID_BLUETOOTH
- (usually 1002) with process name "com.android.bluetooth". The process is
- started in Java and loads native libraries through JNI. Other systems that
- do not use Java virtual machine may have a pure native process. Multiple
- threads may exist in this process for various reasons. The GD stack runs
- entirely in this process.
-
-### Threads in Bluetooth stack process
-
-Currently, the goals of thread optimization in the Bluetooth stack are:
-
-* Reduce the number of threads as much as possible to simplify synchronization
-* Do blocking I/O operations in separate threads
-* Try moving I/O operations into polling mode so that we can use event driven
- methods to interact with it on main thread
-* Move alarm and timer mechanisms to their calling threads to avoid a separate
- alarm thread
-* Isolate individual components so that each component can be started and
- stopped individually without terminating the main thread
-* Prefer data passing over data sharing among threads to reduce locking and
- race conditions
-
-After above optimization, we are left with five main types of threads within the
-native code:
-
-**Main thread**
-: The main workhorse in the Bluetooth stack. The thread's execution context is
- further divided into [`Handlers`](#handler) that reside in individual
- [`Modules`](#module). This thread can be divided further into smaller ones
- if performance is constrained on the running platform. Deployer just needs
- to bind handlers to different threads and that should not affect the overall
- operation.
-
-**JNI thread**
-: In the native thread, we treat the Java layer as a separate application as
- its threading module is completely different. Therefore, we put a thread
- between these two layers to buffer any blocking operation.
-
-**HCI thread (or other HW I/O thread)**
-: This thread is responsible for deadling with hardware I/O and can be
- potentially blocking. Hence it has its separate thread to avoid blocking the
- main thread.
-
-**Audio worker thread**
-: Responsible for audio encoding and decoding operations that require higher
- precision execution timing. Such worker has its separate thread to avoid
- being affected by the main thread.
-
-**Socket I/O thread**
-: Communicate with various applications that uses the
- [`BluetootSocket`](https://developer.android.com/reference/android/bluetooth/BluetoothSocket)
- interface. It has its sepearate thread due to potential I/O delay.
-
-### Data flow diagram
-
-Function invocations between different components are abstracted as control
-packets (function closure) passed through queues. Data flow between components
-are data packets sent through queues, signaled using [`Reactor`](#reactor). They
-will merge to the input queue for each component. We define three types of
-queues:
-
-**Non-blocking queue**
-: When users try to dequeue when it’s empty, or enqueue when it’s full, it
- will return immediately. All queueing within a thread must be non-blocking,
- because otherwise it will deadlock.
-
-**Blocking queue**
-: When users try to dequeue when it’s empty, or enqueue when it’s full, it
- will block, until other thread makes the queue to be writable/readable. It
- can be used as a flow control mechanism to avoid too many packets from user
- thread.
-
-**Leaky queue**
-: Same as non-blocking queue, but it will flush when it’s full and user tries
- to enqueue. This is useful for audio encoding.
-
-![Threading Model](./data_flow_diagram.png)
-
-## Building blocks
-
-### Module {#module}
-
-Code in GD is packed into C++ objects called
-[`Module`](https://android.googlesource.com/platform/system/bt/+/master/gd/module.h).
-A module standardized the following aspects of GD code:
-
-* **Dependencies**: A module provides its own dependencies on other modules by
- implementing `ListDependencies()`
-* **Life Cycle**: A module must implement `Start()` and `Stop()` life cycle
- methods
-* **Threading Module**: The `Module` base class provides a `Handler` for code
- execution context via `GetHandler()`
-* **Metrics**: A `Module` can dump its state information for dumpsys through
- `DumpState()`
-
-See its definition at: https://android.googlesource.com/platform/system/bt/+/master/gd/module.h
-
-### Handler {#handler}
-
-Similar to
-[`android.os.Handler`](https://developer.android.com/reference/android/os/Handler),
-[`bluetooth::os::Handler`](https://android.googlesource.com/platform/system/bt/+/master/gd/os/handler.h)
-provides a sequential execution context while hiding the concept of thread from
-the executing code.
-
-By scoping execution context into smaller areas, `Handler` benefits development
-in the following ways:
-
-* Less need for locking due to sequential execution context
-* Smaller context leads to easier management of code flow
-* Separation from thread gives system deployer more freedom to tweak the
- underlying thread allocation. For example, for real time OS without full
- thread implementation, a `Handler` can be used to provide a near-thread
- execution context
-
-Of course, there are downsides of using `Handler`, which developers should be
-cautious about:
-
-WARNING: Although multiple `Handler` could bind to the same thread, `Handler`
-does not gurantee sequential execution of code across different `Handler` even
-when the are on the same thread.
-
-WARNING: Locking among `Handlers` that were bound to the same thread may result
-in deadlock
-
-WARNING: Data must be copied between `Handler` to avoid both deadlock and race
-condition
-
-See its definition at: https://android.googlesource.com/platform/system/bt/+/master/gd/os/handler.h
-
-### Reactor {#reactor}
-
-[`bluetooth::os:Reactor`](https://android.googlesource.com/platform/system/bt/+/master/gd/os/reactor.h)
-implements the
-[Reactor Design Pattern](https://en.wikipedia.org/wiki/Reactor_pattern), in
-which concurrent _Events_ are demultiplexed by a _Synchronous Event
-Demultiplexer_ to a list of _Request Handlers_ registered through a
-_Dispatcher_.
-
-In a generic Linux operating system, such as Android, we implemented it using
-file descriptors such as
-[eventfd](http://man7.org/linux/man-pages/man2/eventfd.2.html) for `Handler`,
-[timerfd](http://man7.org/linux/man-pages/man2/timerfd_create.2.html) for
-`Alarm`, and [socketfd](http://man7.org/linux/man-pages/man2/socket.2.html) for
-data processing pipelines. In the context of file descriptors, events are
-catigorized into two types:
-
-* **OnReadReady**: means that the demultiplexer has some events for the
- handler and the handler can read at least one event from the underlying
- event queue. This is often associated with `EPOLLIN`, `EPOLLHUP`,
- `EPOLLRDHUP`, and `EPOLLERR`.
-* **OnWriteReady**: means that the demultiplexer is ready to consume more
- events from this handler, and the handler can write at least one event to
- the underlying queue. this is often associated with `EPOLLOUT`.
-
-This pattern naturally creates a back pressure from one queue to another without
-any extra signaling mechanism. When used in networking stack like ours, it
-simplifies the signaling code flow.
-
-See its definition at:
-https://android.googlesource.com/platform/system/bt/+/master/gd/os/reactor.h
-
-A pure data use case of `Reactor` is a `Reactive Queue`, see its definition at:
-https://android.googlesource.com/platform/system/bt/+/master/gd/os/queue.h
-
-## Packet Definition Language (PDL)
-
-Packet parsing and serialization has been a big part of any networking stack. It
-is usually the first snippet of code that interface with a remote device. In the
-past, this has been achieved manually using macros like `STREAM_TO_UNIT8` or
-`UINT8_TO_STREAM`. This manual method is tedious and errorprone. To fix this, we
-created a Packet Definition Language that defines networking packet structure to
-the bits level. C++ headers and Python bindings will be automatically generated
-from its code generator and any fixes to the code generator will apply
-systematically to all packet code generated.
-
-Example PDL:
-
-```
-// Comments
-little_endian_packets // Whether this packet is big or small endian
-
-// Include header from other C++ header files
-custom_field SixBytes : 48 "packet/parser/test/" // expect six_bytes.h
-custom_field Variable "packet/parser/test/" // expect variable.h
-
-// A packet
-packet Parent {
- _fixed_ = 0x12 : 8, // fixed field 0x12 that takes 8 bits
- _size_(_payload_) : 8, // Size field that takes 8 bits
- _payload_, // special payload field of variable size
- footer : 8, // fiexed size footer of 8 bits
-}
-
-packet Child : Parent {
- field_name : 16, // addition field append after Parent
-}
-
-// an enum of 4 bits
-enum FourBits : 4 {
- ONE = 1,
- TWO = 2,
- THREE = 3,
- FIVE = 5,
- TEN = 10,
- LAZY_ME = 15,
-}
-```
-
-See its documentation at:
-https://android.googlesource.com/platform/system/bt/+/master/gd/packet/parser/README
-
-## Calling convention between modules
-
-### Asynchronous server-client model
-
-For most communication among modules, developers should assume an asynchronous
-server-client model in a generic model like:
-
-```c++
-// Define callback function type
-using CallbackFunction = std::function<void(ParamType)>;
-
-// Asynchronous method definition
-bool Foo(Parameter param, CallbackFunction callback);
-
-// A new callback is passed for each asynchronous call
-// Always prefer lambda over std::bind
-CallbackFunction callback = [this] {
- // do something
-};
-Parameter param = {
- // something
-};
-if (Foo(param, callback)) {
- // The callback will be invoked
- // Callback must be invoked in the future
-} else {
- // Failed, no need to wait
-}
-```
-
-Many protocols and profiles fit into such model such as `AclManager` and
-`L2cap`.
-
-### Synchronous database model
-
-In some cases, an asynchronous server-client model is not feasible. In this
-case, developers can consider a synchronous database model. In such a model,
-operations can happen synchronously with help of mutex. When the method returns,
-the changes must be reflected to all dependencies. Any changes in the internal
-states must be applied atomically.
-
-```c++
-// Synchronous method definition
-void Foo(Parameter param, Output* output);
-int Bar(Parameter param);
-Parameter param = {
- // something
-};
-Output output = {};
-Foo(param, &output);
-// output can be used immediately
-int bar_output = Bar(param);
-// bar_output can be used immediately
-```
-
-Many storage and informational modules fit into this model such as `Metrics` and
-`Storage`.
diff --git a/gd/docs/architecture/data_flow_diagram.png b/gd/docs/architecture/data_flow_diagram.png
deleted file mode 100644
index 788b8eea5..000000000
--- a/gd/docs/architecture/data_flow_diagram.png
+++ /dev/null
Binary files differ
diff --git a/gd/docs/architecture/style_guide.md b/gd/docs/architecture/style_guide.md
deleted file mode 100644
index 1711dc7c1..000000000
--- a/gd/docs/architecture/style_guide.md
+++ /dev/null
@@ -1,207 +0,0 @@
-# Gabeldorsche Style Guide
-
-[TOC]
-
-## Base
-
-In general, when not mentioned in this document, developers should follow the
-Google C++ and Google Java style guide as much as possible.
-
-### Google C++ Style Guide
-
-C++ Style Guide: https://google.github.io/styleguide/cppguide.html
-
-### Android and Google Java Style Guide
-
-1. Android Java Style Guide:
- https://source.android.com/setup/contribute/code-style
-
-2. when not covered by (1), see External Java Style Guide:
- https://google.github.io/styleguide/javaguide.html
-
-line length limit is 120 characters for C++ and Java
-
-### Python Style Guide
-
-The GD stack uses the Google Python Style Guide:
-
-* http://google.github.io/styleguide/pyguide.html
-
-with the following modifications as shown in the
-[.style.yapf](https://android.googlesource.com/platform/system/bt/+/refs/heads/master/.style.yapf) definition:
-
-```yapf
-based_on_style: google
-indent_width: 4
-column_limit: 120
-```
-
-## Build files
-
-* One build target for the entire stack in system/bt (i.e. one cc_library())
- * If only part of the stack needs to be compiled, configure it using the
- “target†configuration in Android.bp
-* One build target for all unit tests (i.e. one cc_test)
-* When needed, filgroup() can be created in Android.bp in sub-directories. The
- main build target should use these filegroups() to build the main output
- library.
-* All targets must have host_supported == true unless it is dependent on the
- OS
-* If the stack needs to be compiled using other build system, then the build
- files should also live in system/bt
-
-## Namespace and include
-
-* Namespace must follow directory names
-* Top level namespace for internal code is “bluetoothâ€
-* Top level namespace for externally visible code is “android::bluetoothâ€
-* Include path must be relative to the root directory of the stack. Normally
- it is system/bt, for GD refactor code, it is system/bt/gd
-
-## Multiple implementations of the same header
-
-Since GD interact with many lower level components that are platform dependent,
-frequently there is need to implement the same header multiple times for
-different platform or hardware. When doing this:
-
-* Avoid #define macros as much as possible. Instead put code into different
- source files and selectively compile them for different targets.
-* Convention of operating system used:
- * android/
- * All Android devices that use HIDL
- * linux/
- * All non-Android linux devices
- * linux_generic/
- * Android and non-Android linux devices
-
-## Directory structure
-
-Root directory under Android tree:
-[**system/bt/gd/**](https://android.googlesource.com/platform/system/bt/+/refs/heads/master/gd/)
-
-* Directory structure should be as flat as possible
-* Each file should contain at most one class
-* Header, source code, and unit test should live in the same directory with
- the following naming guideline:
- * Source: bb.cc
- * Header: bb.h
- * Test: bb_test.cc
-* Each profile should have its own directory and module
-* Source and sink, server and client profiles should live in two sub folders
- of the same common directory where common code can be stored. However,
- source and sink must have separate modules
-* Module file is also the external API header
-* Prefer underscore over dashes
-
-### Example: utility library with OS dependent implementation
-
-* os/: OS dependent classes such as Alarm, Thread, Handler
- * Android.bp: Build file that defines file groups that would include
- different source files based on compile time target
- * alarm.h: common header for alarm
- * linux_generic/: Implementations for generic Linux OS
- * alarm.cc: Linux generic implementation of alarm.h using timer_fd
- * alarm_test.cc: unit test for alarm.h
- * fuzz/: library needed for fuzz tests in the os/ library
-
-### Example: module with hardware dependent implementation
-
-* hal/: Hardware abstraction layer such as HCI interfaces, Audio interfaces
- * Android.bp: Build file that defines file groups that would include
- different source files based on compile time target
- * hci_hal.h: common library header
- * hci_hal_android_hidl.cc: implementation of hci_hal.h using Android HIDL
- * hci_hal_android_hidl_test.cc: unit tests for the Android HIDL
- implementation
- * hci_hal_host.cc: implementation of hci_hal.h using root-canal
- emulator or linux Bluetooth HCI socket
- * hci_hal_host_test.cc: unit tests for the socket based HAL (root-canal)
- emulator implementation
- * facade.proto: gRPC automation interface definition for this layer
- * facade.h/cc: an implementation of the above gRPC interface for the GD
- stack
- * cert/: certification tests for this module
- * fuzz/: library needed for fuzz tests in the hal/ module
-
-### Example: similar protocol with the same base
-
-* l2cap/: L2CAP layer, splitted among classic and LE
- * classic/: Classic L2CAP module
- * cert/: certification tests for this module
- * internal/: internal code to be used only in classic
- * Source code and headers being exported to other modules
- * le/: LE L2CAP module
- * cert/: certification tests for this module
- * internal/: internal code to be used only in classic
- * Source code and headers being exported to other modules
- * internal/: L2CAP internal code that should not be used by sources
- outside L2CAP
- * data_pipeline_manager.h
- * data_pipeline_manager.cc
- * data_pipeline_manager_mock.h: Mock of this class, used in unit tests
- * dynamic_channel_allocator.h
- * dynamic_channel_allocator.cc
- * dynamic_channel_allocator_test.cc: GTest unit test of this class
- * dynamic_channel_allocator_fuzz_test.cc: Fuzz test of this class
- * *.h/.cc: Common headers and sources that is exposed to other modules
-
-### Example: protocol or profiles with client and server side implementations
-
-* a2dp/: A2DP profile
- * sink/: A2DP sink module (e.g. headset)
- * source/: A2DP source module (e.g. phone)
-* avrcp/
- * controller/: AVRCP peripheral module (e.g. carkit)
- * target/: AVRCP target module (e.g. Phone)
-* hfp/
- * hf/: Handsfree device (e.g. headset)
- * ag/: Audio gateway (e.g. phone)
-
-## External libraries
-
-To maintain high portability, we are trying to stick with C++ STL as much as
-possible. Hence, before including an external library, please ask the team for
-review.
-
-Examples of currently used libraries:
-
-* boringssl: Google's openssl implementation
-* small parts of libchrome, to be removed or replaced eventually
- * base::OnceCallback
- * base::Callback
- * base::BindOnce
- * base::Bind
-* google-breakpad: host binary crash handler
-* libbacktrace: print stacktrace on crash on host
-
-## Exposed symbols
-
-Given that entire Fluoride library is held in libbluetooth.so dynamic library
-file, we need a way to load this library and extract entry points to it. The
-only symbols that should be exposed are:
-
-* An entry point to a normal running adapter module libbluetooth.so
-* A header library to all exposed API service to profiles and layers
-* An entry point to a certification interface, libbluetooth\_certification.so
-* A header library to this certification stack
-
-## Logging
-
-Gabeldorsche uses `printf` style logging with macros defined in `os/log.h`. Five
-log levels are available.
-
-* LOG_VERBOSE(fmt, args...): Will be disabled by default
-* LOG_INFO(fmt, args...): Will be disabled by default
-* LOG_INFO(fmt, args...): Enabled
-* LOG_WARN(fmt, args...): Enabled
-* LOG_ERROR(fmt, args...): Enabled
-* LOG_ALWAYS_FATAL(fmt, args...): Enabled, will always crash
-* ASSERT(condition): Enabled, will crash when condition is false
-* ASSERT_LOG(conditon, fmt, args...): Enabled, will crash and print log when
- condition is false
-
-In general, errors that are caused by remote device should never crash our stack
-and should be logged using LOG_WARN() only. Recoverable errors due to our stack
-or badly behaved bluetooth controller firmware should be logged using
-LOG_ERROR() before recovery. Non-recoverable errors should be logged as
-LOG_ALWAYS_FATAL() to crash the stack and restart.
diff --git a/gd/docs/testing/cert_test.md b/gd/docs/testing/cert_test.md
deleted file mode 100644
index ef6968164..000000000
--- a/gd/docs/testing/cert_test.md
+++ /dev/null
@@ -1,254 +0,0 @@
-# Gabeldorsche Certification Tests
-
-[TOC]
-
-## What is GD cert test
-
-A core problem behind Bluetooth interoperability testing is testers' inability to
-automate test operations on certain peripherals. For example, although an user
-can automate API calls on Android with tools like
-[SL4A](https://android.googlesource.com/platform/external/sl4a/) or ADB shell
-commands, they often struggle with automating corresponding operations on
-carkits, headsets, and smart watches. Even if they find a way to automatically
-control one model of such peripheral device using device maker's tools or
-self-developed after-market tools such as relays and robotic arms, such kind of
-tool usually does not scale to other models of peripherals due to their
-differences in physical user interfaces.
-
-GD certification test framework comes into rescue. In
-the framework, a common API is defined using a [gRPC](https://grpc.io/) protobuf
-for profiles such as HFP, AVRCP and function groups like pairing, scanning, and
-advertising. Everyone who wants to test their Bluetooth device implements an
-**gRPC Facade Server** using this protobuf definition. This server executable is
-responsible in gluing various gRPC based APIs with their device specific
-automation hook through a **Device Specific Driver**. The server will then
-expose an IP address and a port number to the test runner. A **Test Runner**
-process will load and execute the actual test case and use the auto-generated
-gRPC facade client APIs to interact with the device being tested. The following
-diagram shows how the system could be configured:
-
-![cert_test_architecture_drawing](./cert_test_architecture_drawing.png)
-
-## Terminology
-
-**gRPC Facade**
-: A set of automation APIs of a specific profile (HFP, AVRCP, etc) or function
- group (pairing, scanning, advertising, etc) defined in gRPC protobuf format.
-
-**Test Runner**
-: A process that loads and runs the actual test cases and use auto-generated
- gRPC facade client library to interact with test devices. Currently, the
- preferred test runner is the [Android ACTS](https://android.googlesource.com/platform/tools/test/connectivity/+/refs/heads/master/acts/)
- framework and test cases are written in Python for fast iteration and easy debugging
-
-**gRPC Facade Server**
-: A concrete implementation of the gRPC automation APIs, which will convert
- RPC requests into invocations of device specific automation hook using a
- **Device Specific Driver**. This server can be written in any language and
- on any platform. The server need to expose an IP address and 3 ports
-
-**Tester Signal Port**
-: A port to indicate that the server is ready for operation to the **Test
- Runner**
-
-**gRPC Root Server Port**
-: A port that allows **Test Runner** to start and stop various functional
- facade services
-
-**gRPC Facade Server Port**
-: A port that allows **Test Runner** to interact with actual profile
- implementations on the test device
-
-**Device Specific Driver**
-: A library or some mechanism that allows the **gRPC Facade Server** to
- control the test device. This library is opaque to the **Test Runner** that
- should have no knowledge of how this component works * **Root-Canal**: A
- Bluetooth PHY emulator that takes either LMP or HCI packets. The goal is for
- this emulator to simulate a Physical RF environment without using any real
- Bluetooth adatper.
-
-## How to run GD cert test in Android tree
-
-Assume user has an Android checkout and finished `source build/envsetup.sh` and
-`lunch` to a preferred target
-
-### Run GD cert tests on host machine
-
-```shell
-$ANDROID_BUILD_TOP/system/bt/gd/cert/run --host
-```
-
-#### Python 3.8+
-The cert tests require >python3.8 to operate and the associated python
-virtualenv package. The script may help properly install these requisites.
-
-```shell
-source $ANDROID_BUILD_TOP/system/bt/gd/cert/set_up_virtualenv.sh
-```
-
-### Run GD cert tests on devices for the first time
-
-Connect at least two Android devices and follow on-screen instructions after
-running the following command
-
-```shell
-$ANDROID_BUILD_TOP/system/bt/gd/cert/set_up_and_run_device_cert.sh
-```
-
-### Run GD cert tests on devices for the second time and after
-
-Keeping the same set of devices connected
-
-```shell
-$ANDROID_BUILD_TOP/system/bt/gd/cert/run
-```
-
-### `system/bt/gd/cert/run` command reference
-
-* `--host`: Run tests on host only using `root-canal`
-* `--clean`: Remove any test setup files and do a clean test run
-* `--repeat=N`: Repeat running the same set of tests N times without redoing
- test setup
-* `--test_file=<file_name>`: Running only tests listed in `<file_name>`
-* `--test_filter=<test_filter>`: Test case filter in the format of
- "TestClass:test_case_name", for multiple test cases, quote them using " and
- separate each filter by space such as "TestClass1:test_case_1
- TestClass2:test_case_2"
-
-### Run GD cert tests on devices over SSH
-
-The following assumptions assume the following configuration
-
-* Local setup: Linux or MAC laptop with two Android phones connected
-* Remote setup: Linux or MAC workstation
-
-1. Check if your ADB version is up to date on both host machine and remote
- workstation. Both versions should be 29.0.3 or above. If not, uninstall and
- reinstall your adb.
-
-1. Enable SSH port forwarding for both ADB port and various ports used by our
- tests, run the following command on your Mac, assuming the following
- configuration {value=2}
-
- * ADB Port: 5037
- * Cert Device:
- * gRPC Root Server Port: 8896
- * gRPC Facade Port: 8898
- * Signal Port: 8894
- * Device Under Test:
- * gRPC Root Server Port: 8897
- * gRPC Facade Port: 8899
- * Signal Port: 8895
-
- Among these ports, ADB Port needs to be forwarded from local machine to
- listen on remote workstation so that its adb client can connect to local
- machine's adb server (`ssh -R`). Signal Port needs to be forwarded from
- remote workstation to listen on local machine so that local phone can
- connect to Test Runner listening on this port during Facade Server bring up
- (`ssh -L`). Both gRPC Root Server Port and gRPC Facade Port need to be
- forwarded from local machine to listen on remote workstation so that Test
- Runner can connect to these ports on the Facade Server (`ssh -R`).
-
- Hence, the resulting `ssh` command is:
-
- ```shell
- ssh -R 5037:127.0.0.1:5037 -R 6401:127.0.0.1:6401 -R 6402:127.0.0.1:6402 \
- -R 6403:127.0.0.1:6403 -L 8894:127.0.0.1:8894 -L 8895:127.0.0.1:8895 \
- -R 8896:127.0.0.1:8896 -R 8897:127.0.0.1:8897 -R 8898:127.0.0.1:8898 \
- -R 8899:127.0.0.1:8899 <host_name>
- ```
-
-1. Connect all your devices, open a different terminal on your Mac and run
-
- ```shell
- adb kill-server && adb devices
- ```
-
- You should see devices on your local machine shows up
-
-1. SSH into your remote workstation and run
-
- ```shell
- adb kill-server && adb devices
- ```
-
- You should see same set of devices connected to your local machine
-
-1. Continue with device setup
-
- ```shell
- $ANDROID_BUILD_TOP/system/bt/gd/cert/set_up_and_run_device_cert.sh
- ```
-
-1. In subsequent runs
-
- ```shell
- $ANDROID_BUILD_TOP/system/bt/gd/cert/run
- ```
-
-## How to debug GD cert tests
-
-Logs are produced and saved whenever GD cert tests runs. Depending on how the
-tests were run, the log root is different
-
-When running tests on local Android checkout, logs or most recent run are stored
-at
-
-* /tmp/logs/HostOnlyCert/latest
-
-Navigate test logs
-
-In test root, the following logs are available:
-
-* In every directory layer:
- * test_run_debug.txt: DEBUG level output from Python logging API
- scoped at their respective layer based on the directory
-* In test root directory:
- * test_summary.json: A summary test results, including stack traces
- for any failures and metadata
- * test_configs.json: The ACTs config used to run this test
- * GdDevice_cert_stack_backing_process_coverage_summary.txt: code
- coverage summary from llvm-cov
-* In test class directory:
- * rootcanal_logs.txt: Root-Canal stdout and stderrr, host test only
- * Cert stack logs:
- * GdDevice_cert_stack_backing_logs.txt: facade server process log
- * cert_stack_btsnoop_hci.log: HCI packet log on cert device
- * cert_stack_system_log: Android phone logcat output, device based
- test only
- * Device under test logs:
- * GdDevice_stack_under_test_backing_logs.txt: facade server
- process log
- * stack_under_test_btsnoop_hci.log: HCI packet log on cert device
- * stack_under_test_system_log: Android phone logcat output, device
- based test only
- * Individual test directories: logs for individual test cases
-
-## PTS test case coverage
-
-A Python decorator is used to indicate a test's association with a Bluetooth SIG
-Profile Tuning Suite (PTS) Qualification test. For example
-
-```python
-@metadata(
- pts_test_id="L2CAP/EXF/BV-01-C",
- pts_test_name="Extended Features Information Response for "
- "Enhanced Retransmission Mode")
-```
-
-These information can be found at the Test Case Reference List (TCRL) document
-in
-[Qualification Test Requirements](https://www.bluetooth.com/specifications/qualification-test-requirements/)
-page at the Bluetooth SIG website.
-
-## Code coverage
-
-If the facade server binary is compiled using [`clang`](https://clang.llvm.org/)
-and with
-[`-fprofile-instr-generate -fcoverage-mapping`](https://clang.llvm.org/docs/SourceBasedCodeCoverage.html)
-flags. A `.profraw` file will be generated in ech test class log directory after
-the test run. The Test Runner will then try to index these profiling data using
-[`llvm-profdata`](https://llvm.org/docs/CommandGuide/llvm-profdata.html),
-iteratively merge them from each test class, and generate a line-by-line test
-coverage report using
-[`llvm-cov`](https://llvm.org/docs/CommandGuide/llvm-cov.html).
diff --git a/gd/docs/testing/cert_test_architecture_drawing.png b/gd/docs/testing/cert_test_architecture_drawing.png
deleted file mode 100644
index de4903558..000000000
--- a/gd/docs/testing/cert_test_architecture_drawing.png
+++ /dev/null
Binary files differ
diff --git a/gd/docs/testing/gtest.md b/gd/docs/testing/gtest.md
deleted file mode 100644
index b1aa77932..000000000
--- a/gd/docs/testing/gtest.md
+++ /dev/null
@@ -1,283 +0,0 @@
-# GTest Unit Tests
-
-[TOC]
-
-## GTest Unit Tests
-
-[GTest](https://github.com/google/googletest) is a Google developed open source
-unit testing framework for C++ and C code. As the majority of GD code is writeen
-in C++, GTest provide the first layer of defence against bugs from the
-implementation level. Used in combination with
-[GMock](https://github.com/google/googlemock) developers can easily isolate
-classes and functions from their code to conduct unit testing.
-
-* [GTest Primer](https://github.com/google/googletest/blob/master/googletest/docs/primer.md)
-* [GMock for Dummies](https://github.com/google/googletest/blob/master/googlemock/docs/for_dummies.md)
-
-### Test Binary
-
-All Gd unit test classes are compiled into a single binary
-[bluetooth_test_gd](https://android.googlesource.com/platform/system/bt/+/master/gd/Android.bp).
-
-### Test Sources Definitions
-
-* Tests should live in the same directory as the source code
-* Mocks should live in the same directory as the source header so that it can
- be shared among multiple tests
-* Tests should not modify global states that would affect other tests, so that
- all tests could be executed using the same binary
-* Each module can define a filegroup() that includes all test sources. This
- filegroup is then included in a single cc_test() target that produce a
- single test binary
- [bluetooth_test_gd](https://android.googlesource.com/platform/system/bt/+/master/gd/Android.bp).
- A single test binary simplifies the configuration effort needed for
- compilation, presubmit and postsubmit execution, and so on.
-
-### How to run tests
-
-#### Use `atest`
-
-[ATest](https://source.android.com/compatibility/tests/development/atest) is an
-Android tool that allows a developers to run multiple modes of tests from the
-same `atest` command, including Java Instrumentation Tests, C/C++ GTests,
-CTS/GTS tests, etc. To use `atest` with GD, simplying sync your Android tree,
-run `source build/envsetup.sh` and `lunch` to a desired target. Then
-
-* To run tests on device, the following command will automatically build,
- push, and execute tests on a connected Android device
-
- ```shell
- atest bluetooth_test_gd
- ```
-
-* To run tests on host, the following command will automatically build and run
- tests on your host machine
-
- ```shell
- atest --host bluetooth_test_gd
- ```
-
-* To run a single test case, use `<test_binary>:<test_class>#<test_method>`
- format, such as
-
- ```shell
- atest --host bluetooth_test_gd:AclManagerTest#invoke_registered_callback_connection_complete_success
- ```
-
- See `atest --help` for more documentation on how to use atest to run various
- tests
-
-#### Run it yourself (Not receommended unless really needed)
-
-Sometimes, you may want to execute the test binary directly because you want to
-attach a debugger or you want to avoid the test boostrap delay in `atest`. You
-can do it with the following steps
-
-1. Sync Android tree, run `build/envsetup` and `lunch` desired target, `cd`
- into Android checkout root directory
-
-1. Make bluetooth_test_gd binary
-
- ```shell
- m -j40 bluetooth_test_gd
- ```
-
-1. Run the test on host {value=3}
-
- ```shell
- $ANDROID_HOST_OUT/nativetest64/bluetooth_test_gd/bluetooth_test_gd
- ```
-
-1. Run the test on device {value=4}
-
- Push test to device
-
- ```shell
- adb push $ANDROID_PRODUCT_OUT/testcases/bluetooth_test_gd/arm64/bluetooth_test_gd /data/nativetest64/bluetooth_test_gd
- ```
-
- Run test using ADB
-
- ```shell
- adb shell /data/nativetest64/bluetooth_test_gd
- ```
-
-1. Run test with filter (Works the same way for device based test) {value=5}
-
- ```shell
- $ANDROID_HOST_OUT/nativetest64/bluetooth_test_gd/bluetooth_test_gd --gtest_filter=AclManagerTest.invoke_registered_callback_connection_complete_success*
- ```
-
- Note: the '*' wildcard is very important
-
-1. Get command line help {value=6}
-
- ```shell
- $ANDROID_HOST_OUT/nativetest64/bluetooth_test_gd/bluetooth_test_gd --help
- ```
-
-### Example: L2capClassicFixedChannelImplTest
-
-Note: All paths are relative to
-[system/bt/gd](https://android.googlesource.com/platform/system/bt/+/master/gd)
-
-#### Source code:
-
-* [l2cap/classic/internal/fixed_channel_impl.h](https://android.googlesource.com/platform/system/bt/+/master/gd/l2cap/classic/internal/fixed_channel_impl.h)
-
-```c++
-#pragma once
-
-#include "common/bidi_queue.h"
-#include "l2cap/cid.h"
-#include "l2cap/classic/fixed_channel.h"
-#include "l2cap/internal/channel_impl.h"
-#include "l2cap/l2cap_packets.h"
-#include "os/handler.h"
-#include "os/log.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace classic {
-namespace internal {
-
-class Link;
-
-class FixedChannelImpl : public l2cap::internal::ChannelImpl {
- public:
- FixedChannelImpl(Cid cid, Link* link, os::Handler* l2cap_handler);
- virtual ~FixedChannelImpl() = default;
- hci::Address GetDevice() const;
- virtual void RegisterOnCloseCallback(os::Handler* user_handler, FixedChannel::OnCloseCallback on_close_callback);
- virtual void Acquire();
- virtual void Release();
- virtual bool IsAcquired() const;
- virtual void OnClosed(hci::ErrorCode status);
- virtual std::string ToString();
- common::BidiQueueEnd<packet::BasePacketBuilder, packet::PacketView<packet::kLittleEndian>>* GetQueueUpEnd();
- common::BidiQueueEnd<packet::PacketView<packet::kLittleEndian>, packet::BasePacketBuilder>* GetQueueDownEnd();
- Cid GetCid() const;
- Cid GetRemoteCid() const;
- private:
- // private fields omitted in doc ...
-};
-
-} // namespace internal
-} // namespace classic
-} // namespace l2cap
-} // namespace bluetooth
-```
-
-* [system/bt/gd/l2cap/classic/internal/fixed_channel_impl.cc](https://android.googlesource.com/platform/system/bt/+/master/gd/l2cap/classic/internal/fixed_channel_impl.cc)
-
-#### Mocks for dependencies' unit tests
-
-* [l2cap/classic/internal/fixed_channel_impl_mock.h](https://android.googlesource.com/platform/system/bt/+/master/gd/l2cap/classic/internal/fixed_channel_impl_mock.h)
-
-```c++
-#pragma once
-
-#include "l2cap/classic/internal/fixed_channel_impl.h"
-
-#include <gmock/gmock.h>
-
-// Unit test interfaces
-namespace bluetooth {
-namespace l2cap {
-namespace classic {
-namespace internal {
-namespace testing {
-
-class MockFixedChannelImpl : public FixedChannelImpl {
- public:
- MockFixedChannelImpl(Cid cid, Link* link, os::Handler* l2cap_handler) : FixedChannelImpl(cid, link, l2cap_handler) {}
- MOCK_METHOD(void, RegisterOnCloseCallback,
- (os::Handler * user_handler, FixedChannel::OnCloseCallback on_close_callback), (override));
- MOCK_METHOD(void, Acquire, (), (override));
- MOCK_METHOD(void, Release, (), (override));
- MOCK_METHOD(bool, IsAcquired, (), (override, const));
- MOCK_METHOD(void, OnClosed, (hci::ErrorCode status), (override));
-};
-
-} // namespace testing
-} // namespace internal
-} // namespace classic
-} // namespace l2cap
-} // namespace bluetooth
-```
-
-#### Tests
-
-* [l2cap/classic/internal/fixed_channel_impl_test.cc](https://android.googlesource.com/platform/system/bt/+/master/gd/l2cap/classic/internal/fixed_channel_impl_test.cc)
-
-```c++
-#include "l2cap/classic/internal/fixed_channel_impl.h"
-
-#include "common/testing/bind_test_util.h"
-#include "l2cap/cid.h"
-#include "l2cap/classic/internal/link_mock.h"
-#include "l2cap/internal/parameter_provider_mock.h"
-#include "os/handler.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-namespace bluetooth {
-namespace l2cap {
-namespace classic {
-namespace internal {
-
-using l2cap::internal::testing::MockParameterProvider;
-using ::testing::_;
-using testing::MockLink;
-using ::testing::Return;
-
-class L2capClassicFixedChannelImplTest : public ::testing::Test {
- public:
- static void SyncHandler(os::Handler* handler) {
- std::promise<void> promise;
- auto future = promise.get_future();
- handler->Post(common::BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)));
- future.wait_for(std::chrono::seconds(1));
- }
-
- protected:
- void SetUp() override {
- thread_ = new os::Thread("test_thread", os::Thread::Priority::NORMAL);
- l2cap_handler_ = new os::Handler(thread_);
- }
-
- void TearDown() override {
- l2cap_handler_->Clear();
- delete l2cap_handler_;
- delete thread_;
- }
-
- os::Thread* thread_ = nullptr;
- os::Handler* l2cap_handler_ = nullptr;
-};
-
-TEST_F(L2capClassicFixedChannelImplTest, get_device) {
- MockParameterProvider mock_parameter_provider;
- EXPECT_CALL(mock_parameter_provider, GetClassicLinkIdleDisconnectTimeout())
- .WillRepeatedly(Return(std::chrono::seconds(5)));
- testing::MockClassicAclConnection* mock_acl_connection = new testing::MockClassicAclConnection();
- EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
- EXPECT_CALL(*mock_acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
- EXPECT_CALL(*mock_acl_connection, UnregisterCallbacks(_)).Times(1);
- MockLink mock_classic_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockClassicAclConnection>(mock_acl_connection));
- hci::AddressWithType device{hci::Address{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
- hci::AddressType::PUBLIC_IDENTITY_ADDRESS};
- EXPECT_CALL(mock_classic_link, GetDevice()).WillRepeatedly(Return(device));
- FixedChannelImpl fixed_channel_impl(kSmpBrCid, &mock_classic_link, l2cap_handler_);
- EXPECT_EQ(device.GetAddress(), fixed_channel_impl.GetDevice());
-}
-
-// Other test cases omitted in doc ...
-
-} // namespace internal
-} // namespace classic
-} // namespace l2cap
-} // namespace bluetooth
-```
diff --git a/gd/dumpsys/Android.bp b/gd/dumpsys/Android.bp
deleted file mode 100644
index 4ad6376ba..000000000
--- a/gd/dumpsys/Android.bp
+++ /dev/null
@@ -1,151 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-filegroup {
- name: "BluetoothDumpsysSources",
- srcs: [
- "filter.cc",
- "init_flags.cc",
- "internal/filter_internal.cc",
- "reflection_schema.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothDumpsysTestSources",
- srcs: [
- "filter_test.cc",
- "internal/filter_internal_test.cc",
- "reflection_schema_test.cc",
- ],
-}
-
-genrule {
- name: "BluetoothGeneratedDumpsysTestData_h",
- tools: [
- "flatc",
- ],
- cmd: "$(location flatc) -I system/bt/gd -b --schema -o $(genDir) --cpp $(in) ",
- srcs: [
- "test_data/root.fbs",
- "test_data/bar.fbs",
- "test_data/baz.fbs",
- "test_data/foo.fbs",
- "test_data/qux.fbs",
- ],
- out: [
- "root_generated.h",
- "bar_generated.h",
- "baz_generated.h",
- "foo_generated.h",
- "qux_generated.h",
- ],
-}
-
-genrule {
- name: "BluetoothGeneratedDumpsysTestData_bfbs",
- tools: [
- "flatc",
- ],
- cmd: "$(location flatc) -I system/bt/gd -b --schema -o $(genDir) --cpp $(in) ",
- srcs: [
- "test_data/root.fbs",
- "test_data/bar.fbs",
- "test_data/baz.fbs",
- "test_data/foo.fbs",
- "test_data/qux.fbs",
- ],
- out: [
- "root.bfbs",
- "bar.bfbs",
- "baz.bfbs",
- "foo.bfbs",
- "qux.bfbs",
- ],
-}
-
-genrule {
- name: "BluetoothGeneratedDumpsysTestSchema_h",
- tools: [
- "bluetooth_flatbuffer_bundler",
- ],
- cmd: "$(location bluetooth_flatbuffer_bundler) -w -m bluetooth.DumpsysData -f dumpsys_module_schema_data -n testing -g $(genDir) $(locations :BluetoothGeneratedDumpsysBinarySchema_bfbs)",
- srcs: [
- ":BluetoothGeneratedDumpsysBinarySchema_bfbs",
- ],
- out: [
- "dumpsys_module_schema_data.h",
- ],
-}
-
-genrule {
- name: "BluetoothGeneratedDumpsysBundledSchema_h",
- tools: [
- "bluetooth_flatbuffer_bundler",
- ],
- cmd: "$(location bluetooth_flatbuffer_bundler) -w -m bluetooth.DumpsysData -f generated_dumpsys_bundled_schema -n bluetooth::dumpsys -g $(genDir) $(locations :BluetoothGeneratedDumpsysBinarySchema_bfbs)",
- srcs: [
- ":BluetoothGeneratedDumpsysBinarySchema_bfbs",
- ],
- out: [
- "generated_dumpsys_bundled_schema.h",
- ],
-}
-
-genrule {
- name: "BluetoothGeneratedDumpsysBundledTestSchema_h",
- tools: [
- "bluetooth_flatbuffer_bundler",
- ],
- cmd: "$(location bluetooth_flatbuffer_bundler) -w -m testing.DumpsysTestDataRoot -f generated_dumpsys_bundled_test_schema -n testing -g $(genDir) $(locations :BluetoothGeneratedDumpsysTestData_bfbs)",
- srcs: [
- ":BluetoothGeneratedDumpsysTestData_bfbs",
- ],
- out: [
- "generated_dumpsys_bundled_test_schema.h",
- ],
-}
-
-genrule {
- name: "BluetoothFlatbufferTestData_h",
- tools: [
- "flatc",
- ],
- cmd: "$(location flatc) -I system/bt/gd -b --schema -o $(genDir) --cpp $(in) ",
- srcs: [
- "bluetooth_flatbuffer_test.fbs",
- ],
- out: [
- "bluetooth_flatbuffer_test_generated.h", "bluetooth_flatbuffer_test.bfbs",
- ],
-}
-
-cc_test {
- name: "bluetooth_flatbuffer_test",
- test_suites: ["device-tests"],
- host_supported: true,
- test_options: {
- unit_test: true,
- },
- static_libs: [
- "libgmock",
- "libflatbuffers-cpp",
- ],
- srcs: [
- "bluetooth_flatbuffer_test.cc",
- ],
- generated_headers: [
- "BluetoothFlatbufferTestData_h",
- ],
- cflags: [
- "-Werror",
- "-Wall",
- "-Wextra",
- ],
-}
diff --git a/gd/dumpsys/BUILD.gn b/gd/dumpsys/BUILD.gn
deleted file mode 100644
index 82779f8d3..000000000
--- a/gd/dumpsys/BUILD.gn
+++ /dev/null
@@ -1,37 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import("//bt/gd/dumpsys/bundler/bundler.gni")
-
-source_set("BluetoothDumpsysSources") {
- sources = [
- "filter.cc",
- "init_flags.cc",
- "internal/filter_internal.cc",
- "reflection_schema.cc",
- ]
-
- cflags_cc = [ "-Wno-enum-compare-switch" ]
-
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ "//bt/gd:gd_default_deps" ]
-}
-
-bt_flatc_bundler("BluetoothGeneratedDumpsysBundledSchema_h") {
- root_name = "bluetooth.DumpsysData"
- filename = "generated_dumpsys_bundled_schema"
- namespace = "bluetooth::dumpsys"
- deps = [ "//bt/gd:BluetoothGeneratedDumpsysBinarySchema_bfbs" ]
-}
diff --git a/gd/dumpsys/bluetooth_flatbuffer_test.cc b/gd/dumpsys/bluetooth_flatbuffer_test.cc
deleted file mode 100644
index 4b836763c..000000000
--- a/gd/dumpsys/bluetooth_flatbuffer_test.cc
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "bluetooth_flatbuffer_test_generated.h"
-#include "flatbuffers/flatbuffers.h"
-#include "flatbuffers/idl.h"
-#include "flatbuffers/util.h"
-
-namespace bluetooth {
-namespace dumpsys {
-
-class BluetoothFlatbufferTest : public ::testing::Test {
- protected:
- void SetUp() override {}
-
- void TearDown() override {}
-};
-
-TEST_F(BluetoothFlatbufferTest, precondition) {}
-
-TEST_F(BluetoothFlatbufferTest, BuilderTest) {
- flatbuffers::FlatBufferBuilder builder(1024);
- auto string_private = builder.CreateString("String private");
- auto string_opaque = builder.CreateString("String opaque");
- auto string_anonymized = builder.CreateString("String anonymized");
- auto string_any = builder.CreateString("String any");
-
- TestTableBuilder table_builder(builder);
- table_builder.add_string_private(string_private);
- table_builder.add_string_opaque(string_opaque);
- table_builder.add_string_anonymized(string_anonymized);
- table_builder.add_string_any(string_any);
-
- table_builder.add_int_private(123);
- table_builder.add_int_opaque(456);
- table_builder.add_int_anonymized(789);
- table_builder.add_int_any(0xabc);
-
- builder.Finish(table_builder.Finish());
-
- const TestTable* test_table = GetTestTable(builder.GetBufferPointer());
-
- ASSERT_EQ("String private", test_table->string_private()->str());
- ASSERT_EQ("String opaque", test_table->string_opaque()->str());
- ASSERT_EQ("String anonymized", test_table->string_anonymized()->str());
- ASSERT_EQ("String any", test_table->string_any()->str());
-
- ASSERT_EQ(123, test_table->int_private());
- ASSERT_EQ(456, test_table->int_opaque());
- ASSERT_EQ(789, test_table->int_anonymized());
- ASSERT_EQ(0xabc, test_table->int_any());
-}
-
-} // namespace dumpsys
-} // namespace bluetooth
diff --git a/gd/dumpsys/bluetooth_flatbuffer_test.fbs b/gd/dumpsys/bluetooth_flatbuffer_test.fbs
deleted file mode 100644
index f44981362..000000000
--- a/gd/dumpsys/bluetooth_flatbuffer_test.fbs
+++ /dev/null
@@ -1,17 +0,0 @@
-// Bluetooth module test schema
-
-attribute "privacy";
-
-table TestTable {
- string_private:string; // no privacy attribute implies private
- string_opaque:string (privacy:"Opaque");
- string_anonymized:string (privacy:"Anonymized");
- string_any:string (privacy:"Any");
-
- int_private:int32 (privacy:"Private"); // Explicitly private
- int_opaque:int32 (privacy:"Opaque");
- int_anonymized:int32 (privacy:"Anonymized");
- int_any:int32 (privacy:"Any");
-}
-
-root_type TestTable;
diff --git a/gd/dumpsys/bundler/Android.bp b/gd/dumpsys/bundler/Android.bp
deleted file mode 100644
index 67081c9aa..000000000
--- a/gd/dumpsys/bundler/Android.bp
+++ /dev/null
@@ -1,85 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-filegroup {
- name: "BluetoothFlatbufferBundlerSources",
- srcs: [
- "bundler.cc",
- "main.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothFlatbufferBundlerTestSources",
- srcs: [
- "bundler.cc",
- "test.cc",
- ],
-}
-
-genrule {
- name: "BluetoothGeneratedBundlerSchema_h_bfbs",
- tools: [
- "flatc",
- ],
- cmd: "$(location flatc) -I system/bt/gd -b --schema -o $(genDir) --cpp $(in) ",
- srcs: [
- "bundler.fbs",
- ],
- out: [
- "bundler_generated.h", "bundler.bfbs",
- ],
-}
-
-cc_defaults {
- name: "bluetooth_flatbuffer_bundler_defaults",
- cpp_std: "c++17",
- cflags: [
- "-Wall",
- "-Werror",
- "-Wno-unused-parameter",
- "-Wno-unused-variable",
- ],
- generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- ],
- sanitize: {
- misc_undefined: ["bounds"],
- },
- static_libs: [
- "libflatbuffers-cpp",
- ],
-}
-
-cc_binary_host {
- name: "bluetooth_flatbuffer_bundler",
- srcs: [
- ":BluetoothFlatbufferBundlerSources",
- ],
- defaults: [
- "bluetooth_flatbuffer_bundler_defaults",
- ],
-}
-
-cc_test {
- name: "bluetooth_flatbuffer_bundler_test",
- host_supported: true,
- srcs: [
- ":BluetoothFlatbufferBundlerTestSources",
- ],
- defaults: [
- "bluetooth_flatbuffer_bundler_defaults",
- ],
- data: [
- "test.bfbs",
- ],
- test_options: {
- unit_test: true,
- },
-}
diff --git a/gd/dumpsys/bundler/BUILD.gn b/gd/dumpsys/bundler/BUILD.gn
deleted file mode 100644
index ada6b9c5d..000000000
--- a/gd/dumpsys/bundler/BUILD.gn
+++ /dev/null
@@ -1,51 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import("//bt/gd/dumpsys/bundler/bundler.gni")
-import("//common-mk/flatbuffer.gni")
-
-bt_flatc_binary_schema("BluetoothGeneratedBundlerSchema_h_bfbs") {
- sources = [ "bundler.fbs" ]
- include_dir = "bt/gd"
- gen_header = true
-}
-
-#
-# The remaining rules are for building on the host
-#
-
-config("bundler_defaults") {
- cflags = [ "-fPIC" ]
-
- cflags_cc = [
- "-std=c++17",
- "-Wno-unused-parameter",
- "-Wno-unused-variable",
- "-Wno-poison-system-directories",
- ]
-}
-
-executable("bluetooth_flatbuffer_bundler") {
- sources = [
- "bundler.cc",
- "main.cc",
- ]
-
- libs = [ "flatbuffers" ]
-
- deps = [ ":BluetoothGeneratedBundlerSchema_h_bfbs" ]
-
- configs += [ ":bundler_defaults" ]
-}
diff --git a/gd/dumpsys/bundler/bundler.cc b/gd/dumpsys/bundler/bundler.cc
deleted file mode 100644
index d37aca034..000000000
--- a/gd/dumpsys/bundler/bundler.cc
+++ /dev/null
@@ -1,335 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#include <assert.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <unistd.h>
-#include <cassert>
-#include <list>
-#include <map>
-#include <vector>
-
-#include "bundler.h"
-#include "bundler_generated.h"
-#include "flatbuffers/idl.h"
-#include "flatbuffers/util.h"
-
-using namespace bluetooth;
-using namespace dumpsys;
-
-struct Opts opts;
-
-/**
- * Load a binary schema from persistent store using flatbuffer API.
- *
- * @param filename; Name of file to open and read.
- * @param binary_schema: Backing store for flatbuffer binary schema data.
- *
- * @return: True if operation successful, false otherwise.
- */
-bool LoadBinarySchema(const char* filename, std::string* binary_schema) {
- assert(filename != nullptr);
- assert(binary_schema != nullptr);
- if (!flatbuffers::LoadFile(filename, helper::AsBinaryFile, binary_schema)) {
- fprintf(stderr, "Unable to open binary flatbuffer schema file:%s\n", filename);
- return false;
- };
- return true;
-}
-
-/**
- * Verify a binary schema using flatbuffer API.
- *
- * @param schema: Raw binary schema to verify
- *
- * @return: True if operation successful, false otherwise.
- */
-bool VerifyBinarySchema(const std::vector<uint8_t>& raw_schema) {
- flatbuffers::Verifier verifier(raw_schema.data(), raw_schema.size());
- if (!reflection::VerifySchemaBuffer(verifier)) {
- return false;
- }
- return true;
-}
-
-/**
- * Bundle a set of binary flatbuffer schema into the bundler database.
- *
- * @param builder; Flatbuffer builder
- * @param filenames: Set of filenames to include in bundle
- * @param vector_map: Filename to filedata mapping
- *
- * @return: True if operation successful, false otherwise.
- */
-bool CreateBinarySchemaBundle(
- flatbuffers::FlatBufferBuilder* builder,
- const std::vector<std::string>& filenames,
- std::vector<flatbuffers::Offset<BundledSchemaMap>>* vector_map,
- std::list<std::string>* bundled_names) {
- assert(builder != nullptr);
- assert(vector_map != nullptr);
- assert(bundled_names != nullptr);
-
- for (auto filename : filenames) {
- std::string string_schema;
- if (!LoadBinarySchema(filename.c_str(), &string_schema)) {
- fprintf(stderr, "Unable to load binary schema from filename:%s\n", filename.c_str());
- return false;
- }
- std::vector<uint8_t> raw_schema(string_schema.begin(), string_schema.end());
- if (!VerifyBinarySchema(raw_schema)) {
- fprintf(stderr, "Failed verification on binary schema filename:%s\n", filename.c_str());
- return false;
- }
-
- const reflection::Schema* schema = reflection::GetSchema(raw_schema.data());
- if (schema->root_table() == nullptr) {
- fprintf(stderr, "Unable to find root table for binary flatbuffer schema:%s\n", filename.c_str());
- return false;
- }
-
- bundled_names->push_back(schema->root_table()->name()->str());
- auto name = builder->CreateString(schema->root_table()->name()->str());
- auto data = builder->CreateVector<uint8_t>(raw_schema.data(), raw_schema.size());
- vector_map->push_back(CreateBundledSchemaMap(*builder, name, data));
-
- if (opts.verbose) {
- fprintf(stdout, "Bundled binary schema file:%s\n", schema->root_table()->name()->c_str());
- }
- }
- return true;
-}
-
-/**
- * Write generated header file containing the bundled binary schema
- * data and meta data
- *
- * @param data: Source file data.
- * @param data_len: length of data
- */
-void WriteHeaderFile(FILE* fp, const uint8_t* data, size_t data_len) {
- assert(fp != nullptr);
- std::string delim(kDefaultNamespaceDelim);
- std::string ns_string(opts.ns_name);
- std::vector<std::string> namespaces;
-
- size_t start = 0;
- size_t end = ns_string.find(delim);
- while (end != std::string::npos) {
- namespaces.push_back(ns_string.substr(start, end - start));
- start = end + delim.size();
- end = ns_string.find(delim, start);
- }
- if (start != 0 && start != std::string::npos) {
- namespaces.push_back(ns_string.substr(start));
- } else if (!ns_string.empty()) {
- namespaces.push_back(ns_string);
- }
-
- std::string namespace_prefix;
- for (const auto& name : namespaces) namespace_prefix += (name + '_');
-
- fprintf(
- fp,
- "// Generated file by bluetooth_flatbuffer bundler\n"
- "#pragma once\n"
- "#include <sys/types.h>\n"
- "#include <string>\n");
- for_each(
- namespaces.begin(), namespaces.end(), [fp](const std::string& s) { fprintf(fp, "namespace %s {\n", s.c_str()); });
- fprintf(
- fp,
- "extern const unsigned char* data;\n"
- "extern const size_t data_size;\n"
- "const std::string& GetBundledSchemaData();\n");
- for_each(namespaces.crbegin(), namespaces.crend(), [fp](const std::string& s) {
- fprintf(fp, "} // namespace %s\n", s.c_str());
- });
- fprintf(
- fp,
- "namespace {\n"
- "const unsigned char %sdata_[] = {\n",
- namespace_prefix.c_str());
-
- for (auto i = 0; i < data_len; i++) {
- fprintf(fp, " 0x%02x", data[i]);
- if (i != data_len - 1) {
- fprintf(fp, ",");
- }
- if ((i + 1) % 16 == 0) {
- fprintf(fp, "\n");
- }
- }
- fprintf(fp, " };\n");
- fprintf(
- fp,
- "const std::string %sstring_data_(%sdata_, %sdata_ + sizeof(%sdata_));\n",
- namespace_prefix.c_str(),
- namespace_prefix.c_str(),
- namespace_prefix.c_str(),
- namespace_prefix.c_str());
- fprintf(fp, "} // namespace\n");
- fprintf(fp, "const unsigned char* %s::data = %sdata_;\n", opts.ns_name, namespace_prefix.c_str());
- fprintf(fp, "const size_t %s::data_size = %zu;\n", opts.ns_name, data_len);
- fprintf(
- fp,
- "const std::string& %s::GetBundledSchemaData() { return %sstring_data_; }\n",
- opts.ns_name,
- namespace_prefix.c_str());
-}
-
-int ReadBundledSchema() {
- const char* filename = opts.filename;
- assert(filename != nullptr);
-
- std::string flatfile_data;
- if (!flatbuffers::LoadFile(filename, helper::AsBinaryFile, &flatfile_data)) {
- fprintf(stderr, "Unable to load schema data file:%s\n", filename);
- return -5;
- }
-
- auto bundle_schema = flatbuffers::GetRoot<BundledSchema>(flatfile_data.c_str());
- const flatbuffers::Vector<flatbuffers::Offset<BundledSchemaMap>>* map = bundle_schema->map();
-
- fprintf(stdout, "Bundle schema title:%s\n", bundle_schema->title()->c_str());
- fprintf(stdout, "Bundle schema root_name:%s\n", bundle_schema->root_name()->c_str());
- int cnt = 0;
- for (auto it = map->cbegin(); it != map->cend(); ++it, cnt++) {
- fprintf(stdout, " %d name:%s schema:%s\n", cnt, it->name()->c_str(), "schema");
- }
- return EXIT_SUCCESS;
-}
-
-int WriteBundledSchema() {
- const char* filename = opts.filename;
- assert(filename != nullptr);
-
- const char* main_root_name = opts.main_root_name;
- if (main_root_name == nullptr) {
- fprintf(stderr, "Must specify the name of the main root name for this bundle\n");
- return EXIT_FAILURE;
- }
-
- std::vector<std::string> bfbs_filenames;
- for (int i = 0; i < opts.arg.c; i++) {
- bfbs_filenames.push_back(std::string(opts.arg.v[i]));
- }
- if (bfbs_filenames.empty()) {
- fprintf(stderr, "No bfbs files are specified to bundle\n");
- return EXIT_FAILURE;
- }
-
- flatbuffers::FlatBufferBuilder builder(1024);
-
- std::list<std::string> bundled_names;
- std::vector<flatbuffers::Offset<BundledSchemaMap>> vector_map;
- if (!CreateBinarySchemaBundle(&builder, bfbs_filenames, &vector_map, &bundled_names)) {
- fprintf(stderr, "Unable to bundle schema bfbs files\n");
- return EXIT_FAILURE;
- }
-
- if (std::find(bundled_names.begin(), bundled_names.end(), main_root_name) == bundled_names.end()) {
- fprintf(stderr, "The main root name must match one of the bundled schema names\n");
- fprintf(stderr, " main root name:%s\n", main_root_name);
- for (auto name : bundled_names) {
- fprintf(stderr, " bundled schema name:%s\n", name.c_str());
- }
- return EXIT_FAILURE;
- }
-
- const char* title = opts.title;
- auto schema_offset = CreateBundledSchemaDirect(builder, title, main_root_name, &vector_map);
- builder.Finish(schema_offset);
-
- std::string final_filename(opts.gen);
- final_filename.append("/");
- final_filename.append(filename);
- if (!flatbuffers::SaveFile(
- final_filename.c_str(), (const char*)builder.GetBufferPointer(), builder.GetSize(), helper::AsBinaryFile)) {
- fprintf(stderr, "Unable to save file:%s\n", final_filename.c_str());
- return EXIT_FAILURE;
- }
-
- std::string header(opts.gen);
- header += ("/" + std::string(opts.filename) + ".h");
- FILE* fp = fopen(header.c_str(), "w+");
- if (fp == nullptr) {
- fprintf(stdout, "Unable to open for writing header file:%s\n", header.c_str());
- return EXIT_FAILURE;
- }
- WriteHeaderFile(fp, builder.GetBufferPointer(), builder.GetSize());
- fclose(fp);
- return EXIT_SUCCESS;
-}
-
-int Usage(int argc, char** argv) {
- fprintf(
- stderr,
- "Usage: %s [-r | -w] [-f <filename>] [-g <gen_out_path>] [-n <namespace> ] [-v] -m <main_root_name> <file.bfbs "
- "...>\n",
- argv[0]);
- fprintf(stderr, " -r|-w : Read or write a dumpsys file\n");
- fprintf(stderr, " -f : Filename bundled schema to read or write (default:%s)\n", kDefaultBundleDataFile);
- fprintf(stderr, " -g : Generated file output path\n");
- fprintf(stderr, " -n : Namespace to embed binary output bundle data source\n");
- fprintf(stderr, " -m : Name of the main root of this bundle\n");
- fprintf(stderr, " -v : Verbose printing mode\n");
- return EXIT_FAILURE;
-}
-
-void ParseArgs(int argc, char** argv) {
- int opt;
- int parsed_cnt = 1;
- while ((opt = getopt(argc, argv, "f:g:m:n:rt:vw")) != -1) {
- parsed_cnt++;
- switch (opt) {
- case 'f':
- opts.filename = optarg;
- parsed_cnt++;
- break;
- case 'g':
- opts.gen = optarg;
- parsed_cnt++;
- break;
- case 'm':
- opts.main_root_name = optarg;
- parsed_cnt++;
- break;
- case 'n':
- opts.ns_name = optarg;
- parsed_cnt++;
- break;
- case 'r':
- opts.read = true;
- break;
- case 'w':
- opts.write = true;
- break;
- case 't':
- opts.title = optarg;
- parsed_cnt++;
- break;
- case 'v':
- opts.verbose = true;
- break;
- default:
- exit(Usage(argc, argv));
- break;
- }
- }
- opts.arg.c = argc - parsed_cnt;
- opts.arg.v = &argv[parsed_cnt];
-}
diff --git a/gd/dumpsys/bundler/bundler.fbs b/gd/dumpsys/bundler/bundler.fbs
deleted file mode 100644
index a11fb7f15..000000000
--- a/gd/dumpsys/bundler/bundler.fbs
+++ /dev/null
@@ -1,19 +0,0 @@
-// Bundled Schema
-//
-// Describes a collection of binary flatbuffer schema.
-//
-
-namespace bluetooth.dumpsys;
-
-table BundledSchemaMap {
- name:string;
- data:[ubyte];
-}
-
-table BundledSchema {
- title:string;
- root_name:string;
- map:[BundledSchemaMap];
-}
-
-root_type BundledSchema;
diff --git a/gd/dumpsys/bundler/bundler.gni b/gd/dumpsys/bundler/bundler.gni
deleted file mode 100644
index c3b893ba7..000000000
--- a/gd/dumpsys/bundler/bundler.gni
+++ /dev/null
@@ -1,180 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-# Generate bundled flat buffers
-#
-# Args:
-# include_dir: Path to include directory
-# sources: Flatbuffer source files
-# gen_header [optional]: Whether to generate headers.
-template("bt_flatc_binary_schema") {
- action_name = "${target_name}_gen"
- action(action_name) {
- forward_variables_from(invoker,
- [
- "include_dir",
- "sources",
- ])
- assert(defined(include_dir), "include_dir must be set")
- assert(defined(sources), "sources must be set")
-
- gen_header = defined(invoker.gen_header) && invoker.gen_header
-
- script = "//common-mk/file_generator_wrapper.py"
- binfile = "flatc"
- args = [
- binfile,
- "-I",
- "${include_dir}",
- "-b",
- "--schema",
- "-o",
- "${target_gen_dir}",
- ]
-
- bfbs_names = []
- srclist = []
- outputs = []
-
- foreach(s, sources) {
- srclist += [ rebase_path(s) ]
-
- # bfbs get generated into ${target_gen_root} directory
- name = string_replace(get_path_info(s, "file"), ".fbs", ".bfbs")
- bfbs_names += [ "${target_gen_dir}/${name}" ]
- outputs += [ "${target_gen_dir}/${name}" ]
-
- # headers get generated ito subdirectories based on relative path
- if (gen_header) {
- header_name = string_replace(s, ".fbs", ".h")
- outputs += [ "${target_gen_dir}/${header_name}" ]
- }
- }
-
- # Generate header file as well
- if (gen_header) {
- args += [ "--cpp" ]
- }
-
- # Actual input files at the end
- args += srclist
-
- metadata = {
- bfbs_outputs = bfbs_names
- }
- }
-
- all_dependent_config_name = "_${target_name}_all_dependent_config"
- config(all_dependent_config_name) {
- # Since each header will be generated into a subdirectory, add them to the
- # include dirs as well
- gen_dirs = []
- foreach(s, invoker.sources) {
- gen_dirs += [ get_path_info(s, "gen_dir") ]
- }
-
- include_dirs = [ "${target_gen_dir}" ] + gen_dirs
- }
-
- generated_file(target_name) {
- outputs = [ "${target_gen_dir}/${target_name}.files" ]
- output_conversion = "list lines"
- data_keys = [ "bfbs_outputs" ]
-
- all_dependent_configs = [ ":${all_dependent_config_name}" ]
- if (defined(invoker.all_dependent_configs)) {
- all_dependent_configs += invoker.all_dependent_configs
- }
-
- deps = [ ":${action_name}" ]
- if (defined(invoker.deps)) {
- deps += invoker.deps
- }
-
- if (defined(invoker.configs)) {
- configs += invoker.configs
- }
- }
-}
-
-# Generate bundled header
-template("bt_flatc_bundler") {
- action_name = "${target_name}_gen"
- action(action_name) {
- forward_variables_from(invoker, [ "deps" ])
- assert(defined(deps), "deps must be set")
- assert(defined(invoker.root_name), "root_name must be set")
- assert(defined(invoker.filename), "filename must be set")
- assert(defined(invoker.namespace), "namespace must be set")
-
- files_list = []
- foreach(s, deps) {
- name = get_label_info(s, "name")
- gen_dir = get_label_info(s, "target_gen_dir")
- files_list += [ "${gen_dir}/${name}.files" ]
- }
-
- script = "//bt/gd/dumpsys/bundler/extract_files_and_call.py"
- binfile = "${root_out_dir}/bluetooth_flatbuffer_bundler"
- args = files_list
- args += [
- "--",
- binfile,
- "-w",
- "-m",
- "${invoker.root_name}",
- "-f",
- "${invoker.filename}",
- "-n",
- "${invoker.namespace}",
- "-g",
- "${target_gen_dir}",
- ]
-
- outputs = [
- "${target_gen_dir}/${invoker.filename}.h",
- "${target_gen_dir}/${invoker.filename}",
- ]
-
- metadata = {
- all_outputs = outputs
- }
- }
-
- all_dependent_config_name = "_${target_name}_all_dependent_config"
- config(all_dependent_config_name) {
- include_dirs = [ "${target_gen_dir}" ]
- }
-
- generated_file(target_name) {
- outputs = [ "${target_gen_dir}/${target_name}.files" ]
- output_conversion = "list lines"
- data_keys = [ "all_outputs" ]
-
- all_dependent_configs = [ ":${all_dependent_config_name}" ]
- if (defined(invoker.all_dependent_configs)) {
- all_dependent_configs += invoker.all_dependent_configs
- }
-
- deps = [ ":${action_name}" ]
- if (defined(invoker.deps)) {
- deps += invoker.deps
- }
-
- if (defined(invoker.configs)) {
- configs += invoker.configs
- }
- }
-}
diff --git a/gd/dumpsys/bundler/bundler.h b/gd/dumpsys/bundler/bundler.h
deleted file mode 100644
index 9dc4b243d..000000000
--- a/gd/dumpsys/bundler/bundler.h
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-namespace {
-constexpr char kDefaultBundleDataFile[] = "bundle_bfbs.bin";
-constexpr char kDefaultGeneratedOutputPath[] = ".";
-constexpr char kDefaultNamespace[] = "";
-constexpr char kDefaultNamespaceDelim[] = "::";
-constexpr char kDefaultTitle[] = "Bundled schema tables";
-} // namespace
-
-struct Opts {
- bool verbose{false};
- bool read{false};
- bool write{false};
- const char* filename{kDefaultBundleDataFile};
- const char* gen{kDefaultGeneratedOutputPath};
- const char* main_root_name{nullptr};
- const char* ns_name{kDefaultNamespace};
- const char* title{kDefaultTitle};
- struct {
- int c{0};
- char** v{nullptr};
- } arg;
-};
-extern Opts opts;
-
-namespace {
-namespace helper { // Part of flatbuffers API
-constexpr bool AsBinaryFile = true;
-constexpr bool AsTextFile = false;
-} // namespace helper
-
-} // namespace
-
-/**
- * Read and parse a previously generated bundle data file
- *
- **/
-int ReadBundledSchema();
-
-/**
- * Generate a bundle data file from the binary flatbuffer schema
- * files provided as input
- *
- **/
-int WriteBundledSchema();
-
-/**
- * Print tool usage options
- */
-int Usage(int argc, char** argv);
-
-/**
- * Parse tool usage options
- */
-void ParseArgs(int argc, char** argv);
diff --git a/gd/dumpsys/bundler/extract_files_and_call.py b/gd/dumpsys/bundler/extract_files_and_call.py
deleted file mode 100755
index df0415f61..000000000
--- a/gd/dumpsys/bundler/extract_files_and_call.py
+++ /dev/null
@@ -1,58 +0,0 @@
-#!/usr/bin/env python3
-# -*- coding: utf-8 -*-
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-""" Get contents of given files and pass as args to remaining params.
-
-Example:
- a.files = [ "foo", "bar" ]
- b.files = [ "fizz", "buzz" ]
-
- extract_files_and_call.py a.files b.files -- somebin -a --set foo -c -o
-
- will result in this call:
-
- somebin -a --set foo -c -o foo bar fizz buzz
-
-"""
-
-from __future__ import print_function
-
-import subprocess
-import sys
-
-
-def file_to_args(filename):
- """ Read file and return lines with empties removed.
- """
- with open(filename, 'r') as f:
- return [x.strip() for x in f.readlines() if x.strip()]
-
-
-def main():
- file_contents = []
- args = []
- for i in range(1, len(sys.argv) - 1):
- if sys.argv[i] == '--':
- args = sys.argv[i + 1:] + file_contents
- break
- else:
- file_contents.extend(file_to_args(sys.argv[i]))
-
- subprocess.check_call(args)
-
-
-if __name__ == "__main__":
- main()
diff --git a/gd/dumpsys/bundler/main.cc b/gd/dumpsys/bundler/main.cc
deleted file mode 100644
index 23eb1e037..000000000
--- a/gd/dumpsys/bundler/main.cc
+++ /dev/null
@@ -1,27 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#include "bundler.h"
-#include "bundler_generated.h"
-
-int main(int argc, char** argv) {
- ParseArgs(argc, argv);
- if (opts.read) {
- exit(ReadBundledSchema());
- }
- if (opts.write) {
- exit(WriteBundledSchema());
- }
-}
diff --git a/gd/dumpsys/bundler/test.bfbs b/gd/dumpsys/bundler/test.bfbs
deleted file mode 100644
index 0dda6e54f..000000000
--- a/gd/dumpsys/bundler/test.bfbs
+++ /dev/null
Binary files differ
diff --git a/gd/dumpsys/bundler/test.cc b/gd/dumpsys/bundler/test.cc
deleted file mode 100644
index af8c40868..000000000
--- a/gd/dumpsys/bundler/test.cc
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#include <gtest/gtest.h>
-#include <list>
-#include <vector>
-
-#include "bundler.h"
-#include "bundler_generated.h"
-#include "flatbuffers/flatbuffers.h"
-
-bool LoadBinarySchema(const char* filename, std::string* binary_schema);
-bool VerifyBinarySchema(const std::vector<uint8_t>& raw_schema);
-bool CreateBinarySchemaBundle(
- flatbuffers::FlatBufferBuilder* builder,
- const std::vector<std::string>& filenames,
- std::vector<flatbuffers::Offset<bluetooth::dumpsys::BundledSchemaMap>>* vector_map,
- std::list<std::string>* bundled_names);
-int WriteHeaderFile(FILE* fp, const uint8_t* data, size_t data_len);
-
-class BundlerTest : public ::testing::Test {
- public:
- void SetUp() override {}
-
- void TearDown() override {}
-};
-
-TEST_F(BundlerTest, LoadBinarySchema) {
- std::string string_schema;
- ASSERT_FALSE(LoadBinarySchema(nullptr, &string_schema));
- ASSERT_DEATH(LoadBinarySchema("test.bfbs", nullptr), "");
- ASSERT_TRUE(LoadBinarySchema("test.bfbs", &string_schema));
- ASSERT_FALSE(LoadBinarySchema("does_not_exist.bfbs", &string_schema));
-}
-
-TEST_F(BundlerTest, VerifyBinarySchema) {
- std::string string_schema;
- ASSERT_TRUE(LoadBinarySchema("test.bfbs", &string_schema));
- std::vector<uint8_t> raw_schema(string_schema.begin(), string_schema.end());
- ASSERT_TRUE(VerifyBinarySchema(raw_schema));
-
- std::vector<uint8_t> bogus_raw_schema(string_schema.begin() + 1, string_schema.end());
- ASSERT_FALSE(VerifyBinarySchema(bogus_raw_schema));
-}
-
-TEST_F(BundlerTest, CreateBinarySchemaBundle) {
- flatbuffers::FlatBufferBuilder builder;
- std::vector<std::string> filenames;
- std::vector<flatbuffers::Offset<bluetooth::dumpsys::BundledSchemaMap>> vector_map;
- std::list<std::string> bundled_names;
- ASSERT_TRUE(CreateBinarySchemaBundle(&builder, filenames, &vector_map, &bundled_names));
- ASSERT_EQ(0, vector_map.size());
-}
-
-TEST_F(BundlerTest, WriteHeaderFile) {
- std::vector<uint8_t> data;
- data.push_back(0x10);
- data.push_back(0x11);
- data.push_back(0x12);
- data.push_back(0x13);
- ASSERT_DEATH(WriteHeaderFile(nullptr, data.data(), data.size()), "");
- FILE* fp = fopen("/tmp/test.h", "w+");
- ASSERT_NE(fp, nullptr);
- WriteHeaderFile(fp, data.data(), data.size());
- fseek(fp, 0L, SEEK_SET);
- char buf[16];
- fread(buf, 1, 15, fp);
- buf[12] = '\0';
- std::string s(buf);
- ASSERT_EQ("// Generated", s);
- fclose(fp);
- unlink("/tmp/test.h");
-}
diff --git a/gd/dumpsys/filter.cc b/gd/dumpsys/filter.cc
deleted file mode 100644
index 315e313a5..000000000
--- a/gd/dumpsys/filter.cc
+++ /dev/null
@@ -1,200 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <memory>
-
-#include "dumpsys/filter.h"
-#include "dumpsys/internal/filter_internal.h"
-#include "os/log.h"
-
-using namespace bluetooth;
-using namespace dumpsys;
-
-class Filter {
- public:
- Filter(const dumpsys::ReflectionSchema& reflection_schema) : reflection_schema_(reflection_schema) {}
-
- virtual ~Filter() = default;
-
- virtual void FilterInPlace(char* dumpsys_data) = 0;
-
- static std::unique_ptr<Filter> Factory(
- dumpsys::FilterType filter_type, const dumpsys::ReflectionSchema& reflection_schema);
-
- protected:
- /**
- * Given both reflection field data and the populated flatbuffer table data, if any,
- * filter the contents of the field based upon the filtering privacy level.
- *
- * Primitives and composite strings may be successfully processed at this point.
- * Other composite types (e.g. structs or tables) must be expanded into the
- * respective grouping of subfields.
- *
- * @param field The reflection field information from the bundled schema
- * @param table The populated field data, if any
- *
- * @return true if field was filtered successfully, false otherwise.
- */
- virtual bool FilterField(const reflection::Field* field, flatbuffers::Table* table) {
- return false;
- }
-
- /**
- * Given both reflection object data and the populated flatbuffer table data, if any,
- * filter the object fields based upon the filtering privacy level.
- *
- * @param object The reflection object information from the bundled schema
- * @param table The populated field data, if any
- *
- */
- virtual void FilterObject(const reflection::Object* object, flatbuffers::Table* table){};
-
- /**
- * Given both reflection field data and the populated table data, if any,
- * filter the contents of the table based upon the filtering privacy level.
- *
- * @param schema The reflection schema information from the bundled schema
- * @param table The populated field data, if any
- *
- */
- virtual void FilterTable(const reflection::Schema* schema, flatbuffers::Table* table){};
-
- const dumpsys::ReflectionSchema& reflection_schema_;
-};
-
-class DeveloperPrivacyFilter : public Filter {
- public:
- DeveloperPrivacyFilter(const dumpsys::ReflectionSchema& reflection_schema) : Filter(reflection_schema) {}
- void FilterInPlace(char* dumpsys_data) override {}
-};
-
-class UserPrivacyFilter : public Filter {
- public:
- UserPrivacyFilter(const dumpsys::ReflectionSchema& reflection_schema) : Filter(reflection_schema) {}
- void FilterInPlace(char* dumpsys_data) override;
-
- protected:
- bool FilterField(const reflection::Field* field, flatbuffers::Table* table) override;
- void FilterObject(const reflection::Object* object, flatbuffers::Table* table) override;
- void FilterTable(const reflection::Schema* schema, flatbuffers::Table* table) override;
-};
-
-bool UserPrivacyFilter::FilterField(const reflection::Field* field, flatbuffers::Table* table) {
- ASSERT(field != nullptr);
- ASSERT(table != nullptr);
- internal::PrivacyLevel privacy_level = internal::FindFieldPrivacyLevel(*field);
-
- switch (field->type()->base_type()) {
- case flatbuffers::BASE_TYPE_INT:
- return internal::FilterTypeInteger(*field, table, privacy_level);
- break;
- case flatbuffers::BASE_TYPE_FLOAT:
- return internal::FilterTypeFloat(*field, table, privacy_level);
- break;
- case flatbuffers::BASE_TYPE_STRING:
- return internal::FilterTypeString(*field, table, privacy_level);
- break;
- case flatbuffers::BASE_TYPE_STRUCT:
- return internal::FilterTypeStruct(*field, table, privacy_level);
- break;
- case flatbuffers::BASE_TYPE_BOOL:
- return internal::FilterTypeBool(*field, table, privacy_level);
- break;
- default:
- LOG_WARN("%s WARN Unsupported base type\n", __func__);
- break;
- }
- return false;
-}
-
-void UserPrivacyFilter::FilterObject(const reflection::Object* object, flatbuffers::Table* table) {
- ASSERT(object != nullptr);
- if (table == nullptr) {
- return; // table data is not populated
- }
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- if (!FilterField(*it, table)) {
- LOG_ERROR("%s Unable to filter field from an object when it's expected it will work", __func__);
- };
- }
-}
-
-void UserPrivacyFilter::FilterTable(const reflection::Schema* schema, flatbuffers::Table* table) {
- if (schema == nullptr) {
- LOG_WARN("%s schema is nullptr...probably ok", __func__);
- return;
- }
-
- const reflection::Object* object = schema->root_table();
- if (object == nullptr) {
- LOG_WARN("%s reflection object is nullptr...is ok ?", __func__);
- return;
- }
-
- if (table == nullptr) {
- return; // table not populated
- }
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- if (FilterField(*it, table)) {
- continue; // Field successfully filtered
- }
- // Get the index of this complex non-string object from the schema which is
- // also the same index into the data table.
- int32_t index = it->type()->index();
- ASSERT(index != -1);
-
- flatbuffers::Table* sub_table = table->GetPointer<flatbuffers::Table*>(it->offset());
- const reflection::Schema* sub_schema =
- reflection_schema_.FindInReflectionSchema(schema->objects()->Get(index)->name()->str());
-
- if (sub_schema != nullptr) {
- FilterTable(sub_schema, sub_table); // Top level schema
- } else {
- // Leaf node schema
- const flatbuffers::String* name = schema->objects()->Get(index)->name();
- const reflection::Object* sub_object = internal::FindReflectionObject(schema->objects(), name);
- if (sub_object != nullptr) {
- FilterObject(sub_object, sub_table);
- } else {
- LOG_ERROR("Unable to find reflection sub object:%s\n", name->c_str());
- }
- }
- }
-}
-
-void UserPrivacyFilter::FilterInPlace(char* dumpsys_data) {
- ASSERT(dumpsys_data != nullptr);
- const reflection::Schema* root_schema = reflection_schema_.FindInReflectionSchema(reflection_schema_.GetRootName());
- flatbuffers::Table* table = const_cast<flatbuffers::Table*>(flatbuffers::GetRoot<flatbuffers::Table>(dumpsys_data));
- FilterTable(root_schema, table);
-}
-
-std::unique_ptr<Filter> Filter::Factory(
- dumpsys::FilterType filter_type, const dumpsys::ReflectionSchema& reflection_schema) {
- switch (filter_type) {
- case dumpsys::FilterType::AS_DEVELOPER:
- return std::make_unique<DeveloperPrivacyFilter>(reflection_schema);
- default:
- return std::make_unique<UserPrivacyFilter>(reflection_schema);
- }
-}
-
-void bluetooth::dumpsys::FilterInPlace(
- FilterType filter_type, const ReflectionSchema& reflection_schema, std::string* dumpsys_data) {
- auto filter = Filter::Factory(filter_type, reflection_schema);
- filter->FilterInPlace(dumpsys_data->data());
-}
diff --git a/gd/dumpsys/filter.h b/gd/dumpsys/filter.h
deleted file mode 100644
index a572c403d..000000000
--- a/gd/dumpsys/filter.h
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <string>
-#include "dumpsys/reflection_schema.h"
-
-namespace bluetooth {
-namespace dumpsys {
-
-enum FilterType { AS_USER = 0, AS_DEVELOPER };
-
-void FilterInPlace(FilterType filter_type, const ReflectionSchema& reflection_schema, std::string* dumpsys_data);
-
-} // namespace dumpsys
-} // namespace bluetooth
diff --git a/gd/dumpsys/filter_test.cc b/gd/dumpsys/filter_test.cc
deleted file mode 100644
index 1f02f408a..000000000
--- a/gd/dumpsys/filter_test.cc
+++ /dev/null
@@ -1,187 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <list>
-#include <queue>
-
-#include "dumpsys/filter.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "test_data/bar.h"
-#include "test_data/baz.h"
-#include "test_data/foo.h"
-#include "test_data/qux.h"
-#include "test_data/root.h"
-
-// TODO(cmanton) fix bundler to split header/code
-//#include "generated_dumpsys_bundled_test_schema.h"
-namespace testing {
-extern const unsigned char* data;
-extern const size_t data_size;
-const std::string& GetBundledSchemaData();
-} // namespace testing
-
-namespace testing {
-
-using namespace bluetooth;
-
-class DumpsysFilterTest : public Test {
- protected:
- void SetUp() override {
- test_data_classes_.push_back(std::make_unique<BarTestDataClass>());
- test_data_classes_.push_back(std::make_unique<BazTestDataClass>());
- test_data_classes_.push_back(std::make_unique<FooTestDataClass>());
- test_data_classes_.push_back(std::make_unique<QuxTestDataClass>());
- }
-
- void TearDown() override {}
-
- std::list<std::unique_ptr<DumpsysTestDataClass>> test_data_classes_;
-
- std::string PopulateTestSchema();
-};
-
-std::string DumpsysFilterTest::PopulateTestSchema() {
- flatbuffers::FlatBufferBuilder fb_builder(1024);
-
- auto string_private = fb_builder.CreateString("String private");
- auto string_opaque = fb_builder.CreateString("String opaque");
- auto string_anonymized = fb_builder.CreateString("String anonymized");
- auto string_any = fb_builder.CreateString("String any");
-
- std::queue<TableAddFunction> queue;
- for (auto& test_data_class : test_data_classes_) {
- queue.push(test_data_class->GetTable(fb_builder));
- }
-
- testing::DumpsysTestDataRootBuilder builder(fb_builder);
-
- builder.add_string_private(string_private);
- builder.add_string_opaque(string_opaque);
- builder.add_string_anonymized(string_anonymized);
- builder.add_string_any(string_any);
-
- builder.add_int_private(123);
- builder.add_int_opaque(456);
- builder.add_int_anonymized(789);
- builder.add_int_any(0xabc);
-
- while (!queue.empty()) {
- queue.front()(&builder);
- queue.pop();
- }
- fb_builder.Finish(builder.Finish());
-
- return std::string(fb_builder.GetBufferPointer(), fb_builder.GetBufferPointer() + fb_builder.GetSize());
-}
-
-TEST_F(DumpsysFilterTest, filter_as_developer) {
- std::string dumpsys_data = PopulateTestSchema();
- dumpsys::ReflectionSchema reflection_schema(testing::GetBundledSchemaData());
-
- dumpsys::FilterInPlace(dumpsys::FilterType::AS_DEVELOPER, reflection_schema, &dumpsys_data);
-
- const testing::DumpsysTestDataRoot* data_root = GetDumpsysTestDataRoot(dumpsys_data.data());
-
- ASSERT_TRUE(data_root->string_private()->str() == "String private");
- ASSERT_TRUE(data_root->string_opaque()->str() == "String opaque");
- ASSERT_TRUE(data_root->string_anonymized()->str() == "String anonymized");
- ASSERT_TRUE(data_root->string_any()->str() == "String any");
-
- ASSERT_TRUE(data_root->int_private() == 123);
- ASSERT_TRUE(data_root->int_opaque() == 456);
- ASSERT_TRUE(data_root->int_anonymized() == 789);
- ASSERT_TRUE(data_root->int_any() == 0xabc);
-
- ASSERT_EQ(nullptr, data_root->bar_module_data());
-
- const testing::FooTestSchema* foo = data_root->foo_module_data();
-
- ASSERT_EQ(123, foo->foo_int_private());
- ASSERT_EQ(123, foo->foo_int_opaque());
- ASSERT_EQ(123, foo->foo_int_anonymized());
- ASSERT_EQ(123, foo->foo_int_any());
- ASSERT_STREQ("123", foo->foo_int_string()->c_str());
-
- ASSERT_FLOAT_EQ(123.456, foo->foo_float_private());
- ASSERT_FLOAT_EQ(123.456, foo->foo_float_opaque());
- ASSERT_FLOAT_EQ(123.456, foo->foo_float_anonymized());
- ASSERT_FLOAT_EQ(123.456, foo->foo_float_any());
- ASSERT_STREQ("123.456", foo->foo_float_string()->c_str());
-}
-
-TEST_F(DumpsysFilterTest, filter_as_user) {
- std::string dumpsys_data = PopulateTestSchema();
- dumpsys::ReflectionSchema reflection_schema(testing::GetBundledSchemaData());
-
- dumpsys::FilterInPlace(dumpsys::FilterType::AS_USER, reflection_schema, &dumpsys_data);
-
- [[maybe_unused]] const testing::DumpsysTestDataRoot* data_root = GetDumpsysTestDataRoot(dumpsys_data.data());
-
- ASSERT_TRUE(data_root->string_private() == nullptr);
- ASSERT_TRUE(data_root->string_opaque()->str() == "*************");
- ASSERT_TRUE(data_root->string_anonymized()->str() != "String anonymized");
- ASSERT_TRUE(data_root->string_any()->str() == "String any");
-
- ASSERT_TRUE(data_root->int_private() == 0);
- ASSERT_TRUE(data_root->int_opaque() == 0);
- ASSERT_TRUE(data_root->int_anonymized() != 789);
- ASSERT_TRUE(data_root->int_any() == 0xabc);
-
- // bar
- ASSERT_EQ(nullptr, data_root->bar_module_data());
-
- // baz
- const testing::BazTestSchema* baz = data_root->baz_module_data();
- ASSERT_NE(nullptr, baz);
-
- const testing::BazSubTableAny* baz_any = baz->sub_table_any();
- ASSERT_NE(nullptr, baz_any);
- ASSERT_EQ(nullptr, baz->sub_table_anonymized());
- ASSERT_EQ(nullptr, baz->sub_table_opaque());
- ASSERT_EQ(nullptr, baz->sub_table_private());
-
- ASSERT_EQ(0, baz_any->subtable_int_private()); // 1
- ASSERT_EQ(0, baz_any->subtable_int_opaque()); // 2
- ASSERT_NE(3, baz_any->subtable_int_anonymized()); // 3
- ASSERT_EQ(4, baz_any->subtable_int_any()); // 4
- ASSERT_STREQ("Baz Subtable Any", baz_any->subtable_string_any()->c_str());
-
- // foo
- const testing::FooTestSchema* foo = data_root->foo_module_data();
- ASSERT_EQ(0, foo->foo_int_private());
- ASSERT_EQ(0, foo->foo_int_opaque());
- ASSERT_NE(123, foo->foo_int_anonymized());
- ASSERT_EQ(123, foo->foo_int_any());
- ASSERT_STREQ("123", foo->foo_int_string()->c_str());
- ASSERT_FLOAT_EQ(0.0, foo->foo_float_private());
- ASSERT_FLOAT_EQ(0.0, foo->foo_float_opaque());
- ASSERT_THAT(foo->foo_float_anonymized(), Not(FloatEq(123.456)));
- ASSERT_FLOAT_EQ(123.456, foo->foo_float_any());
- ASSERT_STREQ("123.456", foo->foo_float_string()->c_str());
-
- // qux
- const testing::QuxTestSchema* qux = data_root->qux_module_data();
- ASSERT_EQ(0, qux->qux_int_private());
- ASSERT_EQ(0, qux->qux_int_opaque());
- ASSERT_NE(789, qux->qux_int_anonymized());
- ASSERT_EQ(0xabc, qux->qux_int_any());
- ASSERT_STREQ("Qux Module String", qux->qux_string_name()->c_str());
-}
-
-} // namespace testing
diff --git a/gd/dumpsys/init_flags.cc b/gd/dumpsys/init_flags.cc
deleted file mode 100644
index 7efbb905e..000000000
--- a/gd/dumpsys/init_flags.cc
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "common/init_flags.h"
-#include "dumpsys/init_flags.h"
-#include "init_flags_generated.h"
-
-flatbuffers::Offset<bluetooth::common::InitFlagsData> bluetooth::dumpsys::InitFlags::Dump(
- flatbuffers::FlatBufferBuilder* fb_builder) {
- auto title = fb_builder->CreateString("----- Init Flags -----");
- common::InitFlagsDataBuilder builder(*fb_builder);
- builder.add_title(title);
- builder.add_gd_advertising_enabled(bluetooth::common::init_flags::gd_advertising_is_enabled());
- builder.add_gd_scanning_enabled(bluetooth::common::init_flags::gd_scanning_is_enabled());
- builder.add_gd_security_enabled(bluetooth::common::init_flags::gd_security_is_enabled());
- builder.add_gd_acl_enabled(bluetooth::common::init_flags::gd_acl_is_enabled());
- builder.add_gd_hci_enabled(bluetooth::common::init_flags::gd_hci_is_enabled());
- builder.add_gd_controller_enabled(bluetooth::common::init_flags::gd_controller_is_enabled());
- builder.add_gd_core_enabled(bluetooth::common::init_flags::gd_core_is_enabled());
- builder.add_btaa_hci_log_enabled(bluetooth::common::init_flags::btaa_hci_is_enabled());
- return builder.Finish();
-}
diff --git a/gd/dumpsys/init_flags.h b/gd/dumpsys/init_flags.h
deleted file mode 100644
index a46fba35b..000000000
--- a/gd/dumpsys/init_flags.h
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "flatbuffers/flatbuffers.h"
-#include "init_flags_generated.h"
-
-namespace bluetooth {
-namespace dumpsys {
-
-class InitFlags {
- public:
- static flatbuffers::Offset<common::InitFlagsData> Dump(flatbuffers::FlatBufferBuilder* fb_builder);
-};
-
-} // namespace dumpsys
-} // namespace bluetooth
diff --git a/gd/dumpsys/internal/filter_internal.cc b/gd/dumpsys/internal/filter_internal.cc
deleted file mode 100644
index 3a7d88112..000000000
--- a/gd/dumpsys/internal/filter_internal.cc
+++ /dev/null
@@ -1,247 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <algorithm>
-#include <string>
-
-#include "dumpsys/internal/filter_internal.h"
-#include "flatbuffers/flatbuffers.h"
-#include "flatbuffers/idl.h"
-#include "os/log.h"
-
-#define DBG 0
-
-using namespace bluetooth;
-using namespace dumpsys;
-
-constexpr flatbuffers::voffset_t kErasedFromTable = 0;
-constexpr bool kFieldIsNotPopulated = true;
-constexpr bool kFieldHasBeenFiltered = true;
-constexpr bool kFieldContinueFiltering = false;
-
-void internal::ScrubFromTable(flatbuffers::Table* table, flatbuffers::voffset_t field_offset) {
- ASSERT(table != nullptr);
- uint8_t* vtable = const_cast<uint8_t*>(table->GetVTable());
- vtable[field_offset] = kErasedFromTable;
-}
-
-void internal::ReplaceInString(flatbuffers::String* string, int c) {
- uint8_t* p = const_cast<uint8_t*>(string->Data());
- memset(p, c, string->size());
-}
-
-void internal::RandomizeInString(flatbuffers::String* string) {
- std::size_t hash = std::hash<std::string>{}(string->str());
- std::string hashed_string = std::to_string(hash);
- ReplaceInString(string, ' ');
- size_t len = std::min(static_cast<size_t>(string->size()), hashed_string.size());
- uint8_t* p = const_cast<uint8_t*>(string->Data());
- memcpy(p, hashed_string.c_str(), len);
-}
-
-const char* internal::PrivacyLevelName(PrivacyLevel privacy_level) {
- switch (privacy_level) {
- case kPrivate:
- return "Private";
- break;
- case kOpaque:
- return "Opaque";
- break;
- case kAnonymized:
- return "Anonymized";
- break;
- case kAny:
- return "Any";
- break;
- }
-};
-internal::PrivacyLevel internal::GetPrivacyLevelAttribute(const std::string& string) {
- if (string == "Any") {
- return kAny;
- } else if (string == "Anonymized") {
- return kAnonymized;
- } else if (string == "Opaque") {
- return kOpaque;
- } else if (string == "Private") {
- return kPrivate;
- }
- return kDefaultPrivacyLevel;
-}
-
-internal::PrivacyLevel internal::FindFieldPrivacyLevel(const reflection::Field& field) {
- PrivacyLevel privacy_level = kDefaultPrivacyLevel;
-
- if (field.attributes() != nullptr) {
- auto key = field.attributes()->LookupByKey(kPrivacyAttributeKeyword);
- if (key != nullptr) {
- privacy_level = internal::GetPrivacyLevelAttribute(key->value()->str());
- }
- }
- return privacy_level;
-}
-
-const reflection::Object* internal::FindReflectionObject(
- const flatbuffers::Vector<flatbuffers::Offset<reflection::Object>>* objects, const flatbuffers::String* name) {
- ASSERT(objects != nullptr);
- ASSERT(name != nullptr);
- for (auto it = objects->cbegin(); it != objects->cend(); ++it) {
- if (it->name()->str() == name->str()) {
- return *it;
- }
- }
- return nullptr;
-}
-
-bool internal::FilterTypeBool(const reflection::Field& field, flatbuffers::Table* table, PrivacyLevel privacy_level) {
- ASSERT(table != nullptr);
-
- // TODO(cmanton) Figure out boolean filtering
- return kFieldHasBeenFiltered;
-}
-
-bool internal::FilterTypeInteger(
- const reflection::Field& field, flatbuffers::Table* table, PrivacyLevel privacy_level) {
- ASSERT(table != nullptr);
- ASSERT(flatbuffers::IsInteger(field.type()->base_type()));
-
- int32_t default_val = flatbuffers::GetFieldDefaultI<int32_t>(field);
- flatbuffers::voffset_t field_offset = field.offset();
- [[maybe_unused]] int32_t val = table->GetField<int32_t>(field_offset, default_val);
-
- switch (privacy_level) {
- case kPrivate:
- flatbuffers::SetField<int32_t>(table, field, default_val);
- internal::ScrubFromTable(table, field_offset);
- break;
- case kOpaque:
- flatbuffers::SetField<int32_t>(table, field, default_val);
- break;
- case kAnonymized: {
- auto target_field = flatbuffers::GetFieldI<int32_t>(*table, field);
- int32_t new_val = static_cast<int32_t>(std::hash<std::string>{}(std::to_string(target_field)));
- flatbuffers::SetField<int32_t>(table, field, new_val);
- } break;
- default:
- case kAny:
- break;
- }
-
- if (DBG) {
- LOG_INFO(
- "Integer Field_name:%s privacy_level:%s old_value:%d / 0x%x ==> new_value:%d\n",
- field.name()->c_str(),
- PrivacyLevelName(privacy_level),
- val,
- val,
- table->GetField<int32_t>(field_offset, default_val));
- }
- return kFieldHasBeenFiltered;
-}
-
-bool internal::FilterTypeFloat(const reflection::Field& field, flatbuffers::Table* table, PrivacyLevel privacy_level) {
- ASSERT(table != nullptr);
- ASSERT(flatbuffers::IsFloat(field.type()->base_type()));
-
- float default_val = flatbuffers::GetFieldDefaultI<float>(field);
- flatbuffers::voffset_t field_offset = field.offset();
- [[maybe_unused]] float val = table->GetField<float>(field_offset, default_val);
- switch (privacy_level) {
- case kPrivate:
- flatbuffers::SetField<float>(table, field, default_val);
- internal::ScrubFromTable(table, field_offset);
- break;
- case kOpaque:
- flatbuffers::SetField<float>(table, field, default_val);
- break;
- case kAnonymized: {
- auto target_field = flatbuffers::GetFieldF<float>(*table, field);
- int32_t new_val = static_cast<float>(std::hash<std::string>{}(std::to_string(target_field)));
- flatbuffers::SetField<float>(table, field, new_val);
- } break;
- default:
- case kAny:
- break;
- }
- if (DBG) {
- LOG_INFO(
- "Float Field_name:%s privacy_level:%s old_value:%f ==> new_value:%f",
- field.name()->c_str(),
- PrivacyLevelName(privacy_level),
- val,
- table->GetField<float>(field_offset, default_val));
- }
- return kFieldHasBeenFiltered;
-}
-
-bool internal::FilterTypeString(const reflection::Field& field, flatbuffers::Table* table, PrivacyLevel privacy_level) {
- ASSERT(table != nullptr);
- ASSERT(field.type()->base_type() == reflection::BaseType::String);
-
- flatbuffers::voffset_t field_offset = field.offset();
-
- const flatbuffers::String* string = flatbuffers::GetFieldS(*table, field);
- if (string == nullptr) {
- return kFieldIsNotPopulated;
- // Field is not populated
- }
- ASSERT(string != nullptr);
- flatbuffers::String* mutable_string = const_cast<flatbuffers::String*>(string);
-
- [[maybe_unused]] std::string old_string(string->str());
- switch (privacy_level) {
- case kPrivate:
- internal::ReplaceInString(mutable_string, '*');
- internal::ScrubFromTable(table, field_offset);
- break;
- case kOpaque:
- internal::ReplaceInString(mutable_string, '*');
- break;
- case kAnonymized:
- internal::RandomizeInString(mutable_string);
- break;
- default:
- case kAny:
- break;
- }
- if (DBG) {
- LOG_INFO(
- "%s Field_name:%s size:%u privacy_level:%s old_string:%s ==> new_string:%s",
- __func__,
- field.name()->c_str(),
- string->size(),
- PrivacyLevelName(privacy_level),
- old_string.c_str(),
- string->c_str());
- }
- return kFieldHasBeenFiltered;
-}
-
-bool internal::FilterTypeStruct(const reflection::Field& field, flatbuffers::Table* table, PrivacyLevel privacy_level) {
- ASSERT(table != nullptr);
- ASSERT(!flatbuffers::IsScalar(field.type()->base_type()));
-
- flatbuffers::voffset_t field_offset = field.offset();
-
- if (privacy_level != kAny) {
- flatbuffers::SetFieldT(table, field, nullptr);
- internal::ScrubFromTable(table, field_offset);
- if (DBG) {
- LOG_INFO(
- " Table Removing field name:%s privacy_level:%s", field.name()->c_str(), PrivacyLevelName(privacy_level));
- }
- }
- return kFieldContinueFiltering;
-}
diff --git a/gd/dumpsys/internal/filter_internal.h b/gd/dumpsys/internal/filter_internal.h
deleted file mode 100644
index f2668c4c4..000000000
--- a/gd/dumpsys/internal/filter_internal.h
+++ /dev/null
@@ -1,123 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <string>
-
-#include "flatbuffers/flatbuffers.h"
-#include "flatbuffers/idl.h"
-
-namespace bluetooth {
-namespace dumpsys {
-namespace internal {
-
-constexpr char kPrivacyAttributeKeyword[] = "privacy";
-
-enum PrivacyLevel {
- kPrivate = 0,
- kOpaque = 1,
- kAnonymized = 2,
- kAny = 4,
- kDefaultPrivacyLevel = kPrivate,
-};
-
-/**
- * Remove the field offset from flatbuffer table eliminating ability to
- * access value.
- *
- * @param table Table under consideration for field removeal
- * @param field_offset Virtual offset of field into table.
- */
-void ScrubFromTable(flatbuffers::Table* table, flatbuffers::voffset_t field_offset);
-
-/**
- * Overwrite ihe contents of flatbuffer string with the integer value proviced.
- * The entire size of the string will be set to the value provided.
- *
- * @param string Flatbuffer string under consideration for content changing.
- * @param value Value to overwrite the string contents.
- */
-void ReplaceInString(flatbuffers::String* string, int value);
-
-/**
- * Overwrite the contents of flatbuffer string with a hashed value.
- * The portion of the string greater than the hash value will be set to SPACE.
- * If the string is not large enough for the entire hash value, the hash
- * value will be truncated to the size of the string.
- *
- * @param string Flatbuffer string under consideration for content changing.
- */
-void RandomizeInString(flatbuffers::String* string);
-
-/**
- * Returns the privacy level name corresponding to the axtual numeric level.
- *
- * @param privacy_level PrivacyLevel
- *
- * @return Name of privacy level.
- */
-const char* PrivacyLevelName(PrivacyLevel privacy_level);
-
-/**
- * Returns the privacy level for the given field. If there is no explicitly
- * privacy level for this field, the default privacy level is returned.
- *
- * @param field The reflection field for the schema
- *
- * @return Privacy level enumeration value
- */
-PrivacyLevel FindFieldPrivacyLevel(const reflection::Field& field);
-
-/**
- * Returns the privacy level for given privacy level keyword name.
- * If the privacy level for this field, the default privacy level is returned.
- *
- * @param name The privacy level name.
- *
- * @return Privacy level enumeration value.
- */
-PrivacyLevel GetPrivacyLevelAttribute(const std::string& name);
-
-/**
- * Find a the reflection object that corresponds to the name provided.
- * Returns nullptr is not found.
- *
- * @param objects Vector container of flatbuffer objects
- * @param name Flatbuffer string name to search
- *
- * @return Reflection object if found, nullptr otherwise.
- */
-const reflection::Object* FindReflectionObject(
- const flatbuffers::Vector<flatbuffers::Offset<reflection::Object>>* objects, const flatbuffers::String* name);
-
-/**
- * Process and filter the respective data types.
- *
- * @param field The reflection field schema.
- * @param table The mutable table data corresponding to the schema.
- * @param privacy_level The privacy level in which to filter the data.
- *
- * @return true if successfully filtered, false otherwise.
- */
-bool FilterTypeBool(const reflection::Field& field, flatbuffers::Table* table, PrivacyLevel privacy_level);
-bool FilterTypeInteger(const reflection::Field& field, flatbuffers::Table* table, PrivacyLevel privacy_level);
-bool FilterTypeFloat(const reflection::Field& field, flatbuffers::Table* table, PrivacyLevel privacy_level);
-bool FilterTypeString(const reflection::Field& field, flatbuffers::Table* table, PrivacyLevel privacy_level);
-bool FilterTypeStruct(const reflection::Field& field, flatbuffers::Table* table, PrivacyLevel privacy_level);
-
-} // namespace internal
-} // namespace dumpsys
-} // namespace bluetooth
diff --git a/gd/dumpsys/internal/filter_internal_test.cc b/gd/dumpsys/internal/filter_internal_test.cc
deleted file mode 100644
index d3c780181..000000000
--- a/gd/dumpsys/internal/filter_internal_test.cc
+++ /dev/null
@@ -1,416 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "dumpsys/internal/filter_internal.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "dumpsys/internal/test_data/float_bfbs.h"
-#include "dumpsys/internal/test_data/float_generated.h"
-#include "dumpsys/internal/test_data/integer_bfbs.h"
-#include "dumpsys/internal/test_data/integer_generated.h"
-#include "dumpsys/internal/test_data/string_bfbs.h"
-#include "dumpsys/internal/test_data/string_generated.h"
-#include "dumpsys/internal/test_data/struct_bfbs.h"
-#include "dumpsys/internal/test_data/struct_generated.h"
-#include "os/log.h"
-
-namespace testing {
-
-class DumpsysFilterInternalTest : public Test {
- protected:
- void SetUp() override {}
- void TearDown() override {}
-
- flatbuffers::Table* GetMutableTable() const {
- return flatbuffers::GetMutableRoot<flatbuffers::Table>(fb_builder_.GetBufferPointer());
- }
-
- void ParseReflectionSchema(unsigned char* bfbs, unsigned int bfbs_len) {
- ASSERT_TRUE(reflection_schema_.empty());
- reflection_schema_ = std::move(std::vector<const uint8_t>(bfbs, bfbs + bfbs_len));
- flatbuffers::Verifier verifier(reflection_schema_.data(), reflection_schema_.size());
- ASSERT_TRUE(reflection::VerifySchemaBuffer(verifier));
- schema_ = reflection::GetSchema(reflection_schema_.data());
- ASSERT_TRUE(schema_ != nullptr);
- }
-
- const reflection::Schema* schema_{nullptr};
- flatbuffers::FlatBufferBuilder fb_builder_ = std::move(flatbuffers::FlatBufferBuilder(1024));
-
- private:
- std::vector<const uint8_t> reflection_schema_;
-};
-
-class DumpsysFilterInternalIntegerTest : public DumpsysFilterInternalTest {
- protected:
- void SetUp() override {
- this->ParseReflectionSchema(integer_bfbs, integer_bfbs_len);
- }
-
- const testing::TestTableInteger* CreateInteger(int32_t value) {
- TestTableIntegerBuilder builder(fb_builder_);
- builder.add_test_int(value);
- fb_builder_.Finish(builder.Finish());
- return GetTestTableInteger(fb_builder_.GetBufferPointer());
- }
-};
-
-class DumpsysFilterInternalFloatTest : public DumpsysFilterInternalTest {
- protected:
- void SetUp() override {
- this->ParseReflectionSchema(float_bfbs, float_bfbs_len);
- }
-
- const testing::TestTableFloat* CreateFloat(double value) {
- TestTableFloatBuilder builder(fb_builder_);
- builder.add_test_float(value);
- fb_builder_.Finish(builder.Finish());
- return GetTestTableFloat(fb_builder_.GetBufferPointer());
- }
-};
-
-class DumpsysFilterInternalStringTest : public DumpsysFilterInternalTest {
- protected:
- void SetUp() override {
- this->ParseReflectionSchema(string_bfbs, string_bfbs_len);
- }
-
- const testing::TestTableString* CreateString(std::string string) {
- auto test_string = fb_builder_.CreateString(string);
- TestTableStringBuilder builder(fb_builder_);
- builder.add_test_string(test_string);
- fb_builder_.Finish(builder.Finish());
- return GetTestTableString(fb_builder_.GetBufferPointer());
- }
-};
-
-class DumpsysFilterInternalStructTest : public DumpsysFilterInternalTest {
- protected:
- void SetUp() override {
- this->ParseReflectionSchema(struct_bfbs, struct_bfbs_len);
- }
-
- flatbuffers::Offset<TestSubTable> CreateSubTable(int val) {
- TestSubTableBuilder builder(fb_builder_);
- builder.add_placeholder(val);
- return builder.Finish();
- }
-
- const testing::TestTableStruct* CreateStruct(int val) {
- auto sub_table = CreateSubTable(val);
-
- TestTableStructBuilder builder(fb_builder_);
- builder.add_sub_table(sub_table);
- fb_builder_.Finish(builder.Finish());
- return GetTestTableStruct(fb_builder_.GetBufferPointer());
- }
-};
-
-TEST_F(DumpsysFilterInternalIntegerTest, filter_type_integer_any) {
- const testing::TestTableInteger* test_table = CreateInteger(123);
- ASSERT_EQ(123, test_table->test_int());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeInteger(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kAny);
- }
- ASSERT_EQ(123, test_table->test_int());
-}
-
-TEST_F(DumpsysFilterInternalIntegerTest, filter_type_integer_anonymized) {
- const testing::TestTableInteger* test_table = CreateInteger(123);
- ASSERT_EQ(123, test_table->test_int());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeInteger(
- **it, table, bluetooth::dumpsys::internal::PrivacyLevel::kAnonymized);
- }
- ASSERT_NE(123, test_table->test_int());
-}
-
-TEST_F(DumpsysFilterInternalIntegerTest, filter_type_integer_opaque) {
- const testing::TestTableInteger* test_table = CreateInteger(123);
- ASSERT_EQ(123, test_table->test_int());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeInteger(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kOpaque);
- }
- ASSERT_EQ(0, test_table->test_int());
-}
-
-TEST_F(DumpsysFilterInternalIntegerTest, filter_type_integer_privacy) {
- const testing::TestTableInteger* test_table = CreateInteger(123);
- ASSERT_EQ(123, test_table->test_int());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeInteger(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kPrivate);
- }
- ASSERT_EQ(0, test_table->test_int());
-}
-
-TEST_F(DumpsysFilterInternalFloatTest, filter_type_float_any) {
- const testing::TestTableFloat* test_table = CreateFloat(1.23);
- ASSERT_FLOAT_EQ(1.23, test_table->test_float());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeFloat(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kAny);
- }
- ASSERT_FLOAT_EQ(1.23, test_table->test_float());
-}
-
-TEST_F(DumpsysFilterInternalFloatTest, filter_type_float_anonymized) {
- const testing::TestTableFloat* test_table = CreateFloat(1.23);
- ASSERT_FLOAT_EQ(1.23, test_table->test_float());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeFloat(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kAnonymized);
- }
- ASSERT_THAT(test_table->test_float(), Not(FloatEq(1.23)));
-}
-
-TEST_F(DumpsysFilterInternalFloatTest, filter_type_float_opaque) {
- const testing::TestTableFloat* test_table = CreateFloat(1.23);
- ASSERT_FLOAT_EQ(1.23, test_table->test_float());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeFloat(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kOpaque);
- }
- ASSERT_FLOAT_EQ(0.0, test_table->test_float());
-}
-
-TEST_F(DumpsysFilterInternalFloatTest, filter_type_float_private) {
- const testing::TestTableFloat* test_table = CreateFloat(1.23);
- ASSERT_FLOAT_EQ(1.23, test_table->test_float());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeFloat(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kPrivate);
- }
- ASSERT_FLOAT_EQ(0.0, test_table->test_float());
-}
-
-TEST_F(DumpsysFilterInternalStringTest, filter_type_string_any) {
- const testing::TestTableString* test_table = CreateString("This is a string");
- ASSERT_STREQ("This is a string", test_table->test_string()->c_str());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeString(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kAny);
- }
- ASSERT_STREQ("This is a string", test_table->test_string()->c_str());
-}
-
-TEST_F(DumpsysFilterInternalStringTest, filter_type_string_anonymous) {
- const testing::TestTableString* test_table = CreateString("This is a string");
- ASSERT_STREQ("This is a string", test_table->test_string()->c_str());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeString(
- **it, table, bluetooth::dumpsys::internal::PrivacyLevel::kAnonymized);
- }
- ASSERT_NE("This is a string", test_table->test_string()->c_str());
-}
-
-TEST_F(DumpsysFilterInternalStringTest, filter_type_string_anonymous_small) {
- const testing::TestTableString* test_table = CreateString("A");
- ASSERT_STREQ("A", test_table->test_string()->c_str());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeString(
- **it, table, bluetooth::dumpsys::internal::PrivacyLevel::kAnonymized);
- }
- ASSERT_NE("A", test_table->test_string()->c_str());
-}
-
-TEST_F(DumpsysFilterInternalStringTest, filter_type_string_anonymous_large) {
- const testing::TestTableString* test_table = CreateString("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz");
- ASSERT_STREQ("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz", test_table->test_string()->c_str());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeString(
- **it, table, bluetooth::dumpsys::internal::PrivacyLevel::kAnonymized);
- }
- ASSERT_NE("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz", test_table->test_string()->c_str());
-}
-
-TEST_F(DumpsysFilterInternalStringTest, filter_type_string_opaque) {
- const testing::TestTableString* test_table = CreateString("This is a string");
- ASSERT_STREQ("This is a string", test_table->test_string()->c_str());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeString(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kOpaque);
- }
-
- std::string opaque_expected(strlen("This is a string"), '*');
- ASSERT_STREQ(opaque_expected.c_str(), test_table->test_string()->c_str());
-}
-
-TEST_F(DumpsysFilterInternalStringTest, filter_type_string_private) {
- const testing::TestTableString* test_table = CreateString("This is a string");
- ASSERT_STREQ("This is a string", test_table->test_string()->c_str());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeString(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kPrivate);
- }
- ASSERT_EQ(nullptr, test_table->test_string());
-}
-
-TEST_F(DumpsysFilterInternalStringTest, filter_type_string_private_small) {
- const testing::TestTableString* test_table = CreateString("A");
- ASSERT_STREQ("A", test_table->test_string()->c_str());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeString(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kPrivate);
- }
- ASSERT_EQ(nullptr, test_table->test_string());
-}
-
-TEST_F(DumpsysFilterInternalStructTest, filter_type_struct_any) {
- const testing::TestTableStruct* test_table = CreateStruct(456);
- ASSERT_EQ(456, test_table->sub_table()->placeholder());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeStruct(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kAny);
- }
- ASSERT_EQ(456, test_table->sub_table()->placeholder());
-}
-
-TEST_F(DumpsysFilterInternalStructTest, filter_type_struct_anonymous) {
- const testing::TestTableStruct* test_table = CreateStruct(456);
- ASSERT_EQ(456, test_table->sub_table()->placeholder());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeStruct(
- **it, table, bluetooth::dumpsys::internal::PrivacyLevel::kAnonymized);
- }
- ASSERT_EQ(nullptr, test_table->sub_table());
-}
-
-TEST_F(DumpsysFilterInternalStructTest, filter_type_struct_opaque) {
- const testing::TestTableStruct* test_table = CreateStruct(456);
- ASSERT_EQ(456, test_table->sub_table()->placeholder());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeStruct(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kOpaque);
- }
- ASSERT_EQ(nullptr, test_table->sub_table());
-}
-
-TEST_F(DumpsysFilterInternalStructTest, filter_type_struct_private) {
- const testing::TestTableStruct* test_table = CreateStruct(456);
- ASSERT_EQ(456, test_table->sub_table()->placeholder());
-
- flatbuffers::Table* table = GetMutableTable();
-
- const reflection::Object* object = schema_->root_table();
- ASSERT_TRUE(object != nullptr);
-
- for (auto it = object->fields()->cbegin(); it != object->fields()->cend(); ++it) {
- bluetooth::dumpsys::internal::FilterTypeStruct(**it, table, bluetooth::dumpsys::internal::PrivacyLevel::kPrivate);
- }
- ASSERT_EQ(nullptr, test_table->sub_table());
-}
-
-} // namespace testing
diff --git a/gd/dumpsys/internal/test_data/float.bfbs b/gd/dumpsys/internal/test_data/float.bfbs
deleted file mode 100644
index 9eb4707e1..000000000
--- a/gd/dumpsys/internal/test_data/float.bfbs
+++ /dev/null
Binary files differ
diff --git a/gd/dumpsys/internal/test_data/float.fbs b/gd/dumpsys/internal/test_data/float.fbs
deleted file mode 100644
index 2f832e685..000000000
--- a/gd/dumpsys/internal/test_data/float.fbs
+++ /dev/null
@@ -1,7 +0,0 @@
-namespace testing;
-
-table TestTableFloat {
- test_float:float;
-}
-
-root_type TestTableFloat;
diff --git a/gd/dumpsys/internal/test_data/float_bfbs.h b/gd/dumpsys/internal/test_data/float_bfbs.h
deleted file mode 100644
index d2da54d5a..000000000
--- a/gd/dumpsys/internal/test_data/float_bfbs.h
+++ /dev/null
@@ -1,13 +0,0 @@
-unsigned char float_bfbs[] = {
- 0x18, 0x00, 0x00, 0x00, 0x42, 0x46, 0x42, 0x53, 0x10, 0x00, 0x1c, 0x00, 0x04, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x10,
- 0x00, 0x14, 0x00, 0x18, 0x00, 0x10, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x1c, 0x00,
- 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x01, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x10, 0x00, 0x04, 0x00, 0x08, 0x00, 0x00, 0x00, 0x0c,
- 0x00, 0x0c, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00,
- 0x00, 0x00, 0x2c, 0x00, 0x00, 0x00, 0x16, 0x00, 0x00, 0x00, 0x74, 0x65, 0x73, 0x74, 0x69, 0x6e, 0x67, 0x2e, 0x54,
- 0x65, 0x73, 0x74, 0x54, 0x61, 0x62, 0x6c, 0x65, 0x46, 0x6c, 0x6f, 0x61, 0x74, 0x00, 0x00, 0x0c, 0x00, 0x12, 0x00,
- 0x08, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x06, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x18, 0x00, 0x00,
- 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x08, 0x00, 0x07, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x0b, 0x0a, 0x00, 0x00, 0x00, 0x74, 0x65, 0x73, 0x74, 0x5f, 0x66, 0x6c, 0x6f, 0x61, 0x74, 0x00, 0x00};
-unsigned int float_bfbs_len = 208;
diff --git a/gd/dumpsys/internal/test_data/float_generated.h b/gd/dumpsys/internal/test_data/float_generated.h
deleted file mode 100644
index cb54e51f2..000000000
--- a/gd/dumpsys/internal/test_data/float_generated.h
+++ /dev/null
@@ -1,81 +0,0 @@
-// automatically generated by the FlatBuffers compiler, do not modify
-
-#ifndef FLATBUFFERS_GENERATED_FLOAT_TESTING_H_
-#define FLATBUFFERS_GENERATED_FLOAT_TESTING_H_
-
-#include "flatbuffers/flatbuffers.h"
-
-namespace testing {
-
-struct TestTableFloat;
-struct TestTableFloatBuilder;
-
-struct TestTableFloat FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
- typedef TestTableFloatBuilder Builder;
- enum FlatBuffersVTableOffset FLATBUFFERS_VTABLE_UNDERLYING_TYPE { VT_TEST_FLOAT = 4 };
- float test_float() const {
- return GetField<float>(VT_TEST_FLOAT, 0.0f);
- }
- bool Verify(flatbuffers::Verifier& verifier) const {
- return VerifyTableStart(verifier) && VerifyField<float>(verifier, VT_TEST_FLOAT) && verifier.EndTable();
- }
-};
-
-struct TestTableFloatBuilder {
- typedef TestTableFloat Table;
- flatbuffers::FlatBufferBuilder& fbb_;
- flatbuffers::uoffset_t start_;
- void add_test_float(float test_float) {
- fbb_.AddElement<float>(TestTableFloat::VT_TEST_FLOAT, test_float, 0.0f);
- }
- explicit TestTableFloatBuilder(flatbuffers::FlatBufferBuilder& _fbb) : fbb_(_fbb) {
- start_ = fbb_.StartTable();
- }
- TestTableFloatBuilder& operator=(const TestTableFloatBuilder&);
- flatbuffers::Offset<TestTableFloat> Finish() {
- const auto end = fbb_.EndTable(start_);
- auto o = flatbuffers::Offset<TestTableFloat>(end);
- return o;
- }
-};
-
-inline flatbuffers::Offset<TestTableFloat> CreateTestTableFloat(
- flatbuffers::FlatBufferBuilder& _fbb, float test_float = 0.0f) {
- TestTableFloatBuilder builder_(_fbb);
- builder_.add_test_float(test_float);
- return builder_.Finish();
-}
-
-inline const testing::TestTableFloat* GetTestTableFloat(const void* buf) {
- return flatbuffers::GetRoot<testing::TestTableFloat>(buf);
-}
-
-inline const testing::TestTableFloat* GetSizePrefixedTestTableFloat(const void* buf) {
- return flatbuffers::GetSizePrefixedRoot<testing::TestTableFloat>(buf);
-}
-
-inline bool VerifyTestTableFloatBuffer(flatbuffers::Verifier& verifier) {
- return verifier.VerifyBuffer<testing::TestTableFloat>(nullptr);
-}
-
-inline bool VerifySizePrefixedTestTableFloatBuffer(flatbuffers::Verifier& verifier) {
- return verifier.VerifySizePrefixedBuffer<testing::TestTableFloat>(nullptr);
-}
-
-inline const char* TestTableFloatExtension() {
- return "bfbs";
-}
-
-inline void FinishTestTableFloatBuffer(
- flatbuffers::FlatBufferBuilder& fbb, flatbuffers::Offset<testing::TestTableFloat> root) {
- fbb.Finish(root);
-}
-
-inline void FinishSizePrefixedTestTableFloatBuffer(
- flatbuffers::FlatBufferBuilder& fbb, flatbuffers::Offset<testing::TestTableFloat> root) {
- fbb.FinishSizePrefixed(root);
-}
-
-} // namespace testing
-
-#endif // FLATBUFFERS_GENERATED_FLOAT_TESTING_H_
diff --git a/gd/dumpsys/internal/test_data/integer.bfbs b/gd/dumpsys/internal/test_data/integer.bfbs
deleted file mode 100644
index 9d036e3b3..000000000
--- a/gd/dumpsys/internal/test_data/integer.bfbs
+++ /dev/null
Binary files differ
diff --git a/gd/dumpsys/internal/test_data/integer.fbs b/gd/dumpsys/internal/test_data/integer.fbs
deleted file mode 100644
index b8a5569eb..000000000
--- a/gd/dumpsys/internal/test_data/integer.fbs
+++ /dev/null
@@ -1,7 +0,0 @@
-namespace testing;
-
-table TestTableInteger {
- test_int:int;
-}
-
-root_type TestTableInteger;
diff --git a/gd/dumpsys/internal/test_data/integer_bfbs.h b/gd/dumpsys/internal/test_data/integer_bfbs.h
deleted file mode 100644
index 60720e964..000000000
--- a/gd/dumpsys/internal/test_data/integer_bfbs.h
+++ /dev/null
@@ -1,14 +0,0 @@
-unsigned char integer_bfbs[] = {
- 0x18, 0x00, 0x00, 0x00, 0x42, 0x46, 0x42, 0x53, 0x10, 0x00, 0x1c, 0x00, 0x04, 0x00, 0x08, 0x00, 0x0c, 0x00,
- 0x10, 0x00, 0x14, 0x00, 0x18, 0x00, 0x10, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00,
- 0x1c, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x10, 0x00, 0x04, 0x00,
- 0x08, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
- 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x74, 0x65,
- 0x73, 0x74, 0x69, 0x6e, 0x67, 0x2e, 0x54, 0x65, 0x73, 0x74, 0x54, 0x61, 0x62, 0x6c, 0x65, 0x49, 0x6e, 0x74,
- 0x65, 0x67, 0x65, 0x72, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x12, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x00, 0x00,
- 0x06, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x18, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x06, 0x00, 0x08, 0x00, 0x07, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x08, 0x00,
- 0x00, 0x00, 0x74, 0x65, 0x73, 0x74, 0x5f, 0x69, 0x6e, 0x74, 0x00, 0x00, 0x00, 0x00};
-unsigned int integer_bfbs_len = 212;
diff --git a/gd/dumpsys/internal/test_data/integer_generated.h b/gd/dumpsys/internal/test_data/integer_generated.h
deleted file mode 100644
index 16d18bf1d..000000000
--- a/gd/dumpsys/internal/test_data/integer_generated.h
+++ /dev/null
@@ -1,81 +0,0 @@
-// automatically generated by the FlatBuffers compiler, do not modify
-
-#ifndef FLATBUFFERS_GENERATED_INTEGER_TESTING_H_
-#define FLATBUFFERS_GENERATED_INTEGER_TESTING_H_
-
-#include "flatbuffers/flatbuffers.h"
-
-namespace testing {
-
-struct TestTableInteger;
-struct TestTableIntegerBuilder;
-
-struct TestTableInteger FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
- typedef TestTableIntegerBuilder Builder;
- enum FlatBuffersVTableOffset FLATBUFFERS_VTABLE_UNDERLYING_TYPE { VT_TEST_INT = 4 };
- int32_t test_int() const {
- return GetField<int32_t>(VT_TEST_INT, 0);
- }
- bool Verify(flatbuffers::Verifier& verifier) const {
- return VerifyTableStart(verifier) && VerifyField<int32_t>(verifier, VT_TEST_INT) && verifier.EndTable();
- }
-};
-
-struct TestTableIntegerBuilder {
- typedef TestTableInteger Table;
- flatbuffers::FlatBufferBuilder& fbb_;
- flatbuffers::uoffset_t start_;
- void add_test_int(int32_t test_int) {
- fbb_.AddElement<int32_t>(TestTableInteger::VT_TEST_INT, test_int, 0);
- }
- explicit TestTableIntegerBuilder(flatbuffers::FlatBufferBuilder& _fbb) : fbb_(_fbb) {
- start_ = fbb_.StartTable();
- }
- TestTableIntegerBuilder& operator=(const TestTableIntegerBuilder&);
- flatbuffers::Offset<TestTableInteger> Finish() {
- const auto end = fbb_.EndTable(start_);
- auto o = flatbuffers::Offset<TestTableInteger>(end);
- return o;
- }
-};
-
-inline flatbuffers::Offset<TestTableInteger> CreateTestTableInteger(
- flatbuffers::FlatBufferBuilder& _fbb, int32_t test_int = 0) {
- TestTableIntegerBuilder builder_(_fbb);
- builder_.add_test_int(test_int);
- return builder_.Finish();
-}
-
-inline const testing::TestTableInteger* GetTestTableInteger(const void* buf) {
- return flatbuffers::GetRoot<testing::TestTableInteger>(buf);
-}
-
-inline const testing::TestTableInteger* GetSizePrefixedTestTableInteger(const void* buf) {
- return flatbuffers::GetSizePrefixedRoot<testing::TestTableInteger>(buf);
-}
-
-inline bool VerifyTestTableIntegerBuffer(flatbuffers::Verifier& verifier) {
- return verifier.VerifyBuffer<testing::TestTableInteger>(nullptr);
-}
-
-inline bool VerifySizePrefixedTestTableIntegerBuffer(flatbuffers::Verifier& verifier) {
- return verifier.VerifySizePrefixedBuffer<testing::TestTableInteger>(nullptr);
-}
-
-inline const char* TestTableIntegerExtension() {
- return "bfbs";
-}
-
-inline void FinishTestTableIntegerBuffer(
- flatbuffers::FlatBufferBuilder& fbb, flatbuffers::Offset<testing::TestTableInteger> root) {
- fbb.Finish(root);
-}
-
-inline void FinishSizePrefixedTestTableIntegerBuffer(
- flatbuffers::FlatBufferBuilder& fbb, flatbuffers::Offset<testing::TestTableInteger> root) {
- fbb.FinishSizePrefixed(root);
-}
-
-} // namespace testing
-
-#endif // FLATBUFFERS_GENERATED_INTEGER_TESTING_H_
diff --git a/gd/dumpsys/internal/test_data/mkfiles b/gd/dumpsys/internal/test_data/mkfiles
deleted file mode 100644
index 95577d05d..000000000
--- a/gd/dumpsys/internal/test_data/mkfiles
+++ /dev/null
@@ -1,9 +0,0 @@
-../../../../../out/host/linux-x86/bin/flatc -b --schema --cpp string.fbs
-xxd -i string.bfbs > string_bfbs.h
-../../../../../out/host/linux-x86/bin/flatc -b --schema --cpp integer.fbs
-xxd -i integer.bfbs > integer_bfbs.h
-../../../../../out/host/linux-x86/bin/flatc -b --schema --cpp float.fbs
-xxd -i float.bfbs > float_bfbs.h
-../../../../../out/host/linux-x86/bin/flatc -b --schema --cpp struct.fbs
-xxd -i struct.bfbs > struct_bfbs.h
-
diff --git a/gd/dumpsys/internal/test_data/root.h b/gd/dumpsys/internal/test_data/root.h
deleted file mode 100644
index 5830ee8cf..000000000
--- a/gd/dumpsys/internal/test_data/root.h
+++ /dev/null
@@ -1,17 +0,0 @@
-
-
-#pragma once
-
-#include "flatbuffers/flatbuffers.h"
-#include "root_generated.h"
-
-using TableAddFunction = std::function<void(testing::DumpsysTestDataRootBuilder* root_builder)>;
-
-namespace testing {
-
-struct DumpsysTestDataClass {
- virtual TableAddFunction GetTable(flatbuffers::FlatBufferBuilder& builder) = 0;
- virtual ~DumpsysTestDataClass() = default;
-};
-
-} // namespace testing
diff --git a/gd/dumpsys/internal/test_data/string.bfbs b/gd/dumpsys/internal/test_data/string.bfbs
deleted file mode 100644
index a414802b4..000000000
--- a/gd/dumpsys/internal/test_data/string.bfbs
+++ /dev/null
Binary files differ
diff --git a/gd/dumpsys/internal/test_data/string.fbs b/gd/dumpsys/internal/test_data/string.fbs
deleted file mode 100644
index ba4f2fdfc..000000000
--- a/gd/dumpsys/internal/test_data/string.fbs
+++ /dev/null
@@ -1,7 +0,0 @@
-namespace testing;
-
-table TestTableString {
- test_string:string;
-}
-
-root_type TestTableString;
diff --git a/gd/dumpsys/internal/test_data/string_bfbs.h b/gd/dumpsys/internal/test_data/string_bfbs.h
deleted file mode 100644
index 9d614ef46..000000000
--- a/gd/dumpsys/internal/test_data/string_bfbs.h
+++ /dev/null
@@ -1,13 +0,0 @@
-unsigned char string_bfbs[] = {
- 0x18, 0x00, 0x00, 0x00, 0x42, 0x46, 0x42, 0x53, 0x10, 0x00, 0x1c, 0x00, 0x04, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x10,
- 0x00, 0x14, 0x00, 0x18, 0x00, 0x10, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x1c, 0x00,
- 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x01, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x10, 0x00, 0x04, 0x00, 0x08, 0x00, 0x00, 0x00, 0x0c,
- 0x00, 0x0c, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00,
- 0x00, 0x00, 0x2c, 0x00, 0x00, 0x00, 0x17, 0x00, 0x00, 0x00, 0x74, 0x65, 0x73, 0x74, 0x69, 0x6e, 0x67, 0x2e, 0x54,
- 0x65, 0x73, 0x74, 0x54, 0x61, 0x62, 0x6c, 0x65, 0x53, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x00, 0x0c, 0x00, 0x12, 0x00,
- 0x08, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x06, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x18, 0x00, 0x00,
- 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x08, 0x00, 0x07, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x0d, 0x0b, 0x00, 0x00, 0x00, 0x74, 0x65, 0x73, 0x74, 0x5f, 0x73, 0x74, 0x72, 0x69, 0x6e, 0x67, 0x00};
-unsigned int string_bfbs_len = 208;
diff --git a/gd/dumpsys/internal/test_data/string_generated.h b/gd/dumpsys/internal/test_data/string_generated.h
deleted file mode 100644
index 83ea7fe10..000000000
--- a/gd/dumpsys/internal/test_data/string_generated.h
+++ /dev/null
@@ -1,88 +0,0 @@
-// automatically generated by the FlatBuffers compiler, do not modify
-
-#ifndef FLATBUFFERS_GENERATED_STRING_TESTING_H_
-#define FLATBUFFERS_GENERATED_STRING_TESTING_H_
-
-#include "flatbuffers/flatbuffers.h"
-
-namespace testing {
-
-struct TestTableString;
-struct TestTableStringBuilder;
-
-struct TestTableString FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
- typedef TestTableStringBuilder Builder;
- enum FlatBuffersVTableOffset FLATBUFFERS_VTABLE_UNDERLYING_TYPE { VT_TEST_STRING = 4 };
- const flatbuffers::String* test_string() const {
- return GetPointer<const flatbuffers::String*>(VT_TEST_STRING);
- }
- bool Verify(flatbuffers::Verifier& verifier) const {
- return VerifyTableStart(verifier) && VerifyOffset(verifier, VT_TEST_STRING) &&
- verifier.VerifyString(test_string()) && verifier.EndTable();
- }
-};
-
-struct TestTableStringBuilder {
- typedef TestTableString Table;
- flatbuffers::FlatBufferBuilder& fbb_;
- flatbuffers::uoffset_t start_;
- void add_test_string(flatbuffers::Offset<flatbuffers::String> test_string) {
- fbb_.AddOffset(TestTableString::VT_TEST_STRING, test_string);
- }
- explicit TestTableStringBuilder(flatbuffers::FlatBufferBuilder& _fbb) : fbb_(_fbb) {
- start_ = fbb_.StartTable();
- }
- TestTableStringBuilder& operator=(const TestTableStringBuilder&);
- flatbuffers::Offset<TestTableString> Finish() {
- const auto end = fbb_.EndTable(start_);
- auto o = flatbuffers::Offset<TestTableString>(end);
- return o;
- }
-};
-
-inline flatbuffers::Offset<TestTableString> CreateTestTableString(
- flatbuffers::FlatBufferBuilder& _fbb, flatbuffers::Offset<flatbuffers::String> test_string = 0) {
- TestTableStringBuilder builder_(_fbb);
- builder_.add_test_string(test_string);
- return builder_.Finish();
-}
-
-inline flatbuffers::Offset<TestTableString> CreateTestTableStringDirect(
- flatbuffers::FlatBufferBuilder& _fbb, const char* test_string = nullptr) {
- auto test_string__ = test_string ? _fbb.CreateString(test_string) : 0;
- return testing::CreateTestTableString(_fbb, test_string__);
-}
-
-inline const testing::TestTableString* GetTestTableString(const void* buf) {
- return flatbuffers::GetRoot<testing::TestTableString>(buf);
-}
-
-inline const testing::TestTableString* GetSizePrefixedTestTableString(const void* buf) {
- return flatbuffers::GetSizePrefixedRoot<testing::TestTableString>(buf);
-}
-
-inline bool VerifyTestTableStringBuffer(flatbuffers::Verifier& verifier) {
- return verifier.VerifyBuffer<testing::TestTableString>(nullptr);
-}
-
-inline bool VerifySizePrefixedTestTableStringBuffer(flatbuffers::Verifier& verifier) {
- return verifier.VerifySizePrefixedBuffer<testing::TestTableString>(nullptr);
-}
-
-inline const char* TestTableStringExtension() {
- return "bfbs";
-}
-
-inline void FinishTestTableStringBuffer(
- flatbuffers::FlatBufferBuilder& fbb, flatbuffers::Offset<testing::TestTableString> root) {
- fbb.Finish(root);
-}
-
-inline void FinishSizePrefixedTestTableStringBuffer(
- flatbuffers::FlatBufferBuilder& fbb, flatbuffers::Offset<testing::TestTableString> root) {
- fbb.FinishSizePrefixed(root);
-}
-
-} // namespace testing
-
-#endif // FLATBUFFERS_GENERATED_STRING_TESTING_H_
diff --git a/gd/dumpsys/internal/test_data/struct.bfbs b/gd/dumpsys/internal/test_data/struct.bfbs
deleted file mode 100644
index 9803cc5df..000000000
--- a/gd/dumpsys/internal/test_data/struct.bfbs
+++ /dev/null
Binary files differ
diff --git a/gd/dumpsys/internal/test_data/struct.fbs b/gd/dumpsys/internal/test_data/struct.fbs
deleted file mode 100644
index 83d4974f9..000000000
--- a/gd/dumpsys/internal/test_data/struct.fbs
+++ /dev/null
@@ -1,11 +0,0 @@
-namespace testing;
-
-table TestSubTable {
- placeholder:int;
-}
-
-table TestTableStruct{
- sub_table:TestSubTable;
-}
-
-root_type TestTableStruct;
diff --git a/gd/dumpsys/internal/test_data/struct_bfbs.h b/gd/dumpsys/internal/test_data/struct_bfbs.h
deleted file mode 100644
index bbd8e22fc..000000000
--- a/gd/dumpsys/internal/test_data/struct_bfbs.h
+++ /dev/null
@@ -1,19 +0,0 @@
-unsigned char struct_bfbs[] = {
- 0x18, 0x00, 0x00, 0x00, 0x42, 0x46, 0x42, 0x53, 0x10, 0x00, 0x1c, 0x00, 0x04, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x10,
- 0x00, 0x14, 0x00, 0x18, 0x00, 0x10, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x28, 0x00, 0x00, 0x00, 0x1c, 0x00,
- 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x2c, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x02, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x94, 0xff, 0xff, 0xff, 0x14, 0x00, 0x00,
- 0x00, 0x08, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x17, 0x00,
- 0x00, 0x00, 0x74, 0x65, 0x73, 0x74, 0x69, 0x6e, 0x67, 0x2e, 0x54, 0x65, 0x73, 0x74, 0x54, 0x61, 0x62, 0x6c, 0x65,
- 0x53, 0x74, 0x72, 0x75, 0x63, 0x74, 0x00, 0x88, 0xff, 0xff, 0xff, 0x00, 0x00, 0x04, 0x00, 0x20, 0x00, 0x00, 0x00,
- 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x0c, 0x00, 0x07, 0x00, 0x00, 0x00, 0x08, 0x00, 0x0a, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x09, 0x00, 0x00, 0x00, 0x73, 0x75, 0x62, 0x5f, 0x74, 0x61,
- 0x62, 0x6c, 0x65, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x10, 0x00, 0x04, 0x00, 0x08, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x0c,
- 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
- 0x2c, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x74, 0x65, 0x73, 0x74, 0x69, 0x6e, 0x67, 0x2e, 0x54, 0x65, 0x73,
- 0x74, 0x53, 0x75, 0x62, 0x54, 0x61, 0x62, 0x6c, 0x65, 0x00, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x12, 0x00, 0x08, 0x00,
- 0x0c, 0x00, 0x00, 0x00, 0x06, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x18, 0x00, 0x00, 0x00, 0x0c,
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x00, 0x08, 0x00, 0x07, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07,
- 0x0b, 0x00, 0x00, 0x00, 0x70, 0x6c, 0x61, 0x63, 0x65, 0x68, 0x6f, 0x6c, 0x64, 0x65, 0x72, 0x00};
-unsigned int struct_bfbs_len = 320;
diff --git a/gd/dumpsys/internal/test_data/struct_generated.h b/gd/dumpsys/internal/test_data/struct_generated.h
deleted file mode 100644
index 22e2e0bc8..000000000
--- a/gd/dumpsys/internal/test_data/struct_generated.h
+++ /dev/null
@@ -1,121 +0,0 @@
-// automatically generated by the FlatBuffers compiler, do not modify
-
-#ifndef FLATBUFFERS_GENERATED_STRUCT_TESTING_H_
-#define FLATBUFFERS_GENERATED_STRUCT_TESTING_H_
-
-#include "flatbuffers/flatbuffers.h"
-
-namespace testing {
-
-struct TestSubTable;
-struct TestSubTableBuilder;
-
-struct TestTableStruct;
-struct TestTableStructBuilder;
-
-struct TestSubTable FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
- typedef TestSubTableBuilder Builder;
- enum FlatBuffersVTableOffset FLATBUFFERS_VTABLE_UNDERLYING_TYPE { VT_PLACEHOLDER = 4 };
- int32_t placeholder() const {
- return GetField<int32_t>(VT_PLACEHOLDER, 0);
- }
- bool Verify(flatbuffers::Verifier& verifier) const {
- return VerifyTableStart(verifier) && VerifyField<int32_t>(verifier, VT_PLACEHOLDER) && verifier.EndTable();
- }
-};
-
-struct TestSubTableBuilder {
- typedef TestSubTable Table;
- flatbuffers::FlatBufferBuilder& fbb_;
- flatbuffers::uoffset_t start_;
- void add_placeholder(int32_t placeholder) {
- fbb_.AddElement<int32_t>(TestSubTable::VT_PLACEHOLDER, placeholder, 0);
- }
- explicit TestSubTableBuilder(flatbuffers::FlatBufferBuilder& _fbb) : fbb_(_fbb) {
- start_ = fbb_.StartTable();
- }
- TestSubTableBuilder& operator=(const TestSubTableBuilder&);
- flatbuffers::Offset<TestSubTable> Finish() {
- const auto end = fbb_.EndTable(start_);
- auto o = flatbuffers::Offset<TestSubTable>(end);
- return o;
- }
-};
-
-inline flatbuffers::Offset<TestSubTable> CreateTestSubTable(
- flatbuffers::FlatBufferBuilder& _fbb, int32_t placeholder = 0) {
- TestSubTableBuilder builder_(_fbb);
- builder_.add_placeholder(placeholder);
- return builder_.Finish();
-}
-
-struct TestTableStruct FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
- typedef TestTableStructBuilder Builder;
- enum FlatBuffersVTableOffset FLATBUFFERS_VTABLE_UNDERLYING_TYPE { VT_SUB_TABLE = 4 };
- const testing::TestSubTable* sub_table() const {
- return GetPointer<const testing::TestSubTable*>(VT_SUB_TABLE);
- }
- bool Verify(flatbuffers::Verifier& verifier) const {
- return VerifyTableStart(verifier) && VerifyOffset(verifier, VT_SUB_TABLE) && verifier.VerifyTable(sub_table()) &&
- verifier.EndTable();
- }
-};
-
-struct TestTableStructBuilder {
- typedef TestTableStruct Table;
- flatbuffers::FlatBufferBuilder& fbb_;
- flatbuffers::uoffset_t start_;
- void add_sub_table(flatbuffers::Offset<testing::TestSubTable> sub_table) {
- fbb_.AddOffset(TestTableStruct::VT_SUB_TABLE, sub_table);
- }
- explicit TestTableStructBuilder(flatbuffers::FlatBufferBuilder& _fbb) : fbb_(_fbb) {
- start_ = fbb_.StartTable();
- }
- TestTableStructBuilder& operator=(const TestTableStructBuilder&);
- flatbuffers::Offset<TestTableStruct> Finish() {
- const auto end = fbb_.EndTable(start_);
- auto o = flatbuffers::Offset<TestTableStruct>(end);
- return o;
- }
-};
-
-inline flatbuffers::Offset<TestTableStruct> CreateTestTableStruct(
- flatbuffers::FlatBufferBuilder& _fbb, flatbuffers::Offset<testing::TestSubTable> sub_table = 0) {
- TestTableStructBuilder builder_(_fbb);
- builder_.add_sub_table(sub_table);
- return builder_.Finish();
-}
-
-inline const testing::TestTableStruct* GetTestTableStruct(const void* buf) {
- return flatbuffers::GetRoot<testing::TestTableStruct>(buf);
-}
-
-inline const testing::TestTableStruct* GetSizePrefixedTestTableStruct(const void* buf) {
- return flatbuffers::GetSizePrefixedRoot<testing::TestTableStruct>(buf);
-}
-
-inline bool VerifyTestTableStructBuffer(flatbuffers::Verifier& verifier) {
- return verifier.VerifyBuffer<testing::TestTableStruct>(nullptr);
-}
-
-inline bool VerifySizePrefixedTestTableStructBuffer(flatbuffers::Verifier& verifier) {
- return verifier.VerifySizePrefixedBuffer<testing::TestTableStruct>(nullptr);
-}
-
-inline const char* TestTableStructExtension() {
- return "bfbs";
-}
-
-inline void FinishTestTableStructBuffer(
- flatbuffers::FlatBufferBuilder& fbb, flatbuffers::Offset<testing::TestTableStruct> root) {
- fbb.Finish(root);
-}
-
-inline void FinishSizePrefixedTestTableStructBuffer(
- flatbuffers::FlatBufferBuilder& fbb, flatbuffers::Offset<testing::TestTableStruct> root) {
- fbb.FinishSizePrefixed(root);
-}
-
-} // namespace testing
-
-#endif // FLATBUFFERS_GENERATED_STRUCT_TESTING_H_
diff --git a/gd/dumpsys/reflection_schema.cc b/gd/dumpsys/reflection_schema.cc
deleted file mode 100644
index 809fb0a65..000000000
--- a/gd/dumpsys/reflection_schema.cc
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "dumpsys/reflection_schema.h"
-#include <string>
-#include "bundler_generated.h"
-#include "flatbuffers/flatbuffers.h"
-#include "flatbuffers/idl.h"
-#include "os/log.h"
-
-using namespace bluetooth;
-
-dumpsys::ReflectionSchema::ReflectionSchema(const std::string& pre_bundled_schema)
- : pre_bundled_schema_(pre_bundled_schema) {
- bundled_schema_ = flatbuffers::GetRoot<bluetooth::dumpsys::BundledSchema>(pre_bundled_schema_.data());
- ASSERT(bundled_schema_ != nullptr);
-}
-
-int dumpsys::ReflectionSchema::GetNumberOfBundledSchemas() const {
- return bundled_schema_->map()->size();
-}
-
-std::string dumpsys::ReflectionSchema::GetTitle() const {
- return bundled_schema_->title()->str();
-}
-
-std::string dumpsys::ReflectionSchema::GetRootName() const {
- return bundled_schema_->root_name()->str();
-}
-
-const reflection::Schema* dumpsys::ReflectionSchema::GetRootReflectionSchema() const {
- return FindInReflectionSchema(GetRootName());
-}
-
-const reflection::Schema* dumpsys::ReflectionSchema::FindInReflectionSchema(const std::string& name) const {
- const flatbuffers::Vector<flatbuffers::Offset<bluetooth::dumpsys::BundledSchemaMap>>* map = bundled_schema_->map();
-
- for (auto it = map->cbegin(); it != map->cend(); ++it) {
- if (it->name()->str() == name) {
- flatbuffers::Verifier verifier(reinterpret_cast<const uint8_t*>(it->data()->Data()), it->data()->size());
- if (!reflection::VerifySchemaBuffer(verifier)) {
- LOG_WARN("Unable to verify schema buffer name:%s", name.c_str());
- return nullptr;
- }
- return reflection::GetSchema(it->data()->Data());
- }
- }
- return nullptr;
-}
-
-void dumpsys::ReflectionSchema::PrintReflectionSchema() const {
- const flatbuffers::Vector<flatbuffers::Offset<bluetooth::dumpsys::BundledSchemaMap>>* map = bundled_schema_->map();
- LOG_INFO(
- " Bundled schema title:%s root_name:%s",
- bundled_schema_->title()->c_str(),
- bundled_schema_->root_name()->c_str());
- for (auto it = map->cbegin(); it != map->cend(); ++it) {
- LOG_INFO(" schema:%s", it->name()->c_str());
- }
-}
-
-bool dumpsys::ReflectionSchema::VerifyReflectionSchema() const {
- const flatbuffers::Vector<flatbuffers::Offset<bluetooth::dumpsys::BundledSchemaMap>>* map = bundled_schema_->map();
-
- for (auto it = map->cbegin(); it != map->cend(); ++it) {
- flatbuffers::Verifier verifier(reinterpret_cast<const uint8_t*>(it->data()->Data()), it->data()->size());
- if (!reflection::VerifySchemaBuffer(verifier)) {
- return false;
- }
- }
- return true;
-}
diff --git a/gd/dumpsys/reflection_schema.h b/gd/dumpsys/reflection_schema.h
deleted file mode 100644
index b2dc679a0..000000000
--- a/gd/dumpsys/reflection_schema.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <string>
-#include "bundler_generated.h"
-#include "flatbuffers/flatbuffers.h"
-#include "flatbuffers/idl.h"
-
-namespace bluetooth {
-namespace dumpsys {
-
-class ReflectionSchema {
- public:
- ReflectionSchema(const std::string& pre_bundled_schema);
-
- std::string GetTitle() const;
- std::string GetRootName() const;
- int GetNumberOfBundledSchemas() const;
-
- bool VerifyReflectionSchema() const;
- const reflection::Schema* GetRootReflectionSchema() const;
- const reflection::Schema* FindInReflectionSchema(const std::string& name) const;
- void PrintReflectionSchema() const;
-
- private:
- const BundledSchema* bundled_schema_;
- const std::string pre_bundled_schema_;
-};
-
-} // namespace dumpsys
-} // namespace bluetooth
diff --git a/gd/dumpsys/reflection_schema_test.cc b/gd/dumpsys/reflection_schema_test.cc
deleted file mode 100644
index 0e9bf804b..000000000
--- a/gd/dumpsys/reflection_schema_test.cc
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gtest/gtest.h>
-
-#include "dumpsys/reflection_schema.h"
-#include "generated_dumpsys_bundled_test_schema.h"
-
-// TODO(cmanton) fix bundler to split header/code
-// #include "generated_dumpsys_bundled_schema.h"
-namespace bluetooth {
-namespace dumpsys {
-extern const unsigned char* data;
-extern const size_t data_size;
-const std::string& GetBundledSchemaData();
-} // namespace dumpsys
-} // namespace bluetooth
-
-namespace testing {
-
-using namespace bluetooth;
-
-class ReflectionSchemaTest : public Test {
- protected:
- void SetUp() override {}
-
- void TearDown() override {}
-};
-
-TEST_F(ReflectionSchemaTest, verify_test_content) {
- dumpsys::ReflectionSchema reflection_schema(testing::GetBundledSchemaData());
- ASSERT_TRUE(reflection_schema.GetNumberOfBundledSchemas() == 5);
- ASSERT_TRUE(reflection_schema.FindInReflectionSchema("testing.DumpsysTestDataRoot") != nullptr);
- ASSERT_TRUE(reflection_schema.FindInReflectionSchema("testing.BarTestSchema") != nullptr);
- ASSERT_TRUE(reflection_schema.FindInReflectionSchema("testing.BazTestSchema") != nullptr);
- ASSERT_TRUE(reflection_schema.FindInReflectionSchema("testing.FooTestSchema") != nullptr);
- ASSERT_TRUE(reflection_schema.FindInReflectionSchema("testing.QuxTestSchema") != nullptr);
- ASSERT_TRUE(reflection_schema.FindInReflectionSchema("DoesNotExist") == nullptr);
-}
-
-TEST_F(ReflectionSchemaTest, verify_test_schema) {
- dumpsys::ReflectionSchema reflection_schema(testing::GetBundledSchemaData());
- ASSERT_TRUE(reflection_schema.VerifyReflectionSchema());
-}
-
-TEST_F(ReflectionSchemaTest, verify_production_schema) {
- dumpsys::ReflectionSchema reflection_schema(bluetooth::dumpsys::GetBundledSchemaData());
- ASSERT_TRUE(reflection_schema.VerifyReflectionSchema());
-}
-
-} // namespace testing
diff --git a/gd/dumpsys/test_data/bar.fbs b/gd/dumpsys/test_data/bar.fbs
deleted file mode 100644
index dc423fea9..000000000
--- a/gd/dumpsys/test_data/bar.fbs
+++ /dev/null
@@ -1,12 +0,0 @@
-namespace testing;
-
-attribute "privacy";
-
-table BarTestSchema {
- bar_x:int;
- bar_y:int;
- another_field:string (privacy:"Any");
-}
-
-root_type BarTestSchema;
-
diff --git a/gd/dumpsys/test_data/bar.h b/gd/dumpsys/test_data/bar.h
deleted file mode 100644
index 5d6d0eead..000000000
--- a/gd/dumpsys/test_data/bar.h
+++ /dev/null
@@ -1,17 +0,0 @@
-/**
- *
- **/
-#include "bar_generated.h"
-#include "root.h"
-#include "root_generated.h"
-
-namespace testing {
-
-class BarTestDataClass : public DumpsysTestDataClass {
- public:
- TableAddFunction GetTable(flatbuffers::FlatBufferBuilder& fb_builder) override {
- return [](DumpsysTestDataRootBuilder* builder) {};
- }
-};
-
-} // namespace testing
diff --git a/gd/dumpsys/test_data/baz.fbs b/gd/dumpsys/test_data/baz.fbs
deleted file mode 100644
index 38649a9c8..000000000
--- a/gd/dumpsys/test_data/baz.fbs
+++ /dev/null
@@ -1,35 +0,0 @@
-namespace testing;
-
-attribute "privacy";
-
-table BazSubTablePrivate {
- subtable_int_any:int (privacy:"Any");
- subtable_string_any:string (privacy:"Any");
-}
-
-table BazSubTableOpaque {
- subtable_int_any:int (privacy:"Any");
- subtable_string_any:string (privacy:"Any");
-}
-
-table BazSubTableAnonymized {
- subtable_int_any:int (privacy:"Any");
- subtable_string_any:string (privacy:"Any");
-}
-
-table BazSubTableAny {
- subtable_int_private:int (privacy:"Private");
- subtable_int_opaque:int (privacy:"Opaque");
- subtable_int_anonymized:int (privacy:"Anonymized");
- subtable_int_any:int (privacy:"Any");
- subtable_string_any:string (privacy:"Any");
-}
-
-table BazTestSchema {
- sub_table_private:BazSubTablePrivate; // private by default
- sub_table_opaque:BazSubTableOpaque (privacy:"Opaque");
- sub_table_anonymized:BazSubTableAnonymized (privacy:"Anonymized");
- sub_table_any:BazSubTableAny (privacy:"Any");
-}
-
-root_type BazTestSchema;
diff --git a/gd/dumpsys/test_data/baz.h b/gd/dumpsys/test_data/baz.h
deleted file mode 100644
index 7797085c4..000000000
--- a/gd/dumpsys/test_data/baz.h
+++ /dev/null
@@ -1,32 +0,0 @@
-
-#include "baz_generated.h"
-#include "root.h"
-#include "root_generated.h"
-
-namespace testing {
-
-class BazTestDataClass : public DumpsysTestDataClass {
- public:
- TableAddFunction GetTable(flatbuffers::FlatBufferBuilder& fb_builder) override {
- auto sub_name_private = fb_builder.CreateString("Baz Subtable Private");
- auto sub_name_opaque = fb_builder.CreateString("Baz Subtable Opaque");
- auto sub_name_anonymized = fb_builder.CreateString("Baz Subtable Anonymized");
- auto sub_name_any = fb_builder.CreateString("Baz Subtable Any");
-
- auto private_subtable = CreateBazSubTablePrivate(fb_builder, 1, sub_name_private);
- auto opaque_subtable = CreateBazSubTableOpaque(fb_builder, 1, sub_name_opaque);
- auto anonymized_subtable = CreateBazSubTableAnonymized(fb_builder, 1, sub_name_anonymized);
- auto any_subtable = CreateBazSubTableAny(fb_builder, 1, 2, 3, 4, sub_name_any);
-
- BazTestSchemaBuilder builder(fb_builder);
- builder.add_sub_table_private(private_subtable);
- builder.add_sub_table_opaque(opaque_subtable);
- builder.add_sub_table_anonymized(anonymized_subtable);
- builder.add_sub_table_any(any_subtable);
- auto baz_table = builder.Finish();
-
- return [baz_table](DumpsysTestDataRootBuilder* builder) { builder->add_baz_module_data(baz_table); };
- }
-};
-
-} // namespace testing
diff --git a/gd/dumpsys/test_data/foo.fbs b/gd/dumpsys/test_data/foo.fbs
deleted file mode 100644
index b7482c326..000000000
--- a/gd/dumpsys/test_data/foo.fbs
+++ /dev/null
@@ -1,25 +0,0 @@
-namespace testing;
-
-attribute "privacy";
-
-table FooTestSchema {
- foo_int_private:int;
- foo_int_opaque:int (privacy:"Opaque");
- foo_int_anonymized:int (privacy:"Anonymized");
- foo_int_any:int (privacy:"Any");
- foo_int_string:string (privacy:"Any");
-
- foo_float_private:float;
- foo_float_opaque:float (privacy:"Opaque");
- foo_float_anonymized:float (privacy:"Anonymized");
- foo_float_any:float (privacy:"Any");
- foo_float_string:string (privacy:"Any");
-
- foo_bool_private:bool (privacy:"Private");
- foo_bool_opaque:bool (privacy:"Opaque");
- foo_bool_anonymized:bool (privacy:"Anonymized");
- foo_bool_any:bool (privacy:"Any");
- foo_bool_string:string (privacy:"Any");
-}
-
-root_type FooTestSchema;
diff --git a/gd/dumpsys/test_data/foo.h b/gd/dumpsys/test_data/foo.h
deleted file mode 100644
index 01a7bd92b..000000000
--- a/gd/dumpsys/test_data/foo.h
+++ /dev/null
@@ -1,40 +0,0 @@
-
-#include "foo_generated.h"
-#include "root.h"
-#include "root_generated.h"
-
-namespace testing {
-
-class FooTestDataClass : public DumpsysTestDataClass {
- public:
- TableAddFunction GetTable(flatbuffers::FlatBufferBuilder& fb_builder) override {
- auto int_string = fb_builder.CreateString("123");
- auto float_string = fb_builder.CreateString("123.456");
- auto bool_string = fb_builder.CreateString("true");
-
- FooTestSchemaBuilder builder(fb_builder);
- builder.add_foo_int_private(123);
- builder.add_foo_int_opaque(123);
- builder.add_foo_int_anonymized(123);
- builder.add_foo_int_any(123);
- builder.add_foo_int_string(int_string);
-
- builder.add_foo_float_private(123.456);
- builder.add_foo_float_opaque(123.456);
- builder.add_foo_float_anonymized(123.456);
- builder.add_foo_float_any(123.456);
- builder.add_foo_float_string(float_string);
-
- builder.add_foo_bool_private(true);
- builder.add_foo_bool_opaque(true);
- builder.add_foo_bool_anonymized(true);
- builder.add_foo_bool_any(true);
- builder.add_foo_bool_string(bool_string);
-
- auto foo_table = builder.Finish();
-
- return [foo_table](DumpsysTestDataRootBuilder* builder) { builder->add_foo_module_data(foo_table); };
- }
-};
-
-} // namespace testing
diff --git a/gd/dumpsys/test_data/qux.fbs b/gd/dumpsys/test_data/qux.fbs
deleted file mode 100644
index 15e17dab7..000000000
--- a/gd/dumpsys/test_data/qux.fbs
+++ /dev/null
@@ -1,13 +0,0 @@
-namespace testing;
-
-attribute "privacy";
-
-table QuxTestSchema {
- qux_int_private:int;
- qux_int_opaque:int (privacy:"Opaque");
- qux_int_anonymized:int (privacy:"Anonymized");
- qux_int_any:int (privacy:"Any");
- qux_string_name:string (privacy:"Any");
-}
-
-root_type QuxTestSchema;
diff --git a/gd/dumpsys/test_data/qux.h b/gd/dumpsys/test_data/qux.h
deleted file mode 100644
index be89d3d51..000000000
--- a/gd/dumpsys/test_data/qux.h
+++ /dev/null
@@ -1,26 +0,0 @@
-
-#include "qux_generated.h"
-#include "root.h"
-#include "root_generated.h"
-
-namespace testing {
-
-class QuxTestDataClass : public DumpsysTestDataClass {
- public:
- TableAddFunction GetTable(flatbuffers::FlatBufferBuilder& fb_builder) override {
- auto name = fb_builder.CreateString("Qux Module String");
-
- QuxTestSchemaBuilder builder(fb_builder);
- builder.add_qux_int_private(123);
- builder.add_qux_int_opaque(456);
- builder.add_qux_int_anonymized(789);
- builder.add_qux_int_any(0xabc);
- builder.add_qux_string_name(name);
-
- auto qux_table = builder.Finish();
-
- return [qux_table](DumpsysTestDataRootBuilder* builder) { builder->add_qux_module_data(qux_table); };
- }
-};
-
-} // namespace testing
diff --git a/gd/dumpsys/test_data/root.fbs b/gd/dumpsys/test_data/root.fbs
deleted file mode 100644
index cedd310d1..000000000
--- a/gd/dumpsys/test_data/root.fbs
+++ /dev/null
@@ -1,27 +0,0 @@
-include "foo.fbs";
-include "bar.fbs";
-include "baz.fbs";
-include "qux.fbs";
-
-namespace testing;
-
-attribute "privacy";
-
-table DumpsysTestDataRoot {
- string_private:string;
- string_opaque:string (privacy:"Opaque");
- string_anonymized:string (privacy:"Anonymized");
- string_any:string (privacy:"Any");
-
- int_private:int32 (privacy:"Private");
- int_opaque:int32 (privacy:"Opaque");
- int_anonymized:int32 (privacy:"Anonymized");
- int_any:int32 (privacy:"Any");
-
- foo_module_data:FooTestSchema (privacy:"Any");
- bar_module_data:BarTestSchema (privacy:"Any");
- baz_module_data:BazTestSchema (privacy:"Any");
- qux_module_data:QuxTestSchema (privacy:"Any");
-}
-
-root_type DumpsysTestDataRoot;
diff --git a/gd/dumpsys/test_data/root.h b/gd/dumpsys/test_data/root.h
deleted file mode 100644
index 9f58c8ebe..000000000
--- a/gd/dumpsys/test_data/root.h
+++ /dev/null
@@ -1,17 +0,0 @@
-
-
-#pragma once
-
-#include "flatbuffers/flatbuffers.h"
-#include "root_generated.h"
-
-using TableAddFunction = std::function<void(testing::DumpsysTestDataRootBuilder* root_builder)>;
-
-namespace testing {
-
-struct DumpsysTestDataClass {
- virtual TableAddFunction GetTable(flatbuffers::FlatBufferBuilder& fb_builder) = 0;
- virtual ~DumpsysTestDataClass() = default;
-};
-
-} // namespace testing
diff --git a/gd/dumpsys_data.fbs b/gd/dumpsys_data.fbs
deleted file mode 100644
index 87f146124..000000000
--- a/gd/dumpsys_data.fbs
+++ /dev/null
@@ -1,25 +0,0 @@
-// Top level module dumpsys data schema
-include "btaa/activity_attribution.fbs";
-include "common/init_flags.fbs";
-include "l2cap/classic/l2cap_classic_module.fbs";
-include "hci/hci_acl_manager.fbs";
-include "module_unittest.fbs";
-include "os/wakelock_manager.fbs";
-include "shim/dumpsys.fbs";
-
-namespace bluetooth;
-
-attribute "privacy";
-
-table DumpsysData {
- title:string;
- init_flags:common.InitFlagsData (privacy:"Any");
- wakelock_manager_data:bluetooth.os.WakelockManagerData (privacy:"Any");
- shim_dumpsys_data:bluetooth.shim.DumpsysModuleData (privacy:"Any");
- l2cap_classic_dumpsys_data:bluetooth.l2cap.classic.L2capClassicModuleData (privacy:"Any");
- hci_acl_manager_dumpsys_data:bluetooth.hci.AclManagerData (privacy:"Any");
- module_unittest_data:bluetooth.ModuleUnitTestData; // private
- activity_attribution_dumpsys_data:bluetooth.activity_attribution.ActivityAttributionData (privacy:"Any");
-}
-
-root_type DumpsysData;
diff --git a/gd/facade/common.proto b/gd/facade/common.proto
index c0215ed9a..b1176a4d5 100644
--- a/gd/facade/common.proto
+++ b/gd/facade/common.proto
@@ -2,10 +2,6 @@ syntax = "proto3";
package bluetooth.facade;
-message Data {
- bytes payload = 1;
-}
-
message BluetoothAddress {
bytes address = 1;
}
@@ -17,13 +13,6 @@ enum BluetoothAddressTypeEnum {
RANDOM_IDENTITY_ADDRESS = 0x3;
}
-enum BluetoothOwnAddressTypeEnum {
- USE_PUBLIC_DEVICE_ADDRESS = 0x0;
- USE_RANDOM_DEVICE_ADDRESS = 0x1;
- RESOLVABLE_OR_PUBLIC_ADDRESS = 0x2;
- RESOLVABLE_OR_RANDOM_ADDRESS = 0x3;
-}
-
message BluetoothAddressWithType {
BluetoothAddress address = 1;
BluetoothAddressTypeEnum type = 2;
diff --git a/gd/facade/facade_main.cc b/gd/facade/facade_main.cc
index 0d9f698c7..8ff1e7287 100644
--- a/gd/facade/facade_main.cc
+++ b/gd/facade/facade_main.cc
@@ -14,103 +14,49 @@
* limitations under the License.
*/
+#include "stack_manager.h"
+
#include <netinet/in.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <unistd.h>
-
#include <csignal>
#include <cstring>
-#include <memory>
#include <string>
#include <thread>
-#include "stack_manager.h"
-
-// clang-format off
-#include <client/linux/handler/exception_handler.h>
-#include <backtrace/Backtrace.h>
-#include <backtrace/backtrace_constants.h>
-// clang-format on
-
-#include "common/init_flags.h"
#include "facade/grpc_root_server.h"
-#include "hal/hci_hal_host.h"
+#include "grpc/grpc_module.h"
+#include "hal/hci_hal.h"
+#include "hal/hci_hal_host_rootcanal.h"
#include "hal/snoop_logger.h"
-#include "os/log.h"
-#include "os/parameter_provider.h"
-#include "os/system_properties.h"
-using ::bluetooth::ModuleList;
-using ::bluetooth::StackManager;
using ::bluetooth::hal::HciHalHostRootcanalConfig;
+using ::bluetooth::StackManager;
+using ::bluetooth::grpc::GrpcModule;
+using ::bluetooth::ModuleList;
using ::bluetooth::os::Thread;
-extern "C" const char* __asan_default_options() {
- return "detect_container_overflow=0";
-}
-
namespace {
::bluetooth::facade::GrpcRootServer grpc_root_server;
-struct sigaction old_act = {};
-void interrupt_handler(int signal_number) {
- LOG_INFO("Stopping gRPC root server due to signal: %s[%d]", strsignal(signal_number), signal_number);
+void interrupt_handler(int) {
grpc_root_server.StopServer();
- if (old_act.sa_handler != nullptr) {
- LOG_INFO("Calling saved signal handler");
- old_act.sa_handler(signal_number);
- }
-}
-struct sigaction new_act = {.sa_handler = interrupt_handler};
-
-bool crash_callback(const void* crash_context, size_t crash_context_size, void* context) {
- pid_t tid = BACKTRACE_CURRENT_THREAD;
- if (crash_context_size >= sizeof(google_breakpad::ExceptionHandler::CrashContext)) {
- auto* ctx = static_cast<const google_breakpad::ExceptionHandler::CrashContext*>(crash_context);
- tid = ctx->tid;
- int signal_number = ctx->siginfo.si_signo;
- LOG_ERROR("Process crashed, signal: %s[%d], tid: %d", strsignal(signal_number), signal_number, ctx->tid);
- } else {
- LOG_ERROR("Process crashed, signal: unknown, tid: unknown");
- }
- std::unique_ptr<Backtrace> backtrace(Backtrace::Create(BACKTRACE_CURRENT_PROCESS, tid));
- if (backtrace == nullptr) {
- LOG_ERROR("Failed to create backtrace object");
- return false;
- }
- if (!backtrace->Unwind(0)) {
- LOG_ERROR("backtrace->Unwind failed");
- return false;
- }
- LOG_ERROR("Backtrace:");
- for (size_t i = 0; i < backtrace->NumFrames(); i++) {
- LOG_ERROR("%s", backtrace->FormatFrameData(i).c_str());
- }
- return true;
}
-
} // namespace
// The entry point for the binary with libbluetooth + facades
int main(int argc, const char** argv) {
- google_breakpad::MinidumpDescriptor descriptor(google_breakpad::MinidumpDescriptor::kMicrodumpOnConsole);
- google_breakpad::ExceptionHandler eh(descriptor, nullptr, nullptr, nullptr, true, -1);
- eh.set_crash_handler(crash_callback);
-
int root_server_port = 8897;
int grpc_port = 8899;
int signal_port = 8895;
- bluetooth::common::InitFlags::SetAllForTesting();
-
const std::string arg_grpc_root_server_port = "--root-server-port=";
const std::string arg_grpc_server_port = "--grpc-port=";
const std::string arg_rootcanal_port = "--rootcanal-port=";
const std::string arg_signal_port = "--signal-port=";
const std::string arg_btsnoop_path = "--btsnoop=";
- const std::string arg_btsnooz_path = "--btsnooz=";
- const std::string arg_btconfig_path = "--btconfig=";
+ std::string btsnoop_path;
for (int i = 1; i < argc; i++) {
std::string arg = argv[i];
if (arg.find(arg_grpc_root_server_port) == 0) {
@@ -126,18 +72,8 @@ int main(int argc, const char** argv) {
HciHalHostRootcanalConfig::Get()->SetPort(std::stoi(port_number));
}
if (arg.find(arg_btsnoop_path) == 0) {
- auto btsnoop_path = arg.substr(arg_btsnoop_path.size());
- ::bluetooth::os::ParameterProvider::OverrideSnoopLogFilePath(btsnoop_path);
- CHECK(::bluetooth::os::SetSystemProperty(
- ::bluetooth::hal::SnoopLogger::kBtSnoopLogModeProperty, ::bluetooth::hal::SnoopLogger::kBtSnoopLogModeFull));
- }
- if (arg.find(arg_btsnooz_path) == 0) {
- auto btsnooz_path = arg.substr(arg_btsnooz_path.size());
- ::bluetooth::os::ParameterProvider::OverrideSnoozLogFilePath(btsnooz_path);
- }
- if (arg.find(arg_btconfig_path) == 0) {
- auto btconfig_path = arg.substr(arg_btconfig_path.size());
- ::bluetooth::os::ParameterProvider::OverrideConfigFilePath(btconfig_path);
+ btsnoop_path = arg.substr(arg_btsnoop_path.size());
+ ::bluetooth::hal::SnoopLogger::SetFilePath(btsnoop_path);
}
if (arg.find(arg_signal_port) == 0) {
auto port_number = arg.substr(arg_signal_port.size());
@@ -145,7 +81,7 @@ int main(int argc, const char** argv) {
}
}
- sigaction(SIGINT, &new_act, &old_act);
+ signal(SIGINT, interrupt_handler);
grpc_root_server.StartServer("0.0.0.0", root_server_port, grpc_port);
int tester_signal_socket = socket(AF_INET, SOCK_STREAM, 0);
struct sockaddr_in addr;
diff --git a/gd/facade/grpc_root_server.cc b/gd/facade/grpc_root_server.cc
index 21e98e425..6a8e5de51 100644
--- a/gd/facade/grpc_root_server.cc
+++ b/gd/facade/grpc_root_server.cc
@@ -27,14 +27,11 @@
#include "hci/facade/facade.h"
#include "hci/facade/le_acl_manager_facade.h"
#include "hci/facade/le_advertising_manager_facade.h"
-#include "hci/facade/le_initiator_address_facade.h"
#include "hci/facade/le_scanning_manager_facade.h"
#include "hci/hci_layer.h"
#include "hci/le_advertising_manager.h"
#include "hci/le_scanning_manager.h"
-#include "iso/facade.h"
#include "l2cap/classic/facade.h"
-#include "l2cap/le/facade.h"
#include "neighbor/connectability.h"
#include "neighbor/discoverability.h"
#include "neighbor/facade/facade.h"
@@ -46,9 +43,9 @@
#include "security/facade.h"
#include "security/security_module.h"
#include "shim/dumpsys.h"
-#include "shim/facade/facade.h"
+#include "shim/l2cap.h"
#include "stack_manager.h"
-#include "storage/storage_module.h"
+#include "storage/legacy.h"
namespace bluetooth {
namespace facade {
@@ -61,10 +58,8 @@ class RootFacadeService : public ::bluetooth::facade::RootFacade::Service {
public:
RootFacadeService(int grpc_port) : grpc_port_(grpc_port) {}
- ::grpc::Status StartStack(
- ::grpc::ServerContext* context,
- const ::bluetooth::facade::StartStackRequest* request,
- ::bluetooth::facade::StartStackResponse* response) override {
+ ::grpc::Status StartStack(::grpc::ServerContext* context, const ::bluetooth::facade::StartStackRequest* request,
+ ::bluetooth::facade::StartStackResponse* response) override {
if (is_running_) {
return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "stack is running");
}
@@ -79,30 +74,24 @@ class RootFacadeService : public ::bluetooth::facade::RootFacade::Service {
break;
case BluetoothModule::HCI:
modules.add<::bluetooth::facade::ReadOnlyPropertyServerModule>();
- modules.add<::bluetooth::hci::facade::HciFacadeModule>();
+ modules.add<::bluetooth::hci::facade::HciLayerFacadeModule>();
break;
case BluetoothModule::HCI_INTERFACES:
modules.add<::bluetooth::facade::ReadOnlyPropertyServerModule>();
- modules.add<::bluetooth::hci::facade::HciFacadeModule>();
+ modules.add<::bluetooth::hci::facade::HciLayerFacadeModule>();
modules.add<::bluetooth::hci::facade::AclManagerFacadeModule>();
modules.add<::bluetooth::hci::facade::ControllerFacadeModule>();
modules.add<::bluetooth::hci::facade::LeAclManagerFacadeModule>();
modules.add<::bluetooth::hci::facade::LeAdvertisingManagerFacadeModule>();
- modules.add<::bluetooth::hci::facade::LeInitiatorAddressFacadeModule>();
modules.add<::bluetooth::hci::facade::LeScanningManagerFacadeModule>();
modules.add<::bluetooth::neighbor::facade::NeighborFacadeModule>();
- modules.add<::bluetooth::iso::IsoModuleFacadeModule>();
break;
case BluetoothModule::L2CAP:
modules.add<::bluetooth::hci::facade::ControllerFacadeModule>();
- modules.add<::bluetooth::hci::facade::LeAdvertisingManagerFacadeModule>();
- modules.add<::bluetooth::hci::facade::LeInitiatorAddressFacadeModule>();
modules.add<::bluetooth::neighbor::facade::NeighborFacadeModule>();
modules.add<::bluetooth::facade::ReadOnlyPropertyServerModule>();
modules.add<::bluetooth::l2cap::classic::L2capClassicModuleFacadeModule>();
- modules.add<::bluetooth::l2cap::le::L2capLeModuleFacadeModule>();
- modules.add<::bluetooth::hci::facade::HciFacadeModule>();
- modules.add<::bluetooth::iso::IsoModuleFacadeModule>();
+ modules.add<::bluetooth::hci::facade::HciLayerFacadeModule>();
break;
case BluetoothModule::SECURITY:
modules.add<::bluetooth::facade::ReadOnlyPropertyServerModule>();
@@ -110,13 +99,24 @@ class RootFacadeService : public ::bluetooth::facade::RootFacade::Service {
modules.add<::bluetooth::security::SecurityModuleFacadeModule>();
modules.add<::bluetooth::neighbor::facade::NeighborFacadeModule>();
modules.add<::bluetooth::l2cap::classic::L2capClassicModuleFacadeModule>();
- modules.add<::bluetooth::hci::facade::HciFacadeModule>();
+ modules.add<::bluetooth::hci::facade::HciLayerFacadeModule>();
modules.add<::bluetooth::hci::facade::ControllerFacadeModule>();
modules.add<::bluetooth::hci::facade::LeAdvertisingManagerFacadeModule>();
modules.add<::bluetooth::hci::facade::LeScanningManagerFacadeModule>();
break;
case BluetoothModule::SHIM:
- modules.add<::bluetooth::shim::facade::ShimFacadeModule>();
+ modules.add<::bluetooth::neighbor::ConnectabilityModule>();
+ modules.add<::bluetooth::neighbor::DiscoverabilityModule>();
+ modules.add<::bluetooth::neighbor::InquiryModule>();
+ modules.add<::bluetooth::neighbor::NameModule>();
+ modules.add<::bluetooth::shim::Dumpsys>();
+ modules.add<::bluetooth::shim::L2cap>();
+ modules.add<::bluetooth::neighbor::PageModule>();
+ modules.add<::bluetooth::hci::HciLayer>();
+ modules.add<::bluetooth::hci::LeAdvertisingManager>();
+ modules.add<::bluetooth::hci::LeScanningManager>();
+ modules.add<::bluetooth::security::SecurityModule>();
+ modules.add<::bluetooth::storage::LegacyModule>();
break;
default:
return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "invalid module under test");
@@ -134,10 +134,8 @@ class RootFacadeService : public ::bluetooth::facade::RootFacade::Service {
return ::grpc::Status::OK;
}
- ::grpc::Status StopStack(
- ::grpc::ServerContext* context,
- const ::bluetooth::facade::StopStackRequest* request,
- ::bluetooth::facade::StopStackResponse* response) override {
+ ::grpc::Status StopStack(::grpc::ServerContext* context, const ::bluetooth::facade::StopStackRequest* request,
+ ::bluetooth::facade::StopStackResponse* response) override {
if (!is_running_) {
return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "stack is not running");
}
diff --git a/gd/facade/grpc_root_server.h b/gd/facade/grpc_root_server.h
index 12faf26e9..9deba356c 100644
--- a/gd/facade/grpc_root_server.h
+++ b/gd/facade/grpc_root_server.h
@@ -16,11 +16,11 @@
#pragma once
-#include <grpc++/grpc++.h>
-
#include <memory>
#include <string>
+#include <grpc++/grpc++.h>
+
namespace bluetooth {
namespace facade {
diff --git a/gd/facade/read_only_property_server.cc b/gd/facade/read_only_property_server.cc
index 5a3c42a36..3c57b879e 100644
--- a/gd/facade/read_only_property_server.cc
+++ b/gd/facade/read_only_property_server.cc
@@ -15,7 +15,6 @@
*/
#include "facade/read_only_property_server.h"
-
#include "hci/controller.h"
namespace bluetooth {
@@ -24,11 +23,9 @@ namespace facade {
class ReadOnlyPropertyService : public ReadOnlyProperty::Service {
public:
ReadOnlyPropertyService(hci::Controller* controller) : controller_(controller) {}
- ::grpc::Status ReadLocalAddress(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::bluetooth::facade::BluetoothAddress* response) override {
- auto address = controller_->GetMacAddress().ToString();
+ ::grpc::Status ReadLocalAddress(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
+ ::bluetooth::facade::BluetoothAddress* response) override {
+ auto address = controller_->GetControllerMacAddress().ToString();
response->set_address(address);
return ::grpc::Status::OK;
}
diff --git a/gd/facade/read_only_property_server.h b/gd/facade/read_only_property_server.h
index ac068b49d..dfac42412 100644
--- a/gd/facade/read_only_property_server.h
+++ b/gd/facade/read_only_property_server.h
@@ -16,10 +16,10 @@
#pragma once
-#include <grpc++/grpc++.h>
-
#include <memory>
+#include <grpc++/grpc++.h>
+
#include "facade/rootservice.grpc.pb.h"
#include "grpc/grpc_module.h"
diff --git a/gd/fuzz/Android.bp b/gd/fuzz/Android.bp
deleted file mode 100644
index 97556d1a3..000000000
--- a/gd/fuzz/Android.bp
+++ /dev/null
@@ -1,15 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-filegroup {
- name: "BluetoothFuzzHelperSources",
- srcs: [
- "helpers.cc",
- ],
-}
diff --git a/gd/fuzz/helpers.cc b/gd/fuzz/helpers.cc
deleted file mode 100644
index 29e53056c..000000000
--- a/gd/fuzz/helpers.cc
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "fuzz/helpers.h"
-
-#include "common/bind.h"
-
-namespace bluetooth {
-namespace fuzz {
-
-// cribbed from https://github.com/google/fuzzing/blob/master/docs/split-inputs.md#magic-separator
-std::vector<std::vector<uint8_t>> SplitInput(
- const uint8_t* data, size_t size, const uint8_t* separator, size_t separatorSize) {
- std::vector<std::vector<uint8_t>> result;
- assert(separatorSize > 0);
- auto beg = data;
- auto end = data + size;
- while (const uint8_t* pos = (const uint8_t*)memmem(beg, end - beg, separator, separatorSize)) {
- result.push_back({beg, pos});
- beg = pos + separatorSize;
- }
- if (beg < end) {
- result.push_back({beg, end});
- }
- return result;
-}
-
-std::vector<uint8_t> GetArbitraryBytes(FuzzedDataProvider* fdp) {
- return fdp->ConsumeBytes<uint8_t>(fdp->ConsumeIntegral<size_t>());
-}
-
-} // namespace fuzz
-} // namespace bluetooth
diff --git a/gd/fuzz/helpers.h b/gd/fuzz/helpers.h
deleted file mode 100644
index c9cbd1898..000000000
--- a/gd/fuzz/helpers.h
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <fuzzer/FuzzedDataProvider.h>
-
-#include <cstdint>
-#include <vector>
-
-#include "os/handler.h"
-
-namespace bluetooth {
-namespace fuzz {
-
-std::vector<std::vector<uint8_t>> SplitInput(
- const uint8_t* data, size_t size, const uint8_t* separator, size_t separatorSize);
-
-std::vector<uint8_t> GetArbitraryBytes(FuzzedDataProvider* fdp);
-
-#define CONSTRUCT_VALID_UNIQUE_OTHERWISE_BAIL(T, name, data) \
- auto name = std::make_unique<T>(T::FromBytes(data)); \
- if (!name->IsValid()) { \
- return; \
- }
-
-template <typename TView>
-void InvokeIfValid(common::ContextualOnceCallback<void(TView)> callback, std::vector<uint8_t> data) {
- auto packet = TView::FromBytes(data);
- if (!packet.IsValid()) {
- return;
- }
- callback.InvokeIfNotEmpty(packet);
-}
-
-template <typename TView>
-void InvokeIfValid(common::ContextualCallback<void(TView)> callback, std::vector<uint8_t> data) {
- auto packet = TView::FromBytes(data);
- if (!packet.IsValid()) {
- return;
- }
- callback.InvokeIfNotEmpty(packet);
-}
-
-} // namespace fuzz
-} // namespace bluetooth
diff --git a/gd/fuzz/run b/gd/fuzz/run
deleted file mode 100755
index add645c79..000000000
--- a/gd/fuzz/run
+++ /dev/null
@@ -1,34 +0,0 @@
-#! /bin/bash
-
-if [[ -z "${ANDROID_BUILD_TOP}" ]]; then
- echo "ANDROID_BUILD_TOP is not set"
-fi
-
-if [[ -z "${ANDROID_HOST_OUT}" ]]; then
- echo "ANDROID_HOST_OUT is not set for host run"
-fi
-
-HOST=false
-POSITIONAL=()
-while [[ $# -gt 0 ]]
-do
-key="$1"
-case $key in
- --host)
- HOST=true
- shift # past argument
- ;;
- *) # unknown option
- POSITIONAL+=("$1") # save it in an array for later
- shift # past argument
- ;;
-esac
-done
-set -- "${POSITIONAL[@]}" # restore positional parameters
-
-TEST_NAME=bluetooth_gd_${1}_fuzz_test
-
-if [ "$HOST" == true ] ; then
- HOST_ARCH=$($ANDROID_BUILD_TOP/build/soong/soong_ui.bash --dumpvar-mode HOST_ARCH)
- SANITIZE_HOST=address $ANDROID_BUILD_TOP/build/soong/soong_ui.bash --build-mode --"all-modules" --dir="$(pwd)" $TEST_NAME && ${ANDROID_HOST_OUT}/fuzz/$HOST_ARCH/$TEST_NAME/$TEST_NAME $2
-fi
diff --git a/gd/grpc/grpc_event_queue.h b/gd/grpc/grpc_event_queue.h
index 9575b2d45..3871679a0 100644
--- a/gd/grpc/grpc_event_queue.h
+++ b/gd/grpc/grpc_event_queue.h
@@ -55,7 +55,7 @@ class GrpcEventQueue {
while (!context->IsCancelled()) {
// Wait for 500 ms so that cancellation can be caught in amortized 250 ms latency
if (pending_events_.wait_to_take(500ms)) {
- LOG_INFO("%s: Got event after queue", log_name_.c_str());
+ LOG_DEBUG("%s: Got event after queue", log_name_.c_str());
writer->Write(pending_events_.take());
}
}
@@ -70,10 +70,10 @@ class GrpcEventQueue {
*/
void OnIncomingEvent(T event) {
if (!running_) {
- LOG_INFO("%s: Discarding an event while not running the loop", log_name_.c_str());
+ LOG_DEBUG("%s: Discarding an event while not running the loop", log_name_.c_str());
return;
}
- LOG_INFO("%s: Got event before queue", log_name_.c_str());
+ LOG_DEBUG("%s: Got event before queue", log_name_.c_str());
pending_events_.push(std::move(event));
}
diff --git a/gd/grpc/grpc_module.cc b/gd/grpc/grpc_module.cc
index d564287bb..bab8899a5 100644
--- a/gd/grpc/grpc_module.cc
+++ b/gd/grpc/grpc_module.cc
@@ -24,7 +24,8 @@ using ::grpc::ServerBuilder;
namespace bluetooth {
namespace grpc {
-void GrpcModule::ListDependencies(ModuleList* list) {}
+void GrpcModule::ListDependencies(ModuleList* list) {
+}
void GrpcModule::Start() {
ASSERT(!started_);
@@ -102,7 +103,10 @@ std::string GrpcModule::ToString() const {
return "Grpc Module";
}
-const ::bluetooth::ModuleFactory GrpcModule::Factory = ::bluetooth::ModuleFactory([]() { return new GrpcModule(); });
+const ::bluetooth::ModuleFactory GrpcModule::Factory = ::bluetooth::ModuleFactory([]() {
+ return new GrpcModule();
+});
+
void GrpcFacadeModule::ListDependencies(ModuleList* list) {
list->add<GrpcModule>();
diff --git a/gd/grpc/grpc_module.h b/gd/grpc/grpc_module.h
index 77bf1b20e..8f50921b5 100644
--- a/gd/grpc/grpc_module.h
+++ b/gd/grpc/grpc_module.h
@@ -16,12 +16,12 @@
#pragma once
-#include <grpc++/grpc++.h>
-#include <module.h>
-
#include <functional>
#include <vector>
+#include <grpc++/grpc++.h>
+#include <module.h>
+
namespace bluetooth {
namespace grpc {
@@ -59,8 +59,7 @@ class GrpcModule : public ::bluetooth::Module {
};
class GrpcFacadeModule : public ::bluetooth::Module {
- friend GrpcModule;
-
+ friend GrpcModule;
protected:
void ListDependencies(ModuleList* list) override;
diff --git a/gd/hal/Android.bp b/gd/hal/Android.bp
index 1e7c18d9f..41b87fcb9 100644
--- a/gd/hal/Android.bp
+++ b/gd/hal/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothHalSources",
srcs: [
@@ -15,16 +6,9 @@ filegroup {
}
filegroup {
- name: "BluetoothHalTestSources",
- srcs: [
- "snoop_logger_test.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothHalSources_hci_host",
+ name: "BluetoothHalSources_hci_rootcanal",
srcs: [
- "hci_hal_host.cc",
+ "hci_hal_host_rootcanal.cc",
],
}
@@ -36,9 +20,9 @@ filegroup {
}
filegroup {
- name: "BluetoothHalTestSources_hci_host",
+ name: "BluetoothHalTestSources_hci_rootcanal",
srcs: [
- "hci_hal_host_test.cc",
+ "hci_hal_host_rootcanal_test.cc",
],
}
@@ -55,10 +39,3 @@ filegroup {
"facade.cc",
],
}
-
-filegroup {
- name: "BluetoothHalFuzzSources",
- srcs: [
- "fuzz/fuzz_hci_hal.cc",
- ],
-}
diff --git a/gd/hal/BUILD.gn b/gd/hal/BUILD.gn
deleted file mode 100644
index 9ed814a7c..000000000
--- a/gd/hal/BUILD.gn
+++ /dev/null
@@ -1,29 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-source_set("BluetoothHalSources") {
- sources = [ "snoop_logger.cc" ]
-
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ "//bt/gd:gd_default_deps" ]
-}
-
-source_set("BluetoothHalSources_hci_host") {
- sources = [ "hci_hal_host.cc" ]
-
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ "//bt/gd:gd_default_deps" ]
-}
diff --git a/gd/hal/cert/simple_hal_test.py b/gd/hal/cert/simple_hal_test.py
index c2224eeae..7094787f3 100644
--- a/gd/hal/cert/simple_hal_test.py
+++ b/gd/hal/cert/simple_hal_test.py
@@ -16,126 +16,404 @@
from datetime import timedelta
-from cert.gd_base_test import GdBaseTestClass
-from cert.event_stream import EventStream
-from cert.truth import assertThat
-from cert.py_hal import PyHal
-from cert.matchers import HciMatchers
-from cert.captures import HciCaptures
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
+from cert.event_callback_stream import EventCallbackStream
+from cert.event_asserts import EventAsserts
from google.protobuf import empty_pb2
from facade import rootservice_pb2 as facade_rootservice_pb2
-from hal import hal_facade_pb2 as hal_facade_pb2
+from hal import facade_pb2 as hal_facade_pb2
from bluetooth_packets_python3 import hci_packets
import bluetooth_packets_python3 as bt_packets
-from bluetooth_packets_python3.hci_packets import AclBuilder
-from bluetooth_packets_python3 import RawBuilder
-_GRPC_TIMEOUT = 10
-
-class SimpleHalTest(GdBaseTestClass):
-
- def setup_class(self):
- super().setup_class(dut_module='HAL', cert_module='HAL')
+class SimpleHalTest(GdFacadeOnlyBaseTestClass):
+
+ def send_cert_hci_command(self, command):
+ self.cert_device.hal.SendHciCommand(
+ hal_facade_pb2.HciCommandPacket(payload=bytes(command.Serialize())))
+
+ def send_cert_acl_data(self, handle, pb_flag, b_flag, acl):
+ lower = handle & 0xff
+ upper = (handle >> 8) & 0xf
+ upper = upper | int(pb_flag) & 0x3
+ upper = upper | ((int(b_flag) & 0x3) << 2)
+ lower_length = len(acl) & 0xff
+ upper_length = (len(acl) & 0xff00) >> 8
+ concatenated = bytes([lower, upper, lower_length, upper_length] +
+ list(acl))
+ self.cert_device.hal.SendHciAcl(
+ hal_facade_pb2.HciAclPacket(payload=concatenated))
+
+ def send_dut_hci_command(self, command):
+ self.device_under_test.hal.SendHciCommand(
+ hal_facade_pb2.HciCommandPacket(payload=bytes(command.Serialize())))
+
+ def send_dut_acl_data(self, handle, pb_flag, b_flag, acl):
+ lower = handle & 0xff
+ upper = (handle >> 8) & 0xf
+ upper = upper | int(pb_flag) & 0x3
+ upper = upper | ((int(b_flag) & 0x3) << 2)
+ lower_length = len(acl) & 0xff
+ upper_length = (len(acl) & 0xff00) >> 8
+ concatenated = bytes([lower, upper, lower_length, upper_length] +
+ list(acl))
+ self.device_under_test.hal.SendHciAcl(
+ hal_facade_pb2.HciAclPacket(payload=concatenated))
def setup_test(self):
- super().setup_test()
+ self.device_under_test.rootservice.StartStack(
+ facade_rootservice_pb2.StartStackRequest(
+ module_under_test=facade_rootservice_pb2.BluetoothModule.Value(
+ 'HAL'),))
+ self.cert_device.rootservice.StartStack(
+ facade_rootservice_pb2.StartStackRequest(
+ module_under_test=facade_rootservice_pb2.BluetoothModule.Value(
+ 'HAL'),))
- self.dut_hal = PyHal(self.dut)
- self.cert_hal = PyHal(self.cert)
+ self.device_under_test.wait_channel_ready()
+ self.cert_device.wait_channel_ready()
- self.dut_hal.reset()
- self.cert_hal.reset()
+ self.send_dut_hci_command(hci_packets.ResetBuilder())
+ self.send_cert_hci_command(hci_packets.ResetBuilder())
def teardown_test(self):
- self.dut_hal.close()
- self.cert_hal.close()
- super().teardown_test()
-
- def test_stream_events(self):
- self.dut_hal.send_hci_command(
- hci_packets.LeAddDeviceToConnectListBuilder(hci_packets.ConnectListAddressType.RANDOM, '0C:05:04:03:02:01'))
-
- assertThat(self.dut_hal.get_hci_event_stream()).emits(
- HciMatchers.Exactly(hci_packets.LeAddDeviceToConnectListCompleteBuilder(1, hci_packets.ErrorCode.SUCCESS)))
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice_pb2.StopStackRequest())
+ self.cert_device.rootservice.StopStack(
+ facade_rootservice_pb2.StopStackRequest())
+
+ def test_none_event(self):
+ with EventCallbackStream(
+ self.device_under_test.hal.FetchHciEvent(
+ empty_pb2.Empty())) as hci_event_stream:
+ hci_event_asserts = EventAsserts(hci_event_stream)
+ hci_event_asserts.assert_none(timeout=timedelta(seconds=1))
+
+ def test_fetch_hci_event(self):
+ with EventCallbackStream(
+ self.device_under_test.hal.FetchHciEvent(
+ empty_pb2.Empty())) as hci_event_stream:
+
+ hci_event_asserts = EventAsserts(hci_event_stream)
+
+ self.send_dut_hci_command(
+ hci_packets.LeAddDeviceToWhiteListBuilder(
+ hci_packets.WhiteListAddressType.RANDOM,
+ '0C:05:04:03:02:01'))
+ event = hci_packets.LeAddDeviceToWhiteListCompleteBuilder(
+ 1, hci_packets.ErrorCode.SUCCESS)
+ hci_event_asserts.assert_event_occurs(
+ lambda packet: bytes(event.Serialize()) in packet.payload)
def test_loopback_hci_command(self):
- self.dut_hal.send_hci_command(hci_packets.WriteLoopbackModeBuilder(hci_packets.LoopbackMode.ENABLE_LOCAL))
-
- command = hci_packets.LeAddDeviceToConnectListBuilder(hci_packets.ConnectListAddressType.RANDOM,
- '0C:05:04:03:02:01')
- self.dut_hal.send_hci_command(command)
+ with EventCallbackStream(
+ self.device_under_test.hal.FetchHciEvent(
+ empty_pb2.Empty())) as hci_event_stream:
- assertThat(self.dut_hal.get_hci_event_stream()).emits(HciMatchers.LoopbackOf(command))
+ self.send_dut_hci_command(
+ hci_packets.WriteLoopbackModeBuilder(
+ hci_packets.LoopbackMode.ENABLE_LOCAL))
- def test_inquiry_from_dut(self):
- self.cert_hal.send_hci_command(hci_packets.WriteScanEnableBuilder(hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN))
+ hci_event_asserts = EventAsserts(hci_event_stream)
- lap = hci_packets.Lap()
- lap.lap = 0x33
- self.dut_hal.send_hci_command(hci_packets.InquiryBuilder(lap, 0x30, 0xff))
+ command = hci_packets.LeAddDeviceToWhiteListBuilder(
+ hci_packets.WhiteListAddressType.RANDOM, '0C:05:04:03:02:01')
+ self.send_dut_hci_command(command)
+ hci_event_asserts.assert_event_occurs(
+ lambda packet: bytes(command.Serialize()) in packet.payload)
- assertThat(self.dut_hal.get_hci_event_stream()).emits(lambda packet: b'\x02\x0f' in packet.payload
- # Expecting an HCI Event (code 0x02, length 0x0f)
- )
+ def test_inquiry_from_dut(self):
+ with EventCallbackStream(
+ self.device_under_test.hal.FetchHciEvent(
+ empty_pb2.Empty())) as hci_event_stream:
+ hci_event_asserts = EventAsserts(hci_event_stream)
+ self.send_cert_hci_command(
+ hci_packets.WriteScanEnableBuilder(
+ hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN))
+ lap = hci_packets.Lap()
+ lap.lap = 0x33
+ self.send_dut_hci_command(
+ hci_packets.InquiryBuilder(lap, 0x30, 0xff))
+ hci_event_asserts.assert_event_occurs(
+ lambda packet: b'\x02\x0f' in packet.payload
+ # Expecting an HCI Event (code 0x02, length 0x0f)
+ )
def test_le_ad_scan_cert_advertises(self):
- self.dut_hal.set_random_le_address('0D:05:04:03:02:01')
-
- self.dut_hal.set_scan_parameters()
- self.dut_hal.start_scanning()
-
- advertisement = self.cert_hal.create_advertisement(
- 0,
- '0C:05:04:03:02:01',
- min_interval=512,
- max_interval=768,
- peer_address='A6:A5:A4:A3:A2:A1',
- tx_power=0x7f,
- sid=1)
- advertisement.set_data(b'Im_A_Cert')
- advertisement.start()
-
- assertThat(self.dut_hal.get_hci_event_stream()).emits(lambda packet: b'Im_A_Cert' in packet.payload)
-
- advertisement.stop()
-
- self.dut_hal.stop_scanning()
+ with EventCallbackStream(
+ self.device_under_test.hal.FetchHciEvent(
+ empty_pb2.Empty())) as hci_event_stream:
+ hci_event_asserts = EventAsserts(hci_event_stream)
+
+ # DUT scans
+ self.send_dut_hci_command(
+ hci_packets.LeSetRandomAddressBuilder('0D:05:04:03:02:01'))
+ phy_scan_params = hci_packets.PhyScanParameters()
+ phy_scan_params.le_scan_interval = 6553
+ phy_scan_params.le_scan_window = 6553
+ phy_scan_params.le_scan_type = hci_packets.LeScanType.ACTIVE
+
+ self.send_dut_hci_command(
+ hci_packets.LeSetExtendedScanParametersBuilder(
+ hci_packets.AddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.LeSetScanningFilterPolicy.ACCEPT_ALL, 1,
+ [phy_scan_params]))
+ self.send_dut_hci_command(
+ hci_packets.LeSetExtendedScanEnableBuilder(
+ hci_packets.Enable.ENABLED,
+ hci_packets.FilterDuplicates.DISABLED, 0, 0))
+
+ # CERT Advertises
+ advertising_handle = 0
+ self.send_cert_hci_command(
+ hci_packets.LeSetExtendedAdvertisingLegacyParametersBuilder(
+ advertising_handle,
+ hci_packets.LegacyAdvertisingProperties.ADV_IND,
+ 512,
+ 768,
+ 7,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.PeerAddressType.
+ PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
+ 'A6:A5:A4:A3:A2:A1',
+ hci_packets.AdvertisingFilterPolicy.ALL_DEVICES,
+ 0x7F,
+ 0, # SID
+ hci_packets.Enable.DISABLED # Scan request notification
+ ))
+
+ self.send_cert_hci_command(
+ hci_packets.LeSetExtendedAdvertisingRandomAddressBuilder(
+ advertising_handle, '0C:05:04:03:02:01'))
+
+ gap_name = hci_packets.GapData()
+ gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
+ gap_name.data = list(bytes(b'Im_A_Cert!')) # TODO: Fix and remove !
+
+ self.send_cert_hci_command(
+ hci_packets.LeSetExtendedAdvertisingDataBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_name]))
+ enabled_set = hci_packets.EnabledSet()
+ enabled_set.advertising_handle = advertising_handle
+ enabled_set.duration = 0
+ enabled_set.max_extended_advertising_events = 0
+ self.send_cert_hci_command(
+ hci_packets.LeSetExtendedAdvertisingEnableBuilder(
+ hci_packets.Enable.ENABLED, [enabled_set]))
+
+ hci_event_asserts.assert_event_occurs(
+ lambda packet: b'Im_A_Cert' in packet.payload)
+
+ # Disable Advertising
+ self.send_cert_hci_command(
+ hci_packets.LeSetExtendedAdvertisingEnableBuilder(
+ hci_packets.Enable.DISABLED, [enabled_set]))
+
+ # Disable Scanning
+ self.send_dut_hci_command(
+ hci_packets.LeSetExtendedScanEnableBuilder(
+ hci_packets.Enable.ENABLED,
+ hci_packets.FilterDuplicates.DISABLED, 0, 0))
def test_le_connection_dut_advertises(self):
- self.cert_hal.set_random_le_address('0C:05:04:03:02:01')
- self.cert_hal.initiate_le_connection('0D:05:04:03:02:01')
-
- # DUT Advertises
- advertisement = self.dut_hal.create_advertisement(0, '0D:05:04:03:02:01')
- advertisement.set_data(b'Im_The_DUT')
- advertisement.set_scan_response(b'Im_The_D')
- advertisement.start()
-
- cert_acl = self.cert_hal.complete_le_connection()
- dut_acl = self.dut_hal.complete_le_connection()
-
- dut_acl.send_first(b'Just SomeAclData')
- cert_acl.send_first(b'Just SomeMoreAclData')
-
- assertThat(self.cert_hal.get_acl_stream()).emits(lambda packet: b'SomeAclData' in packet.payload)
- assertThat(self.dut_hal.get_acl_stream()).emits(lambda packet: b'SomeMoreAclData' in packet.payload)
-
- def test_le_connect_list_connection_cert_advertises(self):
- self.dut_hal.set_random_le_address('0D:05:04:03:02:01')
- self.dut_hal.add_to_connect_list('0C:05:04:03:02:01')
- self.dut_hal.initiate_le_connection_by_connect_list('BA:D5:A4:A3:A2:A1')
-
- advertisement = self.cert_hal.create_advertisement(
- 1,
- '0C:05:04:03:02:01',
- min_interval=512,
- max_interval=768,
- peer_address='A6:A5:A4:A3:A2:A1',
- tx_power=0x7F,
- sid=0)
- advertisement.set_data(b'Im_A_Cert')
- advertisement.start()
-
- assertThat(self.cert_hal.get_hci_event_stream()).emits(HciMatchers.LeConnectionComplete())
- assertThat(self.dut_hal.get_hci_event_stream()).emits(HciMatchers.LeConnectionComplete())
+ with EventCallbackStream(self.device_under_test.hal.FetchHciEvent(empty_pb2.Empty())) as hci_event_stream, \
+ EventCallbackStream(self.cert_device.hal.FetchHciEvent(empty_pb2.Empty())) as cert_hci_event_stream, \
+ EventCallbackStream(self.device_under_test.hal.FetchHciAcl(empty_pb2.Empty())) as acl_data_stream, \
+ EventCallbackStream(self.cert_device.hal.FetchHciAcl(empty_pb2.Empty())) as cert_acl_data_stream:
+
+ hci_event_asserts = EventAsserts(hci_event_stream)
+ cert_hci_event_asserts = EventAsserts(cert_hci_event_stream)
+ acl_data_asserts = EventAsserts(acl_data_stream)
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+
+ # Cert Connects
+ self.send_cert_hci_command(
+ hci_packets.LeSetRandomAddressBuilder('0C:05:04:03:02:01'))
+ phy_scan_params = hci_packets.LeCreateConnPhyScanParameters()
+ phy_scan_params.scan_interval = 0x60
+ phy_scan_params.scan_window = 0x30
+ phy_scan_params.conn_interval_min = 0x18
+ phy_scan_params.conn_interval_max = 0x28
+ phy_scan_params.conn_latency = 0
+ phy_scan_params.supervision_timeout = 0x1f4
+ phy_scan_params.min_ce_length = 0
+ phy_scan_params.max_ce_length = 0
+ self.send_cert_hci_command(
+ hci_packets.LeExtendedCreateConnectionBuilder(
+ hci_packets.InitiatorFilterPolicy.USE_PEER_ADDRESS,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.AddressType.RANDOM_DEVICE_ADDRESS,
+ '0D:05:04:03:02:01', 1, [phy_scan_params]))
+
+ # DUT Advertises
+ advertising_handle = 0
+ self.send_dut_hci_command(
+ hci_packets.LeSetExtendedAdvertisingLegacyParametersBuilder(
+ advertising_handle,
+ hci_packets.LegacyAdvertisingProperties.ADV_IND,
+ 400,
+ 450,
+ 7,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.PeerAddressType.
+ PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
+ '00:00:00:00:00:00',
+ hci_packets.AdvertisingFilterPolicy.ALL_DEVICES,
+ 0xF8,
+ 1, #SID
+ hci_packets.Enable.DISABLED # Scan request notification
+ ))
+
+ self.send_dut_hci_command(
+ hci_packets.LeSetExtendedAdvertisingRandomAddressBuilder(
+ advertising_handle, '0D:05:04:03:02:01'))
+
+ gap_name = hci_packets.GapData()
+ gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
+ gap_name.data = list(
+ bytes(b'Im_The_DUT!')) # TODO: Fix and remove !
+
+ self.send_dut_hci_command(
+ hci_packets.LeSetExtendedAdvertisingDataBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_name]))
+
+ gap_short_name = hci_packets.GapData()
+ gap_short_name.data_type = hci_packets.GapDataType.SHORTENED_LOCAL_NAME
+ gap_short_name.data = list(bytes(b'Im_The_D'))
+
+ self.send_dut_hci_command(
+ hci_packets.LeSetExtendedAdvertisingScanResponseBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_short_name]))
+
+ enabled_set = hci_packets.EnabledSet()
+ enabled_set.advertising_handle = advertising_handle
+ enabled_set.duration = 0
+ enabled_set.max_extended_advertising_events = 0
+ self.send_dut_hci_command(
+ hci_packets.LeSetExtendedAdvertisingEnableBuilder(
+ hci_packets.Enable.ENABLED, [enabled_set]))
+
+ conn_handle = 0xfff
+
+ def payload_handle(packet):
+ packet_bytes = packet.payload
+ if b'\x3e\x13\x01\x00' in packet_bytes:
+ nonlocal conn_handle
+ cc_view = hci_packets.LeConnectionCompleteView(
+ hci_packets.LeMetaEventView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ conn_handle = cc_view.GetConnectionHandle()
+ return True
+ return False
+
+ cert_hci_event_asserts.assert_event_occurs(payload_handle)
+ cert_handle = conn_handle
+ conn_handle = 0xfff
+ hci_event_asserts.assert_event_occurs(payload_handle)
+ dut_handle = conn_handle
+
+ # Send ACL Data
+ self.send_dut_acl_data(
+ dut_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_NON_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'Just SomeAclData'))
+ self.send_cert_acl_data(
+ cert_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_NON_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'Just SomeMoreAclData'))
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeAclData' in packet.payload)
+ acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeMoreAclData' in packet.payload)
+
+ def test_le_white_list_connection_cert_advertises(self):
+ with EventCallbackStream(self.device_under_test.hal.FetchHciEvent(empty_pb2.Empty())) as hci_event_stream, \
+ EventCallbackStream(self.cert_device.hal.FetchHciEvent(empty_pb2.Empty())) as cert_hci_event_stream:
+ hci_event_asserts = EventAsserts(hci_event_stream)
+ cert_hci_event_asserts = EventAsserts(cert_hci_event_stream)
+
+ # DUT Connects
+ self.send_dut_hci_command(
+ hci_packets.LeSetRandomAddressBuilder('0D:05:04:03:02:01'))
+ self.send_dut_hci_command(
+ hci_packets.LeAddDeviceToWhiteListBuilder(
+ hci_packets.WhiteListAddressType.RANDOM,
+ '0C:05:04:03:02:01'))
+ phy_scan_params = hci_packets.LeCreateConnPhyScanParameters()
+ phy_scan_params.scan_interval = 0x60
+ phy_scan_params.scan_window = 0x30
+ phy_scan_params.conn_interval_min = 0x18
+ phy_scan_params.conn_interval_max = 0x28
+ phy_scan_params.conn_latency = 0
+ phy_scan_params.supervision_timeout = 0x1f4
+ phy_scan_params.min_ce_length = 0
+ phy_scan_params.max_ce_length = 0
+ self.send_dut_hci_command(
+ hci_packets.LeExtendedCreateConnectionBuilder(
+ hci_packets.InitiatorFilterPolicy.USE_WHITE_LIST,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.AddressType.RANDOM_DEVICE_ADDRESS,
+ 'BA:D5:A4:A3:A2:A1', 1, [phy_scan_params]))
+
+ # CERT Advertises
+ advertising_handle = 1
+ self.send_cert_hci_command(
+ hci_packets.LeSetExtendedAdvertisingLegacyParametersBuilder(
+ advertising_handle,
+ hci_packets.LegacyAdvertisingProperties.ADV_IND,
+ 512,
+ 768,
+ 7,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.PeerAddressType.
+ PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
+ 'A6:A5:A4:A3:A2:A1',
+ hci_packets.AdvertisingFilterPolicy.ALL_DEVICES,
+ 0x7F,
+ 0, # SID
+ hci_packets.Enable.DISABLED # Scan request notification
+ ))
+
+ self.send_cert_hci_command(
+ hci_packets.LeSetExtendedAdvertisingRandomAddressBuilder(
+ advertising_handle, '0C:05:04:03:02:01'))
+
+ gap_name = hci_packets.GapData()
+ gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
+ gap_name.data = list(bytes(b'Im_A_Cert!')) # TODO: Fix and remove !
+
+ self.send_cert_hci_command(
+ hci_packets.LeSetExtendedAdvertisingDataBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_name]))
+ enabled_set = hci_packets.EnabledSet()
+ enabled_set.advertising_handle = 1
+ enabled_set.duration = 0
+ enabled_set.max_extended_advertising_events = 0
+ self.send_cert_hci_command(
+ hci_packets.LeSetExtendedAdvertisingEnableBuilder(
+ hci_packets.Enable.ENABLED, [enabled_set]))
+
+ # LeConnectionComplete
+ cert_hci_event_asserts.assert_event_occurs(
+ lambda packet: b'\x3e\x13\x01\x00' in packet.payload,
+ timeout=timedelta(seconds=20))
+ hci_event_asserts.assert_event_occurs(
+ lambda packet: b'\x3e\x13\x01\x00' in packet.payload,
+ timeout=timedelta(seconds=20))
diff --git a/gd/hal/facade.cc b/gd/hal/facade.cc
index 931b2d705..3f41d6234 100644
--- a/gd/hal/facade.cc
+++ b/gd/hal/facade.cc
@@ -20,7 +20,7 @@
#include <mutex>
#include "grpc/grpc_event_queue.h"
-#include "hal/hal_facade.grpc.pb.h"
+#include "hal/facade.grpc.pb.h"
#include "hal/hci_hal.h"
using ::grpc::ServerAsyncResponseWriter;
@@ -36,14 +36,12 @@ class HciHalFacadeService : public HciHalFacade::Service, public ::bluetooth::ha
hal->registerIncomingPacketCallback(this);
}
- ~HciHalFacadeService() {
+ ~HciHalFacadeService() override {
hal_->unregisterIncomingPacketCallback();
}
- ::grpc::Status SendCommand(
- ::grpc::ServerContext* context,
- const ::bluetooth::facade::Data* request,
- ::google::protobuf::Empty* response) override {
+ ::grpc::Status SendHciCommand(::grpc::ServerContext* context, const ::bluetooth::hal::HciCommandPacket* request,
+ ::google::protobuf::Empty* response) override {
std::unique_lock<std::mutex> lock(mutex_);
can_send_hci_command_ = false;
std::string req_string = request->payload();
@@ -54,55 +52,38 @@ class HciHalFacadeService : public HciHalFacade::Service, public ::bluetooth::ha
return ::grpc::Status::OK;
}
- ::grpc::Status SendAcl(
- ::grpc::ServerContext* context,
- const ::bluetooth::facade::Data* request,
- ::google::protobuf::Empty* response) override {
+ ::grpc::Status SendHciAcl(::grpc::ServerContext* context, const ::bluetooth::hal::HciAclPacket* request,
+ ::google::protobuf::Empty* response) override {
std::string req_string = request->payload();
hal_->sendAclData(std::vector<uint8_t>(req_string.begin(), req_string.end()));
return ::grpc::Status::OK;
}
- ::grpc::Status SendSco(
- ::grpc::ServerContext* context,
- const ::bluetooth::facade::Data* request,
- ::google::protobuf::Empty* response) override {
+ ::grpc::Status SendHciSco(::grpc::ServerContext* context, const ::bluetooth::hal::HciScoPacket* request,
+ ::google::protobuf::Empty* response) override {
std::string req_string = request->payload();
hal_->sendScoData(std::vector<uint8_t>(req_string.begin(), req_string.end()));
return ::grpc::Status::OK;
}
- ::grpc::Status StreamEvents(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<::bluetooth::facade::Data>* writer) override {
+ ::grpc::Status FetchHciEvent(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
+ ::grpc::ServerWriter<HciEventPacket>* writer) override {
return pending_hci_events_.RunLoop(context, writer);
};
- ::grpc::Status StreamAcl(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<::bluetooth::facade::Data>* writer) override {
+ ::grpc::Status FetchHciAcl(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
+ ::grpc::ServerWriter<HciAclPacket>* writer) override {
return pending_acl_events_.RunLoop(context, writer);
};
- ::grpc::Status StreamSco(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<::bluetooth::facade::Data>* writer) override {
+ ::grpc::Status FetchHciSco(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
+ ::grpc::ServerWriter<HciScoPacket>* writer) override {
return pending_sco_events_.RunLoop(context, writer);
};
- ::grpc::Status StreamIso(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<::bluetooth::facade::Data>* writer) override {
- return pending_iso_events_.RunLoop(context, writer);
- };
-
void hciEventReceived(bluetooth::hal::HciPacket event) override {
{
- ::bluetooth::facade::Data response;
+ HciEventPacket response;
response.set_payload(std::string(event.begin(), event.end()));
pending_hci_events_.OnIncomingEvent(std::move(response));
}
@@ -111,32 +92,25 @@ class HciHalFacadeService : public HciHalFacade::Service, public ::bluetooth::ha
}
void aclDataReceived(bluetooth::hal::HciPacket data) override {
- ::bluetooth::facade::Data response;
+ HciAclPacket response;
response.set_payload(std::string(data.begin(), data.end()));
pending_acl_events_.OnIncomingEvent(std::move(response));
}
void scoDataReceived(bluetooth::hal::HciPacket data) override {
- ::bluetooth::facade::Data response;
+ HciScoPacket response;
response.set_payload(std::string(data.begin(), data.end()));
pending_sco_events_.OnIncomingEvent(std::move(response));
}
- void isoDataReceived(bluetooth::hal::HciPacket data) override {
- ::bluetooth::facade::Data response;
- response.set_payload(std::string(data.begin(), data.end()));
- pending_iso_events_.OnIncomingEvent(std::move(response));
- }
-
private:
HciHal* hal_;
bool can_send_hci_command_ = true;
mutable std::mutex mutex_;
std::condition_variable cv_;
- ::bluetooth::grpc::GrpcEventQueue<::bluetooth::facade::Data> pending_hci_events_{"StreamEvents"};
- ::bluetooth::grpc::GrpcEventQueue<::bluetooth::facade::Data> pending_acl_events_{"StreamAcl"};
- ::bluetooth::grpc::GrpcEventQueue<::bluetooth::facade::Data> pending_sco_events_{"StreamSco"};
- ::bluetooth::grpc::GrpcEventQueue<::bluetooth::facade::Data> pending_iso_events_{"StreamIso"};
+ ::bluetooth::grpc::GrpcEventQueue<HciEventPacket> pending_hci_events_{"FetchHciEvent"};
+ ::bluetooth::grpc::GrpcEventQueue<HciAclPacket> pending_acl_events_{"FetchHciAcl"};
+ ::bluetooth::grpc::GrpcEventQueue<HciScoPacket> pending_sco_events_{"FetchHciSco"};
};
void HciHalFacadeModule::ListDependencies(ModuleList* list) {
diff --git a/gd/hal/facade.h b/gd/hal/facade.h
index ed846d5b5..fa28d1014 100644
--- a/gd/hal/facade.h
+++ b/gd/hal/facade.h
@@ -16,11 +16,11 @@
#pragma once
-#include <grpc++/grpc++.h>
-
#include <list>
#include <mutex>
+#include <grpc++/grpc++.h>
+
#include "grpc/grpc_module.h"
#include "hal/hci_hal.h"
diff --git a/gd/hal/facade.proto b/gd/hal/facade.proto
new file mode 100644
index 000000000..539e81047
--- /dev/null
+++ b/gd/hal/facade.proto
@@ -0,0 +1,31 @@
+syntax = "proto3";
+
+package bluetooth.hal;
+
+import "google/protobuf/empty.proto";
+
+service HciHalFacade {
+ rpc SendHciCommand(HciCommandPacket) returns (google.protobuf.Empty) {}
+ rpc SendHciAcl(HciAclPacket) returns (google.protobuf.Empty) {}
+ rpc SendHciSco(HciScoPacket) returns (google.protobuf.Empty) {}
+
+ rpc FetchHciEvent(google.protobuf.Empty) returns (stream HciEventPacket) {}
+ rpc FetchHciAcl(google.protobuf.Empty) returns (stream HciAclPacket) {}
+ rpc FetchHciSco(google.protobuf.Empty) returns (stream HciScoPacket) {}
+}
+
+message HciEventPacket {
+ bytes payload = 1;
+}
+
+message HciCommandPacket {
+ bytes payload = 1;
+}
+
+message HciAclPacket {
+ bytes payload = 1;
+}
+
+message HciScoPacket {
+ bytes payload = 1;
+}
diff --git a/gd/hal/fuzz/fuzz_hci_hal.cc b/gd/hal/fuzz/fuzz_hci_hal.cc
deleted file mode 100644
index 741fb6d36..000000000
--- a/gd/hal/fuzz/fuzz_hci_hal.cc
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hal/fuzz/fuzz_hci_hal.h"
-
-#include "fuzz/helpers.h"
-#include "hci/fuzz/status_vs_complete_commands.h"
-
-namespace bluetooth {
-namespace hal {
-namespace fuzz {
-using bluetooth::fuzz::GetArbitraryBytes;
-
-void FuzzHciHal::registerIncomingPacketCallback(HciHalCallbacks* callbacks) {
- callbacks_ = callbacks;
-}
-
-void FuzzHciHal::unregisterIncomingPacketCallback() {
- callbacks_ = nullptr;
-}
-
-void FuzzHciHal::injectArbitrary(FuzzedDataProvider& fdp) {
- const uint8_t action = fdp.ConsumeIntegralInRange(0, 4);
- switch (action) {
- case 1:
- injectAclData(GetArbitraryBytes(&fdp));
- break;
- case 2:
- injectHciEvent(GetArbitraryBytes(&fdp));
- break;
- case 3:
- injectScoData(GetArbitraryBytes(&fdp));
- break;
- case 4:
- injectIsoData(GetArbitraryBytes(&fdp));
- break;
- }
-}
-
-void FuzzHciHal::sendHciCommand(HciPacket packet) {
- hci::CommandView command = hci::CommandView::FromBytes(packet);
- if (!command.IsValid()) {
- return;
- }
-
- waiting_opcode_ = command.GetOpCode();
- waiting_for_status_ = hci::fuzz::uses_command_status(waiting_opcode_);
-}
-
-void FuzzHciHal::injectHciEvent(std::vector<uint8_t> data) {
- hci::EventView event = hci::EventView::FromBytes(data);
- if (!event.IsValid()) {
- return;
- }
-
- hci::CommandCompleteView complete = hci::CommandCompleteView::Create(event);
- if (complete.IsValid()) {
- if (waiting_for_status_ || complete.GetCommandOpCode() != waiting_opcode_) {
- return;
- }
- } else if (!waiting_for_status_) {
- return;
- }
-
- hci::CommandStatusView status = hci::CommandStatusView::Create(event);
- if (status.IsValid()) {
- if (!waiting_for_status_ || status.GetCommandOpCode() != waiting_opcode_) {
- return;
- }
- } else if (waiting_for_status_) {
- return;
- }
-
- callbacks_->hciEventReceived(data);
-}
-
-void FuzzHciHal::injectAclData(std::vector<uint8_t> data) {
- hci::AclView aclPacket = hci::AclView::FromBytes(data);
- if (!aclPacket.IsValid()) {
- return;
- }
-
- callbacks_->aclDataReceived(data);
-}
-
-void FuzzHciHal::injectScoData(std::vector<uint8_t> data) {
- hci::ScoView scoPacket = hci::ScoView::FromBytes(data);
- if (!scoPacket.IsValid()) {
- return;
- }
-
- callbacks_->scoDataReceived(data);
-}
-
-void FuzzHciHal::injectIsoData(std::vector<uint8_t> data) {
- hci::IsoView isoPacket = hci::IsoView::FromBytes(data);
- if (!isoPacket.IsValid()) {
- return;
- }
-
- callbacks_->isoDataReceived(data);
-}
-
-const ModuleFactory FuzzHciHal::Factory = ModuleFactory([]() { return new FuzzHciHal(); });
-
-} // namespace fuzz
-} // namespace hal
-} // namespace bluetooth
diff --git a/gd/hal/fuzz/fuzz_hci_hal.h b/gd/hal/fuzz/fuzz_hci_hal.h
deleted file mode 100644
index 6024f3aca..000000000
--- a/gd/hal/fuzz/fuzz_hci_hal.h
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "fuzz/helpers.h"
-#include "hal/hci_hal.h"
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace hal {
-namespace fuzz {
-
-class FuzzHciHal : public HciHal {
- public:
- void registerIncomingPacketCallback(HciHalCallbacks* callbacks) override;
- void unregisterIncomingPacketCallback() override;
-
- void sendHciCommand(HciPacket command) override;
- void sendAclData(HciPacket packet) override {}
- void sendScoData(HciPacket packet) override {}
- void sendIsoData(HciPacket packet) override {}
-
- void injectArbitrary(FuzzedDataProvider& fdp);
-
- std::string ToString() const override {
- return "HciHalFuzz";
- }
-
- static const ModuleFactory Factory;
-
- protected:
- void ListDependencies(ModuleList* list) override {}
- void Start() override {}
- void Stop() override {}
-
- private:
- void injectAclData(std::vector<uint8_t> data);
- void injectHciEvent(std::vector<uint8_t> data);
- void injectScoData(std::vector<uint8_t> data);
- void injectIsoData(std::vector<uint8_t> data);
-
- HciHalCallbacks* callbacks_;
- hci::OpCode waiting_opcode_;
- bool waiting_for_status_;
-};
-
-} // namespace fuzz
-} // namespace hal
-} // namespace bluetooth
diff --git a/gd/hal/hal_facade.proto b/gd/hal/hal_facade.proto
deleted file mode 100644
index 109af0d6e..000000000
--- a/gd/hal/hal_facade.proto
+++ /dev/null
@@ -1,20 +0,0 @@
-syntax = "proto3";
-
-package bluetooth.hal;
-
-import "google/protobuf/empty.proto";
-import "facade/common.proto";
-
-service HciHalFacade {
- rpc SendCommand(facade.Data) returns (google.protobuf.Empty) {}
- rpc StreamEvents(google.protobuf.Empty) returns (stream facade.Data) {}
-
- rpc SendAcl(facade.Data) returns (google.protobuf.Empty) {}
- rpc StreamAcl(google.protobuf.Empty) returns (stream facade.Data) {}
-
- rpc SendSco(facade.Data) returns (google.protobuf.Empty) {}
- rpc StreamSco(google.protobuf.Empty) returns (stream facade.Data) {}
-
- rpc SendIso(facade.Data) returns (google.protobuf.Empty) {}
- rpc StreamIso(google.protobuf.Empty) returns (stream facade.Data) {}
-}
diff --git a/gd/hal/hci_hal.h b/gd/hal/hci_hal.h
index 7a80ffa0e..f95a4f9d1 100644
--- a/gd/hal/hci_hal.h
+++ b/gd/hal/hci_hal.h
@@ -40,17 +40,13 @@ class HciHalCallbacks {
// @param event is the HCI event to be sent to the Bluetooth stack
virtual void hciEventReceived(HciPacket event) = 0;
- // Send an ACL data packet from the controller to the host
+ // Send an ACL data packet form the controller to the host
// @param data the ACL HCI packet to be passed to the host stack
virtual void aclDataReceived(HciPacket data) = 0;
- // Send a SCO data packet from the controller to the host
+ // Send a SCO data packet form the controller to the host
// @param data the SCO HCI packet to be passed to the host stack
virtual void scoDataReceived(HciPacket data) = 0;
-
- // Send an ISO data packet from the controller to the host
- // @param data the ISO HCI packet to be passed to the host stack
- virtual void isoDataReceived(HciPacket data) = 0;
};
// Mirrors hardware/interfaces/bluetooth/1.0/IBluetoothHci.hal in Android
@@ -60,7 +56,6 @@ class HciHalCallbacks {
// Abstraction Layer (HAL). Dealing only in HCI packets and events simplifies
// the stack and abstracts away power management, initialization, and other
// implementation-specific details related to the hardware.
-// LINT.IfChange
class HciHal : public ::bluetooth::Module {
public:
static const ModuleFactory Factory;
@@ -92,13 +87,7 @@ class HciHal : public ::bluetooth::Module {
// V4.2, Vol 2, Part 5, Section 5.4.3) to the Bluetooth controller.
// Packets must be processed in order.
virtual void sendScoData(HciPacket data) = 0;
-
- // Send an HCI ISO data packet (as specified in the Bluetooth Specification
- // V5.2, Vol 4, Part E, Section 5.4.5) to the Bluetooth controller.
- // Packets must be processed in order.
- virtual void sendIsoData(HciPacket data) = 0;
};
-// LINT.ThenChange(fuzz/fuzz_hci_hal.h)
} // namespace hal
} // namespace bluetooth
diff --git a/gd/hal/hci_hal_android_hidl.cc b/gd/hal/hci_hal_android_hidl.cc
index 4979ef056..7e45d89d5 100644
--- a/gd/hal/hci_hal_android_hidl.cc
+++ b/gd/hal/hci_hal_android_hidl.cc
@@ -14,29 +14,25 @@
* limitations under the License.
*/
-#include <android/hardware/bluetooth/1.0/types.h>
-#include <android/hardware/bluetooth/1.1/IBluetoothHci.h>
-#include <android/hardware/bluetooth/1.1/IBluetoothHciCallbacks.h>
-#include <stdlib.h>
+#include "hal/hci_hal.h"
-#include <future>
+#include <stdlib.h>
#include <vector>
+#include <future>
+
+#include <android/hardware/bluetooth/1.0/IBluetoothHci.h>
+#include <android/hardware/bluetooth/1.0/IBluetoothHciCallbacks.h>
+#include <android/hardware/bluetooth/1.0/types.h>
-#include "btaa/activity_attribution.h"
-#include "common/init_flags.h"
-#include "common/stop_watch.h"
-#include "common/strings.h"
-#include "hal/hci_hal.h"
#include "hal/snoop_logger.h"
#include "os/log.h"
using ::android::hardware::hidl_vec;
using ::android::hardware::Return;
using ::android::hardware::Void;
-using ::android::hardware::bluetooth::V1_1::IBluetoothHci;
-using ::android::hardware::bluetooth::V1_1::IBluetoothHciCallbacks;
+using ::android::hardware::bluetooth::V1_0::IBluetoothHci;
+using ::android::hardware::bluetooth::V1_0::IBluetoothHciCallbacks;
using HidlStatus = ::android::hardware::bluetooth::V1_0::Status;
-using IBluetoothHci_1_0 = ::android::hardware::bluetooth::V1_0::IBluetoothHci;
namespace bluetooth {
namespace hal {
@@ -46,26 +42,16 @@ class HciDeathRecipient : public ::android::hardware::hidl_death_recipient {
public:
virtual void serviceDied(uint64_t /*cookie*/, const android::wp<::android::hidl::base::V1_0::IBase>& /*who*/) {
LOG_ERROR("Bluetooth HAL service died!");
- common::StopWatch::DumpStopWatchLog();
abort();
}
};
android::sp<HciDeathRecipient> hci_death_recipient_ = new HciDeathRecipient();
-template <class VecType>
-std::string GetTimerText(const char* func_name, VecType vec) {
- return common::StringFormat(
- "%s: len %zu, 1st 5 bytes '%s'",
- func_name,
- vec.size(),
- common::ToHexString(vec.begin(), std::min(vec.end(), vec.begin() + 5)).c_str());
-}
-
class InternalHciCallbacks : public IBluetoothHciCallbacks {
public:
- InternalHciCallbacks(activity_attribution::ActivityAttribution* btaa_logger_, SnoopLogger* btsnoop_logger)
- : btaa_logger_(btaa_logger_), btsnoop_logger_(btsnoop_logger) {
+ InternalHciCallbacks(SnoopLogger* btsnoop_logger)
+ : btsnoop_logger_(btsnoop_logger) {
init_promise_ = new std::promise<void>();
}
@@ -83,70 +69,52 @@ class InternalHciCallbacks : public IBluetoothHciCallbacks {
}
Return<void> initializationComplete(HidlStatus status) {
- common::StopWatch(__func__);
ASSERT(status == HidlStatus::SUCCESS);
init_promise_->set_value();
return Void();
}
- Return<void> hciEventReceived(const hidl_vec<uint8_t>& event) override {
- common::StopWatch(GetTimerText(__func__, event));
+ Return<void> hciEventReceived(const hidl_vec<uint8_t>& event) {
std::vector<uint8_t> received_hci_packet(event.begin(), event.end());
- btsnoop_logger_->Capture(received_hci_packet, SnoopLogger::Direction::INCOMING, SnoopLogger::PacketType::EVT);
- if (common::init_flags::btaa_hci_is_enabled()) {
- btaa_logger_->Capture(received_hci_packet, SnoopLogger::PacketType::EVT);
- }
+ btsnoop_logger_->capture(received_hci_packet, SnoopLogger::Direction::INCOMING,
+ SnoopLogger::PacketType::EVT);
if (callback_ != nullptr) {
callback_->hciEventReceived(std::move(received_hci_packet));
}
return Void();
}
- Return<void> aclDataReceived(const hidl_vec<uint8_t>& data) override {
- common::StopWatch(GetTimerText(__func__, data));
+ Return<void> aclDataReceived(const hidl_vec<uint8_t>& data) {
std::vector<uint8_t> received_hci_packet(data.begin(), data.end());
- btsnoop_logger_->Capture(received_hci_packet, SnoopLogger::Direction::INCOMING, SnoopLogger::PacketType::ACL);
- if (common::init_flags::btaa_hci_is_enabled()) {
- btaa_logger_->Capture(received_hci_packet, SnoopLogger::PacketType::ACL);
- }
+ btsnoop_logger_->capture(received_hci_packet, SnoopLogger::Direction::INCOMING,
+ SnoopLogger::PacketType::ACL);
if (callback_ != nullptr) {
callback_->aclDataReceived(std::move(received_hci_packet));
}
return Void();
}
- Return<void> scoDataReceived(const hidl_vec<uint8_t>& data) override {
- common::StopWatch(GetTimerText(__func__, data));
+ Return<void> scoDataReceived(const hidl_vec<uint8_t>& data) {
std::vector<uint8_t> received_hci_packet(data.begin(), data.end());
- btsnoop_logger_->Capture(received_hci_packet, SnoopLogger::Direction::INCOMING, SnoopLogger::PacketType::SCO);
- if (common::init_flags::btaa_hci_is_enabled()) {
- btaa_logger_->Capture(received_hci_packet, SnoopLogger::PacketType::SCO);
- }
+ btsnoop_logger_->capture(received_hci_packet, SnoopLogger::Direction::INCOMING,
+ SnoopLogger::PacketType::SCO);
if (callback_ != nullptr) {
callback_->scoDataReceived(std::move(received_hci_packet));
}
return Void();
}
- Return<void> isoDataReceived(const hidl_vec<uint8_t>& data) override {
- common::StopWatch(GetTimerText(__func__, data));
- std::vector<uint8_t> received_hci_packet(data.begin(), data.end());
- btsnoop_logger_->Capture(received_hci_packet, SnoopLogger::Direction::INCOMING, SnoopLogger::PacketType::ISO);
- if (callback_ != nullptr) {
- callback_->isoDataReceived(std::move(received_hci_packet));
- }
- return Void();
- }
-
private:
std::promise<void>* init_promise_ = nullptr;
HciHalCallbacks* callback_ = nullptr;
- activity_attribution::ActivityAttribution* btaa_logger_ = nullptr;
SnoopLogger* btsnoop_logger_ = nullptr;
};
} // namespace
+const std::string SnoopLogger::DefaultFilePath = "/data/misc/bluetooth/logs/btsnoop_hci.log";
+const bool SnoopLogger::AlwaysFlush = false;
+
class HciHalHidl : public HciHal {
public:
void registerIncomingPacketCallback(HciHalCallbacks* callback) override {
@@ -158,73 +126,35 @@ class HciHalHidl : public HciHal {
}
void sendHciCommand(HciPacket command) override {
- btsnoop_logger_->Capture(command, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::CMD);
- if (common::init_flags::btaa_hci_is_enabled()) {
- btaa_logger_->Capture(command, SnoopLogger::PacketType::CMD);
- }
+ btsnoop_logger_->capture(command, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::CMD);
bt_hci_->sendHciCommand(command);
}
void sendAclData(HciPacket packet) override {
- btsnoop_logger_->Capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::ACL);
- if (common::init_flags::btaa_hci_is_enabled()) {
- btaa_logger_->Capture(packet, SnoopLogger::PacketType::ACL);
- }
+ btsnoop_logger_->capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::ACL);
bt_hci_->sendAclData(packet);
}
void sendScoData(HciPacket packet) override {
- btsnoop_logger_->Capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::SCO);
- if (common::init_flags::btaa_hci_is_enabled()) {
- btaa_logger_->Capture(packet, SnoopLogger::PacketType::SCO);
- }
+ btsnoop_logger_->capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::SCO);
bt_hci_->sendScoData(packet);
}
- void sendIsoData(HciPacket packet) override {
- if (bt_hci_1_1_ == nullptr) {
- LOG_ERROR("ISO is not supported in HAL v1.0");
- return;
- }
-
- btsnoop_logger_->Capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::ISO);
- bt_hci_1_1_->sendIsoData(packet);
- }
-
protected:
void ListDependencies(ModuleList* list) override {
list->add<SnoopLogger>();
- if (common::init_flags::btaa_hci_is_enabled()) {
- list->add<activity_attribution::ActivityAttribution>();
- }
}
void Start() override {
- if (common::init_flags::btaa_hci_is_enabled()) {
- btaa_logger_ = GetDependency<activity_attribution::ActivityAttribution>();
- }
btsnoop_logger_ = GetDependency<SnoopLogger>();
-
- bt_hci_1_1_ = IBluetoothHci::getService();
-
- if (bt_hci_1_1_ != nullptr) {
- bt_hci_ = bt_hci_1_1_;
- } else {
- bt_hci_ = IBluetoothHci_1_0::getService();
- }
-
+ bt_hci_ = IBluetoothHci::getService();
ASSERT(bt_hci_ != nullptr);
auto death_link = bt_hci_->linkToDeath(hci_death_recipient_, 0);
ASSERT_LOG(death_link.isOk(), "Unable to set the death recipient for the Bluetooth HAL");
// Block allows allocation of a variable that might be bypassed by goto.
{
- callbacks_ = new InternalHciCallbacks(btaa_logger_, btsnoop_logger_);
- if (bt_hci_1_1_ != nullptr) {
- bt_hci_1_1_->initialize_1_1(callbacks_);
- } else {
- bt_hci_->initialize(callbacks_);
- }
-
+ callbacks_ = new InternalHciCallbacks(btsnoop_logger_);
+ bt_hci_->initialize(callbacks_);
// Don't timeout here, time out at a higher layer
callbacks_->GetInitPromise()->get_future().wait();
}
@@ -239,22 +169,17 @@ class HciHalHidl : public HciHal {
bt_hci_->close();
callbacks_->ResetCallback();
bt_hci_ = nullptr;
- bt_hci_1_1_ = nullptr;
- }
-
- std::string ToString() const override {
- return std::string("HciHalHidl");
}
private:
android::sp<InternalHciCallbacks> callbacks_;
- android::sp<IBluetoothHci_1_0> bt_hci_;
- android::sp<IBluetoothHci> bt_hci_1_1_;
- activity_attribution::ActivityAttribution* btaa_logger_;
+ android::sp<IBluetoothHci> bt_hci_;
SnoopLogger* btsnoop_logger_;
};
-const ModuleFactory HciHal::Factory = ModuleFactory([]() { return new HciHalHidl(); });
+const ModuleFactory HciHal::Factory = ModuleFactory([]() {
+ return new HciHalHidl();
+});
} // namespace hal
} // namespace bluetooth
diff --git a/gd/hal/hci_hal_android_hidl_test.cc b/gd/hal/hci_hal_android_hidl_test.cc
index 1bdff583b..5b8b68dce 100644
--- a/gd/hal/hci_hal_android_hidl_test.cc
+++ b/gd/hal/hci_hal_android_hidl_test.cc
@@ -14,12 +14,13 @@
* limitations under the License.
*/
-#include <gtest/gtest.h>
+#include "hal/hci_hal.h"
#include <chrono>
#include <future>
-#include "hal/hci_hal.h"
+#include <gtest/gtest.h>
+
#include "os/thread.h"
using ::bluetooth::os::Thread;
diff --git a/gd/hal/hci_hal_host.cc b/gd/hal/hci_hal_host_rootcanal.cc
index f5e436d80..0d9bf2252 100644
--- a/gd/hal/hci_hal_host.cc
+++ b/gd/hal/hci_hal_host_rootcanal.cc
@@ -14,21 +14,18 @@
* limitations under the License.
*/
-#include "hal/hci_hal_host.h"
+#include "hal/hci_hal_host_rootcanal.h"
+#include "hal/hci_hal.h"
#include <netdb.h>
-#include <netinet/in.h>
-#include <poll.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <unistd.h>
-
#include <chrono>
#include <csignal>
#include <mutex>
#include <queue>
-#include "hal/hci_hal.h"
#include "hal/snoop_logger.h"
#include "os/log.h"
#include "os/reactor.h"
@@ -41,169 +38,14 @@ constexpr uint8_t kH4Command = 0x01;
constexpr uint8_t kH4Acl = 0x02;
constexpr uint8_t kH4Sco = 0x03;
constexpr uint8_t kH4Event = 0x04;
-constexpr uint8_t kH4Iso = 0x05;
constexpr uint8_t kH4HeaderSize = 1;
constexpr uint8_t kHciAclHeaderSize = 4;
constexpr uint8_t kHciScoHeaderSize = 3;
constexpr uint8_t kHciEvtHeaderSize = 2;
-constexpr uint8_t kHciIsoHeaderSize = 4;
constexpr int kBufSize = 1024 + 4 + 1; // DeviceProperties::acl_data_packet_size_ + ACL header + H4 header
-#ifdef USE_LINUX_HCI_SOCKET
-constexpr uint8_t BTPROTO_HCI = 1;
-constexpr uint16_t HCI_CHANNEL_USER = 1;
-constexpr uint16_t HCI_CHANNEL_CONTROL = 3;
-constexpr uint16_t HCI_DEV_NONE = 0xffff;
-
-/* reference from <kernel>/include/net/bluetooth/mgmt.h */
-#define MGMT_OP_INDEX_LIST 0x0003
-#define MGMT_EV_INDEX_ADDED 0x0004
-#define MGMT_EV_COMMAND_COMP 0x0001
-#define MGMT_EV_SIZE_MAX 1024
-#define WRITE_NO_INTR(fn) \
- do { \
- } while ((fn) == -1 && errno == EINTR)
-
-struct sockaddr_hci {
- sa_family_t hci_family;
- unsigned short hci_dev;
- unsigned short hci_channel;
-};
-
-struct mgmt_pkt {
- uint16_t opcode;
- uint16_t index;
- uint16_t len;
- uint8_t data[MGMT_EV_SIZE_MAX];
-} __attribute__((packed));
-
-struct mgmt_event_read_index {
- uint16_t cc_opcode;
- uint8_t status;
- uint16_t num_intf;
- uint16_t index[0];
-} __attribute__((packed));
-
-int waitHciDev(int hci_interface) {
- struct sockaddr_hci addr;
- struct pollfd fds[1];
- struct mgmt_pkt ev;
- int fd;
- int ret = 0;
-
- fd = socket(PF_BLUETOOTH, SOCK_RAW, BTPROTO_HCI);
- if (fd < 0) {
- LOG_ERROR("Bluetooth socket error: %s", strerror(errno));
- return -1;
- }
- memset(&addr, 0, sizeof(addr));
- addr.hci_family = AF_BLUETOOTH;
- addr.hci_dev = HCI_DEV_NONE;
- addr.hci_channel = HCI_CHANNEL_CONTROL;
- if (bind(fd, (struct sockaddr*)&addr, sizeof(addr)) < 0) {
- LOG_ERROR("HCI Channel Control: %s", strerror(errno));
- close(fd);
- return -1;
- }
-
- fds[0].fd = fd;
- fds[0].events = POLLIN;
-
- /* Read Controller Index List Command */
- ev.opcode = MGMT_OP_INDEX_LIST;
- ev.index = HCI_DEV_NONE;
- ev.len = 0;
-
- ssize_t wrote;
- WRITE_NO_INTR(wrote = write(fd, &ev, 6));
- if (wrote != 6) {
- LOG_ERROR("Unable to write mgmt command: %s", strerror(errno));
- close(fd);
- return -1;
- }
- /* validate mentioned hci interface is present and registered with sock system */
- while (1) {
- int n;
- WRITE_NO_INTR(n = poll(fds, 1, -1));
- if (n == -1) {
- LOG_ERROR("Poll error: %s", strerror(errno));
- ret = -1;
- break;
- } else if (n == 0) {
- LOG_ERROR("Timeout, no HCI device detected");
- ret = -1;
- break;
- }
-
- if (fds[0].revents & POLLIN) {
- WRITE_NO_INTR(n = read(fd, &ev, sizeof(struct mgmt_pkt)));
- if (n < 0) {
- LOG_ERROR("Error reading control channel: %s", strerror(errno));
- ret = -1;
- break;
- }
-
- if (ev.opcode == MGMT_EV_INDEX_ADDED && ev.index == hci_interface) {
- close(fd);
- return -1;
- } else if (ev.opcode == MGMT_EV_COMMAND_COMP) {
- struct mgmt_event_read_index* cc;
- int i;
-
- cc = (struct mgmt_event_read_index*)ev.data;
-
- if (cc->cc_opcode != MGMT_OP_INDEX_LIST || cc->status != 0) continue;
-
- for (i = 0; i < cc->num_intf; i++) {
- if (cc->index[i] == hci_interface) {
- close(fd);
- return 0;
- }
- }
- }
- }
- }
-
- close(fd);
- return -1;
-}
-
-// Connect to Linux HCI socket
-int ConnectToSocket() {
- int socket_fd = socket(AF_BLUETOOTH, SOCK_RAW, BTPROTO_HCI);
- if (socket_fd < 1) {
- LOG_ERROR("can't create socket: %s", strerror(errno));
- return INVALID_FD;
- }
-
- int hci_interface = 0; // Assume we only have HCI 0
-
- if (waitHciDev(hci_interface) != 0) {
- ::close(socket_fd);
- return INVALID_FD;
- }
-
- struct sockaddr_hci addr;
- memset(&addr, 0, sizeof(addr));
- addr.hci_family = AF_BLUETOOTH;
- addr.hci_dev = hci_interface;
- addr.hci_channel = HCI_CHANNEL_USER;
- if (bind(socket_fd, (struct sockaddr*)&addr, sizeof(addr)) < 0) {
- LOG_ERROR("HCI Channel Control: %s", strerror(errno));
- ::close(socket_fd);
- return INVALID_FD;
- }
- LOG_INFO("HCI device ready");
- return socket_fd;
-}
-#else
-// Connect to root canal socket
-int ConnectToSocket() {
- auto* config = bluetooth::hal::HciHalHostRootcanalConfig::Get();
- const std::string& server = config->GetServerAddress();
- int port = config->GetPort();
-
+int ConnectToRootCanal(const std::string& server, int port) {
int socket_fd = socket(AF_INET, SOCK_STREAM, 0);
if (socket_fd < 1) {
LOG_ERROR("can't create socket: %s", strerror(errno));
@@ -240,13 +82,15 @@ int ConnectToSocket() {
}
return socket_fd;
}
-#endif
} // namespace
namespace bluetooth {
namespace hal {
-class HciHalHost : public HciHal {
+const std::string SnoopLogger::DefaultFilePath = "/tmp/btsnoop_hci.log";
+const bool SnoopLogger::AlwaysFlush = true;
+
+class HciHalHostRootcanal : public HciHal {
public:
void registerIncomingPacketCallback(HciHalCallbacks* callback) override {
std::lock_guard<std::mutex> lock(api_mutex_);
@@ -273,36 +117,27 @@ class HciHalHost : public HciHal {
std::lock_guard<std::mutex> lock(api_mutex_);
ASSERT(sock_fd_ != INVALID_FD);
std::vector<uint8_t> packet = std::move(command);
- btsnoop_logger_->Capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::CMD);
+ btsnoop_logger_->capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::CMD);
packet.insert(packet.cbegin(), kH4Command);
- write_to_fd(packet);
+ write_to_rootcanal_fd(packet);
}
void sendAclData(HciPacket data) override {
std::lock_guard<std::mutex> lock(api_mutex_);
ASSERT(sock_fd_ != INVALID_FD);
std::vector<uint8_t> packet = std::move(data);
- btsnoop_logger_->Capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::ACL);
+ btsnoop_logger_->capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::ACL);
packet.insert(packet.cbegin(), kH4Acl);
- write_to_fd(packet);
+ write_to_rootcanal_fd(packet);
}
void sendScoData(HciPacket data) override {
std::lock_guard<std::mutex> lock(api_mutex_);
ASSERT(sock_fd_ != INVALID_FD);
std::vector<uint8_t> packet = std::move(data);
- btsnoop_logger_->Capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::SCO);
+ btsnoop_logger_->capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::SCO);
packet.insert(packet.cbegin(), kH4Sco);
- write_to_fd(packet);
- }
-
- void sendIsoData(HciPacket data) override {
- std::lock_guard<std::mutex> lock(api_mutex_);
- ASSERT(sock_fd_ != INVALID_FD);
- std::vector<uint8_t> packet = std::move(data);
- btsnoop_logger_->Capture(packet, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::ISO);
- packet.insert(packet.cbegin(), kH4Iso);
- write_to_fd(packet);
+ write_to_rootcanal_fd(packet);
}
protected:
@@ -313,23 +148,24 @@ class HciHalHost : public HciHal {
void Start() override {
std::lock_guard<std::mutex> lock(api_mutex_);
ASSERT(sock_fd_ == INVALID_FD);
- sock_fd_ = ConnectToSocket();
+ sock_fd_ = ConnectToRootCanal(config_->GetServerAddress(), config_->GetPort());
ASSERT(sock_fd_ != INVALID_FD);
reactable_ = hci_incoming_thread_.GetReactor()->Register(
- sock_fd_, common::Bind(&HciHalHost::incoming_packet_received, common::Unretained(this)), common::Closure());
+ sock_fd_, common::Bind(&HciHalHostRootcanal::incoming_packet_received, common::Unretained(this)),
+ common::Closure());
btsnoop_logger_ = GetDependency<SnoopLogger>();
- LOG_INFO("HAL opened successfully");
+ LOG_INFO("Rootcanal HAL opened successfully");
}
void Stop() override {
std::lock_guard<std::mutex> lock(api_mutex_);
- LOG_INFO("HAL is closing");
+ LOG_INFO("Rootcanal HAL is closing");
if (reactable_ != nullptr) {
hci_incoming_thread_.GetReactor()->Unregister(reactable_);
- LOG_INFO("HAL is stopping, start waiting for last callback");
+ LOG_INFO("Rootcanal HAL is stopping, start waiting for last callback");
// Wait up to 1 second for the last incoming packet callback to finish
hci_incoming_thread_.GetReactor()->WaitForUnregisteredReactable(std::chrono::milliseconds(1000));
- LOG_INFO("HAL is stopping, finished waiting for last callback");
+ LOG_INFO("Rootcanal HAL is stopping, finished waiting for last callback");
ASSERT(sock_fd_ != INVALID_FD);
}
reactable_ = nullptr;
@@ -339,16 +175,13 @@ class HciHalHost : public HciHal {
}
::close(sock_fd_);
sock_fd_ = INVALID_FD;
- LOG_INFO("HAL is closed");
- }
-
- std::string ToString() const override {
- return std::string("HciHalHost");
+ LOG_INFO("Rootcanal HAL is closed");
}
private:
// Held when APIs are called, NOT to be held during callbacks
std::mutex api_mutex_;
+ HciHalHostRootcanalConfig* config_ = HciHalHostRootcanalConfig::Get();
HciHalCallbacks* incoming_packet_callback_ = nullptr;
std::mutex incoming_packet_callback_mutex_;
int sock_fd_ = INVALID_FD;
@@ -358,14 +191,13 @@ class HciHalHost : public HciHal {
std::queue<std::vector<uint8_t>> hci_outgoing_queue_;
SnoopLogger* btsnoop_logger_ = nullptr;
- void write_to_fd(HciPacket packet) {
+ void write_to_rootcanal_fd(HciPacket packet) {
// TODO: replace this with new queue when it's ready
hci_outgoing_queue_.emplace(packet);
if (hci_outgoing_queue_.size() == 1) {
hci_incoming_thread_.GetReactor()->ModifyRegistration(
- reactable_,
- common::Bind(&HciHalHost::incoming_packet_received, common::Unretained(this)),
- common::Bind(&HciHalHost::send_packet_ready, common::Unretained(this)));
+ reactable_, common::Bind(&HciHalHostRootcanal::incoming_packet_received, common::Unretained(this)),
+ common::Bind(&HciHalHostRootcanal::send_packet_ready, common::Unretained(this)));
}
}
@@ -379,8 +211,7 @@ class HciHalHost : public HciHal {
}
if (hci_outgoing_queue_.empty()) {
this->hci_incoming_thread_.GetReactor()->ModifyRegistration(
- this->reactable_,
- common::Bind(&HciHalHost::incoming_packet_received, common::Unretained(this)),
+ this->reactable_, common::Bind(&HciHalHostRootcanal::incoming_packet_received, common::Unretained(this)),
common::Closure());
}
}
@@ -411,18 +242,16 @@ class HciHalHost : public HciHal {
uint8_t hci_evt_parameter_total_length = buf[2];
ssize_t payload_size;
- RUN_NO_INTR(
- payload_size = recv(sock_fd_, buf + kH4HeaderSize + kHciEvtHeaderSize, hci_evt_parameter_total_length, 0));
+ RUN_NO_INTR(payload_size =
+ recv(sock_fd_, buf + kH4HeaderSize + kHciEvtHeaderSize, hci_evt_parameter_total_length, 0));
ASSERT_LOG(payload_size != -1, "Can't receive from socket: %s", strerror(errno));
- ASSERT_LOG(
- payload_size == hci_evt_parameter_total_length,
- "malformed HCI event total parameter size received: %zu != %d",
- payload_size,
- hci_evt_parameter_total_length);
+ ASSERT_LOG(payload_size == hci_evt_parameter_total_length,
+ "malformed HCI event total parameter size received: %zu != %d", payload_size,
+ hci_evt_parameter_total_length);
HciPacket receivedHciPacket;
receivedHciPacket.assign(buf + kH4HeaderSize, buf + kH4HeaderSize + kHciEvtHeaderSize + payload_size);
- btsnoop_logger_->Capture(receivedHciPacket, SnoopLogger::Direction::INCOMING, SnoopLogger::PacketType::EVT);
+ btsnoop_logger_->capture(receivedHciPacket, SnoopLogger::Direction::INCOMING, SnoopLogger::PacketType::EVT);
{
std::lock_guard<std::mutex> incoming_packet_callback_lock(incoming_packet_callback_mutex_);
if (incoming_packet_callback_ == nullptr) {
@@ -442,16 +271,13 @@ class HciHalHost : public HciHal {
int payload_size;
RUN_NO_INTR(payload_size = recv(sock_fd_, buf + kH4HeaderSize + kHciAclHeaderSize, hci_acl_data_total_length, 0));
ASSERT_LOG(payload_size != -1, "Can't receive from socket: %s", strerror(errno));
- ASSERT_LOG(
- payload_size == hci_acl_data_total_length,
- "malformed ACL length received: %d != %d",
- payload_size,
- hci_acl_data_total_length);
+ ASSERT_LOG(payload_size == hci_acl_data_total_length, "malformed ACL length received: %d != %d", payload_size,
+ hci_acl_data_total_length);
ASSERT_LOG(hci_acl_data_total_length <= kBufSize - kH4HeaderSize - kHciAclHeaderSize, "packet too long");
HciPacket receivedHciPacket;
receivedHciPacket.assign(buf + kH4HeaderSize, buf + kH4HeaderSize + kHciAclHeaderSize + payload_size);
- btsnoop_logger_->Capture(receivedHciPacket, SnoopLogger::Direction::INCOMING, SnoopLogger::PacketType::ACL);
+ btsnoop_logger_->capture(receivedHciPacket, SnoopLogger::Direction::INCOMING, SnoopLogger::PacketType::ACL);
{
std::lock_guard<std::mutex> incoming_packet_callback_lock(incoming_packet_callback_mutex_);
if (incoming_packet_callback_ == nullptr) {
@@ -475,7 +301,7 @@ class HciHalHost : public HciHal {
HciPacket receivedHciPacket;
receivedHciPacket.assign(buf + kH4HeaderSize, buf + kH4HeaderSize + kHciScoHeaderSize + payload_size);
- btsnoop_logger_->Capture(receivedHciPacket, SnoopLogger::Direction::INCOMING, SnoopLogger::PacketType::SCO);
+ btsnoop_logger_->capture(receivedHciPacket, SnoopLogger::Direction::INCOMING, SnoopLogger::PacketType::SCO);
{
std::lock_guard<std::mutex> incoming_packet_callback_lock(incoming_packet_callback_mutex_);
if (incoming_packet_callback_ == nullptr) {
@@ -485,35 +311,11 @@ class HciHalHost : public HciHal {
incoming_packet_callback_->scoDataReceived(receivedHciPacket);
}
}
-
- if (buf[0] == kH4Iso) {
- RUN_NO_INTR(received_size = recv(sock_fd_, buf + kH4HeaderSize, kHciIsoHeaderSize, 0));
- ASSERT_LOG(received_size != -1, "Can't receive from socket: %s", strerror(errno));
- ASSERT_LOG(received_size == kHciIsoHeaderSize, "malformed ISO header received");
-
- uint16_t hci_iso_data_total_length = ((buf[4] & 0x3f) << 8) + buf[3];
- int payload_size;
- RUN_NO_INTR(payload_size = recv(sock_fd_, buf + kH4HeaderSize + kHciIsoHeaderSize, hci_iso_data_total_length, 0));
- ASSERT_LOG(payload_size != -1, "Can't receive from socket: %s", strerror(errno));
- ASSERT_LOG(payload_size == hci_iso_data_total_length, "malformed ISO packet received: size mismatch");
-
- HciPacket receivedHciPacket;
- receivedHciPacket.assign(buf + kH4HeaderSize, buf + kH4HeaderSize + kHciIsoHeaderSize + payload_size);
- btsnoop_logger_->Capture(receivedHciPacket, SnoopLogger::Direction::INCOMING, SnoopLogger::PacketType::ISO);
- {
- std::lock_guard<std::mutex> incoming_packet_callback_lock(incoming_packet_callback_mutex_);
- if (incoming_packet_callback_ == nullptr) {
- LOG_INFO("Dropping a ISO packet after processing");
- return;
- }
- incoming_packet_callback_->isoDataReceived(receivedHciPacket);
- }
- }
memset(buf, 0, kBufSize);
}
};
-const ModuleFactory HciHal::Factory = ModuleFactory([]() { return new HciHalHost(); });
+const ModuleFactory HciHal::Factory = ModuleFactory([]() { return new HciHalHostRootcanal(); });
} // namespace hal
} // namespace bluetooth
diff --git a/gd/hal/hci_hal_host.h b/gd/hal/hci_hal_host_rootcanal.h
index 9b73b151a..9b73b151a 100644
--- a/gd/hal/hci_hal_host.h
+++ b/gd/hal/hci_hal_host_rootcanal.h
diff --git a/gd/hal/hci_hal_host_test.cc b/gd/hal/hci_hal_host_rootcanal_test.cc
index da2ada6a0..aeff6a880 100644
--- a/gd/hal/hci_hal_host_test.cc
+++ b/gd/hal/hci_hal_host_rootcanal_test.cc
@@ -14,25 +14,25 @@
* limitations under the License.
*/
-#include "hal/hci_hal_host.h"
+#include "hal/hci_hal_host_rootcanal.h"
+#include "hal/hci_hal.h"
+#include "hal/serialize_packet.h"
#include <fcntl.h>
-#include <gtest/gtest.h>
#include <netdb.h>
#include <netinet/in.h>
#include <netinet/ip.h>
#include <sys/socket.h>
#include <sys/types.h>
#include <unistd.h>
-
#include <cstring>
#include <queue>
#include <thread>
#include <utility>
#include <vector>
-#include "hal/hci_hal.h"
-#include "hal/serialize_packet.h"
+#include <gtest/gtest.h>
+
#include "os/log.h"
#include "os/thread.h"
#include "os/utils.h"
@@ -50,7 +50,6 @@ constexpr uint8_t kH4Command = 0x01;
constexpr uint8_t kH4Acl = 0x02;
constexpr uint8_t kH4Sco = 0x03;
constexpr uint8_t kH4Event = 0x04;
-constexpr uint8_t kH4Iso = 0x05;
using H4Packet = std::vector<uint8_t>;
@@ -69,10 +68,6 @@ class TestHciHalCallbacks : public HciHalCallbacks {
void scoDataReceived(HciPacket packet) override {
incoming_packets_queue_.emplace(kH4Sco, packet);
}
-
- void isoDataReceived(HciPacket packet) override {
- incoming_packets_queue_.emplace(kH4Iso, packet);
- }
};
// An implementation of rootcanal desktop HCI server which listens on localhost:kListeningPort
@@ -228,15 +223,6 @@ HciPacket make_sample_h4_sco_pkt(uint8_t payload_size) {
return pkt;
}
-HciPacket make_sample_h4_iso_pkt(uint8_t payload_size) {
- HciPacket pkt;
- pkt.assign(1 + 4 + payload_size, 0x01);
- pkt[0] = kH4Iso;
- pkt[3] = payload_size;
- pkt[4] = 0;
- return pkt;
-}
-
size_t read_with_retry(int socket, uint8_t* data, size_t length) {
size_t bytes_read = 0;
ssize_t bytes_read_current = 0;
@@ -279,16 +265,6 @@ TEST_F(HciHalRootcanalTest, receive_hci_sco) {
check_packet_equal(packet, incoming_packet);
}
-TEST_F(HciHalRootcanalTest, receive_hci_iso) {
- H4Packet incoming_packet = make_sample_h4_iso_pkt(3);
- write(fake_server_socket_, incoming_packet.data(), incoming_packet.size());
- while (incoming_packets_queue_.size() != 1) {
- }
- auto packet = incoming_packets_queue_.front();
- incoming_packets_queue_.pop();
- check_packet_equal(packet, incoming_packet);
-}
-
TEST_F(HciHalRootcanalTest, receive_two_hci_evts) {
H4Packet incoming_packet = make_sample_h4_evt_pkt(3);
H4Packet incoming_packet2 = make_sample_h4_evt_pkt(5);
diff --git a/gd/hal/snoop_logger.cc b/gd/hal/snoop_logger.cc
index 786f37aec..3574b17ca 100644
--- a/gd/hal/snoop_logger.cc
+++ b/gd/hal/snoop_logger.cc
@@ -17,28 +17,32 @@
#include "hal/snoop_logger.h"
#include <arpa/inet.h>
-#include <sys/stat.h>
-
-#include <algorithm>
+#include <netinet/in.h>
#include <bitset>
#include <chrono>
-#include <sstream>
-#include "common/circular_buffer.h"
-#include "common/init_flags.h"
-#include "common/strings.h"
-#include "os/files.h"
#include "os/log.h"
-#include "os/parameter_provider.h"
-#include "os/system_properties.h"
namespace bluetooth {
namespace hal {
namespace {
-
-// Epoch in microseconds since 01/01/0000.
-constexpr uint64_t kBtSnoopEpochDelta = 0x00dcddb30f2f8000ULL;
+typedef struct {
+ uint32_t length_original;
+ uint32_t length_captured;
+ uint32_t flags;
+ uint32_t dropped_packets;
+ uint64_t timestamp;
+ uint8_t type;
+} __attribute__((__packed__)) btsnoop_packet_header_t;
+
+typedef struct {
+ uint8_t identification_pattern[8];
+ uint32_t version_number;
+ uint32_t datalink_type;
+} __attribute__((__packed__)) btsnoop_file_header_t;
+
+constexpr uint64_t BTSNOOP_EPOCH_DELTA = 0x00dcddb30f2f8000ULL;
constexpr uint32_t kBytesToTest = 0x12345678;
constexpr uint8_t kFirstByte = (const uint8_t&)kBytesToTest;
@@ -57,200 +61,36 @@ uint64_t htonll(uint64_t ll) {
}
}
-constexpr SnoopLogger::FileHeaderType kBtSnoopFileHeader = {
+constexpr btsnoop_file_header_t BTSNOOP_FILE_HEADER = {
.identification_pattern = {'b', 't', 's', 'n', 'o', 'o', 'p', 0x00},
.version_number = BTSNOOP_VERSION_NUMBER,
.datalink_type = BTSNOOP_DATALINK_TYPE};
-
-// The number of packets per btsnoop file before we rotate to the next file. As of right now there
-// are two snoop files that are rotated through. The size can be dynamically configured by setting
-// the relevant system property
-constexpr size_t kDefaultBtSnoopMaxPacketsPerFile = 0xffff;
-
-// We want to use at most 256 KB memory for btsnooz log
-constexpr size_t kDefaultBtsnoozMaxMemoryUsageBytes = 256 * 1024;
-// We restrict the maximum packet size to 150 bytes
-constexpr size_t kDefaultBtSnoozMaxBytesPerPacket = 150;
-constexpr size_t kDefaultBtSnoozMaxPayloadBytesPerPacket =
- kDefaultBtSnoozMaxBytesPerPacket - sizeof(SnoopLogger::PacketHeaderType);
-// Calculate max number of packets based on max memory usage and max packet size
-constexpr size_t kDefaultBtSnoozMaxPacketsPerBuffer =
- kDefaultBtsnoozMaxMemoryUsageBytes / kDefaultBtSnoozMaxBytesPerPacket;
-
-std::string get_btsnoop_log_path(std::string log_dir, bool filtered) {
- if (filtered) {
- log_dir.append(".filtered");
- }
- return log_dir;
-}
-
-std::string get_last_log_path(std::string log_file_path) {
- return log_file_path.append(".last");
-}
-
-void delete_btsnoop_files(const std::string& log_path) {
- LOG_INFO("Deleting logs if they exist");
- if (os::FileExists(log_path)) {
- if (!os::RemoveFile(log_path)) {
- LOG_ERROR("Failed to remove main log file at \"%s\"", log_path.c_str());
- }
- } else {
- LOG_INFO("Main log file does not exist at \"%s\"", log_path.c_str());
- }
- auto last_log_path = get_last_log_path(log_path);
- if (os::FileExists(last_log_path)) {
- if (!os::RemoveFile(last_log_path)) {
- LOG_ERROR("Failed to remove last log file at \"%s\"", log_path.c_str());
- }
- } else {
- LOG_INFO("Last log file does not exist at \"%s\"", log_path.c_str());
- }
-}
-
-size_t get_btsnooz_packet_length_to_write(const HciPacket& packet, SnoopLogger::PacketType type) {
- static const size_t kAclHeaderSize = 4;
- static const size_t kL2capHeaderSize = 4;
- static const size_t kL2capCidOffset = (kAclHeaderSize + 2);
- static const uint16_t kL2capSignalingCid = 0x0001;
-
- // Maximum amount of ACL data to log.
- // Enough for an RFCOMM frame up to the frame check;
- // not enough for a HID report or audio data.
- static const size_t kMaxBtsnoozAclSize = 14;
-
- // Calculate packet length to be included
- size_t included_length = 0;
- switch (type) {
- case SnoopLogger::PacketType::CMD:
- case SnoopLogger::PacketType::EVT:
- included_length = packet.size();
- break;
-
- case SnoopLogger::PacketType::ACL: {
- // Log ACL and L2CAP header by default
- size_t len_hci_acl = kAclHeaderSize + kL2capHeaderSize;
- // Check if we have enough data for an L2CAP header
- if (packet.size() > len_hci_acl) {
- uint16_t l2cap_cid =
- static_cast<uint16_t>(packet[kL2capCidOffset]) |
- static_cast<uint16_t>((static_cast<uint16_t>(packet[kL2capCidOffset + 1]) << static_cast<uint16_t>(8)));
- if (l2cap_cid == kL2capSignalingCid) {
- // For the signaling CID, take the full packet.
- // That way, the PSM setup is captured, allowing decoding of PSMs down
- // the road.
- return packet.size();
- } else {
- // Otherwise, return as much as we reasonably can
- len_hci_acl = kMaxBtsnoozAclSize;
- }
- }
- included_length = std::min(len_hci_acl, packet.size());
- break;
- }
-
- case SnoopLogger::PacketType::ISO:
- case SnoopLogger::PacketType::SCO:
- default:
- // We are not logging SCO and ISO packets in snooz log as they may contain voice data
- break;
- }
- return std::min(included_length, kDefaultBtSnoozMaxPayloadBytesPerPacket);
-}
-
} // namespace
-const std::string SnoopLogger::kBtSnoopLogModeDisabled = "disabled";
-const std::string SnoopLogger::kBtSnoopLogModeFiltered = "filtered";
-const std::string SnoopLogger::kBtSnoopLogModeFull = "full";
-
-const std::string SnoopLogger::kBtSnoopMaxPacketsPerFileProperty = "persist.bluetooth.btsnoopsize";
-const std::string SnoopLogger::kIsDebuggableProperty = "ro.debuggable";
-const std::string SnoopLogger::kBtSnoopLogModeProperty = "persist.bluetooth.btsnooplogmode";
-const std::string SnoopLogger::kBtSnoopDefaultLogModeProperty = "persist.bluetooth.btsnoopdefaultmode";
-
-SnoopLogger::SnoopLogger(
- std::string snoop_log_path,
- std::string snooz_log_path,
- size_t max_packets_per_file,
- const std::string& btsnoop_mode)
- : snoop_log_path_(std::move(snoop_log_path)),
- snooz_log_path_(std::move(snooz_log_path)),
- max_packets_per_file_(max_packets_per_file),
- btsnooz_buffer_(kDefaultBtSnoozMaxPacketsPerBuffer) {
- if (false && btsnoop_mode == kBtSnoopLogModeFiltered) {
- // TODO(b/163733538): implement filtered snoop log in GD, currently filtered == disabled
- LOG_INFO("Filtered Snoop Logs enabled");
- is_enabled_ = true;
- is_filtered_ = true;
- // delete unfiltered logs
- delete_btsnoop_files(get_btsnoop_log_path(snoop_log_path_, false));
- // delete snooz logs
- delete_btsnoop_files(snooz_log_path_);
- } else if (btsnoop_mode == kBtSnoopLogModeFull) {
- LOG_INFO("Snoop Logs fully enabled");
- is_enabled_ = true;
- is_filtered_ = false;
- // delete filtered logs
- delete_btsnoop_files(get_btsnoop_log_path(snoop_log_path_, true));
- // delete snooz logs
- delete_btsnoop_files(snooz_log_path_);
+SnoopLogger::SnoopLogger() {
+ bool file_exists;
+ {
+ std::ifstream btsnoop_istream(file_path);
+ file_exists = btsnoop_istream.is_open();
+ }
+ btsnoop_ostream_.open(file_path, std::ios::binary | std::ios::app | std::ios::out);
+ if (!file_exists) {
+ LOG_INFO("Creating new BTSNOOP");
+ btsnoop_ostream_.write(reinterpret_cast<const char*>(&BTSNOOP_FILE_HEADER), sizeof(btsnoop_file_header_t));
} else {
- LOG_INFO("Snoop Logs disabled");
- is_enabled_ = false;
- is_filtered_ = false;
- // delete both filtered and unfiltered logs
- delete_btsnoop_files(get_btsnoop_log_path(snoop_log_path_, true));
- delete_btsnoop_files(get_btsnoop_log_path(snoop_log_path_, false));
+ LOG_INFO("Appending to old BTSNOOP");
}
- // Add ".filtered" extension if necessary
- snoop_log_path_ = get_btsnoop_log_path(snoop_log_path_, is_filtered_);
}
-void SnoopLogger::CloseCurrentSnoopLogFile() {
- std::lock_guard<std::recursive_mutex> lock(file_mutex_);
- if (btsnoop_ostream_.is_open()) {
- btsnoop_ostream_.flush();
- btsnoop_ostream_.close();
- }
- packet_counter_ = 0;
+void SnoopLogger::SetFilePath(const std::string& filename) {
+ file_path = filename;
}
-void SnoopLogger::OpenNextSnoopLogFile() {
- std::lock_guard<std::recursive_mutex> lock(file_mutex_);
- CloseCurrentSnoopLogFile();
-
- auto last_file_path = get_last_log_path(snoop_log_path_);
-
- if (os::FileExists(snoop_log_path_)) {
- if (!os::RenameFile(snoop_log_path_, last_file_path)) {
- LOG_ERROR(
- "Unabled to rename existing snoop log from \"%s\" to \"%s\"",
- snoop_log_path_.c_str(),
- last_file_path.c_str());
- }
- } else {
- LOG_INFO("Previous log file \"%s\" does not exist, skip renaming", snoop_log_path_.c_str());
- }
-
- mode_t prevmask = umask(0);
- // do not use std::ios::app as we want override the existing file
- btsnoop_ostream_.open(snoop_log_path_, std::ios::binary | std::ios::out);
- if (!btsnoop_ostream_.good()) {
- LOG_ALWAYS_FATAL("Unable to open snoop log at \"%s\", error: \"%s\"", snoop_log_path_.c_str(), strerror(errno));
- }
- umask(prevmask);
- if (!btsnoop_ostream_.write(reinterpret_cast<const char*>(&kBtSnoopFileHeader), sizeof(FileHeaderType))) {
- LOG_ALWAYS_FATAL("Unable to write file header to \"%s\", error: \"%s\"", snoop_log_path_.c_str(), strerror(errno));
- }
- if (!btsnoop_ostream_.flush()) {
- LOG_ERROR("Failed to flush, error: \"%s\"", strerror(errno));
- }
-}
-
-void SnoopLogger::Capture(const HciPacket& packet, Direction direction, PacketType type) {
+void SnoopLogger::capture(const HciPacket& packet, Direction direction, PacketType type) {
uint64_t timestamp_us =
std::chrono::duration_cast<std::chrono::microseconds>(std::chrono::system_clock::now().time_since_epoch())
.count();
+ std::lock_guard<std::mutex> lock(file_mutex_);
std::bitset<32> flags = 0;
switch (type) {
case PacketType::CMD:
@@ -258,6 +98,9 @@ void SnoopLogger::Capture(const HciPacket& packet, Direction direction, PacketTy
flags.set(1, true);
break;
case PacketType::ACL:
+ flags.set(0, direction == Direction::INCOMING);
+ flags.set(1, false);
+ break;
case PacketType::SCO:
flags.set(0, direction == Direction::INCOMING);
flags.set(1, false);
@@ -266,165 +109,31 @@ void SnoopLogger::Capture(const HciPacket& packet, Direction direction, PacketTy
flags.set(0, true);
flags.set(1, true);
break;
- case PacketType::ISO:
- flags.set(0, direction == Direction::INCOMING);
- flags.set(1, true);
- break;
}
uint32_t length = packet.size() + /* type byte */ 1;
- PacketHeaderType header = {.length_original = htonl(length),
- .length_captured = htonl(length),
- .flags = htonl(static_cast<uint32_t>(flags.to_ulong())),
- .dropped_packets = 0,
- .timestamp = htonll(timestamp_us + kBtSnoopEpochDelta),
- .type = static_cast<uint8_t>(type)};
- {
- std::lock_guard<std::recursive_mutex> lock(file_mutex_);
- if (!is_enabled_) {
- // btsnoop disabled, log in-memory btsnooz log only
- std::stringstream ss;
- size_t included_length = get_btsnooz_packet_length_to_write(packet, type);
- header.length_captured = htonl(included_length + /* type byte */ 1);
- if (!ss.write(reinterpret_cast<const char*>(&header), sizeof(PacketHeaderType))) {
- LOG_ERROR("Failed to write packet header for btsnooz, error: \"%s\"", strerror(errno));
- }
- if (!ss.write(reinterpret_cast<const char*>(packet.data()), included_length)) {
- LOG_ERROR("Failed to write packet payload for btsnooz, error: \"%s\"", strerror(errno));
- }
- btsnooz_buffer_.Push(ss.str());
- return;
- }
- packet_counter_++;
- if (packet_counter_ > max_packets_per_file_) {
- OpenNextSnoopLogFile();
- }
- if (!btsnoop_ostream_.write(reinterpret_cast<const char*>(&header), sizeof(PacketHeaderType))) {
- LOG_ERROR("Failed to write packet header for btsnoop, error: \"%s\"", strerror(errno));
- }
- if (!btsnoop_ostream_.write(reinterpret_cast<const char*>(packet.data()), packet.size())) {
- LOG_ERROR("Failed to write packet payload for btsnoop, error: \"%s\"", strerror(errno));
- }
- // std::ofstream::flush() pushes user data into kernel memory. The data will be written even if this process
- // crashes. However, data will be lost if there is a kernel panic, which is out of scope of BT snoop log.
- // NOTE: std::ofstream::write() followed by std::ofstream::flush() has similar effect as UNIX write(fd, data, len)
- // as write() syscall dumps data into kernel memory directly
- if (!btsnoop_ostream_.flush()) {
- LOG_ERROR("Failed to flush, error: \"%s\"", strerror(errno));
- }
- }
-}
-
-void SnoopLogger::DumpSnoozLogToFile(const std::vector<std::string>& data) const {
- std::lock_guard<std::recursive_mutex> lock(file_mutex_);
- if (is_enabled_) {
- LOG_DEBUG("btsnoop log is enabled, skip dumping btsnooz log");
- return;
- }
-
- auto last_file_path = get_last_log_path(snooz_log_path_);
-
- if (os::FileExists(snooz_log_path_)) {
- if (!os::RenameFile(snooz_log_path_, last_file_path)) {
- LOG_ERROR(
- "Unabled to rename existing snooz log from \"%s\" to \"%s\"",
- snooz_log_path_.c_str(),
- last_file_path.c_str());
- }
- } else {
- LOG_INFO("Previous log file \"%s\" does not exist, skip renaming", snooz_log_path_.c_str());
- }
-
- mode_t prevmask = umask(0);
- // do not use std::ios::app as we want override the existing file
- std::ofstream btsnooz_ostream(snooz_log_path_, std::ios::binary | std::ios::out);
- if (!btsnooz_ostream.good()) {
- LOG_ALWAYS_FATAL("Unable to open snoop log at \"%s\", error: \"%s\"", snooz_log_path_.c_str(), strerror(errno));
- }
- umask(prevmask);
- if (!btsnooz_ostream.write(reinterpret_cast<const char*>(&kBtSnoopFileHeader), sizeof(FileHeaderType))) {
- LOG_ALWAYS_FATAL("Unable to write file header to \"%s\", error: \"%s\"", snooz_log_path_.c_str(), strerror(errno));
- }
- for (const auto& packet : data) {
- if (!btsnooz_ostream.write(packet.data(), packet.size())) {
- LOG_ERROR("Failed to write packet payload for btsnooz, error: \"%s\"", strerror(errno));
- }
- }
- if (!btsnooz_ostream.flush()) {
- LOG_ERROR("Failed to flush, error: \"%s\"", strerror(errno));
- }
+ btsnoop_packet_header_t header = {.length_original = htonl(length),
+ .length_captured = htonl(length),
+ .flags = htonl(static_cast<uint32_t>(flags.to_ulong())),
+ .dropped_packets = 0,
+ .timestamp = htonll(timestamp_us + BTSNOOP_EPOCH_DELTA),
+ .type = static_cast<uint8_t>(type)};
+ btsnoop_ostream_.write(reinterpret_cast<const char*>(&header), sizeof(btsnoop_packet_header_t));
+ btsnoop_ostream_.write(reinterpret_cast<const char*>(packet.data()), packet.size());
+ if (AlwaysFlush) btsnoop_ostream_.flush();
}
void SnoopLogger::ListDependencies(ModuleList* list) {
// We have no dependencies
}
-void SnoopLogger::Start() {
- std::lock_guard<std::recursive_mutex> lock(file_mutex_);
- if (is_enabled_) {
- OpenNextSnoopLogFile();
- }
-}
-
-void SnoopLogger::Stop() {
- std::lock_guard<std::recursive_mutex> lock(file_mutex_);
- LOG_DEBUG("Dumping btsnooz log data to %s", snooz_log_path_.c_str());
- DumpSnoozLogToFile(btsnooz_buffer_.Drain());
- LOG_DEBUG("Closing btsnoop log data at %s", snoop_log_path_.c_str());
- CloseCurrentSnoopLogFile();
-}
+void SnoopLogger::Start() {}
-DumpsysDataFinisher SnoopLogger::GetDumpsysData(flatbuffers::FlatBufferBuilder* builder) const {
- LOG_DEBUG("Dumping btsnooz log data to %s", snooz_log_path_.c_str());
- DumpSnoozLogToFile(btsnooz_buffer_.Pull());
- return Module::GetDumpsysData(builder);
-}
+void SnoopLogger::Stop() {}
-size_t SnoopLogger::GetMaxPacketsPerFile() {
- // Allow override max packet per file via system property
- auto max_packets_per_file = kDefaultBtSnoopMaxPacketsPerFile;
- {
- auto max_packets_per_file_prop = os::GetSystemProperty(kBtSnoopMaxPacketsPerFileProperty);
- if (max_packets_per_file_prop) {
- auto max_packets_per_file_number = common::Uint64FromString(max_packets_per_file_prop.value());
- if (max_packets_per_file_number) {
- max_packets_per_file = max_packets_per_file_number.value();
- }
- }
- }
- return max_packets_per_file;
-}
-
-std::string SnoopLogger::GetBtSnoopMode() {
- // Default mode is DISABLED on user build.
- // In userdebug/eng build, it can also be overwritten by modifying the global setting
- std::string default_mode = kBtSnoopLogModeDisabled;
- {
- auto is_debuggable = os::GetSystemProperty(kIsDebuggableProperty);
- if (is_debuggable.has_value() && common::StringTrim(is_debuggable.value()) == "1") {
- auto default_mode_property = os::GetSystemProperty(kBtSnoopDefaultLogModeProperty);
- if (default_mode_property) {
- default_mode = std::move(default_mode_property.value());
- }
- }
- }
-
- // Get the actual mode if exist
- std::string btsnoop_mode = default_mode;
- {
- auto btsnoop_mode_prop = os::GetSystemProperty(kBtSnoopLogModeProperty);
- if (btsnoop_mode_prop) {
- btsnoop_mode = std::move(btsnoop_mode_prop.value());
- }
- }
- return btsnoop_mode;
-}
+std::string SnoopLogger::file_path = SnoopLogger::DefaultFilePath;
const ModuleFactory SnoopLogger::Factory = ModuleFactory([]() {
- return new SnoopLogger(
- os::ParameterProvider::SnoopLogFilePath(),
- os::ParameterProvider::SnoozLogFilePath(),
- GetMaxPacketsPerFile(),
- GetBtSnoopMode());
+ return new SnoopLogger();
});
} // namespace hal
diff --git a/gd/hal/snoop_logger.h b/gd/hal/snoop_logger.h
index a332e3d01..8021c2b37 100644
--- a/gd/hal/snoop_logger.h
+++ b/gd/hal/snoop_logger.h
@@ -21,7 +21,6 @@
#include <mutex>
#include <string>
-#include "common/circular_buffer.h"
#include "hal/hci_hal.h"
#include "module.h"
@@ -32,85 +31,37 @@ class SnoopLogger : public ::bluetooth::Module {
public:
static const ModuleFactory Factory;
- static const std::string kBtSnoopLogModeDisabled;
- static const std::string kBtSnoopLogModeFiltered;
- static const std::string kBtSnoopLogModeFull;
+ // Each transport using SnoopLogger should define its own DefaultFilepath
+ static const std::string DefaultFilePath;
+ // Set File Path before module is started to ensure all packets are written to the right file
+ static void SetFilePath(const std::string& filename);
+ // Flag to allow flush into persistent memory on every packet captured. This is enabled on host for debugging.
+ static const bool AlwaysFlush;
- static const std::string kBtSnoopMaxPacketsPerFileProperty;
- static const std::string kIsDebuggableProperty;
- static const std::string kBtSnoopLogModeProperty;
- static const std::string kBtSnoopDefaultLogModeProperty;
-
- // Put in header for test
- struct PacketHeaderType {
- uint32_t length_original;
- uint32_t length_captured;
- uint32_t flags;
- uint32_t dropped_packets;
- uint64_t timestamp;
- uint8_t type;
- } __attribute__((__packed__));
-
- // Put in header for test
- struct FileHeaderType {
- uint8_t identification_pattern[8];
- uint32_t version_number;
- uint32_t datalink_type;
- } __attribute__((__packed__));
-
- // Returns the maximum number of packets per file
- // Changes to this value is only effective after restarting Bluetooth
- static size_t GetMaxPacketsPerFile();
-
- // Get snoop logger mode based on current system setup
- // Changes to this values is only effective after restarting Bluetooth
- static std::string GetBtSnoopMode();
-
- // Has to be defined from 1 to 4 per btsnoop format
- enum PacketType {
+ enum class PacketType {
CMD = 1,
ACL = 2,
SCO = 3,
EVT = 4,
- ISO = 5,
};
- enum Direction {
+ enum class Direction {
INCOMING,
OUTGOING,
};
- void Capture(const HciPacket& packet, Direction direction, PacketType type);
+ void capture(const HciPacket& packet, Direction direction, PacketType type);
protected:
void ListDependencies(ModuleList* list) override;
void Start() override;
void Stop() override;
- DumpsysDataFinisher GetDumpsysData(flatbuffers::FlatBufferBuilder* builder) const override;
- std::string ToString() const override {
- return std::string("SnoopLogger");
- }
-
- // Visible for testing
- SnoopLogger(
- std::string snoop_log_path,
- std::string snooz_log_path,
- size_t max_packets_per_file,
- const std::string& btsnoop_mode);
- void CloseCurrentSnoopLogFile();
- void OpenNextSnoopLogFile();
- void DumpSnoozLogToFile(const std::vector<std::string>& data) const;
private:
- std::string snoop_log_path_;
- std::string snooz_log_path_;
+ SnoopLogger();
+ static std::string file_path;
std::ofstream btsnoop_ostream_;
- bool is_enabled_ = false;
- bool is_filtered_ = false;
- size_t max_packets_per_file_;
- common::CircularBuffer<std::string> btsnooz_buffer_;
- size_t packet_counter_ = 0;
- mutable std::recursive_mutex file_mutex_;
+ std::mutex file_mutex_;
};
} // namespace hal
diff --git a/gd/hal/snoop_logger_test.cc b/gd/hal/snoop_logger_test.cc
deleted file mode 100644
index dcfe92d79..000000000
--- a/gd/hal/snoop_logger_test.cc
+++ /dev/null
@@ -1,302 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hal/snoop_logger.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-namespace testing {
-
-namespace {
-std::vector<uint8_t> kInformationRequest = {
- 0xfe,
- 0x2e,
- 0x0a,
- 0x00,
- 0x06,
- 0x00,
- 0x01,
- 0x00,
- 0x0a,
- 0x02,
- 0x02,
- 0x00,
- 0x02,
- 0x00,
-};
-
-std::vector<uint8_t> kSdpConnectionRequest = {
- 0x08, 0x20, 0x0c, 0x00, 0x08, 0x00, 0x01, 0x00, 0x02, 0x0c, 0x04, 0x00, 0x01, 0x00, 0x44, 0x00};
-
-std::vector<uint8_t> kAvdtpSuspend = {0x02, 0x02, 0x00, 0x07, 0x00, 0x03, 0x00, 0x8d, 0x00, 0x90, 0x09, 0x04};
-
-std::vector<uint8_t> kHfpAtNrec0 = {0x02, 0x02, 0x20, 0x13, 0x00, 0x0f, 0x00, 0x41, 0x00, 0x09, 0xff, 0x15,
- 0x01, 0x41, 0x54, 0x2b, 0x4e, 0x52, 0x45, 0x43, 0x3d, 0x30, 0x0d, 0x5c};
-
-} // namespace
-
-using bluetooth::TestModuleRegistry;
-using bluetooth::hal::SnoopLogger;
-
-// Expose protected constructor for test
-class TestSnoopLoggerModule : public SnoopLogger {
- public:
- TestSnoopLoggerModule(
- std::string snoop_log_path,
- std::string snooz_log_path,
- size_t max_packets_per_file,
- const std::string& btsnoop_mode)
- : SnoopLogger(std::move(snoop_log_path), std::move(snooz_log_path), max_packets_per_file, btsnoop_mode) {}
-
- std::string ToString() const override {
- return std::string("TestSnoopLoggerModule");
- }
-};
-
-class SnoopLoggerModuleTest : public Test {
- protected:
- void SetUp() override {
- temp_dir_ = std::filesystem::temp_directory_path();
- temp_snoop_log_ = temp_dir_ / "btsnoop_hci.log";
- temp_snoop_log_last_ = temp_dir_ / "btsnoop_hci.log.last";
- temp_snooz_log_ = temp_dir_ / "btsnooz_hci.log";
- temp_snooz_log_last_ = temp_dir_ / "btsnooz_hci.log.last";
- DeleteSnoopLogFiles();
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_));
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_last_));
- ASSERT_FALSE(std::filesystem::exists(temp_snooz_log_));
- ASSERT_FALSE(std::filesystem::exists(temp_snooz_log_last_));
- }
-
- void TearDown() override {
- DeleteSnoopLogFiles();
- }
-
- void DeleteSnoopLogFiles() {
- if (std::filesystem::exists(temp_snoop_log_)) {
- ASSERT_TRUE(std::filesystem::remove(temp_snoop_log_));
- }
- if (std::filesystem::exists(temp_snoop_log_last_)) {
- ASSERT_TRUE(std::filesystem::remove(temp_snoop_log_last_));
- }
- if (std::filesystem::exists(temp_snooz_log_)) {
- ASSERT_TRUE(std::filesystem::remove(temp_snooz_log_));
- }
- if (std::filesystem::exists(temp_snooz_log_last_)) {
- ASSERT_TRUE(std::filesystem::remove(temp_snooz_log_last_));
- }
- }
-
- std::filesystem::path temp_dir_;
- std::filesystem::path temp_snoop_log_;
- std::filesystem::path temp_snoop_log_last_;
- std::filesystem::path temp_snooz_log_;
- std::filesystem::path temp_snooz_log_last_;
-};
-
-TEST_F(SnoopLoggerModuleTest, empty_snoop_log_test) {
- // Actual test
- auto* snoop_looger = new TestSnoopLoggerModule(
- temp_snoop_log_.string(), temp_snooz_log_.string(), 10, SnoopLogger::kBtSnoopLogModeFull);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&SnoopLogger::Factory, snoop_looger);
- test_registry.StopAll();
-
- // Verify states after test
- ASSERT_TRUE(std::filesystem::exists(temp_snoop_log_));
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_last_));
- ASSERT_EQ(std::filesystem::file_size(temp_snoop_log_), sizeof(SnoopLogger::FileHeaderType));
-}
-
-TEST_F(SnoopLoggerModuleTest, disable_snoop_log_test) {
- // Actual test
- auto* snoop_looger = new TestSnoopLoggerModule(
- temp_snoop_log_.string(), temp_snooz_log_.string(), 10, SnoopLogger::kBtSnoopLogModeDisabled);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&SnoopLogger::Factory, snoop_looger);
- test_registry.StopAll();
-
- // Verify states after test
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_));
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_last_));
- ASSERT_TRUE(std::filesystem::exists(temp_snooz_log_));
-}
-
-TEST_F(SnoopLoggerModuleTest, capture_one_packet_test) {
- // Actual test
- auto* snoop_looger = new TestSnoopLoggerModule(
- temp_snoop_log_.string(), temp_snooz_log_.string(), 10, SnoopLogger::kBtSnoopLogModeFull);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&SnoopLogger::Factory, snoop_looger);
-
- snoop_looger->Capture(kInformationRequest, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::CMD);
-
- test_registry.StopAll();
-
- // Verify states after test
- ASSERT_TRUE(std::filesystem::exists(temp_snoop_log_));
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_last_));
- ASSERT_EQ(
- std::filesystem::file_size(temp_snoop_log_),
- sizeof(SnoopLogger::FileHeaderType) + sizeof(SnoopLogger::PacketHeaderType) + kInformationRequest.size());
-}
-
-TEST_F(SnoopLoggerModuleTest, capture_hci_cmd_btsnooz_test) {
- // Actual test
- auto* snoop_looger = new TestSnoopLoggerModule(
- temp_snoop_log_.string(), temp_snooz_log_.string(), 10, SnoopLogger::kBtSnoopLogModeDisabled);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&SnoopLogger::Factory, snoop_looger);
-
- snoop_looger->Capture(kInformationRequest, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::CMD);
-
- test_registry.StopAll();
-
- // Verify states after test
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_));
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_last_));
- ASSERT_TRUE(std::filesystem::exists(temp_snooz_log_));
- ASSERT_EQ(
- std::filesystem::file_size(temp_snooz_log_),
- sizeof(SnoopLogger::FileHeaderType) + sizeof(SnoopLogger::PacketHeaderType) + kInformationRequest.size());
-}
-
-TEST_F(SnoopLoggerModuleTest, capture_l2cap_signal_packet_btsnooz_test) {
- // Actual test
- auto* snoop_looger = new TestSnoopLoggerModule(
- temp_snoop_log_.string(), temp_snooz_log_.string(), 10, SnoopLogger::kBtSnoopLogModeDisabled);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&SnoopLogger::Factory, snoop_looger);
-
- snoop_looger->Capture(kSdpConnectionRequest, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::ACL);
-
- test_registry.StopAll();
-
- // Verify states after test
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_));
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_last_));
- ASSERT_TRUE(std::filesystem::exists(temp_snooz_log_));
- ASSERT_EQ(
- std::filesystem::file_size(temp_snooz_log_),
- sizeof(SnoopLogger::FileHeaderType) + sizeof(SnoopLogger::PacketHeaderType) + kSdpConnectionRequest.size());
-}
-
-TEST_F(SnoopLoggerModuleTest, capture_l2cap_short_data_packet_btsnooz_test) {
- // Actual test
- auto* snoop_looger = new TestSnoopLoggerModule(
- temp_snoop_log_.string(), temp_snooz_log_.string(), 10, SnoopLogger::kBtSnoopLogModeDisabled);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&SnoopLogger::Factory, snoop_looger);
-
- snoop_looger->Capture(kAvdtpSuspend, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::ACL);
-
- test_registry.StopAll();
-
- // Verify states after test
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_));
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_last_));
- ASSERT_TRUE(std::filesystem::exists(temp_snooz_log_));
- ASSERT_EQ(
- std::filesystem::file_size(temp_snooz_log_),
- sizeof(SnoopLogger::FileHeaderType) + sizeof(SnoopLogger::PacketHeaderType) + kAvdtpSuspend.size());
-}
-
-TEST_F(SnoopLoggerModuleTest, capture_l2cap_long_data_packet_btsnooz_test) {
- // Actual test
- auto* snoop_looger = new TestSnoopLoggerModule(
- temp_snoop_log_.string(), temp_snooz_log_.string(), 10, SnoopLogger::kBtSnoopLogModeDisabled);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&SnoopLogger::Factory, snoop_looger);
-
- snoop_looger->Capture(kHfpAtNrec0, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::ACL);
-
- test_registry.StopAll();
-
- // Verify states after test
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_));
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_last_));
- ASSERT_TRUE(std::filesystem::exists(temp_snooz_log_));
- ASSERT_EQ(
- std::filesystem::file_size(temp_snooz_log_),
- sizeof(SnoopLogger::FileHeaderType) + sizeof(SnoopLogger::PacketHeaderType) + 14);
-}
-
-TEST_F(SnoopLoggerModuleTest, rotate_file_at_new_session_test) {
- // Start once
- {
- auto* snoop_looger = new TestSnoopLoggerModule(
- temp_snoop_log_.string(), temp_snooz_log_.string(), 10, SnoopLogger::kBtSnoopLogModeFull);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&SnoopLogger::Factory, snoop_looger);
- snoop_looger->Capture(kInformationRequest, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::CMD);
- test_registry.StopAll();
- }
-
- // Verify states after test
- ASSERT_TRUE(std::filesystem::exists(temp_snoop_log_));
- ASSERT_FALSE(std::filesystem::exists(temp_snoop_log_last_));
- ASSERT_EQ(
- std::filesystem::file_size(temp_snoop_log_),
- sizeof(SnoopLogger::FileHeaderType) + sizeof(SnoopLogger::PacketHeaderType) + kInformationRequest.size());
-
- // Start again
- {
- auto* snoop_looger = new TestSnoopLoggerModule(
- temp_snoop_log_.string(), temp_snooz_log_.string(), 10, SnoopLogger::kBtSnoopLogModeFull);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&SnoopLogger::Factory, snoop_looger);
- snoop_looger->Capture(kInformationRequest, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::CMD);
- snoop_looger->Capture(kInformationRequest, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::CMD);
- test_registry.StopAll();
- }
-
- // Verify states after test
- ASSERT_TRUE(std::filesystem::exists(temp_snoop_log_));
- ASSERT_TRUE(std::filesystem::exists(temp_snoop_log_last_));
- ASSERT_EQ(
- std::filesystem::file_size(temp_snoop_log_),
- sizeof(SnoopLogger::FileHeaderType) + (sizeof(SnoopLogger::PacketHeaderType) + kInformationRequest.size()) * 2);
- ASSERT_EQ(
- std::filesystem::file_size(temp_snoop_log_last_),
- sizeof(SnoopLogger::FileHeaderType) + sizeof(SnoopLogger::PacketHeaderType) + kInformationRequest.size());
-}
-
-TEST_F(SnoopLoggerModuleTest, rotate_file_after_full_test) {
- // Actual test
- auto* snoop_looger = new TestSnoopLoggerModule(
- temp_snoop_log_.string(), temp_snooz_log_.string(), 10, SnoopLogger::kBtSnoopLogModeFull);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&SnoopLogger::Factory, snoop_looger);
-
- for (int i = 0; i < 11; i++) {
- snoop_looger->Capture(kInformationRequest, SnoopLogger::Direction::OUTGOING, SnoopLogger::PacketType::CMD);
- }
-
- test_registry.StopAll();
-
- // Verify states after test
- ASSERT_TRUE(std::filesystem::exists(temp_snoop_log_));
- ASSERT_TRUE(std::filesystem::exists(temp_snoop_log_last_));
- ASSERT_EQ(
- std::filesystem::file_size(temp_snoop_log_),
- sizeof(SnoopLogger::FileHeaderType) + (sizeof(SnoopLogger::PacketHeaderType) + kInformationRequest.size()) * 1);
- ASSERT_EQ(
- std::filesystem::file_size(temp_snoop_log_last_),
- sizeof(SnoopLogger::FileHeaderType) + (sizeof(SnoopLogger::PacketHeaderType) + kInformationRequest.size()) * 10);
-}
-
-} // namespace testing
diff --git a/gd/hci/Android.bp b/gd/hci/Android.bp
index d25a589b5..98d8d4140 100644
--- a/gd/hci/Android.bp
+++ b/gd/hci/Android.bp
@@ -1,55 +1,33 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothHciSources",
srcs: [
- "acl_manager/acl_connection.cc",
- "acl_manager/classic_acl_connection.cc",
- "acl_manager/le_acl_connection.cc",
- "acl_manager/round_robin_scheduler.cc",
- "acl_manager/acl_fragmenter.cc",
"acl_manager.cc",
+ "acl_fragmenter.cc",
"address.cc",
"class_of_device.cc",
"controller.cc",
+ "device.cc",
+ "device_database.cc",
"hci_layer.cc",
- "hci_metrics_logging.cc",
- "le_address_manager.cc",
"le_advertising_manager.cc",
"le_scanning_manager.cc",
- "link_key.cc",
- "uuid.cc",
- "vendor_specific_event_manager.cc",
],
}
filegroup {
- name: "BluetoothHciUnitTestSources",
+ name: "BluetoothHciTestSources",
srcs: [
"acl_builder_test.cc",
+ "acl_manager_test.cc",
"address_unittest.cc",
"address_with_type_test.cc",
"class_of_device_unittest.cc",
- "hci_packets_test.cc",
- "uuid_unittest.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothHciTestSources",
- srcs: [
- "acl_manager/round_robin_scheduler_test.cc",
- "acl_manager_test.cc",
"controller_test.cc",
+ "device_test.cc",
+ "device_database_test.cc",
+ "dual_device_test.cc",
"hci_layer_test.cc",
- "le_address_manager_test.cc",
+ "hci_packets_test.cc",
"le_advertising_manager_test.cc",
"le_scanning_manager_test.cc",
],
@@ -63,7 +41,6 @@ filegroup {
"facade/controller_facade.cc",
"facade/le_acl_manager_facade.cc",
"facade/le_advertising_manager_facade.cc",
- "facade/le_initiator_address_facade.cc",
"facade/le_scanning_manager_facade.cc",
],
}
@@ -74,12 +51,3 @@ filegroup {
"hci_packets_fuzz_test.cc",
],
}
-
-filegroup {
- name: "BluetoothHciFuzzHelperSources",
- srcs: [
- "fuzz/status_vs_complete_commands.cc",
- "fuzz/hci_layer_fuzz_client.cc",
- "fuzz/fuzz_hci_layer.cc",
- ],
-}
diff --git a/gd/hci/BUILD.gn b/gd/hci/BUILD.gn
deleted file mode 100644
index c424bbfb4..000000000
--- a/gd/hci/BUILD.gn
+++ /dev/null
@@ -1,45 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-source_set("BluetoothHciSources") {
- sources = [
- "acl_manager.cc",
- "acl_manager/acl_connection.cc",
- "acl_manager/acl_fragmenter.cc",
- "acl_manager/classic_acl_connection.cc",
- "acl_manager/le_acl_connection.cc",
- "acl_manager/round_robin_scheduler.cc",
- "address.cc",
- "class_of_device.cc",
- "controller.cc",
- "hci_layer.cc",
- "hci_metrics_logging.cc",
- "le_address_manager.cc",
- "le_advertising_manager.cc",
- "le_scanning_manager.cc",
- "link_key.cc",
- "uuid.cc",
- "vendor_specific_event_manager.cc",
- ]
-
- include_dirs = [ "//bt/gd" ]
-
- deps = [
- "//bt:libbt-platform-protos-lite",
- "//bt/gd:gd_default_deps",
- ]
-
- configs += [ "//bt:target_defaults" ]
-}
diff --git a/gd/hci/acl_builder_test.cc b/gd/hci/acl_builder_test.cc
index 4a86c3172..7fc59c69b 100644
--- a/gd/hci/acl_builder_test.cc
+++ b/gd/hci/acl_builder_test.cc
@@ -58,14 +58,14 @@ class AclBuilderTest : public ::testing::Test {
TEST(AclBuilderTest, buildAclCount) {
uint16_t handle = 0x0314;
PacketBoundaryFlag packet_boundary_flag = PacketBoundaryFlag::FIRST_AUTOMATICALLY_FLUSHABLE;
- BroadcastFlag broadcast_flag = BroadcastFlag::ACTIVE_PERIPHERAL_BROADCAST;
+ BroadcastFlag broadcast_flag = BroadcastFlag::ACTIVE_SLAVE_BROADCAST;
std::unique_ptr<RawBuilder> count_payload = std::make_unique<RawBuilder>();
count_payload->AddOctets(counting_bytes);
ASSERT_EQ(counting_bytes.size(), count_payload->size());
- std::unique_ptr<AclBuilder> count_packet =
- AclBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(count_payload));
+ std::unique_ptr<AclPacketBuilder> count_packet =
+ AclPacketBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(count_payload));
ASSERT_EQ(counting_bytes.size() + 4, count_packet->size());
@@ -74,7 +74,7 @@ TEST(AclBuilderTest, buildAclCount) {
count_packet->Serialize(it);
PacketView<true> count_packet_bytes_view(count_packet_bytes);
- AclView count_packet_view = AclView::Create(count_packet_bytes_view);
+ AclPacketView count_packet_view = AclPacketView::Create(count_packet_bytes_view);
ASSERT_TRUE(count_packet_view.IsValid());
ASSERT_EQ(handle, count_packet_view.GetHandle());
@@ -97,8 +97,8 @@ TEST(AclBuilderTest, buildAclCountInverted) {
counting_down_bytes_payload->AddOctets(counting_down_bytes);
ASSERT_EQ(counting_down_bytes.size(), counting_down_bytes_payload->size());
- std::unique_ptr<AclBuilder> counting_down_bytes_packet =
- AclBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(counting_down_bytes_payload));
+ std::unique_ptr<AclPacketBuilder> counting_down_bytes_packet =
+ AclPacketBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(counting_down_bytes_payload));
ASSERT_EQ(counting_down_bytes.size() + 4, counting_down_bytes_packet->size());
@@ -106,7 +106,7 @@ TEST(AclBuilderTest, buildAclCountInverted) {
BitInserter it(*counting_down_bytes_packet_bytes);
counting_down_bytes_packet->Serialize(it);
PacketView<true> counting_down_bytes_packet_bytes_view(counting_down_bytes_packet_bytes);
- AclView counting_down_bytes_packet_view = AclView::Create(counting_down_bytes_packet_bytes_view);
+ AclPacketView counting_down_bytes_packet_view = AclPacketView::Create(counting_down_bytes_packet_bytes_view);
ASSERT_TRUE(counting_down_bytes_packet_view.IsValid());
ASSERT_EQ(handle, counting_down_bytes_packet_view.GetHandle());
@@ -130,8 +130,8 @@ TEST(AclBuilderTest, buildInformationRequest) {
payload->AddOctets(payload_bytes);
ASSERT_EQ(payload_bytes.size(), payload->size());
- std::unique_ptr<AclBuilder> packet =
- AclBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(payload));
+ std::unique_ptr<AclPacketBuilder> packet =
+ AclPacketBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(payload));
ASSERT_EQ(information_request.size(), packet->size());
@@ -139,7 +139,7 @@ TEST(AclBuilderTest, buildInformationRequest) {
BitInserter it(*packet_bytes);
packet->Serialize(it);
PacketView<true> packet_bytes_view(packet_bytes);
- AclView packet_view = AclView::Create(packet_bytes_view);
+ AclPacketView packet_view = AclPacketView::Create(packet_bytes_view);
ASSERT_TRUE(packet_view.IsValid());
ASSERT_EQ(packet_bytes->size(), information_request.size());
diff --git a/gd/hci/acl_connection_interface.h b/gd/hci/acl_connection_interface.h
deleted file mode 100644
index f4932eefa..000000000
--- a/gd/hci/acl_connection_interface.h
+++ /dev/null
@@ -1,47 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "common/callback.h"
-#include "hci/command_interface.h"
-#include "hci/hci_packets.h"
-#include "os/utils.h"
-
-namespace bluetooth {
-namespace hci {
-
-constexpr EventCode AclConnectionEvents[] = {
- EventCode::CONNECTION_PACKET_TYPE_CHANGED,
- EventCode::ROLE_CHANGE,
- EventCode::CONNECTION_COMPLETE,
- EventCode::CONNECTION_REQUEST,
- EventCode::AUTHENTICATION_COMPLETE,
- EventCode::READ_CLOCK_OFFSET_COMPLETE,
- EventCode::MODE_CHANGE,
- EventCode::SNIFF_SUBRATING,
- EventCode::QOS_SETUP_COMPLETE,
- EventCode::FLOW_SPECIFICATION_COMPLETE,
- EventCode::FLUSH_OCCURRED,
- EventCode::READ_REMOTE_SUPPORTED_FEATURES_COMPLETE,
- EventCode::READ_REMOTE_EXTENDED_FEATURES_COMPLETE,
- EventCode::LINK_SUPERVISION_TIMEOUT_CHANGED,
-};
-
-typedef CommandInterface<AclCommandBuilder> AclConnectionInterface;
-
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/acl_fragmenter.cc b/gd/hci/acl_fragmenter.cc
index 16cbe6970..fa3b31df1 100644
--- a/gd/hci/acl_manager/acl_fragmenter.cc
+++ b/gd/hci/acl_fragmenter.cc
@@ -14,14 +14,13 @@
* limitations under the License.
*/
-#include "hci/acl_manager/acl_fragmenter.h"
+#include "hci/acl_fragmenter.h"
#include "os/log.h"
#include "packet/fragmenting_inserter.h"
namespace bluetooth {
namespace hci {
-namespace acl_manager {
AclFragmenter::AclFragmenter(size_t mtu, std::unique_ptr<packet::BasePacketBuilder> packet)
: mtu_(mtu), packet_(std::move(packet)) {}
@@ -34,6 +33,5 @@ std::vector<std::unique_ptr<packet::RawBuilder>> AclFragmenter::GetFragments() {
return to_return;
}
-} // namespace acl_manager
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/acl_manager/acl_fragmenter.h b/gd/hci/acl_fragmenter.h
index 37badef29..4bc3d0618 100644
--- a/gd/hci/acl_manager/acl_fragmenter.h
+++ b/gd/hci/acl_fragmenter.h
@@ -27,7 +27,6 @@
namespace bluetooth {
namespace hci {
-namespace acl_manager {
class AclFragmenter {
public:
@@ -41,6 +40,5 @@ class AclFragmenter {
std::unique_ptr<packet::BasePacketBuilder> packet_;
};
-} // namespace acl_manager
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/acl_manager.cc b/gd/hci/acl_manager.cc
index 9017c3a2e..027185445 100644
--- a/gd/hci/acl_manager.cc
+++ b/gd/hci/acl_manager.cc
@@ -16,40 +16,139 @@
#include "hci/acl_manager.h"
-#include <atomic>
#include <future>
+#include <queue>
#include <set>
+#include <utility>
+#include "acl_fragmenter.h"
+#include "acl_manager.h"
#include "common/bidi_queue.h"
-#include "hci/acl_manager/classic_impl.h"
-#include "hci/acl_manager/connection_management_callbacks.h"
-#include "hci/acl_manager/le_acl_connection.h"
-#include "hci/acl_manager/le_impl.h"
-#include "hci/acl_manager/round_robin_scheduler.h"
#include "hci/controller.h"
#include "hci/hci_layer.h"
-#include "hci_acl_manager_generated.h"
-#include "security/security_module.h"
-#include "storage/storage_module.h"
namespace bluetooth {
namespace hci {
constexpr uint16_t kQualcommDebugHandle = 0xedc;
+constexpr size_t kMaxQueuedPacketsPerConnection = 10;
-using acl_manager::AclConnection;
using common::Bind;
using common::BindOnce;
-using acl_manager::classic_impl;
-using acl_manager::ClassicAclConnection;
-using acl_manager::ConnectionCallbacks;
+namespace {
+class PacketViewForRecombination : public packet::PacketView<kLittleEndian> {
+ public:
+ PacketViewForRecombination(const PacketView& packetView) : PacketView(packetView) {}
+ void AppendPacketView(packet::PacketView<kLittleEndian> to_append) {
+ Append(to_append);
+ }
+};
+
+constexpr int kL2capBasicFrameHeaderSize = 4;
+
+// Per spec 5.1 Vol 2 Part B 5.3, ACL link shall carry L2CAP data. Therefore, an ACL packet shall contain L2CAP PDU.
+// This function returns the PDU size of the L2CAP data if it's a starting packet. Returns 0 if it's invalid.
+uint16_t GetL2capPduSize(AclPacketView packet) {
+ auto l2cap_payload = packet.GetPayload();
+ if (l2cap_payload.size() < kL2capBasicFrameHeaderSize) {
+ LOG_ERROR("Controller sent an invalid L2CAP starting packet!");
+ return 0;
+ }
+ return (l2cap_payload.at(1) << 8) + l2cap_payload.at(0);
+}
+
+} // namespace
+
+struct AclManager::acl_connection {
+ acl_connection(AddressWithType address_with_type, os::Handler* handler)
+ : address_with_type_(address_with_type), handler_(handler) {}
+ friend AclConnection;
+ AddressWithType address_with_type_;
+ os::Handler* handler_;
+ std::unique_ptr<AclConnection::Queue> queue_ = std::make_unique<AclConnection::Queue>(10);
+ bool is_disconnected_ = false;
+ ErrorCode disconnect_reason_;
+ os::Handler* command_complete_handler_ = nullptr;
+ os::Handler* disconnect_handler_ = nullptr;
+ ConnectionManagementCallbacks* command_complete_callbacks_ = nullptr;
+ common::OnceCallback<void(ErrorCode)> on_disconnect_callback_;
+ // For LE Connection parameter update from L2CAP
+ common::OnceCallback<void(ErrorCode)> on_connection_update_complete_callback_;
+ os::Handler* on_connection_update_complete_callback_handler_ = nullptr;
+ // Round-robin: Track if dequeue is registered for this connection
+ bool is_registered_ = false;
+ // Credits: Track the number of packets which have been sent to the controller
+ uint16_t number_of_sent_packets_ = 0;
+ PacketViewForRecombination recombination_stage_{std::make_shared<std::vector<uint8_t>>()};
+ int remaining_sdu_continuation_packet_size_ = 0;
+ bool enqueue_registered_ = false;
+ std::queue<packet::PacketView<kLittleEndian>> incoming_queue_;
+
+ std::unique_ptr<packet::PacketView<kLittleEndian>> on_incoming_data_ready() {
+ auto packet = incoming_queue_.front();
+ incoming_queue_.pop();
+ if (incoming_queue_.empty()) {
+ auto queue_end = queue_->GetDownEnd();
+ queue_end->UnregisterEnqueue();
+ enqueue_registered_ = false;
+ }
+ return std::make_unique<PacketView<kLittleEndian>>(packet);
+ }
+
+ void on_incoming_packet(AclPacketView packet) {
+ // TODO: What happens if the connection is stalled and fills up?
+ PacketView<kLittleEndian> payload = packet.GetPayload();
+ auto payload_size = payload.size();
+ auto packet_boundary_flag = packet.GetPacketBoundaryFlag();
+ if (packet_boundary_flag == PacketBoundaryFlag::FIRST_NON_AUTOMATICALLY_FLUSHABLE) {
+ LOG_ERROR("Controller is not allowed to send FIRST_NON_AUTOMATICALLY_FLUSHABLE to host except loopback mode");
+ return;
+ }
+ if (packet_boundary_flag == PacketBoundaryFlag::CONTINUING_FRAGMENT) {
+ if (remaining_sdu_continuation_packet_size_ < payload_size) {
+ LOG_WARN("Remote sent unexpected L2CAP PDU. Drop the entire L2CAP PDU");
+ recombination_stage_ = PacketViewForRecombination(std::make_shared<std::vector<uint8_t>>());
+ remaining_sdu_continuation_packet_size_ = 0;
+ return;
+ }
+ remaining_sdu_continuation_packet_size_ -= payload_size;
+ recombination_stage_.AppendPacketView(payload);
+ if (remaining_sdu_continuation_packet_size_ != 0) {
+ return;
+ } else {
+ payload = recombination_stage_;
+ recombination_stage_ = PacketViewForRecombination(std::make_shared<std::vector<uint8_t>>());
+ }
+ } else if (packet_boundary_flag == PacketBoundaryFlag::FIRST_AUTOMATICALLY_FLUSHABLE) {
+ if (recombination_stage_.size() > 0) {
+ LOG_ERROR("Controller sent a starting packet without finishing previous packet. Drop previous one.");
+ }
+ auto l2cap_pdu_size = GetL2capPduSize(packet);
+ remaining_sdu_continuation_packet_size_ = l2cap_pdu_size - (payload_size - kL2capBasicFrameHeaderSize);
+ if (remaining_sdu_continuation_packet_size_ > 0) {
+ recombination_stage_ = payload;
+ return;
+ }
+ }
+ if (incoming_queue_.size() > kMaxQueuedPacketsPerConnection) {
+ LOG_ERROR("Dropping packet due to congestion from remote:%s", address_with_type_.ToString().c_str());
+ return;
+ }
-using acl_manager::le_impl;
-using acl_manager::LeAclConnection;
-using acl_manager::LeConnectionCallbacks;
+ incoming_queue_.push(payload);
+ if (!enqueue_registered_) {
+ enqueue_registered_ = true;
+ auto queue_end = queue_->GetDownEnd();
+ queue_end->RegisterEnqueue(
+ handler_, common::Bind(&AclManager::acl_connection::on_incoming_data_ready, common::Unretained(this)));
+ }
+ }
-using acl_manager::RoundRobinScheduler;
+ void call_disconnect_callback() {
+ disconnect_handler_->Post(BindOnce(std::move(on_disconnect_callback_), disconnect_reason_));
+ }
+};
struct AclManager::impl {
impl(const AclManager& acl_manager) : acl_manager_(acl_manager) {}
@@ -58,31 +157,178 @@ struct AclManager::impl {
hci_layer_ = acl_manager_.GetDependency<HciLayer>();
handler_ = acl_manager_.GetHandler();
controller_ = acl_manager_.GetDependency<Controller>();
- round_robin_scheduler_ = new RoundRobinScheduler(handler_, controller_, hci_layer_->GetAclQueueEnd());
+ max_acl_packet_credits_ = controller_->GetControllerNumAclPacketBuffers();
+ acl_packet_credits_ = max_acl_packet_credits_;
+ acl_buffer_length_ = controller_->GetControllerAclPacketLength();
+ controller_->RegisterCompletedAclPacketsCallback(
+ common::Bind(&impl::incoming_acl_credits, common::Unretained(this)), handler_);
+ // TODO: determine when we should reject connection
+ should_accept_connection_ = common::Bind([](Address, ClassOfDevice) { return true; });
hci_queue_end_ = hci_layer_->GetAclQueueEnd();
hci_queue_end_->RegisterDequeue(
handler_, common::Bind(&impl::dequeue_and_route_acl_packet_to_connection, common::Unretained(this)));
- bool crash_on_unknown_handle = false;
- classic_impl_ =
- new classic_impl(hci_layer_, controller_, handler_, round_robin_scheduler_, crash_on_unknown_handle);
- le_impl_ = new le_impl(hci_layer_, controller_, handler_, round_robin_scheduler_, crash_on_unknown_handle);
+ hci_layer_->RegisterEventHandler(EventCode::CONNECTION_COMPLETE,
+ Bind(&impl::on_connection_complete, common::Unretained(this)), handler_);
+ hci_layer_->RegisterEventHandler(EventCode::DISCONNECTION_COMPLETE,
+ Bind(&impl::on_disconnection_complete, common::Unretained(this)), handler_);
+ hci_layer_->RegisterEventHandler(EventCode::CONNECTION_REQUEST,
+ Bind(&impl::on_incoming_connection, common::Unretained(this)), handler_);
+ hci_layer_->RegisterLeEventHandler(SubeventCode::CONNECTION_COMPLETE,
+ Bind(&impl::on_le_connection_complete, common::Unretained(this)), handler_);
+ hci_layer_->RegisterLeEventHandler(SubeventCode::ENHANCED_CONNECTION_COMPLETE,
+ Bind(&impl::on_le_enhanced_connection_complete, common::Unretained(this)),
+ handler_);
+ hci_layer_->RegisterLeEventHandler(SubeventCode::CONNECTION_UPDATE_COMPLETE,
+ Bind(&impl::on_le_connection_update_complete, common::Unretained(this)),
+ handler_);
+ hci_layer_->RegisterEventHandler(EventCode::CONNECTION_PACKET_TYPE_CHANGED,
+ Bind(&impl::on_connection_packet_type_changed, common::Unretained(this)),
+ handler_);
+ hci_layer_->RegisterEventHandler(EventCode::AUTHENTICATION_COMPLETE,
+ Bind(&impl::on_authentication_complete, common::Unretained(this)), handler_);
+ hci_layer_->RegisterEventHandler(EventCode::READ_CLOCK_OFFSET_COMPLETE,
+ Bind(&impl::on_read_clock_offset_complete, common::Unretained(this)), handler_);
+ hci_layer_->RegisterEventHandler(EventCode::MODE_CHANGE, Bind(&impl::on_mode_change, common::Unretained(this)),
+ handler_);
+ hci_layer_->RegisterEventHandler(EventCode::QOS_SETUP_COMPLETE,
+ Bind(&impl::on_qos_setup_complete, common::Unretained(this)), handler_);
+ hci_layer_->RegisterEventHandler(EventCode::ROLE_CHANGE, Bind(&impl::on_role_change, common::Unretained(this)),
+ handler_);
+ hci_layer_->RegisterEventHandler(EventCode::FLOW_SPECIFICATION_COMPLETE,
+ Bind(&impl::on_flow_specification_complete, common::Unretained(this)), handler_);
+ hci_layer_->RegisterEventHandler(EventCode::FLUSH_OCCURRED,
+ Bind(&impl::on_flush_occurred, common::Unretained(this)), handler_);
+ hci_layer_->RegisterEventHandler(EventCode::READ_REMOTE_SUPPORTED_FEATURES_COMPLETE,
+ Bind(&impl::on_read_remote_supported_features_complete, common::Unretained(this)),
+ handler_);
+ hci_layer_->RegisterEventHandler(EventCode::READ_REMOTE_EXTENDED_FEATURES_COMPLETE,
+ Bind(&impl::on_read_remote_extended_features_complete, common::Unretained(this)),
+ handler_);
+ hci_layer_->RegisterEventHandler(EventCode::READ_REMOTE_VERSION_INFORMATION_COMPLETE,
+ Bind(&impl::on_read_remote_version_information_complete, common::Unretained(this)),
+ handler_);
+ hci_layer_->RegisterEventHandler(EventCode::ENCRYPTION_CHANGE,
+ Bind(&impl::on_encryption_change, common::Unretained(this)), handler_);
+ hci_layer_->RegisterEventHandler(EventCode::LINK_SUPERVISION_TIMEOUT_CHANGED,
+ Bind(&impl::on_link_supervision_timeout_changed, common::Unretained(this)),
+ handler_);
+ hci_mtu_ = controller_->GetControllerAclPacketLength();
}
void Stop() {
- delete le_impl_;
- delete classic_impl_;
+ hci_layer_->UnregisterEventHandler(EventCode::DISCONNECTION_COMPLETE);
+ hci_layer_->UnregisterEventHandler(EventCode::CONNECTION_COMPLETE);
+ hci_layer_->UnregisterEventHandler(EventCode::CONNECTION_REQUEST);
+ hci_layer_->UnregisterEventHandler(EventCode::AUTHENTICATION_COMPLETE);
+ hci_layer_->UnregisterEventHandler(EventCode::READ_REMOTE_SUPPORTED_FEATURES_COMPLETE);
+ hci_layer_->UnregisterEventHandler(EventCode::READ_REMOTE_EXTENDED_FEATURES_COMPLETE);
hci_queue_end_->UnregisterDequeue();
- delete round_robin_scheduler_;
- if (enqueue_registered_.exchange(false)) {
- hci_queue_end_->UnregisterEnqueue();
- }
+ unregister_all_connections();
+ acl_connections_.clear();
hci_queue_end_ = nullptr;
handler_ = nullptr;
hci_layer_ = nullptr;
}
- // Invoked from some external Queue Reactable context 2
+ void incoming_acl_credits(uint16_t handle, uint16_t credits) {
+ auto connection_pair = acl_connections_.find(handle);
+ if (connection_pair == acl_connections_.end()) {
+ LOG_INFO("Dropping %hx received credits to unknown connection 0x%0hx", credits, handle);
+ return;
+ }
+ if (connection_pair->second.is_disconnected_) {
+ LOG_INFO("Dropping %hx received credits to disconnected connection 0x%0hx", credits, handle);
+ return;
+ }
+ connection_pair->second.number_of_sent_packets_ -= credits;
+ acl_packet_credits_ += credits;
+ ASSERT(acl_packet_credits_ <= max_acl_packet_credits_);
+ start_round_robin();
+ }
+
+ // Round-robin scheduler
+ void start_round_robin() {
+ if (acl_packet_credits_ == 0) {
+ return;
+ }
+ if (!fragments_to_send_.empty()) {
+ send_next_fragment();
+ return;
+ }
+ for (auto connection_pair = acl_connections_.begin(); connection_pair != acl_connections_.end();
+ connection_pair = std::next(connection_pair)) {
+ if (connection_pair->second.is_registered_) {
+ continue;
+ }
+ connection_pair->second.is_registered_ = true;
+ connection_pair->second.queue_->GetDownEnd()->RegisterDequeue(
+ handler_, common::Bind(&impl::handle_dequeue_from_upper, common::Unretained(this), connection_pair));
+ }
+ }
+
+ void handle_dequeue_from_upper(std::map<uint16_t, acl_connection>::iterator connection_pair) {
+ current_connection_pair_ = connection_pair;
+ buffer_packet();
+ }
+
+ void unregister_all_connections() {
+ for (auto connection_pair = acl_connections_.begin(); connection_pair != acl_connections_.end();
+ connection_pair = std::next(connection_pair)) {
+ if (connection_pair->second.is_registered_) {
+ connection_pair->second.is_registered_ = false;
+ connection_pair->second.queue_->GetDownEnd()->UnregisterDequeue();
+ }
+ }
+ }
+
+ void buffer_packet() {
+ unregister_all_connections();
+ BroadcastFlag broadcast_flag = BroadcastFlag::POINT_TO_POINT;
+ // Wrap packet and enqueue it
+ uint16_t handle = current_connection_pair_->first;
+
+ auto packet = current_connection_pair_->second.queue_->GetDownEnd()->TryDequeue();
+ ASSERT(packet != nullptr);
+
+ if (packet->size() <= hci_mtu_) {
+ fragments_to_send_.push_front(AclPacketBuilder::Create(handle, PacketBoundaryFlag::FIRST_AUTOMATICALLY_FLUSHABLE,
+ broadcast_flag, std::move(packet)));
+ } else {
+ auto fragments = AclFragmenter(hci_mtu_, std::move(packet)).GetFragments();
+ PacketBoundaryFlag packet_boundary_flag = PacketBoundaryFlag::FIRST_AUTOMATICALLY_FLUSHABLE;
+ for (size_t i = 0; i < fragments.size(); i++) {
+ fragments_to_send_.push_back(
+ AclPacketBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(fragments[i])));
+ packet_boundary_flag = PacketBoundaryFlag::CONTINUING_FRAGMENT;
+ }
+ }
+ ASSERT(fragments_to_send_.size() > 0);
+
+ current_connection_pair_->second.number_of_sent_packets_ += fragments_to_send_.size();
+ send_next_fragment();
+ }
+
+ void send_next_fragment() {
+ hci_queue_end_->RegisterEnqueue(handler_,
+ common::Bind(&impl::handle_enqueue_next_fragment, common::Unretained(this)));
+ }
+
+ std::unique_ptr<AclPacketBuilder> handle_enqueue_next_fragment() {
+ ASSERT(acl_packet_credits_ > 0);
+ if (acl_packet_credits_ == 1 || fragments_to_send_.size() == 1) {
+ hci_queue_end_->UnregisterEnqueue();
+ if (fragments_to_send_.size() == 1) {
+ handler_->Post(common::BindOnce(&impl::start_round_robin, common::Unretained(this)));
+ }
+ }
+ ASSERT(fragments_to_send_.size() > 0);
+ auto raw_pointer = fragments_to_send_.front().release();
+ acl_packet_credits_ -= 1;
+ fragments_to_send_.pop_front();
+ return std::unique_ptr<AclPacketBuilder>(raw_pointer);
+ }
+
void dequeue_and_route_acl_packet_to_connection() {
auto packet = hci_queue_end_->TryDequeue();
ASSERT(packet != nullptr);
@@ -94,195 +340,1792 @@ struct AclManager::impl {
if (handle == kQualcommDebugHandle) {
return;
}
- auto connection_pair = classic_impl_->acl_connections_.find(handle);
- if (connection_pair != classic_impl_->acl_connections_.end()) {
- connection_pair->second.assembler_.on_incoming_packet(*packet);
+ auto connection_pair = acl_connections_.find(handle);
+ if (connection_pair == acl_connections_.end()) {
+ LOG_INFO("Dropping packet of size %zu to unknown connection 0x%0hx", packet->size(), handle);
+ return;
+ }
+
+ connection_pair->second.on_incoming_packet(*packet);
+ }
+
+ void on_incoming_connection(EventPacketView packet) {
+ ConnectionRequestView request = ConnectionRequestView::Create(packet);
+ ASSERT(request.IsValid());
+ Address address = request.GetBdAddr();
+ if (client_callbacks_ == nullptr) {
+ LOG_ERROR("No callbacks to call");
+ auto reason = RejectConnectionReason::LIMITED_RESOURCES;
+ this->reject_connection(RejectConnectionRequestBuilder::Create(address, reason));
+ return;
+ }
+ connecting_.insert(address);
+ if (is_classic_link_already_connected(address)) {
+ auto reason = RejectConnectionReason::UNACCEPTABLE_BD_ADDR;
+ this->reject_connection(RejectConnectionRequestBuilder::Create(address, reason));
+ } else if (should_accept_connection_.Run(address, request.GetClassOfDevice())) {
+ this->accept_connection(address);
+ } else {
+ auto reason = RejectConnectionReason::LIMITED_RESOURCES; // TODO: determine reason
+ this->reject_connection(RejectConnectionRequestBuilder::Create(address, reason));
+ }
+ }
+
+ void on_classic_connection_complete(Address address) {
+ auto connecting_addr = connecting_.find(address);
+ if (connecting_addr == connecting_.end()) {
+ LOG_WARN("No prior connection request for %s", address.ToString().c_str());
+ } else {
+ connecting_.erase(connecting_addr);
+ }
+ }
+
+ void on_common_le_connection_complete(AddressWithType address_with_type) {
+ auto connecting_addr_with_type = connecting_le_.find(address_with_type);
+ if (connecting_addr_with_type == connecting_le_.end()) {
+ LOG_WARN("No prior connection request for %s", address_with_type.ToString().c_str());
+ } else {
+ connecting_le_.erase(connecting_addr_with_type);
+ }
+ }
+
+ void on_le_connection_complete(LeMetaEventView packet) {
+ LeConnectionCompleteView connection_complete = LeConnectionCompleteView::Create(packet);
+ ASSERT(connection_complete.IsValid());
+ auto status = connection_complete.GetStatus();
+ auto address = connection_complete.GetPeerAddress();
+ auto peer_address_type = connection_complete.GetPeerAddressType();
+ // TODO: find out which address and type was used to initiate the connection
+ AddressWithType address_with_type(address, peer_address_type);
+ on_common_le_connection_complete(address_with_type);
+ if (status != ErrorCode::SUCCESS) {
+ le_client_handler_->Post(common::BindOnce(&LeConnectionCallbacks::OnLeConnectFail,
+ common::Unretained(le_client_callbacks_), address_with_type, status));
+ return;
+ }
+ // TODO: Check and save other connection parameters
+ uint16_t handle = connection_complete.GetConnectionHandle();
+ ASSERT(acl_connections_.count(handle) == 0);
+ acl_connections_.emplace(std::piecewise_construct, std::forward_as_tuple(handle),
+ std::forward_as_tuple(address_with_type, handler_));
+ if (acl_connections_.size() == 1 && fragments_to_send_.size() == 0) {
+ start_round_robin();
+ }
+ auto role = connection_complete.GetRole();
+ std::unique_ptr<AclConnection> connection_proxy(
+ new AclConnection(&acl_manager_, handle, address, peer_address_type, role));
+ le_client_handler_->Post(common::BindOnce(&LeConnectionCallbacks::OnLeConnectSuccess,
+ common::Unretained(le_client_callbacks_), address_with_type,
+ std::move(connection_proxy)));
+ }
+
+ void on_le_enhanced_connection_complete(LeMetaEventView packet) {
+ LeEnhancedConnectionCompleteView connection_complete = LeEnhancedConnectionCompleteView::Create(packet);
+ ASSERT(connection_complete.IsValid());
+ auto status = connection_complete.GetStatus();
+ auto address = connection_complete.GetPeerAddress();
+ auto peer_address_type = connection_complete.GetPeerAddressType();
+ auto peer_resolvable_address = connection_complete.GetPeerResolvablePrivateAddress();
+ AddressWithType reporting_address_with_type(address, peer_address_type);
+ if (!peer_resolvable_address.IsEmpty()) {
+ reporting_address_with_type = AddressWithType(peer_resolvable_address, AddressType::RANDOM_DEVICE_ADDRESS);
+ }
+ on_common_le_connection_complete(reporting_address_with_type);
+ if (status != ErrorCode::SUCCESS) {
+ le_client_handler_->Post(common::BindOnce(&LeConnectionCallbacks::OnLeConnectFail,
+ common::Unretained(le_client_callbacks_), reporting_address_with_type,
+ status));
+ return;
+ }
+ // TODO: Check and save other connection parameters
+ uint16_t handle = connection_complete.GetConnectionHandle();
+ ASSERT(acl_connections_.count(handle) == 0);
+ acl_connections_.emplace(std::piecewise_construct, std::forward_as_tuple(handle),
+ std::forward_as_tuple(reporting_address_with_type, handler_));
+ if (acl_connections_.size() == 1 && fragments_to_send_.size() == 0) {
+ start_round_robin();
+ }
+ auto role = connection_complete.GetRole();
+ std::unique_ptr<AclConnection> connection_proxy(
+ new AclConnection(&acl_manager_, handle, address, peer_address_type, role));
+ le_client_handler_->Post(common::BindOnce(&LeConnectionCallbacks::OnLeConnectSuccess,
+ common::Unretained(le_client_callbacks_), reporting_address_with_type,
+ std::move(connection_proxy)));
+ }
+
+ void on_connection_complete(EventPacketView packet) {
+ ConnectionCompleteView connection_complete = ConnectionCompleteView::Create(packet);
+ ASSERT(connection_complete.IsValid());
+ auto status = connection_complete.GetStatus();
+ auto address = connection_complete.GetBdAddr();
+ on_classic_connection_complete(address);
+ if (status != ErrorCode::SUCCESS) {
+ client_handler_->Post(common::BindOnce(&ConnectionCallbacks::OnConnectFail, common::Unretained(client_callbacks_),
+ address, status));
+ return;
+ }
+ uint16_t handle = connection_complete.GetConnectionHandle();
+ ASSERT(acl_connections_.count(handle) == 0);
+ acl_connections_.emplace(
+ std::piecewise_construct, std::forward_as_tuple(handle),
+ std::forward_as_tuple(AddressWithType{address, AddressType::PUBLIC_DEVICE_ADDRESS}, handler_));
+ if (acl_connections_.size() == 1 && fragments_to_send_.size() == 0) {
+ start_round_robin();
+ }
+ std::unique_ptr<AclConnection> connection_proxy(new AclConnection(&acl_manager_, handle, address));
+ client_handler_->Post(common::BindOnce(&ConnectionCallbacks::OnConnectSuccess,
+ common::Unretained(client_callbacks_), std::move(connection_proxy)));
+ while (!pending_outgoing_connections_.empty()) {
+ auto create_connection_packet_and_address = std::move(pending_outgoing_connections_.front());
+ pending_outgoing_connections_.pop();
+ if (!is_classic_link_already_connected(create_connection_packet_and_address.first)) {
+ connecting_.insert(create_connection_packet_and_address.first);
+ hci_layer_->EnqueueCommand(std::move(create_connection_packet_and_address.second),
+ common::BindOnce([](CommandStatusView status) {
+ ASSERT(status.IsValid());
+ ASSERT(status.GetCommandOpCode() == OpCode::CREATE_CONNECTION);
+ }),
+ handler_);
+ break;
+ }
+ }
+ }
+
+ void on_disconnection_complete(EventPacketView packet) {
+ DisconnectionCompleteView disconnection_complete = DisconnectionCompleteView::Create(packet);
+ ASSERT(disconnection_complete.IsValid());
+ uint16_t handle = disconnection_complete.GetConnectionHandle();
+ auto status = disconnection_complete.GetStatus();
+ if (status == ErrorCode::SUCCESS) {
+ ASSERT(acl_connections_.count(handle) == 1);
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ acl_connection.is_disconnected_ = true;
+ acl_connection.disconnect_reason_ = disconnection_complete.GetReason();
+ acl_connection.call_disconnect_callback();
+ // Reclaim outstanding packets
+ acl_packet_credits_ += acl_connection.number_of_sent_packets_;
+ acl_connection.number_of_sent_packets_ = 0;
} else {
- auto le_connection_pair = le_impl_->le_acl_connections_.find(handle);
- if (le_connection_pair == le_impl_->le_acl_connections_.end()) {
- LOG_INFO("Dropping packet of size %zu to unknown connection 0x%0hx", packet->size(), handle);
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received disconnection complete with error code %s, handle 0x%02hx", error_code.c_str(), handle);
+ }
+ }
+
+ void on_connection_packet_type_changed(EventPacketView packet) {
+ ConnectionPacketTypeChangedView packet_type_changed = ConnectionPacketTypeChangedView::Create(packet);
+ if (!packet_type_changed.IsValid()) {
+ LOG_ERROR("Received on_connection_packet_type_changed with invalid packet");
+ return;
+ } else if (packet_type_changed.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = packet_type_changed.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_connection_packet_type_changed with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = packet_type_changed.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ uint16_t packet_type = packet_type_changed.GetPacketType();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnConnectionPacketTypeChanged,
+ common::Unretained(acl_connection.command_complete_callbacks_), packet_type));
+ }
+ }
+
+ void on_master_link_key_complete(EventPacketView packet) {
+ MasterLinkKeyCompleteView complete_view = MasterLinkKeyCompleteView::Create(packet);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_master_link_key_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_master_link_key_complete with error code %s", error_code.c_str());
+ return;
+ }
+ if (acl_manager_client_callbacks_ != nullptr) {
+ uint16_t connection_handle = complete_view.GetConnectionHandle();
+ KeyFlag key_flag = complete_view.GetKeyFlag();
+ acl_manager_client_handler_->Post(common::BindOnce(&AclManagerCallbacks::OnMasterLinkKeyComplete,
+ common::Unretained(acl_manager_client_callbacks_),
+ connection_handle, key_flag));
+ }
+ }
+
+ void on_authentication_complete(EventPacketView packet) {
+ AuthenticationCompleteView authentication_complete = AuthenticationCompleteView::Create(packet);
+ if (!authentication_complete.IsValid()) {
+ LOG_ERROR("Received on_authentication_complete with invalid packet");
+ return;
+ } else if (authentication_complete.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = authentication_complete.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_authentication_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = authentication_complete.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnAuthenticationComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_)));
+ }
+ }
+
+ void on_encryption_change(EventPacketView packet) {
+ EncryptionChangeView encryption_change_view = EncryptionChangeView::Create(packet);
+ if (!encryption_change_view.IsValid()) {
+ LOG_ERROR("Received on_encryption_change with invalid packet");
+ return;
+ } else if (encryption_change_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = encryption_change_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_change_connection_link_key_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = encryption_change_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ EncryptionEnabled enabled = encryption_change_view.GetEncryptionEnabled();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnEncryptionChange,
+ common::Unretained(acl_connection.command_complete_callbacks_), enabled));
+ }
+ }
+
+ void on_change_connection_link_key_complete(EventPacketView packet) {
+ ChangeConnectionLinkKeyCompleteView complete_view = ChangeConnectionLinkKeyCompleteView::Create(packet);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_change_connection_link_key_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_change_connection_link_key_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnChangeConnectionLinkKeyComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_)));
+ }
+ }
+
+ void on_read_clock_offset_complete(EventPacketView packet) {
+ ReadClockOffsetCompleteView complete_view = ReadClockOffsetCompleteView::Create(packet);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_read_clock_offset_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_read_clock_offset_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ uint16_t clock_offset = complete_view.GetClockOffset();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnReadClockOffsetComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), clock_offset));
+ }
+ }
+
+ void on_mode_change(EventPacketView packet) {
+ ModeChangeView mode_change_view = ModeChangeView::Create(packet);
+ if (!mode_change_view.IsValid()) {
+ LOG_ERROR("Received on_mode_change with invalid packet");
+ return;
+ } else if (mode_change_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = mode_change_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_mode_change with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = mode_change_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ Mode current_mode = mode_change_view.GetCurrentMode();
+ uint16_t interval = mode_change_view.GetInterval();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnModeChange,
+ common::Unretained(acl_connection.command_complete_callbacks_), current_mode, interval));
+ }
+ }
+
+ void on_qos_setup_complete(EventPacketView packet) {
+ QosSetupCompleteView complete_view = QosSetupCompleteView::Create(packet);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_qos_setup_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_qos_setup_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ ServiceType service_type = complete_view.GetServiceType();
+ uint32_t token_rate = complete_view.GetTokenRate();
+ uint32_t peak_bandwidth = complete_view.GetPeakBandwidth();
+ uint32_t latency = complete_view.GetLatency();
+ uint32_t delay_variation = complete_view.GetDelayVariation();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnQosSetupComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), service_type, token_rate,
+ peak_bandwidth, latency, delay_variation));
+ }
+ }
+
+ void on_role_change(EventPacketView packet) {
+ RoleChangeView role_change_view = RoleChangeView::Create(packet);
+ if (!role_change_view.IsValid()) {
+ LOG_ERROR("Received on_role_change with invalid packet");
+ return;
+ } else if (role_change_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = role_change_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_role_change with error code %s", error_code.c_str());
+ return;
+ }
+ if (acl_manager_client_callbacks_ != nullptr) {
+ Address bd_addr = role_change_view.GetBdAddr();
+ Role new_role = role_change_view.GetNewRole();
+ acl_manager_client_handler_->Post(common::BindOnce(
+ &AclManagerCallbacks::OnRoleChange, common::Unretained(acl_manager_client_callbacks_), bd_addr, new_role));
+ }
+ }
+
+ void on_flow_specification_complete(EventPacketView packet) {
+ FlowSpecificationCompleteView complete_view = FlowSpecificationCompleteView::Create(packet);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_flow_specification_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_flow_specification_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ FlowDirection flow_direction = complete_view.GetFlowDirection();
+ ServiceType service_type = complete_view.GetServiceType();
+ uint32_t token_rate = complete_view.GetTokenRate();
+ uint32_t token_bucket_size = complete_view.GetTokenBucketSize();
+ uint32_t peak_bandwidth = complete_view.GetPeakBandwidth();
+ uint32_t access_latency = complete_view.GetAccessLatency();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnFlowSpecificationComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), flow_direction, service_type,
+ token_rate, token_bucket_size, peak_bandwidth, access_latency));
+ }
+ }
+
+ void on_flush_occurred(EventPacketView packet) {
+ FlushOccurredView flush_occurred_view = FlushOccurredView::Create(packet);
+ if (!flush_occurred_view.IsValid()) {
+ LOG_ERROR("Received on_flush_occurred with invalid packet");
+ return;
+ }
+ uint16_t handle = flush_occurred_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnFlushOccurred,
+ common::Unretained(acl_connection.command_complete_callbacks_)));
+ }
+ }
+
+ void on_read_remote_version_information_complete(EventPacketView packet) {
+ auto view = ReadRemoteVersionInformationCompleteView::Create(packet);
+ ASSERT_LOG(view.IsValid(), "Read remote version information packet invalid");
+ LOG_INFO("UNIMPLEMENTED called");
+ }
+
+ void on_read_remote_supported_features_complete(EventPacketView packet) {
+ auto view = ReadRemoteSupportedFeaturesCompleteView::Create(packet);
+ ASSERT_LOG(view.IsValid(), "Read remote supported features packet invalid");
+ LOG_INFO("UNIMPLEMENTED called");
+ }
+
+ void on_read_remote_extended_features_complete(EventPacketView packet) {
+ auto view = ReadRemoteExtendedFeaturesCompleteView::Create(packet);
+ ASSERT_LOG(view.IsValid(), "Read remote extended features packet invalid");
+ LOG_INFO("UNIMPLEMENTED called");
+ }
+
+ void on_link_supervision_timeout_changed(EventPacketView packet) {
+ auto view = LinkSupervisionTimeoutChangedView::Create(packet);
+ ASSERT_LOG(view.IsValid(), "Link supervision timeout changed packet invalid");
+ LOG_INFO("UNIMPLEMENTED called");
+ }
+
+ void on_role_discovery_complete(CommandCompleteView view) {
+ auto complete_view = RoleDiscoveryCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_role_discovery_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_role_discovery_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ Role role = complete_view.GetCurrentRole();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnRoleDiscoveryComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), role));
+ }
+ }
+
+ void on_read_link_policy_settings_complete(CommandCompleteView view) {
+ auto complete_view = ReadLinkPolicySettingsCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_read_link_policy_settings_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_read_link_policy_settings_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ uint16_t link_policy_settings = complete_view.GetLinkPolicySettings();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnReadLinkPolicySettingsComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), link_policy_settings));
+ }
+ }
+
+ void on_read_default_link_policy_settings_complete(CommandCompleteView view) {
+ auto complete_view = ReadDefaultLinkPolicySettingsCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_read_link_policy_settings_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_read_link_policy_settings_complete with error code %s", error_code.c_str());
+ return;
+ }
+ if (acl_manager_client_callbacks_ != nullptr) {
+ uint16_t default_link_policy_settings = complete_view.GetDefaultLinkPolicySettings();
+ acl_manager_client_handler_->Post(common::BindOnce(&AclManagerCallbacks::OnReadDefaultLinkPolicySettingsComplete,
+ common::Unretained(acl_manager_client_callbacks_),
+ default_link_policy_settings));
+ }
+ }
+
+ void on_read_automatic_flush_timeout_complete(CommandCompleteView view) {
+ auto complete_view = ReadAutomaticFlushTimeoutCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_read_automatic_flush_timeout_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_read_automatic_flush_timeout_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ uint16_t flush_timeout = complete_view.GetFlushTimeout();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnReadAutomaticFlushTimeoutComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), flush_timeout));
+ }
+ }
+
+ void on_read_transmit_power_level_complete(CommandCompleteView view) {
+ auto complete_view = ReadTransmitPowerLevelCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_read_transmit_power_level_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_read_transmit_power_level_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ uint8_t transmit_power_level = complete_view.GetTransmitPowerLevel();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnReadTransmitPowerLevelComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), transmit_power_level));
+ }
+ }
+
+ void on_read_link_supervision_timeout_complete(CommandCompleteView view) {
+ auto complete_view = ReadLinkSupervisionTimeoutCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_read_link_supervision_timeout_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_read_link_supervision_timeout_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ uint16_t link_supervision_timeout = complete_view.GetLinkSupervisionTimeout();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnReadLinkSupervisionTimeoutComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), link_supervision_timeout));
+ }
+ }
+
+ void on_read_failed_contact_counter_complete(CommandCompleteView view) {
+ auto complete_view = ReadFailedContactCounterCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_read_failed_contact_counter_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_read_failed_contact_counter_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ uint16_t failed_contact_counter = complete_view.GetFailedContactCounter();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnReadFailedContactCounterComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), failed_contact_counter));
+ }
+ }
+
+ void on_read_link_quality_complete(CommandCompleteView view) {
+ auto complete_view = ReadLinkQualityCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_read_link_quality_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_read_link_quality_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ uint8_t link_quality = complete_view.GetLinkQuality();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnReadLinkQualityComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), link_quality));
+ }
+ }
+
+ void on_read_afh_channel_map_complete(CommandCompleteView view) {
+ auto complete_view = ReadAfhChannelMapCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_read_afh_channel_map_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_read_afh_channel_map_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ AfhMode afh_mode = complete_view.GetAfhMode();
+ std::array<uint8_t, 10> afh_channel_map = complete_view.GetAfhChannelMap();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnReadAfhChannelMapComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), afh_mode, afh_channel_map));
+ }
+ }
+
+ void on_read_rssi_complete(CommandCompleteView view) {
+ auto complete_view = ReadRssiCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_read_rssi_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_read_rssi_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ uint8_t rssi = complete_view.GetRssi();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnReadRssiComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), rssi));
+ }
+ }
+
+ void on_read_remote_version_information_status(CommandStatusView view) {
+ ASSERT_LOG(view.IsValid(), "Bad status packet!");
+ LOG_INFO("UNIMPLEMENTED called: %s", hci::ErrorCodeText(view.GetStatus()).c_str());
+ }
+
+ void on_read_remote_supported_features_status(CommandStatusView view) {
+ ASSERT_LOG(view.IsValid(), "Bad status packet!");
+ LOG_INFO("UNIMPLEMENTED called: %s", hci::ErrorCodeText(view.GetStatus()).c_str());
+ }
+
+ void on_read_remote_extended_features_status(CommandStatusView view) {
+ ASSERT_LOG(view.IsValid(), "Broken");
+ LOG_INFO("UNIMPLEMENTED called: %s", hci::ErrorCodeText(view.GetStatus()).c_str());
+ }
+
+ void on_read_clock_complete(CommandCompleteView view) {
+ auto complete_view = ReadClockCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_read_clock_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_read_clock_complete with error code %s", error_code.c_str());
+ return;
+ }
+ uint16_t handle = complete_view.GetConnectionHandle();
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.command_complete_handler_ != nullptr) {
+ uint32_t clock = complete_view.GetClock();
+ uint16_t accuracy = complete_view.GetAccuracy();
+ acl_connection.command_complete_handler_->Post(
+ common::BindOnce(&ConnectionManagementCallbacks::OnReadClockComplete,
+ common::Unretained(acl_connection.command_complete_callbacks_), clock, accuracy));
+ }
+ }
+
+ void on_le_connection_update_complete(LeMetaEventView view) {
+ auto complete_view = LeConnectionUpdateCompleteView::Create(view);
+ if (!complete_view.IsValid()) {
+ LOG_ERROR("Received on_le_connection_update_complete with invalid packet");
+ return;
+ } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
+ auto status = complete_view.GetStatus();
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received on_le_connection_update_complete with error code %s", error_code.c_str());
+ return;
+ }
+ auto handle = complete_view.GetConnectionHandle();
+ if (acl_connections_.find(handle) == acl_connections_.end()) {
+ LOG_WARN("Can't find connection");
+ return;
+ }
+ auto& connection = acl_connections_.find(handle)->second;
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return;
+ }
+ if (!connection.on_connection_update_complete_callback_.is_null()) {
+ connection.on_connection_update_complete_callback_handler_->Post(
+ common::BindOnce(std::move(connection.on_connection_update_complete_callback_), complete_view.GetStatus()));
+ connection.on_connection_update_complete_callback_handler_ = nullptr;
+ }
+ }
+
+ bool is_classic_link_already_connected(Address address) {
+ for (const auto& connection : acl_connections_) {
+ if (connection.second.address_with_type_.GetAddress() == address) {
+ return true;
+ }
+ }
+ return false;
+ }
+
+ void create_connection(Address address) {
+ // TODO: Configure default connection parameters?
+ uint16_t packet_type = 0x4408 /* DM 1,3,5 */ | 0x8810 /*DH 1,3,5 */;
+ PageScanRepetitionMode page_scan_repetition_mode = PageScanRepetitionMode::R1;
+ uint16_t clock_offset = 0;
+ ClockOffsetValid clock_offset_valid = ClockOffsetValid::INVALID;
+ CreateConnectionRoleSwitch allow_role_switch = CreateConnectionRoleSwitch::ALLOW_ROLE_SWITCH;
+ ASSERT(client_callbacks_ != nullptr);
+ std::unique_ptr<CreateConnectionBuilder> packet = CreateConnectionBuilder::Create(
+ address, packet_type, page_scan_repetition_mode, clock_offset, clock_offset_valid, allow_role_switch);
+
+ if (connecting_.empty()) {
+ if (is_classic_link_already_connected(address)) {
+ LOG_WARN("already connected: %s", address.ToString().c_str());
return;
}
- le_connection_pair->second.assembler_.on_incoming_packet(*packet);
+ connecting_.insert(address);
+ hci_layer_->EnqueueCommand(std::move(packet), common::BindOnce([](CommandStatusView status) {
+ ASSERT(status.IsValid());
+ ASSERT(status.GetCommandOpCode() == OpCode::CREATE_CONNECTION);
+ }),
+ handler_);
+ } else {
+ pending_outgoing_connections_.emplace(address, std::move(packet));
}
}
- void Dump(
- std::promise<flatbuffers::Offset<AclManagerData>> promise, flatbuffers::FlatBufferBuilder* fb_builder) const;
+ void create_le_connection(AddressWithType address_with_type) {
+ // TODO: Add white list handling.
+ // TODO: Configure default LE connection parameters?
+ uint16_t le_scan_interval = 0x0060;
+ uint16_t le_scan_window = 0x0030;
+ InitiatorFilterPolicy initiator_filter_policy = InitiatorFilterPolicy::USE_PEER_ADDRESS;
+ OwnAddressType own_address_type = OwnAddressType::RANDOM_DEVICE_ADDRESS;
+ uint16_t conn_interval_min = 0x0018;
+ uint16_t conn_interval_max = 0x0028;
+ uint16_t conn_latency = 0x0000;
+ uint16_t supervision_timeout = 0x001f4;
+ ASSERT(le_client_callbacks_ != nullptr);
+
+ connecting_le_.insert(address_with_type);
+
+ // TODO: make features check nicer, like HCI_LE_EXTENDED_ADVERTISING_SUPPORTED
+ if (controller_->GetControllerLeLocalSupportedFeatures() & 0x0010) {
+ LeCreateConnPhyScanParameters tmp;
+ tmp.scan_interval_ = le_scan_interval;
+ tmp.scan_window_ = le_scan_window;
+ tmp.conn_interval_min_ = conn_interval_min;
+ tmp.conn_interval_max_ = conn_interval_max;
+ tmp.conn_latency_ = conn_latency;
+ tmp.supervision_timeout_ = supervision_timeout;
+ tmp.min_ce_length_ = 0x00;
+ tmp.max_ce_length_ = 0x00;
+
+ // With real controllers, we must set random address before using it to establish connection
+ // TODO: have separate state machine generate new address when needed, consider using auto-generation in
+ // controller
+ hci_layer_->EnqueueCommand(hci::LeSetRandomAddressBuilder::Create(Address{{0x00, 0x11, 0xFF, 0xFF, 0x33, 0x22}}),
+ common::BindOnce([](CommandCompleteView status) {}), handler_);
+
+ hci_layer_->EnqueueCommand(LeExtendedCreateConnectionBuilder::Create(
+ initiator_filter_policy, own_address_type, address_with_type.GetAddressType(),
+ address_with_type.GetAddress(), 0x01 /* 1M PHY ONLY */, {tmp}),
+ common::BindOnce([](CommandStatusView status) {
+ ASSERT(status.IsValid());
+ ASSERT(status.GetCommandOpCode() == OpCode::LE_EXTENDED_CREATE_CONNECTION);
+ }),
+ handler_);
+ } else {
+ hci_layer_->EnqueueCommand(
+ LeCreateConnectionBuilder::Create(le_scan_interval, le_scan_window, initiator_filter_policy,
+ address_with_type.GetAddressType(), address_with_type.GetAddress(),
+ own_address_type, conn_interval_min, conn_interval_max, conn_latency,
+ supervision_timeout, kMinimumCeLength, kMaximumCeLength),
+ common::BindOnce([](CommandStatusView status) {
+ ASSERT(status.IsValid());
+ ASSERT(status.GetCommandOpCode() == OpCode::LE_CREATE_CONNECTION);
+ }),
+ handler_);
+ }
+ }
+
+ void cancel_connect(Address address) {
+ auto connecting_addr = connecting_.find(address);
+ if (connecting_addr == connecting_.end()) {
+ LOG_INFO("Cannot cancel non-existent connection to %s", address.ToString().c_str());
+ return;
+ }
+ std::unique_ptr<CreateConnectionCancelBuilder> packet = CreateConnectionCancelBuilder::Create(address);
+ hci_layer_->EnqueueCommand(std::move(packet), common::BindOnce([](CommandCompleteView complete) { /* TODO */ }),
+ handler_);
+ }
+
+ void master_link_key(KeyFlag key_flag) {
+ std::unique_ptr<MasterLinkKeyBuilder> packet = MasterLinkKeyBuilder::Create(key_flag);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ common::BindOnce(&impl::check_command_status<MasterLinkKeyStatusView>, common::Unretained(this)), handler_);
+ }
+
+ void switch_role(Address address, Role role) {
+ std::unique_ptr<SwitchRoleBuilder> packet = SwitchRoleBuilder::Create(address, role);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ common::BindOnce(&impl::check_command_status<SwitchRoleStatusView>, common::Unretained(this)), handler_);
+ }
+
+ void read_default_link_policy_settings() {
+ std::unique_ptr<ReadDefaultLinkPolicySettingsBuilder> packet = ReadDefaultLinkPolicySettingsBuilder::Create();
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ common::BindOnce(&impl::on_read_default_link_policy_settings_complete, common::Unretained(this)), handler_);
+ }
+
+ void write_default_link_policy_settings(uint16_t default_link_policy_settings) {
+ std::unique_ptr<WriteDefaultLinkPolicySettingsBuilder> packet =
+ WriteDefaultLinkPolicySettingsBuilder::Create(default_link_policy_settings);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_complete<WriteDefaultLinkPolicySettingsCompleteView>,
+ common::Unretained(this)),
+ handler_);
+ }
+
+ void accept_connection(Address address) {
+ auto role = AcceptConnectionRequestRole::BECOME_MASTER; // We prefer to be master
+ hci_layer_->EnqueueCommand(AcceptConnectionRequestBuilder::Create(address, role),
+ common::BindOnce(&impl::on_accept_connection_status, common::Unretained(this), address),
+ handler_);
+ }
+
+ void handle_disconnect(uint16_t handle, DisconnectReason reason) {
+ ASSERT(acl_connections_.count(handle) == 1);
+ std::unique_ptr<DisconnectBuilder> packet = DisconnectBuilder::Create(handle, reason);
+ hci_layer_->EnqueueCommand(std::move(packet), BindOnce([](CommandStatusView status) { /* TODO: check? */ }),
+ handler_);
+ }
+
+ void handle_change_connection_packet_type(uint16_t handle, uint16_t packet_type) {
+ ASSERT(acl_connections_.count(handle) == 1);
+ std::unique_ptr<ChangeConnectionPacketTypeBuilder> packet =
+ ChangeConnectionPacketTypeBuilder::Create(handle, packet_type);
+ hci_layer_->EnqueueCommand(std::move(packet),
+ BindOnce(&AclManager::impl::check_command_status<ChangeConnectionPacketTypeStatusView>,
+ common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_authentication_requested(uint16_t handle) {
+ std::unique_ptr<AuthenticationRequestedBuilder> packet = AuthenticationRequestedBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_status<AuthenticationRequestedStatusView>, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_set_connection_encryption(uint16_t handle, Enable enable) {
+ std::unique_ptr<SetConnectionEncryptionBuilder> packet = SetConnectionEncryptionBuilder::Create(handle, enable);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_status<SetConnectionEncryptionStatusView>, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_change_connection_link_key(uint16_t handle) {
+ std::unique_ptr<ChangeConnectionLinkKeyBuilder> packet = ChangeConnectionLinkKeyBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_status<ChangeConnectionLinkKeyStatusView>, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_read_clock_offset(uint16_t handle) {
+ std::unique_ptr<ReadClockOffsetBuilder> packet = ReadClockOffsetBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_status<ReadClockOffsetStatusView>, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_hold_mode(uint16_t handle, uint16_t max_interval, uint16_t min_interval) {
+ std::unique_ptr<HoldModeBuilder> packet = HoldModeBuilder::Create(handle, max_interval, min_interval);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_status<HoldModeStatusView>, common::Unretained(this)), handler_);
+ }
+
+ void handle_sniff_mode(uint16_t handle, uint16_t max_interval, uint16_t min_interval, int16_t attempt,
+ uint16_t timeout) {
+ std::unique_ptr<SniffModeBuilder> packet =
+ SniffModeBuilder::Create(handle, max_interval, min_interval, attempt, timeout);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_status<SniffModeStatusView>, common::Unretained(this)), handler_);
+ }
+
+ void handle_exit_sniff_mode(uint16_t handle) {
+ std::unique_ptr<ExitSniffModeBuilder> packet = ExitSniffModeBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_status<ExitSniffModeStatusView>, common::Unretained(this)), handler_);
+ }
+
+ void handle_qos_setup_mode(uint16_t handle, ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth,
+ uint32_t latency, uint32_t delay_variation) {
+ std::unique_ptr<QosSetupBuilder> packet =
+ QosSetupBuilder::Create(handle, service_type, token_rate, peak_bandwidth, latency, delay_variation);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_status<QosSetupStatusView>, common::Unretained(this)), handler_);
+ }
+
+ void handle_role_discovery(uint16_t handle) {
+ std::unique_ptr<RoleDiscoveryBuilder> packet = RoleDiscoveryBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(std::move(packet),
+ common::BindOnce(&impl::on_role_discovery_complete, common::Unretained(this)), handler_);
+ }
+
+ void handle_read_link_policy_settings(uint16_t handle) {
+ std::unique_ptr<ReadLinkPolicySettingsBuilder> packet = ReadLinkPolicySettingsBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(std::move(packet),
+ common::BindOnce(&impl::on_read_link_policy_settings_complete, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_write_link_policy_settings(uint16_t handle, uint16_t link_policy_settings) {
+ std::unique_ptr<WriteLinkPolicySettingsBuilder> packet =
+ WriteLinkPolicySettingsBuilder::Create(handle, link_policy_settings);
+ hci_layer_->EnqueueCommand(std::move(packet),
+ BindOnce(&AclManager::impl::check_command_complete<WriteLinkPolicySettingsCompleteView>,
+ common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_flow_specification(uint16_t handle, FlowDirection flow_direction, ServiceType service_type,
+ uint32_t token_rate, uint32_t token_bucket_size, uint32_t peak_bandwidth,
+ uint32_t access_latency) {
+ std::unique_ptr<FlowSpecificationBuilder> packet = FlowSpecificationBuilder::Create(
+ handle, flow_direction, service_type, token_rate, token_bucket_size, peak_bandwidth, access_latency);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_status<FlowSpecificationStatusView>, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_sniff_subrating(uint16_t handle, uint16_t maximum_latency, uint16_t minimum_remote_timeout,
+ uint16_t minimum_local_timeout) {
+ std::unique_ptr<SniffSubratingBuilder> packet =
+ SniffSubratingBuilder::Create(handle, maximum_latency, minimum_remote_timeout, minimum_local_timeout);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_complete<SniffSubratingCompleteView>, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_flush(uint16_t handle) {
+ std::unique_ptr<FlushBuilder> packet = FlushBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_complete<FlushCompleteView>, common::Unretained(this)), handler_);
+ }
+
+ void handle_read_automatic_flush_timeout(uint16_t handle) {
+ std::unique_ptr<ReadAutomaticFlushTimeoutBuilder> packet = ReadAutomaticFlushTimeoutBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(
+ std::move(packet), common::BindOnce(&impl::on_read_automatic_flush_timeout_complete, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_write_automatic_flush_timeout(uint16_t handle, uint16_t flush_timeout) {
+ std::unique_ptr<WriteAutomaticFlushTimeoutBuilder> packet =
+ WriteAutomaticFlushTimeoutBuilder::Create(handle, flush_timeout);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_complete<WriteAutomaticFlushTimeoutCompleteView>,
+ common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_read_transmit_power_level(uint16_t handle, TransmitPowerLevelType type) {
+ std::unique_ptr<ReadTransmitPowerLevelBuilder> packet = ReadTransmitPowerLevelBuilder::Create(handle, type);
+ hci_layer_->EnqueueCommand(std::move(packet),
+ common::BindOnce(&impl::on_read_transmit_power_level_complete, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_read_link_supervision_timeout(uint16_t handle) {
+ std::unique_ptr<ReadLinkSupervisionTimeoutBuilder> packet = ReadLinkSupervisionTimeoutBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(
+ std::move(packet), common::BindOnce(&impl::on_read_link_supervision_timeout_complete, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_write_link_supervision_timeout(uint16_t handle, uint16_t link_supervision_timeout) {
+ std::unique_ptr<WriteLinkSupervisionTimeoutBuilder> packet =
+ WriteLinkSupervisionTimeoutBuilder::Create(handle, link_supervision_timeout);
+ hci_layer_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&AclManager::impl::check_command_complete<WriteLinkSupervisionTimeoutCompleteView>,
+ common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_read_failed_contact_counter(uint16_t handle) {
+ std::unique_ptr<ReadFailedContactCounterBuilder> packet = ReadFailedContactCounterBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(
+ std::move(packet), common::BindOnce(&impl::on_read_failed_contact_counter_complete, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_reset_failed_contact_counter(uint16_t handle) {
+ std::unique_ptr<ResetFailedContactCounterBuilder> packet = ResetFailedContactCounterBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(std::move(packet), BindOnce([](CommandCompleteView view) { /* TODO: check? */ }),
+ handler_);
+ }
+
+ void handle_read_link_quality(uint16_t handle) {
+ std::unique_ptr<ReadLinkQualityBuilder> packet = ReadLinkQualityBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(
+ std::move(packet), common::BindOnce(&impl::on_read_link_quality_complete, common::Unretained(this)), handler_);
+ }
+
+ void handle_afh_channel_map(uint16_t handle) {
+ std::unique_ptr<ReadAfhChannelMapBuilder> packet = ReadAfhChannelMapBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(std::move(packet),
+ common::BindOnce(&impl::on_read_afh_channel_map_complete, common::Unretained(this)),
+ handler_);
+ }
+
+ void handle_read_rssi(uint16_t handle) {
+ std::unique_ptr<ReadRssiBuilder> packet = ReadRssiBuilder::Create(handle);
+ hci_layer_->EnqueueCommand(std::move(packet),
+ common::BindOnce(&impl::on_read_rssi_complete, common::Unretained(this)), handler_);
+ }
+
+ void handle_read_remote_version_information(uint16_t handle) {
+ hci_layer_->EnqueueCommand(
+ ReadRemoteVersionInformationBuilder::Create(handle),
+ common::BindOnce(&impl::on_read_remote_version_information_status, common::Unretained(this)), handler_);
+ }
+
+ void handle_read_remote_supported_features(uint16_t handle) {
+ hci_layer_->EnqueueCommand(
+ ReadRemoteSupportedFeaturesBuilder::Create(handle),
+ common::BindOnce(&impl::on_read_remote_supported_features_status, common::Unretained(this)), handler_);
+ }
+
+ void handle_read_remote_extended_features(uint16_t handle) {
+ // TODO(optedoblivion): Read the other pages until max pages
+ hci_layer_->EnqueueCommand(
+ ReadRemoteExtendedFeaturesBuilder::Create(handle, 1),
+ common::BindOnce(&impl::on_read_remote_extended_features_status, common::Unretained(this)), handler_);
+ }
+
+ void handle_read_clock(uint16_t handle, WhichClock which_clock) {
+ std::unique_ptr<ReadClockBuilder> packet = ReadClockBuilder::Create(handle, which_clock);
+ hci_layer_->EnqueueCommand(std::move(packet),
+ common::BindOnce(&impl::on_read_clock_complete, common::Unretained(this)), handler_);
+ }
+
+ void handle_le_connection_update(uint16_t handle, uint16_t conn_interval_min, uint16_t conn_interval_max,
+ uint16_t conn_latency, uint16_t supervision_timeout) {
+ auto packet = LeConnectionUpdateBuilder::Create(handle, conn_interval_min, conn_interval_max, conn_latency,
+ supervision_timeout, kMinimumCeLength, kMaximumCeLength);
+ hci_layer_->EnqueueCommand(std::move(packet), common::BindOnce([](CommandStatusView status) {
+ ASSERT(status.IsValid());
+ ASSERT(status.GetCommandOpCode() == OpCode::LE_CREATE_CONNECTION);
+ }),
+ handler_);
+ }
+
+ template <class T>
+ void check_command_complete(CommandCompleteView view) {
+ ASSERT(view.IsValid());
+ auto status_view = T::Create(view);
+ if (!status_view.IsValid()) {
+ LOG_ERROR("Received command complete with invalid packet, opcode 0x%02hx", view.GetCommandOpCode());
+ return;
+ }
+ ErrorCode status = status_view.GetStatus();
+ OpCode op_code = status_view.GetCommandOpCode();
+ if (status != ErrorCode::SUCCESS) {
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received command complete with error code %s, opcode 0x%02hx", error_code.c_str(), op_code);
+ return;
+ }
+ }
+
+ template <class T>
+ void check_command_status(CommandStatusView view) {
+ ASSERT(view.IsValid());
+ auto status_view = T::Create(view);
+ if (!status_view.IsValid()) {
+ LOG_ERROR("Received command status with invalid packet, opcode 0x%02hx", view.GetCommandOpCode());
+ return;
+ }
+ ErrorCode status = status_view.GetStatus();
+ OpCode op_code = status_view.GetCommandOpCode();
+ if (status != ErrorCode::SUCCESS) {
+ std::string error_code = ErrorCodeText(status);
+ LOG_ERROR("Received command status with error code %s, opcode 0x%02hx", error_code.c_str(), op_code);
+ return;
+ }
+ }
+
+ void cleanup(uint16_t handle) {
+ ASSERT(acl_connections_.count(handle) == 1);
+ auto& acl_connection = acl_connections_.find(handle)->second;
+ if (acl_connection.is_registered_) {
+ acl_connection.is_registered_ = false;
+ acl_connection.queue_->GetDownEnd()->UnregisterDequeue();
+ }
+ acl_connections_.erase(handle);
+ }
+
+ void on_accept_connection_status(Address address, CommandStatusView status) {
+ auto accept_status = AcceptConnectionRequestStatusView::Create(status);
+ ASSERT(accept_status.IsValid());
+ if (status.GetStatus() != ErrorCode::SUCCESS) {
+ cancel_connect(address);
+ }
+ }
+
+ void reject_connection(std::unique_ptr<RejectConnectionRequestBuilder> builder) {
+ hci_layer_->EnqueueCommand(std::move(builder), BindOnce([](CommandStatusView status) { /* TODO: check? */ }),
+ handler_);
+ }
+
+ void handle_register_callbacks(ConnectionCallbacks* callbacks, os::Handler* handler) {
+ ASSERT(client_callbacks_ == nullptr);
+ ASSERT(client_handler_ == nullptr);
+ client_callbacks_ = callbacks;
+ client_handler_ = handler;
+ }
+
+ void handle_register_le_callbacks(LeConnectionCallbacks* callbacks, os::Handler* handler) {
+ ASSERT(le_client_callbacks_ == nullptr);
+ ASSERT(le_client_handler_ == nullptr);
+ le_client_callbacks_ = callbacks;
+ le_client_handler_ = handler;
+ }
+
+ void handle_register_acl_manager_callbacks(AclManagerCallbacks* callbacks, os::Handler* handler) {
+ ASSERT(acl_manager_client_callbacks_ == nullptr);
+ ASSERT(acl_manager_client_handler_ == nullptr);
+ acl_manager_client_callbacks_ = callbacks;
+ acl_manager_client_handler_ = handler;
+ }
+
+ void handle_register_le_acl_manager_callbacks(AclManagerCallbacks* callbacks, os::Handler* handler) {
+ ASSERT(le_acl_manager_client_callbacks_ == nullptr);
+ ASSERT(le_acl_manager_client_handler_ == nullptr);
+ le_acl_manager_client_callbacks_ = callbacks;
+ le_acl_manager_client_handler_ = handler;
+ }
+
+ acl_connection& check_and_get_connection(uint16_t handle) {
+ auto connection = acl_connections_.find(handle);
+ ASSERT(connection != acl_connections_.end());
+ return connection->second;
+ }
+
+ AclConnection::QueueUpEnd* get_acl_queue_end(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ return connection.queue_->GetUpEnd();
+ }
+
+ void RegisterCallbacks(uint16_t handle, ConnectionManagementCallbacks* callbacks, os::Handler* handler) {
+ auto& connection = check_and_get_connection(handle);
+ ASSERT(connection.command_complete_callbacks_ == nullptr);
+ connection.command_complete_callbacks_ = callbacks;
+ connection.command_complete_handler_ = handler;
+ }
+
+ void UnregisterCallbacks(uint16_t handle, ConnectionManagementCallbacks* callbacks) {
+ auto& connection = check_and_get_connection(handle);
+ ASSERT(connection.command_complete_callbacks_ == callbacks);
+ connection.command_complete_callbacks_ = nullptr;
+ }
+
+ void RegisterDisconnectCallback(uint16_t handle, common::OnceCallback<void(ErrorCode)> on_disconnect,
+ os::Handler* handler) {
+ auto& connection = check_and_get_connection(handle);
+ connection.on_disconnect_callback_ = std::move(on_disconnect);
+ connection.disconnect_handler_ = handler;
+ if (connection.is_disconnected_) {
+ connection.call_disconnect_callback();
+ }
+ }
+
+ bool Disconnect(uint16_t handle, DisconnectReason reason) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_disconnect, common::Unretained(this), handle, reason));
+ return true;
+ }
+
+ bool ChangeConnectionPacketType(uint16_t handle, uint16_t packet_type) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(
+ BindOnce(&impl::handle_change_connection_packet_type, common::Unretained(this), handle, packet_type));
+ return true;
+ }
+
+ bool AuthenticationRequested(uint16_t handle) {
+ LOG_INFO("Auth reqiuest");
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_authentication_requested, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool SetConnectionEncryption(uint16_t handle, Enable enable) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_set_connection_encryption, common::Unretained(this), handle, enable));
+ return true;
+ }
+
+ bool ChangeConnectionLinkKey(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_change_connection_link_key, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool ReadClockOffset(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_clock_offset, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool HoldMode(uint16_t handle, uint16_t max_interval, uint16_t min_interval) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_hold_mode, common::Unretained(this), handle, max_interval, min_interval));
+ return true;
+ }
+
+ bool SniffMode(uint16_t handle, uint16_t max_interval, uint16_t min_interval, int16_t attempt, uint16_t timeout) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_sniff_mode, common::Unretained(this), handle, max_interval, min_interval,
+ attempt, timeout));
+ return true;
+ }
+
+ bool ExitSniffMode(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_exit_sniff_mode, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool QosSetup(uint16_t handle, ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth,
+ uint32_t latency, uint32_t delay_variation) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_qos_setup_mode, common::Unretained(this), handle, service_type, token_rate,
+ peak_bandwidth, latency, delay_variation));
+ return true;
+ }
+
+ bool RoleDiscovery(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_role_discovery, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool ReadLinkPolicySettings(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_link_policy_settings, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool WriteLinkPolicySettings(uint16_t handle, uint16_t link_policy_settings) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(
+ BindOnce(&impl::handle_write_link_policy_settings, common::Unretained(this), handle, link_policy_settings));
+ return true;
+ }
+
+ bool FlowSpecification(uint16_t handle, FlowDirection flow_direction, ServiceType service_type, uint32_t token_rate,
+ uint32_t token_bucket_size, uint32_t peak_bandwidth, uint32_t access_latency) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_flow_specification, common::Unretained(this), handle, flow_direction,
+ service_type, token_rate, token_bucket_size, peak_bandwidth, access_latency));
+ return true;
+ }
+
+ bool SniffSubrating(uint16_t handle, uint16_t maximum_latency, uint16_t minimum_remote_timeout,
+ uint16_t minimum_local_timeout) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_sniff_subrating, common::Unretained(this), handle, maximum_latency,
+ minimum_remote_timeout, minimum_local_timeout));
+ return true;
+ }
+
+ bool Flush(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_flush, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool ReadAutomaticFlushTimeout(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_automatic_flush_timeout, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool WriteAutomaticFlushTimeout(uint16_t handle, uint16_t flush_timeout) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(
+ BindOnce(&impl::handle_write_automatic_flush_timeout, common::Unretained(this), handle, flush_timeout));
+ return true;
+ }
+
+ bool ReadTransmitPowerLevel(uint16_t handle, TransmitPowerLevelType type) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_transmit_power_level, common::Unretained(this), handle, type));
+ return true;
+ }
+
+ bool ReadLinkSupervisionTimeout(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_link_supervision_timeout, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool WriteLinkSupervisionTimeout(uint16_t handle, uint16_t link_supervision_timeout) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_write_link_supervision_timeout, common::Unretained(this), handle,
+ link_supervision_timeout));
+ return true;
+ }
+
+ bool ReadFailedContactCounter(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_failed_contact_counter, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool ResetFailedContactCounter(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_reset_failed_contact_counter, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool ReadLinkQuality(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_link_quality, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool ReadAfhChannelMap(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_afh_channel_map, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool ReadRssi(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_rssi, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool ReadRemoteVersionInformation(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_remote_version_information, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool ReadRemoteSupportedFeatures(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_remote_supported_features, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool ReadRemoteExtendedFeatures(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_remote_extended_features, common::Unretained(this), handle));
+ return true;
+ }
+
+ bool ReadClock(uint16_t handle, WhichClock which_clock) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_read_clock, common::Unretained(this), handle, which_clock));
+ return true;
+ }
+
+ bool LeConnectionUpdate(uint16_t handle, uint16_t conn_interval_min, uint16_t conn_interval_max,
+ uint16_t conn_latency, uint16_t supervision_timeout,
+ common::OnceCallback<void(ErrorCode)> done_callback, os::Handler* handler) {
+ auto& connection = check_and_get_connection(handle);
+ if (connection.is_disconnected_) {
+ LOG_INFO("Already disconnected");
+ return false;
+ }
+ if (!connection.on_connection_update_complete_callback_.is_null()) {
+ LOG_INFO("There is another pending connection update");
+ return false;
+ }
+ connection.on_connection_update_complete_callback_ = std::move(done_callback);
+ connection.on_connection_update_complete_callback_handler_ = handler;
+ if (conn_interval_min < 0x0006 || conn_interval_min > 0x0C80 || conn_interval_max < 0x0006 ||
+ conn_interval_max > 0x0C80 || conn_latency > 0x01F3 || supervision_timeout < 0x000A ||
+ supervision_timeout > 0x0C80) {
+ LOG_ERROR("Invalid parameter");
+ return false;
+ }
+ handler_->Post(BindOnce(&impl::handle_le_connection_update, common::Unretained(this), handle, conn_interval_min,
+ conn_interval_max, conn_latency, supervision_timeout));
+ return true;
+ }
+
+ void Finish(uint16_t handle) {
+ auto& connection = check_and_get_connection(handle);
+ ASSERT_LOG(connection.is_disconnected_, "Finish must be invoked after disconnection (handle 0x%04hx)", handle);
+ handler_->Post(BindOnce(&impl::cleanup, common::Unretained(this), handle));
+ }
const AclManager& acl_manager_;
- classic_impl* classic_impl_ = nullptr;
- le_impl* le_impl_ = nullptr;
- os::Handler* handler_ = nullptr;
+ static constexpr uint16_t kMinimumCeLength = 0x0002;
+ static constexpr uint16_t kMaximumCeLength = 0x0C00;
+
Controller* controller_ = nullptr;
+ uint16_t max_acl_packet_credits_ = 0;
+ uint16_t acl_packet_credits_ = 0;
+ uint16_t acl_buffer_length_ = 0;
+
+ std::list<std::unique_ptr<AclPacketBuilder>> fragments_to_send_;
+ std::map<uint16_t, acl_connection>::iterator current_connection_pair_;
+
HciLayer* hci_layer_ = nullptr;
- RoundRobinScheduler* round_robin_scheduler_ = nullptr;
- common::BidiQueueEnd<AclBuilder, AclView>* hci_queue_end_ = nullptr;
- std::atomic_bool enqueue_registered_ = false;
- uint16_t default_link_policy_settings_ = 0xffff;
+ os::Handler* handler_ = nullptr;
+ ConnectionCallbacks* client_callbacks_ = nullptr;
+ os::Handler* client_handler_ = nullptr;
+ LeConnectionCallbacks* le_client_callbacks_ = nullptr;
+ os::Handler* le_client_handler_ = nullptr;
+ AclManagerCallbacks* acl_manager_client_callbacks_ = nullptr;
+ os::Handler* acl_manager_client_handler_ = nullptr;
+ AclManagerCallbacks* le_acl_manager_client_callbacks_ = nullptr;
+ os::Handler* le_acl_manager_client_handler_ = nullptr;
+ common::BidiQueueEnd<AclPacketBuilder, AclPacketView>* hci_queue_end_ = nullptr;
+ std::map<uint16_t, AclManager::acl_connection> acl_connections_;
+ std::set<Address> connecting_;
+ std::set<AddressWithType> connecting_le_;
+ common::Callback<bool(Address, ClassOfDevice)> should_accept_connection_;
+ std::queue<std::pair<Address, std::unique_ptr<CreateConnectionBuilder>>> pending_outgoing_connections_;
+ size_t hci_mtu_{0};
};
-AclManager::AclManager() : pimpl_(std::make_unique<impl>(*this)) {}
+AclConnection::QueueUpEnd* AclConnection::GetAclQueueEnd() const {
+ return manager_->pimpl_->get_acl_queue_end(handle_);
+}
-void AclManager::RegisterCallbacks(ConnectionCallbacks* callbacks, os::Handler* handler) {
- ASSERT(callbacks != nullptr && handler != nullptr);
- GetHandler()->Post(common::BindOnce(&classic_impl::handle_register_callbacks,
- common::Unretained(pimpl_->classic_impl_), common::Unretained(callbacks),
- common::Unretained(handler)));
+void AclConnection::RegisterCallbacks(ConnectionManagementCallbacks* callbacks, os::Handler* handler) {
+ return manager_->pimpl_->RegisterCallbacks(handle_, callbacks, handler);
}
-void AclManager::UnregisterCallbacks(ConnectionCallbacks* callbacks, std::promise<void> promise) {
- ASSERT(callbacks != nullptr);
- CallOn(
- pimpl_->classic_impl_,
- &classic_impl::handle_unregister_callbacks,
- common::Unretained(callbacks),
- std::move(promise));
+void AclConnection::UnregisterCallbacks(ConnectionManagementCallbacks* callbacks) {
+ return manager_->pimpl_->UnregisterCallbacks(handle_, callbacks);
}
-void AclManager::RegisterLeCallbacks(LeConnectionCallbacks* callbacks, os::Handler* handler) {
- ASSERT(callbacks != nullptr && handler != nullptr);
- CallOn(
- pimpl_->le_impl_,
- &le_impl::handle_register_le_callbacks,
- common::Unretained(callbacks),
- common::Unretained(handler));
+void AclConnection::RegisterDisconnectCallback(common::OnceCallback<void(ErrorCode)> on_disconnect,
+ os::Handler* handler) {
+ return manager_->pimpl_->RegisterDisconnectCallback(handle_, std::move(on_disconnect), handler);
}
-void AclManager::UnregisterLeCallbacks(LeConnectionCallbacks* callbacks, std::promise<void> promise) {
- ASSERT(callbacks != nullptr);
- CallOn(pimpl_->le_impl_, &le_impl::handle_unregister_le_callbacks, common::Unretained(callbacks), std::move(promise));
+bool AclConnection::Disconnect(DisconnectReason reason) {
+ return manager_->pimpl_->Disconnect(handle_, reason);
}
-void AclManager::CreateConnection(Address address) {
- CallOn(pimpl_->classic_impl_, &classic_impl::create_connection, address);
-}
-
-void AclManager::CreateLeConnection(AddressWithType address_with_type, bool is_direct) {
- CallOn(pimpl_->le_impl_, &le_impl::create_le_connection, address_with_type, true, is_direct);
-}
-
-void AclManager::SetLeSuggestedDefaultDataParameters(uint16_t octets, uint16_t time) {
- CallOn(pimpl_->le_impl_, &le_impl::set_le_suggested_default_data_parameters, octets, time);
-}
-
-void AclManager::SetPrivacyPolicyForInitiatorAddress(
- LeAddressManager::AddressPolicy address_policy,
- AddressWithType fixed_address,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time) {
- crypto_toolbox::Octet16 rotation_irk{};
- auto irk = GetDependency<storage::StorageModule>()->GetAdapterConfig().GetLeIdentityResolvingKey();
- if (irk.has_value()) {
- rotation_irk = irk->bytes;
- }
- CallOn(
- pimpl_->le_impl_,
- &le_impl::set_privacy_policy_for_initiator_address,
- address_policy,
- fixed_address,
- rotation_irk,
- minimum_rotation_time,
- maximum_rotation_time);
-}
-
-// TODO(jpawlowski): remove once we have config file abstraction in cert tests
-void AclManager::SetPrivacyPolicyForInitiatorAddressForTest(
- LeAddressManager::AddressPolicy address_policy,
- AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time) {
- CallOn(
- pimpl_->le_impl_,
- &le_impl::set_privacy_policy_for_initiator_address_for_test,
- address_policy,
- fixed_address,
- rotation_irk,
- minimum_rotation_time,
- maximum_rotation_time);
+bool AclConnection::ChangeConnectionPacketType(uint16_t packet_type) {
+ return manager_->pimpl_->ChangeConnectionPacketType(handle_, packet_type);
}
-void AclManager::CancelConnect(Address address) {
- CallOn(pimpl_->classic_impl_, &classic_impl::cancel_connect, address);
+bool AclConnection::AuthenticationRequested() {
+ return manager_->pimpl_->AuthenticationRequested(handle_);
}
-void AclManager::CancelLeConnect(AddressWithType address_with_type) {
- CallOn(pimpl_->le_impl_, &le_impl::cancel_connect, address_with_type);
+bool AclConnection::SetConnectionEncryption(Enable enable) {
+ return manager_->pimpl_->SetConnectionEncryption(handle_, enable);
}
-void AclManager::AddDeviceToConnectList(AddressWithType address_with_type) {
- CallOn(pimpl_->le_impl_, &le_impl::add_device_to_connect_list, address_with_type);
+bool AclConnection::ChangeConnectionLinkKey() {
+ return manager_->pimpl_->ChangeConnectionLinkKey(handle_);
}
-void AclManager::AddDeviceToResolvingList(
- AddressWithType address_with_type,
- const std::array<uint8_t, 16>& peer_irk,
- const std::array<uint8_t, 16>& local_irk) {
- CallOn(pimpl_->le_impl_, &le_impl::add_device_to_resolving_list, address_with_type, peer_irk, local_irk);
+bool AclConnection::ReadClockOffset() {
+ return manager_->pimpl_->ReadClockOffset(handle_);
}
-void AclManager::RemoveDeviceFromConnectList(AddressWithType address_with_type) {
- CallOn(pimpl_->le_impl_, &le_impl::remove_device_from_connect_list, address_with_type);
+bool AclConnection::HoldMode(uint16_t max_interval, uint16_t min_interval) {
+ return manager_->pimpl_->HoldMode(handle_, max_interval, min_interval);
}
-void AclManager::RemoveDeviceFromResolvingList(AddressWithType address_with_type) {
- CallOn(pimpl_->le_impl_, &le_impl::remove_device_from_resolving_list, address_with_type);
+bool AclConnection::SniffMode(uint16_t max_interval, uint16_t min_interval, uint16_t attempt, uint16_t timeout) {
+ return manager_->pimpl_->SniffMode(handle_, max_interval, min_interval, attempt, timeout);
}
-void AclManager::CentralLinkKey(KeyFlag key_flag) {
- CallOn(pimpl_->classic_impl_, &classic_impl::central_link_key, key_flag);
+bool AclConnection::ExitSniffMode() {
+ return manager_->pimpl_->ExitSniffMode(handle_);
}
-void AclManager::SwitchRole(Address address, Role role) {
- CallOn(pimpl_->classic_impl_, &classic_impl::switch_role, address, role);
+bool AclConnection::QosSetup(ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth, uint32_t latency,
+ uint32_t delay_variation) {
+ return manager_->pimpl_->QosSetup(handle_, service_type, token_rate, peak_bandwidth, latency, delay_variation);
}
-uint16_t AclManager::ReadDefaultLinkPolicySettings() {
- ASSERT_LOG(pimpl_->default_link_policy_settings_ != 0xffff, "Settings were never written");
- return pimpl_->default_link_policy_settings_;
+bool AclConnection::RoleDiscovery() {
+ return manager_->pimpl_->RoleDiscovery(handle_);
}
-void AclManager::WriteDefaultLinkPolicySettings(uint16_t default_link_policy_settings) {
- pimpl_->default_link_policy_settings_ = default_link_policy_settings;
- CallOn(pimpl_->classic_impl_, &classic_impl::write_default_link_policy_settings, default_link_policy_settings);
+bool AclConnection::ReadLinkPolicySettings() {
+ return manager_->pimpl_->ReadLinkPolicySettings(handle_);
}
-void AclManager::OnAdvertisingSetTerminated(ErrorCode status, uint16_t conn_handle, hci::AddressWithType adv_address) {
- if (status == ErrorCode::SUCCESS) {
- CallOn(pimpl_->le_impl_, &le_impl::UpdateLocalAddress, conn_handle, adv_address);
- }
+bool AclConnection::WriteLinkPolicySettings(uint16_t link_policy_settings) {
+ return manager_->pimpl_->WriteLinkPolicySettings(handle_, link_policy_settings);
+}
+
+bool AclConnection::FlowSpecification(FlowDirection flow_direction, ServiceType service_type, uint32_t token_rate,
+ uint32_t token_bucket_size, uint32_t peak_bandwidth, uint32_t access_latency) {
+ return manager_->pimpl_->FlowSpecification(handle_, flow_direction, service_type, token_rate, token_bucket_size,
+ peak_bandwidth, access_latency);
+}
+
+bool AclConnection::SniffSubrating(uint16_t maximum_latency, uint16_t minimum_remote_timeout,
+ uint16_t minimum_local_timeout) {
+ return manager_->pimpl_->SniffSubrating(handle_, maximum_latency, minimum_remote_timeout, minimum_local_timeout);
+}
+
+bool AclConnection::Flush() {
+ return manager_->pimpl_->Flush(handle_);
+}
+
+bool AclConnection::ReadAutomaticFlushTimeout() {
+ return manager_->pimpl_->ReadAutomaticFlushTimeout(handle_);
+}
+
+bool AclConnection::WriteAutomaticFlushTimeout(uint16_t flush_timeout) {
+ return manager_->pimpl_->WriteAutomaticFlushTimeout(handle_, flush_timeout);
+}
+
+bool AclConnection::ReadTransmitPowerLevel(TransmitPowerLevelType type) {
+ return manager_->pimpl_->ReadTransmitPowerLevel(handle_, type);
+}
+
+bool AclConnection::ReadLinkSupervisionTimeout() {
+ return manager_->pimpl_->ReadLinkSupervisionTimeout(handle_);
}
-void AclManager::SetSecurityModule(security::SecurityModule* security_module) {
- CallOn(pimpl_->classic_impl_, &classic_impl::set_security_module, security_module);
+bool AclConnection::WriteLinkSupervisionTimeout(uint16_t link_supervision_timeout) {
+ return manager_->pimpl_->WriteLinkSupervisionTimeout(handle_, link_supervision_timeout);
}
-LeAddressManager* AclManager::GetLeAddressManager() {
- return pimpl_->le_impl_->le_address_manager_;
+bool AclConnection::ReadFailedContactCounter() {
+ return manager_->pimpl_->ReadFailedContactCounter(handle_);
}
-uint16_t AclManager::HACK_GetHandle(Address address) {
- return pimpl_->classic_impl_->HACK_get_handle(address);
+bool AclConnection::ResetFailedContactCounter() {
+ return manager_->pimpl_->ResetFailedContactCounter(handle_);
}
-uint16_t AclManager::HACK_GetLeHandle(Address address) {
- return pimpl_->le_impl_->HACK_get_handle(address);
+bool AclConnection::ReadLinkQuality() {
+ return manager_->pimpl_->ReadLinkQuality(handle_);
}
-void AclManager::HACK_SetScoDisconnectCallback(std::function<void(uint16_t, uint8_t)> callback) {
- pimpl_->classic_impl_->HACK_SetScoDisconnectCallback(callback);
+bool AclConnection::ReadAfhChannelMap() {
+ return manager_->pimpl_->ReadAfhChannelMap(handle_);
}
-void AclManager::HACK_SetAclTxPriority(uint8_t handle, bool high_priority) {
- CallOn(pimpl_->round_robin_scheduler_, &RoundRobinScheduler::SetLinkPriority, handle, high_priority);
+bool AclConnection::ReadRssi() {
+ return manager_->pimpl_->ReadRssi(handle_);
+}
+
+bool AclConnection::ReadRemoteVersionInformation() {
+ return manager_->pimpl_->ReadRemoteVersionInformation(handle_);
+}
+
+bool AclConnection::ReadRemoteSupportedFeatures() {
+ return manager_->pimpl_->ReadRemoteSupportedFeatures(handle_);
+}
+
+bool AclConnection::ReadRemoteExtendedFeatures() {
+ return manager_->pimpl_->ReadRemoteExtendedFeatures(handle_);
+}
+
+bool AclConnection::ReadClock(WhichClock which_clock) {
+ return manager_->pimpl_->ReadClock(handle_, which_clock);
+}
+
+bool AclConnection::LeConnectionUpdate(uint16_t conn_interval_min, uint16_t conn_interval_max, uint16_t conn_latency,
+ uint16_t supervision_timeout,
+ common::OnceCallback<void(ErrorCode)> done_callback, os::Handler* handler) {
+ return manager_->pimpl_->LeConnectionUpdate(handle_, conn_interval_min, conn_interval_max, conn_latency,
+ supervision_timeout, std::move(done_callback), handler);
+}
+
+void AclConnection::Finish() {
+ return manager_->pimpl_->Finish(handle_);
+}
+
+AclManager::AclManager() : pimpl_(std::make_unique<impl>(*this)) {}
+
+void AclManager::RegisterCallbacks(ConnectionCallbacks* callbacks, os::Handler* handler) {
+ ASSERT(callbacks != nullptr && handler != nullptr);
+ GetHandler()->Post(common::BindOnce(&impl::handle_register_callbacks, common::Unretained(pimpl_.get()),
+ common::Unretained(callbacks), common::Unretained(handler)));
+}
+
+void AclManager::RegisterLeCallbacks(LeConnectionCallbacks* callbacks, os::Handler* handler) {
+ ASSERT(callbacks != nullptr && handler != nullptr);
+ GetHandler()->Post(common::BindOnce(&impl::handle_register_le_callbacks, common::Unretained(pimpl_.get()),
+ common::Unretained(callbacks), common::Unretained(handler)));
+}
+
+void AclManager::RegisterAclManagerCallbacks(AclManagerCallbacks* callbacks, os::Handler* handler) {
+ ASSERT(callbacks != nullptr && handler != nullptr);
+ GetHandler()->Post(common::BindOnce(&impl::handle_register_acl_manager_callbacks, common::Unretained(pimpl_.get()),
+ common::Unretained(callbacks), common::Unretained(handler)));
+}
+
+void AclManager::RegisterLeAclManagerCallbacks(AclManagerCallbacks* callbacks, os::Handler* handler) {
+ ASSERT(callbacks != nullptr && handler != nullptr);
+ GetHandler()->Post(common::BindOnce(&impl::handle_register_le_acl_manager_callbacks, common::Unretained(pimpl_.get()),
+ common::Unretained(callbacks), common::Unretained(handler)));
+}
+
+void AclManager::CreateConnection(Address address) {
+ GetHandler()->Post(common::BindOnce(&impl::create_connection, common::Unretained(pimpl_.get()), address));
+}
+
+void AclManager::CreateLeConnection(AddressWithType address_with_type) {
+ GetHandler()->Post(
+ common::BindOnce(&impl::create_le_connection, common::Unretained(pimpl_.get()), address_with_type));
+}
+
+void AclManager::CancelConnect(Address address) {
+ GetHandler()->Post(BindOnce(&impl::cancel_connect, common::Unretained(pimpl_.get()), address));
+}
+
+void AclManager::MasterLinkKey(KeyFlag key_flag) {
+ GetHandler()->Post(BindOnce(&impl::master_link_key, common::Unretained(pimpl_.get()), key_flag));
+}
+
+void AclManager::SwitchRole(Address address, Role role) {
+ GetHandler()->Post(BindOnce(&impl::switch_role, common::Unretained(pimpl_.get()), address, role));
+}
+
+void AclManager::ReadDefaultLinkPolicySettings() {
+ GetHandler()->Post(BindOnce(&impl::read_default_link_policy_settings, common::Unretained(pimpl_.get())));
+}
+
+void AclManager::WriteDefaultLinkPolicySettings(uint16_t default_link_policy_settings) {
+ GetHandler()->Post(BindOnce(&impl::write_default_link_policy_settings, common::Unretained(pimpl_.get()),
+ default_link_policy_settings));
}
void AclManager::ListDependencies(ModuleList* list) {
list->add<HciLayer>();
list->add<Controller>();
- list->add<storage::StorageModule>();
}
void AclManager::Start() {
@@ -301,28 +2144,5 @@ const ModuleFactory AclManager::Factory = ModuleFactory([]() { return new AclMan
AclManager::~AclManager() = default;
-void AclManager::impl::Dump(
- std::promise<flatbuffers::Offset<AclManagerData>> promise, flatbuffers::FlatBufferBuilder* fb_builder) const {
- auto title = fb_builder->CreateString("----- Acl Manager Dumpsys -----");
- AclManagerDataBuilder builder(*fb_builder);
- builder.add_title(title);
- flatbuffers::Offset<AclManagerData> dumpsys_data = builder.Finish();
- promise.set_value(dumpsys_data);
-}
-
-DumpsysDataFinisher AclManager::GetDumpsysData(flatbuffers::FlatBufferBuilder* fb_builder) const {
- ASSERT(fb_builder != nullptr);
-
- std::promise<flatbuffers::Offset<AclManagerData>> promise;
- auto future = promise.get_future();
- pimpl_->Dump(std::move(promise), fb_builder);
-
- auto dumpsys_data = future.get();
-
- return [dumpsys_data](DumpsysDataBuilder* dumpsys_builder) {
- dumpsys_builder->add_hci_acl_manager_dumpsys_data(dumpsys_data);
- };
-}
-
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/acl_manager.h b/gd/hci/acl_manager.h
index 48dac9512..9d2483594 100644
--- a/gd/hci/acl_manager.h
+++ b/gd/hci/acl_manager.h
@@ -16,137 +16,248 @@
#pragma once
-#include <functional>
-#include <future>
#include <memory>
#include "common/bidi_queue.h"
#include "common/callback.h"
-#include "hci/acl_manager/connection_callbacks.h"
-#include "hci/acl_manager/le_connection_callbacks.h"
#include "hci/address.h"
#include "hci/address_with_type.h"
#include "hci/hci_layer.h"
#include "hci/hci_packets.h"
-#include "hci/le_address_manager.h"
#include "module.h"
#include "os/handler.h"
namespace bluetooth {
-
-namespace security {
-class SecurityModule;
-}
-namespace shim {
-namespace legacy {
-class Acl;
-}
-
-class Btm;
-void L2CA_UseLegacySecurityModule();
-bool L2CA_SetAclPriority(uint16_t, bool);
-}
-
namespace hci {
-class AclManager : public Module {
- friend class bluetooth::shim::Btm;
- friend class bluetooth::shim::legacy::Acl;
- friend void bluetooth::shim::L2CA_UseLegacySecurityModule();
- friend bool bluetooth::shim::L2CA_SetAclPriority(uint16_t, bool);
-
-public:
- AclManager();
- // NOTE: It is necessary to forward declare a default destructor that overrides the base class one, because
- // "struct impl" is forwarded declared in .cc and compiler needs a concrete definition of "struct impl" when
- // compiling AclManager's destructor. Hence we need to forward declare the destructor for AclManager to delay
- // compiling AclManager's destructor until it starts linking the .cc file.
- ~AclManager();
-
- // Should register only once when user module starts.
- // Generates OnConnectSuccess when an incoming connection is established.
- virtual void RegisterCallbacks(acl_manager::ConnectionCallbacks* callbacks, os::Handler* handler);
- virtual void UnregisterCallbacks(acl_manager::ConnectionCallbacks* callbacks, std::promise<void> promise);
-
- // Should register only once when user module starts.
- virtual void RegisterLeCallbacks(acl_manager::LeConnectionCallbacks* callbacks, os::Handler* handler);
- virtual void UnregisterLeCallbacks(acl_manager::LeConnectionCallbacks* callbacks, std::promise<void> promise);
-
- // Generates OnConnectSuccess if connected, or OnConnectFail otherwise
- virtual void CreateConnection(Address address);
+class AclManager;
+
+class ConnectionManagementCallbacks {
+ public:
+ virtual ~ConnectionManagementCallbacks() = default;
+ // Invoked when controller sends Connection Packet Type Changed event with Success error code
+ virtual void OnConnectionPacketTypeChanged(uint16_t packet_type) = 0;
+ // Invoked when controller sends Authentication Complete event with Success error code
+ virtual void OnAuthenticationComplete() = 0;
+ // Invoked when controller sends Encryption Change event with Success error code
+ virtual void OnEncryptionChange(EncryptionEnabled enabled) = 0;
+ // Invoked when controller sends Change Connection Link Key Complete event with Success error code
+ virtual void OnChangeConnectionLinkKeyComplete() = 0;
+ // Invoked when controller sends Read Clock Offset Complete event with Success error code
+ virtual void OnReadClockOffsetComplete(uint16_t clock_offset) = 0;
+ // Invoked when controller sends Mode Change event with Success error code
+ virtual void OnModeChange(Mode current_mode, uint16_t interval) = 0;
+ // Invoked when controller sends QoS Setup Complete event with Success error code
+ virtual void OnQosSetupComplete(ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth,
+ uint32_t latency, uint32_t delay_variation) = 0;
+ // Invoked when controller sends Flow Specification Complete event with Success error code
+ virtual void OnFlowSpecificationComplete(FlowDirection flow_direction, ServiceType service_type, uint32_t token_rate,
+ uint32_t token_bucket_size, uint32_t peak_bandwidth,
+ uint32_t access_latency) = 0;
+ // Invoked when controller sends Flush Occurred event
+ virtual void OnFlushOccurred() = 0;
+ // Invoked when controller sends Command Complete event for Role Discovery command with Success error code
+ virtual void OnRoleDiscoveryComplete(Role current_role) = 0;
+ // Invoked when controller sends Command Complete event for Read Link Policy Settings command with Success error code
+ virtual void OnReadLinkPolicySettingsComplete(uint16_t link_policy_settings) = 0;
+ // Invoked when controller sends Command Complete event for Read Automatic Flush Timeout command with Success error
+ // code
+ virtual void OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout) = 0;
+ // Invoked when controller sends Command Complete event for Read Transmit Power Level command with Success error code
+ virtual void OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level) = 0;
+ // Invoked when controller sends Command Complete event for Read Link Supervision Time out command with Success error
+ // code
+ virtual void OnReadLinkSupervisionTimeoutComplete(uint16_t link_supervision_timeout) = 0;
+ // Invoked when controller sends Command Complete event for Read Failed Contact Counter command with Success error
+ // code
+ virtual void OnReadFailedContactCounterComplete(uint16_t failed_contact_counter) = 0;
+ // Invoked when controller sends Command Complete event for Read Link Quality command with Success error code
+ virtual void OnReadLinkQualityComplete(uint8_t link_quality) = 0;
+ // Invoked when controller sends Command Complete event for Read AFH Channel Map command with Success error code
+ virtual void OnReadAfhChannelMapComplete(AfhMode afh_mode, std::array<uint8_t, 10> afh_channel_map) = 0;
+ // Invoked when controller sends Command Complete event for Read RSSI command with Success error code
+ virtual void OnReadRssiComplete(uint8_t rssi) = 0;
+ // Invoked when controller sends Command Complete event for Read Clock command with Success error code
+ virtual void OnReadClockComplete(uint32_t clock, uint16_t accuracy) = 0;
+};
- // Generates OnLeConnectSuccess if connected, or OnLeConnectFail otherwise
- virtual void CreateLeConnection(AddressWithType address_with_type, bool is_direct);
+class AclConnection {
+ public:
+ AclConnection()
+ : manager_(nullptr), handle_(0), address_(Address::kEmpty), address_type_(AddressType::PUBLIC_DEVICE_ADDRESS){};
+ virtual ~AclConnection() = default;
+
+ virtual Address GetAddress() const {
+ return address_;
+ }
+
+ virtual AddressType GetAddressType() const {
+ return address_type_;
+ }
+
+ uint16_t GetHandle() const {
+ return handle_;
+ }
+
+ /* This return role for LE devices only, for Classic, please see |RoleDiscovery| method.
+ * TODO: split AclConnection for LE and Classic
+ */
+ Role GetRole() const {
+ return role_;
+ }
+
+ using Queue = common::BidiQueue<PacketView<kLittleEndian>, BasePacketBuilder>;
+ using QueueUpEnd = common::BidiQueueEnd<BasePacketBuilder, PacketView<kLittleEndian>>;
+ using QueueDownEnd = common::BidiQueueEnd<PacketView<kLittleEndian>, BasePacketBuilder>;
+ virtual QueueUpEnd* GetAclQueueEnd() const;
+ virtual void RegisterCallbacks(ConnectionManagementCallbacks* callbacks, os::Handler* handler);
+ virtual void UnregisterCallbacks(ConnectionManagementCallbacks* callbacks);
+ virtual void RegisterDisconnectCallback(common::OnceCallback<void(ErrorCode)> on_disconnect, os::Handler* handler);
+ virtual bool Disconnect(DisconnectReason reason);
+ virtual bool ChangeConnectionPacketType(uint16_t packet_type);
+ virtual bool AuthenticationRequested();
+ virtual bool SetConnectionEncryption(Enable enable);
+ virtual bool ChangeConnectionLinkKey();
+ virtual bool ReadClockOffset();
+ virtual bool HoldMode(uint16_t max_interval, uint16_t min_interval);
+ virtual bool SniffMode(uint16_t max_interval, uint16_t min_interval, uint16_t attempt, uint16_t timeout);
+ virtual bool ExitSniffMode();
+ virtual bool QosSetup(ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth, uint32_t latency,
+ uint32_t delay_variation);
+ virtual bool RoleDiscovery();
+ virtual bool ReadLinkPolicySettings();
+ virtual bool WriteLinkPolicySettings(uint16_t link_policy_settings);
+ virtual bool FlowSpecification(FlowDirection flow_direction, ServiceType service_type, uint32_t token_rate,
+ uint32_t token_bucket_size, uint32_t peak_bandwidth, uint32_t access_latency);
+ virtual bool SniffSubrating(uint16_t maximum_latency, uint16_t minimum_remote_timeout,
+ uint16_t minimum_local_timeout);
+ virtual bool Flush();
+ virtual bool ReadAutomaticFlushTimeout();
+ virtual bool WriteAutomaticFlushTimeout(uint16_t flush_timeout);
+ virtual bool ReadTransmitPowerLevel(TransmitPowerLevelType type);
+ virtual bool ReadLinkSupervisionTimeout();
+ virtual bool WriteLinkSupervisionTimeout(uint16_t link_supervision_timeout);
+ virtual bool ReadFailedContactCounter();
+ virtual bool ResetFailedContactCounter();
+ virtual bool ReadLinkQuality();
+ virtual bool ReadAfhChannelMap();
+ virtual bool ReadRssi();
+ virtual bool ReadClock(WhichClock which_clock);
+ virtual bool ReadRemoteVersionInformation();
+ virtual bool ReadRemoteSupportedFeatures();
+ virtual bool ReadRemoteExtendedFeatures();
+
+ // LE ACL Method
+ virtual bool LeConnectionUpdate(uint16_t conn_interval_min, uint16_t conn_interval_max, uint16_t conn_latency,
+ uint16_t supervision_timeout, common::OnceCallback<void(ErrorCode)> done_callback,
+ os::Handler* handler);
+
+ // Ask AclManager to clean me up. Must invoke after on_disconnect is called
+ virtual void Finish();
+
+ // TODO: API to change link settings ... ?
+
+ private:
+ friend AclManager;
+ AclConnection(const AclManager* manager, uint16_t handle, Address address)
+ : manager_(manager), handle_(handle), address_(address), address_type_(AddressType::PUBLIC_DEVICE_ADDRESS) {}
+ AclConnection(const AclManager* manager, uint16_t handle, Address address, AddressType address_type, Role role)
+ : manager_(manager), handle_(handle), address_(address), address_type_(address_type), role_(role) {}
+ const AclManager* manager_;
+ uint16_t handle_;
+ Address address_;
+ AddressType address_type_;
+ Role role_;
+ DISALLOW_COPY_AND_ASSIGN(AclConnection);
+};
- // Ask the controller for specific data parameters
- virtual void SetLeSuggestedDefaultDataParameters(uint16_t octets, uint16_t time);
+class ConnectionCallbacks {
+ public:
+ virtual ~ConnectionCallbacks() = default;
+ // Invoked when controller sends Connection Complete event with Success error code
+ virtual void OnConnectSuccess(std::unique_ptr<AclConnection> /* , initiated_by_local ? */) = 0;
+ // Invoked when controller sends Connection Complete event with non-Success error code
+ virtual void OnConnectFail(Address, ErrorCode reason) = 0;
+};
- virtual void SetPrivacyPolicyForInitiatorAddress(
- LeAddressManager::AddressPolicy address_policy,
- AddressWithType fixed_address,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time);
+class LeConnectionCallbacks {
+ public:
+ virtual ~LeConnectionCallbacks() = default;
+ // Invoked when controller sends Connection Complete event with Success error code
+ // AddressWithType is always equal to the object used in AclManager#CreateLeConnection
+ virtual void OnLeConnectSuccess(AddressWithType, std::unique_ptr<AclConnection> /* , initiated_by_local ? */) = 0;
+ // Invoked when controller sends Connection Complete event with non-Success error code
+ virtual void OnLeConnectFail(AddressWithType, ErrorCode reason) = 0;
+};
- // TODO(jpawlowski): remove once we have config file abstraction in cert tests
- virtual void SetPrivacyPolicyForInitiatorAddressForTest(
- LeAddressManager::AddressPolicy address_policy,
- AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time);
+class AclManagerCallbacks {
+ public:
+ virtual ~AclManagerCallbacks() = default;
+ // Invoked when controller sends Master Link Key Complete event with Success error code
+ virtual void OnMasterLinkKeyComplete(uint16_t connection_handle, KeyFlag key_flag) = 0;
+ // Invoked when controller sends Role Change event with Success error code
+ virtual void OnRoleChange(Address bd_addr, Role new_role) = 0;
+ // Invoked when controller sends Command Complete event for Read Default Link Policy Settings command with Success
+ // error code
+ virtual void OnReadDefaultLinkPolicySettingsComplete(uint16_t default_link_policy_settings) = 0;
+};
- // Generates OnConnectFail with error code "terminated by local host 0x16" if cancelled, or OnConnectSuccess if not
- // successfully cancelled and already connected
- virtual void CancelConnect(Address address);
+class AclManager : public Module {
+ public:
+ AclManager();
+ // NOTE: It is necessary to forward declare a default destructor that overrides the base class one, because
+ // "struct impl" is forwarded declared in .cc and compiler needs a concrete definition of "struct impl" when
+ // compiling AclManager's destructor. Hence we need to forward declare the destructor for AclManager to delay
+ // compiling AclManager's destructor until it starts linking the .cc file.
+ ~AclManager() override;
- virtual void CancelLeConnect(AddressWithType address_with_type);
- virtual void AddDeviceToConnectList(AddressWithType address_with_type);
- virtual void AddDeviceToResolvingList(
- AddressWithType address_with_type,
- const std::array<uint8_t, 16>& peer_irk,
- const std::array<uint8_t, 16>& local_irk);
- virtual void RemoveDeviceFromConnectList(AddressWithType address_with_type);
- virtual void RemoveDeviceFromResolvingList(AddressWithType address_with_type);
+ // Should register only once when user module starts.
+ // Generates OnConnectSuccess when an incoming connection is established.
+ virtual void RegisterCallbacks(ConnectionCallbacks* callbacks, os::Handler* handler);
- virtual void CentralLinkKey(KeyFlag key_flag);
- virtual void SwitchRole(Address address, Role role);
- virtual uint16_t ReadDefaultLinkPolicySettings();
- virtual void WriteDefaultLinkPolicySettings(uint16_t default_link_policy_settings);
+ // Should register only once when user module starts.
+ virtual void RegisterLeCallbacks(LeConnectionCallbacks* callbacks, os::Handler* handler);
- // Callback from Advertising Manager to notify the advitiser (local) address
- virtual void OnAdvertisingSetTerminated(ErrorCode status, uint16_t conn_handle, hci::AddressWithType adv_address);
+ // Should register only once when user module starts.
+ virtual void RegisterAclManagerCallbacks(AclManagerCallbacks* callbacks, os::Handler* handler);
- // In order to avoid circular dependency use setter rather than module dependency.
- virtual void SetSecurityModule(security::SecurityModule* security_module);
+ // Should register only once when user module starts.
+ virtual void RegisterLeAclManagerCallbacks(AclManagerCallbacks* callbacks, os::Handler* handler);
- virtual LeAddressManager* GetLeAddressManager();
+ // Generates OnConnectSuccess if connected, or OnConnectFail otherwise
+ virtual void CreateConnection(Address address);
- static const ModuleFactory Factory;
+ // Generates OnLeConnectSuccess if connected, or OnLeConnectFail otherwise
+ virtual void CreateLeConnection(AddressWithType address_with_type);
-protected:
- void ListDependencies(ModuleList* list) override;
+ // Generates OnConnectFail with error code "terminated by local host 0x16" if cancelled, or OnConnectSuccess if not
+ // successfully cancelled and already connected
+ virtual void CancelConnect(Address address);
- void Start() override;
+ virtual void MasterLinkKey(KeyFlag key_flag);
+ virtual void SwitchRole(Address address, Role role);
+ virtual void ReadDefaultLinkPolicySettings();
+ virtual void WriteDefaultLinkPolicySettings(uint16_t default_link_policy_settings);
- void Stop() override;
+ static const ModuleFactory Factory;
- std::string ToString() const override;
+ protected:
+ void ListDependencies(ModuleList* list) override;
- DumpsysDataFinisher GetDumpsysData(flatbuffers::FlatBufferBuilder* builder) const override; // Module
+ void Start() override;
-private:
- virtual uint16_t HACK_GetHandle(const Address address);
- virtual uint16_t HACK_GetLeHandle(const Address address);
+ void Stop() override;
- // Hack for the shim to get SCO disconnect callback. Shim needs to post to their handler!
- virtual void HACK_SetScoDisconnectCallback(std::function<void(uint16_t /* handle */, uint8_t /* reason */)>);
+ std::string ToString() const override;
- virtual void HACK_SetAclTxPriority(uint8_t handle, bool high_priority);
+ private:
+ friend AclConnection;
- struct impl;
- std::unique_ptr<impl> pimpl_;
+ struct impl;
+ std::unique_ptr<impl> pimpl_;
- DISALLOW_COPY_AND_ASSIGN(AclManager);
+ struct acl_connection;
+ DISALLOW_COPY_AND_ASSIGN(AclManager);
};
} // namespace hci
diff --git a/gd/hci/acl_manager/acl_connection.cc b/gd/hci/acl_manager/acl_connection.cc
deleted file mode 100644
index c678bf978..000000000
--- a/gd/hci/acl_manager/acl_connection.cc
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/acl_manager/acl_connection.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-AclConnection::QueueUpEnd* AclConnection::GetAclQueueEnd() const {
- return queue_up_end_;
-}
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/acl_connection.h b/gd/hci/acl_manager/acl_connection.h
deleted file mode 100644
index c396b1833..000000000
--- a/gd/hci/acl_manager/acl_connection.h
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <memory>
-
-#include "common/bidi_queue.h"
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-class AclConnection {
- public:
- AclConnection() : queue_up_end_(nullptr), handle_(0){};
- virtual ~AclConnection() = default;
-
- uint16_t GetHandle() const {
- return handle_;
- }
-
- virtual bool ReadRemoteVersionInformation() = 0;
-
- using Queue = common::BidiQueue<PacketView<kLittleEndian>, BasePacketBuilder>;
- using QueueUpEnd = common::BidiQueueEnd<BasePacketBuilder, PacketView<kLittleEndian>>;
- using QueueDownEnd = common::BidiQueueEnd<PacketView<kLittleEndian>, BasePacketBuilder>;
- virtual QueueUpEnd* GetAclQueueEnd() const;
-
- bool locally_initiated_{false};
-
- protected:
- AclConnection(QueueUpEnd* queue_up_end, uint16_t handle) : queue_up_end_(queue_up_end), handle_(handle) {}
- QueueUpEnd* queue_up_end_;
- uint16_t handle_;
- DISALLOW_COPY_AND_ASSIGN(AclConnection);
-};
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/assembler.h b/gd/hci/acl_manager/assembler.h
deleted file mode 100644
index b0bf26a33..000000000
--- a/gd/hci/acl_manager/assembler.h
+++ /dev/null
@@ -1,131 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-namespace {
-class PacketViewForRecombination : public packet::PacketView<kLittleEndian> {
- public:
- PacketViewForRecombination(const PacketView& packetView) : PacketView(packetView) {}
- void AppendPacketView(packet::PacketView<kLittleEndian> to_append) {
- Append(to_append);
- }
-};
-
-constexpr size_t kMaxQueuedPacketsPerConnection = 10;
-constexpr int kL2capBasicFrameHeaderSize = 4;
-
-// Per spec 5.1 Vol 2 Part B 5.3, ACL link shall carry L2CAP data. Therefore, an ACL packet shall contain L2CAP PDU.
-// This function returns the PDU size of the L2CAP data if it's a starting packet. Returns 0 if it's invalid.
-uint16_t GetL2capPduSize(AclView packet) {
- auto l2cap_payload = packet.GetPayload();
- if (l2cap_payload.size() < kL2capBasicFrameHeaderSize) {
- LOG_ERROR("Controller sent an invalid L2CAP starting packet!");
- return 0;
- }
- return (l2cap_payload.at(1) << 8u) + l2cap_payload.at(0);
-}
-
-} // namespace
-
-struct assembler {
- assembler(AddressWithType address_with_type, AclConnection::QueueDownEnd* down_end, os::Handler* handler)
- : address_with_type_(address_with_type), down_end_(down_end), handler_(handler) {}
- AddressWithType address_with_type_;
- AclConnection::QueueDownEnd* down_end_;
- os::Handler* handler_;
- PacketViewForRecombination recombination_stage_{PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>())};
- int remaining_sdu_continuation_packet_size_ = 0;
- std::shared_ptr<std::atomic_bool> enqueue_registered_ = std::make_shared<std::atomic_bool>(false);
- std::queue<packet::PacketView<kLittleEndian>> incoming_queue_;
-
- ~assembler() {
- if (enqueue_registered_->exchange(false)) {
- down_end_->UnregisterEnqueue();
- }
- }
-
- // Invoked from some external Queue Reactable context
- std::unique_ptr<packet::PacketView<kLittleEndian>> on_le_incoming_data_ready() {
- auto packet = incoming_queue_.front();
- incoming_queue_.pop();
- if (incoming_queue_.empty() && enqueue_registered_->exchange(false)) {
- down_end_->UnregisterEnqueue();
- }
- return std::make_unique<PacketView<kLittleEndian>>(packet);
- }
-
- void on_incoming_packet(AclView packet) {
- PacketView<kLittleEndian> payload = packet.GetPayload();
- auto payload_size = payload.size();
- auto broadcast_flag = packet.GetBroadcastFlag();
- if (broadcast_flag == BroadcastFlag::ACTIVE_PERIPHERAL_BROADCAST) {
- LOG_WARN("Dropping broadcast from remote");
- return;
- }
- auto packet_boundary_flag = packet.GetPacketBoundaryFlag();
- if (packet_boundary_flag == PacketBoundaryFlag::FIRST_NON_AUTOMATICALLY_FLUSHABLE) {
- LOG_ERROR("Controller is not allowed to send FIRST_NON_AUTOMATICALLY_FLUSHABLE to host except loopback mode");
- return;
- }
- if (packet_boundary_flag == PacketBoundaryFlag::CONTINUING_FRAGMENT) {
- if (remaining_sdu_continuation_packet_size_ < payload_size) {
- LOG_WARN("Remote sent unexpected L2CAP PDU. Drop the entire L2CAP PDU");
- recombination_stage_ =
- PacketViewForRecombination(PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>()));
- remaining_sdu_continuation_packet_size_ = 0;
- return;
- }
- remaining_sdu_continuation_packet_size_ -= payload_size;
- recombination_stage_.AppendPacketView(payload);
- if (remaining_sdu_continuation_packet_size_ != 0) {
- return;
- } else {
- payload = recombination_stage_;
- recombination_stage_ =
- PacketViewForRecombination(PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>()));
- }
- } else if (packet_boundary_flag == PacketBoundaryFlag::FIRST_AUTOMATICALLY_FLUSHABLE) {
- if (recombination_stage_.size() > 0) {
- LOG_ERROR("Controller sent a starting packet without finishing previous packet. Drop previous one.");
- }
- auto l2cap_pdu_size = GetL2capPduSize(packet);
- remaining_sdu_continuation_packet_size_ = l2cap_pdu_size - (payload_size - kL2capBasicFrameHeaderSize);
- if (remaining_sdu_continuation_packet_size_ > 0) {
- recombination_stage_ = payload;
- return;
- }
- }
- if (incoming_queue_.size() > kMaxQueuedPacketsPerConnection) {
- LOG_ERROR("Dropping packet from %s due to congestion", address_with_type_.ToString().c_str());
- return;
- }
-
- incoming_queue_.push(payload);
- if (!enqueue_registered_->exchange(true)) {
- down_end_->RegisterEnqueue(handler_,
- common::Bind(&assembler::on_le_incoming_data_ready, common::Unretained(this)));
- }
- }
-};
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/classic_acl_connection.cc b/gd/hci/acl_manager/classic_acl_connection.cc
deleted file mode 100644
index 26326e7dc..000000000
--- a/gd/hci/acl_manager/classic_acl_connection.cc
+++ /dev/null
@@ -1,590 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/acl_manager/classic_acl_connection.h"
-#include "hci/acl_manager/event_checkers.h"
-#include "hci/address.h"
-#include "os/metrics.h"
-
-using bluetooth::hci::Address;
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-class AclConnectionTracker : public ConnectionManagementCallbacks {
- public:
- AclConnectionTracker(
- AclConnectionInterface* acl_connection_interface, const Address& address, uint16_t connection_handle)
- : acl_connection_interface_(acl_connection_interface), address_(address), connection_handle_(connection_handle) {}
- ~AclConnectionTracker() {
- // If callbacks were registered, they should have been delivered.
- ASSERT(client_callbacks_ == nullptr || queued_callbacks_.empty());
- }
- void RegisterCallbacks(ConnectionManagementCallbacks* callbacks, os::Handler* handler) {
- client_handler_ = handler;
- client_callbacks_ = callbacks;
- while (!queued_callbacks_.empty()) {
- auto iter = queued_callbacks_.begin();
- handler->Post(std::move(*iter));
- queued_callbacks_.erase(iter);
- }
- }
-
-#define SAVE_OR_CALL(f, ...) \
- if (client_handler_ == nullptr) { \
- queued_callbacks_.emplace_back( \
- common::BindOnce(&ConnectionManagementCallbacks::f, common::Unretained(this), ##__VA_ARGS__)); \
- } else { \
- client_handler_->Post( \
- common::BindOnce(&ConnectionManagementCallbacks::f, common::Unretained(client_callbacks_), ##__VA_ARGS__)); \
- }
-
- void OnConnectionPacketTypeChanged(uint16_t packet_type) override {
- SAVE_OR_CALL(OnConnectionPacketTypeChanged, packet_type)
- }
- void OnAuthenticationComplete(hci::ErrorCode hci_status) override {
- SAVE_OR_CALL(OnAuthenticationComplete, hci_status)
- }
- void OnEncryptionChange(EncryptionEnabled enabled) override {
- SAVE_OR_CALL(OnEncryptionChange, enabled)
- }
- void OnChangeConnectionLinkKeyComplete() override {
- SAVE_OR_CALL(OnChangeConnectionLinkKeyComplete)
- }
- void OnReadClockOffsetComplete(uint16_t clock_offset) override {
- SAVE_OR_CALL(OnReadClockOffsetComplete, clock_offset)
- }
- void OnModeChange(ErrorCode status, Mode current_mode, uint16_t interval) override {
- SAVE_OR_CALL(OnModeChange, status, current_mode, interval)
- }
- void OnSniffSubrating(
- hci::ErrorCode hci_status,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) override {
- SAVE_OR_CALL(
- OnSniffSubrating,
- hci_status,
- maximum_transmit_latency,
- maximum_receive_latency,
- minimum_remote_timeout,
- minimum_local_timeout);
- }
- void OnQosSetupComplete(ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth, uint32_t latency,
- uint32_t delay_variation) override {
- SAVE_OR_CALL(OnQosSetupComplete, service_type, token_rate, peak_bandwidth, latency, delay_variation)
- }
- void OnFlowSpecificationComplete(FlowDirection flow_direction, ServiceType service_type, uint32_t token_rate,
- uint32_t token_bucket_size, uint32_t peak_bandwidth,
- uint32_t access_latency) override {
- SAVE_OR_CALL(OnFlowSpecificationComplete, flow_direction, service_type, token_rate, token_bucket_size,
- peak_bandwidth, access_latency)
- }
- void OnFlushOccurred() override {
- SAVE_OR_CALL(OnFlushOccurred)
- }
- void OnRoleDiscoveryComplete(Role current_role) override {
- SAVE_OR_CALL(OnRoleDiscoveryComplete, current_role)
- }
- void OnReadLinkPolicySettingsComplete(uint16_t link_policy_settings) override {
- SAVE_OR_CALL(OnReadLinkPolicySettingsComplete, link_policy_settings)
- }
- void OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout) override {
- SAVE_OR_CALL(OnReadAutomaticFlushTimeoutComplete, flush_timeout)
- }
- void OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level) override {
- bluetooth::os::LogMetricReadTxPowerLevelResult(
- address_, connection_handle_, static_cast<uint8_t>(ErrorCode::SUCCESS), transmit_power_level);
- SAVE_OR_CALL(OnReadTransmitPowerLevelComplete, transmit_power_level)
- }
- void OnReadLinkSupervisionTimeoutComplete(uint16_t link_supervision_timeout) override {
- SAVE_OR_CALL(OnReadLinkSupervisionTimeoutComplete, link_supervision_timeout)
- }
- void OnReadFailedContactCounterComplete(uint16_t failed_contact_counter) override {
- bluetooth::os::LogMetricReadFailedContactCounterResult(
- address_, connection_handle_, static_cast<uint8_t>(ErrorCode::SUCCESS), failed_contact_counter);
- SAVE_OR_CALL(OnReadFailedContactCounterComplete, failed_contact_counter);
- }
- void OnReadLinkQualityComplete(uint8_t link_quality) override {
- SAVE_OR_CALL(OnReadLinkQualityComplete, link_quality)
- }
- void OnReadAfhChannelMapComplete(AfhMode afh_mode, std::array<uint8_t, 10> afh_channel_map) override {
- SAVE_OR_CALL(OnReadAfhChannelMapComplete, afh_mode, afh_channel_map)
- }
- void OnReadRssiComplete(uint8_t rssi) override {
- bluetooth::os::LogMetricReadRssiResult(
- address_, connection_handle_, static_cast<uint8_t>(ErrorCode::SUCCESS), rssi);
- SAVE_OR_CALL(OnReadRssiComplete, rssi);
- }
- void OnReadClockComplete(uint32_t clock, uint16_t accuracy) override {
- SAVE_OR_CALL(OnReadClockComplete, clock, accuracy)
- }
- void OnCentralLinkKeyComplete(KeyFlag key_flag) override {
- SAVE_OR_CALL(OnCentralLinkKeyComplete, key_flag)
- }
- void OnRoleChange(hci::ErrorCode hci_status, Role new_role) override {
- SAVE_OR_CALL(OnRoleChange, hci_status, new_role)
- }
- void OnReadRemoteVersionInformationComplete(
- hci::ErrorCode hci_status, uint8_t lmp_version, uint16_t manufacturer_name, uint16_t sub_version) override {
- bluetooth::os::LogMetricRemoteVersionInfo(
- connection_handle_, static_cast<uint8_t>(hci_status), lmp_version, manufacturer_name, sub_version);
- SAVE_OR_CALL(OnReadRemoteVersionInformationComplete, hci_status, lmp_version, manufacturer_name, sub_version);
- }
- void OnReadRemoteSupportedFeaturesComplete(uint64_t features) override {
- SAVE_OR_CALL(OnReadRemoteSupportedFeaturesComplete, features);
- }
- void OnReadRemoteExtendedFeaturesComplete(uint8_t page_number, uint8_t max_page_number, uint64_t features) override {
- SAVE_OR_CALL(OnReadRemoteExtendedFeaturesComplete, page_number, max_page_number, features);
- }
- void OnDisconnection(ErrorCode reason) {
- SAVE_OR_CALL(OnDisconnection, reason);
- }
-
-#undef SAVE_OR_CALL
-
- void on_role_discovery_complete(CommandCompleteView view) {
- auto complete_view = RoleDiscoveryCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_role_discovery_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_role_discovery_complete with error code %s", error_code.c_str());
- return;
- }
- OnRoleDiscoveryComplete(complete_view.GetCurrentRole());
- }
-
- void on_read_link_policy_settings_complete(CommandCompleteView view) {
- auto complete_view = ReadLinkPolicySettingsCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_read_link_policy_settings_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_read_link_policy_settings_complete with error code %s", error_code.c_str());
- return;
- }
- OnReadLinkPolicySettingsComplete(complete_view.GetLinkPolicySettings());
- }
-
- void on_read_automatic_flush_timeout_complete(CommandCompleteView view) {
- auto complete_view = ReadAutomaticFlushTimeoutCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_read_automatic_flush_timeout_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_read_automatic_flush_timeout_complete with error code %s", error_code.c_str());
- return;
- }
- OnReadAutomaticFlushTimeoutComplete(complete_view.GetFlushTimeout());
- }
-
- void on_read_transmit_power_level_complete(CommandCompleteView view) {
- auto complete_view = ReadTransmitPowerLevelCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_read_transmit_power_level_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_read_transmit_power_level_complete with error code %s", error_code.c_str());
- return;
- }
- OnReadTransmitPowerLevelComplete(complete_view.GetTransmitPowerLevel());
- }
-
- void on_read_link_supervision_timeout_complete(CommandCompleteView view) {
- auto complete_view = ReadLinkSupervisionTimeoutCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_read_link_supervision_timeout_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_read_link_supervision_timeout_complete with error code %s", error_code.c_str());
- return;
- }
- OnReadLinkSupervisionTimeoutComplete(complete_view.GetLinkSupervisionTimeout());
- }
-
- void on_read_failed_contact_counter_complete(CommandCompleteView view) {
- auto complete_view = ReadFailedContactCounterCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_read_failed_contact_counter_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_read_failed_contact_counter_complete with error code %s", error_code.c_str());
- return;
- }
- OnReadFailedContactCounterComplete(complete_view.GetFailedContactCounter());
- }
-
- void on_read_link_quality_complete(CommandCompleteView view) {
- auto complete_view = ReadLinkQualityCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_read_link_quality_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_read_link_quality_complete with error code %s", error_code.c_str());
- return;
- }
- OnReadLinkQualityComplete(complete_view.GetLinkQuality());
- }
-
- void on_read_afh_channel_map_complete(CommandCompleteView view) {
- auto complete_view = ReadAfhChannelMapCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_read_afh_channel_map_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_read_afh_channel_map_complete with error code %s", error_code.c_str());
- return;
- }
- OnReadAfhChannelMapComplete(complete_view.GetAfhMode(), complete_view.GetAfhChannelMap());
- }
-
- void on_read_rssi_complete(CommandCompleteView view) {
- auto complete_view = ReadRssiCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_read_rssi_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_read_rssi_complete with error code %s", error_code.c_str());
- return;
- }
- OnReadRssiComplete(complete_view.GetRssi());
- }
-
- void on_read_remote_version_information_status(CommandStatusView view) {
- ASSERT_LOG(view.IsValid(), "Bad status packet!");
- }
-
- void on_read_remote_supported_features_status(CommandStatusView view) {
- ASSERT_LOG(view.IsValid(), "Bad status packet!");
- }
-
- void on_read_remote_extended_features_status(CommandStatusView view) {
- ASSERT_LOG(view.IsValid(), "Bad status packet!");
- }
-
- void on_read_clock_complete(CommandCompleteView view) {
- auto complete_view = ReadClockCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_read_clock_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_read_clock_complete with error code %s", error_code.c_str());
- return;
- }
- uint32_t clock = complete_view.GetClock();
- uint16_t accuracy = complete_view.GetAccuracy();
- OnReadClockComplete(clock, accuracy);
- }
-
- AclConnectionInterface* acl_connection_interface_;
- os::Handler* client_handler_ = nullptr;
- ConnectionManagementCallbacks* client_callbacks_ = nullptr;
- std::list<common::OnceClosure> queued_callbacks_;
- Address address_;
- uint16_t connection_handle_;
-};
-
-struct ClassicAclConnection::impl {
- impl(
- AclConnectionInterface* acl_connection_interface,
- std::shared_ptr<Queue> queue,
- const Address& address,
- uint16_t connection_handle)
- : tracker(acl_connection_interface, address, connection_handle), queue_(std::move(queue)) {}
- ConnectionManagementCallbacks* GetEventCallbacks() {
- ASSERT(!callbacks_given_);
- callbacks_given_ = true;
- return &tracker;
- }
-
- bool callbacks_given_{false};
- AclConnectionTracker tracker;
- std::shared_ptr<Queue> queue_;
-};
-
-ClassicAclConnection::ClassicAclConnection()
- : AclConnection(), acl_connection_interface_(nullptr), address_(Address::kEmpty) {}
-
-ClassicAclConnection::ClassicAclConnection(std::shared_ptr<Queue> queue,
- AclConnectionInterface* acl_connection_interface, uint16_t handle,
- Address address)
- : AclConnection(queue->GetUpEnd(), handle), acl_connection_interface_(acl_connection_interface), address_(address) {
- pimpl_ = new ClassicAclConnection::impl(acl_connection_interface, std::move(queue), address, handle);
-}
-
-ClassicAclConnection::~ClassicAclConnection() {
- delete pimpl_;
-}
-
-ConnectionManagementCallbacks* ClassicAclConnection::GetEventCallbacks() {
- return pimpl_->GetEventCallbacks();
-}
-
-void ClassicAclConnection::RegisterCallbacks(ConnectionManagementCallbacks* callbacks, os::Handler* handler) {
- return pimpl_->tracker.RegisterCallbacks(callbacks, handler);
-}
-
-bool ClassicAclConnection::Disconnect(DisconnectReason reason) {
- acl_connection_interface_->EnqueueCommand(
- DisconnectBuilder::Create(handle_, reason),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_status<DisconnectStatusView>));
- return true;
-}
-
-bool ClassicAclConnection::ChangeConnectionPacketType(uint16_t packet_type) {
- acl_connection_interface_->EnqueueCommand(
- ChangeConnectionPacketTypeBuilder::Create(handle_, packet_type),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_status<ChangeConnectionPacketTypeStatusView>));
- return true;
-}
-
-bool ClassicAclConnection::AuthenticationRequested() {
- acl_connection_interface_->EnqueueCommand(
- AuthenticationRequestedBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_status<AuthenticationRequestedStatusView>));
- return true;
-}
-
-bool ClassicAclConnection::SetConnectionEncryption(Enable enable) {
- acl_connection_interface_->EnqueueCommand(
- SetConnectionEncryptionBuilder::Create(handle_, enable),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_status<SetConnectionEncryptionStatusView>));
- return true;
-}
-
-bool ClassicAclConnection::ChangeConnectionLinkKey() {
- acl_connection_interface_->EnqueueCommand(
- ChangeConnectionLinkKeyBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_status<ChangeConnectionLinkKeyStatusView>));
- return true;
-}
-
-bool ClassicAclConnection::ReadClockOffset() {
- acl_connection_interface_->EnqueueCommand(
- ReadClockOffsetBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_status<ReadClockOffsetStatusView>));
- return true;
-}
-
-bool ClassicAclConnection::HoldMode(uint16_t max_interval, uint16_t min_interval) {
- acl_connection_interface_->EnqueueCommand(
- HoldModeBuilder::Create(handle_, max_interval, min_interval),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_status<HoldModeStatusView>));
- return true;
-}
-
-bool ClassicAclConnection::SniffMode(uint16_t max_interval, uint16_t min_interval, uint16_t attempt, uint16_t timeout) {
- acl_connection_interface_->EnqueueCommand(
- SniffModeBuilder::Create(handle_, max_interval, min_interval, attempt, timeout),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_status<SniffModeStatusView>));
- return true;
-}
-
-bool ClassicAclConnection::ExitSniffMode() {
- acl_connection_interface_->EnqueueCommand(
- ExitSniffModeBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_status<ExitSniffModeStatusView>));
- return true;
-}
-
-bool ClassicAclConnection::QosSetup(ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth,
- uint32_t latency, uint32_t delay_variation) {
- acl_connection_interface_->EnqueueCommand(
- QosSetupBuilder::Create(handle_, service_type, token_rate, peak_bandwidth, latency, delay_variation),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_status<QosSetupStatusView>));
- return true;
-}
-
-bool ClassicAclConnection::RoleDiscovery() {
- acl_connection_interface_->EnqueueCommand(
- RoleDiscoveryBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker, &AclConnectionTracker::on_role_discovery_complete));
- return true;
-}
-
-bool ClassicAclConnection::ReadLinkPolicySettings() {
- acl_connection_interface_->EnqueueCommand(
- ReadLinkPolicySettingsBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker,
- &AclConnectionTracker::on_read_link_policy_settings_complete));
- return true;
-}
-
-bool ClassicAclConnection::WriteLinkPolicySettings(uint16_t link_policy_settings) {
- acl_connection_interface_->EnqueueCommand(
- WriteLinkPolicySettingsBuilder::Create(handle_, link_policy_settings),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_complete<WriteLinkPolicySettingsCompleteView>));
- return true;
-}
-
-bool ClassicAclConnection::FlowSpecification(FlowDirection flow_direction, ServiceType service_type,
- uint32_t token_rate, uint32_t token_bucket_size, uint32_t peak_bandwidth,
- uint32_t access_latency) {
- acl_connection_interface_->EnqueueCommand(
- FlowSpecificationBuilder::Create(handle_, flow_direction, service_type, token_rate, token_bucket_size,
- peak_bandwidth, access_latency),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_status<FlowSpecificationStatusView>));
- return true;
-}
-
-bool ClassicAclConnection::SniffSubrating(uint16_t maximum_latency, uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) {
- acl_connection_interface_->EnqueueCommand(
- SniffSubratingBuilder::Create(handle_, maximum_latency, minimum_remote_timeout, minimum_local_timeout),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_complete<SniffSubratingCompleteView>));
- return true;
-}
-
-bool ClassicAclConnection::Flush() {
- acl_connection_interface_->EnqueueCommand(
- FlushBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_complete<FlushCompleteView>));
- return true;
-}
-
-bool ClassicAclConnection::ReadAutomaticFlushTimeout() {
- acl_connection_interface_->EnqueueCommand(
- ReadAutomaticFlushTimeoutBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker,
- &AclConnectionTracker::on_read_automatic_flush_timeout_complete));
- return true;
-}
-
-bool ClassicAclConnection::WriteAutomaticFlushTimeout(uint16_t flush_timeout) {
- acl_connection_interface_->EnqueueCommand(
- WriteAutomaticFlushTimeoutBuilder::Create(handle_, flush_timeout),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_complete<WriteAutomaticFlushTimeoutCompleteView>));
- return true;
-}
-
-bool ClassicAclConnection::ReadTransmitPowerLevel(TransmitPowerLevelType type) {
- acl_connection_interface_->EnqueueCommand(
- ReadTransmitPowerLevelBuilder::Create(handle_, type),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker,
- &AclConnectionTracker::on_read_transmit_power_level_complete));
- return true;
-}
-
-bool ClassicAclConnection::ReadLinkSupervisionTimeout() {
- acl_connection_interface_->EnqueueCommand(
- ReadLinkSupervisionTimeoutBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker,
- &AclConnectionTracker::on_read_link_supervision_timeout_complete));
- return true;
-}
-
-bool ClassicAclConnection::WriteLinkSupervisionTimeout(uint16_t link_supervision_timeout) {
- acl_connection_interface_->EnqueueCommand(
- WriteLinkSupervisionTimeoutBuilder::Create(handle_, link_supervision_timeout),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_complete<WriteLinkSupervisionTimeoutCompleteView>));
- return true;
-}
-
-bool ClassicAclConnection::ReadFailedContactCounter() {
- acl_connection_interface_->EnqueueCommand(
- ReadFailedContactCounterBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker,
- &AclConnectionTracker::on_read_failed_contact_counter_complete));
- return true;
-}
-
-bool ClassicAclConnection::ResetFailedContactCounter() {
- acl_connection_interface_->EnqueueCommand(
- ResetFailedContactCounterBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnce(&check_command_complete<ResetFailedContactCounterCompleteView>));
- return true;
-}
-
-bool ClassicAclConnection::ReadLinkQuality() {
- acl_connection_interface_->EnqueueCommand(
- ReadLinkQualityBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker,
- &AclConnectionTracker::on_read_link_quality_complete));
- return true;
-}
-
-bool ClassicAclConnection::ReadAfhChannelMap() {
- acl_connection_interface_->EnqueueCommand(
- ReadAfhChannelMapBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker,
- &AclConnectionTracker::on_read_afh_channel_map_complete));
- return true;
-}
-
-bool ClassicAclConnection::ReadRssi() {
- acl_connection_interface_->EnqueueCommand(
- ReadRssiBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker, &AclConnectionTracker::on_read_rssi_complete));
- return true;
-}
-
-bool ClassicAclConnection::ReadRemoteVersionInformation() {
- acl_connection_interface_->EnqueueCommand(
- ReadRemoteVersionInformationBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker,
- &AclConnectionTracker::on_read_remote_version_information_status));
- return true;
-}
-
-bool ClassicAclConnection::ReadRemoteSupportedFeatures() {
- acl_connection_interface_->EnqueueCommand(
- ReadRemoteSupportedFeaturesBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker,
- &AclConnectionTracker::on_read_remote_supported_features_status));
- return true;
-}
-
-bool ClassicAclConnection::ReadRemoteExtendedFeatures(uint8_t page_number) {
- acl_connection_interface_->EnqueueCommand(
- ReadRemoteExtendedFeaturesBuilder::Create(handle_, page_number),
- pimpl_->tracker.client_handler_->BindOnceOn(
- &pimpl_->tracker, &AclConnectionTracker::on_read_remote_extended_features_status));
- return true;
-}
-
-bool ClassicAclConnection::ReadClock(WhichClock which_clock) {
- pimpl_->tracker.acl_connection_interface_->EnqueueCommand(
- ReadClockBuilder::Create(handle_, which_clock),
- pimpl_->tracker.client_handler_->BindOnceOn(&pimpl_->tracker, &AclConnectionTracker::on_read_clock_complete));
- return true;
-}
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/classic_acl_connection.h b/gd/hci/acl_manager/classic_acl_connection.h
deleted file mode 100644
index b2526cba2..000000000
--- a/gd/hci/acl_manager/classic_acl_connection.h
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "hci/acl_connection_interface.h"
-#include "hci/acl_manager/acl_connection.h"
-#include "hci/acl_manager/connection_management_callbacks.h"
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-class ClassicAclConnection : public AclConnection {
- public:
- ClassicAclConnection();
- ClassicAclConnection(std::shared_ptr<Queue> queue, AclConnectionInterface* acl_connection_interface, uint16_t handle,
- Address address);
- ~ClassicAclConnection();
-
- virtual Address GetAddress() const {
- return address_;
- }
-
- virtual void RegisterCallbacks(ConnectionManagementCallbacks* callbacks, os::Handler* handler);
- virtual bool Disconnect(DisconnectReason reason);
- virtual bool ChangeConnectionPacketType(uint16_t packet_type);
- virtual bool AuthenticationRequested();
- virtual bool SetConnectionEncryption(Enable enable);
- virtual bool ChangeConnectionLinkKey();
- virtual bool ReadClockOffset();
- virtual bool HoldMode(uint16_t max_interval, uint16_t min_interval);
- virtual bool SniffMode(uint16_t max_interval, uint16_t min_interval, uint16_t attempt, uint16_t timeout);
- virtual bool ExitSniffMode();
- virtual bool QosSetup(ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth, uint32_t latency,
- uint32_t delay_variation);
- virtual bool RoleDiscovery();
- virtual bool ReadLinkPolicySettings();
- virtual bool WriteLinkPolicySettings(uint16_t link_policy_settings);
- virtual bool FlowSpecification(FlowDirection flow_direction, ServiceType service_type, uint32_t token_rate,
- uint32_t token_bucket_size, uint32_t peak_bandwidth, uint32_t access_latency);
- virtual bool SniffSubrating(uint16_t maximum_latency, uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout);
- virtual bool Flush();
- virtual bool ReadAutomaticFlushTimeout();
- virtual bool WriteAutomaticFlushTimeout(uint16_t flush_timeout);
- virtual bool ReadTransmitPowerLevel(TransmitPowerLevelType type);
- virtual bool ReadLinkSupervisionTimeout();
- virtual bool WriteLinkSupervisionTimeout(uint16_t link_supervision_timeout);
- virtual bool ReadFailedContactCounter();
- virtual bool ResetFailedContactCounter();
- virtual bool ReadLinkQuality();
- virtual bool ReadAfhChannelMap();
- virtual bool ReadRssi();
- virtual bool ReadClock(WhichClock which_clock);
- virtual bool ReadRemoteVersionInformation() override;
- virtual bool ReadRemoteSupportedFeatures();
- virtual bool ReadRemoteExtendedFeatures(uint8_t page_number);
-
- // Called once before passing the connection to the client
- virtual ConnectionManagementCallbacks* GetEventCallbacks();
-
- private:
- AclConnectionInterface* acl_connection_interface_;
-
- protected:
- Address address_;
-
- private:
- struct impl;
- struct impl* pimpl_ = nullptr;
- DISALLOW_COPY_AND_ASSIGN(ClassicAclConnection);
-};
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/classic_impl.h b/gd/hci/acl_manager/classic_impl.h
deleted file mode 100644
index 19d1380ed..000000000
--- a/gd/hci/acl_manager/classic_impl.h
+++ /dev/null
@@ -1,703 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "common/bind.h"
-#include "hci/acl_manager/assembler.h"
-#include "hci/acl_manager/event_checkers.h"
-#include "hci/acl_manager/round_robin_scheduler.h"
-#include "hci/controller.h"
-#include "security/security_manager_listener.h"
-#include "security/security_module.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-struct acl_connection {
- acl_connection(AddressWithType address_with_type, AclConnection::QueueDownEnd* queue_down_end, os::Handler* handler)
- : assembler_(address_with_type, queue_down_end, handler), address_with_type_(address_with_type) {}
- ~acl_connection() = default;
- struct acl_manager::assembler assembler_;
- AddressWithType address_with_type_;
- ConnectionManagementCallbacks* connection_management_callbacks_ = nullptr;
-};
-
-struct classic_impl : public security::ISecurityManagerListener {
- classic_impl(
- HciLayer* hci_layer,
- Controller* controller,
- os::Handler* handler,
- RoundRobinScheduler* round_robin_scheduler,
- bool crash_on_unknown_handle)
- : hci_layer_(hci_layer),
- controller_(controller),
- round_robin_scheduler_(round_robin_scheduler),
- crash_on_unknown_handle_(crash_on_unknown_handle) {
- hci_layer_ = hci_layer;
- controller_ = controller;
- handler_ = handler;
- should_accept_connection_ = common::Bind([](Address, ClassOfDevice) { return true; });
- acl_connection_interface_ = hci_layer_->GetAclConnectionInterface(
- handler_->BindOn(this, &classic_impl::on_classic_event),
- handler_->BindOn(this, &classic_impl::on_classic_disconnect),
- handler_->BindOn(this, &classic_impl::on_read_remote_version_information));
- }
-
- ~classic_impl() {
- for (auto event_code : AclConnectionEvents) {
- hci_layer_->UnregisterEventHandler(event_code);
- }
- acl_connections_.clear();
- security_manager_.reset();
- }
-
- ConnectionManagementCallbacks* get_callbacks(uint16_t handle) {
- auto conn = acl_connections_.find(handle);
- if (conn == acl_connections_.end()) {
- return nullptr;
- } else {
- return conn->second.connection_management_callbacks_;
- }
- }
-
- void on_classic_event(EventView event_packet) {
- EventCode event_code = event_packet.GetEventCode();
- switch (event_code) {
- case EventCode::CONNECTION_COMPLETE:
- on_connection_complete(event_packet);
- break;
- case EventCode::CONNECTION_REQUEST:
- on_incoming_connection(event_packet);
- break;
- case EventCode::CONNECTION_PACKET_TYPE_CHANGED:
- on_connection_packet_type_changed(event_packet);
- break;
- case EventCode::AUTHENTICATION_COMPLETE:
- on_authentication_complete(event_packet);
- break;
- case EventCode::READ_CLOCK_OFFSET_COMPLETE:
- on_read_clock_offset_complete(event_packet);
- break;
- case EventCode::MODE_CHANGE:
- on_mode_change(event_packet);
- break;
- case EventCode::SNIFF_SUBRATING:
- on_sniff_subrating(event_packet);
- break;
- case EventCode::QOS_SETUP_COMPLETE:
- on_qos_setup_complete(event_packet);
- break;
- case EventCode::ROLE_CHANGE:
- on_role_change(event_packet);
- break;
- case EventCode::FLOW_SPECIFICATION_COMPLETE:
- on_flow_specification_complete(event_packet);
- break;
- case EventCode::FLUSH_OCCURRED:
- on_flush_occurred(event_packet);
- break;
- case EventCode::READ_REMOTE_SUPPORTED_FEATURES_COMPLETE:
- on_read_remote_supported_features_complete(event_packet);
- break;
- case EventCode::READ_REMOTE_EXTENDED_FEATURES_COMPLETE:
- on_read_remote_extended_features_complete(event_packet);
- break;
- case EventCode::LINK_SUPERVISION_TIMEOUT_CHANGED:
- on_link_supervision_timeout_changed(event_packet);
- break;
- case EventCode::CENTRAL_LINK_KEY_COMPLETE:
- on_central_link_key_complete(event_packet);
- break;
- default:
- LOG_ALWAYS_FATAL("Unhandled event code %s", EventCodeText(event_code).c_str());
- }
- }
-
- void on_classic_disconnect(uint16_t handle, ErrorCode reason) {
- auto callbacks = get_callbacks(handle);
- if (callbacks != nullptr) {
- round_robin_scheduler_->Unregister(handle);
- callbacks->OnDisconnection(reason);
- acl_connections_.erase(handle);
- } else {
- // This handle is probably for SCO, so we use the callback workaround.
- if (sco_disconnect_callback_ != nullptr) {
- sco_disconnect_callback_(handle, static_cast<uint8_t>(reason));
- }
- }
- }
-
- void handle_register_callbacks(ConnectionCallbacks* callbacks, os::Handler* handler) {
- ASSERT(client_callbacks_ == nullptr);
- ASSERT(client_handler_ == nullptr);
- client_callbacks_ = callbacks;
- client_handler_ = handler;
- }
-
- void handle_unregister_callbacks(ConnectionCallbacks* callbacks, std::promise<void> promise) {
- ASSERT_LOG(client_callbacks_ == callbacks, "Registered callback entity is different then unregister request");
- client_callbacks_ = nullptr;
- client_handler_ = nullptr;
- promise.set_value();
- }
-
- void on_incoming_connection(EventView packet) {
- ConnectionRequestView request = ConnectionRequestView::Create(packet);
- ASSERT(request.IsValid());
- Address address = request.GetBdAddr();
- if (client_callbacks_ == nullptr) {
- LOG_ERROR("No callbacks to call");
- auto reason = RejectConnectionReason::LIMITED_RESOURCES;
- this->reject_connection(RejectConnectionRequestBuilder::Create(address, reason));
- return;
- }
-
- switch (request.GetLinkType()) {
- case ConnectionRequestLinkType::SCO:
- client_handler_->CallOn(
- client_callbacks_, &ConnectionCallbacks::HACK_OnScoConnectRequest, address, request.GetClassOfDevice());
- return;
-
- case ConnectionRequestLinkType::ACL:
- break;
-
- case ConnectionRequestLinkType::ESCO:
- client_handler_->CallOn(
- client_callbacks_, &ConnectionCallbacks::HACK_OnEscoConnectRequest, address, request.GetClassOfDevice());
- return;
-
- case ConnectionRequestLinkType::UNKNOWN:
- LOG_ERROR("Request has unknown ConnectionRequestLinkType.");
- return;
- }
-
- incoming_connecting_address_ = address;
- if (is_classic_link_already_connected(address)) {
- auto reason = RejectConnectionReason::UNACCEPTABLE_BD_ADDR;
- this->reject_connection(RejectConnectionRequestBuilder::Create(address, reason));
- } else if (should_accept_connection_.Run(address, request.GetClassOfDevice())) {
- this->accept_connection(address);
- } else {
- auto reason = RejectConnectionReason::LIMITED_RESOURCES; // TODO: determine reason
- this->reject_connection(RejectConnectionRequestBuilder::Create(address, reason));
- }
- }
-
- bool is_classic_link_already_connected(Address address) {
- for (const auto& connection : acl_connections_) {
- if (connection.second.address_with_type_.GetAddress() == address) {
- return true;
- }
- }
- return false;
- }
-
- void create_connection(Address address) {
- // TODO: Configure default connection parameters?
- uint16_t packet_type = 0x4408 /* DM 1,3,5 */ | 0x8810 /*DH 1,3,5 */;
- PageScanRepetitionMode page_scan_repetition_mode = PageScanRepetitionMode::R1;
- uint16_t clock_offset = 0;
- ClockOffsetValid clock_offset_valid = ClockOffsetValid::INVALID;
- CreateConnectionRoleSwitch allow_role_switch = CreateConnectionRoleSwitch::ALLOW_ROLE_SWITCH;
- ASSERT(client_callbacks_ != nullptr);
- std::unique_ptr<CreateConnectionBuilder> packet = CreateConnectionBuilder::Create(
- address, packet_type, page_scan_repetition_mode, clock_offset, clock_offset_valid, allow_role_switch);
-
- if (incoming_connecting_address_ == Address::kEmpty && outgoing_connecting_address_ == Address::kEmpty) {
- if (is_classic_link_already_connected(address)) {
- LOG_WARN("already connected: %s", address.ToString().c_str());
- return;
- }
- outgoing_connecting_address_ = address;
- acl_connection_interface_->EnqueueCommand(std::move(packet), handler_->BindOnce([](CommandStatusView status) {
- ASSERT(status.IsValid());
- ASSERT(status.GetCommandOpCode() == OpCode::CREATE_CONNECTION);
- }));
- } else {
- pending_outgoing_connections_.emplace(address, std::move(packet));
- }
- }
-
- void on_connection_complete(EventView packet) {
- ConnectionCompleteView connection_complete = ConnectionCompleteView::Create(packet);
- ASSERT(connection_complete.IsValid());
- auto status = connection_complete.GetStatus();
- auto address = connection_complete.GetBdAddr();
- Role current_role = Role::CENTRAL;
- bool locally_initiated = true;
- if (outgoing_connecting_address_ == address) {
- outgoing_connecting_address_ = Address::kEmpty;
- } else {
- locally_initiated = false;
- if (incoming_connecting_address_ != address && status == ErrorCode::UNKNOWN_CONNECTION) {
- LOG_WARN("No matching connection to %s (%s)", address.ToString().c_str(), ErrorCodeText(status).c_str());
- LOG_WARN("Firmware error after RemoteNameRequestCancel?");
- return;
- }
- ASSERT_LOG(incoming_connecting_address_ == address, "No prior connection request for %s",
- address.ToString().c_str());
- incoming_connecting_address_ = Address::kEmpty;
- current_role = Role::PERIPHERAL;
- }
- if (client_callbacks_ == nullptr) {
- LOG_WARN("No client callbacks registered for connection");
- return;
- }
- if (status != ErrorCode::SUCCESS) {
- client_handler_->Post(common::BindOnce(&ConnectionCallbacks::OnConnectFail, common::Unretained(client_callbacks_),
- address, status));
- return;
- }
- uint16_t handle = connection_complete.GetConnectionHandle();
- auto queue = std::make_shared<AclConnection::Queue>(10);
- auto conn_pair = acl_connections_.emplace(
- std::piecewise_construct,
- std::forward_as_tuple(handle),
- std::forward_as_tuple(
- AddressWithType{address, AddressType::PUBLIC_DEVICE_ADDRESS}, queue->GetDownEnd(), handler_));
- ASSERT(conn_pair.second); // Make sure it's not a duplicate
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::CLASSIC, handle, queue);
- std::unique_ptr<ClassicAclConnection> connection(
- new ClassicAclConnection(std::move(queue), acl_connection_interface_, handle, address));
- connection->locally_initiated_ = locally_initiated;
- auto& connection_proxy = conn_pair.first->second;
- connection_proxy.connection_management_callbacks_ = connection->GetEventCallbacks();
- if (delayed_role_change_ != nullptr) {
- if (delayed_role_change_->GetBdAddr() == address) {
- LOG_INFO("Sending delayed role change for %s", delayed_role_change_->GetBdAddr().ToString().c_str());
- connection_proxy.connection_management_callbacks_->OnRoleChange(
- delayed_role_change_->GetStatus(), delayed_role_change_->GetNewRole());
- }
- delayed_role_change_ = nullptr;
- } else {
- connection_proxy.connection_management_callbacks_->OnRoleChange(hci::ErrorCode::SUCCESS, current_role);
- }
- client_handler_->Post(common::BindOnce(&ConnectionCallbacks::OnConnectSuccess,
- common::Unretained(client_callbacks_), std::move(connection)));
- while (!pending_outgoing_connections_.empty()) {
- auto create_connection_packet_and_address = std::move(pending_outgoing_connections_.front());
- pending_outgoing_connections_.pop();
- if (!is_classic_link_already_connected(create_connection_packet_and_address.first)) {
- outgoing_connecting_address_ = create_connection_packet_and_address.first;
- acl_connection_interface_->EnqueueCommand(std::move(create_connection_packet_and_address.second),
- handler_->BindOnce([](CommandStatusView status) {
- ASSERT(status.IsValid());
- ASSERT(status.GetCommandOpCode() == OpCode::CREATE_CONNECTION);
- }));
- break;
- }
- }
- }
-
- void on_connection_packet_type_changed(EventView packet) {
- ConnectionPacketTypeChangedView packet_type_changed = ConnectionPacketTypeChangedView::Create(packet);
- if (!packet_type_changed.IsValid()) {
- LOG_ERROR("Received on_connection_packet_type_changed with invalid packet");
- return;
- } else if (packet_type_changed.GetStatus() != ErrorCode::SUCCESS) {
- auto status = packet_type_changed.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_connection_packet_type_changed with error code %s", error_code.c_str());
- return;
- }
- uint16_t handle = packet_type_changed.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- // We don't handle this event; we didn't do this in legacy stack either.
- }
-
- void on_central_link_key_complete(EventView packet) {
- CentralLinkKeyCompleteView complete_view = CentralLinkKeyCompleteView::Create(packet);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_central_link_key_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_central_link_key_complete with error code %s", error_code.c_str());
- return;
- }
- uint16_t handle = complete_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- KeyFlag key_flag = complete_view.GetKeyFlag();
- callbacks->OnCentralLinkKeyComplete(key_flag);
- }
-
- void on_authentication_complete(EventView packet) {
- AuthenticationCompleteView authentication_complete = AuthenticationCompleteView::Create(packet);
- if (!authentication_complete.IsValid()) {
- LOG_ERROR("Received on_authentication_complete with invalid packet");
- return;
- }
- uint16_t handle = authentication_complete.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnAuthenticationComplete(authentication_complete.GetStatus());
- }
-
- void cancel_connect(Address address) {
- if (outgoing_connecting_address_ == address) {
- LOG_INFO("Cannot cancel non-existent connection to %s", address.ToString().c_str());
- return;
- }
- std::unique_ptr<CreateConnectionCancelBuilder> packet = CreateConnectionCancelBuilder::Create(address);
- acl_connection_interface_->EnqueueCommand(
- std::move(packet), handler_->BindOnce(&check_command_complete<CreateConnectionCancelCompleteView>));
- }
-
- void central_link_key(KeyFlag key_flag) {
- std::unique_ptr<CentralLinkKeyBuilder> packet = CentralLinkKeyBuilder::Create(key_flag);
- acl_connection_interface_->EnqueueCommand(
- std::move(packet), handler_->BindOnce(&check_command_status<CentralLinkKeyStatusView>));
- }
-
- void switch_role(Address address, Role role) {
- std::unique_ptr<SwitchRoleBuilder> packet = SwitchRoleBuilder::Create(address, role);
- acl_connection_interface_->EnqueueCommand(std::move(packet),
- handler_->BindOnce(&check_command_status<SwitchRoleStatusView>));
- }
-
- void write_default_link_policy_settings(uint16_t default_link_policy_settings) {
- std::unique_ptr<WriteDefaultLinkPolicySettingsBuilder> packet =
- WriteDefaultLinkPolicySettingsBuilder::Create(default_link_policy_settings);
- acl_connection_interface_->EnqueueCommand(
- std::move(packet), handler_->BindOnce(&check_command_complete<WriteDefaultLinkPolicySettingsCompleteView>));
- }
-
- void accept_connection(Address address) {
- auto role = AcceptConnectionRequestRole::BECOME_CENTRAL; // We prefer to be central
- acl_connection_interface_->EnqueueCommand(
- AcceptConnectionRequestBuilder::Create(address, role),
- handler_->BindOnceOn(this, &classic_impl::on_accept_connection_status, address));
- }
-
- void on_change_connection_link_key_complete(EventView packet) {
- ChangeConnectionLinkKeyCompleteView complete_view = ChangeConnectionLinkKeyCompleteView::Create(packet);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_change_connection_link_key_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_change_connection_link_key_complete with error code %s", error_code.c_str());
- return;
- }
- uint16_t handle = complete_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnChangeConnectionLinkKeyComplete();
- }
-
- void on_read_clock_offset_complete(EventView packet) {
- ReadClockOffsetCompleteView complete_view = ReadClockOffsetCompleteView::Create(packet);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_read_clock_offset_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_read_clock_offset_complete with error code %s", error_code.c_str());
- return;
- }
- uint16_t handle = complete_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- uint16_t clock_offset = complete_view.GetClockOffset();
- callbacks->OnReadClockOffsetComplete(clock_offset);
- }
-
- void on_mode_change(EventView packet) {
- ModeChangeView mode_change_view = ModeChangeView::Create(packet);
- if (!mode_change_view.IsValid()) {
- LOG_ERROR("Received on_mode_change with invalid packet");
- return;
- }
- uint16_t handle = mode_change_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnModeChange(
- mode_change_view.GetStatus(), mode_change_view.GetCurrentMode(), mode_change_view.GetInterval());
- }
-
- void on_sniff_subrating(EventView packet) {
- SniffSubratingEventView sniff_subrating_view = SniffSubratingEventView::Create(packet);
- if (!sniff_subrating_view.IsValid()) {
- LOG_ERROR("Received on_sniff_subrating with invalid packet");
- return;
- }
- uint16_t handle = sniff_subrating_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnSniffSubrating(
- sniff_subrating_view.GetStatus(),
- sniff_subrating_view.GetMaximumTransmitLatency(),
- sniff_subrating_view.GetMaximumReceiveLatency(),
- sniff_subrating_view.GetMinimumRemoteTimeout(),
- sniff_subrating_view.GetMinimumLocalTimeout());
- }
-
- void on_qos_setup_complete(EventView packet) {
- QosSetupCompleteView complete_view = QosSetupCompleteView::Create(packet);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_qos_setup_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_qos_setup_complete with error code %s", error_code.c_str());
- return;
- }
- uint16_t handle = complete_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- ServiceType service_type = complete_view.GetServiceType();
- uint32_t token_rate = complete_view.GetTokenRate();
- uint32_t peak_bandwidth = complete_view.GetPeakBandwidth();
- uint32_t latency = complete_view.GetLatency();
- uint32_t delay_variation = complete_view.GetDelayVariation();
- callbacks->OnQosSetupComplete(service_type, token_rate, peak_bandwidth, latency, delay_variation);
- }
-
- void on_role_change(EventView packet) {
- RoleChangeView role_change_view = RoleChangeView::Create(packet);
- if (!role_change_view.IsValid()) {
- LOG_ERROR("Received on_role_change with invalid packet");
- return;
- }
- bool sent = false;
- auto hci_status = role_change_view.GetStatus();
- Address bd_addr = role_change_view.GetBdAddr();
- Role new_role = role_change_view.GetNewRole();
- for (auto& connection_pair : acl_connections_) {
- if (connection_pair.second.address_with_type_.GetAddress() == bd_addr) {
- connection_pair.second.connection_management_callbacks_->OnRoleChange(hci_status, new_role);
- sent = true;
- }
- }
- if (!sent) {
- if (delayed_role_change_ != nullptr) {
- LOG_WARN("Second delayed role change (@%s dropped)", delayed_role_change_->GetBdAddr().ToString().c_str());
- }
- LOG_INFO(
- "Role change for %s with no matching connection (new role: %s)",
- role_change_view.GetBdAddr().ToString().c_str(),
- RoleText(role_change_view.GetNewRole()).c_str());
- delayed_role_change_ = std::make_unique<RoleChangeView>(role_change_view);
- }
- }
-
- void on_flow_specification_complete(EventView packet) {
- FlowSpecificationCompleteView complete_view = FlowSpecificationCompleteView::Create(packet);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_flow_specification_complete with invalid packet");
- return;
- } else if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received on_flow_specification_complete with error code %s", error_code.c_str());
- return;
- }
- uint16_t handle = complete_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- FlowDirection flow_direction = complete_view.GetFlowDirection();
- ServiceType service_type = complete_view.GetServiceType();
- uint32_t token_rate = complete_view.GetTokenRate();
- uint32_t token_bucket_size = complete_view.GetTokenBucketSize();
- uint32_t peak_bandwidth = complete_view.GetPeakBandwidth();
- uint32_t access_latency = complete_view.GetAccessLatency();
- callbacks->OnFlowSpecificationComplete(
- flow_direction, service_type, token_rate, token_bucket_size, peak_bandwidth, access_latency);
- }
-
- void on_flush_occurred(EventView packet) {
- FlushOccurredView flush_occurred_view = FlushOccurredView::Create(packet);
- if (!flush_occurred_view.IsValid()) {
- LOG_ERROR("Received on_flush_occurred with invalid packet");
- return;
- }
- uint16_t handle = flush_occurred_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnFlushOccurred();
- }
-
- void on_read_remote_version_information(
- hci::ErrorCode hci_status, uint16_t handle, uint8_t version, uint16_t manufacturer_name, uint16_t sub_version) {
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnReadRemoteVersionInformationComplete(hci_status, version, manufacturer_name, sub_version);
- }
-
- void on_read_remote_supported_features_complete(EventView packet) {
- auto view = ReadRemoteSupportedFeaturesCompleteView::Create(packet);
- ASSERT_LOG(view.IsValid(), "Read remote supported features packet invalid");
- uint16_t handle = view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnReadRemoteSupportedFeaturesComplete(view.GetLmpFeatures());
- }
-
- void on_read_remote_extended_features_complete(EventView packet) {
- auto view = ReadRemoteExtendedFeaturesCompleteView::Create(packet);
- ASSERT_LOG(view.IsValid(), "Read remote extended features packet invalid");
- uint16_t handle = view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnReadRemoteExtendedFeaturesComplete(
- view.GetPageNumber(), view.GetMaximumPageNumber(), view.GetExtendedLmpFeatures());
- }
-
- void on_link_supervision_timeout_changed(EventView packet) {
- auto view = LinkSupervisionTimeoutChangedView::Create(packet);
- ASSERT_LOG(view.IsValid(), "Link supervision timeout changed packet invalid");
- LOG_INFO("UNIMPLEMENTED called");
- }
-
- void on_accept_connection_status(Address address, CommandStatusView status) {
- auto accept_status = AcceptConnectionRequestStatusView::Create(status);
- ASSERT(accept_status.IsValid());
- if (status.GetStatus() != ErrorCode::SUCCESS) {
- cancel_connect(address);
- }
- }
-
- void reject_connection(std::unique_ptr<RejectConnectionRequestBuilder> builder) {
- acl_connection_interface_->EnqueueCommand(
- std::move(builder), handler_->BindOnce(&check_command_status<RejectConnectionRequestStatusView>));
- }
-
- void OnDeviceBonded(bluetooth::hci::AddressWithType device) override {}
- void OnDeviceUnbonded(bluetooth::hci::AddressWithType device) override {}
- void OnDeviceBondFailed(bluetooth::hci::AddressWithType device, security::PairingFailure status) override {}
-
- void OnEncryptionStateChanged(EncryptionChangeView encryption_change_view) override {
- if (!encryption_change_view.IsValid()) {
- LOG_ERROR("Invalid packet");
- return;
- } else if (encryption_change_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = encryption_change_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("error_code %s", error_code.c_str());
- return;
- }
- uint16_t handle = encryption_change_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Unknown connection handle 0x%04hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- EncryptionEnabled enabled = encryption_change_view.GetEncryptionEnabled();
- callbacks->OnEncryptionChange(enabled);
- }
-
- void set_security_module(security::SecurityModule* security_module) {
- security_manager_ = security_module->GetSecurityManager();
- security_manager_->RegisterCallbackListener(this, handler_);
- }
-
- uint16_t HACK_get_handle(Address address) {
- for (auto it = acl_connections_.begin(); it != acl_connections_.end(); it++) {
- if (it->second.address_with_type_.GetAddress() == address) {
- return it->first;
- }
- }
- return 0xFFFF;
- }
-
- void HACK_SetScoDisconnectCallback(std::function<void(uint16_t, uint8_t)> callback) {
- sco_disconnect_callback_ = callback;
- }
-
- HciLayer* hci_layer_ = nullptr;
- Controller* controller_ = nullptr;
- RoundRobinScheduler* round_robin_scheduler_ = nullptr;
- AclConnectionInterface* acl_connection_interface_ = nullptr;
- os::Handler* handler_ = nullptr;
- ConnectionCallbacks* client_callbacks_ = nullptr;
- os::Handler* client_handler_ = nullptr;
- std::map<uint16_t, acl_connection> acl_connections_;
- Address outgoing_connecting_address_{Address::kEmpty};
- Address incoming_connecting_address_{Address::kEmpty};
- common::Callback<bool(Address, ClassOfDevice)> should_accept_connection_;
- std::queue<std::pair<Address, std::unique_ptr<CreateConnectionBuilder>>> pending_outgoing_connections_;
- std::unique_ptr<RoleChangeView> delayed_role_change_ = nullptr;
-
- std::unique_ptr<security::SecurityManager> security_manager_;
- bool crash_on_unknown_handle_ = false;
-
- std::function<void(uint16_t, uint8_t)> sco_disconnect_callback_;
-};
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/connection_callbacks.h b/gd/hci/acl_manager/connection_callbacks.h
deleted file mode 100644
index 9a72654e2..000000000
--- a/gd/hci/acl_manager/connection_callbacks.h
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <memory>
-#include "hci/acl_manager/classic_acl_connection.h"
-#include "hci/address.h"
-#include "hci/class_of_device.h"
-#include "hci/hci_packets.h"
-#include "os/handler.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-class ConnectionCallbacks {
- public:
- virtual ~ConnectionCallbacks() = default;
- // Invoked when controller sends Connection Complete event with Success error code
- virtual void OnConnectSuccess(std::unique_ptr<ClassicAclConnection>) = 0;
- // Invoked when controller sends Connection Complete event with non-Success error code
- virtual void OnConnectFail(Address, ErrorCode reason) = 0;
-
- virtual void HACK_OnEscoConnectRequest(Address, ClassOfDevice) = 0;
- virtual void HACK_OnScoConnectRequest(Address, ClassOfDevice) = 0;
-};
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/connection_management_callbacks.h b/gd/hci/acl_manager/connection_management_callbacks.h
deleted file mode 100644
index 1b2eea28d..000000000
--- a/gd/hci/acl_manager/connection_management_callbacks.h
+++ /dev/null
@@ -1,99 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include <memory>
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-class ConnectionManagementCallbacks {
- public:
- virtual ~ConnectionManagementCallbacks() = default;
- // Invoked when controller sends Connection Packet Type Changed event with Success error code
- virtual void OnConnectionPacketTypeChanged(uint16_t packet_type) = 0;
- // Invoked when controller sends Authentication Complete event with Success error code
- virtual void OnAuthenticationComplete(hci::ErrorCode hci_status) = 0;
- // Invoked when controller sends Encryption Change event with Success error code
- virtual void OnEncryptionChange(EncryptionEnabled enabled) = 0;
- // Invoked when controller sends Change Connection Link Key Complete event with Success error code
- virtual void OnChangeConnectionLinkKeyComplete() = 0;
- // Invoked when controller sends Read Clock Offset Complete event with Success error code
- virtual void OnReadClockOffsetComplete(uint16_t clock_offset) = 0;
- // Invoked when controller sends Mode Change event with Success error code
- virtual void OnModeChange(ErrorCode status, Mode current_mode, uint16_t interval) = 0;
- // Invoked when controller sends Sniff Subrating event with Success error code
- virtual void OnSniffSubrating(
- hci::ErrorCode hci_status,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) = 0;
- // Invoked when controller sends QoS Setup Complete event with Success error code
- virtual void OnQosSetupComplete(ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth,
- uint32_t latency, uint32_t delay_variation) = 0;
- // Invoked when controller sends Flow Specification Complete event with Success error code
- virtual void OnFlowSpecificationComplete(FlowDirection flow_direction, ServiceType service_type, uint32_t token_rate,
- uint32_t token_bucket_size, uint32_t peak_bandwidth,
- uint32_t access_latency) = 0;
- // Invoked when controller sends Flush Occurred event
- virtual void OnFlushOccurred() = 0;
- // Invoked when controller sends Command Complete event for Role Discovery command with Success error code
- virtual void OnRoleDiscoveryComplete(Role current_role) = 0;
- // Invoked when controller sends Command Complete event for Read Link Policy Settings command with Success error code
- virtual void OnReadLinkPolicySettingsComplete(uint16_t link_policy_settings) = 0;
- // Invoked when controller sends Command Complete event for Read Automatic Flush Timeout command with Success error
- // code
- virtual void OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout) = 0;
- // Invoked when controller sends Command Complete event for Read Transmit Power Level command with Success error code
- virtual void OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level) = 0;
- // Invoked when controller sends Command Complete event for Read Link Supervision Time out command with Success error
- // code
- virtual void OnReadLinkSupervisionTimeoutComplete(uint16_t link_supervision_timeout) = 0;
- // Invoked when controller sends Command Complete event for Read Failed Contact Counter command with Success error
- // code
- virtual void OnReadFailedContactCounterComplete(uint16_t failed_contact_counter) = 0;
- // Invoked when controller sends Command Complete event for Read Link Quality command with Success error code
- virtual void OnReadLinkQualityComplete(uint8_t link_quality) = 0;
- // Invoked when controller sends Command Complete event for Read AFH Channel Map command with Success error code
- virtual void OnReadAfhChannelMapComplete(AfhMode afh_mode, std::array<uint8_t, 10> afh_channel_map) = 0;
- // Invoked when controller sends Command Complete event for Read RSSI command with Success error code
- virtual void OnReadRssiComplete(uint8_t rssi) = 0;
- // Invoked when controller sends Command Complete event for Read Clock command with Success error code
- virtual void OnReadClockComplete(uint32_t clock, uint16_t accuracy) = 0;
- // Invoked when controller sends Central Link Key Complete event
- virtual void OnCentralLinkKeyComplete(KeyFlag key_flag) = 0;
- // Invoked when controller sends Role Change event
- virtual void OnRoleChange(hci::ErrorCode hci_status, Role new_role) = 0;
- // Invoked when controller sends DisconnectComplete
- virtual void OnDisconnection(ErrorCode reason) = 0;
- // Invoked when controller sends Read Remote Version Information Complete
- virtual void OnReadRemoteVersionInformationComplete(
- hci::ErrorCode hci_status, uint8_t lmp_version, uint16_t manufacturer_name, uint16_t sub_version) = 0;
- // Invoked when controller sends Read Remote Supported Features Complete
- virtual void OnReadRemoteSupportedFeaturesComplete(uint64_t features) = 0;
- // Invoked when controller sends Read Remote Extended Features Complete
- virtual void OnReadRemoteExtendedFeaturesComplete(
- uint8_t page_number, uint8_t max_page_number, uint64_t features) = 0;
-};
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/event_checkers.h b/gd/hci/acl_manager/event_checkers.h
deleted file mode 100644
index 1765661e2..000000000
--- a/gd/hci/acl_manager/event_checkers.h
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-template <class T>
-void check_command_complete(CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto status_view = T::Create(view);
- if (!status_view.IsValid()) {
- LOG_ERROR("Received command complete with invalid packet, opcode 0x%02hx", view.GetCommandOpCode());
- return;
- }
- ErrorCode status = status_view.GetStatus();
- OpCode op_code = status_view.GetCommandOpCode();
- if (status != ErrorCode::SUCCESS) {
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received command complete with error code %s, opcode 0x%02hx", error_code.c_str(), op_code);
- return;
- }
-}
-
-template <class T>
-void check_command_status(CommandStatusView view) {
- ASSERT(view.IsValid());
- auto status_view = T::Create(view);
- if (!status_view.IsValid()) {
- LOG_ERROR("Received command status with invalid packet, opcode 0x%02hx", view.GetCommandOpCode());
- return;
- }
- ErrorCode status = status_view.GetStatus();
- OpCode op_code = status_view.GetCommandOpCode();
- if (status != ErrorCode::SUCCESS) {
- std::string error_code = ErrorCodeText(status);
- LOG_ERROR("Received command status with error code %s, opcode 0x%02hx", error_code.c_str(), op_code);
- return;
- }
-}
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/le_acl_connection.cc b/gd/hci/acl_manager/le_acl_connection.cc
deleted file mode 100644
index 9333204c0..000000000
--- a/gd/hci/acl_manager/le_acl_connection.cc
+++ /dev/null
@@ -1,193 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/acl_manager/le_acl_connection.h"
-#include "hci/acl_manager/le_connection_management_callbacks.h"
-#include "os/metrics.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-class LeAclConnectionTracker : public LeConnectionManagementCallbacks {
- public:
- LeAclConnectionTracker(LeAclConnectionInterface* le_acl_connection_interface, uint16_t connection_handle)
- : le_acl_connection_interface_(le_acl_connection_interface), connection_handle_(connection_handle) {}
- ~LeAclConnectionTracker() {
- ASSERT(queued_callbacks_.empty());
- }
- void RegisterCallbacks(LeConnectionManagementCallbacks* callbacks, os::Handler* handler) {
- client_handler_ = handler;
- client_callbacks_ = callbacks;
- while (!queued_callbacks_.empty()) {
- auto iter = queued_callbacks_.begin();
- handler->Post(std::move(*iter));
- queued_callbacks_.erase(iter);
- }
- }
-
-#define SAVE_OR_CALL(f, ...) \
- if (client_handler_ == nullptr) { \
- queued_callbacks_.emplace_back( \
- common::BindOnce(&LeConnectionManagementCallbacks::f, common::Unretained(this), __VA_ARGS__)); \
- } else { \
- client_handler_->Post( \
- common::BindOnce(&LeConnectionManagementCallbacks::f, common::Unretained(client_callbacks_), __VA_ARGS__)); \
- }
-
- void OnConnectionUpdate(
- hci::ErrorCode hci_status, uint16_t conn_interval, uint16_t conn_latency, uint16_t supervision_timeout) override {
- SAVE_OR_CALL(OnConnectionUpdate, hci_status, conn_interval, conn_latency, supervision_timeout)
- }
-
- void OnDataLengthChange(uint16_t tx_octets, uint16_t tx_time, uint16_t rx_octets, uint16_t rx_time) override {
- SAVE_OR_CALL(OnDataLengthChange, tx_octets, tx_time, rx_octets, rx_time)
- }
-
- void OnReadRemoteVersionInformationComplete(
- hci::ErrorCode hci_status, uint8_t lmp_version, uint16_t manufacturer_name, uint16_t sub_version) {
- bluetooth::os::LogMetricRemoteVersionInfo(
- connection_handle_, static_cast<uint8_t>(hci_status), lmp_version, manufacturer_name, sub_version);
- SAVE_OR_CALL(OnReadRemoteVersionInformationComplete, hci_status, lmp_version, manufacturer_name, sub_version);
- }
- void OnPhyUpdate(hci::ErrorCode hci_status, uint8_t tx_phy, uint8_t rx_phy) override {
- SAVE_OR_CALL(OnPhyUpdate, hci_status, tx_phy, rx_phy);
- }
- void OnLocalAddressUpdate(AddressWithType address_with_type) override {
- SAVE_OR_CALL(OnLocalAddressUpdate, address_with_type);
- }
-
- void OnDisconnection(ErrorCode reason) override {
- SAVE_OR_CALL(OnDisconnection, reason);
- }
-#undef SAVE_OR_CALL
-
- LeAclConnectionInterface* le_acl_connection_interface_;
- os::Handler* client_handler_ = nullptr;
- LeConnectionManagementCallbacks* client_callbacks_ = nullptr;
- std::list<common::OnceClosure> queued_callbacks_;
- uint16_t connection_handle_;
-};
-
-struct LeAclConnection::impl {
- impl(LeAclConnectionInterface* le_acl_connection_interface, std::shared_ptr<Queue> queue, uint16_t connection_handle)
- : queue_(std::move(queue)), tracker(le_acl_connection_interface, connection_handle) {}
- LeConnectionManagementCallbacks* GetEventCallbacks() {
- ASSERT(!callbacks_given_);
- callbacks_given_ = true;
- return &tracker;
- }
-
- bool callbacks_given_{false};
- std::shared_ptr<Queue> queue_;
- LeAclConnectionTracker tracker;
-};
-
-LeAclConnection::LeAclConnection()
- : AclConnection(), local_address_(Address::kEmpty, AddressType::PUBLIC_DEVICE_ADDRESS),
- remote_address_(Address::kEmpty, AddressType::PUBLIC_DEVICE_ADDRESS) {}
-
-LeAclConnection::LeAclConnection(
- std::shared_ptr<Queue> queue,
- LeAclConnectionInterface* le_acl_connection_interface,
- uint16_t handle,
- AddressWithType local_address,
- AddressWithType remote_address,
- Role role)
- : AclConnection(queue->GetUpEnd(), handle),
- local_address_(local_address),
- remote_address_(remote_address),
- role_(role) {
- pimpl_ = new LeAclConnection::impl(le_acl_connection_interface, std::move(queue), handle);
-}
-
-LeAclConnection::~LeAclConnection() {
- delete pimpl_;
-}
-
-void LeAclConnection::RegisterCallbacks(LeConnectionManagementCallbacks* callbacks, os::Handler* handler) {
- return pimpl_->tracker.RegisterCallbacks(callbacks, handler);
-}
-
-void LeAclConnection::Disconnect(DisconnectReason reason) {
- pimpl_->tracker.le_acl_connection_interface_->EnqueueCommand(
- DisconnectBuilder::Create(handle_, reason),
- pimpl_->tracker.client_handler_->BindOnce([](CommandStatusView status) {
- ASSERT(status.IsValid());
- ASSERT(status.GetCommandOpCode() == OpCode::DISCONNECT);
- auto disconnect_status = DisconnectStatusView::Create(status);
- ASSERT(disconnect_status.IsValid());
- auto error_code = disconnect_status.GetStatus();
- if (error_code != ErrorCode::SUCCESS) {
- LOG_INFO("Disconnect status %s", ErrorCodeText(error_code).c_str());
- }
- }));
-}
-
-LeConnectionManagementCallbacks* LeAclConnection::GetEventCallbacks() {
- return pimpl_->GetEventCallbacks();
-}
-
-bool LeAclConnection::LeConnectionUpdate(uint16_t conn_interval_min, uint16_t conn_interval_max, uint16_t conn_latency,
- uint16_t supervision_timeout, uint16_t min_ce_length, uint16_t max_ce_length) {
- if (!check_connection_parameters(conn_interval_min, conn_interval_max, conn_latency, supervision_timeout)) {
- LOG_ERROR("Invalid parameter");
- return false;
- }
- pimpl_->tracker.le_acl_connection_interface_->EnqueueCommand(
- LeConnectionUpdateBuilder::Create(handle_, conn_interval_min, conn_interval_max, conn_latency,
- supervision_timeout, min_ce_length, max_ce_length),
- pimpl_->tracker.client_handler_->BindOnce([](CommandStatusView status) {
- ASSERT(status.IsValid());
- ASSERT(status.GetCommandOpCode() == OpCode::LE_CONNECTION_UPDATE);
- }));
- return true;
-}
-
-bool LeAclConnection::ReadRemoteVersionInformation() {
- pimpl_->tracker.le_acl_connection_interface_->EnqueueCommand(
- ReadRemoteVersionInformationBuilder::Create(handle_),
- pimpl_->tracker.client_handler_->BindOnce([](CommandStatusView status) {
- ASSERT(status.IsValid());
- ASSERT(status.GetCommandOpCode() == OpCode::READ_REMOTE_VERSION_INFORMATION);
- }));
- return true;
-}
-
-bool LeAclConnection::check_connection_parameters(
- uint16_t conn_interval_min, uint16_t conn_interval_max, uint16_t conn_latency, uint16_t supervision_timeout) {
- if (conn_interval_min < 0x0006 || conn_interval_min > 0x0C80 || conn_interval_max < 0x0006 ||
- conn_interval_max > 0x0C80 || conn_latency > 0x01F3 || supervision_timeout < 0x000A ||
- supervision_timeout > 0x0C80) {
- LOG_ERROR("Invalid parameter");
- return false;
- }
- // The Maximum interval in milliseconds will be conn_interval_max * 1.25 ms
- // The Timeout in milliseconds will be expected_supervision_timeout * 10 ms
- // The Timeout in milliseconds shall be larger than (1 + Latency) * Interval_Max * 2, where Interval_Max is given in
- // milliseconds.
- uint32_t supervision_timeout_min = (uint32_t)(1 + conn_latency) * conn_interval_max * 2 + 1;
- if (supervision_timeout * 8 < supervision_timeout_min || conn_interval_max < conn_interval_min) {
- LOG_ERROR("Invalid parameter");
- return false;
- }
-
- return true;
-}
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/le_acl_connection.h b/gd/hci/acl_manager/le_acl_connection.h
deleted file mode 100644
index 90cc471c6..000000000
--- a/gd/hci/acl_manager/le_acl_connection.h
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "hci/acl_manager/acl_connection.h"
-#include "hci/acl_manager/le_connection_management_callbacks.h"
-#include "hci/address_with_type.h"
-#include "hci/hci_packets.h"
-#include "hci/le_acl_connection_interface.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-class LeAclConnection : public AclConnection {
- public:
- LeAclConnection();
- LeAclConnection(
- std::shared_ptr<Queue> queue,
- LeAclConnectionInterface* le_acl_connection_interface,
- uint16_t handle,
- AddressWithType local_address,
- AddressWithType remote_address,
- Role role);
- ~LeAclConnection();
-
- virtual AddressWithType GetLocalAddress() const {
- return local_address_;
- }
-
- virtual void UpdateLocalAddress(AddressWithType address) {
- local_address_ = address;
- }
-
- virtual AddressWithType GetRemoteAddress() const {
- return remote_address_;
- }
-
- virtual Role GetRole() const {
- return role_;
- }
-
- virtual void RegisterCallbacks(LeConnectionManagementCallbacks* callbacks, os::Handler* handler);
- virtual void Disconnect(DisconnectReason reason);
-
- virtual bool LeConnectionUpdate(uint16_t conn_interval_min, uint16_t conn_interval_max, uint16_t conn_latency,
- uint16_t supervision_timeout, uint16_t min_ce_length, uint16_t max_ce_length);
-
- virtual bool ReadRemoteVersionInformation() override;
-
- // TODO implement LeRemoteConnectionParameterRequestReply, LeRemoteConnectionParameterRequestNegativeReply
-
- // Called once before passing the connection to the client
- virtual LeConnectionManagementCallbacks* GetEventCallbacks();
-
- private:
- virtual bool check_connection_parameters(
- uint16_t conn_interval_min,
- uint16_t conn_interval_max,
- uint16_t expected_conn_latency,
- uint16_t expected_supervision_timeout);
- struct impl;
- struct impl* pimpl_ = nullptr;
- AddressWithType local_address_;
- AddressWithType remote_address_;
- Role role_;
- DISALLOW_COPY_AND_ASSIGN(LeAclConnection);
-};
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/le_connection_callbacks.h b/gd/hci/acl_manager/le_connection_callbacks.h
deleted file mode 100644
index b79f16cba..000000000
--- a/gd/hci/acl_manager/le_connection_callbacks.h
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <memory>
-#include "hci/acl_manager/le_acl_connection.h"
-#include "hci/address_with_type.h"
-#include "hci/hci_packets.h"
-#include "os/handler.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-class LeConnectionCallbacks {
- public:
- virtual ~LeConnectionCallbacks() = default;
- // Invoked when controller sends Connection Complete event with Success error code
- // AddressWithType is always equal to the object used in AclManager#CreateLeConnection
- virtual void OnLeConnectSuccess(AddressWithType, std::unique_ptr<LeAclConnection>) = 0;
- // Invoked when controller sends Connection Complete event with non-Success error code
- virtual void OnLeConnectFail(AddressWithType, ErrorCode reason) = 0;
-};
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/le_connection_management_callbacks.h b/gd/hci/acl_manager/le_connection_management_callbacks.h
deleted file mode 100644
index 59d38a698..000000000
--- a/gd/hci/acl_manager/le_connection_management_callbacks.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <memory>
-
-#include "hci/address_with_type.h"
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-class LeConnectionManagementCallbacks {
- public:
- virtual ~LeConnectionManagementCallbacks() = default;
- virtual void OnConnectionUpdate(
- hci::ErrorCode hci_status,
- uint16_t connection_interval,
- uint16_t connection_latency,
- uint16_t supervision_timeout) = 0;
- virtual void OnDataLengthChange(uint16_t tx_octets, uint16_t tx_time, uint16_t rx_octets, uint16_t rx_time) = 0;
- virtual void OnDisconnection(ErrorCode reason) = 0;
- virtual void OnReadRemoteVersionInformationComplete(
- hci::ErrorCode hci_status, uint8_t lmp_version, uint16_t manufacturer_name, uint16_t sub_version) = 0;
- virtual void OnPhyUpdate(hci::ErrorCode hci_status, uint8_t tx_phy, uint8_t rx_phy) = 0;
- virtual void OnLocalAddressUpdate(AddressWithType address_with_type) = 0;
-};
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/le_impl.h b/gd/hci/acl_manager/le_impl.h
deleted file mode 100644
index e1cc7cd88..000000000
--- a/gd/hci/acl_manager/le_impl.h
+++ /dev/null
@@ -1,707 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "common/bind.h"
-#include "crypto_toolbox/crypto_toolbox.h"
-#include "hci/acl_manager/assembler.h"
-#include "hci/acl_manager/round_robin_scheduler.h"
-#include "hci/le_address_manager.h"
-#include "os/alarm.h"
-#include "os/rand.h"
-
-using bluetooth::crypto_toolbox::Octet16;
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-using common::BindOnce;
-
-constexpr uint16_t kScanIntervalFast = 0x0060;
-constexpr uint16_t kScanWindowFast = 0x0030;
-constexpr uint16_t kScanIntervalSlow = 0x0800;
-constexpr uint16_t kScanWindowSlow = 0x0030;
-constexpr std::chrono::milliseconds kCreateConnectionTimeoutMs = std::chrono::milliseconds(30 * 1000);
-
-struct le_acl_connection {
- le_acl_connection(AddressWithType remote_address, AclConnection::QueueDownEnd* queue_down_end, os::Handler* handler)
- : assembler_(remote_address, queue_down_end, handler), remote_address_(remote_address) {}
- ~le_acl_connection() = default;
- struct acl_manager::assembler assembler_;
- AddressWithType remote_address_;
- LeConnectionManagementCallbacks* le_connection_management_callbacks_ = nullptr;
-};
-
-struct le_impl : public bluetooth::hci::LeAddressManagerCallback {
- le_impl(
- HciLayer* hci_layer,
- Controller* controller,
- os::Handler* handler,
- RoundRobinScheduler* round_robin_scheduler,
- bool crash_on_unknown_handle)
- : hci_layer_(hci_layer),
- controller_(controller),
- round_robin_scheduler_(round_robin_scheduler),
- crash_on_unknown_handle_(crash_on_unknown_handle) {
- hci_layer_ = hci_layer;
- controller_ = controller;
- handler_ = handler;
- le_acl_connection_interface_ = hci_layer_->GetLeAclConnectionInterface(
- handler_->BindOn(this, &le_impl::on_le_event),
- handler_->BindOn(this, &le_impl::on_le_disconnect),
- handler_->BindOn(this, &le_impl::on_le_read_remote_version_information));
- le_address_manager_ = new LeAddressManager(
- common::Bind(&le_impl::enqueue_command, common::Unretained(this)),
- handler_,
- controller->GetMacAddress(),
- controller->GetLeConnectListSize(),
- controller->GetLeResolvingListSize());
- }
-
- ~le_impl() {
- for (auto subevent_code : LeConnectionManagementEvents) {
- hci_layer_->UnregisterLeEventHandler(subevent_code);
- }
- if (address_manager_registered) {
- le_address_manager_->Unregister(this);
- }
- delete le_address_manager_;
- le_acl_connections_.clear();
- }
-
- void on_le_event(LeMetaEventView event_packet) {
- SubeventCode code = event_packet.GetSubeventCode();
- switch (code) {
- case SubeventCode::CONNECTION_COMPLETE:
- on_le_connection_complete(event_packet);
- break;
- case SubeventCode::ENHANCED_CONNECTION_COMPLETE:
- on_le_enhanced_connection_complete(event_packet);
- break;
- case SubeventCode::CONNECTION_UPDATE_COMPLETE:
- on_le_connection_update_complete(event_packet);
- break;
- case SubeventCode::PHY_UPDATE_COMPLETE:
- on_le_phy_update_complete(event_packet);
- break;
- case SubeventCode::DATA_LENGTH_CHANGE:
- on_data_length_change(event_packet);
- break;
- case SubeventCode::REMOTE_CONNECTION_PARAMETER_REQUEST:
- on_remote_connection_parameter_request(event_packet);
- break;
- default:
- LOG_ALWAYS_FATAL("Unhandled event code %s", SubeventCodeText(code).c_str());
- }
- }
-
- LeConnectionManagementCallbacks* get_callbacks(uint16_t handle) {
- auto connection = le_acl_connections_.find(handle);
- if (connection == le_acl_connections_.end()) {
- return nullptr;
- }
- return connection->second.le_connection_management_callbacks_;
- }
-
- void on_le_disconnect(uint16_t handle, ErrorCode reason) {
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- return;
- }
- round_robin_scheduler_->Unregister(handle);
- callbacks->OnDisconnection(reason);
- le_acl_connections_.erase(handle);
- }
-
- void on_common_le_connection_complete(AddressWithType address_with_type) {
- auto connecting_addr_with_type = connecting_le_.find(address_with_type);
- if (connecting_addr_with_type == connecting_le_.end()) {
- LOG_WARN("No prior connection request for %s", address_with_type.ToString().c_str());
- } else {
- connecting_le_.erase(connecting_addr_with_type);
- }
- if (create_connection_timeout_alarms_.find(address_with_type) != create_connection_timeout_alarms_.end()) {
- create_connection_timeout_alarms_.at(address_with_type).Cancel();
- create_connection_timeout_alarms_.erase(address_with_type);
- }
- }
-
- void on_le_connection_complete(LeMetaEventView packet) {
- LeConnectionCompleteView connection_complete = LeConnectionCompleteView::Create(packet);
- ASSERT(connection_complete.IsValid());
- auto status = connection_complete.GetStatus();
- auto address = connection_complete.GetPeerAddress();
- auto peer_address_type = connection_complete.GetPeerAddressType();
- // TODO: find out which address and type was used to initiate the connection
- AddressWithType remote_address(address, peer_address_type);
- AddressWithType local_address = le_address_manager_->GetCurrentAddress();
- on_common_le_connection_complete(remote_address);
- if (status == ErrorCode::UNKNOWN_CONNECTION && pause_connection) {
- // connection canceled by LeAddressManager.OnPause(), will auto reconnect by LeAddressManager.OnResume()
- return;
- } else {
- canceled_connections_.erase(remote_address);
- ready_to_unregister = true;
- remove_device_from_connect_list(remote_address);
- }
-
- if (le_client_handler_ == nullptr) {
- LOG_ERROR("No callbacks to call");
- return;
- }
-
- if (status != ErrorCode::SUCCESS) {
- le_client_handler_->Post(common::BindOnce(&LeConnectionCallbacks::OnLeConnectFail,
- common::Unretained(le_client_callbacks_), remote_address, status));
- return;
- }
-
- uint16_t conn_interval = connection_complete.GetConnInterval();
- uint16_t conn_latency = connection_complete.GetConnLatency();
- uint16_t supervision_timeout = connection_complete.GetSupervisionTimeout();
- if (!check_connection_parameters(conn_interval, conn_interval, conn_latency, supervision_timeout)) {
- LOG_ERROR("Receive connection complete with invalid connection parameters");
- return;
- }
-
- auto role = connection_complete.GetRole();
- uint16_t handle = connection_complete.GetConnectionHandle();
- auto queue = std::make_shared<AclConnection::Queue>(10);
- auto emplace_pair = le_acl_connections_.emplace(
- std::piecewise_construct,
- std::forward_as_tuple(handle),
- std::forward_as_tuple(remote_address, queue->GetDownEnd(), handler_));
- ASSERT(emplace_pair.second); // Make sure the connection is unique
- auto& connection_proxy = emplace_pair.first->second;
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::LE, handle, queue);
- std::unique_ptr<LeAclConnection> connection(new LeAclConnection(
- std::move(queue), le_acl_connection_interface_, handle, local_address, remote_address, role));
- connection_proxy.le_connection_management_callbacks_ = connection->GetEventCallbacks();
- le_client_handler_->Post(common::BindOnce(&LeConnectionCallbacks::OnLeConnectSuccess,
- common::Unretained(le_client_callbacks_), remote_address,
- std::move(connection)));
- }
-
- void on_le_enhanced_connection_complete(LeMetaEventView packet) {
- LeEnhancedConnectionCompleteView connection_complete = LeEnhancedConnectionCompleteView::Create(packet);
- ASSERT(connection_complete.IsValid());
- auto status = connection_complete.GetStatus();
- auto address = connection_complete.GetPeerAddress();
- auto peer_address_type = connection_complete.GetPeerAddressType();
- auto peer_resolvable_address = connection_complete.GetPeerResolvablePrivateAddress();
- AddressWithType remote_address(address, peer_address_type);
- if (!peer_resolvable_address.IsEmpty()) {
- remote_address = AddressWithType(peer_resolvable_address, AddressType::RANDOM_DEVICE_ADDRESS);
- }
- on_common_le_connection_complete(remote_address);
- if (status == ErrorCode::UNKNOWN_CONNECTION && pause_connection) {
- // connection canceled by LeAddressManager.OnPause(), will auto reconnect by LeAddressManager.OnResume()
- return;
- } else {
- canceled_connections_.erase(remote_address);
- ready_to_unregister = true;
- remove_device_from_connect_list(remote_address);
- }
-
- if (le_client_handler_ == nullptr) {
- LOG_ERROR("No callbacks to call");
- return;
- }
-
- if (status != ErrorCode::SUCCESS) {
- le_client_handler_->Post(common::BindOnce(&LeConnectionCallbacks::OnLeConnectFail,
- common::Unretained(le_client_callbacks_), remote_address, status));
- return;
- }
-
- auto role = connection_complete.GetRole();
- AddressWithType local_address;
- if (role == hci::Role::CENTRAL) {
- local_address = le_address_manager_->GetCurrentAddress();
- } else {
- // when accepting connection, we must obtain the address from the advertiser.
- // When we receive "set terminated event", we associate connection handle with advertiser address
- local_address = AddressWithType{};
- }
-
- uint16_t conn_interval = connection_complete.GetConnInterval();
- uint16_t conn_latency = connection_complete.GetConnLatency();
- uint16_t supervision_timeout = connection_complete.GetSupervisionTimeout();
- if (!check_connection_parameters(conn_interval, conn_interval, conn_latency, supervision_timeout)) {
- LOG_ERROR("Receive enhenced connection complete with invalid connection parameters");
- return;
- }
- uint16_t handle = connection_complete.GetConnectionHandle();
- auto queue = std::make_shared<AclConnection::Queue>(10);
- auto emplace_pair = le_acl_connections_.emplace(
- std::piecewise_construct,
- std::forward_as_tuple(handle),
- std::forward_as_tuple(remote_address, queue->GetDownEnd(), handler_));
- ASSERT(emplace_pair.second); // Make sure it's not a duplicate
- auto& connection_proxy = emplace_pair.first->second;
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::LE, handle, queue);
- std::unique_ptr<LeAclConnection> connection(new LeAclConnection(
- std::move(queue), le_acl_connection_interface_, handle, local_address, remote_address, role));
- connection_proxy.le_connection_management_callbacks_ = connection->GetEventCallbacks();
- le_client_handler_->Post(common::BindOnce(&LeConnectionCallbacks::OnLeConnectSuccess,
- common::Unretained(le_client_callbacks_), remote_address,
- std::move(connection)));
- }
-
- void on_le_connection_update_complete(LeMetaEventView view) {
- auto complete_view = LeConnectionUpdateCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_le_connection_update_complete with invalid packet");
- return;
- }
- auto handle = complete_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Can't find connection 0x%hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnConnectionUpdate(
- complete_view.GetStatus(),
- complete_view.GetConnInterval(),
- complete_view.GetConnLatency(),
- complete_view.GetSupervisionTimeout());
- }
-
- void on_le_phy_update_complete(LeMetaEventView view) {
- auto complete_view = LePhyUpdateCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received on_le_phy_update_complete with invalid packet");
- return;
- }
- auto handle = complete_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Can't find connection 0x%hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnPhyUpdate(complete_view.GetStatus(), complete_view.GetTxPhy(), complete_view.GetRxPhy());
- }
-
- void on_le_read_remote_version_information(
- hci::ErrorCode hci_status, uint16_t handle, uint8_t version, uint16_t manufacturer_name, uint16_t sub_version) {
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_INFO("No le connection registered for 0x%hx", handle);
- return;
- }
- callbacks->OnReadRemoteVersionInformationComplete(hci_status, version, manufacturer_name, sub_version);
- }
-
- void enqueue_command(std::unique_ptr<CommandBuilder> command_packet) {
- hci_layer_->EnqueueCommand(
- std::move(command_packet),
- handler_->BindOnce(&LeAddressManager::OnCommandComplete, common::Unretained(le_address_manager_)));
- }
-
- void on_data_length_change(LeMetaEventView view) {
- auto data_length_view = LeDataLengthChangeView::Create(view);
- if (!data_length_view.IsValid()) {
- LOG_ERROR("Invalid packet");
- return;
- }
- auto handle = data_length_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Can't find connection 0x%hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnDataLengthChange(
- data_length_view.GetMaxTxOctets(),
- data_length_view.GetMaxTxTime(),
- data_length_view.GetMaxRxOctets(),
- data_length_view.GetMaxRxTime());
- }
-
- void on_remote_connection_parameter_request(LeMetaEventView view) {
- auto request_view = LeRemoteConnectionParameterRequestView::Create(view);
- if (!request_view.IsValid()) {
- LOG_ERROR("Invalid packet");
- return;
- }
-
- auto handle = request_view.GetConnectionHandle();
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Can't find connection 0x%hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- // TODO: this is blindly accepting any parameters, just so we don't hang connection
- // have proper parameter negotiation
- le_acl_connection_interface_->EnqueueCommand(
- LeRemoteConnectionParameterRequestReplyBuilder::Create(
- handle,
- request_view.GetIntervalMin(),
- request_view.GetIntervalMax(),
- request_view.GetLatency(),
- request_view.GetTimeout(),
- 0,
- 0),
- handler_->BindOnce([](CommandCompleteView status) {}));
- }
-
- void add_device_to_connect_list(AddressWithType address_with_type) {
- AddressType address_type = address_with_type.GetAddressType();
- if (!address_manager_registered) {
- le_address_manager_->Register(this);
- address_manager_registered = true;
- }
- pause_connection = true;
- switch (address_type) {
- case AddressType::PUBLIC_DEVICE_ADDRESS:
- case AddressType::PUBLIC_IDENTITY_ADDRESS: {
- le_address_manager_->AddDeviceToConnectList(ConnectListAddressType::PUBLIC, address_with_type.GetAddress());
- } break;
- case AddressType::RANDOM_DEVICE_ADDRESS:
- case AddressType::RANDOM_IDENTITY_ADDRESS: {
- le_address_manager_->AddDeviceToConnectList(ConnectListAddressType::RANDOM, address_with_type.GetAddress());
- }
- }
- }
-
- void add_device_to_resolving_list(
- AddressWithType address_with_type,
- const std::array<uint8_t, 16>& peer_irk,
- const std::array<uint8_t, 16>& local_irk) {
- AddressType address_type = address_with_type.GetAddressType();
- if (!address_manager_registered) {
- le_address_manager_->Register(this);
- address_manager_registered = true;
- }
- pause_connection = true;
- switch (address_type) {
- case AddressType::PUBLIC_DEVICE_ADDRESS:
- case AddressType::PUBLIC_IDENTITY_ADDRESS: {
- le_address_manager_->AddDeviceToResolvingList(
- PeerAddressType::PUBLIC_DEVICE_OR_IDENTITY_ADDRESS, address_with_type.GetAddress(), peer_irk, local_irk);
- } break;
- case AddressType::RANDOM_DEVICE_ADDRESS:
- case AddressType::RANDOM_IDENTITY_ADDRESS: {
- le_address_manager_->AddDeviceToResolvingList(
- PeerAddressType::RANDOM_DEVICE_OR_IDENTITY_ADDRESS, address_with_type.GetAddress(), peer_irk, local_irk);
- }
- }
- }
-
- void create_le_connection(AddressWithType address_with_type, bool add_to_connect_list, bool is_direct) {
- // TODO: Configure default LE connection parameters?
- if (add_to_connect_list) {
- add_device_to_connect_list(address_with_type);
- if (is_direct) {
- direct_connections_.insert(address_with_type);
- if (create_connection_timeout_alarms_.find(address_with_type) == create_connection_timeout_alarms_.end()) {
- create_connection_timeout_alarms_.emplace(
- std::piecewise_construct,
- std::forward_as_tuple(address_with_type.GetAddress(), address_with_type.GetAddressType()),
- std::forward_as_tuple(handler_));
- create_connection_timeout_alarms_.at(address_with_type)
- .Schedule(
- common::BindOnce(&le_impl::on_create_connection_timeout, common::Unretained(this), address_with_type),
- kCreateConnectionTimeoutMs);
- }
- }
- }
-
- if (!address_manager_registered) {
- auto policy = le_address_manager_->Register(this);
- address_manager_registered = true;
-
- // Pause connection, wait for set random address complete
- if (policy == LeAddressManager::AddressPolicy::USE_RESOLVABLE_ADDRESS ||
- policy == LeAddressManager::AddressPolicy::USE_NON_RESOLVABLE_ADDRESS) {
- pause_connection = true;
- }
- }
-
- if (pause_connection) {
- canceled_connections_.insert(address_with_type);
- return;
- }
- if (le_client_callbacks_ == nullptr) {
- LOG_ERROR("No callbacks to call");
- return;
- }
-
- uint16_t le_scan_interval = kScanIntervalSlow;
- uint16_t le_scan_window = kScanWindowSlow;
- // If there is any direct connection in the connection list, use the fast parameter
- if (!direct_connections_.empty()) {
- le_scan_interval = kScanIntervalFast;
- le_scan_window = kScanWindowFast;
- }
- InitiatorFilterPolicy initiator_filter_policy = InitiatorFilterPolicy::USE_CONNECT_LIST;
- OwnAddressType own_address_type =
- static_cast<OwnAddressType>(le_address_manager_->GetCurrentAddress().GetAddressType());
- uint16_t conn_interval_min = 0x0018;
- uint16_t conn_interval_max = 0x0028;
- uint16_t conn_latency = 0x0000;
- uint16_t supervision_timeout = 0x001f4;
- ASSERT(check_connection_parameters(conn_interval_min, conn_interval_max, conn_latency, supervision_timeout));
-
- connecting_le_.insert(address_with_type);
-
- if (initiator_filter_policy == InitiatorFilterPolicy::USE_CONNECT_LIST) {
- address_with_type = AddressWithType();
- }
-
- if (controller_->IsSupported(OpCode::LE_EXTENDED_CREATE_CONNECTION)) {
- LeCreateConnPhyScanParameters tmp;
- tmp.scan_interval_ = le_scan_interval;
- tmp.scan_window_ = le_scan_window;
- tmp.conn_interval_min_ = conn_interval_min;
- tmp.conn_interval_max_ = conn_interval_max;
- tmp.conn_latency_ = conn_latency;
- tmp.supervision_timeout_ = supervision_timeout;
- tmp.min_ce_length_ = 0x00;
- tmp.max_ce_length_ = 0x00;
-
- le_acl_connection_interface_->EnqueueCommand(
- LeExtendedCreateConnectionBuilder::Create(initiator_filter_policy, own_address_type,
- address_with_type.GetAddressType(), address_with_type.GetAddress(),
- 0x01 /* 1M PHY ONLY */, {tmp}),
- handler_->BindOnce([](CommandStatusView status) {
- ASSERT(status.IsValid());
- ASSERT(status.GetCommandOpCode() == OpCode::LE_EXTENDED_CREATE_CONNECTION);
- }));
- } else {
- le_acl_connection_interface_->EnqueueCommand(
- LeCreateConnectionBuilder::Create(le_scan_interval, le_scan_window, initiator_filter_policy,
- address_with_type.GetAddressType(), address_with_type.GetAddress(),
- own_address_type, conn_interval_min, conn_interval_max, conn_latency,
- supervision_timeout, kMinimumCeLength, kMaximumCeLength),
- handler_->BindOnce([](CommandStatusView status) {
- ASSERT(status.IsValid());
- ASSERT(status.GetCommandOpCode() == OpCode::LE_CREATE_CONNECTION);
- }));
- }
- }
-
- void on_create_connection_timeout(AddressWithType address_with_type) {
- LOG_INFO("on_create_connection_timeout, address: %s", address_with_type.ToString().c_str());
- if (create_connection_timeout_alarms_.find(address_with_type) != create_connection_timeout_alarms_.end()) {
- create_connection_timeout_alarms_.at(address_with_type).Cancel();
- create_connection_timeout_alarms_.erase(address_with_type);
- cancel_connect(address_with_type);
- }
- }
-
- void cancel_connect(AddressWithType address_with_type) {
- // the connection will be canceled by LeAddressManager.OnPause()
- remove_device_from_connect_list(address_with_type);
- }
-
- void set_le_suggested_default_data_parameters(uint16_t length, uint16_t time) {
- auto packet = LeWriteSuggestedDefaultDataLengthBuilder::Create(length, time);
- le_acl_connection_interface_->EnqueueCommand(
- std::move(packet), handler_->BindOnce([](CommandCompleteView complete) {}));
- }
-
- void remove_device_from_connect_list(AddressWithType address_with_type) {
- AddressType address_type = address_with_type.GetAddressType();
- direct_connections_.erase(address_with_type);
- if (!address_manager_registered) {
- le_address_manager_->Register(this);
- address_manager_registered = true;
- }
- pause_connection = true;
- switch (address_type) {
- case AddressType::PUBLIC_DEVICE_ADDRESS:
- case AddressType::PUBLIC_IDENTITY_ADDRESS: {
- le_address_manager_->RemoveDeviceFromConnectList(
- ConnectListAddressType::PUBLIC, address_with_type.GetAddress());
- } break;
- case AddressType::RANDOM_DEVICE_ADDRESS:
- case AddressType::RANDOM_IDENTITY_ADDRESS: {
- le_address_manager_->RemoveDeviceFromConnectList(
- ConnectListAddressType::RANDOM, address_with_type.GetAddress());
- }
- }
- }
-
- void remove_device_from_resolving_list(AddressWithType address_with_type) {
- AddressType address_type = address_with_type.GetAddressType();
- if (!address_manager_registered) {
- le_address_manager_->Register(this);
- address_manager_registered = true;
- }
- pause_connection = true;
- switch (address_type) {
- case AddressType::PUBLIC_DEVICE_ADDRESS:
- case AddressType::PUBLIC_IDENTITY_ADDRESS: {
- le_address_manager_->RemoveDeviceFromResolvingList(
- PeerAddressType::PUBLIC_DEVICE_OR_IDENTITY_ADDRESS, address_with_type.GetAddress());
- } break;
- case AddressType::RANDOM_DEVICE_ADDRESS:
- case AddressType::RANDOM_IDENTITY_ADDRESS: {
- le_address_manager_->RemoveDeviceFromResolvingList(
- PeerAddressType::RANDOM_DEVICE_OR_IDENTITY_ADDRESS, address_with_type.GetAddress());
- }
- }
- }
-
- void set_privacy_policy_for_initiator_address(
- LeAddressManager::AddressPolicy address_policy,
- AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time) {
- le_address_manager_->SetPrivacyPolicyForInitiatorAddress(
- address_policy, fixed_address, rotation_irk, minimum_rotation_time, maximum_rotation_time);
- }
-
- // TODO(jpawlowski): remove once we have config file abstraction in cert tests
- void set_privacy_policy_for_initiator_address_for_test(
- LeAddressManager::AddressPolicy address_policy,
- AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time) {
- le_address_manager_->SetPrivacyPolicyForInitiatorAddressForTest(
- address_policy, fixed_address, rotation_irk, minimum_rotation_time, maximum_rotation_time);
- }
-
- void handle_register_le_callbacks(LeConnectionCallbacks* callbacks, os::Handler* handler) {
- ASSERT(le_client_callbacks_ == nullptr);
- ASSERT(le_client_handler_ == nullptr);
- le_client_callbacks_ = callbacks;
- le_client_handler_ = handler;
- }
-
- void handle_unregister_le_callbacks(LeConnectionCallbacks* callbacks, std::promise<void> promise) {
- ASSERT_LOG(le_client_callbacks_ == callbacks, "Registered le callback entity is different then unregister request");
- le_client_callbacks_ = nullptr;
- le_client_handler_ = nullptr;
- promise.set_value();
- }
-
- bool check_connection_parameters(
- uint16_t conn_interval_min, uint16_t conn_interval_max, uint16_t conn_latency, uint16_t supervision_timeout) {
- if (conn_interval_min < 0x0006 || conn_interval_min > 0x0C80 || conn_interval_max < 0x0006 ||
- conn_interval_max > 0x0C80 || conn_latency > 0x01F3 || supervision_timeout < 0x000A ||
- supervision_timeout > 0x0C80) {
- LOG_ERROR("Invalid parameter");
- return false;
- }
-
- // The Maximum interval in milliseconds will be conn_interval_max * 1.25 ms
- // The Timeout in milliseconds will be expected_supervision_timeout * 10 ms
- // The Timeout in milliseconds shall be larger than (1 + Latency) * Interval_Max * 2, where Interval_Max is given in
- // milliseconds.
- uint32_t supervision_timeout_min = (uint32_t)(1 + conn_latency) * conn_interval_max * 2 + 1;
- if (supervision_timeout * 8 < supervision_timeout_min || conn_interval_max < conn_interval_min) {
- LOG_ERROR("Invalid parameter");
- return false;
- }
-
- return true;
- }
-
- void OnPause() override {
- pause_connection = true;
- if (connecting_le_.empty()) {
- le_address_manager_->AckPause(this);
- return;
- }
- canceled_connections_ = connecting_le_;
- le_acl_connection_interface_->EnqueueCommand(
- LeCreateConnectionCancelBuilder::Create(),
- handler_->BindOnce(&le_impl::on_create_connection_cancel_complete, common::Unretained(this)));
- le_address_manager_->AckPause(this);
- }
-
- void on_create_connection_cancel_complete(CommandCompleteView view) {
- auto complete_view = LeCreateConnectionCancelCompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- auto status = complete_view.GetStatus();
- std::string error_code = ErrorCodeText(status);
- LOG_WARN("Received on_create_connection_cancel_complete with error code %s", error_code.c_str());
- }
- }
-
- void check_for_unregister() {
- if (le_acl_connections_.empty() && connecting_le_.empty() && canceled_connections_.empty() &&
- address_manager_registered && ready_to_unregister) {
- le_address_manager_->Unregister(this);
- address_manager_registered = false;
- pause_connection = false;
- ready_to_unregister = false;
- }
- }
-
- void OnResume() override {
- pause_connection = false;
- if (!canceled_connections_.empty()) {
- create_le_connection(*canceled_connections_.begin(), false, false);
- }
- canceled_connections_.clear();
- le_address_manager_->AckResume(this);
- check_for_unregister();
- }
-
- uint16_t HACK_get_handle(Address address) {
- for (auto it = le_acl_connections_.begin(); it != le_acl_connections_.end(); it++) {
- if (it->second.remote_address_.GetAddress() == address) {
- return it->first;
- }
- }
- return 0xFFFF;
- }
-
- void UpdateLocalAddress(uint16_t handle, hci::AddressWithType address_with_type) {
- auto callbacks = get_callbacks(handle);
- if (callbacks == nullptr) {
- LOG_WARN("Can't find connection 0x%hx", handle);
- ASSERT(!crash_on_unknown_handle_);
- return;
- }
- callbacks->OnLocalAddressUpdate(address_with_type);
- }
-
- static constexpr uint16_t kMinimumCeLength = 0x0002;
- static constexpr uint16_t kMaximumCeLength = 0x0C00;
- HciLayer* hci_layer_ = nullptr;
- Controller* controller_ = nullptr;
- os::Handler* handler_ = nullptr;
- RoundRobinScheduler* round_robin_scheduler_ = nullptr;
- LeAddressManager* le_address_manager_ = nullptr;
- LeAclConnectionInterface* le_acl_connection_interface_ = nullptr;
- LeConnectionCallbacks* le_client_callbacks_ = nullptr;
- os::Handler* le_client_handler_ = nullptr;
- std::map<uint16_t, le_acl_connection> le_acl_connections_;
- std::set<AddressWithType> connecting_le_;
- std::set<AddressWithType> canceled_connections_;
- std::set<AddressWithType> direct_connections_;
- bool address_manager_registered = false;
- bool ready_to_unregister = false;
- bool pause_connection = false;
- bool crash_on_unknown_handle_ = false;
- std::map<AddressWithType, os::Alarm> create_connection_timeout_alarms_;
-};
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/round_robin_scheduler.cc b/gd/hci/acl_manager/round_robin_scheduler.cc
deleted file mode 100644
index 9da0a609e..000000000
--- a/gd/hci/acl_manager/round_robin_scheduler.cc
+++ /dev/null
@@ -1,256 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/acl_manager/round_robin_scheduler.h"
-#include "hci/acl_manager/acl_fragmenter.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-RoundRobinScheduler::RoundRobinScheduler(
- os::Handler* handler, Controller* controller, common::BidiQueueEnd<AclBuilder, AclView>* hci_queue_end)
- : handler_(handler), controller_(controller), hci_queue_end_(hci_queue_end) {
- max_acl_packet_credits_ = controller_->GetNumAclPacketBuffers();
- acl_packet_credits_ = max_acl_packet_credits_;
- hci_mtu_ = controller_->GetAclPacketLength();
- LeBufferSize le_buffer_size = controller_->GetLeBufferSize();
- le_max_acl_packet_credits_ = le_buffer_size.total_num_le_packets_;
- le_acl_packet_credits_ = le_max_acl_packet_credits_;
- le_hci_mtu_ = le_buffer_size.le_data_packet_length_;
- controller_->RegisterCompletedAclPacketsCallback(handler->BindOn(this, &RoundRobinScheduler::incoming_acl_credits));
-}
-
-RoundRobinScheduler::~RoundRobinScheduler() {
- unregister_all_connections();
- controller_->UnregisterCompletedAclPacketsCallback();
-}
-
-void RoundRobinScheduler::Register(ConnectionType connection_type, uint16_t handle,
- std::shared_ptr<acl_manager::AclConnection::Queue> queue) {
- acl_queue_handler acl_queue_handler = {connection_type, std::move(queue), false, 0};
- acl_queue_handlers_.insert(std::pair<uint16_t, RoundRobinScheduler::acl_queue_handler>(handle, acl_queue_handler));
- if (fragments_to_send_.size() == 0) {
- start_round_robin();
- }
-}
-
-void RoundRobinScheduler::Unregister(uint16_t handle) {
- ASSERT(acl_queue_handlers_.count(handle) == 1);
- auto acl_queue_handler = acl_queue_handlers_.find(handle)->second;
- // Reclaim outstanding packets
- if (acl_queue_handler.connection_type_ == ConnectionType::CLASSIC) {
- acl_packet_credits_ += acl_queue_handler.number_of_sent_packets_;
- } else {
- le_acl_packet_credits_ += acl_queue_handler.number_of_sent_packets_;
- }
- acl_queue_handler.number_of_sent_packets_ = 0;
-
- if (acl_queue_handler.dequeue_is_registered_) {
- acl_queue_handler.dequeue_is_registered_ = false;
- acl_queue_handler.queue_->GetDownEnd()->UnregisterDequeue();
- }
- acl_queue_handlers_.erase(handle);
- starting_point_ = acl_queue_handlers_.begin();
-}
-
-void RoundRobinScheduler::SetLinkPriority(uint16_t handle, bool high_priority) {
- auto acl_queue_handler = acl_queue_handlers_.find(handle);
- if (acl_queue_handler == acl_queue_handlers_.end()) {
- LOG_WARN("handle %d is invalid", handle);
- return;
- }
- acl_queue_handler->second.high_priority_ = high_priority;
-}
-
-uint16_t RoundRobinScheduler::GetCredits() {
- return acl_packet_credits_;
-}
-
-uint16_t RoundRobinScheduler::GetLeCredits() {
- return le_acl_packet_credits_;
-}
-
-void RoundRobinScheduler::start_round_robin() {
- if (acl_packet_credits_ == 0 && le_acl_packet_credits_ == 0) {
- return;
- }
- if (!fragments_to_send_.empty()) {
- auto connection_type = fragments_to_send_.front().first;
- bool classic_buffer_full = acl_packet_credits_ == 0 && connection_type == ConnectionType::CLASSIC;
- bool le_buffer_full = le_acl_packet_credits_ == 0 && connection_type == ConnectionType::LE;
- if (classic_buffer_full || le_buffer_full) {
- LOG_WARN("Buffer of connection_type %d is full", connection_type);
- return;
- }
- send_next_fragment();
- return;
- }
- if (acl_queue_handlers_.empty()) {
- LOG_INFO("No any acl connection");
- return;
- }
-
- if (acl_queue_handlers_.size() == 1 || starting_point_ == acl_queue_handlers_.end()) {
- starting_point_ = acl_queue_handlers_.begin();
- }
- size_t count = acl_queue_handlers_.size();
-
- for (auto acl_queue_handler = starting_point_; count > 0; count--) {
- // Prevent registration when credits is zero
- bool classic_buffer_full =
- acl_packet_credits_ == 0 && acl_queue_handler->second.connection_type_ == ConnectionType::CLASSIC;
- bool le_buffer_full =
- le_acl_packet_credits_ == 0 && acl_queue_handler->second.connection_type_ == ConnectionType::LE;
- if (!acl_queue_handler->second.dequeue_is_registered_ && !classic_buffer_full && !le_buffer_full) {
- acl_queue_handler->second.dequeue_is_registered_ = true;
- acl_queue_handler->second.queue_->GetDownEnd()->RegisterDequeue(
- handler_, common::Bind(&RoundRobinScheduler::buffer_packet, common::Unretained(this), acl_queue_handler));
- }
- acl_queue_handler = std::next(acl_queue_handler);
- if (acl_queue_handler == acl_queue_handlers_.end()) {
- acl_queue_handler = acl_queue_handlers_.begin();
- }
- }
-
- starting_point_ = std::next(starting_point_);
-}
-
-void RoundRobinScheduler::buffer_packet(std::map<uint16_t, acl_queue_handler>::iterator acl_queue_handler) {
- BroadcastFlag broadcast_flag = BroadcastFlag::POINT_TO_POINT;
- // Wrap packet and enqueue it
- uint16_t handle = acl_queue_handler->first;
- auto packet = acl_queue_handler->second.queue_->GetDownEnd()->TryDequeue();
- ASSERT(packet != nullptr);
-
- ConnectionType connection_type = acl_queue_handler->second.connection_type_;
- size_t mtu = connection_type == ConnectionType::CLASSIC ? hci_mtu_ : le_hci_mtu_;
- PacketBoundaryFlag packet_boundary_flag = (packet->IsFlushable())
- ? PacketBoundaryFlag::FIRST_AUTOMATICALLY_FLUSHABLE
- : PacketBoundaryFlag::FIRST_NON_AUTOMATICALLY_FLUSHABLE;
-
- int acl_priority = acl_queue_handler->second.high_priority_ ? 1 : 0;
- if (packet->size() <= mtu) {
- fragments_to_send_.push(
- std::make_pair(
- connection_type, AclBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(packet))),
- acl_priority);
- } else {
- auto fragments = AclFragmenter(mtu, std::move(packet)).GetFragments();
- for (size_t i = 0; i < fragments.size(); i++) {
- fragments_to_send_.push(
- std::make_pair(
- connection_type,
- AclBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(fragments[i]))),
- acl_priority);
- packet_boundary_flag = PacketBoundaryFlag::CONTINUING_FRAGMENT;
- }
- }
- ASSERT(fragments_to_send_.size() > 0);
- unregister_all_connections();
-
- acl_queue_handler->second.number_of_sent_packets_ += fragments_to_send_.size();
- send_next_fragment();
-}
-
-void RoundRobinScheduler::unregister_all_connections() {
- for (auto acl_queue_handler = acl_queue_handlers_.begin(); acl_queue_handler != acl_queue_handlers_.end();
- acl_queue_handler = std::next(acl_queue_handler)) {
- if (acl_queue_handler->second.dequeue_is_registered_) {
- acl_queue_handler->second.dequeue_is_registered_ = false;
- acl_queue_handler->second.queue_->GetDownEnd()->UnregisterDequeue();
- }
- }
-}
-
-void RoundRobinScheduler::send_next_fragment() {
- if (!enqueue_registered_.exchange(true)) {
- hci_queue_end_->RegisterEnqueue(
- handler_, common::Bind(&RoundRobinScheduler::handle_enqueue_next_fragment, common::Unretained(this)));
- }
-}
-
-// Invoked from some external Queue Reactable context 1
-std::unique_ptr<AclBuilder> RoundRobinScheduler::handle_enqueue_next_fragment() {
- ConnectionType connection_type = fragments_to_send_.front().first;
- if (connection_type == ConnectionType::CLASSIC) {
- ASSERT(acl_packet_credits_ > 0);
- acl_packet_credits_ -= 1;
- } else {
- ASSERT(le_acl_packet_credits_ > 0);
- le_acl_packet_credits_ -= 1;
- }
-
- auto raw_pointer = fragments_to_send_.front().second.release();
- fragments_to_send_.pop();
- if (fragments_to_send_.empty()) {
- if (enqueue_registered_.exchange(false)) {
- hci_queue_end_->UnregisterEnqueue();
- }
- handler_->Post(common::BindOnce(&RoundRobinScheduler::start_round_robin, common::Unretained(this)));
- } else {
- ConnectionType next_connection_type = fragments_to_send_.front().first;
- bool classic_buffer_full = next_connection_type == ConnectionType::CLASSIC && acl_packet_credits_ == 0;
- bool le_buffer_full = next_connection_type == ConnectionType::LE && le_acl_packet_credits_ == 0;
- if ((classic_buffer_full || le_buffer_full) && enqueue_registered_.exchange(false)) {
- hci_queue_end_->UnregisterEnqueue();
- }
- }
- return std::unique_ptr<AclBuilder>(raw_pointer);
-}
-
-void RoundRobinScheduler::incoming_acl_credits(uint16_t handle, uint16_t credits) {
- auto acl_queue_handler = acl_queue_handlers_.find(handle);
- if (acl_queue_handler == acl_queue_handlers_.end()) {
- LOG_INFO("Dropping %hx received credits to unknown connection 0x%0hx", credits, handle);
- return;
- }
-
- if (acl_queue_handler->second.number_of_sent_packets_ >= credits) {
- acl_queue_handler->second.number_of_sent_packets_ -= credits;
- } else {
- LOG_WARN("receive more credits than we sent");
- acl_queue_handler->second.number_of_sent_packets_ = 0;
- }
-
- bool credit_was_zero = false;
- if (acl_queue_handler->second.connection_type_ == ConnectionType::CLASSIC) {
- if (acl_packet_credits_ == 0) {
- credit_was_zero = true;
- }
- acl_packet_credits_ += credits;
- if (acl_packet_credits_ > max_acl_packet_credits_) {
- acl_packet_credits_ = max_acl_packet_credits_;
- LOG_WARN("acl packet credits overflow due to receive %hx credits", credits);
- }
- } else {
- if (le_acl_packet_credits_ == 0) {
- credit_was_zero = true;
- }
- le_acl_packet_credits_ += credits;
- if (le_acl_packet_credits_ > le_max_acl_packet_credits_) {
- le_acl_packet_credits_ = le_max_acl_packet_credits_;
- LOG_WARN("le acl packet credits overflow due to receive %hx credits", credits);
- }
- }
- if (credit_was_zero) {
- start_round_robin();
- }
-}
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager/round_robin_scheduler.h b/gd/hci/acl_manager/round_robin_scheduler.h
deleted file mode 100644
index d78bf511d..000000000
--- a/gd/hci/acl_manager/round_robin_scheduler.h
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <stdint.h>
-
-#include "common/bidi_queue.h"
-#include "common/multi_priority_queue.h"
-#include "hci/acl_manager.h"
-#include "hci/controller.h"
-#include "hci/hci_packets.h"
-#include "os/handler.h"
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-class RoundRobinScheduler {
- public:
- RoundRobinScheduler(
- os::Handler* handler, Controller* controller, common::BidiQueueEnd<AclBuilder, AclView>* hci_queue_end);
- ~RoundRobinScheduler();
-
- enum ConnectionType { CLASSIC, LE };
-
- struct acl_queue_handler {
- ConnectionType connection_type_;
- std::shared_ptr<acl_manager::AclConnection::Queue> queue_;
- bool dequeue_is_registered_ = false;
- uint16_t number_of_sent_packets_ = 0; // Track credits
- bool high_priority_ = false; // For A2dp use
- };
-
- void Register(ConnectionType connection_type, uint16_t handle,
- std::shared_ptr<acl_manager::AclConnection::Queue> queue);
- void Unregister(uint16_t handle);
- void SetLinkPriority(uint16_t handle, bool high_priority);
- uint16_t GetCredits();
- uint16_t GetLeCredits();
-
- private:
- void start_round_robin();
- void buffer_packet(std::map<uint16_t, acl_queue_handler>::iterator acl_queue_handler);
- void unregister_all_connections();
- void send_next_fragment();
- std::unique_ptr<AclBuilder> handle_enqueue_next_fragment();
- void incoming_acl_credits(uint16_t handle, uint16_t credits);
-
- os::Handler* handler_ = nullptr;
- Controller* controller_ = nullptr;
- std::map<uint16_t, acl_queue_handler> acl_queue_handlers_;
- common::MultiPriorityQueue<std::pair<ConnectionType, std::unique_ptr<AclBuilder>>, 2> fragments_to_send_;
- uint16_t max_acl_packet_credits_ = 0;
- uint16_t acl_packet_credits_ = 0;
- uint16_t le_max_acl_packet_credits_ = 0;
- uint16_t le_acl_packet_credits_ = 0;
- size_t hci_mtu_{0};
- size_t le_hci_mtu_{0};
- std::atomic_bool enqueue_registered_ = false;
- common::BidiQueueEnd<AclBuilder, AclView>* hci_queue_end_ = nullptr;
- // first register queue end for the Round-robin schedule
- std::map<uint16_t, acl_queue_handler>::iterator starting_point_;
-};
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/hci/acl_manager/round_robin_scheduler_test.cc b/gd/hci/acl_manager/round_robin_scheduler_test.cc
deleted file mode 100644
index 9d43c0f6f..000000000
--- a/gd/hci/acl_manager/round_robin_scheduler_test.cc
+++ /dev/null
@@ -1,415 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/acl_manager/round_robin_scheduler.h"
-
-#include <gtest/gtest.h>
-
-#include "common/bidi_queue.h"
-#include "common/callback.h"
-#include "hci/acl_manager.h"
-#include "hci/controller.h"
-#include "hci/hci_packets.h"
-#include "os/handler.h"
-#include "os/log.h"
-#include "packet/raw_builder.h"
-
-using ::bluetooth::common::BidiQueue;
-using ::bluetooth::common::Callback;
-using ::bluetooth::os::Handler;
-using ::bluetooth::os::Thread;
-
-namespace bluetooth {
-namespace hci {
-namespace acl_manager {
-
-class TestController : public Controller {
- public:
- uint16_t GetNumAclPacketBuffers() const {
- return max_acl_packet_credits_;
- }
-
- uint16_t GetAclPacketLength() const {
- return hci_mtu_;
- }
-
- LeBufferSize GetLeBufferSize() const {
- LeBufferSize le_buffer_size;
- le_buffer_size.le_data_packet_length_ = le_hci_mtu_;
- le_buffer_size.total_num_le_packets_ = le_max_acl_packet_credits_;
- return le_buffer_size;
- }
-
- void RegisterCompletedAclPacketsCallback(CompletedAclPacketsCallback cb) {
- acl_credits_callback_ = cb;
- }
-
- void SendCompletedAclPacketsCallback(uint16_t handle, uint16_t credits) {
- acl_credits_callback_.Invoke(handle, credits);
- }
-
- void UnregisterCompletedAclPacketsCallback() {
- acl_credits_callback_ = {};
- }
-
- const uint16_t max_acl_packet_credits_ = 10;
- const uint16_t hci_mtu_ = 1024;
- const uint16_t le_max_acl_packet_credits_ = 15;
- const uint16_t le_hci_mtu_ = 27;
-
- private:
- CompletedAclPacketsCallback acl_credits_callback_;
-};
-
-class RoundRobinSchedulerTest : public ::testing::Test {
- public:
- void SetUp() override {
- thread_ = new Thread("thread", Thread::Priority::NORMAL);
- handler_ = new Handler(thread_);
- controller_ = new TestController();
- round_robin_scheduler_ = new RoundRobinScheduler(handler_, controller_, hci_queue_.GetUpEnd());
- hci_queue_.GetDownEnd()->RegisterDequeue(
- handler_, common::Bind(&RoundRobinSchedulerTest::HciDownEndDequeue, common::Unretained(this)));
- }
-
- void TearDown() override {
- hci_queue_.GetDownEnd()->UnregisterDequeue();
- delete round_robin_scheduler_;
- delete controller_;
- handler_->Clear();
- delete handler_;
- delete thread_;
- }
-
- void sync_handler() {
- std::promise<void> promise;
- auto future = promise.get_future();
- handler_->BindOnceOn(&promise, &std::promise<void>::set_value).Invoke();
- auto status = future.wait_for(std::chrono::milliseconds(3));
- EXPECT_EQ(status, std::future_status::ready);
- }
-
- void EnqueueAclUpEnd(AclConnection::QueueUpEnd* queue_up_end, std::vector<uint8_t> packet) {
- if (enqueue_promise_ != nullptr) {
- enqueue_future_->wait();
- }
- enqueue_promise_ = std::make_unique<std::promise<void>>();
- enqueue_future_ = std::make_unique<std::future<void>>(enqueue_promise_->get_future());
- queue_up_end->RegisterEnqueue(handler_, common::Bind(&RoundRobinSchedulerTest::enqueue_callback,
- common::Unretained(this), queue_up_end, packet));
- }
-
- std::unique_ptr<packet::BasePacketBuilder> enqueue_callback(AclConnection::QueueUpEnd* queue_up_end,
- std::vector<uint8_t> packet) {
- auto packet_one = std::make_unique<packet::RawBuilder>(2000);
- packet_one->AddOctets(packet);
- queue_up_end->UnregisterEnqueue();
- enqueue_promise_->set_value();
- return packet_one;
- };
-
- void HciDownEndDequeue() {
- auto packet = hci_queue_.GetDownEnd()->TryDequeue();
- // Convert from a Builder to a View
- auto bytes = std::make_shared<std::vector<uint8_t>>();
- bluetooth::packet::BitInserter i(*bytes);
- bytes->reserve(packet->size());
- packet->Serialize(i);
- auto packet_view = bluetooth::packet::PacketView<bluetooth::packet::kLittleEndian>(bytes);
- AclView acl_packet_view = AclView::Create(packet_view);
- ASSERT_TRUE(acl_packet_view.IsValid());
- PacketView<true> count_view = acl_packet_view.GetPayload();
- sent_acl_packets_.push(acl_packet_view);
-
- packet_count_--;
- if (packet_count_ == 0) {
- packet_promise_->set_value();
- packet_promise_ = nullptr;
- }
- }
-
- void VerifyPacket(uint16_t handle, std::vector<uint8_t> packet) {
- auto acl_packet_view = sent_acl_packets_.front();
- ASSERT_EQ(handle, acl_packet_view.GetHandle());
- auto payload = acl_packet_view.GetPayload();
- for (size_t i = 0; i < payload.size(); i++) {
- ASSERT_EQ(payload[i], packet[i]);
- }
- sent_acl_packets_.pop();
- }
-
- void SetPacketFuture(uint16_t count) {
- ASSERT_LOG(packet_promise_ == nullptr, "Promises, Promises, ... Only one at a time.");
- packet_count_ = count;
- packet_promise_ = std::make_unique<std::promise<void>>();
- packet_future_ = std::make_unique<std::future<void>>(packet_promise_->get_future());
- }
-
- BidiQueue<AclView, AclBuilder> hci_queue_{3};
- Thread* thread_;
- Handler* handler_;
- TestController* controller_;
- RoundRobinScheduler* round_robin_scheduler_;
- std::queue<AclView> sent_acl_packets_;
- uint16_t packet_count_;
- std::unique_ptr<std::promise<void>> packet_promise_;
- std::unique_ptr<std::future<void>> packet_future_;
- std::unique_ptr<std::promise<void>> enqueue_promise_;
- std::unique_ptr<std::future<void>> enqueue_future_;
-};
-
-TEST_F(RoundRobinSchedulerTest, startup_teardown) {}
-
-TEST_F(RoundRobinSchedulerTest, register_unregister_connection) {
- uint16_t handle = 0x01;
- auto connection_queue = std::make_shared<AclConnection::Queue>(10);
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::CLASSIC, handle, connection_queue);
- round_robin_scheduler_->Unregister(handle);
-}
-
-TEST_F(RoundRobinSchedulerTest, buffer_packet) {
- uint16_t handle = 0x01;
- auto connection_queue = std::make_shared<AclConnection::Queue>(10);
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::CLASSIC, handle, connection_queue);
-
- SetPacketFuture(2);
- AclConnection::QueueUpEnd* queue_up_end = connection_queue->GetUpEnd();
- std::vector<uint8_t> packet1 = {0x01, 0x02, 0x03};
- std::vector<uint8_t> packet2 = {0x04, 0x05, 0x06};
- EnqueueAclUpEnd(queue_up_end, packet1);
- EnqueueAclUpEnd(queue_up_end, packet2);
-
- packet_future_->wait();
- VerifyPacket(handle, packet1);
- VerifyPacket(handle, packet2);
- ASSERT_EQ(round_robin_scheduler_->GetCredits(), controller_->max_acl_packet_credits_ - 2);
-
- round_robin_scheduler_->Unregister(handle);
-}
-
-TEST_F(RoundRobinSchedulerTest, buffer_packet_from_two_connections) {
- uint16_t handle = 0x01;
- uint16_t le_handle = 0x02;
- auto connection_queue = std::make_shared<AclConnection::Queue>(10);
- auto le_connection_queue = std::make_shared<AclConnection::Queue>(10);
-
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::CLASSIC, handle, connection_queue);
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::LE, le_handle, le_connection_queue);
-
- SetPacketFuture(2);
- AclConnection::QueueUpEnd* queue_up_end = connection_queue->GetUpEnd();
- AclConnection::QueueUpEnd* le_queue_up_end = le_connection_queue->GetUpEnd();
- std::vector<uint8_t> packet = {0x01, 0x02, 0x03};
- std::vector<uint8_t> le_packet = {0x04, 0x05, 0x06};
- EnqueueAclUpEnd(le_queue_up_end, le_packet);
- EnqueueAclUpEnd(queue_up_end, packet);
-
- packet_future_->wait();
- VerifyPacket(le_handle, le_packet);
- VerifyPacket(handle, packet);
- ASSERT_EQ(round_robin_scheduler_->GetCredits(), controller_->max_acl_packet_credits_ - 1);
- ASSERT_EQ(round_robin_scheduler_->GetLeCredits(), controller_->le_max_acl_packet_credits_ - 1);
-
- round_robin_scheduler_->Unregister(handle);
- round_robin_scheduler_->Unregister(le_handle);
-}
-
-TEST_F(RoundRobinSchedulerTest, do_not_register_when_credits_is_zero) {
- uint16_t handle = 0x01;
- auto connection_queue = std::make_shared<AclConnection::Queue>(15);
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::CLASSIC, handle, connection_queue);
-
- SetPacketFuture(10);
- AclConnection::QueueUpEnd* queue_up_end = connection_queue->GetUpEnd();
- for (uint8_t i = 0; i < 15; i++) {
- std::vector<uint8_t> packet = {0x01, 0x02, 0x03, i};
- EnqueueAclUpEnd(queue_up_end, packet);
- }
-
- packet_future_->wait();
- for (uint8_t i = 0; i < 10; i++) {
- std::vector<uint8_t> packet = {0x01, 0x02, 0x03, i};
- VerifyPacket(handle, packet);
- }
- ASSERT_EQ(round_robin_scheduler_->GetCredits(), 0);
-
- SetPacketFuture(5);
- controller_->SendCompletedAclPacketsCallback(0x01, 10);
- sync_handler();
- packet_future_->wait();
- for (uint8_t i = 10; i < 15; i++) {
- std::vector<uint8_t> packet = {0x01, 0x02, 0x03, i};
- VerifyPacket(handle, packet);
- }
- ASSERT_EQ(round_robin_scheduler_->GetCredits(), 5);
-
- round_robin_scheduler_->Unregister(handle);
-}
-
-TEST_F(RoundRobinSchedulerTest, reveived_completed_callback_with_unknown_handle) {
- controller_->SendCompletedAclPacketsCallback(0x00, 1);
- sync_handler();
- EXPECT_EQ(round_robin_scheduler_->GetCredits(), controller_->max_acl_packet_credits_);
- EXPECT_EQ(round_robin_scheduler_->GetLeCredits(), controller_->le_max_acl_packet_credits_);
-}
-
-TEST_F(RoundRobinSchedulerTest, buffer_packet_intervally) {
- uint16_t handle1 = 0x01;
- uint16_t handle2 = 0x02;
- uint16_t le_handle1 = 0x03;
- uint16_t le_handle2 = 0x04;
- auto connection_queue1 = std::make_shared<AclConnection::Queue>(10);
- auto connection_queue2 = std::make_shared<AclConnection::Queue>(10);
- auto le_connection_queue1 = std::make_shared<AclConnection::Queue>(10);
- auto le_connection_queue2 = std::make_shared<AclConnection::Queue>(10);
-
- SetPacketFuture(18);
- AclConnection::QueueUpEnd* queue_up_end1 = connection_queue1->GetUpEnd();
- AclConnection::QueueUpEnd* queue_up_end2 = connection_queue2->GetUpEnd();
- AclConnection::QueueUpEnd* le_queue_up_end1 = le_connection_queue1->GetUpEnd();
- AclConnection::QueueUpEnd* le_queue_up_end2 = le_connection_queue2->GetUpEnd();
-
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::CLASSIC, handle1, connection_queue1);
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::CLASSIC, handle2, connection_queue2);
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::LE, le_handle1, le_connection_queue1);
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::LE, le_handle2, le_connection_queue2);
-
- std::vector<uint8_t> packet = {0x01, 0x02, 0x03};
- EnqueueAclUpEnd(queue_up_end1, packet);
- EnqueueAclUpEnd(le_queue_up_end2, packet);
- for (uint8_t i = 0; i < 4; i++) {
- std::vector<uint8_t> packet1 = {0x01, 0x02, 0x03, i};
- std::vector<uint8_t> packet2 = {0x02, 0x02, 0x03, i};
- std::vector<uint8_t> le_packet1 = {0x04, 0x05, 0x06, i};
- std::vector<uint8_t> le_packet2 = {0x05, 0x05, 0x06, i};
- EnqueueAclUpEnd(queue_up_end1, packet1);
- EnqueueAclUpEnd(queue_up_end2, packet2);
- EnqueueAclUpEnd(le_queue_up_end1, le_packet1);
- EnqueueAclUpEnd(le_queue_up_end2, le_packet2);
- }
-
- packet_future_->wait();
- VerifyPacket(handle1, packet);
- VerifyPacket(le_handle2, packet);
- for (uint8_t i = 0; i < 4; i++) {
- std::vector<uint8_t> packet1 = {0x01, 0x02, 0x03, i};
- std::vector<uint8_t> packet2 = {0x02, 0x02, 0x03, i};
- std::vector<uint8_t> le_packet1 = {0x04, 0x05, 0x06, i};
- std::vector<uint8_t> le_packet2 = {0x05, 0x05, 0x06, i};
- VerifyPacket(handle1, packet1);
- VerifyPacket(handle2, packet2);
- VerifyPacket(le_handle1, le_packet1);
- VerifyPacket(le_handle2, le_packet2);
- }
-
- ASSERT_EQ(round_robin_scheduler_->GetCredits(), controller_->max_acl_packet_credits_ - 9);
- ASSERT_EQ(round_robin_scheduler_->GetLeCredits(), controller_->le_max_acl_packet_credits_ - 9);
-
- round_robin_scheduler_->Unregister(handle1);
- round_robin_scheduler_->Unregister(handle2);
- round_robin_scheduler_->Unregister(le_handle1);
- round_robin_scheduler_->Unregister(le_handle2);
-}
-
-TEST_F(RoundRobinSchedulerTest, send_fragments_without_interval) {
- uint16_t handle = 0x01;
- uint16_t le_handle = 0x02;
- auto connection_queue = std::make_shared<AclConnection::Queue>(10);
- auto le_connection_queue = std::make_shared<AclConnection::Queue>(10);
-
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::CLASSIC, handle, connection_queue);
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::LE, le_handle, le_connection_queue);
-
- SetPacketFuture(5);
- AclConnection::QueueUpEnd* queue_up_end = connection_queue->GetUpEnd();
- AclConnection::QueueUpEnd* le_queue_up_end = le_connection_queue->GetUpEnd();
- std::vector<uint8_t> packet(controller_->hci_mtu_, 0xff);
- std::vector<uint8_t> packet_part1(controller_->hci_mtu_, 0xff);
- std::vector<uint8_t> packet_part2 = {0x03, 0x02, 0x01};
- packet.insert(packet.end(), packet_part2.begin(), packet_part2.end());
-
- std::vector<uint8_t> le_packet;
- std::vector<uint8_t> le_packet_part1;
- std::vector<uint8_t> le_packet_part2;
- std::vector<uint8_t> le_packet_part3;
- for (uint8_t i = 0; i < controller_->le_hci_mtu_; i++) {
- le_packet.push_back(i);
- le_packet_part1.push_back(i);
- le_packet_part2.push_back(i * 2);
- le_packet_part3.push_back(i * 3);
- }
- le_packet.insert(le_packet.end(), le_packet_part2.begin(), le_packet_part2.end());
- le_packet.insert(le_packet.end(), le_packet_part3.begin(), le_packet_part3.end());
-
- EnqueueAclUpEnd(le_queue_up_end, le_packet);
- EnqueueAclUpEnd(queue_up_end, packet);
-
- packet_future_->wait();
- VerifyPacket(le_handle, le_packet_part1);
- VerifyPacket(le_handle, le_packet_part2);
- VerifyPacket(le_handle, le_packet_part3);
- VerifyPacket(handle, packet_part1);
- VerifyPacket(handle, packet_part2);
- ASSERT_EQ(round_robin_scheduler_->GetCredits(), controller_->max_acl_packet_credits_ - 2);
- ASSERT_EQ(round_robin_scheduler_->GetLeCredits(), controller_->le_max_acl_packet_credits_ - 3);
-
- round_robin_scheduler_->Unregister(handle);
- round_robin_scheduler_->Unregister(le_handle);
-}
-
-TEST_F(RoundRobinSchedulerTest, receive_le_credit_when_next_fragment_is_classic) {
- uint16_t handle = 0x01;
- uint16_t le_handle = 0x02;
- auto connection_queue = std::make_shared<AclConnection::Queue>(20);
- auto le_connection_queue = std::make_shared<AclConnection::Queue>(20);
-
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::CLASSIC, handle, connection_queue);
- round_robin_scheduler_->Register(RoundRobinScheduler::ConnectionType::LE, le_handle, le_connection_queue);
-
- SetPacketFuture(controller_->le_max_acl_packet_credits_ + controller_->max_acl_packet_credits_);
- AclConnection::QueueUpEnd* queue_up_end = connection_queue->GetUpEnd();
- AclConnection::QueueUpEnd* le_queue_up_end = le_connection_queue->GetUpEnd();
- std::vector<uint8_t> huge_packet(2000);
- std::vector<uint8_t> packet = {0x01, 0x02, 0x03};
- std::vector<uint8_t> le_packet = {0x04, 0x05, 0x06};
-
- // Make le_acl_packet_credits_ = 0;
- for (uint16_t i = 0; i < controller_->le_max_acl_packet_credits_; i++) {
- EnqueueAclUpEnd(le_queue_up_end, le_packet);
- }
-
- // Make acl_packet_credits_ = 0 and remain 1 acl fragment in fragments_to_send_
- for (uint16_t i = 0; i < controller_->max_acl_packet_credits_ - 1; i++) {
- EnqueueAclUpEnd(queue_up_end, packet);
- }
- EnqueueAclUpEnd(queue_up_end, huge_packet);
-
- packet_future_->wait();
-
- // Trigger start_round_robin
- controller_->SendCompletedAclPacketsCallback(0x02, 1);
- std::this_thread::sleep_for(std::chrono::milliseconds(20));
-
- ASSERT_EQ(round_robin_scheduler_->GetCredits(), 0);
- ASSERT_EQ(round_robin_scheduler_->GetLeCredits(), 1);
-
- round_robin_scheduler_->Unregister(handle);
- round_robin_scheduler_->Unregister(le_handle);
-}
-
-} // namespace acl_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/acl_manager_mock.h b/gd/hci/acl_manager_mock.h
index 7349e2f22..d34b3ef19 100644
--- a/gd/hci/acl_manager_mock.h
+++ b/gd/hci/acl_manager_mock.h
@@ -16,12 +16,6 @@
#pragma once
#include "hci/acl_manager.h"
-#include "hci/acl_manager/classic_acl_connection.h"
-#include "hci/acl_manager/connection_callbacks.h"
-#include "hci/acl_manager/connection_management_callbacks.h"
-#include "hci/acl_manager/le_acl_connection.h"
-#include "hci/acl_manager/le_connection_callbacks.h"
-#include "hci/acl_manager/le_connection_management_callbacks.h"
#include <gmock/gmock.h>
@@ -30,36 +24,16 @@ namespace bluetooth {
namespace hci {
namespace testing {
-using acl_manager::LeAclConnection;
-using acl_manager::LeConnectionCallbacks;
-using acl_manager::LeConnectionManagementCallbacks;
-
-using acl_manager::ClassicAclConnection;
-using acl_manager::ConnectionCallbacks;
-using acl_manager::ConnectionManagementCallbacks;
-
-class MockClassicAclConnection : public ClassicAclConnection {
+class MockAclConnection : public AclConnection {
public:
MOCK_METHOD(Address, GetAddress, (), (const, override));
+ MOCK_METHOD(AddressType, GetAddressType, (), (const, override));
+ MOCK_METHOD(void, RegisterDisconnectCallback,
+ (common::OnceCallback<void(ErrorCode)> on_disconnect, os::Handler* handler), (override));
MOCK_METHOD(bool, Disconnect, (DisconnectReason reason), (override));
+ MOCK_METHOD(void, Finish, (), (override));
MOCK_METHOD(void, RegisterCallbacks, (ConnectionManagementCallbacks * callbacks, os::Handler* handler), (override));
- MOCK_METHOD(bool, ReadRemoteVersionInformation, (), (override));
- MOCK_METHOD(bool, ReadRemoteSupportedFeatures, (), (override));
- MOCK_METHOD(bool, ReadRemoteExtendedFeatures, (uint8_t), (override));
-
- QueueUpEnd* GetAclQueueEnd() const override {
- return acl_queue_.GetUpEnd();
- }
- mutable common::BidiQueue<PacketView<kLittleEndian>, BasePacketBuilder> acl_queue_{10};
-};
-
-class MockLeAclConnection : public LeAclConnection {
- public:
- MOCK_METHOD(AddressWithType, GetLocalAddress, (), (const, override));
- MOCK_METHOD(AddressWithType, GetRemoteAddress, (), (const, override));
- MOCK_METHOD(void, Disconnect, (DisconnectReason reason), (override));
- MOCK_METHOD(void, RegisterCallbacks, (LeConnectionManagementCallbacks * callbacks, os::Handler* handler), (override));
- MOCK_METHOD(bool, ReadRemoteVersionInformation, (), (override));
+ MOCK_METHOD(void, UnregisterCallbacks, (ConnectionManagementCallbacks * callbacks), (override));
QueueUpEnd* GetAclQueueEnd() const override {
return acl_queue_.GetUpEnd();
@@ -72,19 +46,8 @@ class MockAclManager : public AclManager {
MOCK_METHOD(void, RegisterCallbacks, (ConnectionCallbacks * callbacks, os::Handler* handler), (override));
MOCK_METHOD(void, RegisterLeCallbacks, (LeConnectionCallbacks * callbacks, os::Handler* handler), (override));
MOCK_METHOD(void, CreateConnection, (Address address), (override));
- MOCK_METHOD(void, CreateLeConnection, (AddressWithType address_with_type, bool is_direct), (override));
+ MOCK_METHOD(void, CreateLeConnection, (AddressWithType address_with_type), (override));
MOCK_METHOD(void, CancelConnect, (Address address), (override));
- MOCK_METHOD(
- void,
- SetPrivacyPolicyForInitiatorAddress,
- (LeAddressManager::AddressPolicy address_policy,
- AddressWithType fixed_address,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time),
- (override));
-
- // PRIVATE TO SHIM
- MOCK_METHOD(void, HACK_SetScoDisconnectCallback, (std::function<void(uint16_t /* handle */, uint8_t /* reason */)>));
};
} // namespace testing
diff --git a/gd/hci/acl_manager_test.cc b/gd/hci/acl_manager_test.cc
index 3975e2775..c741d455e 100644
--- a/gd/hci/acl_manager_test.cc
+++ b/gd/hci/acl_manager_test.cc
@@ -26,7 +26,6 @@
#include "common/bind.h"
#include "hci/address.h"
-#include "hci/class_of_device.h"
#include "hci/controller.h"
#include "hci/hci_layer.h"
#include "os/thread.h"
@@ -34,7 +33,6 @@
namespace bluetooth {
namespace hci {
-namespace acl_manager {
namespace {
using common::BidiQueue;
@@ -44,11 +42,6 @@ using packet::PacketView;
using packet::RawBuilder;
constexpr std::chrono::seconds kTimeout = std::chrono::seconds(2);
-constexpr uint16_t kScanIntervalFast = 0x0060;
-constexpr uint16_t kScanWindowFast = 0x0030;
-constexpr uint16_t kScanIntervalSlow = 0x0800;
-constexpr uint16_t kScanWindowSlow = 0x0030;
-const AddressWithType empty_address_with_type = hci::AddressWithType();
PacketView<kLittleEndian> GetPacketView(std::unique_ptr<packet::BasePacketBuilder> packet) {
auto bytes = std::make_shared<std::vector<uint8_t>>();
@@ -68,49 +61,41 @@ std::unique_ptr<BasePacketBuilder> NextPayload(uint16_t handle) {
return std::move(payload);
}
-std::unique_ptr<AclBuilder> NextAclPacket(uint16_t handle) {
+std::unique_ptr<AclPacketBuilder> NextAclPacket(uint16_t handle) {
PacketBoundaryFlag packet_boundary_flag = PacketBoundaryFlag::FIRST_AUTOMATICALLY_FLUSHABLE;
- BroadcastFlag broadcast_flag = BroadcastFlag::POINT_TO_POINT;
- return AclBuilder::Create(handle, packet_boundary_flag, broadcast_flag, NextPayload(handle));
+ BroadcastFlag broadcast_flag = BroadcastFlag::ACTIVE_SLAVE_BROADCAST;
+ return AclPacketBuilder::Create(handle, packet_boundary_flag, broadcast_flag, NextPayload(handle));
}
class TestController : public Controller {
public:
- void RegisterCompletedAclPacketsCallback(
- common::ContextualCallback<void(uint16_t /* handle */, uint16_t /* packets */)> cb) override {
+ void RegisterCompletedAclPacketsCallback(common::Callback<void(uint16_t /* handle */, uint16_t /* packets */)> cb,
+ os::Handler* handler) override {
acl_cb_ = cb;
+ acl_cb_handler_ = handler;
}
- void UnregisterCompletedAclPacketsCallback() override {
- acl_cb_ = {};
- }
-
- uint16_t GetAclPacketLength() const override {
+ uint16_t GetControllerAclPacketLength() const override {
return acl_buffer_length_;
}
- uint16_t GetNumAclPacketBuffers() const override {
+ uint16_t GetControllerNumAclPacketBuffers() const override {
return total_acl_buffers_;
}
- bool IsSupported(bluetooth::hci::OpCode op_code) const override {
- return false;
- }
-
- LeBufferSize GetLeBufferSize() const override {
- LeBufferSize le_buffer_size;
- le_buffer_size.total_num_le_packets_ = 2;
- le_buffer_size.le_data_packet_length_ = 32;
- return le_buffer_size;
+ uint64_t GetControllerLeLocalSupportedFeatures() const override {
+ return le_local_supported_features_;
}
void CompletePackets(uint16_t handle, uint16_t packets) {
- acl_cb_.Invoke(handle, packets);
+ acl_cb_handler_->Post(common::BindOnce(acl_cb_, handle, packets));
}
uint16_t acl_buffer_length_ = 1024;
uint16_t total_acl_buffers_ = 2;
- common::ContextualCallback<void(uint16_t /* handle */, uint16_t /* packets */)> acl_cb_;
+ uint64_t le_local_supported_features_ = 0;
+ common::Callback<void(uint16_t /* handle */, uint16_t /* packets */)> acl_cb_;
+ os::Handler* acl_cb_handler_ = nullptr;
protected:
void Start() override {}
@@ -120,22 +105,20 @@ class TestController : public Controller {
class TestHciLayer : public HciLayer {
public:
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(CommandStatusView)> on_status) override {
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) override {
command_queue_.push(std::move(command));
- command_status_callbacks.push_back(std::move(on_status));
+ command_status_callbacks.push_front(std::move(on_status));
if (command_promise_ != nullptr) {
command_promise_->set_value();
command_promise_.reset();
}
}
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(CommandCompleteView)> on_complete) override {
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) override {
command_queue_.push(std::move(command));
- command_complete_callbacks.push_back(std::move(on_complete));
+ command_complete_callbacks.push_front(std::move(on_complete));
if (command_promise_ != nullptr) {
command_promise_->set_value();
command_promise_.reset();
@@ -148,55 +131,32 @@ class TestHciLayer : public HciLayer {
command_future_ = std::make_unique<std::future<void>>(command_promise_->get_future());
}
- CommandView GetLastCommand() {
+ std::unique_ptr<CommandPacketBuilder> GetLastCommand() {
if (command_queue_.size() == 0) {
- return CommandView::Create(PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>()));
+ return nullptr;
}
auto last = std::move(command_queue_.front());
command_queue_.pop();
- return CommandView::Create(GetPacketView(std::move(last)));
+ return last;
}
- ConnectionManagementCommandView GetCommand(OpCode op_code) {
+ ConnectionManagementCommandView GetCommandPacket(OpCode op_code) {
if (command_future_ != nullptr) {
auto result = command_future_->wait_for(std::chrono::milliseconds(1000));
EXPECT_NE(std::future_status::timeout, result);
}
- if (command_queue_.empty()) {
- return ConnectionManagementCommandView::Create(AclCommandView::Create(
- CommandView::Create(PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>()))));
- }
- CommandView command_packet_view = GetLastCommand();
- ConnectionManagementCommandView command =
- ConnectionManagementCommandView::Create(AclCommandView::Create(command_packet_view));
- EXPECT_TRUE(command.IsValid());
+ ASSERT(command_queue_.size() > 0);
+ auto packet_view = GetPacketView(GetLastCommand());
+ CommandPacketView command_packet_view = CommandPacketView::Create(packet_view);
+ ConnectionManagementCommandView command = ConnectionManagementCommandView::Create(command_packet_view);
+ ASSERT(command.IsValid());
EXPECT_EQ(command.GetOpCode(), op_code);
return command;
}
- ConnectionManagementCommandView GetLastCommand(OpCode op_code) {
- if (!command_queue_.empty() && command_future_ != nullptr) {
- command_future_.reset();
- command_promise_.reset();
- } else if (command_future_ != nullptr) {
- auto result = command_future_->wait_for(std::chrono::milliseconds(1000));
- EXPECT_NE(std::future_status::timeout, result);
- }
- if (command_queue_.empty()) {
- return ConnectionManagementCommandView::Create(AclCommandView::Create(
- CommandView::Create(PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>()))));
- }
- CommandView command_packet_view = GetLastCommand();
- ConnectionManagementCommandView command =
- ConnectionManagementCommandView::Create(AclCommandView::Create(command_packet_view));
- EXPECT_TRUE(command.IsValid());
- EXPECT_EQ(command.GetOpCode(), op_code);
-
- return command;
- }
-
- void RegisterEventHandler(EventCode event_code, common::ContextualCallback<void(EventView)> event_handler) override {
+ void RegisterEventHandler(EventCode event_code, common::Callback<void(EventPacketView)> event_handler,
+ os::Handler* handler) override {
registered_events_[event_code] = event_handler;
}
@@ -204,32 +164,32 @@ class TestHciLayer : public HciLayer {
registered_events_.erase(event_code);
}
- void RegisterLeEventHandler(SubeventCode subevent_code,
- common::ContextualCallback<void(LeMetaEventView)> event_handler) override {
+ void RegisterLeEventHandler(SubeventCode subevent_code, common::Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler) override {
registered_le_events_[subevent_code] = event_handler;
}
- void UnregisterLeEventHandler(SubeventCode subevent_code) override {
+ void UnregisterLeEventHandler(SubeventCode subevent_code) {
registered_le_events_.erase(subevent_code);
}
- void IncomingEvent(std::unique_ptr<EventBuilder> event_builder) {
+ void IncomingEvent(std::unique_ptr<EventPacketBuilder> event_builder) {
auto packet = GetPacketView(std::move(event_builder));
- EventView event = EventView::Create(packet);
+ EventPacketView event = EventPacketView::Create(packet);
ASSERT_TRUE(event.IsValid());
EventCode event_code = event.GetEventCode();
- ASSERT_NE(registered_events_.find(event_code), registered_events_.end()) << EventCodeText(event_code);
- registered_events_[event_code].Invoke(event);
+ ASSERT_TRUE(registered_events_.find(event_code) != registered_events_.end()) << EventCodeText(event_code);
+ registered_events_[event_code].Run(event);
}
void IncomingLeMetaEvent(std::unique_ptr<LeMetaEventBuilder> event_builder) {
auto packet = GetPacketView(std::move(event_builder));
- EventView event = EventView::Create(packet);
+ EventPacketView event = EventPacketView::Create(packet);
LeMetaEventView meta_event_view = LeMetaEventView::Create(event);
EXPECT_TRUE(meta_event_view.IsValid());
SubeventCode subevent_code = meta_event_view.GetSubeventCode();
EXPECT_TRUE(registered_le_events_.find(subevent_code) != registered_le_events_.end());
- registered_le_events_[subevent_code].Invoke(meta_event_view);
+ registered_le_events_[subevent_code].Run(meta_event_view);
}
void IncomingAclData(uint16_t handle) {
@@ -241,10 +201,10 @@ class TestHciLayer : public HciLayer {
common::Bind(
[](decltype(queue_end) queue_end, uint16_t handle, std::promise<void> promise) {
auto packet = GetPacketView(NextAclPacket(handle));
- AclView acl2 = AclView::Create(packet);
+ AclPacketView acl2 = AclPacketView::Create(packet);
queue_end->UnregisterEnqueue();
promise.set_value();
- return std::make_unique<AclView>(acl2);
+ return std::make_unique<AclPacketView>(acl2);
},
queue_end, handle, common::Passed(std::move(promise))));
auto status = future.wait_for(kTimeout);
@@ -256,23 +216,23 @@ class TestHciLayer : public HciLayer {
EXPECT_EQ(queue_end->TryDequeue(), nullptr);
}
- void CommandCompleteCallback(EventView event) {
+ void CommandCompleteCallback(EventPacketView event) {
CommandCompleteView complete_view = CommandCompleteView::Create(event);
- ASSERT_TRUE(complete_view.IsValid());
- std::move(command_complete_callbacks.front()).Invoke(complete_view);
+ ASSERT(complete_view.IsValid());
+ std::move(command_complete_callbacks.front()).Run(complete_view);
command_complete_callbacks.pop_front();
}
- void CommandStatusCallback(EventView event) {
+ void CommandStatusCallback(EventPacketView event) {
CommandStatusView status_view = CommandStatusView::Create(event);
- ASSERT_TRUE(status_view.IsValid());
- std::move(command_status_callbacks.front()).Invoke(status_view);
+ ASSERT(status_view.IsValid());
+ std::move(command_status_callbacks.front()).Run(status_view);
command_status_callbacks.pop_front();
}
PacketView<kLittleEndian> OutgoingAclData() {
auto queue_end = acl_queue_.GetDownEnd();
- std::unique_ptr<AclBuilder> received;
+ std::unique_ptr<AclPacketBuilder> received;
do {
received = queue_end->TryDequeue();
} while (received == nullptr);
@@ -280,71 +240,44 @@ class TestHciLayer : public HciLayer {
return GetPacketView(std::move(received));
}
- BidiQueueEnd<AclBuilder, AclView>* GetAclQueueEnd() override {
+ BidiQueueEnd<AclPacketBuilder, AclPacketView>* GetAclQueueEnd() override {
return acl_queue_.GetUpEnd();
}
void ListDependencies(ModuleList* list) override {}
void Start() override {
RegisterEventHandler(EventCode::COMMAND_COMPLETE,
- GetHandler()->BindOn(this, &TestHciLayer::CommandCompleteCallback));
- RegisterEventHandler(EventCode::COMMAND_STATUS, GetHandler()->BindOn(this, &TestHciLayer::CommandStatusCallback));
+ base::Bind(&TestHciLayer::CommandCompleteCallback, common::Unretained(this)), nullptr);
+ RegisterEventHandler(EventCode::COMMAND_STATUS,
+ base::Bind(&TestHciLayer::CommandStatusCallback, common::Unretained(this)), nullptr);
}
void Stop() override {}
- void Disconnect(uint16_t handle, ErrorCode reason) override {
- GetHandler()->Post(common::BindOnce(&TestHciLayer::do_disconnect, common::Unretained(this), handle, reason));
- }
-
private:
- std::map<EventCode, common::ContextualCallback<void(EventView)>> registered_events_;
- std::map<SubeventCode, common::ContextualCallback<void(LeMetaEventView)>> registered_le_events_;
- std::list<common::ContextualOnceCallback<void(CommandCompleteView)>> command_complete_callbacks;
- std::list<common::ContextualOnceCallback<void(CommandStatusView)>> command_status_callbacks;
- BidiQueue<AclView, AclBuilder> acl_queue_{3 /* TODO: Set queue depth */};
+ std::map<EventCode, common::Callback<void(EventPacketView)>> registered_events_;
+ std::map<SubeventCode, common::Callback<void(LeMetaEventView)>> registered_le_events_;
+ std::list<base::OnceCallback<void(CommandCompleteView)>> command_complete_callbacks;
+ std::list<base::OnceCallback<void(CommandStatusView)>> command_status_callbacks;
+ BidiQueue<AclPacketView, AclPacketBuilder> acl_queue_{3 /* TODO: Set queue depth */};
- std::queue<std::unique_ptr<CommandBuilder>> command_queue_;
+ std::queue<std::unique_ptr<CommandPacketBuilder>> command_queue_;
std::unique_ptr<std::promise<void>> command_promise_;
std::unique_ptr<std::future<void>> command_future_;
-
- void do_disconnect(uint16_t handle, ErrorCode reason) {
- HciLayer::Disconnect(handle, reason);
- }
};
class AclManagerNoCallbacksTest : public ::testing::Test {
protected:
void SetUp() override {
test_hci_layer_ = new TestHciLayer; // Ownership is transferred to registry
+ test_hci_layer_->Start();
test_controller_ = new TestController;
fake_registry_.InjectTestModule(&HciLayer::Factory, test_hci_layer_);
fake_registry_.InjectTestModule(&Controller::Factory, test_controller_);
client_handler_ = fake_registry_.GetTestModuleHandler(&HciLayer::Factory);
- ASSERT_NE(client_handler_, nullptr);
- test_hci_layer_->SetCommandFuture();
+ EXPECT_NE(client_handler_, nullptr);
fake_registry_.Start<AclManager>(&thread_);
acl_manager_ = static_cast<AclManager*>(fake_registry_.GetModuleUnderTest(&AclManager::Factory));
Address::FromString("A1:A2:A3:A4:A5:A6", remote);
-
- hci::Address address;
- Address::FromString("D0:05:04:03:02:01", address);
- hci::AddressWithType address_with_type(address, hci::AddressType::RANDOM_DEVICE_ADDRESS);
- auto minimum_rotation_time = std::chrono::milliseconds(7 * 60 * 1000);
- auto maximum_rotation_time = std::chrono::milliseconds(15 * 60 * 1000);
- acl_manager_->SetPrivacyPolicyForInitiatorAddress(
- LeAddressManager::AddressPolicy::USE_STATIC_ADDRESS,
- address_with_type,
- minimum_rotation_time,
- maximum_rotation_time);
-
- auto set_random_address_packet = LeSetRandomAddressView::Create(
- LeAdvertisingCommandView::Create(test_hci_layer_->GetCommand(OpCode::LE_SET_RANDOM_ADDRESS)));
- ASSERT_TRUE(set_random_address_packet.IsValid());
- my_initiating_address =
- AddressWithType(set_random_address_packet.GetRandomAddress(), AddressType::RANDOM_DEVICE_ADDRESS);
- // Verify LE Set Random Address was sent during setup
- test_hci_layer_->GetLastCommand(OpCode::LE_SET_RANDOM_ADDRESS);
- test_hci_layer_->IncomingEvent(LeSetRandomAddressCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
}
void TearDown() override {
@@ -359,8 +292,6 @@ class AclManagerNoCallbacksTest : public ::testing::Test {
AclManager* acl_manager_ = nullptr;
os::Handler* client_handler_ = nullptr;
Address remote;
- AddressWithType my_initiating_address;
- const bool use_connect_list_ = true; // gd currently only supports connect list
std::future<void> GetConnectionFuture() {
ASSERT_LOG(mock_connection_callback_.connection_promise_ == nullptr, "Promises promises ... Only one at a time");
@@ -375,15 +306,16 @@ class AclManagerNoCallbacksTest : public ::testing::Test {
return mock_le_connection_callbacks_.le_connection_promise_->get_future();
}
- std::shared_ptr<ClassicAclConnection> GetLastConnection() {
+ std::shared_ptr<AclConnection> GetLastConnection() {
return mock_connection_callback_.connections_.back();
}
- std::shared_ptr<LeAclConnection> GetLastLeConnection() {
+ std::shared_ptr<AclConnection> GetLastLeConnection() {
return mock_le_connection_callbacks_.le_connections_.back();
}
- void SendAclData(uint16_t handle, AclConnection::QueueUpEnd* queue_end) {
+ void SendAclData(uint16_t handle, std::shared_ptr<AclConnection> connection) {
+ auto queue_end = connection->GetAclQueueEnd();
std::promise<void> promise;
auto future = promise.get_future();
queue_end->RegisterEnqueue(client_handler_,
@@ -400,7 +332,7 @@ class AclManagerNoCallbacksTest : public ::testing::Test {
class MockConnectionCallback : public ConnectionCallbacks {
public:
- void OnConnectSuccess(std::unique_ptr<ClassicAclConnection> connection) override {
+ void OnConnectSuccess(std::unique_ptr<AclConnection> connection) override {
// Convert to std::shared_ptr during push_back()
connections_.push_back(std::move(connection));
if (connection_promise_ != nullptr) {
@@ -410,16 +342,13 @@ class AclManagerNoCallbacksTest : public ::testing::Test {
}
MOCK_METHOD(void, OnConnectFail, (Address, ErrorCode reason), (override));
- MOCK_METHOD(void, HACK_OnEscoConnectRequest, (Address, ClassOfDevice), (override));
- MOCK_METHOD(void, HACK_OnScoConnectRequest, (Address, ClassOfDevice), (override));
-
- std::list<std::shared_ptr<ClassicAclConnection>> connections_;
+ std::list<std::shared_ptr<AclConnection>> connections_;
std::unique_ptr<std::promise<void>> connection_promise_;
} mock_connection_callback_;
class MockLeConnectionCallbacks : public LeConnectionCallbacks {
public:
- void OnLeConnectSuccess(AddressWithType address_with_type, std::unique_ptr<LeAclConnection> connection) override {
+ void OnLeConnectSuccess(AddressWithType address_with_type, std::unique_ptr<AclConnection> connection) override {
le_connections_.push_back(std::move(connection));
if (le_connection_promise_ != nullptr) {
le_connection_promise_->set_value();
@@ -428,9 +357,16 @@ class AclManagerNoCallbacksTest : public ::testing::Test {
}
MOCK_METHOD(void, OnLeConnectFail, (AddressWithType, ErrorCode reason), (override));
- std::list<std::shared_ptr<LeAclConnection>> le_connections_;
+ std::list<std::shared_ptr<AclConnection>> le_connections_;
std::unique_ptr<std::promise<void>> le_connection_promise_;
} mock_le_connection_callbacks_;
+
+ class MockAclManagerCallbacks : public AclManagerCallbacks {
+ public:
+ MOCK_METHOD(void, OnMasterLinkKeyComplete, (uint16_t connection_handle, KeyFlag key_flag), (override));
+ MOCK_METHOD(void, OnRoleChange, (Address bd_addr, Role new_role), (override));
+ MOCK_METHOD(void, OnReadDefaultLinkPolicySettingsComplete, (uint16_t default_link_policy_settings), (override));
+ } mock_acl_manager_callbacks_;
};
class AclManagerTest : public AclManagerNoCallbacksTest {
@@ -439,6 +375,7 @@ class AclManagerTest : public AclManagerNoCallbacksTest {
AclManagerNoCallbacksTest::SetUp();
acl_manager_->RegisterCallbacks(&mock_connection_callback_, client_handler_);
acl_manager_->RegisterLeCallbacks(&mock_le_connection_callbacks_, client_handler_);
+ acl_manager_->RegisterAclManagerCallbacks(&mock_acl_manager_callbacks_, client_handler_);
}
};
@@ -451,12 +388,10 @@ class AclManagerWithConnectionTest : public AclManagerTest {
acl_manager_->CreateConnection(remote);
// Wait for the connection request
- auto last_command = test_hci_layer_->GetCommand(OpCode::CREATE_CONNECTION);
- while (!last_command.IsValid()) {
- last_command = test_hci_layer_->GetCommand(OpCode::CREATE_CONNECTION);
- }
-
- EXPECT_CALL(mock_connection_management_callbacks_, OnRoleChange(hci::ErrorCode::SUCCESS, Role::CENTRAL));
+ std::unique_ptr<CommandPacketBuilder> last_command;
+ do {
+ last_command = test_hci_layer_->GetLastCommand();
+ } while (last_command == nullptr);
auto first_connection = GetConnectionFuture();
test_hci_layer_->IncomingEvent(
@@ -469,12 +404,6 @@ class AclManagerWithConnectionTest : public AclManagerTest {
connection_->RegisterCallbacks(&mock_connection_management_callbacks_, client_handler_);
}
- void TearDown() override {
- fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
- fake_registry_.SynchronizeModuleHandler(&AclManager::Factory, std::chrono::milliseconds(20));
- fake_registry_.StopAll();
- }
-
void sync_client_handler() {
std::promise<void> promise;
auto future = promise.get_future();
@@ -484,24 +413,16 @@ class AclManagerWithConnectionTest : public AclManagerTest {
}
uint16_t handle_;
- std::shared_ptr<ClassicAclConnection> connection_;
+ std::shared_ptr<AclConnection> connection_;
class MockConnectionManagementCallbacks : public ConnectionManagementCallbacks {
public:
MOCK_METHOD1(OnConnectionPacketTypeChanged, void(uint16_t packet_type));
- MOCK_METHOD1(OnAuthenticationComplete, void(hci::ErrorCode hci_status));
+ MOCK_METHOD0(OnAuthenticationComplete, void());
MOCK_METHOD1(OnEncryptionChange, void(EncryptionEnabled enabled));
MOCK_METHOD0(OnChangeConnectionLinkKeyComplete, void());
MOCK_METHOD1(OnReadClockOffsetComplete, void(uint16_t clock_offse));
- MOCK_METHOD3(OnModeChange, void(ErrorCode status, Mode current_mode, uint16_t interval));
- MOCK_METHOD5(
- OnSniffSubrating,
- void(
- ErrorCode status,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout));
+ MOCK_METHOD2(OnModeChange, void(Mode current_mode, uint16_t interval));
MOCK_METHOD5(OnQosSetupComplete, void(ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth,
uint32_t latency, uint32_t delay_variation));
MOCK_METHOD6(OnFlowSpecificationComplete,
@@ -518,15 +439,6 @@ class AclManagerWithConnectionTest : public AclManagerTest {
MOCK_METHOD2(OnReadAfhChannelMapComplete, void(AfhMode afh_mode, std::array<uint8_t, 10> afh_channel_map));
MOCK_METHOD1(OnReadRssiComplete, void(uint8_t rssi));
MOCK_METHOD2(OnReadClockComplete, void(uint32_t clock, uint16_t accuracy));
- MOCK_METHOD1(OnCentralLinkKeyComplete, void(KeyFlag flag));
- MOCK_METHOD2(OnRoleChange, void(ErrorCode hci_status, Role new_role));
- MOCK_METHOD1(OnDisconnection, void(ErrorCode reason));
- MOCK_METHOD4(
- OnReadRemoteVersionInformationComplete,
- void(hci::ErrorCode hci_status, uint8_t lmp_version, uint16_t manufacturer_name, uint16_t sub_version));
- MOCK_METHOD1(OnReadRemoteSupportedFeaturesComplete, void(uint64_t features));
- MOCK_METHOD3(
- OnReadRemoteExtendedFeaturesComplete, void(uint8_t page_number, uint8_t max_page_number, uint64_t features));
} mock_connection_management_callbacks_;
};
@@ -540,7 +452,9 @@ TEST_F(AclManagerNoCallbacksTest, acl_connection_before_registered_callbacks) {
fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
fake_registry_.SynchronizeModuleHandler(&AclManager::Factory, std::chrono::milliseconds(20));
fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
- CommandView command = CommandView::Create(test_hci_layer_->GetLastCommand());
+ auto last_command = test_hci_layer_->GetLastCommand();
+ auto packet = GetPacketView(std::move(last_command));
+ CommandPacketView command = CommandPacketView::Create(packet);
EXPECT_TRUE(command.IsValid());
OpCode op_code = command.GetOpCode();
EXPECT_EQ(op_code, OpCode::REJECT_CONNECTION_REQUEST);
@@ -553,10 +467,10 @@ TEST_F(AclManagerTest, invoke_registered_callback_connection_complete_success) {
acl_manager_->CreateConnection(remote);
// Wait for the connection request
- auto last_command = test_hci_layer_->GetCommand(OpCode::CREATE_CONNECTION);
- while (!last_command.IsValid()) {
- last_command = test_hci_layer_->GetCommand(OpCode::CREATE_CONNECTION);
- }
+ std::unique_ptr<CommandPacketBuilder> last_command;
+ do {
+ last_command = test_hci_layer_->GetLastCommand();
+ } while (last_command == nullptr);
auto first_connection = GetConnectionFuture();
@@ -566,7 +480,7 @@ TEST_F(AclManagerTest, invoke_registered_callback_connection_complete_success) {
auto first_connection_status = first_connection.wait_for(kTimeout);
ASSERT_EQ(first_connection_status, std::future_status::ready);
- auto connection = GetLastConnection();
+ std::shared_ptr<AclConnection> connection = GetLastConnection();
ASSERT_EQ(connection->GetAddress(), remote);
}
@@ -577,10 +491,10 @@ TEST_F(AclManagerTest, invoke_registered_callback_connection_complete_fail) {
acl_manager_->CreateConnection(remote);
// Wait for the connection request
- auto last_command = test_hci_layer_->GetCommand(OpCode::CREATE_CONNECTION);
- while (!last_command.IsValid()) {
- last_command = test_hci_layer_->GetCommand(OpCode::CREATE_CONNECTION);
- }
+ std::unique_ptr<CommandPacketBuilder> last_command;
+ do {
+ last_command = test_hci_layer_->GetLastCommand();
+ } while (last_command == nullptr);
EXPECT_CALL(mock_connection_callback_, OnConnectFail(remote, ErrorCode::PAGE_TIMEOUT));
test_hci_layer_->IncomingEvent(
@@ -590,116 +504,45 @@ TEST_F(AclManagerTest, invoke_registered_callback_connection_complete_fail) {
fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
}
-class AclManagerWithLeConnectionTest : public AclManagerTest {
- protected:
- void SetUp() override {
- AclManagerTest::SetUp();
-
- remote_with_type_ = AddressWithType(remote, AddressType::PUBLIC_DEVICE_ADDRESS);
- test_hci_layer_->SetCommandFuture();
- acl_manager_->CreateLeConnection(remote_with_type_, true);
- test_hci_layer_->GetCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- test_hci_layer_->SetCommandFuture();
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_CREATE_CONNECTION);
- auto le_connection_management_command_view =
- LeConnectionManagementCommandView::Create(AclCommandView::Create(packet));
- auto command_view = LeCreateConnectionView::Create(le_connection_management_command_view);
- ASSERT_TRUE(command_view.IsValid());
- if (use_connect_list_) {
- ASSERT_EQ(command_view.GetPeerAddress(), empty_address_with_type.GetAddress());
- ASSERT_EQ(command_view.GetPeerAddressType(), empty_address_with_type.GetAddressType());
- } else {
- ASSERT_EQ(command_view.GetPeerAddress(), remote);
- ASSERT_EQ(command_view.GetPeerAddressType(), AddressType::PUBLIC_DEVICE_ADDRESS);
- }
-
- test_hci_layer_->IncomingEvent(LeCreateConnectionStatusBuilder::Create(ErrorCode::SUCCESS, 0x01));
-
- auto first_connection = GetLeConnectionFuture();
-
- test_hci_layer_->IncomingLeMetaEvent(LeConnectionCompleteBuilder::Create(
- ErrorCode::SUCCESS,
- handle_,
- Role::PERIPHERAL,
- AddressType::PUBLIC_DEVICE_ADDRESS,
- remote,
- 0x0100,
- 0x0010,
- 0x0C80,
- ClockAccuracy::PPM_30));
-
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_REMOVE_DEVICE_FROM_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeRemoveDeviceFromConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-
- auto first_connection_status = first_connection.wait_for(kTimeout);
- ASSERT_EQ(first_connection_status, std::future_status::ready);
+// TODO: implement version of this test where controller supports Extended Advertising Feature in
+// GetControllerLeLocalSupportedFeatures, and LE Extended Create Connection is used
+TEST_F(AclManagerTest, invoke_registered_callback_le_connection_complete_success) {
+ AddressWithType remote_with_type(remote, AddressType::PUBLIC_DEVICE_ADDRESS);
+ test_hci_layer_->SetCommandFuture();
+ acl_manager_->CreateLeConnection(remote_with_type);
- connection_ = GetLastLeConnection();
- }
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::LE_CREATE_CONNECTION);
+ auto le_connection_management_command_view = LeConnectionManagementCommandView::Create(packet);
+ auto command_view = LeCreateConnectionView::Create(le_connection_management_command_view);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetPeerAddress(), remote);
+ EXPECT_EQ(command_view.GetPeerAddressType(), AddressType::PUBLIC_DEVICE_ADDRESS);
- void TearDown() override {
- fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
- fake_registry_.SynchronizeModuleHandler(&AclManager::Factory, std::chrono::milliseconds(20));
- fake_registry_.StopAll();
- }
+ test_hci_layer_->IncomingEvent(LeCreateConnectionStatusBuilder::Create(ErrorCode::SUCCESS, 0x01));
- void sync_client_handler() {
- std::promise<void> promise;
- auto future = promise.get_future();
- client_handler_->Post(common::BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)));
- auto future_status = future.wait_for(std::chrono::seconds(1));
- EXPECT_EQ(future_status, std::future_status::ready);
- }
+ auto first_connection = GetLeConnectionFuture();
- uint16_t handle_ = 0x123;
- std::shared_ptr<LeAclConnection> connection_;
- AddressWithType remote_with_type_;
+ test_hci_layer_->IncomingLeMetaEvent(
+ LeConnectionCompleteBuilder::Create(ErrorCode::SUCCESS, 0x123, Role::SLAVE, AddressType::PUBLIC_DEVICE_ADDRESS,
+ remote, 0x0100, 0x0010, 0x0011, MasterClockAccuracy::PPM_30));
- class MockLeConnectionManagementCallbacks : public LeConnectionManagementCallbacks {
- public:
- MOCK_METHOD1(OnDisconnection, void(ErrorCode reason));
- MOCK_METHOD4(
- OnConnectionUpdate,
- void(
- hci::ErrorCode hci_status,
- uint16_t connection_interval,
- uint16_t connection_latency,
- uint16_t supervision_timeout));
- MOCK_METHOD4(OnDataLengthChange, void(uint16_t tx_octets, uint16_t tx_time, uint16_t rx_octets, uint16_t rx_time));
- MOCK_METHOD4(
- OnReadRemoteVersionInformationComplete,
- void(hci::ErrorCode hci_status, uint8_t version, uint16_t manufacturer_name, uint16_t sub_version));
- MOCK_METHOD3(OnPhyUpdate, void(hci::ErrorCode hci_status, uint8_t tx_phy, uint8_t rx_phy));
- MOCK_METHOD1(OnLocalAddressUpdate, void(AddressWithType address_with_type));
- } mock_le_connection_management_callbacks_;
-};
+ auto first_connection_status = first_connection.wait_for(kTimeout);
+ ASSERT_EQ(first_connection_status, std::future_status::ready);
-// TODO: implement version of this test where controller supports Extended Advertising Feature in
-// GetLeLocalSupportedFeatures, and LE Extended Create Connection is used
-TEST_F(AclManagerWithLeConnectionTest, invoke_registered_callback_le_connection_complete_success) {
- ASSERT_EQ(connection_->GetLocalAddress(), my_initiating_address);
- ASSERT_EQ(connection_->GetRemoteAddress(), remote_with_type_);
+ std::shared_ptr<AclConnection> connection = GetLastLeConnection();
+ ASSERT_EQ(connection->GetAddress(), remote);
}
TEST_F(AclManagerTest, invoke_registered_callback_le_connection_complete_fail) {
AddressWithType remote_with_type(remote, AddressType::PUBLIC_DEVICE_ADDRESS);
test_hci_layer_->SetCommandFuture();
- acl_manager_->CreateLeConnection(remote_with_type, true);
- test_hci_layer_->GetLastCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- test_hci_layer_->SetCommandFuture();
- auto packet = test_hci_layer_->GetLastCommand(OpCode::LE_CREATE_CONNECTION);
- auto le_connection_management_command_view =
- LeConnectionManagementCommandView::Create(AclCommandView::Create(packet));
+ acl_manager_->CreateLeConnection(remote_with_type);
+
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::LE_CREATE_CONNECTION);
+ auto le_connection_management_command_view = LeConnectionManagementCommandView::Create(packet);
auto command_view = LeCreateConnectionView::Create(le_connection_management_command_view);
- ASSERT_TRUE(command_view.IsValid());
- if (use_connect_list_) {
- ASSERT_EQ(command_view.GetPeerAddress(), hci::Address::kEmpty);
- } else {
- ASSERT_EQ(command_view.GetPeerAddress(), remote);
- }
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetPeerAddress(), remote);
EXPECT_EQ(command_view.GetPeerAddressType(), AddressType::PUBLIC_DEVICE_ADDRESS);
test_hci_layer_->IncomingEvent(LeCreateConnectionStatusBuilder::Create(ErrorCode::SUCCESS, 0x01));
@@ -707,222 +550,158 @@ TEST_F(AclManagerTest, invoke_registered_callback_le_connection_complete_fail) {
EXPECT_CALL(mock_le_connection_callbacks_,
OnLeConnectFail(remote_with_type, ErrorCode::CONNECTION_REJECTED_LIMITED_RESOURCES));
test_hci_layer_->IncomingLeMetaEvent(LeConnectionCompleteBuilder::Create(
- ErrorCode::CONNECTION_REJECTED_LIMITED_RESOURCES,
- 0x123,
- Role::PERIPHERAL,
- AddressType::PUBLIC_DEVICE_ADDRESS,
- remote,
- 0x0100,
- 0x0010,
- 0x0011,
- ClockAccuracy::PPM_30));
-
- test_hci_layer_->SetCommandFuture();
- packet = test_hci_layer_->GetLastCommand(OpCode::LE_REMOVE_DEVICE_FROM_CONNECT_LIST);
- le_connection_management_command_view = LeConnectionManagementCommandView::Create(AclCommandView::Create(packet));
- auto remove_command_view = LeRemoveDeviceFromConnectListView::Create(le_connection_management_command_view);
- ASSERT_TRUE(remove_command_view.IsValid());
- test_hci_layer_->IncomingEvent(LeRemoveDeviceFromConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
+ ErrorCode::CONNECTION_REJECTED_LIMITED_RESOURCES, 0x123, Role::SLAVE, AddressType::PUBLIC_DEVICE_ADDRESS, remote,
+ 0x0100, 0x0010, 0x0011, MasterClockAccuracy::PPM_30));
}
-TEST_F(AclManagerTest, cancel_le_connection) {
+TEST_F(AclManagerTest, invoke_registered_callback_le_connection_update_success) {
AddressWithType remote_with_type(remote, AddressType::PUBLIC_DEVICE_ADDRESS);
test_hci_layer_->SetCommandFuture();
- acl_manager_->CreateLeConnection(remote_with_type, true);
- test_hci_layer_->GetLastCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetLastCommand(OpCode::LE_CREATE_CONNECTION);
-
- test_hci_layer_->SetCommandFuture();
- acl_manager_->CancelLeConnect(remote_with_type);
- auto packet = test_hci_layer_->GetLastCommand(OpCode::LE_CREATE_CONNECTION_CANCEL);
- auto le_connection_management_command_view =
- LeConnectionManagementCommandView::Create(AclCommandView::Create(packet));
- auto command_view = LeCreateConnectionCancelView::Create(le_connection_management_command_view);
- ASSERT_TRUE(command_view.IsValid());
-
- test_hci_layer_->IncomingEvent(LeCreateConnectionCancelCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- test_hci_layer_->IncomingLeMetaEvent(LeConnectionCompleteBuilder::Create(
- ErrorCode::UNKNOWN_CONNECTION,
- 0x123,
- Role::PERIPHERAL,
- AddressType::PUBLIC_DEVICE_ADDRESS,
- remote,
- 0x0100,
- 0x0010,
- 0x0011,
- ClockAccuracy::PPM_30));
+ acl_manager_->CreateLeConnection(remote_with_type);
- test_hci_layer_->SetCommandFuture();
- packet = test_hci_layer_->GetLastCommand(OpCode::LE_REMOVE_DEVICE_FROM_CONNECT_LIST);
- le_connection_management_command_view = LeConnectionManagementCommandView::Create(AclCommandView::Create(packet));
- auto remove_command_view = LeRemoveDeviceFromConnectListView::Create(le_connection_management_command_view);
- ASSERT_TRUE(remove_command_view.IsValid());
-
- test_hci_layer_->IncomingEvent(LeRemoveDeviceFromConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-}
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::LE_CREATE_CONNECTION);
+ auto le_connection_management_command_view = LeConnectionManagementCommandView::Create(packet);
+ auto command_view = LeCreateConnectionView::Create(le_connection_management_command_view);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetPeerAddress(), remote);
+ EXPECT_EQ(command_view.GetPeerAddressType(), AddressType::PUBLIC_DEVICE_ADDRESS);
-TEST_F(AclManagerTest, create_connection_with_fast_mode) {
- AddressWithType remote_with_type(remote, AddressType::PUBLIC_DEVICE_ADDRESS);
- test_hci_layer_->SetCommandFuture();
- acl_manager_->CreateLeConnection(remote_with_type, true);
- test_hci_layer_->GetLastCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- test_hci_layer_->SetCommandFuture();
- auto packet = test_hci_layer_->GetLastCommand(OpCode::LE_CREATE_CONNECTION);
- auto command_view =
- LeCreateConnectionView::Create(LeConnectionManagementCommandView::Create(AclCommandView::Create(packet)));
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetLeScanInterval(), kScanIntervalFast);
- ASSERT_EQ(command_view.GetLeScanWindow(), kScanWindowFast);
test_hci_layer_->IncomingEvent(LeCreateConnectionStatusBuilder::Create(ErrorCode::SUCCESS, 0x01));
+
auto first_connection = GetLeConnectionFuture();
- test_hci_layer_->IncomingLeMetaEvent(LeConnectionCompleteBuilder::Create(
- ErrorCode::SUCCESS,
- 0x00,
- Role::PERIPHERAL,
- AddressType::PUBLIC_DEVICE_ADDRESS,
- remote,
- 0x0100,
- 0x0010,
- 0x0C80,
- ClockAccuracy::PPM_30));
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_REMOVE_DEVICE_FROM_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeRemoveDeviceFromConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
+
+ test_hci_layer_->IncomingLeMetaEvent(
+ LeConnectionCompleteBuilder::Create(ErrorCode::SUCCESS, 0x123, Role::SLAVE, AddressType::PUBLIC_DEVICE_ADDRESS,
+ remote, 0x0100, 0x0010, 0x0011, MasterClockAccuracy::PPM_30));
+
auto first_connection_status = first_connection.wait_for(kTimeout);
ASSERT_EQ(first_connection_status, std::future_status::ready);
+
+ std::shared_ptr<AclConnection> connection = GetLastLeConnection();
+ ASSERT_EQ(connection->GetAddress(), remote);
+
+ std::promise<ErrorCode> promise;
+ auto future = promise.get_future();
+ connection->LeConnectionUpdate(
+ 0x0006, 0x0C80, 0x0000, 0x000A,
+ common::BindOnce([](std::promise<ErrorCode> promise, ErrorCode code) { promise.set_value(code); },
+ std::move(promise)),
+ client_handler_);
+ test_hci_layer_->IncomingLeMetaEvent(
+ LeConnectionUpdateCompleteBuilder::Create(ErrorCode::SUCCESS, 0x123, 0x0006, 0x0000, 0x000A));
+ EXPECT_EQ(future.wait_for(std::chrono::milliseconds(3)), std::future_status::ready);
+ EXPECT_EQ(future.get(), ErrorCode::SUCCESS);
}
-TEST_F(AclManagerTest, create_connection_with_slow_mode) {
- AddressWithType remote_with_type(remote, AddressType::PUBLIC_DEVICE_ADDRESS);
- test_hci_layer_->SetCommandFuture();
- acl_manager_->CreateLeConnection(remote_with_type, false);
- test_hci_layer_->GetLastCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- test_hci_layer_->SetCommandFuture();
- auto packet = test_hci_layer_->GetLastCommand(OpCode::LE_CREATE_CONNECTION);
- auto command_view =
- LeCreateConnectionView::Create(LeConnectionManagementCommandView::Create(AclCommandView::Create(packet)));
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetLeScanInterval(), kScanIntervalSlow);
- ASSERT_EQ(command_view.GetLeScanWindow(), kScanWindowSlow);
- test_hci_layer_->IncomingEvent(LeCreateConnectionStatusBuilder::Create(ErrorCode::SUCCESS, 0x01));
- auto first_connection = GetLeConnectionFuture();
- test_hci_layer_->IncomingLeMetaEvent(LeConnectionCompleteBuilder::Create(
- ErrorCode::SUCCESS,
- 0x00,
- Role::PERIPHERAL,
- AddressType::PUBLIC_DEVICE_ADDRESS,
- remote,
- 0x0100,
- 0x0010,
- 0x0C80,
- ClockAccuracy::PPM_30));
+TEST_F(AclManagerTest, invoke_registered_callback_disconnection_complete) {
+ uint16_t handle = 0x123;
+
test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_REMOVE_DEVICE_FROM_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeRemoveDeviceFromConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
+ acl_manager_->CreateConnection(remote);
+
+ // Wait for the connection request
+ std::unique_ptr<CommandPacketBuilder> last_command;
+ do {
+ last_command = test_hci_layer_->GetLastCommand();
+ } while (last_command == nullptr);
+
+ auto first_connection = GetConnectionFuture();
+
+ test_hci_layer_->IncomingEvent(
+ ConnectionCompleteBuilder::Create(ErrorCode::SUCCESS, handle, remote, LinkType::ACL, Enable::DISABLED));
+
auto first_connection_status = first_connection.wait_for(kTimeout);
ASSERT_EQ(first_connection_status, std::future_status::ready);
+
+ std::shared_ptr<AclConnection> connection = GetLastConnection();
+
+ // Register the disconnect handler
+ std::promise<ErrorCode> promise;
+ auto future = promise.get_future();
+ connection->RegisterDisconnectCallback(
+ common::BindOnce([](std::promise<ErrorCode> promise, ErrorCode reason) { promise.set_value(reason); },
+ std::move(promise)),
+ client_handler_);
+
+ test_hci_layer_->IncomingEvent(
+ DisconnectionCompleteBuilder::Create(ErrorCode::SUCCESS, handle, ErrorCode::REMOTE_USER_TERMINATED_CONNECTION));
+
+ auto disconnection_status = future.wait_for(kTimeout);
+ ASSERT_EQ(disconnection_status, std::future_status::ready);
+ ASSERT_EQ(ErrorCode::REMOTE_USER_TERMINATED_CONNECTION, future.get());
+
+ fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
}
-TEST_F(AclManagerWithLeConnectionTest, acl_send_data_one_le_connection) {
- ASSERT_EQ(connection_->GetRemoteAddress(), remote_with_type_);
- ASSERT_EQ(connection_->GetHandle(), handle_);
+TEST_F(AclManagerTest, acl_connection_finish_after_disconnected) {
+ uint16_t handle = 0x123;
- // Send a packet from HCI
- test_hci_layer_->IncomingAclData(handle_);
- auto queue_end = connection_->GetAclQueueEnd();
+ test_hci_layer_->SetCommandFuture();
+ acl_manager_->CreateConnection(remote);
- std::unique_ptr<PacketView<kLittleEndian>> received;
+ // Wait for the connection request
+ std::unique_ptr<CommandPacketBuilder> last_command;
do {
- received = queue_end->TryDequeue();
- } while (received == nullptr);
+ last_command = test_hci_layer_->GetLastCommand();
+ } while (last_command == nullptr);
- PacketView<kLittleEndian> received_packet = *received;
+ auto first_connection = GetConnectionFuture();
- // Send a packet from the connection
- SendAclData(handle_, connection_->GetAclQueueEnd());
+ test_hci_layer_->IncomingEvent(
+ ConnectionCompleteBuilder::Create(ErrorCode::SUCCESS, handle, remote, LinkType::ACL, Enable::DISABLED));
- auto sent_packet = test_hci_layer_->OutgoingAclData();
+ auto first_connection_status = first_connection.wait_for(kTimeout);
+ ASSERT_EQ(first_connection_status, std::future_status::ready);
- // Send another packet from the connection
- SendAclData(handle_, connection_->GetAclQueueEnd());
+ std::shared_ptr<AclConnection> connection = GetLastConnection();
- sent_packet = test_hci_layer_->OutgoingAclData();
-}
+ // Register the disconnect handler
+ std::promise<ErrorCode> promise;
+ auto future = promise.get_future();
+ connection->RegisterDisconnectCallback(
+ common::BindOnce([](std::promise<ErrorCode> promise, ErrorCode reason) { promise.set_value(reason); },
+ std::move(promise)),
+ client_handler_);
-TEST_F(AclManagerWithLeConnectionTest, invoke_registered_callback_le_connection_update_success) {
- ASSERT_EQ(connection_->GetLocalAddress(), my_initiating_address);
- ASSERT_EQ(connection_->GetRemoteAddress(), remote_with_type_);
- ASSERT_EQ(connection_->GetHandle(), handle_);
- connection_->RegisterCallbacks(&mock_le_connection_management_callbacks_, client_handler_);
+ test_hci_layer_->IncomingEvent(DisconnectionCompleteBuilder::Create(
+ ErrorCode::SUCCESS, handle, ErrorCode::REMOTE_DEVICE_TERMINATED_CONNECTION_POWER_OFF));
- std::promise<ErrorCode> promise;
- ErrorCode hci_status = hci::ErrorCode::SUCCESS;
- uint16_t connection_interval_min = 0x0012;
- uint16_t connection_interval_max = 0x0080;
- uint16_t connection_interval = (connection_interval_max + connection_interval_min) / 2;
- uint16_t connection_latency = 0x0001;
- uint16_t supervision_timeout = 0x0A00;
- test_hci_layer_->SetCommandFuture();
- connection_->LeConnectionUpdate(connection_interval_min, connection_interval_max, connection_latency,
- supervision_timeout, 0x10, 0x20);
- auto update_packet = test_hci_layer_->GetCommand(OpCode::LE_CONNECTION_UPDATE);
- auto update_view =
- LeConnectionUpdateView::Create(LeConnectionManagementCommandView::Create(AclCommandView::Create(update_packet)));
- ASSERT_TRUE(update_view.IsValid());
- EXPECT_EQ(update_view.GetConnectionHandle(), handle_);
- EXPECT_CALL(
- mock_le_connection_management_callbacks_,
- OnConnectionUpdate(hci_status, connection_interval, connection_latency, supervision_timeout));
- test_hci_layer_->IncomingLeMetaEvent(LeConnectionUpdateCompleteBuilder::Create(
- ErrorCode::SUCCESS, handle_, connection_interval, connection_latency, supervision_timeout));
+ auto disconnection_status = future.wait_for(kTimeout);
+ ASSERT_EQ(disconnection_status, std::future_status::ready);
+ ASSERT_EQ(ErrorCode::REMOTE_DEVICE_TERMINATED_CONNECTION_POWER_OFF, future.get());
+
+ connection->Finish();
}
-TEST_F(AclManagerWithLeConnectionTest, invoke_registered_callback_le_disconnect) {
- ASSERT_EQ(connection_->GetRemoteAddress(), remote_with_type_);
- ASSERT_EQ(connection_->GetHandle(), handle_);
- connection_->RegisterCallbacks(&mock_le_connection_management_callbacks_, client_handler_);
+TEST_F(AclManagerTest, acl_send_data_one_connection) {
+ uint16_t handle = 0x123;
- auto reason = ErrorCode::REMOTE_USER_TERMINATED_CONNECTION;
- EXPECT_CALL(mock_le_connection_management_callbacks_, OnDisconnection(reason));
- test_hci_layer_->Disconnect(handle_, reason);
-}
+ acl_manager_->CreateConnection(remote);
-TEST_F(AclManagerWithLeConnectionTest, DISABLED_invoke_registered_callback_le_disconnect_data_race) {
- ASSERT_EQ(connection_->GetRemoteAddress(), remote_with_type_);
- ASSERT_EQ(connection_->GetHandle(), handle_);
- connection_->RegisterCallbacks(&mock_le_connection_management_callbacks_, client_handler_);
+ // Wait for the connection request
+ std::unique_ptr<CommandPacketBuilder> last_command;
+ do {
+ last_command = test_hci_layer_->GetLastCommand();
+ } while (last_command == nullptr);
- test_hci_layer_->IncomingAclData(handle_);
- auto reason = ErrorCode::REMOTE_USER_TERMINATED_CONNECTION;
- EXPECT_CALL(mock_le_connection_management_callbacks_, OnDisconnection(reason));
- test_hci_layer_->Disconnect(handle_, reason);
-}
+ auto first_connection = GetConnectionFuture();
-TEST_F(AclManagerWithLeConnectionTest, invoke_registered_callback_le_queue_disconnect) {
- auto reason = ErrorCode::REMOTE_USER_TERMINATED_CONNECTION;
- test_hci_layer_->Disconnect(handle_, reason);
- fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
- fake_registry_.SynchronizeModuleHandler(&AclManager::Factory, std::chrono::milliseconds(20));
+ test_hci_layer_->IncomingEvent(
+ ConnectionCompleteBuilder::Create(ErrorCode::SUCCESS, handle, remote, LinkType::ACL, Enable::DISABLED));
- EXPECT_CALL(mock_le_connection_management_callbacks_, OnDisconnection(reason));
- connection_->RegisterCallbacks(&mock_le_connection_management_callbacks_, client_handler_);
- sync_client_handler();
-}
+ auto first_connection_status = first_connection.wait_for(kTimeout);
+ ASSERT_EQ(first_connection_status, std::future_status::ready);
-TEST_F(AclManagerWithConnectionTest, invoke_registered_callback_disconnection_complete) {
- auto reason = ErrorCode::REMOTE_USER_TERMINATED_CONNECTION;
- EXPECT_CALL(mock_connection_management_callbacks_, OnDisconnection(reason));
- test_hci_layer_->Disconnect(handle_, reason);
-}
+ std::shared_ptr<AclConnection> connection = GetLastConnection();
+
+ // Register the disconnect handler
+ connection->RegisterDisconnectCallback(
+ common::Bind([](std::shared_ptr<AclConnection> conn, ErrorCode) { conn->Finish(); }, connection),
+ client_handler_);
-TEST_F(AclManagerWithConnectionTest, acl_send_data_one_connection) {
// Send a packet from HCI
- test_hci_layer_->IncomingAclData(handle_);
- auto queue_end = connection_->GetAclQueueEnd();
+ test_hci_layer_->IncomingAclData(handle);
+ auto queue_end = connection->GetAclQueueEnd();
std::unique_ptr<PacketView<kLittleEndian>> received;
do {
@@ -932,80 +711,120 @@ TEST_F(AclManagerWithConnectionTest, acl_send_data_one_connection) {
PacketView<kLittleEndian> received_packet = *received;
// Send a packet from the connection
- SendAclData(handle_, connection_->GetAclQueueEnd());
+ SendAclData(handle, connection);
auto sent_packet = test_hci_layer_->OutgoingAclData();
// Send another packet from the connection
- SendAclData(handle_, connection_->GetAclQueueEnd());
+ SendAclData(handle, connection);
sent_packet = test_hci_layer_->OutgoingAclData();
- test_hci_layer_->SetCommandFuture();
- auto reason = ErrorCode::AUTHENTICATION_FAILURE;
- EXPECT_CALL(mock_connection_management_callbacks_, OnDisconnection(reason));
- connection_->Disconnect(DisconnectReason::AUTHENTICATION_FAILURE);
- auto packet = test_hci_layer_->GetCommand(OpCode::DISCONNECT);
- auto command_view = DisconnectView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetConnectionHandle(), handle_);
- test_hci_layer_->Disconnect(handle_, reason);
+ connection->Disconnect(DisconnectReason::AUTHENTICATION_FAILURE);
}
-TEST_F(AclManagerWithConnectionTest, acl_send_data_credits) {
+TEST_F(AclManagerTest, acl_send_data_credits) {
+ uint16_t handle = 0x123;
+
+ acl_manager_->CreateConnection(remote);
+
+ // Wait for the connection request
+ std::unique_ptr<CommandPacketBuilder> last_command;
+ do {
+ last_command = test_hci_layer_->GetLastCommand();
+ } while (last_command == nullptr);
+
+ auto first_connection = GetConnectionFuture();
+ test_hci_layer_->IncomingEvent(
+ ConnectionCompleteBuilder::Create(ErrorCode::SUCCESS, handle, remote, LinkType::ACL, Enable::DISABLED));
+
+ auto first_connection_status = first_connection.wait_for(kTimeout);
+ ASSERT_EQ(first_connection_status, std::future_status::ready);
+
+ std::shared_ptr<AclConnection> connection = GetLastConnection();
+
+ // Register the disconnect handler
+ connection->RegisterDisconnectCallback(
+ common::BindOnce([](std::shared_ptr<AclConnection> conn, ErrorCode) { conn->Finish(); }, connection),
+ client_handler_);
+
// Use all the credits
for (uint16_t credits = 0; credits < test_controller_->total_acl_buffers_; credits++) {
// Send a packet from the connection
- SendAclData(handle_, connection_->GetAclQueueEnd());
+ SendAclData(handle, connection);
auto sent_packet = test_hci_layer_->OutgoingAclData();
}
// Send another packet from the connection
- SendAclData(handle_, connection_->GetAclQueueEnd());
+ SendAclData(handle, connection);
test_hci_layer_->AssertNoOutgoingAclData();
- test_controller_->CompletePackets(handle_, 1);
+ test_controller_->CompletePackets(handle, 1);
auto after_credits_sent_packet = test_hci_layer_->OutgoingAclData();
+
+ connection->Disconnect(DisconnectReason::AUTHENTICATION_FAILURE);
}
TEST_F(AclManagerWithConnectionTest, send_switch_role) {
test_hci_layer_->SetCommandFuture();
- acl_manager_->SwitchRole(connection_->GetAddress(), Role::PERIPHERAL);
- auto packet = test_hci_layer_->GetCommand(OpCode::SWITCH_ROLE);
+ acl_manager_->SwitchRole(connection_->GetAddress(), Role::SLAVE);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::SWITCH_ROLE);
auto command_view = SwitchRoleView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetBdAddr(), connection_->GetAddress());
- ASSERT_EQ(command_view.GetRole(), Role::PERIPHERAL);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetBdAddr(), connection_->GetAddress());
+ EXPECT_EQ(command_view.GetRole(), Role::SLAVE);
- EXPECT_CALL(mock_connection_management_callbacks_, OnRoleChange(hci::ErrorCode::SUCCESS, Role::PERIPHERAL));
+ EXPECT_CALL(mock_acl_manager_callbacks_, OnRoleChange(connection_->GetAddress(), Role::SLAVE));
+ test_hci_layer_->IncomingEvent(RoleChangeBuilder::Create(ErrorCode::SUCCESS, connection_->GetAddress(), Role::SLAVE));
+}
+
+TEST_F(AclManagerWithConnectionTest, send_read_default_link_policy_settings) {
+ test_hci_layer_->SetCommandFuture();
+ acl_manager_->ReadDefaultLinkPolicySettings();
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::READ_DEFAULT_LINK_POLICY_SETTINGS);
+ auto command_view = ReadDefaultLinkPolicySettingsView::Create(packet);
+ ASSERT(command_view.IsValid());
+
+ test_hci_layer_->SetCommandFuture();
+ EXPECT_CALL(mock_acl_manager_callbacks_, OnReadDefaultLinkPolicySettingsComplete(0x07));
+ uint8_t num_packets = 1;
test_hci_layer_->IncomingEvent(
- RoleChangeBuilder::Create(ErrorCode::SUCCESS, connection_->GetAddress(), Role::PERIPHERAL));
+ ReadDefaultLinkPolicySettingsCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS, 0x07));
}
TEST_F(AclManagerWithConnectionTest, send_write_default_link_policy_settings) {
test_hci_layer_->SetCommandFuture();
- uint16_t link_policy_settings = 0x05;
- acl_manager_->WriteDefaultLinkPolicySettings(link_policy_settings);
- auto packet = test_hci_layer_->GetCommand(OpCode::WRITE_DEFAULT_LINK_POLICY_SETTINGS);
+ acl_manager_->WriteDefaultLinkPolicySettings(0x05);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::WRITE_DEFAULT_LINK_POLICY_SETTINGS);
auto command_view = WriteDefaultLinkPolicySettingsView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetDefaultLinkPolicySettings(), 0x05);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetDefaultLinkPolicySettings(), 0x05);
uint8_t num_packets = 1;
test_hci_layer_->IncomingEvent(
WriteDefaultLinkPolicySettingsCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS));
+}
- ASSERT_EQ(link_policy_settings, acl_manager_->ReadDefaultLinkPolicySettings());
+TEST_F(AclManagerWithConnectionTest, send_change_connection_packet_type) {
+ test_hci_layer_->SetCommandFuture();
+ connection_->ChangeConnectionPacketType(0xEE1C);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::CHANGE_CONNECTION_PACKET_TYPE);
+ auto command_view = ChangeConnectionPacketTypeView::Create(packet);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetPacketType(), 0xEE1C);
+
+ EXPECT_CALL(mock_connection_management_callbacks_, OnConnectionPacketTypeChanged(0xEE1C));
+ test_hci_layer_->IncomingEvent(ConnectionPacketTypeChangedBuilder::Create(ErrorCode::SUCCESS, handle_, 0xEE1C));
}
TEST_F(AclManagerWithConnectionTest, send_authentication_requested) {
test_hci_layer_->SetCommandFuture();
connection_->AuthenticationRequested();
- auto packet = test_hci_layer_->GetCommand(OpCode::AUTHENTICATION_REQUESTED);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::AUTHENTICATION_REQUESTED);
auto command_view = AuthenticationRequestedView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
EXPECT_CALL(mock_connection_management_callbacks_, OnAuthenticationComplete);
test_hci_layer_->IncomingEvent(AuthenticationCompleteBuilder::Create(ErrorCode::SUCCESS, handle_));
@@ -1014,9 +833,9 @@ TEST_F(AclManagerWithConnectionTest, send_authentication_requested) {
TEST_F(AclManagerWithConnectionTest, send_read_clock_offset) {
test_hci_layer_->SetCommandFuture();
connection_->ReadClockOffset();
- auto packet = test_hci_layer_->GetCommand(OpCode::READ_CLOCK_OFFSET);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::READ_CLOCK_OFFSET);
auto command_view = ReadClockOffsetView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
EXPECT_CALL(mock_connection_management_callbacks_, OnReadClockOffsetComplete(0x0123));
test_hci_layer_->IncomingEvent(ReadClockOffsetCompleteBuilder::Create(ErrorCode::SUCCESS, handle_, 0x0123));
@@ -1025,53 +844,53 @@ TEST_F(AclManagerWithConnectionTest, send_read_clock_offset) {
TEST_F(AclManagerWithConnectionTest, send_hold_mode) {
test_hci_layer_->SetCommandFuture();
connection_->HoldMode(0x0500, 0x0020);
- auto packet = test_hci_layer_->GetCommand(OpCode::HOLD_MODE);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::HOLD_MODE);
auto command_view = HoldModeView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetHoldModeMaxInterval(), 0x0500);
- ASSERT_EQ(command_view.GetHoldModeMinInterval(), 0x0020);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetHoldModeMaxInterval(), 0x0500);
+ EXPECT_EQ(command_view.GetHoldModeMinInterval(), 0x0020);
- EXPECT_CALL(mock_connection_management_callbacks_, OnModeChange(ErrorCode::SUCCESS, Mode::HOLD, 0x0020));
+ EXPECT_CALL(mock_connection_management_callbacks_, OnModeChange(Mode::HOLD, 0x0020));
test_hci_layer_->IncomingEvent(ModeChangeBuilder::Create(ErrorCode::SUCCESS, handle_, Mode::HOLD, 0x0020));
}
TEST_F(AclManagerWithConnectionTest, send_sniff_mode) {
test_hci_layer_->SetCommandFuture();
connection_->SniffMode(0x0500, 0x0020, 0x0040, 0x0014);
- auto packet = test_hci_layer_->GetCommand(OpCode::SNIFF_MODE);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::SNIFF_MODE);
auto command_view = SniffModeView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetSniffMaxInterval(), 0x0500);
- ASSERT_EQ(command_view.GetSniffMinInterval(), 0x0020);
- ASSERT_EQ(command_view.GetSniffAttempt(), 0x0040);
- ASSERT_EQ(command_view.GetSniffTimeout(), 0x0014);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetSniffMaxInterval(), 0x0500);
+ EXPECT_EQ(command_view.GetSniffMinInterval(), 0x0020);
+ EXPECT_EQ(command_view.GetSniffAttempt(), 0x0040);
+ EXPECT_EQ(command_view.GetSniffTimeout(), 0x0014);
- EXPECT_CALL(mock_connection_management_callbacks_, OnModeChange(ErrorCode::SUCCESS, Mode::SNIFF, 0x0028));
+ EXPECT_CALL(mock_connection_management_callbacks_, OnModeChange(Mode::SNIFF, 0x0028));
test_hci_layer_->IncomingEvent(ModeChangeBuilder::Create(ErrorCode::SUCCESS, handle_, Mode::SNIFF, 0x0028));
}
TEST_F(AclManagerWithConnectionTest, send_exit_sniff_mode) {
test_hci_layer_->SetCommandFuture();
connection_->ExitSniffMode();
- auto packet = test_hci_layer_->GetCommand(OpCode::EXIT_SNIFF_MODE);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::EXIT_SNIFF_MODE);
auto command_view = ExitSniffModeView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
- EXPECT_CALL(mock_connection_management_callbacks_, OnModeChange(ErrorCode::SUCCESS, Mode::ACTIVE, 0x00));
+ EXPECT_CALL(mock_connection_management_callbacks_, OnModeChange(Mode::ACTIVE, 0x00));
test_hci_layer_->IncomingEvent(ModeChangeBuilder::Create(ErrorCode::SUCCESS, handle_, Mode::ACTIVE, 0x00));
}
TEST_F(AclManagerWithConnectionTest, send_qos_setup) {
test_hci_layer_->SetCommandFuture();
connection_->QosSetup(ServiceType::BEST_EFFORT, 0x1234, 0x1233, 0x1232, 0x1231);
- auto packet = test_hci_layer_->GetCommand(OpCode::QOS_SETUP);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::QOS_SETUP);
auto command_view = QosSetupView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetServiceType(), ServiceType::BEST_EFFORT);
- ASSERT_EQ(command_view.GetTokenRate(), 0x1234);
- ASSERT_EQ(command_view.GetPeakBandwidth(), 0x1233);
- ASSERT_EQ(command_view.GetLatency(), 0x1232);
- ASSERT_EQ(command_view.GetDelayVariation(), 0x1231);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetServiceType(), ServiceType::BEST_EFFORT);
+ EXPECT_EQ(command_view.GetTokenRate(), 0x1234);
+ EXPECT_EQ(command_view.GetPeakBandwidth(), 0x1233);
+ EXPECT_EQ(command_view.GetLatency(), 0x1232);
+ EXPECT_EQ(command_view.GetDelayVariation(), 0x1231);
EXPECT_CALL(mock_connection_management_callbacks_,
OnQosSetupComplete(ServiceType::BEST_EFFORT, 0x1234, 0x1233, 0x1232, 0x1231));
@@ -1083,15 +902,15 @@ TEST_F(AclManagerWithConnectionTest, send_flow_specification) {
test_hci_layer_->SetCommandFuture();
connection_->FlowSpecification(FlowDirection::OUTGOING_FLOW, ServiceType::BEST_EFFORT, 0x1234, 0x1233, 0x1232,
0x1231);
- auto packet = test_hci_layer_->GetCommand(OpCode::FLOW_SPECIFICATION);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::FLOW_SPECIFICATION);
auto command_view = FlowSpecificationView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetFlowDirection(), FlowDirection::OUTGOING_FLOW);
- ASSERT_EQ(command_view.GetServiceType(), ServiceType::BEST_EFFORT);
- ASSERT_EQ(command_view.GetTokenRate(), 0x1234);
- ASSERT_EQ(command_view.GetTokenBucketSize(), 0x1233);
- ASSERT_EQ(command_view.GetPeakBandwidth(), 0x1232);
- ASSERT_EQ(command_view.GetAccessLatency(), 0x1231);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetFlowDirection(), FlowDirection::OUTGOING_FLOW);
+ EXPECT_EQ(command_view.GetServiceType(), ServiceType::BEST_EFFORT);
+ EXPECT_EQ(command_view.GetTokenRate(), 0x1234);
+ EXPECT_EQ(command_view.GetTokenBucketSize(), 0x1233);
+ EXPECT_EQ(command_view.GetPeakBandwidth(), 0x1232);
+ EXPECT_EQ(command_view.GetAccessLatency(), 0x1231);
EXPECT_CALL(mock_connection_management_callbacks_,
OnFlowSpecificationComplete(FlowDirection::OUTGOING_FLOW, ServiceType::BEST_EFFORT, 0x1234, 0x1233,
@@ -1104,9 +923,9 @@ TEST_F(AclManagerWithConnectionTest, send_flow_specification) {
TEST_F(AclManagerWithConnectionTest, send_flush) {
test_hci_layer_->SetCommandFuture();
connection_->Flush();
- auto packet = test_hci_layer_->GetCommand(OpCode::FLUSH);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::FLUSH);
auto command_view = FlushView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
EXPECT_CALL(mock_connection_management_callbacks_, OnFlushOccurred());
test_hci_layer_->IncomingEvent(FlushOccurredBuilder::Create(handle_));
@@ -1115,22 +934,22 @@ TEST_F(AclManagerWithConnectionTest, send_flush) {
TEST_F(AclManagerWithConnectionTest, send_role_discovery) {
test_hci_layer_->SetCommandFuture();
connection_->RoleDiscovery();
- auto packet = test_hci_layer_->GetCommand(OpCode::ROLE_DISCOVERY);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::ROLE_DISCOVERY);
auto command_view = RoleDiscoveryView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
- EXPECT_CALL(mock_connection_management_callbacks_, OnRoleDiscoveryComplete(Role::CENTRAL));
+ EXPECT_CALL(mock_connection_management_callbacks_, OnRoleDiscoveryComplete(Role::MASTER));
uint8_t num_packets = 1;
test_hci_layer_->IncomingEvent(
- RoleDiscoveryCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS, handle_, Role::CENTRAL));
+ RoleDiscoveryCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS, handle_, Role::MASTER));
}
TEST_F(AclManagerWithConnectionTest, send_read_link_policy_settings) {
test_hci_layer_->SetCommandFuture();
connection_->ReadLinkPolicySettings();
- auto packet = test_hci_layer_->GetCommand(OpCode::READ_LINK_POLICY_SETTINGS);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::READ_LINK_POLICY_SETTINGS);
auto command_view = ReadLinkPolicySettingsView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
EXPECT_CALL(mock_connection_management_callbacks_, OnReadLinkPolicySettingsComplete(0x07));
uint8_t num_packets = 1;
@@ -1141,10 +960,10 @@ TEST_F(AclManagerWithConnectionTest, send_read_link_policy_settings) {
TEST_F(AclManagerWithConnectionTest, send_write_link_policy_settings) {
test_hci_layer_->SetCommandFuture();
connection_->WriteLinkPolicySettings(0x05);
- auto packet = test_hci_layer_->GetCommand(OpCode::WRITE_LINK_POLICY_SETTINGS);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::WRITE_LINK_POLICY_SETTINGS);
auto command_view = WriteLinkPolicySettingsView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetLinkPolicySettings(), 0x05);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetLinkPolicySettings(), 0x05);
uint8_t num_packets = 1;
test_hci_layer_->IncomingEvent(
@@ -1154,12 +973,12 @@ TEST_F(AclManagerWithConnectionTest, send_write_link_policy_settings) {
TEST_F(AclManagerWithConnectionTest, send_sniff_subrating) {
test_hci_layer_->SetCommandFuture();
connection_->SniffSubrating(0x1234, 0x1235, 0x1236);
- auto packet = test_hci_layer_->GetCommand(OpCode::SNIFF_SUBRATING);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::SNIFF_SUBRATING);
auto command_view = SniffSubratingView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetMaximumLatency(), 0x1234);
- ASSERT_EQ(command_view.GetMinimumRemoteTimeout(), 0x1235);
- ASSERT_EQ(command_view.GetMinimumLocalTimeout(), 0x1236);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetMaximumLatency(), 0x1234);
+ EXPECT_EQ(command_view.GetMinimumRemoteTimeout(), 0x1235);
+ EXPECT_EQ(command_view.GetMinimumLocalTimeout(), 0x1236);
uint8_t num_packets = 1;
test_hci_layer_->IncomingEvent(SniffSubratingCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS, handle_));
@@ -1168,9 +987,9 @@ TEST_F(AclManagerWithConnectionTest, send_sniff_subrating) {
TEST_F(AclManagerWithConnectionTest, send_read_automatic_flush_timeout) {
test_hci_layer_->SetCommandFuture();
connection_->ReadAutomaticFlushTimeout();
- auto packet = test_hci_layer_->GetCommand(OpCode::READ_AUTOMATIC_FLUSH_TIMEOUT);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::READ_AUTOMATIC_FLUSH_TIMEOUT);
auto command_view = ReadAutomaticFlushTimeoutView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
EXPECT_CALL(mock_connection_management_callbacks_, OnReadAutomaticFlushTimeoutComplete(0x07ff));
uint8_t num_packets = 1;
@@ -1181,10 +1000,10 @@ TEST_F(AclManagerWithConnectionTest, send_read_automatic_flush_timeout) {
TEST_F(AclManagerWithConnectionTest, send_write_automatic_flush_timeout) {
test_hci_layer_->SetCommandFuture();
connection_->WriteAutomaticFlushTimeout(0x07FF);
- auto packet = test_hci_layer_->GetCommand(OpCode::WRITE_AUTOMATIC_FLUSH_TIMEOUT);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::WRITE_AUTOMATIC_FLUSH_TIMEOUT);
auto command_view = WriteAutomaticFlushTimeoutView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetFlushTimeout(), 0x07FF);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetFlushTimeout(), 0x07FF);
uint8_t num_packets = 1;
test_hci_layer_->IncomingEvent(
@@ -1194,10 +1013,10 @@ TEST_F(AclManagerWithConnectionTest, send_write_automatic_flush_timeout) {
TEST_F(AclManagerWithConnectionTest, send_read_transmit_power_level) {
test_hci_layer_->SetCommandFuture();
connection_->ReadTransmitPowerLevel(TransmitPowerLevelType::CURRENT);
- auto packet = test_hci_layer_->GetCommand(OpCode::READ_TRANSMIT_POWER_LEVEL);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::READ_TRANSMIT_POWER_LEVEL);
auto command_view = ReadTransmitPowerLevelView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetTransmitPowerLevelType(), TransmitPowerLevelType::CURRENT);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetType(), TransmitPowerLevelType::CURRENT);
EXPECT_CALL(mock_connection_management_callbacks_, OnReadTransmitPowerLevelComplete(0x07));
uint8_t num_packets = 1;
@@ -1208,9 +1027,9 @@ TEST_F(AclManagerWithConnectionTest, send_read_transmit_power_level) {
TEST_F(AclManagerWithConnectionTest, send_read_link_supervision_timeout) {
test_hci_layer_->SetCommandFuture();
connection_->ReadLinkSupervisionTimeout();
- auto packet = test_hci_layer_->GetCommand(OpCode::READ_LINK_SUPERVISION_TIMEOUT);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::READ_LINK_SUPERVISION_TIMEOUT);
auto command_view = ReadLinkSupervisionTimeoutView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
EXPECT_CALL(mock_connection_management_callbacks_, OnReadLinkSupervisionTimeoutComplete(0x5677));
uint8_t num_packets = 1;
@@ -1221,10 +1040,10 @@ TEST_F(AclManagerWithConnectionTest, send_read_link_supervision_timeout) {
TEST_F(AclManagerWithConnectionTest, send_write_link_supervision_timeout) {
test_hci_layer_->SetCommandFuture();
connection_->WriteLinkSupervisionTimeout(0x5678);
- auto packet = test_hci_layer_->GetCommand(OpCode::WRITE_LINK_SUPERVISION_TIMEOUT);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::WRITE_LINK_SUPERVISION_TIMEOUT);
auto command_view = WriteLinkSupervisionTimeoutView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetLinkSupervisionTimeout(), 0x5678);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetLinkSupervisionTimeout(), 0x5678);
uint8_t num_packets = 1;
test_hci_layer_->IncomingEvent(
@@ -1234,9 +1053,9 @@ TEST_F(AclManagerWithConnectionTest, send_write_link_supervision_timeout) {
TEST_F(AclManagerWithConnectionTest, send_read_failed_contact_counter) {
test_hci_layer_->SetCommandFuture();
connection_->ReadFailedContactCounter();
- auto packet = test_hci_layer_->GetCommand(OpCode::READ_FAILED_CONTACT_COUNTER);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::READ_FAILED_CONTACT_COUNTER);
auto command_view = ReadFailedContactCounterView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
EXPECT_CALL(mock_connection_management_callbacks_, OnReadFailedContactCounterComplete(0x00));
uint8_t num_packets = 1;
@@ -1247,9 +1066,9 @@ TEST_F(AclManagerWithConnectionTest, send_read_failed_contact_counter) {
TEST_F(AclManagerWithConnectionTest, send_reset_failed_contact_counter) {
test_hci_layer_->SetCommandFuture();
connection_->ResetFailedContactCounter();
- auto packet = test_hci_layer_->GetCommand(OpCode::RESET_FAILED_CONTACT_COUNTER);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::RESET_FAILED_CONTACT_COUNTER);
auto command_view = ResetFailedContactCounterView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
uint8_t num_packets = 1;
test_hci_layer_->IncomingEvent(
@@ -1259,9 +1078,9 @@ TEST_F(AclManagerWithConnectionTest, send_reset_failed_contact_counter) {
TEST_F(AclManagerWithConnectionTest, send_read_link_quality) {
test_hci_layer_->SetCommandFuture();
connection_->ReadLinkQuality();
- auto packet = test_hci_layer_->GetCommand(OpCode::READ_LINK_QUALITY);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::READ_LINK_QUALITY);
auto command_view = ReadLinkQualityView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
EXPECT_CALL(mock_connection_management_callbacks_, OnReadLinkQualityComplete(0xa9));
uint8_t num_packets = 1;
@@ -1272,9 +1091,9 @@ TEST_F(AclManagerWithConnectionTest, send_read_link_quality) {
TEST_F(AclManagerWithConnectionTest, send_read_afh_channel_map) {
test_hci_layer_->SetCommandFuture();
connection_->ReadAfhChannelMap();
- auto packet = test_hci_layer_->GetCommand(OpCode::READ_AFH_CHANNEL_MAP);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::READ_AFH_CHANNEL_MAP);
auto command_view = ReadAfhChannelMapView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
std::array<uint8_t, 10> afh_channel_map = {0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09};
EXPECT_CALL(mock_connection_management_callbacks_,
@@ -1287,9 +1106,9 @@ TEST_F(AclManagerWithConnectionTest, send_read_afh_channel_map) {
TEST_F(AclManagerWithConnectionTest, send_read_rssi) {
test_hci_layer_->SetCommandFuture();
connection_->ReadRssi();
- auto packet = test_hci_layer_->GetCommand(OpCode::READ_RSSI);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::READ_RSSI);
auto command_view = ReadRssiView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
+ ASSERT(command_view.IsValid());
sync_client_handler();
EXPECT_CALL(mock_connection_management_callbacks_, OnReadRssiComplete(0x00));
uint8_t num_packets = 1;
@@ -1299,10 +1118,10 @@ TEST_F(AclManagerWithConnectionTest, send_read_rssi) {
TEST_F(AclManagerWithConnectionTest, send_read_clock) {
test_hci_layer_->SetCommandFuture();
connection_->ReadClock(WhichClock::LOCAL);
- auto packet = test_hci_layer_->GetCommand(OpCode::READ_CLOCK);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::READ_CLOCK);
auto command_view = ReadClockView::Create(packet);
- ASSERT_TRUE(command_view.IsValid());
- ASSERT_EQ(command_view.GetWhichClock(), WhichClock::LOCAL);
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(command_view.GetWhichClock(), WhichClock::LOCAL);
EXPECT_CALL(mock_connection_management_callbacks_, OnReadClockComplete(0x00002e6a, 0x0000));
uint8_t num_packets = 1;
@@ -1310,255 +1129,6 @@ TEST_F(AclManagerWithConnectionTest, send_read_clock) {
ReadClockCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS, handle_, 0x00002e6a, 0x0000));
}
-class AclManagerWithResolvableAddressTest : public AclManagerNoCallbacksTest {
- protected:
- void SetUp() override {
- test_hci_layer_ = new TestHciLayer; // Ownership is transferred to registry
- test_controller_ = new TestController;
- fake_registry_.InjectTestModule(&HciLayer::Factory, test_hci_layer_);
- fake_registry_.InjectTestModule(&Controller::Factory, test_controller_);
- client_handler_ = fake_registry_.GetTestModuleHandler(&HciLayer::Factory);
- ASSERT_NE(client_handler_, nullptr);
- test_hci_layer_->SetCommandFuture();
- fake_registry_.Start<AclManager>(&thread_);
- acl_manager_ = static_cast<AclManager*>(fake_registry_.GetModuleUnderTest(&AclManager::Factory));
- Address::FromString("A1:A2:A3:A4:A5:A6", remote);
-
- hci::Address address;
- Address::FromString("D0:05:04:03:02:01", address);
- hci::AddressWithType address_with_type(address, hci::AddressType::RANDOM_DEVICE_ADDRESS);
- acl_manager_->RegisterCallbacks(&mock_connection_callback_, client_handler_);
- acl_manager_->RegisterLeCallbacks(&mock_le_connection_callbacks_, client_handler_);
- auto minimum_rotation_time = std::chrono::milliseconds(7 * 60 * 1000);
- auto maximum_rotation_time = std::chrono::milliseconds(15 * 60 * 1000);
- acl_manager_->SetPrivacyPolicyForInitiatorAddress(
- LeAddressManager::AddressPolicy::USE_RESOLVABLE_ADDRESS,
- address_with_type,
- minimum_rotation_time,
- maximum_rotation_time);
-
- test_hci_layer_->GetLastCommand(OpCode::LE_SET_RANDOM_ADDRESS);
- test_hci_layer_->IncomingEvent(LeSetRandomAddressCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- }
-};
-
-TEST_F(AclManagerWithResolvableAddressTest, create_connection_cancel_fail) {
- auto remote_with_type_ = AddressWithType(remote, AddressType::PUBLIC_DEVICE_ADDRESS);
- test_hci_layer_->SetCommandFuture();
- acl_manager_->CreateLeConnection(remote_with_type_, true);
-
- // Set random address
- test_hci_layer_->GetLastCommand(OpCode::LE_SET_RANDOM_ADDRESS);
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->IncomingEvent(LeSetRandomAddressCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-
- // Add device to connect list
- test_hci_layer_->GetLastCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-
- // send create connection command
- test_hci_layer_->GetLastCommand(OpCode::LE_CREATE_CONNECTION);
- test_hci_layer_->IncomingEvent(LeCreateConnectionStatusBuilder::Create(ErrorCode::SUCCESS, 0x01));
-
- fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
- fake_registry_.SynchronizeModuleHandler(&AclManager::Factory, std::chrono::milliseconds(20));
-
- Address remote2;
- Address::FromString("A1:A2:A3:A4:A5:A7", remote2);
- auto remote_with_type2 = AddressWithType(remote2, AddressType::PUBLIC_DEVICE_ADDRESS);
-
- // create another connection
- test_hci_layer_->SetCommandFuture();
- acl_manager_->CreateLeConnection(remote_with_type2, true);
-
- // cancel previous connection
- test_hci_layer_->GetLastCommand(OpCode::LE_CREATE_CONNECTION_CANCEL);
-
- // receive connection complete of first device
- test_hci_layer_->IncomingLeMetaEvent(LeConnectionCompleteBuilder::Create(
- ErrorCode::SUCCESS,
- 0x123,
- Role::PERIPHERAL,
- AddressType::PUBLIC_DEVICE_ADDRESS,
- remote,
- 0x0100,
- 0x0010,
- 0x0011,
- ClockAccuracy::PPM_30));
-
- // receive create connection cancel complete with ErrorCode::CONNECTION_ALREADY_EXISTS
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->IncomingEvent(
- LeCreateConnectionCancelCompleteBuilder::Create(0x01, ErrorCode::CONNECTION_ALREADY_EXISTS));
-
- // Add another device to connect list
- test_hci_layer_->GetLastCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-}
-
-class AclManagerLifeCycleTest : public AclManagerNoCallbacksTest {
- protected:
- void SetUp() override {
- AclManagerNoCallbacksTest::SetUp();
- acl_manager_->RegisterCallbacks(&mock_connection_callback_, client_handler_);
- acl_manager_->RegisterLeCallbacks(&mock_le_connection_callbacks_, client_handler_);
- }
-
- AddressWithType remote_with_type_;
- uint16_t handle_{0x123};
-};
-
-TEST_F(AclManagerLifeCycleTest, unregister_classic_after_create_connection) {
- // Inject create connection
- test_hci_layer_->SetCommandFuture();
- acl_manager_->CreateConnection(remote);
- auto connection_command = test_hci_layer_->GetCommand(OpCode::CREATE_CONNECTION);
-
- // Unregister callbacks after sending connection request
- auto promise = std::promise<void>();
- auto future = promise.get_future();
- acl_manager_->UnregisterCallbacks(&mock_connection_callback_, std::move(promise));
- future.get();
-
- // Inject peer sending connection complete
- auto connection_future = GetConnectionFuture();
- test_hci_layer_->IncomingEvent(
- ConnectionCompleteBuilder::Create(ErrorCode::SUCCESS, handle_, remote, LinkType::ACL, Enable::DISABLED));
- auto connection_future_status = connection_future.wait_for(kTimeout);
- ASSERT_NE(connection_future_status, std::future_status::ready);
-}
-
-TEST_F(AclManagerLifeCycleTest, unregister_classic_before_connection_request) {
- ClassOfDevice class_of_device;
-
- // Unregister callbacks before receiving connection request
- auto promise = std::promise<void>();
- auto future = promise.get_future();
- acl_manager_->UnregisterCallbacks(&mock_connection_callback_, std::move(promise));
- future.get();
-
- // Inject peer sending connection request
- auto connection_future = GetConnectionFuture();
- test_hci_layer_->IncomingEvent(
- ConnectionRequestBuilder::Create(remote, class_of_device, ConnectionRequestLinkType::ACL));
- auto connection_future_status = connection_future.wait_for(kTimeout);
- ASSERT_NE(connection_future_status, std::future_status::ready);
-
- test_hci_layer_->GetLastCommand(OpCode::REJECT_CONNECTION_REQUEST);
-}
-
-TEST_F(AclManagerLifeCycleTest, unregister_le_before_connection_complete) {
- AddressWithType remote_with_type(remote, AddressType::PUBLIC_DEVICE_ADDRESS);
- test_hci_layer_->SetCommandFuture();
- acl_manager_->CreateLeConnection(remote_with_type, true);
- test_hci_layer_->GetLastCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-
- test_hci_layer_->SetCommandFuture();
- auto packet = test_hci_layer_->GetLastCommand(OpCode::LE_CREATE_CONNECTION);
- auto le_connection_management_command_view =
- LeConnectionManagementCommandView::Create(AclCommandView::Create(packet));
- auto command_view = LeCreateConnectionView::Create(le_connection_management_command_view);
- ASSERT_TRUE(command_view.IsValid());
- if (use_connect_list_) {
- ASSERT_EQ(command_view.GetPeerAddress(), hci::Address::kEmpty);
- } else {
- ASSERT_EQ(command_view.GetPeerAddress(), remote);
- }
- ASSERT_EQ(command_view.GetPeerAddressType(), AddressType::PUBLIC_DEVICE_ADDRESS);
-
- // Unregister callbacks after sending connection request
- auto promise = std::promise<void>();
- auto future = promise.get_future();
- acl_manager_->UnregisterLeCallbacks(&mock_le_connection_callbacks_, std::move(promise));
- future.get();
-
- auto connection_future = GetLeConnectionFuture();
- test_hci_layer_->IncomingLeMetaEvent(LeConnectionCompleteBuilder::Create(
- ErrorCode::SUCCESS,
- 0x123,
- Role::PERIPHERAL,
- AddressType::PUBLIC_DEVICE_ADDRESS,
- remote,
- 0x0100,
- 0x0010,
- 0x0500,
- ClockAccuracy::PPM_30));
-
- auto connection_future_status = connection_future.wait_for(kTimeout);
- ASSERT_NE(connection_future_status, std::future_status::ready);
-}
-
-TEST_F(AclManagerLifeCycleTest, unregister_le_before_enhanced_connection_complete) {
- AddressWithType remote_with_type(remote, AddressType::PUBLIC_DEVICE_ADDRESS);
- test_hci_layer_->SetCommandFuture();
- acl_manager_->CreateLeConnection(remote_with_type, true);
- test_hci_layer_->GetLastCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-
- test_hci_layer_->SetCommandFuture();
- auto packet = test_hci_layer_->GetLastCommand(OpCode::LE_CREATE_CONNECTION);
- auto le_connection_management_command_view =
- LeConnectionManagementCommandView::Create(AclCommandView::Create(packet));
- auto command_view = LeCreateConnectionView::Create(le_connection_management_command_view);
- ASSERT_TRUE(command_view.IsValid());
- if (use_connect_list_) {
- ASSERT_EQ(command_view.GetPeerAddress(), hci::Address::kEmpty);
- } else {
- ASSERT_EQ(command_view.GetPeerAddress(), remote);
- }
- ASSERT_EQ(command_view.GetPeerAddressType(), AddressType::PUBLIC_DEVICE_ADDRESS);
-
- // Unregister callbacks after sending connection request
- auto promise = std::promise<void>();
- auto future = promise.get_future();
- acl_manager_->UnregisterLeCallbacks(&mock_le_connection_callbacks_, std::move(promise));
- future.get();
-
- auto connection_future = GetLeConnectionFuture();
- test_hci_layer_->IncomingLeMetaEvent(LeEnhancedConnectionCompleteBuilder::Create(
- ErrorCode::SUCCESS,
- 0x123,
- Role::PERIPHERAL,
- AddressType::PUBLIC_DEVICE_ADDRESS,
- remote,
- Address::kEmpty,
- Address::kEmpty,
- 0x0100,
- 0x0010,
- 0x0500,
- ClockAccuracy::PPM_30));
-
- auto connection_future_status = connection_future.wait_for(kTimeout);
- ASSERT_NE(connection_future_status, std::future_status::ready);
-}
-
-TEST_F(AclManagerWithConnectionTest, remote_sco_connect_request) {
- ClassOfDevice class_of_device;
-
- EXPECT_CALL(mock_connection_callback_, HACK_OnScoConnectRequest(remote, class_of_device));
-
- test_hci_layer_->IncomingEvent(
- ConnectionRequestBuilder::Create(remote, class_of_device, ConnectionRequestLinkType::SCO));
- fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
- fake_registry_.SynchronizeModuleHandler(&AclManager::Factory, std::chrono::milliseconds(20));
- fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
-}
-
-TEST_F(AclManagerWithConnectionTest, remote_esco_connect_request) {
- ClassOfDevice class_of_device;
-
- EXPECT_CALL(mock_connection_callback_, HACK_OnEscoConnectRequest(remote, class_of_device));
-
- test_hci_layer_->IncomingEvent(
- ConnectionRequestBuilder::Create(remote, class_of_device, ConnectionRequestLinkType::ESCO));
- fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
- fake_registry_.SynchronizeModuleHandler(&AclManager::Factory, std::chrono::milliseconds(20));
- fake_registry_.SynchronizeModuleHandler(&HciLayer::Factory, std::chrono::milliseconds(20));
-}
-
} // namespace
-} // namespace acl_manager
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/address.cc b/gd/hci/address.cc
index 3dc013f17..8a407fb70 100644
--- a/gd/hci/address.cc
+++ b/gd/hci/address.cc
@@ -18,105 +18,76 @@
#include "hci/address.h"
+#include <stdint.h>
#include <algorithm>
-#include <cstdint>
-#include <cstdio>
-#include <iomanip>
#include <sstream>
+#include <vector>
-#include "common/strings.h"
+#include "os/log.h"
namespace bluetooth {
namespace hci {
+static_assert(sizeof(Address) == 6, "Address must be 6 bytes long!");
+
const Address Address::kAny{{0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF}};
const Address Address::kEmpty{{0x00, 0x00, 0x00, 0x00, 0x00, 0x00}};
-// Address cannot initialize member variables as it is a POD type
-// NOLINTNEXTLINE(cppcoreguidelines-pro-type-member-init)
Address::Address(const uint8_t (&addr)[6]) {
- std::copy(addr, addr + kLength, data());
-}
-
-Address::Address(std::initializer_list<uint8_t> l) {
- std::copy(l.begin(), std::min(l.begin() + kLength, l.end()), data());
-}
+ std::copy(addr, addr + kLength, address);
+};
std::string Address::ToString() const {
- std::stringstream ss;
- for (auto it = address.rbegin(); it != address.rend(); it++) {
- ss << std::nouppercase << std::hex << std::setw(2) << std::setfill('0') << +*it;
- if (std::next(it) != address.rend()) {
- ss << ':';
- }
- }
- return ss.str();
-}
-
-std::string Address::ToLegacyConfigString() const {
- return ToString();
-}
-
-std::optional<Address> Address::FromLegacyConfigString(const std::string& str) {
- return FromString(str);
+ char buffer[] = "00:00:00:00:00:00";
+ std::snprintf(&buffer[0], sizeof(buffer), "%02x:%02x:%02x:%02x:%02x:%02x", address[5], address[4], address[3],
+ address[2], address[1], address[0]);
+ std::string str(buffer);
+ return str;
}
-std::optional<Address> Address::FromString(const std::string& from) {
+bool Address::FromString(const std::string& from, Address& to) {
+ Address new_addr;
if (from.length() != 17) {
- return std::nullopt;
+ return false;
}
- Address addr{};
std::istringstream stream(from);
std::string token;
int index = 0;
while (getline(stream, token, ':')) {
if (index >= 6) {
- return std::nullopt;
+ return false;
}
if (token.length() != 2) {
- return std::nullopt;
+ return false;
}
char* temp = nullptr;
- addr.address.at(5 - index) = std::strtol(token.c_str(), &temp, 16);
- if (temp == token.c_str()) {
- // string token is empty or has wrong format
- return std::nullopt;
- }
- if (temp != (token.c_str() + token.size())) {
- // cannot parse whole string
- return std::nullopt;
+ new_addr.address[5 - index] = strtol(token.c_str(), &temp, 16);
+ if (*temp != '\0') {
+ return false;
}
index++;
}
if (index != 6) {
- return std::nullopt;
- }
-
- return addr;
-}
-
-bool Address::FromString(const std::string& from, Address& to) {
- auto addr = FromString(from);
- if (!addr) {
- to = {};
return false;
}
- to = std::move(*addr);
+
+ to = new_addr;
return true;
}
size_t Address::FromOctets(const uint8_t* from) {
- std::copy(from, from + kLength, data());
+ std::copy(from, from + kLength, address);
return kLength;
};
bool Address::IsValidAddress(const std::string& address) {
- return Address::FromString(address).has_value();
+ Address tmp;
+ return Address::FromString(address, tmp);
}
} // namespace hci
diff --git a/gd/hci/address.h b/gd/hci/address.h
index 260dc55a2..3bc507fb3 100644
--- a/gd/hci/address.h
+++ b/gd/hci/address.h
@@ -18,47 +18,26 @@
#pragma once
-#include <array>
#include <cstring>
-#include <initializer_list>
-#include <optional>
#include <string>
-#include "packet/custom_field_fixed_size_interface.h"
-#include "storage/serializable.h"
-
namespace bluetooth {
namespace hci {
-class Address final : public packet::CustomFieldFixedSizeInterface<Address>, public storage::Serializable<Address> {
+class Address final {
public:
- static constexpr size_t kLength = 6;
+ static constexpr unsigned int kLength = 6;
- std::array<uint8_t, kLength> address = {};
+ uint8_t address[kLength];
Address() = default;
- Address(const uint8_t (&addr)[kLength]);
- Address(std::initializer_list<uint8_t> l);
-
- // CustomFieldFixedSizeInterface methods
- inline uint8_t* data() override {
- return address.data();
- }
- inline const uint8_t* data() const override {
- return address.data();
- }
-
- // storage::Serializable methods
- std::string ToString() const override;
- static std::optional<Address> FromString(const std::string& from);
- std::string ToLegacyConfigString() const override;
- static std::optional<Address> FromLegacyConfigString(const std::string& str);
+ Address(const uint8_t (&addr)[6]);
bool operator<(const Address& rhs) const {
- return address < rhs.address;
+ return (std::memcmp(address, rhs.address, sizeof(address)) < 0);
}
bool operator==(const Address& rhs) const {
- return address == rhs.address;
+ return (std::memcmp(address, rhs.address, sizeof(address)) == 0);
}
bool operator>(const Address& rhs) const {
return (rhs < *this);
@@ -77,6 +56,8 @@ class Address final : public packet::CustomFieldFixedSizeInterface<Address>, pub
return *this == kEmpty;
}
+ std::string ToString() const;
+
// Converts |string| to Address and places it in |to|. If |from| does
// not represent a Bluetooth address, |to| is not modified and this function
// returns false. Otherwise, it returns true.
@@ -106,8 +87,8 @@ struct hash<bluetooth::hci::Address> {
std::size_t operator()(const bluetooth::hci::Address& val) const {
static_assert(sizeof(uint64_t) >= bluetooth::hci::Address::kLength);
uint64_t int_addr = 0;
- memcpy(reinterpret_cast<uint8_t*>(&int_addr), val.data(), bluetooth::hci::Address::kLength);
+ memcpy(reinterpret_cast<uint8_t*>(&int_addr), val.address, bluetooth::hci::Address::kLength);
return std::hash<uint64_t>{}(int_addr);
}
};
-} // namespace std
+} // namespace std \ No newline at end of file
diff --git a/gd/hci/address_unittest.cc b/gd/hci/address_unittest.cc
index ae2c2e79a..17ecd3a70 100644
--- a/gd/hci/address_unittest.cc
+++ b/gd/hci/address_unittest.cc
@@ -18,7 +18,6 @@
#include <unordered_map>
-#include <gmock/gmock.h>
#include <gtest/gtest.h>
#include "hci/address.h"
@@ -94,14 +93,14 @@ TEST(AddressTest, test_equals) {
Address bdaddr3;
Address::FromString(test_addr, bdaddr1);
Address::FromString(test_addr, bdaddr2);
- ASSERT_TRUE(bdaddr1 == bdaddr2);
- ASSERT_FALSE(bdaddr1 != bdaddr2);
- ASSERT_TRUE(bdaddr1 == bdaddr1);
- ASSERT_FALSE(bdaddr1 != bdaddr1);
+ EXPECT_TRUE(bdaddr1 == bdaddr2);
+ EXPECT_FALSE(bdaddr1 != bdaddr2);
+ EXPECT_TRUE(bdaddr1 == bdaddr1);
+ EXPECT_FALSE(bdaddr1 != bdaddr1);
Address::FromString(test_addr2, bdaddr3);
- ASSERT_FALSE(bdaddr2 == bdaddr3);
- ASSERT_TRUE(bdaddr2 != bdaddr3);
+ EXPECT_FALSE(bdaddr2 == bdaddr3);
+ EXPECT_TRUE(bdaddr2 != bdaddr3);
}
TEST(AddressTest, test_less_than) {
@@ -110,12 +109,12 @@ TEST(AddressTest, test_less_than) {
Address bdaddr3;
Address::FromString(test_addr, bdaddr1);
Address::FromString(test_addr, bdaddr2);
- ASSERT_FALSE(bdaddr1 < bdaddr2);
- ASSERT_FALSE(bdaddr1 < bdaddr1);
+ EXPECT_FALSE(bdaddr1 < bdaddr2);
+ EXPECT_FALSE(bdaddr1 < bdaddr1);
Address::FromString(test_addr2, bdaddr3);
- ASSERT_TRUE(bdaddr2 < bdaddr3);
- ASSERT_FALSE(bdaddr3 < bdaddr2);
+ EXPECT_TRUE(bdaddr2 < bdaddr3);
+ EXPECT_FALSE(bdaddr3 < bdaddr2);
}
TEST(AddressTest, test_more_than) {
@@ -124,12 +123,12 @@ TEST(AddressTest, test_more_than) {
Address bdaddr3;
Address::FromString(test_addr, bdaddr1);
Address::FromString(test_addr, bdaddr2);
- ASSERT_FALSE(bdaddr1 > bdaddr2);
- ASSERT_FALSE(bdaddr1 > bdaddr1);
+ EXPECT_FALSE(bdaddr1 > bdaddr2);
+ EXPECT_FALSE(bdaddr1 > bdaddr1);
Address::FromString(test_addr2, bdaddr3);
- ASSERT_FALSE(bdaddr2 > bdaddr3);
- ASSERT_TRUE(bdaddr3 > bdaddr2);
+ EXPECT_FALSE(bdaddr2 > bdaddr3);
+ EXPECT_TRUE(bdaddr3 > bdaddr2);
}
TEST(AddressTest, test_less_than_or_equal) {
@@ -138,12 +137,12 @@ TEST(AddressTest, test_less_than_or_equal) {
Address bdaddr3;
Address::FromString(test_addr, bdaddr1);
Address::FromString(test_addr, bdaddr2);
- ASSERT_TRUE(bdaddr1 <= bdaddr2);
- ASSERT_TRUE(bdaddr1 <= bdaddr1);
+ EXPECT_TRUE(bdaddr1 <= bdaddr2);
+ EXPECT_TRUE(bdaddr1 <= bdaddr1);
Address::FromString(test_addr2, bdaddr3);
- ASSERT_TRUE(bdaddr2 <= bdaddr3);
- ASSERT_FALSE(bdaddr3 <= bdaddr2);
+ EXPECT_TRUE(bdaddr2 <= bdaddr3);
+ EXPECT_FALSE(bdaddr3 <= bdaddr2);
}
TEST(AddressTest, test_more_than_or_equal) {
@@ -152,12 +151,12 @@ TEST(AddressTest, test_more_than_or_equal) {
Address bdaddr3;
Address::FromString(test_addr, bdaddr1);
Address::FromString(test_addr, bdaddr2);
- ASSERT_TRUE(bdaddr1 >= bdaddr2);
- ASSERT_TRUE(bdaddr1 >= bdaddr1);
+ EXPECT_TRUE(bdaddr1 >= bdaddr2);
+ EXPECT_TRUE(bdaddr1 >= bdaddr1);
Address::FromString(test_addr2, bdaddr3);
- ASSERT_FALSE(bdaddr2 >= bdaddr3);
- ASSERT_TRUE(bdaddr3 >= bdaddr2);
+ EXPECT_FALSE(bdaddr2 >= bdaddr3);
+ EXPECT_TRUE(bdaddr3 >= bdaddr2);
}
TEST(AddressTest, test_copy) {
@@ -166,41 +165,39 @@ TEST(AddressTest, test_copy) {
Address::FromString(test_addr, bdaddr1);
bdaddr2 = bdaddr1;
- ASSERT_TRUE(bdaddr1 == bdaddr2);
+ EXPECT_TRUE(bdaddr1 == bdaddr2);
}
TEST(AddressTest, IsValidAddress) {
- ASSERT_FALSE(Address::IsValidAddress(""));
- ASSERT_FALSE(Address::IsValidAddress("000000000000"));
- ASSERT_FALSE(Address::IsValidAddress("00:00:00:00:0000"));
- ASSERT_FALSE(Address::IsValidAddress("00:00:00:00:00:0"));
- ASSERT_FALSE(Address::IsValidAddress("00:00:00:00:00:0;"));
- ASSERT_TRUE(Address::IsValidAddress("00:00:00:00:00:00"));
- ASSERT_TRUE(Address::IsValidAddress("AB:cd:00:00:00:00"));
- ASSERT_FALSE(Address::IsValidAddress("aB:cD:eF:Gh:iJ:Kl"));
+ EXPECT_FALSE(Address::IsValidAddress(""));
+ EXPECT_FALSE(Address::IsValidAddress("000000000000"));
+ EXPECT_FALSE(Address::IsValidAddress("00:00:00:00:0000"));
+ EXPECT_FALSE(Address::IsValidAddress("00:00:00:00:00:0"));
+ EXPECT_FALSE(Address::IsValidAddress("00:00:00:00:00:0;"));
+ EXPECT_TRUE(Address::IsValidAddress("00:00:00:00:00:00"));
+ EXPECT_TRUE(Address::IsValidAddress("AB:cd:00:00:00:00"));
+ EXPECT_FALSE(Address::IsValidAddress("aB:cD:eF:Gh:iJ:Kl"));
}
TEST(AddressTest, BdAddrFromString) {
- Address addr = {};
+ Address addr;
+ memset(&addr, 0, sizeof(addr));
- ASSERT_TRUE(Address::FromString("00:00:00:00:00:00", addr));
+ EXPECT_TRUE(Address::FromString("00:00:00:00:00:00", addr));
const Address result0 = {{0x00, 0x00, 0x00, 0x00, 0x00, 0x00}};
- ASSERT_EQ(0, memcmp(addr.data(), result0.data(), Address::kLength));
+ EXPECT_EQ(0, memcmp(&addr, &result0, sizeof(addr)));
- ASSERT_TRUE(Address::FromString("ab:01:4C:d5:21:9f", addr));
+ EXPECT_TRUE(Address::FromString("ab:01:4C:d5:21:9f", addr));
const Address result1 = {{0x9f, 0x21, 0xd5, 0x4c, 0x01, 0xab}};
- ASSERT_EQ("ab:01:4c:d5:21:9f", addr.ToString());
- ASSERT_EQ("ab:01:4c:d5:21:9f", result1.ToString());
- ASSERT_THAT(addr.address, testing::ElementsAre(0x9f, 0x21, 0xd5, 0x4c, 0x01, 0xab));
- ASSERT_EQ(0, memcmp(addr.data(), result1.data(), Address::kLength));
+ EXPECT_EQ(0, memcmp(&addr, &result1, sizeof(addr)));
}
TEST(AddressTest, BdAddrFromStringToStringEquivalent) {
std::string address = "c1:c2:c3:d1:d2:d3";
Address addr;
- ASSERT_TRUE(Address::FromString(address, addr));
- ASSERT_EQ(addr.ToString(), address);
+ EXPECT_TRUE(Address::FromString(address, addr));
+ EXPECT_EQ(addr.ToString(), address);
}
TEST(AddressTest, BdAddrSameValueSameOrder) {
@@ -208,28 +205,28 @@ TEST(AddressTest, BdAddrSameValueSameOrder) {
Address addr2{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
// Test if two addresses with same byte value have the same hash
struct std::hash<bluetooth::hci::Address> hasher;
- ASSERT_EQ(hasher(addr1), hasher(addr2));
+ EXPECT_EQ(hasher(addr1), hasher(addr2));
// Test if two addresses with the same hash and the same value, they will
// still map to the same value
std::unordered_map<Address, int> data = {};
data[addr1] = 5;
data[addr2] = 8;
- ASSERT_EQ(data[addr1], data[addr2]);
+ EXPECT_EQ(data[addr1], data[addr2]);
}
TEST(AddressTest, BdAddrHashDifferentForDifferentAddressesZeroAddr) {
Address addr1{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
struct std::hash<Address> hasher;
- ASSERT_NE(hasher(addr1), hasher(Address::kEmpty));
+ EXPECT_NE(hasher(addr1), hasher(Address::kEmpty));
}
TEST(AddressTest, BdAddrHashDifferentForDifferentAddressesFullAddr) {
Address addr1{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
struct std::hash<Address> hasher;
- ASSERT_NE(hasher(addr1), hasher(Address::kAny));
+ EXPECT_NE(hasher(addr1), hasher(Address::kAny));
}
TEST(AddressTest, BdAddrHashDifferentForDifferentAddressesZeroAndFullAddr) {
struct std::hash<Address> hasher;
- ASSERT_NE(hasher(Address::kEmpty), hasher(Address::kAny));
+ EXPECT_NE(hasher(Address::kEmpty), hasher(Address::kAny));
}
diff --git a/gd/hci/address_with_type.h b/gd/hci/address_with_type.h
index 88d8e1574..ca77e2dfe 100644
--- a/gd/hci/address_with_type.h
+++ b/gd/hci/address_with_type.h
@@ -31,8 +31,7 @@ namespace hci {
class AddressWithType final {
public:
- AddressWithType(Address address, AddressType address_type)
- : address_(std::move(address)), address_type_(address_type) {}
+ AddressWithType(Address address, AddressType address_type) : address_(address), address_type_(address_type) {}
explicit AddressWithType() : address_(Address::kEmpty), address_type_(AddressType::PUBLIC_DEVICE_ADDRESS) {}
@@ -46,7 +45,7 @@ class AddressWithType final {
/* Is this an Resolvable Private Address ? */
inline bool IsRpa() const {
- return address_type_ == hci::AddressType::RANDOM_DEVICE_ADDRESS && ((address_.data())[0] & 0xc0) == 0x40;
+ return address_type_ == hci::AddressType::RANDOM_DEVICE_ADDRESS && ((address_.address)[0] & 0xc0) == 0x40;
}
/* Is this an Resolvable Private Address, that was generated from given irk ? */
@@ -114,12 +113,12 @@ namespace std {
template <>
struct hash<bluetooth::hci::AddressWithType> {
std::size_t operator()(const bluetooth::hci::AddressWithType& val) const {
- static_assert(sizeof(uint64_t) >= (bluetooth::hci::Address::kLength + sizeof(bluetooth::hci::AddressType)));
+ static_assert(sizeof(uint64_t) >= (sizeof(bluetooth::hci::Address) + sizeof(bluetooth::hci::AddressType)));
uint64_t int_addr = 0;
- memcpy(reinterpret_cast<uint8_t*>(&int_addr), val.GetAddress().data(), bluetooth::hci::Address::kLength);
+ memcpy(reinterpret_cast<uint8_t*>(&int_addr), val.GetAddress().address, sizeof(bluetooth::hci::Address));
bluetooth::hci::AddressType address_type = val.GetAddressType();
- memcpy(
- reinterpret_cast<uint8_t*>(&int_addr) + bluetooth::hci::Address::kLength, &address_type, sizeof(address_type));
+ memcpy(reinterpret_cast<uint8_t*>(&int_addr) + sizeof(bluetooth::hci::Address), &address_type,
+ sizeof(address_type));
return std::hash<uint64_t>{}(int_addr);
}
};
diff --git a/gd/hci/cert/acl_manager_test.py b/gd/hci/cert/acl_manager_test.py
index ce8bea63a..1f25c7d51 100644
--- a/gd/hci/cert/acl_manager_test.py
+++ b/gd/hci/cert/acl_manager_test.py
@@ -14,106 +14,351 @@
# See the License for the specific language governing permissions and
# limitations under the License.
-from cert.gd_base_test import GdBaseTestClass
-from cert.truth import assertThat
+import os
+import sys
+import logging
+
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
+from cert.event_callback_stream import EventCallbackStream
+from cert.event_asserts import EventAsserts
+from google.protobuf import empty_pb2 as empty_proto
+from facade import rootservice_pb2 as facade_rootservice
+from hci.facade import acl_manager_facade_pb2 as acl_manager_facade
from neighbor.facade import facade_pb2 as neighbor_facade
+from hci.facade import controller_facade_pb2 as controller_facade
+from hci.facade import facade_pb2 as hci_facade
+import bluetooth_packets_python3 as bt_packets
from bluetooth_packets_python3 import hci_packets
-from cert.py_hci import PyHci
-from cert.py_acl_manager import PyAclManager
-
-class AclManagerTest(GdBaseTestClass):
- def setup_class(self):
- super().setup_class(dut_module='HCI_INTERFACES', cert_module='HCI')
+class AclManagerTest(GdFacadeOnlyBaseTestClass):
- # todo: move into GdBaseTestClass, based on modules inited
def setup_test(self):
- super().setup_test()
- self.cert_hci = PyHci(self.cert, acl_streaming=True)
- self.dut_acl_manager = PyAclManager(self.dut)
+ self.device_under_test.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI_INTERFACES'),))
+ self.cert_device.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI'),))
+
+ self.device_under_test.wait_channel_ready()
+ self.cert_device.wait_channel_ready()
def teardown_test(self):
- self.cert_hci.close()
- super().teardown_test()
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+ self.cert_device.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+
+ def register_for_event(self, event_code):
+ msg = hci_facade.EventCodeMsg(code=int(event_code))
+ self.cert_device.hci.RegisterEventHandler(msg)
+
+ def enqueue_hci_command(self, command, expect_complete):
+ cmd_bytes = bytes(command.Serialize())
+ cmd = hci_facade.CommandMsg(command=cmd_bytes)
+ if (expect_complete):
+ self.cert_device.hci.EnqueueCommandWithComplete(cmd)
+ else:
+ self.cert_device.hci.EnqueueCommandWithStatus(cmd)
+
+ def enqueue_acl_data(self, handle, pb_flag, b_flag, acl):
+ acl_msg = hci_facade.AclMsg(
+ handle=int(handle),
+ packet_boundary_flag=int(pb_flag),
+ broadcast_flag=int(b_flag),
+ data=acl)
+ self.cert_device.hci.SendAclData(acl_msg)
def test_dut_connects(self):
- self.cert_hci.enable_inquiry_and_page_scan()
- cert_address = self.cert_hci.read_own_address()
+ self.register_for_event(hci_packets.EventCode.CONNECTION_REQUEST)
+ self.register_for_event(hci_packets.EventCode.CONNECTION_COMPLETE)
+ self.register_for_event(
+ hci_packets.EventCode.CONNECTION_PACKET_TYPE_CHANGED)
+ with EventCallbackStream(self.cert_device.hci.FetchEvents(empty_proto.Empty())) as cert_hci_event_stream, \
+ EventCallbackStream(self.cert_device.hci.FetchAclPackets(empty_proto.Empty())) as cert_acl_data_stream, \
+ EventCallbackStream(self.device_under_test.hci_acl_manager.FetchAclData(empty_proto.Empty())) as acl_data_stream:
- self.dut_acl_manager.initiate_connection(cert_address)
- cert_acl = self.cert_hci.accept_connection()
- with self.dut_acl_manager.complete_outgoing_connection() as dut_acl:
- cert_acl.send_first(b'\x26\x00\x07\x00This is just SomeAclData from the Cert')
- dut_acl.send(b'\x29\x00\x07\x00This is just SomeMoreAclData from the DUT')
+ cert_hci_event_asserts = EventAsserts(cert_hci_event_stream)
+ acl_data_asserts = EventAsserts(acl_data_stream)
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
- assertThat(cert_acl).emits(lambda packet: b'SomeMoreAclData' in packet.payload)
- assertThat(dut_acl).emits(lambda packet: b'SomeAclData' in packet.payload)
+ # CERT Enables scans and gets its address
+ self.enqueue_hci_command(
+ hci_packets.WriteScanEnableBuilder(
+ hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN), True)
- def test_cert_connects(self):
- dut_address = self.dut.hci_controller.GetMacAddressSimple()
- self.dut.neighbor.EnablePageScan(neighbor_facade.EnableMsg(enabled=True))
+ cert_address = None
+
+ def get_address_from_complete(packet):
+ packet_bytes = packet.event
+ if b'\x0e\x0a\x01\x09\x10' in packet_bytes:
+ nonlocal cert_address
+ addr_view = hci_packets.ReadBdAddrCompleteView(
+ hci_packets.CommandCompleteView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ cert_address = addr_view.GetBdAddr()
+ return True
+ return False
+
+ self.enqueue_hci_command(hci_packets.ReadBdAddrBuilder(), True)
+
+ cert_hci_event_asserts.assert_event_occurs(
+ get_address_from_complete)
- self.dut_acl_manager.listen_for_an_incoming_connection()
- self.cert_hci.initiate_connection(dut_address)
- with self.dut_acl_manager.complete_incoming_connection() as dut_acl:
- cert_acl = self.cert_hci.complete_connection()
+ with EventCallbackStream(
+ self.device_under_test.hci_acl_manager.CreateConnection(
+ acl_manager_facade.ConnectionMsg(
+ address_type=int(
+ hci_packets.AddressType.PUBLIC_DEVICE_ADDRESS),
+ address=bytes(cert_address,
+ 'utf8')))) as connection_event_stream:
- dut_acl.send(b'\x29\x00\x07\x00This is just SomeMoreAclData from the DUT')
+ connection_event_asserts = EventAsserts(connection_event_stream)
+ connection_request = None
- cert_acl.send_first(b'\x26\x00\x07\x00This is just SomeAclData from the Cert')
+ def get_connect_request(packet):
+ if b'\x04\x0a' in packet.event:
+ nonlocal connection_request
+ connection_request = hci_packets.ConnectionRequestView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet.event))))
+ return True
+ return False
- assertThat(cert_acl).emits(lambda packet: b'SomeMoreAclData' in packet.payload)
- assertThat(dut_acl).emits(lambda packet: b'SomeAclData' in packet.payload)
+ # Cert Accepts
+ cert_hci_event_asserts.assert_event_occurs(get_connect_request)
+ self.enqueue_hci_command(
+ hci_packets.AcceptConnectionRequestBuilder(
+ connection_request.GetBdAddr(),
+ hci_packets.AcceptConnectionRequestRole.REMAIN_SLAVE),
+ False)
+
+ # Cert gets ConnectionComplete with a handle and sends ACL data
+ handle = 0xfff
+
+ def get_handle(packet):
+ packet_bytes = packet.event
+ if b'\x03\x0b\x00' in packet_bytes:
+ nonlocal handle
+ cc_view = hci_packets.ConnectionCompleteView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes))))
+ handle = cc_view.GetConnectionHandle()
+ return True
+ return False
+
+ cert_hci_event_asserts.assert_event_occurs(get_handle)
+ cert_handle = handle
+
+ self.enqueue_acl_data(
+ cert_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(
+ b'\x26\x00\x07\x00This is just SomeAclData from the Cert'
+ ))
+
+ # DUT gets a connection complete event and sends and receives
+ handle = 0xfff
+ connection_event_asserts.assert_event_occurs(get_handle)
+
+ self.device_under_test.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=handle,
+ payload=bytes(
+ b'\x29\x00\x07\x00This is just SomeMoreAclData from the DUT'
+ )))
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeMoreAclData' in packet.data)
+ acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeAclData' in packet.payload)
+
+ def test_cert_connects(self):
+ self.register_for_event(hci_packets.EventCode.CONNECTION_COMPLETE)
+ self.register_for_event(hci_packets.EventCode.ROLE_CHANGE)
+ self.register_for_event(
+ hci_packets.EventCode.CONNECTION_PACKET_TYPE_CHANGED)
+ with EventCallbackStream(self.cert_device.hci.FetchEvents(empty_proto.Empty())) as cert_hci_event_stream, \
+ EventCallbackStream(self.cert_device.hci.FetchAclPackets(empty_proto.Empty())) as cert_acl_data_stream, \
+ EventCallbackStream(self.device_under_test.hci_acl_manager.FetchIncomingConnection(empty_proto.Empty())) as incoming_connection_stream, \
+ EventCallbackStream(self.device_under_test.hci_acl_manager.FetchAclData(empty_proto.Empty())) as acl_data_stream:
- def test_reject_broadcast(self):
- dut_address = self.dut.hci_controller.GetMacAddressSimple()
- self.dut.neighbor.EnablePageScan(neighbor_facade.EnableMsg(enabled=True))
+ cert_hci_event_asserts = EventAsserts(cert_hci_event_stream)
+ incoming_connection_asserts = EventAsserts(
+ incoming_connection_stream)
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ acl_data_asserts = EventAsserts(acl_data_stream)
- self.dut_acl_manager.listen_for_an_incoming_connection()
- self.cert_hci.initiate_connection(dut_address)
- with self.dut_acl_manager.complete_incoming_connection() as dut_acl:
- cert_acl = self.cert_hci.complete_connection()
+ # DUT Enables scans and gets its address
+ dut_address = self.device_under_test.hci_controller.GetMacAddress(
+ empty_proto.Empty()).address
- cert_acl.send(hci_packets.PacketBoundaryFlag.FIRST_AUTOMATICALLY_FLUSHABLE,
- hci_packets.BroadcastFlag.ACTIVE_PERIPHERAL_BROADCAST,
- b'\x26\x00\x07\x00This is a Broadcast from the Cert')
- assertThat(dut_acl).emitsNone()
+ self.device_under_test.neighbor.EnablePageScan(
+ neighbor_facade.EnableMsg(enabled=True))
- cert_acl.send(hci_packets.PacketBoundaryFlag.FIRST_AUTOMATICALLY_FLUSHABLE,
- hci_packets.BroadcastFlag.POINT_TO_POINT,
- b'\x26\x00\x07\x00This is just SomeAclData from the Cert')
- assertThat(dut_acl).emits(lambda packet: b'SomeAclData' in packet.payload)
+ # Cert connects
+ self.enqueue_hci_command(
+ hci_packets.CreateConnectionBuilder(
+ dut_address.decode('utf-8'),
+ 0xcc18, # Packet Type
+ hci_packets.PageScanRepetitionMode.R1,
+ 0x0,
+ hci_packets.ClockOffsetValid.INVALID,
+ hci_packets.CreateConnectionRoleSwitch.ALLOW_ROLE_SWITCH),
+ False)
- def test_cert_connects_disconnects(self):
- dut_address = self.dut.hci_controller.GetMacAddressSimple()
- self.dut.neighbor.EnablePageScan(neighbor_facade.EnableMsg(enabled=True))
+ conn_handle = 0xfff
- self.dut_acl_manager.listen_for_an_incoming_connection()
- self.cert_hci.initiate_connection(dut_address)
- with self.dut_acl_manager.complete_incoming_connection() as dut_acl:
- cert_acl = self.cert_hci.complete_connection()
+ def get_handle(packet):
+ packet_bytes = packet.event
+ if b'\x03\x0b\x00' in packet_bytes:
+ nonlocal conn_handle
+ cc_view = hci_packets.ConnectionCompleteView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes))))
+ conn_handle = cc_view.GetConnectionHandle()
+ return True
+ return False
- dut_acl.send(b'\x29\x00\x07\x00This is just SomeMoreAclData from the DUT')
+ # DUT gets a connection request
+ incoming_connection_asserts.assert_event_occurs(get_handle)
- cert_acl.send_first(b'\x26\x00\x07\x00This is just SomeAclData from the Cert')
+ self.device_under_test.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=conn_handle,
+ payload=bytes(
+ b'\x29\x00\x07\x00This is just SomeMoreAclData from the DUT'
+ )))
- assertThat(cert_acl).emits(lambda packet: b'SomeMoreAclData' in packet.payload)
- assertThat(dut_acl).emits(lambda packet: b'SomeAclData' in packet.payload)
+ conn_handle = 0xfff
- dut_acl.disconnect(hci_packets.DisconnectReason.REMOTE_USER_TERMINATED_CONNECTION)
- dut_acl.wait_for_disconnection_complete()
+ cert_hci_event_asserts.assert_event_occurs(get_handle)
+ cert_handle = conn_handle
+
+ self.enqueue_acl_data(
+ cert_handle,
+ hci_packets.PacketBoundaryFlag.FIRST_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(
+ b'\x26\x00\x07\x00This is just SomeAclData from the Cert'))
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeMoreAclData' in packet.data)
+ acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeAclData' in packet.payload)
def test_recombination_l2cap_packet(self):
- self.cert_hci.enable_inquiry_and_page_scan()
- cert_address = self.cert_hci.read_own_address()
-
- self.dut_acl_manager.initiate_connection(cert_address)
- cert_acl = self.cert_hci.accept_connection()
- with self.dut_acl_manager.complete_outgoing_connection() as dut_acl:
- cert_acl.send_first(b'\x06\x00\x07\x00Hello')
- cert_acl.send_continuing(b'!')
- cert_acl.send_first(b'\xe8\x03\x07\x00' + b'Hello' * 200)
-
- assertThat(dut_acl).emits(lambda packet: b'Hello!' in packet.payload,
- lambda packet: b'Hello' * 200 in packet.payload).inOrder()
+ self.register_for_event(hci_packets.EventCode.CONNECTION_REQUEST)
+ self.register_for_event(hci_packets.EventCode.CONNECTION_COMPLETE)
+ self.register_for_event(
+ hci_packets.EventCode.CONNECTION_PACKET_TYPE_CHANGED)
+ with EventCallbackStream(self.cert_device.hci.FetchEvents(empty_proto.Empty())) as cert_hci_event_stream, \
+ EventCallbackStream(self.cert_device.hci.FetchAclPackets(empty_proto.Empty())) as cert_acl_data_stream, \
+ EventCallbackStream(self.device_under_test.hci_acl_manager.FetchAclData(empty_proto.Empty())) as acl_data_stream:
+
+ cert_hci_event_asserts = EventAsserts(cert_hci_event_stream)
+ acl_data_asserts = EventAsserts(acl_data_stream)
+
+ # CERT Enables scans and gets its address
+ self.enqueue_hci_command(
+ hci_packets.WriteScanEnableBuilder(
+ hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN), True)
+
+ cert_address = None
+
+ def get_address_from_complete(packet):
+ packet_bytes = packet.event
+ if b'\x0e\x0a\x01\x09\x10' in packet_bytes:
+ nonlocal cert_address
+ addr_view = hci_packets.ReadBdAddrCompleteView(
+ hci_packets.CommandCompleteView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ cert_address = addr_view.GetBdAddr()
+ return True
+ return False
+
+ self.enqueue_hci_command(hci_packets.ReadBdAddrBuilder(), True)
+
+ cert_hci_event_asserts.assert_event_occurs(
+ get_address_from_complete)
+
+ with EventCallbackStream(
+ self.device_under_test.hci_acl_manager.CreateConnection(
+ acl_manager_facade.ConnectionMsg(
+ address_type=int(
+ hci_packets.AddressType.PUBLIC_DEVICE_ADDRESS),
+ address=bytes(cert_address,
+ 'utf8')))) as connection_event_stream:
+
+ connection_event_asserts = EventAsserts(connection_event_stream)
+ connection_request = None
+
+ def get_connect_request(packet):
+ if b'\x04\x0a' in packet.event:
+ nonlocal connection_request
+ connection_request = hci_packets.ConnectionRequestView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet.event))))
+ return True
+ return False
+
+ # Cert Accepts
+ cert_hci_event_asserts.assert_event_occurs(get_connect_request)
+ self.enqueue_hci_command(
+ hci_packets.AcceptConnectionRequestBuilder(
+ connection_request.GetBdAddr(),
+ hci_packets.AcceptConnectionRequestRole.REMAIN_SLAVE),
+ False)
+
+ # Cert gets ConnectionComplete with a handle and sends ACL data
+ handle = 0xfff
+
+ def get_handle(packet):
+ packet_bytes = packet.event
+ if b'\x03\x0b\x00' in packet_bytes:
+ nonlocal handle
+ cc_view = hci_packets.ConnectionCompleteView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes))))
+ handle = cc_view.GetConnectionHandle()
+ return True
+ return False
+
+ cert_hci_event_asserts.assert_event_occurs(get_handle)
+ cert_handle = handle
+
+ self.enqueue_acl_data(
+ cert_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'\x06\x00\x07\x00Hello'))
+ self.enqueue_acl_data(
+ cert_handle,
+ hci_packets.PacketBoundaryFlag.CONTINUING_FRAGMENT,
+ hci_packets.BroadcastFlag.POINT_TO_POINT, bytes(b'!'))
+ self.enqueue_acl_data(
+ cert_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'\xe8\x03\x07\x00' + b'Hello' * 200))
+
+ # DUT gets a connection complete event and sends and receives
+ connection_event_asserts.assert_event_occurs(get_handle)
+
+ acl_data_asserts.assert_event_occurs(
+ lambda packet: b'Hello!' in packet.payload)
+ acl_data_asserts.assert_event_occurs(
+ lambda packet: b'Hello' * 200 in packet.payload)
diff --git a/gd/hci/cert/api.proto b/gd/hci/cert/api.proto
new file mode 100644
index 000000000..30b35919f
--- /dev/null
+++ b/gd/hci/cert/api.proto
@@ -0,0 +1,46 @@
+syntax = "proto3";
+
+package bluetooth.hci.cert;
+
+import "google/protobuf/empty.proto";
+import "facade/common.proto";
+
+service AclManagerCert {
+ rpc SetPageScanMode(PageScanMode) returns (google.protobuf.Empty) {}
+ rpc SetIncomingConnectionPolicy(IncomingConnectionPolicy) returns (google.protobuf.Empty) {}
+ rpc Connect(facade.BluetoothAddress) returns (google.protobuf.Empty) {}
+ rpc Disconnect(facade.BluetoothAddress) returns (google.protobuf.Empty) {}
+ rpc FetchConnectionComplete(google.protobuf.Empty) returns (stream ConnectionEvent) {}
+ rpc FetchDisconnection(google.protobuf.Empty) returns (stream DisconnectionEvent) {}
+ rpc FetchConnectionFailed(google.protobuf.Empty) returns (stream ConnectionFailedEvent) {}
+ rpc SendAclData(AclData) returns (google.protobuf.Empty) {}
+ rpc FetchAclData(google.protobuf.Empty) returns (stream AclData) {}
+}
+
+message PageScanMode {
+ bool enabled = 1;
+}
+
+message IncomingConnectionPolicy {
+ facade.BluetoothAddress remote = 1;
+ bool accepted = 2;
+}
+
+message ConnectionEvent {
+ facade.BluetoothAddress remote = 1;
+}
+
+message DisconnectionEvent {
+ facade.BluetoothAddress remote = 1;
+ uint32 reason = 2;
+}
+
+message ConnectionFailedEvent {
+ facade.BluetoothAddress remote = 1;
+ uint32 reason = 2;
+}
+
+message AclData {
+ facade.BluetoothAddress remote = 1;
+ bytes payload = 2;
+}
diff --git a/gd/hci/cert/cert.cc b/gd/hci/cert/cert.cc
new file mode 100644
index 000000000..e69de29bb
--- /dev/null
+++ b/gd/hci/cert/cert.cc
diff --git a/gd/hci/cert/controller_test.py b/gd/hci/cert/controller_test.py
index 20fe937e6..6dc23c429 100644
--- a/gd/hci/cert/controller_test.py
+++ b/gd/hci/cert/controller_test.py
@@ -16,30 +16,71 @@
import time
-from cert.gd_base_test import GdBaseTestClass
-from cert.truth import assertThat
+from acts import asserts
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
from google.protobuf import empty_pb2 as empty_proto
from facade import rootservice_pb2 as facade_rootservice
from hci.facade import controller_facade_pb2 as controller_facade
-class ControllerTest(GdBaseTestClass):
+class ControllerTest(GdFacadeOnlyBaseTestClass):
- def setup_class(self):
- super().setup_class(dut_module='HCI_INTERFACES', cert_module='HCI_INTERFACES')
+ def setup_test(self):
+ self.device_under_test.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI_INTERFACES'),))
+ self.cert_device.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI_INTERFACES'),))
- def test_get_addresses(self):
- cert_address = self.cert.hci_controller.GetMacAddressSimple()
- dut_address = self.dut.hci_controller.GetMacAddressSimple()
+ self.device_under_test.wait_channel_ready()
+ self.cert_device.wait_channel_ready()
+
+ def teardown_test(self):
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+ self.cert_device.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
- assertThat(cert_address).isNotEqualTo(dut_address)
+ def test_get_addresses(self):
+ cert_address_response = self.cert_device.hci_controller.GetMacAddress(
+ empty_proto.Empty())
+ dut_address_response = self.device_under_test.hci_controller.GetMacAddress(
+ empty_proto.Empty())
+ asserts.assert_true(
+ cert_address_response.address != dut_address_response.address,
+ msg="Expected cert and dut address to be different %s" %
+ cert_address_response.address)
time.sleep(1) # This shouldn't be needed b/149120542
- def test_write_local_name(self):
- self.dut.hci_controller.WriteLocalName(controller_facade.NameMsg(name=b'ImTheDUT'))
- self.cert.hci_controller.WriteLocalName(controller_facade.NameMsg(name=b'ImTheCert'))
- cert_name = self.cert.hci_controller.GetLocalNameSimple()
- dut_name = self.dut.hci_controller.GetLocalNameSimple()
+ def test_get_local_extended_features(self):
+ request = controller_facade.PageNumberMsg()
+ request.page_number = 1
+ dut_feature_response1 = self.device_under_test.hci_controller.GetLocalExtendedFeatures(
+ request)
+ request0 = controller_facade.PageNumberMsg()
+ request0.page_number = 0
+ dut_feature_response0 = self.device_under_test.hci_controller.GetLocalExtendedFeatures(
+ request0)
+ asserts.assert_true(
+ dut_feature_response1.page != dut_feature_response0.page,
+ msg="Expected cert dut feature pages to be different %d" %
+ dut_feature_response1.page)
- assertThat(dut_name).isEqualTo(b'ImTheDUT')
- assertThat(cert_name).isEqualTo(b'ImTheCert')
+ def test_write_local_name(self):
+ self.device_under_test.hci_controller.WriteLocalName(
+ controller_facade.NameMsg(name=b'ImTheDUT'))
+ self.cert_device.hci_controller.WriteLocalName(
+ controller_facade.NameMsg(name=b'ImTheCert'))
+ cert_name_msg = self.cert_device.hci_controller.GetLocalName(
+ empty_proto.Empty()).name
+ dut_name_msg = self.device_under_test.hci_controller.GetLocalName(
+ empty_proto.Empty()).name
+ asserts.assert_true(
+ dut_name_msg == b'ImTheDUT',
+ msg="unexpected dut name %s" % dut_name_msg)
+ asserts.assert_true(
+ cert_name_msg == b'ImTheCert',
+ msg="unexpected cert name %s" % cert_name_msg)
diff --git a/gd/hci/cert/direct_hci_test.py b/gd/hci/cert/direct_hci_test.py
index ee67e8800..b9d86426d 100644
--- a/gd/hci/cert/direct_hci_test.py
+++ b/gd/hci/cert/direct_hci_test.py
@@ -15,283 +15,688 @@
# limitations under the License.
from datetime import timedelta
+import os
+import sys
import logging
-from cert.captures import HalCaptures, HciCaptures
-from cert.gd_base_test import GdBaseTestClass
-from cert.matchers import HciMatchers
-from cert.py_hal import PyHal
-from cert.py_hci import PyHci
-from cert.truth import assertThat
-from hci.facade import hci_facade_pb2 as hci_facade
-from facade import common_pb2 as common
-from bluetooth_packets_python3.hci_packets import EventCode
-from bluetooth_packets_python3.hci_packets import LoopbackMode
-from bluetooth_packets_python3.hci_packets import WriteLoopbackModeBuilder
-from bluetooth_packets_python3.hci_packets import ReadLocalNameBuilder
-from bluetooth_packets_python3.hci_packets import WriteScanEnableBuilder
-from bluetooth_packets_python3.hci_packets import ScanEnable
-from bluetooth_packets_python3.hci_packets import InquiryBuilder
-from bluetooth_packets_python3.hci_packets import SubeventCode
-from bluetooth_packets_python3.hci_packets import LeSetRandomAddressBuilder
-from bluetooth_packets_python3.hci_packets import PhyScanParameters
-from bluetooth_packets_python3.hci_packets import LeScanType
-from bluetooth_packets_python3.hci_packets import LeSetExtendedScanParametersBuilder
-from bluetooth_packets_python3.hci_packets import OwnAddressType
-from bluetooth_packets_python3.hci_packets import LeScanningFilterPolicy
-from bluetooth_packets_python3.hci_packets import Enable
-from bluetooth_packets_python3.hci_packets import FilterDuplicates
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingLegacyParametersBuilder
-from bluetooth_packets_python3.hci_packets import LegacyAdvertisingProperties
-from bluetooth_packets_python3.hci_packets import PeerAddressType
-from bluetooth_packets_python3.hci_packets import AdvertisingFilterPolicy
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingRandomAddressBuilder
-from bluetooth_packets_python3.hci_packets import GapData
-from bluetooth_packets_python3.hci_packets import GapDataType
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingDataBuilder
-from bluetooth_packets_python3.hci_packets import Operation
-from bluetooth_packets_python3.hci_packets import FragmentPreference
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingScanResponseBuilder
-from bluetooth_packets_python3.hci_packets import LeSetExtendedAdvertisingEnableBuilder
-from bluetooth_packets_python3.hci_packets import LeSetExtendedScanEnableBuilder
-from bluetooth_packets_python3.hci_packets import EnabledSet
-from bluetooth_packets_python3.hci_packets import LeCreateConnPhyScanParameters
-from bluetooth_packets_python3.hci_packets import LeExtendedCreateConnectionBuilder
-from bluetooth_packets_python3.hci_packets import InitiatorFilterPolicy
-from bluetooth_packets_python3.hci_packets import AddressType
-from bluetooth_packets_python3.hci_packets import BroadcastFlag
-from bluetooth_packets_python3.hci_packets import ConnectListAddressType
-from bluetooth_packets_python3.hci_packets import LeAddDeviceToConnectListBuilder
-from bluetooth_packets_python3.hci_packets import LeSetRandomAddressBuilder
-from bluetooth_packets_python3.hci_packets import LeReadRemoteFeaturesBuilder
-from bluetooth_packets_python3.hci_packets import WritePageTimeoutBuilder
-from bluetooth_packets_python3.hci_packets import ReadBdAddrBuilder
-from bluetooth_packets_python3.hci_packets import CreateConnectionBuilder
-from bluetooth_packets_python3.hci_packets import PageScanRepetitionMode
-from bluetooth_packets_python3.hci_packets import ClockOffsetValid
-from bluetooth_packets_python3.hci_packets import CreateConnectionRoleSwitch
-from bluetooth_packets_python3.hci_packets import AcceptConnectionRequestBuilder
-from bluetooth_packets_python3.hci_packets import AcceptConnectionRequestRole
-from bluetooth_packets_python3.hci_packets import PacketBoundaryFlag
-from bluetooth_packets_python3.hci_packets import ResetBuilder
-from bluetooth_packets_python3.hci_packets import Lap
-from bluetooth_packets_python3.hci_packets import OpCode
-from bluetooth_packets_python3.hci_packets import AclBuilder
-from bluetooth_packets_python3 import RawBuilder
-
-
-class DirectHciTest(GdBaseTestClass):
-
- def setup_class(self):
- super().setup_class(dut_module='HCI', cert_module='HAL')
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
+from cert.event_callback_stream import EventCallbackStream
+from cert.event_asserts import EventAsserts
+from google.protobuf import empty_pb2 as empty_proto
+from facade import rootservice_pb2 as facade_rootservice
+from hal import facade_pb2 as hal_facade
+from hci.facade import facade_pb2 as hci_facade
+from bluetooth_packets_python3 import hci_packets
+import bluetooth_packets_python3 as bt_packets
+
+
+class DirectHciTest(GdFacadeOnlyBaseTestClass):
def setup_test(self):
- super().setup_test()
- self.dut_hci = PyHci(self.dut, acl_streaming=True)
- self.cert_hal = PyHal(self.cert)
- self.cert_hal.send_hci_command(ResetBuilder())
+ self.device_under_test.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI'),))
+ self.cert_device.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HAL'),))
+
+ self.device_under_test.wait_channel_ready()
+ self.cert_device.wait_channel_ready()
+
+ self.cert_device.hal.SendHciCommand(
+ hal_facade.HciCommandPacket(
+ payload=bytes(hci_packets.ResetBuilder().Serialize())))
def teardown_test(self):
- self.dut_hci.close()
- self.cert_hal.close()
- super().teardown_test()
-
- def enqueue_acl_data(self, handle, pb_flag, b_flag, data):
- acl = AclBuilder(handle, pb_flag, b_flag, RawBuilder(data))
- self.dut.hci.SendAcl(common.Data(payload=bytes(acl.Serialize())))
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+ self.cert_device.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+
+ def register_for_event(self, event_code):
+ msg = hci_facade.EventCodeMsg(code=int(event_code))
+ self.device_under_test.hci.RegisterEventHandler(msg)
+
+ def register_for_le_event(self, event_code):
+ msg = hci_facade.LeSubeventCodeMsg(code=int(event_code))
+ self.device_under_test.hci.RegisterLeEventHandler(msg)
+
+ def enqueue_hci_command(self, command, expect_complete):
+ cmd_bytes = bytes(command.Serialize())
+ cmd = hci_facade.CommandMsg(command=cmd_bytes)
+ if (expect_complete):
+ self.device_under_test.hci.EnqueueCommandWithComplete(cmd)
+ else:
+ self.device_under_test.hci.EnqueueCommandWithStatus(cmd)
+
+ def send_hal_hci_command(self, command):
+ self.cert_device.hal.SendHciCommand(
+ hal_facade.HciCommandPacket(payload=bytes(command.Serialize())))
+
+ def enqueue_acl_data(self, handle, pb_flag, b_flag, acl):
+ acl_msg = hci_facade.AclMsg(
+ handle=int(handle),
+ packet_boundary_flag=int(pb_flag),
+ broadcast_flag=int(b_flag),
+ data=acl)
+ self.device_under_test.hci.SendAclData(acl_msg)
+
+ def send_hal_acl_data(self, handle, pb_flag, b_flag, acl):
+ lower = handle & 0xff
+ upper = (handle >> 8) & 0xf
+ upper = upper | int(pb_flag) & 0x3
+ upper = upper | ((int(b_flag) & 0x3) << 2)
+ lower_length = len(acl) & 0xff
+ upper_length = (len(acl) & 0xff00) >> 8
+ concatenated = bytes([lower, upper, lower_length, upper_length] +
+ list(acl))
+ self.cert_device.hal.SendHciAcl(
+ hal_facade.HciAclPacket(payload=concatenated))
def test_local_hci_cmd_and_event(self):
# Loopback mode responds with ACL and SCO connection complete
- self.dut_hci.register_for_events(EventCode.LOOPBACK_COMMAND)
- self.dut_hci.send_command(WriteLoopbackModeBuilder(LoopbackMode.ENABLE_LOCAL))
-
- self.dut_hci.send_command(ReadLocalNameBuilder())
- assertThat(self.dut_hci.get_event_stream()).emits(HciMatchers.LoopbackOf(ReadLocalNameBuilder()))
+ self.register_for_event(hci_packets.EventCode.CONNECTION_COMPLETE)
+ self.register_for_event(hci_packets.EventCode.LOOPBACK_COMMAND)
+ self.register_for_event(
+ hci_packets.EventCode.CONNECTION_PACKET_TYPE_CHANGED)
+ with EventCallbackStream(
+ self.device_under_test.hci.FetchEvents(
+ empty_proto.Empty())) as hci_event_stream:
+ hci_event_asserts = EventAsserts(hci_event_stream)
+
+ self.enqueue_hci_command(
+ hci_packets.WriteLoopbackModeBuilder(
+ hci_packets.LoopbackMode.ENABLE_LOCAL), True)
+
+ cmd2loop = hci_packets.ReadLocalNameBuilder()
+ self.enqueue_hci_command(cmd2loop, True)
+
+ looped_bytes = bytes(cmd2loop.Serialize())
+ hci_event_asserts.assert_event_occurs(
+ lambda packet: looped_bytes in packet.event)
def test_inquiry_from_dut(self):
- self.dut_hci.register_for_events(EventCode.INQUIRY_RESULT)
-
- self.cert_hal.enable_inquiry_and_page_scan()
- lap = Lap()
- lap.lap = 0x33
- self.dut_hci.send_command(InquiryBuilder(lap, 0x30, 0xff))
- assertThat(self.dut_hci.get_event_stream()).emits(HciMatchers.EventWithCode(EventCode.INQUIRY_RESULT))
+ self.register_for_event(hci_packets.EventCode.INQUIRY_RESULT)
+ with EventCallbackStream(
+ self.device_under_test.hci.FetchEvents(
+ empty_proto.Empty())) as hci_event_stream:
+
+ hci_event_asserts = EventAsserts(hci_event_stream)
+
+ self.send_hal_hci_command(
+ hci_packets.WriteScanEnableBuilder(
+ hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN))
+ lap = hci_packets.Lap()
+ lap.lap = 0x33
+ self.enqueue_hci_command(
+ hci_packets.InquiryBuilder(lap, 0x30, 0xff), False)
+ hci_event_asserts.assert_event_occurs(
+ lambda packet: b'\x02\x0f' in packet.event
+ # Expecting an HCI Event (code 0x02, length 0x0f)
+ )
def test_le_ad_scan_cert_advertises(self):
- self.dut_hci.register_for_le_events(SubeventCode.EXTENDED_ADVERTISING_REPORT, SubeventCode.ADVERTISING_REPORT)
-
- # DUT Scans
- self.dut_hci.send_command(LeSetRandomAddressBuilder('0D:05:04:03:02:01'))
- phy_scan_params = PhyScanParameters()
- phy_scan_params.le_scan_interval = 6553
- phy_scan_params.le_scan_window = 6553
- phy_scan_params.le_scan_type = LeScanType.ACTIVE
-
- self.dut_hci.send_command(
- LeSetExtendedScanParametersBuilder(OwnAddressType.RANDOM_DEVICE_ADDRESS, LeScanningFilterPolicy.ACCEPT_ALL,
- 1, [phy_scan_params]))
- self.dut_hci.send_command(LeSetExtendedScanEnableBuilder(Enable.ENABLED, FilterDuplicates.DISABLED, 0, 0))
-
- # CERT Advertises
- advertising_handle = 0
- self.cert_hal.send_hci_command(
- LeSetExtendedAdvertisingLegacyParametersBuilder(
- advertising_handle,
- LegacyAdvertisingProperties.ADV_IND,
- 512,
- 768,
- 7,
- OwnAddressType.RANDOM_DEVICE_ADDRESS,
- PeerAddressType.PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
- 'A6:A5:A4:A3:A2:A1',
- AdvertisingFilterPolicy.ALL_DEVICES,
- 0xF7,
- 1, # SID
- Enable.DISABLED # Scan request notification
- ))
-
- self.cert_hal.send_hci_command(
- LeSetExtendedAdvertisingRandomAddressBuilder(advertising_handle, '0C:05:04:03:02:01'))
- gap_name = GapData()
- gap_name.data_type = GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(b'Im_A_Cert'))
-
- self.cert_hal.send_hci_command(
- LeSetExtendedAdvertisingDataBuilder(advertising_handle, Operation.COMPLETE_ADVERTISEMENT,
- FragmentPreference.CONTROLLER_SHOULD_NOT, [gap_name]))
-
- gap_short_name = GapData()
- gap_short_name.data_type = GapDataType.SHORTENED_LOCAL_NAME
- gap_short_name.data = list(bytes(b'Im_A_C'))
-
- self.cert_hal.send_hci_command(
- LeSetExtendedAdvertisingScanResponseBuilder(advertising_handle, Operation.COMPLETE_ADVERTISEMENT,
- FragmentPreference.CONTROLLER_SHOULD_NOT, [gap_short_name]))
-
- enabled_set = EnabledSet()
- enabled_set.advertising_handle = 0
- enabled_set.duration = 0
- enabled_set.max_extended_advertising_events = 0
- self.cert_hal.send_hci_command(LeSetExtendedAdvertisingEnableBuilder(Enable.ENABLED, [enabled_set]))
-
- assertThat(self.dut_hci.get_le_event_stream()).emits(lambda packet: b'Im_A_Cert' in packet.payload)
-
- self.cert_hal.send_hci_command(LeSetExtendedAdvertisingEnableBuilder(Enable.DISABLED, [enabled_set]))
- self.dut_hci.send_command(LeSetExtendedScanEnableBuilder(Enable.DISABLED, FilterDuplicates.DISABLED, 0, 0))
-
- def _verify_le_connection_complete(self):
- cert_conn_complete_capture = HalCaptures.LeConnectionCompleteCapture()
- assertThat(self.cert_hal.get_hci_event_stream()).emits(cert_conn_complete_capture)
- cert_handle = cert_conn_complete_capture.get().GetConnectionHandle()
-
- dut_conn_complete_capture = HciCaptures.LeConnectionCompleteCapture()
- assertThat(self.dut_hci.get_le_event_stream()).emits(dut_conn_complete_capture)
- dut_handle = dut_conn_complete_capture.get().GetConnectionHandle()
-
- return (dut_handle, cert_handle)
-
- @staticmethod
- def _create_phy_scan_params():
- phy_scan_params = LeCreateConnPhyScanParameters()
- phy_scan_params.scan_interval = 0x60
- phy_scan_params.scan_window = 0x30
- phy_scan_params.conn_interval_min = 0x18
- phy_scan_params.conn_interval_max = 0x28
- phy_scan_params.conn_latency = 0
- phy_scan_params.supervision_timeout = 0x1f4
- phy_scan_params.min_ce_length = 0
- phy_scan_params.max_ce_length = 0
- return phy_scan_params
+ self.register_for_le_event(
+ hci_packets.SubeventCode.EXTENDED_ADVERTISING_REPORT)
+ self.register_for_le_event(hci_packets.SubeventCode.ADVERTISING_REPORT)
+ with EventCallbackStream(
+ self.device_under_test.hci.FetchLeSubevents(
+ empty_proto.Empty())) as hci_le_event_stream:
+
+ hci_event_asserts = EventAsserts(hci_le_event_stream)
+
+ # DUT Scans
+ self.enqueue_hci_command(
+ hci_packets.LeSetRandomAddressBuilder('0D:05:04:03:02:01'),
+ True)
+ phy_scan_params = hci_packets.PhyScanParameters()
+ phy_scan_params.le_scan_interval = 6553
+ phy_scan_params.le_scan_window = 6553
+ phy_scan_params.le_scan_type = hci_packets.LeScanType.ACTIVE
+
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedScanParametersBuilder(
+ hci_packets.AddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.LeSetScanningFilterPolicy.ACCEPT_ALL, 1,
+ [phy_scan_params]), True)
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedScanEnableBuilder(
+ hci_packets.Enable.ENABLED,
+ hci_packets.FilterDuplicates.DISABLED, 0, 0), True)
+
+ # CERT Advertises
+ advertising_handle = 0
+ self.send_hal_hci_command(
+ hci_packets.LeSetExtendedAdvertisingLegacyParametersBuilder(
+ advertising_handle,
+ hci_packets.LegacyAdvertisingProperties.ADV_IND,
+ 512,
+ 768,
+ 7,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.PeerAddressType.
+ PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
+ 'A6:A5:A4:A3:A2:A1',
+ hci_packets.AdvertisingFilterPolicy.ALL_DEVICES,
+ 0xF7,
+ 1, # SID
+ hci_packets.Enable.DISABLED # Scan request notification
+ ))
+
+ self.send_hal_hci_command(
+ hci_packets.LeSetExtendedAdvertisingRandomAddressBuilder(
+ advertising_handle, '0C:05:04:03:02:01'))
+ gap_name = hci_packets.GapData()
+ gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
+ gap_name.data = list(bytes(b'Im_A_Cert!')) # TODO: Fix and remove !
+
+ self.send_hal_hci_command(
+ hci_packets.LeSetExtendedAdvertisingDataBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_name]))
+
+ gap_short_name = hci_packets.GapData()
+ gap_short_name.data_type = hci_packets.GapDataType.SHORTENED_LOCAL_NAME
+ gap_short_name.data = list(bytes(b'Im_A_C'))
+
+ self.send_hal_hci_command(
+ hci_packets.LeSetExtendedAdvertisingScanResponseBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_short_name]))
+
+ enabled_set = hci_packets.EnabledSet()
+ enabled_set.advertising_handle = 0
+ enabled_set.duration = 0
+ enabled_set.max_extended_advertising_events = 0
+ self.send_hal_hci_command(
+ hci_packets.LeSetExtendedAdvertisingEnableBuilder(
+ hci_packets.Enable.ENABLED, [enabled_set]))
+
+ hci_event_asserts.assert_event_occurs(
+ lambda packet: b'Im_A_Cert' in packet.event)
+
+ self.send_hal_hci_command(
+ hci_packets.LeSetExtendedAdvertisingEnableBuilder(
+ hci_packets.Enable.DISABLED, [enabled_set]))
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedScanEnableBuilder(
+ hci_packets.Enable.DISABLED,
+ hci_packets.FilterDuplicates.DISABLED, 0, 0), True)
def test_le_connection_dut_advertises(self):
- self.dut_hci.register_for_le_events(SubeventCode.CONNECTION_COMPLETE, SubeventCode.ADVERTISING_SET_TERMINATED,
- SubeventCode.ENHANCED_CONNECTION_COMPLETE,
- SubeventCode.READ_REMOTE_FEATURES_COMPLETE)
- # Cert Connects
- self.cert_hal.send_hci_command(LeSetRandomAddressBuilder('0C:05:04:03:02:01'))
- phy_scan_params = DirectHciTest._create_phy_scan_params()
- self.cert_hal.send_hci_command(
- LeExtendedCreateConnectionBuilder(InitiatorFilterPolicy.USE_PEER_ADDRESS,
- OwnAddressType.RANDOM_DEVICE_ADDRESS, AddressType.RANDOM_DEVICE_ADDRESS,
- '0D:05:04:03:02:01', 1, [phy_scan_params]))
-
- advertisement = self.dut_hci.create_advertisement(0, '0D:05:04:03:02:01')
- advertisement.set_data(b'Im_The_DUT')
- advertisement.set_scan_response(b'Im_The_D')
- advertisement.start()
-
- (dut_handle, cert_handle) = self._verify_le_connection_complete()
-
- self.dut_hci.send_command(LeReadRemoteFeaturesBuilder(dut_handle))
- assertThat(self.dut_hci.get_le_event_stream()).emits(
- lambda packet: packet.payload[0] == int(EventCode.LE_META_EVENT) and packet.payload[2] == int(SubeventCode.READ_REMOTE_FEATURES_COMPLETE)
- )
-
- # Send ACL Data
- self.enqueue_acl_data(dut_handle, PacketBoundaryFlag.FIRST_NON_AUTOMATICALLY_FLUSHABLE,
- BroadcastFlag.POINT_TO_POINT, bytes(b'Just SomeAclData'))
- self.cert_hal.send_acl_first(cert_handle, bytes(b'Just SomeMoreAclData'))
-
- assertThat(self.cert_hal.get_acl_stream()).emits(
- lambda packet: logging.debug(packet.payload) or b'SomeAclData' in packet.payload)
- assertThat(self.dut_hci.get_raw_acl_stream()).emits(
- lambda packet: logging.debug(packet.payload) or b'SomeMoreAclData' in packet.payload)
-
- def test_le_connect_list_connection_cert_advertises(self):
- self.dut_hci.register_for_le_events(SubeventCode.CONNECTION_COMPLETE, SubeventCode.ENHANCED_CONNECTION_COMPLETE)
- # DUT Connects
- self.dut_hci.send_command(LeSetRandomAddressBuilder('0D:05:04:03:02:01'))
- self.dut_hci.send_command(LeAddDeviceToConnectListBuilder(ConnectListAddressType.RANDOM, '0C:05:04:03:02:01'))
- phy_scan_params = DirectHciTest._create_phy_scan_params()
- self.dut_hci.send_command(
- LeExtendedCreateConnectionBuilder(InitiatorFilterPolicy.USE_CONNECT_LIST,
- OwnAddressType.RANDOM_DEVICE_ADDRESS, AddressType.RANDOM_DEVICE_ADDRESS,
- 'BA:D5:A4:A3:A2:A1', 1, [phy_scan_params]))
-
- advertisement = self.cert_hal.create_advertisement(
- 1,
- '0C:05:04:03:02:01',
- min_interval=512,
- max_interval=768,
- peer_address='A6:A5:A4:A3:A2:A1',
- tx_power=0x7f,
- sid=0)
- advertisement.set_data(b'Im_A_Cert')
- advertisement.start()
-
- # LeConnectionComplete
- self._verify_le_connection_complete()
+ self.register_for_le_event(hci_packets.SubeventCode.CONNECTION_COMPLETE)
+ with EventCallbackStream(self.device_under_test.hci.FetchLeSubevents(empty_proto.Empty())) as le_event_stream, \
+ EventCallbackStream(self.device_under_test.hci.FetchEvents(empty_proto.Empty())) as event_stream, \
+ EventCallbackStream(self.device_under_test.hci.FetchAclPackets(empty_proto.Empty())) as acl_data_stream, \
+ EventCallbackStream(self.cert_device.hal.FetchHciEvent(empty_proto.Empty())) as cert_hci_event_stream, \
+ EventCallbackStream(self.cert_device.hal.FetchHciAcl(empty_proto.Empty())) as cert_acl_data_stream:
+
+ le_event_asserts = EventAsserts(le_event_stream)
+ event_asserts = EventAsserts(event_stream)
+ cert_hci_event_asserts = EventAsserts(cert_hci_event_stream)
+ acl_data_asserts = EventAsserts(acl_data_stream)
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+
+ # Cert Connects
+ self.send_hal_hci_command(
+ hci_packets.LeSetRandomAddressBuilder('0C:05:04:03:02:01'))
+ phy_scan_params = hci_packets.LeCreateConnPhyScanParameters()
+ phy_scan_params.scan_interval = 0x60
+ phy_scan_params.scan_window = 0x30
+ phy_scan_params.conn_interval_min = 0x18
+ phy_scan_params.conn_interval_max = 0x28
+ phy_scan_params.conn_latency = 0
+ phy_scan_params.supervision_timeout = 0x1f4
+ phy_scan_params.min_ce_length = 0
+ phy_scan_params.max_ce_length = 0
+ self.send_hal_hci_command(
+ hci_packets.LeExtendedCreateConnectionBuilder(
+ hci_packets.InitiatorFilterPolicy.USE_PEER_ADDRESS,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.AddressType.RANDOM_DEVICE_ADDRESS,
+ '0D:05:04:03:02:01', 1, [phy_scan_params]))
+
+ # DUT Advertises
+ advertising_handle = 0
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingLegacyParametersBuilder(
+ advertising_handle,
+ hci_packets.LegacyAdvertisingProperties.ADV_IND,
+ 400,
+ 450,
+ 7,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.PeerAddressType.
+ PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
+ '00:00:00:00:00:00',
+ hci_packets.AdvertisingFilterPolicy.ALL_DEVICES,
+ 0xF8,
+ 1, #SID
+ hci_packets.Enable.DISABLED # Scan request notification
+ ),
+ True)
+
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingRandomAddressBuilder(
+ advertising_handle, '0D:05:04:03:02:01'), True)
+
+ gap_name = hci_packets.GapData()
+ gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
+ gap_name.data = list(
+ bytes(b'Im_The_DUT!')) # TODO: Fix and remove !
+
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingDataBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_name]), True)
+
+ gap_short_name = hci_packets.GapData()
+ gap_short_name.data_type = hci_packets.GapDataType.SHORTENED_LOCAL_NAME
+ gap_short_name.data = list(bytes(b'Im_The_D'))
+
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingScanResponseBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_short_name]), True)
+
+ enabled_set = hci_packets.EnabledSet()
+ enabled_set.advertising_handle = advertising_handle
+ enabled_set.duration = 0
+ enabled_set.max_extended_advertising_events = 0
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingEnableBuilder(
+ hci_packets.Enable.ENABLED, [enabled_set]), True)
+
+ # Check for success of Enable
+ event_asserts.assert_event_occurs(
+ lambda packet: b'\x0e\x04\x01\x39\x20\x00' in packet.event)
+
+ conn_handle = 0xfff
+
+ def event_handle(packet):
+ packet_bytes = packet.event
+ if b'\x3e\x13\x01\x00' in packet_bytes:
+ nonlocal conn_handle
+ cc_view = hci_packets.LeConnectionCompleteView(
+ hci_packets.LeMetaEventView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ conn_handle = cc_view.GetConnectionHandle()
+ return True
+ return False
+
+ def payload_handle(packet):
+ packet_bytes = packet.payload
+ if b'\x3e\x13\x01\x00' in packet_bytes:
+ nonlocal conn_handle
+ cc_view = hci_packets.LeConnectionCompleteView(
+ hci_packets.LeMetaEventView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ conn_handle = cc_view.GetConnectionHandle()
+ return True
+ return False
+
+ cert_hci_event_asserts.assert_event_occurs(payload_handle)
+ cert_handle = conn_handle
+ conn_handle = 0xfff
+ le_event_asserts.assert_event_occurs(event_handle)
+ dut_handle = conn_handle
+ if dut_handle == 0xfff:
+ logging.warning("Failed to get the DUT handle")
+ return False
+ if cert_handle == 0xfff:
+ logging.warning("Failed to get the CERT handle")
+ return False
+
+ # Send ACL Data
+ self.enqueue_acl_data(
+ dut_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_NON_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'Just SomeAclData'))
+ self.send_hal_acl_data(
+ cert_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_NON_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'Just SomeMoreAclData'))
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: logging.debug(packet.payload) or b'SomeAclData' in packet.payload
+ )
+ acl_data_asserts.assert_event_occurs(
+ lambda packet: logging.debug(packet.data) or b'SomeMoreAclData' in packet.data
+ )
+
+ def test_le_white_list_connection_cert_advertises(self):
+ self.register_for_le_event(hci_packets.SubeventCode.CONNECTION_COMPLETE)
+ with EventCallbackStream(self.device_under_test.hci.FetchLeSubevents(empty_proto.Empty())) as le_event_stream, \
+ EventCallbackStream(self.cert_device.hal.FetchHciEvent(empty_proto.Empty())) as cert_hci_event_stream:
+ le_event_asserts = EventAsserts(le_event_stream)
+ cert_hci_event_asserts = EventAsserts(cert_hci_event_stream)
+
+ # DUT Connects
+ self.enqueue_hci_command(
+ hci_packets.LeSetRandomAddressBuilder('0D:05:04:03:02:01'),
+ True)
+ self.enqueue_hci_command(
+ hci_packets.LeAddDeviceToWhiteListBuilder(
+ hci_packets.WhiteListAddressType.RANDOM,
+ '0C:05:04:03:02:01'), True)
+ phy_scan_params = hci_packets.LeCreateConnPhyScanParameters()
+ phy_scan_params.scan_interval = 0x60
+ phy_scan_params.scan_window = 0x30
+ phy_scan_params.conn_interval_min = 0x18
+ phy_scan_params.conn_interval_max = 0x28
+ phy_scan_params.conn_latency = 0
+ phy_scan_params.supervision_timeout = 0x1f4
+ phy_scan_params.min_ce_length = 0
+ phy_scan_params.max_ce_length = 0
+ self.enqueue_hci_command(
+ hci_packets.LeExtendedCreateConnectionBuilder(
+ hci_packets.InitiatorFilterPolicy.USE_WHITE_LIST,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.AddressType.RANDOM_DEVICE_ADDRESS,
+ 'BA:D5:A4:A3:A2:A1', 1, [phy_scan_params]), False)
+
+ # CERT Advertises
+ advertising_handle = 1
+ self.send_hal_hci_command(
+ hci_packets.LeSetExtendedAdvertisingLegacyParametersBuilder(
+ advertising_handle,
+ hci_packets.LegacyAdvertisingProperties.ADV_IND,
+ 512,
+ 768,
+ 7,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.PeerAddressType.
+ PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
+ 'A6:A5:A4:A3:A2:A1',
+ hci_packets.AdvertisingFilterPolicy.ALL_DEVICES,
+ 0x7F,
+ 0, # SID
+ hci_packets.Enable.DISABLED # Scan request notification
+ ))
+
+ self.send_hal_hci_command(
+ hci_packets.LeSetExtendedAdvertisingRandomAddressBuilder(
+ advertising_handle, '0C:05:04:03:02:01'))
+
+ gap_name = hci_packets.GapData()
+ gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
+ gap_name.data = list(bytes(b'Im_A_Cert!')) # TODO: Fix and remove !
+
+ self.send_hal_hci_command(
+ hci_packets.LeSetExtendedAdvertisingDataBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_name]))
+ enabled_set = hci_packets.EnabledSet()
+ enabled_set.advertising_handle = 1
+ enabled_set.duration = 0
+ enabled_set.max_extended_advertising_events = 0
+ self.send_hal_hci_command(
+ hci_packets.LeSetExtendedAdvertisingEnableBuilder(
+ hci_packets.Enable.ENABLED, [enabled_set]))
+
+ # LeConnectionComplete
+ cert_hci_event_asserts.assert_event_occurs(
+ lambda packet: b'\x3e\x13\x01\x00' in packet.payload,
+ timeout=timedelta(seconds=20))
+ le_event_asserts.assert_event_occurs(
+ lambda packet: b'\x3e\x13\x01\x00' in packet.event)
def test_connection_dut_connects(self):
- self.dut_hci.send_command(WritePageTimeoutBuilder(0x4000))
-
- self.cert_hal.enable_inquiry_and_page_scan()
- address = self.cert_hal.read_own_address()
-
- self.dut_hci.initiate_connection(address)
- cert_acl = self.cert_hal.accept_connection()
- dut_acl = self.dut_hci.complete_connection()
-
- # Send ACL Data
- dut_acl.send_first(b'Just SomeAclData')
- cert_acl.send_first(b'Just SomeMoreAclData')
-
- assertThat(self.cert_hal.get_acl_stream()).emits(lambda packet: b'SomeAclData' in packet.payload)
- assertThat(self.dut_hci.get_raw_acl_stream()).emits(lambda packet: b'SomeMoreAclData' in packet.payload)
+ self.register_for_event(hci_packets.EventCode.CONNECTION_COMPLETE)
+ self.register_for_event(
+ hci_packets.EventCode.CONNECTION_PACKET_TYPE_CHANGED)
+ self.enqueue_hci_command(
+ hci_packets.WritePageTimeoutBuilder(0x4000), True)
+ with EventCallbackStream(self.device_under_test.hci.FetchEvents(empty_proto.Empty())) as hci_event_stream, \
+ EventCallbackStream(self.device_under_test.hci.FetchAclPackets(empty_proto.Empty())) as acl_data_stream, \
+ EventCallbackStream(self.cert_device.hal.FetchHciEvent(empty_proto.Empty())) as cert_hci_event_stream, \
+ EventCallbackStream(self.cert_device.hal.FetchHciAcl(empty_proto.Empty())) as cert_acl_data_stream:
+
+ cert_hci_event_asserts = EventAsserts(cert_hci_event_stream)
+ hci_event_asserts = EventAsserts(hci_event_stream)
+ acl_data_asserts = EventAsserts(acl_data_stream)
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+
+ address = hci_packets.Address()
+
+ def get_address_from_complete(packet):
+ packet_bytes = packet.payload
+ if b'\x0e\x0a\x01\x09\x10' in packet_bytes:
+ nonlocal address
+ addr_view = hci_packets.ReadBdAddrCompleteView(
+ hci_packets.CommandCompleteView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ address = addr_view.GetBdAddr()
+ return True
+ return False
+
+ # CERT Enables scans and gets its address
+ self.send_hal_hci_command(hci_packets.ReadBdAddrBuilder())
+
+ cert_hci_event_asserts.assert_event_occurs(
+ get_address_from_complete)
+ self.send_hal_hci_command(
+ hci_packets.WriteScanEnableBuilder(
+ hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN))
+
+ # DUT Connects
+ self.enqueue_hci_command(
+ hci_packets.CreateConnectionBuilder(
+ address,
+ 0xcc18, # Packet Type
+ hci_packets.PageScanRepetitionMode.R0,
+ 0,
+ hci_packets.ClockOffsetValid.INVALID,
+ hci_packets.CreateConnectionRoleSwitch.ALLOW_ROLE_SWITCH),
+ False)
+
+ # Cert Accepts
+ connection_request = None
+
+ def get_connect_request(packet):
+ if b'\x04\x0a' in packet.payload:
+ nonlocal connection_request
+ connection_request = hci_packets.ConnectionRequestView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet.payload))))
+ return True
+ return False
+
+ # Cert Accepts
+ cert_hci_event_asserts.assert_event_occurs(
+ get_connect_request, timeout=timedelta(seconds=20))
+ self.send_hal_hci_command(
+ hci_packets.AcceptConnectionRequestBuilder(
+ connection_request.GetBdAddr(),
+ hci_packets.AcceptConnectionRequestRole.REMAIN_SLAVE))
+
+ conn_handle = 0xfff
+
+ def get_handle(packet_bytes):
+ if b'\x03\x0b\x00' in packet_bytes:
+ nonlocal conn_handle
+ cc_view = hci_packets.ConnectionCompleteView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes))))
+ conn_handle = cc_view.GetConnectionHandle()
+ return True
+ return False
+
+ def event_handle(packet):
+ packet_bytes = packet.event
+ return get_handle(packet_bytes)
+
+ def payload_handle(packet):
+ packet_bytes = packet.payload
+ return get_handle(packet_bytes)
+
+ cert_hci_event_asserts.assert_event_occurs(payload_handle)
+ cert_handle = conn_handle
+ conn_handle = 0xfff
+ hci_event_asserts.assert_event_occurs(event_handle)
+ dut_handle = conn_handle
+ if dut_handle == 0xfff:
+ logging.warning("Failed to get the DUT handle")
+ return False
+ if cert_handle == 0xfff:
+ logging.warning("Failed to get the CERT handle")
+ return False
+
+ # Send ACL Data
+ self.enqueue_acl_data(
+ dut_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_NON_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'Just SomeAclData'))
+ self.send_hal_acl_data(
+ cert_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_NON_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'Just SomeMoreAclData'))
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeAclData' in packet.payload)
+ acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeMoreAclData' in packet.data)
def test_connection_cert_connects(self):
- self.cert_hal.send_hci_command(WritePageTimeoutBuilder(0x4000))
-
- self.dut_hci.enable_inquiry_and_page_scan()
- address = self.dut_hci.read_own_address()
-
- self.cert_hal.initiate_connection(address)
- dut_acl = self.dut_hci.accept_connection()
- cert_acl = self.cert_hal.complete_connection()
-
- # Send ACL Data
- dut_acl.send_first(b'This is just SomeAclData')
- cert_acl.send_first(b'This is just SomeMoreAclData')
-
- assertThat(self.cert_hal.get_acl_stream()).emits(lambda packet: b'SomeAclData' in packet.payload)
- assertThat(self.dut_hci.get_raw_acl_stream()).emits(lambda packet: b'SomeMoreAclData' in packet.payload)
+ self.register_for_event(hci_packets.EventCode.CONNECTION_COMPLETE)
+ self.register_for_event(
+ hci_packets.EventCode.CONNECTION_PACKET_TYPE_CHANGED)
+ self.register_for_event(hci_packets.EventCode.CONNECTION_REQUEST)
+ self.send_hal_hci_command(hci_packets.WritePageTimeoutBuilder(0x4000))
+ with EventCallbackStream(self.device_under_test.hci.FetchEvents(empty_proto.Empty())) as hci_event_stream, \
+ EventCallbackStream(self.device_under_test.hci.FetchAclPackets(empty_proto.Empty())) as acl_data_stream, \
+ EventCallbackStream(self.cert_device.hal.FetchHciEvent(empty_proto.Empty())) as cert_hci_event_stream, \
+ EventCallbackStream(self.cert_device.hal.FetchHciAcl(empty_proto.Empty())) as cert_acl_data_stream:
+
+ hci_event_asserts = EventAsserts(hci_event_stream)
+ cert_hci_event_asserts = EventAsserts(cert_hci_event_stream)
+ acl_data_asserts = EventAsserts(acl_data_stream)
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+
+ address = hci_packets.Address()
+
+ def get_address_from_complete(packet):
+ packet_bytes = packet.event
+ if b'\x0e\x0a\x01\x09\x10' in packet_bytes:
+ nonlocal address
+ addr_view = hci_packets.ReadBdAddrCompleteView(
+ hci_packets.CommandCompleteView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ address = addr_view.GetBdAddr()
+ return True
+ return False
+
+ # DUT Enables scans and gets its address
+ self.enqueue_hci_command(
+ hci_packets.WriteScanEnableBuilder(
+ hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN), True)
+ self.enqueue_hci_command(hci_packets.ReadBdAddrBuilder(), True)
+
+ hci_event_asserts.assert_event_occurs(get_address_from_complete)
+
+ # Cert Connects
+ self.send_hal_hci_command(
+ hci_packets.CreateConnectionBuilder(
+ address,
+ 0xcc18, # Packet Type
+ hci_packets.PageScanRepetitionMode.R0,
+ 0,
+ hci_packets.ClockOffsetValid.INVALID,
+ hci_packets.CreateConnectionRoleSwitch.ALLOW_ROLE_SWITCH))
+
+ # DUT Accepts
+ connection_request = None
+
+ def get_connect_request(packet):
+ if b'\x04\x0a' in packet.event:
+ nonlocal connection_request
+ connection_request = hci_packets.ConnectionRequestView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet.event))))
+ return True
+ return False
+
+ hci_event_asserts.assert_event_occurs(
+ get_connect_request, timeout=timedelta(seconds=20))
+ self.enqueue_hci_command(
+ hci_packets.AcceptConnectionRequestBuilder(
+ connection_request.GetBdAddr(),
+ hci_packets.AcceptConnectionRequestRole.REMAIN_SLAVE),
+ False)
+
+ conn_handle = 0xfff
+
+ def get_handle(packet_bytes):
+ if b'\x03\x0b\x00' in packet_bytes:
+ nonlocal conn_handle
+ cc_view = hci_packets.ConnectionCompleteView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes))))
+ conn_handle = cc_view.GetConnectionHandle()
+ return True
+ return False
+
+ def event_handle(packet):
+ packet_bytes = packet.event
+ return get_handle(packet_bytes)
+
+ def payload_handle(packet):
+ packet_bytes = packet.payload
+ return get_handle(packet_bytes)
+
+ cert_hci_event_asserts.assert_event_occurs(payload_handle)
+ cert_handle = conn_handle
+ conn_handle = 0xfff
+ hci_event_asserts.assert_event_occurs(event_handle)
+ dut_handle = conn_handle
+ if dut_handle == 0xfff:
+ logging.warning("Failed to get the DUT handle")
+ return False
+ if cert_handle == 0xfff:
+ logging.warning("Failed to get the CERT handle")
+ return False
+
+ # Send ACL Data
+ self.enqueue_acl_data(
+ dut_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_NON_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'This is just SomeAclData'))
+ self.send_hal_acl_data(
+ cert_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_NON_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'This is just SomeMoreAclData'))
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeAclData' in packet.payload)
+ acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeMoreAclData' in packet.data)
diff --git a/gd/hci/cert/le_acl_manager_test.py b/gd/hci/cert/le_acl_manager_test.py
index aa3d75e94..1abf0a20a 100644
--- a/gd/hci/cert/le_acl_manager_test.py
+++ b/gd/hci/cert/le_acl_manager_test.py
@@ -14,279 +14,406 @@
# See the License for the specific language governing permissions and
# limitations under the License.
-from cert.closable import safeClose
-from cert.gd_base_test import GdBaseTestClass
-from cert.event_stream import EventStream
-from cert.truth import assertThat
-from cert.py_le_acl_manager import PyLeAclManager
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
+from cert.event_callback_stream import EventCallbackStream
+from cert.event_asserts import EventAsserts
from google.protobuf import empty_pb2 as empty_proto
+from facade import rootservice_pb2 as facade_rootservice
from facade import common_pb2 as common
from hci.facade import le_acl_manager_facade_pb2 as le_acl_manager_facade
from hci.facade import le_advertising_manager_facade_pb2 as le_advertising_facade
-from hci.facade import le_initiator_address_facade_pb2 as le_initiator_address_facade
-from hci.facade import hci_facade_pb2 as hci_facade
+from hci.facade import facade_pb2 as hci_facade
import bluetooth_packets_python3 as bt_packets
from bluetooth_packets_python3 import hci_packets
-from bluetooth_packets_python3 import RawBuilder
-class LeAclManagerTest(GdBaseTestClass):
-
- def setup_class(self):
- super().setup_class(dut_module='HCI_INTERFACES', cert_module='HCI')
+class LeAclManagerTest(GdFacadeOnlyBaseTestClass):
def setup_test(self):
- super().setup_test()
- self.dut_le_acl_manager = PyLeAclManager(self.dut)
- self.cert_hci_le_event_stream = EventStream(self.cert.hci.StreamLeSubevents(empty_proto.Empty()))
- self.cert_acl_data_stream = EventStream(self.cert.hci.StreamAcl(empty_proto.Empty()))
+ self.device_under_test.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI_INTERFACES'),))
+ self.cert_device.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI'),))
+
+ self.device_under_test.wait_channel_ready()
+ self.cert_device.wait_channel_ready()
def teardown_test(self):
- safeClose(self.cert_hci_le_event_stream)
- safeClose(self.cert_acl_data_stream)
- safeClose(self.dut_le_acl_manager)
- super().teardown_test()
-
- def set_privacy_policy_static(self):
- self.dut_address = b'd0:05:04:03:02:01'
- private_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_STATIC_ADDRESS,
- address_with_type=common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes(self.dut_address)), type=common.RANDOM_DEVICE_ADDRESS))
- self.dut.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(private_policy)
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+ self.cert_device.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
def register_for_event(self, event_code):
- msg = hci_facade.EventRequest(code=int(event_code))
- self.cert.hci.RequestEvent(msg)
+ msg = hci_facade.EventCodeMsg(code=int(event_code))
+ self.cert_device.hci.RegisterEventHandler(msg)
def register_for_le_event(self, event_code):
- msg = hci_facade.EventRequest(code=int(event_code))
- self.cert.hci.RequestLeSubevent(msg)
+ msg = hci_facade.LeSubeventCodeMsg(code=int(event_code))
+ self.cert_device.hci.RegisterLeEventHandler(msg)
- def enqueue_hci_command(self, command):
+ def enqueue_hci_command(self, command, expect_complete):
cmd_bytes = bytes(command.Serialize())
- cmd = common.Data(payload=cmd_bytes)
- self.cert.hci.SendCommand(cmd)
-
- def enqueue_acl_data(self, handle, pb_flag, b_flag, data):
- acl = hci_packets.AclBuilder(handle, pb_flag, b_flag, RawBuilder(data))
- self.cert.hci.SendAcl(common.Data(payload=bytes(acl.Serialize())))
-
- def dut_connects(self, check_address):
- self.register_for_le_event(hci_packets.SubeventCode.CONNECTION_COMPLETE)
- self.register_for_le_event(hci_packets.SubeventCode.ENHANCED_CONNECTION_COMPLETE)
-
- # Cert Advertises
- advertising_handle = 0
- self.enqueue_hci_command(
- hci_packets.LeSetExtendedAdvertisingLegacyParametersBuilder(
- advertising_handle,
- hci_packets.LegacyAdvertisingProperties.ADV_IND,
- 400,
- 450,
- 7,
- hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
- hci_packets.PeerAddressType.PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
- '00:00:00:00:00:00',
- hci_packets.AdvertisingFilterPolicy.ALL_DEVICES,
- 0xF8,
- 1, #SID
- hci_packets.Enable.DISABLED # Scan request notification
- ))
-
- self.enqueue_hci_command(
- hci_packets.LeSetExtendedAdvertisingRandomAddressBuilder(advertising_handle, '0C:05:04:03:02:01'))
-
- gap_name = hci_packets.GapData()
- gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(b'Im_A_Cert'))
-
- self.enqueue_hci_command(
- hci_packets.LeSetExtendedAdvertisingDataBuilder(
- advertising_handle, hci_packets.Operation.COMPLETE_ADVERTISEMENT,
- hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT, [gap_name]))
-
- gap_short_name = hci_packets.GapData()
- gap_short_name.data_type = hci_packets.GapDataType.SHORTENED_LOCAL_NAME
- gap_short_name.data = list(bytes(b'Im_A_C'))
-
- self.enqueue_hci_command(
- hci_packets.LeSetExtendedAdvertisingScanResponseBuilder(
- advertising_handle, hci_packets.Operation.COMPLETE_ADVERTISEMENT,
- hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT, [gap_short_name]))
-
- enabled_set = hci_packets.EnabledSet()
- enabled_set.advertising_handle = advertising_handle
- enabled_set.duration = 0
- enabled_set.max_extended_advertising_events = 0
- self.enqueue_hci_command(
- hci_packets.LeSetExtendedAdvertisingEnableBuilder(hci_packets.Enable.ENABLED, [enabled_set]))
-
- self.dut_le_acl = self.dut_le_acl_manager.connect_to_remote(
- remote_addr=common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes('0C:05:04:03:02:01', 'utf8')),
- type=int(hci_packets.AddressType.RANDOM_DEVICE_ADDRESS)))
-
- # Cert gets ConnectionComplete with a handle and sends ACL data
- handle = 0xfff
- address = hci_packets.Address()
-
- def get_handle(packet):
- packet_bytes = packet.payload
- nonlocal handle
- nonlocal address
- if b'\x3e\x13\x01\x00' in packet_bytes:
- cc_view = hci_packets.LeConnectionCompleteView(
- hci_packets.LeMetaEventView(
- hci_packets.EventView(bt_packets.PacketViewLittleEndian(list(packet_bytes)))))
- handle = cc_view.GetConnectionHandle()
- address = cc_view.GetPeerAddress()
- return True
- if b'\x3e\x13\x0A\x00' in packet_bytes:
- cc_view = hci_packets.LeEnhancedConnectionCompleteView(
- hci_packets.LeMetaEventView(
- hci_packets.EventView(bt_packets.PacketViewLittleEndian(list(packet_bytes)))))
- handle = cc_view.GetConnectionHandle()
- address = cc_view.GetPeerResolvablePrivateAddress()
- return True
- return False
-
- self.cert_hci_le_event_stream.assert_event_occurs(get_handle)
- self.cert_handle = handle
- dut_address_from_complete = address
- if check_address:
- assertThat(dut_address_from_complete).isEqualTo(self.dut_address.decode())
-
- def send_receive_and_check(self):
- self.enqueue_acl_data(self.cert_handle, hci_packets.PacketBoundaryFlag.FIRST_NON_AUTOMATICALLY_FLUSHABLE,
- hci_packets.BroadcastFlag.POINT_TO_POINT,
- bytes(b'\x19\x00\x07\x00SomeAclData from the Cert'))
-
- self.dut_le_acl.send(b'\x1C\x00\x07\x00SomeMoreAclData from the DUT')
- self.cert_acl_data_stream.assert_event_occurs(lambda packet: b'SomeMoreAclData' in packet.payload)
- assertThat(self.dut_le_acl).emits(lambda packet: b'SomeAclData' in packet.payload)
+ cmd = hci_facade.CommandMsg(command=cmd_bytes)
+ if (expect_complete):
+ self.cert_device.hci.EnqueueCommandWithComplete(cmd)
+ else:
+ self.cert_device.hci.EnqueueCommandWithStatus(cmd)
+
+ def enqueue_acl_data(self, handle, pb_flag, b_flag, acl):
+ acl_msg = hci_facade.AclMsg(
+ handle=int(handle),
+ packet_boundary_flag=int(pb_flag),
+ broadcast_flag=int(b_flag),
+ data=acl)
+ self.cert_device.hci.SendAclData(acl_msg)
def test_dut_connects(self):
- self.set_privacy_policy_static()
- self.dut_connects(check_address=True)
- self.send_receive_and_check()
-
- def test_dut_connects_resolvable_address(self):
- privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_RESOLVABLE_ADDRESS,
- rotation_irk=b'\x00\x01\x02\x03\x04\x05\x06\x07\x08\x09\x0a\x0b\x0c\x0d\x0e\x0f',
- minimum_rotation_time=7 * 60 * 1000,
- maximum_rotation_time=15 * 60 * 1000)
- self.dut.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(privacy_policy)
- self.dut_connects(check_address=False)
- self.send_receive_and_check()
-
- def test_dut_connects_non_resolvable_address(self):
- privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_NON_RESOLVABLE_ADDRESS,
- rotation_irk=b'\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f',
- minimum_rotation_time=8 * 60 * 1000,
- maximum_rotation_time=14 * 60 * 1000)
- self.dut.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(privacy_policy)
- self.dut_connects(check_address=False)
- self.send_receive_and_check()
-
- def test_dut_connects_public_address(self):
- self.dut.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(
- le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_PUBLIC_ADDRESS))
- self.dut_connects(check_address=False)
- self.send_receive_and_check()
-
- def test_dut_connects_public_address_cancelled(self):
- self.dut.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(
- le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_PUBLIC_ADDRESS))
- self.dut_connects(check_address=False)
- self.send_receive_and_check()
+ self.register_for_le_event(hci_packets.SubeventCode.CONNECTION_COMPLETE)
+ with EventCallbackStream(self.cert_device.hci.FetchLeSubevents(empty_proto.Empty())) as cert_hci_le_event_stream, \
+ EventCallbackStream(self.cert_device.hci.FetchAclPackets(empty_proto.Empty())) as cert_acl_data_stream, \
+ EventCallbackStream(self.device_under_test.hci_le_acl_manager.FetchAclData(empty_proto.Empty())) as acl_data_stream:
+
+ cert_hci_le_event_asserts = EventAsserts(cert_hci_le_event_stream)
+ acl_data_asserts = EventAsserts(acl_data_stream)
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+
+ # Cert Advertises
+ advertising_handle = 0
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingLegacyParametersBuilder(
+ advertising_handle,
+ hci_packets.LegacyAdvertisingProperties.ADV_IND,
+ 400,
+ 450,
+ 7,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.PeerAddressType.
+ PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
+ '00:00:00:00:00:00',
+ hci_packets.AdvertisingFilterPolicy.ALL_DEVICES,
+ 0xF8,
+ 1, #SID
+ hci_packets.Enable.DISABLED # Scan request notification
+ ),
+ True)
+
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingRandomAddressBuilder(
+ advertising_handle, '0C:05:04:03:02:01'), True)
+
+ gap_name = hci_packets.GapData()
+ gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
+ gap_name.data = list(bytes(b'Im_A_Cert'))
+
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingDataBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_name]), True)
+
+ gap_short_name = hci_packets.GapData()
+ gap_short_name.data_type = hci_packets.GapDataType.SHORTENED_LOCAL_NAME
+ gap_short_name.data = list(bytes(b'Im_A_C'))
+
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingScanResponseBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_short_name]), True)
+
+ enabled_set = hci_packets.EnabledSet()
+ enabled_set.advertising_handle = advertising_handle
+ enabled_set.duration = 0
+ enabled_set.max_extended_advertising_events = 0
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingEnableBuilder(
+ hci_packets.Enable.ENABLED, [enabled_set]), True)
+
+ with EventCallbackStream(
+ self.device_under_test.hci_le_acl_manager.CreateConnection(
+ le_acl_manager_facade.LeConnectionMsg(
+ address_type=int(
+ hci_packets.AddressType.RANDOM_DEVICE_ADDRESS),
+ address=bytes('0C:05:04:03:02:01',
+ 'utf8')))) as connection_event_stream:
+
+ connection_event_asserts = EventAsserts(connection_event_stream)
+
+ # Cert gets ConnectionComplete with a handle and sends ACL data
+ handle = 0xfff
+
+ def get_handle(packet):
+ packet_bytes = packet.event
+ nonlocal handle
+ if b'\x3e\x13\x01\x00' in packet_bytes:
+ cc_view = hci_packets.LeConnectionCompleteView(
+ hci_packets.LeMetaEventView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ handle = cc_view.GetConnectionHandle()
+ return True
+ if b'\x3e\x13\x0A\x00' in packet_bytes:
+ cc_view = hci_packets.LeEnhancedConnectionCompleteView(
+ hci_packets.LeMetaEventView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ handle = cc_view.GetConnectionHandle()
+ return True
+ return False
+
+ cert_hci_le_event_asserts.assert_event_occurs(get_handle)
+ cert_handle = handle
+
+ self.enqueue_acl_data(
+ cert_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'\x19\x00\x07\x00SomeAclData from the Cert'))
+
+ # DUT gets a connection complete event and sends and receives
+ handle = 0xfff
+ connection_event_asserts.assert_event_occurs(get_handle)
+
+ self.device_under_test.hci_le_acl_manager.SendAclData(
+ le_acl_manager_facade.LeAclData(
+ handle=handle,
+ payload=bytes(
+ b'\x1C\x00\x07\x00SomeMoreAclData from the DUT')))
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeMoreAclData' in packet.data)
+ acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeAclData' in packet.payload)
def test_cert_connects(self):
- self.set_privacy_policy_static()
self.register_for_le_event(hci_packets.SubeventCode.CONNECTION_COMPLETE)
-
- self.dut_le_acl_manager.listen_for_incoming_connections()
-
- # DUT Advertises
- gap_name = hci_packets.GapData()
- gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(b'Im_The_DUT'))
- gap_data = le_advertising_facade.GapDataMsg(data=bytes(gap_name.Serialize()))
- config = le_advertising_facade.AdvertisingConfig(
- advertisement=[gap_data],
- interval_min=512,
- interval_max=768,
- advertising_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
- own_address_type=common.USE_RANDOM_DEVICE_ADDRESS,
- peer_address_type=common.PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
- peer_address=common.BluetoothAddress(address=bytes(b'A6:A5:A4:A3:A2:A1')),
- channel_map=7,
- filter_policy=le_advertising_facade.AdvertisingFilterPolicy.ALL_DEVICES)
- request = le_advertising_facade.CreateAdvertiserRequest(config=config)
-
- self.dut.hci_le_advertising_manager.CreateAdvertiser(request)
-
- # Cert Connects
- self.enqueue_hci_command(hci_packets.LeSetRandomAddressBuilder('0C:05:04:03:02:01'))
- phy_scan_params = hci_packets.LeCreateConnPhyScanParameters()
- phy_scan_params.scan_interval = 0x60
- phy_scan_params.scan_window = 0x30
- phy_scan_params.conn_interval_min = 0x18
- phy_scan_params.conn_interval_max = 0x28
- phy_scan_params.conn_latency = 0
- phy_scan_params.supervision_timeout = 0x1f4
- phy_scan_params.min_ce_length = 0
- phy_scan_params.max_ce_length = 0
- self.enqueue_hci_command(
- hci_packets.LeExtendedCreateConnectionBuilder(hci_packets.InitiatorFilterPolicy.USE_PEER_ADDRESS,
- hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
- hci_packets.AddressType.RANDOM_DEVICE_ADDRESS,
- self.dut_address.decode(), 1, [phy_scan_params]))
-
- # Cert gets ConnectionComplete with a handle and sends ACL data
- handle = 0xfff
-
- def get_handle(packet):
- packet_bytes = packet.payload
- nonlocal handle
- if b'\x3e\x13\x01\x00' in packet_bytes:
- cc_view = hci_packets.LeConnectionCompleteView(
- hci_packets.LeMetaEventView(
- hci_packets.EventView(bt_packets.PacketViewLittleEndian(list(packet_bytes)))))
- handle = cc_view.GetConnectionHandle()
- return True
- if b'\x3e\x13\x0A\x00' in packet_bytes:
- cc_view = hci_packets.LeEnhancedConnectionCompleteView(
- hci_packets.LeMetaEventView(
- hci_packets.EventView(bt_packets.PacketViewLittleEndian(list(packet_bytes)))))
- handle = cc_view.GetConnectionHandle()
- return True
- return False
-
- self.cert_hci_le_event_stream.assert_event_occurs(get_handle)
- self.cert_handle = handle
-
- self.enqueue_acl_data(self.cert_handle, hci_packets.PacketBoundaryFlag.FIRST_NON_AUTOMATICALLY_FLUSHABLE,
- hci_packets.BroadcastFlag.POINT_TO_POINT,
- bytes(b'\x19\x00\x07\x00SomeAclData from the Cert'))
-
- # DUT gets a connection complete event and sends and receives
- handle = 0xfff
- self.dut_le_acl = self.dut_le_acl_manager.complete_incoming_connection()
-
- self.send_receive_and_check()
+ with EventCallbackStream(self.cert_device.hci.FetchLeSubevents(empty_proto.Empty())) as cert_hci_le_event_stream, \
+ EventCallbackStream(self.cert_device.hci.FetchAclPackets(empty_proto.Empty())) as cert_acl_data_stream, \
+ EventCallbackStream(self.device_under_test.hci_le_acl_manager.FetchIncomingConnection(empty_proto.Empty())) as incoming_connection_stream, \
+ EventCallbackStream(self.device_under_test.hci_le_acl_manager.FetchAclData(empty_proto.Empty())) as acl_data_stream:
+
+ cert_hci_le_event_asserts = EventAsserts(cert_hci_le_event_stream)
+ incoming_connection_asserts = EventAsserts(
+ incoming_connection_stream)
+ acl_data_asserts = EventAsserts(acl_data_stream)
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+
+ # DUT Advertises
+ gap_name = hci_packets.GapData()
+ gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
+ gap_name.data = list(bytes(b'Im_The_DUT'))
+ gap_data = le_advertising_facade.GapDataMsg(
+ data=bytes(gap_name.Serialize()))
+ config = le_advertising_facade.AdvertisingConfig(
+ advertisement=[gap_data],
+ random_address=common.BluetoothAddress(
+ address=bytes(b'0D:05:04:03:02:01')),
+ interval_min=512,
+ interval_max=768,
+ event_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
+ address_type=common.RANDOM_DEVICE_ADDRESS,
+ peer_address_type=common.PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
+ peer_address=common.BluetoothAddress(
+ address=bytes(b'A6:A5:A4:A3:A2:A1')),
+ channel_map=7,
+ filter_policy=le_advertising_facade.AdvertisingFilterPolicy.
+ ALL_DEVICES)
+ request = le_advertising_facade.CreateAdvertiserRequest(
+ config=config)
+
+ create_response = self.device_under_test.hci_le_advertising_manager.CreateAdvertiser(
+ request)
+
+ # Cert Connects
+ self.enqueue_hci_command(
+ hci_packets.LeSetRandomAddressBuilder('0C:05:04:03:02:01'),
+ True)
+ phy_scan_params = hci_packets.LeCreateConnPhyScanParameters()
+ phy_scan_params.scan_interval = 0x60
+ phy_scan_params.scan_window = 0x30
+ phy_scan_params.conn_interval_min = 0x18
+ phy_scan_params.conn_interval_max = 0x28
+ phy_scan_params.conn_latency = 0
+ phy_scan_params.supervision_timeout = 0x1f4
+ phy_scan_params.min_ce_length = 0
+ phy_scan_params.max_ce_length = 0
+ self.enqueue_hci_command(
+ hci_packets.LeExtendedCreateConnectionBuilder(
+ hci_packets.InitiatorFilterPolicy.USE_PEER_ADDRESS,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.AddressType.RANDOM_DEVICE_ADDRESS,
+ '0D:05:04:03:02:01', 1, [phy_scan_params]), False)
+
+ # Cert gets ConnectionComplete with a handle and sends ACL data
+ handle = 0xfff
+
+ def get_handle(packet):
+ packet_bytes = packet.event
+ nonlocal handle
+ if b'\x3e\x13\x01\x00' in packet_bytes:
+ cc_view = hci_packets.LeConnectionCompleteView(
+ hci_packets.LeMetaEventView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ handle = cc_view.GetConnectionHandle()
+ return True
+ if b'\x3e\x13\x0A\x00' in packet_bytes:
+ cc_view = hci_packets.LeEnhancedConnectionCompleteView(
+ hci_packets.LeMetaEventView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ handle = cc_view.GetConnectionHandle()
+ return True
+ return False
+
+ cert_hci_le_event_asserts.assert_event_occurs(get_handle)
+ cert_handle = handle
+
+ self.enqueue_acl_data(
+ cert_handle,
+ hci_packets.PacketBoundaryFlag.FIRST_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'\x19\x00\x07\x00SomeAclData from the Cert'))
+
+ # DUT gets a connection complete event and sends and receives
+ handle = 0xfff
+ incoming_connection_asserts.assert_event_occurs(get_handle)
+
+ self.device_under_test.hci_le_acl_manager.SendAclData(
+ le_acl_manager_facade.LeAclData(
+ handle=handle,
+ payload=bytes(
+ b'\x1C\x00\x07\x00SomeMoreAclData from the DUT')))
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeMoreAclData' in packet.data)
+ acl_data_asserts.assert_event_occurs(
+ lambda packet: b'SomeAclData' in packet.payload)
def test_recombination_l2cap_packet(self):
- self.set_privacy_policy_static()
- self.dut_connects(check_address=True)
-
- self.enqueue_acl_data(self.cert_handle, hci_packets.PacketBoundaryFlag.FIRST_NON_AUTOMATICALLY_FLUSHABLE,
- hci_packets.BroadcastFlag.POINT_TO_POINT, bytes(b'\x06\x00\x07\x00Hello'))
- self.enqueue_acl_data(self.cert_handle, hci_packets.PacketBoundaryFlag.CONTINUING_FRAGMENT,
- hci_packets.BroadcastFlag.POINT_TO_POINT, bytes(b'!'))
-
- assertThat(self.dut_le_acl).emits(lambda packet: b'Hello!' in packet.payload)
+ self.register_for_le_event(hci_packets.SubeventCode.CONNECTION_COMPLETE)
+ with EventCallbackStream(self.cert_device.hci.FetchLeSubevents(empty_proto.Empty())) as cert_hci_le_event_stream, \
+ EventCallbackStream(self.cert_device.hci.FetchAclPackets(empty_proto.Empty())) as cert_acl_data_stream, \
+ EventCallbackStream(self.device_under_test.hci_le_acl_manager.FetchAclData(empty_proto.Empty())) as acl_data_stream:
+
+ cert_hci_le_event_asserts = EventAsserts(cert_hci_le_event_stream)
+ acl_data_asserts = EventAsserts(acl_data_stream)
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+
+ # Cert Advertises
+ advertising_handle = 0
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingLegacyParametersBuilder(
+ advertising_handle,
+ hci_packets.LegacyAdvertisingProperties.ADV_IND,
+ 400,
+ 450,
+ 7,
+ hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.PeerAddressType.
+ PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
+ '00:00:00:00:00:00',
+ hci_packets.AdvertisingFilterPolicy.ALL_DEVICES,
+ 0xF8,
+ 1, #SID
+ hci_packets.Enable.DISABLED # Scan request notification
+ ),
+ True)
+
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingRandomAddressBuilder(
+ advertising_handle, '0C:05:04:03:02:01'), True)
+
+ gap_name = hci_packets.GapData()
+ gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
+ gap_name.data = list(bytes(b'Im_A_Cert'))
+
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingDataBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_name]), True)
+
+ gap_short_name = hci_packets.GapData()
+ gap_short_name.data_type = hci_packets.GapDataType.SHORTENED_LOCAL_NAME
+ gap_short_name.data = list(bytes(b'Im_A_C'))
+
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingScanResponseBuilder(
+ advertising_handle,
+ hci_packets.Operation.COMPLETE_ADVERTISEMENT,
+ hci_packets.FragmentPreference.CONTROLLER_SHOULD_NOT,
+ [gap_short_name]), True)
+
+ enabled_set = hci_packets.EnabledSet()
+ enabled_set.advertising_handle = advertising_handle
+ enabled_set.duration = 0
+ enabled_set.max_extended_advertising_events = 0
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedAdvertisingEnableBuilder(
+ hci_packets.Enable.ENABLED, [enabled_set]), True)
+
+ with EventCallbackStream(
+ self.device_under_test.hci_le_acl_manager.CreateConnection(
+ le_acl_manager_facade.LeConnectionMsg(
+ address_type=int(
+ hci_packets.AddressType.RANDOM_DEVICE_ADDRESS),
+ address=bytes('0C:05:04:03:02:01',
+ 'utf8')))) as connection_event_stream:
+
+ connection_event_asserts = EventAsserts(connection_event_stream)
+
+ # Cert gets ConnectionComplete with a handle and sends ACL data
+ handle = 0xfff
+
+ def get_handle(packet):
+ packet_bytes = packet.event
+ nonlocal handle
+ if b'\x3e\x13\x01\x00' in packet_bytes:
+ cc_view = hci_packets.LeConnectionCompleteView(
+ hci_packets.LeMetaEventView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ handle = cc_view.GetConnectionHandle()
+ return True
+ if b'\x3e\x13\x0A\x00' in packet_bytes:
+ cc_view = hci_packets.LeEnhancedConnectionCompleteView(
+ hci_packets.LeMetaEventView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ handle = cc_view.GetConnectionHandle()
+ return True
+ return False
+
+ cert_hci_le_event_asserts.assert_event_occurs(get_handle)
+ cert_handle = handle
+
+ # DUT gets a connection complete event
+ connection_event_asserts.assert_event_occurs(get_handle)
+
+ self.enqueue_acl_data(
+ cert_handle, hci_packets.PacketBoundaryFlag.
+ FIRST_AUTOMATICALLY_FLUSHABLE,
+ hci_packets.BroadcastFlag.POINT_TO_POINT,
+ bytes(b'\x06\x00\x07\x00Hello'))
+ self.enqueue_acl_data(
+ cert_handle,
+ hci_packets.PacketBoundaryFlag.CONTINUING_FRAGMENT,
+ hci_packets.BroadcastFlag.POINT_TO_POINT, bytes(b'!'))
+
+ acl_data_asserts.assert_event_occurs(
+ lambda packet: b'Hello!' in packet.payload)
diff --git a/gd/hci/cert/le_advertising_manager_test.py b/gd/hci/cert/le_advertising_manager_test.py
index aef3710d7..7d163bfac 100644
--- a/gd/hci/cert/le_advertising_manager_test.py
+++ b/gd/hci/cert/le_advertising_manager_test.py
@@ -18,70 +18,117 @@ import os
import sys
import logging
-from cert.gd_base_test import GdBaseTestClass
-from cert.event_stream import EventStream
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
+from cert.event_callback_stream import EventCallbackStream
+from cert.event_asserts import EventAsserts
from google.protobuf import empty_pb2 as empty_proto
from facade import rootservice_pb2 as facade_rootservice
-from hci.facade import hci_facade_pb2 as hci_facade
+from hci.facade import facade_pb2 as hci_facade
from hci.facade import \
le_advertising_manager_facade_pb2 as le_advertising_facade
from bluetooth_packets_python3 import hci_packets
from facade import common_pb2 as common
-from cert.py_hci import PyHci
-from cert.truth import assertThat
-class LeAdvertisingManagerTest(GdBaseTestClass):
-
- def setup_class(self):
- super().setup_class(dut_module='HCI_INTERFACES', cert_module='HCI')
+class LeAdvertisingManagerTest(GdFacadeOnlyBaseTestClass):
def setup_test(self):
- super().setup_test()
- self.cert_hci = PyHci(self.cert, acl_streaming=True)
+ self.device_under_test.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI_INTERFACES'),))
+ self.cert_device.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI'),))
+
+ self.device_under_test.wait_channel_ready()
+ self.cert_device.wait_channel_ready()
def teardown_test(self):
- self.cert_hci.close()
- super().teardown_test()
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+ self.cert_device.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+
+ def register_for_event(self, event_code):
+ msg = hci_facade.EventCodeMsg(code=int(event_code))
+ self.cert_device.hci.RegisterEventHandler(msg)
+
+ def register_for_le_event(self, event_code):
+ msg = hci_facade.LeSubeventCodeMsg(code=int(event_code))
+ self.cert_device.hci.RegisterLeEventHandler(msg)
+
+ def enqueue_hci_command(self, command, expect_complete):
+ cmd_bytes = bytes(command.Serialize())
+ cmd = hci_facade.CommandMsg(command=cmd_bytes)
+ if (expect_complete):
+ self.cert_device.hci.EnqueueCommandWithComplete(cmd)
+ else:
+ self.cert_device.hci.EnqueueCommandWithStatus(cmd)
def test_le_ad_scan_dut_advertises(self):
- self.cert_hci.register_for_le_events(hci_packets.SubeventCode.ADVERTISING_REPORT,
- hci_packets.SubeventCode.EXTENDED_ADVERTISING_REPORT)
-
- # CERT Scans
- self.cert_hci.send_command(hci_packets.LeSetRandomAddressBuilder('0C:05:04:03:02:01'))
- scan_parameters = hci_packets.PhyScanParameters()
- scan_parameters.le_scan_type = hci_packets.LeScanType.ACTIVE
- scan_parameters.le_scan_interval = 40
- scan_parameters.le_scan_window = 20
- self.cert_hci.send_command(
- hci_packets.LeSetExtendedScanParametersBuilder(hci_packets.OwnAddressType.RANDOM_DEVICE_ADDRESS,
- hci_packets.LeScanningFilterPolicy.ACCEPT_ALL, 1,
- [scan_parameters]))
- self.cert_hci.send_command(
- hci_packets.LeSetExtendedScanEnableBuilder(hci_packets.Enable.ENABLED,
- hci_packets.FilterDuplicates.DISABLED, 0, 0))
-
- # DUT Advertises
- gap_name = hci_packets.GapData()
- gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(b'Im_The_DUT'))
- gap_data = le_advertising_facade.GapDataMsg(data=bytes(gap_name.Serialize()))
- config = le_advertising_facade.AdvertisingConfig(
- advertisement=[gap_data],
- interval_min=512,
- interval_max=768,
- advertising_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
- own_address_type=common.USE_RANDOM_DEVICE_ADDRESS,
- channel_map=7,
- filter_policy=le_advertising_facade.AdvertisingFilterPolicy.ALL_DEVICES)
- request = le_advertising_facade.CreateAdvertiserRequest(config=config)
-
- create_response = self.dut.hci_le_advertising_manager.CreateAdvertiser(request)
-
- assertThat(self.cert_hci.get_le_event_stream()).emits(lambda packet: b'Im_The_DUT' in packet.payload)
-
- remove_request = le_advertising_facade.RemoveAdvertiserRequest(advertiser_id=create_response.advertiser_id)
- self.dut.hci_le_advertising_manager.RemoveAdvertiser(remove_request)
- self.cert_hci.send_command(
- hci_packets.LeSetScanEnableBuilder(hci_packets.Enable.DISABLED, hci_packets.Enable.DISABLED))
+ self.register_for_le_event(hci_packets.SubeventCode.ADVERTISING_REPORT)
+ self.register_for_le_event(
+ hci_packets.SubeventCode.EXTENDED_ADVERTISING_REPORT)
+ with EventCallbackStream(
+ self.cert_device.hci.FetchLeSubevents(
+ empty_proto.Empty())) as hci_le_event_stream:
+
+ hci_event_asserts = EventAsserts(hci_le_event_stream)
+
+ # CERT Scans
+ self.enqueue_hci_command(
+ hci_packets.LeSetRandomAddressBuilder('0C:05:04:03:02:01'),
+ True)
+ scan_parameters = hci_packets.PhyScanParameters()
+ scan_parameters.le_scan_type = hci_packets.LeScanType.ACTIVE
+ scan_parameters.le_scan_interval = 40
+ scan_parameters.le_scan_window = 20
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedScanParametersBuilder(
+ hci_packets.AddressType.RANDOM_DEVICE_ADDRESS,
+ hci_packets.LeSetScanningFilterPolicy.ACCEPT_ALL, 1,
+ [scan_parameters]), True)
+ self.enqueue_hci_command(
+ hci_packets.LeSetExtendedScanEnableBuilder(
+ hci_packets.Enable.ENABLED,
+ hci_packets.FilterDuplicates.DISABLED, 0, 0), True)
+
+ # DUT Advertises
+ gap_name = hci_packets.GapData()
+ gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
+ gap_name.data = list(bytes(b'Im_The_DUT!'))
+ gap_data = le_advertising_facade.GapDataMsg(
+ data=bytes(gap_name.Serialize()))
+ config = le_advertising_facade.AdvertisingConfig(
+ advertisement=[gap_data],
+ random_address=common.BluetoothAddress(
+ address=bytes(b'0D:05:04:03:02:01')),
+ interval_min=512,
+ interval_max=768,
+ event_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
+ address_type=common.RANDOM_DEVICE_ADDRESS,
+ peer_address_type=common.PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
+ peer_address=common.BluetoothAddress(
+ address=bytes(b'A6:A5:A4:A3:A2:A1')),
+ channel_map=7,
+ filter_policy=le_advertising_facade.AdvertisingFilterPolicy.
+ ALL_DEVICES)
+ request = le_advertising_facade.CreateAdvertiserRequest(
+ config=config)
+
+ create_response = self.device_under_test.hci_le_advertising_manager.CreateAdvertiser(
+ request)
+
+ hci_event_asserts.assert_event_occurs(
+ lambda packet: b'Im_The_DUT' in packet.event)
+
+ remove_request = le_advertising_facade.RemoveAdvertiserRequest(
+ advertiser_id=create_response.advertiser_id)
+ self.device_under_test.hci_le_advertising_manager.RemoveAdvertiser(
+ remove_request)
+ self.enqueue_hci_command(
+ hci_packets.LeSetScanEnableBuilder(hci_packets.Enable.DISABLED,
+ hci_packets.Enable.DISABLED),
+ True)
diff --git a/gd/hci/cert/le_scanning_manager_test.py b/gd/hci/cert/le_scanning_manager_test.py
index b91118eea..5946a22a6 100644
--- a/gd/hci/cert/le_scanning_manager_test.py
+++ b/gd/hci/cert/le_scanning_manager_test.py
@@ -18,80 +18,93 @@ import os
import sys
import logging
-from cert.gd_base_test import GdBaseTestClass
-from cert.event_stream import EventStream
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
+from cert.event_callback_stream import EventCallbackStream
+from cert.event_asserts import EventAsserts
from google.protobuf import empty_pb2 as empty_proto
from facade import rootservice_pb2 as facade_rootservice
-from hci.facade import hci_facade_pb2 as hci_facade
+from hci.facade import facade_pb2 as hci_facade
from hci.facade import le_scanning_manager_facade_pb2 as le_scanning_facade
from hci.facade import le_advertising_manager_facade_pb2 as le_advertising_facade
-from hci.facade import le_initiator_address_facade_pb2 as le_initiator_address_facade
from bluetooth_packets_python3 import hci_packets
from facade import common_pb2 as common
-class LeScanningManagerTest(GdBaseTestClass):
+class LeScanningManagerTest(GdFacadeOnlyBaseTestClass):
- def setup_class(self):
- super().setup_class(dut_module='HCI_INTERFACES', cert_module='HCI_INTERFACES')
+ def setup_test(self):
+ self.device_under_test.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI_INTERFACES'),))
+ self.cert_device.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI_INTERFACES'),))
+
+ self.device_under_test.wait_channel_ready()
+ self.cert_device.wait_channel_ready()
+
+ def teardown_test(self):
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+ self.cert_device.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
def register_for_event(self, event_code):
msg = hci_facade.EventCodeMsg(code=int(event_code))
- self.cert.hci.RegisterEventHandler(msg)
+ self.cert_device.hci.RegisterEventHandler(msg)
def register_for_le_event(self, event_code):
msg = hci_facade.LeSubeventCodeMsg(code=int(event_code))
- self.cert.hci.RegisterLeEventHandler(msg)
+ self.cert_device.hci.RegisterLeEventHandler(msg)
def enqueue_hci_command(self, command, expect_complete):
cmd_bytes = bytes(command.Serialize())
- cmd = common.Data(payload=cmd_bytes)
+ cmd = hci_facade.CommandMsg(command=cmd_bytes)
if (expect_complete):
- self.cert.hci.EnqueueCommandWithComplete(cmd)
+ self.cert_device.hci.EnqueueCommandWithComplete(cmd)
else:
- self.cert.hci.EnqueueCommandWithStatus(cmd)
+ self.cert_device.hci.EnqueueCommandWithStatus(cmd)
def test_le_ad_scan_dut_scans(self):
- privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_STATIC_ADDRESS,
- address_with_type=common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes(b'D0:05:04:03:02:01')),
- type=common.RANDOM_DEVICE_ADDRESS),
- rotation_irk=b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00',
- minimum_rotation_time=0,
- maximum_rotation_time=0)
- self.dut.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(privacy_policy)
- cert_privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_STATIC_ADDRESS,
- address_with_type=common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes(b'C0:05:04:03:02:01')),
- type=common.RANDOM_DEVICE_ADDRESS),
- rotation_irk=b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00',
- minimum_rotation_time=0,
- maximum_rotation_time=0)
- self.cert.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(cert_privacy_policy)
- with EventStream(
+ with EventCallbackStream(
# DUT Scans
- self.dut.hci_le_scanning_manager.StartScan(empty_proto.Empty())) as advertising_event_stream:
+ self.device_under_test.hci_le_scanning_manager.StartScan(
+ empty_proto.Empty())) as advertising_event_stream:
+
+ hci_event_asserts = EventAsserts(advertising_event_stream)
# CERT Advertises
gap_name = hci_packets.GapData()
gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
gap_name.data = list(bytes(b'Im_The_CERT!'))
- gap_data = le_advertising_facade.GapDataMsg(data=bytes(gap_name.Serialize()))
+ gap_data = le_advertising_facade.GapDataMsg(
+ data=bytes(gap_name.Serialize()))
config = le_advertising_facade.AdvertisingConfig(
advertisement=[gap_data],
+ random_address=common.BluetoothAddress(
+ address=bytes(b'A6:A5:A4:A3:A2:A1')),
interval_min=512,
interval_max=768,
- advertising_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
- own_address_type=common.USE_RANDOM_DEVICE_ADDRESS,
+ event_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
+ address_type=common.RANDOM_DEVICE_ADDRESS,
+ peer_address_type=common.PUBLIC_DEVICE_OR_IDENTITY_ADDRESS,
+ peer_address=common.BluetoothAddress(
+ address=bytes(b'0C:05:04:03:02:01')),
channel_map=7,
- filter_policy=le_advertising_facade.AdvertisingFilterPolicy.ALL_DEVICES)
- request = le_advertising_facade.CreateAdvertiserRequest(config=config)
+ filter_policy=le_advertising_facade.AdvertisingFilterPolicy.
+ ALL_DEVICES)
+ request = le_advertising_facade.CreateAdvertiserRequest(
+ config=config)
- create_response = self.cert.hci_le_advertising_manager.CreateAdvertiser(request)
+ create_response = self.cert_device.hci_le_advertising_manager.CreateAdvertiser(
+ request)
- advertising_event_stream.assert_event_occurs(lambda packet: b'Im_The_CERT' in packet.event)
+ hci_event_asserts.assert_event_occurs(
+ lambda packet: b'Im_The_CERT' in packet.event)
- remove_request = le_advertising_facade.RemoveAdvertiserRequest(advertiser_id=create_response.advertiser_id)
- self.cert.hci_le_advertising_manager.RemoveAdvertiser(remove_request)
+ remove_request = le_advertising_facade.RemoveAdvertiserRequest(
+ advertiser_id=create_response.advertiser_id)
+ self.cert_device.hci_le_advertising_manager.RemoveAdvertiser(
+ remove_request)
diff --git a/gd/hci/cert/le_scanning_with_security_test.py b/gd/hci/cert/le_scanning_with_security_test.py
deleted file mode 100644
index e4813571c..000000000
--- a/gd/hci/cert/le_scanning_with_security_test.py
+++ /dev/null
@@ -1,86 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2019 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from cert.gd_base_test import GdBaseTestClass
-from cert.event_stream import EventStream
-from cert.truth import assertThat
-from google.protobuf import empty_pb2 as empty_proto
-from hci.facade import hci_facade_pb2 as hci_facade
-from hci.facade import le_advertising_manager_facade_pb2 as le_advertising_facade
-from hci.facade import le_initiator_address_facade_pb2 as le_initiator_address_facade
-from bluetooth_packets_python3 import hci_packets
-from facade import common_pb2 as common
-
-
-class LeScanningWithSecurityTest(GdBaseTestClass):
-
- def setup_class(self):
- super().setup_class(dut_module='SECURITY', cert_module='HCI_INTERFACES')
-
- def register_for_event(self, event_code):
- msg = hci_facade.EventCodeMsg(code=int(event_code))
- self.cert.hci.RegisterEventHandler(msg)
-
- def register_for_le_event(self, event_code):
- msg = hci_facade.LeSubeventCodeMsg(code=int(event_code))
- self.cert.hci.RegisterLeEventHandler(msg)
-
- def enqueue_hci_command(self, command, expect_complete):
- cmd_bytes = bytes(command.Serialize())
- cmd = common.Data(command=cmd_bytes)
- if (expect_complete):
- self.cert.hci.EnqueueCommandWithComplete(cmd)
- else:
- self.cert.hci.EnqueueCommandWithStatus(cmd)
-
- def test_le_ad_scan_dut_scans(self):
- """
- Verify that the IUT address policy is correctly initiated by SecurityManager, and we can start a scan.
- """
- cert_privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_STATIC_ADDRESS,
- address_with_type=common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes(b'C0:05:04:03:02:01')),
- type=common.RANDOM_DEVICE_ADDRESS),
- rotation_irk=b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00',
- minimum_rotation_time=0,
- maximum_rotation_time=0)
- self.cert.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(cert_privacy_policy)
- with EventStream(
- # DUT Scans
- self.dut.hci_le_scanning_manager.StartScan(empty_proto.Empty())) as advertising_event_stream:
-
- # CERT Advertises
- gap_name = hci_packets.GapData()
- gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(b'Im_The_CERT!'))
- gap_data = le_advertising_facade.GapDataMsg(data=bytes(gap_name.Serialize()))
- config = le_advertising_facade.AdvertisingConfig(
- advertisement=[gap_data],
- interval_min=512,
- interval_max=768,
- advertising_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
- own_address_type=common.USE_RANDOM_DEVICE_ADDRESS,
- channel_map=7,
- filter_policy=le_advertising_facade.AdvertisingFilterPolicy.ALL_DEVICES)
- request = le_advertising_facade.CreateAdvertiserRequest(config=config)
-
- create_response = self.cert.hci_le_advertising_manager.CreateAdvertiser(request)
-
- assertThat(advertising_event_stream).emits(lambda packet: b'Im_The_CERT' in packet.event)
-
- remove_request = le_advertising_facade.RemoveAdvertiserRequest(advertiser_id=create_response.advertiser_id)
- self.cert.hci_le_advertising_manager.RemoveAdvertiser(remove_request)
diff --git a/gd/hci/class_of_device.cc b/gd/hci/class_of_device.cc
index 316361310..36dd2923f 100644
--- a/gd/hci/class_of_device.cc
+++ b/gd/hci/class_of_device.cc
@@ -16,26 +16,22 @@
*
******************************************************************************/
-#include "hci/class_of_device.h"
+#include "class_of_device.h"
+#include <stdint.h>
#include <algorithm>
-#include <cstdint>
-#include <cstdio>
-#include <cstdlib>
#include <sstream>
#include <vector>
-#include "common/numbers.h"
-#include "common/strings.h"
#include "os/log.h"
namespace bluetooth {
namespace hci {
-// ClassOfDevice cannot initialize member variables as it is a POD type
-// NOLINTNEXTLINE(cppcoreguidelines-pro-type-member-init)
+static_assert(sizeof(ClassOfDevice) == ClassOfDevice::kLength, "ClassOfDevice must be 3 bytes long!");
+
ClassOfDevice::ClassOfDevice(const uint8_t (&class_of_device)[kLength]) {
- std::copy(class_of_device, class_of_device + kLength, cod.data());
+ std::copy(class_of_device, class_of_device + kLength, cod);
};
std::string ClassOfDevice::ToString() const {
@@ -46,94 +42,56 @@ std::string ClassOfDevice::ToString() const {
return str;
}
-std::string ClassOfDevice::ToLegacyConfigString() const {
- return std::to_string(ToUint32Legacy());
-}
-
-std::optional<ClassOfDevice> ClassOfDevice::FromString(const std::string& str) {
- if (str.length() != 8) {
- return std::nullopt;
- }
+bool ClassOfDevice::FromString(const std::string& from, ClassOfDevice& to) {
+ ClassOfDevice new_cod;
+ if (from.length() != 8) return false;
- std::istringstream stream(str);
+ std::istringstream stream(from);
std::string token;
int index = 0;
uint16_t values[3];
- ClassOfDevice new_cod{};
while (getline(stream, token, '-')) {
if (index >= 3) {
- return std::nullopt;
+ return false;
}
if (index == 0 && token.length() != 3) {
- return std::nullopt;
+ return false;
} else if (index == 1 && token.length() != 1) {
- return std::nullopt;
+ return false;
} else if (index == 2 && token.length() != 2) {
- return std::nullopt;
+ return false;
}
char* temp = nullptr;
- values[index] = std::strtol(token.c_str(), &temp, 16);
+ values[index] = strtol(token.c_str(), &temp, 16);
if (*temp != '\0') {
- return std::nullopt;
+ return false;
}
index++;
}
if (index != 3) {
- return std::nullopt;
+ return false;
}
new_cod.cod[0] = values[2];
new_cod.cod[1] = values[1] | ((values[0] & 0xf) << 4);
new_cod.cod[2] = values[0] >> 4;
- return new_cod;
-}
-
-bool ClassOfDevice::FromString(const std::string& from, ClassOfDevice& to) {
- auto new_cod = FromString(from);
- if (!new_cod) {
- to = {};
- return false;
- }
- to = std::move(*new_cod);
+ to = new_cod;
return true;
}
-std::optional<ClassOfDevice> ClassOfDevice::FromUint32Legacy(uint32_t cod_int) {
- if (cod_int != 0 && (cod_int >> 24) != 0) {
- return std::nullopt;
- }
- ClassOfDevice result = {};
- result.cod[2] = static_cast<uint8_t>(cod_int);
- result.cod[1] = static_cast<uint8_t>(cod_int >> 8);
- result.cod[0] = static_cast<uint8_t>(cod_int >> 16);
- return result;
-}
-
-std::optional<ClassOfDevice> ClassOfDevice::FromLegacyConfigString(const std::string& str) {
- char* ptr = nullptr;
- auto num = std::strtoull(str.data(), &ptr, 10);
- if (num > 0xffffff) {
- return std::nullopt;
- }
- return FromUint32Legacy(static_cast<uint32_t>(num));
-}
-
-uint32_t ClassOfDevice::ToUint32Legacy() const {
- return (cod[2]) | (cod[1] << 8) | (cod[0] << 16);
-}
-
size_t ClassOfDevice::FromOctets(const uint8_t* from) {
- std::copy(from, from + kLength, data());
+ std::copy(from, from + kLength, cod);
return kLength;
};
bool ClassOfDevice::IsValid(const std::string& cod) {
- return ClassOfDevice::FromString(cod).has_value();
+ ClassOfDevice tmp;
+ return ClassOfDevice::FromString(cod, tmp);
}
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/class_of_device.h b/gd/hci/class_of_device.h
index 245908a87..b44a45e03 100644
--- a/gd/hci/class_of_device.h
+++ b/gd/hci/class_of_device.h
@@ -18,71 +18,35 @@
#pragma once
-#include <array>
-#include <optional>
#include <string>
-#include "packet/custom_field_fixed_size_interface.h"
-#include "storage/serializable.h"
-
namespace bluetooth {
namespace hci {
-class ClassOfDevice final : public packet::CustomFieldFixedSizeInterface<ClassOfDevice>,
- public storage::Serializable<ClassOfDevice> {
+class ClassOfDevice final {
public:
- static constexpr size_t kLength = 3;
+ static constexpr unsigned int kLength = 3;
- std::array<uint8_t, kLength> cod = {};
+ uint8_t cod[kLength];
ClassOfDevice() = default;
ClassOfDevice(const uint8_t (&class_of_device)[kLength]);
- // packet::CustomFieldFixedSizeInterface methods
- inline uint8_t* data() override {
- return cod.data();
- }
- inline const uint8_t* data() const override {
- return cod.data();
- }
-
- // storage::Serializable methods
- std::string ToString() const;
- static std::optional<ClassOfDevice> FromString(const std::string& str);
- std::string ToLegacyConfigString() const override;
- static std::optional<ClassOfDevice> FromLegacyConfigString(const std::string& str);
-
- bool operator<(const ClassOfDevice& rhs) const {
- return cod < rhs.cod;
- }
bool operator==(const ClassOfDevice& rhs) const {
- return cod == rhs.cod;
- }
- bool operator>(const ClassOfDevice& rhs) const {
- return (rhs < *this);
- }
- bool operator<=(const ClassOfDevice& rhs) const {
- return !(*this > rhs);
- }
- bool operator>=(const ClassOfDevice& rhs) const {
- return !(*this < rhs);
+ return (std::memcmp(cod, rhs.cod, sizeof(cod)) == 0);
}
+
bool operator!=(const ClassOfDevice& rhs) const {
- return !(*this == rhs);
+ return std::memcmp(cod, rhs.cod, sizeof(cod)) != 0;
}
+ std::string ToString() const;
+
// Converts |string| to ClassOfDevice and places it in |to|. If |from| does
// not represent a Class of Device, |to| is not modified and this function
// returns false. Otherwise, it returns true.
static bool FromString(const std::string& from, ClassOfDevice& to);
- // Converts uint32_t encoded class of device to ClassOfDevice object
- // uint32_t encoding:
- // <high> uint8_t(cod[0]) | uint8_t(cod[1]) | uint8_t(cod[2]) <low>
- // Only used in legacy stack device config
- static std::optional<ClassOfDevice> FromUint32Legacy(uint32_t cod_int);
- uint32_t ToUint32Legacy() const;
-
// Copies |from| raw Class of Device octets to the local object.
// Returns the number of copied octets (always ClassOfDevice::kLength)
size_t FromOctets(const uint8_t* from);
diff --git a/gd/hci/class_of_device_unittest.cc b/gd/hci/class_of_device_unittest.cc
index eb0ced265..85472dd31 100644
--- a/gd/hci/class_of_device_unittest.cc
+++ b/gd/hci/class_of_device_unittest.cc
@@ -16,7 +16,6 @@
*
******************************************************************************/
-#include <gmock/gmock.h>
#include <gtest/gtest.h>
#include "hci/class_of_device.h"
@@ -77,37 +76,23 @@ TEST(ClassOfDeviceTest, test_copy) {
}
TEST(ClassOfDeviceTest, IsValid) {
- ASSERT_FALSE(ClassOfDevice::IsValid(""));
- ASSERT_FALSE(ClassOfDevice::IsValid("000000"));
- ASSERT_FALSE(ClassOfDevice::IsValid("00-00-00"));
- ASSERT_FALSE(ClassOfDevice::IsValid("000-0-0"));
- ASSERT_TRUE(ClassOfDevice::IsValid("000-0-00"));
- ASSERT_TRUE(ClassOfDevice::IsValid("ABc-d-00"));
- ASSERT_TRUE(ClassOfDevice::IsValid("aBc-D-eF"));
+ EXPECT_FALSE(ClassOfDevice::IsValid(""));
+ EXPECT_FALSE(ClassOfDevice::IsValid("000000"));
+ EXPECT_FALSE(ClassOfDevice::IsValid("00-00-00"));
+ EXPECT_FALSE(ClassOfDevice::IsValid("000-0-0"));
+ EXPECT_TRUE(ClassOfDevice::IsValid("000-0-00"));
+ EXPECT_TRUE(ClassOfDevice::IsValid("ABc-d-00"));
+ EXPECT_TRUE(ClassOfDevice::IsValid("aBc-D-eF"));
}
TEST(ClassOfDeviceTest, classOfDeviceFromString) {
ClassOfDevice cod;
- ASSERT_TRUE(ClassOfDevice::FromString("000-0-00", cod));
+ EXPECT_TRUE(ClassOfDevice::FromString("000-0-00", cod));
const ClassOfDevice result0 = {{0x00, 0x00, 0x00}};
- ASSERT_EQ(0, memcmp(cod.data(), result0.data(), ClassOfDevice::kLength));
+ EXPECT_EQ(0, memcmp(&cod, &result0, sizeof(cod)));
- ASSERT_TRUE(ClassOfDevice::FromString("ab2-1-4C", cod));
+ EXPECT_TRUE(ClassOfDevice::FromString("ab2-1-4C", cod));
const ClassOfDevice result1 = {{0x4c, 0x21, 0xab}};
- ASSERT_EQ(0, memcmp(cod.data(), result1.data(), ClassOfDevice::kLength));
-}
-
-TEST(ClassOfDeviceTest, classOfDeviceFromUint32Legacy) {
- auto cod = ClassOfDevice::FromUint32Legacy(0);
- ASSERT_TRUE(cod);
- ASSERT_THAT(cod->cod, testing::ElementsAre(0x00, 0x00, 0x00));
- ASSERT_EQ(cod->ToUint32Legacy(), 0);
-
- cod = ClassOfDevice::FromUint32Legacy(0xab214c);
- ASSERT_TRUE(cod);
- ASSERT_THAT(cod->cod, testing::ElementsAre(0xab, 0x21, 0x4c));
- ASSERT_EQ(cod->ToUint32Legacy(), 0xab214c);
-
- ASSERT_FALSE(ClassOfDevice::FromUint32Legacy(0x1ab214c));
+ EXPECT_EQ(0, memcmp(&cod, &result1, sizeof(cod)));
}
diff --git a/stack/test/common/mock_btif_storage.h b/gd/hci/classic_device.h
index 19a2de213..53ff0ba2f 100644
--- a/stack/test/common/mock_btif_storage.h
+++ b/gd/hci/classic_device.h
@@ -1,6 +1,6 @@
/******************************************************************************
*
- * Copyright 2020 The Android Open Source Project
+ * Copyright 2019 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -17,30 +17,19 @@
******************************************************************************/
#pragma once
-#include <gmock/gmock.h>
+#include "hci/device.h"
-namespace bluetooth {
-namespace manager {
-
-class BtifStorageInterface {
- public:
- virtual void LoadBondedEatt(void) = 0;
- virtual ~BtifStorageInterface() = default;
-};
-
-class MockBtifStorageInterface : public BtifStorageInterface {
- public:
- MOCK_METHOD0(LoadBondedEatt, void(void));
-};
+namespace bluetooth::hci {
/**
- * Set the {@link MockBifStorageInterface} for testing
+ * A device representing a CLASSIC device.
*
- * @param mock_btif_storage_interface pointer to mock btm security
- * internal interface, could be null
+ * <p>This can be a CLASSIC only or a piece of a DUAL MODE device.
*/
-void SetMockBtifStorageInterface(
- MockBtifStorageInterface* mock_btif_storage_interface);
+class ClassicDevice : public Device {
+ protected:
+ friend class DeviceDatabase;
+ explicit ClassicDevice(Address address) : Device(address, DeviceType::CLASSIC) {}
+};
-} // namespace manager
-} // namespace bluetooth \ No newline at end of file
+} // namespace bluetooth::hci
diff --git a/gd/hci/command_interface.h b/gd/hci/command_interface.h
deleted file mode 100644
index eba01dbe0..000000000
--- a/gd/hci/command_interface.h
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "common/contextual_callback.h"
-#include "hci/hci_packets.h"
-#include "os/handler.h"
-#include "os/utils.h"
-
-namespace bluetooth {
-namespace hci {
-
-template <typename T>
-class CommandInterface {
- public:
- CommandInterface() = default;
- virtual ~CommandInterface() = default;
- DISALLOW_COPY_AND_ASSIGN(CommandInterface);
-
- virtual void EnqueueCommand(std::unique_ptr<T> command,
- common::ContextualOnceCallback<void(CommandCompleteView)> on_complete) = 0;
-
- virtual void EnqueueCommand(std::unique_ptr<T> command,
- common::ContextualOnceCallback<void(CommandStatusView)> on_status) = 0;
-};
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/controller.cc b/gd/hci/controller.cc
index 700c348d3..abb0b5b47 100644
--- a/gd/hci/controller.cc
+++ b/gd/hci/controller.cc
@@ -18,15 +18,21 @@
#include <future>
#include <memory>
-#include <string>
#include <utility>
-#include "common/init_flags.h"
+#include "common/bind.h"
+#include "common/callback.h"
#include "hci/hci_layer.h"
namespace bluetooth {
namespace hci {
+using common::Bind;
+using common::BindOnce;
+using common::Callback;
+using common::Closure;
+using common::OnceCallback;
+using common::OnceClosure;
using os::Handler;
struct Controller::impl {
@@ -34,169 +40,106 @@ struct Controller::impl {
void Start(hci::HciLayer* hci) {
hci_ = hci;
- Handler* handler = module_.GetHandler();
- if (common::init_flags::gd_acl_is_enabled() || common::init_flags::gd_l2cap_is_enabled()) {
- hci_->RegisterEventHandler(
- EventCode::NUMBER_OF_COMPLETED_PACKETS, handler->BindOn(this, &Controller::impl::NumberOfCompletedPackets));
- }
+ hci_->RegisterEventHandler(EventCode::NUMBER_OF_COMPLETED_PACKETS,
+ Bind(&Controller::impl::NumberOfCompletedPackets, common::Unretained(this)),
+ module_.GetHandler());
- le_set_event_mask(kDefaultLeEventMask);
set_event_mask(kDefaultEventMask);
- write_le_host_support(Enable::ENABLED);
- // SSP is managed by security layer once enabled
- if (!common::init_flags::gd_security_is_enabled()) {
- write_simple_pairing_mode(Enable::ENABLED);
- hci_->EnqueueCommand(
- WriteSecureConnectionsHostSupportBuilder::Create(Enable::ENABLED),
- handler->BindOnceOn(this, &Controller::impl::write_secure_connections_host_support_complete_handler));
- }
hci_->EnqueueCommand(ReadLocalNameBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::read_local_name_complete_handler));
- hci_->EnqueueCommand(ReadLocalVersionInformationBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::read_local_version_information_complete_handler));
- hci_->EnqueueCommand(ReadLocalSupportedCommandsBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::read_local_supported_commands_complete_handler));
+ BindOnce(&Controller::impl::read_local_name_complete_handler, common::Unretained(this)),
+ module_.GetHandler());
+ hci_->EnqueueCommand(
+ ReadLocalVersionInformationBuilder::Create(),
+ BindOnce(&Controller::impl::read_local_version_information_complete_handler, common::Unretained(this)),
+ module_.GetHandler());
+ hci_->EnqueueCommand(
+ ReadLocalSupportedCommandsBuilder::Create(),
+ BindOnce(&Controller::impl::read_local_supported_commands_complete_handler, common::Unretained(this)),
+ module_.GetHandler());
+ hci_->EnqueueCommand(
+ ReadLocalSupportedFeaturesBuilder::Create(),
+ BindOnce(&Controller::impl::read_local_supported_features_complete_handler, common::Unretained(this)),
+ module_.GetHandler());
// Wait for all extended features read
std::promise<void> features_promise;
auto features_future = features_promise.get_future();
hci_->EnqueueCommand(ReadLocalExtendedFeaturesBuilder::Create(0x00),
- handler->BindOnceOn(this, &Controller::impl::read_local_extended_features_complete_handler,
- std::move(features_promise)));
+ BindOnce(&Controller::impl::read_local_extended_features_complete_handler,
+ common::Unretained(this), std::move(features_promise)),
+ module_.GetHandler());
features_future.wait();
hci_->EnqueueCommand(ReadBufferSizeBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::read_buffer_size_complete_handler));
+ BindOnce(&Controller::impl::read_buffer_size_complete_handler, common::Unretained(this)),
+ module_.GetHandler());
- if (is_supported(OpCode::LE_READ_BUFFER_SIZE_V2)) {
- hci_->EnqueueCommand(
- LeReadBufferSizeV2Builder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_read_buffer_size_v2_handler));
- } else {
- hci_->EnqueueCommand(
- LeReadBufferSizeV1Builder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_read_buffer_size_handler));
- }
-
- hci_->EnqueueCommand(LeReadLocalSupportedFeaturesBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_read_local_supported_features_handler));
-
- hci_->EnqueueCommand(LeReadSupportedStatesBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_read_supported_states_handler));
+ hci_->EnqueueCommand(LeReadBufferSizeBuilder::Create(),
+ BindOnce(&Controller::impl::le_read_buffer_size_handler, common::Unretained(this)),
+ module_.GetHandler());
hci_->EnqueueCommand(
- LeReadConnectListSizeBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_read_connect_list_size_handler));
+ LeReadLocalSupportedFeaturesBuilder::Create(),
+ BindOnce(&Controller::impl::le_read_local_supported_features_handler, common::Unretained(this)),
+ module_.GetHandler());
- hci_->EnqueueCommand(
- LeReadResolvingListSizeBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_read_resolving_list_size_handler));
+ hci_->EnqueueCommand(LeReadSupportedStatesBuilder::Create(),
+ BindOnce(&Controller::impl::le_read_supported_states_handler, common::Unretained(this)),
+ module_.GetHandler());
if (is_supported(OpCode::LE_READ_MAXIMUM_DATA_LENGTH)) {
hci_->EnqueueCommand(LeReadMaximumDataLengthBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_read_maximum_data_length_handler));
- } else {
- le_maximum_data_length_.supported_max_rx_octets_ = 0;
- le_maximum_data_length_.supported_max_rx_time_ = 0;
- le_maximum_data_length_.supported_max_tx_octets_ = 0;
- le_maximum_data_length_.supported_max_tx_time_ = 0;
- }
- if (is_supported(OpCode::LE_READ_SUGGESTED_DEFAULT_DATA_LENGTH)) {
- hci_->EnqueueCommand(
- LeReadSuggestedDefaultDataLengthBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_read_suggested_default_data_length_handler));
+ BindOnce(&Controller::impl::le_read_maximum_data_length_handler, common::Unretained(this)),
+ module_.GetHandler());
}
if (is_supported(OpCode::LE_READ_MAXIMUM_ADVERTISING_DATA_LENGTH)) {
hci_->EnqueueCommand(
LeReadMaximumAdvertisingDataLengthBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_read_maximum_advertising_data_length_handler));
- } else {
- le_maximum_advertising_data_length_ = 31;
+ BindOnce(&Controller::impl::le_read_maximum_advertising_data_length_handler, common::Unretained(this)),
+ module_.GetHandler());
}
if (is_supported(OpCode::LE_READ_NUMBER_OF_SUPPORTED_ADVERTISING_SETS)) {
hci_->EnqueueCommand(
LeReadNumberOfSupportedAdvertisingSetsBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_read_number_of_supported_advertising_sets_handler));
- } else {
- le_number_supported_advertising_sets_ = 1;
- }
- if (is_supported(OpCode::LE_READ_PERIODIC_ADVERTISING_LIST_SIZE)) {
- hci_->EnqueueCommand(
- LeReadPeriodicAdvertiserListSizeBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_read_periodic_advertiser_list_size_handler));
+ BindOnce(&Controller::impl::le_read_number_of_supported_advertising_sets_handler, common::Unretained(this)),
+ module_.GetHandler());
}
hci_->EnqueueCommand(LeGetVendorCapabilitiesBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::le_get_vendor_capabilities_handler));
+ BindOnce(&Controller::impl::le_get_vendor_capabilities_handler, common::Unretained(this)),
+ module_.GetHandler());
// We only need to synchronize the last read. Make BD_ADDR to be the last one.
std::promise<void> promise;
auto future = promise.get_future();
hci_->EnqueueCommand(
ReadBdAddrBuilder::Create(),
- handler->BindOnceOn(this, &Controller::impl::read_controller_mac_address_handler, std::move(promise)));
+ BindOnce(&Controller::impl::read_controller_mac_address_handler, common::Unretained(this), std::move(promise)),
+ module_.GetHandler());
future.wait();
}
void Stop() {
- if (bluetooth::common::init_flags::gd_core_is_enabled()) {
- hci_->UnregisterEventHandler(EventCode::NUMBER_OF_COMPLETED_PACKETS);
- }
+ hci_->UnregisterEventHandler(EventCode::NUMBER_OF_COMPLETED_PACKETS);
hci_ = nullptr;
}
- void NumberOfCompletedPackets(EventView event) {
- if (acl_credits_callback_.IsEmpty()) {
- LOG_WARN("Received event when AclManager is not listening");
- return;
- }
+ void NumberOfCompletedPackets(EventPacketView event) {
+ ASSERT(acl_credits_handler_ != nullptr);
auto complete_view = NumberOfCompletedPacketsView::Create(event);
ASSERT(complete_view.IsValid());
for (auto completed_packets : complete_view.GetCompletedPackets()) {
uint16_t handle = completed_packets.connection_handle_;
uint16_t credits = completed_packets.host_num_of_completed_packets_;
- acl_credits_callback_.Invoke(handle, credits);
- if (!acl_monitor_credits_callback_.IsEmpty()) {
- acl_monitor_credits_callback_.Invoke(handle, credits);
- }
+ acl_credits_handler_->Post(Bind(acl_credits_callback_, handle, credits));
}
}
- void register_completed_acl_packets_callback(CompletedAclPacketsCallback callback) {
- ASSERT(acl_credits_callback_.IsEmpty());
- acl_credits_callback_ = callback;
- }
-
- void unregister_completed_acl_packets_callback() {
- ASSERT(!acl_credits_callback_.IsEmpty());
- acl_credits_callback_ = {};
- }
-
- void register_completed_monitor_acl_packets_callback(CompletedAclPacketsCallback callback) {
- ASSERT(acl_monitor_credits_callback_.IsEmpty());
- acl_monitor_credits_callback_ = callback;
- }
-
- void unregister_completed_monitor_acl_packets_callback() {
- ASSERT(!acl_monitor_credits_callback_.IsEmpty());
- acl_monitor_credits_callback_ = {};
- }
-
- void register_monitor_completed_acl_packets_callback(CompletedAclPacketsCallback callback) {
- ASSERT(acl_monitor_credits_callback_.IsEmpty());
- acl_monitor_credits_callback_ = callback;
- }
-
- void unregister_monitor_completed_acl_packets_callback() {
- ASSERT(!acl_monitor_credits_callback_.IsEmpty());
- acl_monitor_credits_callback_ = {};
- }
-
- void write_secure_connections_host_support_complete_handler(CommandCompleteView view) {
- auto complete_view = WriteSecureConnectionsHostSupportCompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- ErrorCode status = complete_view.GetStatus();
- ASSERT_LOG(status == ErrorCode::SUCCESS, "Status 0x%02hhx, %s", status, ErrorCodeText(status).c_str());
+ void RegisterCompletedAclPacketsCallback(Callback<void(uint16_t /* handle */, uint16_t /* packets */)> cb,
+ Handler* handler) {
+ ASSERT(acl_credits_handler_ == nullptr);
+ acl_credits_callback_ = cb;
+ acl_credits_handler_ = handler;
}
void read_local_name_complete_handler(CommandCompleteView view) {
@@ -228,6 +171,14 @@ struct Controller::impl {
local_supported_commands_ = complete_view.GetSupportedCommands();
}
+ void read_local_supported_features_complete_handler(CommandCompleteView view) {
+ auto complete_view = ReadLocalSupportedFeaturesCompleteView::Create(view);
+ ASSERT(complete_view.IsValid());
+ ErrorCode status = complete_view.GetStatus();
+ ASSERT_LOG(status == ErrorCode::SUCCESS, "Status 0x%02hhx, %s", status, ErrorCodeText(status).c_str());
+ local_supported_features_ = complete_view.GetLmpFeatures();
+ }
+
void read_local_extended_features_complete_handler(std::promise<void> promise, CommandCompleteView view) {
auto complete_view = ReadLocalExtendedFeaturesCompleteView::Create(view);
ASSERT(complete_view.IsValid());
@@ -240,10 +191,10 @@ struct Controller::impl {
// Query all extended features
if (page_number < maximum_page_number_) {
page_number++;
- hci_->EnqueueCommand(
- ReadLocalExtendedFeaturesBuilder::Create(page_number),
- module_.GetHandler()->BindOnceOn(this, &Controller::impl::read_local_extended_features_complete_handler,
- std::move(promise)));
+ hci_->EnqueueCommand(ReadLocalExtendedFeaturesBuilder::Create(page_number),
+ BindOnce(&Controller::impl::read_local_extended_features_complete_handler,
+ common::Unretained(this), std::move(promise)),
+ module_.GetHandler());
} else {
promise.set_value();
}
@@ -271,36 +222,11 @@ struct Controller::impl {
}
void le_read_buffer_size_handler(CommandCompleteView view) {
- auto complete_view = LeReadBufferSizeV1CompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- ErrorCode status = complete_view.GetStatus();
- ASSERT_LOG(status == ErrorCode::SUCCESS, "Status 0x%02hhx, %s", status, ErrorCodeText(status).c_str());
- le_buffer_size_ = complete_view.GetLeBufferSize();
-
- // If LE buffer size is zero, then buffers returned by Read_Buffer_Size are shared between BR/EDR and LE.
- if (le_buffer_size_.total_num_le_packets_ == 0) {
- ASSERT(acl_buffers_ != 0);
- le_buffer_size_.total_num_le_packets_ = acl_buffers_ / 2;
- acl_buffers_ -= le_buffer_size_.total_num_le_packets_;
- le_buffer_size_.le_data_packet_length_ = acl_buffer_length_;
- }
- }
-
- void le_read_buffer_size_v2_handler(CommandCompleteView view) {
- auto complete_view = LeReadBufferSizeV2CompleteView::Create(view);
+ auto complete_view = LeReadBufferSizeCompleteView::Create(view);
ASSERT(complete_view.IsValid());
ErrorCode status = complete_view.GetStatus();
ASSERT_LOG(status == ErrorCode::SUCCESS, "Status 0x%02hhx, %s", status, ErrorCodeText(status).c_str());
le_buffer_size_ = complete_view.GetLeBufferSize();
- iso_buffer_size_ = complete_view.GetIsoBufferSize();
-
- // If LE buffer size is zero, then buffers returned by Read_Buffer_Size are shared between BR/EDR and LE.
- if (le_buffer_size_.total_num_le_packets_ == 0) {
- ASSERT(acl_buffers_ != 0);
- le_buffer_size_.total_num_le_packets_ = acl_buffers_ / 2;
- acl_buffers_ -= le_buffer_size_.total_num_le_packets_;
- le_buffer_size_.le_data_packet_length_ = acl_buffer_length_;
- }
}
void le_read_local_supported_features_handler(CommandCompleteView view) {
@@ -319,22 +245,6 @@ struct Controller::impl {
le_supported_states_ = complete_view.GetLeStates();
}
- void le_read_connect_list_size_handler(CommandCompleteView view) {
- auto complete_view = LeReadConnectListSizeCompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- ErrorCode status = complete_view.GetStatus();
- ASSERT_LOG(status == ErrorCode::SUCCESS, "Status 0x%02hhx, %s", status, ErrorCodeText(status).c_str());
- le_connect_list_size_ = complete_view.GetConnectListSize();
- }
-
- void le_read_resolving_list_size_handler(CommandCompleteView view) {
- auto complete_view = LeReadResolvingListSizeCompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- ErrorCode status = complete_view.GetStatus();
- ASSERT_LOG(status == ErrorCode::SUCCESS, "Status 0x%02hhx, %s", status, ErrorCodeText(status).c_str());
- le_resolving_list_size_ = complete_view.GetResolvingListSize();
- }
-
void le_read_maximum_data_length_handler(CommandCompleteView view) {
auto complete_view = LeReadMaximumDataLengthCompleteView::Create(view);
ASSERT(complete_view.IsValid());
@@ -343,14 +253,6 @@ struct Controller::impl {
le_maximum_data_length_ = complete_view.GetLeMaximumDataLength();
}
- void le_read_suggested_default_data_length_handler(CommandCompleteView view) {
- auto complete_view = LeReadSuggestedDefaultDataLengthCompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- ErrorCode status = complete_view.GetStatus();
- ASSERT_LOG(status == ErrorCode::SUCCESS, "Status 0x%02hhx, %s", status, ErrorCodeText(status).c_str());
- le_suggested_default_data_length_ = complete_view.GetTxOctets();
- }
-
void le_read_maximum_advertising_data_length_handler(CommandCompleteView view) {
auto complete_view = LeReadMaximumAdvertisingDataLengthCompleteView::Create(view);
ASSERT(complete_view.IsValid());
@@ -367,14 +269,6 @@ struct Controller::impl {
le_number_supported_advertising_sets_ = complete_view.GetNumberSupportedAdvertisingSets();
}
- void le_read_periodic_advertiser_list_size_handler(CommandCompleteView view) {
- auto complete_view = LeReadPeriodicAdvertiserListSizeCompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- ErrorCode status = complete_view.GetStatus();
- ASSERT_LOG(status == ErrorCode::SUCCESS, "Status 0x%02hhx, %s", status, ErrorCodeText(status).c_str());
- le_periodic_advertiser_list_size_ = complete_view.GetPeriodicAdvertiserListSize();
- }
-
void le_get_vendor_capabilities_handler(CommandCompleteView view) {
auto complete_view = LeGetVendorCapabilitiesCompleteView::Create(view);
@@ -451,35 +345,23 @@ struct Controller::impl {
void set_event_mask(uint64_t event_mask) {
std::unique_ptr<SetEventMaskBuilder> packet = SetEventMaskBuilder::Create(event_mask);
- hci_->EnqueueCommand(std::move(packet), module_.GetHandler()->BindOnceOn(
- this, &Controller::impl::check_status<SetEventMaskCompleteView>));
- }
-
- void write_le_host_support(Enable enable) {
- // Since Bluetooth Core Spec 4.1, this bit should be 0, but some controllers still require it
- Enable simultaneous_le_host = Enable::ENABLED;
- std::unique_ptr<WriteLeHostSupportBuilder> packet = WriteLeHostSupportBuilder::Create(enable, simultaneous_le_host);
- hci_->EnqueueCommand(
- std::move(packet),
- module_.GetHandler()->BindOnceOn(this, &Controller::impl::check_status<WriteLeHostSupportCompleteView>));
- }
-
- void write_simple_pairing_mode(Enable enable) {
- std::unique_ptr<WriteSimplePairingModeBuilder> packet = WriteSimplePairingModeBuilder::Create(enable);
- hci_->EnqueueCommand(
- std::move(packet),
- module_.GetHandler()->BindOnceOn(this, &Controller::impl::check_status<WriteSimplePairingModeCompleteView>));
+ hci_->EnqueueCommand(std::move(packet),
+ BindOnce(&Controller::impl::check_status<SetEventMaskCompleteView>, common::Unretained(this)),
+ module_.GetHandler());
}
void reset() {
std::unique_ptr<ResetBuilder> packet = ResetBuilder::Create();
hci_->EnqueueCommand(std::move(packet),
- module_.GetHandler()->BindOnceOn(this, &Controller::impl::check_status<ResetCompleteView>));
+ BindOnce(&Controller::impl::check_status<ResetCompleteView>, common::Unretained(this)),
+ module_.GetHandler());
}
void set_event_filter(std::unique_ptr<SetEventFilterBuilder> packet) {
- hci_->EnqueueCommand(std::move(packet), module_.GetHandler()->BindOnceOn(
- this, &Controller::impl::check_status<SetEventFilterCompleteView>));
+ hci_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&Controller::impl::check_status<SetEventFilterCompleteView>, common::Unretained(this)),
+ module_.GetHandler());
}
void write_local_name(std::string local_name) {
@@ -490,8 +372,10 @@ struct Controller::impl {
std::copy(std::begin(local_name), std::end(local_name), std::begin(local_name_array));
std::unique_ptr<WriteLocalNameBuilder> packet = WriteLocalNameBuilder::Create(local_name_array);
- hci_->EnqueueCommand(std::move(packet), module_.GetHandler()->BindOnceOn(
- this, &Controller::impl::check_status<WriteLocalNameCompleteView>));
+ hci_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&Controller::impl::check_status<WriteLocalNameCompleteView>, common::Unretained(this)),
+ module_.GetHandler());
}
void host_buffer_size(uint16_t host_acl_data_packet_length, uint8_t host_synchronous_data_packet_length,
@@ -499,14 +383,18 @@ struct Controller::impl {
std::unique_ptr<HostBufferSizeBuilder> packet =
HostBufferSizeBuilder::Create(host_acl_data_packet_length, host_synchronous_data_packet_length,
host_total_num_acl_data_packets, host_total_num_synchronous_data_packets);
- hci_->EnqueueCommand(std::move(packet), module_.GetHandler()->BindOnceOn(
- this, &Controller::impl::check_status<HostBufferSizeCompleteView>));
+ hci_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&Controller::impl::check_status<HostBufferSizeCompleteView>, common::Unretained(this)),
+ module_.GetHandler());
}
void le_set_event_mask(uint64_t le_event_mask) {
std::unique_ptr<LeSetEventMaskBuilder> packet = LeSetEventMaskBuilder::Create(le_event_mask);
- hci_->EnqueueCommand(std::move(packet), module_.GetHandler()->BindOnceOn(
- this, &Controller::impl::check_status<LeSetEventMaskCompleteView>));
+ hci_->EnqueueCommand(
+ std::move(packet),
+ BindOnce(&Controller::impl::check_status<LeSetEventMaskCompleteView>, common::Unretained(this)),
+ module_.GetHandler());
}
template <class T>
@@ -524,7 +412,7 @@ struct Controller::impl {
uint16_t bit_index = index % 10; \
bool supported = local_supported_commands_[byte_index] & (1 << bit_index); \
if (!supported) { \
- LOG_DEBUG("unsupported command opcode: 0x%04x", (uint16_t)OpCode::name); \
+ LOG_WARN("unsupported command opcode: 0x%04x", (uint16_t)OpCode::name); \
} \
return supported; \
}
@@ -548,7 +436,7 @@ struct Controller::impl {
OP_CODE_MAPPING(AUTHENTICATION_REQUESTED)
OP_CODE_MAPPING(SET_CONNECTION_ENCRYPTION)
OP_CODE_MAPPING(CHANGE_CONNECTION_LINK_KEY)
- OP_CODE_MAPPING(CENTRAL_LINK_KEY)
+ OP_CODE_MAPPING(MASTER_LINK_KEY)
OP_CODE_MAPPING(REMOTE_NAME_REQUEST)
OP_CODE_MAPPING(REMOTE_NAME_REQUEST_CANCEL)
OP_CODE_MAPPING(READ_REMOTE_SUPPORTED_FEATURES)
@@ -655,19 +543,17 @@ struct Controller::impl {
OP_CODE_MAPPING(WRITE_SIMPLE_PAIRING_DEBUG_MODE)
OP_CODE_MAPPING(REMOTE_OOB_DATA_REQUEST_NEGATIVE_REPLY)
OP_CODE_MAPPING(SEND_KEYPRESS_NOTIFICATION)
- OP_CODE_MAPPING(SET_EVENT_MASK_PAGE_2)
OP_CODE_MAPPING(IO_CAPABILITY_REQUEST_NEGATIVE_REPLY)
- OP_CODE_MAPPING(REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY)
OP_CODE_MAPPING(READ_ENCRYPTION_KEY_SIZE)
OP_CODE_MAPPING(READ_DATA_BLOCK_SIZE)
OP_CODE_MAPPING(READ_LE_HOST_SUPPORT)
OP_CODE_MAPPING(WRITE_LE_HOST_SUPPORT)
OP_CODE_MAPPING(LE_SET_EVENT_MASK)
- OP_CODE_MAPPING(LE_READ_BUFFER_SIZE_V1)
+ OP_CODE_MAPPING(LE_READ_BUFFER_SIZE)
OP_CODE_MAPPING(LE_READ_LOCAL_SUPPORTED_FEATURES)
OP_CODE_MAPPING(LE_SET_RANDOM_ADDRESS)
OP_CODE_MAPPING(LE_SET_ADVERTISING_PARAMETERS)
- OP_CODE_MAPPING(LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER)
+ OP_CODE_MAPPING(LE_READ_ADVERTISING_CHANNEL_TX_POWER)
OP_CODE_MAPPING(LE_SET_ADVERTISING_DATA)
OP_CODE_MAPPING(LE_SET_SCAN_RESPONSE_DATA)
OP_CODE_MAPPING(LE_SET_ADVERTISING_ENABLE)
@@ -675,10 +561,10 @@ struct Controller::impl {
OP_CODE_MAPPING(LE_SET_SCAN_ENABLE)
OP_CODE_MAPPING(LE_CREATE_CONNECTION)
OP_CODE_MAPPING(LE_CREATE_CONNECTION_CANCEL)
- OP_CODE_MAPPING(LE_READ_CONNECT_LIST_SIZE)
- OP_CODE_MAPPING(LE_CLEAR_CONNECT_LIST)
- OP_CODE_MAPPING(LE_ADD_DEVICE_TO_CONNECT_LIST)
- OP_CODE_MAPPING(LE_REMOVE_DEVICE_FROM_CONNECT_LIST)
+ OP_CODE_MAPPING(LE_READ_WHITE_LIST_SIZE)
+ OP_CODE_MAPPING(LE_CLEAR_WHITE_LIST)
+ OP_CODE_MAPPING(LE_ADD_DEVICE_TO_WHITE_LIST)
+ OP_CODE_MAPPING(LE_REMOVE_DEVICE_FROM_WHITE_LIST)
OP_CODE_MAPPING(LE_CONNECTION_UPDATE)
OP_CODE_MAPPING(LE_SET_HOST_CHANNEL_CLASSIFICATION)
OP_CODE_MAPPING(LE_READ_CHANNEL_MAP)
@@ -694,7 +580,7 @@ struct Controller::impl {
OP_CODE_MAPPING(LE_TEST_END)
OP_CODE_MAPPING(ENHANCED_SETUP_SYNCHRONOUS_CONNECTION)
OP_CODE_MAPPING(ENHANCED_ACCEPT_SYNCHRONOUS_CONNECTION)
- OP_CODE_MAPPING(READ_LOCAL_SUPPORTED_CODECS_V1)
+ OP_CODE_MAPPING(READ_LOCAL_SUPPORTED_CODECS)
OP_CODE_MAPPING(READ_SECURE_CONNECTIONS_HOST_SUPPORT)
OP_CODE_MAPPING(WRITE_SECURE_CONNECTIONS_HOST_SUPPORT)
OP_CODE_MAPPING(READ_LOCAL_OOB_EXTENDED_DATA)
@@ -746,42 +632,7 @@ struct Controller::impl {
OP_CODE_MAPPING(LE_READ_RF_PATH_COMPENSATION_POWER)
OP_CODE_MAPPING(LE_WRITE_RF_PATH_COMPENSATION_POWER)
OP_CODE_MAPPING(LE_SET_PRIVACY_MODE)
- OP_CODE_MAPPING(LE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE)
- OP_CODE_MAPPING(LE_PERIODIC_ADVERTISING_SYNC_TRANSFER)
- OP_CODE_MAPPING(LE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER)
- OP_CODE_MAPPING(LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS)
- OP_CODE_MAPPING(LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS)
OP_CODE_MAPPING(LE_GENERATE_DHKEY_COMMAND)
- OP_CODE_MAPPING(LE_MODIFY_SLEEP_CLOCK_ACCURACY)
- OP_CODE_MAPPING(LE_READ_BUFFER_SIZE_V2)
- OP_CODE_MAPPING(LE_READ_ISO_TX_SYNC)
- OP_CODE_MAPPING(LE_SET_CIG_PARAMETERS)
- OP_CODE_MAPPING(LE_SET_CIG_PARAMETERS_TEST)
- OP_CODE_MAPPING(LE_CREATE_CIS)
- OP_CODE_MAPPING(LE_REMOVE_CIG)
- OP_CODE_MAPPING(LE_ACCEPT_CIS_REQUEST)
- OP_CODE_MAPPING(LE_REJECT_CIS_REQUEST)
- OP_CODE_MAPPING(LE_CREATE_BIG)
- OP_CODE_MAPPING(LE_TERMINATE_BIG)
- OP_CODE_MAPPING(LE_BIG_CREATE_SYNC)
- OP_CODE_MAPPING(LE_BIG_TERMINATE_SYNC)
- OP_CODE_MAPPING(LE_REQUEST_PEER_SCA)
- OP_CODE_MAPPING(LE_SETUP_ISO_DATA_PATH)
- OP_CODE_MAPPING(LE_REMOVE_ISO_DATA_PATH)
- OP_CODE_MAPPING(LE_SET_HOST_FEATURE)
- OP_CODE_MAPPING(LE_READ_ISO_LINK_QUALITY)
- OP_CODE_MAPPING(LE_ENHANCED_READ_TRANSMIT_POWER_LEVEL)
- OP_CODE_MAPPING(LE_READ_REMOTE_TRANSMIT_POWER_LEVEL)
- OP_CODE_MAPPING(LE_SET_PATH_LOSS_REPORTING_PARAMETERS)
- OP_CODE_MAPPING(LE_SET_PATH_LOSS_REPORTING_ENABLE)
- OP_CODE_MAPPING(LE_SET_TRANSMIT_POWER_REPORTING_ENABLE)
- OP_CODE_MAPPING(SET_ECOSYSTEM_BASE_INTERVAL)
- OP_CODE_MAPPING(READ_LOCAL_SUPPORTED_CODECS_V2)
- OP_CODE_MAPPING(READ_LOCAL_SUPPORTED_CODEC_CAPABILITIES)
- OP_CODE_MAPPING(READ_LOCAL_SUPPORTED_CONTROLLER_DELAY)
- OP_CODE_MAPPING(CONFIGURE_DATA_PATH)
- OP_CODE_MAPPING(ENHANCED_FLUSH)
-
// vendor specific
case OpCode::LE_GET_VENDOR_CAPABILITIES:
return vendor_capabilities_.is_supported_ == 0x01;
@@ -791,6 +642,8 @@ struct Controller::impl {
return vendor_capabilities_.total_scan_results_storage_ != 0x00;
case OpCode::LE_ADV_FILTER:
return vendor_capabilities_.filtering_support_ == 0x01;
+ case OpCode::LE_TRACK_ADV:
+ return vendor_capabilities_.total_num_of_advt_tracked_ > 0;
case OpCode::LE_ENERGY_INFO:
return vendor_capabilities_.activity_energy_info_support_ == 0x01;
case OpCode::LE_EXTENDED_SCAN_PARAMS:
@@ -802,6 +655,7 @@ struct Controller::impl {
case OpCode::CONTROLLER_BQR:
return vendor_capabilities_.bluetooth_quality_report_support_ == 0x01;
// undefined in local_supported_commands_
+ case OpCode::CREATE_NEW_UNIT_KEY:
case OpCode::READ_LOCAL_SUPPORTED_COMMANDS:
return true;
case OpCode::NONE:
@@ -815,10 +669,11 @@ struct Controller::impl {
HciLayer* hci_;
- CompletedAclPacketsCallback acl_credits_callback_{};
- CompletedAclPacketsCallback acl_monitor_credits_callback_{};
+ Callback<void(uint16_t, uint16_t)> acl_credits_callback_;
+ Handler* acl_credits_handler_ = nullptr;
LocalVersionInformation local_version_information_;
std::array<uint8_t, 64> local_supported_commands_;
+ uint64_t local_supported_features_;
uint8_t maximum_page_number_;
std::vector<uint64_t> extended_lmp_features_array_;
uint16_t acl_buffer_length_ = 0;
@@ -828,16 +683,11 @@ struct Controller::impl {
Address mac_address_;
std::string local_name_;
LeBufferSize le_buffer_size_;
- LeBufferSize iso_buffer_size_;
uint64_t le_local_supported_features_;
uint64_t le_supported_states_;
- uint8_t le_connect_list_size_;
- uint8_t le_resolving_list_size_;
LeMaximumDataLength le_maximum_data_length_;
uint16_t le_maximum_advertising_data_length_;
- uint16_t le_suggested_default_data_length_;
uint8_t le_number_supported_advertising_sets_;
- uint8_t le_periodic_advertiser_list_size_;
VendorCapabilities vendor_capabilities_;
}; // namespace hci
@@ -845,151 +695,94 @@ Controller::Controller() : impl_(std::make_unique<impl>(*this)) {}
Controller::~Controller() = default;
-void Controller::RegisterCompletedAclPacketsCallback(CompletedAclPacketsCallback cb) {
- CallOn(impl_.get(), &impl::register_completed_acl_packets_callback, cb);
+void Controller::RegisterCompletedAclPacketsCallback(Callback<void(uint16_t /* handle */, uint16_t /* packets */)> cb,
+ Handler* handler) {
+ impl_->RegisterCompletedAclPacketsCallback(cb, handler); // TODO hsz: why here?
}
-void Controller::UnregisterCompletedAclPacketsCallback() {
- CallOn(impl_.get(), &impl::unregister_completed_acl_packets_callback);
+std::string Controller::GetControllerLocalName() const {
+ return impl_->local_name_;
}
-void Controller::RegisterCompletedMonitorAclPacketsCallback(CompletedAclPacketsCallback cb) {
- CallOn(impl_.get(), &impl::register_completed_monitor_acl_packets_callback, cb);
+LocalVersionInformation Controller::GetControllerLocalVersionInformation() const {
+ return impl_->local_version_information_;
}
-void Controller::UnregisterCompletedMonitorAclPacketsCallback() {
- CallOn(impl_.get(), &impl::unregister_completed_monitor_acl_packets_callback);
+std::array<uint8_t, 64> Controller::GetControllerLocalSupportedCommands() const {
+ return impl_->local_supported_commands_;
}
-std::string Controller::GetLocalName() const {
- return impl_->local_name_;
+uint8_t Controller::GetControllerLocalExtendedFeaturesMaxPageNumber() const {
+ return impl_->maximum_page_number_;
}
-LocalVersionInformation Controller::GetLocalVersionInformation() const {
- return impl_->local_version_information_;
+uint64_t Controller::GetControllerLocalSupportedFeatures() const {
+ return impl_->local_supported_features_;
}
-#define BIT(x) (0x1ULL << (x))
-
-#define LOCAL_FEATURE_ACCESSOR(name, page, bit) \
- bool Controller::name() const { \
- return GetLocalFeatures(page) & BIT(bit); \
- }
-
-LOCAL_FEATURE_ACCESSOR(SupportsSimplePairing, 0, 51)
-LOCAL_FEATURE_ACCESSOR(SupportsSecureConnections, 2, 8)
-LOCAL_FEATURE_ACCESSOR(SupportsSimultaneousLeBrEdr, 0, 49)
-LOCAL_FEATURE_ACCESSOR(SupportsInterlacedInquiryScan, 0, 28)
-LOCAL_FEATURE_ACCESSOR(SupportsRssiWithInquiryResults, 0, 30)
-LOCAL_FEATURE_ACCESSOR(SupportsExtendedInquiryResponse, 0, 48)
-LOCAL_FEATURE_ACCESSOR(SupportsRoleSwitch, 0, 5)
-LOCAL_FEATURE_ACCESSOR(Supports3SlotPackets, 0, 0)
-LOCAL_FEATURE_ACCESSOR(Supports5SlotPackets, 0, 1)
-LOCAL_FEATURE_ACCESSOR(SupportsClassic2mPhy, 0, 25)
-LOCAL_FEATURE_ACCESSOR(SupportsClassic3mPhy, 0, 26)
-LOCAL_FEATURE_ACCESSOR(Supports3SlotEdrPackets, 0, 39)
-LOCAL_FEATURE_ACCESSOR(Supports5SlotEdrPackets, 0, 40)
-LOCAL_FEATURE_ACCESSOR(SupportsSco, 0, 11)
-LOCAL_FEATURE_ACCESSOR(SupportsHv2Packets, 0, 12)
-LOCAL_FEATURE_ACCESSOR(SupportsHv3Packets, 0, 13)
-LOCAL_FEATURE_ACCESSOR(SupportsEv3Packets, 0, 31)
-LOCAL_FEATURE_ACCESSOR(SupportsEv4Packets, 0, 32)
-LOCAL_FEATURE_ACCESSOR(SupportsEv5Packets, 0, 33)
-LOCAL_FEATURE_ACCESSOR(SupportsEsco2mPhy, 0, 45)
-LOCAL_FEATURE_ACCESSOR(SupportsEsco3mPhy, 0, 46)
-LOCAL_FEATURE_ACCESSOR(Supports3SlotEscoEdrPackets, 0, 47)
-LOCAL_FEATURE_ACCESSOR(SupportsHoldMode, 0, 6)
-LOCAL_FEATURE_ACCESSOR(SupportsSniffMode, 0, 7)
-LOCAL_FEATURE_ACCESSOR(SupportsParkMode, 0, 8)
-LOCAL_FEATURE_ACCESSOR(SupportsNonFlushablePb, 0, 54)
-LOCAL_FEATURE_ACCESSOR(SupportsSniffSubrating, 0, 41)
-LOCAL_FEATURE_ACCESSOR(SupportsEncryptionPause, 0, 42)
-LOCAL_FEATURE_ACCESSOR(SupportsBle, 0, 38)
-
-#define LOCAL_LE_FEATURE_ACCESSOR(name, bit) \
- bool Controller::name() const { \
- return GetLocalLeFeatures() & BIT(bit); \
- }
-
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBleConnectionParameterRequest, 1)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBleConnectionParametersRequest, 2)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBlePeripheralInitiatedFeatureExchange, 3)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBlePacketExtension, 5)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBlePrivacy, 6)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBle2mPhy, 8)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBleCodedPhy, 11)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBleExtendedAdvertising, 12)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBlePeriodicAdvertising, 13)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBlePeriodicAdvertisingSyncTransferSender, 24)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBlePeriodicAdvertisingSyncTransferRecipient, 25)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBleConnectedIsochronousStreamCentral, 28)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBleConnectedIsochronousStreamPeripheral, 29)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBleIsochronousBroadcaster, 30)
-LOCAL_LE_FEATURE_ACCESSOR(SupportsBleSynchronizedReceiver, 31)
-
-uint64_t Controller::GetLocalFeatures(uint8_t page_number) const {
+uint64_t Controller::GetControllerLocalExtendedFeatures(uint8_t page_number) const {
if (page_number <= impl_->maximum_page_number_) {
return impl_->extended_lmp_features_array_[page_number];
}
return 0x00;
}
-uint16_t Controller::GetAclPacketLength() const {
+uint16_t Controller::GetControllerAclPacketLength() const {
return impl_->acl_buffer_length_;
}
-uint16_t Controller::GetNumAclPacketBuffers() const {
+uint16_t Controller::GetControllerNumAclPacketBuffers() const {
return impl_->acl_buffers_;
}
-uint8_t Controller::GetScoPacketLength() const {
+uint8_t Controller::GetControllerScoPacketLength() const {
return impl_->sco_buffer_length_;
}
-uint16_t Controller::GetNumScoPacketBuffers() const {
+uint16_t Controller::GetControllerNumScoPacketBuffers() const {
return impl_->sco_buffers_;
}
-Address Controller::GetMacAddress() const {
+Address Controller::GetControllerMacAddress() const {
return impl_->mac_address_;
}
void Controller::SetEventMask(uint64_t event_mask) {
- CallOn(impl_.get(), &impl::set_event_mask, event_mask);
+ GetHandler()->Post(common::BindOnce(&impl::set_event_mask, common::Unretained(impl_.get()), event_mask));
}
void Controller::Reset() {
- CallOn(impl_.get(), &impl::reset);
+ GetHandler()->Post(common::BindOnce(&impl::reset, common::Unretained(impl_.get())));
}
void Controller::SetEventFilterClearAll() {
std::unique_ptr<SetEventFilterClearAllBuilder> packet = SetEventFilterClearAllBuilder::Create();
- CallOn(impl_.get(), &impl::set_event_filter, std::move(packet));
+ GetHandler()->Post(common::BindOnce(&impl::set_event_filter, common::Unretained(impl_.get()), std::move(packet)));
}
void Controller::SetEventFilterInquiryResultAllDevices() {
std::unique_ptr<SetEventFilterInquiryResultAllDevicesBuilder> packet =
SetEventFilterInquiryResultAllDevicesBuilder::Create();
- CallOn(impl_.get(), &impl::set_event_filter, std::move(packet));
+ GetHandler()->Post(common::BindOnce(&impl::set_event_filter, common::Unretained(impl_.get()), std::move(packet)));
}
void Controller::SetEventFilterInquiryResultClassOfDevice(ClassOfDevice class_of_device,
ClassOfDevice class_of_device_mask) {
std::unique_ptr<SetEventFilterInquiryResultClassOfDeviceBuilder> packet =
SetEventFilterInquiryResultClassOfDeviceBuilder::Create(class_of_device, class_of_device_mask);
- CallOn(impl_.get(), &impl::set_event_filter, std::move(packet));
+ GetHandler()->Post(common::BindOnce(&impl::set_event_filter, common::Unretained(impl_.get()), std::move(packet)));
}
void Controller::SetEventFilterInquiryResultAddress(Address address) {
std::unique_ptr<SetEventFilterInquiryResultAddressBuilder> packet =
SetEventFilterInquiryResultAddressBuilder::Create(address);
- CallOn(impl_.get(), &impl::set_event_filter, std::move(packet));
+ GetHandler()->Post(common::BindOnce(&impl::set_event_filter, common::Unretained(impl_.get()), std::move(packet)));
}
void Controller::SetEventFilterConnectionSetupAllDevices(AutoAcceptFlag auto_accept_flag) {
std::unique_ptr<SetEventFilterConnectionSetupAllDevicesBuilder> packet =
SetEventFilterConnectionSetupAllDevicesBuilder::Create(auto_accept_flag);
- CallOn(impl_.get(), &impl::set_event_filter, std::move(packet));
+ GetHandler()->Post(common::BindOnce(&impl::set_event_filter, common::Unretained(impl_.get()), std::move(packet)));
}
void Controller::SetEventFilterConnectionSetupClassOfDevice(ClassOfDevice class_of_device,
@@ -998,88 +791,60 @@ void Controller::SetEventFilterConnectionSetupClassOfDevice(ClassOfDevice class_
std::unique_ptr<SetEventFilterConnectionSetupClassOfDeviceBuilder> packet =
SetEventFilterConnectionSetupClassOfDeviceBuilder::Create(class_of_device, class_of_device_mask,
auto_accept_flag);
- CallOn(impl_.get(), &impl::set_event_filter, std::move(packet));
+ GetHandler()->Post(common::BindOnce(&impl::set_event_filter, common::Unretained(impl_.get()), std::move(packet)));
}
void Controller::SetEventFilterConnectionSetupAddress(Address address, AutoAcceptFlag auto_accept_flag) {
std::unique_ptr<SetEventFilterConnectionSetupAddressBuilder> packet =
SetEventFilterConnectionSetupAddressBuilder::Create(address, auto_accept_flag);
- CallOn(impl_.get(), &impl::set_event_filter, std::move(packet));
+ GetHandler()->Post(common::BindOnce(&impl::set_event_filter, common::Unretained(impl_.get()), std::move(packet)));
}
void Controller::WriteLocalName(std::string local_name) {
impl_->local_name_ = local_name;
- CallOn(impl_.get(), &impl::write_local_name, local_name);
+ GetHandler()->Post(common::BindOnce(&impl::write_local_name, common::Unretained(impl_.get()), local_name));
}
void Controller::HostBufferSize(uint16_t host_acl_data_packet_length, uint8_t host_synchronous_data_packet_length,
uint16_t host_total_num_acl_data_packets,
uint16_t host_total_num_synchronous_data_packets) {
- CallOn(
- impl_.get(),
- &impl::host_buffer_size,
- host_acl_data_packet_length,
- host_synchronous_data_packet_length,
- host_total_num_acl_data_packets,
- host_total_num_synchronous_data_packets);
+ GetHandler()->Post(common::BindOnce(&impl::host_buffer_size, common::Unretained(impl_.get()),
+ host_acl_data_packet_length, host_synchronous_data_packet_length,
+ host_total_num_acl_data_packets, host_total_num_synchronous_data_packets));
}
void Controller::LeSetEventMask(uint64_t le_event_mask) {
- CallOn(impl_.get(), &impl::le_set_event_mask, le_event_mask);
+ GetHandler()->Post(common::BindOnce(&impl::le_set_event_mask, common::Unretained(impl_.get()), le_event_mask));
}
-LeBufferSize Controller::GetLeBufferSize() const {
+LeBufferSize Controller::GetControllerLeBufferSize() const {
return impl_->le_buffer_size_;
}
-uint64_t Controller::GetLocalLeFeatures() const {
- return impl_->le_local_supported_features_;
-}
-
-LeBufferSize Controller::GetControllerIsoBufferSize() const {
- return impl_->iso_buffer_size_;
-}
-
uint64_t Controller::GetControllerLeLocalSupportedFeatures() const {
return impl_->le_local_supported_features_;
}
-uint64_t Controller::GetLeSupportedStates() const {
+uint64_t Controller::GetControllerLeSupportedStates() const {
return impl_->le_supported_states_;
}
-uint8_t Controller::GetLeConnectListSize() const {
- return impl_->le_connect_list_size_;
-}
-
-uint8_t Controller::GetLeResolvingListSize() const {
- return impl_->le_resolving_list_size_;
-}
-
-LeMaximumDataLength Controller::GetLeMaximumDataLength() const {
+LeMaximumDataLength Controller::GetControllerLeMaximumDataLength() const {
return impl_->le_maximum_data_length_;
}
-uint16_t Controller::GetLeMaximumAdvertisingDataLength() const {
+uint16_t Controller::GetControllerLeMaximumAdvertisingDataLength() const {
return impl_->le_maximum_advertising_data_length_;
}
-uint16_t Controller::GetLeSuggestedDefaultDataLength() const {
- return impl_->le_suggested_default_data_length_;
-}
-
-uint8_t Controller::GetLeNumberOfSupportedAdverisingSets() const {
+uint8_t Controller::GetControllerLeNumberOfSupportedAdverisingSets() const {
return impl_->le_number_supported_advertising_sets_;
}
-VendorCapabilities Controller::GetVendorCapabilities() const {
+VendorCapabilities Controller::GetControllerVendorCapabilities() const {
return impl_->vendor_capabilities_;
}
-uint8_t Controller::GetLePeriodicAdvertiserListSize() const {
- return impl_->le_periodic_advertiser_list_size_;
-}
-
bool Controller::IsSupported(bluetooth::hci::OpCode op_code) const {
return impl_->is_supported(op_code);
}
diff --git a/gd/hci/controller.h b/gd/hci/controller.h
index e2cb9a36a..ba02dcbcb 100644
--- a/gd/hci/controller.h
+++ b/gd/hci/controller.h
@@ -16,7 +16,7 @@
#pragma once
-#include "common/contextual_callback.h"
+#include "common/callback.h"
#include "hci/address.h"
#include "hci/hci_packets.h"
#include "module.h"
@@ -31,74 +31,30 @@ class Controller : public Module {
virtual ~Controller();
DISALLOW_COPY_AND_ASSIGN(Controller);
- using CompletedAclPacketsCallback =
- common::ContextualCallback<void(uint16_t /* handle */, uint16_t /* num_packets */)>;
- virtual void RegisterCompletedAclPacketsCallback(CompletedAclPacketsCallback cb);
-
- virtual void UnregisterCompletedAclPacketsCallback();
-
- virtual void RegisterCompletedMonitorAclPacketsCallback(CompletedAclPacketsCallback cb);
- virtual void UnregisterCompletedMonitorAclPacketsCallback();
-
- virtual std::string GetLocalName() const;
-
- virtual LocalVersionInformation GetLocalVersionInformation() const;
-
- virtual bool SupportsSimplePairing() const;
- virtual bool SupportsSecureConnections() const;
- virtual bool SupportsSimultaneousLeBrEdr() const;
- virtual bool SupportsInterlacedInquiryScan() const;
- virtual bool SupportsRssiWithInquiryResults() const;
- virtual bool SupportsExtendedInquiryResponse() const;
- virtual bool SupportsRoleSwitch() const;
- virtual bool Supports3SlotPackets() const;
- virtual bool Supports5SlotPackets() const;
- virtual bool SupportsClassic2mPhy() const;
- virtual bool SupportsClassic3mPhy() const;
- virtual bool Supports3SlotEdrPackets() const;
- virtual bool Supports5SlotEdrPackets() const;
- virtual bool SupportsSco() const;
- virtual bool SupportsHv2Packets() const;
- virtual bool SupportsHv3Packets() const;
- virtual bool SupportsEv3Packets() const;
- virtual bool SupportsEv4Packets() const;
- virtual bool SupportsEv5Packets() const;
- virtual bool SupportsEsco2mPhy() const;
- virtual bool SupportsEsco3mPhy() const;
- virtual bool Supports3SlotEscoEdrPackets() const;
- virtual bool SupportsHoldMode() const;
- virtual bool SupportsSniffMode() const;
- virtual bool SupportsParkMode() const;
- virtual bool SupportsNonFlushablePb() const;
- virtual bool SupportsSniffSubrating() const;
- virtual bool SupportsEncryptionPause() const;
-
- virtual bool SupportsBle() const;
- virtual bool SupportsBlePrivacy() const;
- virtual bool SupportsBlePacketExtension() const;
- virtual bool SupportsBleConnectionParametersRequest() const;
- virtual bool SupportsBle2mPhy() const;
- virtual bool SupportsBleCodedPhy() const;
- virtual bool SupportsBleExtendedAdvertising() const;
- virtual bool SupportsBlePeriodicAdvertising() const;
- virtual bool SupportsBlePeripheralInitiatedFeatureExchange() const;
- virtual bool SupportsBleConnectionParameterRequest() const;
- virtual bool SupportsBlePeriodicAdvertisingSyncTransferSender() const;
- virtual bool SupportsBlePeriodicAdvertisingSyncTransferRecipient() const;
- virtual bool SupportsBleConnectedIsochronousStreamCentral() const;
- virtual bool SupportsBleConnectedIsochronousStreamPeripheral() const;
- virtual bool SupportsBleIsochronousBroadcaster() const;
- virtual bool SupportsBleSynchronizedReceiver() const;
-
- virtual uint16_t GetAclPacketLength() const;
-
- virtual uint16_t GetNumAclPacketBuffers() const;
-
- virtual uint8_t GetScoPacketLength() const;
-
- virtual uint16_t GetNumScoPacketBuffers() const;
-
- virtual Address GetMacAddress() const;
+ virtual void RegisterCompletedAclPacketsCallback(
+ common::Callback<void(uint16_t /* handle */, uint16_t /* num_packets */)> cb, os::Handler* handler);
+
+ virtual std::string GetControllerLocalName() const;
+
+ virtual LocalVersionInformation GetControllerLocalVersionInformation() const;
+
+ virtual std::array<uint8_t, 64> GetControllerLocalSupportedCommands() const;
+
+ virtual uint64_t GetControllerLocalSupportedFeatures() const;
+
+ virtual uint8_t GetControllerLocalExtendedFeaturesMaxPageNumber() const;
+
+ virtual uint64_t GetControllerLocalExtendedFeatures(uint8_t page_number) const;
+
+ virtual uint16_t GetControllerAclPacketLength() const;
+
+ virtual uint16_t GetControllerNumAclPacketBuffers() const;
+
+ virtual uint8_t GetControllerScoPacketLength() const;
+
+ virtual uint16_t GetControllerNumScoPacketBuffers() const;
+
+ virtual Address GetControllerMacAddress() const;
virtual void SetEventMask(uint64_t event_mask);
@@ -130,36 +86,25 @@ class Controller : public Module {
// LE controller commands
virtual void LeSetEventMask(uint64_t le_event_mask);
- virtual LeBufferSize GetLeBufferSize() const;
-
- virtual uint64_t GetLeSupportedStates() const;
-
- virtual LeBufferSize GetControllerIsoBufferSize() const;
+ virtual LeBufferSize GetControllerLeBufferSize() const;
virtual uint64_t GetControllerLeLocalSupportedFeatures() const;
- virtual uint8_t GetLeConnectListSize() const;
+ virtual uint64_t GetControllerLeSupportedStates() const;
- virtual uint8_t GetLeResolvingListSize() const;
+ virtual LeMaximumDataLength GetControllerLeMaximumDataLength() const;
- virtual LeMaximumDataLength GetLeMaximumDataLength() const;
+ virtual uint16_t GetControllerLeMaximumAdvertisingDataLength() const;
- virtual uint16_t GetLeMaximumAdvertisingDataLength() const;
+ virtual uint8_t GetControllerLeNumberOfSupportedAdverisingSets() const;
- virtual uint16_t GetLeSuggestedDefaultDataLength() const;
-
- virtual uint8_t GetLeNumberOfSupportedAdverisingSets() const;
-
- virtual uint8_t GetLePeriodicAdvertiserListSize() const;
-
- virtual VendorCapabilities GetVendorCapabilities() const;
+ virtual VendorCapabilities GetControllerVendorCapabilities() const;
virtual bool IsSupported(OpCode op_code) const;
static const ModuleFactory Factory;
static constexpr uint64_t kDefaultEventMask = 0x3dbfffffffffffff;
- static constexpr uint64_t kDefaultLeEventMask = 0x0000000000021e7f;
protected:
void ListDependencies(ModuleList* list) override;
@@ -171,9 +116,6 @@ class Controller : public Module {
std::string ToString() const override;
private:
- virtual uint64_t GetLocalFeatures(uint8_t page_number) const;
- virtual uint64_t GetLocalLeFeatures() const;
-
struct impl;
std::unique_ptr<impl> impl_;
};
diff --git a/gd/hci/controller_mock.h b/gd/hci/controller_mock.h
deleted file mode 100644
index 6ad9ba5f3..000000000
--- a/gd/hci/controller_mock.h
+++ /dev/null
@@ -1,133 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <cstdint>
-
-#include "common/contextual_callback.h"
-#include "hci/address.h"
-#include "hci/controller.h"
-#include "hci/hci_packets.h"
-#include "module.h"
-#include "os/handler.h"
-
-#include <gmock/gmock.h>
-
-// Unit test interfaces
-namespace bluetooth {
-namespace hci {
-namespace testing {
-
-class MockController : public Controller {
- public:
- MOCK_METHOD(void, RegisterCompletedAclPacketsCallback, (CompletedAclPacketsCallback cb));
- MOCK_METHOD(void, UnregisterCompletedAclPacketsCallback, ());
- MOCK_METHOD(void, RegisterCompletedMonitorAclPacketsCallback, (CompletedAclPacketsCallback cb));
- MOCK_METHOD(void, UnregisterCompletedMonitorAclPacketsCallback, ());
- MOCK_METHOD(std::string, GetLocalName, (), (const));
- MOCK_METHOD(LocalVersionInformation, GetLocalVersionInformation, (), (const));
- MOCK_METHOD(bool, SupportsSimplePairing, (), (const));
- MOCK_METHOD(bool, SupportsSecureConnections, (), (const));
- MOCK_METHOD(bool, SupportsSimultaneousLeBrEdr, (), (const));
- MOCK_METHOD(bool, SupportsInterlacedInquiryScan, (), (const));
- MOCK_METHOD(bool, SupportsRssiWithInquiryResults, (), (const));
- MOCK_METHOD(bool, SupportsExtendedInquiryResponse, (), (const));
- MOCK_METHOD(bool, SupportsRoleSwitch, (), (const));
- MOCK_METHOD(bool, Supports3SlotPackets, (), (const));
- MOCK_METHOD(bool, Supports5SlotPackets, (), (const));
- MOCK_METHOD(bool, SupportsClassic2mPhy, (), (const));
- MOCK_METHOD(bool, SupportsClassic3mPhy, (), (const));
- MOCK_METHOD(bool, Supports3SlotEdrPackets, (), (const));
- MOCK_METHOD(bool, Supports5SlotEdrPackets, (), (const));
- MOCK_METHOD(bool, SupportsSco, (), (const));
- MOCK_METHOD(bool, SupportsHv2Packets, (), (const));
- MOCK_METHOD(bool, SupportsHv3Packets, (), (const));
- MOCK_METHOD(bool, SupportsEv3Packets, (), (const));
- MOCK_METHOD(bool, SupportsEv4Packets, (), (const));
- MOCK_METHOD(bool, SupportsEv5Packets, (), (const));
- MOCK_METHOD(bool, SupportsEsco2mPhy, (), (const));
- MOCK_METHOD(bool, SupportsEsco3mPhy, (), (const));
- MOCK_METHOD(bool, Supports3SlotEscoEdrPackets, (), (const));
- MOCK_METHOD(bool, SupportsHoldMode, (), (const));
- MOCK_METHOD(bool, SupportsSniffMode, (), (const));
- MOCK_METHOD(bool, SupportsParkMode, (), (const));
- MOCK_METHOD(bool, SupportsNonFlushablePb, (), (const));
- MOCK_METHOD(bool, SupportsSniffSubrating, (), (const));
- MOCK_METHOD(bool, SupportsEncryptionPause, (), (const));
- MOCK_METHOD(bool, SupportsBle, (), (const));
- MOCK_METHOD(bool, SupportsBlePrivacy, (), (const));
- MOCK_METHOD(bool, SupportsBlePacketExtension, (), (const));
- MOCK_METHOD(bool, SupportsBleConnectionParametersRequest, (), (const));
- MOCK_METHOD(bool, SupportsBle2mPhy, (), (const));
- MOCK_METHOD(bool, SupportsBleCodedPhy, (), (const));
- MOCK_METHOD(bool, SupportsBleExtendedAdvertising, (), (const));
- MOCK_METHOD(bool, SupportsBlePeriodicAdvertising, (), (const));
- MOCK_METHOD(bool, SupportsBlePeripheralInitiatedFeatureExchange, (), (const));
- MOCK_METHOD(bool, SupportsBleConnectionParameterRequest, (), (const));
- MOCK_METHOD(bool, SupportsBlePeriodicAdvertisingSyncTransferSender, (), (const));
- MOCK_METHOD(bool, SupportsBlePeriodicAdvertisingSyncTransferRecipient, (), (const));
- MOCK_METHOD(bool, SupportsBleConnectedIsochronousStreamCentral, (), (const));
- MOCK_METHOD(bool, SupportsBleConnectedIsochronousStreamPeripheral, (), (const));
- MOCK_METHOD(bool, SupportsBleIsochronousBroadcaster, (), (const));
- MOCK_METHOD(bool, SupportsBleSynchronizedReceiver, (), (const));
- MOCK_METHOD(uint16_t, GetAclPacketLength, (), (const));
- MOCK_METHOD(uint16_t, GetNumAclPacketBuffers, (), (const));
- MOCK_METHOD(uint8_t, GetScoPacketLength, (), (const));
- MOCK_METHOD(uint16_t, GetNumScoPacketBuffers, (), (const));
- MOCK_METHOD(Address, GetMacAddress, (), (const));
- MOCK_METHOD(void, SetEventMask, (uint64_t event_mask));
- MOCK_METHOD(void, Reset, ());
- MOCK_METHOD(void, SetEventFilterClearAll, ());
- MOCK_METHOD(void, SetEventFilterInquiryResultAllDevices, ());
- MOCK_METHOD(
- void,
- SetEventFilterInquiryResultClassOfDevice,
- (ClassOfDevice class_of_device, ClassOfDevice class_of_device_mask));
- MOCK_METHOD(void, SetEventFilterInquiryResultAddress, (Address address));
- MOCK_METHOD(void, SetEventFilterConnectionSetupAllDevices, (AutoAcceptFlag auto_accept_flag));
- MOCK_METHOD(
- void,
- SetEventFilterConnectionSetupClassOfDevice,
- (ClassOfDevice class_of_device, ClassOfDevice class_of_device_mask, AutoAcceptFlag auto_accept_flag));
- MOCK_METHOD(void, SetEventFilterConnectionSetupAddress, (Address address, AutoAcceptFlag auto_accept_flag));
- MOCK_METHOD(void, WriteLocalName, (std::string local_name));
- MOCK_METHOD(
- void,
- HostBufferSize,
- (uint16_t host_acl_data_packet_length,
- uint8_t host_synchronous_data_packet_length,
- uint16_t host_total_num_acl_data_packets,
- uint16_t host_total_num_synchronous_data_packets));
- // LE controller commands
- MOCK_METHOD(void, LeSetEventMask, (uint64_t le_event_mask));
- MOCK_METHOD(LeBufferSize, GetLeBufferSize, (), (const));
- MOCK_METHOD(uint64_t, GetLeSupportedStates, (), (const));
- MOCK_METHOD(LeBufferSize, GetControllerIsoBufferSize, (), (const));
- MOCK_METHOD(uint64_t, GetControllerLeLocalSupportedFeatures, (), (const));
- MOCK_METHOD(uint8_t, GetLeConnectListSize, (), (const));
- MOCK_METHOD(uint8_t, GetLeResolvingListSize, (), (const));
- MOCK_METHOD(LeMaximumDataLength, GetLeMaximumDataLength, (), (const));
- MOCK_METHOD(uint16_t, GetLeMaximumAdvertisingDataLength, (), (const));
- MOCK_METHOD(uint16_t, GetLeSuggestedDefaultDataLength, (), (const));
- MOCK_METHOD(uint8_t, GetLeNumberOfSupportedAdverisingSets, (), (const));
- MOCK_METHOD(uint8_t, GetLePeriodicAdvertiserListSize, (), (const));
- MOCK_METHOD(VendorCapabilities, GetVendorCapabilities, (), (const));
- MOCK_METHOD(bool, IsSupported, (OpCode op_code), (const));
-};
-
-} // namespace testing
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/controller_test.cc b/gd/hci/controller_test.cc
index 75f6db10b..c77ed7ba3 100644
--- a/gd/hci/controller_test.cc
+++ b/gd/hci/controller_test.cc
@@ -25,7 +25,6 @@
#include "common/bind.h"
#include "common/callback.h"
-#include "common/init_flags.h"
#include "hci/address.h"
#include "hci/hci_layer.h"
#include "os/thread.h"
@@ -57,25 +56,22 @@ PacketView<kLittleEndian> GetPacketView(std::unique_ptr<packet::BasePacketBuilde
class TestHciLayer : public HciLayer {
public:
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(CommandCompleteView)> on_complete) override {
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) override {
GetHandler()->Post(common::BindOnce(&TestHciLayer::HandleCommand, common::Unretained(this), std::move(command),
- std::move(on_complete)));
+ std::move(on_complete), common::Unretained(handler)));
}
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(CommandStatusView)> on_status) override {
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) override {
EXPECT_TRUE(false) << "Controller properties should not generate Command Status";
}
- void HandleCommand(
- std::unique_ptr<CommandBuilder> command_builder,
- common::ContextualOnceCallback<void(CommandCompleteView)> on_complete) {
+ void HandleCommand(std::unique_ptr<CommandPacketBuilder> command_builder,
+ common::OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) {
auto packet_view = GetPacketView(std::move(command_builder));
- CommandView command = CommandView::Create(packet_view);
- ASSERT_TRUE(command.IsValid());
+ CommandPacketView command = CommandPacketView::Create(packet_view);
+ ASSERT(command.IsValid());
uint8_t num_packets = 1;
std::unique_ptr<packet::BasePacketBuilder> event_builder;
@@ -105,9 +101,14 @@ class TestHciLayer : public HciLayer {
event_builder =
ReadLocalSupportedCommandsCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS, supported_commands);
} break;
+ case (OpCode::READ_LOCAL_SUPPORTED_FEATURES): {
+ uint64_t lmp_features = 0x012345678abcdef;
+ event_builder =
+ ReadLocalSupportedFeaturesCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS, lmp_features);
+ } break;
case (OpCode::READ_LOCAL_EXTENDED_FEATURES): {
ReadLocalExtendedFeaturesView read_command = ReadLocalExtendedFeaturesView::Create(command);
- ASSERT_TRUE(read_command.IsValid());
+ ASSERT(read_command.IsValid());
uint8_t page_bumber = read_command.GetPageNumber();
uint64_t lmp_features = 0x012345678abcdef;
lmp_features += page_bumber;
@@ -122,11 +123,11 @@ class TestHciLayer : public HciLayer {
case (OpCode::READ_BD_ADDR): {
event_builder = ReadBdAddrCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS, Address::kAny);
} break;
- case (OpCode::LE_READ_BUFFER_SIZE_V1): {
+ case (OpCode::LE_READ_BUFFER_SIZE): {
LeBufferSize le_buffer_size;
le_buffer_size.le_data_packet_length_ = 0x16;
le_buffer_size.total_num_le_packets_ = 0x08;
- event_builder = LeReadBufferSizeV1CompleteBuilder::Create(num_packets, ErrorCode::SUCCESS, le_buffer_size);
+ event_builder = LeReadBufferSizeCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS, le_buffer_size);
} break;
case (OpCode::LE_READ_LOCAL_SUPPORTED_FEATURES): {
event_builder =
@@ -174,20 +175,14 @@ class TestHciLayer : public HciLayer {
} break;
case (OpCode::SET_EVENT_MASK): {
auto view = SetEventMaskView::Create(command);
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
event_mask = view.GetEventMask();
event_builder = SetEventMaskCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS);
} break;
- case (OpCode::LE_SET_EVENT_MASK): {
- auto view = LeSetEventMaskView::Create(command);
- ASSERT_TRUE(view.IsValid());
- le_event_mask = view.GetLeEventMask();
- event_builder = LeSetEventMaskCompleteBuilder::Create(num_packets, ErrorCode::SUCCESS);
- } break;
-
case (OpCode::RESET):
case (OpCode::SET_EVENT_FILTER):
case (OpCode::HOST_BUFFER_SIZE):
+ case (OpCode::LE_SET_EVENT_MASK):
command_queue_.push(command);
not_empty_.notify_all();
return;
@@ -196,21 +191,24 @@ class TestHciLayer : public HciLayer {
return;
}
auto packet = GetPacketView(std::move(event_builder));
- EventView event = EventView::Create(packet);
- ASSERT_TRUE(event.IsValid());
+ EventPacketView event = EventPacketView::Create(packet);
+ ASSERT(event.IsValid());
CommandCompleteView command_complete = CommandCompleteView::Create(event);
- ASSERT_TRUE(command_complete.IsValid());
- on_complete.Invoke(std::move(command_complete));
+ ASSERT(command_complete.IsValid());
+ handler->Post(common::BindOnce(std::move(on_complete), std::move(command_complete)));
}
- void RegisterEventHandler(EventCode event_code, common::ContextualCallback<void(EventView)> event_handler) override {
+ void RegisterEventHandler(EventCode event_code, common::Callback<void(EventPacketView)> event_handler,
+ os::Handler* handler) override {
EXPECT_EQ(event_code, EventCode::NUMBER_OF_COMPLETED_PACKETS) << "Only NUMBER_OF_COMPLETED_PACKETS is needed";
number_of_completed_packets_callback_ = event_handler;
+ client_handler_ = handler;
}
void UnregisterEventHandler(EventCode event_code) override {
EXPECT_EQ(event_code, EventCode::NUMBER_OF_COMPLETED_PACKETS) << "Only NUMBER_OF_COMPLETED_PACKETS is needed";
number_of_completed_packets_callback_ = {};
+ client_handler_ = nullptr;
}
void IncomingCredit() {
@@ -224,12 +222,12 @@ class TestHciLayer : public HciLayer {
completed_packets.push_back(cp);
auto event_builder = NumberOfCompletedPacketsBuilder::Create(completed_packets);
auto packet = GetPacketView(std::move(event_builder));
- EventView event = EventView::Create(packet);
- ASSERT_TRUE(event.IsValid());
- number_of_completed_packets_callback_.Invoke(event);
+ EventPacketView event = EventPacketView::Create(packet);
+ ASSERT(event.IsValid());
+ client_handler_->Post(common::BindOnce(number_of_completed_packets_callback_, event));
}
- CommandView GetCommand(OpCode op_code) {
+ CommandPacketView GetCommand(OpCode op_code) {
std::unique_lock<std::mutex> lock(mutex_);
std::chrono::milliseconds time = std::chrono::milliseconds(3000);
@@ -239,11 +237,8 @@ class TestHciLayer : public HciLayer {
break;
}
}
- EXPECT_TRUE(command_queue_.size() > 0);
- if (command_queue_.empty()) {
- return CommandView::Create(PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>()));
- }
- CommandView command = command_queue_.front();
+ ASSERT(command_queue_.size() > 0);
+ CommandPacketView command = command_queue_.front();
EXPECT_EQ(command.GetOpCode(), op_code);
command_queue_.pop();
return command;
@@ -258,11 +253,11 @@ class TestHciLayer : public HciLayer {
constexpr static uint16_t total_num_acl_data_packets = 10;
constexpr static uint16_t total_num_synchronous_data_packets = 12;
uint64_t event_mask = 0;
- uint64_t le_event_mask = 0;
private:
- common::ContextualCallback<void(EventView)> number_of_completed_packets_callback_;
- std::queue<CommandView> command_queue_;
+ common::Callback<void(EventPacketView)> number_of_completed_packets_callback_;
+ os::Handler* client_handler_;
+ std::queue<CommandPacketView> command_queue_;
mutable std::mutex mutex_;
std::condition_variable not_empty_;
};
@@ -270,7 +265,6 @@ class TestHciLayer : public HciLayer {
class ControllerTest : public ::testing::Test {
protected:
void SetUp() override {
- bluetooth::common::InitFlags::SetAllForTesting();
test_hci_layer_ = new TestHciLayer;
fake_registry_.InjectTestModule(&HciLayer::Factory, test_hci_layer_);
client_handler_ = fake_registry_.GetTestModuleHandler(&HciLayer::Factory);
@@ -292,32 +286,45 @@ class ControllerTest : public ::testing::Test {
TEST_F(ControllerTest, startup_teardown) {}
TEST_F(ControllerTest, read_controller_info) {
- ASSERT_EQ(controller_->GetAclPacketLength(), test_hci_layer_->acl_data_packet_length);
- ASSERT_EQ(controller_->GetNumAclPacketBuffers(), test_hci_layer_->total_num_acl_data_packets);
- ASSERT_EQ(controller_->GetScoPacketLength(), test_hci_layer_->synchronous_data_packet_length);
- ASSERT_EQ(controller_->GetNumScoPacketBuffers(), test_hci_layer_->total_num_synchronous_data_packets);
- ASSERT_EQ(controller_->GetMacAddress(), Address::kAny);
- LocalVersionInformation local_version_information = controller_->GetLocalVersionInformation();
+ ASSERT_EQ(controller_->GetControllerAclPacketLength(), test_hci_layer_->acl_data_packet_length);
+ ASSERT_EQ(controller_->GetControllerNumAclPacketBuffers(), test_hci_layer_->total_num_acl_data_packets);
+ ASSERT_EQ(controller_->GetControllerScoPacketLength(), test_hci_layer_->synchronous_data_packet_length);
+ ASSERT_EQ(controller_->GetControllerNumScoPacketBuffers(), test_hci_layer_->total_num_synchronous_data_packets);
+ ASSERT_EQ(controller_->GetControllerMacAddress(), Address::kAny);
+ LocalVersionInformation local_version_information = controller_->GetControllerLocalVersionInformation();
ASSERT_EQ(local_version_information.hci_version_, HciVersion::V_5_0);
ASSERT_EQ(local_version_information.hci_revision_, 0x1234);
ASSERT_EQ(local_version_information.lmp_version_, LmpVersion::V_4_2);
ASSERT_EQ(local_version_information.manufacturer_name_, 0xBAD);
ASSERT_EQ(local_version_information.lmp_subversion_, 0x5678);
- ASSERT_EQ(controller_->GetLeBufferSize().le_data_packet_length_, 0x16);
- ASSERT_EQ(controller_->GetLeBufferSize().total_num_le_packets_, 0x08);
- ASSERT_EQ(controller_->GetLeSupportedStates(), 0x001f123456789abe);
- ASSERT_EQ(controller_->GetLeMaximumDataLength().supported_max_tx_octets_, 0x12);
- ASSERT_EQ(controller_->GetLeMaximumDataLength().supported_max_tx_time_, 0x34);
- ASSERT_EQ(controller_->GetLeMaximumDataLength().supported_max_rx_octets_, 0x56);
- ASSERT_EQ(controller_->GetLeMaximumDataLength().supported_max_rx_time_, 0x78);
- ASSERT_EQ(controller_->GetLeMaximumAdvertisingDataLength(), 0x0672);
- ASSERT_EQ(controller_->GetLeNumberOfSupportedAdverisingSets(), 0xF0);
+ std::array<uint8_t, 64> supported_commands;
+ for (int i = 0; i < 37; i++) {
+ supported_commands[i] = 0xff;
+ }
+ for (int i = 37; i < 64; i++) {
+ supported_commands[i] = 0x00;
+ }
+ ASSERT_EQ(controller_->GetControllerLocalSupportedCommands(), supported_commands);
+ ASSERT_EQ(controller_->GetControllerLocalSupportedFeatures(), 0x012345678abcdef);
+ ASSERT_EQ(controller_->GetControllerLocalExtendedFeaturesMaxPageNumber(), 0x02);
+ ASSERT_EQ(controller_->GetControllerLocalExtendedFeatures(0), 0x012345678abcdef);
+ ASSERT_EQ(controller_->GetControllerLocalExtendedFeatures(1), 0x012345678abcdf0);
+ ASSERT_EQ(controller_->GetControllerLocalExtendedFeatures(2), 0x012345678abcdf1);
+ ASSERT_EQ(controller_->GetControllerLocalExtendedFeatures(100), 0x00);
+ ASSERT_EQ(controller_->GetControllerLeBufferSize().le_data_packet_length_, 0x16);
+ ASSERT_EQ(controller_->GetControllerLeBufferSize().total_num_le_packets_, 0x08);
+ ASSERT_EQ(controller_->GetControllerLeLocalSupportedFeatures(), 0x001f123456789abc);
+ ASSERT_EQ(controller_->GetControllerLeSupportedStates(), 0x001f123456789abe);
+ ASSERT_EQ(controller_->GetControllerLeMaximumDataLength().supported_max_tx_octets_, 0x12);
+ ASSERT_EQ(controller_->GetControllerLeMaximumDataLength().supported_max_rx_octets_, 0x56);
+ ASSERT_EQ(controller_->GetControllerLeMaximumAdvertisingDataLength(), 0x0672);
+ ASSERT_EQ(controller_->GetControllerLeNumberOfSupportedAdverisingSets(), 0xF0);
}
TEST_F(ControllerTest, read_write_local_name) {
- ASSERT_EQ(controller_->GetLocalName(), "DUT");
+ ASSERT_EQ(controller_->GetControllerLocalName(), "DUT");
controller_->WriteLocalName("New name");
- ASSERT_EQ(controller_->GetLocalName(), "New name");
+ ASSERT_EQ(controller_->GetControllerLocalName(), "New name");
}
TEST_F(ControllerTest, send_set_event_mask_command) {
@@ -333,7 +340,7 @@ TEST_F(ControllerTest, send_reset_command) {
controller_->Reset();
auto packet = test_hci_layer_->GetCommand(OpCode::RESET);
auto command = ResetView::Create(packet);
- ASSERT_TRUE(command.IsValid());
+ ASSERT(command.IsValid());
}
TEST_F(ControllerTest, send_set_event_filter_command) {
@@ -342,7 +349,7 @@ TEST_F(ControllerTest, send_set_event_filter_command) {
auto set_event_filter_view1 = SetEventFilterView::Create(packet);
auto set_event_filter_inquiry_result_view1 = SetEventFilterInquiryResultView::Create(set_event_filter_view1);
auto command1 = SetEventFilterInquiryResultAllDevicesView::Create(set_event_filter_inquiry_result_view1);
- ASSERT_TRUE(command1.IsValid());
+ ASSERT(command1.IsValid());
ClassOfDevice class_of_device({0xab, 0xcd, 0xef});
ClassOfDevice class_of_device_mask({0x12, 0x34, 0x56});
@@ -351,7 +358,7 @@ TEST_F(ControllerTest, send_set_event_filter_command) {
auto set_event_filter_view2 = SetEventFilterView::Create(packet);
auto set_event_filter_inquiry_result_view2 = SetEventFilterInquiryResultView::Create(set_event_filter_view2);
auto command2 = SetEventFilterInquiryResultClassOfDeviceView::Create(set_event_filter_inquiry_result_view2);
- ASSERT_TRUE(command2.IsValid());
+ ASSERT(command2.IsValid());
ASSERT_EQ(command2.GetClassOfDevice(), class_of_device);
Address bdaddr({0x12, 0x34, 0x56, 0x78, 0x9a, 0xbc});
@@ -360,7 +367,7 @@ TEST_F(ControllerTest, send_set_event_filter_command) {
auto set_event_filter_view3 = SetEventFilterView::Create(packet);
auto set_event_filter_connection_setup_view = SetEventFilterConnectionSetupView::Create(set_event_filter_view3);
auto command3 = SetEventFilterConnectionSetupAddressView::Create(set_event_filter_connection_setup_view);
- ASSERT_TRUE(command3.IsValid());
+ ASSERT(command3.IsValid());
ASSERT_EQ(command3.GetAddress(), bdaddr);
}
@@ -368,7 +375,7 @@ TEST_F(ControllerTest, send_host_buffer_size_command) {
controller_->HostBufferSize(0xFF00, 0xF1, 0xFF02, 0xFF03);
auto packet = test_hci_layer_->GetCommand(OpCode::HOST_BUFFER_SIZE);
auto command = HostBufferSizeView::Create(packet);
- ASSERT_TRUE(command.IsValid());
+ ASSERT(command.IsValid());
ASSERT_EQ(command.GetHostAclDataPacketLength(), 0xFF00);
ASSERT_EQ(command.GetHostSynchronousDataPacketLength(), 0xF1);
ASSERT_EQ(command.GetHostTotalNumAclDataPackets(), 0xFF02);
@@ -376,12 +383,11 @@ TEST_F(ControllerTest, send_host_buffer_size_command) {
}
TEST_F(ControllerTest, send_le_set_event_mask_command) {
- uint64_t new_le_event_mask = test_hci_layer_->event_mask - 1;
- controller_->LeSetEventMask(new_le_event_mask);
- // Send another command to make sure it was applied
- controller_->Reset();
- auto packet = test_hci_layer_->GetCommand(OpCode::RESET);
- ASSERT_EQ(new_le_event_mask, test_hci_layer_->le_event_mask);
+ controller_->LeSetEventMask(0x000000000000001F);
+ auto packet = test_hci_layer_->GetCommand(OpCode::LE_SET_EVENT_MASK);
+ auto command = LeSetEventMaskView::Create(packet);
+ ASSERT(command.IsValid());
+ ASSERT_EQ(command.GetLeEventMask(), 0x000000000000001F);
}
TEST_F(ControllerTest, is_supported_test) {
@@ -394,32 +400,36 @@ TEST_F(ControllerTest, is_supported_test) {
}
TEST_F(ControllerTest, feature_spec_version_055_test) {
- EXPECT_EQ(controller_->GetVendorCapabilities().version_supported_, 55);
+ EXPECT_EQ(controller_->GetControllerVendorCapabilities().version_supported_, 55);
EXPECT_TRUE(controller_->IsSupported(OpCode::LE_MULTI_ADVT));
+ EXPECT_FALSE(controller_->IsSupported(OpCode::LE_TRACK_ADV));
EXPECT_FALSE(controller_->IsSupported(OpCode::CONTROLLER_DEBUG_INFO));
EXPECT_FALSE(controller_->IsSupported(OpCode::CONTROLLER_A2DP_OPCODE));
feature_spec_version = 95;
}
TEST_F(ControllerTest, feature_spec_version_095_test) {
- EXPECT_EQ(controller_->GetVendorCapabilities().version_supported_, 95);
+ EXPECT_EQ(controller_->GetControllerVendorCapabilities().version_supported_, 95);
EXPECT_TRUE(controller_->IsSupported(OpCode::LE_MULTI_ADVT));
+ EXPECT_TRUE(controller_->IsSupported(OpCode::LE_TRACK_ADV));
EXPECT_FALSE(controller_->IsSupported(OpCode::CONTROLLER_DEBUG_INFO));
EXPECT_FALSE(controller_->IsSupported(OpCode::CONTROLLER_A2DP_OPCODE));
feature_spec_version = 96;
}
TEST_F(ControllerTest, feature_spec_version_096_test) {
- EXPECT_EQ(controller_->GetVendorCapabilities().version_supported_, 96);
+ EXPECT_EQ(controller_->GetControllerVendorCapabilities().version_supported_, 96);
EXPECT_TRUE(controller_->IsSupported(OpCode::LE_MULTI_ADVT));
+ EXPECT_TRUE(controller_->IsSupported(OpCode::LE_TRACK_ADV));
EXPECT_FALSE(controller_->IsSupported(OpCode::CONTROLLER_DEBUG_INFO));
EXPECT_FALSE(controller_->IsSupported(OpCode::CONTROLLER_A2DP_OPCODE));
feature_spec_version = 98;
}
TEST_F(ControllerTest, feature_spec_version_098_test) {
- EXPECT_EQ(controller_->GetVendorCapabilities().version_supported_, 98);
+ EXPECT_EQ(controller_->GetControllerVendorCapabilities().version_supported_, 98);
EXPECT_TRUE(controller_->IsSupported(OpCode::LE_MULTI_ADVT));
+ EXPECT_TRUE(controller_->IsSupported(OpCode::LE_TRACK_ADV));
EXPECT_FALSE(controller_->IsSupported(OpCode::CONTROLLER_DEBUG_INFO));
EXPECT_TRUE(controller_->IsSupported(OpCode::CONTROLLER_A2DP_OPCODE));
}
@@ -443,25 +453,13 @@ void CheckReceivedCredits(uint16_t handle, uint16_t credits) {
}
TEST_F(ControllerTest, aclCreditCallbacksTest) {
- controller_->RegisterCompletedAclPacketsCallback(client_handler_->Bind(&CheckReceivedCredits));
+ controller_->RegisterCompletedAclPacketsCallback(common::Bind(&CheckReceivedCredits), client_handler_);
test_hci_layer_->IncomingCredit();
credits1_set.get_future().wait();
credits2_set.get_future().wait();
}
-
-TEST_F(ControllerTest, aclCreditCallbackListenerUnregistered) {
- os::Thread thread("test_thread", os::Thread::Priority::NORMAL);
- os::Handler handler(&thread);
- controller_->RegisterCompletedAclPacketsCallback(handler.Bind(&CheckReceivedCredits));
-
- handler.Clear();
- handler.WaitUntilStopped(std::chrono::milliseconds(100));
- controller_->UnregisterCompletedAclPacketsCallback();
-
- test_hci_layer_->IncomingCredit();
-}
} // namespace
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/device.cc b/gd/hci/device.cc
new file mode 100644
index 000000000..d008daec1
--- /dev/null
+++ b/gd/hci/device.cc
@@ -0,0 +1,32 @@
+/******************************************************************************
+ *
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+#include "hci/device.h"
+
+using namespace bluetooth::hci;
+
+std::string Device::generate_uid() {
+ // TODO(optedoblivion): Figure out a good way to do this for what we want
+ // to do
+ // TODO(optedoblivion): Need to make a way to override something for LE pub addr case
+ // Not sure if something like this is needed, but here is the idea (I think it came from mylesgw)
+ // CLASSIC: have all 0s in front for classic then have private address
+ // LE: have first public address in front then all 0s
+ // LE: have first public address in front then private address
+ //
+ return address_.ToString();
+}
diff --git a/gd/hci/device.h b/gd/hci/device.h
new file mode 100644
index 000000000..8324d00e8
--- /dev/null
+++ b/gd/hci/device.h
@@ -0,0 +1,136 @@
+/******************************************************************************
+ *
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+#pragma once
+
+#include <string>
+
+#include "hci/address.h"
+#include "hci/class_of_device.h"
+
+namespace bluetooth::hci {
+
+/**
+ * Used to determine device functionality
+ */
+enum DeviceType { DUAL, CLASSIC, LE };
+
+/**
+ * Represents a physical HCI device.
+ *
+ * <p>Contains all of the metadata required to represent a phycial device.
+ *
+ * <p>Devices should only be created and modified by HCI.
+ */
+class Device {
+ public:
+ virtual ~Device() = default;
+
+ Address GetAddress() const {
+ return address_;
+ }
+
+ /**
+ * Returns 1 of 3 enum values for device's type (DUAL, CLASSIC, LE)
+ */
+ DeviceType GetDeviceType() const {
+ return device_type_;
+ }
+
+ /**
+ * Unique identifier for bluetooth devices
+ *
+ * @return string representation of the uuid
+ */
+ std::string /** use UUID when ported */ GetUuid() {
+ return uid_;
+ }
+
+ std::string GetName() {
+ return name_;
+ }
+
+ ClassOfDevice GetClassOfDevice() {
+ return class_of_device_;
+ }
+
+ bool IsBonded() {
+ return is_bonded_;
+ }
+
+ bool operator==(const Device& rhs) const {
+ return this->uid_ == rhs.uid_ && this->address_ == rhs.address_ && this->device_type_ == rhs.device_type_ &&
+ this->is_bonded_ == rhs.is_bonded_;
+ }
+
+ protected:
+ friend class DeviceDatabase;
+ friend class DualDevice;
+
+ /**
+ * @param raw_address the address of the device
+ * @param device_type specify the type of device to create
+ */
+ Device(Address address, DeviceType device_type)
+ : address_(address), device_type_(device_type), uid_(generate_uid()), name_(""), class_of_device_() {}
+
+ /**
+ * Called only by friend class DeviceDatabase
+ *
+ * @param address
+ */
+ virtual void SetAddress(Address address) {
+ address_ = address;
+ uid_ = generate_uid();
+ }
+
+ /**
+ * Set the type of the device.
+ *
+ * <p>Needed by dual mode to arbitrarily set the valure to DUAL for corresponding LE/Classic devices
+ *
+ * @param type of device
+ */
+ void SetDeviceType(DeviceType type) {
+ device_type_ = type;
+ }
+
+ void SetName(std::string& name) {
+ name_ = name;
+ }
+
+ void SetClassOfDevice(ClassOfDevice class_of_device) {
+ class_of_device_ = class_of_device;
+ }
+
+ void SetIsBonded(bool is_bonded) {
+ is_bonded_ = is_bonded;
+ }
+
+ private:
+ Address address_{Address::kEmpty};
+ DeviceType device_type_;
+ std::string uid_;
+ std::string name_;
+ ClassOfDevice class_of_device_;
+ bool is_bonded_ = false;
+
+ /* Uses specific information about the device to calculate a UID */
+ std::string generate_uid();
+};
+
+} // namespace bluetooth::hci
diff --git a/gd/hci/device_database.cc b/gd/hci/device_database.cc
new file mode 100644
index 000000000..0027074f4
--- /dev/null
+++ b/gd/hci/device_database.cc
@@ -0,0 +1,276 @@
+/******************************************************************************
+ *
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+#include "hci/device_database.h"
+
+#include <memory>
+#include <utility>
+
+#include "hci/classic_device.h"
+#include "hci/dual_device.h"
+#include "hci/le_device.h"
+#include "os/log.h"
+
+using namespace bluetooth::hci;
+
+std::shared_ptr<ClassicDevice> DeviceDatabase::CreateClassicDevice(Address address) {
+ ClassicDevice device(address);
+ const std::string uuid = device.GetUuid();
+ AddDeviceToMap(std::move(device));
+ return GetClassicDevice(uuid);
+}
+
+std::shared_ptr<LeDevice> DeviceDatabase::CreateLeDevice(Address address) {
+ LeDevice device(address);
+ const std::string uuid = device.GetUuid();
+ AddDeviceToMap(std::move(device));
+ return GetLeDevice(uuid);
+}
+
+std::shared_ptr<DualDevice> DeviceDatabase::CreateDualDevice(Address address) {
+ auto classic = CreateClassicDevice(address);
+ auto le = CreateLeDevice(address);
+ if (classic && le) {
+ DualDevice device(address, classic, le);
+ std::string uuid = device.GetUuid();
+ AddDeviceToMap(std::move(device));
+ return GetDualDevice(uuid);
+ }
+ LOG_WARN("Attempting to instert a DUAL device that already exists!");
+ return std::shared_ptr<DualDevice>();
+}
+
+bool DeviceDatabase::RemoveDevice(const std::shared_ptr<Device>& device) {
+ const DeviceType type = device->GetDeviceType();
+ bool success;
+ switch (type) {
+ case CLASSIC:
+ success = false;
+ {
+ std::lock_guard<std::mutex> lock(device_map_mutex_);
+ auto classic_it = classic_device_map_.find(device->GetUuid());
+ // If we have a record with the same key
+ if (classic_it != classic_device_map_.end()) {
+ classic_device_map_.erase(device->GetUuid());
+ success = true;
+ }
+ }
+ if (success) {
+ ASSERT_LOG(WriteToDisk(), "Failed to write data to disk!");
+ } else {
+ LOG_WARN("Device not in database!");
+ }
+ return success;
+ case LE:
+ success = false;
+ {
+ std::lock_guard<std::mutex> lock(device_map_mutex_);
+ auto le_it = le_device_map_.find(device->GetUuid());
+ // If we have a record with the same key
+ if (le_it != le_device_map_.end()) {
+ le_device_map_.erase(device->GetUuid());
+ success = true;
+ }
+ }
+ if (success) {
+ ASSERT_LOG(WriteToDisk(), "Failed to write data to disk!");
+ } else {
+ LOG_WARN("Device not in database!");
+ }
+ return success;
+ case DUAL:
+ std::shared_ptr<DualDevice> dual_device = nullptr;
+ {
+ std::lock_guard<std::mutex> lock(device_map_mutex_);
+ auto dual_it = dual_device_map_.find(device->GetUuid());
+ if (dual_it != dual_device_map_.end()) {
+ dual_device = GetDualDevice(device->GetUuid());
+ }
+ }
+ success = false;
+ if (dual_device != nullptr) {
+ if (RemoveDevice(dual_device->GetClassicDevice()) && RemoveDevice(dual_device->GetLeDevice())) {
+ dual_device_map_.erase(device->GetUuid());
+ success = true;
+ }
+ }
+ if (success) {
+ ASSERT_LOG(WriteToDisk(), "Failed to write data to disk!");
+ } else {
+ LOG_WARN("Device not in database!");
+ }
+ return success;
+ }
+}
+
+std::shared_ptr<ClassicDevice> DeviceDatabase::GetClassicDevice(const std::string& uuid) {
+ std::lock_guard<std::mutex> lock(device_map_mutex_);
+ auto it = classic_device_map_.find(uuid);
+ if (it != classic_device_map_.end()) {
+ return it->second;
+ }
+ LOG_WARN("Device '%s' not found!", uuid.c_str());
+ return std::shared_ptr<ClassicDevice>();
+}
+
+std::shared_ptr<LeDevice> DeviceDatabase::GetLeDevice(const std::string& uuid) {
+ std::lock_guard<std::mutex> lock(device_map_mutex_);
+ auto it = le_device_map_.find(uuid);
+ if (it != le_device_map_.end()) {
+ return it->second;
+ }
+ LOG_WARN("Device '%s' not found!", uuid.c_str());
+ return std::shared_ptr<LeDevice>();
+}
+
+std::shared_ptr<DualDevice> DeviceDatabase::GetDualDevice(const std::string& uuid) {
+ std::lock_guard<std::mutex> lock(device_map_mutex_);
+ auto it = dual_device_map_.find(uuid);
+ if (it != dual_device_map_.end()) {
+ return it->second;
+ }
+ LOG_WARN("Device '%s' not found!", uuid.c_str());
+ return std::shared_ptr<DualDevice>();
+}
+
+bool DeviceDatabase::UpdateDeviceAddress(const std::shared_ptr<Device>& device, Address new_address) {
+ // Hold onto device
+ const DeviceType type = device->GetDeviceType();
+ if (type == CLASSIC) {
+ auto classic_device = GetClassicDevice(device->GetUuid());
+ // This gets rid of the shared_ptr in the map
+ ASSERT_LOG(RemoveDevice(device), "Failed to remove the device!");
+ classic_device->SetAddress(new_address);
+ // Move the value located at the pointer
+ return AddDeviceToMap(std::move(*(classic_device.get())));
+ } else if (type == LE) {
+ auto le_device = GetLeDevice(device->GetUuid());
+ // This gets rid of the shared_ptr in the map
+ ASSERT_LOG(RemoveDevice(device), "Failed to remove the device!");
+ le_device->SetAddress(new_address);
+ // Move the value located at the pointer
+ return AddDeviceToMap(std::move(*(le_device.get())));
+ } else if (type == DUAL) {
+ auto dual_device = GetDualDevice(device->GetUuid());
+ // This gets rid of the shared_ptr in the map
+ ASSERT_LOG(RemoveDevice(device), "Failed to remove the device!");
+ dual_device->SetAddress(new_address);
+ // Move the value located at the pointer
+ return AddDeviceToMap(std::move(*(dual_device.get())));
+ }
+ LOG_ALWAYS_FATAL("Someone added a device type but didn't account for it here.");
+ return false;
+}
+
+bool DeviceDatabase::AddDeviceToMap(ClassicDevice&& device) {
+ const std::string uuid = device.GetUuid();
+ bool success = false;
+ {
+ std::lock_guard<std::mutex> lock(device_map_mutex_);
+ auto it = classic_device_map_.find(device.GetUuid());
+ // If we have a record with the same key
+ if (it != classic_device_map_.end()) {
+ // We don't want to insert and overwrite
+ return false;
+ }
+ std::shared_ptr<ClassicDevice> device_ptr = std::make_shared<ClassicDevice>(std::move(device));
+ // returning the boolean value of insert success
+ if (classic_device_map_
+ .insert(std::pair<std::string, std::shared_ptr<ClassicDevice>>(device_ptr->GetUuid(), device_ptr))
+ .second) {
+ success = true;
+ }
+ }
+ if (success) {
+ ASSERT_LOG(WriteToDisk(), "Failed to write data to disk!");
+ } else {
+ LOG_WARN("Failed to add device '%s' to map.", uuid.c_str());
+ }
+ return success;
+}
+
+bool DeviceDatabase::AddDeviceToMap(LeDevice&& device) {
+ const std::string uuid = device.GetUuid();
+ bool success = false;
+ {
+ std::lock_guard<std::mutex> lock(device_map_mutex_);
+ auto it = le_device_map_.find(device.GetUuid());
+ // If we have a record with the same key
+ if (it != le_device_map_.end()) {
+ // We don't want to insert and overwrite
+ return false;
+ }
+ std::shared_ptr<LeDevice> device_ptr = std::make_shared<LeDevice>(std::move(device));
+ // returning the boolean value of insert success
+ if (le_device_map_.insert(std::pair<std::string, std::shared_ptr<LeDevice>>(device_ptr->GetUuid(), device_ptr))
+ .second) {
+ success = true;
+ }
+ }
+ if (success) {
+ ASSERT_LOG(WriteToDisk(), "Failed to write data to disk!");
+ } else {
+ LOG_WARN("Failed to add device '%s' to map.", uuid.c_str());
+ }
+ return success;
+}
+
+bool DeviceDatabase::AddDeviceToMap(DualDevice&& device) {
+ const std::string uuid = device.GetUuid();
+ bool success = false;
+ {
+ std::lock_guard<std::mutex> lock(device_map_mutex_);
+ auto it = dual_device_map_.find(device.GetUuid());
+ // If we have a record with the same key
+ if (it != dual_device_map_.end()) {
+ // We don't want to insert and overwrite
+ return false;
+ }
+ std::shared_ptr<DualDevice> device_ptr = std::make_shared<DualDevice>(std::move(device));
+ // returning the boolean value of insert success
+ if (dual_device_map_.insert(std::pair<std::string, std::shared_ptr<DualDevice>>(device_ptr->GetUuid(), device_ptr))
+ .second) {
+ success = true;
+ }
+ }
+ if (success) {
+ ASSERT_LOG(WriteToDisk(), "Failed to write data to disk!");
+ } else {
+ LOG_WARN("Failed to add device '%s' to map.", uuid.c_str());
+ }
+ return success;
+}
+
+bool DeviceDatabase::WriteToDisk() {
+ // TODO(optedoblivion): Implement
+ // TODO(optedoblivion): FIX ME!
+ // If synchronous stack dies before async write, we can miss adding device
+ // post(WriteToDisk());
+ // Current Solution: Synchronous disk I/O...
+ std::lock_guard<std::mutex> lock(device_map_mutex_);
+ // Collect information to sync to database
+ // Create SQL query for insert/update
+ // submit SQL
+ return true;
+}
+
+bool DeviceDatabase::ReadFromDisk() {
+ // TODO(optedoblivion): Implement
+ // Current Solution: Synchronous disk I/O...
+ std::lock_guard<std::mutex> lock(device_map_mutex_);
+ return true;
+}
diff --git a/gd/hci/device_database.h b/gd/hci/device_database.h
new file mode 100644
index 000000000..88434a432
--- /dev/null
+++ b/gd/hci/device_database.h
@@ -0,0 +1,149 @@
+/******************************************************************************
+ *
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+#pragma once
+
+#include <map>
+#include <mutex>
+
+#include "hci/classic_device.h"
+#include "hci/device.h"
+#include "hci/dual_device.h"
+#include "hci/le_device.h"
+#include "os/log.h"
+
+namespace bluetooth::hci {
+
+/**
+ * Stores all of the paired or connected devices in the database.
+ *
+ * <p>If a device is stored here it is actively being used by the stack.
+ *
+ * <p>This database is not meant for scan results.
+ */
+class DeviceDatabase {
+ public:
+ DeviceDatabase() : classic_device_map_(), le_device_map_(), dual_device_map_() {
+ if (!ReadFromDisk()) {
+ LOG_WARN("First boot or missing data!");
+ }
+ }
+
+ /**
+ * Adds a device to the internal memory map and triggers a WriteToDisk.
+ *
+ * @param address private address for device
+ * @return weak pointer to the device or empty pointer if device already exists
+ */
+ std::shared_ptr<ClassicDevice> CreateClassicDevice(Address address);
+
+ /**
+ * Adds a device to the internal memory map and triggers a WriteToDisk.
+ *
+ * @param address private address for device
+ * @return weak pointer to the device or empty pointer if device already exists
+ */
+ std::shared_ptr<LeDevice> CreateLeDevice(Address address);
+
+ /**
+ * Adds a device to the internal memory map and triggers a WriteToDisk.
+ *
+ * @param address private address for device
+ * @return weak pointer to the device or empty pointer if device already exists
+ */
+ std::shared_ptr<DualDevice> CreateDualDevice(Address address);
+
+ /**
+ * Fetches a Classic Device matching the given uuid.
+ *
+ * @param uuid generated uuid from a Device
+ * @return a weak reference to the matching Device or empty shared_ptr (nullptr)
+ */
+ std::shared_ptr<ClassicDevice> GetClassicDevice(const std::string& uuid);
+
+ /**
+ * Fetches a Le Device matching the given uuid.
+ *
+ * @param uuid generated uuid from a Device
+ * @return a weak reference to the matching Device or empty shared_ptr (nullptr)
+ */
+ std::shared_ptr<LeDevice> GetLeDevice(const std::string& uuid);
+
+ /**
+ * Fetches a Dual Device matching the given uuid.
+ *
+ * @param uuid generated uuid from a Device
+ * @return a weak reference to the matching Device or empty shared_ptr (nullptr)
+ */
+ std::shared_ptr<DualDevice> GetDualDevice(const std::string& uuid);
+
+ /**
+ * Removes a device from the internal database.
+ *
+ * @param device weak pointer to device to remove from the database
+ * @return <code>true</code> if the device is removed
+ */
+ bool RemoveDevice(const std::shared_ptr<Device>& device);
+
+ /**
+ * Changes an address for a device.
+ *
+ * Also fixes the key mapping for the device.
+ *
+ * @param new_address this will replace the existing address
+ * @return <code>true</code> if updated
+ */
+ bool UpdateDeviceAddress(const std::shared_ptr<Device>& device, Address new_address);
+
+ // TODO(optedoblivion): Make interfaces for device modification
+ // We want to keep the device modification encapsulated to the DeviceDatabase.
+ // Pass around shared_ptr to device, device metadata only accessible via Getters.
+ // Choices:
+ // a) Have Getters/Setters on device object
+ // b) Have Getters/Setters on device database accepting a device object
+ // c) Have Getters on device object and Setters on device database accepting a device object
+ // I chose to go with option c for now as I think it is the best option.
+
+ /**
+ * Fetches a list of classic devices.
+ *
+ * @return vector of weak pointers to classic devices
+ */
+ std::vector<std::shared_ptr<Device>> GetClassicDevices();
+
+ /**
+ * Fetches a list of le devices
+ *
+ * @return vector of weak pointers to le devices
+ */
+ std::vector<std::shared_ptr<Device>> GetLeDevices();
+
+ private:
+ std::mutex device_map_mutex_;
+ std::map<std::string, std::shared_ptr<ClassicDevice>> classic_device_map_;
+ std::map<std::string, std::shared_ptr<LeDevice>> le_device_map_;
+ std::map<std::string, std::shared_ptr<DualDevice>> dual_device_map_;
+
+ bool AddDeviceToMap(ClassicDevice&& device);
+ bool AddDeviceToMap(LeDevice&& device);
+ bool AddDeviceToMap(DualDevice&& device);
+
+ bool WriteToDisk();
+ bool ReadFromDisk();
+};
+
+} // namespace bluetooth::hci
diff --git a/gd/hci/device_database_test.cc b/gd/hci/device_database_test.cc
new file mode 100644
index 000000000..330571dc9
--- /dev/null
+++ b/gd/hci/device_database_test.cc
@@ -0,0 +1,134 @@
+/******************************************************************************
+ *
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+#include "device_database.h"
+#include "classic_device.h"
+
+#include <gtest/gtest.h>
+
+using namespace bluetooth::hci;
+
+namespace bluetooth::hci {
+namespace {
+
+Address address({0x01, 0x02, 0x03, 0x04, 0x05, 0x06});
+std::string address_str = "06:05:04:03:02:01";
+class DeviceDatabaseTest : public ::testing::Test {
+ protected:
+ DeviceDatabaseTest() = default;
+
+ void SetUp() override {}
+
+ void TearDown() override {}
+
+ DeviceDatabase device_database_;
+};
+
+TEST_F(DeviceDatabaseTest, create_classic_device) {
+ auto classic_device = device_database_.CreateClassicDevice(address);
+ ASSERT_TRUE(classic_device);
+ ASSERT_EQ(CLASSIC, classic_device->GetDeviceType());
+ ASSERT_EQ(address_str, classic_device->GetUuid());
+}
+
+TEST_F(DeviceDatabaseTest, create_le_device) {
+ auto le_device = device_database_.CreateLeDevice(address);
+ ASSERT_TRUE(le_device);
+ ASSERT_EQ(LE, le_device->GetDeviceType());
+ ASSERT_EQ(address_str, le_device->GetUuid());
+}
+
+TEST_F(DeviceDatabaseTest, create_dual_device) {
+ auto dual_device = device_database_.CreateDualDevice(address);
+ ASSERT_TRUE(dual_device);
+ ASSERT_EQ(DUAL, dual_device->GetDeviceType());
+ ASSERT_EQ(DUAL, dual_device->GetClassicDevice()->GetDeviceType());
+ ASSERT_EQ(DUAL, dual_device->GetLeDevice()->GetDeviceType());
+ ASSERT_EQ(address_str, dual_device->GetUuid());
+}
+
+// Shouldn't fail when creating twice. Should just get back a s_ptr the same device
+TEST_F(DeviceDatabaseTest, create_classic_device_twice) {
+ auto classic_device = device_database_.CreateClassicDevice(address);
+ ASSERT_TRUE(classic_device);
+ ASSERT_EQ(CLASSIC, classic_device->GetDeviceType());
+ ASSERT_EQ(address_str, classic_device->GetUuid());
+ ASSERT_TRUE(device_database_.CreateClassicDevice(address));
+}
+
+TEST_F(DeviceDatabaseTest, create_le_device_twice) {
+ auto le_device = device_database_.CreateLeDevice(address);
+ ASSERT_TRUE(le_device);
+ ASSERT_EQ(LE, le_device->GetDeviceType());
+ ASSERT_EQ(address_str, le_device->GetUuid());
+ ASSERT_TRUE(device_database_.CreateLeDevice(address));
+}
+
+TEST_F(DeviceDatabaseTest, create_dual_device_twice) {
+ auto dual_device = device_database_.CreateDualDevice(address);
+ ASSERT_TRUE(dual_device);
+
+ // Dual
+ ASSERT_EQ(DUAL, dual_device->GetDeviceType());
+ ASSERT_EQ(address_str, dual_device->GetUuid());
+
+ // Classic
+ ASSERT_EQ(DUAL, dual_device->GetClassicDevice()->GetDeviceType());
+ ASSERT_EQ(address_str, dual_device->GetClassicDevice()->GetUuid());
+
+ // LE
+ ASSERT_EQ(DUAL, dual_device->GetLeDevice()->GetDeviceType());
+ ASSERT_EQ(address_str, dual_device->GetLeDevice()->GetUuid());
+
+ ASSERT_TRUE(device_database_.CreateDualDevice(address));
+}
+
+TEST_F(DeviceDatabaseTest, remove_device) {
+ std::shared_ptr<Device> created_device = device_database_.CreateClassicDevice(address);
+ ASSERT_TRUE(created_device);
+ ASSERT_TRUE(device_database_.RemoveDevice(created_device));
+ ASSERT_TRUE(device_database_.CreateClassicDevice(address));
+}
+
+TEST_F(DeviceDatabaseTest, remove_device_twice) {
+ std::shared_ptr<Device> created_device = device_database_.CreateClassicDevice(address);
+ ASSERT_TRUE(device_database_.RemoveDevice(created_device));
+ ASSERT_FALSE(device_database_.RemoveDevice(created_device));
+}
+
+TEST_F(DeviceDatabaseTest, get_nonexistent_device) {
+ std::shared_ptr<Device> device_ptr = device_database_.GetClassicDevice(address_str);
+ ASSERT_FALSE(device_ptr);
+}
+
+TEST_F(DeviceDatabaseTest, address_modification_check) {
+ std::shared_ptr<Device> created_device = device_database_.CreateClassicDevice(address);
+ std::shared_ptr<Device> gotten_device = device_database_.GetClassicDevice(address.ToString());
+ ASSERT_TRUE(created_device);
+ ASSERT_TRUE(gotten_device);
+ ASSERT_EQ(address_str, created_device->GetAddress().ToString());
+ ASSERT_EQ(address_str, gotten_device->GetAddress().ToString());
+ device_database_.UpdateDeviceAddress(created_device, Address({0x01, 0x01, 0x01, 0x01, 0x01, 0x01}));
+ ASSERT_EQ("01:01:01:01:01:01", created_device->GetAddress().ToString());
+ ASSERT_EQ("01:01:01:01:01:01", gotten_device->GetAddress().ToString());
+ std::shared_ptr<Device> gotten_modified_device = device_database_.GetClassicDevice("01:01:01:01:01:01");
+ ASSERT_TRUE(gotten_modified_device);
+ ASSERT_TRUE(device_database_.RemoveDevice(gotten_modified_device));
+ ASSERT_FALSE(device_database_.GetClassicDevice("01:01:01:01:01:01"));
+}
+} // namespace
+} // namespace bluetooth::hci
diff --git a/gd/hci/device_test.cc b/gd/hci/device_test.cc
new file mode 100644
index 000000000..1b4fafc79
--- /dev/null
+++ b/gd/hci/device_test.cc
@@ -0,0 +1,101 @@
+/******************************************************************************
+ *
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+#include "device.h"
+#include "classic_device.h"
+
+#include <gtest/gtest.h>
+
+using namespace bluetooth::hci;
+
+static const char* test_addr_str = "bc:9a:78:56:34:12";
+static const uint8_t test_addr[] = {0x12, 0x34, 0x56, 0x78, 0x9a, 0xbc};
+static const Address address(test_addr);
+
+namespace bluetooth::hci {
+namespace {
+class TestableDevice : public Device {
+ public:
+ explicit TestableDevice(Address a) : Device(a, CLASSIC) {}
+
+ void SetTheAddress() {
+ Address a({0x01, 0x02, 0x03, 0x04, 0x05, 0x06});
+ this->SetAddress(a);
+ }
+ void SetTheClassOfDevice() {
+ ClassOfDevice class_of_device({0x01, 0x02, 0x03});
+ this->SetClassOfDevice(class_of_device);
+ }
+ void SetTheName() {
+ std::string name = "Some Name";
+ this->SetName(name);
+ }
+ void SetTheIsBonded() {
+ this->SetIsBonded(true);
+ }
+};
+class DeviceTest : public ::testing::Test {
+ public:
+ DeviceTest() : device_(Address(test_addr)) {}
+
+ protected:
+ void SetUp() override {}
+
+ void TearDown() override {}
+ TestableDevice device_;
+};
+
+TEST_F(DeviceTest, initial_integrity) {
+ ASSERT_STREQ(test_addr_str, device_.GetAddress().ToString().c_str());
+ ASSERT_STREQ(test_addr_str, device_.GetUuid().c_str());
+ ASSERT_EQ(DeviceType::CLASSIC, device_.GetDeviceType());
+ ASSERT_EQ("", device_.GetName());
+}
+
+TEST_F(DeviceTest, set_get_class_of_device) {
+ ClassOfDevice class_of_device({0x01, 0x02, 0x03});
+ ASSERT_NE(class_of_device, device_.GetClassOfDevice());
+ device_.SetTheClassOfDevice();
+ ASSERT_EQ(class_of_device, device_.GetClassOfDevice());
+}
+
+TEST_F(DeviceTest, set_get_name) {
+ std::string name = "Some Name";
+ ASSERT_EQ("", device_.GetName());
+ device_.SetTheName();
+ ASSERT_EQ(name, device_.GetName());
+}
+
+TEST_F(DeviceTest, operator_iseq) {
+ TestableDevice d(address);
+ EXPECT_EQ(device_, d);
+}
+
+TEST_F(DeviceTest, set_address) {
+ ASSERT_EQ(test_addr_str, device_.GetAddress().ToString());
+ device_.SetTheAddress();
+ ASSERT_EQ("06:05:04:03:02:01", device_.GetAddress().ToString());
+}
+
+TEST_F(DeviceTest, set_bonded) {
+ ASSERT_FALSE(device_.IsBonded());
+ device_.SetTheIsBonded();
+ ASSERT_TRUE(device_.IsBonded());
+}
+
+} // namespace
+} // namespace bluetooth::hci
diff --git a/gd/hci/dual_device.h b/gd/hci/dual_device.h
new file mode 100644
index 000000000..8d0801935
--- /dev/null
+++ b/gd/hci/dual_device.h
@@ -0,0 +1,60 @@
+/******************************************************************************
+ *
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+#pragma once
+
+#include "hci/classic_device.h"
+#include "hci/device.h"
+#include "hci/le_device.h"
+
+namespace bluetooth::hci {
+
+/**
+ * A device representing a DUAL device.
+ *
+ * <p>This can be a DUAL only.
+ */
+class DualDevice : public Device {
+ public:
+ std::shared_ptr<Device> GetClassicDevice() {
+ return classic_device_;
+ }
+
+ std::shared_ptr<Device> GetLeDevice() {
+ return le_device_;
+ }
+
+ protected:
+ friend class DeviceDatabase;
+ DualDevice(Address address, std::shared_ptr<ClassicDevice> classic_device, std::shared_ptr<LeDevice> le_device)
+ : Device(address, DUAL), classic_device_(std::move(classic_device)), le_device_(std::move(le_device)) {
+ classic_device_->SetDeviceType(DUAL);
+ le_device_->SetDeviceType(DUAL);
+ }
+
+ void SetAddress(Address address) override {
+ Device::SetAddress(address);
+ GetClassicDevice()->SetAddress(address);
+ GetLeDevice()->SetAddress(address);
+ }
+
+ private:
+ std::shared_ptr<ClassicDevice> classic_device_;
+ std::shared_ptr<LeDevice> le_device_;
+};
+
+} // namespace bluetooth::hci
diff --git a/gd/hci/dual_device_test.cc b/gd/hci/dual_device_test.cc
new file mode 100644
index 000000000..1c4c2b01a
--- /dev/null
+++ b/gd/hci/dual_device_test.cc
@@ -0,0 +1,81 @@
+/******************************************************************************
+ *
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+#include "dual_device.h"
+#include "device.h"
+
+#include <gtest/gtest.h>
+
+using namespace bluetooth::hci;
+
+static const char* test_addr_str = "bc:9a:78:56:34:12";
+static const uint8_t test_addr[] = {0x12, 0x34, 0x56, 0x78, 0x9a, 0xbc};
+static const Address address(test_addr);
+
+namespace bluetooth::hci {
+namespace {
+class TestableClassicDevice : public ClassicDevice {
+ public:
+ explicit TestableClassicDevice(Address a) : ClassicDevice(a) {}
+};
+class TestableLeDevice : public LeDevice {
+ public:
+ explicit TestableLeDevice(Address a) : LeDevice(a) {}
+};
+class TestableDevice : public DualDevice {
+ public:
+ TestableDevice(Address a, std::shared_ptr<TestableClassicDevice>& classic_device,
+ std::shared_ptr<TestableLeDevice>& le_device)
+ : DualDevice(a, classic_device, le_device) {}
+
+ void SetTheAddress() {
+ Address a({0x01, 0x02, 0x03, 0x04, 0x05, 0x06});
+ this->SetAddress(a);
+ }
+};
+std::shared_ptr<TestableClassicDevice> classic_device = std::make_shared<TestableClassicDevice>(address);
+std::shared_ptr<TestableLeDevice> le_device = std::make_shared<TestableLeDevice>(address);
+class DualDeviceTest : public ::testing::Test {
+ public:
+ DualDeviceTest() : device_(Address(test_addr), classic_device, le_device) {}
+
+ protected:
+ void SetUp() override {}
+
+ void TearDown() override {}
+ TestableDevice device_;
+};
+
+TEST_F(DualDeviceTest, initial_integrity) {
+ Address a = device_.GetAddress();
+ ASSERT_EQ(test_addr_str, a.ToString());
+
+ ASSERT_EQ(DUAL, device_.GetClassicDevice()->GetDeviceType());
+ ASSERT_EQ(a.ToString(), device_.GetClassicDevice()->GetAddress().ToString());
+
+ ASSERT_EQ(DUAL, device_.GetLeDevice()->GetDeviceType());
+ ASSERT_EQ(a.ToString(), device_.GetLeDevice()->GetAddress().ToString());
+
+ device_.SetTheAddress();
+
+ ASSERT_EQ("06:05:04:03:02:01", device_.GetAddress().ToString());
+ ASSERT_EQ("06:05:04:03:02:01", device_.GetClassicDevice()->GetAddress().ToString());
+ ASSERT_EQ("06:05:04:03:02:01", device_.GetLeDevice()->GetAddress().ToString());
+}
+
+} // namespace
+} // namespace bluetooth::hci
diff --git a/gd/hci/enum_helper.h b/gd/hci/enum_helper.h
deleted file mode 100644
index adbc3c71e..000000000
--- a/gd/hci/enum_helper.h
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <type_traits>
-
-#include "common/strings.h"
-#include "hci/hci_packets.h"
-
-// Define new enums or parsers for existing enums
-namespace bluetooth {
-namespace hci {
-
-// Must be 0b00, 0b01, 0b10, and 0b11 as this is a bit mask
-enum DeviceType { UNKNOWN = 0, BR_EDR = 1, LE = 2, DUAL = 3 };
-
-// Scan mode from legacy stack, which is different from hci::ScanEnable
-enum LegacyScanMode { BT_SCAN_MODE_NONE = 0, BT_SCAN_MODE_CONNECTABLE = 1, BT_SCAN_MODE_CONNECTABLE_DISCOVERABLE = 2 };
-
-} // namespace hci
-
-// Must be defined in bluetooth namespace
-template <typename T, typename std::enable_if<std::is_same_v<T, hci::DeviceType>, int>::type = 0>
-std::optional<hci::DeviceType> FromLegacyConfigString(const std::string& str) {
- auto raw_value = common::Int64FromString(str);
- if (!raw_value) {
- return std::nullopt;
- }
- if (*raw_value < hci::DeviceType::UNKNOWN || *raw_value > hci::DeviceType::DUAL) {
- return std::nullopt;
- }
- return static_cast<hci::DeviceType>(*raw_value);
-}
-
-// Must be defined in bluetooth namespace
-template <typename T, typename std::enable_if<std::is_same_v<T, hci::AddressType>, int>::type = 0>
-std::optional<hci::AddressType> FromLegacyConfigString(const std::string& str) {
- auto raw_value = common::Int64FromString(str);
- if (!raw_value) {
- return std::nullopt;
- }
- if (*raw_value < static_cast<int64_t>(hci::AddressType::PUBLIC_DEVICE_ADDRESS) ||
- *raw_value > static_cast<int64_t>(hci::AddressType::RANDOM_IDENTITY_ADDRESS)) {
- return std::nullopt;
- }
- return static_cast<hci::AddressType>(*raw_value);
-}
-
-// Must be defined in bluetooth namespace
-template <typename T, typename std::enable_if<std::is_same_v<T, hci::KeyType>, int>::type = 0>
-std::optional<hci::KeyType> FromLegacyConfigString(const std::string& str) {
- auto raw_value = common::Int64FromString(str);
- if (!raw_value) {
- return std::nullopt;
- }
- if (*raw_value < static_cast<int64_t>(hci::KeyType::COMBINATION) ||
- *raw_value > static_cast<int64_t>(hci::KeyType::AUTHENTICATED_P256)) {
- return std::nullopt;
- }
- return static_cast<hci::KeyType>(*raw_value);
-}
-
-// Must be defined in bluetooth namespace
-template <typename T, typename std::enable_if<std::is_same_v<T, hci::LegacyScanMode>, int>::type = 0>
-std::optional<hci::LegacyScanMode> FromLegacyConfigString(const std::string& str) {
- auto raw_value = common::Int64FromString(str);
- if (!raw_value) {
- return std::nullopt;
- }
- if (*raw_value < static_cast<int64_t>(hci::LegacyScanMode::BT_SCAN_MODE_NONE) ||
- *raw_value > static_cast<int64_t>(hci::LegacyScanMode::BT_SCAN_MODE_CONNECTABLE_DISCOVERABLE)) {
- return std::nullopt;
- }
- return static_cast<hci::LegacyScanMode>(*raw_value);
-}
-
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/hci/facade/acl_manager_facade.cc b/gd/hci/facade/acl_manager_facade.cc
index 384426e49..35d8452e5 100644
--- a/gd/hci/facade/acl_manager_facade.cc
+++ b/gd/hci/facade/acl_manager_facade.cc
@@ -23,8 +23,6 @@
#include "common/bind.h"
#include "grpc/grpc_event_queue.h"
#include "hci/acl_manager.h"
-#include "hci/address.h"
-#include "hci/class_of_device.h"
#include "hci/facade/acl_manager_facade.grpc.pb.h"
#include "hci/facade/acl_manager_facade.pb.h"
#include "hci/hci_packets.h"
@@ -40,28 +38,26 @@ namespace bluetooth {
namespace hci {
namespace facade {
-using acl_manager::ClassicAclConnection;
-using acl_manager::ConnectionCallbacks;
-using acl_manager::ConnectionManagementCallbacks;
-
-class AclManagerFacadeService : public AclManagerFacade::Service, public ConnectionCallbacks {
+class AclManagerFacadeService : public AclManagerFacade::Service,
+ public ::bluetooth::hci::ConnectionCallbacks,
+ public ::bluetooth::hci::ConnectionManagementCallbacks,
+ public ::bluetooth::hci::AclManagerCallbacks {
public:
AclManagerFacadeService(AclManager* acl_manager, ::bluetooth::os::Handler* facade_handler)
: acl_manager_(acl_manager), facade_handler_(facade_handler) {
acl_manager_->RegisterCallbacks(this, facade_handler_);
+ acl_manager_->RegisterAclManagerCallbacks(this, facade_handler_);
}
- ~AclManagerFacadeService() {
+ ~AclManagerFacadeService() override {
std::unique_lock<std::mutex> lock(acl_connections_mutex_);
- for (auto& connection : acl_connections_) {
- connection.second.connection_->GetAclQueueEnd()->UnregisterDequeue();
+ for (auto connection : acl_connections_) {
+ connection.second->GetAclQueueEnd()->UnregisterDequeue();
}
}
- ::grpc::Status CreateConnection(
- ::grpc::ServerContext* context,
- const ConnectionMsg* request,
- ::grpc::ServerWriter<ConnectionEvent>* writer) override {
+ ::grpc::Status CreateConnection(::grpc::ServerContext* context, const ConnectionMsg* request,
+ ::grpc::ServerWriter<ConnectionEvent>* writer) override {
Address peer;
ASSERT(Address::FromString(request->address(), peer));
acl_manager_->CreateConnection(peer);
@@ -73,197 +69,34 @@ class AclManagerFacadeService : public AclManagerFacade::Service, public Connect
return per_connection_events_[current_connection_request_]->RunLoop(context, writer);
}
- ::grpc::Status Disconnect(
- ::grpc::ServerContext* context, const HandleMsg* request, ::google::protobuf::Empty* response) override {
+ ::grpc::Status Disconnect(::grpc::ServerContext* context, const HandleMsg* request,
+ ::google::protobuf::Empty* response) override {
std::unique_lock<std::mutex> lock(acl_connections_mutex_);
auto connection = acl_connections_.find(request->handle());
if (connection == acl_connections_.end()) {
LOG_ERROR("Invalid handle");
return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle");
} else {
- connection->second.connection_->Disconnect(DisconnectReason::REMOTE_USER_TERMINATED_CONNECTION);
+ connection->second->Disconnect(DisconnectReason::REMOTE_USER_TERMINATED_CONNECTION);
return ::grpc::Status::OK;
}
}
- ::grpc::Status AuthenticationRequested(
- ::grpc::ServerContext* context, const HandleMsg* request, ::google::protobuf::Empty* response) override {
+ ::grpc::Status AuthenticationRequested(::grpc::ServerContext* context, const HandleMsg* request,
+ ::google::protobuf::Empty* response) override {
std::unique_lock<std::mutex> lock(acl_connections_mutex_);
auto connection = acl_connections_.find(request->handle());
if (connection == acl_connections_.end()) {
LOG_ERROR("Invalid handle");
return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle");
} else {
- connection->second.connection_->AuthenticationRequested();
+ connection->second->AuthenticationRequested();
return ::grpc::Status::OK;
}
};
-#define GET_CONNECTION(view) \
- std::map<uint16_t, Connection>::iterator connection; \
- do { \
- if (!view.IsValid()) { \
- return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle"); \
- } \
- std::unique_lock<std::mutex> lock(acl_connections_mutex_); \
- connection = acl_connections_.find(view.GetConnectionHandle()); \
- if (connection == acl_connections_.end()) { \
- return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle"); \
- } \
- } while (0)
-
- ::grpc::Status ConnectionCommand(
- ::grpc::ServerContext* context,
- const ConnectionCommandMsg* request,
- ::google::protobuf::Empty* response) override {
- auto command_view =
- ConnectionManagementCommandView::Create(AclCommandView::Create(CommandView::Create(PacketView<kLittleEndian>(
- std::make_shared<std::vector<uint8_t>>(request->packet().begin(), request->packet().end())))));
- if (!command_view.IsValid()) {
- return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid command packet");
- }
- switch (command_view.GetOpCode()) {
- case OpCode::AUTHENTICATION_REQUESTED: {
- GET_CONNECTION(AuthenticationRequestedView::Create(command_view));
- connection->second.connection_->AuthenticationRequested();
- return ::grpc::Status::OK;
- }
- case OpCode::DISCONNECT: {
- auto view = DisconnectView::Create(command_view);
- GET_CONNECTION(view);
- connection->second.connection_->Disconnect(view.GetReason());
- return ::grpc::Status::OK;
- }
- case OpCode::CHANGE_CONNECTION_PACKET_TYPE: {
- auto view = ChangeConnectionPacketTypeView::Create(command_view);
- GET_CONNECTION(view);
- connection->second.connection_->ChangeConnectionPacketType(view.GetPacketType());
- return ::grpc::Status::OK;
- }
- case OpCode::SET_CONNECTION_ENCRYPTION: {
- auto view = SetConnectionEncryptionView::Create(command_view);
- GET_CONNECTION(view);
- connection->second.connection_->SetConnectionEncryption(view.GetEncryptionEnable());
- return ::grpc::Status::OK;
- }
- case OpCode::CHANGE_CONNECTION_LINK_KEY: {
- GET_CONNECTION(ChangeConnectionLinkKeyView::Create(command_view));
- connection->second.connection_->ChangeConnectionLinkKey();
- return ::grpc::Status::OK;
- }
- case OpCode::READ_CLOCK_OFFSET: {
- GET_CONNECTION(ReadClockOffsetView::Create(command_view));
- connection->second.connection_->ReadClockOffset();
- return ::grpc::Status::OK;
- }
- case OpCode::HOLD_MODE: {
- auto view = HoldModeView::Create(command_view);
- GET_CONNECTION(view);
- connection->second.connection_->HoldMode(view.GetHoldModeMaxInterval(), view.GetHoldModeMinInterval());
- return ::grpc::Status::OK;
- }
- case OpCode::SNIFF_MODE: {
- auto view = SniffModeView::Create(command_view);
- GET_CONNECTION(view);
- connection->second.connection_->SniffMode(
- view.GetSniffMaxInterval(), view.GetSniffMinInterval(), view.GetSniffAttempt(), view.GetSniffTimeout());
- return ::grpc::Status::OK;
- }
- case OpCode::EXIT_SNIFF_MODE: {
- GET_CONNECTION(ExitSniffModeView::Create(command_view));
- connection->second.connection_->ExitSniffMode();
- return ::grpc::Status::OK;
- }
- case OpCode::FLUSH: {
- GET_CONNECTION(FlushView::Create(command_view));
- connection->second.connection_->Flush();
- return ::grpc::Status::OK;
- }
- case OpCode::READ_AUTOMATIC_FLUSH_TIMEOUT: {
- GET_CONNECTION(ReadAutomaticFlushTimeoutView::Create(command_view));
- connection->second.connection_->ReadAutomaticFlushTimeout();
- return ::grpc::Status::OK;
- }
- case OpCode::WRITE_AUTOMATIC_FLUSH_TIMEOUT: {
- auto view = WriteAutomaticFlushTimeoutView::Create(command_view);
- GET_CONNECTION(view);
- connection->second.connection_->WriteAutomaticFlushTimeout(view.GetFlushTimeout());
- return ::grpc::Status::OK;
- }
- case OpCode::READ_TRANSMIT_POWER_LEVEL: {
- auto view = ReadTransmitPowerLevelView::Create(command_view);
- GET_CONNECTION(view);
- connection->second.connection_->ReadTransmitPowerLevel(view.GetTransmitPowerLevelType());
- return ::grpc::Status::OK;
- }
- case OpCode::READ_LINK_SUPERVISION_TIMEOUT: {
- GET_CONNECTION(ReadLinkSupervisionTimeoutView::Create(command_view));
- connection->second.connection_->ReadLinkSupervisionTimeout();
- return ::grpc::Status::OK;
- }
- case OpCode::WRITE_LINK_SUPERVISION_TIMEOUT: {
- auto view = WriteLinkSupervisionTimeoutView::Create(command_view);
- GET_CONNECTION(view);
- connection->second.connection_->WriteLinkSupervisionTimeout(view.GetLinkSupervisionTimeout());
- return ::grpc::Status::OK;
- }
- case OpCode::READ_FAILED_CONTACT_COUNTER: {
- GET_CONNECTION(ReadFailedContactCounterView::Create(command_view));
- connection->second.connection_->ReadFailedContactCounter();
- return ::grpc::Status::OK;
- }
- case OpCode::RESET_FAILED_CONTACT_COUNTER: {
- GET_CONNECTION(ResetFailedContactCounterView::Create(command_view));
- connection->second.connection_->ResetFailedContactCounter();
- return ::grpc::Status::OK;
- }
- case OpCode::READ_LINK_QUALITY: {
- GET_CONNECTION(ReadLinkQualityView::Create(command_view));
- connection->second.connection_->ReadLinkQuality();
- return ::grpc::Status::OK;
- }
- case OpCode::READ_AFH_CHANNEL_MAP: {
- GET_CONNECTION(ReadAfhChannelMapView::Create(command_view));
- connection->second.connection_->ReadAfhChannelMap();
- return ::grpc::Status::OK;
- }
- case OpCode::READ_RSSI: {
- GET_CONNECTION(ReadRssiView::Create(command_view));
- connection->second.connection_->ReadRssi();
- return ::grpc::Status::OK;
- }
- case OpCode::READ_CLOCK: {
- auto view = ReadClockView::Create(command_view);
- GET_CONNECTION(view);
- connection->second.connection_->ReadClock(view.GetWhichClock());
- return ::grpc::Status::OK;
- }
- case OpCode::READ_REMOTE_VERSION_INFORMATION: {
- GET_CONNECTION(ReadRemoteVersionInformationView::Create(command_view));
- connection->second.connection_->ReadRemoteVersionInformation();
- return ::grpc::Status::OK;
- }
- case OpCode::READ_REMOTE_SUPPORTED_FEATURES: {
- GET_CONNECTION(ReadRemoteSupportedFeaturesView::Create(command_view));
- connection->second.connection_->ReadRemoteSupportedFeatures();
- return ::grpc::Status::OK;
- }
- case OpCode::READ_REMOTE_EXTENDED_FEATURES: {
- GET_CONNECTION(ReadRemoteExtendedFeaturesView::Create(command_view));
- uint8_t page_number = 0;
- connection->second.connection_->ReadRemoteExtendedFeatures(page_number);
- return ::grpc::Status::OK;
- }
- default:
- return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid command packet");
- }
- }
-#undef GET_CONNECTION
-
- ::grpc::Status FetchIncomingConnection(
- ::grpc::ServerContext* context,
- const google::protobuf::Empty* request,
- ::grpc::ServerWriter<ConnectionEvent>* writer) override {
+ ::grpc::Status FetchIncomingConnection(::grpc::ServerContext* context, const google::protobuf::Empty* request,
+ ::grpc::ServerWriter<ConnectionEvent>* writer) override {
if (per_connection_events_.size() > current_connection_request_) {
return ::grpc::Status(::grpc::StatusCode::RESOURCE_EXHAUSTED, "Only one outstanding connection is supported");
}
@@ -272,49 +105,37 @@ class AclManagerFacadeService : public AclManagerFacade::Service, public Connect
return per_connection_events_[current_connection_request_]->RunLoop(context, writer);
}
- ::grpc::Status SendAclData(
- ::grpc::ServerContext* context, const AclData* request, ::google::protobuf::Empty* response) override {
+ ::grpc::Status SendAclData(::grpc::ServerContext* context, const AclData* request,
+ ::google::protobuf::Empty* response) override {
std::promise<void> promise;
auto future = promise.get_future();
{
std::unique_lock<std::mutex> lock(acl_connections_mutex_);
auto connection = acl_connections_.find(request->handle());
if (connection == acl_connections_.end()) {
+ LOG_ERROR("Invalid handle");
return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle");
- }
- // TODO: This is unsafe because connection may have gone
- connection->second.connection_->GetAclQueueEnd()->RegisterEnqueue(
- facade_handler_,
- common::Bind(
- &AclManagerFacadeService::enqueue_packet,
- common::Unretained(this),
- common::Unretained(request),
- common::Passed(std::move(promise))));
- auto status = future.wait_for(std::chrono::milliseconds(1000));
- if (status != std::future_status::ready) {
- return ::grpc::Status(::grpc::StatusCode::RESOURCE_EXHAUSTED, "Can't send packet");
+ } else {
+ connection->second->GetAclQueueEnd()->RegisterEnqueue(
+ facade_handler_, common::Bind(&AclManagerFacadeService::enqueue_packet, common::Unretained(this),
+ common::Unretained(request), common::Passed(std::move(promise))));
}
}
+ future.wait();
return ::grpc::Status::OK;
}
std::unique_ptr<BasePacketBuilder> enqueue_packet(const AclData* request, std::promise<void> promise) {
- auto connection = acl_connections_.find(request->handle());
- ASSERT_LOG(connection != acl_connections_.end(), "handle %d", request->handle());
- connection->second.connection_->GetAclQueueEnd()->UnregisterEnqueue();
+ acl_connections_[request->handle()]->GetAclQueueEnd()->UnregisterEnqueue();
std::unique_ptr<RawBuilder> packet =
std::make_unique<RawBuilder>(std::vector<uint8_t>(request->payload().begin(), request->payload().end()));
promise.set_value();
return packet;
}
- ::grpc::Status FetchAclData(
- ::grpc::ServerContext* context, const HandleMsg* request, ::grpc::ServerWriter<AclData>* writer) override {
- auto connection = acl_connections_.find(request->handle());
- if (connection == acl_connections_.end()) {
- return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle");
- }
- return connection->second.pending_acl_data_.RunLoop(context, writer);
+ ::grpc::Status FetchAclData(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
+ ::grpc::ServerWriter<AclData>* writer) override {
+ return pending_acl_data_.RunLoop(context, writer);
}
static inline uint16_t to_handle(uint32_t current_request) {
@@ -328,232 +149,157 @@ class AclManagerFacadeService : public AclManagerFacade::Service, public Connect
return std::string(bytes.begin(), bytes.end());
}
- void on_incoming_acl(std::shared_ptr<ClassicAclConnection> connection, uint16_t handle) {
+ void on_incoming_acl(std::shared_ptr<AclConnection> connection, uint16_t handle) {
auto packet = connection->GetAclQueueEnd()->TryDequeue();
- auto connection_tracker = acl_connections_.find(handle);
- ASSERT_LOG(connection_tracker != acl_connections_.end(), "handle %d", handle);
AclData acl_data;
acl_data.set_handle(handle);
acl_data.set_payload(std::string(packet->begin(), packet->end()));
- connection_tracker->second.pending_acl_data_.OnIncomingEvent(acl_data);
+ pending_acl_data_.OnIncomingEvent(acl_data);
}
- void OnConnectSuccess(std::unique_ptr<ClassicAclConnection> connection) override {
+ void on_disconnect(std::shared_ptr<AclConnection> connection, uint32_t entry, ErrorCode code) {
+ connection->GetAclQueueEnd()->UnregisterDequeue();
+ connection->Finish();
+ std::unique_ptr<BasePacketBuilder> builder =
+ DisconnectBuilder::Create(to_handle(entry), static_cast<DisconnectReason>(code));
+ ConnectionEvent disconnection;
+ disconnection.set_event(builder_to_string(std::move(builder)));
+ per_connection_events_[entry]->OnIncomingEvent(disconnection);
+ }
+
+ void OnConnectSuccess(std::unique_ptr<::bluetooth::hci::AclConnection> connection) override {
std::unique_lock<std::mutex> lock(acl_connections_mutex_);
- std::shared_ptr<ClassicAclConnection> shared_connection = std::move(connection);
- uint16_t handle = to_handle(current_connection_request_);
- acl_connections_.emplace(
- std::piecewise_construct,
- std::forward_as_tuple(handle),
- std::forward_as_tuple(handle, shared_connection, per_connection_events_[current_connection_request_]));
+ auto addr = connection->GetAddress();
+ std::shared_ptr<::bluetooth::hci::AclConnection> shared_connection = std::move(connection);
+ acl_connections_.emplace(to_handle(current_connection_request_), shared_connection);
+ auto remote_address = shared_connection->GetAddress().ToString();
shared_connection->GetAclQueueEnd()->RegisterDequeue(
- facade_handler_,
- common::Bind(&AclManagerFacadeService::on_incoming_acl, common::Unretained(this), shared_connection, handle));
- auto callbacks = acl_connections_.find(handle)->second.GetCallbacks();
- shared_connection->RegisterCallbacks(callbacks, facade_handler_);
- auto addr = shared_connection->GetAddress();
- std::unique_ptr<BasePacketBuilder> builder =
- ConnectionCompleteBuilder::Create(ErrorCode::SUCCESS, handle, addr, LinkType::ACL, Enable::DISABLED);
+ facade_handler_, common::Bind(&AclManagerFacadeService::on_incoming_acl, common::Unretained(this),
+ shared_connection, to_handle(current_connection_request_)));
+ shared_connection->RegisterDisconnectCallback(
+ common::BindOnce(&AclManagerFacadeService::on_disconnect, common::Unretained(this), shared_connection,
+ current_connection_request_),
+ facade_handler_);
+ shared_connection->RegisterCallbacks(this, facade_handler_);
+ std::unique_ptr<BasePacketBuilder> builder = ConnectionCompleteBuilder::Create(
+ ErrorCode::SUCCESS, to_handle(current_connection_request_), addr, LinkType::ACL, Enable::DISABLED);
ConnectionEvent success;
- success.set_payload(builder_to_string(std::move(builder)));
+ success.set_event(builder_to_string(std::move(builder)));
per_connection_events_[current_connection_request_]->OnIncomingEvent(success);
current_connection_request_++;
}
+ void OnMasterLinkKeyComplete(uint16_t connection_handle, KeyFlag key_flag) override {
+ LOG_DEBUG("OnMasterLinkKeyComplete connection_handle:%d", connection_handle);
+ }
+
+ void OnRoleChange(Address bd_addr, Role new_role) override {
+ LOG_DEBUG("OnRoleChange bd_addr:%s, new_role:%d", bd_addr.ToString().c_str(), (uint8_t)new_role);
+ }
+
+ void OnReadDefaultLinkPolicySettingsComplete(uint16_t default_link_policy_settings) override {
+ LOG_DEBUG("OnReadDefaultLinkPolicySettingsComplete default_link_policy_settings:%d", default_link_policy_settings);
+ }
+
void OnConnectFail(Address address, ErrorCode reason) override {
std::unique_ptr<BasePacketBuilder> builder =
ConnectionCompleteBuilder::Create(reason, 0, address, LinkType::ACL, Enable::DISABLED);
ConnectionEvent fail;
- fail.set_payload(builder_to_string(std::move(builder)));
+ fail.set_event(builder_to_string(std::move(builder)));
per_connection_events_[current_connection_request_]->OnIncomingEvent(fail);
current_connection_request_++;
}
- void HACK_OnEscoConnectRequest(Address address, ClassOfDevice cod) override {
- LOG_ERROR("Remote ESCO connect request unimplemented");
+ void OnConnectionPacketTypeChanged(uint16_t packet_type) override {
+ LOG_DEBUG("OnConnectionPacketTypeChanged packet_type:%d", packet_type);
}
- void HACK_OnScoConnectRequest(Address address, ClassOfDevice cod) override {
- LOG_ERROR("Remote SCO connect request unimplemented");
+ void OnAuthenticationComplete() override {
+ LOG_DEBUG("OnAuthenticationComplete");
}
- class Connection : public ConnectionManagementCallbacks {
- public:
- Connection(
- uint16_t handle,
- std::shared_ptr<ClassicAclConnection> connection,
- std::shared_ptr<::bluetooth::grpc::GrpcEventQueue<ConnectionEvent>> event_stream)
- : handle_(handle), connection_(std::move(connection)), event_stream_(std::move(event_stream)) {}
-
- ConnectionManagementCallbacks* GetCallbacks() {
- return this;
- }
-
- void OnCentralLinkKeyComplete(KeyFlag key_flag) override {
- LOG_INFO("key_flag:%s", KeyFlagText(key_flag).c_str());
- }
-
- void OnRoleChange(hci::ErrorCode hci_status, Role new_role) override {
- LOG_INFO("new_role:%d", (uint8_t)new_role);
- }
-
- void OnReadLinkPolicySettingsComplete(uint16_t link_policy_settings) override {
- LOG_INFO("link_policy_settings:%d", link_policy_settings);
- }
-
- void OnConnectionPacketTypeChanged(uint16_t packet_type) override {
- LOG_INFO("OnConnectionPacketTypeChanged packet_type:%d", packet_type);
- }
-
- void OnAuthenticationComplete(hci::ErrorCode hci_status) override {
- LOG_INFO("OnAuthenticationComplete");
- }
+ void OnEncryptionChange(EncryptionEnabled enabled) override {
+ LOG_DEBUG("OnConnectionPacketTypeChanged enabled:%d", (uint8_t)enabled);
+ }
- void OnEncryptionChange(EncryptionEnabled enabled) override {
- LOG_INFO("OnConnectionPacketTypeChanged enabled:%d", (uint8_t)enabled);
- }
+ void OnChangeConnectionLinkKeyComplete() override {
+ LOG_DEBUG("OnChangeConnectionLinkKeyComplete");
+ };
- void OnChangeConnectionLinkKeyComplete() override {
- LOG_INFO("OnChangeConnectionLinkKeyComplete");
- };
-
- void OnReadClockOffsetComplete(uint16_t clock_offset) override {
- LOG_INFO("OnReadClockOffsetComplete clock_offset:%d", clock_offset);
- };
-
- void OnModeChange(ErrorCode status, Mode current_mode, uint16_t interval) override {
- LOG_INFO("OnModeChange Mode:%d, interval:%d", (uint8_t)current_mode, interval);
- };
-
- void OnSniffSubrating(
- hci::ErrorCode hci_status,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) override {
- LOG_INFO(
- "OnSniffSubrating maximum_transmit_latency:%d, maximum_receive_latency:%d"
- " minimum_remote_timeout:%d minimum_local_timeout:%d",
- maximum_transmit_latency,
- maximum_receive_latency,
- minimum_remote_timeout,
- minimum_local_timeout);
- }
+ void OnReadClockOffsetComplete(uint16_t clock_offset) override {
+ LOG_DEBUG("OnReadClockOffsetComplete clock_offset:%d", clock_offset);
+ };
- void OnQosSetupComplete(
- ServiceType service_type,
- uint32_t token_rate,
- uint32_t peak_bandwidth,
- uint32_t latency,
- uint32_t delay_variation) override {
- LOG_INFO(
- "OnQosSetupComplete service_type:%d, token_rate:%d, peak_bandwidth:%d, latency:%d, delay_variation:%d",
- (uint8_t)service_type,
- token_rate,
- peak_bandwidth,
- latency,
- delay_variation);
- }
+ void OnModeChange(Mode current_mode, uint16_t interval) override {
+ LOG_DEBUG("OnModeChange Mode:%d, interval:%d", (uint8_t)current_mode, interval);
+ };
- void OnFlowSpecificationComplete(
- FlowDirection flow_direction,
- ServiceType service_type,
- uint32_t token_rate,
- uint32_t token_bucket_size,
- uint32_t peak_bandwidth,
- uint32_t access_latency) override {
- LOG_INFO(
- "OnFlowSpecificationComplete flow_direction:%d. service_type:%d, token_rate:%d, token_bucket_size:%d, "
- "peak_bandwidth:%d, access_latency:%d",
- (uint8_t)flow_direction,
- (uint8_t)service_type,
- token_rate,
- token_bucket_size,
- peak_bandwidth,
- access_latency);
- }
+ void OnQosSetupComplete(ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth, uint32_t latency,
+ uint32_t delay_variation) override {
+ LOG_DEBUG("OnQosSetupComplete service_type:%d, token_rate:%d, peak_bandwidth:%d, latency:%d, delay_variation:%d",
+ (uint8_t)service_type, token_rate, peak_bandwidth, latency, delay_variation);
+ }
- void OnFlushOccurred() override {
- LOG_INFO("OnFlushOccurred");
- }
+ void OnFlowSpecificationComplete(FlowDirection flow_direction, ServiceType service_type, uint32_t token_rate,
+ uint32_t token_bucket_size, uint32_t peak_bandwidth,
+ uint32_t access_latency) override {
+ LOG_DEBUG(
+ "OnFlowSpecificationComplete flow_direction:%d. service_type:%d, token_rate:%d, token_bucket_size:%d, "
+ "peak_bandwidth:%d, access_latency:%d",
+ (uint8_t)flow_direction, (uint8_t)service_type, token_rate, token_bucket_size, peak_bandwidth, access_latency);
+ }
- void OnRoleDiscoveryComplete(Role current_role) override {
- LOG_INFO("OnRoleDiscoveryComplete current_role:%d", (uint8_t)current_role);
- }
+ void OnFlushOccurred() override {
+ LOG_DEBUG("OnFlushOccurred");
+ }
- void OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout) override {
- LOG_INFO("OnReadAutomaticFlushTimeoutComplete flush_timeout:%d", flush_timeout);
- }
+ void OnRoleDiscoveryComplete(Role current_role) override {
+ LOG_DEBUG("OnRoleDiscoveryComplete current_role:%d", (uint8_t)current_role);
+ }
- void OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level) override {
- LOG_INFO("OnReadTransmitPowerLevelComplete transmit_power_level:%d", transmit_power_level);
- }
+ void OnReadLinkPolicySettingsComplete(uint16_t link_policy_settings) override {
+ LOG_DEBUG("OnReadLinkPolicySettingsComplete link_policy_settings:%d", link_policy_settings);
+ }
- void OnReadLinkSupervisionTimeoutComplete(uint16_t link_supervision_timeout) override {
- LOG_INFO("OnReadLinkSupervisionTimeoutComplete link_supervision_timeout:%d", link_supervision_timeout);
- }
+ void OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout) override {
+ LOG_DEBUG("OnReadAutomaticFlushTimeoutComplete flush_timeout:%d", flush_timeout);
+ }
- void OnReadFailedContactCounterComplete(uint16_t failed_contact_counter) override {
- LOG_INFO("OnReadFailedContactCounterComplete failed_contact_counter:%d", failed_contact_counter);
- }
+ void OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level) override {
+ LOG_DEBUG("OnReadTransmitPowerLevelComplete transmit_power_level:%d", transmit_power_level);
+ }
- void OnReadLinkQualityComplete(uint8_t link_quality) override {
- LOG_INFO("OnReadLinkQualityComplete link_quality:%d", link_quality);
- }
+ void OnReadLinkSupervisionTimeoutComplete(uint16_t link_supervision_timeout) override {
+ LOG_DEBUG("OnReadLinkSupervisionTimeoutComplete link_supervision_timeout:%d", link_supervision_timeout);
+ }
- void OnReadAfhChannelMapComplete(AfhMode afh_mode, std::array<uint8_t, 10> afh_channel_map) override {
- LOG_INFO("OnReadAfhChannelMapComplete afh_mode:%d", (uint8_t)afh_mode);
- }
+ void OnReadFailedContactCounterComplete(uint16_t failed_contact_counter) override {
+ LOG_DEBUG("OnReadFailedContactCounterComplete failed_contact_counter:%d", failed_contact_counter);
+ }
- void OnReadRssiComplete(uint8_t rssi) override {
- LOG_INFO("OnReadRssiComplete rssi:%d", rssi);
- }
+ void OnReadLinkQualityComplete(uint8_t link_quality) override {
+ LOG_DEBUG("OnReadLinkQualityComplete link_quality:%d", link_quality);
+ }
- void OnReadClockComplete(uint32_t clock, uint16_t accuracy) override {
- LOG_INFO("OnReadClockComplete clock:%d, accuracy:%d", clock, accuracy);
- }
+ void OnReadAfhChannelMapComplete(AfhMode afh_mode, std::array<uint8_t, 10> afh_channel_map) override {
+ LOG_DEBUG("OnReadAfhChannelMapComplete afh_mode:%d", (uint8_t)afh_mode);
+ }
- void OnDisconnection(ErrorCode reason) override {
- LOG_INFO("OnDisconnection reason: %s", ErrorCodeText(reason).c_str());
- std::unique_ptr<BasePacketBuilder> builder =
- DisconnectionCompleteBuilder::Create(ErrorCode::SUCCESS, handle_, reason);
- ConnectionEvent disconnection;
- disconnection.set_payload(builder_to_string(std::move(builder)));
- event_stream_->OnIncomingEvent(disconnection);
- }
- void OnReadRemoteVersionInformationComplete(
- hci::ErrorCode error_status, uint8_t lmp_version, uint16_t manufacturer_name, uint16_t sub_version) override {
- LOG_INFO(
- "OnReadRemoteVersionInformationComplete lmp_version:%hhu manufacturer_name:%hu sub_version:%hu",
- lmp_version,
- manufacturer_name,
- sub_version);
- }
- void OnReadRemoteSupportedFeaturesComplete(uint64_t features) override {
- LOG_INFO("OnReadRemoteSupportedFeaturesComplete features:0x%lx", static_cast<unsigned long>(features));
- }
- void OnReadRemoteExtendedFeaturesComplete(
- uint8_t page_number, uint8_t max_page_number, uint64_t features) override {
- LOG_INFO(
- "OnReadRemoteExtendedFeaturesComplete page_number:%hhu max_page_number:%hhu features:0x%lx",
- page_number,
- max_page_number,
- static_cast<unsigned long>(features));
- }
+ void OnReadRssiComplete(uint8_t rssi) override {
+ LOG_DEBUG("OnReadRssiComplete rssi:%d", rssi);
+ }
- uint16_t handle_;
- std::shared_ptr<ClassicAclConnection> connection_;
- std::shared_ptr<::bluetooth::grpc::GrpcEventQueue<ConnectionEvent>> event_stream_;
- ::bluetooth::grpc::GrpcEventQueue<AclData> pending_acl_data_{std::string("PendingAclData") +
- std::to_string(handle_)};
- };
+ void OnReadClockComplete(uint32_t clock, uint16_t accuracy) override {
+ LOG_DEBUG("OnReadClockComplete clock:%d, accuracy:%d", clock, accuracy);
+ }
private:
AclManager* acl_manager_;
::bluetooth::os::Handler* facade_handler_;
mutable std::mutex acl_connections_mutex_;
- std::map<uint16_t, Connection> acl_connections_;
- std::vector<std::shared_ptr<::bluetooth::grpc::GrpcEventQueue<ConnectionEvent>>> per_connection_events_;
+ std::map<uint16_t, std::shared_ptr<AclConnection>> acl_connections_;
+ ::bluetooth::grpc::GrpcEventQueue<AclData> pending_acl_data_{"FetchAclData"};
+ std::vector<std::unique_ptr<::bluetooth::grpc::GrpcEventQueue<ConnectionEvent>>> per_connection_events_;
uint32_t current_connection_request_{0};
};
diff --git a/gd/hci/facade/acl_manager_facade.proto b/gd/hci/facade/acl_manager_facade.proto
index 890a1836a..8a40f8f81 100644
--- a/gd/hci/facade/acl_manager_facade.proto
+++ b/gd/hci/facade/acl_manager_facade.proto
@@ -8,12 +8,9 @@ service AclManagerFacade {
rpc CreateConnection(ConnectionMsg) returns (stream ConnectionEvent) {}
rpc CancelConnection(ConnectionMsg) returns (google.protobuf.Empty) {}
rpc Disconnect(HandleMsg) returns (google.protobuf.Empty) {}
- rpc WriteDefaultLinkPolicySettings(PolicyMsg) returns (google.protobuf.Empty) {}
rpc AuthenticationRequested(HandleMsg) returns (google.protobuf.Empty) {}
- rpc ConnectionCommand(ConnectionCommandMsg) returns (google.protobuf.Empty) {}
- rpc SwitchRole(RoleMsg) returns (google.protobuf.Empty) {}
rpc SendAclData(AclData) returns (google.protobuf.Empty) {}
- rpc FetchAclData(HandleMsg) returns (stream AclData) {}
+ rpc FetchAclData(google.protobuf.Empty) returns (stream AclData) {}
rpc FetchIncomingConnection(google.protobuf.Empty) returns (stream ConnectionEvent) {}
}
@@ -22,29 +19,12 @@ message HandleMsg {
}
message ConnectionMsg {
- bytes address = 1;
-}
-
-message PolicyMsg {
- uint32 policy = 1;
-}
-
-enum NewRole {
- CENTRAL = 0;
- PERIPHERAL = 1;
-}
-
-message RoleMsg {
- bytes address = 1;
- NewRole role = 2;
-}
-
-message ConnectionCommandMsg {
- bytes packet = 1;
+ uint32 address_type = 1;
+ bytes address = 2;
}
message ConnectionEvent {
- bytes payload = 1;
+ bytes event = 1;
}
message AclData {
diff --git a/gd/hci/facade/controller_facade.cc b/gd/hci/facade/controller_facade.cc
index 9425be598..c65dff0db 100644
--- a/gd/hci/facade/controller_facade.cc
+++ b/gd/hci/facade/controller_facade.cc
@@ -42,14 +42,14 @@ class ControllerFacadeService : public ControllerFacade::Service {
::grpc::Status GetMacAddress(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
AddressMsg* response) override {
- Address local_address = controller_->GetMacAddress();
+ Address local_address = controller_->GetControllerMacAddress();
response->set_address(local_address.ToString());
return ::grpc::Status::OK;
}
::grpc::Status GetLocalName(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
NameMsg* response) override {
- std::string local_name = controller_->GetLocalName();
+ std::string local_name = controller_->GetControllerLocalName();
response->set_name(local_name);
return ::grpc::Status::OK;
}
@@ -60,6 +60,15 @@ class ControllerFacadeService : public ControllerFacade::Service {
return ::grpc::Status::OK;
}
+ ::grpc::Status GetLocalExtendedFeatures(::grpc::ServerContext* context, const PageNumberMsg* request,
+ FeaturesMsg* response) override {
+ if (request->page_number() > controller_->GetControllerLocalExtendedFeaturesMaxPageNumber()) {
+ return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Local Extended Features page number out of range");
+ }
+ response->set_page(controller_->GetControllerLocalExtendedFeatures(request->page_number()));
+ return ::grpc::Status::OK;
+ }
+
private:
Controller* controller_;
};
diff --git a/gd/hci/facade/controller_facade.proto b/gd/hci/facade/controller_facade.proto
index ecd9714b4..edf9de722 100644
--- a/gd/hci/facade/controller_facade.proto
+++ b/gd/hci/facade/controller_facade.proto
@@ -8,6 +8,7 @@ service ControllerFacade {
rpc GetMacAddress(google.protobuf.Empty) returns (AddressMsg) {}
rpc WriteLocalName(NameMsg) returns (google.protobuf.Empty) {}
rpc GetLocalName(google.protobuf.Empty) returns (NameMsg) {}
+ rpc GetLocalExtendedFeatures(PageNumberMsg) returns (FeaturesMsg) {}
}
message AddressMsg {
@@ -17,3 +18,11 @@ message AddressMsg {
message NameMsg {
bytes name = 1;
}
+
+message PageNumberMsg {
+ uint32 page_number = 1;
+}
+
+message FeaturesMsg {
+ uint64 page = 1;
+}
diff --git a/gd/hci/facade/facade.cc b/gd/hci/facade/facade.cc
index fb1e232b8..9650bcd00 100644
--- a/gd/hci/facade/facade.cc
+++ b/gd/hci/facade/facade.cc
@@ -21,7 +21,7 @@
#include "common/bind.h"
#include "grpc/grpc_event_queue.h"
#include "hci/controller.h"
-#include "hci/facade/hci_facade.grpc.pb.h"
+#include "hci/facade/facade.grpc.pb.h"
#include "hci/hci_layer.h"
#include "hci/hci_packets.h"
@@ -33,12 +33,12 @@ namespace bluetooth {
namespace hci {
namespace facade {
-class HciFacadeService : public HciFacade::Service {
+class HciLayerFacadeService : public HciLayerFacade::Service {
public:
- HciFacadeService(HciLayer* hci_layer, Controller* controller, ::bluetooth::os::Handler* facade_handler)
+ HciLayerFacadeService(HciLayer* hci_layer, Controller* controller, ::bluetooth::os::Handler* facade_handler)
: hci_layer_(hci_layer), controller_(controller), facade_handler_(facade_handler) {}
- virtual ~HciFacadeService() {
+ virtual ~HciLayerFacadeService() {
if (unregister_acl_dequeue_) {
hci_layer_->GetAclQueueEnd()->UnregisterDequeue();
}
@@ -50,9 +50,10 @@ class HciFacadeService : public HciFacade::Service {
}
}
- class TestCommandBuilder : public CommandBuilder {
+ class TestCommandBuilder : public CommandPacketBuilder {
public:
- explicit TestCommandBuilder(std::vector<uint8_t> bytes) : CommandBuilder(OpCode::NONE), bytes_(std::move(bytes)) {}
+ explicit TestCommandBuilder(std::vector<uint8_t> bytes)
+ : CommandPacketBuilder(OpCode::NONE), bytes_(std::move(bytes)) {}
size_t size() const override {
return bytes_.size();
}
@@ -66,105 +67,113 @@ class HciFacadeService : public HciFacade::Service {
std::vector<uint8_t> bytes_;
};
- ::grpc::Status SendCommand(
- ::grpc::ServerContext* context,
- const ::bluetooth::facade::Data* command,
- ::google::protobuf::Empty* response) override {
- auto payload = std::vector<uint8_t>(command->payload().begin(), command->payload().end());
- auto packet = std::make_unique<TestCommandBuilder>(payload);
- auto opcode = static_cast<const bluetooth::hci::OpCode>(payload.at(1) << 8 | payload.at(0));
- if (Checker::IsCommandStatusOpcode(opcode)) {
- hci_layer_->EnqueueCommand(std::move(packet), facade_handler_->BindOnceOn(this, &HciFacadeService::on_status));
- } else {
- hci_layer_->EnqueueCommand(std::move(packet), facade_handler_->BindOnceOn(this, &HciFacadeService::on_complete));
- }
+ ::grpc::Status EnqueueCommandWithComplete(::grpc::ServerContext* context, const ::bluetooth::hci::CommandMsg* command,
+ ::google::protobuf::Empty* response) override {
+ auto packet = std::make_unique<TestCommandBuilder>(
+ std::vector<uint8_t>(command->command().begin(), command->command().end()));
+ hci_layer_->EnqueueCommand(std::move(packet),
+ common::BindOnce(&HciLayerFacadeService::on_complete, common::Unretained(this)),
+ facade_handler_);
+ return ::grpc::Status::OK;
+ }
+
+ ::grpc::Status EnqueueCommandWithStatus(::grpc::ServerContext* context, const ::bluetooth::hci::CommandMsg* command,
+ ::google::protobuf::Empty* response) override {
+ auto packet = std::make_unique<TestCommandBuilder>(
+ std::vector<uint8_t>(command->command().begin(), command->command().end()));
+ hci_layer_->EnqueueCommand(std::move(packet),
+ common::BindOnce(&HciLayerFacadeService::on_status, common::Unretained(this)),
+ facade_handler_);
return ::grpc::Status::OK;
}
- ::grpc::Status RequestEvent(
- ::grpc::ServerContext* context,
- const ::bluetooth::hci::EventRequest* event,
- ::google::protobuf::Empty* response) override {
- hci_layer_->RegisterEventHandler(
- static_cast<EventCode>(event->code()), facade_handler_->BindOn(this, &HciFacadeService::on_event));
+ ::grpc::Status RegisterEventHandler(::grpc::ServerContext* context, const ::bluetooth::hci::EventCodeMsg* event,
+ ::google::protobuf::Empty* response) override {
+ hci_layer_->RegisterEventHandler(static_cast<EventCode>(event->code()),
+ common::Bind(&HciLayerFacadeService::on_event, common::Unretained(this)),
+ facade_handler_);
return ::grpc::Status::OK;
}
- ::grpc::Status RequestLeSubevent(
- ::grpc::ServerContext* context,
- const ::bluetooth::hci::EventRequest* event,
- ::google::protobuf::Empty* response) override {
- hci_layer_->RegisterLeEventHandler(
- static_cast<SubeventCode>(event->code()), facade_handler_->BindOn(this, &HciFacadeService::on_le_subevent));
+ ::grpc::Status RegisterLeEventHandler(::grpc::ServerContext* context,
+ const ::bluetooth::hci::LeSubeventCodeMsg* event,
+ ::google::protobuf::Empty* response) override {
+ hci_layer_->RegisterLeEventHandler(static_cast<SubeventCode>(event->code()),
+ common::Bind(&HciLayerFacadeService::on_le_subevent, common::Unretained(this)),
+ facade_handler_);
return ::grpc::Status::OK;
}
- ::grpc::Status StreamEvents(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<::bluetooth::facade::Data>* writer) override {
+ ::grpc::Status FetchEvents(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
+ ::grpc::ServerWriter<EventMsg>* writer) override {
return pending_events_.RunLoop(context, writer);
};
- ::grpc::Status StreamLeSubevents(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<::bluetooth::facade::Data>* writer) override {
+ ::grpc::Status FetchLeSubevents(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
+ ::grpc::ServerWriter<LeSubeventMsg>* writer) override {
return pending_le_events_.RunLoop(context, writer);
};
- class TestAclBuilder : public AclBuilder {
+ class TestAclBuilder : public AclPacketBuilder {
public:
- explicit TestAclBuilder(std::vector<uint8_t> payload)
- : AclBuilder(0xbad, PacketBoundaryFlag::CONTINUING_FRAGMENT, BroadcastFlag::ACTIVE_PERIPHERAL_BROADCAST),
- bytes_(std::move(payload)) {}
+ explicit TestAclBuilder(uint16_t handle, uint8_t packet_boundary_flag, uint8_t broadcast_flag,
+ std::vector<uint8_t> payload)
+ : AclPacketBuilder(0xbad, PacketBoundaryFlag::CONTINUING_FRAGMENT, BroadcastFlag::ACTIVE_SLAVE_BROADCAST),
+ handle_(handle), pb_flag_(packet_boundary_flag), b_flag_(broadcast_flag), bytes_(std::move(payload)) {}
size_t size() const override {
return bytes_.size();
}
void Serialize(BitInserter& bit_inserter) const override {
+ LOG_INFO("handle 0x%hx boundary 0x%hhx broadcast 0x%hhx", handle_, pb_flag_, b_flag_);
+ bit_inserter.insert_byte(handle_);
+ bit_inserter.insert_bits((handle_ >> 8) & 0xf, 4);
+ bit_inserter.insert_bits(pb_flag_, 2);
+ bit_inserter.insert_bits(b_flag_, 2);
+ bit_inserter.insert_byte(bytes_.size() & 0xff);
+ bit_inserter.insert_byte((bytes_.size() & 0xff00) >> 8);
for (auto&& b : bytes_) {
bit_inserter.insert_byte(b);
}
}
private:
+ uint16_t handle_;
+ uint8_t pb_flag_;
+ uint8_t b_flag_;
std::vector<uint8_t> bytes_;
};
- ::grpc::Status SendAcl(
- ::grpc::ServerContext* context,
- const ::bluetooth::facade::Data* acl,
- ::google::protobuf::Empty* response) override {
+ ::grpc::Status SendAclData(::grpc::ServerContext* context, const ::bluetooth::hci::AclMsg* acl,
+ ::google::protobuf::Empty* response) override {
waiting_acl_packet_ =
- std::make_unique<TestAclBuilder>(std::vector<uint8_t>(acl->payload().begin(), acl->payload().end()));
+ std::make_unique<TestAclBuilder>(acl->handle(), acl->packet_boundary_flag(), acl->broadcast_flag(),
+ std::vector<uint8_t>(acl->data().begin(), acl->data().end()));
std::promise<void> enqueued;
auto future = enqueued.get_future();
if (!completed_packets_callback_registered_) {
- controller_->RegisterCompletedAclPacketsCallback(
- facade_handler_->Bind([](uint16_t, uint16_t) { /* do nothing */ }));
+ controller_->RegisterCompletedAclPacketsCallback(common::Bind([](uint16_t, uint16_t) { /* do nothing */ }),
+ facade_handler_);
completed_packets_callback_registered_ = true;
}
hci_layer_->GetAclQueueEnd()->RegisterEnqueue(
- facade_handler_,
- common::Bind(&HciFacadeService::handle_enqueue_acl, common::Unretained(this), common::Unretained(&enqueued)));
+ facade_handler_, common::Bind(&HciLayerFacadeService::handle_enqueue_acl, common::Unretained(this),
+ common::Unretained(&enqueued)));
auto result = future.wait_for(std::chrono::milliseconds(100));
ASSERT(std::future_status::ready == result);
return ::grpc::Status::OK;
}
- ::grpc::Status StreamAcl(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<::bluetooth::facade::Data>* writer) override {
+ ::grpc::Status FetchAclPackets(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
+ ::grpc::ServerWriter<AclMsg>* writer) override {
hci_layer_->GetAclQueueEnd()->RegisterDequeue(
- facade_handler_, common::Bind(&HciFacadeService::on_acl_ready, common::Unretained(this)));
+ facade_handler_, common::Bind(&HciLayerFacadeService::on_acl_ready, common::Unretained(this)));
unregister_acl_dequeue_ = true;
return pending_acl_events_.RunLoop(context, writer);
};
private:
- std::unique_ptr<AclBuilder> handle_enqueue_acl(std::promise<void>* promise) {
+ std::unique_ptr<AclPacketBuilder> handle_enqueue_acl(std::promise<void>* promise) {
promise->set_value();
hci_layer_->GetAclQueueEnd()->UnregisterEnqueue();
return std::move(waiting_acl_packet_);
@@ -175,75 +184,76 @@ class HciFacadeService : public HciFacade::Service {
ASSERT(acl_ptr != nullptr);
ASSERT(acl_ptr->IsValid());
LOG_INFO("Got an Acl message for handle 0x%hx", acl_ptr->GetHandle());
- ::bluetooth::facade::Data incoming;
- incoming.set_payload(std::string(acl_ptr->begin(), acl_ptr->end()));
+ AclMsg incoming;
+ incoming.set_data(std::string(acl_ptr->begin(), acl_ptr->end()));
pending_acl_events_.OnIncomingEvent(std::move(incoming));
}
- void on_event(hci::EventView view) {
+ void on_event(hci::EventPacketView view) {
ASSERT(view.IsValid());
LOG_INFO("Got an Event %s", EventCodeText(view.GetEventCode()).c_str());
- ::bluetooth::facade::Data response;
- response.set_payload(std::string(view.begin(), view.end()));
+ EventMsg response;
+ response.set_event(std::string(view.begin(), view.end()));
pending_events_.OnIncomingEvent(std::move(response));
}
void on_le_subevent(hci::LeMetaEventView view) {
ASSERT(view.IsValid());
LOG_INFO("Got an LE Event %s", SubeventCodeText(view.GetSubeventCode()).c_str());
- ::bluetooth::facade::Data response;
- response.set_payload(std::string(view.begin(), view.end()));
+ LeSubeventMsg response;
+ response.set_event(std::string(view.begin(), view.end()));
pending_le_events_.OnIncomingEvent(std::move(response));
}
void on_complete(hci::CommandCompleteView view) {
ASSERT(view.IsValid());
LOG_INFO("Got a Command complete %s", OpCodeText(view.GetCommandOpCode()).c_str());
- ::bluetooth::facade::Data response;
- response.set_payload(std::string(view.begin(), view.end()));
+ EventMsg response;
+ response.set_event(std::string(view.begin(), view.end()));
pending_events_.OnIncomingEvent(std::move(response));
}
void on_status(hci::CommandStatusView view) {
ASSERT(view.IsValid());
LOG_INFO("Got a Command status %s", OpCodeText(view.GetCommandOpCode()).c_str());
- ::bluetooth::facade::Data response;
- response.set_payload(std::string(view.begin(), view.end()));
+ EventMsg response;
+ response.set_event(std::string(view.begin(), view.end()));
pending_events_.OnIncomingEvent(std::move(response));
}
HciLayer* hci_layer_;
Controller* controller_;
::bluetooth::os::Handler* facade_handler_;
- ::bluetooth::grpc::GrpcEventQueue<::bluetooth::facade::Data> pending_events_{"StreamEvents"};
- ::bluetooth::grpc::GrpcEventQueue<::bluetooth::facade::Data> pending_le_events_{"StreamLeSubevents"};
- ::bluetooth::grpc::GrpcEventQueue<::bluetooth::facade::Data> pending_acl_events_{"StreamAcl"};
+ ::bluetooth::grpc::GrpcEventQueue<EventMsg> pending_events_{"FetchHciEvent"};
+ ::bluetooth::grpc::GrpcEventQueue<LeSubeventMsg> pending_le_events_{"FetchLeSubevent"};
+ ::bluetooth::grpc::GrpcEventQueue<AclMsg> pending_acl_events_{"FetchAclData"};
bool unregister_acl_dequeue_{false};
std::unique_ptr<TestAclBuilder> waiting_acl_packet_;
bool completed_packets_callback_registered_{false};
};
-void HciFacadeModule::ListDependencies(ModuleList* list) {
+void HciLayerFacadeModule::ListDependencies(ModuleList* list) {
::bluetooth::grpc::GrpcFacadeModule::ListDependencies(list);
list->add<HciLayer>();
list->add<Controller>();
}
-void HciFacadeModule::Start() {
+void HciLayerFacadeModule::Start() {
::bluetooth::grpc::GrpcFacadeModule::Start();
- service_ = new HciFacadeService(GetDependency<HciLayer>(), GetDependency<Controller>(), GetHandler());
+ service_ = new HciLayerFacadeService(GetDependency<HciLayer>(), GetDependency<Controller>(), GetHandler());
}
-void HciFacadeModule::Stop() {
+void HciLayerFacadeModule::Stop() {
delete service_;
::bluetooth::grpc::GrpcFacadeModule::Stop();
}
-::grpc::Service* HciFacadeModule::GetService() const {
+::grpc::Service* HciLayerFacadeModule::GetService() const {
return service_;
}
-const ModuleFactory HciFacadeModule::Factory = ::bluetooth::ModuleFactory([]() { return new HciFacadeModule(); });
+const ModuleFactory HciLayerFacadeModule::Factory =
+ ::bluetooth::ModuleFactory([]() { return new HciLayerFacadeModule(); });
} // namespace facade
} // namespace hci
diff --git a/gd/hci/facade/facade.h b/gd/hci/facade/facade.h
index 0966aa5ab..88ba36f67 100644
--- a/gd/hci/facade/facade.h
+++ b/gd/hci/facade/facade.h
@@ -25,9 +25,9 @@ namespace bluetooth {
namespace hci {
namespace facade {
-class HciFacadeService;
+class HciLayerFacadeService;
-class HciFacadeModule : public ::bluetooth::grpc::GrpcFacadeModule {
+class HciLayerFacadeModule : public ::bluetooth::grpc::GrpcFacadeModule {
public:
static const ModuleFactory Factory;
@@ -37,7 +37,7 @@ class HciFacadeModule : public ::bluetooth::grpc::GrpcFacadeModule {
::grpc::Service* GetService() const override;
private:
- HciFacadeService* service_;
+ HciLayerFacadeService* service_;
};
} // namespace facade
diff --git a/gd/hci/facade/facade.proto b/gd/hci/facade/facade.proto
new file mode 100644
index 000000000..bcce542bf
--- /dev/null
+++ b/gd/hci/facade/facade.proto
@@ -0,0 +1,43 @@
+syntax = "proto3";
+
+package bluetooth.hci;
+
+import "google/protobuf/empty.proto";
+
+service HciLayerFacade {
+ rpc EnqueueCommandWithComplete(CommandMsg) returns (google.protobuf.Empty) {}
+ rpc EnqueueCommandWithStatus(CommandMsg) returns (google.protobuf.Empty) {}
+ rpc RegisterEventHandler(EventCodeMsg) returns (google.protobuf.Empty) {}
+ rpc RegisterLeEventHandler(LeSubeventCodeMsg) returns (google.protobuf.Empty) {}
+ rpc SendAclData(AclMsg) returns (google.protobuf.Empty) {}
+ rpc FetchEvents(google.protobuf.Empty) returns (stream EventMsg) {}
+ rpc FetchLeSubevents(google.protobuf.Empty) returns (stream LeSubeventMsg) {}
+ rpc FetchAclPackets(google.protobuf.Empty) returns (stream AclMsg) {}
+}
+
+message CommandMsg {
+ bytes command = 1;
+}
+
+message EventMsg {
+ bytes event = 1;
+}
+
+message LeSubeventMsg {
+ bytes event = 1;
+}
+
+message AclMsg {
+ uint32 handle = 1;
+ uint32 packet_boundary_flag = 2;
+ uint32 broadcast_flag = 3;
+ bytes data = 4;
+}
+
+message EventCodeMsg {
+ uint32 code = 1;
+}
+
+message LeSubeventCodeMsg {
+ uint32 code = 1;
+}
diff --git a/gd/hci/facade/hci_facade.proto b/gd/hci/facade/hci_facade.proto
deleted file mode 100644
index 7465a45ab..000000000
--- a/gd/hci/facade/hci_facade.proto
+++ /dev/null
@@ -1,23 +0,0 @@
-syntax = "proto3";
-
-package bluetooth.hci;
-
-import "google/protobuf/empty.proto";
-import "facade/common.proto";
-
-service HciFacade {
- rpc SendCommand(facade.Data) returns (google.protobuf.Empty) {}
-
- rpc RequestEvent(EventRequest) returns (google.protobuf.Empty) {}
- rpc StreamEvents(google.protobuf.Empty) returns (stream facade.Data) {}
-
- rpc RequestLeSubevent(EventRequest) returns (google.protobuf.Empty) {}
- rpc StreamLeSubevents(google.protobuf.Empty) returns (stream facade.Data) {}
-
- rpc SendAcl(facade.Data) returns (google.protobuf.Empty) {}
- rpc StreamAcl(google.protobuf.Empty) returns (stream facade.Data) {}
-}
-
-message EventRequest {
- uint32 code = 1;
-}
diff --git a/gd/hci/facade/le_acl_manager_facade.cc b/gd/hci/facade/le_acl_manager_facade.cc
index ffc0dc1fa..38d5ecb61 100644
--- a/gd/hci/facade/le_acl_manager_facade.cc
+++ b/gd/hci/facade/le_acl_manager_facade.cc
@@ -38,35 +38,30 @@ namespace bluetooth {
namespace hci {
namespace facade {
-using acl_manager::LeAclConnection;
-using acl_manager::LeConnectionCallbacks;
-using acl_manager::LeConnectionManagementCallbacks;
-
-class LeAclManagerFacadeService : public LeAclManagerFacade::Service, public LeConnectionCallbacks {
+class LeAclManagerFacadeService : public LeAclManagerFacade::Service,
+ public ::bluetooth::hci::LeConnectionCallbacks,
+ public ::bluetooth::hci::ConnectionManagementCallbacks,
+ public ::bluetooth::hci::AclManagerCallbacks {
public:
LeAclManagerFacadeService(AclManager* acl_manager, ::bluetooth::os::Handler* facade_handler)
: acl_manager_(acl_manager), facade_handler_(facade_handler) {
acl_manager_->RegisterLeCallbacks(this, facade_handler_);
+ acl_manager_->RegisterLeAclManagerCallbacks(this, facade_handler_);
}
- ~LeAclManagerFacadeService() {
+ ~LeAclManagerFacadeService() override {
std::unique_lock<std::mutex> lock(acl_connections_mutex_);
- for (auto& conn : acl_connections_) {
- if (conn.second.connection_ != nullptr) {
- conn.second.connection_->GetAclQueueEnd()->UnregisterDequeue();
- conn.second.connection_.reset();
- }
+ for (auto connection : acl_connections_) {
+ connection.second->GetAclQueueEnd()->UnregisterDequeue();
}
}
- ::grpc::Status CreateConnection(
- ::grpc::ServerContext* context,
- const ::bluetooth::facade::BluetoothAddressWithType* request,
- ::grpc::ServerWriter<LeConnectionEvent>* writer) override {
+ ::grpc::Status CreateConnection(::grpc::ServerContext* context, const LeConnectionMsg* request,
+ ::grpc::ServerWriter<LeConnectionEvent>* writer) override {
Address peer_address;
- ASSERT(Address::FromString(request->address().address(), peer_address));
- AddressWithType peer(peer_address, static_cast<AddressType>(request->type()));
- acl_manager_->CreateLeConnection(peer, /* is_direct */ true);
+ ASSERT(Address::FromString(request->address(), peer_address));
+ AddressWithType peer(peer_address, static_cast<AddressType>(request->address_type()));
+ acl_manager_->CreateLeConnection(peer);
if (per_connection_events_.size() > current_connection_request_) {
return ::grpc::Status(::grpc::StatusCode::RESOURCE_EXHAUSTED, "Only one outstanding request is supported");
}
@@ -75,21 +70,6 @@ class LeAclManagerFacadeService : public LeAclManagerFacade::Service, public LeC
return per_connection_events_[current_connection_request_]->RunLoop(context, writer);
}
- ::grpc::Status CancelConnection(
- ::grpc::ServerContext* context,
- const ::bluetooth::facade::BluetoothAddressWithType* request,
- google::protobuf::Empty* response) override {
- Address peer_address;
- ASSERT(Address::FromString(request->address().address(), peer_address));
- AddressWithType peer(peer_address, static_cast<AddressType>(request->type()));
- if (per_connection_events_.size() == current_connection_request_) {
- // Todo: Check that the address matches an outstanding connection request
- return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "No matching outstanding connection");
- }
- acl_manager_->CancelLeConnect(peer);
- return ::grpc::Status::OK;
- }
-
::grpc::Status Disconnect(::grpc::ServerContext* context, const LeHandleMsg* request,
::google::protobuf::Empty* response) override {
std::unique_lock<std::mutex> lock(acl_connections_mutex_);
@@ -98,51 +78,26 @@ class LeAclManagerFacadeService : public LeAclManagerFacade::Service, public LeC
LOG_ERROR("Invalid handle");
return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle");
} else {
- connection->second.connection_->Disconnect(DisconnectReason::REMOTE_USER_TERMINATED_CONNECTION);
+ connection->second->Disconnect(DisconnectReason::REMOTE_USER_TERMINATED_CONNECTION);
return ::grpc::Status::OK;
}
}
-#define GET_CONNECTION(view) \
- std::map<uint16_t, Connection>::iterator connection; \
- do { \
- if (!view.IsValid()) { \
- return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle"); \
- } \
- std::unique_lock<std::mutex> lock(acl_connections_mutex_); \
- connection = acl_connections_.find(view.GetConnectionHandle()); \
- if (connection == acl_connections_.end()) { \
- return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle"); \
- } \
- } while (0)
-
- ::grpc::Status ConnectionCommand(
- ::grpc::ServerContext* context,
- const LeConnectionCommandMsg* request,
- ::google::protobuf::Empty* response) override {
- auto command_view =
- ConnectionManagementCommandView::Create(AclCommandView::Create(CommandView::Create(PacketView<kLittleEndian>(
- std::make_shared<std::vector<uint8_t>>(request->packet().begin(), request->packet().end())))));
- if (!command_view.IsValid()) {
- return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid command packet");
- }
- switch (command_view.GetOpCode()) {
- case OpCode::DISCONNECT: {
- auto view = DisconnectView::Create(command_view);
- GET_CONNECTION(view);
- connection->second.connection_->Disconnect(view.GetReason());
- return ::grpc::Status::OK;
- }
- default:
- return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid command packet");
+ ::grpc::Status AuthenticationRequested(::grpc::ServerContext* context, const LeHandleMsg* request,
+ ::google::protobuf::Empty* response) override {
+ std::unique_lock<std::mutex> lock(acl_connections_mutex_);
+ auto connection = acl_connections_.find(request->handle());
+ if (connection == acl_connections_.end()) {
+ LOG_ERROR("Invalid handle");
+ return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle");
+ } else {
+ connection->second->AuthenticationRequested();
+ return ::grpc::Status::OK;
}
- }
-#undef GET_CONNECTION
+ };
- ::grpc::Status FetchIncomingConnection(
- ::grpc::ServerContext* context,
- const google::protobuf::Empty* request,
- ::grpc::ServerWriter<LeConnectionEvent>* writer) override {
+ ::grpc::Status FetchIncomingConnection(::grpc::ServerContext* context, const google::protobuf::Empty* request,
+ ::grpc::ServerWriter<LeConnectionEvent>* writer) override {
if (per_connection_events_.size() > current_connection_request_) {
return ::grpc::Status(::grpc::StatusCode::RESOURCE_EXHAUSTED, "Only one outstanding connection is supported");
}
@@ -151,48 +106,41 @@ class LeAclManagerFacadeService : public LeAclManagerFacade::Service, public LeC
return per_connection_events_[current_connection_request_]->RunLoop(context, writer);
}
- ::grpc::Status SendAclData(
- ::grpc::ServerContext* context, const LeAclData* request, ::google::protobuf::Empty* response) override {
+ ::grpc::Status SendAclData(::grpc::ServerContext* context, const LeAclData* request,
+ ::google::protobuf::Empty* response) override {
std::promise<void> promise;
auto future = promise.get_future();
{
std::unique_lock<std::mutex> lock(acl_connections_mutex_);
auto connection = acl_connections_.find(request->handle());
if (connection == acl_connections_.end()) {
+ LOG_ERROR("Invalid handle");
return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle");
- }
- connection->second.connection_->GetAclQueueEnd()->RegisterEnqueue(
- facade_handler_,
- common::Bind(
- &LeAclManagerFacadeService::enqueue_packet,
- common::Unretained(this),
- common::Unretained(request),
- common::Passed(std::move(promise))));
- auto status = future.wait_for(std::chrono::milliseconds(1000));
- if (status != std::future_status::ready) {
- return ::grpc::Status(::grpc::StatusCode::RESOURCE_EXHAUSTED, "Can't send packet");
+ } else {
+ connection->second->GetAclQueueEnd()->RegisterEnqueue(
+ facade_handler_, common::Bind(&LeAclManagerFacadeService::enqueue_packet, common::Unretained(this),
+ common::Unretained(request), common::Passed(std::move(promise))));
}
}
+ future.wait();
return ::grpc::Status::OK;
}
std::unique_ptr<BasePacketBuilder> enqueue_packet(const LeAclData* request, std::promise<void> promise) {
- auto connection = acl_connections_.find(request->handle());
- ASSERT_LOG(connection != acl_connections_.end(), "handle %d", request->handle());
- connection->second.connection_->GetAclQueueEnd()->UnregisterEnqueue();
+ acl_connections_[request->handle()]->GetAclQueueEnd()->UnregisterEnqueue();
std::unique_ptr<RawBuilder> packet =
std::make_unique<RawBuilder>(std::vector<uint8_t>(request->payload().begin(), request->payload().end()));
promise.set_value();
return packet;
}
- ::grpc::Status FetchAclData(
- ::grpc::ServerContext* context, const LeHandleMsg* request, ::grpc::ServerWriter<LeAclData>* writer) override {
- auto connection = acl_connections_.find(request->handle());
- if (connection == acl_connections_.end()) {
- return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Invalid handle");
- }
- return connection->second.pending_acl_data_.RunLoop(context, writer);
+ ::grpc::Status FetchAclData(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
+ ::grpc::ServerWriter<LeAclData>* writer) override {
+ return pending_acl_data_.RunLoop(context, writer);
+ }
+
+ static inline uint16_t to_handle(uint32_t current_request) {
+ return (current_request + 0x10) % 0xe00;
}
static inline std::string builder_to_string(std::unique_ptr<BasePacketBuilder> builder) {
@@ -202,113 +150,163 @@ class LeAclManagerFacadeService : public LeAclManagerFacade::Service, public LeC
return std::string(bytes.begin(), bytes.end());
}
- void on_incoming_acl(std::shared_ptr<LeAclConnection> connection, uint16_t handle) {
+ void on_incoming_acl(std::shared_ptr<AclConnection> connection, uint16_t handle) {
auto packet = connection->GetAclQueueEnd()->TryDequeue();
- auto connection_tracker = acl_connections_.find(handle);
- ASSERT_LOG(connection_tracker != acl_connections_.end(), "handle %d", handle);
LeAclData acl_data;
acl_data.set_handle(handle);
acl_data.set_payload(std::string(packet->begin(), packet->end()));
- connection_tracker->second.pending_acl_data_.OnIncomingEvent(acl_data);
+ pending_acl_data_.OnIncomingEvent(acl_data);
}
- void OnLeConnectSuccess(AddressWithType address_with_type, std::unique_ptr<LeAclConnection> connection) override {
- LOG_INFO("%s", address_with_type.ToString().c_str());
+ void on_disconnect(std::shared_ptr<AclConnection> connection, uint32_t entry, ErrorCode code) {
+ connection->GetAclQueueEnd()->UnregisterDequeue();
+ connection->Finish();
+ std::unique_ptr<BasePacketBuilder> builder =
+ DisconnectBuilder::Create(to_handle(entry), static_cast<DisconnectReason>(code));
+ LeConnectionEvent disconnection;
+ disconnection.set_event(builder_to_string(std::move(builder)));
+ per_connection_events_[entry]->OnIncomingEvent(disconnection);
+ }
+
+ void OnLeConnectSuccess(AddressWithType address_with_type,
+ std::unique_ptr<::bluetooth::hci::AclConnection> connection) override {
+ LOG_DEBUG("%s", address_with_type.ToString().c_str());
std::unique_lock<std::mutex> lock(acl_connections_mutex_);
auto addr = address_with_type.GetAddress();
- std::shared_ptr<LeAclConnection> shared_connection = std::move(connection);
- uint16_t handle = shared_connection->GetHandle();
- acl_connections_.emplace(
- std::piecewise_construct,
- std::forward_as_tuple(handle),
- std::forward_as_tuple(handle, shared_connection, per_connection_events_[current_connection_request_]));
+ std::shared_ptr<::bluetooth::hci::AclConnection> shared_connection = std::move(connection);
+ acl_connections_.emplace(to_handle(current_connection_request_), shared_connection);
+ auto remote_address = shared_connection->GetAddress().ToString();
shared_connection->GetAclQueueEnd()->RegisterDequeue(
- facade_handler_,
- common::Bind(&LeAclManagerFacadeService::on_incoming_acl, common::Unretained(this), shared_connection, handle));
- auto callbacks = acl_connections_.find(handle)->second.GetCallbacks();
- shared_connection->RegisterCallbacks(callbacks, facade_handler_);
+ facade_handler_, common::Bind(&LeAclManagerFacadeService::on_incoming_acl, common::Unretained(this),
+ shared_connection, to_handle(current_connection_request_)));
+ shared_connection->RegisterDisconnectCallback(
+ common::BindOnce(&LeAclManagerFacadeService::on_disconnect, common::Unretained(this), shared_connection,
+ current_connection_request_),
+ facade_handler_);
+ shared_connection->RegisterCallbacks(this, facade_handler_);
{
std::unique_ptr<BasePacketBuilder> builder = LeConnectionCompleteBuilder::Create(
- ErrorCode::SUCCESS,
- handle,
- Role::CENTRAL,
- address_with_type.GetAddressType(),
- addr,
- 1,
- 2,
- 3,
- ClockAccuracy::PPM_20);
+ ErrorCode::SUCCESS, to_handle(current_connection_request_), Role::MASTER, address_with_type.GetAddressType(),
+ addr, 1, 2, 3, MasterClockAccuracy::PPM_20);
LeConnectionEvent success;
- success.set_payload(builder_to_string(std::move(builder)));
+ success.set_event(builder_to_string(std::move(builder)));
per_connection_events_[current_connection_request_]->OnIncomingEvent(success);
}
current_connection_request_++;
}
+ void OnMasterLinkKeyComplete(uint16_t connection_handle, KeyFlag key_flag) override {
+ LOG_DEBUG("OnMasterLinkKeyComplete connection_handle:%d", connection_handle);
+ }
+
+ void OnRoleChange(Address bd_addr, Role new_role) override {
+ LOG_DEBUG("OnRoleChange bd_addr:%s, new_role:%d", bd_addr.ToString().c_str(), (uint8_t)new_role);
+ }
+
+ void OnReadDefaultLinkPolicySettingsComplete(uint16_t default_link_policy_settings) override {
+ LOG_DEBUG("OnReadDefaultLinkPolicySettingsComplete default_link_policy_settings:%d", default_link_policy_settings);
+ }
+
void OnLeConnectFail(AddressWithType address, ErrorCode reason) override {
std::unique_ptr<BasePacketBuilder> builder = LeConnectionCompleteBuilder::Create(
- reason, 0, Role::CENTRAL, address.GetAddressType(), address.GetAddress(), 0, 0, 0, ClockAccuracy::PPM_20);
+ reason, 0, Role::MASTER, address.GetAddressType(), address.GetAddress(), 0, 0, 0, MasterClockAccuracy::PPM_20);
LeConnectionEvent fail;
- fail.set_payload(builder_to_string(std::move(builder)));
+ fail.set_event(builder_to_string(std::move(builder)));
per_connection_events_[current_connection_request_]->OnIncomingEvent(fail);
current_connection_request_++;
}
- class Connection : public LeConnectionManagementCallbacks {
- public:
- Connection(
- uint16_t handle,
- std::shared_ptr<LeAclConnection> connection,
- std::shared_ptr<::bluetooth::grpc::GrpcEventQueue<LeConnectionEvent>> event_stream)
- : handle_(handle), connection_(std::move(connection)), event_stream_(std::move(event_stream)) {}
- void OnConnectionUpdate(
- hci::ErrorCode hci_status,
- uint16_t connection_interval,
- uint16_t connection_latency,
- uint16_t supervision_timeout) override {
- LOG_INFO(
- "interval: 0x%hx, latency: 0x%hx, timeout 0x%hx",
- connection_interval,
- connection_latency,
- supervision_timeout);
- }
+ void OnConnectionPacketTypeChanged(uint16_t packet_type) override {
+ LOG_DEBUG("OnConnectionPacketTypeChanged packet_type:%d", packet_type);
+ }
- void OnDataLengthChange(uint16_t tx_octets, uint16_t tx_time, uint16_t rx_octets, uint16_t rx_time) override {
- LOG_INFO(
- "tx_octets: 0x%hx, tx_time: 0x%hx, rx_octets 0x%hx, rx_time 0x%hx", tx_octets, tx_time, rx_octets, rx_time);
- }
+ void OnAuthenticationComplete() override {
+ LOG_DEBUG("OnAuthenticationComplete");
+ }
- void OnPhyUpdate(hci::ErrorCode hci_status, uint8_t tx_phy, uint8_t rx_phy) override {}
- void OnLocalAddressUpdate(AddressWithType address_with_type) override {}
- void OnDisconnection(ErrorCode reason) override {
- std::unique_ptr<BasePacketBuilder> builder =
- DisconnectionCompleteBuilder::Create(ErrorCode::SUCCESS, handle_, reason);
- LeConnectionEvent disconnection;
- disconnection.set_payload(builder_to_string(std::move(builder)));
- event_stream_->OnIncomingEvent(disconnection);
- }
+ void OnEncryptionChange(EncryptionEnabled enabled) override {
+ LOG_DEBUG("OnConnectionPacketTypeChanged enabled:%d", (uint8_t)enabled);
+ }
- void OnReadRemoteVersionInformationComplete(
- hci::ErrorCode hci_status, uint8_t lmp_version, uint16_t manufacturer_name, uint16_t sub_version) override {}
+ void OnChangeConnectionLinkKeyComplete() override {
+ LOG_DEBUG("OnChangeConnectionLinkKeyComplete");
+ };
- LeConnectionManagementCallbacks* GetCallbacks() {
- return this;
- }
+ void OnReadClockOffsetComplete(uint16_t clock_offset) override {
+ LOG_DEBUG("OnReadClockOffsetComplete clock_offset:%d", clock_offset);
+ };
- uint16_t handle_;
- std::shared_ptr<LeAclConnection> connection_;
- std::shared_ptr<::bluetooth::grpc::GrpcEventQueue<LeConnectionEvent>> event_stream_;
- ::bluetooth::grpc::GrpcEventQueue<LeAclData> pending_acl_data_{std::string("PendingAclData") +
- std::to_string(handle_)};
+ void OnModeChange(Mode current_mode, uint16_t interval) override {
+ LOG_DEBUG("OnModeChange Mode:%d, interval:%d", (uint8_t)current_mode, interval);
};
+ void OnQosSetupComplete(ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth, uint32_t latency,
+ uint32_t delay_variation) override {
+ LOG_DEBUG("OnQosSetupComplete service_type:%d, token_rate:%d, peak_bandwidth:%d, latency:%d, delay_variation:%d",
+ (uint8_t)service_type, token_rate, peak_bandwidth, latency, delay_variation);
+ }
+
+ void OnFlowSpecificationComplete(FlowDirection flow_direction, ServiceType service_type, uint32_t token_rate,
+ uint32_t token_bucket_size, uint32_t peak_bandwidth,
+ uint32_t access_latency) override {
+ LOG_DEBUG(
+ "OnFlowSpecificationComplete flow_direction:%d. service_type:%d, token_rate:%d, token_bucket_size:%d, "
+ "peak_bandwidth:%d, access_latency:%d",
+ (uint8_t)flow_direction, (uint8_t)service_type, token_rate, token_bucket_size, peak_bandwidth, access_latency);
+ }
+
+ void OnFlushOccurred() override {
+ LOG_DEBUG("OnFlushOccurred");
+ }
+
+ void OnRoleDiscoveryComplete(Role current_role) override {
+ LOG_DEBUG("OnRoleDiscoveryComplete current_role:%d", (uint8_t)current_role);
+ }
+
+ void OnReadLinkPolicySettingsComplete(uint16_t link_policy_settings) override {
+ LOG_DEBUG("OnReadLinkPolicySettingsComplete link_policy_settings:%d", link_policy_settings);
+ }
+
+ void OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout) override {
+ LOG_DEBUG("OnReadAutomaticFlushTimeoutComplete flush_timeout:%d", flush_timeout);
+ }
+
+ void OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level) override {
+ LOG_DEBUG("OnReadTransmitPowerLevelComplete transmit_power_level:%d", transmit_power_level);
+ }
+
+ void OnReadLinkSupervisionTimeoutComplete(uint16_t link_supervision_timeout) override {
+ LOG_DEBUG("OnReadLinkSupervisionTimeoutComplete link_supervision_timeout:%d", link_supervision_timeout);
+ }
+
+ void OnReadFailedContactCounterComplete(uint16_t failed_contact_counter) override {
+ LOG_DEBUG("OnReadFailedContactCounterComplete failed_contact_counter:%d", failed_contact_counter);
+ }
+
+ void OnReadLinkQualityComplete(uint8_t link_quality) override {
+ LOG_DEBUG("OnReadLinkQualityComplete link_quality:%d", link_quality);
+ }
+
+ void OnReadAfhChannelMapComplete(AfhMode afh_mode, std::array<uint8_t, 10> afh_channel_map) override {
+ LOG_DEBUG("OnReadAfhChannelMapComplete afh_mode:%d", (uint8_t)afh_mode);
+ }
+
+ void OnReadRssiComplete(uint8_t rssi) override {
+ LOG_DEBUG("OnReadRssiComplete rssi:%d", rssi);
+ }
+
+ void OnReadClockComplete(uint32_t clock, uint16_t accuracy) override {
+ LOG_DEBUG("OnReadClockComplete clock:%d, accuracy:%d", clock, accuracy);
+ }
+
private:
AclManager* acl_manager_;
::bluetooth::os::Handler* facade_handler_;
mutable std::mutex acl_connections_mutex_;
- std::vector<std::shared_ptr<::bluetooth::grpc::GrpcEventQueue<LeConnectionEvent>>> per_connection_events_;
- std::map<uint16_t, Connection> acl_connections_;
+ std::map<uint16_t, std::shared_ptr<AclConnection>> acl_connections_;
+ ::bluetooth::grpc::GrpcEventQueue<LeAclData> pending_acl_data_{"FetchAclData"};
+ std::vector<std::unique_ptr<::bluetooth::grpc::GrpcEventQueue<LeConnectionEvent>>> per_connection_events_;
uint32_t current_connection_request_{0};
};
diff --git a/gd/hci/facade/le_acl_manager_facade.proto b/gd/hci/facade/le_acl_manager_facade.proto
index ed1000ac5..8450b9255 100644
--- a/gd/hci/facade/le_acl_manager_facade.proto
+++ b/gd/hci/facade/le_acl_manager_facade.proto
@@ -3,15 +3,14 @@ syntax = "proto3";
package bluetooth.hci;
import "google/protobuf/empty.proto";
-import "facade/common.proto";
service LeAclManagerFacade {
- rpc CreateConnection(bluetooth.facade.BluetoothAddressWithType) returns (stream LeConnectionEvent) {}
- rpc CancelConnection(bluetooth.facade.BluetoothAddressWithType) returns (google.protobuf.Empty) {}
+ rpc CreateConnection(LeConnectionMsg) returns (stream LeConnectionEvent) {}
+ rpc CancelConnection(LeConnectionMsg) returns (google.protobuf.Empty) {}
rpc Disconnect(LeHandleMsg) returns (google.protobuf.Empty) {}
- rpc ConnectionCommand(LeConnectionCommandMsg) returns (google.protobuf.Empty) {}
+ rpc AuthenticationRequested(LeHandleMsg) returns (google.protobuf.Empty) {}
rpc SendAclData(LeAclData) returns (google.protobuf.Empty) {}
- rpc FetchAclData(LeHandleMsg) returns (stream LeAclData) {}
+ rpc FetchAclData(google.protobuf.Empty) returns (stream LeAclData) {}
rpc FetchIncomingConnection(google.protobuf.Empty) returns (stream LeConnectionEvent) {}
}
@@ -19,16 +18,16 @@ message LeHandleMsg {
uint32 handle = 1;
}
-message LeConnectionEvent {
- bytes payload = 1;
+message LeConnectionMsg {
+ uint32 address_type = 1;
+ bytes address = 2;
}
-message LeConnectionCommandMsg {
- bytes packet = 1;
+message LeConnectionEvent {
+ bytes event = 1;
}
message LeAclData {
uint32 handle = 1;
bytes payload = 2;
}
-
diff --git a/gd/hci/facade/le_advertising_manager_facade.cc b/gd/hci/facade/le_advertising_manager_facade.cc
index 8e017bb1b..bfba5da80 100644
--- a/gd/hci/facade/le_advertising_manager_facade.cc
+++ b/gd/hci/facade/le_advertising_manager_facade.cc
@@ -59,6 +59,8 @@ bool AdvertisingConfigFromProto(const AdvertisingConfig& config_proto, hci::Adve
config->scan_response.push_back(GapDataFromProto(elem));
}
+ hci::Address::FromString(config_proto.random_address().address(), config->random_address);
+
if (config_proto.interval_min() > UINT16_MAX || config_proto.interval_min() < 0) {
LOG_WARN("Bad interval_min: %d", config_proto.interval_min());
return false;
@@ -71,9 +73,9 @@ bool AdvertisingConfigFromProto(const AdvertisingConfig& config_proto, hci::Adve
}
config->interval_max = static_cast<uint16_t>(config_proto.interval_max());
- config->advertising_type = static_cast<hci::AdvertisingType>(config_proto.advertising_type());
+ config->event_type = static_cast<hci::AdvertisingEventType>(config_proto.event_type());
- config->own_address_type = static_cast<::bluetooth::hci::OwnAddressType>(config_proto.own_address_type());
+ config->address_type = static_cast<::bluetooth::hci::AddressType>(config_proto.address_type());
config->peer_address_type = static_cast<::bluetooth::hci::PeerAddressType>(config_proto.peer_address_type());
@@ -127,21 +129,16 @@ class LeAdvertisingManagerFacadeService : public LeAdvertisingManagerFacade::Ser
::grpc::Status CreateAdvertiser(::grpc::ServerContext* context, const CreateAdvertiserRequest* request,
CreateAdvertiserResponse* response) override {
- hci::ExtendedAdvertisingConfig config = {};
+ hci::AdvertisingConfig config = {};
if (!AdvertisingConfigFromProto(request->config(), &config)) {
LOG_WARN("Error parsing advertising config %s", request->SerializeAsString().c_str());
response->set_advertiser_id(LeAdvertisingManager::kInvalidId);
return ::grpc::Status(::grpc::StatusCode::INVALID_ARGUMENT, "Error while parsing advertising config");
}
LeAdvertiser le_advertiser(config);
- auto advertiser_id = le_advertising_manager_->ExtendedCreateAdvertiser(
- -1,
- config,
- common::Bind(&LeAdvertiser::ScanCallback, common::Unretained(&le_advertiser)),
- common::Bind(&LeAdvertiser::TerminatedCallback, common::Unretained(&le_advertiser)),
- 0,
- 0,
- facade_handler_);
+ auto advertiser_id = le_advertising_manager_->CreateAdvertiser(
+ config, common::Bind(&LeAdvertiser::ScanCallback, common::Unretained(&le_advertiser)),
+ common::Bind(&LeAdvertiser::TerminatedCallback, common::Unretained(&le_advertiser)), facade_handler_);
if (advertiser_id != LeAdvertisingManager::kInvalidId) {
le_advertiser.SetAdvertiserId(advertiser_id);
le_advertisers_.push_back(le_advertiser);
diff --git a/gd/hci/facade/le_advertising_manager_facade.proto b/gd/hci/facade/le_advertising_manager_facade.proto
index edb70cf52..9c75bd949 100644
--- a/gd/hci/facade/le_advertising_manager_facade.proto
+++ b/gd/hci/facade/le_advertising_manager_facade.proto
@@ -26,20 +26,21 @@ enum AdvertisingEventType {
enum AdvertisingFilterPolicy {
ALL_DEVICES = 0x0;
- LISTED_SCAN = 0x1;
- LISTED_CONNECT = 0x2;
- LISTED_SCAN_AND_CONNECT = 0x3;
+ WHITELISTED_SCAN = 0x1;
+ WHITELISTED_CONNECT = 0x2;
+ WHITELISTED_SCAN_AND_CONNECT = 0x3;
};
message AdvertisingConfig {
repeated GapDataMsg advertisement = 1;
repeated GapDataMsg scan_response = 2;
+ bluetooth.facade.BluetoothAddress random_address = 3;
// Unit: number of Bluetooth slots in 0.125 ms increment
int32 interval_min = 4;
// Unit: number of Bluetooth slots in 0.125 ms increment
int32 interval_max = 5;
- AdvertisingEventType advertising_type = 6;
- bluetooth.facade.BluetoothOwnAddressTypeEnum own_address_type = 7;
+ AdvertisingEventType event_type = 6;
+ bluetooth.facade.BluetoothAddressTypeEnum address_type = 7;
bluetooth.facade.BluetoothPeerAddressTypeEnum peer_address_type = 8;
bluetooth.facade.BluetoothAddress peer_address = 9;
int32 channel_map = 10;
@@ -86,4 +87,4 @@ message GetNumberOfAdvertisingInstancesResponse {
message RemoveAdvertiserRequest {
int32 advertiser_id = 1;
-}
+} \ No newline at end of file
diff --git a/gd/hci/facade/le_initiator_address_facade.cc b/gd/hci/facade/le_initiator_address_facade.cc
deleted file mode 100644
index d2f7bcef7..000000000
--- a/gd/hci/facade/le_initiator_address_facade.cc
+++ /dev/null
@@ -1,128 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/facade/le_initiator_address_facade.h"
-
-#include <condition_variable>
-#include <memory>
-#include <mutex>
-
-#include "common/bind.h"
-#include "grpc/grpc_event_queue.h"
-#include "hci/acl_manager.h"
-#include "hci/facade/le_initiator_address_facade.grpc.pb.h"
-#include "hci/facade/le_initiator_address_facade.pb.h"
-#include "hci/hci_packets.h"
-#include "packet/raw_builder.h"
-
-using ::grpc::ServerAsyncResponseWriter;
-using ::grpc::ServerAsyncWriter;
-using ::grpc::ServerContext;
-
-using ::bluetooth::packet::RawBuilder;
-
-namespace bluetooth {
-namespace hci {
-namespace facade {
-
-class LeInitiatorAddressFacadeService : public LeInitiatorAddressFacade::Service {
- public:
- LeInitiatorAddressFacadeService(AclManager* acl_manager, ::bluetooth::os::Handler* facade_handler)
- : acl_manager_(acl_manager),
- address_manager_(acl_manager_->GetLeAddressManager()),
- facade_handler_(facade_handler) {
- ASSERT(facade_handler_ != nullptr);
- }
-
- ::grpc::Status SetPrivacyPolicyForInitiatorAddress(
- ::grpc::ServerContext* context, const PrivacyPolicy* request, ::google::protobuf::Empty* writer) override {
- Address address = Address::kEmpty;
- LeAddressManager::AddressPolicy address_policy =
- static_cast<LeAddressManager::AddressPolicy>(request->address_policy());
- if (address_policy == LeAddressManager::AddressPolicy::USE_STATIC_ADDRESS) {
- ASSERT(Address::FromString(request->address_with_type().address().address(), address));
- }
- AddressWithType address_with_type(address, static_cast<AddressType>(request->address_with_type().type()));
- crypto_toolbox::Octet16 irk = {};
- auto request_irk_length = request->rotation_irk().end() - request->rotation_irk().begin();
- if (request_irk_length == crypto_toolbox::OCTET16_LEN) {
- std::vector<uint8_t> irk_data(request->rotation_irk().begin(), request->rotation_irk().end());
- std::copy_n(irk_data.begin(), crypto_toolbox::OCTET16_LEN, irk.begin());
- } else {
- ASSERT(request_irk_length == 0);
- }
- auto minimum_rotation_time = std::chrono::milliseconds(request->minimum_rotation_time());
- auto maximum_rotation_time = std::chrono::milliseconds(request->maximum_rotation_time());
- acl_manager_->SetPrivacyPolicyForInitiatorAddress(
- address_policy, address_with_type, minimum_rotation_time, maximum_rotation_time);
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status GetCurrentInitiatorAddress(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::bluetooth::facade::BluetoothAddressWithType* response) override {
- AddressWithType current = address_manager_->GetCurrentAddress();
- auto bluetooth_address = new ::bluetooth::facade::BluetoothAddress();
- bluetooth_address->set_address(current.GetAddress().ToString());
- response->set_type(static_cast<::bluetooth::facade::BluetoothAddressTypeEnum>(current.GetAddressType()));
- response->set_allocated_address(bluetooth_address);
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status GetAnotherAddress(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::bluetooth::facade::BluetoothAddressWithType* response) override {
- AddressWithType another = address_manager_->GetAnotherAddress();
- auto bluetooth_address = new ::bluetooth::facade::BluetoothAddress();
- bluetooth_address->set_address(another.GetAddress().ToString());
- response->set_type(static_cast<::bluetooth::facade::BluetoothAddressTypeEnum>(another.GetAddressType()));
- response->set_allocated_address(bluetooth_address);
- return ::grpc::Status::OK;
- }
-
- private:
- AclManager* acl_manager_;
- LeAddressManager* address_manager_;
- ::bluetooth::os::Handler* facade_handler_;
-};
-
-void LeInitiatorAddressFacadeModule::ListDependencies(ModuleList* list) {
- ::bluetooth::grpc::GrpcFacadeModule::ListDependencies(list);
- list->add<AclManager>();
-}
-
-void LeInitiatorAddressFacadeModule::Start() {
- ::bluetooth::grpc::GrpcFacadeModule::Start();
- service_ = new LeInitiatorAddressFacadeService(GetDependency<AclManager>(), GetHandler());
-}
-
-void LeInitiatorAddressFacadeModule::Stop() {
- delete service_;
- ::bluetooth::grpc::GrpcFacadeModule::Stop();
-}
-
-::grpc::Service* LeInitiatorAddressFacadeModule::GetService() const {
- return service_;
-}
-
-const ModuleFactory LeInitiatorAddressFacadeModule::Factory =
- ::bluetooth::ModuleFactory([]() { return new LeInitiatorAddressFacadeModule(); });
-
-} // namespace facade
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/facade/le_initiator_address_facade.h b/gd/hci/facade/le_initiator_address_facade.h
deleted file mode 100644
index 9e1a42d46..000000000
--- a/gd/hci/facade/le_initiator_address_facade.h
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <grpc++/grpc++.h>
-
-#include "grpc/grpc_module.h"
-#include "hci/acl_manager.h"
-
-namespace bluetooth {
-namespace hci {
-namespace facade {
-
-class LeInitiatorAddressFacadeService;
-
-class LeInitiatorAddressFacadeModule : public ::bluetooth::grpc::GrpcFacadeModule {
- public:
- static const ModuleFactory Factory;
-
- void ListDependencies(ModuleList* list) override;
- void Start() override;
- void Stop() override;
- ::grpc::Service* GetService() const override;
-
- private:
- LeInitiatorAddressFacadeService* service_;
-};
-
-} // namespace facade
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/facade/le_initiator_address_facade.proto b/gd/hci/facade/le_initiator_address_facade.proto
deleted file mode 100644
index 50aeea249..000000000
--- a/gd/hci/facade/le_initiator_address_facade.proto
+++ /dev/null
@@ -1,28 +0,0 @@
-syntax = "proto3";
-
-package bluetooth.hci;
-
-import "google/protobuf/empty.proto";
-import "facade/common.proto";
-
-service LeInitiatorAddressFacade {
- rpc SetPrivacyPolicyForInitiatorAddress(PrivacyPolicy) returns (google.protobuf.Empty) {}
- rpc GetCurrentInitiatorAddress(google.protobuf.Empty) returns (bluetooth.facade.BluetoothAddressWithType) {}
- rpc GetAnotherAddress(google.protobuf.Empty) returns (bluetooth.facade.BluetoothAddressWithType) {}
-}
-
-enum AddressPolicy {
- POLICY_NOT_SET = 0x00;
- USE_PUBLIC_ADDRESS = 0x01;
- USE_STATIC_ADDRESS = 0x02;
- USE_NON_RESOLVABLE_ADDRESS = 0x03;
- USE_RESOLVABLE_ADDRESS = 0x04;
-}
-
-message PrivacyPolicy {
- AddressPolicy address_policy = 1;
- facade.BluetoothAddressWithType address_with_type = 2;
- bytes rotation_irk = 3;
- uint64 minimum_rotation_time = 4;
- uint64 maximum_rotation_time = 5;
-}
diff --git a/gd/hci/facade/le_scanning_manager_facade.cc b/gd/hci/facade/le_scanning_manager_facade.cc
index 4306fc0f3..bf790b78e 100644
--- a/gd/hci/facade/le_scanning_manager_facade.cc
+++ b/gd/hci/facade/le_scanning_manager_facade.cc
@@ -26,6 +26,7 @@
#include "hci/facade/le_scanning_manager_facade.grpc.pb.h"
#include "hci/facade/le_scanning_manager_facade.h"
#include "hci/facade/le_scanning_manager_facade.pb.h"
+#include "hci/le_report.h"
#include "os/log.h"
#include "packet/raw_builder.h"
@@ -39,63 +40,105 @@ using ::grpc::ServerContext;
using ::grpc::ServerWriter;
using ::grpc::Status;
-class LeScanningManagerFacadeService : public LeScanningManagerFacade::Service, ScanningCallback {
+class LeScanningManagerFacadeService : public LeScanningManagerFacade::Service, public LeScanningManagerCallbacks {
public:
LeScanningManagerFacadeService(LeScanningManager* le_scanning_manager, os::Handler* facade_handler)
: le_scanning_manager_(le_scanning_manager), facade_handler_(facade_handler) {
ASSERT(le_scanning_manager_ != nullptr);
ASSERT(facade_handler_ != nullptr);
- le_scanning_manager_->RegisterScanningCallback(this);
}
::grpc::Status StartScan(::grpc::ServerContext* context, const ::google::protobuf::Empty*,
::grpc::ServerWriter<LeReportMsg>* writer) override {
- le_scanning_manager_->Scan(true);
+ le_scanning_manager_->StartScan(this);
return pending_events_.RunLoop(context, writer);
}
::grpc::Status StopScan(::grpc::ServerContext* context, const ::google::protobuf::Empty*,
ScanStoppedMsg* response) override {
- le_scanning_manager_->Scan(false);
+ std::shared_ptr<std::promise<void>> on_stopped = std::make_shared<std::promise<void>>();
+ auto future = on_stopped->get_future();
+ le_scanning_manager_->StopScan(
+ common::Bind([](std::shared_ptr<std::promise<void>> p) { p->set_value(); }, on_stopped));
+ auto result = future.wait_for(std::chrono::milliseconds(1000));
+ ASSERT(result == std::future_status::ready);
return ::grpc::Status::OK;
}
- void OnScannerRegistered(const bluetooth::hci::Uuid app_uuid, ScannerId scanner_id, ScanningStatus status){};
- void OnScanResult(
- uint16_t event_type,
- uint8_t address_type,
- Address address,
- uint8_t primary_phy,
- uint8_t secondary_phy,
- uint8_t advertising_sid,
- int8_t tx_power,
- int8_t rssi,
- uint16_t periodic_advertising_interval,
- std::vector<uint8_t> advertising_data) {
+ void on_advertisements(std::vector<std::shared_ptr<LeReport>> reports) override {
+ for (const auto report : reports) {
+ switch (report->report_type_) {
+ case hci::LeReport::ReportType::ADVERTISING_EVENT: {
+ LeReportMsg le_report_msg;
+ std::vector<LeAdvertisingReport> advertisements;
+ LeAdvertisingReport le_advertising_report;
+ le_advertising_report.address_type_ = report->address_type_;
+ le_advertising_report.address_ = report->address_;
+ le_advertising_report.advertising_data_ = report->gap_data_;
+ le_advertising_report.event_type_ = report->advertising_event_type_;
+ le_advertising_report.rssi_ = report->rssi_;
+ advertisements.push_back(le_advertising_report);
+
+ auto builder = LeAdvertisingReportBuilder::Create(advertisements);
+ std::vector<uint8_t> bytes;
+ BitInserter bit_inserter(bytes);
+ builder->Serialize(bit_inserter);
+ le_report_msg.set_event(std::string(bytes.begin(), bytes.end()));
+ pending_events_.OnIncomingEvent(std::move(le_report_msg));
+ } break;
+ case hci::LeReport::ReportType::EXTENDED_ADVERTISING_EVENT: {
+ LeReportMsg le_report_msg;
+ std::vector<LeExtendedAdvertisingReport> advertisements;
+ LeExtendedAdvertisingReport le_extended_advertising_report;
+ le_extended_advertising_report.address_ = report->address_;
+ le_extended_advertising_report.advertising_data_ = report->gap_data_;
+ le_extended_advertising_report.rssi_ = report->rssi_;
+ advertisements.push_back(le_extended_advertising_report);
+
+ auto builder = LeExtendedAdvertisingReportBuilder::Create(advertisements);
+ std::vector<uint8_t> bytes;
+ BitInserter bit_inserter(bytes);
+ builder->Serialize(bit_inserter);
+ le_report_msg.set_event(std::string(bytes.begin(), bytes.end()));
+ pending_events_.OnIncomingEvent(std::move(le_report_msg));
+ } break;
+ case hci::LeReport::ReportType::DIRECTED_ADVERTISING_EVENT: {
+ LeReportMsg le_report_msg;
+ std::vector<LeDirectedAdvertisingReport> advertisements;
+ LeDirectedAdvertisingReport le_directed_advertising_report;
+ le_directed_advertising_report.address_ = report->address_;
+ le_directed_advertising_report.direct_address_ = ((DirectedLeReport*)report.get())->direct_address_;
+ le_directed_advertising_report.direct_address_type_ = DirectAddressType::RANDOM_DEVICE_ADDRESS;
+ le_directed_advertising_report.event_type_ = DirectAdvertisingEventType::ADV_DIRECT_IND;
+ le_directed_advertising_report.rssi_ = report->rssi_;
+ advertisements.push_back(le_directed_advertising_report);
+
+ auto builder = LeDirectedAdvertisingReportBuilder::Create(advertisements);
+ std::vector<uint8_t> bytes;
+ BitInserter bit_inserter(bytes);
+ builder->Serialize(bit_inserter);
+ le_report_msg.set_event(std::string(bytes.begin(), bytes.end()));
+ pending_events_.OnIncomingEvent(std::move(le_report_msg));
+ } break;
+ default:
+ LOG_INFO("Skipping unknown report type %d", static_cast<int>(report->report_type_));
+ }
+ }
+ }
+
+ void on_timeout() override {
LeReportMsg le_report_msg;
- std::vector<LeExtendedAdvertisingReport> advertisements;
- LeExtendedAdvertisingReport le_extended_advertising_report;
- le_extended_advertising_report.address_type_ = (DirectAdvertisingAddressType)address_type;
- le_extended_advertising_report.address_ = address;
- le_extended_advertising_report.advertising_data_ = advertising_data;
- le_extended_advertising_report.rssi_ = rssi;
- advertisements.push_back(le_extended_advertising_report);
-
- auto builder = LeExtendedAdvertisingReportBuilder::Create(advertisements);
+ auto builder = LeScanTimeoutBuilder::Create();
std::vector<uint8_t> bytes;
BitInserter bit_inserter(bytes);
builder->Serialize(bit_inserter);
le_report_msg.set_event(std::string(bytes.begin(), bytes.end()));
pending_events_.OnIncomingEvent(std::move(le_report_msg));
- };
- void OnTrackAdvFoundLost(AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info){};
- void OnBatchScanReports(int client_if, int status, int report_format, int num_records, std::vector<uint8_t> data){};
- void OnBatchScanThresholdCrossed(int client_if){};
- void OnTimeout(){};
- void OnFilterEnable(Enable enable, uint8_t status){};
- void OnFilterParamSetup(uint8_t available_spaces, ApcfAction action, uint8_t status){};
- void OnFilterConfigCallback(
- ApcfFilterType filter_type, uint8_t available_spaces, ApcfAction action, uint8_t status){};
+ }
+
+ os::Handler* Handler() override {
+ return facade_handler_;
+ }
LeScanningManager* le_scanning_manager_;
os::Handler* facade_handler_;
diff --git a/gd/hci/fuzz/acl_manager_fuzz_test.cc b/gd/hci/fuzz/acl_manager_fuzz_test.cc
deleted file mode 100644
index 106b3bb2d..000000000
--- a/gd/hci/fuzz/acl_manager_fuzz_test.cc
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <stddef.h>
-#include <stdint.h>
-#include "fuzz/helpers.h"
-#include "hci/acl_manager.h"
-#include "hci/fuzz/fuzz_hci_layer.h"
-#include "hci/hci_layer.h"
-#include "module.h"
-#include "os/fuzz/fake_timerfd.h"
-#include "os/log.h"
-
-#include <fuzzer/FuzzedDataProvider.h>
-
-using bluetooth::FuzzTestModuleRegistry;
-using bluetooth::fuzz::GetArbitraryBytes;
-using bluetooth::hci::AclManager;
-using bluetooth::hci::HciLayer;
-using bluetooth::hci::fuzz::FuzzHciLayer;
-using bluetooth::os::fuzz::fake_timerfd_advance;
-using bluetooth::os::fuzz::fake_timerfd_cap_at;
-using bluetooth::os::fuzz::fake_timerfd_reset;
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
- FuzzedDataProvider dataProvider(data, size);
-
- static FuzzTestModuleRegistry moduleRegistry = FuzzTestModuleRegistry();
- FuzzHciLayer* fuzzHci = moduleRegistry.Inject<FuzzHciLayer>(&HciLayer::Factory);
- fuzzHci->TurnOnAutoReply(&dataProvider);
- moduleRegistry.Start<AclManager>();
- fuzzHci->TurnOffAutoReply();
-
- while (dataProvider.remaining_bytes() > 0) {
- const uint8_t action = dataProvider.ConsumeIntegralInRange(0, 2);
- switch (action) {
- case 1:
- fake_timerfd_advance(dataProvider.ConsumeIntegral<uint64_t>());
- break;
- case 2:
- fuzzHci->injectArbitrary(dataProvider);
- break;
- }
- }
-
- moduleRegistry.WaitForIdleAndStopAll();
- fake_timerfd_reset();
- return 0;
-}
diff --git a/gd/hci/fuzz/fuzz_hci_layer.cc b/gd/hci/fuzz/fuzz_hci_layer.cc
deleted file mode 100644
index c54960d56..000000000
--- a/gd/hci/fuzz/fuzz_hci_layer.cc
+++ /dev/null
@@ -1,195 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/fuzz/fuzz_hci_layer.h"
-#include "fuzz/helpers.h"
-
-namespace bluetooth {
-namespace hci {
-namespace fuzz {
-
-using bluetooth::common::ContextualCallback;
-using bluetooth::fuzz::GetArbitraryBytes;
-using bluetooth::fuzz::InvokeIfValid;
-
-hci::SecurityInterface* FuzzHciLayer::GetSecurityInterface(ContextualCallback<void(hci::EventView)> event_handler) {
- return &security_interface_;
-}
-
-hci::LeSecurityInterface* FuzzHciLayer::GetLeSecurityInterface(
- ContextualCallback<void(hci::LeMetaEventView)> event_handler) {
- return &le_security_interface_;
-}
-
-hci::AclConnectionInterface* FuzzHciLayer::GetAclConnectionInterface(
- ContextualCallback<void(hci::EventView)> event_handler,
- ContextualCallback<void(uint16_t, hci::ErrorCode)> on_disconnect,
- ContextualCallback<
- void(hci::ErrorCode, uint16_t, uint8_t version, uint16_t manufacturer_name, uint16_t sub_version)>
- on_read_remote_version) {
- return &acl_connection_interface_;
-}
-
-hci::LeAclConnectionInterface* FuzzHciLayer::GetLeAclConnectionInterface(
- ContextualCallback<void(hci::LeMetaEventView)> event_handler,
- ContextualCallback<void(uint16_t, hci::ErrorCode)> on_disconnect,
- ContextualCallback<
- void(hci::ErrorCode, uint16_t, uint8_t version, uint16_t manufacturer_name, uint16_t sub_version)>
- on_read_remote_version) {
- return &le_acl_connection_interface_;
-}
-
-hci::LeAdvertisingInterface* FuzzHciLayer::GetLeAdvertisingInterface(
- ContextualCallback<void(hci::LeMetaEventView)> event_handler) {
- return &le_advertising_interface_;
-}
-
-hci::LeScanningInterface* FuzzHciLayer::GetLeScanningInterface(
- ContextualCallback<void(hci::LeMetaEventView)> event_handler) {
- return &le_scanning_interface_;
-}
-
-hci::LeIsoInterface* FuzzHciLayer::GetLeIsoInterface(ContextualCallback<void(hci::LeMetaEventView)> event_handler) {
- return &le_iso_interface_;
-}
-
-void FuzzHciLayer::Start() {
- acl_dev_null_ = new os::fuzz::DevNullQueue<AclBuilder>(acl_queue_.GetDownEnd(), GetHandler());
- acl_dev_null_->Start();
- acl_inject_ = new os::fuzz::FuzzInjectQueue<AclView>(acl_queue_.GetDownEnd(), GetHandler());
-}
-
-void FuzzHciLayer::Stop() {
- acl_dev_null_->Stop();
- delete acl_dev_null_;
- delete acl_inject_;
-}
-
-void FuzzHciLayer::injectArbitrary(FuzzedDataProvider& fdp) {
- const uint8_t action = fdp.ConsumeIntegralInRange(0, 13);
- switch (action) {
- case 1:
- injectAclData(GetArbitraryBytes(&fdp));
- break;
- case 2:
- injectCommandComplete(GetArbitraryBytes(&fdp));
- break;
- case 3:
- injectCommandStatus(GetArbitraryBytes(&fdp));
- break;
- case 4:
- injectEvent(fdp);
- break;
- case 5:
- injectLeEvent(fdp);
- break;
- case 6:
- injectSecurityEvent(GetArbitraryBytes(&fdp));
- break;
- case 7:
- injectLeSecurityEvent(GetArbitraryBytes(&fdp));
- break;
- case 8:
- injectAclEvent(GetArbitraryBytes(&fdp));
- break;
- case 9:
- injectAclDisconnect(fdp);
- break;
- case 10:
- injectLeAclEvent(GetArbitraryBytes(&fdp));
- break;
- case 11:
- injectLeAclDisconnect(fdp);
- break;
- case 12:
- injectLeAdvertisingEvent(GetArbitraryBytes(&fdp));
- break;
- case 13:
- injectLeScanningEvent(GetArbitraryBytes(&fdp));
- break;
- }
-}
-
-void FuzzHciLayer::injectAclData(std::vector<uint8_t> data) {
- CONSTRUCT_VALID_UNIQUE_OTHERWISE_BAIL(hci::AclView, packet, data);
- acl_inject_->Inject(std::move(packet));
-}
-
-void FuzzHciLayer::injectCommandComplete(std::vector<uint8_t> data) {
- InvokeIfValid<hci::CommandCompleteView>(std::move(on_command_complete_), data);
-}
-
-void FuzzHciLayer::injectCommandStatus(std::vector<uint8_t> data) {
- InvokeIfValid<hci::CommandStatusView>(std::move(on_command_status_), data);
-}
-
-void FuzzHciLayer::injectEvent(FuzzedDataProvider& fdp) {
- auto handler_pair = event_handlers_.find(static_cast<EventCode>(fdp.ConsumeIntegral<uint8_t>()));
- if (handler_pair != event_handlers_.end()) {
- InvokeIfValid<EventView>(handler_pair->second, GetArbitraryBytes(&fdp));
- }
-}
-
-void FuzzHciLayer::injectLeEvent(FuzzedDataProvider& fdp) {
- auto handler_pair = le_event_handlers_.find(static_cast<SubeventCode>(fdp.ConsumeIntegral<uint8_t>()));
- if (handler_pair != le_event_handlers_.end()) {
- InvokeIfValid<LeMetaEventView>(handler_pair->second, GetArbitraryBytes(&fdp));
- }
-}
-
-void FuzzHciLayer::injectSecurityEvent(std::vector<uint8_t> data) {
- InvokeIfValid<EventView>(security_event_handler_, data);
-}
-
-void FuzzHciLayer::injectLeSecurityEvent(std::vector<uint8_t> data) {
- InvokeIfValid<LeMetaEventView>(le_security_event_handler_, data);
-}
-
-void FuzzHciLayer::injectAclEvent(std::vector<uint8_t> data) {
- InvokeIfValid<EventView>(acl_event_handler_, data);
-}
-
-void FuzzHciLayer::injectAclDisconnect(FuzzedDataProvider& fdp) {
- acl_on_disconnect_.InvokeIfNotEmpty(fdp.ConsumeIntegral<uint16_t>(),
- static_cast<hci::ErrorCode>(fdp.ConsumeIntegral<uint8_t>()));
-}
-
-void FuzzHciLayer::injectLeAclEvent(std::vector<uint8_t> data) {
- InvokeIfValid<LeMetaEventView>(le_acl_event_handler_, data);
-}
-
-void FuzzHciLayer::injectLeAclDisconnect(FuzzedDataProvider& fdp) {
- le_acl_on_disconnect_.InvokeIfNotEmpty(fdp.ConsumeIntegral<uint16_t>(),
- static_cast<hci::ErrorCode>(fdp.ConsumeIntegral<uint8_t>()));
-}
-
-void FuzzHciLayer::injectLeAdvertisingEvent(std::vector<uint8_t> data) {
- InvokeIfValid<LeMetaEventView>(le_advertising_event_handler_, data);
-}
-
-void FuzzHciLayer::injectLeScanningEvent(std::vector<uint8_t> data) {
- InvokeIfValid<LeMetaEventView>(le_scanning_event_handler_, data);
-}
-
-void FuzzHciLayer::injectLeIsoEvent(std::vector<uint8_t> data) {
- InvokeIfValid<LeMetaEventView>(le_iso_event_handler_, data);
-}
-
-const ModuleFactory FuzzHciLayer::Factory = ModuleFactory([]() { return new FuzzHciLayer(); });
-
-} // namespace fuzz
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/fuzz/fuzz_hci_layer.h b/gd/hci/fuzz/fuzz_hci_layer.h
deleted file mode 100644
index 3e92bcc42..000000000
--- a/gd/hci/fuzz/fuzz_hci_layer.h
+++ /dev/null
@@ -1,195 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "hci/command_interface.h"
-#include "hci/hci_layer.h"
-#include "os/fuzz/dev_null_queue.h"
-#include "os/fuzz/fuzz_inject_queue.h"
-#include "os/log.h"
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "fuzz/helpers.h"
-
-namespace bluetooth {
-namespace hci {
-namespace fuzz {
-
-template <typename T>
-class FuzzCommandInterface : public CommandInterface<T> {
- public:
- void EnqueueCommand(std::unique_ptr<T> command,
- common::ContextualOnceCallback<void(hci::CommandCompleteView)> on_complete) override {}
-
- void EnqueueCommand(std::unique_ptr<T> command,
- common::ContextualOnceCallback<void(hci::CommandStatusView)> on_status) override {}
-};
-
-class FuzzHciLayer : public HciLayer {
- public:
- void TurnOnAutoReply(FuzzedDataProvider* fdp) {
- auto_reply_fdp = fdp;
- }
-
- void TurnOffAutoReply() {
- auto_reply_fdp = nullptr;
- }
-
- void EnqueueCommand(
- std::unique_ptr<hci::CommandBuilder> command,
- common::ContextualOnceCallback<void(hci::CommandCompleteView)> on_complete) override {
- on_command_complete_ = std::move(on_complete);
- if (auto_reply_fdp != nullptr) {
- injectCommandComplete(bluetooth::fuzz::GetArbitraryBytes(auto_reply_fdp));
- }
- }
-
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(hci::CommandStatusView)> on_status) override {
- on_command_status_ = std::move(on_status);
- if (auto_reply_fdp != nullptr) {
- injectCommandStatus(bluetooth::fuzz::GetArbitraryBytes(auto_reply_fdp));
- }
- }
-
- common::BidiQueueEnd<hci::AclBuilder, hci::AclView>* GetAclQueueEnd() override {
- return acl_queue_.GetUpEnd();
- }
-
- common::BidiQueueEnd<hci::IsoBuilder, hci::IsoView>* GetIsoQueueEnd() override {
- return iso_queue_.GetUpEnd();
- }
-
- void RegisterEventHandler(hci::EventCode event, common::ContextualCallback<void(hci::EventView)> handler) override {
- event_handlers_[event] = handler;
- }
-
- void UnregisterEventHandler(hci::EventCode event) override {
- auto it = event_handlers_.find(event);
- if (it != event_handlers_.end()) {
- event_handlers_.erase(it);
- }
- }
-
- void RegisterLeEventHandler(hci::SubeventCode event,
- common::ContextualCallback<void(hci::LeMetaEventView)> handler) override {
- le_event_handlers_[event] = handler;
- }
-
- void UnregisterLeEventHandler(hci::SubeventCode event) override {
- auto it = le_event_handlers_.find(event);
- if (it != le_event_handlers_.end()) {
- le_event_handlers_.erase(it);
- }
- }
-
- hci::SecurityInterface* GetSecurityInterface(common::ContextualCallback<void(hci::EventView)> event_handler) override;
-
- hci::LeSecurityInterface* GetLeSecurityInterface(
- common::ContextualCallback<void(hci::LeMetaEventView)> event_handler) override;
-
- hci::AclConnectionInterface* GetAclConnectionInterface(
- common::ContextualCallback<void(hci::EventView)> event_handler,
- common::ContextualCallback<void(uint16_t, hci::ErrorCode)> on_disconnect,
- common::ContextualCallback<void(hci::ErrorCode hci_status, uint16_t, uint8_t, uint16_t, uint16_t)>
- on_read_remote_version) override;
-
- hci::LeAclConnectionInterface* GetLeAclConnectionInterface(
- common::ContextualCallback<void(hci::LeMetaEventView)> event_handler,
- common::ContextualCallback<void(uint16_t, hci::ErrorCode)> on_disconnect,
- common::ContextualCallback<void(hci::ErrorCode hci_status, uint16_t, uint8_t, uint16_t, uint16_t)>
- on_read_remote_version) override;
-
- hci::LeAdvertisingInterface* GetLeAdvertisingInterface(
- common::ContextualCallback<void(hci::LeMetaEventView)> event_handler) override;
-
- hci::LeScanningInterface* GetLeScanningInterface(
- common::ContextualCallback<void(hci::LeMetaEventView)> event_handler) override;
-
- hci::LeIsoInterface* GetLeIsoInterface(common::ContextualCallback<void(LeMetaEventView)> event_handler) override;
-
- void injectArbitrary(FuzzedDataProvider& fdp);
-
- std::string ToString() const override {
- return "FuzzHciLayer";
- }
-
- static const ModuleFactory Factory;
-
- protected:
- void ListDependencies(ModuleList* list) override {}
- void Start() override;
- void Stop() override;
-
- private:
- void injectAclData(std::vector<uint8_t> data);
-
- void injectCommandComplete(std::vector<uint8_t> data);
- void injectCommandStatus(std::vector<uint8_t> data);
-
- void injectEvent(FuzzedDataProvider& fdp);
- void injectLeEvent(FuzzedDataProvider& fdp);
-
- void injectSecurityEvent(std::vector<uint8_t> data);
- void injectLeSecurityEvent(std::vector<uint8_t> data);
-
- void injectAclEvent(std::vector<uint8_t> data);
- void injectAclDisconnect(FuzzedDataProvider& fdp);
- void injectLeAclEvent(std::vector<uint8_t> data);
- void injectLeAclDisconnect(FuzzedDataProvider& fdp);
-
- void injectLeAdvertisingEvent(std::vector<uint8_t> data);
-
- void injectLeScanningEvent(std::vector<uint8_t> data);
- void injectLeIsoEvent(std::vector<uint8_t> data);
-
- FuzzedDataProvider* auto_reply_fdp;
-
- common::BidiQueue<hci::AclView, hci::AclBuilder> acl_queue_{3};
- common::BidiQueue<hci::IsoView, hci::IsoBuilder> iso_queue_{3};
- os::fuzz::DevNullQueue<AclBuilder>* acl_dev_null_;
- os::fuzz::FuzzInjectQueue<AclView>* acl_inject_;
-
- FuzzCommandInterface<AclCommandBuilder> acl_connection_interface_{};
- FuzzCommandInterface<AclCommandBuilder> le_acl_connection_interface_{};
- FuzzCommandInterface<SecurityCommandBuilder> security_interface_{};
- FuzzCommandInterface<LeSecurityCommandBuilder> le_security_interface_{};
- FuzzCommandInterface<LeAdvertisingCommandBuilder> le_advertising_interface_{};
- FuzzCommandInterface<LeScanningCommandBuilder> le_scanning_interface_{};
- FuzzCommandInterface<LeIsoCommandBuilder> le_iso_interface_{};
-
- common::ContextualOnceCallback<void(hci::CommandCompleteView)> on_command_complete_;
- common::ContextualOnceCallback<void(hci::CommandStatusView)> on_command_status_;
-
- std::map<hci::EventCode, common::ContextualCallback<void(hci::EventView)>> event_handlers_;
- std::map<hci::SubeventCode, common::ContextualCallback<void(hci::LeMetaEventView)>> le_event_handlers_;
-
- common::ContextualCallback<void(hci::EventView)> security_event_handler_;
- common::ContextualCallback<void(hci::LeMetaEventView)> le_security_event_handler_;
- common::ContextualCallback<void(hci::EventView)> acl_event_handler_;
- common::ContextualCallback<void(uint16_t, hci::ErrorCode)> acl_on_disconnect_;
- common::ContextualCallback<void(hci::LeMetaEventView)> le_acl_event_handler_;
- common::ContextualCallback<void(uint16_t, hci::ErrorCode)> le_acl_on_disconnect_;
- common::ContextualCallback<void(hci::LeMetaEventView)> le_advertising_event_handler_;
- common::ContextualCallback<void(hci::LeMetaEventView)> le_scanning_event_handler_;
- common::ContextualCallback<void(hci::LeMetaEventView)> le_iso_event_handler_;
-};
-
-} // namespace fuzz
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/fuzz/hci_layer_fuzz_client.cc b/gd/hci/fuzz/hci_layer_fuzz_client.cc
deleted file mode 100644
index 3a19df4d1..000000000
--- a/gd/hci/fuzz/hci_layer_fuzz_client.cc
+++ /dev/null
@@ -1,124 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/fuzz/hci_layer_fuzz_client.h"
-#include "fuzz/helpers.h"
-
-namespace bluetooth {
-namespace hci {
-namespace fuzz {
-using bluetooth::fuzz::GetArbitraryBytes;
-using bluetooth::hci::AclView;
-
-const ModuleFactory HciLayerFuzzClient::Factory = ModuleFactory([]() { return new HciLayerFuzzClient(); });
-
-void HciLayerFuzzClient::Start() {
- hci_ = GetDependency<hci::HciLayer>();
- aclDevNull_ = new os::fuzz::DevNullQueue<AclView>(hci_->GetAclQueueEnd(), GetHandler());
- aclDevNull_->Start();
- aclInject_ = new os::fuzz::FuzzInjectQueue<AclBuilder>(hci_->GetAclQueueEnd(), GetHandler());
-
- // Can't do security right now, due to the Encryption Change conflict between ACL manager & security
- // security_interface_ = hci_->GetSecurityInterface(common::Bind([](EventView){}), GetHandler());
- le_security_interface_ = hci_->GetLeSecurityInterface(GetHandler()->Bind([](LeMetaEventView) {}));
- acl_connection_interface_ = hci_->GetAclConnectionInterface(
- GetHandler()->Bind([](EventView) {}),
- GetHandler()->Bind([](uint16_t, hci::ErrorCode) {}),
- GetHandler()->Bind([](hci::ErrorCode, uint16_t, uint8_t, uint16_t, uint16_t) {}));
- le_acl_connection_interface_ = hci_->GetLeAclConnectionInterface(
- GetHandler()->Bind([](LeMetaEventView) {}),
- GetHandler()->Bind([](uint16_t, hci::ErrorCode) {}),
- GetHandler()->Bind([](hci::ErrorCode, uint16_t, uint8_t, uint16_t, uint16_t) {}));
- le_advertising_interface_ = hci_->GetLeAdvertisingInterface(GetHandler()->Bind([](LeMetaEventView) {}));
- le_scanning_interface_ = hci_->GetLeScanningInterface(GetHandler()->Bind([](LeMetaEventView) {}));
-}
-
-void HciLayerFuzzClient::Stop() {
- aclDevNull_->Stop();
- delete aclDevNull_;
- delete aclInject_;
-}
-
-void HciLayerFuzzClient::injectArbitrary(FuzzedDataProvider& fdp) {
- const uint8_t action = fdp.ConsumeIntegralInRange(0, 8);
- switch (action) {
- case 1:
- injectAclData(GetArbitraryBytes(&fdp));
- break;
- case 2:
- injectHciCommand(GetArbitraryBytes(&fdp));
- break;
- case 3:
- // TODO: injectSecurityCommand(GetArbitraryBytes(&fdp));
- break;
- case 4:
- injectLeSecurityCommand(GetArbitraryBytes(&fdp));
- break;
- case 5:
- injectAclConnectionCommand(GetArbitraryBytes(&fdp));
- break;
- case 6:
- injectLeAclConnectionCommand(GetArbitraryBytes(&fdp));
- break;
- case 7:
- injectLeAdvertisingCommand(GetArbitraryBytes(&fdp));
- break;
- case 8:
- injectLeScanningCommand(GetArbitraryBytes(&fdp));
- break;
- }
-}
-
-void HciLayerFuzzClient::injectAclData(std::vector<uint8_t> data) {
- hci::AclView aclPacket = hci::AclView::FromBytes(data);
- if (!aclPacket.IsValid()) {
- return;
- }
-
- aclInject_->Inject(AclBuilder::FromView(aclPacket));
-}
-
-void HciLayerFuzzClient::injectHciCommand(std::vector<uint8_t> data) {
- inject_command<CommandView, CommandBuilder>(data, hci_);
-}
-
-void HciLayerFuzzClient::injectSecurityCommand(std::vector<uint8_t> data) {
- inject_command<SecurityCommandView, SecurityCommandBuilder>(data, security_interface_);
-}
-
-void HciLayerFuzzClient::injectLeSecurityCommand(std::vector<uint8_t> data) {
- inject_command<LeSecurityCommandView, LeSecurityCommandBuilder>(data, le_security_interface_);
-}
-
-void HciLayerFuzzClient::injectAclConnectionCommand(std::vector<uint8_t> data) {
- inject_command<AclCommandView, AclCommandBuilder>(data, acl_connection_interface_);
-}
-
-void HciLayerFuzzClient::injectLeAclConnectionCommand(std::vector<uint8_t> data) {
- inject_command<AclCommandView, AclCommandBuilder>(data, le_acl_connection_interface_);
-}
-
-void HciLayerFuzzClient::injectLeAdvertisingCommand(std::vector<uint8_t> data) {
- inject_command<LeAdvertisingCommandView, LeAdvertisingCommandBuilder>(data, le_advertising_interface_);
-}
-
-void HciLayerFuzzClient::injectLeScanningCommand(std::vector<uint8_t> data) {
- inject_command<LeScanningCommandView, LeScanningCommandBuilder>(data, le_scanning_interface_);
-}
-
-} // namespace fuzz
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/fuzz/hci_layer_fuzz_client.h b/gd/hci/fuzz/hci_layer_fuzz_client.h
deleted file mode 100644
index a5f2367d8..000000000
--- a/gd/hci/fuzz/hci_layer_fuzz_client.h
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <stddef.h>
-#include <stdint.h>
-#include "hci/fuzz/status_vs_complete_commands.h"
-#include "hci/hci_layer.h"
-#include "hci/hci_packets.h"
-#include "module.h"
-#include "os/fuzz/dev_null_queue.h"
-#include "os/fuzz/fuzz_inject_queue.h"
-
-#include <fuzzer/FuzzedDataProvider.h>
-
-namespace bluetooth {
-namespace hci {
-namespace fuzz {
-
-class HciLayerFuzzClient : public Module {
- public:
- HciLayerFuzzClient() : Module() {}
-
- void Start() override;
- void Stop() override;
-
- void injectArbitrary(FuzzedDataProvider& fdp);
-
- void ListDependencies(ModuleList* list) override {
- list->add<hci::HciLayer>();
- }
-
- static const ModuleFactory Factory;
-
- std::string ToString() const override {
- return "DevNullHci";
- }
-
- private:
- void injectAclData(std::vector<uint8_t> data);
- void injectHciCommand(std::vector<uint8_t> data);
- void injectSecurityCommand(std::vector<uint8_t> data);
- void injectLeSecurityCommand(std::vector<uint8_t> data);
- void injectAclConnectionCommand(std::vector<uint8_t> data);
- void injectLeAclConnectionCommand(std::vector<uint8_t> data);
- void injectLeAdvertisingCommand(std::vector<uint8_t> data);
- void injectLeScanningCommand(std::vector<uint8_t> data);
-
- template <typename TVIEW, typename TBUILDER>
- void inject_command(std::vector<uint8_t> data, CommandInterface<TBUILDER>* interface) {
- TVIEW commandPacket = TVIEW::FromBytes(data);
- if (!commandPacket.IsValid()) {
- return;
- }
-
- if (uses_command_status(commandPacket.GetOpCode())) {
- interface->EnqueueCommand(TBUILDER::FromView(commandPacket),
- GetHandler()->BindOnce([](CommandStatusView status) {}));
- } else {
- interface->EnqueueCommand(TBUILDER::FromView(commandPacket),
- GetHandler()->BindOnce([](CommandCompleteView status) {}));
- }
- }
-
- hci::HciLayer* hci_ = nullptr;
- os::fuzz::DevNullQueue<AclView>* aclDevNull_;
- os::fuzz::FuzzInjectQueue<AclBuilder>* aclInject_;
-
- SecurityInterface* security_interface_;
- LeSecurityInterface* le_security_interface_;
- AclConnectionInterface* acl_connection_interface_;
- LeAclConnectionInterface* le_acl_connection_interface_;
- LeAdvertisingInterface* le_advertising_interface_;
- LeScanningInterface* le_scanning_interface_;
-};
-
-} // namespace fuzz
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/fuzz/hci_layer_fuzz_test.cc b/gd/hci/fuzz/hci_layer_fuzz_test.cc
deleted file mode 100644
index e6e27d813..000000000
--- a/gd/hci/fuzz/hci_layer_fuzz_test.cc
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <stddef.h>
-#include <stdint.h>
-#include "fuzz/helpers.h"
-#include "hal/fuzz/fuzz_hci_hal.h"
-#include "hci/fuzz/hci_layer_fuzz_client.h"
-#include "hci/hci_layer.h"
-#include "module.h"
-#include "os/fuzz/fake_timerfd.h"
-#include "os/log.h"
-
-#include <fuzzer/FuzzedDataProvider.h>
-
-using bluetooth::FuzzTestModuleRegistry;
-using bluetooth::fuzz::GetArbitraryBytes;
-using bluetooth::hal::HciHal;
-using bluetooth::hal::fuzz::FuzzHciHal;
-using bluetooth::hci::fuzz::HciLayerFuzzClient;
-using bluetooth::os::fuzz::fake_timerfd_advance;
-using bluetooth::os::fuzz::fake_timerfd_cap_at;
-using bluetooth::os::fuzz::fake_timerfd_reset;
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
- FuzzedDataProvider dataProvider(data, size);
- fake_timerfd_cap_at(1999); // prevent command timeouts
-
- static FuzzTestModuleRegistry moduleRegistry = FuzzTestModuleRegistry();
- FuzzHciHal* fuzzHal = moduleRegistry.Inject<FuzzHciHal>(&HciHal::Factory);
- HciLayerFuzzClient* fuzzClient = moduleRegistry.Start<HciLayerFuzzClient>();
-
- while (dataProvider.remaining_bytes() > 0) {
- const uint8_t action = dataProvider.ConsumeIntegralInRange(0, 5);
- switch (action) {
- case 1:
- fake_timerfd_advance(dataProvider.ConsumeIntegral<uint64_t>());
- break;
- case 2:
- fuzzHal->injectArbitrary(dataProvider);
- break;
- case 3:
- fuzzClient->injectArbitrary(dataProvider);
- break;
- }
- }
-
- moduleRegistry.WaitForIdleAndStopAll();
- fake_timerfd_reset();
- return 0;
-}
diff --git a/gd/hci/fuzz/status_vs_complete_commands.cc b/gd/hci/fuzz/status_vs_complete_commands.cc
deleted file mode 100644
index cf4a5ff5f..000000000
--- a/gd/hci/fuzz/status_vs_complete_commands.cc
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/fuzz/status_vs_complete_commands.h"
-#include <map>
-
-namespace bluetooth {
-namespace hci {
-namespace fuzz {
-
-using ::bluetooth::hci::OpCode;
-
-constexpr OpCode StatusOpCodes[] = {
- OpCode::RESET,
-};
-
-static std::map<OpCode, bool> commands_that_use_status;
-
-static void maybe_populate_list() {
- if (!commands_that_use_status.empty()) {
- return;
- }
-
- for (OpCode code : StatusOpCodes) {
- commands_that_use_status[code] = true;
- }
-}
-
-bool uses_command_status(OpCode code) {
- maybe_populate_list();
- return commands_that_use_status.find(code) != commands_that_use_status.end();
-}
-
-} // namespace fuzz
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/hci_acl_manager.fbs b/gd/hci/hci_acl_manager.fbs
deleted file mode 100644
index a8481eb94..000000000
--- a/gd/hci/hci_acl_manager.fbs
+++ /dev/null
@@ -1,9 +0,0 @@
-namespace bluetooth.hci;
-
-attribute "privacy";
-
-table AclManagerData {
- title:string (privacy:"Any");
-}
-
-root_type AclManagerData;
diff --git a/gd/hci/hci_layer.cc b/gd/hci/hci_layer.cc
index dae1f4d5f..9f707da6e 100644
--- a/gd/hci/hci_layer.cc
+++ b/gd/hci/hci_layer.cc
@@ -17,194 +17,334 @@
#include "hci/hci_layer.h"
#include "common/bind.h"
-#include "common/init_flags.h"
-#include "common/stop_watch.h"
-#include "hci/hci_metrics_logging.h"
+#include "common/callback.h"
#include "os/alarm.h"
-#include "os/metrics.h"
#include "os/queue.h"
#include "packet/packet_builder.h"
-#include "storage/storage_module.h"
-namespace bluetooth {
-namespace hci {
-using bluetooth::common::BindOn;
+namespace {
+using bluetooth::common::Bind;
using bluetooth::common::BindOnce;
-using bluetooth::common::ContextualCallback;
-using bluetooth::common::ContextualOnceCallback;
-using bluetooth::hci::CommandBuilder;
+using bluetooth::common::Callback;
+using bluetooth::common::Closure;
+using bluetooth::common::OnceCallback;
+using bluetooth::common::OnceClosure;
using bluetooth::hci::CommandCompleteView;
+using bluetooth::hci::CommandPacketBuilder;
using bluetooth::hci::CommandStatusView;
-using bluetooth::hci::EventView;
+using bluetooth::hci::EventPacketView;
using bluetooth::hci::LeMetaEventView;
using bluetooth::os::Handler;
+
+class EventHandler {
+ public:
+ EventHandler() : event_handler(), handler(nullptr) {}
+ EventHandler(Callback<void(EventPacketView)> on_event, Handler* on_event_handler)
+ : event_handler(std::move(on_event)), handler(on_event_handler) {}
+ Callback<void(EventPacketView)> event_handler;
+ Handler* handler;
+};
+
+class SubeventHandler {
+ public:
+ SubeventHandler() : subevent_handler(), handler(nullptr) {}
+ SubeventHandler(Callback<void(LeMetaEventView)> on_event, Handler* on_event_handler)
+ : subevent_handler(std::move(on_event)), handler(on_event_handler) {}
+ Callback<void(LeMetaEventView)> subevent_handler;
+ Handler* handler;
+};
+
+class CommandQueueEntry {
+ public:
+ CommandQueueEntry(std::unique_ptr<CommandPacketBuilder> command_packet,
+ OnceCallback<void(CommandCompleteView)> on_complete_function, Handler* handler)
+ : command(std::move(command_packet)), waiting_for_status_(false), on_complete(std::move(on_complete_function)),
+ caller_handler(handler) {}
+
+ CommandQueueEntry(std::unique_ptr<CommandPacketBuilder> command_packet,
+ OnceCallback<void(CommandStatusView)> on_status_function, Handler* handler)
+ : command(std::move(command_packet)), waiting_for_status_(true), on_status(std::move(on_status_function)),
+ caller_handler(handler) {}
+
+ std::unique_ptr<CommandPacketBuilder> command;
+ bool waiting_for_status_;
+ OnceCallback<void(CommandStatusView)> on_status;
+ OnceCallback<void(CommandCompleteView)> on_complete;
+ Handler* caller_handler;
+};
+} // namespace
+
+namespace bluetooth {
+namespace hci {
+
using common::BidiQueue;
using common::BidiQueueEnd;
-using hci::OpCode;
-using hci::ResetCompleteView;
using os::Alarm;
using os::Handler;
-using std::move;
-using std::unique_ptr;
-static void fail_if_reset_complete_not_success(CommandCompleteView complete) {
+namespace {
+using hci::OpCode;
+using hci::ResetCompleteView;
+
+void fail_if_reset_complete_not_success(CommandCompleteView complete) {
auto reset_complete = ResetCompleteView::Create(complete);
ASSERT(reset_complete.IsValid());
ASSERT(reset_complete.GetStatus() == ErrorCode::SUCCESS);
}
-static void abort_after_time_out(OpCode op_code) {
- bluetooth::os::LogMetricHciTimeoutEvent(static_cast<uint32_t>(op_code));
- ASSERT_LOG(false, "Done waiting for debug information after HCI timeout (%s)", OpCodeText(op_code).c_str());
+void on_hci_timeout(OpCode op_code) {
+ ASSERT_LOG(false, "Timed out waiting for 0x%02hx (%s)", op_code, OpCodeText(op_code).c_str());
}
+} // namespace
-class CommandQueueEntry {
+class SecurityInterfaceImpl : public SecurityInterface {
public:
- CommandQueueEntry(
- unique_ptr<CommandBuilder> command_packet, ContextualOnceCallback<void(CommandCompleteView)> on_complete_function)
- : command(move(command_packet)), waiting_for_status_(false), on_complete(move(on_complete_function)) {}
+ SecurityInterfaceImpl(HciLayer& hci) : hci_(hci) {}
+ virtual ~SecurityInterfaceImpl() = default;
- CommandQueueEntry(
- unique_ptr<CommandBuilder> command_packet, ContextualOnceCallback<void(CommandStatusView)> on_status_function)
- : command(move(command_packet)), waiting_for_status_(true), on_status(move(on_status_function)) {}
+ virtual void EnqueueCommand(std::unique_ptr<SecurityCommandBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete,
+ os::Handler* handler) override {
+ hci_.EnqueueCommand(std::move(command), std::move(on_complete), handler);
+ }
- unique_ptr<CommandBuilder> command;
- unique_ptr<CommandView> command_view;
+ virtual void EnqueueCommand(std::unique_ptr<SecurityCommandBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) override {
+ hci_.EnqueueCommand(std::move(command), std::move(on_status), handler);
+ }
+ HciLayer& hci_;
+};
- bool waiting_for_status_;
- ContextualOnceCallback<void(CommandStatusView)> on_status;
- ContextualOnceCallback<void(CommandCompleteView)> on_complete;
+class LeSecurityInterfaceImpl : public LeSecurityInterface {
+ public:
+ LeSecurityInterfaceImpl(HciLayer& hci) : hci_(hci) {}
+ virtual ~LeSecurityInterfaceImpl() = default;
- template <typename TView>
- ContextualOnceCallback<void(TView)>* GetCallback() {
- return nullptr;
+ virtual void EnqueueCommand(std::unique_ptr<LeSecurityCommandBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete,
+ os::Handler* handler) override {
+ hci_.EnqueueCommand(std::move(command), std::move(on_complete), handler);
}
- template <>
- ContextualOnceCallback<void(CommandStatusView)>* GetCallback<CommandStatusView>() {
- return &on_status;
+ virtual void EnqueueCommand(std::unique_ptr<LeSecurityCommandBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) override {
+ hci_.EnqueueCommand(std::move(command), std::move(on_status), handler);
}
+ HciLayer& hci_;
+};
- template <>
- ContextualOnceCallback<void(CommandCompleteView)>* GetCallback<CommandCompleteView>() {
- return &on_complete;
+class LeAdvertisingInterfaceImpl : public LeAdvertisingInterface {
+ public:
+ LeAdvertisingInterfaceImpl(HciLayer& hci) : hci_(hci) {}
+ virtual ~LeAdvertisingInterfaceImpl() = default;
+
+ virtual void EnqueueCommand(std::unique_ptr<LeAdvertisingCommandBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete,
+ os::Handler* handler) override {
+ hci_.EnqueueCommand(std::move(command), std::move(on_complete), handler);
+ }
+
+ virtual void EnqueueCommand(std::unique_ptr<LeAdvertisingCommandBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) override {
+ hci_.EnqueueCommand(std::move(command), std::move(on_status), handler);
}
+ HciLayer& hci_;
};
-struct HciLayer::impl {
- impl(hal::HciHal* hal, HciLayer& module) : hal_(hal), module_(module) {
- hci_timeout_alarm_ = new Alarm(module.GetHandler());
+class LeScanningInterfaceImpl : public LeScanningInterface {
+ public:
+ LeScanningInterfaceImpl(HciLayer& hci) : hci_(hci) {}
+ virtual ~LeScanningInterfaceImpl() = default;
+
+ virtual void EnqueueCommand(std::unique_ptr<LeScanningCommandBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete,
+ os::Handler* handler) override {
+ hci_.EnqueueCommand(std::move(command), std::move(on_complete), handler);
}
- ~impl() {
- incoming_acl_buffer_.Clear();
- incoming_iso_buffer_.Clear();
- if (hci_timeout_alarm_ != nullptr) {
- delete hci_timeout_alarm_;
- }
- if (hci_abort_alarm_ != nullptr) {
- delete hci_abort_alarm_;
- }
- command_queue_.clear();
+ virtual void EnqueueCommand(std::unique_ptr<LeScanningCommandBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) override {
+ hci_.EnqueueCommand(std::move(command), std::move(on_status), handler);
}
+ HciLayer& hci_;
+};
+
+struct HciLayer::impl : public hal::HciHalCallbacks {
+ impl(HciLayer& module) : hal_(nullptr), module_(module) {}
- void drop(EventView event) {
- LOG_INFO("Dropping event %s", EventCodeText(event.GetEventCode()).c_str());
+ ~impl() {}
+
+ void Start(hal::HciHal* hal) {
+ hal_ = hal;
+ hci_timeout_alarm_ = new Alarm(module_.GetHandler());
+
+ auto queue_end = acl_queue_.GetDownEnd();
+ Handler* handler = module_.GetHandler();
+ queue_end->RegisterDequeue(handler, Bind(&impl::dequeue_and_send_acl, common::Unretained(this)));
+ RegisterEventHandler(EventCode::COMMAND_COMPLETE, Bind(&impl::command_complete_callback, common::Unretained(this)),
+ handler);
+ RegisterEventHandler(EventCode::COMMAND_STATUS, Bind(&impl::command_status_callback, common::Unretained(this)),
+ handler);
+ RegisterEventHandler(EventCode::LE_META_EVENT, Bind(&impl::le_meta_event_callback, common::Unretained(this)),
+ handler);
+ // TODO find the right place
+ RegisterEventHandler(EventCode::PAGE_SCAN_REPETITION_MODE_CHANGE, Bind(&impl::drop, common::Unretained(this)),
+ handler);
+ RegisterEventHandler(EventCode::MAX_SLOTS_CHANGE, Bind(&impl::drop, common::Unretained(this)), handler);
+ RegisterEventHandler(EventCode::VENDOR_SPECIFIC, Bind(&impl::drop, common::Unretained(this)), handler);
+
+ EnqueueCommand(ResetBuilder::Create(), BindOnce(&fail_if_reset_complete_not_success), handler);
+ hal_->registerIncomingPacketCallback(this);
}
- void on_outbound_acl_ready() {
+ void drop(EventPacketView) {}
+
+ void dequeue_and_send_acl() {
auto packet = acl_queue_.GetDownEnd()->TryDequeue();
+ send_acl(std::move(packet));
+ }
+
+ void Stop() {
+ hal_->unregisterIncomingPacketCallback();
+ UnregisterEventHandler(EventCode::COMMAND_COMPLETE);
+ UnregisterEventHandler(EventCode::COMMAND_STATUS);
+ UnregisterEventHandler(EventCode::LE_META_EVENT);
+ UnregisterEventHandler(EventCode::PAGE_SCAN_REPETITION_MODE_CHANGE);
+ UnregisterEventHandler(EventCode::MAX_SLOTS_CHANGE);
+ UnregisterEventHandler(EventCode::VENDOR_SPECIFIC);
+
+ acl_queue_.GetDownEnd()->UnregisterDequeue();
+ incoming_acl_packet_buffer_.Clear();
+ delete hci_timeout_alarm_;
+ command_queue_.clear();
+ hal_ = nullptr;
+ }
+
+ void send_acl(std::unique_ptr<hci::BasePacketBuilder> packet) {
std::vector<uint8_t> bytes;
BitInserter bi(bytes);
packet->Serialize(bi);
hal_->sendAclData(bytes);
}
- void on_outbound_iso_ready() {
- auto packet = iso_queue_.GetDownEnd()->TryDequeue();
+ void send_sco(std::unique_ptr<hci::BasePacketBuilder> packet) {
std::vector<uint8_t> bytes;
BitInserter bi(bytes);
packet->Serialize(bi);
- hal_->sendIsoData(bytes);
+ hal_->sendScoData(bytes);
}
- template <typename TResponse>
- void enqueue_command(unique_ptr<CommandBuilder> command, ContextualOnceCallback<void(TResponse)> on_response) {
- command_queue_.emplace_back(move(command), move(on_response));
- send_next_command();
- }
-
- void on_command_status(EventView event) {
- CommandStatusView response_view = CommandStatusView::Create(event);
- ASSERT(response_view.IsValid());
- OpCode op_code = response_view.GetCommandOpCode();
- ErrorCode status = response_view.GetStatus();
- if (status != ErrorCode::SUCCESS) {
- LOG_ERROR(
- "Received UNEXPECTED command status:%s opcode:0x%02hx (%s)",
- ErrorCodeText(status).c_str(),
- op_code,
- OpCodeText(op_code).c_str());
+ void command_status_callback(EventPacketView event) {
+ CommandStatusView status_view = CommandStatusView::Create(event);
+ ASSERT(status_view.IsValid());
+ command_credits_ = status_view.GetNumHciCommandPackets();
+ OpCode op_code = status_view.GetCommandOpCode();
+ if (op_code == OpCode::NONE) {
+ send_next_command();
+ return;
}
- handle_command_response<CommandStatusView>(event, "status");
- }
-
- void on_command_complete(EventView event) {
- handle_command_response<CommandCompleteView>(event, "complete");
+ ASSERT_LOG(!command_queue_.empty(), "Unexpected status event with OpCode 0x%02hx (%s)", op_code,
+ OpCodeText(op_code).c_str());
+ ASSERT_LOG(waiting_command_ == op_code, "Waiting for 0x%02hx (%s), got 0x%02hx (%s)", waiting_command_,
+ OpCodeText(waiting_command_).c_str(), op_code, OpCodeText(op_code).c_str());
+ ASSERT_LOG(command_queue_.front().waiting_for_status_,
+ "Waiting for command complete 0x%02hx (%s), got command status for 0x%02hx (%s)", waiting_command_,
+ OpCodeText(waiting_command_).c_str(), op_code, OpCodeText(op_code).c_str());
+ auto caller_handler = command_queue_.front().caller_handler;
+ caller_handler->Post(BindOnce(std::move(command_queue_.front().on_status), std::move(status_view)));
+ command_queue_.pop_front();
+ waiting_command_ = OpCode::NONE;
+ hci_timeout_alarm_->Cancel();
+ send_next_command();
}
- template <typename TResponse>
- void handle_command_response(EventView event, std::string logging_id) {
- TResponse response_view = TResponse::Create(event);
- ASSERT(response_view.IsValid());
- command_credits_ = response_view.GetNumHciCommandPackets();
- OpCode op_code = response_view.GetCommandOpCode();
+ void command_complete_callback(EventPacketView event) {
+ CommandCompleteView complete_view = CommandCompleteView::Create(event);
+ ASSERT(complete_view.IsValid());
+ command_credits_ = complete_view.GetNumHciCommandPackets();
+ OpCode op_code = complete_view.GetCommandOpCode();
if (op_code == OpCode::NONE) {
send_next_command();
return;
}
- bool is_status = logging_id == "status";
-
- ASSERT_LOG(!command_queue_.empty(), "Unexpected %s event with OpCode 0x%02hx (%s)", logging_id.c_str(), op_code,
+ ASSERT_LOG(command_queue_.size() > 0, "Unexpected command complete with OpCode 0x%02hx (%s)", op_code,
OpCodeText(op_code).c_str());
ASSERT_LOG(waiting_command_ == op_code, "Waiting for 0x%02hx (%s), got 0x%02hx (%s)", waiting_command_,
OpCodeText(waiting_command_).c_str(), op_code, OpCodeText(op_code).c_str());
- ASSERT_LOG(command_queue_.front().waiting_for_status_ == is_status, "0x%02hx (%s) was not expecting %s event",
- op_code, OpCodeText(op_code).c_str(), logging_id.c_str());
-
- command_queue_.front().GetCallback<TResponse>()->Invoke(move(response_view));
+ ASSERT_LOG(!command_queue_.front().waiting_for_status_,
+ "Waiting for command status 0x%02hx (%s), got command complete for 0x%02hx (%s)", waiting_command_,
+ OpCodeText(waiting_command_).c_str(), op_code, OpCodeText(op_code).c_str());
+ auto caller_handler = command_queue_.front().caller_handler;
+ caller_handler->Post(BindOnce(std::move(command_queue_.front().on_complete), complete_view));
command_queue_.pop_front();
waiting_command_ = OpCode::NONE;
- if (hci_timeout_alarm_ != nullptr) {
- hci_timeout_alarm_->Cancel();
- send_next_command();
- }
+ hci_timeout_alarm_->Cancel();
+ send_next_command();
}
- void on_hci_timeout(OpCode op_code) {
- common::StopWatch::DumpStopWatchLog();
- LOG_ERROR("Timed out waiting for 0x%02hx (%s)", op_code, OpCodeText(op_code).c_str());
- // TODO: LogMetricHciTimeoutEvent(static_cast<uint32_t>(op_code));
+ void le_meta_event_callback(EventPacketView event) {
+ LeMetaEventView meta_event_view = LeMetaEventView::Create(event);
+ ASSERT(meta_event_view.IsValid());
+ SubeventCode subevent_code = meta_event_view.GetSubeventCode();
+ ASSERT_LOG(subevent_handlers_.find(subevent_code) != subevent_handlers_.end(),
+ "Unhandled le event of type 0x%02hhx (%s)", subevent_code, SubeventCodeText(subevent_code).c_str());
+ auto& registered_handler = subevent_handlers_[subevent_code].subevent_handler;
+ subevent_handlers_[subevent_code].handler->Post(BindOnce(registered_handler, meta_event_view));
+ }
- LOG_ERROR("Flushing %zd waiting commands", command_queue_.size());
- // Clear any waiting commands (there is an abort coming anyway)
- command_queue_.clear();
- command_credits_ = 1;
- waiting_command_ = OpCode::NONE;
- enqueue_command(
- ControllerDebugInfoBuilder::Create(), module_.GetHandler()->BindOnce(&fail_if_reset_complete_not_success));
- // Don't time out for this one;
- if (hci_timeout_alarm_ != nullptr) {
- hci_timeout_alarm_->Cancel();
- delete hci_timeout_alarm_;
- hci_timeout_alarm_ = nullptr;
- }
- if (hci_abort_alarm_ == nullptr) {
- hci_abort_alarm_ = new Alarm(module_.GetHandler());
- hci_abort_alarm_->Schedule(BindOnce(&abort_after_time_out, op_code), kHciTimeoutRestartMs);
- } else {
- LOG_WARN("Unable to schedul abort timer");
- }
+ void hciEventReceived(hal::HciPacket event_bytes) override {
+ auto packet = packet::PacketView<packet::kLittleEndian>(std::make_shared<std::vector<uint8_t>>(event_bytes));
+ EventPacketView event = EventPacketView::Create(packet);
+ ASSERT(event.IsValid());
+ module_.GetHandler()->Post(
+ BindOnce(&HciLayer::impl::hci_event_received_handler, common::Unretained(this), std::move(event)));
+ }
+
+ void hci_event_received_handler(EventPacketView event) {
+ EventCode event_code = event.GetEventCode();
+ ASSERT_LOG(event_handlers_.find(event_code) != event_handlers_.end(), "Unhandled event of type 0x%02hhx (%s)",
+ event_code, EventCodeText(event_code).c_str());
+ auto& registered_handler = event_handlers_[event_code].event_handler;
+ event_handlers_[event_code].handler->Post(BindOnce(registered_handler, std::move(event)));
+ }
+
+ void aclDataReceived(hal::HciPacket data_bytes) override {
+ auto packet =
+ packet::PacketView<packet::kLittleEndian>(std::make_shared<std::vector<uint8_t>>(std::move(data_bytes)));
+ AclPacketView acl = AclPacketView::Create(packet);
+ incoming_acl_packet_buffer_.Enqueue(std::make_unique<AclPacketView>(acl), module_.GetHandler());
+ }
+
+ void scoDataReceived(hal::HciPacket data_bytes) override {
+ auto packet = packet::PacketView<packet::kLittleEndian>(std::make_shared<std::vector<uint8_t>>(data_bytes));
+ ScoPacketView sco = ScoPacketView::Create(packet);
+ }
+
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) {
+ module_.GetHandler()->Post(common::BindOnce(&impl::handle_enqueue_command_with_complete, common::Unretained(this),
+ std::move(command), std::move(on_complete),
+ common::Unretained(handler)));
+ }
+
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command, OnceCallback<void(CommandStatusView)> on_status,
+ os::Handler* handler) {
+ module_.GetHandler()->Post(common::BindOnce(&impl::handle_enqueue_command_with_status, common::Unretained(this),
+ std::move(command), std::move(on_status), common::Unretained(handler)));
+ }
+
+ void handle_enqueue_command_with_complete(std::unique_ptr<CommandPacketBuilder> command,
+ OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) {
+ command_queue_.emplace_back(std::move(command), std::move(on_complete), handler);
+
+ send_next_command();
+ }
+
+ void handle_enqueue_command_with_status(std::unique_ptr<CommandPacketBuilder> command,
+ OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) {
+ command_queue_.emplace_back(std::move(command), std::move(on_status), handler);
+
+ send_next_command();
}
void send_next_command() {
@@ -221,352 +361,176 @@ struct HciLayer::impl {
BitInserter bi(*bytes);
command_queue_.front().command->Serialize(bi);
hal_->sendHciCommand(*bytes);
-
- auto cmd_view = CommandView::Create(PacketView<kLittleEndian>(bytes));
+ auto cmd_view = CommandPacketView::Create(bytes);
ASSERT(cmd_view.IsValid());
OpCode op_code = cmd_view.GetOpCode();
- command_queue_.front().command_view = std::make_unique<CommandView>(std::move(cmd_view));
- log_link_layer_connection_command_status(command_queue_.front().command_view, ErrorCode::STATUS_UNKNOWN);
- log_classic_pairing_command_status(command_queue_.front().command_view, ErrorCode::STATUS_UNKNOWN);
waiting_command_ = op_code;
command_credits_ = 0; // Only allow one outstanding command
- if (hci_timeout_alarm_ != nullptr) {
- hci_timeout_alarm_->Schedule(BindOnce(&impl::on_hci_timeout, common::Unretained(this), op_code), kHciTimeoutMs);
- } else {
- LOG_WARN("%s sent without an hci-timeout timer", OpCodeText(op_code).c_str());
- }
- }
-
- void register_event(EventCode event, ContextualCallback<void(EventView)> handler) {
- ASSERT_LOG(
- event != EventCode::LE_META_EVENT,
- "Can not register handler for %02hhx (%s)",
- EventCode::LE_META_EVENT,
- EventCodeText(EventCode::LE_META_EVENT).c_str());
- ASSERT_LOG(event_handlers_.count(event) == 0, "Can not register a second handler for %02hhx (%s)", event,
- EventCodeText(event).c_str());
- event_handlers_[event] = handler;
+ hci_timeout_alarm_->Schedule(BindOnce(&on_hci_timeout, op_code), kHciTimeoutMs);
}
- void unregister_event(EventCode event) {
- event_handlers_.erase(event);
+ BidiQueueEnd<AclPacketBuilder, AclPacketView>* GetAclQueueEnd() {
+ return acl_queue_.GetUpEnd();
}
- void register_le_meta_event(ContextualCallback<void(EventView)> handler) {
- ASSERT_LOG(
- event_handlers_.count(EventCode::LE_META_EVENT) == 0,
- "Can not register a second handler for %02hhx (%s)",
- EventCode::LE_META_EVENT,
- EventCodeText(EventCode::LE_META_EVENT).c_str());
- event_handlers_[EventCode::LE_META_EVENT] = handler;
+ void RegisterEventHandler(EventCode event_code, Callback<void(EventPacketView)> event_handler, os::Handler* handler) {
+ module_.GetHandler()->Post(common::BindOnce(&impl::handle_register_event_handler, common::Unretained(this),
+ event_code, event_handler, common::Unretained(handler)));
}
- void unregister_le_meta_event() {
- unregister_event(EventCode::LE_META_EVENT);
+ void handle_register_event_handler(EventCode event_code, Callback<void(EventPacketView)> event_handler,
+ os::Handler* handler) {
+ ASSERT_LOG(event_handlers_.count(event_code) == 0, "Can not register a second handler for event_code %02hhx (%s)",
+ event_code, EventCodeText(event_code).c_str());
+ EventHandler to_save(event_handler, handler);
+ event_handlers_[event_code] = to_save;
}
- void register_le_event(SubeventCode event, ContextualCallback<void(LeMetaEventView)> handler) {
- ASSERT_LOG(subevent_handlers_.count(event) == 0, "Can not register a second handler for %02hhx (%s)", event,
- SubeventCodeText(event).c_str());
- subevent_handlers_[event] = handler;
+ void UnregisterEventHandler(EventCode event_code) {
+ module_.GetHandler()->Post(
+ common::BindOnce(&impl::handle_unregister_event_handler, common::Unretained(this), event_code));
}
- void unregister_le_event(SubeventCode event) {
- subevent_handlers_.erase(subevent_handlers_.find(event));
+ void handle_unregister_event_handler(EventCode event_code) {
+ event_handlers_.erase(event_code);
}
- static void abort_after_root_inflammation(uint8_t vse_error) {
- ASSERT_LOG(false, "Root inflammation with reason 0x%02hhx", vse_error);
+ void RegisterLeEventHandler(SubeventCode subevent_code, Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler) {
+ module_.GetHandler()->Post(common::BindOnce(&impl::handle_register_le_event_handler, common::Unretained(this),
+ subevent_code, event_handler, common::Unretained(handler)));
}
- void handle_root_inflammation(uint8_t vse_error_reason) {
- LOG_ERROR("Received a Root Inflammation Event vendor reason 0x%02hhx, scheduling an abort",
- vse_error_reason);
- bluetooth::os::LogMetricBluetoothHalCrashReason(Address::kEmpty, 0, vse_error_reason);
- // Add Logging for crash reason
- if (hci_timeout_alarm_ != nullptr) {
- hci_timeout_alarm_->Cancel();
- delete hci_timeout_alarm_;
- hci_timeout_alarm_ = nullptr;
- }
- if (hci_abort_alarm_ == nullptr) {
- hci_abort_alarm_ = new Alarm(module_.GetHandler());
- hci_abort_alarm_->Schedule(BindOnce(&abort_after_root_inflammation, vse_error_reason), kHciTimeoutRestartMs);
- } else {
- LOG_WARN("Abort timer already scheduled");
- }
+ void handle_register_le_event_handler(SubeventCode subevent_code, Callback<void(LeMetaEventView)> subevent_handler,
+ os::Handler* handler) {
+ ASSERT_LOG(subevent_handlers_.count(subevent_code) == 0,
+ "Can not register a second handler for subevent_code %02hhx (%s)", subevent_code,
+ SubeventCodeText(subevent_code).c_str());
+ SubeventHandler to_save(subevent_handler, handler);
+ subevent_handlers_[subevent_code] = to_save;
}
- void on_hci_event(EventView event) {
- ASSERT(event.IsValid());
- log_hci_event(command_queue_.front().command_view, event, module_.GetDependency<storage::StorageModule>());
- EventCode event_code = event.GetEventCode();
- // Root Inflamation is a special case, since it aborts here
- if (event_code == EventCode::VENDOR_SPECIFIC) {
- auto view = VendorSpecificEventView::Create(event);
- ASSERT(view.IsValid());
- if (view.GetSubeventCode() == VseSubeventCode::BQR_EVENT) {
- auto bqr_quality_view = BqrLinkQualityEventView::Create(BqrEventView::Create(view));
- auto inflammation = BqrRootInflammationEventView::Create(bqr_quality_view);
- if (bqr_quality_view.IsValid() && inflammation.IsValid()) {
- handle_root_inflammation(inflammation.GetVendorSpecificErrorCode());
- return;
- }
- }
- }
- if (event_handlers_.find(event_code) == event_handlers_.end()) {
- LOG_WARN("Unhandled event of type 0x%02hhx (%s)", event_code, EventCodeText(event_code).c_str());
- return;
- }
- event_handlers_[event_code].Invoke(event);
+ void UnregisterLeEventHandler(SubeventCode subevent_code) {
+ module_.GetHandler()->Post(
+ common::BindOnce(&impl::handle_unregister_le_event_handler, common::Unretained(this), subevent_code));
}
- void on_le_meta_event(EventView event) {
- LeMetaEventView meta_event_view = LeMetaEventView::Create(event);
- ASSERT(meta_event_view.IsValid());
- SubeventCode subevent_code = meta_event_view.GetSubeventCode();
- if (subevent_handlers_.find(subevent_code) == subevent_handlers_.end()) {
- LOG_WARN("Unhandled le subevent of type 0x%02hhx (%s)", subevent_code, SubeventCodeText(subevent_code).c_str());
- return;
- }
- subevent_handlers_[subevent_code].Invoke(meta_event_view);
+ void handle_unregister_le_event_handler(SubeventCode subevent_code) {
+ subevent_handlers_.erase(subevent_code);
}
+ // The HAL
hal::HciHal* hal_;
+
+ // A reference to the HciLayer module
HciLayer& module_;
+ // Interfaces
+ SecurityInterfaceImpl security_interface{module_};
+ LeSecurityInterfaceImpl le_security_interface{module_};
+ LeAdvertisingInterfaceImpl le_advertising_interface{module_};
+ LeScanningInterfaceImpl le_scanning_interface{module_};
+
// Command Handling
std::list<CommandQueueEntry> command_queue_;
- std::map<EventCode, ContextualCallback<void(EventView)>> event_handlers_;
- std::map<SubeventCode, ContextualCallback<void(LeMetaEventView)>> subevent_handlers_;
+ std::map<EventCode, EventHandler> event_handlers_;
+ std::map<SubeventCode, SubeventHandler> subevent_handlers_;
OpCode waiting_command_{OpCode::NONE};
uint8_t command_credits_{1}; // Send reset first
Alarm* hci_timeout_alarm_{nullptr};
- Alarm* hci_abort_alarm_{nullptr};
// Acl packets
- BidiQueue<AclView, AclBuilder> acl_queue_{3 /* TODO: Set queue depth */};
- os::EnqueueBuffer<AclView> incoming_acl_buffer_{acl_queue_.GetDownEnd()};
-
- // ISO packets
- BidiQueue<IsoView, IsoBuilder> iso_queue_{3 /* TODO: Set queue depth */};
- os::EnqueueBuffer<IsoView> incoming_iso_buffer_{iso_queue_.GetDownEnd()};
+ BidiQueue<AclPacketView, AclPacketBuilder> acl_queue_{3 /* TODO: Set queue depth */};
+ os::EnqueueBuffer<AclPacketView> incoming_acl_packet_buffer_{acl_queue_.GetDownEnd()};
};
-// All functions here are running on the HAL thread
-struct HciLayer::hal_callbacks : public hal::HciHalCallbacks {
- hal_callbacks(HciLayer& module) : module_(module) {}
-
- void hciEventReceived(hal::HciPacket event_bytes) override {
- auto packet = packet::PacketView<packet::kLittleEndian>(std::make_shared<std::vector<uint8_t>>(event_bytes));
- EventView event = EventView::Create(packet);
- module_.CallOn(module_.impl_, &impl::on_hci_event, move(event));
- }
-
- void aclDataReceived(hal::HciPacket data_bytes) override {
- auto packet = packet::PacketView<packet::kLittleEndian>(std::make_shared<std::vector<uint8_t>>(move(data_bytes)));
- auto acl = std::make_unique<AclView>(AclView::Create(packet));
- module_.impl_->incoming_acl_buffer_.Enqueue(move(acl), module_.GetHandler());
- }
-
- void scoDataReceived(hal::HciPacket data_bytes) override {
- // Not implemented yet
- }
-
- void isoDataReceived(hal::HciPacket data_bytes) override {
- auto packet = packet::PacketView<packet::kLittleEndian>(std::make_shared<std::vector<uint8_t>>(move(data_bytes)));
- auto iso = std::make_unique<IsoView>(IsoView::Create(packet));
- module_.impl_->incoming_iso_buffer_.Enqueue(move(iso), module_.GetHandler());
- }
-
- HciLayer& module_;
-};
-
-HciLayer::HciLayer() : impl_(nullptr), hal_callbacks_(nullptr) {}
+HciLayer::HciLayer() : impl_(std::make_unique<impl>(*this)) {}
HciLayer::~HciLayer() {
+ impl_.reset();
}
-common::BidiQueueEnd<AclBuilder, AclView>* HciLayer::GetAclQueueEnd() {
- return impl_->acl_queue_.GetUpEnd();
+void HciLayer::EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) {
+ impl_->EnqueueCommand(std::move(command), std::move(on_complete), handler);
}
-common::BidiQueueEnd<IsoBuilder, IsoView>* HciLayer::GetIsoQueueEnd() {
- return impl_->iso_queue_.GetUpEnd();
+void HciLayer::EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) {
+ impl_->EnqueueCommand(std::move(command), std::move(on_status), handler);
}
-void HciLayer::EnqueueCommand(
- unique_ptr<CommandBuilder> command, ContextualOnceCallback<void(CommandCompleteView)> on_complete) {
- CallOn(impl_, &impl::enqueue_command<CommandCompleteView>, move(command), move(on_complete));
+common::BidiQueueEnd<AclPacketBuilder, AclPacketView>* HciLayer::GetAclQueueEnd() {
+ return impl_->GetAclQueueEnd();
}
-void HciLayer::EnqueueCommand(
- unique_ptr<CommandBuilder> command, ContextualOnceCallback<void(CommandStatusView)> on_status) {
- CallOn(impl_, &impl::enqueue_command<CommandStatusView>, move(command), move(on_status));
+void HciLayer::RegisterEventHandler(EventCode event_code, common::Callback<void(EventPacketView)> event_handler,
+ os::Handler* handler) {
+ impl_->RegisterEventHandler(event_code, std::move(event_handler), handler);
}
-void HciLayer::RegisterEventHandler(EventCode event, ContextualCallback<void(EventView)> handler) {
- CallOn(impl_, &impl::register_event, event, handler);
+void HciLayer::UnregisterEventHandler(EventCode event_code) {
+ impl_->UnregisterEventHandler(event_code);
}
-void HciLayer::RegisterLeMetaEventHandler(ContextualCallback<void(EventView)> handler) {
- CallOn(impl_, &impl::register_le_meta_event, handler);
+void HciLayer::RegisterLeEventHandler(SubeventCode subevent_code, common::Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler) {
+ impl_->RegisterLeEventHandler(subevent_code, std::move(event_handler), handler);
}
-void HciLayer::UnregisterEventHandler(EventCode event) {
- CallOn(impl_, &impl::unregister_event, event);
+void HciLayer::UnregisterLeEventHandler(SubeventCode subevent_code) {
+ impl_->UnregisterLeEventHandler(subevent_code);
}
-void HciLayer::RegisterLeEventHandler(SubeventCode event, ContextualCallback<void(LeMetaEventView)> handler) {
- CallOn(impl_, &impl::register_le_event, event, handler);
-}
-
-void HciLayer::UnregisterLeEventHandler(SubeventCode event) {
- CallOn(impl_, &impl::unregister_le_event, event);
-}
-
-void HciLayer::on_disconnection_complete(EventView event_view) {
- auto disconnection_view = DisconnectionCompleteView::Create(event_view);
- if (!disconnection_view.IsValid()) {
- LOG_INFO("Dropping invalid disconnection packet");
- return;
+SecurityInterface* HciLayer::GetSecurityInterface(common::Callback<void(EventPacketView)> event_handler,
+ os::Handler* handler) {
+ for (const auto event : SecurityInterface::SecurityEvents) {
+ RegisterEventHandler(event, event_handler, handler);
}
-
- uint16_t handle = disconnection_view.GetConnectionHandle();
- ErrorCode reason = disconnection_view.GetReason();
- Disconnect(handle, reason);
+ return &impl_->security_interface;
}
-void HciLayer::Disconnect(uint16_t handle, ErrorCode reason) {
- for (auto callback : disconnect_handlers_) {
- callback.Invoke(handle, reason);
+LeSecurityInterface* HciLayer::GetLeSecurityInterface(common::Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler) {
+ for (const auto subevent : LeSecurityInterface::LeSecurityEvents) {
+ RegisterLeEventHandler(subevent, event_handler, handler);
}
+ return &impl_->le_security_interface;
}
-void HciLayer::on_read_remote_version_complete(EventView event_view) {
- auto view = ReadRemoteVersionInformationCompleteView::Create(event_view);
- ASSERT_LOG(view.IsValid(), "Read remote version information packet invalid");
- ReadRemoteVersion(
- view.GetStatus(),
- view.GetConnectionHandle(),
- view.GetVersion(),
- view.GetManufacturerName(),
- view.GetSubVersion());
-}
-
-void HciLayer::ReadRemoteVersion(
- hci::ErrorCode hci_status, uint16_t handle, uint8_t version, uint16_t manufacturer_name, uint16_t sub_version) {
- for (auto callback : read_remote_version_handlers_) {
- callback.Invoke(hci_status, handle, version, manufacturer_name, sub_version);
- }
-}
-
-AclConnectionInterface* HciLayer::GetAclConnectionInterface(
- ContextualCallback<void(EventView)> event_handler,
- ContextualCallback<void(uint16_t, ErrorCode)> on_disconnect,
- ContextualCallback<
- void(hci::ErrorCode hci_status, uint16_t, uint8_t version, uint16_t manufacturer_name, uint16_t sub_version)>
- on_read_remote_version) {
- for (const auto event : AclConnectionEvents) {
- RegisterEventHandler(event, event_handler);
- }
- disconnect_handlers_.push_back(on_disconnect);
- read_remote_version_handlers_.push_back(on_read_remote_version);
- return &acl_connection_manager_interface_;
-}
-
-LeAclConnectionInterface* HciLayer::GetLeAclConnectionInterface(
- ContextualCallback<void(LeMetaEventView)> event_handler,
- ContextualCallback<void(uint16_t, ErrorCode)> on_disconnect,
- ContextualCallback<
- void(hci::ErrorCode hci_status, uint16_t, uint8_t version, uint16_t manufacturer_name, uint16_t sub_version)>
- on_read_remote_version) {
- for (const auto event : LeConnectionManagementEvents) {
- RegisterLeEventHandler(event, event_handler);
- }
- disconnect_handlers_.push_back(on_disconnect);
- read_remote_version_handlers_.push_back(on_read_remote_version);
- return &le_acl_connection_manager_interface_;
-}
-
-SecurityInterface* HciLayer::GetSecurityInterface(ContextualCallback<void(EventView)> event_handler) {
- for (const auto event : SecurityEvents) {
- RegisterEventHandler(event, event_handler);
- }
- return &security_interface;
-}
-
-LeSecurityInterface* HciLayer::GetLeSecurityInterface(ContextualCallback<void(LeMetaEventView)> event_handler) {
- for (const auto subevent : LeSecurityEvents) {
- RegisterLeEventHandler(subevent, event_handler);
- }
- return &le_security_interface;
-}
-
-LeAdvertisingInterface* HciLayer::GetLeAdvertisingInterface(ContextualCallback<void(LeMetaEventView)> event_handler) {
- for (const auto subevent : LeAdvertisingEvents) {
- RegisterLeEventHandler(subevent, event_handler);
+LeAdvertisingInterface* HciLayer::GetLeAdvertisingInterface(common::Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler) {
+ for (const auto subevent : LeAdvertisingInterface::LeAdvertisingEvents) {
+ RegisterLeEventHandler(subevent, event_handler, handler);
}
- return &le_advertising_interface;
+ return &impl_->le_advertising_interface;
}
-LeScanningInterface* HciLayer::GetLeScanningInterface(ContextualCallback<void(LeMetaEventView)> event_handler) {
- for (const auto subevent : LeScanningEvents) {
- RegisterLeEventHandler(subevent, event_handler);
+LeScanningInterface* HciLayer::GetLeScanningInterface(common::Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler) {
+ for (const auto subevent : LeScanningInterface::LeScanningEvents) {
+ RegisterLeEventHandler(subevent, event_handler, handler);
}
- return &le_scanning_interface;
-}
-
-LeIsoInterface* HciLayer::GetLeIsoInterface(ContextualCallback<void(LeMetaEventView)> event_handler) {
- for (const auto subevent : LeIsoEvents) {
- RegisterLeEventHandler(subevent, event_handler);
- }
- return &le_iso_interface;
+ return &impl_->le_scanning_interface;
}
const ModuleFactory HciLayer::Factory = ModuleFactory([]() { return new HciLayer(); });
void HciLayer::ListDependencies(ModuleList* list) {
list->add<hal::HciHal>();
- list->add<storage::StorageModule>();
}
void HciLayer::Start() {
- auto hal = GetDependency<hal::HciHal>();
- impl_ = new impl(hal, *this);
- hal_callbacks_ = new hal_callbacks(*this);
-
- Handler* handler = GetHandler();
- impl_->acl_queue_.GetDownEnd()->RegisterDequeue(handler, BindOn(impl_, &impl::on_outbound_acl_ready));
- impl_->iso_queue_.GetDownEnd()->RegisterDequeue(handler, BindOn(impl_, &impl::on_outbound_iso_ready));
- RegisterEventHandler(EventCode::COMMAND_COMPLETE, handler->BindOn(impl_, &impl::on_command_complete));
- RegisterEventHandler(EventCode::COMMAND_STATUS, handler->BindOn(impl_, &impl::on_command_status));
- RegisterLeMetaEventHandler(handler->BindOn(impl_, &impl::on_le_meta_event));
- if (bluetooth::common::init_flags::gd_acl_is_enabled() || bluetooth::common::init_flags::gd_l2cap_is_enabled()) {
- RegisterEventHandler(
- EventCode::DISCONNECTION_COMPLETE, handler->BindOn(this, &HciLayer::on_disconnection_complete));
- RegisterEventHandler(
- EventCode::READ_REMOTE_VERSION_INFORMATION_COMPLETE,
- handler->BindOn(this, &HciLayer::on_read_remote_version_complete));
- }
- auto drop_packet = handler->BindOn(impl_, &impl::drop);
- RegisterEventHandler(EventCode::PAGE_SCAN_REPETITION_MODE_CHANGE, drop_packet);
- RegisterEventHandler(EventCode::MAX_SLOTS_CHANGE, drop_packet);
-
- EnqueueCommand(ResetBuilder::Create(), handler->BindOnce(&fail_if_reset_complete_not_success));
- hal->registerIncomingPacketCallback(hal_callbacks_);
+ impl_->Start(GetDependency<hal::HciHal>());
}
void HciLayer::Stop() {
- auto hal = GetDependency<hal::HciHal>();
- hal->unregisterIncomingPacketCallback();
- delete hal_callbacks_;
-
- impl_->acl_queue_.GetDownEnd()->UnregisterDequeue();
- impl_->iso_queue_.GetDownEnd()->UnregisterDequeue();
- delete impl_;
+ impl_->Stop();
}
+std::string HciLayer::ToString() const {
+ return "Hci Layer";
+}
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/hci_layer.h b/gd/hci/hci_layer.h
index c6454a7c7..3e299d493 100644
--- a/gd/hci/hci_layer.h
+++ b/gd/hci/hci_layer.h
@@ -23,13 +23,9 @@
#include "class_of_device.h"
#include "common/bidi_queue.h"
#include "common/callback.h"
-#include "common/contextual_callback.h"
#include "hal/hci_hal.h"
-#include "hci/acl_connection_interface.h"
#include "hci/hci_packets.h"
-#include "hci/le_acl_connection_interface.h"
#include "hci/le_advertising_interface.h"
-#include "hci/le_iso_interface.h"
#include "hci/le_scanning_interface.h"
#include "hci/le_security_interface.h"
#include "hci/security_interface.h"
@@ -39,117 +35,55 @@
namespace bluetooth {
namespace hci {
-class HciLayer : public Module, public CommandInterface<CommandBuilder> {
- // LINT.IfChange
+class HciLayer : public Module {
public:
HciLayer();
virtual ~HciLayer();
DISALLOW_COPY_AND_ASSIGN(HciLayer);
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(CommandCompleteView)> on_complete) override;
+ virtual void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler);
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(CommandStatusView)> on_status) override;
+ virtual void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler);
- virtual common::BidiQueueEnd<AclBuilder, AclView>* GetAclQueueEnd();
+ virtual common::BidiQueueEnd<AclPacketBuilder, AclPacketView>* GetAclQueueEnd();
- virtual common::BidiQueueEnd<IsoBuilder, IsoView>* GetIsoQueueEnd();
-
- virtual void RegisterEventHandler(EventCode event_code, common::ContextualCallback<void(EventView)> event_handler);
+ virtual void RegisterEventHandler(EventCode event_code, common::Callback<void(EventPacketView)> event_handler,
+ os::Handler* handler);
virtual void UnregisterEventHandler(EventCode event_code);
- virtual void RegisterLeEventHandler(SubeventCode subevent_code,
- common::ContextualCallback<void(LeMetaEventView)> event_handler);
+ virtual void RegisterLeEventHandler(SubeventCode subevent_code, common::Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler);
virtual void UnregisterLeEventHandler(SubeventCode subevent_code);
- virtual SecurityInterface* GetSecurityInterface(common::ContextualCallback<void(EventView)> event_handler);
-
- virtual LeSecurityInterface* GetLeSecurityInterface(common::ContextualCallback<void(LeMetaEventView)> event_handler);
-
- virtual AclConnectionInterface* GetAclConnectionInterface(
- common::ContextualCallback<void(EventView)> event_handler,
- common::ContextualCallback<void(uint16_t, hci::ErrorCode)> on_disconnect,
- common::ContextualCallback<void(hci::ErrorCode, uint16_t, uint8_t, uint16_t, uint16_t)>
- on_read_remote_version_complete);
-
- virtual LeAclConnectionInterface* GetLeAclConnectionInterface(
- common::ContextualCallback<void(LeMetaEventView)> event_handler,
- common::ContextualCallback<void(uint16_t, hci::ErrorCode)> on_disconnect,
- common::ContextualCallback<void(hci::ErrorCode, uint16_t, uint8_t, uint16_t, uint16_t)>
- on_read_remote_version_complete);
+ SecurityInterface* GetSecurityInterface(common::Callback<void(EventPacketView)> event_handler, os::Handler* handler);
- virtual LeAdvertisingInterface* GetLeAdvertisingInterface(
- common::ContextualCallback<void(LeMetaEventView)> event_handler);
+ LeSecurityInterface* GetLeSecurityInterface(common::Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler);
- virtual LeScanningInterface* GetLeScanningInterface(common::ContextualCallback<void(LeMetaEventView)> event_handler);
+ LeAdvertisingInterface* GetLeAdvertisingInterface(common::Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler);
- virtual LeIsoInterface* GetLeIsoInterface(common::ContextualCallback<void(LeMetaEventView)> event_handler);
-
- std::string ToString() const override {
- return "Hci Layer";
- }
-
- static constexpr std::chrono::milliseconds kHciTimeoutMs = std::chrono::milliseconds(2000);
- static constexpr std::chrono::milliseconds kHciTimeoutRestartMs = std::chrono::milliseconds(5000);
+ LeScanningInterface* GetLeScanningInterface(common::Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler);
static const ModuleFactory Factory;
- protected:
- // LINT.ThenChange(fuzz/fuzz_hci_layer.h)
void ListDependencies(ModuleList* list) override;
void Start() override;
void Stop() override;
- virtual void Disconnect(uint16_t handle, ErrorCode reason);
- virtual void ReadRemoteVersion(
- hci::ErrorCode hci_status, uint16_t handle, uint8_t version, uint16_t manufacturer_name, uint16_t sub_version);
- virtual void RegisterLeMetaEventHandler(common::ContextualCallback<void(EventView)> event_handler);
+ std::string ToString() const override;
+ static constexpr std::chrono::milliseconds kHciTimeoutMs = std::chrono::milliseconds(2000);
private:
struct impl;
- struct hal_callbacks;
- impl* impl_;
- hal_callbacks* hal_callbacks_;
-
- template <typename T>
- class CommandInterfaceImpl : public CommandInterface<T> {
- public:
- explicit CommandInterfaceImpl(HciLayer& hci) : hci_(hci) {}
- ~CommandInterfaceImpl() = default;
-
- void EnqueueCommand(std::unique_ptr<T> command,
- common::ContextualOnceCallback<void(CommandCompleteView)> on_complete) override {
- hci_.EnqueueCommand(move(command), std::move(on_complete));
- }
-
- void EnqueueCommand(std::unique_ptr<T> command,
- common::ContextualOnceCallback<void(CommandStatusView)> on_status) override {
- hci_.EnqueueCommand(move(command), std::move(on_status));
- }
- HciLayer& hci_;
- };
-
- std::list<common::ContextualCallback<void(uint16_t, ErrorCode)>> disconnect_handlers_;
- std::list<common::ContextualCallback<void(hci::ErrorCode, uint16_t, uint8_t, uint16_t, uint16_t)>>
- read_remote_version_handlers_;
- void on_disconnection_complete(EventView event_view);
- void on_read_remote_version_complete(EventView event_view);
-
- // Interfaces
- CommandInterfaceImpl<AclCommandBuilder> acl_connection_manager_interface_{*this};
- CommandInterfaceImpl<AclCommandBuilder> le_acl_connection_manager_interface_{*this};
- CommandInterfaceImpl<SecurityCommandBuilder> security_interface{*this};
- CommandInterfaceImpl<LeSecurityCommandBuilder> le_security_interface{*this};
- CommandInterfaceImpl<LeAdvertisingCommandBuilder> le_advertising_interface{*this};
- CommandInterfaceImpl<LeScanningCommandBuilder> le_scanning_interface{*this};
- CommandInterfaceImpl<LeIsoCommandBuilder> le_iso_interface{*this};
+ std::unique_ptr<impl> impl_;
};
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/hci_layer_test.cc b/gd/hci/hci_layer_test.cc
index 745b71a0e..d79648823 100644
--- a/gd/hci/hci_layer_test.cc
+++ b/gd/hci/hci_layer_test.cc
@@ -35,20 +35,7 @@ using std::vector;
namespace {
vector<uint8_t> information_request = {
- 0xfe,
- 0x2e,
- 0x0a,
- 0x00,
- 0x06,
- 0x00,
- 0x01,
- 0x00,
- 0x0a,
- 0x02,
- 0x02,
- 0x00,
- 0x02,
- 0x00,
+ 0xfe, 0x2e, 0x0a, 0x00, 0x06, 0x00, 0x01, 0x00, 0x0a, 0x02, 0x02, 0x00, 0x02, 0x00,
};
// 0x00, 0x01, 0x02, 0x03, ...
vector<uint8_t> counting_bytes;
@@ -90,7 +77,7 @@ class TestHciHal : public hal::HciHal {
}
void sendAclData(hal::HciPacket data) override {
- outgoing_acl_.push_back(std::move(data));
+ outgoing_acl_.push_front(std::move(data));
if (sent_acl_promise_ != nullptr) {
auto promise = std::move(sent_acl_promise_);
sent_acl_promise_.reset();
@@ -99,16 +86,7 @@ class TestHciHal : public hal::HciHal {
}
void sendScoData(hal::HciPacket data) override {
- outgoing_sco_.push_back(std::move(data));
- }
-
- void sendIsoData(hal::HciPacket data) override {
- outgoing_iso_.push_back(std::move(data));
- if (sent_iso_promise_ != nullptr) {
- auto promise = std::move(sent_iso_promise_);
- sent_iso_promise_.reset();
- promise->set_value();
- }
+ outgoing_sco_.push_front(std::move(data));
}
hal::HciHalCallbacks* callbacks = nullptr;
@@ -128,10 +106,10 @@ class TestHciHal : public hal::HciHal {
return sent_command_promise_->get_future();
}
- CommandView GetSentCommand() {
+ CommandPacketView GetSentCommand() {
auto packetview = GetPacketView(std::move(outgoing_commands_.front()));
outgoing_commands_.pop_front();
- return CommandView::Create(packetview);
+ return CommandPacketView::Create(packetview);
}
std::future<void> GetSentAclFuture() {
@@ -146,38 +124,20 @@ class TestHciHal : public hal::HciHal {
return packetview;
}
- std::future<void> GetSentIsoFuture() {
- ASSERT_LOG(sent_iso_promise_ == nullptr, "Promises promises ... Only one at a time");
- sent_iso_promise_ = std::make_unique<std::promise<void>>();
- return sent_iso_promise_->get_future();
- }
-
- PacketView<kLittleEndian> GetSentIso() {
- auto packetview = GetPacketView(std::move(outgoing_iso_.front()));
- outgoing_iso_.pop_front();
- return packetview;
- }
-
void Start() {}
void Stop() {}
void ListDependencies(ModuleList*) {}
- std::string ToString() const override {
- return std::string("TestHciHal");
- }
-
static const ModuleFactory Factory;
private:
std::list<hal::HciPacket> outgoing_commands_;
std::list<hal::HciPacket> outgoing_acl_;
std::list<hal::HciPacket> outgoing_sco_;
- std::list<hal::HciPacket> outgoing_iso_;
std::unique_ptr<std::promise<void>> sent_command_promise_;
std::unique_ptr<std::promise<void>> sent_acl_promise_;
- std::unique_ptr<std::promise<void>> sent_iso_promise_;
};
const ModuleFactory TestHciHal::Factory = ModuleFactory([]() { return new TestHciHal(); });
@@ -186,55 +146,52 @@ class DependsOnHci : public Module {
public:
DependsOnHci() : Module() {}
- void SendHciCommandExpectingStatus(std::unique_ptr<CommandBuilder> command) {
- hci_->EnqueueCommand(
- std::move(command), GetHandler()->BindOnceOn(this, &DependsOnHci::handle_event<CommandStatusView>));
+ void SendHciCommandExpectingStatus(std::unique_ptr<CommandPacketBuilder> command) {
+ hci_->EnqueueCommand(std::move(command),
+ common::Bind(&DependsOnHci::handle_event<CommandStatusView>, common::Unretained(this)),
+ GetHandler());
}
- void SendHciCommandExpectingComplete(std::unique_ptr<CommandBuilder> command) {
- hci_->EnqueueCommand(
- std::move(command), GetHandler()->BindOnceOn(this, &DependsOnHci::handle_event<CommandCompleteView>));
+ void SendHciCommandExpectingComplete(std::unique_ptr<CommandPacketBuilder> command) {
+ hci_->EnqueueCommand(std::move(command),
+ common::Bind(&DependsOnHci::handle_event<CommandCompleteView>, common::Unretained(this)),
+ GetHandler());
}
void SendSecurityCommandExpectingComplete(std::unique_ptr<SecurityCommandBuilder> command) {
if (security_interface_ == nullptr) {
- security_interface_ =
- hci_->GetSecurityInterface(GetHandler()->BindOn(this, &DependsOnHci::handle_event<EventView>));
+ security_interface_ = hci_->GetSecurityInterface(
+ common::Bind(&DependsOnHci::handle_event<EventPacketView>, common::Unretained(this)), GetHandler());
}
- hci_->EnqueueCommand(
- std::move(command), GetHandler()->BindOnceOn(this, &DependsOnHci::handle_event<CommandCompleteView>));
+ hci_->EnqueueCommand(std::move(command),
+ common::Bind(&DependsOnHci::handle_event<CommandCompleteView>, common::Unretained(this)),
+ GetHandler());
}
void SendLeSecurityCommandExpectingComplete(std::unique_ptr<LeSecurityCommandBuilder> command) {
if (le_security_interface_ == nullptr) {
- le_security_interface_ =
- hci_->GetLeSecurityInterface(GetHandler()->BindOn(this, &DependsOnHci::handle_event<LeMetaEventView>));
+ le_security_interface_ = hci_->GetLeSecurityInterface(
+ common::Bind(&DependsOnHci::handle_event<LeMetaEventView>, common::Unretained(this)), GetHandler());
}
- hci_->EnqueueCommand(
- std::move(command), GetHandler()->BindOnceOn(this, &DependsOnHci::handle_event<CommandCompleteView>));
+ hci_->EnqueueCommand(std::move(command),
+ common::Bind(&DependsOnHci::handle_event<CommandCompleteView>, common::Unretained(this)),
+ GetHandler());
}
- void SendAclData(std::unique_ptr<AclBuilder> acl) {
+ void SendAclData(std::unique_ptr<AclPacketBuilder> acl) {
outgoing_acl_.push(std::move(acl));
auto queue_end = hci_->GetAclQueueEnd();
queue_end->RegisterEnqueue(GetHandler(), common::Bind(&DependsOnHci::handle_enqueue, common::Unretained(this)));
}
- void SendIsoData(std::unique_ptr<IsoBuilder> iso) {
- outgoing_iso_.push(std::move(iso));
- auto queue_end = hci_->GetIsoQueueEnd();
- queue_end->RegisterEnqueue(GetHandler(), common::Bind(&DependsOnHci::handle_enqueue_iso, common::Unretained(this)));
- }
-
std::future<void> GetReceivedEventFuture() {
ASSERT_LOG(event_promise_ == nullptr, "Promises promises ... Only one at a time");
event_promise_ = std::make_unique<std::promise<void>>();
return event_promise_->get_future();
}
- EventView GetReceivedEvent() {
- std::lock_guard<std::mutex> lock(list_protector_);
- EventView packetview = incoming_events_.front();
+ EventPacketView GetReceivedEvent() {
+ EventPacketView packetview = incoming_events_.front();
incoming_events_.pop_front();
return packetview;
}
@@ -249,72 +206,44 @@ class DependsOnHci : public Module {
return incoming_acl_packets_.size();
}
- AclView GetReceivedAcl() {
- std::lock_guard<std::mutex> lock(list_protector_);
- AclView packetview = incoming_acl_packets_.front();
+ AclPacketView GetReceivedAcl() {
+ AclPacketView packetview = incoming_acl_packets_.front();
incoming_acl_packets_.pop_front();
return packetview;
}
- std::future<void> GetReceivedIsoFuture() {
- ASSERT_LOG(iso_promise_ == nullptr, "Promises promises ... Only one at a time");
- iso_promise_ = std::make_unique<std::promise<void>>();
- return iso_promise_->get_future();
- }
-
- size_t GetNumReceivedIsoPackets() {
- return incoming_iso_packets_.size();
- }
-
- IsoView GetReceivedIso() {
- std::lock_guard<std::mutex> lock(list_protector_);
- IsoView packetview = incoming_iso_packets_.front();
- incoming_iso_packets_.pop_front();
- return packetview;
- }
-
void Start() {
hci_ = GetDependency<HciLayer>();
- hci_->RegisterEventHandler(
- EventCode::CONNECTION_COMPLETE, GetHandler()->BindOn(this, &DependsOnHci::handle_event<EventView>));
- hci_->RegisterLeEventHandler(
- SubeventCode::CONNECTION_COMPLETE, GetHandler()->BindOn(this, &DependsOnHci::handle_event<LeMetaEventView>));
- hci_->GetAclQueueEnd()->RegisterDequeue(
- GetHandler(), common::Bind(&DependsOnHci::handle_acl, common::Unretained(this)));
- hci_->GetIsoQueueEnd()->RegisterDequeue(
- GetHandler(), common::Bind(&DependsOnHci::handle_iso, common::Unretained(this)));
+ hci_->RegisterEventHandler(EventCode::CONNECTION_COMPLETE,
+ common::Bind(&DependsOnHci::handle_event<EventPacketView>, common::Unretained(this)),
+ GetHandler());
+ hci_->RegisterLeEventHandler(SubeventCode::CONNECTION_COMPLETE,
+ common::Bind(&DependsOnHci::handle_event<LeMetaEventView>, common::Unretained(this)),
+ GetHandler());
+ hci_->GetAclQueueEnd()->RegisterDequeue(GetHandler(),
+ common::Bind(&DependsOnHci::handle_acl, common::Unretained(this)));
}
void Stop() {
hci_->GetAclQueueEnd()->UnregisterDequeue();
- hci_->GetIsoQueueEnd()->UnregisterDequeue();
}
void ListDependencies(ModuleList* list) {
list->add<HciLayer>();
}
- std::string ToString() const override {
- return std::string("DependsOnHci");
- }
-
static const ModuleFactory Factory;
private:
HciLayer* hci_ = nullptr;
const SecurityInterface* security_interface_;
const LeSecurityInterface* le_security_interface_;
- std::list<EventView> incoming_events_;
- std::list<AclView> incoming_acl_packets_;
- std::list<IsoView> incoming_iso_packets_;
+ std::list<EventPacketView> incoming_events_;
+ std::list<AclPacketView> incoming_acl_packets_;
std::unique_ptr<std::promise<void>> event_promise_;
std::unique_ptr<std::promise<void>> acl_promise_;
- std::unique_ptr<std::promise<void>> iso_promise_;
- /* This mutex is protecting lists above from being pushed/popped from different threads at same time */
- std::mutex list_protector_;
void handle_acl() {
- std::lock_guard<std::mutex> lock(list_protector_);
auto acl_ptr = hci_->GetAclQueueEnd()->TryDequeue();
incoming_acl_packets_.push_back(*acl_ptr);
if (acl_promise_ != nullptr) {
@@ -326,7 +255,6 @@ class DependsOnHci : public Module {
template <typename T>
void handle_event(T event) {
- std::lock_guard<std::mutex> lock(list_protector_);
incoming_events_.push_back(event);
if (event_promise_ != nullptr) {
auto promise = std::move(event_promise_);
@@ -335,34 +263,14 @@ class DependsOnHci : public Module {
}
}
- void handle_iso() {
- std::lock_guard<std::mutex> lock(list_protector_);
- auto iso_ptr = hci_->GetIsoQueueEnd()->TryDequeue();
- incoming_iso_packets_.push_back(*iso_ptr);
- if (iso_promise_ != nullptr) {
- auto promise = std::move(iso_promise_);
- iso_promise_.reset();
- promise->set_value();
- }
- }
-
- std::queue<std::unique_ptr<AclBuilder>> outgoing_acl_;
+ std::queue<std::unique_ptr<AclPacketBuilder>> outgoing_acl_;
- std::unique_ptr<AclBuilder> handle_enqueue() {
+ std::unique_ptr<AclPacketBuilder> handle_enqueue() {
hci_->GetAclQueueEnd()->UnregisterEnqueue();
auto acl = std::move(outgoing_acl_.front());
outgoing_acl_.pop();
return acl;
}
-
- std::queue<std::unique_ptr<IsoBuilder>> outgoing_iso_;
-
- std::unique_ptr<IsoBuilder> handle_enqueue_iso() {
- hci_->GetIsoQueueEnd()->UnregisterEnqueue();
- auto iso = std::move(outgoing_iso_.front());
- outgoing_iso_.pop();
- return iso;
- }
};
const ModuleFactory DependsOnHci::Factory = ModuleFactory([]() { return new DependsOnHci(); });
@@ -384,7 +292,7 @@ class HciTest : public ::testing::Test {
fake_registry_.Start<DependsOnHci>(&fake_registry_.GetTestThread());
hci = static_cast<HciLayer*>(fake_registry_.GetModuleUnderTest(&HciLayer::Factory));
upper = static_cast<DependsOnHci*>(fake_registry_.GetModuleUnderTest(&DependsOnHci::Factory));
- ASSERT_TRUE(fake_registry_.IsStarted<HciLayer>());
+ ASSERT(fake_registry_.IsStarted<HciLayer>());
auto reset_sent_status = command_future.wait_for(kTimeout);
ASSERT_EQ(reset_sent_status, std::future_status::ready);
@@ -393,7 +301,7 @@ class HciTest : public ::testing::Test {
ASSERT_EQ(1, hal->GetNumSentCommands());
auto sent_command = hal->GetSentCommand();
- auto reset_view = ResetView::Create(CommandView::Create(sent_command));
+ auto reset_view = ResetView::Create(CommandPacketView::Create(sent_command));
ASSERT_TRUE(reset_view.IsValid());
// Verify that only one was sent
@@ -431,50 +339,23 @@ TEST_F(HciTest, leMetaEvent) {
// Send an LE event
ErrorCode status = ErrorCode::SUCCESS;
uint16_t handle = 0x123;
- Role role = Role::CENTRAL;
+ Role role = Role::MASTER;
AddressType peer_address_type = AddressType::PUBLIC_DEVICE_ADDRESS;
Address peer_address = Address::kAny;
uint16_t conn_interval = 0x0ABC;
uint16_t conn_latency = 0x0123;
uint16_t supervision_timeout = 0x0B05;
- ClockAccuracy central_clock_accuracy = ClockAccuracy::PPM_50;
- hal->callbacks->hciEventReceived(GetPacketBytes(LeConnectionCompleteBuilder::Create(
- status,
- handle,
- role,
- peer_address_type,
- peer_address,
- conn_interval,
- conn_latency,
- supervision_timeout,
- central_clock_accuracy)));
+ MasterClockAccuracy master_clock_accuracy = MasterClockAccuracy::PPM_50;
+ hal->callbacks->hciEventReceived(GetPacketBytes(
+ LeConnectionCompleteBuilder::Create(status, handle, role, peer_address_type, peer_address, conn_interval,
+ conn_latency, supervision_timeout, master_clock_accuracy)));
// Wait for the event
auto event_status = event_future.wait_for(kTimeout);
ASSERT_EQ(event_status, std::future_status::ready);
auto event = upper->GetReceivedEvent();
- ASSERT_TRUE(LeConnectionCompleteView::Create(LeMetaEventView::Create(EventView::Create(event))).IsValid());
-}
-
-TEST_F(HciTest, hciTimeOut) {
- auto event_future = upper->GetReceivedEventFuture();
- auto reset_command_future = hal->GetSentCommandFuture();
- upper->SendHciCommandExpectingComplete(ResetBuilder::Create());
- auto reset_command_sent_status = reset_command_future.wait_for(kTimeout);
- ASSERT_EQ(reset_command_sent_status, std::future_status::ready);
- auto reset = hal->GetSentCommand();
- ASSERT_TRUE(reset.IsValid());
- ASSERT_EQ(reset.GetOpCode(), OpCode::RESET);
-
- auto debug_command_future = hal->GetSentCommandFuture();
- auto event_status = event_future.wait_for(HciLayer::kHciTimeoutMs);
- ASSERT_NE(event_status, std::future_status::ready);
- auto debug_command_sent_status = debug_command_future.wait_for(kTimeout);
- ASSERT_EQ(debug_command_sent_status, std::future_status::ready);
- auto debug = hal->GetSentCommand();
- ASSERT_TRUE(debug.IsValid());
- ASSERT_EQ(debug.GetOpCode(), OpCode::CONTROLLER_DEBUG_INFO);
+ ASSERT(LeConnectionCompleteView::Create(LeMetaEventView::Create(EventPacketView::Create(event))).IsValid());
}
TEST_F(HciTest, noOpCredits) {
@@ -517,8 +398,8 @@ TEST_F(HciTest, noOpCredits) {
ASSERT_EQ(event_status, std::future_status::ready);
auto event = upper->GetReceivedEvent();
- ASSERT_TRUE(
- ReadLocalVersionInformationCompleteView::Create(CommandCompleteView::Create(EventView::Create(event))).IsValid());
+ ASSERT(ReadLocalVersionInformationCompleteView::Create(CommandCompleteView::Create(EventPacketView::Create(event)))
+ .IsValid());
}
TEST_F(HciTest, creditsTest) {
@@ -538,7 +419,7 @@ TEST_F(HciTest, creditsTest) {
ASSERT_EQ(1, hal->GetNumSentCommands());
auto sent_command = hal->GetSentCommand();
- auto version_view = ReadLocalVersionInformationView::Create(CommandView::Create(sent_command));
+ auto version_view = ReadLocalVersionInformationView::Create(CommandPacketView::Create(sent_command));
ASSERT_TRUE(version_view.IsValid());
// Verify that only one was sent
@@ -564,8 +445,8 @@ TEST_F(HciTest, creditsTest) {
ASSERT_EQ(event_status, std::future_status::ready);
auto event = upper->GetReceivedEvent();
- ASSERT_TRUE(
- ReadLocalVersionInformationCompleteView::Create(CommandCompleteView::Create(EventView::Create(event))).IsValid());
+ ASSERT(ReadLocalVersionInformationCompleteView::Create(CommandCompleteView::Create(EventPacketView::Create(event)))
+ .IsValid());
// Verify that the second one is sent
command_sent_status = command_future.wait_for(kTimeout);
@@ -573,7 +454,7 @@ TEST_F(HciTest, creditsTest) {
ASSERT_EQ(1, hal->GetNumSentCommands());
sent_command = hal->GetSentCommand();
- auto supported_commands_view = ReadLocalSupportedCommandsView::Create(CommandView::Create(sent_command));
+ auto supported_commands_view = ReadLocalSupportedCommandsView::Create(CommandPacketView::Create(sent_command));
ASSERT_TRUE(supported_commands_view.IsValid());
// Verify that only one was sent
@@ -593,15 +474,15 @@ TEST_F(HciTest, creditsTest) {
ASSERT_EQ(event_status, std::future_status::ready);
event = upper->GetReceivedEvent();
- ASSERT_TRUE(
- ReadLocalSupportedCommandsCompleteView::Create(CommandCompleteView::Create(EventView::Create(event))).IsValid());
+ ASSERT(ReadLocalSupportedCommandsCompleteView::Create(CommandCompleteView::Create(EventPacketView::Create(event)))
+ .IsValid());
// Verify that the third one is sent
command_sent_status = command_future.wait_for(kTimeout);
ASSERT_EQ(command_sent_status, std::future_status::ready);
ASSERT_EQ(1, hal->GetNumSentCommands());
sent_command = hal->GetSentCommand();
- auto supported_features_view = ReadLocalSupportedFeaturesView::Create(CommandView::Create(sent_command));
+ auto supported_features_view = ReadLocalSupportedFeaturesView::Create(CommandPacketView::Create(sent_command));
ASSERT_TRUE(supported_features_view.IsValid());
// Verify that only one was sent
@@ -617,8 +498,8 @@ TEST_F(HciTest, creditsTest) {
event_status = event_future.wait_for(kTimeout);
ASSERT_EQ(event_status, std::future_status::ready);
event = upper->GetReceivedEvent();
- ASSERT_TRUE(
- ReadLocalSupportedFeaturesCompleteView::Create(CommandCompleteView::Create(EventView::Create(event))).IsValid());
+ ASSERT(ReadLocalSupportedFeaturesCompleteView::Create(CommandCompleteView::Create(EventPacketView::Create(event)))
+ .IsValid());
}
TEST_F(HciTest, leSecurityInterfaceTest) {
@@ -632,7 +513,7 @@ TEST_F(HciTest, leSecurityInterfaceTest) {
// Check the command
auto sent_command = hal->GetSentCommand();
ASSERT_LT(0, sent_command.size());
- LeRandView view = LeRandView::Create(LeSecurityCommandView::Create(CommandView::Create(sent_command)));
+ LeRandView view = LeRandView::Create(LeSecurityCommandView::Create(CommandPacketView::Create(sent_command)));
ASSERT_TRUE(view.IsValid());
// Send a Command Complete to the host
@@ -663,7 +544,7 @@ TEST_F(HciTest, securityInterfacesTest) {
// Check the command
auto sent_command = hal->GetSentCommand();
ASSERT_LT(0, sent_command.size());
- auto view = WriteSimplePairingModeView::Create(SecurityCommandView::Create(CommandView::Create(sent_command)));
+ auto view = WriteSimplePairingModeView::Create(SecurityCommandView::Create(CommandPacketView::Create(sent_command)));
ASSERT_TRUE(view.IsValid());
// Send a Command Complete to the host
@@ -700,8 +581,8 @@ TEST_F(HciTest, createConnectionTest) {
// Check the command
auto sent_command = hal->GetSentCommand();
ASSERT_LT(0, sent_command.size());
- CreateConnectionView view = CreateConnectionView::Create(
- ConnectionManagementCommandView::Create(AclCommandView::Create(CommandView::Create(sent_command))));
+ CreateConnectionView view =
+ CreateConnectionView::Create(ConnectionManagementCommandView::Create(CommandPacketView::Create(sent_command)));
ASSERT_TRUE(view.IsValid());
ASSERT_EQ(bd_addr, view.GetBdAddr());
ASSERT_EQ(packet_type, view.GetPacketType());
@@ -751,14 +632,14 @@ TEST_F(HciTest, createConnectionTest) {
acl_payload->AddOctets2(handle);
auto incoming_acl_future = upper->GetReceivedAclFuture();
hal->callbacks->aclDataReceived(
- GetPacketBytes(AclBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(acl_payload))));
+ GetPacketBytes(AclPacketBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(acl_payload))));
// Verify the ACL packet
auto incoming_acl_status = incoming_acl_future.wait_for(kAclTimeout);
ASSERT_EQ(incoming_acl_status, std::future_status::ready);
auto acl_view = upper->GetReceivedAcl();
ASSERT_TRUE(acl_view.IsValid());
- ASSERT_EQ(bd_addr.length() + sizeof(handle), acl_view.GetPayload().size());
+ ASSERT_EQ(sizeof(bd_addr) + sizeof(handle), acl_view.GetPayload().size());
auto itr = acl_view.GetPayload().begin();
ASSERT_EQ(bd_addr, itr.extract<Address>());
ASSERT_EQ(handle, itr.extract<uint16_t>());
@@ -770,16 +651,16 @@ TEST_F(HciTest, createConnectionTest) {
acl_payload2->AddOctets2(handle);
acl_payload2->AddAddress(bd_addr);
auto sent_acl_future = hal->GetSentAclFuture();
- upper->SendAclData(AclBuilder::Create(handle, packet_boundary_flag2, broadcast_flag2, std::move(acl_payload2)));
+ upper->SendAclData(AclPacketBuilder::Create(handle, packet_boundary_flag2, broadcast_flag2, std::move(acl_payload2)));
// Verify the ACL packet
auto sent_acl_status = sent_acl_future.wait_for(kAclTimeout);
ASSERT_EQ(sent_acl_status, std::future_status::ready);
auto sent_acl = hal->GetSentAcl();
ASSERT_LT(0, sent_acl.size());
- AclView sent_acl_view = AclView::Create(sent_acl);
+ AclPacketView sent_acl_view = AclPacketView::Create(sent_acl);
ASSERT_TRUE(sent_acl_view.IsValid());
- ASSERT_EQ(bd_addr.length() + sizeof(handle), sent_acl_view.GetPayload().size());
+ ASSERT_EQ(sizeof(bd_addr) + sizeof(handle), sent_acl_view.GetPayload().size());
auto sent_itr = sent_acl_view.GetPayload().begin();
ASSERT_EQ(handle, sent_itr.extract<uint16_t>());
ASSERT_EQ(bd_addr, sent_itr.extract<Address>());
@@ -789,7 +670,7 @@ TEST_F(HciTest, receiveMultipleAclPackets) {
Address bd_addr;
ASSERT_TRUE(Address::FromString("A1:A2:A3:A4:A5:A6", bd_addr));
uint16_t handle = 0x0001;
- const uint16_t num_packets = 100;
+ uint16_t num_packets = 100;
PacketBoundaryFlag packet_boundary_flag = PacketBoundaryFlag::FIRST_AUTOMATICALLY_FLUSHABLE;
BroadcastFlag broadcast_flag = BroadcastFlag::POINT_TO_POINT;
for (uint16_t i = 0; i < num_packets; i++) {
@@ -798,23 +679,20 @@ TEST_F(HciTest, receiveMultipleAclPackets) {
acl_payload->AddOctets2(handle);
acl_payload->AddOctets2(i);
hal->callbacks->aclDataReceived(
- GetPacketBytes(AclBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(acl_payload))));
+ GetPacketBytes(AclPacketBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(acl_payload))));
}
auto incoming_acl_future = upper->GetReceivedAclFuture();
uint16_t received_packets = 0;
while (received_packets < num_packets - 1) {
- size_t num_rcv_packets = upper->GetNumReceivedAclPackets();
- if (num_rcv_packets == 0) {
- auto incoming_acl_status = incoming_acl_future.wait_for(kAclTimeout);
- // Get the next future.
- ASSERT_EQ(incoming_acl_status, std::future_status::ready);
- incoming_acl_future = upper->GetReceivedAclFuture();
- num_rcv_packets = upper->GetNumReceivedAclPackets();
- }
- for (size_t i = 0; i < num_rcv_packets; i++) {
+ auto incoming_acl_status = incoming_acl_future.wait_for(kAclTimeout);
+ // Get the next future.
+ incoming_acl_future = upper->GetReceivedAclFuture();
+ ASSERT_EQ(incoming_acl_status, std::future_status::ready);
+ size_t num_packets = upper->GetNumReceivedAclPackets();
+ for (size_t i = 0; i < num_packets; i++) {
auto acl_view = upper->GetReceivedAcl();
ASSERT_TRUE(acl_view.IsValid());
- ASSERT_EQ(bd_addr.length() + sizeof(handle) + sizeof(received_packets), acl_view.GetPayload().size());
+ ASSERT_EQ(sizeof(bd_addr) + sizeof(handle) + sizeof(received_packets), acl_view.GetPayload().size());
auto itr = acl_view.GetPayload().begin();
ASSERT_EQ(bd_addr, itr.extract<Address>());
ASSERT_EQ(handle, itr.extract<uint16_t>());
@@ -836,73 +714,16 @@ TEST_F(HciTest, receiveMultipleAclPackets) {
acl_payload->AddOctets2(handle);
acl_payload->AddOctets2(num_packets);
hal->callbacks->aclDataReceived(
- GetPacketBytes(AclBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(acl_payload))));
+ GetPacketBytes(AclPacketBuilder::Create(handle, packet_boundary_flag, broadcast_flag, std::move(acl_payload))));
auto incoming_acl_status = incoming_acl_future.wait_for(kAclTimeout);
ASSERT_EQ(incoming_acl_status, std::future_status::ready);
auto acl_view = upper->GetReceivedAcl();
ASSERT_TRUE(acl_view.IsValid());
- ASSERT_EQ(bd_addr.length() + sizeof(handle) + sizeof(received_packets), acl_view.GetPayload().size());
+ ASSERT_EQ(sizeof(bd_addr) + sizeof(handle) + sizeof(received_packets), acl_view.GetPayload().size());
auto itr = acl_view.GetPayload().begin();
ASSERT_EQ(bd_addr, itr.extract<Address>());
ASSERT_EQ(handle, itr.extract<uint16_t>());
ASSERT_EQ(received_packets, itr.extract<uint16_t>());
}
-
-TEST_F(HciTest, receiveMultipleIsoPackets) {
- uint16_t handle = 0x0001;
- const uint16_t num_packets = 100;
- IsoPacketBoundaryFlag packet_boundary_flag = IsoPacketBoundaryFlag::COMPLETE_SDU;
- TimeStampFlag timestamp_flag = TimeStampFlag::NOT_PRESENT;
- for (uint16_t i = 0; i < num_packets; i++) {
- auto iso_payload = std::make_unique<RawBuilder>();
- iso_payload->AddOctets2(handle);
- iso_payload->AddOctets2(i);
- hal->callbacks->isoDataReceived(
- GetPacketBytes(IsoBuilder::Create(handle, packet_boundary_flag, timestamp_flag, std::move(iso_payload))));
- }
- auto incoming_iso_future = upper->GetReceivedIsoFuture();
- uint16_t received_packets = 0;
- while (received_packets < num_packets - 1) {
- size_t num_rcv_packets = upper->GetNumReceivedIsoPackets();
- if (num_rcv_packets == 0) {
- auto incoming_iso_status = incoming_iso_future.wait_for(kAclTimeout);
- // Get the next future.
- ASSERT_EQ(incoming_iso_status, std::future_status::ready);
- incoming_iso_future = upper->GetReceivedIsoFuture();
- num_rcv_packets = upper->GetNumReceivedIsoPackets();
- }
- for (size_t i = 0; i < num_rcv_packets; i++) {
- auto iso_view = upper->GetReceivedIso();
- ASSERT_TRUE(iso_view.IsValid());
- ASSERT_EQ(sizeof(handle) + sizeof(received_packets), iso_view.GetPayload().size());
- auto itr = iso_view.GetPayload().begin();
- ASSERT_EQ(handle, itr.extract<uint16_t>());
- ASSERT_EQ(received_packets, itr.extract<uint16_t>());
- received_packets += 1;
- }
- }
-
- // Check to see if this future was already fulfilled.
- auto iso_race_status = incoming_iso_future.wait_for(std::chrono::milliseconds(1));
- if (iso_race_status == std::future_status::ready) {
- // Get the next future.
- incoming_iso_future = upper->GetReceivedIsoFuture();
- }
-
- // One last packet to make sure they were all sent. Already got the future.
- auto iso_payload = std::make_unique<RawBuilder>();
- iso_payload->AddOctets2(handle);
- iso_payload->AddOctets2(num_packets);
- hal->callbacks->isoDataReceived(
- GetPacketBytes(IsoBuilder::Create(handle, packet_boundary_flag, timestamp_flag, std::move(iso_payload))));
- auto incoming_iso_status = incoming_iso_future.wait_for(kAclTimeout);
- ASSERT_EQ(incoming_iso_status, std::future_status::ready);
- auto iso_view = upper->GetReceivedIso();
- ASSERT_TRUE(iso_view.IsValid());
- ASSERT_EQ(sizeof(handle) + sizeof(received_packets), iso_view.GetPayload().size());
- auto itr = iso_view.GetPayload().begin();
- ASSERT_EQ(handle, itr.extract<uint16_t>());
- ASSERT_EQ(received_packets, itr.extract<uint16_t>());
-}
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/hci_metrics_logging.cc b/gd/hci/hci_metrics_logging.cc
deleted file mode 100644
index 00fb9a211..000000000
--- a/gd/hci/hci_metrics_logging.cc
+++ /dev/null
@@ -1,877 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
-
-#include "common/strings.h"
-#include "hci/hci_metrics_logging.h"
-#include "os/metrics.h"
-#include "storage/device.h"
-
-namespace bluetooth {
-namespace hci {
-
-void log_hci_event(
- std::unique_ptr<CommandView>& command_view, EventView event_view, storage::StorageModule* storage_module) {
- ASSERT(event_view.IsValid());
- EventCode event_code = event_view.GetEventCode();
- switch (event_code) {
- case EventCode::COMMAND_COMPLETE: {
- ASSERT(command_view->IsValid());
- log_link_layer_connection_command_complete(event_view, command_view);
- log_classic_pairing_command_complete(event_view, command_view);
- break;
- }
- case EventCode::COMMAND_STATUS: {
- ASSERT(command_view->IsValid());
- CommandStatusView response_view = CommandStatusView::Create(event_view);
- ASSERT(response_view.IsValid());
- log_link_layer_connection_command_status(command_view, response_view.GetStatus());
- log_classic_pairing_command_status(command_view, response_view.GetStatus());
- break;
- }
- case EventCode::LE_META_EVENT: {
- LeMetaEventView le_meta_event_view = LeMetaEventView::Create(event_view);
- ASSERT(le_meta_event_view.IsValid());
- log_link_layer_connection_event_le_meta(le_meta_event_view);
- break;
- }
- default:
- log_link_layer_connection_other_hci_event(event_view, storage_module);
- log_classic_pairing_other_hci_event(event_view);
- }
-}
-void log_link_layer_connection_command_status(std::unique_ptr<CommandView>& command_view, ErrorCode status) {
- // get op_code
- ASSERT(command_view->IsValid());
- OpCode op_code = command_view->GetOpCode();
-
- // init parameters to log
- Address address = Address::kEmpty;
- uint32_t connection_handle = bluetooth::os::kUnknownConnectionHandle;
- uint16_t reason = static_cast<uint16_t>(ErrorCode::UNKNOWN_HCI_COMMAND);
- static uint16_t kUnknownBleEvt = android::bluetooth::hci::BLE_EVT_UNKNOWN;
- uint16_t event_code = android::bluetooth::hci::EVT_COMMAND_STATUS;
- android::bluetooth::DirectionEnum direction = android::bluetooth::DIRECTION_UNKNOWN;
- uint16_t link_type = android::bluetooth::LINK_TYPE_UNKNOWN;
-
- // get ConnectionManagementCommandView
- ConnectionManagementCommandView connection_management_command_view =
- ConnectionManagementCommandView::Create(AclCommandView::Create(*command_view));
- ASSERT(connection_management_command_view.IsValid());
- switch (op_code) {
- case OpCode::CREATE_CONNECTION: {
- auto create_connection_view = CreateConnectionView::Create(std::move(connection_management_command_view));
- ASSERT(create_connection_view.IsValid());
- address = create_connection_view.GetBdAddr();
- direction = android::bluetooth::DIRECTION_OUTGOING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- break;
- }
- case OpCode::CREATE_CONNECTION_CANCEL: {
- auto create_connection_cancel_view =
- CreateConnectionCancelView::Create(std::move(connection_management_command_view));
- ASSERT(create_connection_cancel_view.IsValid());
- address = create_connection_cancel_view.GetBdAddr();
- direction = android::bluetooth::DIRECTION_OUTGOING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- break;
- }
- case OpCode::DISCONNECT: {
- auto disconnect_view = DisconnectView::Create(std::move(connection_management_command_view));
- ASSERT(disconnect_view.IsValid());
- connection_handle = disconnect_view.GetConnectionHandle();
- reason = static_cast<uint16_t>(disconnect_view.GetReason());
- break;
- }
- case OpCode::SETUP_SYNCHRONOUS_CONNECTION: {
- auto setup_synchronous_connection_view = SetupSynchronousConnectionView::Create(
- ScoConnectionCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(setup_synchronous_connection_view.IsValid());
- connection_handle = setup_synchronous_connection_view.GetConnectionHandle();
- direction = android::bluetooth::DIRECTION_OUTGOING;
- break;
- }
- case OpCode::ENHANCED_SETUP_SYNCHRONOUS_CONNECTION: {
- auto enhanced_setup_synchronous_connection_view = EnhancedSetupSynchronousConnectionView::Create(
- ScoConnectionCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(enhanced_setup_synchronous_connection_view.IsValid());
- connection_handle = enhanced_setup_synchronous_connection_view.GetConnectionHandle();
- direction = android::bluetooth::DIRECTION_OUTGOING;
- break;
- }
- case OpCode::ACCEPT_CONNECTION_REQUEST: {
- auto accept_connection_request_view =
- AcceptConnectionRequestView::Create(std::move(connection_management_command_view));
- ASSERT(accept_connection_request_view.IsValid());
- address = accept_connection_request_view.GetBdAddr();
- direction = android::bluetooth::DIRECTION_INCOMING;
- break;
- }
- case OpCode::ACCEPT_SYNCHRONOUS_CONNECTION: {
- auto accept_synchronous_connection_view = AcceptSynchronousConnectionView::Create(
- ScoConnectionCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(accept_synchronous_connection_view.IsValid());
- address = accept_synchronous_connection_view.GetBdAddr();
- direction = android::bluetooth::DIRECTION_INCOMING;
- break;
- }
- case OpCode::ENHANCED_ACCEPT_SYNCHRONOUS_CONNECTION: {
- auto enhanced_accept_synchronous_connection_view = EnhancedAcceptSynchronousConnectionView::Create(
- ScoConnectionCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(enhanced_accept_synchronous_connection_view.IsValid());
- address = enhanced_accept_synchronous_connection_view.GetBdAddr();
- direction = android::bluetooth::DIRECTION_INCOMING;
- break;
- }
- case OpCode::REJECT_CONNECTION_REQUEST: {
- auto reject_connection_request_view =
- RejectConnectionRequestView::Create(std::move(connection_management_command_view));
- ASSERT(reject_connection_request_view.IsValid());
- address = reject_connection_request_view.GetBdAddr();
- reason = static_cast<uint16_t>(reject_connection_request_view.GetReason());
- direction = android::bluetooth::DIRECTION_INCOMING;
- break;
- }
- case OpCode::REJECT_SYNCHRONOUS_CONNECTION: {
- auto reject_synchronous_connection_view = RejectSynchronousConnectionView::Create(
- ScoConnectionCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(reject_synchronous_connection_view.IsValid());
- address = reject_synchronous_connection_view.GetBdAddr();
- reason = static_cast<uint16_t>(reject_synchronous_connection_view.GetReason());
- direction = android::bluetooth::DIRECTION_INCOMING;
- break;
- }
- case OpCode::LE_CREATE_CONNECTION: {
- auto le_create_connection_view = LeCreateConnectionView::Create(
- LeConnectionManagementCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(le_create_connection_view.IsValid());
- uint8_t initiator_filter_policy = static_cast<uint8_t>(le_create_connection_view.GetInitiatorFilterPolicy());
- if (initiator_filter_policy != 0x00 && status == ErrorCode::SUCCESS) {
- return;
- }
- address = le_create_connection_view.GetPeerAddress();
- direction = android::bluetooth::DIRECTION_INCOMING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- break;
- }
- case OpCode::LE_EXTENDED_CREATE_CONNECTION: {
- auto le_extended_create_connection_view = LeExtendedCreateConnectionView::Create(
- LeConnectionManagementCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(le_extended_create_connection_view.IsValid());
- uint8_t initiator_filter_policy =
- static_cast<uint8_t>(le_extended_create_connection_view.GetInitiatorFilterPolicy());
- if (initiator_filter_policy != 0x00 && status == ErrorCode::SUCCESS) {
- return;
- }
- address = le_extended_create_connection_view.GetPeerAddress();
- direction = android::bluetooth::DIRECTION_OUTGOING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- break;
- }
- case OpCode::LE_CREATE_CONNECTION_CANCEL: {
- auto le_create_connection_cancel_view = LeCreateConnectionCancelView::Create(
- LeConnectionManagementCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(le_create_connection_cancel_view.IsValid());
- if (status == ErrorCode::SUCCESS) {
- return;
- }
- direction = android::bluetooth::DIRECTION_OUTGOING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- break;
- }
- case OpCode::LE_CLEAR_CONNECT_LIST: {
- auto le_clear_connect_list_view = LeClearConnectListView::Create(
- LeConnectionManagementCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(le_clear_connect_list_view.IsValid());
- direction = android::bluetooth::DIRECTION_INCOMING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- break;
- }
- case OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST: {
- auto le_add_device_to_connect_list_view = LeAddDeviceToConnectListView::Create(
- LeConnectionManagementCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(le_add_device_to_connect_list_view.IsValid());
- address = le_add_device_to_connect_list_view.GetAddress();
- direction = android::bluetooth::DIRECTION_INCOMING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- break;
- }
- case OpCode::LE_REMOVE_DEVICE_FROM_CONNECT_LIST: {
- auto le_remove_device_from_connect_list_view = LeRemoveDeviceFromConnectListView::Create(
- LeConnectionManagementCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(le_remove_device_from_connect_list_view.IsValid());
- address = le_remove_device_from_connect_list_view.GetAddress();
- direction = android::bluetooth::DIRECTION_INCOMING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- break;
- }
- default:
- return;
- }
- os::LogMetricLinkLayerConnectionEvent(
- &address,
- connection_handle,
- direction,
- link_type,
- static_cast<uint32_t>(op_code),
- static_cast<uint16_t>(event_code),
- kUnknownBleEvt,
- static_cast<uint16_t>(status),
- static_cast<uint16_t>(reason));
-}
-
-void log_link_layer_connection_command_complete(EventView event_view, std::unique_ptr<CommandView>& command_view) {
- CommandCompleteView command_complete_view = CommandCompleteView::Create(std::move(event_view));
- ASSERT(command_complete_view.IsValid());
- OpCode op_code = command_complete_view.GetCommandOpCode();
-
- // init parameters to log
- Address address = Address::kEmpty;
- uint32_t connection_handle = bluetooth::os::kUnknownConnectionHandle;
- ErrorCode status = ErrorCode::UNKNOWN_HCI_COMMAND;
- ErrorCode reason = ErrorCode::UNKNOWN_HCI_COMMAND;
- static uint16_t kUnknownBleEvt = android::bluetooth::hci::BLE_EVT_UNKNOWN;
- uint16_t event_code = android::bluetooth::hci::EVT_COMMAND_COMPLETE;
- android::bluetooth::DirectionEnum direction = android::bluetooth::DIRECTION_UNKNOWN;
- uint16_t link_type = android::bluetooth::LINK_TYPE_UNKNOWN;
-
- // get ConnectionManagementCommandView
- ConnectionManagementCommandView connection_management_command_view =
- ConnectionManagementCommandView::Create(AclCommandView::Create(*command_view));
- ASSERT(connection_management_command_view.IsValid());
-
- switch (op_code) {
- case OpCode::LE_CLEAR_CONNECT_LIST: {
- auto le_clear_connect_list_view = LeClearConnectListView::Create(
- LeConnectionManagementCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(le_clear_connect_list_view.IsValid());
- direction = android::bluetooth::DIRECTION_INCOMING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- break;
- }
- case OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST: {
- auto le_add_device_to_connect_list_view = LeAddDeviceToConnectListView::Create(
- LeConnectionManagementCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(le_add_device_to_connect_list_view.IsValid());
- address = le_add_device_to_connect_list_view.GetAddress();
- direction = android::bluetooth::DIRECTION_INCOMING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- break;
- }
- case OpCode::LE_REMOVE_DEVICE_FROM_CONNECT_LIST: {
- auto le_remove_device_from_connect_list_view = LeRemoveDeviceFromConnectListView::Create(
- LeConnectionManagementCommandView::Create(std::move(connection_management_command_view)));
- ASSERT(le_remove_device_from_connect_list_view.IsValid());
- address = le_remove_device_from_connect_list_view.GetAddress();
- direction = android::bluetooth::DIRECTION_INCOMING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- break;
- }
- case OpCode::CREATE_CONNECTION_CANCEL: {
- auto create_connection_cancel_complete_view =
- CreateConnectionCancelCompleteView::Create(std::move(command_complete_view));
- ASSERT(create_connection_cancel_complete_view.IsValid());
- address = create_connection_cancel_complete_view.GetBdAddr();
- direction = android::bluetooth::DIRECTION_OUTGOING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- status = create_connection_cancel_complete_view.GetStatus();
- break;
- }
- case OpCode::LE_CREATE_CONNECTION_CANCEL: {
- auto le_create_connection_cancel_complete_view =
- LeCreateConnectionCancelCompleteView::Create(std::move(command_complete_view));
- ASSERT(le_create_connection_cancel_complete_view.IsValid());
- direction = android::bluetooth::DIRECTION_OUTGOING;
- link_type = android::bluetooth::LINK_TYPE_ACL;
- status = le_create_connection_cancel_complete_view.GetStatus();
- break;
- }
- default:
- return;
- }
- os::LogMetricLinkLayerConnectionEvent(
- &address,
- connection_handle,
- direction,
- link_type,
- static_cast<uint32_t>(op_code),
- static_cast<uint16_t>(event_code),
- kUnknownBleEvt,
- static_cast<uint16_t>(status),
- static_cast<uint16_t>(reason));
-}
-
-void log_link_layer_connection_other_hci_event(EventView packet, storage::StorageModule* storage_module) {
- EventCode event_code = packet.GetEventCode();
- Address address = Address::kEmpty;
- uint32_t connection_handle = bluetooth::os::kUnknownConnectionHandle;
- android::bluetooth::DirectionEnum direction = android::bluetooth::DIRECTION_UNKNOWN;
- uint16_t link_type = android::bluetooth::LINK_TYPE_UNKNOWN;
- ErrorCode status = ErrorCode::UNKNOWN_HCI_COMMAND;
- ErrorCode reason = ErrorCode::UNKNOWN_HCI_COMMAND;
- uint32_t cmd = android::bluetooth::hci::CMD_UNKNOWN;
- switch (event_code) {
- case EventCode::CONNECTION_COMPLETE: {
- auto connection_complete_view = ConnectionCompleteView::Create(std::move(packet));
- ASSERT(connection_complete_view.IsValid());
- address = connection_complete_view.GetBdAddr();
- connection_handle = connection_complete_view.GetConnectionHandle();
- link_type = static_cast<uint16_t>(connection_complete_view.GetLinkType());
- status = connection_complete_view.GetStatus();
-
- // besides log link layer connection events, also log remote device manufacturer info
- log_remote_device_information(address, connection_handle, status, storage_module);
- break;
- }
- case EventCode::CONNECTION_REQUEST: {
- auto connection_request_view = ConnectionRequestView::Create(std::move(packet));
- ASSERT(connection_request_view.IsValid());
- address = connection_request_view.GetBdAddr();
- link_type = static_cast<uint16_t>(connection_request_view.GetLinkType());
- direction = android::bluetooth::DIRECTION_INCOMING;
- break;
- }
- case EventCode::DISCONNECTION_COMPLETE: {
- auto disconnection_complete_view = DisconnectionCompleteView::Create(std::move(packet));
- ASSERT(disconnection_complete_view.IsValid());
- status = disconnection_complete_view.GetStatus();
- connection_handle = disconnection_complete_view.GetConnectionHandle();
- reason = disconnection_complete_view.GetReason();
- break;
- }
- case EventCode::SYNCHRONOUS_CONNECTION_COMPLETE: {
- auto synchronous_connection_complete_view = SynchronousConnectionCompleteView::Create(std::move(packet));
- ASSERT(synchronous_connection_complete_view.IsValid());
- connection_handle = synchronous_connection_complete_view.GetConnectionHandle();
- address = synchronous_connection_complete_view.GetBdAddr();
- link_type = static_cast<uint16_t>(synchronous_connection_complete_view.GetLinkType());
- status = synchronous_connection_complete_view.GetStatus();
- break;
- }
- case EventCode::SYNCHRONOUS_CONNECTION_CHANGED: {
- auto synchronous_connection_changed_view = SynchronousConnectionChangedView::Create(std::move(packet));
- ASSERT(synchronous_connection_changed_view.IsValid());
- status = synchronous_connection_changed_view.GetStatus();
- connection_handle = synchronous_connection_changed_view.GetConnectionHandle();
- break;
- }
- default:
- return;
- }
- os::LogMetricLinkLayerConnectionEvent(
- &address,
- connection_handle,
- direction,
- link_type,
- static_cast<uint32_t>(cmd),
- static_cast<uint16_t>(event_code),
- android::bluetooth::hci::BLE_EVT_UNKNOWN,
- static_cast<uint16_t>(status),
- static_cast<uint16_t>(reason));
-}
-
-void log_link_layer_connection_event_le_meta(LeMetaEventView le_meta_event_view) {
- SubeventCode leEvt = le_meta_event_view.GetSubeventCode();
- auto le_connection_complete_view = LeConnectionCompleteView::Create(std::move(le_meta_event_view));
- if (!le_connection_complete_view.IsValid()) {
- // function is called for all le meta events. Only need to process le connection complete.
- return;
- }
- ASSERT(le_connection_complete_view.IsValid());
- // init parameters to log
- EventCode event_code = EventCode::LE_META_EVENT;
- Address address = le_connection_complete_view.GetPeerAddress();
- uint32_t connection_handle = le_connection_complete_view.GetConnectionHandle();
- android::bluetooth::DirectionEnum direction = android::bluetooth::DIRECTION_UNKNOWN;
- uint16_t link_type = android::bluetooth::LINK_TYPE_ACL;
- ErrorCode status = le_connection_complete_view.GetStatus();
- ErrorCode reason = ErrorCode::UNKNOWN_HCI_COMMAND;
- uint32_t cmd = android::bluetooth::hci::CMD_UNKNOWN;
-
- os::LogMetricLinkLayerConnectionEvent(
- &address,
- connection_handle,
- direction,
- link_type,
- static_cast<uint32_t>(cmd),
- static_cast<uint16_t>(event_code),
- static_cast<uint16_t>(leEvt),
- static_cast<uint16_t>(status),
- static_cast<uint16_t>(reason));
-}
-
-void log_classic_pairing_other_hci_event(EventView packet) {
- EventCode event_code = packet.GetEventCode();
- Address address = Address::kEmpty;
- uint32_t cmd = android::bluetooth::hci::CMD_UNKNOWN;
- ErrorCode status = ErrorCode::UNKNOWN_HCI_COMMAND;
- ErrorCode reason = ErrorCode::UNKNOWN_HCI_COMMAND;
- uint32_t connection_handle = bluetooth::os::kUnknownConnectionHandle;
- int64_t value = 0;
-
- switch (event_code) {
- case EventCode::IO_CAPABILITY_REQUEST: {
- IoCapabilityRequestView io_capability_request_view = IoCapabilityRequestView::Create(std::move(packet));
- ASSERT(io_capability_request_view.IsValid());
- address = io_capability_request_view.GetBdAddr();
- break;
- }
- case EventCode::IO_CAPABILITY_RESPONSE: {
- IoCapabilityResponseView io_capability_response_view = IoCapabilityResponseView::Create(std::move(packet));
- ASSERT(io_capability_response_view.IsValid());
- address = io_capability_response_view.GetBdAddr();
- break;
- }
- case EventCode::LINK_KEY_REQUEST: {
- LinkKeyRequestView link_key_request_view = LinkKeyRequestView::Create(std::move(packet));
- ASSERT(link_key_request_view.IsValid());
- address = link_key_request_view.GetBdAddr();
- break;
- }
- case EventCode::LINK_KEY_NOTIFICATION: {
- LinkKeyNotificationView link_key_notification_view = LinkKeyNotificationView::Create(std::move(packet));
- ASSERT(link_key_notification_view.IsValid());
- address = link_key_notification_view.GetBdAddr();
- break;
- }
- case EventCode::USER_PASSKEY_REQUEST: {
- UserPasskeyRequestView user_passkey_request_view = UserPasskeyRequestView::Create(std::move(packet));
- ASSERT(user_passkey_request_view.IsValid());
- address = user_passkey_request_view.GetBdAddr();
- break;
- }
- case EventCode::USER_PASSKEY_NOTIFICATION: {
- UserPasskeyNotificationView user_passkey_notification_view = UserPasskeyNotificationView::Create(std::move(packet));
- ASSERT(user_passkey_notification_view.IsValid());
- address = user_passkey_notification_view.GetBdAddr();
- break;
- }
- case EventCode::USER_CONFIRMATION_REQUEST: {
- UserConfirmationRequestView user_confirmation_request_view = UserConfirmationRequestView::Create(std::move(packet));
- ASSERT(user_confirmation_request_view.IsValid());
- address = user_confirmation_request_view.GetBdAddr();
- break;
- }
- case EventCode::KEYPRESS_NOTIFICATION: {
- KeypressNotificationView keypress_notification_view = KeypressNotificationView::Create(std::move(packet));
- ASSERT(keypress_notification_view.IsValid());
- address = keypress_notification_view.GetBdAddr();
- break;
- }
- case EventCode::REMOTE_OOB_DATA_REQUEST: {
- RemoteOobDataRequestView remote_oob_data_request_view = RemoteOobDataRequestView::Create(std::move(packet));
- ASSERT(remote_oob_data_request_view.IsValid());
- address = remote_oob_data_request_view.GetBdAddr();
- break;
- }
- case EventCode::SIMPLE_PAIRING_COMPLETE: {
- SimplePairingCompleteView simple_pairing_complete_view = SimplePairingCompleteView::Create(std::move(packet));
- ASSERT(simple_pairing_complete_view.IsValid());
- address = simple_pairing_complete_view.GetBdAddr();
- status = simple_pairing_complete_view.GetStatus();
- break;
- }
- case EventCode::REMOTE_NAME_REQUEST_COMPLETE: {
- RemoteNameRequestCompleteView remote_name_request_complete_view = RemoteNameRequestCompleteView::Create(std::move(packet));
- ASSERT(remote_name_request_complete_view.IsValid());
- address = remote_name_request_complete_view.GetBdAddr();
- status = remote_name_request_complete_view.GetStatus();
- break;
- }
- case EventCode::AUTHENTICATION_COMPLETE: {
- AuthenticationCompleteView authentication_complete_view = AuthenticationCompleteView::Create(std::move(packet));
- ASSERT(authentication_complete_view.IsValid());
- status = authentication_complete_view.GetStatus();
- connection_handle = authentication_complete_view.GetConnectionHandle();
- break;
- }
- case EventCode::ENCRYPTION_CHANGE: {
- EncryptionChangeView encryption_change_view = EncryptionChangeView::Create(std::move(packet));
- ASSERT(encryption_change_view.IsValid());
- status = encryption_change_view.GetStatus();
- connection_handle = encryption_change_view.GetConnectionHandle();
- value = static_cast<int64_t>(encryption_change_view.GetEncryptionEnabled());
- break;
- }
- default:
- return;
- }
- os::LogMetricClassicPairingEvent(
- address,
- connection_handle,
- static_cast<uint32_t>(cmd),
- static_cast<uint16_t>(event_code),
- static_cast<uint16_t>(status),
- static_cast<uint16_t>(reason),
- value);
-}
-
-void log_classic_pairing_command_status(std::unique_ptr<CommandView>& command_view, ErrorCode status) {
- // get op_code
- ASSERT(command_view->IsValid());
- OpCode op_code = command_view->GetOpCode();
-
- // init parameters
- Address address = Address::kEmpty;
- ErrorCode reason = ErrorCode::UNKNOWN_HCI_COMMAND;
- uint32_t connection_handle = bluetooth::os::kUnknownConnectionHandle;
- int64_t value = 0;
- uint16_t event_code = android::bluetooth::hci::EVT_COMMAND_STATUS;
-
- // create SecurityCommandView
- SecurityCommandView security_command_view = SecurityCommandView::Create(*command_view);
- ASSERT(security_command_view.IsValid());
-
- // create ConnectionManagementCommandView
- ConnectionManagementCommandView connection_management_command_view =
- ConnectionManagementCommandView::Create(AclCommandView::Create(*command_view));
- ASSERT(connection_management_command_view.IsValid());
-
- // create DiscoveryCommandView
- DiscoveryCommandView discovery_command_view = DiscoveryCommandView::Create(*command_view);
- ASSERT(discovery_command_view.IsValid());
-
- switch (op_code) {
- case OpCode::READ_LOCAL_OOB_DATA: {
- ReadLocalOobDataView read_local_oob_data_view = ReadLocalOobDataView::Create(std::move(security_command_view));
- ASSERT(read_local_oob_data_view.IsValid());
- break;
- }
- case OpCode::WRITE_SIMPLE_PAIRING_MODE: {
- WriteSimplePairingModeView write_simple_pairing_mode_view
- = WriteSimplePairingModeView::Create(std::move(security_command_view));
- ASSERT(write_simple_pairing_mode_view.IsValid());
- value = static_cast<int64_t>(write_simple_pairing_mode_view.GetSimplePairingMode());
- break;
- }
- case OpCode::WRITE_SECURE_CONNECTIONS_HOST_SUPPORT: {
- WriteSecureConnectionsHostSupportView write_secure_connections_host_support_view
- = WriteSecureConnectionsHostSupportView::Create(std::move(security_command_view));
- ASSERT(write_secure_connections_host_support_view.IsValid());
- value = static_cast<int64_t>(write_secure_connections_host_support_view.GetSecureConnectionsHostSupport());
- break;
- }
- case OpCode::AUTHENTICATION_REQUESTED: {
- AuthenticationRequestedView authentication_requested_view
- = AuthenticationRequestedView::Create(std::move(connection_management_command_view));
- ASSERT(authentication_requested_view.IsValid());
- connection_handle = authentication_requested_view.GetConnectionHandle();
- break;
- }
- case OpCode::SET_CONNECTION_ENCRYPTION: {
- SetConnectionEncryptionView set_connection_encryption_view
- = SetConnectionEncryptionView::Create(std::move(connection_management_command_view));
- ASSERT(set_connection_encryption_view.IsValid());
- connection_handle = set_connection_encryption_view.GetConnectionHandle();
- value = static_cast<int64_t>(set_connection_encryption_view.GetEncryptionEnable());
- break;
- }
- case OpCode::DELETE_STORED_LINK_KEY: {
- DeleteStoredLinkKeyView delete_stored_link_key_view
- = DeleteStoredLinkKeyView::Create(std::move(security_command_view));
- ASSERT(delete_stored_link_key_view.IsValid());
- address = delete_stored_link_key_view.GetBdAddr();
- value = static_cast<int64_t>(delete_stored_link_key_view.GetDeleteAllFlag());
- break;
- }
- case OpCode::REMOTE_NAME_REQUEST: {
- RemoteNameRequestView remote_name_request_view = RemoteNameRequestView::Create(std::move(discovery_command_view));
- ASSERT(remote_name_request_view.IsValid());
- address = remote_name_request_view.GetBdAddr();
- break;
- }
- case OpCode::REMOTE_NAME_REQUEST_CANCEL: {
- RemoteNameRequestCancelView remote_name_request_cancel_view
- = RemoteNameRequestCancelView::Create(std::move(discovery_command_view));
- ASSERT(remote_name_request_cancel_view.IsValid());
- address = remote_name_request_cancel_view.GetBdAddr();
- break;
- }
- case OpCode::LINK_KEY_REQUEST_REPLY: {
- LinkKeyRequestReplyView link_key_request_reply_view
- = LinkKeyRequestReplyView::Create(std::move(security_command_view));
- ASSERT(link_key_request_reply_view.IsValid());
- address = link_key_request_reply_view.GetBdAddr();
- break;
- }
- case OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY: {
- LinkKeyRequestNegativeReplyView link_key_request_negative_reply_view
- = LinkKeyRequestNegativeReplyView::Create(std::move(security_command_view));
- ASSERT(link_key_request_negative_reply_view.IsValid());
- address = link_key_request_negative_reply_view.GetBdAddr();
- break;
- }
- case OpCode::IO_CAPABILITY_REQUEST_REPLY: {
- IoCapabilityRequestReplyView io_capability_request_reply_view
- = IoCapabilityRequestReplyView::Create(std::move(security_command_view));
- ASSERT(io_capability_request_reply_view.IsValid());
- address = io_capability_request_reply_view.GetBdAddr();
- break;
- }
- case OpCode::USER_CONFIRMATION_REQUEST_REPLY: {
- UserConfirmationRequestReplyView user_confirmation_request_reply
- = UserConfirmationRequestReplyView::Create(std::move(security_command_view));
- ASSERT(user_confirmation_request_reply.IsValid());
- address = user_confirmation_request_reply.GetBdAddr();
- break;
- }
- case OpCode::USER_CONFIRMATION_REQUEST_NEGATIVE_REPLY: {
- UserConfirmationRequestNegativeReplyView user_confirmation_request_negative_reply
- = UserConfirmationRequestNegativeReplyView::Create(std::move(security_command_view));
- ASSERT(user_confirmation_request_negative_reply.IsValid());
- address = user_confirmation_request_negative_reply.GetBdAddr();
- break;
- }
- case OpCode::USER_PASSKEY_REQUEST_REPLY: {
- UserPasskeyRequestReplyView user_passkey_request_reply
- = UserPasskeyRequestReplyView::Create(std::move(security_command_view));
- ASSERT(user_passkey_request_reply.IsValid());
- address = user_passkey_request_reply.GetBdAddr();
- break;
- }
- case OpCode::USER_PASSKEY_REQUEST_NEGATIVE_REPLY: {
- UserPasskeyRequestNegativeReplyView user_passkey_request_negative_reply
- = UserPasskeyRequestNegativeReplyView::Create(std::move(security_command_view));
- ASSERT(user_passkey_request_negative_reply.IsValid());
- address = user_passkey_request_negative_reply.GetBdAddr();
- break;
- }
- case OpCode::REMOTE_OOB_DATA_REQUEST_REPLY: {
- RemoteOobDataRequestReplyView remote_oob_data_request_reply_view
- = RemoteOobDataRequestReplyView::Create(std::move(security_command_view));
- ASSERT(remote_oob_data_request_reply_view.IsValid());
- address = remote_oob_data_request_reply_view.GetBdAddr();
- break;
- }
- case OpCode::REMOTE_OOB_DATA_REQUEST_NEGATIVE_REPLY: {
- RemoteOobDataRequestNegativeReplyView remote_oob_data_request_negative_reply_view
- = RemoteOobDataRequestNegativeReplyView::Create(std::move(security_command_view));
- ASSERT(remote_oob_data_request_negative_reply_view.IsValid());
- address = remote_oob_data_request_negative_reply_view.GetBdAddr();
- break;
- }
- case OpCode::IO_CAPABILITY_REQUEST_NEGATIVE_REPLY: {
- IoCapabilityRequestNegativeReplyView io_capability_request_negative_reply_view
- = IoCapabilityRequestNegativeReplyView::Create(std::move(security_command_view));
- ASSERT(io_capability_request_negative_reply_view.IsValid());
- address = io_capability_request_negative_reply_view.GetBdAddr();
- reason = io_capability_request_negative_reply_view.GetReason();
- break;
- }
- default:
- return;
- }
- os::LogMetricClassicPairingEvent(
- address,
- connection_handle,
- static_cast<uint32_t>(op_code),
- static_cast<uint16_t>(event_code),
- static_cast<uint16_t>(status),
- static_cast<uint16_t>(reason),
- value);
-}
-
-void log_classic_pairing_command_complete(EventView event_view, std::unique_ptr<CommandView>& command_view) {
-
- // get op_code
- CommandCompleteView command_complete_view = CommandCompleteView::Create(std::move(event_view));
- ASSERT(command_complete_view.IsValid());
- OpCode op_code = command_complete_view.GetCommandOpCode();
-
- // init parameters
- Address address = Address::kEmpty;
- ErrorCode status = ErrorCode::UNKNOWN_HCI_COMMAND;
- ErrorCode reason = ErrorCode::UNKNOWN_HCI_COMMAND;
- uint32_t connection_handle = bluetooth::os::kUnknownConnectionHandle;
- int64_t value = 0;
- EventCode event_code = EventCode::COMMAND_COMPLETE;
-
- // get ConnectionManagementCommandView
- ConnectionManagementCommandView connection_management_command_view =
- ConnectionManagementCommandView::Create(AclCommandView::Create(*command_view));
- ASSERT(connection_management_command_view.IsValid());
-
- // create SecurityCommandView
- SecurityCommandView security_command_view = SecurityCommandView::Create(*command_view);
- ASSERT(security_command_view.IsValid());
-
- switch (op_code) {
- case OpCode::DELETE_STORED_LINK_KEY: {
- auto delete_stored_link_key_complete_view = DeleteStoredLinkKeyCompleteView::Create(std::move(command_complete_view));
- ASSERT(delete_stored_link_key_complete_view.IsValid());
- status = delete_stored_link_key_complete_view.GetStatus();
- break;
- }
- case OpCode::READ_LOCAL_OOB_DATA: {
- auto read_local_oob_data_complete_view = ReadLocalOobDataCompleteView::Create(std::move(command_complete_view));
- ASSERT(read_local_oob_data_complete_view.IsValid());
- status = read_local_oob_data_complete_view.GetStatus();
- break;
- }
- case OpCode::WRITE_SIMPLE_PAIRING_MODE: {
- auto write_simple_pairing_mode_complete_view = WriteSimplePairingModeCompleteView::Create(std::move(command_complete_view));
- ASSERT(write_simple_pairing_mode_complete_view.IsValid());
- status = write_simple_pairing_mode_complete_view.GetStatus();
- break;
- }
- case OpCode::WRITE_SECURE_CONNECTIONS_HOST_SUPPORT: {
- auto write_secure_connections_host_support_complete_view = WriteSecureConnectionsHostSupportCompleteView::Create(std::move(command_complete_view));
- ASSERT(write_secure_connections_host_support_complete_view.IsValid());
- status = write_secure_connections_host_support_complete_view.GetStatus();
- break;
- }
- case OpCode::READ_ENCRYPTION_KEY_SIZE: {
- auto read_encryption_key_size_complete_view = ReadEncryptionKeySizeCompleteView::Create(std::move(command_complete_view));
- ASSERT(read_encryption_key_size_complete_view.IsValid());
- status = read_encryption_key_size_complete_view.GetStatus();
- connection_handle = read_encryption_key_size_complete_view.GetConnectionHandle();
- value = read_encryption_key_size_complete_view.GetKeySize();
- break;
- }
- case OpCode::LINK_KEY_REQUEST_REPLY: {
- auto link_key_request_reply_complete_view = LinkKeyRequestReplyCompleteView::Create(std::move(command_complete_view));
- ASSERT(link_key_request_reply_complete_view.IsValid());
- status = link_key_request_reply_complete_view.GetStatus();
- auto link_key_request_reply_view = LinkKeyRequestReplyView::Create(std::move(security_command_view));
- ASSERT(link_key_request_reply_view.IsValid());
- address = link_key_request_reply_view.GetBdAddr();
- break;
- }
- case OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY: {
- auto link_key_request_negative_reply_complete_view = LinkKeyRequestNegativeReplyCompleteView::Create(std::move(command_complete_view));
- ASSERT(link_key_request_negative_reply_complete_view.IsValid());
- status = link_key_request_negative_reply_complete_view.GetStatus();
- auto link_key_request_negative_reply_view = LinkKeyRequestNegativeReplyView::Create(std::move(security_command_view));
- ASSERT(link_key_request_negative_reply_view.IsValid());
- address = link_key_request_negative_reply_view.GetBdAddr();
- break;
- }
- case OpCode::IO_CAPABILITY_REQUEST_REPLY: {
- auto io_capability_request_reply_complete_view = IoCapabilityRequestReplyCompleteView::Create(std::move(command_complete_view));
- ASSERT(io_capability_request_reply_complete_view.IsValid());
- status = io_capability_request_reply_complete_view.GetStatus();
- auto io_capability_request_reply_view = IoCapabilityRequestReplyView::Create(std::move(security_command_view));
- ASSERT(io_capability_request_reply_view.IsValid());
- address = io_capability_request_reply_view.GetBdAddr();
- break;
- }
- case OpCode::IO_CAPABILITY_REQUEST_NEGATIVE_REPLY: {
- auto io_capability_request_negative_reply_complete_view = IoCapabilityRequestNegativeReplyCompleteView::Create(std::move(command_complete_view));
- ASSERT(io_capability_request_negative_reply_complete_view.IsValid());
- status = io_capability_request_negative_reply_complete_view.GetStatus();
- auto io_capability_request_negative_reply_view = IoCapabilityRequestNegativeReplyView::Create(std::move(security_command_view));
- ASSERT(io_capability_request_negative_reply_view.IsValid());
- address = io_capability_request_negative_reply_view.GetBdAddr();
- break;
- }
- case OpCode::USER_CONFIRMATION_REQUEST_REPLY: {
- auto user_confirmation_request_reply_complete_view = UserConfirmationRequestReplyCompleteView::Create(std::move(command_complete_view));
- ASSERT(user_confirmation_request_reply_complete_view.IsValid());
- status = user_confirmation_request_reply_complete_view.GetStatus();
- auto user_confirmation_request_reply_view = UserConfirmationRequestReplyView::Create(std::move(security_command_view));
- ASSERT(user_confirmation_request_reply_view.IsValid());
- address = user_confirmation_request_reply_view.GetBdAddr();
- break;
- }
- case OpCode::USER_CONFIRMATION_REQUEST_NEGATIVE_REPLY: {
- auto user_confirmation_request_negative_reply_complete_view = UserConfirmationRequestNegativeReplyCompleteView::Create(std::move(command_complete_view));
- ASSERT(user_confirmation_request_negative_reply_complete_view.IsValid());
- status = user_confirmation_request_negative_reply_complete_view.GetStatus();
- auto user_confirmation_request_negative_reply_view = UserConfirmationRequestNegativeReplyView::Create(std::move(security_command_view));
- ASSERT(user_confirmation_request_negative_reply_view.IsValid());
- address = user_confirmation_request_negative_reply_view.GetBdAddr();
- break;
- }
- case OpCode::USER_PASSKEY_REQUEST_REPLY: {
- auto user_passkey_request_reply_complete_view = UserPasskeyRequestReplyCompleteView::Create(std::move(command_complete_view));
- ASSERT(user_passkey_request_reply_complete_view.IsValid());
- status = user_passkey_request_reply_complete_view.GetStatus();
- auto user_passkey_request_reply_view = UserPasskeyRequestReplyView::Create(std::move(security_command_view));
- ASSERT(user_passkey_request_reply_view.IsValid());
- address = user_passkey_request_reply_view.GetBdAddr();
- break;
- }
- case OpCode::USER_PASSKEY_REQUEST_NEGATIVE_REPLY: {
- auto user_passkey_request_negative_reply_complete_view = UserPasskeyRequestNegativeReplyCompleteView::Create(std::move(command_complete_view));
- ASSERT(user_passkey_request_negative_reply_complete_view.IsValid());
- status = user_passkey_request_negative_reply_complete_view.GetStatus();
- auto user_passkey_request_negative_reply_view = UserPasskeyRequestNegativeReplyView::Create(std::move(security_command_view));
- ASSERT(user_passkey_request_negative_reply_view.IsValid());
- address = user_passkey_request_negative_reply_view.GetBdAddr();
- break;
- }
- case OpCode::REMOTE_OOB_DATA_REQUEST_REPLY: {
- auto remote_oob_data_request_reply_complete_view = RemoteOobDataRequestReplyCompleteView::Create(std::move(command_complete_view));
- ASSERT(remote_oob_data_request_reply_complete_view.IsValid());
- status = remote_oob_data_request_reply_complete_view.GetStatus();
- auto remote_oob_data_request_reply_view = RemoteOobDataRequestReplyView::Create(std::move(security_command_view));
- ASSERT(remote_oob_data_request_reply_view.IsValid());
- address = remote_oob_data_request_reply_view.GetBdAddr();
- break;
- }
- case OpCode::REMOTE_OOB_DATA_REQUEST_NEGATIVE_REPLY: {
- auto remote_oob_data_request_negative_reply_complete_view = RemoteOobDataRequestNegativeReplyCompleteView::Create(std::move(command_complete_view));
- ASSERT(remote_oob_data_request_negative_reply_complete_view.IsValid());
- status = remote_oob_data_request_negative_reply_complete_view.GetStatus();
- auto remote_oob_data_request_negative_reply_view = RemoteOobDataRequestNegativeReplyView::Create(std::move(security_command_view));
- ASSERT(remote_oob_data_request_negative_reply_view.IsValid());
- address = remote_oob_data_request_negative_reply_view.GetBdAddr();
- break;
- }
- default:
- return;
- }
- os::LogMetricClassicPairingEvent(
- address,
- connection_handle,
- static_cast<uint32_t>(op_code),
- static_cast<uint16_t>(event_code),
- static_cast<uint16_t>(status),
- static_cast<uint16_t>(reason),
- value);
-}
-
-void log_remote_device_information(
- const Address& address, uint32_t connection_handle, ErrorCode status, storage::StorageModule* storage_module) {
- if (address.IsEmpty()) {
- return;
- }
- const storage::Device device = storage_module->GetDeviceByLegacyKey(address);
- // log ManufacturerInfo
- std::stringstream sdp_di_vendor_id_source;
- // [N - native]::SDP::[DIP - Device ID Profile]
- sdp_di_vendor_id_source << "N:SDP::DIP::" << common::ToHexString(device.GetSdpDiVendorIdSource().value_or(0)).c_str();
- os::LogMetricManufacturerInfo(
- address,
- android::bluetooth::DeviceInfoSrcEnum::DEVICE_INFO_INTERNAL,
- sdp_di_vendor_id_source.str(),
- common::ToHexString(device.GetSdpDiManufacturer().value_or(0)).c_str(),
- common::ToHexString(device.GetSdpDiModel().value_or(0)).c_str(),
- common::ToHexString(device.GetSdpDiHardwareVersion().value_or(0)).c_str(),
- "");
-
- // log RemoteVersionInfo
- os::LogMetricRemoteVersionInfo(
- connection_handle,
- static_cast<uint16_t>(status),
- device.GetLmpVersion().value_or(-1),
- device.GetManufacturerCode().value_or(-1),
- device.GetLmpSubVersion().value_or(-1));
-}
-
-} // namespace hci
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/hci/hci_metrics_logging.h b/gd/hci/hci_metrics_logging.h
deleted file mode 100644
index c1f9c284f..000000000
--- a/gd/hci/hci_metrics_logging.h
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "hci/hci_packets.h"
-#include "storage/storage_module.h"
-
-namespace bluetooth {
-namespace hci {
-void log_hci_event(
- std::unique_ptr<CommandView>& command_view, EventView packet, storage::StorageModule* storage_module);
-void log_link_layer_connection_command_status(std::unique_ptr<CommandView>& command_view, ErrorCode status);
-void log_link_layer_connection_command_complete(EventView event, std::unique_ptr<CommandView>& command_view);
-void log_link_layer_connection_event_le_meta(LeMetaEventView le_meta_event_view);
-void log_link_layer_connection_other_hci_event(EventView packet, storage::StorageModule* storage_module);
-
-void log_classic_pairing_command_status(std::unique_ptr<CommandView>& command_view, ErrorCode status);
-void log_classic_pairing_command_complete(EventView event, std::unique_ptr<CommandView>& command_view);
-void log_classic_pairing_other_hci_event(EventView packet);
-
-void log_remote_device_information(
- const Address& address, uint32_t connection_handle, ErrorCode status, storage::StorageModule* storage_module);
-} // namespace hci
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/hci/hci_packets.pdl b/gd/hci/hci_packets.pdl
index d0efe7a76..1a3db54d5 100644
--- a/gd/hci/hci_packets.pdl
+++ b/gd/hci/hci_packets.pdl
@@ -22,38 +22,10 @@ enum GapDataType : 8 {
COMPLETE_LOCAL_NAME = 0x09,
TX_POWER_LEVEL = 0x0A,
CLASS_OF_DEVICE = 0x0D,
- SIMPLE_PAIRING_HASH_C = 0x0E,
- SIMPLE_PAIRING_RANDOMIZER_R = 0x0F,
- DEVICE_ID = 0x10,
- SECURITY_MANAGER_OOB_FLAGS = 0x11,
- SLAVE_CONNECTION_INTERVAL_RANGE = 0x12,
- LIST_16BIT_SERVICE_SOLICITATION_UUIDS = 0x14,
- LIST_128BIT_SERVICE_SOLICITATION_UUIDS = 0x15,
SERVICE_DATA_16_BIT_UUIDS = 0x16,
- PUBLIC_TARGET_ADDRESS = 0x17,
- RANDOM_TARGET_ADDRESS = 0x18,
APPEARANCE = 0x19,
- ADVERTISING_INTERVAL = 0x1A,
- LE_BLUETOOTH_DEVICE_ADDRESS = 0x1B,
- LE_ROLE = 0x1C,
- SIMPLE_PAIRING_HASH_C_256 = 0x1D,
- SIMPLE_PAIRING_RANDOMIZER_R_256 = 0x1E,
- LIST_32BIT_SERVICE_SOLICITATION_UUIDS = 0x1F,
SERVICE_DATA_32_BIT_UUIDS = 0x20,
SERVICE_DATA_128_BIT_UUIDS = 0x21,
- LE_SECURE_CONNECTIONS_CONFIRMATION_VALUE = 0x22,
- LE_SECURE_CONNECTIONS_RANDOM_VALUE = 0x23,
- URI = 0x24,
- INDOOR_POSITIONING = 0x25,
- TRANSPORT_DISCOVERY_DATA = 0x26,
- LE_SUPPORTED_FEATURES = 0x27,
- CHANNEL_MAP_UPDATE_INDICATION = 0x28,
- MESH_PB_ADV = 0x29,
- MESH_MESSAGE = 0x2A,
- MESH_BEACON = 0x2B,
- BIG_INFO = 0x2C,
- BROADCAST_CODE = 0x2D,
- THREE_D_INFORMATION_DATA = 0x3D,
MANUFACTURER_SPECIFIC_DATA = 0xFF,
}
@@ -73,10 +45,10 @@ enum PacketBoundaryFlag : 2 {
enum BroadcastFlag : 2 {
POINT_TO_POINT = 0,
- ACTIVE_PERIPHERAL_BROADCAST = 1,
+ ACTIVE_SLAVE_BROADCAST = 1,
}
-packet Acl {
+packet AclPacket {
handle : 12,
packet_boundary_flag : PacketBoundaryFlag,
broadcast_flag : BroadcastFlag,
@@ -93,7 +65,7 @@ enum PacketStatusFlag : 2 {
PARTIALLY_LOST = 3,
}
-packet Sco {
+packet ScoPacket {
handle : 12,
packet_status_flag : PacketStatusFlag,
_reserved_ : 2, // BroadcastFlag
@@ -124,7 +96,7 @@ enum OpCode : 16 {
AUTHENTICATION_REQUESTED = 0x0411,
SET_CONNECTION_ENCRYPTION = 0x0413,
CHANGE_CONNECTION_LINK_KEY = 0x0415,
- CENTRAL_LINK_KEY = 0x0417,
+ MASTER_LINK_KEY = 0x0417,
REMOTE_NAME_REQUEST = 0x0419,
REMOTE_NAME_REQUEST_CANCEL = 0x041A,
READ_REMOTE_SUPPORTED_FEATURES = 0x041B,
@@ -145,7 +117,6 @@ enum OpCode : 16 {
IO_CAPABILITY_REQUEST_NEGATIVE_REPLY = 0x0434,
ENHANCED_SETUP_SYNCHRONOUS_CONNECTION = 0x043D,
ENHANCED_ACCEPT_SYNCHRONOUS_CONNECTION = 0x043E,
- REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY = 0x0445,
// LINK_POLICY
HOLD_MODE = 0x0801,
@@ -168,6 +139,7 @@ enum OpCode : 16 {
FLUSH = 0x0C08,
READ_PIN_TYPE = 0x0C09,
WRITE_PIN_TYPE = 0x0C0A,
+ CREATE_NEW_UNIT_KEY = 0x0C0B,
READ_STORED_LINK_KEY = 0x0C0D,
WRITE_STORED_LINK_KEY = 0x0C11,
DELETE_STORED_LINK_KEY = 0x0C12,
@@ -223,20 +195,14 @@ enum OpCode : 16 {
READ_LOCAL_OOB_DATA = 0x0C57,
READ_INQUIRY_RESPONSE_TRANSMIT_POWER_LEVEL = 0x0C58,
WRITE_INQUIRY_TRANSMIT_POWER_LEVEL = 0x0C59,
- ENHANCED_FLUSH = 0x0C5F,
SEND_KEYPRESS_NOTIFICATION = 0x0C60,
- // Allow stacks to disable AMP events
- SET_EVENT_MASK_PAGE_2 = 0x0C63,
-
READ_LE_HOST_SUPPORT = 0x0C6C,
WRITE_LE_HOST_SUPPORT = 0x0C6D,
READ_SECURE_CONNECTIONS_HOST_SUPPORT = 0x0C79,
WRITE_SECURE_CONNECTIONS_HOST_SUPPORT = 0x0C7A,
READ_LOCAL_OOB_EXTENDED_DATA = 0x0C7D,
- SET_ECOSYSTEM_BASE_INTERVAL = 0x0C82,
- CONFIGURE_DATA_PATH = 0x0C83,
// INFORMATIONAL_PARAMETERS
READ_LOCAL_VERSION_INFORMATION = 0x1001,
@@ -246,10 +212,7 @@ enum OpCode : 16 {
READ_BUFFER_SIZE = 0x1005,
READ_BD_ADDR = 0x1009,
READ_DATA_BLOCK_SIZE = 0x100A,
- READ_LOCAL_SUPPORTED_CODECS_V1 = 0x100B,
- READ_LOCAL_SUPPORTED_CODECS_V2 = 0x100D,
- READ_LOCAL_SUPPORTED_CODEC_CAPABILITIES = 0x100E,
- READ_LOCAL_SUPPORTED_CONTROLLER_DELAY = 0x100F,
+ READ_LOCAL_SUPPORTED_CODECS = 0x100B,
// STATUS_PARAMETERS
READ_FAILED_CONTACT_COUNTER = 0x1401,
@@ -269,11 +232,11 @@ enum OpCode : 16 {
// LE_CONTROLLER
LE_SET_EVENT_MASK = 0x2001,
- LE_READ_BUFFER_SIZE_V1 = 0x2002,
+ LE_READ_BUFFER_SIZE = 0x2002,
LE_READ_LOCAL_SUPPORTED_FEATURES = 0x2003,
LE_SET_RANDOM_ADDRESS = 0x2005,
LE_SET_ADVERTISING_PARAMETERS = 0x2006,
- LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER = 0x2007,
+ LE_READ_ADVERTISING_CHANNEL_TX_POWER = 0x2007,
LE_SET_ADVERTISING_DATA = 0x2008,
LE_SET_SCAN_RESPONSE_DATA = 0x2009,
LE_SET_ADVERTISING_ENABLE = 0x200A,
@@ -281,10 +244,10 @@ enum OpCode : 16 {
LE_SET_SCAN_ENABLE = 0x200C,
LE_CREATE_CONNECTION = 0x200D,
LE_CREATE_CONNECTION_CANCEL = 0x200E,
- LE_READ_CONNECT_LIST_SIZE = 0x200F,
- LE_CLEAR_CONNECT_LIST = 0x2010,
- LE_ADD_DEVICE_TO_CONNECT_LIST = 0x2011,
- LE_REMOVE_DEVICE_FROM_CONNECT_LIST = 0x2012,
+ LE_READ_WHITE_LIST_SIZE = 0x200F,
+ LE_CLEAR_WHITE_LIST = 0x2010,
+ LE_ADD_DEVICE_TO_WHITE_LIST = 0x2011,
+ LE_REMOVE_DEVICE_FROM_WHITE_LIST = 0x2012,
LE_CONNECTION_UPDATE = 0x2013,
LE_SET_HOST_CHANNEL_CLASSIFICATION = 0x2014,
LE_READ_CHANNEL_MAP = 0x2015,
@@ -346,41 +309,14 @@ enum OpCode : 16 {
LE_READ_RF_PATH_COMPENSATION_POWER = 0x204C,
LE_WRITE_RF_PATH_COMPENSATION_POWER = 0x204D,
LE_SET_PRIVACY_MODE = 0x204E,
- LE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE = 0x2059,
- LE_PERIODIC_ADVERTISING_SYNC_TRANSFER = 0x205A,
- LE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER = 0x205B,
- LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS = 0x205C,
- LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS = 0x205D,
LE_GENERATE_DHKEY_COMMAND = 0x205E,
- LE_MODIFY_SLEEP_CLOCK_ACCURACY = 0x205F,
- LE_READ_BUFFER_SIZE_V2 = 0x2060,
- LE_READ_ISO_TX_SYNC = 0x2061,
- LE_SET_CIG_PARAMETERS = 0x2062,
- LE_SET_CIG_PARAMETERS_TEST = 0x2063,
- LE_CREATE_CIS = 0x2064,
- LE_REMOVE_CIG = 0x2065,
- LE_ACCEPT_CIS_REQUEST = 0x2066,
- LE_REJECT_CIS_REQUEST = 0x2067,
- LE_CREATE_BIG = 0x2068,
- LE_TERMINATE_BIG = 0x206A,
- LE_BIG_CREATE_SYNC = 0x206B,
- LE_BIG_TERMINATE_SYNC = 0x206C,
- LE_REQUEST_PEER_SCA = 0x206D,
- LE_SETUP_ISO_DATA_PATH = 0x206E,
- LE_REMOVE_ISO_DATA_PATH = 0x206F,
- LE_SET_HOST_FEATURE = 0x2074,
- LE_READ_ISO_LINK_QUALITY = 0x2075,
- LE_ENHANCED_READ_TRANSMIT_POWER_LEVEL = 0x2076,
- LE_READ_REMOTE_TRANSMIT_POWER_LEVEL = 0x2077,
- LE_SET_PATH_LOSS_REPORTING_PARAMETERS = 0x2078,
- LE_SET_PATH_LOSS_REPORTING_ENABLE = 0x2079,
- LE_SET_TRANSMIT_POWER_REPORTING_ENABLE = 0x207A,
// VENDOR_SPECIFIC
LE_GET_VENDOR_CAPABILITIES = 0xFD53,
LE_MULTI_ADVT = 0xFD54,
LE_BATCH_SCAN = 0xFD56,
LE_ADV_FILTER = 0xFD57,
+ LE_TRACK_ADV = 0xFD58,
LE_ENERGY_INFO = 0xFD59,
LE_EXTENDED_SCAN_PARAMS = 0xFD5A,
CONTROLLER_DEBUG_INFO = 0xFD5B,
@@ -408,7 +344,7 @@ enum OpCodeIndex : 16 {
AUTHENTICATION_REQUESTED = 17,
SET_CONNECTION_ENCRYPTION = 20,
CHANGE_CONNECTION_LINK_KEY = 21,
- CENTRAL_LINK_KEY = 22,
+ MASTER_LINK_KEY = 22,
REMOTE_NAME_REQUEST = 23,
REMOTE_NAME_REQUEST_CANCEL = 24,
READ_REMOTE_SUPPORTED_FEATURES = 25,
@@ -513,21 +449,19 @@ enum OpCodeIndex : 16 {
USER_PASSKEY_REQUEST_NEGATIVE_REPLY = 193,
REMOTE_OOB_DATA_REQUEST_REPLY = 194,
WRITE_SIMPLE_PAIRING_DEBUG_MODE = 195,
- ENHANCED_FLUSH = 196,
REMOTE_OOB_DATA_REQUEST_NEGATIVE_REPLY = 197,
SEND_KEYPRESS_NOTIFICATION = 202,
IO_CAPABILITY_REQUEST_NEGATIVE_REPLY = 203,
READ_ENCRYPTION_KEY_SIZE = 204,
- SET_EVENT_MASK_PAGE_2 = 222,
READ_DATA_BLOCK_SIZE = 232,
READ_LE_HOST_SUPPORT = 245,
WRITE_LE_HOST_SUPPORT = 246,
LE_SET_EVENT_MASK = 250,
- LE_READ_BUFFER_SIZE_V1 = 251,
+ LE_READ_BUFFER_SIZE = 251,
LE_READ_LOCAL_SUPPORTED_FEATURES = 252,
LE_SET_RANDOM_ADDRESS = 254,
LE_SET_ADVERTISING_PARAMETERS = 255,
- LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER = 256,
+ LE_READ_ADVERTISING_CHANNEL_TX_POWER = 256,
LE_SET_ADVERTISING_DATA = 257,
LE_SET_SCAN_RESPONSE_DATA = 260,
LE_SET_ADVERTISING_ENABLE = 261,
@@ -535,10 +469,10 @@ enum OpCodeIndex : 16 {
LE_SET_SCAN_ENABLE = 263,
LE_CREATE_CONNECTION = 264,
LE_CREATE_CONNECTION_CANCEL = 265,
- LE_READ_CONNECT_LIST_SIZE = 266,
- LE_CLEAR_CONNECT_LIST = 267,
- LE_ADD_DEVICE_TO_CONNECT_LIST = 270,
- LE_REMOVE_DEVICE_FROM_CONNECT_LIST = 271,
+ LE_READ_WHITE_LIST_SIZE = 266,
+ LE_CLEAR_WHITE_LIST = 267,
+ LE_ADD_DEVICE_TO_WHITE_LIST = 270,
+ LE_REMOVE_DEVICE_FROM_WHITE_LIST = 271,
LE_CONNECTION_UPDATE = 272,
LE_SET_HOST_CHANNEL_CLASSIFICATION = 273,
LE_READ_CHANNEL_MAP = 274,
@@ -554,8 +488,7 @@ enum OpCodeIndex : 16 {
LE_TEST_END = 286,
ENHANCED_SETUP_SYNCHRONOUS_CONNECTION = 293,
ENHANCED_ACCEPT_SYNCHRONOUS_CONNECTION = 294,
- READ_LOCAL_SUPPORTED_CODECS_V1 = 295,
- REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY = 321,
+ READ_LOCAL_SUPPORTED_CODECS = 295,
READ_SECURE_CONNECTIONS_HOST_SUPPORT = 322,
WRITE_SECURE_CONNECTIONS_HOST_SUPPORT = 323,
READ_LOCAL_OOB_EXTENDED_DATA = 326,
@@ -607,44 +540,10 @@ enum OpCodeIndex : 16 {
LE_READ_RF_PATH_COMPENSATION_POWER = 390,
LE_WRITE_RF_PATH_COMPENSATION_POWER = 391,
LE_SET_PRIVACY_MODE = 392,
-
- LE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE = 405,
- LE_PERIODIC_ADVERTISING_SYNC_TRANSFER = 406,
- LE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER = 407,
- LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS = 410,
- LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS = 411,
LE_GENERATE_DHKEY_COMMAND = 412,
- LE_MODIFY_SLEEP_CLOCK_ACCURACY = 414,
- LE_READ_BUFFER_SIZE_V2 = 415,
- LE_READ_ISO_TX_SYNC = 416,
- LE_SET_CIG_PARAMETERS = 417,
- LE_SET_CIG_PARAMETERS_TEST = 418,
- LE_CREATE_CIS = 421,
- LE_REMOVE_CIG = 422,
- LE_ACCEPT_CIS_REQUEST = 423,
- LE_REJECT_CIS_REQUEST = 424,
- LE_CREATE_BIG = 425,
- LE_TERMINATE_BIG = 427,
- LE_BIG_CREATE_SYNC = 430,
- LE_BIG_TERMINATE_SYNC = 431,
- LE_REQUEST_PEER_SCA = 432,
- LE_SETUP_ISO_DATA_PATH = 433,
- LE_REMOVE_ISO_DATA_PATH = 434,
- LE_SET_HOST_FEATURE = 441,
- LE_READ_ISO_LINK_QUALITY = 442,
- LE_ENHANCED_READ_TRANSMIT_POWER_LEVEL = 443,
- LE_READ_REMOTE_TRANSMIT_POWER_LEVEL = 444,
- LE_SET_PATH_LOSS_REPORTING_PARAMETERS = 445,
- LE_SET_PATH_LOSS_REPORTING_ENABLE = 446,
- LE_SET_TRANSMIT_POWER_REPORTING_ENABLE = 447,
- SET_ECOSYSTEM_BASE_INTERVAL = 451,
- READ_LOCAL_SUPPORTED_CODECS_V2 = 452,
- READ_LOCAL_SUPPORTED_CODEC_CAPABILITIES = 453,
- READ_LOCAL_SUPPORTED_CONTROLLER_DELAY = 454,
- CONFIGURE_DATA_PATH = 455,
-}
-
-packet Command {
+}
+
+packet CommandPacket {
op_code : OpCode,
_size_(_payload_) : 8,
_payload_,
@@ -652,17 +551,15 @@ packet Command {
// Packets for interfaces
-packet DiscoveryCommand : Command { _payload_, }
-packet AclCommand : Command { _payload_, }
-packet ConnectionManagementCommand : AclCommand { _payload_, }
-packet SecurityCommand : Command { _payload_, }
-packet ScoConnectionCommand : AclCommand { _payload_, }
-packet LeAdvertisingCommand : Command { _payload_, }
-packet LeScanningCommand : Command { _payload_, }
-packet LeConnectionManagementCommand : AclCommand { _payload_, }
-packet LeSecurityCommand : Command { _payload_, }
-packet LeIsoCommand : Command { _payload_, }
-packet VendorCommand : Command { _payload_, }
+packet DiscoveryCommand : CommandPacket { _payload_, }
+packet ConnectionManagementCommand : CommandPacket { _payload_, }
+packet SecurityCommand : CommandPacket { _payload_, }
+packet ScoConnectionCommand : CommandPacket { _payload_, }
+packet LeAdvertisingCommand : CommandPacket { _payload_, }
+packet LeScanningCommand : CommandPacket { _payload_, }
+packet LeConnectionManagementCommand : CommandPacket { _payload_, }
+packet LeSecurityCommand : CommandPacket { _payload_, }
+packet VendorCommand : CommandPacket { _payload_, }
// HCI Event Packets
@@ -676,7 +573,7 @@ enum EventCode : 8 {
REMOTE_NAME_REQUEST_COMPLETE = 0x07,
ENCRYPTION_CHANGE = 0x08,
CHANGE_CONNECTION_LINK_KEY_COMPLETE = 0x09,
- CENTRAL_LINK_KEY_COMPLETE = 0x0A,
+ MASTER_LINK_KEY_COMPLETE = 0x0A,
READ_REMOTE_SUPPORTED_FEATURES_COMPLETE = 0x0B,
READ_REMOTE_VERSION_INFORMATION_COMPLETE = 0x0C,
QOS_SETUP_COMPLETE = 0x0D,
@@ -722,7 +619,7 @@ enum EventCode : 8 {
VENDOR_SPECIFIC = 0xFF,
}
-packet Event {
+packet EventPacket {
event_code : EventCode,
_size_(_payload_) : 8,
_payload_,
@@ -750,21 +647,6 @@ enum SubeventCode : 8 {
SCAN_TIMEOUT = 0x11,
ADVERTISING_SET_TERMINATED = 0x12,
SCAN_REQUEST_RECEIVED = 0x13,
- CHANNEL_SELECTION_ALGORITHM = 0x14,
- CONNECTIONLESS_IQ_REPORT = 0x15,
- CONNECTION_IQ_REPORT = 0x16,
- CTE_REQUEST_FAILED = 0x17,
- PERIODIC_ADVERTISING_SYNC_TRANSFER_RECEIVED = 0x18,
- CIS_ESTABLISHED = 0x19,
- CIS_REQUEST = 0x1A,
- CREATE_BIG_COMPLETE = 0x1B,
- TERMINATE_BIG_COMPLETE = 0x1C,
- BIG_SYNC_ESTABLISHED = 0x1D,
- BIG_SYNC_LOST = 0x1E,
- REQUEST_PEER_SCA_COMPLETE = 0x1F,
- PATH_LOSS_THRESHOLD = 0x20,
- TRANSMIT_POWER_REPORTING = 0x21,
- BIG_INFO_ADVERTISING_REPORT = 0x22,
}
// Vendor specific events
@@ -783,7 +665,6 @@ enum FeatureFlag : 1 {
}
enum ErrorCode: 8 {
- STATUS_UNKNOWN = 0xFF,
SUCCESS = 0x00,
UNKNOWN_HCI_COMMAND = 0x01,
UNKNOWN_CONNECTION = 0x02,
@@ -820,20 +701,18 @@ enum ErrorCode: 8 {
ROLE_CHANGE_NOT_ALLOWED = 0x21,
LINK_LAYER_COLLISION = 0x23,
ENCRYPTION_MODE_NOT_ACCEPTABLE = 0x25,
- ROLE_SWITCH_FAILED = 0x35,
CONTROLLER_BUSY = 0x3A,
- CONNECTION_FAILED_ESTABLISHMENT = 0x3E,
}
// Events that are defined with their respective commands
-packet CommandComplete : Event (event_code = COMMAND_COMPLETE) {
+packet CommandComplete : EventPacket (event_code = COMMAND_COMPLETE){
num_hci_command_packets : 8,
command_op_code : OpCode,
_payload_,
}
-packet CommandStatus : Event (event_code = COMMAND_STATUS) {
+packet CommandStatus : EventPacket (event_code = COMMAND_STATUS){
status : ErrorCode, // SUCCESS means PENDING
num_hci_command_packets : 8,
command_op_code : OpCode,
@@ -841,7 +720,7 @@ packet CommandStatus : Event (event_code = COMMAND_STATUS) {
}
// Credits
-packet NoCommandComplete : CommandComplete (command_op_code = NONE) {
+packet NoCommandComplete : CommandComplete (command_op_code = NONE){
}
struct Lap { // Lower Address Part
@@ -857,32 +736,16 @@ packet Inquiry : DiscoveryCommand (op_code = INQUIRY) {
num_responses : 8, // 0x00 unlimited
}
-test Inquiry {
- "\x01\x04\x05\x33\x8b\x9e\xaa\xbb",
-}
-
packet InquiryStatus : CommandStatus (command_op_code = INQUIRY) {
}
-test InquiryStatus {
- "\x0f\x04\x00\x01\x01\x04",
-}
-
packet InquiryCancel : DiscoveryCommand (op_code = INQUIRY_CANCEL) {
}
-test InquiryCancel {
- "\x02\x04\x00",
-}
-
packet InquiryCancelComplete : CommandComplete (command_op_code = INQUIRY_CANCEL) {
status : ErrorCode,
}
-test InquiryCancelComplete {
- "\x0e\x04\x01\x02\x04\x00",
-}
-
packet PeriodicInquiryMode : DiscoveryCommand (op_code = PERIODIC_INQUIRY_MODE) {
max_period_length : 16, // Range 0x0003 to 0xffff (times 1.28s)
min_period_length : 16, // Range 0x0002 to 0xfffe (times 1.28s)
@@ -891,33 +754,17 @@ packet PeriodicInquiryMode : DiscoveryCommand (op_code = PERIODIC_INQUIRY_MODE)
num_responses : 8, // 0x00 unlimited
}
-test PeriodicInquiryMode {
- "\x03\x04\x09\x12\x34\x56\x78\x11\x8b\x9e\x9a\xbc",
-}
-
packet PeriodicInquiryModeComplete : CommandComplete (command_op_code = PERIODIC_INQUIRY_MODE) {
status : ErrorCode,
}
-test PeriodicInquiryModeComplete {
- "\x0e\x04\x01\x03\x04\x00",
-}
-
packet ExitPeriodicInquiryMode : DiscoveryCommand (op_code = EXIT_PERIODIC_INQUIRY_MODE) {
}
-test ExitPeriodicInquiryMode {
- "\x04\x04\x00",
-}
-
packet ExitPeriodicInquiryModeComplete : CommandComplete (command_op_code = EXIT_PERIODIC_INQUIRY_MODE) {
status : ErrorCode,
}
-test ExitPeriodicInquiryModeComplete {
- "\x0e\x04\x01\x04\x04\x00",
-}
-
enum PageScanRepetitionMode : 8 {
R0 = 0x00,
R1 = 0x01,
@@ -930,7 +777,7 @@ enum ClockOffsetValid : 1 {
}
enum CreateConnectionRoleSwitch : 8 {
- REMAIN_CENTRAL = 0x00,
+ REMAIN_MASTER = 0x00,
ALLOW_ROLE_SWITCH = 0x01,
}
@@ -957,7 +804,7 @@ enum DisconnectReason : 8 {
UNACCEPTABLE_CONNECTION_PARAMETERS = 0x3B,
}
-packet Disconnect : AclCommand (op_code = DISCONNECT) {
+packet Disconnect : ConnectionManagementCommand (op_code = DISCONNECT) {
connection_handle : 12,
_reserved_ : 4,
reason : DisconnectReason,
@@ -976,8 +823,8 @@ packet CreateConnectionCancelComplete : CommandComplete (command_op_code = CREAT
}
enum AcceptConnectionRequestRole : 8 {
- BECOME_CENTRAL = 0x00,
- REMAIN_PERIPHERAL = 0x01,
+ BECOME_MASTER = 0x00,
+ REMAIN_SLAVE = 0x01,
}
packet AcceptConnectionRequest : ConnectionManagementCommand (op_code = ACCEPT_CONNECTION_REQUEST) {
@@ -1080,11 +927,11 @@ enum KeyFlag : 8 {
TEMPORARY = 0x01,
}
-packet CentralLinkKey : ConnectionManagementCommand (op_code = CENTRAL_LINK_KEY) {
+packet MasterLinkKey : ConnectionManagementCommand (op_code = MASTER_LINK_KEY) {
key_flag : KeyFlag,
}
-packet CentralLinkKeyStatus : CommandStatus (command_op_code = CENTRAL_LINK_KEY) {
+packet MasterLinkKeyStatus : CommandStatus (command_op_code = MASTER_LINK_KEY) {
}
packet RemoteNameRequest : DiscoveryCommand (op_code = REMOTE_NAME_REQUEST) {
@@ -1107,7 +954,7 @@ packet RemoteNameRequestCancelComplete : CommandComplete (command_op_code = REMO
bd_addr : Address,
}
-packet ReadRemoteSupportedFeatures : ConnectionManagementCommand (op_code = READ_REMOTE_SUPPORTED_FEATURES) {
+packet ReadRemoteSupportedFeatures : DiscoveryCommand (op_code = READ_REMOTE_SUPPORTED_FEATURES) {
connection_handle : 12,
_reserved_ : 4,
}
@@ -1115,7 +962,7 @@ packet ReadRemoteSupportedFeatures : ConnectionManagementCommand (op_code = READ
packet ReadRemoteSupportedFeaturesStatus : CommandStatus (command_op_code = READ_REMOTE_SUPPORTED_FEATURES) {
}
-packet ReadRemoteExtendedFeatures : ConnectionManagementCommand (op_code = READ_REMOTE_EXTENDED_FEATURES) {
+packet ReadRemoteExtendedFeatures : DiscoveryCommand (op_code = READ_REMOTE_EXTENDED_FEATURES) {
connection_handle : 12,
_reserved_ : 4,
page_number : 8,
@@ -1124,7 +971,7 @@ packet ReadRemoteExtendedFeatures : ConnectionManagementCommand (op_code = READ_
packet ReadRemoteExtendedFeaturesStatus : CommandStatus (command_op_code = READ_REMOTE_EXTENDED_FEATURES) {
}
-packet ReadRemoteVersionInformation : AclCommand (op_code = READ_REMOTE_VERSION_INFORMATION) {
+packet ReadRemoteVersionInformation : DiscoveryCommand (op_code = READ_REMOTE_VERSION_INFORMATION) {
connection_handle : 12,
_reserved_ : 4,
}
@@ -1154,40 +1001,15 @@ packet ReadLmpHandleComplete : CommandComplete (command_op_code = READ_LMP_HANDL
}
packet SetupSynchronousConnection : ScoConnectionCommand (op_code = SETUP_SYNCHRONOUS_CONNECTION) {
- connection_handle : 12,
- _reserved_ : 4,
- transmit_bandwidth : 32,
- receive_bandwidth : 32,
- max_latency : 16, // 0-3 reserved, 0xFFFF = don't care
- voice_setting : 10,
- _reserved_ : 6,
- retransmission_effort : 8,
- packet_type : 16,
-}
-
-packet SetupSynchronousConnectionStatus : CommandStatus (command_op_code = SETUP_SYNCHRONOUS_CONNECTION) {
+ _payload_, // placeholder (unimplemented)
}
packet AcceptSynchronousConnection : ScoConnectionCommand (op_code = ACCEPT_SYNCHRONOUS_CONNECTION) {
- bd_addr : Address,
- transmit_bandwidth : 32,
- receive_bandwidth : 32,
- max_latency : 16, // 0-3 reserved, 0xFFFF = don't care
- voice_setting : 10,
- _reserved_ : 6,
- retransmission_effort : 8,
- packet_type : 16,
-}
-
-packet AcceptSynchronousConnectionStatus : CommandStatus (command_op_code = ACCEPT_SYNCHRONOUS_CONNECTION) {
+ _payload_, // placeholder (unimplemented)
}
packet RejectSynchronousConnection : ScoConnectionCommand (op_code = REJECT_SYNCHRONOUS_CONNECTION) {
- bd_addr : Address,
- reason : RejectConnectionReason,
-}
-
-packet RejectSynchronousConnectionStatus : CommandStatus (command_op_code = REJECT_SYNCHRONOUS_CONNECTION) {
+ _payload_, // placeholder (unimplemented)
}
enum IoCapability : 8 {
@@ -1292,177 +1114,12 @@ packet IoCapabilityRequestNegativeReplyComplete : CommandComplete (command_op_co
bd_addr : Address,
}
-enum ScoCodingFormatValues : 8 {
- ULAW_LONG = 0x00,
- ALAW_LONG = 0x01,
- CVSD = 0x02,
- TRANSPARENT = 0x03,
- LINEAR_PCM = 0x04,
- MSBC = 0x05,
- LC3 = 0x06,
- VENDOR_SPECIFIC = 0xFF,
-}
-
-struct ScoCodingFormat {
- coding_format : ScoCodingFormatValues,
- company_id : 16,
- vendor_specific_codec_id : 16,
-}
-
-enum ScoPcmDataFormat : 8 {
- NOT_USED = 0x00,
- ONES_COMPLEMENT = 0x01,
- TWOS_COMPLEMENT = 0x02,
- SIGN_MAGNITUDE = 0x03,
- UNSIGNED = 0x04,
-}
-
-enum ScoDataPath : 8 {
- HCI = 0x00,
- // 0x01 to 0xFE are Logical_Channel_Number.
- // The meaning of the logical channels will be vendor specific.
- // In GD and legacy Android Bluetooth stack, we use channel 0x01 for hardware
- // offloaded SCO encoding
- GD_PCM = 0x01,
- AUDIO_TEST_MODE = 0xFF,
-}
-
-enum SynchronousPacketTypeBits : 16 {
- HV1_ALLOWED = 0x0000,
- HV2_ALLOWED = 0x0001,
- HV3_ALLOWED = 0x0002,
- EV3_ALLOWED = 0x0004,
- EV4_ALLOWED = 0x0008,
- EV5_ALLOWED = 0x0010,
- NO_2_EV3_ALLOWED = 0x0020,
- NO_3_EV3_ALLOWED = 0x0040,
- NO_2_EV5_ALLOWED = 0x0080,
- NO_3_EV5_ALLOWED = 0x0100,
-}
-
-enum RetransmissionEffort : 8 {
- NO_RETRANSMISSION = 0x00,
- OPTIMIZED_FOR_POWER = 0x01,
- OPTIMIZED_FOR_LINK_QUALITY = 0x02,
- DO_NOT_CARE = 0xFF,
-}
-
packet EnhancedSetupSynchronousConnection : ScoConnectionCommand (op_code = ENHANCED_SETUP_SYNCHRONOUS_CONNECTION) {
- connection_handle: 12,
- _reserved_ : 4,
- // Next two items
- // [0x00000000, 0xFFFFFFFE] Bandwidth in octets per second.
- // [0xFFFFFFFF]: Don't care
- transmit_bandwidth_octets_per_second : 32,
- receive_bandwidth_octets_per_second : 32,
- transmit_coding_format : ScoCodingFormat,
- receive_coding_format : ScoCodingFormat,
- // Next two items
- // [0x0001, 0xFFFF]: the actual size of the over-the-air encoded frame in
- // octets.
- transmit_codec_frame_size : 16,
- receive_codec_frame_size : 16,
- // Next two items
- // Host to Controller nominal data rate in octets per second.
- input_bandwidth_octets_per_second : 32,
- output_bandwidth_octets_per_second : 32,
- input_coding_format : ScoCodingFormat,
- output_coding_format : ScoCodingFormat,
- // Next two items
- // Size, in bits, of the sample or framed data
- input_coded_data_bits : 16,
- output_coded_data_bits : 16,
- input_pcm_data_format : ScoPcmDataFormat,
- output_pcm_data_format : ScoPcmDataFormat,
- // Next two items
- // The number of bit positions within an audio sample that the MSB of the
- // sample is away from starting at the MSB of the data.
- input_pcm_sample_payload_msb_position : 8,
- output_pcm_sample_payload_msb_position : 8,
- input_data_path : ScoDataPath,
- output_data_path : ScoDataPath,
- // Next two items
- // [1, 255] The number of bits in each unit of data received from the Host
- // over the audio data transport.
- // [0] Not applicable (implied by the choice of audio data transport)
- input_transport_unit_bits : 8,
- output_transport_unit_bits : 8,
- // [0x0004, 0xFFFE]: in milliseconds
- // Upper limit represent the sum of the synchronous interval and the size
- // of the eSCO window, where the eSCO window is reserved slots plus the
- // retransmission window
- // [0xFFFF]: don't care
- max_latency_ms: 16,
- packet_type : 16, // Or together SynchronousPacketTypeBits
- retransmission_effort : RetransmissionEffort,
-}
-
-packet EnhancedSetupSynchronousConnectionStatus : CommandStatus (command_op_code = ENHANCED_SETUP_SYNCHRONOUS_CONNECTION) {
+ _payload_, // placeholder (unimplemented)
}
packet EnhancedAcceptSynchronousConnection : ScoConnectionCommand (op_code = ENHANCED_ACCEPT_SYNCHRONOUS_CONNECTION) {
- bd_addr : Address,
- // Next two items
- // [0x00000000, 0xFFFFFFFE] Bandwidth in octets per second.
- // [0xFFFFFFFF]: Don't care
- transmit_bandwidth : 32,
- receive_bandwidth : 32,
- transmit_coding_format : ScoCodingFormat,
- receive_coding_format : ScoCodingFormat,
- // Next two items
- // [0x0001, 0xFFFF]: the actual size of the over-the-air encoded frame in
- // octets.
- transmit_codec_frame_size : 16,
- receive_codec_frame_size : 16,
- // Next two items
- // Host to Controller nominal data rate in octets per second.
- input_bandwidth : 32,
- output_bandwidth : 32,
- input_coding_format : ScoCodingFormat,
- output_coding_format : ScoCodingFormat,
- // Next two items
- // Size, in bits, of the sample or framed data
- input_coded_data_bits : 16,
- output_coded_data_bits : 16,
- input_pcm_data_format : ScoPcmDataFormat,
- output_pcm_data_format : ScoPcmDataFormat,
- // Next two items
- // The number of bit positions within an audio sample that the MSB of the
- // sample is away from starting at the MSB of the data.
- input_pcm_sample_payload_msb_position : 8,
- output_pcm_sample_payload_msb_position : 8,
- input_data_path : ScoDataPath,
- output_data_path : ScoDataPath,
- // Next two items
- // [1, 255] The number of bits in each unit of data received from the Host
- // over the audio data transport.
- // [0] Not applicable (implied by the choice of audio data transport)
- input_transport_unit_bits : 8,
- output_transport_unit_bits : 8,
- // [0x0004, 0xFFFE]: in milliseconds
- // Upper limit represent the sum of the synchronous interval and the size
- // of the eSCO window, where the eSCO window is reserved slots plus the
- // retransmission window
- // [0xFFFF]: don't care
- max_latency : 16,
- packet_type : 16, // Or together SynchronousPacketTypeBits
- retransmission_effort : RetransmissionEffort,
-}
-
-packet EnhancedAcceptSynchronousConnectionStatus : CommandStatus (command_op_code = ENHANCED_ACCEPT_SYNCHRONOUS_CONNECTION) {
-}
-
-packet RemoteOobExtendedDataRequestReply : SecurityCommand (op_code = REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY) {
- bd_addr : Address,
- c_192 : 8[16],
- r_192 : 8[16],
- c_256 : 8[16],
- r_256 : 8[16],
-}
-
-packet RemoteOobExtendedDataRequestReplyComplete : CommandComplete (command_op_code = REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY) {
- status : ErrorCode,
- bd_addr : Address,
+ _payload_, // placeholder (unimplemented)
}
@@ -1525,8 +1182,8 @@ packet RoleDiscovery : ConnectionManagementCommand (op_code = ROLE_DISCOVERY) {
}
enum Role : 8 {
- CENTRAL = 0x00,
- PERIPHERAL = 0x01,
+ MASTER = 0x00,
+ SLAVE = 0x01,
}
packet RoleDiscoveryComplete : CommandComplete (command_op_code = ROLE_DISCOVERY) {
@@ -1627,7 +1284,7 @@ packet SniffSubratingComplete : CommandComplete (command_op_code = SNIFF_SUBRATI
}
// CONTROLLER_AND_BASEBAND
-packet SetEventMask : Command (op_code = SET_EVENT_MASK) {
+packet SetEventMask : CommandPacket (op_code = SET_EVENT_MASK) {
event_mask : 64,
}
@@ -1635,29 +1292,20 @@ packet SetEventMaskComplete : CommandComplete (command_op_code = SET_EVENT_MASK)
status : ErrorCode,
}
-packet Reset : Command (op_code = RESET) {
-}
-
-test Reset {
- "\x03\x0c\x00",
+packet Reset : CommandPacket (op_code = RESET) {
}
packet ResetComplete : CommandComplete (command_op_code = RESET) {
status : ErrorCode,
}
-test ResetComplete {
- "\x0e\x04\x01\x03\x0c\x00",
- "\x0e\x04\x01\x03\x0c\x01", // unknown command
-}
-
enum FilterType : 8 {
CLEAR_ALL_FILTERS = 0x00,
INQUIRY_RESULT = 0x01,
CONNECTION_SETUP = 0x02,
}
-packet SetEventFilter : Command (op_code = SET_EVENT_FILTER) {
+packet SetEventFilter : CommandPacket (op_code = SET_EVENT_FILTER) {
filter_type : FilterType,
_body_,
}
@@ -1734,7 +1382,7 @@ enum PinType : 8 {
FIXED = 1,
}
-packet ReadPinType : Command (op_code = READ_PIN_TYPE) {
+packet ReadPinType : CommandPacket (op_code = READ_PIN_TYPE) {
}
packet ReadPinTypeComplete : CommandComplete (command_op_code = READ_PIN_TYPE) {
@@ -1742,7 +1390,7 @@ packet ReadPinTypeComplete : CommandComplete (command_op_code = READ_PIN_TYPE) {
pin_type : PinType,
}
-packet WritePinType : Command (op_code = WRITE_PIN_TYPE) {
+packet WritePinType : CommandPacket (op_code = WRITE_PIN_TYPE) {
pin_type : PinType,
}
@@ -1750,6 +1398,10 @@ packet WritePinTypeComplete : CommandComplete (command_op_code = WRITE_PIN_TYPE)
status : ErrorCode,
}
+packet CreateNewUnitKey : CommandPacket (op_code = CREATE_NEW_UNIT_KEY) {
+ _payload_, // placeholder (unimplemented)
+}
+
enum ReadStoredLinkKeyReadAllFlag : 8 {
SPECIFIED_BD_ADDR = 0x00,
ALL = 0x01,
@@ -1796,7 +1448,7 @@ packet DeleteStoredLinkKeyComplete : CommandComplete (command_op_code = DELETE_S
num_keys_deleted : 16,
}
-packet WriteLocalName : Command (op_code = WRITE_LOCAL_NAME) {
+packet WriteLocalName : CommandPacket (op_code = WRITE_LOCAL_NAME) {
local_name : 8[248], // Null-terminated UTF-8 encoded name
}
@@ -1804,7 +1456,7 @@ packet WriteLocalNameComplete : CommandComplete (command_op_code = WRITE_LOCAL_N
status : ErrorCode,
}
-packet ReadLocalName : Command (op_code = READ_LOCAL_NAME) {
+packet ReadLocalName : CommandPacket (op_code = READ_LOCAL_NAME) {
}
packet ReadLocalNameComplete : CommandComplete (command_op_code = READ_LOCAL_NAME) {
@@ -1831,35 +1483,19 @@ packet WriteConnectionAcceptTimeoutComplete : CommandComplete (command_op_code =
packet ReadPageTimeout : DiscoveryCommand (op_code = READ_PAGE_TIMEOUT) {
}
-test ReadPageTimeout {
- "\x17\x0c\x00",
-}
-
packet ReadPageTimeoutComplete : CommandComplete (command_op_code = READ_PAGE_TIMEOUT) {
status : ErrorCode,
page_timeout : 16,
}
-test ReadPageTimeoutComplete {
- "\x0e\x06\x01\x17\x0c\x00\x11\x22",
-}
-
packet WritePageTimeout : DiscoveryCommand (op_code = WRITE_PAGE_TIMEOUT) {
page_timeout : 16,
}
-test WritePageTimeout {
- "\x18\x0c\x02\x00\x20",
-}
-
packet WritePageTimeoutComplete : CommandComplete (command_op_code = WRITE_PAGE_TIMEOUT) {
status : ErrorCode,
}
-test WritePageTimeoutComplete {
- "\x0e\x04\x01\x18\x0c\x00",
-}
-
enum ScanEnable : 8 {
NO_SCANS = 0x00,
INQUIRY_SCAN_ONLY = 0x01,
@@ -1904,43 +1540,27 @@ packet WritePageScanActivityComplete : CommandComplete (command_op_code = WRITE_
packet ReadInquiryScanActivity : DiscoveryCommand (op_code = READ_INQUIRY_SCAN_ACTIVITY) {
}
-test ReadInquiryScanActivity {
- "\x1d\x0c\x00",
-}
-
packet ReadInquiryScanActivityComplete : CommandComplete (command_op_code = READ_INQUIRY_SCAN_ACTIVITY) {
status : ErrorCode,
inquiry_scan_interval : 16, // Range: 0x0012 to 0x1000; only even values are valid * 0x625 ms
inquiry_scan_window : 16, // Range: 0x0011 to 0x1000
}
-test ReadInquiryScanActivityComplete {
- "\x0e\x08\x01\x1d\x0c\x00\xaa\xbb\xcc\xdd",
-}
-
packet WriteInquiryScanActivity : DiscoveryCommand (op_code = WRITE_INQUIRY_SCAN_ACTIVITY) {
inquiry_scan_interval : 16, // Range: 0x0012 to 0x1000; only even values are valid * 0x625 ms
inquiry_scan_window : 16, // Range: 0x0011 to 0x1000
}
-test WriteInquiryScanActivity {
- "\x1e\x0c\x04\x00\x08\x12\x00",
-}
-
packet WriteInquiryScanActivityComplete : CommandComplete (command_op_code = WRITE_INQUIRY_SCAN_ACTIVITY) {
status : ErrorCode,
}
-test WriteInquiryScanActivityComplete {
- "\x0e\x04\x01\x1e\x0c\x00",
-}
-
enum AuthenticationEnable : 8 {
NOT_REQUIRED = 0x00,
REQUIRED = 0x01,
}
-packet ReadAuthenticationEnable : Command (op_code = READ_AUTHENTICATION_ENABLE) {
+packet ReadAuthenticationEnable : CommandPacket (op_code = READ_AUTHENTICATION_ENABLE) {
}
packet ReadAuthenticationEnableComplete : CommandComplete (command_op_code = READ_AUTHENTICATION_ENABLE) {
@@ -1972,18 +1592,12 @@ packet WriteClassOfDeviceComplete : CommandComplete (command_op_code = WRITE_CLA
status : ErrorCode,
}
-packet ReadVoiceSetting : Command (op_code = READ_VOICE_SETTING) {
-}
-
-packet ReadVoiceSettingComplete : CommandComplete (command_op_code = READ_VOICE_SETTING) {
- status : ErrorCode,
- voice_setting : 10,
- _reserved_ : 6,
+packet ReadVoiceSetting : CommandPacket (op_code = READ_VOICE_SETTING) {
+ _payload_, // placeholder (unimplemented)
}
-packet WriteVoiceSetting : Command (op_code = WRITE_VOICE_SETTING) {
- voice_setting : 10,
- _reserved_ : 6,
+packet WriteVoiceSetting : CommandPacket (op_code = WRITE_VOICE_SETTING) {
+ _payload_, // placeholder (unimplemented)
}
packet WriteVoiceSettingComplete : CommandComplete (command_op_code = WRITE_VOICE_SETTING) {
@@ -2014,44 +1628,22 @@ packet WriteAutomaticFlushTimeoutComplete : CommandComplete (command_op_code = W
_reserved_ : 4,
}
-packet ReadNumBroadcastRetransmits : Command (op_code = READ_NUM_BROADCAST_RETRANSMITS) {
-}
-
-packet ReadNumBroadcastRetransmitsComplete : CommandComplete (command_op_code = READ_NUM_BROADCAST_RETRANSMITS) {
- status : ErrorCode,
- num_broadcast_retransmissions : 8,
-}
-
-packet WriteNumBroadcastRetransmits : Command (op_code = WRITE_NUM_BROADCAST_RETRANSMITS) {
- num_broadcast_retransmissions : 8,
-}
-
-packet WriteNumBroadcastRetransmitsComplete : CommandComplete (command_op_code = WRITE_NUM_BROADCAST_RETRANSMITS) {
- status : ErrorCode,
-}
-
-enum HoldModeActivity : 8 {
- MAINTAIN_CURRENT_POWER_STATE = 0x00,
- SUSPEND_PAGE_SCAN = 0x01,
- SUSPEND_INQUIRY_SCAN = 0x02,
- SUSPEND_PERIODIC_INQUIRY = 0x03,
+packet ReadNumBroadcastRetransmits : CommandPacket (op_code = READ_NUM_BROADCAST_RETRANSMITS) {
+ _payload_, // placeholder (unimplemented)
}
-packet ReadHoldModeActivity : Command (op_code = READ_HOLD_MODE_ACTIVITY) {
+packet WriteNumBroadcastRetransmits : CommandPacket (op_code = WRITE_NUM_BROADCAST_RETRANSMITS) {
+ _payload_, // placeholder (unimplemented)
}
-packet ReadHoldModeActivityComplete : CommandComplete (command_op_code = READ_HOLD_MODE_ACTIVITY) {
- status : ErrorCode,
- hold_mode_activity : HoldModeActivity,
+packet ReadHoldModeActivity : CommandPacket (op_code = READ_HOLD_MODE_ACTIVITY) {
+ _payload_, // placeholder (unimplemented)
}
-packet WriteHoldModeActivity : Command (op_code = WRITE_HOLD_MODE_ACTIVITY) {
- hold_mode_activity : HoldModeActivity,
+packet WriteHoldModeActivity : CommandPacket (op_code = WRITE_HOLD_MODE_ACTIVITY) {
+ _payload_, // placeholder (unimplemented)
}
-packet WriteHoldModeActivityComplete : CommandComplete (command_op_code = WRITE_HOLD_MODE_ACTIVITY) {
- status : ErrorCode,
-}
enum TransmitPowerLevelType : 8 {
CURRENT = 0x00,
@@ -2061,7 +1653,7 @@ enum TransmitPowerLevelType : 8 {
packet ReadTransmitPowerLevel : ConnectionManagementCommand (op_code = READ_TRANSMIT_POWER_LEVEL) {
connection_handle : 12,
_reserved_ : 4,
- transmit_power_level_type : TransmitPowerLevelType,
+ type : TransmitPowerLevelType,
}
@@ -2072,58 +1664,36 @@ packet ReadTransmitPowerLevelComplete : CommandComplete (command_op_code = READ_
transmit_power_level : 8,
}
-packet ReadSynchronousFlowControlEnable : Command (op_code = READ_SYNCHRONOUS_FLOW_CONTROL_ENABLE) {
-}
-
-packet ReadSynchronousFlowControlEnableComplete : CommandComplete (command_op_code = READ_SYNCHRONOUS_FLOW_CONTROL_ENABLE) {
- status : ErrorCode,
- enable : Enable,
-}
-
-packet WriteSynchronousFlowControlEnable : Command (op_code = WRITE_SYNCHRONOUS_FLOW_CONTROL_ENABLE) {
- enable : Enable,
-}
-
-packet WriteSynchronousFlowControlEnableComplete : CommandComplete (command_op_code = WRITE_SYNCHRONOUS_FLOW_CONTROL_ENABLE) {
- status : ErrorCode,
+packet ReadSynchronousFlowControlEnable : CommandPacket (op_code = READ_SYNCHRONOUS_FLOW_CONTROL_ENABLE) {
+ _payload_, // placeholder (unimplemented)
}
-packet SetControllerToHostFlowControl : Command (op_code = SET_CONTROLLER_TO_HOST_FLOW_CONTROL) {
- acl : 1,
- synchronous : 1,
- _reserved_ : 6,
+packet WriteSynchronousFlowControlEnable : CommandPacket (op_code = WRITE_SYNCHRONOUS_FLOW_CONTROL_ENABLE) {
+ _payload_, // placeholder (unimplemented)
}
-packet SetControllerToHostFlowControlComplete : CommandComplete (command_op_code = SET_CONTROLLER_TO_HOST_FLOW_CONTROL) {
- status : ErrorCode,
+packet SetControllerToHostFlowControl : CommandPacket (op_code = SET_CONTROLLER_TO_HOST_FLOW_CONTROL) {
+ _payload_, // placeholder (unimplemented)
}
-packet HostBufferSize : Command (op_code = HOST_BUFFER_SIZE) {
+packet HostBufferSize : CommandPacket (op_code = HOST_BUFFER_SIZE) {
host_acl_data_packet_length : 16,
host_synchronous_data_packet_length : 8,
host_total_num_acl_data_packets : 16,
host_total_num_synchronous_data_packets : 16,
}
-test HostBufferSize {
- "\x33\x0c\x07\x9b\x06\xff\x14\x00\x0a\x00",
-}
-
packet HostBufferSizeComplete : CommandComplete (command_op_code = HOST_BUFFER_SIZE) {
status : ErrorCode,
}
-test HostBufferSizeComplete {
- "\x0e\x04\x01\x33\x0c\x00",
-}
-
struct CompletedPackets {
connection_handle : 12,
_reserved_ : 4,
host_num_of_completed_packets : 16,
}
-packet HostNumCompletedPackets : Command (op_code = HOST_NUM_COMPLETED_PACKETS) {
+packet HostNumCompletedPackets : CommandPacket (op_code = HOST_NUM_COMPLETED_PACKETS) {
_count_(completed_packets) : 8,
completed_packets : CompletedPackets[],
}
@@ -2145,7 +1715,7 @@ packet ReadLinkSupervisionTimeoutComplete : CommandComplete (command_op_code = R
}
packet WriteLinkSupervisionTimeout : ConnectionManagementCommand (op_code = WRITE_LINK_SUPERVISION_TIMEOUT) {
- connection_handle : 12,
+ handle : 12,
_reserved_ : 4,
link_supervision_timeout : 16, // 0x001-0xFFFF (0.625ms-40.9s)
}
@@ -2159,54 +1729,30 @@ packet WriteLinkSupervisionTimeoutComplete : CommandComplete (command_op_code =
packet ReadNumberOfSupportedIac : DiscoveryCommand (op_code = READ_NUMBER_OF_SUPPORTED_IAC) {
}
-test ReadNumberOfSupportedIac {
- "\x38\x0c\x00",
-}
-
packet ReadNumberOfSupportedIacComplete : CommandComplete (command_op_code = READ_NUMBER_OF_SUPPORTED_IAC) {
status : ErrorCode,
num_support_iac : 8,
}
-test ReadNumberOfSupportedIacComplete {
- "\x0e\x05\x01\x38\x0c\x00\x99",
-}
-
packet ReadCurrentIacLap : DiscoveryCommand (op_code = READ_CURRENT_IAC_LAP) {
}
-test ReadCurrentIacLap {
- "\x39\x0c\x00",
-}
-
packet ReadCurrentIacLapComplete : CommandComplete (command_op_code = READ_CURRENT_IAC_LAP) {
status : ErrorCode,
_count_(laps_to_read) : 8,
laps_to_read : Lap[],
}
-test ReadCurrentIacLapComplete {
- "\x0e\x0b\x01\x39\x0c\x00\x02\x11\x8b\x9e\x22\x8b\x9e",
-}
-
packet WriteCurrentIacLap : DiscoveryCommand (op_code = WRITE_CURRENT_IAC_LAP) {
_count_(laps_to_write) : 8,
laps_to_write : Lap[],
}
-test WriteCurrentIacLap {
- "\x3a\x0c\x07\x02\x11\x8b\x9e\x22\x8b\x9e",
-}
-
packet WriteCurrentIacLapComplete : CommandComplete (command_op_code = WRITE_CURRENT_IAC_LAP) {
status : ErrorCode,
}
-test WriteCurrentIacLapComplete {
- "\x0e\x04\x01\x3a\x0c\x00",
-}
-
-packet SetAfhHostChannelClassification : Command (op_code = SET_AFH_HOST_CHANNEL_CLASSIFICATION) {
+packet SetAfhHostChannelClassification : CommandPacket (op_code = SET_AFH_HOST_CHANNEL_CLASSIFICATION) {
afh_host_channel_classification : 8[10],
}
@@ -2278,20 +1824,12 @@ packet WritePageScanTypeComplete : CommandComplete (command_op_code = WRITE_PAGE
status : ErrorCode,
}
-packet ReadAfhChannelAssessmentMode : Command (op_code = READ_AFH_CHANNEL_ASSESSMENT_MODE) {
-}
-
-packet ReadAfhChannelAssessmentModeComplete : CommandComplete (command_op_code = READ_AFH_CHANNEL_ASSESSMENT_MODE) {
- status : ErrorCode,
- controller_channel_assessment : Enable,
-}
-
-packet WriteAfhChannelAssessmentMode : Command (op_code = WRITE_AFH_CHANNEL_ASSESSMENT_MODE) {
- controller_channel_assessment : Enable,
+packet ReadAfhChannelAssessmentMode : CommandPacket (op_code = READ_AFH_CHANNEL_ASSESSMENT_MODE) {
+ _payload_, // placeholder (unimplemented)
}
-packet WriteAfhChannelAssessmentModeComplete : CommandComplete (command_op_code = WRITE_AFH_CHANNEL_ASSESSMENT_MODE) {
- status : ErrorCode,
+packet WriteAfhChannelAssessmentMode : CommandPacket (op_code = WRITE_AFH_CHANNEL_ASSESSMENT_MODE) {
+ _payload_, // placeholder (unimplemented)
}
enum FecRequired : 8 {
@@ -2299,7 +1837,7 @@ enum FecRequired : 8 {
REQUIRED = 0x01,
}
-packet ReadExtendedInquiryResponse : Command (op_code = READ_EXTENDED_INQUIRY_RESPONSE) {
+packet ReadExtendedInquiryResponse : CommandPacket (op_code = READ_EXTENDED_INQUIRY_RESPONSE) {
}
packet ReadExtendedInquiryResponseComplete : CommandComplete (command_op_code = READ_EXTENDED_INQUIRY_RESPONSE) {
@@ -2308,10 +1846,10 @@ packet ReadExtendedInquiryResponseComplete : CommandComplete (command_op_code =
extended_inquiry_response : GapData[],
}
-packet WriteExtendedInquiryResponse : Command (op_code = WRITE_EXTENDED_INQUIRY_RESPONSE) {
+packet WriteExtendedInquiryResponse : CommandPacket (op_code = WRITE_EXTENDED_INQUIRY_RESPONSE) {
fec_required : FecRequired,
extended_inquiry_response : GapData[],
- _padding_[240], // Zero padding GapData[] to be 240 octets
+ _padding_[244], // Zero padding to be 240 octets (GapData[]) + 2 (opcode) + 1 (size) + 1 (FecRequired)
}
packet WriteExtendedInquiryResponseComplete : CommandComplete (command_op_code = WRITE_EXTENDED_INQUIRY_RESPONSE) {
@@ -2338,18 +1876,10 @@ packet WriteSimplePairingMode : SecurityCommand (op_code = WRITE_SIMPLE_PAIRING_
simple_pairing_mode : Enable,
}
-test WriteSimplePairingMode {
- "\x56\x0c\x01\x01",
-}
-
packet WriteSimplePairingModeComplete : CommandComplete (command_op_code = WRITE_SIMPLE_PAIRING_MODE) {
status : ErrorCode,
}
-test WriteSimplePairingModeComplete {
- "\x0e\x04\x01\x56\x0c\x00",
-}
-
packet ReadLocalOobData : SecurityCommand (op_code = READ_LOCAL_OOB_DATA) {
}
@@ -2393,33 +1923,29 @@ packet SendKeypressNotificationComplete : CommandComplete (command_op_code = SEN
bd_addr : Address,
}
-packet ReadLeHostSupport : Command (op_code = READ_LE_HOST_SUPPORT) {
+enum SimultaneousLeHost : 8 {
+ DISABLED = 0x00,
+}
+
+packet ReadLeHostSupport : CommandPacket (op_code = READ_LE_HOST_SUPPORT) {
}
packet ReadLeHostSupportComplete : CommandComplete (command_op_code = READ_LE_HOST_SUPPORT) {
status : ErrorCode,
le_supported_host : Enable,
- _reserved_ : 8, // simultaneous_le_host reserved since 4.1
+ simultaneous_le_host : SimultaneousLeHost,
}
-packet WriteLeHostSupport : Command (op_code = WRITE_LE_HOST_SUPPORT) {
+packet WriteLeHostSupport : CommandPacket (op_code = WRITE_LE_HOST_SUPPORT) {
le_supported_host : Enable,
- simultaneous_le_host : Enable, // According to the spec, this should be 0x00 since 4.1
-}
-
-test WriteLeHostSupport {
- "\x6d\x0c\x02\x01\x01",
+ simultaneous_le_host : SimultaneousLeHost,
}
packet WriteLeHostSupportComplete : CommandComplete (command_op_code = WRITE_LE_HOST_SUPPORT) {
status : ErrorCode,
}
-test WriteLeHostSupportComplete {
- "\x0e\x04\x01\x6d\x0c\x00",
-}
-
-packet ReadSecureConnectionsHostSupport : Command (op_code = READ_SECURE_CONNECTIONS_HOST_SUPPORT) {
+packet ReadSecureConnectionsHostSupport : CommandPacket (op_code = READ_SECURE_CONNECTIONS_HOST_SUPPORT) {
}
packet ReadSecureConnectionsHostSupportComplete : CommandComplete (command_op_code = READ_SECURE_CONNECTIONS_HOST_SUPPORT) {
@@ -2431,18 +1957,10 @@ packet WriteSecureConnectionsHostSupport : SecurityCommand (op_code = WRITE_SECU
secure_connections_host_support : Enable,
}
-test WriteSecureConnectionsHostSupport {
- "\x7a\x0c\x01\x01",
-}
-
packet WriteSecureConnectionsHostSupportComplete : CommandComplete (command_op_code = WRITE_SECURE_CONNECTIONS_HOST_SUPPORT) {
status : ErrorCode,
}
-test WriteSecureConnectionsHostSupportComplete {
- "\x0e\x04\x01\x7a\x0c\x00",
-}
-
packet ReadLocalOobExtendedData : SecurityCommand (op_code = READ_LOCAL_OOB_EXTENDED_DATA) {
}
@@ -2454,37 +1972,9 @@ packet ReadLocalOobExtendedDataComplete : CommandComplete (command_op_code = REA
r_256 : 8[16],
}
-packet SetEcosystemBaseInterval : Command (op_code = SET_ECOSYSTEM_BASE_INTERVAL) {
- interval : 16,
-}
-
-packet SetEcosystemBaseIntervalComplete : CommandComplete (command_op_code = SET_ECOSYSTEM_BASE_INTERVAL) {
- status : ErrorCode,
-}
-
-enum DataPathDirection : 8 {
- INPUT = 0,
- OUTPUT = 1,
-}
-
-packet ConfigureDataPath : Command (op_code = CONFIGURE_DATA_PATH) {
- data_path_direction : DataPathDirection,
- data_path_id : 8,
- _size_(vendor_specific_config) : 8,
- vendor_specific_config : 8[],
-}
-
-packet ConfigureDataPathComplete : CommandComplete (command_op_code = CONFIGURE_DATA_PATH) {
- status : ErrorCode,
-}
-
// INFORMATIONAL_PARAMETERS
-packet ReadLocalVersionInformation : Command (op_code = READ_LOCAL_VERSION_INFORMATION) {
-}
-
-test ReadLocalVersionInformation {
- "\x01\x10\x00",
+packet ReadLocalVersionInformation : CommandPacket (op_code = READ_LOCAL_VERSION_INFORMATION) {
}
enum HciVersion : 8 {
@@ -2499,7 +1989,6 @@ enum HciVersion : 8 {
V_4_2 = 0x08,
V_5_0 = 0x09,
V_5_1 = 0x0a,
- V_5_2 = 0x0b,
}
enum LmpVersion : 8 {
@@ -2514,7 +2003,6 @@ enum LmpVersion : 8 {
V_4_2 = 0x08,
V_5_0 = 0x09,
V_5_1 = 0x0a,
- V_5_2 = 0x0b,
}
struct LocalVersionInformation {
@@ -2530,15 +2018,7 @@ packet ReadLocalVersionInformationComplete : CommandComplete (command_op_code =
local_version_information : LocalVersionInformation,
}
-test ReadLocalVersionInformationComplete {
- "\x0e\x0c\x01\x01\x10\x00\x09\x00\x00\x09\x1d\x00\xbe\x02",
-}
-
-packet ReadLocalSupportedCommands : Command (op_code = READ_LOCAL_SUPPORTED_COMMANDS) {
-}
-
-test ReadLocalSupportedCommands {
- "\x02\x10\x00",
+packet ReadLocalSupportedCommands : CommandPacket (op_code = READ_LOCAL_SUPPORTED_COMMANDS) {
}
packet ReadLocalSupportedCommandsComplete : CommandComplete (command_op_code = READ_LOCAL_SUPPORTED_COMMANDS) {
@@ -2546,11 +2026,7 @@ packet ReadLocalSupportedCommandsComplete : CommandComplete (command_op_code = R
supported_commands : 8[64],
}
-test ReadLocalSupportedCommandsComplete {
- "\x0e\x44\x01\x02\x10\x00\xff\xff\xff\x03\xce\xff\xef\xff\xff\xff\xff\x7f\xf2\x0f\xe8\xfe\x3f\xf7\x83\xff\x1c\x00\x00\x00\x61\xff\xff\xff\x7f\xbe\x20\xf5\xff\xf0\xff\xff\xff\xff\xff\x07\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00",
-}
-
-packet ReadLocalSupportedFeatures : Command (op_code = READ_LOCAL_SUPPORTED_FEATURES) {
+packet ReadLocalSupportedFeatures : CommandPacket (op_code = READ_LOCAL_SUPPORTED_FEATURES) {
}
packet ReadLocalSupportedFeaturesComplete : CommandComplete (command_op_code = READ_LOCAL_SUPPORTED_FEATURES) {
@@ -2558,16 +2034,10 @@ packet ReadLocalSupportedFeaturesComplete : CommandComplete (command_op_code = R
lmp_features : 64,
}
-packet ReadLocalExtendedFeatures : Command (op_code = READ_LOCAL_EXTENDED_FEATURES) {
+packet ReadLocalExtendedFeatures : CommandPacket (op_code = READ_LOCAL_EXTENDED_FEATURES) {
page_number : 8,
}
-test ReadLocalExtendedFeatures {
- "\x04\x10\x01\x00",
- "\x04\x10\x01\x01",
- "\x04\x10\x01\x02",
-}
-
packet ReadLocalExtendedFeaturesComplete : CommandComplete (command_op_code = READ_LOCAL_EXTENDED_FEATURES) {
status : ErrorCode,
page_number : 8,
@@ -2575,17 +2045,7 @@ packet ReadLocalExtendedFeaturesComplete : CommandComplete (command_op_code = RE
extended_lmp_features : 64,
}
-test ReadLocalExtendedFeaturesComplete {
- "\x0e\x0e\x01\x04\x10\x00\x00\x02\xff\xfe\x8f\xfe\xd8\x3f\x5b\x87",
- "\x0e\x0e\x01\x04\x10\x00\x01\x02\x07\x00\x00\x00\x00\x00\x00\x00",
- "\x0e\x0e\x01\x04\x10\x00\x02\x02\x45\x03\x00\x00\x00\x00\x00\x00",
-}
-
-packet ReadBufferSize : Command (op_code = READ_BUFFER_SIZE) {
-}
-
-test ReadBufferSize {
- "\x05\x10\x00",
+packet ReadBufferSize : CommandPacket (op_code = READ_BUFFER_SIZE) {
}
packet ReadBufferSizeComplete : CommandComplete (command_op_code = READ_BUFFER_SIZE) {
@@ -2596,15 +2056,7 @@ packet ReadBufferSizeComplete : CommandComplete (command_op_code = READ_BUFFER_S
total_num_synchronous_data_packets : 16,
}
-test ReadBufferSizeComplete {
- "\x0e\x0b\x01\x05\x10\x00\x00\x04\x3c\x07\x00\x08\x00",
-}
-
-packet ReadBdAddr : Command (op_code = READ_BD_ADDR) {
-}
-
-test ReadBdAddr {
- "\x09\x10\x00",
+packet ReadBdAddr : CommandPacket (op_code = READ_BD_ADDR) {
}
packet ReadBdAddrComplete : CommandComplete (command_op_code = READ_BD_ADDR) {
@@ -2612,24 +2064,13 @@ packet ReadBdAddrComplete : CommandComplete (command_op_code = READ_BD_ADDR) {
bd_addr : Address,
}
-test ReadBdAddrComplete {
- "\x0e\x0a\x01\x09\x10\x00\x14\x8e\x61\x5f\x36\x88",
+packet ReadDataBlockSize : CommandPacket (op_code = READ_DATA_BLOCK_SIZE) {
}
-packet ReadDataBlockSize : Command (op_code = READ_DATA_BLOCK_SIZE) {
+packet ReadLocalSupportedCodecs : CommandPacket (op_code = READ_LOCAL_SUPPORTED_CODECS) {
}
-packet ReadDataBlockSizeComplete : CommandComplete (command_op_code = READ_DATA_BLOCK_SIZE) {
- status : ErrorCode,
- max_acl_data_packet_length : 16,
- data_block_length : 16,
- total_num_data_blocks : 16,
-}
-
-packet ReadLocalSupportedCodecsV1 : Command (op_code = READ_LOCAL_SUPPORTED_CODECS_V1) {
-}
-
-packet ReadLocalSupportedCodecsV1Complete : CommandComplete (command_op_code = READ_LOCAL_SUPPORTED_CODECS_V1) {
+packet ReadLocalSupportedCodecsComplete : CommandComplete (command_op_code = READ_LOCAL_SUPPORTED_CODECS) {
status : ErrorCode,
_size_(supported_codecs) : 8,
supported_codecs : 8[],
@@ -2637,72 +2078,6 @@ packet ReadLocalSupportedCodecsV1Complete : CommandComplete (command_op_code = R
vendor_specific_codecs : 32[],
}
-packet ReadLocalSupportedCodecsV2 : Command (op_code = READ_LOCAL_SUPPORTED_CODECS_V2) {
-}
-
-group CodecTransport {
- br_edr : 1,
- br_edr_sco_and_esco : 1,
- le_cis : 1,
- le_bis : 1,
- _reserved_ : 4,
-}
-
-struct CodecConfiguration {
- codec_id : 8,
- CodecTransport,
-}
-
-struct VendorCodecConfiguration {
- company_id : 16,
- codec_vendor_id : 16,
- CodecTransport,
-}
-
-packet ReadLocalSupportedCodecsV2Complete : CommandComplete (command_op_code = READ_LOCAL_SUPPORTED_CODECS_V2) {
- status : ErrorCode,
- _size_(supported_codecs) : 8,
- supported_codecs : CodecConfiguration[],
- _size_(vendor_specific_codecs) : 8,
- vendor_specific_codecs : VendorCodecConfiguration[],
-}
-
-packet ReadLocalSupportedCodecCapabilities : Command (op_code = READ_LOCAL_SUPPORTED_CODEC_CAPABILITIES) {
- codec_id : 8,
- company_id : 16,
- codec_vendor_id : 16,
- CodecTransport,
- direction : DataPathDirection,
-}
-
-struct CodecCapability {
- _size_(capability) : 8,
- capability : 8[],
-}
-
-packet ReadLocalSupportedCodecCapabilitiesComplete : CommandComplete (command_op_code = READ_LOCAL_SUPPORTED_CODEC_CAPABILITIES) {
- status : ErrorCode,
- _count_(codec_capabilities) : 8,
- codec_capabilities : CodecCapability[],
-}
-
-packet ReadLocalSupportedControllerDelay : Command (op_code = READ_LOCAL_SUPPORTED_CONTROLLER_DELAY) {
- codec_id : 8,
- company_id : 16,
- codec_vendor_id : 16,
- CodecTransport,
- direction : DataPathDirection,
- _size_(codec_configuration) : 8,
- codec_configuration : 8[],
-}
-
-packet ReadLocalSupportedControllerDelayComplete : CommandComplete (command_op_code = READ_LOCAL_SUPPORTED_CONTROLLER_DELAY) {
- status : ErrorCode,
- min_controller_delay : 24,
- max_controller_delay : 24,
-}
-
-
// STATUS_PARAMETERS
packet ReadFailedContactCounter : ConnectionManagementCommand (op_code = READ_FAILED_CONTACT_COUNTER) {
connection_handle : 12,
@@ -2739,7 +2114,7 @@ packet ReadLinkQualityComplete : CommandComplete (command_op_code = READ_LINK_QU
link_quality : 8,
}
-packet ReadRssi : AclCommand (op_code = READ_RSSI) {
+packet ReadRssi : ConnectionManagementCommand (op_code = READ_RSSI) {
connection_handle : 12,
_reserved_ : 4,
}
@@ -2809,7 +2184,7 @@ enum LoopbackMode : 8 {
ENABLE_REMOTE = 0x02,
}
-packet ReadLoopbackMode : Command (op_code = READ_LOOPBACK_MODE) {
+packet ReadLoopbackMode : CommandPacket (op_code = READ_LOOPBACK_MODE) {
}
packet ReadLoopbackModeComplete : CommandComplete (command_op_code = READ_LOOPBACK_MODE) {
@@ -2817,7 +2192,7 @@ packet ReadLoopbackModeComplete : CommandComplete (command_op_code = READ_LOOPBA
loopback_mode : LoopbackMode,
}
-packet WriteLoopbackMode : Command (op_code = WRITE_LOOPBACK_MODE) {
+packet WriteLoopbackMode : CommandPacket (op_code = WRITE_LOOPBACK_MODE) {
loopback_mode : LoopbackMode,
}
@@ -2825,7 +2200,7 @@ packet WriteLoopbackModeComplete : CommandComplete (command_op_code = WRITE_LOOP
status : ErrorCode,
}
-packet EnableDeviceUnderTestMode : Command (op_code = ENABLE_DEVICE_UNDER_TEST_MODE) {
+packet EnableDeviceUnderTestMode : CommandPacket (op_code = ENABLE_DEVICE_UNDER_TEST_MODE) {
}
packet EnableDeviceUnderTestModeComplete : CommandComplete (command_op_code = ENABLE_DEVICE_UNDER_TEST_MODE) {
@@ -2840,7 +2215,7 @@ packet WriteSimplePairingDebugModeComplete : CommandComplete (command_op_code =
status : ErrorCode,
}
-packet WriteSecureConnectionsTestMode : Command (op_code = WRITE_SECURE_CONNECTIONS_TEST_MODE) {
+packet WriteSecureConnectionsTestMode : CommandPacket (op_code = WRITE_SECURE_CONNECTIONS_TEST_MODE) {
connection_handle : 12,
_reserved_ : 4,
dm1_aclu_mode : Enable,
@@ -2852,7 +2227,7 @@ packet WriteSecureConnectionsTestModeComplete : CommandComplete (command_op_code
}
// LE_CONTROLLER
-packet LeSetEventMask : Command (op_code = LE_SET_EVENT_MASK) {
+packet LeSetEventMask : CommandPacket (op_code = LE_SET_EVENT_MASK) {
le_event_mask : 64,
}
@@ -2860,7 +2235,7 @@ packet LeSetEventMaskComplete : CommandComplete (command_op_code = LE_SET_EVENT_
status : ErrorCode,
}
-packet LeReadBufferSizeV1 : Command (op_code = LE_READ_BUFFER_SIZE_V1) {
+packet LeReadBufferSize : CommandPacket (op_code = LE_READ_BUFFER_SIZE) {
}
struct LeBufferSize {
@@ -2868,20 +2243,12 @@ struct LeBufferSize {
total_num_le_packets : 8,
}
-test LeReadBufferSizeV1 {
- "\x02\x20\x00",
-}
-
-packet LeReadBufferSizeV1Complete : CommandComplete (command_op_code = LE_READ_BUFFER_SIZE_V1) {
+packet LeReadBufferSizeComplete : CommandComplete (command_op_code = LE_READ_BUFFER_SIZE) {
status : ErrorCode,
le_buffer_size : LeBufferSize,
}
-test LeReadBufferSizeV1Complete {
- "\x0e\x07\x01\x02\x20\x00\xfb\x00\x10",
-}
-
-packet LeReadLocalSupportedFeatures : Command (op_code = LE_READ_LOCAL_SUPPORTED_FEATURES) {
+packet LeReadLocalSupportedFeatures : CommandPacket (op_code = LE_READ_LOCAL_SUPPORTED_FEATURES) {
}
packet LeReadLocalSupportedFeaturesComplete : CommandComplete (command_op_code = LE_READ_LOCAL_SUPPORTED_FEATURES) {
@@ -2899,9 +2266,9 @@ packet LeSetRandomAddressComplete : CommandComplete (command_op_code = LE_SET_RA
enum AdvertisingFilterPolicy : 2 {
ALL_DEVICES = 0, // Default
- LISTED_SCAN = 1,
- LISTED_CONNECT = 2,
- LISTED_SCAN_AND_CONNECT = 3,
+ WHITELISTED_SCAN = 1,
+ WHITELISTED_CONNECT = 2,
+ WHITELISTED_SCAN_AND_CONNECT = 3,
}
enum PeerAddressType : 8 {
@@ -2909,7 +2276,7 @@ enum PeerAddressType : 8 {
RANDOM_DEVICE_OR_IDENTITY_ADDRESS = 0x01,
}
-enum AdvertisingType : 8 {
+enum AdvertisingEventType : 8 {
ADV_IND = 0x00,
ADV_DIRECT_IND = 0x01,
ADV_SCAN_IND = 0x02,
@@ -2924,18 +2291,11 @@ enum AddressType : 8 {
RANDOM_IDENTITY_ADDRESS = 0x03,
}
-enum OwnAddressType : 8 {
- PUBLIC_DEVICE_ADDRESS = 0x00,
- RANDOM_DEVICE_ADDRESS = 0x01,
- RESOLVABLE_OR_PUBLIC_ADDRESS = 0x02,
- RESOLVABLE_OR_RANDOM_ADDRESS = 0x03,
-}
-
packet LeSetAdvertisingParameters : LeAdvertisingCommand (op_code = LE_SET_ADVERTISING_PARAMETERS) {
interval_min : 16,
interval_max : 16,
- advt_type : AdvertisingType,
- own_address_type : OwnAddressType,
+ type : AdvertisingEventType,
+ own_address_type : AddressType,
peer_address_type : PeerAddressType,
peer_address : Address,
channel_map : 8,
@@ -2947,18 +2307,18 @@ packet LeSetAdvertisingParametersComplete : CommandComplete (command_op_code = L
status : ErrorCode,
}
-packet LeReadAdvertisingPhysicalChannelTxPower : LeAdvertisingCommand (op_code = LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER) {
+packet LeReadAdvertisingChannelTxPower : LeAdvertisingCommand (op_code = LE_READ_ADVERTISING_CHANNEL_TX_POWER) {
}
-packet LeReadAdvertisingPhysicalChannelTxPowerComplete : CommandComplete (command_op_code = LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER) {
+packet LeReadAdvertisingChannelTxPowerComplete : CommandComplete (command_op_code = LE_READ_ADVERTISING_CHANNEL_TX_POWER) {
status : ErrorCode,
- transmit_power_level : 8, // (-127dBm to 20dBm) Accuracy: +/-4dB
+ transmit_power_level : 8, // (-20dBm to 10dBm) Accuracy: +/-4dB
}
packet LeSetAdvertisingData : LeAdvertisingCommand (op_code = LE_SET_ADVERTISING_DATA) {
_size_(advertising_data) : 8,
advertising_data : GapData[],
- _padding_[31], // Zero padding to 31 bytes of advertising_data
+ _padding_[35], // Zero padding to 31 bytes of advertising_data + 1 size + 2 opcode + 1 total_size
}
packet LeSetAdvertisingDataComplete : CommandComplete (command_op_code = LE_SET_ADVERTISING_DATA) {
@@ -2968,7 +2328,7 @@ packet LeSetAdvertisingDataComplete : CommandComplete (command_op_code = LE_SET_
packet LeSetScanResponseData : LeAdvertisingCommand (op_code = LE_SET_SCAN_RESPONSE_DATA) {
_size_(advertising_data) : 8,
advertising_data : GapData[],
- _padding_[31], // Zero padding to 31 bytes of advertising_data
+ _padding_[35], // Zero padding to 31 bytes of advertising_data + 1 size + 2 opcode + 1 total_size
}
packet LeSetScanResponseDataComplete : CommandComplete (command_op_code = LE_SET_SCAN_RESPONSE_DATA) {
@@ -2988,23 +2348,19 @@ enum LeScanType : 8 {
ACTIVE = 0x01,
}
-enum LeScanningFilterPolicy : 8 {
+enum LeSetScanningFilterPolicy : 8 {
ACCEPT_ALL = 0x00, // Default
- CONNECT_LIST_ONLY = 0x01,
+ WHITE_LIST_ONLY = 0x01,
CHECK_INITIATORS_IDENTITY = 0x02,
- CONNECT_LIST_AND_INITIATORS_IDENTITY = 0x03,
+ WHITE_LIST_AND_INITIATORS_IDENTITY = 0x03,
}
packet LeSetScanParameters : LeScanningCommand (op_code = LE_SET_SCAN_PARAMETERS) {
le_scan_type : LeScanType,
le_scan_interval : 16, // 0x0004-0x4000 Default 0x10 (10ms)
le_scan_window : 16, // Default 0x10 (10ms)
- own_address_type : OwnAddressType,
- scanning_filter_policy : LeScanningFilterPolicy,
-}
-
-test LeSetScanParameters {
- "\x0b\x20\x07\x01\x12\x00\x12\x00\x01\x00",
+ own_address_type : AddressType,
+ scanning_filter_policy : LeSetScanningFilterPolicy,
}
packet LeSetScanParametersComplete : CommandComplete (command_op_code = LE_SET_SCAN_PARAMETERS) {
@@ -3016,17 +2372,20 @@ packet LeSetScanEnable : LeScanningCommand (op_code = LE_SET_SCAN_ENABLE) {
filter_duplicates : Enable,
}
-test LeSetScanEnable {
- "\x0c\x20\x02\x01\x00",
-}
-
packet LeSetScanEnableComplete : CommandComplete (command_op_code = LE_SET_SCAN_ENABLE) {
status : ErrorCode,
}
enum InitiatorFilterPolicy : 8 {
USE_PEER_ADDRESS = 0x00,
- USE_CONNECT_LIST = 0x01,
+ USE_WHITE_LIST = 0x01,
+}
+
+enum OwnAddressType : 8 {
+ PUBLIC_DEVICE_ADDRESS = 0x00,
+ RANDOM_DEVICE_ADDRESS = 0x01,
+ RESOLVABLE_OR_PUBLIC_ADDRESS = 0x02,
+ RESOLVABLE_OR_RANDOM_ADDRESS = 0x03,
}
packet LeCreateConnection : LeConnectionManagementCommand (op_code = LE_CREATE_CONNECTION) {
@@ -3050,54 +2409,49 @@ packet LeCreateConnectionStatus : CommandStatus (command_op_code = LE_CREATE_CON
packet LeCreateConnectionCancel : LeConnectionManagementCommand (op_code = LE_CREATE_CONNECTION_CANCEL) {
}
-packet LeCreateConnectionCancelComplete : CommandComplete (command_op_code = LE_CREATE_CONNECTION_CANCEL) {
- status : ErrorCode,
+packet LeCreateConnectionCancelStatus : CommandStatus (command_op_code = LE_CREATE_CONNECTION_CANCEL) {
}
-packet LeReadConnectListSize : Command (op_code = LE_READ_CONNECT_LIST_SIZE) {
+packet LeCreateConnectionCancelComplete : CommandComplete (command_op_code = LE_CREATE_CONNECTION_CANCEL) {
+ status : ErrorCode,
}
-test LeReadConnectListSize {
- "\x0f\x20\x00",
+packet LeReadWhiteListSize : LeConnectionManagementCommand (op_code = LE_READ_WHITE_LIST_SIZE) {
}
-packet LeReadConnectListSizeComplete : CommandComplete (command_op_code = LE_READ_CONNECT_LIST_SIZE) {
+packet LeReadWhiteListSizeComplete : CommandComplete (command_op_code = LE_READ_WHITE_LIST_SIZE) {
status : ErrorCode,
- connect_list_size : 8,
+ white_list_size : 8,
}
-test LeReadConnectListSizeComplete {
- "\x0e\x05\x01\x0f\x20\x00\x80",
+packet LeClearWhiteList : LeConnectionManagementCommand (op_code = LE_CLEAR_WHITE_LIST) {
}
-packet LeClearConnectList : LeConnectionManagementCommand (op_code = LE_CLEAR_CONNECT_LIST) {
-}
-
-packet LeClearConnectListComplete : CommandComplete (command_op_code = LE_CLEAR_CONNECT_LIST) {
+packet LeClearWhiteListComplete : CommandComplete (command_op_code = LE_CLEAR_WHITE_LIST) {
status : ErrorCode,
}
-enum ConnectListAddressType : 8 {
+enum WhiteListAddressType : 8 {
PUBLIC = 0x00,
RANDOM = 0x01,
ANONYMOUS_ADVERTISERS = 0xFF,
}
-packet LeAddDeviceToConnectList : LeConnectionManagementCommand (op_code = LE_ADD_DEVICE_TO_CONNECT_LIST) {
- address_type : ConnectListAddressType,
+packet LeAddDeviceToWhiteList : LeConnectionManagementCommand (op_code = LE_ADD_DEVICE_TO_WHITE_LIST) {
+ address_type : WhiteListAddressType,
address : Address,
}
-packet LeAddDeviceToConnectListComplete : CommandComplete (command_op_code = LE_ADD_DEVICE_TO_CONNECT_LIST) {
+packet LeAddDeviceToWhiteListComplete : CommandComplete (command_op_code = LE_ADD_DEVICE_TO_WHITE_LIST) {
status : ErrorCode,
}
-packet LeRemoveDeviceFromConnectList : LeConnectionManagementCommand (op_code = LE_REMOVE_DEVICE_FROM_CONNECT_LIST) {
- address_type : ConnectListAddressType,
+packet LeRemoveDeviceFromWhiteList : LeConnectionManagementCommand (op_code = LE_REMOVE_DEVICE_FROM_WHITE_LIST) {
+ address_type : WhiteListAddressType,
address : Address,
}
-packet LeRemoveDeviceFromConnectListComplete : CommandComplete (command_op_code = LE_REMOVE_DEVICE_FROM_CONNECT_LIST) {
+packet LeRemoveDeviceFromWhiteListComplete : CommandComplete (command_op_code = LE_REMOVE_DEVICE_FROM_WHITE_LIST) {
status : ErrorCode,
}
@@ -3126,7 +2480,7 @@ packet LeSetHostChannelClassificationComplete : CommandComplete (command_op_code
packet LeReadChannelMap : LeConnectionManagementCommand (op_code = LE_READ_CHANNEL_MAP) {
}
-packet LeReadChannelMapComplete : CommandComplete (command_op_code = LE_READ_CHANNEL_MAP) {
+packet LeReadChannelMapComplete : CommandComplete (command_op_code = LE_SET_HOST_CHANNEL_CLASSIFICATION) {
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
@@ -3138,9 +2492,6 @@ packet LeReadRemoteFeatures : LeConnectionManagementCommand (op_code = LE_READ_R
_reserved_ : 4,
}
-packet LeReadRemoteFeaturesStatus : CommandStatus (command_op_code = LE_READ_REMOTE_FEATURES) {
-}
-
packet LeEncrypt : LeSecurityCommand (op_code = LE_ENCRYPT) {
key : 8[16],
plaintext_data : 8[16],
@@ -3191,7 +2542,7 @@ packet LeLongTermKeyRequestNegativeReplyComplete : CommandComplete (command_op_c
_reserved_ : 4,
}
-packet LeReadSupportedStates : Command (op_code = LE_READ_SUPPORTED_STATES) {
+packet LeReadSupportedStates : CommandPacket (op_code = LE_READ_SUPPORTED_STATES) {
}
packet LeReadSupportedStatesComplete : CommandComplete (command_op_code = LE_READ_SUPPORTED_STATES) {
@@ -3199,40 +2550,16 @@ packet LeReadSupportedStatesComplete : CommandComplete (command_op_code = LE_REA
le_states : 64,
}
-packet LeReceiverTest : Command (op_code = LE_RECEIVER_TEST) {
- rx_channel : 8,
-}
-
-packet LeReceiverTestComplete : CommandComplete (command_op_code = LE_RECEIVER_TEST) {
- status : ErrorCode,
-}
-
-enum LeTestPayload : 8 {
- PRBS9 = 0x00,
- REPEATED_F0 = 0x01,
- REPEATED_AA = 0x02,
- PRBS15 = 0x03,
- REPEATED_FF = 0x04,
- REPEATED_00 = 0x05,
- REPEATED_0F = 0x06,
- REPEATED_55 = 0x07,
-}
-
-packet LeTransmitterTest : Command (op_code = LE_TRANSMITTER_TEST) {
- tx_channel : 8,
- test_data_length : 8,
- packet_payload : LeTestPayload,
-}
-
-packet LeTransmitterTestComplete : CommandComplete (command_op_code = LE_TRANSMITTER_TEST) {
- status : ErrorCode,
+packet LeReceiverTest : CommandPacket (op_code = LE_RECEIVER_TEST) {
+ _payload_, // placeholder (unimplemented)
}
-packet LeTestEnd : Command (op_code = LE_TEST_END) {
+packet LeTransmitterTest : CommandPacket (op_code = LE_TRANSMITTER_TEST) {
+ _payload_, // placeholder (unimplemented)
}
-packet LeTestEndComplete : CommandComplete (command_op_code = LE_TEST_END) {
- status : ErrorCode,
+packet LeTestEnd : CommandPacket (op_code = LE_TEST_END) {
+ _payload_, // placeholder (unimplemented)
}
packet LeRemoteConnectionParameterRequestReply : LeConnectionManagementCommand (op_code = LE_REMOTE_CONNECTION_PARAMETER_REQUEST_REPLY) {
@@ -3298,9 +2625,6 @@ packet LeWriteSuggestedDefaultDataLengthComplete : CommandComplete (command_op_c
packet LeReadLocalP256PublicKeyCommand : LeSecurityCommand (op_code = LE_READ_LOCAL_P_256_PUBLIC_KEY_COMMAND) {
}
-packet LeReadLocalP256PublicKeyCommandStatus : CommandStatus (command_op_code = LE_READ_LOCAL_P_256_PUBLIC_KEY_COMMAND) {
-}
-
packet LeGenerateDhkeyV1Command : LeSecurityCommand (op_code = LE_GENERATE_DHKEY_COMMAND_V1) {
remote_p_256_public_key : 8[64],
}
@@ -3335,12 +2659,11 @@ packet LeClearResolvingListComplete : CommandComplete (command_op_code = LE_CLEA
status : ErrorCode,
}
-packet LeReadResolvingListSize : Command (op_code = LE_READ_RESOLVING_LIST_SIZE) {
+packet LeReadResolvingListSize : LeSecurityCommand (op_code = LE_READ_RESOLVING_LIST_SIZE) {
}
packet LeReadResolvingListSizeComplete : CommandComplete (command_op_code = LE_READ_RESOLVING_LIST_SIZE) {
status : ErrorCode,
- resolving_list_size : 8,
}
packet LeReadPeerResolvableAddress : LeSecurityCommand (op_code = LE_READ_PEER_RESOLVABLE_ADDRESS) {
@@ -3379,7 +2702,7 @@ packet LeSetResolvablePrivateAddressTimeoutComplete : CommandComplete (command_o
status : ErrorCode,
}
-packet LeReadMaximumDataLength : Command (op_code = LE_READ_MAXIMUM_DATA_LENGTH) {
+packet LeReadMaximumDataLength : CommandPacket (op_code = LE_READ_MAXIMUM_DATA_LENGTH) {
}
struct LeMaximumDataLength {
@@ -3395,84 +2718,23 @@ packet LeReadMaximumDataLengthComplete : CommandComplete (command_op_code = LE_R
}
packet LeReadPhy : LeConnectionManagementCommand (op_code = LE_READ_PHY) {
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-enum PhyType : 8 {
- LE_1M = 0x01,
- LE_2M = 0x02,
- LE_CODED = 0x03,
-}
-
-packet LeReadPhyComplete : CommandComplete (command_op_code = LE_READ_PHY) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
- tx_phy : PhyType,
- rx_phy : PhyType,
+ _payload_, // placeholder (unimplemented)
}
packet LeSetDefaultPhy : LeConnectionManagementCommand (op_code = LE_SET_DEFAULT_PHY) {
- all_phys_no_transmit_preference : 1,
- all_phys_no_receive_preference : 1,
- _reserved_ : 6,
- tx_phys_bitmask : 3,
- _reserved_ : 5,
- rx_phys_bitmask : 3,
- _reserved_ : 5,
-}
-
-packet LeSetDefaultPhyComplete : CommandComplete (command_op_code = LE_SET_DEFAULT_PHY) {
- status : ErrorCode,
-}
-
-enum PhyOptions : 8 {
- NO_PREFERENCE = 0x00,
- S_2 = 0x01,
- S_8 = 0x02,
+ _payload_, // placeholder (unimplemented)
}
packet LeSetPhy : LeConnectionManagementCommand (op_code = LE_SET_PHY) {
- connection_handle : 12,
- _reserved_ : 4,
- all_phys_no_transmit_preference : 1,
- all_phys_no_receive_preference : 1,
- _reserved_ : 6,
- tx_phys_bitmask : 3,
- _reserved_ : 5,
- rx_phys_bitmask : 3,
- _reserved_ : 5,
- phy_options : PhyOptions,
-}
-
-packet LeSetPhyStatus : CommandStatus (command_op_code = LE_SET_PHY) {
-}
-
-enum ModulationIndex : 8 {
- STANDARD = 0x00,
- STABLE = 0x01,
-}
-
-packet LeEnhancedReceiverTest : Command (op_code = LE_ENHANCED_RECEIVER_TEST) {
- rx_channel : 8,
- phy : PhyType,
- modulation_index : ModulationIndex,
-}
-
-packet LeEnhancedReceiverTestComplete : CommandComplete (command_op_code = LE_ENHANCED_RECEIVER_TEST) {
- status : ErrorCode,
+ _payload_, // placeholder (unimplemented)
}
-packet LeEnhancedTransmitterTest : Command (op_code = LE_ENHANCED_TRANSMITTER_TEST) {
- tx_channel : 8,
- test_data_length : 8,
- packet_payload : LeTestPayload,
- phy : PhyType,
+packet LeEnhancedReceiverTest : CommandPacket (op_code = LE_ENHANCED_RECEIVER_TEST) {
+ _payload_, // placeholder (unimplemented)
}
-packet LeEnhancedTransmitterTestComplete : CommandComplete (command_op_code = LE_ENHANCED_TRANSMITTER_TEST) {
- status : ErrorCode,
+packet LeEnhancedTransmitterTest : CommandPacket (op_code = LE_ENHANCED_TRANSMITTER_TEST) {
+ _payload_, // placeholder (unimplemented)
}
packet LeSetExtendedAdvertisingRandomAddress : LeAdvertisingCommand (op_code = LE_SET_EXTENDED_ADVERTISING_RANDOM_ADDRESS) {
@@ -3480,18 +2742,10 @@ packet LeSetExtendedAdvertisingRandomAddress : LeAdvertisingCommand (op_code = L
advertising_random_address : Address,
}
-test LeSetExtendedAdvertisingRandomAddress {
- "\x35\x20\x07\x00\x77\x58\xeb\xd3\x1c\x6e",
-}
-
packet LeSetExtendedAdvertisingRandomAddressComplete : CommandComplete (command_op_code = LE_SET_EXTENDED_ADVERTISING_RANDOM_ADDRESS) {
status : ErrorCode,
}
-test LeSetExtendedAdvertisingRandomAddressComplete {
- "\x0e\x04\x01\x35\x20\x00",
-}
-
// The lower 4 bits of the advertising event properties
enum LegacyAdvertisingProperties : 4 {
ADV_IND = 0x3,
@@ -3535,11 +2789,6 @@ packet LeSetExtendedAdvertisingLegacyParameters : LeAdvertisingCommand (op_code
scan_request_notification_enable : Enable,
}
-test LeSetExtendedAdvertisingLegacyParameters {
- "\x36\x20\x19\x00\x13\x00\x90\x01\x00\xc2\x01\x00\x07\x01\x00\x00\x00\x00\x00\x00\x00\x00\xf9\x01\x00\x01\x01\x00",
- "\x36\x20\x19\x01\x13\x00\x90\x01\x00\xc2\x01\x00\x07\x01\x00\x00\x00\x00\x00\x00\x00\x00\xf9\x01\x00\x01\x01\x00",
-}
-
packet LeSetExtendedAdvertisingParameters : LeAdvertisingCommand (op_code = LE_SET_EXTENDED_ADVERTISING_PARAMETERS) {
advertising_handle : 8,
advertising_event_legacy_properties : 4,
@@ -3591,10 +2840,6 @@ packet LeSetExtendedAdvertisingData : LeAdvertisingCommand (op_code = LE_SET_EXT
advertising_data : GapData[],
}
-test LeSetExtendedAdvertisingData {
- "\x37\x20\x12\x00\x03\x01\x0e\x02\x01\x02\x0a\x09\x50\x69\x78\x65\x6c\x20\x33\x20\x58",
-}
-
packet LeSetExtendedAdvertisingDataRaw : LeAdvertisingCommand (op_code = LE_SET_EXTENDED_ADVERTISING_DATA) {
advertising_handle : 8,
operation : Operation,
@@ -3609,10 +2854,6 @@ packet LeSetExtendedAdvertisingDataComplete : CommandComplete (command_op_code =
status : ErrorCode,
}
-test LeSetExtendedAdvertisingDataComplete {
- "\x0e\x04\x01\x37\x20\x00",
-}
-
packet LeSetExtendedAdvertisingScanResponse : LeAdvertisingCommand (op_code = LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE) {
advertising_handle : 8,
operation : Operation,
@@ -3666,19 +2907,11 @@ packet LeSetExtendedAdvertisingEnable : LeAdvertisingCommand (op_code = LE_SET_E
enabled_sets : EnabledSet[],
}
-test LeSetExtendedAdvertisingEnable {
- "\x39\x20\x06\x00\x01\x01\x00\x00\x00",
-}
-
packet LeSetExtendedAdvertisingEnableComplete : CommandComplete (command_op_code = LE_SET_EXTENDED_ADVERTISING_ENABLE) {
status : ErrorCode,
}
-test LeSetExtendedAdvertisingEnableComplete {
- "\x0e\x04\x01\x39\x20\x00",
-}
-
-packet LeReadMaximumAdvertisingDataLength : Command (op_code = LE_READ_MAXIMUM_ADVERTISING_DATA_LENGTH) {
+packet LeReadMaximumAdvertisingDataLength : CommandPacket (op_code = LE_READ_MAXIMUM_ADVERTISING_DATA_LENGTH) {
}
packet LeReadMaximumAdvertisingDataLengthComplete : CommandComplete (command_op_code = LE_READ_MAXIMUM_ADVERTISING_DATA_LENGTH) {
@@ -3686,7 +2919,7 @@ packet LeReadMaximumAdvertisingDataLengthComplete : CommandComplete (command_op_
maximum_advertising_data_length : 16,
}
-packet LeReadNumberOfSupportedAdvertisingSets : Command (op_code = LE_READ_NUMBER_OF_SUPPORTED_ADVERTISING_SETS) {
+packet LeReadNumberOfSupportedAdvertisingSets : CommandPacket (op_code = LE_READ_NUMBER_OF_SUPPORTED_ADVERTISING_SETS) {
}
packet LeReadNumberOfSupportedAdvertisingSetsComplete : CommandComplete (command_op_code = LE_READ_NUMBER_OF_SUPPORTED_ADVERTISING_SETS) {
@@ -3698,18 +2931,10 @@ packet LeRemoveAdvertisingSet : LeAdvertisingCommand (op_code = LE_REMOVE_ADVERT
advertising_handle : 8,
}
-test LeRemoveAdvertisingSet {
- "\x3c\x20\x01\x01",
-}
-
packet LeRemoveAdvertisingSetComplete : CommandComplete (command_op_code = LE_REMOVE_ADVERTISING_SET) {
status : ErrorCode,
}
-test LeRemoveAdvertisingSetComplete {
- "\x0e\x04\x01\x3c\x20\x00",
-}
-
packet LeClearAdvertisingSets : LeAdvertisingCommand (op_code = LE_CLEAR_ADVERTISING_SETS) {
}
@@ -3735,7 +2960,7 @@ packet LeSetPeriodicAdvertisingData : LeAdvertisingCommand (op_code = LE_SET_PER
operation : Operation,
_reserved_ : 5,
_size_(scan_response_data) : 8,
- scan_response_data : GapData[],
+ scan_response_data : 8[],
}
packet LeSetPeriodicAdvertisingDataComplete : CommandComplete (command_op_code = LE_SET_PERIODIC_ADVERTISING_DATA) {
@@ -3743,8 +2968,8 @@ packet LeSetPeriodicAdvertisingDataComplete : CommandComplete (command_op_code =
}
packet LeSetPeriodicAdvertisingEnable : LeAdvertisingCommand (op_code = LE_SET_PERIODIC_ADVERTISING_ENABLE) {
- enable : Enable,
advertising_handle : 8,
+ enable : Enable,
}
packet LeSetPeriodicAdvertisingEnableComplete : CommandComplete (command_op_code = LE_SET_PERIODIC_ADVERTISING_ENABLE) {
@@ -3758,25 +2983,16 @@ struct PhyScanParameters {
}
packet LeSetExtendedScanParameters : LeScanningCommand (op_code = LE_SET_EXTENDED_SCAN_PARAMETERS) {
- own_address_type : OwnAddressType,
- scanning_filter_policy : LeScanningFilterPolicy,
+ own_address_type : AddressType,
+ scanning_filter_policy : LeSetScanningFilterPolicy,
scanning_phys : 8,
parameters : PhyScanParameters[],
}
-test LeSetExtendedScanParameters {
- "\x41\x20\x08\x01\x00\x01\x01\x12\x00\x12\x00",
- "\x41\x20\x08\x01\x00\x01\x01\x99\x19\x99\x19",
-}
-
packet LeSetExtendedScanParametersComplete : CommandComplete (command_op_code = LE_SET_EXTENDED_SCAN_PARAMETERS) {
status : ErrorCode,
}
-test LeSetExtendedScanParametersComplete {
- "\x0e\x04\x01\x41\x20\x00",
-}
-
enum FilterDuplicates : 8 {
DISABLED = 0,
ENABLED = 1,
@@ -3790,19 +3006,10 @@ packet LeSetExtendedScanEnable : LeScanningCommand (op_code = LE_SET_EXTENDED_SC
period : 16, // 0 - Scan continuously, N * 1.28 sec
}
-test LeSetExtendedScanEnable {
- "\x42\x20\x06\x01\x00\x00\x00\x00\x00",
- "\x42\x20\x06\x00\x01\x00\x00\x00\x00",
-}
-
packet LeSetExtendedScanEnableComplete : CommandComplete (command_op_code = LE_SET_EXTENDED_SCAN_ENABLE) {
status : ErrorCode,
}
-test LeSetExtendedScanEnableComplete {
- "\x0e\x04\x01\x42\x20\x00",
-}
-
struct LeCreateConnPhyScanParameters {
scan_interval : 16, // 0x0004-0xFFFF
scan_window : 16, // < = LeScanInterval
@@ -3823,10 +3030,6 @@ packet LeExtendedCreateConnection : LeConnectionManagementCommand (op_code = LE_
phy_scan_parameters : LeCreateConnPhyScanParameters[],
}
-test LeExtendedCreateConnection {
- "\x43\x20\x2a\x01\x01\x00\x00\x00\x00\x00\x00\x00\x03\x00\x08\x30\x00\x18\x00\x28\x00\x00\x00\xf4\x01\x00\x00\x00\x00\x00\x08\x30\x00\x18\x00\x28\x00\x00\x00\xf4\x01\x00\x00\x00\x00",
-}
-
packet LeExtendedCreateConnectionStatus : CommandStatus (command_op_code = LE_EXTENDED_CREATE_CONNECTION) {
}
@@ -3834,89 +3037,40 @@ packet LePeriodicAdvertisingCreateSync : LeAdvertisingCommand (op_code = LE_PERI
_payload_, // placeholder (unimplemented)
}
-packet LePeriodicAdvertisingCreateSyncStatus : CommandStatus (command_op_code = LE_PERIODIC_ADVERTISING_CREATE_SYNC) {
-}
-
packet LePeriodicAdvertisingCreateSyncCancel : LeAdvertisingCommand (op_code = LE_PERIODIC_ADVERTISING_CREATE_SYNC_CANCEL) {
_payload_, // placeholder (unimplemented)
}
-packet LePeriodicAdvertisingCreateSyncCancelComplete : CommandComplete (command_op_code = LE_PERIODIC_ADVERTISING_CREATE_SYNC_CANCEL) {
- status : ErrorCode,
-}
-
packet LePeriodicAdvertisingTerminateSync : LeAdvertisingCommand (op_code = LE_PERIODIC_ADVERTISING_TERMINATE_SYNC) {
_payload_, // placeholder (unimplemented)
}
-packet LePeriodicAdvertisingTerminateSyncComplete : CommandComplete (command_op_code = LE_PERIODIC_ADVERTISING_TERMINATE_SYNC) {
- status : ErrorCode,
-}
-
-enum AdvertisingAddressType : 8 {
- PUBLIC_ADDRESS = 0x00,
- RANDOM_ADDRESS = 0x01,
-}
-
packet LeAddDeviceToPeriodicAdvertisingList : LeAdvertisingCommand (op_code = LE_ADD_DEVICE_TO_PERIODIC_ADVERTISING_LIST) {
- advertising_address_type : AdvertisingAddressType,
- advertiser_address : Address,
- advertising_sid : 4,
- _reserved_ : 4,
-}
-
-packet LeAddDeviceToPeriodicAdvertisingListComplete : CommandComplete (command_op_code = LE_ADD_DEVICE_TO_PERIODIC_ADVERTISING_LIST) {
- status : ErrorCode,
+ _payload_, // placeholder (unimplemented)
}
packet LeRemoveDeviceFromPeriodicAdvertisingList : LeAdvertisingCommand (op_code = LE_REMOVE_DEVICE_FROM_PERIODIC_ADVERTISING_LIST) {
_payload_, // placeholder (unimplemented)
}
-packet LeRemoveDeviceFromPeriodicAdvertisingListComplete : CommandComplete (command_op_code = LE_REMOVE_DEVICE_FROM_PERIODIC_ADVERTISING_LIST) {
- status : ErrorCode,
-}
-
packet LeClearPeriodicAdvertisingList : LeAdvertisingCommand (op_code = LE_CLEAR_PERIODIC_ADVERTISING_LIST) {
+ _payload_, // placeholder (unimplemented)
}
-packet LeClearPeriodicAdvertisingListComplete : CommandComplete (command_op_code = LE_CLEAR_PERIODIC_ADVERTISING_LIST) {
- status : ErrorCode,
-}
-
-packet LeReadPeriodicAdvertiserListSize : Command (op_code = LE_READ_PERIODIC_ADVERTISING_LIST_SIZE) {
-}
-
-packet LeReadPeriodicAdvertiserListSizeComplete : CommandComplete (command_op_code = LE_READ_PERIODIC_ADVERTISING_LIST_SIZE) {
- status : ErrorCode,
- periodic_advertiser_list_size : 8,
+packet LeReadPeriodicAdvertisingListSize : LeAdvertisingCommand (op_code = LE_READ_PERIODIC_ADVERTISING_LIST_SIZE) {
+ _payload_, // placeholder (unimplemented)
}
packet LeReadTransmitPower : LeAdvertisingCommand (op_code = LE_READ_TRANSMIT_POWER) {
-}
-
-packet LeReadTransmitPowerComplete : CommandComplete (command_op_code = LE_READ_TRANSMIT_POWER) {
- status : ErrorCode,
- min_tx_power_dbm : 8,
- max_tx_power_dbm : 8,
+ _payload_, // placeholder (unimplemented)
}
packet LeReadRfPathCompensationPower : LeAdvertisingCommand (op_code = LE_READ_RF_PATH_COMPENSATION_POWER) {
-}
-
-packet LeReadRfPathCompensationPowerComplete : CommandComplete (command_op_code = LE_READ_RF_PATH_COMPENSATION_POWER) {
- status : ErrorCode,
- rf_tx_path_compensation_tenths_db : 16,
- rf_rx_path_compensation_tenths_db : 16,
+ _payload_, // placeholder (unimplemented)
}
packet LeWriteRfPathCompensationPower : LeAdvertisingCommand (op_code = LE_WRITE_RF_PATH_COMPENSATION_POWER) {
- rf_tx_path_compensation_tenths_db : 16,
- rf_rx_path_compensation_tenths_db : 16,
-}
-
-packet LeWriteRfPathCompensationPowerComplete : CommandComplete (command_op_code = LE_WRITE_RF_PATH_COMPENSATION_POWER) {
- status : ErrorCode,
+ _payload_, // placeholder (unimplemented)
}
enum PrivacyMode : 8 {
@@ -3934,74 +3088,6 @@ packet LeSetPrivacyModeComplete : CommandComplete (command_op_code = LE_SET_PRIV
status : ErrorCode,
}
-packet LeSetPeriodicAdvertisingReceiveEnable : Command (op_code = LE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE) {
- sync_handle : 12,
- _reserved_ : 4,
- enable : 8,
-}
-
-packet LeSetPeriodicAdvertisingReceiveEnableComplete : CommandComplete (command_op_code = LE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE) {
- status : ErrorCode,
-}
-
-packet LePeriodicAdvertisingSyncTransfer : Command (op_code = LE_PERIODIC_ADVERTISING_SYNC_TRANSFER) {
- connection_handle : 12,
- _reserved_ : 4,
- service_data : 16,
- sync_handle: 12,
- _reserved_ : 4,
-}
-
-packet LePeriodicAdvertisingSyncTransferComplete : CommandComplete (command_op_code = LE_PERIODIC_ADVERTISING_SYNC_TRANSFER) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LePeriodicAdvertisingSetInfoTransfer : Command (op_code = LE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER) {
- connection_handle : 12,
- _reserved_ : 4,
- service_data : 16,
- advertising_handle: 8,
-}
-
-packet LePeriodicAdvertisingSetInfoTransferComplete : CommandComplete (command_op_code = LE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-enum SyncTransferMode : 8 {
- NO_SYNC = 0,
- SEND_SYNC_RECEIVED_DISABLE_REPORTS = 1,
- SEND_SYNC_RECEIVED_SEND_REPORTS = 2,
-}
-
-packet LeSetPeriodicAdvertisingSyncTransferParameters : Command (op_code = LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS) {
- connection_handle : 12,
- _reserved_ : 4,
- mode : SyncTransferMode,
- skip: 16,
- sync_timeout : 16,
- cte_type : 8,
-}
-
-packet LeSetPeriodicAdvertisingSyncTransferParametersComplete : CommandComplete (command_op_code = LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LeSetDefaultPeriodicAdvertisingSyncTransferParameters : Command (op_code = LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS) {
- mode : SyncTransferMode,
- skip: 16,
- sync_timeout : 16,
- cte_type : 8,
-}
-
-packet LeSetDefaultPeriodicAdvertisingSyncTransferParametersComplete : CommandComplete (command_op_code = LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMETERS) {
-}
-
enum UseDebugKey : 8 {
USE_GENERATED_KEY = 0,
USE_DEBUG_KEY = 1,
@@ -4015,367 +3101,10 @@ packet LeGenerateDhkeyCommand : LeSecurityCommand (op_code = LE_GENERATE_DHKEY_C
packet LeGenerateDhkeyCommandStatus : CommandStatus (command_op_code = LE_GENERATE_DHKEY_COMMAND) {
}
-enum ScaAction : 8 {
- MORE_ACCURATE_CLOCK = 0,
- LESS_ACCURATE_CLOCK = 1,
-}
-
-packet LeModifySleepClockAccuracy : Command (op_code = LE_MODIFY_SLEEP_CLOCK_ACCURACY) {
- action : ScaAction,
-}
-
-packet LeModifySleepClockAccuracyComplete : CommandComplete (command_op_code = LE_MODIFY_SLEEP_CLOCK_ACCURACY) {
- status : ErrorCode,
-}
-
-packet LeReadBufferSizeV2 : Command (op_code = LE_READ_BUFFER_SIZE_V2) {
-}
-
-packet LeReadBufferSizeV2Complete : CommandComplete (command_op_code = LE_READ_BUFFER_SIZE_V2) {
- status : ErrorCode,
- le_buffer_size : LeBufferSize,
- iso_buffer_size : LeBufferSize,
-}
-
-packet LeReadIsoTxSync : LeIsoCommand (op_code = LE_READ_ISO_TX_SYNC) {
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LeReadIsoTxSyncComplete : CommandComplete (command_op_code = LE_READ_ISO_TX_SYNC) {
- connection_handle : 12,
- _reserved_ : 4,
- packet_sequence_number : 16,
- timestamp : 32,
- time_offset : 24,
-}
-
-struct CisParametersConfig {
- cis_id : 8,
- max_sdu_m_to_s : 12,
- _reserved_ : 4,
- max_sdu_s_to_m : 12,
- _reserved_ : 4,
- phy_m_to_s : 3,
- _reserved_ : 5,
- phy_s_to_m : 3,
- _reserved_ : 5,
- rtn_m_to_s : 4,
- _reserved_ : 4,
- rtn_s_to_m : 4,
- _reserved_ : 4,
-}
-
-enum Packing : 8 {
- SEQUENTIAL = 0,
- INTERLEAVED = 1,
-}
-
-enum ClockAccuracy : 8 {
- PPM_500 = 0x00,
- PPM_250 = 0x01,
- PPM_150 = 0x02,
- PPM_100 = 0x03,
- PPM_75 = 0x04,
- PPM_50 = 0x05,
- PPM_30 = 0x06,
- PPM_20 = 0x07,
-}
-
-packet LeSetCigParameters : LeIsoCommand (op_code = LE_SET_CIG_PARAMETERS) {
- cig_id : 8,
- sdu_interval_m_to_s : 24,
- sdu_interval_s_to_m : 24,
- peripherals_clock_accuracy : ClockAccuracy,
- packing : Packing,
- framing : Enable,
- max_transport_latency_m_to_s : 16,
- max_transport_latency_s_to_m : 16,
- _count_(cis_config) : 8,
- cis_config : CisParametersConfig[],
-}
-
-packet LeSetCigParametersComplete : CommandComplete (command_op_code = LE_SET_CIG_PARAMETERS) {
- status : ErrorCode,
- cig_id : 8,
- _count_(connection_handle) : 8,
- connection_handle : 16[],
-}
-
-struct LeCisParametersTestConfig {
- cis_id : 8,
- nse : 8,
- max_sdu_m_to_s : 16,
- max_sdu_s_to_m : 16,
- max_pdu_m_to_s : 16,
- max_pdu_s_to_m : 16,
- phy_m_to_s : 8,
- phy_s_to_m : 8,
- bn_m_to_s : 8,
- bn_s_to_m : 8,
-}
-
-packet LeSetCigParametersTest : LeIsoCommand (op_code = LE_SET_CIG_PARAMETERS_TEST) {
- cig_id : 8,
- sdu_interval_m_to_s : 24,
- sdu_interval_s_to_m : 24,
- ft_m_to_s : 8,
- ft_s_to_m : 8,
- iso_interval : 16,
- peripherals_clock_accuracy : ClockAccuracy,
- packing : Packing,
- framing : Enable,
- _count_(cis_config) : 8,
- cis_config : LeCisParametersTestConfig[],
-}
-
-packet LeSetCigParametersTestComplete : CommandComplete (command_op_code = LE_SET_CIG_PARAMETERS_TEST) {
- status : ErrorCode,
- cig_id : 8,
- _count_(connection_handle) : 8,
- connection_handle : 16[],
-}
-
-struct CreateCisConfig {
- cis_connection_handle : 12,
- _reserved_ : 4,
- acl_connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LeCreateCis : LeIsoCommand (op_code = LE_CREATE_CIS) {
- _count_(cis_config) : 8,
- cis_config : CreateCisConfig[],
-}
-
-packet LeCreateCisStatus : CommandStatus (command_op_code = LE_CREATE_CIS) {
-}
-
-packet LeRemoveCig : LeIsoCommand (op_code = LE_REMOVE_CIG) {
- cig_id : 8,
-}
-
-packet LeRemoveCigComplete : CommandComplete (command_op_code = LE_REMOVE_CIG) {
- status : ErrorCode,
- cig_id : 8,
-}
-
-packet LeAcceptCisRequest : LeIsoCommand (op_code = LE_ACCEPT_CIS_REQUEST) {
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LeAcceptCisRequestStatus : CommandStatus (command_op_code = LE_ACCEPT_CIS_REQUEST) {
-}
-
-packet LeRejectCisRequest : LeIsoCommand (op_code = LE_REJECT_CIS_REQUEST) {
- connection_handle : 12,
- _reserved_ : 4,
- reason : ErrorCode,
-}
-
-packet LeRejectCisRequestComplete : CommandComplete (command_op_code = LE_REJECT_CIS_REQUEST) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LeCreateBig : LeIsoCommand (op_code = LE_CREATE_BIG) {
- big_handle : 8,
- advertising_handle : 8,
- num_bis : 8,
- sdu_interval : 24,
- max_sdu : 16,
- max_transport_latency : 16,
- rtn : 4,
- _reserved_ : 4,
- phy : SecondaryPhyType,
- packing : Packing,
- framing : Enable,
- encryption : Enable,
- broadcast_code: 16[],
-}
-
-packet LeCreateBigStatus : CommandStatus (command_op_code = LE_CREATE_BIG) {
-}
-
-packet LeTerminateBig : LeIsoCommand (op_code = LE_TERMINATE_BIG) {
- big_handle : 8,
- reason : ErrorCode,
-}
-
-packet LeTerminateBigStatus : CommandStatus (command_op_code = LE_TERMINATE_BIG) {
-}
-
-packet LeBigCreateSync : LeIsoCommand (op_code = LE_BIG_CREATE_SYNC) {
- big_handle : 8,
- sync_handle : 12,
- _reserved_ : 4,
- encryption : Enable,
- broadcast_code : 16[],
- mse : 5,
- _reserved_ : 3,
- big_sync_timeout : 16,
- _count_(bis) : 8,
- bis : 8[],
-}
-
-packet LeBigCreateSyncStatus : CommandStatus (command_op_code = LE_BIG_CREATE_SYNC) {
-}
-
-packet LeBigTerminateSync : LeIsoCommand (op_code = LE_BIG_TERMINATE_SYNC) {
- big_handle : 8,
-}
-
-packet LeBigTerminateSyncComplete : CommandComplete (command_op_code = LE_BIG_TERMINATE_SYNC) {
- status : ErrorCode,
- big_handle : 8,
-}
-
-packet LeRequestPeerSca : Command (op_code = LE_REQUEST_PEER_SCA) {
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LeRequestPeerScaStatus : CommandStatus (command_op_code = LE_REQUEST_PEER_SCA) {
-}
-
-packet LeSetupIsoDataPath : LeIsoCommand (op_code = LE_SETUP_ISO_DATA_PATH) {
- connection_handle : 12,
- _reserved_ : 4,
- data_path_direction : DataPathDirection,
- data_path_id : 8,
- codec_id : 40,
- controller_delay : 24,
- _count_(codec_configuration) : 8,
- codec_configuration : 8[],
-}
-
-packet LeSetupIsoDataPathComplete : CommandComplete (command_op_code = LE_SETUP_ISO_DATA_PATH) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LeRemoveIsoDataPath : LeIsoCommand (op_code = LE_REMOVE_ISO_DATA_PATH) {
- connection_handle : 12,
- _reserved_ : 4,
- data_path_direction : DataPathDirection,
-}
-
-packet LeRemoveIsoDataPathComplete : CommandComplete (command_op_code = LE_REMOVE_ISO_DATA_PATH) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LeSetHostFeature : Command (op_code = LE_SET_HOST_FEATURE) {
- bit_number : 8,
- bit_value: Enable,
-}
-
-packet LeSetHostFeatureComplete : CommandComplete (command_op_code = LE_SET_HOST_FEATURE) {
- status : ErrorCode,
-}
-
-packet LeReadIsoLinkQuality : LeIsoCommand (op_code = LE_READ_ISO_LINK_QUALITY) {
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LeReadIsoLinkQualityComplete : CommandComplete (command_op_code = LE_READ_ISO_LINK_QUALITY) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
- tx_unacked_packets : 32,
- tx_flushed_packets : 32,
- tx_last_subevent_packets : 32,
- retransmitted_packets : 32,
- crc_error_packets : 32,
- rx_unreceived_packets : 32,
- duplicate_packets : 32,
-}
-
-packet LeEnhancedReadTransmitPowerLevel : Command (op_code = LE_ENHANCED_READ_TRANSMIT_POWER_LEVEL) {
- connection_handle : 12,
- _reserved_ : 4,
- phy : 8,
-}
-
-enum PhyWithCodedSpecified : 8 {
- LE_1M = 1,
- LE_2M = 2,
- LE_CODED_S_8 = 3,
- LE_CODED_S_2 = 4,
-}
-
-packet LeEnhancedReadTransmitPowerLevelComplete : CommandComplete (command_op_code = LE_ENHANCED_READ_TRANSMIT_POWER_LEVEL) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
- phy : PhyWithCodedSpecified,
- current_transmit_power_level : 8,
- max_transmit_power_level : 8,
-}
-
-packet LeReadRemoteTransmitPowerLevel : Command (op_code = LE_READ_REMOTE_TRANSMIT_POWER_LEVEL) {
- connection_handle : 12,
- _reserved_ : 4,
- phy : 8,
-}
-
-packet LeReadRemoteTransmitPowerLevelStatus : CommandStatus (command_op_code = LE_READ_REMOTE_TRANSMIT_POWER_LEVEL) {
-}
-
-packet LeSetPathLossReportingParameters : Command (op_code = LE_SET_PATH_LOSS_REPORTING_PARAMETERS) {
- connection_handle : 12,
- _reserved_ : 4,
- high_threshold : 8,
- high_hysteresis : 8,
- low_threshold : 8,
- low_hysteresis : 8,
- min_time_spent : 16,
-}
-
-packet LeSetPathLossReportingParametersComplete : CommandComplete (command_op_code = LE_SET_PATH_LOSS_REPORTING_PARAMETERS) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LeSetPathLossReportingEnable : Command (op_code = LE_SET_PATH_LOSS_REPORTING_ENABLE) {
- connection_handle : 12,
- _reserved_ : 4,
- enable : 8,
-}
-
-packet LeSetPathLossReportingEnableComplete : CommandComplete (command_op_code = LE_SET_PATH_LOSS_REPORTING_ENABLE) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet LeSetTransmitPowerReportingEnable : Command (op_code = LE_SET_TRANSMIT_POWER_REPORTING_ENABLE) {
- connection_handle : 12,
- _reserved_ : 4,
- local_enable : 8,
- remote_enable : 8,
-}
-
-packet LeSetTransmitPowerReportingEnableComplete : CommandComplete (command_op_code = LE_SET_TRANSMIT_POWER_REPORTING_ENABLE) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
-}
-
// VENDOR_SPECIFIC
packet LeGetVendorCapabilities : VendorCommand (op_code = LE_GET_VENDOR_CAPABILITIES) {
}
-test LeGetVendorCapabilities {
- "\x53\xfd\x00",
-}
-
struct VendorCapabilities {
is_supported : 8,
max_advt_instances: 8,
@@ -4409,7 +3138,6 @@ packet LeGetVendorCapabilitiesComplete : CommandComplete (command_op_code = LE_G
base_vendor_capabilities : BaseVendorCapabilities,
_payload_,
}
-
packet LeGetVendorCapabilitiesComplete095 : LeGetVendorCapabilitiesComplete {
version_supported: 16,
total_num_of_advt_tracked: 16,
@@ -4417,7 +3145,6 @@ packet LeGetVendorCapabilitiesComplete095 : LeGetVendorCapabilitiesComplete {
debug_logging_supported: 8,
_payload_,
}
-
packet LeGetVendorCapabilitiesComplete096 : LeGetVendorCapabilitiesComplete095 {
le_address_generation_offloading_support: 8,
_payload_,
@@ -4449,8 +3176,8 @@ packet LeMultiAdvtComplete : CommandComplete (command_op_code = LE_MULTI_ADVT) {
packet LeMultiAdvtParam : LeMultiAdvt (sub_cmd = SET_PARAM) {
interval_min : 16,
interval_max : 16,
- advt_type : AdvertisingType,
- own_address_type : OwnAddressType,
+ type : AdvertisingEventType,
+ own_address_type : AddressType,
peer_address_type : PeerAddressType,
peer_address : Address,
channel_map : 8,
@@ -4466,7 +3193,7 @@ packet LeMultiAdvtParamComplete : LeMultiAdvtComplete (sub_cmd = SET_PARAM) {
packet LeMultiAdvtSetData : LeMultiAdvt (sub_cmd = SET_DATA) {
_size_(advertising_data) : 8,
advertising_data : GapData[],
- _padding_[31], // Zero padding to 31 bytes of advertising_data
+ _padding_[36], // Zero padding to 31 bytes of advertising_data + 1 size + 2 opcode + 1 total_size + 1 set
advertising_instance : 8,
}
@@ -4476,7 +3203,7 @@ packet LeMultiAdvtSetDataComplete : LeMultiAdvtComplete (sub_cmd = SET_DATA) {
packet LeMultiAdvtSetScanResp : LeMultiAdvt (sub_cmd = SET_SCAN_RESP) {
_size_(advertising_data) : 8,
advertising_data : GapData[],
- _padding_[31], // Zero padding to 31 bytes of advertising_data
+ _padding_[36], // Zero padding to 31 bytes of advertising_data + 1 size + 2 opcode + 1 total_size + 1 set
advertising_instance : 8,
}
@@ -4499,107 +3226,8 @@ packet LeMultiAdvtSetEnable : LeMultiAdvt (sub_cmd = SET_ENABLE) {
packet LeMultiAdvtSetEnableComplete : LeMultiAdvtComplete (sub_cmd = SET_ENABLE) {
}
-enum BatchScanOpcode : 8 {
- ENABLE = 0x01,
- SET_STORAGE_PARAMETERS = 0x02,
- SET_SCAN_PARAMETERS = 0x03,
- READ_RESULT_PARAMETERS = 0x04,
-}
-
-// https://source.android.com/devices/bluetooth/hci_requirements#batching-of-scan-results
-packet LeBatchScan : LeScanningCommand (op_code = LE_BATCH_SCAN) {
- batch_scan_opcode : BatchScanOpcode,
- _body_,
-}
-
-packet LeBatchScanComplete : CommandComplete (command_op_code = LE_BATCH_SCAN) {
- status : ErrorCode,
- batch_scan_opcode : BatchScanOpcode,
- _body_,
-}
-
-packet LeBatchScanEnable : LeBatchScan (batch_scan_opcode = ENABLE) {
- enable : Enable,
-}
-
-packet LeBatchScanEnableComplete : LeBatchScanComplete (batch_scan_opcode = ENABLE) {
-}
-
-packet LeBatchScanSetStorageParameters : LeBatchScan (batch_scan_opcode = SET_STORAGE_PARAMETERS) {
- batch_scan_full_max_percentage : 8,
- batch_scan_truncated_max_percentage : 8,
- batch_scan_notify_threshold_percentage : 8,
-}
-
-packet LeBatchScanSetStorageParametersComplete : LeBatchScanComplete (batch_scan_opcode = SET_STORAGE_PARAMETERS) {
-}
-
-enum BatchScanDiscardRule : 8 {
- OLDEST = 0x00,
- WEAKEST_RSSI = 0x01,
-}
-
-packet LeBatchScanSetScanParameters : LeBatchScan (batch_scan_opcode = SET_SCAN_PARAMETERS) {
- truncated_mode_enabled : 1,
- full_mode_enabled : 1,
- _reserved_ : 6,
- duty_cycle_scan_window_slots : 32,
- duty_cycle_scan_interval_slots : 32,
- own_address_type : AdvertisingAddressType,
- batch_scan_discard_rule : BatchScanDiscardRule,
-}
-
-packet LeBatchScanSetScanParametersComplete : LeBatchScanComplete (batch_scan_opcode = SET_SCAN_PARAMETERS) {
-}
-
-enum BatchScanDataRead : 8 {
- TRUNCATED_MODE_DATA = 0x01,
- FULL_MODE_DATA = 0x02,
-}
-
-packet LeBatchScanReadResultParameters : LeBatchScan (batch_scan_opcode = READ_RESULT_PARAMETERS) {
- batch_scan_data_read : BatchScanDataRead,
-}
-
-packet LeBatchScanReadResultParametersCompleteRaw : LeBatchScanComplete (batch_scan_opcode = READ_RESULT_PARAMETERS) {
- batch_scan_data_read : BatchScanDataRead,
- num_of_records : 8,
- raw_data : 8[],
-}
-
-packet LeBatchScanReadResultParametersComplete : LeBatchScanComplete (batch_scan_opcode = READ_RESULT_PARAMETERS) {
- batch_scan_data_read : BatchScanDataRead,
- _body_,
-}
-
-struct TruncatedResult {
- bd_addr : Address,
- address_type : AddressType,
- tx_power : 8,
- rssi : 8,
- timestamp : 16,
-}
-
-packet LeBatchScanReadTruncatedResultParametersComplete : LeBatchScanReadResultParametersComplete (batch_scan_data_read = TRUNCATED_MODE_DATA) {
- _count_(results) : 8,
- results : TruncatedResult[],
-}
-
-struct FullResult {
- bd_addr : Address,
- address_type : AddressType,
- tx_power : 8,
- rssi : 8,
- timestamp : 16,
- _size_(adv_packet) : 8,
- adv_packet : 8[],
- _size_(scan_response) : 8,
- scan_response : 8[],
-}
-
-packet LeBatchScanReadFullResultParametersComplete : LeBatchScanReadResultParametersComplete (batch_scan_data_read = FULL_MODE_DATA) {
- _count_(results) : 8,
- results : FullResult[],
+packet LeBatchScan : VendorCommand (op_code = LE_BATCH_SCAN) {
+ _payload_, // placeholder (unimplemented)
}
enum ApcfOpcode : 8 {
@@ -4613,7 +3241,6 @@ enum ApcfOpcode : 8 {
SERVICE_DATA = 0x07,
}
-// https://source.android.com/devices/bluetooth/hci_requirements#advertising-packet-content-filter
packet LeAdvFilter : LeScanningCommand (op_code = LE_ADV_FILTER) {
apcf_opcode : ApcfOpcode,
_body_,
@@ -4622,167 +3249,22 @@ packet LeAdvFilter : LeScanningCommand (op_code = LE_ADV_FILTER) {
packet LeAdvFilterComplete : CommandComplete (command_op_code = LE_ADV_FILTER) {
status : ErrorCode,
apcf_opcode : ApcfOpcode,
- _body_,
-}
-
-packet LeAdvFilterEnable : LeAdvFilter (apcf_opcode = ENABLE) {
- apcf_enable : Enable,
-}
-
-packet LeAdvFilterEnableComplete : LeAdvFilterComplete (apcf_opcode = ENABLE) {
- apcf_enable : Enable,
-}
-
-enum ApcfAction : 8 {
- ADD = 0x00,
- DELETE = 0x01,
- CLEAR = 0x02,
-}
-
-enum DeliveryMode : 8 {
- IMMEDIATE = 0x00,
- ONFOUND = 0x01,
- BATCHED = 0x02,
-}
-
-// Bit masks for the selected features
-enum ApcfFilterType : 8 {
- BROADCASTER_ADDRESS = 0x00,
- SERVICE_DATA_CHANGE = 0x01,
- SERVICE_UUID = 0x02,
- SERVICE_SOLICITATION_UUID = 0x03,
- LOCAL_NAME = 0x04,
- MANUFACTURER_DATA = 0x05,
- SERVICE_DATA = 0x06,
-}
-
-packet LeAdvFilterSetFilteringParameters : LeAdvFilter (apcf_opcode = SET_FILTERING_PARAMETERS) {
- apcf_action : ApcfAction,
- _body_,
-}
-
-packet LeAdvFilterAddFilteringParameters : LeAdvFilterSetFilteringParameters (apcf_action = ADD) {
- apcf_filter_index : 8,
- apcf_feature_selection : 16,
- apcf_list_logic_type : 16,
- apcf_filter_logic_type : 8,
- rssi_high_thresh : 8,
- delivery_mode : DeliveryMode,
- onfound_timeout : 16,
- onfound_timeout_cnt : 8,
- rssi_low_thresh : 8,
- onlost_timeout : 16,
- num_of_tracking_entries : 16,
-}
-
-packet LeAdvFilterDeleteFilteringParameters : LeAdvFilterSetFilteringParameters (apcf_action = DELETE) {
- apcf_filter_index : 8,
-}
-
-packet LeAdvFilterClearFilteringParameters : LeAdvFilterSetFilteringParameters (apcf_action = CLEAR) {
-}
-
-packet LeAdvFilterSetFilteringParametersComplete : LeAdvFilterComplete (apcf_opcode = SET_FILTERING_PARAMETERS) {
- apcf_action : ApcfAction,
- apcf_available_spaces : 8,
-}
-
-enum ApcfApplicationAddressType : 8 {
- PUBLIC = 0x00,
- RANDOM = 0x01,
- NOT_APPLICABLE = 0x02,
-}
-
-packet LeAdvFilterBroadcasterAddress : LeAdvFilter (apcf_opcode = BROADCASTER_ADDRESS) {
- apcf_action : ApcfAction,
- apcf_filter_index : 8,
- apcf_broadcaster_address : Address,
- apcf_application_address_type : ApcfApplicationAddressType,
-}
-
-packet LeAdvFilterClearBroadcasterAddress : LeAdvFilter (apcf_opcode = BROADCASTER_ADDRESS) {
- _fixed_ = 0x02 : 8,
- apcf_filter_index : 8,
-}
-
-packet LeAdvFilterBroadcasterAddressComplete : LeAdvFilterComplete (apcf_opcode = BROADCASTER_ADDRESS) {
- apcf_action : ApcfAction,
- apcf_available_spaces : 8,
-}
-
-
-packet LeAdvFilterServiceUuid : LeAdvFilter (apcf_opcode = SERVICE_UUID) {
- apcf_action : ApcfAction,
- apcf_filter_index : 8,
- acpf_uuid_data : 8[],
-}
-
-packet LeAdvFilterServiceUuidComplete : LeAdvFilterComplete (apcf_opcode = SERVICE_UUID) {
- apcf_action : ApcfAction,
- apcf_available_spaces : 8,
-}
-
-packet LeAdvFilterSolicitationUuid : LeAdvFilter (apcf_opcode = SERVICE_SOLICITATION_UUID) {
- apcf_action : ApcfAction,
- apcf_filter_index : 8,
- acpf_uuid_data : 8[],
-}
-
-packet LeAdvFilterSolicitationUuidComplete : LeAdvFilterComplete (apcf_opcode = SERVICE_SOLICITATION_UUID) {
- apcf_action : ApcfAction,
- apcf_available_spaces : 8,
-}
-
-packet LeAdvFilterLocalName : LeAdvFilter (apcf_opcode = LOCAL_NAME) {
- apcf_action : ApcfAction,
- apcf_filter_index : 8,
- apcf_local_name : 8[],
-}
-
-packet LeAdvFilterLocalNameComplete : LeAdvFilterComplete (apcf_opcode = LOCAL_NAME) {
- apcf_action : ApcfAction,
- apcf_available_spaces : 8,
}
-packet LeAdvFilterManufacturerData : LeAdvFilter (apcf_opcode = MANUFACTURER_DATA) {
- apcf_action : ApcfAction,
- apcf_filter_index : 8,
- apcf_manufacturer_data : 8[],
-}
-
-packet LeAdvFilterManufacturerDataComplete : LeAdvFilterComplete (apcf_opcode = MANUFACTURER_DATA) {
- apcf_action : ApcfAction,
- apcf_available_spaces : 8,
-}
-
-packet LeAdvFilterServiceData : LeAdvFilter (apcf_opcode = SERVICE_DATA) {
- apcf_action : ApcfAction,
- apcf_filter_index : 8,
- apcf_service_data : 8[],
-}
-
-packet LeAdvFilterServiceDataComplete : LeAdvFilterComplete (apcf_opcode = SERVICE_DATA) {
- apcf_action : ApcfAction,
- apcf_available_spaces : 8,
+packet LeTrackAdv : VendorCommand (op_code = LE_TRACK_ADV) {
+ _payload_, // placeholder (unimplemented)
}
packet LeEnergyInfo : VendorCommand (op_code = LE_ENERGY_INFO) {
-}
-
-packet LeEnergyInfoComplete : CommandComplete (command_op_code = LE_ENERGY_INFO) {
- status : ErrorCode,
- total_tx_time_ms : 32,
- total_rx_time_ms : 32,
- total_idle_time_ms : 32,
- total_energy_used_ma_v_ms : 32,
+ _payload_, // placeholder (unimplemented)
}
packet LeExtendedScanParams : LeScanningCommand (op_code = LE_EXTENDED_SCAN_PARAMS) {
le_scan_type : LeScanType,
le_scan_interval : 32, // 0x0004-0x4000 Default 0x10 (10ms)
le_scan_window : 32, // Default 0x10 (10ms)
- own_address_type : OwnAddressType,
- scanning_filter_policy : LeScanningFilterPolicy,
+ own_address_type : AddressType,
+ scanning_filter_policy : LeSetScanningFilterPolicy,
}
packet LeExtendedScanParamsComplete : CommandComplete (command_op_code = LE_EXTENDED_SCAN_PARAMS) {
@@ -4790,17 +3272,10 @@ packet LeExtendedScanParamsComplete : CommandComplete (command_op_code = LE_EXTE
}
packet ControllerDebugInfo : VendorCommand (op_code = CONTROLLER_DEBUG_INFO) {
-}
-
-packet ControllerDebugInfoComplete : CommandComplete (command_op_code = CONTROLLER_DEBUG_INFO) {
- status : ErrorCode,
-}
-
-packet ControllerA2DPOpcode : VendorCommand (op_code = CONTROLLER_A2DP_OPCODE) {
_payload_, // placeholder (unimplemented)
}
-packet ControllerA2DPOpcodeComplete : CommandComplete (command_op_code = CONTROLLER_A2DP_OPCODE) {
+packet ControllerA2DPOpcode : VendorCommand (op_code = CONTROLLER_A2DP_OPCODE) {
_payload_, // placeholder (unimplemented)
}
@@ -4816,22 +3291,14 @@ packet ControllerBqr : VendorCommand(op_code = CONTROLLER_BQR) {
bqr_minimum_report_interval : 16,
}
-test ControllerBqr {
- "\x5e\xfd\x07\x00\x1f\x00\x07\x00\x88\x13",
-}
-
packet ControllerBqrComplete : CommandComplete (command_op_code = CONTROLLER_BQR) {
status : ErrorCode,
current_quality_event_mask : 32
}
-test ControllerBqrComplete {
- "\x0e\x08\x01\x5e\xfd\x00\x1f\x00\x07\x00",
-}
-
// HCI Event Packets
-packet InquiryComplete : Event (event_code = INQUIRY_COMPLETE) {
+packet InquiryComplete : EventPacket (event_code = INQUIRY_COMPLETE){
status : ErrorCode,
}
@@ -4845,7 +3312,7 @@ struct InquiryResult {
_reserved_ : 1,
}
-packet InquiryResult : Event (event_code = INQUIRY_RESULT) {
+packet InquiryResult : EventPacket (event_code = INQUIRY_RESULT){
_count_(inquiry_results) : 8,
inquiry_results : InquiryResult[],
}
@@ -4855,7 +3322,7 @@ enum LinkType : 8 {
ACL = 0x01,
}
-packet ConnectionComplete : Event (event_code = CONNECTION_COMPLETE) {
+packet ConnectionComplete : EventPacket (event_code = CONNECTION_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
@@ -4865,32 +3332,31 @@ packet ConnectionComplete : Event (event_code = CONNECTION_COMPLETE) {
}
enum ConnectionRequestLinkType : 8 {
- UNKNOWN = 0xFF,
SCO = 0x00,
ACL = 0x01,
ESCO = 0x02,
}
-packet ConnectionRequest : Event (event_code = CONNECTION_REQUEST) {
+packet ConnectionRequest : EventPacket (event_code = CONNECTION_REQUEST){
bd_addr : Address,
class_of_device : ClassOfDevice,
link_type : ConnectionRequestLinkType,
}
-packet DisconnectionComplete : Event (event_code = DISCONNECTION_COMPLETE) {
+packet DisconnectionComplete : EventPacket (event_code = DISCONNECTION_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
reason : ErrorCode,
}
-packet AuthenticationComplete : Event (event_code = AUTHENTICATION_COMPLETE) {
+packet AuthenticationComplete : EventPacket (event_code = AUTHENTICATION_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
}
-packet RemoteNameRequestComplete : Event (event_code = REMOTE_NAME_REQUEST_COMPLETE) {
+packet RemoteNameRequestComplete : EventPacket (event_code = REMOTE_NAME_REQUEST_COMPLETE){
status : ErrorCode,
bd_addr : Address,
remote_name : 8[248], // UTF-8 encoded user-friendly descriptive name
@@ -4902,34 +3368,34 @@ enum EncryptionEnabled : 8 {
BR_EDR_AES_CCM = 0x02,
}
-packet EncryptionChange : Event (event_code = ENCRYPTION_CHANGE) {
+packet EncryptionChange : EventPacket (event_code = ENCRYPTION_CHANGE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
encryption_enabled : EncryptionEnabled,
}
-packet ChangeConnectionLinkKeyComplete : Event (event_code = CHANGE_CONNECTION_LINK_KEY_COMPLETE) {
+packet ChangeConnectionLinkKeyComplete : EventPacket (event_code = CHANGE_CONNECTION_LINK_KEY_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
}
-packet CentralLinkKeyComplete : Event (event_code = CENTRAL_LINK_KEY_COMPLETE) {
+packet MasterLinkKeyComplete : EventPacket (event_code = MASTER_LINK_KEY_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
key_flag : KeyFlag,
}
-packet ReadRemoteSupportedFeaturesComplete : Event (event_code = READ_REMOTE_SUPPORTED_FEATURES_COMPLETE) {
+packet ReadRemoteSupportedFeaturesComplete : EventPacket (event_code = READ_REMOTE_SUPPORTED_FEATURES_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
lmp_features : 64,
}
-packet ReadRemoteVersionInformationComplete : Event (event_code = READ_REMOTE_VERSION_INFORMATION_COMPLETE) {
+packet ReadRemoteVersionInformationComplete : EventPacket (event_code = READ_REMOTE_VERSION_INFORMATION_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
@@ -4938,7 +3404,7 @@ packet ReadRemoteVersionInformationComplete : Event (event_code = READ_REMOTE_VE
sub_version : 16,
}
-packet QosSetupComplete : Event (event_code = QOS_SETUP_COMPLETE) {
+packet QosSetupComplete : EventPacket (event_code = QOS_SETUP_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
@@ -4952,22 +3418,22 @@ packet QosSetupComplete : Event (event_code = QOS_SETUP_COMPLETE) {
// Command Complete and Command Status Events are implemented above Commands.
-packet HardwareError : Event (event_code = HARDWARE_ERROR) {
+packet HardwareError : EventPacket (event_code = HARDWARE_ERROR){
hardware_code : 8,
}
-packet FlushOccurred : Event (event_code = FLUSH_OCCURRED) {
+packet FlushOccurred : EventPacket (event_code = FLUSH_OCCURRED){
connection_handle : 12,
_reserved_ : 4,
}
-packet RoleChange : Event (event_code = ROLE_CHANGE) {
+packet RoleChange : EventPacket (event_code = ROLE_CHANGE){
status : ErrorCode,
bd_addr : Address,
new_role : Role,
}
-packet NumberOfCompletedPackets : Event (event_code = NUMBER_OF_COMPLETED_PACKETS) {
+packet NumberOfCompletedPackets : EventPacket (event_code = NUMBER_OF_COMPLETED_PACKETS){
_count_(completed_packets) : 8,
completed_packets : CompletedPackets[],
}
@@ -4978,7 +3444,7 @@ enum Mode : 8 {
SNIFF = 0x02,
}
-packet ModeChange : Event (event_code = MODE_CHANGE) {
+packet ModeChange : EventPacket (event_code = MODE_CHANGE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
@@ -4992,16 +3458,16 @@ struct ZeroKeyAndAddress {
_fixed_ = 0 : 64,
}
-packet ReturnLinkKeys : Event (event_code = RETURN_LINK_KEYS) {
+packet ReturnLinkKeys : EventPacket (event_code = RETURN_LINK_KEYS){
_count_(keys) : 8,
keys : ZeroKeyAndAddress[],
}
-packet PinCodeRequest : Event (event_code = PIN_CODE_REQUEST) {
+packet PinCodeRequest : EventPacket (event_code = PIN_CODE_REQUEST){
bd_addr : Address,
}
-packet LinkKeyRequest : Event (event_code = LINK_KEY_REQUEST) {
+packet LinkKeyRequest : EventPacket (event_code = LINK_KEY_REQUEST){
bd_addr : Address,
}
@@ -5015,27 +3481,27 @@ enum KeyType : 8 {
AUTHENTICATED_P256 = 0x08,
}
-packet LinkKeyNotification : Event (event_code = LINK_KEY_NOTIFICATION) {
+packet LinkKeyNotification : EventPacket (event_code = LINK_KEY_NOTIFICATION){
bd_addr : Address,
link_key : 8[16],
key_type : KeyType,
}
-packet LoopbackCommand : Event (event_code = LOOPBACK_COMMAND) {
+packet LoopbackCommand : EventPacket (event_code = LOOPBACK_COMMAND){
_payload_, // Command packet, truncated if it was longer than 252 bytes
}
-packet DataBufferOverflow : Event (event_code = DATA_BUFFER_OVERFLOW) {
+packet DataBufferOverflow : EventPacket (event_code = DATA_BUFFER_OVERFLOW){
link_type : LinkType,
}
-packet MaxSlotsChange : Event (event_code = MAX_SLOTS_CHANGE) {
+packet MaxSlotsChange : EventPacket (event_code = MAX_SLOTS_CHANGE){
connection_handle : 12,
_reserved_ : 4,
lmp_max_slots : 8,
}
-packet ReadClockOffsetComplete : Event (event_code = READ_CLOCK_OFFSET_COMPLETE) {
+packet ReadClockOffsetComplete : EventPacket (event_code = READ_CLOCK_OFFSET_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
@@ -5043,24 +3509,22 @@ packet ReadClockOffsetComplete : Event (event_code = READ_CLOCK_OFFSET_COMPLETE)
_reserved_ : 1,
}
-packet ConnectionPacketTypeChanged : Event (event_code = CONNECTION_PACKET_TYPE_CHANGED) {
+packet ConnectionPacketTypeChanged : EventPacket (event_code = CONNECTION_PACKET_TYPE_CHANGED){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
packet_type : 16,
}
-packet QosViolation : Event (event_code = QOS_VIOLATION) {
- connection_handle : 12,
- _reserved_ : 4,
+packet QosViolation : EventPacket (event_code = QOS_VIOLATION){
+ _payload_, // placeholder (unimplemented)
}
-packet PageScanRepetitionModeChange : Event (event_code = PAGE_SCAN_REPETITION_MODE_CHANGE) {
- bd_addr : Address,
- page_scan_repetition_mode : PageScanRepetitionMode,
+packet PageScanRepetitionModeChange : EventPacket (event_code = PAGE_SCAN_REPETITION_MODE_CHANGE){
+ _payload_, // placeholder (unimplemented)
}
-packet FlowSpecificationComplete : Event (event_code = FLOW_SPECIFICATION_COMPLETE) {
+packet FlowSpecificationComplete : EventPacket (event_code = FLOW_SPECIFICATION_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
@@ -5083,12 +3547,12 @@ struct InquiryResultWithRssi {
rssi : 8,
}
-packet InquiryResultWithRssi : Event (event_code = INQUIRY_RESULT_WITH_RSSI) {
+packet InquiryResultWithRssi : EventPacket (event_code = INQUIRY_RESULT_WITH_RSSI){
_count_(inquiry_results) : 8,
inquiry_results : InquiryResultWithRssi[],
}
-packet ReadRemoteExtendedFeaturesComplete : Event (event_code = READ_REMOTE_EXTENDED_FEATURES_COMPLETE) {
+packet ReadRemoteExtendedFeaturesComplete : EventPacket (event_code = READ_REMOTE_EXTENDED_FEATURES_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
@@ -5097,55 +3561,15 @@ packet ReadRemoteExtendedFeaturesComplete : Event (event_code = READ_REMOTE_EXTE
extended_lmp_features : 64,
}
-enum ScoLinkType : 8 {
- SCO = 0x00,
- ESCO = 0x02,
-}
-
-enum ScoAirMode : 8 {
- ULAW_LOG = 0x00,
- ALAW_LOG = 0x01,
- CVSD = 0x02,
- TRANSPARENT = 0x03,
+packet SynchronousConnectionComplete : EventPacket (event_code = SYNCHRONOUS_CONNECTION_COMPLETE){
+ _payload_, // placeholder (unimplemented)
}
-packet SynchronousConnectionComplete : Event (event_code = SYNCHRONOUS_CONNECTION_COMPLETE) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
- bd_addr : Address,
- link_type : ScoLinkType,
- // Time between two consecutive eSCO instants measured in slots.
- // eSCO only, Shall be zero for SCO links.
- transmission_interval_slots : 8,
- // The size of the retransmission window measured in slots.
- // eSCO only. Shall be zero for SCO links.
- retransmission_window_slots : 8,
- // Length in bytes of the eSCO payload in the receive direction.
- // eSCO only. Shall be zero for SCO links.
- rx_packet_length : 16,
- // Length in bytes of the eSCO payload in the transmit direction.
- // eSCO only. Shall be zero for SCO links.
- tx_packet_length : 16,
- air_mode : ScoAirMode,
-}
-
-packet SynchronousConnectionChanged : Event (event_code = SYNCHRONOUS_CONNECTION_CHANGED) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
- // Time between two consecutive eSCO instants measured in slots.
- // eSCO only, Shall be zero for SCO links.
- transmission_interval_slots : 8,
- // Time between two consecutive SCO/eSCO instants measured in slots.
- retransmission_window_slots : 8,
- // Length in bytes of the SCO/eSCO payload in the receive direction.
- rx_packet_length : 16,
- // Length in bytes of the SCO/eSCO payload in the transmit direction.
- tx_packet_length : 16,
+packet SynchronousConnectionChanged : EventPacket (event_code = SYNCHRONOUS_CONNECTION_CHANGED){
+ _payload_, // placeholder (unimplemented)
}
-packet SniffSubratingEvent : Event (event_code = SNIFF_SUBRATING) {
+packet SniffSubratingEvent : EventPacket (event_code = SNIFF_SUBRATING){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
@@ -5155,7 +3579,7 @@ packet SniffSubratingEvent : Event (event_code = SNIFF_SUBRATING) {
minimum_local_timeout : 16, // 0x000 - 0xFFFE (0s - 40.9s)
}
-packet ExtendedInquiryResult : Event (event_code = EXTENDED_INQUIRY_RESULT) {
+packet ExtendedInquiryResult : EventPacket (event_code = EXTENDED_INQUIRY_RESULT) {
_fixed_ = 0x01 : 8,
address : Address,
page_scan_repetition_mode : PageScanRepetitionMode,
@@ -5165,99 +3589,93 @@ packet ExtendedInquiryResult : Event (event_code = EXTENDED_INQUIRY_RESULT) {
_reserved_ : 1,
rssi : 8,
extended_inquiry_response : GapData[],
- // Extended inquiry Result is always 255 bytes long
- // padded GapData with zeroes as necessary
- // Refer to BLUETOOTH CORE SPECIFICATION Version 5.2 | Vol 3, Part C Section 8 on page 1340
- _padding_[240],
}
-packet EncryptionKeyRefreshComplete : Event (event_code = ENCRYPTION_KEY_REFRESH_COMPLETE) {
+packet EncryptionKeyRefreshComplete : EventPacket (event_code = ENCRYPTION_KEY_REFRESH_COMPLETE){
status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
}
-packet IoCapabilityRequest : Event (event_code = IO_CAPABILITY_REQUEST) {
+packet IoCapabilityRequest : EventPacket (event_code = IO_CAPABILITY_REQUEST){
bd_addr : Address,
}
-packet IoCapabilityResponse : Event (event_code = IO_CAPABILITY_RESPONSE) {
+packet IoCapabilityResponse : EventPacket (event_code = IO_CAPABILITY_RESPONSE){
bd_addr : Address,
io_capability : IoCapability,
oob_data_present : OobDataPresent,
authentication_requirements : AuthenticationRequirements,
}
-packet UserConfirmationRequest : Event (event_code = USER_CONFIRMATION_REQUEST) {
+packet UserConfirmationRequest : EventPacket (event_code = USER_CONFIRMATION_REQUEST){
bd_addr : Address,
numeric_value : 20, // 0x00000-0xF423F (000000 - 999999)
_reserved_ : 12,
}
-packet UserPasskeyRequest : Event (event_code = USER_PASSKEY_REQUEST) {
+packet UserPasskeyRequest : EventPacket (event_code = USER_PASSKEY_REQUEST){
bd_addr : Address,
}
-packet RemoteOobDataRequest : Event (event_code = REMOTE_OOB_DATA_REQUEST) {
+packet RemoteOobDataRequest : EventPacket (event_code = REMOTE_OOB_DATA_REQUEST){
bd_addr : Address,
}
-packet SimplePairingComplete : Event (event_code = SIMPLE_PAIRING_COMPLETE) {
+packet SimplePairingComplete : EventPacket (event_code = SIMPLE_PAIRING_COMPLETE){
status : ErrorCode,
bd_addr : Address,
}
-packet LinkSupervisionTimeoutChanged : Event (event_code = LINK_SUPERVISION_TIMEOUT_CHANGED) {
+packet LinkSupervisionTimeoutChanged : EventPacket (event_code = LINK_SUPERVISION_TIMEOUT_CHANGED){
connection_handle : 12,
_reserved_ : 4,
link_supervision_timeout : 16, // 0x001-0xFFFF (0.625ms-40.9s)
}
-enum FlushablePacketType : 8 {
- AUTOMATICALLY_FLUSHABLE_ONLY = 0,
-}
-
-packet EnhancedFlush : Command (op_code = ENHANCED_FLUSH) {
+packet EnhancedFlushComplete : EventPacket (event_code = ENHANCED_FLUSH_COMPLETE){
connection_handle : 12,
_reserved_ : 4,
- packet_type : FlushablePacketType,
}
-packet EnhancedFlushStatus : CommandStatus (command_op_code = ENHANCED_FLUSH) {
-}
-
-packet EnhancedFlushComplete : Event (event_code = ENHANCED_FLUSH_COMPLETE) {
- connection_handle : 12,
- _reserved_ : 4,
-}
-
-packet UserPasskeyNotification : Event (event_code = USER_PASSKEY_NOTIFICATION) {
+packet UserPasskeyNotification : EventPacket (event_code = USER_PASSKEY_NOTIFICATION){
bd_addr : Address,
passkey : 20, // 0x00000-0xF423F (000000 - 999999)
_reserved_ : 12,
}
-packet KeypressNotification : Event (event_code = KEYPRESS_NOTIFICATION) {
+packet KeypressNotification : EventPacket (event_code = KEYPRESS_NOTIFICATION){
bd_addr : Address,
notification_type : KeypressNotificationType,
}
-packet RemoteHostSupportedFeaturesNotification : Event (event_code = REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION) {
+packet RemoteHostSupportedFeaturesNotification : EventPacket (event_code = REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION){
bd_addr : Address,
host_supported_features : 64,
}
-packet LeMetaEvent : Event (event_code = LE_META_EVENT) {
+packet LeMetaEvent : EventPacket (event_code = LE_META_EVENT) {
subevent_code : SubeventCode,
- _body_,
+ _payload_,
}
-packet NumberOfCompletedDataBlocks : Event (event_code = NUMBER_OF_COMPLETED_DATA_BLOCKS) {
- total_num_data_blocks : 16,
+packet NumberOfCompletedDataBlocks : EventPacket (event_code = NUMBER_OF_COMPLETED_DATA_BLOCKS){
_payload_, // placeholder (unimplemented)
}
// LE Events
+
+enum MasterClockAccuracy : 8 {
+ PPM_500 = 0x00,
+ PPM_250 = 0x01,
+ PPM_150 = 0x02,
+ PPM_100 = 0x03,
+ PPM_75 = 0x04,
+ PPM_50 = 0x05,
+ PPM_30 = 0x06,
+ PPM_20 = 0x07,
+}
+
packet LeConnectionComplete : LeMetaEvent (subevent_code = CONNECTION_COMPLETE) {
status : ErrorCode,
connection_handle : 12,
@@ -5268,15 +3686,7 @@ packet LeConnectionComplete : LeMetaEvent (subevent_code = CONNECTION_COMPLETE)
conn_interval : 16, // 0x006 - 0x0C80 (7.5ms - 4000ms)
conn_latency : 16, // Number of connection events
supervision_timeout : 16, // 0x000A to 0x0C80 (100ms to 32s)
- central_clock_accuracy : ClockAccuracy,
-}
-
-enum AdvertisingEventType : 8 {
- ADV_IND = 0x00,
- ADV_DIRECT_IND = 0x01,
- ADV_SCAN_IND = 0x02,
- ADV_NONCONN_IND = 0x03,
- SCAN_RESPONSE = 0x04,
+ master_clock_accuracy : MasterClockAccuracy,
}
struct LeAdvertisingReport {
@@ -5310,9 +3720,10 @@ packet LeReadRemoteFeaturesComplete : LeMetaEvent (subevent_code = READ_REMOTE_F
}
packet LeLongTermKeyRequest : LeMetaEvent (subevent_code = LONG_TERM_KEY_REQUEST) {
+ status : ErrorCode,
connection_handle : 12,
_reserved_ : 4,
- random_number : 8[8],
+ random_number : 64,
encrypted_diversifier : 16,
}
@@ -5356,7 +3767,7 @@ packet LeEnhancedConnectionComplete : LeMetaEvent (subevent_code = ENHANCED_CONN
conn_interval : 16, // 0x006 - 0x0C80 (7.5ms - 4000ms)
conn_latency : 16, // Number of connection events
supervision_timeout : 16, // 0x000A to 0x0C80 (100ms to 32s)
- central_clock_accuracy : ClockAccuracy,
+ master_clock_accuracy : MasterClockAccuracy,
}
enum DirectAdvertisingAddressType : 8 {
@@ -5391,11 +3802,7 @@ packet LeDirectedAdvertisingReport : LeMetaEvent (subevent_code = DIRECTED_ADVER
}
packet LePhyUpdateComplete : LeMetaEvent (subevent_code = PHY_UPDATE_COMPLETE) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
- tx_phy : 8,
- rx_phy : 8,
+ _payload_, // placeholder (unimplemented)
}
enum DataStatus : 2 {
@@ -5410,21 +3817,21 @@ struct LeExtendedAdvertisingReport {
scannable : 1,
directed : 1,
scan_response : 1,
- legacy : 1,
data_status : DataStatus,
- _reserved_ : 9,
+ _reserved_ : 10,
address_type : DirectAdvertisingAddressType,
address : Address,
primary_phy : PrimaryPhyType,
secondary_phy : SecondaryPhyType,
- advertising_sid : 8, // SID subfield in the ADI field
+ advertising_sid : 4, // SID subfield in the ADI field
+ _reserved_ : 4,
tx_power : 8,
rssi : 8, // -127 to +20 (0x7F means not available)
periodic_advertising_interval : 16, // 0x006 to 0xFFFF (7.5 ms to 82s)
direct_address_type : DirectAdvertisingAddressType,
direct_address : Address,
_size_(advertising_data) : 8,
- advertising_data : 8[],
+ advertising_data : GapData[],
}
packet LeExtendedAdvertisingReport : LeMetaEvent (subevent_code = EXTENDED_ADVERTISING_REPORT) {
@@ -5461,201 +3868,14 @@ packet LeScanRequestReceived : LeMetaEvent (subevent_code = SCAN_REQUEST_RECEIVE
scanner_address : Address,
}
-enum ChannelSelectionAlgorithm : 8 {
- ALGORITHM_1 = 0,
- ALGORITHM_2 = 1,
-}
-
-packet LeChannelSelectionAlgorithm : LeMetaEvent (subevent_code = CHANNEL_SELECTION_ALGORITHM) {
- connection_handle : 12,
- _reserved_ : 4,
- channel_selection_algorithm : ChannelSelectionAlgorithm,
-}
-
-packet LeConnectionlessIqReport : LeMetaEvent (subevent_code = CONNECTIONLESS_IQ_REPORT) {
- _payload_, // placeholder (unimplemented)
-}
-
-packet LeConnectionIqReport : LeMetaEvent (subevent_code = CONNECTION_IQ_REPORT) {
- _payload_, // placeholder (unimplemented)
-}
-
-packet LeCteRequestFailed : LeMetaEvent (subevent_code = CTE_REQUEST_FAILED) {
- _payload_, // placeholder (unimplemented)
-}
-
-packet LePeriodicAdvertisingSyncTransferReceived : LeMetaEvent (subevent_code = PERIODIC_ADVERTISING_SYNC_TRANSFER_RECEIVED) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
- service_data : 16,
- sync_handle : 12,
- _reserved_ : 4,
- advertising_sid : 4,
- _reserved_ : 4,
- advertiser_address_type : AddressType,
- advertiser_address : Address,
- advertiser_phy : SecondaryPhyType,
- periodic_advertising_interval : 16,
- advertiser_clock_accuracy : ClockAccuracy,
-}
-
-packet LeCisEstablished : LeMetaEvent (subevent_code = CIS_ESTABLISHED) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
- cig_sync_delay : 24,
- cis_sync_delay : 24,
- transport_latency_m_to_s : 24,
- transport_latency_s_to_m : 24,
- phy_m_to_s : SecondaryPhyType,
- phy_s_to_m : SecondaryPhyType,
- nse : 8,
- bn_m_to_s : 4,
- _reserved_ : 4,
- bn_s_to_m : 4,
- _reserved_ : 4,
- ft_m_to_s : 8,
- ft_s_to_m : 8,
- max_pdu_m_to_s : 8,
- _reserved_ : 8,
- max_pdu_s_to_m : 8,
- _reserved_ : 8,
- iso_interval : 16,
-}
-
-packet LeCisRequest : LeMetaEvent (subevent_code = CIS_REQUEST) {
- acl_connection_handle : 12,
- _reserved_ : 4,
- cis_connection_handle : 12,
- _reserved_ : 4,
- cig_id : 8,
- cis_id : 8,
-}
-
-packet LeCreateBigComplete : LeMetaEvent (subevent_code = CREATE_BIG_COMPLETE) {
- status : ErrorCode,
- big_handle : 8,
- big_sync_delay : 24,
- transport_latency_big: 24,
- phy : SecondaryPhyType,
- nse : 8,
- bn : 8,
- pto : 8,
- irc : 8,
- max_pdu : 16,
- iso_interval : 16,
- _size_(connection_handle) : 8,
- connection_handle : 16[],
-}
-
-packet LeTerminateBigComplete : LeMetaEvent (subevent_code = TERMINATE_BIG_COMPLETE) {
- big_handle : 8,
- reason : ErrorCode,
-}
-
-packet LeBigSyncEstablished : LeMetaEvent (subevent_code = BIG_SYNC_ESTABLISHED) {
- status : ErrorCode,
- big_handle : 8,
- transport_latency_big : 24,
- nse : 8,
- bn : 8,
- pto : 8,
- irc : 8,
- max_pdu : 16,
- iso_interval : 16,
- _size_(connection_handle) : 8,
- connection_handle : 16[],
-}
-
-packet LeBigSyncLost : LeMetaEvent (subevent_code = BIG_SYNC_LOST) {
- big_handle : 8,
- reason : ErrorCode,
-}
-
-packet LeRequestPeerScaComplete : LeMetaEvent (subevent_code = REQUEST_PEER_SCA_COMPLETE) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
- peer_clock_accuracy : ClockAccuracy,
-}
-
-enum PathLossZone : 8 {
- LOW = 0,
- MID = 1,
- HIGH = 2,
-}
-
-packet LePathLossThreshold : LeMetaEvent (subevent_code = PATH_LOSS_THRESHOLD) {
- connection_handle : 12,
- _reserved_ : 4,
- current_path_loss : 8,
- zone_entered : PathLossZone,
-}
-
-packet LeTransmitPowerReporting : LeMetaEvent (subevent_code = TRANSMIT_POWER_REPORTING) {
- status : ErrorCode,
- connection_handle : 12,
- _reserved_ : 4,
- reason : 8,
- phy : 8,
- transmit_power_level : 8,
- transmit_power_level_flag : 8,
- delta : 8,
-}
-
-packet LeBigInfoAdvertisingReport : LeMetaEvent (subevent_code = BIG_INFO_ADVERTISING_REPORT) {
- sync_handle : 12,
- _reserved_ : 4,
- num_bis : 8,
- nse : 8,
- iso_interval : 16,
- bn : 8,
- pto : 8,
- irc : 8,
- max_pdu : 16,
- sdu_interval : 24,
- max_sdu : 16,
- phy : SecondaryPhyType,
- framing : Enable,
- encryption : Enable,
-}
-
// Vendor specific events
-packet VendorSpecificEvent : Event (event_code = VENDOR_SPECIFIC) {
+packet VendorSpecificEvent : EventPacket (event_code = VENDOR_SPECIFIC) {
subevent_code : VseSubeventCode,
_payload_,
}
-packet StorageThresholdBreachEvent : VendorSpecificEvent (subevent_code = BLE_THRESHOLD) {
-}
-
-enum AdvtInfoPresent : 8 {
- ADVT_INFO_PRESENT = 0x00,
- NO_ADVT_INFO_PRESENT = 0x01,
-}
-
-packet LEAdvertisementTrackingEvent : VendorSpecificEvent (subevent_code = BLE_TRACKING) {
- apcf_filter_index : 8,
- advertiser_state : 8,
- advt_info_present : AdvtInfoPresent,
- advertiser_address : Address,
- advertiser_address_type : 8,
- _body_,
-}
-
-packet LEAdvertisementTrackingWithInfoEvent : LEAdvertisementTrackingEvent {
- tx_power : 8,
- rssi : 8,
- timestamp : 16,
- _size_(adv_packet) : 8,
- adv_packet : 8[],
- _size_(scan_response) : 8,
- scan_response : 8[],
-}
-
-enum QualityReportId : 8 {
+enum qualityReportId : 8 {
MONITOR_MODE = 0x01,
APPROACH_LSTO = 0x02,
A2DP_AUDIO_CHOPPY = 0x03,
@@ -5667,7 +3887,7 @@ enum QualityReportId : 8 {
}
packet BqrEvent : VendorSpecificEvent (subevent_code = BQR_EVENT) {
- quality_report_id : QualityReportId,
+ quality_report_id : qualityReportId,
_payload_,
}
@@ -5764,50 +3984,3 @@ packet BqrBtSchedulingTraceEvent : BqrLogDumpEvent (quality_report_id = BT_SCHED
packet BqrControllerDbgInfoEvent : BqrLogDumpEvent (quality_report_id = CONTROLLER_DBG_INFO) {
_payload_, // vendor specific parameter
}
-
-// Isochronous Adaptation Layer
-
-enum IsoPacketBoundaryFlag : 2 {
- FIRST_FRAGMENT = 0,
- CONTINUATION_FRAGMENT = 1,
- COMPLETE_SDU = 2,
- LAST_FRAGMENT = 3,
-}
-
-enum TimeStampFlag : 1 {
- NOT_PRESENT = 0,
- PRESENT = 1,
-}
-
-packet Iso {
- connection_handle : 12,
- pb_flag : IsoPacketBoundaryFlag,
- ts_flag : TimeStampFlag,
- _reserved_ : 1,
- _size_(_payload_) : 14,
- _reserved_ : 2,
- _payload_,
-}
-
-enum IsoPacketStatusFlag : 2 {
- VALID = 0,
- POSSIBLY_INVALID = 1,
- LOST_DATA = 2,
-}
-
-packet IsoWithTimestamp : Iso (ts_flag = PRESENT) {
- time_stamp : 32,
- packet_sequence_number : 16,
- _size_(_payload_) : 12, // iso_sdu_length
- _reserved_ : 2,
- packet_status_flag : IsoPacketStatusFlag,
- _payload_,
-}
-
-packet IsoWithoutTimestamp : Iso (ts_flag = NOT_PRESENT) {
- packet_sequence_number : 16,
- _size_(_payload_) : 12, // iso_sdu_length
- _reserved_ : 2,
- packet_status_flag : IsoPacketStatusFlag,
- _payload_,
-}
diff --git a/gd/hci/hci_packets_fuzz_test.cc b/gd/hci/hci_packets_fuzz_test.cc
index 9bc428603..5ef3ef613 100644
--- a/gd/hci/hci_packets_fuzz_test.cc
+++ b/gd/hci/hci_packets_fuzz_test.cc
@@ -72,13 +72,13 @@ DEFINE_AND_REGISTER_WriteSecureConnectionsHostSupportReflectionFuzzTest(hci_pack
DEFINE_AND_REGISTER_WriteSecureConnectionsHostSupportCompleteReflectionFuzzTest(hci_packet_fuzz_tests);
-DEFINE_AND_REGISTER_LeReadConnectListSizeReflectionFuzzTest(hci_packet_fuzz_tests);
+DEFINE_AND_REGISTER_LeReadWhiteListSizeReflectionFuzzTest(hci_packet_fuzz_tests);
-DEFINE_AND_REGISTER_LeReadConnectListSizeCompleteReflectionFuzzTest(hci_packet_fuzz_tests);
+DEFINE_AND_REGISTER_LeReadWhiteListSizeCompleteReflectionFuzzTest(hci_packet_fuzz_tests);
-DEFINE_AND_REGISTER_LeReadBufferSizeV1ReflectionFuzzTest(hci_packet_fuzz_tests);
+DEFINE_AND_REGISTER_LeReadBufferSizeReflectionFuzzTest(hci_packet_fuzz_tests);
-DEFINE_AND_REGISTER_LeReadBufferSizeV1CompleteReflectionFuzzTest(hci_packet_fuzz_tests);
+DEFINE_AND_REGISTER_LeReadBufferSizeCompleteReflectionFuzzTest(hci_packet_fuzz_tests);
DEFINE_AND_REGISTER_WriteCurrentIacLapReflectionFuzzTest(hci_packet_fuzz_tests);
@@ -132,4 +132,4 @@ void RunHciPacketFuzzTest(const uint8_t* data, size_t size) {
for (auto test_function : bluetooth::hci::hci_packet_fuzz_tests) {
test_function(data, size);
}
-}
+} \ No newline at end of file
diff --git a/gd/hci/hci_packets_test.cc b/gd/hci/hci_packets_test.cc
index 999633545..02e7d707f 100644
--- a/gd/hci/hci_packets_test.cc
+++ b/gd/hci/hci_packets_test.cc
@@ -14,12 +14,13 @@
* limitations under the License.
*/
+#define PACKET_TESTING
+#include "hci/hci_packets.h"
+
#include <gtest/gtest.h>
+#include <forward_list>
#include <memory>
-#define PACKET_TESTING // Instantiate the tests in the packet files
-#include "hci/hci_packets.h"
-
#include "os/log.h"
#include "packet/bit_inserter.h"
#include "packet/raw_builder.h"
@@ -31,6 +32,168 @@ using std::vector;
namespace bluetooth {
namespace hci {
+std::vector<uint8_t> reset = {0x03, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_ResetReflectionTest(reset);
+
+std::vector<uint8_t> reset_complete = {0x0e, 0x04, 0x01, 0x03, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_ResetCompleteReflectionTest(reset_complete);
+
+std::vector<uint8_t> read_buffer_size = {0x05, 0x10, 0x00};
+DEFINE_AND_INSTANTIATE_ReadBufferSizeReflectionTest(read_buffer_size);
+
+std::vector<uint8_t> read_buffer_size_complete = {0x0e, 0x0b, 0x01, 0x05, 0x10, 0x00, 0x00,
+ 0x04, 0x3c, 0x07, 0x00, 0x08, 0x00};
+DEFINE_AND_INSTANTIATE_ReadBufferSizeCompleteReflectionTest(read_buffer_size_complete);
+
+std::vector<uint8_t> host_buffer_size = {0x33, 0x0c, 0x07, 0x9b, 0x06, 0xff, 0x14, 0x00, 0x0a, 0x00};
+DEFINE_AND_INSTANTIATE_HostBufferSizeReflectionTest(host_buffer_size);
+
+std::vector<uint8_t> host_buffer_size_complete = {0x0e, 0x04, 0x01, 0x33, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_HostBufferSizeCompleteReflectionTest(host_buffer_size_complete);
+
+std::vector<uint8_t> read_local_version_information = {0x01, 0x10, 0x00};
+DEFINE_AND_INSTANTIATE_ReadLocalVersionInformationReflectionTest(read_local_version_information);
+
+std::vector<uint8_t> read_local_version_information_complete = {0x0e, 0x0c, 0x01, 0x01, 0x10, 0x00, 0x09,
+ 0x00, 0x00, 0x09, 0x1d, 0x00, 0xbe, 0x02};
+DEFINE_AND_INSTANTIATE_ReadLocalVersionInformationCompleteReflectionTest(read_local_version_information_complete);
+
+std::vector<uint8_t> read_bd_addr = {0x09, 0x10, 0x00};
+DEFINE_AND_INSTANTIATE_ReadBdAddrReflectionTest(read_bd_addr);
+
+std::vector<uint8_t> read_bd_addr_complete = {0x0e, 0x0a, 0x01, 0x09, 0x10, 0x00, 0x14, 0x8e, 0x61, 0x5f, 0x36, 0x88};
+DEFINE_AND_INSTANTIATE_ReadBdAddrCompleteReflectionTest(read_bd_addr_complete);
+
+std::vector<uint8_t> read_local_supported_commands = {0x02, 0x10, 0x00};
+DEFINE_AND_INSTANTIATE_ReadLocalSupportedCommandsReflectionTest(read_local_supported_commands);
+
+std::vector<uint8_t> read_local_supported_commands_complete = {
+ 0x0e, 0x44, 0x01, 0x02, 0x10, 0x00, /* Supported commands start here (total 64 bytes) */
+ 0xff, 0xff, 0xff, 0x03, 0xce, 0xff, 0xef, 0xff, 0xff, 0xff, 0xff, 0x7f, 0xf2, 0x0f, 0xe8, 0xfe,
+ 0x3f, 0xf7, 0x83, 0xff, 0x1c, 0x00, 0x00, 0x00, 0x61, 0xff, 0xff, 0xff, 0x7f, 0xbe, 0x20, 0xf5,
+ 0xff, 0xf0, 0xff, 0xff, 0xff, 0xff, 0xff, 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
+DEFINE_AND_INSTANTIATE_ReadLocalSupportedCommandsCompleteReflectionTest(read_local_supported_commands_complete);
+
+std::vector<uint8_t> read_local_extended_features_0 = {0x04, 0x10, 0x01, 0x00};
+
+std::vector<uint8_t> read_local_extended_features_complete_0 = {0x0e, 0x0e, 0x01, 0x04, 0x10, 0x00, 0x00, 0x02,
+ 0xff, 0xfe, 0x8f, 0xfe, 0xd8, 0x3f, 0x5b, 0x87};
+
+std::vector<uint8_t> write_simple_paring_mode = {0x56, 0x0c, 0x01, 0x01};
+DEFINE_AND_INSTANTIATE_WriteSimplePairingModeReflectionTest(write_simple_paring_mode);
+
+std::vector<uint8_t> write_simple_paring_mode_complete = {0x0e, 0x04, 0x01, 0x56, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_WriteSimplePairingModeCompleteReflectionTest(write_simple_paring_mode_complete);
+
+std::vector<uint8_t> write_le_host_supported = {0x6d, 0x0c, 0x02, 0x01, 0x01};
+DEFINE_AND_INSTANTIATE_WriteLeHostSupportReflectionTest(write_le_host_supported);
+
+std::vector<uint8_t> write_le_host_supported_complete = {0x0e, 0x04, 0x01, 0x6d, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_WriteLeHostSupportCompleteReflectionTest(write_le_host_supported_complete);
+
+std::vector<uint8_t> read_local_extended_features_1 = {0x04, 0x10, 0x01, 0x01};
+
+std::vector<uint8_t> read_local_extended_features_complete_1 = {0x0e, 0x0e, 0x01, 0x04, 0x10, 0x00, 0x01, 0x02,
+ 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
+
+std::vector<uint8_t> read_local_extended_features_2 = {0x04, 0x10, 0x01, 0x02};
+DEFINE_AND_INSTANTIATE_ReadLocalExtendedFeaturesReflectionTest(read_local_extended_features_0,
+ read_local_extended_features_1,
+ read_local_extended_features_2);
+
+std::vector<uint8_t> read_local_extended_features_complete_2 = {0x0e, 0x0e, 0x01, 0x04, 0x10, 0x00, 0x02, 0x02,
+ 0x45, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
+DEFINE_AND_INSTANTIATE_ReadLocalExtendedFeaturesCompleteReflectionTest(read_local_extended_features_complete_0,
+ read_local_extended_features_complete_1,
+ read_local_extended_features_complete_2);
+
+std::vector<uint8_t> write_secure_connections_host_support = {0x7a, 0x0c, 0x01, 0x01};
+DEFINE_AND_INSTANTIATE_WriteSecureConnectionsHostSupportReflectionTest(write_secure_connections_host_support);
+
+std::vector<uint8_t> write_secure_connections_host_support_complete = {0x0e, 0x04, 0x01, 0x7a, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_WriteSecureConnectionsHostSupportCompleteReflectionTest(
+ write_secure_connections_host_support_complete);
+
+std::vector<uint8_t> le_read_white_list_size = {0x0f, 0x20, 0x00};
+DEFINE_AND_INSTANTIATE_LeReadWhiteListSizeReflectionTest(le_read_white_list_size);
+
+std::vector<uint8_t> le_read_white_list_size_complete = {0x0e, 0x05, 0x01, 0x0f, 0x20, 0x00, 0x80};
+DEFINE_AND_INSTANTIATE_LeReadWhiteListSizeCompleteReflectionTest(le_read_white_list_size_complete);
+
+std::vector<uint8_t> le_read_buffer_size = {0x02, 0x20, 0x00};
+DEFINE_AND_INSTANTIATE_LeReadBufferSizeReflectionTest(le_read_buffer_size);
+
+std::vector<uint8_t> le_read_buffer_size_complete = {0x0e, 0x07, 0x01, 0x02, 0x20, 0x00, 0xfb, 0x00, 0x10};
+DEFINE_AND_INSTANTIATE_LeReadBufferSizeCompleteReflectionTest(le_read_buffer_size_complete);
+
+std::vector<uint8_t> write_current_iac_laps = {0x3a, 0x0c, 0x07, 0x02, 0x11, 0x8b, 0x9e, 0x22, 0x8b, 0x9e};
+DEFINE_AND_INSTANTIATE_WriteCurrentIacLapReflectionTest(write_current_iac_laps);
+
+std::vector<uint8_t> write_current_iac_laps_complete = {0x0e, 0x04, 0x01, 0x3a, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_WriteCurrentIacLapCompleteReflectionTest(write_current_iac_laps_complete);
+
+std::vector<uint8_t> write_inquiry_scan_activity = {0x1e, 0x0c, 0x04, 0x00, 0x08, 0x12, 0x00};
+DEFINE_AND_INSTANTIATE_WriteInquiryScanActivityReflectionTest(write_inquiry_scan_activity);
+
+std::vector<uint8_t> write_inquiry_scan_activity_complete = {0x0e, 0x04, 0x01, 0x1e, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_WriteInquiryScanActivityCompleteReflectionTest(write_inquiry_scan_activity_complete);
+
+std::vector<uint8_t> read_inquiry_scan_activity = {0x1d, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_ReadInquiryScanActivityReflectionTest(read_inquiry_scan_activity);
+
+std::vector<uint8_t> read_inquiry_scan_activity_complete = {0x0e, 0x08, 0x01, 0x1d, 0x0c, 0x00, 0xaa, 0xbb, 0xcc, 0xdd};
+DEFINE_AND_INSTANTIATE_ReadInquiryScanActivityCompleteReflectionTest(read_inquiry_scan_activity_complete);
+
+std::vector<uint8_t> read_current_iac_lap = {0x39, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_ReadCurrentIacLapReflectionTest(read_current_iac_lap);
+
+std::vector<uint8_t> read_current_iac_lap_complete = {0x0e, 0x0b, 0x01, 0x39, 0x0c, 0x00, 0x02,
+ 0x11, 0x8b, 0x9e, 0x22, 0x8b, 0x9e};
+DEFINE_AND_INSTANTIATE_ReadCurrentIacLapCompleteReflectionTest(read_current_iac_lap_complete);
+
+std::vector<uint8_t> read_number_of_supported_iac = {0x38, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_ReadNumberOfSupportedIacReflectionTest(read_number_of_supported_iac);
+
+std::vector<uint8_t> read_number_of_supported_iac_complete = {0x0e, 0x05, 0x01, 0x38, 0x0c, 0x00, 0x99};
+DEFINE_AND_INSTANTIATE_ReadNumberOfSupportedIacCompleteReflectionTest(read_number_of_supported_iac_complete);
+
+std::vector<uint8_t> read_page_timeout = {0x17, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_ReadPageTimeoutReflectionTest(read_page_timeout);
+
+std::vector<uint8_t> read_page_timeout_complete = {0x0e, 0x06, 0x01, 0x17, 0x0c, 0x00, 0x11, 0x22};
+DEFINE_AND_INSTANTIATE_ReadPageTimeoutCompleteReflectionTest(read_page_timeout_complete);
+
+std::vector<uint8_t> write_page_timeout = {0x18, 0x0c, 0x02, 0x00, 0x20};
+DEFINE_AND_INSTANTIATE_WritePageTimeoutReflectionTest(write_page_timeout);
+
+std::vector<uint8_t> write_page_timeout_complete = {0x0e, 0x04, 0x01, 0x18, 0x0c, 0x00};
+DEFINE_AND_INSTANTIATE_WritePageTimeoutCompleteReflectionTest(write_page_timeout_complete);
+
+std::vector<uint8_t> inquiry = {0x01, 0x04, 0x05, 0x33, 0x8b, 0x9e, 0xaa, 0xbb};
+DEFINE_AND_INSTANTIATE_InquiryReflectionTest(inquiry);
+
+std::vector<uint8_t> inquiry_status = {0x0f, 0x04, 0x00, 0x01, 0x01, 0x04};
+DEFINE_AND_INSTANTIATE_InquiryStatusReflectionTest(inquiry_status);
+
+std::vector<uint8_t> inquiry_cancel = {0x02, 0x04, 0x00};
+DEFINE_AND_INSTANTIATE_InquiryCancelReflectionTest(inquiry_cancel);
+
+std::vector<uint8_t> inquiry_cancel_complete = {0x0e, 0x04, 0x01, 0x02, 0x04, 0x00};
+DEFINE_AND_INSTANTIATE_InquiryCancelCompleteReflectionTest(inquiry_cancel_complete);
+
+std::vector<uint8_t> periodic_inquiry_mode = {0x03, 0x04, 0x09, 0x12, 0x34, 0x56, 0x78, 0x11, 0x8b, 0x9e, 0x9a, 0xbc};
+DEFINE_AND_INSTANTIATE_PeriodicInquiryModeReflectionTest(periodic_inquiry_mode);
+
+std::vector<uint8_t> periodic_inquiry_mode_complete = {0x0e, 0x04, 0x01, 0x03, 0x04, 0x00};
+DEFINE_AND_INSTANTIATE_PeriodicInquiryModeCompleteReflectionTest(periodic_inquiry_mode_complete);
+
+std::vector<uint8_t> exit_periodic_inquiry_mode = {0x04, 0x04, 0x00};
+DEFINE_AND_INSTANTIATE_ExitPeriodicInquiryModeReflectionTest(exit_periodic_inquiry_mode);
+
+std::vector<uint8_t> exit_periodic_inquiry_mode_complete = {0x0e, 0x04, 0x01, 0x04, 0x04, 0x00};
+DEFINE_AND_INSTANTIATE_ExitPeriodicInquiryModeCompleteReflectionTest(exit_periodic_inquiry_mode_complete);
+
std::vector<uint8_t> pixel_3_xl_write_extended_inquiry_response{
0x52, 0x0c, 0xf1, 0x01, 0x0b, 0x09, 0x50, 0x69, 0x78, 0x65, 0x6c, 0x20, 0x33, 0x20, 0x58, 0x4c, 0x19, 0x03, 0x05,
0x11, 0x0a, 0x11, 0x0c, 0x11, 0x0e, 0x11, 0x12, 0x11, 0x15, 0x11, 0x16, 0x11, 0x1f, 0x11, 0x2d, 0x11, 0x2f, 0x11,
@@ -70,7 +233,7 @@ TEST(HciPacketsTest, testWriteExtendedInquiryResponse) {
std::make_shared<std::vector<uint8_t>>(pixel_3_xl_write_extended_inquiry_response);
PacketView<kLittleEndian> packet_bytes_view(view_bytes);
- auto view = WriteExtendedInquiryResponseView::Create(CommandView::Create(packet_bytes_view));
+ auto view = WriteExtendedInquiryResponseView::Create(CommandPacketView::Create(packet_bytes_view));
ASSERT_TRUE(view.IsValid());
auto gap_data = view.GetExtendedInquiryResponse();
ASSERT_GE(gap_data.size(), 4);
@@ -105,28 +268,33 @@ std::vector<uint8_t> le_set_scan_parameters{
};
TEST(HciPacketsTest, testLeSetScanParameters) {
PacketView<kLittleEndian> packet_bytes_view(std::make_shared<std::vector<uint8_t>>(le_set_scan_parameters));
- auto view = LeSetScanParametersView::Create(LeScanningCommandView::Create(CommandView::Create(packet_bytes_view)));
+ auto view =
+ LeSetScanParametersView::Create(LeScanningCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
ASSERT_EQ(LeScanType::ACTIVE, view.GetLeScanType());
ASSERT_EQ(0x12, view.GetLeScanInterval());
ASSERT_EQ(0x12, view.GetLeScanWindow());
- ASSERT_EQ(OwnAddressType::RANDOM_DEVICE_ADDRESS, view.GetOwnAddressType());
- ASSERT_EQ(LeScanningFilterPolicy::ACCEPT_ALL, view.GetScanningFilterPolicy());
+ ASSERT_EQ(AddressType::RANDOM_DEVICE_ADDRESS, view.GetOwnAddressType());
+ ASSERT_EQ(LeSetScanningFilterPolicy::ACCEPT_ALL, view.GetScanningFilterPolicy());
}
+DEFINE_AND_INSTANTIATE_LeSetScanParametersReflectionTest(le_set_scan_parameters);
+
std::vector<uint8_t> le_set_scan_enable{
0x0c, 0x20, 0x02, 0x01, 0x00,
};
TEST(HciPacketsTest, testLeSetScanEnable) {
PacketView<kLittleEndian> packet_bytes_view(std::make_shared<std::vector<uint8_t>>(le_set_scan_enable));
- auto view = LeSetScanEnableView::Create(LeScanningCommandView::Create(CommandView::Create(packet_bytes_view)));
+ auto view = LeSetScanEnableView::Create(LeScanningCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
ASSERT_EQ(Enable::ENABLED, view.GetLeScanEnable());
ASSERT_EQ(Enable::DISABLED, view.GetFilterDuplicates());
}
+DEFINE_AND_INSTANTIATE_LeSetScanEnableReflectionTest(le_set_scan_enable);
+
std::vector<uint8_t> le_get_vendor_capabilities{
0x53,
0xfd,
@@ -134,21 +302,24 @@ std::vector<uint8_t> le_get_vendor_capabilities{
};
TEST(HciPacketsTest, testLeGetVendorCapabilities) {
PacketView<kLittleEndian> packet_bytes_view(std::make_shared<std::vector<uint8_t>>(le_get_vendor_capabilities));
- auto view = LeGetVendorCapabilitiesView::Create(VendorCommandView::Create(CommandView::Create(packet_bytes_view)));
+ auto view =
+ LeGetVendorCapabilitiesView::Create(VendorCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
}
+DEFINE_AND_INSTANTIATE_LeGetVendorCapabilitiesReflectionTest(le_get_vendor_capabilities);
+
std::vector<uint8_t> le_get_vendor_capabilities_complete{
0x0e, 0x0c, 0x01, 0x53, 0xfd, 0x00, 0x05, 0x01, 0x00, 0x04, 0x80, 0x01, 0x10, 0x01,
};
TEST(HciPacketsTest, testLeGetVendorCapabilitiesComplete) {
PacketView<kLittleEndian> packet_bytes_view(
std::make_shared<std::vector<uint8_t>>(le_get_vendor_capabilities_complete));
- auto view =
- LeGetVendorCapabilitiesCompleteView::Create(CommandCompleteView::Create(EventView::Create(packet_bytes_view)));
+ auto view = LeGetVendorCapabilitiesCompleteView::Create(
+ CommandCompleteView::Create(EventPacketView::Create(packet_bytes_view)));
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
auto base_capabilities = view.GetBaseVendorCapabilities();
ASSERT_EQ(5, base_capabilities.max_advt_instances_);
ASSERT_EQ(1, base_capabilities.offloaded_resolution_of_private_address_);
@@ -159,16 +330,18 @@ TEST(HciPacketsTest, testLeGetVendorCapabilitiesComplete) {
ASSERT_EQ(1, base_capabilities.activity_energy_info_support_);
}
+DEFINE_AND_INSTANTIATE_LeGetVendorCapabilitiesCompleteReflectionTest(le_get_vendor_capabilities_complete);
+
std::vector<uint8_t> le_set_extended_scan_parameters{
0x41, 0x20, 0x08, 0x01, 0x00, 0x01, 0x01, 0x12, 0x00, 0x12, 0x00,
};
TEST(HciPacketsTest, testLeSetExtendedScanParameters) {
PacketView<kLittleEndian> packet_bytes_view(std::make_shared<std::vector<uint8_t>>(le_set_extended_scan_parameters));
- auto view =
- LeSetExtendedScanParametersView::Create(LeScanningCommandView::Create(CommandView::Create(packet_bytes_view)));
+ auto view = LeSetExtendedScanParametersView::Create(
+ LeScanningCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
ASSERT_EQ(1, view.GetScanningPhys());
auto params = view.GetParameters();
ASSERT_EQ(1, params.size());
@@ -184,10 +357,10 @@ std::vector<uint8_t> le_set_extended_scan_parameters_6553{
TEST(HciPacketsTest, testLeSetExtendedScanParameters_6553) {
PacketView<kLittleEndian> packet_bytes_view(
std::make_shared<std::vector<uint8_t>>(le_set_extended_scan_parameters_6553));
- auto view =
- LeSetExtendedScanParametersView::Create(LeScanningCommandView::Create(CommandView::Create(packet_bytes_view)));
+ auto view = LeSetExtendedScanParametersView::Create(
+ LeScanningCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
ASSERT_EQ(1, view.GetScanningPhys());
auto params = view.GetParameters();
ASSERT_EQ(1, params.size());
@@ -196,6 +369,14 @@ TEST(HciPacketsTest, testLeSetExtendedScanParameters_6553) {
ASSERT_EQ(6553, params[0].le_scan_window_);
}
+DEFINE_AND_INSTANTIATE_LeSetExtendedScanParametersReflectionTest(le_set_extended_scan_parameters,
+ le_set_extended_scan_parameters_6553);
+
+std::vector<uint8_t> le_set_extended_scan_parameters_complete{
+ 0x0e, 0x04, 0x01, 0x41, 0x20, 0x00,
+};
+DEFINE_AND_INSTANTIATE_LeSetExtendedScanParametersCompleteReflectionTest(le_set_extended_scan_parameters_complete);
+
std::vector<uint8_t> le_set_extended_scan_enable{
0x42, 0x20, 0x06, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00,
};
@@ -203,9 +384,9 @@ std::vector<uint8_t> le_set_extended_scan_enable{
TEST(HciPacketsTest, testLeSetExtendedScanEnable) {
PacketView<kLittleEndian> packet_bytes_view(std::make_shared<std::vector<uint8_t>>(le_set_extended_scan_enable));
auto view =
- LeSetExtendedScanEnableView::Create(LeScanningCommandView::Create(CommandView::Create(packet_bytes_view)));
+ LeSetExtendedScanEnableView::Create(LeScanningCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
ASSERT_EQ(FilterDuplicates::DISABLED, view.GetFilterDuplicates());
ASSERT_EQ(Enable::ENABLED, view.GetEnable());
ASSERT_EQ(0, view.GetDuration());
@@ -220,26 +401,35 @@ TEST(HciPacketsTest, testLeSetExtendedScanEnableDisable) {
PacketView<kLittleEndian> packet_bytes_view(
std::make_shared<std::vector<uint8_t>>(le_set_extended_scan_enable_disable));
auto view =
- LeSetExtendedScanEnableView::Create(LeScanningCommandView::Create(CommandView::Create(packet_bytes_view)));
+ LeSetExtendedScanEnableView::Create(LeScanningCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
ASSERT_EQ(FilterDuplicates::ENABLED, view.GetFilterDuplicates());
ASSERT_EQ(Enable::DISABLED, view.GetEnable());
ASSERT_EQ(0, view.GetDuration());
ASSERT_EQ(0, view.GetPeriod());
}
+DEFINE_AND_INSTANTIATE_LeSetExtendedScanEnableReflectionTest(le_set_extended_scan_enable,
+ le_set_extended_scan_enable_disable);
+
+std::vector<uint8_t> le_set_extended_scan_enable_complete{
+ 0x0e, 0x04, 0x01, 0x42, 0x20, 0x00,
+};
+DEFINE_AND_INSTANTIATE_LeSetExtendedScanEnableCompleteReflectionTest(le_set_extended_scan_enable_complete);
+
std::vector<uint8_t> le_extended_create_connection = {
0x43, 0x20, 0x2a, 0x01, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x08,
0x30, 0x00, 0x18, 0x00, 0x28, 0x00, 0x00, 0x00, 0xf4, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00,
0x08, 0x30, 0x00, 0x18, 0x00, 0x28, 0x00, 0x00, 0x00, 0xf4, 0x01, 0x00, 0x00, 0x00, 0x00};
+DEFINE_AND_INSTANTIATE_LeExtendedCreateConnectionReflectionTest(le_extended_create_connection);
TEST(HciPacketsTest, testLeExtendedCreateConnection) {
std::shared_ptr<std::vector<uint8_t>> packet_bytes =
std::make_shared<std::vector<uint8_t>>(le_extended_create_connection);
PacketView<kLittleEndian> packet_bytes_view(packet_bytes);
auto view = LeExtendedCreateConnectionView::Create(
- LeConnectionManagementCommandView::Create(AclCommandView::Create(CommandView::Create(packet_bytes_view))));
+ LeConnectionManagementCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
ASSERT_TRUE(view.IsValid());
}
@@ -252,12 +442,19 @@ TEST(HciPacketsTest, testLeSetExtendedAdvertisingRandomAddress) {
std::make_shared<std::vector<uint8_t>>(le_set_extended_advertising_random_address);
PacketView<kLittleEndian> packet_bytes_view(packet_bytes);
auto view = LeSetExtendedAdvertisingRandomAddressView::Create(
- LeAdvertisingCommandView::Create(CommandView::Create(packet_bytes_view)));
+ LeAdvertisingCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
ASSERT_TRUE(view.IsValid());
uint8_t random_address_bytes[] = {0x77, 0x58, 0xeb, 0xd3, 0x1c, 0x6e};
ASSERT_EQ(0, view.GetAdvertisingHandle());
ASSERT_EQ(Address(random_address_bytes), view.GetAdvertisingRandomAddress());
}
+DEFINE_AND_INSTANTIATE_LeSetExtendedAdvertisingRandomAddressReflectionTest(le_set_extended_advertising_random_address);
+
+std::vector<uint8_t> le_set_extended_advertising_random_address_complete{
+ 0x0e, 0x04, 0x01, 0x35, 0x20, 0x00,
+};
+DEFINE_AND_INSTANTIATE_LeSetExtendedAdvertisingRandomAddressCompleteReflectionTest(
+ le_set_extended_advertising_random_address_complete);
std::vector<uint8_t> le_set_extended_advertising_data{
0x37, 0x20, 0x12, 0x00, 0x03, 0x01, 0x0e, 0x02, 0x01, 0x02, 0x0a,
@@ -268,7 +465,7 @@ TEST(HciPacketsTest, testLeSetExtendedAdvertisingData) {
std::make_shared<std::vector<uint8_t>>(le_set_extended_advertising_data);
PacketView<kLittleEndian> packet_bytes_view(packet_bytes);
auto view = LeSetExtendedAdvertisingDataRawView::Create(
- LeAdvertisingCommandView::Create(CommandView::Create(packet_bytes_view)));
+ LeAdvertisingCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
ASSERT_TRUE(view.IsValid());
ASSERT_EQ(0, view.GetAdvertisingHandle());
ASSERT_EQ(Operation::COMPLETE_ADVERTISEMENT, view.GetOperation());
@@ -279,6 +476,13 @@ TEST(HciPacketsTest, testLeSetExtendedAdvertisingData) {
ASSERT_EQ(advertising_data, view.GetAdvertisingData());
}
+DEFINE_AND_INSTANTIATE_LeSetExtendedAdvertisingDataRawReflectionTest(le_set_extended_advertising_data);
+
+std::vector<uint8_t> le_set_extended_advertising_data_complete{
+ 0x0e, 0x04, 0x01, 0x37, 0x20, 0x00,
+};
+DEFINE_AND_INSTANTIATE_LeSetExtendedAdvertisingDataCompleteReflectionTest(le_set_extended_advertising_data_complete);
+
std::vector<uint8_t> le_set_extended_advertising_parameters_set_0{
0x36, 0x20, 0x19, 0x00, 0x13, 0x00, 0x90, 0x01, 0x00, 0xc2, 0x01, 0x00, 0x07, 0x01,
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xf9, 0x01, 0x00, 0x01, 0x01, 0x00,
@@ -288,7 +492,7 @@ TEST(HciPacketsTest, testLeSetExtendedAdvertisingParametersLegacySet0) {
std::make_shared<std::vector<uint8_t>>(le_set_extended_advertising_parameters_set_0);
PacketView<kLittleEndian> packet_bytes_view(packet_bytes);
auto view = LeSetExtendedAdvertisingLegacyParametersView::Create(
- LeAdvertisingCommandView::Create(CommandView::Create(packet_bytes_view)));
+ LeAdvertisingCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
ASSERT_TRUE(view.IsValid());
ASSERT_EQ(0, view.GetAdvertisingHandle());
ASSERT_EQ(400, view.GetPrimaryAdvertisingIntervalMin());
@@ -311,7 +515,7 @@ TEST(HciPacketsTest, testLeSetExtendedAdvertisingParametersSet1) {
std::make_shared<std::vector<uint8_t>>(le_set_extended_advertising_parameters_set_1);
PacketView<kLittleEndian> packet_bytes_view(packet_bytes);
auto view = LeSetExtendedAdvertisingLegacyParametersView::Create(
- LeAdvertisingCommandView::Create(CommandView::Create(packet_bytes_view)));
+ LeAdvertisingCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
ASSERT_TRUE(view.IsValid());
ASSERT_EQ(1, view.GetAdvertisingHandle());
ASSERT_EQ(400, view.GetPrimaryAdvertisingIntervalMin());
@@ -325,17 +529,23 @@ TEST(HciPacketsTest, testLeSetExtendedAdvertisingParametersSet1) {
ASSERT_EQ(Enable::DISABLED, view.GetScanRequestNotificationEnable());
}
+DEFINE_AND_INSTANTIATE_LeSetExtendedAdvertisingLegacyParametersReflectionTest(
+ le_set_extended_advertising_parameters_set_0, le_set_extended_advertising_parameters_set_1);
+
std::vector<uint8_t> le_set_extended_advertising_parameters_complete{0x0e, 0x05, 0x01, 0x36, 0x20, 0x00, 0xf5};
TEST(HciPacketsTest, testLeSetExtendedAdvertisingParametersComplete) {
std::shared_ptr<std::vector<uint8_t>> packet_bytes =
std::make_shared<std::vector<uint8_t>>(le_set_extended_advertising_parameters_complete);
PacketView<kLittleEndian> packet_bytes_view(packet_bytes);
auto view = LeSetExtendedAdvertisingParametersCompleteView::Create(
- CommandCompleteView::Create(EventView::Create(packet_bytes_view)));
+ CommandCompleteView::Create(EventPacketView::Create(packet_bytes_view)));
ASSERT_TRUE(view.IsValid());
ASSERT_EQ(static_cast<uint8_t>(-11), view.GetSelectedTxPower());
}
+DEFINE_AND_INSTANTIATE_LeSetExtendedAdvertisingParametersCompleteReflectionTest(
+ le_set_extended_advertising_parameters_complete);
+
std::vector<uint8_t> le_remove_advertising_set_1{
0x3c,
0x20,
@@ -346,12 +556,19 @@ TEST(HciPacketsTest, testLeRemoveAdvertisingSet1) {
std::shared_ptr<std::vector<uint8_t>> packet_bytes =
std::make_shared<std::vector<uint8_t>>(le_remove_advertising_set_1);
PacketView<kLittleEndian> packet_bytes_view(packet_bytes);
- auto view =
- LeRemoveAdvertisingSetView::Create(LeAdvertisingCommandView::Create(CommandView::Create(packet_bytes_view)));
+ auto view = LeRemoveAdvertisingSetView::Create(
+ LeAdvertisingCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
ASSERT_TRUE(view.IsValid());
ASSERT_EQ(1, view.GetAdvertisingHandle());
}
+DEFINE_AND_INSTANTIATE_LeRemoveAdvertisingSetReflectionTest(le_remove_advertising_set_1);
+
+std::vector<uint8_t> le_remove_advertising_set_complete{
+ 0x0e, 0x04, 0x01, 0x3c, 0x20, 0x00,
+};
+DEFINE_AND_INSTANTIATE_LeRemoveAdvertisingSetCompleteReflectionTest(le_remove_advertising_set_complete);
+
std::vector<uint8_t> le_set_extended_advertising_disable_1{
0x39, 0x20, 0x06, 0x00, 0x01, 0x01, 0x00, 0x00, 0x00,
};
@@ -360,13 +577,21 @@ TEST(HciPacketsTest, testLeSetExtendedAdvertisingDisable1) {
std::make_shared<std::vector<uint8_t>>(le_set_extended_advertising_disable_1);
PacketView<kLittleEndian> packet_bytes_view(packet_bytes);
auto view = LeSetExtendedAdvertisingDisableView::Create(
- LeAdvertisingCommandView::Create(CommandView::Create(packet_bytes_view)));
+ LeAdvertisingCommandView::Create(CommandPacketView::Create(packet_bytes_view)));
ASSERT_TRUE(view.IsValid());
auto disabled_set = view.GetDisabledSets();
ASSERT_EQ(1, disabled_set.size());
ASSERT_EQ(1, disabled_set[0].advertising_handle_);
}
+DEFINE_AND_INSTANTIATE_LeSetExtendedAdvertisingDisableReflectionTest(le_set_extended_advertising_disable_1);
+
+std::vector<uint8_t> le_set_extended_advertising_enable_complete{
+ 0x0e, 0x04, 0x01, 0x39, 0x20, 0x00,
+};
+DEFINE_AND_INSTANTIATE_LeSetExtendedAdvertisingEnableCompleteReflectionTest(
+ le_set_extended_advertising_enable_complete);
+
TEST(HciPacketsTest, testLeSetAdvertisingDataBuilderLength) {
GapData gap_data;
gap_data.data_type_ = GapDataType::COMPLETE_LOCAL_NAME;
@@ -378,11 +603,11 @@ TEST(HciPacketsTest, testLeSetAdvertisingDataBuilderLength) {
packet_bytes->reserve(builder->size());
BitInserter bit_inserter(*packet_bytes);
builder->Serialize(bit_inserter);
- auto command_view = LeAdvertisingCommandView::Create(CommandView::Create(PacketView<kLittleEndian>(packet_bytes)));
- ASSERT_TRUE(command_view.IsValid());
+ auto command_view = LeAdvertisingCommandView::Create(CommandPacketView::Create(packet_bytes));
+ ASSERT(command_view.IsValid());
ASSERT_EQ(1 /* data_length */ + 31 /* data */, command_view.GetPayload().size());
auto view = LeSetAdvertisingDataView::Create(command_view);
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
}
TEST(HciPacketsTest, testLeSetScanResponseDataBuilderLength) {
@@ -396,11 +621,11 @@ TEST(HciPacketsTest, testLeSetScanResponseDataBuilderLength) {
packet_bytes->reserve(builder->size());
BitInserter bit_inserter(*packet_bytes);
builder->Serialize(bit_inserter);
- auto command_view = LeAdvertisingCommandView::Create(CommandView::Create(PacketView<kLittleEndian>(packet_bytes)));
- ASSERT_TRUE(command_view.IsValid());
+ auto command_view = LeAdvertisingCommandView::Create(CommandPacketView::Create(packet_bytes));
+ ASSERT(command_view.IsValid());
ASSERT_EQ(1 /* data_length */ + 31 /* data */, command_view.GetPayload().size());
auto view = LeSetScanResponseDataView::Create(command_view);
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
}
TEST(HciPacketsTest, testLeMultiAdvSetAdvertisingDataBuilderLength) {
@@ -409,19 +634,18 @@ TEST(HciPacketsTest, testLeMultiAdvSetAdvertisingDataBuilderLength) {
gap_data.data_ = std::vector<uint8_t>({'A', ' ', 'g', 'o', 'o', 'd', ' ', 'n', 'a', 'm', 'e'});
uint8_t set = 3;
auto builder = LeMultiAdvtSetDataBuilder::Create({gap_data}, set);
+ ASSERT_EQ(2 /*opcode*/ + 1 /* parameter size */ + 1 /* data_length */ + 31 /* data */ + 1 /* set */, builder->size());
auto packet_bytes = std::make_shared<std::vector<uint8_t>>();
packet_bytes->reserve(builder->size());
BitInserter bit_inserter(*packet_bytes);
builder->Serialize(bit_inserter);
- auto command_view = LeMultiAdvtSetDataView::Create(LeMultiAdvtView::Create(
- LeAdvertisingCommandView::Create(CommandView::Create(PacketView<kLittleEndian>(packet_bytes)))));
- ASSERT_TRUE(command_view.IsValid());
+ auto command_view =
+ LeMultiAdvtView::Create(LeAdvertisingCommandView::Create(CommandPacketView::Create(packet_bytes)));
+ ASSERT(command_view.IsValid());
+ EXPECT_EQ(1 /* data_length */ + 31 /* data */ + 1 /* set */, command_view.GetPayload().size());
auto view = LeMultiAdvtSetDataView::Create(command_view);
- ASSERT_TRUE(view.IsValid());
- ASSERT_TRUE(view.GetAdvertisingData().size() > 0);
- ASSERT_EQ(view.GetAdvertisingData()[0].data_, gap_data.data_);
- ASSERT_EQ(view.GetAdvertisingInstance(), 3);
+ ASSERT(view.IsValid());
}
TEST(HciPacketsTest, testLeMultiAdvSetScanResponseDataBuilderLength) {
@@ -430,19 +654,64 @@ TEST(HciPacketsTest, testLeMultiAdvSetScanResponseDataBuilderLength) {
gap_data.data_ = std::vector<uint8_t>({'A', ' ', 'g', 'o', 'o', 'd', ' ', 'n', 'a', 'm', 'e'});
uint8_t set = 3;
auto builder = LeMultiAdvtSetScanRespBuilder::Create({gap_data}, set);
+ EXPECT_EQ(2 /*opcode*/ + 1 /* parameter size */ + 1 /*data_length */ + 31 /* data */ + 1 /* set */, builder->size());
auto packet_bytes = std::make_shared<std::vector<uint8_t>>();
packet_bytes->reserve(builder->size());
BitInserter bit_inserter(*packet_bytes);
builder->Serialize(bit_inserter);
- auto command_view = LeMultiAdvtSetScanRespView::Create(LeMultiAdvtView::Create(
- LeAdvertisingCommandView::Create(CommandView::Create(PacketView<kLittleEndian>(packet_bytes)))));
- ASSERT_TRUE(command_view.IsValid());
+ auto command_view =
+ LeMultiAdvtView::Create(LeAdvertisingCommandView::Create(CommandPacketView::Create(packet_bytes)));
+ ASSERT(command_view.IsValid());
+ ASSERT_EQ(1 /* data_length */ + 31 /* data */ + 1 /* set */, command_view.GetPayload().size());
auto view = LeMultiAdvtSetScanRespView::Create(command_view);
- ASSERT_TRUE(view.IsValid());
- ASSERT_EQ(view.GetAdvertisingData()[0].data_, gap_data.data_);
- ASSERT_EQ(view.GetAdvertisingInstance(), 3);
+ ASSERT(view.IsValid());
}
+std::vector<uint8_t> controller_bqr = {0x5e, 0xfd, 0x07, 0x00, 0x1f, 0x00, 0x07, 0x00, 0x88, 0x13};
+DEFINE_AND_INSTANTIATE_ControllerBqrReflectionTest(controller_bqr);
+
+std::vector<uint8_t> controller_bqr_complete = {0x0e, 0x08, 0x01, 0x5e, 0xfd, 0x00, 0x1f, 0x00, 0x07, 0x00};
+DEFINE_AND_INSTANTIATE_ControllerBqrCompleteReflectionTest(controller_bqr_complete);
+
+std::vector<uint8_t> bqr_monitor_mode_event = {
+ 0xff, 0x31, 0x58, 0x01, 0x10, 0x02, 0x00, 0x00, 0x07, 0xd5, 0x00, 0x14, 0x00, 0x40, 0x1f, 0xed, 0x41,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x06, 0x3c, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0xff, 0xff, 0xff, 0x0f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00};
+DEFINE_AND_INSTANTIATE_BqrMonitorModeEventReflectionTest(bqr_monitor_mode_event);
+
+std::vector<uint8_t> bqr_approach_lsto_event = {
+ 0xff, 0x48, 0x58, 0x02, 0x10, 0x02, 0x00, 0x01, 0x09, 0xaf, 0x00, 0x2d, 0x00, 0x00, 0x7d, 0x94, 0xe9, 0x03, 0x01,
+ 0x20, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0x00, 0x30, 0xa8, 0x0f, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x81, 0x9b, 0xf2, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0xcc, 0xcc, 0xcc, 0xcc, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11, 0x4e, 0x11, 0x00, 0x0c, 0x54, 0x10, 0x00};
+DEFINE_AND_INSTANTIATE_BqrApproachLstoEventReflectionTest(bqr_approach_lsto_event);
+
+std::vector<uint8_t> bqr_a2dp_audio_choppy_event = {
+ 0xff, 0x41, 0x58, 0x03, 0x19, 0x09, 0x00, 0x00, 0x07, 0xcb, 0x00, 0x3a, 0x01, 0x40, 0x1f, 0x7e, 0xce,
+ 0x58, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x00, 0x00, 0x32, 0x00, 0x00, 0x00, 0x7e, 0xce, 0x58,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x45, 0xd1, 0x57, 0x00, 0x30, 0x1c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x0d, 0xce, 0x58, 0x00, 0x3a, 0xce, 0x58, 0x00, 0x01, 0x00, 0x07, 0x00, 0x00, 0x00, 0x00, 0x01};
+DEFINE_AND_INSTANTIATE_BqrA2dpAudioChoppyEventReflectionTest(bqr_a2dp_audio_choppy_event);
+
+std::vector<uint8_t> bqr_sco_voice_choppy_event = {
+ 0xff, 0x4a, 0x58, 0x04, 0x09, 0x08, 0x00, 0x00, 0x08, 0xbf, 0x00, 0x03, 0x00, 0x40, 0x1f, 0x92, 0x6c, 0x0a, 0x0d,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x00, 0x06, 0x02, 0x02, 0x0b,
+ 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x4f, 0x00, 0x00, 0x00};
+DEFINE_AND_INSTANTIATE_BqrScoVoiceChoppyEventReflectionTest(bqr_sco_voice_choppy_event);
+
+std::vector<uint8_t> bqr_root_inflammation_event = {0xff, 0x04, 0x58, 0x05, 0x00, 0xfe};
+DEFINE_AND_INSTANTIATE_BqrRootInflammationEventReflectionTest(bqr_root_inflammation_event);
+
+std::vector<uint8_t> bqr_lmp_ll_message_trace_event = {0xff, 0x11, 0x58, 0x11, 0x03, 0x00, 0x01, 0xff, 0x11, 0x55,
+ 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55, 0x55};
+DEFINE_AND_INSTANTIATE_BqrLmpLlMessageTraceEventReflectionTest(bqr_lmp_ll_message_trace_event);
+
+std::vector<uint8_t> bqr_bt_scheduling_trace_event = {0xff, 0x1d, 0x58, 0x12, 0x05, 0x00, 0x02, 0xd9, 0xae, 0x08, 0x01,
+ 0x05, 0x00, 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11,
+ 0x00, 0x01, 0x0c, 0x00, 0x36, 0x3c, 0x00, 0x00, 0x00};
+DEFINE_AND_INSTANTIATE_BqrBtSchedulingTraceEventReflectionTest(bqr_bt_scheduling_trace_event);
+
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/le_acl_connection_interface.h b/gd/hci/le_acl_connection_interface.h
deleted file mode 100644
index 8f1a9487d..000000000
--- a/gd/hci/le_acl_connection_interface.h
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "hci/command_interface.h"
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace hci {
-
-constexpr SubeventCode LeConnectionManagementEvents[] = {
- SubeventCode::CONNECTION_COMPLETE,
- SubeventCode::ENHANCED_CONNECTION_COMPLETE,
- SubeventCode::CONNECTION_UPDATE_COMPLETE,
- SubeventCode::PHY_UPDATE_COMPLETE,
- SubeventCode::DATA_LENGTH_CHANGE,
- SubeventCode::REMOTE_CONNECTION_PARAMETER_REQUEST,
-};
-
-typedef CommandInterface<AclCommandBuilder> LeAclConnectionInterface;
-
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/le_address_manager.cc b/gd/hci/le_address_manager.cc
deleted file mode 100644
index b030e23e1..000000000
--- a/gd/hci/le_address_manager.cc
+++ /dev/null
@@ -1,450 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/le_address_manager.h"
-#include "common/init_flags.h"
-#include "os/log.h"
-#include "os/rand.h"
-
-namespace bluetooth {
-namespace hci {
-
-static constexpr uint8_t BLE_ADDR_MASK = 0xc0u;
-
-LeAddressManager::LeAddressManager(
- common::Callback<void(std::unique_ptr<CommandBuilder>)> enqueue_command,
- os::Handler* handler,
- Address public_address,
- uint8_t connect_list_size,
- uint8_t resolving_list_size)
- : enqueue_command_(enqueue_command),
- handler_(handler),
- public_address_(public_address),
- connect_list_size_(connect_list_size),
- resolving_list_size_(resolving_list_size){};
-
-LeAddressManager::~LeAddressManager() {
- if (address_rotation_alarm_ != nullptr) {
- address_rotation_alarm_->Cancel();
- address_rotation_alarm_.reset();
- }
-}
-
-// Aborts if called more than once
-void LeAddressManager::SetPrivacyPolicyForInitiatorAddress(
- AddressPolicy address_policy,
- AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time) {
- ASSERT(address_policy_ == AddressPolicy::POLICY_NOT_SET);
- ASSERT(address_policy != AddressPolicy::POLICY_NOT_SET);
- ASSERT_LOG(registered_clients_.empty(), "Policy must be set before clients are registered.");
- address_policy_ = address_policy;
-
- switch (address_policy_) {
- case AddressPolicy::USE_PUBLIC_ADDRESS:
- le_address_ = fixed_address;
- handler_->BindOnceOn(this, &LeAddressManager::resume_registered_clients).Invoke();
- break;
- case AddressPolicy::USE_STATIC_ADDRESS: {
- auto addr = fixed_address.GetAddress();
- auto address = addr.address;
- // The two most significant bits of the static address shall be equal to 1
- ASSERT_LOG((address[5] & BLE_ADDR_MASK) == BLE_ADDR_MASK, "The two most significant bits shall be equal to 1");
- // Bits of the random part of the address shall not be all 1 or all 0
- if ((address[0] == 0x00 && address[1] == 0x00 && address[2] == 0x00 && address[3] == 0x00 && address[4] == 0x00 &&
- address[5] == BLE_ADDR_MASK) ||
- (address[0] == 0xFF && address[1] == 0xFF && address[2] == 0xFF && address[3] == 0xFF && address[4] == 0xFF &&
- address[5] == 0xFF)) {
- LOG_ALWAYS_FATAL("Bits of the random part of the address shall not be all 1 or all 0");
- }
- le_address_ = fixed_address;
- auto packet = hci::LeSetRandomAddressBuilder::Create(le_address_.GetAddress());
- handler_->Post(common::BindOnce(enqueue_command_, std::move(packet)));
- } break;
- case AddressPolicy::USE_NON_RESOLVABLE_ADDRESS:
- case AddressPolicy::USE_RESOLVABLE_ADDRESS:
- le_address_ = fixed_address;
- rotation_irk_ = rotation_irk;
- minimum_rotation_time_ = minimum_rotation_time;
- maximum_rotation_time_ = maximum_rotation_time;
- address_rotation_alarm_ = std::make_unique<os::Alarm>(handler_);
- set_random_address();
- break;
- case AddressPolicy::POLICY_NOT_SET:
- LOG_ALWAYS_FATAL("invalid parameters");
- }
-}
-
-// TODO(jpawlowski): remove once we have config file abstraction in cert tests
-void LeAddressManager::SetPrivacyPolicyForInitiatorAddressForTest(
- AddressPolicy address_policy,
- AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time) {
- ASSERT(address_policy != AddressPolicy::POLICY_NOT_SET);
- ASSERT_LOG(registered_clients_.empty(), "Policy must be set before clients are registered.");
- address_policy_ = address_policy;
-
- switch (address_policy_) {
- case AddressPolicy::USE_PUBLIC_ADDRESS:
- le_address_ = fixed_address;
- break;
- case AddressPolicy::USE_STATIC_ADDRESS: {
- auto addr = fixed_address.GetAddress();
- auto address = addr.address;
- // The two most significant bits of the static address shall be equal to 1
- ASSERT_LOG((address[5] & BLE_ADDR_MASK) == BLE_ADDR_MASK, "The two most significant bits shall be equal to 1");
- // Bits of the random part of the address shall not be all 1 or all 0
- if ((address[0] == 0x00 && address[1] == 0x00 && address[2] == 0x00 && address[3] == 0x00 && address[4] == 0x00 &&
- address[5] == BLE_ADDR_MASK) ||
- (address[0] == 0xFF && address[1] == 0xFF && address[2] == 0xFF && address[3] == 0xFF && address[4] == 0xFF &&
- address[5] == 0xFF)) {
- LOG_ALWAYS_FATAL("Bits of the random part of the address shall not be all 1 or all 0");
- }
- le_address_ = fixed_address;
- auto packet = hci::LeSetRandomAddressBuilder::Create(le_address_.GetAddress());
- handler_->Call(enqueue_command_, std::move(packet));
- } break;
- case AddressPolicy::USE_NON_RESOLVABLE_ADDRESS:
- case AddressPolicy::USE_RESOLVABLE_ADDRESS:
- rotation_irk_ = rotation_irk;
- minimum_rotation_time_ = minimum_rotation_time;
- maximum_rotation_time_ = maximum_rotation_time;
- address_rotation_alarm_ = std::make_unique<os::Alarm>(handler_);
- break;
- case AddressPolicy::POLICY_NOT_SET:
- LOG_ALWAYS_FATAL("invalid parameters");
- }
-}
-LeAddressManager::AddressPolicy LeAddressManager::GetAddressPolicy() {
- return address_policy_;
-}
-
-LeAddressManager::AddressPolicy LeAddressManager::Register(LeAddressManagerCallback* callback) {
- handler_->BindOnceOn(this, &LeAddressManager::register_client, callback).Invoke();
- return address_policy_;
-}
-
-void LeAddressManager::register_client(LeAddressManagerCallback* callback) {
- registered_clients_.insert(std::pair<LeAddressManagerCallback*, ClientState>(callback, ClientState::RESUMED));
- if (address_policy_ == AddressPolicy::POLICY_NOT_SET) {
- LOG_INFO("address policy isn't set yet, pause clients and return");
- pause_registered_clients();
- return;
- } else if (
- address_policy_ == AddressPolicy::USE_RESOLVABLE_ADDRESS ||
- address_policy_ == AddressPolicy::USE_NON_RESOLVABLE_ADDRESS) {
- if (bluetooth::common::init_flags::gd_acl_is_enabled() || bluetooth::common::init_flags::gd_l2cap_is_enabled()) {
- if (registered_clients_.size() == 1) {
- schedule_rotate_random_address();
- }
- } else {
- prepare_to_rotate();
- }
- }
-}
-
-void LeAddressManager::Unregister(LeAddressManagerCallback* callback) {
- handler_->BindOnceOn(this, &LeAddressManager::unregister_client, callback).Invoke();
-}
-
-void LeAddressManager::unregister_client(LeAddressManagerCallback* callback) {
- registered_clients_.erase(callback);
- if (registered_clients_.empty() && address_rotation_alarm_ != nullptr) {
- address_rotation_alarm_->Cancel();
- }
-}
-
-void LeAddressManager::AckPause(LeAddressManagerCallback* callback) {
- handler_->BindOnceOn(this, &LeAddressManager::ack_pause, callback).Invoke();
-}
-
-void LeAddressManager::AckResume(LeAddressManagerCallback* callback) {
- handler_->BindOnceOn(this, &LeAddressManager::ack_resume, callback).Invoke();
-}
-
-AddressWithType LeAddressManager::GetCurrentAddress() {
- ASSERT(address_policy_ != AddressPolicy::POLICY_NOT_SET);
- return le_address_;
-}
-
-AddressWithType LeAddressManager::GetAnotherAddress() {
- ASSERT(
- address_policy_ == AddressPolicy::USE_NON_RESOLVABLE_ADDRESS ||
- address_policy_ == AddressPolicy::USE_RESOLVABLE_ADDRESS);
- hci::Address address = generate_rpa();
- auto random_address = AddressWithType(address, AddressType::RANDOM_DEVICE_ADDRESS);
- return random_address;
-}
-
-void LeAddressManager::pause_registered_clients() {
- for (auto& client : registered_clients_) {
- if (client.second != ClientState::PAUSED && client.second != ClientState::WAITING_FOR_PAUSE) {
- client.second = ClientState::WAITING_FOR_PAUSE;
- client.first->OnPause();
- }
- }
-}
-
-void LeAddressManager::push_command(Command command) {
- pause_registered_clients();
- cached_commands_.push(std::move(command));
-}
-
-void LeAddressManager::ack_pause(LeAddressManagerCallback* callback) {
- ASSERT(registered_clients_.find(callback) != registered_clients_.end());
- registered_clients_.find(callback)->second = ClientState::PAUSED;
- for (auto client : registered_clients_) {
- if (client.second != ClientState::PAUSED) {
- // make sure all client paused
- return;
- }
- }
-
- if (address_policy_ != AddressPolicy::POLICY_NOT_SET) {
- handle_next_command();
- }
-}
-
-void LeAddressManager::resume_registered_clients() {
- // Do not resume clients if cached command is not empty
- if (!cached_commands_.empty()) {
- handle_next_command();
- return;
- }
-
- for (auto& client : registered_clients_) {
- client.second = ClientState::WAITING_FOR_RESUME;
- client.first->OnResume();
- }
-}
-
-void LeAddressManager::ack_resume(LeAddressManagerCallback* callback) {
- ASSERT(registered_clients_.find(callback) != registered_clients_.end());
- registered_clients_.find(callback)->second = ClientState::RESUMED;
-}
-
-void LeAddressManager::prepare_to_rotate() {
- Command command = {CommandType::ROTATE_RANDOM_ADDRESS, nullptr};
- cached_commands_.push(std::move(command));
- pause_registered_clients();
-}
-
-void LeAddressManager::schedule_rotate_random_address() {
- address_rotation_alarm_->Schedule(
- common::BindOnce(&LeAddressManager::prepare_to_rotate, common::Unretained(this)),
- GetNextPrivateAddressIntervalMs());
-}
-
-void LeAddressManager::set_random_address() {
- if (address_policy_ != AddressPolicy::USE_RESOLVABLE_ADDRESS &&
- address_policy_ != AddressPolicy::USE_NON_RESOLVABLE_ADDRESS) {
- LOG_ALWAYS_FATAL("Invalid address policy!");
- return;
- }
-
- hci::Address address;
- if (address_policy_ == AddressPolicy::USE_RESOLVABLE_ADDRESS) {
- address = generate_rpa();
- } else {
- address = generate_nrpa();
- }
- auto packet = hci::LeSetRandomAddressBuilder::Create(address);
- enqueue_command_.Run(std::move(packet));
- cached_address_ = AddressWithType(address, AddressType::RANDOM_DEVICE_ADDRESS);
-}
-
-void LeAddressManager::rotate_random_address() {
- if (address_policy_ != AddressPolicy::USE_RESOLVABLE_ADDRESS &&
- address_policy_ != AddressPolicy::USE_NON_RESOLVABLE_ADDRESS) {
- LOG_ALWAYS_FATAL("Invalid address policy!");
- return;
- }
-
- schedule_rotate_random_address();
- set_random_address();
-}
-
-/* This function generates Resolvable Private Address (RPA) from Identity
- * Resolving Key |irk| and |prand|*/
-hci::Address LeAddressManager::generate_rpa() {
- // most significant bit, bit7, bit6 is 01 to be resolvable random
- // Bits of the random part of prand shall not be all 1 or all 0
- std::array<uint8_t, 3> prand = os::GenerateRandom<3>();
- constexpr uint8_t BLE_RESOLVE_ADDR_MSB = 0x40;
- prand[2] &= ~BLE_ADDR_MASK;
- if ((prand[0] == 0x00 && prand[1] == 0x00 && prand[2] == 0x00) ||
- (prand[0] == 0xFF && prand[1] == 0xFF && prand[2] == 0x3F)) {
- prand[0] = (uint8_t)(os::GenerateRandom() % 0xFE + 1);
- }
- prand[2] |= BLE_RESOLVE_ADDR_MSB;
-
- hci::Address address;
- address.address[3] = prand[0];
- address.address[4] = prand[1];
- address.address[5] = prand[2];
-
- /* encrypt with IRK */
- crypto_toolbox::Octet16 p = crypto_toolbox::aes_128(rotation_irk_, prand.data(), 3);
-
- /* set hash to be LSB of rpAddress */
- address.address[0] = p[0];
- address.address[1] = p[1];
- address.address[2] = p[2];
- return address;
-}
-
-// This function generates NON-Resolvable Private Address (NRPA)
-hci::Address LeAddressManager::generate_nrpa() {
- // The two most significant bits of the address shall be equal to 0
- // Bits of the random part of the address shall not be all 1 or all 0
- std::array<uint8_t, 6> random = os::GenerateRandom<6>();
- random[5] &= ~BLE_ADDR_MASK;
- if ((random[0] == 0x00 && random[1] == 0x00 && random[2] == 0x00 && random[3] == 0x00 && random[4] == 0x00 &&
- random[5] == 0x00) ||
- (random[0] == 0xFF && random[1] == 0xFF && random[2] == 0xFF && random[3] == 0xFF && random[4] == 0xFF &&
- random[5] == 0x3F)) {
- random[0] = (uint8_t)(os::GenerateRandom() % 0xFE + 1);
- }
-
- hci::Address address;
- address.FromOctets(random.data());
-
- // the address shall not be equal to the public address
- while (address == public_address_) {
- address.address[0] = (uint8_t)(os::GenerateRandom() % 0xFE + 1);
- }
-
- return address;
-}
-
-std::chrono::milliseconds LeAddressManager::GetNextPrivateAddressIntervalMs() {
- auto interval_random_part_max_ms = maximum_rotation_time_ - minimum_rotation_time_;
- auto random_ms = std::chrono::milliseconds(os::GenerateRandom()) % (interval_random_part_max_ms);
- return minimum_rotation_time_ + random_ms;
-}
-
-uint8_t LeAddressManager::GetConnectListSize() {
- return connect_list_size_;
-}
-
-uint8_t LeAddressManager::GetResolvingListSize() {
- return resolving_list_size_;
-}
-
-void LeAddressManager::handle_next_command() {
- for (auto client : registered_clients_) {
- if (client.second != ClientState::PAUSED) {
- // make sure all client paused, if not, this function will be trigger again by ack_pause
- LOG_INFO("waiting for ack_pause, return");
- return;
- }
- }
-
- ASSERT(!cached_commands_.empty());
- auto command = std::move(cached_commands_.front());
- cached_commands_.pop();
-
- if (command.command_type == CommandType::ROTATE_RANDOM_ADDRESS) {
- rotate_random_address();
- } else {
- enqueue_command_.Run(std::move(command.command_packet));
- }
-}
-
-void LeAddressManager::AddDeviceToConnectList(
- ConnectListAddressType connect_list_address_type, bluetooth::hci::Address address) {
- auto packet_builder = hci::LeAddDeviceToConnectListBuilder::Create(connect_list_address_type, address);
- Command command = {CommandType::ADD_DEVICE_TO_CONNECT_LIST, std::move(packet_builder)};
- handler_->BindOnceOn(this, &LeAddressManager::push_command, std::move(command)).Invoke();
-}
-
-void LeAddressManager::AddDeviceToResolvingList(
- PeerAddressType peer_identity_address_type,
- Address peer_identity_address,
- const std::array<uint8_t, 16>& peer_irk,
- const std::array<uint8_t, 16>& local_irk) {
- auto packet_builder = hci::LeAddDeviceToResolvingListBuilder::Create(
- peer_identity_address_type, peer_identity_address, peer_irk, local_irk);
- Command command = {CommandType::ADD_DEVICE_TO_RESOLVING_LIST, std::move(packet_builder)};
- handler_->BindOnceOn(this, &LeAddressManager::push_command, std::move(command)).Invoke();
-}
-
-void LeAddressManager::RemoveDeviceFromConnectList(
- ConnectListAddressType connect_list_address_type, bluetooth::hci::Address address) {
- auto packet_builder = hci::LeRemoveDeviceFromConnectListBuilder::Create(connect_list_address_type, address);
- Command command = {CommandType::REMOVE_DEVICE_FROM_CONNECT_LIST, std::move(packet_builder)};
- handler_->BindOnceOn(this, &LeAddressManager::push_command, std::move(command)).Invoke();
-}
-
-void LeAddressManager::RemoveDeviceFromResolvingList(
- PeerAddressType peer_identity_address_type, Address peer_identity_address) {
- auto packet_builder =
- hci::LeRemoveDeviceFromResolvingListBuilder::Create(peer_identity_address_type, peer_identity_address);
- Command command = {CommandType::REMOVE_DEVICE_FROM_RESOLVING_LIST, std::move(packet_builder)};
- handler_->BindOnceOn(this, &LeAddressManager::push_command, std::move(command)).Invoke();
-}
-
-void LeAddressManager::ClearConnectList() {
- auto packet_builder = hci::LeClearConnectListBuilder::Create();
- Command command = {CommandType::CLEAR_CONNECT_LIST, std::move(packet_builder)};
- handler_->BindOnceOn(this, &LeAddressManager::push_command, std::move(command)).Invoke();
-}
-
-void LeAddressManager::ClearResolvingList() {
- auto packet_builder = hci::LeClearResolvingListBuilder::Create();
- Command command = {CommandType::CLEAR_RESOLVING_LIST, std::move(packet_builder)};
- handler_->BindOnceOn(this, &LeAddressManager::push_command, std::move(command)).Invoke();
-}
-
-void LeAddressManager::OnCommandComplete(bluetooth::hci::CommandCompleteView view) {
- if (!view.IsValid()) {
- LOG_ERROR("Received command complete with invalid packet");
- return;
- }
- std::string op_code = OpCodeText(view.GetCommandOpCode());
- LOG_INFO("Received command complete with op_code %s", op_code.c_str());
-
- // The command was sent before any client registered, we can make sure all the clients paused when command complete.
- if (view.GetCommandOpCode() == OpCode::LE_SET_RANDOM_ADDRESS) {
- if (address_policy_ == AddressPolicy::USE_STATIC_ADDRESS) {
- LOG_INFO("Received LE_SET_RANDOM_ADDRESS complete and Address policy is USE_STATIC_ADDRESS, return");
- return;
- }
- auto complete_view = LeSetRandomAddressCompleteView::Create(view);
- if (!complete_view.IsValid()) {
- LOG_ERROR("Received LE_SET_RANDOM_ADDRESS complete with invalid packet");
- } else if (complete_view.IsValid() && complete_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_ERROR(
- "Received LE_SET_RANDOM_ADDRESS complete with status %s", ErrorCodeText(complete_view.GetStatus()).c_str());
- } else {
- LOG_INFO("update random address : %s", cached_address_.GetAddress().ToString().c_str());
- le_address_ = cached_address_;
- }
- }
-
- if (cached_commands_.empty()) {
- handler_->BindOnceOn(this, &LeAddressManager::resume_registered_clients).Invoke();
- } else {
- handler_->BindOnceOn(this, &LeAddressManager::handle_next_command).Invoke();
- }
-}
-
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/le_address_manager.h b/gd/hci/le_address_manager.h
deleted file mode 100644
index 9624c218f..000000000
--- a/gd/hci/le_address_manager.h
+++ /dev/null
@@ -1,148 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <map>
-#include <mutex>
-#include <set>
-
-#include "common/callback.h"
-#include "hci/address_with_type.h"
-#include "hci/hci_layer.h"
-#include "os/alarm.h"
-
-namespace bluetooth {
-namespace hci {
-
-class LeAddressManagerCallback {
- public:
- virtual ~LeAddressManagerCallback() = default;
- virtual void OnPause() = 0;
- virtual void OnResume() = 0;
-};
-
-class LeAddressManager {
- public:
- LeAddressManager(
- common::Callback<void(std::unique_ptr<CommandBuilder>)> enqueue_command,
- os::Handler* handler,
- Address public_address,
- uint8_t connect_list_size,
- uint8_t resolving_list_size);
- virtual ~LeAddressManager();
-
- enum AddressPolicy {
- POLICY_NOT_SET,
- USE_PUBLIC_ADDRESS,
- USE_STATIC_ADDRESS,
- USE_NON_RESOLVABLE_ADDRESS,
- USE_RESOLVABLE_ADDRESS
- };
-
- // Aborts if called more than once
- void SetPrivacyPolicyForInitiatorAddress(
- AddressPolicy address_policy,
- AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time);
- // TODO(jpawlowski): remove once we have config file abstraction in cert tests
- void SetPrivacyPolicyForInitiatorAddressForTest(
- AddressPolicy address_policy,
- AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time);
- AddressPolicy GetAddressPolicy();
- void AckPause(LeAddressManagerCallback* callback);
- void AckResume(LeAddressManagerCallback* callback);
- virtual AddressPolicy Register(LeAddressManagerCallback* callback);
- virtual void Unregister(LeAddressManagerCallback* callback);
- AddressWithType GetCurrentAddress(); // What was set in SetRandomAddress()
- virtual AddressWithType GetAnotherAddress(); // A new random address without rotating.
-
- uint8_t GetConnectListSize();
- uint8_t GetResolvingListSize();
- void AddDeviceToConnectList(ConnectListAddressType connect_list_address_type, Address address);
- void AddDeviceToResolvingList(
- PeerAddressType peer_identity_address_type,
- Address peer_identity_address,
- const std::array<uint8_t, 16>& peer_irk,
- const std::array<uint8_t, 16>& local_irk);
- void RemoveDeviceFromConnectList(ConnectListAddressType connect_list_address_type, Address address);
- void RemoveDeviceFromResolvingList(PeerAddressType peer_identity_address_type, Address peer_identity_address);
- void ClearConnectList();
- void ClearResolvingList();
- void OnCommandComplete(CommandCompleteView view);
- std::chrono::milliseconds GetNextPrivateAddressIntervalMs();
-
- private:
- enum ClientState {
- WAITING_FOR_PAUSE,
- PAUSED,
- WAITING_FOR_RESUME,
- RESUMED,
- };
-
- enum CommandType {
- ROTATE_RANDOM_ADDRESS,
- ADD_DEVICE_TO_CONNECT_LIST,
- REMOVE_DEVICE_FROM_CONNECT_LIST,
- CLEAR_CONNECT_LIST,
- ADD_DEVICE_TO_RESOLVING_LIST,
- REMOVE_DEVICE_FROM_RESOLVING_LIST,
- CLEAR_RESOLVING_LIST
- };
-
- struct Command {
- CommandType command_type;
- std::unique_ptr<CommandBuilder> command_packet;
- };
-
- void pause_registered_clients();
- void push_command(Command command);
- void ack_pause(LeAddressManagerCallback* callback);
- void resume_registered_clients();
- void ack_resume(LeAddressManagerCallback* callback);
- void register_client(LeAddressManagerCallback* callback);
- void unregister_client(LeAddressManagerCallback* callback);
- void prepare_to_rotate();
- void rotate_random_address();
- void schedule_rotate_random_address();
- void set_random_address();
- hci::Address generate_rpa();
- hci::Address generate_nrpa();
- void handle_next_command();
-
- common::Callback<void(std::unique_ptr<CommandBuilder>)> enqueue_command_;
- os::Handler* handler_;
- std::map<LeAddressManagerCallback*, ClientState> registered_clients_;
-
- AddressPolicy address_policy_ = AddressPolicy::POLICY_NOT_SET;
- AddressWithType le_address_;
- AddressWithType cached_address_;
- Address public_address_;
- std::unique_ptr<os::Alarm> address_rotation_alarm_;
- crypto_toolbox::Octet16 rotation_irk_;
- std::chrono::milliseconds minimum_rotation_time_;
- std::chrono::milliseconds maximum_rotation_time_;
- uint8_t connect_list_size_;
- uint8_t resolving_list_size_;
- std::queue<Command> cached_commands_;
-};
-
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/le_address_manager_test.cc b/gd/hci/le_address_manager_test.cc
deleted file mode 100644
index 237a30c6f..000000000
--- a/gd/hci/le_address_manager_test.cc
+++ /dev/null
@@ -1,463 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/le_address_manager.h"
-
-#include <gtest/gtest.h>
-
-#include "common/init_flags.h"
-#include "os/log.h"
-#include "packet/raw_builder.h"
-
-using ::bluetooth::crypto_toolbox::Octet16;
-using ::bluetooth::os::Handler;
-using ::bluetooth::os::Thread;
-
-namespace bluetooth {
-namespace hci {
-
-using packet::kLittleEndian;
-using packet::PacketView;
-using packet::RawBuilder;
-
-PacketView<kLittleEndian> GetPacketView(std::unique_ptr<packet::BasePacketBuilder> packet) {
- auto bytes = std::make_shared<std::vector<uint8_t>>();
- BitInserter i(*bytes);
- bytes->reserve(packet->size());
- packet->Serialize(i);
- return packet::PacketView<packet::kLittleEndian>(bytes);
-}
-
-class TestHciLayer : public HciLayer {
- public:
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(CommandCompleteView)> on_complete) override {
- std::lock_guard<std::mutex> lock(mutex_);
- command_queue_.push(std::move(command));
- command_complete_callbacks.push_back(std::move(on_complete));
- if (command_promise_ != nullptr) {
- command_promise_->set_value();
- command_promise_.reset();
- }
- }
-
- void SetCommandFuture() {
- ASSERT_LOG(command_promise_ == nullptr, "Promises, Promises, ... Only one at a time.");
- command_promise_ = std::make_unique<std::promise<void>>();
- command_future_ = std::make_unique<std::future<void>>(command_promise_->get_future());
- }
-
- CommandView GetLastCommand() {
- if (command_queue_.size() == 0) {
- return CommandView::Create(PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>()));
- }
- auto last = std::move(command_queue_.front());
- command_queue_.pop();
- return CommandView::Create(GetPacketView(std::move(last)));
- }
-
- CommandView GetCommand(OpCode op_code) {
- if (!command_queue_.empty()) {
- std::lock_guard<std::mutex> lock(mutex_);
- if (command_future_ != nullptr) {
- command_future_.reset();
- command_promise_.reset();
- }
- } else if (command_future_ != nullptr) {
- auto result = command_future_->wait_for(std::chrono::milliseconds(1000));
- EXPECT_NE(std::future_status::timeout, result);
- }
- std::lock_guard<std::mutex> lock(mutex_);
- ASSERT_LOG(
- !command_queue_.empty(), "Expecting command %s but command queue was empty", OpCodeText(op_code).c_str());
- CommandView command_packet_view = GetLastCommand();
- EXPECT_TRUE(command_packet_view.IsValid());
- EXPECT_EQ(command_packet_view.GetOpCode(), op_code);
- return command_packet_view;
- }
-
- void IncomingEvent(std::unique_ptr<EventBuilder> event_builder) {
- auto packet = GetPacketView(std::move(event_builder));
- EventView event = EventView::Create(packet);
- ASSERT_TRUE(event.IsValid());
- CommandCompleteCallback(event);
- }
-
- void CommandCompleteCallback(EventView event) {
- CommandCompleteView complete_view = CommandCompleteView::Create(event);
- ASSERT_TRUE(complete_view.IsValid());
- std::move(command_complete_callbacks.front()).Invoke(complete_view);
- command_complete_callbacks.pop_front();
- }
-
- void ListDependencies(ModuleList* list) override {}
- void Start() override {}
- void Stop() override {}
-
- private:
- std::list<common::ContextualOnceCallback<void(CommandCompleteView)>> command_complete_callbacks;
- std::queue<std::unique_ptr<CommandBuilder>> command_queue_;
- std::unique_ptr<std::promise<void>> command_promise_;
- std::unique_ptr<std::future<void>> command_future_;
- mutable std::mutex mutex_;
-};
-
-class RotatorClient : public LeAddressManagerCallback {
- public:
- RotatorClient(LeAddressManager* le_address_manager, size_t id) : le_address_manager_(le_address_manager), id_(id){};
-
- void OnPause() {
- paused = true;
- le_address_manager_->AckPause(this);
- }
-
- void OnResume() {
- paused = false;
- le_address_manager_->AckResume(this);
- if (resume_promise_ != nullptr) {
- resume_promise_->set_value();
- resume_promise_.reset();
- }
- }
-
- void WaitForResume() {
- if (paused) {
- resume_promise_ = std::make_unique<std::promise<void>>();
- auto resume_future = resume_promise_->get_future();
- auto result = resume_future.wait_for(std::chrono::milliseconds(1000));
- EXPECT_NE(std::future_status::timeout, result);
- }
- }
-
- bool paused{false};
- LeAddressManager* le_address_manager_;
- size_t id_;
- std::unique_ptr<std::promise<void>> resume_promise_;
-};
-
-class LeAddressManagerTest : public ::testing::Test {
- public:
- void SetUp() override {
- thread_ = new Thread("thread", Thread::Priority::NORMAL);
- handler_ = new Handler(thread_);
- test_hci_layer_ = new TestHciLayer;
- Address address({0x01, 0x02, 0x03, 0x04, 0x05, 0x06});
- le_address_manager_ = new LeAddressManager(
- common::Bind(&LeAddressManagerTest::enqueue_command, common::Unretained(this)), handler_, address, 0x3F, 0x3F);
- AllocateClients(1);
- }
-
- void sync_handler(os::Handler* handler) {
- std::promise<void> promise;
- auto future = promise.get_future();
- handler_->Post(common::BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)));
- auto future_status = future.wait_for(std::chrono::seconds(1));
- EXPECT_EQ(future_status, std::future_status::ready);
- }
-
- void TearDown() override {
- sync_handler(handler_);
- delete le_address_manager_;
- delete test_hci_layer_;
- handler_->Clear();
- delete handler_;
- delete thread_;
- }
-
- void AllocateClients(size_t num_clients) {
- size_t first_id = clients.size();
- for (size_t i = 0; i < num_clients; i++) {
- clients.emplace_back(std::make_unique<RotatorClient>(le_address_manager_, first_id + i));
- }
- }
-
- void enqueue_command(std::unique_ptr<CommandBuilder> command_packet) {
- test_hci_layer_->EnqueueCommand(
- std::move(command_packet),
- handler_->BindOnce(&LeAddressManager::OnCommandComplete, common::Unretained(le_address_manager_)));
- }
-
- Thread* thread_;
- Handler* handler_;
- TestHciLayer* test_hci_layer_ = nullptr;
- LeAddressManager* le_address_manager_;
- std::vector<std::unique_ptr<RotatorClient>> clients;
-};
-
-TEST_F(LeAddressManagerTest, startup_teardown) {}
-
-TEST_F(LeAddressManagerTest, register_unregister_callback) {
- le_address_manager_->Register(clients[0].get());
- sync_handler(handler_);
- le_address_manager_->Unregister(clients[0].get());
- sync_handler(handler_);
-}
-
-TEST_F(LeAddressManagerTest, rotator_address_for_single_client) {
- Octet16 irk = {0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05, 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
- auto minimum_rotation_time = std::chrono::milliseconds(1000);
- auto maximum_rotation_time = std::chrono::milliseconds(3000);
- AddressWithType remote_address(Address::kEmpty, AddressType::RANDOM_DEVICE_ADDRESS);
- le_address_manager_->SetPrivacyPolicyForInitiatorAddress(
- LeAddressManager::AddressPolicy::USE_RESOLVABLE_ADDRESS,
- remote_address,
- irk,
- minimum_rotation_time,
- maximum_rotation_time);
-
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->Register(clients[0].get());
- sync_handler(handler_);
- test_hci_layer_->GetCommand(OpCode::LE_SET_RANDOM_ADDRESS);
- test_hci_layer_->IncomingEvent(LeSetRandomAddressCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- clients[0].get()->WaitForResume();
- le_address_manager_->Unregister(clients[0].get());
- sync_handler(handler_);
-}
-
-TEST_F(LeAddressManagerTest, rotator_non_resolvable_address_for_single_client) {
- Octet16 irk = {};
- auto minimum_rotation_time = std::chrono::milliseconds(1000);
- auto maximum_rotation_time = std::chrono::milliseconds(3000);
- AddressWithType remote_address(Address::kEmpty, AddressType::RANDOM_DEVICE_ADDRESS);
- le_address_manager_->SetPrivacyPolicyForInitiatorAddress(
- LeAddressManager::AddressPolicy::USE_NON_RESOLVABLE_ADDRESS,
- remote_address,
- irk,
- minimum_rotation_time,
- maximum_rotation_time);
-
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->Register(clients[0].get());
- sync_handler(handler_);
- test_hci_layer_->GetCommand(OpCode::LE_SET_RANDOM_ADDRESS);
- test_hci_layer_->IncomingEvent(LeSetRandomAddressCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- clients[0].get()->WaitForResume();
- le_address_manager_->Unregister(clients[0].get());
- sync_handler(handler_);
-}
-
-// TODO handle the case "register during rotate_random_address" and enable this
-TEST_F(LeAddressManagerTest, DISABLED_rotator_address_for_multiple_clients) {
- AllocateClients(2);
- Octet16 irk = {0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05, 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
- auto minimum_rotation_time = std::chrono::milliseconds(1000);
- auto maximum_rotation_time = std::chrono::milliseconds(3000);
- AddressWithType remote_address(Address::kEmpty, AddressType::RANDOM_DEVICE_ADDRESS);
- le_address_manager_->SetPrivacyPolicyForInitiatorAddress(
- LeAddressManager::AddressPolicy::USE_RESOLVABLE_ADDRESS,
- remote_address,
- irk,
- minimum_rotation_time,
- maximum_rotation_time);
- le_address_manager_->Register(clients[0].get());
- le_address_manager_->Register(clients[1].get());
- le_address_manager_->Register(clients[2].get());
- sync_handler(handler_);
-
- le_address_manager_->Unregister(clients[0].get());
- le_address_manager_->Unregister(clients[1].get());
- le_address_manager_->Unregister(clients[2].get());
- sync_handler(handler_);
-}
-
-class LeAddressManagerWithSingleClientTest : public LeAddressManagerTest {
- public:
- void SetUp() override {
- bluetooth::common::InitFlags::SetAllForTesting();
- thread_ = new Thread("thread", Thread::Priority::NORMAL);
- handler_ = new Handler(thread_);
- test_hci_layer_ = new TestHciLayer;
- Address address({0x01, 0x02, 0x03, 0x04, 0x05, 0x06});
- le_address_manager_ = new LeAddressManager(
- common::Bind(&LeAddressManagerWithSingleClientTest::enqueue_command, common::Unretained(this)),
- handler_,
- address,
- 0x3F,
- 0x3F);
- AllocateClients(1);
-
- Octet16 irk = {0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05, 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
- auto minimum_rotation_time = std::chrono::milliseconds(1000);
- auto maximum_rotation_time = std::chrono::milliseconds(3000);
- AddressWithType remote_address(Address::kEmpty, AddressType::RANDOM_DEVICE_ADDRESS);
- le_address_manager_->SetPrivacyPolicyForInitiatorAddress(
- LeAddressManager::AddressPolicy::USE_RESOLVABLE_ADDRESS,
- remote_address,
- irk,
- minimum_rotation_time,
- maximum_rotation_time);
-
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->Register(clients[0].get());
- sync_handler(handler_);
- test_hci_layer_->GetCommand(OpCode::LE_SET_RANDOM_ADDRESS);
- test_hci_layer_->IncomingEvent(LeSetRandomAddressCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- }
-
- void enqueue_command(std::unique_ptr<CommandBuilder> command_packet) {
- test_hci_layer_->EnqueueCommand(
- std::move(command_packet),
- handler_->BindOnce(&LeAddressManager::OnCommandComplete, common::Unretained(le_address_manager_)));
- }
-
- void TearDown() override {
- le_address_manager_->Unregister(clients[0].get());
- sync_handler(handler_);
- delete le_address_manager_;
- delete test_hci_layer_;
- handler_->Clear();
- delete handler_;
- delete thread_;
- }
-};
-
-TEST_F(LeAddressManagerWithSingleClientTest, add_device_to_connect_list) {
- Address address;
- Address::FromString("01:02:03:04:05:06", address);
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->AddDeviceToConnectList(ConnectListAddressType::RANDOM, address);
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- auto packet_view =
- LeAddDeviceToConnectListView::Create(LeConnectionManagementCommandView::Create(AclCommandView::Create(packet)));
- ASSERT_TRUE(packet_view.IsValid());
- ASSERT_EQ(ConnectListAddressType::RANDOM, packet_view.GetAddressType());
- ASSERT_EQ(address, packet_view.GetAddress());
-
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- clients[0].get()->WaitForResume();
-}
-
-TEST_F(LeAddressManagerWithSingleClientTest, remove_device_from_connect_list) {
- Address address;
- Address::FromString("01:02:03:04:05:06", address);
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->AddDeviceToConnectList(ConnectListAddressType::RANDOM, address);
- test_hci_layer_->GetCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->RemoveDeviceFromConnectList(ConnectListAddressType::RANDOM, address);
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_REMOVE_DEVICE_FROM_CONNECT_LIST);
- auto packet_view = LeRemoveDeviceFromConnectListView::Create(
- LeConnectionManagementCommandView::Create(AclCommandView::Create(packet)));
- ASSERT_TRUE(packet_view.IsValid());
- ASSERT_EQ(ConnectListAddressType::RANDOM, packet_view.GetAddressType());
- ASSERT_EQ(address, packet_view.GetAddress());
- test_hci_layer_->IncomingEvent(LeRemoveDeviceFromConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- clients[0].get()->WaitForResume();
-}
-
-TEST_F(LeAddressManagerWithSingleClientTest, clear_connect_list) {
- Address address;
- Address::FromString("01:02:03:04:05:06", address);
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->AddDeviceToConnectList(ConnectListAddressType::RANDOM, address);
- test_hci_layer_->GetCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->ClearConnectList();
- test_hci_layer_->GetCommand(OpCode::LE_CLEAR_CONNECT_LIST);
- test_hci_layer_->IncomingEvent(LeClearConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- clients[0].get()->WaitForResume();
-}
-
-TEST_F(LeAddressManagerWithSingleClientTest, add_device_to_resolving_list) {
- Address address;
- Address::FromString("01:02:03:04:05:06", address);
- Octet16 peer_irk = {0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05, 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
- Octet16 local_irk = {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10};
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->AddDeviceToResolvingList(
- PeerAddressType::RANDOM_DEVICE_OR_IDENTITY_ADDRESS, address, peer_irk, local_irk);
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_ADD_DEVICE_TO_RESOLVING_LIST);
- auto packet_view = LeAddDeviceToResolvingListView::Create(LeSecurityCommandView::Create(packet));
- ASSERT_TRUE(packet_view.IsValid());
- ASSERT_EQ(PeerAddressType::RANDOM_DEVICE_OR_IDENTITY_ADDRESS, packet_view.GetPeerIdentityAddressType());
- ASSERT_EQ(address, packet_view.GetPeerIdentityAddress());
- ASSERT_EQ(peer_irk, packet_view.GetPeerIrk());
- ASSERT_EQ(local_irk, packet_view.GetLocalIrk());
-
- test_hci_layer_->IncomingEvent(LeAddDeviceToResolvingListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- clients[0].get()->WaitForResume();
-}
-
-TEST_F(LeAddressManagerWithSingleClientTest, remove_device_from_resolving_list) {
- Address address;
- Address::FromString("01:02:03:04:05:06", address);
- Octet16 peer_irk = {0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05, 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
- Octet16 local_irk = {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10};
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->AddDeviceToResolvingList(
- PeerAddressType::RANDOM_DEVICE_OR_IDENTITY_ADDRESS, address, peer_irk, local_irk);
- test_hci_layer_->GetCommand(OpCode::LE_ADD_DEVICE_TO_RESOLVING_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToResolvingListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->RemoveDeviceFromResolvingList(PeerAddressType::RANDOM_DEVICE_OR_IDENTITY_ADDRESS, address);
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_REMOVE_DEVICE_FROM_RESOLVING_LIST);
- auto packet_view = LeRemoveDeviceFromResolvingListView::Create(LeSecurityCommandView::Create(packet));
- ASSERT_TRUE(packet_view.IsValid());
- ASSERT_EQ(PeerAddressType::RANDOM_DEVICE_OR_IDENTITY_ADDRESS, packet_view.GetPeerIdentityAddressType());
- ASSERT_EQ(address, packet_view.GetPeerIdentityAddress());
- test_hci_layer_->IncomingEvent(LeRemoveDeviceFromResolvingListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- clients[0].get()->WaitForResume();
-}
-
-TEST_F(LeAddressManagerWithSingleClientTest, clear_resolving_list) {
- Address address;
- Address::FromString("01:02:03:04:05:06", address);
- Octet16 peer_irk = {0xec, 0x02, 0x34, 0xa3, 0x57, 0xc8, 0xad, 0x05, 0x34, 0x10, 0x10, 0xa6, 0x0a, 0x39, 0x7d, 0x9b};
- Octet16 local_irk = {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f, 0x10};
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->AddDeviceToResolvingList(
- PeerAddressType::RANDOM_DEVICE_OR_IDENTITY_ADDRESS, address, peer_irk, local_irk);
- test_hci_layer_->GetCommand(OpCode::LE_ADD_DEVICE_TO_RESOLVING_LIST);
- test_hci_layer_->IncomingEvent(LeAddDeviceToResolvingListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->ClearResolvingList();
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_CLEAR_RESOLVING_LIST);
- auto packet_view = LeClearResolvingListView::Create(LeSecurityCommandView::Create(packet));
- ASSERT_TRUE(packet_view.IsValid());
- test_hci_layer_->IncomingEvent(LeClearResolvingListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
- clients[0].get()->WaitForResume();
-}
-
-TEST_F(LeAddressManagerWithSingleClientTest, register_during_command_complete) {
- Address address;
- Address::FromString("01:02:03:04:05:06", address);
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->AddDeviceToConnectList(ConnectListAddressType::RANDOM, address);
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_ADD_DEVICE_TO_CONNECT_LIST);
- auto packet_view =
- LeAddDeviceToConnectListView::Create(LeConnectionManagementCommandView::Create(AclCommandView::Create(packet)));
- ASSERT_TRUE(packet_view.IsValid());
- ASSERT_EQ(ConnectListAddressType::RANDOM, packet_view.GetAddressType());
- ASSERT_EQ(address, packet_view.GetAddress());
- test_hci_layer_->IncomingEvent(LeAddDeviceToConnectListCompleteBuilder::Create(0x01, ErrorCode::SUCCESS));
-
- AllocateClients(1);
- test_hci_layer_->SetCommandFuture();
- le_address_manager_->Register(clients[1].get());
- clients[0].get()->WaitForResume();
- clients[1].get()->WaitForResume();
-}
-
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/le_advertising_interface.h b/gd/hci/le_advertising_interface.h
index c419c4268..f915c0247 100644
--- a/gd/hci/le_advertising_interface.h
+++ b/gd/hci/le_advertising_interface.h
@@ -16,18 +16,30 @@
#pragma once
-#include "hci/command_interface.h"
+#include "common/callback.h"
#include "hci/hci_packets.h"
+#include "os/handler.h"
+#include "os/utils.h"
namespace bluetooth {
namespace hci {
-constexpr hci::SubeventCode LeAdvertisingEvents[] = {
- hci::SubeventCode::SCAN_REQUEST_RECEIVED,
- hci::SubeventCode::ADVERTISING_SET_TERMINATED,
-};
+class LeAdvertisingInterface {
+ public:
+ LeAdvertisingInterface() = default;
+ virtual ~LeAdvertisingInterface() = default;
+ DISALLOW_COPY_AND_ASSIGN(LeAdvertisingInterface);
+
+ virtual void EnqueueCommand(std::unique_ptr<LeAdvertisingCommandBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) = 0;
-typedef CommandInterface<LeAdvertisingCommandBuilder> LeAdvertisingInterface;
+ virtual void EnqueueCommand(std::unique_ptr<LeAdvertisingCommandBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) = 0;
+ static constexpr hci::SubeventCode LeAdvertisingEvents[] = {
+ hci::SubeventCode::SCAN_REQUEST_RECEIVED,
+ hci::SubeventCode::ADVERTISING_SET_TERMINATED,
+ };
+};
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/le_advertising_manager.cc b/gd/hci/le_advertising_manager.cc
index 660e7c5e4..6a99dcc74 100644
--- a/gd/hci/le_advertising_manager.cc
+++ b/gd/hci/le_advertising_manager.cc
@@ -16,7 +16,6 @@
#include <memory>
#include <mutex>
-#include "hci/acl_manager.h"
#include "hci/controller.h"
#include "hci/hci_layer.h"
#include "hci/hci_packets.h"
@@ -32,49 +31,34 @@ namespace hci {
const ModuleFactory LeAdvertisingManager::Factory = ModuleFactory([]() { return new LeAdvertisingManager(); });
enum class AdvertisingApiType {
- LEGACY = 1,
+ LE_4_0 = 1,
ANDROID_HCI = 2,
- EXTENDED = 3,
-};
-
-enum class AdvertisingFlag : uint8_t {
- LE_LIMITED_DISCOVERABLE = 0x01,
- LE_GENERAL_DISCOVERABLE = 0x02,
- BR_EDR_NOT_SUPPORTED = 0x04,
- SIMULTANEOUS_LE_AND_BR_EDR_CONTROLLER = 0x08,
- SIMULTANEOUS_LE_AND_BR_EDR_HOST = 0x10,
+ LE_5_0 = 3,
};
struct Advertiser {
os::Handler* handler;
- AddressWithType current_address;
common::Callback<void(Address, AddressType)> scan_callback;
common::Callback<void(ErrorCode, uint8_t, uint8_t)> set_terminated_callback;
- int8_t tx_power;
- uint16_t duration;
- uint8_t max_extended_advertising_events;
- bool started = false;
- bool connectable = false;
- std::unique_ptr<os::Alarm> address_rotation_alarm;
};
ExtendedAdvertisingConfig::ExtendedAdvertisingConfig(const AdvertisingConfig& config) : AdvertisingConfig(config) {
- switch (config.advertising_type) {
- case AdvertisingType::ADV_IND:
+ switch (config.event_type) {
+ case AdvertisingEventType::ADV_IND:
connectable = true;
scannable = true;
break;
- case AdvertisingType::ADV_DIRECT_IND:
+ case AdvertisingEventType::ADV_DIRECT_IND:
connectable = true;
directed = true;
high_duty_directed_connectable = true;
break;
- case AdvertisingType::ADV_SCAN_IND:
+ case AdvertisingEventType::ADV_SCAN_IND:
scannable = true;
break;
- case AdvertisingType::ADV_NONCONN_IND:
+ case AdvertisingEventType::ADV_NONCONN_IND:
break;
- case AdvertisingType::ADV_DIRECT_IND_LOW:
+ case AdvertisingEventType::ADV_DIRECT_IND_LOW:
connectable = true;
directed = true;
break;
@@ -82,43 +66,32 @@ ExtendedAdvertisingConfig::ExtendedAdvertisingConfig(const AdvertisingConfig& co
LOG_WARN("Unknown event type");
break;
}
+ if (config.address_type == AddressType::PUBLIC_DEVICE_ADDRESS) {
+ own_address_type = OwnAddressType::PUBLIC_DEVICE_ADDRESS;
+ } else if (config.address_type == AddressType::RANDOM_DEVICE_ADDRESS) {
+ own_address_type = OwnAddressType::RANDOM_DEVICE_ADDRESS;
+ }
+ // TODO(b/149221472): Support fragmentation
+ operation = Operation::COMPLETE_ADVERTISEMENT;
}
-struct LeAdvertisingManager::impl : public bluetooth::hci::LeAddressManagerCallback {
+struct LeAdvertisingManager::impl {
impl(Module* module) : module_(module), le_advertising_interface_(nullptr), num_instances_(0) {}
- ~impl() {
- if (address_manager_registered) {
- le_address_manager_->Unregister(this);
- }
- advertising_sets_.clear();
- }
-
- void start(os::Handler* handler, hci::HciLayer* hci_layer, hci::Controller* controller,
- hci::AclManager* acl_manager) {
+ void start(os::Handler* handler, hci::HciLayer* hci_layer, hci::Controller* controller) {
module_handler_ = handler;
hci_layer_ = hci_layer;
controller_ = controller;
- le_maximum_advertising_data_length_ = controller_->GetLeMaximumAdvertisingDataLength();
- acl_manager_ = acl_manager;
- le_address_manager_ = acl_manager->GetLeAddressManager();
- le_advertising_interface_ =
- hci_layer_->GetLeAdvertisingInterface(module_handler_->BindOn(this, &LeAdvertisingManager::impl::handle_event));
- num_instances_ = controller_->GetLeNumberOfSupportedAdverisingSets();
+ le_advertising_interface_ = hci_layer_->GetLeAdvertisingInterface(
+ common::Bind(&LeAdvertisingManager::impl::handle_event, common::Unretained(this)), module_handler_);
+ num_instances_ = controller_->GetControllerLeNumberOfSupportedAdverisingSets();
enabled_sets_ = std::vector<EnabledSet>(num_instances_);
- for (size_t i = 0; i < enabled_sets_.size(); i++) {
- enabled_sets_[i].advertising_handle_ = kInvalidHandle;
- }
-
if (controller_->IsSupported(hci::OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS)) {
- advertising_api_type_ = AdvertisingApiType::EXTENDED;
+ advertising_api_type_ = AdvertisingApiType::LE_5_0;
} else if (controller_->IsSupported(hci::OpCode::LE_MULTI_ADVT)) {
advertising_api_type_ = AdvertisingApiType::ANDROID_HCI;
} else {
- advertising_api_type_ = AdvertisingApiType::LEGACY;
- hci_layer_->EnqueueCommand(
- LeReadAdvertisingPhysicalChannelTxPowerBuilder::Create(),
- handler->BindOnceOn(this, &impl::on_read_advertising_physical_channel_tx_power));
+ advertising_api_type_ = AdvertisingApiType::LE_4_0;
}
}
@@ -126,14 +99,6 @@ struct LeAdvertisingManager::impl : public bluetooth::hci::LeAddressManagerCallb
return num_instances_;
}
- AdvertisingApiType get_advertising_api_type() const {
- return advertising_api_type_;
- }
-
- void register_advertising_callback(AdvertisingCallback* advertising_callback) {
- advertising_callbacks_ = advertising_callback;
- }
-
void handle_event(LeMetaEventView event) {
switch (event.GetSubeventCode()) {
case hci::SubeventCode::SCAN_REQUEST_RECEIVED:
@@ -161,19 +126,9 @@ struct LeAdvertisingManager::impl : public bluetooth::hci::LeAddressManagerCallb
LOG_INFO("Dropping invalid advertising event");
return;
}
-
- uint8_t advertiser_id = event_view.GetAdvertisingHandle();
-
- if (advertising_sets_[advertiser_id].address_rotation_alarm != nullptr) {
- advertising_sets_[advertiser_id].address_rotation_alarm->Cancel();
- advertising_sets_[advertiser_id].address_rotation_alarm.reset();
- }
- enabled_sets_[advertiser_id].advertising_handle_ = kInvalidHandle;
-
- AddressWithType advertiser_address = advertising_sets_[event_view.GetAdvertisingHandle()].current_address;
-
- acl_manager_->OnAdvertisingSetTerminated(
- event_view.GetStatus(), event_view.GetConnectionHandle(), advertiser_address);
+ registered_handler_->Post(common::BindOnce(set_terminated_callback_, event_view.GetStatus(),
+ event_view.GetAdvertisingHandle(),
+ event_view.GetNumCompletedExtendedAdvertisingEvents()));
}
AdvertiserId allocate_advertiser() {
@@ -190,942 +145,203 @@ struct LeAdvertisingManager::impl : public bluetooth::hci::LeAddressManagerCallb
return id;
}
- void remove_advertiser(AdvertiserId advertiser_id) {
- stop_advertising(advertiser_id);
+ void remove_advertiser(AdvertiserId id) {
+ stop_advertising(id);
std::unique_lock lock(id_mutex_);
- if (advertising_sets_.count(advertiser_id) == 0) {
+ if (advertising_sets_.count(id) == 0) {
return;
}
- if (advertising_sets_.empty() && address_manager_registered) {
- le_address_manager_->Unregister(this);
- address_manager_registered = false;
- paused = false;
- }
- if (advertising_api_type_ == AdvertisingApiType::EXTENDED) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeRemoveAdvertisingSetBuilder::Create(advertiser_id),
- module_handler_->BindOnce(impl::check_status<LeRemoveAdvertisingSetCompleteView>));
-
- if (advertising_sets_[advertiser_id].address_rotation_alarm != nullptr) {
- advertising_sets_[advertiser_id].address_rotation_alarm->Cancel();
- advertising_sets_[advertiser_id].address_rotation_alarm.reset();
- }
- }
- advertising_sets_.erase(advertiser_id);
+ advertising_sets_.erase(id);
}
- void create_advertiser(
- AdvertiserId id,
- const AdvertisingConfig config,
- const common::Callback<void(Address, AddressType)>& scan_callback,
- const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback,
- os::Handler* handler) {
+ void create_advertiser(AdvertiserId id, const AdvertisingConfig& config,
+ const common::Callback<void(Address, AddressType)>& scan_callback,
+ const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback,
+ os::Handler* handler) {
advertising_sets_[id].scan_callback = scan_callback;
advertising_sets_[id].set_terminated_callback = set_terminated_callback;
advertising_sets_[id].handler = handler;
- advertising_sets_[id].current_address = AddressWithType{};
-
- if (!address_manager_registered) {
- le_address_manager_->Register(this);
- address_manager_registered = true;
- }
-
switch (advertising_api_type_) {
- case (AdvertisingApiType::LEGACY): {
- set_parameters(id, config);
- if (config.advertising_type == AdvertisingType::ADV_IND ||
- config.advertising_type == AdvertisingType::ADV_NONCONN_IND) {
- set_data(id, true, config.scan_response);
- }
- set_data(id, false, config.advertisement);
- if (!paused) {
- enable_advertiser(id, true, 0, 0);
- } else {
- enabled_sets_[id].advertising_handle_ = id;
- }
- } break;
- case (AdvertisingApiType::ANDROID_HCI): {
- set_parameters(id, config);
- if (config.advertising_type == AdvertisingType::ADV_IND ||
- config.advertising_type == AdvertisingType::ADV_NONCONN_IND) {
- set_data(id, true, config.scan_response);
- }
- set_data(id, false, config.advertisement);
- advertising_sets_[id].current_address = le_address_manager_->GetAnotherAddress();
+ case (AdvertisingApiType::LE_4_0):
le_advertising_interface_->EnqueueCommand(
- hci::LeMultiAdvtSetRandomAddrBuilder::Create(advertising_sets_[id].current_address.GetAddress(), id),
- module_handler_->BindOnce(impl::check_status<LeMultiAdvtCompleteView>));
- if (!paused) {
- enable_advertiser(id, true, 0, 0);
- } else {
- enabled_sets_[id].advertising_handle_ = id;
+ hci::LeSetAdvertisingParametersBuilder::Create(
+ config.interval_min, config.interval_max, config.event_type, config.address_type,
+ config.peer_address_type, config.peer_address, config.channel_map, config.filter_policy),
+ common::BindOnce(impl::check_status<LeSetAdvertisingParametersCompleteView>), module_handler_);
+ le_advertising_interface_->EnqueueCommand(hci::LeSetRandomAddressBuilder::Create(config.random_address),
+ common::BindOnce(impl::check_status<LeSetRandomAddressCompleteView>),
+ module_handler_);
+ if (!config.scan_response.empty()) {
+ le_advertising_interface_->EnqueueCommand(
+ hci::LeSetScanResponseDataBuilder::Create(config.scan_response),
+ common::BindOnce(impl::check_status<LeSetScanResponseDataCompleteView>), module_handler_);
}
- } break;
- case (AdvertisingApiType::EXTENDED): {
- LOG_WARN("Unexpected AdvertisingApiType EXTENDED");
- } break;
- }
- }
-
- void create_extended_advertiser(
- int reg_id,
- AdvertiserId id,
- const ExtendedAdvertisingConfig config,
- const common::Callback<void(Address, AddressType)>& scan_callback,
- const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback,
- uint16_t duration,
- uint8_t max_ext_adv_events,
- os::Handler* handler) {
- id_map_[id] = reg_id;
-
- if (advertising_api_type_ != AdvertisingApiType::EXTENDED) {
- create_advertiser(id, config, scan_callback, set_terminated_callback, handler);
- return;
- }
-
- advertising_sets_[id].scan_callback = scan_callback;
- advertising_sets_[id].set_terminated_callback = set_terminated_callback;
- advertising_sets_[id].duration = duration;
- advertising_sets_[id].max_extended_advertising_events = max_ext_adv_events;
- advertising_sets_[id].handler = handler;
-
- set_parameters(id, config);
-
- auto address_policy = le_address_manager_->GetAddressPolicy();
- if (config.own_address_type == OwnAddressType::RANDOM_DEVICE_ADDRESS) {
- if (address_policy == LeAddressManager::AddressPolicy::USE_NON_RESOLVABLE_ADDRESS ||
- address_policy == LeAddressManager::AddressPolicy::USE_RESOLVABLE_ADDRESS) {
- AddressWithType address_with_type = le_address_manager_->GetAnotherAddress();
le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingRandomAddressBuilder::Create(id, address_with_type.GetAddress()),
- module_handler_->BindOnceOn(
- this,
- &impl::on_set_advertising_set_random_address_complete<
- LeSetExtendedAdvertisingRandomAddressCompleteView>,
- id,
- address_with_type));
-
- // start timer for random address
- advertising_sets_[id].address_rotation_alarm = std::make_unique<os::Alarm>(module_handler_);
- advertising_sets_[id].address_rotation_alarm->Schedule(
- common::BindOnce(&impl::set_advertising_set_random_address, common::Unretained(this), id),
- le_address_manager_->GetNextPrivateAddressIntervalMs());
- } else {
- advertising_sets_[id].current_address = le_address_manager_->GetCurrentAddress();
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingRandomAddressBuilder::Create(
- id, advertising_sets_[id].current_address.GetAddress()),
- module_handler_->BindOnce(impl::check_status<LeSetExtendedAdvertisingRandomAddressCompleteView>));
- }
- } else {
- advertising_sets_[id].current_address =
- AddressWithType(controller_->GetMacAddress(), AddressType::PUBLIC_DEVICE_ADDRESS);
- }
- if (config.advertising_type == AdvertisingType::ADV_IND ||
- config.advertising_type == AdvertisingType::ADV_NONCONN_IND) {
- set_data(id, true, config.scan_response);
- }
- set_data(id, false, config.advertisement);
-
- if (!config.periodic_data.empty()) {
- set_periodic_parameter(id, config.periodic_advertising_parameters);
- set_periodic_data(id, config.periodic_data);
- enable_periodic_advertising(id, true);
- }
-
- if (!paused) {
- enable_advertiser(id, true, duration, max_ext_adv_events);
- } else {
- EnabledSet curr_set;
- curr_set.advertising_handle_ = id;
- curr_set.duration_ = duration;
- curr_set.max_extended_advertising_events_ = max_ext_adv_events;
- std::vector<EnabledSet> enabled_sets = {curr_set};
- enabled_sets_[id] = curr_set;
- }
- }
-
- void stop_advertising(AdvertiserId advertiser_id) {
- if (advertising_sets_.find(advertiser_id) == advertising_sets_.end()) {
- LOG_INFO("Unknown advertising set %u", advertiser_id);
- return;
- }
- EnabledSet curr_set;
- curr_set.advertising_handle_ = advertiser_id;
- std::vector<EnabledSet> enabled_vector{curr_set};
-
- // If advertising or periodic advertising on the advertising set is enabled,
- // then the Controller will return the error code Command Disallowed (0x0C).
- // Thus, we should disable it before removing it.
- switch (advertising_api_type_) {
- case (AdvertisingApiType::LEGACY):
+ hci::LeSetAdvertisingDataBuilder::Create(config.advertisement),
+ common::BindOnce(impl::check_status<LeSetAdvertisingDataCompleteView>), module_handler_);
le_advertising_interface_->EnqueueCommand(
- hci::LeSetAdvertisingEnableBuilder::Create(Enable::DISABLED),
- module_handler_->BindOnce(impl::check_status<LeSetAdvertisingEnableCompleteView>));
+ hci::LeSetAdvertisingEnableBuilder::Create(Enable::ENABLED),
+ common::BindOnce(impl::check_status<LeSetAdvertisingEnableCompleteView>), module_handler_);
break;
case (AdvertisingApiType::ANDROID_HCI):
le_advertising_interface_->EnqueueCommand(
- hci::LeMultiAdvtSetEnableBuilder::Create(Enable::DISABLED, advertiser_id),
- module_handler_->BindOnce(impl::check_status<LeMultiAdvtCompleteView>));
- break;
- case (AdvertisingApiType::EXTENDED): {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingEnableBuilder::Create(Enable::DISABLED, enabled_vector),
- module_handler_->BindOnce(impl::check_status<LeSetExtendedAdvertisingEnableCompleteView>));
-
+ hci::LeMultiAdvtParamBuilder::Create(config.interval_min, config.interval_max, config.event_type,
+ config.address_type, config.peer_address_type, config.peer_address,
+ config.channel_map, config.filter_policy, id, config.tx_power),
+ common::BindOnce(impl::check_status<LeMultiAdvtCompleteView>), module_handler_);
+ le_advertising_interface_->EnqueueCommand(hci::LeMultiAdvtSetDataBuilder::Create(config.advertisement, id),
+ common::BindOnce(impl::check_status<LeMultiAdvtCompleteView>),
+ module_handler_);
+ if (!config.scan_response.empty()) {
+ le_advertising_interface_->EnqueueCommand(
+ hci::LeMultiAdvtSetScanRespBuilder::Create(config.scan_response, id),
+ common::BindOnce(impl::check_status<LeMultiAdvtCompleteView>), module_handler_);
+ }
le_advertising_interface_->EnqueueCommand(
- hci::LeSetPeriodicAdvertisingEnableBuilder::Create(Enable::DISABLED, advertiser_id),
- module_handler_->BindOnce(impl::check_status<LeSetPeriodicAdvertisingEnableCompleteView>));
+ hci::LeMultiAdvtSetRandomAddrBuilder::Create(config.random_address, id),
+ common::BindOnce(impl::check_status<LeMultiAdvtCompleteView>), module_handler_);
+ le_advertising_interface_->EnqueueCommand(hci::LeMultiAdvtSetEnableBuilder::Create(Enable::ENABLED, id),
+ common::BindOnce(impl::check_status<LeMultiAdvtCompleteView>),
+ module_handler_);
+ break;
+ case (AdvertisingApiType::LE_5_0): {
+ ExtendedAdvertisingConfig new_config = config;
+ new_config.legacy_pdus = true;
+ create_extended_advertiser(id, new_config, scan_callback, set_terminated_callback, handler);
} break;
}
-
- std::unique_lock lock(id_mutex_);
- enabled_sets_[advertiser_id].advertising_handle_ = kInvalidHandle;
}
- void set_advertising_set_random_address(AdvertiserId advertiser_id) {
- // This function should only be trigger by enabled advertising set
- if (enabled_sets_[advertiser_id].advertising_handle_ == kInvalidHandle) {
- if (advertising_sets_[advertiser_id].address_rotation_alarm != nullptr) {
- advertising_sets_[advertiser_id].address_rotation_alarm->Cancel();
- advertising_sets_[advertiser_id].address_rotation_alarm.reset();
- }
+ void create_extended_advertiser(AdvertiserId id, const ExtendedAdvertisingConfig& config,
+ const common::Callback<void(Address, AddressType)>& scan_callback,
+ const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback,
+ os::Handler* handler) {
+ if (advertising_api_type_ != AdvertisingApiType::LE_5_0) {
+ create_advertiser(id, config, scan_callback, set_terminated_callback, handler);
return;
}
- // TODO handle duration and max_extended_advertising_events_
- EnabledSet curr_set;
- curr_set.advertising_handle_ = advertiser_id;
- curr_set.duration_ = advertising_sets_[advertiser_id].duration;
- curr_set.max_extended_advertising_events_ = advertising_sets_[advertiser_id].max_extended_advertising_events;
- std::vector<EnabledSet> enabled_sets = {curr_set};
-
- // For connectable advertising, we should disable it first
- if (advertising_sets_[advertiser_id].connectable) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingEnableBuilder::Create(Enable::DISABLED, enabled_sets),
- module_handler_->BindOnce(impl::check_status<LeSetExtendedAdvertisingEnableCompleteView>));
- }
-
- AddressWithType address_with_type = le_address_manager_->GetAnotherAddress();
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingRandomAddressBuilder::Create(advertiser_id, address_with_type.GetAddress()),
- module_handler_->BindOnceOn(
- this,
- &impl::on_set_advertising_set_random_address_complete<LeSetExtendedAdvertisingRandomAddressCompleteView>,
- advertiser_id,
- address_with_type));
-
- if (advertising_sets_[advertiser_id].connectable) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingEnableBuilder::Create(Enable::ENABLED, enabled_sets),
- module_handler_->BindOnce(impl::check_status<LeSetExtendedAdvertisingEnableCompleteView>));
- }
-
- advertising_sets_[advertiser_id].address_rotation_alarm->Schedule(
- common::BindOnce(&impl::set_advertising_set_random_address, common::Unretained(this), advertiser_id),
- le_address_manager_->GetNextPrivateAddressIntervalMs());
- }
-
- void set_parameters(AdvertiserId advertiser_id, ExtendedAdvertisingConfig config) {
- advertising_sets_[advertiser_id].connectable = config.connectable;
- advertising_sets_[advertiser_id].tx_power = config.tx_power;
-
- switch (advertising_api_type_) {
- case (AdvertisingApiType::LEGACY): {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetAdvertisingParametersBuilder::Create(
- config.interval_min,
- config.interval_max,
- config.advertising_type,
- config.own_address_type,
- config.peer_address_type,
- config.peer_address,
- config.channel_map,
- config.filter_policy),
- module_handler_->BindOnceOn(
- this, &impl::check_status_with_id<LeSetAdvertisingParametersCompleteView>, advertiser_id));
- } break;
- case (AdvertisingApiType::ANDROID_HCI): {
- le_advertising_interface_->EnqueueCommand(
- hci::LeMultiAdvtParamBuilder::Create(
- config.interval_min,
- config.interval_max,
- config.advertising_type,
- config.own_address_type,
- config.peer_address_type,
- config.peer_address,
- config.channel_map,
- config.filter_policy,
- advertiser_id,
- config.tx_power),
- module_handler_->BindOnceOn(this, &impl::check_status_with_id<LeMultiAdvtCompleteView>, advertiser_id));
- } break;
- case (AdvertisingApiType::EXTENDED): {
- // sid must be in range 0x00 to 0x0F. Since no controller supports more than
- // 16 advertisers, it's safe to make sid equal to id.
- config.sid = advertiser_id % kAdvertisingSetIdMask;
-
- if (config.legacy_pdus) {
- LegacyAdvertisingProperties legacy_properties = LegacyAdvertisingProperties::ADV_IND;
- if (config.connectable && config.directed) {
- if (config.high_duty_directed_connectable) {
- legacy_properties = LegacyAdvertisingProperties::ADV_DIRECT_IND_HIGH;
- } else {
- legacy_properties = LegacyAdvertisingProperties::ADV_DIRECT_IND_LOW;
- }
- }
- if (config.scannable && !config.connectable) {
- legacy_properties = LegacyAdvertisingProperties::ADV_SCAN_IND;
- }
- if (!config.scannable && !config.connectable) {
- legacy_properties = LegacyAdvertisingProperties::ADV_NONCONN_IND;
- }
-
- le_advertising_interface_->EnqueueCommand(
- LeSetExtendedAdvertisingLegacyParametersBuilder::Create(
- advertiser_id,
- legacy_properties,
- config.interval_min,
- config.interval_max,
- config.channel_map,
- config.own_address_type,
- config.peer_address_type,
- config.peer_address,
- config.filter_policy,
- config.tx_power,
- config.sid,
- config.enable_scan_request_notifications),
- module_handler_->BindOnceOn(
- this,
- &impl::on_set_extended_advertising_parameters_complete<
- LeSetExtendedAdvertisingParametersCompleteView>,
- advertiser_id));
+ if (config.legacy_pdus) {
+ LegacyAdvertisingProperties legacy_properties = LegacyAdvertisingProperties::ADV_IND;
+ if (config.connectable && config.directed) {
+ if (config.high_duty_directed_connectable) {
+ legacy_properties = LegacyAdvertisingProperties::ADV_DIRECT_IND_HIGH;
} else {
- uint8_t legacy_properties = (config.connectable ? 0x1 : 0x00) | (config.scannable ? 0x2 : 0x00) |
- (config.directed ? 0x4 : 0x00) |
- (config.high_duty_directed_connectable ? 0x8 : 0x00);
- uint8_t extended_properties = (config.anonymous ? 0x20 : 0x00) | (config.include_tx_power ? 0x40 : 0x00);
- extended_properties = extended_properties >> 5;
-
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingParametersBuilder::Create(
- advertiser_id,
- legacy_properties,
- extended_properties,
- config.interval_min,
- config.interval_max,
- config.channel_map,
- config.own_address_type,
- config.peer_address_type,
- config.peer_address,
- config.filter_policy,
- config.tx_power,
- (config.use_le_coded_phy ? PrimaryPhyType::LE_CODED : PrimaryPhyType::LE_1M),
- config.secondary_max_skip,
- config.secondary_advertising_phy,
- config.sid,
- config.enable_scan_request_notifications),
- module_handler_->BindOnceOn(
- this,
- &impl::on_set_extended_advertising_parameters_complete<
- LeSetExtendedAdvertisingParametersCompleteView>,
- advertiser_id));
+ legacy_properties = LegacyAdvertisingProperties::ADV_DIRECT_IND_LOW;
}
- } break;
- }
- }
-
- void set_data(AdvertiserId advertiser_id, bool set_scan_rsp, std::vector<GapData> data) {
- if (!set_scan_rsp && advertising_sets_[advertiser_id].connectable) {
- GapData gap_data;
- gap_data.data_type_ = GapDataType::FLAGS;
- if (advertising_sets_[advertiser_id].duration == 0) {
- gap_data.data_.push_back(static_cast<uint8_t>(AdvertisingFlag::LE_GENERAL_DISCOVERABLE));
- } else {
- gap_data.data_.push_back(static_cast<uint8_t>(AdvertisingFlag::LE_LIMITED_DISCOVERABLE));
}
- data.insert(data.begin(), gap_data);
- }
-
- // Find and fill TX Power with the correct value.
- for (auto& gap_data : data) {
- if (gap_data.data_type_ == GapDataType::TX_POWER_LEVEL) {
- gap_data.data_[0] = advertising_sets_[advertiser_id].tx_power;
- break;
+ if (config.scannable && !config.connectable) {
+ legacy_properties = LegacyAdvertisingProperties::ADV_SCAN_IND;
+ }
+ if (!config.scannable && !config.connectable) {
+ legacy_properties = LegacyAdvertisingProperties::ADV_NONCONN_IND;
}
- }
-
- switch (advertising_api_type_) {
- case (AdvertisingApiType::LEGACY): {
- if (set_scan_rsp) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetScanResponseDataBuilder::Create(data),
- module_handler_->BindOnceOn(
- this, &impl::check_status_with_id<LeSetScanResponseDataCompleteView>, advertiser_id));
- } else {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetAdvertisingDataBuilder::Create(data),
- module_handler_->BindOnceOn(
- this, &impl::check_status_with_id<LeSetAdvertisingDataCompleteView>, advertiser_id));
- }
- } break;
- case (AdvertisingApiType::ANDROID_HCI): {
- if (set_scan_rsp) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeMultiAdvtSetScanRespBuilder::Create(data, advertiser_id),
- module_handler_->BindOnceOn(this, &impl::check_status_with_id<LeMultiAdvtCompleteView>, advertiser_id));
- } else {
- le_advertising_interface_->EnqueueCommand(
- hci::LeMultiAdvtSetDataBuilder::Create(data, advertiser_id),
- module_handler_->BindOnceOn(this, &impl::check_status_with_id<LeMultiAdvtCompleteView>, advertiser_id));
- }
- } break;
- case (AdvertisingApiType::EXTENDED): {
- uint16_t data_len = 0;
- // check data size
- for (int i = 0; i < data.size(); i++) {
- if (data[i].size() > kLeMaximumFragmentLength) {
- LOG_WARN("AD data len shall not greater than %d", kLeMaximumFragmentLength);
- if (advertising_callbacks_ != nullptr) {
- if (set_scan_rsp) {
- advertising_callbacks_->OnScanResponseDataSet(
- advertiser_id, AdvertisingCallback::AdvertisingStatus::INTERNAL_ERROR);
- } else {
- advertising_callbacks_->OnAdvertisingDataSet(
- advertiser_id, AdvertisingCallback::AdvertisingStatus::INTERNAL_ERROR);
- }
- }
- return;
- }
- data_len += data[i].size();
- }
-
- if (data_len > le_maximum_advertising_data_length_) {
- LOG_WARN(
- "advertising data len exceeds le_maximum_advertising_data_length_ %d",
- le_maximum_advertising_data_length_);
- if (advertising_callbacks_ != nullptr) {
- if (set_scan_rsp) {
- advertising_callbacks_->OnScanResponseDataSet(
- advertiser_id, AdvertisingCallback::AdvertisingStatus::DATA_TOO_LARGE);
- } else {
- advertising_callbacks_->OnAdvertisingDataSet(
- advertiser_id, AdvertisingCallback::AdvertisingStatus::DATA_TOO_LARGE);
- }
- }
- return;
- }
- if (data_len <= kLeMaximumFragmentLength) {
- send_data_fragment(advertiser_id, set_scan_rsp, data, Operation::COMPLETE_ADVERTISEMENT);
- } else {
- std::vector<GapData> sub_data;
- uint16_t sub_data_len = 0;
- Operation operation = Operation::FIRST_FRAGMENT;
+ le_advertising_interface_->EnqueueCommand(
+ LeSetExtendedAdvertisingLegacyParametersBuilder::Create(
+ id, legacy_properties, config.interval_min, config.interval_max, config.channel_map,
+ config.own_address_type, config.peer_address_type, config.peer_address, config.filter_policy,
+ config.tx_power, config.sid, config.enable_scan_request_notifications),
+ common::BindOnce(impl::check_status<LeSetExtendedAdvertisingParametersCompleteView>), module_handler_);
+ } else {
+ uint8_t legacy_properties = (config.connectable ? 0x1 : 0x00) | (config.scannable ? 0x2 : 0x00) |
+ (config.directed ? 0x4 : 0x00) | (config.high_duty_directed_connectable ? 0x8 : 0x00);
+ uint8_t extended_properties = (config.anonymous ? 0x20 : 0x00) | (config.include_tx_power ? 0x40 : 0x00);
- for (int i = 0; i < data.size(); i++) {
- if (sub_data_len + data[i].size() > kLeMaximumFragmentLength) {
- send_data_fragment(advertiser_id, set_scan_rsp, sub_data, operation);
- operation = Operation::INTERMEDIATE_FRAGMENT;
- sub_data_len = 0;
- sub_data.clear();
- }
- sub_data.push_back(data[i]);
- sub_data_len += data[i].size();
- }
- send_data_fragment(advertiser_id, set_scan_rsp, sub_data, Operation::LAST_FRAGMENT);
- }
- } break;
+ le_advertising_interface_->EnqueueCommand(
+ hci::LeSetExtendedAdvertisingParametersBuilder::Create(
+ id, legacy_properties, extended_properties, config.interval_min, config.interval_max, config.channel_map,
+ config.own_address_type, config.peer_address_type, config.peer_address, config.filter_policy,
+ config.tx_power, (config.use_le_coded_phy ? PrimaryPhyType::LE_CODED : PrimaryPhyType::LE_1M),
+ config.secondary_max_skip, config.secondary_advertising_phy, config.sid,
+ config.enable_scan_request_notifications),
+ common::BindOnce(impl::check_status<LeSetExtendedAdvertisingParametersCompleteView>), module_handler_);
}
- }
- void send_data_fragment(
- AdvertiserId advertiser_id, bool set_scan_rsp, std::vector<GapData> data, Operation operation) {
- if (operation == Operation::COMPLETE_ADVERTISEMENT || operation == Operation::LAST_FRAGMENT) {
- if (set_scan_rsp) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingScanResponseBuilder::Create(
- advertiser_id, operation, kFragment_preference, data),
- module_handler_->BindOnceOn(
- this, &impl::check_status_with_id<LeSetExtendedAdvertisingScanResponseCompleteView>, advertiser_id));
- } else {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingDataBuilder::Create(advertiser_id, operation, kFragment_preference, data),
- module_handler_->BindOnceOn(
- this, &impl::check_status_with_id<LeSetExtendedAdvertisingDataCompleteView>, advertiser_id));
- }
- } else {
- // For first and intermediate fragment, do not trigger advertising_callbacks_.
- if (set_scan_rsp) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingScanResponseBuilder::Create(
- advertiser_id, operation, kFragment_preference, data),
- module_handler_->BindOnce(impl::check_status<LeSetExtendedAdvertisingScanResponseCompleteView>));
- } else {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingDataBuilder::Create(advertiser_id, operation, kFragment_preference, data),
- module_handler_->BindOnce(impl::check_status<LeSetExtendedAdvertisingDataCompleteView>));
- }
+ le_advertising_interface_->EnqueueCommand(
+ hci::LeSetExtendedAdvertisingRandomAddressBuilder::Create(id, config.random_address),
+ common::BindOnce(impl::check_status<LeSetExtendedAdvertisingRandomAddressCompleteView>), module_handler_);
+ if (!config.scan_response.empty()) {
+ le_advertising_interface_->EnqueueCommand(
+ hci::LeSetExtendedAdvertisingScanResponseBuilder::Create(id, config.operation, config.fragment_preference,
+ config.scan_response),
+ common::BindOnce(impl::check_status<LeSetExtendedAdvertisingScanResponseCompleteView>), module_handler_);
}
- }
+ le_advertising_interface_->EnqueueCommand(
+ hci::LeSetExtendedAdvertisingDataBuilder::Create(id, config.operation, config.fragment_preference,
+ config.advertisement),
+ common::BindOnce(impl::check_status<LeSetExtendedAdvertisingDataCompleteView>), module_handler_);
- void enable_advertiser(
- AdvertiserId advertiser_id, bool enable, uint16_t duration, uint8_t max_extended_advertising_events) {
EnabledSet curr_set;
- curr_set.advertising_handle_ = advertiser_id;
- curr_set.duration_ = duration;
- curr_set.max_extended_advertising_events_ = max_extended_advertising_events;
+ curr_set.advertising_handle_ = id;
+ curr_set.duration_ = 0; // TODO: 0 means until the host disables it
+ curr_set.max_extended_advertising_events_ = 0; // TODO: 0 is no maximum
std::vector<EnabledSet> enabled_sets = {curr_set};
- Enable enable_value = enable ? Enable::ENABLED : Enable::DISABLED;
-
- switch (advertising_api_type_) {
- case (AdvertisingApiType::LEGACY): {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetAdvertisingEnableBuilder::Create(enable_value),
- module_handler_->BindOnceOn(
- this,
- &impl::on_set_advertising_enable_complete<LeSetAdvertisingEnableCompleteView>,
- enable,
- enabled_sets));
- } break;
- case (AdvertisingApiType::ANDROID_HCI): {
- le_advertising_interface_->EnqueueCommand(
- hci::LeMultiAdvtSetEnableBuilder::Create(enable_value, advertiser_id),
- module_handler_->BindOnceOn(
- this, &impl::on_set_advertising_enable_complete<LeMultiAdvtCompleteView>, enable, enabled_sets));
- } break;
- case (AdvertisingApiType::EXTENDED): {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingEnableBuilder::Create(enable_value, enabled_sets),
- module_handler_->BindOnceOn(
- this,
- &impl::on_set_extended_advertising_enable_complete<LeSetExtendedAdvertisingEnableCompleteView>,
- enable,
- enabled_sets));
- } break;
- }
-
- if (enable) {
- enabled_sets_[advertiser_id].advertising_handle_ = advertiser_id;
- advertising_sets_[advertiser_id].duration = duration;
- advertising_sets_[advertiser_id].max_extended_advertising_events = max_extended_advertising_events;
- } else {
- enabled_sets_[advertiser_id].advertising_handle_ = kInvalidHandle;
- if (advertising_sets_[advertiser_id].address_rotation_alarm != nullptr) {
- advertising_sets_[advertiser_id].address_rotation_alarm->Cancel();
- advertising_sets_[advertiser_id].address_rotation_alarm.reset();
- }
- }
- }
-
- void set_periodic_parameter(
- AdvertiserId advertiser_id, PeriodicAdvertisingParameters periodic_advertising_parameters) {
- uint8_t include_tx_power = periodic_advertising_parameters.properties >>
- PeriodicAdvertisingParameters::AdvertisingProperty::INCLUDE_TX_POWER;
+ enabled_sets_[id] = curr_set;
le_advertising_interface_->EnqueueCommand(
- hci::LeSetPeriodicAdvertisingParamBuilder::Create(
- advertiser_id,
- periodic_advertising_parameters.min_interval,
- periodic_advertising_parameters.max_interval,
- include_tx_power),
- module_handler_->BindOnceOn(
- this, &impl::check_status_with_id<LeSetPeriodicAdvertisingParamCompleteView>, advertiser_id));
- }
-
- void set_periodic_data(AdvertiserId advertiser_id, std::vector<GapData> data) {
- uint16_t data_len = 0;
- // check data size
- for (int i = 0; i < data.size(); i++) {
- if (data[i].size() > kLeMaximumFragmentLength) {
- LOG_WARN("AD data len shall not greater than %d", kLeMaximumFragmentLength);
- if (advertising_callbacks_ != nullptr) {
- advertising_callbacks_->OnPeriodicAdvertisingDataSet(
- advertiser_id, AdvertisingCallback::AdvertisingStatus::INTERNAL_ERROR);
- }
- return;
- }
- data_len += data[i].size();
- }
-
- if (data_len > le_maximum_advertising_data_length_) {
- LOG_WARN(
- "advertising data len exceeds le_maximum_advertising_data_length_ %d", le_maximum_advertising_data_length_);
- if (advertising_callbacks_ != nullptr) {
- advertising_callbacks_->OnPeriodicAdvertisingDataSet(
- advertiser_id, AdvertisingCallback::AdvertisingStatus::DATA_TOO_LARGE);
- }
- return;
- }
-
- if (data_len <= kLeMaximumFragmentLength) {
- send_periodic_data_fragment(advertiser_id, data, Operation::COMPLETE_ADVERTISEMENT);
- } else {
- std::vector<GapData> sub_data;
- uint16_t sub_data_len = 0;
- Operation operation = Operation::FIRST_FRAGMENT;
+ hci::LeSetExtendedAdvertisingEnableBuilder::Create(Enable::ENABLED, enabled_sets),
+ common::BindOnce(impl::check_status<LeSetExtendedAdvertisingEnableCompleteView>), module_handler_);
- for (int i = 0; i < data.size(); i++) {
- if (sub_data_len + data[i].size() > kLeMaximumFragmentLength) {
- send_periodic_data_fragment(advertiser_id, sub_data, operation);
- operation = Operation::INTERMEDIATE_FRAGMENT;
- sub_data_len = 0;
- sub_data.clear();
- }
- sub_data.push_back(data[i]);
- sub_data_len += data[i].size();
- }
- send_periodic_data_fragment(advertiser_id, sub_data, Operation::LAST_FRAGMENT);
- }
+ advertising_sets_[id].scan_callback = scan_callback;
+ advertising_sets_[id].set_terminated_callback = set_terminated_callback;
+ advertising_sets_[id].handler = handler;
}
- void send_periodic_data_fragment(AdvertiserId advertiser_id, std::vector<GapData> data, Operation operation) {
- if (operation == Operation::COMPLETE_ADVERTISEMENT || operation == Operation::LAST_FRAGMENT) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetPeriodicAdvertisingDataBuilder::Create(advertiser_id, operation, data),
- module_handler_->BindOnceOn(
- this, &impl::check_status_with_id<LeSetPeriodicAdvertisingDataCompleteView>, advertiser_id));
- } else {
- // For first and intermediate fragment, do not trigger advertising_callbacks_.
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetPeriodicAdvertisingDataBuilder::Create(advertiser_id, operation, data),
- module_handler_->BindOnce(impl::check_status<LeSetPeriodicAdvertisingDataCompleteView>));
+ void stop_advertising(AdvertiserId advertising_set) {
+ if (advertising_sets_.find(advertising_set) == advertising_sets_.end()) {
+ LOG_INFO("Unknown advertising set %u", advertising_set);
+ return;
}
- }
-
- void enable_periodic_advertising(AdvertiserId advertiser_id, bool enable) {
- Enable enable_value = enable ? Enable::ENABLED : Enable::DISABLED;
-
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetPeriodicAdvertisingEnableBuilder::Create(enable_value, advertiser_id),
- module_handler_->BindOnceOn(
- this,
- &impl::on_set_periodic_advertising_enable_complete<LeSetPeriodicAdvertisingEnableCompleteView>,
- enable,
- advertiser_id));
- }
-
- void OnPause() override {
- paused = true;
- if (!advertising_sets_.empty()) {
- std::vector<EnabledSet> enabled_sets = {};
- for (size_t i = 0; i < enabled_sets_.size(); i++) {
- EnabledSet curr_set = enabled_sets_[i];
- if (enabled_sets_[i].advertising_handle_ != kInvalidHandle) {
- enabled_sets.push_back(enabled_sets_[i]);
- }
- }
-
- switch (advertising_api_type_) {
- case (AdvertisingApiType::LEGACY): {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetAdvertisingEnableBuilder::Create(Enable::DISABLED),
- module_handler_->BindOnceOn(
- this,
- &impl::on_set_advertising_enable_complete<LeSetAdvertisingEnableCompleteView>,
- false,
- enabled_sets));
- } break;
- case (AdvertisingApiType::ANDROID_HCI): {
- for (size_t i = 0; i < enabled_sets_.size(); i++) {
- uint8_t id = enabled_sets_[i].advertising_handle_;
- if (id != kInvalidHandle) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeMultiAdvtSetEnableBuilder::Create(Enable::DISABLED, id),
- module_handler_->BindOnce(impl::check_status<LeMultiAdvtCompleteView>));
- }
- }
- } break;
- case (AdvertisingApiType::EXTENDED): {
- if (enabled_sets.size() != 0) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingEnableBuilder::Create(Enable::DISABLED, enabled_sets),
- module_handler_->BindOnceOn(
- this,
- &impl::on_set_extended_advertising_enable_complete<LeSetExtendedAdvertisingEnableCompleteView>,
- false,
- enabled_sets));
- }
- } break;
- }
+ switch (advertising_api_type_) {
+ case (AdvertisingApiType::LE_4_0):
+ le_advertising_interface_->EnqueueCommand(
+ hci::LeSetAdvertisingEnableBuilder::Create(Enable::DISABLED),
+ common::BindOnce(impl::check_status<LeSetAdvertisingEnableCompleteView>), module_handler_);
+ break;
+ case (AdvertisingApiType::ANDROID_HCI):
+ le_advertising_interface_->EnqueueCommand(
+ hci::LeMultiAdvtSetEnableBuilder::Create(Enable::DISABLED, advertising_set),
+ common::BindOnce(impl::check_status<LeMultiAdvtCompleteView>), module_handler_);
+ break;
+ case (AdvertisingApiType::LE_5_0): {
+ EnabledSet curr_set;
+ curr_set.advertising_handle_ = advertising_set;
+ std::vector<EnabledSet> enabled_vector{curr_set};
+ le_advertising_interface_->EnqueueCommand(
+ hci::LeSetExtendedAdvertisingEnableBuilder::Create(Enable::DISABLED, enabled_vector),
+ common::BindOnce(impl::check_status<LeSetExtendedAdvertisingEnableCompleteView>), module_handler_);
+ } break;
}
- le_address_manager_->AckPause(this);
- }
- void OnResume() override {
- paused = false;
- if (!advertising_sets_.empty()) {
- std::vector<EnabledSet> enabled_sets = {};
- for (size_t i = 0; i < enabled_sets_.size(); i++) {
- EnabledSet curr_set = enabled_sets_[i];
- if (enabled_sets_[i].advertising_handle_ != kInvalidHandle) {
- enabled_sets.push_back(enabled_sets_[i]);
- }
- }
-
- switch (advertising_api_type_) {
- case (AdvertisingApiType::LEGACY): {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetAdvertisingEnableBuilder::Create(Enable::ENABLED),
- module_handler_->BindOnceOn(
- this,
- &impl::on_set_advertising_enable_complete<LeSetAdvertisingEnableCompleteView>,
- true,
- enabled_sets));
- } break;
- case (AdvertisingApiType::ANDROID_HCI): {
- for (size_t i = 0; i < enabled_sets_.size(); i++) {
- uint8_t id = enabled_sets_[i].advertising_handle_;
- if (id != kInvalidHandle) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeMultiAdvtSetEnableBuilder::Create(Enable::ENABLED, id),
- module_handler_->BindOnce(impl::check_status<LeMultiAdvtCompleteView>));
- }
- }
- } break;
- case (AdvertisingApiType::EXTENDED): {
- if (enabled_sets.size() != 0) {
- le_advertising_interface_->EnqueueCommand(
- hci::LeSetExtendedAdvertisingEnableBuilder::Create(Enable::ENABLED, enabled_sets),
- module_handler_->BindOnceOn(
- this,
- &impl::on_set_extended_advertising_enable_complete<LeSetExtendedAdvertisingEnableCompleteView>,
- true,
- enabled_sets));
- }
- } break;
- }
- }
- le_address_manager_->AckResume(this);
+ std::unique_lock lock(id_mutex_);
+ enabled_sets_[advertising_set].advertising_handle_ = -1;
+ advertising_sets_.erase(advertising_set);
}
common::Callback<void(Address, AddressType)> scan_callback_;
- common::ContextualCallback<void(ErrorCode, uint16_t, hci::AddressWithType)> set_terminated_callback_{};
- AdvertisingCallback* advertising_callbacks_ = nullptr;
+ common::Callback<void(ErrorCode, uint8_t, uint8_t)> set_terminated_callback_;
os::Handler* registered_handler_{nullptr};
Module* module_;
os::Handler* module_handler_;
hci::HciLayer* hci_layer_;
hci::Controller* controller_;
- uint16_t le_maximum_advertising_data_length_;
- int8_t le_physical_channel_tx_power_ = 0;
hci::LeAdvertisingInterface* le_advertising_interface_;
std::map<AdvertiserId, Advertiser> advertising_sets_;
- hci::LeAddressManager* le_address_manager_;
- hci::AclManager* acl_manager_;
- bool address_manager_registered = false;
- bool paused = false;
std::mutex id_mutex_;
size_t num_instances_;
std::vector<hci::EnabledSet> enabled_sets_;
- std::map<uint8_t, int> id_map_;
AdvertisingApiType advertising_api_type_{0};
- void on_read_advertising_physical_channel_tx_power(CommandCompleteView view) {
- auto complete_view = LeReadAdvertisingPhysicalChannelTxPowerCompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO("Got a command complete with status %s", ErrorCodeText(complete_view.GetStatus()).c_str());
- return;
- }
- le_physical_channel_tx_power_ = complete_view.GetTransmitPowerLevel();
- }
-
- template <class View>
- void on_set_advertising_enable_complete(bool enable, std::vector<EnabledSet> enabled_sets, CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto complete_view = View::Create(view);
- ASSERT(complete_view.IsValid());
- AdvertisingCallback::AdvertisingStatus advertising_status = AdvertisingCallback::AdvertisingStatus::SUCCESS;
- if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO("Got a command complete with status %s", ErrorCodeText(complete_view.GetStatus()).c_str());
- }
-
- if (advertising_callbacks_ == nullptr) {
- return;
- }
- for (EnabledSet enabled_set : enabled_sets) {
- bool started = advertising_sets_[enabled_set.advertising_handle_].started;
- uint8_t id = enabled_set.advertising_handle_;
- if (id == kInvalidHandle) {
- continue;
- }
-
- if (started) {
- advertising_callbacks_->OnAdvertisingEnabled(id, enable, advertising_status);
- } else {
- int reg_id = id_map_[id];
- advertising_sets_[enabled_set.advertising_handle_].started = true;
- advertising_callbacks_->OnAdvertisingSetStarted(reg_id, id, le_physical_channel_tx_power_, advertising_status);
- }
- }
- }
-
- template <class View>
- void on_set_extended_advertising_enable_complete(
- bool enable, std::vector<EnabledSet> enabled_sets, CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto complete_view = LeSetExtendedAdvertisingEnableCompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- AdvertisingCallback::AdvertisingStatus advertising_status = AdvertisingCallback::AdvertisingStatus::SUCCESS;
- if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO("Got a command complete with status %s", ErrorCodeText(complete_view.GetStatus()).c_str());
- advertising_status = AdvertisingCallback::AdvertisingStatus::INTERNAL_ERROR;
- }
-
- if (advertising_callbacks_ == nullptr) {
- return;
- }
-
- for (EnabledSet enabled_set : enabled_sets) {
- int8_t tx_power = advertising_sets_[enabled_set.advertising_handle_].tx_power;
- bool started = advertising_sets_[enabled_set.advertising_handle_].started;
- uint8_t id = enabled_set.advertising_handle_;
- if (id == kInvalidHandle) {
- continue;
- }
-
- if (started) {
- advertising_callbacks_->OnAdvertisingEnabled(id, enable, advertising_status);
- } else {
- int reg_id = id_map_[id];
- advertising_sets_[enabled_set.advertising_handle_].started = true;
- advertising_callbacks_->OnAdvertisingSetStarted(reg_id, id, tx_power, advertising_status);
- }
- }
- }
-
- template <class View>
- void on_set_extended_advertising_parameters_complete(AdvertiserId id, CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto complete_view = LeSetExtendedAdvertisingParametersCompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- AdvertisingCallback::AdvertisingStatus advertising_status = AdvertisingCallback::AdvertisingStatus::SUCCESS;
- if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO("Got a command complete with status %s", ErrorCodeText(complete_view.GetStatus()).c_str());
- advertising_status = AdvertisingCallback::AdvertisingStatus::INTERNAL_ERROR;
- }
- advertising_sets_[id].tx_power = complete_view.GetSelectedTxPower();
-
- if (advertising_sets_[id].started) {
- advertising_callbacks_->OnAdvertisingParametersUpdated(id, advertising_sets_[id].tx_power, advertising_status);
- }
- }
-
- template <class View>
- void on_set_periodic_advertising_enable_complete(bool enable, AdvertiserId id, CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto complete_view = LeSetPeriodicAdvertisingEnableCompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- AdvertisingCallback::AdvertisingStatus advertising_status = AdvertisingCallback::AdvertisingStatus::SUCCESS;
- if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO("Got a command complete with status %s", ErrorCodeText(complete_view.GetStatus()).c_str());
- advertising_status = AdvertisingCallback::AdvertisingStatus::INTERNAL_ERROR;
- }
-
- if (advertising_callbacks_ == nullptr || !advertising_sets_[id].started) {
- return;
- }
-
- advertising_callbacks_->OnPeriodicAdvertisingEnabled(id, enable, advertising_status);
- }
-
- template <class View>
- void on_set_advertising_set_random_address_complete(
- AdvertiserId advertiser_id, AddressWithType address_with_type, CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto complete_view = LeSetExtendedAdvertisingRandomAddressCompleteView::Create(view);
- ASSERT(complete_view.IsValid());
- if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO("Got a command complete with status %s", ErrorCodeText(complete_view.GetStatus()).c_str());
- } else {
- LOG_INFO(
- "update random address for advertising set %d : %s",
- advertiser_id,
- address_with_type.GetAddress().ToString().c_str());
- advertising_sets_[advertiser_id].current_address = address_with_type;
- }
- }
-
- template <class View>
- void check_status_with_id(AdvertiserId id, CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto status_view = View::Create(view);
- ASSERT(status_view.IsValid());
- if (status_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO(
- "Got a Command complete %s, status %s",
- OpCodeText(view.GetCommandOpCode()).c_str(),
- ErrorCodeText(status_view.GetStatus()).c_str());
- }
- AdvertisingCallback::AdvertisingStatus advertising_status = AdvertisingCallback::AdvertisingStatus::SUCCESS;
- if (status_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO("Got a command complete with status %s", ErrorCodeText(status_view.GetStatus()).c_str());
- advertising_status = AdvertisingCallback::AdvertisingStatus::INTERNAL_ERROR;
- }
-
- // Do not trigger callback if the advertiser not stated yet
- if (advertising_callbacks_ == nullptr || !advertising_sets_[id].started) {
- return;
- }
-
- OpCode opcode = view.GetCommandOpCode();
-
- switch (opcode) {
- case OpCode::LE_SET_ADVERTISING_PARAMETERS:
- advertising_callbacks_->OnAdvertisingParametersUpdated(id, le_physical_channel_tx_power_, advertising_status);
- break;
- case OpCode::LE_SET_ADVERTISING_DATA:
- case OpCode::LE_SET_EXTENDED_ADVERTISING_DATA:
- advertising_callbacks_->OnAdvertisingDataSet(id, advertising_status);
- break;
- case OpCode::LE_SET_SCAN_RESPONSE_DATA:
- case OpCode::LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE:
- advertising_callbacks_->OnScanResponseDataSet(id, advertising_status);
- break;
- case OpCode::LE_SET_PERIODIC_ADVERTISING_PARAM:
- advertising_callbacks_->OnPeriodicAdvertisingParametersUpdated(id, advertising_status);
- break;
- case OpCode::LE_SET_PERIODIC_ADVERTISING_DATA:
- advertising_callbacks_->OnPeriodicAdvertisingDataSet(id, advertising_status);
- break;
- case OpCode::LE_MULTI_ADVT: {
- auto command_view = LeMultiAdvtCompleteView::Create(view);
- ASSERT(command_view.IsValid());
- auto sub_opcode = command_view.GetSubCmd();
- switch (sub_opcode) {
- case SubOcf::SET_PARAM:
- advertising_callbacks_->OnAdvertisingParametersUpdated(
- id, le_physical_channel_tx_power_, advertising_status);
- break;
- case SubOcf::SET_DATA:
- advertising_callbacks_->OnAdvertisingDataSet(id, advertising_status);
- break;
- case SubOcf::SET_SCAN_RESP:
- advertising_callbacks_->OnScanResponseDataSet(id, advertising_status);
- break;
- default:
- LOG_WARN("Unexpected sub event type %s", SubOcfText(command_view.GetSubCmd()).c_str());
- }
- } break;
- default:
- LOG_WARN("Unexpected event type %s", OpCodeText(view.GetCommandOpCode()).c_str());
- }
- }
-
template <class View>
static void check_status(CommandCompleteView view) {
ASSERT(view.IsValid());
auto status_view = View::Create(view);
ASSERT(status_view.IsValid());
if (status_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO(
- "Got a Command complete %s, status %s",
- OpCodeText(view.GetCommandOpCode()).c_str(),
- ErrorCodeText(status_view.GetStatus()).c_str());
+ LOG_INFO("SetEnable returned status %s", ErrorCodeText(status_view.GetStatus()).c_str());
}
}
};
@@ -1137,12 +353,10 @@ LeAdvertisingManager::LeAdvertisingManager() {
void LeAdvertisingManager::ListDependencies(ModuleList* list) {
list->add<hci::HciLayer>();
list->add<hci::Controller>();
- list->add<hci::AclManager>();
}
void LeAdvertisingManager::Start() {
- pimpl_->start(GetHandler(), GetDependency<hci::HciLayer>(), GetDependency<hci::Controller>(),
- GetDependency<AclManager>());
+ pimpl_->start(GetHandler(), GetDependency<hci::HciLayer>(), GetDependency<hci::Controller>());
}
void LeAdvertisingManager::Stop() {
@@ -1157,19 +371,17 @@ size_t LeAdvertisingManager::GetNumberOfAdvertisingInstances() const {
return pimpl_->GetNumberOfAdvertisingInstances();
}
-AdvertiserId LeAdvertisingManager::create_advertiser(
- const AdvertisingConfig config,
- const common::Callback<void(Address, AddressType)>& scan_callback,
- const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback,
- os::Handler* handler) {
+AdvertiserId LeAdvertisingManager::CreateAdvertiser(
+ const AdvertisingConfig& config, const common::Callback<void(Address, AddressType)>& scan_callback,
+ const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback, os::Handler* handler) {
if (config.peer_address == Address::kEmpty) {
- if (config.own_address_type == hci::OwnAddressType::RESOLVABLE_OR_PUBLIC_ADDRESS ||
- config.own_address_type == hci::OwnAddressType::RESOLVABLE_OR_RANDOM_ADDRESS) {
+ if (config.address_type == hci::AddressType::PUBLIC_IDENTITY_ADDRESS ||
+ config.address_type == hci::AddressType::RANDOM_IDENTITY_ADDRESS) {
LOG_WARN("Peer address can not be empty");
return kInvalidId;
}
- if (config.advertising_type == hci::AdvertisingType::ADV_DIRECT_IND ||
- config.advertising_type == hci::AdvertisingType::ADV_DIRECT_IND_LOW) {
+ if (config.event_type == hci::AdvertisingEventType::ADV_DIRECT_IND ||
+ config.event_type == hci::AdvertisingEventType::ADV_DIRECT_IND_LOW) {
LOG_WARN("Peer address can not be empty for directed advertising");
return kInvalidId;
}
@@ -1184,18 +396,8 @@ AdvertiserId LeAdvertisingManager::create_advertiser(
}
AdvertiserId LeAdvertisingManager::ExtendedCreateAdvertiser(
- int reg_id,
- const ExtendedAdvertisingConfig config,
- const common::Callback<void(Address, AddressType)>& scan_callback,
- const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback,
- uint16_t duration,
- uint8_t max_extended_advertising_events,
- os::Handler* handler) {
- AdvertisingApiType advertising_api_type = pimpl_->get_advertising_api_type();
- if (advertising_api_type != AdvertisingApiType::EXTENDED) {
- return create_advertiser(config, scan_callback, set_terminated_callback, handler);
- };
-
+ const ExtendedAdvertisingConfig& config, const common::Callback<void(Address, AddressType)>& scan_callback,
+ const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback, os::Handler* handler) {
if (config.directed) {
if (config.peer_address == Address::kEmpty) {
LOG_INFO("Peer address can not be empty for directed advertising");
@@ -1224,52 +426,13 @@ AdvertiserId LeAdvertisingManager::ExtendedCreateAdvertiser(
if (id == kInvalidId) {
return id;
}
- CallOn(
- pimpl_.get(),
- &impl::create_extended_advertiser,
- reg_id,
- id,
- config,
- scan_callback,
- set_terminated_callback,
- duration,
- max_extended_advertising_events,
- handler);
+ GetHandler()->Post(common::BindOnce(&impl::create_extended_advertiser, common::Unretained(pimpl_.get()), id, config,
+ scan_callback, set_terminated_callback, handler));
return id;
}
-void LeAdvertisingManager::SetParameters(AdvertiserId advertiser_id, ExtendedAdvertisingConfig config) {
- CallOn(pimpl_.get(), &impl::set_parameters, advertiser_id, config);
-}
-
-void LeAdvertisingManager::SetData(AdvertiserId advertiser_id, bool set_scan_rsp, std::vector<GapData> data) {
- CallOn(pimpl_.get(), &impl::set_data, advertiser_id, set_scan_rsp, data);
-}
-
-void LeAdvertisingManager::EnableAdvertiser(
- AdvertiserId advertiser_id, bool enable, uint16_t duration, uint8_t max_extended_advertising_events) {
- CallOn(pimpl_.get(), &impl::enable_advertiser, advertiser_id, enable, duration, max_extended_advertising_events);
-}
-
-void LeAdvertisingManager::SetPeriodicParameters(
- AdvertiserId advertiser_id, PeriodicAdvertisingParameters periodic_advertising_parameters) {
- CallOn(pimpl_.get(), &impl::set_periodic_parameter, advertiser_id, periodic_advertising_parameters);
-}
-
-void LeAdvertisingManager::SetPeriodicData(AdvertiserId advertiser_id, std::vector<GapData> data) {
- CallOn(pimpl_.get(), &impl::set_periodic_data, advertiser_id, data);
-}
-
-void LeAdvertisingManager::EnablePeriodicAdvertising(AdvertiserId advertiser_id, bool enable) {
- CallOn(pimpl_.get(), &impl::enable_periodic_advertising, advertiser_id, enable);
-}
-
-void LeAdvertisingManager::RemoveAdvertiser(AdvertiserId advertiser_id) {
- CallOn(pimpl_.get(), &impl::remove_advertiser, advertiser_id);
-}
-
-void LeAdvertisingManager::RegisterAdvertisingCallback(AdvertisingCallback* advertising_callback) {
- CallOn(pimpl_.get(), &impl::register_advertising_callback, advertising_callback);
+void LeAdvertisingManager::RemoveAdvertiser(AdvertiserId id) {
+ GetHandler()->Post(common::BindOnce(&impl::remove_advertiser, common::Unretained(pimpl_.get()), id));
}
} // namespace hci
diff --git a/gd/hci/le_advertising_manager.h b/gd/hci/le_advertising_manager.h
index 45e6d6446..d410dece2 100644
--- a/gd/hci/le_advertising_manager.h
+++ b/gd/hci/le_advertising_manager.h
@@ -17,30 +17,21 @@
#include <memory>
-#include "common/callback.h"
-#include "hci/address_with_type.h"
#include "hci/hci_packets.h"
#include "module.h"
namespace bluetooth {
namespace hci {
-class PeriodicAdvertisingParameters {
- public:
- uint16_t min_interval;
- uint16_t max_interval;
- uint16_t properties;
- enum AdvertisingProperty { INCLUDE_TX_POWER = 0x06 };
-};
-
class AdvertisingConfig {
public:
std::vector<GapData> advertisement;
std::vector<GapData> scan_response;
+ Address random_address;
uint16_t interval_min;
uint16_t interval_max;
- AdvertisingType advertising_type;
- OwnAddressType own_address_type;
+ AdvertisingEventType event_type;
+ AddressType address_type;
PeerAddressType peer_address_type;
Address peer_address;
uint8_t channel_map;
@@ -62,73 +53,32 @@ class ExtendedAdvertisingConfig : public AdvertisingConfig {
SecondaryPhyType secondary_advertising_phy;
uint8_t sid = 0x00;
Enable enable_scan_request_notifications = Enable::DISABLED;
- std::vector<GapData> periodic_data;
- PeriodicAdvertisingParameters periodic_advertising_parameters;
+ OwnAddressType own_address_type;
+ Operation operation; // TODO(b/149221472): Support fragmentation
+ FragmentPreference fragment_preference = FragmentPreference::CONTROLLER_SHOULD_NOT;
ExtendedAdvertisingConfig() = default;
ExtendedAdvertisingConfig(const AdvertisingConfig& config);
};
-using AdvertiserId = uint8_t;
-
-class AdvertisingCallback {
- public:
- enum AdvertisingStatus {
- SUCCESS,
- DATA_TOO_LARGE,
- TOO_MANY_ADVERTISERS,
- ALREADY_STARTED,
- INTERNAL_ERROR,
- FEATURE_UNSUPPORTED
- };
-
- virtual ~AdvertisingCallback() = default;
- virtual void OnAdvertisingSetStarted(
- int reg_id, uint8_t advertiser_id, int8_t tx_power, AdvertisingStatus status) = 0;
- virtual void OnAdvertisingEnabled(uint8_t advertiser_id, bool enable, uint8_t status) = 0;
- virtual void OnAdvertisingDataSet(uint8_t advertiser_id, uint8_t status) = 0;
- virtual void OnScanResponseDataSet(uint8_t advertiser_id, uint8_t status) = 0;
- virtual void OnAdvertisingParametersUpdated(uint8_t advertiser_id, int8_t tx_power, uint8_t status) = 0;
- virtual void OnPeriodicAdvertisingParametersUpdated(uint8_t advertiser_id, uint8_t status) = 0;
- virtual void OnPeriodicAdvertisingDataSet(uint8_t advertiser_id, uint8_t status) = 0;
- virtual void OnPeriodicAdvertisingEnabled(uint8_t advertiser_id, bool enable, uint8_t status) = 0;
-};
+using AdvertiserId = int32_t;
class LeAdvertisingManager : public bluetooth::Module {
public:
- static constexpr AdvertiserId kInvalidId = 0xFF;
- static constexpr uint8_t kInvalidHandle = 0xFF;
- static constexpr uint8_t kAdvertisingSetIdMask = 0x0F;
- static constexpr uint16_t kLeMaximumFragmentLength = 251;
- static constexpr FragmentPreference kFragment_preference = FragmentPreference::CONTROLLER_SHOULD_NOT;
+ static constexpr AdvertiserId kInvalidId = -1;
LeAdvertisingManager();
size_t GetNumberOfAdvertisingInstances() const;
+ // Return -1 if the advertiser was not created, otherwise the advertiser ID.
+ AdvertiserId CreateAdvertiser(const AdvertisingConfig& config,
+ const common::Callback<void(Address, AddressType)>& scan_callback,
+ const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback,
+ os::Handler* handler);
AdvertiserId ExtendedCreateAdvertiser(
- int reg_id,
- const ExtendedAdvertisingConfig config,
- const common::Callback<void(Address, AddressType)>& scan_callback,
- const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback,
- uint16_t duration,
- uint8_t max_extended_advertising_events,
- os::Handler* handler);
+ const ExtendedAdvertisingConfig& config, const common::Callback<void(Address, AddressType)>& scan_callback,
+ const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback, os::Handler* handler);
- void SetParameters(AdvertiserId advertiser_id, ExtendedAdvertisingConfig config);
-
- void SetData(AdvertiserId advertiser_id, bool set_scan_rsp, std::vector<GapData> data);
-
- void EnableAdvertiser(
- AdvertiserId advertiser_id, bool enable, uint16_t duration, uint8_t max_extended_advertising_events);
-
- void SetPeriodicParameters(AdvertiserId advertiser_id, PeriodicAdvertisingParameters periodic_advertising_parameters);
-
- void SetPeriodicData(AdvertiserId advertiser_id, std::vector<GapData> data);
-
- void EnablePeriodicAdvertising(AdvertiserId advertiser_id, bool enable);
-
- void RemoveAdvertiser(AdvertiserId advertiser_id);
-
- void RegisterAdvertisingCallback(AdvertisingCallback* advertising_callback);
+ void RemoveAdvertiser(AdvertiserId id);
static const ModuleFactory Factory;
@@ -142,12 +92,6 @@ class LeAdvertisingManager : public bluetooth::Module {
std::string ToString() const override;
private:
- // Return -1 if the advertiser was not created, otherwise the advertiser ID.
- AdvertiserId create_advertiser(
- const AdvertisingConfig config,
- const common::Callback<void(Address, AddressType)>& scan_callback,
- const common::Callback<void(ErrorCode, uint8_t, uint8_t)>& set_terminated_callback,
- os::Handler* handler);
struct impl;
std::unique_ptr<impl> pimpl_;
DISALLOW_COPY_AND_ASSIGN(LeAdvertisingManager);
diff --git a/gd/hci/le_advertising_manager_mock.h b/gd/hci/le_advertising_manager_mock.h
deleted file mode 100644
index f5e976333..000000000
--- a/gd/hci/le_advertising_manager_mock.h
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include "hci/le_advertising_manager.h"
-
-#include <gmock/gmock.h>
-
-// Unit test interfaces
-namespace bluetooth {
-namespace hci {
-
-struct LeAdvertisingManager::impl : public bluetooth::hci::LeAddressManagerCallback {};
-
-namespace testing {
-
-using hci::AdvertiserId;
-using hci::LeAdvertisingManager;
-
-class MockLeAdvertisingManager : public LeAdvertisingManager {
- public:
- MOCK_METHOD(size_t, GetNumberOfAdvertisingInstances, (), (const));
- MOCK_METHOD(
- AdvertiserId,
- ExtendedCreateAdvertiser,
- (int regId,
- const ExtendedAdvertisingConfig,
- const common::Callback<void(Address, AddressType)>&,
- const common::Callback<void(ErrorCode, uint8_t, uint8_t)>&,
- uint16_t,
- uint8_t,
- os::Handler*));
- MOCK_METHOD(void, RemoveAdvertiser, (AdvertiserId));
-
-};
-
-} // namespace testing
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/le_advertising_manager_test.cc b/gd/hci/le_advertising_manager_test.cc
index e7c7b11c0..d2a5b7bdb 100644
--- a/gd/hci/le_advertising_manager_test.cc
+++ b/gd/hci/le_advertising_manager_test.cc
@@ -25,7 +25,6 @@
#include <gtest/gtest.h>
#include "common/bind.h"
-#include "hci/acl_manager.h"
#include "hci/address.h"
#include "hci/controller.h"
#include "hci/hci_layer.h"
@@ -58,14 +57,10 @@ class TestController : public Controller {
supported_opcodes_.insert(op_code);
}
- uint8_t GetLeNumberOfSupportedAdverisingSets() const override {
+ uint8_t GetControllerLeNumberOfSupportedAdverisingSets() const override {
return num_advertisers;
}
- uint16_t GetLeMaximumAdvertisingDataLength() const override {
- return 0x0672;
- }
-
uint8_t num_advertisers{0};
protected:
@@ -79,12 +74,17 @@ class TestController : public Controller {
class TestHciLayer : public HciLayer {
public:
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(CommandStatusView)> on_status) override {
- auto packet_view = CommandView::Create(GetPacketView(std::move(command)));
- ASSERT_TRUE(packet_view.IsValid());
- std::lock_guard<std::mutex> lock(mutex_);
+ TestHciLayer() {
+ RegisterEventHandler(EventCode::COMMAND_COMPLETE,
+ base::Bind(&TestHciLayer::CommandCompleteCallback, common::Unretained(this)), nullptr);
+ RegisterEventHandler(EventCode::COMMAND_STATUS,
+ base::Bind(&TestHciLayer::CommandStatusCallback, common::Unretained(this)), nullptr);
+ }
+
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) override {
+ auto packet_view = CommandPacketView::Create(GetPacketView(std::move(command)));
+ ASSERT(packet_view.IsValid());
command_queue_.push_back(packet_view);
command_status_callbacks.push_back(std::move(on_status));
if (command_promise_ != nullptr &&
@@ -97,19 +97,17 @@ class TestHciLayer : public HciLayer {
}
}
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(CommandCompleteView)> on_complete) override {
- auto packet_view = CommandView::Create(GetPacketView(std::move(command)));
- ASSERT_TRUE(packet_view.IsValid());
- std::lock_guard<std::mutex> lock(mutex_);
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) override {
+ auto packet_view = CommandPacketView::Create(GetPacketView(std::move(command)));
+ ASSERT(packet_view.IsValid());
command_queue_.push_back(packet_view);
command_complete_callbacks.push_back(std::move(on_complete));
if (command_promise_ != nullptr &&
(command_op_code_ == OpCode::NONE || command_op_code_ == packet_view.GetOpCode())) {
if (command_op_code_ == OpCode::LE_MULTI_ADVT) {
auto sub_view = LeMultiAdvtView::Create(LeAdvertisingCommandView::Create(packet_view));
- ASSERT_TRUE(sub_view.IsValid());
+ ASSERT(sub_view.IsValid());
if (sub_view.GetSubCmd() != command_sub_ocf_) {
return;
}
@@ -119,188 +117,107 @@ class TestHciLayer : public HciLayer {
}
}
- void SetCommandFuture(OpCode op_code = OpCode::NONE) {
- ASSERT_LOG(command_promise_ == nullptr, "Promises, Promises, ... Only one at a time.");
+ std::future<size_t> GetCommandFuture(OpCode op_code = OpCode::NONE) {
+ ASSERT_LOG(command_promise_ == nullptr, "Promises promises ... Only one at a time");
command_op_code_ = op_code;
command_promise_ = std::make_unique<std::promise<size_t>>();
- command_future_ = std::make_unique<std::future<size_t>>(command_promise_->get_future());
+ return command_promise_->get_future();
}
- void ResetCommandFuture() {
- if (command_future_ != nullptr) {
- command_future_.reset();
- command_promise_.reset();
- }
- }
-
- void SetSubCommandFuture(SubOcf sub_ocf) {
+ std::future<size_t> GetSubCommandFuture(SubOcf sub_ocf) {
ASSERT_LOG(command_promise_ == nullptr, "Promises promises ... Only one at a time");
command_op_code_ = OpCode::LE_MULTI_ADVT;
command_sub_ocf_ = sub_ocf;
command_promise_ = std::make_unique<std::promise<size_t>>();
- command_future_ = std::make_unique<std::future<size_t>>(command_promise_->get_future());
+ return command_promise_->get_future();
}
- ConnectionManagementCommandView GetCommand(OpCode op_code) {
- if (!command_queue_.empty()) {
- std::lock_guard<std::mutex> lock(mutex_);
- if (command_future_ != nullptr) {
- command_future_.reset();
- command_promise_.reset();
- }
- } else if (command_future_ != nullptr) {
- auto result = command_future_->wait_for(std::chrono::milliseconds(1000));
- EXPECT_NE(std::future_status::timeout, result);
- }
- ASSERT_LOG(
- !command_queue_.empty(), "Expecting command %s but command queue was empty", OpCodeText(op_code).c_str());
- std::lock_guard<std::mutex> lock(mutex_);
- CommandView command_packet_view = CommandView::Create(command_queue_.front());
+ ConnectionManagementCommandView GetCommandPacket(OpCode op_code) {
+ ASSERT(!command_queue_.empty());
+ CommandPacketView command_packet_view = CommandPacketView::Create(command_queue_.front());
command_queue_.pop_front();
- auto command = ConnectionManagementCommandView::Create(AclCommandView::Create(command_packet_view));
- EXPECT_TRUE(command.IsValid());
+ ConnectionManagementCommandView command = ConnectionManagementCommandView::Create(command_packet_view);
+ ASSERT(command.IsValid());
EXPECT_EQ(command.GetOpCode(), op_code);
return command;
}
- void RegisterEventHandler(EventCode event_code, common::ContextualCallback<void(EventView)> event_handler) override {
+ void RegisterEventHandler(EventCode event_code, common::Callback<void(EventPacketView)> event_handler,
+ os::Handler* handler) override {
registered_events_[event_code] = event_handler;
}
- void RegisterLeEventHandler(SubeventCode subevent_code,
- common::ContextualCallback<void(LeMetaEventView)> event_handler) override {
+ void RegisterLeEventHandler(SubeventCode subevent_code, common::Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler) override {
registered_le_events_[subevent_code] = event_handler;
}
- void IncomingEvent(std::unique_ptr<EventBuilder> event_builder) {
+ void IncomingEvent(std::unique_ptr<EventPacketBuilder> event_builder) {
auto packet = GetPacketView(std::move(event_builder));
- EventView event = EventView::Create(packet);
+ EventPacketView event = EventPacketView::Create(packet);
ASSERT_TRUE(event.IsValid());
EventCode event_code = event.GetEventCode();
- ASSERT_NE(registered_events_.find(event_code), registered_events_.end()) << EventCodeText(event_code);
- registered_events_[event_code].Invoke(event);
+ ASSERT_TRUE(registered_events_.find(event_code) != registered_events_.end()) << EventCodeText(event_code);
+ registered_events_[event_code].Run(event);
}
void IncomingLeMetaEvent(std::unique_ptr<LeMetaEventBuilder> event_builder) {
auto packet = GetPacketView(std::move(event_builder));
- EventView event = EventView::Create(packet);
+ EventPacketView event = EventPacketView::Create(packet);
LeMetaEventView meta_event_view = LeMetaEventView::Create(event);
ASSERT_TRUE(meta_event_view.IsValid());
SubeventCode subevent_code = meta_event_view.GetSubeventCode();
- ASSERT_NE(registered_le_events_.find(subevent_code), registered_le_events_.end())
+ ASSERT_TRUE(registered_le_events_.find(subevent_code) != registered_le_events_.end())
<< SubeventCodeText(subevent_code);
- registered_le_events_[subevent_code].Invoke(meta_event_view);
+ registered_le_events_[subevent_code].Run(meta_event_view);
}
- void CommandCompleteCallback(EventView event) {
+ void CommandCompleteCallback(EventPacketView event) {
CommandCompleteView complete_view = CommandCompleteView::Create(event);
- ASSERT_TRUE(complete_view.IsValid());
- std::move(command_complete_callbacks.front()).Invoke(complete_view);
+ ASSERT(complete_view.IsValid());
+ std::move(command_complete_callbacks.front()).Run(complete_view);
command_complete_callbacks.pop_front();
}
- void CommandStatusCallback(EventView event) {
+ void CommandStatusCallback(EventPacketView event) {
CommandStatusView status_view = CommandStatusView::Create(event);
- ASSERT_TRUE(status_view.IsValid());
- std::move(command_status_callbacks.front()).Invoke(status_view);
+ ASSERT(status_view.IsValid());
+ std::move(command_status_callbacks.front()).Run(status_view);
command_status_callbacks.pop_front();
}
void ListDependencies(ModuleList* list) override {}
- void Start() override {
- RegisterEventHandler(EventCode::COMMAND_COMPLETE,
- GetHandler()->BindOn(this, &TestHciLayer::CommandCompleteCallback));
- RegisterEventHandler(EventCode::COMMAND_STATUS, GetHandler()->BindOn(this, &TestHciLayer::CommandStatusCallback));
- }
+ void Start() override {}
void Stop() override {}
private:
- std::map<EventCode, common::ContextualCallback<void(EventView)>> registered_events_;
- std::map<SubeventCode, common::ContextualCallback<void(LeMetaEventView)>> registered_le_events_;
- std::list<common::ContextualOnceCallback<void(CommandCompleteView)>> command_complete_callbacks;
- std::list<common::ContextualOnceCallback<void(CommandStatusView)>> command_status_callbacks;
+ std::map<EventCode, common::Callback<void(EventPacketView)>> registered_events_;
+ std::map<SubeventCode, common::Callback<void(LeMetaEventView)>> registered_le_events_;
+ std::list<base::OnceCallback<void(CommandCompleteView)>> command_complete_callbacks;
+ std::list<base::OnceCallback<void(CommandStatusView)>> command_status_callbacks;
- std::list<CommandView> command_queue_;
+ std::list<CommandPacketView> command_queue_;
mutable std::mutex mutex_;
std::unique_ptr<std::promise<size_t>> command_promise_{};
- std::unique_ptr<std::future<size_t>> command_future_{};
OpCode command_op_code_;
SubOcf command_sub_ocf_;
};
-class TestLeAddressManager : public LeAddressManager {
- public:
- TestLeAddressManager(
- common::Callback<void(std::unique_ptr<CommandBuilder>)> enqueue_command,
- os::Handler* handler,
- Address public_address,
- uint8_t connect_list_size,
- uint8_t resolving_list_size)
- : LeAddressManager(enqueue_command, handler, public_address, connect_list_size, resolving_list_size) {}
-
- AddressPolicy Register(LeAddressManagerCallback* callback) override {
- return AddressPolicy::USE_STATIC_ADDRESS;
- }
-
- void Unregister(LeAddressManagerCallback* callback) override {}
-
- AddressWithType GetAnotherAddress() override {
- hci::Address address;
- Address::FromString("05:04:03:02:01:00", address);
- auto random_address = AddressWithType(address, AddressType::RANDOM_DEVICE_ADDRESS);
- return random_address;
- }
-};
-
-class TestAclManager : public AclManager {
- public:
- LeAddressManager* GetLeAddressManager() override {
- return test_le_address_manager_;
- }
-
- protected:
- void Start() override {
- thread_ = new os::Thread("thread", os::Thread::Priority::NORMAL);
- handler_ = new os::Handler(thread_);
- Address address({0x01, 0x02, 0x03, 0x04, 0x05, 0x06});
- test_le_address_manager_ = new TestLeAddressManager(
- common::Bind(&TestAclManager::enqueue_command, common::Unretained(this)), handler_, address, 0x3F, 0x3F);
- }
-
- void Stop() override {
- delete test_le_address_manager_;
- handler_->Clear();
- delete handler_;
- delete thread_;
- }
-
- void ListDependencies(ModuleList* list) override {}
-
- void SetRandomAddress(Address address) {}
-
- void enqueue_command(std::unique_ptr<CommandBuilder> command_packet){};
-
- os::Thread* thread_;
- os::Handler* handler_;
- TestLeAddressManager* test_le_address_manager_;
-};
-
class LeAdvertisingManagerTest : public ::testing::Test {
protected:
void SetUp() override {
test_hci_layer_ = new TestHciLayer; // Ownership is transferred to registry
test_controller_ = new TestController;
- test_acl_manager_ = new TestAclManager;
test_controller_->AddSupported(param_opcode_);
fake_registry_.InjectTestModule(&HciLayer::Factory, test_hci_layer_);
fake_registry_.InjectTestModule(&Controller::Factory, test_controller_);
- fake_registry_.InjectTestModule(&AclManager::Factory, test_acl_manager_);
client_handler_ = fake_registry_.GetTestModuleHandler(&HciLayer::Factory);
ASSERT_NE(client_handler_, nullptr);
test_controller_->num_advertisers = 1;
- le_advertising_manager_ = fake_registry_.Start<LeAdvertisingManager>(&thread_);
- le_advertising_manager_->RegisterAdvertisingCallback(&mock_advertising_callback_);
+ fake_registry_.Start<LeAdvertisingManager>(&thread_);
+ le_advertising_manager_ =
+ static_cast<LeAdvertisingManager*>(fake_registry_.GetModuleUnderTest(&LeAdvertisingManager::Factory));
}
void TearDown() override {
@@ -311,7 +228,6 @@ class LeAdvertisingManagerTest : public ::testing::Test {
TestModuleRegistry fake_registry_;
TestHciLayer* test_hci_layer_ = nullptr;
TestController* test_controller_ = nullptr;
- TestAclManager* test_acl_manager_ = nullptr;
os::Thread& thread_ = fake_registry_.GetTestThread();
LeAdvertisingManager* le_advertising_manager_ = nullptr;
os::Handler* client_handler_ = nullptr;
@@ -347,85 +263,10 @@ class LeAdvertisingManagerTest : public ::testing::Test {
set_terminated_promise_.reset();
}
- void sync_client_handler() {
- std::promise<void> promise;
- auto future = promise.get_future();
- client_handler_->Call(common::BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)));
- auto future_status = future.wait_for(std::chrono::seconds(1));
- ASSERT_EQ(future_status, std::future_status::ready);
- }
-
std::unique_ptr<std::promise<Address>> address_promise_{};
std::unique_ptr<std::promise<ErrorCode>> set_terminated_promise_{};
OpCode param_opcode_{OpCode::LE_SET_ADVERTISING_PARAMETERS};
-
- class MockAdvertisingCallback : public AdvertisingCallback {
- public:
- MOCK_METHOD4(
- OnAdvertisingSetStarted, void(int reg_id, uint8_t advertiser_id, int8_t tx_power, AdvertisingStatus status));
- MOCK_METHOD3(OnAdvertisingEnabled, void(uint8_t advertiser_id, bool enable, uint8_t status));
- MOCK_METHOD2(OnAdvertisingDataSet, void(uint8_t advertiser_id, uint8_t status));
- MOCK_METHOD2(OnScanResponseDataSet, void(uint8_t advertiser_id, uint8_t status));
- MOCK_METHOD3(OnAdvertisingParametersUpdated, void(uint8_t advertiser_id, int8_t tx_power, uint8_t status));
- MOCK_METHOD2(OnPeriodicAdvertisingParametersUpdated, void(uint8_t advertiser_id, uint8_t status));
- MOCK_METHOD2(OnPeriodicAdvertisingDataSet, void(uint8_t advertiser_id, uint8_t status));
- MOCK_METHOD3(OnPeriodicAdvertisingEnabled, void(uint8_t advertiser_id, bool enable, uint8_t status));
- } mock_advertising_callback_;
-};
-
-class LeAdvertisingAPITest : public LeAdvertisingManagerTest {
- protected:
- void SetUp() override {
- LeAdvertisingManagerTest::SetUp();
-
- // start advertising set
- ExtendedAdvertisingConfig advertising_config{};
- advertising_config.advertising_type = AdvertisingType::ADV_IND;
- advertising_config.own_address_type = OwnAddressType::PUBLIC_DEVICE_ADDRESS;
- std::vector<GapData> gap_data{};
- GapData data_item{};
- data_item.data_type_ = GapDataType::FLAGS;
- data_item.data_ = {0x34};
- gap_data.push_back(data_item);
- data_item.data_type_ = GapDataType::COMPLETE_LOCAL_NAME;
- data_item.data_ = {'r', 'a', 'n', 'd', 'o', 'm', ' ', 'd', 'e', 'v', 'i', 'c', 'e'};
- gap_data.push_back(data_item);
- advertising_config.advertisement = gap_data;
- advertising_config.scan_response = gap_data;
-
- test_hci_layer_->SetCommandFuture();
- advertiser_id_ = le_advertising_manager_->ExtendedCreateAdvertiser(
- 0x00, advertising_config, scan_callback, set_terminated_callback, 0, 0, client_handler_);
- ASSERT_NE(LeAdvertisingManager::kInvalidId, advertiser_id_);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingSetStarted(0x00, advertiser_id_, 0x00, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- std::vector<OpCode> adv_opcodes = {
- OpCode::LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER,
- OpCode::LE_SET_ADVERTISING_PARAMETERS,
- OpCode::LE_SET_SCAN_RESPONSE_DATA,
- OpCode::LE_SET_ADVERTISING_DATA,
- OpCode::LE_SET_ADVERTISING_ENABLE,
- };
- std::vector<uint8_t> success_vector{static_cast<uint8_t>(ErrorCode::SUCCESS)};
- for (size_t i = 0; i < adv_opcodes.size(); i++) {
- auto packet_view = test_hci_layer_->GetCommand(adv_opcodes[i]);
- CommandView command_packet_view = CommandView::Create(packet_view);
- if (adv_opcodes[i] == OpCode::LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER) {
- test_hci_layer_->IncomingEvent(
- LeReadAdvertisingPhysicalChannelTxPowerCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, 0x00));
- } else {
- test_hci_layer_->IncomingEvent(
- CommandCompleteBuilder::Create(uint8_t{1}, adv_opcodes[i], std::make_unique<RawBuilder>(success_vector)));
- }
- test_hci_layer_->SetCommandFuture();
- }
- sync_client_handler();
- test_hci_layer_->ResetCommandFuture();
- }
-
- AdvertiserId advertiser_id_;
};
class LeAndroidHciAdvertisingManagerTest : public LeAdvertisingManagerTest {
@@ -437,54 +278,6 @@ class LeAndroidHciAdvertisingManagerTest : public LeAdvertisingManagerTest {
}
};
-class LeAndroidHciAdvertisingAPITest : public LeAndroidHciAdvertisingManagerTest {
- protected:
- void SetUp() override {
- LeAndroidHciAdvertisingManagerTest::SetUp();
-
- ExtendedAdvertisingConfig advertising_config{};
- advertising_config.advertising_type = AdvertisingType::ADV_IND;
- advertising_config.own_address_type = OwnAddressType::PUBLIC_DEVICE_ADDRESS;
- std::vector<GapData> gap_data{};
- GapData data_item{};
- data_item.data_type_ = GapDataType::FLAGS;
- data_item.data_ = {0x34};
- gap_data.push_back(data_item);
- data_item.data_type_ = GapDataType::COMPLETE_LOCAL_NAME;
- data_item.data_ = {'r', 'a', 'n', 'd', 'o', 'm', ' ', 'd', 'e', 'v', 'i', 'c', 'e'};
- gap_data.push_back(data_item);
- advertising_config.advertisement = gap_data;
- advertising_config.scan_response = gap_data;
-
- test_hci_layer_->SetSubCommandFuture(SubOcf::SET_PARAM);
- advertiser_id_ = le_advertising_manager_->ExtendedCreateAdvertiser(
- 0x00, advertising_config, scan_callback, set_terminated_callback, 0, 0, client_handler_);
- ASSERT_NE(LeAdvertisingManager::kInvalidId, advertiser_id_);
- std::vector<SubOcf> sub_ocf = {
- SubOcf::SET_PARAM,
- SubOcf::SET_DATA,
- SubOcf::SET_SCAN_RESP,
- SubOcf::SET_RANDOM_ADDR,
- SubOcf::SET_ENABLE,
- };
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingSetStarted(0, advertiser_id_, 0, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- for (size_t i = 0; i < sub_ocf.size(); i++) {
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_MULTI_ADVT);
- auto sub_packet = LeMultiAdvtView::Create(LeAdvertisingCommandView::Create(packet));
- ASSERT_TRUE(sub_packet.IsValid());
- test_hci_layer_->IncomingEvent(LeMultiAdvtCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, sub_ocf[i]));
- if ((i + 1) < sub_ocf.size()) {
- test_hci_layer_->SetSubCommandFuture(sub_ocf[i + 1]);
- }
- }
- sync_client_handler();
- }
-
- AdvertiserId advertiser_id_;
-};
-
class LeExtendedAdvertisingManagerTest : public LeAdvertisingManagerTest {
protected:
void SetUp() override {
@@ -494,62 +287,6 @@ class LeExtendedAdvertisingManagerTest : public LeAdvertisingManagerTest {
}
};
-class LeExtendedAdvertisingAPITest : public LeExtendedAdvertisingManagerTest {
- protected:
- void SetUp() override {
- LeExtendedAdvertisingManagerTest::SetUp();
-
- // start advertising set
- ExtendedAdvertisingConfig advertising_config{};
- advertising_config.advertising_type = AdvertisingType::ADV_IND;
- advertising_config.own_address_type = OwnAddressType::PUBLIC_DEVICE_ADDRESS;
- std::vector<GapData> gap_data{};
- GapData data_item{};
- data_item.data_type_ = GapDataType::FLAGS;
- data_item.data_ = {0x34};
- gap_data.push_back(data_item);
- data_item.data_type_ = GapDataType::COMPLETE_LOCAL_NAME;
- data_item.data_ = {'r', 'a', 'n', 'd', 'o', 'm', ' ', 'd', 'e', 'v', 'i', 'c', 'e'};
- gap_data.push_back(data_item);
- advertising_config.advertisement = gap_data;
- advertising_config.scan_response = gap_data;
- advertising_config.channel_map = 1;
- advertising_config.sid = 0x01;
-
- test_hci_layer_->SetCommandFuture();
- advertiser_id_ = le_advertising_manager_->ExtendedCreateAdvertiser(
- 0x00, advertising_config, scan_callback, set_terminated_callback, 0, 0, client_handler_);
- ASSERT_NE(LeAdvertisingManager::kInvalidId, advertiser_id_);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingSetStarted(0x00, advertiser_id_, -23, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- std::vector<OpCode> adv_opcodes = {
- OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS,
- OpCode::LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE,
- OpCode::LE_SET_EXTENDED_ADVERTISING_DATA,
- OpCode::LE_SET_EXTENDED_ADVERTISING_ENABLE,
- };
- std::vector<uint8_t> success_vector{static_cast<uint8_t>(ErrorCode::SUCCESS)};
- for (size_t i = 0; i < adv_opcodes.size(); i++) {
- auto packet_view = test_hci_layer_->GetCommand(adv_opcodes[i]);
- CommandView command_packet_view = CommandView::Create(packet_view);
- auto command = ConnectionManagementCommandView::Create(AclCommandView::Create(command_packet_view));
- if (adv_opcodes[i] == OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS) {
- test_hci_layer_->IncomingEvent(LeSetExtendedAdvertisingParametersCompleteBuilder::Create(
- uint8_t{1}, ErrorCode::SUCCESS, static_cast<uint8_t>(-23)));
- } else {
- test_hci_layer_->IncomingEvent(
- CommandCompleteBuilder::Create(uint8_t{1}, adv_opcodes[i], std::make_unique<RawBuilder>(success_vector)));
- }
- test_hci_layer_->SetCommandFuture();
- }
- sync_client_handler();
- test_hci_layer_->ResetCommandFuture();
- }
-
- AdvertiserId advertiser_id_;
-};
-
TEST_F(LeAdvertisingManagerTest, startup_teardown) {}
TEST_F(LeAndroidHciAdvertisingManagerTest, startup_teardown) {}
@@ -557,9 +294,9 @@ TEST_F(LeAndroidHciAdvertisingManagerTest, startup_teardown) {}
TEST_F(LeExtendedAdvertisingManagerTest, startup_teardown) {}
TEST_F(LeAdvertisingManagerTest, create_advertiser_test) {
- ExtendedAdvertisingConfig advertising_config{};
- advertising_config.advertising_type = AdvertisingType::ADV_IND;
- advertising_config.own_address_type = OwnAddressType::PUBLIC_DEVICE_ADDRESS;
+ AdvertisingConfig advertising_config{};
+ advertising_config.event_type = AdvertisingEventType::ADV_IND;
+ advertising_config.address_type = AddressType::PUBLIC_DEVICE_ADDRESS;
std::vector<GapData> gap_data{};
GapData data_item{};
data_item.data_type_ = GapDataType::FLAGS;
@@ -571,46 +308,36 @@ TEST_F(LeAdvertisingManagerTest, create_advertiser_test) {
advertising_config.advertisement = gap_data;
advertising_config.scan_response = gap_data;
- test_hci_layer_->SetCommandFuture();
- auto id = le_advertising_manager_->ExtendedCreateAdvertiser(
- 0x00, advertising_config, scan_callback, set_terminated_callback, 0, 0, client_handler_);
+ auto last_command_future = test_hci_layer_->GetCommandFuture(OpCode::LE_SET_ADVERTISING_ENABLE);
+ auto id = le_advertising_manager_->CreateAdvertiser(advertising_config, scan_callback, set_terminated_callback,
+ client_handler_);
ASSERT_NE(LeAdvertisingManager::kInvalidId, id);
std::vector<OpCode> adv_opcodes = {
- OpCode::LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER,
- OpCode::LE_SET_ADVERTISING_PARAMETERS,
- OpCode::LE_SET_SCAN_RESPONSE_DATA,
- OpCode::LE_SET_ADVERTISING_DATA,
- OpCode::LE_SET_ADVERTISING_ENABLE,
+ OpCode::LE_SET_ADVERTISING_PARAMETERS, OpCode::LE_SET_RANDOM_ADDRESS, OpCode::LE_SET_SCAN_RESPONSE_DATA,
+ OpCode::LE_SET_ADVERTISING_DATA, OpCode::LE_SET_ADVERTISING_ENABLE,
};
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingSetStarted(0x00, id, 0x00, AdvertisingCallback::AdvertisingStatus::SUCCESS));
std::vector<uint8_t> success_vector{static_cast<uint8_t>(ErrorCode::SUCCESS)};
+ auto result = last_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
+ ASSERT_EQ(std::future_status::ready, result);
for (size_t i = 0; i < adv_opcodes.size(); i++) {
- auto packet_view = test_hci_layer_->GetCommand(adv_opcodes[i]);
- CommandView command_packet_view = CommandView::Create(packet_view);
- auto command = ConnectionManagementCommandView::Create(AclCommandView::Create(command_packet_view));
- if (adv_opcodes[i] == OpCode::LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER) {
- test_hci_layer_->IncomingEvent(
- LeReadAdvertisingPhysicalChannelTxPowerCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, 0x00));
- } else {
- test_hci_layer_->IncomingEvent(
- CommandCompleteBuilder::Create(uint8_t{1}, adv_opcodes[i], std::make_unique<RawBuilder>(success_vector)));
- }
- test_hci_layer_->SetCommandFuture();
+ auto packet_view = test_hci_layer_->GetCommandPacket(adv_opcodes[i]);
+ CommandPacketView command_packet_view = CommandPacketView::Create(packet_view);
+ ConnectionManagementCommandView command = ConnectionManagementCommandView::Create(command_packet_view);
+ test_hci_layer_->IncomingEvent(
+ CommandCompleteBuilder::Create(uint8_t{1}, adv_opcodes[i], std::make_unique<RawBuilder>(success_vector)));
}
- sync_client_handler();
-
// Disable the advertiser
+ last_command_future = test_hci_layer_->GetCommandFuture(OpCode::LE_SET_ADVERTISING_ENABLE);
le_advertising_manager_->RemoveAdvertiser(id);
- test_hci_layer_->GetCommand(OpCode::LE_SET_ADVERTISING_ENABLE);
- sync_client_handler();
+ result = last_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
+ ASSERT_EQ(std::future_status::ready, result);
+ test_hci_layer_->IncomingEvent(LeSetAdvertisingEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
}
TEST_F(LeAndroidHciAdvertisingManagerTest, create_advertiser_test) {
- ExtendedAdvertisingConfig advertising_config{};
- advertising_config.advertising_type = AdvertisingType::ADV_IND;
- advertising_config.own_address_type = OwnAddressType::PUBLIC_DEVICE_ADDRESS;
+ AdvertisingConfig advertising_config{};
+ advertising_config.event_type = AdvertisingEventType::ADV_IND;
+ advertising_config.address_type = AddressType::PUBLIC_DEVICE_ADDRESS;
std::vector<GapData> gap_data{};
GapData data_item{};
data_item.data_type_ = GapDataType::FLAGS;
@@ -622,38 +349,36 @@ TEST_F(LeAndroidHciAdvertisingManagerTest, create_advertiser_test) {
advertising_config.advertisement = gap_data;
advertising_config.scan_response = gap_data;
- test_hci_layer_->SetSubCommandFuture(SubOcf::SET_PARAM);
- auto id = le_advertising_manager_->ExtendedCreateAdvertiser(
- 0x00, advertising_config, scan_callback, set_terminated_callback, 0, 0, client_handler_);
+ auto next_command_future = test_hci_layer_->GetSubCommandFuture(SubOcf::SET_ENABLE);
+ auto id = le_advertising_manager_->CreateAdvertiser(advertising_config, scan_callback, set_terminated_callback,
+ client_handler_);
ASSERT_NE(LeAdvertisingManager::kInvalidId, id);
std::vector<SubOcf> sub_ocf = {
SubOcf::SET_PARAM, SubOcf::SET_DATA, SubOcf::SET_SCAN_RESP, SubOcf::SET_RANDOM_ADDR, SubOcf::SET_ENABLE,
};
- EXPECT_CALL(
- mock_advertising_callback_, OnAdvertisingSetStarted(0, id, 0, AdvertisingCallback::AdvertisingStatus::SUCCESS));
+ auto result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
+ ASSERT_EQ(std::future_status::ready, result);
+ size_t num_commands = next_command_future.get();
for (size_t i = 0; i < sub_ocf.size(); i++) {
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_MULTI_ADVT);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::LE_MULTI_ADVT);
auto sub_packet = LeMultiAdvtView::Create(LeAdvertisingCommandView::Create(packet));
- ASSERT_TRUE(sub_packet.IsValid());
+ ASSERT(sub_packet.IsValid());
test_hci_layer_->IncomingEvent(LeMultiAdvtCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, sub_ocf[i]));
- if ((i + 1) < sub_ocf.size()) {
- test_hci_layer_->SetSubCommandFuture(sub_ocf[i + 1]);
- }
+ num_commands -= 1;
}
- sync_client_handler();
-
+ ASSERT_EQ(0, num_commands);
// Disable the advertiser
- test_hci_layer_->SetSubCommandFuture(SubOcf::SET_ENABLE);
+ next_command_future = test_hci_layer_->GetSubCommandFuture(SubOcf::SET_ENABLE);
le_advertising_manager_->RemoveAdvertiser(id);
- test_hci_layer_->GetCommand(OpCode::LE_MULTI_ADVT);
+ result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
+ ASSERT_EQ(std::future_status::ready, result);
test_hci_layer_->IncomingEvent(LeMultiAdvtSetEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
}
TEST_F(LeExtendedAdvertisingManagerTest, create_advertiser_test) {
ExtendedAdvertisingConfig advertising_config{};
- advertising_config.advertising_type = AdvertisingType::ADV_IND;
- advertising_config.own_address_type = OwnAddressType::PUBLIC_DEVICE_ADDRESS;
+ advertising_config.event_type = AdvertisingEventType::ADV_IND;
+ advertising_config.address_type = AddressType::PUBLIC_DEVICE_ADDRESS;
std::vector<GapData> gap_data{};
GapData data_item{};
data_item.data_type_ = GapDataType::FLAGS;
@@ -665,26 +390,23 @@ TEST_F(LeExtendedAdvertisingManagerTest, create_advertiser_test) {
advertising_config.advertisement = gap_data;
advertising_config.scan_response = gap_data;
advertising_config.channel_map = 1;
- advertising_config.sid = 0x01;
- test_hci_layer_->SetCommandFuture();
- auto id = le_advertising_manager_->ExtendedCreateAdvertiser(
- 0x00, advertising_config, scan_callback, set_terminated_callback, 0, 0, client_handler_);
+ auto last_command_future = test_hci_layer_->GetCommandFuture(OpCode::LE_SET_EXTENDED_ADVERTISING_ENABLE);
+ auto id = le_advertising_manager_->ExtendedCreateAdvertiser(advertising_config, scan_callback,
+ set_terminated_callback, client_handler_);
ASSERT_NE(LeAdvertisingManager::kInvalidId, id);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingSetStarted(0x00, id, -23, AdvertisingCallback::AdvertisingStatus::SUCCESS));
std::vector<OpCode> adv_opcodes = {
- OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS,
- OpCode::LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE,
- OpCode::LE_SET_EXTENDED_ADVERTISING_DATA,
+ OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS, OpCode::LE_SET_EXTENDED_ADVERTISING_RANDOM_ADDRESS,
+ OpCode::LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE, OpCode::LE_SET_EXTENDED_ADVERTISING_DATA,
OpCode::LE_SET_EXTENDED_ADVERTISING_ENABLE,
};
+ auto result = last_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
std::vector<uint8_t> success_vector{static_cast<uint8_t>(ErrorCode::SUCCESS)};
+ ASSERT_EQ(std::future_status::ready, result);
for (size_t i = 0; i < adv_opcodes.size(); i++) {
- auto packet_view = test_hci_layer_->GetCommand(adv_opcodes[i]);
- CommandView command_packet_view = CommandView::Create(packet_view);
- auto command = ConnectionManagementCommandView::Create(AclCommandView::Create(command_packet_view));
+ auto packet_view = test_hci_layer_->GetCommandPacket(adv_opcodes[i]);
+ CommandPacketView command_packet_view = CommandPacketView::Create(packet_view);
+ ConnectionManagementCommandView command = ConnectionManagementCommandView::Create(command_packet_view);
if (adv_opcodes[i] == OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS) {
test_hci_layer_->IncomingEvent(LeSetExtendedAdvertisingParametersCompleteBuilder::Create(
uint8_t{1}, ErrorCode::SUCCESS, static_cast<uint8_t>(-23)));
@@ -692,521 +414,14 @@ TEST_F(LeExtendedAdvertisingManagerTest, create_advertiser_test) {
test_hci_layer_->IncomingEvent(
CommandCompleteBuilder::Create(uint8_t{1}, adv_opcodes[i], std::make_unique<RawBuilder>(success_vector)));
}
- test_hci_layer_->SetCommandFuture();
}
- sync_client_handler();
-
- // Remove the advertiser
+ // Disable the advertiser
+ last_command_future = test_hci_layer_->GetCommandFuture(OpCode::LE_SET_EXTENDED_ADVERTISING_ENABLE);
le_advertising_manager_->RemoveAdvertiser(id);
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_ENABLE);
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_SET_PERIODIC_ADVERTISING_ENABLE);
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_REMOVE_ADVERTISING_SET);
- sync_client_handler();
-}
-
-TEST_F(LeAdvertisingAPITest, startup_teardown) {}
-
-TEST_F(LeAndroidHciAdvertisingAPITest, startup_teardown) {}
-
-TEST_F(LeExtendedAdvertisingAPITest, startup_teardown) {}
-
-TEST_F(LeAdvertisingAPITest, set_parameter) {
- ExtendedAdvertisingConfig advertising_config{};
- advertising_config.advertising_type = AdvertisingType::ADV_IND;
- advertising_config.own_address_type = OwnAddressType::PUBLIC_DEVICE_ADDRESS;
- std::vector<GapData> gap_data{};
- GapData data_item{};
- data_item.data_type_ = GapDataType::COMPLETE_LOCAL_NAME;
- data_item.data_ = {'r', 'a', 'n', 'd', 'o', 'm', ' ', 'd', 'e', 'v', 'i', 'c', 'e'};
- gap_data.push_back(data_item);
- advertising_config.advertisement = gap_data;
- advertising_config.channel_map = 1;
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->SetParameters(advertiser_id_, advertising_config);
- test_hci_layer_->GetCommand(OpCode::LE_SET_ADVERTISING_PARAMETERS);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingParametersUpdated(advertiser_id_, 0x00, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetAdvertisingParametersCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-}
-
-TEST_F(LeAndroidHciAdvertisingAPITest, set_parameter) {
- ExtendedAdvertisingConfig advertising_config{};
- advertising_config.advertising_type = AdvertisingType::ADV_IND;
- advertising_config.own_address_type = OwnAddressType::PUBLIC_DEVICE_ADDRESS;
- std::vector<GapData> gap_data{};
- GapData data_item{};
- data_item.data_type_ = GapDataType::COMPLETE_LOCAL_NAME;
- data_item.data_ = {'r', 'a', 'n', 'd', 'o', 'm', ' ', 'd', 'e', 'v', 'i', 'c', 'e'};
- gap_data.push_back(data_item);
- advertising_config.advertisement = gap_data;
- advertising_config.channel_map = 1;
- test_hci_layer_->SetSubCommandFuture(SubOcf::SET_PARAM);
- le_advertising_manager_->SetParameters(advertiser_id_, advertising_config);
- test_hci_layer_->GetCommand(OpCode::LE_MULTI_ADVT);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingParametersUpdated(advertiser_id_, 0x00, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeMultiAdvtCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, SubOcf::SET_PARAM));
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, set_parameter) {
- ExtendedAdvertisingConfig advertising_config{};
- advertising_config.advertising_type = AdvertisingType::ADV_IND;
- advertising_config.own_address_type = OwnAddressType::PUBLIC_DEVICE_ADDRESS;
- std::vector<GapData> gap_data{};
- GapData data_item{};
- data_item.data_type_ = GapDataType::COMPLETE_LOCAL_NAME;
- data_item.data_ = {'r', 'a', 'n', 'd', 'o', 'm', ' ', 'd', 'e', 'v', 'i', 'c', 'e'};
- gap_data.push_back(data_item);
- advertising_config.advertisement = gap_data;
- advertising_config.channel_map = 1;
- advertising_config.sid = 0x01;
- advertising_config.tx_power = 0x08;
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->SetParameters(advertiser_id_, advertising_config);
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingParametersUpdated(advertiser_id_, 0x08, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(
- LeSetExtendedAdvertisingParametersCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, 0x08));
- sync_client_handler();
-}
-
-TEST_F(LeAdvertisingAPITest, set_data_test) {
- // Set advertising data
- std::vector<GapData> advertising_data{};
- GapData data_item{};
- data_item.data_type_ = GapDataType::TX_POWER_LEVEL;
- data_item.data_ = {0x00};
- advertising_data.push_back(data_item);
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->SetData(advertiser_id_, false, advertising_data);
- test_hci_layer_->GetCommand(OpCode::LE_SET_ADVERTISING_DATA);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetAdvertisingDataCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-
- // Set scan response data
- std::vector<GapData> response_data{};
- GapData data_item2{};
- data_item2.data_type_ = GapDataType::COMPLETE_LOCAL_NAME;
- data_item2.data_ = {'t', 'e', 's', 't', ' ', 'd', 'e', 'v', 'i', 'c', 'e'};
- response_data.push_back(data_item2);
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->SetData(advertiser_id_, true, response_data);
- test_hci_layer_->GetCommand(OpCode::LE_SET_SCAN_RESPONSE_DATA);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnScanResponseDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetScanResponseDataCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, set_data_test) {
- // Set advertising data
- std::vector<GapData> advertising_data{};
- GapData data_item{};
- data_item.data_type_ = GapDataType::TX_POWER_LEVEL;
- data_item.data_ = {0x00};
- advertising_data.push_back(data_item);
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->SetData(advertiser_id_, false, advertising_data);
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_DATA);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetExtendedAdvertisingDataCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-
- // Set scan response data
- std::vector<GapData> response_data{};
- GapData data_item2{};
- data_item2.data_type_ = GapDataType::COMPLETE_LOCAL_NAME;
- data_item2.data_ = {'t', 'e', 's', 't', ' ', 'd', 'e', 'v', 'i', 'c', 'e'};
- response_data.push_back(data_item2);
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->SetData(advertiser_id_, true, response_data);
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnScanResponseDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(
- LeSetExtendedAdvertisingScanResponseCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-}
-
-TEST_F(LeAndroidHciAdvertisingAPITest, set_data_test) {
- // Set advertising data
- std::vector<GapData> advertising_data{};
- GapData data_item{};
- data_item.data_type_ = GapDataType::TX_POWER_LEVEL;
- data_item.data_ = {0x00};
- advertising_data.push_back(data_item);
- test_hci_layer_->SetSubCommandFuture(SubOcf::SET_DATA);
- le_advertising_manager_->SetData(advertiser_id_, false, advertising_data);
- test_hci_layer_->GetCommand(OpCode::LE_MULTI_ADVT);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeMultiAdvtCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, SubOcf::SET_DATA));
- sync_client_handler();
-
- // Set scan response data
- std::vector<GapData> response_data{};
- GapData data_item2{};
- data_item2.data_type_ = GapDataType::COMPLETE_LOCAL_NAME;
- data_item2.data_ = {'t', 'e', 's', 't', ' ', 'd', 'e', 'v', 'i', 'c', 'e'};
- response_data.push_back(data_item2);
- test_hci_layer_->SetSubCommandFuture(SubOcf::SET_SCAN_RESP);
- le_advertising_manager_->SetData(advertiser_id_, true, response_data);
- test_hci_layer_->GetCommand(OpCode::LE_MULTI_ADVT);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnScanResponseDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(
- LeMultiAdvtCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, SubOcf::SET_SCAN_RESP));
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, set_data_fragments_test) {
- // Set advertising data
- std::vector<GapData> advertising_data{};
- for (uint8_t i = 0; i < 3; i++) {
- GapData data_item{};
- data_item.data_.push_back(0xda);
- data_item.data_type_ = GapDataType::SERVICE_DATA_128_BIT_UUIDS;
- uint8_t uuid[16] = {0xf0, 0x34, 0x9b, 0x5f, 0x80, 0x00, 0x00, 0x80, 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, i};
- std::copy_n(uuid, 16, std::back_inserter(data_item.data_));
- uint8_t service_data[200];
- std::copy_n(service_data, 200, std::back_inserter(data_item.data_));
- advertising_data.push_back(data_item);
- }
- le_advertising_manager_->SetData(advertiser_id_, false, advertising_data);
-
- // First fragment
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_DATA);
-
- // Intermediate fragment
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_DATA);
-
- // Last fragment
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_DATA);
-
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetExtendedAdvertisingDataCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetExtendedAdvertisingDataCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetExtendedAdvertisingDataCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
-
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, set_scan_response_fragments_test) {
- // Set advertising data
- std::vector<GapData> advertising_data{};
- for (uint8_t i = 0; i < 3; i++) {
- GapData data_item{};
- data_item.data_.push_back(0xfa);
- data_item.data_type_ = GapDataType::SERVICE_DATA_128_BIT_UUIDS;
- uint8_t uuid[16] = {0xf0, 0x34, 0x9b, 0x5f, 0x80, 0x00, 0x00, 0x80, 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, i};
- std::copy_n(uuid, 16, std::back_inserter(data_item.data_));
- uint8_t service_data[232];
- std::copy_n(service_data, 232, std::back_inserter(data_item.data_));
- advertising_data.push_back(data_item);
- }
- le_advertising_manager_->SetData(advertiser_id_, true, advertising_data);
-
- // First fragment
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE);
-
- // Intermediate fragment
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE);
-
- // Last fragment
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE);
-
- EXPECT_CALL(
- mock_advertising_callback_,
- OnScanResponseDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(
- LeSetExtendedAdvertisingScanResponseCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- test_hci_layer_->IncomingEvent(
- LeSetExtendedAdvertisingScanResponseCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- test_hci_layer_->IncomingEvent(
- LeSetExtendedAdvertisingScanResponseCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
-
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, set_data_with_invalid_ad_structure) {
- // Set advertising data with AD structure that length greater than 251
- std::vector<GapData> advertising_data{};
- GapData data_item{};
- data_item.data_.push_back(0xfb);
- data_item.data_type_ = GapDataType::SERVICE_DATA_128_BIT_UUIDS;
- uint8_t uuid[16] = {0xf0, 0x34, 0x9b, 0x5f, 0x80, 0x00, 0x00, 0x80, 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00};
- std::copy_n(uuid, 16, std::back_inserter(data_item.data_));
- uint8_t service_data[233];
- std::copy_n(service_data, 233, std::back_inserter(data_item.data_));
- advertising_data.push_back(data_item);
-
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::INTERNAL_ERROR));
-
- le_advertising_manager_->SetData(advertiser_id_, false, advertising_data);
-
- EXPECT_CALL(
- mock_advertising_callback_,
- OnScanResponseDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::INTERNAL_ERROR));
- le_advertising_manager_->SetData(advertiser_id_, true, advertising_data);
-
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, set_data_with_invalid_length) {
- // Set advertising data with data that greater than le_maximum_advertising_data_length_
- std::vector<GapData> advertising_data{};
- for (uint8_t i = 0; i < 10; i++) {
- GapData data_item{};
- data_item.data_.push_back(0xfb);
- data_item.data_type_ = GapDataType::SERVICE_DATA_128_BIT_UUIDS;
- uint8_t uuid[16] = {0xf0, 0x34, 0x9b, 0x5f, 0x80, 0x00, 0x00, 0x80, 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, i};
- std::copy_n(uuid, 16, std::back_inserter(data_item.data_));
- uint8_t service_data[200];
- std::copy_n(service_data, 200, std::back_inserter(data_item.data_));
- advertising_data.push_back(data_item);
- }
-
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::DATA_TOO_LARGE));
- le_advertising_manager_->SetData(advertiser_id_, false, advertising_data);
-
- EXPECT_CALL(
- mock_advertising_callback_,
- OnScanResponseDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::DATA_TOO_LARGE));
- le_advertising_manager_->SetData(advertiser_id_, true, advertising_data);
-
- sync_client_handler();
-}
-
-TEST_F(LeAdvertisingAPITest, disable_enable_advertiser_test) {
- // disable advertiser
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->EnableAdvertiser(advertiser_id_, false, 0x00, 0x00);
- test_hci_layer_->GetCommand(OpCode::LE_SET_ADVERTISING_ENABLE);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingEnabled(advertiser_id_, false, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetAdvertisingEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-
- // enable advertiser
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->EnableAdvertiser(advertiser_id_, true, 0x00, 0x00);
- test_hci_layer_->GetCommand(OpCode::LE_SET_ADVERTISING_ENABLE);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingEnabled(advertiser_id_, true, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetAdvertisingEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-}
-
-TEST_F(LeAndroidHciAdvertisingAPITest, disable_enable_advertiser_test) {
- // disable advertiser
- test_hci_layer_->SetSubCommandFuture(SubOcf::SET_ENABLE);
- le_advertising_manager_->EnableAdvertiser(advertiser_id_, false, 0x00, 0x00);
- test_hci_layer_->GetCommand(OpCode::LE_MULTI_ADVT);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingEnabled(advertiser_id_, false, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(
- LeMultiAdvtCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, SubOcf::SET_ENABLE));
- sync_client_handler();
-
- // enable advertiser
- test_hci_layer_->SetSubCommandFuture(SubOcf::SET_ENABLE);
- le_advertising_manager_->EnableAdvertiser(advertiser_id_, true, 0x00, 0x00);
- test_hci_layer_->GetCommand(OpCode::LE_MULTI_ADVT);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingEnabled(advertiser_id_, true, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(
- LeMultiAdvtCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, SubOcf::SET_ENABLE));
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, disable_enable_advertiser_test) {
- // disable advertiser
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->EnableAdvertiser(advertiser_id_, false, 0x00, 0x00);
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_ENABLE);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingEnabled(advertiser_id_, false, AdvertisingCallback::AdvertisingStatus::SUCCESS));
+ result = last_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
+ ASSERT_EQ(std::future_status::ready, result);
test_hci_layer_->IncomingEvent(LeSetExtendedAdvertisingEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-
- // enable advertiser
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->EnableAdvertiser(advertiser_id_, true, 0x00, 0x00);
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_ADVERTISING_ENABLE);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnAdvertisingEnabled(advertiser_id_, true, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetExtendedAdvertisingEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, set_periodic_parameter) {
- PeriodicAdvertisingParameters advertising_config{};
- advertising_config.max_interval = 0x1000;
- advertising_config.min_interval = 0x0006;
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->SetPeriodicParameters(advertiser_id_, advertising_config);
- test_hci_layer_->GetCommand(OpCode::LE_SET_PERIODIC_ADVERTISING_PARAM);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnPeriodicAdvertisingParametersUpdated(advertiser_id_, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetPeriodicAdvertisingParamCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
}
-
-TEST_F(LeExtendedAdvertisingAPITest, set_periodic_data_test) {
- // Set advertising data
- std::vector<GapData> advertising_data{};
- GapData data_item{};
- data_item.data_type_ = GapDataType::TX_POWER_LEVEL;
- data_item.data_ = {0x00};
- advertising_data.push_back(data_item);
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->SetPeriodicData(advertiser_id_, advertising_data);
- test_hci_layer_->GetCommand(OpCode::LE_SET_PERIODIC_ADVERTISING_DATA);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnPeriodicAdvertisingDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetPeriodicAdvertisingDataCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, set_periodic_data_fragments_test) {
- // Set advertising data
- std::vector<GapData> advertising_data{};
- for (uint8_t i = 0; i < 3; i++) {
- GapData data_item{};
- data_item.data_.push_back(0xfa);
- data_item.data_type_ = GapDataType::SERVICE_DATA_128_BIT_UUIDS;
- uint8_t uuid[16] = {0xf0, 0x34, 0x9b, 0x5f, 0x80, 0x00, 0x00, 0x80, 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, i};
- std::copy_n(uuid, 16, std::back_inserter(data_item.data_));
- uint8_t service_data[232];
- std::copy_n(service_data, 232, std::back_inserter(data_item.data_));
- advertising_data.push_back(data_item);
- }
- le_advertising_manager_->SetPeriodicData(advertiser_id_, advertising_data);
-
- // First fragment
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_SET_PERIODIC_ADVERTISING_DATA);
-
- // Intermediate fragment
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_SET_PERIODIC_ADVERTISING_DATA);
-
- // Last fragment
- test_hci_layer_->SetCommandFuture();
- test_hci_layer_->GetCommand(OpCode::LE_SET_PERIODIC_ADVERTISING_DATA);
-
- EXPECT_CALL(
- mock_advertising_callback_,
- OnPeriodicAdvertisingDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetPeriodicAdvertisingDataCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetPeriodicAdvertisingDataCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetPeriodicAdvertisingDataCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
-
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, set_perodic_data_with_invalid_ad_structure) {
- // Set advertising data with AD structure that length greater than 251
- std::vector<GapData> advertising_data{};
- GapData data_item{};
- data_item.data_.push_back(0xfb);
- data_item.data_type_ = GapDataType::SERVICE_DATA_128_BIT_UUIDS;
- uint8_t uuid[16] = {0xf0, 0x34, 0x9b, 0x5f, 0x80, 0x00, 0x00, 0x80, 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00};
- std::copy_n(uuid, 16, std::back_inserter(data_item.data_));
- uint8_t service_data[233];
- std::copy_n(service_data, 233, std::back_inserter(data_item.data_));
- advertising_data.push_back(data_item);
-
- EXPECT_CALL(
- mock_advertising_callback_,
- OnPeriodicAdvertisingDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::INTERNAL_ERROR));
-
- le_advertising_manager_->SetPeriodicData(advertiser_id_, advertising_data);
-
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, set_perodic_data_with_invalid_length) {
- // Set advertising data with data that greater than le_maximum_advertising_data_length_
- std::vector<GapData> advertising_data{};
- for (uint8_t i = 0; i < 10; i++) {
- GapData data_item{};
- data_item.data_.push_back(0xfb);
- data_item.data_type_ = GapDataType::SERVICE_DATA_128_BIT_UUIDS;
- uint8_t uuid[16] = {0xf0, 0x34, 0x9b, 0x5f, 0x80, 0x00, 0x00, 0x80, 0x00, 0x10, 0x00, 0x00, 0x00, 0x10, 0x00, i};
- std::copy_n(uuid, 16, std::back_inserter(data_item.data_));
- uint8_t service_data[200];
- std::copy_n(service_data, 200, std::back_inserter(data_item.data_));
- advertising_data.push_back(data_item);
- }
-
- EXPECT_CALL(
- mock_advertising_callback_,
- OnPeriodicAdvertisingDataSet(advertiser_id_, AdvertisingCallback::AdvertisingStatus::DATA_TOO_LARGE));
- le_advertising_manager_->SetPeriodicData(advertiser_id_, advertising_data);
-
- sync_client_handler();
-}
-
-TEST_F(LeExtendedAdvertisingAPITest, disable_enable_periodic_advertiser_test) {
- // disable advertiser
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->EnablePeriodicAdvertising(advertiser_id_, false);
- test_hci_layer_->GetCommand(OpCode::LE_SET_PERIODIC_ADVERTISING_ENABLE);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnPeriodicAdvertisingEnabled(advertiser_id_, false, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetPeriodicAdvertisingEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-
- // enable advertiser
- test_hci_layer_->SetCommandFuture();
- le_advertising_manager_->EnablePeriodicAdvertising(advertiser_id_, true);
- test_hci_layer_->GetCommand(OpCode::LE_SET_PERIODIC_ADVERTISING_ENABLE);
- EXPECT_CALL(
- mock_advertising_callback_,
- OnPeriodicAdvertisingEnabled(advertiser_id_, true, AdvertisingCallback::AdvertisingStatus::SUCCESS));
- test_hci_layer_->IncomingEvent(LeSetPeriodicAdvertisingEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- sync_client_handler();
-}
-
} // namespace
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/le_device.h b/gd/hci/le_device.h
new file mode 100644
index 000000000..35a620b66
--- /dev/null
+++ b/gd/hci/le_device.h
@@ -0,0 +1,89 @@
+/******************************************************************************
+ *
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+#pragma once
+
+#include "hci/device.h"
+
+namespace bluetooth::hci {
+
+/**
+ * TODO(optedoblivion): Build out AddressType getter/setter
+ */
+// enum AddressType {};
+
+/**
+ * A device representing a LE device.
+ *
+ * <p>This can be a LE only or a piece of a DUAL MODE device.
+ *
+ * <p>LE specific public address logic goes here.
+ */
+class LeDevice : public Device {
+ public:
+ void SetPublicAddress(Address public_address) {
+ public_address_ = public_address;
+ }
+
+ Address GetPublicAddress() {
+ return public_address_;
+ }
+
+ void SetIrk(uint8_t irk) {
+ irk_ = irk;
+ // TODO(optedoblivion): Set derived Address
+ }
+
+ uint8_t GetIrk() {
+ return irk_;
+ }
+
+ protected:
+ friend class DeviceDatabase;
+ // TODO(optedoblivion): How to set public address. Do I set it when no IRK is known?
+ // Right now my thought is to do this:
+ // 1. Construct LeDevice with address of all 0s
+ // 2. IF NO IRK AND NO PRIVATE ADDRESS: (i.e. nothing in disk cache)
+ // a. Hopefully pairing will happen
+ // b. Pending successful pairing get the IRK and Private Address
+ // c. Set Both to device.
+ // (d). If available set IRK to the controller (later iteration)
+ // [#3 should indicate we have a bug]
+ // 3. IF YES IRK AND NO PRIVATE ADDRESS: (Partial Disk Cache Information)
+ // a. Set IRK
+ // b. Generate Private Address
+ // c. Set Private Address to device
+ // (d). If available set IRK to the controller (later iteration)
+ // 4. IF YES IRK AND YES PRIVATE ADDRESS: (i.e. Disk cache hit)
+ // a. Construct with private address
+ // b. Set IRK
+ // (c). If available set IRK to the controller (later iteration)
+ // 5. IF NO IRK AND YES PRIVATE ADDRESS (we have a bug)
+ // a1. -Construct with private address-
+ // b. -Indicate we need to repair or query for IRK?-
+ //
+ // or
+ //
+ // a2. Don't use class
+ explicit LeDevice(Address address) : Device(address, DeviceType::LE), public_address_(), irk_(0) {}
+
+ private:
+ Address public_address_;
+ uint8_t irk_;
+};
+
+} // namespace bluetooth::hci
diff --git a/gd/hci/le_iso_interface.h b/gd/hci/le_iso_interface.h
deleted file mode 100644
index a6a8a31a4..000000000
--- a/gd/hci/le_iso_interface.h
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "hci/command_interface.h"
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace hci {
-
-constexpr hci::SubeventCode LeIsoEvents[] = {
- hci::SubeventCode::CIS_ESTABLISHED,
- hci::SubeventCode::CIS_REQUEST,
- hci::SubeventCode::CREATE_BIG_COMPLETE,
- hci::SubeventCode::TERMINATE_BIG_COMPLETE,
- hci::SubeventCode::BIG_SYNC_ESTABLISHED,
- hci::SubeventCode::BIG_SYNC_LOST,
- hci::SubeventCode::BIG_INFO_ADVERTISING_REPORT,
-};
-
-typedef CommandInterface<LeIsoCommandBuilder> LeIsoInterface;
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/le_report.h b/gd/hci/le_report.h
new file mode 100644
index 000000000..7beeed6d8
--- /dev/null
+++ b/gd/hci/le_report.h
@@ -0,0 +1,86 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#pragma once
+
+#include <memory>
+
+#include "hci/hci_packets.h"
+
+namespace bluetooth::hci {
+
+class LeReport {
+ public:
+ explicit LeReport(const LeAdvertisingReport& advertisement)
+ : report_type_(ReportType::ADVERTISING_EVENT), advertising_event_type_(advertisement.event_type_),
+ address_(advertisement.address_), address_type_(advertisement.address_type_), rssi_(advertisement.rssi_),
+ gap_data_(advertisement.advertising_data_) {}
+ explicit LeReport(const LeDirectedAdvertisingReport& advertisement)
+ : report_type_(ReportType::DIRECTED_ADVERTISING_EVENT), address_(advertisement.address_),
+ rssi_(advertisement.rssi_) {}
+ explicit LeReport(const LeExtendedAdvertisingReport& advertisement)
+ : report_type_(ReportType::EXTENDED_ADVERTISING_EVENT), address_(advertisement.address_),
+ rssi_(advertisement.rssi_), gap_data_(advertisement.advertising_data_) {}
+ virtual ~LeReport() = default;
+
+ enum class ReportType {
+ ADVERTISING_EVENT = 1,
+ DIRECTED_ADVERTISING_EVENT = 2,
+ EXTENDED_ADVERTISING_EVENT = 3,
+ };
+ const ReportType report_type_;
+
+ ReportType GetReportType() const {
+ return report_type_;
+ }
+
+ // Advertising Event
+ const AdvertisingEventType advertising_event_type_{};
+ const Address address_{};
+ const AddressType address_type_{};
+ const int8_t rssi_;
+ const std::vector<GapData> gap_data_{};
+};
+
+class DirectedLeReport : public LeReport {
+ public:
+ explicit DirectedLeReport(const LeDirectedAdvertisingReport& advertisement)
+ : LeReport(advertisement), direct_address_type_(advertisement.address_type_),
+ direct_address_(advertisement.direct_address_) {}
+ explicit DirectedLeReport(const LeExtendedAdvertisingReport& advertisement)
+ : LeReport(advertisement), direct_address_type_(advertisement.address_type_),
+ direct_address_(advertisement.direct_address_) {}
+
+ const DirectAdvertisingAddressType direct_address_type_{};
+ const Address direct_address_{};
+};
+
+class ExtendedLeReport : public DirectedLeReport {
+ public:
+ explicit ExtendedLeReport(const LeExtendedAdvertisingReport& advertisement)
+ : DirectedLeReport(advertisement), connectable_(advertisement.connectable_), scannable_(advertisement.scannable_),
+ directed_(advertisement.directed_), scan_response_(advertisement.scan_response_),
+ complete_(advertisement.data_status_ == DataStatus::COMPLETE),
+ truncated_(advertisement.data_status_ == DataStatus::TRUNCATED) {}
+
+ // Extended
+ bool connectable_;
+ bool scannable_;
+ bool directed_;
+ bool scan_response_;
+ bool complete_;
+ bool truncated_;
+};
+} // namespace bluetooth::hci \ No newline at end of file
diff --git a/gd/hci/le_scanning_interface.h b/gd/hci/le_scanning_interface.h
index 49d1ab118..97a676625 100644
--- a/gd/hci/le_scanning_interface.h
+++ b/gd/hci/le_scanning_interface.h
@@ -16,22 +16,35 @@
#pragma once
-#include "hci/command_interface.h"
+#include "common/callback.h"
#include "hci/hci_packets.h"
+#include "os/handler.h"
+#include "os/utils.h"
namespace bluetooth {
namespace hci {
-constexpr hci::SubeventCode LeScanningEvents[] = {
- hci::SubeventCode::SCAN_TIMEOUT,
- hci::SubeventCode::ADVERTISING_REPORT,
- hci::SubeventCode::DIRECTED_ADVERTISING_REPORT,
- hci::SubeventCode::EXTENDED_ADVERTISING_REPORT,
- hci::SubeventCode::PERIODIC_ADVERTISING_REPORT,
- hci::SubeventCode::PERIODIC_ADVERTISING_SYNC_ESTABLISHED,
- hci::SubeventCode::PERIODIC_ADVERTISING_SYNC_LOST,
-};
+class LeScanningInterface {
+ public:
+ LeScanningInterface() = default;
+ virtual ~LeScanningInterface() = default;
+ DISALLOW_COPY_AND_ASSIGN(LeScanningInterface);
+
+ virtual void EnqueueCommand(std::unique_ptr<LeScanningCommandBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) = 0;
-typedef CommandInterface<LeScanningCommandBuilder> LeScanningInterface;
+ virtual void EnqueueCommand(std::unique_ptr<LeScanningCommandBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) = 0;
+
+ static constexpr hci::SubeventCode LeScanningEvents[] = {
+ hci::SubeventCode::SCAN_TIMEOUT,
+ hci::SubeventCode::ADVERTISING_REPORT,
+ hci::SubeventCode::DIRECTED_ADVERTISING_REPORT,
+ hci::SubeventCode::EXTENDED_ADVERTISING_REPORT,
+ hci::SubeventCode::PERIODIC_ADVERTISING_REPORT,
+ hci::SubeventCode::PERIODIC_ADVERTISING_SYNC_ESTABLISHED,
+ hci::SubeventCode::PERIODIC_ADVERTISING_SYNC_LOST,
+ };
+};
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/le_scanning_manager.cc b/gd/hci/le_scanning_manager.cc
index 3a7380627..c3b96d9f4 100644
--- a/gd/hci/le_scanning_manager.cc
+++ b/gd/hci/le_scanning_manager.cc
@@ -17,13 +17,11 @@
#include <mutex>
#include <set>
-#include "hci/acl_manager.h"
#include "hci/controller.h"
#include "hci/hci_layer.h"
#include "hci/hci_packets.h"
#include "hci/le_scanning_interface.h"
#include "hci/le_scanning_manager.h"
-#include "hci/vendor_specific_event_manager.h"
#include "module.h"
#include "os/handler.h"
#include "os/log.h"
@@ -31,1212 +29,171 @@
namespace bluetooth {
namespace hci {
-constexpr uint16_t kLeScanWindowMin = 0x0004;
-constexpr uint16_t kLeScanWindowMax = 0x4000;
-constexpr uint16_t kDefaultLeExtendedScanWindow = 4800;
-constexpr uint16_t kLeExtendedScanWindowMax = 0xFFFF;
-constexpr uint16_t kLeScanIntervalMin = 0x0004;
-constexpr uint16_t kLeScanIntervalMax = 0x4000;
-constexpr uint16_t kDefaultLeExtendedScanInterval = 4800;
-constexpr uint16_t kLeExtendedScanIntervalMax = 0xFFFF;
-
-constexpr uint8_t kScannableBit = 1;
-constexpr uint8_t kDirectedBit = 2;
-constexpr uint8_t kScanResponseBit = 3;
-constexpr uint8_t kLegacyBit = 4;
-constexpr uint8_t kDataStatusBits = 5;
+constexpr uint16_t kDefaultLeScanWindow = 4800;
+constexpr uint16_t kDefaultLeScanInterval = 4800;
const ModuleFactory LeScanningManager::Factory = ModuleFactory([]() { return new LeScanningManager(); });
enum class ScanApiType {
- LEGACY = 1,
+ LE_4_0 = 1,
ANDROID_HCI = 2,
- EXTENDED = 3,
-};
-
-struct Scanner {
- Uuid app_uuid;
- bool in_use;
-};
-
-class AdvertisingCache {
- public:
- const std::vector<uint8_t>& Set(const AddressWithType& address_with_type, std::vector<uint8_t> data) {
- auto it = Find(address_with_type);
- if (it != items.end()) {
- it->data = std::move(data);
- return it->data;
- }
-
- if (items.size() > cache_max) {
- items.pop_back();
- }
-
- items.emplace_front(address_with_type, std::move(data));
- return items.front().data;
- }
-
- bool Exist(const AddressWithType& address_with_type) {
- auto it = Find(address_with_type);
- if (it == items.end()) {
- return false;
- }
- return true;
- }
-
- const std::vector<uint8_t>& Append(const AddressWithType& address_with_type, std::vector<uint8_t> data) {
- auto it = Find(address_with_type);
- if (it != items.end()) {
- it->data.insert(it->data.end(), data.begin(), data.end());
- return it->data;
- }
-
- if (items.size() > cache_max) {
- items.pop_back();
- }
-
- items.emplace_front(address_with_type, std::move(data));
- return items.front().data;
- }
-
- /* Clear data for device |addr_type, addr| */
- void Clear(AddressWithType address_with_type) {
- auto it = Find(address_with_type);
- if (it != items.end()) {
- items.erase(it);
- }
- }
-
- void ClearAll() {
- items.clear();
- }
-
- struct Item {
- AddressWithType address_with_type;
- std::vector<uint8_t> data;
-
- Item(const AddressWithType& address_with_type, std::vector<uint8_t> data)
- : address_with_type(address_with_type), data(data) {}
- };
-
- std::list<Item>::iterator Find(const AddressWithType& address_with_type) {
- for (auto it = items.begin(); it != items.end(); it++) {
- if (it->address_with_type == address_with_type) {
- return it;
- }
- }
- return items.end();
- }
-
- /* we keep maximum 7 devices in the cache */
- const size_t cache_max = 1000;
- std::list<Item> items;
-};
-
-class NullScanningCallback : public ScanningCallback {
- void OnScannerRegistered(const bluetooth::hci::Uuid app_uuid, ScannerId scanner_id, ScanningStatus status) {
- LOG_INFO("OnScannerRegistered in NullScanningCallback");
- }
- void OnScanResult(
- uint16_t event_type,
- uint8_t address_type,
- Address address,
- uint8_t primary_phy,
- uint8_t secondary_phy,
- uint8_t advertising_sid,
- int8_t tx_power,
- int8_t rssi,
- uint16_t periodic_advertising_interval,
- std::vector<uint8_t> advertising_data) {
- LOG_INFO("OnScanResult in NullScanningCallback");
- }
- void OnTrackAdvFoundLost(AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info) {
- LOG_INFO("OnTrackAdvFoundLost in NullScanningCallback");
- }
- void OnBatchScanReports(int client_if, int status, int report_format, int num_records, std::vector<uint8_t> data) {
- LOG_INFO("OnBatchScanReports in NullScanningCallback");
- }
- void OnBatchScanThresholdCrossed(int client_if) {
- LOG_INFO("OnBatchScanThresholdCrossed in NullScanningCallback");
- }
- void OnTimeout() {
- LOG_INFO("OnTimeout in NullScanningCallback");
- }
- void OnFilterEnable(Enable enable, uint8_t status) {
- LOG_INFO("OnFilterEnable in NullScanningCallback");
- }
- void OnFilterParamSetup(uint8_t available_spaces, ApcfAction action, uint8_t status) {
- LOG_INFO("OnFilterParamSetup in NullScanningCallback");
- }
- void OnFilterConfigCallback(
- ApcfFilterType filter_type, uint8_t available_spaces, ApcfAction action, uint8_t status) {
- LOG_INFO("OnFilterConfigCallback in NullScanningCallback");
- }
-};
-
-enum class BatchScanState {
- ERROR_STATE = 0,
- ENABLE_CALLED = 1,
- ENABLED_STATE = 2,
- DISABLE_CALLED = 3,
- DISABLED_STATE = 4,
+ LE_5_0 = 3,
};
-#define BTM_BLE_BATCH_SCAN_MODE_DISABLE 0
-#define BTM_BLE_BATCH_SCAN_MODE_PASS 1
-#define BTM_BLE_BATCH_SCAN_MODE_ACTI 2
-#define BTM_BLE_BATCH_SCAN_MODE_PASS_ACTI 3
-
-struct BatchScanConfig {
- BatchScanState current_state;
- BatchScanMode scan_mode;
- uint32_t scan_interval;
- uint32_t scan_window;
- BatchScanDiscardRule discard_rule;
- ScannerId ref_value;
-};
-
-struct LeScanningManager::impl : public bluetooth::hci::LeAddressManagerCallback {
+struct LeScanningManager::impl {
impl(Module* module) : module_(module), le_scanning_interface_(nullptr) {}
- ~impl() {
- if (address_manager_registered_) {
- le_address_manager_->Unregister(this);
- }
- }
-
- void start(
- os::Handler* handler,
- hci::HciLayer* hci_layer,
- hci::Controller* controller,
- hci::AclManager* acl_manager,
- hci::VendorSpecificEventManager* vendor_specific_event_manager) {
+ void start(os::Handler* handler, hci::HciLayer* hci_layer, hci::Controller* controller) {
module_handler_ = handler;
hci_layer_ = hci_layer;
controller_ = controller;
- vendor_specific_event_manager_ = vendor_specific_event_manager;
- le_address_manager_ = acl_manager->GetLeAddressManager();
le_scanning_interface_ = hci_layer_->GetLeScanningInterface(
- module_handler_->BindOn(this, &LeScanningManager::impl::handle_scan_results));
+ common::Bind(&LeScanningManager::impl::handle_scan_results, common::Unretained(this)), module_handler_);
if (controller_->IsSupported(OpCode::LE_SET_EXTENDED_SCAN_PARAMETERS)) {
- api_type_ = ScanApiType::EXTENDED;
- interval_ms_ = kDefaultLeExtendedScanInterval;
- window_ms_ = kDefaultLeExtendedScanWindow;
+ api_type_ = ScanApiType::LE_5_0;
} else if (controller_->IsSupported(OpCode::LE_EXTENDED_SCAN_PARAMS)) {
api_type_ = ScanApiType::ANDROID_HCI;
} else {
- api_type_ = ScanApiType::LEGACY;
- }
- is_filter_support_ = controller_->IsSupported(OpCode::LE_ADV_FILTER);
- is_batch_scan_support_ = controller->IsSupported(OpCode::LE_BATCH_SCAN);
- if (is_batch_scan_support_) {
- vendor_specific_event_manager_->RegisterEventHandler(
- VseSubeventCode::BLE_THRESHOLD, handler->BindOn(this, &LeScanningManager::impl::on_storage_threshold_breach));
- vendor_specific_event_manager_->RegisterEventHandler(
- VseSubeventCode::BLE_TRACKING, handler->BindOn(this, &LeScanningManager::impl::on_advertisement_tracking));
- }
- scanners_ = std::vector<Scanner>(kMaxAppNum + 1);
- for (size_t i = 0; i < scanners_.size(); i++) {
- scanners_[i].app_uuid = Uuid::kEmpty;
- scanners_[i].in_use = false;
+ api_type_ = ScanApiType::LE_4_0;
}
- batch_scan_config_.current_state = BatchScanState::DISABLED_STATE;
- batch_scan_config_.ref_value = kInvalidScannerId;
configure_scan();
}
- void stop() {
- for (auto subevent_code : LeScanningEvents) {
- hci_layer_->UnregisterLeEventHandler(subevent_code);
- }
- if (is_batch_scan_support_) {
- // TODO implete vse module
- // hci_layer_->UnregisterVesEventHandler(VseSubeventCode::BLE_THRESHOLD);
- // hci_layer_->UnregisterVesEventHandler(VseSubeventCode::BLE_TRACKING);
- }
- batch_scan_config_.current_state = BatchScanState::DISABLED_STATE;
- batch_scan_config_.ref_value = kInvalidScannerId;
- scanning_callbacks_ = &null_scanning_callback_;
- }
-
void handle_scan_results(LeMetaEventView event) {
switch (event.GetSubeventCode()) {
case hci::SubeventCode::ADVERTISING_REPORT:
- handle_advertising_report(LeAdvertisingReportView::Create(event));
+ handle_advertising_report<LeAdvertisingReportView, LeAdvertisingReport, LeReport>(
+ LeAdvertisingReportView::Create(event));
break;
case hci::SubeventCode::DIRECTED_ADVERTISING_REPORT:
- handle_directed_advertising_report(LeDirectedAdvertisingReportView::Create(event));
+ handle_advertising_report<LeDirectedAdvertisingReportView, LeDirectedAdvertisingReport, DirectedLeReport>(
+ LeDirectedAdvertisingReportView::Create(event));
break;
case hci::SubeventCode::EXTENDED_ADVERTISING_REPORT:
- handle_extended_advertising_report(LeExtendedAdvertisingReportView::Create(event));
+ handle_advertising_report<LeExtendedAdvertisingReportView, LeExtendedAdvertisingReport, ExtendedLeReport>(
+ LeExtendedAdvertisingReportView::Create(event));
break;
case hci::SubeventCode::SCAN_TIMEOUT:
- scanning_callbacks_->OnTimeout();
+ if (registered_callback_ != nullptr) {
+ registered_callback_->Handler()->Post(
+ common::BindOnce(&LeScanningManagerCallbacks::on_timeout, common::Unretained(registered_callback_)));
+ registered_callback_ = nullptr;
+ }
break;
default:
LOG_ALWAYS_FATAL("Unknown advertising subevent %s", hci::SubeventCodeText(event.GetSubeventCode()).c_str());
}
}
- struct ExtendedEventTypeOptions {
- bool connectable{false};
- bool scannable{false};
- bool directed{false};
- bool scan_response{false};
- bool legacy{false};
- bool continuing{false};
- bool truncated{false};
- };
-
- void transform_to_extended_event_type(uint16_t* extended_event_type, ExtendedEventTypeOptions o) {
- ASSERT(extended_event_type != nullptr);
- *extended_event_type = (o.connectable ? 0x0001 << 0 : 0) | (o.scannable ? 0x0001 << 1 : 0) |
- (o.directed ? 0x0001 << 2 : 0) | (o.scan_response ? 0x0001 << 3 : 0) |
- (o.legacy ? 0x0001 << 4 : 0) | (o.continuing ? 0x0001 << 5 : 0) |
- (o.truncated ? 0x0001 << 6 : 0);
- }
-
- void handle_advertising_report(LeAdvertisingReportView event_view) {
- if (!event_view.IsValid()) {
- LOG_INFO("Dropping invalid advertising event");
- return;
- }
- std::vector<LeAdvertisingReport> reports = event_view.GetAdvertisingReports();
- if (reports.empty()) {
- LOG_INFO("Zero results in advertising event");
- return;
- }
-
- for (LeAdvertisingReport report : reports) {
- uint16_t extended_event_type = 0;
- switch (report.event_type_) {
- case hci::AdvertisingEventType::ADV_IND:
- transform_to_extended_event_type(
- &extended_event_type, {.connectable = true, .scannable = true, .legacy = true});
- break;
- case hci::AdvertisingEventType::ADV_DIRECT_IND:
- transform_to_extended_event_type(
- &extended_event_type, {.connectable = true, .directed = true, .legacy = true});
- break;
- case hci::AdvertisingEventType::ADV_SCAN_IND:
- transform_to_extended_event_type(&extended_event_type, {.scannable = true, .legacy = true});
- break;
- case hci::AdvertisingEventType::ADV_NONCONN_IND:
- transform_to_extended_event_type(&extended_event_type, {.legacy = true});
- break;
- case hci::AdvertisingEventType::SCAN_RESPONSE:
- transform_to_extended_event_type(
- &extended_event_type, {.connectable = true, .scannable = true, .scan_response = true, .legacy = true});
- break;
- default:
- LOG_WARN("Unsupported event type:%d", (uint16_t)report.event_type_);
- return;
- }
-
- std::vector<uint8_t> advertising_data = {};
- for (auto gap_data : report.advertising_data_) {
- advertising_data.push_back((uint8_t)gap_data.size() - 1);
- advertising_data.push_back((uint8_t)gap_data.data_type_);
- advertising_data.insert(advertising_data.end(), gap_data.data_.begin(), gap_data.data_.end());
- }
-
- process_advertising_package_content(
- extended_event_type,
- (uint8_t)report.address_type_,
- report.address_,
- (uint8_t)PrimaryPhyType::LE_1M,
- (uint8_t)SecondaryPhyType::NO_PACKETS,
- kAdvertisingDataInfoNotPresent,
- kTxPowerInformationNotPresent,
- report.rssi_,
- kNotPeriodicAdvertisement,
- advertising_data);
- }
- }
-
- void handle_directed_advertising_report(LeDirectedAdvertisingReportView event_view) {
- if (!event_view.IsValid()) {
- LOG_INFO("Dropping invalid advertising event");
- return;
- }
- std::vector<LeDirectedAdvertisingReport> reports = event_view.GetAdvertisingReports();
- if (reports.empty()) {
- LOG_INFO("Zero results in advertising event");
+ template <class EventType, class ReportStructType, class ReportType>
+ void handle_advertising_report(EventType event_view) {
+ if (registered_callback_ == nullptr) {
+ LOG_INFO("Dropping advertising event (no registered handler)");
return;
}
- uint16_t extended_event_type = 0;
- transform_to_extended_event_type(&extended_event_type, {.connectable = true, .directed = true, .legacy = true});
- // TODO: parse report
- }
-
- void handle_extended_advertising_report(LeExtendedAdvertisingReportView event_view) {
if (!event_view.IsValid()) {
LOG_INFO("Dropping invalid advertising event");
return;
}
- std::vector<LeExtendedAdvertisingReport> reports = event_view.GetAdvertisingReports();
- if (reports.empty()) {
+ std::vector<ReportStructType> report_vector = event_view.GetAdvertisingReports();
+ if (report_vector.empty()) {
LOG_INFO("Zero results in advertising event");
return;
}
-
- for (LeExtendedAdvertisingReport report : reports) {
- uint16_t event_type = report.connectable_ | (report.scannable_ << kScannableBit) |
- (report.directed_ << kDirectedBit) | (report.scan_response_ << kScanResponseBit) |
- (report.legacy_ << kLegacyBit) | ((uint16_t)report.data_status_ << kDataStatusBits);
- process_advertising_package_content(
- event_type,
- (uint8_t)report.address_type_,
- report.address_,
- (uint8_t)report.primary_phy_,
- (uint8_t)report.secondary_phy_,
- report.advertising_sid_,
- report.tx_power_,
- report.rssi_,
- report.periodic_advertising_interval_,
- report.advertising_data_);
- }
- }
-
- void process_advertising_package_content(
- uint16_t event_type,
- uint8_t address_type,
- Address address,
- uint8_t primary_phy,
- uint8_t secondary_phy,
- uint8_t advertising_sid,
- int8_t tx_power,
- int8_t rssi,
- uint16_t periodic_advertising_interval,
- std::vector<uint8_t> advertising_data) {
- bool is_scannable = event_type & (1 << kScannableBit);
- bool is_scan_response = event_type & (1 << kScanResponseBit);
- bool is_legacy = event_type & (1 << kLegacyBit);
-
- if (address_type == (uint8_t)DirectAdvertisingAddressType::NO_ADDRESS) {
- scanning_callbacks_->OnScanResult(
- event_type,
- address_type,
- address,
- primary_phy,
- secondary_phy,
- advertising_sid,
- tx_power,
- rssi,
- periodic_advertising_interval,
- advertising_data);
- return;
- } else if (address == Address::kEmpty) {
- LOG_WARN("Receive non-anonymous advertising report with empty address, skip!");
- return;
- }
-
- AddressWithType address_with_type(address, (AddressType)address_type);
-
- if (is_legacy && is_scan_response && !advertising_cache_.Exist(address_with_type)) {
- return;
- }
-
- bool is_start = is_legacy && is_scannable && !is_scan_response;
-
- std::vector<uint8_t> const& adv_data = is_start ? advertising_cache_.Set(address_with_type, advertising_data)
- : advertising_cache_.Append(address_with_type, advertising_data);
-
- uint8_t data_status = event_type >> kDataStatusBits;
- if (data_status == (uint8_t)DataStatus::CONTINUING) {
- // Waiting for whole data
- return;
- }
-
- if (is_scannable && !is_scan_response) {
- // Waiting for scan response
- return;
+ std::vector<std::shared_ptr<LeReport>> param;
+ param.reserve(report_vector.size());
+ for (const ReportStructType& report : report_vector) {
+ param.push_back(std::shared_ptr<LeReport>(static_cast<LeReport*>(new ReportType(report))));
}
-
- scanning_callbacks_->OnScanResult(
- event_type,
- address_type,
- address,
- primary_phy,
- secondary_phy,
- advertising_sid,
- tx_power,
- rssi,
- periodic_advertising_interval,
- adv_data);
-
- advertising_cache_.Clear(address_with_type);
+ registered_callback_->Handler()->Post(common::BindOnce(&LeScanningManagerCallbacks::on_advertisements,
+ common::Unretained(registered_callback_), param));
}
void configure_scan() {
std::vector<PhyScanParameters> parameter_vector;
PhyScanParameters phy_scan_parameters;
- phy_scan_parameters.le_scan_window_ = window_ms_;
- phy_scan_parameters.le_scan_interval_ = interval_ms_;
- phy_scan_parameters.le_scan_type_ = le_scan_type_;
+ phy_scan_parameters.le_scan_window_ = kDefaultLeScanWindow;
+ phy_scan_parameters.le_scan_interval_ = kDefaultLeScanInterval;
+ phy_scan_parameters.le_scan_type_ = LeScanType::ACTIVE;
parameter_vector.push_back(phy_scan_parameters);
uint8_t phys_in_use = 1;
- // The Host shall not issue set scan parameter command when scanning is enabled
- stop_scan();
-
- if (le_address_manager_->GetAddressPolicy() != LeAddressManager::USE_PUBLIC_ADDRESS) {
- own_address_type_ = OwnAddressType::RANDOM_DEVICE_ADDRESS;
- }
-
switch (api_type_) {
- case ScanApiType::EXTENDED:
+ case ScanApiType::LE_5_0:
le_scanning_interface_->EnqueueCommand(hci::LeSetExtendedScanParametersBuilder::Create(
own_address_type_, filter_policy_, phys_in_use, parameter_vector),
- module_handler_->BindOnce(impl::check_status));
+ common::BindOnce(impl::check_status), module_handler_);
break;
case ScanApiType::ANDROID_HCI:
le_scanning_interface_->EnqueueCommand(
hci::LeExtendedScanParamsBuilder::Create(LeScanType::ACTIVE, interval_ms_, window_ms_, own_address_type_,
filter_policy_),
- module_handler_->BindOnce(impl::check_status));
+ common::BindOnce(impl::check_status), module_handler_);
break;
- case ScanApiType::LEGACY:
+ case ScanApiType::LE_4_0:
le_scanning_interface_->EnqueueCommand(
hci::LeSetScanParametersBuilder::Create(LeScanType::ACTIVE, interval_ms_, window_ms_, own_address_type_,
filter_policy_),
- module_handler_->BindOnce(impl::check_status));
+ common::BindOnce(impl::check_status), module_handler_);
break;
}
}
- void register_scanner(const Uuid app_uuid) {
- for (uint8_t i = 1; i <= kMaxAppNum; i++) {
- if (scanners_[i].in_use && scanners_[i].app_uuid == app_uuid) {
- LOG_ERROR("Application already registered %s", app_uuid.ToString().c_str());
- scanning_callbacks_->OnScannerRegistered(app_uuid, 0x00, ScanningCallback::ScanningStatus::INTERNAL_ERROR);
- return;
- }
- }
-
- // valid value of scanner id : 1 ~ kMaxAppNum
- for (uint8_t i = 1; i <= kMaxAppNum; i++) {
- if (!scanners_[i].in_use) {
- scanners_[i].app_uuid = app_uuid;
- scanners_[i].in_use = true;
- scanning_callbacks_->OnScannerRegistered(app_uuid, i, ScanningCallback::ScanningStatus::SUCCESS);
- return;
- }
- }
-
- LOG_ERROR("Unable to register scanner, max client reached:%d", kMaxAppNum);
- scanning_callbacks_->OnScannerRegistered(app_uuid, 0x00, ScanningCallback::ScanningStatus::NO_RESOURCES);
- }
-
- void unregister_scanner(ScannerId scanner_id) {
- if (scanner_id <= 0 || scanner_id > kMaxAppNum) {
- LOG_WARN("Invalid scanner id");
- return;
- }
-
- if (scanners_[scanner_id].in_use) {
- scanners_[scanner_id].in_use = false;
- scanners_[scanner_id].app_uuid = Uuid::kEmpty;
- } else {
- LOG_WARN("Unregister scanner with unused scanner id");
- }
- }
-
- void scan(bool start) {
- if (start) {
- configure_scan();
- start_scan();
- } else {
- if (address_manager_registered_) {
- le_address_manager_->Unregister(this);
- address_manager_registered_ = false;
- }
- stop_scan();
- }
- }
-
- void start_scan() {
- // If we receive start_scan during paused, set scan_on_resume_ to true
- if (paused_) {
- scan_on_resume_ = true;
- return;
- }
- is_scanning_ = true;
- if (!address_manager_registered_) {
- le_address_manager_->Register(this);
- address_manager_registered_ = true;
- }
-
+ void start_scan(LeScanningManagerCallbacks* le_scanning_manager_callbacks) {
+ registered_callback_ = le_scanning_manager_callbacks;
switch (api_type_) {
- case ScanApiType::EXTENDED:
+ case ScanApiType::LE_5_0:
le_scanning_interface_->EnqueueCommand(
- hci::LeSetExtendedScanEnableBuilder::Create(
- Enable::ENABLED, FilterDuplicates::DISABLED /* filter duplicates */, 0, 0),
- module_handler_->BindOnce(impl::check_status));
+ hci::LeSetExtendedScanEnableBuilder::Create(Enable::ENABLED,
+ FilterDuplicates::DISABLED /* filter duplicates */, 0, 0),
+ common::BindOnce(impl::check_status), module_handler_);
break;
case ScanApiType::ANDROID_HCI:
- case ScanApiType::LEGACY:
+ case ScanApiType::LE_4_0:
le_scanning_interface_->EnqueueCommand(
hci::LeSetScanEnableBuilder::Create(Enable::ENABLED, Enable::DISABLED /* filter duplicates */),
- module_handler_->BindOnce(impl::check_status));
+ common::BindOnce(impl::check_status), module_handler_);
break;
}
}
- void stop_scan() {
- is_scanning_ = false;
-
+ void stop_scan(common::Callback<void()> on_stopped) {
+ if (registered_callback_ == nullptr) {
+ return;
+ }
+ registered_callback_->Handler()->Post(std::move(on_stopped));
switch (api_type_) {
- case ScanApiType::EXTENDED:
+ case ScanApiType::LE_5_0:
le_scanning_interface_->EnqueueCommand(
- hci::LeSetExtendedScanEnableBuilder::Create(
- Enable::DISABLED, FilterDuplicates::DISABLED /* filter duplicates */, 0, 0),
- module_handler_->BindOnce(impl::check_status));
+ hci::LeSetExtendedScanEnableBuilder::Create(Enable::DISABLED,
+ FilterDuplicates::DISABLED /* filter duplicates */, 0, 0),
+ common::BindOnce(impl::check_status), module_handler_);
+ registered_callback_ = nullptr;
break;
case ScanApiType::ANDROID_HCI:
- case ScanApiType::LEGACY:
+ case ScanApiType::LE_4_0:
le_scanning_interface_->EnqueueCommand(
hci::LeSetScanEnableBuilder::Create(Enable::DISABLED, Enable::DISABLED /* filter duplicates */),
- module_handler_->BindOnce(impl::check_status));
- break;
- }
- }
-
- void set_scan_parameters(LeScanType scan_type, uint16_t scan_interval, uint16_t scan_window) {
- uint32_t max_scan_interval = kLeScanIntervalMax;
- uint32_t max_scan_window = kLeScanWindowMax;
- if (api_type_ == ScanApiType::EXTENDED) {
- max_scan_interval = kLeExtendedScanIntervalMax;
- max_scan_window = kLeExtendedScanWindowMax;
- }
-
- if (scan_type != LeScanType::ACTIVE && scan_type != LeScanType::PASSIVE) {
- LOG_ERROR("Invalid scan type");
- return;
- }
- if (scan_interval > max_scan_interval || scan_interval < kLeScanIntervalMin) {
- LOG_ERROR("Invalid scan_interval %d", scan_interval);
- return;
- }
- if (scan_window > max_scan_window || scan_window < kLeScanWindowMin) {
- LOG_ERROR("Invalid scan_window %d", scan_window);
- return;
- }
- le_scan_type_ = scan_type;
- interval_ms_ = scan_interval;
- window_ms_ = scan_window;
- }
-
- void scan_filter_enable(bool enable) {
- if (!is_filter_support_) {
- LOG_WARN("Advertising filter is not supported");
- return;
- }
-
- Enable apcf_enable = enable ? Enable::ENABLED : Enable::DISABLED;
- le_scanning_interface_->EnqueueCommand(
- LeAdvFilterEnableBuilder::Create(apcf_enable),
- module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
- }
-
- void scan_filter_parameter_setup(
- ApcfAction action, uint8_t filter_index, AdvertisingFilterParameter advertising_filter_parameter) {
- if (!is_filter_support_) {
- LOG_WARN("Advertising filter is not supported");
- return;
- }
-
- switch (action) {
- case ApcfAction::ADD:
- le_scanning_interface_->EnqueueCommand(
- LeAdvFilterAddFilteringParametersBuilder::Create(
- filter_index,
- advertising_filter_parameter.feature_selection,
- advertising_filter_parameter.list_logic_type,
- advertising_filter_parameter.filter_logic_type,
- advertising_filter_parameter.rssi_high_thresh,
- advertising_filter_parameter.delivery_mode,
- advertising_filter_parameter.onfound_timeout,
- advertising_filter_parameter.onfound_timeout_cnt,
- advertising_filter_parameter.rssi_low_thres,
- advertising_filter_parameter.onlost_timeout,
- advertising_filter_parameter.num_of_tracking_entries),
- module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
- break;
- case ApcfAction::DELETE:
- le_scanning_interface_->EnqueueCommand(
- LeAdvFilterDeleteFilteringParametersBuilder::Create(filter_index),
- module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
+ common::BindOnce(impl::check_status), module_handler_);
+ registered_callback_ = nullptr;
break;
- case ApcfAction::CLEAR:
- le_scanning_interface_->EnqueueCommand(
- LeAdvFilterClearFilteringParametersBuilder::Create(),
- module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
- break;
- default:
- LOG_ERROR("Unknown action type: %d", (uint16_t)action);
- break;
- }
- }
-
- void scan_filter_add(uint8_t filter_index, std::vector<AdvertisingPacketContentFilterCommand> filters) {
- if (!is_filter_support_) {
- LOG_WARN("Advertising filter is not supported");
- return;
- }
-
- ApcfAction apcf_action = ApcfAction::ADD;
- for (auto filter : filters) {
- /* If data is passed, both mask and data have to be the same length */
- if (filter.data.size() != filter.data_mask.size() && filter.data.size() != 0 && filter.data_mask.size() != 0) {
- LOG_ERROR("data and data_mask are of different size");
- continue;
- }
-
- switch (filter.filter_type) {
- case ApcfFilterType::BROADCASTER_ADDRESS: {
- update_address_filter(apcf_action, filter_index, filter.address, filter.application_address_type);
- break;
- }
- case ApcfFilterType::SERVICE_UUID:
- case ApcfFilterType::SERVICE_SOLICITATION_UUID: {
- update_uuid_filter(apcf_action, filter_index, filter.filter_type, filter.uuid, filter.uuid_mask);
- break;
- }
- case ApcfFilterType::LOCAL_NAME: {
- update_local_name_filter(apcf_action, filter_index, filter.name);
- break;
- }
- case ApcfFilterType::MANUFACTURER_DATA: {
- update_manufacturer_data_filter(
- apcf_action, filter_index, filter.company, filter.company_mask, filter.data, filter.data_mask);
- break;
- }
- case ApcfFilterType::SERVICE_DATA: {
- update_service_data_filter(apcf_action, filter_index, filter.data, filter.data_mask);
- break;
- }
- default:
- LOG_ERROR("Unknown filter type: %d", (uint16_t)filter.filter_type);
- break;
- }
- }
- }
-
- void update_address_filter(
- ApcfAction action, uint8_t filter_index, Address address, ApcfApplicationAddressType address_type) {
- if (action != ApcfAction::CLEAR) {
- le_scanning_interface_->EnqueueCommand(
- LeAdvFilterBroadcasterAddressBuilder::Create(action, filter_index, address, address_type),
- module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
- } else {
- le_scanning_interface_->EnqueueCommand(
- LeAdvFilterClearBroadcasterAddressBuilder::Create(filter_index),
- module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
- }
- }
-
- void update_uuid_filter(
- ApcfAction action, uint8_t filter_index, ApcfFilterType filter_type, Uuid uuid, Uuid uuid_mask) {
- std::vector<uint8_t> combined_data = {};
- if (action != ApcfAction::CLEAR) {
- uint8_t uuid_len = uuid.GetShortestRepresentationSize();
- if (uuid_len == Uuid::kNumBytes16) {
- uint16_t data = uuid.As16Bit();
- combined_data.push_back((uint8_t)data);
- combined_data.push_back((uint8_t)(data >> 8));
- } else if (uuid_len == Uuid::kNumBytes32) {
- uint16_t data = uuid.As32Bit();
- combined_data.push_back((uint8_t)data);
- combined_data.push_back((uint8_t)(data >> 8));
- combined_data.push_back((uint8_t)(data >> 16));
- combined_data.push_back((uint8_t)(data >> 24));
- } else if (uuid_len == Uuid::kNumBytes128) {
- auto data = uuid.To128BitLE();
- combined_data.insert(combined_data.end(), data.begin(), data.end());
- } else {
- LOG_ERROR("illegal UUID length: %d", (uint16_t)uuid_len);
- return;
- }
-
- if (!uuid_mask.IsEmpty()) {
- if (uuid_len == Uuid::kNumBytes16) {
- uint16_t data = uuid_mask.As16Bit();
- combined_data.push_back((uint8_t)data);
- combined_data.push_back((uint8_t)(data >> 8));
- } else if (uuid_len == Uuid::kNumBytes32) {
- uint16_t data = uuid_mask.As32Bit();
- combined_data.push_back((uint8_t)data);
- combined_data.push_back((uint8_t)(data >> 8));
- combined_data.push_back((uint8_t)(data >> 16));
- combined_data.push_back((uint8_t)(data >> 24));
- } else if (uuid_len == Uuid::kNumBytes128) {
- auto data = uuid_mask.To128BitLE();
- combined_data.insert(combined_data.end(), data.begin(), data.end());
- }
- } else {
- std::vector<uint8_t> data(uuid_len, 0xFF);
- combined_data.insert(combined_data.end(), data.begin(), data.end());
- }
- }
-
- if (filter_type == ApcfFilterType::SERVICE_UUID) {
- le_scanning_interface_->EnqueueCommand(
- LeAdvFilterServiceUuidBuilder::Create(action, filter_index, combined_data),
- module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
- } else {
- le_scanning_interface_->EnqueueCommand(
- LeAdvFilterSolicitationUuidBuilder::Create(action, filter_index, combined_data),
- module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
- }
- }
-
- void update_local_name_filter(ApcfAction action, uint8_t filter_index, std::vector<uint8_t> name) {
- le_scanning_interface_->EnqueueCommand(
- LeAdvFilterLocalNameBuilder::Create(action, filter_index, name),
- module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
- }
-
- void update_manufacturer_data_filter(
- ApcfAction action,
- uint8_t filter_index,
- uint16_t company_id,
- uint16_t company_id_mask,
- std::vector<uint8_t> data,
- std::vector<uint8_t> data_mask) {
- if (data.size() != data_mask.size()) {
- LOG_ERROR("manufacturer data mask should have the same length as manufacturer data");
- return;
- }
- std::vector<uint8_t> combined_data = {};
- if (action != ApcfAction::CLEAR) {
- combined_data.push_back((uint8_t)company_id);
- combined_data.push_back((uint8_t)(company_id >> 8));
- if (data.size() != 0) {
- combined_data.insert(combined_data.end(), data.begin(), data.end());
- }
- if (company_id_mask != 0) {
- combined_data.push_back((uint8_t)company_id_mask);
- combined_data.push_back((uint8_t)(company_id_mask >> 8));
- } else {
- combined_data.push_back(0xFF);
- combined_data.push_back(0xFF);
- }
- if (data_mask.size() != 0) {
- combined_data.insert(combined_data.end(), data_mask.begin(), data_mask.end());
- }
- }
-
- le_scanning_interface_->EnqueueCommand(
- LeAdvFilterManufacturerDataBuilder::Create(action, filter_index, combined_data),
- module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
- }
-
- void update_service_data_filter(
- ApcfAction action, uint8_t filter_index, std::vector<uint8_t> data, std::vector<uint8_t> data_mask) {
- if (data.size() != data_mask.size()) {
- LOG_ERROR("service data mask should have the same length as service data");
- return;
- }
- std::vector<uint8_t> combined_data = {};
- if (action != ApcfAction::CLEAR && data.size() != 0) {
- combined_data.insert(combined_data.end(), data.begin(), data.end());
- combined_data.insert(combined_data.end(), data_mask.begin(), data_mask.end());
- }
-
- le_scanning_interface_->EnqueueCommand(
- LeAdvFilterServiceDataBuilder::Create(action, filter_index, combined_data),
- module_handler_->BindOnceOn(this, &impl::on_advertising_filter_complete));
- }
-
- void batch_scan_set_storage_parameter(
- uint8_t batch_scan_full_max,
- uint8_t batch_scan_truncated_max,
- uint8_t batch_scan_notify_threshold,
- ScannerId scanner_id) {
- if (!is_batch_scan_support_) {
- LOG_WARN("Batch scan is not supported");
- return;
- }
- // scanner id for OnBatchScanThresholdCrossed
- batch_scan_config_.ref_value = scanner_id;
-
- if (batch_scan_config_.current_state == BatchScanState::ERROR_STATE ||
- batch_scan_config_.current_state == BatchScanState::DISABLED_STATE ||
- batch_scan_config_.current_state == BatchScanState::DISABLE_CALLED) {
- batch_scan_config_.current_state = BatchScanState::ENABLE_CALLED;
- le_scanning_interface_->EnqueueCommand(
- LeBatchScanEnableBuilder::Create(Enable::ENABLED),
- module_handler_->BindOnceOn(this, &impl::on_batch_scan_enable_complete));
- }
-
- le_scanning_interface_->EnqueueCommand(
- LeBatchScanSetStorageParametersBuilder::Create(
- batch_scan_full_max, batch_scan_truncated_max, batch_scan_notify_threshold),
- module_handler_->BindOnceOn(this, &impl::on_batch_scan_complete));
- }
-
- void batch_scan_enable(
- BatchScanMode scan_mode,
- uint32_t duty_cycle_scan_window_slots,
- uint32_t duty_cycle_scan_interval_slots,
- BatchScanDiscardRule batch_scan_discard_rule) {
- if (!is_batch_scan_support_) {
- LOG_WARN("Batch scan is not supported");
- return;
- }
-
- if (batch_scan_config_.current_state == BatchScanState::ERROR_STATE ||
- batch_scan_config_.current_state == BatchScanState::DISABLED_STATE ||
- batch_scan_config_.current_state == BatchScanState::DISABLE_CALLED) {
- batch_scan_config_.current_state = BatchScanState::ENABLE_CALLED;
- le_scanning_interface_->EnqueueCommand(
- LeBatchScanEnableBuilder::Create(Enable::ENABLED),
- module_handler_->BindOnceOn(this, &impl::on_batch_scan_enable_complete));
- }
-
- batch_scan_config_.scan_mode = scan_mode;
- batch_scan_config_.scan_interval = duty_cycle_scan_interval_slots;
- batch_scan_config_.scan_window = duty_cycle_scan_window_slots;
- batch_scan_config_.discard_rule = batch_scan_discard_rule;
- /* This command starts batch scanning, if enabled */
- batch_scan_set_scan_parameter(
- scan_mode, duty_cycle_scan_window_slots, duty_cycle_scan_interval_slots, batch_scan_discard_rule);
- }
-
- void batch_scan_disable() {
- if (!is_batch_scan_support_) {
- LOG_WARN("Batch scan is not supported");
- return;
- }
- batch_scan_config_.current_state = BatchScanState::DISABLE_CALLED;
- batch_scan_set_scan_parameter(
- BatchScanMode::DISABLE,
- batch_scan_config_.scan_window,
- batch_scan_config_.scan_interval,
- batch_scan_config_.discard_rule);
- }
-
- void batch_scan_set_scan_parameter(
- BatchScanMode scan_mode,
- uint32_t duty_cycle_scan_window_slots,
- uint32_t duty_cycle_scan_interval_slots,
- BatchScanDiscardRule batch_scan_discard_rule) {
- if (!is_batch_scan_support_) {
- LOG_WARN("Batch scan is not supported");
- return;
- }
- AdvertisingAddressType own_address_type = AdvertisingAddressType::PUBLIC_ADDRESS;
- if (own_address_type_ == OwnAddressType::RANDOM_DEVICE_ADDRESS ||
- own_address_type_ == OwnAddressType::RESOLVABLE_OR_RANDOM_ADDRESS) {
- own_address_type = AdvertisingAddressType::RANDOM_ADDRESS;
- }
- uint8_t truncated_mode_enabled = 0x00;
- uint8_t full_mode_enabled = 0x00;
- if (scan_mode == BatchScanMode::TRUNCATED || scan_mode == BatchScanMode::TRUNCATED_AND_FULL) {
- truncated_mode_enabled = 0x01;
- }
- if (scan_mode == BatchScanMode::FULL || scan_mode == BatchScanMode::TRUNCATED_AND_FULL) {
- full_mode_enabled = 0x01;
- }
-
- if (scan_mode == BatchScanMode::DISABLE) {
- le_scanning_interface_->EnqueueCommand(
- LeBatchScanSetScanParametersBuilder::Create(
- truncated_mode_enabled,
- full_mode_enabled,
- duty_cycle_scan_window_slots,
- duty_cycle_scan_interval_slots,
- own_address_type,
- batch_scan_discard_rule),
- module_handler_->BindOnceOn(this, &impl::on_batch_scan_disable_complete));
- } else {
- le_scanning_interface_->EnqueueCommand(
- LeBatchScanSetScanParametersBuilder::Create(
- truncated_mode_enabled,
- full_mode_enabled,
- duty_cycle_scan_window_slots,
- duty_cycle_scan_interval_slots,
- own_address_type,
- batch_scan_discard_rule),
- module_handler_->BindOnceOn(this, &impl::on_batch_scan_complete));
- }
- }
-
- void batch_scan_read_results(ScannerId scanner_id, uint16_t total_num_of_records, BatchScanMode scan_mode) {
- if (!is_batch_scan_support_) {
- LOG_WARN("Batch scan is not supported");
- int status = static_cast<int>(ErrorCode::UNSUPORTED_FEATURE_OR_PARAMETER_VALUE);
- scanning_callbacks_->OnBatchScanReports(scanner_id, status, 0, 0, {});
- return;
- }
-
- if (scan_mode != BatchScanMode::FULL && scan_mode != BatchScanMode::TRUNCATED) {
- LOG_WARN("Invalid scan mode %d", (uint16_t)scan_mode);
- int status = static_cast<int>(ErrorCode::INVALID_HCI_COMMAND_PARAMETERS);
- scanning_callbacks_->OnBatchScanReports(scanner_id, status, 0, 0, {});
- return;
- }
-
- if (batch_scan_result_cache_.find(scanner_id) == batch_scan_result_cache_.end()) {
- std::vector<uint8_t> empty_data = {};
- batch_scan_result_cache_.emplace(scanner_id, empty_data);
- }
-
- le_scanning_interface_->EnqueueCommand(
- LeBatchScanReadResultParametersBuilder::Create(static_cast<BatchScanDataRead>(scan_mode)),
- module_handler_->BindOnceOn(this, &impl::on_batch_scan_read_result_complete, scanner_id, total_num_of_records));
- }
-
- void track_advertiser(ScannerId scanner_id) {
- if (!is_batch_scan_support_) {
- LOG_WARN("Batch scan is not supported");
- AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info = {};
- on_found_on_lost_info.scanner_id = scanner_id;
- on_found_on_lost_info.advertiser_info_present = AdvtInfoPresent::NO_ADVT_INFO_PRESENT;
- scanning_callbacks_->OnTrackAdvFoundLost(on_found_on_lost_info);
- return;
- }
- tracker_id = scanner_id;
- }
-
- void register_scanning_callback(ScanningCallback* scanning_callbacks) {
- scanning_callbacks_ = scanning_callbacks;
- }
-
- void on_advertising_filter_complete(CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto status_view = LeAdvFilterCompleteView::Create(view);
- ASSERT(status_view.IsValid());
- if (status_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO(
- "Got a Command complete %s, status %s",
- OpCodeText(view.GetCommandOpCode()).c_str(),
- ErrorCodeText(status_view.GetStatus()).c_str());
- }
-
- ApcfOpcode apcf_opcode = status_view.GetApcfOpcode();
- switch (apcf_opcode) {
- case ApcfOpcode::ENABLE: {
- auto complete_view = LeAdvFilterEnableCompleteView::Create(status_view);
- ASSERT(complete_view.IsValid());
- scanning_callbacks_->OnFilterEnable(complete_view.GetApcfEnable(), (uint8_t)complete_view.GetStatus());
- } break;
- case ApcfOpcode::SET_FILTERING_PARAMETERS: {
- auto complete_view = LeAdvFilterSetFilteringParametersCompleteView::Create(status_view);
- ASSERT(complete_view.IsValid());
- scanning_callbacks_->OnFilterParamSetup(
- complete_view.GetApcfAvailableSpaces(), complete_view.GetApcfAction(), (uint8_t)complete_view.GetStatus());
- } break;
- case ApcfOpcode::BROADCASTER_ADDRESS: {
- auto complete_view = LeAdvFilterBroadcasterAddressCompleteView::Create(status_view);
- ASSERT(complete_view.IsValid());
- scanning_callbacks_->OnFilterConfigCallback(
- ApcfFilterType::BROADCASTER_ADDRESS,
- complete_view.GetApcfAvailableSpaces(),
- complete_view.GetApcfAction(),
- (uint8_t)complete_view.GetStatus());
- } break;
- case ApcfOpcode::SERVICE_UUID: {
- auto complete_view = LeAdvFilterServiceUuidCompleteView::Create(status_view);
- ASSERT(complete_view.IsValid());
- scanning_callbacks_->OnFilterConfigCallback(
- ApcfFilterType::SERVICE_UUID,
- complete_view.GetApcfAvailableSpaces(),
- complete_view.GetApcfAction(),
- (uint8_t)complete_view.GetStatus());
- } break;
- case ApcfOpcode::SERVICE_SOLICITATION_UUID: {
- auto complete_view = LeAdvFilterSolicitationUuidCompleteView::Create(status_view);
- ASSERT(complete_view.IsValid());
- scanning_callbacks_->OnFilterConfigCallback(
- ApcfFilterType::SERVICE_SOLICITATION_UUID,
- complete_view.GetApcfAvailableSpaces(),
- complete_view.GetApcfAction(),
- (uint8_t)complete_view.GetStatus());
- } break;
- case ApcfOpcode::LOCAL_NAME: {
- auto complete_view = LeAdvFilterLocalNameCompleteView::Create(status_view);
- ASSERT(complete_view.IsValid());
- scanning_callbacks_->OnFilterConfigCallback(
- ApcfFilterType::LOCAL_NAME,
- complete_view.GetApcfAvailableSpaces(),
- complete_view.GetApcfAction(),
- (uint8_t)complete_view.GetStatus());
- } break;
- case ApcfOpcode::MANUFACTURER_DATA: {
- auto complete_view = LeAdvFilterManufacturerDataCompleteView::Create(status_view);
- ASSERT(complete_view.IsValid());
- scanning_callbacks_->OnFilterConfigCallback(
- ApcfFilterType::MANUFACTURER_DATA,
- complete_view.GetApcfAvailableSpaces(),
- complete_view.GetApcfAction(),
- (uint8_t)complete_view.GetStatus());
- } break;
- case ApcfOpcode::SERVICE_DATA: {
- auto complete_view = LeAdvFilterServiceDataCompleteView::Create(status_view);
- ASSERT(complete_view.IsValid());
- scanning_callbacks_->OnFilterConfigCallback(
- ApcfFilterType::SERVICE_DATA,
- complete_view.GetApcfAvailableSpaces(),
- complete_view.GetApcfAction(),
- (uint8_t)complete_view.GetStatus());
- } break;
- default:
- LOG_WARN("Unexpected event type %s", OpCodeText(view.GetCommandOpCode()).c_str());
- }
- }
-
- void on_batch_scan_complete(CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto status_view = LeBatchScanCompleteView::Create(view);
- ASSERT(status_view.IsValid());
- if (status_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO(
- "Got a Command complete %s, status %s, batch_scan_opcode %s",
- OpCodeText(view.GetCommandOpCode()).c_str(),
- ErrorCodeText(status_view.GetStatus()).c_str(),
- BatchScanOpcodeText(status_view.GetBatchScanOpcode()).c_str());
- }
- }
-
- void on_batch_scan_enable_complete(CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto status_view = LeBatchScanCompleteView::Create(view);
- ASSERT(status_view.IsValid());
- auto complete_view = LeBatchScanEnableCompleteView::Create(status_view);
- ASSERT(complete_view.IsValid());
- if (status_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO("Got batch scan enable complete, status %s", ErrorCodeText(status_view.GetStatus()).c_str());
- batch_scan_config_.current_state = BatchScanState::ERROR_STATE;
- } else {
- batch_scan_config_.current_state = BatchScanState::ENABLED_STATE;
- }
- }
-
- void on_batch_scan_disable_complete(CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto status_view = LeBatchScanCompleteView::Create(view);
- ASSERT(status_view.IsValid());
- auto complete_view = LeBatchScanSetScanParametersCompleteView::Create(status_view);
- ASSERT(complete_view.IsValid());
- ASSERT(status_view.GetStatus() == ErrorCode::SUCCESS);
- batch_scan_config_.current_state = BatchScanState::DISABLED_STATE;
- }
-
- void on_batch_scan_read_result_complete(
- ScannerId scanner_id, uint16_t total_num_of_records, CommandCompleteView view) {
- ASSERT(view.IsValid());
- auto status_view = LeBatchScanCompleteView::Create(view);
- ASSERT(status_view.IsValid());
- auto complete_view = LeBatchScanReadResultParametersCompleteRawView::Create(status_view);
- ASSERT(complete_view.IsValid());
- if (complete_view.GetStatus() != ErrorCode::SUCCESS) {
- LOG_INFO("Got batch scan read result complete, status %s", ErrorCodeText(status_view.GetStatus()).c_str());
- }
- uint8_t num_of_records = complete_view.GetNumOfRecords();
- auto report_format = complete_view.GetBatchScanDataRead();
- if (num_of_records == 0) {
- scanning_callbacks_->OnBatchScanReports(
- scanner_id, 0x00, (int)report_format, total_num_of_records, batch_scan_result_cache_[scanner_id]);
- batch_scan_result_cache_.erase(scanner_id);
- } else {
- auto raw_data = complete_view.GetRawData();
- batch_scan_result_cache_[scanner_id].insert(
- batch_scan_result_cache_[scanner_id].end(), raw_data.begin(), raw_data.end());
- total_num_of_records += num_of_records;
- batch_scan_read_results(scanner_id, total_num_of_records, static_cast<BatchScanMode>(report_format));
}
}
- void on_storage_threshold_breach(VendorSpecificEventView event) {
- if (batch_scan_config_.ref_value == kInvalidScannerId) {
- LOG_WARN("storage threshold was not set !!");
- return;
- }
- scanning_callbacks_->OnBatchScanThresholdCrossed(static_cast<int>(batch_scan_config_.ref_value));
- }
-
- void on_advertisement_tracking(VendorSpecificEventView event) {
- if (tracker_id == kInvalidScannerId) {
- LOG_WARN("Advertisement track is not register");
- return;
- }
- auto view = LEAdvertisementTrackingEventView::Create(event);
- ASSERT(view.IsValid());
- AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info = {};
- on_found_on_lost_info.scanner_id = tracker_id;
- on_found_on_lost_info.filter_index = view.GetApcfFilterIndex();
- on_found_on_lost_info.advertiser_state = view.GetAdvertiserState();
- on_found_on_lost_info.advertiser_address = view.GetAdvertiserAddress();
- on_found_on_lost_info.advertiser_address_type = view.GetAdvertiserAddressType();
- on_found_on_lost_info.advertiser_info_present = view.GetAdvtInfoPresent();
- /* Extract the adv info details */
- if (on_found_on_lost_info.advertiser_info_present == AdvtInfoPresent::ADVT_INFO_PRESENT) {
- auto info_view = LEAdvertisementTrackingWithInfoEventView::Create(view);
- ASSERT(info_view.IsValid());
- on_found_on_lost_info.tx_power = info_view.GetTxPower();
- on_found_on_lost_info.rssi = info_view.GetRssi();
- on_found_on_lost_info.time_stamp = info_view.GetTimestamp();
- auto adv_data = info_view.GetAdvPacket();
- on_found_on_lost_info.adv_packet.reserve(adv_data.size());
- on_found_on_lost_info.adv_packet.insert(on_found_on_lost_info.adv_packet.end(), adv_data.begin(), adv_data.end());
- auto scan_rsp_data = info_view.GetScanResponse();
- on_found_on_lost_info.scan_response.reserve(scan_rsp_data.size());
- on_found_on_lost_info.scan_response.insert(
- on_found_on_lost_info.scan_response.end(), scan_rsp_data.begin(), scan_rsp_data.end());
- }
- scanning_callbacks_->OnTrackAdvFoundLost(on_found_on_lost_info);
- }
-
- void OnPause() override {
- paused_ = true;
- scan_on_resume_ = is_scanning_;
- stop_scan();
- ack_pause();
- }
-
- void ack_pause() {
- le_address_manager_->AckPause(this);
- }
-
- void OnResume() override {
- paused_ = false;
- if (scan_on_resume_ == true) {
- start_scan();
- }
- le_address_manager_->AckResume(this);
- }
-
ScanApiType api_type_;
+ LeScanningManagerCallbacks* registered_callback_;
Module* module_;
os::Handler* module_handler_;
hci::HciLayer* hci_layer_;
hci::Controller* controller_;
- hci::VendorSpecificEventManager* vendor_specific_event_manager_;
hci::LeScanningInterface* le_scanning_interface_;
- hci::LeAddressManager* le_address_manager_;
- bool address_manager_registered_ = false;
- NullScanningCallback null_scanning_callback_;
- ScanningCallback* scanning_callbacks_ = &null_scanning_callback_;
- std::vector<Scanner> scanners_;
- bool is_scanning_ = false;
- bool scan_on_resume_ = false;
- bool paused_ = false;
- AdvertisingCache advertising_cache_;
- bool is_filter_support_ = false;
- bool is_batch_scan_support_ = false;
- LeScanType le_scan_type_ = LeScanType::ACTIVE;
uint32_t interval_ms_{1000};
uint16_t window_ms_{1000};
- OwnAddressType own_address_type_{OwnAddressType::PUBLIC_DEVICE_ADDRESS};
- LeScanningFilterPolicy filter_policy_{LeScanningFilterPolicy::ACCEPT_ALL};
- BatchScanConfig batch_scan_config_;
- std::map<ScannerId, std::vector<uint8_t>> batch_scan_result_cache_;
- ScannerId tracker_id = kInvalidScannerId;
+ AddressType own_address_type_{AddressType::PUBLIC_DEVICE_ADDRESS};
+ LeSetScanningFilterPolicy filter_policy_{LeSetScanningFilterPolicy::ACCEPT_ALL};
static void check_status(CommandCompleteView view) {
switch (view.GetCommandOpCode()) {
@@ -1277,22 +234,14 @@ LeScanningManager::LeScanningManager() {
void LeScanningManager::ListDependencies(ModuleList* list) {
list->add<hci::HciLayer>();
- list->add<hci::VendorSpecificEventManager>();
list->add<hci::Controller>();
- list->add<hci::AclManager>();
}
void LeScanningManager::Start() {
- pimpl_->start(
- GetHandler(),
- GetDependency<hci::HciLayer>(),
- GetDependency<hci::Controller>(),
- GetDependency<AclManager>(),
- GetDependency<VendorSpecificEventManager>());
+ pimpl_->start(GetHandler(), GetDependency<hci::HciLayer>(), GetDependency<hci::Controller>());
}
void LeScanningManager::Stop() {
- pimpl_->stop();
pimpl_.reset();
}
@@ -1300,78 +249,12 @@ std::string LeScanningManager::ToString() const {
return "Le Scanning Manager";
}
-void LeScanningManager::RegisterScanner(Uuid app_uuid) {
- CallOn(pimpl_.get(), &impl::register_scanner, app_uuid);
-}
-
-void LeScanningManager::Unregister(ScannerId scanner_id) {
- CallOn(pimpl_.get(), &impl::unregister_scanner, scanner_id);
-}
-
-void LeScanningManager::Scan(bool start) {
- CallOn(pimpl_.get(), &impl::scan, start);
-}
-
-void LeScanningManager::SetScanParameters(LeScanType scan_type, uint16_t scan_interval, uint16_t scan_window) {
- CallOn(pimpl_.get(), &impl::set_scan_parameters, scan_type, scan_interval, scan_window);
-}
-
-void LeScanningManager::ScanFilterEnable(bool enable) {
- CallOn(pimpl_.get(), &impl::scan_filter_enable, enable);
-}
-
-void LeScanningManager::ScanFilterParameterSetup(
- ApcfAction action, uint8_t filter_index, AdvertisingFilterParameter advertising_filter_parameter) {
- CallOn(pimpl_.get(), &impl::scan_filter_parameter_setup, action, filter_index, advertising_filter_parameter);
-}
-
-void LeScanningManager::ScanFilterAdd(
- uint8_t filter_index, std::vector<AdvertisingPacketContentFilterCommand> filters) {
- CallOn(pimpl_.get(), &impl::scan_filter_add, filter_index, filters);
-}
-
-void LeScanningManager::BatchScanConifgStorage(
- uint8_t batch_scan_full_max,
- uint8_t batch_scan_truncated_max,
- uint8_t batch_scan_notify_threshold,
- ScannerId scanner_id) {
- CallOn(
- pimpl_.get(),
- &impl::batch_scan_set_storage_parameter,
- batch_scan_full_max,
- batch_scan_truncated_max,
- batch_scan_notify_threshold,
- scanner_id);
-}
-
-void LeScanningManager::BatchScanEnable(
- BatchScanMode scan_mode,
- uint32_t duty_cycle_scan_window_slots,
- uint32_t duty_cycle_scan_interval_slots,
- BatchScanDiscardRule batch_scan_discard_rule) {
- CallOn(
- pimpl_.get(),
- &impl::batch_scan_enable,
- scan_mode,
- duty_cycle_scan_window_slots,
- duty_cycle_scan_interval_slots,
- batch_scan_discard_rule);
-}
-
-void LeScanningManager::BatchScanDisable() {
- CallOn(pimpl_.get(), &impl::batch_scan_disable);
-}
-
-void LeScanningManager::BatchScanReadReport(ScannerId scanner_id, BatchScanMode scan_mode) {
- CallOn(pimpl_.get(), &impl::batch_scan_read_results, scanner_id, 0, scan_mode);
-}
-
-void LeScanningManager::TrackAdvertiser(ScannerId scanner_id) {
- CallOn(pimpl_.get(), &impl::track_advertiser, scanner_id);
+void LeScanningManager::StartScan(LeScanningManagerCallbacks* callbacks) {
+ GetHandler()->Post(common::Bind(&impl::start_scan, common::Unretained(pimpl_.get()), callbacks));
}
-void LeScanningManager::RegisterScanningCallback(ScanningCallback* scanning_callback) {
- CallOn(pimpl_.get(), &impl::register_scanning_callback, scanning_callback);
+void LeScanningManager::StopScan(common::Callback<void()> on_stopped) {
+ GetHandler()->Post(common::Bind(&impl::stop_scan, common::Unretained(pimpl_.get()), on_stopped));
}
} // namespace hci
diff --git a/gd/hci/le_scanning_manager.h b/gd/hci/le_scanning_manager.h
index 491795f9d..2f348d2d1 100644
--- a/gd/hci/le_scanning_manager.h
+++ b/gd/hci/le_scanning_manager.h
@@ -18,141 +18,28 @@
#include <memory>
#include "common/callback.h"
-#include "hci/address_with_type.h"
#include "hci/hci_packets.h"
-#include "hci/uuid.h"
+#include "hci/le_report.h"
#include "module.h"
namespace bluetooth {
namespace hci {
-using ScannerId = uint8_t;
-
-class AdvertisingFilterOnFoundOnLostInfo {
- public:
- uint8_t scanner_id;
- uint8_t filter_index;
- uint8_t advertiser_state;
- AdvtInfoPresent advertiser_info_present;
- Address advertiser_address;
- uint8_t advertiser_address_type;
- uint8_t tx_power;
- int8_t rssi;
- uint16_t time_stamp;
- std::vector<uint8_t> adv_packet;
- std::vector<uint8_t> scan_response;
-};
-
-class ScanningCallback {
- public:
- enum ScanningStatus {
- SUCCESS,
- NO_RESOURCES = 0x80,
- INTERNAL_ERROR = 0x85,
- };
-
- virtual ~ScanningCallback() = default;
- virtual void OnScannerRegistered(
- const bluetooth::hci::Uuid app_uuid, ScannerId scanner_id, ScanningStatus status) = 0;
- virtual void OnScanResult(
- uint16_t event_type,
- uint8_t address_type,
- Address address,
- uint8_t primary_phy,
- uint8_t secondary_phy,
- uint8_t advertising_sid,
- int8_t tx_power,
- int8_t rssi,
- uint16_t periodic_advertising_interval,
- std::vector<uint8_t> advertising_data) = 0;
- virtual void OnTrackAdvFoundLost(AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info) = 0;
- virtual void OnBatchScanReports(
- int client_if, int status, int report_format, int num_records, std::vector<uint8_t> data) = 0;
- virtual void OnBatchScanThresholdCrossed(int client_if) = 0;
- virtual void OnTimeout() = 0;
- virtual void OnFilterEnable(Enable enable, uint8_t status) = 0;
- virtual void OnFilterParamSetup(uint8_t available_spaces, ApcfAction action, uint8_t status) = 0;
- virtual void OnFilterConfigCallback(
- ApcfFilterType filter_type, uint8_t available_spaces, ApcfAction action, uint8_t status) = 0;
-};
-
-class AdvertisingPacketContentFilterCommand {
- public:
- ApcfFilterType filter_type;
- Address address;
- ApcfApplicationAddressType application_address_type;
- Uuid uuid;
- Uuid uuid_mask;
- std::vector<uint8_t> name;
- uint16_t company;
- uint16_t company_mask;
- std::vector<uint8_t> data;
- std::vector<uint8_t> data_mask;
-};
-
-class AdvertisingFilterParameter {
+class LeScanningManagerCallbacks {
public:
- uint16_t feature_selection;
- uint16_t list_logic_type;
- uint8_t filter_logic_type;
- uint8_t rssi_high_thresh;
- DeliveryMode delivery_mode;
- uint16_t onfound_timeout;
- uint8_t onfound_timeout_cnt;
- uint8_t rssi_low_thres;
- uint16_t onlost_timeout;
- uint16_t num_of_tracking_entries;
-};
-
-enum class BatchScanMode : uint8_t {
- DISABLE = 0,
- TRUNCATED = 1,
- FULL = 2,
- TRUNCATED_AND_FULL = 3,
+ virtual ~LeScanningManagerCallbacks() = default;
+ virtual void on_advertisements(std::vector<std::shared_ptr<LeReport>>) = 0;
+ virtual void on_timeout() = 0;
+ virtual os::Handler* Handler() = 0;
};
class LeScanningManager : public bluetooth::Module {
public:
- static constexpr uint8_t kMaxAppNum = 32;
- static constexpr uint8_t kAdvertisingDataInfoNotPresent = 0xff;
- static constexpr uint8_t kTxPowerInformationNotPresent = 0x7f;
- static constexpr uint8_t kNotPeriodicAdvertisement = 0x00;
- static constexpr ScannerId kInvalidScannerId = 0xFF;
LeScanningManager();
- void RegisterScanner(const Uuid app_uuid);
-
- void Unregister(ScannerId scanner_id);
-
- void Scan(bool start);
-
- void SetScanParameters(LeScanType scan_type, uint16_t scan_interval, uint16_t scan_window);
-
- /* Scan filter */
- void ScanFilterEnable(bool enable);
-
- void ScanFilterParameterSetup(
- ApcfAction action, uint8_t filter_index, AdvertisingFilterParameter advertising_filter_parameter);
-
- void ScanFilterAdd(uint8_t filter_index, std::vector<AdvertisingPacketContentFilterCommand> filters);
-
- /*Batch Scan*/
- void BatchScanConifgStorage(
- uint8_t batch_scan_full_max,
- uint8_t batch_scan_truncated_max,
- uint8_t batch_scan_notify_threshold,
- ScannerId scanner_id);
- void BatchScanEnable(
- BatchScanMode scan_mode,
- uint32_t duty_cycle_scan_window_slots,
- uint32_t duty_cycle_scan_interval_slots,
- BatchScanDiscardRule batch_scan_discard_rule);
- void BatchScanDisable();
- void BatchScanReadReport(ScannerId scanner_id, BatchScanMode scan_mode);
-
- void TrackAdvertiser(ScannerId scanner_id);
+ void StartScan(LeScanningManagerCallbacks* callbacks);
- void RegisterScanningCallback(ScanningCallback* scanning_callback);
+ void StopScan(common::Callback<void()> on_stopped);
static const ModuleFactory Factory;
diff --git a/gd/hci/le_scanning_manager_test.cc b/gd/hci/le_scanning_manager_test.cc
index 565a10bfc..fe9815909 100644
--- a/gd/hci/le_scanning_manager_test.cc
+++ b/gd/hci/le_scanning_manager_test.cc
@@ -23,7 +23,6 @@
#include <map>
#include "common/bind.h"
-#include "hci/acl_manager.h"
#include "hci/address.h"
#include "hci/controller.h"
#include "hci/hci_layer.h"
@@ -68,22 +67,27 @@ class TestController : public Controller {
class TestHciLayer : public HciLayer {
public:
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(CommandStatusView)> on_status) override {
+ TestHciLayer() {
+ RegisterEventHandler(EventCode::COMMAND_COMPLETE,
+ base::Bind(&TestHciLayer::CommandCompleteCallback, common::Unretained(this)), nullptr);
+ RegisterEventHandler(EventCode::COMMAND_STATUS,
+ base::Bind(&TestHciLayer::CommandStatusCallback, common::Unretained(this)), nullptr);
+ }
+
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) override {
command_queue_.push(std::move(command));
- command_status_callbacks.push_back(std::move(on_status));
+ command_status_callbacks.push_front(std::move(on_status));
if (command_promise_ != nullptr) {
command_promise_->set_value();
command_promise_.reset();
}
}
- void EnqueueCommand(
- std::unique_ptr<CommandBuilder> command,
- common::ContextualOnceCallback<void(CommandCompleteView)> on_complete) override {
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) override {
command_queue_.push(std::move(command));
- command_complete_callbacks.push_back(std::move(on_complete));
+ command_complete_callbacks.push_front(std::move(on_complete));
if (command_promise_ != nullptr) {
command_promise_->set_value();
command_promise_.reset();
@@ -96,175 +100,100 @@ class TestHciLayer : public HciLayer {
return command_promise_->get_future();
}
- CommandView GetLastCommand() {
- if (command_queue_.empty()) {
- return CommandView::Create(GetPacketView(nullptr));
- } else {
- auto last = std::move(command_queue_.front());
- command_queue_.pop();
- return CommandView::Create(GetPacketView(std::move(last)));
- }
+ std::unique_ptr<CommandPacketBuilder> GetLastCommand() {
+ ASSERT(!command_queue_.empty());
+ auto last = std::move(command_queue_.front());
+ command_queue_.pop();
+ return last;
}
- ConnectionManagementCommandView GetCommand(OpCode op_code) {
- CommandView command_packet_view = GetLastCommand();
- auto command = ConnectionManagementCommandView::Create(AclCommandView::Create(command_packet_view));
- EXPECT_TRUE(command.IsValid());
+ ConnectionManagementCommandView GetCommandPacket(OpCode op_code) {
+ auto packet_view = GetPacketView(GetLastCommand());
+ CommandPacketView command_packet_view = CommandPacketView::Create(packet_view);
+ ConnectionManagementCommandView command = ConnectionManagementCommandView::Create(command_packet_view);
+ ASSERT(command.IsValid());
EXPECT_EQ(command.GetOpCode(), op_code);
+
return command;
}
- void RegisterEventHandler(EventCode event_code, common::ContextualCallback<void(EventView)> event_handler) override {
+ void RegisterEventHandler(EventCode event_code, common::Callback<void(EventPacketView)> event_handler,
+ os::Handler* handler) override {
registered_events_[event_code] = event_handler;
}
- void UnregisterEventHandler(EventCode event_code) override {
- registered_events_.erase(event_code);
- }
-
- void RegisterLeEventHandler(SubeventCode subevent_code,
- common::ContextualCallback<void(LeMetaEventView)> event_handler) override {
+ void RegisterLeEventHandler(SubeventCode subevent_code, common::Callback<void(LeMetaEventView)> event_handler,
+ os::Handler* handler) override {
registered_le_events_[subevent_code] = event_handler;
}
- void UnregisterLeEventHandler(SubeventCode subevent_code) override {
- registered_le_events_.erase(subevent_code);
- }
-
- void IncomingEvent(std::unique_ptr<EventBuilder> event_builder) {
+ void IncomingEvent(std::unique_ptr<EventPacketBuilder> event_builder) {
auto packet = GetPacketView(std::move(event_builder));
- EventView event = EventView::Create(packet);
+ EventPacketView event = EventPacketView::Create(packet);
ASSERT_TRUE(event.IsValid());
EventCode event_code = event.GetEventCode();
- ASSERT_NE(registered_events_.find(event_code), registered_events_.end()) << EventCodeText(event_code);
- registered_events_[event_code].Invoke(event);
+ ASSERT_TRUE(registered_events_.find(event_code) != registered_events_.end()) << EventCodeText(event_code);
+ registered_events_[event_code].Run(event);
}
void IncomingLeMetaEvent(std::unique_ptr<LeMetaEventBuilder> event_builder) {
auto packet = GetPacketView(std::move(event_builder));
- EventView event = EventView::Create(packet);
+ EventPacketView event = EventPacketView::Create(packet);
LeMetaEventView meta_event_view = LeMetaEventView::Create(event);
ASSERT_TRUE(meta_event_view.IsValid());
SubeventCode subevent_code = meta_event_view.GetSubeventCode();
- ASSERT_NE(registered_le_events_.find(subevent_code), registered_le_events_.end())
+ ASSERT_TRUE(registered_le_events_.find(subevent_code) != registered_le_events_.end())
<< SubeventCodeText(subevent_code);
- registered_le_events_[subevent_code].Invoke(meta_event_view);
+ registered_le_events_[subevent_code].Run(meta_event_view);
}
- void CommandCompleteCallback(EventView event) {
+ void CommandCompleteCallback(EventPacketView event) {
CommandCompleteView complete_view = CommandCompleteView::Create(event);
- ASSERT_TRUE(complete_view.IsValid());
- ASSERT_NE(command_complete_callbacks.size(), 0);
- std::move(command_complete_callbacks.front()).Invoke(complete_view);
+ ASSERT(complete_view.IsValid());
+ std::move(command_complete_callbacks.front()).Run(complete_view);
command_complete_callbacks.pop_front();
}
- void CommandStatusCallback(EventView event) {
+ void CommandStatusCallback(EventPacketView event) {
CommandStatusView status_view = CommandStatusView::Create(event);
- ASSERT_TRUE(status_view.IsValid());
- ASSERT_NE(command_status_callbacks.size(), 0);
- std::move(command_status_callbacks.front()).Invoke(status_view);
+ ASSERT(status_view.IsValid());
+ std::move(command_status_callbacks.front()).Run(status_view);
command_status_callbacks.pop_front();
}
void ListDependencies(ModuleList* list) override {}
- void Start() override {
- RegisterEventHandler(EventCode::COMMAND_COMPLETE,
- GetHandler()->BindOn(this, &TestHciLayer::CommandCompleteCallback));
- RegisterEventHandler(EventCode::COMMAND_STATUS, GetHandler()->BindOn(this, &TestHciLayer::CommandStatusCallback));
- }
+ void Start() override {}
void Stop() override {}
private:
- std::map<EventCode, common::ContextualCallback<void(EventView)>> registered_events_;
- std::map<SubeventCode, common::ContextualCallback<void(LeMetaEventView)>> registered_le_events_;
- std::list<common::ContextualOnceCallback<void(CommandCompleteView)>> command_complete_callbacks;
- std::list<common::ContextualOnceCallback<void(CommandStatusView)>> command_status_callbacks;
+ std::map<EventCode, common::Callback<void(EventPacketView)>> registered_events_;
+ std::map<SubeventCode, common::Callback<void(LeMetaEventView)>> registered_le_events_;
+ std::list<base::OnceCallback<void(CommandCompleteView)>> command_complete_callbacks;
+ std::list<base::OnceCallback<void(CommandStatusView)>> command_status_callbacks;
- std::queue<std::unique_ptr<CommandBuilder>> command_queue_;
+ std::queue<std::unique_ptr<CommandPacketBuilder>> command_queue_;
mutable std::mutex mutex_;
std::unique_ptr<std::promise<void>> command_promise_{};
};
-class TestLeAddressManager : public LeAddressManager {
- public:
- TestLeAddressManager(
- common::Callback<void(std::unique_ptr<CommandBuilder>)> enqueue_command,
- os::Handler* handler,
- Address public_address,
- uint8_t connect_list_size,
- uint8_t resolving_list_size)
- : LeAddressManager(enqueue_command, handler, public_address, connect_list_size, resolving_list_size) {}
-
- AddressPolicy Register(LeAddressManagerCallback* callback) override {
- return AddressPolicy::USE_STATIC_ADDRESS;
- }
-
- void Unregister(LeAddressManagerCallback* callback) override {}
-};
-
-class TestAclManager : public AclManager {
- public:
- LeAddressManager* GetLeAddressManager() override {
- return test_le_address_manager_;
- }
-
- protected:
- void Start() override {
- thread_ = new os::Thread("thread", os::Thread::Priority::NORMAL);
- handler_ = new os::Handler(thread_);
- Address address({0x01, 0x02, 0x03, 0x04, 0x05, 0x06});
- test_le_address_manager_ = new TestLeAddressManager(
- common::Bind(&TestAclManager::enqueue_command, common::Unretained(this)), handler_, address, 0x3F, 0x3F);
- }
-
- void Stop() override {
- delete test_le_address_manager_;
- handler_->Clear();
- delete handler_;
- delete thread_;
- }
-
- void ListDependencies(ModuleList* list) override {}
-
- void SetRandomAddress(Address address) {}
-
- void enqueue_command(std::unique_ptr<CommandBuilder> command_packet){};
-
- os::Thread* thread_;
- os::Handler* handler_;
- TestLeAddressManager* test_le_address_manager_;
-};
-
class LeScanningManagerTest : public ::testing::Test {
protected:
void SetUp() override {
test_hci_layer_ = new TestHciLayer; // Ownership is transferred to registry
test_controller_ = new TestController;
test_controller_->AddSupported(param_opcode_);
- if (is_filter_support_) {
- test_controller_->AddSupported(OpCode::LE_ADV_FILTER);
- }
- if (is_batch_scan_support_) {
- test_controller_->AddSupported(OpCode::LE_BATCH_SCAN);
- }
- test_acl_manager_ = new TestAclManager;
fake_registry_.InjectTestModule(&HciLayer::Factory, test_hci_layer_);
fake_registry_.InjectTestModule(&Controller::Factory, test_controller_);
- fake_registry_.InjectTestModule(&AclManager::Factory, test_acl_manager_);
client_handler_ = fake_registry_.GetTestModuleHandler(&HciLayer::Factory);
+ ASSERT_NE(client_handler_, nullptr);
+ mock_callbacks_.handler_ = client_handler_;
std::future<void> config_future = test_hci_layer_->GetCommandFuture();
fake_registry_.Start<LeScanningManager>(&thread_);
le_scanning_manager =
static_cast<LeScanningManager*>(fake_registry_.GetModuleUnderTest(&LeScanningManager::Factory));
auto result = config_future.wait_for(std::chrono::duration(std::chrono::milliseconds(1000)));
ASSERT_EQ(std::future_status::ready, result);
- auto packet = test_hci_layer_->GetCommand(enable_opcode_);
- test_hci_layer_->IncomingEvent(LeSetScanEnableCompleteBuilder::Create(1, ErrorCode::SUCCESS));
- config_future.wait_for(std::chrono::duration(std::chrono::milliseconds(1000)));
- ASSERT_EQ(std::future_status::ready, result);
HandleConfiguration();
- le_scanning_manager->RegisterScanningCallback(&mock_callbacks_);
}
void TearDown() override {
@@ -273,86 +202,39 @@ class LeScanningManagerTest : public ::testing::Test {
}
virtual void HandleConfiguration() {
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_SET_SCAN_PARAMETERS);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::LE_SET_SCAN_PARAMETERS);
test_hci_layer_->IncomingEvent(LeSetScanParametersCompleteBuilder::Create(1, ErrorCode::SUCCESS));
}
- void sync_client_handler() {
- std::promise<void> promise;
- auto future = promise.get_future();
- client_handler_->Call(common::BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)));
- auto future_status = future.wait_for(std::chrono::seconds(1));
- ASSERT_EQ(future_status, std::future_status::ready);
- }
-
TestModuleRegistry fake_registry_;
TestHciLayer* test_hci_layer_ = nullptr;
TestController* test_controller_ = nullptr;
- TestAclManager* test_acl_manager_ = nullptr;
os::Thread& thread_ = fake_registry_.GetTestThread();
LeScanningManager* le_scanning_manager = nullptr;
os::Handler* client_handler_ = nullptr;
- class MockCallbacks : public bluetooth::hci::ScanningCallback {
+ class MockLeScanningManagerCallbacks : public LeScanningManagerCallbacks {
public:
- MOCK_METHOD(
- void,
- OnScannerRegistered,
- (const bluetooth::hci::Uuid app_uuid, ScannerId scanner_id, ScanningStatus status),
- (override));
- MOCK_METHOD(
- void,
- OnScanResult,
- (uint16_t event_type,
- uint8_t address_type,
- Address address,
- uint8_t primary_phy,
- uint8_t secondary_phy,
- uint8_t advertising_sid,
- int8_t tx_power,
- int8_t rssi,
- uint16_t periodic_advertising_interval,
- std::vector<uint8_t> advertising_data),
- (override));
- MOCK_METHOD(
- void,
- OnTrackAdvFoundLost,
- (bluetooth::hci::AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info),
- (override));
- MOCK_METHOD(
- void,
- OnBatchScanReports,
- (int client_if, int status, int report_format, int num_records, std::vector<uint8_t> data),
- (override));
- MOCK_METHOD(void, OnBatchScanThresholdCrossed, (int client_if), (override));
- MOCK_METHOD(void, OnTimeout, (), (override));
- MOCK_METHOD(void, OnFilterEnable, (Enable enable, uint8_t status), (override));
- MOCK_METHOD(void, OnFilterParamSetup, (uint8_t available_spaces, ApcfAction action, uint8_t status), (override));
- MOCK_METHOD(
- void,
- OnFilterConfigCallback,
- (ApcfFilterType filter_type, uint8_t available_spaces, ApcfAction action, uint8_t status),
- (override));
+ MOCK_METHOD(void, on_advertisements, (std::vector<std::shared_ptr<LeReport>>), (override));
+ MOCK_METHOD(void, on_timeout, (), (override));
+ os::Handler* Handler() {
+ return handler_;
+ }
+ os::Handler* handler_{nullptr};
} mock_callbacks_;
OpCode param_opcode_{OpCode::LE_SET_ADVERTISING_PARAMETERS};
- OpCode enable_opcode_{OpCode::LE_SET_SCAN_ENABLE};
- bool is_filter_support_ = false;
- bool is_batch_scan_support_ = false;
};
class LeAndroidHciScanningManagerTest : public LeScanningManagerTest {
protected:
void SetUp() override {
param_opcode_ = OpCode::LE_EXTENDED_SCAN_PARAMS;
- is_filter_support_ = true;
- is_batch_scan_support_ = true;
LeScanningManagerTest::SetUp();
- test_controller_->AddSupported(OpCode::LE_ADV_FILTER);
}
void HandleConfiguration() override {
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_EXTENDED_SCAN_PARAMS);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::LE_EXTENDED_SCAN_PARAMS);
test_hci_layer_->IncomingEvent(LeExtendedScanParamsCompleteBuilder::Create(1, ErrorCode::SUCCESS));
}
};
@@ -361,12 +243,11 @@ class LeExtendedScanningManagerTest : public LeScanningManagerTest {
protected:
void SetUp() override {
param_opcode_ = OpCode::LE_SET_EXTENDED_SCAN_PARAMETERS;
- enable_opcode_ = OpCode::LE_SET_EXTENDED_SCAN_ENABLE;
LeScanningManagerTest::SetUp();
}
void HandleConfiguration() override {
- auto packet = test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_SCAN_PARAMETERS);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::LE_SET_EXTENDED_SCAN_PARAMETERS);
test_hci_layer_->IncomingEvent(LeSetExtendedScanParametersCompleteBuilder::Create(1, ErrorCode::SUCCESS));
}
};
@@ -375,14 +256,14 @@ TEST_F(LeScanningManagerTest, startup_teardown) {}
TEST_F(LeScanningManagerTest, start_scan_test) {
auto next_command_future = test_hci_layer_->GetCommandFuture();
- le_scanning_manager->Scan(true);
+ le_scanning_manager->StartScan(&mock_callbacks_);
auto result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
ASSERT_EQ(std::future_status::ready, result);
test_hci_layer_->IncomingEvent(LeSetScanEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
LeAdvertisingReport report{};
- report.event_type_ = AdvertisingEventType::ADV_DIRECT_IND;
+ report.event_type_ = AdvertisingEventType::ADV_IND;
report.address_type_ = AddressType::PUBLIC_DEVICE_ADDRESS;
Address::FromString("12:34:56:78:9a:bc", report.address_);
std::vector<GapData> gap_data{};
@@ -395,21 +276,21 @@ TEST_F(LeScanningManagerTest, start_scan_test) {
gap_data.push_back(data_item);
report.advertising_data_ = gap_data;
- EXPECT_CALL(mock_callbacks_, OnScanResult);
+ EXPECT_CALL(mock_callbacks_, on_advertisements);
test_hci_layer_->IncomingLeMetaEvent(LeAdvertisingReportBuilder::Create({report}));
}
TEST_F(LeAndroidHciScanningManagerTest, start_scan_test) {
auto next_command_future = test_hci_layer_->GetCommandFuture();
- le_scanning_manager->Scan(true);
+ le_scanning_manager->StartScan(&mock_callbacks_);
auto result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
ASSERT_EQ(std::future_status::ready, result);
test_hci_layer_->IncomingEvent(LeSetScanEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
LeAdvertisingReport report{};
- report.event_type_ = AdvertisingEventType::ADV_DIRECT_IND;
+ report.event_type_ = AdvertisingEventType::ADV_IND;
report.address_type_ = AddressType::PUBLIC_DEVICE_ADDRESS;
Address::FromString("12:34:56:78:9a:bc", report.address_);
std::vector<GapData> gap_data{};
@@ -422,113 +303,24 @@ TEST_F(LeAndroidHciScanningManagerTest, start_scan_test) {
gap_data.push_back(data_item);
report.advertising_data_ = gap_data;
- EXPECT_CALL(mock_callbacks_, OnScanResult);
+ EXPECT_CALL(mock_callbacks_, on_advertisements);
test_hci_layer_->IncomingLeMetaEvent(LeAdvertisingReportBuilder::Create({report}));
}
-TEST_F(LeAndroidHciScanningManagerTest, scan_filter_enable_test) {
- auto next_command_future = test_hci_layer_->GetCommandFuture();
- le_scanning_manager->ScanFilterEnable(true);
- auto result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
- ASSERT_EQ(std::future_status::ready, result);
- EXPECT_CALL(mock_callbacks_, OnFilterEnable);
- test_hci_layer_->IncomingEvent(
- LeAdvFilterEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, Enable::ENABLED));
- sync_client_handler();
-}
-
-TEST_F(LeAndroidHciScanningManagerTest, scan_filter_parameter_test) {
- auto next_command_future = test_hci_layer_->GetCommandFuture();
- AdvertisingFilterParameter advertising_filter_parameter{};
- advertising_filter_parameter.delivery_mode = DeliveryMode::IMMEDIATE;
- le_scanning_manager->ScanFilterParameterSetup(ApcfAction::ADD, 0x01, advertising_filter_parameter);
- auto result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
- ASSERT_EQ(std::future_status::ready, result);
- EXPECT_CALL(mock_callbacks_, OnFilterParamSetup);
- test_hci_layer_->IncomingEvent(
- LeAdvFilterSetFilteringParametersCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, ApcfAction::ADD, 0x0a));
- sync_client_handler();
-}
-
-TEST_F(LeAndroidHciScanningManagerTest, scan_filter_add_test) {
- auto next_command_future = test_hci_layer_->GetCommandFuture();
- std::vector<AdvertisingPacketContentFilterCommand> filters = {};
- AdvertisingPacketContentFilterCommand filter{};
- filter.filter_type = ApcfFilterType::BROADCASTER_ADDRESS;
- filter.address = Address::kEmpty;
- filter.application_address_type = ApcfApplicationAddressType::RANDOM;
- filters.push_back(filter);
- le_scanning_manager->ScanFilterAdd(0x01, filters);
- EXPECT_CALL(mock_callbacks_, OnFilterConfigCallback);
- auto result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
- ASSERT_EQ(std::future_status::ready, result);
- test_hci_layer_->IncomingEvent(
- LeAdvFilterBroadcasterAddressCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS, ApcfAction::ADD, 0x0a));
- sync_client_handler();
-}
-
-TEST_F(LeAndroidHciScanningManagerTest, read_batch_scan_result) {
- // Enable batch scan feature
- auto next_command_future = test_hci_layer_->GetCommandFuture();
- le_scanning_manager->BatchScanConifgStorage(100, 0, 95, 0x00);
- auto result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
- ASSERT_EQ(std::future_status::ready, result);
- test_hci_layer_->IncomingEvent(LeBatchScanEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
- test_hci_layer_->IncomingEvent(
- LeBatchScanSetStorageParametersCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
-
- // Enable batch scan
- next_command_future = test_hci_layer_->GetCommandFuture();
- le_scanning_manager->BatchScanEnable(BatchScanMode::FULL, 2400, 2400, BatchScanDiscardRule::OLDEST);
- result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
- ASSERT_EQ(std::future_status::ready, result);
- test_hci_layer_->IncomingEvent(LeBatchScanSetScanParametersCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
-
- // Read batch scan data
- next_command_future = test_hci_layer_->GetCommandFuture();
- le_scanning_manager->BatchScanReadReport(0x01, BatchScanMode::FULL);
- result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
- ASSERT_EQ(std::future_status::ready, result);
-
- EXPECT_CALL(mock_callbacks_, OnBatchScanReports);
- std::vector<uint8_t> raw_data = {0x5c, 0x1f, 0xa2, 0xc3, 0x63, 0x5d, 0x01, 0xf5, 0xb3, 0x5e, 0x00, 0x0c, 0x02,
- 0x01, 0x02, 0x05, 0x09, 0x6d, 0x76, 0x38, 0x76, 0x02, 0x0a, 0xf5, 0x00};
- next_command_future = test_hci_layer_->GetCommandFuture();
- // We will send read command while num_of_record != 0
- test_hci_layer_->IncomingEvent(LeBatchScanReadResultParametersCompleteRawBuilder::Create(
- uint8_t{1}, ErrorCode::SUCCESS, BatchScanDataRead::FULL_MODE_DATA, 1, raw_data));
- result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
- ASSERT_EQ(std::future_status::ready, result);
-
- // OnBatchScanReports will be trigger when num_of_record == 0
- test_hci_layer_->IncomingEvent(LeBatchScanReadResultParametersCompleteRawBuilder::Create(
- uint8_t{1}, ErrorCode::SUCCESS, BatchScanDataRead::FULL_MODE_DATA, 0, {}));
-}
-
TEST_F(LeExtendedScanningManagerTest, start_scan_test) {
auto next_command_future = test_hci_layer_->GetCommandFuture();
- le_scanning_manager->Scan(true);
+ le_scanning_manager->StartScan(&mock_callbacks_);
auto result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
ASSERT_EQ(std::future_status::ready, result);
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_SCAN_ENABLE);
- test_hci_layer_->IncomingEvent(LeSetScanEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
-
- result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
- ASSERT_EQ(std::future_status::ready, result);
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_SCAN_PARAMETERS);
- test_hci_layer_->IncomingEvent(LeSetExtendedScanParametersCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
-
- result = next_command_future.wait_for(std::chrono::duration(std::chrono::milliseconds(100)));
- ASSERT_EQ(std::future_status::ready, result);
- test_hci_layer_->GetCommand(OpCode::LE_SET_EXTENDED_SCAN_ENABLE);
+ auto packet = test_hci_layer_->GetCommandPacket(OpCode::LE_SET_EXTENDED_SCAN_ENABLE);
test_hci_layer_->IncomingEvent(LeSetScanEnableCompleteBuilder::Create(uint8_t{1}, ErrorCode::SUCCESS));
LeExtendedAdvertisingReport report{};
report.connectable_ = 1;
- report.scannable_ = 0;
+ report.scannable_ = 1;
report.address_type_ = DirectAdvertisingAddressType::PUBLIC_DEVICE_ADDRESS;
Address::FromString("12:34:56:78:9a:bc", report.address_);
std::vector<GapData> gap_data{};
@@ -539,16 +331,9 @@ TEST_F(LeExtendedScanningManagerTest, start_scan_test) {
data_item.data_type_ = GapDataType::COMPLETE_LOCAL_NAME;
data_item.data_ = {'r', 'a', 'n', 'd', 'o', 'm', ' ', 'd', 'e', 'v', 'i', 'c', 'e'};
gap_data.push_back(data_item);
- std::vector<uint8_t> advertising_data = {};
- for (auto data : gap_data) {
- advertising_data.push_back((uint8_t)data.size() - 1);
- advertising_data.push_back((uint8_t)data.data_type_);
- advertising_data.insert(advertising_data.end(), data.data_.begin(), data.data_.end());
- }
-
- report.advertising_data_ = advertising_data;
+ report.advertising_data_ = gap_data;
- EXPECT_CALL(mock_callbacks_, OnScanResult);
+ EXPECT_CALL(mock_callbacks_, on_advertisements);
test_hci_layer_->IncomingLeMetaEvent(LeExtendedAdvertisingReportBuilder::Create({report}));
}
diff --git a/gd/hci/le_security_interface.h b/gd/hci/le_security_interface.h
index da1e62d7b..13c3ef36d 100644
--- a/gd/hci/le_security_interface.h
+++ b/gd/hci/le_security_interface.h
@@ -16,19 +16,31 @@
#pragma once
-#include "hci/command_interface.h"
+#include "common/callback.h"
#include "hci/hci_packets.h"
+#include "os/handler.h"
+#include "os/utils.h"
namespace bluetooth {
namespace hci {
-constexpr hci::SubeventCode LeSecurityEvents[] = {
- hci::SubeventCode::LONG_TERM_KEY_REQUEST,
- hci::SubeventCode::READ_LOCAL_P256_PUBLIC_KEY_COMPLETE,
- hci::SubeventCode::GENERATE_DHKEY_COMPLETE,
-};
+class LeSecurityInterface {
+ public:
+ LeSecurityInterface() = default;
+ virtual ~LeSecurityInterface() = default;
+ DISALLOW_COPY_AND_ASSIGN(LeSecurityInterface);
+
+ virtual void EnqueueCommand(std::unique_ptr<LeSecurityCommandBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) = 0;
-typedef CommandInterface<LeSecurityCommandBuilder> LeSecurityInterface;
+ virtual void EnqueueCommand(std::unique_ptr<LeSecurityCommandBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) = 0;
+ static constexpr hci::SubeventCode LeSecurityEvents[] = {
+ hci::SubeventCode::LONG_TERM_KEY_REQUEST,
+ hci::SubeventCode::READ_LOCAL_P256_PUBLIC_KEY_COMPLETE,
+ hci::SubeventCode::GENERATE_DHKEY_COMPLETE,
+ };
+};
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/link_key.cc b/gd/hci/link_key.cc
deleted file mode 100644
index 98074bbb1..000000000
--- a/gd/hci/link_key.cc
+++ /dev/null
@@ -1,25 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/link_key.h"
-
-namespace bluetooth {
-namespace hci {
-
-const LinkKey kExampleLinkKey{
- {0x4C, 0x68, 0x38, 0x41, 0x39, 0xf5, 0x74, 0xd8, 0x36, 0xbc, 0xf3, 0x4e, 0x9d, 0xfb, 0x01, 0xbf}};
-}
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/hci/link_key.h b/gd/hci/link_key.h
deleted file mode 100644
index ed873e6e7..000000000
--- a/gd/hci/link_key.h
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include "common/byte_array.h"
-
-namespace bluetooth {
-namespace hci {
-
-// convenience type for 128 bit link keys
-using LinkKey = common::ByteArray<16>;
-
-// example link key from Bluetooth spec, do not use in real device
-extern const LinkKey kExampleLinkKey;
-
-} // namespace hci
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/hci/security_interface.h b/gd/hci/security_interface.h
index 5ac30866c..1258122bf 100644
--- a/gd/hci/security_interface.h
+++ b/gd/hci/security_interface.h
@@ -16,33 +16,43 @@
#pragma once
-#include "hci/command_interface.h"
+#include "common/callback.h"
#include "hci/hci_packets.h"
+#include "os/utils.h"
namespace bluetooth {
namespace hci {
-constexpr hci::EventCode SecurityEvents[] = {
- hci::EventCode::ENCRYPTION_CHANGE,
- hci::EventCode::CHANGE_CONNECTION_LINK_KEY_COMPLETE,
- hci::EventCode::CENTRAL_LINK_KEY_COMPLETE,
- hci::EventCode::RETURN_LINK_KEYS,
- hci::EventCode::PIN_CODE_REQUEST,
- hci::EventCode::LINK_KEY_REQUEST,
- hci::EventCode::LINK_KEY_NOTIFICATION,
- hci::EventCode::ENCRYPTION_KEY_REFRESH_COMPLETE,
- hci::EventCode::IO_CAPABILITY_REQUEST,
- hci::EventCode::IO_CAPABILITY_RESPONSE,
- hci::EventCode::REMOTE_OOB_DATA_REQUEST,
- hci::EventCode::SIMPLE_PAIRING_COMPLETE,
- hci::EventCode::USER_PASSKEY_NOTIFICATION,
- hci::EventCode::KEYPRESS_NOTIFICATION,
- hci::EventCode::USER_CONFIRMATION_REQUEST,
- hci::EventCode::USER_PASSKEY_REQUEST,
- hci::EventCode::REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION,
-};
+class SecurityInterface {
+ public:
+ SecurityInterface() = default;
+ virtual ~SecurityInterface() = default;
+ DISALLOW_COPY_AND_ASSIGN(SecurityInterface);
+
+ virtual void EnqueueCommand(std::unique_ptr<SecurityCommandBuilder> command,
+ common::OnceCallback<void(CommandCompleteView)> on_complete, os::Handler* handler) = 0;
-typedef CommandInterface<SecurityCommandBuilder> SecurityInterface;
+ virtual void EnqueueCommand(std::unique_ptr<SecurityCommandBuilder> command,
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) = 0;
+ static constexpr hci::EventCode SecurityEvents[] = {
+ hci::EventCode::CHANGE_CONNECTION_LINK_KEY_COMPLETE,
+ hci::EventCode::MASTER_LINK_KEY_COMPLETE,
+ hci::EventCode::RETURN_LINK_KEYS,
+ hci::EventCode::PIN_CODE_REQUEST,
+ hci::EventCode::LINK_KEY_REQUEST,
+ hci::EventCode::LINK_KEY_NOTIFICATION,
+ hci::EventCode::ENCRYPTION_KEY_REFRESH_COMPLETE,
+ hci::EventCode::IO_CAPABILITY_REQUEST,
+ hci::EventCode::IO_CAPABILITY_RESPONSE,
+ hci::EventCode::REMOTE_OOB_DATA_REQUEST,
+ hci::EventCode::SIMPLE_PAIRING_COMPLETE,
+ hci::EventCode::USER_PASSKEY_NOTIFICATION,
+ hci::EventCode::KEYPRESS_NOTIFICATION,
+ hci::EventCode::USER_CONFIRMATION_REQUEST,
+ hci::EventCode::USER_PASSKEY_REQUEST,
+ hci::EventCode::REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION,
+ };
+};
} // namespace hci
} // namespace bluetooth
diff --git a/gd/hci/uuid.cc b/gd/hci/uuid.cc
deleted file mode 100644
index 551bc2b9e..000000000
--- a/gd/hci/uuid.cc
+++ /dev/null
@@ -1,231 +0,0 @@
-/******************************************************************************
- *
- * Copyright (C) 2017 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#include "hci/uuid.h"
-
-#include <openssl/rand.h>
-
-#include <string.h>
-#include <algorithm>
-
-namespace bluetooth {
-namespace hci {
-
-using UUID128Bit = Uuid::UUID128Bit;
-
-const Uuid Uuid::kEmpty = Uuid::From128BitBE(UUID128Bit{{0x00}});
-
-namespace {
-Uuid kBase = Uuid::From128BitBE(
- UUID128Bit{{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00, 0x80, 0x00, 0x00, 0x80, 0x5f, 0x9b, 0x34, 0xfb}});
-} // namespace
-
-size_t Uuid::GetShortestRepresentationSize() const {
- if (memcmp(uu.data() + kNumBytes32, kBase.uu.data() + kNumBytes32, kNumBytes128 - kNumBytes32) != 0) {
- return kNumBytes128;
- }
-
- if (uu[0] == 0 && uu[1] == 0) {
- return kNumBytes16;
- }
-
- return kNumBytes32;
-}
-
-bool Uuid::Is16Bit() const {
- return GetShortestRepresentationSize() == kNumBytes16;
-}
-
-uint16_t Uuid::As16Bit() const {
- return (((uint16_t)uu[2]) << 8) + uu[3];
-}
-
-uint32_t Uuid::As32Bit() const {
- return (((uint32_t)uu[0]) << 24) + (((uint32_t)uu[1]) << 16) + (((uint32_t)uu[2]) << 8) + uu[3];
-}
-
-std::optional<Uuid> Uuid::FromString(const std::string& uuid) {
- if (uuid.empty()) {
- return std::nullopt;
- }
-
- Uuid ret = kBase;
- uint8_t* p = ret.uu.data();
- if (uuid.size() == kString128BitLen) {
- if (uuid[8] != '-' || uuid[13] != '-' || uuid[18] != '-' || uuid[23] != '-') {
- return std::nullopt;
- }
-
- int c;
- int rc = sscanf(
- uuid.c_str(),
- "%02hhx%02hhx%02hhx%02hhx-%02hhx%02hhx-%02hhx%02hhx"
- "-%02hhx%02hhx-%02hhx%02hhx%02hhx%02hhx%02hhx%02hhx%n",
- &p[0],
- &p[1],
- &p[2],
- &p[3],
- &p[4],
- &p[5],
- &p[6],
- &p[7],
- &p[8],
- &p[9],
- &p[10],
- &p[11],
- &p[12],
- &p[13],
- &p[14],
- &p[15],
- &c);
- if (rc != 16) {
- return std::nullopt;
- }
- if (c != kString128BitLen) {
- return std::nullopt;
- }
-
- } else if (uuid.size() == 8) {
- int c;
- int rc = sscanf(uuid.c_str(), "%02hhx%02hhx%02hhx%02hhx%n", &p[0], &p[1], &p[2], &p[3], &c);
- if (rc != 4) {
- return std::nullopt;
- }
- if (c != 8) {
- return std::nullopt;
- }
-
- } else if (uuid.size() == 4) {
- int c;
- int rc = sscanf(uuid.c_str(), "%02hhx%02hhx%n", &p[2], &p[3], &c);
- if (rc != 2) {
- return std::nullopt;
- }
- if (c != 4) {
- return std::nullopt;
- }
- } else {
- return std::nullopt;
- }
-
- return ret;
-}
-
-std::optional<Uuid> Uuid::FromLegacyConfigString(const std::string& uuid) {
- return FromString(uuid);
-}
-
-Uuid Uuid::From16Bit(uint16_t uuid16) {
- Uuid u = kBase;
-
- u.uu[2] = (uint8_t)((0xFF00 & uuid16) >> 8);
- u.uu[3] = (uint8_t)(0x00FF & uuid16);
- return u;
-}
-
-Uuid Uuid::From32Bit(uint32_t uuid32) {
- Uuid u = kBase;
-
- u.uu[0] = (uint8_t)((0xFF000000 & uuid32) >> 24);
- u.uu[1] = (uint8_t)((0x00FF0000 & uuid32) >> 16);
- u.uu[2] = (uint8_t)((0x0000FF00 & uuid32) >> 8);
- u.uu[3] = (uint8_t)(0x000000FF & uuid32);
- return u;
-}
-
-Uuid Uuid::From128BitBE(const uint8_t* uuid) {
- UUID128Bit tmp;
- memcpy(tmp.data(), uuid, kNumBytes128);
- return From128BitBE(tmp);
-}
-
-Uuid Uuid::From128BitLE(const UUID128Bit& uuid) {
- Uuid u;
- std::reverse_copy(uuid.data(), uuid.data() + kNumBytes128, u.uu.begin());
- return u;
-}
-
-Uuid Uuid::From128BitLE(const uint8_t* uuid) {
- UUID128Bit tmp;
- memcpy(tmp.data(), uuid, kNumBytes128);
- return From128BitLE(tmp);
-}
-
-UUID128Bit Uuid::To128BitLE() const {
- UUID128Bit le;
- std::reverse_copy(uu.data(), uu.data() + kNumBytes128, le.begin());
- return le;
-}
-
-const UUID128Bit& Uuid::To128BitBE() const {
- return uu;
-}
-
-Uuid Uuid::GetRandom() {
- Uuid uuid;
- RAND_bytes(uuid.uu.data(), uuid.uu.size());
- return uuid;
-}
-
-bool Uuid::IsEmpty() const {
- return *this == kEmpty;
-}
-
-bool Uuid::operator<(const Uuid& rhs) const {
- return std::lexicographical_compare(uu.begin(), uu.end(), rhs.uu.begin(), rhs.uu.end());
-}
-
-bool Uuid::operator==(const Uuid& rhs) const {
- return uu == rhs.uu;
-}
-
-bool Uuid::operator!=(const Uuid& rhs) const {
- return uu != rhs.uu;
-}
-
-std::string Uuid::ToString() const {
- char buf[kString128BitLen + 1] = {};
- std::snprintf(
- buf,
- sizeof(buf),
- "%02x%02x%02x%02x-%02x%02x-%02x%02x-%02x%02x-%02x%02x%02x%02x%02x%02x",
- uu[0],
- uu[1],
- uu[2],
- uu[3],
- uu[4],
- uu[5],
- uu[6],
- uu[7],
- uu[8],
- uu[9],
- uu[10],
- uu[11],
- uu[12],
- uu[13],
- uu[14],
- uu[15]);
- return std::string(buf);
-}
-
-std::string Uuid::ToLegacyConfigString() const {
- return ToString();
-}
-
-} // namespace hci
-} // namespace bluetooth
diff --git a/gd/hci/uuid.h b/gd/hci/uuid.h
deleted file mode 100644
index ca8a14255..000000000
--- a/gd/hci/uuid.h
+++ /dev/null
@@ -1,153 +0,0 @@
-/******************************************************************************
- *
- * Copyright (C) 2017 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#pragma once
-
-#include <array>
-#include <cstdint>
-#include <optional>
-#include <string>
-
-#include "storage/serializable.h"
-
-namespace bluetooth {
-
-namespace hci {
-
-// This class is representing Bluetooth UUIDs across whole stack.
-// Here are some general endianness rules:
-// 1. UUID is internally kept as as Big Endian.
-// 2. Bytes representing UUID coming from upper layers, Java or Binder, are Big Endian.
-// 3. Bytes representing UUID coming from lower layer, HCI packets, are Little Endian.
-// 4. UUID in storage is always string.
-class Uuid final : public storage::Serializable<Uuid> {
- public:
- static constexpr size_t kNumBytes128 = 16;
- static constexpr size_t kNumBytes32 = 4;
- static constexpr size_t kNumBytes16 = 2;
-
- static constexpr size_t kString128BitLen = 36;
-
- static const Uuid kEmpty; // 00000000-0000-0000-0000-000000000000
-
- using UUID128Bit = std::array<uint8_t, kNumBytes128>;
-
- Uuid() = default;
-
- inline uint8_t* data() {
- return uu.data();
- }
-
- inline const uint8_t* data() const {
- return uu.data();
- }
-
- // storage::Serializable methods
- // Converts string representing 128, 32, or 16 bit UUID in
- // xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx, xxxxxxxx, or xxxx format to UUID.
- // return uuid on success, std::nullopt otherwise
- static std::optional<Uuid> FromString(const std::string& uuid);
- static std::optional<Uuid> FromLegacyConfigString(const std::string& uuid);
- // Returns string representing this UUID in
- // xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx format, lowercase.
- std::string ToString() const override;
- std::string ToLegacyConfigString() const override;
-
- // Creates and returns a random 128-bit UUID.
- static Uuid GetRandom();
-
- // Returns the shortest possible representation of this UUID in bytes. Either
- // kNumBytes16, kNumBytes32, or kNumBytes128
- size_t GetShortestRepresentationSize() const;
-
- // Returns true if this UUID can be represented as 16 bit.
- bool Is16Bit() const;
-
- // Returns 16 bit Little Endian representation of this UUID. Use
- // GetShortestRepresentationSize() or Is16Bit() before using this method.
- uint16_t As16Bit() const;
-
- // Returns 32 bit Little Endian representation of this UUID. Use
- // GetShortestRepresentationSize() before using this method.
- uint32_t As32Bit() const;
-
- // Converts 16bit Little Endian representation of UUID to UUID
- static Uuid From16Bit(uint16_t uuid16bit);
-
- // Converts 32bit Little Endian representation of UUID to UUID
- static Uuid From32Bit(uint32_t uuid32bit);
-
- // Converts 128 bit Big Endian array representing UUID to UUID.
- static Uuid From128BitBE(const UUID128Bit& uuid) {
- Uuid u(uuid);
- return u;
- }
-
- // Converts 128 bit Big Endian array representing UUID to UUID. |uuid| points
- // to beginning of array.
- static Uuid From128BitBE(const uint8_t* uuid);
-
- // Converts 128 bit Little Endian array representing UUID to UUID.
- static Uuid From128BitLE(const UUID128Bit& uuid);
-
- // Converts 128 bit Little Endian array representing UUID to UUID. |uuid|
- // points to beginning of array.
- static Uuid From128BitLE(const uint8_t* uuid);
-
- // Returns 128 bit Little Endian representation of this UUID
- UUID128Bit To128BitLE() const;
-
- // Returns 128 bit Big Endian representation of this UUID
- const UUID128Bit& To128BitBE() const;
-
- // Returns true if this UUID is equal to kEmpty
- bool IsEmpty() const;
-
- bool operator<(const Uuid& rhs) const;
- bool operator==(const Uuid& rhs) const;
- bool operator!=(const Uuid& rhs) const;
-
- private:
- constexpr Uuid(const UUID128Bit& val) : uu{val} {};
-
- // Network-byte-ordered ID (Big Endian).
- UUID128Bit uu = {};
-};
-} // namespace hci
-
-} // namespace bluetooth
-
-inline std::ostream& operator<<(std::ostream& os, const bluetooth::hci::Uuid& a) {
- os << a.ToString();
- return os;
-}
-
-// Custom std::hash specialization so that bluetooth::UUID can be used as a key
-// in std::unordered_map.
-namespace std {
-
-template <>
-struct hash<bluetooth::hci::Uuid> {
- std::size_t operator()(const bluetooth::hci::Uuid& key) const {
- const auto& uuid_bytes = key.To128BitBE();
- std::hash<std::string> hash_fn;
- return hash_fn(std::string(reinterpret_cast<const char*>(uuid_bytes.data()), uuid_bytes.size()));
- }
-};
-
-} // namespace std
diff --git a/gd/hci/uuid_unittest.cc b/gd/hci/uuid_unittest.cc
deleted file mode 100644
index 929b2d385..000000000
--- a/gd/hci/uuid_unittest.cc
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "hci/uuid.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-namespace testing {
-
-using bluetooth::hci::Uuid;
-
-static const Uuid ONES = Uuid::From128BitBE(
- Uuid::UUID128Bit{{0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11}});
-
-static const Uuid SEQUENTIAL = Uuid::From128BitBE(
- Uuid::UUID128Bit{{0x01, 0x23, 0x45, 0x67, 0x89, 0xab, 0xcd, 0xef, 0xab, 0xcd, 0xef, 0x01, 0x23, 0x45, 0x67, 0x89}});
-
-static const Uuid kBase = Uuid::From128BitBE(
- Uuid::UUID128Bit{{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00, 0x80, 0x00, 0x00, 0x80, 0x5f, 0x9b, 0x34, 0xfb}});
-
-TEST(UuidTest, IsEmpty) {
- ASSERT_TRUE(Uuid::kEmpty.IsEmpty());
- ASSERT_FALSE(kBase.IsEmpty());
-}
-
-TEST(UuidTest, GetShortestRepresentationSize) {
- ASSERT_TRUE(Uuid::kNumBytes16 == kBase.GetShortestRepresentationSize());
- ASSERT_TRUE(Uuid::kNumBytes32 == Uuid::From32Bit(0x01234567).GetShortestRepresentationSize());
- ASSERT_TRUE(Uuid::kNumBytes128 == Uuid::kEmpty.GetShortestRepresentationSize());
-}
-
-TEST(UuidTest, As16Bit) {
- // Even though this is is not 16bit UUID, we should be able to get proper bits
- ASSERT_EQ((uint16_t)0x1111, ONES.As16Bit());
- ASSERT_EQ((uint16_t)0x4567, SEQUENTIAL.As16Bit());
- ASSERT_EQ((uint16_t)0x0000, kBase.As16Bit());
-}
-
-TEST(UuidTest, As32Bit) {
- // Even though this is is not 32bit UUID, we should be able to get proper bits
- ASSERT_EQ((uint32_t)0x11111111, ONES.As32Bit());
- ASSERT_EQ((uint32_t)0x01234567, SEQUENTIAL.As32Bit());
- ASSERT_EQ((uint32_t)0x00000000, kBase.As32Bit());
- ASSERT_EQ((uint32_t)0x12345678, Uuid::From32Bit(0x12345678).As32Bit());
-}
-
-TEST(UuidTest, Is16Bit) {
- ASSERT_FALSE(ONES.Is16Bit());
- ASSERT_FALSE(SEQUENTIAL.Is16Bit());
- ASSERT_TRUE(kBase.Is16Bit());
- auto uuid = Uuid::FromString("1ae8");
- ASSERT_TRUE(uuid);
- ASSERT_TRUE(uuid->Is16Bit());
-}
-
-TEST(UuidTest, From16Bit) {
- ASSERT_EQ(Uuid::From16Bit(0x0000), kBase);
-
- const uint8_t u2[] = {0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x10, 0x00, 0x80, 0x00, 0x00, 0x80, 0x5f, 0x9b, 0x34, 0xfb};
- Uuid uuid = Uuid::From16Bit(0x0001);
- ASSERT_TRUE(memcmp(uuid.data(), u2, sizeof(u2)) == 0);
-
- const uint8_t u3[] = {0x00, 0x00, 0x55, 0x3e, 0x00, 0x00, 0x10, 0x00, 0x80, 0x00, 0x00, 0x80, 0x5f, 0x9b, 0x34, 0xfb};
- uuid = Uuid::From16Bit(0x553e);
- ASSERT_TRUE(memcmp(uuid.data(), u3, sizeof(u3)) == 0);
-
- const uint8_t u4[] = {0x00, 0x00, 0xff, 0xff, 0x00, 0x00, 0x10, 0x00, 0x80, 0x00, 0x00, 0x80, 0x5f, 0x9b, 0x34, 0xfb};
- uuid = Uuid::From16Bit(0xffff);
- ASSERT_TRUE(memcmp(uuid.data(), u4, sizeof(u4)) == 0);
-}
-
-TEST(UuidTest, From32Bit) {
- ASSERT_EQ(Uuid::From32Bit(0x00000000), kBase);
-
- const uint8_t u2[] = {0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x10, 0x00, 0x80, 0x00, 0x00, 0x80, 0x5f, 0x9b, 0x34, 0xfb};
- Uuid uuid = Uuid::From32Bit(0x00000001);
- ASSERT_TRUE(memcmp(uuid.data(), u2, sizeof(u2)) == 0);
-
- const uint8_t u3[] = {0x33, 0x44, 0x55, 0x3e, 0x00, 0x00, 0x10, 0x00, 0x80, 0x00, 0x00, 0x80, 0x5f, 0x9b, 0x34, 0xfb};
- uuid = Uuid::From32Bit(0x3344553e);
- ASSERT_TRUE(memcmp(uuid.data(), u3, sizeof(u3)) == 0);
-
- const uint8_t u4[] = {0xff, 0xff, 0xff, 0xff, 0x00, 0x00, 0x10, 0x00, 0x80, 0x00, 0x00, 0x80, 0x5f, 0x9b, 0x34, 0xfb};
- uuid = Uuid::From32Bit(0xffffffff);
- ASSERT_TRUE(memcmp(uuid.data(), u4, sizeof(u4)) == 0);
-}
-
-TEST(UuidTest, ToString) {
- const std::string UUID_BASE_STR = "00000000-0000-1000-8000-00805f9b34fb";
- const std::string UUID_EMP_STR = "00000000-0000-0000-0000-000000000000";
- const std::string UUID_ONES_STR = "11111111-1111-1111-1111-111111111111";
- const std::string UUID_SEQ_STR = "01234567-89ab-cdef-abcd-ef0123456789";
-
- ASSERT_EQ(UUID_BASE_STR, kBase.ToString());
- ASSERT_EQ(UUID_EMP_STR, Uuid::kEmpty.ToString());
- ASSERT_EQ(UUID_ONES_STR, ONES.ToString());
- ASSERT_EQ(UUID_SEQ_STR, SEQUENTIAL.ToString());
-
- Uuid uuid = Uuid::From32Bit(0x12345678);
- ASSERT_EQ("12345678-0000-1000-8000-00805f9b34fb", uuid.ToString());
-}
-
-TEST(UuidTest, test_string_to_uuid) {
- const uint8_t u1[] = {0xe3, 0x9c, 0x62, 0x85, 0x86, 0x7f, 0x4b, 0x1d, 0x9d, 0xb0, 0x35, 0xfb, 0xd9, 0xae, 0xbf, 0x22};
- auto uuid = Uuid::FromString("e39c6285-867f-4b1d-9db0-35fbd9aebf22");
- ASSERT_TRUE(uuid);
- ASSERT_TRUE(memcmp(uuid->data(), u1, sizeof(u1)) == 0);
-
- const uint8_t u2[] = {0x00, 0x00, 0x1a, 0xe8, 0x00, 0x00, 0x10, 0x00, 0x80, 0x00, 0x00, 0x80, 0x5f, 0x9b, 0x34, 0xfb};
- uuid = Uuid::FromString("1Ae8");
- ASSERT_TRUE(uuid);
- ASSERT_TRUE(memcmp(uuid->data(), u2, sizeof(u2)) == 0);
-
- const uint8_t u3[] = {0x12, 0x34, 0x11, 0x28, 0x00, 0x00, 0x10, 0x00, 0x80, 0x00, 0x00, 0x80, 0x5f, 0x9b, 0x34, 0xfb};
- uuid = Uuid::FromString("12341128");
- ASSERT_TRUE(uuid);
- ASSERT_TRUE(memcmp(uuid->data(), u3, sizeof(u3)) == 0);
-}
-
-TEST(UuidTest, test_string_to_uuid_invalid) {
- ASSERT_FALSE(Uuid::FromString("This is not a UUID"));
- ASSERT_FALSE(Uuid::FromString("11212"));
- ASSERT_FALSE(Uuid::FromString("1121 "));
- ASSERT_FALSE(Uuid::FromString("AGFE"));
- ASSERT_FALSE(Uuid::FromString("ABFG"));
- ASSERT_FALSE(Uuid::FromString("e39c6285867f14b1d9db035fbd9aebf22"));
- ASSERT_FALSE(Uuid::FromString("12234567-89ab-cdef-abcd-ef01234567ZZ"));
-}
-
-} // namespace testing
diff --git a/gd/hci/vendor_specific_event_manager.cc b/gd/hci/vendor_specific_event_manager.cc
deleted file mode 100644
index 914a9137e..000000000
--- a/gd/hci/vendor_specific_event_manager.cc
+++ /dev/null
@@ -1,132 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#include "hci/vendor_specific_event_manager.h"
-
-#include "hci/controller.h"
-#include "hci/hci_layer.h"
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace hci {
-
-const ModuleFactory VendorSpecificEventManager::Factory =
- ModuleFactory([]() { return new VendorSpecificEventManager(); });
-
-struct VendorSpecificEventManager::impl {
- impl(Module* module) : module_(module){};
-
- ~impl() {}
-
- void start(os::Handler* handler, hci::HciLayer* hci_layer, hci::Controller* controller) {
- module_handler_ = handler;
- hci_layer_ = hci_layer;
- controller_ = controller;
- hci_layer_->RegisterEventHandler(
- EventCode::VENDOR_SPECIFIC, handler->BindOn(this, &VendorSpecificEventManager::impl::on_vendor_specific_event));
- vendor_capabilities_ = controller->GetVendorCapabilities();
- }
-
- void stop() {}
-
- void register_event(VseSubeventCode event, common::ContextualCallback<void(VendorSpecificEventView)> handler) {
- ASSERT_LOG(
- subevent_handlers_.count(event) == 0,
- "Can not register a second handler for %02hhx (%s)",
- event,
- VseSubeventCodeText(event).c_str());
- subevent_handlers_[event] = handler;
- }
-
- void unregister_event(VseSubeventCode event) {
- subevent_handlers_.erase(subevent_handlers_.find(event));
- }
-
- bool check_event_supported(VseSubeventCode event) {
- switch (event) {
- case (VseSubeventCode::BLE_THRESHOLD): {
- if (vendor_capabilities_.total_scan_results_storage_ > 0) {
- return true;
- }
- } break;
- case (VseSubeventCode::BLE_TRACKING): {
- if (vendor_capabilities_.total_num_of_advt_tracked_ > 0) {
- return true;
- }
- } break;
- case (VseSubeventCode::DEBUG_INFO): {
- return vendor_capabilities_.debug_logging_supported_;
- } break;
- case (VseSubeventCode::BQR_EVENT): {
- return vendor_capabilities_.bluetooth_quality_report_support_;
- } break;
- default:
- LOG_WARN("Unhandled event %s", VseSubeventCodeText(event).c_str());
- }
- return false;
- }
-
- void on_vendor_specific_event(EventView event_view) {
- auto vendor_specific_event_view = VendorSpecificEventView::Create(event_view);
- ASSERT(vendor_specific_event_view.IsValid());
- VseSubeventCode vse_subevent_code = vendor_specific_event_view.GetSubeventCode();
- if (subevent_handlers_.find(vse_subevent_code) == subevent_handlers_.end()) {
- LOG_WARN("Unhandled vendor specific event of type 0x%02hhx", vse_subevent_code);
- return;
- }
- subevent_handlers_[vse_subevent_code].Invoke(vendor_specific_event_view);
- }
-
- Module* module_;
- os::Handler* module_handler_;
- hci::HciLayer* hci_layer_;
- hci::Controller* controller_;
- VendorCapabilities vendor_capabilities_;
- std::map<VseSubeventCode, common::ContextualCallback<void(VendorSpecificEventView)>> subevent_handlers_;
-};
-
-VendorSpecificEventManager::VendorSpecificEventManager() {
- pimpl_ = std::make_unique<impl>(this);
-}
-
-void VendorSpecificEventManager::ListDependencies(ModuleList* list) {
- list->add<hci::HciLayer>();
- list->add<hci::Controller>();
-}
-
-void VendorSpecificEventManager::Start() {
- pimpl_->start(GetHandler(), GetDependency<hci::HciLayer>(), GetDependency<hci::Controller>());
-}
-
-void VendorSpecificEventManager::Stop() {
- pimpl_->stop();
- pimpl_.reset();
-}
-
-std::string VendorSpecificEventManager::ToString() const {
- return "Vendor Specific Event Manager";
-}
-
-void VendorSpecificEventManager::RegisterEventHandler(
- VseSubeventCode event, common::ContextualCallback<void(VendorSpecificEventView)> handler) {
- CallOn(pimpl_.get(), &impl::register_event, event, handler);
-}
-
-void VendorSpecificEventManager::UnregisterEventHandler(VseSubeventCode event) {
- CallOn(pimpl_.get(), &impl::unregister_event, event);
-}
-
-} // namespace hci
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/hci/vendor_specific_event_manager.h b/gd/hci/vendor_specific_event_manager.h
deleted file mode 100644
index a0535aae0..000000000
--- a/gd/hci/vendor_specific_event_manager.h
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include "hci/hci_packets.h"
-#include "module.h"
-
-namespace bluetooth {
-namespace hci {
-
-class VendorSpecificEventManager : public bluetooth::Module {
- public:
- VendorSpecificEventManager();
-
- void RegisterEventHandler(VseSubeventCode event, common::ContextualCallback<void(VendorSpecificEventView)> handler);
-
- void UnregisterEventHandler(VseSubeventCode event);
-
- static const ModuleFactory Factory;
-
- protected:
- void ListDependencies(ModuleList* list) override;
-
- void Start() override;
-
- void Stop() override;
-
- std::string ToString() const override;
-
- private:
- struct impl;
- std::unique_ptr<impl> pimpl_;
- DISALLOW_COPY_AND_ASSIGN(VendorSpecificEventManager);
-};
-
-} // namespace hci
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/iso/Android.bp b/gd/iso/Android.bp
deleted file mode 100644
index 6d07c39f3..000000000
--- a/gd/iso/Android.bp
+++ /dev/null
@@ -1,30 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-filegroup {
- name: "BluetoothIsoSources",
- srcs: [
- "iso_manager.cc",
- "iso_module.cc",
- "internal/iso_manager_impl.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothIsoTestSources",
- srcs: [
- ],
-}
-
-filegroup {
- name: "BluetoothFacade_iso_layer",
- srcs: [
- "facade.cc",
- ],
-}
diff --git a/gd/iso/cert/cert_le_iso.py b/gd/iso/cert/cert_le_iso.py
deleted file mode 100644
index 94043649b..000000000
--- a/gd/iso/cert/cert_le_iso.py
+++ /dev/null
@@ -1,59 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2021 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import logging
-
-from cert.closable import Closable
-from cert.closable import safeClose
-from cert.py_le_iso import PyLeIso
-import bluetooth_packets_python3 as bt_packets
-from bluetooth_packets_python3 import l2cap_packets
-
-
-class CertLeIso(Closable):
-
- def __init__(self, device):
- self._device = device
- self._le_iso = PyLeIso(device)
-
- def close(self):
- logging.info("DUT: close")
- self._le_iso.close()
-
- def le_set_cig_parameters(self, cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, peripherals_clock_accuracy,
- packing, framing, max_transport_latency_m_to_s, max_transport_latency_s_to_m, cis_id,
- max_sdu_m_to_s, max_sdu_s_to_m, phy_m_to_s, phy_s_to_m, rtn_m_to_s, rtn_s_to_m):
- return self._le_iso.le_set_cig_parameters(
- cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, peripherals_clock_accuracy, packing, framing,
- max_transport_latency_m_to_s, max_transport_latency_s_to_m, cis_id, max_sdu_m_to_s, max_sdu_s_to_m,
- phy_m_to_s, phy_s_to_m, rtn_m_to_s, rtn_s_to_m)
-
- def le_set_cig_parameters_test(self, cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, ft_m_to_s, ft_s_to_m,
- iso_interval, peripherals_clock_accuracy, packing, framing,
- max_transport_latency_m_to_s, max_transport_latency_s_to_m, cis_configs):
- return self._le_iso.le_set_cig_parameters_test(cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, ft_m_to_s,
- ft_s_to_m, iso_interval, peripherals_clock_accuracy, packing,
- framing, max_transport_latency_m_to_s,
- max_transport_latency_s_to_m, cis_configs)
-
- def wait_le_set_cig_parameters_complete(self):
- return self._le_iso.wait_le_set_cig_parameters_complete()
-
- def le_cretate_cis(self, cis_and_acl_handle_array):
- self._le_iso.le_create_cis(cis_and_acl_handle_array)
-
- def wait_le_cis_established(self):
- return self._le_iso.wait_le_cis_established()
diff --git a/gd/iso/cert/le_iso_test.py b/gd/iso/cert/le_iso_test.py
deleted file mode 100644
index c1d3d65e3..000000000
--- a/gd/iso/cert/le_iso_test.py
+++ /dev/null
@@ -1,286 +0,0 @@
-#
-# Copyright 2021 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import time
-import logging
-
-from bluetooth_packets_python3 import hci_packets
-from cert.event_stream import EventStream
-from cert.gd_base_test import GdBaseTestClass
-from cert.matchers import HciMatchers, IsoMatchers, L2capMatchers
-from cert.metadata import metadata
-from cert.py_hci import PyHci
-from cert.py_l2cap import PyLeL2cap
-from cert.py_le_iso import PyLeIso
-from cert.py_le_iso import CisTestParameters
-from cert.truth import assertThat
-from datetime import timedelta
-from facade import common_pb2 as common
-from hci.facade import controller_facade_pb2 as controller_facade
-from hci.facade import le_advertising_manager_facade_pb2 as le_advertising_facade
-from hci.facade import le_initiator_address_facade_pb2 as le_initiator_address_facade
-from google.protobuf import empty_pb2 as empty_proto
-from neighbor.facade import facade_pb2 as neighbor_facade
-from l2cap.le.cert.cert_le_l2cap import CertLeL2cap
-from iso.cert.cert_le_iso import CertLeIso
-
-import time
-from bluetooth_packets_python3.hci_packets import OpCode
-
-
-class LeIsoTest(GdBaseTestClass):
- """
- Collection of tests that each sample results from
- different (unique) combinations of io capabilities, authentication requirements, and oob data.
- """
-
- def setup_class(self):
- super().setup_class(dut_module='L2CAP', cert_module='HCI_INTERFACES')
-
- def setup_test(self):
- super().setup_test()
-
- self.dut_l2cap = PyLeL2cap(self.dut)
- self.cert_l2cap = CertLeL2cap(self.cert)
- self.dut_address = common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes(b'D0:05:04:03:02:01')), type=common.RANDOM_DEVICE_ADDRESS)
- self.cert_address = common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes(b'C0:11:FF:AA:33:22')), type=common.RANDOM_DEVICE_ADDRESS)
- dut_privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_STATIC_ADDRESS,
- address_with_type=self.dut_address,
- rotation_irk=b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00',
- minimum_rotation_time=0,
- maximum_rotation_time=0)
- self.dut_l2cap._device.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(dut_privacy_policy)
- privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_STATIC_ADDRESS,
- address_with_type=self.cert_address,
- rotation_irk=b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00',
- minimum_rotation_time=0,
- maximum_rotation_time=0)
- self.cert_l2cap._device.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(privacy_policy)
-
- self.dut_iso = PyLeIso(self.dut)
- self.cert_iso = CertLeIso(self.cert)
-
- def teardown_test(self):
- self.dut_iso.close()
- self.cert_iso.close()
-
- self.cert_l2cap.close()
- self.dut_l2cap.close()
- super().teardown_test()
-
- #cert becomes central of connection, dut peripheral
- def _setup_link_from_cert(self):
- # DUT Advertises
- gap_name = hci_packets.GapData()
- gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(b'Im_The_DUT'))
- gap_data = le_advertising_facade.GapDataMsg(data=bytes(gap_name.Serialize()))
- config = le_advertising_facade.AdvertisingConfig(
- advertisement=[gap_data],
- interval_min=512,
- interval_max=768,
- advertising_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
- own_address_type=common.USE_RANDOM_DEVICE_ADDRESS,
- channel_map=7,
- filter_policy=le_advertising_facade.AdvertisingFilterPolicy.ALL_DEVICES)
- request = le_advertising_facade.CreateAdvertiserRequest(config=config)
- create_response = self.dut.hci_le_advertising_manager.CreateAdvertiser(request)
- self.cert_l2cap.connect_le_acl(self.dut_address)
-
- def _setup_cis_from_cert(self, cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, ft_m_to_s, ft_s_to_m, iso_interval,
- peripherals_clock_accuracy, packing, framing, max_transport_latency_m_to_s,
- max_transport_latency_s_to_m, cis_configs):
- self.cert_iso.le_set_cig_parameters_test(cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, ft_m_to_s, ft_s_to_m,
- iso_interval, peripherals_clock_accuracy, packing, framing,
- max_transport_latency_m_to_s, max_transport_latency_s_to_m,
- cis_configs)
-
- cis_handles = self.cert_iso.wait_le_set_cig_parameters_complete()
-
- cis_handle = cis_handles[0]
-
- acl_connection_handle = self.cert_l2cap._le_acl.handle
- self.cert_iso.le_cretate_cis([(cis_handle, acl_connection_handle)])
- dut_cis_stream = self.dut_iso.wait_le_cis_established()
- cert_cis_stream = self.cert_iso.wait_le_cis_established()
- return (dut_cis_stream, cert_cis_stream)
-
- @metadata(
- pts_test_id="IAL/CIS/UNF/SLA/BV-01-C",
- pts_test_name="connected isochronous stream, unframed data, peripheral role")
- def test_iso_cis_unf_sla_bv_01_c(self):
- """
- Verify that the IUT can send an SDU with length ≤ the Isochronous PDU length.
- """
- cig_id = 0x01
- sdu_interval_m_to_s = 0
- sdu_interval_s_to_m = 0x186a
- ft_m_to_s = 0
- ft_s_to_m = 1
- iso_interval = 0x0A
- peripherals_clock_accuracy = 0
- packing = 0
- framing = 0
- max_transport_latency_m_to_s = 0
- max_transport_latency_s_to_m = 0
- cis_configs = [
- CisTestParameters(
- cis_id=0x01,
- nse=2,
- max_sdu_m_to_s=100,
- max_sdu_s_to_m=100,
- max_pdu_m_to_s=100,
- max_pdu_s_to_m=100,
- phy_m_to_s=0x02,
- phy_s_to_m=0x00,
- bn_m_to_s=0,
- bn_s_to_m=2,
- )
- ]
-
- self._setup_link_from_cert()
- (dut_cis_stream, cert_cis_stream) = self._setup_cis_from_cert(
- cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, ft_m_to_s, ft_s_to_m, iso_interval,
- peripherals_clock_accuracy, packing, framing, max_transport_latency_m_to_s, max_transport_latency_s_to_m,
- cis_configs)
- dut_cis_stream.send(b'abcdefgh' * 10)
- assertThat(cert_cis_stream).emits(IsoMatchers.Data(b'abcdefgh' * 10))
-
- @metadata(
- pts_test_id="IAL/CIS/UNF/SLA/BV-25-C",
- pts_test_name="connected isochronous stream, unframed data, peripheral role")
- def test_iso_cis_unf_sla_bv_25_c(self):
- """
- Verify that the IUT can send an SDU with length ≤ the Isochronous PDU length.
- """
- cig_id = 0x01
- sdu_interval_m_to_s = 0x7530
- sdu_interval_s_to_m = 0x7530
- ft_m_to_s = 3
- ft_s_to_m = 2
- iso_interval = 0x18
- peripherals_clock_accuracy = 0
- packing = 0
- framing = 0
- max_transport_latency_m_to_s = 0
- max_transport_latency_s_to_m = 0
- cis_configs = [
- CisTestParameters(
- cis_id=0x01,
- nse=5,
- max_sdu_m_to_s=100,
- max_sdu_s_to_m=100,
- max_pdu_m_to_s=100,
- max_pdu_s_to_m=100,
- phy_m_to_s=0x02,
- phy_s_to_m=0x00,
- bn_m_to_s=3,
- bn_s_to_m=1,
- )
- ]
-
- self._setup_link_from_cert()
- (dut_cis_stream, cert_cis_stream) = self._setup_cis_from_cert(
- cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, ft_m_to_s, ft_s_to_m, iso_interval,
- peripherals_clock_accuracy, packing, framing, max_transport_latency_m_to_s, max_transport_latency_s_to_m,
- cis_configs)
- dut_cis_stream.send(b'abcdefgh' * 10)
- assertThat(cert_cis_stream).emits(IsoMatchers.Data(b'abcdefgh' * 10))
-
- @metadata(
- pts_test_id="IAL/CIS/FRA/SLA/BV-03-C",
- pts_test_name="connected isochronous stream, framed data, peripheral role")
- def test_iso_cis_fra_sla_bv_03_c(self):
- """
- Verify that the IUT can send an SDU with length ≤ the Isochronous PDU length.
- """
- cig_id = 0x01
- sdu_interval_m_to_s = 0x0000
- sdu_interval_s_to_m = 0x4e30
- ft_m_to_s = 0
- ft_s_to_m = 2
- iso_interval = 0x14
- peripherals_clock_accuracy = 0
- packing = 0
- framing = 1
- max_transport_latency_m_to_s = 0
- max_transport_latency_s_to_m = 0
- cis_configs = [
- CisTestParameters(
- cis_id=0x01,
- nse=4,
- max_sdu_m_to_s=100,
- max_sdu_s_to_m=100,
- max_pdu_m_to_s=100,
- max_pdu_s_to_m=100,
- phy_m_to_s=0x02,
- phy_s_to_m=0x00,
- bn_m_to_s=0,
- bn_s_to_m=2,
- )
- ]
-
- self._setup_link_from_cert()
- (dut_cis_stream, cert_cis_stream) = self._setup_cis_from_cert(
- cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, ft_m_to_s, ft_s_to_m, iso_interval,
- peripherals_clock_accuracy, packing, framing, max_transport_latency_m_to_s, max_transport_latency_s_to_m,
- cis_configs)
- dut_cis_stream.send(b'abcdefgh' * 10)
- assertThat(cert_cis_stream).emits(IsoMatchers.Data(b'abcdefgh' * 10))
-
- @metadata(
- pts_test_id="IAL/CIS/FRA/SLA/BV-26-C",
- pts_test_name="connected isochronous stream, framed data, peripheral role")
- def test_iso_cis_fra_sla_bv_26_c(self):
- """
- Verify that the IUT can send an SDU with length ≤ the Isochronous PDU length.
- """
- cig_id = 0x01
- sdu_interval_m_to_s = 0x14D5
- sdu_interval_s_to_m = 0x14D5
- ft_m_to_s = 1
- ft_s_to_m = 1
- iso_interval = 0x08
- peripherals_clock_accuracy = 0
- packing = 0
- framing = 1
- max_transport_latency_m_to_s = 0
- max_transport_latency_s_to_m = 0
- cis_configs = [
- CisTestParameters(
- cis_id=0x01,
- nse=2,
- max_sdu_m_to_s=100,
- max_sdu_s_to_m=100,
- max_pdu_m_to_s=100,
- max_pdu_s_to_m=100,
- phy_m_to_s=0x02,
- phy_s_to_m=0x00,
- bn_m_to_s=1,
- bn_s_to_m=1,
- )
- ]
-
- self._setup_link_from_cert()
- (dut_cis_stream, cert_cis_stream) = self._setup_cis_from_cert(
- cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, ft_m_to_s, ft_s_to_m, iso_interval,
- peripherals_clock_accuracy, packing, framing, max_transport_latency_m_to_s, max_transport_latency_s_to_m,
- cis_configs)
- dut_cis_stream.send(b'abcdefgh' * 10)
- assertThat(cert_cis_stream).emits(IsoMatchers.Data(b'abcdefgh' * 10))
diff --git a/gd/iso/facade.cc b/gd/iso/facade.cc
deleted file mode 100644
index 9b5c88e8b..000000000
--- a/gd/iso/facade.cc
+++ /dev/null
@@ -1,232 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#include "iso/facade.h"
-
-#include "common/contextual_callback.h"
-#include "grpc/grpc_event_queue.h"
-#include "hci/acl_manager.h"
-#include "hci/address_with_type.h"
-#include "hci/le_address_manager.h"
-#include "iso/facade.grpc.pb.h"
-#include "iso/iso_module.h"
-#include "os/handler.h"
-
-using bluetooth::hci::AclManager;
-
-namespace bluetooth {
-namespace iso {
-
-class IsoModuleFacadeService : public IsoModuleFacade::Service {
- public:
- IsoModuleFacadeService(IsoModule* iso_module, AclManager* acl_manager, ::bluetooth::os::Handler* iso_handler)
- : iso_module_(iso_module), acl_manager_(acl_manager), iso_handler_(iso_handler) {
- ASSERT(iso_module_);
- ASSERT(iso_handler_);
-
- iso_module_->GetIsoManager()->RegisterIsoEstablishedCallback(iso_handler_->Bind(
- [](::bluetooth::grpc::GrpcEventQueue<LeIsoEventsMsg>* le_iso_events_, uint16_t cis_connection_handle) {
- LeIsoEventsMsg msg;
- msg.set_message_type(IsoMsgType::ISO_CIS_ESTABLISHED);
- msg.add_cis_handle(cis_connection_handle);
- le_iso_events_->OnIncomingEvent(msg);
- },
- &le_iso_events_));
-
- iso_module_->GetIsoManager()->RegisterIsoDataCallback(
- iso_handler_->BindOn(this, &IsoModuleFacadeService::OnIsoPacketReceived));
- }
-
- ::grpc::Status LeSetCigParameters(
- ::grpc::ServerContext* context,
- const ::bluetooth::iso::LeSetCigParametersRequest* request,
- ::google::protobuf::Empty* response) override {
- std::vector<hci::CisParametersConfig> cis_config;
-
- hci::CisParametersConfig cfg;
- cfg.cis_id_ = request->cis_id();
- cfg.max_sdu_m_to_s_ = request->max_sdu_m_to_s();
- cfg.max_sdu_s_to_m_ = request->max_sdu_s_to_m();
- cfg.phy_m_to_s_ = request->phy_m_to_s();
- cfg.phy_s_to_m_ = request->phy_s_to_m();
- cfg.rtn_m_to_s_ = request->rtn_m_to_s();
- cfg.rtn_s_to_m_ = request->rtn_s_to_m();
-
- cis_config.push_back(cfg);
-
- iso_module_->GetIsoManager()->SetCigParameters(
- request->cig_id(),
- request->sdu_interval_m_to_s(),
- request->sdu_interval_s_to_m(),
- static_cast<hci::ClockAccuracy>(request->peripherals_clock_accuracy()),
- static_cast<hci::Packing>(request->packing()),
- static_cast<hci::Enable>(request->framing()),
- request->max_transport_latency_m_to_s(),
- request->max_transport_latency_s_to_m(),
- cis_config,
- iso_handler_->BindOnce(
- [](::bluetooth::grpc::GrpcEventQueue<LeIsoEventsMsg>* le_iso_events_, std::vector<uint16_t> conn_handles) {
- LeIsoEventsMsg msg;
-
- msg.set_message_type(IsoMsgType::ISO_PARAMETERS_SET_COMPLETE);
- for (const uint16_t conn_handle : conn_handles) {
- msg.add_cis_handle(conn_handle);
- }
- le_iso_events_->OnIncomingEvent(msg);
- },
- &le_iso_events_));
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status LeSetCigParametersTest(
- ::grpc::ServerContext* context,
- const ::bluetooth::iso::LeSetCigParametersTestRequest* request,
- ::google::protobuf::Empty* response) override {
- std::vector<hci::LeCisParametersTestConfig> cis_config;
-
- for (const auto& cc : request->cis_configs()) {
- hci::LeCisParametersTestConfig cfg;
- cfg.cis_id_ = cc.cis_id();
- cfg.nse_ = cc.nse();
- cfg.max_sdu_m_to_s_ = cc.max_sdu_m_to_s();
- cfg.max_sdu_s_to_m_ = cc.max_sdu_s_to_m();
- cfg.max_pdu_m_to_s_ = cc.max_pdu_m_to_s();
- cfg.max_pdu_s_to_m_ = cc.max_pdu_s_to_m();
- cfg.phy_m_to_s_ = cc.phy_m_to_s();
- cfg.phy_s_to_m_ = cc.phy_s_to_m();
- cfg.bn_m_to_s_ = cc.bn_m_to_s();
- cfg.bn_s_to_m_ = cc.bn_s_to_m();
- cis_config.push_back(cfg);
- }
- iso_module_->GetIsoManager()->SetCigParametersTest(
- request->cig_id(),
- request->sdu_interval_m_to_s(),
- request->sdu_interval_s_to_m(),
- request->ft_m_to_s(),
- request->ft_s_to_m(),
- request->iso_interval(),
- static_cast<hci::ClockAccuracy>(request->peripherals_clock_accuracy()),
- static_cast<hci::Packing>(request->packing()),
- static_cast<hci::Enable>(request->framing()),
- request->max_transport_latency_m_to_s(),
- request->max_transport_latency_s_to_m(),
- cis_config,
- iso_handler_->BindOnce(
- [](::bluetooth::grpc::GrpcEventQueue<LeIsoEventsMsg>* le_iso_events_, std::vector<uint16_t> conn_handles) {
- LeIsoEventsMsg msg;
-
- msg.set_message_type(IsoMsgType::ISO_PARAMETERS_SET_COMPLETE);
- for (const uint16_t conn_handle : conn_handles) {
- msg.add_cis_handle(conn_handle);
- }
- le_iso_events_->OnIncomingEvent(msg);
- },
- &le_iso_events_));
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status LeCreateCis(
- ::grpc::ServerContext* context,
- const ::bluetooth::iso::LeCreateCisRequest* request,
- ::google::protobuf::Empty* response) override {
- std::vector<std::pair<uint16_t, uint16_t>> create_cis_params;
- for (const auto& handle_pair : request->handle_pair()) {
- create_cis_params.push_back(
- std::make_pair<uint16_t, uint16_t>(handle_pair.cis_handle(), handle_pair.acl_handle()));
- }
- iso_module_->GetIsoManager()->LeCreateCis(create_cis_params);
-
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status FetchIsoData(
- ::grpc::ServerContext* context, const LeCisHandleMsg* request, ::grpc::ServerWriter<IsoPacket>* writer) override {
- return le_iso_data_.RunLoop(context, writer);
- }
-
- ::grpc::Status FetchIsoEvents(
- ::grpc::ServerContext* context,
- const google::protobuf::Empty* request,
- ::grpc::ServerWriter<LeIsoEventsMsg>* writer) override {
- return le_iso_events_.RunLoop(context, writer);
- }
-
- ::grpc::Status SendIsoPacket(
- ::grpc::ServerContext* context,
- const ::bluetooth::iso::IsoPacket* request,
- ::google::protobuf::Empty* response) override {
- std::vector<uint8_t> packet(request->payload().begin(), request->payload().end());
- iso_module_->GetIsoManager()->SendIsoPacket(request->handle(), packet);
- return ::grpc::Status::OK;
- }
-
- void OnIsoPacketReceived(std::unique_ptr<hci::IsoView> iso_view) {
- ASSERT(iso_view->IsValid());
-
- IsoPacket packet;
- packet.set_handle(iso_view->GetConnectionHandle());
-
- if (iso_view->GetTsFlag() == hci::TimeStampFlag::NOT_PRESENT) {
- hci::IsoWithoutTimestampView nts = hci::IsoWithoutTimestampView::Create(*iso_view);
- ASSERT(nts.IsValid());
-
- auto data_vec = nts.GetPayload();
- std::string data = std::string(data_vec.begin(), data_vec.end());
- packet.set_payload(data);
- le_iso_data_.OnIncomingEvent(packet);
- } else {
- hci::IsoWithTimestampView tsv = hci::IsoWithTimestampView::Create(*iso_view);
- ASSERT(tsv.IsValid());
-
- auto data_vec = tsv.GetPayload();
- std::string data = std::string(data_vec.begin(), data_vec.end());
- packet.set_payload(data);
- le_iso_data_.OnIncomingEvent(packet);
- }
- }
-
- private:
- IsoModule* iso_module_;
- ::bluetooth::grpc::GrpcEventQueue<LeIsoEventsMsg> le_iso_events_{"LE ISO events"};
- ::bluetooth::grpc::GrpcEventQueue<IsoPacket> le_iso_data_{"LE ISO data"};
- AclManager* acl_manager_ __attribute__((unused));
- ::bluetooth::os::Handler* iso_handler_;
-};
-
-void IsoModuleFacadeModule::ListDependencies(ModuleList* list) {
- ::bluetooth::grpc::GrpcFacadeModule::ListDependencies(list);
- list->add<IsoModule>();
- list->add<AclManager>();
-}
-
-void IsoModuleFacadeModule::Start() {
- ::bluetooth::grpc::GrpcFacadeModule::Start();
- service_ = new IsoModuleFacadeService(GetDependency<IsoModule>(), GetDependency<AclManager>(), GetHandler());
-}
-
-void IsoModuleFacadeModule::Stop() {
- delete service_;
- ::bluetooth::grpc::GrpcFacadeModule::Stop();
-}
-
-::grpc::Service* IsoModuleFacadeModule::GetService() const {
- return service_;
-}
-
-const ModuleFactory IsoModuleFacadeModule::Factory =
- ::bluetooth::ModuleFactory([]() { return new IsoModuleFacadeModule(); });
-
-} // namespace iso
-} // namespace bluetooth
diff --git a/gd/iso/facade.h b/gd/iso/facade.h
deleted file mode 100644
index 266bb0958..000000000
--- a/gd/iso/facade.h
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <grpc++/grpc++.h>
-
-#include "grpc/grpc_module.h"
-
-namespace bluetooth {
-namespace iso {
-
-class IsoModuleFacadeService;
-
-class IsoModuleFacadeModule : public ::bluetooth::grpc::GrpcFacadeModule {
- public:
- static const ModuleFactory Factory;
-
- void ListDependencies(ModuleList* list) override;
- void Start() override;
- void Stop() override;
- ::grpc::Service* GetService() const override;
-
- private:
- IsoModuleFacadeService* service_;
-};
-
-} // namespace iso
-} // namespace bluetooth
diff --git a/gd/iso/facade.proto b/gd/iso/facade.proto
deleted file mode 100644
index 28f9d27bc..000000000
--- a/gd/iso/facade.proto
+++ /dev/null
@@ -1,90 +0,0 @@
-syntax = "proto3";
-
-package bluetooth.iso;
-
-import "google/protobuf/empty.proto";
-import "facade/common.proto";
-
-service IsoModuleFacade {
- rpc LeSetCigParameters(LeSetCigParametersRequest) returns (google.protobuf.Empty) {}
- rpc LeSetCigParametersTest(LeSetCigParametersTestRequest) returns (google.protobuf.Empty) {}
- rpc LeCreateCis(LeCreateCisRequest) returns (google.protobuf.Empty) {}
- rpc FetchIsoData(LeCisHandleMsg) returns (stream IsoPacket) {}
- rpc FetchIsoEvents(google.protobuf.Empty) returns (stream LeIsoEventsMsg) {}
- rpc SendIsoPacket(IsoPacket) returns (google.protobuf.Empty) {}
-}
-
-message IsoPacket {
- uint32 handle = 1;
- bytes payload = 3;
-}
-
-message LeSetCigParametersRequest {
- uint32 cig_id = 1;
- uint32 sdu_interval_m_to_s = 2;
- uint32 sdu_interval_s_to_m = 3;
- uint32 peripherals_clock_accuracy = 4;
- uint32 packing = 5;
- uint32 framing = 6;
- uint32 max_transport_latency_m_to_s = 7;
- uint32 max_transport_latency_s_to_m = 8;
- uint32 cis_id = 9;
- uint32 max_sdu_m_to_s = 10;
- uint32 max_sdu_s_to_m = 11;
- uint32 phy_m_to_s = 12;
- uint32 phy_s_to_m = 13;
- uint32 rtn_m_to_s = 14;
- uint32 rtn_s_to_m = 15;
-}
-
-message LeSetCigParametersTestRequest {
- uint32 cig_id = 1;
- uint32 sdu_interval_m_to_s = 2;
- uint32 sdu_interval_s_to_m = 3;
- uint32 ft_m_to_s = 4;
- uint32 ft_s_to_m = 5;
- uint32 iso_interval = 6;
- uint32 peripherals_clock_accuracy = 7;
- uint32 packing = 8;
- uint32 framing = 9;
- uint32 max_transport_latency_m_to_s = 10;
- uint32 max_transport_latency_s_to_m = 11;
-
- message LeCisParametersTestConfig {
- uint32 cis_id = 1;
- uint32 nse = 2;
- uint32 max_sdu_m_to_s = 3;
- uint32 max_sdu_s_to_m = 4;
- uint32 max_pdu_m_to_s = 5;
- uint32 max_pdu_s_to_m = 6;
- uint32 phy_m_to_s = 7;
- uint32 phy_s_to_m = 8;
- uint32 bn_m_to_s = 9;
- uint32 bn_s_to_m = 10;
- }
-
- repeated LeCisParametersTestConfig cis_configs = 12;
-}
-
-message LeCreateCisRequest {
- message HandlePair {
- uint32 cis_handle = 1;
- uint32 acl_handle = 2;
- }
-
- repeated HandlePair handle_pair = 1;
-}
-
-enum IsoMsgType {
- ISO_PARAMETERS_SET_COMPLETE = 0;
- ISO_CIS_ESTABLISHED = 1;
-}
-
-message LeIsoEventsMsg {
- IsoMsgType message_type = 1;
- repeated uint32 cis_handle = 2;
-}
-
-message LeCisHandleMsg {
- uint32 handle = 1;
-}
diff --git a/gd/iso/internal/iso_manager_impl.cc b/gd/iso/internal/iso_manager_impl.cc
deleted file mode 100644
index 1ea385894..000000000
--- a/gd/iso/internal/iso_manager_impl.cc
+++ /dev/null
@@ -1,271 +0,0 @@
-/*
- *
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-#include "iso_manager_impl.h"
-
-#include "common/bind.h"
-#include "hci/hci_packets.h"
-#include "iso/iso_manager.h"
-#include "os/handler.h"
-#include "os/log.h"
-#include "packet/raw_builder.h"
-
-namespace bluetooth {
-namespace iso {
-namespace internal {
-
-using bluetooth::hci::IsoBuilder;
-
-IsoManagerImpl::IsoManagerImpl(os::Handler* iso_handler, hci::HciLayer* hci_layer, hci::Controller* controller)
- : iso_handler_(iso_handler),
- hci_layer_(hci_layer),
- hci_le_iso_interface_(hci_layer->GetLeIsoInterface(iso_handler_->BindOn(this, &IsoManagerImpl::OnHciLeEvent))),
- controller_(controller) {
- hci_layer_->GetIsoQueueEnd()->RegisterDequeue(
- iso_handler_, common::Bind(&IsoManagerImpl::OnIncomingPacket, common::Unretained(this)));
- iso_enqueue_buffer_ = std::make_unique<os::EnqueueBuffer<IsoBuilder>>(hci_layer_->GetIsoQueueEnd());
-}
-
-IsoManagerImpl::~IsoManagerImpl() {
- hci_layer_->GetIsoQueueEnd()->UnregisterDequeue();
- iso_enqueue_buffer_ = nullptr;
-}
-
-void IsoManagerImpl::OnHciLeEvent(hci::LeMetaEventView event) {
- hci::SubeventCode code = event.GetSubeventCode();
-
- if (code == hci::SubeventCode::CIS_ESTABLISHED) {
- hci::LeCisEstablishedView le_cis_established_view = hci::LeCisEstablishedView::Create(event);
- if (!le_cis_established_view.IsValid()) {
- LOG_ERROR("Invalid LeCisEstablishedView packet received");
- return;
- }
-
- cis_established_callback.Invoke(le_cis_established_view.GetConnectionHandle());
- return;
- } else if (code == hci::SubeventCode::CIS_REQUEST) {
- hci::LeCisRequestView le_cis_request_view = hci::LeCisRequestView::Create(event);
- if (!le_cis_request_view.IsValid()) {
- LOG_ERROR("Invalid LeCisRequestView packet received");
- return;
- }
-
- hci_le_iso_interface_->EnqueueCommand(
- hci::LeAcceptCisRequestBuilder::Create(le_cis_request_view.GetCisConnectionHandle()),
- iso_handler_->BindOnce([](hci::CommandStatusView command_status) {
- LOG_INFO("command_status=%hhu ", command_status.GetStatus());
- }));
-
- return;
- }
-
- LOG_ERROR("Unhandled HCI LE ISO event, code %s", hci::SubeventCodeText(code).c_str());
- ASSERT_LOG(false, "Unhandled HCI LE ISO event");
-}
-
-void IsoManagerImpl::SetCigParameters(
- uint8_t cig_id,
- uint32_t sdu_interval_m_to_s,
- uint32_t sdu_interval_s_to_m,
- hci::ClockAccuracy peripherals_clock_accuracy,
- hci::Packing packing,
- hci::Enable framing,
- uint16_t max_transport_latency_m_to_s,
- uint16_t max_transport_latency_s_to_m,
- const std::vector<hci::CisParametersConfig>& cis_configs,
- SetCigParametersCallback command_complete_callback) {
- hci_le_iso_interface_->EnqueueCommand(
- hci::LeSetCigParametersBuilder::Create(
- cig_id,
- sdu_interval_m_to_s,
- sdu_interval_s_to_m,
- peripherals_clock_accuracy,
- packing,
- framing,
- max_transport_latency_m_to_s,
- max_transport_latency_s_to_m,
- cis_configs),
- iso_handler_->BindOnce(
- &IsoManagerImpl::SetCigParametersComplete,
- common::Unretained(this),
- cig_id,
- cis_configs,
- std::move(command_complete_callback)));
-}
-
-void IsoManagerImpl::SetCigParametersComplete(
- uint8_t cig_id,
- const std::vector<hci::CisParametersConfig>& cis_configs,
- SetCigParametersCallback command_complete_callback,
- hci::CommandCompleteView command_complete) {
- ASSERT(command_complete.IsValid());
-
- hci::LeSetCigParametersCompleteView setCigParamsComplete =
- hci::LeSetCigParametersCompleteView::Create(command_complete);
- ASSERT(setCigParamsComplete.IsValid());
-
- if (setCigParamsComplete.GetStatus() == hci::ErrorCode::SUCCESS) {
- uint8_t cig_id_back_from_ctrl = setCigParamsComplete.GetCigId();
- auto conn_handles = setCigParamsComplete.GetConnectionHandle();
-
- ASSERT(cig_id_back_from_ctrl == cig_id);
- ASSERT(conn_handles.size() == cis_configs.size());
-
- auto cis_it = cis_configs.begin();
- auto handle_it = conn_handles.begin();
-
- std::vector<uint16_t> handles;
- while (cis_it != cis_configs.end()) {
- iso_connections_.push_back({
- .cig_id = cig_id,
- .cis_id = cis_it->cis_id_,
- .connection_handle = *handle_it,
- });
-
- handles.push_back(*handle_it);
-
- cis_it++;
- handle_it++;
- }
-
- command_complete_callback.Invoke(handles);
- }
-}
-
-void IsoManagerImpl::SetCigParametersTest(
- uint8_t cig_id,
- uint32_t sdu_interval_m_to_s,
- uint32_t sdu_interval_s_to_m,
- uint8_t ft_m_to_s,
- uint8_t ft_s_to_m,
- uint16_t iso_interval,
- hci::ClockAccuracy peripherals_clock_accuracy,
- hci::Packing packing,
- hci::Enable framing,
- uint16_t max_transport_latency_m_to_s,
- uint16_t max_transport_latency_s_to_m,
- const std::vector<hci::LeCisParametersTestConfig>& cis_test_configs,
- SetCigParametersCallback command_complete_callback) {
- hci_le_iso_interface_->EnqueueCommand(
- hci::LeSetCigParametersTestBuilder::Create(
- cig_id,
- sdu_interval_m_to_s,
- sdu_interval_s_to_m,
- ft_m_to_s,
- ft_s_to_m,
- iso_interval,
- peripherals_clock_accuracy,
- packing,
- framing,
- cis_test_configs),
- iso_handler_->BindOnce(
- &IsoManagerImpl::SetCigParametersTestComplete,
- common::Unretained(this),
- cig_id,
- cis_test_configs,
- std::move(command_complete_callback)));
-}
-
-void IsoManagerImpl::SetCigParametersTestComplete(
- uint8_t cig_id,
- const std::vector<hci::LeCisParametersTestConfig>& cis_configs,
- SetCigParametersCallback command_complete_callback,
- hci::CommandCompleteView command_complete) {
- ASSERT(command_complete.IsValid());
-
- hci::LeSetCigParametersTestCompleteView setCigParamsComplete =
- hci::LeSetCigParametersTestCompleteView::Create(command_complete);
- ASSERT(setCigParamsComplete.IsValid());
-
- if (setCigParamsComplete.GetStatus() == hci::ErrorCode::SUCCESS) {
- uint8_t cig_id_back_from_ctrl = setCigParamsComplete.GetCigId();
- auto conn_handles = setCigParamsComplete.GetConnectionHandle();
-
- ASSERT(cig_id_back_from_ctrl == cig_id);
- ASSERT(conn_handles.size() == cis_configs.size());
-
- auto cis_it = cis_configs.begin();
- auto handle_it = conn_handles.begin();
-
- std::vector<uint16_t> handles;
- while (cis_it != cis_configs.end()) {
- iso_connections_.push_back({
- .cig_id = cig_id,
- .cis_id = cis_it->cis_id_,
- .connection_handle = *handle_it,
- });
-
- handles.push_back(*handle_it);
-
- cis_it++;
- handle_it++;
- }
-
- command_complete_callback.Invoke(handles);
- }
-}
-
-void IsoManagerImpl::LeCreateCis(std::vector<std::pair<uint16_t, uint16_t>> cis_and_acl_handles) {
- std::vector<hci::CreateCisConfig> cis_configs;
-
- for (const auto& handle_pair : cis_and_acl_handles) {
- hci::CreateCisConfig config;
- config.cis_connection_handle_ = handle_pair.first;
- config.acl_connection_handle_ = handle_pair.second;
- cis_configs.push_back(config);
- }
-
- hci_le_iso_interface_->EnqueueCommand(
- hci::LeCreateCisBuilder::Create(cis_configs), iso_handler_->BindOnce([](hci::CommandStatusView command_status) {
- LOG_INFO("command_status=%hhu ", command_status.GetStatus());
- }));
-}
-
-void IsoManagerImpl::RemoveCig(uint8_t cig_id) {
- ASSERT(IsKnownCig(cig_id));
-
- hci_le_iso_interface_->EnqueueCommand(
- hci::LeRemoveCigBuilder::Create(cig_id),
- iso_handler_->BindOnce(&IsoManagerImpl::RemoveCigComplete, common::Unretained(this)));
-}
-
-void IsoManagerImpl::RemoveCigComplete(hci::CommandCompleteView command_complete) {
- ASSERT(command_complete.IsValid());
-
- hci::LeRemoveCigCompleteView removeCigComplete = hci::LeRemoveCigCompleteView::Create(command_complete);
- ASSERT(removeCigComplete.IsValid());
-}
-
-void IsoManagerImpl::SendIsoPacket(uint16_t cis_handle, std::vector<uint8_t> packet) {
- auto builder = hci::IsoWithoutTimestampBuilder::Create(
- cis_handle,
- hci::IsoPacketBoundaryFlag::COMPLETE_SDU,
- 0 /* sequence_number*/,
- hci::IsoPacketStatusFlag::VALID,
- std::make_unique<bluetooth::packet::RawBuilder>(packet));
- LOG_INFO("%c%c", packet[0], packet[1]);
- iso_enqueue_buffer_->Enqueue(std::move(builder), iso_handler_);
-}
-
-void IsoManagerImpl::OnIncomingPacket() {
- std::unique_ptr<hci::IsoView> packet = hci_layer_->GetIsoQueueEnd()->TryDequeue();
- iso_data_callback.Invoke(std::move(packet));
-}
-
-} // namespace internal
-} // namespace iso
-} // namespace bluetooth
diff --git a/gd/iso/internal/iso_manager_impl.h b/gd/iso/internal/iso_manager_impl.h
deleted file mode 100644
index b29702505..000000000
--- a/gd/iso/internal/iso_manager_impl.h
+++ /dev/null
@@ -1,118 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "hci/controller.h"
-#include "hci/hci_layer.h"
-#include "hci/hci_packets.h"
-#include "os/handler.h"
-
-#include <list>
-
-namespace bluetooth {
-namespace iso {
-using SetCigParametersCallback = common::ContextualOnceCallback<void(std::vector<uint16_t>)>;
-using CisEstablishedCallback = common::ContextualCallback<void(uint16_t)>;
-using IsoDataCallback = common::ContextualCallback<void(std::unique_ptr<hci::IsoView>)>;
-
-namespace internal {
-
-struct IsochronousConnection {
- uint16_t connection_handle;
- uint8_t cig_id;
- uint8_t cis_id;
-};
-
-class IsoManagerImpl {
- public:
- explicit IsoManagerImpl(os::Handler* iso_handler, hci::HciLayer* hci_layer, hci::Controller* controller);
- ~IsoManagerImpl();
-
- void RegisterIsoEstablishedCallback(CisEstablishedCallback cb) {
- this->cis_established_callback = cb;
- }
-
- void RegisterIsoDataCallback(IsoDataCallback cb) {
- this->iso_data_callback = cb;
- }
-
- void OnHciLeEvent(hci::LeMetaEventView event);
-
- void SetCigParameters(
- uint8_t cig_id,
- uint32_t sdu_interval_m_to_s,
- uint32_t sdu_interval_s_to_m,
- hci::ClockAccuracy peripherals_clock_accuracy,
- hci::Packing packing,
- hci::Enable framing,
- uint16_t max_transport_latency_m_to_s,
- uint16_t max_transport_latency_s_to_m,
- const std::vector<hci::CisParametersConfig>& cis_config,
- SetCigParametersCallback command_complete_callback);
- void SetCigParametersComplete(
- uint8_t cig_id,
- const std::vector<hci::CisParametersConfig>& cis_configs,
- SetCigParametersCallback command_complete_callback,
- hci::CommandCompleteView command_complete);
-
- void SetCigParametersTest(
- uint8_t cig_id,
- uint32_t sdu_interval_m_to_s,
- uint32_t sdu_interval_s_to_m,
- uint8_t ft_m_to_s,
- uint8_t ft_s_to_m,
- uint16_t iso_interval,
- hci::ClockAccuracy peripherals_clock_accuracy,
- hci::Packing packing,
- hci::Enable framing,
- uint16_t max_transport_latency_m_to_s,
- uint16_t max_transport_latency_s_to_m,
- const std::vector<hci::LeCisParametersTestConfig>& cis_config,
- SetCigParametersCallback command_complete_callback);
- void SetCigParametersTestComplete(
- uint8_t cig_id,
- const std::vector<hci::LeCisParametersTestConfig>& cis_configs,
- SetCigParametersCallback command_complete_callback,
- hci::CommandCompleteView command_complete);
-
- void LeCreateCis(std::vector<std::pair<uint16_t, uint16_t>> cis_and_acl_handles);
-
- void RemoveCig(uint8_t cig_id);
- void RemoveCigComplete(hci::CommandCompleteView command_complete);
-
- void SendIsoPacket(uint16_t cis_handle, std::vector<uint8_t> packet);
- void OnIncomingPacket();
-
- bool IsKnownCig(uint8_t cig_id) {
- return find_if(iso_connections_.begin(), iso_connections_.end(), [cig_id](const IsochronousConnection& c) {
- return c.cig_id == cig_id;
- }) != iso_connections_.end();
- }
-
- private:
- os::Handler* iso_handler_;
- hci::HciLayer* hci_layer_;
- hci::LeIsoInterface* hci_le_iso_interface_;
- std::unique_ptr<os::EnqueueBuffer<bluetooth::hci::IsoBuilder>> iso_enqueue_buffer_;
- hci::Controller* controller_ __attribute__((unused));
- std::list<IsochronousConnection> iso_connections_;
- CisEstablishedCallback cis_established_callback;
- IsoDataCallback iso_data_callback;
-};
-} // namespace internal
-} // namespace iso
-} // namespace bluetooth
diff --git a/gd/iso/iso_manager.cc b/gd/iso/iso_manager.cc
deleted file mode 100644
index c072bae56..000000000
--- a/gd/iso/iso_manager.cc
+++ /dev/null
@@ -1,104 +0,0 @@
-/*
- *
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-#include "iso_manager.h"
-
-#include "os/log.h"
-
-namespace bluetooth {
-namespace iso {
-
-void IsoManager::RegisterIsoEstablishedCallback(CisEstablishedCallback cb) {
- iso_handler_->CallOn(iso_manager_impl_, &internal::IsoManagerImpl::RegisterIsoEstablishedCallback, cb);
-}
-
-void IsoManager::RegisterIsoDataCallback(IsoDataCallback cb) {
- iso_handler_->CallOn(iso_manager_impl_, &internal::IsoManagerImpl::RegisterIsoDataCallback, cb);
-}
-
-void IsoManager::SetCigParameters(
- uint8_t cig_id,
- uint32_t sdu_interval_m_to_s,
- uint32_t sdu_interval_s_to_m,
- hci::ClockAccuracy peripherals_clock_accuracy,
- hci::Packing packing,
- hci::Enable framing,
- uint16_t max_transport_latency_m_to_s,
- uint16_t max_transport_latency_s_to_m,
- std::vector<hci::CisParametersConfig> cis_config,
- SetCigParametersCallback command_complete_callback) {
- iso_handler_->CallOn(
- iso_manager_impl_,
- &internal::IsoManagerImpl::SetCigParameters,
- cig_id,
- sdu_interval_m_to_s,
- sdu_interval_s_to_m,
- peripherals_clock_accuracy,
- packing,
- framing,
- max_transport_latency_m_to_s,
- max_transport_latency_s_to_m,
- cis_config,
- std::move(command_complete_callback));
-}
-
-void IsoManager::SetCigParametersTest(
- uint8_t cig_id,
- uint32_t sdu_interval_m_to_s,
- uint32_t sdu_interval_s_to_m,
- uint8_t ft_m_to_s,
- uint8_t ft_s_to_m,
- uint16_t iso_interval,
- hci::ClockAccuracy peripherals_clock_accuracy,
- hci::Packing packing,
- hci::Enable framing,
- uint16_t max_transport_latency_m_to_s,
- uint16_t max_transport_latency_s_to_m,
- std::vector<hci::LeCisParametersTestConfig> cis_config,
- SetCigParametersCallback command_complete_callback) {
- iso_handler_->CallOn(
- iso_manager_impl_,
- &internal::IsoManagerImpl::SetCigParametersTest,
- cig_id,
- sdu_interval_m_to_s,
- sdu_interval_s_to_m,
- ft_m_to_s,
- ft_s_to_m,
- iso_interval,
- peripherals_clock_accuracy,
- packing,
- framing,
- max_transport_latency_m_to_s,
- max_transport_latency_s_to_m,
- cis_config,
- std::move(command_complete_callback));
-}
-
-void IsoManager::LeCreateCis(std::vector<std::pair<uint16_t, uint16_t>> cis_and_acl_handles) {
- iso_handler_->CallOn(iso_manager_impl_, &internal::IsoManagerImpl::LeCreateCis, cis_and_acl_handles);
-}
-
-void IsoManager::RemoveCig(uint8_t cig_id) {
- iso_handler_->CallOn(iso_manager_impl_, &internal::IsoManagerImpl::RemoveCig, cig_id);
-}
-
-void IsoManager::SendIsoPacket(uint16_t cis_handle, std::vector<uint8_t> packet) {
- iso_handler_->CallOn(iso_manager_impl_, &internal::IsoManagerImpl::SendIsoPacket, cis_handle, packet);
-}
-
-} // namespace iso
-} // namespace bluetooth
diff --git a/gd/iso/iso_manager.h b/gd/iso/iso_manager.h
deleted file mode 100644
index d38405c4e..000000000
--- a/gd/iso/iso_manager.h
+++ /dev/null
@@ -1,87 +0,0 @@
-/*
- *
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include <memory>
-#include <vector>
-
-#include "hci/address_with_type.h"
-#include "iso/internal/iso_manager_impl.h"
-#include "os/handler.h"
-
-namespace bluetooth {
-namespace iso {
-using SetCigParametersCallback = common::ContextualOnceCallback<void(std::vector<uint16_t> /* connectino handles*/)>;
-using CisEstablishedCallback = common::ContextualCallback<void(uint16_t)>;
-using IsoDataCallback = common::ContextualCallback<void(std::unique_ptr<hci::IsoView>)>;
-
-/**
- * Manages the iso attributes, pairing, bonding of devices, and the
- * encryption/decryption of communications.
- */
-class IsoManager {
- public:
- friend class IsoModule;
-
- void RegisterIsoEstablishedCallback(CisEstablishedCallback cb);
- void RegisterIsoDataCallback(IsoDataCallback cb);
-
- void SetCigParameters(
- uint8_t cig_id,
- uint32_t sdu_interval_m_to_s,
- uint32_t sdu_interval_s_to_m,
- hci::ClockAccuracy peripherals_clock_accuracy,
- hci::Packing packing,
- hci::Enable framing,
- uint16_t max_transport_latency_m_to_s,
- uint16_t max_transport_latency_s_to_m,
- std::vector<hci::CisParametersConfig> cis_config,
- SetCigParametersCallback command_complete_callback);
- void SetCigParametersTest(
- uint8_t cig_id,
- uint32_t sdu_interval_m_to_s,
- uint32_t sdu_interval_s_to_m,
- uint8_t ft_m_to_s,
- uint8_t ft_s_to_m,
- uint16_t iso_interval,
- hci::ClockAccuracy peripherals_clock_accuracy,
- hci::Packing packing,
- hci::Enable framing,
- uint16_t max_transport_latency_m_to_s,
- uint16_t max_transport_latency_s_to_m,
- std::vector<hci::LeCisParametersTestConfig> cis_config,
- SetCigParametersCallback command_complete_callback);
-
- void LeCreateCis(std::vector<std::pair<uint16_t, uint16_t>> cis_and_acl_handles);
- void RemoveCig(uint8_t cig_id);
-
- void SendIsoPacket(uint16_t cis_handle, std::vector<uint8_t> packet);
-
- protected:
- IsoManager(os::Handler* iso_handler, internal::IsoManagerImpl* iso_manager_impl)
- : iso_handler_(iso_handler), iso_manager_impl_(iso_manager_impl) {}
-
- private:
- os::Handler* iso_handler_ = nullptr;
- internal::IsoManagerImpl* iso_manager_impl_;
- DISALLOW_COPY_AND_ASSIGN(IsoManager);
-};
-
-} // namespace iso
-} // namespace bluetooth
diff --git a/gd/iso/iso_module.cc b/gd/iso/iso_module.cc
deleted file mode 100644
index 367884181..000000000
--- a/gd/iso/iso_module.cc
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "iso"
-
-#include <memory>
-#include "module.h"
-#include "os/handler.h"
-#include "os/log.h"
-
-#include "hci/acl_manager.h"
-#include "hci/hci_layer.h"
-#include "iso/iso_module.h"
-
-namespace bluetooth {
-namespace iso {
-
-const ModuleFactory IsoModule::Factory = ModuleFactory([]() { return new IsoModule(); });
-
-struct IsoModule::impl {
- impl(os::Handler* iso_handler, hci::HciLayer* hci_layer, hci::Controller* controller)
- : iso_handler_(iso_handler), hci_layer_(hci_layer), controller_(controller) {}
-
- os::Handler* iso_handler_;
- hci::HciLayer* hci_layer_;
- hci::Controller* controller_;
-
- internal::IsoManagerImpl iso_manager_impl{iso_handler_, hci_layer_, controller_};
-};
-
-void IsoModule::ListDependencies(ModuleList* list) {
- list->add<hci::HciLayer>();
- list->add<hci::Controller>();
-}
-
-void IsoModule::Start() {
- pimpl_ = std::make_unique<impl>(GetHandler(), GetDependency<hci::HciLayer>(), GetDependency<hci::Controller>());
-}
-
-void IsoModule::Stop() {
- pimpl_.reset();
-}
-
-std::string IsoModule::ToString() const {
- return "Iso Module";
-}
-
-std::unique_ptr<IsoManager> IsoModule::GetIsoManager() {
- return std::unique_ptr<IsoManager>(new IsoManager(pimpl_->iso_handler_, &pimpl_->iso_manager_impl));
-}
-
-} // namespace iso
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/l2cap/Android.bp b/gd/l2cap/Android.bp
index bdec3a653..c04a9d30b 100644
--- a/gd/l2cap/Android.bp
+++ b/gd/l2cap/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothL2capSources",
srcs: [
@@ -22,7 +13,6 @@ filegroup {
"classic/internal/link.cc",
"classic/internal/link_manager.cc",
"classic/internal/signalling_manager.cc",
- "classic/internal/dumpsys_helper.cc",
"classic/l2cap_classic_module.cc",
"dynamic_channel.cc",
"internal/basic_mode_channel_data_controller.cc",
@@ -34,13 +24,11 @@ filegroup {
"internal/receiver.cc",
"internal/scheduler_fifo.cc",
"internal/sender.cc",
- "le/dynamic_channel.cc",
"le/dynamic_channel_manager.cc",
"le/dynamic_channel_service.cc",
"le/fixed_channel.cc",
"le/fixed_channel_manager.cc",
"le/fixed_channel_service.cc",
- "le/link_options.cc",
"le/internal/dynamic_channel_service_manager_impl.cc",
"le/internal/fixed_channel_impl.cc",
"le/internal/fixed_channel_service_manager_impl.cc",
@@ -69,17 +57,11 @@ filegroup {
"internal/receiver_test.cc",
"internal/scheduler_fifo_test.cc",
"internal/sender_test.cc",
+ "l2cap_packet_test.cc",
"le/internal/dynamic_channel_service_manager_test.cc",
"le/internal/fixed_channel_impl_test.cc",
"le/internal/fixed_channel_service_manager_test.cc",
"le/internal/link_manager_test.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothL2capUnitTestSources",
- srcs: [
- "l2cap_packet_test.cc",
"signal_id_test.cc",
],
}
@@ -88,7 +70,6 @@ filegroup {
name: "BluetoothFacade_l2cap_layer",
srcs: [
"classic/facade.cc",
- "le/facade.cc",
],
}
diff --git a/gd/l2cap/BUILD.gn b/gd/l2cap/BUILD.gn
deleted file mode 100644
index f5350f505..000000000
--- a/gd/l2cap/BUILD.gn
+++ /dev/null
@@ -1,60 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-source_set("BluetoothL2capSources") {
- sources = [
- "classic/dynamic_channel_manager.cc",
- "classic/dynamic_channel_service.cc",
- "classic/fixed_channel.cc",
- "classic/fixed_channel_manager.cc",
- "classic/fixed_channel_service.cc",
- "classic/internal/dumpsys_helper.cc",
- "classic/internal/dynamic_channel_service_manager_impl.cc",
- "classic/internal/fixed_channel_impl.cc",
- "classic/internal/fixed_channel_service_manager_impl.cc",
- "classic/internal/link.cc",
- "classic/internal/link_manager.cc",
- "classic/internal/signalling_manager.cc",
- "classic/l2cap_classic_module.cc",
- "dynamic_channel.cc",
- "fcs.cc",
- "internal/basic_mode_channel_data_controller.cc",
- "internal/data_pipeline_manager.cc",
- "internal/dynamic_channel_allocator.cc",
- "internal/dynamic_channel_impl.cc",
- "internal/enhanced_retransmission_mode_channel_data_controller.cc",
- "internal/le_credit_based_channel_data_controller.cc",
- "internal/receiver.cc",
- "internal/scheduler_fifo.cc",
- "internal/sender.cc",
- "le/dynamic_channel.cc",
- "le/dynamic_channel_manager.cc",
- "le/dynamic_channel_service.cc",
- "le/fixed_channel.cc",
- "le/fixed_channel_manager.cc",
- "le/fixed_channel_service.cc",
- "le/internal/dynamic_channel_service_manager_impl.cc",
- "le/internal/fixed_channel_impl.cc",
- "le/internal/fixed_channel_service_manager_impl.cc",
- "le/internal/link.cc",
- "le/internal/link_manager.cc",
- "le/internal/signalling_manager.cc",
- "le/l2cap_le_module.cc",
- "le/link_options.cc",
- ]
-
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ "//bt/gd:gd_default_deps" ]
-}
diff --git a/gd/l2cap/cid.h b/gd/l2cap/cid.h
index 9a21abb03..729272c6e 100644
--- a/gd/l2cap/cid.h
+++ b/gd/l2cap/cid.h
@@ -36,5 +36,7 @@ constexpr Cid kLeSignallingCid = 5;
constexpr Cid kSmpCid = 6;
constexpr Cid kSmpBrCid = 7;
+constexpr Cid kClassicPairingTriggerCid = kLastFixedChannel - 1;
+
} // namespace l2cap
} // namespace bluetooth
diff --git a/gd/l2cap/classic/cert/cert_l2cap.py b/gd/l2cap/classic/cert/cert_l2cap.py
deleted file mode 100644
index 88e09b820..000000000
--- a/gd/l2cap/classic/cert/cert_l2cap.py
+++ /dev/null
@@ -1,384 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import logging
-
-from cert.behavior import IHasBehaviors, SingleArgumentBehavior, ReplyStage
-from cert.closable import Closable
-from cert.closable import safeClose
-from cert.py_acl_manager import PyAclManager
-from cert.truth import assertThat
-import bluetooth_packets_python3 as bt_packets
-from bluetooth_packets_python3 import l2cap_packets
-from bluetooth_packets_python3 import RawBuilder
-from bluetooth_packets_python3.l2cap_packets import CommandCode
-from bluetooth_packets_python3.l2cap_packets import Final
-from bluetooth_packets_python3.l2cap_packets import SegmentationAndReassembly
-from bluetooth_packets_python3.l2cap_packets import SupervisoryFunction
-from bluetooth_packets_python3.l2cap_packets import Poll
-from bluetooth_packets_python3.l2cap_packets import InformationRequestInfoType
-from bluetooth_packets_python3.l2cap_packets import ConfigurationResponseResult
-from cert.event_stream import FilteringEventStream
-from cert.event_stream import IEventStream
-from cert.matchers import L2capMatchers
-from cert.captures import L2capCaptures
-
-
-class CertL2capChannel(IEventStream):
-
- def __init__(self, device, scid, dcid, acl_stream, acl, control_channel, fcs=None):
- self._device = device
- self._scid = scid
- self._dcid = dcid
- self._acl_stream = acl_stream
- self._acl = acl
- self._control_channel = control_channel
- self._config_rsp_received = False
- self._config_rsp_sent = False
- if fcs == l2cap_packets.FcsType.DEFAULT:
- self._our_acl_view = FilteringEventStream(acl_stream, L2capMatchers.ExtractBasicFrameWithFcs(scid))
- else:
- self._our_acl_view = FilteringEventStream(acl_stream, L2capMatchers.ExtractBasicFrame(scid))
-
- def get_event_queue(self):
- return self._our_acl_view.get_event_queue()
-
- def is_configured(self):
- return self._config_rsp_received and self._config_rsp_sent
-
- def send(self, packet):
- frame = l2cap_packets.BasicFrameBuilder(self._dcid, packet)
- self._acl.send(frame.Serialize())
-
- def send_i_frame(self,
- tx_seq,
- req_seq,
- f=Final.NOT_SET,
- sar=SegmentationAndReassembly.UNSEGMENTED,
- payload=None,
- fcs=False):
- if fcs == l2cap_packets.FcsType.DEFAULT:
- frame = l2cap_packets.EnhancedInformationFrameWithFcsBuilder(self._dcid, tx_seq, f, req_seq, sar, payload)
- else:
- frame = l2cap_packets.EnhancedInformationFrameBuilder(self._dcid, tx_seq, f, req_seq, sar, payload)
- self._acl.send(frame.Serialize())
-
- def send_s_frame(self, req_seq, s=SupervisoryFunction.RECEIVER_READY, p=Poll.NOT_SET, f=Final.NOT_SET):
- frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(self._dcid, s, p, f, req_seq)
- self._acl.send(frame.Serialize())
-
- def config_request_for_me(self):
- return L2capMatchers.ConfigurationRequest(self._scid)
-
- def send_configure_request(self, options, sid=2, continuation=l2cap_packets.Continuation.END):
- assertThat(self._scid).isNotEqualTo(1)
- request = l2cap_packets.ConfigurationRequestBuilder(sid, self._dcid, continuation, options)
- self._control_channel.send(request)
-
- def _send_information_request(self, type):
- assertThat(self._scid).isEqualTo(1)
- signal_id = 3
- information_request = l2cap_packets.InformationRequestBuilder(signal_id, type)
- self.send(information_request)
-
- def send_extended_features_request(self):
- self._send_information_request(InformationRequestInfoType.EXTENDED_FEATURES_SUPPORTED)
-
- def verify_configuration_request_and_respond(self, result=ConfigurationResponseResult.SUCCESS, options=None):
- request_capture = L2capCaptures.ConfigurationRequest(self._scid)
- assertThat(self._control_channel).emits(request_capture)
- request = request_capture.get()
- sid = request.GetIdentifier()
- if options is None:
- options = []
- config_response = l2cap_packets.ConfigurationResponseBuilder(sid, self._dcid, l2cap_packets.Continuation.END,
- result, options)
- self._control_channel.send(config_response)
-
- def send_configuration_response(self, request, result=ConfigurationResponseResult.SUCCESS, options=None):
- sid = request.GetIdentifier()
- if options is None:
- options = []
- config_response = l2cap_packets.ConfigurationResponseBuilder(sid, self._dcid, l2cap_packets.Continuation.END,
- result, options)
- self._control_channel.send(config_response)
- self._config_rsp_sent = True
-
- def verify_configuration_response(self, result=ConfigurationResponseResult.SUCCESS):
- assertThat(self._control_channel).emits(L2capMatchers.ConfigurationResponse(result))
-
- def disconnect_and_verify(self):
- assertThat(self._scid).isNotEqualTo(1)
- self._control_channel.send(l2cap_packets.DisconnectionRequestBuilder(1, self._dcid, self._scid))
-
- assertThat(self._control_channel).emits(L2capMatchers.DisconnectionResponse(self._scid, self._dcid))
-
- def verify_disconnect_request(self):
- assertThat(self._control_channel).emits(L2capMatchers.DisconnectionRequest(self._dcid, self._scid))
-
-
-class CertL2capControlChannelBehaviors(object):
-
- def __init__(self, parent):
- self.on_config_req_behavior = SingleArgumentBehavior(
- lambda: CertL2capControlChannelBehaviors.CertReplyStage(parent))
-
- def on_config_req(self, matcher):
- return self.on_config_req_behavior.begin(matcher)
-
- class CertReplyStage(ReplyStage):
-
- def __init__(self, parent):
- self.parent = parent
-
- def send_configuration_response(self, result=ConfigurationResponseResult.SUCCESS, options=None):
- self._commit(lambda request: self._send_configuration_response(request, result, options))
- return self
-
- def _send_configuration_response(self, request, result=ConfigurationResponseResult.SUCCESS, options=None):
- dcid = request.GetDestinationCid()
- if dcid not in self.parent.scid_to_channel:
- logging.warning("Received config request with unknown dcid")
- return
- self.parent.scid_to_channel[dcid].send_configuration_response(request, result, options)
-
-
-class CertL2cap(Closable, IHasBehaviors):
-
- def __init__(self, device):
- self._device = device
- self._acl_manager = PyAclManager(device)
- self._acl = None
-
- self.control_table = {
- CommandCode.CONNECTION_RESPONSE: self._on_connection_response_default,
- CommandCode.CONFIGURATION_REQUEST: self._on_configuration_request_default,
- CommandCode.CONFIGURATION_RESPONSE: self._on_configuration_response_default,
- CommandCode.DISCONNECTION_REQUEST: self._on_disconnection_request_default,
- CommandCode.DISCONNECTION_RESPONSE: self._on_disconnection_response_default,
- CommandCode.INFORMATION_REQUEST: self._on_information_request_default,
- CommandCode.INFORMATION_RESPONSE: self._on_information_response_default
- }
-
- self.scid_to_channel = {}
-
- self.support_ertm = True
- self.support_fcs = True
-
- self._control_behaviors = CertL2capControlChannelBehaviors(self)
- self._control_behaviors.on_config_req_behavior.set_default(self._send_configuration_response_default)
-
- def close(self):
- self._acl_manager.close()
- safeClose(self._acl)
-
- def get_behaviors(self):
- return self._control_behaviors
-
- def connect_acl(self, remote_addr):
- self._acl_manager.initiate_connection(remote_addr)
- self._acl = self._acl_manager.complete_outgoing_connection()
- self.control_channel = CertL2capChannel(
- self._device, 1, 1, self._acl.acl_stream, self._acl, control_channel=None)
- self._acl.acl_stream.register_callback(self._handle_control_packet)
-
- def accept_incoming_connection(self):
- self._acl_manager.listen_for_an_incoming_connection()
- self._acl = self._acl_manager.complete_incoming_connection()
-
- def open_channel(self, signal_id, psm, scid, fcs=None):
- self.control_channel.send(l2cap_packets.ConnectionRequestBuilder(signal_id, psm, scid))
-
- response = L2capCaptures.ConnectionResponse(scid)
- assertThat(self.control_channel).emits(response)
- channel = CertL2capChannel(self._device, scid,
- response.get().GetDestinationCid(), self._acl.acl_stream, self._acl,
- self.control_channel, fcs)
- self.scid_to_channel[scid] = channel
-
- return channel
-
- def verify_and_respond_open_channel_from_remote(self, psm=0x33, scid=None, fcs=None):
-
- request = L2capCaptures.ConnectionRequest(psm)
- assertThat(self.control_channel).emits(request)
-
- sid = request.get().GetIdentifier()
- dcid = request.get().GetSourceCid()
- if scid is None or scid in self.scid_to_channel:
- scid = dcid
- channel = CertL2capChannel(self._device, scid, dcid, self._acl.acl_stream, self._acl, self.control_channel, fcs)
- self.scid_to_channel[scid] = channel
-
- connection_response = l2cap_packets.ConnectionResponseBuilder(
- sid, scid, dcid, l2cap_packets.ConnectionResponseResult.SUCCESS,
- l2cap_packets.ConnectionResponseStatus.NO_FURTHER_INFORMATION_AVAILABLE)
- self.control_channel.send(connection_response)
-
- return channel
-
- def verify_and_respond_open_channel_from_remote_and_send_config_req(self, psm=0x33):
- """
- Verify a connection request, and send a combo packet of connection response and configuration request
- """
- request = L2capCaptures.ConnectionRequest(psm)
- assertThat(self.control_channel).emits(request)
-
- sid = request.get().GetIdentifier()
- dcid = request.get().GetSourceCid()
- scid = dcid
- channel = CertL2capChannel(self._device, scid, dcid, self._acl.acl_stream, self._acl, self.control_channel)
- self.scid_to_channel[scid] = channel
-
- # Connection response and config request combo packet
- conn_rsp_and_config_req = RawBuilder([
- 0x03, sid, 0x08, 0x00, dcid, 0x00, dcid, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, sid + 1, 0x04, 0x00, dcid,
- 0x00, 0x00, 0x00
- ])
- self.control_channel.send(conn_rsp_and_config_req)
-
- return channel
-
- # prefer to use channel abstraction instead, if at all possible
- def send_acl(self, packet):
- self._acl.send(packet.Serialize())
-
- def get_control_channel(self):
- return self.control_channel
-
- # Disable ERTM when exchange extened feature
- def claim_ertm_unsupported(self):
- self.support_ertm = False
-
- def _on_connection_response_default(self, l2cap_control_view):
- pass
-
- def _on_configuration_request_default(self, l2cap_control_view):
- request = l2cap_packets.ConfigurationRequestView(l2cap_control_view)
- dcid = request.GetDestinationCid()
- if dcid not in self.scid_to_channel:
- logging.warning("Received config request with unknown dcid")
- return
- self._control_behaviors.on_config_req_behavior.run(request)
-
- def _send_configuration_response_default(self, captured_request_view):
- dcid = captured_request_view.GetDestinationCid()
- if dcid not in self.scid_to_channel:
- return
- self.scid_to_channel[dcid].send_configuration_response(captured_request_view)
-
- @staticmethod
- def config_option_basic_explicit(mtu=642):
- mtu_opt = l2cap_packets.MtuConfigurationOption()
- mtu_opt.mtu = mtu
- rfc_opt = l2cap_packets.RetransmissionAndFlowControlConfigurationOption()
- rfc_opt.mode = l2cap_packets.RetransmissionAndFlowControlModeOption.L2CAP_BASIC
- return [mtu_opt, rfc_opt]
-
- @staticmethod
- def config_option_mtu_explicit(mtu=642):
- mtu_opt = l2cap_packets.MtuConfigurationOption()
- mtu_opt.mtu = mtu
- return [mtu_opt]
-
- @staticmethod
- def config_option_ertm(mtu=642,
- fcs=None,
- max_transmit=10,
- mps=1010,
- tx_window_size=10,
- monitor_time_out=2000,
- retransmission_time_out=1000):
- result = []
- mtu_opt = l2cap_packets.MtuConfigurationOption()
- mtu_opt.mtu = mtu
- result.append(mtu_opt)
- if fcs is not None:
- fcs_opt = l2cap_packets.FrameCheckSequenceOption()
- fcs_opt.fcs_type = fcs
- result.append(fcs_opt)
- rfc_opt = l2cap_packets.RetransmissionAndFlowControlConfigurationOption()
- rfc_opt.mode = l2cap_packets.RetransmissionAndFlowControlModeOption.ENHANCED_RETRANSMISSION
- rfc_opt.tx_window_size = tx_window_size
- rfc_opt.max_transmit = max_transmit
- rfc_opt.retransmission_time_out = retransmission_time_out
- rfc_opt.monitor_time_out = monitor_time_out
- rfc_opt.maximum_pdu_size = mps
- result.append(rfc_opt)
- return result
-
- @staticmethod
- def config_option_ertm_with_max_transmit_one():
- return CertL2cap.config_option_ertm(max_transmit=1)
-
- @staticmethod
- def config_option_ertm_with_mps(mps=1010):
- return CertL2cap.config_option_ertm(mps=mps)
-
- def _on_configuration_response_default(self, l2cap_control_view):
- response = l2cap_packets.ConfigurationResponseView(l2cap_control_view)
- scid = response.GetSourceCid()
- if scid not in self.scid_to_channel:
- logging.warning("Received config request with unknown dcid")
- return
- result = response.GetResult()
- if result == ConfigurationResponseResult.SUCCESS:
- self.scid_to_channel[scid]._config_rsp_received = True
-
- def _on_disconnection_request_default(self, l2cap_control_view):
- disconnection_request = l2cap_packets.DisconnectionRequestView(l2cap_control_view)
- sid = disconnection_request.GetIdentifier()
- scid = disconnection_request.GetSourceCid()
- dcid = disconnection_request.GetDestinationCid()
- disconnection_response = l2cap_packets.DisconnectionResponseBuilder(sid, dcid, scid)
- self.control_channel.send(disconnection_response)
-
- def _on_disconnection_response_default(self, l2cap_control_view):
- pass
-
- def _on_information_request_default(self, l2cap_control_view):
- information_request = l2cap_packets.InformationRequestView(l2cap_control_view)
- sid = information_request.GetIdentifier()
- information_type = information_request.GetInfoType()
- if information_type == l2cap_packets.InformationRequestInfoType.CONNECTIONLESS_MTU:
- response = l2cap_packets.InformationResponseConnectionlessMtuBuilder(
- sid, l2cap_packets.InformationRequestResult.SUCCESS, 100)
- self.control_channel.send(response)
- return
- if information_type == l2cap_packets.InformationRequestInfoType.EXTENDED_FEATURES_SUPPORTED:
- response = l2cap_packets.InformationResponseExtendedFeaturesBuilder(
- sid, l2cap_packets.InformationRequestResult.SUCCESS, 0, 0, 0, self.support_ertm, 0, self.support_fcs, 0,
- 0, 0, 0, 0)
- self.control_channel.send(response)
- return
- if information_type == l2cap_packets.InformationRequestInfoType.FIXED_CHANNELS_SUPPORTED:
- response = l2cap_packets.InformationResponseFixedChannelsBuilder(
- sid, l2cap_packets.InformationRequestResult.SUCCESS, 2)
- self.control_channel.send(response)
- return
-
- def _on_information_response_default(self, l2cap_control_view):
- pass
-
- def _handle_control_packet(self, l2cap_packet):
- packet_bytes = l2cap_packet.payload
- l2cap_view = l2cap_packets.BasicFrameView(bt_packets.PacketViewLittleEndian(list(packet_bytes)))
- if l2cap_view.GetChannelId() != 1:
- return
- l2cap_control_view = l2cap_packets.ControlView(l2cap_view.GetPayload())
- fn = self.control_table.get(l2cap_control_view.GetCode())
- if fn is not None:
- fn(l2cap_control_view)
diff --git a/gd/l2cap/classic/cert/l2cap_performance_test.py b/gd/l2cap/classic/cert/l2cap_performance_test.py
deleted file mode 100644
index 9c387eec3..000000000
--- a/gd/l2cap/classic/cert/l2cap_performance_test.py
+++ /dev/null
@@ -1,187 +0,0 @@
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from datetime import datetime, timedelta
-
-from bluetooth_packets_python3 import RawBuilder
-from cert.matchers import L2capMatchers
-from cert.truth import assertThat
-from cert.performance_test_logger import PerformanceTestLogger
-from l2cap.classic.cert.cert_l2cap import CertL2cap
-from l2cap.classic.cert.l2cap_test import L2capTestBase
-from l2cap.classic.facade_pb2 import RetransmissionFlowControlMode
-from bluetooth_packets_python3.l2cap_packets import FcsType
-from bluetooth_packets_python3.l2cap_packets import SupervisoryFunction
-
-
-class L2capPerformanceTest(L2capTestBase):
-
- def setup_test(self):
- super().setup_test()
- self.performance_test_logger = PerformanceTestLogger()
-
- def teardown_test(self):
- super().teardown_test()
-
- def _basic_mode_tx(self, mtu, packets):
- """
- Send the specified number of packets and return the time interval in ms.
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- self.performance_test_logger.start_interval("TX")
- for _ in range(packets):
- dut_channel.send(b'a' * mtu)
- assertThat(cert_channel).emits(
- L2capMatchers.Data(b'a' * mtu), at_least_times=packets, timeout=timedelta(seconds=60))
- self.performance_test_logger.end_interval("TX")
-
- duration = self.performance_test_logger.get_duration_of_intervals("TX")[0]
- self.log.info("Duration: %s" % str(duration))
-
- return duration
-
- def _basic_mode_tx_fixed_interval(self, mtu, interval=timedelta(seconds=10), batch_size=20):
- """
- Send packets as much as possible over a certain interval, and return the
- number of packets sent
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- start_time = datetime.now()
- end_time = start_time + interval
- packets_sent = 0
- while datetime.now() < end_time:
- for _ in range(batch_size):
- dut_channel.send(b'a' * mtu)
- packets_sent += batch_size
- assertThat(cert_channel).emits(L2capMatchers.Data(b'a' * mtu), at_least_times=batch_size)
-
- return packets_sent
-
- def _basic_mode_rx(self, mtu, packets):
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- self.performance_test_logger.start_interval("RX")
- data = b"a" * mtu
- data_packet = RawBuilder([x for x in data])
- for _ in range(packets):
- cert_channel.send(data_packet)
- assertThat(dut_channel).emits(
- L2capMatchers.PacketPayloadRawData(data), at_least_times=packets, timeout=timedelta(seconds=60))
- self.performance_test_logger.end_interval("RX")
-
- duration = self.performance_test_logger.get_duration_of_intervals("RX")[0]
- self.log.info("Duration: %s" % str(duration))
-
- def _ertm_mode_tx(self, mtu, packets, tx_window_size=10):
- """
- Send the specified number of packets and return the time interval in ms.
- """
- # Make sure that number of packets is a multiple of tx_window_size
- packets = packets // tx_window_size * tx_window_size
- # For ERTM TX test, we have to do it sequentially because cert needs to ack
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, tx_window_size=tx_window_size)
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM,
- fcs=FcsType.NO_FCS,
- req_config_options=config,
- rsp_config_options=config)
-
- self.performance_test_logger.start_interval("TX")
- for i in range(packets):
- dut_channel.send(b'a' * mtu)
- if i % tx_window_size == tx_window_size - 1:
- assertThat(cert_channel).emits(L2capMatchers.IFrame(payload=b'a' * mtu), at_least_times=tx_window_size)
- cert_channel.send_s_frame(req_seq=(i + 1) % 64, s=SupervisoryFunction.RECEIVER_READY)
-
- self.performance_test_logger.end_interval("TX")
-
- duration = self.performance_test_logger.get_duration_of_intervals("TX")[0]
- self.log.info("Duration: %s" % str(duration))
-
- return duration
-
- def _ertm_mode_rx(self, mtu, packets, tx_window_size=10):
- # Make sure that number of packets is a multiple of tx_window_size
- packets = packets // tx_window_size * tx_window_size
-
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, tx_window_size=tx_window_size)
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM,
- fcs=FcsType.NO_FCS,
- req_config_options=config,
- rsp_config_options=config)
-
- data = b"a" * mtu
- data_packet = RawBuilder([x for x in data])
- self.performance_test_logger.start_interval("RX")
- for i in range(packets):
- cert_channel.send_i_frame(tx_seq=i % 64, req_seq=0, payload=data_packet)
- if i % tx_window_size == (tx_window_size - 1):
- assertThat(cert_channel).emits(L2capMatchers.SFrame(req_seq=(i + 1) % 64))
- self.performance_test_logger.end_interval("RX")
-
- duration = self.performance_test_logger.get_duration_of_intervals("RX")[0]
- self.log.info("Duration: %s" % str(duration))
-
- def test_basic_mode_tx_672_100(self):
- duration = self._basic_mode_tx(672, 100)
- assertThat(duration).isWithin(timedelta(seconds=2))
-
- def test_basic_mode_tx_100_100(self):
- duration = self._basic_mode_tx(100, 100)
- assertThat(duration).isWithin(timedelta(seconds=2))
-
- def test_ertm_mode_tx_672_100(self):
- duration = self._ertm_mode_tx(672, 100)
- assertThat(duration).isWithin(timedelta(seconds=5))
-
- def test_basic_mode_rx_672_100(self):
- self._basic_mode_rx(672, 100)
-
- def test_ertm_mode_rx_672_100(self):
- self._ertm_mode_rx(672, 100)
-
- def test_basic_mode_end_to_end_latency(self):
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert()
-
- data = b"a" * 100
- data_packet = RawBuilder([x for x in data])
- for i in range(100):
- self.performance_test_logger.start_interval("RX")
- cert_channel.send(data_packet)
- assertThat(dut_channel).emits(L2capMatchers.PacketPayloadRawData(data))
- self.performance_test_logger.end_interval("RX")
- duration = self.performance_test_logger.get_duration_of_intervals("RX")
- mean = sum(duration, timedelta()) / len(duration)
- self.log.info("Mean: %s" % str(mean))
-
- def test_basic_mode_number_of_packets_10_seconds_672(self):
- number_packets = self._basic_mode_tx_fixed_interval(672)
- # Requiring that 500 packets (20ms period on average) are sent
- self.log.info("Packets sent: %d" % number_packets)
- assertThat(number_packets > 500).isTrue()
diff --git a/gd/l2cap/classic/cert/l2cap_test.py b/gd/l2cap/classic/cert/l2cap_test.py
index 081ee7b6b..3fcb4f168 100644
--- a/gd/l2cap/classic/cert/l2cap_test.py
+++ b/gd/l2cap/classic/cert/l2cap_test.py
@@ -13,1276 +13,2033 @@
# See the License for the specific language governing permissions and
# limitations under the License.
+import time
from datetime import timedelta
-
from mobly import asserts
-from bluetooth_packets_python3 import l2cap_packets
-from bluetooth_packets_python3 import RawBuilder
-from bluetooth_packets_python3.l2cap_packets import FcsType
-from bluetooth_packets_python3.l2cap_packets import Final
-from bluetooth_packets_python3.l2cap_packets import Poll
-from bluetooth_packets_python3.l2cap_packets import SegmentationAndReassembly
-from bluetooth_packets_python3.l2cap_packets import SupervisoryFunction
-from cert.behavior import when, anything, wait_until
-from cert.event_stream import EventStream
-from cert.gd_base_test import GdBaseTestClass
-from cert.matchers import L2capMatchers
-from cert.metadata import metadata
-from cert.py_l2cap import PyL2cap
-from cert.truth import assertThat
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
+from cert.event_asserts import EventAsserts
+from cert.event_callback_stream import EventCallbackStream
from facade import common_pb2
+from facade import rootservice_pb2 as facade_rootservice
from google.protobuf import empty_pb2 as empty_proto
-from l2cap.classic.cert.cert_l2cap import CertL2cap
-from l2cap.classic.facade_pb2 import RetransmissionFlowControlMode
+from l2cap.classic import facade_pb2 as l2cap_facade_pb2
from neighbor.facade import facade_pb2 as neighbor_facade
+from hci.facade import acl_manager_facade_pb2 as acl_manager_facade
+import bluetooth_packets_python3 as bt_packets
+from bluetooth_packets_python3 import hci_packets, l2cap_packets
-# Assemble a sample packet.
-SAMPLE_PACKET_DATA = b"\x19\x26\x08\x17"
-SAMPLE_PACKET = RawBuilder([x for x in SAMPLE_PACKET_DATA])
-
+# Assemble a sample packet. TODO: Use RawBuilder
+SAMPLE_PACKET = l2cap_packets.CommandRejectNotUnderstoodBuilder(1)
-class L2capTestBase(GdBaseTestClass):
- def setup_class(self):
- super().setup_class(dut_module='L2CAP', cert_module='HCI_INTERFACES')
+class L2capTest(GdFacadeOnlyBaseTestClass):
def setup_test(self):
- super().setup_test()
-
- self.dut_address = self.dut.hci_controller.GetMacAddressSimple()
- cert_address = common_pb2.BluetoothAddress(
- address=self.cert.controller_read_only_property.ReadLocalAddress(empty_proto.Empty()).address)
-
- self.dut_l2cap = PyL2cap(self.dut, cert_address)
- self.cert_l2cap = CertL2cap(self.cert)
+ self.device_under_test.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'L2CAP'),))
+ self.cert_device.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI_INTERFACES'),))
+
+ self.device_under_test.wait_channel_ready()
+ self.cert_device.wait_channel_ready()
+
+ self.device_under_test.address = self.device_under_test.hci_controller.GetMacAddress(
+ empty_proto.Empty()).address
+ cert_address = self.cert_device.controller_read_only_property.ReadLocalAddress(
+ empty_proto.Empty()).address
+ self.cert_device.address = cert_address
+ self.dut_address = common_pb2.BluetoothAddress(
+ address=self.device_under_test.address)
+ self.cert_address = common_pb2.BluetoothAddress(
+ address=self.cert_device.address)
+
+ self.device_under_test.neighbor.EnablePageScan(
+ neighbor_facade.EnableMsg(enabled=True))
+
+ self.cert_acl_handle = 0
+
+ self.on_connection_request = None
+ self.on_connection_response = None
+ self.on_configuration_request = None
+ self.on_configuration_response = None
+ self.on_disconnection_request = None
+ self.on_disconnection_response = None
+ self.on_information_request = None
+ self.on_information_response = None
+
+ self.scid_to_dcid = {}
+ self.ertm_tx_window_size = 10
+ self.ertm_max_transmit = 20
+
+ def _on_connection_request_default(self, l2cap_control_view):
+ connection_request_view = l2cap_packets.ConnectionRequestView(
+ l2cap_control_view)
+ sid = connection_request_view.GetIdentifier()
+ cid = connection_request_view.GetSourceCid()
+
+ self.scid_to_dcid[cid] = cid
+
+ connection_response = l2cap_packets.ConnectionResponseBuilder(
+ sid, cid, cid, l2cap_packets.ConnectionResponseResult.SUCCESS,
+ l2cap_packets.ConnectionResponseStatus.
+ NO_FURTHER_INFORMATION_AVAILABLE)
+ connection_response_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, connection_response)
+ self.cert_device.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=self.cert_acl_handle,
+ payload=bytes(connection_response_l2cap.Serialize())))
+ return True
+
+ def _on_connection_response_default(self, l2cap_control_view):
+ connection_response_view = l2cap_packets.ConnectionResponseView(
+ l2cap_control_view)
+ sid = connection_response_view.GetIdentifier()
+ scid = connection_response_view.GetSourceCid()
+ dcid = connection_response_view.GetDestinationCid()
+ self.scid_to_dcid[scid] = dcid
+
+ config_request = l2cap_packets.ConfigurationRequestBuilder(
+ sid + 1, dcid, l2cap_packets.Continuation.END, [])
+ config_request_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, config_request)
+ self.cert_device.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=self.cert_acl_handle,
+ payload=bytes(config_request_l2cap.Serialize())))
+ return True
+
+ def _on_connection_response_use_ertm(self, l2cap_control_view):
+ connection_response_view = l2cap_packets.ConnectionResponseView(
+ l2cap_control_view)
+ sid = connection_response_view.GetIdentifier()
+ scid = connection_response_view.GetSourceCid()
+ dcid = connection_response_view.GetDestinationCid()
+ self.scid_to_dcid[scid] = dcid
+
+ # FIXME: This doesn't work!
+ ertm_option = l2cap_packets.RetransmissionAndFlowControlConfigurationOption(
+ )
+ ertm_option.mode = l2cap_packets.RetransmissionAndFlowControlModeOption.L2CAP_BASIC
+ ertm_option.tx_window_size = self.ertm_tx_window_size
+ ertm_option.max_transmit = self.ertm_max_transmit
+ ertm_option.retransmission_time_out = 2000
+ ertm_option.monitor_time_out = 12000
+ ertm_option.maximum_pdu_size = 1010
+
+ options = [ertm_option]
+
+ config_request = l2cap_packets.ConfigurationRequestBuilder(
+ sid + 1, dcid, l2cap_packets.Continuation.END, options)
+
+ config_request_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, config_request)
+
+ config_packet = bytearray([
+ 0x1a,
+ 0x00,
+ 0x01,
+ 0x00,
+ 0x04,
+ sid + 1,
+ 0x16,
+ 0x00,
+ dcid & 0xff,
+ dcid >> 8,
+ 0x00,
+ 0x00,
+ 0x01,
+ 0x02,
+ 0xa0,
+ 0x02, # MTU
+ 0x04,
+ 0x09,
+ 0x03,
+ self.ertm_tx_window_size,
+ self.ertm_max_transmit,
+ 0xd0,
+ 0x07,
+ 0xe0,
+ 0x2e,
+ 0xf2,
+ 0x03, # ERTM
+ 0x05,
+ 0x01,
+ 0x00 # FCS
+ ])
+
+ self.cert_device.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=self.cert_acl_handle, payload=bytes(config_packet)))
+ return True
+
+ def _on_connection_response_use_ertm_and_fcs(self, l2cap_control_view):
+ connection_response_view = l2cap_packets.ConnectionResponseView(
+ l2cap_control_view)
+ sid = connection_response_view.GetIdentifier()
+ scid = connection_response_view.GetSourceCid()
+ dcid = connection_response_view.GetDestinationCid()
+ self.scid_to_dcid[scid] = dcid
+
+ # FIXME: This doesn't work!
+ ertm_option = l2cap_packets.RetransmissionAndFlowControlConfigurationOption(
+ )
+ ertm_option.mode = l2cap_packets.RetransmissionAndFlowControlModeOption.L2CAP_BASIC
+ ertm_option.tx_window_size = self.ertm_tx_window_size
+ ertm_option.max_transmit = self.ertm_max_transmit
+ ertm_option.retransmission_time_out = 2000
+ ertm_option.monitor_time_out = 12000
+ ertm_option.maximum_pdu_size = 1010
+
+ options = [ertm_option]
+
+ config_request = l2cap_packets.ConfigurationRequestBuilder(
+ sid + 1, dcid, l2cap_packets.Continuation.END, options)
+
+ config_request_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, config_request)
+
+ config_packet = bytearray([
+ 0x1a,
+ 0x00,
+ 0x01,
+ 0x00,
+ 0x04,
+ sid + 1,
+ 0x16,
+ 0x00,
+ dcid & 0xff,
+ dcid >> 8,
+ 0x00,
+ 0x00,
+ 0x01,
+ 0x02,
+ 0xa0,
+ 0x02, # MTU
+ 0x04,
+ 0x09,
+ 0x03,
+ self.ertm_tx_window_size,
+ self.ertm_max_transmit,
+ 0xd0,
+ 0x07,
+ 0xe0,
+ 0x2e,
+ 0xf2,
+ 0x03, # ERTM
+ 0x05,
+ 0x01,
+ 0x01 # FCS
+ ])
+
+ self.cert_device.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=self.cert_acl_handle, payload=bytes(config_packet)))
+ return True
+
+ def _on_configuration_request_default(self, l2cap_control_view):
+ configuration_request = l2cap_packets.ConfigurationRequestView(
+ l2cap_control_view)
+ sid = configuration_request.GetIdentifier()
+ dcid = configuration_request.GetDestinationCid()
+ config_response = l2cap_packets.ConfigurationResponseBuilder(
+ sid, self.scid_to_dcid.get(dcid, 0), l2cap_packets.Continuation.END,
+ l2cap_packets.ConfigurationResponseResult.SUCCESS, [])
+ config_response_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, config_response)
+ self.cert_send_b_frame(config_response_l2cap)
+
+ def _on_configuration_response_default(self, l2cap_control_view):
+ configuration_response = l2cap_packets.ConfigurationResponseView(
+ l2cap_control_view)
+ sid = configuration_response.GetIdentifier()
+
+ def _on_disconnection_request_default(self, l2cap_control_view):
+ disconnection_request = l2cap_packets.DisconnectionRequestView(
+ l2cap_control_view)
+ sid = disconnection_request.GetIdentifier()
+ scid = disconnection_request.GetSourceCid()
+ dcid = disconnection_request.GetDestinationCid()
+ disconnection_response = l2cap_packets.DisconnectionResponseBuilder(
+ sid, dcid, scid)
+ disconnection_response_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, disconnection_response)
+ self.cert_device.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=self.cert_acl_handle,
+ payload=bytes(disconnection_response_l2cap.Serialize())))
+
+ def _on_disconnection_response_default(self, l2cap_control_view):
+ disconnection_response = l2cap_packets.DisconnectionResponseView(
+ l2cap_control_view)
+
+ def _on_information_request_default(self, l2cap_control_view):
+ information_request = l2cap_packets.InformationRequestView(
+ l2cap_control_view)
+ sid = information_request.GetIdentifier()
+ information_type = information_request.GetInfoType()
+ if information_type == l2cap_packets.InformationRequestInfoType.CONNECTIONLESS_MTU:
+ response = l2cap_packets.InformationResponseConnectionlessMtuBuilder(
+ sid, l2cap_packets.InformationRequestResult.SUCCESS, 100)
+ response_l2cap = l2cap_packets.BasicFrameBuilder(1, response)
+ self.cert_device.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=self.cert_acl_handle,
+ payload=bytes(response_l2cap.Serialize())))
+ return
+ if information_type == l2cap_packets.InformationRequestInfoType.EXTENDED_FEATURES_SUPPORTED:
+ response = l2cap_packets.InformationResponseExtendedFeaturesBuilder(
+ sid, l2cap_packets.InformationRequestResult.SUCCESS, 0, 0, 0, 1,
+ 0, 1, 0, 0, 0, 0)
+ response_l2cap = l2cap_packets.BasicFrameBuilder(1, response)
+ self.cert_device.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=self.cert_acl_handle,
+ payload=bytes(response_l2cap.Serialize())))
+ return
+ if information_type == l2cap_packets.InformationRequestInfoType.FIXED_CHANNELS_SUPPORTED:
+ response = l2cap_packets.InformationResponseFixedChannelsBuilder(
+ sid, l2cap_packets.InformationRequestResult.SUCCESS, 2)
+ response_l2cap = l2cap_packets.BasicFrameBuilder(1, response)
+ self.cert_device.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=self.cert_acl_handle,
+ payload=bytes(response_l2cap.Serialize())))
+ return
+
+ def _on_information_response_default(self, l2cap_control_view):
+ information_response = l2cap_packets.InformationResponseView(
+ l2cap_control_view)
def teardown_test(self):
- self.cert_l2cap.close()
- self.dut_l2cap.close()
- super().teardown_test()
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+ self.cert_device.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+
+ def _handle_control_packet(self, l2cap_packet):
+ packet_bytes = l2cap_packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != 1:
+ return
+ l2cap_control_view = l2cap_packets.ControlView(l2cap_view.GetPayload())
+ if l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.CONNECTION_REQUEST:
+ return self.on_connection_request(
+ l2cap_control_view
+ ) if self.on_connection_request else self._on_connection_request_default(
+ l2cap_control_view)
+ if l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.CONNECTION_RESPONSE:
+ return self.on_connection_response(
+ l2cap_control_view
+ ) if self.on_connection_response else self._on_connection_response_default(
+ l2cap_control_view)
+ if l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.CONFIGURATION_REQUEST:
+ return self.on_configuration_request(
+ l2cap_control_view
+ ) if self.on_configuration_request else self._on_configuration_request_default(
+ l2cap_control_view)
+ if l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.CONFIGURATION_RESPONSE:
+ return self.on_configuration_response(
+ l2cap_control_view
+ ) if self.on_configuration_response else self._on_configuration_response_default(
+ l2cap_control_view)
+ if l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.DISCONNECTION_REQUEST:
+ return self.on_disconnection_request(
+ l2cap_control_view
+ ) if self.on_disconnection_request else self._on_disconnection_request_default(
+ l2cap_control_view)
+ if l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.DISCONNECTION_RESPONSE:
+ return self.on_disconnection_response(
+ l2cap_control_view
+ ) if self.on_disconnection_response else self._on_disconnection_response_default(
+ l2cap_control_view)
+ if l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.INFORMATION_REQUEST:
+ return self.on_information_request(
+ l2cap_control_view
+ ) if self.on_information_request else self._on_information_request_default(
+ l2cap_control_view)
+ if l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.INFORMATION_RESPONSE:
+ return self.on_information_response(
+ l2cap_control_view
+ ) if self.on_information_response else self._on_information_response_default(
+ l2cap_control_view)
+ return
+
+ def is_correct_connection_request(self, l2cap_packet):
+ packet_bytes = l2cap_packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != 1:
+ return False
+ l2cap_control_view = l2cap_packets.ControlView(l2cap_view.GetPayload())
+ return l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.CONNECTION_REQUEST
+
+ def is_correct_configuration_response(self, l2cap_packet):
+ packet_bytes = l2cap_packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != 1:
+ return False
+ l2cap_control_view = l2cap_packets.ControlView(l2cap_view.GetPayload())
+ if l2cap_control_view.GetCode(
+ ) != l2cap_packets.CommandCode.CONFIGURATION_RESPONSE:
+ return False
+ configuration_response_view = l2cap_packets.ConfigurationResponseView(
+ l2cap_control_view)
+ return configuration_response_view.GetResult(
+ ) == l2cap_packets.ConfigurationResponseResult.SUCCESS
+
+ def is_correct_configuration_request(self, l2cap_packet):
+ packet_bytes = l2cap_packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != 1:
+ return False
+ l2cap_control_view = l2cap_packets.ControlView(l2cap_view.GetPayload())
+ return l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.CONFIGURATION_REQUEST
+
+ def is_correct_disconnection_request(self, l2cap_packet):
+ packet_bytes = l2cap_packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != 1:
+ return False
+ l2cap_control_view = l2cap_packets.ControlView(l2cap_view.GetPayload())
+ return l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.DISCONNECTION_REQUEST
+
+ def cert_send_b_frame(self, b_frame):
+ self.cert_device.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=self.cert_acl_handle,
+ payload=bytes(b_frame.Serialize())))
+
+ def get_req_seq_from_ertm_s_frame(self, scid, packet):
+ packet_bytes = packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != scid:
+ return False
+ standard_view = l2cap_packets.StandardFrameView(l2cap_view)
+ if standard_view.GetFrameType() == l2cap_packets.FrameType.I_FRAME:
+ return False
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameView(standard_view)
+ return s_frame.GetReqSeq()
+
+ def get_s_from_ertm_s_frame(self, scid, packet):
+ packet_bytes = packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != scid:
+ return False
+ standard_view = l2cap_packets.StandardFrameView(l2cap_view)
+ if standard_view.GetFrameType() == l2cap_packets.FrameType.I_FRAME:
+ return False
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameView(standard_view)
+ return s_frame.GetS()
+
+ def get_p_from_ertm_s_frame(self, scid, packet):
+ packet_bytes = packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != scid:
+ return False
+ standard_view = l2cap_packets.StandardFrameView(l2cap_view)
+ if standard_view.GetFrameType() == l2cap_packets.FrameType.I_FRAME:
+ return False
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameView(standard_view)
+ return s_frame.GetP()
+
+ def get_f_from_ertm_s_frame(self, scid, packet):
+ packet_bytes = packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != scid:
+ return False
+ standard_view = l2cap_packets.StandardFrameView(l2cap_view)
+ if standard_view.GetFrameType() == l2cap_packets.FrameType.I_FRAME:
+ return False
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameView(standard_view)
+ return s_frame.GetF()
+
+ def get_tx_seq_from_ertm_i_frame(self, scid, packet):
+ packet_bytes = packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != scid:
+ return False
+ standard_view = l2cap_packets.StandardFrameView(l2cap_view)
+ if standard_view.GetFrameType() == l2cap_packets.FrameType.S_FRAME:
+ return False
+ i_frame = l2cap_packets.EnhancedInformationFrameView(standard_view)
+ return i_frame.GetTxSeq()
+
+ def get_payload_from_ertm_i_frame(self, scid, packet):
+ packet_bytes = packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != scid:
+ return False
+ standard_view = l2cap_packets.StandardFrameView(l2cap_view)
+ if standard_view.GetFrameType() == l2cap_packets.FrameType.S_FRAME:
+ return False
+ i_frame = l2cap_packets.EnhancedInformationFrameView(standard_view)
+ return i_frame.GetPayload() # TODO(mylesgw): This doesn't work!
def _setup_link_from_cert(self):
- self.dut.neighbor.EnablePageScan(neighbor_facade.EnableMsg(enabled=True))
- self.cert_l2cap.connect_acl(self.dut_address)
-
- def _open_unconfigured_channel_from_cert(self,
- signal_id=1,
- scid=0x0101,
- psm=0x33,
- mode=RetransmissionFlowControlMode.BASIC,
- fcs=None):
-
- dut_channel = self.dut_l2cap.register_dynamic_channel(psm, mode)
- cert_channel = self.cert_l2cap.open_channel(signal_id, psm, scid, fcs=fcs)
-
- return (dut_channel, cert_channel)
-
- def _open_channel_from_cert(self,
- signal_id=1,
- scid=0x0101,
- psm=0x33,
- mode=RetransmissionFlowControlMode.BASIC,
- fcs=None,
- req_config_options=None,
- rsp_config_options=None):
- request_matcher = L2capMatchers.ConfigurationRequestView(scid)
- if rsp_config_options is not None:
- when(self.cert_l2cap).on_config_req(request_matcher).then().send_configuration_response(
- options=rsp_config_options)
- if rsp_config_options is None and fcs is not None:
- when(self.cert_l2cap).on_config_req(request_matcher).then().send_configuration_response(
- options=CertL2cap.config_option_ertm(fcs=fcs))
-
- (dut_channel, cert_channel) = self._open_unconfigured_channel_from_cert(signal_id, scid, psm, mode, fcs)
- if req_config_options is None:
- req_config_options = CertL2cap.config_option_ertm(
- fcs=fcs) if mode == RetransmissionFlowControlMode.ERTM else []
-
- cert_channel.send_configure_request(req_config_options)
- cert_channel.verify_configuration_response()
-
- wait_until(self.cert_l2cap).on_config_req(request_matcher).times(1)
-
- assertThat(cert_channel.is_configured()).isTrue()
-
- return (dut_channel, cert_channel)
-
- def _open_channel_from_dut(self, psm=0x33, mode=RetransmissionFlowControlMode.BASIC):
- dut_channel_future = self.dut_l2cap.connect_dynamic_channel_to_cert(psm, mode)
- cert_channel = self.cert_l2cap.verify_and_respond_open_channel_from_remote(psm)
- dut_channel = dut_channel_future.get_channel()
-
- cert_channel.verify_configuration_request_and_respond()
- outgoing_config = []
- if mode == RetransmissionFlowControlMode.ERTM:
- outgoing_config = CertL2cap.config_option_ertm()
- cert_channel.send_configure_request(outgoing_config)
- cert_channel.verify_configuration_response()
-
- return (dut_channel, cert_channel)
-
-
-class L2capTest(L2capTestBase):
+ self.device_under_test.neighbor.EnablePageScan(
+ neighbor_facade.EnableMsg(enabled=True))
+
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.CreateConnection(
+ acl_manager_facade.ConnectionMsg(
+ address_type=int(
+ hci_packets.AddressType.PUBLIC_DEVICE_ADDRESS),
+ address=bytes(self.dut_address.address)))
+ ) as connection_event_stream:
+
+ connection_event_asserts = EventAsserts(connection_event_stream)
+
+ # Cert gets ConnectionComplete with a handle and sends ACL data
+ handle = 0xfff
+
+ def get_handle(packet):
+ packet_bytes = packet.event
+ if b'\x03\x0b\x00' in packet_bytes:
+ nonlocal handle
+ cc_view = hci_packets.ConnectionCompleteView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes))))
+ handle = cc_view.GetConnectionHandle()
+ return True
+ return False
+
+ connection_event_asserts.assert_event_occurs(get_handle)
+
+ self.cert_acl_handle = handle
+ return handle
+
+ def _open_channel(
+ self,
+ cert_acl_data_stream,
+ signal_id=1,
+ cert_acl_handle=0x1,
+ scid=0x0101,
+ psm=0x33,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC):
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+
+ self.device_under_test.l2cap.SetDynamicChannel(
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=mode))
+ open_channel = l2cap_packets.ConnectionRequestBuilder(
+ signal_id, psm, scid)
+ open_channel_l2cap = l2cap_packets.BasicFrameBuilder(1, open_channel)
+ self.cert_send_b_frame(open_channel_l2cap)
+
+ def verify_connection_response(packet):
+ packet_bytes = packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ l2cap_control_view = l2cap_packets.ControlView(
+ l2cap_view.GetPayload())
+ if l2cap_control_view.GetCode(
+ ) != l2cap_packets.CommandCode.CONNECTION_RESPONSE:
+ return False
+ connection_response_view = l2cap_packets.ConnectionResponseView(
+ l2cap_control_view)
+ return connection_response_view.GetSourceCid(
+ ) == scid and connection_response_view.GetResult(
+ ) == l2cap_packets.ConnectionResponseResult.SUCCESS and connection_response_view.GetDestinationCid(
+ ) != 0
+
+ cert_acl_data_asserts.assert_event_occurs(verify_connection_response)
def test_connect_dynamic_channel_and_send_data(self):
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert()
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.Data(b'abc'))
-
- def test_receive_packet_from_unknown_channel(self):
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(scid=0x41, psm=0x33)
-
- i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
- 0x99, 0, Final.NOT_SET, 1, l2cap_packets.SegmentationAndReassembly.UNSEGMENTED, SAMPLE_PACKET)
- self.cert_l2cap.send_acl(i_frame)
- assertThat(cert_channel).emitsNone(L2capMatchers.SFrame(req_seq=4), timeout=timedelta(seconds=1))
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(cert_acl_data_stream, 1, cert_acl_handle, scid,
+ psm)
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=0x33, payload=b'abc'))
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b'abc' in packet.payload)
+
+ def test_fixed_channel(self):
+ cert_acl_handle = self._setup_link_from_cert()
+ self.device_under_test.l2cap.RegisterChannel(
+ l2cap_facade_pb2.RegisterChannelRequest(channel=2))
+ asserts.skip("FIXME: Not working")
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ self.device_under_test.l2cap.SendL2capPacket(
+ l2cap_facade_pb2.L2capPacket(channel=2, payload=b"123"))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b'123' in packet.payload)
def test_open_two_channels(self):
- self._setup_link_from_cert()
-
- self._open_channel_from_cert(signal_id=1, scid=0x41, psm=0x41)
- self._open_channel_from_cert(signal_id=2, scid=0x43, psm=0x43)
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self._open_channel(cert_acl_data_stream, 1, cert_acl_handle, 0x41,
+ 0x41)
+ self._open_channel(cert_acl_data_stream, 2, cert_acl_handle, 0x43,
+ 0x43)
def test_connect_and_send_data_ertm_no_segmentation(self):
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(
+ psm=psm, payload=b'abc' * 34))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b'abc' * 34 in packet.payload)
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 0, l2cap_packets.Final.NOT_SET, 1,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
- dut_channel.send(b'abc' * 34)
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0, payload=b'abc' * 34))
-
- cert_channel.send_i_frame(tx_seq=0, req_seq=1, payload=SAMPLE_PACKET)
- # todo verify received?
-
- @metadata(pts_test_id="L2CAP/COS/CED/BV-01-C", pts_test_name="Request Connection")
def test_basic_operation_request_connection(self):
"""
- Verify that the IUT is able to request the connection establishment for
- an L2CAP data channel and initiate the configuration procedure.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_dut()
-
- @metadata(pts_test_id="L2CAP/COS/CED/BV-03-C", pts_test_name="Send data")
- def test_send_data(self):
- """
- Verify that the IUT is able to send DATA
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- dut_channel.send(b'hello')
- assertThat(cert_channel).emits(L2capMatchers.Data(b'hello'))
-
- @metadata(pts_test_id="L2CAP/COS/CED/BV-04-C", pts_test_name="Disconnect")
- def test_disconnect(self):
- """
- Verify that the IUT is able to disconnect the data channel
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- dut_channel.close_channel()
- cert_channel.verify_disconnect_request()
-
- @metadata(pts_test_id="L2CAP/COS/CED/BV-05-C", pts_test_name="Accept connection")
- def test_accept_connection(self):
- """
- Also verify that DUT can send 48 bytes PDU (minimal MTU)
- """
- self._setup_link_from_cert()
+ L2CAP/COS/CED/BV-01-C [Request Connection]
+ Verify that the IUT is able to request the connection establishment for an L2CAP data channel and
+ initiate the configuration procedure.
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ psm = 0x33
+ # TODO: Use another test case
+ self.device_under_test.l2cap.OpenChannel(
+ l2cap_facade_pb2.OpenChannelRequest(
+ remote=self.cert_address, psm=psm))
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_connection_request)
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- dut_channel.send(b'a' * 48)
- assertThat(cert_channel).emits(L2capMatchers.Data(b'a' * 48))
-
- @metadata(pts_test_id="L2CAP/COS/CED/BV-07-C", pts_test_name="Accept Disconnect")
def test_accept_disconnect(self):
"""
- Verify that the IUT is able to respond to the request to disconnect the
- data channel
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- cert_channel.disconnect_and_verify()
+ L2CAP/COS/CED/BV-07-C
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+
+ scid = 0x41
+ psm = 0x33
+ self._open_channel(cert_acl_data_stream, 1, cert_acl_handle, scid,
+ psm)
+
+ dcid = self.scid_to_dcid[scid]
+
+ close_channel = l2cap_packets.DisconnectionRequestBuilder(
+ 1, dcid, scid)
+ close_channel_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, close_channel)
+ self.cert_send_b_frame(close_channel_l2cap)
+
+ def verify_disconnection_response(packet):
+ packet_bytes = packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ l2cap_control_view = l2cap_packets.ControlView(
+ l2cap_view.GetPayload())
+ if l2cap_control_view.GetCode(
+ ) != l2cap_packets.CommandCode.DISCONNECTION_RESPONSE:
+ return False
+ disconnection_response_view = l2cap_packets.DisconnectionResponseView(
+ l2cap_control_view)
+ return disconnection_response_view.GetSourceCid(
+ ) == scid and disconnection_response_view.GetDestinationCid(
+ ) == dcid
+
+ cert_acl_data_asserts.assert_event_occurs(
+ verify_disconnection_response)
- @metadata(pts_test_id="L2CAP/COS/CED/BV-08-C", pts_test_name="Disconnect on Timeout")
def test_disconnect_on_timeout(self):
"""
- Verify that the IUT disconnects the data channel and shuts down this
- channel if no response occurs
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_unconfigured_channel_from_cert()
-
- assertThat(self.cert_l2cap.get_control_channel()).emitsNone(L2capMatchers.ConfigurationResponse())
- # TODO: Verify that IUT sends disconnect request (not mandated)
-
- @metadata(pts_test_id="L2CAP/COS/CED/BV-09-C", pts_test_name="Receive Multi-Command Packet")
- def test_receive_multi_command_packet(self):
- """
- Verify that the IUT is able to receive more than one signaling command in one L2CAP
- packet.
- """
- self._setup_link_from_cert()
-
- psm = 0x33
- self.dut_l2cap.connect_dynamic_channel_to_cert(psm)
- self.cert_l2cap.verify_and_respond_open_channel_from_remote_and_send_config_req(psm)
-
- assertThat(self.cert_l2cap.get_control_channel()).emits(L2capMatchers.ConfigurationResponse())
-
- @metadata(pts_test_id="L2CAP/COS/CED/BV-11-C", pts_test_name="Configure MTU size")
- def test_configure_mtu_size(self):
- """
- Verify that the IUT is able to configure the supported MTU size
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_unconfigured_channel_from_cert()
- cert_channel.send_configure_request(CertL2cap.config_option_mtu_explicit(672))
- cert_channel.verify_configuration_request_and_respond()
- # TODO: Probably remove verify_configuration_request_and_respond
-
- @metadata(pts_test_id="L2CAP/COS/CFD/BV-01-C", pts_test_name="Continuation Flag")
- def test_continuation_flag(self):
- """
- Verify the IUT is able to receive configuration requests that have the
- continuation flag set
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_unconfigured_channel_from_cert()
-
- # Send configuration request with CONTINUE
- mtu_opt = l2cap_packets.MtuConfigurationOption()
- mtu_opt.mtu = 0x1234
- cert_channel.send_configure_request([mtu_opt], 2, l2cap_packets.Continuation.CONTINUE)
-
- flush_timeout_option = l2cap_packets.FlushTimeoutConfigurationOption()
- flush_timeout_option.flush_timeout = 65535
- cert_channel.send_configure_request([flush_timeout_option], 3, l2cap_packets.Continuation.END)
-
- assertThat(self.cert_l2cap.get_control_channel()).emits(L2capMatchers.ConfigurationResponse(), at_least_times=2)
-
- @metadata(pts_test_id="L2CAP/COS/CFD/BV-02-C", pts_test_name="Negotiation with Reject")
- def test_retry_config_after_rejection(self):
- """
- Verify that the IUT is able to perform negotiation while the Lower
- Tester rejects the proposed configuration parameter values
- """
- self._setup_link_from_cert()
- scid = 0x41
- when(self.cert_l2cap).on_config_req(
- L2capMatchers.ConfigurationRequestView(scid)).then().send_configuration_response(
- result=l2cap_packets.ConfigurationResponseResult.UNACCEPTABLE_PARAMETERS,
- options=CertL2cap.config_option_mtu_explicit(200)).send_configuration_response(options=[])
- (dut_channel, cert_channel) = self._open_unconfigured_channel_from_cert(scid=scid)
-
- assertThat(self.cert_l2cap.get_control_channel()).emits(L2capMatchers.ConfigurationRequest(), at_least_times=2)
-
- @metadata(pts_test_id="L2CAP/COS/CFD/BV-03-C", pts_test_name="Send Requested Options")
- def test_send_requested_options(self):
- """
- Verify that the IUT can receive a configuration request with no options
- and send the requested options to the Lower Tester
+ L2CAP/COS/CED/BV-08-C
"""
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert(scid=0x41, psm=0x33)
+ cert_acl_handle = self._setup_link_from_cert()
- # TODO(hsz) implement me!
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ scid = 0x41
+ psm = 0x33
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
- @metadata(pts_test_id="L2CAP/COS/CFD/BV-08-C", pts_test_name="Non-blocking Config Response")
- def test_non_blocking_config_response(self):
- """
- Verify that the IUT does not block transmitting L2CAP_ConfigRsp while
- waiting for L2CAP_ConfigRsp from the Lower Tester
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_unconfigured_channel_from_cert()
+ # Don't send configuration request or response back
+ self.on_configuration_request = lambda _: True
+ self.on_connection_response = lambda _: True
- cert_channel.send_configure_request([])
- cert_channel.verify_configuration_response()
- cert_channel.verify_configuration_request_and_respond()
+ self._open_channel(cert_acl_data_stream, 1, cert_acl_handle, scid,
+ psm)
- # TODO(hsz) implement me!
+ def is_configuration_response(l2cap_packet):
+ packet_bytes = l2cap_packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != 1:
+ return False
+ l2cap_control_view = l2cap_packets.ControlView(
+ l2cap_view.GetPayload())
+ return l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.CONFIGURATION_RESPONSE
- @metadata(pts_test_id="L2CAP/COS/CFD/BV-09-C", pts_test_name="Mandatory 48 Byte MTU")
- def test_mandatory_48_byte_mtu(self):
- """
- Verify that the IUT can support mandatory 48 byte MTU
- """
- self._setup_link_from_cert()
- (dut_channel,
- cert_channel) = self._open_channel_from_cert(req_config_options=CertL2cap.config_option_mtu_explicit(48))
-
- dut_channel.send(b"a" * 44)
- assertThat(cert_channel).emits(L2capMatchers.Data(b"a" * 44))
-
- @metadata(pts_test_id="L2CAP/COS/CFD/BV-11-C", pts_test_name="Negotiation of Unsupported Parameter")
- def test_negotiation_of_unsupported_parameter(self):
- """
- Verify that the IUT can negotiate when the Lower Tester proposes an unsupported configuration
- parameter value.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_unconfigured_channel_from_cert()
-
- cert_channel.send_configure_request(CertL2cap.config_option_mtu_explicit(20))
- # Invalid because minimum is 48
-
- cert_channel.verify_configuration_response(l2cap_packets.ConfigurationResponseResult.UNACCEPTABLE_PARAMETERS)
-
- @metadata(pts_test_id="L2CAP/COS/CFD/BV-12-C", pts_test_name="Unknown Option Response")
- def test_config_unknown_options_with_hint(self):
- """
- Verify that the IUT can give the appropriate error code when the Lower
- Tester proposes any number of unknown options that are optional
- NOTE: In GD stack, ExtendedWindowSizeOption in unsupported
- """
- self._setup_link_from_cert()
+ cert_acl_data_asserts.assert_none_matching(
+ is_configuration_response)
- (dut_channel, cert_channel) = self._open_unconfigured_channel_from_cert()
-
- unknown_opt_hint = l2cap_packets.ExtendedWindowSizeOption()
- unknown_opt_hint.max_window_size = 20
- unknown_opt_hint.is_hint = l2cap_packets.ConfigurationOptionIsHint.OPTION_IS_A_HINT
-
- for i in range(10):
- cert_channel.send_configure_request([unknown_opt_hint] * i)
- cert_channel.verify_configuration_response(l2cap_packets.ConfigurationResponseResult.SUCCESS)
-
- @metadata(pts_test_id="L2CAP/COS/CFD/BV-14-C", pts_test_name="Unknown Mandatory Options Request")
- def test_unknown_mandatory_options_request(self):
- """
- Verify that the IUT can give the appropriate error code when the Lower
- Tester proposes any number of unknown options where at least one is
- mandatory.
- Note: GD stack doesn't support extended window size. For other stacks,
- we may need to use some other config option
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_unconfigured_channel_from_cert(scid=0x41, psm=0x33)
-
- unknown_opt = l2cap_packets.ExtendedWindowSizeOption()
- unknown_opt.max_window_size = 20
-
- unknown_opt_hint = l2cap_packets.ExtendedWindowSizeOption()
- unknown_opt_hint.max_window_size = 20
- unknown_opt_hint.is_hint = l2cap_packets.ConfigurationOptionIsHint.OPTION_IS_A_HINT
-
- configuration_option_attempts = [[unknown_opt], [unknown_opt, unknown_opt_hint], [
- unknown_opt, unknown_opt, unknown_opt
- ], [unknown_opt, unknown_opt_hint, unknown_opt_hint,
- unknown_opt], [unknown_opt_hint, unknown_opt_hint, unknown_opt_hint, unknown_opt_hint, unknown_opt], [
- unknown_opt, unknown_opt_hint, unknown_opt_hint, unknown_opt, unknown_opt_hint, unknown_opt_hint
- ], [unknown_opt, unknown_opt, unknown_opt, unknown_opt, unknown_opt, unknown_opt, unknown_opt], [
- unknown_opt_hint, unknown_opt_hint, unknown_opt_hint, unknown_opt_hint, unknown_opt_hint,
- unknown_opt_hint, unknown_opt_hint, unknown_opt
- ], [
- unknown_opt_hint, unknown_opt_hint, unknown_opt_hint, unknown_opt_hint, unknown_opt_hint,
- unknown_opt_hint, unknown_opt_hint, unknown_opt, unknown_opt
- ], [
- unknown_opt_hint, unknown_opt_hint, unknown_opt_hint, unknown_opt_hint, unknown_opt_hint,
- unknown_opt_hint, unknown_opt_hint, unknown_opt_hint, unknown_opt_hint, unknown_opt
- ]]
-
- for option_list in configuration_option_attempts:
- cert_channel.send_configure_request(option_list)
- cert_channel.verify_configuration_response(l2cap_packets.ConfigurationResponseResult.UNKNOWN_OPTIONS)
-
- @metadata(pts_test_id="L2CAP/COS/ECH/BV-01-C", pts_test_name="Respond to Echo Request")
def test_respond_to_echo_request(self):
"""
+ L2CAP/COS/ECH/BV-01-C [Respond to Echo Request]
Verify that the IUT responds to an echo request.
"""
- self._setup_link_from_cert()
- echo_request = l2cap_packets.EchoRequestBuilder(100, RawBuilder([1, 2, 3]))
- self.cert_l2cap.get_control_channel().send(echo_request)
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
- assertThat(self.cert_l2cap.get_control_channel()).emits(L2capMatchers.EchoResponse())
+ echo_request = l2cap_packets.EchoRequestBuilder(
+ 100, l2cap_packets.DisconnectionRequestBuilder(1, 2, 3))
+ echo_request_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, echo_request)
+ self.cert_send_b_frame(echo_request_l2cap)
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b"\x06\x01\x04\x00\x02\x00\x03\x00" in packet.payload
+ )
- @metadata(pts_test_id="L2CAP/COS/CED/BI-01-C", pts_test_name="Reject Unknown Command")
def test_reject_unknown_command(self):
"""
- Verify that the IUT rejects an unknown signaling command
- """
- self._setup_link_from_cert()
-
- # Command code ff, Signal id 01, size 0000
- invalid_command_packet = RawBuilder([0xff, 0x01, 0x00, 0x00])
- self.cert_l2cap.get_control_channel().send(invalid_command_packet)
+ L2CAP/COS/CED/BI-01-C
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+
+ invalid_command_packet = b"\x04\x00\x01\x00\xff\x01\x00\x00"
+ self.cert_device.hci_acl_manager.SendAclData(
+ acl_manager_facade.AclData(
+ handle=cert_acl_handle,
+ payload=bytes(invalid_command_packet)))
+
+ def is_command_reject(l2cap_packet):
+ packet_bytes = l2cap_packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != 1:
+ return False
+ l2cap_control_view = l2cap_packets.ControlView(
+ l2cap_view.GetPayload())
+ return l2cap_control_view.GetCode(
+ ) == l2cap_packets.CommandCode.COMMAND_REJECT
+
+ cert_acl_data_asserts.assert_event_occurs(is_command_reject)
- assertThat(self.cert_l2cap.get_control_channel()).emits(L2capMatchers.CommandReject())
-
- @metadata(pts_test_id="L2CAP/COS/IEX/BV-01-C", pts_test_name="Query for 1.2 Features")
def test_query_for_1_2_features(self):
"""
- Verify that the IUT transmits an information request command to solicit
- if the remote device supports Specification 1.2 features.
- """
- self._setup_link_from_cert()
- assertThat(self.cert_l2cap.get_control_channel()).emits(
- L2capMatchers.InformationRequestWithType(
- l2cap_packets.InformationRequestInfoType.EXTENDED_FEATURES_SUPPORTED))
+ L2CAP/COS/IEX/BV-01-C [Query for 1.2 Features]
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_asserts_alt = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ signal_id = 3
+ information_request = l2cap_packets.InformationRequestBuilder(
+ signal_id, l2cap_packets.InformationRequestInfoType.
+ EXTENDED_FEATURES_SUPPORTED)
+ information_request_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, information_request)
+ self.cert_send_b_frame(information_request_l2cap)
+
+ def is_correct_information_response(l2cap_packet):
+ packet_bytes = l2cap_packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != 1:
+ return False
+ l2cap_control_view = l2cap_packets.ControlView(
+ l2cap_view.GetPayload())
+ if l2cap_control_view.GetCode(
+ ) != l2cap_packets.CommandCode.INFORMATION_RESPONSE:
+ return False
+ information_response_view = l2cap_packets.InformationResponseView(
+ l2cap_control_view)
+ return information_response_view.GetInfoType(
+ ) == l2cap_packets.InformationRequestInfoType.EXTENDED_FEATURES_SUPPORTED
+
+ cert_acl_data_asserts.assert_event_occurs(
+ is_correct_information_response)
+
+ def is_correct_information_request(l2cap_packet):
+ packet_bytes = l2cap_packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != 1:
+ return False
+ l2cap_control_view = l2cap_packets.ControlView(
+ l2cap_view.GetPayload())
+ if l2cap_control_view.GetCode(
+ ) != l2cap_packets.CommandCode.INFORMATION_REQUEST:
+ return False
+ information_request_view = l2cap_packets.InformationRequestView(
+ l2cap_control_view)
+ return information_request_view.GetInfoType(
+ ) == l2cap_packets.InformationRequestInfoType.EXTENDED_FEATURES_SUPPORTED
+
+ cert_acl_data_asserts_alt.assert_event_occurs(
+ is_correct_information_request)
- @metadata(pts_test_id="L2CAP/COS/IEX/BV-02-C", pts_test_name="Respond with 1.2 Features")
- def test_respond_with_1_2_features(self):
- """
- Verify that the IUT responds to an information request command
- soliciting for Specification 1.2 features
- """
- self._setup_link_from_cert()
- control_channel = self.cert_l2cap.get_control_channel()
-
- control_channel.send_extended_features_request()
-
- assertThat(control_channel).emits(L2capMatchers.InformationResponseExtendedFeatures())
-
- @metadata(
- pts_test_id="L2CAP/EXF/BV-01-C",
- pts_test_name="Extended Features Information Response for "
- "Enhanced Retransmission Mode")
def test_extended_feature_info_response_ertm(self):
"""
- Verify the IUT can format an Information Response for the information
- type of Extended Features that correctly identifies that Enhanced
- Retransmission Mode is locally supported
- """
- self._setup_link_from_cert()
- control_channel = self.cert_l2cap.get_control_channel()
-
- control_channel.send_extended_features_request()
-
- assertThat(control_channel).emits(L2capMatchers.InformationResponseExtendedFeatures(supports_ertm=True))
-
- @metadata(
- pts_test_id="L2CAP/EXF/BV-02-C", pts_test_name="Extended Features Information Response for "
- "Streaming Mode")
- def test_extended_feature_info_response_streaming(self):
- """
- Verify the IUT can format an Information Response for the information
- type of Extended Features that correctly identifies that Streaming Mode
- is locally supported
- """
- asserts.skip("Streaming not supported")
- self._setup_link_from_cert()
- control_channel = self.cert_l2cap.get_control_channel()
-
- control_channel.send_extended_features_request()
+ L2CAP/EXF/BV-01-C [Extended Features Information Response for Enhanced
+ Retransmission Mode]
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+
+ signal_id = 3
+ information_request = l2cap_packets.InformationRequestBuilder(
+ signal_id, l2cap_packets.InformationRequestInfoType.
+ EXTENDED_FEATURES_SUPPORTED)
+ information_request_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, information_request)
+ self.cert_send_b_frame(information_request_l2cap)
+
+ def is_correct_information_response(l2cap_packet):
+ packet_bytes = l2cap_packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != 1:
+ return False
+ l2cap_control_view = l2cap_packets.ControlView(
+ l2cap_view.GetPayload())
+ if l2cap_control_view.GetCode(
+ ) != l2cap_packets.CommandCode.INFORMATION_RESPONSE:
+ return False
+ information_response_view = l2cap_packets.InformationResponseView(
+ l2cap_control_view)
+ if information_response_view.GetInfoType(
+ ) != l2cap_packets.InformationRequestInfoType.EXTENDED_FEATURES_SUPPORTED:
+ return False
+ extended_features_view = l2cap_packets.InformationResponseExtendedFeaturesView(
+ information_response_view)
+ return extended_features_view.GetEnhancedRetransmissionMode()
+
+ cert_acl_data_asserts.assert_event_occurs(
+ is_correct_information_response)
- assertThat(control_channel).emits(L2capMatchers.InformationResponseExtendedFeatures(supports_streaming=True))
-
- @metadata(pts_test_id="L2CAP/EXF/BV-03-C", pts_test_name="Extended Features Information Response for FCS " "Option")
def test_extended_feature_info_response_fcs(self):
"""
- Verify the IUT can format an Information Response for the information
- type of Extended Features that correctly identifies that the FCS Option
- is locally supported.
-
+ L2CAP/EXF/BV-03-C [Extended Features Information Response for FCS Option]
Note: This is not mandated by L2CAP Spec
"""
- self._setup_link_from_cert()
- control_channel = self.cert_l2cap.get_control_channel()
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+
+ signal_id = 3
+ information_request = l2cap_packets.InformationRequestBuilder(
+ signal_id, l2cap_packets.InformationRequestInfoType.
+ EXTENDED_FEATURES_SUPPORTED)
+ information_request_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, information_request)
+ self.cert_send_b_frame(information_request_l2cap)
+
+ def is_correct_information_response(l2cap_packet):
+ packet_bytes = l2cap_packet.payload
+ l2cap_view = l2cap_packets.BasicFrameView(
+ bt_packets.PacketViewLittleEndian(list(packet_bytes)))
+ if l2cap_view.GetChannelId() != 1:
+ return False
+ l2cap_control_view = l2cap_packets.ControlView(
+ l2cap_view.GetPayload())
+ if l2cap_control_view.GetCode(
+ ) != l2cap_packets.CommandCode.INFORMATION_RESPONSE:
+ return False
+ information_response_view = l2cap_packets.InformationResponseView(
+ l2cap_control_view)
+ if information_response_view.GetInfoType(
+ ) != l2cap_packets.InformationRequestInfoType.EXTENDED_FEATURES_SUPPORTED:
+ return False
+ extended_features_view = l2cap_packets.InformationResponseExtendedFeaturesView(
+ information_response_view)
+ return extended_features_view.GetFcsOption()
+
+ cert_acl_data_asserts.assert_event_occurs(
+ is_correct_information_response)
- control_channel.send_extended_features_request()
-
- assertThat(control_channel).emits(L2capMatchers.InformationResponseExtendedFeatures(supports_fcs=True))
-
- @metadata(
- pts_test_id="L2CAP/EXF/BV-05-C", pts_test_name="Extended Features Information Response for Fixed "
- "Channels")
- def test_extended_feature_info_response_fixed_channels(self):
- """
- Verify the IUT can format an Information Response for the information
- type of Extended Features that correctly identifies that the Fixed
- Channels option is locally supported
-
- Note: This is not mandated by L2CAP Spec
- """
- self._setup_link_from_cert()
- control_channel = self.cert_l2cap.get_control_channel()
-
- control_channel.send_extended_features_request()
-
- assertThat(control_channel).emits(
- L2capMatchers.InformationResponseExtendedFeatures(supports_fixed_channels=True))
-
- @metadata(pts_test_id="L2CAP/FIX/BV-01-C", pts_test_name="Fixed Channels Supported Information Request")
- def test_fixed_channels_supported_information_request(self):
- """
- Verify that the IUT can send an Information Request for the information
- type of Fixed Channels Supported.
- """
- self._setup_link_from_cert()
- assertThat(self.cert_l2cap.get_control_channel()).emits(
- L2capMatchers.InformationRequestWithType(l2cap_packets.InformationRequestInfoType.FIXED_CHANNELS_SUPPORTED))
-
- @metadata(pts_test_id="L2CAP/FOC/BV-01-C", pts_test_name="IUT Initiated Configuration of the FCS Option")
def test_config_channel_not_use_FCS(self):
"""
+ L2CAP/FOC/BV-01-C [IUT Initiated Configuration of the FCS Option]
Verify the IUT can configure a channel to not use FCS in I/S-frames.
"""
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0, payload=b'abc'))
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b"abc" in packet.payload)
- @metadata(pts_test_id="L2CAP/FOC/BV-02-C", pts_test_name="Lower Tester Explicitly Requests FCS should be " "Used")
def test_explicitly_request_use_FCS(self):
"""
- Verify the IUT will include the FCS in I/S-frames if the Lower Tester
- explicitly requests that FCS should be used
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.DEFAULT)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.IFrameWithFcs(payload=b"abc"))
+ L2CAP/FOC/BV-02-C [Lower Tester Explicitly Requests FCS should be Used]
+ Verify the IUT will include the FCS in I/S-frames if the Lower Tester explicitly requests that FCS
+ should be used.
+ """
+
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+
+ self.on_connection_response = self._on_connection_response_use_ertm_and_fcs
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b"abc\x4f\xa3" in packet.payload
+ ) # TODO: Use packet parser
- @metadata(pts_test_id="L2CAP/FOC/BV-03-C", pts_test_name="Lower Tester Implicitly Requests FCS should be " "Used")
def test_implicitly_request_use_FCS(self):
"""
- Verify the IUT will include the FCS in I/S-frames if the Lower Tester
- implicitly requests that FCS should be used.
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM,
- fcs=FcsType.DEFAULT,
- req_config_options=CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS))
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.IFrameWithFcs(payload=b"abc"))
-
- @metadata(pts_test_id="L2CAP/OFS/BV-01-C", pts_test_name="Sending I-Frames without FCS for ERTM")
- def test_sending_i_frames_without_fcs_for_ertm(self):
- """
- Verify the IUT does not include the FCS in I-frames.
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0, payload=b"abc"))
-
- @metadata(pts_test_id="L2CAP/OFS/BV-02-C", pts_test_name="Receiving I-Frames without FCS for ERTM")
- def test_receiving_i_frames_without_fcs_for_ertm(self):
- """
- Verify the IUT can handle I-frames that do not contain the FCS.
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
-
- cert_channel.send_i_frame(tx_seq=0, req_seq=0, payload=SAMPLE_PACKET)
- assertThat(dut_channel).emits(L2capMatchers.PacketPayloadRawData(SAMPLE_PACKET_DATA))
-
- @metadata(pts_test_id="L2CAP/OFS/BV-05-C", pts_test_name="Sending I-Frames with FCS for ERTM")
- def test_sending_i_frames_with_fcs_for_ertm(self):
- """
- Verify the IUT does include the FCS in I-frames.
- """
- self._setup_link_from_cert()
+ L2CAP/FOC/BV-03-C [Lower Tester Implicitly Requests FCS should be Used]
+ TODO: Update this test case. What's the difference between this one and test_explicitly_request_use_FCS?
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+
+ self.on_connection_response = self._on_connection_response_use_ertm_and_fcs
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b"abc\x4f\xa3" in packet.payload
+ ) # TODO: Use packet parser
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.DEFAULT)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.IFrameWithFcs(tx_seq=0, payload=b"abc"))
-
- @metadata(pts_test_id="L2CAP/OFS/BV-06-C", pts_test_name="Receiving I-Frames with FCS for ERTM")
- def test_receiving_i_frames_with_fcs_for_ertm(self):
- """
- Verify the IUT can handle I-frames that do contain the FCS.
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.DEFAULT)
-
- cert_channel.send_i_frame(tx_seq=0, req_seq=0, payload=SAMPLE_PACKET, fcs=FcsType.DEFAULT)
- assertThat(dut_channel).emits(L2capMatchers.PacketPayloadRawData(SAMPLE_PACKET_DATA))
-
- @metadata(pts_test_id="L2CAP/ERM/BV-01-C", pts_test_name="Transmit I-frames")
def test_transmit_i_frames(self):
"""
- Verify the IUT can send correctly formatted sequential I-frames with
- valid values for the enhanced control fields (SAR, F-bit, ReqSeq,
- TxSeq)
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0, payload=b"abc"))
+ L2CAP/ERM/BV-01-C [Transmit I-frames]
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+
+ self.on_connection_response = self._on_connection_response_use_ertm
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ dcid = self.scid_to_dcid[scid]
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b"abc" in packet.payload)
+
+ # Assemble a sample packet. TODO: Use RawBuilder
+ SAMPLE_PACKET = l2cap_packets.CommandRejectNotUnderstoodBuilder(1)
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 0, l2cap_packets.Final.NOT_SET, 1,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b"abc" in packet.payload)
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 1, l2cap_packets.Final.NOT_SET, 2,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: b"abc" in packet.payload)
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 2, l2cap_packets.Final.NOT_SET, 3,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
- cert_channel.send_i_frame(tx_seq=0, req_seq=1, payload=SAMPLE_PACKET)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=1, payload=b"abc"))
-
- cert_channel.send_i_frame(tx_seq=1, req_seq=2, payload=SAMPLE_PACKET)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.PartialData(b"abc"))
-
- cert_channel.send_i_frame(tx_seq=2, req_seq=3, payload=SAMPLE_PACKET)
-
- @metadata(pts_test_id="L2CAP/ERM/BV-02-C", pts_test_name="Receive I-Frames")
def test_receive_i_frames(self):
"""
- Verify the IUT can receive in-sequence valid I-frames and deliver L2CAP
- SDUs to the Upper Tester
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
-
- for i in range(3):
- cert_channel.send_i_frame(tx_seq=i, req_seq=0, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(req_seq=i + 1))
-
- cert_channel.send_i_frame(tx_seq=3, req_seq=0, sar=SegmentationAndReassembly.START, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(req_seq=4))
+ L2CAP/ERM/BV-02-C [Receive I-Frames]
+ Verify the IUT can receive in-sequence valid I-frames and deliver L2CAP SDUs to the Upper Tester
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ dcid = self.scid_to_dcid[scid]
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ for i in range(3):
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, i, l2cap_packets.Final.NOT_SET, 0,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_req_seq_from_ertm_s_frame(scid, packet) == i + 1
+ )
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 3, l2cap_packets.Final.NOT_SET, 0,
+ l2cap_packets.SegmentationAndReassembly.START, SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_req_seq_from_ertm_s_frame(scid, packet) == 4
+ )
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 4, l2cap_packets.Final.NOT_SET, 0,
+ l2cap_packets.SegmentationAndReassembly.CONTINUATION,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_req_seq_from_ertm_s_frame(scid, packet) == 5
+ )
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 5, l2cap_packets.Final.NOT_SET, 0,
+ l2cap_packets.SegmentationAndReassembly.END, SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_req_seq_from_ertm_s_frame(scid, packet) == 6
+ )
- cert_channel.send_i_frame(
- tx_seq=4, req_seq=0, sar=SegmentationAndReassembly.CONTINUATION, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(req_seq=5))
-
- cert_channel.send_i_frame(tx_seq=5, req_seq=0, sar=SegmentationAndReassembly.END, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(req_seq=6))
-
- @metadata(pts_test_id="L2CAP/ERM/BV-03-C", pts_test_name="Acknowledging Received I-Frames")
def test_acknowledging_received_i_frames(self):
"""
- Verify the IUT sends S-frame [RR] with the Poll bit not set to
- acknowledge data received from the Lower Tester
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
-
- for i in range(3):
- cert_channel.send_i_frame(tx_seq=i, req_seq=0, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(req_seq=i + 1))
+ L2CAP/ERM/BV-03-C [Acknowledging Received I-Frames]
+ Verify the IUT sends S-frame [RR] with the Poll bit not set to acknowledge data received from the
+ Lower Tester
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ dcid = self.scid_to_dcid[scid]
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ for i in range(3):
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, i, l2cap_packets.Final.NOT_SET, 0,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_req_seq_from_ertm_s_frame(scid, packet) == i + 1
+ )
+
+ cert_acl_data_asserts.assert_none_matching(
+ lambda packet: self.get_req_seq_from_ertm_s_frame(scid, packet) == 4,
+ timedelta(seconds=1))
- assertThat(cert_channel).emitsNone(L2capMatchers.SFrame(req_seq=4), timeout=timedelta(seconds=1))
-
- @metadata(
- pts_test_id="L2CAP/ERM/BV-05-C",
- pts_test_name="Resume Transmitting I-Frames when an S-Frame [RR] "
- "is Received")
def test_resume_transmitting_when_received_rr(self):
"""
- Verify the IUT will cease transmission of I-frames when the negotiated
- TxWindow is full. Verify the IUT will resume transmission of I-frames
- when an S-frame [RR] is received that acknowledges previously sent
- I-frames
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, tx_window_size=1)
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- dut_channel.send(b'abc')
- dut_channel.send(b'def')
+ L2CAP/ERM/BV-05-C [Resume Transmitting I-Frames when an S-Frame [RR] is Received]
+ Verify the IUT will cease transmission of I-frames when the negotiated TxWindow is full. Verify the
+ IUT will resume transmission of I-frames when an S-frame [RR] is received that acknowledges
+ previously sent I-frames.
+ """
+ self.ertm_tx_window_size = 1
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ dcid = self.scid_to_dcid[scid]
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'def'))
+
+ # TODO: Besides checking TxSeq, we also want to check payload, once we can get it from packet view
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0
+ )
+ cert_acl_data_asserts.assert_none_matching(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 1,
+ )
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.RECEIVER_READY,
+ l2cap_packets.Poll.NOT_SET, l2cap_packets.Final.POLL_RESPONSE,
+ 1)
+ self.cert_send_b_frame(s_frame)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 1
+ )
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0, payload=b'abc'))
- assertThat(cert_channel).emitsNone(L2capMatchers.IFrame(tx_seq=1, payload=b'def'))
-
- cert_channel.send_s_frame(req_seq=1, f=Final.POLL_RESPONSE)
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=1))
-
- @metadata(
- pts_test_id="L2CAP/ERM/BV-06-C", pts_test_name="Resume Transmitting I-Frames when an I-Frame is "
- "Received")
def test_resume_transmitting_when_acknowledge_previously_sent(self):
"""
- Verify the IUT will cease transmission of I-frames when the negotiated
- TxWindow is full. Verify the IUT will resume transmission of I-frames
- when an I-frame is received that acknowledges previously sent I-frames
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, tx_window_size=1)
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- dut_channel.send(b'abc')
- dut_channel.send(b'def')
-
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0, payload=b'abc'))
- assertThat(cert_channel).emitsNone(
- L2capMatchers.IFrame(tx_seq=1, payload=b'abc'), timeout=timedelta(seconds=0.5))
-
- cert_channel.send_i_frame(tx_seq=0, req_seq=1, payload=SAMPLE_PACKET)
-
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=1, payload=b'def'))
-
- cert_channel.send_i_frame(tx_seq=1, req_seq=2, payload=SAMPLE_PACKET)
-
- @metadata(pts_test_id="L2CAP/ERM/BV-07-C", pts_test_name="Send S-Frame [RNR]")
- def test_send_s_frame_rnr(self):
- """
- Verify the IUT sends an S-frame [RNR] when it detects local busy condition
- NOTE: In GD stack, we enter local busy condition if client doesn't dequeue
- and packets are accumulating in buffer
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, tx_window_size=10)
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM,
- fcs=FcsType.NO_FCS,
- req_config_options=config,
- rsp_config_options=config)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0, payload=b'abc'))
- cert_channel.send_i_frame(tx_seq=0, req_seq=1, payload=SAMPLE_PACKET)
-
- dut_channel.set_traffic_paused(True)
-
- # Allow 1 additional packet in channel queue buffer
- buffer_size = self.dut_l2cap.get_channel_queue_buffer_size() + 1
-
- for i in range(buffer_size):
- cert_channel.send_i_frame(tx_seq=i + 1, req_seq=1, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(s=l2cap_packets.SupervisoryFunction.RECEIVER_READY))
+ L2CAP/ERM/BV-06-C [Resume Transmitting I-Frames when an I-Frame is Received]
+ Verify the IUT will cease transmission of I-frames when the negotiated TxWindow is full. Verify the
+ IUT will resume transmission of I-frames when an I-frame is received that acknowledges previously
+ sent I-frames.
+ """
+ self.ertm_tx_window_size = 1
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ dcid = self.scid_to_dcid[scid]
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'def'))
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0
+ )
+ # TODO: If 1 second is greater than their retransmit timeout, use a smaller timeout
+ cert_acl_data_asserts.assert_none_matching(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 1,
+ timedelta(seconds=1))
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 0, l2cap_packets.Final.NOT_SET, 1,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 1
+ )
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 1, l2cap_packets.Final.NOT_SET, 2,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
- cert_channel.send_i_frame(tx_seq=buffer_size + 1, req_seq=1, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(s=l2cap_packets.SupervisoryFunction.RECEIVER_NOT_READY))
-
- @metadata(pts_test_id="L2CAP/ERM/BV-08-C", pts_test_name="Send S-Frame [RR] with Poll Bit Set")
def test_transmit_s_frame_rr_with_poll_bit_set(self):
"""
- Verify the IUT sends an S-frame [RR] with the Poll bit set when its
- retransmission timer expires.
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, retransmission_time_out=1500)
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM,
- fcs=FcsType.NO_FCS,
- req_config_options=config,
- rsp_config_options=config)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.SFrame(p=l2cap_packets.Poll.POLL))
+ L2CAP/ERM/BV-08-C [Send S-Frame [RR] with Poll Bit Set]
+ Verify the IUT sends an S-frame [RR] with the Poll bit set when its retransmission timer expires.
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ # TODO: Always use their retransmission timeout value
+ time.sleep(2)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_p_from_ertm_s_frame(scid, packet) == l2cap_packets.Poll.POLL
+ )
- @metadata(pts_test_id="L2CAP/ERM/BV-09-C", pts_test_name="Send S-Frame [RR] with Final Bit Set")
def test_transmit_s_frame_rr_with_final_bit_set(self):
"""
- Verify the IUT responds with an S-frame [RR] with the Final bit set
- after receiving an S-frame [RR] with the Poll bit set
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
-
- cert_channel.send_s_frame(req_seq=0, p=Poll.POLL)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(f=Final.POLL_RESPONSE))
-
- @metadata(pts_test_id="L2CAP/ERM/BV-10-C", pts_test_name="Retransmit S-Frame [RR] with Final Bit Set")
- def test_retransmit_s_frame_rr_with_poll_bit_set(self):
- """
- Verify the IUT will retransmit the S-frame [RR] with the Poll bit set
- when the Monitor Timer expires
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
- dut_channel.send(b'abc')
+ L2CAP/ERM/BV-09-C [Send S-Frame [RR] with Final Bit Set]
+ Verify the IUT responds with an S-frame [RR] with the Final bit set after receiving an S-frame [RR]
+ with the Poll bit set.
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.RECEIVER_READY,
+ l2cap_packets.Poll.POLL, l2cap_packets.Final.NOT_SET, 0)
+ self.cert_send_b_frame(s_frame)
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_f_from_ertm_s_frame(scid, packet) == l2cap_packets.Final.POLL_RESPONSE
+ )
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0, payload=b'abc'))
- assertThat(cert_channel).emits(L2capMatchers.SFrame(req_seq=0, p=Poll.POLL, f=Final.NOT_SET))
- cert_channel.send_s_frame(req_seq=1, f=Final.POLL_RESPONSE)
-
- @metadata(pts_test_id="L2CAP/ERM/BV-11-C", pts_test_name="S-Frame Transmissions Exceed MaxTransmit")
def test_s_frame_transmissions_exceed_max_transmit(self):
"""
+ L2CAP/ERM/BV-11-C [S-Frame Transmissions Exceed MaxTransmit]
Verify the IUT will close the channel when the Monitor Timer expires.
"""
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, tx_window_size=1, max_transmit=1, monitor_time_out=10)
+ asserts.skip("Need to configure DUT to have a shorter timer")
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+
+ # Retransmission timer = 2, 20 * monitor timer = 360, so total timeout is 362
+ time.sleep(362)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_disconnection_request)
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- dut_channel.send(b'abc')
- cert_channel.verify_disconnect_request()
-
- @metadata(pts_test_id="L2CAP/ERM/BV-12-C", pts_test_name="I-Frame Transmissions Exceed MaxTransmit")
def test_i_frame_transmissions_exceed_max_transmit(self):
"""
- Verify the IUT will close the channel when it receives an S-frame [RR]
- with the final bit set that does not acknowledge the previous I-frame
- sent by the IUT
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, tx_window_size=1, max_transmit=1)
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
+ L2CAP/ERM/BV-12-C [I-Frame Transmissions Exceed MaxTransmit]
+ Verify the IUT will close the channel when it receives an S-frame [RR] with the final bit set that does
+ not acknowledge the previous I-frame sent by the IUT.
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0
+ )
+
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.RECEIVER_READY,
+ l2cap_packets.Poll.NOT_SET, l2cap_packets.Final.POLL_RESPONSE,
+ 0)
+ self.cert_send_b_frame(s_frame)
+
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_disconnection_request)
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0), L2capMatchers.SFrame(p=Poll.POLL)).inOrder()
-
- cert_channel.send_s_frame(req_seq=0, f=Final.POLL_RESPONSE)
- cert_channel.verify_disconnect_request()
-
- @metadata(pts_test_id="L2CAP/ERM/BV-13-C", pts_test_name="Respond to S-Frame [REJ]")
def test_respond_to_rej(self):
"""
- Verify the IUT retransmits I-frames starting from the sequence number
- specified in the S-frame [REJ]
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, tx_window_size=2, max_transmit=2)
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- dut_channel.send(b'abc')
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(
- L2capMatchers.IFrame(tx_seq=0, payload=b'abc'), L2capMatchers.IFrame(tx_seq=1, payload=b'abc')).inOrder()
-
- cert_channel.send_s_frame(req_seq=0, s=SupervisoryFunction.REJECT)
-
- assertThat(cert_channel).emits(
- L2capMatchers.IFrame(tx_seq=0, payload=b'abc'), L2capMatchers.IFrame(tx_seq=1, payload=b'abc')).inOrder()
-
- @metadata(pts_test_id="L2CAP/ERM/BV-14-C", pts_test_name="Respond to S-Frame [SREJ] POLL Bit Set")
- def test_respond_to_srej_p_set(self):
- """
- Verify the IUT responds with the correct I-frame when sent an SREJ
- frame. Verify that the IUT processes the acknowledgment of previously
- unacknowledged I-frames
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, max_transmit=2, tx_window_size=3)
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- for _ in range(4):
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(
- L2capMatchers.IFrame(tx_seq=0, payload=b'abc'), L2capMatchers.IFrame(tx_seq=1, payload=b'abc'),
- L2capMatchers.IFrame(tx_seq=2, payload=b'abc')).inOrder()
-
- cert_channel.send_s_frame(req_seq=1, p=Poll.POLL, s=SupervisoryFunction.SELECT_REJECT)
-
- assertThat(cert_channel).emits(
- L2capMatchers.IFrame(tx_seq=1, payload=b'abc', f=Final.POLL_RESPONSE),
- L2capMatchers.IFrame(tx_seq=3, payload=b'abc')).inOrder()
-
- @metadata(pts_test_id="L2CAP/ERM/BV-15-C", pts_test_name="Respond to S-Frame [SREJ] POLL Bit Clear")
- def test_respond_to_srej_p_clear(self):
- """
- Verify the IUT responds with the correct I-frame when sent an SREJ frame
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, max_transmit=2, tx_window_size=3)
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- for _ in range(4):
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(
- L2capMatchers.IFrame(tx_seq=0, payload=b'abc'), L2capMatchers.IFrame(tx_seq=1, payload=b'abc'),
- L2capMatchers.IFrame(tx_seq=2, payload=b'abc')).inOrder()
-
- cert_channel.send_s_frame(req_seq=1, s=SupervisoryFunction.SELECT_REJECT)
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=1, payload=b'abc', f=Final.NOT_SET))
- cert_channel.send_s_frame(req_seq=3, s=SupervisoryFunction.RECEIVER_READY)
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=3, payload=b'abc', f=Final.NOT_SET))
-
- @metadata(pts_test_id="L2CAP/ERM/BV-16-C", pts_test_name="Send S-Frame [REJ]")
- def test_send_s_frame_rej(self):
- """
- Verify the IUT can send an S-Frame [REJ] after receiving out of sequence
- I-Frames
- """
- self._setup_link_from_cert()
- tx_window_size = 4
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, tx_window_size=tx_window_size)
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- cert_channel.send_i_frame(tx_seq=0, req_seq=0, f=Final.NOT_SET, payload=SAMPLE_PACKET)
- cert_channel.send_i_frame(tx_seq=2, req_seq=0, f=Final.NOT_SET, payload=SAMPLE_PACKET)
-
- assertThat(cert_channel).emits(
- L2capMatchers.SFrame(req_seq=1, f=Final.NOT_SET, s=SupervisoryFunction.REJECT, p=Poll.NOT_SET))
+ L2CAP/ERM/BV-13-C [Respond to S-Frame [REJ]]
+ Verify the IUT retransmits I-frames starting from the sequence number specified in the S-frame [REJ].
+ """
+ self.ertm_tx_window_size = 2
+ self.ertm_max_transmit = 2
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ for i in range(2):
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == i,
+ timeout=timedelta(seconds=0.5))
+
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.REJECT,
+ l2cap_packets.Poll.NOT_SET, l2cap_packets.Final.NOT_SET, 0)
+ self.cert_send_b_frame(s_frame)
+
+ for i in range(2):
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == i,
+ timeout=timedelta(seconds=0.5))
- for i in range(1, tx_window_size):
- cert_channel.send_i_frame(tx_seq=i, req_seq=0, f=Final.NOT_SET, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(
- L2capMatchers.SFrame(req_seq=i + 1, f=Final.NOT_SET, s=SupervisoryFunction.RECEIVER_READY))
-
- @metadata(pts_test_id="L2CAP/ERM/BV-18-C", pts_test_name="Receive S-Frame [RR] Final Bit = 1")
def test_receive_s_frame_rr_final_bit_set(self):
"""
- Verify the IUT will retransmit any previously sent I-frames
- unacknowledged by receipt of an S-Frame [RR] with the Final Bit set
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, retransmission_time_out=1500)
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- dut_channel.send(b'abc')
+ L2CAP/ERM/BV-18-C [Receive S-Frame [RR] Final Bit = 1]
+ Verify the IUT will retransmit any previously sent I-frames unacknowledged by receipt of an S-Frame
+ [RR] with the Final Bit set.
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+
+ # TODO: Always use their retransmission timeout value
+ time.sleep(2)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_p_from_ertm_s_frame(scid, packet) == l2cap_packets.Poll.POLL
+ )
+
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.RECEIVER_READY,
+ l2cap_packets.Poll.NOT_SET, l2cap_packets.Final.POLL_RESPONSE,
+ 0)
+ self.cert_send_b_frame(s_frame)
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0
+ )
- assertThat(cert_channel).emits(L2capMatchers.SFrame(p=l2cap_packets.Poll.POLL))
-
- cert_channel.send_s_frame(req_seq=0, f=Final.POLL_RESPONSE)
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0))
-
- @metadata(pts_test_id="L2CAP/ERM/BV-19-C", pts_test_name="Receive I-Frame Final Bit = 1")
def test_receive_i_frame_final_bit_set(self):
"""
- Verify the IUT will retransmit any previously sent I-frames
- unacknowledged by receipt of an I-frame with the final bit set
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, retransmission_time_out=1500)
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.SFrame(p=Poll.POLL))
-
- cert_channel.send_i_frame(tx_seq=0, req_seq=0, f=Final.POLL_RESPONSE, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0))
-
- @metadata(pts_test_id="L2CAP/ERM/BV-20-C", pts_test_name="Enter Remote Busy Condition")
- def test_receive_rnr(self):
- """
- Verify the IUT will not retransmit any I-frames when it receives a
- remote busy indication from the Lower Tester (S-frame [RNR])
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, retransmission_time_out=1500)
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.SFrame(p=l2cap_packets.Poll.POLL))
-
- cert_channel.send_s_frame(req_seq=0, s=SupervisoryFunction.RECEIVER_NOT_READY, f=Final.POLL_RESPONSE)
- assertThat(cert_channel).emitsNone(L2capMatchers.IFrame(tx_seq=0))
-
- @metadata(pts_test_id="L2CAP/ERM/BV-22-C", pts_test_name="Exit Local Busy Condition")
- def test_exit_local_busy_condition(self):
- """
- Verify the IUT sends an S-frame [RR] Poll = 1 when the local busy condition is cleared
- NOTE: In GD stack, we enter local busy condition if client doesn't dequeue
- and packets are accumulating in buffer
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, tx_window_size=10)
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM,
- fcs=FcsType.NO_FCS,
- req_config_options=config,
- rsp_config_options=config)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0, payload=b'abc'))
- cert_channel.send_i_frame(tx_seq=0, req_seq=1, payload=SAMPLE_PACKET)
-
- dut_channel.set_traffic_paused(True)
+ L2CAP/ERM/BV-19-C [Receive I-Frame Final Bit = 1]
+ Verify the IUT will retransmit any previously sent I-frames unacknowledged by receipt of an I-frame
+ with the final bit set.
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+
+ # TODO: Always use their retransmission timeout value
+ time.sleep(2)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_p_from_ertm_s_frame(scid, packet) == l2cap_packets.Poll.POLL
+ )
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 0, l2cap_packets.Final.POLL_RESPONSE, 0,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0
+ )
+
+ def test_recieve_rnr(self):
+ """
+ L2CAP/ERM/BV-20-C [Enter Remote Busy Condition]
+ Verify the IUT will not retransmit any I-frames when it receives a remote busy indication from the
+ Lower Tester (S-frame [RNR]).
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=0x33, payload=b'abc'))
+
+ # TODO: Always use their retransmission timeout value
+ time.sleep(2)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_p_from_ertm_s_frame(scid, packet) == l2cap_packets.Poll.POLL
+ )
+
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.RECEIVER_NOT_READY,
+ l2cap_packets.Poll.NOT_SET, l2cap_packets.Final.POLL_RESPONSE,
+ 0)
+ self.cert_send_b_frame(s_frame)
+
+ cert_acl_data_asserts.assert_none_matching(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0
+ )
- # Allow 1 additional packet in channel queue buffer
- buffer_size = self.dut_l2cap.get_channel_queue_buffer_size() + 1
-
- for i in range(buffer_size):
- cert_channel.send_i_frame(tx_seq=i + 1, req_seq=1, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(s=l2cap_packets.SupervisoryFunction.RECEIVER_READY))
-
- cert_channel.send_i_frame(tx_seq=buffer_size + 1, req_seq=1, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(s=l2cap_packets.SupervisoryFunction.RECEIVER_NOT_READY))
-
- dut_channel.set_traffic_paused(False)
- assertThat(cert_channel).emits(
- L2capMatchers.SFrame(s=l2cap_packets.SupervisoryFunction.RECEIVER_READY, p=l2cap_packets.Poll.POLL))
- cert_channel.send_s_frame(1, f=l2cap_packets.Final.POLL_RESPONSE)
-
- @metadata(pts_test_id="L2CAP/ERM/BV-23-C", pts_test_name="Transmit I-Frames using SAR")
- def test_transmit_i_frames_using_sar(self):
- """
- Verify the IUT can send correctly formatted sequential I-frames with
- valid values for the enhanced control fields (SAR, F-bit, ReqSeq,
- TxSeq) when performing SAR.
- """
- self._setup_link_from_cert()
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, mps=11)
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- dut_channel.send(b'abcabcabc')
- # First IFrame should contain SDU size after control field
- assertThat(cert_channel).emits(
- L2capMatchers.IFrameStart(tx_seq=0, payload=b'abc'), L2capMatchers.IFrame(tx_seq=1, payload=b'abc'),
- L2capMatchers.IFrame(tx_seq=2, payload=b'abc')).inOrder()
-
- cert_channel.send_s_frame(req_seq=3, s=SupervisoryFunction.RECEIVER_READY)
-
- dut_channel.send(b'defdefdef')
- # First IFrame should contain SDU size after control field
- assertThat(cert_channel).emits(
- L2capMatchers.IFrameStart(tx_seq=3, payload=b'def'), L2capMatchers.IFrame(tx_seq=4, payload=b'def'),
- L2capMatchers.IFrame(tx_seq=5, payload=b'def')).inOrder()
-
- @metadata(pts_test_id="L2CAP/ERM/BI-01-C", pts_test_name="S-Frame [REJ] Lost or Corrupted")
def test_sent_rej_lost(self):
"""
- Verify the IUT can handle receipt of an S-=frame [RR] Poll = 1 if the
- S-frame [REJ] sent from the IUT is lost
- """
- self._setup_link_from_cert()
- ertm_tx_window_size = 5
-
- config = CertL2cap.config_option_ertm(fcs=FcsType.NO_FCS, tx_window_size=ertm_tx_window_size)
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, req_config_options=config, rsp_config_options=config)
-
- cert_channel.send_i_frame(tx_seq=0, req_seq=0, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(req_seq=1))
+ L2CAP/ERM/BI-01-C [S-Frame [REJ] Lost or Corrupted]
+ Verify the IUT can handle receipt of an S-=frame [RR] Poll = 1 if the S-frame [REJ] sent from the IUT
+ is lost.
+ """
+ self.ertm_tx_window_size = 5
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 0, l2cap_packets.Final.NOT_SET, 0,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_req_seq_from_ertm_s_frame(scid, packet) == 1
+ )
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, self.ertm_tx_window_size - 1, l2cap_packets.Final.NOT_SET,
+ 0, l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_s_from_ertm_s_frame(scid, packet) == l2cap_packets.SupervisoryFunction.REJECT
+ )
+
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.RECEIVER_READY,
+ l2cap_packets.Poll.POLL, l2cap_packets.Final.NOT_SET, 0)
+ self.cert_send_b_frame(s_frame)
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_req_seq_from_ertm_s_frame(scid, packet) == 1 and self.get_f_from_ertm_s_frame(scid, packet) == l2cap_packets.Final.POLL_RESPONSE)
+ for i in range(1, self.ertm_tx_window_size):
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, i, l2cap_packets.Final.NOT_SET, 0,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_req_seq_from_ertm_s_frame(scid, packet) == i + 1
+ )
- cert_channel.send_i_frame(tx_seq=ertm_tx_window_size - 1, req_seq=0, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(s=SupervisoryFunction.REJECT))
-
- cert_channel.send_s_frame(req_seq=0, p=Poll.POLL)
-
- assertThat(cert_channel).emits(L2capMatchers.SFrame(req_seq=1, f=l2cap_packets.Final.POLL_RESPONSE))
- for i in range(1, ertm_tx_window_size):
- cert_channel.send_i_frame(tx_seq=i, req_seq=0, payload=SAMPLE_PACKET)
- assertThat(cert_channel).emits(L2capMatchers.SFrame(req_seq=i + 1))
-
- @metadata(pts_test_id="L2CAP/ERM/BI-03-C", pts_test_name="Handle Duplicate S-Frame [SREJ]")
def test_handle_duplicate_srej(self):
"""
- Verify the IUT will only retransmit the requested I-frame once after
- receiving a duplicate SREJ
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
+ L2CAP/ERM/BI-03-C [Handle Duplicate S-Frame [SREJ]]
+ Verify the IUT will only retransmit the requested I-frame once after receiving a duplicate SREJ.
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0,
+ timeout=timedelta(0.5))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 1,
+ timeout=timedelta(0.5))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_p_from_ertm_s_frame(scid, packet) == l2cap_packets.Poll.POLL
+ )
+
+ # Send SREJ with F not set
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.SELECT_REJECT,
+ l2cap_packets.Poll.NOT_SET, l2cap_packets.Final.NOT_SET, 0)
+ self.cert_send_b_frame(s_frame)
+
+ cert_acl_data_asserts.assert_none(timeout=timedelta(seconds=0.5))
+ # Send SREJ with F set
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.SELECT_REJECT,
+ l2cap_packets.Poll.NOT_SET, l2cap_packets.Final.POLL_RESPONSE,
+ 0)
+ self.cert_send_b_frame(s_frame)
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0
+ )
- dut_channel.send(b'abc')
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(
- L2capMatchers.IFrame(tx_seq=0), L2capMatchers.IFrame(tx_seq=1),
- L2capMatchers.SFrame(p=Poll.POLL)).inOrder()
-
- cert_channel.send_s_frame(req_seq=0, s=SupervisoryFunction.SELECT_REJECT)
- assertThat(cert_channel).emitsNone(timeout=timedelta(seconds=0.5))
-
- cert_channel.send_s_frame(req_seq=0, s=SupervisoryFunction.SELECT_REJECT, f=Final.POLL_RESPONSE)
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0))
-
- @metadata(
- pts_test_id="L2CAP/ERM/BI-04-C",
- pts_test_name="Handle Receipt of S-Frame [REJ] and S-Frame "
- "[RR, F=1] that Both Require Retransmission of the "
- "Same I-Frames")
def test_handle_receipt_rej_and_rr_with_f_set(self):
"""
- Verify the IUT will only retransmit the requested I-frames once after
- receiving an S-frame [REJ] followed by an S-frame [RR] with the Final
- bit set that indicates the same I-frames should be retransmitted
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
-
- dut_channel.send(b'abc')
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(
- L2capMatchers.IFrame(tx_seq=0),
- L2capMatchers.IFrame(tx_seq=1),
- L2capMatchers.SFrame(p=l2cap_packets.Poll.POLL)).inOrder()
-
- cert_channel.send_s_frame(req_seq=0, s=SupervisoryFunction.REJECT)
- assertThat(cert_channel).emitsNone(timeout=timedelta(seconds=0.5))
-
- # Send RR with F set
- cert_channel.send_s_frame(req_seq=0, s=SupervisoryFunction.REJECT, f=Final.POLL_RESPONSE)
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0))
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=1))
-
- @metadata(
- pts_test_id="L2CAP/ERM/BI-05-C",
- pts_test_name="Handle receipt of S-Frame [REJ] and I-Frame [F=1] "
- "that Both Require Retransmission of the Same "
- "I-Frames")
- def test_handle_rej_and_i_frame_with_f_set(self):
- """
- Verify the IUT will only retransmit the requested I-frames once after
- receiving an S-frame [REJ] followed by an I-frame with the Final bit
- set that indicates the same I-frames should be retransmitted
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM, fcs=FcsType.NO_FCS)
-
- dut_channel.send(b'abc')
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(
- L2capMatchers.IFrame(tx_seq=0),
- L2capMatchers.IFrame(tx_seq=1),
- L2capMatchers.SFrame(p=l2cap_packets.Poll.POLL)).inOrder()
-
- # Send SREJ with F not set
- cert_channel.send_s_frame(req_seq=0, s=SupervisoryFunction.SELECT_REJECT)
- assertThat(cert_channel).emitsNone(timeout=timedelta(seconds=0.5))
+ L2CAP/ERM/BI-04-C [Handle Receipt of S-Frame [REJ] and S-Frame [RR, F=1] that Both Require Retransmission of the Same I-Frames]
+ Verify the IUT will only retransmit the requested I-frames once after receiving an S-frame [REJ]
+ followed by an S-frame [RR] with the Final bit set that indicates the same I-frames should be
+ retransmitted.
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0,
+ timeout=timedelta(0.5))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 1,
+ timeout=timedelta(0.5))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_p_from_ertm_s_frame(scid, packet) == l2cap_packets.Poll.POLL,
+ timeout=timedelta(2))
+
+ # Send REJ with F not set
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.REJECT,
+ l2cap_packets.Poll.NOT_SET, l2cap_packets.Final.NOT_SET, 0)
+ self.cert_send_b_frame(s_frame)
+
+ cert_acl_data_asserts.assert_none(timeout=timedelta(seconds=0.5))
+
+ # Send RR with F set
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.REJECT,
+ l2cap_packets.Poll.NOT_SET, l2cap_packets.Final.POLL_RESPONSE,
+ 0)
+ self.cert_send_b_frame(s_frame)
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0
+ )
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 1
+ )
- cert_channel.send_i_frame(tx_seq=0, req_seq=0, f=Final.POLL_RESPONSE, payload=SAMPLE_PACKET)
-
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=0))
- assertThat(cert_channel).emits(L2capMatchers.IFrame(tx_seq=1))
-
- @metadata(
- pts_test_id="L2CAP/CMC/BV-01-C", pts_test_name="IUT Initiated Configuration of Enhanced "
- "Retransmission Mode")
- def test_initiated_configuration_request_ertm(self):
- """
- Verify the IUT can send a Configuration Request command containing the
- F&EC option that specifies Enhanced Retransmission Mode
+ def test_handle_rej_and_i_frame_with_f_set(self):
"""
- self._setup_link_from_cert()
+ L2CAP/ERM/BI-05-C [Handle receipt of S-Frame [REJ] and I-Frame [F=1] that Both Require Retransmission of the Same I-Frames]
+ Verify the IUT will only retransmit the requested I-frames once after receiving an S-frame [REJ]
+ followed by an I-frame with the Final bit set that indicates the same I-frames should be retransmitted.
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # FIXME: Order shouldn't matter here
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+
+ dcid = self.scid_to_dcid[scid]
+
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ self.device_under_test.l2cap.SendDynamicChannelPacket(
+ l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0,
+ timeout=timedelta(0.5))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 1,
+ timeout=timedelta(0.5))
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_p_from_ertm_s_frame(scid, packet) == l2cap_packets.Poll.POLL,
+ timeout=timedelta(2))
+
+ # Send SREJ with F not set
+ s_frame = l2cap_packets.EnhancedSupervisoryFrameBuilder(
+ dcid, l2cap_packets.SupervisoryFunction.SELECT_REJECT,
+ l2cap_packets.Poll.NOT_SET, l2cap_packets.Final.NOT_SET, 0)
+ self.cert_send_b_frame(s_frame)
+
+ cert_acl_data_asserts.assert_none(timeout=timedelta(seconds=0.5))
+
+ i_frame = l2cap_packets.EnhancedInformationFrameBuilder(
+ dcid, 0, l2cap_packets.Final.POLL_RESPONSE, 0,
+ l2cap_packets.SegmentationAndReassembly.UNSEGMENTED,
+ SAMPLE_PACKET)
+ self.cert_send_b_frame(i_frame)
+
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 0
+ )
+ cert_acl_data_asserts.assert_event_occurs(
+ lambda packet: self.get_tx_seq_from_ertm_i_frame(scid, packet) == 1
+ )
+
+ def test_initiated_configurtion_request_ertm(self):
+ """
+ L2CAP/CMC/BV-01-C [IUT Initiated Configuration of Enhanced Retransmission Mode]
+ Verify the IUT can send a Configuration Request command containing the F&EC option that specifies
+ Enhanced Retransmission Mode.
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ self.on_connection_response = self._on_connection_response_use_ertm
+
+ psm = 0x33
+ scid = 0x41
+ self._open_channel(
+ cert_acl_data_stream,
+ 1,
+ cert_acl_handle,
+ scid,
+ psm,
+ mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM)
+
+ # TODO: Fix this test. It doesn't work so far with PDL struct
+
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_request)
+ asserts.skip("Struct not working")
- self._open_unconfigured_channel_from_cert(scid=0x41, psm=0x33, mode=RetransmissionFlowControlMode.ERTM)
-
- assertThat(self.cert_l2cap.get_control_channel()).emits(L2capMatchers.ConfigurationRequestWithErtm())
-
- @metadata(
- pts_test_id="L2CAP/CMC/BV-02-C",
- pts_test_name="Lower Tester Initiated Configuration of Enhanced "
- "Retransmission Mode")
def test_respond_configuration_request_ertm(self):
"""
- Verify the IUT can accept a Configuration Request from the Lower Tester
- containing an F&EC option that specifies Enhanced Retransmission Mode
- """
- self._setup_link_from_cert()
-
- self._open_channel_from_dut(psm=0x33, mode=RetransmissionFlowControlMode.ERTM)
-
- @metadata(
- pts_test_id="L2CAP/CMC/BV-12-C",
- pts_test_name="ERTM Not Supported by Lower Tester for Mandatory "
- "ERTM channel")
- def test_respond_not_support_ertm_when_using_mandatory_ertm(self):
- """
- The IUT is initiating connection of an L2CAP channel that mandates use
- of ERTM. Verify the IUT will not attempt to configure the connection to
- ERTM if the Lower Tester has not indicated support for ERTM in the
- Information Response [Extended Features]
- """
- self._setup_link_from_cert()
- self.cert_l2cap.claim_ertm_unsupported()
- dut_channel_future = self.dut_l2cap.connect_dynamic_channel_to_cert(
- psm=0x33, mode=RetransmissionFlowControlMode.ERTM)
- assertThat(self.cert_l2cap.get_control_channel()).emitsNone(L2capMatchers.ConnectionRequest(0x33))
-
- @metadata(
- pts_test_id="L2CAP/CMC/BI-01-C",
- pts_test_name="Failed Configuration of Enhanced Retransmission "
- "Mode when use of the Mode is Mandatory]")
- def test_config_respond_basic_mode_when_using_mandatory_ertm(self):
- """
- When creating a connection for a PSM that mandates the use of ERTM
- verify the IUT can handle receipt (close the channel in accordance with
- the specification) of a Configure Response indicating the peer L2CAP
- entity doesn’t wish to use Enhanced Retransmission Mode (Configure
- Response Result = Reject Unacceptable Parameters)
- """
-
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_channel_from_cert(
- mode=RetransmissionFlowControlMode.ERTM,
- req_config_options=CertL2cap.config_option_ertm(),
- rsp_config_options=CertL2cap.config_option_basic_explicit())
-
- cert_channel.verify_disconnect_request()
-
- @metadata(
- pts_test_id="L2CAP/CMC/BI-02-C",
- pts_test_name="Configuration Mode mismatch when use of Enhanced "
- "Retransmission Mode is Mandatory")
- def test_config_request_basic_mode_when_using_mandatory_ertm(self):
- """
- When creating a connection for a PSM that mandates the use of ERTM,
- verify the IUT will close the channel if the Lower Tester attempts to
- configure Basic Mode.
- """
- self._setup_link_from_cert()
-
- (dut_channel, cert_channel) = self._open_unconfigured_channel_from_cert(mode=RetransmissionFlowControlMode.ERTM)
- cert_channel.send_configure_request(CertL2cap.config_option_basic_explicit())
- cert_channel.verify_disconnect_request()
-
- def test_initiate_connection_for_security(self):
- """
- This will test the PyL2cap API for initiating a connection for security
- via the security api
- """
- self.dut.neighbor.EnablePageScan(neighbor_facade.EnableMsg(enabled=True))
- self.cert.neighbor.EnablePageScan(neighbor_facade.EnableMsg(enabled=True))
- self.dut_l2cap.initiate_connection_for_security()
- self.cert_l2cap.accept_incoming_connection()
- self.dut_l2cap.verify_security_connection()
+ L2CAP/CMC/BV-02-C [Lower Tester Initiated Configuration of Enhanced Retransmission Mode]
+ Verify the IUT can accept a Configuration Request from the Lower Tester containing an F&EC option
+ that specifies Enhanced Retransmission Mode.
+ """
+ cert_acl_handle = self._setup_link_from_cert()
+ with EventCallbackStream(
+ self.cert_device.hci_acl_manager.FetchAclData(
+ empty_proto.Empty())) as cert_acl_data_stream:
+ cert_acl_data_asserts = EventAsserts(cert_acl_data_stream)
+ cert_acl_data_stream.register_callback(self._handle_control_packet)
+ psm = 1
+ scid = 0x0101
+ self.retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
+ self.device_under_test.l2cap.SetDynamicChannel(
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=self.retransmission_mode))
+
+ open_channel = l2cap_packets.ConnectionRequestBuilder(1, psm, scid)
+ open_channel_l2cap = l2cap_packets.BasicFrameBuilder(
+ 1, open_channel)
+ self.cert_send_b_frame(open_channel_l2cap)
+
+ # TODO: Verify that the type should be ERTM
+ cert_acl_data_asserts.assert_event_occurs(
+ self.is_correct_configuration_response)
diff --git a/gd/l2cap/classic/cert/pts_l2cap_test.py b/gd/l2cap/classic/cert/pts_l2cap_test.py
index cf8ed4ea1..68c2751ef 100644
--- a/gd/l2cap/classic/cert/pts_l2cap_test.py
+++ b/gd/l2cap/classic/cert/pts_l2cap_test.py
@@ -17,7 +17,8 @@ from datetime import timedelta
import time
from cert.pts_base_test import PTSBaseTestClass
-from cert.event_stream import EventStream
+from cert.event_asserts import EventAsserts
+from cert.event_callback_stream import EventCallbackStream
from facade import common_pb2
from facade import rootservice_pb2 as facade_rootservice_pb2
from l2cap.classic import facade_pb2 as l2cap_facade_pb2
@@ -32,35 +33,48 @@ class PTSL2capTest(PTSBaseTestClass):
self.device_under_test.rootservice.StartStack(
facade_rootservice_pb2.StartStackRequest(
- module_under_test=facade_rootservice_pb2.BluetoothModule.Value('L2CAP'),))
+ module_under_test=facade_rootservice_pb2.BluetoothModule.Value(
+ 'L2CAP'),))
self.device_under_test.wait_channel_ready()
- dut_address = self.device_under_test.controller_read_only_property.ReadLocalAddress(empty_pb2.Empty()).address
+ dut_address = self.device_under_test.controller_read_only_property.ReadLocalAddress(
+ empty_pb2.Empty()).address
pts_address = self.controller_configs.get('pts_address').lower()
self.device_under_test.address = dut_address
- self.dut_address = common_pb2.BluetoothAddress(address=self.device_under_test.address)
- self.pts_address = common_pb2.BluetoothAddress(address=str.encode(pts_address))
+ self.dut_address = common_pb2.BluetoothAddress(
+ address=self.device_under_test.address)
+ self.pts_address = common_pb2.BluetoothAddress(
+ address=str.encode(pts_address))
- self.device_under_test.neighbor.EnablePageScan(neighbor_facade.EnableMsg(enabled=True))
+ self.device_under_test.neighbor.EnablePageScan(
+ neighbor_facade.EnableMsg(enabled=True))
def teardown_test(self):
- self.device_under_test.rootservice.StopStack(facade_rootservice_pb2.StopStackRequest())
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice_pb2.StopStackRequest())
def _dut_connection_stream(self):
- return EventStream(self.device_under_test.l2cap.FetchConnectionComplete(empty_pb2.Empty()))
+ return EventCallbackStream(
+ self.device_under_test.l2cap.FetchConnectionComplete(
+ empty_pb2.Empty()))
def _dut_connection_close_stream(self):
- return EventStream(self.device_under_test.l2cap.FetchConnectionClose(empty_pb2.Empty()))
+ return EventCallbackStream(
+ self.device_under_test.l2cap.FetchConnectionClose(
+ empty_pb2.Empty()))
- def _assert_connection_complete(self, dut_connection_stream, timeout=30):
- dut_connection_stream.assert_event_occurs(
- lambda device: device.remote.address == self.pts_address.address, timeout=timedelta(seconds=timeout))
+ def _assert_connection_complete(self, due_connection_asserts, timeout=30):
+ due_connection_asserts.assert_event_occurs(
+ lambda device: device.remote.address == self.pts_address.address,
+ timeout=timedelta(seconds=timeout))
- def _assert_connection_close(self, dut_connection_close_stream, timeout=30):
- dut_connection_close_stream.assert_event_occurs(
- lambda device: device.remote.address == self.pts_address.address, timeout=timedelta(seconds=timeout))
+ def _assert_connection_close(self, due_connection_close_asserts,
+ timeout=30):
+ due_connection_close_asserts.assert_event_occurs(
+ lambda device: device.remote.address == self.pts_address.address,
+ timeout=timedelta(seconds=timeout))
def test_L2CAP_IEX_BV_01_C(self):
"""
@@ -69,7 +83,9 @@ class PTSL2capTest(PTSBaseTestClass):
Specification 1.2 features.
"""
psm = 1
- self.device_under_test.l2cap.OpenChannel(l2cap_facade_pb2.OpenChannelRequest(remote=self.pts_address, psm=psm))
+ self.device_under_test.l2cap.OpenChannel(
+ l2cap_facade_pb2.OpenChannelRequest(
+ remote=self.pts_address, psm=psm))
time.sleep(5)
def test_L2CAP_IEX_BV_02_C(self):
@@ -81,7 +97,8 @@ class PTSL2capTest(PTSBaseTestClass):
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
time.sleep(20)
def test_L2CAP_EXF_BV_01_C(self):
@@ -94,7 +111,8 @@ class PTSL2capTest(PTSBaseTestClass):
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
time.sleep(5)
def test_L2CAP_EXF_BV_03_C(self):
@@ -106,7 +124,8 @@ class PTSL2capTest(PTSBaseTestClass):
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
time.sleep(5)
def test_L2CAP_CMC_BV_01_C(self):
@@ -116,11 +135,14 @@ class PTSL2capTest(PTSBaseTestClass):
Enhanced Retransmission Mode.
"""
with self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_CMC_BV_02_C(self):
"""
@@ -129,11 +151,14 @@ class PTSL2capTest(PTSBaseTestClass):
that specifies Enhanced Retransmission Mode.
"""
with self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_01_C(self):
"""
@@ -143,18 +168,22 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_02_C(self):
"""
@@ -163,12 +192,16 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_03_C(self):
"""
@@ -176,12 +209,16 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_05_C(self):
"""
@@ -192,17 +229,22 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
self.device_under_test.l2cap.SetDynamicChannel(
l2cap_facade_pb2.SetEnableDynamicChannelRequest(
- psm=psm, retransmission_mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM))
- self._assert_connection_complete(dut_connection_stream)
+ psm=psm,
+ retransmission_mode=l2cap_facade_pb2.
+ RetransmissionFlowControlMode.ERTM))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_06_C(self):
"""
@@ -213,17 +255,22 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
self.device_under_test.l2cap.SetDynamicChannel(
l2cap_facade_pb2.SetEnableDynamicChannelRequest(
- psm=psm, retransmission_mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM))
- self._assert_connection_complete(dut_connection_stream)
+ psm=psm,
+ retransmission_mode=l2cap_facade_pb2.
+ RetransmissionFlowControlMode.ERTM))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_08_C(self):
"""
@@ -232,14 +279,18 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_09_C(self):
"""
@@ -249,12 +300,16 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_10_C(self):
"""
@@ -263,14 +318,18 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_13_C(self):
"""
@@ -278,17 +337,22 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
self.device_under_test.l2cap.SetDynamicChannel(
l2cap_facade_pb2.SetEnableDynamicChannelRequest(
- psm=psm, retransmission_mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM))
- self._assert_connection_complete(dut_connection_stream)
+ psm=psm,
+ retransmission_mode=l2cap_facade_pb2.
+ RetransmissionFlowControlMode.ERTM))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_16_C(self):
"""
@@ -297,13 +361,19 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
self.device_under_test.l2cap.SetDynamicChannel(
l2cap_facade_pb2.SetEnableDynamicChannelRequest(
- psm=psm, retransmission_mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM))
- self._assert_connection_complete(dut_connection_stream)
- self._assert_connection_close(dut_connection_close_stream, timeout=60)
+ psm=psm,
+ retransmission_mode=l2cap_facade_pb2.
+ RetransmissionFlowControlMode.ERTM))
+ self._assert_connection_complete(due_connection_asserts)
+ self._assert_connection_close(
+ due_connection_close_asserts, timeout=60)
def test_L2CAP_ERM_BV_18_C(self):
"""
@@ -313,14 +383,18 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_19_C(self):
"""
@@ -330,14 +404,18 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BV_20_C(self):
"""
@@ -347,14 +425,18 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_COS_CED_BV_01_C(self):
"""
@@ -364,13 +446,18 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
self.device_under_test.l2cap.OpenChannel(
- l2cap_facade_pb2.OpenChannelRequest(remote=self.pts_address, psm=psm))
- self._assert_connection_complete(dut_connection_stream)
+ l2cap_facade_pb2.OpenChannelRequest(
+ remote=self.pts_address, psm=psm))
+ self._assert_connection_complete(due_connection_asserts)
- self.device_under_test.l2cap.CloseChannel(l2cap_facade_pb2.CloseChannelRequest(psm=psm))
- self._assert_connection_close(dut_connection_close_stream)
+ self.device_under_test.l2cap.CloseChannel(
+ l2cap_facade_pb2.CloseChannelRequest(psm=psm))
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_COS_CED_BV_03_C(self):
"""
@@ -379,15 +466,20 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
- l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc' * 34))
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.DynamicChannelPacket(
+ psm=psm, payload=b'abc' * 34))
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_COS_CED_BV_04_C(self):
"""
@@ -396,14 +488,19 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
time.sleep(2)
- self.device_under_test.l2cap.CloseChannel(l2cap_facade_pb2.CloseChannelRequest(psm=psm))
- self._assert_connection_close(dut_connection_close_stream)
+ self.device_under_test.l2cap.CloseChannel(
+ l2cap_facade_pb2.CloseChannelRequest(psm=psm))
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_COS_CED_BV_05_C(self):
"""
@@ -412,12 +509,16 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_COS_CED_BV_07_C(self):
"""
@@ -426,12 +527,16 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_COS_CED_BV_08_C(self):
"""
@@ -440,10 +545,14 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
time.sleep(120)
def test_L2CAP_COS_CED_BV_09_C(self):
@@ -453,12 +562,16 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_COS_CED_BV_11_C(self):
"""
@@ -467,12 +580,16 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_COS_CED_BI_01_C(self):
"""
@@ -481,11 +598,15 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
time.sleep(5)
def test_L2CAP_COS_CFD_BV_03_C(self):
@@ -496,11 +617,15 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.BASIC
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_COS_CFD_BV_08_C(self):
"""
@@ -510,13 +635,18 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
self.device_under_test.l2cap.OpenChannel(
- l2cap_facade_pb2.OpenChannelRequest(remote=self.pts_address, psm=psm))
- self._assert_connection_complete(dut_connection_stream)
- self.device_under_test.l2cap.CloseChannel(l2cap_facade_pb2.CloseChannelRequest(psm=psm))
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.OpenChannelRequest(
+ remote=self.pts_address, psm=psm))
+ self._assert_connection_complete(due_connection_asserts)
+ self.device_under_test.l2cap.CloseChannel(
+ l2cap_facade_pb2.CloseChannelRequest(psm=psm))
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BI_01_C(self):
"""
@@ -526,12 +656,16 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
retransmission_mode = l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM
self.device_under_test.l2cap.SetDynamicChannel(
- l2cap_facade_pb2.SetEnableDynamicChannelRequest(psm=psm, retransmission_mode=retransmission_mode))
- self._assert_connection_complete(dut_connection_stream)
- self._assert_connection_close(dut_connection_close_stream)
+ l2cap_facade_pb2.SetEnableDynamicChannelRequest(
+ psm=psm, retransmission_mode=retransmission_mode))
+ self._assert_connection_complete(due_connection_asserts)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BI_03_C(self):
"""
@@ -539,17 +673,22 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
self.device_under_test.l2cap.SetDynamicChannel(
l2cap_facade_pb2.SetEnableDynamicChannelRequest(
- psm=psm, retransmission_mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM))
- self._assert_connection_complete(dut_connection_stream)
+ psm=psm,
+ retransmission_mode=l2cap_facade_pb2.
+ RetransmissionFlowControlMode.ERTM))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BI_04_C(self):
"""
@@ -558,17 +697,22 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
self.device_under_test.l2cap.SetDynamicChannel(
l2cap_facade_pb2.SetEnableDynamicChannelRequest(
- psm=psm, retransmission_mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM))
- self._assert_connection_complete(dut_connection_stream)
+ psm=psm,
+ retransmission_mode=l2cap_facade_pb2.
+ RetransmissionFlowControlMode.ERTM))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
def test_L2CAP_ERM_BI_05_C(self):
"""
@@ -577,14 +721,19 @@ class PTSL2capTest(PTSBaseTestClass):
"""
with self._dut_connection_stream() as dut_connection_stream, \
self._dut_connection_close_stream() as dut_connection_close_stream:
+ due_connection_asserts = EventAsserts(dut_connection_stream)
+ due_connection_close_asserts = EventAsserts(
+ dut_connection_close_stream)
psm = 1
self.device_under_test.l2cap.SetDynamicChannel(
l2cap_facade_pb2.SetEnableDynamicChannelRequest(
- psm=psm, retransmission_mode=l2cap_facade_pb2.RetransmissionFlowControlMode.ERTM))
- self._assert_connection_complete(dut_connection_stream)
+ psm=psm,
+ retransmission_mode=l2cap_facade_pb2.
+ RetransmissionFlowControlMode.ERTM))
+ self._assert_connection_complete(due_connection_asserts)
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
self.device_under_test.l2cap.SendDynamicChannelPacket(
l2cap_facade_pb2.DynamicChannelPacket(psm=psm, payload=b'abc'))
- self._assert_connection_close(dut_connection_close_stream)
+ self._assert_connection_close(due_connection_close_asserts)
diff --git a/gd/l2cap/classic/dynamic_channel_configuration_option.h b/gd/l2cap/classic/dynamic_channel_configuration_option.h
index 2d8de2913..3f3cc02cc 100644
--- a/gd/l2cap/classic/dynamic_channel_configuration_option.h
+++ b/gd/l2cap/classic/dynamic_channel_configuration_option.h
@@ -30,7 +30,6 @@ struct DynamicChannelConfigurationOption {
enum class RetransmissionAndFlowControlMode {
L2CAP_BASIC,
ENHANCED_RETRANSMISSION,
- ENHANCED_RETRANSMISSION_OPTIONAL,
};
/**
* Retransmission and flow control mode. Currently L2CAP_BASIC and ENHANCED_RETRANSMISSION.
@@ -42,11 +41,6 @@ struct DynamicChannelConfigurationOption {
* Maximum SDU size that the L2CAP Channel user is able to process.
*/
Mtu incoming_mtu = kDefaultClassicMtu;
-
- /**
- * Minimum MTU that we enforce the remote channel to have
- */
- Mtu minimal_remote_mtu = kMinimumClassicMtu;
};
} // namespace classic
diff --git a/gd/l2cap/classic/dynamic_channel_manager.cc b/gd/l2cap/classic/dynamic_channel_manager.cc
index 8620086bb..dbbd465b8 100644
--- a/gd/l2cap/classic/dynamic_channel_manager.cc
+++ b/gd/l2cap/classic/dynamic_channel_manager.cc
@@ -24,35 +24,38 @@ namespace bluetooth {
namespace l2cap {
namespace classic {
-void DynamicChannelManager::ConnectChannel(
- hci::Address device,
- DynamicChannelConfigurationOption configuration_option,
- Psm psm,
- OnConnectionOpenCallback on_connection_open,
- OnConnectionFailureCallback on_fail_callback) {
- internal::Link::PendingDynamicChannelConnection pending_connection{
+bool DynamicChannelManager::ConnectChannel(hci::Address device, DynamicChannelConfigurationOption configuration_option,
+ Psm psm, OnConnectionOpenCallback on_connection_open,
+ OnConnectionFailureCallback on_fail_callback, os::Handler* handler) {
+ internal::Link::PendingDynamicChannelConnection pending_dynamic_channel_connection{
+ .handler_ = handler,
.on_open_callback_ = std::move(on_connection_open),
.on_fail_callback_ = std::move(on_fail_callback),
.configuration_ = configuration_option,
};
- l2cap_layer_handler_->CallOn(
- link_manager_, &internal::LinkManager::ConnectDynamicChannelServices, device, std::move(pending_connection), psm);
+ l2cap_layer_handler_->Post(common::BindOnce(&internal::LinkManager::ConnectDynamicChannelServices,
+ common::Unretained(link_manager_), device,
+ std::move(pending_dynamic_channel_connection), psm));
+
+ return true;
}
-void DynamicChannelManager::RegisterService(
- Psm psm,
- DynamicChannelConfigurationOption configuration_option,
- const classic::SecurityPolicy& security_policy,
- OnRegistrationCompleteCallback on_registration_complete,
- OnConnectionOpenCallback on_connection_open) {
+bool DynamicChannelManager::RegisterService(Psm psm, DynamicChannelConfigurationOption configuration_option,
+ const SecurityPolicy& security_policy,
+ OnRegistrationCompleteCallback on_registration_complete,
+ OnConnectionOpenCallback on_connection_open, os::Handler* handler) {
internal::DynamicChannelServiceImpl::PendingRegistration pending_registration{
+ .user_handler_ = handler,
.security_policy_ = security_policy,
.on_registration_complete_callback_ = std::move(on_registration_complete),
.on_connection_open_callback_ = std::move(on_connection_open),
.configuration_ = configuration_option,
};
- l2cap_layer_handler_->CallOn(
- service_manager_, &internal::DynamicChannelServiceManagerImpl::Register, psm, std::move(pending_registration));
+ l2cap_layer_handler_->Post(common::BindOnce(&internal::DynamicChannelServiceManagerImpl::Register,
+ common::Unretained(service_manager_), psm,
+ std::move(pending_registration)));
+
+ return true;
}
} // namespace classic
diff --git a/gd/l2cap/classic/dynamic_channel_manager.h b/gd/l2cap/classic/dynamic_channel_manager.h
index 66e3aeec5..f459f31cc 100644
--- a/gd/l2cap/classic/dynamic_channel_manager.h
+++ b/gd/l2cap/classic/dynamic_channel_manager.h
@@ -17,15 +17,14 @@
#include <string>
-#include "common/contextual_callback.h"
#include "hci/acl_manager.h"
#include "hci/address.h"
#include "l2cap/classic/dynamic_channel.h"
#include "l2cap/classic/dynamic_channel_configuration_option.h"
#include "l2cap/classic/dynamic_channel_service.h"
-#include "l2cap/classic/security_policy.h"
#include "l2cap/l2cap_packets.h"
#include "l2cap/psm.h"
+#include "l2cap/security_policy.h"
#include "os/handler.h"
namespace bluetooth {
@@ -46,8 +45,6 @@ class DynamicChannelManager {
FAIL_NO_SERVICE_REGISTERED = 1, // No service is registered
FAIL_HCI_ERROR = 2, // See hci_error
FAIL_L2CAP_ERROR = 3, // See l2cap_connection_response_result
- FAIL_REMOTE_NOT_SUPPORT = 4, // Remote not support required retansmission and flow control mode
- FAIL_SECURITY_BLOCK = 5, // Cannot enhance required security level
};
struct ConnectionResult {
@@ -55,10 +52,15 @@ class DynamicChannelManager {
hci::ErrorCode hci_error = hci::ErrorCode::SUCCESS;
ConnectionResponseResult l2cap_connection_response_result = ConnectionResponseResult::SUCCESS;
};
+ /**
+ * OnConnectionFailureCallback(std::string failure_reason);
+ */
+ using OnConnectionFailureCallback = common::OnceCallback<void(ConnectionResult result)>;
- using OnConnectionFailureCallback = common::ContextualOnceCallback<void(ConnectionResult result)>;
-
- using OnConnectionOpenCallback = common::ContextualCallback<void(std::unique_ptr<DynamicChannel>)>;
+ /**
+ * OnConnectionOpenCallback(DynamicChannel channel);
+ */
+ using OnConnectionOpenCallback = common::Callback<void(std::unique_ptr<DynamicChannel>)>;
enum class RegistrationResult {
SUCCESS = 0,
@@ -66,8 +68,11 @@ class DynamicChannelManager {
FAIL_INVALID_SERVICE = 2, // Invalid PSM
};
+ /**
+ * OnRegistrationFailureCallback(RegistrationResult result, DynamicChannelService service);
+ */
using OnRegistrationCompleteCallback =
- common::ContextualOnceCallback<void(RegistrationResult, std::unique_ptr<DynamicChannelService>)>;
+ common::OnceCallback<void(RegistrationResult, std::unique_ptr<DynamicChannelService>)>;
/**
* Connect to a Dynamic channel on a remote device
@@ -84,14 +89,14 @@ class DynamicChannelManager {
* @param psm: Service PSM to connect. PSM is defined in Core spec Vol 3 Part A 4.2.
* @param on_open_callback: A callback to indicate success of a connection initiated from a remote device.
* @param on_fail_callback: A callback to indicate connection failure along with a status code.
+ * @param handler: The handler context in which to execute the @callback parameters.
* @param configuration_option: The configuration options for this channel
+ *
+ * Returns: true if connection was able to be initiated, false otherwise.
*/
- virtual void ConnectChannel(
- hci::Address device,
- DynamicChannelConfigurationOption configuration_option,
- Psm psm,
- OnConnectionOpenCallback on_connection_open,
- OnConnectionFailureCallback on_fail_callback);
+ virtual bool ConnectChannel(hci::Address device, DynamicChannelConfigurationOption configuration_option, Psm psm,
+ OnConnectionOpenCallback on_connection_open, OnConnectionFailureCallback on_fail_callback,
+ os::Handler* handler);
/**
* Register a service to receive incoming connections bound to a specific channel.
@@ -111,14 +116,13 @@ class DynamicChannelManager {
* @param on_registration_complete: A callback to indicate the service setup has completed. If the return status is
* not SUCCESS, it means service is not registered due to reasons like PSM already take
* @param on_open_callback: A callback to indicate success of a connection initiated from a remote device.
+ * @param handler: The handler context in which to execute the @callback parameter.
* @param configuration_option: The configuration options for this channel
*/
- virtual void RegisterService(
- Psm psm,
- DynamicChannelConfigurationOption configuration_option,
- const SecurityPolicy& security_policy,
- OnRegistrationCompleteCallback on_registration_complete,
- OnConnectionOpenCallback on_connection_open);
+ virtual bool RegisterService(Psm psm, DynamicChannelConfigurationOption configuration_option,
+ const SecurityPolicy& security_policy,
+ OnRegistrationCompleteCallback on_registration_complete,
+ OnConnectionOpenCallback on_connection_open, os::Handler* handler);
friend class L2capClassicModule;
diff --git a/gd/l2cap/classic/dynamic_channel_service.cc b/gd/l2cap/classic/dynamic_channel_service.cc
index 4a2dfeebc..ee97d374d 100644
--- a/gd/l2cap/classic/dynamic_channel_service.cc
+++ b/gd/l2cap/classic/dynamic_channel_service.cc
@@ -22,10 +22,11 @@ namespace bluetooth {
namespace l2cap {
namespace classic {
-void DynamicChannelService::Unregister(OnUnregisteredCallback on_unregistered) {
+void DynamicChannelService::Unregister(OnUnregisteredCallback on_unregistered, os::Handler* on_unregistered_handler) {
ASSERT_LOG(manager_ != nullptr, "this service is invalid");
- l2cap_layer_handler_->CallOn(
- manager_, &internal::DynamicChannelServiceManagerImpl::Unregister, psm_, std::move(on_unregistered));
+ l2cap_layer_handler_->Post(common::BindOnce(&internal::DynamicChannelServiceManagerImpl::Unregister,
+ common::Unretained(manager_), psm_, std::move(on_unregistered),
+ on_unregistered_handler));
}
Psm DynamicChannelService::GetPsm() const {
diff --git a/gd/l2cap/classic/dynamic_channel_service.h b/gd/l2cap/classic/dynamic_channel_service.h
index f098db1a0..24b7403ff 100644
--- a/gd/l2cap/classic/dynamic_channel_service.h
+++ b/gd/l2cap/classic/dynamic_channel_service.h
@@ -16,7 +16,7 @@
#pragma once
-#include "common/contextual_callback.h"
+#include "common/callback.h"
#include "l2cap/psm.h"
#include "os/handler.h"
#include "os/log.h"
@@ -33,7 +33,7 @@ class DynamicChannelService {
public:
DynamicChannelService() = default;
- using OnUnregisteredCallback = common::ContextualOnceCallback<void()>;
+ using OnUnregisteredCallback = common::OnceCallback<void()>;
/**
* Unregister a service from L2CAP module. This operation cannot fail.
@@ -41,7 +41,7 @@ class DynamicChannelService {
*
* @param on_unregistered will be triggered when unregistration is complete
*/
- void Unregister(OnUnregisteredCallback on_unregistered);
+ void Unregister(OnUnregisteredCallback on_unregistered, os::Handler* on_unregistered_handler);
friend internal::DynamicChannelServiceManagerImpl;
diff --git a/gd/l2cap/classic/facade.cc b/gd/l2cap/classic/facade.cc
index 57d825570..eabeb080a 100644
--- a/gd/l2cap/classic/facade.cc
+++ b/gd/l2cap/classic/facade.cc
@@ -20,12 +20,12 @@
#include "common/bidi_queue.h"
#include "common/bind.h"
-#include "common/callback.h"
#include "grpc/grpc_event_queue.h"
#include "hci/address.h"
#include "l2cap/classic/facade.grpc.pb.h"
#include "l2cap/classic/facade.h"
#include "l2cap/classic/l2cap_classic_module.h"
+#include "l2cap/l2cap_packets.h"
#include "os/log.h"
#include "packet/raw_builder.h"
@@ -39,10 +39,10 @@ namespace bluetooth {
namespace l2cap {
namespace classic {
-class L2capClassicModuleFacadeService : public L2capClassicModuleFacade::Service, public LinkSecurityInterfaceListener {
+class L2capClassicModuleFacadeService : public L2capClassicModuleFacade::Service {
public:
L2capClassicModuleFacadeService(L2capClassicModule* l2cap_layer, os::Handler* facade_handler)
- : l2cap_layer_(l2cap_layer), facade_handler_(facade_handler), security_interface_(nullptr) {
+ : l2cap_layer_(l2cap_layer), facade_handler_(facade_handler) {
ASSERT(l2cap_layer_ != nullptr);
ASSERT(facade_handler_ != nullptr);
}
@@ -57,6 +57,30 @@ class L2capClassicModuleFacadeService : public L2capClassicModuleFacade::Service
return pending_connection_close_.RunLoop(context, writer);
}
+ ::grpc::Status Connect(::grpc::ServerContext* context, const facade::BluetoothAddress* request,
+ ::google::protobuf::Empty* response) override {
+ auto fixed_channel_manager = l2cap_layer_->GetFixedChannelManager();
+ hci::Address peer;
+ ASSERT(hci::Address::FromString(request->address(), peer));
+ fixed_channel_manager->ConnectServices(peer, common::BindOnce([](FixedChannelManager::ConnectionResult) {}),
+ facade_handler_);
+ return ::grpc::Status::OK;
+ }
+
+ ::grpc::Status SendL2capPacket(::grpc::ServerContext* context, const classic::L2capPacket* request,
+ SendL2capPacketResult* response) override {
+ std::unique_lock<std::mutex> lock(channel_map_mutex_);
+ if (fixed_channel_helper_map_.find(request->channel()) == fixed_channel_helper_map_.end()) {
+ return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Channel not registered");
+ }
+ std::vector<uint8_t> packet(request->payload().begin(), request->payload().end());
+ if (!fixed_channel_helper_map_[request->channel()]->SendPacket(packet)) {
+ return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Channel not open");
+ }
+ response->set_result_type(SendL2capPacketResultType::OK);
+ return ::grpc::Status::OK;
+ }
+
::grpc::Status SendDynamicChannelPacket(::grpc::ServerContext* context, const DynamicChannelPacket* request,
::google::protobuf::Empty* response) override {
std::unique_lock<std::mutex> lock(channel_map_mutex_);
@@ -73,13 +97,14 @@ class L2capClassicModuleFacadeService : public L2capClassicModuleFacade::Service
::grpc::Status OpenChannel(::grpc::ServerContext* context,
const ::bluetooth::l2cap::classic::OpenChannelRequest* request,
::google::protobuf::Empty* response) override {
- auto service_helper = dynamic_channel_helper_map_.find(request->psm());
- if (service_helper == dynamic_channel_helper_map_.end()) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Psm not registered");
- }
+ std::unique_lock<std::mutex> lock(channel_map_mutex_);
+ auto psm = request->psm();
+ auto mode = request->mode();
+ dynamic_channel_helper_map_.emplace(
+ psm, std::make_unique<L2capDynamicChannelHelper>(this, l2cap_layer_, facade_handler_, psm, mode));
hci::Address peer;
ASSERT(hci::Address::FromString(request->remote().address(), peer));
- dynamic_channel_helper_map_[request->psm()]->Connect(peer);
+ dynamic_channel_helper_map_[psm]->Connect(peer);
return ::grpc::Status::OK;
}
@@ -90,274 +115,234 @@ class L2capClassicModuleFacadeService : public L2capClassicModuleFacade::Service
if (dynamic_channel_helper_map_.find(request->psm()) == dynamic_channel_helper_map_.end()) {
return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Psm not registered");
}
- dynamic_channel_helper_map_[psm]->Disconnect();
+ dynamic_channel_helper_map_[psm]->disconnect();
return ::grpc::Status::OK;
}
::grpc::Status FetchL2capData(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
::grpc::ServerWriter<classic::L2capPacket>* writer) override {
- auto status = pending_l2cap_data_.RunLoop(context, writer);
-
- return status;
- }
+ {
+ std::unique_lock<std::mutex> lock(channel_map_mutex_);
+
+ for (auto& connection : fixed_channel_helper_map_) {
+ if (connection.second->channel_ != nullptr) {
+ connection.second->channel_->GetQueueUpEnd()->RegisterDequeue(
+ facade_handler_,
+ common::Bind(&L2capFixedChannelHelper::on_incoming_packet, common::Unretained(connection.second.get())));
+ }
+ }
- ::grpc::Status SetDynamicChannel(::grpc::ServerContext* context, const SetEnableDynamicChannelRequest* request,
- google::protobuf::Empty* response) override {
- dynamic_channel_helper_map_.emplace(
- request->psm(), std::make_unique<L2capDynamicChannelHelper>(this, l2cap_layer_, facade_handler_, request->psm(),
- request->retransmission_mode()));
- return ::grpc::Status::OK;
- }
+ for (auto& connection : dynamic_channel_helper_map_) {
+ if (connection.second->channel_ != nullptr) {
+ connection.second->channel_->GetQueueUpEnd()->RegisterDequeue(
+ facade_handler_, common::Bind(&L2capDynamicChannelHelper::on_incoming_packet,
+ common::Unretained(connection.second.get())));
+ }
+ }
- ::grpc::Status SetTrafficPaused(::grpc::ServerContext* context, const SetTrafficPausedRequest* request,
- ::google::protobuf::Empty* response) override {
- auto psm = request->psm();
- if (dynamic_channel_helper_map_.find(request->psm()) == dynamic_channel_helper_map_.end()) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Psm not registered");
- }
- if (request->paused()) {
- dynamic_channel_helper_map_[psm]->SuspendDequeue();
- } else {
- dynamic_channel_helper_map_[psm]->ResumeDequeue();
+ fetch_l2cap_data_ = true;
}
- return ::grpc::Status::OK;
- }
- ::grpc::Status GetChannelQueueDepth(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
- GetChannelQueueDepthResponse* response) override {
- // Use the value kChannelQueueSize (5) in internal/dynamic_channel_impl.h
- response->set_size(5);
- return ::grpc::Status::OK;
- }
+ auto status = pending_l2cap_data_.RunLoop(context, writer);
- ::grpc::Status InitiateConnectionForSecurity(
- ::grpc::ServerContext* context,
- const facade::BluetoothAddress* request,
- ::google::protobuf::Empty* response) override {
- hci::Address peer;
- ASSERT(hci::Address::FromString(request->address(), peer));
- outgoing_pairing_remote_devices_.insert(peer);
- security_interface_->InitiateConnectionForSecurity(peer);
- return ::grpc::Status::OK;
- }
+ {
+ std::unique_lock<std::mutex> lock(channel_map_mutex_);
- void SecurityConnectionEventOccurred(
- hci::ErrorCode hci_status, hci::Address remote, LinkSecurityInterfaceCallbackEventType event_type) {
- LinkSecurityInterfaceCallbackEvent msg;
- msg.mutable_address()->set_address(remote.ToString());
- msg.set_event_type(event_type);
- security_connection_events_.OnIncomingEvent(msg);
- }
+ fetch_l2cap_data_ = false;
- ::grpc::Status FetchSecurityConnectionEvents(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<LinkSecurityInterfaceCallbackEvent>* writer) override {
- security_interface_ = l2cap_layer_->GetSecurityInterface(facade_handler_, this);
- return security_connection_events_.RunLoop(context, writer);
- }
+ for (auto& connection : fixed_channel_helper_map_) {
+ if (connection.second->channel_ != nullptr) {
+ connection.second->channel_->GetQueueUpEnd()->RegisterDequeue(
+ facade_handler_,
+ common::Bind(&L2capFixedChannelHelper::on_incoming_packet, common::Unretained(connection.second.get())));
+ }
+ }
- ::grpc::Status SecurityLinkHold(
- ::grpc::ServerContext* context,
- const facade::BluetoothAddress* request,
- ::google::protobuf::Empty* response) override {
- hci::Address peer;
- ASSERT(hci::Address::FromString(request->address(), peer));
- auto entry = security_link_map_.find(peer);
- if (entry == security_link_map_.end()) {
- LOG_WARN("Unknown address '%s'", peer.ToString().c_str());
- } else {
- entry->second->Hold();
+ for (auto& connection : dynamic_channel_helper_map_) {
+ if (connection.second->channel_ != nullptr) {
+ connection.second->channel_->GetQueueUpEnd()->RegisterDequeue(
+ facade_handler_, common::Bind(&L2capDynamicChannelHelper::on_incoming_packet,
+ common::Unretained(connection.second.get())));
+ }
+ }
}
- return ::grpc::Status::OK;
+
+ return status;
}
- ::grpc::Status SecurityLinkEnsureAuthenticated(
- ::grpc::ServerContext* context,
- const facade::BluetoothAddress* request,
- ::google::protobuf::Empty* response) override {
- hci::Address peer;
- ASSERT(hci::Address::FromString(request->address(), peer));
- auto entry = security_link_map_.find(peer);
- if (entry == security_link_map_.end()) {
- LOG_WARN("Unknown address '%s'", peer.ToString().c_str());
- } else {
- entry->second->EnsureAuthenticated();
+ ::grpc::Status RegisterChannel(::grpc::ServerContext* context, const classic::RegisterChannelRequest* request,
+ ::google::protobuf::Empty* response) override {
+ std::unique_lock<std::mutex> lock(channel_map_mutex_);
+ if (fixed_channel_helper_map_.find(request->channel()) != fixed_channel_helper_map_.end()) {
+ return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Already registered");
}
+ fixed_channel_helper_map_.emplace(request->channel(), std::make_unique<L2capFixedChannelHelper>(
+ this, l2cap_layer_, facade_handler_, request->channel()));
+
return ::grpc::Status::OK;
}
- ::grpc::Status SecurityLinkRelease(
- ::grpc::ServerContext* context,
- const facade::BluetoothAddress* request,
- ::google::protobuf::Empty* response) override {
- hci::Address peer;
- ASSERT(hci::Address::FromString(request->address(), peer));
- outgoing_pairing_remote_devices_.erase(peer);
- auto entry = security_link_map_.find(peer);
- if (entry == security_link_map_.end()) {
- LOG_WARN("Unknown address '%s'", peer.ToString().c_str());
- } else {
- entry->second->Release();
+ class L2capFixedChannelHelper {
+ public:
+ L2capFixedChannelHelper(L2capClassicModuleFacadeService* service, L2capClassicModule* l2cap_layer,
+ os::Handler* handler, Cid cid)
+ : facade_service_(service), l2cap_layer_(l2cap_layer), handler_(handler), cid_(cid) {
+ fixed_channel_manager_ = l2cap_layer_->GetFixedChannelManager();
+ fixed_channel_manager_->RegisterService(
+ cid, {},
+ common::BindOnce(&L2capFixedChannelHelper::on_l2cap_service_registration_complete, common::Unretained(this)),
+ common::Bind(&L2capFixedChannelHelper::on_connection_open, common::Unretained(this)), handler_);
}
- return ::grpc::Status::OK;
- }
- ::grpc::Status SecurityLinkDisconnect(
- ::grpc::ServerContext* context,
- const facade::BluetoothAddress* request,
- ::google::protobuf::Empty* response) override {
- hci::Address peer;
- ASSERT(hci::Address::FromString(request->address(), peer));
- outgoing_pairing_remote_devices_.erase(peer);
- auto entry = security_link_map_.find(peer);
- if (entry == security_link_map_.end()) {
- LOG_WARN("Unknown address '%s'", peer.ToString().c_str());
- } else {
- entry->second->Disconnect();
+ void on_l2cap_service_registration_complete(FixedChannelManager::RegistrationResult registration_result,
+ std::unique_ptr<FixedChannelService> service) {
+ service_ = std::move(service);
}
- return ::grpc::Status::OK;
- }
- void OnLinkConnected(std::unique_ptr<LinkSecurityInterface> link) override {
- auto remote = link->GetRemoteAddress();
- if (outgoing_pairing_remote_devices_.count(remote) == 1) {
- link->Hold();
- link->EnsureAuthenticated();
- outgoing_pairing_remote_devices_.erase(remote);
+ void on_connection_open(std::unique_ptr<FixedChannel> channel) {
+ ConnectionCompleteEvent event;
+ event.mutable_remote()->set_address(channel->GetDevice().ToString());
+ facade_service_->pending_connection_complete_.OnIncomingEvent(event);
+ channel_ = std::move(channel);
+ channel_->RegisterOnCloseCallback(
+ facade_service_->facade_handler_,
+ common::BindOnce(&L2capFixedChannelHelper::on_close_callback, common::Unretained(this)));
+ {
+ std::unique_lock<std::mutex> lock(facade_service_->channel_map_mutex_);
+ if (facade_service_->fetch_l2cap_data_) {
+ channel_->GetQueueUpEnd()->RegisterDequeue(
+ facade_service_->facade_handler_,
+ common::Bind(&L2capFixedChannelHelper::on_incoming_packet, common::Unretained(this)));
+ }
+ }
}
- security_link_map_.emplace(remote, std::move(link));
- SecurityConnectionEventOccurred(
- hci::ErrorCode::SUCCESS, remote, LinkSecurityInterfaceCallbackEventType::ON_CONNECTED);
- }
- void OnLinkDisconnected(hci::Address remote) override {
- auto entry = security_link_map_.find(remote);
- if (entry == security_link_map_.end()) {
- LOG_WARN("Unknown address '%s'", remote.ToString().c_str());
- return;
+ bool SendPacket(const std::vector<uint8_t>& packet) {
+ if (channel_ == nullptr) {
+ LOG_WARN("Channel is not open");
+ return false;
+ }
+ channel_->GetQueueUpEnd()->RegisterEnqueue(
+ handler_, common::Bind(&L2capFixedChannelHelper::enqueue_callback, common::Unretained(this), packet));
+ return true;
}
- entry->second.reset();
- security_link_map_.erase(entry);
- SecurityConnectionEventOccurred(
- hci::ErrorCode::SUCCESS, remote, LinkSecurityInterfaceCallbackEventType::ON_DISCONNECTED);
- }
- void OnAuthenticationComplete(hci::ErrorCode hci_status, hci::Address remote) override {
- auto entry = security_link_map_.find(remote);
- if (entry != security_link_map_.end()) {
- entry->second->EnsureEncrypted();
- return;
+ void on_close_callback(hci::ErrorCode error_code) {
+ {
+ std::unique_lock<std::mutex> lock(facade_service_->channel_map_mutex_);
+ if (facade_service_->fetch_l2cap_data_) {
+ channel_->GetQueueUpEnd()->UnregisterDequeue();
+ }
+ }
+ channel_ = nullptr;
+ classic::ConnectionCloseEvent event;
+ event.mutable_remote()->set_address(channel_->GetDevice().ToString());
+ event.set_reason(static_cast<uint32_t>(error_code));
+ facade_service_->pending_connection_close_.OnIncomingEvent(event);
}
- SecurityConnectionEventOccurred(
- hci_status, remote, LinkSecurityInterfaceCallbackEventType::ON_AUTHENTICATION_COMPLETE);
- }
- void OnEncryptionChange(hci::Address remote, bool encrypted) override {
- SecurityConnectionEventOccurred(
- hci::ErrorCode::SUCCESS, remote, LinkSecurityInterfaceCallbackEventType::ON_ENCRYPTION_CHANGE);
+ void on_incoming_packet() {
+ auto packet = channel_->GetQueueUpEnd()->TryDequeue();
+ std::string data = std::string(packet->begin(), packet->end());
+ L2capPacket l2cap_data;
+ l2cap_data.set_channel(cid_);
+ l2cap_data.set_payload(data);
+ facade_service_->pending_l2cap_data_.OnIncomingEvent(l2cap_data);
+ }
+
+ std::unique_ptr<packet::BasePacketBuilder> enqueue_callback(const std::vector<uint8_t>& packet) {
+ auto packet_one = std::make_unique<packet::RawBuilder>();
+ packet_one->AddOctets(packet);
+ channel_->GetQueueUpEnd()->UnregisterEnqueue();
+ return packet_one;
+ };
+
+ L2capClassicModuleFacadeService* facade_service_;
+ L2capClassicModule* l2cap_layer_;
+ os::Handler* handler_;
+ std::unique_ptr<FixedChannelManager> fixed_channel_manager_;
+ std::unique_ptr<FixedChannelService> service_;
+ std::unique_ptr<FixedChannel> channel_ = nullptr;
+ Cid cid_;
+ };
+
+ ::grpc::Status SetDynamicChannel(::grpc::ServerContext* context, const SetEnableDynamicChannelRequest* request,
+ google::protobuf::Empty* response) override {
+ dynamic_channel_helper_map_.emplace(
+ request->psm(), std::make_unique<L2capDynamicChannelHelper>(this, l2cap_layer_, facade_handler_, request->psm(),
+ request->retransmission_mode()));
+ return ::grpc::Status::OK;
}
class L2capDynamicChannelHelper {
public:
L2capDynamicChannelHelper(L2capClassicModuleFacadeService* service, L2capClassicModule* l2cap_layer,
os::Handler* handler, Psm psm, RetransmissionFlowControlMode mode)
- : facade_service_(service), l2cap_layer_(l2cap_layer), handler_(handler), psm_(psm), mode_(mode) {
+ : facade_service_(service), l2cap_layer_(l2cap_layer), handler_(handler), psm_(psm) {
dynamic_channel_manager_ = l2cap_layer_->GetDynamicChannelManager();
DynamicChannelConfigurationOption configuration_option = {};
- configuration_option.channel_mode = (DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode)mode;
- dynamic_channel_manager_->RegisterService(
- psm,
- configuration_option,
- SecurityPolicy::_SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK,
- handler_->BindOnceOn(this, &L2capDynamicChannelHelper::on_l2cap_service_registration_complete),
- handler_->BindOn(this, &L2capDynamicChannelHelper::on_connection_open));
- }
-
- ~L2capDynamicChannelHelper() {
- if (dequeue_registered_) {
- channel_->GetQueueUpEnd()->UnregisterDequeue();
- channel_ = nullptr;
+ if (mode == RetransmissionFlowControlMode::BASIC) {
+ configuration_option.channel_mode =
+ DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode::L2CAP_BASIC;
+ } else if (mode == RetransmissionFlowControlMode::ERTM) {
+ configuration_option.channel_mode =
+ DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode::ENHANCED_RETRANSMISSION;
}
- enqueue_buffer_.reset();
+ dynamic_channel_manager_->RegisterService(
+ psm, configuration_option, {},
+ common::BindOnce(&L2capDynamicChannelHelper::on_l2cap_service_registration_complete,
+ common::Unretained(this)),
+ common::Bind(&L2capDynamicChannelHelper::on_connection_open, common::Unretained(this)), handler_);
}
void Connect(hci::Address address) {
- DynamicChannelConfigurationOption configuration_option = l2cap::classic::DynamicChannelConfigurationOption();
- configuration_option.channel_mode = (DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode)mode_;
-
+ // TODO: specify channel mode
dynamic_channel_manager_->ConnectChannel(
- address,
- configuration_option,
- psm_,
- handler_->BindOn(this, &L2capDynamicChannelHelper::on_connection_open),
- handler_->BindOnceOn(this, &L2capDynamicChannelHelper::on_connect_fail));
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- if (!channel_open_cv_.wait_for(lock, std::chrono::seconds(2), [this] { return channel_ != nullptr; })) {
- LOG_WARN("Channel is not open for psm %d", psm_);
- }
+ address, {}, psm_, common::Bind(&L2capDynamicChannelHelper::on_connection_open, common::Unretained(this)),
+ common::Bind(&L2capDynamicChannelHelper::on_connect_fail, common::Unretained(this)), handler_);
}
- void Disconnect() {
- if (channel_ == nullptr) {
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- if (!channel_open_cv_.wait_for(lock, std::chrono::seconds(2), [this] { return channel_ != nullptr; })) {
- LOG_WARN("Channel is not open for psm %d", psm_);
- return;
- }
- }
+ void disconnect() {
channel_->Close();
}
void on_l2cap_service_registration_complete(DynamicChannelManager::RegistrationResult registration_result,
std::unique_ptr<DynamicChannelService> service) {}
- // invoked from Facade Handler
void on_connection_open(std::unique_ptr<DynamicChannel> channel) {
ConnectionCompleteEvent event;
- event.mutable_remote()->set_address(channel->GetDevice().GetAddress().ToString());
+ event.mutable_remote()->set_address(channel->GetDevice().ToString());
facade_service_->pending_connection_complete_.OnIncomingEvent(event);
{
std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
channel_ = std::move(channel);
- enqueue_buffer_ = std::make_unique<os::EnqueueBuffer<BasePacketBuilder>>(channel_->GetQueueUpEnd());
}
channel_open_cv_.notify_all();
channel_->RegisterOnCloseCallback(
- facade_service_->facade_handler_->BindOnceOn(this, &L2capDynamicChannelHelper::on_close_callback));
- dequeue_registered_ = true;
- channel_->GetQueueUpEnd()->RegisterDequeue(
facade_service_->facade_handler_,
- common::Bind(&L2capDynamicChannelHelper::on_incoming_packet, common::Unretained(this)));
+ common::BindOnce(&L2capDynamicChannelHelper::on_close_callback, common::Unretained(this)));
+ {
+ std::unique_lock<std::mutex> lock(facade_service_->channel_map_mutex_);
+ if (facade_service_->fetch_l2cap_data_) {
+ channel_->GetQueueUpEnd()->RegisterDequeue(
+ facade_service_->facade_handler_,
+ common::Bind(&L2capDynamicChannelHelper::on_incoming_packet, common::Unretained(this)));
+ }
+ }
}
void on_close_callback(hci::ErrorCode error_code) {
{
std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- if (dequeue_registered_.exchange(false)) {
+ if (facade_service_->fetch_l2cap_data_) {
channel_->GetQueueUpEnd()->UnregisterDequeue();
}
}
classic::ConnectionCloseEvent event;
- event.mutable_remote()->set_address(channel_->GetDevice().GetAddress().ToString());
+ event.mutable_remote()->set_address(channel_->GetDevice().ToString());
+ channel_ = nullptr;
event.set_reason(static_cast<uint32_t>(error_code));
facade_service_->pending_connection_close_.OnIncomingEvent(event);
- channel_ = nullptr;
- enqueue_buffer_.reset();
- }
-
- void SuspendDequeue() {
- if (dequeue_registered_.exchange(false)) {
- channel_->GetQueueUpEnd()->UnregisterDequeue();
- }
- }
-
- void ResumeDequeue() {
- if (!dequeue_registered_.exchange(true)) {
- channel_->GetQueueUpEnd()->RegisterDequeue(
- facade_service_->facade_handler_,
- common::Bind(&L2capDynamicChannelHelper::on_incoming_packet, common::Unretained(this)));
- }
}
void on_connect_fail(DynamicChannelManager::ConnectionResult result) {}
@@ -366,7 +351,7 @@ class L2capClassicModuleFacadeService : public L2capClassicModuleFacade::Service
auto packet = channel_->GetQueueUpEnd()->TryDequeue();
std::string data = std::string(packet->begin(), packet->end());
L2capPacket l2cap_data;
- l2cap_data.set_psm(psm_);
+ // l2cap_data.set_channel(cid_);
l2cap_data.set_payload(data);
facade_service_->pending_l2cap_data_.OnIncomingEvent(l2cap_data);
}
@@ -374,26 +359,30 @@ class L2capClassicModuleFacadeService : public L2capClassicModuleFacade::Service
bool SendPacket(std::vector<uint8_t> packet) {
if (channel_ == nullptr) {
std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- if (!channel_open_cv_.wait_for(lock, std::chrono::seconds(2), [this] { return channel_ != nullptr; })) {
+ if (!channel_open_cv_.wait_for(lock, std::chrono::seconds(1), [this] { return channel_ != nullptr; })) {
LOG_WARN("Channel is not open");
return false;
}
}
- auto packet_one = std::make_unique<packet::RawBuilder>(2000);
- packet_one->AddOctets(packet);
- enqueue_buffer_->Enqueue(std::move(packet_one), handler_);
+ channel_->GetQueueUpEnd()->RegisterEnqueue(
+ handler_, common::Bind(&L2capDynamicChannelHelper::enqueue_callback, common::Unretained(this), packet));
return true;
}
+
+ std::unique_ptr<packet::BasePacketBuilder> enqueue_callback(std::vector<uint8_t> packet) {
+ auto packet_one = std::make_unique<packet::RawBuilder>(2000);
+ packet_one->AddOctets(packet);
+ channel_->GetQueueUpEnd()->UnregisterEnqueue();
+ return packet_one;
+ };
+
L2capClassicModuleFacadeService* facade_service_;
L2capClassicModule* l2cap_layer_;
os::Handler* handler_;
std::unique_ptr<DynamicChannelManager> dynamic_channel_manager_;
std::unique_ptr<DynamicChannelService> service_;
std::unique_ptr<DynamicChannel> channel_ = nullptr;
- std::unique_ptr<os::EnqueueBuffer<BasePacketBuilder>> enqueue_buffer_ = nullptr;
Psm psm_;
- RetransmissionFlowControlMode mode_ = RetransmissionFlowControlMode::BASIC;
- std::atomic_bool dequeue_registered_ = false;
std::condition_variable channel_open_cv_;
std::mutex channel_open_cv_mutex_;
};
@@ -401,16 +390,13 @@ class L2capClassicModuleFacadeService : public L2capClassicModuleFacade::Service
L2capClassicModule* l2cap_layer_;
::bluetooth::os::Handler* facade_handler_;
std::mutex channel_map_mutex_;
+ std::map<Cid, std::unique_ptr<L2capFixedChannelHelper>> fixed_channel_helper_map_;
std::map<Psm, std::unique_ptr<L2capDynamicChannelHelper>> dynamic_channel_helper_map_;
+ bool fetch_l2cap_data_ = false;
::bluetooth::grpc::GrpcEventQueue<classic::ConnectionCompleteEvent> pending_connection_complete_{
"FetchConnectionComplete"};
::bluetooth::grpc::GrpcEventQueue<classic::ConnectionCloseEvent> pending_connection_close_{"FetchConnectionClose"};
::bluetooth::grpc::GrpcEventQueue<L2capPacket> pending_l2cap_data_{"FetchL2capData"};
- ::bluetooth::grpc::GrpcEventQueue<LinkSecurityInterfaceCallbackEvent> security_connection_events_{
- "Security Connection Events"};
- SecurityInterface* security_interface_;
- std::unordered_map<hci::Address, std::unique_ptr<l2cap::classic::LinkSecurityInterface>> security_link_map_;
- std::set<hci::Address> outgoing_pairing_remote_devices_;
};
void L2capClassicModuleFacadeModule::ListDependencies(ModuleList* list) {
diff --git a/gd/l2cap/classic/facade.proto b/gd/l2cap/classic/facade.proto
index 73c204fa7..b5faf03df 100644
--- a/gd/l2cap/classic/facade.proto
+++ b/gd/l2cap/classic/facade.proto
@@ -6,42 +6,23 @@ import "google/protobuf/empty.proto";
import "facade/common.proto";
service L2capClassicModuleFacade {
+ rpc RegisterChannel(RegisterChannelRequest) returns (google.protobuf.Empty) {
+ // Testing Android Bluetooth stack only. Optional for other stack.
+ }
rpc FetchConnectionComplete(google.protobuf.Empty) returns (stream ConnectionCompleteEvent) {
// Testing Android Bluetooth stack only. Optional for other stack.
}
rpc FetchConnectionClose(google.protobuf.Empty) returns (stream ConnectionCloseEvent) {
// Testing Android Bluetooth stack only. Optional for other stack.
}
+ rpc Connect(facade.BluetoothAddress) returns (google.protobuf.Empty) {}
rpc OpenChannel(OpenChannelRequest) returns (google.protobuf.Empty) {}
rpc CloseChannel(CloseChannelRequest) returns (google.protobuf.Empty) {}
+ rpc ConfigureChannel(ConfigureChannelRequest) returns (google.protobuf.Empty) {}
+ rpc SendL2capPacket(L2capPacket) returns (SendL2capPacketResult) {}
rpc FetchL2capData(google.protobuf.Empty) returns (stream L2capPacket) {}
rpc SetDynamicChannel(SetEnableDynamicChannelRequest) returns (google.protobuf.Empty) {}
rpc SendDynamicChannelPacket(DynamicChannelPacket) returns (google.protobuf.Empty) {}
- rpc SetTrafficPaused(SetTrafficPausedRequest) returns (google.protobuf.Empty) {}
- rpc GetChannelQueueDepth(google.protobuf.Empty) returns (GetChannelQueueDepthResponse) {
- // Get the buffer size of channel queue end for L2CAP user (how many packets we can buffer
- // before L2CAP user dequeues.
- }
- rpc InitiateConnectionForSecurity(facade.BluetoothAddress) returns (google.protobuf.Empty) {}
- rpc FetchSecurityConnectionEvents(google.protobuf.Empty) returns (stream LinkSecurityInterfaceCallbackEvent) {}
- rpc SecurityLinkEnsureAuthenticated(facade.BluetoothAddress) returns (google.protobuf.Empty) {}
- rpc SecurityLinkHold(facade.BluetoothAddress) returns (google.protobuf.Empty) {}
- rpc SecurityLinkDisconnect(facade.BluetoothAddress) returns (google.protobuf.Empty) {}
- rpc SecurityLinkRelease(facade.BluetoothAddress) returns (google.protobuf.Empty) {}
-}
-
-enum LinkSecurityInterfaceCallbackEventType {
- ON_CONNECTED = 0;
- ON_DISCONNECTED = 1;
- ON_AUTHENTICATION_COMPLETE = 2;
- ON_ENCRYPTION_CHANGE = 3;
- ON_READ_REMOTE_VERSION_INFO = 4;
- ON_READ_REMOTE_EXTENDED_FEATURES = 5;
-}
-
-message LinkSecurityInterfaceCallbackEvent {
- facade.BluetoothAddress address = 1;
- LinkSecurityInterfaceCallbackEventType event_type = 2;
}
message RegisterChannelRequest {
@@ -59,8 +40,7 @@ message ConnectionCloseEvent {
enum RetransmissionFlowControlMode {
BASIC = 0;
- ERTM = 1;
- ERTM_OPTIONAL = 2;
+ ERTM = 3;
}
message OpenChannelRequest {
@@ -69,6 +49,11 @@ message OpenChannelRequest {
RetransmissionFlowControlMode mode = 3;
}
+message ConfigureChannelRequest {
+ facade.BluetoothAddress remote = 1;
+ // Config
+}
+
message CloseChannelRequest {
uint32 psm = 1;
}
@@ -94,10 +79,8 @@ message SendL2capPacketResult {
}
message L2capPacket {
- oneof channel_type {
- uint32 psm = 1;
- uint32 fixed_cid = 2;
- }
+ facade.BluetoothAddress remote = 1;
+ uint32 channel = 2;
bytes payload = 3;
}
@@ -112,19 +95,3 @@ message DynamicChannelPacket {
uint32 psm = 2;
bytes payload = 3;
}
-
-message SetTrafficPausedRequest {
- bool paused = 1;
- uint32 psm = 2;
-}
-
-message GetChannelQueueDepthResponse {
- uint32 size = 1;
-}
-
-enum ClassicSecurityPolicy {
- ENCRYPTED_TRANSPORT = 0;
- AUTHENTICATED_ENCRYPTED_TRANSPORT = 1;
- BEST = 2;
- _SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK = 3;
-}
diff --git a/gd/l2cap/classic/fixed_channel_manager.cc b/gd/l2cap/classic/fixed_channel_manager.cc
index 24e78bd9f..0c3e5c78f 100644
--- a/gd/l2cap/classic/fixed_channel_manager.cc
+++ b/gd/l2cap/classic/fixed_channel_manager.cc
@@ -35,7 +35,8 @@ bool FixedChannelManager::ConnectServices(hci::Address device, OnConnectionFailu
return true;
}
-bool FixedChannelManager::RegisterService(Cid cid, OnRegistrationCompleteCallback on_registration_complete,
+bool FixedChannelManager::RegisterService(Cid cid, const SecurityPolicy& security_policy,
+ OnRegistrationCompleteCallback on_registration_complete,
OnConnectionOpenCallback on_connection_open, os::Handler* handler) {
internal::FixedChannelServiceImpl::PendingRegistration pending_registration{
.user_handler_ = handler,
diff --git a/gd/l2cap/classic/fixed_channel_manager.h b/gd/l2cap/classic/fixed_channel_manager.h
index a3285e7d3..65c0b7341 100644
--- a/gd/l2cap/classic/fixed_channel_manager.h
+++ b/gd/l2cap/classic/fixed_channel_manager.h
@@ -22,6 +22,7 @@
#include "l2cap/cid.h"
#include "l2cap/classic/fixed_channel.h"
#include "l2cap/classic/fixed_channel_service.h"
+#include "l2cap/security_policy.h"
#include "os/handler.h"
namespace bluetooth {
@@ -121,12 +122,14 @@ class FixedChannelManager {
* - on_open_callback, will only be triggered after on_service_registered callback
*
* @param cid: cid used to receive incoming connections
+ * @param security_policy: The security policy used for the connection.
* @param on_registration_complete: A callback to indicate the service setup has completed. If the return status is
* not SUCCESS, it means service is not registered due to reasons like CID already take
* @param on_open_callback: A callback to indicate success of a connection initiated from a remote device.
* @param handler: The handler context in which to execute the @callback parameter.
*/
- virtual bool RegisterService(Cid cid, OnRegistrationCompleteCallback on_registration_complete,
+ virtual bool RegisterService(Cid cid, const SecurityPolicy& security_policy,
+ OnRegistrationCompleteCallback on_registration_complete,
OnConnectionOpenCallback on_connection_open, os::Handler* handler);
virtual ~FixedChannelManager() = default;
diff --git a/gd/l2cap/classic/fixed_channel_manager_mock.h b/gd/l2cap/classic/fixed_channel_manager_mock.h
index 513213e67..5ead957e8 100644
--- a/gd/l2cap/classic/fixed_channel_manager_mock.h
+++ b/gd/l2cap/classic/fixed_channel_manager_mock.h
@@ -31,7 +31,7 @@ class MockFixedChannelManager : public FixedChannelManager {
MOCK_METHOD(bool, ConnectServices,
(hci::Address device, OnConnectionFailureCallback on_fail_callback, os::Handler* handler), (override));
MOCK_METHOD(bool, RegisterService,
- (Cid cid, OnRegistrationCompleteCallback on_registration_complete,
+ (Cid cid, const SecurityPolicy& security_policy, OnRegistrationCompleteCallback on_registration_complete,
OnConnectionOpenCallback on_connection_open, os::Handler* handler),
(override));
};
diff --git a/gd/l2cap/classic/internal/channel_configuration_state.h b/gd/l2cap/classic/internal/channel_configuration_state.h
index cee905ed4..b0dead596 100644
--- a/gd/l2cap/classic/internal/channel_configuration_state.h
+++ b/gd/l2cap/classic/internal/channel_configuration_state.h
@@ -49,6 +49,8 @@ struct ChannelConfigurationState {
};
State state_ = State::WAIT_CONFIG_REQ_RSP;
+ Mtu incoming_mtu_ = kDefaultClassicMtu;
+ Mtu outgoing_mtu_ = kDefaultClassicMtu;
RetransmissionAndFlowControlModeOption retransmission_and_flow_control_mode_;
RetransmissionAndFlowControlConfigurationOption local_retransmission_and_flow_control_;
RetransmissionAndFlowControlConfigurationOption remote_retransmission_and_flow_control_;
diff --git a/gd/l2cap/classic/internal/dumpsys_helper.cc b/gd/l2cap/classic/internal/dumpsys_helper.cc
deleted file mode 100644
index d69d690d8..000000000
--- a/gd/l2cap/classic/internal/dumpsys_helper.cc
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <string>
-
-#include "l2cap/classic/internal/dumpsys_helper.h"
-#include "l2cap/classic/internal/fixed_channel_impl.h"
-#include "l2cap/classic/internal/link.h"
-#include "l2cap/classic/internal/link_manager.h"
-#include "l2cap/internal/dynamic_channel_impl.h"
-#include "l2cap_classic_module_generated.h"
-#include "os/log.h"
-
-bluetooth::l2cap::classic::internal::DumpsysHelper::DumpsysHelper(const LinkManager& link_manager)
- : link_manager_(link_manager) {}
-
-std::vector<flatbuffers::Offset<bluetooth::l2cap::classic::ChannelData>>
-bluetooth::l2cap::classic::internal::DumpsysHelper::DumpActiveDynamicChannels(
- flatbuffers::FlatBufferBuilder* fb_builder,
- const l2cap::internal::DynamicChannelAllocator& channel_allocator) const {
- std::vector<flatbuffers::Offset<bluetooth::l2cap::classic::ChannelData>> channel_offsets;
-
- for (auto it = channel_allocator.channels_.cbegin(); it != channel_allocator.channels_.cend(); ++it) {
- ChannelDataBuilder builder(*fb_builder);
- builder.add_cid(it->first);
- channel_offsets.push_back(builder.Finish());
- }
- return channel_offsets;
-}
-
-std::vector<flatbuffers::Offset<::bluetooth::l2cap::classic::ChannelData>>
-bluetooth::l2cap::classic::internal::DumpsysHelper::DumpActiveFixedChannels(
- flatbuffers::FlatBufferBuilder* fb_builder,
- const bluetooth::l2cap::internal::FixedChannelAllocator<
- bluetooth::l2cap::classic::internal::FixedChannelImpl,
- bluetooth::l2cap::classic::internal::Link>& channel_allocator) const {
- std::vector<flatbuffers::Offset<bluetooth::l2cap::classic::ChannelData>> channel_offsets;
-
- for (auto it = channel_allocator.channels_.cbegin(); it != channel_allocator.channels_.cend(); ++it) {
- ChannelDataBuilder builder(*fb_builder);
- builder.add_cid(it->first);
- channel_offsets.push_back(builder.Finish());
- }
- return channel_offsets;
-}
-
-std::vector<flatbuffers::Offset<bluetooth::l2cap::classic::LinkData>>
-bluetooth::l2cap::classic::internal::DumpsysHelper::DumpActiveLinks(flatbuffers::FlatBufferBuilder* fb_builder) const {
- const std::unordered_map<hci::Address, Link>* links = &link_manager_.links_;
-
- std::vector<flatbuffers::Offset<LinkData>> link_offsets;
-
- for (auto it = links->cbegin(); it != links->cend(); ++it) {
- auto link_address = fb_builder->CreateString(it->second.ToString());
- auto dynamic_channel_offsets = DumpActiveDynamicChannels(fb_builder, it->second.dynamic_channel_allocator_);
- auto dynamic_channels = fb_builder->CreateVector(dynamic_channel_offsets);
-
- auto fixed_channel_offsets = DumpActiveFixedChannels(fb_builder, it->second.fixed_channel_allocator_);
- auto fixed_channels = fb_builder->CreateVector(fixed_channel_offsets);
-
- LinkDataBuilder builder(*fb_builder);
- builder.add_address(link_address);
- builder.add_dynamic_channels(dynamic_channels);
- builder.add_fixed_channels(fixed_channels);
- link_offsets.push_back(builder.Finish());
- }
- return link_offsets;
-}
diff --git a/gd/l2cap/classic/internal/dumpsys_helper.h b/gd/l2cap/classic/internal/dumpsys_helper.h
deleted file mode 100644
index 134917bbd..000000000
--- a/gd/l2cap/classic/internal/dumpsys_helper.h
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "l2cap/classic/internal/fixed_channel_impl.h"
-#include "l2cap/classic/internal/link.h"
-#include "l2cap/classic/internal/link_manager.h"
-#include "l2cap/internal/dynamic_channel_allocator.h"
-#include "l2cap/internal/fixed_channel_allocator.h"
-#include "l2cap_classic_module_generated.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace classic {
-namespace internal {
-
-class DumpsysHelper {
- public:
- DumpsysHelper(const LinkManager& link_manager);
-
- std::vector<flatbuffers::Offset<ChannelData>> DumpActiveDynamicChannels(
- flatbuffers::FlatBufferBuilder* fb_builder,
- const l2cap::internal::DynamicChannelAllocator& channel_allocator) const;
- std::vector<flatbuffers::Offset<ChannelData>> DumpActiveFixedChannels(
- flatbuffers::FlatBufferBuilder* fb_builder,
- const l2cap::internal::FixedChannelAllocator<FixedChannelImpl, Link>& channel_allocator) const;
- std::vector<flatbuffers::Offset<LinkData>> DumpActiveLinks(flatbuffers::FlatBufferBuilder* fb_builder) const;
-
- private:
- const LinkManager& link_manager_;
-};
-
-} // namespace internal
-} // namespace classic
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/classic/internal/dynamic_channel_service_impl.h b/gd/l2cap/classic/internal/dynamic_channel_service_impl.h
index b444c7b15..3aae9ba70 100644
--- a/gd/l2cap/classic/internal/dynamic_channel_service_impl.h
+++ b/gd/l2cap/classic/internal/dynamic_channel_service_impl.h
@@ -22,7 +22,7 @@
#include "l2cap/classic/dynamic_channel_configuration_option.h"
#include "l2cap/classic/dynamic_channel_manager.h"
#include "l2cap/classic/dynamic_channel_service.h"
-#include "l2cap/classic/security_policy.h"
+#include "l2cap/security_policy.h"
namespace bluetooth {
namespace l2cap {
@@ -34,21 +34,21 @@ class DynamicChannelServiceImpl {
struct PendingRegistration {
os::Handler* user_handler_ = nullptr;
- classic::SecurityPolicy security_policy_;
+ SecurityPolicy security_policy_;
DynamicChannelManager::OnRegistrationCompleteCallback on_registration_complete_callback_;
DynamicChannelManager::OnConnectionOpenCallback on_connection_open_callback_;
DynamicChannelConfigurationOption configuration_;
};
virtual void NotifyChannelCreation(std::unique_ptr<DynamicChannel> channel) {
- on_connection_open_callback_.Invoke(std::move(channel));
+ user_handler_->Post(common::BindOnce(on_connection_open_callback_, std::move(channel)));
}
- virtual DynamicChannelConfigurationOption GetConfigOption() const {
+ DynamicChannelConfigurationOption GetConfigOption() const {
return config_option_;
}
- virtual SecurityPolicy GetSecurityPolicy() const {
+ SecurityPolicy GetSecurityPolicy() const {
return security_policy_;
}
@@ -56,16 +56,16 @@ class DynamicChannelServiceImpl {
protected:
// protected access for mocking
- DynamicChannelServiceImpl(
- classic::SecurityPolicy security_policy,
- DynamicChannelManager::OnConnectionOpenCallback on_connection_open_callback,
- DynamicChannelConfigurationOption config_option)
- : security_policy_(security_policy),
- on_connection_open_callback_(std::move(on_connection_open_callback)),
+ DynamicChannelServiceImpl(os::Handler* user_handler,
+ SecurityPolicy security_policy,
+ DynamicChannelManager::OnConnectionOpenCallback on_connection_open_callback,
+ DynamicChannelConfigurationOption config_option)
+ : user_handler_(user_handler), security_policy_(security_policy), on_connection_open_callback_(std::move(on_connection_open_callback)),
config_option_(config_option) {}
private:
- classic::SecurityPolicy security_policy_;
+ os::Handler* user_handler_ = nullptr;
+ SecurityPolicy security_policy_;
DynamicChannelManager::OnConnectionOpenCallback on_connection_open_callback_;
DynamicChannelConfigurationOption config_option_;
};
diff --git a/gd/l2cap/classic/internal/dynamic_channel_service_impl_mock.h b/gd/l2cap/classic/internal/dynamic_channel_service_impl_mock.h
deleted file mode 100644
index 299841e9c..000000000
--- a/gd/l2cap/classic/internal/dynamic_channel_service_impl_mock.h
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include "l2cap/classic/internal/dynamic_channel_service_impl.h"
-
-#include <gmock/gmock.h>
-
-// Unit test interfaces
-namespace bluetooth {
-namespace l2cap {
-namespace classic {
-namespace internal {
-namespace testing {
-
-class MockDynamicChannelServiceImpl : public DynamicChannelServiceImpl {
- public:
- MockDynamicChannelServiceImpl() : DynamicChannelServiceImpl({}, {}, {}) {}
- MOCK_METHOD(SecurityPolicy, GetSecurityPolicy, (), (const, override));
-};
-
-} // namespace testing
-} // namespace internal
-} // namespace classic
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.cc b/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.cc
index 1aa4f7e22..ad48ef48f 100644
--- a/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.cc
+++ b/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.cc
@@ -29,29 +29,32 @@ void DynamicChannelServiceManagerImpl::Register(Psm psm,
DynamicChannelServiceImpl::PendingRegistration pending_registration) {
if (!IsPsmValid(psm)) {
std::unique_ptr<DynamicChannelService> invalid_service(new DynamicChannelService());
- pending_registration.on_registration_complete_callback_.Invoke(
- DynamicChannelManager::RegistrationResult::FAIL_INVALID_SERVICE, std::move(invalid_service));
+ pending_registration.user_handler_->Post(
+ common::BindOnce(std::move(pending_registration.on_registration_complete_callback_),
+ DynamicChannelManager::RegistrationResult::FAIL_INVALID_SERVICE, std::move(invalid_service)));
} else if (IsServiceRegistered(psm)) {
std::unique_ptr<DynamicChannelService> invalid_service(new DynamicChannelService());
- pending_registration.on_registration_complete_callback_.Invoke(
- DynamicChannelManager::RegistrationResult::FAIL_DUPLICATE_SERVICE, std::move(invalid_service));
+ pending_registration.user_handler_->Post(common::BindOnce(
+ std::move(pending_registration.on_registration_complete_callback_),
+ DynamicChannelManager::RegistrationResult::FAIL_DUPLICATE_SERVICE, std::move(invalid_service)));
} else {
- service_map_.try_emplace(
- psm,
- DynamicChannelServiceImpl(
- pending_registration.security_policy_,
- std::move(pending_registration.on_connection_open_callback_),
- pending_registration.configuration_));
+ service_map_.try_emplace(psm,
+ DynamicChannelServiceImpl(pending_registration.user_handler_,
+ pending_registration.security_policy_,
+ std::move(pending_registration.on_connection_open_callback_),
+ pending_registration.configuration_));
std::unique_ptr<DynamicChannelService> user_service(new DynamicChannelService(psm, this, l2cap_layer_handler_));
- pending_registration.on_registration_complete_callback_.Invoke(
- DynamicChannelManager::RegistrationResult::SUCCESS, std::move(user_service));
+ pending_registration.user_handler_->Post(
+ common::BindOnce(std::move(pending_registration.on_registration_complete_callback_),
+ DynamicChannelManager::RegistrationResult::SUCCESS, std::move(user_service)));
}
}
-void DynamicChannelServiceManagerImpl::Unregister(Psm psm, DynamicChannelService::OnUnregisteredCallback callback) {
+void DynamicChannelServiceManagerImpl::Unregister(Psm psm, DynamicChannelService::OnUnregisteredCallback callback,
+ os::Handler* handler) {
if (IsServiceRegistered(psm)) {
service_map_.erase(psm);
- callback.Invoke();
+ handler->Post(std::move(callback));
} else {
LOG_ERROR("service not registered psm:%d", psm);
}
diff --git a/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.h b/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.h
index 724d70a02..c98063990 100644
--- a/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.h
+++ b/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.h
@@ -20,7 +20,6 @@
#include "l2cap/classic/dynamic_channel_service.h"
#include "l2cap/classic/internal/dynamic_channel_service_impl.h"
-#include "l2cap/classic/security_enforcement_interface.h"
#include "l2cap/psm.h"
#include "os/handler.h"
#include "os/log.h"
@@ -40,25 +39,14 @@ class DynamicChannelServiceManagerImpl {
// All APIs must be invoked in L2CAP layer handler
//
virtual void Register(Psm psm, DynamicChannelServiceImpl::PendingRegistration pending_registration);
- virtual void Unregister(Psm psm, DynamicChannelService::OnUnregisteredCallback callback);
+ virtual void Unregister(Psm psm, DynamicChannelService::OnUnregisteredCallback callback, os::Handler* handler);
virtual bool IsServiceRegistered(Psm psm) const;
virtual DynamicChannelServiceImpl* GetService(Psm psm);
virtual std::vector<std::pair<Psm, DynamicChannelServiceImpl*>> GetRegisteredServices();
-
- // Implementation is set by SecurityManager through L2capModule
- void SetSecurityEnforcementInterface(SecurityEnforcementInterface* impl) {
- security_enforcement_interface_ = impl;
- }
-
- virtual SecurityEnforcementInterface* GetSecurityEnforcementInterface() {
- return security_enforcement_interface_;
- }
-
private:
os::Handler* l2cap_layer_handler_ = nullptr;
std::unordered_map<Psm, DynamicChannelServiceImpl> service_map_;
- SecurityEnforcementInterface* security_enforcement_interface_ = nullptr;
};
} // namespace internal
} // namespace classic
diff --git a/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl_mock.h b/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl_mock.h
index eb25d292f..05d4b7fc3 100644
--- a/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl_mock.h
+++ b/gd/l2cap/classic/internal/dynamic_channel_service_manager_impl_mock.h
@@ -16,7 +16,6 @@
#pragma once
#include "l2cap/classic/internal/dynamic_channel_service_manager_impl.h"
-#include "l2cap/classic/security_enforcement_interface.h"
#include "l2cap/internal/dynamic_channel_impl.h"
#include <gmock/gmock.h>
@@ -33,15 +32,15 @@ class MockDynamicChannelServiceManagerImpl : public DynamicChannelServiceManager
MockDynamicChannelServiceManagerImpl() : DynamicChannelServiceManagerImpl(nullptr) {}
MOCK_METHOD(void, Register, (Psm psm, DynamicChannelServiceImpl::PendingRegistration pending_registration),
(override));
- MOCK_METHOD(void, Unregister, (Psm psm, DynamicChannelService::OnUnregisteredCallback callback), (override));
+ MOCK_METHOD(void, Unregister, (Psm psm, DynamicChannelService::OnUnregisteredCallback callback, os::Handler* handler),
+ (override));
MOCK_METHOD(bool, IsServiceRegistered, (Psm psm), (const, override));
MOCK_METHOD(DynamicChannelServiceImpl*, GetService, (Psm psm), (override));
MOCK_METHOD((std::vector<std::pair<Psm, DynamicChannelServiceImpl*>>), GetRegisteredServices, (), (override));
- MOCK_METHOD(SecurityEnforcementInterface*, GetSecurityEnforcementInterface, (), (override));
};
} // namespace testing
} // namespace internal
} // namespace classic
} // namespace l2cap
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/gd/l2cap/classic/internal/dynamic_channel_service_manager_test.cc b/gd/l2cap/classic/internal/dynamic_channel_service_manager_test.cc
index 5decd3005..4cf32c6c8 100644
--- a/gd/l2cap/classic/internal/dynamic_channel_service_manager_test.cc
+++ b/gd/l2cap/classic/internal/dynamic_channel_service_manager_test.cc
@@ -34,7 +34,7 @@ namespace {
class L2capDynamicServiceManagerTest : public ::testing::Test {
public:
- ~L2capDynamicServiceManagerTest() = default;
+ ~L2capDynamicServiceManagerTest() override = default;
void OnServiceRegistered(bool expect_success, DynamicChannelManager::RegistrationResult result,
std::unique_ptr<DynamicChannelService> user_service) {
@@ -62,7 +62,7 @@ class L2capDynamicServiceManagerTest : public ::testing::Test {
void sync_user_handler() {
std::promise<void> promise;
auto future = promise.get_future();
- user_handler_->CallOn(&promise, &std::promise<void>::set_value);
+ user_handler_->Post(common::BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)));
auto future_status = future.wait_for(std::chrono::seconds(1));
EXPECT_EQ(future_status, std::future_status::ready);
}
@@ -78,24 +78,23 @@ class L2capDynamicServiceManagerTest : public ::testing::Test {
TEST_F(L2capDynamicServiceManagerTest, register_and_unregister_classic_dynamic_channel) {
DynamicChannelServiceImpl::PendingRegistration pending_registration{
.user_handler_ = user_handler_,
- .security_policy_ = SecurityPolicy::_SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK,
.on_registration_complete_callback_ =
- user_handler_->BindOnceOn(this, &L2capDynamicServiceManagerTest::OnServiceRegistered, true)};
+ common::BindOnce(&L2capDynamicServiceManagerTest::OnServiceRegistered, common::Unretained(this), true)};
Cid cid = kSmpBrCid;
EXPECT_FALSE(manager_->IsServiceRegistered(cid));
manager_->Register(cid, std::move(pending_registration));
EXPECT_TRUE(manager_->IsServiceRegistered(cid));
sync_user_handler();
EXPECT_TRUE(service_registered_);
- manager_->Unregister(cid, user_handler_->BindOnce([] {}));
+ manager_->Unregister(cid, common::BindOnce([] {}), user_handler_);
EXPECT_FALSE(manager_->IsServiceRegistered(cid));
}
TEST_F(L2capDynamicServiceManagerTest, register_classic_dynamic_channel_bad_cid) {
DynamicChannelServiceImpl::PendingRegistration pending_registration{
- .security_policy_ = SecurityPolicy::_SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK,
+ .user_handler_ = user_handler_,
.on_registration_complete_callback_ =
- user_handler_->BindOnceOn(this, &L2capDynamicServiceManagerTest::OnServiceRegistered, false)};
+ common::BindOnce(&L2capDynamicServiceManagerTest::OnServiceRegistered, common::Unretained(this), false)};
Cid cid = 0x1000;
EXPECT_FALSE(manager_->IsServiceRegistered(cid));
manager_->Register(cid, std::move(pending_registration));
diff --git a/gd/l2cap/classic/internal/fixed_channel_impl.cc b/gd/l2cap/classic/internal/fixed_channel_impl.cc
index d575f6682..9bfaef819 100644
--- a/gd/l2cap/classic/internal/fixed_channel_impl.cc
+++ b/gd/l2cap/classic/internal/fixed_channel_impl.cc
@@ -19,6 +19,7 @@
#include "l2cap/cid.h"
#include "l2cap/classic/internal/fixed_channel_impl.h"
#include "l2cap/classic/internal/link.h"
+#include "l2cap/security_policy.h"
#include "os/handler.h"
#include "os/log.h"
@@ -71,7 +72,7 @@ void FixedChannelImpl::Acquire() {
return;
}
if (acquired_) {
- LOG_INFO("%s was already acquired", ToString().c_str());
+ LOG_DEBUG("%s was already acquired", ToString().c_str());
return;
}
acquired_ = true;
@@ -86,7 +87,7 @@ void FixedChannelImpl::Release() {
return;
}
if (!acquired_) {
- LOG_INFO("%s was already released", ToString().c_str());
+ LOG_DEBUG("%s was already released", ToString().c_str());
return;
}
acquired_ = false;
diff --git a/gd/l2cap/classic/internal/fixed_channel_impl_test.cc b/gd/l2cap/classic/internal/fixed_channel_impl_test.cc
index efd379894..95817b7e0 100644
--- a/gd/l2cap/classic/internal/fixed_channel_impl_test.cc
+++ b/gd/l2cap/classic/internal/fixed_channel_impl_test.cc
@@ -63,12 +63,13 @@ TEST_F(L2capClassicFixedChannelImplTest, get_device) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetClassicLinkIdleDisconnectTimeout())
.WillRepeatedly(Return(std::chrono::seconds(5)));
- testing::MockClassicAclConnection* mock_acl_connection = new testing::MockClassicAclConnection();
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
EXPECT_CALL(*mock_acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*mock_acl_connection, UnregisterCallbacks(_)).Times(1);
MockLink mock_classic_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockClassicAclConnection>(mock_acl_connection),
- nullptr /* LinkManager */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
hci::AddressWithType device{hci::Address{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::PUBLIC_IDENTITY_ADDRESS};
EXPECT_CALL(mock_classic_link, GetDevice()).WillRepeatedly(Return(device));
@@ -80,12 +81,13 @@ TEST_F(L2capClassicFixedChannelImplTest, close_triggers_callback) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetClassicLinkIdleDisconnectTimeout())
.WillRepeatedly(Return(std::chrono::seconds(5)));
- testing::MockClassicAclConnection* mock_acl_connection = new testing::MockClassicAclConnection();
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
EXPECT_CALL(*mock_acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*mock_acl_connection, UnregisterCallbacks(_)).Times(1);
MockLink mock_classic_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockClassicAclConnection>(mock_acl_connection),
- nullptr /* LinkManager */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
hci::AddressWithType device{hci::Address{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::PUBLIC_IDENTITY_ADDRESS};
EXPECT_CALL(mock_classic_link, GetDevice()).WillRepeatedly(Return(device));
@@ -109,12 +111,13 @@ TEST_F(L2capClassicFixedChannelImplTest, register_callback_after_close_should_ca
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetClassicLinkIdleDisconnectTimeout())
.WillRepeatedly(Return(std::chrono::seconds(5)));
- testing::MockClassicAclConnection* mock_acl_connection = new testing::MockClassicAclConnection();
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
EXPECT_CALL(*mock_acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*mock_acl_connection, UnregisterCallbacks(_)).Times(1);
MockLink mock_classic_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockClassicAclConnection>(mock_acl_connection),
- nullptr /* LinkManager */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
hci::AddressWithType device{hci::Address{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::PUBLIC_IDENTITY_ADDRESS};
EXPECT_CALL(mock_classic_link, GetDevice()).WillRepeatedly(Return(device));
@@ -139,12 +142,13 @@ TEST_F(L2capClassicFixedChannelImplTest, close_twice_should_fail) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetClassicLinkIdleDisconnectTimeout())
.WillRepeatedly(Return(std::chrono::seconds(5)));
- testing::MockClassicAclConnection* mock_acl_connection = new testing::MockClassicAclConnection();
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
EXPECT_CALL(*mock_acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*mock_acl_connection, UnregisterCallbacks(_)).Times(1);
MockLink mock_classic_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockClassicAclConnection>(mock_acl_connection),
- nullptr /* LinkManager */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
hci::AddressWithType device{hci::Address{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::PUBLIC_IDENTITY_ADDRESS};
EXPECT_CALL(mock_classic_link, GetDevice()).WillRepeatedly(Return(device));
@@ -172,12 +176,13 @@ TEST_F(L2capClassicFixedChannelImplTest, multiple_registration_should_fail) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetClassicLinkIdleDisconnectTimeout())
.WillRepeatedly(Return(std::chrono::seconds(5)));
- testing::MockClassicAclConnection* mock_acl_connection = new testing::MockClassicAclConnection();
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
EXPECT_CALL(*mock_acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*mock_acl_connection, UnregisterCallbacks(_)).Times(1);
MockLink mock_classic_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockClassicAclConnection>(mock_acl_connection),
- nullptr /* LinkManager */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
hci::AddressWithType device{hci::Address{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::PUBLIC_IDENTITY_ADDRESS};
EXPECT_CALL(mock_classic_link, GetDevice()).WillRepeatedly(Return(device));
@@ -201,12 +206,13 @@ TEST_F(L2capClassicFixedChannelImplTest, call_acquire_before_registration_should
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetClassicLinkIdleDisconnectTimeout())
.WillRepeatedly(Return(std::chrono::seconds(5)));
- testing::MockClassicAclConnection* mock_acl_connection = new testing::MockClassicAclConnection();
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
EXPECT_CALL(*mock_acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*mock_acl_connection, UnregisterCallbacks(_)).Times(1);
MockLink mock_classic_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockClassicAclConnection>(mock_acl_connection),
- nullptr /* LinkManager */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
hci::AddressWithType device{hci::Address{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::PUBLIC_IDENTITY_ADDRESS};
EXPECT_CALL(mock_classic_link, GetDevice()).WillRepeatedly(Return(device));
@@ -219,12 +225,13 @@ TEST_F(L2capClassicFixedChannelImplTest, call_release_before_registration_should
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetClassicLinkIdleDisconnectTimeout())
.WillRepeatedly(Return(std::chrono::seconds(5)));
- testing::MockClassicAclConnection* mock_acl_connection = new testing::MockClassicAclConnection();
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
EXPECT_CALL(*mock_acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*mock_acl_connection, UnregisterCallbacks(_)).Times(1);
MockLink mock_classic_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockClassicAclConnection>(mock_acl_connection),
- nullptr /* LinkManager */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
hci::AddressWithType device{hci::Address{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::PUBLIC_IDENTITY_ADDRESS};
EXPECT_CALL(mock_classic_link, GetDevice()).WillRepeatedly(Return(device));
@@ -238,12 +245,13 @@ TEST_F(L2capClassicFixedChannelImplTest, test_acquire_release_channel) {
.WillRepeatedly(Return(std::chrono::seconds(5)));
EXPECT_CALL(mock_parameter_provider, GetClassicLinkIdleDisconnectTimeout())
.WillRepeatedly(Return(std::chrono::seconds(5)));
- testing::MockClassicAclConnection* mock_acl_connection = new testing::MockClassicAclConnection();
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
EXPECT_CALL(*mock_acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*mock_acl_connection, UnregisterCallbacks(_)).Times(1);
MockLink mock_classic_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockClassicAclConnection>(mock_acl_connection),
- nullptr /* LinkManager */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
hci::AddressWithType device{hci::Address{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::PUBLIC_IDENTITY_ADDRESS};
EXPECT_CALL(mock_classic_link, GetDevice()).WillRepeatedly(Return(device));
@@ -276,12 +284,13 @@ TEST_F(L2capClassicFixedChannelImplTest, test_acquire_after_close) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetClassicLinkIdleDisconnectTimeout())
.WillRepeatedly(Return(std::chrono::seconds(5)));
- testing::MockClassicAclConnection* mock_acl_connection = new testing::MockClassicAclConnection();
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
EXPECT_CALL(*mock_acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*mock_acl_connection, UnregisterCallbacks(_)).Times(1);
MockLink mock_classic_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockClassicAclConnection>(mock_acl_connection),
- nullptr /* LinkManager */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
hci::AddressWithType device{hci::Address{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::PUBLIC_IDENTITY_ADDRESS};
EXPECT_CALL(mock_classic_link, GetDevice()).WillRepeatedly(Return(device));
diff --git a/gd/l2cap/classic/internal/fixed_channel_service_manager_test.cc b/gd/l2cap/classic/internal/fixed_channel_service_manager_test.cc
index 7d5d8afdf..d58691388 100644
--- a/gd/l2cap/classic/internal/fixed_channel_service_manager_test.cc
+++ b/gd/l2cap/classic/internal/fixed_channel_service_manager_test.cc
@@ -34,7 +34,7 @@ namespace internal {
class L2capClassicFixedServiceManagerTest : public ::testing::Test {
public:
- ~L2capClassicFixedServiceManagerTest() = default;
+ ~L2capClassicFixedServiceManagerTest() override = default;
void OnServiceRegistered(bool expect_success, FixedChannelManager::RegistrationResult result,
std::unique_ptr<FixedChannelService> user_service) {
diff --git a/gd/l2cap/classic/internal/link.cc b/gd/l2cap/classic/internal/link.cc
index e6d4f0d0a..135f67f33 100644
--- a/gd/l2cap/classic/internal/link.cc
+++ b/gd/l2cap/classic/internal/link.cc
@@ -14,16 +14,13 @@
* limitations under the License.
*/
-#include "l2cap/classic/internal/link.h"
-
#include <chrono>
#include <memory>
-#include "common/bind.h"
-#include "hci/acl_manager/classic_acl_connection.h"
+#include "hci/acl_manager.h"
#include "l2cap/classic/dynamic_channel_manager.h"
#include "l2cap/classic/internal/fixed_channel_impl.h"
-#include "l2cap/classic/internal/link_manager.h"
+#include "l2cap/classic/internal/link.h"
#include "l2cap/internal/parameter_provider.h"
#include "os/alarm.h"
@@ -32,32 +29,16 @@ namespace l2cap {
namespace classic {
namespace internal {
-using RetransmissionAndFlowControlMode = DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode;
-using ConnectionResult = DynamicChannelManager::ConnectionResult;
-using ConnectionResultCode = DynamicChannelManager::ConnectionResultCode;
-
-Link::Link(
- os::Handler* l2cap_handler,
- std::unique_ptr<hci::acl_manager::ClassicAclConnection> acl_connection,
- l2cap::internal::ParameterProvider* parameter_provider,
- DynamicChannelServiceManagerImpl* dynamic_service_manager,
- FixedChannelServiceManagerImpl* fixed_service_manager,
- LinkManager* link_manager)
- : l2cap_handler_(l2cap_handler),
- acl_connection_(std::move(acl_connection)),
+Link::Link(os::Handler* l2cap_handler, std::unique_ptr<hci::AclConnection> acl_connection,
+ l2cap::internal::ParameterProvider* parameter_provider,
+ DynamicChannelServiceManagerImpl* dynamic_service_manager,
+ FixedChannelServiceManagerImpl* fixed_service_manager)
+ : l2cap_handler_(l2cap_handler), acl_connection_(std::move(acl_connection)),
data_pipeline_manager_(l2cap_handler, this, acl_connection_->GetAclQueueEnd()),
- parameter_provider_(parameter_provider),
- dynamic_service_manager_(dynamic_service_manager),
+ parameter_provider_(parameter_provider), dynamic_service_manager_(dynamic_service_manager),
fixed_service_manager_(fixed_service_manager),
- link_manager_(link_manager),
- signalling_manager_(
- l2cap_handler_,
- this,
- &data_pipeline_manager_,
- dynamic_service_manager_,
- &dynamic_channel_allocator_,
- fixed_service_manager_),
- acl_handle_(acl_connection_->GetHandle()) {
+ signalling_manager_(l2cap_handler_, this, &data_pipeline_manager_, dynamic_service_manager_,
+ &dynamic_channel_allocator_, fixed_service_manager_) {
ASSERT(l2cap_handler_ != nullptr);
ASSERT(acl_connection_ != nullptr);
ASSERT(parameter_provider_ != nullptr);
@@ -66,12 +47,16 @@ Link::Link(
acl_connection_->RegisterCallbacks(this, l2cap_handler_);
}
+Link::~Link() {
+ acl_connection_->UnregisterCallbacks(this);
+}
+
void Link::OnAclDisconnected(hci::ErrorCode status) {
signalling_manager_.CancelAlarm();
fixed_channel_allocator_.OnAclDisconnected(status);
dynamic_channel_allocator_.OnAclDisconnected(status);
- ConnectionResult result{
- .connection_result_code = ConnectionResultCode::FAIL_HCI_ERROR,
+ DynamicChannelManager::ConnectionResult result{
+ .connection_result_code = DynamicChannelManager::ConnectionResultCode::FAIL_HCI_ERROR,
.hci_error = status,
.l2cap_connection_response_result = ConnectionResponseResult::SUCCESS,
};
@@ -86,16 +71,11 @@ void Link::Disconnect() {
}
void Link::Encrypt() {
- if (encryption_enabled_ == hci::EncryptionEnabled::OFF) {
- acl_connection_->SetConnectionEncryption(hci::Enable::ENABLED);
- }
+ acl_connection_->SetConnectionEncryption(hci::Enable::ENABLED);
}
void Link::Authenticate() {
- if (!IsAuthenticated() && !has_requested_authentication_) {
- has_requested_authentication_ = true;
- acl_connection_->AuthenticationRequested();
- }
+ acl_connection_->AuthenticationRequested();
}
bool Link::IsAuthenticated() const {
@@ -110,25 +90,16 @@ void Link::ReadRemoteSupportedFeatures() {
acl_connection_->ReadRemoteSupportedFeatures();
}
-void Link::ReadRemoteExtendedFeatures(uint8_t page_number) {
- acl_connection_->ReadRemoteExtendedFeatures(page_number);
+void Link::ReadRemoteExtendedFeatures() {
+ acl_connection_->ReadRemoteExtendedFeatures();
}
void Link::ReadClockOffset() {
acl_connection_->ReadClockOffset();
}
-void Link::AcquireSecurityHold() {
- used_by_security_module_ = true;
- RefreshRefCount();
-}
-void Link::ReleaseSecurityHold() {
- used_by_security_module_ = false;
- RefreshRefCount();
-}
-
-std::shared_ptr<FixedChannelImpl> Link::AllocateFixedChannel(Cid cid) {
- auto channel = fixed_channel_allocator_.AllocateChannel(cid);
+std::shared_ptr<FixedChannelImpl> Link::AllocateFixedChannel(Cid cid, SecurityPolicy security_policy) {
+ auto channel = fixed_channel_allocator_.AllocateChannel(cid, security_policy);
data_pipeline_manager_.AttachChannel(cid, channel, l2cap::internal::DataPipelineManager::ChannelMode::BASIC);
return channel;
}
@@ -147,74 +118,23 @@ void Link::SendConnectionRequest(Psm psm, Cid local_cid) {
void Link::SendConnectionRequest(Psm psm, Cid local_cid,
PendingDynamicChannelConnection pending_dynamic_channel_connection) {
- if (pending_dynamic_channel_connection.configuration_.channel_mode ==
- RetransmissionAndFlowControlMode::ENHANCED_RETRANSMISSION &&
- !remote_extended_feature_received_) {
- pending_dynamic_psm_list_.push_back(psm);
- pending_dynamic_channel_callback_list_.push_back(std::move(pending_dynamic_channel_connection));
- LOG_INFO("Will connect after information response ERTM feature support is received");
- dynamic_channel_allocator_.FreeChannel(local_cid);
- return;
- } else if (pending_dynamic_channel_connection.configuration_.channel_mode ==
- RetransmissionAndFlowControlMode::ENHANCED_RETRANSMISSION &&
- !GetRemoteSupportsErtm()) {
- LOG_WARN("Remote doesn't support ERTM. Dropping connection request");
- ConnectionResult result{
- .connection_result_code = ConnectionResultCode::FAIL_REMOTE_NOT_SUPPORT,
- };
- pending_dynamic_channel_connection.on_fail_callback_.Invoke(result);
- dynamic_channel_allocator_.FreeChannel(local_cid);
- return;
- } else {
- local_cid_to_pending_dynamic_channel_connection_map_[local_cid] = std::move(pending_dynamic_channel_connection);
- signalling_manager_.SendConnectionRequest(psm, local_cid);
- }
-}
-
-void Link::SetChannelTxPriority(Cid local_cid, bool high_priority) {
- data_pipeline_manager_.SetChannelTxPriority(local_cid, high_priority);
-}
-
-void Link::SetPendingDynamicChannels(std::list<Psm> psm_list,
- std::list<Link::PendingDynamicChannelConnection> callback_list) {
- ASSERT(psm_list.size() == callback_list.size());
- pending_dynamic_psm_list_ = std::move(psm_list);
- pending_dynamic_channel_callback_list_ = std::move(callback_list);
-}
-
-void Link::connect_to_pending_dynamic_channels() {
- auto psm = pending_dynamic_psm_list_.begin();
- auto callback = pending_dynamic_channel_callback_list_.begin();
- while (psm != pending_dynamic_psm_list_.end()) {
- SendConnectionRequest(*psm, ReserveDynamicChannel(), std::move(*callback));
- psm++;
- callback++;
- }
-}
-
-void Link::send_pending_configuration_requests() {
- for (auto local_cid : pending_outgoing_configuration_request_list_) {
- signalling_manager_.SendInitialConfigRequest(local_cid);
- }
- pending_outgoing_configuration_request_list_.clear();
+ local_cid_to_pending_dynamic_channel_connection_map_[local_cid] = std::move(pending_dynamic_channel_connection);
+ signalling_manager_.SendConnectionRequest(psm, local_cid);
}
-void Link::OnOutgoingConnectionRequestFail(Cid local_cid, ConnectionResult result) {
+void Link::OnOutgoingConnectionRequestFail(Cid local_cid) {
if (local_cid_to_pending_dynamic_channel_connection_map_.find(local_cid) !=
local_cid_to_pending_dynamic_channel_connection_map_.end()) {
+ DynamicChannelManager::ConnectionResult result{
+ .connection_result_code = DynamicChannelManager::ConnectionResultCode::FAIL_HCI_ERROR,
+ .hci_error = hci::ErrorCode::CONNECTION_TIMEOUT,
+ .l2cap_connection_response_result = ConnectionResponseResult::SUCCESS,
+ };
NotifyChannelFail(local_cid, result);
}
dynamic_channel_allocator_.FreeChannel(local_cid);
}
-void Link::SendInitialConfigRequestOrQueue(Cid local_cid) {
- if (remote_extended_feature_received_) {
- signalling_manager_.SendInitialConfigRequest(local_cid);
- } else {
- pending_outgoing_configuration_request_list_.push_back(local_cid);
- }
-}
-
void Link::SendDisconnectionRequest(Cid local_cid, Cid remote_cid) {
signalling_manager_.SendDisconnectionRequest(local_cid, remote_cid);
}
@@ -223,19 +143,24 @@ void Link::SendInformationRequest(InformationRequestInfoType type) {
signalling_manager_.SendInformationRequest(type);
}
-std::shared_ptr<l2cap::internal::DynamicChannelImpl> Link::AllocateDynamicChannel(Psm psm, Cid remote_cid) {
- auto channel = dynamic_channel_allocator_.AllocateChannel(psm, remote_cid);
+std::shared_ptr<l2cap::internal::DynamicChannelImpl> Link::AllocateDynamicChannel(Psm psm, Cid remote_cid,
+ SecurityPolicy security_policy) {
+ auto channel = dynamic_channel_allocator_.AllocateChannel(psm, remote_cid, security_policy);
if (channel != nullptr) {
+ data_pipeline_manager_.AttachChannel(channel->GetCid(), channel,
+ l2cap::internal::DataPipelineManager::ChannelMode::BASIC);
RefreshRefCount();
- channel->local_initiated_ = false;
}
+ channel->local_initiated_ = false;
return channel;
}
-std::shared_ptr<l2cap::internal::DynamicChannelImpl> Link::AllocateReservedDynamicChannel(Cid reserved_cid, Psm psm,
- Cid remote_cid) {
- auto channel = dynamic_channel_allocator_.AllocateReservedChannel(reserved_cid, psm, remote_cid);
+std::shared_ptr<l2cap::internal::DynamicChannelImpl> Link::AllocateReservedDynamicChannel(
+ Cid reserved_cid, Psm psm, Cid remote_cid, SecurityPolicy security_policy) {
+ auto channel = dynamic_channel_allocator_.AllocateReservedChannel(reserved_cid, psm, remote_cid, security_policy);
if (channel != nullptr) {
+ data_pipeline_manager_.AttachChannel(channel->GetCid(), channel,
+ l2cap::internal::DataPipelineManager::ChannelMode::BASIC);
RefreshRefCount();
}
channel->local_initiated_ = true;
@@ -252,6 +177,7 @@ void Link::FreeDynamicChannel(Cid cid) {
if (dynamic_channel_allocator_.FindChannelByCid(cid) == nullptr) {
return;
}
+ data_pipeline_manager_.DetachChannel(cid);
dynamic_channel_allocator_.FreeChannel(cid);
RefreshRefCount();
}
@@ -260,9 +186,6 @@ void Link::RefreshRefCount() {
int ref_count = 0;
ref_count += fixed_channel_allocator_.GetRefCount();
ref_count += dynamic_channel_allocator_.NumberOfChannels();
- if (used_by_security_module_) {
- ref_count += 1;
- }
ASSERT_LOG(ref_count >= 0, "ref_count %d is less than 0", ref_count);
if (ref_count > 0) {
link_idle_disconnect_alarm_.Cancel();
@@ -276,15 +199,17 @@ void Link::NotifyChannelCreation(Cid cid, std::unique_ptr<DynamicChannel> user_c
ASSERT(local_cid_to_pending_dynamic_channel_connection_map_.find(cid) !=
local_cid_to_pending_dynamic_channel_connection_map_.end());
auto& pending_dynamic_channel_connection = local_cid_to_pending_dynamic_channel_connection_map_[cid];
- pending_dynamic_channel_connection.on_open_callback_.Invoke(std::move(user_channel));
+ pending_dynamic_channel_connection.handler_->Post(
+ common::BindOnce(std::move(pending_dynamic_channel_connection.on_open_callback_), std::move(user_channel)));
local_cid_to_pending_dynamic_channel_connection_map_.erase(cid);
}
-void Link::NotifyChannelFail(Cid cid, ConnectionResult result) {
+void Link::NotifyChannelFail(Cid cid, DynamicChannelManager::ConnectionResult result) {
ASSERT(local_cid_to_pending_dynamic_channel_connection_map_.find(cid) !=
local_cid_to_pending_dynamic_channel_connection_map_.end());
auto& pending_dynamic_channel_connection = local_cid_to_pending_dynamic_channel_connection_map_[cid];
- pending_dynamic_channel_connection.on_fail_callback_.Invoke(result);
+ pending_dynamic_channel_connection.handler_->Post(
+ common::BindOnce(std::move(pending_dynamic_channel_connection.on_fail_callback_), result));
local_cid_to_pending_dynamic_channel_connection_map_.erase(cid);
}
@@ -296,176 +221,110 @@ Mtu Link::GetRemoteConnectionlessMtu() const {
return remote_connectionless_mtu_;
}
+void Link::SetRemoteSupportsErtm(bool supported) {
+ remote_supports_ertm_ = supported;
+}
+
bool Link::GetRemoteSupportsErtm() const {
return remote_supports_ertm_;
}
+void Link::SetRemoteSupportsFcs(bool supported) {
+ remote_supports_fcs_ = supported;
+}
+
bool Link::GetRemoteSupportsFcs() const {
return remote_supports_fcs_;
}
-void Link::OnRemoteExtendedFeatureReceived(bool ertm_supported, bool fcs_supported) {
- remote_supports_ertm_ = ertm_supported;
- remote_supports_fcs_ = fcs_supported;
- remote_extended_feature_received_ = true;
- connect_to_pending_dynamic_channels();
- send_pending_configuration_requests();
+void Link::AddChannelPendingingAuthentication(PendingAuthenticateDynamicChannelConnection pending_channel) {
+ pending_channel_list_.push_back(std::move(pending_channel));
}
void Link::OnConnectionPacketTypeChanged(uint16_t packet_type) {
- LOG_INFO("UNIMPLEMENTED %s packet_type:%x", __func__, packet_type);
+ LOG_DEBUG("UNIMPLEMENTED %s packet_type:%x", __func__, packet_type);
}
-void Link::OnAuthenticationComplete(hci::ErrorCode hci_status) {
- link_manager_->OnAuthenticationComplete(hci_status, GetDevice().GetAddress());
+void Link::OnAuthenticationComplete() {
+ if (!pending_channel_list_.empty()) {
+ acl_connection_->SetConnectionEncryption(hci::Enable::ENABLED);
+ }
}
void Link::OnEncryptionChange(hci::EncryptionEnabled enabled) {
encryption_enabled_ = enabled;
- link_manager_->OnEncryptionChange(GetDevice().GetAddress(), enabled);
- for (auto& listener : encryption_change_listener_) {
- signalling_manager_.on_security_result_for_outgoing(
- ClassicSignallingManager::SecurityEnforcementType::ENCRYPTION,
- listener.psm,
- listener.cid,
- enabled != hci::EncryptionEnabled::OFF);
+ if (encryption_enabled_ == hci::EncryptionEnabled::OFF) {
+ LOG_DEBUG("Encryption has changed to disabled");
+ return;
+ }
+ LOG_DEBUG("Encryption has changed to enabled .. restarting channels:%zd", pending_channel_list_.size());
+
+ for (auto& channel : pending_channel_list_) {
+ local_cid_to_pending_dynamic_channel_connection_map_[channel.cid_] =
+ std::move(channel.pending_dynamic_channel_connection_);
+ signalling_manager_.SendConnectionRequest(channel.psm_, channel.cid_);
}
+ pending_channel_list_.clear();
}
void Link::OnChangeConnectionLinkKeyComplete() {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_DEBUG("UNIMPLEMENTED %s", __func__);
}
void Link::OnReadClockOffsetComplete(uint16_t clock_offset) {
- link_manager_->OnReadClockOffset(GetDevice().GetAddress(), clock_offset);
+ LOG_DEBUG("UNIMPLEMENTED %s clock_offset:%d", __func__, clock_offset);
}
-void Link::OnModeChange(hci::ErrorCode status, hci::Mode current_mode, uint16_t interval) {
- link_manager_->OnModeChange(status, GetDevice().GetAddress(), current_mode, interval);
-}
-
-void Link::OnSniffSubrating(
- hci::ErrorCode hci_status,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) {
- link_manager_->OnSniffSubrating(
- hci_status,
- GetDevice().GetAddress(),
- maximum_transmit_latency,
- maximum_receive_latency,
- minimum_remote_timeout,
- minimum_local_timeout);
+void Link::OnModeChange(hci::Mode current_mode, uint16_t interval) {
+ LOG_DEBUG("UNIMPLEMENTED %s mode:%s interval:%d", __func__, hci::ModeText(current_mode).c_str(), interval);
}
void Link::OnQosSetupComplete(hci::ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth,
uint32_t latency, uint32_t delay_variation) {
- LOG_INFO(
- "UNIMPLEMENTED %s service_type:%s token_rate:%d peak_bandwidth:%d latency:%d delay_varitation:%d",
- __func__,
- hci::ServiceTypeText(service_type).c_str(),
- token_rate,
- peak_bandwidth,
- latency,
- delay_variation);
+ LOG_DEBUG("UNIMPLEMENTED %s service_type:%s token_rate:%d peak_bandwidth:%d latency:%d delay_varitation:%d", __func__,
+ hci::ServiceTypeText(service_type).c_str(), token_rate, peak_bandwidth, latency, delay_variation);
}
void Link::OnFlowSpecificationComplete(hci::FlowDirection flow_direction, hci::ServiceType service_type,
uint32_t token_rate, uint32_t token_bucket_size, uint32_t peak_bandwidth,
uint32_t access_latency) {
- LOG_INFO(
+ LOG_DEBUG(
"UNIMPLEMENTED %s flow_direction:%s service_type:%s token_rate:%d token_bucket_size:%d peak_bandwidth:%d "
"access_latency:%d",
- __func__,
- hci::FlowDirectionText(flow_direction).c_str(),
- hci::ServiceTypeText(service_type).c_str(),
- token_rate,
- token_bucket_size,
- peak_bandwidth,
- access_latency);
+ __func__, hci::FlowDirectionText(flow_direction).c_str(), hci::ServiceTypeText(service_type).c_str(), token_rate,
+ token_bucket_size, peak_bandwidth, access_latency);
}
void Link::OnFlushOccurred() {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_DEBUG("UNIMPLEMENTED %s", __func__);
}
void Link::OnRoleDiscoveryComplete(hci::Role current_role) {
- role_ = current_role;
+ LOG_DEBUG("UNIMPLEMENTED %s current_role:%s", __func__, hci::RoleText(current_role).c_str());
}
void Link::OnReadLinkPolicySettingsComplete(uint16_t link_policy_settings) {
- LOG_INFO("UNIMPLEMENTED %s link_policy_settings:0x%x", __func__, link_policy_settings);
+ LOG_DEBUG("UNIMPLEMENTED %s link_policy_settings:0x%x", __func__, link_policy_settings);
}
void Link::OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout) {
- LOG_INFO("UNIMPLEMENTED %s flush_timeout:%d", __func__, flush_timeout);
+ LOG_DEBUG("UNIMPLEMENTED %s flush_timeout:%d", __func__, flush_timeout);
}
void Link::OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level) {
- LOG_INFO("UNIMPLEMENTED %s transmit_power_level:%d", __func__, transmit_power_level);
+ LOG_DEBUG("UNIMPLEMENTED %s transmit_power_level:%d", __func__, transmit_power_level);
}
void Link::OnReadLinkSupervisionTimeoutComplete(uint16_t link_supervision_timeout) {
- LOG_INFO("UNIMPLEMENTED %s link_supervision_timeout:%d", __func__, link_supervision_timeout);
+ LOG_DEBUG("UNIMPLEMENTED %s link_supervision_timeout:%d", __func__, link_supervision_timeout);
}
void Link::OnReadFailedContactCounterComplete(uint16_t failed_contact_counter) {
- LOG_INFO("UNIMPLEMENTED %sfailed_contact_counter:%hu", __func__, failed_contact_counter);
+ LOG_DEBUG("UNIMPLEMENTED %sfailed_contact_counter:%hu", __func__, failed_contact_counter);
}
void Link::OnReadLinkQualityComplete(uint8_t link_quality) {
- LOG_INFO("UNIMPLEMENTED %s link_quality:%hhu", __func__, link_quality);
+ LOG_DEBUG("UNIMPLEMENTED %s link_quality:%hhu", __func__, link_quality);
}
void Link::OnReadAfhChannelMapComplete(hci::AfhMode afh_mode, std::array<uint8_t, 10> afh_channel_map) {
- LOG_INFO("UNIMPLEMENTED %s afh_mode:%s", __func__, hci::AfhModeText(afh_mode).c_str());
+ LOG_DEBUG("UNIMPLEMENTED %s afh_mode:%s", __func__, hci::AfhModeText(afh_mode).c_str());
}
void Link::OnReadRssiComplete(uint8_t rssi) {
- LOG_INFO("UNIMPLEMENTED %s rssi:%hhd", __func__, rssi);
+ LOG_DEBUG("UNIMPLEMENTED %s rssi:%hhd", __func__, rssi);
}
void Link::OnReadClockComplete(uint32_t clock, uint16_t accuracy) {
- LOG_INFO("UNIMPLEMENTED %s clock:%u accuracy:%hu", __func__, clock, accuracy);
-}
-void Link::OnCentralLinkKeyComplete(hci::KeyFlag key_flag) {
- LOG_INFO("UNIMPLEMENTED key_flag:%s", hci::KeyFlagText(key_flag).c_str());
-}
-void Link::OnRoleChange(hci::ErrorCode hci_status, hci::Role new_role) {
- role_ = new_role;
- link_manager_->OnRoleChange(hci_status, GetDevice().GetAddress(), new_role);
-}
-void Link::OnDisconnection(hci::ErrorCode reason) {
- OnAclDisconnected(reason);
- link_manager_->OnDisconnect(GetDevice().GetAddress(), reason);
-}
-void Link::OnReadRemoteVersionInformationComplete(
- hci::ErrorCode hci_status, uint8_t lmp_version, uint16_t manufacturer_name, uint16_t sub_version) {
- LOG_INFO(
- "UNIMPLEMENTED hci_status:%s lmp_version:%hhu manufacturer_name:%hu sub_version:%hu",
- ErrorCodeText(hci_status).c_str(),
- lmp_version,
- manufacturer_name,
- sub_version);
- link_manager_->OnReadRemoteVersionInformation(
- hci_status, GetDevice().GetAddress(), lmp_version, manufacturer_name, sub_version);
-}
-void Link::OnReadRemoteSupportedFeaturesComplete(uint64_t features) {
- LOG_INFO("page_number:%hhu features:0x%lx", static_cast<uint8_t>(0), static_cast<unsigned long>(features));
- link_manager_->OnReadRemoteSupportedFeatures(GetDevice().GetAddress(), features);
-}
-
-void Link::OnReadRemoteExtendedFeaturesComplete(uint8_t page_number, uint8_t max_page_number, uint64_t features) {
- LOG_INFO(
- "page_number:%hhu max_page_number:%hhu features:0x%lx",
- page_number,
- max_page_number,
- static_cast<unsigned long>(features));
- link_manager_->OnReadRemoteExtendedFeatures(GetDevice().GetAddress(), page_number, max_page_number, features);
-}
-
-void Link::AddEncryptionChangeListener(EncryptionChangeListener listener) {
- encryption_change_listener_.push_back(listener);
-}
-
-void Link::OnPendingPacketChange(Cid local_cid, bool has_packet) {
- if (has_packet) {
- remaining_packets_to_be_sent_++;
- } else {
- remaining_packets_to_be_sent_--;
- }
- if (link_manager_ != nullptr) {
- link_manager_->OnPendingPacketChange(GetDevice().GetAddress(), remaining_packets_to_be_sent_);
- }
+ LOG_DEBUG("UNIMPLEMENTED %s clock:%u accuracy:%hu", __func__, clock, accuracy);
}
} // namespace internal
diff --git a/gd/l2cap/classic/internal/link.h b/gd/l2cap/classic/internal/link.h
index a5b17a9dc..fe40b5268 100644
--- a/gd/l2cap/classic/internal/link.h
+++ b/gd/l2cap/classic/internal/link.h
@@ -16,16 +16,14 @@
#pragma once
-#include <atomic>
#include <memory>
#include <unordered_map>
-#include "hci/acl_manager/classic_acl_connection.h"
+#include "hci/acl_manager.h"
#include "l2cap/classic/dynamic_channel_configuration_option.h"
#include "l2cap/classic/internal/dynamic_channel_service_manager_impl.h"
#include "l2cap/classic/internal/fixed_channel_impl.h"
#include "l2cap/classic/internal/fixed_channel_service_manager_impl.h"
-#include "l2cap/classic/security_enforcement_interface.h"
#include "l2cap/internal/data_pipeline_manager.h"
#include "l2cap/internal/dynamic_channel_allocator.h"
#include "l2cap/internal/dynamic_channel_impl.h"
@@ -41,18 +39,16 @@ namespace l2cap {
namespace classic {
namespace internal {
-class LinkManager;
-class DumpsysHelper;
-
-class Link : public l2cap::internal::ILink, public hci::acl_manager::ConnectionManagementCallbacks {
+class Link : public l2cap::internal::ILink, public hci::ConnectionManagementCallbacks {
public:
- Link(os::Handler* l2cap_handler, std::unique_ptr<hci::acl_manager::ClassicAclConnection> acl_connection,
+ Link(os::Handler* l2cap_handler, std::unique_ptr<hci::AclConnection> acl_connection,
l2cap::internal::ParameterProvider* parameter_provider,
- DynamicChannelServiceManagerImpl* dynamic_service_manager, FixedChannelServiceManagerImpl* fixed_service_manager,
- LinkManager* link_manager);
+ DynamicChannelServiceManagerImpl* dynamic_service_manager,
+ FixedChannelServiceManagerImpl* fixed_service_manager);
+ ~Link();
- hci::AddressWithType GetDevice() const override {
- return {acl_connection_->GetAddress(), hci::AddressType::PUBLIC_DEVICE_ADDRESS};
+ hci::AddressWithType GetDevice() override {
+ return {acl_connection_->GetAddress(), acl_connection_->GetAddressType()};
}
struct PendingDynamicChannelConnection {
@@ -84,19 +80,13 @@ class Link : public l2cap::internal::ILink, public hci::acl_manager::ConnectionM
virtual void ReadRemoteSupportedFeatures();
- virtual void ReadRemoteExtendedFeatures(uint8_t page_number);
+ virtual void ReadRemoteExtendedFeatures();
virtual void ReadClockOffset();
- // Increase the link usage refcount to ensure the link won't be disconnected when SecurityModule needs it
- virtual void AcquireSecurityHold();
-
- // Decrease the link usage refcount when SecurityModule no longer needs it
- virtual void ReleaseSecurityHold();
-
// FixedChannel methods
- std::shared_ptr<FixedChannelImpl> AllocateFixedChannel(Cid cid);
+ std::shared_ptr<FixedChannelImpl> AllocateFixedChannel(Cid cid, SecurityPolicy security_policy);
virtual bool IsFixedChannelAllocated(Cid cid);
@@ -107,25 +97,19 @@ class Link : public l2cap::internal::ILink, public hci::acl_manager::ConnectionM
virtual void SendConnectionRequest(Psm psm, Cid local_cid);
virtual void SendConnectionRequest(Psm psm, Cid local_cid,
PendingDynamicChannelConnection pending_dynamic_channel_connection);
- void SetChannelTxPriority(Cid local_cid, bool high_priority) override;
-
- // When a Link is established, LinkManager notifies pending dynamic channels to connect
- virtual void SetPendingDynamicChannels(std::list<Psm> psm_list,
- std::list<Link::PendingDynamicChannelConnection> callback_list);
// Invoked by signalling manager to indicate an outgoing connection request failed and link shall free resources
- virtual void OnOutgoingConnectionRequestFail(Cid local_cid, DynamicChannelManager::ConnectionResult result);
-
- virtual void SendInitialConfigRequestOrQueue(Cid local_cid);
+ virtual void OnOutgoingConnectionRequestFail(Cid local_cid);
virtual void SendInformationRequest(InformationRequestInfoType type);
virtual void SendDisconnectionRequest(Cid local_cid, Cid remote_cid) override;
- virtual std::shared_ptr<l2cap::internal::DynamicChannelImpl> AllocateDynamicChannel(Psm psm, Cid remote_cid);
+ virtual std::shared_ptr<l2cap::internal::DynamicChannelImpl> AllocateDynamicChannel(Psm psm, Cid remote_cid,
+ SecurityPolicy security_policy);
- virtual std::shared_ptr<l2cap::internal::DynamicChannelImpl> AllocateReservedDynamicChannel(Cid reserved_cid, Psm psm,
- Cid remote_cid);
+ virtual std::shared_ptr<l2cap::internal::DynamicChannelImpl> AllocateReservedDynamicChannel(
+ Cid reserved_cid, Psm psm, Cid remote_cid, SecurityPolicy security_policy);
virtual classic::DynamicChannelConfigurationOption GetConfigurationForInitialConfiguration(Cid cid);
@@ -140,100 +124,60 @@ class Link : public l2cap::internal::ILink, public hci::acl_manager::ConnectionM
// Information received from signaling channel
virtual void SetRemoteConnectionlessMtu(Mtu mtu);
virtual Mtu GetRemoteConnectionlessMtu() const;
+ virtual void SetRemoteSupportsErtm(bool supported);
virtual bool GetRemoteSupportsErtm() const;
+ virtual void SetRemoteSupportsFcs(bool supported);
virtual bool GetRemoteSupportsFcs() const;
- virtual void OnRemoteExtendedFeatureReceived(bool ertm_supported, bool fcs_supported);
- virtual std::string ToString() const {
+ virtual std::string ToString() {
return GetDevice().ToString();
}
void SendLeCredit(Cid local_cid, uint16_t credit) override {}
- // ConnectionManagementCallbacks
- void OnConnectionPacketTypeChanged(uint16_t packet_type) override;
- void OnAuthenticationComplete(hci::ErrorCode hci_status) override;
- void OnEncryptionChange(hci::EncryptionEnabled enabled) override;
- void OnChangeConnectionLinkKeyComplete() override;
- void OnReadClockOffsetComplete(uint16_t clock_offset) override;
- void OnModeChange(hci::ErrorCode status, hci::Mode current_mode, uint16_t interval) override;
- void OnSniffSubrating(
- hci::ErrorCode hci_status,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) override;
- void OnQosSetupComplete(hci::ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth, uint32_t latency,
- uint32_t delay_variation) override;
- void OnFlowSpecificationComplete(hci::FlowDirection flow_direction, hci::ServiceType service_type,
- uint32_t token_rate, uint32_t token_bucket_size, uint32_t peak_bandwidth,
- uint32_t access_latency) override;
- void OnFlushOccurred() override;
- void OnRoleDiscoveryComplete(hci::Role current_role) override;
- void OnReadLinkPolicySettingsComplete(uint16_t link_policy_settings) override;
- void OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout) override;
- void OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level) override;
- void OnReadLinkSupervisionTimeoutComplete(uint16_t link_supervision_timeout) override;
- void OnReadFailedContactCounterComplete(uint16_t failed_contact_counter) override;
- void OnReadLinkQualityComplete(uint8_t link_quality) override;
- void OnReadAfhChannelMapComplete(hci::AfhMode afh_mode, std::array<uint8_t, 10> afh_channel_map) override;
- void OnReadRssiComplete(uint8_t rssi) override;
- void OnReadClockComplete(uint32_t clock, uint16_t accuracy) override;
- void OnCentralLinkKeyComplete(hci::KeyFlag key_flag) override;
- void OnRoleChange(hci::ErrorCode hci_status, hci::Role new_role) override;
- void OnDisconnection(hci::ErrorCode reason) override;
- void OnReadRemoteVersionInformationComplete(
- hci::ErrorCode hci_status, uint8_t lmp_version, uint16_t manufacturer_name, uint16_t sub_version);
- void OnReadRemoteSupportedFeaturesComplete(uint64_t features);
- void OnReadRemoteExtendedFeaturesComplete(uint8_t page_number, uint8_t max_page_number, uint64_t features);
-
- struct EncryptionChangeListener {
- Cid cid;
- Psm psm;
- };
- void AddEncryptionChangeListener(EncryptionChangeListener);
+ void AddChannelPendingingAuthentication(PendingAuthenticateDynamicChannelConnection pending_channel);
- uint16_t GetAclHandle() const {
- return acl_handle_;
- }
-
- hci::Role GetRole() const {
- return role_;
- }
-
- void OnPendingPacketChange(Cid local_cid, bool has_packet) override;
+ // ConnectionManagementCallbacks
+ virtual void OnConnectionPacketTypeChanged(uint16_t packet_type) override;
+ virtual void OnAuthenticationComplete() override;
+ virtual void OnEncryptionChange(hci::EncryptionEnabled enabled) override;
+ virtual void OnChangeConnectionLinkKeyComplete() override;
+ virtual void OnReadClockOffsetComplete(uint16_t clock_offset) override;
+ virtual void OnModeChange(hci::Mode current_mode, uint16_t interval) override;
+ virtual void OnQosSetupComplete(hci::ServiceType service_type, uint32_t token_rate, uint32_t peak_bandwidth,
+ uint32_t latency, uint32_t delay_variation) override;
+ virtual void OnFlowSpecificationComplete(hci::FlowDirection flow_direction, hci::ServiceType service_type,
+ uint32_t token_rate, uint32_t token_bucket_size, uint32_t peak_bandwidth,
+ uint32_t access_latency) override;
+ virtual void OnFlushOccurred() override;
+ virtual void OnRoleDiscoveryComplete(hci::Role current_role) override;
+ virtual void OnReadLinkPolicySettingsComplete(uint16_t link_policy_settings) override;
+ virtual void OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout) override;
+ virtual void OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level) override;
+ virtual void OnReadLinkSupervisionTimeoutComplete(uint16_t link_supervision_timeout) override;
+ virtual void OnReadFailedContactCounterComplete(uint16_t failed_contact_counter) override;
+ virtual void OnReadLinkQualityComplete(uint8_t link_quality) override;
+ virtual void OnReadAfhChannelMapComplete(hci::AfhMode afh_mode, std::array<uint8_t, 10> afh_channel_map) override;
+ virtual void OnReadRssiComplete(uint8_t rssi) override;
+ virtual void OnReadClockComplete(uint32_t clock, uint16_t accuracy) override;
private:
- friend class DumpsysHelper;
- void connect_to_pending_dynamic_channels();
- void send_pending_configuration_requests();
-
os::Handler* l2cap_handler_;
l2cap::internal::FixedChannelAllocator<FixedChannelImpl, Link> fixed_channel_allocator_{this, l2cap_handler_};
l2cap::internal::DynamicChannelAllocator dynamic_channel_allocator_{this, l2cap_handler_};
- std::unique_ptr<hci::acl_manager::ClassicAclConnection> acl_connection_;
+ std::unique_ptr<hci::AclConnection> acl_connection_;
l2cap::internal::DataPipelineManager data_pipeline_manager_;
l2cap::internal::ParameterProvider* parameter_provider_;
DynamicChannelServiceManagerImpl* dynamic_service_manager_;
FixedChannelServiceManagerImpl* fixed_service_manager_;
- LinkManager* link_manager_;
+ ClassicSignallingManager signalling_manager_;
std::unordered_map<Cid, PendingDynamicChannelConnection> local_cid_to_pending_dynamic_channel_connection_map_;
os::Alarm link_idle_disconnect_alarm_{l2cap_handler_};
- ClassicSignallingManager signalling_manager_;
- uint16_t acl_handle_;
Mtu remote_connectionless_mtu_ = kMinimumClassicMtu;
- hci::Role role_ = hci::Role::CENTRAL;
- bool remote_extended_feature_received_ = false;
bool remote_supports_ertm_ = false;
bool remote_supports_fcs_ = false;
hci::EncryptionEnabled encryption_enabled_ = hci::EncryptionEnabled::OFF;
- std::list<Psm> pending_dynamic_psm_list_;
- std::list<Link::PendingDynamicChannelConnection> pending_dynamic_channel_callback_list_;
- std::list<uint16_t> pending_outgoing_configuration_request_list_;
- bool used_by_security_module_ = false;
- bool has_requested_authentication_ = false;
- std::list<EncryptionChangeListener> encryption_change_listener_;
- std::atomic_int remaining_packets_to_be_sent_ = 0;
+ std::list<Link::PendingAuthenticateDynamicChannelConnection> pending_channel_list_;
DISALLOW_COPY_AND_ASSIGN(Link);
};
diff --git a/gd/l2cap/classic/internal/link_manager.cc b/gd/l2cap/classic/internal/link_manager.cc
index f8ff461d7..d71e35aad 100644
--- a/gd/l2cap/classic/internal/link_manager.cc
+++ b/gd/l2cap/classic/internal/link_manager.cc
@@ -16,9 +16,8 @@
#include <memory>
#include <unordered_map>
-#include "hci/acl_manager/classic_acl_connection.h"
+#include "hci/acl_manager.h"
#include "hci/address.h"
-#include "hci/class_of_device.h"
#include "l2cap/classic/internal/link.h"
#include "l2cap/internal/scheduler_fifo.h"
#include "os/log.h"
@@ -53,8 +52,11 @@ void LinkManager::ConnectFixedChannelServices(hci::Address device,
// This channel is already allocated for this link, do not allocated twice
continue;
}
+ if (fixed_channel_service.first == kClassicPairingTriggerCid) {
+ this->TriggerPairing(link);
+ }
// Allocate channel for newly registered fixed channels
- auto fixed_channel_impl = link->AllocateFixedChannel(fixed_channel_service.first);
+ auto fixed_channel_impl = link->AllocateFixedChannel(fixed_channel_service.first, SecurityPolicy());
fixed_channel_service.second->NotifyChannelCreation(
std::make_unique<FixedChannel>(fixed_channel_impl, l2cap_handler_));
num_new_channels++;
@@ -84,9 +86,6 @@ void LinkManager::ConnectFixedChannelServices(hci::Address device,
void LinkManager::ConnectDynamicChannelServices(
hci::Address device, Link::PendingDynamicChannelConnection pending_dynamic_channel_connection, Psm psm) {
- if (!IsPsmValid(psm)) {
- return;
- }
auto* link = GetLink(device);
if (link == nullptr) {
acl_manager_->CreateConnection(device);
@@ -99,40 +98,14 @@ void LinkManager::ConnectDynamicChannelServices(
}
return;
}
- link->SendConnectionRequest(psm, link->ReserveDynamicChannel(), std::move(pending_dynamic_channel_connection));
-}
-
-void LinkManager::InitiateConnectionForSecurity(hci::Address remote) {
- auto* link = GetLink(remote);
- if (link != nullptr) {
- LOG_ERROR("Link already exists for %s", remote.ToString().c_str());
- }
- acl_manager_->CreateConnection(remote);
-}
-
-void LinkManager::RegisterLinkSecurityInterfaceListener(os::Handler* handler, LinkSecurityInterfaceListener* listener) {
- link_security_interface_listener_handler_ = handler;
- link_security_interface_listener_ = listener;
-}
-
-LinkSecurityInterfaceListener* LinkManager::GetLinkSecurityInterfaceListener() {
- return link_security_interface_listener_;
-}
-
-void LinkManager::RegisterLinkPropertyListener(os::Handler* handler, LinkPropertyListener* listener) {
- link_property_callback_handler_ = handler;
- link_property_listener_ = listener;
-}
-
-void LinkManager::OnPendingPacketChange(hci::Address remote, int num_packets) {
- if (disconnected_links_.count(remote) != 0 && num_packets == 0) {
- links_.erase(remote);
- links_with_pending_packets_.erase(remote);
- } else if (num_packets != 0) {
- links_with_pending_packets_.emplace(remote);
- } else {
- links_with_pending_packets_.erase(remote);
+ if (dynamic_channel_service_manager_->GetService(psm)->GetSecurityPolicy().RequiresAuthentication() &&
+ !link->IsAuthenticated()) {
+ link->AddChannelPendingingAuthentication(
+ {psm, link->ReserveDynamicChannel(), std::move(pending_dynamic_channel_connection)});
+ link->Authenticate();
+ return;
}
+ link->SendConnectionRequest(psm, link->ReserveDynamicChannel(), std::move(pending_dynamic_channel_connection));
}
Link* LinkManager::GetLink(const hci::Address device) {
@@ -142,146 +115,58 @@ Link* LinkManager::GetLink(const hci::Address device) {
return &links_.find(device)->second;
}
-void LinkManager::handle_link_security_hold(hci::Address remote) {
- auto link = GetLink(remote);
- if (link == nullptr) {
- LOG_WARN("Remote is disconnected");
- return;
- }
- link->AcquireSecurityHold();
-}
-
-void LinkManager::handle_link_security_release(hci::Address remote) {
- auto link = GetLink(remote);
- if (link == nullptr) {
- LOG_WARN("Remote is disconnected");
- return;
+void LinkManager::TriggerPairing(Link* link) {
+ if (!link->IsAuthenticated()) {
+ link->Authenticate();
}
- link->ReleaseSecurityHold();
-}
-
-void LinkManager::handle_link_security_disconnect(hci::Address remote) {
- auto link = GetLink(remote);
- if (link == nullptr) {
- LOG_WARN("Remote is disconnected");
- return;
- }
- link->Disconnect();
-}
-
-void LinkManager::handle_link_security_ensure_authenticated(hci::Address remote) {
- auto link = GetLink(remote);
- if (link == nullptr) {
- LOG_WARN("Remote is disconnected");
- return;
- }
- link->Authenticate();
-}
-
-void LinkManager::handle_link_security_ensure_encrypted(hci::Address remote) {
- auto link = GetLink(remote);
- if (link == nullptr) {
- LOG_WARN("Remote is disconnected");
- return;
- }
- link->Encrypt();
+ link->ReadRemoteVersionInformation();
+ link->ReadRemoteSupportedFeatures();
+ link->ReadRemoteExtendedFeatures();
+ link->ReadClockOffset();
}
-/**
- * The implementation for LinkSecurityInterface, which allows the SecurityModule to access some link functionalities.
- * Note: All public methods implementing this interface are invoked from external context.
- */
-class LinkSecurityInterfaceImpl : public LinkSecurityInterface {
- public:
- LinkSecurityInterfaceImpl(os::Handler* handler, LinkManager* link_manager, Link* link)
- : handler_(handler),
- link_manager_(link_manager),
- remote_(link->GetDevice().GetAddress()),
- acl_handle_(link->GetAclHandle()) {}
-
- hci::Address GetRemoteAddress() override {
- return remote_;
- }
-
- void Hold() override {
- handler_->CallOn(link_manager_, &LinkManager::handle_link_security_hold, remote_);
- }
-
- void Release() override {
- handler_->CallOn(link_manager_, &LinkManager::handle_link_security_release, remote_);
- }
-
- void Disconnect() override {
- handler_->CallOn(link_manager_, &LinkManager::handle_link_security_disconnect, remote_);
- }
-
- void EnsureAuthenticated() override {
- handler_->CallOn(link_manager_, &LinkManager::handle_link_security_ensure_authenticated, remote_);
- }
-
- void EnsureEncrypted() override {
- handler_->CallOn(link_manager_, &LinkManager::handle_link_security_ensure_encrypted, remote_);
- }
-
- uint16_t GetAclHandle() override {
- return acl_handle_;
- }
-
- hci::Role GetRole() override {
- return link_manager_->GetLink(remote_)->GetRole();
- }
-
- os::Handler* handler_;
- LinkManager* link_manager_;
- hci::Address remote_;
- uint16_t acl_handle_;
-};
-
-void LinkManager::OnConnectSuccess(std::unique_ptr<hci::acl_manager::ClassicAclConnection> acl_connection) {
+void LinkManager::OnConnectSuccess(std::unique_ptr<hci::AclConnection> acl_connection) {
// Same link should not be connected twice
hci::Address device = acl_connection->GetAddress();
ASSERT_LOG(GetLink(device) == nullptr, "%s is connected twice without disconnection",
acl_connection->GetAddress().ToString().c_str());
+ // Register ACL disconnection callback in LinkManager so that we can clean up link resource properly
+ acl_connection->RegisterDisconnectCallback(
+ common::BindOnce(&LinkManager::OnDisconnect, common::Unretained(this), device), l2cap_handler_);
links_.try_emplace(device, l2cap_handler_, std::move(acl_connection), parameter_provider_,
- dynamic_channel_service_manager_, fixed_channel_service_manager_, this);
+ dynamic_channel_service_manager_, fixed_channel_service_manager_);
auto* link = GetLink(device);
ASSERT(link != nullptr);
link->SendInformationRequest(InformationRequestInfoType::EXTENDED_FEATURES_SUPPORTED);
link->SendInformationRequest(InformationRequestInfoType::FIXED_CHANNELS_SUPPORTED);
- link->ReadRemoteVersionInformation();
- link->ReadRemoteSupportedFeatures();
- link->ReadRemoteExtendedFeatures(1);
// Allocate and distribute channels for all registered fixed channel services
auto fixed_channel_services = fixed_channel_service_manager_->GetRegisteredServices();
for (auto& fixed_channel_service : fixed_channel_services) {
- auto fixed_channel_impl = link->AllocateFixedChannel(fixed_channel_service.first);
+ auto fixed_channel_impl = link->AllocateFixedChannel(fixed_channel_service.first, SecurityPolicy());
fixed_channel_service.second->NotifyChannelCreation(
std::make_unique<FixedChannel>(fixed_channel_impl, l2cap_handler_));
+ if (fixed_channel_service.first == kClassicPairingTriggerCid) {
+ this->TriggerPairing(link);
+ }
}
if (pending_dynamic_channels_.find(device) != pending_dynamic_channels_.end()) {
- auto psm_list = pending_dynamic_channels_[device];
- auto& callback_list = pending_dynamic_channels_callbacks_[device];
- link->SetPendingDynamicChannels(psm_list, std::move(callback_list));
+ for (Psm psm : pending_dynamic_channels_[device]) {
+ auto& callbacks = pending_dynamic_channels_callbacks_[device].front();
+ link->SendConnectionRequest(psm, link->ReserveDynamicChannel(), std::move(callbacks));
+ pending_dynamic_channels_callbacks_[device].pop_front();
+ }
pending_dynamic_channels_.erase(device);
pending_dynamic_channels_callbacks_.erase(device);
}
- // Notify link property listener
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(
- link_property_listener_, &LinkPropertyListener::OnLinkConnected, device, link->GetAclHandle());
- }
-
- // Notify security manager
- if (link_security_interface_listener_handler_ != nullptr) {
- link_security_interface_listener_handler_->CallOn(
- link_security_interface_listener_,
- &LinkSecurityInterfaceListener::OnLinkConnected,
- std::make_unique<LinkSecurityInterfaceImpl>(l2cap_handler_, this, link));
- }
-
// Remove device from pending links list, if any
- pending_links_.erase(device);
+ auto pending_link = pending_links_.find(device);
+ if (pending_link == pending_links_.end()) {
+ // This an incoming connection, exit
+ return;
+ }
+ // This is an outgoing connection, remove entry in pending link list
+ pending_links_.erase(pending_link);
}
void LinkManager::OnConnectFail(hci::Address device, hci::ErrorCode reason) {
@@ -289,15 +174,14 @@ void LinkManager::OnConnectFail(hci::Address device, hci::ErrorCode reason) {
auto pending_link = pending_links_.find(device);
if (pending_link == pending_links_.end()) {
// There is no pending link, exit
- LOG_INFO(
- "Connection to %s failed without a pending link; reason: %s",
- device.ToString().c_str(),
- hci::ErrorCodeText(reason).c_str());
+ LOG_DEBUG("Connection to %s failed without a pending link; reason: %s", device.ToString().c_str(),
+ hci::ErrorCodeText(reason).c_str());
if (pending_dynamic_channels_callbacks_.find(device) != pending_dynamic_channels_callbacks_.end()) {
for (Link::PendingDynamicChannelConnection& callbacks : pending_dynamic_channels_callbacks_[device]) {
- callbacks.on_fail_callback_.Invoke(DynamicChannelManager::ConnectionResult{
- .hci_error = hci::ErrorCode::CONNECTION_TIMEOUT,
- });
+ callbacks.handler_->Post(common::BindOnce(std::move(callbacks.on_fail_callback_),
+ DynamicChannelManager::ConnectionResult{
+ .hci_error = hci::ErrorCode::CONNECTION_TIMEOUT,
+ }));
}
pending_dynamic_channels_.erase(device);
pending_dynamic_channels_callbacks_.erase(device);
@@ -314,130 +198,12 @@ void LinkManager::OnConnectFail(hci::Address device, hci::ErrorCode reason) {
pending_links_.erase(pending_link);
}
-void LinkManager::HACK_OnEscoConnectRequest(hci::Address device, hci::ClassOfDevice cod) {
- LOG_ERROR("Remote ESCO connect request unimplemented");
-}
-
-void LinkManager::HACK_OnScoConnectRequest(hci::Address device, hci::ClassOfDevice cod) {
- LOG_ERROR("Remote SCO connect request unimplemented");
-}
-
void LinkManager::OnDisconnect(hci::Address device, hci::ErrorCode status) {
auto* link = GetLink(device);
ASSERT_LOG(link != nullptr, "Device %s is disconnected with reason 0x%x, but not in local database",
device.ToString().c_str(), static_cast<uint8_t>(status));
- if (link_security_interface_listener_handler_ != nullptr) {
- link_security_interface_listener_handler_->CallOn(
- link_security_interface_listener_, &LinkSecurityInterfaceListener::OnLinkDisconnected, device);
- }
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(link_property_listener_, &LinkPropertyListener::OnLinkDisconnected, device);
- }
-
- if (links_with_pending_packets_.count(device) != 0) {
- disconnected_links_.emplace(device);
- } else {
- links_.erase(device);
- }
-}
-
-void LinkManager::OnAuthenticationComplete(hci::ErrorCode hci_status, hci::Address device) {
- if (link_security_interface_listener_handler_ != nullptr) {
- link_security_interface_listener_handler_->CallOn(
- link_security_interface_listener_,
- &LinkSecurityInterfaceListener::OnAuthenticationComplete,
- hci_status,
- device);
- }
-}
-
-void LinkManager::OnEncryptionChange(hci::Address device, hci::EncryptionEnabled enabled) {
- if (link_security_interface_listener_handler_ != nullptr) {
- link_security_interface_listener_handler_->CallOn(
- link_security_interface_listener_,
- &LinkSecurityInterfaceListener::OnEncryptionChange,
- device,
- enabled == hci::EncryptionEnabled::ON || enabled == hci::EncryptionEnabled::BR_EDR_AES_CCM);
- }
-}
-
-void LinkManager::OnReadRemoteVersionInformation(
- hci::ErrorCode hci_status,
- hci::Address device,
- uint8_t lmp_version,
- uint16_t manufacturer_name,
- uint16_t sub_version) {
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(
- link_property_listener_,
- &LinkPropertyListener::OnReadRemoteVersionInformation,
- hci_status,
- device,
- lmp_version,
- manufacturer_name,
- sub_version);
- }
-}
-
-void LinkManager::OnReadRemoteSupportedFeatures(hci::Address device, uint64_t features) {
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(
- link_property_listener_, &LinkPropertyListener::OnReadRemoteSupportedFeatures, device, features);
- }
-}
-
-void LinkManager::OnReadRemoteExtendedFeatures(
- hci::Address device, uint8_t page_number, uint8_t max_page_number, uint64_t features) {
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(
- link_property_listener_,
- &LinkPropertyListener::OnReadRemoteExtendedFeatures,
- device,
- page_number,
- max_page_number,
- features);
- }
-}
-
-void LinkManager::OnRoleChange(hci::ErrorCode hci_status, hci::Address remote, hci::Role role) {
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(
- link_property_listener_, &LinkPropertyListener::OnRoleChange, hci_status, remote, role);
- }
-}
-
-void LinkManager::OnReadClockOffset(hci::Address remote, uint16_t clock_offset) {
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(
- link_property_listener_, &LinkPropertyListener::OnReadClockOffset, remote, clock_offset);
- }
-}
-
-void LinkManager::OnModeChange(hci::ErrorCode hci_status, hci::Address remote, hci::Mode mode, uint16_t interval) {
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(
- link_property_listener_, &LinkPropertyListener::OnModeChange, hci_status, remote, mode, interval);
- }
-}
-
-void LinkManager::OnSniffSubrating(
- hci::ErrorCode hci_status,
- hci::Address remote,
- uint16_t max_tx_lat,
- uint16_t max_rx_lat,
- uint16_t min_remote_timeout,
- uint16_t min_local_timeout) {
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(
- link_property_listener_,
- &LinkPropertyListener::OnSniffSubrating,
- hci_status,
- remote,
- max_tx_lat,
- max_rx_lat,
- min_remote_timeout,
- min_local_timeout);
- }
+ link->OnAclDisconnected(status);
+ links_.erase(device);
}
} // namespace internal
diff --git a/gd/l2cap/classic/internal/link_manager.h b/gd/l2cap/classic/internal/link_manager.h
index a81b0f5aa..661533b2e 100644
--- a/gd/l2cap/classic/internal/link_manager.h
+++ b/gd/l2cap/classic/internal/link_manager.h
@@ -19,16 +19,13 @@
#include <memory>
#include <unordered_map>
-#include "hci/acl_manager/classic_acl_connection.h"
+#include "hci/acl_manager.h"
#include "hci/address.h"
-#include "hci/class_of_device.h"
#include "l2cap/classic/dynamic_channel_manager.h"
#include "l2cap/classic/fixed_channel_manager.h"
#include "l2cap/classic/internal/dynamic_channel_service_manager_impl.h"
#include "l2cap/classic/internal/fixed_channel_service_manager_impl.h"
#include "l2cap/classic/internal/link.h"
-#include "l2cap/classic/link_property_listener.h"
-#include "l2cap/classic/link_security_interface.h"
#include "l2cap/internal/parameter_provider.h"
#include "l2cap/internal/scheduler.h"
#include "os/handler.h"
@@ -38,9 +35,7 @@ namespace l2cap {
namespace classic {
namespace internal {
-class DumpsysHelper;
-
-class LinkManager : public hci::acl_manager::ConnectionCallbacks {
+class LinkManager : public hci::ConnectionCallbacks {
public:
LinkManager(os::Handler* l2cap_handler, hci::AclManager* acl_manager,
FixedChannelServiceManagerImpl* fixed_channel_service_manager,
@@ -64,34 +59,9 @@ class LinkManager : public hci::acl_manager::ConnectionCallbacks {
// ACL methods
Link* GetLink(hci::Address device);
- void OnConnectSuccess(std::unique_ptr<hci::acl_manager::ClassicAclConnection> acl_connection) override;
+ void OnConnectSuccess(std::unique_ptr<hci::AclConnection> acl_connection) override;
void OnConnectFail(hci::Address device, hci::ErrorCode reason) override;
-
- void HACK_OnEscoConnectRequest(hci::Address, hci::ClassOfDevice) override;
- void HACK_OnScoConnectRequest(hci::Address, hci::ClassOfDevice) override;
-
- virtual void OnDisconnect(hci::Address device, hci::ErrorCode status);
- void OnAuthenticationComplete(hci::ErrorCode hci_status, hci::Address device);
- void OnEncryptionChange(hci::Address device, hci::EncryptionEnabled enabled);
- void OnReadRemoteVersionInformation(
- hci::ErrorCode hci_status,
- hci::Address device,
- uint8_t lmp_version,
- uint16_t manufacturer_name,
- uint16_t sub_version);
- void OnReadRemoteSupportedFeatures(hci::Address device, uint64_t features);
- void OnReadRemoteExtendedFeatures(
- hci::Address device, uint8_t page_number, uint8_t max_page_number, uint64_t features);
- void OnRoleChange(hci::ErrorCode hci_status, hci::Address remote, hci::Role role);
- void OnReadClockOffset(hci::Address remote, uint16_t clock_offset);
- void OnModeChange(hci::ErrorCode hci_status, hci::Address remote, hci::Mode mode, uint16_t interval);
- void OnSniffSubrating(
- hci::ErrorCode hci_status,
- hci::Address remote,
- uint16_t max_tx_lat,
- uint16_t max_rx_lat,
- uint16_t min_remote_timeout,
- uint16_t min_local_timeout);
+ void OnDisconnect(hci::Address device, hci::ErrorCode status);
// FixedChannelManager methods
@@ -99,34 +69,11 @@ class LinkManager : public hci::acl_manager::ConnectionCallbacks {
// DynamicChannelManager methods
- void ConnectDynamicChannelServices(
- hci::Address device, Link::PendingDynamicChannelConnection pending_connection, Psm psm);
-
- // For SecurityModule to initiate an ACL link
- void InitiateConnectionForSecurity(hci::Address remote);
-
- // LinkManager will handle sending OnLinkConnected() callback and construct a LinkSecurityInterface proxy.
- void RegisterLinkSecurityInterfaceListener(os::Handler* handler, LinkSecurityInterfaceListener* listener);
-
- // For the link to get LinkSecurityInterfaceListener
- LinkSecurityInterfaceListener* GetLinkSecurityInterfaceListener();
-
- // Registerlink callbacks
- void RegisterLinkPropertyListener(os::Handler* handler, LinkPropertyListener* listener);
-
- // Reported by link to indicate how many pending packets are remaining to be set.
- // If there is anything outstanding, don't delete link
- void OnPendingPacketChange(hci::Address remote, int num_packets);
+ void ConnectDynamicChannelServices(hci::Address device,
+ Link::PendingDynamicChannelConnection pending_dynamic_channel_connection, Psm psm);
private:
- // Handles requests from LinkSecurityInterface
- friend class LinkSecurityInterfaceImpl;
- friend class DumpsysHelper;
- void handle_link_security_hold(hci::Address remote);
- void handle_link_security_release(hci::Address remote);
- void handle_link_security_disconnect(hci::Address remote);
- void handle_link_security_ensure_authenticated(hci::Address remote);
- void handle_link_security_ensure_encrypted(hci::Address remote);
+ void TriggerPairing(Link* link);
// Dependencies
os::Handler* l2cap_handler_;
@@ -141,13 +88,6 @@ class LinkManager : public hci::acl_manager::ConnectionCallbacks {
std::unordered_map<hci::Address, std::list<Psm>> pending_dynamic_channels_;
std::unordered_map<hci::Address, std::list<Link::PendingDynamicChannelConnection>>
pending_dynamic_channels_callbacks_;
- os::Handler* link_security_interface_listener_handler_ = nullptr;
- LinkSecurityInterfaceListener* link_security_interface_listener_ = nullptr;
- LinkPropertyListener* link_property_listener_ = nullptr;
- os::Handler* link_property_callback_handler_ = nullptr;
- std::unordered_set<hci::Address> disconnected_links_;
- std::unordered_set<hci::Address> links_with_pending_packets_;
-
DISALLOW_COPY_AND_ASSIGN(LinkManager);
};
diff --git a/gd/l2cap/classic/internal/link_manager_test.cc b/gd/l2cap/classic/internal/link_manager_test.cc
index d59e0dd9b..c385756e9 100644
--- a/gd/l2cap/classic/internal/link_manager_test.cc
+++ b/gd/l2cap/classic/internal/link_manager_test.cc
@@ -26,7 +26,6 @@
#include "hci/address.h"
#include "l2cap/cid.h"
#include "l2cap/classic/fixed_channel_manager.h"
-#include "l2cap/classic/internal/dynamic_channel_service_impl_mock.h"
#include "l2cap/classic/internal/fixed_channel_service_impl_mock.h"
#include "l2cap/classic/internal/fixed_channel_service_manager_impl_mock.h"
#include "l2cap/internal/parameter_provider_mock.h"
@@ -42,13 +41,12 @@ namespace classic {
namespace internal {
namespace {
+using hci::testing::MockAclConnection;
using hci::testing::MockAclManager;
-using hci::testing::MockClassicAclConnection;
using l2cap::internal::testing::MockParameterProvider;
using ::testing::_; // Matcher to any value
using ::testing::ByMove;
using ::testing::DoAll;
-using testing::MockDynamicChannelServiceImpl;
using testing::MockDynamicChannelServiceManagerImpl;
using testing::MockFixedChannelServiceImpl;
using testing::MockFixedChannelServiceManagerImpl;
@@ -91,23 +89,15 @@ class L2capClassicLinkManagerTest : public ::testing::Test {
TEST_F(L2capClassicLinkManagerTest, connect_fixed_channel_service_without_acl) {
MockFixedChannelServiceManagerImpl mock_classic_fixed_channel_service_manager;
MockDynamicChannelServiceManagerImpl mock_classic_dynamic_channel_service_manager;
- SecurityEnforcementRejectAllImpl security_module_impl;
- MockDynamicChannelServiceImpl service;
- ON_CALL(service, GetSecurityPolicy())
- .WillByDefault(Return(SecurityPolicy::_SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK));
-
- ON_CALL(mock_classic_dynamic_channel_service_manager, GetSecurityEnforcementInterface())
- .WillByDefault(Return(&security_module_impl));
MockAclManager mock_acl_manager;
hci::Address device{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
auto user_handler = std::make_unique<os::Handler>(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::ConnectionCallbacks* hci_connection_callbacks = nullptr;
+ hci::ConnectionCallbacks* hci_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
- ON_CALL(mock_classic_dynamic_channel_service_manager, GetService(_)).WillByDefault(Return(&service));
LinkManager classic_link_manager(l2cap_handler_, &mock_acl_manager, &mock_classic_fixed_channel_service_manager,
&mock_classic_dynamic_channel_service_manager, mock_parameter_provider_);
EXPECT_EQ(hci_connection_callbacks, &classic_link_manager);
@@ -129,9 +119,12 @@ TEST_F(L2capClassicLinkManagerTest, connect_fixed_channel_service_without_acl) {
// Step 3: ACL connection success event should trigger channel creation for all registered services
- std::unique_ptr<MockClassicAclConnection> acl_connection = std::make_unique<MockClassicAclConnection>();
+ std::unique_ptr<MockAclConnection> acl_connection = std::make_unique<MockAclConnection>();
EXPECT_CALL(*acl_connection, GetAddress()).WillRepeatedly(Return(device));
+ EXPECT_CALL(*acl_connection, GetAddressType()).WillRepeatedly(Return(hci::AddressType::PUBLIC_DEVICE_ADDRESS));
EXPECT_CALL(*acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*acl_connection, RegisterDisconnectCallback(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*acl_connection, UnregisterCallbacks(_)).Times(1);
std::unique_ptr<FixedChannel> channel_1, channel_2;
std::promise<void> promise_1, promise_2;
auto future_1 = promise_1.get_future();
@@ -146,7 +139,7 @@ TEST_F(L2capClassicLinkManagerTest, connect_fixed_channel_service_without_acl) {
channel_2 = std::move(channel);
promise_2.set_value();
});
- hci_callback_handler->Post(common::BindOnce(&hci::acl_manager::ConnectionCallbacks::OnConnectSuccess,
+ hci_callback_handler->Post(common::BindOnce(&hci::ConnectionCallbacks::OnConnectSuccess,
common::Unretained(hci_connection_callbacks), std::move(acl_connection)));
SyncHandler(hci_callback_handler);
auto future_1_status = future_1.wait_for(kTestIdleDisconnectTimeoutShort);
@@ -193,7 +186,7 @@ TEST_F(L2capClassicLinkManagerTest, connect_fixed_channel_service_without_acl_wi
auto user_handler = std::make_unique<os::Handler>(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::ConnectionCallbacks* hci_connection_callbacks = nullptr;
+ hci::ConnectionCallbacks* hci_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
@@ -227,7 +220,7 @@ TEST_F(L2capClassicLinkManagerTest, connect_fixed_channel_service_without_acl_wi
auto user_handler = std::make_unique<os::Handler>(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::ConnectionCallbacks* hci_connection_callbacks = nullptr;
+ hci::ConnectionCallbacks* hci_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
@@ -253,7 +246,7 @@ TEST_F(L2capClassicLinkManagerTest, connect_fixed_channel_service_without_acl_wi
// Step 3: ACL connection failure event should trigger connection failure callback
EXPECT_CALL(mock_service_1, NotifyChannelCreation(_)).Times(0);
- hci_callback_handler->Post(common::BindOnce(&hci::acl_manager::ConnectionCallbacks::OnConnectFail,
+ hci_callback_handler->Post(common::BindOnce(&hci::ConnectionCallbacks::OnConnectFail,
common::Unretained(hci_connection_callbacks), device,
hci::ErrorCode::PAGE_TIMEOUT));
SyncHandler(hci_callback_handler);
@@ -273,7 +266,7 @@ TEST_F(L2capClassicLinkManagerTest, not_acquiring_channels_should_disconnect_acl
auto user_handler = std::make_unique<os::Handler>(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::ConnectionCallbacks* hci_connection_callbacks = nullptr;
+ hci::ConnectionCallbacks* hci_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
@@ -297,10 +290,13 @@ TEST_F(L2capClassicLinkManagerTest, not_acquiring_channels_should_disconnect_acl
classic_link_manager.ConnectFixedChannelServices(device, std::move(pending_fixed_channel_connection));
// Step 3: ACL connection success event should trigger channel creation for all registered services
- auto* raw_acl_connection = new MockClassicAclConnection();
- std::unique_ptr<MockClassicAclConnection> acl_connection(raw_acl_connection);
+ auto* raw_acl_connection = new MockAclConnection();
+ std::unique_ptr<MockAclConnection> acl_connection(raw_acl_connection);
EXPECT_CALL(*acl_connection, GetAddress()).WillRepeatedly(Return(device));
+ EXPECT_CALL(*acl_connection, GetAddressType()).WillRepeatedly(Return(hci::AddressType::PUBLIC_DEVICE_ADDRESS));
EXPECT_CALL(*acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*acl_connection, RegisterDisconnectCallback(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*acl_connection, UnregisterCallbacks(_)).Times(1);
std::unique_ptr<FixedChannel> channel_1, channel_2;
std::promise<void> promise_1, promise_2;
auto future_1 = promise_1.get_future();
@@ -315,7 +311,7 @@ TEST_F(L2capClassicLinkManagerTest, not_acquiring_channels_should_disconnect_acl
channel_2 = std::move(channel);
promise_2.set_value();
});
- hci_callback_handler->Post(common::BindOnce(&hci::acl_manager::ConnectionCallbacks::OnConnectSuccess,
+ hci_callback_handler->Post(common::BindOnce(&hci::ConnectionCallbacks::OnConnectSuccess,
common::Unretained(hci_connection_callbacks), std::move(acl_connection)));
SyncHandler(hci_callback_handler);
auto future_1_status = future_1.wait_for(kTestIdleDisconnectTimeoutShort);
@@ -335,6 +331,12 @@ TEST_F(L2capClassicLinkManagerTest, not_acquiring_channels_should_disconnect_acl
EXPECT_CALL(*raw_acl_connection, Disconnect(hci::DisconnectReason::REMOTE_USER_TERMINATED_CONNECTION)).Times(1);
std::this_thread::sleep_for(kTestIdleDisconnectTimeoutShort * 1.2);
+ // Step 5: Link disconnect will trigger all callbacks
+ classic_link_manager.OnDisconnect(device, hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST);
+ SyncHandler(user_handler.get());
+ EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_1);
+ EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_2);
+
user_handler->Clear();
}
@@ -347,7 +349,7 @@ TEST_F(L2capClassicLinkManagerTest, acquiring_channels_should_not_disconnect_acl
auto user_handler = std::make_unique<os::Handler>(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::ConnectionCallbacks* hci_connection_callbacks = nullptr;
+ hci::ConnectionCallbacks* hci_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
@@ -371,10 +373,13 @@ TEST_F(L2capClassicLinkManagerTest, acquiring_channels_should_not_disconnect_acl
classic_link_manager.ConnectFixedChannelServices(device, std::move(pending_fixed_channel_connection));
// Step 3: ACL connection success event should trigger channel creation for all registered services
- auto* raw_acl_connection = new MockClassicAclConnection();
- std::unique_ptr<MockClassicAclConnection> acl_connection(raw_acl_connection);
+ auto* raw_acl_connection = new MockAclConnection();
+ std::unique_ptr<MockAclConnection> acl_connection(raw_acl_connection);
EXPECT_CALL(*acl_connection, GetAddress()).WillRepeatedly(Return(device));
+ EXPECT_CALL(*acl_connection, GetAddressType()).WillRepeatedly(Return(hci::AddressType::PUBLIC_DEVICE_ADDRESS));
EXPECT_CALL(*acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*acl_connection, RegisterDisconnectCallback(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*acl_connection, UnregisterCallbacks(_)).Times(1);
std::unique_ptr<FixedChannel> channel_1, channel_2;
std::promise<void> promise_1, promise_2;
auto future_1 = promise_1.get_future();
@@ -389,7 +394,7 @@ TEST_F(L2capClassicLinkManagerTest, acquiring_channels_should_not_disconnect_acl
channel_2 = std::move(channel);
promise_2.set_value();
});
- hci_callback_handler->Post(common::BindOnce(&hci::acl_manager::ConnectionCallbacks::OnConnectSuccess,
+ hci_callback_handler->Post(common::BindOnce(&hci::ConnectionCallbacks::OnConnectSuccess,
common::Unretained(hci_connection_callbacks), std::move(acl_connection)));
SyncHandler(hci_callback_handler);
auto future_1_status = future_1.wait_for(kTestIdleDisconnectTimeoutShort);
@@ -411,6 +416,12 @@ TEST_F(L2capClassicLinkManagerTest, acquiring_channels_should_not_disconnect_acl
EXPECT_CALL(*raw_acl_connection, Disconnect(hci::DisconnectReason::REMOTE_USER_TERMINATED_CONNECTION)).Times(0);
std::this_thread::sleep_for(kTestIdleDisconnectTimeoutShort * 2);
+ // Step 5: Link disconnect will trigger all callbacks
+ classic_link_manager.OnDisconnect(device, hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST);
+ SyncHandler(user_handler.get());
+ EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_1);
+ EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_2);
+
user_handler->Clear();
}
@@ -423,7 +434,7 @@ TEST_F(L2capClassicLinkManagerTest, acquiring_and_releasing_channels_should_even
auto user_handler = std::make_unique<os::Handler>(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::ConnectionCallbacks* hci_connection_callbacks = nullptr;
+ hci::ConnectionCallbacks* hci_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
@@ -447,10 +458,13 @@ TEST_F(L2capClassicLinkManagerTest, acquiring_and_releasing_channels_should_even
classic_link_manager.ConnectFixedChannelServices(device, std::move(pending_fixed_channel_connection));
// Step 3: ACL connection success event should trigger channel creation for all registered services
- auto* raw_acl_connection = new MockClassicAclConnection();
- std::unique_ptr<MockClassicAclConnection> acl_connection(raw_acl_connection);
+ auto* raw_acl_connection = new MockAclConnection();
+ std::unique_ptr<MockAclConnection> acl_connection(raw_acl_connection);
EXPECT_CALL(*acl_connection, GetAddress()).WillRepeatedly(Return(device));
+ EXPECT_CALL(*acl_connection, GetAddressType()).WillRepeatedly(Return(hci::AddressType::PUBLIC_DEVICE_ADDRESS));
EXPECT_CALL(*acl_connection, RegisterCallbacks(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*acl_connection, RegisterDisconnectCallback(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*acl_connection, UnregisterCallbacks(_)).Times(1);
std::unique_ptr<FixedChannel> channel_1, channel_2;
std::promise<void> promise_1, promise_2;
auto future_1 = promise_1.get_future();
@@ -465,7 +479,7 @@ TEST_F(L2capClassicLinkManagerTest, acquiring_and_releasing_channels_should_even
channel_2 = std::move(channel);
promise_2.set_value();
});
- hci_callback_handler->Post(common::BindOnce(&hci::acl_manager::ConnectionCallbacks::OnConnectSuccess,
+ hci_callback_handler->Post(common::BindOnce(&hci::ConnectionCallbacks::OnConnectSuccess,
common::Unretained(hci_connection_callbacks), std::move(acl_connection)));
SyncHandler(hci_callback_handler);
auto future_1_status = future_1.wait_for(kTestIdleDisconnectTimeoutShort);
@@ -492,6 +506,12 @@ TEST_F(L2capClassicLinkManagerTest, acquiring_and_releasing_channels_should_even
EXPECT_CALL(*raw_acl_connection, Disconnect(hci::DisconnectReason::REMOTE_USER_TERMINATED_CONNECTION)).Times(1);
std::this_thread::sleep_for(kTestIdleDisconnectTimeoutShort * 1.2);
+ // Step 6: Link disconnect will trigger all callbacks
+ classic_link_manager.OnDisconnect(device, hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST);
+ SyncHandler(user_handler.get());
+ EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_1);
+ EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_2);
+
user_handler->Clear();
}
diff --git a/gd/l2cap/classic/internal/link_mock.h b/gd/l2cap/classic/internal/link_mock.h
index 05202ee81..4eb336eef 100644
--- a/gd/l2cap/classic/internal/link_mock.h
+++ b/gd/l2cap/classic/internal/link_mock.h
@@ -29,21 +29,20 @@ namespace classic {
namespace internal {
namespace testing {
-using hci::testing::MockClassicAclConnection;
+using hci::testing::MockAclConnection;
class MockLink : public Link {
public:
explicit MockLink(os::Handler* handler, l2cap::internal::ParameterProvider* parameter_provider)
- : Link(handler, std::make_unique<MockClassicAclConnection>(), parameter_provider, nullptr, nullptr, nullptr){};
+ : Link(handler, std::make_unique<MockAclConnection>(), parameter_provider, nullptr, nullptr){};
explicit MockLink(os::Handler* handler, l2cap::internal::ParameterProvider* parameter_provider,
- std::unique_ptr<hci::acl_manager::ClassicAclConnection> acl_connection, LinkManager* link_manager)
- : Link(handler, std::move(acl_connection), parameter_provider, nullptr, nullptr, nullptr){};
- MOCK_METHOD(hci::AddressWithType, GetDevice, (), (const, override));
+ std::unique_ptr<hci::AclConnection> acl_connection)
+ : Link(handler, std::move(acl_connection), parameter_provider, nullptr, nullptr){};
+ MOCK_METHOD(hci::AddressWithType, GetDevice, (), (override));
MOCK_METHOD(void, OnAclDisconnected, (hci::ErrorCode status), (override));
MOCK_METHOD(void, Disconnect, (), (override));
- MOCK_METHOD(std::shared_ptr<l2cap::internal::DynamicChannelImpl>, AllocateDynamicChannel, (Psm psm, Cid cid),
- (override));
-
+ MOCK_METHOD(std::shared_ptr<l2cap::internal::DynamicChannelImpl>, AllocateDynamicChannel,
+ (Psm psm, Cid cid, SecurityPolicy security_policy), (override));
MOCK_METHOD(bool, IsFixedChannelAllocated, (Cid cid), (override));
MOCK_METHOD(void, RefreshRefCount, (), (override));
};
@@ -52,4 +51,4 @@ class MockLink : public Link {
} // namespace internal
} // namespace classic
} // namespace l2cap
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/gd/l2cap/classic/internal/link_test.cc b/gd/l2cap/classic/internal/link_test.cc
index 89d6dc75d..67064f316 100644
--- a/gd/l2cap/classic/internal/link_test.cc
+++ b/gd/l2cap/classic/internal/link_test.cc
@@ -18,7 +18,6 @@
#include "hci/acl_manager_mock.h"
#include "hci/address.h"
-#include "l2cap/classic/internal/dynamic_channel_service_impl_mock.h"
#include "l2cap/classic/internal/dynamic_channel_service_manager_impl_mock.h"
#include "l2cap/classic/internal/fixed_channel_service_manager_impl_mock.h"
#include "l2cap/internal/parameter_provider_mock.h"
@@ -38,9 +37,8 @@ namespace {
constexpr Psm kPsm = 123;
constexpr Cid kCid = 456;
-using classic::internal::testing::MockDynamicChannelServiceImpl;
using classic::internal::testing::MockDynamicChannelServiceManagerImpl;
-using hci::testing::MockClassicAclConnection;
+using hci::testing::MockAclConnection;
using l2cap::internal::testing::MockParameterProvider;
using testing::MockFixedChannelServiceManagerImpl;
@@ -76,10 +74,10 @@ class L2capClassicLinkTest : public ::testing::Test {
handler_ = new os::Handler(thread_);
signalling_handler_ = new os::Handler(thread_);
- raw_acl_connection_ = new NiceMock<MockClassicAclConnection>();
- link_ = new Link(signalling_handler_, std::unique_ptr<MockClassicAclConnection>(raw_acl_connection_),
+ raw_acl_connection_ = new NiceMock<MockAclConnection>();
+ link_ = new Link(signalling_handler_, std::unique_ptr<MockAclConnection>(raw_acl_connection_),
&mock_parameter_provider_, &mock_classic_dynamic_channel_service_manager_,
- &mock_classic_fixed_channel_service_manager_, nullptr);
+ &mock_classic_fixed_channel_service_manager_);
}
void TearDown() override {
@@ -98,13 +96,12 @@ class L2capClassicLinkTest : public ::testing::Test {
os::Handler* handler_ = nullptr;
os::Handler* signalling_handler_ = nullptr;
- MockClassicAclConnection* raw_acl_connection_ = nullptr;
- std::unique_ptr<MockClassicAclConnection> acl_connection_;
+ MockAclConnection* raw_acl_connection_ = nullptr;
+ std::unique_ptr<MockAclConnection> acl_connection_;
NiceMock<MockParameterProvider> mock_parameter_provider_;
MockFixedChannelServiceManagerImpl mock_classic_fixed_channel_service_manager_;
MockDynamicChannelServiceManagerImpl mock_classic_dynamic_channel_service_manager_;
- SecurityEnforcementRejectAllImpl security_module_impl_;
std::promise<void> on_open_promise_;
std::promise<void> on_fail_promise_;
@@ -117,21 +114,13 @@ TEST_F(L2capClassicLinkTest, pending_channels_get_notified_on_acl_disconnect) {
EnqueueCallbackForTest();
Link::PendingDynamicChannelConnection pending_dynamic_channel_connection{
- .on_open_callback_ = handler_->BindOn(this, &L2capClassicLinkTest::OnOpen),
- .on_fail_callback_ = handler_->BindOnceOn(this, &L2capClassicLinkTest::OnFail),
+ .handler_ = handler_,
+ .on_open_callback_ = common::Bind(&L2capClassicLinkTest::OnOpen, common::Unretained(this)),
+ .on_fail_callback_ = common::Bind(&L2capClassicLinkTest::OnFail, common::Unretained(this)),
.configuration_ = DynamicChannelConfigurationOption(),
};
auto future = on_fail_promise_.get_future();
- MockDynamicChannelServiceImpl service;
- ON_CALL(service, GetSecurityPolicy())
- .WillByDefault(::testing::Return(SecurityPolicy::_SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK));
-
- EXPECT_CALL(mock_classic_dynamic_channel_service_manager_, GetSecurityEnforcementInterface())
- .WillOnce(::testing::Return(&security_module_impl_));
- EXPECT_CALL(mock_classic_dynamic_channel_service_manager_, GetService(::testing::_))
- .WillRepeatedly(::testing::Return(&service));
-
link_->SendConnectionRequest(kPsm, kCid, std::move(pending_dynamic_channel_connection));
link_->OnAclDisconnected(hci::ErrorCode::UNKNOWN_HCI_COMMAND);
future.wait();
diff --git a/gd/l2cap/classic/internal/signalling_manager.cc b/gd/l2cap/classic/internal/signalling_manager.cc
index 3187975a8..30553ca0d 100644
--- a/gd/l2cap/classic/internal/signalling_manager.cc
+++ b/gd/l2cap/classic/internal/signalling_manager.cc
@@ -32,22 +32,6 @@ namespace classic {
namespace internal {
static constexpr auto kTimeout = std::chrono::seconds(3);
-static std::vector<ControlView> GetCommandsFromPacketView(PacketView<kLittleEndian> packet) {
- size_t curr = 0;
- size_t end = packet.size();
- std::vector<ControlView> result;
- while (curr < end) {
- auto sub_view = packet.GetLittleEndianSubview(curr, end);
- auto control = ControlView::Create(sub_view);
- if (!control.IsValid()) {
- return {};
- }
- result.push_back(control);
- curr += 1 + 1 + 2 + control.GetPayload().size();
- }
- return result;
-}
-
ClassicSignallingManager::ClassicSignallingManager(os::Handler* handler, Link* link,
l2cap::internal::DataPipelineManager* data_pipeline_manager,
DynamicChannelServiceManagerImpl* dynamic_service_manager,
@@ -58,7 +42,7 @@ ClassicSignallingManager::ClassicSignallingManager(os::Handler* handler, Link* l
fixed_service_manager_(fixed_service_manager), alarm_(handler) {
ASSERT(handler_ != nullptr);
ASSERT(link_ != nullptr);
- signalling_channel_ = link_->AllocateFixedChannel(kClassicSignallingCid);
+ signalling_channel_ = link_->AllocateFixedChannel(kClassicSignallingCid, {});
signalling_channel_->GetQueueUpEnd()->RegisterDequeue(
handler_, common::Bind(&ClassicSignallingManager::on_incoming_packet, common::Unretained(this)));
enqueue_buffer_ =
@@ -66,22 +50,17 @@ ClassicSignallingManager::ClassicSignallingManager(os::Handler* handler, Link* l
}
ClassicSignallingManager::~ClassicSignallingManager() {
- alarm_.Cancel();
+ enqueue_buffer_.reset();
signalling_channel_->GetQueueUpEnd()->UnregisterDequeue();
signalling_channel_ = nullptr;
- enqueue_buffer_->Clear();
- enqueue_buffer_.reset();
}
void ClassicSignallingManager::OnCommandReject(CommandRejectView command_reject_view) {
- if (command_just_sent_.signal_id_ != command_reject_view.GetIdentifier()) {
+ if (command_just_sent_.signal_id_ != command_reject_view.GetIdentifier() ||
+ command_just_sent_.command_code_ != command_reject_view.GetCode()) {
LOG_WARN("Unexpected command reject: no pending request");
return;
}
- if (command_just_sent_.command_code_ == CommandCode::INFORMATION_REQUEST &&
- command_just_sent_.info_type_ == InformationRequestInfoType::EXTENDED_FEATURES_SUPPORTED) {
- link_->OnRemoteExtendedFeatureReceived(false, false);
- }
alarm_.Cancel();
handle_send_next_command();
@@ -89,40 +68,6 @@ void ClassicSignallingManager::OnCommandReject(CommandRejectView command_reject_
}
void ClassicSignallingManager::SendConnectionRequest(Psm psm, Cid local_cid) {
- dynamic_service_manager_->GetSecurityEnforcementInterface()->Enforce(
- link_->GetDevice(),
- dynamic_service_manager_->GetService(psm)->GetSecurityPolicy(),
- handler_->BindOnceOn(
- this,
- &ClassicSignallingManager::on_security_result_for_outgoing,
- SecurityEnforcementType::LINK_KEY,
- psm,
- local_cid));
-}
-
-void ClassicSignallingManager::on_security_result_for_outgoing(
- SecurityEnforcementType type, Psm psm, Cid local_cid, bool result) {
- if (enqueue_buffer_.get() == nullptr) {
- LOG_ERROR("Got security result callback after deletion");
- return;
- }
- if (!result) {
- LOG_WARN("Security requirement can't be satisfied. Dropping connection request");
- DynamicChannelManager::ConnectionResult connection_result{
- .connection_result_code = DynamicChannelManager::ConnectionResultCode::FAIL_SECURITY_BLOCK,
- .hci_error = hci::ErrorCode::SUCCESS,
- .l2cap_connection_response_result = ConnectionResponseResult::NO_RESOURCES_AVAILABLE,
- };
- link_->OnOutgoingConnectionRequestFail(local_cid, connection_result);
- return;
- }
- if (type == SecurityEnforcementType::LINK_KEY && !link_->IsAuthenticated() &&
- dynamic_service_manager_->GetService(psm)->GetSecurityPolicy() !=
- SecurityPolicy::_SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK) {
- link_->Encrypt();
- // TODO(b/171253721): If we can receive ENCRYPTION_CHANGE event, we can send command after callback is received.
- }
-
PendingCommand pending_command = {next_signal_id_, CommandCode::CONNECTION_REQUEST, psm, local_cid, {}, {}, {}};
next_signal_id_++;
pending_commands_.push(std::move(pending_command));
@@ -131,8 +76,8 @@ void ClassicSignallingManager::on_security_result_for_outgoing(
}
}
-void ClassicSignallingManager::send_configuration_request(Cid remote_cid,
- std::vector<std::unique_ptr<ConfigurationOption>> config) {
+void ClassicSignallingManager::SendConfigurationRequest(Cid remote_cid,
+ std::vector<std::unique_ptr<ConfigurationOption>> config) {
PendingCommand pending_command = {next_signal_id_, CommandCode::CONFIGURATION_REQUEST, {}, {}, remote_cid, {},
std::move(config)};
next_signal_id_++;
@@ -147,6 +92,7 @@ void ClassicSignallingManager::SendDisconnectionRequest(Cid local_cid, Cid remot
next_signal_id_, CommandCode::DISCONNECTION_REQUEST, {}, local_cid, remote_cid, {}, {}};
next_signal_id_++;
pending_commands_.push(std::move(pending_command));
+ channel_configuration_.erase(local_cid);
if (command_just_sent_.signal_id_ == kInvalidSignalId) {
handle_send_next_command();
}
@@ -183,14 +129,12 @@ void ClassicSignallingManager::OnConnectionRequest(SignalId signal_id, Psm psm,
ConnectionResponseStatus::NO_FURTHER_INFORMATION_AVAILABLE);
return;
}
- /* TODO(zachoverflow): add back in with policy
if (channel_allocator_->IsPsmUsed(psm)) {
LOG_WARN("Psm already exists");
send_connection_response(signal_id, remote_cid, kInvalidCid, ConnectionResponseResult::PSM_NOT_SUPPORTED,
ConnectionResponseStatus::NO_FURTHER_INFORMATION_AVAILABLE);
return;
}
- */
if (!dynamic_service_manager_->IsServiceRegistered(psm)) {
LOG_INFO("Service for this psm (%d) is not registered", psm);
@@ -199,47 +143,56 @@ void ClassicSignallingManager::OnConnectionRequest(SignalId signal_id, Psm psm,
return;
}
- dynamic_service_manager_->GetSecurityEnforcementInterface()->Enforce(
- link_->GetDevice(),
- dynamic_service_manager_->GetService(psm)->GetSecurityPolicy(),
- handler_->BindOnceOn(
- this, &ClassicSignallingManager::on_security_result_for_incoming, psm, remote_cid, signal_id));
-}
-
-void ClassicSignallingManager::on_security_result_for_incoming(
- Psm psm, Cid remote_cid, SignalId signal_id, bool result) {
- if (enqueue_buffer_.get() == nullptr) {
- LOG_ERROR("Got security result callback after deletion");
- return;
- }
- if (!result) {
- send_connection_response(
- signal_id,
- remote_cid,
- 0,
- ConnectionResponseResult::SECURITY_BLOCK,
- ConnectionResponseStatus::NO_FURTHER_INFORMATION_AVAILABLE);
- DynamicChannelManager::ConnectionResult connection_result{
- .connection_result_code = DynamicChannelManager::ConnectionResultCode::FAIL_SECURITY_BLOCK,
- .hci_error = hci::ErrorCode::SUCCESS,
- .l2cap_connection_response_result = ConnectionResponseResult::NO_RESOURCES_AVAILABLE,
- };
- link_->OnOutgoingConnectionRequestFail(0, connection_result);
- }
-
- auto new_channel = link_->AllocateDynamicChannel(psm, remote_cid);
+ auto new_channel = link_->AllocateDynamicChannel(psm, remote_cid, {});
if (new_channel == nullptr) {
LOG_WARN("Can't allocate dynamic channel");
return;
}
- send_connection_response(
- signal_id,
- remote_cid,
- new_channel->GetCid(),
- ConnectionResponseResult::SUCCESS,
- ConnectionResponseStatus::NO_FURTHER_INFORMATION_AVAILABLE);
+ send_connection_response(signal_id, remote_cid, new_channel->GetCid(), ConnectionResponseResult::SUCCESS,
+ ConnectionResponseStatus::NO_FURTHER_INFORMATION_AVAILABLE);
+ auto& configuration_state = channel_configuration_[new_channel->GetCid()];
+ auto* service = dynamic_service_manager_->GetService(psm);
+ auto initial_config = service->GetConfigOption();
+
+ auto mtu_configuration = std::make_unique<MtuConfigurationOption>();
+ mtu_configuration->mtu_ = initial_config.incoming_mtu;
+ configuration_state.incoming_mtu_ = initial_config.incoming_mtu;
+
+ auto fcs_option = std::make_unique<FrameCheckSequenceOption>();
+ fcs_option->fcs_type_ = FcsType::NO_FCS;
+ if (link_->GetRemoteSupportsFcs()) {
+ fcs_option->fcs_type_ = FcsType::DEFAULT;
+ configuration_state.fcs_type_ = FcsType::DEFAULT;
+ }
+
+ auto retransmission_flow_control_configuration = std::make_unique<RetransmissionAndFlowControlConfigurationOption>();
+ switch (initial_config.channel_mode) {
+ case DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode::L2CAP_BASIC:
+ retransmission_flow_control_configuration->mode_ = RetransmissionAndFlowControlModeOption::L2CAP_BASIC;
+ configuration_state.retransmission_and_flow_control_mode_ = RetransmissionAndFlowControlModeOption::L2CAP_BASIC;
+ break;
+ case DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode::ENHANCED_RETRANSMISSION:
+ retransmission_flow_control_configuration->mode_ =
+ RetransmissionAndFlowControlModeOption::ENHANCED_RETRANSMISSION;
+ configuration_state.retransmission_and_flow_control_mode_ =
+ RetransmissionAndFlowControlModeOption::ENHANCED_RETRANSMISSION;
+ // TODO: Decide where to put initial values
+ retransmission_flow_control_configuration->tx_window_size_ = 10;
+ retransmission_flow_control_configuration->max_transmit_ = 20;
+ retransmission_flow_control_configuration->retransmission_time_out_ = 2000;
+ retransmission_flow_control_configuration->monitor_time_out_ = 12000;
+ retransmission_flow_control_configuration->maximum_pdu_size_ = 1010;
+ break;
+ }
+ configuration_state.local_retransmission_and_flow_control_ = *retransmission_flow_control_configuration;
- link_->SendInitialConfigRequestOrQueue(new_channel->GetCid());
+ std::vector<std::unique_ptr<ConfigurationOption>> config;
+ config.emplace_back(std::move(mtu_configuration));
+ if (initial_config.channel_mode != DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode::L2CAP_BASIC) {
+ config.emplace_back(std::move(retransmission_flow_control_configuration));
+ config.emplace_back(std::move(fcs_option));
+ }
+ SendConfigurationRequest(remote_cid, std::move(config));
}
void ClassicSignallingManager::OnConnectionResponse(SignalId signal_id, Cid remote_cid, Cid cid,
@@ -265,140 +218,31 @@ void ClassicSignallingManager::OnConnectionResponse(SignalId signal_id, Cid remo
command_just_sent_.signal_id_ = kInvalidSignalId;
alarm_.Cancel();
if (result != ConnectionResponseResult::SUCCESS) {
- DynamicChannelManager::ConnectionResult connection_result{
- .connection_result_code = DynamicChannelManager::ConnectionResultCode::FAIL_L2CAP_ERROR,
- .hci_error = hci::ErrorCode::SUCCESS,
- .l2cap_connection_response_result = result,
- };
- link_->OnOutgoingConnectionRequestFail(cid, connection_result);
+ link_->OnOutgoingConnectionRequestFail(cid);
handle_send_next_command();
return;
}
Psm pending_psm = command_just_sent_.psm_;
- auto new_channel = link_->AllocateReservedDynamicChannel(cid, pending_psm, remote_cid);
+ auto new_channel = link_->AllocateReservedDynamicChannel(cid, pending_psm, remote_cid, {});
if (new_channel == nullptr) {
LOG_WARN("Can't allocate dynamic channel");
- DynamicChannelManager::ConnectionResult connection_result{
- .connection_result_code = DynamicChannelManager::ConnectionResultCode::FAIL_L2CAP_ERROR,
- .hci_error = hci::ErrorCode::SUCCESS,
- .l2cap_connection_response_result = ConnectionResponseResult::NO_RESOURCES_AVAILABLE,
- };
- link_->OnOutgoingConnectionRequestFail(cid, connection_result);
+ link_->OnOutgoingConnectionRequestFail(cid);
handle_send_next_command();
return;
}
- link_->SendInitialConfigRequestOrQueue(cid);
-}
-
-void ClassicSignallingManager::OnConfigurationRequest(SignalId signal_id, Cid cid, Continuation is_continuation,
- std::vector<std::unique_ptr<ConfigurationOption>> options) {
- auto channel = channel_allocator_->FindChannelByCid(cid);
- if (channel == nullptr) {
- LOG_WARN("Configuration request for an unknown channel");
- return;
- }
-
- auto& configuration_state = channel_configuration_[cid];
- std::vector<std::unique_ptr<ConfigurationOption>> rsp_options;
- ConfigurationResponseResult result = ConfigurationResponseResult::SUCCESS;
- auto remote_rfc_mode = RetransmissionAndFlowControlModeOption::L2CAP_BASIC;
-
- auto initial_config_option = dynamic_service_manager_->GetService(channel->GetPsm())->GetConfigOption();
-
- for (auto& option : options) {
- switch (option->type_) {
- case ConfigurationOptionType::MTU: {
- auto* config = MtuConfigurationOption::Specialize(option.get());
- if (config->mtu_ < initial_config_option.minimal_remote_mtu) {
- LOG_WARN("Configuration request with unacceptable MTU");
- config->mtu_ = initial_config_option.minimal_remote_mtu;
- result = ConfigurationResponseResult::UNACCEPTABLE_PARAMETERS;
- }
- rsp_options.emplace_back(std::make_unique<MtuConfigurationOption>(*config));
- break;
- }
- case ConfigurationOptionType::FLUSH_TIMEOUT: {
- auto* config = FlushTimeoutConfigurationOption::Specialize(option.get());
- rsp_options.emplace_back(std::make_unique<FlushTimeoutConfigurationOption>(*config));
- break;
- }
- case ConfigurationOptionType::RETRANSMISSION_AND_FLOW_CONTROL: {
- auto* config = RetransmissionAndFlowControlConfigurationOption::Specialize(option.get());
- remote_rfc_mode = config->mode_;
- if (config->mode_ == RetransmissionAndFlowControlModeOption::ENHANCED_RETRANSMISSION) {
- if (config->retransmission_time_out_ == 0) {
- config->retransmission_time_out_ = 2000;
- }
- if (config->monitor_time_out_ == 0) {
- config->monitor_time_out_ = 12000;
- }
- }
- configuration_state.remote_retransmission_and_flow_control_ = *config;
- configuration_state.retransmission_and_flow_control_mode_ = config->mode_;
- rsp_options.emplace_back(std::make_unique<RetransmissionAndFlowControlConfigurationOption>(*config));
- break;
- }
- case ConfigurationOptionType::FRAME_CHECK_SEQUENCE: {
- // We determine whether to use FCS or not when we send config request
- break;
- }
- default:
- if (option->is_hint_ != ConfigurationOptionIsHint::OPTION_IS_A_HINT) {
- LOG_WARN("Received some unsupported configuration option: %d", static_cast<int>(option->type_));
- auto response =
- ConfigurationResponseBuilder::Create(signal_id.Value(), channel->GetRemoteCid(), is_continuation,
- ConfigurationResponseResult::UNKNOWN_OPTIONS, {});
- enqueue_buffer_->Enqueue(std::move(response), handler_);
- return;
- }
- break;
- }
- }
-
- if (remote_rfc_mode == RetransmissionAndFlowControlModeOption::L2CAP_BASIC &&
- initial_config_option.channel_mode ==
- DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode::ENHANCED_RETRANSMISSION) {
- LOG_WARN("ERTM mandatory not allow mode configuration, disconnect channel.");
- SendDisconnectionRequest(channel->GetCid(), channel->GetRemoteCid());
- return;
- }
-
- if (configuration_state.state_ == ChannelConfigurationState::State::WAIT_CONFIG_REQ) {
- std::unique_ptr<DynamicChannel> user_channel = std::make_unique<DynamicChannel>(channel, handler_);
- if (channel->local_initiated_) {
- link_->NotifyChannelCreation(cid, std::move(user_channel));
- } else {
- dynamic_service_manager_->GetService(channel->GetPsm())->NotifyChannelCreation(std::move(user_channel));
- }
- configuration_state.state_ = ChannelConfigurationState::State::CONFIGURED;
- data_pipeline_manager_->AttachChannel(cid, channel, l2cap::internal::DataPipelineManager::ChannelMode::BASIC);
- data_pipeline_manager_->UpdateClassicConfiguration(cid, configuration_state);
- } else if (configuration_state.state_ == ChannelConfigurationState::State::WAIT_CONFIG_REQ_RSP) {
- configuration_state.state_ = ChannelConfigurationState::State::WAIT_CONFIG_RSP;
- }
-
- auto response = ConfigurationResponseBuilder::Create(signal_id.Value(), channel->GetRemoteCid(), is_continuation,
- result, std::move(rsp_options));
- enqueue_buffer_->Enqueue(std::move(response), handler_);
-}
-
-void ClassicSignallingManager::SendInitialConfigRequest(Cid local_cid) {
- auto channel = channel_allocator_->FindChannelByCid(local_cid);
- auto psm = channel->GetPsm();
- auto& configuration_state = channel_configuration_[local_cid];
- auto* service = dynamic_service_manager_->GetService(psm);
- auto initial_config = service->GetConfigOption();
+ auto& configuration_state = channel_configuration_[new_channel->GetCid()];
+ auto initial_config = link_->GetConfigurationForInitialConfiguration(new_channel->GetCid());
auto mtu_configuration = std::make_unique<MtuConfigurationOption>();
mtu_configuration->mtu_ = initial_config.incoming_mtu;
+ configuration_state.incoming_mtu_ = initial_config.incoming_mtu;
auto fcs_option = std::make_unique<FrameCheckSequenceOption>();
- fcs_option->fcs_type_ = FcsType::NO_FCS;
- configuration_state.fcs_type_ = FcsType::NO_FCS;
- if (link_->GetRemoteSupportsFcs()) {
- fcs_option->fcs_type_ = FcsType::DEFAULT;
- configuration_state.fcs_type_ = FcsType::DEFAULT;
+ fcs_option->fcs_type_ = FcsType::DEFAULT;
+ if (!link_->GetRemoteSupportsFcs()) {
+ fcs_option->fcs_type_ = FcsType::NO_FCS;
+ configuration_state.fcs_type_ = FcsType::NO_FCS;
}
auto retransmission_flow_control_configuration = std::make_unique<RetransmissionAndFlowControlConfigurationOption>();
@@ -408,7 +252,6 @@ void ClassicSignallingManager::SendInitialConfigRequest(Cid local_cid) {
configuration_state.retransmission_and_flow_control_mode_ = RetransmissionAndFlowControlModeOption::L2CAP_BASIC;
break;
case DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode::ENHANCED_RETRANSMISSION:
- case DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode::ENHANCED_RETRANSMISSION_OPTIONAL:
retransmission_flow_control_configuration->mode_ =
RetransmissionAndFlowControlModeOption::ENHANCED_RETRANSMISSION;
configuration_state.retransmission_and_flow_control_mode_ =
@@ -429,67 +272,73 @@ void ClassicSignallingManager::SendInitialConfigRequest(Cid local_cid) {
config.emplace_back(std::move(retransmission_flow_control_configuration));
config.emplace_back(std::move(fcs_option));
}
- send_configuration_request(channel->GetRemoteCid(), std::move(config));
+ SendConfigurationRequest(remote_cid, std::move(config));
}
-void ClassicSignallingManager::negotiate_configuration(Cid cid, Continuation is_continuation,
- std::vector<std::unique_ptr<ConfigurationOption>> options) {
+void ClassicSignallingManager::OnConfigurationRequest(SignalId signal_id, Cid cid, Continuation is_continuation,
+ std::vector<std::unique_ptr<ConfigurationOption>> options) {
auto channel = channel_allocator_->FindChannelByCid(cid);
- auto& configuration_state = channel_configuration_[channel->GetCid()];
- std::vector<std::unique_ptr<ConfigurationOption>> negotiation_config;
- bool can_negotiate = false;
+ if (channel == nullptr) {
+ LOG_WARN("Configuration request for an unknown channel");
+ return;
+ }
+
+ auto& configuration_state = channel_configuration_[cid];
+ std::vector<std::unique_ptr<ConfigurationOption>> rsp_options;
+
for (auto& option : options) {
switch (option->type_) {
case ConfigurationOptionType::MTU: {
- // MTU is non-negotiable option. Use default mtu size
- auto mtu_configuration = std::make_unique<MtuConfigurationOption>();
- mtu_configuration->mtu_ = kDefaultClassicMtu;
- negotiation_config.emplace_back(std::move(mtu_configuration));
- can_negotiate = true;
+ configuration_state.outgoing_mtu_ = MtuConfigurationOption::Specialize(option.get())->mtu_;
+ // TODO: If less than minimum (required by spec), reject
break;
}
- case ConfigurationOptionType::FRAME_CHECK_SEQUENCE:
case ConfigurationOptionType::FLUSH_TIMEOUT: {
- // TODO: Handle these two configuration options negotiation.
- can_negotiate = true;
+ // TODO: Handle this configuration option
break;
}
case ConfigurationOptionType::RETRANSMISSION_AND_FLOW_CONTROL: {
auto* config = RetransmissionAndFlowControlConfigurationOption::Specialize(option.get());
- if (config->mode_ == RetransmissionAndFlowControlModeOption::ENHANCED_RETRANSMISSION) {
- configuration_state.retransmission_and_flow_control_mode_ = config->mode_;
- configuration_state.local_retransmission_and_flow_control_ = *config;
- negotiation_config.emplace_back(std::make_unique<RetransmissionAndFlowControlConfigurationOption>(*config));
- } else if (config->mode_ == RetransmissionAndFlowControlModeOption::L2CAP_BASIC) {
- auto initial_config_option = dynamic_service_manager_->GetService(channel->GetPsm())->GetConfigOption();
- if (initial_config_option.channel_mode ==
- DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode::ENHANCED_RETRANSMISSION) {
- // ERTM mandatory is not allow negotiating of retransmission and flow control mode, disconnect channel
- SendDisconnectionRequest(channel->GetCid(), channel->GetRemoteCid());
- return;
- } else if (initial_config_option.channel_mode ==
- DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode::
- ENHANCED_RETRANSMISSION_OPTIONAL) {
- can_negotiate = true;
- negotiation_config.emplace_back(std::make_unique<RetransmissionAndFlowControlConfigurationOption>(*config));
- }
- } else {
- // Not support other retransmission and flow control mode, disconnect channel.
- SendDisconnectionRequest(channel->GetCid(), channel->GetRemoteCid());
- return;
+ if (config->retransmission_time_out_ == 0) {
+ config->retransmission_time_out_ = 2000;
}
+ if (config->monitor_time_out_ == 0) {
+ config->monitor_time_out_ = 12000;
+ }
+ configuration_state.remote_retransmission_and_flow_control_ = *config;
+ rsp_options.emplace_back(std::make_unique<RetransmissionAndFlowControlConfigurationOption>(*config));
+ break;
+ }
+ case ConfigurationOptionType::FRAME_CHECK_SEQUENCE: {
+ configuration_state.fcs_type_ = FrameCheckSequenceOption::Specialize(option.get())->fcs_type_;
break;
}
default:
LOG_WARN("Received some unsupported configuration option: %d", static_cast<int>(option->type_));
+ auto response =
+ ConfigurationResponseBuilder::Create(signal_id.Value(), channel->GetRemoteCid(), is_continuation,
+ ConfigurationResponseResult::UNKNOWN_OPTIONS, {});
+ enqueue_buffer_->Enqueue(std::move(response), handler_);
return;
}
}
- if (can_negotiate) {
- send_configuration_request(channel->GetRemoteCid(), std::move(negotiation_config));
- } else {
- LOG_INFO("No suggested parameter received");
+
+ if (configuration_state.state_ == ChannelConfigurationState::State::WAIT_CONFIG_REQ) {
+ std::unique_ptr<DynamicChannel> user_channel = std::make_unique<DynamicChannel>(channel, handler_);
+ if (channel->local_initiated_) {
+ link_->NotifyChannelCreation(cid, std::move(user_channel));
+ } else {
+ dynamic_service_manager_->GetService(channel->GetPsm())->NotifyChannelCreation(std::move(user_channel));
+ }
+ configuration_state.state_ = ChannelConfigurationState::State::CONFIGURED;
+ data_pipeline_manager_->UpdateClassicConfiguration(cid, configuration_state);
+ } else if (configuration_state.state_ == ChannelConfigurationState::State::WAIT_CONFIG_REQ_RSP) {
+ configuration_state.state_ = ChannelConfigurationState::State::WAIT_CONFIG_RSP;
}
+
+ auto response = ConfigurationResponseBuilder::Create(signal_id.Value(), channel->GetRemoteCid(), is_continuation,
+ ConfigurationResponseResult::SUCCESS, std::move(rsp_options));
+ enqueue_buffer_->Enqueue(std::move(response), handler_);
}
void ClassicSignallingManager::OnConfigurationResponse(SignalId signal_id, Cid cid, Continuation is_continuation,
@@ -510,50 +359,34 @@ void ClassicSignallingManager::OnConfigurationResponse(SignalId signal_id, Cid c
return;
}
- switch (result) {
- default:
- case ConfigurationResponseResult::REJECTED:
- case ConfigurationResponseResult::UNKNOWN_OPTIONS:
- case ConfigurationResponseResult::FLOW_SPEC_REJECTED:
- LOG_WARN("Configuration response not SUCCESS: %s", ConfigurationResponseResultText(result).c_str());
- alarm_.Cancel();
- handle_send_next_command();
- return;
-
- case ConfigurationResponseResult::PENDING:
- alarm_.Schedule(common::BindOnce(&ClassicSignallingManager::on_command_timeout, common::Unretained(this)),
- kTimeout);
- return;
-
- case ConfigurationResponseResult::UNACCEPTABLE_PARAMETERS:
- LOG_INFO("Configuration response with unacceptable parameters");
- alarm_.Cancel();
- negotiate_configuration(cid, is_continuation, std::move(options));
- handle_send_next_command();
- return;
+ if (result == ConfigurationResponseResult::PENDING) {
+ alarm_.Schedule(common::BindOnce(&ClassicSignallingManager::on_command_timeout, common::Unretained(this)),
+ kTimeout);
+ return;
+ }
- case ConfigurationResponseResult::SUCCESS:
- break;
+ if (result != ConfigurationResponseResult::SUCCESS) {
+ LOG_WARN("Configuration response not SUCCESS");
+ handle_send_next_command();
+ return;
}
+
auto& configuration_state = channel_configuration_[channel->GetCid()];
for (auto& option : options) {
switch (option->type_) {
case ConfigurationOptionType::MTU: {
- // Since they accepted our MTU, no need to read the new value.
+ auto config = MtuConfigurationOption::Specialize(option.get());
+ configuration_state.incoming_mtu_ = config->mtu_;
break;
}
case ConfigurationOptionType::FLUSH_TIMEOUT: {
+ // TODO: Handle this configuration option
break;
}
case ConfigurationOptionType::RETRANSMISSION_AND_FLOW_CONTROL: {
auto config = RetransmissionAndFlowControlConfigurationOption::Specialize(option.get());
- if (configuration_state.retransmission_and_flow_control_mode_ != config->mode_) {
- SendDisconnectionRequest(cid, channel->GetRemoteCid());
- alarm_.Cancel();
- handle_send_next_command();
- return;
- }
+ configuration_state.retransmission_and_flow_control_mode_ = config->mode_;
configuration_state.local_retransmission_and_flow_control_ = *config;
break;
}
@@ -563,8 +396,6 @@ void ClassicSignallingManager::OnConfigurationResponse(SignalId signal_id, Cid c
}
default:
LOG_WARN("Received some unsupported configuration option: %d", static_cast<int>(option->type_));
- alarm_.Cancel();
- handle_send_next_command();
return;
}
}
@@ -577,7 +408,6 @@ void ClassicSignallingManager::OnConfigurationResponse(SignalId signal_id, Cid c
dynamic_service_manager_->GetService(channel->GetPsm())->NotifyChannelCreation(std::move(user_channel));
}
configuration_state.state_ = ChannelConfigurationState::State::CONFIGURED;
- data_pipeline_manager_->AttachChannel(cid, channel, l2cap::internal::DataPipelineManager::ChannelMode::BASIC);
data_pipeline_manager_->UpdateClassicConfiguration(cid, configuration_state);
} else if (configuration_state.state_ == ChannelConfigurationState::State::WAIT_CONFIG_REQ_RSP) {
configuration_state.state_ = ChannelConfigurationState::State::WAIT_CONFIG_REQ;
@@ -594,15 +424,11 @@ void ClassicSignallingManager::OnDisconnectionRequest(SignalId signal_id, Cid ci
LOG_WARN("Disconnect request for an unknown channel");
return;
}
+ channel_configuration_.erase(cid);
auto builder = DisconnectionResponseBuilder::Create(signal_id.Value(), cid, remote_cid);
enqueue_buffer_->Enqueue(std::move(builder), handler_);
channel->OnClosed(hci::ErrorCode::SUCCESS);
- auto& configuration_state = channel_configuration_[channel->GetCid()];
- if (configuration_state.state_ == configuration_state.CONFIGURED) {
- data_pipeline_manager_->DetachChannel(cid);
- }
link_->FreeDynamicChannel(cid);
- channel_configuration_.erase(cid);
}
void ClassicSignallingManager::OnDisconnectionResponse(SignalId signal_id, Cid remote_cid, Cid cid) {
@@ -624,13 +450,8 @@ void ClassicSignallingManager::OnDisconnectionResponse(SignalId signal_id, Cid r
}
channel->OnClosed(hci::ErrorCode::SUCCESS);
- auto& configuration_state = channel_configuration_[cid];
- if (configuration_state.state_ == configuration_state.CONFIGURED) {
- data_pipeline_manager_->DetachChannel(cid);
- }
link_->FreeDynamicChannel(cid);
handle_send_next_command();
- channel_configuration_.erase(cid);
}
void ClassicSignallingManager::OnEchoRequest(SignalId signal_id, const PacketView<kLittleEndian>& packet) {
@@ -662,9 +483,9 @@ void ClassicSignallingManager::OnInformationRequest(SignalId signal_id, Informat
break;
}
case InformationRequestInfoType::EXTENDED_FEATURES_SUPPORTED: {
+ // TODO: implement this response
auto response = InformationResponseExtendedFeaturesBuilder::Create(
- signal_id.Value(), InformationRequestResult::SUCCESS, 0, 0, 0, 1 /* ERTM */, 0 /* Streaming mode */,
- 1 /* FCS */, 0, 1 /* Fixed Channels */, 0, 0, 0 /* COC */);
+ signal_id.Value(), InformationRequestResult::SUCCESS, 0, 0, 0, 1, 0, 1, 0, 0, 0, 0);
enqueue_buffer_->Enqueue(std::move(response), handler_);
break;
}
@@ -703,7 +524,8 @@ void ClassicSignallingManager::OnInformationResponse(SignalId signal_id, const I
LOG_WARN("Invalid InformationResponseExtendedFeatures received");
return;
}
- link_->OnRemoteExtendedFeatureReceived(view.GetEnhancedRetransmissionMode(), view.GetFcsOption());
+ link_->SetRemoteSupportsErtm((view.GetEnhancedRetransmissionMode()));
+ link_->SetRemoteSupportsFcs(view.GetFcsOption());
// We don't care about other parameters
break;
}
@@ -724,13 +546,7 @@ void ClassicSignallingManager::OnInformationResponse(SignalId signal_id, const I
void ClassicSignallingManager::on_incoming_packet() {
auto packet = signalling_channel_->GetQueueUpEnd()->TryDequeue();
- auto command_list = GetCommandsFromPacketView(*packet);
- for (auto& command : command_list) {
- handle_one_command(command);
- }
-}
-
-void ClassicSignallingManager::handle_one_command(ControlView control_packet_view) {
+ ControlView control_packet_view = ControlView::Create(*packet);
if (!control_packet_view.IsValid()) {
LOG_WARN("Invalid signalling packet received");
return;
@@ -834,42 +650,6 @@ void ClassicSignallingManager::handle_one_command(ControlView control_packet_vie
OnInformationResponse(information_response_view.GetIdentifier(), information_response_view);
return;
}
- case CommandCode::CREDIT_BASED_CONNECTION_REQUEST: {
- CreditBasedConnectionRequestView request_view = CreditBasedConnectionRequestView::Create(control_packet_view);
- if (!request_view.IsValid()) {
- return;
- }
- return;
- }
- case CommandCode::CREDIT_BASED_CONNECTION_RESPONSE: {
- CreditBasedConnectionResponseView response_view = CreditBasedConnectionResponseView::Create(control_packet_view);
- if (!response_view.IsValid()) {
- return;
- }
- return;
- }
- case CommandCode::CREDIT_BASED_RECONFIGURE_REQUEST: {
- CreditBasedReconfigureRequestView request_view = CreditBasedReconfigureRequestView::Create(control_packet_view);
- if (!request_view.IsValid()) {
- return;
- }
- return;
- }
- case CommandCode::CREDIT_BASED_RECONFIGURE_RESPONSE: {
- CreditBasedReconfigureResponseView response_view =
- CreditBasedReconfigureResponseView::Create(control_packet_view);
- if (!response_view.IsValid()) {
- return;
- }
- return;
- }
- case CommandCode::FLOW_CONTROL_CREDIT: {
- FlowControlCreditView credit_view = FlowControlCreditView::Create(control_packet_view);
- if (!credit_view.IsValid()) {
- return;
- }
- return;
- }
default:
LOG_WARN("Unhandled event 0x%x", static_cast<int>(code));
auto builder = CommandRejectNotUnderstoodBuilder::Create(control_packet_view.GetIdentifier());
@@ -891,26 +671,15 @@ void ClassicSignallingManager::on_command_timeout() {
LOG_ERROR("No pending command");
return;
}
- LOG_WARN("Response time out for %s", CommandCodeText(command_just_sent_.command_code_).c_str());
+
switch (command_just_sent_.command_code_) {
case CommandCode::CONNECTION_REQUEST: {
- DynamicChannelManager::ConnectionResult connection_result{
- .connection_result_code = DynamicChannelManager::ConnectionResultCode::FAIL_L2CAP_ERROR,
- .hci_error = hci::ErrorCode::SUCCESS,
- .l2cap_connection_response_result = ConnectionResponseResult::NO_RESOURCES_AVAILABLE,
- };
- link_->OnOutgoingConnectionRequestFail(command_just_sent_.source_cid_, connection_result);
+ link_->OnOutgoingConnectionRequestFail(command_just_sent_.source_cid_);
break;
}
case CommandCode::CONFIGURATION_REQUEST: {
auto channel = channel_allocator_->FindChannelByRemoteCid(command_just_sent_.destination_cid_);
SendDisconnectionRequest(channel->GetCid(), channel->GetRemoteCid());
- return;
- }
- case CommandCode::INFORMATION_REQUEST: {
- if (command_just_sent_.info_type_ == InformationRequestInfoType::EXTENDED_FEATURES_SUPPORTED) {
- link_->OnRemoteExtendedFeatureReceived(false, false);
- }
break;
}
default:
diff --git a/gd/l2cap/classic/internal/signalling_manager.h b/gd/l2cap/classic/internal/signalling_manager.h
index 76637ae56..2a7b3c5e8 100644
--- a/gd/l2cap/classic/internal/signalling_manager.h
+++ b/gd/l2cap/classic/internal/signalling_manager.h
@@ -66,7 +66,7 @@ class ClassicSignallingManager {
void SendConnectionRequest(Psm psm, Cid local_cid);
- void SendInitialConfigRequest(Cid local_cid);
+ void SendConfigurationRequest(Cid remote_cid, std::vector<std::unique_ptr<ConfigurationOption>> config);
void SendDisconnectionRequest(Cid local_cid, Cid remote_cid);
@@ -99,26 +99,13 @@ class ClassicSignallingManager {
void OnInformationResponse(SignalId signal_id, const InformationResponseView& response);
- enum class SecurityEnforcementType {
- LINK_KEY,
- ENCRYPTION,
- };
- void on_security_result_for_outgoing(SecurityEnforcementType type, Psm psm, Cid local_cid, bool result);
-
private:
void on_incoming_packet();
- void handle_one_command(ControlView control_view);
void send_connection_response(SignalId signal_id, Cid remote_cid, Cid local_cid, ConnectionResponseResult result,
ConnectionResponseStatus status);
void on_command_timeout();
void handle_send_next_command();
- void negotiate_configuration(Cid cid, Continuation is_continuation,
- std::vector<std::unique_ptr<ConfigurationOption>>);
-
- void send_configuration_request(Cid remote_cid, std::vector<std::unique_ptr<ConfigurationOption>> config);
- void on_security_result_for_incoming(Psm psm, Cid remote_cid, SignalId signal_id, bool result);
-
os::Handler* handler_;
Link* link_;
l2cap::internal::DataPipelineManager* data_pipeline_manager_;
diff --git a/gd/l2cap/classic/l2cap_classic_module.cc b/gd/l2cap/classic/l2cap_classic_module.cc
index e70f1db11..ca5a0d5f3 100644
--- a/gd/l2cap/classic/l2cap_classic_module.cc
+++ b/gd/l2cap/classic/l2cap_classic_module.cc
@@ -15,7 +15,6 @@
*/
#define LOG_TAG "l2cap2"
-#include <future>
#include <memory>
#include "common/bidi_queue.h"
@@ -23,31 +22,25 @@
#include "hci/address.h"
#include "hci/hci_layer.h"
#include "hci/hci_packets.h"
-#include "l2cap/classic/internal/dumpsys_helper.h"
#include "l2cap/classic/internal/dynamic_channel_service_manager_impl.h"
#include "l2cap/classic/internal/fixed_channel_service_manager_impl.h"
#include "l2cap/classic/internal/link_manager.h"
-#include "l2cap/classic/l2cap_classic_module.h"
#include "l2cap/internal/parameter_provider.h"
-#include "l2cap_classic_module_generated.h"
#include "module.h"
#include "os/handler.h"
#include "os/log.h"
+#include "l2cap/classic/l2cap_classic_module.h"
+
namespace bluetooth {
namespace l2cap {
namespace classic {
const ModuleFactory L2capClassicModule::Factory = ModuleFactory([]() { return new L2capClassicModule(); });
-static SecurityEnforcementRejectAllImpl default_security_module_impl_;
-
struct L2capClassicModule::impl {
impl(os::Handler* l2cap_handler, hci::AclManager* acl_manager)
- : l2cap_handler_(l2cap_handler), acl_manager_(acl_manager) {
- dynamic_channel_service_manager_impl_.SetSecurityEnforcementInterface(&default_security_module_impl_);
- dumpsys_helper_ = std::make_unique<internal::DumpsysHelper>(link_manager_);
- }
+ : l2cap_handler_(l2cap_handler), acl_manager_(acl_manager) {}
os::Handler* l2cap_handler_;
hci::AclManager* acl_manager_;
l2cap::internal::ParameterProvider parameter_provider_;
@@ -55,34 +48,6 @@ struct L2capClassicModule::impl {
internal::DynamicChannelServiceManagerImpl dynamic_channel_service_manager_impl_{l2cap_handler_};
internal::LinkManager link_manager_{l2cap_handler_, acl_manager_, &fixed_channel_service_manager_impl_,
&dynamic_channel_service_manager_impl_, &parameter_provider_};
- std::unique_ptr<internal::DumpsysHelper> dumpsys_helper_;
-
- struct SecurityInterfaceImpl : public SecurityInterface {
- SecurityInterfaceImpl(impl* module_impl) : module_impl_(module_impl) {}
-
- void RegisterLinkSecurityInterfaceListener(os::Handler* handler, LinkSecurityInterfaceListener* listener) {
- ASSERT(!registered_);
- module_impl_->link_manager_.RegisterLinkSecurityInterfaceListener(handler, listener);
- registered_ = true;
- }
-
- void InitiateConnectionForSecurity(hci::Address remote) override {
- ASSERT(registered_);
- module_impl_->link_manager_.InitiateConnectionForSecurity(remote);
- }
-
- void Unregister() override {
- ASSERT(registered_);
- module_impl_->link_manager_.RegisterLinkSecurityInterfaceListener(nullptr, nullptr);
- registered_ = false;
- }
- impl* module_impl_;
- bool registered_ = false;
- } security_interface_impl_{this};
-
- void Dump(
- std::promise<flatbuffers::Offset<L2capClassicModuleData>> promise,
- flatbuffers::FlatBufferBuilder* fb_builder) const;
};
L2capClassicModule::L2capClassicModule() {}
@@ -115,57 +80,6 @@ std::unique_ptr<DynamicChannelManager> L2capClassicModule::GetDynamicChannelMana
&pimpl_->dynamic_channel_service_manager_impl_, &pimpl_->link_manager_, pimpl_->l2cap_handler_));
}
-void L2capClassicModule::InjectSecurityEnforcementInterface(
- SecurityEnforcementInterface* security_enforcement_interface) {
- if (security_enforcement_interface != nullptr) {
- pimpl_->dynamic_channel_service_manager_impl_.SetSecurityEnforcementInterface(security_enforcement_interface);
- } else {
- pimpl_->dynamic_channel_service_manager_impl_.SetSecurityEnforcementInterface(&default_security_module_impl_);
- }
-}
-
-SecurityInterface* L2capClassicModule::GetSecurityInterface(
- os::Handler* handler, LinkSecurityInterfaceListener* listener) {
- pimpl_->security_interface_impl_.RegisterLinkSecurityInterfaceListener(handler, listener);
- return &pimpl_->security_interface_impl_;
-}
-
-void L2capClassicModule::SetLinkPropertyListener(os::Handler* handler, LinkPropertyListener* listener) {
- pimpl_->link_manager_.RegisterLinkPropertyListener(handler, listener);
-}
-
-void L2capClassicModule::impl::Dump(
- std::promise<flatbuffers::Offset<L2capClassicModuleData>> promise,
- flatbuffers::FlatBufferBuilder* fb_builder) const {
- auto title = fb_builder->CreateString("----- L2cap Classic Dumpsys -----");
-
- std::vector<flatbuffers::Offset<bluetooth::l2cap::classic::LinkData>> link_offsets =
- dumpsys_helper_->DumpActiveLinks(fb_builder);
-
- auto active_links = fb_builder->CreateVector(link_offsets);
-
- L2capClassicModuleDataBuilder builder(*fb_builder);
- builder.add_title(title);
- builder.add_active_links(active_links);
- flatbuffers::Offset<L2capClassicModuleData> dumpsys_data = builder.Finish();
-
- promise.set_value(dumpsys_data);
-}
-
-DumpsysDataFinisher L2capClassicModule::GetDumpsysData(flatbuffers::FlatBufferBuilder* fb_builder) const {
- ASSERT(fb_builder != nullptr);
-
- std::promise<flatbuffers::Offset<L2capClassicModuleData>> promise;
- auto future = promise.get_future();
- pimpl_->Dump(std::move(promise), fb_builder);
-
- auto dumpsys_data = future.get();
-
- return [dumpsys_data](DumpsysDataBuilder* dumpsys_builder) {
- dumpsys_builder->add_l2cap_classic_dumpsys_data(dumpsys_data);
- };
-}
-
} // namespace classic
} // namespace l2cap
} // namespace bluetooth
diff --git a/gd/l2cap/classic/l2cap_classic_module.fbs b/gd/l2cap/classic/l2cap_classic_module.fbs
deleted file mode 100644
index f1a102481..000000000
--- a/gd/l2cap/classic/l2cap_classic_module.fbs
+++ /dev/null
@@ -1,20 +0,0 @@
-namespace bluetooth.l2cap.classic;
-
-attribute "privacy";
-
-table ChannelData {
- cid:int;
-}
-
-table LinkData {
- address:string;
- dynamic_channels:[ChannelData];
- fixed_channels:[ChannelData];
-}
-
-table L2capClassicModuleData {
- title:string (privacy:"Any");
- active_links:[LinkData] (privacy:"Any");
-}
-
-root_type L2capClassicModuleData;
diff --git a/gd/l2cap/classic/l2cap_classic_module.h b/gd/l2cap/classic/l2cap_classic_module.h
index d775694a6..388cae28d 100644
--- a/gd/l2cap/classic/l2cap_classic_module.h
+++ b/gd/l2cap/classic/l2cap_classic_module.h
@@ -19,17 +19,9 @@
#include "l2cap/classic/dynamic_channel_manager.h"
#include "l2cap/classic/fixed_channel_manager.h"
-#include "l2cap/classic/link_property_listener.h"
-#include "l2cap/classic/link_security_interface.h"
-#include "l2cap/classic/security_enforcement_interface.h"
#include "module.h"
namespace bluetooth {
-
-namespace security {
-class SecurityModule;
-}
-
namespace l2cap {
namespace classic {
@@ -49,28 +41,6 @@ class L2capClassicModule : public bluetooth::Module {
virtual std::unique_ptr<DynamicChannelManager> GetDynamicChannelManager();
static const ModuleFactory Factory;
- /**
- * Only for the classic security module to inject functionality to enforce security level for a connection. When
- * classic security module is stopping, inject nullptr. Note: We expect this only to be called during stack startup.
- * This is not synchronized.
- */
- virtual void InjectSecurityEnforcementInterface(SecurityEnforcementInterface* security_enforcement_interface);
-
- /**
- * Get the interface for Security Module to access link function.
- * Security Module needs to register the callback for ACL link connected and disconnected. When connected, either by
- * incoming or by outgoing connection request, Security Module receives a LinkSecurityInterface proxy, which can be
- * used to access some link functionlities.
- */
- virtual SecurityInterface* GetSecurityInterface(os::Handler* handler, LinkSecurityInterfaceListener* listener);
-
- friend security::SecurityModule;
-
- /**
- * Set the link property listener.
- * This is not synchronized.
- */
- virtual void SetLinkPropertyListener(os::Handler* handler, LinkPropertyListener* listener);
protected:
void ListDependencies(ModuleList* list) override;
@@ -81,12 +51,9 @@ class L2capClassicModule : public bluetooth::Module {
std::string ToString() const override;
- DumpsysDataFinisher GetDumpsysData(flatbuffers::FlatBufferBuilder* builder) const override; // Module
-
private:
struct impl;
std::unique_ptr<impl> pimpl_;
-
DISALLOW_COPY_AND_ASSIGN(L2capClassicModule);
};
diff --git a/gd/l2cap/classic/link_property_listener.h b/gd/l2cap/classic/link_property_listener.h
deleted file mode 100644
index 288507459..000000000
--- a/gd/l2cap/classic/link_property_listener.h
+++ /dev/null
@@ -1,95 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <memory>
-
-#include "hci/address.h"
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace classic {
-
-/**
- * This is the listener interface for link property callbacks.
- */
-class LinkPropertyListener {
- public:
- virtual ~LinkPropertyListener() = default;
-
- /**
- * Invoked when an ACL link is connected.
- */
- virtual void OnLinkConnected(hci::Address remote, uint16_t handle) {}
-
- /**
- * Invoked when an ACL link is disconnected.
- */
- virtual void OnLinkDisconnected(hci::Address remote) {}
-
- /**
- * Invoked when received remote version information for a given link
- */
- virtual void OnReadRemoteVersionInformation(
- hci::ErrorCode hci_status,
- hci::Address remote,
- uint8_t lmp_version,
- uint16_t manufacturer_name,
- uint16_t sub_version) {}
-
- /**
- * Invoked when received remote features and remote supported features for a given link
- */
- virtual void OnReadRemoteSupportedFeatures(hci::Address remote, uint64_t features) {}
-
- /**
- * Invoked when received remote features and remote extended features for a given link
- */
- virtual void OnReadRemoteExtendedFeatures(
- hci::Address remote, uint8_t page_number, uint8_t max_page_number, uint64_t features) {}
-
- /**
- * Invoked when received role change
- */
- virtual void OnRoleChange(hci::ErrorCode hci_status, hci::Address remote, hci::Role role) {}
-
- /**
- * Invoked when received clock offset
- */
- virtual void OnReadClockOffset(hci::Address remote, uint16_t clock_offset) {}
-
- /**
- * Invoked when received mode change
- */
- virtual void OnModeChange(hci::ErrorCode hci_status, hci::Address remote, hci::Mode mode, uint16_t interval) {}
-
- /**
- * Invoked when received sniff subrating
- */
- virtual void OnSniffSubrating(
- hci::ErrorCode hci_status,
- hci::Address remote,
- uint16_t max_tx_lat,
- uint16_t max_rx_lat,
- uint16_t min_remote_timeout,
- uint16_t min_local_timeout) {}
-};
-
-} // namespace classic
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/classic/link_security_interface.h b/gd/l2cap/classic/link_security_interface.h
deleted file mode 100644
index 90fac62e6..000000000
--- a/gd/l2cap/classic/link_security_interface.h
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <memory>
-
-#include "hci/address.h"
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace classic {
-
-/**
- * This is a proxy for Security Module to unregister itself, or to initiate link connection.
- */
-class SecurityInterface {
- public:
- virtual ~SecurityInterface() = default;
-
- /**
- * Page a remote device for ACL connection, when Security Module needs it for pairing. When the remote device is
- * connected, Security Module will receive a callback through LinkSecurityInterfaceListener.
- */
- virtual void InitiateConnectionForSecurity(hci::Address remote) = 0;
-
- /**
- * Unregister the security interface and the LinkSecurityInterfaceListener.
- */
- virtual void Unregister() = 0;
-};
-
-/**
- * This is a proxy for Security Module to access some link function. This object is passed to Security Module when a
- * link is established.
- */
-class LinkSecurityInterface {
- public:
- virtual ~LinkSecurityInterface() = default;
-
- virtual hci::Address GetRemoteAddress() = 0;
-
- /**
- * Hold the ACL link connection. Don't disconnect the link until Release() is called.
- */
- virtual void Hold() = 0;
-
- /**
- * Release the ACL link connection. This doesn't guarantee link disconnection, if other L2cap services are using the
- * link.
- */
- virtual void Release() = 0;
-
- /**
- * Force the ACL link to disconnect.
- */
- virtual void Disconnect() = 0;
-
- /**
- * Initiate pairing to HCI layer.
- */
- virtual void EnsureAuthenticated() = 0;
-
- /**
- * Start encryption on an authenticated link (not necessarily MITM link key).
- */
- virtual void EnsureEncrypted() = 0;
-
- virtual uint16_t GetAclHandle() = 0;
-
- virtual hci::Role GetRole() {
- return hci::Role::CENTRAL;
- }
-};
-
-class LinkSecurityInterfaceListener {
- public:
- virtual ~LinkSecurityInterfaceListener() = default;
-
- /**
- * Each time when an ACL link is connected, security manager receives this callback to use LinkSecurityInterface
- * functions.
- */
- virtual void OnLinkConnected(std::unique_ptr<LinkSecurityInterface>) {}
-
- /**
- * When an ACL link is disconnected, security manager receives this callback. The corresponding LinkSecurityInterface
- * is invalidated then.
- * @param remote
- */
- virtual void OnLinkDisconnected(hci::Address remote) {}
-
- /**
- * Invoked when AuthenticationComplete event is received for a given link
- */
- virtual void OnAuthenticationComplete(hci::ErrorCode hci_status, hci::Address remote) {}
-
- /**
- * Invoked when EncryptionChange event is received for a given link
- * @param encrypted
- */
- virtual void OnEncryptionChange(hci::Address remote, bool encrypted) {}
-};
-
-} // namespace classic
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/classic/security_enforcement_interface.h b/gd/l2cap/classic/security_enforcement_interface.h
deleted file mode 100644
index 01a5c7aad..000000000
--- a/gd/l2cap/classic/security_enforcement_interface.h
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "common/contextual_callback.h"
-#include "hci/address_with_type.h"
-#include "l2cap/classic/security_policy.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace classic {
-
-/**
- * The interface for Security Module to implement.
- */
-class SecurityEnforcementInterface {
- public:
- virtual ~SecurityEnforcementInterface() = default;
-
- using ResultCallback = common::ContextualOnceCallback<void(bool)>;
-
- /**
- * Invoked when L2CAP needs to open a channel with given security requirement. When the Security Module satisfies the
- * required security level, or cannot satisfy at all, invoke the result_callback.
- */
- virtual void Enforce(hci::AddressWithType remote, SecurityPolicy policy, ResultCallback result_callback) = 0;
-};
-
-/**
- * A default implementation which cannot satisfy any security level except
- * _SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK.
- */
-class SecurityEnforcementRejectAllImpl : public SecurityEnforcementInterface {
- public:
- void Enforce(hci::AddressWithType remote, SecurityPolicy policy, ResultCallback result_callback) override {
- if (policy == SecurityPolicy::_SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK) {
- result_callback.InvokeIfNotEmpty(true);
- } else {
- result_callback.InvokeIfNotEmpty(false);
- }
- }
-};
-} // namespace classic
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/dynamic_channel.cc b/gd/l2cap/dynamic_channel.cc
index a49aed763..f8b64e609 100644
--- a/gd/l2cap/dynamic_channel.cc
+++ b/gd/l2cap/dynamic_channel.cc
@@ -21,31 +21,23 @@
namespace bluetooth {
namespace l2cap {
-hci::AddressWithType DynamicChannel::GetDevice() const {
+hci::Address DynamicChannel::GetDevice() const {
return impl_->GetDevice();
}
-void DynamicChannel::RegisterOnCloseCallback(DynamicChannel::OnCloseCallback on_close_callback) {
- l2cap_handler_->CallOn(
- impl_.get(), &l2cap::internal::DynamicChannelImpl::RegisterOnCloseCallback, std::move(on_close_callback));
+void DynamicChannel::RegisterOnCloseCallback(os::Handler* user_handler,
+ DynamicChannel::OnCloseCallback on_close_callback) {
+ l2cap_handler_->Post(common::BindOnce(&l2cap::internal::DynamicChannelImpl::RegisterOnCloseCallback, impl_,
+ user_handler, std::move(on_close_callback)));
}
void DynamicChannel::Close() {
- l2cap_handler_->CallOn(impl_.get(), &l2cap::internal::DynamicChannelImpl::Close);
+ l2cap_handler_->Post(common::BindOnce(&l2cap::internal::DynamicChannelImpl::Close, impl_));
}
common::BidiQueueEnd<packet::BasePacketBuilder, packet::PacketView<packet::kLittleEndian>>*
DynamicChannel::GetQueueUpEnd() const {
return impl_->GetQueueUpEnd();
}
-
-Cid DynamicChannel::HACK_GetRemoteCid() {
- return impl_->GetRemoteCid();
-}
-
-void DynamicChannel::HACK_SetChannelTxPriority(bool high_priority) {
- return impl_->SetChannelTxPriority(high_priority);
-}
-
} // namespace l2cap
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/gd/l2cap/dynamic_channel.h b/gd/l2cap/dynamic_channel.h
index ba4e750eb..b7496f847 100644
--- a/gd/l2cap/dynamic_channel.h
+++ b/gd/l2cap/dynamic_channel.h
@@ -18,7 +18,6 @@
#include "common/bidi_queue.h"
#include "common/callback.h"
#include "hci/acl_manager.h"
-#include "l2cap/cid.h"
#include "os/handler.h"
#include "packet/base_packet_builder.h"
#include "packet/packet_view.h"
@@ -43,17 +42,18 @@ class DynamicChannel {
ASSERT(l2cap_handler_ != nullptr);
}
- hci::AddressWithType GetDevice() const;
+ hci::Address GetDevice() const;
/**
* Register close callback. If close callback is registered, when a channel is closed, the channel's resource will
* only be freed after on_close callback is invoked. Otherwise, if no on_close callback is registered, the channel's
* resource will be freed immediately after closing.
*
+ * @param user_handler The handler used to invoke the callback on
* @param on_close_callback The callback invoked upon channel closing.
*/
- using OnCloseCallback = common::ContextualOnceCallback<void(hci::ErrorCode)>;
- void RegisterOnCloseCallback(OnCloseCallback on_close_callback);
+ using OnCloseCallback = common::OnceCallback<void(hci::ErrorCode)>;
+ void RegisterOnCloseCallback(os::Handler* user_handler, OnCloseCallback on_close_callback);
/**
* Indicate that this Dynamic Channel should be closed. OnCloseCallback will be invoked when channel close is done.
@@ -70,14 +70,6 @@ class DynamicChannel {
*/
common::BidiQueueEnd<packet::BasePacketBuilder, packet::PacketView<packet::kLittleEndian>>* GetQueueUpEnd() const;
- Cid HACK_GetRemoteCid();
-
- /**
- * Used by A2dp software encoding to prioritize Tx of this channel
- * @param high_priority
- */
- void HACK_SetChannelTxPriority(bool high_priority);
-
private:
std::shared_ptr<l2cap::internal::DynamicChannelImpl> impl_;
os::Handler* l2cap_handler_;
diff --git a/gd/l2cap/fuzz/Android.bp b/gd/l2cap/fuzz/Android.bp
deleted file mode 100755
index 64907dbf5..000000000
--- a/gd/l2cap/fuzz/Android.bp
+++ /dev/null
@@ -1,44 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "bluetooth_gd_l2cap_fuzzer",
- defaults: ["gd_fuzz_defaults"],
- include_dirs: [
- "system/bt",
- "system/bt/gd",
- "system/bt/bta/include",
- "system/bt/bta/sys",
- "system/bt/bta/dm",
- "system/bt/btcore/include",
- "system/bt/internal_include",
- "system/bt/stack/include",
- "system/bt/stack/l2cap",
- "system/bt/stack/a2dp",
- "system/bt/stack/btm",
- "system/bt/stack/avdt",
- "system/bt/udrv/include",
- "system/bt/btif/include",
- "system/bt/btif/co",
- "system/bt/hci/include",
- "system/bt/vnd/include",
- "system/bt/embdrv/sbc/encoder/include",
- "system/bt/embdrv/sbc/decoder/include",
- "system/bt/utils/include",
- "system/security/keystore/include",
- "hardware/interfaces/keymaster/4.0/support/include",
- ],
- srcs: [
- "channel_fuzz_controller.cc",
- "fuzz_l2cap.cc",
- ],
- static_libs: [
- "libbte",
- ],
-}
diff --git a/gd/l2cap/fuzz/channel_fuzz_controller.cc b/gd/l2cap/fuzz/channel_fuzz_controller.cc
deleted file mode 100755
index 41738ccbf..000000000
--- a/gd/l2cap/fuzz/channel_fuzz_controller.cc
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-// Authors: corbin.souffrant@leviathansecurity.com
-// dylan.katz@leviathansecurity.com
-
-#include "channel_fuzz_controller.h"
-
-namespace bluetooth {
-using l2cap::classic::internal::FixedChannelImpl;
-using l2cap::internal::DynamicChannelImpl;
-using os::Handler;
-
-ChannelFuzzController::ChannelFuzzController(Handler* l2cap_handler, std::shared_ptr<DynamicChannelImpl> chan) {
- EnqueueType* queue = reinterpret_cast<EnqueueType*>(chan->GetQueueUpEnd());
- channelInject_ = std::make_shared<ChannelFuzzQueueType>(queue, l2cap_handler);
-}
-
-ChannelFuzzController::ChannelFuzzController(Handler* l2cap_handler, std::shared_ptr<FixedChannelImpl> chan) {
- EnqueueType* queue = reinterpret_cast<EnqueueType*>(chan->GetQueueUpEnd());
- channelInject_ = std::make_shared<ChannelFuzzQueueType>(queue, l2cap_handler);
-}
-
-void ChannelFuzzController::injectFrame(std::vector<uint8_t> data) {
- CONSTRUCT_VALID_UNIQUE_OTHERWISE_BAIL(l2cap::BasicFrameView, packet, data);
- channelInject_->Inject(std::move(packet));
-}
-} // namespace bluetooth
diff --git a/gd/l2cap/fuzz/channel_fuzz_controller.h b/gd/l2cap/fuzz/channel_fuzz_controller.h
deleted file mode 100755
index ade2026ec..000000000
--- a/gd/l2cap/fuzz/channel_fuzz_controller.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-// Authors: corbin.souffrant@leviathansecurity.com
-// dylan.katz@leviathansecurity.com
-
-#pragma once
-#include "gd/fuzz/helpers.h"
-#include "l2cap/classic/internal/fixed_channel_impl.h"
-#include "l2cap/internal/dynamic_channel_impl.h"
-#include "l2cap/l2cap_packets.h"
-#include "os/fuzz/fuzz_inject_queue.h"
-#include "os/handler.h"
-#include "packet/packet_view.h"
-
-namespace bluetooth {
-
-typedef os::IQueueEnqueue<packet::PacketView<packet::kLittleEndian>> EnqueueType;
-typedef os::fuzz::FuzzInjectQueue<packet::PacketView<packet::kLittleEndian>> ChannelFuzzQueueType;
-
-class ChannelFuzzController {
- public:
- ChannelFuzzController(os::Handler* l2cap_handler, std::shared_ptr<l2cap::internal::DynamicChannelImpl> chan);
-
- ChannelFuzzController(os::Handler* l2cap_handler, std::shared_ptr<l2cap::classic::internal::FixedChannelImpl> chan);
-
- void injectPacketData(std::vector<uint8_t> data);
-
- void injectFrame(std::vector<uint8_t> data);
-
- private:
- std::shared_ptr<ChannelFuzzQueueType> channelInject_;
-};
-} // namespace bluetooth
diff --git a/gd/l2cap/fuzz/fuzz_dynamic_channel_manager.h b/gd/l2cap/fuzz/fuzz_dynamic_channel_manager.h
deleted file mode 100755
index 22b529185..000000000
--- a/gd/l2cap/fuzz/fuzz_dynamic_channel_manager.h
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-// Authors: corbin.souffrant@leviathansecurity.com
-// dylan.katz@leviathansecurity.com
-
-#pragma once
-
-#include <gd/l2cap/classic/dynamic_channel_service.h>
-#include <gd/l2cap/classic/internal/dynamic_channel_service_impl.h>
-#include <gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.h>
-#include <memory>
-
-#include "hci/address.h"
-#include "l2cap/classic/dynamic_channel_configuration_option.h"
-#include "l2cap/classic/dynamic_channel_manager.h"
-#include "l2cap/classic/security_policy.h"
-#include "l2cap/psm.h"
-#include "os/handler.h"
-
-#include "fuzz_dynamic_channel_manager_impl.h"
-
-namespace bluetooth {
-namespace shim {
-namespace {
-class FuzzDynamicChannelManager : public l2cap::classic::DynamicChannelManager {
- public:
- void ConnectChannel(
- hci::Address device,
- l2cap::classic::DynamicChannelConfigurationOption configuration_option,
- l2cap::Psm psm,
- l2cap::classic::DynamicChannelManager::OnConnectionOpenCallback on_open_callback,
- l2cap::classic::DynamicChannelManager::OnConnectionFailureCallback on_fail_callback) override {
- impl_.ConnectChannel(device, configuration_option, psm, std::move(on_open_callback), std::move(on_fail_callback));
- }
-
- void RegisterService(
- l2cap::Psm psm,
- l2cap::classic::DynamicChannelConfigurationOption configuration_option,
- const l2cap::classic::SecurityPolicy& security_policy,
- l2cap::classic::DynamicChannelManager::OnRegistrationCompleteCallback on_registration_complete,
- l2cap::classic::DynamicChannelManager::OnConnectionOpenCallback on_open_callback) override {
- impl_.RegisterService(
- psm, configuration_option, security_policy, std::move(on_registration_complete), std::move(on_open_callback));
- }
- FuzzDynamicChannelManager(FuzzDynamicChannelManagerImpl& impl) : impl_(impl) {}
- FuzzDynamicChannelManagerImpl& impl_;
-};
-} // namespace
-} // namespace shim
-} // namespace bluetooth
diff --git a/gd/l2cap/fuzz/fuzz_dynamic_channel_manager_impl.h b/gd/l2cap/fuzz/fuzz_dynamic_channel_manager_impl.h
deleted file mode 100755
index 9962c6571..000000000
--- a/gd/l2cap/fuzz/fuzz_dynamic_channel_manager_impl.h
+++ /dev/null
@@ -1,109 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-// Authors: corbin.souffrant@leviathansecurity.com
-// dylan.katz@leviathansecurity.com
-
-#pragma once
-
-#include <gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.h>
-#include <future>
-#include <memory>
-
-#include "hci/address.h"
-#include "l2cap/classic/dynamic_channel_configuration_option.h"
-#include "l2cap/classic/dynamic_channel_manager.h"
-#include "l2cap/classic/security_policy.h"
-#include "l2cap/psm.h"
-#include "os/handler.h"
-
-namespace bluetooth {
-namespace shim {
-namespace {
-class FuzzDynamicChannelManagerImpl {
- public:
- void ConnectChannel(
- hci::Address device,
- l2cap::classic::DynamicChannelConfigurationOption configuration_option,
- l2cap::Psm,
- l2cap::classic::DynamicChannelManager::OnConnectionOpenCallback on_open_callback,
- l2cap::classic::DynamicChannelManager::OnConnectionFailureCallback on_fail_callback) {
- connections_++;
- on_open_callback_ = std::move(on_open_callback);
- on_fail_callback_ = std::move(on_fail_callback);
-
- connected_promise_.set_value();
- }
- int connections_{0};
-
- void RegisterService(
- l2cap::Psm,
- l2cap::classic::DynamicChannelConfigurationOption,
- const l2cap::classic::SecurityPolicy&,
- l2cap::classic::DynamicChannelManager::OnRegistrationCompleteCallback on_registration_complete,
- l2cap::classic::DynamicChannelManager::OnConnectionOpenCallback on_open_callback) {
- services_++;
- on_registration_complete_ = std::move(on_registration_complete);
- on_open_callback_ = std::move(on_open_callback);
-
- register_promise_.set_value();
- }
- int services_{0};
-
- void SetConnectionFuture() {
- connected_promise_ = std::promise<void>();
- }
-
- void WaitConnectionFuture() {
- connected_future_ = connected_promise_.get_future();
- connected_future_.wait();
- }
-
- void SetRegistrationFuture() {
- register_promise_ = std::promise<void>();
- }
-
- void WaitRegistrationFuture() {
- register_future_ = register_promise_.get_future();
- register_future_.wait();
- }
-
- void SetConnectionOnFail(l2cap::classic::DynamicChannelManager::ConnectionResult result, std::promise<void> promise) {
- std::move(on_fail_callback_).Invoke(result);
- promise.set_value();
- }
-
- void SetConnectionOnOpen(std::unique_ptr<l2cap::DynamicChannel> channel, std::promise<void> promise) {
- std::move(on_open_callback_).Invoke(std::move(channel));
- promise.set_value();
- }
-
- l2cap::classic::DynamicChannelManager::OnRegistrationCompleteCallback on_registration_complete_{};
- l2cap::classic::DynamicChannelManager::OnConnectionOpenCallback on_open_callback_{};
- l2cap::classic::DynamicChannelManager::OnConnectionFailureCallback on_fail_callback_{};
-
- FuzzDynamicChannelManagerImpl() = default;
- ~FuzzDynamicChannelManagerImpl() = default;
-
- private:
- std::promise<void> connected_promise_;
- std::future<void> connected_future_;
-
- std::promise<void> register_promise_;
- std::future<void> register_future_;
-};
-} // namespace
-} // namespace shim
-} // namespace bluetooth
diff --git a/gd/l2cap/fuzz/fuzz_l2cap.cc b/gd/l2cap/fuzz/fuzz_l2cap.cc
deleted file mode 100755
index ed7bfb9fe..000000000
--- a/gd/l2cap/fuzz/fuzz_l2cap.cc
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-// Authors: corbin.souffrant@leviathansecurity.com
-// dylan.katz@leviathansecurity.com
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <hci/address.h>
-#include "l2cap/psm.h"
-#include "os/log.h"
-
-#include "channel_fuzz_controller.h"
-#include "shim_l2cap.h"
-
-namespace bluetooth {
-using hci::Address;
-using hci::AddressType;
-using hci::acl_manager::AclConnection;
-using hci::acl_manager::ClassicAclConnection;
-using l2cap::Cid;
-using l2cap::Psm;
-using l2cap::classic::internal::Link;
-
-using shim::ShimL2capFuzz;
-
-class FakeCommandInterface : public hci::CommandInterface<hci::AclCommandBuilder> {
- public:
- virtual void EnqueueCommand(
- std::unique_ptr<hci::AclCommandBuilder> command,
- common::ContextualOnceCallback<void(hci::CommandCompleteView)> on_complete) {}
-
- virtual void EnqueueCommand(
- std::unique_ptr<hci::AclCommandBuilder> command,
- common::ContextualOnceCallback<void(hci::CommandStatusView)> on_status) {}
-} fake_command_interface;
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
- FuzzedDataProvider fdp = FuzzedDataProvider(data, size);
- ShimL2capFuzz l2shim(&fdp);
-
- std::vector<uint8_t> addressVals = fdp.ConsumeBytes<uint8_t>(Address::kLength);
-
- // Make sure the address is always at least kLength.
- while (addressVals.size() < Address::kLength) {
- addressVals.push_back(0);
- }
- Address myAddress;
- myAddress.FromOctets(addressVals.data());
- hci::AddressWithType addressWithType = hci::AddressWithType(myAddress, AddressType::PUBLIC_DEVICE_ADDRESS);
-
- // Associate a ClassicAclConnection so that we can grab a link.
- auto throwaway_queue = std::make_shared<AclConnection::Queue>(10);
- l2shim.link_manager->OnConnectSuccess(std::unique_ptr<ClassicAclConnection>(
- new ClassicAclConnection(throwaway_queue, &fake_command_interface, 0, myAddress)));
- Link* link = l2shim.link_manager->GetLink(myAddress);
-
- // 0x0001-0x007F Fixed, 0x0080-0x00FF Dynamic
- uint16_t psm = fdp.ConsumeIntegralInRange<uint16_t>(0x0001, 0x007F);
- psm = 0x0101u ^ 0x0100u;
- uint16_t dynamicPsm = fdp.ConsumeIntegralInRange<uint16_t>(0x0080, 0x00FF);
- dynamicPsm = 0x0101u ^ 0x0100u;
-
- // Open a connection and assign an ID
- Cid fixedCid = l2cap::kLeSignallingCid;
-
- // Fixed channels must be acquired.
- auto fixedChannel = link->AllocateFixedChannel(fixedCid);
- fixedChannel->RegisterOnCloseCallback(l2shim.handler_.get(), common::BindOnce([](hci::ErrorCode) {}));
- fixedChannel->Acquire();
- ChannelFuzzController fixedChannelController(l2shim.handler_.get(), fixedChannel);
- // Generate a valid dynamic channel ID
- Cid dynamicCid = fdp.ConsumeIntegralInRange<uint16_t>(l2cap::kFirstDynamicChannel, l2cap::kLastDynamicChannel);
- auto dynamicChannel = link->AllocateDynamicChannel(dynamicPsm, dynamicCid);
- ChannelFuzzController dynamicChannelController(l2shim.handler_.get(), dynamicChannel);
-
- while (fdp.remaining_bytes() > 0) {
- // Are we using the dynamic queue?
- bool dynamic = fdp.ConsumeBool();
-
- // Consume at most UINT16_MAX or remaining_bytes, whatever is smaller.
- uint16_t packetSize =
- static_cast<uint16_t>(std::min(static_cast<size_t>(fdp.ConsumeIntegral<uint16_t>()), fdp.remaining_bytes()));
- std::vector<uint8_t> data = fdp.ConsumeBytes<uint8_t>(packetSize);
- if (dynamic) {
- dynamicChannelController.injectFrame(data);
- } else {
- fixedChannelController.injectFrame(data);
- }
- }
-
- // Cleanup stuff.
- fixedChannel->Release();
- dynamicChannel->Close();
- l2shim.stopRegistry();
- link->OnAclDisconnected(hci::ErrorCode::SUCCESS);
- l2shim.link_manager->OnDisconnect(myAddress, hci::ErrorCode::SUCCESS);
- return 0;
-}
-} // namespace bluetooth
diff --git a/gd/l2cap/fuzz/fuzz_l2cap_classic_module.h b/gd/l2cap/fuzz/fuzz_l2cap_classic_module.h
deleted file mode 100755
index 8028f94ac..000000000
--- a/gd/l2cap/fuzz/fuzz_l2cap_classic_module.h
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-// Authors: corbin.souffrant@leviathansecurity.com
-// dylan.katz@leviathansecurity.com
-
-#pragma once
-
-#include <fuzzer/FuzzedDataProvider.h>
-
-#include "l2cap/classic/dynamic_channel_manager.h"
-#include "l2cap/classic/l2cap_classic_module.h"
-
-#include "fuzz_dynamic_channel_manager.h"
-#include "fuzz_dynamic_channel_manager_impl.h"
-
-namespace bluetooth {
-namespace shim {
-namespace {
-class FuzzL2capClassicModule : public l2cap::classic::L2capClassicModule {
- public:
- std::unique_ptr<l2cap::classic::DynamicChannelManager> GetDynamicChannelManager() override {
- return std::make_unique<FuzzDynamicChannelManager>(*impl_);
- }
-
- void ListDependencies(ModuleList*) override {}
- void Start() override;
- void Stop() override;
-
- std::unique_ptr<FuzzDynamicChannelManagerImpl> impl_;
-};
-
-void FuzzL2capClassicModule::Start() {
- impl_ = std::make_unique<FuzzDynamicChannelManagerImpl>();
-}
-
-void FuzzL2capClassicModule::Stop() {
- impl_.reset();
-}
-} // namespace
-} // namespace shim
-} // namespace bluetooth
diff --git a/gd/l2cap/fuzz/shim_l2cap.h b/gd/l2cap/fuzz/shim_l2cap.h
deleted file mode 100755
index 1d59f866e..000000000
--- a/gd/l2cap/fuzz/shim_l2cap.h
+++ /dev/null
@@ -1,106 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-// Authors: corbin.souffrant@leviathansecurity.com
-// dylan.katz@leviathansecurity.com
-
-#pragma once
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <gd/l2cap/classic/internal/dynamic_channel_service_manager_impl.h>
-#include <gd/l2cap/classic/internal/fixed_channel_service_manager_impl.h>
-#include <gd/l2cap/classic/internal/link_manager.h>
-#include <gd/l2cap/internal/parameter_provider.h>
-#include <future>
-#include <memory>
-
-#include "hci/fuzz/fuzz_hci_layer.h"
-#include "l2cap/classic/l2cap_classic_module.h"
-#include "os/handler.h"
-
-#include "fuzz_l2cap_classic_module.h"
-
-namespace bluetooth {
-
-namespace shim {
-namespace {
-class ShimL2capFuzz {
- public:
- uint16_t CreateConnection(uint16_t psm, hci::Address device_address) {
- std::promise<uint16_t> promise;
- auto future = promise.get_future();
-
- fuzz_l2cap_classic_module_->GetDynamicChannelManager()->ConnectChannel(
- device_address,
- {},
- psm,
- handler_->BindOn(this, &ShimL2capFuzz::OnConnectionComplete),
- handler_->BindOnceOn(this, &ShimL2capFuzz::OnConnectionFail));
-
- return future.get();
- }
-
- void OnConnectionComplete(std::unique_ptr<l2cap::classic::DynamicChannel> channel) {}
-
- void OnConnectionFail(l2cap::classic::DynamicChannelManager::ConnectionResult result) {}
-
- ShimL2capFuzz(FuzzedDataProvider* fdp) {
- hci::fuzz::FuzzHciLayer* fuzzHci = fake_registry_.Inject<hci::fuzz::FuzzHciLayer>(&hci::HciLayer::Factory);
- fuzz_l2cap_classic_module_ = new FuzzL2capClassicModule();
- fake_registry_.InjectTestModule(&l2cap::classic::L2capClassicModule::Factory, fuzz_l2cap_classic_module_);
- fake_registry_.Start<l2cap::classic::L2capClassicModule>();
-
- // The autoreply is needed to prevent it from hanging.
- fuzzHci->TurnOnAutoReply(fdp);
- acl_manager_ = fake_registry_.Start<hci::AclManager>();
- fuzzHci->TurnOffAutoReply();
-
- // Create the LinkManager
- handler_ = std::unique_ptr<os::Handler>(new os::Handler(&thread_));
- dynamic_channel_impl = std::unique_ptr<l2cap::classic::internal::DynamicChannelServiceManagerImpl>(
- new l2cap::classic::internal::DynamicChannelServiceManagerImpl(handler_.get()));
- fixed_channel_impl = std::unique_ptr<l2cap::classic::internal::FixedChannelServiceManagerImpl>(
- new l2cap::classic::internal::FixedChannelServiceManagerImpl(handler_.get()));
- parameter_provider = std::unique_ptr<l2cap::internal::ParameterProvider>(new l2cap::internal::ParameterProvider());
- link_manager = std::unique_ptr<l2cap::classic::internal::LinkManager>(new l2cap::classic::internal::LinkManager(
- handler_.get(), acl_manager_, fixed_channel_impl.get(), dynamic_channel_impl.get(), parameter_provider.get()));
- }
-
- ~ShimL2capFuzz() {
- handler_->Clear();
- }
-
- void stopRegistry() {
- fake_registry_.WaitForIdleAndStopAll();
- }
-
- std::promise<void> connection_complete_promise_;
-
- FuzzL2capClassicModule* fuzz_l2cap_classic_module_{nullptr};
- hci::AclManager* acl_manager_{nullptr};
-
- std::unique_ptr<os::Handler> handler_;
- std::unique_ptr<l2cap::classic::internal::FixedChannelServiceManagerImpl> fixed_channel_impl;
- std::unique_ptr<l2cap::classic::internal::DynamicChannelServiceManagerImpl> dynamic_channel_impl;
- std::unique_ptr<l2cap::classic::internal::LinkManager> link_manager;
- std::unique_ptr<l2cap::internal::ParameterProvider> parameter_provider;
-
- private:
- FuzzTestModuleRegistry fake_registry_;
- os::Thread& thread_ = fake_registry_.GetTestThread();
-};
-} // namespace
-} // namespace shim
-} // namespace bluetooth
diff --git a/gd/l2cap/internal/basic_mode_channel_data_controller.cc b/gd/l2cap/internal/basic_mode_channel_data_controller.cc
index 90ebfab68..0badf0e64 100644
--- a/gd/l2cap/internal/basic_mode_channel_data_controller.cc
+++ b/gd/l2cap/internal/basic_mode_channel_data_controller.cc
@@ -27,10 +27,6 @@ BasicModeDataController::BasicModeDataController(Cid cid, Cid remote_cid, UpperQ
: cid_(cid), remote_cid_(remote_cid), enqueue_buffer_(channel_queue_end), handler_(handler), scheduler_(scheduler) {
}
-BasicModeDataController::~BasicModeDataController() {
- enqueue_buffer_.Clear();
-}
-
void BasicModeDataController::OnSdu(std::unique_ptr<packet::BasePacketBuilder> sdu) {
auto l2cap_information = BasicFrameBuilder::Create(remote_cid_, std::move(sdu));
pdu_queue_.emplace(std::move(l2cap_information));
diff --git a/gd/l2cap/internal/basic_mode_channel_data_controller.h b/gd/l2cap/internal/basic_mode_channel_data_controller.h
index ae4e508b9..8e40402f8 100644
--- a/gd/l2cap/internal/basic_mode_channel_data_controller.h
+++ b/gd/l2cap/internal/basic_mode_channel_data_controller.h
@@ -44,8 +44,6 @@ class BasicModeDataController : public DataController {
BasicModeDataController(Cid cid, Cid remote_cid, UpperQueueDownEnd* channel_queue_end, os::Handler* handler,
Scheduler* scheduler);
- ~BasicModeDataController();
-
void OnSdu(std::unique_ptr<packet::BasePacketBuilder> sdu) override;
void OnPdu(packet::PacketView<true> pdu) override;
diff --git a/gd/l2cap/internal/data_pipeline_manager.cc b/gd/l2cap/internal/data_pipeline_manager.cc
index e3fe89b8e..8fd40fbc0 100644
--- a/gd/l2cap/internal/data_pipeline_manager.cc
+++ b/gd/l2cap/internal/data_pipeline_manager.cc
@@ -36,14 +36,10 @@ void DataPipelineManager::AttachChannel(Cid cid, std::shared_ptr<ChannelImpl> ch
void DataPipelineManager::DetachChannel(Cid cid) {
ASSERT(sender_map_.find(cid) != sender_map_.end());
sender_map_.erase(cid);
- scheduler_->RemoveChannel(cid);
- scheduler_->SetChannelTxPriority(cid, false);
}
DataController* DataPipelineManager::GetDataController(Cid cid) {
- if (sender_map_.find(cid) == sender_map_.end()) {
- return nullptr;
- };
+ ASSERT(sender_map_.find(cid) != sender_map_.end());
return sender_map_.find(cid)->second.GetDataController();
}
@@ -57,11 +53,6 @@ void DataPipelineManager::UpdateClassicConfiguration(Cid cid, classic::internal:
sender_map_.find(cid)->second.UpdateClassicConfiguration(config);
}
-void DataPipelineManager::SetChannelTxPriority(Cid cid, bool high_priority) {
- ASSERT(sender_map_.find(cid) != sender_map_.end());
- scheduler_->SetChannelTxPriority(cid, high_priority);
-}
-
} // namespace internal
} // namespace l2cap
} // namespace bluetooth
diff --git a/gd/l2cap/internal/data_pipeline_manager.h b/gd/l2cap/internal/data_pipeline_manager.h
index 104f49ec7..0424de9ca 100644
--- a/gd/l2cap/internal/data_pipeline_manager.h
+++ b/gd/l2cap/internal/data_pipeline_manager.h
@@ -66,15 +66,14 @@ class DataPipelineManager {
virtual DataController* GetDataController(Cid cid);
virtual void OnPacketSent(Cid cid);
virtual void UpdateClassicConfiguration(Cid cid, classic::internal::ChannelConfigurationState config);
- virtual void SetChannelTxPriority(Cid cid, bool high_priority);
virtual ~DataPipelineManager() = default;
private:
os::Handler* handler_;
ILink* link_;
- std::unordered_map<Cid, Sender> sender_map_;
std::unique_ptr<Scheduler> scheduler_;
Receiver receiver_;
+ std::unordered_map<Cid, Sender> sender_map_;
};
} // namespace internal
} // namespace l2cap
diff --git a/gd/l2cap/internal/dynamic_channel_allocator.cc b/gd/l2cap/internal/dynamic_channel_allocator.cc
index 881249238..1b3447138 100644
--- a/gd/l2cap/internal/dynamic_channel_allocator.cc
+++ b/gd/l2cap/internal/dynamic_channel_allocator.cc
@@ -18,16 +18,19 @@
#include "l2cap/cid.h"
#include "l2cap/classic/internal/link.h"
-#include "l2cap/classic/security_policy.h"
#include "l2cap/internal/dynamic_channel_allocator.h"
#include "l2cap/internal/dynamic_channel_impl.h"
+#include "l2cap/security_policy.h"
#include "os/log.h"
namespace bluetooth {
namespace l2cap {
namespace internal {
-std::shared_ptr<DynamicChannelImpl> DynamicChannelAllocator::AllocateChannel(Psm psm, Cid remote_cid) {
+std::shared_ptr<DynamicChannelImpl> DynamicChannelAllocator::AllocateChannel(Psm psm, Cid remote_cid,
+ SecurityPolicy security_policy) {
+ ASSERT_LOG(IsPsmValid(psm), "Psm 0x%x is invalid", psm);
+
if (used_remote_cid_.find(remote_cid) != used_remote_cid_.end()) {
LOG_INFO("Remote cid 0x%x is used", remote_cid);
return nullptr;
@@ -51,7 +54,10 @@ std::shared_ptr<DynamicChannelImpl> DynamicChannelAllocator::AllocateChannel(Psm
}
std::shared_ptr<DynamicChannelImpl> DynamicChannelAllocator::AllocateReservedChannel(Cid reserved_cid, Psm psm,
- Cid remote_cid) {
+ Cid remote_cid,
+ SecurityPolicy security_policy) {
+ ASSERT_LOG(IsPsmValid(psm), "Psm 0x%x is invalid", psm);
+
if (used_remote_cid_.find(remote_cid) != used_remote_cid_.end()) {
LOG_INFO("Remote cid 0x%x is used", remote_cid);
return nullptr;
@@ -82,7 +88,7 @@ void DynamicChannelAllocator::FreeChannel(Cid cid) {
used_cid_.erase(cid);
auto channel = FindChannelByCid(cid);
if (channel == nullptr) {
- LOG_INFO("Channel is not in use: cid %d, device %s", cid, link_->GetDevice().ToString().c_str());
+ LOG_INFO("Channel is not in use: psm %d, device %s", cid, link_->GetDevice().ToString().c_str());
return;
}
used_remote_cid_.erase(channel->GetRemoteCid());
diff --git a/gd/l2cap/internal/dynamic_channel_allocator.h b/gd/l2cap/internal/dynamic_channel_allocator.h
index 1d56d444f..09a358837 100644
--- a/gd/l2cap/internal/dynamic_channel_allocator.h
+++ b/gd/l2cap/internal/dynamic_channel_allocator.h
@@ -21,21 +21,14 @@
#include "hci/acl_manager.h"
#include "l2cap/cid.h"
-#include "l2cap/classic/security_policy.h"
#include "l2cap/internal/ilink.h"
#include "l2cap/psm.h"
+#include "l2cap/security_policy.h"
#include "os/handler.h"
#include "os/log.h"
namespace bluetooth {
namespace l2cap {
-
-namespace classic {
-namespace internal {
-class DumpsysHelper;
-} // namespace internal
-} // namespace classic
-
namespace internal {
class DynamicChannelImpl;
@@ -52,15 +45,16 @@ class DynamicChannelAllocator {
// Allocates a channel. If psm is used, OR the remote cid already exists, return nullptr.
// NOTE: The returned DynamicChannelImpl object is still owned by the channel allocator, NOT the client.
- std::shared_ptr<DynamicChannelImpl> AllocateChannel(Psm psm, Cid remote_cid);
+ std::shared_ptr<DynamicChannelImpl> AllocateChannel(Psm psm, Cid remote_cid, SecurityPolicy security_policy);
- std::shared_ptr<DynamicChannelImpl> AllocateReservedChannel(Cid reserved_cid, Psm psm, Cid remote_cid);
+ std::shared_ptr<DynamicChannelImpl> AllocateReservedChannel(Cid reserved_cid, Psm psm, Cid remote_cid,
+ SecurityPolicy security_policy);
// Gives an unused Cid to be used for opening a channel. If a channel is used, call AllocateReservedChannel. If no
// longer needed, use FreeChannel.
Cid ReserveChannel();
- // Frees a channel (existing or reserved)
+ // Frees a channel. If psm doesn't exist, it will crash
void FreeChannel(Cid cid);
bool IsPsmUsed(Psm psm) const;
@@ -74,7 +68,6 @@ class DynamicChannelAllocator {
void OnAclDisconnected(hci::ErrorCode hci_status);
private:
- friend class bluetooth::l2cap::classic::internal::DumpsysHelper;
l2cap::internal::ILink* link_;
os::Handler* l2cap_handler_;
std::unordered_set<Cid> used_cid_;
diff --git a/gd/l2cap/internal/dynamic_channel_allocator_fuzz_test.cc b/gd/l2cap/internal/dynamic_channel_allocator_fuzz_test.cc
index be46086a8..c3821dcca 100644
--- a/gd/l2cap/internal/dynamic_channel_allocator_fuzz_test.cc
+++ b/gd/l2cap/internal/dynamic_channel_allocator_fuzz_test.cc
@@ -25,7 +25,7 @@ namespace l2cap {
namespace internal {
using classic::internal::testing::MockLink;
-using hci::testing::MockClassicAclConnection;
+using hci::testing::MockAclConnection;
using l2cap::internal::testing::MockParameterProvider;
using l2cap::internal::testing::MockScheduler;
using ::testing::NiceMock;
@@ -46,8 +46,8 @@ class L2capClassicDynamicChannelAllocatorFuzzTest {
thread_ = new os::Thread("test_thread", os::Thread::Priority::NORMAL);
handler_ = new os::Handler(thread_);
mock_parameter_provider_ = new NiceMock<MockParameterProvider>();
- mock_classic_link_ = new NiceMock<MockLink>(handler_, mock_parameter_provider_,
- std::make_unique<NiceMock<MockClassicAclConnection>>(), nullptr);
+ mock_classic_link_ =
+ new NiceMock<MockLink>(handler_, mock_parameter_provider_, std::make_unique<NiceMock<MockAclConnection>>());
EXPECT_CALL(*mock_classic_link_, GetDevice()).WillRepeatedly(Return(device));
channel_allocator_ = std::make_unique<DynamicChannelAllocator>(mock_classic_link_, handler_);
}
@@ -83,4 +83,4 @@ class L2capClassicDynamicChannelAllocatorFuzzTest {
void RunL2capClassicDynamicChannelAllocatorFuzzTest(const uint8_t* data, size_t size) {
bluetooth::l2cap::internal::L2capClassicDynamicChannelAllocatorFuzzTest test;
test.RunTests(data, size);
-}
+} \ No newline at end of file
diff --git a/gd/l2cap/internal/dynamic_channel_allocator_test.cc b/gd/l2cap/internal/dynamic_channel_allocator_test.cc
index 566e2c406..4fc01601d 100644
--- a/gd/l2cap/internal/dynamic_channel_allocator_test.cc
+++ b/gd/l2cap/internal/dynamic_channel_allocator_test.cc
@@ -66,7 +66,7 @@ TEST_F(L2capClassicDynamicChannelAllocatorTest, precondition) {
TEST_F(L2capClassicDynamicChannelAllocatorTest, allocate_and_free_channel) {
Psm psm = 0x03;
Cid remote_cid = kFirstDynamicChannel;
- auto channel = channel_allocator_->AllocateChannel(psm, remote_cid);
+ auto channel = channel_allocator_->AllocateChannel(psm, remote_cid, {});
Cid local_cid = channel->GetCid();
EXPECT_TRUE(channel_allocator_->IsPsmUsed(psm));
EXPECT_EQ(channel, channel_allocator_->FindChannelByCid(local_cid));
@@ -78,7 +78,7 @@ TEST_F(L2capClassicDynamicChannelAllocatorTest, reserve_channel) {
Psm psm = 0x03;
Cid remote_cid = kFirstDynamicChannel;
Cid reserved = channel_allocator_->ReserveChannel();
- auto channel = channel_allocator_->AllocateReservedChannel(reserved, psm, remote_cid);
+ auto channel = channel_allocator_->AllocateReservedChannel(reserved, psm, remote_cid, {});
Cid local_cid = channel->GetCid();
EXPECT_EQ(local_cid, reserved);
EXPECT_TRUE(channel_allocator_->IsPsmUsed(psm));
diff --git a/gd/l2cap/internal/dynamic_channel_impl.cc b/gd/l2cap/internal/dynamic_channel_impl.cc
index 6a3ecc5d8..947a32f0e 100644
--- a/gd/l2cap/internal/dynamic_channel_impl.cc
+++ b/gd/l2cap/internal/dynamic_channel_impl.cc
@@ -18,10 +18,10 @@
#include "l2cap/cid.h"
#include "l2cap/classic/internal/link.h"
-#include "l2cap/classic/security_policy.h"
#include "l2cap/internal/dynamic_channel_impl.h"
#include "l2cap/internal/sender.h"
#include "l2cap/psm.h"
+#include "l2cap/security_policy.h"
#include "os/handler.h"
#include "os/log.h"
@@ -33,31 +33,30 @@ DynamicChannelImpl::DynamicChannelImpl(Psm psm, Cid cid, Cid remote_cid, l2cap::
os::Handler* l2cap_handler)
: psm_(psm), cid_(cid), remote_cid_(remote_cid), link_(link), l2cap_handler_(l2cap_handler),
device_(link->GetDevice()) {
+ ASSERT(IsPsmValid(psm_));
ASSERT(cid_ > 0);
ASSERT(remote_cid_ > 0);
ASSERT(link_ != nullptr);
ASSERT(l2cap_handler_ != nullptr);
}
-hci::AddressWithType DynamicChannelImpl::GetDevice() const {
- return device_;
+hci::Address DynamicChannelImpl::GetDevice() const {
+ return device_.GetAddress();
}
-void DynamicChannelImpl::RegisterOnCloseCallback(DynamicChannel::OnCloseCallback on_close_callback) {
- ASSERT_LOG(on_close_callback_.IsEmpty(), "OnCloseCallback can only be registered once");
+void DynamicChannelImpl::RegisterOnCloseCallback(os::Handler* user_handler,
+ DynamicChannel::OnCloseCallback on_close_callback) {
+ ASSERT_LOG(user_handler_ == nullptr, "OnCloseCallback can only be registered once");
// If channel is already closed, call the callback immediately without saving it
if (closed_) {
- on_close_callback.Invoke(close_reason_);
+ user_handler->Post(common::BindOnce(std::move(on_close_callback), close_reason_));
return;
}
+ user_handler_ = user_handler;
on_close_callback_ = std::move(on_close_callback);
}
void DynamicChannelImpl::Close() {
- if (link_ == nullptr) {
- LOG_ERROR("Channel is already closed");
- return;
- }
link_->SendDisconnectionRequest(cid_, remote_cid_);
}
@@ -68,8 +67,13 @@ void DynamicChannelImpl::OnClosed(hci::ErrorCode status) {
close_reason_ = status;
link_ = nullptr;
l2cap_handler_ = nullptr;
- on_close_callback_.InvokeIfNotEmpty(close_reason_);
- on_close_callback_ = {};
+ if (user_handler_ == nullptr) {
+ return;
+ }
+ // On close callback can only be called once
+ user_handler_->Post(common::BindOnce(std::move(on_close_callback_), status));
+ user_handler_ = nullptr;
+ on_close_callback_.Reset();
}
std::string DynamicChannelImpl::ToString() {
diff --git a/gd/l2cap/internal/dynamic_channel_impl.h b/gd/l2cap/internal/dynamic_channel_impl.h
index a012fff2d..856e21d24 100644
--- a/gd/l2cap/internal/dynamic_channel_impl.h
+++ b/gd/l2cap/internal/dynamic_channel_impl.h
@@ -38,9 +38,9 @@ class DynamicChannelImpl : public l2cap::internal::ChannelImpl {
virtual ~DynamicChannelImpl() = default;
- hci::AddressWithType GetDevice() const;
+ hci::Address GetDevice() const;
- virtual void RegisterOnCloseCallback(DynamicChannel::OnCloseCallback on_close_callback);
+ virtual void RegisterOnCloseCallback(os::Handler* user_handler, DynamicChannel::OnCloseCallback on_close_callback);
virtual void Close();
virtual void OnClosed(hci::ErrorCode status);
@@ -66,10 +66,6 @@ class DynamicChannelImpl : public l2cap::internal::ChannelImpl {
return psm_;
}
- virtual void SetChannelTxPriority(bool high_priority) {
- link_->SetChannelTxPriority(cid_, high_priority);
- }
-
// TODO(cmanton) Do something a little bit better than this
bool local_initiated_{false};
@@ -82,12 +78,13 @@ class DynamicChannelImpl : public l2cap::internal::ChannelImpl {
const hci::AddressWithType device_;
// User supported states
+ os::Handler* user_handler_ = nullptr;
DynamicChannel::OnCloseCallback on_close_callback_{};
// Internal states
bool closed_ = false;
hci::ErrorCode close_reason_ = hci::ErrorCode::SUCCESS;
- static constexpr size_t kChannelQueueSize = 5;
+ static constexpr size_t kChannelQueueSize = 10;
common::BidiQueue<packet::PacketView<packet::kLittleEndian>, packet::BasePacketBuilder> channel_queue_{
kChannelQueueSize};
diff --git a/gd/l2cap/internal/dynamic_channel_impl_test.cc b/gd/l2cap/internal/dynamic_channel_impl_test.cc
index 7469869b9..677b50491 100644
--- a/gd/l2cap/internal/dynamic_channel_impl_test.cc
+++ b/gd/l2cap/internal/dynamic_channel_impl_test.cc
@@ -58,14 +58,6 @@ class L2capClassicDynamicChannelImplTest : public ::testing::Test {
os::Handler* l2cap_handler_ = nullptr;
};
-class StatusCapture {
- public:
- hci::ErrorCode value = hci::ErrorCode::SUCCESS;
- void capture(hci::ErrorCode status) {
- value = status;
- }
-};
-
TEST_F(L2capClassicDynamicChannelImplTest, get_device) {
MockParameterProvider mock_parameter_provider;
MockLink mock_classic_link(l2cap_handler_, &mock_parameter_provider);
@@ -73,7 +65,7 @@ TEST_F(L2capClassicDynamicChannelImplTest, get_device) {
EXPECT_CALL(mock_classic_link, GetDevice()).WillRepeatedly(Return(device));
DynamicChannelImpl dynamic_channel_impl(0x01, kFirstDynamicChannel, kFirstDynamicChannel, &mock_classic_link,
l2cap_handler_);
- EXPECT_EQ(device, dynamic_channel_impl.GetDevice());
+ EXPECT_EQ(device.GetAddress(), dynamic_channel_impl.GetDevice());
}
TEST_F(L2capClassicDynamicChannelImplTest, close_triggers_callback) {
@@ -86,16 +78,16 @@ TEST_F(L2capClassicDynamicChannelImplTest, close_triggers_callback) {
// Register on close callback
auto user_handler = std::make_unique<os::Handler>(thread_);
- StatusCapture* my_status = new StatusCapture();
- dynamic_channel_impl.RegisterOnCloseCallback(user_handler->BindOnceOn(my_status, &StatusCapture::capture));
+ hci::ErrorCode my_status = hci::ErrorCode::SUCCESS;
+ dynamic_channel_impl.RegisterOnCloseCallback(
+ user_handler.get(), common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { my_status = status; }));
// Channel closure should trigger such callback
dynamic_channel_impl.OnClosed(hci::ErrorCode::REMOTE_USER_TERMINATED_CONNECTION);
SyncHandler(user_handler.get());
- EXPECT_EQ(hci::ErrorCode::REMOTE_USER_TERMINATED_CONNECTION, my_status->value);
+ EXPECT_EQ(hci::ErrorCode::REMOTE_USER_TERMINATED_CONNECTION, my_status);
user_handler->Clear();
- delete my_status;
}
TEST_F(L2capClassicDynamicChannelImplTest, register_callback_after_close_should_call_immediately) {
@@ -111,14 +103,13 @@ TEST_F(L2capClassicDynamicChannelImplTest, register_callback_after_close_should_
// Register on close callback should trigger callback immediately
auto user_handler = std::make_unique<os::Handler>(thread_);
- StatusCapture* my_status = new StatusCapture();
- dynamic_channel_impl.RegisterOnCloseCallback(user_handler->BindOnceOn(my_status, &StatusCapture::capture));
-
+ hci::ErrorCode my_status = hci::ErrorCode::SUCCESS;
+ dynamic_channel_impl.RegisterOnCloseCallback(
+ user_handler.get(), common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { my_status = status; }));
SyncHandler(user_handler.get());
- EXPECT_EQ(hci::ErrorCode::REMOTE_USER_TERMINATED_CONNECTION, my_status->value);
+ EXPECT_EQ(hci::ErrorCode::REMOTE_USER_TERMINATED_CONNECTION, my_status);
user_handler->Clear();
- delete my_status;
}
TEST_F(L2capClassicDynamicChannelImplTest, close_twice_should_fail) {
@@ -131,19 +122,19 @@ TEST_F(L2capClassicDynamicChannelImplTest, close_twice_should_fail) {
// Register on close callback
auto user_handler = std::make_unique<os::Handler>(thread_);
- StatusCapture* my_status = new StatusCapture();
- dynamic_channel_impl.RegisterOnCloseCallback(user_handler->BindOnceOn(my_status, &StatusCapture::capture));
+ hci::ErrorCode my_status = hci::ErrorCode::SUCCESS;
+ dynamic_channel_impl.RegisterOnCloseCallback(
+ user_handler.get(), common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { my_status = status; }));
// Channel closure should trigger such callback
dynamic_channel_impl.OnClosed(hci::ErrorCode::REMOTE_USER_TERMINATED_CONNECTION);
SyncHandler(user_handler.get());
- EXPECT_EQ(hci::ErrorCode::REMOTE_USER_TERMINATED_CONNECTION, my_status->value);
+ EXPECT_EQ(hci::ErrorCode::REMOTE_USER_TERMINATED_CONNECTION, my_status);
// 2nd OnClose() callback should fail
EXPECT_DEATH(dynamic_channel_impl.OnClosed(hci::ErrorCode::PAGE_TIMEOUT), ".*OnClosed.*");
user_handler->Clear();
- delete my_status;
}
TEST_F(L2capClassicDynamicChannelImplTest, multiple_registeration_should_fail) {
@@ -156,15 +147,15 @@ TEST_F(L2capClassicDynamicChannelImplTest, multiple_registeration_should_fail) {
// Register on close callback
auto user_handler = std::make_unique<os::Handler>(thread_);
- StatusCapture* my_status = new StatusCapture();
- dynamic_channel_impl.RegisterOnCloseCallback(user_handler->BindOnceOn(my_status, &StatusCapture::capture));
+ hci::ErrorCode my_status = hci::ErrorCode::SUCCESS;
+ dynamic_channel_impl.RegisterOnCloseCallback(
+ user_handler.get(), common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { my_status = status; }));
- EXPECT_DEATH(
- dynamic_channel_impl.RegisterOnCloseCallback(user_handler->BindOnce([](hci::ErrorCode status) { FAIL(); })),
- ".*RegisterOnCloseCallback.*");
+ EXPECT_DEATH(dynamic_channel_impl.RegisterOnCloseCallback(user_handler.get(),
+ common::BindOnce([](hci::ErrorCode status) { FAIL(); })),
+ ".*RegisterOnCloseCallback.*");
user_handler->Clear();
- delete my_status;
}
} // namespace internal
diff --git a/gd/l2cap/internal/enhanced_retransmission_mode_channel_data_controller.cc b/gd/l2cap/internal/enhanced_retransmission_mode_channel_data_controller.cc
index 9f1c4e3b7..e57f70872 100644
--- a/gd/l2cap/internal/enhanced_retransmission_mode_channel_data_controller.cc
+++ b/gd/l2cap/internal/enhanced_retransmission_mode_channel_data_controller.cc
@@ -34,9 +34,7 @@ ErtmController::ErtmController(ILink* link, Cid cid, Cid remote_cid, UpperQueueD
: link_(link), cid_(cid), remote_cid_(remote_cid), enqueue_buffer_(channel_queue_end), handler_(handler),
scheduler_(scheduler), pimpl_(std::make_unique<impl>(this, handler)) {}
-ErtmController::~ErtmController() {
- enqueue_buffer_.Clear();
-}
+ErtmController::~ErtmController() = default;
struct ErtmController::impl {
impl(ErtmController* controller, os::Handler* handler)
@@ -167,7 +165,6 @@ struct ErtmController::impl {
send_rr_or_rnr(Poll::POLL);
start_monitor_timer();
} else if (tx_state_ == TxState::WAIT_F) {
- LOG_INFO("Close channel because max transmit reached");
CloseChannel();
}
}
@@ -246,7 +243,7 @@ struct ErtmController::impl {
void recv_rr(uint8_t req_seq, Poll p = Poll::NOT_SET, Final f = Final::NOT_SET) {
if (rx_state_ == RxState::RECV) {
- if (p == Poll::NOT_SET && f == Final::NOT_SET && with_valid_req_seq(req_seq) && with_valid_f_bit(f)) {
+ if (p == Poll::NOT_SET && f == Final::NOT_SET && with_valid_req_seq_rr(req_seq) && with_valid_f_bit(f)) {
pass_to_tx(req_seq, f);
if (remote_busy() && unacked_frames_ > 0) {
start_retrans_timer();
@@ -265,7 +262,7 @@ struct ErtmController::impl {
} else if (p == Poll::POLL && with_valid_req_seq(req_seq) && with_valid_f_bit(f)) {
pass_to_tx(req_seq, f);
send_i_or_rr_or_rnr(Final::POLL_RESPONSE);
- } else if (with_invalid_req_seq(req_seq)) {
+ } else if (with_invalid_req_seq_rr(req_seq)) {
CloseChannel();
}
} else if (rx_state_ == RxState::REJ_SENT) {
@@ -278,7 +275,7 @@ struct ErtmController::impl {
rej_actioned_ = false;
}
send_pending_i_frames();
- } else if (p == Poll::NOT_SET && f == Final::NOT_SET && with_valid_req_seq(req_seq) && with_valid_f_bit(f)) {
+ } else if (p == Poll::NOT_SET && f == Final::NOT_SET && with_valid_req_seq_rr(req_seq) && with_valid_f_bit(f)) {
pass_to_tx(req_seq, f);
if (remote_busy() and unacked_frames_ > 0) {
start_retrans_timer();
@@ -292,7 +289,7 @@ struct ErtmController::impl {
}
remote_busy_ = false;
send_rr(Final::POLL_RESPONSE);
- } else if (with_invalid_req_seq(req_seq)) {
+ } else if (with_invalid_req_seq_rr(req_seq)) {
CloseChannel();
}
} else if (rx_state_ == RxState::SREJ_SENT) {
@@ -412,7 +409,6 @@ struct ErtmController::impl {
remote_busy_ = false;
pass_to_tx(req_seq, f);
retransmit_requested_i_frame(req_seq, p);
- send_pending_i_frames();
if (p_bit_outstanding()) {
srej_actioned_ = true;
srej_save_req_seq_ = req_seq;
@@ -490,30 +486,16 @@ struct ErtmController::impl {
return retry_count_ < controller_->local_max_transmit_;
}
- // Compares two sequence numbers (tx_seq or rx_seq)
- bool sequence_less_than(uint8_t x, uint8_t y) {
- // Assuming the maximum overflow of sequence number is the same as local_tx_window_ (10 by default).
- return x < y || kMaxTxWin - (x - y) < controller_->local_tx_window_;
- }
-
- // Compares two sequence numbers (tx_seq or rx_seq)
- bool sequence_less_than_or_equal(uint8_t x, uint8_t y) {
- // Assuming the maximum overflow of sequence number is the same as local_tx_window_ (10 by default).
- return x <= y || kMaxTxWin - (x - y) <= controller_->local_tx_window_;
- }
-
bool with_expected_tx_seq(uint8_t tx_seq) {
return tx_seq == expected_tx_seq_;
}
bool with_valid_req_seq(uint8_t req_seq) {
- return sequence_less_than_or_equal(expected_ack_seq_, req_seq) &&
- sequence_less_than_or_equal(req_seq, next_tx_seq_);
+ return expected_ack_seq_ <= req_seq && req_seq <= next_tx_seq_;
}
bool with_valid_req_seq_retrans(uint8_t req_seq) {
- return sequence_less_than_or_equal(expected_ack_seq_, req_seq) &&
- sequence_less_than_or_equal(req_seq, next_tx_seq_);
+ return expected_ack_seq_ <= req_seq && req_seq <= next_tx_seq_;
}
bool with_valid_f_bit(Final f) {
@@ -521,32 +503,38 @@ struct ErtmController::impl {
}
bool with_unexpected_tx_seq(uint8_t tx_seq) {
- return sequence_less_than(expected_tx_seq_, tx_seq) &&
- sequence_less_than_or_equal(tx_seq, expected_tx_seq_ + controller_->local_tx_window_);
+ return tx_seq > expected_tx_seq_ && tx_seq <= expected_tx_seq_ + controller_->local_tx_window_;
}
bool with_duplicate_tx_seq(uint8_t tx_seq) {
- return sequence_less_than(tx_seq, expected_tx_seq_) &&
- sequence_less_than_or_equal(expected_tx_seq_ - controller_->local_tx_window_, tx_seq);
+ return tx_seq < expected_tx_seq_ && tx_seq >= expected_tx_seq_ - controller_->local_tx_window_;
}
bool with_invalid_tx_seq(uint8_t tx_seq) {
- return sequence_less_than(tx_seq, expected_tx_seq_ - controller_->local_tx_window_) ||
- sequence_less_than(expected_tx_seq_ + controller_->local_tx_window_, tx_seq);
+ return tx_seq < expected_tx_seq_ - controller_->local_tx_window_ ||
+ tx_seq > expected_tx_seq_ + controller_->local_tx_window_;
}
bool with_invalid_req_seq(uint8_t req_seq) {
- return sequence_less_than(req_seq, expected_ack_seq_) || sequence_less_than(next_tx_seq_, req_seq);
+ return req_seq < expected_ack_seq_ || req_seq > next_tx_seq_;
}
bool with_invalid_req_seq_retrans(uint8_t req_seq) {
- return sequence_less_than(req_seq, expected_ack_seq_) || sequence_less_than(next_tx_seq_, req_seq);
+ return req_seq < expected_ack_seq_ || req_seq >= next_tx_seq_;
}
bool not_with_expected_tx_seq(uint8_t tx_seq) {
return !with_invalid_tx_seq(tx_seq) && !with_expected_tx_seq(tx_seq);
}
+ bool with_valid_req_seq_rr(uint8_t req_seq) {
+ return expected_ack_seq_ < req_seq && req_seq <= next_tx_seq_;
+ }
+
+ bool with_invalid_req_seq_rr(uint8_t req_seq) {
+ return req_seq <= expected_ack_seq_ || req_seq > next_tx_seq_;
+ }
+
bool with_expected_tx_seq_srej() {
// We don't support sending SREJ
return false;
@@ -623,7 +611,6 @@ struct ErtmController::impl {
retry_i_frames_[i] = 0;
}
unacked_frames_ -= ((req_seq - expected_ack_seq_) + kMaxTxWin) % kMaxTxWin;
- expected_ack_seq_ = req_seq;
if (unacked_frames_ == 0) {
stop_retrans_timer();
}
@@ -653,7 +640,6 @@ struct ErtmController::impl {
void send_rnr(Final f) {
_send_s_frame(SupervisoryFunction::RECEIVER_NOT_READY, expected_tx_seq_, Poll::NOT_SET, f);
- rnr_sent_ = true;
}
void send_rej(Poll p = Poll::NOT_SET, Final f = Final::NOT_SET) {
@@ -741,7 +727,7 @@ struct ErtmController::impl {
}
void store_or_ignore() {
- // We choose to ignore.
+ // We choose to ignore. We don't support local busy so far.
}
bool p_bit_outstanding() {
@@ -813,9 +799,7 @@ struct ErtmController::impl {
void ErtmController::OnSdu(std::unique_ptr<packet::BasePacketBuilder> sdu) {
auto sdu_size = sdu->size();
std::vector<std::unique_ptr<packet::RawBuilder>> segments;
- auto size_each_packet = (remote_mps_ - 4 /* basic L2CAP header */ - 2 /* SDU length */ - 2 /* Enhanced control */ -
- (fcs_enabled_ ? 2 : 0));
- packet::FragmentingInserter fragmenting_inserter(size_each_packet, std::back_insert_iterator(segments));
+ packet::FragmentingInserter fragmenting_inserter(size_each_packet_, std::back_insert_iterator(segments));
sdu->Serialize(fragmenting_inserter);
fragmenting_inserter.finalize();
if (segments.size() == 1) {
@@ -965,8 +949,6 @@ std::unique_ptr<packet::BasePacketBuilder> ErtmController::GetNextPacket() {
void ErtmController::stage_for_reassembly(SegmentationAndReassembly sar, uint16_t sdu_size,
const packet::PacketView<kLittleEndian>& payload) {
- // If EnqueueBuffer has more than 1 packets, we claim LocalBusy, until queue is empty
- constexpr size_t kEnqueueBufferBusyThreshold = 3;
switch (sar) {
case SegmentationAndReassembly::UNSEGMENTED:
if (sar_state_ != SegmentationAndReassembly::END) {
@@ -976,10 +958,6 @@ void ErtmController::stage_for_reassembly(SegmentationAndReassembly sar, uint16_
}
// TODO: Enforce MTU
enqueue_buffer_.Enqueue(std::make_unique<packet::PacketView<kLittleEndian>>(payload), handler_);
- if (enqueue_buffer_.Size() == kEnqueueBufferBusyThreshold) {
- pimpl_->local_busy_detected();
- enqueue_buffer_.NotifyOnEmpty(common::BindOnce(&impl::local_busy_clear, common::Unretained(pimpl_.get())));
- }
break;
case SegmentationAndReassembly::START:
if (sar_state_ != SegmentationAndReassembly::END) {
@@ -1011,18 +989,13 @@ void ErtmController::stage_for_reassembly(SegmentationAndReassembly sar, uint16_
remaining_sdu_continuation_packet_size_ -= payload.size();
if (remaining_sdu_continuation_packet_size_ != 0) {
LOG_WARN("Received invalid END I-Frame");
- reassembly_stage_ =
- PacketViewForReassembly(PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>()));
+ reassembly_stage_ = PacketViewForReassembly(std::make_shared<std::vector<uint8_t>>());
remaining_sdu_continuation_packet_size_ = 0;
close_channel();
return;
}
reassembly_stage_.AppendPacketView(payload);
enqueue_buffer_.Enqueue(std::make_unique<packet::PacketView<kLittleEndian>>(reassembly_stage_), handler_);
- if (enqueue_buffer_.Size() == kEnqueueBufferBusyThreshold) {
- pimpl_->local_busy_detected();
- enqueue_buffer_.NotifyOnEmpty(common::BindOnce(&impl::local_busy_clear, common::Unretained(pimpl_.get())));
- }
break;
}
}
@@ -1042,7 +1015,6 @@ void ErtmController::SetRetransmissionAndFlowControlOptions(
local_max_transmit_ = option.max_transmit_;
local_retransmit_timeout_ms_ = option.retransmission_time_out_;
local_monitor_timeout_ms_ = option.monitor_time_out_;
- remote_mps_ = option.maximum_pdu_size_;
}
void ErtmController::close_channel() {
diff --git a/gd/l2cap/internal/enhanced_retransmission_mode_channel_data_controller.h b/gd/l2cap/internal/enhanced_retransmission_mode_channel_data_controller.h
index 1a0c36270..184d6c160 100644
--- a/gd/l2cap/internal/enhanced_retransmission_mode_channel_data_controller.h
+++ b/gd/l2cap/internal/enhanced_retransmission_mode_channel_data_controller.h
@@ -72,6 +72,9 @@ class ErtmController : public DataController {
uint16_t remote_tx_window_ = 10;
uint16_t remote_mps_ = 1010;
+ uint16_t size_each_packet_ =
+ (remote_mps_ - 4 /* basic L2CAP header */ - 2 /* SDU length */ - 2 /* Extended control */ - 2 /* FCS */);
+
class PacketViewForReassembly : public packet::PacketView<kLittleEndian> {
public:
PacketViewForReassembly(const PacketView& packetView) : PacketView(packetView) {}
@@ -92,7 +95,7 @@ class ErtmController : public DataController {
std::shared_ptr<packet::RawBuilder> builder_;
};
- PacketViewForReassembly reassembly_stage_{PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>())};
+ PacketViewForReassembly reassembly_stage_{std::make_shared<std::vector<uint8_t>>()};
SegmentationAndReassembly sar_state_ = SegmentationAndReassembly::END;
uint16_t remaining_sdu_continuation_packet_size_ = 0;
diff --git a/gd/l2cap/internal/fixed_channel_allocator.h b/gd/l2cap/internal/fixed_channel_allocator.h
index 14151ca43..b821cb1a3 100644
--- a/gd/l2cap/internal/fixed_channel_allocator.h
+++ b/gd/l2cap/internal/fixed_channel_allocator.h
@@ -21,18 +21,12 @@
#include "hci/hci_packets.h"
#include "l2cap/cid.h"
+#include "l2cap/security_policy.h"
#include "os/handler.h"
#include "os/log.h"
namespace bluetooth {
namespace l2cap {
-
-namespace classic {
-namespace internal {
-class DumpsysHelper;
-} // namespace internal
-} // namespace classic
-
namespace internal {
// Helper class for keeping channels in a Link. It allocates and frees Channel object, and supports querying whether a
@@ -49,7 +43,7 @@ class FixedChannelAllocator {
// Allocates a channel. If cid is used, return nullptr. NOTE: The returned BaseFixedChannelImpl object is still
// owned by the channel allocator, NOT the client.
- virtual std::shared_ptr<FixedChannelImplType> AllocateChannel(Cid cid) {
+ virtual std::shared_ptr<FixedChannelImplType> AllocateChannel(Cid cid, SecurityPolicy security_policy) {
ASSERT_LOG(!IsChannelAllocated((cid)), "Cid 0x%x for link %s is already in use", cid, link_->ToString().c_str());
ASSERT_LOG(cid >= kFirstFixedChannel && cid <= kLastFixedChannel, "Cid %d out of bound", cid);
auto elem = channels_.try_emplace(cid, std::make_shared<FixedChannelImplType>(cid, link_, l2cap_handler_));
@@ -94,7 +88,6 @@ class FixedChannelAllocator {
}
private:
- friend class bluetooth::l2cap::classic::internal::DumpsysHelper;
LinkType* link_;
os::Handler* l2cap_handler_;
std::unordered_map<Cid, std::shared_ptr<FixedChannelImplType>> channels_;
diff --git a/gd/l2cap/internal/fixed_channel_allocator_test.cc b/gd/l2cap/internal/fixed_channel_allocator_test.cc
index 5295cc733..38eac136a 100644
--- a/gd/l2cap/internal/fixed_channel_allocator_test.cc
+++ b/gd/l2cap/internal/fixed_channel_allocator_test.cc
@@ -69,7 +69,7 @@ TEST_F(L2capFixedChannelAllocatorTest, precondition) {
TEST_F(L2capFixedChannelAllocatorTest, allocate_and_free_channel) {
Cid cid = kFirstFixedChannel;
- auto channel = channel_allocator_->AllocateChannel(cid);
+ auto channel = channel_allocator_->AllocateChannel(cid, {});
EXPECT_TRUE(channel_allocator_->IsChannelAllocated(cid));
EXPECT_EQ(channel, channel_allocator_->FindChannel(cid));
ASSERT_NO_FATAL_FAILURE(channel_allocator_->FreeChannel(cid));
diff --git a/gd/l2cap/internal/ilink.h b/gd/l2cap/internal/ilink.h
index dfac77951..abeb2ea89 100644
--- a/gd/l2cap/internal/ilink.h
+++ b/gd/l2cap/internal/ilink.h
@@ -30,17 +30,10 @@ class ILink {
public:
virtual ~ILink() = default;
virtual void SendDisconnectionRequest(Cid local_cid, Cid remote_cid) = 0;
- virtual hci::AddressWithType GetDevice() const = 0;
-
- // Used by sender to indicate whether there is any pending packet to be sent.
- // If there is pending packet, don't delete the link.
- virtual void OnPendingPacketChange(Cid local_cid, bool has_packet) {}
+ virtual hci::AddressWithType GetDevice() = 0;
// To be used by LE credit based channel data controller over LE link
- virtual void SendLeCredit(Cid local_cid, uint16_t credit) {}
-
- // Used by A2dp software encoding
- virtual void SetChannelTxPriority(Cid local_cid, bool high_priority) {}
+ virtual void SendLeCredit(Cid local_cid, uint16_t credit) = 0;
};
} // namespace internal
} // namespace l2cap
diff --git a/gd/l2cap/internal/ilink_mock.h b/gd/l2cap/internal/ilink_mock.h
index 29250f598..18fc62635 100644
--- a/gd/l2cap/internal/ilink_mock.h
+++ b/gd/l2cap/internal/ilink_mock.h
@@ -28,7 +28,7 @@ namespace testing {
class MockILink : public ILink {
public:
- MOCK_METHOD(hci::AddressWithType, GetDevice, (), (const, override));
+ MOCK_METHOD(hci::AddressWithType, GetDevice, (), (override));
MOCK_METHOD(void, SendDisconnectionRequest, (Cid, Cid), (override));
MOCK_METHOD(void, SendLeCredit, (Cid, uint16_t), (override));
};
diff --git a/gd/l2cap/internal/le_credit_based_channel_data_controller.cc b/gd/l2cap/internal/le_credit_based_channel_data_controller.cc
index ca42d1d16..943cb17b2 100644
--- a/gd/l2cap/internal/le_credit_based_channel_data_controller.cc
+++ b/gd/l2cap/internal/le_credit_based_channel_data_controller.cc
@@ -93,7 +93,7 @@ void LeCreditBasedDataController::OnPdu(packet::PacketView<true> pdu) {
enqueue_buffer_.Enqueue(std::make_unique<PacketView<kLittleEndian>>(reassembly_stage_), handler_);
} else if (remaining_sdu_continuation_packet_size_ < 0 || reassembly_stage_.size() > mtu_) {
LOG_WARN("Received larger SDU size than expected");
- reassembly_stage_ = PacketViewForReassembly(PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>()));
+ reassembly_stage_ = PacketViewForReassembly(std::make_shared<std::vector<uint8_t>>());
remaining_sdu_continuation_packet_size_ = 0;
link_->SendDisconnectionRequest(cid_, remote_cid_);
}
@@ -102,7 +102,6 @@ void LeCreditBasedDataController::OnPdu(packet::PacketView<true> pdu) {
}
std::unique_ptr<packet::BasePacketBuilder> LeCreditBasedDataController::GetNextPacket() {
- ASSERT(!pdu_queue_.empty());
auto next = std::move(pdu_queue_.front());
pdu_queue_.pop();
return next;
@@ -124,7 +123,6 @@ void LeCreditBasedDataController::OnCredit(uint16_t credits) {
credits_ = total_credits;
if (pending_frames_count_ > 0 && credits_ >= pending_frames_count_) {
scheduler_->OnPacketsReady(cid_, pending_frames_count_);
- pending_frames_count_ = 0;
credits_ -= pending_frames_count_;
} else if (pending_frames_count_ > 0) {
scheduler_->OnPacketsReady(cid_, credits_);
diff --git a/gd/l2cap/internal/le_credit_based_channel_data_controller.h b/gd/l2cap/internal/le_credit_based_channel_data_controller.h
index 75998c5b7..bbd4c066f 100644
--- a/gd/l2cap/internal/le_credit_based_channel_data_controller.h
+++ b/gd/l2cap/internal/le_credit_based_channel_data_controller.h
@@ -78,7 +78,7 @@ class LeCreditBasedDataController : public DataController {
Append(to_append);
}
};
- PacketViewForReassembly reassembly_stage_{PacketView<kLittleEndian>(std::make_shared<std::vector<uint8_t>>())};
+ PacketViewForReassembly reassembly_stage_{std::make_shared<std::vector<uint8_t>>()};
uint16_t remaining_sdu_continuation_packet_size_ = 0;
};
diff --git a/gd/l2cap/internal/le_credit_based_channel_data_controller_test.cc b/gd/l2cap/internal/le_credit_based_channel_data_controller_test.cc
index ab23dd219..885826ae6 100644
--- a/gd/l2cap/internal/le_credit_based_channel_data_controller_test.cc
+++ b/gd/l2cap/internal/le_credit_based_channel_data_controller_test.cc
@@ -29,7 +29,9 @@ namespace internal {
namespace {
std::unique_ptr<packet::BasePacketBuilder> CreateSdu(std::vector<uint8_t> payload) {
- return std::make_unique<packet::RawBuilder>(std::move(payload));
+ auto raw_builder = std::make_unique<packet::RawBuilder>();
+ raw_builder->AddOctets(payload);
+ return raw_builder;
}
PacketView<kLittleEndian> GetPacketView(std::unique_ptr<packet::BasePacketBuilder> packet) {
diff --git a/gd/l2cap/internal/parameter_provider.h b/gd/l2cap/internal/parameter_provider.h
index bec032248..5de6c545f 100644
--- a/gd/l2cap/internal/parameter_provider.h
+++ b/gd/l2cap/internal/parameter_provider.h
@@ -34,7 +34,7 @@ class ParameterProvider {
return std::chrono::seconds(20);
}
virtual std::chrono::milliseconds GetLeLinkIdleDisconnectTimeout() {
- return std::chrono::seconds(1);
+ return std::chrono::seconds(20);
}
virtual uint16_t GetLeMps() {
return 251;
diff --git a/gd/l2cap/internal/receiver.cc b/gd/l2cap/internal/receiver.cc
index 8af645593..86f43ae85 100644
--- a/gd/l2cap/internal/receiver.cc
+++ b/gd/l2cap/internal/receiver.cc
@@ -33,12 +33,10 @@ Receiver::Receiver(LowerQueueUpEnd* link_queue_up_end, os::Handler* handler,
common::Bind(&Receiver::link_queue_dequeue_callback, common::Unretained(this)));
}
-// Invoked from external handler/thread (ModuleRegistry)
Receiver::~Receiver() {
link_queue_up_end_->UnregisterDequeue();
}
-// Invoked from external (Queue Reactable)
void Receiver::link_queue_dequeue_callback() {
auto packet = link_queue_up_end_->TryDequeue();
auto basic_frame_view = BasicFrameView::Create(*packet);
@@ -49,7 +47,6 @@ void Receiver::link_queue_dequeue_callback() {
Cid cid = static_cast<Cid>(basic_frame_view.GetChannelId());
auto* data_controller = data_pipeline_manager_->GetDataController(cid);
if (data_controller == nullptr) {
- // TODO(b/150170271): Buffer a few packets before data controller is attached
LOG_WARN("Received a packet with invalid cid: %d", cid);
return;
}
diff --git a/gd/l2cap/internal/scheduler.h b/gd/l2cap/internal/scheduler.h
index 281bf8ef9..416c97280 100644
--- a/gd/l2cap/internal/scheduler.h
+++ b/gd/l2cap/internal/scheduler.h
@@ -54,17 +54,6 @@ class Scheduler {
*/
virtual void OnPacketsReady(Cid cid, int number_packets) {}
- /**
- * Let the scheduler send the specified cid first.
- * Used by A2dp software encoding.
- */
- virtual void SetChannelTxPriority(Cid cid, bool high_priority) {}
-
- /**
- * Called by data controller to indicate that a channel is closed and packets should be dropped
- */
- virtual void RemoveChannel(Cid cid) {}
-
virtual ~Scheduler() = default;
};
diff --git a/gd/l2cap/internal/scheduler_fifo.cc b/gd/l2cap/internal/scheduler_fifo.cc
index 110fe0820..8d2a64a1d 100644
--- a/gd/l2cap/internal/scheduler_fifo.cc
+++ b/gd/l2cap/internal/scheduler_fifo.cc
@@ -30,47 +30,20 @@ Fifo::Fifo(DataPipelineManager* data_pipeline_manager, LowerQueueUpEnd* link_que
ASSERT(link_queue_up_end_ != nullptr && handler_ != nullptr);
}
-// Invoked from some external Handler context
Fifo::~Fifo() {
- // TODO(hsz): notify Sender don't send callback to me
- if (link_queue_enqueue_registered_.exchange(false)) {
+ if (link_queue_enqueue_registered_) {
link_queue_up_end_->UnregisterEnqueue();
}
}
-// Invoked within L2CAP Handler context
void Fifo::OnPacketsReady(Cid cid, int number_packets) {
if (number_packets == 0) {
return;
}
- int priority = high_priority_cids_.count(cid) != 0;
- next_to_dequeue_and_num_packets.push(std::make_pair(cid, number_packets), priority);
+ next_to_dequeue_and_num_packets.push(std::make_pair(cid, number_packets));
try_register_link_queue_enqueue();
}
-// Invoked within L2CAP Handler context
-void Fifo::SetChannelTxPriority(Cid cid, bool high_priority) {
- if (high_priority) {
- high_priority_cids_.emplace(cid);
- } else {
- high_priority_cids_.erase(cid);
- }
-}
-
-void Fifo::RemoveChannel(Cid cid) {
- for (int i = 0; i < next_to_dequeue_and_num_packets.size(); i++) {
- auto& channel_id_and_number_packets = next_to_dequeue_and_num_packets.front();
- if (channel_id_and_number_packets.second != cid) {
- next_to_dequeue_and_num_packets.push(channel_id_and_number_packets);
- }
- next_to_dequeue_and_num_packets.pop();
- }
- if (next_to_dequeue_and_num_packets.empty() && link_queue_enqueue_registered_.exchange(false)) {
- link_queue_up_end_->UnregisterEnqueue();
- }
-}
-
-// Invoked from some external Queue Reactable context
std::unique_ptr<Fifo::UpperDequeue> Fifo::link_queue_enqueue_callback() {
ASSERT(!next_to_dequeue_and_num_packets.empty());
auto& channel_id_and_number_packets = next_to_dequeue_and_num_packets.front();
@@ -82,18 +55,20 @@ std::unique_ptr<Fifo::UpperDequeue> Fifo::link_queue_enqueue_callback() {
auto packet = data_pipeline_manager_->GetDataController(channel_id)->GetNextPacket();
data_pipeline_manager_->OnPacketSent(channel_id);
- if (next_to_dequeue_and_num_packets.empty() && link_queue_enqueue_registered_.exchange(false)) {
+ if (next_to_dequeue_and_num_packets.empty()) {
link_queue_up_end_->UnregisterEnqueue();
+ link_queue_enqueue_registered_ = false;
}
return packet;
}
void Fifo::try_register_link_queue_enqueue() {
- if (link_queue_enqueue_registered_.exchange(true)) {
+ if (link_queue_enqueue_registered_) {
return;
}
link_queue_up_end_->RegisterEnqueue(handler_,
common::Bind(&Fifo::link_queue_enqueue_callback, common::Unretained(this)));
+ link_queue_enqueue_registered_ = true;
}
} // namespace internal
diff --git a/gd/l2cap/internal/scheduler_fifo.h b/gd/l2cap/internal/scheduler_fifo.h
index 23a292c6c..f6fcf7f8c 100644
--- a/gd/l2cap/internal/scheduler_fifo.h
+++ b/gd/l2cap/internal/scheduler_fifo.h
@@ -16,14 +16,11 @@
#pragma once
-#include <atomic>
#include <string>
#include <unordered_map>
-#include <unordered_set>
#include "common/bidi_queue.h"
#include "common/bind.h"
-#include "common/multi_priority_queue.h"
#include "l2cap/cid.h"
#include "l2cap/internal/channel_impl.h"
#include "l2cap/internal/scheduler.h"
@@ -39,19 +36,15 @@ class DataPipelineManager;
class Fifo : public Scheduler {
public:
Fifo(DataPipelineManager* data_pipeline_manager, LowerQueueUpEnd* link_queue_up_end, os::Handler* handler);
- ~Fifo();
+ ~Fifo() override;
void OnPacketsReady(Cid cid, int number_packets) override;
- void SetChannelTxPriority(Cid cid, bool high_priority) override;
- void RemoveChannel(Cid cid) override;
private:
DataPipelineManager* data_pipeline_manager_;
LowerQueueUpEnd* link_queue_up_end_;
os::Handler* handler_;
- using ChannelAndNumPackets = std::pair<Cid, int>;
- common::MultiPriorityQueue<ChannelAndNumPackets, 2> next_to_dequeue_and_num_packets;
- std::unordered_set<Cid> high_priority_cids_;
- std::atomic_bool link_queue_enqueue_registered_ = false;
+ std::queue<std::pair<Cid, int>> next_to_dequeue_and_num_packets;
+ bool link_queue_enqueue_registered_ = false;
void try_register_link_queue_enqueue();
std::unique_ptr<LowerEnqueue> link_queue_enqueue_callback();
diff --git a/gd/l2cap/internal/scheduler_fifo_test.cc b/gd/l2cap/internal/scheduler_fifo_test.cc
index 9a0579f14..cafd3b634 100644
--- a/gd/l2cap/internal/scheduler_fifo_test.cc
+++ b/gd/l2cap/internal/scheduler_fifo_test.cc
@@ -18,12 +18,13 @@
#include <gmock/gmock.h>
#include <gtest/gtest.h>
+#include <future>
#include "l2cap/internal/channel_impl_mock.h"
#include "l2cap/internal/data_controller_mock.h"
#include "l2cap/internal/data_pipeline_manager_mock.h"
#include "os/handler.h"
-#include "os/mock_queue.h"
+#include "os/queue.h"
#include "os/thread.h"
#include "packet/raw_builder.h"
@@ -49,116 +50,67 @@ PacketView<kLittleEndian> GetPacketView(std::unique_ptr<packet::BasePacketBuilde
return packet::PacketView<packet::kLittleEndian>(bytes);
}
+void sync_handler(os::Handler* handler) {
+ std::promise<void> promise;
+ auto future = promise.get_future();
+ handler->Post(common::BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)));
+ auto status = future.wait_for(std::chrono::milliseconds(300));
+ EXPECT_EQ(status, std::future_status::ready);
+}
+
class MyDataController : public testing::MockDataController {
public:
std::unique_ptr<BasePacketBuilder> GetNextPacket() override {
- auto next = std::move(next_packets.front());
- next_packets.pop();
- return next;
+ return std::move(next_packet);
}
- std::queue<std::unique_ptr<BasePacketBuilder>> next_packets;
+ std::unique_ptr<BasePacketBuilder> next_packet;
};
class L2capSchedulerFifoTest : public ::testing::Test {
protected:
void SetUp() override {
thread_ = new os::Thread("test_thread", os::Thread::Priority::NORMAL);
+ user_handler_ = new os::Handler(thread_);
queue_handler_ = new os::Handler(thread_);
- mock_data_pipeline_manager_ = new testing::MockDataPipelineManager(queue_handler_, &queue_end_);
- fifo_ = new Fifo(mock_data_pipeline_manager_, &queue_end_, queue_handler_);
+ mock_data_pipeline_manager_ = new testing::MockDataPipelineManager(queue_handler_, link_queue_.GetUpEnd());
+ fifo_ = new Fifo(mock_data_pipeline_manager_, link_queue_.GetUpEnd(), queue_handler_);
}
void TearDown() override {
delete fifo_;
delete mock_data_pipeline_manager_;
queue_handler_->Clear();
+ user_handler_->Clear();
delete queue_handler_;
+ delete user_handler_;
delete thread_;
}
os::Thread* thread_ = nullptr;
+ os::Handler* user_handler_ = nullptr;
os::Handler* queue_handler_ = nullptr;
- os::MockIQueueDequeue<Scheduler::LowerDequeue> dequeue_;
- os::MockIQueueEnqueue<Scheduler::LowerEnqueue> enqueue_;
- common::BidiQueueEnd<Scheduler::LowerEnqueue, Scheduler::LowerDequeue> queue_end_{&enqueue_, &dequeue_};
+ common::BidiQueue<Scheduler::LowerDequeue, Scheduler::LowerEnqueue> link_queue_{10};
testing::MockDataPipelineManager* mock_data_pipeline_manager_ = nullptr;
- MyDataController data_controller_1_;
- MyDataController data_controller_2_;
+ MyDataController data_controller_;
Fifo* fifo_ = nullptr;
};
TEST_F(L2capSchedulerFifoTest, send_packet) {
auto frame = BasicFrameBuilder::Create(1, CreateSdu({'a', 'b', 'c'}));
- data_controller_1_.next_packets.push(std::move(frame));
- EXPECT_CALL(*mock_data_pipeline_manager_, GetDataController(_)).WillOnce(Return(&data_controller_1_));
+ data_controller_.next_packet = std::move(frame);
+ EXPECT_CALL(*mock_data_pipeline_manager_, GetDataController(_)).WillOnce(Return(&data_controller_));
EXPECT_CALL(*mock_data_pipeline_manager_, OnPacketSent(1));
fifo_->OnPacketsReady(1, 1);
- enqueue_.run_enqueue();
- auto&& packet = enqueue_.enqueued.front();
+ sync_handler(queue_handler_);
+ sync_handler(user_handler_);
+ auto packet = link_queue_.GetDownEnd()->TryDequeue();
auto packet_view = GetPacketView(std::move(packet));
auto basic_frame_view = BasicFrameView::Create(packet_view);
- ASSERT_TRUE(basic_frame_view.IsValid());
- ASSERT_EQ(basic_frame_view.GetChannelId(), 1);
- auto payload = basic_frame_view.GetPayload();
- ASSERT_EQ(std::string(payload.begin(), payload.end()), "abc");
- enqueue_.enqueued.pop();
-}
-
-TEST_F(L2capSchedulerFifoTest, prioritize_channel) {
- auto frame = BasicFrameBuilder::Create(1, CreateSdu({'a', 'b', 'c'}));
- data_controller_1_.next_packets.push(std::move(frame));
- frame = BasicFrameBuilder::Create(2, CreateSdu({'d', 'e', 'f'}));
- data_controller_2_.next_packets.push(std::move(frame));
-
- EXPECT_CALL(*mock_data_pipeline_manager_, GetDataController(1)).WillRepeatedly(Return(&data_controller_1_));
- EXPECT_CALL(*mock_data_pipeline_manager_, GetDataController(2)).WillRepeatedly(Return(&data_controller_2_));
- EXPECT_CALL(*mock_data_pipeline_manager_, OnPacketSent(1));
- EXPECT_CALL(*mock_data_pipeline_manager_, OnPacketSent(2));
- fifo_->SetChannelTxPriority(1, true);
- fifo_->OnPacketsReady(2, 1);
- fifo_->OnPacketsReady(1, 1);
- enqueue_.run_enqueue(2);
- auto packet1 = std::move(enqueue_.enqueued.front());
- auto packet_view = GetPacketView(std::move(packet1));
- auto basic_frame_view = BasicFrameView::Create(packet_view);
- ASSERT_TRUE(basic_frame_view.IsValid());
- ASSERT_EQ(basic_frame_view.GetChannelId(), 1);
- auto payload = basic_frame_view.GetPayload();
- ASSERT_EQ(std::string(payload.begin(), payload.end()), "abc");
- enqueue_.enqueued.pop();
-
- auto packet2 = std::move(enqueue_.enqueued.front());
- packet_view = GetPacketView(std::move(packet2));
- basic_frame_view = BasicFrameView::Create(packet_view);
- ASSERT_TRUE(basic_frame_view.IsValid());
- ASSERT_EQ(basic_frame_view.GetChannelId(), 2);
- payload = basic_frame_view.GetPayload();
- ASSERT_EQ(std::string(payload.begin(), payload.end()), "def");
- enqueue_.enqueued.pop();
-}
-
-TEST_F(L2capSchedulerFifoTest, remove_channel) {
- auto frame = BasicFrameBuilder::Create(1, CreateSdu({'a', 'b', 'c'}));
- data_controller_1_.next_packets.push(std::move(frame));
- frame = BasicFrameBuilder::Create(2, CreateSdu({'d', 'e', 'f'}));
- data_controller_2_.next_packets.push(std::move(frame));
-
- EXPECT_CALL(*mock_data_pipeline_manager_, GetDataController(1)).WillRepeatedly(Return(&data_controller_1_));
- EXPECT_CALL(*mock_data_pipeline_manager_, GetDataController(2)).WillRepeatedly(Return(&data_controller_2_));
- EXPECT_CALL(*mock_data_pipeline_manager_, OnPacketSent(2));
- fifo_->OnPacketsReady(1, 1);
- fifo_->OnPacketsReady(2, 1);
- fifo_->RemoveChannel(1);
- enqueue_.run_enqueue(1);
- auto packet1 = std::move(enqueue_.enqueued.front());
- auto packet_view = GetPacketView(std::move(packet1));
- auto basic_frame_view = BasicFrameView::Create(packet_view);
- ASSERT_TRUE(basic_frame_view.IsValid());
- ASSERT_EQ(basic_frame_view.GetChannelId(), 2);
+ EXPECT_TRUE(basic_frame_view.IsValid());
+ EXPECT_EQ(basic_frame_view.GetChannelId(), 1);
auto payload = basic_frame_view.GetPayload();
- ASSERT_EQ(std::string(payload.begin(), payload.end()), "def");
- enqueue_.enqueued.pop();
+ EXPECT_EQ(std::string(payload.begin(), payload.end()), "abc");
}
} // namespace
diff --git a/gd/l2cap/internal/sender.cc b/gd/l2cap/internal/sender.cc
index d9ef716d7..c031cb5ff 100644
--- a/gd/l2cap/internal/sender.cc
+++ b/gd/l2cap/internal/sender.cc
@@ -55,13 +55,12 @@ Sender::Sender(os::Handler* handler, ILink* link, Scheduler* scheduler, std::sha
}
Sender::~Sender() {
- if (is_dequeue_registered_.exchange(false)) {
+ if (is_dequeue_registered_) {
queue_end_->UnregisterDequeue();
}
}
void Sender::OnPacketSent() {
- link_->OnPendingPacketChange(channel_id_, false);
try_register_dequeue();
}
@@ -74,22 +73,19 @@ DataController* Sender::GetDataController() {
}
void Sender::try_register_dequeue() {
- if (is_dequeue_registered_.exchange(true)) {
+ if (is_dequeue_registered_) {
return;
}
queue_end_->RegisterDequeue(handler_, common::Bind(&Sender::dequeue_callback, common::Unretained(this)));
+ is_dequeue_registered_ = true;
}
-// From external context
void Sender::dequeue_callback() {
auto packet = queue_end_->TryDequeue();
ASSERT(packet != nullptr);
- handler_->Post(
- common::BindOnce(&DataController::OnSdu, common::Unretained(data_controller_.get()), std::move(packet)));
- if (is_dequeue_registered_.exchange(false)) {
- queue_end_->UnregisterDequeue();
- }
- link_->OnPendingPacketChange(channel_id_, true);
+ data_controller_->OnSdu(std::move(packet));
+ queue_end_->UnregisterDequeue();
+ is_dequeue_registered_ = false;
}
void Sender::UpdateClassicConfiguration(classic::internal::ChannelConfigurationState config) {
diff --git a/gd/l2cap/internal/sender.h b/gd/l2cap/internal/sender.h
index 3e541a96b..540064f23 100644
--- a/gd/l2cap/internal/sender.h
+++ b/gd/l2cap/internal/sender.h
@@ -16,7 +16,6 @@
#pragma once
-#include <atomic>
#include <string>
#include <unordered_map>
@@ -82,7 +81,7 @@ class Sender {
Scheduler* scheduler_;
const Cid channel_id_;
const Cid remote_channel_id_;
- std::atomic_bool is_dequeue_registered_ = false;
+ bool is_dequeue_registered_ = false;
RetransmissionAndFlowControlModeOption mode_ = RetransmissionAndFlowControlModeOption::L2CAP_BASIC;
std::unique_ptr<DataController> data_controller_;
diff --git a/gd/l2cap/internal/sender_test.cc b/gd/l2cap/internal/sender_test.cc
index 99a9b31d3..bd24fd4fb 100644
--- a/gd/l2cap/internal/sender_test.cc
+++ b/gd/l2cap/internal/sender_test.cc
@@ -21,7 +21,6 @@
#include <future>
#include "l2cap/internal/channel_impl_mock.h"
-#include "l2cap/internal/ilink_mock.h"
#include "l2cap/internal/scheduler.h"
#include "os/handler.h"
#include "os/queue.h"
@@ -78,7 +77,7 @@ class L2capSenderTest : public ::testing::Test {
EXPECT_CALL(*mock_channel_, GetQueueDownEnd()).WillRepeatedly(Return(channel_queue_.GetDownEnd()));
EXPECT_CALL(*mock_channel_, GetCid()).WillRepeatedly(Return(cid_));
EXPECT_CALL(*mock_channel_, GetRemoteCid()).WillRepeatedly(Return(cid_));
- sender_ = new Sender(queue_handler_, &link_, &scheduler_, mock_channel_);
+ sender_ = new Sender(queue_handler_, nullptr, &scheduler_, mock_channel_);
}
void TearDown() override {
@@ -98,7 +97,6 @@ class L2capSenderTest : public ::testing::Test {
Sender* sender_ = nullptr;
Cid cid_ = 0x41;
FakeScheduler scheduler_;
- testing::MockILink link_;
};
TEST_F(L2capSenderTest, send_packet) {
diff --git a/gd/l2cap/l2cap_packet_fuzz_test.cc b/gd/l2cap/l2cap_packet_fuzz_test.cc
index 90bd9653d..6fecafce5 100644
--- a/gd/l2cap/l2cap_packet_fuzz_test.cc
+++ b/gd/l2cap/l2cap_packet_fuzz_test.cc
@@ -46,7 +46,7 @@ DEFINE_AND_REGISTER_ConfigurationRequestReflectionFuzzTest(l2cap_packet_fuzz_tes
} // namespace bluetooth
void RunL2capPacketFuzzTest(const uint8_t* data, size_t size) {
- if (data == nullptr || size > 65536 /* Max ACL packet size */) return;
+ if (data == nullptr) return;
for (auto test_function : bluetooth::l2cap::l2cap_packet_fuzz_tests) {
test_function(data, size);
}
diff --git a/gd/l2cap/l2cap_packet_test.cc b/gd/l2cap/l2cap_packet_test.cc
index 7a413f41c..34645effa 100644
--- a/gd/l2cap/l2cap_packet_test.cc
+++ b/gd/l2cap/l2cap_packet_test.cc
@@ -62,68 +62,6 @@ DEFINE_AND_INSTANTIATE_GroupFrameReflectionTest(g_frame);
std::vector<uint8_t> config_mtu_request = {0x04, 0x05, 0x08, 0x00, 0x41, 0x00, 0x00, 0x00, 0x01, 0x02, 0xa0, 0x02};
DEFINE_AND_INSTANTIATE_ConfigurationRequestReflectionTest(config_mtu_request);
-std::vector<uint8_t> config_request_one_defined_option = {0x04, 0x05, 0x08, 0x00, 0x41, 0x00,
- 0x00, 0x00, 0x01, 0x02, 0x12, 0x34};
-std::vector<uint8_t> config_request_two_defined_options = {0x04, 0x05, 0x0c, 0x00, 0x41, 0x00, 0x00, 0x00,
- 0x01, 0x02, 0x12, 0x34, 0x02, 0x02, 0x56, 0x78};
-std::vector<uint8_t> config_request_two_undefined_options = {0x04, 0x05, 0x0e, 0x00, 0x41, 0x00, 0x00, 0x00, 0x7f,
- 0x02, 0x01, 0x00, 0x7e, 0x04, 0x11, 0x11, 0x00, 0x00};
-std::vector<uint8_t> config_request_hint_one_defined_option = {0x04, 0x05, 0x08, 0x00, 0x41, 0x00,
- 0x00, 0x00, 0x81, 0x02, 0x12, 0x34};
-std::vector<uint8_t> config_request_hint_two_undefined_options = {0x04, 0x05, 0x0c, 0x00, 0x41, 0x00, 0x00, 0x00,
- 0x90, 0x02, 0x01, 0x00, 0x91, 0x02, 0x11, 0x11};
-TEST(L2capPacketsTest, testConfigRequestOptions) {
- {
- std::shared_ptr<std::vector<uint8_t>> view_bytes =
- std::make_shared<std::vector<uint8_t>>(config_request_one_defined_option);
-
- PacketView<kLittleEndian> packet_bytes_view(view_bytes);
- auto view = ConfigurationRequestView::Create(ControlView::Create(packet_bytes_view));
- ASSERT_TRUE(view.IsValid());
- ASSERT_EQ(1, view.GetConfig().size());
- }
-
- {
- std::shared_ptr<std::vector<uint8_t>> view_bytes =
- std::make_shared<std::vector<uint8_t>>(config_request_two_defined_options);
-
- PacketView<kLittleEndian> packet_bytes_view(view_bytes);
- auto view = ConfigurationRequestView::Create(ControlView::Create(packet_bytes_view));
- ASSERT_TRUE(view.IsValid());
- ASSERT_EQ(2, view.GetConfig().size());
- }
-
- {
- std::shared_ptr<std::vector<uint8_t>> view_bytes =
- std::make_shared<std::vector<uint8_t>>(config_request_two_undefined_options);
-
- PacketView<kLittleEndian> packet_bytes_view(view_bytes);
- auto view = ConfigurationRequestView::Create(ControlView::Create(packet_bytes_view));
- ASSERT_TRUE(view.IsValid());
- ASSERT_EQ(2, view.GetConfig().size());
- }
-
- {
- std::shared_ptr<std::vector<uint8_t>> view_bytes =
- std::make_shared<std::vector<uint8_t>>(config_request_hint_one_defined_option);
-
- PacketView<kLittleEndian> packet_bytes_view(view_bytes);
- auto view = ConfigurationRequestView::Create(ControlView::Create(packet_bytes_view));
- ASSERT_TRUE(view.IsValid());
- ASSERT_EQ(1, view.GetConfig().size());
- }
-
- {
- std::shared_ptr<std::vector<uint8_t>> view_bytes =
- std::make_shared<std::vector<uint8_t>>(config_request_hint_two_undefined_options);
-
- PacketView<kLittleEndian> packet_bytes_view(view_bytes);
- auto view = ConfigurationRequestView::Create(ControlView::Create(packet_bytes_view));
- ASSERT_TRUE(view.IsValid());
- ASSERT_EQ(2, view.GetConfig().size());
- }
-}
-
DEFINE_ConfigurationRequestReflectionFuzzTest();
TEST(L2capFuzzRegressions, ConfigurationRequestFuzz_5691566077247488) {
@@ -141,15 +79,5 @@ TEST(L2capFuzzRegressions, ConfigurationRequestFuzz_5747922062802944) {
RunConfigurationRequestReflectionFuzzTest(bluetooth_gd_fuzz_test_5747922062802944,
sizeof(bluetooth_gd_fuzz_test_5747922062802944));
}
-
-TEST(L2capFuzzRegressions, ConfigurationRequestFuzz_5202709231697920) {
- uint8_t bluetooth_gd_fuzz_test_5747922062802944[] = {
- 0x04, 0x01, 0x45, 0x45, 0x05, 0x01, 0x01, 0x45, 0x05, 0x01,
- };
-
- RunConfigurationRequestReflectionFuzzTest(bluetooth_gd_fuzz_test_5747922062802944,
- sizeof(bluetooth_gd_fuzz_test_5747922062802944));
-}
-
} // namespace l2cap
} // namespace bluetooth
diff --git a/gd/l2cap/l2cap_packets.pdl b/gd/l2cap/l2cap_packets.pdl
index b3235da0e..ae44cb1b8 100644
--- a/gd/l2cap/l2cap_packets.pdl
+++ b/gd/l2cap/l2cap_packets.pdl
@@ -227,11 +227,6 @@ enum CommandCode : 8 {
MOVE_CHANNEL_RESPONSE = 0x0F,
MOVE_CHANNEL_CONFIRMATION_REQUEST = 0x10,
MOVE_CHANNEL_CONFIRMATION_RESPONSE = 0x11,
- FLOW_CONTROL_CREDIT = 0x16, // Core 5.2 COC
- CREDIT_BASED_CONNECTION_REQUEST = 0x17,
- CREDIT_BASED_CONNECTION_RESPONSE = 0x18,
- CREDIT_BASED_RECONFIGURE_REQUEST = 0x19,
- CREDIT_BASED_RECONFIGURE_RESPONSE = 0x1A,
}
packet ControlFrame : BasicFrame (channel_id = 0x0001) {
@@ -314,15 +309,15 @@ enum ConfigurationOptionIsHint : 1 {
struct ConfigurationOption {
type : ConfigurationOptionType,
is_hint : ConfigurationOptionIsHint,
- _size_(_body_) : 8,
+ length : 8,
_body_,
}
-struct MtuConfigurationOption : ConfigurationOption (type = MTU) {
+struct MtuConfigurationOption : ConfigurationOption (type = MTU, length = 2) {
mtu : 16,
}
-struct FlushTimeoutConfigurationOption : ConfigurationOption (type = FLUSH_TIMEOUT) {
+struct FlushTimeoutConfigurationOption : ConfigurationOption (type = FLUSH_TIMEOUT, length = 2) {
flush_timeout : 16,
}
@@ -332,7 +327,7 @@ enum QosServiceType : 8 {
GUARANTEED = 0x02,
}
-struct QualityOfServiceConfigurationOption : ConfigurationOption (type = QUALITY_OF_SERVICE) {
+struct QualityOfServiceConfigurationOption : ConfigurationOption (type = QUALITY_OF_SERVICE, length = 22) {
_reserved_ : 8, // Flags
service_type : QosServiceType,
token_rate : 32, // 0 = ignore, 0xffffffff = max available
@@ -351,7 +346,7 @@ enum RetransmissionAndFlowControlModeOption : 8 {
}
-struct RetransmissionAndFlowControlConfigurationOption : ConfigurationOption (type = RETRANSMISSION_AND_FLOW_CONTROL) {
+struct RetransmissionAndFlowControlConfigurationOption : ConfigurationOption (type = RETRANSMISSION_AND_FLOW_CONTROL, length = 9) {
mode : RetransmissionAndFlowControlModeOption,
tx_window_size : 8, // 1-32 for Flow Control and Retransmission, 1-63 for Enhanced
max_transmit : 8,
@@ -365,12 +360,12 @@ enum FcsType : 8 {
DEFAULT = 1, // 16-bit FCS
}
-struct FrameCheckSequenceOption : ConfigurationOption (type = FRAME_CHECK_SEQUENCE) {
+struct FrameCheckSequenceOption : ConfigurationOption (type = FRAME_CHECK_SEQUENCE, length = 1) {
fcs_type : FcsType,
}
-struct ExtendedFlowSpecificationOption : ConfigurationOption (type = EXTENDED_FLOW_SPECIFICATION) {
+struct ExtendedFlowSpecificationOption : ConfigurationOption (type = EXTENDED_FLOW_SPECIFICATION, length = 16) {
identifier : 8, // Default 0x01, must be 0x01 for Extended Flow-Best-Effort
service_type : QosServiceType,
maximum_sdu_size : 16, // Octets
@@ -379,7 +374,7 @@ struct ExtendedFlowSpecificationOption : ConfigurationOption (type = EXTENDED_FL
flush_timeout : 32, // in microseconds 0x0 = no retransmissions 0xFFFFFFFF = never flushed
}
-struct ExtendedWindowSizeOption : ConfigurationOption (type = EXTENDED_WINDOW_SIZE) {
+struct ExtendedWindowSizeOption : ConfigurationOption (type = EXTENDED_WINDOW_SIZE, length = 2) {
max_window_size : 16, // 0x0000 = Valid for streaming, 0x0001-0x3FFF Valid for Enhanced Retransmission
}
@@ -462,8 +457,7 @@ packet InformationResponseExtendedFeatures : InformationResponse (info_type = EX
fixed_channels : 1,
extended_window_size : 1,
unicast_connectionless_data_reception : 1,
- enhanced_credit_based_flow_control_mode : 1,
- _reserved_ : 21,
+ _reserved_ : 22,
}
packet InformationResponseFixedChannels : InformationResponse (info_type = FIXED_CHANNELS_SUPPORTED) {
@@ -535,61 +529,6 @@ packet MoveChannelConfirmationResponse : Control (code = MOVE_CHANNEL_CONFIRMATI
initiator_cid : 16,
}
-// Core 5.2 COC
-
-packet FlowControlCredit : Control (code = FLOW_CONTROL_CREDIT) {
- cid : 16, // Receiver's destination CID
- credits : 16,
-}
-
-packet CreditBasedConnectionRequest : Control (code = CREDIT_BASED_CONNECTION_REQUEST) {
- spsm : 16,
- mtu : 16,
- mps : 16,
- initial_credits : 16,
- source_cid : 16[],
-}
-
-enum CreditBasedConnectionResponseResult : 16 {
- SUCCESS = 0x0000,
- SPSM_NOT_SUPPORTED = 0x0002,
- SOME_REFUSED_NO_RESOURCES_AVAILABLE = 0x0004,
- ALL_REFUSED_INSUFFICIENT_AUTHENTICATION = 0x0005,
- ALL_REFUSED_INSUFFICIENT_AUTHORIZATION = 0x0006,
- ALL_REFUSED_INSUFFICIENT_ENCRYPTION_KEY_SIZE = 0x0007,
- ALL_REFUSED_INSUFFICIENT_ENCRYPTION = 0x0008,
- SOME_REFUSED_INVALID_SOURCE_CID = 0x0009,
- SOME_REFUSED_SOURCE_CID_ALREADY_ALLOCATED = 0x000A,
- ALL_REFUSED_UNACCEPTABLE_PARAMETERS = 0x000B,
- ALL_REFUSED_INVALID_PARAMETERS = 0x000C,
-}
-
-packet CreditBasedConnectionResponse : Control (code = CREDIT_BASED_CONNECTION_RESPONSE) {
- mtu : 16,
- mps : 16,
- initial_credits : 16,
- result : CreditBasedConnectionResponseResult,
- destination_cid : 16[],
-}
-
-packet CreditBasedReconfigureRequest : Control (code = CREDIT_BASED_RECONFIGURE_REQUEST) {
- mtu : 16,
- mps : 16,
- destination_cid : 16[],
-}
-
-enum CreditBasedReconfigureResponseResult : 16 {
- SUCCESS = 0x0000,
- MTU_NOT_ALLOWED = 0x01,
- MPS_NOT_ALLOWED = 0x02,
- INVALID_DESTINATION_CID = 0x03,
- UNACCEPTABLE_PARAMETERS = 0x04,
-}
-
-packet CreditBasedReconfigureResponse : Control (code = CREDIT_BASED_RECONFIGURE_RESPONSE) {
- result: CreditBasedReconfigureResponseResult,
-}
-
enum LeCommandCode : 8 {
COMMAND_REJECT = 0x01,
DISCONNECTION_REQUEST = 0x06,
@@ -599,10 +538,6 @@ enum LeCommandCode : 8 {
LE_CREDIT_BASED_CONNECTION_REQUEST = 0x14,
LE_CREDIT_BASED_CONNECTION_RESPONSE = 0x15,
LE_FLOW_CONTROL_CREDIT = 0x16,
- CREDIT_BASED_CONNECTION_REQUEST = 0x17, // Core 5.2 COC
- CREDIT_BASED_CONNECTION_RESPONSE = 0x18,
- CREDIT_BASED_RECONFIGURE_REQUEST = 0x19,
- CREDIT_BASED_RECONFIGURE_RESPONSE = 0x1A,
}
packet LeControlFrame : BasicFrame (channel_id = 0x0005) {
@@ -647,7 +582,7 @@ packet LeDisconnectionResponse : LeControl (code = DISCONNECTION_RESPONSE) {
packet ConnectionParameterUpdateRequest : LeControl (code = CONNECTION_PARAMETER_UPDATE_REQUEST) {
interval_min : 16,
interval_max : 16,
- peripheral_latency : 16,
+ slave_latency : 16,
timeout_multiplier : 16,
}
@@ -694,28 +629,3 @@ packet LeFlowControlCredit : LeControl (code = LE_FLOW_CONTROL_CREDIT) {
credits : 16,
}
-packet LeEnhancedCreditBasedConnectionRequest : LeControl (code = CREDIT_BASED_CONNECTION_REQUEST) {
- spsm : 16,
- mtu : 16,
- mps : 16,
- initial_credits : 16,
- source_cid : 16[],
-}
-
-packet LeEnhancedCreditBasedConnectionResponse : LeControl (code = CREDIT_BASED_CONNECTION_RESPONSE) {
- mtu : 16,
- mps : 16,
- initial_credits : 16,
- result : CreditBasedConnectionResponseResult,
- destination_cid : 16[],
-}
-
-packet LeEnhancedCreditBasedReconfigureRequest : LeControl (code = CREDIT_BASED_RECONFIGURE_REQUEST) {
- mtu : 16,
- mps : 16,
- destination_cid : 16[],
-}
-
-packet LeEnhancedCreditBasedReconfigureResponse : LeControl (code = CREDIT_BASED_RECONFIGURE_RESPONSE) {
- result: CreditBasedReconfigureResponseResult,
-}
diff --git a/gd/l2cap/le/cert/cert_le_l2cap.py b/gd/l2cap/le/cert/cert_le_l2cap.py
deleted file mode 100644
index fe691a6dd..000000000
--- a/gd/l2cap/le/cert/cert_le_l2cap.py
+++ /dev/null
@@ -1,201 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from cert.closable import Closable
-from cert.closable import safeClose
-from cert.py_le_acl_manager import PyLeAclManager
-from cert.truth import assertThat
-import bluetooth_packets_python3 as bt_packets
-from bluetooth_packets_python3 import l2cap_packets
-from bluetooth_packets_python3.l2cap_packets import LeCommandCode
-from bluetooth_packets_python3.l2cap_packets import LeCreditBasedConnectionResponseResult
-from cert.event_stream import FilteringEventStream
-from cert.event_stream import IEventStream
-from cert.matchers import L2capMatchers
-from cert.captures import L2capCaptures
-from mobly import asserts
-
-
-class CertLeL2capChannel(IEventStream):
-
- def __init__(self, device, scid, dcid, acl_stream, acl, control_channel, initial_credits=0):
- self._device = device
- self._scid = scid
- self._dcid = dcid
- self._acl_stream = acl_stream
- self._acl = acl
- self._control_channel = control_channel
- self._our_acl_view = FilteringEventStream(acl_stream, L2capMatchers.ExtractBasicFrame(scid))
- self._credits_left = initial_credits
-
- def get_event_queue(self):
- return self._our_acl_view.get_event_queue()
-
- def send(self, packet):
- frame = l2cap_packets.BasicFrameBuilder(self._dcid, packet)
- self._acl.send(frame.Serialize())
- self._credits_left -= 1
-
- def send_first_le_i_frame(self, sdu_size, packet):
- frame = l2cap_packets.FirstLeInformationFrameBuilder(self._dcid, sdu_size, packet)
- self._acl.send(frame.Serialize())
- self._credits_left -= 1
-
- def disconnect_and_verify(self):
- assertThat(self._scid).isNotEqualTo(1)
- self._control_channel.send(l2cap_packets.LeDisconnectionRequestBuilder(1, self._dcid, self._scid))
-
- assertThat(self._control_channel).emits(L2capMatchers.LeDisconnectionResponse(self._scid, self._dcid))
-
- def verify_disconnect_request(self):
- assertThat(self._control_channel).emits(L2capMatchers.LeDisconnectionRequest(self._dcid, self._scid))
-
- def send_credits(self, num_credits):
- self._control_channel.send(l2cap_packets.LeFlowControlCreditBuilder(2, self._scid, num_credits))
-
- def credits_left(self):
- return self._credits_left
-
-
-class CertLeL2cap(Closable):
-
- def __init__(self, device):
- self._device = device
- self._le_acl_manager = PyLeAclManager(device)
- self._le_acl = None
-
- self.control_table = {
- LeCommandCode.DISCONNECTION_REQUEST: self._on_disconnection_request_default,
- LeCommandCode.DISCONNECTION_RESPONSE: self._on_disconnection_response_default,
- LeCommandCode.LE_FLOW_CONTROL_CREDIT: self._on_credit,
- }
-
- self._cid_to_cert_channels = {}
-
- def close(self):
- self._le_acl_manager.close()
- safeClose(self._le_acl)
-
- def connect_le_acl(self, remote_addr):
- self._le_acl = self._le_acl_manager.connect_to_remote(remote_addr)
- self.control_channel = CertLeL2capChannel(
- self._device, 5, 5, self._get_acl_stream(), self._le_acl, control_channel=None)
- self._get_acl_stream().register_callback(self._handle_control_packet)
-
- def wait_for_connection(self):
- self._le_acl = self._le_acl_manager.wait_for_connection()
- self.control_channel = CertLeL2capChannel(
- self._device, 5, 5, self._get_acl_stream(), self._le_acl, control_channel=None)
- self._get_acl_stream().register_callback(self._handle_control_packet)
-
- def open_fixed_channel(self, cid=4):
- channel = CertLeL2capChannel(self._device, cid, cid, self._get_acl_stream(), self._le_acl, None, 0)
- return channel
-
- def open_channel(self, signal_id, psm, scid, mtu=1000, mps=100, initial_credit=6):
- self.control_channel.send(
- l2cap_packets.LeCreditBasedConnectionRequestBuilder(signal_id, psm, scid, mtu, mps, initial_credit))
-
- response = L2capCaptures.CreditBasedConnectionResponse()
- assertThat(self.control_channel).emits(response)
- channel = CertLeL2capChannel(self._device, scid,
- response.get().GetDestinationCid(), self._get_acl_stream(), self._le_acl,
- self.control_channel,
- response.get().GetInitialCredits())
- self._cid_to_cert_channels[scid] = channel
- return channel
-
- def open_channel_with_expected_result(self, psm=0x33, result=LeCreditBasedConnectionResponseResult.SUCCESS):
- self.control_channel.send(l2cap_packets.LeCreditBasedConnectionRequestBuilder(1, psm, 0x40, 1000, 100, 6))
-
- response = L2capMatchers.CreditBasedConnectionResponse(result)
- assertThat(self.control_channel).emits(response)
-
- def verify_and_respond_open_channel_from_remote(self,
- psm=0x33,
- result=LeCreditBasedConnectionResponseResult.SUCCESS,
- our_scid=None):
- request = L2capCaptures.CreditBasedConnectionRequest(psm)
- assertThat(self.control_channel).emits(request)
- (scid, dcid) = self._respond_connection_request_default(request.get(), result, our_scid)
- channel = CertLeL2capChannel(self._device, scid, dcid, self._get_acl_stream(), self._le_acl,
- self.control_channel,
- request.get().GetInitialCredits())
- self._cid_to_cert_channels[scid] = channel
- return channel
-
- def verify_and_reject_open_channel_from_remote(self, psm=0x33):
- request = L2capCaptures.CreditBasedConnectionRequest(psm)
- assertThat(self.control_channel).emits(request)
- sid = request.get().GetIdentifier()
- reject = l2cap_packets.LeCommandRejectNotUnderstoodBuilder(sid)
- self.control_channel.send(reject)
-
- def verify_le_flow_control_credit(self, channel):
- assertThat(self.control_channel).emits(L2capMatchers.LeFlowControlCredit(channel._dcid))
-
- def _respond_connection_request_default(self,
- request,
- result=LeCreditBasedConnectionResponseResult.SUCCESS,
- our_scid=None):
- sid = request.GetIdentifier()
- their_scid = request.GetSourceCid()
- mtu = request.GetMtu()
- mps = request.GetMps()
- initial_credits = request.GetInitialCredits()
- # If our_scid is not specified, we use the same value - their scid as their scid
- if our_scid is None:
- our_scid = their_scid
- our_dcid = their_scid
- response = l2cap_packets.LeCreditBasedConnectionResponseBuilder(sid, our_scid, mtu, mps, initial_credits,
- result)
- self.control_channel.send(response)
- return (our_scid, our_dcid)
-
- def get_control_channel(self):
- return self.control_channel
-
- def _get_acl_stream(self):
- return self._le_acl.acl_stream
-
- def _on_disconnection_request_default(self, request):
- disconnection_request = l2cap_packets.LeDisconnectionRequestView(request)
- sid = disconnection_request.GetIdentifier()
- scid = disconnection_request.GetSourceCid()
- dcid = disconnection_request.GetDestinationCid()
- response = l2cap_packets.LeDisconnectionResponseBuilder(sid, dcid, scid)
- self.control_channel.send(response)
-
- def _on_disconnection_response_default(self, request):
- disconnection_response = l2cap_packets.LeDisconnectionResponseView(request)
-
- def _on_credit(self, l2cap_le_control_view):
- credit_view = l2cap_packets.LeFlowControlCreditView(l2cap_le_control_view)
- cid = credit_view.GetCid()
- if cid not in self._cid_to_cert_channels:
- return
- self._cid_to_cert_channels[cid]._credits_left += credit_view.GetCredits()
-
- def _handle_control_packet(self, l2cap_packet):
- packet_bytes = l2cap_packet.payload
- l2cap_view = l2cap_packets.BasicFrameView(bt_packets.PacketViewLittleEndian(list(packet_bytes)))
- if l2cap_view.GetChannelId() != 5:
- return
- request = l2cap_packets.LeControlView(l2cap_view.GetPayload())
- fn = self.control_table.get(request.GetCode())
- if fn is not None:
- fn(request)
- return
diff --git a/gd/l2cap/le/cert/dual_l2cap_test.py b/gd/l2cap/le/cert/dual_l2cap_test.py
deleted file mode 100644
index 00e6392b7..000000000
--- a/gd/l2cap/le/cert/dual_l2cap_test.py
+++ /dev/null
@@ -1,187 +0,0 @@
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from cert.gd_base_test import GdBaseTestClass
-from cert.truth import assertThat
-from cert.py_l2cap import PyLeL2cap, PyL2cap
-from cert.matchers import L2capMatchers
-from cert.metadata import metadata
-from facade import common_pb2 as common
-from google.protobuf import empty_pb2 as empty_proto
-from hci.facade import le_acl_manager_facade_pb2 as le_acl_manager_facade
-from hci.facade import le_advertising_manager_facade_pb2 as le_advertising_facade
-from hci.facade import le_initiator_address_facade_pb2 as le_initiator_address_facade
-import bluetooth_packets_python3 as bt_packets
-from bluetooth_packets_python3 import hci_packets, l2cap_packets
-from l2cap.classic.cert.cert_l2cap import CertL2cap
-from l2cap.le.cert.cert_le_l2cap import CertLeL2cap
-from neighbor.facade import facade_pb2 as neighbor_facade
-
-# Assemble a sample packet.
-SAMPLE_PACKET = bt_packets.RawBuilder([0x19, 0x26, 0x08, 0x17])
-
-
-class DualL2capTest(GdBaseTestClass):
-
- def setup_class(self):
- super().setup_class(dut_module='L2CAP', cert_module='HCI_INTERFACES')
-
- def setup_test(self):
- super().setup_test()
-
- self.dut_address = self.dut.hci_controller.GetMacAddressSimple()
- cert_address = common.BluetoothAddress(
- address=self.cert.controller_read_only_property.ReadLocalAddress(empty_proto.Empty()).address)
-
- self.dut_l2cap = PyL2cap(self.dut, cert_address)
- self.cert_l2cap = CertL2cap(self.cert)
- self.dut_le_l2cap = PyLeL2cap(self.dut)
- self.cert_le_l2cap = CertLeL2cap(self.cert)
- self.dut_le_address = common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes(b'D0:05:04:03:02:01')), type=common.RANDOM_DEVICE_ADDRESS)
- self.cert_address = common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes(b'C0:11:FF:AA:33:22')), type=common.RANDOM_DEVICE_ADDRESS)
- dut_privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_STATIC_ADDRESS,
- address_with_type=self.dut_le_address,
- rotation_irk=b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00',
- minimum_rotation_time=0,
- maximum_rotation_time=0)
- self.dut_l2cap._device.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(dut_privacy_policy)
- privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_STATIC_ADDRESS,
- address_with_type=self.cert_address,
- rotation_irk=b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00',
- minimum_rotation_time=0,
- maximum_rotation_time=0)
- self.cert_le_l2cap._device.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(privacy_policy)
-
- def teardown_test(self):
- self.cert_le_l2cap.close()
- self.dut_le_l2cap.close()
- self.cert_l2cap.close()
- self.dut_l2cap.close()
- super().teardown_test()
-
- def _setup_acl_link_from_cert(self):
- self.dut.neighbor.EnablePageScan(neighbor_facade.EnableMsg(enabled=True))
- self.cert_l2cap.connect_acl(self.dut_address)
-
- def _setup_le_link_from_cert(self):
- # DUT Advertises
- gap_name = hci_packets.GapData()
- gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(b'Im_The_DUT'))
- gap_data = le_advertising_facade.GapDataMsg(data=bytes(gap_name.Serialize()))
- config = le_advertising_facade.AdvertisingConfig(
- advertisement=[gap_data],
- interval_min=512,
- interval_max=768,
- advertising_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
- own_address_type=common.USE_RANDOM_DEVICE_ADDRESS,
- channel_map=7,
- filter_policy=le_advertising_facade.AdvertisingFilterPolicy.ALL_DEVICES)
- request = le_advertising_facade.CreateAdvertiserRequest(config=config)
- create_response = self.dut.hci_le_advertising_manager.CreateAdvertiser(request)
- self.cert_le_l2cap.connect_le_acl(self.dut_le_address)
-
- def _open_le_coc_from_dut(self, psm=0x33, our_scid=None):
- response_future = self.dut_le_l2cap.connect_coc_to_cert(self.cert_address, psm)
- cert_channel = self.cert_le_l2cap.verify_and_respond_open_channel_from_remote(psm=psm, our_scid=our_scid)
- dut_channel = response_future.get_channel()
- return (dut_channel, cert_channel)
-
- def _open_channel_from_dut(self, psm=0x33, our_scid=None):
- dut_channel_future = self.dut_l2cap.connect_dynamic_channel_to_cert(psm)
- cert_channel = self.cert_l2cap.verify_and_respond_open_channel_from_remote(psm=psm, scid=our_scid)
- dut_channel = dut_channel_future.get_channel()
-
- cert_channel.verify_configuration_request_and_respond()
- cert_channel.send_configure_request([])
- cert_channel.verify_configuration_response()
-
- return (dut_channel, cert_channel)
-
- def _open_unconfigured_channel_from_cert(self, signal_id=1, scid=0x0101, psm=0x33):
-
- dut_channel = self.dut_l2cap.register_dynamic_channel(psm)
- cert_channel = self.cert_l2cap.open_channel(signal_id, psm, scid)
-
- return (dut_channel, cert_channel)
-
- def _open_channel_from_cert(self, signal_id=1, scid=0x0101, psm=0x33):
- (dut_channel, cert_channel) = self._open_unconfigured_channel_from_cert(signal_id, scid, psm)
- cert_channel.verify_configuration_request_and_respond()
- cert_channel.send_configure_request([])
- cert_channel.verify_configuration_response()
-
- return (dut_channel, cert_channel)
-
- def _open_le_coc_from_cert(self, signal_id=1, scid=0x0101, psm=0x35, mtu=1000, mps=100, initial_credit=6):
-
- dut_channel = self.dut_le_l2cap.register_coc(self.cert_address, psm)
- cert_channel = self.cert_le_l2cap.open_channel(signal_id, psm, scid, mtu, mps, initial_credit)
-
- return (dut_channel, cert_channel)
-
- @metadata(pts_test_id="L2CAP/LE/CID/BV-01-C", pts_test_name="Receiving DCID over BR/EDR and LE")
- def test_receiving_dcid_over_bredr_and_le(self):
- """
- Test that the L2CAP entity can receive the same DCID in L2CAP connect responses on both the
- BR/EDR and LE links.
- """
- self._setup_acl_link_from_cert()
- # TODO: We should let LE use public address, same as classic link.
- # TODO: Update AclManager::impl::create_le_connection
- self._setup_le_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_dut(0x33, 0x70)
- (le_dut_channel, le_cert_channel) = self._open_le_coc_from_dut(0x35, 0x70)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.Data(b'abc'))
-
- le_dut_channel.send(b'hello')
- assertThat(le_cert_channel).emits(L2capMatchers.FirstLeIFrame(b'hello', sdu_size=5))
-
- le_cert_channel.send_first_le_i_frame(4, SAMPLE_PACKET)
- assertThat(le_dut_channel).emits(L2capMatchers.PacketPayloadRawData(b'\x19\x26\x08\x17'))
-
- cert_channel.disconnect_and_verify()
- le_cert_channel.disconnect_and_verify()
-
- @metadata(pts_test_id="L2CAP/LE/CID/BV-02-C", pts_test_name="Receiving SCID over BR/EDR and LE")
- def test_receiving_scid_over_bredr_and_le(self):
- """
- Test that the L2CAP entity can receive the same SCID in L2CAP connect requests on both the
- BR/EDR and LE links.
- """
- self._setup_acl_link_from_cert()
- # TODO: We should let LE use public address, same as classic link.
- # TODO: Update AclManager::impl::create_le_connection
- self._setup_le_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert(0x33, 0x70)
- (le_dut_channel, le_cert_channel) = self._open_le_coc_from_cert(0x35, 0x70)
-
- dut_channel.send(b'abc')
- assertThat(cert_channel).emits(L2capMatchers.Data(b'abc'))
-
- le_dut_channel.send(b'hello')
- assertThat(le_cert_channel).emits(L2capMatchers.FirstLeIFrame(b'hello', sdu_size=5))
-
- le_cert_channel.send_first_le_i_frame(4, SAMPLE_PACKET)
- assertThat(le_dut_channel).emits(L2capMatchers.PacketPayloadRawData(b'\x19\x26\x08\x17'))
-
- cert_channel.disconnect_and_verify()
- le_cert_channel.disconnect_and_verify()
diff --git a/gd/l2cap/le/cert/le_l2cap_test.py b/gd/l2cap/le/cert/le_l2cap_test.py
deleted file mode 100644
index 80f3aed26..000000000
--- a/gd/l2cap/le/cert/le_l2cap_test.py
+++ /dev/null
@@ -1,571 +0,0 @@
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from cert.gd_base_test import GdBaseTestClass
-from cert.truth import assertThat
-from cert.py_l2cap import PyLeL2cap
-from cert.matchers import L2capMatchers
-from cert.metadata import metadata
-from facade import common_pb2 as common
-from google.protobuf import empty_pb2 as empty_proto
-from hci.facade import le_acl_manager_facade_pb2 as le_acl_manager_facade
-from hci.facade import le_advertising_manager_facade_pb2 as le_advertising_facade
-from hci.facade import le_initiator_address_facade_pb2 as le_initiator_address_facade
-import bluetooth_packets_python3 as bt_packets
-from bluetooth_packets_python3 import hci_packets, l2cap_packets
-from bluetooth_packets_python3.l2cap_packets import LeCreditBasedConnectionResponseResult
-from l2cap.le.cert.cert_le_l2cap import CertLeL2cap
-from l2cap.le.facade_pb2 import SecurityLevel
-
-# Assemble a sample packet.
-SAMPLE_PACKET = bt_packets.RawBuilder([0x19, 0x26, 0x08, 0x17])
-
-
-class LeL2capTest(GdBaseTestClass):
-
- def setup_class(self):
- super().setup_class(dut_module='L2CAP', cert_module='HCI_INTERFACES')
-
- def setup_test(self):
- super().setup_test()
-
- self.dut_l2cap = PyLeL2cap(self.dut)
- self.cert_l2cap = CertLeL2cap(self.cert)
- self.dut_address = common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes(b'D0:05:04:03:02:01')), type=common.RANDOM_DEVICE_ADDRESS)
- self.cert_address = common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes(b'C0:11:FF:AA:33:22')), type=common.RANDOM_DEVICE_ADDRESS)
- dut_privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_STATIC_ADDRESS,
- address_with_type=self.dut_address,
- rotation_irk=b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00',
- minimum_rotation_time=0,
- maximum_rotation_time=0)
- self.dut_l2cap._device.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(dut_privacy_policy)
- privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_STATIC_ADDRESS,
- address_with_type=self.cert_address,
- rotation_irk=b'\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00',
- minimum_rotation_time=0,
- maximum_rotation_time=0)
- self.cert_l2cap._device.hci_le_initiator_address.SetPrivacyPolicyForInitiatorAddress(privacy_policy)
-
- def teardown_test(self):
- self.cert_l2cap.close()
- self.dut_l2cap.close()
- super().teardown_test()
-
- def _setup_link_from_cert(self):
- # DUT Advertises
- gap_name = hci_packets.GapData()
- gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(b'Im_The_DUT'))
- gap_data = le_advertising_facade.GapDataMsg(data=bytes(gap_name.Serialize()))
- config = le_advertising_facade.AdvertisingConfig(
- advertisement=[gap_data],
- interval_min=512,
- interval_max=768,
- advertising_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
- own_address_type=common.USE_RANDOM_DEVICE_ADDRESS,
- channel_map=7,
- filter_policy=le_advertising_facade.AdvertisingFilterPolicy.ALL_DEVICES)
- request = le_advertising_facade.CreateAdvertiserRequest(config=config)
- create_response = self.dut.hci_le_advertising_manager.CreateAdvertiser(request)
- self.cert_l2cap.connect_le_acl(self.dut_address)
-
- def _set_link_from_dut_and_open_channel(self,
- signal_id=1,
- scid=0x0101,
- psm=0x33,
- mtu=1000,
- mps=100,
- initial_credit=6):
- # Cert Advertises
- gap_name = hci_packets.GapData()
- gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(b'Im_The_DUT'))
- gap_data = le_advertising_facade.GapDataMsg(data=bytes(gap_name.Serialize()))
- config = le_advertising_facade.AdvertisingConfig(
- advertisement=[gap_data],
- interval_min=512,
- interval_max=768,
- advertising_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
- own_address_type=common.USE_RANDOM_DEVICE_ADDRESS,
- channel_map=7,
- filter_policy=le_advertising_facade.AdvertisingFilterPolicy.ALL_DEVICES)
- request = le_advertising_facade.CreateAdvertiserRequest(config=config)
- create_response = self.cert.hci_le_advertising_manager.CreateAdvertiser(request)
- response_future = self.dut_l2cap.connect_coc_to_cert(self.cert_address, psm)
- self.cert_l2cap.wait_for_connection()
- # TODO: Currently we can only connect by using Dynamic channel API. Use fixed channel instead.
- cert_channel = self.cert_l2cap.verify_and_respond_open_channel_from_remote(psm)
- dut_channel = response_future.get_channel()
- return (dut_channel, cert_channel)
-
- def _open_channel_from_cert(self, signal_id=1, scid=0x0101, psm=0x33, mtu=1000, mps=100, initial_credit=6):
-
- dut_channel = self.dut_l2cap.register_coc(self.cert_address, psm)
- cert_channel = self.cert_l2cap.open_channel(signal_id, psm, scid, mtu, mps, initial_credit)
-
- return (dut_channel, cert_channel)
-
- def _open_channel_from_dut(self, psm=0x33):
- response_future = self.dut_l2cap.connect_coc_to_cert(self.cert_address, psm)
- cert_channel = self.cert_l2cap.verify_and_respond_open_channel_from_remote(psm)
- dut_channel = response_future.get_channel()
- return (dut_channel, cert_channel)
-
- def _open_fixed_channel(self, cid=4):
- dut_channel = self.dut_l2cap.get_fixed_channel(cid)
- cert_channel = self.cert_l2cap.open_fixed_channel(cid)
- return (dut_channel, cert_channel)
-
- def test_fixed_channel_send(self):
- self.dut_l2cap.enable_fixed_channel(4)
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_fixed_channel(4)
- dut_channel.send(b'hello' * 40)
- assertThat(cert_channel).emits(L2capMatchers.Data(b'hello' * 40))
-
- def test_fixed_channel_receive(self):
- self.dut_l2cap.enable_fixed_channel(4)
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_fixed_channel(4)
- cert_channel.send(SAMPLE_PACKET)
- assertThat(dut_channel).emits(L2capMatchers.PacketPayloadRawData(b'\x19\x26\x08\x17'))
-
- def test_connect_from_dut_and_open_dynamic_channel(self):
- """
- Internal test for GD stack only
- """
- self._set_link_from_dut_and_open_channel()
-
- @metadata(pts_test_id="L2CAP/LE/CPU/BV-01-C", pts_test_name="Send Connection Parameter Update Request")
- def test_send_connection_parameter_update_request(self):
- """
- Verify that the IUT is able to send the connection parameter update Request to Lower Tester when acting as a peripheral device.
- NOTE: This is an optional feature. Also if both LL central and peripheral supports 4.1+ connection parameter update, this should happen in LL only, not L2CAP
- NOTE: Currently we need to establish at least one dynamic channel to allow update.
- """
- self._setup_link_from_cert()
- self._open_channel_from_dut()
- self.dut_l2cap.update_connection_parameter()
- assertThat(self.cert_l2cap.get_control_channel()).emits(L2capMatchers.LeConnectionParameterUpdateRequest())
-
- @metadata(pts_test_id="L2CAP/LE/CPU/BV-02-C", pts_test_name="Accept Connection Parameter Update Request")
- def test_accept_connection_parameter_update_request(self):
- """
- Verify that the IUT is able to receive and handle a request for connection parameter update when acting as a central device.
- NOTE: Currently we need to establish at least one dynamic channel to allow update.
- """
- self._set_link_from_dut_and_open_channel()
- self.cert_l2cap.get_control_channel().send(
- l2cap_packets.ConnectionParameterUpdateRequestBuilder(2, 0x10, 0x10, 0x0a, 0x64))
- assertThat(self.cert_l2cap.get_control_channel()).emits(
- L2capMatchers.LeConnectionParameterUpdateResponse(
- l2cap_packets.ConnectionParameterUpdateResponseResult.ACCEPTED))
-
- @metadata(pts_test_id="L2CAP/LE/CPU/BI-01-C", pts_test_name="Reject Connection Parameter Update Parameters")
- def test_reject_connection_parameter_update_parameters(self):
- """
- Verify that the IUT is able to reject a request for connection parameter update with illegal parameters.
- NOTE: Currently we need to establish at least one dynamic channel to allow update.
- """
- self._set_link_from_dut_and_open_channel()
- self.cert_l2cap.get_control_channel().send(
- l2cap_packets.ConnectionParameterUpdateRequestBuilder(2, 0x10, 0x10, 512, 0x64))
- assertThat(self.cert_l2cap.get_control_channel()).emits(
- L2capMatchers.LeConnectionParameterUpdateResponse(
- l2cap_packets.ConnectionParameterUpdateResponseResult.REJECTED))
-
- @metadata(pts_test_id="L2CAP/LE/CPU/BI-02-C", pts_test_name="Reject Connection Parameter Update Request")
- def test_reject_connection_parameter_update_request(self):
- """
- Verify that the IUT is able to reject a request for connection parameter update in peripheral mode.
- """
- self._setup_link_from_cert()
- self.cert_l2cap.get_control_channel().send(
- l2cap_packets.ConnectionParameterUpdateRequestBuilder(2, 0x10, 0x10, 0x0a, 0x64))
- assertThat(self.cert_l2cap.get_control_channel()).emits(L2capMatchers.LeCommandReject())
-
- @metadata(pts_test_id="L2CAP/COS/CFC/BV-01-C", pts_test_name="Segmentation")
- def test_segmentation(self):
- """
- Verify that the IUT can send data segments which are larger than the LE frame size.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert(mtu=1000, mps=102)
- dut_channel.send(b'hello' * 20 + b'world')
- # The first LeInformation packet contains 2 bytes of SDU size.
- # The packet is divided into first 100 bytes from 'hellohello....'
- # and remaining 5 bytes 'world'
- assertThat(cert_channel).emits(
- L2capMatchers.FirstLeIFrame(b'hello' * 20, sdu_size=105), L2capMatchers.Data(b'world')).inOrder()
-
- @metadata(pts_test_id="L2CAP/COS/CFC/BV-02-C", pts_test_name="No Segmentation")
- def test_no_segmentation(self):
- """
- Verify that the IUT can send data segments which do not require segmentation.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert(mtu=1000, mps=202)
- dut_channel.send(b'hello' * 40)
- assertThat(cert_channel).emits(L2capMatchers.FirstLeIFrame(b'hello' * 40, sdu_size=200))
-
- def test_no_segmentation_dut_is_central(self):
- """
- L2CAP/COS/CFC/BV-02-C
- """
- (dut_channel, cert_channel) = self._set_link_from_dut_and_open_channel()
- dut_channel.send(b'hello' * 40)
- assertThat(cert_channel).emits(L2capMatchers.FirstLeIFrame(b'hello' * 40, sdu_size=200))
-
- @metadata(pts_test_id="L2CAP/COS/CFC/BV-03-C", pts_test_name="Reassembling")
- def test_reassembling(self):
- """
- Verify that the IUT can correctly reassemble data received from the Lower Tester which is greater than the IUT LE-frame size.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- sdu_size_for_two_sample_packet = 8
- cert_channel.send_first_le_i_frame(sdu_size_for_two_sample_packet, SAMPLE_PACKET)
- cert_channel.send(SAMPLE_PACKET)
- assertThat(dut_channel).emits(L2capMatchers.PacketPayloadRawData(b'\x19\x26\x08\x17' * 2))
-
- @metadata(pts_test_id="L2CAP/COS/CFC/BV-04-C", pts_test_name="Data Receiving")
- def test_data_receiving(self):
- """
- Verify that the IUT can receive unsegmented data correctly.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- cert_channel.send_first_le_i_frame(4, SAMPLE_PACKET)
- assertThat(dut_channel).emits(L2capMatchers.PacketPayloadRawData(b'\x19\x26\x08\x17'))
-
- def test_data_receiving_dut_is_central(self):
- """
- L2CAP/COS/CFC/BV-04-C
- """
- (dut_channel, cert_channel) = self._set_link_from_dut_and_open_channel()
- cert_channel.send_first_le_i_frame(4, SAMPLE_PACKET)
- assertThat(dut_channel).emits(L2capMatchers.PacketPayloadRawData(b'\x19\x26\x08\x17'))
-
- @metadata(pts_test_id="L2CAP/COS/CFC/BV-05-C", pts_test_name="Multiple Channels with Interleaved Data Streams")
- def test_multiple_channels_with_interleaved_data_streams(self):
- """
- Verify that an IUT can create multiple channels and receives data streams on the channels when the streams are interleaved.
- """
- self._setup_link_from_cert()
- (dut_channel_x, cert_channel_x) = self._open_channel_from_cert(signal_id=1, scid=0x0103, psm=0x33)
- (dut_channel_y, cert_channel_y) = self._open_channel_from_cert(signal_id=2, scid=0x0105, psm=0x35)
- (dut_channel_z, cert_channel_z) = self._open_channel_from_cert(signal_id=3, scid=0x0107, psm=0x37)
- cert_channel_y.send_first_le_i_frame(4, SAMPLE_PACKET)
- cert_channel_z.send_first_le_i_frame(4, SAMPLE_PACKET)
- cert_channel_y.send_first_le_i_frame(4, SAMPLE_PACKET)
- cert_channel_z.send_first_le_i_frame(4, SAMPLE_PACKET)
- cert_channel_y.send_first_le_i_frame(4, SAMPLE_PACKET)
- # TODO: We should assert two events in order, but it got stuck
- assertThat(dut_channel_y).emits(L2capMatchers.PacketPayloadRawData(b'\x19\x26\x08\x17'), at_least_times=3)
- assertThat(dut_channel_z).emits(
- L2capMatchers.PacketPayloadRawData(b'\x19\x26\x08\x17'),
- L2capMatchers.PacketPayloadRawData(b'\x19\x26\x08\x17')).inOrder()
- cert_channel_z.send_first_le_i_frame(4, SAMPLE_PACKET)
- assertThat(dut_channel_z).emits(L2capMatchers.PacketPayloadRawData(b'\x19\x26\x08\x17'))
-
- @metadata(pts_test_id="L2CAP/LE/REJ/BI-01-C", pts_test_name="Reject Unknown Command in LE Signaling Channel")
- def test_reject_unknown_command_in_le_sigling_channel(self):
- """
- Verify that the IUT is able to reject unknown command.
- """
- self._setup_link_from_cert()
- self.cert_l2cap.get_control_channel().send(
- l2cap_packets.InformationRequestBuilder(
- 2, l2cap_packets.InformationRequestInfoType.EXTENDED_FEATURES_SUPPORTED))
- assertThat(self.cert_l2cap.get_control_channel()).emits(L2capMatchers.LeCommandReject())
-
- @metadata(pts_test_id="L2CAP/LE/REJ/BI-02-C", pts_test_name="Command Reject – Reserved PDU Codes")
- def test_command_reject_reserved_pdu_codes(self):
- """
- Verify that an IUT receiving a PDU with a reserved command code sends a command reject.
- """
- self._setup_link_from_cert()
- self.cert_l2cap.get_control_channel().send(l2cap_packets.MoveChannelRequestBuilder(2, 0, 0))
- assertThat(self.cert_l2cap.get_control_channel()).emits(L2capMatchers.LeCommandReject())
-
- @metadata(pts_test_id="L2CAP/LE/CFC/BV-01-C", pts_test_name="LE Credit Based Connection Request - Legacy Peer")
- def test_le_credit_based_connection_request_legacy_peer(self):
- """
- Verify that an IUT sending an LE Credit Based Connection Request to a legacy peer and receiving a Command Reject does not establish the channel.
- """
- self._setup_link_from_cert()
- response_future = self.dut_l2cap.connect_coc_to_cert(self.cert_address, psm=0x33)
- self.cert_l2cap.verify_and_reject_open_channel_from_remote(psm=0x33)
- assertThat(response_future.get_status()).isNotEqualTo(LeCreditBasedConnectionResponseResult.SUCCESS)
-
- @metadata(
- pts_test_id="L2CAP/LE/CFC/BV-02-C", pts_test_name="LE Credit Based Connection Request on Supported LE_PSM")
- def test_le_credit_based_connection_request_on_supported_le_psm(self):
- """
- Verify that an IUT sending an LE Credit Based Connection Request to a peer will establish the channel upon receiving the LE Credit Based Connection Response.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_dut()
- cert_channel.send_first_le_i_frame(4, SAMPLE_PACKET)
- assertThat(dut_channel).emits(L2capMatchers.PacketPayloadRawData(b'\x19\x26\x08\x17'))
-
- @metadata(
- pts_test_id="L2CAP/LE/CFC/BV-03-C", pts_test_name="LE Credit Based Connection Response on Supported LE_PSM")
- def test_credit_based_connection_response_on_supported_le_psm(self):
- """
- Verify that an IUT receiving a valid LE Credit Based Connection Request from a peer will send an LE Credit Based Connection Response and establish the channel.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- dut_channel.send(b'hello')
- assertThat(cert_channel).emits(L2capMatchers.FirstLeIFrame(b'hello', sdu_size=5))
-
- @metadata(
- pts_test_id="L2CAP/LE/CFC/BV-04-C", pts_test_name="LE Credit Based Connection Request on an Unsupported LE_PSM")
- def test_credit_based_connection_request_on_an_unsupported_le_psm(self):
- """
- Verify that an IUT sending an LE Credit Based Connection Request on an unsupported LE_PSM will not establish a channel upon receiving an LE Credit Based Connection Response refusing the connection.
- """
- self._setup_link_from_cert()
- response_future = self.dut_l2cap.connect_coc_to_cert(self.cert_address, psm=0x33)
- self.cert_l2cap.verify_and_respond_open_channel_from_remote(
- psm=0x33, result=LeCreditBasedConnectionResponseResult.LE_PSM_NOT_SUPPORTED)
- assertThat(response_future.get_status()).isEqualTo(LeCreditBasedConnectionResponseResult.LE_PSM_NOT_SUPPORTED)
-
- @metadata(
- pts_test_id="L2CAP/LE/CFC/BV-05-C", pts_test_name="LE Credit Based Connection Request - unsupported LE_PSM")
- def test_credit_based_connection_request_unsupported_le_psm(self):
- """
- Verify that an IUT receiving an LE Credit Based Connection Request on an unsupported LE_PSM will respond with an LE Credit Based Connection Response refusing the connection.
- """
- self._setup_link_from_cert()
- self.cert_l2cap.get_control_channel().send(
- l2cap_packets.LeCreditBasedConnectionRequestBuilder(1, 0x34, 0x0101, 2000, 1000, 1000))
- assertThat(self.cert_l2cap.get_control_channel()).emits(
- L2capMatchers.CreditBasedConnectionResponse(
- result=LeCreditBasedConnectionResponseResult.LE_PSM_NOT_SUPPORTED))
-
- @metadata(pts_test_id="L2CAP/LE/CFC/BV-06-C", pts_test_name="Credit Exchange – Receiving Incremental Credits")
- def test_credit_exchange_receiving_incremental_credits(self):
- """
- Verify the IUT handles flow control correctly, by handling the LE Flow Control Credit sent by the peer.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert(initial_credit=0)
- for _ in range(4):
- dut_channel.send(b'hello')
- cert_channel.send_credits(1)
- assertThat(cert_channel).emits(L2capMatchers.FirstLeIFrame(b'hello', sdu_size=5))
- cert_channel.send_credits(1)
- assertThat(cert_channel).emits(L2capMatchers.FirstLeIFrame(b'hello', sdu_size=5))
- cert_channel.send_credits(2)
- assertThat(cert_channel).emits(
- L2capMatchers.FirstLeIFrame(b'hello', sdu_size=5), L2capMatchers.FirstLeIFrame(b'hello', sdu_size=5))
-
- @metadata(pts_test_id="L2CAP/LE/CFC/BV-07-C", pts_test_name="Credit Exchange – Sending Credits")
- def test_credit_exchange_sending_credits(self):
- """
- Verify that the IUT sends LE Flow Control Credit to the peer.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- credits = cert_channel.credits_left()
- # Note: DUT only needs to send credit when ALL credits are consumed.
- # Here we enforce that DUT sends credit after receiving 3 packets, to
- # test without sending too many packets (may take too long).
- # This behavior is not expected for all Bluetooth stacks.
- for _ in range(min(credits + 1, 3)):
- cert_channel.send_first_le_i_frame(4, SAMPLE_PACKET)
- self.cert_l2cap.verify_le_flow_control_credit(cert_channel)
-
- @metadata(pts_test_id="L2CAP/LE/CFC/BV-08-C", pts_test_name="Disconnection Request")
- def test_disconnection_request(self):
- """
- Verify that the IUT can disconnect the channel.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- dut_channel.close_channel()
- cert_channel.verify_disconnect_request()
-
- @metadata(pts_test_id="L2CAP/LE/CFC/BV-09-C", pts_test_name="Disconnection Response")
- def test_disconnection_response(self):
- """
- Verify that the IUT responds correctly to reception of a Disconnection Request.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- cert_channel.disconnect_and_verify()
-
- @metadata(pts_test_id="L2CAP/LE/CFC/BV-10-C", pts_test_name="Security - Insufficient Authentication – Initiator")
- def test_security_insufficient_authentication_initiator(self):
- """
- Verify that the IUT does not establish the channel upon receipt of an LE Credit Based Connection Response indicating the connection was refused with Result “0x0005 – Connection Refused – Insufficient Authentication".
- """
- self._setup_link_from_cert()
- response_future = self.dut_l2cap.connect_coc_to_cert(self.cert_address, psm=0x33)
- self.cert_l2cap.verify_and_respond_open_channel_from_remote(
- psm=0x33, result=LeCreditBasedConnectionResponseResult.INSUFFICIENT_AUTHENTICATION)
- assertThat(response_future.get_status()).isEqualTo(
- LeCreditBasedConnectionResponseResult.INSUFFICIENT_AUTHENTICATION)
-
- @metadata(pts_test_id="L2CAP/LE/CFC/BV-11-C", pts_test_name="Security - Insufficient Authentication – Responder")
- def test_security_insufficient_authentication_responder(self):
- """
- Verify that an IUT refuses to create a connection upon reception of an LE Credit Based Connection
-Request which fails to satisfy authentication requirements.
- """
- self._setup_link_from_cert()
- psm = 0x33
- self.dut_l2cap.register_coc(self.cert_address, psm, SecurityLevel.AUTHENTICATED_PAIRING_WITH_ENCRYPTION)
- self.cert_l2cap.open_channel_with_expected_result(
- psm, LeCreditBasedConnectionResponseResult.INSUFFICIENT_AUTHENTICATION)
-
- @metadata(pts_test_id="L2CAP/LE/CFC/BV-12-C", pts_test_name="Security - Insufficient Authorization – Initiator")
- def test_security_insufficient_authorization_initiator(self):
- """
- Verify that the IUT does not establish the channel upon receipt of an LE Credit Based Connection Response indicating the connection was refused with Result “0x0006 – Connection Refused – Insufficient Authorizationâ€.
- """
- self._setup_link_from_cert()
- response_future = self.dut_l2cap.connect_coc_to_cert(self.cert_address, psm=0x33)
- self.cert_l2cap.verify_and_respond_open_channel_from_remote(
- psm=0x33, result=LeCreditBasedConnectionResponseResult.INSUFFICIENT_AUTHORIZATION)
- assertThat(response_future.get_status()).isEqualTo(
- LeCreditBasedConnectionResponseResult.INSUFFICIENT_AUTHORIZATION)
-
- @metadata(pts_test_id="L2CAP/LE/CFC/BV-13-C", pts_test_name="Security - Insufficient Authorization – Responder")
- def test_security_insufficient_authorization_responder(self):
- """
- Verify that an IUT refuses to create a connection upon reception of an LE Credit Based Connection
- Request which fails to satisfy authentication requirements.
- """
- self._setup_link_from_cert()
- psm = 0x33
- self.dut_l2cap.register_coc(self.cert_address, psm, SecurityLevel.AUTHORIZATION)
- self.cert_l2cap.open_channel_with_expected_result(
- psm, LeCreditBasedConnectionResponseResult.INSUFFICIENT_AUTHORIZATION)
-
- @metadata(pts_test_id="L2CAP/LE/CFC/BV-14-C", pts_test_name="Security - Insufficient Key Size – Initiator")
- def test_security_insufficient_key_size_initiator(self):
- """
- Verify that the IUT does not establish the channel upon receipt of an
- LE Credit Based Connection Response indicating the connection was
- refused with Result "0x0007 – Connection Refused – Insufficient
- Encryption Key Size".
- """
- self._setup_link_from_cert()
- response_future = self.dut_l2cap.connect_coc_to_cert(self.cert_address, psm=0x33)
- self.cert_l2cap.verify_and_respond_open_channel_from_remote(
- psm=0x33, result=LeCreditBasedConnectionResponseResult.INSUFFICIENT_ENCRYPTION_KEY_SIZE)
- assertThat(response_future.get_status()).isEqualTo(
- LeCreditBasedConnectionResponseResult.INSUFFICIENT_ENCRYPTION_KEY_SIZE)
-
- @metadata(
- pts_test_id="L2CAP/LE/CFC/BV-15-C", pts_test_name="Security - Insufficient Encryption Key Size – Responder")
- def test_security_insufficient_encryption_key_size_responder(self):
- """
- Verify that an IUT refuses to create a connection upon receipt of an LE Credit Based Connection
- Request which fails to satisfy Encryption Key Size requirements.
- """
- self._setup_link_from_cert()
- psm = 0x33
- self.dut_l2cap.register_coc(self.cert_address, psm, SecurityLevel.AUTHENTICATED_PAIRING_WITH_128_BIT_KEY)
- self.cert_l2cap.open_channel_with_expected_result(
- psm, LeCreditBasedConnectionResponseResult.INSUFFICIENT_ENCRYPTION_KEY_SIZE)
-
- @metadata(
- pts_test_id="L2CAP/LE/CFC/BV-16-C",
- pts_test_name="LE Credit Based Connection Request - refuse due to insufficient resources - Initiator")
- def test_le_connection_request_insufficient_resources_initiator(self):
- """
- Verify that an IUT sending an LE Credit Based Connection Request does
- not establish the channel upon receiving an LE Credit Based Connection
- Response refusing the connection with result "0x0004 – Connection
- refused – no resources available".
- """
- self._setup_link_from_cert()
- response_future = self.dut_l2cap.connect_coc_to_cert(self.cert_address, psm=0x33)
- self.cert_l2cap.verify_and_respond_open_channel_from_remote(
- psm=0x33, result=LeCreditBasedConnectionResponseResult.NO_RESOURCES_AVAILABLE)
- assertThat(response_future.get_status()).isEqualTo(LeCreditBasedConnectionResponseResult.NO_RESOURCES_AVAILABLE)
-
- @metadata(
- pts_test_id="L2CAP/LE/CFC/BV-18-C",
- pts_test_name="LE Credit Based Connection Request - refused due to Invalid Source CID - Initiator")
- def test_request_refused_due_to_invalid_source_cid_initiator(self):
- """
- Verify that an IUT sending an LE Credit Based Connection Request does not establish the channel upon receiving an LE Credit Based Connection Response refusing the connection with result "0x0009 – Connection refused – Invalid Source CID".
- """
- self._setup_link_from_cert()
- response_future = self.dut_l2cap.connect_coc_to_cert(self.cert_address, psm=0x33)
- self.cert_l2cap.verify_and_respond_open_channel_from_remote(
- psm=0x33, result=LeCreditBasedConnectionResponseResult.INVALID_SOURCE_CID)
- assertThat(response_future.get_status()).isEqualTo(LeCreditBasedConnectionResponseResult.INVALID_SOURCE_CID)
-
- @metadata(
- pts_test_id="L2CAP/LE/CFC/BV-19-C",
- pts_test_name="LE Credit Based Connection Request - refused due to source CID already allocated - Initiator")
- def test_request_refused_due_to_source_cid_already_allocated_initiator(self):
- """
- Verify that an IUT sending an LE Credit Based Connection Request does not establish the channel upon receiving an LE Credit Based Connection Response refusing the connection with result "0x000A – Connection refused – Source CID already allocated".
- """
- self._setup_link_from_cert()
- response_future = self.dut_l2cap.connect_coc_to_cert(self.cert_address, psm=0x33)
- self.cert_l2cap.verify_and_respond_open_channel_from_remote(
- psm=0x33, result=LeCreditBasedConnectionResponseResult.SOURCE_CID_ALREADY_ALLOCATED)
- assertThat(response_future.get_status()).isEqualTo(
- LeCreditBasedConnectionResponseResult.SOURCE_CID_ALREADY_ALLOCATED)
-
- @metadata(
- pts_test_id="L2CAP/LE/CFC/BV-20-C",
- pts_test_name="LE Credit Based Connection Response - refused due to Source CID already allocated - Responder")
- def test_request_refused_due_to_source_cid_already_allocated_responder(self):
- """
- Verify that an IUT receiving an LE Credit Based Connection Request for a second channel will refuse the connection with result "0x000A - Connection refused – Source CID already allocated" if it receives a Source CID which is already in use.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert(psm=0x33, scid=0x0101)
- self.dut_l2cap.register_coc(self.cert_address, psm=0x35)
- self.cert_l2cap.get_control_channel().send(
- l2cap_packets.LeCreditBasedConnectionRequestBuilder(2, 0x35, 0x0101, 1000, 1000, 1000))
- assertThat(self.cert_l2cap.get_control_channel()).emits(L2capMatchers.CreditBasedConnectionResponseUsedCid())
-
- @metadata(
- pts_test_id="L2CAP/LE/CFC/BV-21-C",
- pts_test_name="LE Credit Based Connection Request - refused due to Unacceptable Parameters - Initiator")
- def test_request_refused_due_to_unacceptable_parameters_initiator(self):
- """
- Verify that an IUT sending an LE Credit Based Connection Request does not establish the channel upon receiving an LE Credit Based Connection Response refusing the connection with result "0x000B – Connection refused – Unacceptable Parameters".
- """
- self._setup_link_from_cert()
- response_future = self.dut_l2cap.connect_coc_to_cert(self.cert_address, psm=0x33)
- self.cert_l2cap.verify_and_respond_open_channel_from_remote(
- psm=0x33, result=LeCreditBasedConnectionResponseResult.UNACCEPTABLE_PARAMETERS)
- assertThat(response_future.get_status()).isEqualTo(
- LeCreditBasedConnectionResponseResult.UNACCEPTABLE_PARAMETERS)
-
- @metadata(pts_test_id="L2CAP/LE/CFC/BI-01-C", pts_test_name="Credit Exchange – Exceed Initial Credits")
- def test_credit_exchange_exceed_initial_credits(self):
- """
- Verify that the IUT disconnects the LE Data Channel when the credit count exceeds 65535.
- """
- self._setup_link_from_cert()
- (dut_channel, cert_channel) = self._open_channel_from_cert()
- cert_channel.send_credits(65535)
- cert_channel.verify_disconnect_request()
diff --git a/gd/l2cap/le/dynamic_channel.cc b/gd/l2cap/le/dynamic_channel.cc
deleted file mode 100644
index 108b65f97..000000000
--- a/gd/l2cap/le/dynamic_channel.cc
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "l2cap/le/dynamic_channel.h"
-#include "l2cap/le/internal/link.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace le {
-LinkOptions* DynamicChannel::GetLinkOptions() {
- return link_->GetLinkOptions();
-}
-
-Mtu DynamicChannel::GetMtu() const {
- return mtu_;
-}
-
-} // namespace le
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/le/dynamic_channel.h b/gd/l2cap/le/dynamic_channel.h
index 988d12aef..db1d82287 100644
--- a/gd/l2cap/le/dynamic_channel.h
+++ b/gd/l2cap/le/dynamic_channel.h
@@ -17,38 +17,12 @@
#pragma once
#include "l2cap/dynamic_channel.h"
-#include "l2cap/le/link_options.h"
-#include "l2cap/mtu.h"
namespace bluetooth {
namespace l2cap {
namespace le {
-namespace internal {
-class Link;
-}
-class DynamicChannel : public l2cap::DynamicChannel {
- public:
- DynamicChannel(
- std::shared_ptr<l2cap::internal::DynamicChannelImpl> impl,
- os::Handler* l2cap_handler,
- internal::Link* link,
- Mtu mtu)
- : l2cap::DynamicChannel(impl, l2cap_handler), link_(link), mtu_(mtu) {}
-
- /**
- * Get the Proxy for L2CAP Link Options.
- * Only few special L2CAP users need to use it, including
- * Hearing Aid Profile and Java API.
- */
- LinkOptions* GetLinkOptions();
-
- Mtu GetMtu() const;
-
- private:
- internal::Link* link_;
- Mtu mtu_;
-};
+using DynamicChannel = l2cap::DynamicChannel;
} // namespace le
} // namespace l2cap
diff --git a/gd/l2cap/le/dynamic_channel_manager.cc b/gd/l2cap/le/dynamic_channel_manager.cc
index 677e92c6f..b8303c1d9 100644
--- a/gd/l2cap/le/dynamic_channel_manager.cc
+++ b/gd/l2cap/le/dynamic_channel_manager.cc
@@ -47,7 +47,6 @@ bool DynamicChannelManager::RegisterService(Psm psm, DynamicChannelConfiguration
OnConnectionOpenCallback on_connection_open, os::Handler* handler) {
internal::DynamicChannelServiceImpl::PendingRegistration pending_registration{
.user_handler_ = handler,
- .security_policy_ = security_policy,
.on_registration_complete_callback_ = std::move(on_registration_complete),
.on_connection_open_callback_ = std::move(on_connection_open),
.configuration_ = configuration_option,
diff --git a/gd/l2cap/le/dynamic_channel_manager.h b/gd/l2cap/le/dynamic_channel_manager.h
index e5334ef13..b57ec2c87 100644
--- a/gd/l2cap/le/dynamic_channel_manager.h
+++ b/gd/l2cap/le/dynamic_channel_manager.h
@@ -23,8 +23,8 @@
#include "l2cap/le/dynamic_channel.h"
#include "l2cap/le/dynamic_channel_configuration_option.h"
#include "l2cap/le/dynamic_channel_service.h"
-#include "l2cap/le/security_policy.h"
#include "l2cap/psm.h"
+#include "l2cap/security_policy.h"
#include "os/handler.h"
namespace bluetooth {
@@ -50,8 +50,7 @@ class DynamicChannelManager {
struct ConnectionResult {
ConnectionResultCode connection_result_code = ConnectionResultCode::SUCCESS;
hci::ErrorCode hci_error = hci::ErrorCode::SUCCESS;
- LeCreditBasedConnectionResponseResult l2cap_connection_response_result =
- LeCreditBasedConnectionResponseResult::SUCCESS;
+ ConnectionResponseResult l2cap_connection_response_result = ConnectionResponseResult::SUCCESS;
};
/**
* OnConnectionFailureCallback(std::string failure_reason);
diff --git a/gd/l2cap/le/dynamic_channel_service.h b/gd/l2cap/le/dynamic_channel_service.h
index 898c885ec..408a20c34 100644
--- a/gd/l2cap/le/dynamic_channel_service.h
+++ b/gd/l2cap/le/dynamic_channel_service.h
@@ -50,6 +50,7 @@ class DynamicChannelService {
protected:
DynamicChannelService(Psm psm, internal::DynamicChannelServiceManagerImpl* manager, os::Handler* handler)
: psm_(psm), manager_(manager), l2cap_layer_handler_(handler) {
+ ASSERT(IsPsmValid(psm));
ASSERT(manager_ != nullptr);
ASSERT(l2cap_layer_handler_ != nullptr);
}
diff --git a/gd/l2cap/le/facade.cc b/gd/l2cap/le/facade.cc
deleted file mode 100644
index 0555e9bf0..000000000
--- a/gd/l2cap/le/facade.cc
+++ /dev/null
@@ -1,447 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "l2cap/le/facade.h"
-
-#include "grpc/grpc_event_queue.h"
-#include "l2cap/le/dynamic_channel.h"
-#include "l2cap/le/dynamic_channel_manager.h"
-#include "l2cap/le/dynamic_channel_service.h"
-#include "l2cap/le/facade.grpc.pb.h"
-#include "l2cap/le/l2cap_le_module.h"
-#include "l2cap/le/security_policy.h"
-#include "l2cap/psm.h"
-#include "packet/raw_builder.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace le {
-
-SecurityPolicy SecurityLevelToPolicy(SecurityLevel level) {
- switch (level) {
- case SecurityLevel::NO_SECURITY:
- return SecurityPolicy::NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK;
- case SecurityLevel::UNAUTHENTICATED_PAIRING_WITH_ENCRYPTION:
- return SecurityPolicy::ENCRYPTED_TRANSPORT;
- case SecurityLevel::AUTHENTICATED_PAIRING_WITH_ENCRYPTION:
- return SecurityPolicy::AUTHENTICATED_ENCRYPTED_TRANSPORT;
- case SecurityLevel::AUTHENTICATED_PAIRING_WITH_128_BIT_KEY:
- return SecurityPolicy::_NOT_FOR_YOU__AUTHENTICATED_PAIRING_WITH_128_BIT_KEY;
- case SecurityLevel::AUTHORIZATION:
- return SecurityPolicy::_NOT_FOR_YOU__AUTHORIZATION;
- default:
- return SecurityPolicy::NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK;
- }
-}
-
-static constexpr auto kChannelOpenTimeout = std::chrono::seconds(4);
-
-class L2capLeModuleFacadeService : public L2capLeModuleFacade::Service {
- public:
- L2capLeModuleFacadeService(L2capLeModule* l2cap_layer, os::Handler* facade_handler)
- : l2cap_layer_(l2cap_layer), facade_handler_(facade_handler) {
- ASSERT(l2cap_layer_ != nullptr);
- ASSERT(facade_handler_ != nullptr);
- }
-
- ::grpc::Status FetchL2capData(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<::bluetooth::l2cap::le::L2capPacket>* writer) override {
- return pending_l2cap_data_.RunLoop(context, writer);
- }
-
- ::grpc::Status OpenDynamicChannel(::grpc::ServerContext* context, const OpenDynamicChannelRequest* request,
- OpenDynamicChannelResponse* response) override {
- auto service_helper = dynamic_channel_helper_map_.find(request->psm());
- if (service_helper == dynamic_channel_helper_map_.end()) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Psm not registered");
- }
- hci::Address peer_address;
- ASSERT(hci::Address::FromString(request->remote().address().address(), peer_address));
- // TODO: Support different address type
- hci::AddressWithType peer(peer_address, hci::AddressType::RANDOM_DEVICE_ADDRESS);
- service_helper->second->Connect(peer);
- response->set_status(
- static_cast<int>(service_helper->second->channel_open_fail_reason_.l2cap_connection_response_result));
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status CloseDynamicChannel(::grpc::ServerContext* context, const CloseDynamicChannelRequest* request,
- ::google::protobuf::Empty* response) override {
- auto service_helper = dynamic_channel_helper_map_.find(request->psm());
- if (service_helper == dynamic_channel_helper_map_.end()) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Psm not registered");
- }
- if (service_helper->second->channel_ == nullptr) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Channel not open");
- }
- auto address = service_helper->second->channel_->GetDevice().GetAddress();
- hci::Address peer_address;
- ASSERT(hci::Address::FromString(request->remote().address().address(), peer_address));
- if (address != peer_address) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Remote address doesn't match");
- }
- service_helper->second->channel_->Close();
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status SetDynamicChannel(::grpc::ServerContext* context,
- const ::bluetooth::l2cap::le::SetEnableDynamicChannelRequest* request,
- ::google::protobuf::Empty* response) override {
- if (request->enable()) {
- dynamic_channel_helper_map_.emplace(request->psm(), std::make_unique<L2capDynamicChannelHelper>(
- this, l2cap_layer_, facade_handler_, request->psm(),
- SecurityLevelToPolicy(request->security_level())));
- return ::grpc::Status::OK;
- } else {
- auto service_helper = dynamic_channel_helper_map_.find(request->psm());
- if (service_helper == dynamic_channel_helper_map_.end()) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Psm not registered");
- }
- service_helper->second->service_->Unregister(common::BindOnce([] {}), facade_handler_);
- return ::grpc::Status::OK;
- }
- }
-
- ::grpc::Status SendDynamicChannelPacket(::grpc::ServerContext* context,
- const ::bluetooth::l2cap::le::DynamicChannelPacket* request,
- ::google::protobuf::Empty* response) override {
- std::unique_lock<std::mutex> lock(channel_map_mutex_);
- if (dynamic_channel_helper_map_.find(request->psm()) == dynamic_channel_helper_map_.end()) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Psm not registered");
- }
- std::vector<uint8_t> packet(request->payload().begin(), request->payload().end());
- if (!dynamic_channel_helper_map_[request->psm()]->SendPacket(packet)) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Channel not open");
- }
- return ::grpc::Status::OK;
- }
-
- class L2capDynamicChannelHelper {
- public:
- L2capDynamicChannelHelper(L2capLeModuleFacadeService* service, L2capLeModule* l2cap_layer, os::Handler* handler,
- Psm psm, SecurityPolicy security_policy)
- : facade_service_(service), l2cap_layer_(l2cap_layer), handler_(handler), psm_(psm) {
- dynamic_channel_manager_ = l2cap_layer_->GetDynamicChannelManager();
- dynamic_channel_manager_->RegisterService(
- psm, {}, security_policy,
- common::BindOnce(&L2capDynamicChannelHelper::on_l2cap_service_registration_complete,
- common::Unretained(this)),
- common::Bind(&L2capDynamicChannelHelper::on_connection_open, common::Unretained(this)), handler_);
- }
-
- ~L2capDynamicChannelHelper() {
- if (channel_ != nullptr) {
- channel_->GetQueueUpEnd()->UnregisterDequeue();
- channel_ = nullptr;
- }
- }
-
- void Connect(hci::AddressWithType address) {
- dynamic_channel_manager_->ConnectChannel(
- address, {}, psm_, common::Bind(&L2capDynamicChannelHelper::on_connection_open, common::Unretained(this)),
- common::Bind(&L2capDynamicChannelHelper::on_connect_fail, common::Unretained(this)), handler_);
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- if (!channel_open_cv_.wait_for(lock, kChannelOpenTimeout, [this] { return channel_ != nullptr; })) {
- LOG_WARN("Channel is not open for psm %d", psm_);
- }
- }
-
- void on_l2cap_service_registration_complete(DynamicChannelManager::RegistrationResult registration_result,
- std::unique_ptr<DynamicChannelService> service) {
- if (registration_result != DynamicChannelManager::RegistrationResult::SUCCESS) {
- LOG_ERROR("Service registration failed");
- } else {
- service_ = std::move(service);
- }
- }
-
- // invoked from Facade Handler
- void on_connection_open(std::unique_ptr<DynamicChannel> channel) {
- {
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- channel_ = std::move(channel);
- }
- channel_open_cv_.notify_all();
- channel_->RegisterOnCloseCallback(
- facade_service_->facade_handler_->BindOnceOn(this, &L2capDynamicChannelHelper::on_close_callback));
- channel_->GetQueueUpEnd()->RegisterDequeue(
- facade_service_->facade_handler_,
- common::Bind(&L2capDynamicChannelHelper::on_incoming_packet, common::Unretained(this)));
- }
-
- void on_close_callback(hci::ErrorCode error_code) {
- {
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- channel_->GetQueueUpEnd()->UnregisterDequeue();
- }
- channel_ = nullptr;
- }
-
- void on_connect_fail(DynamicChannelManager::ConnectionResult result) {
- {
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- channel_ = nullptr;
- channel_open_fail_reason_ = result;
- }
- channel_open_cv_.notify_all();
- }
-
- void on_incoming_packet() {
- auto packet = channel_->GetQueueUpEnd()->TryDequeue();
- std::string data = std::string(packet->begin(), packet->end());
- L2capPacket l2cap_data;
- l2cap_data.set_psm(psm_);
- l2cap_data.set_payload(data);
- facade_service_->pending_l2cap_data_.OnIncomingEvent(l2cap_data);
- }
-
- bool SendPacket(std::vector<uint8_t> packet) {
- if (channel_ == nullptr) {
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- if (!channel_open_cv_.wait_for(lock, kChannelOpenTimeout, [this] { return channel_ != nullptr; })) {
- LOG_WARN("Channel is not open for psm %d", psm_);
- return false;
- }
- }
- std::promise<void> promise;
- auto future = promise.get_future();
- channel_->GetQueueUpEnd()->RegisterEnqueue(
- handler_, common::Bind(&L2capDynamicChannelHelper::enqueue_callback, common::Unretained(this), packet,
- common::Passed(std::move(promise))));
- auto status = future.wait_for(std::chrono::milliseconds(500));
- if (status != std::future_status::ready) {
- LOG_ERROR("Can't send packet because the previous packet wasn't sent yet");
- return false;
- }
- return true;
- }
-
- std::unique_ptr<packet::BasePacketBuilder> enqueue_callback(std::vector<uint8_t> packet,
- std::promise<void> promise) {
- auto packet_one = std::make_unique<packet::RawBuilder>(2000);
- packet_one->AddOctets(packet);
- channel_->GetQueueUpEnd()->UnregisterEnqueue();
- promise.set_value();
- return packet_one;
- }
-
- L2capLeModuleFacadeService* facade_service_;
- L2capLeModule* l2cap_layer_;
- os::Handler* handler_;
- std::unique_ptr<DynamicChannelManager> dynamic_channel_manager_;
- std::unique_ptr<DynamicChannelService> service_;
- std::unique_ptr<DynamicChannel> channel_ = nullptr;
- Psm psm_;
- DynamicChannelManager::ConnectionResult channel_open_fail_reason_;
- std::condition_variable channel_open_cv_;
- std::mutex channel_open_cv_mutex_;
- };
-
- ::grpc::Status SetFixedChannel(::grpc::ServerContext* context, const SetEnableFixedChannelRequest* request,
- ::google::protobuf::Empty* response) override {
- if (request->enable()) {
- fixed_channel_helper_map_.emplace(request->cid(), std::make_unique<L2capFixedChannelHelper>(
- this, l2cap_layer_, facade_handler_, request->cid()));
- return ::grpc::Status::OK;
- } else {
- auto service_helper = fixed_channel_helper_map_.find(request->cid());
- if (service_helper == fixed_channel_helper_map_.end()) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Cid not registered");
- }
- service_helper->second->channel_->Release();
- service_helper->second->service_->Unregister(common::BindOnce([] {}), facade_handler_);
- return ::grpc::Status::OK;
- }
- }
-
- ::grpc::Status SendFixedChannelPacket(::grpc::ServerContext* context, const FixedChannelPacket* request,
- ::google::protobuf::Empty* response) override {
- std::unique_lock<std::mutex> lock(channel_map_mutex_);
- if (fixed_channel_helper_map_.find(request->cid()) == fixed_channel_helper_map_.end()) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Cid not registered");
- }
- std::vector<uint8_t> packet(request->payload().begin(), request->payload().end());
- if (!fixed_channel_helper_map_[request->cid()]->SendPacket(packet)) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Channel not open");
- }
- return ::grpc::Status::OK;
- }
-
- class L2capFixedChannelHelper {
- public:
- L2capFixedChannelHelper(L2capLeModuleFacadeService* service, L2capLeModule* l2cap_layer, os::Handler* handler,
- Cid cid)
- : facade_service_(service), l2cap_layer_(l2cap_layer), handler_(handler), cid_(cid) {
- fixed_channel_manager_ = l2cap_layer_->GetFixedChannelManager();
- fixed_channel_manager_->RegisterService(
- cid_,
- common::BindOnce(&L2capFixedChannelHelper::on_l2cap_service_registration_complete, common::Unretained(this)),
- common::Bind(&L2capFixedChannelHelper::on_connection_open, common::Unretained(this)), handler_);
- }
-
- ~L2capFixedChannelHelper() {
- if (channel_ != nullptr) {
- channel_->GetQueueUpEnd()->UnregisterDequeue();
- channel_->Release();
- channel_ = nullptr;
- }
- }
-
- void Connect(hci::AddressWithType address) {
- fixed_channel_manager_->ConnectServices(
- address, common::BindOnce(&L2capFixedChannelHelper::on_connect_fail, common::Unretained(this)), handler_);
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- if (!channel_open_cv_.wait_for(lock, kChannelOpenTimeout, [this] { return channel_ != nullptr; })) {
- LOG_WARN("Channel is not open for cid %d", cid_);
- }
- }
-
- void on_l2cap_service_registration_complete(FixedChannelManager::RegistrationResult registration_result,
- std::unique_ptr<FixedChannelService> service) {
- if (registration_result != FixedChannelManager::RegistrationResult::SUCCESS) {
- LOG_ERROR("Service registration failed");
- } else {
- service_ = std::move(service);
- }
- }
-
- // invoked from Facade Handler
- void on_connection_open(std::unique_ptr<FixedChannel> channel) {
- {
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- channel_ = std::move(channel);
- channel_->RegisterOnCloseCallback(
- handler_, common::BindOnce(&L2capFixedChannelHelper::on_close_callback, common::Unretained(this)));
- channel_->Acquire();
- }
- channel_open_cv_.notify_all();
- channel_->GetQueueUpEnd()->RegisterDequeue(
- facade_service_->facade_handler_,
- common::Bind(&L2capFixedChannelHelper::on_incoming_packet, common::Unretained(this)));
- }
-
- void on_close_callback(hci::ErrorCode error_code) {
- {
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- channel_->GetQueueUpEnd()->UnregisterDequeue();
- }
- channel_ = nullptr;
- }
-
- void on_connect_fail(FixedChannelManager::ConnectionResult result) {
- {
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- channel_ = nullptr;
- }
- channel_open_cv_.notify_all();
- }
-
- void on_incoming_packet() {
- auto packet = channel_->GetQueueUpEnd()->TryDequeue();
- std::string data = std::string(packet->begin(), packet->end());
- L2capPacket l2cap_data;
- l2cap_data.set_fixed_cid(cid_);
- l2cap_data.set_payload(data);
- facade_service_->pending_l2cap_data_.OnIncomingEvent(l2cap_data);
- }
-
- bool SendPacket(std::vector<uint8_t> packet) {
- if (channel_ == nullptr) {
- std::unique_lock<std::mutex> lock(channel_open_cv_mutex_);
- if (!channel_open_cv_.wait_for(lock, kChannelOpenTimeout, [this] { return channel_ != nullptr; })) {
- LOG_WARN("Channel is not open for cid %d", cid_);
- return false;
- }
- }
- std::promise<void> promise;
- auto future = promise.get_future();
- channel_->GetQueueUpEnd()->RegisterEnqueue(
- handler_, common::Bind(&L2capFixedChannelHelper::enqueue_callback, common::Unretained(this), packet,
- common::Passed(std::move(promise))));
- auto status = future.wait_for(std::chrono::milliseconds(500));
- if (status != std::future_status::ready) {
- LOG_ERROR("Can't send packet because the previous packet wasn't sent yet");
- return false;
- }
- return true;
- }
-
- std::unique_ptr<packet::BasePacketBuilder> enqueue_callback(std::vector<uint8_t> packet,
- std::promise<void> promise) {
- auto packet_one = std::make_unique<packet::RawBuilder>(2000);
- packet_one->AddOctets(packet);
- channel_->GetQueueUpEnd()->UnregisterEnqueue();
- promise.set_value();
- return packet_one;
- }
-
- L2capLeModuleFacadeService* facade_service_;
- L2capLeModule* l2cap_layer_;
- os::Handler* handler_;
- std::unique_ptr<FixedChannelManager> fixed_channel_manager_;
- std::unique_ptr<FixedChannelService> service_;
- std::unique_ptr<FixedChannel> channel_ = nullptr;
- Cid cid_;
- std::condition_variable channel_open_cv_;
- std::mutex channel_open_cv_mutex_;
- };
-
- ::grpc::Status SendConnectionParameterUpdate(::grpc::ServerContext* context, const ConnectionParameter* request,
- ::google::protobuf::Empty* response) override {
- if (dynamic_channel_helper_map_.empty()) {
- return ::grpc::Status(::grpc::StatusCode::FAILED_PRECONDITION, "Need to open at least one dynamic channel first");
- }
- auto& dynamic_channel_helper = dynamic_channel_helper_map_.begin()->second;
- dynamic_channel_helper->channel_->GetLinkOptions()->UpdateConnectionParameter(
- request->conn_interval_min(), request->conn_interval_max(), request->conn_latency(),
- request->supervision_timeout(), request->min_ce_length(), request->max_ce_length());
-
- return ::grpc::Status::OK;
- }
-
- L2capLeModule* l2cap_layer_;
- os::Handler* facade_handler_;
- std::mutex channel_map_mutex_;
- std::map<Psm, std::unique_ptr<L2capDynamicChannelHelper>> dynamic_channel_helper_map_;
- std::map<Cid, std::unique_ptr<L2capFixedChannelHelper>> fixed_channel_helper_map_;
- ::bluetooth::grpc::GrpcEventQueue<L2capPacket> pending_l2cap_data_{"FetchL2capData"};
-};
-
-void L2capLeModuleFacadeModule::ListDependencies(ModuleList* list) {
- ::bluetooth::grpc::GrpcFacadeModule::ListDependencies(list);
- list->add<l2cap::le::L2capLeModule>();
-}
-
-void L2capLeModuleFacadeModule::Start() {
- ::bluetooth::grpc::GrpcFacadeModule::Start();
- service_ = new L2capLeModuleFacadeService(GetDependency<l2cap::le::L2capLeModule>(), GetHandler());
-}
-
-void L2capLeModuleFacadeModule::Stop() {
- delete service_;
- ::bluetooth::grpc::GrpcFacadeModule::Stop();
-}
-
-::grpc::Service* L2capLeModuleFacadeModule::GetService() const {
- return service_;
-}
-
-const ModuleFactory L2capLeModuleFacadeModule::Factory =
- ::bluetooth::ModuleFactory([]() { return new L2capLeModuleFacadeModule(); });
-
-} // namespace le
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/le/facade.h b/gd/l2cap/le/facade.h
deleted file mode 100644
index 0f811c8b5..000000000
--- a/gd/l2cap/le/facade.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <grpc++/grpc++.h>
-
-#include "grpc/grpc_module.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace le {
-
-class L2capLeModuleFacadeService;
-
-class L2capLeModuleFacadeModule : public ::bluetooth::grpc::GrpcFacadeModule {
- public:
- static const ModuleFactory Factory;
-
- void ListDependencies(ModuleList* list) override;
-
- void Start() override;
-
- void Stop() override;
-
- ::grpc::Service* GetService() const override;
-
- private:
- L2capLeModuleFacadeService* service_;
-};
-
-} // namespace le
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/le/facade.proto b/gd/l2cap/le/facade.proto
deleted file mode 100644
index b9b4841dd..000000000
--- a/gd/l2cap/le/facade.proto
+++ /dev/null
@@ -1,85 +0,0 @@
-syntax = "proto3";
-
-package bluetooth.l2cap.le;
-
-import "google/protobuf/empty.proto";
-import "facade/common.proto";
-
-service L2capLeModuleFacade {
- rpc FetchL2capData(google.protobuf.Empty) returns (stream L2capPacket) {}
- // Initiate a credit based connection request and block until response is received for up to some timeout (2s)
- rpc OpenDynamicChannel(OpenDynamicChannelRequest) returns (OpenDynamicChannelResponse) {}
- rpc CloseDynamicChannel(CloseDynamicChannelRequest) returns (google.protobuf.Empty) {}
- rpc SetDynamicChannel(SetEnableDynamicChannelRequest) returns (google.protobuf.Empty) {}
- rpc SendDynamicChannelPacket(DynamicChannelPacket) returns (google.protobuf.Empty) {}
- rpc SetFixedChannel(SetEnableFixedChannelRequest) returns (google.protobuf.Empty) {}
- rpc SendFixedChannelPacket(FixedChannelPacket) returns (google.protobuf.Empty) {}
- rpc SendConnectionParameterUpdate(ConnectionParameter) returns (google.protobuf.Empty) {}
-}
-
-message L2capPacket {
- oneof channel_type {
- uint32 psm = 1;
- uint32 fixed_cid = 2;
- }
- bytes payload = 3;
-}
-
-message DynamicChannelOpenEvent {
- uint32 psm = 1;
- uint32 connection_response_result = 2;
-}
-
-message OpenDynamicChannelRequest {
- facade.BluetoothAddressWithType remote = 1;
- uint32 psm = 2;
-}
-
-message OpenDynamicChannelResponse {
- uint32 status = 1;
-}
-
-message CloseDynamicChannelRequest {
- facade.BluetoothAddressWithType remote = 1;
- uint32 psm = 2;
-}
-
-enum SecurityLevel {
- NO_SECURITY = 0;
- UNAUTHENTICATED_PAIRING_WITH_ENCRYPTION = 1;
- AUTHENTICATED_PAIRING_WITH_ENCRYPTION = 2;
- AUTHENTICATED_PAIRING_WITH_128_BIT_KEY = 3;
- AUTHORIZATION = 4;
-}
-
-message SetEnableDynamicChannelRequest {
- uint32 psm = 1;
- bool enable = 2;
- SecurityLevel security_level = 3;
-}
-
-message DynamicChannelPacket {
- facade.BluetoothAddressWithType remote = 1;
- uint32 psm = 2;
- bytes payload = 3;
-}
-
-message SetEnableFixedChannelRequest {
- uint32 cid = 1;
- bool enable = 2;
-}
-
-message FixedChannelPacket {
- facade.BluetoothAddressWithType remote = 1;
- uint32 cid = 2;
- bytes payload = 3;
-}
-
-message ConnectionParameter {
- uint32 conn_interval_min = 2;
- uint32 conn_interval_max = 3;
- uint32 conn_latency = 4;
- uint32 supervision_timeout = 5;
- uint32 min_ce_length = 6;
- uint32 max_ce_length = 7;
-}
diff --git a/gd/l2cap/le/fixed_channel.cc b/gd/l2cap/le/fixed_channel.cc
index fb3fd4c2d..779c18583 100644
--- a/gd/l2cap/le/fixed_channel.cc
+++ b/gd/l2cap/le/fixed_channel.cc
@@ -26,6 +26,14 @@ hci::AddressWithType FixedChannel::GetDevice() const {
return impl_->GetDevice();
}
+hci::Role FixedChannel::GetRole() const {
+ return impl_->GetRole();
+}
+
+hci::AclConnection* FixedChannel::GetAclConnection() const {
+ return impl_->GetAclConnection();
+}
+
void FixedChannel::RegisterOnCloseCallback(os::Handler* user_handler, FixedChannel::OnCloseCallback on_close_callback) {
l2cap_handler_->Post(common::BindOnce(&internal::FixedChannelImpl::RegisterOnCloseCallback, impl_, user_handler,
std::move(on_close_callback)));
@@ -43,11 +51,6 @@ common::BidiQueueEnd<packet::BasePacketBuilder, packet::PacketView<packet::kLitt
FixedChannel::GetQueueUpEnd() const {
return impl_->GetQueueUpEnd();
}
-
-LinkOptions* FixedChannel::GetLinkOptions() {
- return impl_->GetLinkOptions();
-}
-
} // namespace le
} // namespace l2cap
} // namespace bluetooth
diff --git a/gd/l2cap/le/fixed_channel.h b/gd/l2cap/le/fixed_channel.h
index 7a7cc947f..6d3cc423b 100644
--- a/gd/l2cap/le/fixed_channel.h
+++ b/gd/l2cap/le/fixed_channel.h
@@ -19,7 +19,6 @@
#include "common/callback.h"
#include "hci/acl_manager.h"
#include "l2cap/cid.h"
-#include "l2cap/le/link_options.h"
#include "os/handler.h"
#include "packet/base_packet_builder.h"
#include "packet/packet_view.h"
@@ -50,6 +49,13 @@ class FixedChannel {
hci::AddressWithType GetDevice() const;
/**
+ * Return the role we have in the associated link
+ */
+ hci::Role GetRole() const;
+
+ hci::AclConnection* GetAclConnection() const;
+
+ /**
* Register close callback. If close callback is registered, when a channel is closed, the channel's resource will
* only be freed after on_close callback is invoked. Otherwise, if no on_close callback is registered, the channel's
* resource will be freed immediately after closing.
@@ -81,13 +87,6 @@ class FixedChannel {
*/
common::BidiQueueEnd<packet::BasePacketBuilder, packet::PacketView<packet::kLittleEndian>>* GetQueueUpEnd() const;
- /**
- * Get the Proxy for L2CAP Link Options.
- * Only few special L2CAP users need to use it, including
- * GATT, HID Device, Security Manager, and Java API.
- */
- LinkOptions* GetLinkOptions();
-
private:
std::shared_ptr<internal::FixedChannelImpl> impl_;
os::Handler* l2cap_handler_;
diff --git a/gd/l2cap/le/fixed_channel_manager.cc b/gd/l2cap/le/fixed_channel_manager.cc
index c3c476380..e36a7b452 100644
--- a/gd/l2cap/le/fixed_channel_manager.cc
+++ b/gd/l2cap/le/fixed_channel_manager.cc
@@ -35,7 +35,8 @@ bool FixedChannelManager::ConnectServices(hci::AddressWithType address_with_type
return true;
}
-bool FixedChannelManager::RegisterService(Cid cid, OnRegistrationCompleteCallback on_registration_complete,
+bool FixedChannelManager::RegisterService(Cid cid, const SecurityPolicy& security_policy,
+ OnRegistrationCompleteCallback on_registration_complete,
OnConnectionOpenCallback on_connection_open, os::Handler* handler) {
internal::FixedChannelServiceImpl::PendingRegistration pending_registration{
.user_handler_ = handler,
diff --git a/gd/l2cap/le/fixed_channel_manager.h b/gd/l2cap/le/fixed_channel_manager.h
index 1b059ac34..45833104c 100644
--- a/gd/l2cap/le/fixed_channel_manager.h
+++ b/gd/l2cap/le/fixed_channel_manager.h
@@ -17,10 +17,12 @@
#include <string>
+#include "hci/acl_manager.h"
#include "hci/address_with_type.h"
#include "l2cap/cid.h"
#include "l2cap/le/fixed_channel.h"
#include "l2cap/le/fixed_channel_service.h"
+#include "l2cap/security_policy.h"
#include "os/handler.h"
namespace bluetooth {
@@ -113,17 +115,19 @@ class FixedChannelManager {
* FixedChannelService object. The registered service can be managed from that object.
* - If a CID is already registered or some other error happens, on_registration_complete will be triggered with a
* non-SUCCESS value
- * - After a service is registered, any LE ACL connection will create a FixedChannel object that is
+ * - After a service is registered, any classic ACL connection will create a FixedChannel object that is
* delivered through on_open_callback
* - on_open_callback, will only be triggered after on_service_registered callback
*
* @param cid: cid used to receive incoming connections
+ * @param security_policy: The security policy used for the connection.
* @param on_registration_complete: A callback to indicate the service setup has completed. If the return status is
* not SUCCESS, it means service is not registered due to reasons like CID already take
* @param on_open_callback: A callback to indicate success of a connection initiated from a remote device.
* @param handler: The handler context in which to execute the @callback parameter.
*/
- bool RegisterService(Cid cid, OnRegistrationCompleteCallback on_registration_complete,
+ bool RegisterService(Cid cid, const SecurityPolicy& security_policy,
+ OnRegistrationCompleteCallback on_registration_complete,
OnConnectionOpenCallback on_connection_open, os::Handler* handler);
friend class L2capLeModule;
diff --git a/gd/l2cap/le/internal/dynamic_channel_service_impl.h b/gd/l2cap/le/internal/dynamic_channel_service_impl.h
index 25af09428..101ef6224 100644
--- a/gd/l2cap/le/internal/dynamic_channel_service_impl.h
+++ b/gd/l2cap/le/internal/dynamic_channel_service_impl.h
@@ -22,7 +22,6 @@
#include "l2cap/le/dynamic_channel_configuration_option.h"
#include "l2cap/le/dynamic_channel_manager.h"
#include "l2cap/le/dynamic_channel_service.h"
-#include "l2cap/le/security_policy.h"
namespace bluetooth {
namespace l2cap {
@@ -34,7 +33,6 @@ class DynamicChannelServiceImpl {
struct PendingRegistration {
os::Handler* user_handler_ = nullptr;
- SecurityPolicy security_policy_;
DynamicChannelManager::OnRegistrationCompleteCallback on_registration_complete_callback_;
DynamicChannelManager::OnConnectionOpenCallback on_connection_open_callback_;
DynamicChannelConfigurationOption configuration_;
@@ -48,25 +46,20 @@ class DynamicChannelServiceImpl {
return config_option_;
}
- SecurityPolicy GetSecurityPolicy() {
- return security_policy_;
- }
-
friend class DynamicChannelServiceManagerImpl;
protected:
// protected access for mocking
DynamicChannelServiceImpl(os::Handler* user_handler,
DynamicChannelManager::OnConnectionOpenCallback on_connection_open_callback,
- DynamicChannelConfigurationOption config_option, SecurityPolicy security_policy)
+ DynamicChannelConfigurationOption config_option)
: user_handler_(user_handler), on_connection_open_callback_(std::move(on_connection_open_callback)),
- config_option_(config_option), security_policy_(security_policy) {}
+ config_option_(config_option) {}
private:
os::Handler* user_handler_ = nullptr;
DynamicChannelManager::OnConnectionOpenCallback on_connection_open_callback_;
DynamicChannelConfigurationOption config_option_;
- SecurityPolicy security_policy_;
};
} // namespace internal
diff --git a/gd/l2cap/le/internal/dynamic_channel_service_impl_mock.h b/gd/l2cap/le/internal/dynamic_channel_service_impl_mock.h
deleted file mode 100644
index 4edfee864..000000000
--- a/gd/l2cap/le/internal/dynamic_channel_service_impl_mock.h
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include "l2cap/le/internal/dynamic_channel_service_impl.h"
-
-#include <gmock/gmock.h>
-
-// Unit test interfaces
-namespace bluetooth {
-namespace l2cap {
-namespace le {
-namespace internal {
-namespace testing {
-
-class MockDynamicChannelServiceImpl : public DynamicChannelServiceImpl {
- public:
- MOCK_METHOD(SecurityPolicy, GetSecurityPolicy, (), (const, override));
-};
-
-} // namespace testing
-} // namespace internal
-} // namespace le
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/le/internal/dynamic_channel_service_manager_impl.cc b/gd/l2cap/le/internal/dynamic_channel_service_manager_impl.cc
index 4e848f48d..ca3381b06 100644
--- a/gd/l2cap/le/internal/dynamic_channel_service_manager_impl.cc
+++ b/gd/l2cap/le/internal/dynamic_channel_service_manager_impl.cc
@@ -28,16 +28,21 @@ namespace internal {
void DynamicChannelServiceManagerImpl::Register(Psm psm,
DynamicChannelServiceImpl::PendingRegistration pending_registration) {
- if (IsServiceRegistered(psm)) {
+ if (!IsPsmValid(psm)) {
+ std::unique_ptr<DynamicChannelService> invalid_service(new DynamicChannelService());
+ pending_registration.user_handler_->Post(
+ common::BindOnce(std::move(pending_registration.on_registration_complete_callback_),
+ DynamicChannelManager::RegistrationResult::FAIL_INVALID_SERVICE, std::move(invalid_service)));
+ } else if (IsServiceRegistered(psm)) {
std::unique_ptr<DynamicChannelService> invalid_service(new DynamicChannelService());
pending_registration.user_handler_->Post(common::BindOnce(
std::move(pending_registration.on_registration_complete_callback_),
DynamicChannelManager::RegistrationResult::FAIL_DUPLICATE_SERVICE, std::move(invalid_service)));
} else {
- service_map_.try_emplace(
- psm, DynamicChannelServiceImpl(pending_registration.user_handler_,
- std::move(pending_registration.on_connection_open_callback_),
- pending_registration.configuration_, pending_registration.security_policy_));
+ service_map_.try_emplace(psm,
+ DynamicChannelServiceImpl(pending_registration.user_handler_,
+ std::move(pending_registration.on_connection_open_callback_),
+ pending_registration.configuration_));
std::unique_ptr<DynamicChannelService> user_service(new DynamicChannelService(psm, this, l2cap_layer_handler_));
pending_registration.user_handler_->Post(
common::BindOnce(std::move(pending_registration.on_registration_complete_callback_),
diff --git a/gd/l2cap/le/internal/dynamic_channel_service_manager_impl.h b/gd/l2cap/le/internal/dynamic_channel_service_manager_impl.h
index 169853f44..5de5f804a 100644
--- a/gd/l2cap/le/internal/dynamic_channel_service_manager_impl.h
+++ b/gd/l2cap/le/internal/dynamic_channel_service_manager_impl.h
@@ -20,7 +20,6 @@
#include "l2cap/le/dynamic_channel_service.h"
#include "l2cap/le/internal/dynamic_channel_service_impl.h"
-#include "l2cap/le/security_enforcement_interface.h"
#include "l2cap/psm.h"
#include "os/handler.h"
@@ -45,19 +44,9 @@ class DynamicChannelServiceManagerImpl {
virtual std::vector<std::pair<Psm, DynamicChannelServiceImpl*>> GetRegisteredServices();
- // Implementation is set by SecurityManager through L2capModule
- void SetSecurityEnforcementInterface(SecurityEnforcementInterface* impl) {
- security_enforcement_interface_ = impl;
- }
-
- SecurityEnforcementInterface* GetSecurityEnforcementInterface() {
- return security_enforcement_interface_;
- }
-
private:
os::Handler* l2cap_layer_handler_ = nullptr;
std::unordered_map<Psm, DynamicChannelServiceImpl> service_map_;
- SecurityEnforcementInterface* security_enforcement_interface_;
};
} // namespace internal
} // namespace le
diff --git a/gd/l2cap/le/internal/dynamic_channel_service_manager_test.cc b/gd/l2cap/le/internal/dynamic_channel_service_manager_test.cc
index d1f16561d..00d66d144 100644
--- a/gd/l2cap/le/internal/dynamic_channel_service_manager_test.cc
+++ b/gd/l2cap/le/internal/dynamic_channel_service_manager_test.cc
@@ -33,7 +33,7 @@ namespace internal {
class L2capLeDynamicServiceManagerTest : public ::testing::Test {
public:
- ~L2capLeDynamicServiceManagerTest() = default;
+ ~L2capLeDynamicServiceManagerTest() override = default;
void OnServiceRegistered(bool expect_success, DynamicChannelManager::RegistrationResult result,
std::unique_ptr<DynamicChannelService> user_service) {
@@ -76,31 +76,29 @@ class L2capLeDynamicServiceManagerTest : public ::testing::Test {
TEST_F(L2capLeDynamicServiceManagerTest, register_and_unregister_le_dynamic_channel) {
DynamicChannelServiceImpl::PendingRegistration pending_registration{
.user_handler_ = user_handler_,
- .security_policy_ = SecurityPolicy::NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK,
.on_registration_complete_callback_ =
common::BindOnce(&L2capLeDynamicServiceManagerTest::OnServiceRegistered, common::Unretained(this), true)};
- Psm psm = 0x41;
- EXPECT_FALSE(manager_->IsServiceRegistered(psm));
- manager_->Register(psm, std::move(pending_registration));
- EXPECT_TRUE(manager_->IsServiceRegistered(psm));
+ Cid cid = kSmpBrCid;
+ EXPECT_FALSE(manager_->IsServiceRegistered(cid));
+ manager_->Register(cid, std::move(pending_registration));
+ EXPECT_TRUE(manager_->IsServiceRegistered(cid));
sync_user_handler();
EXPECT_TRUE(service_registered_);
- manager_->Unregister(psm, common::BindOnce([] {}), user_handler_);
- EXPECT_FALSE(manager_->IsServiceRegistered(psm));
+ manager_->Unregister(cid, common::BindOnce([] {}), user_handler_);
+ EXPECT_FALSE(manager_->IsServiceRegistered(cid));
}
-TEST_F(L2capLeDynamicServiceManagerTest, register_le_dynamic_channel_even_number_psm) {
+TEST_F(L2capLeDynamicServiceManagerTest, register_le_dynamic_channel_bad_cid) {
DynamicChannelServiceImpl::PendingRegistration pending_registration{
.user_handler_ = user_handler_,
- .security_policy_ = SecurityPolicy::NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK,
.on_registration_complete_callback_ =
- common::BindOnce(&L2capLeDynamicServiceManagerTest::OnServiceRegistered, common::Unretained(this), true)};
- Psm psm = 0x0100;
- EXPECT_FALSE(manager_->IsServiceRegistered(psm));
- manager_->Register(psm, std::move(pending_registration));
- EXPECT_TRUE(manager_->IsServiceRegistered(psm));
+ common::BindOnce(&L2capLeDynamicServiceManagerTest::OnServiceRegistered, common::Unretained(this), false)};
+ Cid cid = 0x1000;
+ EXPECT_FALSE(manager_->IsServiceRegistered(cid));
+ manager_->Register(cid, std::move(pending_registration));
+ EXPECT_FALSE(manager_->IsServiceRegistered(cid));
sync_user_handler();
- EXPECT_TRUE(service_registered_);
+ EXPECT_FALSE(service_registered_);
}
} // namespace internal
diff --git a/gd/l2cap/le/internal/fixed_channel_impl.cc b/gd/l2cap/le/internal/fixed_channel_impl.cc
index da5dbfa3b..af55ba1b3 100644
--- a/gd/l2cap/le/internal/fixed_channel_impl.cc
+++ b/gd/l2cap/le/internal/fixed_channel_impl.cc
@@ -16,10 +16,10 @@
#include <unordered_map>
-#include "hci/acl_manager/le_acl_connection.h"
#include "l2cap/cid.h"
#include "l2cap/le/internal/fixed_channel_impl.h"
#include "l2cap/le/internal/link.h"
+#include "l2cap/security_policy.h"
#include "os/handler.h"
#include "os/log.h"
@@ -32,7 +32,7 @@ hci::Role FixedChannelImpl::GetRole() const {
return link_->GetRole();
}
-hci::acl_manager::LeAclConnection* FixedChannelImpl::GetAclConnection() const {
+hci::AclConnection* FixedChannelImpl::GetAclConnection() const {
return link_->GetAclConnection();
}
@@ -80,7 +80,7 @@ void FixedChannelImpl::Acquire() {
return;
}
if (acquired_) {
- LOG_INFO("%s was already acquired", ToString().c_str());
+ LOG_DEBUG("%s was already acquired", ToString().c_str());
return;
}
acquired_ = true;
@@ -95,7 +95,7 @@ void FixedChannelImpl::Release() {
return;
}
if (!acquired_) {
- LOG_INFO("%s was already released", ToString().c_str());
+ LOG_DEBUG("%s was already released", ToString().c_str());
return;
}
acquired_ = false;
@@ -110,10 +110,6 @@ Cid FixedChannelImpl::GetRemoteCid() const {
return cid_;
}
-LinkOptions* FixedChannelImpl::GetLinkOptions() {
- return link_->GetLinkOptions();
-}
-
} // namespace internal
} // namespace le
} // namespace l2cap
diff --git a/gd/l2cap/le/internal/fixed_channel_impl.h b/gd/l2cap/le/internal/fixed_channel_impl.h
index d4fb3a370..cdb421286 100644
--- a/gd/l2cap/le/internal/fixed_channel_impl.h
+++ b/gd/l2cap/le/internal/fixed_channel_impl.h
@@ -17,11 +17,9 @@
#pragma once
#include "common/bidi_queue.h"
-#include "hci/acl_manager/le_acl_connection.h"
#include "l2cap/cid.h"
#include "l2cap/internal/channel_impl.h"
#include "l2cap/le/fixed_channel.h"
-#include "l2cap/le/link_options.h"
#include "os/handler.h"
#include "os/log.h"
@@ -45,7 +43,7 @@ class FixedChannelImpl : public l2cap::internal::ChannelImpl {
/* Return the role we have in the associated link */
virtual hci::Role GetRole() const;
- virtual hci::acl_manager::LeAclConnection* GetAclConnection() const;
+ virtual hci::AclConnection* GetAclConnection() const;
virtual void RegisterOnCloseCallback(os::Handler* user_handler, FixedChannel::OnCloseCallback on_close_callback);
@@ -75,8 +73,6 @@ class FixedChannelImpl : public l2cap::internal::ChannelImpl {
return channel_queue_.GetDownEnd();
}
- LinkOptions* GetLinkOptions();
-
private:
// Constructor states
// For logging purpose only
diff --git a/gd/l2cap/le/internal/fixed_channel_impl_test.cc b/gd/l2cap/le/internal/fixed_channel_impl_test.cc
index 9b5f276f1..d9388f616 100644
--- a/gd/l2cap/le/internal/fixed_channel_impl_test.cc
+++ b/gd/l2cap/le/internal/fixed_channel_impl_test.cc
@@ -63,10 +63,11 @@ class L2capLeFixedChannelImplTest : public ::testing::Test {
TEST_F(L2capLeFixedChannelImplTest, get_device) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetLeLinkIdleDisconnectTimeout()).Times(1);
- testing::MockLeAclConnection* mock_acl_connection = new testing::MockLeAclConnection();
- EXPECT_CALL(*mock_acl_connection, GetRemoteAddress()).Times(1);
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
+ EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
MockLink mock_le_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockLeAclConnection>(mock_acl_connection), nullptr /* LinkManager* */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
AddressWithType device{{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}}, hci::AddressType::PUBLIC_DEVICE_ADDRESS};
EXPECT_CALL(mock_le_link, GetDevice()).WillRepeatedly(Return(device));
LOG_INFO("------------------");
@@ -77,10 +78,11 @@ TEST_F(L2capLeFixedChannelImplTest, get_device) {
TEST_F(L2capLeFixedChannelImplTest, close_triggers_callback) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetLeLinkIdleDisconnectTimeout()).Times(1);
- testing::MockLeAclConnection* mock_acl_connection = new testing::MockLeAclConnection();
- EXPECT_CALL(*mock_acl_connection, GetRemoteAddress()).Times(1);
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
+ EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
MockLink mock_le_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockLeAclConnection>(mock_acl_connection), nullptr /* LinkManager* */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
AddressWithType device{{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}}, hci::AddressType::PUBLIC_DEVICE_ADDRESS};
EXPECT_CALL(mock_le_link, GetDevice()).WillRepeatedly(Return(device));
FixedChannelImpl fixed_channel_impl(kSmpBrCid, &mock_le_link, l2cap_handler_);
@@ -102,10 +104,11 @@ TEST_F(L2capLeFixedChannelImplTest, close_triggers_callback) {
TEST_F(L2capLeFixedChannelImplTest, register_callback_after_close_should_call_immediately) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetLeLinkIdleDisconnectTimeout()).Times(1);
- testing::MockLeAclConnection* mock_acl_connection = new testing::MockLeAclConnection();
- EXPECT_CALL(*mock_acl_connection, GetRemoteAddress()).Times(1);
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
+ EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
MockLink mock_le_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockLeAclConnection>(mock_acl_connection), nullptr /* LinkManager* */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
AddressWithType device{{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}}, hci::AddressType::PUBLIC_DEVICE_ADDRESS};
EXPECT_CALL(mock_le_link, GetDevice()).WillRepeatedly(Return(device));
FixedChannelImpl fixed_channel_impl(kSmpBrCid, &mock_le_link, l2cap_handler_);
@@ -127,10 +130,11 @@ TEST_F(L2capLeFixedChannelImplTest, register_callback_after_close_should_call_im
TEST_F(L2capLeFixedChannelImplTest, close_twice_should_fail) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetLeLinkIdleDisconnectTimeout()).Times(1);
- testing::MockLeAclConnection* mock_acl_connection = new testing::MockLeAclConnection();
- EXPECT_CALL(*mock_acl_connection, GetRemoteAddress()).Times(1);
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
+ EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
MockLink mock_le_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockLeAclConnection>(mock_acl_connection), nullptr /* LinkManager* */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
AddressWithType device{{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}}, hci::AddressType::PUBLIC_DEVICE_ADDRESS};
EXPECT_CALL(mock_le_link, GetDevice()).WillRepeatedly(Return(device));
FixedChannelImpl fixed_channel_impl(kSmpBrCid, &mock_le_link, l2cap_handler_);
@@ -155,10 +159,11 @@ TEST_F(L2capLeFixedChannelImplTest, close_twice_should_fail) {
TEST_F(L2capLeFixedChannelImplTest, multiple_registeration_should_fail) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetLeLinkIdleDisconnectTimeout()).Times(1);
- testing::MockLeAclConnection* mock_acl_connection = new testing::MockLeAclConnection();
- EXPECT_CALL(*mock_acl_connection, GetRemoteAddress()).Times(1);
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
+ EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
MockLink mock_le_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockLeAclConnection>(mock_acl_connection), nullptr /* LinkManager* */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
AddressWithType device{{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}}, hci::AddressType::PUBLIC_DEVICE_ADDRESS};
EXPECT_CALL(mock_le_link, GetDevice()).WillRepeatedly(Return(device));
FixedChannelImpl fixed_channel_impl(kSmpBrCid, &mock_le_link, l2cap_handler_);
@@ -179,10 +184,11 @@ TEST_F(L2capLeFixedChannelImplTest, multiple_registeration_should_fail) {
TEST_F(L2capLeFixedChannelImplTest, call_acquire_before_registeration_should_fail) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetLeLinkIdleDisconnectTimeout()).Times(1);
- testing::MockLeAclConnection* mock_acl_connection = new testing::MockLeAclConnection();
- EXPECT_CALL(*mock_acl_connection, GetRemoteAddress()).Times(1);
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
+ EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
MockLink mock_le_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockLeAclConnection>(mock_acl_connection), nullptr /* LinkManager* */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
AddressWithType device{{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}}, hci::AddressType::PUBLIC_DEVICE_ADDRESS};
EXPECT_CALL(mock_le_link, GetDevice()).WillRepeatedly(Return(device));
FixedChannelImpl fixed_channel_impl(kSmpBrCid, &mock_le_link, l2cap_handler_);
@@ -192,10 +198,11 @@ TEST_F(L2capLeFixedChannelImplTest, call_acquire_before_registeration_should_fai
TEST_F(L2capLeFixedChannelImplTest, call_release_before_registeration_should_fail) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetLeLinkIdleDisconnectTimeout()).Times(1);
- testing::MockLeAclConnection* mock_acl_connection = new testing::MockLeAclConnection();
- EXPECT_CALL(*mock_acl_connection, GetRemoteAddress()).Times(1);
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
+ EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
MockLink mock_le_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockLeAclConnection>(mock_acl_connection), nullptr /* LinkManager* */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
AddressWithType device{{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}}, hci::AddressType::PUBLIC_DEVICE_ADDRESS};
EXPECT_CALL(mock_le_link, GetDevice()).WillRepeatedly(Return(device));
FixedChannelImpl fixed_channel_impl(kSmpBrCid, &mock_le_link, l2cap_handler_);
@@ -205,10 +212,11 @@ TEST_F(L2capLeFixedChannelImplTest, call_release_before_registeration_should_fai
TEST_F(L2capLeFixedChannelImplTest, test_acquire_release_channel) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetLeLinkIdleDisconnectTimeout()).Times(1);
- testing::MockLeAclConnection* mock_acl_connection = new testing::MockLeAclConnection();
- EXPECT_CALL(*mock_acl_connection, GetRemoteAddress()).Times(1);
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
+ EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
MockLink mock_le_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockLeAclConnection>(mock_acl_connection), nullptr /* LinkManager* */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
AddressWithType device{{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}}, hci::AddressType::PUBLIC_DEVICE_ADDRESS};
EXPECT_CALL(mock_le_link, GetDevice()).WillRepeatedly(Return(device));
FixedChannelImpl fixed_channel_impl(kSmpBrCid, &mock_le_link, l2cap_handler_);
@@ -237,10 +245,11 @@ TEST_F(L2capLeFixedChannelImplTest, test_acquire_release_channel) {
TEST_F(L2capLeFixedChannelImplTest, test_acquire_after_close) {
MockParameterProvider mock_parameter_provider;
EXPECT_CALL(mock_parameter_provider, GetLeLinkIdleDisconnectTimeout()).Times(1);
- testing::MockLeAclConnection* mock_acl_connection = new testing::MockLeAclConnection();
- EXPECT_CALL(*mock_acl_connection, GetRemoteAddress()).Times(1);
+ testing::MockAclConnection* mock_acl_connection = new testing::MockAclConnection();
+ EXPECT_CALL(*mock_acl_connection, GetAddress()).Times(1);
+ EXPECT_CALL(*mock_acl_connection, GetAddressType()).Times(1);
MockLink mock_le_link(l2cap_handler_, &mock_parameter_provider,
- std::unique_ptr<testing::MockLeAclConnection>(mock_acl_connection), nullptr /* LinkManager* */);
+ std::unique_ptr<testing::MockAclConnection>(mock_acl_connection));
AddressWithType device{{{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}}, hci::AddressType::PUBLIC_DEVICE_ADDRESS};
EXPECT_CALL(mock_le_link, GetDevice()).WillRepeatedly(Return(device));
FixedChannelImpl fixed_channel_impl(kSmpBrCid, &mock_le_link, l2cap_handler_);
diff --git a/gd/l2cap/le/internal/fixed_channel_service_manager_test.cc b/gd/l2cap/le/internal/fixed_channel_service_manager_test.cc
index efacf9dbd..030933c59 100644
--- a/gd/l2cap/le/internal/fixed_channel_service_manager_test.cc
+++ b/gd/l2cap/le/internal/fixed_channel_service_manager_test.cc
@@ -34,7 +34,7 @@ namespace internal {
class L2capLeServiceManagerTest : public ::testing::Test {
public:
- ~L2capLeServiceManagerTest() = default;
+ ~L2capLeServiceManagerTest() override = default;
void OnServiceRegistered(bool expect_success, FixedChannelManager::RegistrationResult result,
std::unique_ptr<FixedChannelService> user_service) {
diff --git a/gd/l2cap/le/internal/link.cc b/gd/l2cap/le/internal/link.cc
index be759b2b1..37305fb1d 100644
--- a/gd/l2cap/le/internal/link.cc
+++ b/gd/l2cap/le/internal/link.cc
@@ -14,17 +14,15 @@
* limitations under the License.
*/
-#include "l2cap/le/internal/link.h"
-
#include <chrono>
#include <memory>
-#include "hci/acl_manager/le_acl_connection.h"
+#include "hci/acl_manager.h"
#include "l2cap/internal/dynamic_channel_impl.h"
#include "l2cap/internal/parameter_provider.h"
#include "l2cap/le/dynamic_channel_manager.h"
#include "l2cap/le/internal/fixed_channel_impl.h"
-#include "l2cap/le/internal/link_manager.h"
+#include "l2cap/le/internal/link.h"
#include "os/alarm.h"
namespace bluetooth {
@@ -32,131 +30,40 @@ namespace l2cap {
namespace le {
namespace internal {
-static constexpr uint16_t kDefaultMinimumCeLength = 0x0002;
-static constexpr uint16_t kDefaultMaximumCeLength = 0x0C00;
-
-Link::Link(os::Handler* l2cap_handler, std::unique_ptr<hci::acl_manager::LeAclConnection> acl_connection,
+Link::Link(os::Handler* l2cap_handler, std::unique_ptr<hci::AclConnection> acl_connection,
l2cap::internal::ParameterProvider* parameter_provider,
DynamicChannelServiceManagerImpl* dynamic_service_manager,
- FixedChannelServiceManagerImpl* fixed_service_manager, LinkManager* link_manager)
+ FixedChannelServiceManagerImpl* fixed_service_manager)
: l2cap_handler_(l2cap_handler), acl_connection_(std::move(acl_connection)),
data_pipeline_manager_(l2cap_handler, this, acl_connection_->GetAclQueueEnd()),
parameter_provider_(parameter_provider), dynamic_service_manager_(dynamic_service_manager),
signalling_manager_(l2cap_handler_, this, &data_pipeline_manager_, dynamic_service_manager_,
- &dynamic_channel_allocator_),
- link_manager_(link_manager) {
+ &dynamic_channel_allocator_) {
ASSERT(l2cap_handler_ != nullptr);
ASSERT(acl_connection_ != nullptr);
ASSERT(parameter_provider_ != nullptr);
link_idle_disconnect_alarm_.Schedule(common::BindOnce(&Link::Disconnect, common::Unretained(this)),
parameter_provider_->GetLeLinkIdleDisconnectTimeout());
- acl_connection_->RegisterCallbacks(this, l2cap_handler_);
}
-void Link::OnAclDisconnected(hci::ErrorCode reason) {
- fixed_channel_allocator_.OnAclDisconnected(static_cast<hci::ErrorCode>(reason));
- dynamic_channel_allocator_.OnAclDisconnected(static_cast<hci::ErrorCode>(reason));
-}
-
-void Link::OnDisconnection(hci::ErrorCode status) {
- OnAclDisconnected(status);
-
- link_manager_->OnDisconnect(GetAclConnection()->GetRemoteAddress());
-}
-
-void Link::OnConnectionUpdate(
- hci::ErrorCode hci_status,
- uint16_t connection_interval,
- uint16_t connection_latency,
- uint16_t supervision_timeout) {
- LOG_INFO(
- "interval %hx latency %hx supervision_timeout %hx", connection_interval, connection_latency, supervision_timeout);
- if (update_request_signal_id_ != kInvalidSignalId) {
- hci::ErrorCode result = hci::ErrorCode::SUCCESS;
- if (connection_interval > update_request_interval_max_ || connection_interval < update_request_interval_min_ ||
- connection_latency != update_request_latency_ || supervision_timeout != update_request_supervision_timeout_) {
- LOG_INFO("Received connection update complete with different parameters that provided by the Host");
- }
-
- if (!CheckConnectionParameters(connection_interval, connection_interval, connection_latency, supervision_timeout)) {
- result = hci::ErrorCode::UNSPECIFIED_ERROR;
- }
-
- on_connection_update_complete(update_request_signal_id_, result);
- update_request_signal_id_ = kInvalidSignalId;
- }
-}
-
-void Link::OnDataLengthChange(uint16_t tx_octets, uint16_t tx_time, uint16_t rx_octets, uint16_t rx_time) {
- LOG_INFO("tx_octets %hx tx_time %hx rx_octets %hx rx_time %hx", tx_octets, tx_time, rx_octets, rx_time);
-}
-
-void Link::OnReadRemoteVersionInformationComplete(
- hci::ErrorCode hci_status, uint8_t lmp_version, uint16_t manufacturer_name, uint16_t sub_version) {
- LOG_INFO("lmp_version:%hhu manufacturer_name:%hu sub_version:%hu", lmp_version, manufacturer_name, sub_version);
- link_manager_->OnReadRemoteVersionInformationComplete(
- hci_status, GetDevice(), lmp_version, manufacturer_name, sub_version);
-}
-
-void Link::OnPhyUpdate(hci::ErrorCode hci_status, uint8_t tx_phy, uint8_t rx_phy) {}
-
-void Link::OnLocalAddressUpdate(hci::AddressWithType address_with_type) {
- acl_connection_->UpdateLocalAddress(address_with_type);
+void Link::OnAclDisconnected(hci::ErrorCode status) {
+ fixed_channel_allocator_.OnAclDisconnected(status);
+ dynamic_channel_allocator_.OnAclDisconnected(status);
}
void Link::Disconnect() {
acl_connection_->Disconnect(hci::DisconnectReason::REMOTE_USER_TERMINATED_CONNECTION);
}
-void Link::UpdateConnectionParameterFromRemote(SignalId signal_id, uint16_t conn_interval_min,
- uint16_t conn_interval_max, uint16_t conn_latency,
- uint16_t supervision_timeout) {
- acl_connection_->LeConnectionUpdate(conn_interval_min, conn_interval_max, conn_latency, supervision_timeout,
- kDefaultMinimumCeLength, kDefaultMaximumCeLength);
- update_request_signal_id_ = signal_id;
- update_request_interval_min_ = conn_interval_min;
- update_request_interval_max_ = conn_interval_max;
- update_request_latency_ = conn_latency;
- update_request_supervision_timeout_ = supervision_timeout;
-}
-
-bool Link::CheckConnectionParameters(
- uint16_t conn_interval_min, uint16_t conn_interval_max, uint16_t conn_latency, uint16_t supervision_timeout) {
- if (conn_interval_min < 0x0006 || conn_interval_min > 0x0C80 || conn_interval_max < 0x0006 ||
- conn_interval_max > 0x0C80 || conn_latency > 0x01F3 || supervision_timeout < 0x000A ||
- supervision_timeout > 0x0C80) {
- LOG_ERROR("Invalid parameter");
- return false;
- }
-
- // The Maximum interval in milliseconds will be conn_interval_max * 1.25 ms
- // The Timeout in milliseconds will be expected_supervision_timeout * 10 ms
- // The Timeout in milliseconds shall be larger than (1 + Latency) * Interval_Max * 2, where Interval_Max is given in
- // milliseconds.
- uint32_t supervision_timeout_min = (uint32_t)(1 + conn_latency) * conn_interval_max * 2 + 1;
- if (supervision_timeout * 8 < supervision_timeout_min || conn_interval_max < conn_interval_min) {
- LOG_ERROR("Invalid parameter");
- return false;
- }
-
- return true;
-}
-
-void Link::SendConnectionParameterUpdate(uint16_t conn_interval_min, uint16_t conn_interval_max, uint16_t conn_latency,
- uint16_t supervision_timeout, uint16_t min_ce_length, uint16_t max_ce_length) {
- if (acl_connection_->GetRole() == hci::Role::PERIPHERAL) {
- // TODO: If both LL central and peripheral support 4.1, use HCI command directly
- signalling_manager_.SendConnectionParameterUpdateRequest(conn_interval_min, conn_interval_max, conn_latency,
- supervision_timeout);
- return;
- }
- acl_connection_->LeConnectionUpdate(conn_interval_min, conn_interval_max, conn_latency, supervision_timeout,
- min_ce_length, max_ce_length);
- update_request_signal_id_ = kInvalidSignalId;
+void Link::UpdateConnectionParameter(SignalId signal_id, uint16_t conn_interval_min, uint16_t conn_interval_max,
+ uint16_t conn_latency, uint16_t supervision_timeout) {
+ acl_connection_->LeConnectionUpdate(
+ conn_interval_min, conn_interval_max, conn_latency, supervision_timeout,
+ common::BindOnce(&Link::on_connection_update_complete, common::Unretained(this), signal_id), l2cap_handler_);
}
std::shared_ptr<FixedChannelImpl> Link::AllocateFixedChannel(Cid cid, SecurityPolicy security_policy) {
- auto channel = fixed_channel_allocator_.AllocateChannel(cid);
+ auto channel = fixed_channel_allocator_.AllocateChannel(cid, security_policy);
data_pipeline_manager_.AttachChannel(cid, channel, l2cap::internal::DataPipelineManager::ChannelMode::BASIC);
return channel;
}
@@ -175,9 +82,7 @@ void Link::SendConnectionRequest(Psm psm, PendingDynamicChannelConnection pendin
return;
}
auto reserved_cid = ReserveDynamicChannel();
- auto mtu = pending_dynamic_channel_connection.configuration_.mtu;
- local_cid_to_pending_dynamic_channel_connection_map_[reserved_cid] = std::move(pending_dynamic_channel_connection);
- signalling_manager_.SendConnectionRequest(psm, reserved_cid, mtu);
+ signalling_manager_.SendConnectionRequest(psm, reserved_cid, pending_dynamic_channel_connection.configuration_.mtu);
}
void Link::SendDisconnectionRequest(Cid local_cid, Cid remote_cid) {
@@ -188,23 +93,14 @@ void Link::SendDisconnectionRequest(Cid local_cid, Cid remote_cid) {
signalling_manager_.SendDisconnectRequest(local_cid, remote_cid);
}
-void Link::OnOutgoingConnectionRequestFail(Cid local_cid, LeCreditBasedConnectionResponseResult response_result) {
- if (local_cid_to_pending_dynamic_channel_connection_map_.find(local_cid) !=
- local_cid_to_pending_dynamic_channel_connection_map_.end()) {
- // TODO(hsz): Currently we only notify the client when the remote didn't send connection response SUCCESS.
- // Should we notify the client when the link failed to establish?
- DynamicChannelManager::ConnectionResult result{
- .connection_result_code = DynamicChannelManager::ConnectionResultCode::FAIL_L2CAP_ERROR,
- .hci_error = hci::ErrorCode::SUCCESS,
- .l2cap_connection_response_result = response_result,
- };
- NotifyChannelFail(local_cid, result);
- }
+void Link::OnOutgoingConnectionRequestFail(Cid local_cid) {
+ local_cid_to_pending_dynamic_channel_connection_map_.erase(local_cid);
dynamic_channel_allocator_.FreeChannel(local_cid);
}
-std::shared_ptr<l2cap::internal::DynamicChannelImpl> Link::AllocateDynamicChannel(Psm psm, Cid remote_cid) {
- auto channel = dynamic_channel_allocator_.AllocateChannel(psm, remote_cid);
+std::shared_ptr<l2cap::internal::DynamicChannelImpl> Link::AllocateDynamicChannel(Psm psm, Cid remote_cid,
+ SecurityPolicy security_policy) {
+ auto channel = dynamic_channel_allocator_.AllocateChannel(psm, remote_cid, security_policy);
if (channel != nullptr) {
data_pipeline_manager_.AttachChannel(channel->GetCid(), channel,
l2cap::internal::DataPipelineManager::ChannelMode::LE_CREDIT_BASED);
@@ -214,9 +110,9 @@ std::shared_ptr<l2cap::internal::DynamicChannelImpl> Link::AllocateDynamicChanne
return channel;
}
-std::shared_ptr<l2cap::internal::DynamicChannelImpl> Link::AllocateReservedDynamicChannel(Cid reserved_cid, Psm psm,
- Cid remote_cid) {
- auto channel = dynamic_channel_allocator_.AllocateReservedChannel(reserved_cid, psm, remote_cid);
+std::shared_ptr<l2cap::internal::DynamicChannelImpl> Link::AllocateReservedDynamicChannel(
+ Cid reserved_cid, Psm psm, Cid remote_cid, SecurityPolicy security_policy) {
+ auto channel = dynamic_channel_allocator_.AllocateReservedChannel(reserved_cid, psm, remote_cid, security_policy);
if (channel != nullptr) {
data_pipeline_manager_.AttachChannel(channel->GetCid(), channel,
l2cap::internal::DataPipelineManager::ChannelMode::LE_CREDIT_BASED);
@@ -226,6 +122,12 @@ std::shared_ptr<l2cap::internal::DynamicChannelImpl> Link::AllocateReservedDynam
return channel;
}
+DynamicChannelConfigurationOption Link::GetConfigurationForInitialConfiguration(Cid cid) {
+ ASSERT(local_cid_to_pending_dynamic_channel_connection_map_.find(cid) !=
+ local_cid_to_pending_dynamic_channel_connection_map_.end());
+ return local_cid_to_pending_dynamic_channel_connection_map_[cid].configuration_;
+}
+
void Link::FreeDynamicChannel(Cid cid) {
if (dynamic_channel_allocator_.FindChannelByCid(cid) == nullptr) {
return;
@@ -257,11 +159,12 @@ void Link::NotifyChannelCreation(Cid cid, std::unique_ptr<DynamicChannel> user_c
local_cid_to_pending_dynamic_channel_connection_map_.erase(cid);
}
-void Link::NotifyChannelFail(Cid cid, DynamicChannelManager::ConnectionResult result) {
+void Link::NotifyChannelFail(Cid cid) {
ASSERT(local_cid_to_pending_dynamic_channel_connection_map_.find(cid) !=
local_cid_to_pending_dynamic_channel_connection_map_.end());
auto& pending_dynamic_channel_connection = local_cid_to_pending_dynamic_channel_connection_map_[cid];
// TODO(cmanton) Pass proper connection falure result to user
+ DynamicChannelManager::ConnectionResult result;
pending_dynamic_channel_connection.handler_->Post(
common::BindOnce(std::move(pending_dynamic_channel_connection.on_fail_callback_), result));
local_cid_to_pending_dynamic_channel_connection_map_.erase(cid);
@@ -279,30 +182,13 @@ void Link::SendLeCredit(Cid local_cid, uint16_t credit) {
signalling_manager_.SendCredit(local_cid, credit);
}
-void Link::ReadRemoteVersionInformation() {
- acl_connection_->ReadRemoteVersionInformation();
-}
-
void Link::on_connection_update_complete(SignalId signal_id, hci::ErrorCode error_code) {
- if (!signal_id.IsValid()) {
- LOG_INFO("Invalid signal_id");
- return;
- }
ConnectionParameterUpdateResponseResult result = (error_code == hci::ErrorCode::SUCCESS)
? ConnectionParameterUpdateResponseResult::ACCEPTED
: ConnectionParameterUpdateResponseResult::REJECTED;
signalling_manager_.SendConnectionParameterUpdateResponse(SignalId(), result);
}
-void Link::OnPendingPacketChange(Cid local_cid, bool has_packet) {
- if (has_packet) {
- remaining_packets_to_be_sent_++;
- } else {
- remaining_packets_to_be_sent_--;
- }
- link_manager_->OnPendingPacketChange(GetDevice(), remaining_packets_to_be_sent_);
-}
-
} // namespace internal
} // namespace le
} // namespace l2cap
diff --git a/gd/l2cap/le/internal/link.h b/gd/l2cap/le/internal/link.h
index 518793eb3..3c9085689 100644
--- a/gd/l2cap/le/internal/link.h
+++ b/gd/l2cap/le/internal/link.h
@@ -16,11 +16,10 @@
#pragma once
-#include <atomic>
#include <chrono>
#include <memory>
-#include "hci/acl_manager/le_acl_connection.h"
+#include "hci/acl_manager.h"
#include "l2cap/internal/data_pipeline_manager.h"
#include "l2cap/internal/dynamic_channel_allocator.h"
#include "l2cap/internal/fixed_channel_allocator.h"
@@ -31,8 +30,6 @@
#include "l2cap/le/internal/fixed_channel_impl.h"
#include "l2cap/le/internal/fixed_channel_service_manager_impl.h"
#include "l2cap/le/internal/signalling_manager.h"
-#include "l2cap/le/link_options.h"
-#include "l2cap/le/security_enforcement_interface.h"
#include "os/alarm.h"
namespace bluetooth {
@@ -40,19 +37,17 @@ namespace l2cap {
namespace le {
namespace internal {
-class LinkManager;
-
-class Link : public l2cap::internal::ILink, public hci::acl_manager::LeConnectionManagementCallbacks {
+class Link : public l2cap::internal::ILink {
public:
- Link(os::Handler* l2cap_handler, std::unique_ptr<hci::acl_manager::LeAclConnection> acl_connection,
+ Link(os::Handler* l2cap_handler, std::unique_ptr<hci::AclConnection> acl_connection,
l2cap::internal::ParameterProvider* parameter_provider,
- DynamicChannelServiceManagerImpl* dynamic_service_manager, FixedChannelServiceManagerImpl* fixed_service_manager,
- LinkManager* link_manager);
+ DynamicChannelServiceManagerImpl* dynamic_service_manager,
+ FixedChannelServiceManagerImpl* fixed_service_manager);
- ~Link() = default;
+ ~Link() override = default;
- inline hci::AddressWithType GetDevice() const override {
- return acl_connection_->GetRemoteAddress();
+ inline hci::AddressWithType GetDevice() override {
+ return {acl_connection_->GetAddress(), acl_connection_->GetAddressType()};
}
struct PendingDynamicChannelConnection {
@@ -66,42 +61,19 @@ class Link : public l2cap::internal::ILink, public hci::acl_manager::LeConnectio
return acl_connection_->GetRole();
}
- inline virtual hci::acl_manager::LeAclConnection* GetAclConnection() {
+ inline virtual hci::AclConnection* GetAclConnection() {
return acl_connection_.get();
}
// ACL methods
- virtual void OnAclDisconnected(hci::ErrorCode reason);
-
- void OnDisconnection(hci::ErrorCode reason) override;
-
- void OnConnectionUpdate(
- hci::ErrorCode hci_status,
- uint16_t connection_interval,
- uint16_t connection_latency,
- uint16_t supervision_timeout) override;
-
- void OnDataLengthChange(uint16_t tx_octets, uint16_t tx_time, uint16_t rx_octets, uint16_t rx_time) override;
-
- void OnReadRemoteVersionInformationComplete(
- hci::ErrorCode hci_status, uint8_t lmp_version, uint16_t manufacturer_name, uint16_t sub_version) override;
- void OnPhyUpdate(hci::ErrorCode hci_status, uint8_t tx_phy, uint8_t rx_phy) override;
-
- void OnLocalAddressUpdate(hci::AddressWithType address_with_type) override;
+ virtual void OnAclDisconnected(hci::ErrorCode status);
virtual void Disconnect();
// Handles connection parameter update request from remote
- virtual void UpdateConnectionParameterFromRemote(SignalId signal_id, uint16_t conn_interval_min,
- uint16_t conn_interval_max, uint16_t conn_latency,
- uint16_t supervision_timeout);
- virtual bool CheckConnectionParameters(
- uint16_t conn_interval_min, uint16_t conn_interval_max, uint16_t conn_latency, uint16_t supervision_timeout);
-
- virtual void SendConnectionParameterUpdate(uint16_t conn_interval_min, uint16_t conn_interval_max,
- uint16_t conn_latency, uint16_t supervision_timeout,
- uint16_t min_ce_length, uint16_t max_ce_length);
+ virtual void UpdateConnectionParameter(SignalId signal_id, uint16_t conn_interval_min, uint16_t conn_interval_max,
+ uint16_t conn_latency, uint16_t supervision_timeout);
// FixedChannel methods
@@ -118,12 +90,15 @@ class Link : public l2cap::internal::ILink, public hci::acl_manager::LeConnectio
void SendDisconnectionRequest(Cid local_cid, Cid remote_cid) override;
// Invoked by signalling manager to indicate an outgoing connection request failed and link shall free resources
- virtual void OnOutgoingConnectionRequestFail(Cid local_cid, LeCreditBasedConnectionResponseResult result);
+ virtual void OnOutgoingConnectionRequestFail(Cid local_cid);
+
+ virtual std::shared_ptr<l2cap::internal::DynamicChannelImpl> AllocateDynamicChannel(Psm psm, Cid remote_cid,
+ SecurityPolicy security_policy);
- virtual std::shared_ptr<l2cap::internal::DynamicChannelImpl> AllocateDynamicChannel(Psm psm, Cid remote_cid);
+ virtual std::shared_ptr<l2cap::internal::DynamicChannelImpl> AllocateReservedDynamicChannel(
+ Cid reserved_cid, Psm psm, Cid remote_cid, SecurityPolicy security_policy);
- virtual std::shared_ptr<l2cap::internal::DynamicChannelImpl> AllocateReservedDynamicChannel(Cid reserved_cid, Psm psm,
- Cid remote_cid);
+ virtual DynamicChannelConfigurationOption GetConfigurationForInitialConfiguration(Cid cid);
virtual void FreeDynamicChannel(Cid cid);
@@ -131,7 +106,7 @@ class Link : public l2cap::internal::ILink, public hci::acl_manager::LeConnectio
virtual void RefreshRefCount();
void NotifyChannelCreation(Cid cid, std::unique_ptr<DynamicChannel> user_channel);
- void NotifyChannelFail(Cid cid, DynamicChannelManager::ConnectionResult result);
+ void NotifyChannelFail(Cid cid);
virtual std::string ToString() {
return GetDevice().ToString();
@@ -143,38 +118,19 @@ class Link : public l2cap::internal::ILink, public hci::acl_manager::LeConnectio
void SendLeCredit(Cid local_cid, uint16_t credit) override;
- LinkOptions* GetLinkOptions() {
- return &link_options_;
- }
-
- void ReadRemoteVersionInformation();
-
- void OnPendingPacketChange(Cid local_cid, bool has_packet) override;
-
private:
os::Handler* l2cap_handler_;
l2cap::internal::FixedChannelAllocator<FixedChannelImpl, Link> fixed_channel_allocator_{this, l2cap_handler_};
l2cap::internal::DynamicChannelAllocator dynamic_channel_allocator_{this, l2cap_handler_};
- std::unique_ptr<hci::acl_manager::LeAclConnection> acl_connection_;
+ std::unique_ptr<hci::AclConnection> acl_connection_;
l2cap::internal::DataPipelineManager data_pipeline_manager_;
l2cap::internal::ParameterProvider* parameter_provider_;
DynamicChannelServiceManagerImpl* dynamic_service_manager_;
LeSignallingManager signalling_manager_;
std::unordered_map<Cid, PendingDynamicChannelConnection> local_cid_to_pending_dynamic_channel_connection_map_;
os::Alarm link_idle_disconnect_alarm_{l2cap_handler_};
- LinkOptions link_options_{acl_connection_.get(), this, l2cap_handler_};
- LinkManager* link_manager_;
- SignalId update_request_signal_id_ = kInvalidSignalId;
- uint16_t update_request_interval_min_;
- uint16_t update_request_interval_max_;
- uint16_t update_request_latency_;
- uint16_t update_request_supervision_timeout_;
- std::atomic_int remaining_packets_to_be_sent_ = 0;
DISALLOW_COPY_AND_ASSIGN(Link);
- // Received connection update complete from ACL manager. SignalId is bound to a valid number when we need to send a
- // response to remote. If SignalId is bound to an invalid number, we don't send a response to remote, because the
- // connection update request is not from remote LL peripheral.
void on_connection_update_complete(SignalId signal_id, hci::ErrorCode error_code);
};
diff --git a/gd/l2cap/le/internal/link_manager.cc b/gd/l2cap/le/internal/link_manager.cc
index f2677a3bf..35a3ff23f 100644
--- a/gd/l2cap/le/internal/link_manager.cc
+++ b/gd/l2cap/le/internal/link_manager.cc
@@ -16,7 +16,7 @@
#include <memory>
#include <unordered_map>
-#include "hci/acl_manager/le_acl_connection.h"
+#include "hci/acl_manager.h"
#include "hci/address.h"
#include "l2cap/internal/scheduler_fifo.h"
#include "l2cap/le/internal/link.h"
@@ -54,8 +54,7 @@ void LinkManager::ConnectFixedChannelServices(hci::AddressWithType address_with_
continue;
}
// Allocate channel for newly registered fixed channels
- auto fixed_channel_impl = link->AllocateFixedChannel(
- fixed_channel_service.first, SecurityPolicy::NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK);
+ auto fixed_channel_impl = link->AllocateFixedChannel(fixed_channel_service.first, SecurityPolicy());
fixed_channel_service.second->NotifyChannelCreation(
std::make_unique<FixedChannel>(fixed_channel_impl, l2cap_handler_));
num_new_channels++;
@@ -80,14 +79,14 @@ void LinkManager::ConnectFixedChannelServices(hci::AddressWithType address_with_
}
pending_link->second.pending_fixed_channel_connections_.push_back(std::move(pending_fixed_channel_connection));
// Then create new ACL connection
- acl_manager_->CreateLeConnection(address_with_type, /* is_direct */ true);
+ acl_manager_->CreateLeConnection(address_with_type);
}
void LinkManager::ConnectDynamicChannelServices(
hci::AddressWithType device, Link::PendingDynamicChannelConnection pending_dynamic_channel_connection, Psm psm) {
auto* link = GetLink(device);
if (link == nullptr) {
- acl_manager_->CreateLeConnection(device, /* is_direct */ true);
+ acl_manager_->CreateLeConnection(device);
pending_dynamic_channels_[device].push_back(std::make_pair(psm, std::move(pending_dynamic_channel_connection)));
return;
}
@@ -102,29 +101,40 @@ Link* LinkManager::GetLink(hci::AddressWithType address_with_type) {
}
void LinkManager::OnLeConnectSuccess(hci::AddressWithType connecting_address_with_type,
- std::unique_ptr<hci::acl_manager::LeAclConnection> acl_connection) {
+ std::unique_ptr<hci::AclConnection> acl_connection) {
// Same link should not be connected twice
- hci::AddressWithType connected_address_with_type = acl_connection->GetRemoteAddress();
- uint16_t handle = acl_connection->GetHandle();
+ hci::AddressWithType connected_address_with_type(acl_connection->GetAddress(), acl_connection->GetAddressType());
ASSERT_LOG(GetLink(connected_address_with_type) == nullptr, "%s is connected twice without disconnection",
- acl_connection->GetRemoteAddress().ToString().c_str());
+ acl_connection->GetAddress().ToString().c_str());
+ // Register ACL disconnection callback in LinkManager so that we can clean up link resource properly
+ acl_connection->RegisterDisconnectCallback(
+ common::BindOnce(&LinkManager::OnDisconnect, common::Unretained(this), connected_address_with_type),
+ l2cap_handler_);
links_.try_emplace(connected_address_with_type, l2cap_handler_, std::move(acl_connection), parameter_provider_,
- dynamic_channel_service_manager_, fixed_channel_service_manager_, this);
+ dynamic_channel_service_manager_, fixed_channel_service_manager_);
auto* link = GetLink(connected_address_with_type);
-
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(
- link_property_listener_,
- &LinkPropertyListener::OnLinkConnected,
- connected_address_with_type,
- handle,
- link->GetRole());
+ // Allocate and distribute channels for all registered fixed channel services
+ auto fixed_channel_services = fixed_channel_service_manager_->GetRegisteredServices();
+ for (auto& fixed_channel_service : fixed_channel_services) {
+ auto fixed_channel_impl = link->AllocateFixedChannel(fixed_channel_service.first, SecurityPolicy());
+ fixed_channel_service.second->NotifyChannelCreation(
+ std::make_unique<FixedChannel>(fixed_channel_impl, l2cap_handler_));
+ }
+ if (pending_dynamic_channels_.find(connected_address_with_type) != pending_dynamic_channels_.end()) {
+ for (auto& psm_callback : pending_dynamic_channels_[connected_address_with_type]) {
+ link->SendConnectionRequest(psm_callback.first, std::move(psm_callback.second));
+ }
+ pending_dynamic_channels_.erase(connected_address_with_type);
}
// Remove device from pending links list, if any
- pending_links_.erase(connecting_address_with_type);
-
- link->ReadRemoteVersionInformation();
+ auto pending_link = pending_links_.find(connecting_address_with_type);
+ if (pending_link == pending_links_.end()) {
+ // This an incoming connection, exit
+ return;
+ }
+ // This is an outgoing connection, remove entry in pending link list
+ pending_links_.erase(pending_link);
}
void LinkManager::OnLeConnectFail(hci::AddressWithType address_with_type, hci::ErrorCode reason) {
@@ -132,7 +142,7 @@ void LinkManager::OnLeConnectFail(hci::AddressWithType address_with_type, hci::E
auto pending_link = pending_links_.find(address_with_type);
if (pending_link == pending_links_.end()) {
// There is no pending link, exit
- LOG_INFO("Connection to %s failed without a pending link", address_with_type.ToString().c_str());
+ LOG_DEBUG("Connection to %s failed without a pending link", address_with_type.ToString().c_str());
return;
}
for (auto& pending_fixed_channel_connection : pending_link->second.pending_fixed_channel_connections_) {
@@ -145,70 +155,12 @@ void LinkManager::OnLeConnectFail(hci::AddressWithType address_with_type, hci::E
pending_links_.erase(pending_link);
}
-void LinkManager::OnDisconnect(bluetooth::hci::AddressWithType address_with_type) {
- auto* link = GetLink(address_with_type);
- ASSERT_LOG(link != nullptr, "Device %s is disconnected but not in local database",
- address_with_type.ToString().c_str());
- if (links_with_pending_packets_.count(address_with_type) != 0) {
- disconnected_links_.emplace(address_with_type);
- } else {
- links_.erase(address_with_type);
- }
-
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(
- link_property_listener_, &LinkPropertyListener::OnLinkDisconnected, address_with_type);
- }
-}
-
-void LinkManager::RegisterLinkPropertyListener(os::Handler* handler, LinkPropertyListener* listener) {
- link_property_callback_handler_ = handler;
- link_property_listener_ = listener;
-}
-
-void LinkManager::OnReadRemoteVersionInformationComplete(
- hci::ErrorCode hci_status,
- hci::AddressWithType address_with_type,
- uint8_t lmp_version,
- uint16_t manufacturer_name,
- uint16_t sub_version) {
- if (link_property_callback_handler_ != nullptr) {
- link_property_callback_handler_->CallOn(
- link_property_listener_,
- &LinkPropertyListener::OnReadRemoteVersionInformation,
- hci_status,
- address_with_type,
- lmp_version,
- manufacturer_name,
- sub_version);
- }
-
+void LinkManager::OnDisconnect(hci::AddressWithType address_with_type, hci::ErrorCode status) {
auto* link = GetLink(address_with_type);
- // Allocate and distribute channels for all registered fixed channel services
- auto fixed_channel_services = fixed_channel_service_manager_->GetRegisteredServices();
- for (auto& fixed_channel_service : fixed_channel_services) {
- auto fixed_channel_impl = link->AllocateFixedChannel(
- fixed_channel_service.first, SecurityPolicy::NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK);
- fixed_channel_service.second->NotifyChannelCreation(
- std::make_unique<FixedChannel>(fixed_channel_impl, l2cap_handler_));
- }
- if (pending_dynamic_channels_.find(address_with_type) != pending_dynamic_channels_.end()) {
- for (auto& psm_callback : pending_dynamic_channels_[address_with_type]) {
- link->SendConnectionRequest(psm_callback.first, std::move(psm_callback.second));
- }
- pending_dynamic_channels_.erase(address_with_type);
- }
-}
-
-void LinkManager::OnPendingPacketChange(hci::AddressWithType remote, int num_packets) {
- if (disconnected_links_.count(remote) != 0 && num_packets == 0) {
- links_.erase(remote);
- links_with_pending_packets_.erase(remote);
- } else if (num_packets != 0) {
- links_with_pending_packets_.emplace(remote);
- } else {
- links_with_pending_packets_.erase(remote);
- }
+ ASSERT_LOG(link != nullptr, "Device %s is disconnected with reason 0x%x, but not in local database",
+ address_with_type.ToString().c_str(), static_cast<uint8_t>(status));
+ link->OnAclDisconnected(status);
+ links_.erase(address_with_type);
}
} // namespace internal
diff --git a/gd/l2cap/le/internal/link_manager.h b/gd/l2cap/le/internal/link_manager.h
index c6ec046ec..9e9c0e821 100644
--- a/gd/l2cap/le/internal/link_manager.h
+++ b/gd/l2cap/le/internal/link_manager.h
@@ -18,40 +18,29 @@
#include <memory>
#include <unordered_map>
-#include <unordered_set>
#include <utility>
#include "os/handler.h"
-#include "hci/acl_manager/le_acl_connection.h"
+#include "hci/acl_manager.h"
#include "hci/address.h"
#include "hci/address_with_type.h"
-#include "hci/le_advertising_manager.h"
#include "l2cap/internal/parameter_provider.h"
#include "l2cap/internal/scheduler.h"
#include "l2cap/le/fixed_channel_manager.h"
-#include "l2cap/le/internal/dynamic_channel_service_manager_impl.h"
#include "l2cap/le/internal/fixed_channel_service_manager_impl.h"
#include "l2cap/le/internal/link.h"
-#include "l2cap/le/link_property_listener.h"
namespace bluetooth {
namespace l2cap {
namespace le {
namespace internal {
-class LinkManager : public hci::acl_manager::LeConnectionCallbacks {
+class LinkManager : public hci::LeConnectionCallbacks {
public:
- LinkManager(
- os::Handler* l2cap_handler,
- hci::AclManager* acl_manager,
- FixedChannelServiceManagerImpl* service_manager,
- DynamicChannelServiceManagerImpl* dynamic_service_manager,
- l2cap::internal::ParameterProvider* parameter_provider)
- : l2cap_handler_(l2cap_handler),
- acl_manager_(acl_manager),
- fixed_channel_service_manager_(service_manager),
- dynamic_channel_service_manager_(dynamic_service_manager),
+ LinkManager(os::Handler* l2cap_handler, hci::AclManager* acl_manager, FixedChannelServiceManagerImpl* service_manager,
+ l2cap::internal::ParameterProvider* parameter_provider)
+ : l2cap_handler_(l2cap_handler), acl_manager_(acl_manager), fixed_channel_service_manager_(service_manager),
parameter_provider_(parameter_provider) {
acl_manager_->RegisterLeCallbacks(this, l2cap_handler_);
}
@@ -69,8 +58,9 @@ class LinkManager : public hci::acl_manager::LeConnectionCallbacks {
Link* GetLink(hci::AddressWithType address_with_type);
void OnLeConnectSuccess(hci::AddressWithType connecting_address_with_type,
- std::unique_ptr<hci::acl_manager::LeAclConnection> acl_connection) override;
+ std::unique_ptr<hci::AclConnection> acl_connection) override;
void OnLeConnectFail(hci::AddressWithType address_with_type, hci::ErrorCode reason) override;
+ void OnDisconnect(hci::AddressWithType address_with_type, hci::ErrorCode status);
// FixedChannelManager methods
@@ -82,23 +72,6 @@ class LinkManager : public hci::acl_manager::LeConnectionCallbacks {
void ConnectDynamicChannelServices(hci::AddressWithType device,
Link::PendingDynamicChannelConnection pending_dynamic_channel_connection, Psm psm);
- void OnDisconnect(hci::AddressWithType address_with_type);
-
- // Link methods
-
- void RegisterLinkPropertyListener(os::Handler* handler, LinkPropertyListener* listener);
-
- void OnReadRemoteVersionInformationComplete(
- hci::ErrorCode hci_status,
- hci::AddressWithType address_with_type,
- uint8_t lmp_version,
- uint16_t manufacturer_name,
- uint16_t sub_version);
-
- // Reported by link to indicate how many pending packets are remaining to be set.
- // If there is anything outstanding, don't delete link
- void OnPendingPacketChange(hci::AddressWithType remote, int num_packets);
-
private:
// Dependencies
os::Handler* l2cap_handler_;
@@ -112,11 +85,6 @@ class LinkManager : public hci::acl_manager::LeConnectionCallbacks {
std::unordered_map<hci::AddressWithType, Link> links_;
std::unordered_map<hci::AddressWithType, std::list<std::pair<Psm, Link::PendingDynamicChannelConnection>>>
pending_dynamic_channels_;
- os::Handler* link_property_callback_handler_ = nullptr;
- LinkPropertyListener* link_property_listener_ = nullptr;
- std::unordered_set<hci::AddressWithType> disconnected_links_;
- std::unordered_set<hci::AddressWithType> links_with_pending_packets_;
-
DISALLOW_COPY_AND_ASSIGN(LinkManager);
};
diff --git a/gd/l2cap/le/internal/link_manager_test.cc b/gd/l2cap/le/internal/link_manager_test.cc
index c7585f7f0..cbef3f3f5 100644
--- a/gd/l2cap/le/internal/link_manager_test.cc
+++ b/gd/l2cap/le/internal/link_manager_test.cc
@@ -40,8 +40,8 @@ namespace le {
namespace internal {
namespace {
+using hci::testing::MockAclConnection;
using hci::testing::MockAclManager;
-using hci::testing::MockLeAclConnection;
using l2cap::internal::testing::MockParameterProvider;
using ::testing::_; // Matcher to any value
using ::testing::ByMove;
@@ -67,7 +67,6 @@ class L2capLeLinkManagerTest : public ::testing::Test {
void SetUp() override {
thread_ = new os::Thread("test_thread", os::Thread::Priority::NORMAL);
l2cap_handler_ = new os::Handler(thread_);
- user_handler_ = new os::Handler(thread_);
mock_parameter_provider_ = new MockParameterProvider;
EXPECT_CALL(*mock_parameter_provider_, GetLeLinkIdleDisconnectTimeout)
.WillRepeatedly(Return(kTestIdleDisconnectTimeoutLong));
@@ -77,14 +76,11 @@ class L2capLeLinkManagerTest : public ::testing::Test {
delete mock_parameter_provider_;
l2cap_handler_->Clear();
delete l2cap_handler_;
- user_handler_->Clear();
- delete user_handler_;
delete thread_;
}
os::Thread* thread_ = nullptr;
os::Handler* l2cap_handler_ = nullptr;
- os::Handler* user_handler_ = nullptr;
MockParameterProvider* mock_parameter_provider_ = nullptr;
};
@@ -93,18 +89,15 @@ TEST_F(L2capLeLinkManagerTest, connect_fixed_channel_service_without_acl) {
MockAclManager mock_acl_manager;
hci::AddressWithType address_with_type({{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::RANDOM_DEVICE_ADDRESS);
+ auto user_handler = os::Handler(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
+ hci::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterLeCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_le_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
- LinkManager le_link_manager(
- l2cap_handler_,
- &mock_acl_manager,
- &mock_le_fixed_channel_service_manager,
- nullptr,
- mock_parameter_provider_);
+ LinkManager le_link_manager(l2cap_handler_, &mock_acl_manager, &mock_le_fixed_channel_service_manager,
+ mock_parameter_provider_);
EXPECT_EQ(hci_le_connection_callbacks, &le_link_manager);
EXPECT_EQ(hci_callback_handler, l2cap_handler_);
@@ -116,19 +109,18 @@ TEST_F(L2capLeLinkManagerTest, connect_fixed_channel_service_without_acl) {
EXPECT_CALL(mock_le_fixed_channel_service_manager, GetRegisteredServices()).WillRepeatedly(Return(results));
// Step 2: Connect to fixed channel without ACL connection should trigger ACL connection process
- EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type, true)).Times(1);
+ EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type)).Times(1);
LinkManager::PendingFixedChannelConnection pending_fixed_channel_connection{
- .handler_ = user_handler_,
+ .handler_ = &user_handler,
.on_fail_callback_ = common::BindOnce([](FixedChannelManager::ConnectionResult result) { FAIL(); })};
le_link_manager.ConnectFixedChannelServices(address_with_type, std::move(pending_fixed_channel_connection));
// Step 3: ACL connection success event should trigger channel creation for all registered services
- std::unique_ptr<MockLeAclConnection> acl_connection = std::make_unique<MockLeAclConnection>();
- EXPECT_CALL(*acl_connection, GetRemoteAddress()).WillRepeatedly(Return(address_with_type));
- hci::acl_manager::LeConnectionManagementCallbacks* connection_management_callbacks = nullptr;
- os::Handler* connection_management_handler = nullptr;
- EXPECT_CALL(*acl_connection, RegisterCallbacks(_, _))
- .WillOnce(DoAll(SaveArg<0>(&connection_management_callbacks), SaveArg<1>(&connection_management_handler)));
+
+ std::unique_ptr<MockAclConnection> acl_connection = std::make_unique<MockAclConnection>();
+ EXPECT_CALL(*acl_connection, RegisterDisconnectCallback(_, l2cap_handler_)).Times(1);
+ EXPECT_CALL(*acl_connection, GetAddress()).WillRepeatedly(Return(address_with_type.GetAddress()));
+ EXPECT_CALL(*acl_connection, GetAddressType()).WillRepeatedly(Return(address_with_type.GetAddressType()));
std::unique_ptr<FixedChannel> channel_1, channel_2;
std::promise<void> promise_1, promise_2;
auto future_1 = promise_1.get_future();
@@ -143,32 +135,25 @@ TEST_F(L2capLeLinkManagerTest, connect_fixed_channel_service_without_acl) {
channel_2 = std::move(channel);
promise_2.set_value();
});
- hci_callback_handler->Post(common::BindOnce(&hci::acl_manager::LeConnectionCallbacks::OnLeConnectSuccess,
+ hci_callback_handler->Post(common::BindOnce(&hci::LeConnectionCallbacks::OnLeConnectSuccess,
common::Unretained(hci_le_connection_callbacks), address_with_type,
std::move(acl_connection)));
SyncHandler(hci_callback_handler);
- connection_management_handler->Post(common::BindOnce(
- &hci::acl_manager::LeConnectionManagementCallbacks::OnReadRemoteVersionInformationComplete,
- common::Unretained(connection_management_callbacks),
- hci::ErrorCode::SUCCESS,
- 0,
- 0,
- 0));
auto future_1_status = future_1.wait_for(kTestIdleDisconnectTimeoutShort);
EXPECT_EQ(future_1_status, std::future_status::ready);
auto future_2_status = future_2.wait_for(kTestIdleDisconnectTimeoutShort);
EXPECT_EQ(future_2_status, std::future_status::ready);
- ASSERT_NE(channel_1, nullptr);
- ASSERT_NE(channel_2, nullptr);
+ EXPECT_NE(channel_1, nullptr);
+ EXPECT_NE(channel_2, nullptr);
- // Step 4: Calling ConnectServices() to the same device will not trigger another connection attempt
+ // Step 4: Calling ConnectServices() to the same device will no trigger another connection attempt
FixedChannelManager::ConnectionResult my_result;
LinkManager::PendingFixedChannelConnection pending_fixed_channel_connection_2{
- .handler_ = user_handler_,
+ .handler_ = &user_handler,
.on_fail_callback_ = common::testing::BindLambdaForTesting(
[&my_result](FixedChannelManager::ConnectionResult result) { my_result = result; })};
le_link_manager.ConnectFixedChannelServices(address_with_type, std::move(pending_fixed_channel_connection_2));
- SyncHandler(user_handler_);
+ SyncHandler(&user_handler);
EXPECT_EQ(my_result.connection_result_code,
FixedChannelManager::ConnectionResultCode::FAIL_ALL_SERVICES_HAVE_CHANNEL);
@@ -177,7 +162,7 @@ TEST_F(L2capLeLinkManagerTest, connect_fixed_channel_service_without_acl) {
results.emplace_back(kSmpBrCid + 1, &mock_service_3);
EXPECT_CALL(mock_le_fixed_channel_service_manager, GetRegisteredServices()).WillRepeatedly(Return(results));
LinkManager::PendingFixedChannelConnection pending_fixed_channel_connection_3{
- .handler_ = user_handler_,
+ .handler_ = &user_handler,
.on_fail_callback_ = common::BindOnce([](FixedChannelManager::ConnectionResult result) { FAIL(); })};
std::unique_ptr<FixedChannel> channel_3;
std::promise<void> promise_3;
@@ -192,10 +177,9 @@ TEST_F(L2capLeLinkManagerTest, connect_fixed_channel_service_without_acl) {
EXPECT_EQ(future_3_status, std::future_status::ready);
EXPECT_NE(channel_3, nullptr);
- connection_management_handler->Post(common::BindOnce(
- &hci::acl_manager::LeConnectionManagementCallbacks::OnDisconnection,
- common::Unretained(connection_management_callbacks), hci::ErrorCode::REMOTE_USER_TERMINATED_CONNECTION));
- SyncHandler(connection_management_handler);
+ user_handler.Clear();
+
+ le_link_manager.OnDisconnect(address_with_type, hci::ErrorCode::SUCCESS);
}
TEST_F(L2capLeLinkManagerTest, connect_fixed_channel_service_without_acl_with_no_service) {
@@ -203,18 +187,15 @@ TEST_F(L2capLeLinkManagerTest, connect_fixed_channel_service_without_acl_with_no
MockAclManager mock_acl_manager;
hci::AddressWithType address_with_type({{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::PUBLIC_DEVICE_ADDRESS);
+ auto user_handler = std::make_unique<os::Handler>(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
+ hci::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterLeCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_le_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
- LinkManager le_link_manager(
- l2cap_handler_,
- &mock_acl_manager,
- &mock_le_fixed_channel_service_manager,
- nullptr,
- mock_parameter_provider_);
+ LinkManager le_link_manager(l2cap_handler_, &mock_acl_manager, &mock_le_fixed_channel_service_manager,
+ mock_parameter_provider_);
EXPECT_EQ(hci_le_connection_callbacks, &le_link_manager);
EXPECT_EQ(hci_callback_handler, l2cap_handler_);
@@ -223,16 +204,17 @@ TEST_F(L2capLeLinkManagerTest, connect_fixed_channel_service_without_acl_with_no
EXPECT_CALL(mock_le_fixed_channel_service_manager, GetRegisteredServices()).WillRepeatedly(Return(results));
// Step 2: Connect to fixed channel without any service registered will result in failure
- EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type, true)).Times(0);
+ EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type)).Times(0);
FixedChannelManager::ConnectionResult my_result;
LinkManager::PendingFixedChannelConnection pending_fixed_channel_connection{
- .handler_ = user_handler_,
+ .handler_ = user_handler.get(),
.on_fail_callback_ = common::testing::BindLambdaForTesting(
[&my_result](FixedChannelManager::ConnectionResult result) { my_result = result; })};
le_link_manager.ConnectFixedChannelServices(address_with_type, std::move(pending_fixed_channel_connection));
- SyncHandler(user_handler_);
+ SyncHandler(user_handler.get());
EXPECT_EQ(my_result.connection_result_code, FixedChannelManager::ConnectionResultCode::FAIL_NO_SERVICE_REGISTERED);
+ user_handler->Clear();
}
TEST_F(L2capLeLinkManagerTest, connect_fixed_channel_service_without_acl_with_hci_failure) {
@@ -240,18 +222,15 @@ TEST_F(L2capLeLinkManagerTest, connect_fixed_channel_service_without_acl_with_hc
MockAclManager mock_acl_manager;
hci::AddressWithType address_with_type({{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::RANDOM_DEVICE_ADDRESS);
+ auto user_handler = std::make_unique<os::Handler>(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
+ hci::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterLeCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_le_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
- LinkManager le_link_manager(
- l2cap_handler_,
- &mock_acl_manager,
- &mock_le_fixed_channel_service_manager,
- nullptr,
- mock_parameter_provider_);
+ LinkManager le_link_manager(l2cap_handler_, &mock_acl_manager, &mock_le_fixed_channel_service_manager,
+ mock_parameter_provider_);
EXPECT_EQ(hci_le_connection_callbacks, &le_link_manager);
EXPECT_EQ(hci_callback_handler, l2cap_handler_);
@@ -262,23 +241,25 @@ TEST_F(L2capLeLinkManagerTest, connect_fixed_channel_service_without_acl_with_hc
EXPECT_CALL(mock_le_fixed_channel_service_manager, GetRegisteredServices()).WillRepeatedly(Return(results));
// Step 2: Connect to fixed channel without ACL connection should trigger ACL connection process
- EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type, true)).Times(1);
+ EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type)).Times(1);
FixedChannelManager::ConnectionResult my_result;
LinkManager::PendingFixedChannelConnection pending_fixed_channel_connection{
- .handler_ = user_handler_,
+ .handler_ = user_handler.get(),
.on_fail_callback_ = common::testing::BindLambdaForTesting(
[&my_result](FixedChannelManager::ConnectionResult result) { my_result = result; })};
le_link_manager.ConnectFixedChannelServices(address_with_type, std::move(pending_fixed_channel_connection));
// Step 3: ACL connection failure event should trigger connection failure callback
EXPECT_CALL(mock_service_1, NotifyChannelCreation(_)).Times(0);
- hci_callback_handler->Post(common::BindOnce(&hci::acl_manager::LeConnectionCallbacks::OnLeConnectFail,
+ hci_callback_handler->Post(common::BindOnce(&hci::LeConnectionCallbacks::OnLeConnectFail,
common::Unretained(hci_le_connection_callbacks), address_with_type,
hci::ErrorCode::PAGE_TIMEOUT));
SyncHandler(hci_callback_handler);
- SyncHandler(user_handler_);
+ SyncHandler(user_handler.get());
EXPECT_EQ(my_result.connection_result_code, FixedChannelManager::ConnectionResultCode::FAIL_HCI_ERROR);
EXPECT_EQ(my_result.hci_error, hci::ErrorCode::PAGE_TIMEOUT);
+
+ user_handler->Clear();
}
TEST_F(L2capLeLinkManagerTest, not_acquiring_channels_should_disconnect_acl_after_timeout) {
@@ -288,18 +269,15 @@ TEST_F(L2capLeLinkManagerTest, not_acquiring_channels_should_disconnect_acl_afte
MockAclManager mock_acl_manager;
hci::AddressWithType address_with_type({{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::RANDOM_DEVICE_ADDRESS);
+ auto user_handler = std::make_unique<os::Handler>(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
+ hci::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterLeCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_le_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
- LinkManager le_link_manager(
- l2cap_handler_,
- &mock_acl_manager,
- &mock_le_fixed_channel_service_manager,
- nullptr,
- mock_parameter_provider_);
+ LinkManager le_link_manager(l2cap_handler_, &mock_acl_manager, &mock_le_fixed_channel_service_manager,
+ mock_parameter_provider_);
EXPECT_EQ(hci_le_connection_callbacks, &le_link_manager);
EXPECT_EQ(hci_callback_handler, l2cap_handler_);
@@ -311,20 +289,17 @@ TEST_F(L2capLeLinkManagerTest, not_acquiring_channels_should_disconnect_acl_afte
EXPECT_CALL(mock_le_fixed_channel_service_manager, GetRegisteredServices()).WillRepeatedly(Return(results));
// Step 2: Connect to fixed channel without ACL connection should trigger ACL connection process
- EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type, true)).Times(1);
+ EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type)).Times(1);
LinkManager::PendingFixedChannelConnection pending_fixed_channel_connection{
- .handler_ = user_handler_,
+ .handler_ = user_handler.get(),
.on_fail_callback_ = common::BindOnce([](FixedChannelManager::ConnectionResult result) { FAIL(); })};
le_link_manager.ConnectFixedChannelServices(address_with_type, std::move(pending_fixed_channel_connection));
// Step 3: ACL connection success event should trigger channel creation for all registered services
- auto* raw_acl_connection = new MockLeAclConnection();
- std::unique_ptr<MockLeAclConnection> acl_connection(raw_acl_connection);
- EXPECT_CALL(*acl_connection, GetRemoteAddress()).WillRepeatedly(Return(address_with_type));
- hci::acl_manager::LeConnectionManagementCallbacks* connection_management_callbacks = nullptr;
- os::Handler* connection_management_handler = nullptr;
- EXPECT_CALL(*acl_connection, RegisterCallbacks(_, _))
- .WillOnce(DoAll(SaveArg<0>(&connection_management_callbacks), SaveArg<1>(&connection_management_handler)));
+ auto* raw_acl_connection = new MockAclConnection();
+ std::unique_ptr<MockAclConnection> acl_connection(raw_acl_connection);
+ EXPECT_CALL(*acl_connection, GetAddress()).WillRepeatedly(Return(address_with_type.GetAddress()));
+ EXPECT_CALL(*acl_connection, GetAddressType()).WillRepeatedly(Return(address_with_type.GetAddressType()));
std::unique_ptr<FixedChannel> channel_1, channel_2;
std::promise<void> promise_1, promise_2;
auto future_1 = promise_1.get_future();
@@ -339,17 +314,10 @@ TEST_F(L2capLeLinkManagerTest, not_acquiring_channels_should_disconnect_acl_afte
channel_2 = std::move(channel);
promise_2.set_value();
});
- hci_callback_handler->Post(common::BindOnce(&hci::acl_manager::LeConnectionCallbacks::OnLeConnectSuccess,
+ hci_callback_handler->Post(common::BindOnce(&hci::LeConnectionCallbacks::OnLeConnectSuccess,
common::Unretained(hci_le_connection_callbacks), address_with_type,
std::move(acl_connection)));
SyncHandler(hci_callback_handler);
- connection_management_handler->Post(common::BindOnce(
- &hci::acl_manager::LeConnectionManagementCallbacks::OnReadRemoteVersionInformationComplete,
- common::Unretained(connection_management_callbacks),
- hci::ErrorCode::SUCCESS,
- 0,
- 0,
- 0));
auto future_1_status = future_1.wait_for(kTestIdleDisconnectTimeoutShort);
EXPECT_EQ(future_1_status, std::future_status::ready);
EXPECT_NE(channel_1, nullptr);
@@ -358,23 +326,22 @@ TEST_F(L2capLeLinkManagerTest, not_acquiring_channels_should_disconnect_acl_afte
EXPECT_NE(channel_2, nullptr);
hci::ErrorCode status_1 = hci::ErrorCode::SUCCESS;
channel_1->RegisterOnCloseCallback(
- user_handler_, common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_1 = status; }));
+ user_handler.get(), common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_1 = status; }));
hci::ErrorCode status_2 = hci::ErrorCode::SUCCESS;
channel_2->RegisterOnCloseCallback(
- user_handler_, common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_2 = status; }));
+ user_handler.get(), common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_2 = status; }));
- // Step 4: Leave channel IDLE long enough, they will disconnect
+ // Step 4: ave channel IDLE long enough, they will disconnect
EXPECT_CALL(*raw_acl_connection, Disconnect(hci::DisconnectReason::REMOTE_USER_TERMINATED_CONNECTION)).Times(1);
std::this_thread::sleep_for(kTestIdleDisconnectTimeoutShort * 1.2);
- connection_management_handler->Post(common::BindOnce(
- &hci::acl_manager::LeConnectionManagementCallbacks::OnDisconnection,
- common::Unretained(connection_management_callbacks), hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST));
- SyncHandler(connection_management_handler);
// Step 5: Link disconnect will trigger all callbacks
- SyncHandler(user_handler_);
+ le_link_manager.OnDisconnect(address_with_type, hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST);
+ SyncHandler(user_handler.get());
EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_1);
EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_2);
+
+ user_handler->Clear();
}
TEST_F(L2capLeLinkManagerTest, acquiring_channels_should_not_disconnect_acl_after_timeout) {
@@ -384,18 +351,15 @@ TEST_F(L2capLeLinkManagerTest, acquiring_channels_should_not_disconnect_acl_afte
MockAclManager mock_acl_manager;
hci::AddressWithType address_with_type({{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::RANDOM_DEVICE_ADDRESS);
+ auto user_handler = std::make_unique<os::Handler>(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
+ hci::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterLeCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_le_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
- LinkManager le_link_manager(
- l2cap_handler_,
- &mock_acl_manager,
- &mock_le_fixed_channel_service_manager,
- nullptr,
- mock_parameter_provider_);
+ LinkManager le_link_manager(l2cap_handler_, &mock_acl_manager, &mock_le_fixed_channel_service_manager,
+ mock_parameter_provider_);
EXPECT_EQ(hci_le_connection_callbacks, &le_link_manager);
EXPECT_EQ(hci_callback_handler, l2cap_handler_);
@@ -407,20 +371,17 @@ TEST_F(L2capLeLinkManagerTest, acquiring_channels_should_not_disconnect_acl_afte
EXPECT_CALL(mock_le_fixed_channel_service_manager, GetRegisteredServices()).WillRepeatedly(Return(results));
// Step 2: Connect to fixed channel without ACL connection should trigger ACL connection process
- EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type, true)).Times(1);
+ EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type)).Times(1);
LinkManager::PendingFixedChannelConnection pending_fixed_channel_connection{
- .handler_ = user_handler_,
+ .handler_ = user_handler.get(),
.on_fail_callback_ = common::BindOnce([](FixedChannelManager::ConnectionResult result) { FAIL(); })};
le_link_manager.ConnectFixedChannelServices(address_with_type, std::move(pending_fixed_channel_connection));
// Step 3: ACL connection success event should trigger channel creation for all registered services
- auto* raw_acl_connection = new MockLeAclConnection();
- std::unique_ptr<MockLeAclConnection> acl_connection(raw_acl_connection);
- EXPECT_CALL(*acl_connection, GetRemoteAddress()).WillRepeatedly(Return(address_with_type));
- hci::acl_manager::LeConnectionManagementCallbacks* connection_management_callbacks = nullptr;
- os::Handler* connection_management_handler = nullptr;
- EXPECT_CALL(*acl_connection, RegisterCallbacks(_, _))
- .WillOnce(DoAll(SaveArg<0>(&connection_management_callbacks), SaveArg<1>(&connection_management_handler)));
+ auto* raw_acl_connection = new MockAclConnection();
+ std::unique_ptr<MockAclConnection> acl_connection(raw_acl_connection);
+ EXPECT_CALL(*acl_connection, GetAddress()).WillRepeatedly(Return(address_with_type.GetAddress()));
+ EXPECT_CALL(*acl_connection, GetAddressType()).WillRepeatedly(Return(address_with_type.GetAddressType()));
std::unique_ptr<FixedChannel> channel_1, channel_2;
std::promise<void> promise_1, promise_2;
auto future_1 = promise_1.get_future();
@@ -435,17 +396,10 @@ TEST_F(L2capLeLinkManagerTest, acquiring_channels_should_not_disconnect_acl_afte
channel_2 = std::move(channel);
promise_2.set_value();
});
- hci_callback_handler->Post(common::BindOnce(&hci::acl_manager::LeConnectionCallbacks::OnLeConnectSuccess,
+ hci_callback_handler->Post(common::BindOnce(&hci::LeConnectionCallbacks::OnLeConnectSuccess,
common::Unretained(hci_le_connection_callbacks), address_with_type,
std::move(acl_connection)));
SyncHandler(hci_callback_handler);
- connection_management_handler->Post(common::BindOnce(
- &hci::acl_manager::LeConnectionManagementCallbacks::OnReadRemoteVersionInformationComplete,
- common::Unretained(connection_management_callbacks),
- hci::ErrorCode::SUCCESS,
- 0,
- 0,
- 0));
auto future_1_status = future_1.wait_for(kTestIdleDisconnectTimeoutShort);
EXPECT_EQ(future_1_status, std::future_status::ready);
EXPECT_NE(channel_1, nullptr);
@@ -454,10 +408,10 @@ TEST_F(L2capLeLinkManagerTest, acquiring_channels_should_not_disconnect_acl_afte
EXPECT_NE(channel_2, nullptr);
hci::ErrorCode status_1 = hci::ErrorCode::SUCCESS;
channel_1->RegisterOnCloseCallback(
- user_handler_, common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_1 = status; }));
+ user_handler.get(), common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_1 = status; }));
hci::ErrorCode status_2 = hci::ErrorCode::SUCCESS;
channel_2->RegisterOnCloseCallback(
- user_handler_, common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_2 = status; }));
+ user_handler.get(), common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_2 = status; }));
channel_1->Acquire();
@@ -466,13 +420,12 @@ TEST_F(L2capLeLinkManagerTest, acquiring_channels_should_not_disconnect_acl_afte
std::this_thread::sleep_for(kTestIdleDisconnectTimeoutShort * 2);
// Step 5: Link disconnect will trigger all callbacks
- connection_management_handler->Post(common::BindOnce(
- &hci::acl_manager::LeConnectionManagementCallbacks::OnDisconnection,
- common::Unretained(connection_management_callbacks), hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST));
- SyncHandler(connection_management_handler);
- SyncHandler(user_handler_);
+ le_link_manager.OnDisconnect(address_with_type, hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST);
+ SyncHandler(user_handler.get());
EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_1);
EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_2);
+
+ user_handler->Clear();
}
TEST_F(L2capLeLinkManagerTest, acquiring_and_releasing_channels_should_eventually_disconnect_acl) {
@@ -482,18 +435,15 @@ TEST_F(L2capLeLinkManagerTest, acquiring_and_releasing_channels_should_eventuall
MockAclManager mock_acl_manager;
hci::AddressWithType address_with_type({{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}},
hci::AddressType::PUBLIC_IDENTITY_ADDRESS);
+ auto user_handler = std::make_unique<os::Handler>(thread_);
// Step 1: Verify callback registration with HCI
- hci::acl_manager::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
+ hci::LeConnectionCallbacks* hci_le_connection_callbacks = nullptr;
os::Handler* hci_callback_handler = nullptr;
EXPECT_CALL(mock_acl_manager, RegisterLeCallbacks(_, _))
.WillOnce(DoAll(SaveArg<0>(&hci_le_connection_callbacks), SaveArg<1>(&hci_callback_handler)));
- LinkManager le_link_manager(
- l2cap_handler_,
- &mock_acl_manager,
- &mock_le_fixed_channel_service_manager,
- nullptr,
- mock_parameter_provider_);
+ LinkManager le_link_manager(l2cap_handler_, &mock_acl_manager, &mock_le_fixed_channel_service_manager,
+ mock_parameter_provider_);
EXPECT_EQ(hci_le_connection_callbacks, &le_link_manager);
EXPECT_EQ(hci_callback_handler, l2cap_handler_);
@@ -505,20 +455,17 @@ TEST_F(L2capLeLinkManagerTest, acquiring_and_releasing_channels_should_eventuall
EXPECT_CALL(mock_le_fixed_channel_service_manager, GetRegisteredServices()).WillRepeatedly(Return(results));
// Step 2: Connect to fixed channel without ACL connection should trigger ACL connection process
- EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type, true)).Times(1);
+ EXPECT_CALL(mock_acl_manager, CreateLeConnection(address_with_type)).Times(1);
LinkManager::PendingFixedChannelConnection pending_fixed_channel_connection{
- .handler_ = user_handler_,
+ .handler_ = user_handler.get(),
.on_fail_callback_ = common::BindOnce([](FixedChannelManager::ConnectionResult result) { FAIL(); })};
le_link_manager.ConnectFixedChannelServices(address_with_type, std::move(pending_fixed_channel_connection));
// Step 3: ACL connection success event should trigger channel creation for all registered services
- auto* raw_acl_connection = new MockLeAclConnection();
- std::unique_ptr<MockLeAclConnection> acl_connection(raw_acl_connection);
- EXPECT_CALL(*acl_connection, GetRemoteAddress()).WillRepeatedly(Return(address_with_type));
- hci::acl_manager::LeConnectionManagementCallbacks* connection_management_callbacks = nullptr;
- os::Handler* connection_management_handler = nullptr;
- EXPECT_CALL(*acl_connection, RegisterCallbacks(_, _))
- .WillOnce(DoAll(SaveArg<0>(&connection_management_callbacks), SaveArg<1>(&connection_management_handler)));
+ auto* raw_acl_connection = new MockAclConnection();
+ std::unique_ptr<MockAclConnection> acl_connection(raw_acl_connection);
+ EXPECT_CALL(*acl_connection, GetAddress()).WillRepeatedly(Return(address_with_type.GetAddress()));
+ EXPECT_CALL(*acl_connection, GetAddressType()).WillRepeatedly(Return(address_with_type.GetAddressType()));
std::unique_ptr<FixedChannel> channel_1, channel_2;
std::promise<void> promise_1, promise_2;
auto future_1 = promise_1.get_future();
@@ -533,17 +480,10 @@ TEST_F(L2capLeLinkManagerTest, acquiring_and_releasing_channels_should_eventuall
channel_2 = std::move(channel);
promise_2.set_value();
});
- hci_callback_handler->Post(common::BindOnce(&hci::acl_manager::LeConnectionCallbacks::OnLeConnectSuccess,
+ hci_callback_handler->Post(common::BindOnce(&hci::LeConnectionCallbacks::OnLeConnectSuccess,
common::Unretained(hci_le_connection_callbacks), address_with_type,
std::move(acl_connection)));
SyncHandler(hci_callback_handler);
- connection_management_handler->Post(common::BindOnce(
- &hci::acl_manager::LeConnectionManagementCallbacks::OnReadRemoteVersionInformationComplete,
- common::Unretained(connection_management_callbacks),
- hci::ErrorCode::SUCCESS,
- 0,
- 0,
- 0));
auto future_1_status = future_1.wait_for(kTestIdleDisconnectTimeoutShort);
EXPECT_EQ(future_1_status, std::future_status::ready);
EXPECT_NE(channel_1, nullptr);
@@ -552,10 +492,10 @@ TEST_F(L2capLeLinkManagerTest, acquiring_and_releasing_channels_should_eventuall
EXPECT_NE(channel_2, nullptr);
hci::ErrorCode status_1 = hci::ErrorCode::SUCCESS;
channel_1->RegisterOnCloseCallback(
- user_handler_, common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_1 = status; }));
+ user_handler.get(), common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_1 = status; }));
hci::ErrorCode status_2 = hci::ErrorCode::SUCCESS;
channel_2->RegisterOnCloseCallback(
- user_handler_, common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_2 = status; }));
+ user_handler.get(), common::testing::BindLambdaForTesting([&](hci::ErrorCode status) { status_2 = status; }));
channel_1->Acquire();
@@ -569,13 +509,12 @@ TEST_F(L2capLeLinkManagerTest, acquiring_and_releasing_channels_should_eventuall
std::this_thread::sleep_for(kTestIdleDisconnectTimeoutShort * 1.2);
// Step 6: Link disconnect will trigger all callbacks
- connection_management_handler->Post(common::BindOnce(
- &hci::acl_manager::LeConnectionManagementCallbacks::OnDisconnection,
- common::Unretained(connection_management_callbacks), hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST));
- SyncHandler(connection_management_handler);
- SyncHandler(user_handler_);
+ le_link_manager.OnDisconnect(address_with_type, hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST);
+ SyncHandler(user_handler.get());
EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_1);
EXPECT_EQ(hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST, status_2);
+
+ user_handler->Clear();
}
} // namespace
diff --git a/gd/l2cap/le/internal/link_mock.h b/gd/l2cap/le/internal/link_mock.h
index 98f74ddec..63bb88481 100644
--- a/gd/l2cap/le/internal/link_mock.h
+++ b/gd/l2cap/le/internal/link_mock.h
@@ -29,15 +29,15 @@ namespace le {
namespace internal {
namespace testing {
-using hci::testing::MockLeAclConnection;
+using hci::testing::MockAclConnection;
class MockLink : public Link {
public:
explicit MockLink(os::Handler* handler, l2cap::internal::ParameterProvider* parameter_provider,
- std::unique_ptr<MockLeAclConnection> mock_acl_connection, LinkManager* link_manager)
- : Link(handler, std::move(mock_acl_connection), parameter_provider, nullptr, nullptr, link_manager) {}
+ std::unique_ptr<MockAclConnection> mock_acl_connection)
+ : Link(handler, std::move(mock_acl_connection), parameter_provider, nullptr, nullptr){};
- MOCK_METHOD(hci::AddressWithType, GetDevice, (), (const, override));
+ MOCK_METHOD(hci::AddressWithType, GetDevice, (), (override));
MOCK_METHOD(hci::Role, GetRole, (), (override));
MOCK_METHOD(void, OnAclDisconnected, (hci::ErrorCode status), (override));
MOCK_METHOD(void, Disconnect, (), (override));
diff --git a/gd/l2cap/le/internal/signalling_manager.cc b/gd/l2cap/le/internal/signalling_manager.cc
index 084f900c6..c9d978c51 100644
--- a/gd/l2cap/le/internal/signalling_manager.cc
+++ b/gd/l2cap/le/internal/signalling_manager.cc
@@ -42,8 +42,7 @@ LeSignallingManager::LeSignallingManager(os::Handler* handler, Link* link,
dynamic_service_manager_(dynamic_service_manager), channel_allocator_(channel_allocator), alarm_(handler) {
ASSERT(handler_ != nullptr);
ASSERT(link_ != nullptr);
- signalling_channel_ =
- link_->AllocateFixedChannel(kLeSignallingCid, SecurityPolicy::NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK);
+ signalling_channel_ = link_->AllocateFixedChannel(kLeSignallingCid, {});
signalling_channel_->GetQueueUpEnd()->RegisterDequeue(
handler_, common::Bind(&LeSignallingManager::on_incoming_packet, common::Unretained(this)));
enqueue_buffer_ =
@@ -57,20 +56,9 @@ LeSignallingManager::~LeSignallingManager() {
}
void LeSignallingManager::SendConnectionRequest(Psm psm, Cid local_cid, Mtu mtu) {
- dynamic_service_manager_->GetSecurityEnforcementInterface()->Enforce(
- link_->GetDevice(),
- dynamic_service_manager_->GetService(psm)->GetSecurityPolicy(),
- handler_->BindOnceOn(this, &LeSignallingManager::on_security_result_for_outgoing, psm, local_cid, mtu));
-}
-
-void LeSignallingManager::on_security_result_for_outgoing(Psm psm, Cid local_cid, Mtu mtu, bool result) {
- if (!result) {
- LOG_WARN("Security requirement can't be satisfied. Dropping connection request");
- return;
- }
-
- PendingCommand pending_command = PendingCommand::CreditBasedConnectionRequest(
- next_signal_id_, psm, local_cid, mtu, link_->GetMps(), link_->GetInitialCredit());
+ PendingCommand pending_command = {
+ next_signal_id_, LeCommandCode::LE_CREDIT_BASED_CONNECTION_REQUEST, psm, local_cid, {}, mtu, link_->GetMps(),
+ link_->GetInitialCredit()};
next_signal_id_++;
pending_commands_.push(pending_command);
if (pending_commands_.size() == 1) {
@@ -78,8 +66,9 @@ void LeSignallingManager::on_security_result_for_outgoing(Psm psm, Cid local_cid
}
}
-void LeSignallingManager::SendDisconnectRequest(Cid scid, Cid dcid) {
- PendingCommand pending_command = PendingCommand::DisconnectionRequest(next_signal_id_, scid, dcid);
+void LeSignallingManager::SendDisconnectRequest(Cid local_cid, Cid remote_cid) {
+ PendingCommand pending_command = {
+ next_signal_id_, LeCommandCode::DISCONNECTION_REQUEST, {}, local_cid, remote_cid, {}, {}, {}};
next_signal_id_++;
pending_commands_.push(pending_command);
if (pending_commands_.size() == 1) {
@@ -87,15 +76,9 @@ void LeSignallingManager::SendDisconnectRequest(Cid scid, Cid dcid) {
}
}
-void LeSignallingManager::SendConnectionParameterUpdateRequest(
- uint16_t interval_min, uint16_t interval_max, uint16_t peripheral_latency, uint16_t timeout_multiplier) {
- PendingCommand pending_command = PendingCommand::ConnectionParameterUpdate(
- next_signal_id_, interval_min, interval_max, peripheral_latency, timeout_multiplier);
- next_signal_id_++;
- pending_commands_.push(pending_command);
- if (pending_commands_.size() == 1) {
- handle_send_next_command();
- }
+void LeSignallingManager::SendConnectionParameterUpdateRequest(uint16_t interval_min, uint16_t interval_max,
+ uint16_t slave_latency, uint16_t timeout_multiplier) {
+ LOG_ERROR("Not implemented");
}
void LeSignallingManager::SendConnectionParameterUpdateResponse(SignalId signal_id,
@@ -110,73 +93,40 @@ void LeSignallingManager::SendCredit(Cid local_cid, uint16_t credits) {
enqueue_buffer_->Enqueue(std::move(builder), handler_);
}
-void LeSignallingManager::SendEnhancedConnectionRequest(Psm psm, std::vector<Cid> local_cid, Mtu mtu) {}
-
-void LeSignallingManager::SendEnhancedReconfigureRequest(std::vector<Cid> local_cid, Mtu mtu) {}
-
void LeSignallingManager::CancelAlarm() {
alarm_.Cancel();
}
void LeSignallingManager::OnCommandReject(LeCommandRejectView command_reject_view) {
auto signal_id = command_reject_view.GetIdentifier();
- if (signal_id != command_just_sent_.signal_id_) {
+ if (signal_id != command_just_sent_.signal_id_ || command_just_sent_.command_code_ != command_reject_view.GetCode()) {
LOG_WARN("Unexpected response: no pending request");
return;
}
alarm_.Cancel();
- if (command_just_sent_.command_code_ == LeCommandCode::LE_CREDIT_BASED_CONNECTION_REQUEST) {
- link_->OnOutgoingConnectionRequestFail(command_just_sent_.source_cid_,
- LeCreditBasedConnectionResponseResult::NO_RESOURCES_AVAILABLE);
- }
handle_send_next_command();
LOG_WARN("Command rejected");
}
-void LeSignallingManager::OnConnectionParameterUpdateRequest(
- SignalId signal_id,
- uint16_t interval_min,
- uint16_t interval_max,
- uint16_t peripheral_latency,
- uint16_t timeout_multiplier) {
- if (link_->GetRole() == hci::Role::PERIPHERAL) {
- LOG_WARN("Received request from LL central");
- auto builder = LeCommandRejectNotUnderstoodBuilder::Create(signal_id.Value());
- enqueue_buffer_->Enqueue(std::move(builder), handler_);
- return;
- }
-
- if (!link_->CheckConnectionParameters(interval_min, interval_max, peripheral_latency, timeout_multiplier)) {
- LOG_WARN("Received invalid connection parameter update request from LL central");
- auto builder = ConnectionParameterUpdateResponseBuilder::Create(signal_id.Value(),
- ConnectionParameterUpdateResponseResult::REJECTED);
- enqueue_buffer_->Enqueue(std::move(builder), handler_);
- return;
- }
- link_->UpdateConnectionParameterFromRemote(
- signal_id, interval_min, interval_max, peripheral_latency, timeout_multiplier);
+void LeSignallingManager::OnConnectionParameterUpdateRequest(uint16_t interval_min, uint16_t interval_max,
+ uint16_t slave_latency, uint16_t timeout_multiplier) {
+ LOG_ERROR("Not implemented");
}
-void LeSignallingManager::OnConnectionParameterUpdateResponse(SignalId signal_id,
- ConnectionParameterUpdateResponseResult result) {
- if (signal_id != command_just_sent_.signal_id_) {
- LOG_WARN("Unexpected response: no pending request");
- return;
- }
- if (command_just_sent_.command_code_ != LeCommandCode::CONNECTION_PARAMETER_UPDATE_REQUEST) {
- LOG_WARN("Unexpected response: no pending request");
- return;
- }
- alarm_.Cancel();
- command_just_sent_.signal_id_ = kInitialSignalId;
- if (result != ConnectionParameterUpdateResponseResult::ACCEPTED) {
- LOG_ERROR("Connection parameter update is not accepted");
- }
+void LeSignallingManager::OnConnectionParameterUpdateResponse(ConnectionParameterUpdateResponseResult result) {
+ LOG_ERROR("Not implemented");
}
void LeSignallingManager::OnConnectionRequest(SignalId signal_id, Psm psm, Cid remote_cid, Mtu mtu, uint16_t mps,
uint16_t initial_credits) {
+ if (!IsPsmValid(psm)) {
+ LOG_WARN("Invalid psm received from remote psm:%d remote_cid:%d", psm, remote_cid);
+ send_connection_response(signal_id, kInvalidCid, 0, 0, 0,
+ LeCreditBasedConnectionResponseResult::LE_PSM_NOT_SUPPORTED);
+ return;
+ }
+
if (remote_cid == kInvalidCid) {
LOG_WARN("Invalid remote cid received from remote psm:%d remote_cid:%d", psm, remote_cid);
send_connection_response(signal_id, kInvalidCid, 0, 0, 0,
@@ -198,69 +148,27 @@ void LeSignallingManager::OnConnectionRequest(SignalId signal_id, Psm psm, Cid r
return;
}
- PendingConnection pending{
- .remote_cid = remote_cid,
- .incoming_signal_id = signal_id,
- .initial_credits = initial_credits,
- .max_pdu_size = mps,
- .mtu = mtu,
- };
- dynamic_service_manager_->GetSecurityEnforcementInterface()->Enforce(
- link_->GetDevice(),
- dynamic_service_manager_->GetService(psm)->GetSecurityPolicy(),
- handler_->BindOnceOn(this, &LeSignallingManager::on_security_result_for_incoming, psm, pending));
-}
-
-void LeSignallingManager::on_security_result_for_incoming(Psm psm, PendingConnection request, bool result) {
- auto signal_id = request.incoming_signal_id;
auto* service = dynamic_service_manager_->GetService(psm);
- if (!result) {
- auto security_policy = service->GetSecurityPolicy();
- switch (security_policy) {
- case SecurityPolicy::NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK:
- LOG_ERROR("If no security requirement, we should never fail");
- break;
- case SecurityPolicy::ENCRYPTED_TRANSPORT:
- send_connection_response(signal_id, kInvalidCid, 0, 0, 0,
- LeCreditBasedConnectionResponseResult::INSUFFICIENT_AUTHENTICATION);
- return;
- case SecurityPolicy::AUTHENTICATED_ENCRYPTED_TRANSPORT:
- case SecurityPolicy::BEST:
- send_connection_response(signal_id, kInvalidCid, 0, 0, 0,
- LeCreditBasedConnectionResponseResult::INSUFFICIENT_AUTHENTICATION);
- return;
- case SecurityPolicy::_NOT_FOR_YOU__AUTHENTICATED_PAIRING_WITH_128_BIT_KEY:
- send_connection_response(signal_id, kInvalidCid, 0, 0, 0,
- LeCreditBasedConnectionResponseResult::INSUFFICIENT_ENCRYPTION_KEY_SIZE);
- return;
- case SecurityPolicy::_NOT_FOR_YOU__AUTHORIZATION:
- send_connection_response(signal_id, kInvalidCid, 0, 0, 0,
- LeCreditBasedConnectionResponseResult::INSUFFICIENT_AUTHORIZATION);
- return;
- }
- }
auto config = service->GetConfigOption();
auto local_mtu = config.mtu;
auto local_mps = link_->GetMps();
- auto new_channel = link_->AllocateDynamicChannel(psm, request.remote_cid);
+ auto new_channel = link_->AllocateDynamicChannel(psm, remote_cid, {});
if (new_channel == nullptr) {
LOG_WARN("Can't allocate dynamic channel");
- // TODO: We need to respond with the correct reason
send_connection_response(signal_id, kInvalidCid, 0, 0, 0,
- LeCreditBasedConnectionResponseResult::SOURCE_CID_ALREADY_ALLOCATED);
+ LeCreditBasedConnectionResponseResult::NO_RESOURCES_AVAILABLE);
+
return;
}
-
- send_connection_response(signal_id, new_channel->GetCid(), local_mtu, local_mps, link_->GetInitialCredit(),
+ send_connection_response(signal_id, remote_cid, local_mtu, local_mps, link_->GetInitialCredit(),
LeCreditBasedConnectionResponseResult::SUCCESS);
auto* data_controller = reinterpret_cast<l2cap::internal::LeCreditBasedDataController*>(
data_pipeline_manager_->GetDataController(new_channel->GetCid()));
- auto actual_mtu = std::min(request.mtu, local_mtu);
- data_controller->SetMtu(actual_mtu);
- data_controller->SetMps(std::min(request.max_pdu_size, local_mps));
- data_controller->OnCredit(request.initial_credits);
- auto user_channel = std::make_unique<DynamicChannel>(new_channel, handler_, link_, actual_mtu);
+ data_controller->SetMtu(std::min(mtu, local_mtu));
+ data_controller->SetMps(std::min(mps, local_mps));
+ data_controller->OnCredit(initial_credits);
+ auto user_channel = std::make_unique<DynamicChannel>(new_channel, handler_);
dynamic_service_manager_->GetService(psm)->NotifyChannelCreation(std::move(user_channel));
}
@@ -278,28 +186,25 @@ void LeSignallingManager::OnConnectionResponse(SignalId signal_id, Cid remote_ci
command_just_sent_.signal_id_ = kInitialSignalId;
if (result != LeCreditBasedConnectionResponseResult::SUCCESS) {
LOG_WARN("Connection failed: %s", LeCreditBasedConnectionResponseResultText(result).data());
- link_->OnOutgoingConnectionRequestFail(command_just_sent_.source_cid_, result);
+ link_->OnOutgoingConnectionRequestFail(command_just_sent_.source_cid_);
handle_send_next_command();
return;
}
auto new_channel =
- link_->AllocateReservedDynamicChannel(command_just_sent_.source_cid_, command_just_sent_.psm_, remote_cid);
+ link_->AllocateReservedDynamicChannel(command_just_sent_.source_cid_, command_just_sent_.psm_, remote_cid, {});
if (new_channel == nullptr) {
LOG_WARN("Can't allocate dynamic channel");
- link_->OnOutgoingConnectionRequestFail(command_just_sent_.source_cid_,
- LeCreditBasedConnectionResponseResult::NO_RESOURCES_AVAILABLE);
+ link_->OnOutgoingConnectionRequestFail(command_just_sent_.source_cid_);
handle_send_next_command();
return;
}
auto* data_controller = reinterpret_cast<l2cap::internal::LeCreditBasedDataController*>(
data_pipeline_manager_->GetDataController(new_channel->GetCid()));
- auto actual_mtu = std::min(mtu, command_just_sent_.mtu_);
- data_controller->SetMtu(actual_mtu);
+ data_controller->SetMtu(std::min(mtu, command_just_sent_.mtu_));
data_controller->SetMps(std::min(mps, command_just_sent_.mps_));
data_controller->OnCredit(initial_credits);
- std::unique_ptr<DynamicChannel> user_channel =
- std::make_unique<DynamicChannel>(new_channel, handler_, link_, actual_mtu);
- link_->NotifyChannelCreation(new_channel->GetCid(), std::move(user_channel));
+ std::unique_ptr<DynamicChannel> user_channel = std::make_unique<DynamicChannel>(new_channel, handler_);
+ dynamic_service_manager_->GetService(command_just_sent_.psm_)->NotifyChannelCreation(std::move(user_channel));
}
void LeSignallingManager::OnDisconnectionRequest(SignalId signal_id, Cid cid, Cid remote_cid) {
@@ -318,7 +223,7 @@ void LeSignallingManager::OnDisconnectionRequest(SignalId signal_id, Cid cid, Ci
link_->FreeDynamicChannel(cid);
}
-void LeSignallingManager::OnDisconnectionResponse(SignalId signal_id, Cid remote_cid, Cid cid) {
+void LeSignallingManager::OnDisconnectionResponse(SignalId signal_id, Cid cid, Cid remote_cid) {
if (signal_id != command_just_sent_.signal_id_ ||
command_just_sent_.command_code_ != LeCommandCode::DISCONNECTION_REQUEST) {
LOG_WARN("Unexpected response: no pending request");
@@ -380,11 +285,8 @@ void LeSignallingManager::on_incoming_packet() {
return;
}
OnConnectionParameterUpdateRequest(
- parameter_update_req_view.GetIdentifier(),
- parameter_update_req_view.GetIntervalMin(),
- parameter_update_req_view.GetIntervalMax(),
- parameter_update_req_view.GetPeripheralLatency(),
- parameter_update_req_view.GetTimeoutMultiplier());
+ parameter_update_req_view.GetIntervalMin(), parameter_update_req_view.GetIntervalMax(),
+ parameter_update_req_view.GetSlaveLatency(), parameter_update_req_view.GetTimeoutMultiplier());
return;
}
case LeCommandCode::CONNECTION_PARAMETER_UPDATE_RESPONSE: {
@@ -393,8 +295,7 @@ void LeSignallingManager::on_incoming_packet() {
if (!parameter_update_rsp_view.IsValid()) {
return;
}
- OnConnectionParameterUpdateResponse(parameter_update_rsp_view.GetIdentifier(),
- parameter_update_rsp_view.GetResult());
+ OnConnectionParameterUpdateResponse(parameter_update_rsp_view.GetResult());
return;
}
case LeCommandCode::LE_CREDIT_BASED_CONNECTION_REQUEST: {
@@ -447,38 +348,6 @@ void LeSignallingManager::on_incoming_packet() {
disconnection_response_view.GetSourceCid());
return;
}
- case LeCommandCode::CREDIT_BASED_CONNECTION_REQUEST: {
- LeEnhancedCreditBasedConnectionRequestView request_view =
- LeEnhancedCreditBasedConnectionRequestView::Create(control_packet_view);
- if (!request_view.IsValid()) {
- return;
- }
- return;
- }
- case LeCommandCode::CREDIT_BASED_CONNECTION_RESPONSE: {
- LeEnhancedCreditBasedConnectionResponseView response_view =
- LeEnhancedCreditBasedConnectionResponseView::Create(control_packet_view);
- if (!response_view.IsValid()) {
- return;
- }
- return;
- }
- case LeCommandCode::CREDIT_BASED_RECONFIGURE_REQUEST: {
- LeEnhancedCreditBasedReconfigureRequestView request_view =
- LeEnhancedCreditBasedReconfigureRequestView::Create(control_packet_view);
- if (!request_view.IsValid()) {
- return;
- }
- return;
- }
- case LeCommandCode::CREDIT_BASED_RECONFIGURE_RESPONSE: {
- LeEnhancedCreditBasedReconfigureResponseView response_view =
- LeEnhancedCreditBasedReconfigureResponseView::Create(control_packet_view);
- if (!response_view.IsValid()) {
- return;
- }
- return;
- }
default:
LOG_WARN("Unhandled event 0x%x", static_cast<int>(code));
auto builder = LeCommandRejectNotUnderstoodBuilder::Create(control_packet_view.GetIdentifier());
@@ -503,8 +372,7 @@ void LeSignallingManager::on_command_timeout() {
}
switch (command_just_sent_.command_code_) {
case LeCommandCode::CONNECTION_PARAMETER_UPDATE_REQUEST: {
- link_->OnOutgoingConnectionRequestFail(command_just_sent_.source_cid_,
- LeCreditBasedConnectionResponseResult::NO_RESOURCES_AVAILABLE);
+ link_->OnOutgoingConnectionRequestFail(command_just_sent_.source_cid_);
break;
}
default:
@@ -537,17 +405,6 @@ void LeSignallingManager::handle_send_next_command() {
alarm_.Schedule(common::BindOnce(&LeSignallingManager::on_command_timeout, common::Unretained(this)), kTimeout);
break;
}
- case LeCommandCode::CONNECTION_PARAMETER_UPDATE_REQUEST: {
- auto builder = ConnectionParameterUpdateRequestBuilder::Create(
- command_just_sent_.signal_id_.Value(),
- command_just_sent_.interval_min_,
- command_just_sent_.interval_max_,
- command_just_sent_.peripheral_latency_,
- command_just_sent_.timeout_multiplier_);
- enqueue_buffer_->Enqueue(std::move(builder), handler_);
- alarm_.Schedule(common::BindOnce(&LeSignallingManager::on_command_timeout, common::Unretained(this)), kTimeout);
- break;
- }
default: {
LOG_WARN("Unsupported command code 0x%x", static_cast<int>(command_just_sent_.command_code_));
}
diff --git a/gd/l2cap/le/internal/signalling_manager.h b/gd/l2cap/le/internal/signalling_manager.h
index c4a3e32e5..f2181688b 100644
--- a/gd/l2cap/le/internal/signalling_manager.h
+++ b/gd/l2cap/le/internal/signalling_manager.h
@@ -49,48 +49,6 @@ struct PendingCommand {
Mtu mtu_;
uint16_t mps_;
uint16_t credits_;
- uint16_t interval_min_;
- uint16_t interval_max_;
- uint16_t peripheral_latency_;
- uint16_t timeout_multiplier_;
-
- static PendingCommand CreditBasedConnectionRequest(SignalId signal_id, Psm psm, Cid scid, Mtu mtu, uint16_t mps,
- uint16_t initial_credits) {
- PendingCommand pending_command;
- pending_command.signal_id_ = signal_id;
- pending_command.command_code_ = LeCommandCode::LE_CREDIT_BASED_CONNECTION_REQUEST;
- pending_command.psm_ = psm;
- pending_command.source_cid_ = scid;
- pending_command.mtu_ = mtu;
- pending_command.mps_ = mps;
- pending_command.credits_ = initial_credits;
- return pending_command;
- }
-
- static PendingCommand DisconnectionRequest(SignalId signal_id, Cid scid, Cid dcid) {
- PendingCommand pending_command;
- pending_command.signal_id_ = signal_id;
- pending_command.command_code_ = LeCommandCode::DISCONNECTION_REQUEST;
- pending_command.source_cid_ = scid;
- pending_command.destination_cid_ = dcid;
- return pending_command;
- }
-
- static PendingCommand ConnectionParameterUpdate(
- SignalId signal_id,
- uint16_t interval_min,
- uint16_t interval_max,
- uint16_t peripheral_latency,
- uint16_t timeout_multiplier) {
- PendingCommand pending_command;
- pending_command.signal_id_ = signal_id;
- pending_command.command_code_ = LeCommandCode::CONNECTION_PARAMETER_UPDATE_REQUEST;
- pending_command.interval_min_ = interval_min;
- pending_command.interval_max_ = interval_max;
- pending_command.peripheral_latency_ = peripheral_latency;
- pending_command.timeout_multiplier_ = timeout_multiplier;
- return pending_command;
- }
};
class Link;
@@ -107,29 +65,20 @@ class LeSignallingManager {
void SendDisconnectRequest(Cid local_cid, Cid remote_cid);
- // Note: Since Core 4.1, LL peripheral can send this through HCI command.
- void SendConnectionParameterUpdateRequest(
- uint16_t interval_min, uint16_t interval_max, uint16_t peripheral_latency, uint16_t timeout_multiplier);
+ void SendConnectionParameterUpdateRequest(uint16_t interval_min, uint16_t interval_max, uint16_t slave_latency,
+ uint16_t timeout_multiplier);
void SendConnectionParameterUpdateResponse(SignalId signal_id, ConnectionParameterUpdateResponseResult result);
void SendCredit(Cid local_cid, uint16_t credits);
- void SendEnhancedConnectionRequest(Psm psm, std::vector<Cid> local_cid, Mtu mtu);
-
- void SendEnhancedReconfigureRequest(std::vector<Cid> local_cid, Mtu mtu);
-
void CancelAlarm();
void OnCommandReject(LeCommandRejectView command_reject_view);
- void OnConnectionParameterUpdateRequest(
- SignalId signal_id,
- uint16_t interval_min,
- uint16_t interval_max,
- uint16_t peripheral_latency,
- uint16_t timeout_multiplier);
- void OnConnectionParameterUpdateResponse(SignalId signal_id, ConnectionParameterUpdateResponseResult result);
+ void OnConnectionParameterUpdateRequest(uint16_t interval_min, uint16_t interval_max, uint16_t slave_latency,
+ uint16_t timeout_multiplier);
+ void OnConnectionParameterUpdateResponse(ConnectionParameterUpdateResponseResult result);
void OnConnectionRequest(SignalId signal_id, Psm psm, Cid remote_cid, Mtu mtu, uint16_t mps,
uint16_t initial_credits);
@@ -144,21 +93,11 @@ class LeSignallingManager {
void OnCredit(Cid remote_cid, uint16_t credits);
private:
- struct PendingConnection {
- Cid remote_cid;
- Mtu mtu;
- uint16_t max_pdu_size;
- uint16_t initial_credits;
- SignalId incoming_signal_id;
- };
-
void on_incoming_packet();
void send_connection_response(SignalId signal_id, Cid local_cid, Mtu mtu, uint16_t mps, uint16_t initial_credit,
LeCreditBasedConnectionResponseResult result);
void on_command_timeout();
void handle_send_next_command();
- void on_security_result_for_incoming(Psm psm, PendingConnection request, bool result);
- void on_security_result_for_outgoing(Psm psm, Cid local_cid, Mtu mtu, bool result);
os::Handler* handler_;
Link* link_;
diff --git a/gd/l2cap/le/l2cap_le_module.cc b/gd/l2cap/le/l2cap_le_module.cc
index 02f4408ef..49595477f 100644
--- a/gd/l2cap/le/l2cap_le_module.cc
+++ b/gd/l2cap/le/l2cap_le_module.cc
@@ -13,17 +13,21 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
+#define LOG_TAG "l2cap2"
#include <memory>
+#include "common/bidi_queue.h"
#include "hci/acl_manager.h"
+#include "hci/address.h"
+#include "hci/hci_layer.h"
+#include "hci/hci_packets.h"
#include "l2cap/internal/parameter_provider.h"
-#include "l2cap/le/internal/dynamic_channel_service_manager_impl.h"
#include "l2cap/le/internal/fixed_channel_service_manager_impl.h"
#include "l2cap/le/internal/link_manager.h"
-#include "l2cap/le/security_enforcement_interface.h"
#include "module.h"
#include "os/handler.h"
+#include "os/log.h"
#include "l2cap/le/l2cap_le_module.h"
@@ -33,36 +37,14 @@ namespace le {
const ModuleFactory L2capLeModule::Factory = ModuleFactory([]() { return new L2capLeModule(); });
-/**
- * A default implementation which cannot satisfy any security level except
- * NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK.
- */
-class SecurityEnforcementRejectAllImpl : public SecurityEnforcementInterface {
- public:
- void Enforce(hci::AddressWithType remote, SecurityPolicy policy, ResultCallback result_callback) override {
- if (policy == SecurityPolicy::NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK) {
- result_callback.InvokeIfNotEmpty(true);
- } else {
- result_callback.InvokeIfNotEmpty(false);
- }
- }
-};
-static SecurityEnforcementRejectAllImpl default_security_module_impl_;
-
struct L2capLeModule::impl {
impl(os::Handler* l2cap_handler, hci::AclManager* acl_manager)
- : l2cap_handler_(l2cap_handler), acl_manager_(acl_manager) {
- dynamic_channel_service_manager_impl_.SetSecurityEnforcementInterface(&default_security_module_impl_);
- }
+ : l2cap_handler_(l2cap_handler), acl_manager_(acl_manager) {}
os::Handler* l2cap_handler_;
hci::AclManager* acl_manager_;
l2cap::internal::ParameterProvider parameter_provider_;
internal::FixedChannelServiceManagerImpl fixed_channel_service_manager_impl_{l2cap_handler_};
- internal::DynamicChannelServiceManagerImpl dynamic_channel_service_manager_impl_{l2cap_handler_};
- internal::LinkManager link_manager_{l2cap_handler_,
- acl_manager_,
- &fixed_channel_service_manager_impl_,
- &dynamic_channel_service_manager_impl_,
+ internal::LinkManager link_manager_{l2cap_handler_, acl_manager_, &fixed_channel_service_manager_impl_,
&parameter_provider_};
};
@@ -90,23 +72,6 @@ std::unique_ptr<FixedChannelManager> L2capLeModule::GetFixedChannelManager() {
&pimpl_->link_manager_, pimpl_->l2cap_handler_));
}
-std::unique_ptr<DynamicChannelManager> L2capLeModule::GetDynamicChannelManager() {
- return std::unique_ptr<DynamicChannelManager>(new DynamicChannelManager(
- &pimpl_->dynamic_channel_service_manager_impl_, &pimpl_->link_manager_, pimpl_->l2cap_handler_));
-}
-
-void L2capLeModule::InjectSecurityEnforcementInterface(SecurityEnforcementInterface* security_enforcement_interface) {
- if (security_enforcement_interface != nullptr) {
- pimpl_->dynamic_channel_service_manager_impl_.SetSecurityEnforcementInterface(security_enforcement_interface);
- } else {
- pimpl_->dynamic_channel_service_manager_impl_.SetSecurityEnforcementInterface(&default_security_module_impl_);
- }
-}
-
-void L2capLeModule::SetLinkPropertyListener(os::Handler* handler, LinkPropertyListener* listener) {
- pimpl_->link_manager_.RegisterLinkPropertyListener(handler, listener);
-}
-
} // namespace le
} // namespace l2cap
} // namespace bluetooth
diff --git a/gd/l2cap/le/l2cap_le_module.h b/gd/l2cap/le/l2cap_le_module.h
index f81c396f7..4ed3d9fcb 100644
--- a/gd/l2cap/le/l2cap_le_module.h
+++ b/gd/l2cap/le/l2cap_le_module.h
@@ -17,22 +17,10 @@
#include <memory>
-#include "l2cap/le/dynamic_channel_manager.h"
#include "l2cap/le/fixed_channel_manager.h"
-#include "l2cap/le/link_property_listener.h"
-#include "l2cap/le/security_enforcement_interface.h"
#include "module.h"
namespace bluetooth {
-
-namespace shim {
-void L2CA_UseLegacySecurityModule();
-}
-
-namespace security {
-class SecurityModule;
-}
-
namespace l2cap {
namespace le {
@@ -46,11 +34,6 @@ class L2capLeModule : public bluetooth::Module {
*/
virtual std::unique_ptr<FixedChannelManager> GetFixedChannelManager();
- /**
- * Get the api to the LE dynamic channel l2cap module
- */
- virtual std::unique_ptr<DynamicChannelManager> GetDynamicChannelManager();
-
static const ModuleFactory Factory;
protected:
@@ -65,23 +48,6 @@ class L2capLeModule : public bluetooth::Module {
private:
struct impl;
std::unique_ptr<impl> pimpl_;
-
- friend security::SecurityModule;
- friend void bluetooth::shim::L2CA_UseLegacySecurityModule();
-
- /**
- * Only for the LE security module to inject functionality to enforce security level for a connection. When LE
- * security module is stopping, inject nullptr. Note: We expect this only to be called during stack startup. This is
- * not synchronized.
- */
- virtual void InjectSecurityEnforcementInterface(SecurityEnforcementInterface* security_enforcement_interface);
-
- /**
- * Set the link property listener.
- * This is not synchronized.
- */
- virtual void SetLinkPropertyListener(os::Handler* handler, LinkPropertyListener* listener);
-
DISALLOW_COPY_AND_ASSIGN(L2capLeModule);
};
diff --git a/gd/l2cap/le/link_options.cc b/gd/l2cap/le/link_options.cc
deleted file mode 100644
index adf74eec9..000000000
--- a/gd/l2cap/le/link_options.cc
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "l2cap/le/link_options.h"
-
-#include <cstdint>
-
-#include "hci/hci_packets.h"
-#include "l2cap/le/internal/link.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace le {
-
-LinkOptions::LinkOptions(hci::acl_manager::LeAclConnection* acl_connection, internal::Link* link,
- os::Handler* l2cap_handler)
- : acl_connection_(acl_connection), link_(link), l2cap_handler_(l2cap_handler) {}
-
-hci::Role LinkOptions::GetRole() const {
- return acl_connection_->GetRole();
-}
-
-uint16_t LinkOptions::GetHandle() const {
- return acl_connection_->GetHandle();
-}
-
-hci::AddressWithType LinkOptions::GetLocalAddress() const {
- return acl_connection_->GetLocalAddress();
-}
-
-bool LinkOptions::UpdateConnectionParameter(uint16_t conn_interval_min, uint16_t conn_interval_max,
- uint16_t conn_latency, uint16_t supervision_timeout, uint16_t min_ce_length,
- uint16_t max_ce_length) {
- if (conn_interval_min < 0x0006 || conn_interval_min > 0x0C80 || conn_interval_max < 0x0006 ||
- conn_interval_max > 0x0C80 || conn_latency > 0x01F3 || supervision_timeout < 0x000A ||
- supervision_timeout > 0x0C80) {
- LOG_ERROR("Invalid parameter");
- return false;
- }
-
- l2cap_handler_->Post(common::BindOnce(&internal::Link::SendConnectionParameterUpdate, common::Unretained(link_),
- conn_interval_min, conn_interval_max, conn_latency, supervision_timeout,
- min_ce_length, max_ce_length));
-
- return true;
-}
-
-bool LinkOptions::SetPhy(uint8_t all_phys, uint8_t tx_phys, uint8_t rx_phys, uint16_t phy_options) {
- LOG_ERROR("Not implemented");
- return false;
-}
-
-} // namespace le
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/le/link_options.h b/gd/l2cap/le/link_options.h
deleted file mode 100644
index d7326df5e..000000000
--- a/gd/l2cap/le/link_options.h
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include "hci/acl_manager/le_acl_connection.h"
-#include "hci/hci_packets.h"
-#include "os/handler.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace le {
-namespace internal {
-class Link;
-}
-
-/**
- * Proxy for L2CAP user to get some link layer properties (connection handle, role), and set link layer options
- * (connection parameter update, set PHY). Only few special L2CAP users need to use it, including Security Manager,
- * Hearing Aid Profile, HID Profile, and Java API.
- * Note: Setting link layer options applies to the LINK, not single CHANNEL.
- */
-class LinkOptions {
- public:
- /**
- * Get LL Role. Most applications should NOT know its LL role.
- */
- hci::Role GetRole() const;
-
- /**
- * Get ACL Handle. Most applications should NOT know its ACL handle.
- */
- uint16_t GetHandle() const;
-
- /**
- * Return Local address used for initiation of this connection.
- */
- hci::AddressWithType GetLocalAddress() const;
-
- /**
- * Update the LE link layer connection parameters.
- * Depending on the link role and supported features, may directly send HCI command to update link, or send L2CAP
- * request to advise the remote. The updated connection parameters are still determined by controller. It's a link
- * layer change for performance tuning, and no host layer change should be observable by user.
- * Parameters are defined in Core spec HCI 7.8.18.
- * @return true iff the request is sent to controller through HCI or remote through L2CAP
- * (Use it only if you know what you are doing!)
- */
- bool UpdateConnectionParameter(uint16_t conn_interval_min, uint16_t conn_interval_max, uint16_t conn_latency,
- uint16_t supervision_timeout, uint16_t min_ce_length, uint16_t max_ce_length);
-
- /**
- * Set PHY preference. The PHY is determined by the controller.
- * No host layer change should be observable by user.
- * Parameters are defined in Core spec HCI 7.8.49.
- * @return true iff the request is sent to controller through HCI
- * (Use it only if you know what you are doing!)
- */
- bool SetPhy(uint8_t all_phys, uint8_t tx_phys, uint8_t rx_phys, uint16_t phy_options);
-
- LinkOptions(hci::acl_manager::LeAclConnection* acl_connection, internal::Link* link, os::Handler* l2cap_handler);
-
- private:
- hci::acl_manager::LeAclConnection* acl_connection_ = nullptr;
- internal::Link* link_ = nullptr;
- os::Handler* l2cap_handler_ = nullptr;
-};
-
-} // namespace le
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/le/link_property_listener.h b/gd/l2cap/le/link_property_listener.h
deleted file mode 100644
index 9af175b23..000000000
--- a/gd/l2cap/le/link_property_listener.h
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <memory>
-
-#include "hci/address_with_type.h"
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace le {
-
-/**
- * This is the listener interface for link property callbacks.
- */
-class LinkPropertyListener {
- public:
- virtual ~LinkPropertyListener() = default;
-
- /**
- * Invoked when an ACL link is connected.
- */
- virtual void OnLinkConnected(hci::AddressWithType remote, uint16_t handle, hci::Role my_role) {}
-
- /**
- * Invoked when an ACL link is disconnected.
- */
- virtual void OnLinkDisconnected(hci::AddressWithType remote) {}
-
- /**
- * Invoked when received remote version information for a given link
- */
- virtual void OnReadRemoteVersionInformation(
- hci::ErrorCode hci_status,
- hci::AddressWithType remote,
- uint8_t lmp_version,
- uint16_t manufacturer_name,
- uint16_t sub_version) {}
-
- /**
- * Invoked when received connection update for a given link
- */
- virtual void OnConnectionUpdate(
- hci::AddressWithType remote,
- uint16_t connection_interval,
- uint16_t connection_latency,
- uint16_t supervision_timeout) {}
-
- /**
- * Invoked when received PHY update for a given link
- */
- virtual void OnPhyUpdate(hci::AddressWithType remote, uint8_t tx_phy, uint8_t rx_phy) {}
-
- /**
- * Invoked when received data length exchange for a given link
- */
- virtual void OnDataLengthChange(
- hci::AddressWithType remote, uint16_t tx_octets, uint16_t tx_time, uint16_t rx_octets, uint16_t rx_time) {}
-};
-
-} // namespace le
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/le/security_enforcement_interface.h b/gd/l2cap/le/security_enforcement_interface.h
deleted file mode 100644
index d3bc0d73d..000000000
--- a/gd/l2cap/le/security_enforcement_interface.h
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "common/contextual_callback.h"
-#include "hci/address_with_type.h"
-#include "l2cap/le/security_policy.h"
-
-namespace bluetooth {
-namespace l2cap {
-namespace le {
-
-/**
- * The interface for Security Module to implement.
- */
-class SecurityEnforcementInterface {
- public:
- virtual ~SecurityEnforcementInterface() = default;
-
- using ResultCallback = common::ContextualOnceCallback<void(bool)>;
-
- /**
- * Invoked when L2CAP needs to open a channel with given security requirement. When the Security Module satisfies the
- * required security level, or cannot satisfy at all, invoke the result_callback.
- */
- virtual void Enforce(hci::AddressWithType remote, SecurityPolicy policy, ResultCallback result_callback) = 0;
-};
-
-} // namespace le
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/le/security_policy.h b/gd/l2cap/le/security_policy.h
deleted file mode 100644
index d3f7b57f3..000000000
--- a/gd/l2cap/le/security_policy.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-
-namespace bluetooth {
-namespace l2cap {
-namespace le {
-
-enum class SecurityPolicy {
- // Predefined security policies for user to pick
-
- // No security enforced
- NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK,
-
- // Just encryption, but no MITM
- ENCRYPTED_TRANSPORT,
-
- // Implicitly MITM protected
- AUTHENTICATED_ENCRYPTED_TRANSPORT,
-
- // Same as AUTHENTICATED_ENCRYPTED_TRANSPORT
- BEST,
-
- _NOT_FOR_YOU__AUTHENTICATED_PAIRING_WITH_128_BIT_KEY,
- _NOT_FOR_YOU__AUTHORIZATION,
-};
-
-} // namespace le
-} // namespace l2cap
-} // namespace bluetooth
diff --git a/gd/l2cap/classic/security_policy.h b/gd/l2cap/security_policy.h
index dde297f40..257033abf 100644
--- a/gd/l2cap/classic/security_policy.h
+++ b/gd/l2cap/security_policy.h
@@ -13,32 +13,24 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-
#pragma once
-#include <cstdint>
-
namespace bluetooth {
namespace l2cap {
-namespace classic {
-
-enum class SecurityPolicy {
- // Predefined security policies for user to pick
-
- // Just encryption, but no MITM
- ENCRYPTED_TRANSPORT,
-
- // Implicitly MITM protected
- AUTHENTICATED_ENCRYPTED_TRANSPORT,
-
- // Same as AUTHENTICATED_ENCRYPTED_TRANSPORT
- BEST,
-
- // No security enforced. SDP only.
- _SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK,
+class SecurityPolicy {
+ public:
+ enum class Level {
+ LEVEL_0, // Encryption not needed. Only applies to SDP.
+ LEVEL_2, // Encryption desired. Only needs unauthenticated link key.
+ LEVEL_3, // Encryption required and authenticated link key required.
+ };
+ Level security_level_ = Level::LEVEL_0;
+
+ bool RequiresAuthentication() const {
+ return security_level_ != SecurityPolicy::Level::LEVEL_0;
+ }
};
-} // namespace classic
} // namespace l2cap
} // namespace bluetooth
diff --git a/gd/module.cc b/gd/module.cc
index 180582216..f12da973d 100644
--- a/gd/module.cc
+++ b/gd/module.cc
@@ -13,34 +13,28 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-#define LOG_TAG "BtGdModule"
#include "module.h"
-#include "common/init_flags.h"
-#include "dumpsys/init_flags.h"
-#include "os/wakelock_manager.h"
using ::bluetooth::os::Handler;
using ::bluetooth::os::Thread;
-using ::bluetooth::os::WakelockManager;
namespace bluetooth {
-constexpr std::chrono::milliseconds kModuleStopTimeout = std::chrono::milliseconds(2000);
+constexpr std::chrono::milliseconds kModuleStopTimeout = std::chrono::milliseconds(20);
ModuleFactory::ModuleFactory(std::function<Module*()> ctor) : ctor_(ctor) {
}
+std::string Module::ToString() const {
+ return "Module";
+}
+
Handler* Module::GetHandler() const {
ASSERT_LOG(handler_ != nullptr, "Can't get handler when it's not started");
return handler_;
}
-DumpsysDataFinisher EmptyDumpsysDataFinisher = [](DumpsysDataBuilder* dumpsys_data_builder) {};
-DumpsysDataFinisher Module::GetDumpsysData(flatbuffers::FlatBufferBuilder* builder) const {
- return EmptyDumpsysDataFinisher;
-}
-
const ModuleRegistry* Module::GetModuleRegistry() const {
return registry_;
}
@@ -82,21 +76,15 @@ Module* ModuleRegistry::Start(const ModuleFactory* module, Thread* thread) {
return started_instance->second;
}
- LOG_DEBUG("Constructing next module");
Module* instance = module->ctor_();
- last_instance_ = "starting " + instance->ToString();
set_registry_and_handler(instance, thread);
- LOG_DEBUG("Starting dependencies of %s", instance->ToString().c_str());
instance->ListDependencies(&instance->dependencies_);
Start(&instance->dependencies_, thread);
- LOG_DEBUG("Finished starting dependencies and calling Start() of %s", instance->ToString().c_str());
-
instance->Start();
start_order_.push_back(module);
started_modules_[module] = instance;
- LOG_DEBUG("Started %s", instance->ToString().c_str());
return instance;
}
@@ -105,18 +93,12 @@ void ModuleRegistry::StopAll() {
for (auto it = start_order_.rbegin(); it != start_order_.rend(); it++) {
auto instance = started_modules_.find(*it);
ASSERT(instance != started_modules_.end());
- last_instance_ = "stopping " + instance->second->ToString();
// Clear the handler before stopping the module to allow it to shut down gracefully.
- LOG_INFO("Stopping Handler of Module %s", instance->second->ToString().c_str());
instance->second->handler_->Clear();
instance->second->handler_->WaitUntilStopped(kModuleStopTimeout);
- LOG_INFO("Stopping Module %s", instance->second->ToString().c_str());
instance->second->Stop();
- }
- for (auto it = start_order_.rbegin(); it != start_order_.rend(); it++) {
- auto instance = started_modules_.find(*it);
- ASSERT(instance != started_modules_.end());
+
delete instance->second->handler_;
delete instance->second;
started_modules_.erase(instance);
@@ -133,35 +115,4 @@ os::Handler* ModuleRegistry::GetModuleHandler(const ModuleFactory* module) const
}
return nullptr;
}
-
-void ModuleDumper::DumpState(std::string* output) const {
- ASSERT(output != nullptr);
-
- flatbuffers::FlatBufferBuilder builder(1024);
- auto title = builder.CreateString(title_);
-
- auto init_flags_offset = dumpsys::InitFlags::Dump(&builder);
- auto wakelock_offset = WakelockManager::Get().GetDumpsysData(&builder);
-
- std::queue<DumpsysDataFinisher> queue;
- for (auto it = module_registry_.start_order_.rbegin(); it != module_registry_.start_order_.rend(); it++) {
- auto instance = module_registry_.started_modules_.find(*it);
- ASSERT(instance != module_registry_.started_modules_.end());
- queue.push(instance->second->GetDumpsysData(&builder));
- }
-
- DumpsysDataBuilder data_builder(builder);
- data_builder.add_title(title);
- data_builder.add_init_flags(init_flags_offset);
- data_builder.add_wakelock_manager_data(wakelock_offset);
-
- while (!queue.empty()) {
- queue.front()(&data_builder);
- queue.pop();
- }
-
- builder.Finish(data_builder.Finish());
- *output = std::string(builder.GetBufferPointer(), builder.GetBufferPointer() + builder.GetSize());
-}
-
} // namespace bluetooth
diff --git a/gd/module.h b/gd/module.h
index 083d7b808..045865de5 100644
--- a/gd/module.h
+++ b/gd/module.h
@@ -16,7 +16,6 @@
#pragma once
-#include <flatbuffers/flatbuffers.h>
#include <functional>
#include <future>
#include <map>
@@ -24,7 +23,6 @@
#include <vector>
#include "common/bind.h"
-#include "dumpsys_data_generated.h"
#include "os/handler.h"
#include "os/log.h"
#include "os/thread.h"
@@ -32,38 +30,30 @@
namespace bluetooth {
class Module;
-class ModuleDumper;
class ModuleRegistry;
-class TestModuleRegistry;
-class FuzzTestModuleRegistry;
class ModuleFactory {
friend ModuleRegistry;
- friend FuzzTestModuleRegistry;
-
-public:
- ModuleFactory(std::function<Module*()> ctor);
+ public:
+ ModuleFactory(std::function<Module*()> ctor);
-private:
- std::function<Module*()> ctor_;
+ private:
+ std::function<Module*()> ctor_;
};
class ModuleList {
- friend Module;
friend ModuleRegistry;
-
-public:
- template <class T>
- void add() {
- list_.push_back(&T::Factory);
- }
+ friend Module;
+ public:
+ template <class T>
+ void add() {
+ list_.push_back(&T::Factory);
+ }
private:
std::vector<const ModuleFactory*> list_;
};
-using DumpsysDataFinisher = std::function<void(DumpsysDataBuilder* dumpsys_data_builder)>;
-
// Each leaf node module must have a factory like so:
//
// static const ModuleFactory Factory;
@@ -72,10 +62,7 @@ using DumpsysDataFinisher = std::function<void(DumpsysDataBuilder* dumpsys_data_
// The module registry will also use the factory as the identifier
// for that module.
class Module {
- friend ModuleDumper;
- friend ModuleRegistry;
- friend TestModuleRegistry;
-
+ friend ModuleRegistry;
public:
virtual ~Module() = default;
protected:
@@ -89,10 +76,7 @@ class Module {
// Release all resources, you're about to be deleted
virtual void Stop() = 0;
- // Get relevant state data from the module
- virtual DumpsysDataFinisher GetDumpsysData(flatbuffers::FlatBufferBuilder* builder) const;
-
- virtual std::string ToString() const = 0;
+ virtual std::string ToString() const;
::bluetooth::os::Handler* GetHandler() const;
@@ -103,16 +87,6 @@ class Module {
return static_cast<T*>(GetDependency(&T::Factory));
}
- template <typename Functor, typename... Args>
- void Call(Functor&& functor, Args&&... args) {
- GetHandler()->Call(std::forward<Functor>(functor), std::forward<Args>(args)...);
- }
-
- template <typename T, typename Functor, typename... Args>
- void CallOn(T* obj, Functor&& functor, Args&&... args) {
- GetHandler()->CallOn(obj, std::forward<Functor>(functor), std::forward<Args>(args)...);
- }
-
private:
Module* GetDependency(const ModuleFactory* module) const;
@@ -123,7 +97,6 @@ class Module {
class ModuleRegistry {
friend Module;
- friend ModuleDumper;
friend class StackManager;
public:
template <class T>
@@ -156,18 +129,6 @@ class ModuleRegistry {
std::map<const ModuleFactory*, Module*> started_modules_;
std::vector<const ModuleFactory*> start_order_;
- std::string last_instance_;
-};
-
-class ModuleDumper {
- public:
- ModuleDumper(const ModuleRegistry& module_registry, const char* title)
- : module_registry_(module_registry), title_(title) {}
- void DumpState(std::string* output) const;
-
- private:
- const ModuleRegistry& module_registry_;
- const std::string title_;
};
class TestModuleRegistry : public ModuleRegistry {
@@ -176,18 +137,12 @@ class TestModuleRegistry : public ModuleRegistry {
start_order_.push_back(module);
started_modules_[module] = instance;
set_registry_and_handler(instance, &test_thread);
- instance->Start();
}
Module* GetModuleUnderTest(const ModuleFactory* module) const {
return Get(module);
}
- template <class T>
- T* GetModuleUnderTest() const {
- return static_cast<T*>(GetModuleUnderTest(&T::Factory));
- }
-
os::Handler* GetTestModuleHandler(const ModuleFactory* module) const {
return GetModuleHandler(module);
}
@@ -197,12 +152,9 @@ class TestModuleRegistry : public ModuleRegistry {
}
bool SynchronizeModuleHandler(const ModuleFactory* module, std::chrono::milliseconds timeout) const {
- return SynchronizeHandler(GetTestModuleHandler(module), timeout);
- }
-
- bool SynchronizeHandler(os::Handler* handler, std::chrono::milliseconds timeout) const {
std::promise<void> promise;
auto future = promise.get_future();
+ os::Handler* handler = GetTestModuleHandler(module);
handler->Post(common::BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)));
return future.wait_for(timeout) == std::future_status::ready;
}
@@ -211,26 +163,4 @@ class TestModuleRegistry : public ModuleRegistry {
os::Thread test_thread{"test_thread", os::Thread::Priority::NORMAL};
};
-class FuzzTestModuleRegistry : public TestModuleRegistry {
- public:
- template <class T>
- T* Inject(const ModuleFactory* overriding) {
- Module* instance = T::Factory.ctor_();
- InjectTestModule(overriding, instance);
- return static_cast<T*>(instance);
- }
-
- template <class T>
- T* Start() {
- return ModuleRegistry::Start<T>(&GetTestThread());
- }
-
- void WaitForIdleAndStopAll() {
- if (!GetTestThread().GetReactor()->WaitForIdle(std::chrono::milliseconds(100))) {
- LOG_ERROR("idle timed out");
- }
- StopAll();
- }
-};
-
} // namespace bluetooth
diff --git a/gd/module_unittest.cc b/gd/module_unittest.cc
index f940016fc..d0efb5db5 100644
--- a/gd/module_unittest.cc
+++ b/gd/module_unittest.cc
@@ -15,16 +15,9 @@
*/
#include "module.h"
-#include "module_unittest_generated.h"
-#include "os/handler.h"
-#include "os/thread.h"
#include "gtest/gtest.h"
-#include <functional>
-#include <future>
-#include <string>
-
using ::bluetooth::os::Thread;
namespace bluetooth {
@@ -46,8 +39,6 @@ class ModuleTest : public ::testing::Test {
Thread* thread_;
};
-os::Handler* test_module_no_dependency_handler = nullptr;
-
class TestModuleNoDependency : public Module {
public:
static const ModuleFactory Factory;
@@ -59,25 +50,18 @@ class TestModuleNoDependency : public Module {
void Start() override {
// A module is not considered started until Start() finishes
EXPECT_FALSE(GetModuleRegistry()->IsStarted<TestModuleNoDependency>());
- test_module_no_dependency_handler = GetHandler();
}
void Stop() override {
// A module is not considered stopped until after Stop() finishes
EXPECT_TRUE(GetModuleRegistry()->IsStarted<TestModuleNoDependency>());
}
-
- std::string ToString() const override {
- return std::string("TestModuleNoDependency");
- }
};
const ModuleFactory TestModuleNoDependency::Factory = ModuleFactory([]() {
return new TestModuleNoDependency();
});
-os::Handler* test_module_one_dependency_handler = nullptr;
-
class TestModuleOneDependency : public Module {
public:
static const ModuleFactory Factory;
@@ -92,7 +76,6 @@ class TestModuleOneDependency : public Module {
// A module is not considered started until Start() finishes
EXPECT_FALSE(GetModuleRegistry()->IsStarted<TestModuleOneDependency>());
- test_module_one_dependency_handler = GetHandler();
}
void Stop() override {
@@ -101,10 +84,6 @@ class TestModuleOneDependency : public Module {
// A module is not considered stopped until after Stop() finishes
EXPECT_TRUE(GetModuleRegistry()->IsStarted<TestModuleOneDependency>());
}
-
- std::string ToString() const override {
- return std::string("TestModuleOneDependency");
- }
};
const ModuleFactory TestModuleOneDependency::Factory = ModuleFactory([]() {
@@ -129,10 +108,6 @@ class TestModuleNoDependencyTwo : public Module {
// A module is not considered stopped until after Stop() finishes
EXPECT_TRUE(GetModuleRegistry()->IsStarted<TestModuleNoDependencyTwo>());
}
-
- std::string ToString() const override {
- return std::string("TestModuleNoDependencyTwo");
- }
};
const ModuleFactory TestModuleNoDependencyTwo::Factory = ModuleFactory([]() {
@@ -164,61 +139,12 @@ class TestModuleTwoDependencies : public Module {
// A module is not considered stopped until after Stop() finishes
EXPECT_TRUE(GetModuleRegistry()->IsStarted<TestModuleTwoDependencies>());
}
-
- std::string ToString() const override {
- return std::string("TestModuleTwoDependencies");
- }
};
const ModuleFactory TestModuleTwoDependencies::Factory = ModuleFactory([]() {
return new TestModuleTwoDependencies();
});
-// To generate module unittest flatbuffer headers:
-// $ flatc --cpp module_unittest.fbs
-class TestModuleDumpState : public Module {
- public:
- static const ModuleFactory Factory;
-
- std::string test_string_{"Initial Test String"};
-
- protected:
- void ListDependencies(ModuleList* list) override {
- list->add<TestModuleNoDependency>();
- }
-
- void Start() override {
- EXPECT_TRUE(GetModuleRegistry()->IsStarted<TestModuleNoDependency>());
-
- // A module is not considered started until Start() finishes
- EXPECT_FALSE(GetModuleRegistry()->IsStarted<TestModuleDumpState>());
- test_module_one_dependency_handler = GetHandler();
- }
-
- void Stop() override {
- EXPECT_TRUE(GetModuleRegistry()->IsStarted<TestModuleNoDependency>());
-
- // A module is not considered stopped until after Stop() finishes
- EXPECT_TRUE(GetModuleRegistry()->IsStarted<TestModuleDumpState>());
- }
-
- std::string ToString() const override {
- return std::string("TestModuleDumpState");
- }
-
- DumpsysDataFinisher GetDumpsysData(flatbuffers::FlatBufferBuilder* fb_builder) const override {
- auto string = fb_builder->CreateString(test_string_.c_str());
-
- auto builder = ModuleUnitTestDataBuilder(*fb_builder);
- builder.add_title(string);
- auto table = builder.Finish();
-
- return [table](DumpsysDataBuilder* builder) { builder->add_module_unittest_data(table); };
- }
-};
-
-const ModuleFactory TestModuleDumpState::Factory = ModuleFactory([]() { return new TestModuleDumpState(); });
-
TEST_F(ModuleTest, no_dependency) {
ModuleList list;
list.add<TestModuleNoDependency>();
@@ -273,48 +199,5 @@ TEST_F(ModuleTest, two_dependencies) {
EXPECT_FALSE(registry_->IsStarted<TestModuleTwoDependencies>());
}
-void post_to_module_one_handler() {
- std::this_thread::sleep_for(std::chrono::milliseconds(100));
- test_module_one_dependency_handler->Post(common::BindOnce([] { FAIL(); }));
-}
-
-TEST_F(ModuleTest, shutdown_with_unhandled_callback) {
- ModuleList list;
- list.add<TestModuleOneDependency>();
- registry_->Start(&list, thread_);
- test_module_no_dependency_handler->Post(common::BindOnce(&post_to_module_one_handler));
- registry_->StopAll();
-}
-
-TEST_F(ModuleTest, dump_state) {
- static const char* title = "Test Dump Title";
- ModuleList list;
- list.add<TestModuleDumpState>();
- registry_->Start(&list, thread_);
-
- ModuleDumper dumper(*registry_, title);
-
- std::string output;
- dumper.DumpState(&output);
-
- auto data = flatbuffers::GetRoot<DumpsysData>(output.data());
- EXPECT_STREQ(title, data->title()->c_str());
-
- auto test_data = data->module_unittest_data();
- EXPECT_STREQ("Initial Test String", test_data->title()->c_str());
-
- TestModuleDumpState* test_module =
- static_cast<TestModuleDumpState*>(registry_->Start(&TestModuleDumpState::Factory, nullptr));
- test_module->test_string_ = "A Second Test String";
-
- dumper.DumpState(&output);
-
- data = flatbuffers::GetRoot<DumpsysData>(output.data());
- test_data = data->module_unittest_data();
- EXPECT_STREQ("A Second Test String", test_data->title()->c_str());
-
- registry_->StopAll();
-}
-
} // namespace
} // namespace bluetooth
diff --git a/gd/module_unittest.fbs b/gd/module_unittest.fbs
deleted file mode 100644
index 3c0a1b6bd..000000000
--- a/gd/module_unittest.fbs
+++ /dev/null
@@ -1,10 +0,0 @@
-// module_unittest
-namespace bluetooth;
-
-attribute "privacy";
-
-table ModuleUnitTestData {
- title:string (privacy:"Any");
-}
-
-root_type ModuleUnitTestData;
diff --git a/gd/module_unittest_generated.h b/gd/module_unittest_generated.h
deleted file mode 100644
index 3c9fd362c..000000000
--- a/gd/module_unittest_generated.h
+++ /dev/null
@@ -1,84 +0,0 @@
-// automatically generated by the FlatBuffers compiler, do not modify
-
-#ifndef FLATBUFFERS_GENERATED_MODULEUNITTEST_BLUETOOTH_H_
-#define FLATBUFFERS_GENERATED_MODULEUNITTEST_BLUETOOTH_H_
-
-#include "flatbuffers/flatbuffers.h"
-
-namespace bluetooth {
-
-struct ModuleUnitTestData;
-struct ModuleUnitTestDataBuilder;
-
-struct ModuleUnitTestData FLATBUFFERS_FINAL_CLASS : private flatbuffers::Table {
- typedef ModuleUnitTestDataBuilder Builder;
- enum FlatBuffersVTableOffset FLATBUFFERS_VTABLE_UNDERLYING_TYPE { VT_TITLE = 4 };
- const flatbuffers::String* title() const {
- return GetPointer<const flatbuffers::String*>(VT_TITLE);
- }
- bool Verify(flatbuffers::Verifier& verifier) const {
- return VerifyTableStart(verifier) && VerifyOffset(verifier, VT_TITLE) && verifier.VerifyString(title()) &&
- verifier.EndTable();
- }
-};
-
-struct ModuleUnitTestDataBuilder {
- typedef ModuleUnitTestData Table;
- flatbuffers::FlatBufferBuilder& fbb_;
- flatbuffers::uoffset_t start_;
- void add_title(flatbuffers::Offset<flatbuffers::String> title) {
- fbb_.AddOffset(ModuleUnitTestData::VT_TITLE, title);
- }
- explicit ModuleUnitTestDataBuilder(flatbuffers::FlatBufferBuilder& _fbb) : fbb_(_fbb) {
- start_ = fbb_.StartTable();
- }
- ModuleUnitTestDataBuilder& operator=(const ModuleUnitTestDataBuilder&);
- flatbuffers::Offset<ModuleUnitTestData> Finish() {
- const auto end = fbb_.EndTable(start_);
- auto o = flatbuffers::Offset<ModuleUnitTestData>(end);
- return o;
- }
-};
-
-inline flatbuffers::Offset<ModuleUnitTestData> CreateModuleUnitTestData(
- flatbuffers::FlatBufferBuilder& _fbb, flatbuffers::Offset<flatbuffers::String> title = 0) {
- ModuleUnitTestDataBuilder builder_(_fbb);
- builder_.add_title(title);
- return builder_.Finish();
-}
-
-inline flatbuffers::Offset<ModuleUnitTestData> CreateModuleUnitTestDataDirect(
- flatbuffers::FlatBufferBuilder& _fbb, const char* title = nullptr) {
- auto title__ = title ? _fbb.CreateString(title) : 0;
- return bluetooth::CreateModuleUnitTestData(_fbb, title__);
-}
-
-inline const bluetooth::ModuleUnitTestData* GetModuleUnitTestData(const void* buf) {
- return flatbuffers::GetRoot<bluetooth::ModuleUnitTestData>(buf);
-}
-
-inline const bluetooth::ModuleUnitTestData* GetSizePrefixedModuleUnitTestData(const void* buf) {
- return flatbuffers::GetSizePrefixedRoot<bluetooth::ModuleUnitTestData>(buf);
-}
-
-inline bool VerifyModuleUnitTestDataBuffer(flatbuffers::Verifier& verifier) {
- return verifier.VerifyBuffer<bluetooth::ModuleUnitTestData>(nullptr);
-}
-
-inline bool VerifySizePrefixedModuleUnitTestDataBuffer(flatbuffers::Verifier& verifier) {
- return verifier.VerifySizePrefixedBuffer<bluetooth::ModuleUnitTestData>(nullptr);
-}
-
-inline void FinishModuleUnitTestDataBuffer(
- flatbuffers::FlatBufferBuilder& fbb, flatbuffers::Offset<bluetooth::ModuleUnitTestData> root) {
- fbb.Finish(root);
-}
-
-inline void FinishSizePrefixedModuleUnitTestDataBuffer(
- flatbuffers::FlatBufferBuilder& fbb, flatbuffers::Offset<bluetooth::ModuleUnitTestData> root) {
- fbb.FinishSizePrefixed(root);
-}
-
-} // namespace bluetooth
-
-#endif // FLATBUFFERS_GENERATED_MODULEUNITTEST_BLUETOOTH_H_
diff --git a/gd/neighbor/Android.bp b/gd/neighbor/Android.bp
index 5f6cf71d3..35ec925d0 100644
--- a/gd/neighbor/Android.bp
+++ b/gd/neighbor/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothNeighborSources",
srcs: [
diff --git a/gd/neighbor/BUILD.gn b/gd/neighbor/BUILD.gn
deleted file mode 100644
index 02e4d7923..000000000
--- a/gd/neighbor/BUILD.gn
+++ /dev/null
@@ -1,30 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-source_set("BluetoothNeighborSources") {
- sources = [
- "connectability.cc",
- "discoverability.cc",
- "inquiry.cc",
- "name.cc",
- "name_db.cc",
- "page.cc",
- "scan.cc",
- ]
-
- deps = [ "//bt/gd:gd_default_deps" ]
-
- configs += [ "//bt/gd:gd_defaults" ]
-}
diff --git a/gd/neighbor/cert/neighbor_test.py b/gd/neighbor/cert/neighbor_test.py
index 6b744baf0..e6003c2c1 100644
--- a/gd/neighbor/cert/neighbor_test.py
+++ b/gd/neighbor/cert/neighbor_test.py
@@ -14,43 +14,62 @@
# See the License for the specific language governing permissions and
# limitations under the License.
-from datetime import timedelta
+import os
+import sys
+import logging
-from cert.gd_base_test import GdBaseTestClass
-from cert.matchers import HciMatchers, NeighborMatchers
-from cert.py_hci import PyHci
-from cert.truth import assertThat
-from neighbor.cert.py_neighbor import PyNeighbor
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
+from cert.event_callback_stream import EventCallbackStream
+from cert.event_asserts import EventAsserts
+from google.protobuf import empty_pb2 as empty_proto
+from facade import rootservice_pb2 as facade_rootservice
+from hci.facade import facade_pb2 as hci_facade
+from hci.facade import controller_facade_pb2 as controller_facade
from neighbor.facade import facade_pb2 as neighbor_facade
from bluetooth_packets_python3 import hci_packets
-from bluetooth_packets_python3.hci_packets import OpCode
+import bluetooth_packets_python3 as bt_packets
-class NeighborTest(GdBaseTestClass):
-
- def setup_class(self):
- super().setup_class(dut_module='HCI_INTERFACES', cert_module='HCI')
+class NeighborTest(GdFacadeOnlyBaseTestClass):
def setup_test(self):
- super().setup_test()
- self.cert_hci = PyHci(self.cert, acl_streaming=True)
- self.cert_hci.send_command(hci_packets.WriteScanEnableBuilder(hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN))
- self.cert_name = b'Im_A_Cert'
- self.cert_address = self.cert_hci.read_own_address()
- self.cert_name += b'@' + self.cert_address.encode('utf8')
- self.dut_neighbor = PyNeighbor(self.dut)
+ self.device_under_test.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI_INTERFACES'),))
+ self.cert_device.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'HCI'),))
+
+ self.device_under_test.wait_channel_ready()
+ self.cert_device.wait_channel_ready()
def teardown_test(self):
- self.cert_hci.close()
- super().teardown_test()
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+ self.cert_device.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
+
+ def register_for_dut_event(self, event_code):
+ msg = hci_facade.EventCodeMsg(code=int(event_code))
+ self.device_under_test.hci.RegisterEventHandler(msg)
+
+ def register_for_event(self, event_code):
+ msg = hci_facade.EventCodeMsg(code=int(event_code))
+ self.cert_device.hci.RegisterEventHandler(msg)
- def _set_name(self):
- padded_name = self.cert_name
- while len(padded_name) < 248:
- padded_name = padded_name + b'\0'
- self.cert_hci.send_command(hci_packets.WriteLocalNameBuilder(padded_name))
+ def register_for_le_event(self, event_code):
+ msg = hci_facade.LeSubeventCodeMsg(code=int(event_code))
+ self.cert_device.hci.RegisterLeEventHandler(msg)
- assertThat(self.cert_hci.get_event_stream()).emits(HciMatchers.CommandComplete(OpCode.WRITE_LOCAL_NAME))
+ def enqueue_hci_command(self, command, expect_complete):
+ cmd_bytes = bytes(command.Serialize())
+ cmd = hci_facade.CommandMsg(command=cmd_bytes)
+ if (expect_complete):
+ self.cert_device.hci.EnqueueCommandWithComplete(cmd)
+ else:
+ self.cert_device.hci.EnqueueCommandWithStatus(cmd)
def test_inquiry_from_dut(self):
inquiry_msg = neighbor_facade.InquiryMsg(
@@ -58,41 +77,109 @@ class NeighborTest(GdBaseTestClass):
result_mode=neighbor_facade.ResultMode.STANDARD,
length_1_28s=3,
max_results=0)
- session = self.dut_neighbor.set_inquiry_mode(inquiry_msg)
- self.cert_hci.send_command(hci_packets.WriteScanEnableBuilder(hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN))
- assertThat(session).emits(NeighborMatchers.InquiryResult(self.cert_address), timeout=timedelta(seconds=10))
+ with EventCallbackStream(
+ self.device_under_test.neighbor.SetInquiryMode(
+ inquiry_msg)) as inquiry_event_stream:
+ hci_event_asserts = EventAsserts(inquiry_event_stream)
+ self.enqueue_hci_command(
+ hci_packets.WriteScanEnableBuilder(
+ hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN), True)
+ hci_event_asserts.assert_event_occurs(
+ lambda msg: b'\x02\x0f' in msg.packet
+ # Expecting an HCI Event (code 0x02, length 0x0f)
+ )
def test_inquiry_rssi_from_dut(self):
inquiry_msg = neighbor_facade.InquiryMsg(
inquiry_mode=neighbor_facade.DiscoverabilityMode.GENERAL,
result_mode=neighbor_facade.ResultMode.RSSI,
- length_1_28s=6,
+ length_1_28s=3,
max_results=0)
- session = self.dut_neighbor.set_inquiry_mode(inquiry_msg)
- self.cert_hci.send_command(hci_packets.WriteScanEnableBuilder(hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN))
- assertThat(session).emits(
- NeighborMatchers.InquiryResultwithRssi(self.cert_address), timeout=timedelta(seconds=10))
+ with EventCallbackStream(
+ self.device_under_test.neighbor.SetInquiryMode(
+ inquiry_msg)) as inquiry_event_stream:
+ hci_event_asserts = EventAsserts(inquiry_event_stream)
+ self.enqueue_hci_command(
+ hci_packets.WriteScanEnableBuilder(
+ hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN), True)
+ hci_event_asserts.assert_event_occurs(
+ lambda msg: b'\x22\x0f' in msg.packet
+ # Expecting an HCI Event (code 0x22, length 0x0f)
+ )
def test_inquiry_extended_from_dut(self):
- self._set_name()
+ name_string = b'Im_A_Cert'
gap_name = hci_packets.GapData()
gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(self.cert_name))
+ gap_name.data = list(bytes(name_string))
gap_data = list([gap_name])
- self.cert_hci.send_command(
- hci_packets.WriteExtendedInquiryResponseBuilder(hci_packets.FecRequired.NOT_REQUIRED, gap_data))
+ self.enqueue_hci_command(
+ hci_packets.WriteExtendedInquiryResponseBuilder(
+ hci_packets.FecRequired.NOT_REQUIRED, gap_data), True)
inquiry_msg = neighbor_facade.InquiryMsg(
inquiry_mode=neighbor_facade.DiscoverabilityMode.GENERAL,
result_mode=neighbor_facade.ResultMode.EXTENDED,
- length_1_28s=8,
+ length_1_28s=3,
max_results=0)
- session = self.dut_neighbor.set_inquiry_mode(inquiry_msg)
- self.cert_hci.send_command(hci_packets.WriteScanEnableBuilder(hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN))
- assertThat(session).emits(
- NeighborMatchers.ExtendedInquiryResult(self.cert_address), timeout=timedelta(seconds=10))
+ with EventCallbackStream(
+ self.device_under_test.neighbor.SetInquiryMode(
+ inquiry_msg)) as inquiry_event_stream:
+ hci_event_asserts = EventAsserts(inquiry_event_stream)
+ self.enqueue_hci_command(
+ hci_packets.WriteScanEnableBuilder(
+ hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN), True)
+ hci_event_asserts.assert_event_occurs(
+ lambda msg: name_string in msg.packet)
def test_remote_name(self):
- self._set_name()
- session = self.dut_neighbor.get_remote_name(self.cert_address)
- session.verify_name(self.cert_name)
+ self.register_for_dut_event(
+ hci_packets.EventCode.REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION)
+
+ with EventCallbackStream(self.cert_device.hci.FetchEvents(empty_proto.Empty())) as hci_event_stream, \
+ EventCallbackStream(self.device_under_test.neighbor.GetRemoteNameEvents(empty_proto.Empty())) as name_event_stream:
+ name_event_asserts = EventAsserts(name_event_stream)
+ hci_event_asserts = EventAsserts(hci_event_stream)
+
+ cert_name = b'Im_A_Cert'
+ padded_name = cert_name
+ while len(padded_name) < 248:
+ padded_name = padded_name + b'\0'
+ self.enqueue_hci_command(
+ hci_packets.WriteLocalNameBuilder(padded_name), True)
+
+ hci_event_asserts.assert_event_occurs(
+ lambda msg: b'\x0e\x04\x01\x13\x0c' in msg.event)
+
+ address = hci_packets.Address()
+
+ def get_address_from_complete(packet):
+ packet_bytes = packet.event
+ if b'\x0e\x0a\x01\x09\x10' in packet_bytes:
+ nonlocal address
+ addr_view = hci_packets.ReadBdAddrCompleteView(
+ hci_packets.CommandCompleteView(
+ hci_packets.EventPacketView(
+ bt_packets.PacketViewLittleEndian(
+ list(packet_bytes)))))
+ address = addr_view.GetBdAddr()
+ return True
+ return False
+
+ # DUT Enables scans and gets its address
+ self.enqueue_hci_command(
+ hci_packets.WriteScanEnableBuilder(
+ hci_packets.ScanEnable.INQUIRY_AND_PAGE_SCAN), True)
+ self.enqueue_hci_command(hci_packets.ReadBdAddrBuilder(), True)
+
+ hci_event_asserts.assert_event_occurs(get_address_from_complete)
+
+ cert_address = address.encode('utf8')
+
+ self.device_under_test.neighbor.ReadRemoteName(
+ neighbor_facade.RemoteNameRequestMsg(
+ address=cert_address,
+ page_scan_repetition_mode=1,
+ clock_offset=0x6855))
+ name_event_asserts.assert_event_occurs(
+ lambda msg: cert_name in msg.name)
diff --git a/gd/neighbor/cert/py_neighbor.py b/gd/neighbor/cert/py_neighbor.py
deleted file mode 100644
index cf09c486c..000000000
--- a/gd/neighbor/cert/py_neighbor.py
+++ /dev/null
@@ -1,84 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from datetime import timedelta
-
-from bluetooth_packets_python3 import hci_packets
-from cert.event_stream import EventStream
-from cert.event_stream import IEventStream
-from cert.closable import Closable
-from cert.closable import safeClose
-from cert.truth import assertThat
-from google.protobuf import empty_pb2 as empty_proto
-from hci.facade import hci_facade_pb2 as hci_facade
-from neighbor.facade import facade_pb2 as neighbor_facade
-
-
-class InquirySession(Closable, IEventStream):
-
- def __init__(self, device, inquiry_msg):
- self.inquiry_event_stream = EventStream(device.neighbor.SetInquiryMode(inquiry_msg))
-
- def get_event_queue(self):
- return self.inquiry_event_stream.get_event_queue()
-
- def close(self):
- safeClose(self.inquiry_event_stream)
-
-
-class GetRemoteNameSession(Closable):
-
- def __init__(self, device):
- self.remote_name_stream = EventStream(device.neighbor.GetRemoteNameEvents(empty_proto.Empty()))
-
- def verify_name(self, name):
- assertThat(self.remote_name_stream).emits(lambda msg: bytes(name) in msg.name, timeout=timedelta(seconds=10))
-
- def close(self):
- safeClose(self.remote_name_stream)
-
-
-class PyNeighbor(object):
-
- def __init__(self, device):
- self.device = device
- self.remote_host_supported_features_notification_registered = False
-
- def set_inquiry_mode(self, inquiry_msg):
- """
- Set the inquiry mode and return a session which can be used for event queue assertion
- """
- return InquirySession(self.device, inquiry_msg)
-
- def _register_remote_host_supported_features_notification(self):
- """
- REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION event will be sent when a device sends remote name request
- """
- if self.remote_host_supported_features_notification_registered:
- return
- msg = hci_facade.EventRequest(code=int(hci_packets.EventCode.REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION))
- self.device.hci.RequestEvent(msg)
- self.remote_host_supported_features_notification_registered = True
-
- def get_remote_name(self, remote_address):
- """
- Get the remote name and return a session which can be used for event queue assertion
- """
- self._register_remote_host_supported_features_notification()
- self.device.neighbor.ReadRemoteName(
- neighbor_facade.RemoteNameRequestMsg(
- address=remote_address.encode('utf8'), page_scan_repetition_mode=1, clock_offset=0x6855))
- return GetRemoteNameSession(self.device)
diff --git a/gd/neighbor/connectability.cc b/gd/neighbor/connectability.cc
index d9f2d9010..8a60bdd35 100644
--- a/gd/neighbor/connectability.cc
+++ b/gd/neighbor/connectability.cc
@@ -15,13 +15,12 @@
*/
#define LOG_TAG "neighbor2"
-#include "neighbor/connectability.h"
-
#include <memory>
#include "hci/hci_layer.h"
#include "hci/hci_packets.h"
#include "module.h"
+#include "neighbor/connectability.h"
#include "neighbor/scan.h"
#include "os/handler.h"
#include "os/log.h"
diff --git a/gd/neighbor/connectability.h b/gd/neighbor/connectability.h
index 777dfceca..8cdd64378 100644
--- a/gd/neighbor/connectability.h
+++ b/gd/neighbor/connectability.h
@@ -37,9 +37,6 @@ class ConnectabilityModule : public bluetooth::Module {
void ListDependencies(ModuleList* list) override;
void Start() override;
void Stop() override;
- std::string ToString() const override {
- return std::string("ConnectabilityModule");
- }
private:
struct impl;
diff --git a/gd/neighbor/discoverability.cc b/gd/neighbor/discoverability.cc
index abaa4a7ef..3514cafb7 100644
--- a/gd/neighbor/discoverability.cc
+++ b/gd/neighbor/discoverability.cc
@@ -15,14 +15,13 @@
*/
#define LOG_TAG "bt_gd_neigh"
-#include "neighbor/discoverability.h"
-
#include <memory>
#include "common/bind.h"
#include "hci/hci_layer.h"
#include "hci/hci_packets.h"
#include "module.h"
+#include "neighbor/discoverability.h"
#include "neighbor/scan.h"
#include "os/handler.h"
#include "os/log.h"
@@ -92,10 +91,10 @@ void neighbor::DiscoverabilityModule::impl::OnCommandComplete(hci::CommandComple
void neighbor::DiscoverabilityModule::impl::StartDiscoverability(std::vector<hci::Lap>& laps) {
ASSERT(laps.size() <= num_supported_iac_);
- hci_layer_->EnqueueCommand(
- hci::WriteCurrentIacLapBuilder::Create(laps), handler_->BindOnceOn(this, &impl::OnCommandComplete));
- hci_layer_->EnqueueCommand(
- hci::ReadCurrentIacLapBuilder::Create(), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+ hci_layer_->EnqueueCommand(hci::WriteCurrentIacLapBuilder::Create(laps),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
+ hci_layer_->EnqueueCommand(hci::ReadCurrentIacLapBuilder::Create(),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
scan_module_->SetInquiryScan();
}
@@ -116,19 +115,19 @@ void neighbor::DiscoverabilityModule::impl::Start() {
scan_module_ = module_.GetDependency<neighbor::ScanModule>();
handler_ = module_.GetHandler();
- hci_layer_->EnqueueCommand(
- hci::ReadCurrentIacLapBuilder::Create(), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+ hci_layer_->EnqueueCommand(hci::ReadCurrentIacLapBuilder::Create(),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
- hci_layer_->EnqueueCommand(
- hci::ReadNumberOfSupportedIacBuilder::Create(), handler_->BindOnceOn(this, &impl::OnCommandComplete));
- LOG_INFO("Started discoverability module");
+ hci_layer_->EnqueueCommand(hci::ReadNumberOfSupportedIacBuilder::Create(),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
+ LOG_DEBUG("Started discoverability module");
}
void neighbor::DiscoverabilityModule::impl::Dump() const {
- LOG_INFO("Number of supported iacs:%hhd", num_supported_iac_);
- LOG_INFO("Number of current iacs:%zd", laps_.size());
+ LOG_DEBUG("Number of supported iacs:%hhd", num_supported_iac_);
+ LOG_DEBUG("Number of current iacs:%zd", laps_.size());
for (auto it : laps_) {
- LOG_INFO(" discoverability lap:%x", it.lap_);
+ LOG_DEBUG(" discoverability lap:%x", it.lap_);
}
}
diff --git a/gd/neighbor/discoverability.h b/gd/neighbor/discoverability.h
index 993266221..124716c70 100644
--- a/gd/neighbor/discoverability.h
+++ b/gd/neighbor/discoverability.h
@@ -16,7 +16,6 @@
#pragma once
#include <memory>
-#include <string>
#include "module.h"
@@ -41,9 +40,6 @@ class DiscoverabilityModule : public bluetooth::Module {
void ListDependencies(ModuleList* list) override;
void Start() override;
void Stop() override;
- std::string ToString() const override {
- return std::string("DiscoverabilityModule");
- }
private:
struct impl;
diff --git a/gd/neighbor/facade/facade.cc b/gd/neighbor/facade/facade.cc
index 1a7aef06d..4ede26459 100644
--- a/gd/neighbor/facade/facade.cc
+++ b/gd/neighbor/facade/facade.cc
@@ -33,25 +33,15 @@ namespace facade {
class NeighborFacadeService : public NeighborFacade::Service {
public:
- NeighborFacadeService(
- ConnectabilityModule* connectability_module,
- DiscoverabilityModule* discoverability_module,
- InquiryModule* inquiry_module,
- NameModule* name_module,
- PageModule*,
- ScanModule* scan_module,
- ::bluetooth::os::Handler* facade_handler)
- : connectability_module_(connectability_module),
- discoverability_module_(discoverability_module),
- inquiry_module_(inquiry_module),
- name_module_(name_module),
- scan_module_(scan_module),
+ NeighborFacadeService(ConnectabilityModule* connectability_module, DiscoverabilityModule* discoverability_module,
+ InquiryModule* inquiry_module, NameModule* name_module, PageModule*, ScanModule* scan_module,
+ ::bluetooth::os::Handler* facade_handler)
+ : connectability_module_(connectability_module), discoverability_module_(discoverability_module),
+ inquiry_module_(inquiry_module), name_module_(name_module), scan_module_(scan_module),
facade_handler_(facade_handler) {}
- ::grpc::Status SetConnectability(
- ::grpc::ServerContext* context,
- const ::bluetooth::neighbor::EnableMsg* request,
- ::google::protobuf::Empty* response) override {
+ ::grpc::Status SetConnectability(::grpc::ServerContext* context, const ::bluetooth::neighbor::EnableMsg* request,
+ ::google::protobuf::Empty* response) override {
if (request->enabled()) {
connectability_module_->StartConnectability();
} else {
@@ -60,10 +50,9 @@ class NeighborFacadeService : public NeighborFacade::Service {
return ::grpc::Status::OK;
}
- ::grpc::Status SetDiscoverability(
- ::grpc::ServerContext* context,
- const ::bluetooth::neighbor::DiscoverabilitiyMsg* request,
- ::google::protobuf::Empty* response) override {
+ ::grpc::Status SetDiscoverability(::grpc::ServerContext* context,
+ const ::bluetooth::neighbor::DiscoverabilitiyMsg* request,
+ ::google::protobuf::Empty* response) override {
switch (request->mode()) {
case DiscoverabilityMode::OFF:
discoverability_module_->StopDiscoverability();
@@ -80,10 +69,8 @@ class NeighborFacadeService : public NeighborFacade::Service {
return ::grpc::Status::OK;
}
- ::grpc::Status SetInquiryMode(
- ::grpc::ServerContext* context,
- const ::bluetooth::neighbor::InquiryMsg* request,
- ::grpc::ServerWriter<InquiryResultMsg>* writer) override {
+ ::grpc::Status SetInquiryMode(::grpc::ServerContext* context, const ::bluetooth::neighbor::InquiryMsg* request,
+ ::grpc::ServerWriter<InquiryResultMsg>* writer) override {
inquiry_module_->RegisterCallbacks(inquiry_callbacks_);
switch (request->result_mode()) {
case ResultMode::STANDARD:
@@ -114,10 +101,9 @@ class NeighborFacadeService : public NeighborFacade::Service {
return pending_events_.RunLoop(context, writer);
}
- ::grpc::Status ReadRemoteName(
- ::grpc::ServerContext* context,
- const ::bluetooth::neighbor::RemoteNameRequestMsg* request,
- ::google::protobuf::Empty* response) override {
+ ::grpc::Status ReadRemoteName(::grpc::ServerContext* context,
+ const ::bluetooth::neighbor::RemoteNameRequestMsg* request,
+ ::google::protobuf::Empty* response) override {
hci::Address remote;
ASSERT(hci::Address::FromString(request->address(), remote));
hci::PageScanRepetitionMode mode;
@@ -135,26 +121,19 @@ class NeighborFacadeService : public NeighborFacade::Service {
LOG_ALWAYS_FATAL("Unknown PageScanRepetition mode %d", static_cast<int>(request->page_scan_repetition_mode()));
}
name_module_->ReadRemoteNameRequest(
- remote,
- mode,
- request->clock_offset(),
+ remote, mode, request->clock_offset(),
(request->clock_offset() != 0 ? hci::ClockOffsetValid::VALID : hci::ClockOffsetValid::INVALID),
- common::Bind(&NeighborFacadeService::on_remote_name, common::Unretained(this)),
- facade_handler_);
+ common::Bind(&NeighborFacadeService::on_remote_name, common::Unretained(this)), facade_handler_);
return ::grpc::Status::OK;
}
- ::grpc::Status GetRemoteNameEvents(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<RemoteNameResponseMsg>* writer) override {
+ ::grpc::Status GetRemoteNameEvents(::grpc::ServerContext* context, const ::google::protobuf::Empty* request,
+ ::grpc::ServerWriter<RemoteNameResponseMsg>* writer) override {
return pending_remote_names_.RunLoop(context, writer);
}
- ::grpc::Status EnableInquiryScan(
- ::grpc::ServerContext* context,
- const ::bluetooth::neighbor::EnableMsg* request,
- ::google::protobuf::Empty* response) override {
+ ::grpc::Status EnableInquiryScan(::grpc::ServerContext* context, const ::bluetooth::neighbor::EnableMsg* request,
+ ::google::protobuf::Empty* response) override {
if (request->enabled()) {
scan_module_->SetInquiryScan();
} else {
@@ -163,10 +142,8 @@ class NeighborFacadeService : public NeighborFacade::Service {
return ::grpc::Status::OK;
}
- ::grpc::Status EnablePageScan(
- ::grpc::ServerContext* context,
- const ::bluetooth::neighbor::EnableMsg* request,
- ::google::protobuf::Empty* response) override {
+ ::grpc::Status EnablePageScan(::grpc::ServerContext* context, const ::bluetooth::neighbor::EnableMsg* request,
+ ::google::protobuf::Empty* response) override {
if (request->enabled()) {
scan_module_->SetPageScan();
} else {
@@ -176,7 +153,7 @@ class NeighborFacadeService : public NeighborFacade::Service {
}
private:
- void on_incoming_inquiry_result(hci::EventView view) {
+ void on_incoming_inquiry_result(hci::EventPacketView view) {
InquiryResultMsg inquiry_result_msg;
inquiry_result_msg.set_packet(std::string(view.begin(), view.end()));
pending_events_.OnIncomingEvent(std::move(inquiry_result_msg));
@@ -224,14 +201,9 @@ void NeighborFacadeModule::ListDependencies(ModuleList* list) {
void NeighborFacadeModule::Start() {
::bluetooth::grpc::GrpcFacadeModule::Start();
- service_ = new NeighborFacadeService(
- GetDependency<ConnectabilityModule>(),
- GetDependency<DiscoverabilityModule>(),
- GetDependency<InquiryModule>(),
- GetDependency<NameModule>(),
- GetDependency<PageModule>(),
- GetDependency<ScanModule>(),
- GetHandler());
+ service_ = new NeighborFacadeService(GetDependency<ConnectabilityModule>(), GetDependency<DiscoverabilityModule>(),
+ GetDependency<InquiryModule>(), GetDependency<NameModule>(),
+ GetDependency<PageModule>(), GetDependency<ScanModule>(), GetHandler());
}
void NeighborFacadeModule::Stop() {
diff --git a/gd/neighbor/facade/facade.proto b/gd/neighbor/facade/facade.proto
index a149547e7..315ae32a7 100644
--- a/gd/neighbor/facade/facade.proto
+++ b/gd/neighbor/facade/facade.proto
@@ -7,12 +7,9 @@ import "google/protobuf/empty.proto";
service NeighborFacade {
rpc SetConnectability(EnableMsg) returns (google.protobuf.Empty) {}
rpc SetDiscoverability(DiscoverabilitiyMsg) returns (google.protobuf.Empty) {}
- rpc SetInquiryMode(InquiryMsg) returns (stream InquiryResultMsg) {
- // Sets inquiry mode and fetches inquiry result HCI packet
- }
+ rpc SetInquiryMode(InquiryMsg) returns (stream InquiryResultMsg) {}
rpc ReadRemoteName(RemoteNameRequestMsg) returns (google.protobuf.Empty) {}
rpc GetRemoteNameEvents(google.protobuf.Empty) returns (stream RemoteNameResponseMsg) {}
- // TODO: Should we use a blocking call for ReadRemoteName instead? (Note: blocking model may not work for GD stack)
rpc EnableInquiryScan(EnableMsg) returns (google.protobuf.Empty) {}
rpc EnablePageScan(EnableMsg) returns (google.protobuf.Empty) {}
}
diff --git a/gd/neighbor/inquiry.cc b/gd/neighbor/inquiry.cc
index 332a047a4..ec734f36a 100644
--- a/gd/neighbor/inquiry.cc
+++ b/gd/neighbor/inquiry.cc
@@ -39,12 +39,8 @@ struct InquiryModule::impl {
void StartOneShotInquiry(bool limited, InquiryLength inquiry_length, NumResponses num_responses);
void StopOneShotInquiry();
- void StartPeriodicInquiry(
- bool limited,
- InquiryLength inquiry_length,
- NumResponses num_responses,
- PeriodLength max_delay,
- PeriodLength min_delay);
+ void StartPeriodicInquiry(bool limited, InquiryLength inquiry_length, NumResponses num_responses,
+ PeriodLength max_delay, PeriodLength min_delay);
void StopPeriodicInquiry();
void SetScanActivity(ScanParameters params);
@@ -77,15 +73,15 @@ struct InquiryModule::impl {
bool IsInquiryActive() const;
- void EnqueueCommandComplete(std::unique_ptr<hci::CommandBuilder> command);
- void EnqueueCommandStatus(std::unique_ptr<hci::CommandBuilder> command);
+ void EnqueueCommandComplete(std::unique_ptr<hci::CommandPacketBuilder> command);
+ void EnqueueCommandStatus(std::unique_ptr<hci::CommandPacketBuilder> command);
void OnCommandComplete(hci::CommandCompleteView view);
void OnCommandStatus(hci::CommandStatusView status);
- void EnqueueCommandCompleteSync(std::unique_ptr<hci::CommandBuilder> command);
+ void EnqueueCommandCompleteSync(std::unique_ptr<hci::CommandPacketBuilder> command);
void OnCommandCompleteSync(hci::CommandCompleteView view);
- void OnEvent(hci::EventView view);
+ void OnEvent(hci::EventPacketView view);
std::promise<void>* command_sync_{nullptr};
@@ -184,7 +180,7 @@ void neighbor::InquiryModule::impl::OnCommandStatus(hci::CommandStatusView statu
auto packet = hci::InquiryStatusView::Create(status);
ASSERT(packet.IsValid());
if (active_limited_one_shot_ || active_general_one_shot_) {
- LOG_INFO("Inquiry started lap: %s", active_limited_one_shot_ ? "Limited" : "General");
+ LOG_DEBUG("Inquiry started lap: %s", active_limited_one_shot_ ? "Limited" : "General");
}
} break;
@@ -194,12 +190,12 @@ void neighbor::InquiryModule::impl::OnCommandStatus(hci::CommandStatusView statu
}
}
-void neighbor::InquiryModule::impl::OnEvent(hci::EventView view) {
+void neighbor::InquiryModule::impl::OnEvent(hci::EventPacketView view) {
switch (view.GetEventCode()) {
case hci::EventCode::INQUIRY_COMPLETE: {
auto packet = hci::InquiryCompleteView::Create(view);
ASSERT(packet.IsValid());
- LOG_INFO("inquiry complete");
+ LOG_DEBUG("inquiry complete");
active_limited_one_shot_ = false;
active_general_one_shot_ = false;
inquiry_callbacks_.complete(packet.GetStatus());
@@ -208,27 +204,24 @@ void neighbor::InquiryModule::impl::OnEvent(hci::EventView view) {
case hci::EventCode::INQUIRY_RESULT: {
auto packet = hci::InquiryResultView::Create(view);
ASSERT(packet.IsValid());
- LOG_INFO("Inquiry result size:%zd num_responses:%zu", packet.size(), packet.GetInquiryResults().size());
+ LOG_DEBUG("Inquiry result size:%zd num_responses:%zu", packet.size(), packet.GetInquiryResults().size());
inquiry_callbacks_.result(packet);
} break;
case hci::EventCode::INQUIRY_RESULT_WITH_RSSI: {
auto packet = hci::InquiryResultWithRssiView::Create(view);
ASSERT(packet.IsValid());
- LOG_INFO("Inquiry result with rssi num_responses:%zu", packet.GetInquiryResults().size());
+ LOG_DEBUG("Inquiry result with rssi num_responses:%zu", packet.GetInquiryResults().size());
inquiry_callbacks_.result_with_rssi(packet);
} break;
case hci::EventCode::EXTENDED_INQUIRY_RESULT: {
auto packet = hci::ExtendedInquiryResultView::Create(view);
ASSERT(packet.IsValid());
- LOG_INFO(
- "Extended inquiry result addr:%s repetition_mode:%s cod:%s clock_offset:%d rssi:%hhd",
- packet.GetAddress().ToString().c_str(),
- hci::PageScanRepetitionModeText(packet.GetPageScanRepetitionMode()).c_str(),
- packet.GetClassOfDevice().ToString().c_str(),
- packet.GetClockOffset(),
- packet.GetRssi());
+ LOG_DEBUG("Extended inquiry result addr:%s repetition_mode:%s cod:%s clock_offset:%d rssi:%hhd",
+ packet.GetAddress().ToString().c_str(),
+ hci::PageScanRepetitionModeText(packet.GetPageScanRepetitionMode()).c_str(),
+ packet.GetClassOfDevice().ToString().c_str(), packet.GetClockOffset(), packet.GetRssi());
inquiry_callbacks_.extended_result(packet);
} break;
@@ -244,14 +237,14 @@ void neighbor::InquiryModule::impl::OnEvent(hci::EventView view) {
void neighbor::InquiryModule::impl::RegisterCallbacks(InquiryCallbacks callbacks) {
inquiry_callbacks_ = callbacks;
- hci_layer_->RegisterEventHandler(
- hci::EventCode::INQUIRY_RESULT, handler_->BindOn(this, &InquiryModule::impl::OnEvent));
- hci_layer_->RegisterEventHandler(
- hci::EventCode::INQUIRY_RESULT_WITH_RSSI, handler_->BindOn(this, &InquiryModule::impl::OnEvent));
- hci_layer_->RegisterEventHandler(
- hci::EventCode::EXTENDED_INQUIRY_RESULT, handler_->BindOn(this, &InquiryModule::impl::OnEvent));
- hci_layer_->RegisterEventHandler(
- hci::EventCode::INQUIRY_COMPLETE, handler_->BindOn(this, &InquiryModule::impl::OnEvent));
+ hci_layer_->RegisterEventHandler(hci::EventCode::INQUIRY_RESULT,
+ common::Bind(&InquiryModule::impl::OnEvent, common::Unretained(this)), handler_);
+ hci_layer_->RegisterEventHandler(hci::EventCode::INQUIRY_RESULT_WITH_RSSI,
+ common::Bind(&InquiryModule::impl::OnEvent, common::Unretained(this)), handler_);
+ hci_layer_->RegisterEventHandler(hci::EventCode::EXTENDED_INQUIRY_RESULT,
+ common::Bind(&InquiryModule::impl::OnEvent, common::Unretained(this)), handler_);
+ hci_layer_->RegisterEventHandler(hci::EventCode::INQUIRY_COMPLETE,
+ common::Bind(&InquiryModule::impl::OnEvent, common::Unretained(this)), handler_);
}
void neighbor::InquiryModule::impl::UnregisterCallbacks() {
@@ -263,26 +256,29 @@ void neighbor::InquiryModule::impl::UnregisterCallbacks() {
inquiry_callbacks_ = {nullptr, nullptr, nullptr, nullptr};
}
-void neighbor::InquiryModule::impl::EnqueueCommandComplete(std::unique_ptr<hci::CommandBuilder> command) {
- hci_layer_->EnqueueCommand(std::move(command), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+void neighbor::InquiryModule::impl::EnqueueCommandComplete(std::unique_ptr<hci::CommandPacketBuilder> command) {
+ hci_layer_->EnqueueCommand(std::move(command), common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)),
+ handler_);
}
-void neighbor::InquiryModule::impl::EnqueueCommandStatus(std::unique_ptr<hci::CommandBuilder> command) {
- hci_layer_->EnqueueCommand(std::move(command), handler_->BindOnceOn(this, &impl::OnCommandStatus));
+void neighbor::InquiryModule::impl::EnqueueCommandStatus(std::unique_ptr<hci::CommandPacketBuilder> command) {
+ hci_layer_->EnqueueCommand(std::move(command), common::BindOnce(&impl::OnCommandStatus, common::Unretained(this)),
+ handler_);
}
-void neighbor::InquiryModule::impl::EnqueueCommandCompleteSync(std::unique_ptr<hci::CommandBuilder> command) {
+void neighbor::InquiryModule::impl::EnqueueCommandCompleteSync(std::unique_ptr<hci::CommandPacketBuilder> command) {
ASSERT(command_sync_ == nullptr);
command_sync_ = new std::promise<void>();
auto command_received = command_sync_->get_future();
- hci_layer_->EnqueueCommand(std::move(command), handler_->BindOnceOn(this, &impl::OnCommandCompleteSync));
+ hci_layer_->EnqueueCommand(std::move(command),
+ common::BindOnce(&impl::OnCommandCompleteSync, common::Unretained(this)), handler_);
command_received.wait();
delete command_sync_;
command_sync_ = nullptr;
}
-void neighbor::InquiryModule::impl::StartOneShotInquiry(
- bool limited, InquiryLength inquiry_length, NumResponses num_responses) {
+void neighbor::InquiryModule::impl::StartOneShotInquiry(bool limited, InquiryLength inquiry_length,
+ NumResponses num_responses) {
ASSERT(HasCallbacks());
ASSERT(!IsInquiryActive());
hci::Lap lap;
@@ -303,12 +299,9 @@ void neighbor::InquiryModule::impl::StopOneShotInquiry() {
EnqueueCommandComplete(hci::InquiryCancelBuilder::Create());
}
-void neighbor::InquiryModule::impl::StartPeriodicInquiry(
- bool limited,
- InquiryLength inquiry_length,
- NumResponses num_responses,
- PeriodLength max_delay,
- PeriodLength min_delay) {
+void neighbor::InquiryModule::impl::StartPeriodicInquiry(bool limited, InquiryLength inquiry_length,
+ NumResponses num_responses, PeriodLength max_delay,
+ PeriodLength min_delay) {
ASSERT(HasCallbacks());
ASSERT(!IsInquiryActive());
hci::Lap lap;
@@ -343,39 +336,33 @@ void neighbor::InquiryModule::impl::Start() {
EnqueueCommandComplete(hci::ReadInquiryScanTypeBuilder::Create());
EnqueueCommandCompleteSync(hci::ReadInquiryModeBuilder::Create());
- LOG_INFO("Started inquiry module");
+ LOG_DEBUG("Started inquiry module");
}
void neighbor::InquiryModule::impl::Stop() {
LOG_INFO("Inquiry scan interval:%hu window:%hu", inquiry_scan_.interval, inquiry_scan_.window);
- LOG_INFO(
- "Inquiry mode:%s scan_type:%s",
- hci::InquiryModeText(inquiry_mode_).c_str(),
- hci::InquiryScanTypeText(inquiry_scan_type_).c_str());
+ LOG_INFO("Inquiry mode:%s scan_type:%s", hci::InquiryModeText(inquiry_mode_).c_str(),
+ hci::InquiryScanTypeText(inquiry_scan_type_).c_str());
LOG_INFO("Inquiry response tx power:%hhd", inquiry_response_tx_power_);
- LOG_INFO("Stopped inquiry module");
+ LOG_DEBUG("Stopped inquiry module");
}
void neighbor::InquiryModule::impl::SetInquiryMode(hci::InquiryMode mode) {
EnqueueCommandComplete(hci::WriteInquiryModeBuilder::Create(mode));
inquiry_mode_ = mode;
- LOG_INFO("Set inquiry mode:%s", hci::InquiryModeText(mode).c_str());
+ LOG_DEBUG("Set inquiry mode:%s", hci::InquiryModeText(mode).c_str());
}
void neighbor::InquiryModule::impl::SetScanActivity(ScanParameters params) {
EnqueueCommandComplete(hci::WriteInquiryScanActivityBuilder::Create(params.interval, params.window));
inquiry_scan_ = params;
- LOG_INFO(
- "Set scan activity interval:0x%x/%.02fms window:0x%x/%.02fms",
- params.interval,
- ScanIntervalTimeMs(params.interval),
- params.window,
- ScanWindowTimeMs(params.window));
+ LOG_DEBUG("Set scan activity interval:0x%x/%.02fms window:0x%x/%.02fms", params.interval,
+ ScanIntervalTimeMs(params.interval), params.window, ScanWindowTimeMs(params.window));
}
void neighbor::InquiryModule::impl::SetScanType(hci::InquiryScanType scan_type) {
EnqueueCommandComplete(hci::WriteInquiryScanTypeBuilder::Create(scan_type));
- LOG_INFO("Set scan type:%s", hci::InquiryScanTypeText(scan_type).c_str());
+ LOG_DEBUG("Set scan type:%s", hci::InquiryScanTypeText(scan_type).c_str());
}
bool neighbor::InquiryModule::impl::HasCallbacks() const {
@@ -401,21 +388,13 @@ void neighbor::InquiryModule::UnregisterCallbacks() {
}
void neighbor::InquiryModule::StartGeneralInquiry(InquiryLength inquiry_length, NumResponses num_responses) {
- GetHandler()->Post(common::BindOnce(
- &neighbor::InquiryModule::impl::StartOneShotInquiry,
- common::Unretained(pimpl_.get()),
- false,
- inquiry_length,
- num_responses));
+ GetHandler()->Post(common::BindOnce(&neighbor::InquiryModule::impl::StartOneShotInquiry,
+ common::Unretained(pimpl_.get()), false, inquiry_length, num_responses));
}
void neighbor::InquiryModule::StartLimitedInquiry(InquiryLength inquiry_length, NumResponses num_responses) {
- GetHandler()->Post(common::BindOnce(
- &neighbor::InquiryModule::impl::StartOneShotInquiry,
- common::Unretained(pimpl_.get()),
- true,
- inquiry_length,
- num_responses));
+ GetHandler()->Post(common::BindOnce(&neighbor::InquiryModule::impl::StartOneShotInquiry,
+ common::Unretained(pimpl_.get()), true, inquiry_length, num_responses));
}
void neighbor::InquiryModule::StopInquiry() {
@@ -423,28 +402,18 @@ void neighbor::InquiryModule::StopInquiry() {
common::BindOnce(&neighbor::InquiryModule::impl::StopOneShotInquiry, common::Unretained(pimpl_.get())));
}
-void neighbor::InquiryModule::StartGeneralPeriodicInquiry(
- InquiryLength inquiry_length, NumResponses num_responses, PeriodLength max_delay, PeriodLength min_delay) {
- GetHandler()->Post(common::BindOnce(
- &neighbor::InquiryModule::impl::StartPeriodicInquiry,
- common::Unretained(pimpl_.get()),
- false,
- inquiry_length,
- num_responses,
- max_delay,
- min_delay));
+void neighbor::InquiryModule::StartGeneralPeriodicInquiry(InquiryLength inquiry_length, NumResponses num_responses,
+ PeriodLength max_delay, PeriodLength min_delay) {
+ GetHandler()->Post(common::BindOnce(&neighbor::InquiryModule::impl::StartPeriodicInquiry,
+ common::Unretained(pimpl_.get()), false, inquiry_length, num_responses, max_delay,
+ min_delay));
}
-void neighbor::InquiryModule::StartLimitedPeriodicInquiry(
- InquiryLength inquiry_length, NumResponses num_responses, PeriodLength max_delay, PeriodLength min_delay) {
- GetHandler()->Post(common::BindOnce(
- &neighbor::InquiryModule::impl::StartPeriodicInquiry,
- common::Unretained(pimpl_.get()),
- true,
- inquiry_length,
- num_responses,
- max_delay,
- min_delay));
+void neighbor::InquiryModule::StartLimitedPeriodicInquiry(InquiryLength inquiry_length, NumResponses num_responses,
+ PeriodLength max_delay, PeriodLength min_delay) {
+ GetHandler()->Post(common::BindOnce(&neighbor::InquiryModule::impl::StartPeriodicInquiry,
+ common::Unretained(pimpl_.get()), true, inquiry_length, num_responses, max_delay,
+ min_delay));
}
void neighbor::InquiryModule::StopPeriodicInquiry() {
@@ -458,30 +427,28 @@ void neighbor::InquiryModule::SetScanActivity(ScanParameters params) {
}
void neighbor::InquiryModule::SetInterlacedScan() {
- GetHandler()->Post(common::BindOnce(
- &neighbor::InquiryModule::impl::SetScanType, common::Unretained(pimpl_.get()), hci::InquiryScanType::INTERLACED));
+ GetHandler()->Post(common::BindOnce(&neighbor::InquiryModule::impl::SetScanType, common::Unretained(pimpl_.get()),
+ hci::InquiryScanType::INTERLACED));
}
void neighbor::InquiryModule::SetStandardScan() {
- GetHandler()->Post(common::BindOnce(
- &neighbor::InquiryModule::impl::SetScanType, common::Unretained(pimpl_.get()), hci::InquiryScanType::STANDARD));
+ GetHandler()->Post(common::BindOnce(&neighbor::InquiryModule::impl::SetScanType, common::Unretained(pimpl_.get()),
+ hci::InquiryScanType::STANDARD));
}
void neighbor::InquiryModule::SetStandardInquiryResultMode() {
- GetHandler()->Post(common::BindOnce(
- &neighbor::InquiryModule::impl::SetInquiryMode, common::Unretained(pimpl_.get()), hci::InquiryMode::STANDARD));
+ GetHandler()->Post(common::BindOnce(&neighbor::InquiryModule::impl::SetInquiryMode, common::Unretained(pimpl_.get()),
+ hci::InquiryMode::STANDARD));
}
void neighbor::InquiryModule::SetInquiryWithRssiResultMode() {
- GetHandler()->Post(common::BindOnce(
- &neighbor::InquiryModule::impl::SetInquiryMode, common::Unretained(pimpl_.get()), hci::InquiryMode::RSSI));
+ GetHandler()->Post(common::BindOnce(&neighbor::InquiryModule::impl::SetInquiryMode, common::Unretained(pimpl_.get()),
+ hci::InquiryMode::RSSI));
}
void neighbor::InquiryModule::SetExtendedInquiryResultMode() {
- GetHandler()->Post(common::BindOnce(
- &neighbor::InquiryModule::impl::SetInquiryMode,
- common::Unretained(pimpl_.get()),
- hci::InquiryMode::RSSI_OR_EXTENDED));
+ GetHandler()->Post(common::BindOnce(&neighbor::InquiryModule::impl::SetInquiryMode, common::Unretained(pimpl_.get()),
+ hci::InquiryMode::RSSI_OR_EXTENDED));
}
/**
diff --git a/gd/neighbor/inquiry.h b/gd/neighbor/inquiry.h
index c67127899..33e3d6cf5 100644
--- a/gd/neighbor/inquiry.h
+++ b/gd/neighbor/inquiry.h
@@ -49,10 +49,10 @@ class InquiryModule : public bluetooth::Module {
void StartLimitedInquiry(InquiryLength inquiry_length, NumResponses num_responses);
void StopInquiry();
- void StartGeneralPeriodicInquiry(
- InquiryLength inquiry_length, NumResponses num_responses, PeriodLength max_delay, PeriodLength min_delay);
- void StartLimitedPeriodicInquiry(
- InquiryLength inquiry_length, NumResponses num_responses, PeriodLength max_delay, PeriodLength min_delay);
+ void StartGeneralPeriodicInquiry(InquiryLength inquiry_length, NumResponses num_responses, PeriodLength max_delay,
+ PeriodLength min_delay);
+ void StartLimitedPeriodicInquiry(InquiryLength inquiry_length, NumResponses num_responses, PeriodLength max_delay,
+ PeriodLength min_delay);
void StopPeriodicInquiry();
void SetScanActivity(ScanParameters parms);
@@ -73,9 +73,6 @@ class InquiryModule : public bluetooth::Module {
void ListDependencies(ModuleList* list) override;
void Start() override;
void Stop() override;
- std::string ToString() const override {
- return std::string("InquiryModule");
- }
private:
struct impl;
diff --git a/gd/neighbor/inquiry_mock.h b/gd/neighbor/inquiry_mock.h
deleted file mode 100644
index 1b3df6717..000000000
--- a/gd/neighbor/inquiry_mock.h
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <cstdint>
-#include <memory>
-
-#include "hci/hci_packets.h"
-#include "module.h"
-#include "neighbor/inquiry.h"
-#include "neighbor/scan_parameters.h"
-#include "os/handler.h"
-
-#include <gmock/gmock.h>
-
-// Unit test interfaces
-namespace bluetooth {
-namespace neighbor {
-namespace testing {
-
-class MockInquiryModule : public InquiryModule {
- public:
- MOCK_METHOD(void, RegisterCallbacks, (InquiryCallbacks inquiry_callbacks));
- MOCK_METHOD(void, UnregisterCallbacks, ());
- MOCK_METHOD(void, StartGeneralInquiry, (InquiryLength inquiry_length, NumResponses num_responses));
- MOCK_METHOD(void, StartLimitedInquiry, (InquiryLength inquiry_length, NumResponses num_responses));
- MOCK_METHOD(void, StopInquiry, ());
- MOCK_METHOD(
- void,
- StartGeneralPeriodicInquiry,
- (InquiryLength inquiry_length, NumResponses num_responses, PeriodLength max_delay, PeriodLength min_delay));
- MOCK_METHOD(
- void,
- StartLimitedPeriodicInquiry,
- (InquiryLength inquiry_length, NumResponses num_responses, PeriodLength max_delay, PeriodLength min_delay));
- MOCK_METHOD(void, StopPeriodicInquiry, ());
- MOCK_METHOD(void, SetScanActivity, (ScanParameters parms));
- MOCK_METHOD(void, SetInterlacedScan, ());
- MOCK_METHOD(void, SetStandardScan, ());
- MOCK_METHOD(void, SetStandardInquiryResultMode, ());
- MOCK_METHOD(void, SetInquiryWithRssiResultMode, ());
- MOCK_METHOD(void, SetExtendedInquiryResultMode, ());
-};
-
-} // namespace testing
-} // namespace neighbor
-} // namespace bluetooth
diff --git a/gd/neighbor/inquiry_test.cc b/gd/neighbor/inquiry_test.cc
index 80ac0127f..333b6df51 100644
--- a/gd/neighbor/inquiry_test.cc
+++ b/gd/neighbor/inquiry_test.cc
@@ -16,15 +16,16 @@
#include "neighbor/inquiry.h"
-#include <gtest/gtest.h>
-#include <unistd.h>
-
#include <algorithm>
#include <chrono>
#include <future>
#include <map>
#include <memory>
+#include <unistd.h>
+
+#include <gtest/gtest.h>
+
#include "common/bind.h"
#include "common/callback.h"
#include "hci/address.h"
@@ -84,25 +85,22 @@ hci::PacketView<hci::kLittleEndian> GetPacketView(std::unique_ptr<packet::BasePa
class TestHciLayer : public hci::HciLayer {
public:
- void EnqueueCommand(
- std::unique_ptr<hci::CommandBuilder> command,
- common::ContextualOnceCallback<void(hci::CommandCompleteView)> on_complete) override {
- GetHandler()->Post(common::BindOnce(
- &TestHciLayer::HandleCommand, common::Unretained(this), std::move(command), std::move(on_complete)));
+ void EnqueueCommand(std::unique_ptr<hci::CommandPacketBuilder> command,
+ common::OnceCallback<void(hci::CommandCompleteView)> on_complete, os::Handler* handler) override {
+ GetHandler()->Post(common::BindOnce(&TestHciLayer::HandleCommand, common::Unretained(this), std::move(command),
+ std::move(on_complete), common::Unretained(handler)));
}
- void EnqueueCommand(
- std::unique_ptr<hci::CommandBuilder> command,
- common::ContextualOnceCallback<void(hci::CommandStatusView)> on_status) override {
- GetHandler()->Post(common::BindOnce(
- &TestHciLayer::HandleStatus, common::Unretained(this), std::move(command), std::move(on_status)));
+ void EnqueueCommand(std::unique_ptr<hci::CommandPacketBuilder> command,
+ common::OnceCallback<void(hci::CommandStatusView)> on_status, os::Handler* handler) override {
+ GetHandler()->Post(common::BindOnce(&TestHciLayer::HandleStatus, common::Unretained(this), std::move(command),
+ std::move(on_status), common::Unretained(handler)));
}
- void HandleCommand(
- std::unique_ptr<hci::CommandBuilder> command_builder,
- common::ContextualOnceCallback<void(hci::CommandCompleteView)> on_complete) {
- hci::CommandView command = hci::CommandView::Create(GetPacketView(std::move(command_builder)));
- ASSERT_TRUE(command.IsValid());
+ void HandleCommand(std::unique_ptr<hci::CommandPacketBuilder> command_builder,
+ common::OnceCallback<void(hci::CommandCompleteView)> on_complete, os::Handler* handler) {
+ hci::CommandPacketView command = hci::CommandPacketView::Create(GetPacketView(std::move(command_builder)));
+ ASSERT(command.IsValid());
std::unique_ptr<packet::BasePacketBuilder> event_builder;
switch (command.GetOpCode()) {
@@ -114,7 +112,7 @@ class TestHciLayer : public hci::HciLayer {
case hci::OpCode::PERIODIC_INQUIRY_MODE: {
auto inquiry = hci::PeriodicInquiryModeView::Create(hci::DiscoveryCommandView::Create(command));
- ASSERT_TRUE(inquiry.IsValid());
+ ASSERT(inquiry.IsValid());
event_builder =
hci::PeriodicInquiryModeCompleteBuilder::Create(kNumberPacketsReadyToReceive, hci::ErrorCode::SUCCESS);
hci_register_.periodic_inquiry_active = true;
@@ -135,7 +133,7 @@ class TestHciLayer : public hci::HciLayer {
hci::WriteInquiryModeCompleteBuilder::Create(kNumberPacketsReadyToReceive, hci::ErrorCode::SUCCESS);
{
auto view = hci::WriteInquiryModeView::Create(hci::DiscoveryCommandView::Create(command));
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
hci_register_.inquiry_mode = view.GetInquiryMode();
}
break;
@@ -150,7 +148,7 @@ class TestHciLayer : public hci::HciLayer {
hci::WriteInquiryScanActivityCompleteBuilder::Create(kNumberPacketsReadyToReceive, hci::ErrorCode::SUCCESS);
{
auto view = hci::WriteInquiryScanActivityView::Create(hci::DiscoveryCommandView::Create(command));
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
hci_register_.inquiry_scan_interval = view.GetInquiryScanInterval();
hci_register_.inquiry_scan_window = view.GetInquiryScanWindow();
}
@@ -158,9 +156,7 @@ class TestHciLayer : public hci::HciLayer {
case hci::OpCode::READ_INQUIRY_SCAN_ACTIVITY:
event_builder = hci::ReadInquiryScanActivityCompleteBuilder::Create(
- kNumberPacketsReadyToReceive,
- hci::ErrorCode::SUCCESS,
- hci_register_.inquiry_scan_interval,
+ kNumberPacketsReadyToReceive, hci::ErrorCode::SUCCESS, hci_register_.inquiry_scan_interval,
hci_register_.inquiry_scan_window);
break;
@@ -169,7 +165,7 @@ class TestHciLayer : public hci::HciLayer {
hci::WriteInquiryScanTypeCompleteBuilder::Create(kNumberPacketsReadyToReceive, hci::ErrorCode::SUCCESS);
{
auto view = hci::WriteInquiryScanTypeView::Create(hci::DiscoveryCommandView::Create(command));
- ASSERT_TRUE(view.IsValid());
+ ASSERT(view.IsValid());
hci_register_.inquiry_scan_type = view.GetInquiryScanType();
}
break;
@@ -188,28 +184,27 @@ class TestHciLayer : public hci::HciLayer {
LOG_INFO("Dropping unhandled command:%s", hci::OpCodeText(command.GetOpCode()).c_str());
return;
}
- hci::EventView event = hci::EventView::Create(GetPacketView(std::move(event_builder)));
- ASSERT_TRUE(event.IsValid());
+ hci::EventPacketView event = hci::EventPacketView::Create(GetPacketView(std::move(event_builder)));
+ ASSERT(event.IsValid());
hci::CommandCompleteView command_complete = hci::CommandCompleteView::Create(event);
- ASSERT_TRUE(command_complete.IsValid());
- on_complete.Invoke(std::move(command_complete));
+ ASSERT(command_complete.IsValid());
+ handler->Post(common::BindOnce(std::move(on_complete), std::move(command_complete)));
if (promise_sync_complete_ != nullptr) {
promise_sync_complete_->set_value(command.GetOpCode());
}
}
- void HandleStatus(
- std::unique_ptr<hci::CommandBuilder> command_builder,
- common::ContextualOnceCallback<void(hci::CommandStatusView)> on_status) {
- hci::CommandView command = hci::CommandView::Create(GetPacketView(std::move(command_builder)));
- ASSERT_TRUE(command.IsValid());
+ void HandleStatus(std::unique_ptr<hci::CommandPacketBuilder> command_builder,
+ common::OnceCallback<void(hci::CommandStatusView)> on_status, os::Handler* handler) {
+ hci::CommandPacketView command = hci::CommandPacketView::Create(GetPacketView(std::move(command_builder)));
+ ASSERT(command.IsValid());
std::unique_ptr<packet::BasePacketBuilder> event_builder;
switch (command.GetOpCode()) {
case hci::OpCode::INQUIRY: {
auto inquiry = hci::InquiryView::Create(hci::DiscoveryCommandView::Create(command));
- ASSERT_TRUE(inquiry.IsValid());
+ ASSERT(inquiry.IsValid());
event_builder = hci::InquiryStatusBuilder::Create(hci::ErrorCode::SUCCESS, kNumberPacketsReadyToReceive);
hci_register_.one_shot_inquiry_active = true;
hci_register_.num_responses = inquiry.GetNumResponses();
@@ -219,30 +214,34 @@ class TestHciLayer : public hci::HciLayer {
LOG_INFO("Dropping unhandled status expecting command:%s", hci::OpCodeText(command.GetOpCode()).c_str());
return;
}
- hci::EventView event = hci::EventView::Create(GetPacketView(std::move(event_builder)));
- ASSERT_TRUE(event.IsValid());
+ hci::EventPacketView event = hci::EventPacketView::Create(GetPacketView(std::move(event_builder)));
+ ASSERT(event.IsValid());
hci::CommandStatusView command_status = hci::CommandStatusView::Create(event);
- ASSERT_TRUE(command_status.IsValid());
- on_status.Invoke(std::move(command_status));
+ ASSERT(command_status.IsValid());
+ handler->Post(common::BindOnce(std::move(on_status), std::move(command_status)));
if (promise_sync_complete_ != nullptr) {
promise_sync_complete_->set_value(command.GetOpCode());
}
}
- void RegisterEventHandler(
- hci::EventCode event_code, common::ContextualCallback<void(hci::EventView)> event_handler) override {
+ void RegisterEventHandler(hci::EventCode event_code, common::Callback<void(hci::EventPacketView)> event_handler,
+ os::Handler* handler) override {
switch (event_code) {
case hci::EventCode::INQUIRY_RESULT:
+ inquiry_result_handler_ = handler;
inquiry_result_callback_ = event_handler;
break;
case hci::EventCode::INQUIRY_RESULT_WITH_RSSI:
+ inquiry_result_with_rssi_handler_ = handler;
inquiry_result_with_rssi_callback_ = event_handler;
break;
case hci::EventCode::EXTENDED_INQUIRY_RESULT:
+ extended_inquiry_result_handler_ = handler;
extended_inquiry_result_callback_ = event_handler;
break;
case hci::EventCode::INQUIRY_COMPLETE:
+ inquiry_complete_handler_ = handler;
inquiry_complete_callback_ = event_handler;
break;
default:
@@ -259,15 +258,19 @@ class TestHciLayer : public hci::HciLayer {
switch (event_code) {
case hci::EventCode::INQUIRY_RESULT:
+ inquiry_result_handler_ = nullptr;
inquiry_result_callback_ = {};
break;
case hci::EventCode::INQUIRY_RESULT_WITH_RSSI:
+ inquiry_result_with_rssi_handler_ = nullptr;
inquiry_result_with_rssi_callback_ = {};
break;
case hci::EventCode::EXTENDED_INQUIRY_RESULT:
+ extended_inquiry_result_handler_ = nullptr;
extended_inquiry_result_callback_ = {};
break;
case hci::EventCode::INQUIRY_COMPLETE:
+ inquiry_complete_handler_ = nullptr;
inquiry_complete_callback_ = {};
break;
default:
@@ -277,7 +280,7 @@ class TestHciLayer : public hci::HciLayer {
}
void Synchronize(std::function<void()> func, hci::OpCode op_code) {
- ASSERT_EQ(promise_sync_complete_, nullptr);
+ ASSERT(promise_sync_complete_ == nullptr);
promise_sync_complete_ = new std::promise<hci::OpCode>();
auto future = promise_sync_complete_->get_future();
func();
@@ -289,9 +292,11 @@ class TestHciLayer : public hci::HciLayer {
}
void InjectInquiryResult(std::unique_ptr<hci::InquiryResultBuilder> result) {
- hci::EventView view = hci::EventView::Create(GetPacketView(std::move(result)));
- ASSERT_TRUE(view.IsValid());
- inquiry_result_callback_.Invoke(std::move(view));
+ if (inquiry_result_handler_ != nullptr) {
+ hci::EventPacketView view = hci::EventPacketView::Create(GetPacketView(std::move(result)));
+ ASSERT(view.IsValid());
+ inquiry_result_handler_->Post(common::BindOnce(inquiry_result_callback_, std::move(view)));
+ }
}
void ListDependencies(ModuleList* list) override {}
@@ -301,21 +306,25 @@ class TestHciLayer : public hci::HciLayer {
private:
std::promise<hci::OpCode>* promise_sync_complete_{nullptr};
- common::ContextualCallback<void(hci::EventView)> inquiry_result_callback_;
- common::ContextualCallback<void(hci::EventView)> inquiry_result_with_rssi_callback_;
- common::ContextualCallback<void(hci::EventView)> extended_inquiry_result_callback_;
- common::ContextualCallback<void(hci::EventView)> inquiry_complete_callback_;
+ os::Handler* inquiry_result_handler_{nullptr};
+ common::Callback<void(hci::EventPacketView)> inquiry_result_callback_;
+ os::Handler* inquiry_result_with_rssi_handler_{nullptr};
+ common::Callback<void(hci::EventPacketView)> inquiry_result_with_rssi_callback_;
+ os::Handler* extended_inquiry_result_handler_{nullptr};
+ common::Callback<void(hci::EventPacketView)> extended_inquiry_result_callback_;
+ os::Handler* inquiry_complete_handler_{nullptr};
+ common::Callback<void(hci::EventPacketView)> inquiry_complete_callback_;
};
class InquiryTest : public ::testing::Test {
public:
void Result(hci::InquiryResultView view) {
- ASSERT_TRUE(view.size() >= sizeof(uint16_t));
+ ASSERT(view.size() >= sizeof(uint16_t));
promise_result_complete_->set_value(true);
}
void WaitForInquiryResult(std::function<void()> func) {
- ASSERT_EQ(promise_result_complete_, nullptr);
+ ASSERT(promise_result_complete_ == nullptr);
promise_result_complete_ = new std::promise<bool>();
auto future = promise_result_complete_->get_future();
func();
@@ -325,11 +334,11 @@ class InquiryTest : public ::testing::Test {
}
void ResultWithRssi(hci::InquiryResultWithRssiView view) {
- ASSERT_TRUE(view.size() >= sizeof(uint16_t));
+ ASSERT(view.size() >= sizeof(uint16_t));
}
void ExtendedResult(hci::ExtendedInquiryResultView view) {
- ASSERT_TRUE(view.size() >= sizeof(uint16_t));
+ ASSERT(view.size() >= sizeof(uint16_t));
}
void Complete(hci::ErrorCode status) {}
@@ -368,16 +377,16 @@ class InquiryTest : public ::testing::Test {
TEST_F(InquiryTest, Module) {}
TEST_F(InquiryTest, SetInquiryModes) {
- test_hci_layer_->Synchronize(
- [this] { inquiry_module_->SetInquiryWithRssiResultMode(); }, hci::OpCode::WRITE_INQUIRY_MODE);
+ test_hci_layer_->Synchronize([this] { inquiry_module_->SetInquiryWithRssiResultMode(); },
+ hci::OpCode::WRITE_INQUIRY_MODE);
ASSERT_EQ(hci_register_.inquiry_mode, hci::InquiryMode::RSSI);
- test_hci_layer_->Synchronize(
- [this] { inquiry_module_->SetExtendedInquiryResultMode(); }, hci::OpCode::WRITE_INQUIRY_MODE);
+ test_hci_layer_->Synchronize([this] { inquiry_module_->SetExtendedInquiryResultMode(); },
+ hci::OpCode::WRITE_INQUIRY_MODE);
ASSERT_EQ(hci_register_.inquiry_mode, hci::InquiryMode::RSSI_OR_EXTENDED);
- test_hci_layer_->Synchronize(
- [this] { inquiry_module_->SetStandardInquiryResultMode(); }, hci::OpCode::WRITE_INQUIRY_MODE);
+ test_hci_layer_->Synchronize([this] { inquiry_module_->SetStandardInquiryResultMode(); },
+ hci::OpCode::WRITE_INQUIRY_MODE);
ASSERT_EQ(hci_register_.inquiry_mode, hci::InquiryMode::STANDARD);
}
@@ -395,8 +404,8 @@ TEST_F(InquiryTest, ScanActivity) {
.window = 0x5678,
};
- test_hci_layer_->Synchronize(
- [this, params] { inquiry_module_->SetScanActivity(params); }, hci::OpCode::WRITE_INQUIRY_SCAN_ACTIVITY);
+ test_hci_layer_->Synchronize([this, params] { inquiry_module_->SetScanActivity(params); },
+ hci::OpCode::WRITE_INQUIRY_SCAN_ACTIVITY);
ASSERT_EQ(params.interval, hci_register_.inquiry_scan_interval);
ASSERT_EQ(params.window, hci_register_.inquiry_scan_window);
}
@@ -434,17 +443,16 @@ TEST_F(InquiryTest, GeneralPeriodicInquiry) {
ASSERT_EQ(max_delay, hci_register_.max_period_length);
ASSERT_EQ(min_delay, hci_register_.min_period_length);
- test_hci_layer_->Synchronize(
- [this] { inquiry_module_->StopPeriodicInquiry(); }, hci::OpCode::EXIT_PERIODIC_INQUIRY_MODE);
+ test_hci_layer_->Synchronize([this] { inquiry_module_->StopPeriodicInquiry(); },
+ hci::OpCode::EXIT_PERIODIC_INQUIRY_MODE);
}
TEST_F(InquiryTest, LimitedPeriodicInquiry) {
- test_hci_layer_->Synchronize(
- [this] { inquiry_module_->StartLimitedPeriodicInquiry(128, 100, 1100, 200); },
- hci::OpCode::PERIODIC_INQUIRY_MODE);
+ test_hci_layer_->Synchronize([this] { inquiry_module_->StartLimitedPeriodicInquiry(128, 100, 1100, 200); },
+ hci::OpCode::PERIODIC_INQUIRY_MODE);
- test_hci_layer_->Synchronize(
- [this] { inquiry_module_->StopPeriodicInquiry(); }, hci::OpCode::EXIT_PERIODIC_INQUIRY_MODE);
+ test_hci_layer_->Synchronize([this] { inquiry_module_->StopPeriodicInquiry(); },
+ hci::OpCode::EXIT_PERIODIC_INQUIRY_MODE);
}
TEST_F(InquiryTest, InjectInquiryResult) {
diff --git a/gd/neighbor/name.cc b/gd/neighbor/name.cc
index 3a7cb640f..f3734867c 100644
--- a/gd/neighbor/name.cc
+++ b/gd/neighbor/name.cc
@@ -44,13 +44,9 @@ struct CancelCallbackHandler {
constexpr RemoteName kEmptyName{};
struct NameModule::impl {
- void ReadRemoteNameRequest(
- hci::Address address,
- hci::PageScanRepetitionMode page_scan_repetition_mode,
- uint16_t clock_offset,
- hci::ClockOffsetValid clock_offset_valid,
- ReadRemoteNameCallback callback,
- os::Handler* handler);
+ void ReadRemoteNameRequest(hci::Address address, hci::PageScanRepetitionMode page_scan_repetition_mode,
+ uint16_t clock_offset, hci::ClockOffsetValid clock_offset_valid,
+ ReadRemoteNameCallback callback, os::Handler* handler);
void CancelRemoteNameRequest(hci::Address address, CancelRemoteNameCallback, os::Handler* handler);
void Start();
@@ -61,12 +57,12 @@ struct NameModule::impl {
private:
const NameModule& module_;
- void EnqueueCommandComplete(std::unique_ptr<hci::CommandBuilder> command);
- void EnqueueCommandStatus(std::unique_ptr<hci::CommandBuilder> command);
+ void EnqueueCommandComplete(std::unique_ptr<hci::CommandPacketBuilder> command);
+ void EnqueueCommandStatus(std::unique_ptr<hci::CommandPacketBuilder> command);
void OnCommandComplete(hci::CommandCompleteView view);
void OnCommandStatus(hci::CommandStatusView status);
- void OnEvent(hci::EventView view);
+ void OnEvent(hci::EventPacketView view);
std::unordered_map<hci::Address, std::unique_ptr<ReadCallbackHandler>> read_callback_handler_map_;
std::unordered_map<hci::Address, std::unique_ptr<CancelCallbackHandler>> cancel_callback_handler_map_;
@@ -79,12 +75,14 @@ const ModuleFactory neighbor::NameModule::Factory = ModuleFactory([]() { return
neighbor::NameModule::impl::impl(const neighbor::NameModule& module) : module_(module) {}
-void neighbor::NameModule::impl::EnqueueCommandComplete(std::unique_ptr<hci::CommandBuilder> command) {
- hci_layer_->EnqueueCommand(std::move(command), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+void neighbor::NameModule::impl::EnqueueCommandComplete(std::unique_ptr<hci::CommandPacketBuilder> command) {
+ hci_layer_->EnqueueCommand(std::move(command), common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)),
+ handler_);
}
-void neighbor::NameModule::impl::EnqueueCommandStatus(std::unique_ptr<hci::CommandBuilder> command) {
- hci_layer_->EnqueueCommand(std::move(command), handler_->BindOnceOn(this, &impl::OnCommandStatus));
+void neighbor::NameModule::impl::EnqueueCommandStatus(std::unique_ptr<hci::CommandPacketBuilder> command) {
+ hci_layer_->EnqueueCommand(std::move(command), common::BindOnce(&impl::OnCommandStatus, common::Unretained(this)),
+ handler_);
}
void neighbor::NameModule::impl::OnCommandComplete(hci::CommandCompleteView view) {
@@ -118,7 +116,7 @@ void neighbor::NameModule::impl::OnCommandStatus(hci::CommandStatusView status)
}
}
-void neighbor::NameModule::impl::OnEvent(hci::EventView view) {
+void neighbor::NameModule::impl::OnEvent(hci::EventPacketView view) {
switch (view.GetEventCode()) {
case hci::EventCode::REMOTE_NAME_REQUEST_COMPLETE: {
auto packet = hci::RemoteNameRequestCompleteView::Create(view);
@@ -126,8 +124,8 @@ void neighbor::NameModule::impl::OnEvent(hci::EventView view) {
hci::Address address = packet.GetBdAddr();
ASSERT(read_callback_handler_map_.find(address) != read_callback_handler_map_.end());
auto read_callback_handler = std::move(read_callback_handler_map_[address]);
- read_callback_handler->handler->Post(common::BindOnce(
- std::move(read_callback_handler->callback), packet.GetStatus(), address, packet.GetRemoteName()));
+ read_callback_handler->handler->Post(common::BindOnce(std::move(read_callback_handler->callback),
+ packet.GetStatus(), address, packet.GetRemoteName()));
read_callback_handler_map_.erase(address);
} break;
default:
@@ -140,22 +138,19 @@ void neighbor::NameModule::impl::Start() {
hci_layer_ = module_.GetDependency<hci::HciLayer>();
handler_ = module_.GetHandler();
- hci_layer_->RegisterEventHandler(
- hci::EventCode::REMOTE_NAME_REQUEST_COMPLETE, handler_->BindOn(this, &NameModule::impl::OnEvent));
+ hci_layer_->RegisterEventHandler(hci::EventCode::REMOTE_NAME_REQUEST_COMPLETE,
+ common::Bind(&NameModule::impl::OnEvent, common::Unretained(this)), handler_);
}
void neighbor::NameModule::impl::Stop() {
hci_layer_->UnregisterEventHandler(hci::EventCode::REMOTE_NAME_REQUEST_COMPLETE);
}
-void neighbor::NameModule::impl::ReadRemoteNameRequest(
- hci::Address address,
- hci::PageScanRepetitionMode page_scan_repetition_mode,
- uint16_t clock_offset,
- hci::ClockOffsetValid clock_offset_valid,
- ReadRemoteNameCallback callback,
- os::Handler* handler) {
- LOG_INFO("%s Start read remote name request for %s", __func__, address.ToString().c_str());
+void neighbor::NameModule::impl::ReadRemoteNameRequest(hci::Address address,
+ hci::PageScanRepetitionMode page_scan_repetition_mode,
+ uint16_t clock_offset, hci::ClockOffsetValid clock_offset_valid,
+ ReadRemoteNameCallback callback, os::Handler* handler) {
+ LOG_DEBUG("%s Start read remote name request for %s", __func__, address.ToString().c_str());
if (read_callback_handler_map_.find(address) != read_callback_handler_map_.end()) {
LOG_WARN("Ignoring duplicate read remote name request to:%s", address.ToString().c_str());
@@ -171,9 +166,9 @@ void neighbor::NameModule::impl::ReadRemoteNameRequest(
hci::RemoteNameRequestBuilder::Create(address, page_scan_repetition_mode, clock_offset, clock_offset_valid));
}
-void neighbor::NameModule::impl::CancelRemoteNameRequest(
- hci::Address address, CancelRemoteNameCallback callback, os::Handler* handler) {
- LOG_INFO("%s Cancel remote name request for %s", __func__, address.ToString().c_str());
+void neighbor::NameModule::impl::CancelRemoteNameRequest(hci::Address address, CancelRemoteNameCallback callback,
+ os::Handler* handler) {
+ LOG_DEBUG("%s Cancel remote name request for %s", __func__, address.ToString().c_str());
if (cancel_callback_handler_map_.find(address) != cancel_callback_handler_map_.end()) {
LOG_WARN("Ignoring duplicate cancel remote name request to:%s", address.ToString().c_str());
@@ -196,36 +191,23 @@ neighbor::NameModule::~NameModule() {
pimpl_.reset();
}
-void neighbor::NameModule::ReadRemoteNameRequest(
- hci::Address address,
- hci::PageScanRepetitionMode page_scan_repetition_mode,
- uint16_t clock_offset,
- hci::ClockOffsetValid clock_offset_valid,
- ReadRemoteNameCallback callback,
- os::Handler* handler) {
+void neighbor::NameModule::ReadRemoteNameRequest(hci::Address address,
+ hci::PageScanRepetitionMode page_scan_repetition_mode,
+ uint16_t clock_offset, hci::ClockOffsetValid clock_offset_valid,
+ ReadRemoteNameCallback callback, os::Handler* handler) {
ASSERT(callback);
ASSERT(handler != nullptr);
- GetHandler()->Post(common::BindOnce(
- &NameModule::impl::ReadRemoteNameRequest,
- common::Unretained(pimpl_.get()),
- address,
- page_scan_repetition_mode,
- clock_offset,
- clock_offset_valid,
- std::move(callback),
- handler));
+ GetHandler()->Post(common::BindOnce(&NameModule::impl::ReadRemoteNameRequest, common::Unretained(pimpl_.get()),
+ address, page_scan_repetition_mode, clock_offset, clock_offset_valid,
+ std::move(callback), handler));
}
-void neighbor::NameModule::CancelRemoteNameRequest(
- hci::Address address, CancelRemoteNameCallback callback, os::Handler* handler) {
+void neighbor::NameModule::CancelRemoteNameRequest(hci::Address address, CancelRemoteNameCallback callback,
+ os::Handler* handler) {
ASSERT(callback);
ASSERT(handler != nullptr);
- GetHandler()->Post(common::BindOnce(
- &NameModule::impl::CancelRemoteNameRequest,
- common::Unretained(pimpl_.get()),
- address,
- std::move(callback),
- handler));
+ GetHandler()->Post(common::BindOnce(&NameModule::impl::CancelRemoteNameRequest, common::Unretained(pimpl_.get()),
+ address, std::move(callback), handler));
}
/**
diff --git a/gd/neighbor/name.h b/gd/neighbor/name.h
index 3136e9ccf..c671ddc3e 100644
--- a/gd/neighbor/name.h
+++ b/gd/neighbor/name.h
@@ -33,13 +33,9 @@ using CancelRemoteNameCallback = common::OnceCallback<void(hci::ErrorCode status
class NameModule : public bluetooth::Module {
public:
- void ReadRemoteNameRequest(
- hci::Address address,
- hci::PageScanRepetitionMode page_scan_repetition_mode,
- uint16_t clock_offset,
- hci::ClockOffsetValid clock_offset_valid,
- ReadRemoteNameCallback on_read_name,
- os::Handler* handler);
+ void ReadRemoteNameRequest(hci::Address address, hci::PageScanRepetitionMode page_scan_repetition_mode,
+ uint16_t clock_offset, hci::ClockOffsetValid clock_offset_valid,
+ ReadRemoteNameCallback on_read_name, os::Handler* handler);
void CancelRemoteNameRequest(hci::Address address, CancelRemoteNameCallback on_cancel, os::Handler* handler);
static const ModuleFactory Factory;
@@ -51,9 +47,6 @@ class NameModule : public bluetooth::Module {
void ListDependencies(ModuleList* list) override;
void Start() override;
void Stop() override;
- std::string ToString() const override {
- return std::string("NameModule");
- }
private:
struct impl;
diff --git a/gd/neighbor/name_db.cc b/gd/neighbor/name_db.cc
index 42394759f..e82cc5e7e 100644
--- a/gd/neighbor/name_db.cc
+++ b/gd/neighbor/name_db.cc
@@ -49,7 +49,7 @@ struct NameDbModule::impl {
void Stop();
private:
- std::unordered_map<hci::Address, std::list<PendingRemoteNameRead>> address_to_pending_read_map_;
+ std::unordered_map<hci::Address, PendingRemoteNameRead> address_to_pending_read_map_;
std::unordered_map<hci::Address, RemoteName> address_to_name_map_;
void OnRemoteNameResponse(hci::ErrorCode status, hci::Address address, RemoteName name);
@@ -64,41 +64,33 @@ const ModuleFactory neighbor::NameDbModule::Factory = ModuleFactory([]() { retur
neighbor::NameDbModule::impl::impl(const neighbor::NameDbModule& module) : module_(module) {}
-void neighbor::NameDbModule::impl::ReadRemoteNameRequest(
- hci::Address address, ReadRemoteNameDbCallback callback, os::Handler* handler) {
+void neighbor::NameDbModule::impl::ReadRemoteNameRequest(hci::Address address, ReadRemoteNameDbCallback callback,
+ os::Handler* handler) {
if (address_to_pending_read_map_.find(address) != address_to_pending_read_map_.end()) {
- LOG_WARN("Already have remote read db in progress; adding callback to callback list");
- address_to_pending_read_map_[address].push_back({std::move(callback), handler});
+ LOG_WARN("Already have remote read db in progress and currently can only have one outstanding");
return;
}
- std::list<PendingRemoteNameRead> tmp;
- address_to_pending_read_map_[address] = std::move(tmp);
- address_to_pending_read_map_[address].push_back({std::move(callback), handler});
+ address_to_pending_read_map_[address] = {std::move(callback), std::move(handler)};
// TODO(cmanton) Use remote name request defaults for now
hci::PageScanRepetitionMode page_scan_repetition_mode = hci::PageScanRepetitionMode::R1;
uint16_t clock_offset = 0;
hci::ClockOffsetValid clock_offset_valid = hci::ClockOffsetValid::INVALID;
name_module_->ReadRemoteNameRequest(
- address,
- page_scan_repetition_mode,
- clock_offset,
- clock_offset_valid,
- common::BindOnce(&NameDbModule::impl::OnRemoteNameResponse, common::Unretained(this)),
- handler_);
+ address, page_scan_repetition_mode, clock_offset, clock_offset_valid,
+ common::BindOnce(&NameDbModule::impl::OnRemoteNameResponse, common::Unretained(this)), handler_);
}
void neighbor::NameDbModule::impl::OnRemoteNameResponse(hci::ErrorCode status, hci::Address address, RemoteName name) {
ASSERT(address_to_pending_read_map_.find(address) != address_to_pending_read_map_.end());
+ PendingRemoteNameRead callback_handler = std::move(address_to_pending_read_map_.at(address));
+
if (status == hci::ErrorCode::SUCCESS) {
address_to_name_map_[address] = name;
}
- auto& callback_list = address_to_pending_read_map_.at(address);
- for (auto& it : callback_list) {
- it.handler_->Call(std::move(it.callback_), address, status == hci::ErrorCode::SUCCESS);
- }
- address_to_pending_read_map_.erase(address);
+ callback_handler.handler_->Post(
+ common::BindOnce(std::move(callback_handler.callback_), address, status == hci::ErrorCode::SUCCESS));
}
bool neighbor::NameDbModule::impl::IsNameCached(hci::Address address) const {
@@ -119,14 +111,10 @@ neighbor::NameDbModule::~NameDbModule() {
pimpl_.reset();
}
-void neighbor::NameDbModule::ReadRemoteNameRequest(
- hci::Address address, ReadRemoteNameDbCallback callback, os::Handler* handler) {
- GetHandler()->Post(common::BindOnce(
- &NameDbModule::impl::ReadRemoteNameRequest,
- common::Unretained(pimpl_.get()),
- address,
- std::move(callback),
- handler));
+void neighbor::NameDbModule::ReadRemoteNameRequest(hci::Address address, ReadRemoteNameDbCallback callback,
+ os::Handler* handler) {
+ GetHandler()->Post(common::BindOnce(&NameDbModule::impl::ReadRemoteNameRequest, common::Unretained(pimpl_.get()),
+ address, std::move(callback), handler));
}
bool neighbor::NameDbModule::IsNameCached(hci::Address address) const {
diff --git a/gd/neighbor/name_db.h b/gd/neighbor/name_db.h
index 03e87fa54..010c4941a 100644
--- a/gd/neighbor/name_db.h
+++ b/gd/neighbor/name_db.h
@@ -32,7 +32,7 @@ using ReadRemoteNameDbCallback = common::OnceCallback<void(hci::Address address,
class NameDbModule : public bluetooth::Module {
public:
- virtual void ReadRemoteNameRequest(hci::Address address, ReadRemoteNameDbCallback callback, os::Handler* handler);
+ void ReadRemoteNameRequest(hci::Address address, ReadRemoteNameDbCallback callback, os::Handler* handler);
bool IsNameCached(hci::Address address) const;
RemoteName ReadCachedRemoteName(hci::Address address) const;
@@ -46,9 +46,6 @@ class NameDbModule : public bluetooth::Module {
void ListDependencies(ModuleList* list) override;
void Start() override;
void Stop() override;
- std::string ToString() const override {
- return std::string("NameDb");
- }
private:
struct impl;
diff --git a/gd/neighbor/page.cc b/gd/neighbor/page.cc
index 2f1d1e245..4631875b4 100644
--- a/gd/neighbor/page.cc
+++ b/gd/neighbor/page.cc
@@ -15,14 +15,13 @@
*/
#define LOG_TAG "bt_gd_neigh"
-#include "neighbor/page.h"
-
#include <memory>
#include "common/bind.h"
#include "hci/hci_layer.h"
#include "hci/hci_packets.h"
#include "module.h"
+#include "neighbor/page.h"
#include "neighbor/scan_parameters.h"
#include "os/handler.h"
#include "os/log.h"
@@ -112,34 +111,29 @@ void neighbor::PageModule::impl::Start() {
hci_layer_ = module_.GetDependency<hci::HciLayer>();
handler_ = module_.GetHandler();
- hci_layer_->EnqueueCommand(
- hci::ReadPageScanActivityBuilder::Create(), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+ hci_layer_->EnqueueCommand(hci::ReadPageScanActivityBuilder::Create(),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
- hci_layer_->EnqueueCommand(
- hci::ReadPageScanTypeBuilder::Create(), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+ hci_layer_->EnqueueCommand(hci::ReadPageScanTypeBuilder::Create(),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
- hci_layer_->EnqueueCommand(
- hci::ReadPageTimeoutBuilder::Create(), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+ hci_layer_->EnqueueCommand(hci::ReadPageTimeoutBuilder::Create(),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
}
void neighbor::PageModule::impl::Stop() {
- LOG_INFO("Page scan interval:%hd window:%hd", scan_parameters_.interval, scan_parameters_.window);
- LOG_INFO("Page scan_type:%s", hci::PageScanTypeText(scan_type_).c_str());
+ LOG_DEBUG("Page scan interval:%hd window:%hd", scan_parameters_.interval, scan_parameters_.window);
+ LOG_DEBUG("Page scan_type:%s", hci::PageScanTypeText(scan_type_).c_str());
}
void neighbor::PageModule::impl::SetScanActivity(ScanParameters params) {
- hci_layer_->EnqueueCommand(
- hci::WritePageScanActivityBuilder::Create(params.interval, params.window),
- handler_->BindOnceOn(this, &impl::OnCommandComplete));
+ hci_layer_->EnqueueCommand(hci::WritePageScanActivityBuilder::Create(params.interval, params.window),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
- hci_layer_->EnqueueCommand(
- hci::ReadPageScanActivityBuilder::Create(), handler_->BindOnceOn(this, &impl::OnCommandComplete));
- LOG_INFO(
- "Set page scan activity interval:0x%x/%.02fms window:0x%x/%.02fms",
- params.interval,
- ScanIntervalTimeMs(params.interval),
- params.window,
- ScanWindowTimeMs(params.window));
+ hci_layer_->EnqueueCommand(hci::ReadPageScanActivityBuilder::Create(),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
+ LOG_DEBUG("Set page scan activity interval:0x%x/%.02fms window:0x%x/%.02fms", params.interval,
+ ScanIntervalTimeMs(params.interval), params.window, ScanWindowTimeMs(params.window));
}
ScanParameters neighbor::PageModule::impl::GetScanActivity() const {
@@ -147,21 +141,21 @@ ScanParameters neighbor::PageModule::impl::GetScanActivity() const {
}
void neighbor::PageModule::impl::SetScanType(hci::PageScanType scan_type) {
- hci_layer_->EnqueueCommand(
- hci::WritePageScanTypeBuilder::Create(scan_type), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+ hci_layer_->EnqueueCommand(hci::WritePageScanTypeBuilder::Create(scan_type),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
- hci_layer_->EnqueueCommand(
- hci::ReadPageScanTypeBuilder::Create(), handler_->BindOnceOn(this, &impl::OnCommandComplete));
- LOG_INFO("Set page scan type:%s", hci::PageScanTypeText(scan_type).c_str());
+ hci_layer_->EnqueueCommand(hci::ReadPageScanTypeBuilder::Create(),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
+ LOG_DEBUG("Set page scan type:%s", hci::PageScanTypeText(scan_type).c_str());
}
void neighbor::PageModule::impl::SetTimeout(PageTimeout timeout) {
- hci_layer_->EnqueueCommand(
- hci::WritePageTimeoutBuilder::Create(timeout), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+ hci_layer_->EnqueueCommand(hci::WritePageTimeoutBuilder::Create(timeout),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
- hci_layer_->EnqueueCommand(
- hci::ReadPageTimeoutBuilder::Create(), handler_->BindOnceOn(this, &impl::OnCommandComplete));
- LOG_INFO("Set page scan timeout:0x%x/%.02fms", timeout, PageTimeoutMs(timeout));
+ hci_layer_->EnqueueCommand(hci::ReadPageTimeoutBuilder::Create(),
+ common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)), handler_);
+ LOG_DEBUG("Set page scan timeout:0x%x/%.02fms", timeout, PageTimeoutMs(timeout));
}
/**
diff --git a/gd/neighbor/page.h b/gd/neighbor/page.h
index 224b642af..075217bfd 100644
--- a/gd/neighbor/page.h
+++ b/gd/neighbor/page.h
@@ -49,9 +49,6 @@ class PageModule : public bluetooth::Module {
void ListDependencies(ModuleList* list) override;
void Start() override;
void Stop() override;
- std::string ToString() const override {
- return std::string("Page");
- }
private:
struct impl;
diff --git a/gd/neighbor/scan.cc b/gd/neighbor/scan.cc
index 66bc4cca7..5232b08af 100644
--- a/gd/neighbor/scan.cc
+++ b/gd/neighbor/scan.cc
@@ -16,9 +16,7 @@
#define LOG_TAG "bt_gd_neigh"
#include "neighbor/scan.h"
-
#include <memory>
-
#include "hci/hci_layer.h"
#include "hci/hci_packets.h"
#include "module.h"
@@ -96,12 +94,14 @@ void neighbor::ScanModule::impl::WriteScanEnable() {
{
std::unique_ptr<hci::WriteScanEnableBuilder> packet = hci::WriteScanEnableBuilder::Create(scan_enable);
- hci_layer_->EnqueueCommand(std::move(packet), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+ hci_layer_->EnqueueCommand(std::move(packet), common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)),
+ handler_);
}
{
std::unique_ptr<hci::ReadScanEnableBuilder> packet = hci::ReadScanEnableBuilder::Create();
- hci_layer_->EnqueueCommand(std::move(packet), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+ hci_layer_->EnqueueCommand(std::move(packet), common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)),
+ handler_);
}
}
@@ -152,11 +152,12 @@ void neighbor::ScanModule::impl::Start() {
handler_ = module_.GetHandler();
std::unique_ptr<hci::ReadScanEnableBuilder> packet = hci::ReadScanEnableBuilder::Create();
- hci_layer_->EnqueueCommand(std::move(packet), handler_->BindOnceOn(this, &impl::OnCommandComplete));
+ hci_layer_->EnqueueCommand(std::move(packet), common::BindOnce(&impl::OnCommandComplete, common::Unretained(this)),
+ handler_);
}
void neighbor::ScanModule::impl::Stop() {
- LOG_INFO("inquiry scan enabled:%d page scan enabled:%d", inquiry_scan_enabled_, page_scan_enabled_);
+ LOG_DEBUG("inquiry scan enabled:%d page scan enabled:%d", inquiry_scan_enabled_, page_scan_enabled_);
}
neighbor::ScanModule::ScanModule() : pimpl_(std::make_unique<impl>(*this)) {}
diff --git a/gd/neighbor/scan.h b/gd/neighbor/scan.h
index 83d73cf35..b6499d3cc 100644
--- a/gd/neighbor/scan.h
+++ b/gd/neighbor/scan.h
@@ -41,9 +41,6 @@ class ScanModule : public bluetooth::Module {
void ListDependencies(ModuleList* list) override;
void Start() override;
void Stop() override;
- std::string ToString() const override {
- return std::string("Scan");
- }
private:
struct impl;
diff --git a/gd/os/Android.bp b/gd/os/Android.bp
index fb4c50c2b..b8ad91a10 100644
--- a/gd/os/Android.bp
+++ b/gd/os/Android.bp
@@ -1,59 +1,12 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-filegroup {
- name: "BluetoothOsSources_android",
- srcs: [
- "android/metrics.cc",
- "android/parameter_provider.cc",
- "android/system_properties.cc",
- "android/wakelock_native.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothOsTestSources_android",
- srcs: [
- "android/system_properties_test.cc",
- "android/wakelock_native_test.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothOsSources_host",
- srcs: [
- "host/metrics.cc",
- "host/parameter_provider.cc",
- "host/system_properties.cc",
- "host/wakelock_native.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothOsTestSources_host",
- srcs: [
- "host/system_properties_test.cc",
- ],
-}
-
-
filegroup {
name: "BluetoothOsSources_linux_generic",
srcs: [
"linux_generic/alarm.cc",
- "linux_generic/files.cc",
"linux_generic/handler.cc",
"linux_generic/reactor.cc",
"linux_generic/repeating_alarm.cc",
"linux_generic/reactive_semaphore.cc",
"linux_generic/thread.cc",
- "linux_generic/wakelock_manager.cc",
],
}
@@ -61,28 +14,19 @@ filegroup {
name: "BluetoothOsTestSources_linux_generic",
srcs: [
"linux_generic/alarm_unittest.cc",
- "linux_generic/files_test.cc",
"linux_generic/handler_unittest.cc",
"linux_generic/queue_unittest.cc",
"linux_generic/reactor_unittest.cc",
"linux_generic/repeating_alarm_unittest.cc",
"linux_generic/thread_unittest.cc",
- "linux_generic/wakelock_manager_unittest.cc",
- ],
-}
-
-filegroup {
-name: "BluetoothOsBenchmarkSources",
- srcs: [
- "alarm_benchmark.cc",
- "thread_benchmark.cc",
- "queue_benchmark.cc",
],
}
filegroup {
- name: "BluetoothOsSources_fuzz",
+ name: "BluetoothOsBenchmarkSources",
srcs: [
- "fuzz/fake_timerfd.cc",
+ "alarm_benchmark.cc",
+ "thread_benchmark.cc",
+ "queue_benchmark.cc",
],
}
diff --git a/gd/os/BUILD.gn b/gd/os/BUILD.gn
deleted file mode 100644
index 55a844817..000000000
--- a/gd/os/BUILD.gn
+++ /dev/null
@@ -1,41 +0,0 @@
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-source_set("BluetoothOsSources_linux") {
- sources = [
- "linux/metrics.cc",
- "linux/parameter_provider.cc",
- "linux/system_properties.cc",
- "linux/wakelock_native.cc",
- ]
-
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ "//bt:libbt-platform-protos-lite" ]
-}
-
-source_set("BluetoothOsSources_linux_generic") {
- sources = [
- "linux_generic/alarm.cc",
- "linux_generic/files.cc",
- "linux_generic/handler.cc",
- "linux_generic/reactive_semaphore.cc",
- "linux_generic/reactor.cc",
- "linux_generic/repeating_alarm.cc",
- "linux_generic/thread.cc",
- "linux_generic/wakelock_manager.cc",
- ]
-
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ ":BluetoothOsSources_linux" ]
-}
diff --git a/gd/os/alarm.h b/gd/os/alarm.h
index 773c36f4a..e529fb9e4 100644
--- a/gd/os/alarm.h
+++ b/gd/os/alarm.h
@@ -42,13 +42,13 @@ class Alarm {
DISALLOW_COPY_AND_ASSIGN(Alarm);
// Schedule the alarm with given delay
- void Schedule(common::OnceClosure task, std::chrono::milliseconds delay);
+ void Schedule(OnceClosure task, std::chrono::milliseconds delay);
// Cancel the alarm. No-op if it's not armed.
void Cancel();
private:
- common::OnceClosure task_;
+ OnceClosure task_;
Handler* handler_;
int fd_ = 0;
Reactor::Reactable* token_;
diff --git a/gd/os/alarm_benchmark.cc b/gd/os/alarm_benchmark.cc
index 286ae4e14..215062542 100644
--- a/gd/os/alarm_benchmark.cc
+++ b/gd/os/alarm_benchmark.cc
@@ -19,6 +19,7 @@
#include <unordered_map>
#include "benchmark/benchmark.h"
+
#include "common/bind.h"
#include "os/alarm.h"
#include "os/repeating_alarm.h"
@@ -116,11 +117,9 @@ BENCHMARK_DEFINE_F(BM_ReactableAlarm, periodic_accuracy)(State& state) {
task_length_ = state.range(1);
task_interval_ = state.range(2);
start_time_ = std::chrono::steady_clock::now();
- repeating_alarm_->Schedule(
- Bind(
- &BM_ReactableAlarm_periodic_accuracy_Benchmark::AlarmSleepAndCountDelayedTime,
- bluetooth::common::Unretained(this)),
- std::chrono::milliseconds(task_interval_));
+ repeating_alarm_->Schedule(Bind(&BM_ReactableAlarm_periodic_accuracy_Benchmark::AlarmSleepAndCountDelayedTime,
+ bluetooth::common::Unretained(this)),
+ std::chrono::milliseconds(task_interval_));
promise_.get_future().get();
repeating_alarm_->Cancel();
}
diff --git a/gd/os/android/metrics.cc b/gd/os/android/metrics.cc
deleted file mode 100644
index 52608191b..000000000
--- a/gd/os/android/metrics.cc
+++ /dev/null
@@ -1,430 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#define LOG_TAG "BluetoothMetrics"
-
-#include <statslog.h>
-
-#include "common/metric_id_manager.h"
-#include "common/strings.h"
-#include "os/log.h"
-#include "os/metrics.h"
-
-namespace bluetooth {
-
-namespace os {
-
-using bluetooth::common::MetricIdManager;
-using bluetooth::hci::Address;
-
-/**
- * nullptr and size 0 represent missing value for obfuscated_id
- */
-static const android::util::BytesField byteField(nullptr, 0);
-
-void LogMetricLinkLayerConnectionEvent(
- const Address* address,
- uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction,
- uint16_t link_type,
- uint32_t hci_cmd,
- uint16_t hci_event,
- uint16_t hci_ble_event,
- uint16_t cmd_status,
- uint16_t reason_code) {
- int metric_id = 0;
- if (address != nullptr) {
- metric_id = MetricIdManager::GetInstance().AllocateId(*address);
- }
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_LINK_LAYER_CONNECTION_EVENT,
- byteField,
- connection_handle,
- direction,
- link_type,
- hci_cmd,
- hci_event,
- hci_ble_event,
- cmd_status,
- reason_code,
- metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed to log status %s , reason %s, from cmd %s, event %s, ble_event %s, for %s, handle %d, type %s, "
- "error %d",
- common::ToHexString(cmd_status).c_str(),
- common::ToHexString(reason_code).c_str(),
- common::ToHexString(hci_cmd).c_str(),
- common::ToHexString(hci_event).c_str(),
- common::ToHexString(hci_ble_event).c_str(),
- address ? address->ToString().c_str() : "(NULL)",
- connection_handle,
- common::ToHexString(link_type).c_str(),
- ret);
- }
-}
-
-void LogMetricHciTimeoutEvent(uint32_t hci_cmd) {
- int ret = android::util::stats_write(android::util::BLUETOOTH_HCI_TIMEOUT_REPORTED, static_cast<int64_t>(hci_cmd));
- if (ret < 0) {
- LOG_WARN("Failed for opcode %s, error %d", common::ToHexString(hci_cmd).c_str(), ret);
- }
-}
-
-void LogMetricRemoteVersionInfo(
- uint16_t handle, uint8_t status, uint8_t version, uint16_t manufacturer_name, uint16_t subversion) {
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_REMOTE_VERSION_INFO_REPORTED, handle, status, version, manufacturer_name, subversion);
- if (ret < 0) {
- LOG_WARN(
- "Failed for handle %d, status %s, version %s, manufacturer_name %s, subversion %s, error %d",
- handle,
- common::ToHexString(status).c_str(),
- common::ToHexString(version).c_str(),
- common::ToHexString(manufacturer_name).c_str(),
- common::ToHexString(subversion).c_str(),
- ret);
- }
-}
-
-void LogMetricA2dpAudioUnderrunEvent(
- const Address& address, uint64_t encoding_interval_millis, int num_missing_pcm_bytes) {
- int metric_id = 0;
- if (!address.IsEmpty()) {
- metric_id = MetricIdManager::GetInstance().AllocateId(address);
- }
- int64_t encoding_interval_nanos = encoding_interval_millis * 1000000;
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_A2DP_AUDIO_UNDERRUN_REPORTED,
- byteField,
- encoding_interval_nanos,
- num_missing_pcm_bytes,
- metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed for %s, encoding_interval_nanos %s, num_missing_pcm_bytes %d, error %d",
- address.ToString().c_str(),
- std::to_string(encoding_interval_nanos).c_str(),
- num_missing_pcm_bytes,
- ret);
- }
-}
-
-void LogMetricA2dpAudioOverrunEvent(
- const Address& address,
- uint64_t encoding_interval_millis,
- int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes) {
- int metric_id = 0;
- if (!address.IsEmpty()) {
- metric_id = MetricIdManager::GetInstance().AllocateId(address);
- }
-
- int64_t encoding_interval_nanos = encoding_interval_millis * 1000000;
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_A2DP_AUDIO_OVERRUN_REPORTED,
- byteField,
- encoding_interval_nanos,
- num_dropped_buffers,
- num_dropped_encoded_frames,
- num_dropped_encoded_bytes,
- metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed to log for %s, encoding_interval_nanos %s, num_dropped_buffers %d, "
- "num_dropped_encoded_frames %d, num_dropped_encoded_bytes %d, error %d",
- address.ToString().c_str(),
- std::to_string(encoding_interval_nanos).c_str(),
- num_dropped_buffers,
- num_dropped_encoded_frames,
- num_dropped_encoded_bytes,
- ret);
- }
-}
-
-void LogMetricA2dpPlaybackEvent(const Address& address, int playback_state, int audio_coding_mode) {
- int metric_id = 0;
- if (!address.IsEmpty()) {
- metric_id = MetricIdManager::GetInstance().AllocateId(address);
- }
-
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_A2DP_PLAYBACK_STATE_CHANGED, byteField, playback_state, audio_coding_mode, metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed to log for %s, playback_state %d, audio_coding_mode %d,error %d",
- address.ToString().c_str(),
- playback_state,
- audio_coding_mode,
- ret);
- }
-}
-
-void LogMetricReadRssiResult(const Address& address, uint16_t handle, uint32_t cmd_status, int8_t rssi) {
- int metric_id = 0;
- if (!address.IsEmpty()) {
- metric_id = MetricIdManager::GetInstance().AllocateId(address);
- }
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_DEVICE_RSSI_REPORTED, byteField, handle, cmd_status, rssi, metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed for %s, handle %d, status %s, rssi %d dBm, error %d",
- address.ToString().c_str(),
- handle,
- common::ToHexString(cmd_status).c_str(),
- rssi,
- ret);
- }
-}
-
-void LogMetricReadFailedContactCounterResult(
- const Address& address, uint16_t handle, uint32_t cmd_status, int32_t failed_contact_counter) {
- int metric_id = 0;
- if (!address.IsEmpty()) {
- metric_id = MetricIdManager::GetInstance().AllocateId(address);
- }
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_DEVICE_FAILED_CONTACT_COUNTER_REPORTED,
- byteField,
- handle,
- cmd_status,
- failed_contact_counter,
- metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed for %s, handle %d, status %s, failed_contact_counter %d packets, error %d",
- address.ToString().c_str(),
- handle,
- common::ToHexString(cmd_status).c_str(),
- failed_contact_counter,
- ret);
- }
-}
-
-void LogMetricReadTxPowerLevelResult(
- const Address& address, uint16_t handle, uint32_t cmd_status, int32_t transmit_power_level) {
- int metric_id = 0;
- if (!address.IsEmpty()) {
- metric_id = MetricIdManager::GetInstance().AllocateId(address);
- }
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_DEVICE_TX_POWER_LEVEL_REPORTED,
- byteField,
- handle,
- cmd_status,
- transmit_power_level,
- metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed for %s, handle %d, status %s, transmit_power_level %d packets, error %d",
- address.ToString().c_str(),
- handle,
- common::ToHexString(cmd_status).c_str(),
- transmit_power_level,
- ret);
- }
-}
-
-void LogMetricSmpPairingEvent(
- const Address& address, uint8_t smp_cmd, android::bluetooth::DirectionEnum direction, uint8_t smp_fail_reason) {
- int metric_id = 0;
- if (!address.IsEmpty()) {
- metric_id = MetricIdManager::GetInstance().AllocateId(address);
- }
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_SMP_PAIRING_EVENT_REPORTED, byteField, smp_cmd, direction, smp_fail_reason, metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed for %s, smp_cmd %s, direction %d, smp_fail_reason %s, error %d",
- address.ToString().c_str(),
- common::ToHexString(smp_cmd).c_str(),
- direction,
- common::ToHexString(smp_fail_reason).c_str(),
- ret);
- }
-}
-
-void LogMetricClassicPairingEvent(
- const Address& address,
- uint16_t handle,
- uint32_t hci_cmd,
- uint16_t hci_event,
- uint16_t cmd_status,
- uint16_t reason_code,
- int64_t event_value) {
- int metric_id = 0;
- if (!address.IsEmpty()) {
- metric_id = MetricIdManager::GetInstance().AllocateId(address);
- }
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_CLASSIC_PAIRING_EVENT_REPORTED,
- byteField,
- handle,
- hci_cmd,
- hci_event,
- cmd_status,
- reason_code,
- event_value,
- metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed for %s, handle %d, hci_cmd %s, hci_event %s, cmd_status %s, "
- "reason %s, event_value %s, error %d",
- address.ToString().c_str(),
- handle,
- common::ToHexString(hci_cmd).c_str(),
- common::ToHexString(hci_event).c_str(),
- common::ToHexString(cmd_status).c_str(),
- common::ToHexString(reason_code).c_str(),
- std::to_string(event_value).c_str(),
- ret);
- }
-}
-
-void LogMetricSdpAttribute(
- const Address& address,
- uint16_t protocol_uuid,
- uint16_t attribute_id,
- size_t attribute_size,
- const char* attribute_value) {
- int metric_id = 0;
- if (!address.IsEmpty()) {
- metric_id = MetricIdManager::GetInstance().AllocateId(address);
- }
- android::util::BytesField attribute_field(attribute_value, attribute_size);
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_SDP_ATTRIBUTE_REPORTED,
- byteField,
- protocol_uuid,
- attribute_id,
- attribute_field,
- metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed for %s, protocol_uuid %s, attribute_id %s, error %d",
- address.ToString().c_str(),
- common::ToHexString(protocol_uuid).c_str(),
- common::ToHexString(attribute_id).c_str(),
- ret);
- }
-}
-
-void LogMetricSocketConnectionState(
- const Address& address,
- int port,
- int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes,
- int64_t rx_bytes,
- int uid,
- int server_port,
- android::bluetooth::SocketRoleEnum socket_role) {
- int metric_id = 0;
- if (!address.IsEmpty()) {
- metric_id = MetricIdManager::GetInstance().AllocateId(address);
- }
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_SOCKET_CONNECTION_STATE_CHANGED,
- byteField,
- port,
- type,
- connection_state,
- tx_bytes,
- rx_bytes,
- uid,
- server_port,
- socket_role,
- metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed for %s, port %d, type %d, state %d, tx_bytes %s, rx_bytes %s, uid %d, server_port %d, "
- "socket_role %d, error %d",
- address.ToString().c_str(),
- port,
- type,
- connection_state,
- std::to_string(tx_bytes).c_str(),
- std::to_string(rx_bytes).c_str(),
- uid,
- server_port,
- socket_role,
- ret);
- }
-}
-
-void LogMetricManufacturerInfo(
- const Address& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer,
- const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version) {
- int metric_id = 0;
- if (!address.IsEmpty()) {
- metric_id = MetricIdManager::GetInstance().AllocateId(address);
- }
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_DEVICE_INFO_REPORTED,
- byteField,
- source_type,
- source_name.c_str(),
- manufacturer.c_str(),
- model.c_str(),
- hardware_version.c_str(),
- software_version.c_str(),
- metric_id);
- if (ret < 0) {
- LOG_WARN(
- "Failed for %s, source_type %d, source_name %s, manufacturer %s, model %s, hardware_version %s, "
- "software_version %s, error %d",
- address.ToString().c_str(),
- source_type,
- source_name.c_str(),
- manufacturer.c_str(),
- model.c_str(),
- hardware_version.c_str(),
- software_version.c_str(),
- ret);
- }
-}
-
-void LogMetricBluetoothHalCrashReason(
- const Address& address,
- uint32_t error_code,
- uint32_t vendor_error_code) {
- int ret = android::util::stats_write(
- android::util::BLUETOOTH_HAL_CRASH_REASON_REPORTED,
- 0 /* metric_id */,
- byteField,
- error_code,
- vendor_error_code);
- if (ret < 0) {
- LOG_WARN(
- "Failed for %s, error_code %s, vendor_error_code %s, error %d",
- address.ToString().c_str(),
- common::ToHexString(error_code).c_str(),
- common::ToHexString(vendor_error_code).c_str(),
- ret);
- }
-}
-
-} // namespace os
-} // namespace bluetooth
diff --git a/gd/os/android/parameter_provider.cc b/gd/os/android/parameter_provider.cc
deleted file mode 100644
index dcf7c407e..000000000
--- a/gd/os/android/parameter_provider.cc
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "os/parameter_provider.h"
-
-#include <mutex>
-#include <string>
-
-namespace bluetooth {
-namespace os {
-
-namespace {
-std::mutex parameter_mutex;
-std::string config_file_path;
-std::string snoop_log_file_path;
-std::string snooz_log_file_path;
-} // namespace
-
-// On Android we always write a single default location
-std::string ParameterProvider::ConfigFilePath() {
- {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- if (!config_file_path.empty()) {
- return config_file_path;
- }
- }
- return "/data/misc/bluedroid/bt_config.conf";
-}
-
-void ParameterProvider::OverrideConfigFilePath(const std::string& path) {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- config_file_path = path;
-}
-
-std::string ParameterProvider::SnoopLogFilePath() {
- {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- if (!snoop_log_file_path.empty()) {
- return snoop_log_file_path;
- }
- }
- return "/data/misc/bluetooth/logs/btsnoop_hci.log";
-}
-
-void ParameterProvider::OverrideSnoopLogFilePath(const std::string& path) {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- snoop_log_file_path = path;
-}
-
-// Return the path to the default snooz log file location
-std::string ParameterProvider::SnoozLogFilePath() {
- {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- if (!snooz_log_file_path.empty()) {
- return snooz_log_file_path;
- }
- }
- return "/data/misc/bluetooth/logs/btsnooz_hci.log";
-}
-
-void ParameterProvider::OverrideSnoozLogFilePath(const std::string& path) {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- snooz_log_file_path = path;
-}
-
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/android/system_properties.cc b/gd/os/android/system_properties.cc
deleted file mode 100644
index a53c1bf6d..000000000
--- a/gd/os/android/system_properties.cc
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "os/system_properties.h"
-
-#include <cutils/properties.h>
-
-#include <array>
-
-#include "os/log.h"
-
-namespace bluetooth {
-namespace os {
-
-std::optional<std::string> GetSystemProperty(const std::string& property) {
- std::array<char, PROPERTY_VALUE_MAX> value_array{0};
- auto value_len = property_get(property.c_str(), value_array.data(), nullptr);
- if (value_len <= 0) {
- return std::nullopt;
- }
- return std::string(value_array.data(), value_len);
-}
-
-bool SetSystemProperty(const std::string& property, const std::string& value) {
- if (value.size() >= PROPERTY_VALUE_MAX) {
- LOG_ERROR("Property value's maximum size is %d, but %zu chars were given", PROPERTY_VALUE_MAX - 1, value.size());
- return false;
- }
- auto ret = property_set(property.c_str(), value.c_str());
- if (ret != 0) {
- LOG_ERROR("Set property %s failed with error code %d", property.c_str(), ret);
- return false;
- }
- return true;
-}
-
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/android/system_properties_test.cc b/gd/os/android/system_properties_test.cc
deleted file mode 100644
index 9a2823fbf..000000000
--- a/gd/os/android/system_properties_test.cc
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <string>
-
-#include <gtest/gtest.h>
-
-#include <cutils/properties.h>
-
-#include "os/system_properties.h"
-
-namespace testing {
-
-using bluetooth::os::GetSystemProperty;
-using bluetooth::os::SetSystemProperty;
-
-TEST(SystemPropertiesTest, set_and_get_test) {
- ASSERT_TRUE(SetSystemProperty("persist.bluetooth.factoryreset", "true"));
- auto ret = GetSystemProperty("persist.bluetooth.factoryreset");
- ASSERT_TRUE(ret);
- ASSERT_EQ(ret, "true");
- ASSERT_TRUE(SetSystemProperty("persist.bluetooth.factoryreset", "false"));
- ret = GetSystemProperty("persist.bluetooth.factoryreset");
- ASSERT_TRUE(ret);
- ASSERT_EQ(ret, "false");
- ret = GetSystemProperty("persist.bluetooth.factoryreset_do_not_exist");
- ASSERT_FALSE(ret);
-}
-
-// From Android O and above, there is no limit on property key sizesss
-TEST(SystemPropertiesTest, max_length_test) {
- std::string property(PROP_NAME_MAX, 'a');
- std::string value(PROP_VALUE_MAX, '1');
- ASSERT_TRUE(SetSystemProperty("persist.bluetooth.factoryreset", "false"));
- ASSERT_TRUE(SetSystemProperty(property, "true"));
- ASSERT_FALSE(SetSystemProperty("persist.bluetooth.factoryreset", value));
- ASSERT_FALSE(SetSystemProperty(property, value));
- ASSERT_TRUE(GetSystemProperty(property));
- // make sure no actual operations on system property happened
- auto ret = GetSystemProperty("persist.bluetooth.factoryreset");
- ASSERT_TRUE(ret);
- ASSERT_EQ(ret, "false");
-}
-
-} // namespace testing \ No newline at end of file
diff --git a/gd/os/android/wakelock_native.cc b/gd/os/android/wakelock_native.cc
deleted file mode 100644
index d57528203..000000000
--- a/gd/os/android/wakelock_native.cc
+++ /dev/null
@@ -1,118 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#define LOG_TAG "BtGdWakelockNative"
-
-#include "os/internal/wakelock_native.h"
-
-#include <android/system/suspend/1.0/ISystemSuspend.h>
-#include <fcntl.h>
-#include <unistd.h>
-
-#include <cerrno>
-#include <string>
-
-#include "os/log.h"
-
-namespace bluetooth {
-namespace os {
-namespace internal {
-
-using android::sp;
-using android::system::suspend::V1_0::ISystemSuspend;
-using android::system::suspend::V1_0::IWakeLock;
-using android::system::suspend::V1_0::WakeLockType;
-
-struct WakelockNative::Impl {
- sp<ISystemSuspend> suspend_service = nullptr;
- sp<IWakeLock> current_wakelock = nullptr;
-
- class SystemSuspendDeathRecipient : public ::android::hardware::hidl_death_recipient {
- public:
- explicit SystemSuspendDeathRecipient(WakelockNative::Impl* impl) : impl_(impl) {}
- void serviceDied(uint64_t /*cookie*/, const android::wp<::android::hidl::base::V1_0::IBase>& /*who*/) override {
- LOG_ERROR("ISystemSuspend HAL service died!");
- impl_->suspend_service = nullptr;
- }
-
- private:
- WakelockNative::Impl* impl_ = nullptr;
- };
- sp<SystemSuspendDeathRecipient> suspend_death_recipient;
-};
-
-void WakelockNative::Initialize() {
- LOG_INFO("Initializing native wake locks");
- pimpl_->suspend_service = ISystemSuspend::getService();
- ASSERT_LOG(pimpl_->suspend_service, "Cannot get ISystemSuspend service");
- pimpl_->suspend_death_recipient = new Impl::SystemSuspendDeathRecipient(pimpl_.get());
- pimpl_->suspend_service->linkToDeath(pimpl_->suspend_death_recipient, 0 /* cookie */);
-}
-
-WakelockNative::StatusCode WakelockNative::Acquire(const std::string& lock_name) {
- if (!pimpl_->suspend_service) {
- LOG_ERROR("lock not acquired, ISystemService is not available");
- return StatusCode::NATIVE_SERVICE_NOT_AVAILABLE;
- }
-
- if (pimpl_->current_wakelock) {
- LOG_INFO("wakelock is already acquired");
- return StatusCode::SUCCESS;
- }
-
- pimpl_->current_wakelock = pimpl_->suspend_service->acquireWakeLock(WakeLockType::PARTIAL, lock_name);
- if (!pimpl_->current_wakelock) {
- LOG_ERROR("wake lock not acquired: %s", strerror(errno));
- return StatusCode::NATIVE_API_ERROR;
- }
-
- return StatusCode::SUCCESS;
-}
-
-WakelockNative::StatusCode WakelockNative::Release(const std::string& lock_name) {
- if (!pimpl_->current_wakelock) {
- LOG_WARN("no lock is currently acquired");
- return StatusCode::SUCCESS;
- }
- pimpl_->current_wakelock->release();
- pimpl_->current_wakelock.clear();
- return StatusCode::SUCCESS;
-}
-
-void WakelockNative::CleanUp() {
- LOG_INFO("Cleaning up native wake locks");
- if (pimpl_->current_wakelock) {
- LOG_INFO("releasing current wakelock during clean up");
- pimpl_->current_wakelock->release();
- pimpl_->current_wakelock.clear();
- }
- if (pimpl_->suspend_service) {
- LOG_INFO("Unlink death recipient");
- pimpl_->suspend_service->unlinkToDeath(pimpl_->suspend_death_recipient);
- pimpl_->suspend_death_recipient.clear();
- pimpl_->suspend_service.clear();
- }
-}
-
-WakelockNative::WakelockNative() : pimpl_(std::make_unique<Impl>()) {}
-
-WakelockNative::~WakelockNative() = default;
-
-} // namespace internal
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/android/wakelock_native_test.cc b/gd/os/android/wakelock_native_test.cc
deleted file mode 100644
index 66be72296..000000000
--- a/gd/os/android/wakelock_native_test.cc
+++ /dev/null
@@ -1,273 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2020 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#include "os/internal/wakelock_native.h"
-
-#include <aidl/android/system/suspend/BnSuspendCallback.h>
-#include <aidl/android/system/suspend/BnWakelockCallback.h>
-#include <aidl/android/system/suspend/ISuspendControlService.h>
-#include <android/binder_auto_utils.h>
-#include <android/binder_interface_utils.h>
-#include <android/binder_manager.h>
-#include <android/binder_process.h>
-#include <gtest/gtest.h>
-
-#include <chrono>
-#include <future>
-#include <memory>
-#include <mutex>
-
-namespace testing {
-
-using aidl::android::system::suspend::BnSuspendCallback;
-using aidl::android::system::suspend::BnWakelockCallback;
-using aidl::android::system::suspend::ISuspendControlService;
-using bluetooth::os::internal::WakelockNative;
-using ndk::ScopedAStatus;
-using ndk::SharedRefBase;
-using ndk::SpAIBinder;
-
-static const std::string kTestWakelockName = "BtWakelockNativeTestLock";
-
-static std::recursive_mutex mutex;
-static std::unique_ptr<std::promise<void>> acquire_promise = nullptr;
-static std::unique_ptr<std::promise<void>> release_promise = nullptr;
-
-class PromiseFutureContext {
- public:
- static void FulfilPromise(std::unique_ptr<std::promise<void>>& promise) {
- std::lock_guard<std::recursive_mutex> lock_guard(mutex);
- if (promise != nullptr) {
- promise->set_value();
- promise = nullptr;
- }
- }
-
- explicit PromiseFutureContext(std::unique_ptr<std::promise<void>>& promise, bool expect_fulfillment)
- : promise_(promise), expect_fulfillment_(expect_fulfillment) {
- std::lock_guard<std::recursive_mutex> lock_guard(mutex);
- EXPECT_EQ(promise_, nullptr);
- promise_ = std::make_unique<std::promise<void>>();
- future_ = promise->get_future();
- }
-
- ~PromiseFutureContext() {
- auto future_status = future_.wait_for(std::chrono::seconds(2));
- if (expect_fulfillment_) {
- EXPECT_EQ(future_status, std::future_status::ready);
- } else {
- EXPECT_NE(future_status, std::future_status::ready);
- }
- std::lock_guard<std::recursive_mutex> lock_guard(mutex);
- promise_ = nullptr;
- }
-
- private:
- std::unique_ptr<std::promise<void>>& promise_;
- bool expect_fulfillment_ = true;
- std::future<void> future_;
-};
-
-class WakelockCallback : public BnWakelockCallback {
- public:
- ScopedAStatus notifyAcquired() override {
- std::lock_guard<std::recursive_mutex> lock_guard(mutex);
- net_acquired_count++;
- fprintf(stderr, "notifyAcquired, count = %d\n", net_acquired_count);
- PromiseFutureContext::FulfilPromise(acquire_promise);
- return ScopedAStatus::ok();
- }
- ScopedAStatus notifyReleased() override {
- std::lock_guard<std::recursive_mutex> lock_guard(mutex);
- net_acquired_count--;
- fprintf(stderr, "notifyReleased, count = %d\n", net_acquired_count);
- PromiseFutureContext::FulfilPromise(release_promise);
- return ScopedAStatus::ok();
- }
-
- int net_acquired_count = 0;
-};
-
-class SuspendCallback : public BnSuspendCallback {
- public:
- ScopedAStatus notifyWakeup(bool success, const std::vector<std::string>& wakeup_reasons) override {
- std::lock_guard<std::recursive_mutex> lock_guard(mutex);
- fprintf(stderr, "notifyWakeup\n");
- return ScopedAStatus::ok();
- }
-};
-
-// There is no way to unregister these callbacks besides when this process dies
-// Hence, we want to have only one copy of these callbacks per process
-static std::shared_ptr<SuspendCallback> suspend_callback = nullptr;
-static std::shared_ptr<WakelockCallback> control_callback = nullptr;
-
-class WakelockNativeTest : public Test {
- protected:
- void SetUp() override {
- ABinderProcess_setThreadPoolMaxThreadCount(1);
- ABinderProcess_startThreadPool();
-
- WakelockNative::Get().Initialize();
-
- auto binder_raw = AServiceManager_getService("suspend_control");
- ASSERT_NE(binder_raw, nullptr);
- binder.set(binder_raw);
- control_service_ = ISuspendControlService::fromBinder(binder);
- if (control_service_ == nullptr) {
- FAIL() << "Fail to obtain suspend_control";
- }
-
- if (suspend_callback == nullptr) {
- suspend_callback = SharedRefBase::make<SuspendCallback>();
- bool is_registered = false;
- ScopedAStatus status = control_service_->registerCallback(suspend_callback, &is_registered);
- if (!is_registered || !status.isOk()) {
- FAIL() << "Fail to register suspend callback";
- }
- }
-
- if (control_callback == nullptr) {
- control_callback = SharedRefBase::make<WakelockCallback>();
- bool is_registered = false;
- ScopedAStatus status =
- control_service_->registerWakelockCallback(control_callback, kTestWakelockName, &is_registered);
- if (!is_registered || !status.isOk()) {
- FAIL() << "Fail to register wakeup callback";
- }
- }
- control_callback->net_acquired_count = 0;
- }
-
- void TearDown() override {
- control_service_ = nullptr;
- binder.set(nullptr);
- WakelockNative::Get().CleanUp();
- }
-
- SpAIBinder binder;
- std::shared_ptr<ISuspendControlService> control_service_ = nullptr;
-};
-
-TEST_F(WakelockNativeTest, test_acquire_and_release_wakelocks) {
- ASSERT_EQ(control_callback->net_acquired_count, 0);
-
- {
- PromiseFutureContext context(acquire_promise, true);
- auto status = WakelockNative::Get().Acquire(kTestWakelockName);
- ASSERT_EQ(status, WakelockNative::StatusCode::SUCCESS);
- }
- ASSERT_EQ(control_callback->net_acquired_count, 1);
-
- {
- PromiseFutureContext context(release_promise, true);
- auto status = WakelockNative::Get().Release(kTestWakelockName);
- ASSERT_EQ(status, WakelockNative::StatusCode::SUCCESS);
- }
- ASSERT_EQ(control_callback->net_acquired_count, 0);
-}
-
-TEST_F(WakelockNativeTest, test_acquire_and_release_wakelocks_repeated_acquire) {
- ASSERT_EQ(control_callback->net_acquired_count, 0);
-
- {
- PromiseFutureContext context(acquire_promise, true);
- auto status = WakelockNative::Get().Acquire(kTestWakelockName);
- ASSERT_EQ(status, WakelockNative::StatusCode::SUCCESS);
- }
- ASSERT_EQ(control_callback->net_acquired_count, 1);
-
- {
- PromiseFutureContext context(acquire_promise, false);
- auto status = WakelockNative::Get().Acquire(kTestWakelockName);
- ASSERT_EQ(status, WakelockNative::StatusCode::SUCCESS);
- }
- ASSERT_EQ(control_callback->net_acquired_count, 1);
-
- {
- PromiseFutureContext context(release_promise, true);
- auto status = WakelockNative::Get().Release(kTestWakelockName);
- ASSERT_EQ(status, WakelockNative::StatusCode::SUCCESS);
- }
- ASSERT_EQ(control_callback->net_acquired_count, 0);
-}
-
-TEST_F(WakelockNativeTest, test_acquire_and_release_wakelocks_repeated_release) {
- ASSERT_EQ(control_callback->net_acquired_count, 0);
-
- {
- PromiseFutureContext context(acquire_promise, true);
- auto status = WakelockNative::Get().Acquire(kTestWakelockName);
- ASSERT_EQ(status, WakelockNative::StatusCode::SUCCESS);
- }
- ASSERT_EQ(control_callback->net_acquired_count, 1);
-
- {
- PromiseFutureContext context(release_promise, true);
- auto status = WakelockNative::Get().Release(kTestWakelockName);
- ASSERT_EQ(status, WakelockNative::StatusCode::SUCCESS);
- }
- ASSERT_EQ(control_callback->net_acquired_count, 0);
-
- {
- PromiseFutureContext context(release_promise, false);
- auto status = WakelockNative::Get().Release(kTestWakelockName);
- ASSERT_EQ(status, WakelockNative::StatusCode::SUCCESS);
- }
- ASSERT_EQ(control_callback->net_acquired_count, 0);
-}
-
-TEST_F(WakelockNativeTest, test_acquire_and_release_wakelocks_in_a_loop) {
- ASSERT_EQ(control_callback->net_acquired_count, 0);
-
- for (int i = 0; i < 10; ++i) {
- {
- PromiseFutureContext context(acquire_promise, true);
- auto status = WakelockNative::Get().Acquire(kTestWakelockName);
- ASSERT_EQ(status, WakelockNative::StatusCode::SUCCESS);
- }
- ASSERT_EQ(control_callback->net_acquired_count, 1);
-
- {
- PromiseFutureContext context(release_promise, true);
- auto status = WakelockNative::Get().Release(kTestWakelockName);
- ASSERT_EQ(status, WakelockNative::StatusCode::SUCCESS);
- }
- ASSERT_EQ(control_callback->net_acquired_count, 0);
- }
-}
-
-TEST_F(WakelockNativeTest, test_clean_up) {
- WakelockNative::Get().Initialize();
- ASSERT_EQ(control_callback->net_acquired_count, 0);
-
- {
- PromiseFutureContext context(acquire_promise, true);
- auto status = WakelockNative::Get().Acquire(kTestWakelockName);
- ASSERT_EQ(status, WakelockNative::StatusCode::SUCCESS);
- }
- ASSERT_EQ(control_callback->net_acquired_count, 1);
-
- {
- PromiseFutureContext context(release_promise, true);
- WakelockNative::Get().CleanUp();
- }
- ASSERT_EQ(control_callback->net_acquired_count, 0);
-}
-
-} // namespace testing \ No newline at end of file
diff --git a/gd/os/files.h b/gd/os/files.h
deleted file mode 100644
index 5a6721b1e..000000000
--- a/gd/os/files.h
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <iterator>
-#include <optional>
-
-namespace bluetooth {
-namespace os {
-
-// Return true if |path| exists on disk
-bool FileExists(const std::string& path);
-
-// Rename file from |from| to |to|
-bool RenameFile(const std::string& from, const std::string& to);
-
-// Implement ability to read a whole file from |path| into a C++ string, return std::nullopt on failure
-//
-// Do not use this with large files
-std::optional<std::string> ReadSmallFile(const std::string& path);
-
-// Implement ability to safely write to a file. This function is needed because of deficiencies in existing C++ file
-// libraries, namely:
-// - The ability to open and sync directories with storage media
-// - The ability to block and sync file to storage media
-// Return true on success, false on failure
-bool WriteToFile(const std::string& path, const std::string& data);
-
-// Remove file and print error message if failed
-// Print error log when file is failed to be removed, hence user should make sure file exists before calling this
-// Return true on success, false on failure (e.g. file not exist, failed to remove, etc)
-bool RemoveFile(const std::string& path);
-
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/fuzz/dev_null_queue.h b/gd/os/fuzz/dev_null_queue.h
deleted file mode 100644
index 0b2d7c550..000000000
--- a/gd/os/fuzz/dev_null_queue.h
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "os/queue.h"
-
-namespace bluetooth {
-namespace os {
-namespace fuzz {
-
-// Drops stuff you send it, and banishes it into the void.
-template <typename T>
-class DevNullQueue {
- public:
- DevNullQueue(IQueueDequeue<T>* queue, Handler* handler) : queue_(queue), handler_(handler) {}
- ~DevNullQueue() {}
-
- void Start() {
- queue_->RegisterDequeue(handler_, common::Bind(&DevNullQueue::Dump, common::Unretained(this)));
- }
-
- void Stop() {
- queue_->UnregisterDequeue();
- }
-
- void Dump() {
- queue_->TryDequeue();
- }
-
- private:
- IQueueDequeue<T>* queue_;
- Handler* handler_;
-};
-
-} // namespace fuzz
-} // namespace os
-} // namespace bluetooth
diff --git a/gd/os/fuzz/fake_timerfd.cc b/gd/os/fuzz/fake_timerfd.cc
deleted file mode 100644
index 5b7389beb..000000000
--- a/gd/os/fuzz/fake_timerfd.cc
+++ /dev/null
@@ -1,139 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "os/fuzz/fake_timerfd.h"
-
-#include <sys/eventfd.h>
-#include <unistd.h>
-
-#include <map>
-
-namespace bluetooth {
-namespace os {
-namespace fuzz {
-
-class FakeTimerFd {
- public:
- int fd;
- bool active;
- uint64_t trigger_ms;
- uint64_t period_ms;
-};
-
-static std::map<int, FakeTimerFd*> fake_timers;
-static uint64_t clock = 0;
-static uint64_t max_clock = UINT64_MAX;
-
-static uint64_t timespec_to_ms(const timespec* t) {
- return t->tv_sec * 1000 + t->tv_nsec / 1000000;
-}
-
-int fake_timerfd_create(int clockid, int flags) {
- int fd = eventfd(0, 0);
- if (fd == -1) {
- return fd;
- }
-
- FakeTimerFd* entry = new FakeTimerFd();
- fake_timers[fd] = entry;
- entry->fd = fd;
- return fd;
-}
-
-int fake_timerfd_settime(int fd, int flags, const struct itimerspec* new_value, struct itimerspec* old_value) {
- if (fake_timers.find(fd) == fake_timers.end()) {
- return -1;
- }
-
- FakeTimerFd* entry = fake_timers[fd];
-
- uint64_t trigger_delta_ms = timespec_to_ms(&new_value->it_value);
- entry->active = trigger_delta_ms != 0;
- if (!entry->active) {
- return 0;
- }
-
- uint64_t period_ms = timespec_to_ms(&new_value->it_value);
- entry->trigger_ms = clock + trigger_delta_ms;
- entry->period_ms = period_ms;
- return 0;
-}
-
-int fake_timerfd_close(int fd) {
- auto timer_iterator = fake_timers.find(fd);
- if (timer_iterator != fake_timers.end()) {
- delete timer_iterator->second;
- fake_timers.erase(timer_iterator);
- }
- return close(fd);
-}
-
-void fake_timerfd_reset() {
- clock = 0;
- max_clock = UINT64_MAX;
- // if there are entries still here, it is a failure of our users to clean up
- // so let them leak and trigger errors
- fake_timers.clear();
-}
-
-static bool fire_next_event(uint64_t new_clock) {
- uint64_t earliest_time = new_clock;
- FakeTimerFd* to_fire = nullptr;
- for (auto it = fake_timers.begin(); it != fake_timers.end(); it++) {
- FakeTimerFd* entry = it->second;
- if (!entry->active) {
- continue;
- }
-
- if (entry->trigger_ms > clock && entry->trigger_ms <= new_clock) {
- if (to_fire == nullptr || entry->trigger_ms < earliest_time) {
- to_fire = entry;
- earliest_time = entry->trigger_ms;
- }
- }
- }
-
- if (to_fire == nullptr) {
- return false;
- }
-
- bool is_periodic = to_fire->period_ms != 0;
- if (is_periodic) {
- to_fire->trigger_ms += to_fire->period_ms;
- }
- to_fire->active = is_periodic;
- uint64_t value = 1;
- write(to_fire->fd, &value, sizeof(uint64_t));
- return true;
-}
-
-void fake_timerfd_advance(uint64_t ms) {
- uint64_t new_clock = clock + ms;
- if (new_clock > max_clock) {
- new_clock = max_clock;
- }
- while (fire_next_event(new_clock)) {
- }
- clock = new_clock;
-}
-
-void fake_timerfd_cap_at(uint64_t ms) {
- max_clock = ms;
-}
-
-} // namespace fuzz
-} // namespace os
-} // namespace bluetooth
diff --git a/gd/os/fuzz/fake_timerfd.h b/gd/os/fuzz/fake_timerfd.h
deleted file mode 100644
index 069e15389..000000000
--- a/gd/os/fuzz/fake_timerfd.h
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <sys/timerfd.h>
-
-#include <cstdint>
-
-namespace bluetooth {
-namespace os {
-namespace fuzz {
-
-int fake_timerfd_create(int clockid, int flags);
-
-int fake_timerfd_settime(int fd, int flags, const struct itimerspec* new_value, struct itimerspec* old_value);
-
-int fake_timerfd_close(int fd);
-
-void fake_timerfd_reset();
-
-void fake_timerfd_advance(uint64_t ms);
-
-void fake_timerfd_cap_at(uint64_t ms);
-
-} // namespace fuzz
-} // namespace os
-} // namespace bluetooth
diff --git a/gd/os/fuzz/fuzz_inject_queue.h b/gd/os/fuzz/fuzz_inject_queue.h
deleted file mode 100644
index 2b9ebae96..000000000
--- a/gd/os/fuzz/fuzz_inject_queue.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "os/queue.h"
-
-namespace bluetooth {
-namespace os {
-namespace fuzz {
-
-template <typename T>
-class FuzzInjectQueue {
- public:
- FuzzInjectQueue(IQueueEnqueue<T>* queue, Handler* handler) : handler_(handler) {
- buffer_ = new EnqueueBuffer<T>(queue);
- }
- ~FuzzInjectQueue() {
- delete buffer_;
- }
-
- void Inject(std::unique_ptr<T> data) {
- buffer_->Enqueue(std::move(data), handler_);
- }
-
- private:
- EnqueueBuffer<T>* buffer_;
- Handler* handler_;
-};
-
-} // namespace fuzz
-} // namespace os
-} // namespace bluetooth
diff --git a/gd/os/handler.h b/gd/os/handler.h
index 9e530bc36..d9dea0ba1 100644
--- a/gd/os/handler.h
+++ b/gd/os/handler.h
@@ -21,9 +21,7 @@
#include <mutex>
#include <queue>
-#include "common/bind.h"
#include "common/callback.h"
-#include "common/contextual_callback.h"
#include "os/thread.h"
#include "os/utils.h"
@@ -33,18 +31,18 @@ namespace os {
// A message-queue style handler for reactor-based thread to handle incoming events from different threads. When it's
// constructed, it will register a reactable on the specified thread; when it's destroyed, it will unregister itself
// from the thread.
-class Handler : public common::IPostableContext {
+class Handler {
public:
// Create and register a handler on given thread
explicit Handler(Thread* thread);
// Unregister this handler from the thread and release resource. Unhandled events will be discarded and not executed.
- virtual ~Handler();
+ ~Handler();
DISALLOW_COPY_AND_ASSIGN(Handler);
// Enqueue a closure to the queue of this handler
- virtual void Post(common::OnceClosure closure) override;
+ void Post(OnceClosure closure);
// Remove all pending events from the queue of this handler
void Clear();
@@ -52,43 +50,6 @@ class Handler : public common::IPostableContext {
// Die if the current reactable doesn't stop before the timeout. Must be called after Clear()
void WaitUntilStopped(std::chrono::milliseconds timeout);
- template <typename Functor, typename... Args>
- void Call(Functor&& functor, Args&&... args) {
- Post(common::BindOnce(std::forward<Functor>(functor), std::forward<Args>(args)...));
- }
-
- template <typename T, typename Functor, typename... Args>
- void CallOn(T* obj, Functor&& functor, Args&&... args) {
- Post(common::BindOnce(std::forward<Functor>(functor), common::Unretained(obj), std::forward<Args>(args)...));
- }
-
- template <typename Functor, typename... Args>
- common::ContextualOnceCallback<common::MakeUnboundRunType<Functor, Args...>> BindOnce(
- Functor&& functor, Args&&... args) {
- return common::ContextualOnceCallback<common::MakeUnboundRunType<Functor, Args...>>(
- common::BindOnce(std::forward<Functor>(functor), std::forward<Args>(args)...), this);
- }
-
- template <typename Functor, typename T, typename... Args>
- common::ContextualOnceCallback<common::MakeUnboundRunType<Functor, T, Args...>> BindOnceOn(
- T* obj, Functor&& functor, Args&&... args) {
- return common::ContextualOnceCallback<common::MakeUnboundRunType<Functor, T, Args...>>(
- common::BindOnce(std::forward<Functor>(functor), common::Unretained(obj), std::forward<Args>(args)...), this);
- }
-
- template <typename Functor, typename... Args>
- common::ContextualCallback<common::MakeUnboundRunType<Functor, Args...>> Bind(Functor&& functor, Args&&... args) {
- return common::ContextualCallback<common::MakeUnboundRunType<Functor, Args...>>(
- common::Bind(std::forward<Functor>(functor), std::forward<Args>(args)...), this);
- }
-
- template <typename Functor, typename T, typename... Args>
- common::ContextualCallback<common::MakeUnboundRunType<Functor, T, Args...>> BindOn(
- T* obj, Functor&& functor, Args&&... args) {
- return common::ContextualCallback<common::MakeUnboundRunType<Functor, T, Args...>>(
- common::Bind(std::forward<Functor>(functor), common::Unretained(obj), std::forward<Args>(args)...), this);
- }
-
template <typename T>
friend class Queue;
@@ -100,7 +61,7 @@ class Handler : public common::IPostableContext {
inline bool was_cleared() const {
return tasks_ == nullptr;
};
- std::queue<common::OnceClosure>* tasks_;
+ std::queue<OnceClosure>* tasks_;
Thread* thread_;
int fd_;
Reactor::Reactable* reactable_;
diff --git a/gd/os/host/metrics.cc b/gd/os/host/metrics.cc
deleted file mode 100644
index 925466dbb..000000000
--- a/gd/os/host/metrics.cc
+++ /dev/null
@@ -1,106 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#include "os/metrics.h"
-#include "os/log.h"
-
-namespace bluetooth {
-namespace os {
-
-using bluetooth::hci::Address;
-
-void LogMetricClassicPairingEvent(
- const Address& address,
- uint16_t handle,
- uint32_t hci_cmd,
- uint16_t hci_event,
- uint16_t cmd_status,
- uint16_t reason_code,
- int64_t event_value) {}
-
-void LogMetricSocketConnectionState(
- const Address& address,
- int port,
- int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes,
- int64_t rx_bytes,
- int uid,
- int server_port,
- android::bluetooth::SocketRoleEnum socket_role) {}
-
-void LogMetricHciTimeoutEvent(uint32_t hci_cmd) {}
-
-void LogMetricA2dpAudioUnderrunEvent(
- const Address& address, uint64_t encoding_interval_millis, int num_missing_pcm_bytes) {}
-
-void LogMetricA2dpAudioOverrunEvent(
- const Address& address,
- uint64_t encoding_interval_millis,
- int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes) {}
-
-void LogMetricReadRssiResult(const Address& address, uint16_t handle, uint32_t cmd_status, int8_t rssi) {}
-
-void LogMetricReadFailedContactCounterResult(
- const Address& address, uint16_t handle, uint32_t cmd_status, int32_t failed_contact_counter) {}
-
-void LogMetricReadTxPowerLevelResult(
- const Address& address, uint16_t handle, uint32_t cmd_status, int32_t transmit_power_level) {}
-
-void LogMetricRemoteVersionInfo(
- uint16_t handle, uint8_t status, uint8_t version, uint16_t manufacturer_name, uint16_t subversion) {}
-
-void LogMetricLinkLayerConnectionEvent(
- const Address* address,
- uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction,
- uint16_t link_type,
- uint32_t hci_cmd,
- uint16_t hci_event,
- uint16_t hci_ble_event,
- uint16_t cmd_status,
- uint16_t reason_code) {}
-
-void LogMetricManufacturerInfo(
- const Address& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer,
- const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version) {}
-
-void LogMetricSdpAttribute(
- const Address& address,
- uint16_t protocol_uuid,
- uint16_t attribute_id,
- size_t attribute_size,
- const char* attribute_value) {}
-
-void LogMetricSmpPairingEvent(
- const Address& address, uint8_t smp_cmd, android::bluetooth::DirectionEnum direction, uint8_t smp_fail_reason) {}
-
-void LogMetricA2dpPlaybackEvent(const Address& address, int playback_state, int audio_coding_mode) {}
-
-void LogMetricBluetoothHalCrashReason(
- const Address& address, uint32_t error_code, uint32_t vendor_error_code) {}
-
-} // namespace os
-} // namespace bluetooth
diff --git a/gd/os/host/parameter_provider.cc b/gd/os/host/parameter_provider.cc
deleted file mode 100644
index 2220f940e..000000000
--- a/gd/os/host/parameter_provider.cc
+++ /dev/null
@@ -1,100 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "os/parameter_provider.h"
-
-#include <unistd.h>
-
-#include <cerrno>
-#include <mutex>
-#include <string>
-
-#include "os/log.h"
-
-namespace bluetooth {
-namespace os {
-
-namespace {
-std::mutex parameter_mutex;
-std::string config_file_path;
-std::string snoop_log_file_path;
-std::string snooz_log_file_path;
-} // namespace
-
-// Write to $PWD/bt_stack.conf if $PWD can be found, otherwise, write to $HOME/bt_stack.conf
-std::string ParameterProvider::ConfigFilePath() {
- {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- if (!config_file_path.empty()) {
- return config_file_path;
- }
- }
- char cwd[PATH_MAX] = {};
- if (getcwd(cwd, sizeof(cwd)) == nullptr) {
- LOG_ERROR("Failed to get current working directory due to \"%s\", returning default", strerror(errno));
- return "bt_config.conf";
- }
- return std::string(cwd) + "/bt_config.conf";
-}
-
-void ParameterProvider::OverrideConfigFilePath(const std::string& path) {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- config_file_path = path;
-}
-
-std::string ParameterProvider::SnoopLogFilePath() {
- {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- if (!snoop_log_file_path.empty()) {
- return snoop_log_file_path;
- }
- }
- char cwd[PATH_MAX] = {};
- if (getcwd(cwd, sizeof(cwd)) == nullptr) {
- LOG_ERROR("Failed to get current working directory due to \"%s\", returning default", strerror(errno));
- return "btsnoop_hci.log";
- }
- return std::string(cwd) + "/btsnoop_hci.log";
-}
-
-void ParameterProvider::OverrideSnoopLogFilePath(const std::string& path) {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- snoop_log_file_path = path;
-}
-
-// Return the path to the default snooz log file location
-std::string ParameterProvider::SnoozLogFilePath() {
- {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- if (!snooz_log_file_path.empty()) {
- return snooz_log_file_path;
- }
- }
- char cwd[PATH_MAX] = {};
- if (getcwd(cwd, sizeof(cwd)) == nullptr) {
- LOG_ERROR("Failed to get current working directory due to \"%s\", returning default", strerror(errno));
- return "bt_config.conf";
- }
- return std::string(cwd) + "/btsnooz_hci.log";
-}
-
-void ParameterProvider::OverrideSnoozLogFilePath(const std::string& path) {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- snooz_log_file_path = path;
-}
-
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/host/system_properties.cc b/gd/os/host/system_properties.cc
deleted file mode 100644
index 0b786868c..000000000
--- a/gd/os/host/system_properties.cc
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "os/system_properties.h"
-
-#include <mutex>
-#include <string>
-#include <unordered_map>
-
-namespace bluetooth {
-namespace os {
-
-namespace {
-std::mutex properties_mutex;
-std::unordered_map<std::string, std::string> properties;
-} // namespace
-
-std::optional<std::string> GetSystemProperty(const std::string& property) {
- std::lock_guard<std::mutex> lock(properties_mutex);
- auto iter = properties.find(property);
- if (iter == properties.end()) {
- return std::nullopt;
- }
- return iter->second;
-}
-
-bool SetSystemProperty(const std::string& property, const std::string& value) {
- std::lock_guard<std::mutex> lock(properties_mutex);
- properties.insert_or_assign(property, value);
- return true;
-}
-
-void ClearSystemPropertiesForHost() {
- std::lock_guard<std::mutex> lock(properties_mutex);
- properties.clear();
-}
-
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/host/system_properties_test.cc b/gd/os/host/system_properties_test.cc
deleted file mode 100644
index d88cb9a80..000000000
--- a/gd/os/host/system_properties_test.cc
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <string>
-
-#include <gtest/gtest.h>
-
-#include "os/system_properties.h"
-
-namespace testing {
-
-using bluetooth::os::ClearSystemPropertiesForHost;
-using bluetooth::os::GetSystemProperty;
-using bluetooth::os::SetSystemProperty;
-
-TEST(SystemPropertiesTest, set_and_get_test) {
- ASSERT_TRUE(SetSystemProperty("persist.bluetooth.factoryreset", "true"));
- auto ret = GetSystemProperty("persist.bluetooth.factoryreset");
- ASSERT_TRUE(ret);
- ASSERT_EQ(ret, "true");
- ASSERT_TRUE(SetSystemProperty("persist.bluetooth.factoryreset", "false"));
- ret = GetSystemProperty("persist.bluetooth.factoryreset");
- ASSERT_TRUE(ret);
- ASSERT_EQ(ret, "false");
- ret = GetSystemProperty("persist.bluetooth.factoryreset_do_not_exist");
- ASSERT_FALSE(ret);
- ClearSystemPropertiesForHost();
- ASSERT_FALSE(GetSystemProperty("persist.bluetooth.factoryreset"));
-}
-
-} // namespace testing \ No newline at end of file
diff --git a/gd/os/host/wakelock_native.cc b/gd/os/host/wakelock_native.cc
deleted file mode 100644
index f173cf4fc..000000000
--- a/gd/os/host/wakelock_native.cc
+++ /dev/null
@@ -1,53 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#define LOG_TAG "BtGdWakelockNative"
-
-#include "os/internal/wakelock_native.h"
-#include "os/log.h"
-
-namespace bluetooth {
-namespace os {
-namespace internal {
-
-struct WakelockNative::Impl {};
-
-void WakelockNative::Initialize() {
- LOG_INFO("Host native wakelock is not implemented");
-}
-
-WakelockNative::StatusCode WakelockNative::Acquire(const std::string& lock_name) {
- LOG_INFO("Host native wakelock is not implemented");
- return StatusCode::SUCCESS;
-}
-
-WakelockNative::StatusCode WakelockNative::Release(const std::string& lock_name) {
- LOG_INFO("Host native wakelock is not implemented");
- return StatusCode::SUCCESS;
-}
-void WakelockNative::CleanUp() {
- LOG_INFO("Host native wakelock is not implemented");
-}
-
-WakelockNative::WakelockNative() : pimpl_(std::make_unique<Impl>()) {}
-
-WakelockNative::~WakelockNative() = default;
-
-} // namespace internal
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/internal/wakelock_native.h b/gd/os/internal/wakelock_native.h
deleted file mode 100644
index acbd6ce85..000000000
--- a/gd/os/internal/wakelock_native.h
+++ /dev/null
@@ -1,51 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#pragma once
-
-#include <memory>
-
-namespace bluetooth {
-namespace os {
-namespace internal {
-
-// DO NOT USE OUTSIDE os/
-// Native wakelock APIs implemented by each architecture, not public APIs
-class WakelockNative {
- public:
- static WakelockNative& Get() {
- static WakelockNative instance;
- return instance;
- }
- enum StatusCode : uint8_t { SUCCESS = 0, NATIVE_SERVICE_NOT_AVAILABLE = 1, NATIVE_API_ERROR = 2 };
- void Initialize();
- StatusCode Acquire(const std::string& lock_name);
- StatusCode Release(const std::string& lock_name);
- void CleanUp();
-
- ~WakelockNative();
-
- private:
- WakelockNative();
- struct Impl;
- std::unique_ptr<Impl> pimpl_;
-};
-
-} // namespace internal
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/linux/metrics.cc b/gd/os/linux/metrics.cc
deleted file mode 100644
index 925466dbb..000000000
--- a/gd/os/linux/metrics.cc
+++ /dev/null
@@ -1,106 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#include "os/metrics.h"
-#include "os/log.h"
-
-namespace bluetooth {
-namespace os {
-
-using bluetooth::hci::Address;
-
-void LogMetricClassicPairingEvent(
- const Address& address,
- uint16_t handle,
- uint32_t hci_cmd,
- uint16_t hci_event,
- uint16_t cmd_status,
- uint16_t reason_code,
- int64_t event_value) {}
-
-void LogMetricSocketConnectionState(
- const Address& address,
- int port,
- int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes,
- int64_t rx_bytes,
- int uid,
- int server_port,
- android::bluetooth::SocketRoleEnum socket_role) {}
-
-void LogMetricHciTimeoutEvent(uint32_t hci_cmd) {}
-
-void LogMetricA2dpAudioUnderrunEvent(
- const Address& address, uint64_t encoding_interval_millis, int num_missing_pcm_bytes) {}
-
-void LogMetricA2dpAudioOverrunEvent(
- const Address& address,
- uint64_t encoding_interval_millis,
- int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes) {}
-
-void LogMetricReadRssiResult(const Address& address, uint16_t handle, uint32_t cmd_status, int8_t rssi) {}
-
-void LogMetricReadFailedContactCounterResult(
- const Address& address, uint16_t handle, uint32_t cmd_status, int32_t failed_contact_counter) {}
-
-void LogMetricReadTxPowerLevelResult(
- const Address& address, uint16_t handle, uint32_t cmd_status, int32_t transmit_power_level) {}
-
-void LogMetricRemoteVersionInfo(
- uint16_t handle, uint8_t status, uint8_t version, uint16_t manufacturer_name, uint16_t subversion) {}
-
-void LogMetricLinkLayerConnectionEvent(
- const Address* address,
- uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction,
- uint16_t link_type,
- uint32_t hci_cmd,
- uint16_t hci_event,
- uint16_t hci_ble_event,
- uint16_t cmd_status,
- uint16_t reason_code) {}
-
-void LogMetricManufacturerInfo(
- const Address& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer,
- const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version) {}
-
-void LogMetricSdpAttribute(
- const Address& address,
- uint16_t protocol_uuid,
- uint16_t attribute_id,
- size_t attribute_size,
- const char* attribute_value) {}
-
-void LogMetricSmpPairingEvent(
- const Address& address, uint8_t smp_cmd, android::bluetooth::DirectionEnum direction, uint8_t smp_fail_reason) {}
-
-void LogMetricA2dpPlaybackEvent(const Address& address, int playback_state, int audio_coding_mode) {}
-
-void LogMetricBluetoothHalCrashReason(
- const Address& address, uint32_t error_code, uint32_t vendor_error_code) {}
-
-} // namespace os
-} // namespace bluetooth
diff --git a/gd/os/linux/parameter_provider.cc b/gd/os/linux/parameter_provider.cc
deleted file mode 100644
index 9f0a844f1..000000000
--- a/gd/os/linux/parameter_provider.cc
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "os/parameter_provider.h"
-
-#include <unistd.h>
-
-#include <cerrno>
-#include <mutex>
-#include <string>
-
-#include "os/log.h"
-
-namespace bluetooth {
-namespace os {
-
-namespace {
-std::mutex parameter_mutex;
-std::string config_file_path;
-std::string snoop_log_file_path;
-std::string snooz_log_file_path;
-} // namespace
-
-// Write to $PWD/bt_stack.conf if $PWD can be found, otherwise, write to $HOME/bt_stack.conf
-std::string ParameterProvider::ConfigFilePath() {
- {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- if (!config_file_path.empty()) {
- return config_file_path;
- }
- }
- return "/etc/bluetooth/bt_config.conf";
-}
-
-void ParameterProvider::OverrideConfigFilePath(const std::string& path) {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- config_file_path = path;
-}
-
-std::string ParameterProvider::SnoopLogFilePath() {
- {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- if (!snoop_log_file_path.empty()) {
- return snoop_log_file_path;
- }
- }
-
- return "/etc/bluetooth/btsnoop_hci.log";
-}
-
-void ParameterProvider::OverrideSnoopLogFilePath(const std::string& path) {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- snoop_log_file_path = path;
-}
-
-std::string ParameterProvider::SnoozLogFilePath() {
- {
- std::lock_guard<std::mutex> lock(parameter_mutex);
- if (!snooz_log_file_path.empty()) {
- return snooz_log_file_path;
- }
- }
- return "/etc/bluetooth/btsnooz_hci.log";
-}
-
-} // namespace os
-} // namespace bluetooth
diff --git a/gd/os/linux/system_properties.cc b/gd/os/linux/system_properties.cc
deleted file mode 100644
index 0b786868c..000000000
--- a/gd/os/linux/system_properties.cc
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "os/system_properties.h"
-
-#include <mutex>
-#include <string>
-#include <unordered_map>
-
-namespace bluetooth {
-namespace os {
-
-namespace {
-std::mutex properties_mutex;
-std::unordered_map<std::string, std::string> properties;
-} // namespace
-
-std::optional<std::string> GetSystemProperty(const std::string& property) {
- std::lock_guard<std::mutex> lock(properties_mutex);
- auto iter = properties.find(property);
- if (iter == properties.end()) {
- return std::nullopt;
- }
- return iter->second;
-}
-
-bool SetSystemProperty(const std::string& property, const std::string& value) {
- std::lock_guard<std::mutex> lock(properties_mutex);
- properties.insert_or_assign(property, value);
- return true;
-}
-
-void ClearSystemPropertiesForHost() {
- std::lock_guard<std::mutex> lock(properties_mutex);
- properties.clear();
-}
-
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/linux/system_properties_test.cc b/gd/os/linux/system_properties_test.cc
deleted file mode 100644
index d88cb9a80..000000000
--- a/gd/os/linux/system_properties_test.cc
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <string>
-
-#include <gtest/gtest.h>
-
-#include "os/system_properties.h"
-
-namespace testing {
-
-using bluetooth::os::ClearSystemPropertiesForHost;
-using bluetooth::os::GetSystemProperty;
-using bluetooth::os::SetSystemProperty;
-
-TEST(SystemPropertiesTest, set_and_get_test) {
- ASSERT_TRUE(SetSystemProperty("persist.bluetooth.factoryreset", "true"));
- auto ret = GetSystemProperty("persist.bluetooth.factoryreset");
- ASSERT_TRUE(ret);
- ASSERT_EQ(ret, "true");
- ASSERT_TRUE(SetSystemProperty("persist.bluetooth.factoryreset", "false"));
- ret = GetSystemProperty("persist.bluetooth.factoryreset");
- ASSERT_TRUE(ret);
- ASSERT_EQ(ret, "false");
- ret = GetSystemProperty("persist.bluetooth.factoryreset_do_not_exist");
- ASSERT_FALSE(ret);
- ClearSystemPropertiesForHost();
- ASSERT_FALSE(GetSystemProperty("persist.bluetooth.factoryreset"));
-}
-
-} // namespace testing \ No newline at end of file
diff --git a/gd/os/linux/wakelock_native.cc b/gd/os/linux/wakelock_native.cc
deleted file mode 100644
index b98d75caa..000000000
--- a/gd/os/linux/wakelock_native.cc
+++ /dev/null
@@ -1,53 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#define LOG_TAG "BtGdWakelockNative"
-
-#include "os/internal/wakelock_native.h"
-#include "os/log.h"
-
-namespace bluetooth {
-namespace os {
-namespace internal {
-
-struct WakelockNative::Impl {};
-
-void WakelockNative::Initialize() {
- LOG_INFO("Linux native wakelock is not implemented");
-}
-
-WakelockNative::StatusCode WakelockNative::Acquire(const std::string& lock_name) {
- LOG_INFO("Linux native wakelock is not implemented");
- return StatusCode::SUCCESS;
-}
-
-WakelockNative::StatusCode WakelockNative::Release(const std::string& lock_name) {
- LOG_INFO("Linux native wakelock is not implemented");
- return StatusCode::SUCCESS;
-}
-void WakelockNative::CleanUp() {
- LOG_INFO("Linux native wakelock is not implemented");
-}
-
-WakelockNative::WakelockNative() : pimpl_(std::make_unique<Impl>()) {}
-
-WakelockNative::~WakelockNative() = default;
-
-} // namespace internal
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/linux_generic/alarm.cc b/gd/os/linux_generic/alarm.cc
index cd859b5fe..a2d895e0c 100644
--- a/gd/os/linux_generic/alarm.cc
+++ b/gd/os/linux_generic/alarm.cc
@@ -17,12 +17,10 @@
#include "os/alarm.h"
#include <sys/timerfd.h>
-#include <unistd.h>
-
#include <cstring>
+#include <unistd.h>
#include "common/bind.h"
-#include "os/linux_generic/linux.h"
#include "os/log.h"
#include "os/utils.h"
@@ -34,29 +32,30 @@
namespace bluetooth {
namespace os {
-using common::Closure;
-using common::OnceClosure;
-Alarm::Alarm(Handler* handler) : handler_(handler), fd_(TIMERFD_CREATE(ALARM_CLOCK, 0)) {
+Alarm::Alarm(Handler* handler) : handler_(handler), fd_(timerfd_create(ALARM_CLOCK, 0)) {
ASSERT_LOG(fd_ != -1, "cannot create timerfd: %s", strerror(errno));
- token_ = handler_->thread_->GetReactor()->Register(
- fd_, common::Bind(&Alarm::on_fire, common::Unretained(this)), Closure());
+ token_ = handler_->thread_->GetReactor()->Register(fd_, common::Bind(&Alarm::on_fire, common::Unretained(this)),
+ Closure());
}
Alarm::~Alarm() {
handler_->thread_->GetReactor()->Unregister(token_);
int close_status;
- RUN_NO_INTR(close_status = TIMERFD_CLOSE(fd_));
+ RUN_NO_INTR(close_status = close(fd_));
ASSERT(close_status != -1);
}
void Alarm::Schedule(OnceClosure task, std::chrono::milliseconds delay) {
std::lock_guard<std::mutex> lock(mutex_);
long delay_ms = delay.count();
- itimerspec timer_itimerspec{{/* interval for periodic timer */}, {delay_ms / 1000, delay_ms % 1000 * 1000000}};
- int result = TIMERFD_SETTIME(fd_, 0, &timer_itimerspec, nullptr);
+ itimerspec timer_itimerspec{
+ {/* interval for periodic timer */},
+ {delay_ms / 1000, delay_ms % 1000 * 1000000}
+ };
+ int result = timerfd_settime(fd_, 0, &timer_itimerspec, nullptr);
ASSERT(result == 0);
task_ = std::move(task);
@@ -65,7 +64,7 @@ void Alarm::Schedule(OnceClosure task, std::chrono::milliseconds delay) {
void Alarm::Cancel() {
std::lock_guard<std::mutex> lock(mutex_);
itimerspec disarm_itimerspec{/* disarm timer */};
- int result = TIMERFD_SETTIME(fd_, 0, &disarm_itimerspec, nullptr);
+ int result = timerfd_settime(fd_, 0, &disarm_itimerspec, nullptr);
ASSERT(result == 0);
}
diff --git a/gd/os/linux_generic/alarm_unittest.cc b/gd/os/linux_generic/alarm_unittest.cc
index 9b4a5e554..b389a8207 100644
--- a/gd/os/linux_generic/alarm_unittest.cc
+++ b/gd/os/linux_generic/alarm_unittest.cc
@@ -58,8 +58,8 @@ TEST_F(AlarmTest, schedule) {
auto before = std::chrono::steady_clock::now();
int delay_ms = 10;
int delay_error_ms = 3;
- alarm_->Schedule(
- BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)), std::chrono::milliseconds(delay_ms));
+ alarm_->Schedule(BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)),
+ std::chrono::milliseconds(delay_ms));
future.get();
auto after = std::chrono::steady_clock::now();
auto duration_ms = std::chrono::duration_cast<std::chrono::milliseconds>(after - before);
@@ -81,8 +81,8 @@ TEST_F(AlarmTest, schedule_while_alarm_armed) {
alarm_->Schedule(BindOnce([]() { ASSERT_TRUE(false) << "Should not happen"; }), std::chrono::milliseconds(1));
std::promise<void> promise;
auto future = promise.get_future();
- alarm_->Schedule(
- BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)), std::chrono::milliseconds(10));
+ alarm_->Schedule(BindOnce(&std::promise<void>::set_value, common::Unretained(&promise)),
+ std::chrono::milliseconds(10));
future.get();
}
diff --git a/gd/os/linux_generic/files.cc b/gd/os/linux_generic/files.cc
deleted file mode 100644
index bb018bf37..000000000
--- a/gd/os/linux_generic/files.cc
+++ /dev/null
@@ -1,199 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "os/files.h"
-
-#include <fcntl.h>
-#include <libgen.h>
-#include <sys/stat.h>
-#include <unistd.h>
-
-#include <cerrno>
-#include <cstring>
-#include <fstream>
-#include <streambuf>
-#include <string>
-
-#include "os/log.h"
-
-namespace {
-
-void HandleError(const std::string& temp_path, int* dir_fd, FILE** fp) {
- // This indicates there is a write issue. Unlink as partial data is not
- // acceptable.
- unlink(temp_path.c_str());
- if (*fp) {
- fclose(*fp);
- *fp = nullptr;
- }
- if (*dir_fd != -1) {
- close(*dir_fd);
- *dir_fd = -1;
- }
-}
-
-} // namespace
-
-namespace bluetooth {
-namespace os {
-
-bool FileExists(const std::string& path) {
- std::ifstream input(path, std::ios::binary | std::ios::ate);
- return input.good();
-}
-
-bool RenameFile(const std::string& from, const std::string& to) {
- if (std::rename(from.c_str(), to.c_str()) != 0) {
- LOG_ERROR("unable to rename file from '%s' to '%s', error: %s", from.c_str(), to.c_str(), strerror(errno));
- return false;
- }
- return true;
-}
-
-std::optional<std::string> ReadSmallFile(const std::string& path) {
- std::ifstream input(path, std::ios::binary | std::ios::ate);
- if (!input) {
- LOG_WARN("Failed to open file '%s', error: %s", path.c_str(), strerror(errno));
- return std::nullopt;
- }
- auto file_size = input.tellg();
- if (file_size < 0) {
- LOG_WARN("Failed to get file size for '%s', error: %s", path.c_str(), strerror(errno));
- return std::nullopt;
- }
- std::string result(file_size, '\0');
- if (!input.seekg(0)) {
- LOG_WARN("Failed to go back to the beginning of file '%s', error: %s", path.c_str(), strerror(errno));
- return std::nullopt;
- }
- if (!input.read(result.data(), result.size())) {
- LOG_WARN("Failed to read file '%s', error: %s", path.c_str(), strerror(errno));
- return std::nullopt;
- }
- input.close();
- return result;
-}
-
-bool WriteToFile(const std::string& path, const std::string& data) {
- ASSERT(!path.empty());
- // Steps to ensure content of data gets to disk:
- //
- // 1) Open and write to temp file (e.g. bt_config.conf.new).
- // 2) Flush the stream buffer to the temp file.
- // 3) Sync the temp file to disk with fsync().
- // 4) Rename temp file to actual config file (e.g. bt_config.conf).
- // This ensures atomic update.
- // 5) Sync directory that has the conf file with fsync().
- // This ensures directory entries are up-to-date.
- //
- // We are using traditional C type file methods because C++ std::filesystem and std::ofstream do not support:
- // - Operation on directories
- // - fsync() to ensure content is written to disk
-
- // Build temp config file based on config file (e.g. bt_config.conf.new).
- const std::string temp_path = path + ".new";
-
- // Extract directory from file path (e.g. /data/misc/bluedroid).
- // libc++fs is not supported in APEX yet and hence cannot use std::filesystem::path::parent_path
- std::string directory_path;
- {
- // Make a temporary variable as inputs to dirname() will be modified and return value points to input char array
- // temp_path_for_dir must not be destroyed until results from dirname is appended to directory_path
- std::string temp_path_for_dir(path);
- directory_path.append(dirname(temp_path_for_dir.data()));
- }
- if (directory_path.empty()) {
- LOG_ERROR("error extracting directory from '%s', error: %s", path.c_str(), strerror(errno));
- return false;
- }
-
- int dir_fd = open(directory_path.c_str(), O_RDONLY | O_DIRECTORY);
- if (dir_fd < 0) {
- LOG_ERROR("unable to open dir '%s', error: %s", directory_path.c_str(), strerror(errno));
- return false;
- }
-
- FILE* fp = std::fopen(temp_path.c_str(), "wt");
- if (!fp) {
- LOG_ERROR("unable to write to file '%s', error: %s", temp_path.c_str(), strerror(errno));
- HandleError(temp_path, &dir_fd, &fp);
- return false;
- }
-
- if (std::fprintf(fp, "%s", data.c_str()) < 0) {
- LOG_ERROR("unable to write to file '%s', error: %s", temp_path.c_str(), strerror(errno));
- HandleError(temp_path, &dir_fd, &fp);
- return false;
- }
-
- // Flush the stream buffer to the temp file.
- if (std::fflush(fp) != 0) {
- LOG_ERROR("unable to write flush buffer to file '%s', error: %s", temp_path.c_str(), strerror(errno));
- HandleError(temp_path, &dir_fd, &fp);
- return false;
- }
-
- // Sync written temp file out to disk. fsync() is blocking until data makes it
- // to disk.
- if (fsync(fileno(fp)) != 0) {
- LOG_WARN("unable to fsync file '%s', error: %s", temp_path.c_str(), strerror(errno));
- // Allow fsync to fail and continue
- }
-
- if (std::fclose(fp) != 0) {
- LOG_ERROR("unable to close file '%s', error: %s", temp_path.c_str(), strerror(errno));
- HandleError(temp_path, &dir_fd, &fp);
- return false;
- }
- fp = nullptr;
-
- // Change the file's permissions to Read/Write by User and Group
- if (chmod(temp_path.c_str(), S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP) != 0) {
- LOG_ERROR("unable to change file permissions '%s', error: %s", temp_path.c_str(), strerror(errno));
- HandleError(temp_path, &dir_fd, &fp);
- return false;
- }
-
- // Rename written temp file to the actual config file.
- if (std::rename(temp_path.c_str(), path.c_str()) != 0) {
- LOG_ERROR("unable to commit file from '%s' to '%s', error: %s", temp_path.c_str(), path.c_str(), strerror(errno));
- HandleError(temp_path, &dir_fd, &fp);
- return false;
- }
-
- // This should ensure the directory is updated as well.
- if (fsync(dir_fd) != 0) {
- LOG_WARN("unable to fsync dir '%s', error: %s", directory_path.c_str(), strerror(errno));
- }
-
- if (close(dir_fd) != 0) {
- LOG_ERROR("unable to close dir '%s', error: %s", directory_path.c_str(), strerror(errno));
- HandleError(temp_path, &dir_fd, &fp);
- return false;
- }
- return true;
-}
-
-bool RemoveFile(const std::string& path) {
- if (remove(path.c_str()) != 0) {
- LOG_ERROR("unable to remove file '%s', error: %s", path.c_str(), strerror(errno));
- return false;
- }
- return true;
-}
-
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/linux_generic/files_test.cc b/gd/os/linux_generic/files_test.cc
deleted file mode 100644
index 383083c45..000000000
--- a/gd/os/linux_generic/files_test.cc
+++ /dev/null
@@ -1,89 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "os/files.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include <filesystem>
-
-namespace testing {
-
-using bluetooth::os::FileExists;
-using bluetooth::os::ReadSmallFile;
-using bluetooth::os::RenameFile;
-using bluetooth::os::WriteToFile;
-
-TEST(FilesTest, exist_test) {
- auto temp_dir = std::filesystem::temp_directory_path();
- auto temp_file = temp_dir / "file_1.txt";
- std::string text = "Hello world!\n";
- ASSERT_TRUE(WriteToFile(temp_file.string(), text));
- EXPECT_TRUE(FileExists(temp_file.string()));
- auto none_file = temp_dir / "file_nope.txt";
- EXPECT_FALSE(FileExists(none_file.string()));
-}
-
-TEST(FilesTest, rename_test) {
- auto temp_dir = std::filesystem::temp_directory_path();
- auto temp_file = temp_dir / "file_1.txt";
- std::string text = "Hello world!\n";
- ASSERT_TRUE(WriteToFile(temp_file.string(), text));
- EXPECT_THAT(ReadSmallFile(temp_file.string()), Optional(StrEq(text)));
- auto to_file = temp_dir / "file_2.txt";
- ASSERT_TRUE(RenameFile(temp_file.string(), to_file.string()));
- EXPECT_FALSE(std::filesystem::exists(temp_file));
- EXPECT_THAT(ReadSmallFile(to_file.string()), Optional(StrEq(text)));
- // rename files that do not exist should return false
- ASSERT_FALSE(RenameFile(temp_file.string(), to_file.string()));
-}
-
-TEST(FilesTest, write_read_loopback_test) {
- auto temp_dir = std::filesystem::temp_directory_path();
- auto temp_file = temp_dir / "file_1.txt";
- std::string text = "Hello world!\n";
- ASSERT_TRUE(WriteToFile(temp_file.string(), text));
- EXPECT_THAT(ReadSmallFile(temp_file.string()), Optional(StrEq(text)));
- EXPECT_TRUE(std::filesystem::remove(temp_file));
-}
-
-TEST(FilesTest, overwrite_test) {
- auto temp_dir = std::filesystem::temp_directory_path();
- auto temp_file = temp_dir / "file_1.txt";
- std::string text = "Hello world!\n";
- ASSERT_TRUE(WriteToFile(temp_file.string(), text));
- EXPECT_THAT(ReadSmallFile(temp_file.string()), Optional(StrEq(text)));
- text = "Foo bar!\n";
- ASSERT_TRUE(WriteToFile(temp_file.string(), text));
- EXPECT_THAT(ReadSmallFile(temp_file.string()), Optional(StrEq(text)));
- EXPECT_TRUE(std::filesystem::remove(temp_file));
-}
-
-TEST(FilesTest, write_read_empty_string_test) {
- auto temp_dir = std::filesystem::temp_directory_path();
- auto temp_file = temp_dir / "file_1.txt";
- std::string text;
- ASSERT_TRUE(WriteToFile(temp_file.string(), text));
- EXPECT_THAT(ReadSmallFile(temp_file.string()), Optional(StrEq(text)));
- EXPECT_TRUE(std::filesystem::remove(temp_file));
-}
-
-TEST(FilesTest, read_non_existing_file_test) {
- EXPECT_FALSE(ReadSmallFile("/woof"));
-}
-
-} // namespace testing \ No newline at end of file
diff --git a/gd/os/linux_generic/handler.cc b/gd/os/linux_generic/handler.cc
index 2f996f91e..85cbcc3d4 100644
--- a/gd/os/linux_generic/handler.cc
+++ b/gd/os/linux_generic/handler.cc
@@ -18,7 +18,6 @@
#include <sys/eventfd.h>
#include <unistd.h>
-
#include <cstring>
#include "common/bind.h"
@@ -33,13 +32,12 @@
namespace bluetooth {
namespace os {
-using common::OnceClosure;
Handler::Handler(Thread* thread)
: tasks_(new std::queue<OnceClosure>()), thread_(thread), fd_(eventfd(0, EFD_SEMAPHORE | EFD_NONBLOCK)) {
ASSERT(fd_ != -1);
- reactable_ = thread_->GetReactor()->Register(
- fd_, common::Bind(&Handler::handle_next_event, common::Unretained(this)), common::Closure());
+ reactable_ = thread_->GetReactor()->Register(fd_, common::Bind(&Handler::handle_next_event, common::Unretained(this)),
+ common::Closure());
}
Handler::~Handler() {
@@ -57,7 +55,6 @@ void Handler::Post(OnceClosure closure) {
{
std::lock_guard<std::mutex> lock(mutex_);
if (was_cleared()) {
- LOG_WARN("Posting to a handler which has been cleared");
return;
}
tasks_->emplace(std::move(closure));
diff --git a/gd/os/linux_generic/handler_unittest.cc b/gd/os/linux_generic/handler_unittest.cc
index cea030ef1..80456db98 100644
--- a/gd/os/linux_generic/handler_unittest.cc
+++ b/gd/os/linux_generic/handler_unittest.cc
@@ -17,7 +17,6 @@
#include "os/handler.h"
#include <sys/eventfd.h>
-
#include <future>
#include <thread>
@@ -53,13 +52,12 @@ TEST_F(HandlerTest, post_task_invoked) {
int val = 0;
std::promise<void> closure_ran;
auto future = closure_ran.get_future();
- common::OnceClosure closure = common::BindOnce(
+ OnceClosure closure = common::BindOnce(
[](int* val, std::promise<void> closure_ran) {
*val = *val + 1;
closure_ran.set_value();
},
- common::Unretained(&val),
- std::move(closure_ran));
+ common::Unretained(&val), std::move(closure_ran));
handler_->Post(std::move(closure));
future.wait();
ASSERT_EQ(val, 1);
@@ -78,9 +76,7 @@ TEST_F(HandlerTest, post_task_cleared) {
*val = *val + 1;
can_continue_future.wait();
},
- common::Unretained(&val),
- std::move(closure_started),
- std::move(can_continue_future)));
+ common::Unretained(&val), std::move(closure_started), std::move(can_continue_future)));
handler_->Post(common::BindOnce([]() { ASSERT_TRUE(false); }));
closure_started_future.wait();
handler_->Clear();
diff --git a/gd/os/linux_generic/linux.h b/gd/os/linux_generic/linux.h
index 69fae6a55..524aa7d76 100644
--- a/gd/os/linux_generic/linux.h
+++ b/gd/os/linux_generic/linux.h
@@ -19,14 +19,3 @@
#ifndef EFD_SEMAPHORE
#define EFD_SEMAPHORE 1
#endif
-
-#ifdef FUZZ_TARGET
-#include "os/fuzz/fake_timerfd.h"
-#define TIMERFD_CREATE ::bluetooth::os::fuzz::fake_timerfd_create
-#define TIMERFD_SETTIME ::bluetooth::os::fuzz::fake_timerfd_settime
-#define TIMERFD_CLOSE ::bluetooth::os::fuzz::fake_timerfd_close
-#else
-#define TIMERFD_CREATE timerfd_create
-#define TIMERFD_SETTIME timerfd_settime
-#define TIMERFD_CLOSE close
-#endif
diff --git a/gd/os/linux_generic/queue.tpp b/gd/os/linux_generic/queue.tpp
index 24113b125..bd9a29297 100644
--- a/gd/os/linux_generic/queue.tpp
+++ b/gd/os/linux_generic/queue.tpp
@@ -19,8 +19,8 @@ Queue<T>::Queue(size_t capacity) : enqueue_(capacity), dequeue_(0){};
template <typename T>
Queue<T>::~Queue() {
- ASSERT_LOG(enqueue_.handler_ == nullptr, "Enqueue is not unregistered");
- ASSERT_LOG(dequeue_.handler_ == nullptr, "Dequeue is not unregistered");
+ ASSERT(enqueue_.handler_ == nullptr);
+ ASSERT(dequeue_.handler_ == nullptr);
};
template <typename T>
@@ -37,22 +37,11 @@ void Queue<T>::RegisterEnqueue(Handler* handler, EnqueueCallback callback) {
template <typename T>
void Queue<T>::UnregisterEnqueue() {
- Reactor* reactor = nullptr;
- Reactor::Reactable* to_unregister = nullptr;
- bool wait_for_unregister = false;
- {
- std::lock_guard<std::mutex> lock(mutex_);
- ASSERT(enqueue_.reactable_ != nullptr);
- reactor = enqueue_.handler_->thread_->GetReactor();
- wait_for_unregister = (!enqueue_.handler_->thread_->IsSameThread());
- to_unregister = enqueue_.reactable_;
- enqueue_.reactable_ = nullptr;
- enqueue_.handler_ = nullptr;
- }
- reactor->Unregister(to_unregister);
- if (wait_for_unregister) {
- reactor->WaitForUnregisteredReactable(std::chrono::milliseconds(1000));
- }
+ std::lock_guard<std::mutex> lock(mutex_);
+ ASSERT(enqueue_.reactable_ != nullptr);
+ enqueue_.handler_->thread_->GetReactor()->Unregister(enqueue_.reactable_);
+ enqueue_.reactable_ = nullptr;
+ enqueue_.handler_ = nullptr;
}
template <typename T>
@@ -61,28 +50,17 @@ void Queue<T>::RegisterDequeue(Handler* handler, DequeueCallback callback) {
ASSERT(dequeue_.handler_ == nullptr);
ASSERT(dequeue_.reactable_ == nullptr);
dequeue_.handler_ = handler;
- dequeue_.reactable_ = dequeue_.handler_->thread_->GetReactor()->Register(
- dequeue_.reactive_semaphore_.GetFd(), callback, base::Closure());
+ dequeue_.reactable_ = dequeue_.handler_->thread_->GetReactor()->Register(dequeue_.reactive_semaphore_.GetFd(),
+ callback, base::Closure());
}
template <typename T>
void Queue<T>::UnregisterDequeue() {
- Reactor* reactor = nullptr;
- Reactor::Reactable* to_unregister = nullptr;
- bool wait_for_unregister = false;
- {
- std::lock_guard<std::mutex> lock(mutex_);
- ASSERT(dequeue_.reactable_ != nullptr);
- reactor = dequeue_.handler_->thread_->GetReactor();
- wait_for_unregister = (!dequeue_.handler_->thread_->IsSameThread());
- to_unregister = dequeue_.reactable_;
- dequeue_.reactable_ = nullptr;
- dequeue_.handler_ = nullptr;
- }
- reactor->Unregister(to_unregister);
- if (wait_for_unregister) {
- reactor->WaitForUnregisteredReactable(std::chrono::milliseconds(1000));
- }
+ std::lock_guard<std::mutex> lock(mutex_);
+ ASSERT(dequeue_.reactable_ != nullptr);
+ dequeue_.handler_->thread_->GetReactor()->Unregister(dequeue_.reactable_);
+ dequeue_.reactable_ = nullptr;
+ dequeue_.handler_ = nullptr;
}
template <typename T>
diff --git a/gd/os/linux_generic/queue_unittest.cc b/gd/os/linux_generic/queue_unittest.cc
index 90f061ccd..f0ca2bd99 100644
--- a/gd/os/linux_generic/queue_unittest.cc
+++ b/gd/os/linux_generic/queue_unittest.cc
@@ -17,8 +17,6 @@
#include "os/queue.h"
#include <sys/eventfd.h>
-
-#include <atomic>
#include <future>
#include <unordered_map>
@@ -361,8 +359,8 @@ TEST_F(QueueTest, register_dequeue_with_half_empty_queue) {
// Register dequeue and expect data move to dequeue end buffer
std::unordered_map<int, std::promise<int>> dequeue_promise_map;
- dequeue_promise_map.emplace(
- std::piecewise_construct, std::forward_as_tuple(kHalfOfQueueSize), std::forward_as_tuple());
+ dequeue_promise_map.emplace(std::piecewise_construct, std::forward_as_tuple(kHalfOfQueueSize),
+ std::forward_as_tuple());
auto dequeue_future = dequeue_promise_map[kHalfOfQueueSize].get_future();
test_dequeue_end.RegisterDequeue(&dequeue_promise_map);
dequeue_future.wait();
@@ -420,15 +418,15 @@ TEST_F(QueueTest, queue_becomes_full_dequeue_callback_unregister) {
// Register dequeue
std::unordered_map<int, std::promise<int>> dequeue_promise_map;
- dequeue_promise_map.emplace(
- std::piecewise_construct, std::forward_as_tuple(kHalfOfQueueSize), std::forward_as_tuple());
+ dequeue_promise_map.emplace(std::piecewise_construct, std::forward_as_tuple(kHalfOfQueueSize),
+ std::forward_as_tuple());
auto dequeue_future = dequeue_promise_map[kHalfOfQueueSize].get_future();
test_dequeue_end.RegisterDequeue(&dequeue_promise_map);
// Register enqueue
std::unordered_map<int, std::promise<int>> enqueue_promise_map;
- enqueue_promise_map.emplace(
- std::piecewise_construct, std::forward_as_tuple(kHalfOfQueueSize), std::forward_as_tuple());
+ enqueue_promise_map.emplace(std::piecewise_construct, std::forward_as_tuple(kHalfOfQueueSize),
+ std::forward_as_tuple());
auto enqueue_future = enqueue_promise_map[kHalfOfQueueSize].get_future();
test_enqueue_end.RegisterEnqueue(&enqueue_promise_map);
@@ -605,8 +603,8 @@ TEST_F(QueueTest, queue_becomes_empty_dequeue_callback_only) {
// Register dequeue, expect kHalfOfQueueSize data move to dequeue end buffer
std::unordered_map<int, std::promise<int>> dequeue_promise_map;
- dequeue_promise_map.emplace(
- std::piecewise_construct, std::forward_as_tuple(kHalfOfQueueSize), std::forward_as_tuple());
+ dequeue_promise_map.emplace(std::piecewise_construct, std::forward_as_tuple(kHalfOfQueueSize),
+ std::forward_as_tuple());
auto dequeue_future = dequeue_promise_map[kHalfOfQueueSize].get_future();
test_dequeue_end.RegisterDequeue(&dequeue_promise_map);
dequeue_future.wait();
@@ -690,27 +688,21 @@ TEST_F(QueueTest, pass_smart_pointer_and_unregister) {
// Enqueue a string
std::string valid = "Valid String";
std::shared_ptr<std::string> shared = std::make_shared<std::string>(valid);
- queue->RegisterEnqueue(
- enqueue_handler_,
- common::Bind(
- [](Queue<std::string>* queue, std::shared_ptr<std::string> shared) {
- queue->UnregisterEnqueue();
- return std::make_unique<std::string>(*shared);
- },
- common::Unretained(queue),
- shared));
+ queue->RegisterEnqueue(enqueue_handler_, common::Bind(
+ [](Queue<std::string>* queue, std::shared_ptr<std::string> shared) {
+ queue->UnregisterEnqueue();
+ return std::make_unique<std::string>(*shared);
+ },
+ common::Unretained(queue), shared));
// Dequeue the string
- queue->RegisterDequeue(
- dequeue_handler_,
- common::Bind(
- [](Queue<std::string>* queue, std::string valid) {
- queue->UnregisterDequeue();
- auto answer = *queue->TryDequeue();
- ASSERT_EQ(answer, valid);
- },
- common::Unretained(queue),
- valid));
+ queue->RegisterDequeue(dequeue_handler_, common::Bind(
+ [](Queue<std::string>* queue, std::string valid) {
+ queue->UnregisterDequeue();
+ auto answer = *queue->TryDequeue();
+ ASSERT_EQ(answer, valid);
+ },
+ common::Unretained(queue), valid));
// Wait for both handlers to finish and delete the Queue
std::promise<void> promise;
@@ -723,83 +715,12 @@ TEST_F(QueueTest, pass_smart_pointer_and_unregister) {
delete queue;
promise->set_value();
},
- common::Unretained(queue),
- common::Unretained(promise)));
+ common::Unretained(queue), common::Unretained(promise)));
},
- common::Unretained(dequeue_handler_),
- common::Unretained(queue),
- common::Unretained(&promise)));
+ common::Unretained(dequeue_handler_), common::Unretained(queue), common::Unretained(&promise)));
future.wait();
}
-std::unique_ptr<std::string> sleep_and_enqueue_callback(int* to_increase) {
- std::this_thread::sleep_for(std::chrono::milliseconds(100));
- (*to_increase)++;
- return std::make_unique<std::string>("Hello");
-}
-
-TEST_F(QueueTest, unregister_enqueue_and_wait) {
- Queue<std::string> queue(10);
- int* indicator = new int(100);
- queue.RegisterEnqueue(enqueue_handler_, common::Bind(&sleep_and_enqueue_callback, common::Unretained(indicator)));
- std::this_thread::sleep_for(std::chrono::milliseconds(50));
- queue.UnregisterEnqueue();
- EXPECT_EQ(*indicator, 101);
- delete indicator;
-}
-
-std::unique_ptr<std::string> sleep_and_enqueue_callback_and_unregister(
- int* to_increase, Queue<std::string>* queue, std::atomic_bool* is_registered) {
- std::this_thread::sleep_for(std::chrono::milliseconds(100));
- (*to_increase)++;
- if (is_registered->exchange(false)) {
- queue->UnregisterEnqueue();
- }
- return std::make_unique<std::string>("Hello");
-}
-
-TEST_F(QueueTest, unregister_enqueue_and_wait_maybe_unregistered) {
- Queue<std::string> queue(10);
- int* indicator = new int(100);
- std::atomic_bool is_registered = true;
- queue.RegisterEnqueue(
- enqueue_handler_,
- common::Bind(
- &sleep_and_enqueue_callback_and_unregister,
- common::Unretained(indicator),
- common::Unretained(&queue),
- common::Unretained(&is_registered)));
- std::this_thread::sleep_for(std::chrono::milliseconds(50));
- if (is_registered.exchange(false)) {
- queue.UnregisterEnqueue();
- }
- EXPECT_EQ(*indicator, 101);
- delete indicator;
-}
-
-void sleep_and_dequeue_callback(int* to_increase) {
- std::this_thread::sleep_for(std::chrono::milliseconds(100));
- (*to_increase)++;
-}
-
-TEST_F(QueueTest, unregister_dequeue_and_wait) {
- int* indicator = new int(100);
- Queue<std::string> queue(10);
- queue.RegisterEnqueue(
- enqueue_handler_,
- common::Bind(
- [](Queue<std::string>* queue) {
- queue->UnregisterEnqueue();
- return std::make_unique<std::string>("Hello");
- },
- common::Unretained(&queue)));
- queue.RegisterDequeue(enqueue_handler_, common::Bind(&sleep_and_dequeue_callback, common::Unretained(indicator)));
- std::this_thread::sleep_for(std::chrono::milliseconds(50));
- queue.UnregisterDequeue();
- EXPECT_EQ(*indicator, 101);
- delete indicator;
-}
-
// Create all threads for death tests in the function that dies
class QueueDeathTest : public ::testing::Test {
public:
@@ -807,8 +728,8 @@ class QueueDeathTest : public ::testing::Test {
Thread* enqueue_thread = new Thread("enqueue_thread", Thread::Priority::NORMAL);
Handler* enqueue_handler = new Handler(enqueue_thread);
Queue<std::string>* queue = new Queue<std::string>(kQueueSizeOne);
- queue->RegisterEnqueue(
- enqueue_handler, common::Bind([]() { return std::make_unique<std::string>("A string to fill the queue"); }));
+ queue->RegisterEnqueue(enqueue_handler,
+ common::Bind([]() { return std::make_unique<std::string>("A string to fill the queue"); }));
delete queue;
}
@@ -816,9 +737,8 @@ class QueueDeathTest : public ::testing::Test {
Thread* dequeue_thread = new Thread("dequeue_thread", Thread::Priority::NORMAL);
Handler* dequeue_handler = new Handler(dequeue_thread);
Queue<std::string>* queue = new Queue<std::string>(kQueueSizeOne);
- queue->RegisterDequeue(
- dequeue_handler,
- common::Bind([](Queue<std::string>* queue) { queue->TryDequeue(); }, common::Unretained(queue)));
+ queue->RegisterDequeue(dequeue_handler, common::Bind([](Queue<std::string>* queue) { queue->TryDequeue(); },
+ common::Unretained(queue)));
delete queue;
}
};
@@ -909,18 +829,6 @@ TEST_F(EnqueueBufferTest, clear) {
ASSERT_FALSE(enqueue_.registered_);
}
-TEST_F(EnqueueBufferTest, delete_when_in_callback) {
- Queue<int>* queue = new Queue<int>(kQueueSize);
- EnqueueBuffer<int>* enqueue_buffer = new EnqueueBuffer<int>(queue);
- int num_items = 10;
- for (int i = 0; i < num_items; i++) {
- enqueue_buffer->Enqueue(std::make_unique<int>(i), handler_);
- }
-
- delete enqueue_buffer;
- delete queue;
-}
-
} // namespace
} // namespace os
} // namespace bluetooth
diff --git a/gd/os/linux_generic/reactive_semaphore.cc b/gd/os/linux_generic/reactive_semaphore.cc
index 03339f99e..df0050a60 100644
--- a/gd/os/linux_generic/reactive_semaphore.cc
+++ b/gd/os/linux_generic/reactive_semaphore.cc
@@ -17,10 +17,8 @@
#include "reactive_semaphore.h"
#include <error.h>
-#include <string.h>
#include <sys/eventfd.h>
#include <unistd.h>
-
#include <functional>
#include "os/linux_generic/linux.h"
diff --git a/gd/os/linux_generic/reactor.cc b/gd/os/linux_generic/reactor.cc
index 5722c6139..44b13d86b 100644
--- a/gd/os/linux_generic/reactor.cc
+++ b/gd/os/linux_generic/reactor.cc
@@ -20,10 +20,8 @@
#include <sys/epoll.h>
#include <sys/eventfd.h>
#include <unistd.h>
-
#include <algorithm>
#include <cerrno>
-#include <cinttypes>
#include <cstring>
#include "os/log.h"
@@ -32,23 +30,17 @@ namespace {
// Use at most sizeof(epoll_event) * kEpollMaxEvents kernel memory
constexpr int kEpollMaxEvents = 64;
-constexpr uint64_t kStopReactor = 1 << 0;
-constexpr uint64_t kWaitForIdle = 1 << 1;
} // namespace
namespace bluetooth {
namespace os {
-using common::Closure;
class Reactor::Reactable {
public:
Reactable(int fd, Closure on_read_ready, Closure on_write_ready)
- : fd_(fd),
- on_read_ready_(std::move(on_read_ready)),
- on_write_ready_(std::move(on_write_ready)),
- is_executing_(false),
- removed_(false) {}
+ : fd_(fd), on_read_ready_(std::move(on_read_ready)), on_write_ready_(std::move(on_write_ready)),
+ is_executing_(false), removed_(false) {}
const int fd_;
Closure on_read_ready_;
Closure on_write_ready_;
@@ -58,7 +50,10 @@ class Reactor::Reactable {
std::unique_ptr<std::promise<void>> finished_promise_;
};
-Reactor::Reactor() : epoll_fd_(0), control_fd_(0), is_running_(false) {
+Reactor::Reactor()
+ : epoll_fd_(0),
+ control_fd_(0),
+ is_running_(false) {
RUN_NO_INTR(epoll_fd_ = epoll_create1(EPOLL_CLOEXEC));
ASSERT_LOG(epoll_fd_ != -1, "could not create epoll fd: %s", strerror(errno));
@@ -87,8 +82,6 @@ void Reactor::Run() {
bool already_running = is_running_.exchange(true);
ASSERT(!already_running);
- int timeout_ms = -1;
- bool waiting_for_idle = false;
for (;;) {
{
std::unique_lock<std::mutex> lock(mutex_);
@@ -96,14 +89,8 @@ void Reactor::Run() {
}
epoll_event events[kEpollMaxEvents];
int count;
- RUN_NO_INTR(count = epoll_wait(epoll_fd_, events, kEpollMaxEvents, timeout_ms));
+ RUN_NO_INTR(count = epoll_wait(epoll_fd_, events, kEpollMaxEvents, -1));
ASSERT(count != -1);
- if (waiting_for_idle && count == 0) {
- timeout_ms = -1;
- waiting_for_idle = false;
- idle_promise_->set_value();
- idle_promise_ = nullptr;
- }
for (int i = 0; i < count; ++i) {
auto event = events[i];
@@ -113,21 +100,11 @@ void Reactor::Run() {
if (event.data.ptr == nullptr) {
uint64_t value;
eventfd_read(control_fd_, &value);
- if ((value & kStopReactor) != 0) {
- is_running_ = false;
- return;
- } else if ((value & kWaitForIdle) != 0) {
- timeout_ms = 30;
- waiting_for_idle = true;
- continue;
- } else {
- LOG_ERROR("Unknown control_fd value %" PRIu64 "x", value);
- continue;
- }
+ is_running_ = false;
+ return;
}
auto* reactable = static_cast<Reactor::Reactable*>(event.data.ptr);
std::unique_lock<std::mutex> lock(mutex_);
- executing_reactable_finished_ = nullptr;
// See if this reactable has been removed in the meantime.
if (std::find(invalidation_list_.begin(), invalidation_list_.end(), reactable) != invalidation_list_.end()) {
continue;
@@ -145,11 +122,10 @@ void Reactor::Run() {
reactable->on_write_ready_.Run();
}
{
- std::unique_lock<std::mutex> reactable_lock(reactable->mutex_);
+ std::lock_guard<std::mutex> reactable_lock(reactable->mutex_);
reactable->is_executing_ = false;
if (reactable->removed_) {
reactable->finished_promise_->set_value();
- reactable_lock.unlock();
delete reactable;
}
}
@@ -161,7 +137,7 @@ void Reactor::Stop() {
if (!is_running_) {
LOG_WARN("not running, will stop once it's started");
}
- auto control = eventfd_write(control_fd_, kStopReactor);
+ auto control = eventfd_write(control_fd_, 1);
ASSERT(control != -1);
}
@@ -206,7 +182,7 @@ void Reactor::Unregister(Reactor::Reactable* reactable) {
if (reactable->is_executing_) {
reactable->removed_ = true;
reactable->finished_promise_ = std::make_unique<std::promise<void>>();
- executing_reactable_finished_ = std::make_shared<std::future<void>>(reactable->finished_promise_->get_future());
+ executing_reactable_finished_ = std::make_unique<std::future<void>>(reactable->finished_promise_->get_future());
delaying_delete_until_callback_finished = true;
}
}
@@ -217,32 +193,13 @@ void Reactor::Unregister(Reactor::Reactable* reactable) {
}
bool Reactor::WaitForUnregisteredReactable(std::chrono::milliseconds timeout) {
- std::lock_guard<std::mutex> lock(mutex_);
if (executing_reactable_finished_ == nullptr) {
return true;
}
auto stop_status = executing_reactable_finished_->wait_for(timeout);
- if (stop_status != std::future_status::ready) {
- LOG_ERROR("Unregister reactable timed out");
- }
return stop_status == std::future_status::ready;
}
-bool Reactor::WaitForIdle(std::chrono::milliseconds timeout) {
- auto promise = std::make_shared<std::promise<void>>();
- auto future = std::make_unique<std::future<void>>(promise->get_future());
- {
- std::lock_guard<std::mutex> lock(mutex_);
- idle_promise_ = promise;
- }
-
- auto control = eventfd_write(control_fd_, kWaitForIdle);
- ASSERT(control != -1);
-
- auto idle_status = future->wait_for(timeout);
- return idle_status == std::future_status::ready;
-}
-
void Reactor::ModifyRegistration(Reactor::Reactable* reactable, Closure on_read_ready, Closure on_write_ready) {
ASSERT(reactable != nullptr);
diff --git a/gd/os/linux_generic/reactor_unittest.cc b/gd/os/linux_generic/reactor_unittest.cc
index dd7c7a9c3..b9cd07d6b 100644
--- a/gd/os/linux_generic/reactor_unittest.cc
+++ b/gd/os/linux_generic/reactor_unittest.cc
@@ -17,7 +17,6 @@
#include "os/reactor.h"
#include <sys/eventfd.h>
-
#include <chrono>
#include <future>
#include <thread>
@@ -101,10 +100,9 @@ class FakeReactable {
g_promise->set_value(kReadReadyValue);
}
if (value == kRegisterSampleReactable) {
- reactable_ = reactor_->Register(
- sample_reactable_.fd_,
- Bind(&FakeReactable::OnReadReady, common::Unretained(this)),
- Bind(&FakeReactable::OnWriteReadyNoOp, common::Unretained(this)));
+ reactable_ =
+ reactor_->Register(sample_reactable_.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(this)),
+ Bind(&FakeReactable::OnWriteReadyNoOp, common::Unretained(this)));
g_promise->set_value(kReadReadyValue);
}
if (value == kUnregisterSampleReactable) {
@@ -189,7 +187,7 @@ TEST_F(ReactorTest, stop_multi_times) {
TEST_F(ReactorTest, cold_register_only) {
FakeReactable fake_reactable;
auto* reactable = reactor_->Register(
- fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), common::Closure());
+ fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), Closure());
reactor_->Unregister(reactable);
}
@@ -197,7 +195,7 @@ TEST_F(ReactorTest, cold_register_only) {
TEST_F(ReactorTest, cold_register) {
FakeReactable fake_reactable;
auto* reactable = reactor_->Register(
- fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), common::Closure());
+ fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), Closure());
auto reactor_thread = std::thread(&Reactor::Run, reactor_);
auto future = g_promise->get_future();
@@ -215,7 +213,7 @@ TEST_F(ReactorTest, hot_register_from_different_thread) {
FakeReactable fake_reactable;
auto* reactable = reactor_->Register(
- fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), common::Closure());
+ fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), Closure());
auto write_result = eventfd_write(fake_reactable.fd_, FakeReactable::kSetPromise);
EXPECT_EQ(write_result, 0);
EXPECT_EQ(future.get(), kReadReadyValue);
@@ -228,9 +226,7 @@ TEST_F(ReactorTest, hot_register_from_different_thread) {
TEST_F(ReactorTest, unregister_from_different_thread_while_task_is_executing_) {
FakeRunningReactable fake_reactable;
auto* reactable = reactor_->Register(
- fake_reactable.fd_,
- Bind(&FakeRunningReactable::OnReadReady, common::Unretained(&fake_reactable)),
- common::Closure());
+ fake_reactable.fd_, Bind(&FakeRunningReactable::OnReadReady, common::Unretained(&fake_reactable)), Closure());
auto reactor_thread = std::thread(&Reactor::Run, reactor_);
auto write_result = eventfd_write(fake_reactable.fd_, 1);
ASSERT_EQ(write_result, 0);
@@ -246,8 +242,7 @@ TEST_F(ReactorTest, unregister_from_different_thread_while_task_is_executing_) {
TEST_F(ReactorTest, unregister_from_different_thread_while_task_is_executing_wait_fails) {
FakeRunningReactable fake_reactable;
auto* reactable = reactor_->Register(
- fake_reactable.fd_,
- common::Bind(&FakeRunningReactable::OnReadReady, common::Unretained(&fake_reactable)),
+ fake_reactable.fd_, common::Bind(&FakeRunningReactable::OnReadReady, common::Unretained(&fake_reactable)),
common::Closure());
auto reactor_thread = std::thread(&Reactor::Run, reactor_);
auto write_result = eventfd_write(fake_reactable.fd_, 1);
@@ -265,8 +260,7 @@ TEST_F(ReactorTest, unregister_from_different_thread_while_task_is_executing_wai
TEST_F(ReactorTest, unregister_from_different_thread_while_task_is_executing_wait_succeeds) {
FakeRunningReactable fake_reactable;
auto* reactable = reactor_->Register(
- fake_reactable.fd_,
- common::Bind(&FakeRunningReactable::OnReadReady, common::Unretained(&fake_reactable)),
+ fake_reactable.fd_, common::Bind(&FakeRunningReactable::OnReadReady, common::Unretained(&fake_reactable)),
common::Closure());
auto reactor_thread = std::thread(&Reactor::Run, reactor_);
auto write_result = eventfd_write(fake_reactable.fd_, 1);
@@ -284,7 +278,7 @@ TEST_F(ReactorTest, unregister_from_different_thread_while_task_is_executing_wai
TEST_F(ReactorTest, hot_unregister_from_different_thread) {
FakeReactable fake_reactable;
auto* reactable = reactor_->Register(
- fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), common::Closure());
+ fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), Closure());
auto reactor_thread = std::thread(&Reactor::Run, reactor_);
reactor_->Unregister(reactable);
auto future = g_promise->get_future();
@@ -304,7 +298,7 @@ TEST_F(ReactorTest, hot_register_from_same_thread) {
FakeReactable fake_reactable(reactor_);
auto* reactable = reactor_->Register(
- fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), common::Closure());
+ fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), Closure());
auto write_result = eventfd_write(fake_reactable.fd_, FakeReactable::kRegisterSampleReactable);
EXPECT_EQ(write_result, 0);
EXPECT_EQ(future.get(), kReadReadyValue);
@@ -325,7 +319,7 @@ TEST_F(ReactorTest, hot_unregister_from_same_thread) {
FakeReactable fake_reactable(reactor_);
auto* reactable = reactor_->Register(
- fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), common::Closure());
+ fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), Closure());
auto write_result = eventfd_write(fake_reactable.fd_, FakeReactable::kRegisterSampleReactable);
EXPECT_EQ(write_result, 0);
EXPECT_EQ(future.get(), kReadReadyValue);
@@ -348,13 +342,11 @@ TEST_F(ReactorTest, hot_unregister_from_callback) {
FakeReactable fake_reactable1(reactor_);
auto* reactable1 = reactor_->Register(
- fake_reactable1.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable1)), common::Closure());
+ fake_reactable1.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable1)), Closure());
FakeReactable fake_reactable2(reactor_);
auto* reactable2 = reactor_->Register(
- fake_reactable2.fd_,
- Bind(&FakeReactable::UnregisterInCallback, common::Unretained(&fake_reactable2)),
- common::Closure());
+ fake_reactable2.fd_, Bind(&FakeReactable::UnregisterInCallback, common::Unretained(&fake_reactable2)), Closure());
fake_reactable2.reactable_ = reactable2;
auto write_result = eventfd_write(fake_reactable2.fd_, 1);
EXPECT_EQ(write_result, 0);
@@ -370,13 +362,11 @@ TEST_F(ReactorTest, hot_unregister_during_unregister_from_callback) {
FakeReactable fake_reactable1(reactor_);
auto* reactable1 = reactor_->Register(
- fake_reactable1.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable1)), common::Closure());
+ fake_reactable1.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable1)), Closure());
FakeReactable fake_reactable2(reactor_);
auto* reactable2 = reactor_->Register(
- fake_reactable2.fd_,
- Bind(&FakeReactable::UnregisterInCallback, common::Unretained(&fake_reactable2)),
- common::Closure());
+ fake_reactable2.fd_, Bind(&FakeReactable::UnregisterInCallback, common::Unretained(&fake_reactable2)), Closure());
fake_reactable2.reactable_ = reactable2;
auto write_result = eventfd_write(fake_reactable2.fd_, 1);
EXPECT_EQ(write_result, 0);
@@ -400,8 +390,8 @@ TEST_F(ReactorTest, start_and_stop_multi_times) {
TEST_F(ReactorTest, on_write_ready) {
FakeReactable fake_reactable;
- auto* reactable = reactor_->Register(
- fake_reactable.fd_, common::Closure(), Bind(&FakeReactable::OnWriteReady, common::Unretained(&fake_reactable)));
+ auto* reactable = reactor_->Register(fake_reactable.fd_, Closure(),
+ Bind(&FakeReactable::OnWriteReady, common::Unretained(&fake_reactable)));
auto reactor_thread = std::thread(&Reactor::Run, reactor_);
uint64_t value = 0;
auto read_result = eventfd_read(fake_reactable.fd_, &value);
@@ -417,9 +407,9 @@ TEST_F(ReactorTest, on_write_ready) {
TEST_F(ReactorTest, modify_registration) {
FakeReactable fake_reactable;
auto* reactable = reactor_->Register(
- fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), common::Closure());
- reactor_->ModifyRegistration(
- reactable, common::Closure(), Bind(&FakeReactable::OnWriteReady, common::Unretained(&fake_reactable)));
+ fake_reactable.fd_, Bind(&FakeReactable::OnReadReady, common::Unretained(&fake_reactable)), Closure());
+ reactor_->ModifyRegistration(reactable, Closure(),
+ Bind(&FakeReactable::OnWriteReady, common::Unretained(&fake_reactable)));
auto reactor_thread = std::thread(&Reactor::Run, reactor_);
uint64_t value = 0;
auto read_result = eventfd_read(fake_reactable.fd_, &value);
diff --git a/gd/os/linux_generic/repeating_alarm.cc b/gd/os/linux_generic/repeating_alarm.cc
index 8a718f29f..79cda6da1 100644
--- a/gd/os/linux_generic/repeating_alarm.cc
+++ b/gd/os/linux_generic/repeating_alarm.cc
@@ -17,12 +17,10 @@
#include "os/repeating_alarm.h"
#include <sys/timerfd.h>
-#include <unistd.h>
-
#include <cstring>
+#include <unistd.h>
#include "common/bind.h"
-#include "os/linux_generic/linux.h"
#include "os/log.h"
#include "os/utils.h"
@@ -34,9 +32,8 @@
namespace bluetooth {
namespace os {
-using common::Closure;
-RepeatingAlarm::RepeatingAlarm(Handler* handler) : handler_(handler), fd_(TIMERFD_CREATE(ALARM_CLOCK, 0)) {
+RepeatingAlarm::RepeatingAlarm(Handler* handler) : handler_(handler), fd_(timerfd_create(ALARM_CLOCK, 0)) {
ASSERT(fd_ != -1);
token_ = handler_->thread_->GetReactor()->Register(
@@ -47,16 +44,18 @@ RepeatingAlarm::~RepeatingAlarm() {
handler_->thread_->GetReactor()->Unregister(token_);
int close_status;
- RUN_NO_INTR(close_status = TIMERFD_CLOSE(fd_));
+ RUN_NO_INTR(close_status = close(fd_));
ASSERT(close_status != -1);
}
void RepeatingAlarm::Schedule(Closure task, std::chrono::milliseconds period) {
std::lock_guard<std::mutex> lock(mutex_);
long period_ms = period.count();
- itimerspec timer_itimerspec{{period_ms / 1000, period_ms % 1000 * 1000000},
- {period_ms / 1000, period_ms % 1000 * 1000000}};
- int result = TIMERFD_SETTIME(fd_, 0, &timer_itimerspec, nullptr);
+ itimerspec timer_itimerspec{
+ {period_ms / 1000, period_ms % 1000 * 1000000},
+ {period_ms / 1000, period_ms % 1000 * 1000000}
+ };
+ int result = timerfd_settime(fd_, 0, &timer_itimerspec, nullptr);
ASSERT(result == 0);
task_ = std::move(task);
@@ -65,7 +64,7 @@ void RepeatingAlarm::Schedule(Closure task, std::chrono::milliseconds period) {
void RepeatingAlarm::Cancel() {
std::lock_guard<std::mutex> lock(mutex_);
itimerspec disarm_itimerspec{/* disarm timer */};
- int result = TIMERFD_SETTIME(fd_, 0, &disarm_itimerspec, nullptr);
+ int result = timerfd_settime(fd_, 0, &disarm_itimerspec, nullptr);
ASSERT(result == 0);
}
diff --git a/gd/os/linux_generic/repeating_alarm_unittest.cc b/gd/os/linux_generic/repeating_alarm_unittest.cc
index c7e1022c5..d30bbd93e 100644
--- a/gd/os/linux_generic/repeating_alarm_unittest.cc
+++ b/gd/os/linux_generic/repeating_alarm_unittest.cc
@@ -47,28 +47,16 @@ class RepeatingAlarmTest : public ::testing::Test {
auto future = promise.get_future();
auto start_time = std::chrono::steady_clock::now();
int counter = 0;
- alarm_->Schedule(
- common::Bind(
- &RepeatingAlarmTest::verify_delayed_tasks,
- common::Unretained(this),
- common::Unretained(&counter),
- start_time,
- scheduled_tasks,
- common::Unretained(&promise),
- task_length_ms,
- interval_between_tasks_ms),
- std::chrono::milliseconds(interval_between_tasks_ms));
+ alarm_->Schedule(common::Bind(&RepeatingAlarmTest::verify_delayed_tasks, common::Unretained(this),
+ common::Unretained(&counter), start_time, scheduled_tasks,
+ common::Unretained(&promise), task_length_ms, interval_between_tasks_ms),
+ std::chrono::milliseconds(interval_between_tasks_ms));
future.get();
alarm_->Cancel();
}
- void verify_delayed_tasks(
- int* counter,
- std::chrono::steady_clock::time_point start_time,
- int scheduled_tasks,
- std::promise<void>* promise,
- int task_length_ms,
- int interval_between_tasks_ms) {
+ void verify_delayed_tasks(int* counter, std::chrono::steady_clock::time_point start_time, int scheduled_tasks,
+ std::promise<void>* promise, int task_length_ms, int interval_between_tasks_ms) {
*counter = *counter + 1;
auto time_now = std::chrono::steady_clock::now();
auto time_delta = time_now - start_time;
@@ -81,7 +69,7 @@ class RepeatingAlarmTest : public ::testing::Test {
RepeatingAlarm* alarm_;
- common::Closure should_not_happen_ = common::Bind([] { ASSERT_TRUE(false); });
+ Closure should_not_happen_ = common::Bind([] { ASSERT_TRUE(false); });
private:
Thread* thread_;
@@ -97,8 +85,8 @@ TEST_F(RepeatingAlarmTest, schedule) {
auto future = promise.get_future();
auto before = std::chrono::steady_clock::now();
int period_ms = 10;
- alarm_->Schedule(
- common::Bind(&std::promise<void>::set_value, common::Unretained(&promise)), std::chrono::milliseconds(period_ms));
+ alarm_->Schedule(common::Bind(&std::promise<void>::set_value, common::Unretained(&promise)),
+ std::chrono::milliseconds(period_ms));
future.get();
alarm_->Cancel();
auto after = std::chrono::steady_clock::now();
@@ -107,14 +95,14 @@ TEST_F(RepeatingAlarmTest, schedule) {
}
TEST_F(RepeatingAlarmTest, cancel_alarm) {
- alarm_->Schedule(should_not_happen_, std::chrono::milliseconds(10));
+ alarm_->Schedule(should_not_happen_, std::chrono::milliseconds(1));
alarm_->Cancel();
- std::this_thread::sleep_for(std::chrono::milliseconds(50));
+ std::this_thread::sleep_for(std::chrono::milliseconds(5));
}
TEST_F(RepeatingAlarmTest, cancel_alarm_from_callback) {
- alarm_->Schedule(
- common::Bind(&RepeatingAlarm::Cancel, common::Unretained(this->alarm_)), std::chrono::milliseconds(1));
+ alarm_->Schedule(common::Bind(&RepeatingAlarm::Cancel, common::Unretained(this->alarm_)),
+ std::chrono::milliseconds(1));
std::this_thread::sleep_for(std::chrono::milliseconds(5));
}
@@ -122,8 +110,8 @@ TEST_F(RepeatingAlarmTest, schedule_while_alarm_armed) {
alarm_->Schedule(should_not_happen_, std::chrono::milliseconds(1));
std::promise<void> promise;
auto future = promise.get_future();
- alarm_->Schedule(
- common::Bind(&std::promise<void>::set_value, common::Unretained(&promise)), std::chrono::milliseconds(10));
+ alarm_->Schedule(common::Bind(&std::promise<void>::set_value, common::Unretained(&promise)),
+ std::chrono::milliseconds(10));
future.get();
alarm_->Cancel();
}
diff --git a/gd/os/linux_generic/thread.cc b/gd/os/linux_generic/thread.cc
index e1c1a3436..c2969fe2f 100644
--- a/gd/os/linux_generic/thread.cc
+++ b/gd/os/linux_generic/thread.cc
@@ -17,9 +17,8 @@
#include "os/thread.h"
#include <fcntl.h>
-#include <sys/syscall.h>
#include <unistd.h>
-
+#include <sys/syscall.h>
#include <cerrno>
#include <cstring>
@@ -33,7 +32,9 @@ constexpr int kRealTimeFifoSchedulingPriority = 1;
}
Thread::Thread(const std::string& name, const Priority priority)
- : name_(name), reactor_(), running_thread_(&Thread::run, this, priority) {}
+ : name_(name),
+ reactor_(),
+ running_thread_(&Thread::run, this, priority) {}
void Thread::run(Priority priority) {
if (priority == Priority::REAL_TIME) {
diff --git a/gd/os/linux_generic/thread_unittest.cc b/gd/os/linux_generic/thread_unittest.cc
index 811b6c2a8..f0b8f246b 100644
--- a/gd/os/linux_generic/thread_unittest.cc
+++ b/gd/os/linux_generic/thread_unittest.cc
@@ -85,10 +85,9 @@ TEST_F(ThreadTest, not_same_thread) {
TEST_F(ThreadTest, same_thread) {
Reactor* reactor = thread->GetReactor();
SampleReactable sample_reactable(thread);
- auto* reactable = reactor->Register(
- sample_reactable.fd_,
- common::Bind(&SampleReactable::OnReadReady, common::Unretained(&sample_reactable)),
- common::Closure());
+ auto* reactable =
+ reactor->Register(sample_reactable.fd_,
+ common::Bind(&SampleReactable::OnReadReady, common::Unretained(&sample_reactable)), Closure());
int fd = sample_reactable.fd_;
int write_result = eventfd_write(fd, kCheckIsSameThread);
EXPECT_EQ(write_result, 0);
diff --git a/gd/os/linux_generic/wakelock_manager.cc b/gd/os/linux_generic/wakelock_manager.cc
deleted file mode 100644
index ea7b99a33..000000000
--- a/gd/os/linux_generic/wakelock_manager.cc
+++ /dev/null
@@ -1,274 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#define LOG_TAG "BtGdWakelock"
-
-#include "os/wakelock_manager.h"
-
-#include <cerrno>
-#include <mutex>
-
-#include "os/internal/wakelock_native.h"
-#include "os/log.h"
-
-namespace bluetooth {
-namespace os {
-
-using internal::WakelockNative;
-using StatusCode = WakelockNative::StatusCode;
-
-uint64_t now_ms() {
- struct timespec ts = {};
- if (clock_gettime(CLOCK_BOOTTIME, &ts) == -1) {
- LOG_ERROR("unable to get current time: %s", strerror(errno));
- return 0;
- }
- return (ts.tv_sec * 1000LL) + (ts.tv_nsec / 1000000LL);
-}
-
-const std::string WakelockManager::kBtWakelockId = "bluetooth_gd_timer";
-
-// Wakelock statistics for the "bluetooth_timer"
-struct WakelockManager::Stats {
- bool is_acquired = false;
- size_t acquired_count = 0;
- size_t released_count = 0;
- size_t acquired_errors = 0;
- size_t released_errors = 0;
- uint64_t min_acquired_interval_ms = 0;
- uint64_t max_acquired_interval_ms = 0;
- uint64_t last_acquired_interval_ms = 0;
- uint64_t total_acquired_interval_ms = 0;
- uint64_t last_acquired_timestamp_ms = 0;
- uint64_t last_released_timestamp_ms = 0;
- uint64_t last_reset_timestamp_ms = now_ms();
- StatusCode last_acquired_error = StatusCode::SUCCESS;
- StatusCode last_released_error = StatusCode::SUCCESS;
-
- void Reset() {
- is_acquired = false;
- acquired_count = 0;
- released_count = 0;
- acquired_errors = 0;
- released_errors = 0;
- min_acquired_interval_ms = 0;
- max_acquired_interval_ms = 0;
- last_acquired_interval_ms = 0;
- total_acquired_interval_ms = 0;
- last_acquired_timestamp_ms = 0;
- last_released_timestamp_ms = 0;
- last_reset_timestamp_ms = now_ms();
- last_acquired_error = StatusCode::SUCCESS;
- last_released_error = StatusCode::SUCCESS;
- }
-
- // Update the Bluetooth acquire wakelock statistics.
- //
- // This function should be called every time when the wakelock is acquired.
- // |acquired_status| is the status code that was return when the wakelock was
- // acquired.
- void UpdateAcquiredStats(StatusCode acquired_status) {
- const uint64_t just_now_ms = now_ms();
- if (acquired_status != StatusCode::SUCCESS) {
- acquired_errors++;
- last_acquired_error = acquired_status;
- }
-
- if (is_acquired) {
- return;
- }
-
- is_acquired = true;
- acquired_count++;
- last_acquired_timestamp_ms = just_now_ms;
- }
-
- // Update the Bluetooth release wakelock statistics.
- //
- // This function should be called every time when the wakelock is released.
- // |released_status| is the status code that was return when the wakelock was
- // released.
- void UpdateReleasedStats(StatusCode released_status) {
- const uint64_t just_now_ms = now_ms();
- if (released_status != StatusCode::SUCCESS) {
- released_errors++;
- last_released_error = released_status;
- }
-
- if (!is_acquired) {
- return;
- }
-
- is_acquired = false;
- released_count++;
- last_released_timestamp_ms = just_now_ms;
-
- // Compute the acquired interval and update the statistics
- uint64_t delta_ms = just_now_ms - last_acquired_timestamp_ms;
- if (delta_ms < min_acquired_interval_ms || released_count == 1) {
- min_acquired_interval_ms = delta_ms;
- }
- if (delta_ms > max_acquired_interval_ms) {
- max_acquired_interval_ms = delta_ms;
- }
- last_acquired_interval_ms = delta_ms;
- total_acquired_interval_ms += delta_ms;
- }
-
- flatbuffers::Offset<WakelockManagerData> GetDumpsysData(
- flatbuffers::FlatBufferBuilder* fb_builder, bool is_native) const {
- const uint64_t just_now_ms = now_ms();
- // Compute the last acquired interval if the wakelock is still acquired
- uint64_t delta_ms = 0;
- uint64_t last_interval_ms = last_acquired_interval_ms;
- uint64_t min_interval_ms = min_acquired_interval_ms;
- uint64_t max_interval_ms = max_acquired_interval_ms;
- uint64_t avg_interval_ms = 0;
-
- if (is_acquired) {
- delta_ms = just_now_ms - last_acquired_timestamp_ms;
- if (delta_ms > max_interval_ms) {
- max_interval_ms = delta_ms;
- }
- if (delta_ms < min_interval_ms) {
- min_interval_ms = delta_ms;
- }
- last_interval_ms = delta_ms;
- }
- uint64_t total_interval_ms = total_acquired_interval_ms + delta_ms;
-
- if (acquired_count > 0) {
- avg_interval_ms = total_interval_ms / acquired_count;
- }
-
- WakelockManagerDataBuilder builder(*fb_builder);
- builder.add_title(fb_builder->CreateString("Bluetooth Wakelock Statistics"));
- builder.add_is_acquired(is_acquired);
- builder.add_is_native(is_native);
- builder.add_acquired_count(acquired_count);
- builder.add_released_count(released_count);
- builder.add_acquired_error_count(acquired_errors);
- builder.add_released_error_count(released_errors);
- builder.add_last_acquire_error_code(last_acquired_error);
- builder.add_last_release_error_code(last_released_error);
- builder.add_last_acquired_timestamp_millis(last_interval_ms);
- builder.add_last_released_timestamp_millis(last_released_timestamp_ms);
- builder.add_last_interval_millis(last_acquired_interval_ms);
- builder.add_max_interval_millis(max_interval_ms);
- builder.add_min_interval_millis(min_interval_ms);
- builder.add_avg_interval_millis(avg_interval_ms);
- builder.add_total_interval_millis(total_interval_ms);
- builder.add_total_time_since_reset_millis(just_now_ms - last_reset_timestamp_ms);
- return builder.Finish();
- }
-};
-
-void WakelockManager::SetOsCallouts(OsCallouts* callouts, Handler* handler) {
- std::lock_guard<std::recursive_mutex> lock_guard(mutex_);
- if (initialized_) {
- LOG_WARN("Setting OS callouts after initialization can lead to wakelock leak!");
- }
- os_callouts_ = callouts;
- os_callouts_handler_ = handler;
- is_native_ = (os_callouts_ == nullptr);
- if (is_native_) {
- ASSERT_LOG(os_callouts_handler_ != nullptr, "handler must not be null when callout is not null");
- }
- LOG_INFO("set to %s", is_native_ ? "native" : "non-native");
-}
-
-bool WakelockManager::Acquire() {
- std::lock_guard<std::recursive_mutex> lock_guard(mutex_);
- if (!initialized_) {
- if (is_native_) {
- WakelockNative::Get().Initialize();
- }
- initialized_ = true;
- }
-
- StatusCode status;
- if (is_native_) {
- status = WakelockNative::Get().Acquire(kBtWakelockId);
- } else {
- os_callouts_handler_->CallOn(os_callouts_, &OsCallouts::AcquireCallout, kBtWakelockId);
- status = StatusCode::SUCCESS;
- }
-
- pstats_->UpdateAcquiredStats(status);
-
- if (status != StatusCode::SUCCESS) {
- LOG_ERROR("unable to acquire wake lock, error code: %u", status);
- }
-
- return status == StatusCode ::SUCCESS;
-}
-
-bool WakelockManager::Release() {
- std::lock_guard<std::recursive_mutex> lock_guard(mutex_);
- if (!initialized_) {
- if (is_native_) {
- WakelockNative::Get().Initialize();
- }
- initialized_ = true;
- }
-
- StatusCode status;
- if (is_native_) {
- status = WakelockNative::Get().Release(kBtWakelockId);
- } else {
- os_callouts_handler_->CallOn(os_callouts_, &OsCallouts::ReleaseCallout, kBtWakelockId);
- status = StatusCode ::SUCCESS;
- }
-
- pstats_->UpdateReleasedStats(status);
-
- if (status != StatusCode::SUCCESS) {
- LOG_ERROR("unable to release wake lock, error code: %u", status);
- }
-
- return status == StatusCode ::SUCCESS;
-}
-
-void WakelockManager::CleanUp() {
- std::lock_guard<std::recursive_mutex> lock_guard(mutex_);
- if (!initialized_) {
- LOG_ERROR("Already uninitialized");
- return;
- }
- if (pstats_->is_acquired) {
- LOG_ERROR("Releasing wake lock as part of cleanup");
- Release();
- }
- if (is_native_) {
- WakelockNative::Get().CleanUp();
- }
- pstats_->Reset();
- initialized_ = false;
-}
-
-flatbuffers::Offset<WakelockManagerData> WakelockManager::GetDumpsysData(flatbuffers::FlatBufferBuilder* fb_builder) {
- std::lock_guard<std::recursive_mutex> lock_guard(mutex_);
- return pstats_->GetDumpsysData(fb_builder, is_native_);
-}
-
-WakelockManager::WakelockManager() : pstats_(std::make_unique<Stats>()) {}
-
-WakelockManager::~WakelockManager() = default;
-
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/linux_generic/wakelock_manager_unittest.cc b/gd/os/linux_generic/wakelock_manager_unittest.cc
deleted file mode 100644
index 0ae970448..000000000
--- a/gd/os/linux_generic/wakelock_manager_unittest.cc
+++ /dev/null
@@ -1,192 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2020 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-#include <optional>
-#include <unordered_map>
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "flatbuffers/flatbuffers.h"
-
-#include "common/bind.h"
-#include "os/handler.h"
-#include "os/thread.h"
-#include "os/wakelock_manager.h"
-#include "wakelock_manager_generated.h"
-
-namespace testing {
-
-using bluetooth::os::FinishWakelockManagerDataBuffer;
-using bluetooth::os::GetWakelockManagerData;
-using bluetooth::os::Handler;
-using bluetooth::os::Thread;
-using bluetooth::os::WakelockManager;
-using bluetooth::os::WakelockManagerData;
-using bluetooth::os::WakelockManagerDataBuilder;
-
-class TestOsCallouts : public WakelockManager::OsCallouts {
- public:
- void AcquireCallout(const std::string& lock_name) override {
- auto iter = acquired_lock_counts.find(lock_name);
- if (iter == acquired_lock_counts.end()) {
- acquired_lock_counts[lock_name] = 0;
- }
- acquired_lock_counts[lock_name] += 1;
- }
-
- void ReleaseCallout(const std::string& lock_name) override {
- auto iter = acquired_lock_counts.find(lock_name);
- if (iter == acquired_lock_counts.end()) {
- acquired_lock_counts[lock_name] = 0;
- }
- acquired_lock_counts[lock_name] -= 1;
- }
-
- std::optional<int> GetNetAcquiredCount(const std::string& lock_name) const {
- auto iter = acquired_lock_counts.find(lock_name);
- if (iter == acquired_lock_counts.end()) {
- return std::nullopt;
- }
- return iter->second;
- }
-
- // how many times each lock is acquired, net, can go negative
- std::unordered_map<std::string, int> acquired_lock_counts;
-};
-
-class WakelockManagerTest : public Test {
- protected:
- void SetUp() override {
- thread_ = new Thread("test_thread", Thread::Priority::NORMAL);
- handler_ = new Handler(thread_);
- }
- void TearDown() override {
- handler_->Clear();
- delete handler_;
- delete thread_;
- }
-
- void SyncHandler() {
- std::promise<void> promise;
- auto future = promise.get_future();
- handler_->Post(
- bluetooth::common::BindOnce(&std::promise<void>::set_value, bluetooth::common::Unretained(&promise)));
- auto future_status = future.wait_for(std::chrono::seconds(1));
- ASSERT_EQ(future_status, std::future_status::ready);
- }
-
- Handler* handler_;
- Thread* thread_;
-};
-
-TEST_F(WakelockManagerTest, test_set_os_callouts_repeated_acquire) {
- TestOsCallouts os_callouts;
- WakelockManager::Get().SetOsCallouts(&os_callouts, handler_);
-
- // Initially, no wakelock is acquired
- ASSERT_TRUE(os_callouts.acquired_lock_counts.empty());
- ASSERT_FALSE(os_callouts.GetNetAcquiredCount(WakelockManager::kBtWakelockId));
-
- WakelockManager::Get().Acquire();
- SyncHandler();
- ASSERT_EQ(os_callouts.acquired_lock_counts.size(), 1);
- ASSERT_THAT(os_callouts.GetNetAcquiredCount(WakelockManager::kBtWakelockId), Optional(Eq(1)));
-
- WakelockManager::Get().Acquire();
- SyncHandler();
- ASSERT_EQ(os_callouts.acquired_lock_counts.size(), 1);
- ASSERT_THAT(os_callouts.GetNetAcquiredCount(WakelockManager::kBtWakelockId), Optional(Eq(2)));
-
- WakelockManager::Get().Release();
- SyncHandler();
- ASSERT_THAT(os_callouts.GetNetAcquiredCount(WakelockManager::kBtWakelockId), Optional(Eq(1)));
-
- WakelockManager::Get().CleanUp();
- SyncHandler();
-}
-
-TEST_F(WakelockManagerTest, test_set_os_callouts_repeated_release) {
- TestOsCallouts os_callouts;
- WakelockManager::Get().SetOsCallouts(&os_callouts, handler_);
-
- // Initially, no wakelock is acquired
- ASSERT_TRUE(os_callouts.acquired_lock_counts.empty());
- ASSERT_FALSE(os_callouts.GetNetAcquiredCount(WakelockManager::kBtWakelockId));
-
- WakelockManager::Get().Acquire();
- SyncHandler();
- ASSERT_EQ(os_callouts.acquired_lock_counts.size(), 1);
- ASSERT_THAT(os_callouts.GetNetAcquiredCount(WakelockManager::kBtWakelockId), Optional(Eq(1)));
-
- WakelockManager::Get().Release();
- SyncHandler();
- ASSERT_EQ(os_callouts.acquired_lock_counts.size(), 1);
- ASSERT_THAT(os_callouts.GetNetAcquiredCount(WakelockManager::kBtWakelockId), Optional(Eq(0)));
-
- // OS callouts allow pass through for repeated release calls
- WakelockManager::Get().Release();
- SyncHandler();
- ASSERT_THAT(os_callouts.GetNetAcquiredCount(WakelockManager::kBtWakelockId), Optional(Eq(-1)));
-
- WakelockManager::Get().CleanUp();
- SyncHandler();
-}
-
-TEST_F(WakelockManagerTest, test_with_os_callouts_in_a_loop_and_dump) {
- TestOsCallouts os_callouts;
- WakelockManager::Get().SetOsCallouts(&os_callouts, handler_);
-
- // Initially, no wakelock is acquired
- ASSERT_TRUE(os_callouts.acquired_lock_counts.empty());
- ASSERT_FALSE(os_callouts.GetNetAcquiredCount(WakelockManager::kBtWakelockId));
-
- for (size_t i = 0; i < 1000; i++) {
- WakelockManager::Get().Acquire();
- SyncHandler();
- ASSERT_EQ(os_callouts.acquired_lock_counts.size(), 1);
- ASSERT_THAT(os_callouts.GetNetAcquiredCount(WakelockManager::kBtWakelockId), Optional(Eq(1)));
- WakelockManager::Get().Release();
- SyncHandler();
- ASSERT_THAT(os_callouts.GetNetAcquiredCount(WakelockManager::kBtWakelockId), Optional(Eq(0)));
- }
-
- {
- flatbuffers::FlatBufferBuilder builder(1024);
- auto offset = WakelockManager::Get().GetDumpsysData(&builder);
- FinishWakelockManagerDataBuffer(builder, offset);
- auto data = GetWakelockManagerData(builder.GetBufferPointer());
-
- ASSERT_EQ(data->acquired_count(), 1000);
- ASSERT_EQ(data->released_count(), 1000);
- }
-
- WakelockManager::Get().CleanUp();
- SyncHandler();
-
- {
- flatbuffers::FlatBufferBuilder builder(1024);
- auto offset = WakelockManager::Get().GetDumpsysData(&builder);
- FinishWakelockManagerDataBuffer(builder, offset);
- auto data = GetWakelockManagerData(builder.GetBufferPointer());
-
- ASSERT_EQ(data->acquired_count(), 0);
- ASSERT_EQ(data->released_count(), 0);
- }
-}
-
-} // namespace testing
diff --git a/gd/os/log.h b/gd/os/log.h
index 312de3dec..29ff7517e 100644
--- a/gd/os/log.h
+++ b/gd/os/log.h
@@ -21,43 +21,25 @@
#include <cstdlib>
#ifndef LOG_TAG
-#define LOG_TAG "bluetooth"
+#define LOG_TAG "bt"
#endif
-static_assert(LOG_TAG != nullptr, "LOG_TAG should never be NULL");
-
#if defined(OS_ANDROID)
#include <log/log.h>
-#ifdef FUZZ_TARGET
-#define LOG_VERBOSE(...)
-#define LOG_DEBUG(...)
-#define LOG_INFO(...)
-#define LOG_WARN(...)
-#else
-
-static_assert(LOG_TAG != nullptr, "LOG_TAG is null after header inclusion");
-
-#define LOG_VERBOSE(fmt, args...) \
- do { \
- if (bluetooth::common::InitFlags::IsDebugLoggingEnabledForTag(LOG_TAG)) { \
- ALOGV("%s:%d %s: " fmt, __FILE__, __LINE__, __func__, ##args); \
- } \
- } while (false)
-
-#define LOG_DEBUG(fmt, args...) \
- do { \
- if (bluetooth::common::InitFlags::IsDebugLoggingEnabledForTag(LOG_TAG)) { \
- ALOGD("%s:%d %s: " fmt, __FILE__, __LINE__, __func__, ##args); \
- } \
- } while (false)
+/* When including headers from legacy stack, this log definitions collide with existing logging system. Remove once we
+ * get rid of legacy stack. */
+#ifndef LOG_VERBOSE
+#define LOG_VERBOSE(fmt, args...) ALOGV("%s:%d %s: " fmt, __FILE__, __LINE__, __func__, ##args)
+#define LOG_DEBUG(fmt, args...) ALOGD("%s:%d %s: " fmt, __FILE__, __LINE__, __func__, ##args)
#define LOG_INFO(fmt, args...) ALOGI("%s:%d %s: " fmt, __FILE__, __LINE__, __func__, ##args)
#define LOG_WARN(fmt, args...) ALOGW("%s:%d %s: " fmt, __FILE__, __LINE__, __func__, ##args)
-#endif /* FUZZ_TARGET */
#define LOG_ERROR(fmt, args...) ALOGE("%s:%d %s: " fmt, __FILE__, __LINE__, __func__, ##args)
+#endif /* LOG_VERBOSE*/
+
#else
/* syslog didn't work well here since we would be redefining LOG_DEBUG. */
@@ -65,52 +47,34 @@ static_assert(LOG_TAG != nullptr, "LOG_TAG is null after header inclusion");
#include <cstdio>
#include <ctime>
-#define LOGWRAPPER(fmt, args...) \
- do { \
- auto _now = std::chrono::system_clock::now(); \
- auto _now_ms = std::chrono::time_point_cast<std::chrono::milliseconds>(_now); \
- auto _now_t = std::chrono::system_clock::to_time_t(_now); \
- /* YYYY-MM-DD_HH:MM:SS.sss is 23 byte long, plus 1 for null terminator */ \
- char _buf[24]; \
- auto l = std::strftime(_buf, sizeof(_buf), "%Y-%m-%d %H:%M:%S", std::localtime(&_now_t)); \
- snprintf( \
- _buf + l, sizeof(_buf) - l, ".%03u", static_cast<unsigned int>(_now_ms.time_since_epoch().count() % 1000)); \
- fprintf(stderr, "%s %s - %s:%d - %s: " fmt "\n", _buf, LOG_TAG, __FILE__, __LINE__, __func__, ##args); \
+/* When including headers from legacy stack, this log definitions collide with existing logging system. Remove once we
+ * get rid of legacy stack. */
+#ifndef LOG_VERBOSE
+
+#define LOGWRAPPER(fmt, args...) \
+ do { \
+ auto now = std::chrono::system_clock::now(); \
+ auto now_ms = std::chrono::time_point_cast<std::chrono::milliseconds>(now); \
+ auto now_t = std::chrono::system_clock::to_time_t(now); \
+ /* YYYY-MM-DD_HH:MM:SS.sss is 23 byte long, plus 1 for null terminator */ \
+ char buf[24]; \
+ auto l = std::strftime(buf, sizeof(buf), "%Y-%m-%d %H:%M:%S", std::localtime(&now_t)); \
+ snprintf(buf + l, sizeof(buf) - l, ".%03u", static_cast<unsigned int>(now_ms.time_since_epoch().count() % 1000)); \
+ fprintf(stderr, "%s %s - %s:%d - %s: " fmt "\n", buf, LOG_TAG, __FILE__, __LINE__, __func__, ##args); \
} while (false)
-#ifdef FUZZ_TARGET
-#define LOG_VERBOSE(...)
-#define LOG_DEBUG(...)
-#define LOG_INFO(...)
-#define LOG_WARN(...)
-#else
#define LOG_VERBOSE(...) LOGWRAPPER(__VA_ARGS__)
#define LOG_DEBUG(...) LOGWRAPPER(__VA_ARGS__)
#define LOG_INFO(...) LOGWRAPPER(__VA_ARGS__)
#define LOG_WARN(...) LOGWRAPPER(__VA_ARGS__)
-#endif /* FUZZ_TARGET */
#define LOG_ERROR(...) LOGWRAPPER(__VA_ARGS__)
-
-#ifndef LOG_ALWAYS_FATAL
#define LOG_ALWAYS_FATAL(...) \
do { \
LOGWRAPPER(__VA_ARGS__); \
abort(); \
} while (false)
-#endif
-#ifndef android_errorWriteLog
-#define android_errorWriteLog(tag, subTag) LOG_ERROR("ERROR tag: 0x%x, sub_tag: %s", tag, subTag)
-#endif
-
-#ifndef android_errorWriteWithInfoLog
-#define android_errorWriteWithInfoLog(tag, subTag, uid, data, dataLen) \
- LOG_ERROR("ERROR tag: 0x%x, sub_tag: %s", tag, subTag)
-#endif
-
-#ifndef LOG_EVENT_INT
-#define LOG_EVENT_INT(...)
-#endif
+#endif /* LOG_VERBOE */
#endif /* defined(OS_ANDROID) */
@@ -127,9 +91,3 @@ static_assert(LOG_TAG != nullptr, "LOG_TAG is null after header inclusion");
LOG_ALWAYS_FATAL("assertion '" #condition "' failed - " fmt, ##args); \
} \
} while (false)
-
-#ifndef CASE_RETURN_TEXT
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-#endif
diff --git a/gd/os/metrics.h b/gd/os/metrics.h
deleted file mode 100644
index 6f8ec5797..000000000
--- a/gd/os/metrics.h
+++ /dev/null
@@ -1,268 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#pragma once
-
-#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
-
-#include "hci/address.h"
-
-namespace bluetooth {
-
-namespace os {
-/**
- * Unknown connection handle for metrics purpose
- */
-static const uint32_t kUnknownConnectionHandle = 0xFFFF;
-
-/**
- * Log link layer connection event
- *
- * @param address Stack wide consistent Bluetooth address of this event,
- * nullptr if unknown
- * @param connection_handle connection handle of this event,
- * {@link kUnknownConnectionHandle} if unknown
- * @param direction direction of this connection
- * @param link_type type of the link
- * @param hci_cmd HCI command opecode associated with this event, if any
- * @param hci_event HCI event code associated with this event, if any
- * @param hci_ble_event HCI BLE event code associated with this event, if any
- * @param cmd_status Command status associated with this event, if any
- * @param reason_code Reason code associated with this event, if any
- */
-void LogMetricLinkLayerConnectionEvent(
- const hci::Address* address,
- uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction,
- uint16_t link_type,
- uint32_t hci_cmd,
- uint16_t hci_event,
- uint16_t hci_ble_event,
- uint16_t cmd_status,
- uint16_t reason_code);
-
-/**
- * Logs when Bluetooth controller failed to reply with command status within
- * a timeout period after receiving an HCI command from the host
- *
- * @param hci_cmd opcode of HCI command that caused this timeout
- */
-void LogMetricHciTimeoutEvent(uint32_t hci_cmd);
-
-/**
- * Logs when we receive Bluetooth Read Remote Version Information Complete
- * Event from the remote device, as documented by the Bluetooth Core HCI
- * specification
- *
- * Reference: 5.0 Core Specification, Vol 2, Part E, Page 1118
- *
- * @param handle handle of associated ACL connection
- * @param status HCI command status of this event
- * @param version version code from read remote version complete event
- * @param manufacturer_name manufacturer code from read remote version complete
- * event
- * @param subversion subversion code from read remote version complete event
- */
-void LogMetricRemoteVersionInfo(
- uint16_t handle, uint8_t status, uint8_t version, uint16_t manufacturer_name, uint16_t subversion);
-
-/**
- * Log A2DP audio buffer underrun event
- *
- * @param address A2DP device associated with this event
- * @param encoding_interval_millis encoding interval in milliseconds
- * @param num_missing_pcm_bytes number of PCM bytes that cannot be read from
- * the source
- */
-void LogMetricA2dpAudioUnderrunEvent(
- const hci::Address& address, uint64_t encoding_interval_millis, int num_missing_pcm_bytes);
-
-/**
- * Log A2DP audio buffer overrun event
- *
- * @param address A2DP device associated with this event
- * @param encoding_interval_millis encoding interval in milliseconds
- * @param num_dropped_buffers number of encoded buffers dropped from Tx queue
- * @param num_dropped_encoded_frames number of encoded frames dropped from Tx
- * queue
- * @param num_dropped_encoded_bytes number of encoded bytes dropped from Tx
- * queue
- */
-void LogMetricA2dpAudioOverrunEvent(
- const hci::Address& address,
- uint64_t encoding_interval_millis,
- int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes);
-
-/**
- * Log A2DP audio playback state changed event
- *
- * @param address A2DP device associated with this event
- * @param playback_state A2DP audio playback state, on/off
- * @param audio_coding_mode A2DP audio codec encoding mode, hw/sw
- */
-void LogMetricA2dpPlaybackEvent(const hci::Address& address, int playback_state, int audio_coding_mode);
-
-/**
- * Log read RSSI result
- *
- * @param address device associated with this event
- * @param handle connection handle of this event,
- * {@link kUnknownConnectionHandle} if unknown
- * @param cmd_status command status from read RSSI command
- * @param rssi rssi value in dBm
- */
-void LogMetricReadRssiResult(const hci::Address& address, uint16_t handle, uint32_t cmd_status, int8_t rssi);
-
-/**
- * Log failed contact counter report
- *
- * @param address device associated with this event
- * @param handle connection handle of this event,
- * {@link kUnknownConnectionHandle} if unknown
- * @param cmd_status command status from read failed contact counter command
- * @param failed_contact_counter Number of consecutive failed contacts for a
- * connection corresponding to the Handle
- */
-void LogMetricReadFailedContactCounterResult(
- const hci::Address& address, uint16_t handle, uint32_t cmd_status, int32_t failed_contact_counter);
-
-/**
- * Log transmit power level for a particular device after read
- *
- * @param address device associated with this event
- * @param handle connection handle of this event,
- * {@link kUnknownConnectionHandle} if unknown
- * @param cmd_status command status from read failed contact counter command
- * @param transmit_power_level transmit power level for connection to this
- * device
- */
-void LogMetricReadTxPowerLevelResult(
- const hci::Address& address, uint16_t handle, uint32_t cmd_status, int32_t transmit_power_level);
-
-/**
- * Logs when there is an event related to Bluetooth Security Manager Protocol
- *
- * @param address address of associated device
- * @param smp_cmd SMP command code associated with this event
- * @param direction direction of this SMP command
- * @param smp_fail_reason SMP pairing failure reason code from SMP spec
- */
-void LogMetricSmpPairingEvent(
- const hci::Address& address, uint8_t smp_cmd, android::bluetooth::DirectionEnum direction, uint8_t smp_fail_reason);
-
-/**
- * Logs there is an event related Bluetooth classic pairing
- *
- * @param address address of associated device
- * @param handle connection handle of this event,
- * {@link kUnknownConnectionHandle} if unknown
- * @param hci_cmd HCI command associated with this event
- * @param hci_event HCI event associated with this event
- * @param cmd_status Command status associated with this event
- * @param reason_code Reason code associated with this event
- * @param event_value A status value related to this specific event
- */
-void LogMetricClassicPairingEvent(
- const hci::Address& address,
- uint16_t handle,
- uint32_t hci_cmd,
- uint16_t hci_event,
- uint16_t cmd_status,
- uint16_t reason_code,
- int64_t event_value);
-
-/**
- * Logs when certain Bluetooth SDP attributes are discovered
- *
- * @param address address of associated device
- * @param protocol_uuid 16 bit protocol UUID from Bluetooth Assigned Numbers
- * @param attribute_id 16 bit attribute ID from Bluetooth Assigned Numbers
- * @param attribute_size size of this attribute
- * @param attribute_value pointer to the attribute data, must be larger than
- * attribute_size
- */
-void LogMetricSdpAttribute(
- const hci::Address& address,
- uint16_t protocol_uuid,
- uint16_t attribute_id,
- size_t attribute_size,
- const char* attribute_value);
-
-/**
- * Logs when there is a change in Bluetooth socket connection state
- *
- * @param address address of associated device, empty if this is a server port
- * @param port port of this socket connection
- * @param type type of socket
- * @param connection_state socket connection state
- * @param tx_bytes number of bytes transmitted
- * @param rx_bytes number of bytes received
- * @param server_port server port of this socket, if any. When both
- * |server_port| and |port| fields are populated, |port| must be spawned
- * by |server_port|
- * @param socket_role role of this socket, server or connection
- * @param uid socket owner's uid
- */
-void LogMetricSocketConnectionState(
- const hci::Address& address,
- int port,
- int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes,
- int64_t rx_bytes,
- int uid,
- int server_port,
- android::bluetooth::SocketRoleEnum socket_role);
-
-/**
- * Logs when a Bluetooth device's manufacturer information is learnt
- *
- * @param address address of associated device
- * @param source_type where is this device info obtained from
- * @param source_name name of the data source, internal or external
- * @param manufacturer name of the manufacturer of this device
- * @param model model of this device
- * @param hardware_version hardware version of this device
- * @param software_version software version of this device
- */
-void LogMetricManufacturerInfo(
- const hci::Address& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer,
- const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version);
-
-/**
- * Logs when received Bluetooth HAL crash reason report.
- *
- * @param address current connected address.
- * @param error_code the crash reason from bluetooth hal
- * @param vendor_error_code the vendor crash reason from bluetooth firmware
- */
-void LogMetricBluetoothHalCrashReason(
- const hci::Address& address,
- uint32_t error_code,
- uint32_t vendor_error_code);
-} // namespace os
-
-} // namespace bluetooth
diff --git a/gd/os/mock_queue.h b/gd/os/mock_queue.h
deleted file mode 100644
index c02488076..000000000
--- a/gd/os/mock_queue.h
+++ /dev/null
@@ -1,100 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <unistd.h>
-
-#include <functional>
-#include <mutex>
-#include <queue>
-
-#include "common/bidi_queue.h"
-#include "common/bind.h"
-#include "common/callback.h"
-#include "os/handler.h"
-#include "os/log.h"
-#include "os/queue.h"
-
-namespace bluetooth {
-namespace os {
-
-template <typename T>
-class MockIQueueEnqueue : public IQueueEnqueue<T> {
- public:
- using EnqueueCallback = common::Callback<std::unique_ptr<T>()>;
-
- virtual void RegisterEnqueue(Handler* handler, EnqueueCallback callback) {
- ASSERT(registered_handler == nullptr);
- registered_handler = handler;
- registered_enqueue_callback = callback;
- }
-
- virtual void UnregisterEnqueue() {
- ASSERT(registered_handler != nullptr);
- registered_handler = nullptr;
- registered_enqueue_callback = {};
- }
-
- void run_enqueue(unsigned times = 1) {
- while (registered_handler != nullptr && times > 0) {
- times--;
- enqueued.push(registered_enqueue_callback.Run());
- }
- }
-
- Handler* registered_handler = nullptr;
- EnqueueCallback registered_enqueue_callback = {};
- std::queue<std::unique_ptr<T>> enqueued = {};
-};
-
-template <typename T>
-class MockIQueueDequeue : public IQueueDequeue<T> {
- public:
- using DequeueCallback = common::Callback<void()>;
-
- virtual void RegisterDequeue(Handler* handler, DequeueCallback callback) {
- ASSERT(registered_handler == nullptr);
- registered_handler = handler;
- registered_dequeue_callback = callback;
- }
-
- virtual void UnregisterDequeue() {
- ASSERT(registered_handler != nullptr);
- registered_handler = nullptr;
- registered_dequeue_callback = {};
- }
-
- virtual std::unique_ptr<T> TryDequeue() {
- std::unique_ptr<T> front = std::move(enqueued.front());
- enqueued.pop();
- return front;
- }
-
- void run_dequeue(unsigned times = 1) {
- while (registered_handler != nullptr && times > 0) {
- times--;
- registered_dequeue_callback.Run();
- }
- }
-
- Handler* registered_handler = nullptr;
- DequeueCallback registered_dequeue_callback = {};
- std::queue<std::unique_ptr<T>> enqueued = {};
-};
-
-} // namespace os
-} // namespace bluetooth
diff --git a/gd/os/parameter_provider.h b/gd/os/parameter_provider.h
deleted file mode 100644
index 72557bbd5..000000000
--- a/gd/os/parameter_provider.h
+++ /dev/null
@@ -1,43 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <string>
-
-namespace bluetooth {
-namespace os {
-
-class ParameterProvider {
- public:
- // Return the path to config file for storage module
- static std::string ConfigFilePath();
-
- static void OverrideConfigFilePath(const std::string& path);
-
- // Return the path to the default snoop log file location
- static std::string SnoopLogFilePath();
-
- static void OverrideSnoopLogFilePath(const std::string& path);
-
- // Return the path to the default snooz log file location
- static std::string SnoozLogFilePath();
-
- static void OverrideSnoozLogFilePath(const std::string& path);
-};
-
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/queue.h b/gd/os/queue.h
index cd8b5543d..1d2af024a 100644
--- a/gd/os/queue.h
+++ b/gd/os/queue.h
@@ -17,7 +17,6 @@
#pragma once
#include <unistd.h>
-
#include <functional>
#include <mutex>
#include <queue>
@@ -37,7 +36,7 @@ namespace os {
template <typename T>
class IQueueEnqueue {
public:
- using EnqueueCallback = common::Callback<std::unique_ptr<T>()>;
+ using EnqueueCallback = Callback<std::unique_ptr<T>()>;
virtual ~IQueueEnqueue() = default;
virtual void RegisterEnqueue(Handler* handler, EnqueueCallback callback) = 0;
virtual void UnregisterEnqueue() = 0;
@@ -47,7 +46,7 @@ class IQueueEnqueue {
template <typename T>
class IQueueDequeue {
public:
- using DequeueCallback = common::Callback<void()>;
+ using DequeueCallback = Callback<void()>;
virtual ~IQueueDequeue() = default;
virtual void RegisterDequeue(Handler* handler, DequeueCallback callback) = 0;
virtual void UnregisterDequeue() = 0;
@@ -59,10 +58,10 @@ class Queue : public IQueueEnqueue<T>, public IQueueDequeue<T> {
public:
// A function moving data from enqueue end buffer to queue, it will be continually be invoked until queue
// is full. Enqueue end should make sure buffer isn't empty and UnregisterEnqueue when buffer become empty.
- using EnqueueCallback = common::Callback<std::unique_ptr<T>()>;
+ using EnqueueCallback = Callback<std::unique_ptr<T>()>;
// A function moving data form queue to dequeue end buffer, it will be continually be invoked until queue
// is empty. TryDequeue should be use in this function to get data from queue.
- using DequeueCallback = common::Callback<void()>;
+ using DequeueCallback = Callback<void()>;
// Create a queue with |capacity| is the maximum number of messages a queue can contain
explicit Queue(size_t capacity);
~Queue();
@@ -107,58 +106,37 @@ class EnqueueBuffer {
public:
EnqueueBuffer(IQueueEnqueue<T>* queue) : queue_(queue) {}
- ~EnqueueBuffer() {
- if (enqueue_registered_.exchange(false)) {
- queue_->UnregisterEnqueue();
- }
- }
-
void Enqueue(std::unique_ptr<T> t, os::Handler* handler) {
std::lock_guard<std::mutex> lock(mutex_);
buffer_.push(std::move(t));
- if (!enqueue_registered_.exchange(true)) {
+ if (buffer_.size() == 1) {
queue_->RegisterEnqueue(handler, common::Bind(&EnqueueBuffer<T>::enqueue_callback, common::Unretained(this)));
}
}
void Clear() {
std::lock_guard<std::mutex> lock(mutex_);
- if (enqueue_registered_.exchange(false)) {
+ if (!buffer_.empty()) {
queue_->UnregisterEnqueue();
std::queue<std::unique_ptr<T>> empty;
std::swap(buffer_, empty);
}
}
- auto Size() const {
- return buffer_.size();
- }
-
- void NotifyOnEmpty(common::OnceClosure callback) {
- std::lock_guard<std::mutex> lock(mutex_);
- ASSERT(callback_on_empty_.is_null());
- callback_on_empty_ = std::move(callback);
- }
-
private:
std::unique_ptr<T> enqueue_callback() {
std::lock_guard<std::mutex> lock(mutex_);
std::unique_ptr<T> enqueued_t = std::move(buffer_.front());
buffer_.pop();
- if (buffer_.empty() && enqueue_registered_.exchange(false)) {
+ if (buffer_.empty()) {
queue_->UnregisterEnqueue();
- if (!callback_on_empty_.is_null()) {
- std::move(callback_on_empty_).Run();
- }
}
return enqueued_t;
}
mutable std::mutex mutex_;
IQueueEnqueue<T>* queue_;
- std::atomic_bool enqueue_registered_ = false;
std::queue<std::unique_ptr<T>> buffer_;
- common::OnceClosure callback_on_empty_;
};
#ifdef OS_LINUX_GENERIC
diff --git a/gd/os/queue_benchmark.cc b/gd/os/queue_benchmark.cc
index 2066aeaa7..0c90fe956 100644
--- a/gd/os/queue_benchmark.cc
+++ b/gd/os/queue_benchmark.cc
@@ -14,9 +14,10 @@
* limitations under the License.
*/
+#include "benchmark/benchmark.h"
+
#include <future>
-#include "benchmark/benchmark.h"
#include "os/handler.h"
#include "os/queue.h"
#include "os/thread.h"
diff --git a/gd/os/rand.h b/gd/os/rand.h
deleted file mode 100644
index 3c38c7466..000000000
--- a/gd/os/rand.h
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <openssl/rand.h>
-
-#include <array>
-
-namespace bluetooth {
-namespace os {
-
-template <size_t SIZE>
-std::array<uint8_t, SIZE> GenerateRandom() {
- std::array<uint8_t, SIZE> ret;
- ASSERT(RAND_bytes(ret.data(), ret.size()) == 1);
- return ret;
-}
-
-inline uint32_t GenerateRandom() {
- uint32_t ret{};
- ASSERT(RAND_bytes((uint8_t*)(&ret), sizeof(uint32_t)) == 1);
- return ret;
-}
-
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/reactor.h b/gd/os/reactor.h
index e61f4f5ae..7e8476b42 100644
--- a/gd/os/reactor.h
+++ b/gd/os/reactor.h
@@ -17,7 +17,6 @@
#pragma once
#include <sys/epoll.h>
-
#include <atomic>
#include <functional>
#include <future>
@@ -31,6 +30,11 @@
namespace bluetooth {
namespace os {
+using common::Callback;
+using common::Closure;
+using common::OnceCallback;
+using common::OnceClosure;
+
// A simple implementation of reactor-style looper.
// When a reactor is running, the main loop is polling and blocked until at least one registered reactable is ready to
// read or write. It will invoke on_read_ready() or on_write_ready(), which is registered with the reactor. Then, it
@@ -57,7 +61,7 @@ class Reactor {
// Register a reactable fd to this reactor. Returns a pointer to a Reactable. Caller must use this object to
// unregister or modify registration. Ownership of the memory space is NOT transferred to user.
- Reactable* Register(int fd, common::Closure on_read_ready, common::Closure on_write_ready);
+ Reactable* Register(int fd, Closure on_read_ready, Closure on_write_ready);
// Unregister a reactable from this reactor
void Unregister(Reactable* reactable);
@@ -65,11 +69,8 @@ class Reactor {
// Wait for up to timeout milliseconds, and return true if the reactable finished executing.
bool WaitForUnregisteredReactable(std::chrono::milliseconds timeout);
- // Wait for up to timeout milliseconds, and return true if we reached idle.
- bool WaitForIdle(std::chrono::milliseconds timeout);
-
// Modify the registration for a reactable with given reactable
- void ModifyRegistration(Reactable* reactable, common::Closure on_read_ready, common::Closure on_write_ready);
+ void ModifyRegistration(Reactable* reactable, Closure on_read_ready, Closure on_write_ready);
private:
mutable std::mutex mutex_;
@@ -77,8 +78,7 @@ class Reactor {
int control_fd_;
std::atomic<bool> is_running_;
std::list<Reactable*> invalidation_list_;
- std::shared_ptr<std::future<void>> executing_reactable_finished_;
- std::shared_ptr<std::promise<void>> idle_promise_;
+ std::unique_ptr<std::future<void>> executing_reactable_finished_;
};
} // namespace os
diff --git a/gd/os/repeating_alarm.h b/gd/os/repeating_alarm.h
index 6b37162cf..cd913445e 100644
--- a/gd/os/repeating_alarm.h
+++ b/gd/os/repeating_alarm.h
@@ -42,13 +42,13 @@ class RepeatingAlarm {
DISALLOW_COPY_AND_ASSIGN(RepeatingAlarm);
// Schedule a repeating alarm with given period
- void Schedule(common::Closure task, std::chrono::milliseconds period);
+ void Schedule(Closure task, std::chrono::milliseconds period);
// Cancel the alarm. No-op if it's not armed.
void Cancel();
private:
- common::Closure task_;
+ Closure task_;
Handler* handler_;
int fd_ = 0;
Reactor::Reactable* token_;
diff --git a/gd/os/system_properties.h b/gd/os/system_properties.h
deleted file mode 100644
index e7a14a395..000000000
--- a/gd/os/system_properties.h
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <optional>
-#include <string>
-
-namespace bluetooth {
-namespace os {
-
-// Get |property| keyed system property from supported platform, return std::nullopt if the property does not exist
-// or if the platform does not support system property
-std::optional<std::string> GetSystemProperty(const std::string& property);
-
-// Set |property| keyed system property to |value|, return true if the set was successful and false if the set failed
-// Replace existing value if property already exists
-bool SetSystemProperty(const std::string& property, const std::string& value);
-
-// Clear system properties for host only
-void ClearSystemPropertiesForHost();
-
-} // namespace os
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/os/thread_benchmark.cc b/gd/os/thread_benchmark.cc
index 7a0e1407b..8d62889ce 100644
--- a/gd/os/thread_benchmark.cc
+++ b/gd/os/thread_benchmark.cc
@@ -19,6 +19,7 @@
#include <thread>
#include "benchmark/benchmark.h"
+
#include "common/bind.h"
#include "os/handler.h"
#include "os/thread.h"
@@ -80,8 +81,8 @@ BENCHMARK_DEFINE_F(BM_ReactorThread, batch_enque_dequeue)(State& state) {
counter_promise_ = std::promise<void>();
std::future<void> counter_future = counter_promise_.get_future();
for (int i = 0; i < num_messages_to_send_; i++) {
- handler_->Post(BindOnce(
- &BM_ReactorThread_batch_enque_dequeue_Benchmark::callback_batch, bluetooth::common::Unretained(this)));
+ handler_->Post(BindOnce(&BM_ReactorThread_batch_enque_dequeue_Benchmark::callback_batch,
+ bluetooth::common::Unretained(this)));
}
counter_future.wait();
}
diff --git a/gd/os/wakelock_manager.fbs b/gd/os/wakelock_manager.fbs
deleted file mode 100644
index 7b85e2804..000000000
--- a/gd/os/wakelock_manager.fbs
+++ /dev/null
@@ -1,26 +0,0 @@
-
-namespace bluetooth.os;
-
-attribute "privacy";
-
-table WakelockManagerData {
- title:string;
- is_acquired:bool;
- is_native:bool;
- acquired_count:int;
- released_count:int;
- acquired_error_count:int;
- released_error_count:int;
- last_acquire_error_code:int;
- last_release_error_code:int;
- last_acquired_timestamp_millis:int64;
- last_released_timestamp_millis:int64;
- last_interval_millis:int64;
- max_interval_millis:int64;
- min_interval_millis:int64;
- avg_interval_millis:int64;
- total_interval_millis:int64;
- total_time_since_reset_millis:int64;
-}
-
-root_type WakelockManagerData;
diff --git a/gd/os/wakelock_manager.h b/gd/os/wakelock_manager.h
deleted file mode 100644
index 77645c3a7..000000000
--- a/gd/os/wakelock_manager.h
+++ /dev/null
@@ -1,94 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2021 Google, Inc.
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#pragma once
-
-#include <memory>
-#include <mutex>
-#include <string>
-
-#include <flatbuffers/flatbuffers.h>
-
-#include "handler.h"
-#include "wakelock_manager_generated.h"
-
-namespace bluetooth {
-namespace os {
-
-class WakelockManager {
- public:
- static const std::string kBtWakelockId;
-
- static WakelockManager& Get() {
- static WakelockManager instance;
- return instance;
- }
-
- // The set of functions required by GD to grab wake locks. A caller with a custom wakelock implementation should
- // implement this class and passed into the stack through SetCallouts()
- class OsCallouts {
- public:
- virtual ~OsCallouts() = default;
- virtual void AcquireCallout(const std::string& lock_name) = 0;
- virtual void ReleaseCallout(const std::string& lock_name) = 0;
- };
-
- // Set the Bluetooth OS callouts to |callouts|.
- //
- // This function should be called when native kernel wakelock are not used directly.
- // If this function is not called, or |callouts| is nullptr, then native kernel wakelock will be used.
- // When |callouts| are used, the callbacks are going to be invoked asynchronously to avoid being blocked by upper
- // layer delays. Therefore, a handler is needed and the callout result will be ignored.
- //
- // This method must be called before calling Acquire() or Release()
- void SetOsCallouts(OsCallouts* callouts, Handler* handler);
-
- // Acquire the Bluetooth wakelock.
- // Return true on success, otherwise false.
- // The function is thread safe.
- bool Acquire();
-
- // Release the Bluetooth wakelock.
- // Return true on success, otherwise false.
- // The function is thread safe.
- bool Release();
-
- // Cleanup the wakelock internal runtime state.
- // This will NOT clean up the callouts
- void CleanUp();
-
- // Dump wakelock-related debug info to a flat buffer defined in wakelock_manager.fbs
- flatbuffers::Offset<WakelockManagerData> GetDumpsysData(flatbuffers::FlatBufferBuilder* fb_builder);
-
- ~WakelockManager();
-
- private:
- WakelockManager();
-
- std::recursive_mutex mutex_;
- bool initialized_ = false;
- OsCallouts* os_callouts_ = nullptr;
- Handler* os_callouts_handler_ = nullptr;
- bool is_native_ = true;
-
- struct Stats;
- std::unique_ptr<Stats> pstats_;
-};
-
-} // namespace os
-} // namespace bluetooth
diff --git a/gd/packet/Android.bp b/gd/packet/Android.bp
index 670592c12..c9ddb7ac8 100644
--- a/gd/packet/Android.bp
+++ b/gd/packet/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothPacketSources",
srcs: [
diff --git a/gd/packet/BUILD.gn b/gd/packet/BUILD.gn
deleted file mode 100644
index 6d786b7c3..000000000
--- a/gd/packet/BUILD.gn
+++ /dev/null
@@ -1,32 +0,0 @@
-#
-# Copyright 2021 Google
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-source_set("BluetoothPacketSources") {
- sources = [
- "bit_inserter.cc",
- "byte_inserter.cc",
- "byte_observer.cc",
- "fragmenting_inserter.cc",
- "iterator.cc",
- "packet_view.cc",
- "raw_builder.cc",
- "view.cc",
- ]
-
- include_dirs = [ "//bt/gd" ]
-
- configs += [ "//bt:target_defaults" ]
-}
diff --git a/gd/packet/base_packet_builder.h b/gd/packet/base_packet_builder.h
index cf24dc1db..f0933851a 100644
--- a/gd/packet/base_packet_builder.h
+++ b/gd/packet/base_packet_builder.h
@@ -38,18 +38,8 @@ class BasePacketBuilder {
// Write to the vector with the given iterator.
virtual void Serialize(BitInserter& it) const = 0;
- void SetFlushable(bool is_flushable) {
- is_flushable_ = is_flushable;
- }
- bool IsFlushable() const {
- return is_flushable_;
- }
-
protected:
BasePacketBuilder() = default;
-
- private:
- bool is_flushable_{false};
};
} // namespace packet
diff --git a/gd/packet/bit_inserter.h b/gd/packet/bit_inserter.h
index 29d840815..487eba524 100644
--- a/gd/packet/bit_inserter.h
+++ b/gd/packet/bit_inserter.h
@@ -28,8 +28,8 @@ namespace packet {
class BitInserter : public ByteInserter {
public:
- explicit BitInserter(std::vector<uint8_t>& vector);
- ~BitInserter();
+ BitInserter(std::vector<uint8_t>& vector);
+ ~BitInserter() override;
virtual void insert_bits(uint8_t byte, size_t num_bits);
diff --git a/gd/packet/byte_inserter.h b/gd/packet/byte_inserter.h
index 00787d603..6d33aee94 100644
--- a/gd/packet/byte_inserter.h
+++ b/gd/packet/byte_inserter.h
@@ -28,7 +28,7 @@ namespace packet {
class ByteInserter : public std::back_insert_iterator<std::vector<uint8_t>> {
public:
- explicit ByteInserter(std::vector<uint8_t>& vector);
+ ByteInserter(std::vector<uint8_t>& vector);
virtual ~ByteInserter();
virtual void insert_byte(uint8_t byte);
diff --git a/gd/packet/custom_field_fixed_size_interface.h b/gd/packet/custom_field_fixed_size_interface.h
deleted file mode 100644
index c342bc92b..000000000
--- a/gd/packet/custom_field_fixed_size_interface.h
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <cstdint>
-#include <type_traits>
-
-namespace bluetooth {
-namespace packet {
-
-template <typename T>
-class CustomFieldFixedSizeInterface {
- public:
- virtual ~CustomFieldFixedSizeInterface() = default;
- // Get a pointer to a modifiable and readable continuous array of data
- virtual uint8_t* data() = 0;
- virtual const uint8_t* data() const = 0;
- // Get the length of underlying data array, data() + length() would be invalid
- // subclass T must have kLength variable defined
- static constexpr size_t length() {
- static_assert(
- std::is_same_v<decltype(T::kLength), const size_t>, "T::kLength must be const size_t or constexpr size_t");
- static_assert(std::is_const_v<decltype(T::kLength)>, "T::kLength must be const");
- return T::kLength;
- };
-};
-
-} // namespace packet
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/packet/endian_inserter.h b/gd/packet/endian_inserter.h
index e4eab5326..317c12c8c 100644
--- a/gd/packet/endian_inserter.h
+++ b/gd/packet/endian_inserter.h
@@ -24,7 +24,6 @@
#include "os/log.h"
#include "packet/bit_inserter.h"
-#include "packet/custom_field_fixed_size_interface.h"
namespace bluetooth {
namespace packet {
@@ -38,7 +37,7 @@ class EndianInserter {
virtual ~EndianInserter() = default;
protected:
- // Write sizeof(FixedWidthPODType) bytes using the iterator
+ // Write sizeof(FixedWidthIntegerType) bytes using the iterator
template <typename FixedWidthPODType, typename std::enable_if<std::is_pod<FixedWidthPODType>::value, int>::type = 0>
void insert(FixedWidthPODType value, BitInserter& it) const {
uint8_t* raw_bytes = (uint8_t*)&value;
@@ -51,21 +50,6 @@ class EndianInserter {
}
}
- // Write sizeof(FixedWidthCustomType) bytes using the iterator
- template <
- typename T,
- typename std::enable_if<std::is_base_of<CustomFieldFixedSizeInterface<T>, T>::value, int>::type = 0>
- void insert(const T& value, BitInserter& it) const {
- auto* raw_bytes = value.data();
- for (size_t i = 0; i < CustomFieldFixedSizeInterface<T>::length(); i++) {
- if (little_endian == true) {
- it.insert_byte(raw_bytes[i]);
- } else {
- it.insert_byte(raw_bytes[CustomFieldFixedSizeInterface<T>::length() - i - 1]);
- }
- }
- }
-
// Write num_bits bits using the iterator
template <typename FixedWidthIntegerType,
typename std::enable_if<std::is_pod<FixedWidthIntegerType>::value, int>::type = 0>
diff --git a/gd/packet/iterator.cc b/gd/packet/iterator.cc
index 7551b794b..f924b055a 100644
--- a/gd/packet/iterator.cc
+++ b/gd/packet/iterator.cc
@@ -22,7 +22,7 @@ namespace bluetooth {
namespace packet {
template <bool little_endian>
-Iterator<little_endian>::Iterator(const std::forward_list<View>& data, size_t offset) {
+Iterator<little_endian>::Iterator(std::forward_list<View> data, size_t offset) {
data_ = data;
index_ = offset;
begin_ = 0;
@@ -46,6 +46,13 @@ Iterator<little_endian>& Iterator<little_endian>::operator+=(int offset) {
}
template <bool little_endian>
+Iterator<little_endian> Iterator<little_endian>::operator++(int) {
+ auto itr(*this);
+ index_++;
+ return itr;
+}
+
+template <bool little_endian>
Iterator<little_endian>& Iterator<little_endian>::operator++() {
index_++;
return *this;
@@ -71,6 +78,14 @@ Iterator<little_endian>& Iterator<little_endian>::operator-=(int offset) {
}
template <bool little_endian>
+Iterator<little_endian> Iterator<little_endian>::operator--(int) {
+ auto itr(*this);
+ if (index_ != 0) index_--;
+
+ return itr;
+}
+
+template <bool little_endian>
Iterator<little_endian>& Iterator<little_endian>::operator--() {
if (index_ != 0) index_--;
@@ -79,7 +94,6 @@ Iterator<little_endian>& Iterator<little_endian>::operator--() {
template <bool little_endian>
Iterator<little_endian>& Iterator<little_endian>::operator=(const Iterator<little_endian>& itr) {
- if (this == &itr) return *this;
this->data_ = itr.data_;
this->begin_ = itr.begin_;
this->end_ = itr.end_;
diff --git a/gd/packet/iterator.h b/gd/packet/iterator.h
index 13a277dfa..8d927a06a 100644
--- a/gd/packet/iterator.h
+++ b/gd/packet/iterator.h
@@ -19,9 +19,7 @@
#include <cstdint>
#include <forward_list>
#include <memory>
-#include <type_traits>
-#include "packet/custom_field_fixed_size_interface.h"
#include "packet/view.h"
namespace bluetooth {
@@ -31,18 +29,20 @@ namespace packet {
template <bool little_endian>
class Iterator : public std::iterator<std::random_access_iterator_tag, uint8_t> {
public:
- Iterator(const std::forward_list<View>& data, size_t offset);
+ Iterator(std::forward_list<View> data, size_t offset);
Iterator(const Iterator& itr) = default;
virtual ~Iterator() = default;
// All addition and subtraction operators are unbounded.
Iterator operator+(int offset);
Iterator& operator+=(int offset);
+ Iterator operator++(int);
Iterator& operator++();
Iterator operator-(int offset);
int operator-(Iterator& itr);
Iterator& operator-=(int offset);
+ Iterator operator--(int);
Iterator& operator--();
Iterator& operator=(const Iterator& itr);
@@ -57,33 +57,22 @@ class Iterator : public std::iterator<std::random_access_iterator_tag, uint8_t>
bool operator>=(const Iterator& itr) const;
uint8_t operator*() const;
+ uint8_t operator->() const;
size_t NumBytesRemaining() const;
Iterator Subrange(size_t index, size_t length) const;
// Get the next sizeof(FixedWidthPODType) bytes and return the filled type
- template <typename FixedWidthPODType, typename std::enable_if<std::is_pod<FixedWidthPODType>::value, int>::type = 0>
+ template <typename FixedWidthPODType>
FixedWidthPODType extract() {
static_assert(std::is_pod<FixedWidthPODType>::value, "Iterator::extract requires a fixed-width type.");
- FixedWidthPODType extracted_value{};
+ FixedWidthPODType extracted_value;
uint8_t* value_ptr = (uint8_t*)&extracted_value;
for (size_t i = 0; i < sizeof(FixedWidthPODType); i++) {
size_t index = (little_endian ? i : sizeof(FixedWidthPODType) - i - 1);
- value_ptr[index] = this->operator*();
- this->operator++();
- }
- return extracted_value;
- }
-
- template <typename T, typename std::enable_if<std::is_base_of_v<CustomFieldFixedSizeInterface<T>, T>, int>::type = 0>
- T extract() {
- T extracted_value{};
- for (size_t i = 0; i < CustomFieldFixedSizeInterface<T>::length(); i++) {
- size_t index = (little_endian ? i : CustomFieldFixedSizeInterface<T>::length() - i - 1);
- extracted_value.data()[index] = this->operator*();
- this->operator++();
+ value_ptr[index] = *((*this)++);
}
return extracted_value;
}
diff --git a/gd/packet/packet_view.h b/gd/packet/packet_view.h
index a3ce7d038..304794c85 100644
--- a/gd/packet/packet_view.h
+++ b/gd/packet/packet_view.h
@@ -33,10 +33,9 @@ static const bool kLittleEndian = true;
template <bool little_endian>
class PacketView {
public:
- explicit PacketView(std::forward_list<View> fragments);
+ PacketView(const std::forward_list<class View> fragments);
PacketView(const PacketView& PacketView) = default;
- explicit PacketView(std::shared_ptr<std::vector<uint8_t>> packet);
- PacketView<little_endian>() = delete;
+ PacketView(std::shared_ptr<std::vector<uint8_t>> packet);
virtual ~PacketView() = default;
virtual Iterator<little_endian> begin() const;
@@ -59,6 +58,7 @@ class PacketView {
private:
std::forward_list<View> fragments_;
size_t length_;
+ PacketView<little_endian>() = delete;
std::forward_list<View> GetSubviewList(size_t begin, size_t end) const;
};
diff --git a/gd/packet/packet_view_unittest.cc b/gd/packet/packet_view_unittest.cc
index 208784e79..0ec2ef472 100644
--- a/gd/packet/packet_view_unittest.cc
+++ b/gd/packet/packet_view_unittest.cc
@@ -55,13 +55,13 @@ template <typename T>
class IteratorTest : public ::testing::Test {
public:
IteratorTest() = default;
- ~IteratorTest() override = default;
+ ~IteratorTest() = default;
- void SetUp() override {
+ void SetUp() {
packet = std::shared_ptr<T>(new T({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())}));
}
- void TearDown() override {
+ void TearDown() {
packet.reset();
}
@@ -74,7 +74,7 @@ TYPED_TEST_CASE(IteratorTest, PacketViewTypes);
class IteratorExtractTest : public ::testing::Test {
public:
IteratorExtractTest() = default;
- ~IteratorExtractTest() override = default;
+ ~IteratorExtractTest() = default;
};
template <typename T>
@@ -90,7 +90,7 @@ TYPED_TEST_CASE(PacketViewTest, PacketViewTypes);
class PacketViewMultiViewTest : public ::testing::Test {
public:
PacketViewMultiViewTest() = default;
- ~PacketViewMultiViewTest() override = default;
+ ~PacketViewMultiViewTest() = default;
const PacketView<true> single_view =
PacketView<true>({View(std::make_shared<const vector<uint8_t>>(count_all), 0, count_all.size())});
@@ -104,7 +104,7 @@ class PacketViewMultiViewTest : public ::testing::Test {
class PacketViewMultiViewAppendTest : public ::testing::Test {
public:
PacketViewMultiViewAppendTest() = default;
- ~PacketViewMultiViewAppendTest() override = default;
+ ~PacketViewMultiViewAppendTest() = default;
class AppendedPacketView : public PacketView<true> {
public:
@@ -126,7 +126,7 @@ class PacketViewMultiViewAppendTest : public ::testing::Test {
class ViewTest : public ::testing::Test {
public:
ViewTest() = default;
- ~ViewTest() override = default;
+ ~ViewTest() = default;
};
TEST(IteratorExtractTest, extractLeTest) {
@@ -192,10 +192,8 @@ TYPED_TEST(IteratorTest, preIncrementTest) {
TYPED_TEST(IteratorTest, postIncrementTest) {
auto plus_plus = this->packet->begin();
for (size_t i = 0; i < count_all.size(); i++) {
- ASSERT_EQ(count_all[i], plus_plus.operator*())
- << "Post-increment test: Dereferenced iterator does not equal expected "
- << "at index " << i;
- plus_plus.operator++();
+ ASSERT_EQ(count_all[i], *(plus_plus++)) << "Post-increment test: Dereferenced iterator does not equal expected "
+ << "at index " << i;
}
}
@@ -230,12 +228,10 @@ TYPED_TEST(IteratorTest, preDecrementTest) {
TYPED_TEST(IteratorTest, postDecrementTest) {
auto minus_minus = this->packet->end();
- minus_minus.operator--();
+ minus_minus--;
for (size_t i = count_all.size() - 1; i > 0; i--) {
- ASSERT_EQ(count_all[i], minus_minus.operator*())
- << "Post-decrement test: Dereferenced iterator does not equal expected "
- << "at index " << i;
- minus_minus.operator--();
+ ASSERT_EQ(count_all[i], *(minus_minus--)) << "Post-decrement test: Dereferenced iterator does not equal expected "
+ << "at index " << i;
}
}
@@ -312,16 +308,14 @@ TYPED_TEST(IteratorTest, numBytesRemainingTest) {
size_t remaining = all.NumBytesRemaining();
for (size_t n = remaining; n > 0; n--) {
ASSERT_EQ(remaining, all.NumBytesRemaining());
- all.operator++();
+ all++;
remaining--;
}
ASSERT_EQ(static_cast<size_t>(0), all.NumBytesRemaining());
- all.operator++();
- ASSERT_DEATH(all.operator*(), "");
- all.operator++();
+ ASSERT_DEATH(*(all++), "");
+ all++;
ASSERT_EQ(static_cast<size_t>(0), all.NumBytesRemaining());
- all.operator++();
- ASSERT_DEATH(all.operator*(), "");
+ ASSERT_DEATH(*(all++), "");
}
TYPED_TEST(IteratorTest, subrangeTest) {
@@ -527,9 +521,7 @@ TEST_F(PacketViewMultiViewTest, dereferenceTestLittleEndian) {
auto single_itr = single_view.begin();
auto multi_itr = multi_view.begin();
for (size_t i = 0; i < single_view.size(); i++) {
- ASSERT_EQ(single_itr.operator*(), multi_itr.operator*());
- single_itr.operator++();
- multi_itr.operator++();
+ ASSERT_EQ(*(single_itr++), *(multi_itr++));
}
ASSERT_DEATH(*multi_itr, "");
}
@@ -538,9 +530,7 @@ TEST_F(PacketViewMultiViewTest, dereferenceTestBigEndian) {
auto single_itr = single_view.begin();
auto multi_itr = multi_view.begin();
for (size_t i = 0; i < single_view.size(); i++) {
- ASSERT_EQ(single_itr.operator*(), multi_itr.operator*());
- single_itr.operator++();
- multi_itr.operator++();
+ ASSERT_EQ(*(single_itr++), *(multi_itr++));
}
ASSERT_DEATH(*multi_itr, "");
}
@@ -560,9 +550,7 @@ TEST_F(PacketViewMultiViewAppendTest, dereferenceTestLittleEndianAppend) {
auto single_itr = single_view.begin();
auto multi_itr = multi_view.begin();
for (size_t i = 0; i < single_view.size(); i++) {
- ASSERT_EQ(single_itr.operator*(), multi_itr.operator*());
- single_itr.operator++();
- multi_itr.operator++();
+ ASSERT_EQ(*(single_itr++), *(multi_itr++));
}
ASSERT_DEATH(*multi_itr, "");
}
@@ -571,9 +559,7 @@ TEST_F(PacketViewMultiViewAppendTest, dereferenceTestBigEndianAppend) {
auto single_itr = single_view.begin();
auto multi_itr = multi_view.begin();
for (size_t i = 0; i < single_view.size(); i++) {
- ASSERT_EQ(single_itr.operator*(), multi_itr.operator*());
- single_itr.operator++();
- multi_itr.operator++();
+ ASSERT_EQ(*(single_itr++), *(multi_itr++));
}
ASSERT_DEATH(*multi_itr, "");
}
diff --git a/gd/packet/parser/Android.bp b/gd/packet/parser/Android.bp
index c54e47ddd..97f323a45 100644
--- a/gd/packet/parser/Android.bp
+++ b/gd/packet/parser/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_binary_host {
name: "bluetooth_packetgen",
srcs: [
@@ -42,12 +33,18 @@ cc_binary_host {
"main.cc",
"language_y.yy",
"language_l.ll",
- "gen_cpp.cc",
- "gen_rust.cc",
],
static_libs: [
"libc++fs",
],
+ cppflags: [
+ "-fno-exceptions",
+ "-O0",
+ ],
+ ldflags: [
+ "-fuse-ld=ld",
+ "-O0",
+ ],
yacc: {
gen_location_hh: true,
gen_position_hh: true,
diff --git a/gd/packet/parser/BUILD.gn b/gd/packet/parser/BUILD.gn
deleted file mode 100644
index dd4f3b097..000000000
--- a/gd/packet/parser/BUILD.gn
+++ /dev/null
@@ -1,87 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-import("flex.gni")
-import("bison.gni")
-
-config("pktgen_configs") {
- include_dirs = [ "//bt/gd/packet/parser" ]
-
- cflags = [ "-fPIC" ]
-
- cflags_cc = [
- "-std=c++17",
- "-Wno-inconsistent-missing-override",
- "-Wno-implicit-fallthrough",
- "-Wno-poison-system-directories",
- "-Wno-unknown-warning-option",
- ]
-}
-
-executable("bluetooth_packetgen") {
- sources = [
- "checksum_def.cc",
- "custom_field_def.cc",
- "enum_def.cc",
- "enum_gen.cc",
- "fields/array_field.cc",
- "fields/body_field.cc",
- "fields/checksum_field.cc",
- "fields/checksum_start_field.cc",
- "fields/count_field.cc",
- "fields/custom_field.cc",
- "fields/custom_field_fixed_size.cc",
- "fields/enum_field.cc",
- "fields/fixed_enum_field.cc",
- "fields/fixed_field.cc",
- "fields/fixed_scalar_field.cc",
- "fields/group_field.cc",
- "fields/packet_field.cc",
- "fields/padding_field.cc",
- "fields/payload_field.cc",
- "fields/reserved_field.cc",
- "fields/scalar_field.cc",
- "fields/size_field.cc",
- "fields/struct_field.cc",
- "fields/variable_length_struct_field.cc",
- "fields/vector_field.cc",
- "gen_cpp.cc",
- "gen_rust.cc",
- "main.cc",
- "packet_def.cc",
- "parent_def.cc",
- "struct_def.cc",
- "struct_parser_generator.cc",
- ]
-
- include_dirs = [ "//bt/gd/packet/parser" ]
-
- deps = [
- ":pktlexer",
- ":pktparser",
- ]
- configs += [ ":pktgen_configs" ]
-}
-
-flex_source("pktlexer") {
- sources = [ "language_l.ll" ]
- configs = [ ":pktgen_configs" ]
-}
-
-bison_source("pktparser") {
- sources = [ "language_y.yy" ]
- configs = [ ":pktgen_configs" ]
-}
diff --git a/gd/packet/parser/README b/gd/packet/parser/README
index df9e99fca..9006c941e 100644
--- a/gd/packet/parser/README
+++ b/gd/packet/parser/README
@@ -14,11 +14,11 @@ Packet Views and Builders
Checksum types
checksum MyChecksumClass : 16 "path/to/the/class/"
- Checksum fields need to implement the following three methods:
- void Initialize(MyChecksumClass&);
- void AddByte(MyChecksumClass&, uint8_t);
+ Checksum fields need to implement the following three static methods:
+ static void Initialize(MyChecksumClass&);
+ static void AddByte(MyChecksumClass&, uint8_t);
// Assuming a 16-bit (uint16_t) checksum:
- uint16_t GetChecksum(MyChecksumClass&);
+ static uint16_t GetChecksum(MyChecksumClass&);
-------------
LIMITATIONS
-------------
@@ -51,13 +51,9 @@ One pdl file will result in one header file with all the packets
Things to cover -
Constraints
- Inheritance vs Contains
+ Inheritence vs Contains
-Custom fields with fixed size must extend and implement:
- packet::CustomFieldFixedSizeInterface
-
-Custom fields with variable size need the following functions:
+Custom fields need the folowing functions:
static void Serialize(const Type&, MutableView&);
static std::optional<size_t> Size(Iterator);
static Type Parse(Iterator);
- std::string ToString(); \ No newline at end of file
diff --git a/gd/packet/parser/bison.gni b/gd/packet/parser/bison.gni
deleted file mode 100644
index b52541b32..000000000
--- a/gd/packet/parser/bison.gni
+++ /dev/null
@@ -1,75 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-# Bison is a parser generator which reads a specification of a context-free
-# language and generates a parser which decides whether the input conforms to
-# the grammar specified.
-
-# Generate header and source files using Bison.
-#
-# Note: We generate C++ output for Bison. We also set --language to C++
-# (equivalent to %language c++) which forces Bison to generate a C++ parser.
-#
-# Parameters:
-# sources: Grammar files used to generate the parsers.
-template("bison_source") {
- action_name = "${target_name}_gen"
- action_foreach(action_name) {
- forward_variables_from(invoker, [ "sources" ])
- assert(defined(sources), "sources must be set")
- foreach(s, sources) {
- assert(get_path_info(s, "extension") == "yy",
- "Expecting Bison extension yy: ${s}")
- }
-
- script = "//common-mk/file_generator_wrapper.py"
- outprefix = "${target_gen_dir}/{{source_name_part}}"
- args = [
- "bison",
- "--language=c++",
- "--defines=${outprefix}.h",
- "-o",
- "${outprefix}.cc",
- "{{source}}",
- ]
- outputs = [
- "${outprefix}.h",
- "${outprefix}.cc",
- ]
- }
-
- all_dependent_config_name = "_${target_name}_all_dependent_config"
- config(all_dependent_config_name) {
- include_dirs = [ "${target_gen_dir}" ]
- }
-
- source_set(target_name) {
- sources = get_target_outputs(":${action_name}")
- all_dependent_configs = [ ":${all_dependent_config_name}" ]
- deps = [ ":${action_name}" ]
-
- if (defined(invoker.configs)) {
- configs += invoker.configs
- }
-
- # Silence some warnings. The autogenerated code includes parts that have
- # fallthroughs and unreachable code. This may silence legitimate issues in
- # user written code in the grammar files as well. User beware!
- cflags_cc = [
- "-Wno-implicit-fallthrough",
- "-Wno-unreachable-code",
- ]
- }
-}
diff --git a/gd/packet/parser/custom_field_def.cc b/gd/packet/parser/custom_field_def.cc
index 2d7a6fd9a..fb027c202 100644
--- a/gd/packet/parser/custom_field_def.cc
+++ b/gd/packet/parser/custom_field_def.cc
@@ -61,14 +61,6 @@ void CustomFieldDef::GenUsing(std::ostream& s) const {
s << GetTypeName() << ";";
}
-void CustomFieldDef::GenFixedSizeCustomFieldCheck(std::ostream& s) const {
- s << "static_assert(std::is_base_of_v<CustomFieldFixedSizeInterface<" << name_ << ">, " << name_ << ">, \"";
- s << name_ << " is not a valid fixed size custom field type. Please see README for more details.\");";
- s << "static_assert(CustomFieldFixedSizeInterface<" << name_ << ">::length() * 8 == " << size_
- << ", \"CustomFieldFixedSizeInterface<" << name_ << ">::length * 8 should match PDL defined size (in bits) "
- << size_ << "\");";
-}
-
void CustomFieldDef::GenCustomFieldCheck(std::ostream& s, bool little_endian) const {
s << "static_assert(CustomTypeChecker<" << name_ << ", ";
s << (little_endian ? "" : "!") << "kLittleEndian>::value, \"";
diff --git a/gd/packet/parser/custom_field_def.h b/gd/packet/parser/custom_field_def.h
index 033801acf..f28b116e3 100644
--- a/gd/packet/parser/custom_field_def.h
+++ b/gd/packet/parser/custom_field_def.h
@@ -39,8 +39,6 @@ class CustomFieldDef : public TypeDef {
void GenUsing(std::ostream& s) const;
- void GenFixedSizeCustomFieldCheck(std::ostream& s) const;
-
void GenCustomFieldCheck(std::ostream& s, bool little_endian) const;
const std::string include_;
diff --git a/gd/packet/parser/custom_type_checker.h b/gd/packet/parser/custom_type_checker.h
index 31b466076..5d9962259 100644
--- a/gd/packet/parser/custom_type_checker.h
+++ b/gd/packet/parser/custom_type_checker.h
@@ -36,17 +36,14 @@ class CustomTypeChecker {
template <class C, bool little_endian, std::optional<Iterator<little_endian>> (*)(C* vec, Iterator<little_endian> it)>
struct ParseChecker {};
- template <class C, std::string (C::*)() const>
- struct ToStringChecker {};
-
template <class C, bool little_endian>
static int Test(SerializeChecker<C, &C::Serialize>*, SizeChecker<C, &C::size>*,
- ParseChecker<C, little_endian, &C::Parse>*, ToStringChecker<C, &C::ToString>*);
+ ParseChecker<C, little_endian, &C::Parse>*);
template <class C, bool little_endian>
static char Test(...);
- static constexpr bool value = (sizeof(Test<T, packet_little_endian>(0, 0, 0, 0)) == sizeof(int));
+ static constexpr bool value = (sizeof(Test<T, packet_little_endian>(0, 0, 0)) == sizeof(int));
};
} // namespace packet
} // namespace bluetooth
diff --git a/gd/packet/parser/declarations.h b/gd/packet/parser/declarations.h
index 6d892765f..549ddc439 100644
--- a/gd/packet/parser/declarations.h
+++ b/gd/packet/parser/declarations.h
@@ -47,7 +47,7 @@ class Declarations {
return it->second;
}
- void AddPacketDef(std::string name, PacketDef* def) {
+ void AddPacketDef(std::string name, PacketDef def) {
auto it = packet_defs_.find(name);
if (it != packet_defs_.end()) {
ERROR() << "Redefinition of Packet " << name;
@@ -62,7 +62,7 @@ class Declarations {
return nullptr;
}
- return it->second;
+ return &(it->second);
}
void AddGroupDef(std::string name, FieldList* group_def) {
@@ -85,7 +85,7 @@ class Declarations {
std::map<std::string, TypeDef*> type_defs_;
std::deque<std::pair<std::string, TypeDef*>> type_defs_queue_;
- std::map<std::string, PacketDef*> packet_defs_;
- std::deque<std::pair<std::string, PacketDef*>> packet_defs_queue_;
+ std::map<std::string, PacketDef> packet_defs_;
+ std::deque<std::pair<std::string, PacketDef>> packet_defs_queue_;
bool is_little_endian;
};
diff --git a/gd/packet/parser/enum_def.h b/gd/packet/parser/enum_def.h
index c8f4348e7..5698d0fc5 100644
--- a/gd/packet/parser/enum_def.h
+++ b/gd/packet/parser/enum_def.h
@@ -39,6 +39,4 @@ class EnumDef : public TypeDef {
// data
std::map<uint32_t, std::string> constants_;
std::set<std::string> entries_;
-
- EnumDef* try_from_enum_ = nullptr;
};
diff --git a/gd/packet/parser/enum_gen.cc b/gd/packet/parser/enum_gen.cc
index ee12c90bd..4bd5a2615 100644
--- a/gd/packet/parser/enum_gen.cc
+++ b/gd/packet/parser/enum_gen.cc
@@ -59,33 +59,3 @@ void EnumGen::GenLogging(std::ostream& stream) {
stream << " return os << " << e_.name_ << "Text(param);";
stream << "}\n";
}
-
-void EnumGen::GenRustDef(std::ostream& stream) {
- stream << "#[derive(FromPrimitive, ToPrimitive, Debug, Hash, Eq, PartialEq, Clone, Copy)]\n";
- stream << "pub enum " << e_.name_ << " {";
- for (const auto& pair : e_.constants_) {
- stream << util::ConstantCaseToCamelCase(pair.second) << " = 0x" << std::hex << pair.first << std::dec << ",";
- }
- stream << "}";
-
- if (e_.try_from_enum_ != nullptr) {
- std::vector<std::string> other_items;
- for (const auto& pair : e_.try_from_enum_->constants_) {
- other_items.push_back(pair.second);
- }
- stream << "impl TryFrom<" << e_.try_from_enum_->name_ << "> for " << e_.name_ << " {";
- stream << "type Error = &'static str;";
- stream << "fn try_from(value: " << e_.try_from_enum_->name_ << ") -> std::result::Result<Self, Self::Error> {";
- stream << "match value {";
- for (const auto& pair : e_.constants_) {
- if (std::find(other_items.begin(), other_items.end(), pair.second) == other_items.end()) {
- continue;
- }
- auto constant_name = util::ConstantCaseToCamelCase(pair.second);
- stream << e_.try_from_enum_->name_ << "::" << constant_name << " => Ok(" << e_.name_ << "::" << constant_name
- << "),";
- }
- stream << "_ => Err(\"No mapping for provided key\"),";
- stream << "}}}";
- }
-}
diff --git a/gd/packet/parser/enum_gen.h b/gd/packet/parser/enum_gen.h
index 5586dfcdb..be1655985 100644
--- a/gd/packet/parser/enum_gen.h
+++ b/gd/packet/parser/enum_gen.h
@@ -31,7 +31,5 @@ class EnumGen {
void GenLogging(std::ostream& stream);
- void GenRustDef(std::ostream& stream);
-
EnumDef e_;
};
diff --git a/gd/packet/parser/fields/array_field.cc b/gd/packet/parser/fields/array_field.cc
index c856e5b71..37dea1683 100644
--- a/gd/packet/parser/fields/array_field.cc
+++ b/gd/packet/parser/fields/array_field.cc
@@ -96,7 +96,7 @@ void ArrayField::GenExtractor(std::ostream& s, int num_leading_bits, bool for_st
if (element_field_->BuilderParameterMustBeMoved()) {
s << element_field_->GetDataType() << " " << element_field_->GetName() << "_ptr;";
} else {
- s << "auto " << element_field_->GetName() << "_ptr = ret_it;";
+ s << element_field_->GetDataType() << "* " << element_field_->GetName() << "_ptr = ret_it;";
}
element_field_->GenExtractor(s, num_leading_bits, for_struct);
if (element_field_->BuilderParameterMustBeMoved()) {
@@ -119,7 +119,7 @@ void ArrayField::GenGetter(std::ostream& s, Size start_offset, Size end_offset)
s << "auto to_bound = begin();";
int num_leading_bits = GenBounds(s, start_offset, end_offset, GetSize());
- s << GetDataType() << " " << GetName() << "_value{};";
+ s << GetDataType() << " " << GetName() << "_value;";
s << GetDataType() << "* " << GetName() << "_ptr = &" << GetName() << "_value;";
GenExtractor(s, num_leading_bits, false);
@@ -175,38 +175,3 @@ bool ArrayField::IsContainerField() const {
const PacketField* ArrayField::GetElementField() const {
return element_field_;
}
-
-void ArrayField::GenStringRepresentation(std::ostream& s, std::string accessor) const {
- s << "\"ARRAY[\";";
- s << "/* " << element_field_->GetDataType() << " " << element_field_->GetFieldType() << " */";
-
- std::string arr_idx = "arridx_" + accessor;
- std::string arr_size = std::to_string(array_size_);
- s << "for (size_t index = 0; index < " << arr_size << "; index++) {";
- std::string element_accessor = "(" + accessor + "[index])";
- s << "ss << ((index == 0) ? \"\" : \", \") << ";
-
- if (element_field_->GetFieldType() == CustomField::kFieldType) {
- s << element_accessor << ".ToString()";
- } else {
- element_field_->GenStringRepresentation(s, element_accessor);
- }
-
- s << ";}";
- s << "ss << \"]\"";
-}
-
-std::string ArrayField::GetRustDataType() const {
- return "[" + element_field_->GetRustDataType() + "; " + std::to_string(array_size_) + "]";
-}
-
-void ArrayField::GenRustGetter(std::ostream& s, Size start_offset, Size) const {
- s << "let " << GetName() << " = ";
- s << "bytes[" << start_offset.bytes() << "..";
- s << start_offset.bytes() + GetSize().bytes() << "].try_into().unwrap();";
-}
-
-void ArrayField::GenRustWriter(std::ostream& s, Size start_offset, Size) const {
- s << "&buffer[" << start_offset.bytes() << ".." << start_offset.bytes() + GetSize().bytes()
- << "].copy_from_slice(&self." << GetName() << ");";
-}
diff --git a/gd/packet/parser/fields/array_field.h b/gd/packet/parser/fields/array_field.h
index 0bd487d39..dd49f26ad 100644
--- a/gd/packet/parser/fields/array_field.h
+++ b/gd/packet/parser/fields/array_field.h
@@ -62,14 +62,6 @@ class ArrayField : public PacketField {
virtual const PacketField* GetElementField() const override;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- virtual std::string GetRustDataType() const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
const std::string name_;
const PacketField* element_field_{nullptr};
diff --git a/gd/packet/parser/fields/body_field.cc b/gd/packet/parser/fields/body_field.cc
index 557f18416..5e00b68a8 100644
--- a/gd/packet/parser/fields/body_field.cc
+++ b/gd/packet/parser/fields/body_field.cc
@@ -20,23 +20,12 @@ const std::string BodyField::kFieldType = "BodyField";
BodyField::BodyField(ParseLocation loc) : PacketField("body", loc) {}
-void BodyField::SetSizeField(const SizeField* size_field) {
- if (size_field_ != nullptr) {
- ERROR(this, size_field_, size_field) << "The size field for the body has already been assigned.";
- }
- size_field_ = size_field;
-}
-
const std::string& BodyField::GetFieldType() const {
return BodyField::kFieldType;
}
Size BodyField::GetSize() const {
- if (size_field_ == nullptr) {
- return Size(0);
- }
- std::string dynamic_size = "(" + size_field_->GetName() + " * 8)";
- return dynamic_size;
+ return Size(0);
}
std::string BodyField::GetDataType() const {
@@ -71,16 +60,3 @@ void BodyField::GenInserter(std::ostream&) const {
void BodyField::GenValidator(std::ostream&) const {
// Do nothing
}
-
-void BodyField::GenStringRepresentation(std::ostream& s, std::string accessor) const {
- s << "\"BODY REPRESENTATION_UNIMPLEMENTED " << accessor << " \"";
-}
-
-std::string BodyField::GetRustDataType() const {
- return GetDataType();
-}
-
-void BodyField::GenRustGetter(std::ostream&, Size, Size) const {
-}
-
-void BodyField::GenRustWriter(std::ostream&, Size, Size) const {}
diff --git a/gd/packet/parser/fields/body_field.h b/gd/packet/parser/fields/body_field.h
index c31af7414..ce4ede7dd 100644
--- a/gd/packet/parser/fields/body_field.h
+++ b/gd/packet/parser/fields/body_field.h
@@ -28,8 +28,6 @@ class BodyField : public PacketField {
virtual const std::string& GetFieldType() const override;
- void SetSizeField(const SizeField* size_field);
-
virtual Size GetSize() const override;
virtual std::string GetDataType() const override;
@@ -49,16 +47,4 @@ class BodyField : public PacketField {
virtual void GenInserter(std::ostream&) const override;
virtual void GenValidator(std::ostream&) const override;
-
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- virtual std::string GetRustDataType() const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenBoundsCheck(std::ostream&, Size, Size, std::string) const override{};
- // Body fields can only be dynamically sized.
- const SizeField* size_field_{nullptr};
};
diff --git a/gd/packet/parser/fields/checksum_field.cc b/gd/packet/parser/fields/checksum_field.cc
index bcbcac2fa..464799232 100644
--- a/gd/packet/parser/fields/checksum_field.cc
+++ b/gd/packet/parser/fields/checksum_field.cc
@@ -58,13 +58,3 @@ void ChecksumField::GenInserter(std::ostream& s) const {
void ChecksumField::GenValidator(std::ostream&) const {
// Done in packet_def.cc
}
-
-void ChecksumField::GenStringRepresentation(std::ostream& s, std::string) const {
- // TODO: there is currently no way to get checksum value
- s << "\"CHECKSUM\"";
-}
-
-void ChecksumField::GenRustGetter(std::ostream&, Size, Size) const {
-}
-
-void ChecksumField::GenRustWriter(std::ostream&, Size, Size) const {}
diff --git a/gd/packet/parser/fields/checksum_field.h b/gd/packet/parser/fields/checksum_field.h
index 2b5b22147..c15f023af 100644
--- a/gd/packet/parser/fields/checksum_field.h
+++ b/gd/packet/parser/fields/checksum_field.h
@@ -46,12 +46,6 @@ class ChecksumField : public ScalarField {
virtual void GenValidator(std::ostream&) const override;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
private:
std::string type_name_;
};
diff --git a/gd/packet/parser/fields/checksum_start_field.cc b/gd/packet/parser/fields/checksum_start_field.cc
index e0c03b828..5531c5a5f 100644
--- a/gd/packet/parser/fields/checksum_start_field.cc
+++ b/gd/packet/parser/fields/checksum_start_field.cc
@@ -61,16 +61,3 @@ void ChecksumStartField::GenValidator(std::ostream&) const {}
std::string ChecksumStartField::GetStartedFieldName() const {
return started_field_name_;
}
-
-void ChecksumStartField::GenStringRepresentation(std::ostream&, std::string) const {
- // Print nothing for checksum start
-}
-
-std::string ChecksumStartField::GetRustDataType() const {
- return GetDataType();
-}
-
-void ChecksumStartField::GenRustGetter(std::ostream&, Size, Size) const {
-}
-
-void ChecksumStartField::GenRustWriter(std::ostream&, Size, Size) const {}
diff --git a/gd/packet/parser/fields/checksum_start_field.h b/gd/packet/parser/fields/checksum_start_field.h
index 82e71ba8c..c63806b8e 100644
--- a/gd/packet/parser/fields/checksum_start_field.h
+++ b/gd/packet/parser/fields/checksum_start_field.h
@@ -51,14 +51,6 @@ class ChecksumStartField : public PacketField {
virtual std::string GetStartedFieldName() const;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- virtual std::string GetRustDataType() const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
private:
std::string started_field_name_;
};
diff --git a/gd/packet/parser/fields/count_field.cc b/gd/packet/parser/fields/count_field.cc
index f4b3d907c..8e1cf090b 100644
--- a/gd/packet/parser/fields/count_field.cc
+++ b/gd/packet/parser/fields/count_field.cc
@@ -57,9 +57,3 @@ void CountField::GenValidator(std::ostream&) const {
std::string CountField::GetSizedFieldName() const {
return sized_field_name_;
}
-
-void CountField::GenRustWriter(std::ostream& s, Size start_offset, Size) const {
- s << "buffer[" << start_offset.bytes() << "..";
- s << start_offset.bytes() + GetSize().bytes() << "].copy_from_slice(&";
- s << "(self." << GetSizedFieldName() << ".len() as u8).to_le_bytes());";
-}
diff --git a/gd/packet/parser/fields/count_field.h b/gd/packet/parser/fields/count_field.h
index db7a4e71a..c9cb6739f 100644
--- a/gd/packet/parser/fields/count_field.h
+++ b/gd/packet/parser/fields/count_field.h
@@ -44,8 +44,6 @@ class CountField : public ScalarField {
virtual std::string GetSizedFieldName() const;
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
private:
int size_;
std::string sized_field_name_;
diff --git a/gd/packet/parser/fields/custom_field.cc b/gd/packet/parser/fields/custom_field.cc
index e4761abc9..4e387f825 100644
--- a/gd/packet/parser/fields/custom_field.cc
+++ b/gd/packet/parser/fields/custom_field.cc
@@ -91,20 +91,3 @@ void CustomField::GenInserter(std::ostream& s) const {
void CustomField::GenValidator(std::ostream&) const {
// Do nothing.
}
-
-void CustomField::GenStringRepresentation(std::ostream& s, std::string accessor) const {
- s << accessor << "->ToString()";
-}
-
-void CustomField::GenBuilderParameterFromView(std::ostream& s) const {
- s << "*view.Get" << util::UnderscoreToCamelCase(GetName()) << "()";
-}
-
-std::string CustomField::GetRustDataType() const {
- return type_name_;
-}
-
-void CustomField::GenRustGetter(std::ostream&, Size, Size) const {
-}
-
-void CustomField::GenRustWriter(std::ostream&, Size, Size) const {}
diff --git a/gd/packet/parser/fields/custom_field.h b/gd/packet/parser/fields/custom_field.h
index 55642c9c5..621a3c820 100644
--- a/gd/packet/parser/fields/custom_field.h
+++ b/gd/packet/parser/fields/custom_field.h
@@ -49,16 +49,6 @@ class CustomField : public PacketField {
virtual void GenValidator(std::ostream&) const override;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- virtual void GenBuilderParameterFromView(std::ostream& s) const override;
-
- virtual std::string GetRustDataType() const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
private:
std::string type_name_;
};
diff --git a/gd/packet/parser/fields/custom_field_fixed_size.cc b/gd/packet/parser/fields/custom_field_fixed_size.cc
index 8dc27fa3e..687d48d2c 100644
--- a/gd/packet/parser/fields/custom_field_fixed_size.cc
+++ b/gd/packet/parser/fields/custom_field_fixed_size.cc
@@ -15,7 +15,6 @@
*/
#include "fields/custom_field_fixed_size.h"
-
#include "util.h"
const std::string CustomFieldFixedSize::kFieldType = "CustomField";
@@ -31,10 +30,6 @@ std::string CustomFieldFixedSize::GetDataType() const {
return type_name_;
}
-std::string CustomFieldFixedSize::GetRustDataType() const {
- return type_name_;
-}
-
int CustomFieldFixedSize::GenBounds(std::ostream& s, Size start_offset, Size end_offset, Size size) const {
if (!start_offset.empty()) {
// Default to start if available.
@@ -67,41 +62,3 @@ void CustomFieldFixedSize::GenInserter(std::ostream& s) const {
void CustomFieldFixedSize::GenValidator(std::ostream&) const {
// Do nothing.
}
-
-void CustomFieldFixedSize::GenStringRepresentation(std::ostream& s, std::string accessor) const {
- // We assume that custom fields will have a ToString() method
- s << accessor << ".ToString()";
-}
-
-std::string CustomFieldFixedSize::GetRustParseDataType() const {
- return "[u8; " + std::to_string(GetSize().bytes()) + "]";
-}
-
-void CustomFieldFixedSize::GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const {
- Size size = GetSize();
- int num_leading_bits = GetRustBitOffset(s, start_offset, end_offset, GetSize());
- if (num_leading_bits != 0) {
- ERROR(this) << "must be byte aligned";
- }
- if (size.bits() % 8 != 0) {
- ERROR(this) << "size must be in full bytes";
- }
-
- s << "let " << GetName() << " = bytes[" << start_offset.bytes() << "..";
- s << start_offset.bytes() + size.bytes() << "].try_into().unwrap();";
-}
-
-void CustomFieldFixedSize::GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const {
- Size size = GetSize();
- int num_leading_bits = GetRustBitOffset(s, start_offset, end_offset, GetSize());
- if (num_leading_bits != 0) {
- ERROR(this) << "must be byte aligned";
- }
- if (size.bits() % 8 != 0) {
- ERROR(this) << "size must be in full bytes";
- }
-
- s << "let " << GetName() << ": " << GetRustParseDataType() << " = self." << GetName() << ".into();";
- s << "buffer[" << start_offset.bytes() << ".." << start_offset.bytes() + GetSize().bytes() << "].copy_from_slice(&"
- << GetName() << ");";
-}
diff --git a/gd/packet/parser/fields/custom_field_fixed_size.h b/gd/packet/parser/fields/custom_field_fixed_size.h
index 8423f803b..97acff9db 100644
--- a/gd/packet/parser/fields/custom_field_fixed_size.h
+++ b/gd/packet/parser/fields/custom_field_fixed_size.h
@@ -41,15 +41,5 @@ class CustomFieldFixedSize : public ScalarField {
virtual void GenValidator(std::ostream&) const override;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- virtual std::string GetRustDataType() const override;
-
- virtual std::string GetRustParseDataType() const override;
-
std::string type_name_;
};
diff --git a/gd/packet/parser/fields/enum_field.cc b/gd/packet/parser/fields/enum_field.cc
index 49584f1ca..3080d43c3 100644
--- a/gd/packet/parser/fields/enum_field.cc
+++ b/gd/packet/parser/fields/enum_field.cc
@@ -51,11 +51,3 @@ void EnumField::GenInserter(std::ostream& s) const {
void EnumField::GenValidator(std::ostream&) const {
// Do nothing
}
-
-void EnumField::GenStringRepresentation(std::ostream& s, std::string accessor) const {
- s << GetDataType() << "Text(" << accessor << ")";
-}
-
-std::string EnumField::GetRustDataType() const {
- return enum_def_.name_;
-}
diff --git a/gd/packet/parser/fields/enum_field.h b/gd/packet/parser/fields/enum_field.h
index 7d00f6584..11c64e086 100644
--- a/gd/packet/parser/fields/enum_field.h
+++ b/gd/packet/parser/fields/enum_field.h
@@ -41,10 +41,6 @@ class EnumField : public ScalarField {
virtual void GenValidator(std::ostream&) const override;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- virtual std::string GetRustDataType() const override;
-
private:
EnumDef enum_def_;
std::string value_;
diff --git a/gd/packet/parser/fields/fixed_scalar_field.cc b/gd/packet/parser/fields/fixed_scalar_field.cc
index c745b1206..9bfdf0e9b 100644
--- a/gd/packet/parser/fields/fixed_scalar_field.cc
+++ b/gd/packet/parser/fields/fixed_scalar_field.cc
@@ -33,16 +33,3 @@ std::string FixedScalarField::GetDataType() const {
void FixedScalarField::GenValue(std::ostream& s) const {
s << value_;
}
-
-void FixedScalarField::GenStringRepresentation(std::ostream& s, std::string) const {
- s << "+" << value_;
-}
-
-void FixedScalarField::GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const {
- s << "let " << GetName() << ": " << GetRustDataType() << " = " << value_ << ";";
- FixedField::GenRustWriter(s, start_offset, end_offset);
-}
-
-void FixedScalarField::GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const {
- FixedField::GenRustGetter(s, start_offset, end_offset);
-}
diff --git a/gd/packet/parser/fields/fixed_scalar_field.h b/gd/packet/parser/fields/fixed_scalar_field.h
index 2304ba4a0..0070f6c26 100644
--- a/gd/packet/parser/fields/fixed_scalar_field.h
+++ b/gd/packet/parser/fields/fixed_scalar_field.h
@@ -33,17 +33,10 @@ class FixedScalarField : public FixedField {
virtual std::string GetDataType() const override;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- void GenValue(std::ostream& s) const;
-
static const std::string field_type;
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
private:
+ void GenValue(std::ostream& s) const;
const int64_t value_;
};
diff --git a/gd/packet/parser/fields/group_field.cc b/gd/packet/parser/fields/group_field.cc
index f2e3b95f8..6c9ade976 100644
--- a/gd/packet/parser/fields/group_field.cc
+++ b/gd/packet/parser/fields/group_field.cc
@@ -82,12 +82,3 @@ void GroupField::GenValidator(std::ostream&) const {
const std::list<PacketField*>* GroupField::GetFields() const {
return fields_;
}
-
-std::string GroupField::GetRustDataType() const {
- return GetDataType();
-}
-
-void GroupField::GenRustGetter(std::ostream&, Size, Size) const {
-}
-
-void GroupField::GenRustWriter(std::ostream&, Size, Size) const {}
diff --git a/gd/packet/parser/fields/group_field.h b/gd/packet/parser/fields/group_field.h
index 691fb229f..57e01651d 100644
--- a/gd/packet/parser/fields/group_field.h
+++ b/gd/packet/parser/fields/group_field.h
@@ -55,12 +55,6 @@ class GroupField : public PacketField {
const std::list<PacketField*>* GetFields() const;
- virtual std::string GetRustDataType() const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
private:
std::list<PacketField*>* fields_;
};
diff --git a/gd/packet/parser/fields/packet_field.cc b/gd/packet/parser/fields/packet_field.cc
index 4ce02e22e..7b0bdb70a 100644
--- a/gd/packet/parser/fields/packet_field.cc
+++ b/gd/packet/parser/fields/packet_field.cc
@@ -100,47 +100,3 @@ bool PacketField::IsContainerField() const {
const PacketField* PacketField::GetElementField() const {
return nullptr;
}
-
-void PacketField::GenStringRepresentation(std::ostream& s, std::string accessor) const {
- s << "\"REPRESENTATION_UNIMPLEMENTED " << GetFieldType() << " " << accessor << "\"";
-}
-
-int PacketField::GetRustBitOffset(
- std::ostream&, Size start_offset, Size end_offset, Size size) const {
- // In order to find field_begin and field_end, we must have two of the three Sizes.
- if ((start_offset.empty() && size.empty()) || (start_offset.empty() && end_offset.empty()) ||
- (end_offset.empty() && size.empty())) {
- ERROR(this) << "GenBounds called without enough information. "
- << start_offset << end_offset << size;
- }
-
- if (start_offset.bits() % 8 != 0 || end_offset.bits() % 8 != 0) {
- ERROR(this) << "Can not find the bounds of a field at a non byte-aligned offset."
- << start_offset << end_offset;
- }
-
- return 0; // num_leading_bits
-}
-
-bool PacketField::GenRustNameAndType(std::ostream& s) const {
- auto param_type = GetRustDataType();
- if (param_type.empty()) {
- return false;
- }
- s << GetName() << ": " << param_type;
- return true;
-}
-
-void PacketField::GenBoundsCheck(std::ostream& s, Size start_offset, Size, std::string context) const {
- Size size = GetSize();
- if (size.bits() < 8) {
- return;
- }
- s << "if bytes.len() < " << start_offset.bytes() + size.bytes() << " {";
- s << " return Err(Error::InvalidLengthError{";
- s << " obj: \"" << context << "\".to_string(),";
- s << " field: \"" << GetName() << "\".to_string(),";
- s << " wanted: " << start_offset.bytes() + size.bytes() << ",";
- s << " got: bytes.len()});";
- s << "}";
-}
diff --git a/gd/packet/parser/fields/packet_field.h b/gd/packet/parser/fields/packet_field.h
index 128536223..d9cc019b4 100644
--- a/gd/packet/parser/fields/packet_field.h
+++ b/gd/packet/parser/fields/packet_field.h
@@ -106,34 +106,12 @@ class PacketField : public Loggable {
// Get field of nested elements if this is a container field, nullptr if none
virtual const PacketField* GetElementField() const;
- // Return string representation of this field, that can be displayed for debugging or logging purposes
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const;
-
std::string GetDebugName() const override;
ParseLocation GetLocation() const override;
virtual std::string GetName() const;
- // Generate the Rust variable/field name and type
- virtual bool GenRustNameAndType(std::ostream& s) const;
-
- // Get the type of the field to be used in the member variables.
- virtual std::string GetRustDataType() const = 0;
-
- virtual int GetRustBitOffset(
- std::ostream& s, Size start_offset, Size end_offset, Size size) const;
-
- virtual void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const = 0;
-
- virtual void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const = 0;
-
- virtual void GenBoundsCheck(std::ostream& s, Size start_offset, Size, std::string) const;
-
- virtual bool GetterIsByRef() const {
- return true;
- }
-
private:
ParseLocation loc_;
std::string name_;
diff --git a/gd/packet/parser/fields/padding_field.cc b/gd/packet/parser/fields/padding_field.cc
index e6a2c366b..5f438f88e 100644
--- a/gd/packet/parser/fields/padding_field.cc
+++ b/gd/packet/parser/fields/padding_field.cc
@@ -61,12 +61,3 @@ void PaddingField::GenInserter(std::ostream&) const {
}
void PaddingField::GenValidator(std::ostream&) const {}
-
-std::string PaddingField::GetRustDataType() const {
- return "There's no type for Padding fields";
-}
-
-void PaddingField::GenRustGetter(std::ostream&, Size, Size) const {
-}
-
-void PaddingField::GenRustWriter(std::ostream&, Size, Size) const {}
diff --git a/gd/packet/parser/fields/padding_field.h b/gd/packet/parser/fields/padding_field.h
index ea40ccded..bb99d42a0 100644
--- a/gd/packet/parser/fields/padding_field.h
+++ b/gd/packet/parser/fields/padding_field.h
@@ -51,14 +51,6 @@ class PaddingField : public PacketField {
virtual void GenValidator(std::ostream&) const override;
- virtual std::string GetRustDataType() const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenBoundsCheck(std::ostream&, Size, Size, std::string) const override{};
-
private:
Size size_;
};
diff --git a/gd/packet/parser/fields/payload_field.cc b/gd/packet/parser/fields/payload_field.cc
index 844488242..c075996ed 100644
--- a/gd/packet/parser/fields/payload_field.cc
+++ b/gd/packet/parser/fields/payload_field.cc
@@ -107,24 +107,3 @@ void PayloadField::GenInserter(std::ostream&) const {
void PayloadField::GenValidator(std::ostream&) const {
// Do nothing
}
-
-void PayloadField::GenStringRepresentation(std::ostream& s, std::string) const {
- // TODO: we should parse the child packets
- s << "\"PAYLOAD[]\"";
-}
-
-std::string PayloadField::GetRustDataType() const {
- return "Vec::<u8>";
-}
-
-void PayloadField::GenRustGetter(std::ostream& s, Size start_offset, Size) const {
- s << "let " << GetName() << ": " << GetRustDataType() << " = ";
- if (size_field_ == nullptr) {
- s << "bytes[" << start_offset.bytes() << "..].into();";
- } else {
- s << "bytes[" << start_offset.bytes() << "..(";
- s << start_offset.bytes() << " + " << size_field_->GetName() << " as usize)].into();";
- }
-}
-
-void PayloadField::GenRustWriter(std::ostream&, Size, Size) const {}
diff --git a/gd/packet/parser/fields/payload_field.h b/gd/packet/parser/fields/payload_field.h
index f86f27522..11e626776 100644
--- a/gd/packet/parser/fields/payload_field.h
+++ b/gd/packet/parser/fields/payload_field.h
@@ -54,16 +54,6 @@ class PayloadField : public PacketField {
virtual void GenValidator(std::ostream&) const override;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- virtual std::string GetRustDataType() const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenBoundsCheck(std::ostream&, Size, Size, std::string) const override{};
-
// Payload fields can only be dynamically sized.
const SizeField* size_field_;
// Only used if the size of the payload is based on another field.
diff --git a/gd/packet/parser/fields/reserved_field.cc b/gd/packet/parser/fields/reserved_field.cc
index ac0533831..0acf7b720 100644
--- a/gd/packet/parser/fields/reserved_field.cc
+++ b/gd/packet/parser/fields/reserved_field.cc
@@ -67,12 +67,3 @@ void ReservedField::GenInserter(std::ostream& s) const {
void ReservedField::GenValidator(std::ostream&) const {
// There is no need to validate the value of a reserved field
}
-
-std::string ReservedField::GetRustDataType() const {
- return util::GetRustTypeForSize(size_);
-}
-
-void ReservedField::GenRustGetter(std::ostream&, Size, Size) const {
-}
-
-void ReservedField::GenRustWriter(std::ostream&, Size, Size) const {}
diff --git a/gd/packet/parser/fields/reserved_field.h b/gd/packet/parser/fields/reserved_field.h
index 7fabe499a..7d363528a 100644
--- a/gd/packet/parser/fields/reserved_field.h
+++ b/gd/packet/parser/fields/reserved_field.h
@@ -47,14 +47,6 @@ class ReservedField : public PacketField {
virtual void GenValidator(std::ostream&) const override;
- virtual std::string GetRustDataType() const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenBoundsCheck(std::ostream&, Size, Size, std::string) const override{};
-
private:
std::string name_;
int size_;
diff --git a/gd/packet/parser/fields/scalar_field.cc b/gd/packet/parser/fields/scalar_field.cc
index de5e31c9b..320534a41 100644
--- a/gd/packet/parser/fields/scalar_field.cc
+++ b/gd/packet/parser/fields/scalar_field.cc
@@ -16,8 +16,6 @@
#include "fields/scalar_field.h"
-#include "fields/fixed_scalar_field.h"
-#include "fields/size_field.h"
#include "util.h"
const std::string ScalarField::kFieldType = "ScalarField";
@@ -101,7 +99,7 @@ void ScalarField::GenGetter(std::ostream& s, Size start_offset, Size end_offset)
s << "ASSERT(was_validated_);";
s << "auto to_bound = begin();";
int num_leading_bits = GenBounds(s, start_offset, end_offset, GetSize());
- s << GetDataType() << " " << GetName() << "_value{};";
+ s << GetDataType() << " " << GetName() << "_value;";
s << GetDataType() << "* " << GetName() << "_ptr = &" << GetName() << "_value;";
GenExtractor(s, num_leading_bits, false);
s << "return " << GetName() << "_value;";
@@ -131,122 +129,3 @@ void ScalarField::GenInserter(std::ostream& s) const {
void ScalarField::GenValidator(std::ostream&) const {
// Do nothing
}
-
-void ScalarField::GenStringRepresentation(std::ostream& s, std::string accessor) const {
- s << "+" << accessor;
-}
-
-std::string ScalarField::GetRustDataType() const {
- return util::GetRustTypeForSize(size_);
-}
-
-std::string ScalarField::GetRustParseDataType() const {
- return util::GetRustTypeForSize(size_);
-}
-
-int ScalarField::GetRustBitOffset(
- std::ostream&, Size start_offset, Size end_offset, Size size) const {
- int num_leading_bits = 0;
-
- if (!start_offset.empty()) {
- // Default to start if available.
- num_leading_bits = start_offset.bits() % 8;
- } else if (!end_offset.empty()) {
- num_leading_bits = GetShiftBits(end_offset.bits() + size.bits());
- Size byte_offset = Size(num_leading_bits + size.bits()) + end_offset;
- } else {
- ERROR(this) << "Ambiguous offset for field.";
- }
- return num_leading_bits;
-}
-
-void ScalarField::GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const {
- Size size = GetSize();
-
- int num_leading_bits = GetRustBitOffset(s, start_offset, end_offset, GetSize());
-
- s << "let " << GetName() << " = ";
- auto offset = num_leading_bits == 0 ? 0 : -1;
- s << GetRustParseDataType() << "::from_le_bytes([";
- int total_bytes;
- if (size_ <= 8) {
- total_bytes = 1;
- } else if (size_ <= 16) {
- total_bytes = 2;
- } else if (size_ <= 32) {
- total_bytes = 4;
- } else {
- total_bytes = 8;
- }
- for (int i = 0; i < total_bytes; i++) {
- if (i > 0) {
- s << ",";
- }
- if (i < size.bytes()) {
- s << "bytes[" << start_offset.bytes() + i + offset << "]";
- } else {
- s << 0;
- }
- }
- s << "]);";
-
- if (num_leading_bits != 0) {
- s << "let " << GetName() << " = " << GetName() << " >> " << num_leading_bits << ";";
- }
-
- if (util::RoundSizeUp(size.bits()) != size.bits()) {
- uint64_t mask = 0;
- for (int i = 0; i < size.bits(); i++) {
- mask <<= 1;
- mask |= 1;
- }
- s << "let " << GetName() << " = ";
- s << GetName() << " & 0x" << std::hex << mask << std::dec << ";";
- }
-
- // needs casting from primitive
- if (GetRustParseDataType() != GetRustDataType()) {
- s << "let " << GetName() << " = ";
- s << GetRustDataType() << "::from_" << GetRustParseDataType() << "(" << GetName() << ").unwrap();";
- }
-}
-
-void ScalarField::GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const {
- Size size = GetSize();
- int num_leading_bits = GetRustBitOffset(s, start_offset, end_offset, GetSize());
-
- if (GetFieldType() == SizeField::kFieldType || GetFieldType() == FixedScalarField::kFieldType) {
- // Do nothing, the field access has already happened
- } else if (GetRustParseDataType() != GetRustDataType()) {
- // needs casting to primitive
- s << "let " << GetName() << " = self." << GetName() << ".to_" << GetRustParseDataType() << "().unwrap();";
- } else {
- s << "let " << GetName() << " = self." << GetName() << ";";
- }
- if (util::RoundSizeUp(size.bits()) != size.bits()) {
- uint64_t mask = 0;
- for (int i = 0; i < size.bits(); i++) {
- mask <<= 1;
- mask |= 1;
- }
- s << "let " << GetName() << " = ";
- s << GetName() << " & 0x" << std::hex << mask << std::dec << ";";
- }
-
- int access_offset = 0;
- if (num_leading_bits != 0) {
- access_offset = -1;
- uint64_t mask = 0;
- for (int i = 0; i < num_leading_bits; i++) {
- mask <<= 1;
- mask |= 1;
- }
- s << "let " << GetName() << " = (" << GetName() << " << " << num_leading_bits << ") | ("
- << "(buffer[" << start_offset.bytes() + access_offset << "] as " << GetRustParseDataType() << ") & 0x" << std::hex
- << mask << std::dec << ");";
- }
-
- s << "buffer[" << start_offset.bytes() + access_offset << ".."
- << start_offset.bytes() + GetSize().bytes() + access_offset << "].copy_from_slice(&" << GetName()
- << ".to_le_bytes()[0.." << size.bytes() << "]);";
-}
diff --git a/gd/packet/parser/fields/scalar_field.h b/gd/packet/parser/fields/scalar_field.h
index 81616cee7..65f897e64 100644
--- a/gd/packet/parser/fields/scalar_field.h
+++ b/gd/packet/parser/fields/scalar_field.h
@@ -49,23 +49,6 @@ class ScalarField : public PacketField {
virtual void GenValidator(std::ostream&) const override;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- virtual std::string GetRustDataType() const override;
-
- virtual std::string GetRustParseDataType() const;
-
- virtual int GetRustBitOffset(std::ostream& s, Size start_offset,
- Size end_offset, Size size) const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- virtual bool GetterIsByRef() const override {
- return false;
- }
-
private:
const int size_;
};
diff --git a/gd/packet/parser/fields/size_field.cc b/gd/packet/parser/fields/size_field.cc
index ce2c899d9..0a1b80bd0 100644
--- a/gd/packet/parser/fields/size_field.cc
+++ b/gd/packet/parser/fields/size_field.cc
@@ -61,7 +61,3 @@ void SizeField::GenValidator(std::ostream&) const {
std::string SizeField::GetSizedFieldName() const {
return sized_field_name_;
}
-
-void SizeField::GenStringRepresentation(std::ostream& s, std::string accessor) const {
- s << accessor;
-}
diff --git a/gd/packet/parser/fields/size_field.h b/gd/packet/parser/fields/size_field.h
index 2d40c42eb..b6e86394b 100644
--- a/gd/packet/parser/fields/size_field.h
+++ b/gd/packet/parser/fields/size_field.h
@@ -46,8 +46,6 @@ class SizeField : public ScalarField {
virtual std::string GetSizedFieldName() const;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
private:
int size_;
std::string sized_field_name_;
diff --git a/gd/packet/parser/fields/struct_field.cc b/gd/packet/parser/fields/struct_field.cc
index 75ad1abb0..fbdafcf4e 100644
--- a/gd/packet/parser/fields/struct_field.cc
+++ b/gd/packet/parser/fields/struct_field.cc
@@ -56,7 +56,7 @@ void StructField::GenGetter(std::ostream& s, Size start_offset, Size end_offset)
s << "size_t end_index = size();";
s << "auto to_bound = begin();";
int num_leading_bits = GenBounds(s, start_offset, end_offset, GetSize());
- s << GetDataType() << " " << GetName() << "_value{};";
+ s << GetDataType() << " " << GetName() << "_value;";
s << GetDataType() << "* " << GetName() << "_ptr = &" << GetName() << "_value;";
GenExtractor(s, num_leading_bits, false);
@@ -83,27 +83,3 @@ void StructField::GenInserter(std::ostream& s) const {
void StructField::GenValidator(std::ostream&) const {
// Do nothing
}
-
-void StructField::GenStringRepresentation(std::ostream& s, std::string accessor) const {
- s << accessor << ".ToString()";
-}
-
-std::string StructField::GetRustDataType() const {
- return GetDataType();
-}
-
-void StructField::GenBoundsCheck(std::ostream&, Size, Size, std::string) const {
- // implicitly checked by the struct parser
-}
-
-void StructField::GenRustGetter(std::ostream& s, Size start_offset, Size) const {
- s << "let " << GetName() << " = ";
- s << GetRustDataType() << "::parse(&bytes[" << start_offset.bytes() << "..";
- s << start_offset.bytes() + GetSize().bytes() << "]).unwrap();";
-}
-
-void StructField::GenRustWriter(std::ostream& s, Size start_offset, Size) const {
- s << "let " << GetName() << " = &mut buffer[" << start_offset.bytes();
- s << ".." << start_offset.bytes() + GetSize().bytes() << "];";
- s << "self." << GetName() << ".write_to(" << GetName() << ");";
-}
diff --git a/gd/packet/parser/fields/struct_field.h b/gd/packet/parser/fields/struct_field.h
index acc5fb459..1f4f10028 100644
--- a/gd/packet/parser/fields/struct_field.h
+++ b/gd/packet/parser/fields/struct_field.h
@@ -49,16 +49,6 @@ class StructField : public PacketField {
virtual void GenValidator(std::ostream&) const override;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- virtual std::string GetRustDataType() const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenBoundsCheck(std::ostream& s, Size start_offset, Size end_offset, std::string) const override;
-
private:
std::string type_name_;
diff --git a/gd/packet/parser/fields/variable_length_struct_field.cc b/gd/packet/parser/fields/variable_length_struct_field.cc
index 628b43ad3..ceaf85803 100644
--- a/gd/packet/parser/fields/variable_length_struct_field.cc
+++ b/gd/packet/parser/fields/variable_length_struct_field.cc
@@ -61,7 +61,7 @@ void VariableLengthStructField::GenGetter(std::ostream& s, Size start_offset, Si
s << "size_t end_index = size();";
s << "auto to_bound = begin();";
int num_leading_bits = GenBounds(s, start_offset, end_offset, GetSize());
- s << GetDataType() << " " << GetName() << "_ptr{};";
+ s << GetDataType() << " " << GetName() << "_ptr;";
GenExtractor(s, num_leading_bits, false);
s << "return " << GetName() << "_ptr;";
s << "}\n";
@@ -90,13 +90,3 @@ void VariableLengthStructField::GenInserter(std::ostream& s) const {
void VariableLengthStructField::GenValidator(std::ostream&) const {
// Do nothing
}
-
-std::string VariableLengthStructField::GetRustDataType() const {
- std::string ret = "std::boxed::Box<" + type_name_ + ">";
- return ret;
-}
-
-void VariableLengthStructField::GenRustGetter(std::ostream&, Size, Size) const {
-}
-
-void VariableLengthStructField::GenRustWriter(std::ostream&, Size, Size) const {}
diff --git a/gd/packet/parser/fields/variable_length_struct_field.h b/gd/packet/parser/fields/variable_length_struct_field.h
index 2774d4e7a..0b1b97f66 100644
--- a/gd/packet/parser/fields/variable_length_struct_field.h
+++ b/gd/packet/parser/fields/variable_length_struct_field.h
@@ -51,12 +51,6 @@ class VariableLengthStructField : public PacketField {
virtual void GenValidator(std::ostream&) const override;
- virtual std::string GetRustDataType() const override;
-
- void GenRustGetter(std::ostream&, Size, Size) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
private:
std::string type_name_;
};
diff --git a/gd/packet/parser/fields/vector_field.cc b/gd/packet/parser/fields/vector_field.cc
index 9c8ca0715..ab47c4f58 100644
--- a/gd/packet/parser/fields/vector_field.cc
+++ b/gd/packet/parser/fields/vector_field.cc
@@ -89,15 +89,15 @@ Size VectorField::GetStructSize() const {
// size_field_ is of type SIZE
if (size_field_->GetFieldType() == SizeField::kFieldType) {
- std::string ret = "(static_cast<size_t>(to_fill->" + size_field_->GetName() + "_extracted_) * 8)";
+ std::string ret = "(static_cast<size_t>(" + size_field_->GetName() + "_extracted) * 8)";
if (!size_modifier_.empty()) ret += "-" + size_modifier_;
return ret;
}
// size_field_ is of type COUNT and elements have a fixed size
if (!element_size_.empty() && !element_size_.has_dynamic()) {
- return "(static_cast<size_t>(to_fill->" + size_field_->GetName() + "_extracted_) * " +
- std::to_string(element_size_.bits()) + ")";
+ return "(static_cast<size_t>(" + size_field_->GetName() + "_extracted) * " + std::to_string(element_size_.bits()) +
+ ")";
}
return Size();
@@ -112,7 +112,7 @@ void VectorField::GenExtractor(std::ostream& s, int num_leading_bits, bool for_s
if (size_field_ != nullptr && size_field_->GetFieldType() == CountField::kFieldType) {
s << "size_t " << element_field_->GetName() << "_count = ";
if (for_struct) {
- s << "to_fill->" << size_field_->GetName() << "_extracted_;";
+ s << size_field_->GetName() << "_extracted;";
} else {
s << "Get" << util::UnderscoreToCamelCase(size_field_->GetName()) << "();";
}
@@ -157,7 +157,7 @@ void VectorField::GenGetter(std::ostream& s, Size start_offset, Size end_offset)
s << "auto to_bound = begin();";
int num_leading_bits = GenBounds(s, start_offset, end_offset, GetSize());
- s << GetDataType() << " " << GetName() << "_value{};";
+ s << GetDataType() << " " << GetName() << "_value;";
s << GetDataType() << "* " << GetName() << "_ptr = &" << GetName() << "_value;";
GenExtractor(s, num_leading_bits, false);
@@ -230,151 +230,3 @@ bool VectorField::IsContainerField() const {
const PacketField* VectorField::GetElementField() const {
return element_field_;
}
-
-void VectorField::GenStringRepresentation(std::ostream& s, std::string accessor) const {
- s << "\"VECTOR[\";";
-
- std::string arr_idx = "arridx_" + accessor;
- std::string vec_size = accessor + ".size()";
- s << "for (size_t index = 0; index < " << vec_size << "; index++) {";
- std::string element_accessor = "(" + accessor + "[index])";
- s << "ss << ((index == 0) ? \"\" : \", \") << ";
-
- if (element_field_->GetFieldType() == CustomField::kFieldType) {
- s << element_accessor << ".ToString()";
- } else {
- element_field_->GenStringRepresentation(s, element_accessor);
- }
-
- s << ";}";
- s << "ss << \"]\"";
-}
-
-std::string VectorField::GetRustDataType() const {
- return "Vec::<" + element_field_->GetRustDataType() + ">";
-}
-
-void VectorField::GenBoundsCheck(std::ostream& s, Size start_offset, Size, std::string context) const {
- auto element_field_type = GetElementField()->GetFieldType();
- auto element_field = GetElementField();
- auto element_size = element_field->GetSize().bytes();
-
- if (element_field_type == ScalarField::kFieldType) {
- if (size_field_ == nullptr) {
- s << "let rem_ = (bytes.len() - " << start_offset.bytes() << ") % " << element_size << ";";
- s << "if rem_ != 0 {";
- s << " return Err(Error::InvalidLengthError{";
- s << " obj: \"" << context << "\".to_string(),";
- s << " field: \"" << GetName() << "\".to_string(),";
- s << " wanted: bytes.len() + rem_,";
- s << " got: bytes.len()});";
- s << "}";
- } else if (size_field_->GetFieldType() == CountField::kFieldType) {
- s << "let want_ = " << start_offset.bytes() << " + ((" << size_field_->GetName() << " as usize) * "
- << element_size << ");";
- s << "if bytes.len() < want_ {";
- s << " return Err(Error::InvalidLengthError{";
- s << " obj: \"" << context << "\".to_string(),";
- s << " field: \"" << GetName() << "\".to_string(),";
- s << " wanted: want_,";
- s << " got: bytes.len()});";
- s << "}";
- } else {
- s << "let want_ = " << start_offset.bytes() << " + (" << size_field_->GetName() << " as usize)";
- if (GetSizeModifier() != "") {
- s << " - ((" << GetSizeModifier().substr(1) << ") / 8)";
- }
- s << ";";
- s << "if bytes.len() < want_ {";
- s << " return Err(Error::InvalidLengthError{";
- s << " obj: \"" << context << "\".to_string(),";
- s << " field: \"" << GetName() << "\".to_string(),";
- s << " wanted: want_,";
- s << " got: bytes.len()});";
- s << "}";
- if (GetSizeModifier() != "") {
- s << "if ((" << size_field_->GetName() << " as usize) < ((" << GetSizeModifier().substr(1) << ") / 8)) {";
- s << " return Err(Error::ImpossibleStructError);";
- s << "}";
- }
- }
- }
-}
-
-void VectorField::GenRustGetter(std::ostream& s, Size start_offset, Size) const {
- auto element_field_type = GetElementField()->GetFieldType();
- auto element_field = GetElementField();
- auto element_size = element_field->GetSize().bytes();
-
- if (element_field_type == ScalarField::kFieldType) {
- s << "let " << GetName() << ": " << GetRustDataType() << " = ";
- if (size_field_ == nullptr) {
- s << "bytes[" << start_offset.bytes() << "..]";
- } else if (size_field_->GetFieldType() == CountField::kFieldType) {
- s << "bytes[" << start_offset.bytes() << ".." << start_offset.bytes() << " + ((";
- s << size_field_->GetName() << " as usize) * " << element_size << ")]";
- } else {
- s << "bytes[" << start_offset.bytes() << "..(";
- s << start_offset.bytes() << " + " << size_field_->GetName();
- s << " as usize)";
- if (GetSizeModifier() != "") {
- s << " - ((" << GetSizeModifier().substr(1) << ") / 8)";
- }
- s << "]";
- }
-
- s << ".to_vec().chunks_exact(" << element_size << ").into_iter().map(|i| ";
- s << element_field->GetRustDataType() << "::from_le_bytes([";
-
- for (int j=0; j < element_size; j++) {
- s << "i[" << j << "]";
- if (j != element_size - 1) {
- s << ", ";
- }
- }
- s << "])).collect();";
- } else {
- s << "let mut " << GetName() << ": " << GetRustDataType() << " = Vec::new();";
- if (size_field_ == nullptr) {
- s << "let mut parsable_ = &bytes[" << start_offset.bytes() << "..];";
- s << "while parsable_.len() > 0 {";
- } else if (size_field_->GetFieldType() == CountField::kFieldType) {
- s << "let mut parsable_ = &bytes[" << start_offset.bytes() << "..];";
- s << "let count_ = " << size_field_->GetName() << " as usize;";
- s << "for _ in 0..count_ {";
- } else {
- s << "let mut parsable_ = &bytes[" << start_offset.bytes() << ".." << start_offset.bytes() << " + ("
- << size_field_->GetName() << " as usize)";
- if (GetSizeModifier() != "") {
- s << " - ((" << GetSizeModifier().substr(1) << ") / 8)";
- }
- s << "];";
- s << "while parsable_.len() > 0 {";
- }
- s << " match " << element_field->GetRustDataType() << "::parse(&parsable_) {";
- s << " Ok(parsed) => {";
- s << " parsable_ = &parsable_[parsed.get_total_size()..];";
- s << GetName() << ".push(parsed);";
- s << " },";
- s << " Err(Error::ImpossibleStructError) => break,";
- s << " Err(e) => return Err(e),";
- s << " }";
- s << "}";
- }
-}
-
-void VectorField::GenRustWriter(std::ostream& s, Size start_offset, Size) const {
- if (GetElementField()->GetFieldType() == ScalarField::kFieldType) {
- s << "for (i, e) in self." << GetName() << ".iter().enumerate() {";
- s << "buffer[" << start_offset.bytes() << "+i..";
- s << start_offset.bytes() << "+i+" << GetElementField()->GetSize().bytes() << "]";
- s << ".copy_from_slice(&e.to_le_bytes())";
- s << "}";
- } else {
- s << "let mut vec_buffer_ = &mut buffer[" << start_offset.bytes() << "..];";
- s << "for e_ in &self." << GetName() << " {";
- s << " e_.write_to(&mut vec_buffer_[0..e_.get_total_size()]);";
- s << " vec_buffer_ = &mut vec_buffer_[e_.get_total_size()..];";
- s << "}";
- }
-}
diff --git a/gd/packet/parser/fields/vector_field.h b/gd/packet/parser/fields/vector_field.h
index e6b533039..b2ae95de0 100644
--- a/gd/packet/parser/fields/vector_field.h
+++ b/gd/packet/parser/fields/vector_field.h
@@ -67,16 +67,6 @@ class VectorField : public PacketField {
virtual const PacketField* GetElementField() const override;
- virtual void GenStringRepresentation(std::ostream& s, std::string accessor) const override;
-
- virtual std::string GetRustDataType() const override;
-
- void GenRustGetter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenRustWriter(std::ostream& s, Size start_offset, Size end_offset) const override;
-
- void GenBoundsCheck(std::ostream& s, Size start_offset, Size end_offset, std::string context) const override;
-
const std::string name_;
const PacketField* element_field_{nullptr};
diff --git a/gd/packet/parser/flex.gni b/gd/packet/parser/flex.gni
deleted file mode 100644
index 1fcba233d..000000000
--- a/gd/packet/parser/flex.gni
+++ /dev/null
@@ -1,70 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-# Flex (fast lexical analyzer generator) is used for parsing languages. It is
-# commonly used with a parser generator (like Bison).
-
-# Generate source files using Flex.
-#
-# Note: We generate .cc files for Flex. However, you must set %option c++ if you
-# want to generate a C++ scanner class. We don't use --c++ in case you have
-# %option reentrant set, which is mutually exclusive with %option c++.
-#
-# Parameters:
-# sources: Files used to generate the lexers.
-template("flex_source") {
- action_name = "${target_name}_gen"
- action_foreach(action_name) {
- forward_variables_from(invoker, [ "sources" ])
- assert(defined(sources), "sources must be set")
- foreach(s, sources) {
- assert(get_path_info(s, "extension") == "ll",
- "Expecting Flex extension ll: ${s}")
- }
-
- script = "//common-mk/file_generator_wrapper.py"
- outformat = "${target_gen_dir}/{{source_name_part}}.cc"
- args = [
- "flex",
- "-o",
- outformat,
- "{{source}}",
- ]
- outputs = [ outformat ]
- }
-
- all_dependent_config_name = "_${target_name}_all_dependent_config"
- config(all_dependent_config_name) {
- include_dirs = [ "${target_gen_dir}" ]
- }
-
- source_set(target_name) {
- sources = get_target_outputs(":${action_name}")
- all_dependent_configs = [ ":${all_dependent_config_name}" ]
- deps = [ ":${action_name}" ]
-
- if (defined(invoker.configs)) {
- configs += invoker.configs
- }
-
- # Silence some warnings. The autogenerated code includes parts that have
- # fallthroughs and unreachable code. This may silence legitimate issues in
- # user written code in the lexer as well. User beware!
- cflags_cc = [
- "-Wno-implicit-fallthrough",
- "-Wno-unreachable-code",
- ]
- }
-}
diff --git a/gd/packet/parser/gen_cpp.cc b/gd/packet/parser/gen_cpp.cc
deleted file mode 100644
index ce3cf0e72..000000000
--- a/gd/packet/parser/gen_cpp.cc
+++ /dev/null
@@ -1,411 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <unistd.h>
-#include <cerrno>
-#include <cstdio>
-#include <filesystem>
-#include <fstream>
-#include <iostream>
-#include <queue>
-#include <regex>
-#include <sstream>
-#include <vector>
-
-#include "declarations.h"
-#include "struct_parser_generator.h"
-
-void parse_namespace(
- const std::string& root_namespace,
- const std::filesystem::path& input_file_relative_path,
- std::vector<std::string>* token) {
- std::filesystem::path gen_namespace = root_namespace / input_file_relative_path;
- std::string gen_namespace_str = gen_namespace.u8string();
- std::regex path_tokenizer("/");
- auto it = std::sregex_token_iterator(gen_namespace_str.cbegin(), gen_namespace_str.cend(), path_tokenizer, -1);
- std::sregex_token_iterator it_end = {};
- for (; it != it_end; ++it) {
- token->push_back(it->str());
- }
-}
-
-void generate_namespace_open(const std::vector<std::string>& token, std::ostream& output) {
- for (const auto& ns : token) {
- output << "namespace " << ns << " {" << std::endl;
- }
-}
-
-void generate_namespace_close(const std::vector<std::string>& token, std::ostream& output) {
- for (auto it = token.rbegin(); it != token.rend(); ++it) {
- output << "} //namespace " << *it << std::endl;
- }
-}
-
-bool generate_cpp_headers_one_file(
- const Declarations& decls,
- const std::filesystem::path& input_file,
- const std::filesystem::path& include_dir,
- const std::filesystem::path& out_dir,
- const std::string& root_namespace) {
- auto gen_relative_path = input_file.lexically_relative(include_dir).parent_path();
-
- auto input_filename = input_file.filename().string().substr(0, input_file.filename().string().find(".pdl"));
- auto gen_path = out_dir / gen_relative_path;
-
- std::filesystem::create_directories(gen_path);
-
- auto gen_file = gen_path / (input_filename + ".h");
-
- std::cout << "generating " << gen_file << std::endl;
-
- std::ofstream out_file;
- out_file.open(gen_file);
- if (!out_file.is_open()) {
- std::cerr << "can't open " << gen_file << std::endl;
- return false;
- }
-
- out_file <<
- R"(
-#pragma once
-
-#include <cstdint>
-#include <functional>
-#include <sstream>
-#include <string>
-#include <type_traits>
-
-#include "os/log.h"
-#include "packet/base_packet_builder.h"
-#include "packet/bit_inserter.h"
-#include "packet/custom_field_fixed_size_interface.h"
-#include "packet/iterator.h"
-#include "packet/packet_builder.h"
-#include "packet/packet_struct.h"
-#include "packet/packet_view.h"
-
-#if defined(PACKET_FUZZ_TESTING) || defined(PACKET_TESTING) || defined(FUZZ_TARGET)
-#include "packet/raw_builder.h"
-#endif
-#include "packet/parser/checksum_type_checker.h"
-#include "packet/parser/custom_type_checker.h"
-
-)";
-
- for (const auto& c : decls.type_defs_queue_) {
- if (c.second->GetDefinitionType() == TypeDef::Type::CUSTOM ||
- c.second->GetDefinitionType() == TypeDef::Type::CHECKSUM) {
- ((CustomFieldDef*)c.second)->GenInclude(out_file);
- }
- }
- out_file << "\n\n";
-
- std::vector<std::string> namespace_list;
- parse_namespace(root_namespace, gen_relative_path, &namespace_list);
- generate_namespace_open(namespace_list, out_file);
- out_file << "\n\n";
-
- for (const auto& c : decls.type_defs_queue_) {
- if (c.second->GetDefinitionType() == TypeDef::Type::CUSTOM ||
- c.second->GetDefinitionType() == TypeDef::Type::CHECKSUM) {
- ((CustomFieldDef*)c.second)->GenUsing(out_file);
- }
- }
- out_file <<
- R"(
-
-using ::bluetooth::packet::BasePacketBuilder;
-using ::bluetooth::packet::BitInserter;
-using ::bluetooth::packet::CustomFieldFixedSizeInterface;
-using ::bluetooth::packet::CustomTypeChecker;
-using ::bluetooth::packet::Iterator;
-using ::bluetooth::packet::kLittleEndian;
-using ::bluetooth::packet::PacketBuilder;
-using ::bluetooth::packet::PacketStruct;
-using ::bluetooth::packet::PacketView;
-
-#if defined(PACKET_FUZZ_TESTING) || defined(PACKET_TESTING) || defined(FUZZ_TARGET)
-using ::bluetooth::packet::RawBuilder;
-#endif
-
-using ::bluetooth::packet::parser::ChecksumTypeChecker;
-
-)";
-
- for (const auto& e : decls.type_defs_queue_) {
- if (e.second->GetDefinitionType() == TypeDef::Type::ENUM) {
- const auto* enum_def = static_cast<const EnumDef*>(e.second);
- EnumGen gen(*enum_def);
- gen.GenDefinition(out_file);
- out_file << "\n\n";
- }
- }
- for (const auto& e : decls.type_defs_queue_) {
- if (e.second->GetDefinitionType() == TypeDef::Type::ENUM) {
- const auto* enum_def = static_cast<const EnumDef*>(e.second);
- EnumGen gen(*enum_def);
- gen.GenLogging(out_file);
- out_file << "\n\n";
- }
- }
- for (const auto& ch : decls.type_defs_queue_) {
- if (ch.second->GetDefinitionType() == TypeDef::Type::CHECKSUM) {
- const auto* checksum_def = static_cast<const ChecksumDef*>(ch.second);
- checksum_def->GenChecksumCheck(out_file);
- }
- }
- out_file << "\n/* Done ChecksumChecks */\n";
-
- for (const auto& c : decls.type_defs_queue_) {
- if (c.second->GetDefinitionType() == TypeDef::Type::CUSTOM) {
- if (c.second->size_ == -1 /* Variable Size */) {
- const auto* custom_field_def = static_cast<const CustomFieldDef*>(c.second);
- custom_field_def->GenCustomFieldCheck(out_file, decls.is_little_endian);
- } else { // fixed size
- const auto* custom_field_def = static_cast<const CustomFieldDef*>(c.second);
- custom_field_def->GenFixedSizeCustomFieldCheck(out_file);
- }
- }
- }
- out_file << "\n";
-
- for (auto& s : decls.type_defs_queue_) {
- if (s.second->GetDefinitionType() == TypeDef::Type::STRUCT) {
- const auto* struct_def = static_cast<const StructDef*>(s.second);
- struct_def->GenDefinition(out_file);
- out_file << "\n";
- }
- }
-
- {
- StructParserGenerator spg(decls);
- spg.Generate(out_file);
- out_file << "\n\n";
- }
-
- for (const auto& packet_def : decls.packet_defs_queue_) {
- packet_def.second->GenParserDefinition(out_file);
- out_file << "\n\n";
- }
-
- for (const auto& packet_def : decls.packet_defs_queue_) {
- packet_def.second->GenBuilderDefinition(out_file);
- out_file << "\n\n";
- }
-
- if (input_filename == "hci_packets") {
- out_file << "class Checker { public: static bool IsCommandStatusOpcode(OpCode op_code) {";
- out_file << "switch (op_code) {";
- std::set<std::string> op_codes;
- for (const auto& packet_def : decls.packet_defs_queue_) {
- auto packet = packet_def.second;
- auto op_constraint = packet->parent_constraints_.find("op_code");
- if (op_constraint == packet->parent_constraints_.end()) {
- auto constraint = packet->parent_constraints_.find("command_op_code");
- if (constraint == packet->parent_constraints_.end()) {
- continue;
- }
- if (packet->HasAncestorNamed("CommandStatus")) {
- out_file << "case " << std::get<std::string>(constraint->second) << ":";
- op_codes.erase(std::get<std::string>(constraint->second));
- }
- if (packet->HasAncestorNamed("CommandComplete")) {
- op_codes.erase(std::get<std::string>(constraint->second));
- }
- } else {
- op_codes.insert(std::get<std::string>(op_constraint->second));
- }
- }
- bool unhandled_opcode = false;
- for (const auto& opcode : op_codes) {
- unhandled_opcode = true;
- std::cerr << "Opcode with no Status or Complete " << opcode << std::endl;
- }
- if (unhandled_opcode) {
- ERROR() << "At least one unhandled opcode";
- }
- out_file << "return true; default: return false; }}};";
- }
-
- generate_namespace_close(namespace_list, out_file);
-
- out_file.close();
-
- return true;
-}
-
-// Get the out_file shard at a symbol_count
-std::ofstream& get_out_file(size_t symbol_count, size_t symbol_total, std::vector<std::ofstream>* out_files) {
- auto symbols_per_shard = symbol_total / out_files->size();
- auto file_index = std::min(symbol_count / symbols_per_shard, out_files->size() - 1);
- return out_files->at(file_index);
-}
-
-bool generate_pybind11_sources_one_file(
- const Declarations& decls,
- const std::filesystem::path& input_file,
- const std::filesystem::path& include_dir,
- const std::filesystem::path& out_dir,
- const std::string& root_namespace,
- size_t num_shards) {
- auto gen_relative_path = input_file.lexically_relative(include_dir).parent_path();
-
- auto input_filename = input_file.filename().string().substr(0, input_file.filename().string().find(".pdl"));
- auto gen_path = out_dir / gen_relative_path;
-
- std::filesystem::create_directories(gen_path);
-
- auto gen_relative_header = gen_relative_path / (input_filename + ".h");
-
- std::vector<std::string> namespace_list;
- parse_namespace(root_namespace, gen_relative_path, &namespace_list);
-
- std::vector<std::ofstream> out_file_shards(num_shards);
- for (size_t i = 0; i < out_file_shards.size(); i++) {
- auto filename = gen_path / (input_filename + "_python3_shard_" + std::to_string(i) + ".cc");
- std::cout << "generating " << filename << std::endl;
- auto& out_file = out_file_shards[i];
- out_file.open(filename);
- if (!out_file.is_open()) {
- std::cerr << "can't open " << filename << std::endl;
- return false;
- }
- out_file << "#include <pybind11/pybind11.h>\n";
- out_file << "#include <pybind11/stl.h>\n";
- out_file << "\n\n";
- out_file << "#include " << gen_relative_header << "\n";
- out_file << "\n\n";
- out_file << "#include \"packet/raw_builder.h\"\n";
- out_file << "\n\n";
-
- for (const auto& c : decls.type_defs_queue_) {
- if (c.second->GetDefinitionType() == TypeDef::Type::CUSTOM) {
- const auto* custom_def = static_cast<const CustomFieldDef*>(c.second);
- custom_def->GenPyBind11Include(out_file);
- }
- }
-
- out_file << "\n\n";
-
- generate_namespace_open(namespace_list, out_file);
- out_file << "\n\n";
-
- for (const auto& c : decls.type_defs_queue_) {
- if (c.second->GetDefinitionType() == TypeDef::Type::CUSTOM ||
- c.second->GetDefinitionType() == TypeDef::Type::CHECKSUM) {
- const auto* custom_def = static_cast<const CustomFieldDef*>(c.second);
- custom_def->GenUsing(out_file);
- }
- }
- out_file << "\n\n";
-
- out_file << "using ::bluetooth::packet::BasePacketBuilder;";
- out_file << "using ::bluetooth::packet::BitInserter;";
- out_file << "using ::bluetooth::packet::CustomTypeChecker;";
- out_file << "using ::bluetooth::packet::Iterator;";
- out_file << "using ::bluetooth::packet::kLittleEndian;";
- out_file << "using ::bluetooth::packet::PacketBuilder;";
- out_file << "using ::bluetooth::packet::BaseStruct;";
- out_file << "using ::bluetooth::packet::PacketStruct;";
- out_file << "using ::bluetooth::packet::PacketView;";
- out_file << "using ::bluetooth::packet::RawBuilder;";
- out_file << "using ::bluetooth::packet::parser::ChecksumTypeChecker;";
- out_file << "\n\n";
-
- out_file << "namespace py = pybind11;\n\n";
-
- out_file << "void define_" << input_filename << "_submodule_shard_" << std::to_string(i) << "(py::module& m) {\n\n";
- }
- size_t symbol_total = 0;
- // Only count types that will be generated
- for (const auto& e : decls.type_defs_queue_) {
- if (e.second->GetDefinitionType() == TypeDef::Type::ENUM) {
- symbol_total++;
- } else if (e.second->GetDefinitionType() == TypeDef::Type::STRUCT) {
- symbol_total++;
- }
- }
- // View and builder are counted separately
- symbol_total += decls.packet_defs_queue_.size() * 2;
- size_t symbol_count = 0;
-
- for (const auto& e : decls.type_defs_queue_) {
- if (e.second->GetDefinitionType() == TypeDef::Type::ENUM) {
- const auto* enum_def = static_cast<const EnumDef*>(e.second);
- EnumGen gen(*enum_def);
- auto& out_file = get_out_file(symbol_count, symbol_total, &out_file_shards);
- gen.GenDefinitionPybind11(out_file);
- out_file << "\n\n";
- symbol_count++;
- }
- }
-
- for (const auto& s : decls.type_defs_queue_) {
- if (s.second->GetDefinitionType() == TypeDef::Type::STRUCT) {
- const auto* struct_def = static_cast<const StructDef*>(s.second);
- auto& out_file = get_out_file(symbol_count, symbol_total, &out_file_shards);
- struct_def->GenDefinitionPybind11(out_file);
- out_file << "\n";
- symbol_count++;
- }
- }
-
- for (const auto& packet_def : decls.packet_defs_queue_) {
- auto& out_file = get_out_file(symbol_count, symbol_total, &out_file_shards);
- packet_def.second->GenParserDefinitionPybind11(out_file);
- out_file << "\n\n";
- symbol_count++;
- }
-
- for (const auto& p : decls.packet_defs_queue_) {
- auto& out_file = get_out_file(symbol_count, symbol_total, &out_file_shards);
- p.second->GenBuilderDefinitionPybind11(out_file);
- out_file << "\n\n";
- symbol_count++;
- }
-
- for (auto& out_file : out_file_shards) {
- out_file << "}\n\n";
- generate_namespace_close(namespace_list, out_file);
- }
-
- auto gen_file_main = gen_path / (input_filename + "_python3.cc");
- std::ofstream out_file_main;
- out_file_main.open(gen_file_main);
- if (!out_file_main.is_open()) {
- std::cerr << "can't open " << gen_file_main << std::endl;
- return false;
- }
- out_file_main << "#include <pybind11/pybind11.h>\n";
- generate_namespace_open(namespace_list, out_file_main);
-
- out_file_main << "namespace py = pybind11;\n\n";
-
- for (size_t i = 0; i < out_file_shards.size(); i++) {
- out_file_main << "void define_" << input_filename << "_submodule_shard_" << std::to_string(i)
- << "(py::module& m);\n";
- }
-
- out_file_main << "void define_" << input_filename << "_submodule(py::module& m) {\n\n";
- for (size_t i = 0; i < out_file_shards.size(); i++) {
- out_file_main << "define_" << input_filename << "_submodule_shard_" << std::to_string(i) << "(m);\n";
- }
- out_file_main << "}\n\n";
-
- generate_namespace_close(namespace_list, out_file_main);
-
- return true;
-}
diff --git a/gd/packet/parser/gen_rust.cc b/gd/packet/parser/gen_rust.cc
deleted file mode 100644
index 8a91e757c..000000000
--- a/gd/packet/parser/gen_rust.cc
+++ /dev/null
@@ -1,168 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <filesystem>
-#include <fstream>
-#include <iostream>
-#include "declarations.h"
-
-void generate_rust_packet_preamble(std::ostream& s) {
- s <<
- R"(
-use bytes::{Bytes, BytesMut, BufMut};
-use num_derive::{FromPrimitive, ToPrimitive};
-use num_traits::{FromPrimitive, ToPrimitive};
-use std::convert::TryInto;
-use thiserror::Error;
-use std::sync::Arc;
-
-type Result<T> = std::result::Result<T, Error>;
-
-#[derive(Debug, Error)]
-pub enum Error {
- #[error("Packet parsing failed")]
- InvalidPacketError,
- #[error("{field} was {value:x}, which is not known")]
- ConstraintOutOfBounds {
- field: String,
- value: u64,
- },
- #[error("when parsing {obj}.{field} needed length of {wanted} but got {got}")]
- InvalidLengthError {
- obj: String,
- field: String,
- wanted: usize,
- got: usize,
- },
- #[error("Due to size restrictions a struct could not be parsed.")]
- ImpossibleStructError,
-}
-
-pub trait Packet {
- fn to_bytes(self) -> Bytes;
- fn to_vec(self) -> Vec<u8>;
-}
-
-)";
-}
-
-bool generate_rust_source_one_file(
- const Declarations& decls,
- const std::filesystem::path& input_file,
- const std::filesystem::path& include_dir,
- const std::filesystem::path& out_dir,
- __attribute__((unused)) const std::string& root_namespace) {
- auto gen_relative_path = input_file.lexically_relative(include_dir).parent_path();
-
- auto input_filename = input_file.filename().string().substr(0, input_file.filename().string().find(".pdl"));
- auto gen_path = out_dir / gen_relative_path;
-
- std::filesystem::create_directories(gen_path);
-
- auto gen_file = gen_path / (input_filename + ".rs");
-
- std::cout << "generating " << gen_file << std::endl;
-
- std::ofstream out_file;
- out_file.open(gen_file);
- if (!out_file.is_open()) {
- std::cerr << "can't open " << gen_file << std::endl;
- return false;
- }
-
- out_file << "// @generated rust packets from " << input_file.filename().string() << "\n\n";
-
- generate_rust_packet_preamble(out_file);
- if (input_filename == "hci_packets") {
- out_file << "pub trait CommandExpectations { "
- << "type ResponseType;"
- << "fn _to_response_type(pkt: EventPacket) -> Self::ResponseType;"
- << "}";
-
- for (const auto& packet_def : decls.packet_defs_queue_) {
- auto packet = packet_def.second;
- if (!packet->HasAncestorNamed("Command")) {
- continue;
- }
- auto constraint = packet->parent_constraints_.find("op_code");
- if (constraint == packet->parent_constraints_.end()) {
- continue;
- }
- auto opcode = std::get<std::string>(constraint->second);
- for (const auto& other_packet_def : decls.packet_defs_queue_) {
- auto other_packet = other_packet_def.second;
- bool command_status = other_packet->HasAncestorNamed("CommandStatus");
- bool command_complete = other_packet->HasAncestorNamed("CommandComplete");
- if (!command_status && !command_complete) {
- continue;
- }
- auto other_constraint = other_packet->parent_constraints_.find("command_op_code");
- if (other_constraint == other_packet->parent_constraints_.end()) {
- continue;
- }
-
- auto other_opcode = std::get<std::string>(other_constraint->second);
- if (opcode == other_opcode) {
- packet->complement_ = other_packet;
- break;
- }
- }
- }
-
- EnumDef* opcode = nullptr;
- EnumDef* opcode_index = nullptr;
- for (const auto& e : decls.type_defs_queue_) {
- if (e.second->GetDefinitionType() == TypeDef::Type::ENUM) {
- auto* enum_def = static_cast<EnumDef*>(e.second);
- if (enum_def->name_ == "OpCode") {
- opcode = enum_def;
- } else if (enum_def->name_ == "OpCodeIndex") {
- opcode_index = enum_def;
- }
- }
- }
-
- if (opcode_index != nullptr && opcode != nullptr) {
- opcode_index->try_from_enum_ = opcode;
- out_file << "use std::convert::TryFrom;";
- }
- }
-
- for (const auto& e : decls.type_defs_queue_) {
- if (e.second->GetDefinitionType() == TypeDef::Type::ENUM) {
- const auto* enum_def = static_cast<const EnumDef*>(e.second);
- EnumGen gen(*enum_def);
- gen.GenRustDef(out_file);
- out_file << "\n\n";
- }
- }
-
- for (auto& s : decls.type_defs_queue_) {
- if (s.second->GetDefinitionType() == TypeDef::Type::STRUCT) {
- const auto* struct_def = static_cast<const StructDef*>(s.second);
- struct_def->GenRustDef(out_file);
- out_file << "\n\n";
- }
- }
-
- for (const auto& packet_def : decls.packet_defs_queue_) {
- packet_def.second->GenRustDef(out_file);
- out_file << "\n\n";
- }
-
- out_file.close();
- return true;
-}
diff --git a/gd/packet/parser/language_l.ll b/gd/packet/parser/language_l.ll
index c5e9cf181..5814ec1db 100644
--- a/gd/packet/parser/language_l.ll
+++ b/gd/packet/parser/language_l.ll
@@ -7,14 +7,6 @@
#include "declarations.h"
#include "language_y.h"
-#ifndef YYSTYPE
-#define YYSTYPE yy::parser::semantic_type
-#endif
-
-#ifndef YYLTYPE
-#define YYLTYPE yy::parser::location_type
-#endif
-
using token = yy::parser::token;
#define YY_USER_ACTION yylloc->step(); yylloc->columns(yyleng);
@@ -72,7 +64,6 @@ string_literal \".*\"
"enum" { return(token::ENUM); }
"group" { return(token::GROUP); }
"packet" { return(token::PACKET); }
-"test" { return(token::TEST); }
"struct" { return(token::STRUCT); }
"little_endian_packets" {
yylval->integer = 1;
diff --git a/gd/packet/parser/language_y.yy b/gd/packet/parser/language_y.yy
index 287cb0618..caf8d8122 100644
--- a/gd/packet/parser/language_y.yy
+++ b/gd/packet/parser/language_y.yy
@@ -46,9 +46,6 @@
StructDef* struct_definition_value;
- std::set<std::string*>* test_cases_t;
- std::string* test_case_t;
-
std::map<std::string, std::variant<int64_t, std::string>>* constraint_list_t;
std::pair<std::string, std::variant<int64_t, std::string>>* constraint_t;
}
@@ -73,7 +70,6 @@
%token CHECKSUM "checksum"
%token CHECKSUM_START "checksum_start"
%token PADDING "padding"
-%token TEST "test"
%type<enum_definition> enum_definition
%type<enumeration_values> enumeration_list
@@ -96,10 +92,6 @@
%type<struct_definition_value> struct_definition;
-%type<test_cases_t> test_definition;
-%type<test_cases_t> test_case_list;
-%type<test_case_t> test_case;
-
%type<constraint_list_t> constraint_list;
%type<constraint_t> constraint;
%destructor { std::cout << "DESTROYING STRING " << *$$ << "\n"; delete $$; } IDENTIFIER STRING SIZE_MODIFIER
@@ -130,7 +122,8 @@ declaration
| packet_definition
{
DEBUG() << "FOUND PACKET\n\n";
- decls->AddPacketDef($1->name_, $1);
+ decls->AddPacketDef($1->name_, std::move(*$1));
+ delete $1;
}
| struct_definition
{
@@ -149,10 +142,6 @@ declaration
{
// All actions are handled in custom_field_definition
}
- | test_definition
- {
- // All actions are handled in test_definition
- }
enum_definition
: ENUM IDENTIFIER ':' INTEGER '{' enumeration_list ',' '}'
@@ -223,44 +212,6 @@ custom_field_definition
delete $3;
}
-test_definition
- : TEST IDENTIFIER '{' test_case_list ',' '}'
- {
- auto&& packet_name = *$2;
- DEBUG() << "Test Declared: name=" << *$2 << "\n";
- auto packet = decls->GetPacketDef(packet_name);
- if (packet == nullptr) {
- ERRORLOC(LOC) << "Could not find packet " << packet_name << "\n";
- }
-
- for (const auto& t : *$4) {
- packet->AddTestCase(*t);
- }
- delete $2;
- delete $4;
- }
-
-test_case_list
- : test_case
- {
- DEBUG() << "Test case with comma\n";
- $$ = new std::set<std::string*>();
- $$->insert($1);
- }
- | test_case_list ',' test_case
- {
- DEBUG() << "Test case with list\n";
- $$ = $1;
- $$->insert($3);
- }
-
-test_case
- : STRING
- {
- DEBUG() << "Test Case: name=" << *$1 << "\n";
- $$ = $1;
- }
-
struct_definition
: STRUCT IDENTIFIER '{' field_definition_list '}'
{
@@ -367,7 +318,6 @@ packet_definition
<< " used as parent for " << packet_name;
}
-
auto packet_definition = new PacketDef(std::move(packet_name), std::move(field_definition_list), parent_packet);
packet_definition->AssignSizeFields();
@@ -390,7 +340,7 @@ packet_definition
auto parent_packet = decls->GetPacketDef(parent_packet_name);
if (parent_packet == nullptr) {
ERRORLOC(LOC) << "Could not find packet " << parent_packet_name
- << " used as parent for " << packet_name << "\n";
+ << " used as parent for " << packet_name;
}
auto packet_definition = new PacketDef(std::move(packet_name), std::move(field_definition_list), parent_packet);
@@ -668,11 +618,6 @@ size_field_definition
DEBUG() << "Size for payload defined\n";
$$ = new SizeField("payload", $6, LOC);
}
- | SIZE '(' BODY ')' ':' INTEGER
- {
- DEBUG() << "Size for body defined\n";
- $$ = new SizeField("body", $6, LOC);
- }
| COUNT '(' IDENTIFIER ')' ':' INTEGER
{
DEBUG() << "Count field defined\n";
diff --git a/gd/packet/parser/main.cc b/gd/packet/parser/main.cc
index 4e0441d29..8b6737a26 100644
--- a/gd/packet/parser/main.cc
+++ b/gd/packet/parser/main.cc
@@ -19,7 +19,6 @@
#include <cstdio>
#include <filesystem>
#include <fstream>
-#include <iomanip>
#include <iostream>
#include <queue>
#include <regex>
@@ -31,33 +30,36 @@
#include "language_y.h"
-
-int yylex_init(void**);
-int yylex_destroy(void*);
+void yylex_init(void**);
+void yylex_destroy(void*);
void yyset_debug(int, void*);
void yyset_in(FILE*, void*);
-bool generate_cpp_headers_one_file(
- const Declarations& decls,
- const std::filesystem::path& input_file,
- const std::filesystem::path& include_dir,
- const std::filesystem::path& out_dir,
- const std::string& root_namespace);
-
-bool generate_pybind11_sources_one_file(
- const Declarations& decls,
- const std::filesystem::path& input_file,
- const std::filesystem::path& include_dir,
- const std::filesystem::path& out_dir,
- const std::string& root_namespace,
- size_t num_shards);
-
-bool generate_rust_source_one_file(
- const Declarations& decls,
- const std::filesystem::path& input_file,
- const std::filesystem::path& include_dir,
- const std::filesystem::path& out_dir,
- const std::string& root_namespace);
+namespace {
+
+void parse_namespace(const std::string& root_namespace, const std::filesystem::path& input_file_relative_path,
+ std::vector<std::string>* token) {
+ std::filesystem::path gen_namespace = root_namespace / input_file_relative_path;
+ std::string gen_namespace_str = gen_namespace;
+ std::regex path_tokenizer("/");
+ auto it = std::sregex_token_iterator(gen_namespace_str.cbegin(), gen_namespace_str.cend(), path_tokenizer, -1);
+ std::sregex_token_iterator it_end = {};
+ for (; it != it_end; ++it) {
+ token->push_back(it->str());
+ }
+}
+
+void generate_namespace_open(const std::vector<std::string>& token, std::ostream& output) {
+ for (const auto& ns : token) {
+ output << "namespace " << ns << " {" << std::endl;
+ }
+}
+
+void generate_namespace_close(const std::vector<std::string>& token, std::ostream& output) {
+ for (auto it = token.rbegin(); it != token.rend(); ++it) {
+ output << "} //namespace " << *it << std::endl;
+ }
+}
bool parse_declarations_one_file(const std::filesystem::path& input_file, Declarations* declarations) {
void* scanner;
@@ -84,123 +86,361 @@ bool parse_declarations_one_file(const std::filesystem::path& input_file, Declar
// Set endianess before returning
for (auto& s : declarations->type_defs_queue_) {
if (s.second->GetDefinitionType() == TypeDef::Type::STRUCT) {
- auto* struct_def = static_cast<StructDef*>(s.second);
+ auto* struct_def = dynamic_cast<StructDef*>(s.second);
struct_def->SetEndianness(declarations->is_little_endian);
}
}
for (auto& packet_def : declarations->packet_defs_queue_) {
- packet_def.second->SetEndianness(declarations->is_little_endian);
- if (packet_def.second->parent_ != nullptr) {
- packet_def.second->parent_->children_.push_back(packet_def.second);
+ packet_def.second.SetEndianness(declarations->is_little_endian);
+ }
+
+ return true;
+}
+
+bool generate_cpp_headers_one_file(const Declarations& decls, const std::filesystem::path& input_file,
+ const std::filesystem::path& include_dir, const std::filesystem::path& out_dir,
+ const std::string& root_namespace) {
+ auto gen_relative_path = input_file.lexically_relative(include_dir).parent_path();
+
+ auto input_filename = input_file.filename().string().substr(0, input_file.filename().string().find(".pdl"));
+ auto gen_path = out_dir / gen_relative_path;
+
+ std::filesystem::create_directories(gen_path);
+
+ auto gen_file = gen_path / (input_filename + ".h");
+
+ std::ofstream out_file;
+ out_file.open(gen_file);
+ if (!out_file.is_open()) {
+ std::cerr << "can't open " << gen_file << std::endl;
+ return false;
+ }
+
+ out_file << "\n\n";
+ out_file << "#pragma once\n";
+ out_file << "\n\n";
+ out_file << "#include <stdint.h>\n";
+ out_file << "#include <string>\n";
+ out_file << "#include <functional>\n";
+ out_file << "\n\n";
+ out_file << "#include \"os/log.h\"\n";
+ out_file << "#include \"packet/base_packet_builder.h\"\n";
+ out_file << "#include \"packet/bit_inserter.h\"\n";
+ out_file << "#include \"packet/iterator.h\"\n";
+ out_file << "#include \"packet/packet_builder.h\"\n";
+ out_file << "#include \"packet/packet_struct.h\"\n";
+ out_file << "#include \"packet/packet_view.h\"\n";
+ out_file << "#include \"packet/parser/checksum_type_checker.h\"\n";
+ out_file << "#include \"packet/parser/custom_type_checker.h\"\n";
+ out_file << "\n\n";
+
+ for (const auto& c : decls.type_defs_queue_) {
+ if (c.second->GetDefinitionType() == TypeDef::Type::CUSTOM ||
+ c.second->GetDefinitionType() == TypeDef::Type::CHECKSUM) {
+ ((CustomFieldDef*)c.second)->GenInclude(out_file);
+ }
+ }
+ out_file << "\n\n";
+
+ std::vector<std::string> namespace_list;
+ parse_namespace(root_namespace, gen_relative_path, &namespace_list);
+ generate_namespace_open(namespace_list, out_file);
+ out_file << "\n\n";
+
+ for (const auto& c : decls.type_defs_queue_) {
+ if (c.second->GetDefinitionType() == TypeDef::Type::CUSTOM ||
+ c.second->GetDefinitionType() == TypeDef::Type::CHECKSUM) {
+ ((CustomFieldDef*)c.second)->GenUsing(out_file);
+ }
+ }
+ out_file << "\n\n";
+
+ out_file << "using ::bluetooth::packet::BasePacketBuilder;";
+ out_file << "using ::bluetooth::packet::BitInserter;";
+ out_file << "using ::bluetooth::packet::CustomTypeChecker;";
+ out_file << "using ::bluetooth::packet::Iterator;";
+ out_file << "using ::bluetooth::packet::kLittleEndian;";
+ out_file << "using ::bluetooth::packet::PacketBuilder;";
+ out_file << "using ::bluetooth::packet::PacketStruct;";
+ out_file << "using ::bluetooth::packet::PacketView;";
+ out_file << "using ::bluetooth::packet::parser::ChecksumTypeChecker;";
+ out_file << "\n\n";
+
+ for (const auto& e : decls.type_defs_queue_) {
+ if (e.second->GetDefinitionType() == TypeDef::Type::ENUM) {
+ const auto* enum_def = dynamic_cast<const EnumDef*>(e.second);
+ EnumGen gen(*enum_def);
+ gen.GenDefinition(out_file);
+ out_file << "\n\n";
+ }
+ }
+ for (const auto& e : decls.type_defs_queue_) {
+ if (e.second->GetDefinitionType() == TypeDef::Type::ENUM) {
+ const auto* enum_def = dynamic_cast<const EnumDef*>(e.second);
+ EnumGen gen(*enum_def);
+ gen.GenLogging(out_file);
+ out_file << "\n\n";
+ }
+ }
+ for (const auto& ch : decls.type_defs_queue_) {
+ if (ch.second->GetDefinitionType() == TypeDef::Type::CHECKSUM) {
+ const auto* checksum_def = dynamic_cast<const ChecksumDef*>(ch.second);
+ checksum_def->GenChecksumCheck(out_file);
+ }
+ }
+ out_file << "\n/* Done ChecksumChecks */\n";
+
+ for (const auto& c : decls.type_defs_queue_) {
+ if (c.second->GetDefinitionType() == TypeDef::Type::CUSTOM && c.second->size_ == -1 /* Variable Size */) {
+ const auto* custom_field_def = dynamic_cast<const CustomFieldDef*>(c.second);
+ custom_field_def->GenCustomFieldCheck(out_file, decls.is_little_endian);
+ }
+ }
+ out_file << "\n";
+
+ for (auto& s : decls.type_defs_queue_) {
+ if (s.second->GetDefinitionType() == TypeDef::Type::STRUCT) {
+ const auto* struct_def = dynamic_cast<const StructDef*>(s.second);
+ struct_def->GenDefinition(out_file);
+ out_file << "\n";
}
}
+ {
+ StructParserGenerator spg(decls);
+ spg.Generate(out_file);
+ out_file << "\n\n";
+ }
+
+ for (const auto& packet_def : decls.packet_defs_queue_) {
+ packet_def.second.GenParserDefinition(out_file);
+ out_file << "\n\n";
+ }
+
+ for (const auto& packet_def : decls.packet_defs_queue_) {
+ packet_def.second.GenBuilderDefinition(out_file);
+ out_file << "\n\n";
+ }
+
+ generate_namespace_close(namespace_list, out_file);
+
+ out_file.close();
+
return true;
}
-// TODO(b/141583809): stop leaks
-extern "C" const char* __asan_default_options() {
- return "detect_leaks=0";
+// Get the out_file shard at a symbol_count
+std::ofstream& get_out_file(size_t symbol_count, size_t symbol_total, std::vector<std::ofstream>* out_files) {
+ auto symbols_per_shard = symbol_total / out_files->size();
+ auto file_index = std::min(symbol_count / symbols_per_shard, out_files->size() - 1);
+ return out_files->at(file_index);
}
-void usage(const char* prog) {
- auto& ofs = std::cerr;
+bool generate_pybind11_sources_one_file(const Declarations& decls, const std::filesystem::path& input_file,
+ const std::filesystem::path& include_dir, const std::filesystem::path& out_dir,
+ const std::string& root_namespace, size_t num_shards) {
+ auto gen_relative_path = input_file.lexically_relative(include_dir).parent_path();
+
+ auto input_filename = input_file.filename().string().substr(0, input_file.filename().string().find(".pdl"));
+ auto gen_path = out_dir / gen_relative_path;
- ofs << "Usage: " << prog << " [OPTIONS] file1 file2..." << std::endl;
+ std::filesystem::create_directories(gen_path);
- ofs << std::setw(24) << "--out= ";
- ofs << "Root directory for generated output (relative to cwd)." << std::endl;
+ auto gen_relative_header = gen_relative_path / (input_filename + ".h");
- ofs << std::setw(24) << "--include= ";
- ofs << "Generate namespaces relative to this path per file." << std::endl;
+ std::vector<std::string> namespace_list;
+ parse_namespace(root_namespace, gen_relative_path, &namespace_list);
- ofs << std::setw(24) << "--root_namespace= ";
- ofs << "Change root namespace (default = bluetooth)." << std::endl;
+ std::vector<std::ofstream> out_file_shards(num_shards);
+ for (size_t i = 0; i < out_file_shards.size(); i++) {
+ auto filename = gen_path / (input_filename + "_python3_shard_" + std::to_string(i) + ".cc");
+ auto& out_file = out_file_shards[i];
+ out_file.open(filename);
+ if (!out_file.is_open()) {
+ std::cerr << "can't open " << filename << std::endl;
+ return false;
+ }
+ out_file << "#include <pybind11/pybind11.h>\n";
+ out_file << "#include <pybind11/stl.h>\n";
+ out_file << "\n\n";
+ out_file << "#include " << gen_relative_header << "\n";
+ out_file << "\n\n";
+ out_file << "#include \"packet/raw_builder.h\"\n";
+ out_file << "\n\n";
+
+ for (const auto& c : decls.type_defs_queue_) {
+ if (c.second->GetDefinitionType() == TypeDef::Type::CUSTOM) {
+ const auto* custom_def = dynamic_cast<const CustomFieldDef*>(c.second);
+ custom_def->GenPyBind11Include(out_file);
+ }
+ }
+
+ out_file << "\n\n";
+
+ generate_namespace_open(namespace_list, out_file);
+ out_file << "\n\n";
+
+ for (const auto& c : decls.type_defs_queue_) {
+ if (c.second->GetDefinitionType() == TypeDef::Type::CUSTOM ||
+ c.second->GetDefinitionType() == TypeDef::Type::CHECKSUM) {
+ const auto* custom_def = dynamic_cast<const CustomFieldDef*>(c.second);
+ custom_def->GenUsing(out_file);
+ }
+ }
+ out_file << "\n\n";
+
+ out_file << "using ::bluetooth::packet::BasePacketBuilder;";
+ out_file << "using ::bluetooth::packet::BitInserter;";
+ out_file << "using ::bluetooth::packet::CustomTypeChecker;";
+ out_file << "using ::bluetooth::packet::Iterator;";
+ out_file << "using ::bluetooth::packet::kLittleEndian;";
+ out_file << "using ::bluetooth::packet::PacketBuilder;";
+ out_file << "using ::bluetooth::packet::BaseStruct;";
+ out_file << "using ::bluetooth::packet::PacketStruct;";
+ out_file << "using ::bluetooth::packet::PacketView;";
+ out_file << "using ::bluetooth::packet::RawBuilder;";
+ out_file << "using ::bluetooth::packet::parser::ChecksumTypeChecker;";
+ out_file << "\n\n";
+
+ out_file << "namespace py = pybind11;\n\n";
+
+ out_file << "void define_" << input_filename << "_submodule_shard_" << std::to_string(i) << "(py::module& m) {\n\n";
+ }
+ size_t symbol_total = 0;
+ // Only count types that will be generated
+ for (const auto& e : decls.type_defs_queue_) {
+ if (e.second->GetDefinitionType() == TypeDef::Type::ENUM) {
+ symbol_total++;
+ } else if (e.second->GetDefinitionType() == TypeDef::Type::STRUCT) {
+ symbol_total++;
+ }
+ }
+ // View and builder are counted separately
+ symbol_total += decls.packet_defs_queue_.size() * 2;
+ size_t symbol_count = 0;
+
+ for (const auto& e : decls.type_defs_queue_) {
+ if (e.second->GetDefinitionType() == TypeDef::Type::ENUM) {
+ const auto* enum_def = dynamic_cast<const EnumDef*>(e.second);
+ EnumGen gen(*enum_def);
+ auto& out_file = get_out_file(symbol_count, symbol_total, &out_file_shards);
+ gen.GenDefinitionPybind11(out_file);
+ out_file << "\n\n";
+ symbol_count++;
+ }
+ }
+
+ for (const auto& s : decls.type_defs_queue_) {
+ if (s.second->GetDefinitionType() == TypeDef::Type::STRUCT) {
+ const auto* struct_def = dynamic_cast<const StructDef*>(s.second);
+ auto& out_file = get_out_file(symbol_count, symbol_total, &out_file_shards);
+ struct_def->GenDefinitionPybind11(out_file);
+ out_file << "\n";
+ symbol_count++;
+ }
+ }
+
+ for (const auto& packet_def : decls.packet_defs_queue_) {
+ auto& out_file = get_out_file(symbol_count, symbol_total, &out_file_shards);
+ packet_def.second.GenParserDefinitionPybind11(out_file);
+ out_file << "\n\n";
+ symbol_count++;
+ }
+
+ for (const auto& p : decls.packet_defs_queue_) {
+ auto& out_file = get_out_file(symbol_count, symbol_total, &out_file_shards);
+ p.second.GenBuilderDefinitionPybind11(out_file);
+ out_file << "\n\n";
+ symbol_count++;
+ }
+
+ for (auto& out_file : out_file_shards) {
+ out_file << "}\n\n";
+ generate_namespace_close(namespace_list, out_file);
+ }
+
+ auto gen_file_main = gen_path / (input_filename + "_python3.cc");
+ std::ofstream out_file_main;
+ out_file_main.open(gen_file_main);
+ if (!out_file_main.is_open()) {
+ std::cerr << "can't open " << gen_file_main << std::endl;
+ return false;
+ }
+ out_file_main << "#include <pybind11/pybind11.h>\n";
+ generate_namespace_open(namespace_list, out_file_main);
+
+ out_file_main << "namespace py = pybind11;\n\n";
- ofs << std::setw(24) << "--source_root= ";
- ofs << "Root path to the source directory. Find input files relative to this." << std::endl;
+ for (size_t i = 0; i < out_file_shards.size(); i++) {
+ out_file_main << "void define_" << input_filename << "_submodule_shard_" << std::to_string(i)
+ << "(py::module& m);\n";
+ }
- ofs << std::setw(24) << "--num_shards= ";
- ofs << "Number of shards per output pybind11 cc file." << std::endl;
+ out_file_main << "void define_" << input_filename << "_submodule(py::module& m) {\n\n";
+ for (size_t i = 0; i < out_file_shards.size(); i++) {
+ out_file_main << "define_" << input_filename << "_submodule_shard_" << std::to_string(i) << "(m);\n";
+ }
+ out_file_main << "}\n\n";
+
+ generate_namespace_close(namespace_list, out_file_main);
+
+ return true;
+}
+
+} // namespace
+
+// TODO(b/141583809): stop leaks
+extern "C" const char* __asan_default_options() {
+ return "detect_leaks=0";
}
int main(int argc, const char** argv) {
std::filesystem::path out_dir;
std::filesystem::path include_dir;
- std::filesystem::path cwd = std::filesystem::current_path();
- std::filesystem::path source_root = cwd;
std::string root_namespace = "bluetooth";
// Number of shards per output pybind11 cc file
size_t num_shards = 1;
- bool generate_rust = false;
std::queue<std::filesystem::path> input_files;
-
const std::string arg_out = "--out=";
const std::string arg_include = "--include=";
const std::string arg_namespace = "--root_namespace=";
const std::string arg_num_shards = "--num_shards=";
- const std::string arg_rust = "--rust";
- const std::string arg_source_root = "--source_root=";
-
- // Parse the source root first (if it exists) since it will be used for other
- // paths.
- for (int i = 1; i < argc; i++) {
- std::string arg = argv[i];
- if (arg.find(arg_source_root) == 0) {
- source_root = std::filesystem::path(arg.substr(arg_source_root.size()));
- }
- }
for (int i = 1; i < argc; i++) {
std::string arg = argv[i];
if (arg.find(arg_out) == 0) {
- out_dir = cwd / std::filesystem::path(arg.substr(arg_out.size()));
+ out_dir = std::filesystem::current_path() / std::filesystem::path(arg.substr(arg_out.size()));
} else if (arg.find(arg_include) == 0) {
- include_dir = source_root / std::filesystem::path(arg.substr(arg_include.size()));
+ include_dir = std::filesystem::current_path() / std::filesystem::path(arg.substr(arg_include.size()));
} else if (arg.find(arg_namespace) == 0) {
root_namespace = arg.substr(arg_namespace.size());
} else if (arg.find(arg_num_shards) == 0) {
num_shards = std::stoul(arg.substr(arg_num_shards.size()));
- } else if (arg.find(arg_rust) == 0) {
- generate_rust = true;
- } else if (arg.find(arg_source_root) == 0) {
- // Do nothing (just don't treat it as input_files)
} else {
- input_files.emplace(source_root / std::filesystem::path(arg));
+ input_files.emplace(std::filesystem::current_path() / std::filesystem::path(arg));
}
}
if (out_dir == std::filesystem::path() || include_dir == std::filesystem::path() || num_shards == 0) {
- usage(argv[0]);
+ std::cerr << "Usage: bt-packetgen --out=OUT --include=INCLUDE --root_namespace=NAMESPACE --num_shards=NUM_SHARDS "
+ << "input_files..." << std::endl;
return 1;
}
- std::cout << "out dir: " << out_dir << std::endl;
-
while (!input_files.empty()) {
Declarations declarations;
- std::cout << "parsing: " << input_files.front() << std::endl;
if (!parse_declarations_one_file(input_files.front(), &declarations)) {
std::cerr << "Cannot parse " << input_files.front() << " correctly" << std::endl;
return 2;
}
- if (generate_rust) {
- std::cout << "generating rust" << std::endl;
- if (!generate_rust_source_one_file(declarations, input_files.front(), include_dir, out_dir, root_namespace)) {
- std::cerr << "Didn't generate rust source for " << input_files.front() << std::endl;
- return 5;
- }
- } else {
- std::cout << "generating c++ and pybind11" << std::endl;
- if (!generate_cpp_headers_one_file(declarations, input_files.front(), include_dir, out_dir, root_namespace)) {
- std::cerr << "Didn't generate cpp headers for " << input_files.front() << std::endl;
- return 3;
- }
- if (!generate_pybind11_sources_one_file(
- declarations, input_files.front(), include_dir, out_dir, root_namespace, num_shards)) {
- std::cerr << "Didn't generate pybind11 sources for " << input_files.front() << std::endl;
- return 4;
- }
+ if (!generate_cpp_headers_one_file(declarations, input_files.front(), include_dir, out_dir, root_namespace)) {
+ std::cerr << "Didn't generate cpp headers for " << input_files.front() << std::endl;
+ return 3;
+ }
+ if (!generate_pybind11_sources_one_file(declarations, input_files.front(), include_dir, out_dir, root_namespace,
+ num_shards)) {
+ std::cerr << "Didn't generate pybind11 sources for " << input_files.front() << std::endl;
+ return 4;
}
input_files.pop();
}
diff --git a/gd/packet/parser/packet_def.cc b/gd/packet/parser/packet_def.cc
index a59b06d1f..c2e8ac016 100644
--- a/gd/packet/parser/packet_def.cc
+++ b/gd/packet/parser/packet_def.cc
@@ -16,7 +16,6 @@
#include "packet_def.h"
-#include <iomanip>
#include <list>
#include <set>
@@ -42,14 +41,12 @@ void PacketDef::GenParserDefinition(std::ostream& s) const {
// Specialize function
if (parent_ != nullptr) {
s << "static " << name_ << "View Create(" << parent_->name_ << "View parent)";
- s << "{ return " << name_ << "View(std::move(parent)); }";
+ s << "{ return " << name_ << "View(parent); }";
} else {
s << "static " << name_ << "View Create(PacketView<" << (is_little_endian_ ? "" : "!") << "kLittleEndian> packet) ";
- s << "{ return " << name_ << "View(std::move(packet)); }";
+ s << "{ return " << name_ << "View(packet); }";
}
- GenTestingParserFromBytes(s);
-
std::set<std::string> fixed_types = {
FixedScalarField::kFieldType,
FixedEnumField::kFieldType,
@@ -65,17 +62,13 @@ void PacketDef::GenParserDefinition(std::ostream& s) const {
GenValidator(s);
s << "\n";
- s << " public:";
- GenParserToString(s);
- s << "\n";
-
s << " protected:\n";
// Constructor from a View
if (parent_ != nullptr) {
- s << "explicit " << name_ << "View(" << parent_->name_ << "View parent)";
- s << " : " << parent_->name_ << "View(std::move(parent)) { was_validated_ = false; }";
+ s << name_ << "View(" << parent_->name_ << "View parent)";
+ s << " : " << parent_->name_ << "View(parent) { was_validated_ = false; }";
} else {
- s << "explicit " << name_ << "View(PacketView<" << (is_little_endian_ ? "" : "!") << "kLittleEndian> packet) ";
+ s << name_ << "View(PacketView<" << (is_little_endian_ ? "" : "!") << "kLittleEndian> packet) ";
s << " : PacketView<" << (is_little_endian_ ? "" : "!") << "kLittleEndian>(packet) { was_validated_ = false;}";
}
@@ -91,29 +84,6 @@ void PacketDef::GenParserDefinition(std::ostream& s) const {
s << "};\n";
}
-void PacketDef::GenTestingParserFromBytes(std::ostream& s) const {
- s << "\n#if defined(PACKET_FUZZ_TESTING) || defined(PACKET_TESTING) || defined(FUZZ_TARGET)\n";
-
- s << "static " << name_ << "View FromBytes(std::vector<uint8_t> bytes) {";
- s << "auto vec = std::make_shared<std::vector<uint8_t>>(bytes);";
- s << "return " << name_ << "View::Create(";
- auto ancestor_ptr = parent_;
- size_t parent_parens = 0;
- while (ancestor_ptr != nullptr) {
- s << ancestor_ptr->name_ << "View::Create(";
- parent_parens++;
- ancestor_ptr = ancestor_ptr->parent_;
- }
- s << "PacketView<" << (is_little_endian_ ? "" : "!") << "kLittleEndian>(vec)";
- for (size_t i = 0; i < parent_parens; i++) {
- s << ")";
- }
- s << ");";
- s << "}";
-
- s << "\n#endif\n";
-}
-
void PacketDef::GenParserDefinitionPybind11(std::ostream& s) const {
s << "py::class_<" << name_ << "View";
if (parent_ != nullptr) {
@@ -185,10 +155,6 @@ void PacketDef::GenValidator(std::ostream& s) const {
s << "protected:";
s << "virtual bool IsValid_() const {";
- if (parent_ != nullptr) {
- s << "if (!" << parent_->name_ << "View::IsValid_()) { return false; } ";
- }
-
// Offset by the parents known size. We know that any dynamic fields can
// already be called since the parent must have already been validated by
// this point.
@@ -317,35 +283,6 @@ void PacketDef::GenValidator(std::ostream& s) const {
}
}
-void PacketDef::GenParserToString(std::ostream& s) const {
- s << "virtual std::string ToString() " << (parent_ != nullptr ? " override" : "") << " {";
- s << "std::stringstream ss;";
- s << "ss << std::showbase << std::hex << \"" << name_ << " { \";";
-
- if (fields_.size() > 0) {
- s << "ss << \"\" ";
- bool firstfield = true;
- for (const auto& field : fields_) {
- if (field->GetFieldType() == ReservedField::kFieldType || field->GetFieldType() == FixedScalarField::kFieldType ||
- field->GetFieldType() == ChecksumStartField::kFieldType)
- continue;
-
- s << (firstfield ? " << \"" : " << \", ") << field->GetName() << " = \" << ";
-
- field->GenStringRepresentation(s, field->GetGetterFunctionName() + "()");
-
- if (firstfield) {
- firstfield = false;
- }
- }
- s << ";";
- }
-
- s << "ss << \" }\";";
- s << "return ss.str();";
- s << "}\n";
-}
-
void PacketDef::GenBuilderDefinition(std::ostream& s) const {
s << "class " << name_ << "Builder";
if (parent_ != nullptr) {
@@ -359,14 +296,11 @@ void PacketDef::GenBuilderDefinition(std::ostream& s) const {
}
s << " {";
s << " public:";
- s << " virtual ~" << name_ << "Builder() = default;";
+ s << " virtual ~" << name_ << "Builder()" << (parent_ != nullptr ? " override" : "") << " = default;";
if (!fields_.HasBody()) {
GenBuilderCreate(s);
s << "\n";
-
- GenTestingFromView(s);
- s << "\n";
}
GenSerialize(s);
@@ -392,26 +326,6 @@ void PacketDef::GenBuilderDefinition(std::ostream& s) const {
s << "\n";
}
-void PacketDef::GenTestingFromView(std::ostream& s) const {
- s << "#if defined(PACKET_FUZZ_TESTING) || defined(PACKET_TESTING) || defined(FUZZ_TARGET)\n";
-
- s << "static std::unique_ptr<" << name_ << "Builder> FromView(" << name_ << "View view) {";
- s << "return " << name_ << "Builder::Create(";
- FieldList params = GetParamList().GetFieldsWithoutTypes({
- BodyField::kFieldType,
- });
- for (std::size_t i = 0; i < params.size(); i++) {
- params[i]->GenBuilderParameterFromView(s);
- if (i != params.size() - 1) {
- s << ", ";
- }
- }
- s << ");";
- s << "}";
-
- s << "\n#endif\n";
-}
-
void PacketDef::GenBuilderDefinitionPybind11(std::ostream& s) const {
s << "py::class_<" << name_ << "Builder";
if (parent_ != nullptr) {
@@ -442,16 +356,39 @@ void PacketDef::GenTestDefine(std::ostream& s) const {
s << "class " << name_ << "ReflectionTest : public testing::TestWithParam<std::vector<uint8_t>> { ";
s << "public: ";
s << "void CompareBytes(std::vector<uint8_t> captured_packet) {";
- s << name_ << "View view = " << name_ << "View::FromBytes(captured_packet);";
+ s << "auto vec = std::make_shared<std::vector<uint8_t>>(captured_packet.begin(), captured_packet.end());";
+ s << name_ << "View view = " << name_ << "View::Create(";
+ auto ancestor_ptr = parent_;
+ size_t parent_parens = 0;
+ while (ancestor_ptr != nullptr) {
+ s << ancestor_ptr->name_ << "View::Create(";
+ parent_parens++;
+ ancestor_ptr = ancestor_ptr->parent_;
+ }
+ s << "vec";
+ for (size_t i = 0; i < parent_parens; i++) {
+ s << ")";
+ }
+ s << ");";
s << "if (!view.IsValid()) { LOG_INFO(\"Invalid Packet Bytes (size = %zu)\", view.size());";
- s << "for (size_t i = 0; i < view.size(); i++) { LOG_INFO(\"%5zd:%02X\", i, *(view.begin() + i)); }}";
+ s << "for (size_t i = 0; i < view.size(); i++) { LOG_DEBUG(\"%5zd:%02X\", i, *(view.begin() + i)); }}";
s << "ASSERT_TRUE(view.IsValid());";
- s << "auto packet = " << name_ << "Builder::FromView(view);";
+ s << "auto packet = " << name_ << "Builder::Create(";
+ FieldList params = GetParamList().GetFieldsWithoutTypes({
+ BodyField::kFieldType,
+ });
+ for (int i = 0; i < params.size(); i++) {
+ params[i]->GenBuilderParameterFromView(s);
+ if (i != params.size() - 1) {
+ s << ", ";
+ }
+ }
+ s << ");";
s << "std::shared_ptr<std::vector<uint8_t>> packet_bytes = std::make_shared<std::vector<uint8_t>>();";
s << "packet_bytes->reserve(packet->size());";
s << "BitInserter it(*packet_bytes);";
s << "packet->Serialize(it);";
- s << "ASSERT_EQ(*packet_bytes, captured_packet);";
+ s << "ASSERT_EQ(*packet_bytes, *vec);";
s << "}";
s << "};";
s << "TEST_P(" << name_ << "ReflectionTest, generatedReflectionTest) {";
@@ -459,26 +396,6 @@ void PacketDef::GenTestDefine(std::ostream& s) const {
s << "}";
s << "INSTANTIATE_TEST_SUITE_P(" << name_ << "_reflection, ";
s << name_ << "ReflectionTest, testing::Values(__VA_ARGS__))";
- int i = 0;
- for (const auto& bytes : test_cases_) {
- s << "\nuint8_t " << name_ << "_test_bytes_" << i << "[] = \"" << bytes << "\";";
- s << "std::vector<uint8_t> " << name_ << "_test_vec_" << i << "(";
- s << name_ << "_test_bytes_" << i << ",";
- s << name_ << "_test_bytes_" << i << " + sizeof(";
- s << name_ << "_test_bytes_" << i << ") - 1);";
- i++;
- }
- if (!test_cases_.empty()) {
- i = 0;
- s << "\nDEFINE_AND_INSTANTIATE_" << name_ << "ReflectionTest(";
- for (auto bytes : test_cases_) {
- if (i > 0) {
- s << ",";
- }
- s << name_ << "_test_vec_" << i++;
- }
- s << ");";
- }
s << "\n#endif";
}
@@ -486,10 +403,32 @@ void PacketDef::GenFuzzTestDefine(std::ostream& s) const {
s << "#if defined(PACKET_FUZZ_TESTING) || defined(PACKET_TESTING)\n";
s << "#define DEFINE_" << name_ << "ReflectionFuzzTest() ";
s << "void Run" << name_ << "ReflectionFuzzTest(const uint8_t* data, size_t size) {";
- s << "auto vec = std::vector<uint8_t>(data, data + size);";
- s << name_ << "View view = " << name_ << "View::FromBytes(vec);";
+ s << "auto vec = std::make_shared<std::vector<uint8_t>>(data, data + size);";
+ s << name_ << "View view = " << name_ << "View::Create(";
+ auto ancestor_ptr = parent_;
+ size_t parent_parens = 0;
+ while (ancestor_ptr != nullptr) {
+ s << ancestor_ptr->name_ << "View::Create(";
+ parent_parens++;
+ ancestor_ptr = ancestor_ptr->parent_;
+ }
+ s << "vec";
+ for (size_t i = 0; i < parent_parens; i++) {
+ s << ")";
+ }
+ s << ");";
s << "if (!view.IsValid()) { return; }";
- s << "auto packet = " << name_ << "Builder::FromView(view);";
+ s << "auto packet = " << name_ << "Builder::Create(";
+ FieldList params = GetParamList().GetFieldsWithoutTypes({
+ BodyField::kFieldType,
+ });
+ for (int i = 0; i < params.size(); i++) {
+ params[i]->GenBuilderParameterFromView(s);
+ if (i != params.size() - 1) {
+ s << ", ";
+ }
+ }
+ s << ");";
s << "std::shared_ptr<std::vector<uint8_t>> packet_bytes = std::make_shared<std::vector<uint8_t>>();";
s << "packet_bytes->reserve(packet->size());";
s << "BitInserter it(*packet_bytes);";
@@ -523,7 +462,7 @@ void PacketDef::GenBuilderCreate(std::ostream& s) const {
s << "static std::unique_ptr<" << name_ << "Builder> Create(";
auto params = GetParamList();
- for (std::size_t i = 0; i < params.size(); i++) {
+ for (int i = 0; i < params.size(); i++) {
params[i]->GenBuilderParameter(s);
if (i != params.size() - 1) {
s << ", ";
@@ -539,7 +478,7 @@ void PacketDef::GenBuilderCreate(std::ostream& s) const {
BodyField::kFieldType,
});
// Add the parameters.
- for (std::size_t i = 0; i < params.size(); i++) {
+ for (int i = 0; i < params.size(); i++) {
if (params[i]->BuilderParameterMustBeMoved()) {
s << "std::move(" << params[i]->GetName() << ")";
} else {
@@ -600,17 +539,17 @@ void PacketDef::GenBuilderCreatePybind11(std::ostream& s) const {
// Serialize each struct
s << "auto " << param->GetName() + "_bytes = std::make_shared<std::vector<uint8_t>>();";
s << param->GetName() + "_bytes->reserve(" << param->GetName() << "[i]->size());";
+ s << "auto " << param->GetName() + "_reparsed = std::make_unique<" << struct_type << ">();";
s << "BitInserter " << param->GetName() + "_bi(*" << param->GetName() << "_bytes);";
s << param->GetName() << "[i]->Serialize(" << param->GetName() << "_bi);";
// Parse it again
s << "auto " << param->GetName() << "_view = PacketView<kLittleEndian>(" << param->GetName() << "_bytes);";
- s << param->GetElementField()->GetDataType() << " " << param->GetName() << "_reparsed = ";
- s << "Parse" << struct_type << "(" << param->GetName() + "_view.begin());";
+ s << "auto result = Parse" << struct_type << "(" << param->GetName() + "_view.begin());";
// Push it into a new container
if (param->GetFieldType() == VectorField::kFieldType) {
s << move_only_param_name << ".push_back(std::move(" << param->GetName() + "_reparsed));";
} else if (param->GetFieldType() == ArrayField::kFieldType) {
- s << move_only_param_name << "[i] = std::move(" << param->GetName() << "_reparsed);";
+ s << move_only_param_name << "[i] = " << param->GetName() << "_reparsed;";
} else {
ERROR() << param << " is not supported by Pybind11";
}
@@ -655,7 +594,7 @@ void PacketDef::GenBuilderParameterChecker(std::ostream& s) const {
// Generate function arguments.
s << "void CheckParameterValues(";
- for (std::size_t i = 0; i < params_to_validate.size(); i++) {
+ for (int i = 0; i < params_to_validate.size(); i++) {
params_to_validate[i]->GenBuilderParameter(s);
if (i != params_to_validate.size() - 1) {
s << ", ";
@@ -671,14 +610,14 @@ void PacketDef::GenBuilderParameterChecker(std::ostream& s) const {
}
void PacketDef::GenBuilderConstructor(std::ostream& s) const {
- s << "explicit " << name_ << "Builder(";
+ s << name_ << "Builder(";
// Generate the constructor parameters.
auto params = GetParamList().GetFieldsWithoutTypes({
PayloadField::kFieldType,
BodyField::kFieldType,
});
- for (std::size_t i = 0; i < params.size(); i++) {
+ for (int i = 0; i < params.size(); i++) {
params[i]->GenBuilderParameter(s);
if (i != params.size() - 1) {
s << ", ";
@@ -702,7 +641,7 @@ void PacketDef::GenBuilderConstructor(std::ostream& s) const {
// Go through all the fields and replace constrained fields with fixed values
// when calling the parent constructor.
- for (std::size_t i = 0; i < parent_params.size(); i++) {
+ for (int i = 0; i < parent_params.size(); i++) {
const auto& field = parent_params[i];
const auto& constraint = parent_constraints_.find(field->GetName());
if (constraint != parent_constraints_.end()) {
@@ -736,7 +675,7 @@ void PacketDef::GenBuilderConstructor(std::ostream& s) const {
if (parent_ != nullptr && saved_params.size() > 0) {
s << ",";
}
- for (std::size_t i = 0; i < saved_params.size(); i++) {
+ for (int i = 0; i < saved_params.size(); i++) {
const auto& saved_param_name = saved_params[i]->GetName();
if (saved_params[i]->BuilderParameterMustBeMoved()) {
s << saved_param_name << "_(std::move(" << saved_param_name << "))";
@@ -753,7 +692,7 @@ void PacketDef::GenBuilderConstructor(std::ostream& s) const {
if (params_to_validate.size() > 0) {
s << "CheckParameterValues(";
- for (std::size_t i = 0; i < params_to_validate.size(); i++) {
+ for (int i = 0; i < params_to_validate.size(); i++) {
s << params_to_validate[i]->GetName() << "_";
if (i != params_to_validate.size() - 1) {
s << ", ";
@@ -764,575 +703,3 @@ void PacketDef::GenBuilderConstructor(std::ostream& s) const {
s << "}\n";
}
-
-void PacketDef::GenRustChildEnums(std::ostream& s) const {
- if (HasChildEnums()) {
- bool payload = fields_.HasPayload();
- s << "#[derive(Debug)] ";
- s << "enum " << name_ << "DataChild {";
- for (const auto& child : children_) {
- s << child->name_ << "(Arc<" << child->name_ << "Data>),";
- }
- if (payload) {
- s << "Payload(Bytes),";
- }
- s << "None,";
- s << "}\n";
-
- s << "impl " << name_ << "DataChild {";
- s << "fn get_total_size(&self) -> usize {";
- s << "match self {";
- for (const auto& child : children_) {
- s << name_ << "DataChild::" << child->name_ << "(value) => value.get_total_size(),";
- }
- if (payload) {
- s << name_ << "DataChild::Payload(p) => p.len(),";
- }
- s << name_ << "DataChild::None => 0,";
- s << "}\n";
- s << "}\n";
- s << "}\n";
-
- s << "#[derive(Debug)] ";
- s << "pub enum " << name_ << "Child {";
- for (const auto& child : children_) {
- s << child->name_ << "(" << child->name_ << "Packet),";
- }
- if (payload) {
- s << "Payload(Bytes),";
- }
- s << "None,";
- s << "}\n";
- }
-}
-
-void PacketDef::GenRustStructDeclarations(std::ostream& s) const {
- s << "#[derive(Debug)] ";
- s << "struct " << name_ << "Data {";
-
- // Generate struct fields
- GenRustStructFieldNameAndType(s);
- if (HasChildEnums()) {
- s << "child: " << name_ << "DataChild,";
- }
- s << "}\n";
-
- // Generate accessor struct
- s << "#[derive(Debug, Clone)] ";
- s << "pub struct " << name_ << "Packet {";
- auto lineage = GetAncestors();
- lineage.push_back(this);
- for (auto it = lineage.begin(); it != lineage.end(); it++) {
- auto def = *it;
- s << util::CamelCaseToUnderScore(def->name_) << ": Arc<" << def->name_ << "Data>,";
- }
- s << "}\n";
-
- // Generate builder struct
- s << "#[derive(Debug)] ";
- s << "pub struct " << name_ << "Builder {";
- auto params = GetParamList().GetFieldsWithoutTypes({
- PayloadField::kFieldType,
- BodyField::kFieldType,
- });
- for (auto param : params) {
- s << "pub ";
- param->GenRustNameAndType(s);
- s << ", ";
- }
- if (fields_.HasPayload()) {
- s << "pub payload: Option<Bytes>,";
- }
- s << "}\n";
-}
-
-bool PacketDef::GenRustStructFieldNameAndType(std::ostream& s) const {
- auto fields = fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- CountField::kFieldType,
- PaddingField::kFieldType,
- ReservedField::kFieldType,
- SizeField::kFieldType,
- PayloadField::kFieldType,
- FixedScalarField::kFieldType,
- });
- if (fields.size() == 0) {
- return false;
- }
- for (const auto& field : fields) {
- field->GenRustNameAndType(s);
- s << ", ";
- }
- return true;
-}
-
-void PacketDef::GenRustStructFieldNames(std::ostream& s) const {
- auto fields = fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- CountField::kFieldType,
- PaddingField::kFieldType,
- ReservedField::kFieldType,
- SizeField::kFieldType,
- PayloadField::kFieldType,
- FixedScalarField::kFieldType,
- });
- for (const auto field : fields) {
- s << field->GetName();
- s << ", ";
- }
-}
-
-void PacketDef::GenRustStructImpls(std::ostream& s) const {
- s << "impl " << name_ << "Data {";
-
- // conforms function
- s << "fn conforms(bytes: &[u8]) -> bool {";
- GenRustConformanceCheck(s);
-
- auto fields = fields_.GetFieldsWithTypes({
- StructField::kFieldType,
- });
-
- for (auto const& field : fields) {
- auto start_offset = GetOffsetForField(field->GetName(), false);
- auto end_offset = GetOffsetForField(field->GetName(), true);
-
- s << "if !" << field->GetRustDataType() << "::conforms(&bytes[" << start_offset.bytes();
- s << ".." << start_offset.bytes() + field->GetSize().bytes() << "]) { return false; }";
- }
-
- s << " true";
- s << "}";
-
- // parse function
- if (parent_constraints_.empty() && children_.size() > 1 && parent_ != nullptr) {
- auto constraint = FindConstraintField();
- auto constraint_field = GetParamList().GetField(constraint);
- auto constraint_type = constraint_field->GetRustDataType();
- s << "fn parse(bytes: &[u8], " << constraint << ": " << constraint_type << ") -> Result<Self> {";
- } else {
- s << "fn parse(bytes: &[u8]) -> Result<Self> {";
- }
- fields = fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- });
-
- for (auto const& field : fields) {
- auto start_field_offset = GetOffsetForField(field->GetName(), false);
- auto end_field_offset = GetOffsetForField(field->GetName(), true);
-
- if (start_field_offset.empty() && end_field_offset.empty()) {
- ERROR(field) << "Field location for " << field->GetName() << " is ambiguous, "
- << "no method exists to determine field location from begin() or end().\n";
- }
-
- field->GenBoundsCheck(s, start_field_offset, end_field_offset, name_);
- field->GenRustGetter(s, start_field_offset, end_field_offset);
- }
-
- auto payload_field = fields_.GetFieldsWithTypes({
- PayloadField::kFieldType,
- });
-
- Size payload_offset;
-
- if (payload_field.HasPayload()) {
- payload_offset = GetOffsetForField(payload_field[0]->GetName(), false);
- }
-
- auto constraint_name = FindConstraintField();
- auto constrained_descendants = FindDescendantsWithConstraint(constraint_name);
-
- if (children_.size() > 1) {
- s << "let child = match " << constraint_name << " {";
-
- for (const auto& desc : constrained_descendants) {
- auto desc_path = FindPathToDescendant(desc.first->name_);
- std::reverse(desc_path.begin(), desc_path.end());
- auto constraint_field = GetParamList().GetField(constraint_name);
- auto constraint_type = constraint_field->GetFieldType();
-
- if (constraint_type == EnumField::kFieldType) {
- auto type = std::get<std::string>(desc.second);
- auto variant_name = type.substr(type.find("::") + 2, type.length());
- auto enum_type = type.substr(0, type.find("::"));
- auto enum_variant = enum_type + "::"
- + util::UnderscoreToCamelCase(util::ToLowerCase(variant_name));
- s << enum_variant;
- s << " if " << desc_path[0]->name_ << "Data::conforms(&bytes[..])";
- s << " => {";
- s << name_ << "DataChild::";
- s << desc_path[0]->name_ << "(Arc::new(";
- if (desc_path[0]->parent_constraints_.empty()) {
- s << desc_path[0]->name_ << "Data::parse(&bytes[..]";
- s << ", " << enum_variant << ")?))";
- } else {
- s << desc_path[0]->name_ << "Data::parse(&bytes[..])?))";
- }
- } else if (constraint_type == ScalarField::kFieldType) {
- s << std::get<int64_t>(desc.second) << " => {";
- s << "unimplemented!();";
- }
- s << "}\n";
- }
-
- if (!constrained_descendants.empty()) {
- s << "v => return Err(Error::ConstraintOutOfBounds{field: \"" << constraint_name
- << "\".to_string(), value: v as u64}),";
- }
-
- s << "};\n";
- } else if (children_.size() == 1) {
- auto child = children_.at(0);
- s << "let child = match " << child->name_ << "Data::parse(&bytes[..]) {";
- s << " Ok(c) if " << child->name_ << "Data::conforms(&bytes[..]) => {";
- s << name_ << "DataChild::" << child->name_ << "(Arc::new(c))";
- s << " },";
- s << " Err(Error::InvalidLengthError { .. }) => " << name_ << "DataChild::None,";
- s << " _ => return Err(Error::InvalidPacketError),";
- s << "};";
- } else if (fields_.HasPayload()) {
- s << "let child = if payload.len() > 0 {";
- s << name_ << "DataChild::Payload(Bytes::from(payload))";
- s << "} else {";
- s << name_ << "DataChild::None";
- s << "};";
- }
-
- s << "Ok(Self {";
- fields = fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- CountField::kFieldType,
- PaddingField::kFieldType,
- ReservedField::kFieldType,
- SizeField::kFieldType,
- PayloadField::kFieldType,
- FixedScalarField::kFieldType,
- });
-
- if (fields.size() > 0) {
- for (const auto& field : fields) {
- auto field_type = field->GetFieldType();
- s << field->GetName();
- s << ", ";
- }
- }
-
- if (HasChildEnums()) {
- s << "child,";
- }
- s << "})\n";
- s << "}\n";
-
- // write_to function
- s << "fn write_to(&self, buffer: &mut BytesMut) {";
- GenRustWriteToFields(s);
-
- if (HasChildEnums()) {
- s << "match &self.child {";
- for (const auto& child : children_) {
- s << name_ << "DataChild::" << child->name_ << "(value) => value.write_to(buffer),";
- }
- if (fields_.HasPayload()) {
- auto offset = GetOffsetForField("payload");
- s << name_ << "DataChild::Payload(p) => buffer[" << offset.bytes() << "..].copy_from_slice(&p[..]),";
- }
- s << name_ << "DataChild::None => {}";
- s << "}";
- }
-
- s << "}\n";
-
- s << "fn get_total_size(&self) -> usize {";
- if (HasChildEnums()) {
- s << "self.get_size() + self.child.get_total_size()";
- } else {
- s << "self.get_size()";
- }
- s << "}\n";
-
- s << "fn get_size(&self) -> usize {";
- GenSizeRetVal(s);
- s << "}\n";
- s << "}\n";
-}
-
-void PacketDef::GenRustAccessStructImpls(std::ostream& s) const {
- if (complement_ != nullptr) {
- auto complement_root = complement_->GetRootDef();
- auto complement_root_accessor = util::CamelCaseToUnderScore(complement_root->name_);
- s << "impl CommandExpectations for " << name_ << "Packet {";
- s << " type ResponseType = " << complement_->name_ << "Packet;";
- s << " fn _to_response_type(pkt: EventPacket) -> Self::ResponseType { ";
- s << complement_->name_ << "Packet::new(pkt." << complement_root_accessor << ".clone())";
- s << " }";
- s << "}";
- }
-
- s << "impl Packet for " << name_ << "Packet {";
- auto root = GetRootDef();
- auto root_accessor = util::CamelCaseToUnderScore(root->name_);
-
- s << "fn to_bytes(self) -> Bytes {";
- s << " let mut buffer = BytesMut::new();";
- s << " buffer.resize(self." << root_accessor << ".get_total_size(), 0);";
- s << " self." << root_accessor << ".write_to(&mut buffer);";
- s << " buffer.freeze()";
- s << "}\n";
-
- s << "fn to_vec(self) -> Vec<u8> { self.to_bytes().to_vec() }\n";
- s << "}";
-
- s << "impl " << name_ << "Packet {";
- if (parent_ == nullptr) {
- s << "pub fn parse(bytes: &[u8]) -> Result<Self> { ";
- s << "Ok(Self::new(Arc::new(" << name_ << "Data::parse(bytes)?)))";
- s << "}";
- }
-
- if (HasChildEnums()) {
- s << " pub fn specialize(&self) -> " << name_ << "Child {";
- s << " match &self." << util::CamelCaseToUnderScore(name_) << ".child {";
- for (const auto& child : children_) {
- s << name_ << "DataChild::" << child->name_ << "(_) => " << name_ << "Child::" << child->name_ << "("
- << child->name_ << "Packet::new(self." << root_accessor << ".clone())),";
- }
- if (fields_.HasPayload()) {
- s << name_ << "DataChild::Payload(p) => " << name_ << "Child::Payload(p.clone()),";
- }
- s << name_ << "DataChild::None => " << name_ << "Child::None,";
- s << "}}";
- }
- auto lineage = GetAncestors();
- lineage.push_back(this);
- const ParentDef* prev = nullptr;
-
- s << " fn new(root: Arc<" << root->name_ << "Data>) -> Self {";
- for (auto it = lineage.begin(); it != lineage.end(); it++) {
- auto def = *it;
- auto accessor_name = util::CamelCaseToUnderScore(def->name_);
- if (prev == nullptr) {
- s << "let " << accessor_name << " = root;";
- } else {
- s << "let " << accessor_name << " = match &" << util::CamelCaseToUnderScore(prev->name_) << ".child {";
- s << prev->name_ << "DataChild::" << def->name_ << "(value) => (*value).clone(),";
- s << "_ => panic!(\"inconsistent state - child was not " << def->name_ << "\"),";
- s << "};";
- }
- prev = def;
- }
- s << "Self {";
- for (auto it = lineage.begin(); it != lineage.end(); it++) {
- auto def = *it;
- s << util::CamelCaseToUnderScore(def->name_) << ",";
- }
- s << "}}";
-
- for (auto it = lineage.begin(); it != lineage.end(); it++) {
- auto def = *it;
- auto fields = def->fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- CountField::kFieldType,
- PaddingField::kFieldType,
- ReservedField::kFieldType,
- SizeField::kFieldType,
- PayloadField::kFieldType,
- FixedScalarField::kFieldType,
- });
-
- for (auto const& field : fields) {
- if (field->GetterIsByRef()) {
- s << "pub fn get_" << field->GetName() << "(&self) -> &" << field->GetRustDataType() << "{";
- s << " &self." << util::CamelCaseToUnderScore(def->name_) << ".as_ref()." << field->GetName();
- s << "}\n";
- } else {
- s << "pub fn get_" << field->GetName() << "(&self) -> " << field->GetRustDataType() << "{";
- s << " self." << util::CamelCaseToUnderScore(def->name_) << ".as_ref()." << field->GetName();
- s << "}\n";
- }
- }
- }
-
- s << "}\n";
-
- lineage = GetAncestors();
- for (auto it = lineage.begin(); it != lineage.end(); it++) {
- auto def = *it;
- s << "impl Into<" << def->name_ << "Packet> for " << name_ << "Packet {";
- s << " fn into(self) -> " << def->name_ << "Packet {";
- s << def->name_ << "Packet::new(self." << util::CamelCaseToUnderScore(root->name_) << ")";
- s << " }";
- s << "}\n";
- }
-}
-
-void PacketDef::GenRustBuilderStructImpls(std::ostream& s) const {
- if (complement_ != nullptr) {
- auto complement_root = complement_->GetRootDef();
- auto complement_root_accessor = util::CamelCaseToUnderScore(complement_root->name_);
- s << "impl CommandExpectations for " << name_ << "Builder {";
- s << " type ResponseType = " << complement_->name_ << "Packet;";
- s << " fn _to_response_type(pkt: EventPacket) -> Self::ResponseType { ";
- s << complement_->name_ << "Packet::new(pkt." << complement_root_accessor << ".clone())";
- s << " }";
- s << "}";
- }
-
- s << "impl " << name_ << "Builder {";
- s << "pub fn build(self) -> " << name_ << "Packet {";
- auto lineage = GetAncestors();
- lineage.push_back(this);
- std::reverse(lineage.begin(), lineage.end());
-
- auto all_constraints = GetAllConstraints();
-
- const ParentDef* prev = nullptr;
- for (auto ancestor : lineage) {
- auto fields = ancestor->fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- CountField::kFieldType,
- PaddingField::kFieldType,
- ReservedField::kFieldType,
- SizeField::kFieldType,
- PayloadField::kFieldType,
- FixedScalarField::kFieldType,
- });
-
- auto accessor_name = util::CamelCaseToUnderScore(ancestor->name_);
- s << "let " << accessor_name << "= Arc::new(" << ancestor->name_ << "Data {";
- for (auto field : fields) {
- auto constraint = all_constraints.find(field->GetName());
- s << field->GetName() << ": ";
- if (constraint != all_constraints.end()) {
- if (field->GetFieldType() == ScalarField::kFieldType) {
- s << std::get<int64_t>(constraint->second);
- } else if (field->GetFieldType() == EnumField::kFieldType) {
- auto value = std::get<std::string>(constraint->second);
- auto constant = value.substr(value.find("::") + 2, std::string::npos);
- s << field->GetDataType() << "::" << util::ConstantCaseToCamelCase(constant);
- ;
- } else {
- ERROR(field) << "Constraints on non enum/scalar fields should be impossible.";
- }
- } else {
- s << "self." << field->GetName();
- }
- s << ", ";
- }
- if (ancestor->HasChildEnums()) {
- if (prev == nullptr) {
- if (ancestor->fields_.HasPayload()) {
- s << "child: match self.payload { ";
- s << "None => " << name_ << "DataChild::None,";
- s << "Some(bytes) => " << name_ << "DataChild::Payload(bytes),";
- s << "},";
- } else {
- s << "child: " << name_ << "DataChild::None,";
- }
- } else {
- s << "child: " << ancestor->name_ << "DataChild::" << prev->name_ << "("
- << util::CamelCaseToUnderScore(prev->name_) << "),";
- }
- }
- s << "});";
- prev = ancestor;
- }
-
- s << name_ << "Packet::new(" << util::CamelCaseToUnderScore(prev->name_) << ")";
- s << "}\n";
-
- s << "}\n";
- for (const auto ancestor : GetAncestors()) {
- s << "impl Into<" << ancestor->name_ << "Packet> for " << name_ << "Builder {";
- s << " fn into(self) -> " << ancestor->name_ << "Packet { self.build().into() }";
- s << "}\n";
- }
-}
-
-void PacketDef::GenRustBuilderTest(std::ostream& s) const {
- auto lineage = GetAncestors();
- lineage.push_back(this);
- if (!lineage.empty() && !test_cases_.empty()) {
- s << "macro_rules! " << util::CamelCaseToUnderScore(name_) << "_builder_tests { ";
- s << "($($name:ident: $byte_string:expr,)*) => {";
- s << "$(";
- s << "\n#[test]\n";
- s << "pub fn $name() { ";
- s << "let raw_bytes = $byte_string;";
- for (size_t i = 0; i < lineage.size(); i++) {
- s << "/* (" << i << ") */\n";
- if (i == 0) {
- s << "match " << lineage[i]->name_ << "Packet::parse(raw_bytes) {";
- s << "Ok(" << util::CamelCaseToUnderScore(lineage[i]->name_) << "_packet) => {";
- s << "match " << util::CamelCaseToUnderScore(lineage[i]->name_) << "_packet.specialize() {";
- } else if (i != lineage.size() - 1) {
- s << lineage[i - 1]->name_ << "Child::" << lineage[i]->name_ << "(";
- s << util::CamelCaseToUnderScore(lineage[i]->name_) << "_packet) => {";
- s << "match " << util::CamelCaseToUnderScore(lineage[i]->name_) << "_packet.specialize() {";
- } else {
- s << lineage[i - 1]->name_ << "Child::" << lineage[i]->name_ << "(packet) => {";
- s << "let rebuilder = " << lineage[i]->name_ << "Builder {";
- FieldList params = GetParamList();
- if (params.HasBody()) {
- ERROR() << "Packets with body fields can't be auto-tested. Test a child.";
- }
- for (const auto param : params) {
- s << param->GetName() << " : packet.";
- if (param->GetFieldType() == VectorField::kFieldType) {
- s << util::CamelCaseToUnderScore(param->GetGetterFunctionName()) << "().to_vec(),";
- } else if (param->GetFieldType() == ArrayField::kFieldType) {
- const auto array_param = static_cast<const ArrayField*>(param);
- const auto element_field = array_param->GetElementField();
- if (element_field->GetFieldType() == StructField::kFieldType) {
- s << util::CamelCaseToUnderScore(param->GetGetterFunctionName()) << "().to_vec(),";
- } else {
- s << util::CamelCaseToUnderScore(param->GetGetterFunctionName()) << "().clone(),";
- }
- } else if (param->GetFieldType() == StructField::kFieldType) {
- s << util::CamelCaseToUnderScore(param->GetGetterFunctionName()) << "().clone(),";
- } else {
- s << util::CamelCaseToUnderScore(param->GetGetterFunctionName()) << "(),";
- }
- }
- s << "};";
- s << "let rebuilder_base : " << lineage[0]->name_ << "Packet = rebuilder.into();";
- s << "let rebuilder_bytes : &[u8] = &rebuilder_base.to_bytes();";
- s << "assert_eq!(rebuilder_bytes, raw_bytes);";
- s << "}";
- }
- }
- for (size_t i = 1; i < lineage.size(); i++) {
- s << "_ => {";
- s << "println!(\"Couldn't parse " << util::CamelCaseToUnderScore(lineage[lineage.size() - i]->name_);
- s << "{:02x?}\", " << util::CamelCaseToUnderScore(lineage[lineage.size() - i - 1]->name_) << "_packet); ";
- s << "}}}";
- }
-
- s << ",";
- s << "Err(e) => panic!(\"could not parse " << lineage[0]->name_ << ": {:?} {:02x?}\", e, raw_bytes),";
- s << "}";
- s << "}";
- s << ")*";
- s << "}";
- s << "}";
-
- s << util::CamelCaseToUnderScore(name_) << "_builder_tests! { ";
- int number = 0;
- for (const auto& test_case : test_cases_) {
- s << util::CamelCaseToUnderScore(name_) << "_builder_test_";
- s << std::setfill('0') << std::setw(2) << number++ << ": ";
- s << "b\"" << test_case << "\",";
- }
- s << "}";
- s << "\n";
- }
-}
-
-void PacketDef::GenRustDef(std::ostream& s) const {
- GenRustChildEnums(s);
- GenRustStructDeclarations(s);
- GenRustStructImpls(s);
- GenRustAccessStructImpls(s);
- GenRustBuilderStructImpls(s);
- GenRustBuilderTest(s);
-}
diff --git a/gd/packet/parser/packet_def.h b/gd/packet/parser/packet_def.h
index d20cdc9e5..e8acdc306 100644
--- a/gd/packet/parser/packet_def.h
+++ b/gd/packet/parser/packet_def.h
@@ -33,16 +33,12 @@ class PacketDef : public ParentDef {
void GenParserDefinition(std::ostream& s) const;
- void GenTestingParserFromBytes(std::ostream& s) const;
-
void GenParserDefinitionPybind11(std::ostream& s) const;
void GenParserFieldGetter(std::ostream& s, const PacketField* field) const;
void GenValidator(std::ostream& s) const;
- void GenParserToString(std::ostream& s) const;
-
TypeDef::Type GetDefinitionType() const;
void GenBuilderDefinition(std::ostream& s) const;
@@ -62,24 +58,4 @@ class PacketDef : public ParentDef {
void GenBuilderParameterChecker(std::ostream& s) const;
void GenBuilderConstructor(std::ostream& s) const;
-
- void GenTestingFromView(std::ostream& s) const;
-
- void GenRustChildEnums(std::ostream& s) const;
-
- void GenRustStructDeclarations(std::ostream& s) const;
-
- bool GenRustStructFieldNameAndType(std::ostream& s) const;
-
- void GenRustStructFieldNames(std::ostream& s) const;
-
- void GenRustStructImpls(std::ostream& s) const;
-
- void GenRustAccessStructImpls(std::ostream& s) const;
-
- void GenRustBuilderStructImpls(std::ostream& s) const;
-
- void GenRustBuilderTest(std::ostream& s) const;
-
- void GenRustDef(std::ostream& s) const;
};
diff --git a/gd/packet/parser/packetgen.gni b/gd/packet/parser/packetgen.gni
deleted file mode 100644
index 5156a4d98..000000000
--- a/gd/packet/parser/packetgen.gni
+++ /dev/null
@@ -1,194 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-# Generate pybind11 source files + headers
-#
-# Parameters:
-# include: Base include path (i.e. bt/gd)
-# source_root: Root of source relative to current BUILD.gn
-# sources: PDL files to use for generation.
-# shards [optional]: Shard generated source into N files.
-# Default = 0. Max = 10.
-template("packetgen_py") {
- action_name = "${target_name}_gen"
-
- all_dependent_config_name = "_${target_name}_all_dependent_config"
- config(all_dependent_config_name) {
- include_dirs = [ "${root_gen_dir}" ]
- }
-
- action(action_name) {
- forward_variables_from(invoker, [ "sources", "include", "shards", "source_root" ])
- assert(defined(sources), "sources must be set")
- assert(defined(include), "include must be set")
- assert(defined(source_root), "source root must be set")
-
- outdir = rebase_path(root_gen_dir)
- source_root = rebase_path(source_root)
-
- # Set shards cmd
- shards_cmd = ""
- outputs = []
- source_args = []
- if (defined(shards)) {
- shards_list = ["0", "1", "2", "3", "4", "5", "6", "7", "8", "9"]
- foreach (source, sources) {
- rel_source = rebase_path(source, ".")
- source_args += [ rebase_path(source, source_root) ]
- shards_cmd = "--num_shards=${shards}"
-
- # TODO - GN reference doesn't explain how to programatically create
- # a range (i.e. range(shards)) so we use a fixed list and foreach loop to
- # work around it.
- assert(shards <= 10, "Maximum supported shards is 10.")
- index = 0
- outputs += [ string_replace("${outdir}/${rel_source}_python3.cc", ".pdl", "") ]
- foreach(num, shards_list) {
- if (index < shards) {
- outputs += [ string_replace("${outdir}/${rel_source}_python3_shard_${num}.cc", ".pdl", "") ]
- }
-
- index = index + 1
- }
- }
- }
-
- script = "//common-mk/file_generator_wrapper.py"
- binfile = "${root_out_dir}/bluetooth_packetgen"
- args = [
- binfile,
- "--include=${include}",
- "--out=${outdir}",
- "--source_root=${source_root}",
- shards_cmd,
- ] + source_args
- }
-
- # TODO: Make building with python-dev work.
- # source_set(target_name) {
- # sources = get_target_outputs(":${action_name}")
- # deps = [":${action_name}"]
- # all_dependent_configs = [":${all_dependent_config_name}"]
- # if (defined(invoker.all_dependent_configs)) {
- # all_dependent_configs += invoker.all_dependent_configs
- # }
- # if (defined(invoker.configs)) {
- # configs += invoker.configs
- # }
- # }
-}
-
-# Generate single c++ headers for each pdl
-#
-# Parameters:
-# include: Base include path (i.e. bt/gd)
-# source_root: Root of source relative to current BUILD.gn
-# sources: PDL files to use for generation.
-template("packetgen_headers") {
- all_dependent_config_name = "_${target_name}_all_dependent_config"
- config(all_dependent_config_name) {
- include_dirs = [ "${root_gen_dir}" ]
- }
-
- action(target_name) {
- forward_variables_from(invoker, [ "include", "sources", "source_root" ])
- assert(defined(sources), "sources must be set")
- assert(defined(include), "include must be set")
- assert(defined(source_root), "source root must be set")
-
- outdir = rebase_path(root_gen_dir)
- source_root = rebase_path(source_root)
-
- script = "//common-mk/file_generator_wrapper.py"
- binfile = "${root_out_dir}/bluetooth_packetgen"
- args = [
- binfile,
- "--include=${include}",
- "--out=${outdir}",
- "--source_root=${source_root}",
- ]
-
- outputs = []
- foreach (source, sources) {
- rel_source = rebase_path(source, ".")
- args += [ rebase_path(source, source_root) ]
- outputs += [ string_replace("${outdir}/${rel_source}.h", ".pdl", "") ]
- }
-
- all_dependent_configs = [ ":${all_dependent_config_name}" ]
- if (defined(invoker.all_dependent_configs)) {
- all_dependent_configs += invoker.all_dependent_configs
- }
-
- if (defined(invoker.configs)) {
- configs += invoker.configs
- }
- }
-}
-
-# Generate single Rust files for each pdl
-#
-# Parameters:
-# include: Base include path (i.e. bt/gd)
-# source_root: Root of source relative to current BUILD.gn
-# sources: PDL files to use for generation.
-template("packetgen_rust") {
- action_name = "${target_name}_gen"
- all_dependent_config_name = "_${target_name}_all_dependent_config"
- config(all_dependent_config_name) {
- include_dirs = [ "${root_gen_dir}" ]
- }
-
- action(action_name) {
- forward_variables_from(invoker, [ "include", "sources", "source_root" ])
- assert(defined(sources), "sources must be set")
- assert(defined(include), "include must be set")
- assert(defined(source_root), "source root must be set")
-
- outdir = rebase_path(root_gen_dir)
- source_root = rebase_path(source_root)
-
- script = "//common-mk/file_generator_wrapper.py"
- binfile = "${root_out_dir}/bluetooth_packetgen"
- args = [
- binfile,
- "--include=${include}",
- "--out=${outdir}",
- "--source_root=${source_root}",
- "--rust",
- ]
-
- outputs = []
- foreach (source, sources) {
- rel_source = rebase_path(source, ".")
- args += [ rebase_path(source, source_root) ]
- outputs += [ string_replace("${outdir}/${rel_source}.rs", ".pdl", "") ]
- }
- }
-
- # TODO: Rust source_set is not supported by gn.
- # source_set(target_name) {
- # sources = get_target_outputs(":${action_name}")
- # deps = [ ":${action_name}" ]
- # all_dependent_configs = [":${all_dependent_config_name}"]
- # if (defined(invoker.all_dependent_configs)) {
- # all_dependent_configs += invoker.all_dependent_configs
- # }
- # if (defined(invoker.configs)) {
- # configs += invoker.configs
- # }
- # }
-}
diff --git a/gd/packet/parser/parent_def.cc b/gd/packet/parser/parent_def.cc
index e4b7353cb..1557bf6b0 100644
--- a/gd/packet/parser/parent_def.cc
+++ b/gd/packet/parser/parent_def.cc
@@ -55,10 +55,6 @@ void ParentDef::AddParentConstraint(std::string field_name, std::variant<int64_t
parent_constraints_.insert(std::pair(field_name, value));
}
-void ParentDef::AddTestCase(std::string packet_bytes) {
- test_cases_.insert(std::move(packet_bytes));
-}
-
// Assign all size fields to their corresponding variable length fields.
// Will crash if
// - there aren't any fields that don't match up to a field.
@@ -94,12 +90,6 @@ void ParentDef::AssignSizeFields() {
continue;
}
- if (var_len_field->GetFieldType() == BodyField::kFieldType) {
- const auto& body_field = static_cast<BodyField*>(var_len_field);
- body_field->SetSizeField(size_field);
- continue;
- }
-
if (var_len_field->GetFieldType() == VectorField::kFieldType) {
const auto& vector_field = static_cast<VectorField*>(var_len_field);
vector_field->SetSizeField(size_field);
@@ -172,17 +162,6 @@ Size ParentDef::GetOffsetForField(std::string field_name, bool from_end) const {
ERROR() << "Can't find a field offset for nonexistent field named: " << field_name << " in " << name_;
}
- PacketField* padded_field = nullptr;
- {
- PacketField* last_field = nullptr;
- for (const auto field : fields_) {
- if (field->GetFieldType() == PaddingField::kFieldType) {
- padded_field = last_field;
- }
- last_field = field;
- }
- }
-
// We have to use a generic lambda to conditionally change iteration direction
// due to iterator and reverse_iterator being different types.
auto size_lambda = [&](auto from, auto to) -> Size {
@@ -192,13 +171,11 @@ Size ParentDef::GetOffsetForField(std::string field_name, bool from_end) const {
if ((*it)->GetName() == field_name) break;
const auto& field = *it;
// If there is a field with an unknown size before the field, return an empty Size.
- if (field->GetSize().empty() && padded_field != field) {
+ if (field->GetSize().empty()) {
return Size();
}
- if (field != padded_field) {
- if (!from_end || field->GetFieldType() != PaddingField::kFieldType) {
- size += field->GetSize();
- }
+ if (field->GetFieldType() != PaddingField::kFieldType || !from_end) {
+ size += field->GetSize();
}
}
return size;
@@ -262,9 +239,9 @@ FieldList ParentDef::GetParamList() const {
void ParentDef::GenMembers(std::ostream& s) const {
// Add the parameter list.
- for (const auto& field : fields_) {
- if (field->GenBuilderMember(s)) {
- s << "_{};";
+ for (int i = 0; i < fields_.size(); i++) {
+ if (fields_[i]->GenBuilderMember(s)) {
+ s << "_;";
}
}
}
@@ -273,20 +250,6 @@ void ParentDef::GenSize(std::ostream& s) const {
auto header_fields = fields_.GetFieldsBeforePayloadOrBody();
auto footer_fields = fields_.GetFieldsAfterPayloadOrBody();
- Size padded_size;
- const PacketField* padded_field = nullptr;
- const PacketField* last_field = nullptr;
- for (const auto& field : fields_) {
- if (field->GetFieldType() == PaddingField::kFieldType) {
- if (!padded_size.empty()) {
- ERROR() << "Only one padding field is allowed. Second field: " << field->GetName();
- }
- padded_field = last_field;
- padded_size = field->GetSize();
- }
- last_field = field;
- }
-
s << "protected:";
s << "size_t BitsOfHeader() const {";
s << "return 0";
@@ -300,11 +263,7 @@ void ParentDef::GenSize(std::ostream& s) const {
}
for (const auto& field : header_fields) {
- if (field == padded_field) {
- s << " + " << padded_size;
- } else {
- s << " + " << field->GetBuilderSize();
- }
+ s << " + " << field->GetBuilderSize();
}
s << ";";
@@ -313,11 +272,7 @@ void ParentDef::GenSize(std::ostream& s) const {
s << "size_t BitsOfFooter() const {";
s << "return 0";
for (const auto& field : footer_fields) {
- if (field == padded_field) {
- s << " + " << padded_size;
- } else {
- s << " + " << field->GetBuilderSize();
- }
+ s << " + " << field->GetBuilderSize();
}
if (parent_ != nullptr) {
@@ -337,22 +292,26 @@ void ParentDef::GenSize(std::ostream& s) const {
s << ";}\n\n";
}
+ Size padded_size;
+ for (const auto& field : header_fields) {
+ if (field->GetFieldType() == PaddingField::kFieldType) {
+ if (!padded_size.empty()) {
+ ERROR() << "Only one padding field is allowed. Second field: " << field->GetName();
+ }
+ padded_size = field->GetSize();
+ }
+ }
+
s << "public:";
s << "virtual size_t size() const override {";
+ if (!padded_size.empty()) {
+ s << "return " << padded_size.bytes() << ";}";
+ s << "size_t unpadded_size() const {";
+ }
s << "return (BitsOfHeader() / 8)";
if (fields_.HasPayload()) {
s << "+ payload_->size()";
}
- if (fields_.HasBody()) {
- for (const auto& field : header_fields) {
- if (field->GetFieldType() == SizeField::kFieldType) {
- const auto& field_name = ((SizeField*)field)->GetSizedFieldName();
- if (field_name == "body") {
- s << "+ body_size_extracted_";
- }
- }
- }
- }
s << " + (BitsOfFooter() / 8);";
s << "}\n";
}
@@ -376,17 +335,6 @@ void ParentDef::GenSerialize(std::ostream& s) const {
}
}
- const PacketField* padded_field = nullptr;
- {
- PacketField* last_field = nullptr;
- for (const auto field : header_fields) {
- if (field->GetFieldType() == PaddingField::kFieldType) {
- padded_field = last_field;
- }
- last_field = field;
- }
- }
-
for (const auto& field : header_fields) {
if (field->GetFieldType() == SizeField::kFieldType) {
const auto& field_name = ((SizeField*)field)->GetSizedFieldName();
@@ -403,13 +351,6 @@ void ParentDef::GenSerialize(std::ostream& s) const {
}
s << "ASSERT(payload_bytes < (static_cast<size_t>(1) << " << field->GetSize().bits() << "));";
s << "insert(static_cast<" << field->GetDataType() << ">(payload_bytes), i," << field->GetSize().bits() << ");";
- } else if (sized_field->GetFieldType() == BodyField::kFieldType) {
- s << field->GetName() << "_extracted_ = 0;";
- s << "size_t local_size = " << name_ << "::size();";
-
- s << "ASSERT((size() - local_size) < (static_cast<size_t>(1) << " << field->GetSize().bits() << "));";
- s << "insert(static_cast<" << field->GetDataType() << ">(size() - local_size), i," << field->GetSize().bits()
- << ");";
} else {
if (sized_field->GetFieldType() != VectorField::kFieldType) {
ERROR(field) << __func__ << ": Unhandled sized field type for " << field_name;
@@ -447,17 +388,14 @@ void ParentDef::GenSerialize(std::ostream& s) const {
s << "[shared_checksum_ptr](uint8_t byte){ shared_checksum_ptr->AddByte(byte);},";
s << "[shared_checksum_ptr](){ return static_cast<uint64_t>(shared_checksum_ptr->GetChecksum());}));";
} else if (field->GetFieldType() == PaddingField::kFieldType) {
- s << "ASSERT(unpadded_size <= " << field->GetSize().bytes() << ");";
+ s << "ASSERT(unpadded_size() <= " << field->GetSize().bytes() << ");";
s << "size_t padding_bytes = ";
- s << field->GetSize().bytes() << " - unpadded_size;";
+ s << field->GetSize().bytes() << " - unpadded_size();";
s << "for (size_t padding = 0; padding < padding_bytes; padding++) {i.insert_byte(0);}";
} else if (field->GetFieldType() == CountField::kFieldType) {
const auto& vector_name = ((SizeField*)field)->GetSizedFieldName() + "_";
s << "insert(" << vector_name << ".size(), i, " << field->GetSize().bits() << ");";
} else {
- if (field == padded_field) {
- s << "size_t unpadded_size = (" << field->GetBuilderSize() << ") / 8;";
- }
field->GenInserter(s);
}
}
@@ -502,7 +440,8 @@ void ParentDef::GenInstanceOf(std::ostream& s) const {
});
// Check if constrained parent fields are set to their correct values.
- for (const auto& field : parent_params) {
+ for (int i = 0; i < parent_params.size(); i++) {
+ const auto& field = parent_params[i];
const auto& constraint = parent_constraints_.find(field->GetName());
if (constraint != parent_constraints_.end()) {
s << "if (parent." << field->GetName() << "_ != ";
@@ -520,220 +459,3 @@ void ParentDef::GenInstanceOf(std::ostream& s) const {
s << "return true;}";
}
}
-
-const ParentDef* ParentDef::GetRootDef() const {
- if (parent_ == nullptr) {
- return this;
- }
-
- return parent_->GetRootDef();
-}
-
-std::vector<const ParentDef*> ParentDef::GetAncestors() const {
- std::vector<const ParentDef*> res;
- auto parent = parent_;
- while (parent != nullptr) {
- res.push_back(parent);
- parent = parent->parent_;
- }
- std::reverse(res.begin(), res.end());
- return res;
-}
-
-std::map<std::string, std::variant<int64_t, std::string>> ParentDef::GetAllConstraints() const {
- std::map<std::string, std::variant<int64_t, std::string>> res;
- res.insert(parent_constraints_.begin(), parent_constraints_.end());
- for (auto parent : GetAncestors()) {
- res.insert(parent->parent_constraints_.begin(), parent->parent_constraints_.end());
- }
- return res;
-}
-
-bool ParentDef::HasAncestorNamed(std::string name) const {
- auto parent = parent_;
- while (parent != nullptr) {
- if (parent->name_ == name) {
- return true;
- }
- parent = parent->parent_;
- }
- return false;
-}
-
-std::string ParentDef::FindConstraintField() const {
- std::string res;
- for (const auto& child : children_) {
- if (!child->parent_constraints_.empty()) {
- return child->parent_constraints_.begin()->first;
- }
- res = child->FindConstraintField();
- }
- return res;
-}
-
-std::map<const ParentDef*, const std::variant<int64_t, std::string>>
- ParentDef::FindDescendantsWithConstraint(
- std::string constraint_name) const {
- std::map<const ParentDef*, const std::variant<int64_t, std::string>> res;
-
- for (auto const& child : children_) {
- auto constraint = child->parent_constraints_.find(constraint_name);
- if (constraint != child->parent_constraints_.end()) {
- res.insert(std::pair(child, constraint->second));
- }
- auto m = child->FindDescendantsWithConstraint(constraint_name);
- res.insert(m.begin(), m.end());
- }
- return res;
-}
-
-std::vector<const ParentDef*> ParentDef::FindPathToDescendant(std::string descendant) const {
- std::vector<const ParentDef*> res;
-
- for (auto const& child : children_) {
- auto v = child->FindPathToDescendant(descendant);
- if (v.size() > 0) {
- res.insert(res.begin(), v.begin(), v.end());
- res.push_back(child);
- }
- if (child->name_ == descendant) {
- res.push_back(child);
- return res;
- }
- }
- return res;
-}
-
-bool ParentDef::HasChildEnums() const {
- return !children_.empty() || fields_.HasPayload();
-}
-
-void ParentDef::GenRustConformanceCheck(std::ostream& s) const {
- auto fields = fields_.GetFieldsWithTypes({
- FixedScalarField::kFieldType,
- });
-
- for (auto const& field : fields) {
- auto start_offset = GetOffsetForField(field->GetName(), false);
- auto end_offset = GetOffsetForField(field->GetName(), true);
-
- auto f = (FixedScalarField*)field;
- f->GenRustGetter(s, start_offset, end_offset);
- s << "if " << f->GetName() << " != ";
- f->GenValue(s);
- s << " { return false; } ";
- }
-}
-
-void ParentDef::GenRustWriteToFields(std::ostream& s) const {
- auto fields = fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- PaddingField::kFieldType,
- ReservedField::kFieldType,
- });
-
- for (auto const& field : fields) {
- auto start_field_offset = GetOffsetForField(field->GetName(), false);
- auto end_field_offset = GetOffsetForField(field->GetName(), true);
-
- if (start_field_offset.empty() && end_field_offset.empty()) {
- ERROR(field) << "Field location for " << field->GetName() << " is ambiguous, "
- << "no method exists to determine field location from begin() or end().\n";
- }
-
- if (field->GetFieldType() == SizeField::kFieldType) {
- const auto& field_name = ((SizeField*)field)->GetSizedFieldName();
- const auto& sized_field = fields_.GetField(field_name);
- if (sized_field == nullptr) {
- ERROR(field) << __func__ << ": Can't find sized field named " << field_name;
- }
- if (sized_field->GetFieldType() == PayloadField::kFieldType) {
- std::string modifier = ((PayloadField*)sized_field)->size_modifier_;
- if (modifier != "") {
- ERROR(field) << __func__ << ": size modifiers not implemented yet for " << field_name;
- }
-
- s << "let " << field->GetName() << " = " << field->GetRustDataType()
- << "::try_from(self.child.get_total_size()).expect(\"payload size did not fit\");";
- } else if (sized_field->GetFieldType() == BodyField::kFieldType) {
- s << "let " << field->GetName() << " = " << field->GetRustDataType()
- << "::try_from(self.get_total_size() - self.get_size()).expect(\"payload size did not fit\");";
- } else if (sized_field->GetFieldType() == VectorField::kFieldType) {
- const auto& vector_name = field_name + "_bytes";
- const VectorField* vector = (VectorField*)sized_field;
- if (vector->element_size_.empty() || vector->element_size_.has_dynamic()) {
- s << "let " << vector_name + " = self." << field_name
- << ".iter().fold(0, |acc, x| acc + x.get_total_size());";
- } else {
- s << "let " << vector_name + " = self." << field_name << ".len() * ((" << vector->element_size_ << ") / 8);";
- }
- std::string modifier = vector->GetSizeModifier();
- if (modifier != "") {
- s << "let " << vector_name << " = " << vector_name << " + (" << modifier.substr(1) << ") / 8;";
- }
-
- s << "let " << field->GetName() << " = " << field->GetRustDataType() << "::try_from(" << vector_name
- << ").expect(\"payload size did not fit\");";
- } else {
- ERROR(field) << __func__ << ": Unhandled sized field type for " << field_name;
- }
- }
-
- field->GenRustWriter(s, start_field_offset, end_field_offset);
- }
-}
-
-void ParentDef::GenSizeRetVal(std::ostream& s) const {
- int size = 0;
- auto fields = fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- });
- const PacketField* padded_field = nullptr;
- auto padding_fields = fields_.GetFieldsWithTypes({
- PaddingField::kFieldType,
- });
- if (padding_fields.size()) {
- PacketField* last_field = nullptr;
- for (const auto field : fields) {
- if (field->GetFieldType() == PaddingField::kFieldType) {
- padded_field = last_field;
- }
- last_field = field;
- }
- }
-
- s << "let ret = 0;";
- for (const auto field : fields) {
- bool is_vector = field->GetFieldType() == VectorField::kFieldType;
- if (field != padded_field) { // Skip the size of padded fields
- if (is_vector) {
- if (size > 0) {
- if (size % 8 != 0) {
- ERROR() << "size is not a multiple of 8!\n";
- }
- s << "let ret = ret + " << size / 8 << ";";
- size = 0;
- }
-
- const VectorField* vector = (VectorField*)field;
- if (vector->element_size_.empty() || vector->element_size_.has_dynamic()) {
- s << "let ret = ret + self." << vector->GetName() << ".iter().fold(0, |acc, x| acc + x.get_total_size());";
- } else {
- s << "let ret = ret + (self." << vector->GetName() << ".len() * ((" << vector->element_size_ << ") / 8));";
- }
- } else {
- size += field->GetSize().bits();
- }
- } else {
- s << "/* Skipping " << field->GetName() << " since it is padded */";
- }
- }
- if (size > 0) {
- if (size % 8 != 0) {
- ERROR() << "size is not a multiple of 8!\n";
- }
- s << "let ret = ret + " << size / 8 << ";";
- }
-
- s << "ret";
-}
diff --git a/gd/packet/parser/parent_def.h b/gd/packet/parser/parent_def.h
index 851b7ff85..a293a262f 100644
--- a/gd/packet/parser/parent_def.h
+++ b/gd/packet/parser/parent_def.h
@@ -17,7 +17,6 @@
#pragma once
#include <map>
-#include <set>
#include <variant>
#include "enum_def.h"
@@ -34,8 +33,6 @@ class ParentDef : public TypeDef {
void AddParentConstraint(std::string field_name, std::variant<int64_t, std::string> value);
- void AddTestCase(std::string packet_bytes);
-
// Assign all size fields to their corresponding variable length fields.
// Will crash if
// - there aren't any fields that don't match up to a field.
@@ -64,37 +61,10 @@ class ParentDef : public TypeDef {
void GenInstanceOf(std::ostream& s) const;
- const ParentDef* GetRootDef() const;
-
- bool HasAncestorNamed(std::string name) const;
-
- std::map<std::string, std::variant<int64_t, std::string>> GetAllConstraints() const;
-
- std::vector<const ParentDef*> GetAncestors() const;
-
- std::string FindConstraintField() const;
-
- std::map<const ParentDef*, const std::variant<int64_t, std::string>>
- FindDescendantsWithConstraint(std::string constraint_name) const;
- std::vector<const ParentDef*> FindPathToDescendant(std::string descendant) const;
-
FieldList fields_;
ParentDef* parent_{nullptr};
- ParentDef* complement_{nullptr};
-
- std::vector<ParentDef*> children_;
-
- std::set<std::string> test_cases_;
std::map<std::string, std::variant<int64_t, std::string>> parent_constraints_;
bool is_little_endian_;
-
- bool HasChildEnums() const;
-
- void GenRustWriteToFields(std::ostream& s) const;
-
- void GenSizeRetVal(std::ostream& s) const;
-
- void GenRustConformanceCheck(std::ostream& s) const;
};
diff --git a/gd/packet/parser/struct_def.cc b/gd/packet/parser/struct_def.cc
index d602e25e9..ff9cb78d7 100644
--- a/gd/packet/parser/struct_def.cc
+++ b/gd/packet/parser/struct_def.cc
@@ -45,37 +45,6 @@ void StructDef::GenSpecialize(std::ostream& s) const {
s << "}";
}
-void StructDef::GenToString(std::ostream& s) const {
- s << "std::string ToString() {";
- s << "std::stringstream ss;";
- s << "ss << std::hex << std::showbase << \"" << name_ << " { \";";
-
- if (fields_.size() > 0) {
- s << "ss";
- bool firstfield = true;
- for (const auto& field : fields_) {
- if (field->GetFieldType() == ReservedField::kFieldType ||
- field->GetFieldType() == ChecksumStartField::kFieldType ||
- field->GetFieldType() == FixedScalarField::kFieldType || field->GetFieldType() == CountField::kFieldType ||
- field->GetFieldType() == SizeField::kFieldType)
- continue;
-
- s << (firstfield ? " << \"" : " << \", ") << field->GetName() << " = \" << ";
-
- field->GenStringRepresentation(s, field->GetName() + "_");
-
- if (firstfield) {
- firstfield = false;
- }
- }
- s << ";";
- }
-
- s << "ss << \" }\";";
- s << "return ss.str();";
- s << "}\n";
-}
-
void StructDef::GenParse(std::ostream& s) const {
std::string iterator = (is_little_endian_ ? "Iterator<kLittleEndian>" : "Iterator<!kLittleEndian>");
@@ -112,14 +81,18 @@ void StructDef::GenParse(std::ostream& s) const {
if (!fields_.HasBody()) {
s << "size_t end_index = struct_begin_it.NumBytesRemaining();";
- s << "if (end_index < " << GetSize().bytes() << ")";
+ if (parent_ != nullptr) {
+ s << "if (end_index < " << GetSize().bytes() << " - to_fill->" << parent_->name_ << "::size())";
+ } else {
+ s << "if (end_index < " << GetSize().bytes() << ")";
+ }
s << "{ return struct_begin_it.Subrange(0,0);}";
}
Size total_bits{0};
for (const auto& field : fields_) {
if (field->GetFieldType() != ReservedField::kFieldType && field->GetFieldType() != BodyField::kFieldType &&
- field->GetFieldType() != FixedScalarField::kFieldType &&
+ field->GetFieldType() != FixedScalarField::kFieldType && field->GetFieldType() != SizeField::kFieldType &&
field->GetFieldType() != ChecksumStartField::kFieldType && field->GetFieldType() != ChecksumField::kFieldType &&
field->GetFieldType() != CountField::kFieldType) {
total_bits += field->GetSize().bits();
@@ -146,15 +119,22 @@ void StructDef::GenParse(std::ostream& s) const {
s << "}";
}
if (field->GetFieldType() == CountField::kFieldType || field->GetFieldType() == SizeField::kFieldType) {
+ s << field->GetDataType() << " " << field->GetName() << "_extracted;";
s << "{";
+ s << "if (to_bound.NumBytesRemaining() < " << field->GetSize().bytes() << ")";
+ if (!fields_.HasBody()) {
+ s << "{ return to_bound.Subrange(to_bound.NumBytesRemaining(),0);}";
+ } else {
+ s << "{ return {};}";
+ }
int num_leading_bits =
field->GenBounds(s, GetStructOffsetForField(field->GetName()), Size(), field->GetStructSize());
- s << "auto " << field->GetName() << "_ptr = &to_fill->" << field->GetName() << "_extracted_;";
+ s << "auto " << field->GetName() << "_ptr = &" << field->GetName() << "_extracted;";
field->GenExtractor(s, num_leading_bits, true);
s << "}";
}
}
- s << "return struct_begin_it + to_fill->size();";
+ s << "return struct_begin_it + to_fill->" << name_ << "::size();";
s << "}";
}
@@ -185,7 +165,7 @@ void StructDef::GenDefinition(std::ostream& s) const {
GenConstructor(s);
s << " public:\n";
- s << " virtual ~" << name_ << "() = default;\n";
+ s << " virtual ~" << name_ << "() override = default;\n";
GenSerialize(s);
s << "\n";
@@ -202,16 +182,7 @@ void StructDef::GenDefinition(std::ostream& s) const {
GenSpecialize(s);
s << "\n";
- GenToString(s);
- s << "\n";
-
GenMembers(s);
- for (const auto& field : fields_) {
- if (field->GetFieldType() == CountField::kFieldType || field->GetFieldType() == SizeField::kFieldType) {
- s << "\n private:\n";
- s << " mutable " << field->GetDataType() << " " << field->GetName() << "_extracted_{0};";
- }
- }
s << "};\n";
if (fields_.HasBody()) {
@@ -267,7 +238,8 @@ void StructDef::GenConstructor(std::ostream& s) const {
});
// Set constrained parent fields to their correct values.
- for (const auto& field : parent_params) {
+ for (int i = 0; i < parent_params.size(); i++) {
+ const auto& field = parent_params[i];
const auto& constraint = parent_constraints_.find(field->GetName());
if (constraint != parent_constraints_.end()) {
s << parent_->name_ << "::" << field->GetName() << "_ = ";
@@ -309,116 +281,3 @@ Size StructDef::GetStructOffsetForField(std::string field_name) const {
return size;
}
-
-void StructDef::GenRustFieldNameAndType(std::ostream& s, bool include_fixed) const {
- auto fields = fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- CountField::kFieldType,
- PaddingField::kFieldType,
- ReservedField::kFieldType,
- SizeField::kFieldType,
- });
- for (const auto& field : fields) {
- if (!include_fixed && field->GetFieldType() == FixedScalarField::kFieldType) {
- continue;
- }
- field->GenRustNameAndType(s);
- s << ", ";
- }
-}
-
-void StructDef::GenRustFieldNames(std::ostream& s) const {
- auto fields = fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- CountField::kFieldType,
- PaddingField::kFieldType,
- ReservedField::kFieldType,
- SizeField::kFieldType,
- });
- for (const auto& field : fields) {
- s << field->GetName();
- s << ", ";
- }
-}
-
-void StructDef::GenRustDeclarations(std::ostream& s) const {
- s << "#[derive(Debug, Clone)] ";
- s << "pub struct " << name_ << "{";
-
- // Generate struct fields
- auto fields = fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- CountField::kFieldType,
- PaddingField::kFieldType,
- ReservedField::kFieldType,
- SizeField::kFieldType,
- });
- for (const auto& field : fields) {
- s << "pub ";
- field->GenRustNameAndType(s);
- s << ", ";
- }
- s << "}\n";
-}
-
-void StructDef::GenRustImpls(std::ostream& s) const {
- s << "impl " << name_ << "{";
-
- s << "fn conforms(bytes: &[u8]) -> bool {";
- GenRustConformanceCheck(s);
- s << " true";
- s << "}";
-
- s << "pub fn parse(bytes: &[u8]) -> Result<Self> {";
- auto fields = fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- });
-
- for (const auto& field : fields) {
- auto start_field_offset = GetOffsetForField(field->GetName(), false);
- auto end_field_offset = GetOffsetForField(field->GetName(), true);
-
- if (start_field_offset.empty() && end_field_offset.empty()) {
- ERROR(field) << "Field location for " << field->GetName() << " is ambiguous, "
- << "no method exists to determine field location from begin() or end().\n";
- }
-
- field->GenBoundsCheck(s, start_field_offset, end_field_offset, name_);
- field->GenRustGetter(s, start_field_offset, end_field_offset);
- }
-
- fields = fields_.GetFieldsWithoutTypes({
- BodyField::kFieldType,
- CountField::kFieldType,
- PaddingField::kFieldType,
- ReservedField::kFieldType,
- SizeField::kFieldType,
- });
-
- s << "Ok(Self {";
- for (const auto& field : fields) {
- if (field->GetFieldType() == FixedScalarField::kFieldType) {
- s << field->GetName() << ": ";
- static_cast<FixedScalarField*>(field)->GenValue(s);
- } else {
- s << field->GetName();
- }
- s << ", ";
- }
- s << "})}\n";
-
- // write_to function
- s << "fn write_to(&self, buffer: &mut [u8]) {";
- GenRustWriteToFields(s);
- s << "}\n";
-
- s << "fn get_total_size(&self) -> usize {";
- GenSizeRetVal(s);
- s << "}";
- s << "}\n";
-}
-
-void StructDef::GenRustDef(std::ostream& s) const {
- GenRustDeclarations(s);
- GenRustImpls(s);
-}
diff --git a/gd/packet/parser/struct_def.h b/gd/packet/parser/struct_def.h
index 6008d2b16..74c1b040d 100644
--- a/gd/packet/parser/struct_def.h
+++ b/gd/packet/parser/struct_def.h
@@ -36,8 +36,6 @@ class StructDef : public ParentDef {
void GenSpecialize(std::ostream& s) const;
- void GenToString(std::ostream& s) const;
-
void GenParse(std::ostream& s) const;
void GenParseFunctionPrototype(std::ostream& s) const;
@@ -50,16 +48,6 @@ class StructDef : public ParentDef {
Size GetStructOffsetForField(std::string field_name) const;
- void GenRustDeclarations(std::ostream& s) const;
-
- void GenRustImpls(std::ostream& s) const;
-
- void GenRustFieldNameAndType(std::ostream& s, bool include_fixed) const;
-
- void GenRustFieldNames(std::ostream& s) const;
-
- void GenRustDef(std::ostream& s) const;
-
private:
Size total_size_;
};
diff --git a/gd/packet/parser/struct_parser_generator.cc b/gd/packet/parser/struct_parser_generator.cc
index 7caf6792d..352219eb5 100644
--- a/gd/packet/parser/struct_parser_generator.cc
+++ b/gd/packet/parser/struct_parser_generator.cc
@@ -20,7 +20,7 @@ StructParserGenerator::StructParserGenerator(const Declarations& decls) {
is_little_endian = decls.is_little_endian;
for (const auto& s : decls.type_defs_queue_) {
if (s.second->GetDefinitionType() == TypeDef::Type::STRUCT) {
- const auto* struct_def = static_cast<const StructDef*>(s.second);
+ const auto* struct_def = dynamic_cast<const StructDef*>(s.second);
variable_struct_fields_.emplace_back(struct_def);
}
}
@@ -80,7 +80,7 @@ void StructParserGenerator::Generate(std::ostream& s) const {
s << "std::make_unique<" << node.struct_def_->name_ << ">();";
s << "auto " << field->GetName() << "_it = to_bound;";
- s << "auto parent_optional_it = ";
+ s << "auto optional_it = ";
s << node.struct_def_->name_ << "::Parse( " << field->GetName() << "_value.get(), ";
s << field->GetName() << "_it";
if (node.struct_def_->parent_ != nullptr) {
@@ -88,8 +88,8 @@ void StructParserGenerator::Generate(std::ostream& s) const {
} else {
s << ");";
}
- s << "if (parent_optional_it) {";
- s << field->GetName() << "_it = *parent_optional_it;";
+ s << "if (optional_it) {";
+ s << field->GetName() << "_it = *optional_it;";
s << "} else { return nullptr; }";
explore_children(node, s);
diff --git a/gd/packet/parser/test/Android.bp b/gd/packet/parser/test/Android.bp
index f245a9392..65b2f3e21 100644
--- a/gd/packet/parser/test/Android.bp
+++ b/gd/packet/parser/test/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
genrule {
name: "BluetoothPacketParserTestPacketPdlGen_h",
tools: [
diff --git a/gd/packet/parser/test/generated_packet_test.cc b/gd/packet/parser/test/generated_packet_test.cc
index 4f1da4d24..4feb11ea8 100644
--- a/gd/packet/parser/test/generated_packet_test.cc
+++ b/gd/packet/parser/test/generated_packet_test.cc
@@ -131,10 +131,9 @@ TEST(GeneratedPacketTest, testValidateWayTooSmall) {
std::vector<uint8_t> too_small_bytes = {0x34};
auto too_small = std::make_shared<std::vector<uint8_t>>(too_small_bytes.begin(), too_small_bytes.end());
- ParentWithSixBytesView invalid_parent = ParentWithSixBytesView::Create(PacketView<kLittleEndian>(too_small));
+ ParentWithSixBytesView invalid_parent = ParentWithSixBytesView::Create(too_small);
ASSERT_FALSE(invalid_parent.IsValid());
- ChildWithSixBytesView invalid =
- ChildWithSixBytesView::Create(ParentWithSixBytesView::Create(PacketView<kLittleEndian>(too_small)));
+ ChildWithSixBytesView invalid = ChildWithSixBytesView::Create(ParentWithSixBytesView::Create(too_small));
ASSERT_FALSE(invalid.IsValid());
}
@@ -142,10 +141,9 @@ TEST(GeneratedPacketTest, testValidateTooSmall) {
std::vector<uint8_t> too_small_bytes = {0x34, 0x12, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x11};
auto too_small = std::make_shared<std::vector<uint8_t>>(too_small_bytes.begin(), too_small_bytes.end());
- ParentWithSixBytesView valid_parent = ParentWithSixBytesView::Create(PacketView<kLittleEndian>(too_small));
+ ParentWithSixBytesView valid_parent = ParentWithSixBytesView::Create(too_small);
ASSERT_TRUE(valid_parent.IsValid());
- ChildWithSixBytesView invalid =
- ChildWithSixBytesView::Create(ParentWithSixBytesView::Create(PacketView<kLittleEndian>(too_small)));
+ ChildWithSixBytesView invalid = ChildWithSixBytesView::Create(ParentWithSixBytesView::Create(too_small));
ASSERT_FALSE(invalid.IsValid());
}
@@ -154,8 +152,7 @@ TEST(GeneratedPacketTest, testValidateJustRight) {
0x06, 0x11, 0x12, 0x13, 0x14, 0x15, 0x16};
auto just_right = std::make_shared<std::vector<uint8_t>>(just_right_bytes.begin(), just_right_bytes.end());
- ChildWithSixBytesView valid =
- ChildWithSixBytesView::Create(ParentWithSixBytesView::Create(PacketView<kLittleEndian>(just_right)));
+ ChildWithSixBytesView valid = ChildWithSixBytesView::Create(ParentWithSixBytesView::Create(just_right));
ASSERT_TRUE(valid.IsValid());
}
@@ -164,8 +161,7 @@ TEST(GeneratedPacketTest, testValidateTooBig) {
0x11, 0x12, 0x13, 0x14, 0x15, 0x16, 0x20};
auto too_big = std::make_shared<std::vector<uint8_t>>(too_big_bytes.begin(), too_big_bytes.end());
- ChildWithSixBytesView lenient =
- ChildWithSixBytesView::Create(ParentWithSixBytesView::Create(PacketView<kLittleEndian>(too_big)));
+ ChildWithSixBytesView lenient = ChildWithSixBytesView::Create(ParentWithSixBytesView::Create(too_big));
ASSERT_TRUE(lenient.IsValid());
}
@@ -1764,29 +1760,29 @@ TEST(GeneratedPacketTest, testOneLengthTypeValueStruct) {
}
}
-vector<uint8_t> one_length_type_value_struct_padded_10{
- 0x20, // _size_(payload),
- 0x14, // valid bytes
- 0x04, 0x00, 0x01, 'o', 'n', 'e', // ONE
- 0x04, 0x00, 0x02, 't', 'w', 'o', // TWO
- 0x06, 0x00, 0x03, 't', 'h', 'r', 'e', 'e', // THREE
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // padding to 30
- 0x20, // after padding
+vector<uint8_t> one_length_type_value_struct_padded_20{
+ 0x27, // _size_(payload),
+ // _size_(value):16 type value
+ 0x04, 0x00, 0x01, 'o', 'n', 'e', // ONE
+ 0x04, 0x00, 0x02, 't', 'w', 'o', // TWO
+ 0x06, 0x00, 0x03, 't', 'h', 'r', 'e', 'e', // THREE
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // padding to 30
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // padding to 40
};
-vector<uint8_t> one_length_type_value_struct_padded_18{
- 0x20, // _size_(payload),
- 0x0C, // valid bytes
- 0x04, 0x00, 0x01, 'o', 'n', 'e', // ONE
- 0x04, 0x00, 0x02, 't', 'w', 'o', // TWO
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // padding to 20
+vector<uint8_t> one_length_type_value_struct_padded_28{
+ 0x27, // _size_(payload),
+ // _size_(value):16 type value
+ 0x04, 0x00, 0x01, 'o', 'n', 'e', // ONE
+ 0x04, 0x00, 0x02, 't', 'w', 'o', // TWO
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // padding to 20
0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // padding to 30
- 0x20, // after padding
+ 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, // padding to 40
};
// TODO: Revisit LTV parsing. Right now, the padding bytes are parsed
-// DEFINE_AND_INSTANTIATE_OneLengthTypeValueStructPaddedReflectionTest(one_length_type_value_struct_padded_10,
-// one_length_type_value_struct_padded_18);
+// DEFINE_AND_INSTANTIATE_OneLengthTypeValueStructPaddedReflectionTest(one_length_type_value_struct_padded_20,
+// one_length_type_value_struct_padded_28);
TEST(GeneratedPacketTest, testOneLengthTypeValueStructPaddedGeneration) {
std::vector<LengthTypeValueStruct> ltv_vector;
@@ -1805,18 +1801,17 @@ TEST(GeneratedPacketTest, testOneLengthTypeValueStructPaddedGeneration) {
'o',
};
ltv_vector.push_back(ltv);
- uint8_t after_padding = 0x20;
- auto packet = OneLengthTypeValueStructPaddedBuilder::Create(12, ltv_vector, after_padding);
- ASSERT_EQ(one_length_type_value_struct_padded_18.size(), packet->size());
+ auto packet = OneLengthTypeValueStructPaddedBuilder::Create(ltv_vector);
+ ASSERT_EQ(one_length_type_value_struct_padded_28.size(), packet->size());
std::shared_ptr<std::vector<uint8_t>> packet_bytes = std::make_shared<std::vector<uint8_t>>();
BitInserter it(*packet_bytes);
packet->Serialize(it);
- ASSERT_EQ(one_length_type_value_struct_padded_18.size(), packet_bytes->size());
- for (size_t i = 0; i < one_length_type_value_struct_padded_18.size(); i++) {
- ASSERT_EQ(one_length_type_value_struct_padded_18[i], packet_bytes->at(i));
+ ASSERT_EQ(one_length_type_value_struct_padded_28.size(), packet_bytes->size());
+ for (size_t i = 0; i < one_length_type_value_struct_padded_28.size(); i++) {
+ ASSERT_EQ(one_length_type_value_struct_padded_28[i], packet_bytes->at(i));
}
PacketView<kLittleEndian> packet_bytes_view(packet_bytes);
@@ -1824,12 +1819,11 @@ TEST(GeneratedPacketTest, testOneLengthTypeValueStructPaddedGeneration) {
ASSERT_TRUE(view.IsValid());
auto an_array = view.GetOneArray();
// TODO: Revisit LTV parsing. Right now, the padding bytes are parsed
- ASSERT_LE(ltv_vector.size(), an_array.size());
+ // ASSERT_EQ(ltv_vector.size(), an_array.size());
for (size_t i = 0; i < ltv_vector.size(); i++) {
ASSERT_EQ(ltv_vector[i].type_, an_array[i].type_);
ASSERT_EQ(ltv_vector[i].value_, an_array[i].value_);
}
- ASSERT_EQ(after_padding, view.GetAfterPadding());
}
vector<uint8_t> byte_sized{
@@ -1885,13 +1879,13 @@ DEFINE_AND_INSTANTIATE_ByteSizedFieldsReflectionTest(byte_sized);
TEST(GeneratedPacketTest, testOneGenericStructArrayNoZeroEmpty) {
auto too_few_bytes = std::make_shared<std::vector<uint8_t>>(0);
- auto view = OneGenericStructArrayNoZeroView::Create(PacketView<kLittleEndian>(too_few_bytes));
+ auto view = OneGenericStructArrayNoZeroView::Create(too_few_bytes);
for (size_t i = 0; i < 10; i++) {
if (view.IsValid()) {
view.GetAnArray().size();
}
too_few_bytes->push_back(0);
- view = OneGenericStructArrayNoZeroView::Create(PacketView<kLittleEndian>(too_few_bytes));
+ view = OneGenericStructArrayNoZeroView::Create(too_few_bytes);
}
std::vector<uint8_t> a_two_byte_struct = {
@@ -1900,73 +1894,11 @@ TEST(GeneratedPacketTest, testOneGenericStructArrayNoZeroEmpty) {
0x02,
};
too_few_bytes = std::make_shared<std::vector<uint8_t>>(a_two_byte_struct);
- view = OneGenericStructArrayNoZeroView::Create(PacketView<kLittleEndian>(too_few_bytes));
- ASSERT_TRUE(view.IsValid());
+ view = OneGenericStructArrayNoZeroView::Create(too_few_bytes);
+ ASSERT(view.IsValid());
ASSERT_EQ(1, view.GetAnArray().size());
}
-TEST(GeneratedPacketTest, testToStringOutput) {
- std::vector<TwoRelatedNumbersBe> count_array;
- for (uint8_t i = 1; i < 5; i++) {
- TwoRelatedNumbersBe trn;
- trn.id_ = i;
- trn.count_ = 0x0102 * i;
- count_array.push_back(trn);
- }
-
- auto packet = ArrayOfStructBeBuilder::Create(count_array);
-
- ASSERT_EQ(array_of_struct_be.size(), packet->size());
-
- std::shared_ptr<std::vector<uint8_t>> packet_bytes = std::make_shared<std::vector<uint8_t>>();
- BitInserter it(*packet_bytes);
- packet->Serialize(it);
-
- ASSERT_EQ(array_of_struct_be.size(), packet_bytes->size());
- for (size_t i = 0; i < array_of_struct_be.size(); i++) {
- ASSERT_EQ(array_of_struct_be[i], packet_bytes->at(i));
- }
-
- PacketView<!kLittleEndian> packet_bytes_view(packet_bytes);
- auto view = ArrayOfStructBeView::Create(packet_bytes_view);
- ASSERT_TRUE(view.IsValid());
-
- ASSERT_EQ(
- "ArrayOfStructBe { array_count = 0x4, array = VECTOR[TwoRelatedNumbersBe { id = 0x1, count = 0x102 }, "
- "TwoRelatedNumbersBe { id = 0x2, count = 0x204 }, TwoRelatedNumbersBe { id = 0x3, count = 0x306 }, "
- "TwoRelatedNumbersBe { id = 0x4, count = 0x408 }] }",
- view.ToString());
-}
-
-TEST(GeneratedPacketTest, testToStringOneFixedTypesStruct) {
- StructWithFixedTypes swf;
- swf.four_bits_ = FourBits::FIVE;
- swf.id_ = 0x0d;
- swf.array_ = {{0x01, 0x02, 0x03}};
- swf.six_bytes_ = SixBytes{{0xa1, 0xa2, 0xa3, 0xa4, 0xa5, 0xa6}};
-
- auto packet = OneFixedTypesStructBuilder::Create(swf);
- ASSERT_EQ(one_fixed_types_struct.size(), packet->size());
-
- std::shared_ptr<std::vector<uint8_t>> packet_bytes = std::make_shared<std::vector<uint8_t>>();
- BitInserter it(*packet_bytes);
- packet->Serialize(it);
-
- ASSERT_EQ(one_fixed_types_struct.size(), packet_bytes->size());
- for (size_t i = 0; i < one_fixed_types_struct.size(); i++) {
- ASSERT_EQ(one_fixed_types_struct[i], packet_bytes->at(i));
- }
-
- PacketView<kLittleEndian> packet_bytes_view(packet_bytes);
- auto view = OneFixedTypesStructView::Create(packet_bytes_view);
- ASSERT_TRUE(view.IsValid());
-
- ASSERT_EQ(
- "OneFixedTypesStruct { one = StructWithFixedTypes { four_bits = FIVE, id = 0xd, array = ARRAY[0x1, 0x2, 0x3], "
- "example_checksum = CHECKSUM, six_bytes = SixBytes } }",
- view.ToString());
-}
-
} // namespace parser
} // namespace packet
} // namespace bluetooth
diff --git a/gd/packet/parser/test/six_bytes.cc b/gd/packet/parser/test/six_bytes.cc
index e3b4b8118..614dbaadc 100644
--- a/gd/packet/parser/test/six_bytes.cc
+++ b/gd/packet/parser/test/six_bytes.cc
@@ -23,6 +23,8 @@ namespace packet {
namespace parser {
namespace test {
+static_assert(sizeof(SixBytes) == 6, "SixBytes must be 6 bytes long!");
+
SixBytes::SixBytes(const uint8_t (&six)[6]) {
std::copy(six, six + kLength, six_bytes);
};
diff --git a/gd/packet/parser/test/six_bytes.h b/gd/packet/parser/test/six_bytes.h
index 510ea757f..0f2632475 100644
--- a/gd/packet/parser/test/six_bytes.h
+++ b/gd/packet/parser/test/six_bytes.h
@@ -21,30 +21,20 @@
#include <stdint.h>
#include <string>
-#include "packet/custom_field_fixed_size_interface.h"
-
namespace bluetooth {
namespace packet {
namespace parser {
namespace test {
-class SixBytes final : public packet::CustomFieldFixedSizeInterface<SixBytes> {
+class SixBytes final {
public:
- static constexpr size_t kLength = 6;
+ static constexpr unsigned int kLength = 6;
- uint8_t six_bytes[kLength] = {};
+ uint8_t six_bytes[kLength];
SixBytes() = default;
SixBytes(const uint8_t (&addr)[6]);
- inline uint8_t* data() override {
- return six_bytes;
- }
-
- inline const uint8_t* data() const override {
- return six_bytes;
- }
-
bool operator<(const SixBytes& rhs) const {
return (std::memcmp(six_bytes, rhs.six_bytes, sizeof(six_bytes)) < 0);
}
@@ -63,9 +53,6 @@ class SixBytes final : public packet::CustomFieldFixedSizeInterface<SixBytes> {
bool operator!=(const SixBytes& rhs) const {
return !(*this == rhs);
}
- std::string ToString() const {
- return "SixBytes";
- }
};
} // namespace test
diff --git a/gd/packet/parser/test/test_packets.pdl b/gd/packet/parser/test/test_packets.pdl
index de6b70014..43355eeab 100644
--- a/gd/packet/parser/test/test_packets.pdl
+++ b/gd/packet/parser/test/test_packets.pdl
@@ -391,10 +391,8 @@ packet SizedParent {
}
packet OneLengthTypeValueStructPadded : SizedParent {
- valid_bytes : 8,
one_array : LengthTypeValueStruct[],
- _padding_[30],
- after_padding : 8,
+ _padding_[40],
}
packet ByteSizedFields {
diff --git a/gd/packet/parser/test/variable.h b/gd/packet/parser/test/variable.h
index 920c14fd1..c452a3795 100644
--- a/gd/packet/parser/test/variable.h
+++ b/gd/packet/parser/test/variable.h
@@ -62,10 +62,6 @@ class Variable final {
*instance = ss.str();
return it;
}
-
- std::string ToString() const {
- return data;
- }
};
} // namespace test
diff --git a/gd/packet/parser/util.h b/gd/packet/parser/util.h
index 342e1c5bd..a8b881d5a 100644
--- a/gd/packet/parser/util.h
+++ b/gd/packet/parser/util.h
@@ -103,31 +103,6 @@ inline std::string UnderscoreToCamelCase(std::string value) {
return camel_case.str();
}
-inline std::string ConstantCaseToCamelCase(std::string value) {
- if (value[0] < 'A' || value[0] > 'Z') {
- ERROR() << value << " doesn't look like CONSTANT_CASE";
- }
-
- std::ostringstream camel_case;
-
- bool capitalize = true;
- for (unsigned char c : value) {
- if (c == '_') {
- capitalize = true;
- } else {
- if (capitalize) {
- c = std::toupper(c);
- capitalize = false;
- } else {
- c = std::tolower(c);
- }
- camel_case << c;
- }
- }
-
- return camel_case.str();
-}
-
inline bool IsEnumCase(std::string value) {
if (value[0] < 'A' || value[0] > 'Z') {
return false;
@@ -159,33 +134,4 @@ inline std::string StringFindAndReplaceAll(std::string text, const std::string&
return text;
}
-inline std::string GetRustTypeForSize(int size) {
- if (size > 64) {
- ERROR() << __func__ << ": Cannot use a type larger than 64 bits. (" << size << ")\n";
- }
-
- if (size <= 8) return "u8";
-
- if (size <= 16) return "u16";
-
- if (size <= 32) return "u32";
-
- return "u64";
-}
-
-inline std::string ToLowerCase(std::string value) {
- if (value[0] < 'A' || value[0] > 'Z') {
- ERROR() << value << " doesn't look like CONSTANT_CASE";
- }
-
- std::ostringstream lower_case;
-
- for (unsigned char c : value) {
- c = std::tolower(c);
- lower_case << c;
- }
-
- return lower_case.str();
-}
-
} // namespace util
diff --git a/gd/packet/python3_module.cc b/gd/packet/python3_module.cc
index a5e770f1e..64ccb8272 100644
--- a/gd/packet/python3_module.cc
+++ b/gd/packet/python3_module.cc
@@ -29,7 +29,6 @@
#include "packet/packet_view.h"
#include "packet/parser/checksum_type_checker.h"
#include "packet/parser/custom_type_checker.h"
-#include "packet/raw_builder.h"
namespace py = pybind11;
@@ -58,23 +57,10 @@ using ::bluetooth::packet::kLittleEndian;
using ::bluetooth::packet::PacketBuilder;
using ::bluetooth::packet::PacketStruct;
using ::bluetooth::packet::PacketView;
-using ::bluetooth::packet::RawBuilder;
using ::bluetooth::packet::parser::ChecksumTypeChecker;
PYBIND11_MODULE(bluetooth_packets_python3, m) {
py::class_<BasePacketBuilder, std::shared_ptr<BasePacketBuilder>>(m, "BasePacketBuilder");
- py::class_<RawBuilder, BasePacketBuilder, std::shared_ptr<RawBuilder>>(m, "RawBuilder")
- .def(py::init([](std::vector<uint8_t> bytes) { return std::make_unique<RawBuilder>(bytes); }))
- .def(py::init([](std::string bytes) {
- return std::make_unique<RawBuilder>(std::vector<uint8_t>(bytes.begin(), bytes.end()));
- }))
- .def("Serialize", [](RawBuilder& builder) {
- std::vector<uint8_t> packet;
- BitInserter it(packet);
- builder.Serialize(it);
- std::string result = std::string(packet.begin(), packet.end());
- return py::bytes(result);
- });
py::class_<PacketBuilder<kLittleEndian>, BasePacketBuilder, std::shared_ptr<PacketBuilder<kLittleEndian>>>(
m, "PacketBuilderLittleEndian");
py::class_<PacketBuilder<!kLittleEndian>, BasePacketBuilder, std::shared_ptr<PacketBuilder<!kLittleEndian>>>(
@@ -86,19 +72,11 @@ PYBIND11_MODULE(bluetooth_packets_python3, m) {
m, "PacketStructBigEndian");
py::class_<Iterator<kLittleEndian>>(m, "IteratorLittleEndian");
py::class_<Iterator<!kLittleEndian>>(m, "IteratorBigEndian");
- py::class_<PacketView<kLittleEndian>>(m, "PacketViewLittleEndian")
- .def(py::init([](std::vector<uint8_t> bytes) {
- // Make a copy
- auto bytes_shared = std::make_shared<std::vector<uint8_t>>(bytes);
- return std::make_unique<PacketView<kLittleEndian>>(bytes_shared);
- }))
- .def("GetBytes", [](const PacketView<kLittleEndian> view) {
- std::string result;
- for (auto byte : view) {
- result += byte;
- }
- return py::bytes(result);
- });
+ py::class_<PacketView<kLittleEndian>>(m, "PacketViewLittleEndian").def(py::init([](std::vector<uint8_t> bytes) {
+ // Make a copy
+ auto bytes_shared = std::make_shared<std::vector<uint8_t>>(bytes);
+ return std::make_unique<PacketView<kLittleEndian>>(bytes_shared);
+ }));
py::class_<PacketView<!kLittleEndian>>(m, "PacketViewBigEndian").def(py::init([](std::vector<uint8_t> bytes) {
// Make a copy
auto bytes_shared = std::make_shared<std::vector<uint8_t>>(bytes);
diff --git a/gd/packet/raw_builder.h b/gd/packet/raw_builder.h
index 247bfed38..1c9552a82 100644
--- a/gd/packet/raw_builder.h
+++ b/gd/packet/raw_builder.h
@@ -29,8 +29,8 @@ namespace packet {
class RawBuilder : public PacketBuilder<true> {
public:
RawBuilder() = default;
- explicit RawBuilder(size_t max_bytes);
- explicit RawBuilder(std::vector<uint8_t> vec);
+ RawBuilder(size_t max_bytes);
+ RawBuilder(std::vector<uint8_t> vec);
virtual ~RawBuilder() = default;
virtual size_t size() const override;
diff --git a/gd/proto/Android.bp b/gd/proto/Android.bp
deleted file mode 100644
index a8c1244eb..000000000
--- a/gd/proto/Android.bp
+++ /dev/null
@@ -1,59 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-java_library_static {
- name: "bluetooth-protos-lite",
- host_supported: true,
- proto: {
- type: "lite",
- },
- srcs: [
- "bluetooth/metrics/bluetooth.proto",
- "bluetooth/bluetoothKeystore/keystore.proto",
- ],
- apex_available: [
- "//apex_available:platform",
- "com.android.bluetooth.updatable",
- ],
-}
-
-cc_library_static {
- name: "libbt-protos-lite",
- host_supported: true,
- proto: {
- export_proto_headers: true,
- type: "lite",
- },
- srcs: [
- "bluetooth/metrics/bluetooth.proto",
- "bluetooth/bluetoothKeystore/keystore.proto",
- ],
- apex_available: [
- "//apex_available:platform",
- "com.android.bluetooth.updatable",
- ],
-}
-
-cc_library_static {
- name: "libbluetooth-protos",
- host_supported: true,
- proto: {
- export_proto_headers: true,
- type: "lite",
- include_dirs: ["external/protobuf/src"],
- },
- srcs: [
- "bluetooth/metrics/bluetooth.proto",
- "bluetooth/bluetoothKeystore/keystore.proto",
- ],
- apex_available: [
- "//apex_available:platform",
- "com.android.bluetooth.updatable",
- ],
-}
diff --git a/gd/proto/BUILD.gn b/gd/proto/BUILD.gn
deleted file mode 100644
index ba5cd4eaa..000000000
--- a/gd/proto/BUILD.gn
+++ /dev/null
@@ -1,10 +0,0 @@
-import("//common-mk/proto_library.gni")
-
-proto_library("libbt-protos-lite") {
- sources = [
- "bluetooth/metrics/bluetooth.proto",
- ]
-
- proto_in_dir = "./bluetooth/metrics"
- proto_out_dir = "include/bluetooth/metrics"
-}
diff --git a/gd/rust/README.md b/gd/rust/README.md
deleted file mode 100644
index 0e9985cb2..000000000
--- a/gd/rust/README.md
+++ /dev/null
@@ -1,17 +0,0 @@
-Rust build
-======
-
-Currently, the Rust components are built differently on Android vs Linux. We are
-missing Rust support in our GN toolchain so we currently build the Rust
-libraries as a staticlib and link in C++. This may change in the future once we
-have better support.
-
-For now, you can build all of the Rust code using Cargo.
-
-There are some dependencies:
-* You must have the protobuf-compiler package installed
-* You must have a recent version of Cargo + Rust
-
-You should use `build.py` at the root to do your Rust builds so that it
-correctly points your dependencies towards the vendored crates and sets your
-$CARGO_HOME to the correct location.
diff --git a/gd/rust/common/Android.bp b/gd/rust/common/Android.bp
deleted file mode 100644
index d5b30f65d..000000000
--- a/gd/rust/common/Android.bp
+++ /dev/null
@@ -1,82 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-rust_library {
- name: "libbt_common",
- defaults: ["gd_rust_defaults"],
- crate_name: "bt_common",
- srcs: ["src/lib.rs"],
- edition: "2018",
- rustlibs: [
- "libtokio",
- "libnix",
- "liblazy_static",
- "liblog_rust",
- "libcxx",
- "libgrpcio",
- ],
- target: {
- android: {
- rustlibs: [
- "libandroid_logger",
- ],
- whole_static_libs: ["libbt_common_sys_prop_cxx"],
- shared_libs: [
- "libcutils",
- ],
- },
- host: {
- rustlibs: [
- "libenv_logger",
- ],
- },
- },
- proc_macros: [
- "libpaste",
- ],
-}
-
-rust_test_host {
- name: "libbt_common_inline_tests",
- srcs: ["src/lib.rs"],
- test_suites: ["general-tests"],
- auto_gen_config: true,
- rustlibs: [
- "libtokio",
- "libnix",
- "liblazy_static",
- "liblog_rust",
- "libenv_logger",
- "libcxx",
- "libgrpcio",
- ],
- proc_macros: [
- "libpaste",
- ],
-}
-
-genrule {
- name: "libbt_common_sys_prop_bridge_code",
- tools: ["cxxbridge"],
- cmd: "$(location cxxbridge) $(in) >> $(out)",
- srcs: ["src/sys_prop.rs"],
- out: ["sys_prop_generated.cc"],
-}
-
-cc_library_static {
- name: "libbt_common_sys_prop_cxx",
- defaults: ["gd_ffi_defaults"],
- local_include_dirs: ["src/ffi"],
- srcs: ["src/ffi/sys_prop.cc"],
- generated_headers: ["cxx-bridge-header"],
- generated_sources: ["libbt_common_sys_prop_bridge_code"],
- shared_libs: [
- "libcutils",
- ],
-}
diff --git a/gd/rust/common/BUILD.gn b/gd/rust/common/BUILD.gn
deleted file mode 100644
index 13ea11380..000000000
--- a/gd/rust/common/BUILD.gn
+++ /dev/null
@@ -1,43 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import("//common-mk/cxxbridge.gni")
-
-rust_library("libbt_common") {
- crate_name = "bt_common"
-
- sources = [ "src/lib.rs" ]
-
- configs = [
- "//bt/gd/rust/shim:rust_libs",
- "//bt/gd:rust_defaults",
- ]
-}
-
-cxxbridge_cc("libbt_common_sys_prop_bridge_code") {
- sources = [ "src/sys_prop.rs" ]
-
- configs = [ "//bt/gd:gd_defaults" ]
-}
-
-static_library("libbt_common_sys_prop_cxx") {
- sources = [ "src/ffi/sys_props.cc" ]
-
- include_dirs = [ "src/ffi" ]
-
- deps = [ ":libbt_common_sys_prop_bridge_code" ]
-
- configs += [ "//bt/gd:gd_defaults" ]
-}
diff --git a/gd/rust/common/Cargo.toml b/gd/rust/common/Cargo.toml
deleted file mode 100644
index 22de79a20..000000000
--- a/gd/rust/common/Cargo.toml
+++ /dev/null
@@ -1,34 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bt_common"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-cxx = "*"
-env_logger = "*"
-grpcio = "*"
-lazy_static = "*"
-log = "*"
-nix = "*"
-tokio = { version = "*", features = ['bytes', 'macros', 'net', 'rt-multi-thread', 'time'] }
-
-# Proc Macro dependency
-paste = "*"
-
-[lib]
-crate-type = ["rlib"]
diff --git a/gd/rust/common/src/asserts.rs b/gd/rust/common/src/asserts.rs
deleted file mode 100644
index bcbafce48..000000000
--- a/gd/rust/common/src/asserts.rs
+++ /dev/null
@@ -1,16 +0,0 @@
-/// Assertion check for X is is within Y of Z
-#[macro_export]
-macro_rules! assert_near {
- ($thing:expr, $expected:expr, $error:expr) => {
- match (&$thing, &$expected, &$error) {
- (thing_val, expected_val, error_val) => {
- if thing_val < &(expected_val - error_val) || thing_val > &(expected_val + error_val) {
- panic!(
- "assertion failed: {:?} is not within {:?} of {:?}",
- &*thing_val, &*error_val, &*expected_val
- )
- }
- }
- }
- };
-}
diff --git a/gd/rust/common/src/ffi/sys_prop.cc b/gd/rust/common/src/ffi/sys_prop.cc
deleted file mode 100644
index a3e1cf786..000000000
--- a/gd/rust/common/src/ffi/sys_prop.cc
+++ /dev/null
@@ -1,20 +0,0 @@
-#include "sys_prop.h"
-#include <cutils/properties.h>
-
-namespace bluetooth {
-namespace common {
-namespace sys_prop {
-
-rust::String get(rust::Str property) {
- auto name = std::string(property.data(), property.length());
- std::array<char, PROPERTY_VALUE_MAX> value_array{0};
- auto value_len = property_get(name.c_str(), value_array.data(), nullptr);
- if (value_len <= 0) {
- value_len = 0;
- }
- return rust::String(value_array.data(), value_len);
-}
-
-} // namespace sys_prop
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/rust/common/src/ffi/sys_prop.h b/gd/rust/common/src/ffi/sys_prop.h
deleted file mode 100644
index 80ac5591e..000000000
--- a/gd/rust/common/src/ffi/sys_prop.h
+++ /dev/null
@@ -1,12 +0,0 @@
-#include <string>
-#include "rust/cxx.h"
-
-namespace bluetooth {
-namespace common {
-namespace sys_prop {
-
-rust::String get(rust::Str property);
-
-}
-} // namespace common
-} // namespace bluetooth
diff --git a/gd/rust/common/src/init_flags.rs b/gd/rust/common/src/init_flags.rs
deleted file mode 100644
index 38d277d50..000000000
--- a/gd/rust/common/src/init_flags.rs
+++ /dev/null
@@ -1,114 +0,0 @@
-use log::{error, info};
-use paste::paste;
-use std::sync::Mutex;
-
-macro_rules! init_flags {
- (flags: { $($flag:ident),* }, dependencies: { $($parent:ident => $child:ident),* }) => {
- #[derive(Default)]
- struct InitFlags {
- $($flag: bool,)*
- }
-
- /// Sets all flags to true, for testing
- pub fn set_all_for_testing() {
- *FLAGS.lock().unwrap() = InitFlags { $($flag: true,)* };
- }
-
- impl InitFlags {
- fn parse(flags: Vec<String>) -> Self {
- $(let mut $flag = false;)*
-
- for flag in flags {
- let values: Vec<&str> = flag.split("=").collect();
- if values.len() != 2 {
- error!("Bad flag {}, must be in <FLAG>=<VALUE> format", flag);
- continue;
- }
-
- match values[0] {
- $(concat!("INIT_", stringify!($flag)) => $flag = values[1].parse().unwrap_or(false),)*
- _ => {}
- }
- }
-
- Self { $($flag,)* }.reconcile()
- }
-
- fn reconcile(mut self) -> Self {
- // Loop to ensure dependencies can be specified in any order
- loop {
- let mut any_change = false;
- $(if self.$parent && !self.$child {
- self.$child = true;
- any_change = true;
- })*
-
- if !any_change {
- break;
- }
- }
-
- // TODO: acl should not be off if l2cap is on, but need to reconcile legacy code
- if self.gd_l2cap {
- self.gd_acl = false;
- self.gd_hci = true;
- }
-
- self
- }
-
- fn log(&self) {
- info!(concat!("Flags loaded: ", $(stringify!($flag), "={} ",)*), $(self.$flag,)*);
- }
- }
-
- paste! {
- $(
- #[allow(missing_docs)]
- pub fn [<$flag _is_enabled>]() -> bool {
- FLAGS.lock().unwrap().$flag
- }
- )*
- }
- };
-}
-
-init_flags!(
- flags: {
- gd_core,
- gd_advertising,
- gd_scanning,
- gd_security,
- gd_acl,
- gd_l2cap,
- gd_hci,
- gd_controller,
- gatt_robust_caching,
- btaa_hci,
- gd_rust,
- gd_link_policy
- },
- dependencies: {
- gd_core => gd_security,
- gd_security => gd_acl,
- gd_l2cap => gd_scanning,
- gd_scanning => gd_advertising,
- gd_advertising => gd_acl,
- gd_acl => gd_controller,
- gd_controller => gd_hci,
- gd_link_policy => gd_acl
- }
-);
-
-lazy_static! {
- static ref FLAGS: Mutex<InitFlags> = Mutex::new(InitFlags::default());
-}
-
-/// Loads the flag values from the passed-in vector of string values
-pub fn load(flags: Vec<String>) {
- crate::init_logging();
-
- let flags = InitFlags::parse(flags);
- flags.log();
- *FLAGS.lock().unwrap() = flags;
-}
diff --git a/gd/rust/common/src/lib.rs b/gd/rust/common/src/lib.rs
deleted file mode 100644
index c07279bfb..000000000
--- a/gd/rust/common/src/lib.rs
+++ /dev/null
@@ -1,52 +0,0 @@
-//! Bluetooth common library
-#[macro_use]
-extern crate lazy_static;
-
-/// Provides waking timer abstractions
-pub mod time;
-
-#[macro_use]
-mod ready;
-
-#[cfg(test)]
-#[macro_use]
-mod asserts;
-
-/// Provides runtime configured-at-startup flags
-pub mod init_flags;
-
-/// Provides runtime configured system properties. Stubbed for non-Android.
-pub mod sys_prop;
-
-/// Inits logging for Android
-#[cfg(target_os = "android")]
-pub fn init_logging() {
- android_logger::init_once(
- android_logger::Config::default().with_tag("bt").with_min_level(log::Level::Debug),
- );
-}
-
-/// Inits logging for host
-#[cfg(not(target_os = "android"))]
-pub fn init_logging() {
- env_logger::Builder::new()
- .filter(None, log::LevelFilter::Debug)
- .parse_default_env()
- .try_init()
- .ok();
-}
-
-/// Indicates the object can be converted to a GRPC service
-pub trait GrpcFacade {
- /// Convert the object into the service
- fn into_grpc(self) -> grpcio::Service;
-}
-
-/// Useful for distinguishing between BT classic & LE in functions that support both
-#[derive(Debug, Clone, Copy)]
-pub enum Bluetooth {
- /// Classic BT we all know and love, started in the 90s.
- Classic,
- /// Bluetooth low energy from the 2010s. Also known as BLE, BTLE, etc.
- Le,
-}
diff --git a/gd/rust/common/src/ready.rs b/gd/rust/common/src/ready.rs
deleted file mode 100644
index 4e5cb4ceb..000000000
--- a/gd/rust/common/src/ready.rs
+++ /dev/null
@@ -1,10 +0,0 @@
-/// Simplifies polling futures
-#[macro_export]
-macro_rules! ready {
- ($e:expr $(,)?) => {
- match $e {
- std::task::Poll::Ready(t) => t,
- std::task::Poll::Pending => return std::task::Poll::Pending,
- }
- };
-}
diff --git a/gd/rust/common/src/sys_prop.rs b/gd/rust/common/src/sys_prop.rs
deleted file mode 100644
index 301311c9f..000000000
--- a/gd/rust/common/src/sys_prop.rs
+++ /dev/null
@@ -1,61 +0,0 @@
-//! System properties on Android
-
-#[cfg(target_os = "android")]
-mod wrap {
- #[cxx::bridge(namespace = bluetooth::common::sys_prop)]
- pub mod ffi {
- unsafe extern "C++" {
- include!("src/ffi/sys_prop.h");
- fn get(name: &str) -> String;
- }
- }
-}
-
-#[cfg(target_os = "android")]
-use wrap::ffi;
-
-/// Gets the value of a system property on Android
-#[cfg(target_os = "android")]
-pub fn get(name: &str) -> Option<String> {
- let value = ffi::get(name);
-
- if !value.is_empty() {
- Some(value)
- } else {
- None
- }
-}
-
-/// Fake getter for non-Android, which will always return nothing.
-/// Only added so it compiles & you can conditionally using cfg!
-#[cfg(not(target_os = "android"))]
-pub fn get(_name: &str) -> Option<String> {
- None
-}
-
-/// Gets the specified property as a u32
-pub fn get_u32(name: &str) -> Option<u32> {
- if let Some(value) = get(name) {
- value.parse().ok()
- } else {
- None
- }
-}
-
-/// Gets the specified property as a bool (logic follows libcutils/properties.cpp)
-pub fn get_bool(name: &str) -> Option<bool> {
- if let Some(value) = get(name) {
- match value.as_str() {
- "0" | "n" | "no" | "false" | "off" => Some(false),
- "1" | "y" | "yes" | "true" | "on" => Some(true),
- _ => None,
- }
- } else {
- None
- }
-}
-
-/// Gets whether the current build is debuggable
-pub fn get_debuggable() -> bool {
- get_bool("ro.debuggable").unwrap_or(false)
-}
diff --git a/gd/rust/common/src/time.rs b/gd/rust/common/src/time.rs
deleted file mode 100644
index 24ff435c4..000000000
--- a/gd/rust/common/src/time.rs
+++ /dev/null
@@ -1,144 +0,0 @@
-///! Waking timers for Bluetooth. Implemented using timerfd, but supposed to feel similar to
-///Tokio's time
-use nix::sys::time::TimeSpec;
-use nix::sys::timerfd::{ClockId, Expiration, TimerFd, TimerFlags, TimerSetTimeFlags};
-use std::time::Duration;
-use tokio::io::unix::AsyncFd;
-
-/// A single shot Alarm
-pub struct Alarm {
- fd: AsyncFd<TimerFd>,
-}
-
-impl Alarm {
- /// Construct a new alarm
- pub fn new() -> Self {
- let timer = TimerFd::new(get_clock(), TimerFlags::empty()).unwrap();
- Self { fd: AsyncFd::new(timer).unwrap() }
- }
-
- /// Reset the alarm to duration, starting from now
- pub fn reset(&mut self, duration: Duration) {
- self.fd
- .get_ref()
- .set(Expiration::OneShot(TimeSpec::from(duration)), TimerSetTimeFlags::empty())
- .unwrap();
- }
-
- /// Stop the alarm if it is currently started
- pub fn cancel(&mut self) {
- self.reset(Duration::from_millis(0));
- }
-
- /// Completes when the alarm has expired
- pub async fn expired(&mut self) {
- let mut read_ready = self.fd.readable().await.unwrap();
- read_ready.clear_ready();
- drop(read_ready);
- // Will not block, since we have confirmed it is readable
- self.fd.get_ref().wait().unwrap();
- }
-}
-
-impl Default for Alarm {
- fn default() -> Self {
- Alarm::new()
- }
-}
-
-/// Similar to tokio's interval, except the first tick does *not* complete immediately
-pub fn interval(period: Duration) -> Interval {
- let timer = TimerFd::new(get_clock(), TimerFlags::empty()).unwrap();
- timer.set(Expiration::Interval(TimeSpec::from(period)), TimerSetTimeFlags::empty()).unwrap();
-
- Interval { fd: AsyncFd::new(timer).unwrap() }
-}
-
-/// Future returned by interval()
-pub struct Interval {
- fd: AsyncFd<TimerFd>,
-}
-
-impl Interval {
- /// Call this to get the future for the next tick of the interval
- pub async fn tick(&mut self) {
- let mut read_ready = self.fd.readable().await.unwrap();
- read_ready.clear_ready();
- drop(read_ready);
- // Will not block, since we have confirmed it is readable
- self.fd.get_ref().wait().unwrap();
- }
-}
-
-fn get_clock() -> ClockId {
- if cfg!(target_os = "android") {
- ClockId::CLOCK_BOOTTIME_ALARM
- } else {
- ClockId::CLOCK_BOOTTIME
- }
-}
-
-#[cfg(test)]
-mod tests {
- use super::interval;
- use super::Alarm;
- use crate::assert_near;
- use std::time::{Duration, Instant};
-
- #[test]
- fn alarm_simple_case() {
- let runtime = tokio::runtime::Runtime::new().unwrap();
- runtime.block_on(async {
- let timer = Instant::now();
- let mut alarm = Alarm::new();
- alarm.reset(Duration::from_millis(10));
- alarm.expired().await;
-
- assert_near!(timer.elapsed().as_millis(), 10, 3);
- });
- }
-
- #[test]
- fn alarm_clear_ready_after_expired() {
- // After an alarm expired, we need to make sure we clear ready from AsyncFdReadyGuard.
- // Otherwise it's still ready and select! won't work.
- let runtime = tokio::runtime::Runtime::new().unwrap();
- runtime.block_on(async {
- let timer = Instant::now();
- let mut alarm = Alarm::new();
- alarm.reset(Duration::from_millis(10));
- alarm.expired().await;
- let ready_in_10_ms = async {
- tokio::time::sleep(Duration::from_millis(10)).await;
- };
- tokio::select! {
- _ = alarm.expired() => (),
- _ = ready_in_10_ms => (),
- }
- assert_near!(timer.elapsed().as_millis(), 20, 3);
- });
- }
-
- #[test]
- fn interval_schedule_and_then_drop() {
- let runtime = tokio::runtime::Runtime::new().unwrap();
- runtime.block_on(async {
- interval(Duration::from_millis(10));
- });
- }
-
- #[test]
- fn interval_simple_case() {
- let runtime = tokio::runtime::Runtime::new().unwrap();
- runtime.block_on(async {
- let timer = Instant::now();
- let mut interval = interval(Duration::from_millis(10));
-
- for n in 1..10 {
- interval.tick().await;
- println!("{}", n);
- assert_near!(timer.elapsed().as_millis(), 10 * n, 3);
- }
- });
- }
-}
diff --git a/gd/rust/facade/Android.bp b/gd/rust/facade/Android.bp
deleted file mode 100644
index 53944a844..000000000
--- a/gd/rust/facade/Android.bp
+++ /dev/null
@@ -1,64 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-rust_library {
- name: "libbluetooth_with_facades",
- defaults: ["gd_rust_defaults"],
- crate_name: "bluetooth_with_facades",
- srcs: ["src/lib.rs"],
- edition: "2018",
- rustlibs: [
- "libbt_hal",
- "libbt_hci",
- "libbt_facade_proto",
- "libfutures",
- "libgrpcio",
- "libprotobuf",
- "libtokio",
- "libgddi",
- "libbt_main",
- "liblog_rust",
- ],
-}
-
-rust_binary {
- name: "bluetooth_with_facades",
- defaults: ["gd_rust_defaults"],
- srcs: ["src/main.rs"],
- edition: "2018",
- rustlibs: [
- "libclap",
- "libbluetooth_with_facades",
- "libfutures",
- "libgrpcio",
- "libtokio",
- "libnix",
- "libbt_common",
- "liblog_rust",
- ],
-}
-
-rust_library {
- name: "libbt_facade_helpers",
- defaults: ["gd_rust_defaults"],
- crate_name: "bt_facade_helpers",
- srcs: ["helpers/lib.rs"],
- edition: "2018",
- rustlibs: [
- "libbt_facade_proto",
- "libbt_packets",
- "libbytes",
- "libfutures",
- "libgrpcio",
- "libtokio",
- "libprotobuf",
- "liblog_rust",
- "libcxx",
- ],
-}
diff --git a/gd/rust/facade/BUILD.gn b/gd/rust/facade/BUILD.gn
deleted file mode 100644
index 0140825c2..000000000
--- a/gd/rust/facade/BUILD.gn
+++ /dev/null
@@ -1,26 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-rust_library("libbt_facade_helpers") {
- crate_name = "bt_facade_helpers"
- sources = [
- "helpers/lib.rs",
- ]
-
- configs = [
- "//bt/gd/rust/shim:rust_libs",
- "//bt/gd:rust_defaults",
- ]
-}
diff --git a/gd/rust/facade/Cargo.toml b/gd/rust/facade/Cargo.toml
deleted file mode 100644
index 675887550..000000000
--- a/gd/rust/facade/Cargo.toml
+++ /dev/null
@@ -1,48 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bluetooth_with_facades"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-# GD bluetooth deps
-bt_facade_proto = { path = "../facade_proto" }
-bt_packets = { path = "../packets" }
-
-# External deps
-bytes = "*"
-cxx = "*"
-futures = "*"
-grpcio = "*"
-log = "*"
-protobuf = "*"
-tokio = "*"
-
-# Binary-only deps
-clap = "*"
-lazy_static = "*"
-nix = "*"
-bt_common = { path = "../common" }
-
-
-[[bin]]
-name = "bluetooth_with_facades"
-path = "src/main.rs"
-
-[lib]
-path = "src/lib.rs"
-crate-type = ["rlib"]
diff --git a/gd/rust/facade/helpers/Cargo.toml b/gd/rust/facade/helpers/Cargo.toml
deleted file mode 100644
index ceaa0f4bd..000000000
--- a/gd/rust/facade/helpers/Cargo.toml
+++ /dev/null
@@ -1,38 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bt_facade_helpers"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-# GD bluetooth deps
-bt_facade_proto = { path = "../../facade_proto" }
-bt_packets = { path = "../../packets" }
-
-# External deps
-bytes = "*"
-cxx = "*"
-futures = "*"
-grpcio = "*"
-log = "*"
-protobuf = "*"
-tokio = "*"
-
-[lib]
-path = "lib.rs"
-crate-type = ["rlib"]
-
diff --git a/gd/rust/facade/helpers/lib.rs b/gd/rust/facade/helpers/lib.rs
deleted file mode 100644
index 2d9877610..000000000
--- a/gd/rust/facade/helpers/lib.rs
+++ /dev/null
@@ -1,69 +0,0 @@
-//! common facade & shim helpers
-
-use bt_facade_proto::common::Data;
-use bt_packets::hci::Packet;
-use futures::sink::SinkExt;
-use grpcio::*;
-use std::sync::Arc;
-use tokio::runtime::Runtime;
-use tokio::sync::mpsc::Receiver;
-use tokio::sync::Mutex;
-
-/// Wrapper so we can invoke callbacks
-pub trait U8SliceRunnable {
- /// Do the thing
- fn run(&self, data: &[u8]);
-}
-
-/// Helper for interfacing channels with shim or gRPC boundaries
-#[derive(Clone)]
-pub struct RxAdapter<T> {
- rx: Arc<Mutex<Receiver<T>>>,
- running: bool,
-}
-
-impl<T: 'static + Packet + Send> RxAdapter<T> {
- /// New, from an unwrapped receiver
- pub fn new(rx: Receiver<T>) -> Self {
- Self::from_arc(Arc::new(Mutex::new(rx)))
- }
-
- /// New, from an already arc mutexed receiver
- pub fn from_arc(rx: Arc<Mutex<Receiver<T>>>) -> Self {
- Self { rx, running: false }
- }
-
- /// Stream out the channel over the provided sink
- pub fn stream_grpc(&mut self, ctx: RpcContext<'_>, mut sink: ServerStreamingSink<Data>) {
- assert!(!self.running);
- self.running = true;
-
- let clone_rx = self.rx.clone();
- ctx.spawn(async move {
- while let Some(payload) = clone_rx.lock().await.recv().await {
- let mut data = Data::default();
- data.set_payload(payload.to_vec());
- if let Err(e) = sink.send((data, WriteFlags::default())).await {
- log::error!("failure sending data: {:?}", e);
- }
- }
- });
- }
-
- /// Stream out the channel over the provided shim runnable
- pub fn stream_runnable<R: 'static + U8SliceRunnable + Send>(
- &mut self,
- rt: &Arc<Runtime>,
- runnable: R,
- ) {
- assert!(!self.running);
- self.running = true;
-
- let clone_rx = self.rx.clone();
- rt.spawn(async move {
- while let Some(payload) = clone_rx.lock().await.recv().await {
- runnable.run(&payload.to_bytes());
- }
- });
- }
-}
diff --git a/gd/rust/facade/src/lib.rs b/gd/rust/facade/src/lib.rs
deleted file mode 100644
index 8f9e14466..000000000
--- a/gd/rust/facade/src/lib.rs
+++ /dev/null
@@ -1,161 +0,0 @@
-//! Bluetooth testing root facade service
-
-use bt_facade_proto::rootservice::*;
-use bt_facade_proto::rootservice_grpc::{create_root_facade, RootFacade};
-use bt_hal::facade::HciHalFacadeService;
-use bt_hci::controller_facade::ControllerFacadeService;
-use bt_hci::facade::HciFacadeService;
-use bt_main::Stack;
-use futures::executor::block_on;
-use grpcio::*;
-use std::sync::Arc;
-use tokio::runtime::Runtime;
-use tokio::sync::mpsc::{channel, Sender};
-use tokio::sync::oneshot;
-
-/// Bluetooth testing root facade service
-#[derive(Clone)]
-pub struct RootFacadeService {
- rt: Arc<Runtime>,
- manager: FacadeServiceManager,
-}
-
-impl RootFacadeService {
- /// Create a new instance of the root facade service
- pub fn create(
- rt: Arc<Runtime>,
- grpc_port: u16,
- rootcanal_port: Option<u16>,
- snoop_path: Option<String>,
- ) -> grpcio::Service {
- create_root_facade(Self {
- rt: rt.clone(),
- manager: FacadeServiceManager::create(rt, grpc_port, rootcanal_port, snoop_path),
- })
- }
-}
-
-impl RootFacade for RootFacadeService {
- fn start_stack(
- &mut self,
- _ctx: RpcContext<'_>,
- req: StartStackRequest,
- sink: UnarySink<StartStackResponse>,
- ) {
- self.rt.block_on(self.manager.start(req)).unwrap();
- sink.success(StartStackResponse::default());
- }
-
- fn stop_stack(
- &mut self,
- _ctx: RpcContext<'_>,
- _req: StopStackRequest,
- sink: UnarySink<StopStackResponse>,
- ) {
- self.rt.block_on(self.manager.stop()).unwrap();
- sink.success(StopStackResponse::default());
- }
-}
-
-#[derive(Debug)]
-enum LifecycleCommand {
- Start { req: StartStackRequest, done: oneshot::Sender<()> },
- Stop { done: oneshot::Sender<()> },
-}
-
-#[derive(Clone)]
-struct FacadeServiceManager {
- lifecycle_tx: Sender<LifecycleCommand>,
-}
-
-struct FacadeServer {
- server: Server,
- stack: Stack,
-}
-
-impl FacadeServer {
- async fn start(stack: Stack, req: StartStackRequest, grpc_port: u16) -> Self {
- let mut services = Vec::new();
- match req.get_module_under_test() {
- BluetoothModule::HAL => {
- services.push(stack.get_grpc::<HciHalFacadeService>().await);
- }
- BluetoothModule::HCI => {
- services.push(stack.get_grpc::<HciFacadeService>().await);
- }
- BluetoothModule::HCI_INTERFACES => {
- services.push(stack.get_grpc::<HciFacadeService>().await);
- services.push(stack.get_grpc::<ControllerFacadeService>().await);
- }
- _ => unimplemented!(),
- }
-
- let env = Arc::new(Environment::new(2));
- let mut builder = ServerBuilder::new(env).bind("0.0.0.0", grpc_port);
- for service in services {
- builder = builder.register_service(service);
- }
-
- let mut server = builder.build().unwrap();
- server.start();
-
- Self { server, stack }
- }
-
- async fn stop(&mut self) {
- self.server.shutdown().await.unwrap();
- self.stack.stop().await;
- }
-}
-
-/// Result type
-type Result<T> = std::result::Result<T, Box<dyn std::error::Error + Send + Sync>>;
-
-impl FacadeServiceManager {
- fn create(
- rt: Arc<Runtime>,
- grpc_port: u16,
- rootcanal_port: Option<u16>,
- snoop_path: Option<String>,
- ) -> Self {
- let (tx, mut rx) = channel::<LifecycleCommand>(1);
- let local_rt = rt.clone();
- rt.spawn(async move {
- let mut server: Option<FacadeServer> = None;
- while let Some(cmd) = rx.recv().await {
- match cmd {
- LifecycleCommand::Start { req, done } => {
- let stack = Stack::new(local_rt.clone()).await;
- stack.set_rootcanal_port(rootcanal_port).await;
- stack.configure_snoop(snoop_path.clone()).await;
- server = Some(FacadeServer::start(stack, req, grpc_port).await);
- done.send(()).unwrap();
- }
- LifecycleCommand::Stop { done } => {
- if let Some(s) = &mut server {
- block_on(s.stop());
- server = None;
- }
- done.send(()).unwrap();
- }
- }
- }
- });
-
- Self { lifecycle_tx: tx }
- }
-
- async fn start(&self, req: StartStackRequest) -> Result<()> {
- let (tx, rx) = oneshot::channel();
- self.lifecycle_tx.send(LifecycleCommand::Start { req, done: tx }).await?;
- rx.await?;
- Ok(())
- }
-
- async fn stop(&self) -> Result<()> {
- let (tx, rx) = oneshot::channel();
- self.lifecycle_tx.send(LifecycleCommand::Stop { done: tx }).await?;
- rx.await?;
- Ok(())
- }
-}
diff --git a/gd/rust/facade/src/main.rs b/gd/rust/facade/src/main.rs
deleted file mode 100644
index 55cfb0ca8..000000000
--- a/gd/rust/facade/src/main.rs
+++ /dev/null
@@ -1,108 +0,0 @@
-//! Starts the facade services that allow us to test the Bluetooth stack
-
-#[macro_use]
-extern crate clap;
-use clap::{App, Arg};
-
-#[macro_use]
-extern crate lazy_static;
-
-use bluetooth_with_facades::RootFacadeService;
-use futures::channel::mpsc;
-use futures::executor::block_on;
-use futures::stream::StreamExt;
-use grpcio::*;
-use log::debug;
-use nix::sys::signal;
-use std::net::{IpAddr, Ipv4Addr, SocketAddr};
-use std::sync::{Arc, Mutex};
-use tokio::io::AsyncWriteExt;
-use tokio::net::TcpStream;
-use tokio::runtime::Runtime;
-
-fn main() {
- let sigint = install_sigint();
- bt_common::init_logging();
- let rt = Arc::new(Runtime::new().unwrap());
- rt.block_on(async_main(Arc::clone(&rt), sigint));
-}
-
-async fn async_main(rt: Arc<Runtime>, mut sigint: mpsc::UnboundedReceiver<()>) {
- let matches = App::new("bluetooth_with_facades")
- .about("The bluetooth stack, with testing facades enabled and exposed via gRPC.")
- .arg(
- Arg::with_name("root-server-port")
- .long("root-server-port")
- .default_value("8897")
- .takes_value(true),
- )
- .arg(Arg::with_name("grpc-port").long("grpc-port").default_value("8899").takes_value(true))
- .arg(
- Arg::with_name("signal-port")
- .long("signal-port")
- .default_value("8895")
- .takes_value(true),
- )
- .arg(Arg::with_name("rootcanal-port").long("rootcanal-port").takes_value(true))
- .arg(Arg::with_name("btsnoop").long("btsnoop").takes_value(true))
- .arg(Arg::with_name("btsnooz").long("btsnooz").takes_value(true))
- .arg(Arg::with_name("btconfig").long("btconfig").takes_value(true))
- .get_matches();
-
- let root_server_port = value_t!(matches, "root-server-port", u16).unwrap();
- let grpc_port = value_t!(matches, "grpc-port", u16).unwrap();
- let signal_port = value_t!(matches, "signal-port", u16).unwrap();
- let rootcanal_port = value_t!(matches, "rootcanal-port", u16).ok();
- let env = Arc::new(Environment::new(2));
- let mut server = ServerBuilder::new(env)
- .register_service(RootFacadeService::create(
- rt,
- grpc_port,
- rootcanal_port,
- matches.value_of("btsnoop").map(String::from),
- ))
- .bind("0.0.0.0", root_server_port)
- .build()
- .unwrap();
- server.start();
-
- indicate_started(signal_port).await;
- sigint.next().await;
- block_on(server.shutdown()).unwrap();
-}
-
-async fn indicate_started(signal_port: u16) {
- let address = SocketAddr::new(IpAddr::V4(Ipv4Addr::new(0, 0, 0, 0)), signal_port);
- let mut stream = TcpStream::connect(address).await.unwrap();
- stream.shutdown().await.unwrap();
-}
-
-// TODO: remove as this is a temporary nix-based hack to catch SIGINT
-fn install_sigint() -> mpsc::UnboundedReceiver<()> {
- let (tx, rx) = mpsc::unbounded();
- *SIGINT_TX.lock().unwrap() = Some(tx);
-
- let sig_action = signal::SigAction::new(
- signal::SigHandler::Handler(handle_sigint),
- signal::SaFlags::empty(),
- signal::SigSet::empty(),
- );
- unsafe {
- signal::sigaction(signal::SIGINT, &sig_action).unwrap();
- }
-
- rx
-}
-
-lazy_static! {
- static ref SIGINT_TX: Mutex<Option<mpsc::UnboundedSender<()>>> = Mutex::new(None);
-}
-
-extern "C" fn handle_sigint(_: i32) {
- let mut sigint_tx = SIGINT_TX.lock().unwrap();
- if let Some(tx) = &*sigint_tx {
- debug!("Stopping gRPC root server due to SIGINT");
- tx.unbounded_send(()).unwrap();
- }
- *sigint_tx = None;
-}
diff --git a/gd/rust/facade_proto/Cargo.toml b/gd/rust/facade_proto/Cargo.toml
deleted file mode 100644
index c69c86981..000000000
--- a/gd/rust/facade_proto/Cargo.toml
+++ /dev/null
@@ -1,34 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bt_facade_proto"
-version = "0.0.1"
-edition = "2018"
-build = "build.rs"
-
-[dependencies]
-bt_hci_custom_types = { path = "../hci/custom_types" }
-futures = "*"
-grpcio = "*"
-protobuf = "*"
-
-[build-dependencies]
-protoc-rust = "*"
-protoc-grpcio = "*"
-protobuf-codegen = "*"
-
-[lib]
-crate-types = ["rlib"]
diff --git a/gd/rust/facade_proto/build.rs b/gd/rust/facade_proto/build.rs
deleted file mode 100644
index 7c9bc4c40..000000000
--- a/gd/rust/facade_proto/build.rs
+++ /dev/null
@@ -1,109 +0,0 @@
-//
-// Copyright 2021 Google, Inc.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at:
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-extern crate protobuf_codegen;
-extern crate protoc_grpcio;
-extern crate protoc_rust;
-
-use std::env;
-use std::fs;
-use std::io::Write;
-use std::path::{Path, PathBuf};
-
-fn paths_to_strs<P: AsRef<Path>>(paths: &[P]) -> Vec<&str> {
- paths.iter().map(|p| p.as_ref().as_os_str().to_str().unwrap()).collect()
-}
-
-// Generate mod.rs files for given input files.
-fn gen_mod_rs<P: AsRef<Path>>(out_dir: PathBuf, inputs: &[P], grpc: bool) {
- // Will panic if file doesn't exist or it can't create it
- let mut f = fs::File::create(out_dir.join("mod.rs")).unwrap();
-
- f.write_all(b"// Generated by build.rs\n\n").unwrap();
-
- for i in 0..inputs.len() {
- let stem = inputs[i].as_ref().file_stem().unwrap();
- f.write_all(format!("pub mod {}; \n", stem.to_str().unwrap()).as_bytes()).unwrap();
- if grpc {
- f.write_all(format!("pub mod {}_grpc;\n", stem.to_str().unwrap()).as_bytes()).unwrap();
- }
- }
-}
-
-fn main() {
- let out_dir = PathBuf::from(env::var("OUT_DIR").unwrap());
- let proto_out_dir = out_dir.join("proto_out");
- let grpc_out_dir = out_dir.join("grpc_out");
-
- // Make sure to create the output directories before using it
- match fs::create_dir(proto_out_dir.as_os_str().to_str().unwrap()) {
- Err(e) => println!("Proto dir failed to be created: {}", e),
- _ => (),
- };
-
- match fs::create_dir(grpc_out_dir.as_os_str().to_str().unwrap()) {
- Err(e) => println!("Grpc dir failed to be created: {}", e),
- _ => (),
- }
-
- // Proto root is //platform2/bt/gd
- let proto_root = match env::var("PLATFORM_SUBDIR") {
- Ok(dir) => PathBuf::from(dir).join("bt/gd"),
- // Currently at //platform2/gd/rust/facade_proto
- Err(_) => PathBuf::from(env::current_dir().unwrap()).join("../..").canonicalize().unwrap(),
- };
-
- //
- // Generate protobuf output
- //
- let facade_dir = proto_root.join("facade");
- let proto_input_files = [facade_dir.join("common.proto")];
- let proto_include_dirs = [facade_dir];
-
- protoc_rust::Codegen::new()
- .out_dir(proto_out_dir.as_os_str().to_str().unwrap())
- .inputs(&paths_to_strs(&proto_input_files))
- .includes(&paths_to_strs(&proto_include_dirs))
- .customize(Default::default())
- .run()
- .expect("protoc");
-
- //
- // Generate grpc output
- //
- let grpc_proto_input_files = [
- proto_root.join("hci/facade/hci_facade.proto"),
- proto_root.join("hci/facade/controller_facade.proto"),
- proto_root.join("hal/hal_facade.proto"),
- proto_root.join("facade/rootservice.proto"),
- ];
- let grpc_proto_include_dirs = [
- proto_root.join("hci/facade"),
- proto_root.join("hal"),
- proto_root.join("facade"),
- proto_root,
- ];
-
- protoc_grpcio::compile_grpc_protos(
- &grpc_proto_input_files,
- &grpc_proto_include_dirs,
- &grpc_out_dir,
- None,
- )
- .expect("Failed to compile gRPC definitions");
-
- gen_mod_rs(proto_out_dir, &proto_input_files, false);
- gen_mod_rs(grpc_out_dir, &grpc_proto_input_files, true);
-}
diff --git a/gd/rust/facade_proto/src/common.rs b/gd/rust/facade_proto/src/common.rs
deleted file mode 100644
index e1a6f76fe..000000000
--- a/gd/rust/facade_proto/src/common.rs
+++ /dev/null
@@ -1,20 +0,0 @@
-//
-// Copyright 2021 Google, Inc.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at:
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-// We are not directly including due to bugs with inner and outer attributes.
-//include!(concat!(env!("OUT_DIR"), "/common.rs"));
-
-#[path = concat!(env!("OUT_DIR", "/common.rs"))]
-pub mod common;
diff --git a/gd/rust/facade_proto/src/lib.rs b/gd/rust/facade_proto/src/lib.rs
deleted file mode 100644
index 56f7f7077..000000000
--- a/gd/rust/facade_proto/src/lib.rs
+++ /dev/null
@@ -1,25 +0,0 @@
-//
-// Copyright 2021 Google, Inc.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at:
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-// protoc-rust and protoc-grpcio generates all modules and exports them in mod.rs
-// We have to include them all here to make them available for crate export.
-include!(concat!(env!("OUT_DIR"), "/proto_out/mod.rs"));
-include!(concat!(env!("OUT_DIR"), "/grpc_out/mod.rs"));
-
-// empty.proto is missing so add a workaround
-// See github.com/stepancheg/grpc-rust/issues/156
-pub mod empty {
- pub use protobuf::well_known_types::Empty;
-}
diff --git a/gd/rust/gddi/Android.bp b/gd/rust/gddi/Android.bp
deleted file mode 100644
index fa9837fd2..000000000
--- a/gd/rust/gddi/Android.bp
+++ /dev/null
@@ -1,30 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-rust_library {
- name: "libgddi",
- defaults: ["gd_rust_defaults"],
- crate_name: "gddi",
- srcs: ["src/lib.rs"],
- edition: "2018",
- proc_macros: ["libgddi_macros"],
- rustlibs: ["libtokio"],
-}
-
-rust_proc_macro {
- name: "libgddi_macros",
- crate_name: "gddi_macros",
- srcs: ["macros/lib.rs"],
- edition: "2018",
- rustlibs: [
- "libproc_macro2",
- "libquote",
- "libsyn",
- ],
-}
diff --git a/gd/rust/gddi/Cargo.toml b/gd/rust/gddi/Cargo.toml
deleted file mode 100644
index 9e43a147b..000000000
--- a/gd/rust/gddi/Cargo.toml
+++ /dev/null
@@ -1,31 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "gddi"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-gddi_macros = { path = "macros" }
-
-tokio = { version = "*", features = ['bytes', 'net', 'sync'] }
-quote = "*"
-syn = { version = "*", features = ['default', 'full'] }
-
-[lib]
-path = "src/lib.rs"
-crate-type = ["rlib"]
-
diff --git a/gd/rust/gddi/macros/Cargo.toml b/gd/rust/gddi/macros/Cargo.toml
deleted file mode 100644
index 4038b0c3a..000000000
--- a/gd/rust/gddi/macros/Cargo.toml
+++ /dev/null
@@ -1,28 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "gddi_macros"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-proc-macro2 = "*"
-quote = "*"
-syn = "*"
-
-[lib]
-proc-macro = true
-path = "lib.rs"
diff --git a/gd/rust/gddi/macros/lib.rs b/gd/rust/gddi/macros/lib.rs
deleted file mode 100644
index ea761386d..000000000
--- a/gd/rust/gddi/macros/lib.rs
+++ /dev/null
@@ -1,209 +0,0 @@
-//! Core dependency injection macros
-
-extern crate proc_macro;
-use proc_macro::TokenStream;
-use quote::{format_ident, quote};
-use syn::parse::{Parse, ParseStream, Result};
-use syn::punctuated::Punctuated;
-use syn::{
- braced, parse, parse_macro_input, DeriveInput, Fields, FnArg, Ident, ItemFn, ItemStruct, Path,
- Token, Type,
-};
-
-/// Defines a provider function, with generated helper that implicitly fetches argument instances from the registry
-#[proc_macro_attribute]
-pub fn provides(_attr: TokenStream, item: TokenStream) -> TokenStream {
- let function: ItemFn = parse(item).expect("can only be applied to functions");
-
- // Create the info needed to refer to the function & the injected version we generate
- let ident = function.sig.ident.clone();
- let injected_ident = format_ident!("__gddi_{}_injected", ident);
-
- // Create the info needed to generate the call to the original function
- let inputs = function.sig.inputs.iter().map(|arg| {
- if let FnArg::Typed(t) = arg {
- return t.ty.clone();
- }
- panic!("can't be applied to struct methods");
- });
- let local_var_idents = (0..inputs.len()).map(|i| format_ident!("__input{}", i));
- let local_var_idents_for_call = local_var_idents.clone();
-
- let emitted_code = quote! {
- // Injecting wrapper
- fn #injected_ident(registry: std::sync::Arc<gddi::Registry>) -> std::pin::Pin<gddi::ProviderFutureBox> {
- Box::pin(async move {
- // Create a local variable for each argument, to ensure they get generated in a
- // deterministic order (compiler complains otherwise)
- #(let #local_var_idents = registry.get::<#inputs>().await;)*
-
- // Actually call the original function
- Box::new(#ident(#(#local_var_idents_for_call),*).await) as Box<dyn std::any::Any>
- })
- }
- #function
- };
- emitted_code.into()
-}
-
-struct ModuleDef {
- name: Ident,
- providers: Punctuated<ProviderDef, Token![,]>,
- submodules: Punctuated<Path, Token![,]>,
-}
-
-enum ModuleEntry {
- Providers(Punctuated<ProviderDef, Token![,]>),
- Submodules(Punctuated<Path, Token![,]>),
-}
-
-struct ProviderDef {
- ty: Type,
- ident: Ident,
- parts: bool,
-}
-
-impl Parse for ModuleDef {
- fn parse(input: ParseStream) -> Result<Self> {
- // first thing is the module name followed by a comma
- let name = input.parse()?;
- input.parse::<Token![,]>()?;
- // Then comes submodules or provider sections, in any order
- let entries: Punctuated<ModuleEntry, Token![,]> = Punctuated::parse_terminated(input)?;
- let mut providers = Punctuated::new();
- let mut submodules = Punctuated::new();
- for entry in entries.into_iter() {
- match entry {
- ModuleEntry::Providers(value) => {
- if !providers.is_empty() {
- panic!("providers specified more than once");
- }
- providers = value;
- }
- ModuleEntry::Submodules(value) => {
- if !submodules.is_empty() {
- panic!("submodules specified more than once");
- }
- submodules = value;
- }
- }
- }
- Ok(ModuleDef { name, providers, submodules })
- }
-}
-
-impl Parse for ProviderDef {
- fn parse(input: ParseStream) -> Result<Self> {
- let parts = input.peek3(Token![=>]);
- if parts {
- match input.parse::<Ident>()?.to_string().as_str() {
- "parts" => {}
- keyword => panic!("expected 'parts', got '{}'", keyword),
- }
- }
-
- // A provider definition follows this format: <Type> -> <function name>
- let ty = input.parse()?;
- input.parse::<Token![=>]>()?;
- let ident = input.parse()?;
- Ok(ProviderDef { ty, ident, parts })
- }
-}
-
-impl Parse for ModuleEntry {
- fn parse(input: ParseStream) -> Result<Self> {
- match input.parse::<Ident>()?.to_string().as_str() {
- "providers" => {
- let entries;
- braced!(entries in input);
- Ok(ModuleEntry::Providers(entries.parse_terminated(ProviderDef::parse)?))
- }
- "submodules" => {
- let entries;
- braced!(entries in input);
- Ok(ModuleEntry::Submodules(entries.parse_terminated(Path::parse)?))
- }
- keyword => {
- panic!("unexpected keyword: {}", keyword);
- }
- }
- }
-}
-
-/// Emits a module function that registers submodules & providers with the registry
-#[proc_macro]
-pub fn module(item: TokenStream) -> TokenStream {
- let module = parse_macro_input!(item as ModuleDef);
- let init_ident = module.name.clone();
- let providers = module.providers.iter();
- let types = providers.clone().map(|p| p.ty.clone());
- let provider_idents =
- providers.clone().map(|p| format_ident!("__gddi_{}_injected", p.ident.clone()));
- let parting_functions = providers.filter_map(|p| match &p.ty {
- Type::Path(ty) if p.parts => Some(format_ident!(
- "__gddi_part_out_{}",
- ty.path.get_ident().unwrap().to_string().to_lowercase()
- )),
- _ => None,
- });
- let submodule_idents = module.submodules.iter();
- let emitted_code = quote! {
- #[doc(hidden)]
- #[allow(missing_docs)]
- pub fn #init_ident(builder: gddi::RegistryBuilder) -> gddi::RegistryBuilder {
- // Register all providers on this module
- let ret = builder#(.register_provider::<#types>(Box::new(#provider_idents)))*
- // Register all submodules on this module
- #(.register_module(#submodule_idents))*;
-
- #(let ret = #parting_functions(ret);)*
-
- ret
- }
- };
- emitted_code.into()
-}
-
-/// Emits a default implementation for Stoppable that does nothing;
-#[proc_macro_derive(Stoppable)]
-pub fn derive_nop_stop(item: TokenStream) -> TokenStream {
- let input = parse_macro_input!(item as DeriveInput);
- let ident = input.ident;
- let emitted_code = quote! {
- impl gddi::Stoppable for #ident {}
- };
- emitted_code.into()
-}
-
-/// Generates the code necessary to split up a type into its components
-#[proc_macro_attribute]
-pub fn part_out(_attr: TokenStream, item: TokenStream) -> TokenStream {
- let struct_: ItemStruct = parse(item).expect("can only be applied to struct definitions");
- let struct_ident = struct_.ident.clone();
- let fields = match struct_.fields.clone() {
- Fields::Named(f) => f,
- _ => panic!("can only be applied to structs with named fields"),
- }
- .named;
-
- let field_names = fields.iter().map(|f| f.ident.clone().expect("field without a name"));
- let field_types = fields.iter().map(|f| f.ty.clone());
-
- let fn_ident = format_ident!("__gddi_part_out_{}", struct_ident.to_string().to_lowercase());
-
- let emitted_code = quote! {
- #struct_
-
- fn #fn_ident(builder: gddi::RegistryBuilder) -> gddi::RegistryBuilder {
- builder#(.register_provider::<#field_types>(Box::new(
- |registry: std::sync::Arc<gddi::Registry>| -> std::pin::Pin<gddi::ProviderFutureBox> {
- Box::pin(async move {
- Box::new(async move {
- registry.get::<#struct_ident>().await.#field_names
- }.await) as Box<dyn std::any::Any>
- })
- })))*
- }
- };
- emitted_code.into()
-}
diff --git a/gd/rust/gddi/src/lib.rs b/gd/rust/gddi/src/lib.rs
deleted file mode 100644
index 1e005431f..000000000
--- a/gd/rust/gddi/src/lib.rs
+++ /dev/null
@@ -1,119 +0,0 @@
-//! Core dependency injection objects
-
-use std::any::{Any, TypeId};
-use std::collections::HashMap;
-use std::future::Future;
-use std::pin::Pin;
-use std::sync::Arc;
-use tokio::sync::Mutex;
-
-pub use gddi_macros::{module, part_out, provides, Stoppable};
-
-type InstanceBox = Box<dyn Any + Send + Sync>;
-/// A box around a future for a provider that is safe to send between threads
-pub type ProviderFutureBox = Box<dyn Future<Output = Box<dyn Any>> + Send + Sync>;
-type ProviderFnBox = Box<dyn Fn(Arc<Registry>) -> Pin<ProviderFutureBox> + Send + Sync>;
-
-/// Called to stop an injected object
-pub trait Stoppable {
- /// Stop and close all resources
- fn stop(&self) {}
-}
-
-/// Builder for Registry
-pub struct RegistryBuilder {
- providers: HashMap<TypeId, Provider>,
-}
-
-/// Keeps track of central injection state
-pub struct Registry {
- providers: Arc<Mutex<HashMap<TypeId, Provider>>>,
- instances: Arc<Mutex<HashMap<TypeId, InstanceBox>>>,
- start_order: Arc<Mutex<Vec<Box<dyn Stoppable + Send + Sync>>>>,
-}
-
-#[derive(Clone)]
-struct Provider {
- f: Arc<ProviderFnBox>,
-}
-
-impl Default for RegistryBuilder {
- fn default() -> Self {
- Self::new()
- }
-}
-
-impl RegistryBuilder {
- /// Creates a new RegistryBuilder
- pub fn new() -> Self {
- RegistryBuilder { providers: HashMap::new() }
- }
-
- /// Registers a module with this registry
- pub fn register_module<F>(self, init: F) -> Self
- where
- F: Fn(Self) -> Self,
- {
- init(self)
- }
-
- /// Registers a provider function with this registry
- pub fn register_provider<T: 'static>(mut self, f: ProviderFnBox) -> Self {
- self.providers.insert(TypeId::of::<T>(), Provider { f: Arc::new(f) });
-
- self
- }
-
- /// Construct the Registry from this builder
- pub fn build(self) -> Registry {
- Registry {
- providers: Arc::new(Mutex::new(self.providers)),
- instances: Arc::new(Mutex::new(HashMap::new())),
- start_order: Arc::new(Mutex::new(Vec::new())),
- }
- }
-}
-
-impl Registry {
- /// Gets an instance of a type, implicitly starting any dependencies if necessary
- pub async fn get<T: 'static + Clone + Send + Sync + Stoppable>(self: &Arc<Self>) -> T {
- let typeid = TypeId::of::<T>();
- {
- let instances = self.instances.lock().await;
- if let Some(value) = instances.get(&typeid) {
- return value.downcast_ref::<T>().expect("was not correct type").clone();
- }
- }
-
- let casted = {
- let provider = { self.providers.lock().await[&typeid].clone() };
- let result = (provider.f)(self.clone()).await;
- (*result.downcast::<T>().expect("was not correct type")).clone()
- };
-
- let mut instances = self.instances.lock().await;
- instances.insert(typeid, Box::new(casted.clone()));
-
- let mut start_order = self.start_order.lock().await;
- start_order.push(Box::new(casted.clone()));
-
- casted
- }
-
- /// Inject an already created instance of T. Useful for config.
- pub async fn inject<T: 'static + Clone + Send + Sync>(self: &Arc<Self>, obj: T) {
- let mut instances = self.instances.lock().await;
- instances.insert(TypeId::of::<T>(), Box::new(obj));
- }
-
- /// Stop all instances, in reverse order of start.
- pub async fn stop_all(self: &Arc<Self>) {
- let mut start_order = self.start_order.lock().await;
- while let Some(obj) = start_order.pop() {
- obj.stop();
- }
- self.instances.lock().await.clear();
- }
-}
-
-impl<T> Stoppable for std::sync::Arc<T> {}
diff --git a/gd/rust/hal/Android.bp b/gd/rust/hal/Android.bp
deleted file mode 100644
index 571a8bda0..000000000
--- a/gd/rust/hal/Android.bp
+++ /dev/null
@@ -1,79 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-rust_library {
- name: "libbt_hal",
- defaults: ["gd_rust_defaults"],
- crate_name: "bt_hal",
- srcs: ["src/lib.rs"],
- edition: "2018",
- rustlibs: [
- "libbt_facade_proto",
- "libbt_packets",
- "libbytes",
- "libfutures",
- "libthiserror",
- "libgrpcio",
- "libtokio",
- "libprotobuf",
- "libbt_packets",
- "libgddi",
- "libcxx",
- "liblazy_static",
- "liblog_rust",
- "libbt_common",
- "libnum_traits",
- "libbt_facade_helpers",
- ],
- proc_macros: [
- "libnum_derive",
- ],
- target: {
- android: {
- whole_static_libs: ["libbt_hidl_hal_cxx"],
- shared_libs: [
- "android.hardware.bluetooth@1.0",
- "android.hardware.bluetooth@1.1",
- "libhidlbase",
- "libutils",
- ],
- },
- },
-}
-
-genrule {
- name: "libbt_hidl_hal_bridge_header",
- tools: ["cxxbridge"],
- cmd: "$(location cxxbridge) $(in) --header > $(out)",
- srcs: ["src/hidl_hal.rs"],
- out: ["src/hidl_hal.rs.h"],
-}
-
-genrule {
- name: "libbt_hidl_hal_bridge_code",
- tools: ["cxxbridge"],
- cmd: "$(location cxxbridge) $(in) >> $(out)",
- srcs: ["src/hidl_hal.rs"],
- out: ["hidl_hal_generated.cc"],
-}
-
-cc_library_static {
- name: "libbt_hidl_hal_cxx",
- defaults: ["gd_ffi_defaults"],
- srcs: ["src/ffi/hidl.cc"],
- local_include_dirs: ["src/ffi"],
- generated_headers: ["libbt_hidl_hal_bridge_header", "cxx-bridge-header"],
- generated_sources: ["libbt_hidl_hal_bridge_code"],
- shared_libs: [
- "android.hardware.bluetooth@1.0",
- "android.hardware.bluetooth@1.1",
- "libhidlbase",
- "libutils",
- ],
-}
diff --git a/gd/rust/hal/BUILD.gn b/gd/rust/hal/BUILD.gn
deleted file mode 100644
index cce2f7ba8..000000000
--- a/gd/rust/hal/BUILD.gn
+++ /dev/null
@@ -1,27 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-rust_library("libbt_hal") {
- crate_name = "bt_hal"
-
- sources = [
- "src/lib.rs"
- ]
-
- configs = [
- "//bt/gd/rust/shim:rust_libs",
- "//bt/gd:rust_defaults",
- ]
-}
diff --git a/gd/rust/hal/Cargo.toml b/gd/rust/hal/Cargo.toml
deleted file mode 100644
index fe909e83d..000000000
--- a/gd/rust/hal/Cargo.toml
+++ /dev/null
@@ -1,46 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bt_hal"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-# BT dependencies
-bt_common = { path = "../common" }
-bt_facade_helpers = { path = "../facade/helpers" }
-bt_facade_proto = { path = "../facade_proto" }
-bt_packets = { path = "../packets" }
-gddi = { path = "../gddi" }
-
-# External dependencies
-bytes = "*"
-cxx = "*"
-futures = "*"
-grpcio = "*"
-lazy_static = "*"
-log = "*"
-nix = "*"
-num-traits = "*"
-protobuf = "*"
-thiserror = "*"
-tokio = "*"
-
-# Macro dependencies
-num-derive = "*"
-
-[lib]
-crate-type = ["rlib"]
diff --git a/gd/rust/hal/src/facade.rs b/gd/rust/hal/src/facade.rs
deleted file mode 100644
index 08f29497d..000000000
--- a/gd/rust/hal/src/facade.rs
+++ /dev/null
@@ -1,93 +0,0 @@
-//! BT HCI HAL facade
-
-use crate::{AclHal, ControlHal, IsoHal};
-use bt_common::GrpcFacade;
-use bt_facade_helpers::RxAdapter;
-use bt_facade_proto::common::Data;
-use bt_facade_proto::empty::Empty;
-use bt_facade_proto::hal_facade_grpc::{create_hci_hal_facade, HciHalFacade};
-use bt_packets::hci::{AclPacket, CommandPacket, EventPacket, IsoPacket};
-use gddi::{module, provides, Stoppable};
-use grpcio::*;
-
-module! {
- hal_facade_module,
- providers {
- HciHalFacadeService => provide_facade,
- }
-}
-
-#[provides]
-async fn provide_facade(control: ControlHal, acl: AclHal, iso: IsoHal) -> HciHalFacadeService {
- HciHalFacadeService {
- evt_rx: RxAdapter::from_arc(control.rx.clone()),
- acl_rx: RxAdapter::from_arc(acl.rx.clone()),
- iso_rx: RxAdapter::from_arc(iso.rx.clone()),
- control,
- acl,
- iso,
- }
-}
-
-/// HCI HAL facade service
-#[derive(Clone, Stoppable)]
-pub struct HciHalFacadeService {
- evt_rx: RxAdapter<EventPacket>,
- acl_rx: RxAdapter<AclPacket>,
- iso_rx: RxAdapter<IsoPacket>,
- control: ControlHal,
- acl: AclHal,
- iso: IsoHal,
-}
-
-impl GrpcFacade for HciHalFacadeService {
- fn into_grpc(self) -> grpcio::Service {
- create_hci_hal_facade(self)
- }
-}
-
-impl HciHalFacade for HciHalFacadeService {
- fn send_command(&mut self, ctx: RpcContext<'_>, mut data: Data, sink: UnarySink<Empty>) {
- let cmd_tx = self.control.tx.clone();
- ctx.spawn(async move {
- cmd_tx.send(CommandPacket::parse(&data.take_payload()).unwrap()).await.unwrap();
- sink.success(Empty::default()).await.unwrap();
- });
- }
-
- fn send_acl(&mut self, ctx: RpcContext<'_>, mut data: Data, sink: UnarySink<Empty>) {
- let acl_tx = self.acl.tx.clone();
- ctx.spawn(async move {
- acl_tx.send(AclPacket::parse(&data.take_payload()).unwrap()).await.unwrap();
- sink.success(Empty::default()).await.unwrap();
- });
- }
-
- fn send_sco(&mut self, _ctx: RpcContext<'_>, _sco: Data, _sink: UnarySink<Empty>) {
- unimplemented!()
- }
-
- fn send_iso(&mut self, ctx: RpcContext<'_>, mut data: Data, sink: UnarySink<Empty>) {
- let iso_tx = self.iso.tx.clone();
- ctx.spawn(async move {
- iso_tx.send(IsoPacket::parse(&data.take_payload()).unwrap()).await.unwrap();
- sink.success(Empty::default()).await.unwrap();
- });
- }
-
- fn stream_events(&mut self, ctx: RpcContext<'_>, _: Empty, sink: ServerStreamingSink<Data>) {
- self.evt_rx.stream_grpc(ctx, sink);
- }
-
- fn stream_acl(&mut self, ctx: RpcContext<'_>, _: Empty, sink: ServerStreamingSink<Data>) {
- self.acl_rx.stream_grpc(ctx, sink);
- }
-
- fn stream_sco(&mut self, _ctx: RpcContext<'_>, _: Empty, _sink: ServerStreamingSink<Data>) {
- unimplemented!()
- }
-
- fn stream_iso(&mut self, ctx: RpcContext<'_>, _: Empty, sink: ServerStreamingSink<Data>) {
- self.iso_rx.stream_grpc(ctx, sink);
- }
-}
diff --git a/gd/rust/hal/src/ffi/hidl.cc b/gd/rust/hal/src/ffi/hidl.cc
deleted file mode 100644
index fd46babd7..000000000
--- a/gd/rust/hal/src/ffi/hidl.cc
+++ /dev/null
@@ -1,128 +0,0 @@
-#include <android/hardware/bluetooth/1.0/types.h>
-#include <android/hardware/bluetooth/1.1/IBluetoothHci.h>
-#include <android/hardware/bluetooth/1.1/IBluetoothHciCallbacks.h>
-#include <stdlib.h>
-
-#include "../../os/log.h"
-#include "src/ffi/hidl.h"
-
-using ::android::hardware::hidl_vec;
-using ::android::hardware::Return;
-using ::android::hardware::Void;
-using ::android::hardware::bluetooth::V1_1::IBluetoothHci;
-using ::android::hardware::bluetooth::V1_1::IBluetoothHciCallbacks;
-using HidlStatus = ::android::hardware::bluetooth::V1_0::Status;
-using IBluetoothHci_1_0 = ::android::hardware::bluetooth::V1_0::IBluetoothHci;
-
-namespace bluetooth {
-namespace hal {
-namespace {
-
-class HciDeathRecipient : public ::android::hardware::hidl_death_recipient {
- public:
- virtual void serviceDied(uint64_t /*cookie*/, const android::wp<::android::hidl::base::V1_0::IBase>& /*who*/) {
- LOG_ERROR("Bluetooth HAL service died!");
- abort();
- }
-};
-
-class HciCallbackTrampoline : public IBluetoothHciCallbacks {
- public:
- HciCallbackTrampoline() {}
-
- Return<void> initializationComplete(HidlStatus status) {
- ASSERT(status == HidlStatus::SUCCESS);
- on_init_complete();
- return Void();
- }
-
- Return<void> hciEventReceived(const hidl_vec<uint8_t>& event) {
- on_event(rust::Slice(&event[0], event.size()));
- return Void();
- }
-
- Return<void> aclDataReceived(const hidl_vec<uint8_t>& data) {
- on_acl(rust::Slice(&data[0], data.size()));
- return Void();
- }
-
- Return<void> scoDataReceived(const hidl_vec<uint8_t>& data) {
- on_sco(rust::Slice(&data[0], data.size()));
- return Void();
- }
-
- Return<void> isoDataReceived(const hidl_vec<uint8_t>& data) {
- on_iso(rust::Slice(&data[0], data.size()));
- return Void();
- }
-};
-
-android::sp<HciDeathRecipient> hci_death_recipient_ = new HciDeathRecipient();
-android::sp<IBluetoothHci_1_0> bt_hci_;
-android::sp<IBluetoothHci> bt_hci_1_1_;
-android::sp<HciCallbackTrampoline> trampoline_;
-
-} // namespace
-
-void start_hal() {
- ASSERT(bt_hci_ == nullptr);
-
- bt_hci_1_1_ = IBluetoothHci::getService();
- if (bt_hci_1_1_ != nullptr) {
- bt_hci_ = bt_hci_1_1_;
- } else {
- bt_hci_ = IBluetoothHci_1_0::getService();
- }
-
- ASSERT(bt_hci_ != nullptr);
- auto death_link = bt_hci_->linkToDeath(hci_death_recipient_, 0);
- ASSERT_LOG(death_link.isOk(), "Unable to set the death recipient for the Bluetooth HAL");
-
- trampoline_ = new HciCallbackTrampoline();
- if (bt_hci_1_1_ != nullptr) {
- bt_hci_1_1_->initialize_1_1(trampoline_);
- } else {
- bt_hci_->initialize(trampoline_);
- }
-}
-
-void stop_hal() {
- ASSERT(bt_hci_ != nullptr);
-
- auto death_unlink = bt_hci_->unlinkToDeath(hci_death_recipient_);
- if (!death_unlink.isOk()) {
- LOG_ERROR("Error unlinking death recipient from the Bluetooth HAL");
- }
- bt_hci_->close();
- bt_hci_ = nullptr;
- bt_hci_1_1_ = nullptr;
- trampoline_ = nullptr;
-}
-
-void send_command(rust::Slice<const uint8_t> data) {
- ASSERT(bt_hci_ != nullptr);
- bt_hci_->sendHciCommand(hidl_vec<uint8_t>(data.data(), data.data() + data.length()));
-}
-
-void send_acl(rust::Slice<const uint8_t> data) {
- ASSERT(bt_hci_ != nullptr);
- bt_hci_->sendAclData(hidl_vec<uint8_t>(data.data(), data.data() + data.length()));
-}
-
-void send_sco(rust::Slice<const uint8_t> data) {
- ASSERT(bt_hci_ != nullptr);
- bt_hci_->sendScoData(hidl_vec<uint8_t>(data.data(), data.data() + data.length()));
-}
-
-void send_iso(rust::Slice<const uint8_t> data) {
- if (bt_hci_1_1_ == nullptr) {
- LOG_ERROR("ISO is not supported in HAL v1.0");
- return;
- }
-
- ASSERT(bt_hci_ != nullptr);
- bt_hci_1_1_->sendIsoData(hidl_vec<uint8_t>(data.data(), data.data() + data.length()));
-}
-
-} // namespace hal
-} // namespace bluetooth
diff --git a/gd/rust/hal/src/ffi/hidl.h b/gd/rust/hal/src/ffi/hidl.h
deleted file mode 100644
index 20138f64c..000000000
--- a/gd/rust/hal/src/ffi/hidl.h
+++ /dev/null
@@ -1,15 +0,0 @@
-#pragma once
-#include "src/hidl_hal.rs.h"
-
-namespace bluetooth {
-namespace hal {
-
-void start_hal();
-void stop_hal();
-void send_command(rust::Slice<const uint8_t> data);
-void send_acl(rust::Slice<const uint8_t> data);
-void send_sco(rust::Slice<const uint8_t> data);
-void send_iso(rust::Slice<const uint8_t> data);
-
-} // namespace hal
-} // namespace bluetooth
diff --git a/gd/rust/hal/src/hidl_hal.rs b/gd/rust/hal/src/hidl_hal.rs
deleted file mode 100644
index ea815e697..000000000
--- a/gd/rust/hal/src/hidl_hal.rs
+++ /dev/null
@@ -1,115 +0,0 @@
-//! Implementation of the HAl that talks to BT controller over Android's HIDL
-use crate::internal::{InnerHal, RawHal};
-use bt_packets::hci::{AclPacket, CommandPacket, EventPacket, IsoPacket, Packet};
-use gddi::{module, provides};
-use std::sync::Arc;
-use std::sync::Mutex;
-use tokio::runtime::Runtime;
-use tokio::select;
-use tokio::sync::mpsc::{unbounded_channel, UnboundedReceiver, UnboundedSender};
-
-module! {
- hidl_hal_module,
- providers {
- RawHal => provide_hidl_hal,
- }
-}
-
-#[provides]
-async fn provide_hidl_hal(rt: Arc<Runtime>) -> RawHal {
- let (raw_hal, inner_hal) = InnerHal::new();
- let (init_tx, mut init_rx) = unbounded_channel();
- *CALLBACKS.lock().unwrap() = Some(Callbacks {
- init_tx,
- evt_tx: inner_hal.evt_tx,
- acl_tx: inner_hal.acl_tx,
- iso_tx: inner_hal.iso_tx,
- });
- ffi::start_hal();
- init_rx.recv().await.unwrap();
-
- rt.spawn(dispatch_outgoing(inner_hal.cmd_rx, inner_hal.acl_rx, inner_hal.iso_rx));
-
- raw_hal
-}
-
-#[cxx::bridge(namespace = bluetooth::hal)]
-// TODO Either use or remove these functions, this shouldn't be the long term state
-#[allow(dead_code)]
-mod ffi {
- unsafe extern "C++" {
- include!("src/ffi/hidl.h");
- fn start_hal();
- fn stop_hal();
- fn send_command(data: &[u8]);
- fn send_acl(data: &[u8]);
- fn send_sco(data: &[u8]);
- fn send_iso(data: &[u8]);
- }
-
- extern "Rust" {
- fn on_init_complete();
- fn on_event(data: &[u8]);
- fn on_acl(data: &[u8]);
- fn on_sco(data: &[u8]);
- fn on_iso(data: &[u8]);
- }
-}
-
-struct Callbacks {
- init_tx: UnboundedSender<()>,
- evt_tx: UnboundedSender<EventPacket>,
- acl_tx: UnboundedSender<AclPacket>,
- iso_tx: UnboundedSender<IsoPacket>,
-}
-
-lazy_static! {
- static ref CALLBACKS: Mutex<Option<Callbacks>> = Mutex::new(None);
-}
-
-fn on_init_complete() {
- let callbacks = CALLBACKS.lock().unwrap();
- callbacks.as_ref().unwrap().init_tx.send(()).unwrap();
-}
-
-fn on_event(data: &[u8]) {
- log::error!("got event: {:02x?}", data);
- let callbacks = CALLBACKS.lock().unwrap();
- match EventPacket::parse(data) {
- Ok(p) => callbacks.as_ref().unwrap().evt_tx.send(p).unwrap(),
- Err(e) => log::error!("failure to parse event: {:?} data: {:02x?}", e, data),
- }
-}
-
-fn on_acl(data: &[u8]) {
- let callbacks = CALLBACKS.lock().unwrap();
- match AclPacket::parse(data) {
- Ok(p) => callbacks.as_ref().unwrap().acl_tx.send(p).unwrap(),
- Err(e) => log::error!("failure to parse incoming ACL: {:?} data: {:02x?}", e, data),
- }
-}
-
-fn on_sco(_data: &[u8]) {}
-
-fn on_iso(data: &[u8]) {
- let callbacks = CALLBACKS.lock().unwrap();
- match IsoPacket::parse(data) {
- Ok(p) => callbacks.as_ref().unwrap().iso_tx.send(p).unwrap(),
- Err(e) => log::error!("failure to parse incoming ISO: {:?} data: {:02x?}", e, data),
- }
-}
-
-async fn dispatch_outgoing(
- mut cmd_rx: UnboundedReceiver<CommandPacket>,
- mut acl_rx: UnboundedReceiver<AclPacket>,
- mut iso_rx: UnboundedReceiver<IsoPacket>,
-) {
- loop {
- select! {
- Some(cmd) = cmd_rx.recv() => ffi::send_command(&cmd.to_bytes()),
- Some(acl) = acl_rx.recv() => ffi::send_acl(&acl.to_bytes()),
- Some(iso) = iso_rx.recv() => ffi::send_iso(&iso.to_bytes()),
- else => break,
- }
- }
-}
diff --git a/gd/rust/hal/src/lib.rs b/gd/rust/hal/src/lib.rs
deleted file mode 100644
index e35704af5..000000000
--- a/gd/rust/hal/src/lib.rs
+++ /dev/null
@@ -1,112 +0,0 @@
-//! HCI Hardware Abstraction Layer
-//! Supports sending HCI commands to the HAL and receving
-//! HCI events from the HAL
-#[cfg(target_os = "android")]
-#[macro_use]
-extern crate lazy_static;
-
-pub mod facade;
-pub mod rootcanal_hal;
-pub mod snoop;
-
-#[cfg(target_os = "android")]
-mod hidl_hal;
-
-use gddi::module;
-use thiserror::Error;
-
-#[cfg(target_os = "android")]
-module! {
- hal_module,
- submodules {
- facade::hal_facade_module,
- hidl_hal::hidl_hal_module,
- snoop::snoop_module,
- },
-}
-
-#[cfg(not(target_os = "android"))]
-module! {
- hal_module,
- submodules {
- facade::hal_facade_module,
- rootcanal_hal::rootcanal_hal_module,
- snoop::snoop_module,
- },
-}
-/// H4 packet header size
-const H4_HEADER_SIZE: usize = 1;
-
-pub use snoop::AclHal;
-pub use snoop::ControlHal;
-pub use snoop::IsoHal;
-
-mod internal {
- use bt_packets::hci::{AclPacket, CommandPacket, EventPacket, IsoPacket};
- use gddi::Stoppable;
- use std::sync::Arc;
- use tokio::sync::mpsc::{unbounded_channel, UnboundedReceiver, UnboundedSender};
- use tokio::sync::Mutex;
-
- #[derive(Clone, Stoppable)]
- pub struct RawHal {
- pub cmd_tx: UnboundedSender<CommandPacket>,
- pub evt_rx: Arc<Mutex<UnboundedReceiver<EventPacket>>>,
- pub acl_tx: UnboundedSender<AclPacket>,
- pub acl_rx: Arc<Mutex<UnboundedReceiver<AclPacket>>>,
- pub iso_tx: UnboundedSender<IsoPacket>,
- pub iso_rx: Arc<Mutex<UnboundedReceiver<IsoPacket>>>,
- }
-
- pub struct InnerHal {
- pub cmd_rx: UnboundedReceiver<CommandPacket>,
- pub evt_tx: UnboundedSender<EventPacket>,
- pub acl_rx: UnboundedReceiver<AclPacket>,
- pub acl_tx: UnboundedSender<AclPacket>,
- pub iso_rx: UnboundedReceiver<IsoPacket>,
- pub iso_tx: UnboundedSender<IsoPacket>,
- }
-
- impl InnerHal {
- pub fn new() -> (RawHal, Self) {
- let (cmd_tx, cmd_rx) = unbounded_channel();
- let (evt_tx, evt_rx) = unbounded_channel();
- let (acl_down_tx, acl_down_rx) = unbounded_channel();
- let (iso_down_tx, iso_down_rx) = unbounded_channel();
- let (acl_up_tx, acl_up_rx) = unbounded_channel();
- let (iso_up_tx, iso_up_rx) = unbounded_channel();
- (
- RawHal {
- cmd_tx,
- evt_rx: Arc::new(Mutex::new(evt_rx)),
- acl_tx: acl_down_tx,
- acl_rx: Arc::new(Mutex::new(acl_up_rx)),
- iso_tx: iso_down_tx,
- iso_rx: Arc::new(Mutex::new(iso_up_rx)),
- },
- Self {
- cmd_rx,
- evt_tx,
- acl_rx: acl_down_rx,
- acl_tx: acl_up_tx,
- iso_rx: iso_down_rx,
- iso_tx: iso_up_tx,
- },
- )
- }
- }
-}
-
-/// Result type
-type Result<T> = std::result::Result<T, Box<dyn std::error::Error + Send + Sync>>;
-
-/// Errors that can be encountered while dealing with the HAL
-#[derive(Error, Debug)]
-pub enum HalError {
- /// Invalid rootcanal host error
- #[error("Invalid rootcanal host")]
- InvalidAddressError,
- /// Error while connecting to rootcanal
- #[error("Connection to rootcanal failed: {0}")]
- RootcanalConnectError(#[from] tokio::io::Error),
-}
diff --git a/gd/rust/hal/src/rootcanal_hal.rs b/gd/rust/hal/src/rootcanal_hal.rs
deleted file mode 100644
index 9044412d9..000000000
--- a/gd/rust/hal/src/rootcanal_hal.rs
+++ /dev/null
@@ -1,163 +0,0 @@
-//! Rootcanal HAL
-//! This connects to "rootcanal" which provides a simulated
-//! Bluetooth chip as well as a simulated environment.
-
-use crate::internal::{InnerHal, RawHal};
-use crate::{Result, H4_HEADER_SIZE};
-use bt_packets::hci::{AclPacket, CommandPacket, EventPacket, IsoPacket, Packet};
-use bytes::{BufMut, Bytes, BytesMut};
-use gddi::{module, provides, Stoppable};
-use num_derive::{FromPrimitive, ToPrimitive};
-use std::net::{IpAddr, SocketAddr};
-use std::str::FromStr;
-use std::sync::Arc;
-use tokio::io::{AsyncReadExt, AsyncWriteExt, BufReader};
-use tokio::net::TcpStream;
-use tokio::runtime::Runtime;
-use tokio::select;
-use tokio::sync::mpsc::{UnboundedReceiver, UnboundedSender};
-
-#[derive(FromPrimitive, ToPrimitive)]
-enum HciPacketType {
- Command = 0x01,
- Acl = 0x02,
- Sco = 0x03,
- Event = 0x04,
- Iso = 0x05,
-}
-
-const SIZE_OF_EVENT_HEADER: usize = 2;
-const _SIZE_OF_SCO_HEADER: usize = 3;
-const SIZE_OF_ACL_HEADER: usize = 4;
-const SIZE_OF_ISO_HEADER: usize = 4;
-
-module! {
- rootcanal_hal_module,
- providers {
- RawHal => provide_rootcanal_hal,
- }
-}
-
-#[provides]
-async fn provide_rootcanal_hal(config: RootcanalConfig, rt: Arc<Runtime>) -> RawHal {
- let (raw_hal, inner_hal) = InnerHal::new();
- let (reader, writer) = TcpStream::connect(&config.to_socket_addr().unwrap())
- .await
- .expect("unable to create stream to rootcanal")
- .into_split();
-
- rt.spawn(dispatch_incoming(inner_hal.evt_tx, inner_hal.acl_tx, inner_hal.iso_tx, reader));
- rt.spawn(dispatch_outgoing(inner_hal.cmd_rx, inner_hal.acl_rx, inner_hal.iso_rx, writer));
-
- raw_hal
-}
-
-/// Rootcanal configuration
-#[derive(Clone, Debug, Default, Stoppable)]
-pub struct RootcanalConfig {
- address: String,
- port: u16,
-}
-
-impl RootcanalConfig {
- /// Create a rootcanal config
- pub fn new(address: &str, port: u16) -> Self {
- Self { address: String::from(address), port }
- }
-
- fn to_socket_addr(&self) -> Result<SocketAddr> {
- Ok(SocketAddr::new(IpAddr::from_str(&self.address)?, self.port))
- }
-}
-
-/// Send HCI events received from the HAL to the HCI layer
-async fn dispatch_incoming<R>(
- evt_tx: UnboundedSender<EventPacket>,
- acl_tx: UnboundedSender<AclPacket>,
- iso_tx: UnboundedSender<IsoPacket>,
- reader: R,
-) -> Result<()>
-where
- R: AsyncReadExt + Unpin,
-{
- let mut reader = BufReader::new(reader);
- loop {
- let mut buffer = BytesMut::with_capacity(1024);
- buffer.resize(H4_HEADER_SIZE, 0);
- reader.read_exact(&mut buffer).await?;
- if buffer[0] == HciPacketType::Event as u8 {
- buffer.resize(SIZE_OF_EVENT_HEADER, 0);
- reader.read_exact(&mut buffer).await?;
- let len: usize = buffer[1].into();
- let mut payload = buffer.split_off(SIZE_OF_EVENT_HEADER);
- payload.resize(len, 0);
- reader.read_exact(&mut payload).await?;
- buffer.unsplit(payload);
- let frozen = buffer.freeze();
- match EventPacket::parse(&frozen) {
- Ok(p) => evt_tx.send(p).unwrap(),
- Err(e) => log::error!("dropping invalid event packet: {}: {:02x}", e, frozen),
- }
- } else if buffer[0] == HciPacketType::Acl as u8 {
- buffer.resize(SIZE_OF_ACL_HEADER, 0);
- reader.read_exact(&mut buffer).await?;
- let len: usize = (buffer[2] as u16 + ((buffer[3] as u16) << 8)).into();
- let mut payload = buffer.split_off(SIZE_OF_ACL_HEADER);
- payload.resize(len, 0);
- reader.read_exact(&mut payload).await?;
- buffer.unsplit(payload);
- let frozen = buffer.freeze();
- match AclPacket::parse(&frozen) {
- Ok(p) => acl_tx.send(p).unwrap(),
- Err(e) => log::error!("dropping invalid ACL packet: {}: {:02x}", e, frozen),
- }
- } else if buffer[0] == HciPacketType::Iso as u8 {
- buffer.resize(SIZE_OF_ISO_HEADER, 0);
- reader.read_exact(&mut buffer).await?;
- let len: usize = (buffer[2] as u16 + (((buffer[3] & 0x3f) as u16) << 8)).into();
- let mut payload = buffer.split_off(SIZE_OF_ISO_HEADER);
- payload.resize(len, 0);
- reader.read_exact(&mut payload).await?;
- buffer.unsplit(payload);
- let frozen = buffer.freeze();
- match IsoPacket::parse(&frozen) {
- Ok(p) => iso_tx.send(p).unwrap(),
- Err(e) => log::error!("dropping invalid ISO packet: {}: {:02x}", e, frozen),
- }
- }
- }
-}
-
-/// Send commands received from the HCI later to rootcanal
-async fn dispatch_outgoing<W>(
- mut cmd_rx: UnboundedReceiver<CommandPacket>,
- mut acl_rx: UnboundedReceiver<AclPacket>,
- mut iso_rx: UnboundedReceiver<IsoPacket>,
- mut writer: W,
-) -> Result<()>
-where
- W: AsyncWriteExt + Unpin,
-{
- loop {
- select! {
- Some(cmd) = cmd_rx.recv() => write_with_type(&mut writer, HciPacketType::Command, cmd.to_bytes()).await?,
- Some(acl) = acl_rx.recv() => write_with_type(&mut writer, HciPacketType::Acl, acl.to_bytes()).await?,
- Some(iso) = iso_rx.recv() => write_with_type(&mut writer, HciPacketType::Iso, iso.to_bytes()).await?,
- else => break,
- }
- }
-
- Ok(())
-}
-
-async fn write_with_type<W>(writer: &mut W, t: HciPacketType, b: Bytes) -> Result<()>
-where
- W: AsyncWriteExt + Unpin,
-{
- let mut data = BytesMut::with_capacity(b.len() + 1);
- data.put_u8(t as u8);
- data.extend(b);
- writer.write_all(&data[..]).await?;
-
- Ok(())
-}
diff --git a/gd/rust/hal/src/snoop.rs b/gd/rust/hal/src/snoop.rs
deleted file mode 100644
index ef5400912..000000000
--- a/gd/rust/hal/src/snoop.rs
+++ /dev/null
@@ -1,315 +0,0 @@
-//! BT snoop logger
-
-use crate::internal::RawHal;
-use bt_common::sys_prop;
-use bt_packets::hci::{AclPacket, CommandPacket, EventPacket, IsoPacket, Packet};
-use bytes::{BufMut, Bytes, BytesMut};
-use gddi::{module, part_out, provides, Stoppable};
-use log::error;
-use std::convert::TryFrom;
-use std::sync::Arc;
-use std::time::SystemTime;
-use tokio::fs::{remove_file, rename, File};
-use tokio::io::AsyncWriteExt;
-use tokio::runtime::Runtime;
-use tokio::select;
-use tokio::sync::mpsc::{channel, Receiver, Sender, UnboundedReceiver};
-use tokio::sync::Mutex;
-
-#[part_out]
-#[derive(Clone, Stoppable)]
-struct Hal {
- control: ControlHal,
- acl: AclHal,
- iso: IsoHal,
-}
-
-/// Command & event tx/rx
-#[derive(Clone, Stoppable)]
-pub struct ControlHal {
- /// Transmit end
- pub tx: Sender<CommandPacket>,
- /// Receive end
- pub rx: Arc<Mutex<Receiver<EventPacket>>>,
-}
-
-/// Acl tx/rx
-#[derive(Clone, Stoppable)]
-pub struct AclHal {
- /// Transmit end
- pub tx: Sender<AclPacket>,
- /// Receive end
- pub rx: Arc<Mutex<Receiver<AclPacket>>>,
-}
-
-/// Iso tx/rx
-#[derive(Clone, Stoppable)]
-pub struct IsoHal {
- /// Transmit end
- pub tx: Sender<IsoPacket>,
- /// Receive end
- pub rx: Arc<Mutex<Receiver<IsoPacket>>>,
-}
-
-/// The different modes snoop logging can be in
-#[derive(Clone)]
-pub enum SnoopMode {
- /// All logs disabled
- Disabled,
- /// Only sanitized logs
- Filtered,
- /// Log everything
- Full,
-}
-
-/// There was an error parsing the mode from a string
-pub struct SnoopModeParseError;
-
-impl std::str::FromStr for SnoopMode {
- type Err = SnoopModeParseError;
-
- fn from_str(s: &str) -> Result<Self, Self::Err> {
- match s {
- "disabled" => Ok(SnoopMode::Disabled),
- "filtered" => Ok(SnoopMode::Filtered),
- "full" => Ok(SnoopMode::Full),
- _ => Err(SnoopModeParseError),
- }
- }
-}
-
-/// All snoop logging config
-#[derive(Clone, Stoppable)]
-pub struct SnoopConfig {
- path: String,
- max_packets_per_file: u32,
- mode: SnoopMode,
-}
-
-impl SnoopConfig {
- /// Constructs a new snoop config
- pub fn new() -> Self {
- Self {
- path: "/data/misc/bluetooth/logs/btsnoop_hci.log".to_string(),
- max_packets_per_file: sys_prop::get_u32("persist.bluetooth.btsnoopsize")
- .unwrap_or(0xFFFF),
- mode: get_configured_snoop_mode().parse().unwrap_or(SnoopMode::Disabled),
- }
- }
-
- /// Overwrites the laoded log path with the provided one
- pub fn set_path(&mut self, value: String) {
- self.path = value;
- }
-
- /// Overwrites the loaded mode with the provided one
- pub fn set_mode(&mut self, value: SnoopMode) {
- self.mode = value;
- }
-}
-
-impl Default for SnoopConfig {
- fn default() -> Self {
- Self::new()
- }
-}
-
-fn get_configured_snoop_mode() -> String {
- sys_prop::get("persist.bluetooth.btsnooplogmode").unwrap_or(if sys_prop::get_debuggable() {
- sys_prop::get("persist.bluetooth.btsnoopdefaultmode").unwrap_or_default()
- } else {
- String::default()
- })
-}
-
-module! {
- snoop_module,
- providers {
- parts Hal => provide_snooped_hal,
- },
-}
-
-#[provides]
-async fn provide_snooped_hal(config: SnoopConfig, raw_hal: RawHal, rt: Arc<Runtime>) -> Hal {
- let (cmd_down_tx, mut cmd_down_rx) = channel::<CommandPacket>(10);
- let (evt_up_tx, evt_up_rx) = channel::<EventPacket>(10);
- let (acl_down_tx, mut acl_down_rx) = channel::<AclPacket>(10);
- let (acl_up_tx, acl_up_rx) = channel::<AclPacket>(10);
- let (iso_down_tx, mut iso_down_rx) = channel::<IsoPacket>(10);
- let (iso_up_tx, iso_up_rx) = channel::<IsoPacket>(10);
-
- rt.spawn(async move {
- let mut logger = SnoopLogger::new(config).await;
- loop {
- select! {
- Some(evt) = consume(&raw_hal.evt_rx) => {
- if let Err(e) = evt_up_tx.send(evt.clone()).await {
- error!("evt channel closed {:?}", e);
- break;
- }
- logger.log(Type::Evt, Direction::Up, evt.to_bytes()).await;
- },
- Some(cmd) = cmd_down_rx.recv() => {
- if let Err(e) = raw_hal.cmd_tx.send(cmd.clone()) {
- error!("cmd channel closed {:?}", e);
- break;
- }
- logger.log(Type::Cmd, Direction::Down, cmd.to_bytes()).await;
- },
- Some(acl) = acl_down_rx.recv() => {
- if let Err(e) = raw_hal.acl_tx.send(acl.clone()) {
- error!("acl down channel closed {:?}", e);
- break;
- }
- logger.log(Type::Acl, Direction::Down, acl.to_bytes()).await;
- },
- Some(acl) = consume(&raw_hal.acl_rx) => {
- if let Err(e) = acl_up_tx.send(acl.clone()).await {
- error!("acl up channel closed {:?}", e);
- break;
- }
- logger.log(Type::Acl, Direction::Up, acl.to_bytes()).await;
- },
- Some(iso) = iso_down_rx.recv() => {
- if let Err(e) = raw_hal.iso_tx.send(iso.clone()) {
- error!("iso down channel closed {:?}", e);
- break;
- }
- logger.log(Type::Iso, Direction::Down, iso.to_bytes()).await;
- },
- Some(iso) = consume(&raw_hal.iso_rx) => {
- if let Err(e) = iso_up_tx.send(iso.clone()).await {
- error!("iso up channel closed {:?}", e);
- break;
- }
- logger.log(Type::Iso, Direction::Up, iso.to_bytes()).await;
- },
- else => break,
- }
- }
- });
-
- Hal {
- control: ControlHal { tx: cmd_down_tx, rx: Arc::new(Mutex::new(evt_up_rx)) },
- acl: AclHal { tx: acl_down_tx, rx: Arc::new(Mutex::new(acl_up_rx)) },
- iso: IsoHal { tx: iso_down_tx, rx: Arc::new(Mutex::new(iso_up_rx)) },
- }
-}
-
-async fn consume<T>(rx: &Arc<Mutex<UnboundedReceiver<T>>>) -> Option<T> {
- rx.lock().await.recv().await
-}
-
-#[allow(unused)]
-enum Type {
- Cmd = 1,
- Acl,
- Sco,
- Evt,
- Iso,
-}
-
-enum Direction {
- Up,
- Down,
-}
-
-struct SnoopLogger {
- config: SnoopConfig,
- file: Option<File>,
- packets: u32,
-}
-
-// micros since 0000-01-01
-const SNOOP_EPOCH_DELTA: u64 = 0x00dcddb30f2f8000;
-
-impl SnoopLogger {
- async fn new(mut config: SnoopConfig) -> Self {
- // filtered snoop is not available at this time
- if let SnoopMode::Filtered = config.mode {
- config.mode = SnoopMode::Disabled;
- }
-
- remove_file(&config.path).await.ok();
- remove_file(config.path.clone() + ".last").await.ok();
- if let SnoopMode::Disabled = config.mode {
- remove_file(config.path.clone() + ".filtered").await.ok();
- remove_file(config.path.clone() + ".filtered.last").await.ok();
- }
-
- let mut ret = Self { config, file: None, packets: 0 };
- ret.open_next_file().await;
-
- ret
- }
-
- async fn log(&mut self, t: Type, dir: Direction, bytes: Bytes) {
- if let SnoopMode::Disabled = self.config.mode {
- return;
- }
-
- let mut flags = 0;
- if let Direction::Up = dir {
- flags |= 0b01;
- }
- if let Type::Cmd | Type::Evt = t {
- flags |= 0b10;
- }
-
- let timestamp: u64 = u64::try_from(
- SystemTime::now().duration_since(SystemTime::UNIX_EPOCH).unwrap().as_micros(),
- )
- .unwrap()
- + SNOOP_EPOCH_DELTA;
-
- // Add one for the type byte
- let length = u32::try_from(bytes.len()).unwrap() + 1;
-
- let mut buffer = BytesMut::new();
- buffer.put_u32(length); // original length
- buffer.put_u32(length); // captured length
- buffer.put_u32(flags); // flags
- buffer.put_u32(0); // dropped packets
- buffer.put_u64(timestamp); // timestamp
- buffer.put_u8(t as u8); // type
- buffer.put(bytes);
-
- self.packets += 1;
- if self.packets > self.config.max_packets_per_file {
- self.open_next_file().await;
- }
-
- if let Some(file) = &mut self.file {
- if file.write_all(&buffer).await.is_err() {
- error!("Failed to write");
- }
- if file.flush().await.is_err() {
- error!("Failed to flush");
- }
- } else {
- panic!("Logging without a backing file");
- }
- }
-
- async fn close_file(&mut self) {
- if let Some(file) = &mut self.file {
- file.flush().await.ok();
- self.file = None;
- }
- self.packets = 0;
- }
-
- async fn open_next_file(&mut self) {
- self.close_file().await;
-
- rename(&self.config.path, self.config.path.clone() + ".last").await.ok();
- let mut file = File::create(&self.config.path).await.expect("could not open snoop log");
- file.write_all(b"btsnoop\x00\x00\x00\x00\x01\x00\x00\x03\xea")
- .await
- .expect("could not write snoop header");
- if file.flush().await.is_err() {
- error!("Failed to flush");
- }
- self.file = Some(file);
- }
-}
diff --git a/gd/rust/hci/Android.bp b/gd/rust/hci/Android.bp
deleted file mode 100644
index e00bc695d..000000000
--- a/gd/rust/hci/Android.bp
+++ /dev/null
@@ -1,44 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-rust_library {
- name: "libbt_hci",
- defaults: ["gd_rust_defaults"],
- crate_name: "bt_hci",
- srcs: ["src/lib.rs"],
- edition: "2018",
- rustlibs: [
- "libbt_hal",
- "libbt_facade_proto",
- "libbt_packets",
- "libbytes",
- "libfutures",
- "libgrpcio",
- "libnum_traits",
- "libthiserror",
- "libtokio",
- "libprotobuf",
- "libgddi",
- "liblog_rust",
- "libbt_common",
- "libbt_hci_custom_types",
- "libbt_facade_helpers",
- ],
- proc_macros: [
- "libnum_derive",
- ],
-}
-
-rust_library {
- name: "libbt_hci_custom_types",
- defaults: ["gd_rust_defaults"],
- crate_name: "bt_hci_custom_types",
- srcs: ["custom_types/lib.rs"],
- edition: "2018",
-}
diff --git a/gd/rust/hci/BUILD.gn b/gd/rust/hci/BUILD.gn
deleted file mode 100644
index e120b277a..000000000
--- a/gd/rust/hci/BUILD.gn
+++ /dev/null
@@ -1,27 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-rust_library("libbt_hci") {
- crate_name = "bt_hci"
-
- sources = [
- "src/lib.rs"
- ]
-
- configs = [
- "//bt/gd/rust/shim:rust_libs",
- "//bt/gd:rust_defaults",
- ]
-}
diff --git a/gd/rust/hci/Cargo.toml b/gd/rust/hci/Cargo.toml
deleted file mode 100644
index 48e08a91b..000000000
--- a/gd/rust/hci/Cargo.toml
+++ /dev/null
@@ -1,45 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bt_hci"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-# bt deps
-bt_common = { path = "../common" }
-bt_hci_custom_types = { path = "custom_types" }
-bt_hal = { path = "../hal" }
-bt_facade_helpers = { path = "../facade/helpers" }
-bt_facade_proto = { path = "../facade_proto" }
-bt_packets = { path = "../packets" }
-gddi = { path = "../gddi" }
-
-# external deps
-bytes = "*"
-futures = "*"
-grpcio = "*"
-log = "*"
-num-traits = "*"
-protobuf = "*"
-thiserror = "*"
-tokio = { version = "*", features = ['bytes', 'net'] }
-
-# macro deps
-num-derive = "*"
-
-[lib]
-crate-type = ["rlib"]
diff --git a/gd/rust/hci/custom_types/Cargo.toml b/gd/rust/hci/custom_types/Cargo.toml
deleted file mode 100644
index 3e9c5e19d..000000000
--- a/gd/rust/hci/custom_types/Cargo.toml
+++ /dev/null
@@ -1,23 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bt_hci_custom_types"
-version = "0.0.1"
-edition = "2018"
-
-[lib]
-crate-type = ["rlib"]
-path = "lib.rs"
diff --git a/gd/rust/hci/custom_types/lib.rs b/gd/rust/hci/custom_types/lib.rs
deleted file mode 100644
index 749afdc13..000000000
--- a/gd/rust/hci/custom_types/lib.rs
+++ /dev/null
@@ -1,108 +0,0 @@
-//! custom types to be imported by hci packet pdl
-//! (since hci depends on the packet library, we need to split these out)
-
-use std::convert::TryFrom;
-use std::fmt;
-
-/// Signal for "empty" address
-pub const EMPTY_ADDRESS: Address = Address { bytes: [0x00, 0x00, 0x00, 0x00, 0x00, 0x00] };
-/// Signal for "any" address
-pub const ANY_ADDRESS: Address = Address { bytes: [0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF] };
-
-/// A Bluetooth address
-#[derive(Clone, Copy, Eq, PartialEq, Hash, Ord, PartialOrd, Debug)]
-pub struct Address {
- /// the actual bytes representing this address
- pub bytes: [u8; 6],
-}
-
-impl Address {
- /// whether this address is empty
- pub fn is_empty(&self) -> bool {
- *self == EMPTY_ADDRESS
- }
-}
-
-impl fmt::Display for Address {
- fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
- write!(
- f,
- "{:02X}:{:02X}:{:02X}:{:02X}:{:02X}:{:02X}",
- self.bytes[5],
- self.bytes[4],
- self.bytes[3],
- self.bytes[2],
- self.bytes[1],
- self.bytes[0]
- )
- }
-}
-
-/// When you parse an address and it's not valid
-#[derive(Debug, Clone)]
-pub struct InvalidAddressError;
-
-impl TryFrom<&[u8]> for Address {
- type Error = InvalidAddressError;
-
- fn try_from(slice: &[u8]) -> Result<Self, Self::Error> {
- if slice.len() == 6 {
- match <[u8; 6]>::try_from(slice) {
- Ok(bytes) => Ok(Self { bytes }),
- Err(_) => Err(InvalidAddressError),
- }
- } else {
- Err(InvalidAddressError)
- }
- }
-}
-
-impl From<Address> for [u8; 6] {
- fn from(addr: Address) -> [u8; 6] {
- addr.bytes
- }
-}
-
-/// A Bluetooth class of device
-#[derive(Clone, Eq, Copy, PartialEq, Hash, Ord, PartialOrd, Debug)]
-pub struct ClassOfDevice {
- /// the actual bytes representing this class of device
- pub bytes: [u8; 3],
-}
-
-impl fmt::Display for ClassOfDevice {
- fn fmt(&self, f: &mut fmt::Formatter<'_>) -> fmt::Result {
- write!(
- f,
- "{:03X}-{:01X}-{:02X}",
- ((self.bytes[2] as u16) << 4) | ((self.bytes[1] as u16) >> 4),
- self.bytes[1] & 0x0F,
- self.bytes[0]
- )
- }
-}
-
-/// When you parse a class of device and it's not valid
-#[derive(Debug, Clone)]
-pub struct InvalidClassOfDeviceError;
-
-impl TryFrom<&[u8]> for ClassOfDevice {
- type Error = InvalidClassOfDeviceError;
-
- fn try_from(slice: &[u8]) -> Result<Self, Self::Error> {
- if slice.len() == 3 {
- match <[u8; 3]>::try_from(slice) {
- Ok(bytes) => Ok(Self { bytes }),
- Err(_) => Err(InvalidClassOfDeviceError),
- }
- } else {
- Err(InvalidClassOfDeviceError)
- }
- }
-}
-
-impl From<ClassOfDevice> for [u8; 3] {
- fn from(cod: ClassOfDevice) -> [u8; 3] {
- cod.bytes
- }
-}
diff --git a/gd/rust/hci/src/controller.rs b/gd/rust/hci/src/controller.rs
deleted file mode 100644
index 7e07d8060..000000000
--- a/gd/rust/hci/src/controller.rs
+++ /dev/null
@@ -1,328 +0,0 @@
-//! Loads info from the controller at startup
-
-use crate::{Address, CommandSender};
-use bt_packets::hci::{
- Enable, ErrorCode, LeMaximumDataLength, LeReadBufferSizeV1Builder, LeReadBufferSizeV2Builder,
- LeReadConnectListSizeBuilder, LeReadLocalSupportedFeaturesBuilder,
- LeReadMaximumAdvertisingDataLengthBuilder, LeReadMaximumDataLengthBuilder,
- LeReadNumberOfSupportedAdvertisingSetsBuilder, LeReadPeriodicAdvertiserListSizeBuilder,
- LeReadResolvingListSizeBuilder, LeReadSuggestedDefaultDataLengthBuilder,
- LeReadSupportedStatesBuilder, LeSetEventMaskBuilder, LocalVersionInformation, OpCode,
- OpCodeIndex, ReadBdAddrBuilder, ReadBufferSizeBuilder, ReadLocalExtendedFeaturesBuilder,
- ReadLocalNameBuilder, ReadLocalSupportedCommandsBuilder, ReadLocalVersionInformationBuilder,
- SetEventMaskBuilder, WriteLeHostSupportBuilder, WriteSimplePairingModeBuilder,
-};
-use gddi::{module, provides, Stoppable};
-use num_traits::ToPrimitive;
-use std::convert::TryFrom;
-use std::sync::Arc;
-
-module! {
- controller_module,
- providers {
- Arc<ControllerExports> => provide_controller,
- },
-}
-
-macro_rules! assert_success {
- ($hci:ident.send($builder:expr)) => {{
- let response = $hci.send($builder).await;
- assert!(response.get_status() == ErrorCode::Success);
-
- response
- }};
-}
-
-#[provides]
-async fn provide_controller(mut hci: CommandSender) -> Arc<ControllerExports> {
- assert_success!(hci.send(LeSetEventMaskBuilder { le_event_mask: 0x0000000000021e7f }));
- assert_success!(hci.send(SetEventMaskBuilder { event_mask: 0x3dbfffffffffffff }));
- assert_success!(
- hci.send(WriteSimplePairingModeBuilder { simple_pairing_mode: Enable::Enabled })
- );
- assert_success!(hci.send(WriteLeHostSupportBuilder {
- le_supported_host: Enable::Enabled,
- simultaneous_le_host: Enable::Enabled
- }));
-
- let name = null_terminated_to_string(
- assert_success!(hci.send(ReadLocalNameBuilder {})).get_local_name(),
- );
-
- let version_info = assert_success!(hci.send(ReadLocalVersionInformationBuilder {}))
- .get_local_version_information()
- .clone();
-
- let commands = SupportedCommands {
- supported: *assert_success!(hci.send(ReadLocalSupportedCommandsBuilder {}))
- .get_supported_commands(),
- };
-
- let features = read_features(&mut hci).await;
-
- let buffer_size = assert_success!(hci.send(ReadBufferSizeBuilder {}));
- let acl_buffer_length = buffer_size.get_acl_data_packet_length();
- let mut acl_buffers = buffer_size.get_total_num_acl_data_packets();
-
- let (mut le_buffer_length, mut le_buffers, iso_buffer_length, iso_buffers) =
- if commands.is_supported(OpCode::LeReadBufferSizeV2) {
- let response = assert_success!(hci.send(LeReadBufferSizeV2Builder {}));
- (
- response.get_le_buffer_size().le_data_packet_length,
- response.get_le_buffer_size().total_num_le_packets,
- response.get_iso_buffer_size().le_data_packet_length,
- response.get_iso_buffer_size().total_num_le_packets,
- )
- } else {
- let response = assert_success!(hci.send(LeReadBufferSizeV1Builder {}));
- (
- response.get_le_buffer_size().le_data_packet_length,
- response.get_le_buffer_size().total_num_le_packets,
- 0,
- 0,
- )
- };
-
- // If the controller reports zero LE buffers, the ACL buffers are shared between classic & LE
- if le_buffers == 0 {
- le_buffers = (acl_buffers / 2) as u8;
- acl_buffers -= le_buffers as u16;
- le_buffer_length = acl_buffer_length;
- }
-
- let le_features = SupportedLeFeatures::new(
- assert_success!(hci.send(LeReadLocalSupportedFeaturesBuilder {})).get_le_features(),
- );
- let le_supported_states =
- assert_success!(hci.send(LeReadSupportedStatesBuilder {})).get_le_states();
- let le_connect_list_size =
- assert_success!(hci.send(LeReadConnectListSizeBuilder {})).get_connect_list_size();
- let le_resolving_list_size =
- assert_success!(hci.send(LeReadResolvingListSizeBuilder {})).get_resolving_list_size();
-
- let le_max_data_length = if commands.is_supported(OpCode::LeReadMaximumDataLength) {
- assert_success!(hci.send(LeReadMaximumDataLengthBuilder {}))
- .get_le_maximum_data_length()
- .clone()
- } else {
- LeMaximumDataLength {
- supported_max_rx_octets: 0,
- supported_max_rx_time: 0,
- supported_max_tx_octets: 0,
- supported_max_tx_time: 0,
- }
- };
-
- let le_suggested_default_data_length =
- if commands.is_supported(OpCode::LeReadSuggestedDefaultDataLength) {
- assert_success!(hci.send(LeReadSuggestedDefaultDataLengthBuilder {})).get_tx_octets()
- } else {
- 0
- };
-
- let le_max_advertising_data_length =
- if commands.is_supported(OpCode::LeReadMaximumAdvertisingDataLength) {
- assert_success!(hci.send(LeReadMaximumAdvertisingDataLengthBuilder {}))
- .get_maximum_advertising_data_length()
- } else {
- 31
- };
- let le_supported_advertising_sets =
- if commands.is_supported(OpCode::LeReadNumberOfSupportedAdvertisingSets) {
- assert_success!(hci.send(LeReadNumberOfSupportedAdvertisingSetsBuilder {}))
- .get_number_supported_advertising_sets()
- } else {
- 1
- };
- let le_periodic_advertiser_list_size =
- if commands.is_supported(OpCode::LeReadPeriodicAdvertisingListSize) {
- assert_success!(hci.send(LeReadPeriodicAdvertiserListSizeBuilder {}))
- .get_periodic_advertiser_list_size()
- } else {
- 0
- };
-
- let address = assert_success!(hci.send(ReadBdAddrBuilder {})).get_bd_addr();
-
- Arc::new(ControllerExports {
- name,
- address,
- version_info,
- commands,
- features,
- acl_buffer_length,
- acl_buffers,
- sco_buffer_length: buffer_size.get_synchronous_data_packet_length(),
- sco_buffers: buffer_size.get_total_num_synchronous_data_packets(),
- le_buffer_length,
- le_buffers,
- iso_buffer_length,
- iso_buffers,
- le_features,
- le_supported_states,
- le_connect_list_size,
- le_resolving_list_size,
- le_max_data_length,
- le_suggested_default_data_length,
- le_max_advertising_data_length,
- le_supported_advertising_sets,
- le_periodic_advertiser_list_size,
- })
-}
-
-async fn read_features(hci: &mut CommandSender) -> SupportedFeatures {
- let mut features = Vec::new();
- let mut page_number: u8 = 0;
- let mut max_page_number: u8 = 1;
- while page_number < max_page_number {
- let response = assert_success!(hci.send(ReadLocalExtendedFeaturesBuilder { page_number }));
- max_page_number = response.get_maximum_page_number();
- features.push(response.get_extended_lmp_features());
- page_number += 1;
- }
-
- SupportedFeatures::new(features)
-}
-
-/// Controller interface
-#[derive(Clone, Stoppable)]
-#[allow(missing_docs)]
-pub struct ControllerExports {
- pub name: String,
- pub address: Address,
- pub version_info: LocalVersionInformation,
- pub commands: SupportedCommands,
- pub features: SupportedFeatures,
- pub acl_buffer_length: u16,
- pub acl_buffers: u16,
- pub sco_buffer_length: u8,
- pub sco_buffers: u16,
- pub le_buffer_length: u16,
- pub le_buffers: u8,
- pub iso_buffer_length: u16,
- pub iso_buffers: u8,
- pub le_features: SupportedLeFeatures,
- pub le_supported_states: u64,
- pub le_connect_list_size: u8,
- pub le_resolving_list_size: u8,
- pub le_max_data_length: LeMaximumDataLength,
- pub le_suggested_default_data_length: u16,
- pub le_max_advertising_data_length: u16,
- pub le_supported_advertising_sets: u8,
- pub le_periodic_advertiser_list_size: u8,
-}
-
-/// Convenience struct for checking what commands are supported
-#[derive(Clone)]
-pub struct SupportedCommands {
- supported: [u8; 64],
-}
-
-impl SupportedCommands {
- /// Check whether a given opcode is supported by the controller
- pub fn is_supported(&self, opcode: OpCode) -> bool {
- let converted = OpCodeIndex::try_from(opcode);
- if converted.is_err() {
- return false;
- }
-
- let index = converted.unwrap().to_usize().unwrap();
-
- // OpCodeIndex is encoded as octet * 10 + bit for readability
- self.supported[index / 10] & (1 << (index % 10)) == 1
- }
-}
-
-macro_rules! supported_features {
- ($($id:ident => $page:literal : $bit:literal),*) => {
- /// Convenience struct for checking what features are supported
- #[derive(Clone)]
- #[allow(missing_docs)]
- pub struct SupportedFeatures {
- $(pub $id: bool,)*
- }
-
- impl SupportedFeatures {
- fn new(supported: Vec<u64>) -> Self {
- Self {
- $($id: *supported.get($page).unwrap_or(&0) & (1 << $bit) != 0,)*
- }
- }
- }
- }
-}
-
-supported_features! {
- three_slot_packets => 0:0,
- five_slot_packets => 0:1,
- role_switch => 0:5,
- hold_mode => 0:6,
- sniff_mode => 0:7,
- park_mode => 0:8,
- sco => 0:11,
- hv2_packets => 0:12,
- hv3_packets => 0:13,
- classic_2m_phy => 0:25,
- classic_3m_phy => 0:26,
- interlaced_inquiry_scan => 0:28,
- rssi_with_inquiry_results => 0:30,
- ev3_packets => 0:31,
- ev4_packets => 0:32,
- ev5_packets => 0:33,
- ble => 0:38,
- three_slot_edr_packets => 0:39,
- five_slot_edr_packets => 0:40,
- sniff_subrating => 0:41,
- encryption_pause => 0:42,
- esco_2m_phy => 0:45,
- esco_3m_phy => 0:46,
- three_slot_esco_edr_packets => 0:47,
- extended_inquiry_response => 0:48,
- simultaneous_le_bredr => 0:49,
- simple_pairing => 0:51,
- non_flushable_pb => 0:54,
- secure_connections => 2:8
-}
-
-macro_rules! supported_le_features {
- ($($id:ident => $bit:literal),*) => {
- /// Convenience struct for checking what features are supported
- #[derive(Clone)]
- #[allow(missing_docs)]
- pub struct SupportedLeFeatures {
- $(pub $id: bool,)*
- }
-
- impl SupportedLeFeatures {
- fn new(supported: u64) -> Self {
- Self {
- $($id: supported & (1 << $bit) != 0,)*
- }
- }
- }
- }
-}
-
-supported_le_features! {
- connection_parameter_request => 1,
- connection_parameters_request => 2,
- peripheral_initiated_feature_exchange => 3,
- packet_extension => 5,
- privacy => 6,
- ble_2m_phy => 8,
- ble_coded_phy => 11,
- extended_advertising => 12,
- periodic_advertising => 13,
- periodic_advertising_sync_transfer_sender => 24,
- periodic_advertising_sync_transfer_recipient => 25,
- connected_iso_stream_central => 28,
- connected_iso_stream_peripheral => 29,
- iso_broadcaster => 30,
- synchronized_receiver => 31
-}
-
-/// Convert a null terminated C string into a Rust String
-pub fn null_terminated_to_string(slice: &[u8]) -> String {
- let temp = std::str::from_utf8(slice).unwrap();
- temp[0..temp.find('\0').unwrap()].to_string()
-}
diff --git a/gd/rust/hci/src/controller_facade.rs b/gd/rust/hci/src/controller_facade.rs
deleted file mode 100644
index 52660c408..000000000
--- a/gd/rust/hci/src/controller_facade.rs
+++ /dev/null
@@ -1,72 +0,0 @@
-//! Controller facade
-
-use crate::controller::{null_terminated_to_string, ControllerExports};
-use crate::Hci;
-use bt_common::GrpcFacade;
-use bt_facade_proto::controller_facade::{AddressMsg, NameMsg};
-use bt_facade_proto::controller_facade_grpc::{create_controller_facade, ControllerFacade};
-use bt_facade_proto::empty::Empty;
-use bt_packets::hci::{ReadLocalNameBuilder, WriteLocalNameBuilder};
-use gddi::{module, provides, Stoppable};
-use grpcio::*;
-use std::sync::Arc;
-
-module! {
- controller_facade_module,
- providers {
- ControllerFacadeService => provide_facade,
- }
-}
-
-#[provides]
-async fn provide_facade(exports: Arc<ControllerExports>, hci: Hci) -> ControllerFacadeService {
- ControllerFacadeService { exports, hci }
-}
-
-/// Controller facade service
-#[allow(missing_docs)]
-#[derive(Clone, Stoppable)]
-pub struct ControllerFacadeService {
- pub exports: Arc<ControllerExports>,
- hci: Hci,
-}
-
-impl GrpcFacade for ControllerFacadeService {
- fn into_grpc(self) -> grpcio::Service {
- create_controller_facade(self)
- }
-}
-
-impl ControllerFacade for ControllerFacadeService {
- fn get_mac_address(&mut self, ctx: RpcContext<'_>, _req: Empty, sink: UnarySink<AddressMsg>) {
- let clone = self.clone();
- ctx.spawn(async move {
- let mut address = AddressMsg::new();
- address.set_address(clone.exports.address.bytes.to_vec());
- sink.success(address).await.unwrap();
- });
- }
-
- fn write_local_name(&mut self, ctx: RpcContext<'_>, req: NameMsg, sink: UnarySink<Empty>) {
- let mut clone = self.clone();
- let mut builder = WriteLocalNameBuilder { local_name: [0; 248] };
- builder.local_name[0..req.get_name().len()].copy_from_slice(req.get_name());
- ctx.spawn(async move {
- clone.hci.commands.send(builder.build()).await;
- sink.success(Empty::default()).await.unwrap();
- });
- }
-
- fn get_local_name(&mut self, ctx: RpcContext<'_>, _req: Empty, sink: UnarySink<NameMsg>) {
- let mut clone = self.clone();
- ctx.spawn(async move {
- let local_name = null_terminated_to_string(
- clone.hci.commands.send(ReadLocalNameBuilder {}).await.get_local_name(),
- )
- .into_bytes();
- let mut msg = NameMsg::new();
- msg.set_name(local_name);
- sink.success(msg).await.unwrap();
- });
- }
-}
diff --git a/gd/rust/hci/src/error.rs b/gd/rust/hci/src/error.rs
deleted file mode 100644
index 4ab44e31c..000000000
--- a/gd/rust/hci/src/error.rs
+++ /dev/null
@@ -1,24 +0,0 @@
-//! Defines the Result type and HCI errors
-
-use futures::channel::oneshot;
-use std::fmt::Debug;
-use thiserror::Error;
-use tokio::sync::mpsc::error::SendError;
-use tokio::sync::oneshot::error::RecvError;
-
-/// Result type
-pub type Result<T> = std::result::Result<T, Box<dyn std::error::Error + Send + Sync>>;
-
-/// HCI errors
-#[derive(Error, Debug)]
-pub enum HciError<T: Debug + 'static> {
- /// Error when sending on a bounded channel
- #[error("Error sending: {0}")]
- BoundedSendError(#[from] SendError<T>),
- /// Error when sending on a oneshot channel
- #[error("Error sending: {0}")]
- OneshotSendError(#[from] oneshot::Canceled),
- /// Error receiving from a channel
- #[error("Error receiving: {0}")]
- ChannelRecvError(#[from] RecvError),
-}
diff --git a/gd/rust/hci/src/facade.rs b/gd/rust/hci/src/facade.rs
deleted file mode 100644
index 367222000..000000000
--- a/gd/rust/hci/src/facade.rs
+++ /dev/null
@@ -1,143 +0,0 @@
-//! HCI layer facade
-
-use crate::{EventRegistry, RawCommandSender};
-use bt_common::GrpcFacade;
-use bt_facade_helpers::RxAdapter;
-use bt_facade_proto::common::Data;
-use bt_facade_proto::empty::Empty;
-use bt_facade_proto::hci_facade::EventRequest;
-use bt_facade_proto::hci_facade_grpc::{create_hci_facade, HciFacade};
-use bt_hal::AclHal;
-use bt_hal::IsoHal;
-use bt_packets::hci::{
- AclPacket, CommandPacket, EventCode, EventPacket, IsoPacket, LeMetaEventPacket, SubeventCode,
-};
-use gddi::{module, provides, Stoppable};
-use grpcio::*;
-use num_traits::FromPrimitive;
-use tokio::sync::mpsc::{channel, Sender};
-
-module! {
- facade_module,
- providers {
- HciFacadeService => provide_facade,
- }
-}
-
-#[provides]
-async fn provide_facade(
- commands: RawCommandSender,
- events: EventRegistry,
- acl: AclHal,
- iso: IsoHal,
-) -> HciFacadeService {
- let (evt_tx, evt_rx) = channel::<EventPacket>(10);
- let (le_evt_tx, le_evt_rx) = channel::<LeMetaEventPacket>(10);
- HciFacadeService {
- commands,
- events,
- evt_tx,
- evt_rx: RxAdapter::new(evt_rx),
- le_evt_tx,
- le_evt_rx: RxAdapter::new(le_evt_rx),
- acl_tx: acl.tx,
- acl_rx: RxAdapter::from_arc(acl.rx),
- iso_tx: iso.tx,
- iso_rx: RxAdapter::from_arc(iso.rx),
- }
-}
-
-/// HCI layer facade service
-#[allow(missing_docs)]
-#[derive(Clone, Stoppable)]
-pub struct HciFacadeService {
- pub commands: RawCommandSender,
- events: EventRegistry,
- evt_tx: Sender<EventPacket>,
- pub evt_rx: RxAdapter<EventPacket>,
- le_evt_tx: Sender<LeMetaEventPacket>,
- pub le_evt_rx: RxAdapter<LeMetaEventPacket>,
- pub acl_tx: Sender<AclPacket>,
- pub acl_rx: RxAdapter<AclPacket>,
- pub iso_tx: Sender<IsoPacket>,
- pub iso_rx: RxAdapter<IsoPacket>,
-}
-
-impl HciFacadeService {
- /// Register for the event & plug in the channel to get them back on
- pub async fn register_event(&mut self, code: u32) {
- self.events.register(EventCode::from_u32(code).unwrap(), self.evt_tx.clone()).await;
- }
-
- /// Register for the le event & plug in the channel to get them back on
- pub async fn register_le_event(&mut self, code: u32) {
- self.events
- .register_le(SubeventCode::from_u32(code).unwrap(), self.le_evt_tx.clone())
- .await;
- }
-}
-
-impl GrpcFacade for HciFacadeService {
- fn into_grpc(self) -> grpcio::Service {
- create_hci_facade(self)
- }
-}
-
-impl HciFacade for HciFacadeService {
- fn send_command(&mut self, ctx: RpcContext<'_>, mut data: Data, sink: UnarySink<Empty>) {
- let packet = CommandPacket::parse(&data.take_payload()).unwrap();
- let mut commands = self.commands.clone();
- let evt_tx = self.evt_tx.clone();
- ctx.spawn(async move {
- sink.success(Empty::default()).await.unwrap();
- let response = commands.send(packet).await.unwrap();
- evt_tx.send(response).await.unwrap();
- });
- }
-
- fn request_event(&mut self, ctx: RpcContext<'_>, req: EventRequest, sink: UnarySink<Empty>) {
- let mut clone = self.clone();
- ctx.spawn(async move {
- clone.register_event(req.get_code()).await;
- sink.success(Empty::default()).await.unwrap();
- });
- }
-
- fn request_le_subevent(
- &mut self,
- ctx: RpcContext<'_>,
- req: EventRequest,
- sink: UnarySink<Empty>,
- ) {
- let mut clone = self.clone();
- ctx.spawn(async move {
- clone.register_le_event(req.get_code()).await;
- sink.success(Empty::default()).await.unwrap();
- });
- }
-
- fn send_acl(&mut self, ctx: RpcContext<'_>, mut packet: Data, sink: UnarySink<Empty>) {
- let acl_tx = self.acl_tx.clone();
- ctx.spawn(async move {
- acl_tx.send(AclPacket::parse(&packet.take_payload()).unwrap()).await.unwrap();
- sink.success(Empty::default()).await.unwrap();
- });
- }
-
- fn stream_events(&mut self, ctx: RpcContext<'_>, _req: Empty, sink: ServerStreamingSink<Data>) {
- self.evt_rx.stream_grpc(ctx, sink);
- }
-
- fn stream_le_subevents(
- &mut self,
- ctx: RpcContext<'_>,
- _req: Empty,
- sink: ServerStreamingSink<Data>,
- ) {
- self.le_evt_rx.stream_grpc(ctx, sink);
- }
-
- fn stream_acl(&mut self, ctx: RpcContext<'_>, _req: Empty, sink: ServerStreamingSink<Data>) {
- self.acl_rx.stream_grpc(ctx, sink);
- }
-}
diff --git a/gd/rust/hci/src/lib.rs b/gd/rust/hci/src/lib.rs
deleted file mode 100644
index 428b5d101..000000000
--- a/gd/rust/hci/src/lib.rs
+++ /dev/null
@@ -1,250 +0,0 @@
-//! Host Controller Interface (HCI)
-
-/// HCI controller info
-pub mod controller;
-/// Controller facade service
-pub mod controller_facade;
-/// HCI errors
-pub mod error;
-/// HCI layer facade service
-pub mod facade;
-
-pub use bt_hci_custom_types::*;
-pub use controller::ControllerExports;
-
-use bt_common::time::Alarm;
-use bt_hal::ControlHal;
-use bt_packets::hci::EventChild::{
- CommandComplete, CommandStatus, LeMetaEvent, MaxSlotsChange, PageScanRepetitionModeChange,
- VendorSpecificEvent,
-};
-use bt_packets::hci::{
- CommandExpectations, CommandPacket, ErrorCode, EventCode, EventPacket, LeMetaEventPacket,
- ResetBuilder, SubeventCode,
-};
-use error::Result;
-use gddi::{module, part_out, provides, Stoppable};
-use log::error;
-use std::collections::HashMap;
-use std::sync::Arc;
-use std::time::Duration;
-use tokio::runtime::Runtime;
-use tokio::select;
-use tokio::sync::mpsc::{channel, Receiver, Sender};
-use tokio::sync::{oneshot, Mutex};
-
-module! {
- hci_module,
- submodules {
- facade::facade_module,
- controller_facade::controller_facade_module,
- controller::controller_module,
- },
- providers {
- parts Hci => provide_hci,
- },
-}
-
-#[part_out]
-#[derive(Clone, Stoppable)]
-struct Hci {
- raw_commands: RawCommandSender,
- commands: CommandSender,
- events: EventRegistry,
-}
-
-#[provides]
-async fn provide_hci(control: ControlHal, rt: Arc<Runtime>) -> Hci {
- let (cmd_tx, cmd_rx) = channel::<QueuedCommand>(10);
- let evt_handlers = Arc::new(Mutex::new(HashMap::new()));
- let le_evt_handlers = Arc::new(Mutex::new(HashMap::new()));
-
- rt.spawn(dispatch(
- evt_handlers.clone(),
- le_evt_handlers.clone(),
- control.rx,
- control.tx,
- cmd_rx,
- ));
-
- let raw_commands = RawCommandSender { cmd_tx };
- let mut commands = CommandSender { raw: raw_commands.clone() };
-
- assert!(
- commands.send(ResetBuilder {}).await.get_status() == ErrorCode::Success,
- "reset did not complete successfully"
- );
-
- Hci { raw_commands, commands, events: EventRegistry { evt_handlers, le_evt_handlers } }
-}
-
-#[derive(Debug)]
-struct QueuedCommand {
- cmd: CommandPacket,
- fut: oneshot::Sender<EventPacket>,
-}
-
-/// Sends raw commands. Only useful for facades & shims, or wrapped as a CommandSender.
-#[derive(Clone, Stoppable)]
-pub struct RawCommandSender {
- cmd_tx: Sender<QueuedCommand>,
-}
-
-impl RawCommandSender {
- /// Send a command, but does not automagically associate the expected returning event type.
- ///
- /// Only really useful for facades & shims.
- pub async fn send(&mut self, cmd: CommandPacket) -> Result<EventPacket> {
- let (tx, rx) = oneshot::channel::<EventPacket>();
- self.cmd_tx.send(QueuedCommand { cmd, fut: tx }).await?;
- let event = rx.await?;
- Ok(event)
- }
-}
-
-/// Sends commands to the controller
-#[derive(Clone, Stoppable)]
-pub struct CommandSender {
- raw: RawCommandSender,
-}
-
-impl CommandSender {
- /// Send a command to the controller, getting an expected response back
- pub async fn send<T: Into<CommandPacket> + CommandExpectations>(
- &mut self,
- cmd: T,
- ) -> T::ResponseType {
- T::_to_response_type(self.raw.send(cmd.into()).await.unwrap())
- }
-}
-
-/// Provides ability to register and unregister for HCI events
-#[derive(Clone, Stoppable)]
-pub struct EventRegistry {
- evt_handlers: Arc<Mutex<HashMap<EventCode, Sender<EventPacket>>>>,
- le_evt_handlers: Arc<Mutex<HashMap<SubeventCode, Sender<LeMetaEventPacket>>>>,
-}
-
-impl EventRegistry {
- /// Indicate interest in specific HCI events
- pub async fn register(&mut self, code: EventCode, sender: Sender<EventPacket>) {
- match code {
- EventCode::CommandStatus
- | EventCode::CommandComplete
- | EventCode::LeMetaEvent
- | EventCode::PageScanRepetitionModeChange
- | EventCode::MaxSlotsChange
- | EventCode::VendorSpecific => panic!("{:?} is a protected event", code),
- _ => {
- assert!(
- self.evt_handlers.lock().await.insert(code, sender).is_none(),
- "A handler for {:?} is already registered",
- code
- );
- }
- }
- }
-
- /// Remove interest in specific HCI events
- pub async fn unregister(&mut self, code: EventCode) {
- self.evt_handlers.lock().await.remove(&code);
- }
-
- /// Indicate interest in specific LE events
- pub async fn register_le(&mut self, code: SubeventCode, sender: Sender<LeMetaEventPacket>) {
- assert!(
- self.le_evt_handlers.lock().await.insert(code, sender).is_none(),
- "A handler for {:?} is already registered",
- code
- );
- }
-
- /// Remove interest in specific LE events
- pub async fn unregister_le(&mut self, code: SubeventCode) {
- self.le_evt_handlers.lock().await.remove(&code);
- }
-}
-
-async fn dispatch(
- evt_handlers: Arc<Mutex<HashMap<EventCode, Sender<EventPacket>>>>,
- le_evt_handlers: Arc<Mutex<HashMap<SubeventCode, Sender<LeMetaEventPacket>>>>,
- evt_rx: Arc<Mutex<Receiver<EventPacket>>>,
- cmd_tx: Sender<CommandPacket>,
- mut cmd_rx: Receiver<QueuedCommand>,
-) {
- let mut pending: Option<QueuedCommand> = None;
- let mut hci_timeout = Alarm::new();
- loop {
- select! {
- Some(evt) = consume(&evt_rx) => {
- match evt.specialize() {
- CommandStatus(evt) => {
- hci_timeout.cancel();
- let this_opcode = evt.get_command_op_code();
- match pending.take() {
- Some(QueuedCommand{cmd, fut}) if cmd.get_op_code() == this_opcode => {
- if let Err(e) = fut.send(evt.into()) {
- error!("failure dispatching command status {:?}", e);
- }
- },
- Some(QueuedCommand{cmd, ..}) => panic!("Waiting for {:?}, got {:?}", cmd.get_op_code(), this_opcode),
- None => panic!("Unexpected status event with opcode {:?}", this_opcode),
- }
- },
- CommandComplete(evt) => {
- hci_timeout.cancel();
- let this_opcode = evt.get_command_op_code();
- match pending.take() {
- Some(QueuedCommand{cmd, fut}) if cmd.get_op_code() == this_opcode => {
- if let Err(e) = fut.send(evt.into()) {
- error!("failure dispatching command complete {:?}", e);
- }
- },
- Some(QueuedCommand{cmd, ..}) => panic!("Waiting for {:?}, got {:?}", cmd.get_op_code(), this_opcode),
- None => panic!("Unexpected complete event with opcode {:?}", this_opcode),
- }
- },
- LeMetaEvent(evt) => {
- let code = evt.get_subevent_code();
- match le_evt_handlers.lock().await.get(&code) {
- Some(sender) => {
- if let Err(e) = sender.send(evt).await {
- error!("le meta event channel closed {:?}", e);
- }
- },
- None => panic!("Unhandled le subevent {:?}", code),
- }
- },
- PageScanRepetitionModeChange(_) => {},
- MaxSlotsChange(_) => {},
- VendorSpecificEvent(_) => {},
- _ => {
- let code = evt.get_event_code();
- match evt_handlers.lock().await.get(&code) {
- Some(sender) => {
- if let Err(e) = sender.send(evt).await {
- error!("hci event channel closed {:?}", e);
- }
- },
- None if code == EventCode::NumberOfCompletedPackets =>{},
- None => panic!("Unhandled event {:?}", code),
- }
- },
- }
- },
- Some(queued) = cmd_rx.recv(), if pending.is_none() => {
- if let Err(e) = cmd_tx.send(queued.cmd.clone()).await {
- error!("command queue closed: {:?}", e);
- }
- hci_timeout.reset(Duration::from_secs(2));
- pending = Some(queued);
- },
- _ = hci_timeout.expired() => panic!("Timed out waiting for {:?}", pending.unwrap().cmd.get_op_code()),
- else => break,
- }
- }
-}
-
-async fn consume(evt_rx: &Arc<Mutex<Receiver<EventPacket>>>) -> Option<EventPacket> {
- evt_rx.lock().await.recv().await
-}
diff --git a/gd/rust/link/Android.bp b/gd/rust/link/Android.bp
deleted file mode 100644
index c88ff793c..000000000
--- a/gd/rust/link/Android.bp
+++ /dev/null
@@ -1,37 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-rust_library {
- name: "libbt_link",
- defaults: ["gd_rust_defaults"],
- crate_name: "bt_link",
- srcs: ["src/lib.rs"],
- edition: "2018",
- rustlibs: [
- "libbt_hci",
- "libbt_hal",
- "libbt_facade_proto",
- "libbt_packets",
- "libbytes",
- "libfutures",
- "libgrpcio",
- "libnum_traits",
- "libthiserror",
- "libtokio",
- "libtokio_stream",
- "libprotobuf",
- "libgddi",
- "liblog_rust",
- "libbt_common",
- "libbt_hci_custom_types",
- ],
- proc_macros: [
- "libnum_derive",
- ],
-}
diff --git a/gd/rust/link/Cargo.toml b/gd/rust/link/Cargo.toml
deleted file mode 100644
index 1bde4aa6d..000000000
--- a/gd/rust/link/Cargo.toml
+++ /dev/null
@@ -1,46 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bt_link"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-# bt deps
-bt_common = { path = "../common" }
-bt_hci = { path = "../hci" }
-bt_hci_custom_types = { path = "../hci/custom_types" }
-bt_hal = { path = "../hal" }
-bt_facade_proto = { path = "../facade_proto" }
-bt_packets = { path = "../packets" }
-gddi = { path = "../gddi" }
-
-# external deps
-bytes = "*"
-futures = "*"
-grpcio = "*"
-log = "*"
-num-traits = "*"
-protobuf = "*"
-thiserror = "*"
-tokio = { version = "*", features = ['bytes', 'net'] }
-tokio-stream = "*"
-
-# macro deps
-num-derive = "*"
-
-[lib]
-crate-type = ["rlib"]
diff --git a/gd/rust/link/src/acl/classic/facade.rs b/gd/rust/link/src/acl/classic/facade.rs
deleted file mode 100644
index 313183beb..000000000
--- a/gd/rust/link/src/acl/classic/facade.rs
+++ /dev/null
@@ -1,91 +0,0 @@
-//! Classic ACL facade
-
-use crate::acl::classic::AclManager;
-
-module! {
- facade_module,
- providers {
- ClassicAclFacadeService => provide_facade,
- }
-}
-
-#[provides]
-async fn provide_facade(acl: AclManager) -> ClassicAclFacadeService {
- ClassicAclFacadeService { acl }
-}
-
-pub struct ClassicAclFacadeService {
- acl: AclManager,
-}
-
-impl AclManagerFacade for ClassicAclFacadeService {
- fn create_connection(
- &mut self,
- _ctx: RpcContext<'_>,
- mut _data: ConnectionMsg,
- _sink: ServerStreamingSink<ConnectionEvent>,
- ) {
- unimplemented!();
- }
-
- fn cancel_connection(
- &mut self,
- _ctx: RpcContext<'_>,
- mut _data: ConnectionMsg,
- _sink: UnarySink<Empty>,
- ) {
- unimplemented!();
- }
-
- fn disconnect(&mut self, _ctx: RpcContext<'_>, mut _data: HandleMsg, _sink: UnarySink<Empty>) {
- unimplemented!();
- }
-
- fn disconnect(&mut self, _ctx: RpcContext<'_>, mut _data: PolicyMsg, _sink: UnarySink<Empty>) {
- unimplemented!();
- }
-
- fn authentication_requested(
- &mut self,
- _ctx: RpcContext<'_>,
- mut _data: HandleMsg,
- _sink: UnarySink<Empty>,
- ) {
- unimplemented!();
- }
-
- fn connection_command(
- &mut self,
- _ctx: RpcContext<'_>,
- mut _data: ConnectionCommandMsg,
- _sink: UnarySink<Empty>,
- ) {
- unimplemented!();
- }
-
- fn switch_role(&mut self, _ctx: RpcContext<'_>, mut _data: RoleMsg, _sink: UnarySink<Empty>) {
- unimplemented!();
- }
-
- fn send_acl_data(&mut self, _ctx: RpcContext<'_>, mut _data: AclData, _sink: UnarySink<Empty>) {
- unimplemented!();
- }
-
- fn fetch_acl_data(
- &mut self,
- _ctx: RpcContext<'_>,
- mut _data: HandleMsg,
- _sink: ServerStreamingSink<AclData>,
- ) {
- unimplemented!();
- }
-
- fn fetch_incoming_connection(
- &mut self,
- _ctx: RpcContext<'_>,
- mut _data: Empty,
- _sink: ServerStreamingSink<ConnectionEvent>,
- ) {
- unimplemented!();
- }
-}
diff --git a/gd/rust/link/src/acl/classic/mod.rs b/gd/rust/link/src/acl/classic/mod.rs
deleted file mode 100644
index b92e2fa93..000000000
--- a/gd/rust/link/src/acl/classic/mod.rs
+++ /dev/null
@@ -1,296 +0,0 @@
-//! Classic ACL manager
-
-use crate::acl::core;
-use bt_common::Bluetooth;
-use bt_hci::{Address, CommandSender, EventRegistry};
-use bt_packets::hci::EventChild::{
- AuthenticationComplete, ConnectionComplete, DisconnectionComplete,
-};
-use bt_packets::hci::{
- AcceptConnectionRequestBuilder, AcceptConnectionRequestRole, ClockOffsetValid,
- CreateConnectionBuilder, CreateConnectionCancelBuilder, CreateConnectionRoleSwitch,
- DisconnectBuilder, DisconnectReason, ErrorCode, EventChild, EventCode, EventPacket,
- PageScanRepetitionMode, RejectConnectionReason, RejectConnectionRequestBuilder, Role,
-};
-use bytes::Bytes;
-use gddi::{module, provides, Stoppable};
-use log::warn;
-use std::collections::HashMap;
-use std::sync::Arc;
-use tokio::runtime::Runtime;
-use tokio::select;
-use tokio::sync::mpsc::{channel, Receiver, Sender};
-use tokio::sync::{oneshot, Mutex};
-
-module! {
- classic_acl_module,
- providers {
- AclManager => provide_acl_manager,
- },
-}
-
-/// Classic ACL manager
-#[derive(Clone, Stoppable)]
-pub struct AclManager {
- req_tx: Sender<Request>,
- /// High level events from AclManager
- pub evt_rx: Arc<Mutex<Receiver<Event>>>,
-}
-
-/// Events generated by AclManager
-#[derive(Debug)]
-pub enum Event {
- /// Connection was successful - provides the newly created connection
- ConnectSuccess(Connection),
- /// Locally initialted connection was not successful - indicates address & reason
- ConnectFail {
- /// Address of the failed connection
- addr: Address,
- /// Reason of the failed connection
- reason: ErrorCode,
- },
-}
-
-/// A classic ACL connection
-#[derive(Debug)]
-pub struct Connection {
- addr: Address,
- rx: Receiver<Bytes>,
- tx: Sender<Bytes>,
- shared: Arc<Mutex<ConnectionShared>>,
- requests: Sender<ConnectionRequest>,
- evt_rx: Receiver<ConnectionEvent>,
-}
-
-/// Events generated by Connection
-#[derive(Debug)]
-pub enum ConnectionEvent {
- /// Connection was disconnected with the specified code.
- Disconnected(ErrorCode),
- /// Connection authentication was completed
- AuthenticationComplete,
-}
-
-impl Connection {
- /// Disconnect the connection with the specified reason.
- pub async fn disconnect(&mut self, reason: DisconnectReason) {
- let (tx, rx) = oneshot::channel();
- self.requests.send(ConnectionRequest::Disconnect { reason, fut: tx }).await.unwrap();
- rx.await.unwrap()
- }
-}
-
-#[derive(Debug)]
-enum ConnectionRequest {
- Disconnect { reason: DisconnectReason, fut: oneshot::Sender<()> },
-}
-
-struct ConnectionInternal {
- addr: Address,
- #[allow(dead_code)]
- shared: Arc<Mutex<ConnectionShared>>,
- hci_evt_tx: Sender<EventPacket>,
-}
-
-#[derive(Debug)]
-struct ConnectionShared {
- role: Role,
-}
-
-impl AclManager {
- /// Connect to the specified address, or queue it if a connection is already pending
- pub async fn connect(&mut self, addr: Address) {
- self.req_tx.send(Request::Connect { addr }).await.unwrap();
- }
-
- /// Cancel the connection to the specified address, if it is pending
- pub async fn cancel_connect(&mut self, addr: Address) {
- let (tx, rx) = oneshot::channel();
- self.req_tx.send(Request::CancelConnect { addr, fut: tx }).await.unwrap();
- rx.await.unwrap();
- }
-}
-
-#[derive(Debug)]
-enum Request {
- Connect { addr: Address },
- CancelConnect { addr: Address, fut: oneshot::Sender<()> },
-}
-
-#[derive(Eq, PartialEq)]
-enum PendingConnect {
- Outgoing(Address),
- Incoming(Address),
- None,
-}
-
-impl PendingConnect {
- fn take(&mut self) -> Self {
- std::mem::replace(self, PendingConnect::None)
- }
-}
-
-#[provides]
-async fn provide_acl_manager(
- mut hci: CommandSender,
- mut events: EventRegistry,
- mut dispatch: core::AclDispatch,
- rt: Arc<Runtime>,
-) -> AclManager {
- let (req_tx, mut req_rx) = channel::<Request>(10);
- let (conn_evt_tx, conn_evt_rx) = channel::<Event>(10);
- let local_rt = rt.clone();
-
- local_rt.spawn(async move {
- let connections: Arc<Mutex<HashMap<u16, ConnectionInternal>>> = Arc::new(Mutex::new(HashMap::new()));
- let mut connect_queue: Vec<Address> = Vec::new();
- let mut pending = PendingConnect::None;
-
- let (evt_tx, mut evt_rx) = channel(3);
- events.register(EventCode::ConnectionComplete, evt_tx.clone()).await;
- events.register(EventCode::ConnectionRequest, evt_tx.clone()).await;
- events.register(EventCode::AuthenticationComplete, evt_tx).await;
-
- loop {
- select! {
- Some(req) = req_rx.recv() => {
- match req {
- Request::Connect { addr } => {
- if connections.lock().await.values().any(|c| c.addr == addr) {
- warn!("already connected: {}", addr);
- return;
- }
- if let PendingConnect::None = pending {
- pending = PendingConnect::Outgoing(addr);
- hci.send(build_create_connection(addr)).await;
- } else {
- connect_queue.insert(0, addr);
- }
- },
- Request::CancelConnect { addr, fut } => {
- connect_queue.retain(|p| *p != addr);
- if pending == PendingConnect::Outgoing(addr) {
- hci.send(CreateConnectionCancelBuilder { bd_addr: addr }).await;
- }
- fut.send(()).unwrap();
- }
- }
- }
- Some(evt) = evt_rx.recv() => {
- match evt.specialize() {
- ConnectionComplete(evt) => {
- let addr = evt.get_bd_addr();
- let status = evt.get_status();
- let handle = evt.get_connection_handle();
- let role = match pending.take() {
- PendingConnect::Outgoing(a) if a == addr => Role::Central,
- PendingConnect::Incoming(a) if a == addr => Role::Peripheral,
- _ => panic!("No prior connection request for {}", addr),
- };
-
- match status {
- ErrorCode::Success => {
- let mut core_conn = dispatch.register(handle, Bluetooth::Classic).await;
- let shared = Arc::new(Mutex::new(ConnectionShared { role }));
- let (evt_tx, evt_rx) = channel(10);
- let (req_tx, req_rx) = channel(10);
- let connection = Connection {
- addr,
- shared: shared.clone(),
- rx: core_conn.rx.take().unwrap(),
- tx: core_conn.tx.take().unwrap(),
- requests: req_tx,
- evt_rx,
- };
- let connection_internal = ConnectionInternal {
- addr,
- shared,
- hci_evt_tx: core_conn.evt_tx.clone(),
- };
-
- assert!(connections.lock().await.insert(handle, connection_internal).is_none());
- rt.spawn(run_connection(handle, evt_tx, req_rx, core_conn, connections.clone(), hci.clone()));
- conn_evt_tx.send(Event::ConnectSuccess(connection)).await.unwrap();
- },
- _ => conn_evt_tx.send(Event::ConnectFail { addr, reason: status }).await.unwrap(),
- }
- },
- EventChild::ConnectionRequest(evt) => {
- let addr = evt.get_bd_addr();
- pending = PendingConnect::Incoming(addr);
- if connections.lock().await.values().any(|c| c.addr == addr) {
- hci.send(RejectConnectionRequestBuilder {
- bd_addr: addr,
- reason: RejectConnectionReason::UnacceptableBdAddr
- }).await;
- } else {
- hci.send(AcceptConnectionRequestBuilder {
- bd_addr: addr,
- role: AcceptConnectionRequestRole::BecomeCentral
- }).await;
- }
- },
- AuthenticationComplete(e) => dispatch_to(e.get_connection_handle(), &connections, evt).await,
- _ => unimplemented!(),
- }
- }
- }
- }
- });
-
- AclManager { req_tx, evt_rx: Arc::new(Mutex::new(conn_evt_rx)) }
-}
-
-fn build_create_connection(bd_addr: Address) -> CreateConnectionBuilder {
- CreateConnectionBuilder {
- bd_addr,
- packet_type: 0x4408 /* DM 1,3,5 */ | 0x8810, /*DH 1,3,5 */
- page_scan_repetition_mode: PageScanRepetitionMode::R1,
- clock_offset: 0,
- clock_offset_valid: ClockOffsetValid::Invalid,
- allow_role_switch: CreateConnectionRoleSwitch::AllowRoleSwitch,
- }
-}
-
-async fn dispatch_to(
- handle: u16,
- connections: &Arc<Mutex<HashMap<u16, ConnectionInternal>>>,
- event: EventPacket,
-) {
- if let Some(c) = connections.lock().await.get_mut(&handle) {
- c.hci_evt_tx.send(event).await.unwrap();
- }
-}
-
-async fn run_connection(
- handle: u16,
- evt_tx: Sender<ConnectionEvent>,
- mut req_rx: Receiver<ConnectionRequest>,
- mut core: core::Connection,
- connections: Arc<Mutex<HashMap<u16, ConnectionInternal>>>,
- mut hci: CommandSender,
-) {
- loop {
- select! {
- Some(evt) = core.evt_rx.recv() => {
- match evt.specialize() {
- DisconnectionComplete(evt) => {
- connections.lock().await.remove(&handle);
- evt_tx.send(ConnectionEvent::Disconnected(evt.get_reason())).await.unwrap();
- return; // At this point, there is nothing more to run on the connection.
- },
- AuthenticationComplete(_) => evt_tx.send(ConnectionEvent::AuthenticationComplete).await.unwrap(),
- _ => unimplemented!(),
- }
- },
- Some(req) = req_rx.recv() => {
- match req {
- ConnectionRequest::Disconnect{reason, fut} => {
- hci.send(DisconnectBuilder { connection_handle: handle, reason }).await;
- fut.send(()).unwrap();
- }
- }
- },
- }
- }
-}
diff --git a/gd/rust/link/src/acl/core.rs b/gd/rust/link/src/acl/core.rs
deleted file mode 100644
index 1e837adf7..000000000
--- a/gd/rust/link/src/acl/core.rs
+++ /dev/null
@@ -1,182 +0,0 @@
-//! ACL core dispatch shared between LE and classic
-
-use crate::acl::fragment::{fragmenting_stream, Reassembler};
-use bt_common::Bluetooth::{self, Classic, Le};
-use bt_hal::AclHal;
-use bt_hci::{ControllerExports, EventRegistry};
-use bt_packets::hci::EventChild::{DisconnectionComplete, NumberOfCompletedPackets};
-use bt_packets::hci::{AclPacket, EventCode, EventPacket};
-use bytes::Bytes;
-use futures::stream::{SelectAll, StreamExt};
-use gddi::{module, provides, Stoppable};
-use log::info;
-use std::collections::HashMap;
-use std::sync::Arc;
-use tokio::runtime::Runtime;
-use tokio::select;
-use tokio::sync::mpsc::{channel, Receiver, Sender};
-use tokio::sync::{oneshot, Mutex};
-use tokio_stream::wrappers::ReceiverStream;
-
-module! {
- core_module,
- providers {
- AclDispatch => provide_acl_dispatch,
- },
-}
-
-/// A basic ACL connection
-#[derive(Debug)]
-pub struct Connection {
- pub rx: Option<Receiver<Bytes>>,
- pub tx: Option<Sender<Bytes>>,
- handle: u16,
- requests: Sender<Request>,
- pub evt_rx: Receiver<EventPacket>,
- pub evt_tx: Sender<EventPacket>,
-}
-
-struct ConnectionInternal {
- reassembler: Reassembler,
- bt: Bluetooth,
- close_tx: oneshot::Sender<()>,
- evt_tx: Sender<EventPacket>,
-}
-
-/// Manages rx and tx for open ACL connections
-#[derive(Clone, Stoppable)]
-pub struct AclDispatch {
- requests: Sender<Request>,
-}
-
-impl AclDispatch {
- /// Register the provided connection with the ACL dispatch
- #[allow(dead_code)]
- pub async fn register(&mut self, handle: u16, bt: Bluetooth) -> Connection {
- let (tx, rx) = oneshot::channel();
- self.requests.send(Request::Register { handle, bt, fut: tx }).await.unwrap();
- rx.await.unwrap()
- }
-}
-
-#[derive(Debug)]
-enum Request {
- Register { handle: u16, bt: Bluetooth, fut: oneshot::Sender<Connection> },
-}
-
-const QCOM_DEBUG_HANDLE: u16 = 0xedc;
-
-#[provides]
-async fn provide_acl_dispatch(
- acl: AclHal,
- controller: Arc<ControllerExports>,
- mut events: EventRegistry,
- rt: Arc<Runtime>,
-) -> AclDispatch {
- let (req_tx, mut req_rx) = channel::<Request>(10);
- let req_tx_clone = req_tx.clone();
-
- rt.spawn(async move {
- let mut connections: HashMap<u16, ConnectionInternal> = HashMap::new();
- let mut classic_outbound = SelectAll::new();
- let mut classic_credits = controller.acl_buffers;
- let mut le_outbound = SelectAll::new();
- let mut le_credits: u16 = controller.le_buffers.into();
-
- let (evt_tx, mut evt_rx) = channel(3);
- events.register(EventCode::NumberOfCompletedPackets, evt_tx.clone()).await;
- events.register(EventCode::DisconnectionComplete, evt_tx).await;
-
- loop {
- select! {
- Some(req) = req_rx.recv() => {
- match req {
- Request::Register { handle, bt, fut } => {
- let (out_tx, out_rx) = channel(10);
- let (in_tx, in_rx) = channel(10);
- let (evt_tx, evt_rx) = channel(3);
- let (close_tx, close_rx) = oneshot::channel();
-
- assert!(connections.insert(
- handle,
- ConnectionInternal {
- reassembler: Reassembler::new(out_tx),
- bt,
- close_tx,
- evt_tx: evt_tx.clone(),
- }).is_none());
-
- match bt {
- Classic => {
- classic_outbound.push(fragmenting_stream(
- ReceiverStream::new(in_rx), controller.acl_buffer_length.into(), handle, bt, close_rx));
- },
- Le => {
- le_outbound.push(fragmenting_stream(
- ReceiverStream::new(in_rx), controller.le_buffer_length.into(), handle, bt, close_rx));
- },
- }
-
- fut.send(Connection {
- rx: Some(out_rx),
- tx: Some(in_tx),
- handle,
- requests: req_tx_clone.clone(),
- evt_rx,
- evt_tx,
- }).unwrap();
- },
- }
- },
- Some(p) = consume(&acl.rx) => {
- match connections.get_mut(&p.get_handle()) {
- Some(c) => c.reassembler.on_packet(p).await,
- None if p.get_handle() == QCOM_DEBUG_HANDLE => {},
- None => info!("no acl for {}", p.get_handle()),
- }
- },
- Some(p) = classic_outbound.next(), if classic_credits > 0 => {
- acl.tx.send(p).await.unwrap();
- classic_credits -= 1;
- },
- Some(p) = le_outbound.next(), if le_credits > 0 => {
- acl.tx.send(p).await.unwrap();
- le_credits -= 1;
- },
- Some(evt) = evt_rx.recv() => {
- match evt.specialize() {
- NumberOfCompletedPackets(evt) => {
- for entry in evt.get_completed_packets() {
- match connections.get(&entry.connection_handle) {
- Some(conn) => {
- let credits = entry.host_num_of_completed_packets;
- match conn.bt {
- Classic => classic_credits += credits,
- Le => le_credits += credits,
- }
- assert!(classic_credits <= controller.acl_buffers);
- assert!(le_credits <= controller.le_buffers.into());
- },
- None => info!("dropping credits for unknown connection {}", entry.connection_handle),
- }
- }
- },
- DisconnectionComplete(evt) => {
- if let Some(c) = connections.remove(&evt.get_connection_handle()) {
- c.close_tx.send(()).unwrap();
- c.evt_tx.send(evt.into()).await.unwrap();
- }
- },
- _ => unimplemented!(),
- }
- },
- }
- }
- });
-
- AclDispatch { requests: req_tx }
-}
-
-async fn consume(rx: &Arc<Mutex<Receiver<AclPacket>>>) -> Option<AclPacket> {
- rx.lock().await.recv().await
-}
diff --git a/gd/rust/link/src/acl/fragment.rs b/gd/rust/link/src/acl/fragment.rs
deleted file mode 100644
index 6e52cd50c..000000000
--- a/gd/rust/link/src/acl/fragment.rs
+++ /dev/null
@@ -1,121 +0,0 @@
-//! Handles fragmentation & reassembly of ACL packets into whole L2CAP payloads
-
-use bt_common::Bluetooth;
-use bt_packets::hci::PacketBoundaryFlag::{
- ContinuingFragment, FirstAutomaticallyFlushable, FirstNonAutomaticallyFlushable,
-};
-use bt_packets::hci::{AclBuilder, AclChild, AclPacket, BroadcastFlag};
-use bytes::{Buf, Bytes, BytesMut};
-use futures::stream::{self, StreamExt};
-use log::{error, info, warn};
-use tokio::sync::mpsc::Sender;
-use tokio::sync::oneshot;
-use tokio_stream::wrappers::ReceiverStream;
-
-const L2CAP_BASIC_FRAME_HEADER_LEN: usize = 4;
-
-pub struct Reassembler {
- buffer: Option<BytesMut>,
- remaining: usize,
- out: Sender<Bytes>,
-}
-
-impl Reassembler {
- /// Create a new reassembler
- pub fn new(out: Sender<Bytes>) -> Self {
- Self { buffer: None, remaining: 0, out }
- }
-
- /// Injest the packet and send out if fully reassembled
- pub async fn on_packet(&mut self, packet: AclPacket) {
- let payload = match packet.specialize() {
- AclChild::Payload(payload) => payload,
- AclChild::None => {
- info!("dropping ACL packet with empty payload");
- return;
- }
- };
-
- if let BroadcastFlag::ActivePeripheralBroadcast = packet.get_broadcast_flag() {
- // we do not accept broadcast packets
- return;
- }
-
- match packet.get_packet_boundary_flag() {
- FirstNonAutomaticallyFlushable => error!("not allowed to send FIRST_NON_AUTOMATICALLY_FLUSHABLE to host except loopback mode"),
- FirstAutomaticallyFlushable => {
- if self.buffer.take().is_some() {
- error!("got a start packet without finishing previous reassembly - dropping previous");
- }
-
- let full_size = get_l2cap_pdu_size(&payload);
- self.remaining = full_size - (payload.len() - L2CAP_BASIC_FRAME_HEADER_LEN);
- if self.remaining > 0 {
- let mut buffer = BytesMut::with_capacity(full_size);
- buffer.extend_from_slice(&payload[..]);
- self.buffer = Some(buffer);
- } else {
- self.out.send(payload).await.unwrap();
- }
- },
- ContinuingFragment => {
- match self.buffer.take() {
- None => warn!("got continuation packet without pending reassembly"),
- Some(_) if self.remaining < payload.len() => warn!("remote sent unexpected L2CAP PDU - dropping entire packet"),
- Some(mut buffer) => {
- self.remaining -= payload.len();
- buffer.extend_from_slice(&payload[..]);
- if self.remaining == 0 {
- self.out.send(buffer.freeze()).await.unwrap();
- } else {
- self.buffer = Some(buffer);
- }
- }
- }
- },
- }
- }
-}
-
-fn get_l2cap_pdu_size(first_packet: &Bytes) -> usize {
- if first_packet.len() <= L2CAP_BASIC_FRAME_HEADER_LEN {
- error!("invalid l2cap starting packet");
-
- 0
- } else {
- (&first_packet[..]).get_u16_le() as usize
- }
-}
-
-pub fn fragmenting_stream(
- rx: ReceiverStream<Bytes>,
- mtu: usize,
- handle: u16,
- bt: Bluetooth,
- close_rx: oneshot::Receiver<()>,
-) -> std::pin::Pin<
- std::boxed::Box<dyn futures::Stream<Item = bt_packets::hci::AclPacket> + std::marker::Send>,
-> {
- rx.flat_map(move |data| {
- stream::iter(
- data.chunks(mtu)
- .enumerate()
- .map(move |(i, chunk)| {
- AclBuilder {
- handle,
- packet_boundary_flag: match bt {
- Bluetooth::Classic if i == 0 => FirstAutomaticallyFlushable,
- Bluetooth::Le if i == 0 => FirstNonAutomaticallyFlushable,
- _ => ContinuingFragment,
- },
- broadcast_flag: BroadcastFlag::PointToPoint,
- payload: Some(Bytes::copy_from_slice(chunk)),
- }
- .build()
- })
- .collect::<Vec<AclPacket>>(),
- )
- })
- .take_until(close_rx)
- .boxed()
-}
diff --git a/gd/rust/link/src/acl/mod.rs b/gd/rust/link/src/acl/mod.rs
deleted file mode 100644
index f4134513c..000000000
--- a/gd/rust/link/src/acl/mod.rs
+++ /dev/null
@@ -1,16 +0,0 @@
-//! ACL management
-
-/// Exposes classic ACL functionality
-pub mod classic;
-mod core;
-mod fragment;
-
-use gddi::module;
-
-module! {
- acl_module,
- submodules {
- classic::classic_acl_module,
- core::core_module,
- },
-}
diff --git a/gd/rust/link/src/lib.rs b/gd/rust/link/src/lib.rs
deleted file mode 100644
index 1255344bd..000000000
--- a/gd/rust/link/src/lib.rs
+++ /dev/null
@@ -1,13 +0,0 @@
-//! link management
-
-/// Exposes ACL functionality
-pub mod acl;
-
-use gddi::module;
-
-module! {
- link_module,
- submodules {
- acl::acl_module,
- },
-}
diff --git a/gd/rust/linux/adapter/Cargo.toml b/gd/rust/linux/adapter/Cargo.toml
deleted file mode 100644
index 3c0932e1d..000000000
--- a/gd/rust/linux/adapter/Cargo.toml
+++ /dev/null
@@ -1,37 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bluetooth"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-# BT dependencies
-bt_topshim = { path = "../../topshim" }
-bt_shim = { path = "../../shim" }
-
-num-traits = "*"
-num-derive = "*"
-tokio = { version = "1.0", features = ['bytes', 'fs', 'io-util', 'libc', 'macros', 'memchr', 'mio', 'net', 'num_cpus', 'rt', 'rt-multi-thread', 'sync', 'time', 'tokio-macros'] }
-tokio-stream = "0.1"
-
-[build-dependencies]
-pkg-config = "0.3"
-
-[[bin]]
-name = "bluetoothd"
-path = "src/main.rs"
-build = "build.rs"
diff --git a/gd/rust/linux/adapter/build.rs b/gd/rust/linux/adapter/build.rs
deleted file mode 100644
index 1c58ead43..000000000
--- a/gd/rust/linux/adapter/build.rs
+++ /dev/null
@@ -1,25 +0,0 @@
-use pkg_config::Config;
-
-fn main() {
- // The main linking point with c++ code is the libbluetooth-static.a
- // These includes all the symbols built via C++ but doesn't include other
- // links (i.e. pkg-config)
- println!("cargo:rustc-link-lib=static=bluetooth-static");
-
- // A few dynamic links
- println!("cargo:rustc-link-lib=dylib=flatbuffers");
- println!("cargo:rustc-link-lib=dylib=protobuf");
- println!("cargo:rustc-link-lib=dylib=resolv");
-
- // Clang requires -lc++ instead of -lstdc++
- println!("cargo:rustc-link-lib=c++");
-
- // A few more dependencies from pkg-config. These aren't included as part of
- // the libbluetooth-static.a
- Config::new().probe("libchrome").unwrap();
- Config::new().probe("libmodp_b64").unwrap();
- Config::new().probe("tinyxml2").unwrap();
-
- println!("cargo:rerun-if-changed=build.rs");
- println!("cargo:rerun-if-changed=libbluetooth-static.a");
-}
diff --git a/gd/rust/linux/adapter/src/main.rs b/gd/rust/linux/adapter/src/main.rs
deleted file mode 100644
index 5635538dc..000000000
--- a/gd/rust/linux/adapter/src/main.rs
+++ /dev/null
@@ -1,182 +0,0 @@
-use bt_topshim::btif;
-use bt_topshim::btif::{ffi, BluetoothCallbacks, BluetoothInterface};
-use bt_topshim::topstack;
-use num_traits::{FromPrimitive, ToPrimitive};
-use std::convert::TryFrom;
-use std::env;
-use std::sync::Arc;
-use std::time::Duration;
-use tokio::sync::mpsc;
-use tokio::sync::mpsc::{Receiver, Sender};
-use tokio::time::sleep;
-
-// DO NOT REMOVE
-// Required so that bt_shim is linked into the final image
-extern crate bt_shim;
-
-enum Callbacks {
- AdapterStateChanged(btif::BtState),
- AdapterPropertiesChanged(i32, i32, Vec<ffi::BtProperty>),
- RemoteDevicePropertiesChanged(i32, ffi::RustRawAddress, i32, Vec<ffi::BtProperty>),
- DeviceFound(i32, Vec<ffi::BtProperty>),
- DiscoveryStateChanged(btif::BtDiscoveryState),
-}
-struct Context {
- tx: Sender<Callbacks>,
- rx: Receiver<Callbacks>,
- callbacks: Arc<BluetoothCallbacks>,
- intf: BluetoothInterface,
-}
-
-fn make_context(intf: BluetoothInterface) -> Context {
- let (tx, rx) = mpsc::channel::<Callbacks>(1);
-
- let (tx1, tx2, tx3, tx4, tx5) = (tx.clone(), tx.clone(), tx.clone(), tx.clone(), tx.clone());
- let cb = Arc::new(BluetoothCallbacks {
- adapter_state_changed: Box::new(move |state| {
- let txl = tx1.clone();
- topstack::get_runtime().spawn(async move {
- txl.send(Callbacks::AdapterStateChanged(state)).await;
- });
- }),
- adapter_properties_changed: Box::new(move |status, count, props| {
- let txl = tx2.clone();
- topstack::get_runtime().spawn(async move {
- txl.send(Callbacks::AdapterPropertiesChanged(status, count, props)).await;
- });
- }),
- remote_device_properties_changed: Box::new(move |status, address, count, props| {
- let txl = tx5.clone();
- topstack::get_runtime().spawn(async move {
- txl.send(Callbacks::RemoteDevicePropertiesChanged(status, address, count, props));
- });
- }),
- device_found: Box::new(move |count, props| {
- let txl = tx3.clone();
- topstack::get_runtime().spawn(async move {
- txl.send(Callbacks::DeviceFound(count, props)).await;
- });
- }),
- discovery_state_changed: Box::new(move |state| {
- let txl = tx4.clone();
- topstack::get_runtime().spawn(async move {
- txl.send(Callbacks::DiscoveryStateChanged(state)).await;
- });
- }),
- pin_request: Box::new(move |_address, _bdname, _cod, _min_16_digit| {
- println!("Pin request callback");
- }),
- ssp_request: Box::new(move |_address, _bdname, _cod, _variant, _passkey| {
- println!("Ssp request callback");
- }),
- bond_state_changed: Box::new(move |_status, _address, _state| {
- println!("Bond state changed");
- }),
- acl_state_changed: Box::new(move |_status, _address, _state, _hci_reason| {
- println!("Acl state changed");
- }),
- });
-
- return Context { tx, rx, callbacks: cb, intf };
-}
-
-async fn mainloop(context: &mut Context) {
- 'main: while let Some(cb) = context.rx.recv().await {
- match cb {
- Callbacks::AdapterStateChanged(state) => {
- println!("Adapter state changed to {}", state.to_i32().unwrap());
-
- if state == btif::BtState::On {
- context.intf.get_adapter_properties();
- }
- }
- Callbacks::AdapterPropertiesChanged(status, _count, properties) => {
- if status != 0 {
- println!("Failed property change: {}", status);
- }
-
- for p in properties {
- let proptype = match btif::BtPropertyType::from_i32(p.prop_type) {
- Some(x) => x,
- None => btif::BtPropertyType::Unknown,
- };
- println!("Property {:?} is ({:?})", proptype, p.val);
- }
-
- // Scan for 5s and then cancel
- println!("Starting discovery");
- context.intf.start_discovery();
- }
- Callbacks::RemoteDevicePropertiesChanged(status, address, _count, properties) => {
- if status != 0 {
- println!("Failed remote property change: {}", status);
- }
-
- println!("Properties for {:?}", address.address);
-
- for p in properties {
- let proptype = match btif::BtPropertyType::from_i32(p.prop_type) {
- Some(x) => x,
- None => btif::BtPropertyType::Unknown,
- };
- println!("Property {:?} is ({:?})", proptype, p.val);
- }
- }
- Callbacks::DeviceFound(_count, properties) => {
- print!("Device found: ");
-
- for p in properties {
- let proptype = match btif::BtPropertyType::from_i32(p.prop_type) {
- Some(x) => x,
- None => btif::BtPropertyType::Unknown,
- };
-
- if proptype == btif::BtPropertyType::BdAddr {
- print!(" Addr[{:?}]", p.val);
- } else if proptype == btif::BtPropertyType::BdName {
- print!(
- " Name[{:?}]",
- p.val.iter().map(|u| char::try_from(*u).unwrap()).collect::<String>()
- );
- }
- }
-
- println!("");
- }
- Callbacks::DiscoveryStateChanged(state) => {
- if state == btif::BtDiscoveryState::Started {
- sleep(Duration::from_millis(5000)).await;
- context.intf.cancel_discovery();
-
- break 'main;
- }
- }
- }
- }
-}
-
-fn main() {
- println!("Bluetooth Adapter Daemon");
-
- // Drop the first arg (which is the binary name)
- let all_args: Vec<String> = env::args().collect();
- let args = all_args[1..].to_vec();
-
- let intf = BluetoothInterface::new();
- let mut context = make_context(intf);
-
- topstack::get_runtime().block_on(async move {
- if !context.intf.initialize(context.callbacks.clone(), args) {
- panic!("Couldn't initialize bluetooth interface!");
- }
-
- println!("Enabling...");
- context.intf.enable();
-
- println!("Running mainloop now");
- mainloop(&mut context).await;
-
- println!("Disabling and exiting...");
- context.intf.disable();
- });
-}
diff --git a/gd/rust/linux/dbus_projection/Cargo.toml b/gd/rust/linux/dbus_projection/Cargo.toml
deleted file mode 100644
index 166d9288a..000000000
--- a/gd/rust/linux/dbus_projection/Cargo.toml
+++ /dev/null
@@ -1,7 +0,0 @@
-[package]
-name = "dbus_projection"
-version = "0.1.0"
-edition = "2018"
-
-[dependencies]
-dbus = "0.9.2"
diff --git a/gd/rust/linux/dbus_projection/dbus_macros/Cargo.toml b/gd/rust/linux/dbus_projection/dbus_macros/Cargo.toml
deleted file mode 100644
index 84585d8d4..000000000
--- a/gd/rust/linux/dbus_projection/dbus_macros/Cargo.toml
+++ /dev/null
@@ -1,12 +0,0 @@
-[package]
-name = "dbus_macros"
-version = "0.1.0"
-edition = "2018"
-
-[lib]
-proc-macro = true
-
-[dependencies]
-syn = "1.0"
-quote = "1.0"
-proc-macro2 = "1.0"
diff --git a/gd/rust/linux/dbus_projection/dbus_macros/src/lib.rs b/gd/rust/linux/dbus_projection/dbus_macros/src/lib.rs
deleted file mode 100644
index a4924fe20..000000000
--- a/gd/rust/linux/dbus_projection/dbus_macros/src/lib.rs
+++ /dev/null
@@ -1,628 +0,0 @@
-extern crate proc_macro;
-
-use quote::{format_ident, quote, ToTokens};
-
-use std::fs::File;
-use std::io::Write;
-use std::path::Path;
-
-use syn::parse::Parser;
-use syn::punctuated::Punctuated;
-use syn::token::Comma;
-use syn::{Expr, FnArg, ImplItem, ItemImpl, ItemStruct, Meta, Pat, ReturnType, Type};
-
-use crate::proc_macro::TokenStream;
-
-fn debug_output_to_file(gen: &proc_macro2::TokenStream, filename: String) {
- let path = Path::new(filename.as_str());
- let mut file = File::create(&path).unwrap();
- file.write_all(gen.to_string().as_bytes()).unwrap();
-}
-
-/// Marks a method to be projected to a D-Bus method and specifies the D-Bus method name.
-#[proc_macro_attribute]
-pub fn dbus_method(_attr: TokenStream, item: TokenStream) -> TokenStream {
- let ori_item: proc_macro2::TokenStream = item.clone().into();
- let gen = quote! {
- #[allow(unused_variables)]
- #ori_item
- };
- gen.into()
-}
-
-/// Generates a function to export a Rust object to D-Bus.
-#[proc_macro_attribute]
-pub fn generate_dbus_exporter(attr: TokenStream, item: TokenStream) -> TokenStream {
- let ori_item: proc_macro2::TokenStream = item.clone().into();
-
- let args = Punctuated::<Expr, Comma>::parse_separated_nonempty.parse(attr.clone()).unwrap();
-
- let fn_ident = if let Expr::Path(p) = &args[0] {
- p.path.get_ident().unwrap()
- } else {
- panic!("function name must be specified");
- };
-
- let dbus_iface_name = if let Expr::Lit(lit) = &args[1] {
- lit
- } else {
- panic!("D-Bus interface name must be specified");
- };
-
- let ast: ItemImpl = syn::parse(item.clone()).unwrap();
- let api_iface_ident = ast.trait_.unwrap().1.to_token_stream();
-
- let mut register_methods = quote! {};
-
- for item in ast.items {
- if let ImplItem::Method(method) = item {
- if method.attrs.len() != 1 {
- continue;
- }
-
- let attr = &method.attrs[0];
- if !attr.path.get_ident().unwrap().to_string().eq("dbus_method") {
- continue;
- }
-
- let attr_args = attr.parse_meta().unwrap();
- let dbus_method_name = if let Meta::List(meta_list) = attr_args {
- Some(meta_list.nested[0].clone())
- } else {
- None
- };
-
- if dbus_method_name.is_none() {
- continue;
- }
-
- let method_name = method.sig.ident;
-
- let mut arg_names = quote! {};
- let mut method_args = quote! {};
- let mut make_args = quote! {};
- let mut dbus_input_vars = quote! {};
- let mut dbus_input_types = quote! {};
-
- for input in method.sig.inputs {
- if let FnArg::Typed(ref typed) = input {
- let arg_type = &typed.ty;
- if let Pat::Ident(pat_ident) = &*typed.pat {
- let ident = pat_ident.ident.clone();
- let mut dbus_input_ident = ident.to_string();
- dbus_input_ident.push_str("_");
- let dbus_input_arg = format_ident!("{}", dbus_input_ident);
- let ident_string = ident.to_string();
-
- arg_names = quote! {
- #arg_names #ident_string,
- };
-
- method_args = quote! {
- #method_args #ident,
- };
-
- dbus_input_vars = quote! {
- #dbus_input_vars #dbus_input_arg,
- };
-
- dbus_input_types = quote! {
- #dbus_input_types
- <#arg_type as DBusArg>::DBusType,
- };
-
- make_args = quote! {
- #make_args
- let #ident = <#arg_type as DBusArg>::from_dbus(
- #dbus_input_arg,
- conn_clone.clone(),
- ctx.message().sender().unwrap().into_static(),
- dc_watcher_clone.clone(),
- );
-
- if let Result::Err(e) = #ident {
- return Err(dbus_crossroads::MethodErr::invalid_arg(
- e.to_string().as_str()
- ));
- }
-
- let #ident = #ident.unwrap();
- };
- }
- }
- }
-
- let dbus_input_args = quote! {
- (#dbus_input_vars): (#dbus_input_types)
- };
-
- let mut output_names = quote! {};
- let mut output_type = quote! {};
- let mut ret = quote! {Ok(())};
- if let ReturnType::Type(_, t) = method.sig.output {
- output_type = quote! {#t,};
- ret = quote! {Ok((ret,))};
- output_names = quote! { "out", };
- }
-
- register_methods = quote! {
- #register_methods
-
- let conn_clone = conn.clone();
- let dc_watcher_clone = disconnect_watcher.clone();
- let handle_method = move |ctx: &mut dbus_crossroads::Context,
- obj: &mut ObjType,
- #dbus_input_args |
- -> Result<(#output_type), dbus_crossroads::MethodErr> {
- #make_args
- let ret = obj.lock().unwrap().#method_name(#method_args);
- #ret
- };
- ibuilder.method(
- #dbus_method_name,
- (#arg_names),
- (#output_names),
- handle_method,
- );
- };
- }
- }
-
- let gen = quote! {
- #ori_item
-
- type ObjType = std::sync::Arc<std::sync::Mutex<dyn #api_iface_ident + Send>>;
-
- pub fn #fn_ident(
- path: &'static str,
- conn: std::sync::Arc<SyncConnection>,
- cr: &mut dbus_crossroads::Crossroads,
- obj: ObjType,
- disconnect_watcher: Arc<Mutex<dbus_projection::DisconnectWatcher>>,
- ) {
- fn get_iface_token(
- conn: Arc<SyncConnection>,
- cr: &mut dbus_crossroads::Crossroads,
- disconnect_watcher: std::sync::Arc<std::sync::Mutex<dbus_projection::DisconnectWatcher>>,
- ) -> dbus_crossroads::IfaceToken<ObjType> {
- cr.register(#dbus_iface_name, |ibuilder| {
- #register_methods
- })
- }
-
- let iface_token = get_iface_token(conn, cr, disconnect_watcher);
- cr.insert(path, &[iface_token], obj);
- }
- };
-
- // TODO: Have a switch to turn on/off this debug.
- debug_output_to_file(&gen, format!("/tmp/out-{}.rs", fn_ident.to_string()));
-
- gen.into()
-}
-
-fn copy_without_attributes(item: &TokenStream) -> TokenStream {
- let mut ast: ItemStruct = syn::parse(item.clone()).unwrap();
- for field in &mut ast.fields {
- field.attrs.clear();
- }
-
- let gen = quote! {
- #ast
- };
-
- gen.into()
-}
-
-/// Generates a DBusArg implementation to transform Rust plain structs to a D-Bus data structure.
-// TODO: Support more data types of struct fields (currently only supports integers and enums).
-#[proc_macro_attribute]
-pub fn dbus_propmap(attr: TokenStream, item: TokenStream) -> TokenStream {
- let ori_item: proc_macro2::TokenStream = copy_without_attributes(&item).into();
-
- let ast: ItemStruct = syn::parse(item.clone()).unwrap();
-
- let args = Punctuated::<Expr, Comma>::parse_separated_nonempty.parse(attr.clone()).unwrap();
- let struct_ident =
- if let Expr::Path(p) = &args[0] { p.path.get_ident().unwrap().clone() } else { ast.ident };
-
- let struct_str = struct_ident.to_string();
-
- let mut make_fields = quote! {};
- let mut field_idents = quote! {};
-
- let mut insert_map_fields = quote! {};
- for field in ast.fields {
- let field_ident = field.ident;
-
- if field_ident.is_none() {
- continue;
- }
-
- let field_str = field_ident.as_ref().unwrap().clone().to_string();
-
- let propmap_attr = field.attrs.clone().into_iter().find(|x| {
- let ident = x.path.get_ident();
-
- if ident.is_none() {
- return false;
- }
-
- ident.unwrap().to_string().eq("dbus_propmap_field_propmap")
- });
-
- let field_type_str = if let Type::Path(t) = field.ty {
- t.path.get_ident().unwrap().to_string()
- } else {
- String::from("")
- };
-
- let field_type_ident = format_ident!("{}", field_type_str);
-
- field_idents = quote! {
- #field_idents #field_ident,
- };
-
- let make_field = if !propmap_attr.is_none() {
- quote! {
- let mut map: dbus::arg::PropMap = HashMap::new();
-
- let mut iter = #field_ident.as_iter().unwrap();
- let mut iter = iter.next().unwrap().as_iter().unwrap();
-
- let mut i1 = iter.next();
- let mut i2 = iter.next();
- while !i1.is_none() && !i2.is_none() {
- let k = i1.unwrap().as_str().unwrap().to_string();
- let v = dbus::arg::Variant(i2.unwrap().box_clone());
- map.insert(k, v);
- i1 = iter.next();
- i2 = iter.next();
- }
-
- let #field_ident = #field_type_ident::from_dbus(
- map,
- conn.clone(),
- remote.clone(),
- disconnect_watcher.clone(),
- )?;
- }
- } else {
- quote! {
- match #field_ident.arg_type() {
- dbus::arg::ArgType::Variant => {}
- _ => {
- return Err(Box::new(DBusArgError::new(String::from(format!(
- "{}.{} must be a variant",
- #struct_str, #field_str
- )))));
- }
- };
- let #field_ident = #field_ident.as_static_inner(0).unwrap();
- let any = #field_ident.as_any();
- if !any.is::<<#field_type_ident as DBusArg>::DBusType>() {
- return Err(Box::new(DBusArgError::new(String::from(format!(
- "{}.{} type does not match: expected {}, found {}",
- #struct_str,
- #field_str,
- std::any::type_name::<<#field_type_ident as DBusArg>::DBusType>(),
- #field_ident.arg_type().as_str(),
- )))));
- }
- let #field_ident = *any.downcast_ref::<<#field_type_ident as DBusArg>::DBusType>().unwrap();
- let #field_ident = #field_type_ident::from_dbus(
- #field_ident,
- conn.clone(),
- remote.clone(),
- disconnect_watcher.clone(),
- )?;
- }
- };
-
- make_fields = quote! {
- #make_fields
-
- let #field_ident = match data.get(#field_str) {
- Some(data) => data,
- None => {
- return Err(Box::new(DBusArgError::new(String::from(format!(
- "{}.{} is required",
- #struct_str, #field_str
- )))));
- }
- };
- #make_field
- };
-
- insert_map_fields = quote! {
- #insert_map_fields
- let field_data = DBusArg::to_dbus(data.#field_ident)?;
- map.insert(String::from(#field_str), dbus::arg::Variant(Box::new(field_data)));
- };
- }
-
- let gen = quote! {
- #[allow(dead_code)]
- #ori_item
-
- impl DBusArg for #struct_ident {
- type DBusType = dbus::arg::PropMap;
-
- fn from_dbus(
- data: dbus::arg::PropMap,
- conn: Arc<SyncConnection>,
- remote: BusName<'static>,
- disconnect_watcher: Arc<Mutex<dbus_projection::DisconnectWatcher>>,
- ) -> Result<#struct_ident, Box<dyn Error>> {
- #make_fields
-
- return Ok(#struct_ident {
- #field_idents
- ..Default::default()
- });
- }
-
- fn to_dbus(data: #struct_ident) -> Result<dbus::arg::PropMap, Box<dyn Error>> {
- let mut map: dbus::arg::PropMap = HashMap::new();
- #insert_map_fields
- return Ok(map);
- }
- }
- };
-
- // TODO: Have a switch to turn this debug off/on.
- debug_output_to_file(&gen, format!("/tmp/out-{}.rs", struct_ident.to_string()));
-
- gen.into()
-}
-
-/// Generates a DBusArg implementation of a Remote RPC proxy object.
-#[proc_macro_attribute]
-pub fn dbus_proxy_obj(attr: TokenStream, item: TokenStream) -> TokenStream {
- let ori_item: proc_macro2::TokenStream = item.clone().into();
-
- let args = Punctuated::<Expr, Comma>::parse_separated_nonempty.parse(attr.clone()).unwrap();
-
- let struct_ident = if let Expr::Path(p) = &args[0] {
- p.path.get_ident().unwrap()
- } else {
- panic!("struct name must be specified");
- };
-
- let dbus_iface_name = if let Expr::Lit(lit) = &args[1] {
- lit
- } else {
- panic!("D-Bus interface name must be specified");
- };
-
- let mut method_impls = quote! {};
-
- let ast: ItemImpl = syn::parse(item.clone()).unwrap();
- let self_ty = ast.self_ty;
- let trait_ = ast.trait_.unwrap().1;
-
- for item in ast.items {
- if let ImplItem::Method(method) = item {
- if method.attrs.len() != 1 {
- continue;
- }
-
- let attr = &method.attrs[0];
- if !attr.path.get_ident().unwrap().to_string().eq("dbus_method") {
- continue;
- }
-
- let attr_args = attr.parse_meta().unwrap();
- let dbus_method_name = if let Meta::List(meta_list) = attr_args {
- Some(meta_list.nested[0].clone())
- } else {
- None
- };
-
- if dbus_method_name.is_none() {
- continue;
- }
-
- let method_sig = method.sig.clone();
-
- let mut method_args = quote! {};
-
- for input in method.sig.inputs {
- if let FnArg::Typed(ref typed) = input {
- if let Pat::Ident(pat_ident) = &*typed.pat {
- let ident = pat_ident.ident.clone();
-
- method_args = quote! {
- #method_args DBusArg::to_dbus(#ident).unwrap(),
- };
- }
- }
- }
-
- method_impls = quote! {
- #method_impls
- #[allow(unused_variables)]
- #method_sig {
- let remote = self.remote.clone();
- let objpath = self.objpath.clone();
- let conn = self.conn.clone();
- bt_topshim::topstack::get_runtime().spawn(async move {
- let proxy = dbus::nonblock::Proxy::new(
- remote,
- objpath,
- std::time::Duration::from_secs(2),
- conn,
- );
- let future: dbus::nonblock::MethodReply<()> = proxy.method_call(
- #dbus_iface_name,
- #dbus_method_name,
- (#method_args),
- );
- let _result = future.await;
- });
- }
- };
- }
- }
-
- let gen = quote! {
- #ori_item
-
- impl RPCProxy for #self_ty {
- fn register_disconnect(&mut self, _disconnect_callback: Box<dyn Fn() + Send>) {}
- }
-
- struct #struct_ident {
- conn: Arc<SyncConnection>,
- remote: BusName<'static>,
- objpath: Path<'static>,
- disconnect_watcher: Arc<Mutex<DisconnectWatcher>>,
- }
-
- impl #trait_ for #struct_ident {
- #method_impls
- }
-
- impl RPCProxy for #struct_ident {
- fn register_disconnect(&mut self, disconnect_callback: Box<dyn Fn() + Send>) {
- self.disconnect_watcher.lock().unwrap().add(self.remote.clone(), disconnect_callback);
- }
- }
-
- impl DBusArg for Box<dyn #trait_ + Send> {
- type DBusType = Path<'static>;
-
- fn from_dbus(
- objpath: Path<'static>,
- conn: Arc<SyncConnection>,
- remote: BusName<'static>,
- disconnect_watcher: Arc<Mutex<DisconnectWatcher>>,
- ) -> Result<Box<dyn #trait_ + Send>, Box<dyn Error>> {
- Ok(Box::new(#struct_ident { conn, remote, objpath, disconnect_watcher }))
- }
-
- fn to_dbus(_data: Box<dyn #trait_ + Send>) -> Result<Path<'static>, Box<dyn Error>> {
- // This impl represents a remote DBus object, so `to_dbus` does not make sense.
- panic!("not implemented");
- }
- }
- };
-
- // TODO: Have a switch to turn this debug off/on.
- debug_output_to_file(&gen, format!("/tmp/out-{}.rs", struct_ident.to_string()));
-
- gen.into()
-}
-
-/// Generates the definition of `DBusArg` trait required for D-Bus projection.
-///
-/// Due to Rust orphan rule, `DBusArg` trait needs to be defined locally in the crate that wants to
-/// use D-Bus projection. Providing `DBusArg` as a public trait won't let other crates implement
-/// it for structs defined in foreign crates. As a workaround, this macro is provided to generate
-/// `DBusArg` trait definition.
-#[proc_macro]
-pub fn generate_dbus_arg(_item: TokenStream) -> TokenStream {
- let gen = quote! {
- use dbus::arg::PropMap;
- use dbus::nonblock::SyncConnection;
- use dbus::strings::BusName;
- use dbus_projection::DisconnectWatcher;
-
- use std::error::Error;
- use std::fmt;
- use std::sync::{Arc, Mutex};
-
- #[derive(Debug)]
- pub(crate) struct DBusArgError {
- message: String,
- }
-
- impl DBusArgError {
- pub fn new(message: String) -> DBusArgError {
- DBusArgError { message }
- }
- }
-
- impl fmt::Display for DBusArgError {
- fn fmt(&self, f: &mut fmt::Formatter) -> fmt::Result {
- write!(f, "{}", self.message)
- }
- }
-
- impl Error for DBusArgError {}
-
- pub(crate) trait DBusArg {
- type DBusType;
-
- fn from_dbus(
- x: Self::DBusType,
- conn: Arc<SyncConnection>,
- remote: BusName<'static>,
- disconnect_watcher: Arc<Mutex<DisconnectWatcher>>,
- ) -> Result<Self, Box<dyn Error>>
- where
- Self: Sized;
-
- fn to_dbus(x: Self) -> Result<Self::DBusType, Box<dyn Error>>;
- }
-
- // Types that implement dbus::arg::Append do not need any conversion.
- pub(crate) trait DirectDBus {}
- impl DirectDBus for i32 {}
- impl DirectDBus for u32 {}
- impl DirectDBus for String {}
- impl<T: DirectDBus> DBusArg for T {
- type DBusType = T;
-
- fn from_dbus(
- data: T,
- _conn: Arc<SyncConnection>,
- _remote: BusName<'static>,
- _disconnect_watcher: Arc<Mutex<DisconnectWatcher>>,
- ) -> Result<T, Box<dyn Error>> {
- return Ok(data);
- }
-
- fn to_dbus(data: T) -> Result<T, Box<dyn Error>> {
- return Ok(data);
- }
- }
-
- impl<T: DBusArg> DBusArg for Vec<T> {
- type DBusType = Vec<T::DBusType>;
-
- fn from_dbus(
- data: Vec<T::DBusType>,
- conn: Arc<SyncConnection>,
- remote: BusName<'static>,
- disconnect_watcher: Arc<Mutex<DisconnectWatcher>>,
- ) -> Result<Vec<T>, Box<dyn Error>> {
- let mut list: Vec<T> = vec![];
- for prop in data {
- let t = T::from_dbus(
- prop,
- conn.clone(),
- remote.clone(),
- disconnect_watcher.clone(),
- )?;
- list.push(t);
- }
- Ok(list)
- }
-
- fn to_dbus(data: Vec<T>) -> Result<Vec<T::DBusType>, Box<dyn Error>> {
- let mut list: Vec<T::DBusType> = vec![];
- for item in data {
- let t = T::to_dbus(item)?;
- list.push(t);
- }
- Ok(list)
- }
- }
- };
-
- // TODO: Have a switch to turn this debug off/on.
- debug_output_to_file(&gen, format!("/tmp/out-generate_dbus_arg.rs"));
-
- gen.into()
-}
diff --git a/gd/rust/linux/dbus_projection/src/lib.rs b/gd/rust/linux/dbus_projection/src/lib.rs
deleted file mode 100644
index 7d948a730..000000000
--- a/gd/rust/linux/dbus_projection/src/lib.rs
+++ /dev/null
@@ -1,102 +0,0 @@
-//! This crate provides tools to automatically project generic API to D-Bus RPC.
-//!
-//! For D-Bus projection to work automatically, the API needs to follow certain restrictions.
-
-use dbus::channel::MatchingReceiver;
-use dbus::message::MatchRule;
-use dbus::nonblock::SyncConnection;
-use dbus::strings::BusName;
-
-use std::collections::HashMap;
-use std::sync::{Arc, Mutex};
-
-/// A D-Bus "NameOwnerChanged" handler that continuously monitors client disconnects.
-pub struct DisconnectWatcher {
- callbacks: Arc<Mutex<HashMap<BusName<'static>, Vec<Box<dyn Fn() + Send>>>>>,
-}
-
-impl DisconnectWatcher {
- /// Creates a new DisconnectWatcher with empty callbacks.
- pub fn new() -> DisconnectWatcher {
- DisconnectWatcher { callbacks: Arc::new(Mutex::new(HashMap::new())) }
- }
-}
-
-impl DisconnectWatcher {
- /// Adds a client address to be monitored for disconnect events.
- pub fn add(&mut self, address: BusName<'static>, callback: Box<dyn Fn() + Send>) {
- if !self.callbacks.lock().unwrap().contains_key(&address) {
- self.callbacks.lock().unwrap().insert(address.clone(), vec![]);
- }
-
- (*self.callbacks.lock().unwrap().get_mut(&address).unwrap()).push(callback);
- }
-
- /// Sets up the D-Bus handler that monitors client disconnects.
- pub async fn setup_watch(&mut self, conn: Arc<SyncConnection>) {
- let mr = MatchRule::new_signal("org.freedesktop.DBus", "NameOwnerChanged");
-
- conn.add_match_no_cb(&mr.match_str()).await.unwrap();
- let callbacks_map = self.callbacks.clone();
- conn.start_receive(
- mr,
- Box::new(move |msg, _conn| {
- // The args are "address", "old address", "new address".
- // https://dbus.freedesktop.org/doc/dbus-specification.html#bus-messages-name-owner-changed
- let (addr, old, new) = msg.get3::<String, String, String>();
-
- if addr.is_none() || old.is_none() || new.is_none() {
- return true;
- }
-
- if old.unwrap().eq("") || !new.unwrap().eq("") {
- return true;
- }
-
- // If old address exists but new address is empty, that means that client is
- // disconnected. So call the registered callbacks to be notified of this client
- // disconnect.
- let addr = BusName::new(addr.unwrap()).unwrap().into_static();
- if !callbacks_map.lock().unwrap().contains_key(&addr) {
- return true;
- }
-
- for callback in &callbacks_map.lock().unwrap()[&addr] {
- callback();
- }
-
- callbacks_map.lock().unwrap().remove(&addr);
-
- true
- }),
- );
- }
-}
-
-#[macro_export]
-macro_rules! impl_dbus_arg_enum {
- ($enum_type:ty) => {
- impl DBusArg for $enum_type {
- type DBusType = i32;
- fn from_dbus(
- data: i32,
- _conn: Arc<SyncConnection>,
- _remote: BusName<'static>,
- _disconnect_watcher: Arc<Mutex<dbus_projection::DisconnectWatcher>>,
- ) -> Result<$enum_type, Box<dyn Error>> {
- match <$enum_type>::from_i32(data) {
- Some(x) => Ok(x),
- None => Err(Box::new(DBusArgError::new(String::from(format!(
- "error converting {} to {}",
- data,
- stringify!($enum_type)
- ))))),
- }
- }
-
- fn to_dbus(data: $enum_type) -> Result<i32, Box<dyn Error>> {
- return Ok(data.to_i32().unwrap());
- }
- }
- };
-}
diff --git a/gd/rust/linux/mgmt/Cargo.toml b/gd/rust/linux/mgmt/Cargo.toml
deleted file mode 100644
index 06ad7d0d3..000000000
--- a/gd/rust/linux/mgmt/Cargo.toml
+++ /dev/null
@@ -1,22 +0,0 @@
-[package]
-name = "manager_service"
-version = "0.0.1"
-edition = "2018"
-
-# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
-
-[dependencies]
-
-# bt deps
-bt_common = { path = "../../common" }
-
-# external deps
-dbus = "0.9.2"
-dbus-tokio = "0.7.3"
-dbus-crossroads = "0.3.0"
-inotify = "*"
-nix = "*"
-tokio = { version = "1.0", features = ["fs", "macros", "rt-multi-thread", "sync"] }
-
-[[bin]]
-name = "btmanagerd"
diff --git a/gd/rust/linux/mgmt/src/bin/btmanagerd/main.rs b/gd/rust/linux/mgmt/src/bin/btmanagerd/main.rs
deleted file mode 100644
index 4cc7852c5..000000000
--- a/gd/rust/linux/mgmt/src/bin/btmanagerd/main.rs
+++ /dev/null
@@ -1,148 +0,0 @@
-mod state_machine;
-
-use dbus::channel::MatchingReceiver;
-use dbus::message::MatchRule;
-use dbus_crossroads::Crossroads;
-use dbus_tokio::connection;
-
-#[tokio::main]
-pub async fn main() -> Result<(), Box<dyn std::error::Error>> {
- let context = state_machine::start_new_state_machine_context();
- let proxy = context.get_proxy();
-
- // Connect to the D-Bus system bus (this is blocking, unfortunately).
- let (resource, c) = connection::new_system_sync()?;
-
- // The resource is a task that should be spawned onto a tokio compatible
- // reactor ASAP. If the resource ever finishes, you lost connection to D-Bus.
- tokio::spawn(async {
- let err = resource.await;
- panic!("Lost connection to D-Bus: {}", err);
- });
-
- // Let's request a name on the bus, so that clients can find us.
- c.request_name("org.chromium.bluetooth.Manager", false, true, false).await?;
-
- // Create a new crossroads instance.
- // The instance is configured so that introspection and properties interfaces
- // are added by default on object path additions.
- let mut cr = Crossroads::new();
-
- // Enable async support for the crossroads instance.
- cr.set_async_support(Some((
- c.clone(),
- Box::new(|x| {
- tokio::spawn(x);
- }),
- )));
-
- let iface_token = cr.register("org.chromium.bluetooth.Manager", |b| {
- b.method_with_cr_async(
- "Start",
- ("hci_interface",),
- (),
- |mut ctx, cr, (hci_interface,): (i32,)| {
- let proxy =
- cr.data_mut::<state_machine::StateMachineProxy>(ctx.path()).unwrap().clone();
- println!("Incoming Start call for hci {}!", hci_interface);
- async move {
- let result = proxy.start_bluetooth(hci_interface).await;
- match result {
- Ok(()) => ctx.reply(Ok(())),
- Err(_) => ctx.reply(Err(dbus_crossroads::MethodErr::failed(
- "cannot start Bluetooth",
- ))),
- }
- }
- },
- );
- b.method_with_cr_async("Stop", ("hci_interface",), (), |mut ctx, cr, (hci_interface,) : (i32,)| {
- let proxy =
- cr.data_mut::<state_machine::StateMachineProxy>(ctx.path()).unwrap().clone();
- println!("Incoming Stop call!");
- async move {
- let result = proxy.stop_bluetooth(hci_interface).await;
- match result {
- Ok(()) => ctx.reply(Ok(())),
- Err(_) => {
- ctx.reply(Err(dbus_crossroads::MethodErr::failed("cannot stop Bluetooth")))
- }
- }
- }
- });
- b.method_with_cr_async("GetState", (), ("result",), |mut ctx, cr, ()| {
- let proxy =
- cr.data_mut::<state_machine::StateMachineProxy>(ctx.path()).unwrap().clone();
- async move {
- let state = proxy.get_state().await;
- let result = match state {
- state_machine::State::Off => 0,
- state_machine::State::TurningOn => 1,
- state_machine::State::On => 2,
- state_machine::State::TurningOff => 3,
- };
- ctx.reply(Ok((result,)))
- }
- });
- b.method_with_cr_async(
- "RegisterStateChangeObserver",
- ("object_path",),
- (),
- |mut ctx, cr, (object_path,): (String,)| {
- let proxy =
- cr.data_mut::<state_machine::StateMachineProxy>(ctx.path()).unwrap().clone();
- async move {
- let result = proxy.register_state_change_observer(object_path.clone()).await;
- match result {
- Ok(()) => ctx.reply(Ok(())),
- Err(_) => ctx.reply(Err(dbus_crossroads::MethodErr::failed(&format!(
- "cannot register {}",
- object_path
- )))),
- }
- }
- },
- );
- b.method_with_cr_async(
- "UnregisterStateChangeObserver",
- ("object_path",),
- (),
- |mut ctx, cr, (object_path,): (String,)| {
- let proxy =
- cr.data_mut::<state_machine::StateMachineProxy>(ctx.path()).unwrap().clone();
- async move {
- let result = proxy.unregister_state_change_observer(object_path.clone()).await;
- match result {
- Ok(()) => ctx.reply(Ok(())),
- Err(_) => ctx.reply(Err(dbus_crossroads::MethodErr::failed(&format!(
- "cannot unregister {}",
- object_path
- )))),
- }
- }
- },
- );
- });
-
- // Let's add the "/org/chromium/bluetooth/Manager" path, which implements the org.chromium.bluetooth.Manager interface,
- // to the crossroads instance.
- cr.insert("/org/chromium/bluetooth/Manager", &[iface_token], proxy);
-
- // We add the Crossroads instance to the connection so that incoming method calls will be handled.
- c.start_receive(
- MatchRule::new_method_call(),
- Box::new(move |msg, conn| {
- cr.handle_message(msg, conn).unwrap();
- true
- }),
- );
-
- tokio::spawn(async move {
- state_machine::mainloop(context).await;
- });
-
- loop {}
-
- // Run forever.
- unreachable!()
-}
diff --git a/gd/rust/linux/mgmt/src/bin/btmanagerd/state_machine.rs b/gd/rust/linux/mgmt/src/bin/btmanagerd/state_machine.rs
deleted file mode 100644
index 305fb3eab..000000000
--- a/gd/rust/linux/mgmt/src/bin/btmanagerd/state_machine.rs
+++ /dev/null
@@ -1,572 +0,0 @@
-use bt_common::time::Alarm;
-use std::collections::VecDeque;
-use std::process::{Child, Command, Stdio};
-use std::sync::Arc;
-use std::time::Duration;
-use tokio::io::unix::AsyncFd;
-use tokio::sync::{mpsc, Mutex};
-use tokio::sync::mpsc::error::SendError;
-
-#[derive(Debug, PartialEq, Copy, Clone)]
-pub enum State {
- Off, // Bluetooth is not running
- TurningOn, // We are not notified that the Bluetooth is running
- On, // Bluetooth is running
- TurningOff, // We are not notified that the Bluetooth is stopped
-}
-
-#[derive(Debug)]
-pub enum StateMachineActions {
- StartBluetooth(i32),
- StopBluetooth(i32),
- BluetoothStarted(i32, i32), // PID and HCI
- BluetoothStopped(),
-}
-
-pub struct StateMachineContext<PM> {
- tx: mpsc::Sender<StateMachineActions>,
- rx: mpsc::Receiver<StateMachineActions>,
- state_machine: ManagerStateMachine<PM>,
-}
-
-impl<PM> StateMachineContext<PM> {
- fn new(state_machine: ManagerStateMachine<PM>) -> StateMachineContext<PM>
- where
- PM: ProcessManager + Send,
- {
- let (tx, rx) = mpsc::channel::<StateMachineActions>(1);
- StateMachineContext { tx: tx, rx: rx, state_machine: state_machine }
- }
-
- pub fn get_proxy(&self) -> StateMachineProxy {
- StateMachineProxy {
- tx: self.tx.clone(),
- state: self.state_machine.state.clone(),
- state_change_observers: self.state_machine.state_change_observers.clone(),
- }
- }
-}
-
-pub fn start_new_state_machine_context() -> StateMachineContext<NativeSubprocess> {
- StateMachineContext::new(ManagerStateMachine::new_native())
-}
-
-#[derive(Clone)]
-pub struct StateMachineProxy {
- tx: mpsc::Sender<StateMachineActions>,
- state: Arc<Mutex<State>>,
- state_change_observers: Arc<Mutex<Vec<String>>>,
-}
-
-impl StateMachineProxy {
- pub async fn start_bluetooth(
- &self,
- hci_interface: i32,
- ) -> Result<(), SendError<StateMachineActions>> {
- self.tx.send(StateMachineActions::StartBluetooth(hci_interface)).await
- }
-
- pub async fn stop_bluetooth(&self, hci_interface: i32,) -> Result<(), SendError<StateMachineActions>> {
- self.tx.send(StateMachineActions::StopBluetooth(hci_interface)).await
- }
-
- pub async fn get_state(&self) -> State {
- *self.state.lock().await
- }
-
- pub async fn register_state_change_observer(
- &self,
- object_path: String,
- ) -> Result<(), SendError<StateMachineActions>> {
- self.state_change_observers.lock().await.push(object_path);
- Ok(())
- }
-
- pub async fn unregister_state_change_observer(
- &self,
- object_path: String,
- ) -> Result<(), SendError<StateMachineActions>> {
- let mut observers = self.state_change_observers.lock().await;
- let index = observers.iter().position(|x| *x == object_path).unwrap();
- observers.remove(index);
- Ok(())
- }
-}
-
-pub async fn mainloop<PM>(mut context: StateMachineContext<PM>)
-where
- PM: ProcessManager + Send,
-{
- let mut command_timeout = Alarm::new();
- let mut pid_detector = inotify::Inotify::init().expect("cannot use inotify");
- pid_detector
- .add_watch("/var/run", inotify::WatchMask::CREATE | inotify::WatchMask::DELETE)
- .expect("failed to add watch");
- let mut pid_async_fd = AsyncFd::new(pid_detector).expect("failed to add async fd");
- // let mut async_fd = pid_async_fd.readable_mut();
- // tokio::pin!(async_fd);
- let command_timeout_duration = Duration::from_secs(2);
- loop {
- tokio::select! {
- Some(action) = context.rx.recv() => {
- match action {
- StateMachineActions::StartBluetooth(i) => {
- match context.state_machine.action_start_bluetooth(i) {
- true => {
- command_timeout.reset(command_timeout_duration);
- },
- false => (),
- }
- },
- StateMachineActions::StopBluetooth(i) => {
- match context.state_machine.action_stop_bluetooth(i) {
- true => command_timeout.reset(command_timeout_duration),
- false => (),
- }
- },
- StateMachineActions::BluetoothStarted(pid, hci) => {
- match context.state_machine.action_on_bluetooth_started(pid, hci) {
- true => command_timeout.cancel(),
- false => println!("unexpected BluetoothStarted pid{} hci{}", pid, hci),
- }
- },
- StateMachineActions::BluetoothStopped() => {
- match context.state_machine.action_on_bluetooth_stopped() {
- true => command_timeout.cancel(),
- false => {
- println!("BluetoothStopped");
- command_timeout.reset(command_timeout_duration);
- }
- }
- },
- }
- },
- _ = command_timeout.expired() => {
- println!("expired {:?}", *context.state_machine.state.lock().await);
- let timeout_action = context.state_machine.action_on_command_timeout();
- match timeout_action {
- StateMachineTimeoutActions::Noop => (),
- _ => command_timeout.reset(command_timeout_duration),
- }
- },
- r = pid_async_fd.readable_mut() => {
- let mut fd_ready = r.unwrap();
- let mut buffer: [u8; 1024] = [0; 1024];
- match fd_ready.try_io(|inner| inner.get_mut().read_events(&mut buffer)) {
- Ok(Ok(events)) => {
- for event in events {
- match event.mask {
- inotify::EventMask::CREATE => {
- if event.name == Some(std::ffi::OsStr::new("bluetooth.pid")) {
- let read_result = tokio::fs::read("/var/run/bluetooth.pid").await;
- match read_result {
- Ok(v) => {
- let file_string = String::from_utf8(v).expect("invalid pid file");
- let mut iter = file_string.split_ascii_whitespace();
- let pid = match iter.next() {
- Some(s) => s.parse::<i32>().unwrap(),
- None => 0
- };
- let hci = match iter.next() {
- Some(s) => s.parse::<i32>().unwrap(),
- None => 0
- };
- context.tx.send(StateMachineActions::BluetoothStarted(pid, hci)).await;
- },
- Err(e) => println!("{}", e)
- }
- }
- },
- inotify::EventMask::DELETE => {
- if event.name == Some(std::ffi::OsStr::new("bluetooth.pid")) {
- context.tx.send(StateMachineActions::BluetoothStopped()).await;
- }
- },
- _ => println!("Ignored event {:?}", event.mask)
- }
- }
- }
- Err(_) | Ok(Err(_)) => panic!("why can't we read while the asyncfd is ready?"),
- }
- fd_ready.clear_ready();
- drop(fd_ready);
- },
- }
- }
-}
-
-pub trait ProcessManager {
- fn start(&mut self, hci_interface: String);
- fn stop(&mut self, hci_interface: String);
-}
-
-pub struct NativeSubprocess {
- process_container: Option<Child>,
-}
-
-impl NativeSubprocess {
- pub fn new() -> NativeSubprocess {
- NativeSubprocess { process_container: None }
- }
-}
-
-impl ProcessManager for NativeSubprocess {
- fn start(&mut self, hci_interface: String) {
- self.process_container = Some(
- Command::new("/usr/bin/touch")
- .arg("/var/run/bluetooth.pid")
- .stdout(Stdio::piped())
- .spawn()
- .expect("cannot open"),
- );
- }
- fn stop(&mut self, hci_interface: String) {
- match self.process_container {
- Some(ref mut p) => {
- // TODO: Maybe just SIGINT first, not kill
- p.kill();
- self.process_container = None;
- }
- None => {
- println!("Process doesn't exist");
- }
- }
- }
-}
-
-pub struct UpstartInvoker {
- // Upstart version not implemented
-}
-
-impl UpstartInvoker {
- pub fn new() -> UpstartInvoker {
- UpstartInvoker {}
- }
-}
-
-impl ProcessManager for UpstartInvoker {
- fn start(&mut self, hci_interface: String) {
- Command::new("initctl")
- .arg("start")
- .arg("bluetooth")
- .arg(format!("HCI={}", hci_interface))
- .output()
- .expect("failed to start bluetooth");
- }
-
- fn stop(&mut self, hci_interface: String) {
- Command::new("initctl")
- .arg("stop")
- .arg("bluetooth")
- .arg(format!("HCI={}", hci_interface))
- .output()
- .expect("failed to stop bluetooth");
- }
-}
-
-struct ManagerStateMachine<PM> {
- state: Arc<Mutex<State>>,
- process_manager: PM,
- state_change_observers: Arc<Mutex<Vec<String>>>,
- hci_interface: i32,
- bluetooth_pid: i32,
-}
-
-impl ManagerStateMachine<NativeSubprocess> {
- pub fn new_native() -> ManagerStateMachine<NativeSubprocess> {
- ManagerStateMachine::new(NativeSubprocess::new())
- }
-}
-
-#[derive(Debug, PartialEq)]
-enum StateMachineTimeoutActions {
- RetryStart,
- RetryStop,
- Killed,
- Noop,
-}
-
-impl<PM> ManagerStateMachine<PM>
-where
- PM: ProcessManager + Send,
-{
- pub fn new(process_manager: PM) -> ManagerStateMachine<PM> {
- ManagerStateMachine {
- state: Arc::new(Mutex::new(State::Off)),
- process_manager: process_manager,
- state_change_observers: Arc::new(Mutex::new(Vec::new())),
- hci_interface: 0,
- bluetooth_pid: 0,
- }
- }
-
- /// Returns true if we are starting bluetooth process.
- pub fn action_start_bluetooth(&mut self, hci_interface: i32) -> bool {
- let mut state = self.state.try_lock().unwrap(); // TODO hsz: fix me
- match *state {
- State::Off => {
- *state = State::TurningOn;
- self.hci_interface = hci_interface;
- self.process_manager.start(format!("hci{}", hci_interface));
- true
- }
- // Otherwise no op
- _ => false,
- }
- }
-
- /// Returns true if we are stopping bluetooth process.
- pub fn action_stop_bluetooth(&mut self, hci_interface: i32) -> bool {
- if self.hci_interface != hci_interface {
- println!("We are running hci{} but attempting to stop hci{}", self.hci_interface, hci_interface);
- return false
- }
-
- let mut state = self.state.try_lock().unwrap(); // TODO hsz: fix me
- match *state {
- State::On | State::TurningOn => {
- *state = State::TurningOff;
- self.process_manager.stop(self.hci_interface.to_string());
- true
- }
- // Otherwise no op
- _ => false,
- }
- }
-
- /// Returns true if the event is expected.
- pub fn action_on_bluetooth_started(&mut self, pid: i32, hci_interface: i32) -> bool {
- let mut state = self.state.try_lock().unwrap(); // TODO hsz: fix me
- if self.hci_interface != hci_interface {
- println!("We should start hci{} but hci{} is started; capturing that process", self.hci_interface, hci_interface);
- self.hci_interface = hci_interface;
- }
- if *state != State::TurningOn {
- println!("Unexpected Bluetooth started");
- }
- *state = State::On;
- self.bluetooth_pid = pid;
- true
- }
-
- /// Returns true if the event is expected.
- /// If unexpected, Bluetooth probably crashed;
- /// start the timer for restart timeout
- pub fn action_on_bluetooth_stopped(&mut self) -> bool {
- // Need to check if file exists
- let mut state = self.state.try_lock().unwrap(); // TODO hsz: fix me
-
- match *state {
- State::TurningOff => {
- *state = State::Off;
- true
- }
- State::On => {
- println!("Bluetooth stopped unexpectedly, try restarting");
- *state = State::TurningOn;
- self.process_manager.start(format!("hci{}", self.hci_interface));
- false
- }
- State::TurningOn | State::Off => {
- // Unexpected
- panic!("unexpected bluetooth shutdown");
- }
- }
- }
-
- /// Triggered on Bluetooth start/stop timeout. Return the actions that the
- /// state machine has taken, for the external context to reset the timer.
- pub fn action_on_command_timeout(&mut self) -> StateMachineTimeoutActions {
- let mut state = self.state.try_lock().unwrap(); // TODO hsz: fix me
- match *state {
- State::TurningOn => {
- println!("Restarting bluetooth");
- *state = State::TurningOn;
- self.process_manager.start(format! {"hci{}", self.hci_interface});
- StateMachineTimeoutActions::RetryStart
- }
- State::TurningOff => {
- println!("Killing bluetooth");
-
- *state = State::Off;
- StateMachineTimeoutActions::RetryStop
- // kill bluetooth
- // tx.try_send(StateMachineActions::StopBluetooth());
- }
- _ => panic!("Unexpected timeout on {:?}", *state),
- }
- }
-}
-
-#[cfg(test)]
-mod tests {
- use super::*;
-
- #[derive(Debug, PartialEq)]
- enum ExecutedCommand {
- Start,
- Stop,
- }
-
- struct MockProcessManager {
- last_command: VecDeque<ExecutedCommand>,
- }
-
- impl MockProcessManager {
- fn new() -> MockProcessManager {
- MockProcessManager { last_command: VecDeque::new() }
- }
-
- fn expect_start(&mut self) {
- self.last_command.push_back(ExecutedCommand::Start);
- }
-
- fn expect_stop(&mut self) {
- self.last_command.push_back(ExecutedCommand::Stop);
- }
- }
-
- impl ProcessManager for MockProcessManager {
- fn start(&mut self, hci_interface: String) {
- let start = self.last_command.pop_front().expect("Should expect start event");
- assert_eq!(start, ExecutedCommand::Start);
- }
-
- fn stop(&mut self, hci_interface: String) {
- let stop = self.last_command.pop_front().expect("Should expect stop event");
- assert_eq!(stop, ExecutedCommand::Stop);
- }
- }
-
- impl Drop for MockProcessManager {
- fn drop(&mut self) {
- assert_eq!(self.last_command.len(), 0);
- }
- }
-
- #[test]
- fn initial_state_is_off() {
- let process_manager = MockProcessManager::new();
- let state_machine = ManagerStateMachine::new(process_manager);
- assert_eq!(*state_machine.state.try_lock().unwrap(), State::Off);
- }
-
- #[test]
- fn off_turnoff_should_noop() {
- let process_manager = MockProcessManager::new();
- let mut state_machine = ManagerStateMachine::new(process_manager);
- state_machine.action_stop_bluetooth(0);
- assert_eq!(*state_machine.state.try_lock().unwrap(), State::Off);
- }
-
- #[test]
- fn off_turnon_should_turningon() {
- let mut process_manager = MockProcessManager::new();
- // Expect to send start command
- process_manager.expect_start();
- let mut state_machine = ManagerStateMachine::new(process_manager);
- state_machine.action_start_bluetooth(0);
- assert_eq!(*state_machine.state.try_lock().unwrap(), State::TurningOn);
- }
-
- #[test]
- fn turningon_turnon_again_noop() {
- let mut process_manager = MockProcessManager::new();
- // Expect to send start command just once
- process_manager.expect_start();
- let mut state_machine = ManagerStateMachine::new(process_manager);
- state_machine.action_start_bluetooth(0);
- assert_eq!(state_machine.action_start_bluetooth(0), false);
- }
-
- #[test]
- fn turningon_bluetooth_started() {
- let mut process_manager = MockProcessManager::new();
- process_manager.expect_start();
- let mut state_machine = ManagerStateMachine::new(process_manager);
- state_machine.action_start_bluetooth(0);
- state_machine.action_on_bluetooth_started(0, 0);
- assert_eq!(*state_machine.state.try_lock().unwrap(), State::On);
- }
-
- #[test]
- fn turningon_timeout() {
- let mut process_manager = MockProcessManager::new();
- process_manager.expect_start();
- process_manager.expect_start(); // start bluetooth again
- let mut state_machine = ManagerStateMachine::new(process_manager);
- state_machine.action_start_bluetooth(0);
- assert_eq!(
- state_machine.action_on_command_timeout(),
- StateMachineTimeoutActions::RetryStart
- );
- assert_eq!(*state_machine.state.try_lock().unwrap(), State::TurningOn);
- }
-
- #[test]
- fn turningon_turnoff_should_turningoff_and_send_command() {
- let mut process_manager = MockProcessManager::new();
- process_manager.expect_start();
- // Expect to send stop command
- process_manager.expect_stop();
- let mut state_machine = ManagerStateMachine::new(process_manager);
- state_machine.action_start_bluetooth(0);
- state_machine.action_stop_bluetooth(0);
- assert_eq!(*state_machine.state.try_lock().unwrap(), State::TurningOff);
- }
-
- #[test]
- fn on_turnoff_should_turningoff_and_send_command() {
- let mut process_manager = MockProcessManager::new();
- process_manager.expect_start();
- // Expect to send stop command
- process_manager.expect_stop();
- let mut state_machine = ManagerStateMachine::new(process_manager);
- state_machine.action_start_bluetooth(0);
- state_machine.action_on_bluetooth_started(0, 0);
- state_machine.action_stop_bluetooth(0);
- assert_eq!(*state_machine.state.try_lock().unwrap(), State::TurningOff);
- }
-
- #[test]
- fn on_bluetooth_stopped() {
- let mut process_manager = MockProcessManager::new();
- process_manager.expect_start();
- // Expect to start again
- process_manager.expect_start();
- let mut state_machine = ManagerStateMachine::new(process_manager);
- state_machine.action_start_bluetooth(0);
- state_machine.action_on_bluetooth_started(0, 0);
- assert_eq!(state_machine.action_on_bluetooth_stopped(), false);
- assert_eq!(*state_machine.state.try_lock().unwrap(), State::TurningOn);
- }
-
- #[test]
- fn turningoff_bluetooth_down_should_off() {
- let mut process_manager = MockProcessManager::new();
- process_manager.expect_start();
- process_manager.expect_stop();
- let mut state_machine = ManagerStateMachine::new(process_manager);
- state_machine.action_start_bluetooth(0);
- state_machine.action_on_bluetooth_started(0, 0);
- state_machine.action_stop_bluetooth(0);
- state_machine.action_on_bluetooth_stopped();
- assert_eq!(*state_machine.state.try_lock().unwrap(), State::Off);
- }
-
- #[test]
- fn restart_bluetooth() {
- let mut process_manager = MockProcessManager::new();
- process_manager.expect_start();
- process_manager.expect_stop();
- process_manager.expect_start();
- let mut state_machine = ManagerStateMachine::new(process_manager);
- state_machine.action_start_bluetooth(0);
- state_machine.action_on_bluetooth_started(0, 0);
- state_machine.action_stop_bluetooth(0);
- state_machine.action_on_bluetooth_stopped();
- state_machine.action_start_bluetooth(0);
- state_machine.action_on_bluetooth_started(0, 0);
- assert_eq!(*state_machine.state.try_lock().unwrap(), State::On);
- }
-}
diff --git a/gd/rust/linux/service/Cargo.toml b/gd/rust/linux/service/Cargo.toml
deleted file mode 100644
index b83dbb842..000000000
--- a/gd/rust/linux/service/Cargo.toml
+++ /dev/null
@@ -1,26 +0,0 @@
-[package]
-name = "btserv"
-version = "0.1.0"
-edition = "2018"
-
-[dependencies]
-bt_topshim = { path = "../../topshim" }
-bt_shim = { path = "../../shim" }
-btstack = { path = "../stack" }
-dbus_projection = { path = "../dbus_projection" }
-dbus_macros = { path = "../dbus_projection/dbus_macros" }
-
-dbus = "0.9.2"
-dbus-crossroads = "0.3.0"
-dbus-tokio = "0.7.3"
-futures = "0.3.13"
-num-traits = "*"
-tokio = { version = "1", features = ['bytes', 'fs', 'io-util', 'libc', 'macros', 'memchr', 'mio', 'net', 'num_cpus', 'rt', 'rt-multi-thread', 'sync', 'time', 'tokio-macros'] }
-
-[build-dependencies]
-pkg-config = "0.3.19"
-
-[[bin]]
-name = "btserv"
-path = "src/main.rs"
-build = "build.rs"
diff --git a/gd/rust/linux/service/build.rs b/gd/rust/linux/service/build.rs
deleted file mode 100644
index 41f40834b..000000000
--- a/gd/rust/linux/service/build.rs
+++ /dev/null
@@ -1,27 +0,0 @@
-use pkg_config::Config;
-
-fn main() {
- let target_dir = std::env::var_os("CARGO_TARGET_DIR").unwrap();
-
- // The main linking point with c++ code is the libbluetooth-static.a
- // These includes all the symbols built via C++ but doesn't include other
- // links (i.e. pkg-config)
- println!("cargo:rustc-link-lib=static=bluetooth-static");
- println!("cargo:rustc-link-search=native={}", target_dir.into_string().unwrap());
-
- // A few dynamic links
- println!("cargo:rustc-link-lib=dylib=flatbuffers");
- println!("cargo:rustc-link-lib=dylib=protobuf");
- println!("cargo:rustc-link-lib=dylib=resolv");
-
- // Clang requires -lc++ instead of -lstdc++
- println!("cargo:rustc-link-lib=c++");
-
- // A few more dependencies from pkg-config. These aren't included as part of
- // the libbluetooth-static.a
- Config::new().probe("libchrome").unwrap();
- Config::new().probe("libmodp_b64").unwrap();
- Config::new().probe("tinyxml2").unwrap();
-
- println!("cargo:rerun-if-changed=build.rs");
-}
diff --git a/gd/rust/linux/service/src/dbus_arg.rs b/gd/rust/linux/service/src/dbus_arg.rs
deleted file mode 100644
index d1724aa89..000000000
--- a/gd/rust/linux/service/src/dbus_arg.rs
+++ /dev/null
@@ -1,3 +0,0 @@
-use dbus_macros::generate_dbus_arg;
-
-generate_dbus_arg!();
diff --git a/gd/rust/linux/service/src/iface_bluetooth.rs b/gd/rust/linux/service/src/iface_bluetooth.rs
deleted file mode 100644
index b5ad28f22..000000000
--- a/gd/rust/linux/service/src/iface_bluetooth.rs
+++ /dev/null
@@ -1,51 +0,0 @@
-extern crate bt_shim;
-
-use btstack::bluetooth::{IBluetooth, IBluetoothCallback};
-use btstack::RPCProxy;
-
-use dbus::nonblock::SyncConnection;
-use dbus::strings::{BusName, Path};
-
-use dbus_macros::{dbus_method, dbus_proxy_obj, generate_dbus_exporter};
-
-use dbus_projection::DisconnectWatcher;
-
-use std::error::Error;
-use std::sync::Arc;
-use std::sync::Mutex;
-
-use crate::dbus_arg::DBusArg;
-
-#[allow(dead_code)]
-struct BluetoothCallbackDBus {}
-
-#[dbus_proxy_obj(BluetoothCallback, "org.chromium.bluetooth.BluetoothCallback")]
-impl IBluetoothCallback for BluetoothCallbackDBus {
- #[dbus_method("OnBluetoothStateChange")]
- fn on_bluetooth_state_changed(&self, prev_state: u32, new_state: u32) {}
- #[dbus_method("OnBluetoothAddressChanged")]
- fn on_bluetooth_address_changed(&self, addr: String) {}
-}
-
-#[allow(dead_code)]
-struct IBluetoothDBus {}
-
-#[generate_dbus_exporter(export_bluetooth_dbus_obj, "org.chromium.bluetooth.Bluetooth")]
-impl IBluetooth for IBluetoothDBus {
- #[dbus_method("RegisterCallback")]
- fn register_callback(&mut self, callback: Box<dyn IBluetoothCallback + Send>) {}
-
- #[dbus_method("Enable")]
- fn enable(&mut self) -> bool {
- false
- }
- #[dbus_method("Disable")]
- fn disable(&mut self) -> bool {
- false
- }
-
- #[dbus_method("GetAddress")]
- fn get_address(&self) -> String {
- String::from("")
- }
-}
diff --git a/gd/rust/linux/service/src/iface_bluetooth_gatt.rs b/gd/rust/linux/service/src/iface_bluetooth_gatt.rs
deleted file mode 100644
index c7dc3904e..000000000
--- a/gd/rust/linux/service/src/iface_bluetooth_gatt.rs
+++ /dev/null
@@ -1,73 +0,0 @@
-use btstack::bluetooth_gatt::{
- IBluetoothGatt, IScannerCallback, RSSISettings, ScanFilter, ScanSettings, ScanType,
-};
-use btstack::RPCProxy;
-
-use dbus::arg::RefArg;
-
-use dbus::nonblock::SyncConnection;
-use dbus::strings::{BusName, Path};
-
-use dbus_macros::{dbus_method, dbus_propmap, dbus_proxy_obj, generate_dbus_exporter};
-
-use dbus_projection::impl_dbus_arg_enum;
-use dbus_projection::DisconnectWatcher;
-
-use num_traits::cast::{FromPrimitive, ToPrimitive};
-
-use std::collections::HashMap;
-use std::error::Error;
-use std::sync::{Arc, Mutex};
-
-use crate::dbus_arg::{DBusArg, DBusArgError};
-
-#[allow(dead_code)]
-struct ScannerCallbackDBus {}
-
-#[dbus_proxy_obj(ScannerCallback, "org.chromium.bluetooth.ScannerCallback")]
-impl IScannerCallback for ScannerCallbackDBus {
- #[dbus_method("OnScannerRegistered")]
- fn on_scanner_registered(&self, _status: i32, _scanner_id: i32) {}
-}
-
-#[dbus_propmap(RSSISettings)]
-pub struct RSSISettingsDBus {
- low_threshold: i32,
- high_threshold: i32,
-}
-
-#[dbus_propmap(ScanSettings)]
-struct ScanSettingsDBus {
- interval: i32,
-
- window: i32,
-
- #[dbus_propmap_field_enum]
- scan_type: ScanType,
-
- #[dbus_propmap_field_propmap]
- rssi_settings: RSSISettings,
-}
-
-impl_dbus_arg_enum!(ScanType);
-
-#[dbus_propmap(ScanFilter)]
-struct ScanFilterDBus {}
-
-#[allow(dead_code)]
-struct IBluetoothGattDBus {}
-
-#[generate_dbus_exporter(export_bluetooth_gatt_dbus_obj, "org.chromium.bluetooth.BluetoothGatt")]
-impl IBluetoothGatt for IBluetoothGattDBus {
- #[dbus_method("RegisterScanner")]
- fn register_scanner(&self, callback: Box<dyn IScannerCallback + Send>) {}
-
- #[dbus_method("UnregisterScanner")]
- fn unregister_scanner(&self, scanner_id: i32) {}
-
- #[dbus_method("StartScan")]
- fn start_scan(&self, scanner_id: i32, settings: ScanSettings, filters: Vec<ScanFilter>) {}
-
- #[dbus_method("StopScan")]
- fn stop_scan(&self, scanner_id: i32) {}
-}
diff --git a/gd/rust/linux/service/src/main.rs b/gd/rust/linux/service/src/main.rs
deleted file mode 100644
index 755c61107..000000000
--- a/gd/rust/linux/service/src/main.rs
+++ /dev/null
@@ -1,100 +0,0 @@
-use bt_topshim::btif::BluetoothInterface;
-use bt_topshim::topstack;
-
-use dbus::channel::MatchingReceiver;
-use dbus::message::MatchRule;
-
-use dbus_crossroads::Crossroads;
-
-use dbus_projection::DisconnectWatcher;
-
-use dbus_tokio::connection;
-
-use futures::future;
-
-use btstack::bluetooth::btif_bluetooth_callbacks;
-use btstack::bluetooth::Bluetooth;
-use btstack::bluetooth_gatt::BluetoothGatt;
-use btstack::Stack;
-
-use std::error::Error;
-use std::sync::{Arc, Mutex};
-
-mod dbus_arg;
-mod iface_bluetooth;
-mod iface_bluetooth_gatt;
-
-const DBUS_SERVICE_NAME: &str = "org.chromium.bluetooth";
-const OBJECT_BLUETOOTH: &str = "/org/chromium/bluetooth/adapter";
-const OBJECT_BLUETOOTH_GATT: &str = "/org/chromium/bluetooth/gatt";
-
-/// Runs the Bluetooth daemon serving D-Bus IPC.
-fn main() -> Result<(), Box<dyn Error>> {
- let (tx, rx) = Stack::create_channel();
-
- let intf = Arc::new(Mutex::new(BluetoothInterface::new()));
- let bluetooth = Arc::new(Mutex::new(Bluetooth::new(tx.clone(), intf.clone())));
- let bluetooth_gatt = Arc::new(Mutex::new(BluetoothGatt::new(intf.clone())));
-
- topstack::get_runtime().block_on(async {
- // Connect to D-Bus system bus.
- let (resource, conn) = connection::new_system_sync()?;
-
- // The `resource` is a task that should be spawned onto a tokio compatible
- // reactor ASAP. If the resource ever finishes, we lost connection to D-Bus.
- topstack::get_runtime().spawn(async {
- let err = resource.await;
- panic!("Lost connection to D-Bus: {}", err);
- });
-
- // Request a service name and quit if not able to.
- conn.request_name(DBUS_SERVICE_NAME, false, true, false).await?;
-
- // Prepare D-Bus interfaces.
- let mut cr = Crossroads::new();
- cr.set_async_support(Some((
- conn.clone(),
- Box::new(|x| {
- topstack::get_runtime().spawn(x);
- }),
- )));
-
- intf.lock().unwrap().initialize(Arc::new(btif_bluetooth_callbacks(tx)), vec![]);
-
- // Run the stack main dispatch loop.
- topstack::get_runtime().spawn(Stack::dispatch(rx, bluetooth.clone()));
-
- // Set up the disconnect watcher to monitor client disconnects.
- let disconnect_watcher = Arc::new(Mutex::new(DisconnectWatcher::new()));
- disconnect_watcher.lock().unwrap().setup_watch(conn.clone()).await;
-
- // Register D-Bus method handlers of IBluetooth.
- iface_bluetooth::export_bluetooth_dbus_obj(
- OBJECT_BLUETOOTH,
- conn.clone(),
- &mut cr,
- bluetooth,
- disconnect_watcher.clone(),
- );
- // Register D-Bus method handlers of IBluetoothGatt.
- iface_bluetooth_gatt::export_bluetooth_gatt_dbus_obj(
- OBJECT_BLUETOOTH_GATT,
- conn.clone(),
- &mut cr,
- bluetooth_gatt,
- disconnect_watcher.clone(),
- );
-
- conn.start_receive(
- MatchRule::new_method_call(),
- Box::new(move |msg, conn| {
- cr.handle_message(msg, conn).unwrap();
- true
- }),
- );
-
- // Serve clients forever.
- future::pending::<()>().await;
- unreachable!()
- })
-}
diff --git a/gd/rust/linux/stack/Cargo.toml b/gd/rust/linux/stack/Cargo.toml
deleted file mode 100644
index 65987e8e1..000000000
--- a/gd/rust/linux/stack/Cargo.toml
+++ /dev/null
@@ -1,20 +0,0 @@
-[package]
-name = "btstack"
-version = "0.1.0"
-edition = "2018"
-
-[dependencies]
-bt_topshim = { path = "../../topshim" }
-bt_shim = { path = "../../shim" }
-
-btif_macros = { path = "btif_macros" }
-
-dbus = "0.9.2"
-
-num-traits = "*"
-num-derive = "*"
-
-tokio = { version = "1", features = ['bytes', 'fs', 'io-util', 'libc', 'macros', 'memchr', 'mio', 'net', 'num_cpus', 'rt', 'rt-multi-thread', 'sync', 'time', 'tokio-macros'] }
-
-[lib]
-path = "src/lib.rs"
diff --git a/gd/rust/linux/stack/btif_macros/Cargo.toml b/gd/rust/linux/stack/btif_macros/Cargo.toml
deleted file mode 100644
index 1810867c0..000000000
--- a/gd/rust/linux/stack/btif_macros/Cargo.toml
+++ /dev/null
@@ -1,12 +0,0 @@
-[package]
-name = "btif_macros"
-version = "0.1.0"
-edition = "2018"
-
-[lib]
-proc-macro = true
-
-[dependencies]
-syn = "1.0"
-quote = "1.0"
-proc-macro2 = "1.0"
diff --git a/gd/rust/linux/stack/btif_macros/src/lib.rs b/gd/rust/linux/stack/btif_macros/src/lib.rs
deleted file mode 100644
index bf9cc4383..000000000
--- a/gd/rust/linux/stack/btif_macros/src/lib.rs
+++ /dev/null
@@ -1,136 +0,0 @@
-extern crate proc_macro;
-
-use quote::quote;
-
-use std::fs::File;
-use std::io::Write;
-use std::path::Path;
-
-use syn::parse::Parser;
-use syn::punctuated::Punctuated;
-use syn::token::Comma;
-use syn::{Expr, FnArg, ItemTrait, Meta, Pat, TraitItem};
-
-use crate::proc_macro::TokenStream;
-
-fn debug_output_to_file(gen: &proc_macro2::TokenStream, filename: String) {
- let path = Path::new(filename.as_str());
- let mut file = File::create(&path).unwrap();
- file.write_all(gen.to_string().as_bytes()).unwrap();
-}
-
-/// Specifies the `Stack::Message` associated with a topshim callback.
-#[proc_macro_attribute]
-pub fn stack_message(_attr: TokenStream, item: TokenStream) -> TokenStream {
- let ori_item: proc_macro2::TokenStream = item.clone().into();
- let gen = quote! {
- #[allow(unused_variables)]
- #ori_item
- };
- gen.into()
-}
-
-/// Generates a topshim callback object that contains closures.
-///
-/// The closures are generated to be calls to the corresponding `Stack::Message`.
-#[proc_macro_attribute]
-pub fn btif_callbacks_generator(attr: TokenStream, item: TokenStream) -> TokenStream {
- let args = Punctuated::<Expr, Comma>::parse_separated_nonempty.parse(attr.clone()).unwrap();
-
- let fn_ident = if let Expr::Path(p) = &args[0] {
- p.path.get_ident().unwrap()
- } else {
- panic!("function name must be specified");
- };
-
- let callbacks_struct_ident = if let Expr::Path(p) = &args[1] {
- p.path.get_ident().unwrap()
- } else {
- panic!("callbacks struct ident must be specified");
- };
-
- let ast: ItemTrait = syn::parse(item.clone()).unwrap();
-
- let mut fn_names = quote! {};
- let mut closure_defs = quote! {};
- for attr in ast.items {
- if let TraitItem::Method(m) = attr {
- if m.attrs.len() != 1 {
- continue;
- }
-
- let attr = &m.attrs[0];
- if !attr.path.get_ident().unwrap().to_string().eq("stack_message") {
- continue;
- }
-
- let attr_args = attr.parse_meta().unwrap();
- let stack_message = if let Meta::List(meta_list) = attr_args {
- Some(meta_list.nested[0].clone())
- } else {
- None
- };
-
- if stack_message.is_none() {
- continue;
- }
-
- let mut arg_names = quote! {};
- for input in m.sig.inputs {
- if let FnArg::Typed(t) = input {
- if let Pat::Ident(i) = *t.pat {
- let attr_name = i.ident;
- arg_names = quote! { #arg_names #attr_name, };
- }
- }
- }
- let method_ident = m.sig.ident;
-
- fn_names = quote! {
- #fn_names
- #method_ident,
- };
-
- closure_defs = quote! {
- #closure_defs
- let tx_clone = tx.clone();
- let #method_ident = Box::new(move |#arg_names| {
- let tx = tx_clone.clone();
- topstack::get_runtime().spawn(async move {
- let result = tx.send(Message::#stack_message(#arg_names)).await;
- if let Err(e) = result {
- eprintln!("Error in sending message: {}", e);
- }
- });
- });
- };
- }
- }
-
- let ori_item = proc_macro2::TokenStream::from(item.clone());
-
- let gen = quote! {
- #ori_item
-
- /// Returns a callback object to be passed to topshim.
- pub fn #fn_ident(tx: tokio::sync::mpsc::Sender<Message>) -> #callbacks_struct_ident {
- #closure_defs
- #callbacks_struct_ident {
- #fn_names
- // TODO: Handle these in main loop.
- acl_state_changed: Box::new(|_, _, _, _| {}),
- bond_state_changed: Box::new(|_, _, _| {}),
- device_found: Box::new(|_, _| {}),
- discovery_state_changed: Box::new(|_| {}),
- pin_request: Box::new(|_, _, _, _| {}),
- remote_device_properties_changed: Box::new(|_, _, _, _| {}),
- ssp_request: Box::new(|_, _, _, _, _| {}),
- }
- }
- };
-
- // TODO: Have a simple framework to turn on/off macro-generated code debug.
- debug_output_to_file(&gen, format!("/tmp/out-{}.rs", fn_ident.to_string()));
-
- gen.into()
-}
diff --git a/gd/rust/linux/stack/src/bluetooth.rs b/gd/rust/linux/stack/src/bluetooth.rs
deleted file mode 100644
index a45f37bcb..000000000
--- a/gd/rust/linux/stack/src/bluetooth.rs
+++ /dev/null
@@ -1,192 +0,0 @@
-//! Anything related to the adapter API (IBluetooth).
-
-use bt_topshim::btif::ffi;
-use bt_topshim::btif::{BluetoothCallbacks, BluetoothInterface, BtState};
-use bt_topshim::topstack;
-
-use btif_macros::btif_callbacks_generator;
-use btif_macros::stack_message;
-
-use num_traits::cast::ToPrimitive;
-use num_traits::FromPrimitive;
-
-use std::fmt::Debug;
-use std::sync::Arc;
-use std::sync::Mutex;
-
-use tokio::sync::mpsc::Sender;
-
-use crate::{BDAddr, Message, RPCProxy};
-
-/// Defines the adapter API.
-pub trait IBluetooth {
- /// Adds a callback from a client who wishes to observe adapter events.
- fn register_callback(&mut self, callback: Box<dyn IBluetoothCallback + Send>);
-
- /// Enables the adapter.
- ///
- /// Returns true if the request is accepted.
- fn enable(&mut self) -> bool;
-
- /// Disables the adapter.
- ///
- /// Returns true if the request is accepted.
- fn disable(&mut self) -> bool;
-
- /// Returns the Bluetooth address of the local adapter.
- fn get_address(&self) -> String;
-}
-
-/// The interface for adapter callbacks registered through `IBluetooth::register_callback`.
-pub trait IBluetoothCallback: RPCProxy {
- /// When any of the adapter states is changed.
- fn on_bluetooth_state_changed(&self, prev_state: u32, new_state: u32);
-
- /// When any of the adapter local address is changed.
- fn on_bluetooth_address_changed(&self, addr: String);
-}
-
-/// Implementation of the adapter API.
-pub struct Bluetooth {
- intf: Arc<Mutex<BluetoothInterface>>,
- state: BtState,
- callbacks: Vec<(u32, Box<dyn IBluetoothCallback + Send>)>,
- callbacks_last_id: u32,
- tx: Sender<Message>,
- local_address: Option<BDAddr>,
-}
-
-impl Bluetooth {
- /// Constructs the IBluetooth implementation.
- pub fn new(tx: Sender<Message>, intf: Arc<Mutex<BluetoothInterface>>) -> Bluetooth {
- Bluetooth {
- tx,
- intf,
- state: BtState::Off,
- callbacks: vec![],
- callbacks_last_id: 0,
- local_address: None,
- }
- }
-
- fn update_local_address(&mut self, raw: &Vec<u8>) {
- self.local_address = Some(BDAddr::from_byte_vec(raw));
-
- for callback in &self.callbacks {
- callback.1.on_bluetooth_address_changed(self.local_address.unwrap().to_string());
- }
- }
-
- pub(crate) fn callback_disconnected(&mut self, id: u32) {
- self.callbacks.retain(|x| x.0 != id);
- }
-}
-
-#[btif_callbacks_generator(btif_bluetooth_callbacks, BluetoothCallbacks)]
-pub(crate) trait BtifBluetoothCallbacks {
- #[stack_message(BluetoothAdapterStateChanged)]
- fn adapter_state_changed(&mut self, state: BtState);
-
- #[stack_message(BluetoothAdapterPropertiesChanged)]
- fn adapter_properties_changed(
- &mut self,
- status: i32,
- num_properties: i32,
- properties: Vec<ffi::BtProperty>,
- );
-}
-
-#[derive(FromPrimitive, ToPrimitive, PartialEq, PartialOrd)]
-#[repr(i32)]
-#[derive(Debug)]
-enum PropertyType {
- BDName = 0x01,
- BDAddr,
- Uuids,
- ClassOfDevice,
- TypeOfDevice,
- ServiceRecord,
- AdapterScanMode,
- AdapterBondedDevices,
- AdapterDiscoverableTimeout,
- RemoteFriendlyName,
- RemoteRssi,
- RemoteVersionInfo,
- RemoteLocalLeFeatures,
- RemoteDynamicAudioBuffer = 0x10,
- Unknown = 0x100,
-}
-
-impl BtifBluetoothCallbacks for Bluetooth {
- fn adapter_state_changed(&mut self, state: BtState) {
- for callback in &self.callbacks {
- callback
- .1
- .on_bluetooth_state_changed(self.state.to_u32().unwrap(), state.to_u32().unwrap());
- }
-
- self.state = state;
- }
-
- #[allow(unused_variables)]
- fn adapter_properties_changed(
- &mut self,
- status: i32,
- num_properties: i32,
- properties: Vec<ffi::BtProperty>,
- ) {
- if status != 0 {
- return;
- }
-
- for prop in properties {
- let prop_type = PropertyType::from_i32(prop.prop_type);
-
- if prop_type.is_none() {
- continue;
- }
-
- match prop_type.unwrap() {
- PropertyType::BDAddr => {
- self.update_local_address(&prop.val);
- }
- _ => {}
- }
- }
- }
-}
-
-// TODO: Add unit tests for this implementation
-impl IBluetooth for Bluetooth {
- fn register_callback(&mut self, mut callback: Box<dyn IBluetoothCallback + Send>) {
- let tx = self.tx.clone();
-
- // TODO: Refactor into a separate wrap-around id generator.
- self.callbacks_last_id += 1;
- let id = self.callbacks_last_id;
-
- callback.register_disconnect(Box::new(move || {
- let tx = tx.clone();
- topstack::get_runtime().spawn(async move {
- let _result = tx.send(Message::BluetoothCallbackDisconnected(id)).await;
- });
- }));
-
- self.callbacks.push((id, callback))
- }
-
- fn enable(&mut self) -> bool {
- self.intf.lock().unwrap().enable() == 0
- }
-
- fn disable(&mut self) -> bool {
- self.intf.lock().unwrap().disable() == 0
- }
-
- fn get_address(&self) -> String {
- match self.local_address {
- None => String::from(""),
- Some(addr) => addr.to_string(),
- }
- }
-}
diff --git a/gd/rust/linux/stack/src/bluetooth_gatt.rs b/gd/rust/linux/stack/src/bluetooth_gatt.rs
deleted file mode 100644
index 425276818..000000000
--- a/gd/rust/linux/stack/src/bluetooth_gatt.rs
+++ /dev/null
@@ -1,86 +0,0 @@
-//! Anything related to the GATT API (IBluetoothGatt).
-
-use bt_topshim::btif::BluetoothInterface;
-
-use std::sync::{Arc, Mutex};
-
-/// Defines the GATT API.
-pub trait IBluetoothGatt {
- fn register_scanner(&self, callback: Box<dyn IScannerCallback + Send>);
-
- fn unregister_scanner(&self, scanner_id: i32);
-
- fn start_scan(&self, scanner_id: i32, settings: ScanSettings, filters: Vec<ScanFilter>);
- fn stop_scan(&self, scanner_id: i32);
-}
-
-/// Interface for scanner callbacks to clients, passed to `IBluetoothGatt::register_scanner`.
-pub trait IScannerCallback {
- /// When the `register_scanner` request is done.
- fn on_scanner_registered(&self, status: i32, scanner_id: i32);
-}
-
-#[derive(Debug, FromPrimitive, ToPrimitive)]
-#[repr(i32)]
-/// Scan type configuration.
-pub enum ScanType {
- Active = 0,
- Passive = 1,
-}
-
-impl Default for ScanType {
- fn default() -> Self {
- ScanType::Active
- }
-}
-
-/// Represents RSSI configurations for hardware offloaded scanning.
-// TODO: This is still a placeholder struct, not yet complete.
-#[derive(Debug, Default)]
-pub struct RSSISettings {
- pub low_threshold: i32,
- pub high_threshold: i32,
-}
-
-/// Represents scanning configurations to be passed to `IBluetoothGatt::start_scan`.
-#[derive(Debug, Default)]
-pub struct ScanSettings {
- pub interval: i32,
- pub window: i32,
- pub scan_type: ScanType,
- pub rssi_settings: RSSISettings,
-}
-
-/// Represents a scan filter to be passed to `IBluetoothGatt::start_scan`.
-#[derive(Debug, Default)]
-pub struct ScanFilter {}
-
-/// Implementation of the GATT API (IBluetoothGatt).
-pub struct BluetoothGatt {
- _intf: Arc<Mutex<BluetoothInterface>>,
-}
-
-impl BluetoothGatt {
- /// Constructs a new IBluetoothGatt implementation.
- pub fn new(intf: Arc<Mutex<BluetoothInterface>>) -> BluetoothGatt {
- BluetoothGatt { _intf: intf }
- }
-}
-
-impl IBluetoothGatt for BluetoothGatt {
- fn register_scanner(&self, _callback: Box<dyn IScannerCallback + Send>) {
- // TODO: implement
- }
-
- fn unregister_scanner(&self, _scanner_id: i32) {
- // TODO: implement
- }
-
- fn start_scan(&self, _scanner_id: i32, _settings: ScanSettings, _filters: Vec<ScanFilter>) {
- // TODO: implement
- }
-
- fn stop_scan(&self, _scanner_id: i32) {
- // TODO: implement
- }
-}
diff --git a/gd/rust/linux/stack/src/lib.rs b/gd/rust/linux/stack/src/lib.rs
deleted file mode 100644
index fc4f39ef3..000000000
--- a/gd/rust/linux/stack/src/lib.rs
+++ /dev/null
@@ -1,110 +0,0 @@
-//! Fluoride/GD Bluetooth stack.
-//!
-//! This crate provides the API implementation of the Fluoride/GD Bluetooth stack, independent of
-//! any RPC projection.
-
-#[macro_use]
-extern crate num_derive;
-
-pub mod bluetooth;
-pub mod bluetooth_gatt;
-
-use bt_topshim::btif::ffi;
-use bt_topshim::btif::BtState;
-
-use std::convert::TryInto;
-use std::fmt::{Debug, Formatter, Result};
-use std::sync::{Arc, Mutex};
-
-use tokio::sync::mpsc::channel;
-use tokio::sync::mpsc::{Receiver, Sender};
-
-use crate::bluetooth::{Bluetooth, BtifBluetoothCallbacks};
-
-/// Represents a Bluetooth address.
-// TODO: Add support for LE random addresses.
-#[derive(Copy, Clone)]
-pub struct BDAddr {
- val: [u8; 6],
-}
-
-impl Debug for BDAddr {
- fn fmt(&self, f: &mut Formatter<'_>) -> Result {
- f.write_fmt(format_args!(
- "{:02X}:{:02X}:{:02X}:{:02X}:{:02X}:{:02X}",
- self.val[0], self.val[1], self.val[2], self.val[3], self.val[4], self.val[5]
- ))
- }
-}
-
-impl ToString for BDAddr {
- fn to_string(&self) -> String {
- String::from(format!(
- "{:02X}:{:02X}:{:02X}:{:02X}:{:02X}:{:02X}",
- self.val[0], self.val[1], self.val[2], self.val[3], self.val[4], self.val[5]
- ))
- }
-}
-
-impl BDAddr {
- /// Constructs a BDAddr from a vector of 6 bytes.
- fn from_byte_vec(raw_addr: &Vec<u8>) -> BDAddr {
- BDAddr { val: raw_addr.clone().try_into().unwrap() }
- }
-}
-
-/// Message types that are sent to the stack main dispatch loop.
-pub enum Message {
- BluetoothAdapterStateChanged(BtState),
- BluetoothAdapterPropertiesChanged(i32, i32, Vec<ffi::BtProperty>),
- BluetoothCallbackDisconnected(u32),
-}
-
-/// Umbrella class for the Bluetooth stack.
-pub struct Stack {}
-
-impl Stack {
- /// Creates an mpsc channel for passing messages to the main dispatch loop.
- pub fn create_channel() -> (Sender<Message>, Receiver<Message>) {
- channel::<Message>(1)
- }
-
- /// Runs the main dispatch loop.
- pub async fn dispatch(mut rx: Receiver<Message>, bluetooth: Arc<Mutex<Bluetooth>>) {
- loop {
- let m = rx.recv().await;
-
- if m.is_none() {
- eprintln!("Message dispatch loop quit");
- break;
- }
-
- match m.unwrap() {
- Message::BluetoothAdapterStateChanged(state) => {
- bluetooth.lock().unwrap().adapter_state_changed(state);
- }
-
- Message::BluetoothAdapterPropertiesChanged(status, num_properties, properties) => {
- bluetooth.lock().unwrap().adapter_properties_changed(
- status,
- num_properties,
- properties,
- );
- }
-
- Message::BluetoothCallbackDisconnected(id) => {
- bluetooth.lock().unwrap().callback_disconnected(id);
- }
- }
- }
- }
-}
-
-/// Signifies that the object may be a proxy to a remote RPC object.
-///
-/// An object that implements RPCProxy trait signifies that the object may be a proxy to a remote
-/// RPC object. Therefore the object may be disconnected and thus should implement
-/// `register_disconnect` to let others observe the disconnection event.
-pub trait RPCProxy {
- fn register_disconnect(&mut self, f: Box<dyn Fn() + Send>);
-}
diff --git a/gd/rust/main/Android.bp b/gd/rust/main/Android.bp
deleted file mode 100644
index bed15b368..000000000
--- a/gd/rust/main/Android.bp
+++ /dev/null
@@ -1,24 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-rust_library {
- name: "libbt_main",
- defaults: ["gd_rust_defaults"],
- crate_name: "bt_main",
- srcs: ["src/lib.rs"],
- edition: "2018",
- rustlibs: [
- "libbt_hal",
- "libbt_hci",
- "libtokio",
- "libgddi",
- "libbt_common",
- "libgrpcio",
- ],
-}
diff --git a/gd/rust/main/Cargo.toml b/gd/rust/main/Cargo.toml
deleted file mode 100644
index 3a1e81ee1..000000000
--- a/gd/rust/main/Cargo.toml
+++ /dev/null
@@ -1,33 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bt_main"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-# bt deps
-bt_common = { path = "../common" }
-bt_hal = { path = "../hal" }
-bt_hci = { path = "../hci" }
-gddi = { path = "../gddi" }
-
-# external deps
-tokio = { version = "*", features = ['bytes', 'net'] }
-grpcio = "*"
-
-[lib]
-crate-types = ["rlib"]
diff --git a/gd/rust/main/src/lib.rs b/gd/rust/main/src/lib.rs
deleted file mode 100644
index 353ce54ec..000000000
--- a/gd/rust/main/src/lib.rs
+++ /dev/null
@@ -1,87 +0,0 @@
-//! Main BT lifecycle support
-
-use bt_common::GrpcFacade;
-use bt_hal::rootcanal_hal::RootcanalConfig;
-use bt_hal::snoop::{SnoopConfig, SnoopMode};
-use gddi::{module, Registry, RegistryBuilder, Stoppable};
-use std::sync::Arc;
-use tokio::runtime::Runtime;
-
-module! {
- stack_module,
- submodules {
- bt_hal::hal_module,
- bt_hci::hci_module,
- }
-}
-
-/// Central state manager
-pub struct Stack {
- registry: Arc<Registry>,
- rt: Arc<Runtime>,
-}
-
-impl Stack {
- /// Construct a new Stack
- pub async fn new(rt: Arc<Runtime>) -> Self {
- let registry = Arc::new(RegistryBuilder::new().register_module(stack_module).build());
- registry.inject(rt.clone()).await;
-
- Self { registry, rt }
- }
-
- /// Helper to set the rootcanal port
- pub async fn set_rootcanal_port(&self, port: Option<u16>) {
- if let Some(port) = port {
- self.registry.inject(RootcanalConfig::new("127.0.0.1", port)).await;
- }
- }
-
- /// Configures snoop with defaults
- pub async fn use_default_snoop(&self) {
- self.configure_snoop(None).await;
- }
-
- /// Configures snoop. If the path is provided, full logging is turned on
- pub async fn configure_snoop(&self, path: Option<String>) {
- let mut config = SnoopConfig::default();
- if let Some(path) = path {
- config.set_path(path);
- config.set_mode(SnoopMode::Full);
- }
- self.registry.inject(config).await;
- }
-
- /// Helper forwarding to underlying registry
- pub async fn get<T: 'static + Clone + Send + Sync + Stoppable>(&self) -> T {
- self.registry.get::<T>().await
- }
-
- /// Get, but blocks the current thread.
- pub fn get_blocking<T: 'static + Clone + Send + Sync + Stoppable>(&self) -> T {
- self.rt.block_on(self.get::<T>())
- }
-
- /// Helper to get a grpc service
- pub async fn get_grpc<T: 'static + Clone + Send + Sync + GrpcFacade + Stoppable>(
- &self,
- ) -> grpcio::Service {
- self.get::<T>().await.into_grpc()
- }
-
- /// Stop the stack
- pub async fn stop(&mut self) {
- self.registry.stop_all().await;
- }
-
- /// Stop, but blocks the current thread.
- pub fn stop_blocking(&mut self) {
- let rt = self.rt.clone();
- rt.block_on(self.stop());
- }
-
- /// Get a clone of the underlying runtime for this stack
- pub fn get_runtime(&self) -> Arc<Runtime> {
- self.rt.clone()
- }
-}
diff --git a/gd/rust/packets/Cargo.toml b/gd/rust/packets/Cargo.toml
deleted file mode 100644
index 3e31024be..000000000
--- a/gd/rust/packets/Cargo.toml
+++ /dev/null
@@ -1,34 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bt_packets"
-version = "0.0.1"
-edition = "2018"
-build = "build.rs"
-
-[dependencies]
-bt_hci_custom_types = { path = "../hci/custom_types" }
-
-bindgen = "*"
-bytes = "*"
-num-derive = "*"
-num-traits = "*"
-thiserror = "*"
-walkdir = "*"
-
-[lib]
-path = "lib.rs"
-crate-types = ["rlib"]
diff --git a/gd/rust/packets/build.rs b/gd/rust/packets/build.rs
deleted file mode 100644
index ddaf98185..000000000
--- a/gd/rust/packets/build.rs
+++ /dev/null
@@ -1,60 +0,0 @@
-//
-// Copyright 2021 Google, Inc.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at:
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-
-use std::env;
-use std::path::PathBuf;
-use std::process::Command;
-
-fn main() {
- let out_dir = PathBuf::from(env::var("OUT_DIR").unwrap());
-
- let gd_root = match env::var("PLATFORM_SUBDIR") {
- Ok(dir) => PathBuf::from(dir).join("bt/gd"),
- // Currently at //platform2/gd/rust/rust/packets
- Err(_) => PathBuf::from(env::current_dir().unwrap()).join("../..").canonicalize().unwrap(),
- };
-
- let input_files = [gd_root.join("hci/hci_packets.pdl")];
- let outputted = [out_dir.join("../../hci/hci_packets.rs")];
-
- // Find the packetgen tool. Expecting it at CARGO_HOME/bin
- let packetgen =
- PathBuf::from(env::var("CARGO_HOME").unwrap()).join("bin").join("bluetooth_packetgen");
-
- for i in 0..input_files.len() {
- let output = Command::new(packetgen.as_os_str().to_str().unwrap())
- .arg("--source_root=".to_owned() + gd_root.as_os_str().to_str().unwrap())
- .arg("--out=".to_owned() + out_dir.as_os_str().to_str().unwrap())
- .arg("--include=bt/gd")
- .arg("--rust")
- .arg(input_files[i].as_os_str().to_str().unwrap())
- .output()
- .unwrap();
-
- println!(
- "Status: {}, stdout: {}, stderr: {}",
- output.status,
- String::from_utf8_lossy(output.stdout.as_slice()),
- String::from_utf8_lossy(output.stderr.as_slice())
- );
-
- // File will be at ${OUT_DIR}/../../${input_files[i].strip('.pdl')}.rs
- std::fs::rename(
- outputted[i].as_os_str().to_str().unwrap(),
- out_dir.join(outputted[i].file_name().unwrap()).as_os_str().to_str().unwrap(),
- )
- .unwrap();
- }
-}
diff --git a/gd/rust/packets/lib.rs b/gd/rust/packets/lib.rs
deleted file mode 100644
index b702270b9..000000000
--- a/gd/rust/packets/lib.rs
+++ /dev/null
@@ -1,11 +0,0 @@
-//! reimport of generated packets (to go away once rust_genrule exists)
-
-#![allow(clippy::all)]
-#![allow(unused)]
-#![allow(missing_docs)]
-
-pub mod hci {
- use bt_hci_custom_types::*;
-
- include!(concat!(env!("OUT_DIR"), "/hci_packets.rs"));
-}
diff --git a/gd/rust/shim/Android.bp b/gd/rust/shim/Android.bp
deleted file mode 100644
index 5506e1100..000000000
--- a/gd/rust/shim/Android.bp
+++ /dev/null
@@ -1,158 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-rust_defaults {
- name: "gd_rust_defaults",
- target: {
- darwin: {
- enabled: false,
- },
- },
- host_supported: true,
-}
-
-cc_defaults {
- name: "gd_ffi_defaults",
- target: {
- darwin: {
- enabled: false,
- },
- },
-}
-
-rust_ffi_static {
- name: "libbt_shim_ffi",
- defaults: ["gd_rust_defaults"],
- crate_name: "bt_shim",
- srcs: ["src/lib.rs"],
- rustlibs: [
- "libbt_hal",
- "libbt_hci",
- "libbt_common",
- "libcxx",
- "libtokio",
- "libbt_main",
- "libbt_packets",
- "libfutures",
- "libnum_traits",
- "libnix",
- "liblog_rust",
- "libbt_facade_helpers",
- ],
- proc_macros: [
- "libpaste",
- ],
- whole_static_libs: [
- "libbt_callbacks_cxx",
- ],
-}
-
-cc_library_static {
- name: "libbluetooth_rust_interop",
- defaults: ["gd_ffi_defaults"],
- generated_headers: [
- "libbt_init_flags_bridge_header",
- "libbt_shim_bridge_header",
- "libbt_message_loop_thread_bridge_header",
- "cxx-bridge-header",
- ],
- generated_sources: [
- "libbt_init_flags_bridge_code",
- "libbt_shim_bridge_code",
- "libbt_message_loop_thread_bridge_code",
- ],
- export_generated_headers: [
- "libbt_init_flags_bridge_header",
- "libbt_shim_bridge_header",
- "libbt_message_loop_thread_bridge_header",
- "cxx-bridge-header",
- ],
- header_libs: ["libbt_callbacks_cxx_headers"],
- export_header_lib_headers: ["libbt_callbacks_cxx_headers"],
- cflags: [
- "-Wno-unused-const-variable",
- ],
- host_supported: true,
- apex_available: [
- "//apex_available:platform",
- "com.android.bluetooth.updatable",
- ],
- shared_libs: [
- "libchrome",
- ],
- whole_static_libs: [
- "libbt_shim_ffi",
- ],
-}
-
-cc_library_static {
- name: "libbt_callbacks_cxx",
- defaults: ["gd_ffi_defaults"],
- header_libs: ["libbt_callbacks_cxx_headers"],
- srcs: ["callbacks/callbacks.cc"],
- generated_headers: ["libbt_shim_bridge_header", "cxx-bridge-header"],
- shared_libs: [
- "libchrome",
- ],
- host_supported: true,
-}
-
-cc_library_headers {
- name: "libbt_callbacks_cxx_headers",
- local_include_dirs: ["callbacks"],
- host_supported: true,
-}
-
-genrule {
- name: "libbt_shim_bridge_header",
- tools: ["cxxbridge"],
- cmd: "$(location cxxbridge) $(in) --header > $(out)",
- srcs: ["src/bridge.rs"],
- out: ["src/bridge.rs.h"],
-}
-
-genrule {
- name: "libbt_shim_bridge_code",
- tools: ["cxxbridge"],
- cmd: "$(location cxxbridge) $(in) >> $(out)",
- srcs: ["src/bridge.rs"],
- out: ["bridge.cc"],
-}
-
-genrule {
- name: "libbt_init_flags_bridge_header",
- tools: ["cxxbridge"],
- cmd: "$(location cxxbridge) $(in) --header > $(out)",
- srcs: ["src/init_flags.rs"],
- out: ["src/init_flags.rs.h"],
-}
-
-genrule {
- name: "libbt_init_flags_bridge_code",
- tools: ["cxxbridge"],
- cmd: "$(location cxxbridge) $(in) >> $(out)",
- srcs: ["src/init_flags.rs"],
- out: ["init_flags.cc"],
-}
-
-genrule {
- name: "libbt_message_loop_thread_bridge_header",
- tools: ["cxxbridge"],
- cmd: "$(location cxxbridge) $(in) --header > $(out)",
- srcs: ["src/message_loop_thread.rs"],
- out: ["src/message_loop_thread.rs.h"],
-}
-
-genrule {
- name: "libbt_message_loop_thread_bridge_code",
- tools: ["cxxbridge"],
- cmd: "$(location cxxbridge) $(in) >> $(out)",
- srcs: ["src/message_loop_thread.rs"],
- out: ["message_loop_thread.cc"],
-}
diff --git a/gd/rust/shim/BUILD.gn b/gd/rust/shim/BUILD.gn
deleted file mode 100644
index 9402ac259..000000000
--- a/gd/rust/shim/BUILD.gn
+++ /dev/null
@@ -1,70 +0,0 @@
-#
-# Copyright 2020 Google
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-import("//common-mk/cxxbridge.gni")
-
-config("rust_shim_config") {
- include_dirs = [ "//bt/gd/rust/shim" ]
-}
-
-cxxbridge_header("shim_bridge_header") {
- sources = [ "src/bridge.rs" ]
- all_dependent_configs = [ ":rust_shim_config" ]
- deps = [ ":cxxlibheader" ]
-}
-
-cxxbridge_cc("shim_bridge_code") {
- sources = [ "src/bridge.rs" ]
- deps = [ ":shim_bridge_header" ]
- configs = [ "//bt/gd:gd_defaults" ]
-}
-
-cxxbridge_header("init_flags_bridge_header") {
- sources = [ "src/init_flags.rs" ]
- all_dependent_configs = [ ":rust_shim_config" ]
- deps = [ ":cxxlibheader" ]
-}
-
-cxxbridge_cc("init_flags_bridge_code") {
- sources = [ "src/init_flags.rs" ]
- deps = [ ":init_flags_bridge_header" ]
- configs = [ "//bt/gd:gd_defaults" ]
-}
-
-cxxbridge_header("message_loop_thread_bridge_header") {
- sources = [ "src/message_loop_thread.rs" ]
- all_dependent_configs = [ ":rust_shim_config" ]
- deps = [ ":cxxlibheader" ]
-}
-
-cxxbridge_cc("message_loop_thread_bridge_code") {
- sources = [ "src/message_loop_thread.rs" ]
- deps = [ ":message_loop_thread_bridge_header" ]
- configs = [ "//bt/gd:gd_defaults" ]
-}
-
-cxxbridge_libheader("cxxlibheader") {
- deps = []
-}
-
-static_library("libbluetooth_rust_interop") {
- deps = [
- ":cxxlibheader",
- ":init_flags_bridge_code",
- ":message_loop_thread_bridge_code",
- ":shim_bridge_code",
- ]
-}
diff --git a/gd/rust/shim/Cargo.toml b/gd/rust/shim/Cargo.toml
deleted file mode 100644
index b0e082b1b..000000000
--- a/gd/rust/shim/Cargo.toml
+++ /dev/null
@@ -1,56 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bt_shim"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-# BT dependencies
-bt_common = { path = "../common" }
-bt_facade_helpers = { path = "../facade/helpers" }
-bt_hal = { path = "../hal" }
-bt_hci = { path = "../hci" }
-bt_main = { path = "../main" }
-bt_packets = { path = "../packets" }
-
-# All external dependencies. Keep all versions at build/rust/Cargo.toml
-bindgen = "0.51"
-bytes = "1.0"
-cxx = { version = "1.0.42", features = ["c++17"] }
-env_logger = "0.8"
-futures = "0.3"
-grpcio = { version = "0.7", features = ["protobuf", "protobuf-codec", "openssl"] }
-grpcio-sys = { version = "*", features = ["openssl"] }
-lazy_static = "1.4"
-log = "0.4"
-nix = "0.19"
-num-derive = "0.3"
-num-traits = "0.2"
-paste = "1.0"
-proc-macro2 = "1.0.24"
-protobuf = "2.0"
-protoc-grpcio = "2.0"
-protoc-rust = "2.0"
-quote = "1.0.8"
-thiserror = "1.0"
-syn = { version = "1.0.58", features = ['default', 'full'] }
-tokio = { version = "1.0", features = ['bytes', 'fs', 'io-util', 'libc', 'macros', 'memchr', 'mio', 'net', 'num_cpus', 'rt', 'rt-multi-thread', 'sync', 'time', 'tokio-macros'] }
-tokio-stream = "0.1"
-walkdir = "2.2"
-
-[lib]
-path = "src/lib.rs"
diff --git a/gd/rust/shim/callbacks/callbacks.cc b/gd/rust/shim/callbacks/callbacks.cc
deleted file mode 100644
index dfae9b257..000000000
--- a/gd/rust/shim/callbacks/callbacks.cc
+++ /dev/null
@@ -1 +0,0 @@
-#include "callbacks/callbacks.h"
diff --git a/gd/rust/shim/callbacks/callbacks.h b/gd/rust/shim/callbacks/callbacks.h
deleted file mode 100644
index 98d9f81b6..000000000
--- a/gd/rust/shim/callbacks/callbacks.h
+++ /dev/null
@@ -1,73 +0,0 @@
-#pragma once
-
-#include "base/callback.h"
-#include "base/threading/sequenced_task_runner_handle.h"
-#include "rust/cxx.h"
-
-namespace bluetooth {
-namespace shim {
-namespace rust {
-
-template <class TArg>
-class TrampolineCallback {
- public:
- TrampolineCallback(base::Callback<void(TArg)> callback) : callback_(callback) {}
-
- void Run(TArg value) const {
- callback_.Run(value);
- }
-
- private:
- base::Callback<void(TArg)> callback_;
-};
-
-template <class TArg>
-class TrampolineOnceCallback {
- public:
- TrampolineOnceCallback(base::OnceCallback<void(TArg)> callback)
- : callback_(new base::OnceCallback<void(TArg)>(std::move(callback))) {}
- ~TrampolineOnceCallback() {
- if (callback_ != nullptr) {
- delete callback_;
- callback_ = nullptr;
- }
- }
-
- void Run(TArg value) const {
- std::move(*callback_).Run(value);
- delete callback_;
- ((TrampolineOnceCallback<TArg>*)this)->callback_ = nullptr;
- }
-
- private:
- base::OnceCallback<void(TArg)>* callback_;
-};
-
-class OnceClosure {
- public:
- OnceClosure(base::OnceClosure closure) : closure_(new base::OnceClosure(std::move(closure))) {}
- ~OnceClosure() {
- if (closure_ != nullptr) {
- delete closure_;
- closure_ = nullptr;
- }
- }
-
- void Run() const {
- std::move(*closure_).Run();
- delete closure_;
- ((OnceClosure*)this)->closure_ = nullptr;
- }
-
- private:
- base::OnceClosure* closure_;
-};
-
-using u8SliceCallback = TrampolineCallback<::rust::Slice<const uint8_t>>;
-using u8SliceOnceCallback = TrampolineOnceCallback<::rust::Slice<const uint8_t>>;
-
-} // namespace rust
-} // namespace shim
-} // namespace bluetooth
-
-#include "src/bridge.rs.h"
diff --git a/gd/rust/shim/src/bridge.rs b/gd/rust/shim/src/bridge.rs
deleted file mode 100644
index 1ae776ee0..000000000
--- a/gd/rust/shim/src/bridge.rs
+++ /dev/null
@@ -1,113 +0,0 @@
-//! Merged bridge
-
-pub use crate::controller::*;
-pub use crate::hci::*;
-pub use crate::stack::*;
-
-#[cxx::bridge(namespace = bluetooth::shim::rust)]
-pub mod ffi {
- extern "Rust" {
- type Stack;
- type Hci;
- type Controller;
-
- // Stack
- fn stack_create() -> Box<Stack>;
- fn stack_start(stack: &mut Stack);
- fn stack_stop(stack: &mut Stack);
-
- fn get_hci(stack: &mut Stack) -> Box<Hci>;
- fn get_controller(stack: &mut Stack) -> Box<Controller>;
-
- // HCI
- fn hci_set_acl_callback(hci: &mut Hci, callback: UniquePtr<u8SliceCallback>);
- fn hci_set_evt_callback(hci: &mut Hci, callback: UniquePtr<u8SliceCallback>);
- fn hci_set_le_evt_callback(hci: &mut Hci, callback: UniquePtr<u8SliceCallback>);
-
- fn hci_send_command(hci: &mut Hci, data: &[u8], callback: UniquePtr<u8SliceOnceCallback>);
- fn hci_send_acl(hci: &mut Hci, data: &[u8]);
- fn hci_register_event(hci: &mut Hci, event: u8);
- fn hci_register_le_event(hci: &mut Hci, subevent: u8);
-
- // Controller
- fn controller_supports_simple_pairing(c: &Controller) -> bool;
- fn controller_supports_secure_connections(c: &Controller) -> bool;
- fn controller_supports_simultaneous_le_bredr(c: &Controller) -> bool;
- fn controller_supports_interlaced_inquiry_scan(c: &Controller) -> bool;
- fn controller_supports_rssi_with_inquiry_results(c: &Controller) -> bool;
- fn controller_supports_extended_inquiry_response(c: &Controller) -> bool;
- fn controller_supports_role_switch(c: &Controller) -> bool;
- fn controller_supports_three_slot_packets(c: &Controller) -> bool;
- fn controller_supports_five_slot_packets(c: &Controller) -> bool;
- fn controller_supports_classic_2m_phy(c: &Controller) -> bool;
- fn controller_supports_classic_3m_phy(c: &Controller) -> bool;
- fn controller_supports_three_slot_edr_packets(c: &Controller) -> bool;
- fn controller_supports_five_slot_edr_packets(c: &Controller) -> bool;
- fn controller_supports_sco(c: &Controller) -> bool;
- fn controller_supports_hv2_packets(c: &Controller) -> bool;
- fn controller_supports_hv3_packets(c: &Controller) -> bool;
- fn controller_supports_ev3_packets(c: &Controller) -> bool;
- fn controller_supports_ev4_packets(c: &Controller) -> bool;
- fn controller_supports_ev5_packets(c: &Controller) -> bool;
- fn controller_supports_esco_2m_phy(c: &Controller) -> bool;
- fn controller_supports_esco_3m_phy(c: &Controller) -> bool;
- fn controller_supports_three_slot_esco_edr_packets(c: &Controller) -> bool;
- fn controller_supports_hold_mode(c: &Controller) -> bool;
- fn controller_supports_sniff_mode(c: &Controller) -> bool;
- fn controller_supports_park_mode(c: &Controller) -> bool;
- fn controller_supports_non_flushable_pb(c: &Controller) -> bool;
- fn controller_supports_sniff_subrating(c: &Controller) -> bool;
- fn controller_supports_encryption_pause(c: &Controller) -> bool;
- fn controller_supports_ble(c: &Controller) -> bool;
-
- fn controller_supports_privacy(c: &Controller) -> bool;
- fn controller_supports_packet_extension(c: &Controller) -> bool;
- fn controller_supports_connection_parameters_request(c: &Controller) -> bool;
- fn controller_supports_ble_2m_phy(c: &Controller) -> bool;
- fn controller_supports_ble_coded_phy(c: &Controller) -> bool;
- fn controller_supports_extended_advertising(c: &Controller) -> bool;
- fn controller_supports_periodic_advertising(c: &Controller) -> bool;
- fn controller_supports_peripheral_initiated_feature_exchange(c: &Controller) -> bool;
- fn controller_supports_connection_parameter_request(c: &Controller) -> bool;
- fn controller_supports_periodic_advertising_sync_transfer_sender(c: &Controller) -> bool;
- fn controller_supports_periodic_advertising_sync_transfer_recipient(c: &Controller)
- -> bool;
- fn controller_supports_connected_iso_stream_central(c: &Controller) -> bool;
- fn controller_supports_connected_iso_stream_peripheral(c: &Controller) -> bool;
- fn controller_supports_iso_broadcaster(c: &Controller) -> bool;
- fn controller_supports_synchronized_receiver(c: &Controller) -> bool;
-
- fn controller_supports_reading_remote_extended_features(c: &Controller) -> bool;
- fn controller_supports_enhanced_setup_synchronous_connection(c: &Controller) -> bool;
- fn controller_supports_enhanced_accept_synchronous_connection(c: &Controller) -> bool;
- fn controller_supports_ble_set_privacy_mode(c: &Controller) -> bool;
-
- fn controller_get_acl_buffer_length(c: &Controller) -> u16;
- fn controller_get_le_buffer_length(c: &Controller) -> u16;
- fn controller_get_iso_buffer_length(c: &Controller) -> u16;
- fn controller_get_le_suggested_default_data_length(c: &Controller) -> u16;
- fn controller_get_le_maximum_tx_data_length(c: &Controller) -> u16;
- fn controller_get_le_maximum_tx_time(c: &Controller) -> u16;
- fn controller_get_le_max_advertising_data_length(c: &Controller) -> u16;
- fn controller_get_le_supported_advertising_sets(c: &Controller) -> u8;
- fn controller_get_le_periodic_advertiser_list_size(c: &Controller) -> u8;
- fn controller_get_acl_buffers(c: &Controller) -> u16;
- fn controller_get_le_buffers(c: &Controller) -> u8;
- fn controller_get_iso_buffers(c: &Controller) -> u8;
- fn controller_get_le_connect_list_size(c: &Controller) -> u8;
- fn controller_get_le_resolving_list_size(c: &Controller) -> u8;
- fn controller_get_le_supported_states(c: &Controller) -> u64;
-
- fn controller_get_address(c: &Controller) -> String;
- }
-
- unsafe extern "C++" {
- include!("callbacks/callbacks.h");
-
- type u8SliceCallback;
- fn Run(self: &u8SliceCallback, data: &[u8]);
-
- type u8SliceOnceCallback;
- fn Run(self: &u8SliceOnceCallback, data: &[u8]);
- }
-}
diff --git a/gd/rust/shim/src/controller.rs b/gd/rust/shim/src/controller.rs
deleted file mode 100644
index de01bfdd6..000000000
--- a/gd/rust/shim/src/controller.rs
+++ /dev/null
@@ -1,149 +0,0 @@
-//! Controller shim
-
-use bt_hci::ControllerExports;
-use bt_packets::hci::OpCode;
-use paste::paste;
-use std::ops::Deref;
-use std::sync::Arc;
-
-#[derive(Clone)]
-pub struct Controller(pub Arc<ControllerExports>);
-impl Deref for Controller {
- type Target = Arc<ControllerExports>;
- fn deref(&self) -> &Self::Target {
- &self.0
- }
-}
-
-macro_rules! feature_getters {
- ($($id:ident),*) => {
- paste! {
- $(
- pub fn [<controller_supports_ $id>](c: &Controller) -> bool {
- c.features.$id
- }
- )*
- }
- }
-}
-
-feature_getters! {
- simple_pairing,
- secure_connections,
- simultaneous_le_bredr,
- interlaced_inquiry_scan,
- rssi_with_inquiry_results,
- extended_inquiry_response,
- role_switch,
- three_slot_packets,
- five_slot_packets,
- classic_2m_phy,
- classic_3m_phy,
- three_slot_edr_packets,
- five_slot_edr_packets,
- sco,
- hv2_packets,
- hv3_packets,
- ev3_packets,
- ev4_packets,
- ev5_packets,
- esco_2m_phy,
- esco_3m_phy,
- three_slot_esco_edr_packets,
- hold_mode,
- sniff_mode,
- park_mode,
- non_flushable_pb,
- sniff_subrating,
- encryption_pause,
- ble
-}
-
-macro_rules! le_feature_getters {
- ($($id:ident),*) => {
- paste! {
- $(
- pub fn [<controller_supports_ $id>](c: &Controller) -> bool {
- c.le_features.$id
- }
- )*
- }
- }
-}
-
-le_feature_getters! {
- privacy,
- packet_extension,
- connection_parameters_request,
- ble_2m_phy,
- ble_coded_phy,
- extended_advertising,
- periodic_advertising,
- peripheral_initiated_feature_exchange,
- connection_parameter_request,
- periodic_advertising_sync_transfer_sender,
- periodic_advertising_sync_transfer_recipient,
- connected_iso_stream_central,
- connected_iso_stream_peripheral,
- iso_broadcaster,
- synchronized_receiver
-}
-
-macro_rules! opcode_getters {
- ($($id:ident => $opcode:path),*) => {
- paste! {
- $(
- pub fn [<controller_supports_ $id>](c: &Controller) -> bool {
- c.commands.is_supported($opcode)
- }
- )*
- }
- }
-}
-
-opcode_getters! {
- reading_remote_extended_features => OpCode::ReadRemoteSupportedFeatures,
- enhanced_setup_synchronous_connection => OpCode::EnhancedSetupSynchronousConnection,
- enhanced_accept_synchronous_connection => OpCode::EnhancedAcceptSynchronousConnection,
- ble_set_privacy_mode => OpCode::LeSetPrivacyMode
-}
-
-macro_rules! field_getters {
- ($($id:ident : $type:ty),*) => {
- paste! {
- $(
- pub fn [<controller_get_ $id>](c: &Controller) -> $type {
- c.$id
- }
- )*
- }
- }
-}
-
-field_getters! {
- acl_buffer_length: u16,
- le_buffer_length: u16,
- iso_buffer_length: u16,
- le_suggested_default_data_length: u16,
- le_max_advertising_data_length: u16,
- le_supported_advertising_sets: u8,
- le_periodic_advertiser_list_size: u8,
- acl_buffers: u16,
- le_buffers: u8,
- iso_buffers: u8,
- le_connect_list_size: u8,
- le_resolving_list_size: u8,
- le_supported_states: u64
-}
-
-pub fn controller_get_le_maximum_tx_data_length(c: &Controller) -> u16 {
- c.le_max_data_length.supported_max_tx_octets
-}
-
-pub fn controller_get_le_maximum_tx_time(c: &Controller) -> u16 {
- c.le_max_data_length.supported_max_tx_time
-}
-
-pub fn controller_get_address(c: &Controller) -> String {
- c.address.to_string()
-}
diff --git a/gd/rust/shim/src/hci.rs b/gd/rust/shim/src/hci.rs
deleted file mode 100644
index e0764c8a1..000000000
--- a/gd/rust/shim/src/hci.rs
+++ /dev/null
@@ -1,89 +0,0 @@
-//! Hci shim
-
-use crate::bridge::ffi;
-use bt_facade_helpers::U8SliceRunnable;
-use bt_hci::facade::HciFacadeService;
-use bt_packets::hci::{AclPacket, CommandPacket, Packet};
-use std::sync::Arc;
-use tokio::runtime::Runtime;
-
-// we take ownership when we get the callbacks
-unsafe impl Send for ffi::u8SliceCallback {}
-unsafe impl Send for ffi::u8SliceOnceCallback {}
-
-struct CallbackWrapper {
- cb: cxx::UniquePtr<ffi::u8SliceCallback>,
-}
-
-impl U8SliceRunnable for CallbackWrapper {
- fn run(&self, data: &[u8]) {
- self.cb.Run(data);
- }
-}
-
-pub struct Hci {
- internal: HciFacadeService,
- rt: Arc<Runtime>,
-}
-
-impl Hci {
- pub fn new(rt: Arc<Runtime>, internal: HciFacadeService) -> Self {
- Self { rt, internal }
- }
-}
-
-pub fn hci_send_command(
- hci: &mut Hci,
- data: &[u8],
- callback: cxx::UniquePtr<ffi::u8SliceOnceCallback>,
-) {
- log::error!("sending command: {:02x?}", data);
- match CommandPacket::parse(data) {
- Ok(packet) => {
- let mut commands = hci.internal.commands.clone();
- hci.rt.spawn(async move {
- let resp = commands.send(packet).await.unwrap();
- callback.Run(&resp.to_bytes());
- });
- }
- Err(e) => panic!("could not parse command: {:?} {:02x?}", e, data),
- }
-}
-
-pub fn hci_send_acl(hci: &mut Hci, data: &[u8]) {
- match AclPacket::parse(data) {
- Ok(packet) => {
- let tx = hci.internal.acl_tx.clone();
- hci.rt.spawn(async move {
- tx.send(packet).await.unwrap();
- });
- }
- Err(e) => panic!("could not parse acl: {:?} {:02x?}", e, data),
- }
-}
-
-pub fn hci_register_event(hci: &mut Hci, event: u8) {
- let mut hci_facade = hci.internal.clone();
- hci.rt.spawn(async move {
- hci_facade.register_event(event.into()).await;
- });
-}
-
-pub fn hci_register_le_event(hci: &mut Hci, subevent: u8) {
- let mut hci_facade = hci.internal.clone();
- hci.rt.spawn(async move {
- hci_facade.register_le_event(subevent.into()).await;
- });
-}
-
-pub fn hci_set_acl_callback(hci: &mut Hci, cb: cxx::UniquePtr<ffi::u8SliceCallback>) {
- hci.internal.acl_rx.stream_runnable(&hci.rt, CallbackWrapper { cb });
-}
-
-pub fn hci_set_evt_callback(hci: &mut Hci, cb: cxx::UniquePtr<ffi::u8SliceCallback>) {
- hci.internal.evt_rx.stream_runnable(&hci.rt, CallbackWrapper { cb });
-}
-
-pub fn hci_set_le_evt_callback(hci: &mut Hci, cb: cxx::UniquePtr<ffi::u8SliceCallback>) {
- hci.internal.le_evt_rx.stream_runnable(&hci.rt, CallbackWrapper { cb });
-}
diff --git a/gd/rust/shim/src/init_flags.rs b/gd/rust/shim/src/init_flags.rs
deleted file mode 100644
index df45c09e1..000000000
--- a/gd/rust/shim/src/init_flags.rs
+++ /dev/null
@@ -1,22 +0,0 @@
-#[cxx::bridge(namespace = bluetooth::common::init_flags)]
-mod ffi {
- extern "Rust" {
- fn load(flags: Vec<String>);
- fn set_all_for_testing();
-
- fn gd_core_is_enabled() -> bool;
- fn gd_security_is_enabled() -> bool;
- fn gd_advertising_is_enabled() -> bool;
- fn gd_scanning_is_enabled() -> bool;
- fn gd_acl_is_enabled() -> bool;
- fn gd_l2cap_is_enabled() -> bool;
- fn gd_hci_is_enabled() -> bool;
- fn gd_controller_is_enabled() -> bool;
- fn gatt_robust_caching_is_enabled() -> bool;
- fn btaa_hci_is_enabled() -> bool;
- fn gd_rust_is_enabled() -> bool;
- fn gd_link_policy_is_enabled() -> bool;
- }
-}
-
-use bt_common::init_flags::*;
diff --git a/gd/rust/shim/src/lib.rs b/gd/rust/shim/src/lib.rs
deleted file mode 100644
index a87fb258d..000000000
--- a/gd/rust/shim/src/lib.rs
+++ /dev/null
@@ -1,10 +0,0 @@
-//! The main entry point for the legacy C++ code
-#[macro_use]
-extern crate lazy_static;
-
-mod bridge;
-mod controller;
-mod hci;
-mod init_flags;
-mod message_loop_thread;
-mod stack;
diff --git a/gd/rust/shim/src/message_loop_thread.rs b/gd/rust/shim/src/message_loop_thread.rs
deleted file mode 100644
index 107c85510..000000000
--- a/gd/rust/shim/src/message_loop_thread.rs
+++ /dev/null
@@ -1,81 +0,0 @@
-//! Shim out the main thread in the BT stack, to reduce threading dances at the shim boundary
-
-use bt_common::init_flags;
-use std::convert::TryInto;
-use std::sync::Arc;
-use std::time::Duration;
-use tokio::runtime::Runtime;
-use tokio::sync::mpsc::{unbounded_channel, UnboundedSender};
-
-#[cxx::bridge(namespace = bluetooth::shim::rust)]
-mod ffi {
- unsafe extern "C++" {
- include!("callbacks/callbacks.h");
-
- type OnceClosure;
- fn Run(&self);
- }
-
- extern "Rust" {
- type MessageLoopThread;
-
- fn main_message_loop_thread_create() -> Box<MessageLoopThread>;
- fn main_message_loop_thread_start(thread: &mut MessageLoopThread) -> i32;
- fn main_message_loop_thread_do_delayed(
- thread: &mut MessageLoopThread,
- closure: UniquePtr<OnceClosure>,
- delay_ms: i64,
- );
- }
-}
-
-unsafe impl Send for ffi::OnceClosure {}
-
-pub struct MessageLoopThread {
- rt: Arc<Runtime>,
- tx: UnboundedSender<cxx::UniquePtr<ffi::OnceClosure>>,
-}
-
-pub fn main_message_loop_thread_create() -> Box<MessageLoopThread> {
- assert!(init_flags::gd_rust_is_enabled());
-
- let rt = crate::stack::RUNTIME.clone();
- let (tx, mut rx) = unbounded_channel::<cxx::UniquePtr<ffi::OnceClosure>>();
- rt.spawn(async move {
- while let Some(c) = rx.recv().await {
- c.Run();
- }
- });
-
- Box::new(MessageLoopThread { rt, tx })
-}
-
-pub fn main_message_loop_thread_start(thread: &mut MessageLoopThread) -> i32 {
- assert!(init_flags::gd_rust_is_enabled());
-
- thread.rt.block_on(async move { nix::unistd::gettid().as_raw() })
-}
-
-pub fn main_message_loop_thread_do_delayed(
- thread: &mut MessageLoopThread,
- closure: cxx::UniquePtr<ffi::OnceClosure>,
- delay_ms: i64,
-) {
- assert!(init_flags::gd_rust_is_enabled());
- if delay_ms == 0 {
- if thread.tx.send(closure).is_err() {
- log::error!("could not post task - shutting down?");
- }
- } else {
- thread.rt.spawn(async move {
- // NOTE: tokio's sleep can't wake up the system...
- // but hey, neither could the message loop from libchrome.
- //
- // ...and this way we don't use timerfds arbitrarily.
- //
- // #yolo
- tokio::time::sleep(Duration::from_millis(delay_ms.try_into().unwrap_or(0))).await;
- closure.Run();
- });
- }
-}
diff --git a/gd/rust/shim/src/stack.rs b/gd/rust/shim/src/stack.rs
deleted file mode 100644
index 5c19ca486..000000000
--- a/gd/rust/shim/src/stack.rs
+++ /dev/null
@@ -1,74 +0,0 @@
-//! Stack management
-
-use crate::controller::Controller;
-use crate::hci::Hci;
-use bt_common::init_flags;
-use bt_hci::ControllerExports;
-use std::ops::{Deref, DerefMut};
-use std::sync::Arc;
-use tokio::runtime::{Builder, Runtime};
-
-pub struct Stack(bt_main::Stack);
-
-impl Deref for Stack {
- type Target = bt_main::Stack;
- fn deref(&self) -> &Self::Target {
- &self.0
- }
-}
-
-impl DerefMut for Stack {
- fn deref_mut(&mut self) -> &mut Self::Target {
- &mut self.0
- }
-}
-
-lazy_static! {
- pub static ref RUNTIME: Arc<Runtime> = Arc::new(
- Builder::new_multi_thread()
- .worker_threads(1)
- .max_blocking_threads(1)
- .enable_all()
- .build()
- .unwrap()
- );
-}
-
-pub fn stack_create() -> Box<Stack> {
- assert!(init_flags::gd_rust_is_enabled());
-
- let local_rt = RUNTIME.clone();
- RUNTIME.block_on(async move {
- let stack = bt_main::Stack::new(local_rt).await;
- stack.use_default_snoop().await;
-
- Box::new(Stack(stack))
- })
-}
-
-pub fn stack_start(_stack: &mut Stack) {
- assert!(init_flags::gd_rust_is_enabled());
-}
-
-pub fn stack_stop(stack: &mut Stack) {
- assert!(init_flags::gd_rust_is_enabled());
-
- stack.stop_blocking();
-}
-
-pub fn get_hci(stack: &mut Stack) -> Box<Hci> {
- assert!(init_flags::gd_rust_is_enabled());
- assert!(init_flags::gd_hci_is_enabled());
-
- Box::new(Hci::new(
- stack.get_runtime(),
- stack.get_blocking::<bt_hci::facade::HciFacadeService>(),
- ))
-}
-
-pub fn get_controller(stack: &mut Stack) -> Box<Controller> {
- assert!(init_flags::gd_rust_is_enabled());
- assert!(init_flags::gd_controller_is_enabled());
-
- Box::new(Controller(stack.get_blocking::<Arc<ControllerExports>>()))
-}
diff --git a/gd/rust/topshim/BUILD.gn b/gd/rust/topshim/BUILD.gn
deleted file mode 100644
index be52bc7dd..000000000
--- a/gd/rust/topshim/BUILD.gn
+++ /dev/null
@@ -1,56 +0,0 @@
-#
-# Copyright 2021 Google
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-import("//common-mk/cxxbridge.gni")
-
-config("rust_topshim_config") {
- include_dirs = [
- "//bt/gd/rust/topshim"
- ]
-}
-
-cxxbridge_header("btif_bridge_header") {
- sources = [ "src/btif.rs" ]
- all_dependent_configs = [ ":rust_topshim_config" ]
- deps = [":cxxlibheader"]
-}
-
-cxxbridge_cc("btif_bridge_code") {
- sources = [ "src/btif.rs" ]
- deps = [":btif_bridge_header"]
- configs = [ "//bt/gd:gd_defaults" ]
-}
-
-source_set("btif_cxx_bridge_code") {
- sources = [
- "btif/btif_shim.cc"
- ]
-
- deps = [":btif_bridge_header"]
- configs += ["//bt/gd:gd_defaults"]
-}
-
-cxxbridge_libheader("cxxlibheader") {
- deps = []
-}
-
-static_library("libbluetooth_topshim") {
- deps = [
- ":btif_bridge_code",
- ":btif_cxx_bridge_code",
- ":cxxlibheader",
- ]
-}
diff --git a/gd/rust/topshim/Cargo.toml b/gd/rust/topshim/Cargo.toml
deleted file mode 100644
index 31cc8d13d..000000000
--- a/gd/rust/topshim/Cargo.toml
+++ /dev/null
@@ -1,47 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-[package]
-name = "bt_topshim"
-version = "0.0.1"
-edition = "2018"
-
-[dependencies]
-# BT dependencies
-bt_common = { path = "../common" }
-bt_facade_helpers = { path = "../facade/helpers" }
-bt_hal = { path = "../hal" }
-bt_hci = { path = "../hci" }
-bt_main = { path = "../main" }
-bt_packets = { path = "../packets" }
-
-cxx = "*"
-lazy_static = "*"
-proc-macro2 = "*"
-num-derive = "*"
-num-traits = "*"
-tokio = { version = "*", features = ['bytes', 'fs', 'io-util', 'libc', 'macros', 'memchr', 'mio', 'net', 'num_cpus', 'rt', 'rt-multi-thread', 'sync', 'time', 'tokio-macros'] }
-tokio-stream = "*"
-
-# TODO(abps) - Decide whether we want to use bindgen
-# [build-dependencies]
-# bindgen = "0.51"
-# pkg-config = "0.3"
-
-[lib]
-path = "src/lib.rs"
-
-# Build is only necessary if using bindgen
-# build = "build.rs"
diff --git a/gd/rust/topshim/bindings/wrapper.h b/gd/rust/topshim/bindings/wrapper.h
deleted file mode 100644
index bfd13e30e..000000000
--- a/gd/rust/topshim/bindings/wrapper.h
+++ /dev/null
@@ -1,3 +0,0 @@
-#pragma once
-
-#include "include/hardware/bluetooth.h"
diff --git a/gd/rust/topshim/btif/btif_shim.cc b/gd/rust/topshim/btif/btif_shim.cc
deleted file mode 100644
index 70d87515d..000000000
--- a/gd/rust/topshim/btif/btif_shim.cc
+++ /dev/null
@@ -1,338 +0,0 @@
-/*
- * Copyright (C) 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "gd/rust/topshim/btif/btif_shim.h"
-
-#include <algorithm>
-#include <cstdlib>
-#include <cstring>
-#include <memory>
-
-#include "btcore/include/hal_util.h"
-#include "include/hardware/bluetooth.h"
-#include "rust/cxx.h"
-#include "src/btif.rs.h"
-
-namespace bluetooth {
-namespace topshim {
-namespace rust {
-namespace internal {
-// We need a global pointer to the Bluetooth interface because callbacks don't
-// pass back a pointer to the interface object. As a consequence, attempting to
-// initialize the interface multiple times should cause an abort.
-static BluetoothIntf* g_btif;
-
-namespace rusty = ::bluetooth::topshim::rust;
-
-static ::rust::Vec<BtProperty> prop_to_vec(int num_properties, bt_property_t* properties) {
- ::rust::Vec<BtProperty> rust_properties;
-
- for (int i = 0; i < num_properties; ++i) {
- ::rust::Vec<::rust::u8> val;
- val.reserve(properties[i].len);
-
- ::rust::u8* p = static_cast<::rust::u8*>(properties[i].val);
- for (int j = 0; j < properties[i].len; ++j) {
- val.push_back(p[j]);
- }
-
- BtProperty prop = {.prop_type = properties[i].type, .len = properties[i].len, .val = std::move(val)};
- rust_properties.push_back(std::move(prop));
- }
-
- return rust_properties;
-}
-
-static RustRawAddress to_rust_address(RawAddress* address) {
- RustRawAddress raddr;
- std::copy(std::begin(address->address), std::end(address->address), std::begin(raddr.address));
-
- return raddr;
-}
-
-static RawAddress from_rust_address(const RustRawAddress& address) {
- RawAddress r;
- r.FromOctets(address.address.data());
-
- return r;
-}
-
-static ::rust::String bdname_to_string(bt_bdname_t* bdname) {
- if (!bdname) {
- return std::string("");
- }
-
- return std::string(reinterpret_cast<const char*>(bdname->name));
-}
-
-static void adapter_state_changed_cb(bt_state_t state) {
- rusty::adapter_state_changed_callback(*g_btif->GetCallbacks(), state);
-}
-
-static void adapter_properties_cb(bt_status_t status, int num_properties, bt_property_t* properties) {
- rusty::adapter_properties_callback(
- *g_btif->GetCallbacks(), status, num_properties, prop_to_vec(num_properties, properties));
-}
-
-static void remote_device_properties_cb(
- bt_status_t status, RawAddress* bd_addr, int num_properties, bt_property_t* properties) {
- RustRawAddress addr = to_rust_address(bd_addr);
-
- rusty::remote_device_properties_callback(
- *g_btif->GetCallbacks(), status, addr, num_properties, prop_to_vec(num_properties, properties));
-}
-
-static void device_found_cb(int num_properties, bt_property_t* properties) {
- rusty::device_found_callback(*g_btif->GetCallbacks(), num_properties, prop_to_vec(num_properties, properties));
-}
-
-static void discovery_state_changed_cb(bt_discovery_state_t state) {
- rusty::discovery_state_changed_callback(*g_btif->GetCallbacks(), state);
-}
-
-static void pin_request_cb(RawAddress* remote_bd_addr, bt_bdname_t* bd_name, uint32_t cod, bool min_16_digit) {
- RustRawAddress addr = to_rust_address(remote_bd_addr);
- auto name = bdname_to_string(bd_name);
-
- rusty::pin_request_callback(*g_btif->GetCallbacks(), addr, name, cod, min_16_digit);
-}
-
-static void ssp_request_cb(
- RawAddress* remote_bd_addr,
- bt_bdname_t* bd_name,
- uint32_t cod,
- bt_ssp_variant_t pairing_variant,
- uint32_t pass_key) {
- RustRawAddress addr = to_rust_address(remote_bd_addr);
- auto name = bdname_to_string(bd_name);
-
- rusty::ssp_request_callback(*g_btif->GetCallbacks(), addr, name, cod, pairing_variant, pass_key);
-}
-
-static void bond_state_changed_cb(bt_status_t status, RawAddress* remote_bd_addr, bt_bond_state_t state) {
- RustRawAddress addr = to_rust_address(remote_bd_addr);
-
- rust::bond_state_changed_callback(*g_btif->GetCallbacks(), status, addr, state);
-}
-
-static void acl_state_changed_cb(
- bt_status_t status, RawAddress* remote_bd_addr, bt_acl_state_t state, bt_hci_error_code_t hci_reason) {
- RustRawAddress addr = to_rust_address(remote_bd_addr);
-
- rust::acl_state_changed_callback(*g_btif->GetCallbacks(), status, addr, state, hci_reason);
-}
-
-// TODO(abps) - Implement remaining callbacks
-
-static void thread_event_cb(bt_cb_thread_evt evt) {}
-
-static void dut_mode_recv_cb(uint16_t opcode, uint8_t* buf, uint8_t len) {}
-
-static void le_test_mode_cb(bt_status_t status, uint16_t num_packets) {}
-
-static void energy_info_cb(bt_activity_energy_info* energy_info, bt_uid_traffic_t* uid_data) {}
-
-bt_callbacks_t g_callbacks = {
- sizeof(bt_callbacks_t),
- adapter_state_changed_cb,
- adapter_properties_cb,
- remote_device_properties_cb,
- device_found_cb,
- discovery_state_changed_cb,
- pin_request_cb,
- ssp_request_cb,
- bond_state_changed_cb,
- acl_state_changed_cb,
- thread_event_cb,
- dut_mode_recv_cb,
- le_test_mode_cb,
- energy_info_cb,
-};
-} // namespace internal
-
-// Bluetooth interface handler
-BluetoothIntf::BluetoothIntf() : init_(false) {}
-
-BluetoothIntf::~BluetoothIntf() {
- // We made a copy of flags from initFlags; clean them up here
- if (flags_) {
- int i = 0;
- for (const char* flag = flags_[i]; flags_[i] != nullptr; ++i) {
- std::free(const_cast<void*>(static_cast<const void*>(flag)));
- }
-
- std::free(const_cast<void*>(static_cast<const void*>(flags_)));
- }
-}
-
-void BluetoothIntf::ConvertFlags(::rust::Vec<::rust::String>& initFlags) {
- // Allocate number of flags + 1 (last entry must be null to signify end)
- // Must be calloc so our cleanup correctly frees everything
- flags_ = static_cast<const char**>(std::calloc(initFlags.size() + 1, sizeof(char*)));
- if (!flags_) return;
-
- for (int i = 0; i < initFlags.size(); ++i) {
- flags_[i] = strndup(initFlags[i].data(), initFlags[i].size());
- if (!flags_) {
- return;
- }
- }
-}
-
-bool BluetoothIntf::Initialize(::rust::Box<RustCallbacks> callbacks, ::rust::Vec<::rust::String> initFlags) {
- if (init_) return true;
-
- callbacks_ = std::make_unique<::rust::Box<RustCallbacks>>(std::move(callbacks));
- ConvertFlags(initFlags);
-
- if (!hal_util_load_bt_library(&intf_)) {
- int ret = intf_->init(
- &internal::g_callbacks,
- false, // guest_mode,
- false, // is_niap_mode,
- 0, // config_compare_result,
- flags_,
- false // is_atv
- );
-
- // We only accept SUCCESS and not BT_STATUS_DONE. If some other interface
- // has already been registered, that means our callbacks won't be called and
- // that is problematic.
- init_ = ret == BT_STATUS_SUCCESS;
- }
-
- return init_;
-}
-
-void BluetoothIntf::CleanUp() const {
- intf_->cleanup();
-}
-
-int BluetoothIntf::Enable() const {
- return intf_->enable();
-}
-
-int BluetoothIntf::Disable() const {
- return intf_->disable();
-}
-
-int BluetoothIntf::GetAdapterProperties() const {
- return intf_->get_adapter_properties();
-}
-
-int BluetoothIntf::GetAdapterProperty(int prop) const {
- return intf_->get_adapter_property(static_cast<bt_property_type_t>(prop));
-}
-
-static bt_property_t convert_to_cprop(const BtProperty& prop) {
- bt_property_t c_prop = {
- .type = static_cast<bt_property_type_t>(prop.prop_type),
- .len = prop.len,
- .val = reinterpret_cast<void*>(const_cast<unsigned char*>(prop.val.data())),
- };
-
- return c_prop;
-}
-
-int BluetoothIntf::SetAdapterProperty(const BtProperty& prop) const {
- bt_property_t c_prop = convert_to_cprop(prop);
- return intf_->set_adapter_property(&c_prop);
-}
-
-int BluetoothIntf::GetRemoteDeviceProperties(const RustRawAddress& address) const {
- RawAddress addr = internal::from_rust_address(address);
-
- return intf_->get_remote_device_properties(&addr);
-}
-
-int BluetoothIntf::GetRemoteDeviceProperty(const RustRawAddress& address, int prop_type) const {
- RawAddress addr = internal::from_rust_address(address);
- return intf_->get_remote_device_property(&addr, static_cast<bt_property_type_t>(prop_type));
-}
-
-int BluetoothIntf::SetRemoteDeviceProperty(const RustRawAddress& address, const BtProperty& prop) const {
- RawAddress addr = internal::from_rust_address(address);
-
- bt_property_t c_prop = convert_to_cprop(prop);
- return intf_->set_remote_device_property(&addr, &c_prop);
-}
-
-int BluetoothIntf::GetRemoteServices(const RustRawAddress& address) const {
- RawAddress addr = internal::from_rust_address(address);
-
- return intf_->get_remote_services(&addr);
-}
-
-int BluetoothIntf::StartDiscovery() const {
- return intf_->start_discovery();
-}
-
-int BluetoothIntf::CancelDiscovery() const {
- return intf_->cancel_discovery();
-}
-
-int BluetoothIntf::CreateBond(const RustRawAddress& address, int transport) const {
- RawAddress addr = internal::from_rust_address(address);
-
- return intf_->create_bond(&addr, transport);
-}
-
-int BluetoothIntf::RemoveBond(const RustRawAddress& address) const {
- RawAddress addr = internal::from_rust_address(address);
-
- return intf_->remove_bond(&addr);
-}
-
-int BluetoothIntf::CancelBond(const RustRawAddress& address) const {
- RawAddress addr = internal::from_rust_address(address);
-
- return intf_->cancel_bond(&addr);
-}
-
-int BluetoothIntf::GetConnectionState(const RustRawAddress& address) const {
- RawAddress addr = internal::from_rust_address(address);
-
- return intf_->get_connection_state(&addr);
-}
-
-int BluetoothIntf::PinReply(
- const RustRawAddress& address, uint8_t accept, uint8_t pin_len, const BtPinCode& code) const {
- RawAddress addr = internal::from_rust_address(address);
-
- bt_pin_code_t pin_code;
- std::copy(std::begin(code.pin), std::end(code.pin), pin_code.pin);
-
- return intf_->pin_reply(&addr, accept, pin_len, &pin_code);
-}
-
-int BluetoothIntf::SspReply(const RustRawAddress& address, int ssp_variant, uint8_t accept, uint32_t passkey) const {
- RawAddress addr = internal::from_rust_address(address);
-
- return intf_->ssp_reply(&addr, static_cast<bt_ssp_variant_t>(ssp_variant), accept, passkey);
-}
-
-std::unique_ptr<BluetoothIntf> Load() {
- // Don't allow the bluetooth interface to be allocated twice
- if (internal::g_btif) std::abort();
-
- auto btif = std::make_unique<BluetoothIntf>();
- internal::g_btif = btif.get();
- return btif;
-}
-
-} // namespace rust
-} // namespace topshim
-} // namespace bluetooth
diff --git a/gd/rust/topshim/btif/btif_shim.h b/gd/rust/topshim/btif/btif_shim.h
deleted file mode 100644
index 35a5005bb..000000000
--- a/gd/rust/topshim/btif/btif_shim.h
+++ /dev/null
@@ -1,87 +0,0 @@
-/*
- * Copyright (C) 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#ifndef GD_RUST_TOPSHIM_BTIF_BTIF_SHIM_H
-#define GD_RUST_TOPSHIM_BTIF_BTIF_SHIM_H
-
-#include <memory>
-
-#include "include/hardware/bluetooth.h"
-#include "rust/cxx.h"
-
-namespace bluetooth {
-namespace topshim {
-namespace rust {
-
-struct RustCallbacks;
-struct InitParams;
-struct RustRawAddress;
-struct BtProperty;
-struct BtPinCode;
-struct BtUuid;
-
-class BluetoothIntf {
- public:
- BluetoothIntf();
- ~BluetoothIntf();
-
- bool Initialize(::rust::Box<RustCallbacks> callbacks, ::rust::Vec<::rust::String> initFlags);
- void CleanUp() const;
-
- int Enable() const;
- int Disable() const;
-
- int GetAdapterProperties() const;
- int GetAdapterProperty(int prop_type) const;
- int SetAdapterProperty(const BtProperty& prop) const;
-
- int GetRemoteDeviceProperties(const RustRawAddress& address) const;
- int GetRemoteDeviceProperty(const RustRawAddress& address, int prop_type) const;
- int SetRemoteDeviceProperty(const RustRawAddress& address, const BtProperty& prop) const;
-
- int GetRemoteServices(const RustRawAddress& address) const;
-
- int StartDiscovery() const;
- int CancelDiscovery() const;
-
- int CreateBond(const RustRawAddress& address, int transport) const;
- int RemoveBond(const RustRawAddress& address) const;
- int CancelBond(const RustRawAddress& address) const;
-
- int GetConnectionState(const RustRawAddress& address) const;
-
- int PinReply(const RustRawAddress& address, uint8_t accept, uint8_t pin_len, const BtPinCode& code) const;
- int SspReply(const RustRawAddress& address, int ssp_variant, uint8_t accept, uint32_t passkey) const;
-
- ::rust::Box<RustCallbacks>& GetCallbacks() {
- return *callbacks_;
- }
-
- private:
- void ConvertFlags(::rust::Vec<::rust::String>& flags);
-
- std::unique_ptr<::rust::Box<RustCallbacks>> callbacks_;
- bool init_;
- const char** flags_;
- const bt_interface_t* intf_;
-};
-
-std::unique_ptr<BluetoothIntf> Load();
-
-} // namespace rust
-} // namespace topshim
-} // namespace bluetooth
-
-#endif // GD_RUST_TOPSHIM_BTIF_BTIF_SHIM_H
diff --git a/gd/rust/topshim/src/btif.rs b/gd/rust/topshim/src/btif.rs
deleted file mode 100644
index f17a44c20..000000000
--- a/gd/rust/topshim/src/btif.rs
+++ /dev/null
@@ -1,420 +0,0 @@
-//! Bluetooth interface shim
-//!
-//! This is a shim interface for calling the C++ bluetooth interface via Rust.
-//!
-
-// TODO(abps): Remove this once callbacks are implemented
-#![allow(unused_variables)]
-
-use num_traits::FromPrimitive;
-use std::sync::Arc;
-use std::vec::Vec;
-
-#[derive(FromPrimitive, ToPrimitive, PartialEq, PartialOrd)]
-#[repr(i32)]
-pub enum BtState {
- Off = 0,
- On,
-}
-
-#[derive(FromPrimitive, ToPrimitive, PartialEq, PartialOrd, Debug)]
-#[repr(i32)]
-pub enum BtPropertyType {
- BdName = 0x1,
- BdAddr,
- Uuids,
- ClassOfDevice,
- TypeOfDevice,
- ServiceRecord,
- AdapterScanMode,
- AdapterBondedDevices,
- AdapterDiscoveryTimeout,
- RemoteFriendlyName,
- RemoteRssi,
- RemoteVersionInfo,
- LocalLeFeatures,
- LocalIoCaps,
- LocalIoCapsBle,
- DynamicAudioBuffer,
-
- Unknown = 0xFE,
- RemoteDeviceTimestamp = 0xFF,
-}
-
-#[derive(FromPrimitive, ToPrimitive, PartialEq, PartialOrd)]
-#[repr(i32)]
-pub enum BtDiscoveryState {
- Stopped = 0x0,
- Started,
-}
-
-#[derive(FromPrimitive, ToPrimitive, PartialEq, PartialOrd)]
-#[repr(i32)]
-pub enum BtStatus {
- Success = 0,
- Fail,
- NotReady,
- NoMemory,
- Busy,
- Done,
- Unsupported,
- InvalidParam,
- Unhandled,
- AuthFailure,
- RemoteDeviceDown,
- AuthRejected,
- JniEnvironmentError,
- JniThreadAttachError,
- WakeLockError,
-
- // Any statuses that couldn't be cleanly converted
- Unknown = 0xff,
-}
-
-// FFI is a public module because we want Rust and C++ to share enums listed
-// here. We redefine most of the Bluetooth structures we want to use because
-// of memory management issues (for example, some api calls will free the
-// memory passed into it). Bindgen was attempted but ultimately was not useful.
-#[cxx::bridge(namespace = bluetooth::topshim::rust)]
-pub mod ffi {
-
- pub struct BtPinCode {
- pin: [u8; 16],
- }
-
- pub struct BtProperty {
- prop_type: i32,
- len: i32,
- val: Vec<u8>,
- }
-
- pub struct BtUuid {
- uuid: [u8; 16],
- }
-
- pub struct RustRawAddress {
- address: [u8; 6],
- }
-
- unsafe extern "C++" {
- include!("btif/btif_shim.h");
-
- // Opaque type meant to represent C object for the Bluetooth interface.
- type BluetoothIntf;
-
- // Loads a unique pointer to the underlying interface
- fn Load() -> UniquePtr<BluetoothIntf>;
-
- fn Initialize(
- self: Pin<&mut Self>,
- callbacks: Box<RustCallbacks>,
- init_flags: Vec<String>,
- ) -> bool;
-
- fn CleanUp(&self);
- fn Enable(&self) -> i32;
- fn Disable(&self) -> i32;
-
- fn GetAdapterProperties(&self) -> i32;
- fn GetAdapterProperty(&self, prop_type: i32) -> i32;
- fn SetAdapterProperty(&self, prop: &BtProperty) -> i32;
-
- fn GetRemoteDeviceProperties(&self, address: &RustRawAddress) -> i32;
- fn GetRemoteDeviceProperty(&self, address: &RustRawAddress, prop_type: i32) -> i32;
- fn SetRemoteDeviceProperty(&self, address: &RustRawAddress, prop: &BtProperty) -> i32;
-
- fn GetRemoteServices(&self, address: &RustRawAddress) -> i32;
-
- fn StartDiscovery(&self) -> i32;
- fn CancelDiscovery(&self) -> i32;
-
- fn CreateBond(&self, address: &RustRawAddress, transport: i32) -> i32;
- // TODO(abps): Implement at P3
- // fn CreateBondOutOfBand(address: &RustRawAddress, transport: i32,
- // oob_data: &BtOutOfBandData) -> i32;
- fn RemoveBond(&self, address: &RustRawAddress) -> i32;
- fn CancelBond(&self, address: &RustRawAddress) -> i32;
-
- fn GetConnectionState(&self, address: &RustRawAddress) -> i32;
-
- fn PinReply(
- &self,
- address: &RustRawAddress,
- accept: u8,
- pin_len: u8,
- code: &BtPinCode,
- ) -> i32;
- fn SspReply(
- &self,
- address: &RustRawAddress,
- ssp_variant: i32,
- accept: u8,
- passkey: u32,
- ) -> i32;
-
- // TODO(abps): Implement at P1
- // fn GetProfileInterface(profile_id: &str) -> Option<BtProfileInterface>;
-
- // TODO(abps): Implement at P2
- // fn dut_mode_configure(enable: u8) -> i32;
- // fn dut_mode_send(opcode: u16, buf: [u8], len: u8) -> i32;
- // fn le_test_mode(opcode: u16, buf: [u8], len: u8) -> i32;
-
- // TODO(abps): Implement at P1
- // fn SetOsCallouts(callouts: Box<RustOsCallouts>) -> i32;
-
- // TODO(abps): Implement at P3
- // fn ReadEnergyInfo(&self) -> i32;
- // fn Dump(fd: i32, args: &[str]);
- // fn DumpMetrics() -> String;
- // fn ConfigClear(&self) -> i32;
- // fn InteropDatabaseClear(&self);
- // fn InteropDatabaseAdd(&self, feature: u16, address: &RustRawAddress, match_len: u8);
-
- // TODO(abps): Implement at P1
- // fn GetAvrcpService() -> *mut AvrcpServiceInterface;
-
- // TODO(abps): Implement at P3
- // fn ObfuscateAddress(&self, address: &RustRawAddress) -> String;
- // fn GetMetricId(&self, address: &RustRawAddress) -> i32;
- // fn SetDynamicAudioBufferSize(&self, codec: i32, size: i32) -> i32;
- }
-
- extern "Rust" {
- type RustCallbacks;
-
- // Callbacks from C++ to Rust. The rust callbacks are stored when the
- // `BluetoothIntf` is initialized and consist of closures that take the
- // same parameters (without the first callbacks param).
-
- fn adapter_state_changed_callback(cb: &RustCallbacks, state: i32);
- fn adapter_properties_callback(
- cb: &RustCallbacks,
- status: i32,
- num_properties: i32,
- properties: Vec<BtProperty>,
- );
- fn remote_device_properties_callback(
- cb: &RustCallbacks,
- status: i32,
- address: RustRawAddress,
- num_properties: i32,
- properties: Vec<BtProperty>,
- );
- fn device_found_callback(
- cb: &RustCallbacks,
- num_properties: i32,
- properties: Vec<BtProperty>,
- );
- fn discovery_state_changed_callback(cb: &RustCallbacks, state: i32);
- fn pin_request_callback(
- cb: &RustCallbacks,
- remote_addr: RustRawAddress,
- bd_name: String,
- cod: u32,
- min_16_digit: bool,
- );
- fn ssp_request_callback(
- cb: &RustCallbacks,
- remote_addr: RustRawAddress,
- bd_name: String,
- cod: u32,
- variant: i32,
- pass_key: u32,
- );
- fn bond_state_changed_callback(
- cb: &RustCallbacks,
- status: i32,
- remote_addr: RustRawAddress,
- state: i32,
- );
- fn acl_state_changed_callback(
- cb: &RustCallbacks,
- status: i32,
- remote_addr: RustRawAddress,
- state: i32,
- hci_reason: i32,
- );
-
- }
-
- unsafe impl Box<RustCallbacks> {}
-}
-
-/// Rust struct of closures for all callbacks from C++.
-///
-/// Note: Due to the need to interop with the C interface, we cannot pass
-/// additional state from C++ when calling these callbacks. Capture any
-/// state you need in the closure provided to this struct.
-pub struct BluetoothCallbacks {
- pub adapter_state_changed: Box<dyn Fn(BtState) + Send>,
- pub adapter_properties_changed: Box<dyn Fn(i32, i32, Vec<ffi::BtProperty>) + Send>,
- pub remote_device_properties_changed:
- Box<dyn Fn(i32, ffi::RustRawAddress, i32, Vec<ffi::BtProperty>) + Send>,
- pub device_found: Box<dyn Fn(i32, Vec<ffi::BtProperty>) + Send>,
- pub discovery_state_changed: Box<dyn Fn(BtDiscoveryState) + Send>,
- pub pin_request: Box<dyn Fn(ffi::RustRawAddress, String, u32, bool) + Send>,
- pub ssp_request: Box<dyn Fn(ffi::RustRawAddress, String, u32, i32, u32) + Send>,
- pub bond_state_changed: Box<dyn Fn(i32, ffi::RustRawAddress, i32) + Send>,
- pub acl_state_changed: Box<dyn Fn(i32, ffi::RustRawAddress, i32, i32) + Send>,
-}
-
-pub struct RustCallbacks {
- inner: Arc<BluetoothCallbacks>,
-}
-
-/// Rust interface to native Bluetooth.
-pub struct BluetoothInterface {
- internal: cxx::UniquePtr<ffi::BluetoothIntf>,
-}
-
-impl BluetoothInterface {
- pub fn new() -> BluetoothInterface {
- BluetoothInterface { internal: ffi::Load() }
- }
-
- /// Initialize the BluetoothInterface shim (not strictly necessary as
- /// Load also initializes the interface).
- pub fn initialize(
- &mut self,
- callbacks: Arc<BluetoothCallbacks>,
- init_flags: Vec<String>,
- ) -> bool {
- //ffi::Initialize(*self.internal)
- self.internal
- .pin_mut()
- .Initialize(Box::new(RustCallbacks { inner: callbacks.clone() }), init_flags)
- }
-
- /// Enable the Bluetooth adapter. This triggers an adapter_state_changed callback.
- pub fn enable(&mut self) -> i32 {
- self.internal.Enable()
- }
-
- /// Disable the Bluetooth adapter. This triggers an adapter state changed callback.
- pub fn disable(&mut self) -> i32 {
- self.internal.Disable()
- }
-
- pub fn cleanup(&mut self) {
- self.internal.CleanUp()
- }
-
- pub fn get_adapter_properties(&mut self) -> i32 {
- self.internal.GetAdapterProperties()
- }
-
- pub fn get_adapter_property(&mut self, prop_type: i32) -> i32 {
- self.internal.GetAdapterProperty(prop_type)
- }
-
- pub fn set_adapter_property(&mut self, prop: &ffi::BtProperty) -> i32 {
- self.internal.SetAdapterProperty(prop)
- }
-
- //fn GetRemoteDeviceProperties(&self, address: &RustRawAddress) -> i32;
- //fn GetRemoteDeviceProperty(&self, address: &RustRawAddress, prop_type: i32) -> i32;
- //fn SetRemoteDeviceProperty(&self, address: &RustRawAddress, prop: &BtProperty) -> i32;
- //fn GetRemoteServices(&self, address: &RustRawAddress) -> i32;
-
- pub fn start_discovery(&mut self) -> i32 {
- self.internal.StartDiscovery()
- }
- pub fn cancel_discovery(&mut self) -> i32 {
- self.internal.CancelDiscovery()
- }
-
- pub fn create_bond(&mut self, address: &ffi::RustRawAddress, transport: i32) -> i32 {
- self.internal.CreateBond(address, transport)
- }
- pub fn remove_bond(&mut self, address: &ffi::RustRawAddress) -> i32 {
- self.internal.RemoveBond(address)
- }
- pub fn cancel_bond(&mut self, address: &ffi::RustRawAddress) -> i32 {
- self.internal.CancelBond(address)
- }
-
- pub fn get_connection_state(&mut self, address: &ffi::RustRawAddress) -> i32 {
- self.internal.GetConnectionState(address)
- }
-}
-
-unsafe impl Send for BluetoothInterface {}
-
-fn adapter_state_changed_callback(cb: &RustCallbacks, state: i32) {
- let new_state = match BtState::from_i32(state) {
- Some(x) => x,
- None => BtState::Off,
- };
- (cb.inner.adapter_state_changed)(new_state);
-}
-
-fn adapter_properties_callback(
- cb: &RustCallbacks,
- status: i32,
- num_properties: i32,
- properties: Vec<ffi::BtProperty>,
-) {
- (cb.inner.adapter_properties_changed)(status, num_properties, properties);
-}
-
-fn remote_device_properties_callback(
- cb: &RustCallbacks,
- status: i32,
- address: ffi::RustRawAddress,
- num_properties: i32,
- properties: Vec<ffi::BtProperty>,
-) {
- (cb.inner.remote_device_properties_changed)(status, address, num_properties, properties);
-}
-
-fn device_found_callback(
- cb: &RustCallbacks,
- num_properties: i32,
- properties: Vec<ffi::BtProperty>,
-) {
- (cb.inner.device_found)(num_properties, properties);
-}
-fn discovery_state_changed_callback(cb: &RustCallbacks, state: i32) {
- let new_state = match BtDiscoveryState::from_i32(state) {
- Some(x) => x,
- None => BtDiscoveryState::Stopped,
- };
- (cb.inner.discovery_state_changed)(new_state);
-}
-fn pin_request_callback(
- cb: &RustCallbacks,
- remote_addr: ffi::RustRawAddress,
- bd_name: String,
- cod: u32,
- min_16_digit: bool,
-) {
- (cb.inner.pin_request)(remote_addr, bd_name, cod, min_16_digit);
-}
-fn ssp_request_callback(
- cb: &RustCallbacks,
- remote_addr: ffi::RustRawAddress,
- bd_name: String,
- cod: u32,
- variant: i32,
- pass_key: u32,
-) {
- (cb.inner.ssp_request)(remote_addr, bd_name, cod, variant, pass_key);
-}
-fn bond_state_changed_callback(
- cb: &RustCallbacks,
- status: i32,
- remote_addr: ffi::RustRawAddress,
- state: i32,
-) {
- (cb.inner.bond_state_changed)(status, remote_addr, state);
-}
-fn acl_state_changed_callback(
- cb: &RustCallbacks,
- status: i32,
- remote_addr: ffi::RustRawAddress,
- state: i32,
- hci_reason: i32,
-) {
- (cb.inner.acl_state_changed)(status, remote_addr, state, hci_reason);
-}
diff --git a/gd/rust/topshim/src/lib.rs b/gd/rust/topshim/src/lib.rs
deleted file mode 100644
index be771dd4d..000000000
--- a/gd/rust/topshim/src/lib.rs
+++ /dev/null
@@ -1,8 +0,0 @@
-//! The main entry point for Rust to C++.
-#[macro_use]
-extern crate lazy_static;
-#[macro_use]
-extern crate num_derive;
-
-pub mod btif;
-pub mod topstack;
diff --git a/gd/rust/topshim/src/topstack.rs b/gd/rust/topshim/src/topstack.rs
deleted file mode 100644
index 5306fea7e..000000000
--- a/gd/rust/topshim/src/topstack.rs
+++ /dev/null
@@ -1,23 +0,0 @@
-//! Stack on top of the Bluetooth interface shim
-//!
-//! Helpers for dealing with the stack on top of the Bluetooth interface.
-
-use std::sync::Arc;
-use tokio::runtime::{Builder, Runtime};
-
-lazy_static! {
- // Shared runtime for topshim handlers. All async tasks will get run by this
- // runtime and this will properly serialize all spawned tasks.
- pub static ref RUNTIME: Arc<Runtime> = Arc::new(
- Builder::new_multi_thread()
- .worker_threads(1)
- .max_blocking_threads(1)
- .enable_all()
- .build()
- .unwrap()
- );
-}
-
-pub fn get_runtime() -> Arc<Runtime> {
- RUNTIME.clone()
-}
diff --git a/gd/security/Android.bp b/gd/security/Android.bp
index 17ab2b901..6c373ba1e 100644
--- a/gd/security/Android.bp
+++ b/gd/security/Android.bp
@@ -1,20 +1,9 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothSecuritySources",
srcs: [
"ecc/multprecision.cc",
"ecc/p_256_ecc_pp.cc",
"ecdh_keys.cc",
- "facade_configuration_api.cc",
- "l2cap_security_module_interface.cc",
"pairing_handler_le.cc",
"pairing_handler_le_legacy.cc",
"pairing_handler_le_secure_connections.cc",
@@ -23,27 +12,19 @@ filegroup {
"security_module.cc",
":BluetoothSecurityChannelSources",
":BluetoothSecurityPairingSources",
- ":BluetoothSecurityRecordSources",
- ],
-}
-
-filegroup {
- name: "BluetoothSecurityUnitTestSources",
- srcs: [
- "ecc/multipoint_test.cc",
- "test/ecdh_keys_test.cc",
],
}
filegroup {
name: "BluetoothSecurityTestSources",
srcs: [
+ "ecc/multipoint_test.cc",
"pairing_handler_le_unittest.cc",
+ "test/ecdh_keys_test.cc",
"test/fake_l2cap_test.cc",
"test/pairing_handler_le_pair_test.cc",
":BluetoothSecurityChannelTestSources",
":BluetoothSecurityPairingTestSources",
- ":BluetoothSecurityRecordTestSources",
],
}
diff --git a/gd/security/BUILD.gn b/gd/security/BUILD.gn
deleted file mode 100644
index 1280311f8..000000000
--- a/gd/security/BUILD.gn
+++ /dev/null
@@ -1,57 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-source_set("BluetoothSecurityChannelSources") {
- sources = [ "channel/security_manager_channel.cc" ]
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ "//bt/gd:gd_default_deps" ]
-}
-
-source_set("BluetoothSecurityPairingSources") {
- sources = [ "pairing/classic_pairing_handler.cc" ]
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ "//bt/gd:gd_default_deps" ]
-}
-
-source_set("BluetoothSecurityRecordSources") {
- sources = [ "record/security_record_storage.cc" ]
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ "//bt/gd:gd_default_deps" ]
-}
-
-source_set("BluetoothSecuritySources") {
- sources = [
- "ecc/multprecision.cc",
- "ecc/p_256_ecc_pp.cc",
- "ecdh_keys.cc",
- "facade_configuration_api.cc",
- "internal/security_manager_impl.cc",
- "l2cap_security_module_interface.cc",
- "pairing_handler_le.cc",
- "pairing_handler_le_legacy.cc",
- "pairing_handler_le_secure_connections.cc",
- "security_manager.cc",
- "security_module.cc",
- ]
-
- deps = [
- ":BluetoothSecurityChannelSources",
- ":BluetoothSecurityPairingSources",
- ":BluetoothSecurityRecordSources",
- "//bt/gd:gd_default_deps",
- ]
-
- configs += [ "//bt/gd:gd_defaults" ]
-}
diff --git a/gd/security/cert/cert_security.py b/gd/security/cert/cert_security.py
deleted file mode 100644
index c5cfdab8d..000000000
--- a/gd/security/cert/cert_security.py
+++ /dev/null
@@ -1,364 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import logging
-
-from bluetooth_packets_python3 import hci_packets
-from cert.captures import HciCaptures
-from cert.closable import safeClose
-from cert.event_stream import EventStream
-from cert.matchers import HciMatchers
-from cert.py_hci import PyHci
-from cert.py_security import PySecurity
-from cert.truth import assertThat
-from datetime import datetime
-from google.protobuf import empty_pb2 as empty_proto
-from l2cap.classic import facade_pb2 as l2cap_facade
-from security.facade_pb2 import IoCapabilities
-from security.facade_pb2 import AuthenticationRequirements
-from security.facade_pb2 import OobDataPresent
-
-
-class CertSecurity(PySecurity):
- """
- Contain all of the certification stack logic for sending and receiving
- HCI commands following the Classic Pairing flows.
- """
- _io_cap_lookup = {
- IoCapabilities.DISPLAY_ONLY: hci_packets.IoCapability.DISPLAY_ONLY,
- IoCapabilities.DISPLAY_YES_NO_IO_CAP: hci_packets.IoCapability.DISPLAY_YES_NO,
- IoCapabilities.KEYBOARD_ONLY: hci_packets.IoCapability.KEYBOARD_ONLY,
- IoCapabilities.NO_INPUT_NO_OUTPUT: hci_packets.IoCapability.NO_INPUT_NO_OUTPUT,
- }
-
- _auth_req_lookup = {
- AuthenticationRequirements.NO_BONDING:
- hci_packets.AuthenticationRequirements.NO_BONDING,
- AuthenticationRequirements.NO_BONDING_MITM_PROTECTION:
- hci_packets.AuthenticationRequirements.NO_BONDING_MITM_PROTECTION,
- AuthenticationRequirements.DEDICATED_BONDING:
- hci_packets.AuthenticationRequirements.DEDICATED_BONDING,
- AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION:
- hci_packets.AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION,
- AuthenticationRequirements.GENERAL_BONDING:
- hci_packets.AuthenticationRequirements.GENERAL_BONDING,
- AuthenticationRequirements.GENERAL_BONDING_MITM_PROTECTION:
- hci_packets.AuthenticationRequirements.GENERAL_BONDING_MITM_PROTECTION,
- }
-
- _oob_present_lookup = {
- OobDataPresent.NOT_PRESENT: hci_packets.OobDataPresent.NOT_PRESENT,
- OobDataPresent.P192_PRESENT: hci_packets.OobDataPresent.P_192_PRESENT,
- OobDataPresent.P256_PRESENT: hci_packets.OobDataPresent.P_256_PRESENT,
- OobDataPresent.P192_AND_256_PRESENT: hci_packets.OobDataPresent.P_192_AND_256_PRESENT,
- }
-
- _hci_event_stream = None
- _io_caps = hci_packets.IoCapability.DISPLAY_ONLY
- _auth_reqs = hci_packets.AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION
- _secure_connections_enabled = False
-
- _hci = None
-
- MAX_PIN_LENGTH = 16
- MIN_PIN_LENGTH = 1
-
- def _enqueue_hci_command(self, command, expect_complete):
- if (expect_complete):
- self._hci.send_command(command)
- else:
- self._hci.send_command(command)
-
- def __init__(self, device):
- """
- Don't call super b/c the gRPC stream setup will crash test
- """
- logging.info("Cert: Init")
- self._device = device
- self._device.wait_channel_ready()
- self._hci = PyHci(device)
- self._hci.register_for_events(
- hci_packets.EventCode.ENCRYPTION_CHANGE, hci_packets.EventCode.CHANGE_CONNECTION_LINK_KEY_COMPLETE,
- hci_packets.EventCode.CENTRAL_LINK_KEY_COMPLETE, hci_packets.EventCode.RETURN_LINK_KEYS,
- hci_packets.EventCode.PIN_CODE_REQUEST, hci_packets.EventCode.LINK_KEY_REQUEST,
- hci_packets.EventCode.LINK_KEY_NOTIFICATION, hci_packets.EventCode.ENCRYPTION_KEY_REFRESH_COMPLETE,
- hci_packets.EventCode.IO_CAPABILITY_REQUEST, hci_packets.EventCode.IO_CAPABILITY_RESPONSE,
- hci_packets.EventCode.REMOTE_OOB_DATA_REQUEST, hci_packets.EventCode.SIMPLE_PAIRING_COMPLETE,
- hci_packets.EventCode.USER_PASSKEY_NOTIFICATION, hci_packets.EventCode.KEYPRESS_NOTIFICATION,
- hci_packets.EventCode.USER_CONFIRMATION_REQUEST, hci_packets.EventCode.USER_PASSKEY_REQUEST,
- hci_packets.EventCode.REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION)
- self._hci_event_stream = self._hci.get_event_stream()
-
- def create_bond(self, address, type):
- """
- Creates a bond from the cert perspective
- """
- logging.info("Cert: Creating bond to '%s' from '%s'" % (str(address), str(self._device.address)))
- # TODO(optedoblivion): Trigger connection to Send AuthenticationRequested
-
- def remove_bond(self, address, type):
- """
- We store the link key locally in the test and pretend
- So to remove_bond we need to Remove the "stored" data
- """
- pass
-
- def set_io_capabilities(self, io_capabilities):
- """
- Set the IO Capabilities used for the cert
- """
- logging.info("Cert: setting IO Capabilities data to '%s'" % self._io_capabilities_name_lookup.get(
- io_capabilities, "ERROR"))
- self._io_caps = self._io_cap_lookup.get(io_capabilities, hci_packets.IoCapability.DISPLAY_ONLY)
-
- def set_authentication_requirements(self, auth_reqs):
- """
- Establish authentication requirements for the stack
- """
- logging.info("Cert: setting Authentication Requirements data to '%s'" % self._auth_reqs_name_lookup.get(
- auth_reqs, "ERROR"))
- self._auth_reqs = self._auth_req_lookup.get(auth_reqs, hci_packets.AuthenticationRequirements.GENERAL_BONDING)
-
- def get_oob_data_from_controller(self, pb_oob_data_type):
- """
- Get the Out-of-band data for SSP pairing
-
- :param pb_oob_data_type: Type of data needed
- :return: a tuple of bytes (192c,192r,256c,256r) with increasing security; bytes may be all 0s depending on pb_oob_data_type value
-
- """
- oob_data_type = self._oob_present_lookup[pb_oob_data_type]
-
- if (oob_data_type == hci_packets.OobDataPresent.NOT_PRESENT):
- logging.warn("No data present, no need to call get_oob_data")
- return ([0 for i in range(0, 16)], [0 for i in range(0, 16)], [0 for i in range(0, 16)],
- [0 for i in range(0, 16)])
-
- logging.info("Cert: Requesting OOB data")
- if oob_data_type == hci_packets.OobDataPresent.P_192_PRESENT:
- # If host and controller supports secure connections we always used ReadLocalOobExtendedDataRequest
- if self._secure_connections_enabled:
- logging.info("Cert: Requesting P192 Data; secure connections")
- complete_capture = HciCaptures.ReadLocalOobExtendedDataCompleteCapture()
- self._enqueue_hci_command(hci_packets.ReadLocalOobExtendedDataBuilder(), True)
- logging.info("Cert: Waiting for OOB response from controller")
- assertThat(self._hci_event_stream).emits(complete_capture)
- command_complete = complete_capture.get()
- complete = hci_packets.ReadLocalOobExtendedDataCompleteView(command_complete)
- return (list(complete.GetC192()), list(complete.GetR192()), [0 for i in range(0, 16)],
- [0 for i in range(0, 16)])
- # else we use ReadLocalDataRequest
- else:
- logging.info("Cert: Requesting P192 Data; no secure connections")
- complete_capture = HciCaptures.ReadLocalOobDataCompleteCapture()
- self._enqueue_hci_command(hci_packets.ReadLocalOobDataBuilder(), True)
- logging.info("Cert: Waiting for OOB response from controller")
- assertThat(self._hci_event_stream).emits(complete_capture)
- command_complete = complete_capture.get()
- complete = hci_packets.ReadLocalOobDataCompleteView(command_complete)
- return (list(complete.GetC()), list(complete.GetR()), [0 for i in range(0, 16)],
- [0 for i in range(0, 16)])
-
- # Must be secure connection compatible to use these
- elif oob_data_type == hci_packets.OobDataPresent.P_256_PRESENT:
- logging.info("Cert: Requesting P256 Extended Data; secure connections")
- complete_capture = HciCaptures.ReadLocalOobExtendedDataCompleteCapture()
- self._enqueue_hci_command(hci_packets.ReadLocalOobExtendedDataBuilder(), True)
- logging.info("Cert: Waiting for OOB response from controller")
- assertThat(self._hci_event_stream).emits(complete_capture)
- command_complete = complete_capture.get()
- complete = hci_packets.ReadLocalOobExtendedDataCompleteView(command_complete)
- return ([0 for i in range(0, 16)], [0 for i in range(0, 16)], list(complete.GetC256()),
- list(complete.GetR256()))
-
- else: # Both
- logging.info("Cert: Requesting P192 AND P256 Extended Data; secure connections")
- complete_capture = HciCaptures.ReadLocalOobExtendedDataCompleteCapture()
- self._enqueue_hci_command(hci_packets.ReadLocalOobExtendedDataBuilder(), True)
- logging.info("Cert: Waiting for OOB response from controller")
- assertThat(self._hci_event_stream).emits(complete_capture)
- command_complete = complete_capture.get()
- complete = hci_packets.ReadLocalOobExtendedDataCompleteView(command_complete)
- return (list(complete.GetC192()), list(complete.GetR192()), list(complete.GetC256()),
- list(complete.GetR256()))
-
- def input_passkey(self, address, passkey):
- """
- Pretend to answer the pairing dialog as a user
- """
- logging.info("Cert: Waiting for PASSKEY request")
- assertThat(self._hci_event_stream).emits(HciMatchers.EventWithCode(hci_packets.EventCode.USER_PASSKEY_REQUEST))
- logging.info("Cert: Send user input passkey %d for %s" % (passkey, address))
- peer = address.decode('utf-8')
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.ENTRY_STARTED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.DIGIT_ENTERED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.DIGIT_ENTERED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.CLEARED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.DIGIT_ENTERED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.DIGIT_ENTERED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.DIGIT_ERASED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.DIGIT_ENTERED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.DIGIT_ENTERED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.DIGIT_ENTERED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.DIGIT_ENTERED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.DIGIT_ENTERED), True)
- self._enqueue_hci_command(
- hci_packets.SendKeypressNotificationBuilder(peer, hci_packets.KeypressNotificationType.ENTRY_COMPLETED),
- True)
- self._enqueue_hci_command(hci_packets.UserPasskeyRequestReplyBuilder(peer, passkey), True)
-
- def input_pin(self, address, pin):
- """
- Pretend to answer the pairing dialog as a user
- """
-
- if len(pin) > self.MAX_PIN_LENGTH or len(pin) < self.MIN_PIN_LENGTH:
- raise Exception("Pin code must be within range")
-
- logging.info("Cert: Waiting for PIN request")
- assertThat(self._hci_event_stream).emits(HciMatchers.PinCodeRequest())
- logging.info("Cert: Send user input PIN %s for %s" % (pin.decode(), address))
- peer = address.decode('utf-8')
- pin_list = list(pin)
- # Pad
- for i in range(self.MAX_PIN_LENGTH - len(pin_list)):
- pin_list.append(0)
- self._enqueue_hci_command(hci_packets.PinCodeRequestReplyBuilder(peer, len(pin), pin_list), True)
-
- def __send_ui_callback(self, address, callback_type, b, uid, pin):
- """
- Pretend to answer the pairing dailog as a user
- """
- logging.info("Cert: Send user input callback uid:%d; response: %s" % (uid, b))
- # TODO(optedoblivion): Make callback and set it to the module
-
- def enable_secure_simple_pairing(self):
- """
- This is called when you want to enable SSP for testing
- """
- logging.info("Cert: Sending WRITE_SIMPLE_PAIRING_MODE [True]")
- self._enqueue_hci_command(hci_packets.WriteSimplePairingModeBuilder(hci_packets.Enable.ENABLED), True)
- logging.info("Cert: Waiting for controller response")
- assertThat(self._hci_event_stream).emits(
- HciMatchers.CommandComplete(hci_packets.OpCode.WRITE_SIMPLE_PAIRING_MODE))
-
- def enable_secure_connections(self):
- """
- This is called when you want to enable secure connections support
- """
- logging.info("Cert: Sending WRITE_SECURE_CONNECTIONS_HOST_SUPPORT [True]")
- self._enqueue_hci_command(
- hci_packets.WriteSecureConnectionsHostSupportBuilder(hci_packets.Enable.ENABLED), True)
- logging.info("Cert: Waiting for controller response")
- assertThat(self._hci_event_stream).emits(
- HciMatchers.CommandComplete(hci_packets.OpCode.WRITE_SECURE_CONNECTIONS_HOST_SUPPORT))
- # TODO(optedoblivion): Figure this out and remove (see classic_pairing_handler.cc)
- #self._secure_connections_enabled = True
-
- def send_io_caps(self, address):
- logging.info("Cert: Waiting for IO_CAPABILITY_REQUEST")
- assertThat(self._hci_event_stream).emits(HciMatchers.IoCapabilityRequest())
- logging.info("Cert: Sending IO_CAPABILITY_REQUEST_REPLY")
- oob_data_present = hci_packets.OobDataPresent.NOT_PRESENT
- self._enqueue_hci_command(
- hci_packets.IoCapabilityRequestReplyBuilder(
- address.decode('utf8'), self._io_caps, oob_data_present, self._auth_reqs), True)
-
- def accept_pairing(self, dut_address, reply_boolean):
- """
- Here we handle the pairing events at the HCI level
- """
- logging.info("Cert: Waiting for LINK_KEY_REQUEST")
- assertThat(self._hci_event_stream).emits(HciMatchers.LinkKeyRequest())
- logging.info("Cert: Sending LINK_KEY_REQUEST_NEGATIVE_REPLY")
- self._enqueue_hci_command(hci_packets.LinkKeyRequestNegativeReplyBuilder(dut_address.decode('utf8')), True)
- self.send_io_caps(dut_address)
- logging.info("Cert: Waiting for USER_CONFIRMATION_REQUEST")
- assertThat(self._hci_event_stream).emits(HciMatchers.UserConfirmationRequest())
- logging.info("Cert: Sending Simulated User Response '%s'" % reply_boolean)
- if reply_boolean:
- logging.info("Cert: Sending USER_CONFIRMATION_REQUEST_REPLY")
- self._enqueue_hci_command(hci_packets.UserConfirmationRequestReplyBuilder(dut_address.decode('utf8')), True)
- logging.info("Cert: Waiting for SIMPLE_PAIRING_COMPLETE")
- assertThat(self._hci_event_stream).emits(HciMatchers.SimplePairingComplete())
- logging.info("Cert: Waiting for LINK_KEY_NOTIFICATION")
- assertThat(self._hci_event_stream).emits(HciMatchers.LinkKeyNotification())
- else:
- logging.info("Cert: Sending USER_CONFIRMATION_REQUEST_NEGATIVE_REPLY")
- self._enqueue_hci_command(
- hci_packets.UserConfirmationRequestNegativeReplyBuilder(dut_address.decode('utf8')), True)
- logging.info("Cert: Waiting for SIMPLE_PAIRING_COMPLETE")
- assertThat(self._hci_event_stream).emits(HciMatchers.SimplePairingComplete())
-
- def accept_oob_pairing(self, dut_address):
- logging.info("Cert: Waiting for IO_CAPABILITY_RESPONSE")
- assertThat(self._hci_event_stream).emits(HciMatchers.IoCapabilityResponse())
- self.send_io_caps(dut_address)
- logging.info("Cert: Waiting for SIMPLE_PAIRING_COMPLETE")
- ssp_complete_capture = HciCaptures.SimplePairingCompleteCapture()
- assertThat(self._hci_event_stream).emits(ssp_complete_capture)
- ssp_complete = ssp_complete_capture.get()
- logging.info(ssp_complete.GetStatus())
- assertThat(ssp_complete.GetStatus()).isEqualTo(hci_packets.ErrorCode.SUCCESS)
-
- def on_user_input(self, dut_address, reply_boolean, expected_ui_event):
- """
- Cert doesn't need the test to respond to the ui event
- Cert responds in accept pairing
- """
- pass
-
- def wait_for_bond_event(self, expected_bond_event):
- """
- A bond event will be triggered once the bond process
- is complete. For the DUT we need to wait for it,
- for Cert it isn't needed.
- """
- pass
-
- def enforce_security_policy(self, address, type, policy):
- """
- Pass for now
- """
- pass
-
- def wait_for_enforce_security_event(self, expected_enforce_security_event):
- """
- Cert side needs to pass
- """
- pass
-
- def wait_for_disconnect_event(self):
- """
- Cert side needs to pass
- """
- logging.info("Cert: Waiting for DISCONNECT_COMPLETE")
- assertThat(self._hci_event_stream).emits(HciMatchers.DisconnectionComplete())
-
- def close(self):
- safeClose(self._hci)
diff --git a/gd/security/cert/le_security_test.py b/gd/security/cert/le_security_test.py
deleted file mode 100644
index 7a0719bcb..000000000
--- a/gd/security/cert/le_security_test.py
+++ /dev/null
@@ -1,1097 +0,0 @@
-#
-# Copyright 2019 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import time
-
-from bluetooth_packets_python3 import hci_packets
-from bluetooth_packets_python3 import security_packets
-from cert.event_stream import EventStream
-from cert.gd_base_test import GdBaseTestClass
-from cert.matchers import HciMatchers
-from cert.matchers import SecurityMatchers
-from cert.metadata import metadata
-from cert.py_hci import PyHci
-from cert.py_le_security import PyLeSecurity
-from cert.truth import assertThat
-from datetime import timedelta
-from facade import common_pb2 as common
-from hci.facade import controller_facade_pb2 as controller_facade
-from hci.facade import le_advertising_manager_facade_pb2 as le_advertising_facade
-from hci.facade import le_initiator_address_facade_pb2 as le_initiator_address_facade
-from google.protobuf import empty_pb2 as empty_proto
-from neighbor.facade import facade_pb2 as neighbor_facade
-from security.cert.cert_security import CertSecurity
-from security.facade_pb2 import AuthenticationRequirements
-from security.facade_pb2 import BondMsgType
-from security.facade_pb2 import OobDataMessage
-from security.facade_pb2 import UiCallbackMsg
-from security.facade_pb2 import UiCallbackType
-from security.facade_pb2 import UiMsgType
-from security.facade_pb2 import LeAuthRequirementsMessage
-from security.facade_pb2 import LeIoCapabilityMessage
-from security.facade_pb2 import LeOobDataPresentMessage
-from security.facade_pb2 import LeMaximumEncryptionKeySizeMessage
-
-import time
-from bluetooth_packets_python3.hci_packets import OpCode
-from bluetooth_packets_python3.security_packets import PairingFailedReason
-
-from mobly import asserts
-
-LeIoCapabilities = LeIoCapabilityMessage.LeIoCapabilities
-LeOobDataFlag = LeOobDataPresentMessage.LeOobDataFlag
-
-DISPLAY_ONLY = LeIoCapabilityMessage(capabilities=LeIoCapabilities.DISPLAY_ONLY)
-KEYBOARD_ONLY = LeIoCapabilityMessage(capabilities=LeIoCapabilities.KEYBOARD_ONLY)
-NO_INPUT_NO_OUTPUT = LeIoCapabilityMessage(capabilities=LeIoCapabilities.NO_INPUT_NO_OUTPUT)
-KEYBOARD_DISPLAY = LeIoCapabilityMessage(capabilities=LeIoCapabilities.KEYBOARD_DISPLAY)
-
-OOB_NOT_PRESENT = LeOobDataPresentMessage(data_present=LeOobDataFlag.NOT_PRESENT)
-OOB_PRESENT = LeOobDataPresentMessage(data_present=LeOobDataFlag.PRESENT)
-
-
-class LeSecurityTest(GdBaseTestClass):
- """
- Collection of tests that each sample results from
- different (unique) combinations of io capabilities, authentication requirements, and oob data.
- """
-
- def setup_class(self):
- super().setup_class(dut_module='SECURITY', cert_module='SECURITY')
-
- def setup_test(self):
- super().setup_test()
-
- self.dut_security = PyLeSecurity(self.dut)
- self.cert_security = PyLeSecurity(self.cert)
- self.dut_hci = PyHci(self.dut)
-
- raw_addr = self.dut.hci_controller.GetMacAddress(empty_proto.Empty()).address
-
- self.dut_address = common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=raw_addr), type=common.PUBLIC_DEVICE_ADDRESS)
- privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_PUBLIC_ADDRESS,
- address_with_type=self.dut_address)
- self.dut.security.SetLeInitiatorAddressPolicy(privacy_policy)
- self.cert_address = common.BluetoothAddressWithType(
- address=common.BluetoothAddress(
- address=self.cert.hci_controller.GetMacAddress(empty_proto.Empty()).address),
- type=common.PUBLIC_DEVICE_ADDRESS)
- cert_privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_PUBLIC_ADDRESS,
- address_with_type=self.cert_address)
- self.cert.security.SetLeInitiatorAddressPolicy(cert_privacy_policy)
-
- asserts.skip("Unhandled race condition - Flaky test")
-
- def teardown_test(self):
- self.dut_hci.close()
- self.dut_security.close()
- self.cert_security.close()
- super().teardown_test()
-
- def _prepare_cert_for_connection(self):
- # DUT Advertises
- gap_name = hci_packets.GapData()
- gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(b'Im_The_CERT'))
- gap_data = le_advertising_facade.GapDataMsg(data=bytes(gap_name.Serialize()))
- config = le_advertising_facade.AdvertisingConfig(
- advertisement=[gap_data],
- interval_min=512,
- interval_max=768,
- advertising_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
- own_address_type=common.USE_PUBLIC_DEVICE_ADDRESS,
- channel_map=7,
- filter_policy=le_advertising_facade.AdvertisingFilterPolicy.ALL_DEVICES)
- request = le_advertising_facade.CreateAdvertiserRequest(config=config)
- create_response = self.cert.hci_le_advertising_manager.CreateAdvertiser(request)
-
- def _prepare_dut_for_connection(self):
- # DUT Advertises
- gap_name = hci_packets.GapData()
- gap_name.data_type = hci_packets.GapDataType.COMPLETE_LOCAL_NAME
- gap_name.data = list(bytes(b'Im_The_DUT'))
- gap_data = le_advertising_facade.GapDataMsg(data=bytes(gap_name.Serialize()))
- config = le_advertising_facade.AdvertisingConfig(
- advertisement=[gap_data],
- interval_min=512,
- interval_max=768,
- advertising_type=le_advertising_facade.AdvertisingEventType.ADV_IND,
- own_address_type=common.USE_PUBLIC_DEVICE_ADDRESS,
- channel_map=7,
- filter_policy=le_advertising_facade.AdvertisingFilterPolicy.ALL_DEVICES)
- request = le_advertising_facade.CreateAdvertiserRequest(config=config)
- create_response = self.dut.hci_le_advertising_manager.CreateAdvertiser(request)
-
- @metadata(pts_test_id="SM/MAS/PROT/BV-01-C", pts_test_name="SMP Time Out – IUT Initiator")
- def test_le_smp_timeout_iut_initiator(self):
- """
- Verify that the IUT handles the lack of pairing response after 30 seconds when acting as initiator.
- """
- self._prepare_cert_for_connection()
- self.dut.security.CreateBondLe(self.cert_address)
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BOND_FAILED, self.cert_address), timeout=timedelta(seconds=35))
-
- @metadata(pts_test_id="SM/SLA/PROT/BV-02-C", pts_test_name="SMP Time Out – IUT Responder")
- def test_le_smp_timeout_iut_responder(self):
- """
- Verify that the IUT handles the lack of pairing response after 30 seconds when acting as initiator.
- """
- self.cert.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeIoCapability(DISPLAY_ONLY)
-
- self._prepare_dut_for_connection()
-
- # 1. Lower Tester transmits Pairing Request.
- self.cert.security.CreateBondLe(self.dut_address)
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.cert_address), timeout=timedelta(seconds=35))
-
- # 2. IUT responds with Pairing Response.
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.cert_address))
-
- # 3. In phase 2, Lower Tester does not issue the expected Pairing Confirm.
-
- # Here the cert receives DISPLAY_PASSKEY_ENTRY. By not replying to it we make sure Pairing Confirm is never sent
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PASSKEY_ENTRY, self.dut_address), timeout=timedelta(seconds=5))
-
- # 4. IUT times out 30 seconds after issued Pairing Response and reports the failure to the Upper Tester.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BOND_FAILED, self.cert_address), timeout=timedelta(seconds=35))
-
- # 5. After additionally (at least) 10 seconds the Lower Tester issues the expected Pairing Confirm.
- # 6. The IUT closes the connection before receiving the delayed response or does not respond to it when it is received.
- #TODO:
- #assertThat(self.dut_hci.get_event_stream()).emits(HciMatchers.Disconnect())
-
- @metadata(pts_test_id="SM/MAS/JW/BV-01-C", pts_test_name="Just Works IUT Initiator – Success")
- def test_just_works_iut_initiator(self):
- """
- Verify that the IUT performs the Just Works pairing procedure correctly as central, initiator when both sides do not require MITM protection.
- """
- self._prepare_cert_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements()
-
- self.cert.security.SetLeIoCapability(DISPLAY_ONLY)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements()
-
- # 1. IUT transmits Pairing Request command with:
- # a. IO capability set to any IO capability
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. AuthReq Bonding Flags set to ‘00’ and the MITM flag set to ‘0’ and all the reserved bits are set to ‘0’
- self.dut.security.CreateBondLe(self.cert_address)
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.dut_address))
-
- # 2. Lower Tester responds with a Pairing Response command, with:
- # a. IO capability set to “KeyboardDisplayâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. AuthReq Bonding Flags set to ‘00’, and the MITM flag set to ‘0’ and all the reserved bits are set to ‘0’
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.dut_address))
-
- # 3. IUT and Lower Tester perform phase 2 of the just works pairing procedure and establish an encrypted link with the key generated in phase 2.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address))
-
- @metadata(pts_test_id="SM/SLA/JW/BV-02-C", pts_test_name="Just Works IUT Responder – Success")
- def test_just_works_iut_responder(self):
- """
- Verify that the IUT is able to perform the Just Works pairing procedure correctly when acting as peripheral, responder.
- """
- self._prepare_dut_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements()
-
- self.cert.security.SetLeIoCapability(NO_INPUT_NO_OUTPUT)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements()
-
- # 1. Lower Tester transmits Pairing Request command with:
- # a. IO capability set to “NoInputNoOutputâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. MITM flag set to ‘0’ and all reserved bits are set to ‘0’
- self.cert.security.CreateBondLe(self.dut_address)
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.cert_address))
-
- # 2. IUT responds with a Pairing Response command, with:
- # a. IO capability set to any IO capability
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.cert_address))
-
- # IUT and Lower Tester perform phase 2 of the just works pairing and establish an encrypted link with the generated STK.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address))
-
- @metadata(
- pts_test_id="SM/SLA/JW/BI-03-C", pts_test_name="Just Works IUT Responder – Handle AuthReq flag RFU correctly")
- def test_just_works_iut_responder_auth_req_rfu(self):
- """
- Verify that the IUT is able to perform the Just Works pairing procedure when receiving additional bits set in the AuthReq flag. Reserved For Future Use bits are correctly handled when acting as peripheral, responder.
- """
- self._prepare_dut_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_DISPLAY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements()
-
- self.cert.security.SetLeIoCapability(NO_INPUT_NO_OUTPUT)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(mitm=1, secure_connections=1, reserved_bits=2)
-
- # 1. Lower Tester transmits Pairing Request command with:
- # a. IO Capability set to â€NoInputNoOutputâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. MITM set to ‘0’ and all reserved bits are set to ‘1’
- self.cert.security.CreateBondLe(self.dut_address)
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.cert_address))
-
- # 2. IUT responds with a Pairing Response command, with:
- # a. IO capability set to any IO capability
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. All reserved bits are set to ‘0’
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.cert_address))
-
- # 3. IUT and Lower Tester perform phase 2 of the just works pairing and establish an encrypted link with the generated STK.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address))
-
- @metadata(
- pts_test_id="SM/MAS/JW/BI-04-C", pts_test_name="Just Works IUT Initiator – Handle AuthReq flag RFU correctly")
- def test_just_works_iut_initiator_auth_req_rfu(self):
- """
- Verify that the IUT is able to perform the Just Works pairing procedure when receiving additional bits set in the AuthReq flag. Reserved For Future Use bits are correctly handled when acting as central, initiator.
- """
- self._prepare_cert_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_DISPLAY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements()
-
- self.cert.security.SetLeIoCapability(NO_INPUT_NO_OUTPUT)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(mitm=1, secure_connections=1, reserved_bits=3)
-
- # 1. IUT transmits a Pairing Request command with:
- # a. IO Capability set to any IO Capability
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. All reserved bits are set to ‘0’. For the purposes of this test the Secure Connections bit and the Keypress bits in the AuthReq bonding flag set by the IUT are ignored by the Lower Tester.
- self.dut.security.CreateBondLe(self.cert_address)
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.dut_address))
-
- # 2. Lower Tester responds with a Pairing Response command, with:
- # a. IO Capability set to “NoInputNoOutputâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. AuthReq bonding flag set to the value indicated in the IXIT [7] for ‘Bonding Flags’ and the MITM flag set to ‘0’ and all reserved bits are set to ‘1’. The SC and Keypress bits in the AuthReq bonding flag are set to 0 by the Lower Tester for this test.
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.dut_address))
-
- # 3. IUT and Lower Tester perform phase 2 of the just works pairing and establish an encrypted link with the generated STK.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address))
-
- @metadata(
- pts_test_id="SM/MAS/SCJW/BV-01-C", pts_test_name="Just Works, IUT Initiator, Secure Connections – Success")
- def test_just_works_iut_initiator_secure_connections(self):
- """
- Verify that the IUT supporting LE Secure Connections performs the Just Works or Numeric Comparison pairing procedure correctly as initiator.
- """
- self._prepare_cert_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements(secure_connections=1)
-
- self.cert.security.SetLeIoCapability(DISPLAY_ONLY)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(secure_connections=1)
-
- # 1. IUT transmits Pairing Request command with:
- # a. IO capability set to any IO capability
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. AuthReq Bonding Flags set to ‘00’, the MITM flag set to either ‘0’ for Just Works or '1' for Numeric Comparison, Secure Connections flag set to '1' and all the reserved bits are set to ‘0’
- self.dut.security.CreateBondLe(self.cert_address)
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.dut_address))
-
- # 2. Lower Tester responds with a Pairing Response command, with:
- # a. IO capability set to “KeyboardDisplayâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. AuthReq Bonding Flags set to ‘00’, the MITM flag set to ‘0’, Secure Connections flag set to '1' and all the reserved bits are set to ‘0’
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.dut_address))
-
- # 3. IUT and Lower Tester perform phase 2 of the Just Works or Numeric Comparison pairing procedure according to the MITM flag and IO capabilities, and establish an encrypted link with the LTK generated in phase 2.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address))
-
- @metadata(
- pts_test_id="SM/SLA/SCJW/BV-02-C", pts_test_name="Just Works, IUT Responder, Secure Connections – Success")
- def test_just_works_iut_responder_secure_connections(self):
- """
- Verify that the IUT supporting LE Secure Connections is able to perform the Just Works or Numeric Comparison pairing procedure correctly when acting as responder.
- """
- self._prepare_dut_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements(secure_connections=1)
-
- self.cert.security.SetLeIoCapability(NO_INPUT_NO_OUTPUT)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(secure_connections=1)
-
- # 1. Lower Tester transmits Pairing Request command with:
- # a. IO capability set to “NoInputNoOutputâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. AuthReq Bonding Flags set to ‘00’, MITM flag set to ‘0’, Secure Connections flag set to '1' and all reserved bits are set to ‘0’
- self.cert.security.CreateBondLe(self.dut_address)
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.cert_address))
-
- # 2. IUT responds with a Pairing Response command, with:
- # a. IO capability set to any IO capability
- # b. AuthReq Bonding Flags set to ‘00’, MITM flag set to either ‘0’ for Just Works or '1' for Numeric Comparison, Secure Connections flag set to '1' and all reserved bits are set to ‘0’
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.cert_address))
-
- # 3. UT and Lower Tester perform phase 2 of the Just Works or Numeric Comparison pairing procedure according to the MITM flag and IO capabilities, and establish an encrypted link with the LTK generated in phase 2.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address))
-
- @metadata(
- pts_test_id="SM/SLA/SCJW/BV-03-C",
- pts_test_name="Just Works, IUT Responder, Secure Connections – Handle AuthReq Flag RFU Correctly")
- def test_just_works_iut_responder_secure_connections_auth_req_rfu(self):
- """
- Verify that the IUT is able to perform the Just Works pairing procedure when receiving additional bits set in the AuthReq flag. Reserved For Future Use bits are correctly handled when acting as peripheral, responder.
- """
- self._prepare_dut_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_DISPLAY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements(secure_connections=1)
-
- self.cert.security.SetLeIoCapability(NO_INPUT_NO_OUTPUT)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(mitm=1, secure_connections=1, reserved_bits=3)
-
- # 1. Lower Tester transmits Pairing Request command with:
- # a. IO Capability set to â€NoInputNoOutputâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. MITM set to ‘0’ and all reserved bits are set to a random value.
- self.cert.security.CreateBondLe(self.dut_address)
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.cert_address))
-
- # 2. IUT responds with a Pairing Response command, with:
- # a. IO capability set to any IO capability
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. All reserved bits are set to ‘0’
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.cert_address))
-
- # 3. IUT and Lower Tester perform phase 2 of the Just Works pairing and establish an encrypted link with the generated LTK.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address))
-
- @metadata(
- pts_test_id="SM/MAS/SCJW/BV-04-C",
- pts_test_name="Just Works, IUT Initiator, Secure Connections – Handle AuthReq Flag RFU Correctly")
- def test_just_works_iut_initiator_secure_connections_auth_req_rfu(self):
- """
- Verify that the IUT is able to perform the Just Works pairing procedure when receiving additional bits set in the AuthReq flag. Reserved For Future Use bits are correctly handled when acting as central, initiator.
- """
- self._prepare_cert_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_DISPLAY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements(secure_connections=1)
-
- self.cert.security.SetLeIoCapability(NO_INPUT_NO_OUTPUT)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(mitm=1, secure_connections=1, reserved_bits=3)
-
- # 1. IUT transmits a Pairing Request command with:
- # a. IO Capability set to any IO Capability
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. All reserved bits are set to ‘0’.
- self.dut.security.CreateBondLe(self.cert_address)
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.dut_address))
-
- # 2. Lower Tester responds with a Pairing Response command, with:
- # a. IO Capability set to “NoInputNoOutputâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. AuthReq bonding flag set to the value indicated in the IXIT [7] for ‘Bonding Flags’ and the MITM flag set to ‘0’ and all reserved bits are set to a random value.
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.dut_address))
-
- # 3. IUT and Lower Tester perform phase 2 of the Just Works pairing and establish an encrypted link with the generated LTK.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address))
-
- @metadata(
- pts_test_id="SM/MAS/EKS/BV-01-C",
- pts_test_name="IUT initiator, Lower Tester Maximum Encryption Key Size = Min_Encryption_Key_Length")
- def test_min_encryption_key_size_equal_to_max_iut_initiator(self):
- """
- Verify that the IUT uses correct key size during encryption as initiator.
- """
- self._prepare_cert_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_DISPLAY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements(secure_connections=1)
- self.dut.security.SetLeMaximumEncryptionKeySize(
- LeMaximumEncryptionKeySizeMessage(maximum_encryption_key_size=0x10))
-
- self.cert.security.SetLeIoCapability(NO_INPUT_NO_OUTPUT)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(mitm=1, secure_connections=1)
- self.cert.security.SetLeMaximumEncryptionKeySize(
- LeMaximumEncryptionKeySizeMessage(maximum_encryption_key_size=0x07))
-
- # 1. IUT transmits a Pairing Request
- self.dut.security.CreateBondLe(self.cert_address)
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.dut_address))
-
- # 2. Lower Tester responds with Pairing Response command with Maximum Encryption Key Size field set to Min_Encryption_Key_Length’.
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.dut_address))
-
- # 3. IUT and Lower Tester perform phase 2 of the LE pairing and establish an encrypted link with the key generated in phase 2.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address))
-
- @metadata(
- pts_test_id="SM/SLA/EKS/BV-02-C",
- pts_test_name="IUT Responder, Lower Tester Maximum Encryption Key Size = Min_Encryption_Key_Length")
- def test_min_encryption_key_size_equal_to_max_iut_responder(self):
- """
- Verify that the IUT uses correct key size during encryption as responder.
- """
- self._prepare_dut_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements()
- self.dut.security.SetLeMaximumEncryptionKeySize(
- LeMaximumEncryptionKeySizeMessage(maximum_encryption_key_size=0x07))
-
- self.cert.security.SetLeIoCapability(NO_INPUT_NO_OUTPUT)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements()
- self.cert.security.SetLeMaximumEncryptionKeySize(
- LeMaximumEncryptionKeySizeMessage(maximum_encryption_key_size=0x10))
-
- # 1. Lower Tester initiates Pairing Request command with Maximum Encryption Key Size field set to Min_Encryption_Key_Length’.
- self.cert.security.CreateBondLe(self.dut_address)
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.cert_address))
-
- # 2. IUT responds with Pairing Response command.
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.cert_address))
-
- #3. IUT and Lower Tester perform phase 2 of the LE pairing and establish an encrypted link with the key generated in phase 2.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address))
-
- @metadata(
- pts_test_id="SM/MAS/EKS/BI-01-C",
- pts_test_name="IUT initiator, Lower Tester Maximum Encryption Key Size < Min_Encryption_Key_Length")
- def test_min_encryption_key_size_less_than_min_iut_initiator(self):
- """
- Verify that the IUT checks that the resultant encryption key size is not smaller than the minimum key size.
- """
- self._prepare_cert_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_DISPLAY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements(secure_connections=1)
- self.dut.security.SetLeMaximumEncryptionKeySize(
- LeMaximumEncryptionKeySizeMessage(maximum_encryption_key_size=0x10))
-
- self.cert.security.SetLeIoCapability(NO_INPUT_NO_OUTPUT)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(mitm=1, secure_connections=1)
- self.cert.security.SetLeMaximumEncryptionKeySize(
- LeMaximumEncryptionKeySizeMessage(maximum_encryption_key_size=0x06))
-
- # 1. IUT transmits a Pairing Request
- self.dut.security.CreateBondLe(self.cert_address)
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.dut_address))
-
- # 2. Lower Tester responds with Pairing Response command with Maximum Encryption Key Size field set to Min_Encryption_Key_Length-1’.
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.dut_address))
-
- # 3. IUT transmits the Pairing Failed command.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BOND_FAILED, self.cert_address,
- int(PairingFailedReason.ENCRYPTION_KEY_SIZE)))
-
- @metadata(
- pts_test_id="SM/SLA/EKS/BI-02-C",
- pts_test_name="IUT Responder, Lower Tester Maximum Encryption Key Size < Min_Encryption_Key_Length")
- def test_min_encryption_key_size_less_than_min_iut_responder(self):
- """
- Verify that the IUT uses correct key size during encryption as responder.
- """
- self._prepare_dut_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements()
- self.dut.security.SetLeMaximumEncryptionKeySize(
- LeMaximumEncryptionKeySizeMessage(maximum_encryption_key_size=0x06))
-
- self.cert.security.SetLeIoCapability(NO_INPUT_NO_OUTPUT)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements()
- self.cert.security.SetLeMaximumEncryptionKeySize(
- LeMaximumEncryptionKeySizeMessage(maximum_encryption_key_size=0x10))
-
- # 1. Lower Tester initiates Pairing Request command with Maximum Encryption Key Size field set to Min_Encryption_Key_Length-1.
- self.cert.security.CreateBondLe(self.dut_address)
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.cert_address))
-
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.cert_address))
-
- #3. IUT transmits the Pairing Failed command.
- assertThat(self.cert_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BOND_FAILED, self.dut_address,
- int(PairingFailedReason.ENCRYPTION_KEY_SIZE)))
-
- @metadata(
- pts_test_id="SM/MAS/SCPK/BV-01-C", pts_test_name="Passkey Entry, IUT Initiator, Secure Connections – Success")
- def test_passkey_entry_iut_initiator_secure_connections(self):
- """
- Verify that the IUT supporting LE Secure Connections performs the Passkey Entry pairing procedure correctly as central, initiator.
- """
- self._prepare_cert_for_connection()
-
- self.dut.security.SetLeIoCapability(DISPLAY_ONLY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements(secure_connections=1)
-
- self.cert.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(mitm=1, secure_connections=1)
-
- # 1. IUT transmits Pairing Request command with:
- # a. IO capability set to “DisplayOnly†or “KeyboardOnlyâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. AuthReq bonding flag set to ‘00’, the MITM flag set to ‘0’ and Secure Connections flag set to '1'. Keypress bit is set to '1' if supported
- self.dut.security.CreateBondLe(self.cert_address)
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.dut_address))
-
- # 2. Lower Tester responds with a Pairing Response command, with:
- # a. IO capability set to “KeyboardOnlyâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. AuthReq bonding flag set to ‘00’, the MITM flag set to ‘1’, Secure Connections flag set to '1' and all reserved bits are set to ‘0’. Keypress bit is set to '1' if supported by the IUT.
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.dut_address))
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PASSKEY_ENTRY, self.dut_address))
-
- # 3. During the phase 2 pairing, the IUT displays the 6-digit passkey while the Lower Tester prompts user to enter the 6-digit passkey. If the IUT’s IO capabilities are “KeyboardOnly†the passkey is not displayed and both IUT and Lower Tester enter the same 6-digit passkey. If Keypress bit is set, pairing keypress notifications are sent by the Lower Tester.
- passkey = self.dut_security.wait_for_ui_event_passkey()
-
- if passkey == 0:
- print("Passkey did not arrive into test")
-
- # 4. IUT and Lower Tester use the same 6-digit passkey.
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PASSKEY, numeric_value=passkey, unique_id=1, address=self.dut_address))
-
- # 5. IUT and Lower Tester perform phase 2 of the Passkey Entry pairing procedure and establish an encrypted link with the LTK generated in phase 2.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address), timeout=timedelta(seconds=10))
-
- @metadata(
- pts_test_id="SM/SLA/SCPK/BV-02-C", pts_test_name="Passkey Entry, IUT Responder, Secure Connections – Success")
- def test_passkey_entry_iut_responder_secure_connections(self):
- """
- Verify that the IUT supporting LE Secure Connections is able to perform the Passkey Entry pairing procedure correctly when acting as peripheral, responder.
- """
- self._prepare_dut_for_connection()
-
- self.dut.security.SetLeIoCapability(DISPLAY_ONLY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements(secure_connections=1)
-
- self.cert.security.SetLeIoCapability(KEYBOARD_DISPLAY)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(mitm=1, secure_connections=1)
-
- # 1. Lower Tester transmits Pairing Request command with:
- # a. IO capability set to “KeyboardDisplayâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. AuthReq bonding flag set to the value indicated in the IXIT [7] for ‘Bonding Flags’, and the MITM flag set to ‘1’ Secure Connections flag set to '1' and all reserved bits are set to ‘0’
- self.cert.security.CreateBondLe(self.dut_address)
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.cert_address))
-
- # 2. IUT responds with a Pairing Response command, with:
- # a. IO capability set to “KeyboardOnly†or “KeyboardDisplay†or “DisplayYesNo†or “DisplayOnlyâ€
- # b. Secure Connections flag set to '1'. Keypress bit is set to '1' if supported by IUT
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.cert_address))
-
- # 3. During the phase 2 passkey pairing process, Lower Tester displays the 6-digit passkey while the IUT prompts user to enter the 6-digit passkey. If the IO capabilities of the IUT are “DisplayYesNo†or “DisplayOnly†the IUT displays the 6-digit passkey while the Lower Tester enters the 6-digit passkey. If Keypress bit is set, pairing keypress notifications are send by the IUT
- passkey = self.dut_security.wait_for_ui_event_passkey()
-
- if passkey == 0:
- print("Passkey did not arrive into test")
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PASSKEY_ENTRY, self.dut_address))
-
- # 4. IUT and Lower Tester use the same pre-defined 6-digit passkey.
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PASSKEY, numeric_value=passkey, unique_id=1, address=self.dut_address))
-
- # 5. IUT and Lower Tester perform phase 2 of the LE pairing and establish an encrypted link with the LTK generated in phase 2.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address), timeout=timedelta(seconds=10))
-
- @metadata(
- pts_test_id="SM/SLA/SCPK/BV-03-C",
- pts_test_name="Passkey Entry, IUT Responder, Secure Connections – Handle AuthReq Flag RFU Correctly")
- def test_passkey_entry_iut_responder_secure_connections_auth_req_rfu(self):
- """
- Verify that the IUT supporting LE Secure Connections is able to perform the Passkey Entry pairing procedure when receiving additional bits set in the AuthReq flag. Reserved For Future Use bits are correctly handled when acting as peripheral, responder.
- """
- self._prepare_dut_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements(secure_connections=1)
-
- self.cert.security.SetLeIoCapability(DISPLAY_ONLY)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(mitm=1, secure_connections=1, reserved_bits=3)
-
- # 1. Lower Tester transmits Pairing Request command with:
- # a. IO Capability set to â€KeyboardOnlyâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. MITM set to ‘1’ and all reserved bits are set to a random value
- self.cert.security.CreateBondLe(self.dut_address)
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.cert_address))
-
- # 2. IUT responds with a Pairing Response command, with:
- # a. IO Capability set to “KeyboardOnly†or “DisplayOnlyâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. All reserved bits are set to ‘0’
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.cert_address))
-
- passkey = self.cert_security.wait_for_ui_event_passkey()
-
- if passkey == 0:
- print("Passkey did not arrive into test")
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PASSKEY_ENTRY, self.cert_address))
-
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PASSKEY, numeric_value=passkey, unique_id=1, address=self.cert_address))
-
- # 3. IUT and Lower Tester perform phase 2 of the Passkey Entry pairing and establish an encrypted link with the generated LTK.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address), timeout=timedelta(seconds=10))
-
- @metadata(
- pts_test_id="SM/MAS/SCPK/BV-04-C",
- pts_test_name="Passkey Entry, IUT Initiator, Secure Connections – Handle AuthReq Flag RFU Correctly")
- def test_passkey_entry_iut_initiator_secure_connections_auth_req_rfu(self):
- """
- Verify that the IUT supporting LE Secure Connections is able to perform the Passkey Entry pairing procedure when receiving additional bits set in the AuthReq flag. Reserved For Future Use bits are correctly handled when acting as central, initiator.
- """
- self._prepare_cert_for_connection()
-
- self.dut.security.SetLeIoCapability(KEYBOARD_DISPLAY)
- self.dut.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.dut_security.SetLeAuthRequirements(secure_connections=1)
-
- self.cert.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.cert.security.SetLeOobDataPresent(OOB_NOT_PRESENT)
- self.cert_security.SetLeAuthRequirements(mitm=1, secure_connections=1, reserved_bits=3)
-
- # 1. IUT transmits a Pairing Request command with:
- # a. IO Capability set to “DisplayOnly†or “DisplayYesNo†or “KeyboardOnly†or “KeyboardDisplayâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. All reserved bits are set to ‘0’.
- self.dut.security.CreateBondLe(self.cert_address)
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.dut_address))
-
- # 2. Lower Tester responds with a Pairing Response command, with:
- # a. IO Capability set to “KeyboardOnlyâ€
- # b. OOB data flag set to 0x00 (OOB Authentication data not present)
- # c. AuthReq bonding flag set to the value indicated in the IXIT [7] for ‘Bonding Flags’ and the MITM flag set to ‘1’ and all reserved bits are set to a random value.
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.dut_address))
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PASSKEY_ENTRY, self.dut_address))
-
- passkey = self.dut_security.wait_for_ui_event_passkey()
-
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PASSKEY, numeric_value=passkey, unique_id=1, address=self.dut_address))
-
- # 3. IUT and Lower Tester perform phase 2 of the Just Works pairing and establish an encrypted link with the generated LTK.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address), timeout=timedelta(seconds=10))
-
- @metadata(
- pts_test_id="SM/MAS/SCOB/BV-01-C", pts_test_name="Out of Band, IUT Initiator, Secure Connections – Success")
- def test_out_of_band_iut_initiator_secure_connections(self):
- """
- Verify that the IUT supporting LE Secure Connections performs the Out-of-Band pairing procedure correctly as central, initiator.
- """
-
- oob_combinations = [(OOB_NOT_PRESENT, OOB_PRESENT), (OOB_PRESENT, OOB_NOT_PRESENT), (OOB_PRESENT, OOB_PRESENT)]
-
- for (dut_oob_flag, cert_oob_flag) in oob_combinations:
- print("oob flag combination dut: " + str(dut_oob_flag) + ", cert: " + str(cert_oob_flag))
-
- self._prepare_cert_for_connection()
-
- if dut_oob_flag == LeOobDataFlag.PRESENT:
- oobdata = self.cert.security.GetLeOutOfBandData(empty_proto.Empty())
- self.dut.security.SetOutOfBandData(
- OobDataMessage(
- address=self.cert_address,
- confirmation_value=oobdata.confirmation_value,
- random_value=oobdata.random_value))
-
- if cert_oob_flag == LeOobDataFlag.PRESENT:
- oobdata = self.dut.security.GetLeOutOfBandData(empty_proto.Empty())
- self.cert.security.SetOutOfBandData(
- OobDataMessage(
- address=self.dut_address,
- confirmation_value=oobdata.confirmation_value,
- random_value=oobdata.random_value))
-
- self.dut.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeOobDataPresent(dut_oob_flag)
- self.dut_security.SetLeAuthRequirements(bond=1, mitm=1, secure_connections=1)
-
- self.cert.security.SetLeIoCapability(DISPLAY_ONLY)
- self.cert.security.SetLeOobDataPresent(cert_oob_flag)
- self.cert_security.SetLeAuthRequirements(bond=1, mitm=1, secure_connections=1)
-
- # 1. IUT transmits a Pairing Request command with OOB data flag set to either 0x00 or 0x01, and Secure Connections flag set to '1'.
- self.dut.security.CreateBondLe(self.cert_address)
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.dut_address))
-
- # 2. Lower Tester responds with a Pairing Response command with Secure Connections flag set to '1' and OOB data flag set to either 0x00 or 0x01.
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.dut_address))
-
- # 3. IUT uses the 128-bit value generated by the Lower Tester as the confirm value. Similarly, the Lower Tester uses the 128-bit value generated by the IUT as the confirm value.
-
- # 4. IUT and Lower Tester perform phase 2 of the pairing process and establish an encrypted link with an LTK generated using the OOB data in phase 2.
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address), timeout=timedelta(seconds=10))
-
- assertThat(self.cert_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.dut_address), timeout=timedelta(seconds=10))
-
- self.dut.security.RemoveBond(self.cert_address)
- self.cert.security.RemoveBond(self.dut_address)
-
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_UNBONDED, self.cert_address))
-
- self.dut_security.wait_device_disconnect(self.cert_address)
- self.cert_security.wait_device_disconnect(self.dut_address)
-
- @metadata(
- pts_test_id="SM/SLA/SCOB/BV-02-C", pts_test_name="Out of Band, IUT Responder, Secure Connections – Success")
- def test_out_of_band_iut_responder_secure_connections(self):
- """
- Verify that the IUT supporting LE Secure Connections is able to perform the Out-of-Band pairing procedure correctly when acting as peripheral, responder.
- """
-
- oob_combinations = [(OOB_NOT_PRESENT, OOB_PRESENT), (OOB_PRESENT, OOB_NOT_PRESENT), (OOB_PRESENT, OOB_PRESENT)]
-
- for (dut_oob_flag, cert_oob_flag) in oob_combinations:
- print("oob flag combination dut: " + str(dut_oob_flag) + ", cert: " + str(cert_oob_flag))
-
- self._prepare_dut_for_connection()
-
- if dut_oob_flag == LeOobDataFlag.PRESENT:
- oobdata = self.cert.security.GetLeOutOfBandData(empty_proto.Empty())
- self.dut.security.SetOutOfBandData(
- OobDataMessage(
- address=self.cert_address,
- confirmation_value=oobdata.confirmation_value,
- random_value=oobdata.random_value))
-
- if cert_oob_flag == LeOobDataFlag.PRESENT:
- oobdata = self.dut.security.GetLeOutOfBandData(empty_proto.Empty())
- self.cert.security.SetOutOfBandData(
- OobDataMessage(
- address=self.dut_address,
- confirmation_value=oobdata.confirmation_value,
- random_value=oobdata.random_value))
-
- self.dut.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeOobDataPresent(dut_oob_flag)
- self.dut_security.SetLeAuthRequirements(bond=1, mitm=1, secure_connections=1)
-
- self.cert.security.SetLeIoCapability(DISPLAY_ONLY)
- self.cert.security.SetLeOobDataPresent(cert_oob_flag)
- self.cert_security.SetLeAuthRequirements(bond=1, mitm=1, secure_connections=1)
-
- # 1. Lower Tester transmits a Pairing Request command with OOB data flag set to either 0x00 or 0x01, and Secure Connections flag set to '1'.
- self.cert.security.CreateBondLe(self.dut_address)
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.cert_address))
-
- # 2. IUT responds with a Pairing Response command with Secure Connections flag set to '1' and OOB data flag set to either 0x00 or 0x01.
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.cert_address))
-
- # 3. IUT uses the 128-bit value generated by the Lower Tester as the confirm value. Similarly, the Lower Tester uses the 128-bit value generated by the IUT as the confirm value.
-
- # 4. IUT and Lower Tester perform phase 2 of the pairing process and establish an encrypted link with an LTK generated using the OOB data in phase 2.
- assertThat(self.cert_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.dut_address), timeout=timedelta(seconds=10))
-
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address), timeout=timedelta(seconds=10))
-
- self.cert.security.RemoveBond(self.dut_address)
- self.dut.security.RemoveBond(self.cert_address)
-
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_UNBONDED, self.cert_address))
-
- self.cert_security.wait_device_disconnect(self.dut_address)
- self.dut_security.wait_device_disconnect(self.cert_address)
-
- @metadata(
- pts_test_id="SM/SLA/SCOB/BV-03-C",
- pts_test_name="Out of Band, IUT Responder, Secure Connections – Handle AuthReq Flag RFU Correctly")
- def test_out_of_band_iut_responder_secure_connections_auth_req_rfu(self):
- """
- Verify that the IUT supporting LE Secure Connections is able to perform the Out-of-Band pairing procedure when receiving additional bits set in the AuthReq flag. Reserved For Future Use bits are correctly handled when acting as peripheral, responder.
- """
-
- reserved_bits_combinations = [1, 2, 3]
-
- for reserved_bits in reserved_bits_combinations:
- print("reserved bits in cert dut: " + str(reserved_bits))
-
- self._prepare_dut_for_connection()
-
- oobdata = self.cert.security.GetLeOutOfBandData(empty_proto.Empty())
- self.dut.security.SetOutOfBandData(
- OobDataMessage(
- address=self.cert_address,
- confirmation_value=oobdata.confirmation_value,
- random_value=oobdata.random_value))
-
- oobdata = self.dut.security.GetLeOutOfBandData(empty_proto.Empty())
- self.cert.security.SetOutOfBandData(
- OobDataMessage(
- address=self.dut_address,
- confirmation_value=oobdata.confirmation_value,
- random_value=oobdata.random_value))
-
- self.dut.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeOobDataPresent(OOB_PRESENT)
- self.dut_security.SetLeAuthRequirements(bond=1, mitm=0, secure_connections=1)
-
- self.cert.security.SetLeIoCapability(DISPLAY_ONLY)
- self.cert.security.SetLeOobDataPresent(OOB_PRESENT)
- self.cert_security.SetLeAuthRequirements(bond=1, mitm=1, secure_connections=1, reserved_bits=reserved_bits)
-
- # 1. Lower Tester transmits Pairing Request command with:
- # a. IO Capability set to any IO capability
- # b. OOB data flag set to 0x01 (OOB Authentication data from remote device present)
- # c. MITM set to ‘0’, Secure Connections flag is set to '1', and all reserved bits are set to a random value.
- self.cert.security.CreateBondLe(self.dut_address)
-
- assertThat(self.dut_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.cert_address))
-
- # 2. IUT responds with a Pairing Response command, with:
- # a. IO Capability set to any IO capability
- # b. OOB data flag set to 0x01 (OOB Authentication data present)
- # c. Secure Connections flag is set to '1', All reserved bits are set to ‘0’
- self.dut.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.cert_address))
-
- # 3. IUT and Lower Tester perform phase 2 of the OOB authenticated pairing and establish an encrypted link with the generated LTK.
-
- assertThat(self.cert_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.dut_address), timeout=timedelta(seconds=10))
-
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address), timeout=timedelta(seconds=10))
-
- self.cert.security.RemoveBond(self.dut_address)
- self.dut.security.RemoveBond(self.cert_address)
-
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_UNBONDED, self.cert_address))
-
- self.dut_security.wait_device_disconnect(self.cert_address)
- self.cert_security.wait_device_disconnect(self.dut_address)
-
- @metadata(
- pts_test_id="SM/MAS/SCOB/BV-04-C",
- pts_test_name="Out of Band, IUT Initiator, Secure Connections – Handle AuthReq Flag RFU Correctly")
- def test_out_of_band_iut_initiator_secure_connections_auth_req_rfu(self):
- """
- Verify that the IUT supporting LE Secure Connections is able to perform the Out-of-Band pairing procedure when receiving additional bits set in the AuthReq flag. Reserved For Future Use bits are correctly handled when acting as central, initiator.
- """
-
- reserved_bits_combinations = [1, 2, 3]
-
- for reserved_bits in reserved_bits_combinations:
- print("reserved bits in cert dut: " + str(reserved_bits))
-
- self._prepare_cert_for_connection()
-
- oobdata = self.cert.security.GetLeOutOfBandData(empty_proto.Empty())
- self.dut.security.SetOutOfBandData(
- OobDataMessage(
- address=self.cert_address,
- confirmation_value=oobdata.confirmation_value,
- random_value=oobdata.random_value))
-
- oobdata = self.dut.security.GetLeOutOfBandData(empty_proto.Empty())
- self.cert.security.SetOutOfBandData(
- OobDataMessage(
- address=self.dut_address,
- confirmation_value=oobdata.confirmation_value,
- random_value=oobdata.random_value))
-
- self.dut.security.SetLeIoCapability(KEYBOARD_ONLY)
- self.dut.security.SetLeOobDataPresent(OOB_PRESENT)
- self.dut_security.SetLeAuthRequirements(bond=1, mitm=0, secure_connections=1, reserved_bits=0)
-
- self.cert.security.SetLeIoCapability(DISPLAY_ONLY)
- self.cert.security.SetLeOobDataPresent(OOB_PRESENT)
- self.cert_security.SetLeAuthRequirements(bond=1, mitm=1, secure_connections=1, reserved_bits=reserved_bits)
-
- # 1. IUT transmits Pairing Request command with:
- # a. IO Capability set to any IO capability
- # b. OOB data flag set to 0x01 (OOB Authentication data present)
- # c. MITM set to ‘0’, Secure Connections flag is set to '1', and all reserved bits are set to ‘0’
- self.dut.security.CreateBondLe(self.cert_address)
-
- assertThat(self.cert_security.get_ui_stream()).emits(
- SecurityMatchers.UiMsg(UiMsgType.DISPLAY_PAIRING_PROMPT, self.dut_address))
-
- # 2. Lower Tester responds with a Pairing Response command, with:
- # a. IO Capability set to any IO capability
- # b. OOB data flag set to 0x01 (OOB Authentication data present)
- # c. Secure Connections flag is set to '1', and all reserved bits are set to a random value.
- self.cert.security.SendUiCallback(
- UiCallbackMsg(
- message_type=UiCallbackType.PAIRING_PROMPT, boolean=True, unique_id=1, address=self.dut_address))
-
- # 3. IUT and Lower Tester perform phase 2 of the OOB authenticated pairing and establish an encrypted link with the generated LTK.
-
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.cert_address), timeout=timedelta(seconds=10))
-
- assertThat(self.cert_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_BONDED, self.dut_address), timeout=timedelta(seconds=10))
-
- self.dut.security.RemoveBond(self.cert_address)
- self.cert.security.RemoveBond(self.dut_address)
-
- assertThat(self.dut_security.get_bond_stream()).emits(
- SecurityMatchers.BondMsg(BondMsgType.DEVICE_UNBONDED, self.cert_address))
-
- self.dut_security.wait_device_disconnect(self.cert_address)
- self.cert_security.wait_device_disconnect(self.dut_address)
diff --git a/gd/security/cert/security_test.py b/gd/security/cert/security_test.py
deleted file mode 100644
index 28e04c9f0..000000000
--- a/gd/security/cert/security_test.py
+++ /dev/null
@@ -1,547 +0,0 @@
-#
-# Copyright 2019 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import logging
-import time
-
-from bluetooth_packets_python3 import hci_packets
-from cert.event_stream import EventStream
-from cert.gd_base_test import GdBaseTestClass
-from cert.py_security import PySecurity
-from cert.truth import assertThat
-from facade import common_pb2 as common
-from google.protobuf import empty_pb2 as empty_proto
-from hci.facade import controller_facade_pb2 as controller_facade
-from hci.facade import le_initiator_address_facade_pb2 as le_initiator_address_facade
-from l2cap.classic.facade_pb2 import ClassicSecurityPolicy
-from neighbor.facade import facade_pb2 as neighbor_facade
-from security.cert.cert_security import CertSecurity
-from security.facade_pb2 import AuthenticationRequirements
-from security.facade_pb2 import BondMsgType
-from security.facade_pb2 import IoCapabilities
-from security.facade_pb2 import OobDataPresent
-from security.facade_pb2 import UiMsgType
-
-
-class SecurityTest(GdBaseTestClass):
- """
- Collection of tests that each sample results from
- different (unique) combinations of io capabilities, authentication requirements, and oob data.
- """
-
- _io_capabilities_name_lookup = {
- IoCapabilities.DISPLAY_ONLY: "DISPLAY_ONLY",
- IoCapabilities.DISPLAY_YES_NO_IO_CAP: "DISPLAY_YES_NO_IO_CAP",
- #IoCapabilities.KEYBOARD_ONLY:"KEYBOARD_ONLY",
- IoCapabilities.NO_INPUT_NO_OUTPUT: "NO_INPUT_NO_OUTPUT",
- }
-
- _auth_reqs_name_lookup = {
- AuthenticationRequirements.NO_BONDING: "NO_BONDING",
- AuthenticationRequirements.NO_BONDING_MITM_PROTECTION: "NO_BONDING_MITM_PROTECTION",
- AuthenticationRequirements.DEDICATED_BONDING: "DEDICATED_BONDING",
- AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION: "DEDICATED_BONDING_MITM_PROTECTION",
- AuthenticationRequirements.GENERAL_BONDING: "GENERAL_BONDING",
- AuthenticationRequirements.GENERAL_BONDING_MITM_PROTECTION: "GENERAL_BONDING_MITM_PROTECTION",
- }
-
- # Possible IO Capabilities
- io_capabilities = (
- IoCapabilities.DISPLAY_ONLY,
- IoCapabilities.DISPLAY_YES_NO_IO_CAP,
- # TODO(optedoblivion): Uncomment when Passkey Entry is implemented in ClassicPairingHandler
- #IoCapabilities.KEYBOARD_ONLY,
- IoCapabilities.NO_INPUT_NO_OUTPUT)
-
- # Possible Authentication Requirements
- auth_reqs = (AuthenticationRequirements.NO_BONDING, AuthenticationRequirements.NO_BONDING_MITM_PROTECTION,
- AuthenticationRequirements.DEDICATED_BONDING,
- AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION,
- AuthenticationRequirements.GENERAL_BONDING, AuthenticationRequirements.GENERAL_BONDING_MITM_PROTECTION)
-
- # Possible Out-of-Band data options
- oob_present = (
- OobDataPresent.NOT_PRESENT,
- # TODO(optedoblivion): Uncomment when OOB is implemented in root canal
- #"P192_PRESENT",
- #"P256_PRESENT",
- #"P192_AND_256_PRESENT"
- )
-
- mitm_auth_reqs = (AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION,
- AuthenticationRequirements.GENERAL_BONDING_MITM_PROTECTION,
- AuthenticationRequirements.NO_BONDING_MITM_PROTECTION)
-
- def setup_class(self):
- super().setup_class(dut_module='SECURITY', cert_module='L2CAP')
-
- def setup_test(self):
- super().setup_test()
-
- self.dut.neighbor.EnablePageScan(neighbor_facade.EnableMsg(enabled=True))
- self.cert.neighbor.EnablePageScan(neighbor_facade.EnableMsg(enabled=True))
-
- self.dut.name = b'DUT Device'
- self.dut.address = self.dut.hci_controller.GetMacAddress(empty_proto.Empty()).address
- self.cert.name = b'Cert Device'
- self.cert.address = self.cert.hci_controller.GetMacAddress(empty_proto.Empty()).address
-
- # TODO(optedoblivion): Make this happen in PySecurity or GdDevice
- self.dut.hci_controller.WriteLocalName(controller_facade.NameMsg(name=self.dut.name))
- self.cert.hci_controller.WriteLocalName(controller_facade.NameMsg(name=self.cert.name))
-
- self.dut_security = PySecurity(self.dut)
- self.cert_security = CertSecurity(self.cert)
-
- self.dut_address = common.BluetoothAddressWithType(
- address=common.BluetoothAddress(address=bytes(b'DD:05:04:03:02:01')), type=common.RANDOM_DEVICE_ADDRESS)
- privacy_policy = le_initiator_address_facade.PrivacyPolicy(
- address_policy=le_initiator_address_facade.AddressPolicy.USE_STATIC_ADDRESS,
- address_with_type=self.dut_address)
- self.dut.security.SetLeInitiatorAddressPolicy(privacy_policy)
-
- def teardown_test(self):
- self.dut_security.close()
- self.cert_security.close()
- super().teardown_test()
-
- # Initiates the numeric comparison test
- def _run_ssp_numeric_comparison(self, initiator, responder, init_ui_response, resp_ui_response,
- expected_init_ui_event, expected_resp_ui_event, expected_init_bond_event,
- expected_resp_bond_event):
- initiator.enable_secure_simple_pairing()
- responder.enable_secure_simple_pairing()
- initiator.create_bond(responder.get_address(), common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self._verify_ssp_numeric_comparison(initiator, responder, init_ui_response, resp_ui_response,
- expected_init_ui_event, expected_resp_ui_event, expected_init_bond_event,
- expected_resp_bond_event)
-
- # Verifies the events for the numeric comparion test
- def _verify_ssp_numeric_comparison(self, initiator, responder, init_ui_response, resp_ui_response,
- expected_init_ui_event, expected_resp_ui_event, expected_init_bond_event,
- expected_resp_bond_event):
- responder.accept_pairing(initiator.get_address(), resp_ui_response)
- initiator.on_user_input(responder.get_address(), init_ui_response, expected_init_ui_event)
- initiator.wait_for_bond_event(expected_init_bond_event)
- responder.wait_for_bond_event(expected_resp_bond_event)
-
- def _run_ssp_oob(self, initiator, responder, init_ui_response, resp_ui_response, expected_init_ui_event,
- expected_resp_ui_event, expected_init_bond_event, expected_resp_bond_event, p192_oob_data,
- p256_oob_data):
- initiator.enable_secure_simple_pairing()
- responder.enable_secure_simple_pairing()
- initiator.create_bond_out_of_band(responder.get_address(),
- common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS, p192_oob_data,
- p256_oob_data)
- self._verify_ssp_oob(initiator, responder, init_ui_response, resp_ui_response, expected_init_ui_event,
- expected_resp_ui_event, expected_init_bond_event, expected_resp_bond_event, p192_oob_data,
- p256_oob_data)
-
- # Verifies the events for the numeric comparion test
- def _verify_ssp_oob(self, initiator, responder, init_ui_response, resp_ui_response, expected_init_ui_event,
- expected_resp_ui_event, expected_init_bond_event, expected_resp_bond_event, p192_oob_data,
- p256_oob_data):
- responder.accept_oob_pairing(initiator.get_address())
- initiator.on_user_input(responder.get_address(), init_ui_response, expected_init_ui_event)
- initiator.wait_for_bond_event(expected_init_bond_event)
- responder.wait_for_bond_event(expected_resp_bond_event)
-
- def _run_ssp_passkey(self, initiator, responder, expected_init_bond_event, expected_resp_bond_event):
- initiator.enable_secure_simple_pairing()
- responder.enable_secure_simple_pairing()
- initiator.create_bond(responder.get_address(), common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self._verify_ssp_passkey(initiator, responder, expected_init_bond_event, expected_resp_bond_event)
-
- def _verify_ssp_passkey(self, initiator, responder, expected_init_bond_event, expected_resp_bond_event):
- responder.send_io_caps(initiator.get_address())
- passkey = initiator.wait_for_passkey(responder.get_address())
- responder.input_passkey(initiator.get_address(), passkey)
- initiator.wait_for_bond_event(expected_init_bond_event)
- responder.wait_for_bond_event(expected_resp_bond_event)
-
- def _run_pin(self, initiator, responder, expected_init_bond_event, expected_resp_bond_event):
- initiator.create_bond(responder.get_address(), common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self._verify_pin(initiator, responder, expected_init_bond_event, expected_resp_bond_event)
-
- def _verify_pin(self, initiator, responder, expected_init_bond_event, expected_resp_bond_event):
- pin = b'123456789A'
- logging.info("pin: %s" % pin)
- initiator.input_pin(responder.get_address(), pin)
- responder.input_pin(initiator.get_address(), pin)
- initiator.wait_for_bond_event(expected_init_bond_event)
- responder.wait_for_bond_event(expected_resp_bond_event)
-
- def test_setup_teardown(self):
- """
- Make sure our setup and teardown is sane
- """
- pass
-
- # no_input_no_output + no_input_no_output is JustWorks no confirmation
- def test_dut_initiated_no_input_no_output_no_input_no_output_twice_bond_and_enforce(self):
- # Arrange
- self.dut_security.set_io_capabilities(IoCapabilities.NO_INPUT_NO_OUTPUT)
- self.dut_security.set_authentication_requirements(AuthenticationRequirements.DEDICATED_BONDING)
- self.cert_security.set_io_capabilities(IoCapabilities.NO_INPUT_NO_OUTPUT)
- self.cert_security.set_authentication_requirements(AuthenticationRequirements.DEDICATED_BONDING)
-
- # Act and Assert
- self._run_ssp_numeric_comparison(
- initiator=self.dut_security,
- responder=self.cert_security,
- init_ui_response=True,
- resp_ui_response=True,
- expected_init_ui_event=None,
- expected_resp_ui_event=None,
- expected_init_bond_event=BondMsgType.DEVICE_BONDED,
- expected_resp_bond_event=None)
-
- self.dut_security.enforce_security_policy(self.cert.address,
- common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS,
- ClassicSecurityPolicy.ENCRYPTED_TRANSPORT)
-
- # TODO: We verify enforcement when we make sure EncryptionChange is received on DUT
-
- # no_input_no_output + no_input_no_output is JustWorks no confirmation
- def test_dut_initiated_no_input_no_output_no_input_no_output_twice_with_remove_bond(self):
- # Arrange
- self.dut_security.set_io_capabilities(IoCapabilities.NO_INPUT_NO_OUTPUT)
- self.dut_security.set_authentication_requirements(AuthenticationRequirements.DEDICATED_BONDING)
- self.cert_security.set_io_capabilities(IoCapabilities.NO_INPUT_NO_OUTPUT)
- self.cert_security.set_authentication_requirements(AuthenticationRequirements.DEDICATED_BONDING)
-
- # Act and Assert
- self._run_ssp_numeric_comparison(
- initiator=self.dut_security,
- responder=self.cert_security,
- init_ui_response=True,
- resp_ui_response=True,
- expected_init_ui_event=None,
- expected_resp_ui_event=None,
- expected_init_bond_event=BondMsgType.DEVICE_BONDED,
- expected_resp_bond_event=None)
-
- self.dut_security.remove_bond(self.cert.address, common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self.cert_security.remove_bond(self.cert.address, common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self.dut_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
- self.cert_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
-
- self.dut_security.wait_for_disconnect_event()
- self.cert_security.wait_for_disconnect_event()
-
- # Act and Assert
- self._run_ssp_numeric_comparison(
- initiator=self.dut_security,
- responder=self.cert_security,
- init_ui_response=True,
- resp_ui_response=True,
- expected_init_ui_event=None,
- expected_resp_ui_event=None,
- expected_init_bond_event=BondMsgType.DEVICE_BONDED,
- expected_resp_bond_event=None)
-
- self.dut_security.remove_bond(self.cert.address, common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self.cert_security.remove_bond(self.cert.address, common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self.dut_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
- self.cert_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
-
- self.dut_security.wait_for_disconnect_event()
- self.cert_security.wait_for_disconnect_event()
-
- def test_successful_dut_initiated_ssp_numeric_comparison(self):
- test_count = len(self.io_capabilities) * len(self.auth_reqs) * len(self.oob_present) * len(
- self.io_capabilities) * len(self.auth_reqs) * len(self.oob_present)
- logging.info("Loading %d test combinations" % test_count)
- i = 0
- for dut_io_capability in self.io_capabilities:
- for dut_auth_reqs in self.auth_reqs:
- for dut_oob_present in self.oob_present:
- for cert_io_capability in self.io_capabilities:
- for cert_auth_reqs in self.auth_reqs:
- for cert_oob_present in self.oob_present:
- i = i + 1
- logging.info("")
- logging.info("===================================================")
- logging.info("Running test %d of %d" % (i, test_count))
- logging.info("DUT Test Config: %s ; %s ; %s " % (self._io_capabilities_name_lookup.get(
- dut_io_capability, "ERROR"), self._auth_reqs_name_lookup.get(
- dut_auth_reqs, "ERROR"), dut_oob_present))
- logging.info(
- "CERT Test Config: %s ; %s ; %s " %
- (self._io_capabilities_name_lookup.get(cert_io_capability, "ERROR"),
- self._auth_reqs_name_lookup.get(cert_auth_reqs, "ERROR"), cert_oob_present))
- logging.info("===================================================")
- logging.info("")
- self.dut_security.set_io_capabilities(dut_io_capability)
- self.dut_security.set_authentication_requirements(dut_auth_reqs)
- self.cert_security.set_io_capabilities(cert_io_capability)
- self.cert_security.set_authentication_requirements(cert_auth_reqs)
- init_ui_response = True
- resp_ui_response = True
- expected_init_ui_event = None # None is auto accept
- expected_resp_ui_event = None # None is auto accept
- expected_init_bond_event = BondMsgType.DEVICE_BONDED
- expected_resp_bond_event = None
- if dut_io_capability == IoCapabilities.DISPLAY_ONLY:
- if cert_io_capability == IoCapabilities.DISPLAY_YES_NO_IO_CAP:
- expected_resp_ui_event = UiMsgType.DISPLAY_YES_NO_WITH_VALUE
- if dut_auth_reqs in self.mitm_auth_reqs or cert_auth_reqs in self.mitm_auth_reqs:
- expected_init_bond_event = BondMsgType.DEVICE_BOND_FAILED
- elif cert_io_capability == IoCapabilities.KEYBOARD_ONLY:
- expected_resp_ui_event = UiMsgType.DISPLAY_PASSKEY_ENTRY
- elif cert_io_capability == IoCapabilities.DISPLAY_ONLY:
- if dut_auth_reqs in self.mitm_auth_reqs or cert_auth_reqs in self.mitm_auth_reqs:
- expected_init_bond_event = BondMsgType.DEVICE_BOND_FAILED
- elif cert_io_capability == IoCapabilities.NO_INPUT_NO_OUTPUT:
- if dut_auth_reqs in self.mitm_auth_reqs or cert_auth_reqs in self.mitm_auth_reqs:
- expected_init_bond_event = BondMsgType.DEVICE_BOND_FAILED
- elif dut_io_capability == IoCapabilities.DISPLAY_YES_NO_IO_CAP:
- expected_init_ui_event = UiMsgType.DISPLAY_YES_NO_WITH_VALUE
- if cert_io_capability == IoCapabilities.DISPLAY_YES_NO_IO_CAP:
- expected_resp_ui_event = UiMsgType.DISPLAY_YES_NO_WITH_VALUE
- elif cert_io_capability == IoCapabilities.KEYBOARD_ONLY:
- expected_init_ui_event = UiMsgType.DISPLAY_PASSKEY
- expected_resp_ui_event = UiMsgType.DISPLAY_PASSKEY_ENTRY
- elif cert_io_capability == IoCapabilities.NO_INPUT_NO_OUTPUT:
- expected_init_ui_event = UiMsgType.DISPLAY_YES_NO # No value
- elif dut_io_capability == IoCapabilities.KEYBOARD_ONLY:
- expected_init_ui_event = UiMsgType.DISPLAY_PASSKEY_ENTRY
- if cert_io_capability == IoCapabilities.DISPLAY_ONLY:
- expected_resp_ui_event = UiMsgType.DISPLAY_PASSKEY
- elif cert_io_capability == IoCapabilities.DISPLAY_YES_NO_IO_CAP:
- expected_resp_ui_event = UiMsgType.DISPLAY_PASSKEY_ENTRY
- elif cert_io_capability == IoCapabilities.KEYBOARD_ONLY:
- expected_resp_ui_event = UiMsgType.DISPLAY_PASSKEY_ENTRY
- elif cert_io_capability == IoCapabilities.NO_INPUT_NO_OUTPUT:
- if dut_auth_reqs in self.mitm_auth_reqs or cert_auth_reqs in self.mitm_auth_reqs:
- expected_init_bond_event = BondMsgType.DEVICE_BOND_FAILED
- elif dut_io_capability == IoCapabilities.NO_INPUT_NO_OUTPUT:
- if cert_io_capability == IoCapabilities.DISPLAY_YES_NO_IO_CAP:
- expected_resp_ui_event = UiMsgType.DISPLAY_YES_NO # No value
-
- if dut_auth_reqs in self.mitm_auth_reqs or cert_auth_reqs in self.mitm_auth_reqs:
- expected_init_bond_event = BondMsgType.DEVICE_BOND_FAILED
-
- if cert_oob_present == OobDataPresent.NOT_PRESENT:
- self._run_ssp_numeric_comparison(
- initiator=self.dut_security,
- responder=self.cert_security,
- init_ui_response=init_ui_response,
- resp_ui_response=resp_ui_response,
- expected_init_ui_event=expected_init_ui_event,
- expected_resp_ui_event=expected_resp_ui_event,
- expected_init_bond_event=expected_init_bond_event,
- expected_resp_bond_event=expected_resp_bond_event)
- else:
- logging.error("Code path not yet implemented")
- assertThat(False).isTrue()
-
- self.dut_security.remove_bond(self.cert_security.get_address(),
- common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self.cert_security.remove_bond(self.dut_security.get_address(),
- common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
-
- self.dut_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
- self.cert_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
-
- self.dut_security.wait_for_disconnect_event()
- self.cert_security.wait_for_disconnect_event()
-
- def test_enable_secure_simple_pairing(self):
- self.dut_security.enable_secure_simple_pairing()
- self.cert_security.enable_secure_simple_pairing()
-
- def test_enable_secure_connections(self):
- self.dut_security.enable_secure_simple_pairing()
- self.cert_security.enable_secure_simple_pairing()
- self.dut_security.enable_secure_connections()
- self.cert_security.enable_secure_connections()
-
- def test_get_oob_data_from_dut_controller_p192_present(self):
- oob_data = self.dut_security.get_oob_data_from_controller(OobDataPresent.P192_PRESENT)
- assertThat(len(oob_data)).isEqualTo(4)
- has192C = not all([i == 0 for i in oob_data[0]])
- has192R = not all([i == 0 for i in oob_data[1]])
- has256C = not all([i == 0 for i in oob_data[2]])
- has256R = not all([i == 0 for i in oob_data[3]])
- assertThat(has192C).isTrue()
- assertThat(has192R).isTrue()
- assertThat(has256C).isFalse()
- assertThat(has256R).isFalse()
-
- def test_get_oob_data_from_cert_controller_not_present(self):
- oob_data = self.cert_security.get_oob_data_from_controller(OobDataPresent.NOT_PRESENT)
- assertThat(len(oob_data)).isEqualTo(4)
- has192C = not all([i == 0 for i in oob_data[0]])
- has192R = not all([i == 0 for i in oob_data[1]])
- has256C = not all([i == 0 for i in oob_data[2]])
- has256R = not all([i == 0 for i in oob_data[3]])
- assertThat(has192C).isFalse()
- assertThat(has192R).isFalse()
- assertThat(has256C).isFalse()
- assertThat(has256R).isFalse()
-
- def test_get_oob_data_from_cert_controller_p192_present_no_secure_connections(self):
- oob_data = self.cert_security.get_oob_data_from_controller(OobDataPresent.P192_PRESENT)
- assertThat(len(oob_data)).isEqualTo(4)
- has192C = not all([i == 0 for i in oob_data[0]])
- has192R = not all([i == 0 for i in oob_data[1]])
- has256C = not all([i == 0 for i in oob_data[2]])
- has256R = not all([i == 0 for i in oob_data[3]])
- assertThat(has192C).isTrue()
- assertThat(has192R).isTrue()
- assertThat(has256C).isFalse()
- assertThat(has256R).isFalse()
-
- def test_get_oob_data_from_cert_controller_p192_present(self):
- self.cert_security.enable_secure_simple_pairing()
- self.cert_security.enable_secure_connections()
- oob_data = self.cert_security.get_oob_data_from_controller(OobDataPresent.P192_PRESENT)
- assertThat(len(oob_data)).isEqualTo(4)
- has192C = not all([i == 0 for i in oob_data[0]])
- has192R = not all([i == 0 for i in oob_data[1]])
- has256C = not all([i == 0 for i in oob_data[2]])
- has256R = not all([i == 0 for i in oob_data[3]])
- assertThat(has192C).isTrue()
- assertThat(has192R).isTrue()
- assertThat(has256C).isFalse()
- assertThat(has256R).isFalse()
-
- def test_get_oob_data_from_cert_controller_p256_present(self):
- self.cert_security.enable_secure_simple_pairing()
- self.cert_security.enable_secure_connections()
- oob_data = self.cert_security.get_oob_data_from_controller(OobDataPresent.P256_PRESENT)
- assertThat(len(oob_data)).isEqualTo(4)
- has192C = not all([i == 0 for i in oob_data[0]])
- has192R = not all([i == 0 for i in oob_data[1]])
- has256C = not all([i == 0 for i in oob_data[2]])
- has256R = not all([i == 0 for i in oob_data[3]])
- assertThat(has192C).isFalse()
- assertThat(has192R).isFalse()
- assertThat(has256C).isTrue()
- assertThat(has256R).isTrue()
-
- def test_get_oob_data_from_cert_controller_p192_and_p256_present(self):
- self.cert_security.enable_secure_simple_pairing()
- self.cert_security.enable_secure_connections()
- oob_data = self.cert_security.get_oob_data_from_controller(OobDataPresent.P192_AND_256_PRESENT)
- assertThat(len(oob_data)).isEqualTo(4)
- has192C = not all([i == 0 for i in oob_data[0]])
- has192R = not all([i == 0 for i in oob_data[1]])
- has256C = not all([i == 0 for i in oob_data[2]])
- has256R = not all([i == 0 for i in oob_data[3]])
- assertThat(has192C).isTrue()
- assertThat(has192R).isTrue()
- assertThat(has256C).isTrue()
- assertThat(has256R).isTrue()
-
- def test_successful_dut_initiated_ssp_oob(self):
- dut_io_capability = IoCapabilities.NO_INPUT_NO_OUTPUT
- cert_io_capability = IoCapabilities.NO_INPUT_NO_OUTPUT
- dut_auth_reqs = AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION
- cert_auth_reqs = AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION
- cert_oob_present = OobDataPresent.P192_PRESENT
- self.dut_security.enable_secure_simple_pairing()
- self.dut_security.enable_secure_connections()
- self.cert_security.enable_secure_simple_pairing()
- self.cert_security.enable_secure_connections()
- self.dut_security.set_io_capabilities(dut_io_capability)
- self.dut_security.set_authentication_requirements(dut_auth_reqs)
- self.cert_security.set_io_capabilities(cert_io_capability)
- self.cert_security.set_authentication_requirements(cert_auth_reqs)
- init_ui_response = True
- resp_ui_response = True
- expected_init_ui_event = None # None is auto accept
- expected_resp_ui_event = None # None is auto accept
- expected_init_bond_event = BondMsgType.DEVICE_BONDED
- expected_resp_bond_event = None
- # get_oob_data returns a tuple of bytes (p192c,p192r,p256c,p256r)
- local_oob_data = self.cert_security.get_oob_data_from_controller(cert_oob_present)
- p192_oob_data = local_oob_data[0:2]
- p256_oob_data = local_oob_data[2:4]
- self._run_ssp_oob(
- initiator=self.dut_security,
- responder=self.cert_security,
- init_ui_response=init_ui_response,
- resp_ui_response=resp_ui_response,
- expected_init_ui_event=expected_init_ui_event,
- expected_resp_ui_event=expected_resp_ui_event,
- expected_init_bond_event=expected_init_bond_event,
- expected_resp_bond_event=expected_resp_bond_event,
- p192_oob_data=p192_oob_data,
- p256_oob_data=p256_oob_data)
- self.dut_security.remove_bond(self.cert_security.get_address(),
- common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self.cert_security.remove_bond(self.dut_security.get_address(),
- common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self.dut_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
- self.cert_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
- self.dut_security.wait_for_disconnect_event()
- self.cert_security.wait_for_disconnect_event()
-
- def test_successful_dut_initiated_ssp_keyboard(self):
- dut_io_capability = IoCapabilities.DISPLAY_YES_NO_IO_CAP
- dut_auth_reqs = AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION
- dut_oob_present = OobDataPresent.NOT_PRESENT
- cert_io_capability = IoCapabilities.KEYBOARD_ONLY
- cert_auth_reqs = AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION
- cert_oob_present = OobDataPresent.NOT_PRESENT
- self.dut_security.set_io_capabilities(dut_io_capability)
- self.dut_security.set_authentication_requirements(dut_auth_reqs)
- self.cert_security.set_io_capabilities(cert_io_capability)
- self.cert_security.set_authentication_requirements(cert_auth_reqs)
-
- self._run_ssp_passkey(
- initiator=self.dut_security,
- responder=self.cert_security,
- expected_init_bond_event=BondMsgType.DEVICE_BONDED,
- expected_resp_bond_event=BondMsgType.DEVICE_BONDED)
-
- self.dut_security.remove_bond(self.cert_security.get_address(),
- common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self.cert_security.remove_bond(self.dut_security.get_address(),
- common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
-
- self.dut_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
- self.cert_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
-
- self.dut_security.wait_for_disconnect_event()
- self.cert_security.wait_for_disconnect_event()
-
- def test_successful_dut_initiated_pin(self):
- self.dut_security.set_io_capabilities(IoCapabilities.DISPLAY_YES_NO_IO_CAP)
- self.dut_security.set_authentication_requirements(AuthenticationRequirements.DEDICATED_BONDING)
-
- self._run_pin(
- initiator=self.dut_security,
- responder=self.cert_security,
- expected_init_bond_event=BondMsgType.DEVICE_BONDED,
- expected_resp_bond_event=BondMsgType.DEVICE_BONDED)
-
- self.dut_security.remove_bond(self.cert_security.get_address(),
- common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
- self.cert_security.remove_bond(self.dut_security.get_address(),
- common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS)
-
- self.dut_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
- self.cert_security.wait_for_bond_event(BondMsgType.DEVICE_UNBONDED)
-
- self.dut_security.wait_for_disconnect_event()
- self.cert_security.wait_for_disconnect_event()
-
- def test_make_sure_oob_data_different(self):
- oob_data = self.dut_security.get_oob_data_from_controller(OobDataPresent.P192_PRESENT)
- oob_data2 = self.dut_security.get_oob_data_from_controller(OobDataPresent.P192_PRESENT)
- assertThat(oob_data).isNotEqualTo(oob_data2)
diff --git a/gd/security/cert/simple_security_test.py b/gd/security/cert/simple_security_test.py
new file mode 100644
index 000000000..ff7228e07
--- /dev/null
+++ b/gd/security/cert/simple_security_test.py
@@ -0,0 +1,237 @@
+#!/usr/bin/env python3
+#
+# Copyright 2019 - The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the "License");
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an "AS IS" BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+from datetime import timedelta
+import os
+import sys
+import logging
+
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
+from cert.event_callback_stream import EventCallbackStream
+from cert.event_asserts import EventAsserts
+from google.protobuf import empty_pb2 as empty_proto
+from facade import common_pb2 as common
+from facade import rootservice_pb2 as facade_rootservice_pb2
+from hci.facade import facade_pb2 as hci_facade
+from hci.facade import acl_manager_facade_pb2 as acl_manager_facade
+from hci.facade import controller_facade_pb2 as controller_facade
+from l2cap.classic import facade_pb2 as l2cap_facade
+from neighbor.facade import facade_pb2 as neighbor_facade
+from security import facade_pb2 as security_facade
+from bluetooth_packets_python3 import hci_packets
+import bluetooth_packets_python3 as bt_packets
+
+
+class SimpleSecurityTest(GdFacadeOnlyBaseTestClass):
+
+ def setup_test(self):
+ self.device_under_test.rootservice.StartStack(
+ facade_rootservice_pb2.StartStackRequest(
+ module_under_test=facade_rootservice_pb2.BluetoothModule.Value(
+ 'SECURITY'),))
+ self.cert_device.rootservice.StartStack(
+ facade_rootservice_pb2.StartStackRequest(
+ module_under_test=facade_rootservice_pb2.BluetoothModule.Value(
+ 'L2CAP'),))
+
+ self.device_under_test.address = self.device_under_test.controller_read_only_property.ReadLocalAddress(
+ empty_proto.Empty()).address
+ self.cert_device.address = self.cert_device.controller_read_only_property.ReadLocalAddress(
+ empty_proto.Empty()).address
+
+ self.device_under_test.neighbor.EnablePageScan(
+ neighbor_facade.EnableMsg(enabled=True))
+ self.cert_device.neighbor.EnablePageScan(
+ neighbor_facade.EnableMsg(enabled=True))
+
+ self.dut_address = common.BluetoothAddress(
+ address=self.device_under_test.address)
+ self.cert_address = common.BluetoothAddress(
+ address=self.cert_device.address)
+
+ self.dut_address_with_type = common.BluetoothAddressWithType()
+ self.dut_address_with_type.address.CopyFrom(self.dut_address)
+ self.dut_address_with_type.type = common.BluetoothPeerAddressTypeEnum.PUBLIC_DEVICE_OR_IDENTITY_ADDRESS
+
+ self.cert_address_with_type = common.BluetoothAddressWithType()
+ self.cert_address_with_type.address.CopyFrom(self.cert_address)
+ self.cert_address_with_type.type = common.BluetoothPeerAddressTypeEnum.PUBLIC_DEVICE_OR_IDENTITY_ADDRESS
+
+ self.device_under_test.wait_channel_ready()
+ self.cert_device.wait_channel_ready()
+
+ self.cert_name = b'ImTheCert'
+ self.cert_device.hci_controller.WriteLocalName(
+ controller_facade.NameMsg(name=self.cert_name))
+ self.dut_name = b'ImTheDUT'
+ self.device_under_test.hci_controller.WriteLocalName(
+ controller_facade.NameMsg(name=self.dut_name))
+
+ def teardown_test(self):
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice_pb2.StopStackRequest())
+ self.cert_device.rootservice.StopStack(
+ facade_rootservice_pb2.StopStackRequest())
+
+ def tmp_register_for_event(self, event_code):
+ msg = hci_facade.EventCodeMsg(code=int(event_code))
+ self.device_under_test.hci.RegisterEventHandler(msg)
+
+ def tmp_enqueue_hci_command(self, command, expect_complete):
+ cmd_bytes = bytes(command.Serialize())
+ cmd = hci_facade.CommandMsg(command=cmd_bytes)
+ if (expect_complete):
+ self.device_under_test.hci.EnqueueCommandWithComplete(cmd)
+ else:
+ self.device_under_test.hci.EnqueueCommandWithStatus(cmd)
+
+ def register_for_event(self, event_code):
+ msg = hci_facade.EventCodeMsg(code=int(event_code))
+ self.cert_device.hci.RegisterEventHandler(msg)
+
+ def enqueue_hci_command(self, command, expect_complete):
+ cmd_bytes = bytes(command.Serialize())
+ cmd = hci_facade.CommandMsg(command=cmd_bytes)
+ if (expect_complete):
+ self.cert_device.hci.EnqueueCommandWithComplete(cmd)
+ else:
+ self.cert_device.hci.EnqueueCommandWithStatus(cmd)
+
+ def enqueue_acl_data(self, handle, pb_flag, b_flag, acl):
+ acl_msg = hci_facade.AclMsg(
+ handle=int(handle),
+ packet_boundary_flag=int(pb_flag),
+ broadcast_flag=int(b_flag),
+ data=acl)
+ self.cert_device.hci.SendAclData(acl_msg)
+
+ def pair_justworks(self, cert_iocap_reply, expected_ui_event):
+ # Cert event registration
+ self.register_for_event(hci_packets.EventCode.LINK_KEY_REQUEST)
+ self.register_for_event(hci_packets.EventCode.IO_CAPABILITY_REQUEST)
+ self.register_for_event(hci_packets.EventCode.IO_CAPABILITY_RESPONSE)
+ self.register_for_event(hci_packets.EventCode.USER_PASSKEY_NOTIFICATION)
+ self.register_for_event(hci_packets.EventCode.USER_CONFIRMATION_REQUEST)
+ self.register_for_event(
+ hci_packets.EventCode.REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION)
+ self.register_for_event(hci_packets.EventCode.LINK_KEY_NOTIFICATION)
+ self.register_for_event(hci_packets.EventCode.SIMPLE_PAIRING_COMPLETE)
+ with EventCallbackStream(self.device_under_test.security.FetchUiEvents(empty_proto.Empty())) as dut_ui_stream, \
+ EventCallbackStream(self.device_under_test.security.FetchBondEvents(empty_proto.Empty())) as dut_bond_stream, \
+ EventCallbackStream(self.device_under_test.neighbor.GetRemoteNameEvents(empty_proto.Empty())) as name_event_stream, \
+ EventCallbackStream(self.cert_device.hci.FetchEvents(empty_proto.Empty())) as cert_hci_event_stream:
+
+ cert_hci_event_asserts = EventAsserts(cert_hci_event_stream)
+ dut_ui_event_asserts = EventAsserts(dut_ui_stream)
+ dut_bond_asserts = EventAsserts(dut_bond_stream)
+ dut_name_asserts = EventAsserts(name_event_stream)
+
+ dut_address = self.device_under_test.hci_controller.GetMacAddress(
+ empty_proto.Empty()).address
+ cert_address = self.cert_device.hci_controller.GetMacAddress(
+ empty_proto.Empty()).address
+
+ # Enable Simple Secure Pairing
+ self.enqueue_hci_command(
+ hci_packets.WriteSimplePairingModeBuilder(
+ hci_packets.Enable.ENABLED), True)
+
+ cert_hci_event_asserts.assert_event_occurs(
+ lambda msg: b'\x0e\x04\x01\x56\x0c' in msg.event)
+
+ # Get the name
+ self.device_under_test.neighbor.ReadRemoteName(
+ neighbor_facade.RemoteNameRequestMsg(
+ address=cert_address,
+ page_scan_repetition_mode=1,
+ clock_offset=0x6855))
+
+ dut_name_asserts.assert_event_occurs(
+ lambda msg: self.cert_name in msg.name)
+
+ self.device_under_test.security.CreateBond(
+ common.BluetoothAddressWithType(
+ address=common.BluetoothAddress(address=cert_address),
+ type=common.BluetoothAddressTypeEnum.PUBLIC_DEVICE_ADDRESS))
+
+ cert_hci_event_asserts.assert_event_occurs(
+ lambda event: logging.debug(event.event) or hci_packets.EventCode.IO_CAPABILITY_REQUEST in event.event
+ )
+
+ self.enqueue_hci_command(cert_iocap_reply, True)
+
+ cert_hci_event_asserts.assert_event_occurs(
+ lambda event: logging.debug(event.event) or hci_packets.EventCode.USER_CONFIRMATION_REQUEST in event.event
+ )
+ self.enqueue_hci_command(
+ hci_packets.UserConfirmationRequestReplyBuilder(
+ dut_address.decode('utf8')), True)
+
+ logging.info("Waiting for UI event")
+ ui_id = -1
+
+ def get_unique_id(event):
+ if (event.message_type == expected_ui_event):
+ nonlocal ui_id
+ ui_id = event.unique_id
+ return True
+ return False
+
+ dut_ui_event_asserts.assert_event_occurs(get_unique_id)
+
+ logging.info("Sending UI response")
+ self.device_under_test.security.SendUiCallback(
+ security_facade.UiCallbackMsg(
+ message_type=security_facade.UiCallbackType.YES_NO,
+ boolean=True,
+ unique_id=ui_id))
+
+ dut_bond_asserts.assert_event_occurs(
+ lambda bond_event: bond_event.message_type == security_facade.BondMsgType.DEVICE_BONDED
+ )
+
+ def test_display_only(self):
+ dut_address = self.device_under_test.hci_controller.GetMacAddress(
+ empty_proto.Empty()).address
+ self.pair_justworks(
+ hci_packets.IoCapabilityRequestReplyBuilder(
+ dut_address.decode('utf8'),
+ hci_packets.IoCapability.DISPLAY_ONLY,
+ hci_packets.OobDataPresent.NOT_PRESENT, hci_packets.
+ AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION),
+ security_facade.UiMsgType.DISPLAY_YES_NO_WITH_VALUE)
+
+ def test_no_input_no_output(self):
+ dut_address = self.device_under_test.hci_controller.GetMacAddress(
+ empty_proto.Empty()).address
+ self.pair_justworks(
+ hci_packets.IoCapabilityRequestReplyBuilder(
+ dut_address.decode('utf8'),
+ hci_packets.IoCapability.NO_INPUT_NO_OUTPUT,
+ hci_packets.OobDataPresent.NOT_PRESENT, hci_packets.
+ AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION),
+ security_facade.UiMsgType.DISPLAY_YES_NO)
+
+ def test_display_yes_no(self):
+ dut_address = self.device_under_test.hci_controller.GetMacAddress(
+ empty_proto.Empty()).address
+ self.pair_justworks(
+ hci_packets.IoCapabilityRequestReplyBuilder(
+ dut_address.decode('utf8'),
+ hci_packets.IoCapability.DISPLAY_YES_NO,
+ hci_packets.OobDataPresent.NOT_PRESENT, hci_packets.
+ AuthenticationRequirements.DEDICATED_BONDING_MITM_PROTECTION),
+ security_facade.UiMsgType.DISPLAY_YES_NO_WITH_VALUE)
diff --git a/gd/security/channel/Android.bp b/gd/security/channel/Android.bp
index 9b069a0f2..653902b15 100644
--- a/gd/security/channel/Android.bp
+++ b/gd/security/channel/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothSecurityChannelSources",
srcs: [
diff --git a/gd/security/channel/security_manager_channel.cc b/gd/security/channel/security_manager_channel.cc
index 8c90a360b..fd6e9dfa8 100644
--- a/gd/security/channel/security_manager_channel.cc
+++ b/gd/security/channel/security_manager_channel.cc
@@ -17,115 +17,29 @@
*/
#include "security/channel/security_manager_channel.h"
-#include "hci/address.h"
#include "security/smp_packets.h"
namespace bluetooth {
namespace security {
namespace channel {
-/**
- * Main Constructor
- */
-SecurityManagerChannel::SecurityManagerChannel(os::Handler* handler, hci::HciLayer* hci_layer)
- : listener_(nullptr),
- hci_security_interface_(
- hci_layer->GetSecurityInterface(handler->BindOn(this, &SecurityManagerChannel::OnHciEventReceived))),
- handler_(handler),
- l2cap_security_interface_(nullptr) {}
-
-SecurityManagerChannel::~SecurityManagerChannel() {
- l2cap_security_interface_->Unregister();
- l2cap_security_interface_ = nullptr;
-}
-
-void SecurityManagerChannel::Connect(hci::Address address) {
- ASSERT_LOG(l2cap_security_interface_ != nullptr, "L2cap Security Interface is null!");
- auto entry = link_map_.find(address);
- if (entry != link_map_.end()) {
- LOG_WARN("Already connected to '%s'", address.ToString().c_str());
- entry->second->Hold();
- entry->second->EnsureAuthenticated();
- return;
- }
- l2cap_security_interface_->InitiateConnectionForSecurity(address);
- outgoing_pairing_remote_devices_.insert(address);
-}
-
-void SecurityManagerChannel::Release(hci::Address address) {
- auto entry = link_map_.find(address);
- if (entry == link_map_.end()) {
- LOG_WARN("Unknown address '%s'", address.ToString().c_str());
- return;
- }
- entry->second->Release();
-}
-
-void SecurityManagerChannel::Disconnect(hci::Address address) {
- outgoing_pairing_remote_devices_.erase(address);
- auto entry = link_map_.find(address);
- if (entry == link_map_.end()) {
- LOG_WARN("Unknown address '%s'", address.ToString().c_str());
- return;
- }
- entry->second->Disconnect();
-}
-
void SecurityManagerChannel::OnCommandComplete(hci::CommandCompleteView packet) {
- ASSERT_LOG(packet.IsValid(), "Bad command response");
+ ASSERT(packet.IsValid());
+ // TODO(optedoblivion): Verify HCI commands
}
void SecurityManagerChannel::SendCommand(std::unique_ptr<hci::SecurityCommandBuilder> command) {
- hci_security_interface_->EnqueueCommand(std::move(command),
- handler_->BindOnceOn(this, &SecurityManagerChannel::OnCommandComplete));
+ hci_security_interface_->EnqueueCommand(
+ std::move(command), common::BindOnce(&SecurityManagerChannel::OnCommandComplete, common::Unretained(this)),
+ handler_);
}
-void SecurityManagerChannel::SendCommand(
- std::unique_ptr<hci::SecurityCommandBuilder> command, SecurityCommandStatusCallback callback) {
- hci_security_interface_->EnqueueCommand(std::move(command), std::forward<SecurityCommandStatusCallback>(callback));
-}
-
-void SecurityManagerChannel::OnHciEventReceived(hci::EventView packet) {
+void SecurityManagerChannel::OnHciEventReceived(hci::EventPacketView packet) {
ASSERT_LOG(listener_ != nullptr, "No listener set!");
ASSERT(packet.IsValid());
listener_->OnHciEventReceived(packet);
}
-void SecurityManagerChannel::OnLinkConnected(std::unique_ptr<l2cap::classic::LinkSecurityInterface> link) {
- // Multiple links possible?
- auto remote = link->GetRemoteAddress();
- if (outgoing_pairing_remote_devices_.count(remote) == 1) {
- link->Hold();
- link->EnsureAuthenticated();
- outgoing_pairing_remote_devices_.erase(remote);
- }
- link_map_.emplace(remote, std::move(link));
-}
-
-void SecurityManagerChannel::OnLinkDisconnected(hci::Address address) {
- auto entry = link_map_.find(address);
- if (entry == link_map_.end()) {
- LOG_WARN("Unknown address '%s'", address.ToString().c_str());
- return;
- }
- entry->second.reset();
- link_map_.erase(entry);
- ASSERT_LOG(listener_ != nullptr, "Set listener!");
- listener_->OnConnectionClosed(address);
-}
-
-void SecurityManagerChannel::OnAuthenticationComplete(hci::ErrorCode hci_status, hci::Address remote) {
- ASSERT_LOG(l2cap_security_interface_ != nullptr, "L2cap Security Interface is null!");
- auto entry = link_map_.find(remote);
- if (entry != link_map_.end()) {
- entry->second->EnsureEncrypted();
- return;
- }
-}
-
-void SecurityManagerChannel::OnEncryptionChange(hci::Address remote, bool encrypted) {
-}
-
} // namespace channel
} // namespace security
} // namespace bluetooth
diff --git a/gd/security/channel/security_manager_channel.h b/gd/security/channel/security_manager_channel.h
index 9e2360469..48bd84644 100644
--- a/gd/security/channel/security_manager_channel.h
+++ b/gd/security/channel/security_manager_channel.h
@@ -18,66 +18,36 @@
#pragma once
#include <memory>
-#include <unordered_map>
#include <vector>
-#include "common/contextual_callback.h"
#include "hci/address_with_type.h"
#include "hci/hci_layer.h"
#include "hci/hci_packets.h"
#include "hci/security_interface.h"
-#include "l2cap/classic/l2cap_classic_module.h"
-#include "l2cap/classic/link_security_interface.h"
namespace bluetooth {
namespace security {
namespace channel {
-using SecurityCommandStatusCallback = common::ContextualOnceCallback<void(hci::CommandCompleteView)>;
-
/**
* Interface for listening to the channel for SMP commands.
*/
class ISecurityManagerChannelListener {
public:
virtual ~ISecurityManagerChannelListener() = default;
- virtual void OnHciEventReceived(hci::EventView packet) = 0;
- virtual void OnConnectionClosed(hci::Address) = 0;
+ virtual void OnHciEventReceived(hci::EventPacketView packet) = 0;
};
/**
* Channel for consolidating traffic and making the transport agnostic.
*/
-class SecurityManagerChannel : public l2cap::classic::LinkSecurityInterfaceListener {
+class SecurityManagerChannel {
public:
- SecurityManagerChannel(os::Handler* handler, hci::HciLayer* hci_layer);
-
- virtual ~SecurityManagerChannel();
-
- /**
- * Creates a connection to the device which triggers pairing
- *
- * @param address remote address of device to pair with
- */
- void Connect(hci::Address address);
-
- /**
- * Releases link hold so it can disconnect as normally
- *
- * i.e. signals we no longer need this if acl manager wants to clean it up
- *
- * @param address remote address to disconnect
- */
- void Release(hci::Address address);
-
- /**
- * Immediately disconnects currently connected channel
- *
- * i.e. force disconnect
- *
- * @param address remote address to disconnect
- */
- void Disconnect(hci::Address address);
+ explicit SecurityManagerChannel(os::Handler* handler, hci::HciLayer* hci_layer)
+ : listener_(nullptr),
+ hci_security_interface_(hci_layer->GetSecurityInterface(
+ common::Bind(&SecurityManagerChannel::OnHciEventReceived, common::Unretained(this)), handler)),
+ handler_(handler) {}
/**
* Send a given SMP command over the SecurityManagerChannel
@@ -87,14 +57,6 @@ class SecurityManagerChannel : public l2cap::classic::LinkSecurityInterfaceListe
void SendCommand(std::unique_ptr<hci::SecurityCommandBuilder> command);
/**
- * Send a given SMP command over the SecurityManagerChannel
- *
- * @param command smp command to send
- * @param callback listener to call when command status complete
- */
- void SendCommand(std::unique_ptr<hci::SecurityCommandBuilder> command, SecurityCommandStatusCallback callback);
-
- /**
* Sets the listener to listen for channel events
*
* @param listener the caller interested in events
@@ -103,16 +65,12 @@ class SecurityManagerChannel : public l2cap::classic::LinkSecurityInterfaceListe
listener_ = listener;
}
- void SetSecurityInterface(l2cap::classic::SecurityInterface* security_interface) {
- l2cap_security_interface_ = security_interface;
- }
-
/**
* Called when an incoming HCI event happens
*
* @param event_packet
*/
- void OnHciEventReceived(hci::EventView packet);
+ void OnHciEventReceived(hci::EventPacketView packet);
/**
* Called when an HCI command is completed
@@ -121,19 +79,10 @@ class SecurityManagerChannel : public l2cap::classic::LinkSecurityInterfaceListe
*/
void OnCommandComplete(hci::CommandCompleteView packet);
- // Interface overrides
- void OnLinkConnected(std::unique_ptr<l2cap::classic::LinkSecurityInterface> link) override;
- void OnLinkDisconnected(hci::Address address) override;
- void OnAuthenticationComplete(hci::ErrorCode hci_status, hci::Address remote) override;
- void OnEncryptionChange(hci::Address, bool encrypted) override;
-
private:
- ISecurityManagerChannelListener* listener_{nullptr};
- hci::SecurityInterface* hci_security_interface_{nullptr};
- os::Handler* handler_{nullptr};
- l2cap::classic::SecurityInterface* l2cap_security_interface_{nullptr};
- std::unordered_map<hci::Address, std::unique_ptr<l2cap::classic::LinkSecurityInterface>> link_map_;
- std::set<hci::Address> outgoing_pairing_remote_devices_;
+ ISecurityManagerChannelListener* listener_;
+ hci::SecurityInterface* hci_security_interface_;
+ os::Handler* handler_;
};
} // namespace channel
diff --git a/gd/security/channel/security_manager_channel_unittest.cc b/gd/security/channel/security_manager_channel_unittest.cc
index 22b16d851..14de43f09 100644
--- a/gd/security/channel/security_manager_channel_unittest.cc
+++ b/gd/security/channel/security_manager_channel_unittest.cc
@@ -15,16 +15,14 @@
* limitations under the License.
*
*/
-#include "security/channel/security_manager_channel.h"
+#include "security_manager_channel.h"
#include <gtest/gtest.h>
-#include "hci/address.h"
#include "hci/hci_packets.h"
#include "packet/raw_builder.h"
#include "security/smp_packets.h"
#include "security/test/fake_hci_layer.h"
-#include "security/test/fake_security_interface.h"
namespace bluetooth {
namespace security {
@@ -43,33 +41,11 @@ using os::Handler;
using os::Thread;
using packet::RawBuilder;
-static bool on_link_connected_called = false;
-static bool on_link_disconnected_called = false;
-
-class FakeSecurityManagerChannel : public SecurityManagerChannel {
- public:
- FakeSecurityManagerChannel(os::Handler* handler, hci::HciLayer* hci_layer)
- : SecurityManagerChannel(handler, hci_layer) {}
- ~FakeSecurityManagerChannel() {}
-
- void OnLinkConnected(std::unique_ptr<l2cap::classic::LinkSecurityInterface> link) {
- on_link_connected_called = true;
- }
-
- void OnLinkDisconnected(hci::Address address) {
- on_link_disconnected_called = true;
- }
-
- void OnAuthenticationComplete(hci::ErrorCode hci_status, hci::Address remote) override {}
-
- void OnEncryptionChange(hci::Address address, bool encrypted) override {}
-};
-
class SecurityManagerChannelCallback : public ISecurityManagerChannelListener {
public:
// HCI
bool receivedChangeConnectionLinkKeyComplete = false;
- bool receivedCentralLinkKeyComplete = false;
+ bool receivedMasterLinkKeyComplete = false;
bool receivedPinCodeRequest = false;
bool receivedLinkKeyRequest = false;
bool receivedLinkKeyNotification = false;
@@ -89,9 +65,9 @@ class SecurityManagerChannelCallback : public ISecurityManagerChannelListener {
ASSERT_TRUE(packet.IsValid());
receivedChangeConnectionLinkKeyComplete = true;
}
- void OnReceive(hci::AddressWithType device, hci::CentralLinkKeyCompleteView packet) {
+ void OnReceive(hci::AddressWithType device, hci::MasterLinkKeyCompleteView packet) {
ASSERT_TRUE(packet.IsValid());
- receivedCentralLinkKeyComplete = true;
+ receivedMasterLinkKeyComplete = true;
}
void OnReceive(hci::AddressWithType device, hci::PinCodeRequestView packet) {
ASSERT_TRUE(packet.IsValid());
@@ -150,16 +126,16 @@ class SecurityManagerChannelCallback : public ISecurityManagerChannelListener {
receivedUserPasskeyRequest = true;
}
- void OnHciEventReceived(EventView packet) override {
- auto event = EventView::Create(packet);
+ void OnHciEventReceived(EventPacketView packet) override {
+ auto event = EventPacketView::Create(packet);
ASSERT_LOG(event.IsValid(), "Received invalid packet");
const hci::EventCode code = event.GetEventCode();
switch (code) {
case hci::EventCode::CHANGE_CONNECTION_LINK_KEY_COMPLETE:
OnReceive(hci::AddressWithType(), hci::ChangeConnectionLinkKeyCompleteView::Create(event));
break;
- case hci::EventCode::CENTRAL_LINK_KEY_COMPLETE:
- OnReceive(hci::AddressWithType(), hci::CentralLinkKeyCompleteView::Create(event));
+ case hci::EventCode::MASTER_LINK_KEY_COMPLETE:
+ OnReceive(hci::AddressWithType(), hci::MasterLinkKeyCompleteView::Create(event));
break;
case hci::EventCode::PIN_CODE_REQUEST:
OnReceive(hci::AddressWithType(), hci::PinCodeRequestView::Create(event));
@@ -208,51 +184,34 @@ class SecurityManagerChannelCallback : public ISecurityManagerChannelListener {
break;
}
}
-
- void OnConnectionClosed(hci::Address address) override {
- LOG_INFO("Called");
- }
};
class SecurityManagerChannelTest : public ::testing::Test {
protected:
void SetUp() override {
- hci::Address address;
- hci::Address::FromString("01:23:45:67:89:AB:CD", address);
- device_ = hci::AddressWithType(address, hci::AddressType::PUBLIC_DEVICE_ADDRESS);
- on_link_connected_called = false;
- on_link_disconnected_called = false;
handler_ = new Handler(&thread_);
callback_ = new SecurityManagerChannelCallback();
hci_layer_ = new FakeHciLayer();
fake_registry_.InjectTestModule(&FakeHciLayer::Factory, hci_layer_);
fake_registry_.Start<FakeHciLayer>(&thread_);
- channel_ = new FakeSecurityManagerChannel(handler_, hci_layer_);
+ channel_ = new SecurityManagerChannel(handler_, hci_layer_);
channel_->SetChannelListener(callback_);
- security_interface_ = new FakeSecurityInterface(handler_, channel_);
- channel_->SetSecurityInterface(security_interface_);
}
void TearDown() override {
channel_->SetChannelListener(nullptr);
handler_->Clear();
- synchronize();
+ fake_registry_.SynchronizeModuleHandler(&FakeHciLayer::Factory, std::chrono::milliseconds(20));
fake_registry_.StopAll();
delete handler_;
delete channel_;
delete callback_;
- delete security_interface_;
- }
-
- void synchronize() {
- fake_registry_.SynchronizeModuleHandler(&FakeHciLayer::Factory, std::chrono::milliseconds(20));
}
TestModuleRegistry fake_registry_;
Thread& thread_ = fake_registry_.GetTestThread();
Handler* handler_ = nullptr;
FakeHciLayer* hci_layer_ = nullptr;
- l2cap::classic::SecurityInterface* security_interface_ = nullptr;
SecurityManagerChannel* channel_ = nullptr;
SecurityManagerChannelCallback* callback_ = nullptr;
hci::AddressWithType device_;
@@ -262,7 +221,6 @@ TEST_F(SecurityManagerChannelTest, setup_teardown) {}
TEST_F(SecurityManagerChannelTest, recv_io_cap_request) {
hci_layer_->IncomingEvent(hci::IoCapabilityRequestBuilder::Create(device_.GetAddress()));
- synchronize();
ASSERT_TRUE(callback_->receivedIoCapabilityRequest);
}
@@ -278,7 +236,7 @@ TEST_F(SecurityManagerChannelTest, send_io_cap_request_reply) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -294,7 +252,7 @@ TEST_F(SecurityManagerChannelTest, send_io_cap_request_neg_reply) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -307,13 +265,11 @@ TEST_F(SecurityManagerChannelTest, recv_io_cap_response) {
AuthenticationRequirements authentication_requirements = (AuthenticationRequirements)0x00;
hci_layer_->IncomingEvent(hci::IoCapabilityResponseBuilder::Create(device_.GetAddress(), io_capability, oob_present,
authentication_requirements));
- synchronize();
ASSERT_TRUE(callback_->receivedIoCapabilityResponse);
}
TEST_F(SecurityManagerChannelTest, recv_pin_code_request) {
hci_layer_->IncomingEvent(hci::PinCodeRequestBuilder::Create(device_.GetAddress()));
- synchronize();
ASSERT_TRUE(callback_->receivedPinCodeRequest);
}
@@ -327,7 +283,7 @@ TEST_F(SecurityManagerChannelTest, send_pin_code_request_reply) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -342,7 +298,7 @@ TEST_F(SecurityManagerChannelTest, send_pin_code_request_neg_reply) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -352,14 +308,12 @@ TEST_F(SecurityManagerChannelTest, send_pin_code_request_neg_reply) {
TEST_F(SecurityManagerChannelTest, recv_user_passkey_notification) {
uint32_t passkey = 0x00;
hci_layer_->IncomingEvent(hci::UserPasskeyNotificationBuilder::Create(device_.GetAddress(), passkey));
- synchronize();
ASSERT_TRUE(callback_->receivedUserPasskeyNotification);
}
TEST_F(SecurityManagerChannelTest, recv_user_confirmation_request) {
uint32_t numeric_value = 0x0;
hci_layer_->IncomingEvent(hci::UserConfirmationRequestBuilder::Create(device_.GetAddress(), numeric_value));
- synchronize();
ASSERT_TRUE(callback_->receivedUserConfirmationRequest);
}
@@ -371,7 +325,7 @@ TEST_F(SecurityManagerChannelTest, send_user_confirmation_request_reply) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -386,7 +340,7 @@ TEST_F(SecurityManagerChannelTest, send_user_confirmation_request_negative_reply
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -395,7 +349,6 @@ TEST_F(SecurityManagerChannelTest, send_user_confirmation_request_negative_reply
TEST_F(SecurityManagerChannelTest, recv_remote_oob_data_request) {
hci_layer_->IncomingEvent(hci::RemoteOobDataRequestBuilder::Create(device_.GetAddress()));
- synchronize();
ASSERT_TRUE(callback_->receivedRemoteOobDataRequest);
}
@@ -409,7 +362,7 @@ TEST_F(SecurityManagerChannelTest, send_remote_oob_data_request_reply) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -424,7 +377,7 @@ TEST_F(SecurityManagerChannelTest, send_remote_oob_data_request_neg_reply) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -439,7 +392,7 @@ TEST_F(SecurityManagerChannelTest, send_read_local_oob_data) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -454,7 +407,7 @@ TEST_F(SecurityManagerChannelTest, send_read_local_oob_extended_data) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -463,7 +416,6 @@ TEST_F(SecurityManagerChannelTest, send_read_local_oob_extended_data) {
TEST_F(SecurityManagerChannelTest, recv_link_key_request) {
hci_layer_->IncomingEvent(hci::LinkKeyRequestBuilder::Create(device_.GetAddress()));
- synchronize();
ASSERT_TRUE(callback_->receivedLinkKeyRequest);
}
@@ -471,30 +423,26 @@ TEST_F(SecurityManagerChannelTest, recv_link_key_notification) {
std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
hci_layer_->IncomingEvent(
hci::LinkKeyNotificationBuilder::Create(device_.GetAddress(), link_key, hci::KeyType::DEBUG_COMBINATION));
- synchronize();
ASSERT_TRUE(callback_->receivedLinkKeyNotification);
}
-TEST_F(SecurityManagerChannelTest, recv_central_link_key_complete) {
+TEST_F(SecurityManagerChannelTest, recv_master_link_key_complete) {
uint16_t connection_handle = 0x0;
hci_layer_->IncomingEvent(
- hci::CentralLinkKeyCompleteBuilder::Create(hci::ErrorCode::SUCCESS, connection_handle, hci::KeyFlag::TEMPORARY));
- synchronize();
- ASSERT_TRUE(callback_->receivedCentralLinkKeyComplete);
+ hci::MasterLinkKeyCompleteBuilder::Create(hci::ErrorCode::SUCCESS, connection_handle, hci::KeyFlag::TEMPORARY));
+ ASSERT_TRUE(callback_->receivedMasterLinkKeyComplete);
}
TEST_F(SecurityManagerChannelTest, recv_change_connection_link_key_complete) {
uint16_t connection_handle = 0x0;
hci_layer_->IncomingEvent(
hci::ChangeConnectionLinkKeyCompleteBuilder::Create(hci::ErrorCode::SUCCESS, connection_handle));
- synchronize();
ASSERT_TRUE(callback_->receivedChangeConnectionLinkKeyComplete);
}
TEST_F(SecurityManagerChannelTest, recv_return_link_keys) {
std::vector<hci::ZeroKeyAndAddress> keys;
hci_layer_->IncomingEvent(hci::ReturnLinkKeysBuilder::Create(keys));
- synchronize();
ASSERT_TRUE(callback_->receivedReturnLinkKeys);
}
@@ -507,7 +455,7 @@ TEST_F(SecurityManagerChannelTest, send_link_key_request_reply) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -522,7 +470,7 @@ TEST_F(SecurityManagerChannelTest, send_link_key_request_neg_reply) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -537,7 +485,7 @@ TEST_F(SecurityManagerChannelTest, send_read_stored_link_key) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -553,7 +501,7 @@ TEST_F(SecurityManagerChannelTest, send_write_stored_link_key) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -569,26 +517,17 @@ TEST_F(SecurityManagerChannelTest, send_delete_stored_link_key) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
ASSERT_EQ(OpCode::DELETE_STORED_LINK_KEY, packet_view.GetOpCode());
}
-TEST_F(SecurityManagerChannelTest, recv_encryption_change) {
- uint16_t connection_handle = 0x0;
- hci_layer_->IncomingEvent(
- hci::EncryptionChangeBuilder::Create(hci::ErrorCode::SUCCESS, connection_handle, hci::EncryptionEnabled::ON));
- synchronize();
- ASSERT_TRUE(callback_->receivedEncryptionChange);
-}
-
TEST_F(SecurityManagerChannelTest, recv_encryption_key_refresh) {
uint16_t connection_handle = 0x0;
hci_layer_->IncomingEvent(
hci::EncryptionKeyRefreshCompleteBuilder::Create(hci::ErrorCode::SUCCESS, connection_handle));
- synchronize();
ASSERT_TRUE(callback_->receivedEncryptionKeyRefreshComplete);
}
@@ -601,7 +540,7 @@ TEST_F(SecurityManagerChannelTest, send_refresh_encryption_key) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -617,7 +556,7 @@ TEST_F(SecurityManagerChannelTest, send_read_encryption_key_size) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -626,7 +565,6 @@ TEST_F(SecurityManagerChannelTest, send_read_encryption_key_size) {
TEST_F(SecurityManagerChannelTest, recv_simple_pairing_complete) {
hci_layer_->IncomingEvent(hci::SimplePairingCompleteBuilder::Create(hci::ErrorCode::SUCCESS, device_.GetAddress()));
- synchronize();
ASSERT_TRUE(callback_->receivedSimplePairingComplete);
}
@@ -638,7 +576,7 @@ TEST_F(SecurityManagerChannelTest, send_read_simple_pairing_mode) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -653,7 +591,7 @@ TEST_F(SecurityManagerChannelTest, send_write_simple_pairing_mode) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -663,7 +601,6 @@ TEST_F(SecurityManagerChannelTest, send_write_simple_pairing_mode) {
TEST_F(SecurityManagerChannelTest, recv_keypress_notification) {
hci_layer_->IncomingEvent(
hci::KeypressNotificationBuilder::Create(device_.GetAddress(), hci::KeypressNotificationType::ENTRY_COMPLETED));
- synchronize();
ASSERT_TRUE(callback_->receivedKeypressNotification);
}
@@ -676,7 +613,7 @@ TEST_F(SecurityManagerChannelTest, send_keypress_notification) {
channel_->SendCommand(std::move(packet));
auto last_command = std::move(hci_layer_->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- hci::CommandView packet_view = hci::CommandView::Create(command_packet);
+ hci::CommandPacketView packet_view = hci::CommandPacketView::Create(command_packet);
// Assert
ASSERT_TRUE(packet_view.IsValid());
@@ -685,20 +622,9 @@ TEST_F(SecurityManagerChannelTest, send_keypress_notification) {
TEST_F(SecurityManagerChannelTest, recv_user_passkey_request) {
hci_layer_->IncomingEvent(hci::UserPasskeyRequestBuilder::Create(device_.GetAddress()));
- synchronize();
ASSERT_TRUE(callback_->receivedUserPasskeyRequest);
}
-TEST_F(SecurityManagerChannelTest, test_l2cap_security_interface_api) {
- ASSERT_FALSE(on_link_connected_called);
- channel_->Connect(device_.GetAddress());
- ASSERT_TRUE(on_link_connected_called);
- ASSERT_FALSE(on_link_disconnected_called);
- channel_->Release(device_.GetAddress());
- // TODO(optedoblivion): Lock and wait
- // ASSERT_TRUE(on_link_disconnected_called);
-}
-
} // namespace
} // namespace channel
} // namespace security
diff --git a/gd/security/ecdh_keys.cc b/gd/security/ecdh_keys.cc
index 9a4214b84..951654ce0 100644
--- a/gd/security/ecdh_keys.cc
+++ b/gd/security/ecdh_keys.cc
@@ -22,7 +22,6 @@
TODO: We should have random number management in separate file, and we
should honour all the random number requirements from the spec!!
**********************************************************************************************************************/
-#include <string.h>
#include <chrono>
#include <cstdlib>
diff --git a/gd/security/ecdh_keys.h b/gd/security/ecdh_keys.h
index f9c43023b..8ec25a890 100644
--- a/gd/security/ecdh_keys.h
+++ b/gd/security/ecdh_keys.h
@@ -17,7 +17,6 @@
******************************************************************************/
#pragma once
-#include <stdint.h>
#include <array>
namespace bluetooth {
diff --git a/gd/security/facade.cc b/gd/security/facade.cc
index f2baaf0c9..c9d4ee69c 100644
--- a/gd/security/facade.cc
+++ b/gd/security/facade.cc
@@ -17,139 +17,30 @@
#include "grpc/grpc_event_queue.h"
#include "hci/address_with_type.h"
-#include "hci/le_address_manager.h"
-#include "l2cap/classic/security_policy.h"
-#include "l2cap/le/l2cap_le_module.h"
#include "os/handler.h"
#include "security/facade.grpc.pb.h"
-#include "security/pairing/oob_data.h"
#include "security/security_manager_listener.h"
#include "security/security_module.h"
-#include "security/ui.h"
-
-using bluetooth::l2cap::le::L2capLeModule;
namespace bluetooth {
namespace security {
-namespace {
-constexpr uint8_t AUTH_REQ_NO_BOND = 0x01;
-constexpr uint8_t AUTH_REQ_BOND = 0x01;
-constexpr uint8_t AUTH_REQ_MITM_MASK = 0x04;
-constexpr uint8_t AUTH_REQ_SECURE_CONNECTIONS_MASK = 0x08;
-constexpr uint8_t AUTH_REQ_KEYPRESS_MASK = 0x10;
-constexpr uint8_t AUTH_REQ_CT2_MASK = 0x20;
-constexpr uint8_t AUTH_REQ_RFU_MASK = 0xC0;
-
-facade::BluetoothAddressWithType ToFacadeAddressWithType(hci::AddressWithType address) {
- facade::BluetoothAddressWithType ret;
-
- ret.mutable_address()->set_address(address.GetAddress().ToString());
- ret.set_type(static_cast<facade::BluetoothAddressTypeEnum>(address.GetAddressType()));
-
- return ret;
-}
-
-} // namespace
-
class SecurityModuleFacadeService : public SecurityModuleFacade::Service, public ISecurityManagerListener, public UI {
public:
- SecurityModuleFacadeService(
- SecurityModule* security_module, L2capLeModule* l2cap_le_module, ::bluetooth::os::Handler* security_handler)
- : security_module_(security_module), l2cap_le_module_(l2cap_le_module), security_handler_(security_handler) {
+ SecurityModuleFacadeService(SecurityModule* security_module, ::bluetooth::os::Handler* security_handler)
+ : security_module_(security_module), security_handler_(security_handler) {
security_module_->GetSecurityManager()->RegisterCallbackListener(this, security_handler_);
- security_module_->GetSecurityManager()->SetUserInterfaceHandler(this, security_handler_);
-
- /* In order to receive connect/disconenct event, we must register service */
- l2cap_le_module_->GetFixedChannelManager()->RegisterService(
- bluetooth::l2cap::kLastFixedChannel - 2,
- common::BindOnce(&SecurityModuleFacadeService::OnL2capRegistrationCompleteLe, common::Unretained(this)),
- common::Bind(&SecurityModuleFacadeService::OnConnectionOpenLe, common::Unretained(this)),
- security_handler_);
- }
-
- void OnL2capRegistrationCompleteLe(
- l2cap::le::FixedChannelManager::RegistrationResult result,
- std::unique_ptr<l2cap::le::FixedChannelService> le_smp_service) {
- ASSERT_LOG(
- result == bluetooth::l2cap::le::FixedChannelManager::RegistrationResult::SUCCESS,
- "Failed to register to LE SMP Fixed Channel Service");
- }
-
- void OnConnectionOpenLe(std::unique_ptr<l2cap::le::FixedChannel> channel) {
- channel->RegisterOnCloseCallback(
- security_handler_,
- common::BindOnce(
- &SecurityModuleFacadeService::OnConnectionClosedLe, common::Unretained(this), channel->GetDevice()));
- }
-
- void OnConnectionClosedLe(hci::AddressWithType address, hci::ErrorCode error_code) {
- SecurityHelperMsg disconnected;
- *disconnected.mutable_peer() = ToFacadeAddressWithType(address);
- disconnected.set_message_type(HelperMsgType::DEVICE_DISCONNECTED);
- helper_events_.OnIncomingEvent(disconnected);
}
::grpc::Status CreateBond(::grpc::ServerContext* context, const facade::BluetoothAddressWithType* request,
::google::protobuf::Empty* response) override {
hci::Address peer;
ASSERT(hci::Address::FromString(request->address().address(), peer));
- hci::AddressType peer_type = static_cast<hci::AddressType>(request->type());
+ hci::AddressType peer_type = hci::AddressType::PUBLIC_DEVICE_ADDRESS;
security_module_->GetSecurityManager()->CreateBond(hci::AddressWithType(peer, peer_type));
return ::grpc::Status::OK;
}
- ::grpc::Status CreateBondOutOfBand(
- ::grpc::ServerContext* context,
- const ::bluetooth::security::OobDataBondMessage* request,
- ::google::protobuf::Empty* response) override {
- hci::Address peer;
- ASSERT(hci::Address::FromString(request->address().address().address(), peer));
- hci::AddressType peer_type = static_cast<hci::AddressType>(request->address().type());
- pairing::SimplePairingHash c;
- pairing::SimplePairingRandomizer r;
- std::copy(
- std::begin(request->p192_data().confirmation_value()),
- std::end(request->p192_data().confirmation_value()),
- c.data());
- std::copy(std::begin(request->p192_data().random_value()), std::end(request->p192_data().random_value()), r.data());
- pairing::OobData p192_data(c, r);
- std::copy(
- std::begin(request->p256_data().confirmation_value()),
- std::end(request->p256_data().confirmation_value()),
- c.data());
- std::copy(std::begin(request->p256_data().random_value()), std::end(request->p256_data().random_value()), r.data());
- pairing::OobData p256_data(c, r);
- security_module_->GetSecurityManager()->CreateBondOutOfBand(
- hci::AddressWithType(peer, peer_type), p192_data, p256_data);
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status GetOutOfBandData(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::google::protobuf::Empty* response) override {
- security_module_->GetSecurityManager()->GetOutOfBandData(
- security_handler_->BindOnceOn(this, &SecurityModuleFacadeService::OobDataEventOccurred));
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status FetchGetOutOfBandDataEvents(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<OobDataBondMessage>* writer) override {
- return oob_events_.RunLoop(context, writer);
- }
-
- ::grpc::Status CreateBondLe(::grpc::ServerContext* context, const facade::BluetoothAddressWithType* request,
- ::google::protobuf::Empty* response) override {
- hci::Address peer;
- ASSERT(hci::Address::FromString(request->address().address(), peer));
- hci::AddressType peer_type = static_cast<hci::AddressType>(request->type());
- security_module_->GetSecurityManager()->CreateBondLe(hci::AddressWithType(peer, peer_type));
- return ::grpc::Status::OK;
- }
-
::grpc::Status CancelBond(::grpc::ServerContext* context, const facade::BluetoothAddressWithType* request,
::google::protobuf::Empty* response) override {
hci::Address peer;
@@ -175,28 +66,12 @@ class SecurityModuleFacadeService : public SecurityModuleFacade::Service, public
::grpc::Status SendUiCallback(::grpc::ServerContext* context, const UiCallbackMsg* request,
::google::protobuf::Empty* response) override {
- hci::Address peer;
- ASSERT(hci::Address::FromString(request->address().address().address(), peer));
- hci::AddressType remote_type = static_cast<hci::AddressType>(request->address().type());
-
switch (request->message_type()) {
case UiCallbackType::PASSKEY:
- security_module_->GetSecurityManager()->OnPasskeyEntry(
- hci::AddressWithType(peer, remote_type), request->numeric_value());
+ // TODO: security_module_->GetSecurityManager()->OnPasskeyEntry();
break;
case UiCallbackType::YES_NO:
- security_module_->GetSecurityManager()->OnConfirmYesNo(hci::AddressWithType(peer, remote_type),
- request->boolean());
- break;
- case UiCallbackType::PAIRING_PROMPT:
- security_module_->GetSecurityManager()->OnPairingPromptAccepted(
- hci::AddressWithType(peer, remote_type), request->boolean());
- break;
- case UiCallbackType::PIN:
- LOG_INFO("PIN Callback");
- security_module_->GetSecurityManager()->OnPinEntry(
- hci::AddressWithType(peer, remote_type),
- std::vector<uint8_t>(request->pin().cbegin(), request->pin().cend()));
+ // TODO: security_module_->GetSecurityManager()->OnConfirmYesNo(request->boolean());
break;
default:
LOG_ERROR("Unknown UiCallbackType %d", static_cast<int>(request->message_type()));
@@ -210,280 +85,62 @@ class SecurityModuleFacadeService : public SecurityModuleFacade::Service, public
return bond_events_.RunLoop(context, writer);
}
- ::grpc::Status FetchHelperEvents(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<SecurityHelperMsg>* writer) override {
- return helper_events_.RunLoop(context, writer);
- }
- ::grpc::Status SetIoCapability(::grpc::ServerContext* context, const IoCapabilityMessage* request,
- ::google::protobuf::Empty* response) override {
- security_module_->GetFacadeConfigurationApi()->SetIoCapability(
- static_cast<hci::IoCapability>(request->capability()));
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status SetLeIoCapability(
- ::grpc::ServerContext* context,
- const LeIoCapabilityMessage* request,
- ::google::protobuf::Empty* response) override {
- security_module_->GetFacadeConfigurationApi()->SetLeIoCapability(
- static_cast<security::IoCapability>(request->capabilities()));
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status SetAuthenticationRequirements(::grpc::ServerContext* context,
- const AuthenticationRequirementsMessage* request,
- ::google::protobuf::Empty* response) override {
- security_module_->GetFacadeConfigurationApi()->SetAuthenticationRequirements(
- static_cast<hci::AuthenticationRequirements>(request->requirement()));
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status SetLeAuthRequirements(
- ::grpc::ServerContext* context,
- const LeAuthRequirementsMessage* request,
- ::google::protobuf::Empty* response) override {
- uint8_t auth_req = request->bond() ? AUTH_REQ_BOND : AUTH_REQ_NO_BOND;
-
- if (request->mitm()) auth_req |= AUTH_REQ_MITM_MASK;
- if (request->secure_connections()) auth_req |= AUTH_REQ_SECURE_CONNECTIONS_MASK;
- if (request->keypress()) auth_req |= AUTH_REQ_KEYPRESS_MASK;
- if (request->ct2()) auth_req |= AUTH_REQ_CT2_MASK;
- if (request->reserved_bits()) auth_req |= (((request->reserved_bits()) << 6) & AUTH_REQ_RFU_MASK);
-
- security_module_->GetFacadeConfigurationApi()->SetLeAuthRequirements(auth_req);
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status SetLeMaximumEncryptionKeySize(
- ::grpc::ServerContext* context,
- const LeMaximumEncryptionKeySizeMessage* request,
- ::google::protobuf::Empty* response) override {
- security_module_->GetFacadeConfigurationApi()->SetLeMaximumEncryptionKeySize(
- request->maximum_encryption_key_size());
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status SetLeOobDataPresent(
- ::grpc::ServerContext* context,
- const LeOobDataPresentMessage* request,
- ::google::protobuf::Empty* response) override {
- security_module_->GetFacadeConfigurationApi()->SetLeOobDataPresent(
- static_cast<OobDataFlag>(request->data_present()));
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status SetLeInitiatorAddressPolicy(
- ::grpc::ServerContext* context, const hci::PrivacyPolicy* request, ::google::protobuf::Empty* response) override {
- Address address = Address::kEmpty;
- hci::LeAddressManager::AddressPolicy address_policy =
- static_cast<hci::LeAddressManager::AddressPolicy>(request->address_policy());
- if (address_policy == hci::LeAddressManager::AddressPolicy::USE_STATIC_ADDRESS ||
- address_policy == hci::LeAddressManager::AddressPolicy::USE_PUBLIC_ADDRESS) {
- ASSERT(Address::FromString(request->address_with_type().address().address(), address));
- }
- hci::AddressWithType address_with_type(address, static_cast<hci::AddressType>(request->address_with_type().type()));
- crypto_toolbox::Octet16 irk = {};
- auto request_irk_length = request->rotation_irk().end() - request->rotation_irk().begin();
- if (request_irk_length == crypto_toolbox::OCTET16_LEN) {
- std::vector<uint8_t> irk_data(request->rotation_irk().begin(), request->rotation_irk().end());
- std::copy_n(irk_data.begin(), crypto_toolbox::OCTET16_LEN, irk.begin());
- } else {
- ASSERT(request_irk_length == 0);
- }
- auto minimum_rotation_time = std::chrono::milliseconds(request->minimum_rotation_time());
- auto maximum_rotation_time = std::chrono::milliseconds(request->maximum_rotation_time());
- security_module_->GetSecurityManager()->SetLeInitiatorAddressPolicyForTest(
- address_policy, address_with_type, irk, minimum_rotation_time, maximum_rotation_time);
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status FetchEnforceSecurityPolicyEvents(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<EnforceSecurityPolicyMsg>* writer) override {
- return enforce_security_policy_events_.RunLoop(context, writer);
- }
-
- ::grpc::Status EnforceSecurityPolicy(
- ::grpc::ServerContext* context,
- const SecurityPolicyMessage* request,
- ::google::protobuf::Empty* response) override {
- hci::Address peer;
- ASSERT(hci::Address::FromString(request->address().address().address(), peer));
- hci::AddressType peer_type = static_cast<hci::AddressType>(request->address().type());
- hci::AddressWithType peer_with_type(peer, peer_type);
- l2cap::classic::SecurityEnforcementInterface::ResultCallback callback =
- security_handler_->BindOnceOn(this, &SecurityModuleFacadeService::EnforceSecurityPolicyEvent);
- security_module_->GetFacadeConfigurationApi()->EnforceSecurityPolicy(
- peer_with_type, static_cast<l2cap::classic::SecurityPolicy>(request->policy()), std::move(callback));
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status GetLeOutOfBandData(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::bluetooth::security::OobDataMessage* response) override {
- std::array<uint8_t, 16> le_sc_c;
- std::array<uint8_t, 16> le_sc_r;
- security_module_->GetFacadeConfigurationApi()->GetLeOutOfBandData(&le_sc_c, &le_sc_r);
-
- std::string le_sc_c_str(17, '\0');
- std::copy(le_sc_c.begin(), le_sc_c.end(), le_sc_c_str.data());
- response->set_confirmation_value(le_sc_c_str);
-
- std::string le_sc_r_str(17, '\0');
- std::copy(le_sc_r.begin(), le_sc_r.end(), le_sc_r_str.data());
- response->set_random_value(le_sc_r_str);
-
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status SetOutOfBandData(
- ::grpc::ServerContext* context,
- const ::bluetooth::security::OobDataMessage* request,
- ::google::protobuf::Empty* response) override {
- hci::Address peer;
- ASSERT(hci::Address::FromString(request->address().address().address(), peer));
- hci::AddressType peer_type = static_cast<hci::AddressType>(request->address().type());
- hci::AddressWithType peer_with_type(peer, peer_type);
-
- // We can't simply iterate till end of string, because we have an empty byte added at the end. We know confirm and
- // random are fixed size, 16 bytes
- std::array<uint8_t, 16> le_sc_c;
- auto req_le_sc_c = request->confirmation_value();
- std::copy(req_le_sc_c.begin(), req_le_sc_c.begin() + 16, le_sc_c.data());
-
- std::array<uint8_t, 16> le_sc_r;
- auto req_le_sc_r = request->random_value();
- std::copy(req_le_sc_r.begin(), req_le_sc_r.begin() + 16, le_sc_r.data());
-
- security_module_->GetFacadeConfigurationApi()->SetOutOfBandData(peer_with_type, le_sc_c, le_sc_r);
- return ::grpc::Status::OK;
- }
-
- ::grpc::Status FetchDisconnectEvents(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<DisconnectMsg>* writer) override {
- security_module_->GetFacadeConfigurationApi()->SetDisconnectCallback(
- common::Bind(&SecurityModuleFacadeService::DisconnectEventOccurred, common::Unretained(this)));
- return disconnect_events_.RunLoop(context, writer);
- }
-
- void OobDataEventOccurred(bluetooth::hci::CommandCompleteView packet) {
- LOG_INFO("Got OOB Data event");
- ASSERT(packet.IsValid());
- auto cc = bluetooth::hci::ReadLocalOobDataCompleteView::Create(packet);
- ASSERT(cc.IsValid());
- OobDataBondMessage msg;
- OobDataMessage p192;
- // Just need this to satisfy the proto message
- bluetooth::hci::AddressWithType peer;
- *p192.mutable_address() = ToFacadeAddressWithType(peer);
-
- auto c = cc.GetC();
- p192.set_confirmation_value(c.data(), c.size());
-
- auto r = cc.GetR();
- p192.set_random_value(r.data(), r.size());
-
- // Only the Extended version returns 256 also.
- // The API has a parameter for both, so we set it
- // empty and the module and test suite will ignore it.
- OobDataMessage p256;
- *p256.mutable_address() = ToFacadeAddressWithType(peer);
-
- std::array<uint8_t, 16> empty_val;
- p256.set_confirmation_value(empty_val.data(), empty_val.size());
- p256.set_random_value(empty_val.data(), empty_val.size());
-
- *msg.mutable_address() = ToFacadeAddressWithType(peer);
- *msg.mutable_p192_data() = p192;
- *msg.mutable_p256_data() = p256;
- oob_events_.OnIncomingEvent(msg);
- }
-
- void DisconnectEventOccurred(bluetooth::hci::AddressWithType peer) {
- LOG_INFO("%s", peer.ToString().c_str());
- DisconnectMsg msg;
- *msg.mutable_address() = ToFacadeAddressWithType(peer);
- disconnect_events_.OnIncomingEvent(msg);
- }
-
void DisplayPairingPrompt(const bluetooth::hci::AddressWithType& peer, std::string name) {
LOG_INFO("%s", peer.ToString().c_str());
UiMsg display_yes_no;
- *display_yes_no.mutable_peer() = ToFacadeAddressWithType(peer);
- display_yes_no.set_message_type(UiMsgType::DISPLAY_PAIRING_PROMPT);
+ display_yes_no.mutable_peer()->mutable_address()->set_address(peer.ToString());
+ display_yes_no.mutable_peer()->set_type(facade::BluetoothAddressTypeEnum::PUBLIC_DEVICE_ADDRESS);
+ display_yes_no.set_message_type(UiMsgType::DISPLAY_YES_NO);
display_yes_no.set_unique_id(unique_id++);
- ui_events_.OnIncomingEvent(display_yes_no);
}
- virtual void DisplayConfirmValue(ConfirmationData data) {
- const bluetooth::hci::AddressWithType& peer = data.GetAddressWithType();
- std::string name = data.GetName();
- uint32_t numeric_value = data.GetNumericValue();
+ virtual void DisplayConfirmValue(const bluetooth::hci::AddressWithType& peer, std::string name,
+ uint32_t numeric_value) {
LOG_INFO("%s value = 0x%x", peer.ToString().c_str(), numeric_value);
UiMsg display_with_value;
- *display_with_value.mutable_peer() = ToFacadeAddressWithType(peer);
+ display_with_value.mutable_peer()->mutable_address()->set_address(peer.ToString());
+ display_with_value.mutable_peer()->set_type(facade::BluetoothAddressTypeEnum::PUBLIC_DEVICE_ADDRESS);
display_with_value.set_message_type(UiMsgType::DISPLAY_YES_NO_WITH_VALUE);
display_with_value.set_numeric_value(numeric_value);
display_with_value.set_unique_id(unique_id++);
ui_events_.OnIncomingEvent(display_with_value);
}
- void DisplayYesNoDialog(ConfirmationData data) override {
- const bluetooth::hci::AddressWithType& peer = data.GetAddressWithType();
- std::string name = data.GetName();
+ void DisplayYesNoDialog(const bluetooth::hci::AddressWithType& peer, std::string name) override {
LOG_INFO("%s", peer.ToString().c_str());
UiMsg display_yes_no;
- *display_yes_no.mutable_peer() = ToFacadeAddressWithType(peer);
+ display_yes_no.mutable_peer()->mutable_address()->set_address(peer.ToString());
+ display_yes_no.mutable_peer()->set_type(facade::BluetoothAddressTypeEnum::PUBLIC_DEVICE_ADDRESS);
display_yes_no.set_message_type(UiMsgType::DISPLAY_YES_NO);
display_yes_no.set_unique_id(unique_id++);
- ui_events_.OnIncomingEvent(display_yes_no);
}
- void DisplayPasskey(ConfirmationData data) override {
- const bluetooth::hci::AddressWithType& peer = data.GetAddressWithType();
- std::string name = data.GetName();
- uint32_t passkey = data.GetNumericValue();
+ void DisplayPasskey(const bluetooth::hci::AddressWithType& peer, std::string name, uint32_t passkey) override {
LOG_INFO("%s value = 0x%x", peer.ToString().c_str(), passkey);
UiMsg display_passkey;
- *display_passkey.mutable_peer() = ToFacadeAddressWithType(peer);
+ display_passkey.mutable_peer()->mutable_address()->set_address(peer.ToString());
+ display_passkey.mutable_peer()->set_type(facade::BluetoothAddressTypeEnum::PUBLIC_DEVICE_ADDRESS);
display_passkey.set_message_type(UiMsgType::DISPLAY_PASSKEY);
display_passkey.set_numeric_value(passkey);
display_passkey.set_unique_id(unique_id++);
ui_events_.OnIncomingEvent(display_passkey);
}
- void DisplayEnterPasskeyDialog(ConfirmationData data) override {
- const bluetooth::hci::AddressWithType& peer = data.GetAddressWithType();
- std::string name = data.GetName();
+ void DisplayEnterPasskeyDialog(const bluetooth::hci::AddressWithType& peer, std::string name) override {
LOG_INFO("%s", peer.ToString().c_str());
UiMsg display_passkey_input;
- *display_passkey_input.mutable_peer() = ToFacadeAddressWithType(peer);
+ display_passkey_input.mutable_peer()->mutable_address()->set_address(peer.ToString());
+ display_passkey_input.mutable_peer()->set_type(facade::BluetoothAddressTypeEnum::PUBLIC_DEVICE_ADDRESS);
display_passkey_input.set_message_type(UiMsgType::DISPLAY_PASSKEY_ENTRY);
display_passkey_input.set_unique_id(unique_id++);
ui_events_.OnIncomingEvent(display_passkey_input);
}
- void DisplayEnterPinDialog(ConfirmationData data) override {
- const bluetooth::hci::AddressWithType& peer = data.GetAddressWithType();
- std::string name = data.GetName();
- LOG_INFO("%s", peer.ToString().c_str());
- UiMsg display_pin_input;
- *display_pin_input.mutable_peer() = ToFacadeAddressWithType(peer);
- display_pin_input.set_message_type(UiMsgType::DISPLAY_PIN_ENTRY);
- display_pin_input.set_unique_id(unique_id++);
- ui_events_.OnIncomingEvent(display_pin_input);
- }
-
void Cancel(const bluetooth::hci::AddressWithType& peer) override {
LOG_INFO("%s", peer.ToString().c_str());
UiMsg display_cancel;
- *display_cancel.mutable_peer() = ToFacadeAddressWithType(peer);
+ display_cancel.mutable_peer()->mutable_address()->set_address(peer.ToString());
+ display_cancel.mutable_peer()->set_type(facade::BluetoothAddressTypeEnum::PUBLIC_DEVICE_ADDRESS);
display_cancel.set_message_type(UiMsgType::DISPLAY_CANCEL);
display_cancel.set_unique_id(unique_id++);
ui_events_.OnIncomingEvent(display_cancel);
@@ -492,47 +149,35 @@ class SecurityModuleFacadeService : public SecurityModuleFacade::Service, public
void OnDeviceBonded(hci::AddressWithType peer) override {
LOG_INFO("%s", peer.ToString().c_str());
BondMsg bonded;
- *bonded.mutable_peer() = ToFacadeAddressWithType(peer);
+ bonded.mutable_peer()->mutable_address()->set_address(peer.ToString());
+ bonded.mutable_peer()->set_type(facade::BluetoothAddressTypeEnum::PUBLIC_DEVICE_ADDRESS);
bonded.set_message_type(BondMsgType::DEVICE_BONDED);
bond_events_.OnIncomingEvent(bonded);
}
- void OnEncryptionStateChanged(hci::EncryptionChangeView encryption_change_view) override {}
-
void OnDeviceUnbonded(hci::AddressWithType peer) override {
LOG_INFO("%s", peer.ToString().c_str());
BondMsg unbonded;
- *unbonded.mutable_peer() = ToFacadeAddressWithType(peer);
+ unbonded.mutable_peer()->mutable_address()->set_address(peer.ToString());
+ unbonded.mutable_peer()->set_type(facade::BluetoothAddressTypeEnum::PUBLIC_DEVICE_ADDRESS);
unbonded.set_message_type(BondMsgType::DEVICE_UNBONDED);
bond_events_.OnIncomingEvent(unbonded);
}
- void OnDeviceBondFailed(hci::AddressWithType peer, PairingFailure status) override {
+ void OnDeviceBondFailed(hci::AddressWithType peer) override {
LOG_INFO("%s", peer.ToString().c_str());
BondMsg bond_failed;
- *bond_failed.mutable_peer() = ToFacadeAddressWithType(peer);
+ bond_failed.mutable_peer()->mutable_address()->set_address(peer.ToString());
+ bond_failed.mutable_peer()->set_type(facade::BluetoothAddressTypeEnum::PUBLIC_DEVICE_ADDRESS);
bond_failed.set_message_type(BondMsgType::DEVICE_BOND_FAILED);
- bond_failed.set_reason(static_cast<uint8_t>(status.reason));
bond_events_.OnIncomingEvent(bond_failed);
}
- void EnforceSecurityPolicyEvent(bool result) {
- EnforceSecurityPolicyMsg msg;
- msg.set_result(result);
- enforce_security_policy_events_.OnIncomingEvent(msg);
- }
-
private:
SecurityModule* security_module_;
- L2capLeModule* l2cap_le_module_;
::bluetooth::os::Handler* security_handler_;
::bluetooth::grpc::GrpcEventQueue<UiMsg> ui_events_{"UI events"};
::bluetooth::grpc::GrpcEventQueue<BondMsg> bond_events_{"Bond events"};
- ::bluetooth::grpc::GrpcEventQueue<SecurityHelperMsg> helper_events_{"Events that don't fit any other category"};
- ::bluetooth::grpc::GrpcEventQueue<EnforceSecurityPolicyMsg> enforce_security_policy_events_{
- "Enforce Security Policy Events"};
- ::bluetooth::grpc::GrpcEventQueue<DisconnectMsg> disconnect_events_{"Disconnect events"};
- ::bluetooth::grpc::GrpcEventQueue<OobDataBondMessage> oob_events_{"OOB Data events"};
uint32_t unique_id{1};
std::map<uint32_t, common::OnceCallback<void(bool)>> user_yes_no_callbacks_;
std::map<uint32_t, common::OnceCallback<void(uint32_t)>> user_passkey_callbacks_;
@@ -541,13 +186,11 @@ class SecurityModuleFacadeService : public SecurityModuleFacade::Service, public
void SecurityModuleFacadeModule::ListDependencies(ModuleList* list) {
::bluetooth::grpc::GrpcFacadeModule::ListDependencies(list);
list->add<SecurityModule>();
- list->add<L2capLeModule>();
}
void SecurityModuleFacadeModule::Start() {
::bluetooth::grpc::GrpcFacadeModule::Start();
- service_ =
- new SecurityModuleFacadeService(GetDependency<SecurityModule>(), GetDependency<L2capLeModule>(), GetHandler());
+ service_ = new SecurityModuleFacadeService(GetDependency<SecurityModule>(), GetHandler());
}
void SecurityModuleFacadeModule::Stop() {
diff --git a/gd/security/facade.proto b/gd/security/facade.proto
index 008fdb632..e1362aec3 100644
--- a/gd/security/facade.proto
+++ b/gd/security/facade.proto
@@ -4,45 +4,14 @@ package bluetooth.security;
import "google/protobuf/empty.proto";
import "facade/common.proto";
-import "l2cap/classic/facade.proto";
-import "hci/facade/le_initiator_address_facade.proto";
service SecurityModuleFacade {
rpc CreateBond(facade.BluetoothAddressWithType) returns (google.protobuf.Empty) {}
- rpc CreateBondOutOfBand(OobDataBondMessage) returns (google.protobuf.Empty) {}
- rpc GetOutOfBandData(google.protobuf.Empty) returns (google.protobuf.Empty) {}
- rpc FetchGetOutOfBandDataEvents(google.protobuf.Empty) returns (stream OobDataBondMessage) {}
- rpc CreateBondLe(facade.BluetoothAddressWithType) returns (google.protobuf.Empty) {}
rpc CancelBond(facade.BluetoothAddressWithType) returns (google.protobuf.Empty) {}
rpc RemoveBond(facade.BluetoothAddressWithType) returns (google.protobuf.Empty) {}
- rpc SetIoCapability(IoCapabilityMessage) returns (google.protobuf.Empty) {}
- rpc SetAuthenticationRequirements(AuthenticationRequirementsMessage) returns (google.protobuf.Empty) {}
- rpc SetLeIoCapability(LeIoCapabilityMessage) returns (google.protobuf.Empty) {}
- rpc SetLeAuthRequirements(LeAuthRequirementsMessage) returns (google.protobuf.Empty) {}
- rpc SetLeMaximumEncryptionKeySize(LeMaximumEncryptionKeySizeMessage) returns (google.protobuf.Empty) {}
- rpc GetLeOutOfBandData(google.protobuf.Empty) returns (OobDataMessage) {}
- rpc SetOutOfBandData(OobDataMessage) returns (google.protobuf.Empty) {}
- rpc SetLeOobDataPresent(LeOobDataPresentMessage) returns (google.protobuf.Empty) {}
- rpc SetLeInitiatorAddressPolicy(hci.PrivacyPolicy) returns (google.protobuf.Empty) {}
rpc SendUiCallback(UiCallbackMsg) returns (google.protobuf.Empty) {}
rpc FetchUiEvents(google.protobuf.Empty) returns (stream UiMsg) {}
rpc FetchBondEvents(google.protobuf.Empty) returns (stream BondMsg) {}
- rpc FetchHelperEvents(google.protobuf.Empty) returns (stream SecurityHelperMsg) {}
- rpc EnforceSecurityPolicy(SecurityPolicyMessage) returns (google.protobuf.Empty) {}
- rpc FetchEnforceSecurityPolicyEvents(google.protobuf.Empty) returns (stream EnforceSecurityPolicyMsg) {}
- rpc FetchDisconnectEvents(google.protobuf.Empty) returns (stream DisconnectMsg) {}
-}
-
-message OobDataMessage {
- facade.BluetoothAddressWithType address = 1;
- bytes confirmation_value = 2;
- bytes random_value = 3;
-}
-
-message OobDataBondMessage {
- facade.BluetoothAddressWithType address = 1;
- OobDataMessage p192_data = 2;
- OobDataMessage p256_data = 3;
}
enum UiMsgType {
@@ -51,8 +20,6 @@ enum UiMsgType {
DISPLAY_PASSKEY = 2;
DISPLAY_PASSKEY_ENTRY = 3;
DISPLAY_CANCEL = 4;
- DISPLAY_PAIRING_PROMPT = 5;
- DISPLAY_PIN_ENTRY = 6;
}
message UiMsg {
@@ -65,17 +32,13 @@ message UiMsg {
enum UiCallbackType {
YES_NO = 0;
PASSKEY = 1;
- PAIRING_PROMPT = 2;
- PIN = 3;
}
message UiCallbackMsg {
UiCallbackType message_type = 1;
- facade.BluetoothAddressWithType address = 2;
- bool boolean = 3;
- uint32 numeric_value = 4;
- uint32 unique_id = 5;
- bytes pin = 6;
+ bool boolean = 2;
+ uint32 numeric_value = 3;
+ uint32 unique_id = 4;
}
enum BondMsgType {
@@ -87,93 +50,4 @@ enum BondMsgType {
message BondMsg {
BondMsgType message_type = 1;
facade.BluetoothAddressWithType peer = 2;
- uint32 reason = 3;
-}
-
-enum HelperMsgType { DEVICE_DISCONNECTED = 0; }
-
-message SecurityHelperMsg {
- HelperMsgType message_type = 1;
- facade.BluetoothAddressWithType peer = 2;
-}
-
-enum IoCapabilities {
- DISPLAY_ONLY = 0;
- DISPLAY_YES_NO_IO_CAP = 1;
- KEYBOARD_ONLY = 2;
- NO_INPUT_NO_OUTPUT = 3;
-}
-
-message IoCapabilityMessage {
- IoCapabilities capability = 1;
-}
-
-message LeIoCapabilityMessage {
- enum LeIoCapabilities {
- DISPLAY_ONLY = 0;
- DISPLAY_YES_NO_IO_CAP = 1;
- KEYBOARD_ONLY = 2;
- NO_INPUT_NO_OUTPUT = 3;
- KEYBOARD_DISPLAY = 4;
- }
- LeIoCapabilities capabilities = 1;
-}
-
-enum AuthenticationRequirements {
- NO_BONDING = 0;
- NO_BONDING_MITM_PROTECTION = 1;
- DEDICATED_BONDING = 2;
- DEDICATED_BONDING_MITM_PROTECTION = 3;
- GENERAL_BONDING = 4;
- GENERAL_BONDING_MITM_PROTECTION = 5;
-}
-
-message AuthenticationRequirementsMessage {
- AuthenticationRequirements requirement = 1;
-}
-
-message LeAuthRequirementsMessage {
- bool bond = 1;
- bool mitm = 2;
- bool secure_connections = 3;
- bool keypress = 4;
- bool ct2 = 5;
- uint32 reserved_bits = 6;
-}
-
-message LeMaximumEncryptionKeySizeMessage {
- uint32 maximum_encryption_key_size = 1;
-}
-
-message LeOobDataPresentMessage {
- enum LeOobDataFlag {
- NOT_PRESENT = 0;
- PRESENT = 1;
- }
-
- LeOobDataFlag data_present = 1;
-}
-
-enum OobDataPresent {
- NOT_PRESENT = 0;
- P192_PRESENT = 1;
- P256_PRESENT = 2;
- P192_AND_256_PRESENT = 3;
-}
-
-message OobDataPresentMessage {
- OobDataPresent data_present = 1;
-}
-
-message SecurityPolicyMessage {
- facade.BluetoothAddressWithType address = 1;
- l2cap.classic.ClassicSecurityPolicy policy = 2;
-}
-
-message EnforceSecurityPolicyMsg {
- bool result = 1;
-}
-
-message DisconnectMsg {
- facade.BluetoothAddressWithType address = 1;
}
diff --git a/gd/security/facade_configuration_api.cc b/gd/security/facade_configuration_api.cc
deleted file mode 100644
index c96f567e7..000000000
--- a/gd/security/facade_configuration_api.cc
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- *
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-#include "facade_configuration_api.h"
-
-#include "common/bind.h"
-#include "l2cap/classic/security_enforcement_interface.h"
-#include "os/log.h"
-
-namespace bluetooth {
-namespace security {
-
-void FacadeConfigurationApi::SetDisconnectCallback(internal::SecurityManagerImpl::FacadeDisconnectCallback callback) {
- security_handler_->CallOn(security_manager_impl_, &internal::SecurityManagerImpl::SetDisconnectCallback, callback);
-}
-
-void FacadeConfigurationApi::SetIoCapability(hci::IoCapability io_capability) {
- security_handler_->CallOn(security_manager_impl_, &internal::SecurityManagerImpl::SetIoCapability, io_capability);
-}
-
-void FacadeConfigurationApi::SetAuthenticationRequirements(hci::AuthenticationRequirements authentication_requirement) {
- security_handler_->CallOn(
- security_manager_impl_,
- &internal::SecurityManagerImpl::SetAuthenticationRequirements,
- authentication_requirement);
-}
-
-void FacadeConfigurationApi::SetLeIoCapability(security::IoCapability io_capability) {
- security_handler_->CallOn(security_manager_impl_, &internal::SecurityManagerImpl::SetLeIoCapability, io_capability);
-}
-
-void FacadeConfigurationApi::SetLeAuthRequirements(uint8_t auth_req) {
- security_handler_->CallOn(security_manager_impl_, &internal::SecurityManagerImpl::SetLeAuthRequirements, auth_req);
-}
-
-void FacadeConfigurationApi::SetLeMaximumEncryptionKeySize(uint8_t maximum_encryption_key_size) {
- security_handler_->CallOn(
- security_manager_impl_,
- &internal::SecurityManagerImpl::SetLeMaximumEncryptionKeySize,
- maximum_encryption_key_size);
-}
-
-void FacadeConfigurationApi::SetLeOobDataPresent(OobDataFlag oob_present) {
- security_handler_->CallOn(security_manager_impl_, &internal::SecurityManagerImpl::SetLeOobDataPresent, oob_present);
-}
-
-void FacadeConfigurationApi::GetLeOutOfBandData(
- std::array<uint8_t, 16>* confirmation_value, std::array<uint8_t, 16>* random_value) {
- security_manager_impl_->GetLeOutOfBandData(confirmation_value, random_value);
-}
-
-void FacadeConfigurationApi::SetOutOfBandData(
- hci::AddressWithType remote_address,
- std::array<uint8_t, 16> confirmation_value,
- std::array<uint8_t, 16> random_value) {
- security_handler_->CallOn(
- security_manager_impl_,
- &internal::SecurityManagerImpl::SetOutOfBandData,
- remote_address,
- confirmation_value,
- random_value);
-}
-
-void FacadeConfigurationApi::EnforceSecurityPolicy(
- hci::AddressWithType remote,
- l2cap::classic::SecurityPolicy policy,
- l2cap::classic::SecurityEnforcementInterface::ResultCallback callback) {
- security_handler_->CallOn(
- security_manager_impl_,
- &internal::SecurityManagerImpl::EnforceSecurityPolicy,
- remote,
- policy,
- std::move(callback));
-}
-
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/facade_configuration_api.h b/gd/security/facade_configuration_api.h
deleted file mode 100644
index d6bab7957..000000000
--- a/gd/security/facade_configuration_api.h
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- *
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include <memory>
-#include <vector>
-
-#include "hci/address_with_type.h"
-#include "hci/hci_packets.h"
-#include "security/internal/security_manager_impl.h"
-#include "security/smp_packets.h"
-
-namespace bluetooth {
-namespace security {
-
-/**
- * Manages the security attributes, pairing, bonding of devices, and the
- * encryption/decryption of communications.
- */
-class FacadeConfigurationApi {
- public:
- friend class internal::SecurityManagerImpl;
- friend class SecurityModule;
-
- void SetDisconnectCallback(internal::SecurityManagerImpl::FacadeDisconnectCallback callback);
- void SetIoCapability(hci::IoCapability io_capability);
- void SetAuthenticationRequirements(hci::AuthenticationRequirements authentication_requirement);
- void EnforceSecurityPolicy(
- hci::AddressWithType remote,
- l2cap::classic::SecurityPolicy policy,
- l2cap::classic::SecurityEnforcementInterface::ResultCallback callback);
-
- void SetLeIoCapability(security::IoCapability io_capability);
- void SetLeAuthRequirements(uint8_t auth_req);
- void SetLeMaximumEncryptionKeySize(uint8_t maximum_encryption_key_size);
- void SetLeOobDataPresent(OobDataFlag oob_present);
- void GetLeOutOfBandData(std::array<uint8_t, 16>* confirmation_value, std::array<uint8_t, 16>* random_value);
- void SetOutOfBandData(
- hci::AddressWithType remote_address,
- std::array<uint8_t, 16> confirmation_value,
- std::array<uint8_t, 16> random_value);
-
- protected:
- FacadeConfigurationApi(os::Handler* security_handler, internal::SecurityManagerImpl* security_manager_impl)
- : security_handler_(security_handler), security_manager_impl_(security_manager_impl) {}
-
- private:
- os::Handler* security_handler_ = nullptr;
- internal::SecurityManagerImpl* security_manager_impl_;
- DISALLOW_COPY_AND_ASSIGN(FacadeConfigurationApi);
-};
-
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/initial_informations.h b/gd/security/initial_informations.h
index c5982bd11..5721931b2 100644
--- a/gd/security/initial_informations.h
+++ b/gd/security/initial_informations.h
@@ -37,28 +37,16 @@
namespace bluetooth {
namespace security {
-struct DistributedKeys {
- /* LE Keys*/
- std::optional<crypto_toolbox::Octet16> remote_ltk;
- std::optional<uint16_t> remote_ediv;
- std::optional<std::array<uint8_t, 8>> remote_rand;
- std::optional<hci::AddressWithType> remote_identity_address;
- std::optional<crypto_toolbox::Octet16> remote_irk;
- std::optional<crypto_toolbox::Octet16> remote_signature_key;
- std::optional<crypto_toolbox::Octet16> remote_link_key; /* BR/EDR Keys */
-
- std::optional<crypto_toolbox::Octet16> local_ltk;
- std::optional<uint16_t> local_ediv;
- std::optional<std::array<uint8_t, 8>> local_rand;
- std::optional<crypto_toolbox::Octet16> local_signature_key;
-};
+using DistributedKeys =
+ std::tuple<std::optional<crypto_toolbox::Octet16> /* ltk */, std::optional<uint16_t> /*ediv*/,
+ std::optional<std::array<uint8_t, 8>> /* rand */, std::optional<Address> /* Identity address */,
+ AddrType, std::optional<crypto_toolbox::Octet16> /* IRK */,
+ std::optional<crypto_toolbox::Octet16>> /* Signature Key */;
/* This class represents the result of pairing, as returned from Pairing Handler */
struct PairingResult {
hci::AddressWithType connection_address;
DistributedKeys distributed_keys;
- uint8_t key_size;
- uint8_t security_level;
};
using PairingResultOrFailure = std::variant<PairingResult, PairingFailure>;
@@ -79,9 +67,6 @@ struct InitialInformations {
hci::Role my_role;
hci::AddressWithType my_connection_address;
- hci::AddressWithType my_identity_address;
- crypto_toolbox::Octet16 my_identity_resolving_key;
-
/* My capabilities, as in pairing request/response */
struct {
IoCapability io_capability;
diff --git a/gd/security/internal/security_manager_impl.cc b/gd/security/internal/security_manager_impl.cc
index 46d2e22cf..5ca343648 100644
--- a/gd/security/internal/security_manager_impl.cc
+++ b/gd/security/internal/security_manager_impl.cc
@@ -23,7 +23,6 @@
#include "crypto_toolbox/crypto_toolbox.h"
#include "hci/address_with_type.h"
#include "os/log.h"
-#include "os/rand.h"
#include "security/initial_informations.h"
#include "security/internal/security_manager_impl.h"
#include "security/pairing_handler_le.h"
@@ -34,123 +33,61 @@ namespace bluetooth {
namespace security {
namespace internal {
-void SecurityManagerImpl::DispatchPairingHandler(
- std::shared_ptr<record::SecurityRecord> record,
- bool locally_initiated,
- hci::IoCapability io_capability,
- hci::AuthenticationRequirements auth_requirements,
- pairing::OobData remote_p192_oob_data,
- pairing::OobData remote_p256_oob_data) {
+void SecurityManagerImpl::DispatchPairingHandler(record::SecurityRecord& record, bool locally_initiated,
+ hci::AuthenticationRequirements authentication_requirements) {
common::OnceCallback<void(hci::Address, PairingResultOrFailure)> callback =
common::BindOnce(&SecurityManagerImpl::OnPairingHandlerComplete, common::Unretained(this));
- auto entry = pairing_handler_map_.find(record->GetPseudoAddress()->GetAddress());
+ auto entry = pairing_handler_map_.find(record.GetPseudoAddress().GetAddress());
if (entry != pairing_handler_map_.end()) {
LOG_WARN("Device already has a pairing handler, and is in the middle of pairing!");
return;
}
std::shared_ptr<pairing::PairingHandler> pairing_handler = nullptr;
- switch (record->GetPseudoAddress()->GetAddressType()) {
+ switch (record.GetPseudoAddress().GetAddressType()) {
case hci::AddressType::PUBLIC_DEVICE_ADDRESS: {
+ std::shared_ptr<record::SecurityRecord> record_copy =
+ std::make_shared<record::SecurityRecord>(record.GetPseudoAddress());
pairing_handler = std::make_shared<security::pairing::ClassicPairingHandler>(
- security_manager_channel_,
- record,
- security_handler_,
- std::move(callback),
- user_interface_,
- user_interface_handler_,
- record->GetPseudoAddress()->ToString(),
- name_db_module_);
+ l2cap_classic_module_->GetFixedChannelManager(), security_manager_channel_, record_copy, security_handler_,
+ std::move(callback), user_interface_, user_interface_handler_, "TODO: grab device name properly");
break;
}
default:
- ASSERT_LOG(false, "Pairing type %hhu not implemented!", record->GetPseudoAddress()->GetAddressType());
+ ASSERT_LOG(false, "Pairing type %hhu not implemented!", record.GetPseudoAddress().GetAddressType());
}
auto new_entry = std::pair<hci::Address, std::shared_ptr<pairing::PairingHandler>>(
- record->GetPseudoAddress()->GetAddress(), pairing_handler);
+ record.GetPseudoAddress().GetAddress(), pairing_handler);
pairing_handler_map_.insert(std::move(new_entry));
- pairing_handler->Initiate(
- locally_initiated, io_capability, auth_requirements, remote_p192_oob_data, remote_p256_oob_data);
+ pairing_handler->Initiate(locally_initiated, pairing::kDefaultIoCapability, pairing::kDefaultOobDataPresent,
+ authentication_requirements);
}
void SecurityManagerImpl::Init() {
security_manager_channel_->SetChannelListener(this);
security_manager_channel_->SendCommand(hci::WriteSimplePairingModeBuilder::Create(hci::Enable::ENABLED));
security_manager_channel_->SendCommand(hci::WriteSecureConnectionsHostSupportBuilder::Create(hci::Enable::ENABLED));
-
- ASSERT_LOG(storage_module_ != nullptr, "Storage module must not be null!");
- security_database_.LoadRecordsFromStorage();
-
- storage::AdapterConfig adapter_config = storage_module_->GetAdapterConfig();
- if (!adapter_config.GetLeIdentityResolvingKey()) {
- auto mutation = storage_module_->Modify();
- mutation.Add(adapter_config.SetLeIdentityResolvingKey(bluetooth::os::GenerateRandom<16>()));
- mutation.Commit();
- }
-
- Address controllerAddress = controller_->GetMacAddress();
- if (!adapter_config.GetAddress() || adapter_config.GetAddress().value() != controllerAddress) {
- auto mutation = storage_module_->Modify();
- mutation.Add(adapter_config.SetAddress(controllerAddress));
- mutation.Commit();
- }
-
- local_identity_address_ =
- hci::AddressWithType(adapter_config.GetAddress().value(), hci::AddressType::PUBLIC_DEVICE_ADDRESS);
- local_identity_resolving_key_ = adapter_config.GetLeIdentityResolvingKey().value().bytes;
-
- hci::LeAddressManager::AddressPolicy address_policy = hci::LeAddressManager::AddressPolicy::USE_RESOLVABLE_ADDRESS;
- hci::AddressWithType address_with_type(hci::Address{}, hci::AddressType::RANDOM_DEVICE_ADDRESS);
-
- /* 7 minutes minimum, 15 minutes maximum for random address refreshing */
- auto minimum_rotation_time = std::chrono::minutes(7);
- auto maximum_rotation_time = std::chrono::minutes(15);
-
- acl_manager_->SetPrivacyPolicyForInitiatorAddress(
- address_policy, address_with_type, minimum_rotation_time, maximum_rotation_time);
+ // TODO(optedoblivion): Populate security record memory map from disk
}
void SecurityManagerImpl::CreateBond(hci::AddressWithType device) {
- this->CreateBondOutOfBand(device, pairing::OobData(), pairing::OobData());
-}
-
-void SecurityManagerImpl::CreateBondOutOfBand(
- hci::AddressWithType device, pairing::OobData remote_p192_oob_data, pairing::OobData remote_p256_oob_data) {
- auto record = security_database_.FindOrCreate(device);
- if (record->IsPaired()) {
- // Bonded means we saved it, but the caller doesn't care
- // Bonded will always mean paired
+ record::SecurityRecord& record = security_database_.FindOrCreate(device);
+ if (record.IsBonded()) {
NotifyDeviceBonded(device);
} else {
- if (!record->IsPairing()) {
- // Dispatch pairing handler, if we are calling create we are the initiator
- LOG_WARN("Dispatch #1");
- DispatchPairingHandler(
- record,
- true,
- this->local_io_capability_,
- this->local_authentication_requirements_,
- remote_p192_oob_data,
- remote_p256_oob_data);
- }
+ // Dispatch pairing handler, if we are calling create we are the initiator
+ DispatchPairingHandler(record, true, pairing::kDefaultAuthenticationRequirements);
}
}
void SecurityManagerImpl::CreateBondLe(hci::AddressWithType address) {
- auto record = security_database_.FindOrCreate(address);
- if (record->IsPaired()) {
+ record::SecurityRecord& record = security_database_.FindOrCreate(address);
+ if (record.IsBonded()) {
NotifyDeviceBondFailed(address, PairingFailure("Already bonded"));
return;
}
pending_le_pairing_.address_ = address;
- LeFixedChannelEntry* stored_chan = FindStoredLeChannel(address);
- if (stored_chan) {
- // We are already connected
- ConnectionIsReadyStartPairing(stored_chan);
- return;
- }
-
l2cap_manager_le_->ConnectServices(
address, common::BindOnce(&SecurityManagerImpl::OnConnectionFailureLe, common::Unretained(this)),
security_handler_);
@@ -163,20 +100,14 @@ void SecurityManagerImpl::CancelBond(hci::AddressWithType device) {
pairing_handler_map_.erase(entry);
cancel_me->Cancel();
}
-
- auto record = security_database_.FindOrCreate(device);
- record->CancelPairing();
-
- WipeLePairingHandler();
}
void SecurityManagerImpl::RemoveBond(hci::AddressWithType device) {
CancelBond(device);
- security_manager_channel_->Disconnect(device.GetAddress());
security_database_.Remove(device);
- security_manager_channel_->SendCommand(hci::DeleteStoredLinkKeyBuilder::Create(
- device.GetAddress(), hci::DeleteStoredLinkKeyDeleteAllFlag::SPECIFIED_BD_ADDR));
- NotifyDeviceUnbonded(device);
+ // Signal disconnect
+ // Remove security record
+ // Signal Remove from database
}
void SecurityManagerImpl::SetUserInterfaceHandler(UI* user_interface, os::Handler* handler) {
@@ -187,17 +118,6 @@ void SecurityManagerImpl::SetUserInterfaceHandler(UI* user_interface, os::Handle
user_interface_handler_ = handler;
}
-// TODO(jpawlowski): remove once we have config file abstraction in cert tests
-void SecurityManagerImpl::SetLeInitiatorAddressPolicyForTest(
- hci::LeAddressManager::AddressPolicy address_policy,
- hci::AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time) {
- acl_manager_->SetPrivacyPolicyForInitiatorAddressForTest(
- address_policy, fixed_address, rotation_irk, minimum_rotation_time, maximum_rotation_time);
-}
-
void SecurityManagerImpl::RegisterCallbackListener(ISecurityManagerListener* listener, os::Handler* handler) {
for (auto it = listeners_.begin(); it != listeners_.end(); ++it) {
if (it->first == listener) {
@@ -225,10 +145,10 @@ void SecurityManagerImpl::NotifyDeviceBonded(hci::AddressWithType device) {
}
}
-void SecurityManagerImpl::NotifyDeviceBondFailed(hci::AddressWithType device, PairingFailure status) {
+void SecurityManagerImpl::NotifyDeviceBondFailed(hci::AddressWithType device, PairingResultOrFailure status) {
for (auto& iter : listeners_) {
- iter.second->Post(
- common::Bind(&ISecurityManagerListener::OnDeviceBondFailed, common::Unretained(iter.first), device, status));
+ iter.second->Post(common::Bind(&ISecurityManagerListener::OnDeviceBondFailed, common::Unretained(iter.first),
+ device /*, status */));
}
}
@@ -237,14 +157,6 @@ void SecurityManagerImpl::NotifyDeviceUnbonded(hci::AddressWithType device) {
iter.second->Post(
common::Bind(&ISecurityManagerListener::OnDeviceUnbonded, common::Unretained(iter.first), device));
}
- acl_manager_->RemoveDeviceFromConnectList(device);
-}
-
-void SecurityManagerImpl::NotifyEncryptionStateChanged(hci::EncryptionChangeView encryption_change_view) {
- for (auto& iter : listeners_) {
- iter.second->Post(common::Bind(&ISecurityManagerListener::OnEncryptionStateChanged, common::Unretained(iter.first),
- encryption_change_view));
- }
}
template <class T>
@@ -255,33 +167,27 @@ void SecurityManagerImpl::HandleEvent(T packet) {
if (entry == pairing_handler_map_.end()) {
auto bd_addr = packet.GetBdAddr();
auto event_code = packet.GetEventCode();
+ auto event = hci::EventPacketView::Create(std::move(packet));
+ ASSERT_LOG(event.IsValid(), "Received invalid packet");
- if (event_code != hci::EventCode::LINK_KEY_REQUEST && event_code != hci::EventCode::PIN_CODE_REQUEST &&
- event_code != hci::EventCode::IO_CAPABILITY_RESPONSE) {
+ const hci::EventCode code = event.GetEventCode();
+ if (code != hci::EventCode::LINK_KEY_REQUEST) {
LOG_ERROR("No classic pairing handler for device '%s' ready for command %s ", bd_addr.ToString().c_str(),
hci::EventCodeText(event_code).c_str());
return;
}
- auto device = storage_module_->GetDeviceByClassicMacAddress(bd_addr);
-
auto record =
security_database_.FindOrCreate(hci::AddressWithType{bd_addr, hci::AddressType::PUBLIC_DEVICE_ADDRESS});
- LOG_WARN("Dispatch #2");
- DispatchPairingHandler(
- record,
- false,
- this->local_io_capability_,
- this->local_authentication_requirements_,
- pairing::OobData(),
- pairing::OobData());
+ auto authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
+ DispatchPairingHandler(record, true, authentication_requirements);
entry = pairing_handler_map_.find(bd_addr);
}
entry->second->OnReceive(packet);
}
-void SecurityManagerImpl::OnHciEventReceived(hci::EventView packet) {
- auto event = hci::EventView::Create(packet);
+void SecurityManagerImpl::OnHciEventReceived(hci::EventPacketView packet) {
+ auto event = hci::EventPacketView::Create(packet);
ASSERT_LOG(event.IsValid(), "Received invalid packet");
const hci::EventCode code = event.GetEventCode();
switch (code) {
@@ -323,16 +229,15 @@ void SecurityManagerImpl::OnHciEventReceived(hci::EventView packet) {
break;
case hci::EventCode::ENCRYPTION_CHANGE: {
- EncryptionChangeView encryption_change_view = EncryptionChangeView::Create(event);
- if (!encryption_change_view.IsValid()) {
+ EncryptionChangeView enc_chg_packet = EncryptionChangeView::Create(event);
+ if (!enc_chg_packet.IsValid()) {
LOG_ERROR("Invalid EncryptionChange packet received");
return;
}
- if (encryption_change_view.GetConnectionHandle() == pending_le_pairing_.connection_handle_) {
+ if (enc_chg_packet.GetConnectionHandle() == pending_le_pairing_.connection_handle_) {
pending_le_pairing_.handler_->OnHciEvent(event);
return;
}
- NotifyEncryptionStateChanged(encryption_change_view);
break;
}
@@ -342,44 +247,11 @@ void SecurityManagerImpl::OnHciEventReceived(hci::EventView packet) {
}
}
-void SecurityManagerImpl::OnConnectionClosed(hci::Address address) {
- auto entry = pairing_handler_map_.find(address);
- if (entry != pairing_handler_map_.end()) {
- LOG_INFO("Cancelling pairing handler for '%s'", address.ToString().c_str());
- entry->second->Cancel();
- }
- auto record = security_database_.FindOrCreate(hci::AddressWithType(address, hci::AddressType::PUBLIC_DEVICE_ADDRESS));
- if (record->IsTemporary()) {
- security_database_.Remove(hci::AddressWithType(address, hci::AddressType::PUBLIC_DEVICE_ADDRESS));
- }
- if (this->facade_disconnect_callback_) {
- this->security_handler_->Call(
- *this->facade_disconnect_callback_, hci::AddressWithType(address, hci::AddressType::PUBLIC_DEVICE_ADDRESS));
- }
-}
-
void SecurityManagerImpl::OnHciLeEvent(hci::LeMetaEventView event) {
- hci::SubeventCode code = event.GetSubeventCode();
-
- if (code == hci::SubeventCode::LONG_TERM_KEY_REQUEST) {
- hci::LeLongTermKeyRequestView le_long_term_key_request_view = hci::LeLongTermKeyRequestView::Create(event);
- if (!le_long_term_key_request_view.IsValid()) {
- LOG_ERROR("Invalid LeLongTermKeyRequestView packet received");
- return;
- }
-
- if (le_long_term_key_request_view.GetConnectionHandle() == pending_le_pairing_.connection_handle_) {
- pending_le_pairing_.handler_->OnHciLeEvent(event);
- return;
- }
-
- LOG_INFO("Unhandled HCI LE security event, code %s", hci::SubeventCodeText(code).c_str());
- return;
- }
-
+ // hci::SubeventCode::LONG_TERM_KEY_REQUEST,
// hci::SubeventCode::READ_LOCAL_P256_PUBLIC_KEY_COMPLETE,
// hci::SubeventCode::GENERATE_DHKEY_COMPLETE,
- LOG_ERROR("Unhandled HCI LE security event, code %s", hci::SubeventCodeText(code).c_str());
+ LOG_ERROR("Unhandled HCI LE security event");
}
void SecurityManagerImpl::OnPairingPromptAccepted(const bluetooth::hci::AddressWithType& address, bool confirmed) {
@@ -387,9 +259,7 @@ void SecurityManagerImpl::OnPairingPromptAccepted(const bluetooth::hci::AddressW
if (entry != pairing_handler_map_.end()) {
entry->second->OnPairingPromptAccepted(address, confirmed);
} else {
- if (pending_le_pairing_.address_ == address) {
- pending_le_pairing_.handler_->OnUiAction(PairingEvent::UI_ACTION_TYPE::PAIRING_ACCEPTED, confirmed);
- }
+ pending_le_pairing_.handler_->OnUiAction(PairingEvent::UI_ACTION_TYPE::PAIRING_ACCEPTED, confirmed);
}
}
@@ -415,36 +285,15 @@ void SecurityManagerImpl::OnPasskeyEntry(const bluetooth::hci::AddressWithType&
}
}
-void SecurityManagerImpl::OnPinEntry(const bluetooth::hci::AddressWithType& address, std::vector<uint8_t> pin) {
- auto entry = pairing_handler_map_.find(address.GetAddress());
- if (entry != pairing_handler_map_.end()) {
- LOG_INFO("PIN for %s", address.ToString().c_str());
- entry->second->OnPinEntry(address, pin);
- } else {
- LOG_WARN("No handler found for PIN for %s", address.ToString().c_str());
- // TODO(jpawlowski): Implement LE version
- }
-}
-
void SecurityManagerImpl::OnPairingHandlerComplete(hci::Address address, PairingResultOrFailure status) {
auto entry = pairing_handler_map_.find(address);
if (entry != pairing_handler_map_.end()) {
pairing_handler_map_.erase(entry);
- security_manager_channel_->Release(address);
}
- auto remote = hci::AddressWithType(address, hci::AddressType::PUBLIC_DEVICE_ADDRESS);
if (!std::holds_alternative<PairingFailure>(status)) {
- NotifyDeviceBonded(remote);
+ NotifyDeviceBonded(hci::AddressWithType(address, hci::AddressType::PUBLIC_DEVICE_ADDRESS));
} else {
- NotifyDeviceBondFailed(remote, std::get<PairingFailure>(status));
- }
- auto record = this->security_database_.FindOrCreate(remote);
- record->CancelPairing();
- security_database_.SaveRecordsToStorage();
- // Only call update link if we need to
- auto policy_callback_entry = enforce_security_policy_callback_map_.find(remote);
- if (policy_callback_entry != enforce_security_policy_callback_map_.end()) {
- UpdateLinkSecurityCondition(remote);
+ NotifyDeviceBondFailed(hci::AddressWithType(address, hci::AddressType::PUBLIC_DEVICE_ADDRESS), status);
}
}
@@ -455,177 +304,57 @@ void SecurityManagerImpl::OnL2capRegistrationCompleteLe(
"Failed to register to LE SMP Fixed Channel Service");
}
-LeFixedChannelEntry* SecurityManagerImpl::FindStoredLeChannel(const hci::AddressWithType& device) {
- for (LeFixedChannelEntry& storage : all_channels_) {
- if (storage.channel_->GetDevice() == device) {
- return &storage;
- }
- }
- return nullptr;
-}
+void SecurityManagerImpl::OnSmpCommandLe() {
+ auto packet = pending_le_pairing_.channel_->GetQueueUpEnd()->TryDequeue();
+ if (!packet) LOG_ERROR("Received dequeue, but no data ready...");
-bool SecurityManagerImpl::EraseStoredLeChannel(const hci::AddressWithType& device) {
- for (auto it = all_channels_.begin(); it != all_channels_.end(); it++) {
- if (it->channel_->GetDevice() == device) {
- all_channels_.erase(it);
- return true;
- }
- }
- return false;
-}
-
-void SecurityManagerImpl::OnSmpCommandLe(hci::AddressWithType device) {
- LeFixedChannelEntry* stored_chan = FindStoredLeChannel(device);
- if (!stored_chan) {
- LOG_ALWAYS_FATAL("Received SMP command for unknown channel");
- return;
- }
-
- std::unique_ptr<l2cap::le::FixedChannel>& channel = stored_chan->channel_;
-
- auto packet = channel->GetQueueUpEnd()->TryDequeue();
- if (!packet) {
- LOG_ERROR("Received dequeue, but no data ready...");
- return;
- }
-
- // Pending pairing - pass the data to the handler
auto temp_cmd_view = CommandView::Create(*packet);
- if (pending_le_pairing_.address_ == device) {
- pending_le_pairing_.handler_->OnCommandView(temp_cmd_view);
- return;
- }
-
- // no pending pairing attempt
- if (!temp_cmd_view.IsValid()) {
- LOG_ERROR("Invalid Command packet");
- return;
- }
-
- if (temp_cmd_view.GetCode() == Code::SECURITY_REQUEST) {
- // TODO: either start encryption or pairing
- LOG_WARN("Unhandled security request!!!");
- return;
- }
-
- auto my_role = channel->GetLinkOptions()->GetRole();
- if (temp_cmd_view.GetCode() == Code::PAIRING_REQUEST && my_role == hci::Role::PERIPHERAL) {
- // TODO: if (pending_le_pairing_) { do not start another }
-
- LOG_INFO("start of security request handling!");
-
- stored_chan->channel_->Acquire();
-
- PairingRequestView pairing_request = PairingRequestView::Create(temp_cmd_view);
- auto& enqueue_buffer = stored_chan->enqueue_buffer_;
-
- std::optional<InitialInformations::out_of_band_data> remote_oob_data = std::nullopt;
- if (remote_oob_data_address_.has_value() && remote_oob_data_address_.value() == channel->GetDevice())
- remote_oob_data = InitialInformations::out_of_band_data{.le_sc_c = remote_oob_data_le_sc_c_.value(),
- .le_sc_r = remote_oob_data_le_sc_r_.value()};
-
- // TODO: this doesn't have to be a unique ptr, if there is a way to properly std::move it into place where it's
- // stored
- pending_le_pairing_.connection_handle_ = channel->GetLinkOptions()->GetHandle();
- InitialInformations initial_informations{
- .my_role = my_role,
- .my_connection_address = channel->GetLinkOptions()->GetLocalAddress(),
- .my_identity_address = local_identity_address_,
- .my_identity_resolving_key = local_identity_resolving_key_,
- /*TODO: properly obtain capabilities from device-specific storage*/
- .myPairingCapabilities = {.io_capability = local_le_io_capability_,
- .oob_data_flag = local_le_oob_data_present_,
- .auth_req = local_le_auth_req_,
- .maximum_encryption_key_size = local_maximum_encryption_key_size_,
- .initiator_key_distribution = 0x07,
- .responder_key_distribution = 0x07},
- .remotely_initiated = true,
- .connection_handle = channel->GetLinkOptions()->GetHandle(),
- .remote_connection_address = channel->GetDevice(),
- .remote_name = "TODO: grab proper device name in sec mgr",
- /* contains pairing request, if the pairing was remotely initiated */
- .pairing_request = pairing_request,
- .remote_oob_data = remote_oob_data,
- .my_oob_data = local_le_oob_data_,
- /* Used by Pairing Handler to present user with requests*/
- .user_interface = user_interface_,
- .user_interface_handler = user_interface_handler_,
-
- /* HCI interface to use */
- .le_security_interface = hci_security_interface_le_,
- .proper_l2cap_interface = enqueue_buffer.get(),
- .l2cap_handler = security_handler_,
- /* Callback to execute once the Pairing process is finished */
- // TODO: make it an common::OnceCallback ?
- .OnPairingFinished = std::bind(&SecurityManagerImpl::OnPairingFinished, this, std::placeholders::_1),
- };
- pending_le_pairing_.address_ = device;
- pending_le_pairing_.handler_ = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, initial_informations);
- }
+ pending_le_pairing_.handler_->OnCommandView(temp_cmd_view);
}
-void SecurityManagerImpl::OnConnectionOpenLe(std::unique_ptr<l2cap::le::FixedChannel> channel_param) {
- auto enqueue_buffer_temp =
- std::make_unique<os::EnqueueBuffer<packet::BasePacketBuilder>>(channel_param->GetQueueUpEnd());
-
- all_channels_.push_back({std::move(channel_param), std::move(enqueue_buffer_temp)});
- auto& stored_channel = all_channels_.back();
- auto& channel = stored_channel.channel_;
-
- channel->RegisterOnCloseCallback(
- security_handler_,
- common::BindOnce(&SecurityManagerImpl::OnConnectionClosedLe, common::Unretained(this), channel->GetDevice()));
- channel->GetQueueUpEnd()->RegisterDequeue(
- security_handler_,
- common::Bind(&SecurityManagerImpl::OnSmpCommandLe, common::Unretained(this), channel->GetDevice()));
-
+void SecurityManagerImpl::OnConnectionOpenLe(std::unique_ptr<l2cap::le::FixedChannel> channel) {
if (pending_le_pairing_.address_ != channel->GetDevice()) {
return;
}
-
- ConnectionIsReadyStartPairing(&stored_channel);
-}
-
-void SecurityManagerImpl::ConnectionIsReadyStartPairing(LeFixedChannelEntry* stored_channel) {
- auto& channel = stored_channel->channel_;
- auto& enqueue_buffer = stored_channel->enqueue_buffer_;
-
- stored_channel->channel_->Acquire();
-
- std::optional<InitialInformations::out_of_band_data> remote_oob_data = std::nullopt;
- if (remote_oob_data_address_.has_value() && remote_oob_data_address_.value() == channel->GetDevice())
- remote_oob_data = InitialInformations::out_of_band_data{.le_sc_c = remote_oob_data_le_sc_c_.value(),
- .le_sc_r = remote_oob_data_le_sc_r_.value()};
+ pending_le_pairing_.channel_ = std::move(channel);
+ pending_le_pairing_.channel_->RegisterOnCloseCallback(
+ security_handler_, common::BindOnce(&SecurityManagerImpl::OnConnectionClosedLe, common::Unretained(this),
+ pending_le_pairing_.channel_->GetDevice()));
+ // TODO: this enqueue buffer must be stored together with pairing_handler, and we must make sure it doesn't go out of
+ // scope while the pairing happens
+ pending_le_pairing_.enqueue_buffer_ =
+ std::make_unique<os::EnqueueBuffer<packet::BasePacketBuilder>>(pending_le_pairing_.channel_->GetQueueUpEnd());
+ pending_le_pairing_.channel_->GetQueueUpEnd()->RegisterDequeue(
+ security_handler_, common::Bind(&SecurityManagerImpl::OnSmpCommandLe, common::Unretained(this)));
// TODO: this doesn't have to be a unique ptr, if there is a way to properly std::move it into place where it's stored
- pending_le_pairing_.connection_handle_ = channel->GetLinkOptions()->GetHandle();
+ pending_le_pairing_.connection_handle_ = pending_le_pairing_.channel_->GetAclConnection()->GetHandle();
InitialInformations initial_informations{
- .my_role = channel->GetLinkOptions()->GetRole(),
- .my_connection_address = channel->GetLinkOptions()->GetLocalAddress(),
- .my_identity_address = local_identity_address_,
- .my_identity_resolving_key = local_identity_resolving_key_,
+ .my_role = pending_le_pairing_.channel_->GetAclConnection()->GetRole(),
+ .my_connection_address = {hci::Address{{0x00, 0x11, 0xFF, 0xFF, 0x33, 0x22}} /*TODO: obtain my address*/,
+ hci::AddressType::RANDOM_DEVICE_ADDRESS},
/*TODO: properly obtain capabilities from device-specific storage*/
- .myPairingCapabilities = {.io_capability = local_le_io_capability_,
- .oob_data_flag = local_le_oob_data_present_,
- .auth_req = local_le_auth_req_,
- .maximum_encryption_key_size = local_maximum_encryption_key_size_,
+ .myPairingCapabilities = {.io_capability = IoCapability::KEYBOARD_DISPLAY,
+ .oob_data_flag = OobDataFlag::NOT_PRESENT,
+ .auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
+ .maximum_encryption_key_size = 16,
.initiator_key_distribution = 0x07,
.responder_key_distribution = 0x07},
.remotely_initiated = false,
- .connection_handle = channel->GetLinkOptions()->GetHandle(),
- .remote_connection_address = channel->GetDevice(),
+ .connection_handle = pending_le_pairing_.channel_->GetAclConnection()->GetHandle(),
+ .remote_connection_address = pending_le_pairing_.channel_->GetDevice(),
.remote_name = "TODO: grab proper device name in sec mgr",
/* contains pairing request, if the pairing was remotely initiated */
.pairing_request = std::nullopt, // TODO: handle remotely initiated pairing in SecurityManager properly
- .remote_oob_data = remote_oob_data,
- .my_oob_data = local_le_oob_data_,
+ .remote_oob_data = std::nullopt, // TODO:
+ .my_oob_data = std::nullopt, // TODO:
/* Used by Pairing Handler to present user with requests*/
.user_interface = user_interface_,
.user_interface_handler = user_interface_handler_,
/* HCI interface to use */
.le_security_interface = hci_security_interface_le_,
- .proper_l2cap_interface = enqueue_buffer.get(),
+ .proper_l2cap_interface = pending_le_pairing_.enqueue_buffer_.get(),
.l2cap_handler = security_handler_,
/* Callback to execute once the Pairing process is finished */
// TODO: make it an common::OnceCallback ?
@@ -636,14 +365,6 @@ void SecurityManagerImpl::ConnectionIsReadyStartPairing(LeFixedChannelEntry* sto
void SecurityManagerImpl::OnConnectionClosedLe(hci::AddressWithType address, hci::ErrorCode error_code) {
if (pending_le_pairing_.address_ != address) {
- LeFixedChannelEntry* stored_chan = FindStoredLeChannel(address);
- if (!stored_chan) {
- LOG_ALWAYS_FATAL("Received connection closed for unknown channel");
- return;
- }
- stored_chan->channel_->GetQueueUpEnd()->UnregisterDequeue();
- stored_chan->enqueue_buffer_.reset();
- EraseStoredLeChannel(address);
return;
}
pending_le_pairing_.handler_->SendExitSignal();
@@ -660,31 +381,18 @@ void SecurityManagerImpl::OnConnectionFailureLe(bluetooth::l2cap::le::FixedChann
NotifyDeviceBondFailed(pending_le_pairing_.address_, PairingFailure("Connection establishment failed"));
}
-SecurityManagerImpl::SecurityManagerImpl(
- os::Handler* security_handler,
- l2cap::le::L2capLeModule* l2cap_le_module,
- channel::SecurityManagerChannel* security_manager_channel,
- hci::HciLayer* hci_layer,
- hci::AclManager* acl_manager,
- hci::Controller* controller,
- storage::StorageModule* storage_module,
- neighbor::NameDbModule* name_db_module)
- : security_handler_(security_handler),
- l2cap_le_module_(l2cap_le_module),
- l2cap_manager_le_(l2cap_le_module_->GetFixedChannelManager()),
- hci_security_interface_le_(
- hci_layer->GetLeSecurityInterface(security_handler_->BindOn(this, &SecurityManagerImpl::OnHciLeEvent))),
- security_manager_channel_(security_manager_channel),
- acl_manager_(acl_manager),
- controller_(controller),
- storage_module_(storage_module),
- security_record_storage_(storage_module, security_handler),
- security_database_(security_record_storage_),
- name_db_module_(name_db_module) {
+SecurityManagerImpl::SecurityManagerImpl(os::Handler* security_handler, l2cap::le::L2capLeModule* l2cap_le_module,
+ l2cap::classic::L2capClassicModule* l2cap_classic_module,
+ channel::SecurityManagerChannel* security_manager_channel,
+ hci::HciLayer* hci_layer)
+ : security_handler_(security_handler), l2cap_le_module_(l2cap_le_module),
+ l2cap_classic_module_(l2cap_classic_module), l2cap_manager_le_(l2cap_le_module_->GetFixedChannelManager()),
+ hci_security_interface_le_(hci_layer->GetLeSecurityInterface(
+ common::Bind(&SecurityManagerImpl::OnHciLeEvent, common::Unretained(this)), security_handler)),
+ security_manager_channel_(security_manager_channel) {
Init();
-
l2cap_manager_le_->RegisterService(
- bluetooth::l2cap::kSmpCid,
+ bluetooth::l2cap::kSmpCid, {},
common::BindOnce(&SecurityManagerImpl::OnL2capRegistrationCompleteLe, common::Unretained(this)),
common::Bind(&SecurityManagerImpl::OnConnectionOpenLe, common::Unretained(this)), security_handler_);
}
@@ -692,197 +400,17 @@ SecurityManagerImpl::SecurityManagerImpl(
void SecurityManagerImpl::OnPairingFinished(security::PairingResultOrFailure pairing_result) {
LOG_INFO(" â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â–  Received pairing result");
- LeFixedChannelEntry* stored_chan = FindStoredLeChannel(pending_le_pairing_.address_);
- if (stored_chan) {
- stored_chan->channel_->Release();
- }
-
if (std::holds_alternative<PairingFailure>(pairing_result)) {
PairingFailure failure = std::get<PairingFailure>(pairing_result);
LOG_INFO(" â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â–  failure message: %s",
failure.message.c_str());
- NotifyDeviceBondFailed(stored_chan->channel_->GetDevice(), failure);
- return;
- }
-
- auto result = std::get<PairingResult>(pairing_result);
- LOG_INFO("Pairing with %s was successful", result.connection_address.ToString().c_str());
-
- // TODO: ensure that the security level is not weaker than what we already have.
- auto record = this->security_database_.FindOrCreate(result.connection_address);
- record->identity_address_ = result.distributed_keys.remote_identity_address;
- record->remote_ltk = result.distributed_keys.remote_ltk;
- record->key_size = result.key_size;
- record->security_level = result.security_level;
- record->remote_ediv = result.distributed_keys.remote_ediv;
- record->remote_rand = result.distributed_keys.remote_rand;
- record->remote_irk = result.distributed_keys.remote_irk;
- record->remote_signature_key = result.distributed_keys.remote_signature_key;
- if (result.distributed_keys.remote_link_key)
- record->SetLinkKey(*result.distributed_keys.remote_link_key, hci::KeyType::AUTHENTICATED_P256);
- security_database_.SaveRecordsToStorage();
-
- NotifyDeviceBonded(result.connection_address);
- // We also notify bond complete using identity address. That's what old stack used to do.
- if (result.distributed_keys.remote_identity_address)
- NotifyDeviceBonded(*result.distributed_keys.remote_identity_address);
-
- security_handler_->CallOn(this, &SecurityManagerImpl::WipeLePairingHandler);
-}
-
-void SecurityManagerImpl::WipeLePairingHandler() {
- pending_le_pairing_.handler_.reset();
- pending_le_pairing_.connection_handle_ = 0;
- pending_le_pairing_.address_ = hci::AddressWithType();
-}
-
-// Facade Configuration API functions
-void SecurityManagerImpl::SetDisconnectCallback(FacadeDisconnectCallback callback) {
- this->facade_disconnect_callback_ = std::make_optional<FacadeDisconnectCallback>(callback);
-}
-
-void SecurityManagerImpl::SetIoCapability(hci::IoCapability io_capability) {
- this->local_io_capability_ = io_capability;
-}
-
-void SecurityManagerImpl::SetLeIoCapability(security::IoCapability io_capability) {
- this->local_le_io_capability_ = io_capability;
-}
-
-void SecurityManagerImpl::SetLeAuthRequirements(uint8_t auth_req) {
- this->local_le_auth_req_ = auth_req;
-}
-
-void SecurityManagerImpl::SetLeMaximumEncryptionKeySize(uint8_t maximum_encryption_key_size) {
- this->local_maximum_encryption_key_size_ = maximum_encryption_key_size;
-}
-
-void SecurityManagerImpl::SetLeOobDataPresent(OobDataFlag data_present) {
- this->local_le_oob_data_present_ = data_present;
-}
-
-void SecurityManagerImpl::GetOutOfBandData(channel::SecurityCommandStatusCallback callback) {
- this->security_manager_channel_->SendCommand(
- hci::ReadLocalOobDataBuilder::Create(), std::forward<channel::SecurityCommandStatusCallback>(callback));
-}
-
-void SecurityManagerImpl::GetLeOutOfBandData(
- std::array<uint8_t, 16>* confirmation_value, std::array<uint8_t, 16>* random_value) {
- local_le_oob_data_ = std::make_optional<MyOobData>(PairingHandlerLe::GenerateOobData());
- *confirmation_value = local_le_oob_data_.value().c;
- *random_value = local_le_oob_data_.value().r;
-}
-
-void SecurityManagerImpl::SetOutOfBandData(
- hci::AddressWithType remote_address,
- std::array<uint8_t, 16> confirmation_value,
- std::array<uint8_t, 16> random_value) {
- remote_oob_data_address_ = remote_address;
- remote_oob_data_le_sc_c_ = confirmation_value;
- remote_oob_data_le_sc_r_ = random_value;
-}
-
-void SecurityManagerImpl::SetAuthenticationRequirements(hci::AuthenticationRequirements authentication_requirements) {
- this->local_authentication_requirements_ = authentication_requirements;
-}
-
-void SecurityManagerImpl::InternalEnforceSecurityPolicy(
- hci::AddressWithType remote,
- l2cap::classic::SecurityPolicy policy,
- l2cap::classic::SecurityEnforcementInterface::ResultCallback result_callback) {
- if (IsSecurityRequirementSatisfied(remote, policy)) {
- // Notify client immediately if already satisfied
- std::move(result_callback).Invoke(true);
return;
}
- // At this point we don't meet the security requirements; must pair
- auto record = this->security_database_.FindOrCreate(remote);
- hci::AuthenticationRequirements authentication_requirements = kDefaultAuthenticationRequirements;
- enforce_security_policy_callback_map_[remote] = {policy, std::move(result_callback)};
-
- switch (policy) {
- case l2cap::classic::SecurityPolicy::BEST:
- case l2cap::classic::SecurityPolicy::AUTHENTICATED_ENCRYPTED_TRANSPORT:
- // Force MITM requirement locally
- authentication_requirements = hci::AuthenticationRequirements::GENERAL_BONDING_MITM_PROTECTION;
- break;
- case l2cap::classic::SecurityPolicy::ENCRYPTED_TRANSPORT:
- authentication_requirements = hci::AuthenticationRequirements::GENERAL_BONDING;
- break;
- default:
- // I could hear the voice of Myles, "This should be an ASSERT!"
- ASSERT_LOG(false, "Unreachable code path");
- return;
- }
-
- LOG_WARN("Dispatch #3");
- DispatchPairingHandler(
- record,
- true,
- this->local_io_capability_,
- std::as_const(authentication_requirements),
- pairing::OobData(),
- pairing::OobData());
+ LOG_INFO("Pairing with %s was successfull",
+ std::get<PairingResult>(pairing_result).connection_address.ToString().c_str());
}
-void SecurityManagerImpl::UpdateLinkSecurityCondition(hci::AddressWithType remote) {
- auto entry = enforce_security_policy_callback_map_.find(remote);
- if (entry == enforce_security_policy_callback_map_.end()) {
- LOG_ERROR("No L2CAP security policy callback pending for %s", remote.ToString().c_str());
- return;
- }
- std::move(entry->second.callback_).Invoke(IsSecurityRequirementSatisfied(remote, entry->second.policy_));
- enforce_security_policy_callback_map_.erase(entry);
-}
-
-bool SecurityManagerImpl::IsSecurityRequirementSatisfied(
- hci::AddressWithType remote, l2cap::classic::SecurityPolicy policy) {
- auto record = security_database_.FindOrCreate(remote);
- switch (policy) {
- case l2cap::classic::SecurityPolicy::BEST:
- case l2cap::classic::SecurityPolicy::AUTHENTICATED_ENCRYPTED_TRANSPORT:
- return (record->IsPaired() && record->IsAuthenticated());
- case l2cap::classic::SecurityPolicy::ENCRYPTED_TRANSPORT:
- return record->IsPaired();
- default:
- return true;
- }
-}
-
-void SecurityManagerImpl::EnforceSecurityPolicy(
- hci::AddressWithType remote,
- l2cap::classic::SecurityPolicy policy,
- l2cap::classic::SecurityEnforcementInterface::ResultCallback result_callback) {
- LOG_INFO("Attempting to enforce security policy");
- auto record = security_database_.FindOrCreate(remote);
- if (!record->IsPairing()) {
- this->InternalEnforceSecurityPolicy(remote, policy, std::move(result_callback));
- }
-}
-
-void SecurityManagerImpl::EnforceLeSecurityPolicy(
- hci::AddressWithType remote, l2cap::le::SecurityPolicy policy,
- l2cap::le::SecurityEnforcementInterface::ResultCallback result_callback) {
- bool result = false;
- // TODO(jpawlowski): Implement for LE
- switch (policy) {
- case l2cap::le::SecurityPolicy::BEST:
- break;
- case l2cap::le::SecurityPolicy::AUTHENTICATED_ENCRYPTED_TRANSPORT:
- break;
- case l2cap::le::SecurityPolicy::ENCRYPTED_TRANSPORT:
- break;
- case l2cap::le::SecurityPolicy::NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK:
- result = true;
- break;
- case l2cap::le::SecurityPolicy::_NOT_FOR_YOU__AUTHENTICATED_PAIRING_WITH_128_BIT_KEY:
- break;
- case l2cap::le::SecurityPolicy::_NOT_FOR_YOU__AUTHORIZATION:
- break;
- }
- result_callback.Invoke(result);
-}
} // namespace internal
} // namespace security
} // namespace bluetooth
diff --git a/gd/security/internal/security_manager_impl.h b/gd/security/internal/security_manager_impl.h
index 29b423f9a..fdc601a73 100644
--- a/gd/security/internal/security_manager_impl.h
+++ b/gd/security/internal/security_manager_impl.h
@@ -16,61 +16,33 @@
#pragma once
-#include <storage/storage_module.h>
#include <unordered_map>
#include <utility>
-#include "hci/acl_manager.h"
-#include "hci/controller.h"
-#include "l2cap/classic/security_enforcement_interface.h"
+#include "hci/classic_device.h"
+#include "l2cap/classic/l2cap_classic_module.h"
#include "l2cap/le/l2cap_le_module.h"
-#include "l2cap/le/security_enforcement_interface.h"
-#include "neighbor/name_db.h"
#include "os/handler.h"
#include "security/channel/security_manager_channel.h"
#include "security/initial_informations.h"
#include "security/pairing/classic_pairing_handler.h"
-#include "security/pairing/oob_data.h"
#include "security/pairing_handler_le.h"
#include "security/record/security_record.h"
-#include "security/record/security_record_database.h"
+#include "security/security_record_database.h"
namespace bluetooth {
namespace security {
class ISecurityManagerListener;
-static constexpr hci::IoCapability kDefaultIoCapability = hci::IoCapability::DISPLAY_YES_NO;
-static constexpr hci::AuthenticationRequirements kDefaultAuthenticationRequirements =
- hci::AuthenticationRequirements::GENERAL_BONDING;
-
namespace internal {
-struct LeFixedChannelEntry {
- std::unique_ptr<l2cap::le::FixedChannel> channel_;
- std::unique_ptr<os::EnqueueBuffer<packet::BasePacketBuilder>> enqueue_buffer_;
-};
-
class SecurityManagerImpl : public channel::ISecurityManagerChannelListener, public UICallbacks {
public:
- explicit SecurityManagerImpl(
- os::Handler* security_handler,
- l2cap::le::L2capLeModule* l2cap_le_module,
- channel::SecurityManagerChannel* security_manager_channel,
- hci::HciLayer* hci_layer,
- hci::AclManager* acl_manager,
- hci::Controller* controller,
- storage::StorageModule* storage_module,
- neighbor::NameDbModule* name_db_module);
-
- ~SecurityManagerImpl() {
- /* L2CAP layer doesn't guarantee to send the registered OnCloseCallback during shutdown. Cleanup the remaining
- * queues to prevent crashes */
- for (auto& stored_chan : all_channels_) {
- stored_chan.channel_->GetQueueUpEnd()->UnregisterDequeue();
- stored_chan.enqueue_buffer_.reset();
- }
- }
+ explicit SecurityManagerImpl(os::Handler* security_handler, l2cap::le::L2capLeModule* l2cap_le_module,
+ l2cap::classic::L2capClassicModule* l2cap_classic_module,
+ channel::SecurityManagerChannel* security_manager_channel, hci::HciLayer* hci_layer);
+ ~SecurityManagerImpl() = default;
// All APIs must be invoked in SM layer handler
@@ -87,18 +59,6 @@ class SecurityManagerImpl : public channel::ISecurityManagerChannelListener, pub
void CreateBond(hci::AddressWithType address);
/**
- * Initiates bond over Classic transport with device, if not bonded yet.
- *
- * Allows for OobData to be passed in for use while pairing
- *
- * @param address device address we want to bond with
- * @param remote_p192_oob_data P192 data given to the stack
- * @param remote_p256_oob_data P256 data given to the stack
- */
- void CreateBondOutOfBand(
- hci::AddressWithType address, pairing::OobData remote_p192_oob_data, pairing::OobData remote_p256_oob_data);
-
- /**
* Initiates bond over Low Energy transport with device, if not bonded yet.
*
* @param address device address we want to bond with
@@ -132,16 +92,6 @@ class SecurityManagerImpl : public channel::ISecurityManagerChannelListener, pub
void SetUserInterfaceHandler(UI* user_interface, os::Handler* handler);
/**
- * Specify the initiator address policy used for LE transport. Can only be called once.
- */
- void SetLeInitiatorAddressPolicyForTest(
- hci::LeAddressManager::AddressPolicy address_policy,
- hci::AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time);
-
- /**
* Register to listen for callback events from SecurityManager
*
* @param listener ISecurityManagerListener instance to handle callbacks
@@ -160,14 +110,7 @@ class SecurityManagerImpl : public channel::ISecurityManagerChannelListener, pub
*
* @param packet data received from HCI
*/
- void OnHciEventReceived(hci::EventView packet) override;
-
- /**
- * When a conncetion closes we should clean up the pairing handler
- *
- * @param address Remote address
- */
- void OnConnectionClosed(hci::Address address) override;
+ void OnHciEventReceived(hci::EventPacketView packet) override;
/**
* Pairing handler has finished or cancelled
@@ -181,108 +124,47 @@ class SecurityManagerImpl : public channel::ISecurityManagerChannelListener, pub
void OnPairingPromptAccepted(const bluetooth::hci::AddressWithType& address, bool confirmed) override;
void OnConfirmYesNo(const bluetooth::hci::AddressWithType& address, bool confirmed) override;
void OnPasskeyEntry(const bluetooth::hci::AddressWithType& address, uint32_t passkey) override;
- void OnPinEntry(const bluetooth::hci::AddressWithType& address, std::vector<uint8_t> pin) override;
-
- // Facade Configuration API functions
- using FacadeDisconnectCallback = common::Callback<void(bluetooth::hci::AddressWithType)>;
- void SetDisconnectCallback(FacadeDisconnectCallback callback);
- void SetIoCapability(hci::IoCapability io_capability);
- void SetAuthenticationRequirements(hci::AuthenticationRequirements authentication_requirements);
- void GetOutOfBandData(channel::SecurityCommandStatusCallback callback);
- void SetLeIoCapability(security::IoCapability io_capability);
- void SetLeAuthRequirements(uint8_t auth_req);
- void SetLeMaximumEncryptionKeySize(uint8_t maximum_encryption_key_size);
- void SetLeOobDataPresent(OobDataFlag data_present);
- void GetLeOutOfBandData(std::array<uint8_t, 16>* confirmation_value, std::array<uint8_t, 16>* random_value);
- void SetOutOfBandData(
- hci::AddressWithType remote_address,
- std::array<uint8_t, 16> confirmation_value,
- std::array<uint8_t, 16> random_value);
- void EnforceSecurityPolicy(hci::AddressWithType remote, l2cap::classic::SecurityPolicy policy,
- l2cap::classic::SecurityEnforcementInterface::ResultCallback result_callback);
- void EnforceLeSecurityPolicy(hci::AddressWithType remote, l2cap::le::SecurityPolicy policy,
- l2cap::le::SecurityEnforcementInterface::ResultCallback result_callback);
protected:
std::vector<std::pair<ISecurityManagerListener*, os::Handler*>> listeners_;
UI* user_interface_ = nullptr;
os::Handler* user_interface_handler_ = nullptr;
void NotifyDeviceBonded(hci::AddressWithType device);
- void NotifyDeviceBondFailed(hci::AddressWithType device, PairingFailure status);
+ void NotifyDeviceBondFailed(hci::AddressWithType device, PairingResultOrFailure status);
void NotifyDeviceUnbonded(hci::AddressWithType device);
- void NotifyEncryptionStateChanged(hci::EncryptionChangeView encryption_change_view);
private:
template <class T>
void HandleEvent(T packet);
- void DispatchPairingHandler(
- std::shared_ptr<record::SecurityRecord> record,
- bool locally_initiated,
- hci::IoCapability io_capability,
- hci::AuthenticationRequirements auth_requirements,
- pairing::OobData remote_p192_oob_data_,
- pairing::OobData remote_p256_oob_data_);
+ void DispatchPairingHandler(record::SecurityRecord& record, bool locally_initiated,
+ hci::AuthenticationRequirements authentication_requirements);
void OnL2capRegistrationCompleteLe(l2cap::le::FixedChannelManager::RegistrationResult result,
std::unique_ptr<l2cap::le::FixedChannelService> le_smp_service);
- void OnSmpCommandLe(hci::AddressWithType device);
+ void OnSmpCommandLe();
void OnConnectionOpenLe(std::unique_ptr<l2cap::le::FixedChannel> channel);
void OnConnectionClosedLe(hci::AddressWithType address, hci::ErrorCode error_code);
void OnConnectionFailureLe(bluetooth::l2cap::le::FixedChannelManager::ConnectionResult result);
void OnPairingFinished(bluetooth::security::PairingResultOrFailure pairing_result);
void OnHciLeEvent(hci::LeMetaEventView event);
- LeFixedChannelEntry* FindStoredLeChannel(const hci::AddressWithType& device);
- LeFixedChannelEntry* FindStoredLeChannel(uint8_t connection_handle);
- bool EraseStoredLeChannel(const hci::AddressWithType& device);
- void InternalEnforceSecurityPolicy(
- hci::AddressWithType remote,
- l2cap::classic::SecurityPolicy policy,
- l2cap::classic::SecurityEnforcementInterface::ResultCallback result_callback);
- void UpdateLinkSecurityCondition(hci::AddressWithType remote);
- bool IsSecurityRequirementSatisfied(hci::AddressWithType remote, l2cap::classic::SecurityPolicy policy);
- void ConnectionIsReadyStartPairing(LeFixedChannelEntry* stored_channel);
- void WipeLePairingHandler();
os::Handler* security_handler_ __attribute__((unused));
l2cap::le::L2capLeModule* l2cap_le_module_ __attribute__((unused));
+ l2cap::classic::L2capClassicModule* l2cap_classic_module_ __attribute__((unused));
std::unique_ptr<l2cap::le::FixedChannelManager> l2cap_manager_le_;
hci::LeSecurityInterface* hci_security_interface_le_ __attribute__((unused));
channel::SecurityManagerChannel* security_manager_channel_;
- hci::AclManager* acl_manager_;
- hci::Controller* controller_;
- storage::StorageModule* storage_module_ __attribute__((unused));
- record::SecurityRecordStorage security_record_storage_;
- record::SecurityRecordDatabase security_database_;
- neighbor::NameDbModule* name_db_module_;
+ SecurityRecordDatabase security_database_;
std::unordered_map<hci::Address, std::shared_ptr<pairing::PairingHandler>> pairing_handler_map_;
- hci::IoCapability local_io_capability_ = kDefaultIoCapability;
- hci::AuthenticationRequirements local_authentication_requirements_ = kDefaultAuthenticationRequirements;
- security::IoCapability local_le_io_capability_ = security::IoCapability::KEYBOARD_DISPLAY;
- uint8_t local_le_auth_req_ = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc;
- uint8_t local_maximum_encryption_key_size_ = 0x10;
- OobDataFlag local_le_oob_data_present_ = OobDataFlag::NOT_PRESENT;
- std::optional<MyOobData> local_le_oob_data_;
- std::optional<hci::AddressWithType> remote_oob_data_address_;
- std::optional<crypto_toolbox::Octet16> remote_oob_data_le_sc_c_;
- std::optional<crypto_toolbox::Octet16> remote_oob_data_le_sc_r_;
- std::optional<FacadeDisconnectCallback> facade_disconnect_callback_;
- hci::AddressWithType local_identity_address_;
- crypto_toolbox::Octet16 local_identity_resolving_key_;
-
- struct PendingSecurityEnforcementEntry {
- l2cap::classic::SecurityPolicy policy_;
- l2cap::classic::SecurityEnforcementInterface::ResultCallback callback_;
- };
- std::unordered_map<hci::AddressWithType, PendingSecurityEnforcementEntry> enforce_security_policy_callback_map_;
struct {
hci::AddressWithType address_;
- uint16_t connection_handle_;
+ std::unique_ptr<l2cap::le::FixedChannel> channel_;
+ uint8_t connection_handle_;
std::unique_ptr<PairingHandlerLe> handler_;
+ std::unique_ptr<os::EnqueueBuffer<packet::BasePacketBuilder>> enqueue_buffer_;
} pending_le_pairing_;
-
- std::list<LeFixedChannelEntry> all_channels_;
};
} // namespace internal
} // namespace security
diff --git a/gd/security/l2cap_security_module_interface.cc b/gd/security/l2cap_security_module_interface.cc
deleted file mode 100644
index 939d06b5f..000000000
--- a/gd/security/l2cap_security_module_interface.cc
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#include "security/l2cap_security_module_interface.h"
-#include "common/bind.h"
-
-namespace bluetooth {
-namespace security {
-
-L2capSecurityModuleInterface::L2capSecurityModuleInterface(internal::SecurityManagerImpl* security_manager_impl,
- os::Handler* security_handler)
- : security_manager_impl_(security_manager_impl), security_handler_(security_handler) {}
-
-void L2capSecurityModuleInterface::Enforce(
- hci::AddressWithType remote, l2cap::classic::SecurityPolicy policy,
- l2cap::classic::SecurityEnforcementInterface::ResultCallback result_callback) {
- this->security_handler_->Post(common::BindOnce(
- &internal::SecurityManagerImpl::EnforceSecurityPolicy, common::Unretained(security_manager_impl_),
- std::forward<hci::AddressWithType>(remote), std::forward<l2cap::classic::SecurityPolicy>(policy),
- std::forward<l2cap::classic::SecurityEnforcementInterface::ResultCallback>(result_callback)));
-}
-
-void L2capSecurityModuleInterface::Enforce(hci::AddressWithType remote, l2cap::le::SecurityPolicy policy,
- l2cap::le::SecurityEnforcementInterface::ResultCallback result_callback) {
- this->security_handler_->Post(common::BindOnce(
- &internal::SecurityManagerImpl::EnforceLeSecurityPolicy, common::Unretained(security_manager_impl_),
- std::forward<hci::AddressWithType>(remote), std::forward<l2cap::le::SecurityPolicy>(policy),
- std::forward<l2cap::le::SecurityEnforcementInterface::ResultCallback>(result_callback)));
-}
-
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/l2cap_security_module_interface.h b/gd/security/l2cap_security_module_interface.h
deleted file mode 100644
index 9a8fc8e97..000000000
--- a/gd/security/l2cap_security_module_interface.h
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include "l2cap/classic/security_enforcement_interface.h"
-#include "l2cap/le/security_enforcement_interface.h"
-#include "os/handler.h"
-#include "security/internal/security_manager_impl.h"
-
-namespace bluetooth {
-namespace security {
-class L2capSecurityModuleInterface : public l2cap::classic::SecurityEnforcementInterface,
- public l2cap::le::SecurityEnforcementInterface {
- public:
- L2capSecurityModuleInterface(internal::SecurityManagerImpl* security_manager_impl, os::Handler* security_handler);
- void Enforce(hci::AddressWithType remote, l2cap::classic::SecurityPolicy policy,
- l2cap::classic::SecurityEnforcementInterface::ResultCallback result_callback) override;
- void Enforce(hci::AddressWithType remote, l2cap::le::SecurityPolicy policy,
- l2cap::le::SecurityEnforcementInterface::ResultCallback result_callback) override;
-
- private:
- internal::SecurityManagerImpl* security_manager_impl_;
- os::Handler* security_handler_ = nullptr;
-};
-
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/pairing/Android.bp b/gd/security/pairing/Android.bp
index ad5f32b7e..350c10efc 100644
--- a/gd/security/pairing/Android.bp
+++ b/gd/security/pairing/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothSecurityPairingSources",
srcs: [
diff --git a/gd/security/pairing/classic_pairing_handler.cc b/gd/security/pairing/classic_pairing_handler.cc
index 252a29359..93c0865c2 100644
--- a/gd/security/pairing/classic_pairing_handler.cc
+++ b/gd/security/pairing/classic_pairing_handler.cc
@@ -18,149 +18,117 @@
#include "security/pairing/classic_pairing_handler.h"
#include "common/bind.h"
-#include "neighbor/name.h"
namespace bluetooth {
namespace security {
namespace pairing {
void ClassicPairingHandler::NotifyUiDisplayYesNo(uint32_t numeric_value) {
- ASSERT(user_interface_handler_ != nullptr);
- ConfirmationData data(*GetRecord()->GetPseudoAddress(), device_name_, numeric_value);
- data.SetRemoteIoCaps(remote_io_capability_);
- data.SetRemoteAuthReqs(remote_authentication_requirements_);
- data.SetRemoteOobDataPresent(remote_oob_present_);
- user_interface_handler_->CallOn(user_interface_, &UI::DisplayConfirmValue, data);
+ user_interface_handler_->Post(common::BindOnce(&UI::DisplayConfirmValue, common::Unretained(user_interface_),
+ GetRecord()->GetPseudoAddress(), device_name_, numeric_value));
}
void ClassicPairingHandler::NotifyUiDisplayYesNo() {
- ASSERT(user_interface_handler_ != nullptr);
- ConfirmationData data(*GetRecord()->GetPseudoAddress(), device_name_);
- data.SetRemoteIoCaps(remote_io_capability_);
- data.SetRemoteAuthReqs(remote_authentication_requirements_);
- data.SetRemoteOobDataPresent(remote_oob_present_);
- user_interface_handler_->CallOn(user_interface_, &UI::DisplayYesNoDialog, data);
+ user_interface_handler_->Post(common::BindOnce(&UI::DisplayYesNoDialog, common::Unretained(user_interface_),
+ GetRecord()->GetPseudoAddress(), device_name_));
}
void ClassicPairingHandler::NotifyUiDisplayPasskey(uint32_t passkey) {
- ASSERT(user_interface_handler_ != nullptr);
- ConfirmationData data(*GetRecord()->GetPseudoAddress(), device_name_, passkey);
- data.SetRemoteIoCaps(remote_io_capability_);
- data.SetRemoteAuthReqs(remote_authentication_requirements_);
- data.SetRemoteOobDataPresent(remote_oob_present_);
- user_interface_handler_->CallOn(user_interface_, &UI::DisplayPasskey, data);
+ user_interface_handler_->Post(common::BindOnce(&UI::DisplayPasskey, common::Unretained(user_interface_),
+ GetRecord()->GetPseudoAddress(), device_name_, passkey));
}
void ClassicPairingHandler::NotifyUiDisplayPasskeyInput() {
- ASSERT(user_interface_handler_ != nullptr);
- ConfirmationData data(*GetRecord()->GetPseudoAddress(), device_name_);
- data.SetRemoteIoCaps(remote_io_capability_);
- data.SetRemoteAuthReqs(remote_authentication_requirements_);
- data.SetRemoteOobDataPresent(remote_oob_present_);
- user_interface_handler_->CallOn(user_interface_, &UI::DisplayEnterPasskeyDialog, data);
+ user_interface_handler_->Post(common::BindOnce(&UI::DisplayEnterPasskeyDialog, common::Unretained(user_interface_),
+ GetRecord()->GetPseudoAddress(), device_name_));
}
-void ClassicPairingHandler::NotifyUiDisplayPinCodeInput() {
- ASSERT(user_interface_handler_ != nullptr);
- ConfirmationData data(*GetRecord()->GetPseudoAddress(), device_name_);
- data.SetRemoteIoCaps(remote_io_capability_);
- data.SetRemoteAuthReqs(remote_authentication_requirements_);
- data.SetRemoteOobDataPresent(remote_oob_present_);
- user_interface_handler_->CallOn(user_interface_, &UI::DisplayEnterPinDialog, data);
+void ClassicPairingHandler::NotifyUiDisplayCancel() {
+ user_interface_handler_->Post(
+ common::BindOnce(&UI::Cancel, common::Unretained(user_interface_), GetRecord()->GetPseudoAddress()));
}
-void ClassicPairingHandler::NotifyUiDisplayCancel() {
- ASSERT(user_interface_handler_ != nullptr);
- user_interface_handler_->CallOn(user_interface_, &UI::Cancel, *GetRecord()->GetPseudoAddress());
+void ClassicPairingHandler::OnRegistrationComplete(
+ l2cap::classic::FixedChannelManager::RegistrationResult result,
+ std::unique_ptr<l2cap::classic::FixedChannelService> fixed_channel_service) {
+ if (result != l2cap::classic::FixedChannelManager::RegistrationResult::SUCCESS) {
+ LOG_ERROR("Failed service registration!");
+ return;
+ }
+ fixed_channel_service_ = std::move(fixed_channel_service);
+ fixed_channel_manager_->ConnectServices(
+ GetRecord()->GetPseudoAddress().GetAddress(),
+ common::Bind(&ClassicPairingHandler::OnConnectionFail, common::Unretained(this)), security_handler_);
+}
+
+void ClassicPairingHandler::OnUnregistered() {
+ PairingResultOrFailure result = PairingResult();
+ if (last_status_ != hci::ErrorCode::SUCCESS) {
+ result = PairingFailure(hci::ErrorCodeText(last_status_));
+ }
+ std::move(complete_callback_).Run(GetRecord()->GetPseudoAddress().GetAddress(), result);
+}
+
+void ClassicPairingHandler::OnConnectionOpen(std::unique_ptr<l2cap::classic::FixedChannel> fixed_channel) {
+ ASSERT(fixed_channel_ == nullptr);
+ fixed_channel_ = std::move(fixed_channel);
+ ASSERT(fixed_channel_->GetDevice() == GetRecord()->GetPseudoAddress().GetAddress());
+ fixed_channel_->RegisterOnCloseCallback(
+ security_handler_, common::BindOnce(&ClassicPairingHandler::OnConnectionClose, common::Unretained(this)));
+ fixed_channel_->Acquire();
+}
+
+void ClassicPairingHandler::OnConnectionFail(l2cap::classic::FixedChannelManager::ConnectionResult result) {
+ Cancel();
+}
+
+void ClassicPairingHandler::OnConnectionClose(hci::ErrorCode error_code) {
+ // Called when the connection gets closed
+ LOG_ERROR("Connection closed due to: %s", hci::ErrorCodeText(error_code).c_str());
+ ASSERT(fixed_channel_ != nullptr);
+ fixed_channel_.reset();
+ Cancel();
}
void ClassicPairingHandler::OnPairingPromptAccepted(const bluetooth::hci::AddressWithType& address, bool confirmed) {
- // NOTE: This is not used by Classic, only by LE
- LOG_ALWAYS_FATAL("This is not supported by Classic Pairing Handler, only LE");
+ LOG_WARN("TODO Not Implemented!");
}
void ClassicPairingHandler::OnConfirmYesNo(const bluetooth::hci::AddressWithType& address, bool confirmed) {
- if (confirmed) {
- GetChannel()->SendCommand(
- hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
- } else {
- GetChannel()->SendCommand(
- hci::UserConfirmationRequestNegativeReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
- }
+ LOG_WARN("TODO Not Implemented!");
+ GetChannel()->SendCommand(
+ hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress()));
}
void ClassicPairingHandler::OnPasskeyEntry(const bluetooth::hci::AddressWithType& address, uint32_t passkey) {
- GetChannel()->SendCommand(hci::UserPasskeyRequestReplyBuilder::Create(address.GetAddress(), passkey));
-}
-
-void ClassicPairingHandler::OnPinEntry(const bluetooth::hci::AddressWithType& address, std::vector<uint8_t> pin) {
- std::array<uint8_t, 16> padded_pin;
- for (size_t i = 0; i < 16 && i < pin.size(); i++) {
- padded_pin[i] = pin[i];
- }
- LOG_INFO("%s", address.GetAddress().ToString().c_str());
- GetChannel()->SendCommand(hci::PinCodeRequestReplyBuilder::Create(address.GetAddress(), pin.size(), padded_pin));
+ LOG_WARN("TODO Not Implemented!");
}
-void ClassicPairingHandler::Initiate(
- bool locally_initiated,
- hci::IoCapability io_capability,
- hci::AuthenticationRequirements auth_requirements,
- OobData remote_p192_oob_data,
- OobData remote_p256_oob_data) {
- LOG_INFO("Initiate");
+void ClassicPairingHandler::Initiate(bool locally_initiated, hci::IoCapability io_capability,
+ hci::OobDataPresent oob_present,
+ hci::AuthenticationRequirements auth_requirements) {
locally_initiated_ = locally_initiated;
local_io_capability_ = io_capability;
+ local_oob_present_ = oob_present;
local_authentication_requirements_ = auth_requirements;
- remote_p192_oob_data_ = remote_p192_oob_data;
- remote_p256_oob_data_ = remote_p256_oob_data;
- bool has192 = remote_p192_oob_data.IsValid();
- bool has256 = remote_p256_oob_data.IsValid();
- bool has_both = has192 && has256;
-
- if (has_both) {
- remote_oob_present_ = hci::OobDataPresent::P_192_AND_256_PRESENT;
- } else {
- if (has192) {
- remote_oob_present_ = hci::OobDataPresent::P_192_PRESENT;
- } else if (has256) {
- remote_oob_present_ = hci::OobDataPresent::P_256_PRESENT;
- }
- }
- if (locally_initiated_) {
- GetChannel()->Connect(GetRecord()->GetPseudoAddress()->GetAddress());
- }
-}
+ // TODO(optedoblivion): Read OOB data
+ // if host and controller support secure connections used HCIREADLOCALOOBEXTENDEDDATA vs HCIREADLOCALOOBDATA
-void ClassicPairingHandler::OnNameRequestComplete(hci::Address address, bool success) {
- if (GetNameDbModule()->IsNameCached(address)) {
- auto remote_name = GetNameDbModule()->ReadCachedRemoteName(address);
- std::string tmp_name;
- for (uint8_t i : remote_name) {
- tmp_name += i;
- }
- device_name_ = tmp_name;
- }
- has_gotten_name_response_ = true;
- // For SSP/Numeric comparison flow
- if (user_confirmation_request_) {
- this->OnReceive(*user_confirmation_request_);
- }
- // For OOB Flow; we go to link key notification and must wait for name
- if (link_key_notification_) {
- this->OnReceive(*link_key_notification_);
- }
+ fixed_channel_manager_->RegisterService(
+ l2cap::kClassicPairingTriggerCid, security_policy_,
+ common::Bind(&ClassicPairingHandler::OnRegistrationComplete, common::Unretained(this)),
+ common::Bind(&ClassicPairingHandler::OnConnectionOpen, common::Unretained(this)), security_handler_);
}
void ClassicPairingHandler::Cancel() {
- if (is_cancelled_) return;
- is_cancelled_ = true;
- PairingResultOrFailure result = PairingResult();
- if (last_status_ != hci::ErrorCode::SUCCESS) {
- result = PairingFailure(hci::ErrorCodeText(last_status_));
+ if (fixed_channel_ != nullptr) {
+ fixed_channel_->Release();
+ }
+ if (fixed_channel_service_ != nullptr) {
+ fixed_channel_service_->Unregister(common::Bind(&ClassicPairingHandler::OnUnregistered, common::Unretained(this)),
+ security_handler_);
}
- std::move(complete_callback_).Run(GetRecord()->GetPseudoAddress()->GetAddress(), result);
}
void ClassicPairingHandler::OnReceive(hci::ChangeConnectionLinkKeyCompleteView packet) {
@@ -168,7 +136,7 @@ void ClassicPairingHandler::OnReceive(hci::ChangeConnectionLinkKeyCompleteView p
LOG_INFO("Received unsupported event: %s", hci::EventCodeText(packet.GetEventCode()).c_str());
}
-void ClassicPairingHandler::OnReceive(hci::CentralLinkKeyCompleteView packet) {
+void ClassicPairingHandler::OnReceive(hci::MasterLinkKeyCompleteView packet) {
ASSERT(packet.IsValid());
LOG_INFO("Received unsupported event: %s", hci::EventCodeText(packet.GetEventCode()).c_str());
}
@@ -176,137 +144,60 @@ void ClassicPairingHandler::OnReceive(hci::CentralLinkKeyCompleteView packet) {
void ClassicPairingHandler::OnReceive(hci::PinCodeRequestView packet) {
ASSERT(packet.IsValid());
LOG_INFO("Received: %s", hci::EventCodeText(packet.GetEventCode()).c_str());
- ASSERT_LOG(GetRecord()->GetPseudoAddress()->GetAddress() == packet.GetBdAddr(), "Address mismatch");
- is_legacy_pin_code_ = true;
- NotifyUiDisplayPinCodeInput();
+ ASSERT_LOG(GetRecord()->GetPseudoAddress().GetAddress() == packet.GetBdAddr(), "Address mismatch");
}
void ClassicPairingHandler::OnReceive(hci::LinkKeyRequestView packet) {
ASSERT(packet.IsValid());
- if (already_link_key_replied_) {
- LOG_WARN("Pairing is already in progress...");
- return;
- }
- already_link_key_replied_ = true;
+ // TODO(optedoblivion): Add collision detection here
LOG_INFO("Received: %s", hci::EventCodeText(packet.GetEventCode()).c_str());
- ASSERT_LOG(GetRecord()->GetPseudoAddress()->GetAddress() == packet.GetBdAddr(), "Address mismatch");
- if (GetRecord()->IsPaired()) {
- LOG_INFO("Sending: LINK_KEY_REQUEST_REPLY");
- this->GetChannel()->SendCommand(hci::LinkKeyRequestReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress(), GetRecord()->GetLinkKey()));
- last_status_ = hci::ErrorCode::SUCCESS;
- Cancel();
+ ASSERT_LOG(GetRecord()->GetPseudoAddress().GetAddress() == packet.GetBdAddr(), "Address mismatch");
+ if (GetRecord()->IsBonded() || GetRecord()->IsPaired()) {
+ auto packet = hci::LinkKeyRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress(),
+ GetRecord()->GetLinkKey());
+ this->GetChannel()->SendCommand(std::move(packet));
} else {
- LOG_INFO("Sending: LINK_KEY_REQUEST_NEGATIVE_REPLY");
- this->GetChannel()->SendCommand(
- hci::LinkKeyRequestNegativeReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
+ auto packet = hci::LinkKeyRequestNegativeReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress());
+ this->GetChannel()->SendCommand(std::move(packet));
}
}
void ClassicPairingHandler::OnReceive(hci::LinkKeyNotificationView packet) {
ASSERT(packet.IsValid());
LOG_INFO("Received: %s", hci::EventCodeText(packet.GetEventCode()).c_str());
- ASSERT_LOG(GetRecord()->GetPseudoAddress()->GetAddress() == packet.GetBdAddr(), "Address mismatch");
+ ASSERT_LOG(GetRecord()->GetPseudoAddress().GetAddress() == packet.GetBdAddr(), "Address mismatch");
GetRecord()->SetLinkKey(packet.GetLinkKey(), packet.GetKeyType());
- if (!has_gotten_name_response_) {
- link_key_notification_ = std::make_optional<hci::LinkKeyNotificationView>(packet);
- return;
- }
- if (is_legacy_pin_code_) {
- last_status_ = hci::ErrorCode::SUCCESS;
- }
Cancel();
}
void ClassicPairingHandler::OnReceive(hci::IoCapabilityRequestView packet) {
ASSERT(packet.IsValid());
LOG_INFO("Received: %s", hci::EventCodeText(packet.GetEventCode()).c_str());
- ASSERT_LOG(GetRecord()->GetPseudoAddress()->GetAddress() == packet.GetBdAddr(), "Address mismatch");
+ ASSERT_LOG(GetRecord()->GetPseudoAddress().GetAddress() == packet.GetBdAddr(), "Address mismatch");
hci::IoCapability io_capability = local_io_capability_;
- hci::OobDataPresent oob_present = remote_oob_present_;
+ hci::OobDataPresent oob_present = hci::OobDataPresent::NOT_PRESENT;
hci::AuthenticationRequirements authentication_requirements = local_authentication_requirements_;
auto reply_packet = hci::IoCapabilityRequestReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress(), io_capability, oob_present, authentication_requirements);
+ GetRecord()->GetPseudoAddress().GetAddress(), io_capability, oob_present, authentication_requirements);
this->GetChannel()->SendCommand(std::move(reply_packet));
- GetNameDbModule()->ReadRemoteNameRequest(
- GetRecord()->GetPseudoAddress()->GetAddress(),
- common::BindOnce(&ClassicPairingHandler::OnNameRequestComplete, common::Unretained(this)),
- security_handler_);
}
void ClassicPairingHandler::OnReceive(hci::IoCapabilityResponseView packet) {
ASSERT(packet.IsValid());
LOG_INFO("Received: %s", hci::EventCodeText(packet.GetEventCode()).c_str());
- ASSERT_LOG(GetRecord()->GetPseudoAddress()->GetAddress() == packet.GetBdAddr(), "Address mismatch");
+ ASSERT_LOG(GetRecord()->GetPseudoAddress().GetAddress() == packet.GetBdAddr(), "Address mismatch");
+ // Using local variable until device database pointer is ready
remote_io_capability_ = packet.GetIoCapability();
- remote_authentication_requirements_ = packet.GetAuthenticationRequirements();
-
- switch (remote_authentication_requirements_) {
- case hci::AuthenticationRequirements::NO_BONDING:
- GetRecord()->SetIsEncryptionRequired(
- local_authentication_requirements_ != hci::AuthenticationRequirements::NO_BONDING ||
- local_authentication_requirements_ != hci::AuthenticationRequirements::NO_BONDING_MITM_PROTECTION);
- GetRecord()->SetRequiresMitmProtection(
- local_authentication_requirements_ == hci::AuthenticationRequirements::DEDICATED_BONDING_MITM_PROTECTION ||
- local_authentication_requirements_ == hci::AuthenticationRequirements::GENERAL_BONDING_MITM_PROTECTION ||
- local_authentication_requirements_ == hci::AuthenticationRequirements::NO_BONDING_MITM_PROTECTION);
- // TODO(optedoblivion): check for HID device (CoD) and if HID don't make temporary
- GetRecord()->SetIsTemporary(
- local_authentication_requirements_ == hci::AuthenticationRequirements::NO_BONDING ||
- local_authentication_requirements_ == hci::AuthenticationRequirements::NO_BONDING_MITM_PROTECTION);
- break;
- case hci::AuthenticationRequirements::NO_BONDING_MITM_PROTECTION:
- GetRecord()->SetIsEncryptionRequired(
- local_authentication_requirements_ != hci::AuthenticationRequirements::NO_BONDING ||
- local_authentication_requirements_ != hci::AuthenticationRequirements::NO_BONDING_MITM_PROTECTION);
- GetRecord()->SetRequiresMitmProtection(true);
- GetRecord()->SetIsTemporary(
- local_authentication_requirements_ == hci::AuthenticationRequirements::NO_BONDING ||
- local_authentication_requirements_ == hci::AuthenticationRequirements::NO_BONDING_MITM_PROTECTION);
- break;
- case hci::AuthenticationRequirements::DEDICATED_BONDING:
- GetRecord()->SetIsEncryptionRequired(true);
- GetRecord()->SetRequiresMitmProtection(
- local_authentication_requirements_ == hci::AuthenticationRequirements::DEDICATED_BONDING_MITM_PROTECTION ||
- local_authentication_requirements_ == hci::AuthenticationRequirements::GENERAL_BONDING_MITM_PROTECTION ||
- local_authentication_requirements_ == hci::AuthenticationRequirements::NO_BONDING_MITM_PROTECTION);
- break;
- case hci::AuthenticationRequirements::DEDICATED_BONDING_MITM_PROTECTION:
- GetRecord()->SetIsEncryptionRequired(true);
- GetRecord()->SetRequiresMitmProtection(true);
- break;
- case hci::AuthenticationRequirements::GENERAL_BONDING:
- GetRecord()->SetIsEncryptionRequired(true);
- GetRecord()->SetRequiresMitmProtection(
- local_authentication_requirements_ == hci::AuthenticationRequirements::DEDICATED_BONDING_MITM_PROTECTION ||
- local_authentication_requirements_ == hci::AuthenticationRequirements::GENERAL_BONDING_MITM_PROTECTION ||
- local_authentication_requirements_ == hci::AuthenticationRequirements::NO_BONDING_MITM_PROTECTION);
- break;
- case hci::AuthenticationRequirements::GENERAL_BONDING_MITM_PROTECTION:
- GetRecord()->SetIsEncryptionRequired(true);
- GetRecord()->SetRequiresMitmProtection(true);
- break;
- default:
- GetRecord()->SetIsEncryptionRequired(true);
- GetRecord()->SetRequiresMitmProtection(true);
- break;
- }
-
- has_gotten_io_cap_response_ = true;
- if (user_confirmation_request_) {
- this->OnReceive(*user_confirmation_request_);
- }
}
void ClassicPairingHandler::OnReceive(hci::SimplePairingCompleteView packet) {
ASSERT(packet.IsValid());
LOG_INFO("Received: %s", hci::EventCodeText(packet.GetEventCode()).c_str());
- ASSERT_LOG(GetRecord()->GetPseudoAddress()->GetAddress() == packet.GetBdAddr(), "Address mismatch");
+ ASSERT_LOG(GetRecord()->GetPseudoAddress().GetAddress() == packet.GetBdAddr(), "Address mismatch");
last_status_ = packet.GetStatus();
if (last_status_ != hci::ErrorCode::SUCCESS) {
LOG_INFO("Failed SimplePairingComplete: %s", hci::ErrorCodeText(last_status_).c_str());
- // Cancel here since we won't get LinkKeyNotification
Cancel();
}
}
@@ -329,59 +220,13 @@ void ClassicPairingHandler::OnReceive(hci::EncryptionKeyRefreshCompleteView pack
void ClassicPairingHandler::OnReceive(hci::RemoteOobDataRequestView packet) {
ASSERT(packet.IsValid());
LOG_INFO("Received: %s", hci::EventCodeText(packet.GetEventCode()).c_str());
- ASSERT_LOG(GetRecord()->GetPseudoAddress()->GetAddress() == packet.GetBdAddr(), "Address mismatch");
-
- // Corev5.2 V2PF
- switch (remote_oob_present_) {
- case hci::OobDataPresent::NOT_PRESENT:
- LOG_WARN("Missing remote OOB data");
- GetChannel()->SendCommand(
- hci::RemoteOobDataRequestNegativeReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
- break;
- case hci::OobDataPresent::P_192_PRESENT:
- LOG_INFO("P192 Present");
- // TODO(optedoblivion): Figure this out and remove
- secure_connections_enabled_ = false;
- if (secure_connections_enabled_) {
- GetChannel()->SendCommand(hci::RemoteOobExtendedDataRequestReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress(),
- this->remote_p192_oob_data_.GetC(),
- this->remote_p192_oob_data_.GetR(),
- this->remote_p256_oob_data_.GetC(),
- this->remote_p256_oob_data_.GetR()));
- } else {
- GetChannel()->SendCommand(hci::RemoteOobDataRequestReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress(),
- this->remote_p192_oob_data_.GetC(),
- this->remote_p192_oob_data_.GetR()));
- }
- break;
- case hci::OobDataPresent::P_256_PRESENT:
- LOG_INFO("P256 Present");
- GetChannel()->SendCommand(hci::RemoteOobExtendedDataRequestReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress(),
- this->remote_p192_oob_data_.GetC(),
- this->remote_p192_oob_data_.GetR(),
- this->remote_p256_oob_data_.GetC(),
- this->remote_p256_oob_data_.GetR()));
- break;
- case hci::OobDataPresent::P_192_AND_256_PRESENT:
- LOG_INFO("P192 and P256 Present");
- GetChannel()->SendCommand(hci::RemoteOobExtendedDataRequestReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress(),
- this->remote_p192_oob_data_.GetC(),
- this->remote_p192_oob_data_.GetR(),
- this->remote_p256_oob_data_.GetC(),
- this->remote_p256_oob_data_.GetR()));
- break;
- }
+ ASSERT_LOG(GetRecord()->GetPseudoAddress().GetAddress() == packet.GetBdAddr(), "Address mismatch");
}
void ClassicPairingHandler::OnReceive(hci::UserPasskeyNotificationView packet) {
ASSERT(packet.IsValid());
LOG_INFO("Received: %s", hci::EventCodeText(packet.GetEventCode()).c_str());
- ASSERT_LOG(GetRecord()->GetPseudoAddress()->GetAddress() == packet.GetBdAddr(), "Address mismatch");
- NotifyUiDisplayPasskey(packet.GetPasskey());
+ ASSERT_LOG(GetRecord()->GetPseudoAddress().GetAddress() == packet.GetBdAddr(), "Address mismatch");
}
void ClassicPairingHandler::OnReceive(hci::KeypressNotificationView packet) {
@@ -390,19 +235,19 @@ void ClassicPairingHandler::OnReceive(hci::KeypressNotificationView packet) {
LOG_INFO("Notification Type: %s", hci::KeypressNotificationTypeText(packet.GetNotificationType()).c_str());
switch (packet.GetNotificationType()) {
case hci::KeypressNotificationType::ENTRY_STARTED:
- // Tell the UI to highlight the first digit
+ // Get ready to keep track of key input
break;
case hci::KeypressNotificationType::DIGIT_ENTERED:
- // Tell the UI to move one digit to the right
+ // Append digit to key
break;
case hci::KeypressNotificationType::DIGIT_ERASED:
- // Tell the UI to move back one digit
+ // erase last digit from key
break;
case hci::KeypressNotificationType::CLEARED:
- // Tell the UI to highlight the first digit again
+ // erase all digits from key
break;
case hci::KeypressNotificationType::ENTRY_COMPLETED:
- // Tell the UI to hide the dialog
+ // set full key to security record
break;
}
}
@@ -412,78 +257,43 @@ void ClassicPairingHandler::OnReceive(hci::KeypressNotificationView packet) {
*
* The table is on pg 2133 of the Core v5.1 spec.
*/
-
void ClassicPairingHandler::OnReceive(hci::UserConfirmationRequestView packet) {
- // Ensure we have io cap response otherwise checks will be wrong if it comes late
- // Ensure we have the name response otherwise we cannot show a name for the device to the user
- if (!has_gotten_io_cap_response_ || !has_gotten_name_response_) {
- user_confirmation_request_ = std::make_optional<hci::UserConfirmationRequestView>(packet);
- return;
- }
ASSERT(packet.IsValid());
LOG_INFO("Received: %s", hci::EventCodeText(packet.GetEventCode()).c_str());
- ASSERT_LOG(GetRecord()->GetPseudoAddress()->GetAddress() == packet.GetBdAddr(), "Address mismatch");
+ ASSERT_LOG(GetRecord()->GetPseudoAddress().GetAddress() == packet.GetBdAddr(), "Address mismatch");
// if locally_initialized, use default, otherwise us remote io caps
hci::IoCapability initiator_io_capability = (locally_initiated_) ? local_io_capability_ : remote_io_capability_;
hci::IoCapability responder_io_capability = (!locally_initiated_) ? local_io_capability_ : remote_io_capability_;
+ // TODO(optedoblivion): Check for TEMPORARY pairing case
switch (initiator_io_capability) {
case hci::IoCapability::DISPLAY_ONLY:
switch (responder_io_capability) {
case hci::IoCapability::DISPLAY_ONLY:
// NumericComparison, Both auto confirm
LOG_INFO("Numeric Comparison: A and B auto confirm");
- if (!GetRecord()->RequiresMitmProtection()) {
- GetChannel()->SendCommand(
- hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
- // NOTE(optedoblivion) BTA needs a callback for when auto accepting JustWorks
- // If we auto accept from the ClassicPairingHandler in GD then we won't
- // get a callback to this shim function.
- // We will have to call it anyway until we eliminate the need
- // TODO(optedoblivion): REMOVE WHEN SHIM LEAVES
- NotifyUiDisplayYesNo();
- } else {
- GetChannel()->SendCommand(hci::UserConfirmationRequestNegativeReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress()));
- }
+ GetChannel()->SendCommand(
+ hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress()));
// Unauthenticated
- GetRecord()->SetAuthenticated(false);
break;
case hci::IoCapability::DISPLAY_YES_NO:
// NumericComparison, Initiator auto confirm, Responder display
- if (!GetRecord()->RequiresMitmProtection()) {
- GetChannel()->SendCommand(
- hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
- // TODO(optedoblivion): REMOVE WHEN SHIM LEAVES
- NotifyUiDisplayYesNo();
- } else {
- GetChannel()->SendCommand(hci::UserConfirmationRequestNegativeReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress()));
- }
+ GetChannel()->SendCommand(
+ hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress()));
LOG_INFO("Numeric Comparison: A auto confirm");
// Unauthenticated
- GetRecord()->SetAuthenticated(true);
break;
case hci::IoCapability::KEYBOARD_ONLY:
// PassKey Entry, Initiator display, Responder input
NotifyUiDisplayPasskey(packet.GetNumericValue());
LOG_INFO("Passkey Entry: A display, B input");
// Authenticated
- GetRecord()->SetAuthenticated(true);
break;
case hci::IoCapability::NO_INPUT_NO_OUTPUT:
// NumericComparison, Both auto confirm
LOG_INFO("Numeric Comparison: A and B auto confirm");
- if (!GetRecord()->RequiresMitmProtection()) {
- GetChannel()->SendCommand(
- hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
- // TODO(optedoblivion): REMOVE WHEN SHIM LEAVES
- NotifyUiDisplayYesNo();
- } else {
- GetChannel()->SendCommand(hci::UserConfirmationRequestNegativeReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress()));
- }
+ GetChannel()->SendCommand(
+ hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress()));
// Unauthenticated
- GetRecord()->SetAuthenticated(true);
break;
}
break;
@@ -494,28 +304,24 @@ void ClassicPairingHandler::OnReceive(hci::UserConfirmationRequestView packet) {
LOG_INFO("Numeric Comparison: A DisplayYesNo, B auto confirm");
NotifyUiDisplayYesNo(packet.GetNumericValue());
// Unauthenticated
- GetRecord()->SetAuthenticated(true);
break;
case hci::IoCapability::DISPLAY_YES_NO:
// NumericComparison Both Display, Both confirm
LOG_INFO("Numeric Comparison: A and B DisplayYesNo");
NotifyUiDisplayYesNo(packet.GetNumericValue());
// Authenticated
- GetRecord()->SetAuthenticated(true);
break;
case hci::IoCapability::KEYBOARD_ONLY:
// PassKey Entry, Initiator display, Responder input
NotifyUiDisplayPasskey(packet.GetNumericValue());
LOG_INFO("Passkey Entry: A display, B input");
// Authenticated
- GetRecord()->SetAuthenticated(true);
break;
case hci::IoCapability::NO_INPUT_NO_OUTPUT:
// NumericComparison, auto confirm Responder, Yes/No confirm Initiator. Don't show confirmation value
- LOG_INFO("Numeric Comparison: A DisplayYesNo, B auto confirm, no show value");
NotifyUiDisplayYesNo();
+ LOG_INFO("Numeric Comparison: A DisplayYesNo, B auto confirm, no show value");
// Unauthenticated
- GetRecord()->SetAuthenticated(true);
break;
}
break;
@@ -526,36 +332,25 @@ void ClassicPairingHandler::OnReceive(hci::UserConfirmationRequestView packet) {
NotifyUiDisplayPasskeyInput();
LOG_INFO("Passkey Entry: A input, B display");
// Authenticated
- GetRecord()->SetAuthenticated(true);
break;
case hci::IoCapability::DISPLAY_YES_NO:
// PassKey Entry, Responder display, Initiator input
NotifyUiDisplayPasskeyInput();
LOG_INFO("Passkey Entry: A input, B display");
// Authenticated
- GetRecord()->SetAuthenticated(true);
break;
case hci::IoCapability::KEYBOARD_ONLY:
// PassKey Entry, both input
NotifyUiDisplayPasskeyInput();
LOG_INFO("Passkey Entry: A input, B input");
// Authenticated
- GetRecord()->SetAuthenticated(true);
break;
case hci::IoCapability::NO_INPUT_NO_OUTPUT:
// NumericComparison, both auto confirm
LOG_INFO("Numeric Comparison: A and B auto confirm");
- if (!GetRecord()->RequiresMitmProtection()) {
- GetChannel()->SendCommand(
- hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
- // TODO(optedoblivion): REMOVE WHEN SHIM LEAVES
- NotifyUiDisplayYesNo();
- } else {
- GetChannel()->SendCommand(hci::UserConfirmationRequestNegativeReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress()));
- }
+ GetChannel()->SendCommand(
+ hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress()));
// Unauthenticated
- GetRecord()->SetAuthenticated(false);
break;
}
break;
@@ -564,62 +359,30 @@ void ClassicPairingHandler::OnReceive(hci::UserConfirmationRequestView packet) {
case hci::IoCapability::DISPLAY_ONLY:
// NumericComparison, both auto confirm
LOG_INFO("Numeric Comparison: A and B auto confirm");
- if (!GetRecord()->RequiresMitmProtection()) {
- GetChannel()->SendCommand(
- hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
- // TODO(optedoblivion): REMOVE WHEN SHIM LEAVES
- NotifyUiDisplayYesNo();
- } else {
- GetChannel()->SendCommand(hci::UserConfirmationRequestNegativeReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress()));
- }
+ GetChannel()->SendCommand(
+ hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress()));
// Unauthenticated
- GetRecord()->SetAuthenticated(false);
break;
case hci::IoCapability::DISPLAY_YES_NO:
// NumericComparison, Initiator auto confirm, Responder Yes/No confirm, no show conf val
LOG_INFO("Numeric Comparison: A auto confirm");
- if (!GetRecord()->RequiresMitmProtection()) {
- GetChannel()->SendCommand(
- hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
- // TODO(optedoblivion): REMOVE WHEN SHIM LEAVES
- NotifyUiDisplayYesNo();
- } else {
- GetChannel()->SendCommand(hci::UserConfirmationRequestNegativeReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress()));
- }
+ GetChannel()->SendCommand(
+ hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress()));
// Unauthenticated
- GetRecord()->SetAuthenticated(false);
break;
case hci::IoCapability::KEYBOARD_ONLY:
// NumericComparison, both auto confirm
LOG_INFO("Numeric Comparison: A and B auto confirm");
- if (!GetRecord()->RequiresMitmProtection()) {
- GetChannel()->SendCommand(
- hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
- // TODO(optedoblivion): REMOVE WHEN SHIM LEAVES
- NotifyUiDisplayYesNo();
- } else {
- GetChannel()->SendCommand(hci::UserConfirmationRequestNegativeReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress()));
- }
+ GetChannel()->SendCommand(
+ hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress()));
// Unauthenticated
- GetRecord()->SetAuthenticated(false);
break;
case hci::IoCapability::NO_INPUT_NO_OUTPUT:
// NumericComparison, both auto confirm
LOG_INFO("Numeric Comparison: A and B auto confirm");
- if (!GetRecord()->RequiresMitmProtection()) {
- GetChannel()->SendCommand(
- hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
- // TODO(optedoblivion): REMOVE WHEN SHIM LEAVES
- NotifyUiDisplayYesNo();
- } else {
- GetChannel()->SendCommand(hci::UserConfirmationRequestNegativeReplyBuilder::Create(
- GetRecord()->GetPseudoAddress()->GetAddress()));
- }
+ GetChannel()->SendCommand(
+ hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress()));
// Unauthenticated
- GetRecord()->SetAuthenticated(false);
break;
}
break;
@@ -628,7 +391,7 @@ void ClassicPairingHandler::OnReceive(hci::UserConfirmationRequestView packet) {
void ClassicPairingHandler::OnReceive(hci::UserPasskeyRequestView packet) {
ASSERT(packet.IsValid());
- ASSERT_LOG(GetRecord()->GetPseudoAddress()->GetAddress() == packet.GetBdAddr(), "Address mismatch");
+ ASSERT_LOG(GetRecord()->GetPseudoAddress().GetAddress() == packet.GetBdAddr(), "Address mismatch");
}
void ClassicPairingHandler::OnUserInput(bool user_input) {
@@ -641,12 +404,12 @@ void ClassicPairingHandler::OnUserInput(bool user_input) {
void ClassicPairingHandler::UserClickedYes() {
GetChannel()->SendCommand(
- hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
+ hci::UserConfirmationRequestReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress()));
}
void ClassicPairingHandler::UserClickedNo() {
GetChannel()->SendCommand(
- hci::UserConfirmationRequestNegativeReplyBuilder::Create(GetRecord()->GetPseudoAddress()->GetAddress()));
+ hci::UserConfirmationRequestNegativeReplyBuilder::Create(GetRecord()->GetPseudoAddress().GetAddress()));
}
void ClassicPairingHandler::OnPasskeyInput(uint32_t passkey) {
diff --git a/gd/security/pairing/classic_pairing_handler.h b/gd/security/pairing/classic_pairing_handler.h
index 190395df5..86cb3587e 100644
--- a/gd/security/pairing/classic_pairing_handler.h
+++ b/gd/security/pairing/classic_pairing_handler.h
@@ -33,42 +33,34 @@ class ISecurityManagerListener;
namespace pairing {
+static constexpr hci::IoCapability kDefaultIoCapability = hci::IoCapability::DISPLAY_YES_NO;
+static constexpr hci::OobDataPresent kDefaultOobDataPresent = hci::OobDataPresent::NOT_PRESENT;
+static constexpr hci::AuthenticationRequirements kDefaultAuthenticationRequirements =
+ hci::AuthenticationRequirements::DEDICATED_BONDING_MITM_PROTECTION;
+
class ClassicPairingHandler : public PairingHandler {
public:
- ClassicPairingHandler(
- channel::SecurityManagerChannel* security_manager_channel,
- std::shared_ptr<record::SecurityRecord> record,
- os::Handler* security_handler,
- common::OnceCallback<void(hci::Address, PairingResultOrFailure)> complete_callback,
- UI* user_interface,
- os::Handler* user_interface_handler,
- std::string device_name,
- neighbor::NameDbModule* name_db_module)
- : PairingHandler(security_manager_channel, std::move(record), name_db_module),
- security_handler_(security_handler),
- remote_io_capability_(hci::IoCapability::DISPLAY_YES_NO),
- remote_oob_present_(hci::OobDataPresent::NOT_PRESENT),
- remote_authentication_requirements_(hci::AuthenticationRequirements::DEDICATED_BONDING_MITM_PROTECTION),
- local_io_capability_(hci::IoCapability::DISPLAY_YES_NO),
- local_oob_present_(hci::OobDataPresent::NOT_PRESENT),
- local_authentication_requirements_(hci::AuthenticationRequirements::DEDICATED_BONDING_MITM_PROTECTION),
- complete_callback_(std::move(complete_callback)),
- user_interface_(user_interface),
- user_interface_handler_(user_interface_handler),
- device_name_(std::move(device_name)) {}
-
- ~ClassicPairingHandler() = default;
-
- void Initiate(
- bool locally_initiated,
- hci::IoCapability io_capability,
- hci::AuthenticationRequirements auth_requirements,
- OobData remote_p192_oob_data,
- OobData remote_p256_oob_data) override;
+ ClassicPairingHandler(std::shared_ptr<l2cap::classic::FixedChannelManager> fixed_channel_manager,
+ channel::SecurityManagerChannel* security_manager_channel,
+ std::shared_ptr<record::SecurityRecord> record, os::Handler* security_handler,
+ common::OnceCallback<void(hci::Address, PairingResultOrFailure)> complete_callback,
+ UI* user_interface, os::Handler* user_interface_handler, std::string device_name)
+ : PairingHandler(security_manager_channel, std::move(record)),
+ fixed_channel_manager_(std::move(fixed_channel_manager)), security_policy_(),
+ security_handler_(security_handler), remote_io_capability_(kDefaultIoCapability),
+ local_io_capability_(kDefaultIoCapability), local_oob_present_(kDefaultOobDataPresent),
+ local_authentication_requirements_(kDefaultAuthenticationRequirements),
+ complete_callback_(std::move(complete_callback)), user_interface_(user_interface),
+ user_interface_handler_(user_interface_handler), device_name_(device_name) {}
+
+ ~ClassicPairingHandler() override = default;
+
+ void Initiate(bool locally_initiated, hci::IoCapability io_capability, hci::OobDataPresent oob_present,
+ hci::AuthenticationRequirements auth_requirements) override;
void Cancel() override;
void OnReceive(hci::ChangeConnectionLinkKeyCompleteView packet) override;
- void OnReceive(hci::CentralLinkKeyCompleteView packet) override;
+ void OnReceive(hci::MasterLinkKeyCompleteView packet) override;
void OnReceive(hci::PinCodeRequestView packet) override;
void OnReceive(hci::LinkKeyRequestView packet) override;
void OnReceive(hci::LinkKeyNotificationView packet) override;
@@ -87,48 +79,41 @@ class ClassicPairingHandler : public PairingHandler {
void OnPairingPromptAccepted(const bluetooth::hci::AddressWithType& address, bool confirmed) override;
void OnConfirmYesNo(const bluetooth::hci::AddressWithType& address, bool confirmed) override;
void OnPasskeyEntry(const bluetooth::hci::AddressWithType& address, uint32_t passkey) override;
- void OnPinEntry(const bluetooth::hci::AddressWithType& address, std::vector<uint8_t> pin) override;
-
- void OnNameRequestComplete(hci::Address address, bool success);
private:
+ void OnRegistrationComplete(l2cap::classic::FixedChannelManager::RegistrationResult result,
+ std::unique_ptr<l2cap::classic::FixedChannelService> fixed_channel_service);
+ void OnUnregistered();
+ void OnConnectionOpen(std::unique_ptr<l2cap::classic::FixedChannel> fixed_channel);
+ void OnConnectionFail(l2cap::classic::FixedChannelManager::ConnectionResult result);
+ void OnConnectionClose(hci::ErrorCode error_code);
void OnUserInput(bool user_input);
void OnPasskeyInput(uint32_t passkey);
void NotifyUiDisplayYesNo(uint32_t numeric_value);
void NotifyUiDisplayYesNo();
void NotifyUiDisplayPasskey(uint32_t passkey);
void NotifyUiDisplayPasskeyInput();
- void NotifyUiDisplayPinCodeInput();
void NotifyUiDisplayCancel();
void UserClickedYes();
void UserClickedNo();
+ std::shared_ptr<l2cap::classic::FixedChannelManager> fixed_channel_manager_;
+ std::unique_ptr<l2cap::classic::FixedChannelService> fixed_channel_service_{nullptr};
+ l2cap::SecurityPolicy security_policy_ __attribute__((unused));
os::Handler* security_handler_ __attribute__((unused));
- hci::IoCapability remote_io_capability_;
- hci::OobDataPresent remote_oob_present_ __attribute__((unused));
- hci::AuthenticationRequirements remote_authentication_requirements_ __attribute__((unused));
- hci::IoCapability local_io_capability_;
+ hci::IoCapability remote_io_capability_ __attribute__((unused));
+ hci::IoCapability local_io_capability_ __attribute__((unused));
hci::OobDataPresent local_oob_present_ __attribute__((unused));
hci::AuthenticationRequirements local_authentication_requirements_ __attribute__((unused));
- OobData remote_p192_oob_data_;
- OobData remote_p256_oob_data_;
+ std::unique_ptr<l2cap::classic::FixedChannel> fixed_channel_{nullptr};
common::OnceCallback<void(hci::Address, PairingResultOrFailure)> complete_callback_;
UI* user_interface_;
os::Handler* user_interface_handler_;
std::string device_name_;
- bool is_cancelled_ = false;
-
- bool has_gotten_io_cap_response_ = false;
- bool has_gotten_name_response_ = false;
- std::optional<hci::UserConfirmationRequestView> user_confirmation_request_ = std::nullopt;
- std::optional<hci::LinkKeyNotificationView> link_key_notification_ = std::nullopt;
- hci::ErrorCode last_status_ = hci::ErrorCode::UNKNOWN_HCI_COMMAND;
+ hci::ErrorCode last_status_;
bool locally_initiated_ = false;
uint32_t passkey_ = 0;
- bool already_link_key_replied_ = false;
- bool secure_connections_enabled_ = true;
- bool is_legacy_pin_code_ = false;
};
} // namespace pairing
diff --git a/gd/security/pairing/classic_pairing_handler_unittest.cc b/gd/security/pairing/classic_pairing_handler_unittest.cc
index dde08ccb8..d134ff88d 100644
--- a/gd/security/pairing/classic_pairing_handler_unittest.cc
+++ b/gd/security/pairing/classic_pairing_handler_unittest.cc
@@ -19,20 +19,18 @@
#include <gtest/gtest.h>
#include <memory>
-#include <utility>
#include "hci/hci_packets.h"
+#include "l2cap/classic/fixed_channel_manager_mock.h"
#include "packet/raw_builder.h"
#include "security/channel/security_manager_channel.h"
#include "security/initial_informations.h"
#include "security/smp_packets.h"
#include "security/test/fake_hci_layer.h"
-#include "security/test/fake_name_db.h"
-#include "security/test/fake_security_interface.h"
namespace bluetooth {
namespace security {
-namespace pairing {
+namespace channel {
namespace {
using bluetooth::security::channel::SecurityManagerChannel;
@@ -47,47 +45,12 @@ using os::Handler;
using os::Thread;
using packet::RawBuilder;
-class FakeSecurityManagerChannel : public channel::SecurityManagerChannel {
- public:
- FakeSecurityManagerChannel(os::Handler* handler, hci::HciLayer* hci_layer)
- : channel::SecurityManagerChannel(handler, hci_layer) {}
- ~FakeSecurityManagerChannel() {}
-
- void OnLinkConnected(std::unique_ptr<l2cap::classic::LinkSecurityInterface> link) override {
- LOG_ERROR("CALLED");
- }
-
- void OnLinkDisconnected(hci::Address address) override {
- LOG_ERROR("CALLED");
- }
-
- void OnEncryptionChange(hci::Address address, bool encrypted) override {
- LOG_ERROR("CALLED");
- }
-
- void OnAuthenticationComplete(hci::ErrorCode hci_status, hci::Address remote) override {
- LOG_ERROR("CALLED");
- }
-};
-
-class TestUI : public UI {
- public:
- ~TestUI() = default;
- void DisplayPairingPrompt(const hci::AddressWithType& address, std::string name) override {}
- void Cancel(const hci::AddressWithType& address) override {}
- void DisplayConfirmValue(ConfirmationData data) override {}
- void DisplayYesNoDialog(ConfirmationData data) override {}
- void DisplayEnterPasskeyDialog(ConfirmationData data) override {}
- void DisplayPasskey(ConfirmationData data) override {}
- void DisplayEnterPinDialog(ConfirmationData data) override {}
-};
-
-class SecurityManagerChannelCallback : public channel::ISecurityManagerChannelListener {
+class SecurityManagerChannelCallback : public ISecurityManagerChannelListener {
public:
explicit SecurityManagerChannelCallback(pairing::ClassicPairingHandler* pairing_handler)
: pairing_handler_(pairing_handler) {}
- void OnHciEventReceived(hci::EventView packet) override {
- auto event = hci::EventView::Create(packet);
+ void OnHciEventReceived(hci::EventPacketView packet) override {
+ auto event = hci::EventPacketView::Create(packet);
ASSERT_LOG(event.IsValid(), "Received invalid packet");
const hci::EventCode code = event.GetEventCode();
switch (code) {
@@ -133,104 +96,51 @@ class SecurityManagerChannelCallback : public channel::ISecurityManagerChannelLi
}
}
- void OnConnectionClosed(hci::Address address) override {
- LOG_INFO("Called");
- }
-
private:
pairing::ClassicPairingHandler* pairing_handler_ = nullptr;
};
-bool expect_success_ = true;
-
static void pairing_complete_callback(bluetooth::hci::Address address, PairingResultOrFailure status) {
- if (expect_success_) {
- ASSERT_TRUE(std::holds_alternative<PairingResult>(status));
- } else {
- ASSERT_FALSE(std::holds_alternative<PairingResult>(status));
- }
+ ASSERT(std::holds_alternative<PairingResult>(status));
+ // auto result = std::get<PairingResult>(status);
+ // if (std::holds_alternative<PairingResult>(status)) {
+ // auto result = status::get<PairingResult>(status);
+ // }
+ // if (std::holds_alternative<PairingFailure>(status)) {
+ // auto failure = status::get<PairingFailure>(status);
+ // }
}
class ClassicPairingHandlerTest : public ::testing::Test {
protected:
void SetUp() override {
- expect_success_ = true;
+ handler_ = new Handler(&thread_);
hci_layer_ = new FakeHciLayer();
- name_db_module_ = new FakeNameDbModule();
+ channel_ = new channel::SecurityManagerChannel(handler_, hci_layer_);
fake_registry_.InjectTestModule(&FakeHciLayer::Factory, hci_layer_);
- fake_registry_.InjectTestModule(&neighbor::NameDbModule::Factory, name_db_module_);
- handler_ = fake_registry_.GetTestModuleHandler(&FakeHciLayer::Factory);
- channel_ = new FakeSecurityManagerChannel(handler_, hci_layer_);
+ fake_registry_.Start<FakeHciLayer>(&thread_);
security_record_ = std::make_shared<record::SecurityRecord>(device_);
- user_interface_ = new TestUI();
- user_interface_handler_ = handler_;
- pairing_handler_ = new pairing::ClassicPairingHandler(
- channel_,
- security_record_,
- handler_,
- common::Bind(&pairing_complete_callback),
- user_interface_,
- user_interface_handler_,
- "Fake name",
- name_db_module_);
+ std::shared_ptr<l2cap::classic::testing::MockFixedChannelManager> sptr =
+ std::shared_ptr<l2cap::classic::testing::MockFixedChannelManager>(
+ new l2cap::classic::testing::MockFixedChannelManager());
+ EXPECT_CALL(*sptr, RegisterService(::testing::_, ::testing::_, ::testing::_, ::testing::_, ::testing::_))
+ .Times(::testing::AnyNumber());
+ pairing_handler_ = new pairing::ClassicPairingHandler(sptr, channel_, security_record_, handler_,
+ common::Bind(&pairing_complete_callback), user_interface_,
+ user_interface_handler_, "Fake name");
channel_callback_ = new SecurityManagerChannelCallback(pairing_handler_);
channel_->SetChannelListener(channel_callback_);
- security_interface_ = new FakeSecurityInterface(handler_, channel_);
- channel_->SetSecurityInterface(security_interface_);
}
void TearDown() override {
channel_->SetChannelListener(nullptr);
- synchronize();
+ handler_->Clear();
+ fake_registry_.SynchronizeModuleHandler(&FakeHciLayer::Factory, std::chrono::milliseconds(20));
fake_registry_.StopAll();
- delete user_interface_;
delete pairing_handler_;
+ delete handler_;
delete channel_;
delete channel_callback_;
- delete security_interface_;
- }
-
- void synchronize() {
- fake_registry_.SynchronizeModuleHandler(&FakeHciLayer::Factory, std::chrono::milliseconds(20));
- fake_registry_.SynchronizeModuleHandler(&FakeNameDbModule::Factory, std::chrono::milliseconds(20));
- }
-
- void ReceiveLinkKeyRequest(hci::AddressWithType device) {
- hci_layer_->IncomingEvent(hci::LinkKeyRequestBuilder::Create(device.GetAddress()));
- synchronize();
- }
-
- void ReceiveIoCapabilityRequest(hci::AddressWithType device) {
- hci_layer_->IncomingEvent(hci::IoCapabilityRequestBuilder::Create(device.GetAddress()));
- synchronize();
- }
-
- void ReceiveIoCapabilityResponse(hci::AddressWithType device, hci::IoCapability io_cap,
- hci::OobDataPresent oob_present, hci::AuthenticationRequirements auth_reqs) {
- hci_layer_->IncomingEvent(
- hci::IoCapabilityResponseBuilder::Create(device.GetAddress(), io_cap, oob_present, auth_reqs));
- synchronize();
- }
-
- void ReceiveOobDataRequest(hci::AddressWithType device) {
- hci_layer_->IncomingEvent(hci::RemoteOobDataRequestBuilder::Create(device.GetAddress()));
- synchronize();
- }
-
- void ReceiveUserConfirmationRequest(hci::AddressWithType device, uint32_t numeric_value) {
- hci_layer_->IncomingEvent(hci::UserConfirmationRequestBuilder::Create(device.GetAddress(), numeric_value));
- synchronize();
- }
-
- void ReceiveSimplePairingComplete(hci::ErrorCode status, hci::AddressWithType device) {
- hci_layer_->IncomingEvent(hci::SimplePairingCompleteBuilder::Create(status, device.GetAddress()));
- synchronize();
- }
-
- void ReceiveLinkKeyNotification(hci::AddressWithType device, std::array<uint8_t, 16> link_key,
- hci::KeyType key_type) {
- hci_layer_->IncomingEvent(hci::LinkKeyNotificationBuilder::Create(device.GetAddress(), link_key, key_type));
- synchronize();
}
TestModuleRegistry fake_registry_;
@@ -244,8 +154,6 @@ class ClassicPairingHandlerTest : public ::testing::Test {
std::shared_ptr<record::SecurityRecord> security_record_ = nullptr;
UI* user_interface_;
os::Handler* user_interface_handler_;
- l2cap::classic::SecurityInterface* security_interface_ = nullptr;
- FakeNameDbModule* name_db_module_ = nullptr;
};
// Security Manager Boot Sequence (Required for SSP, these are already set at boot time)
@@ -271,14 +179,40 @@ class ClassicPairingHandlerTest : public ::testing::Test {
// <- EncryptionChange
// -> L2capConnectionResponse (if triggered by L2cap connection request)
+void ReceiveLinkKeyRequest(FakeHciLayer* hci_layer, hci::AddressWithType device) {
+ hci_layer->IncomingEvent(hci::LinkKeyRequestBuilder::Create(device.GetAddress()));
+}
+
+void ReceiveIoCapabilityRequest(FakeHciLayer* hci_layer, hci::AddressWithType device) {
+ hci_layer->IncomingEvent(hci::IoCapabilityRequestBuilder::Create(device.GetAddress()));
+}
+
+void ReceiveIoCapabilityResponse(FakeHciLayer* hci_layer, hci::AddressWithType device, hci::IoCapability io_cap,
+ hci::OobDataPresent oob_present, hci::AuthenticationRequirements auth_reqs) {
+ hci_layer->IncomingEvent(
+ hci::IoCapabilityResponseBuilder::Create(device.GetAddress(), io_cap, oob_present, auth_reqs));
+}
+
+void ReceiveUserConfirmationRequest(FakeHciLayer* hci_layer, hci::AddressWithType device, uint32_t numeric_value) {
+ hci_layer->IncomingEvent(hci::UserConfirmationRequestBuilder::Create(device.GetAddress(), numeric_value));
+}
+
+void ReceiveSimplePairingComplete(FakeHciLayer* hci_layer, hci::ErrorCode status, hci::AddressWithType device) {
+ hci_layer->IncomingEvent(hci::SimplePairingCompleteBuilder::Create(status, device.GetAddress()));
+}
+
+void ReceiveLinkKeyNotification(FakeHciLayer* hci_layer, hci::AddressWithType device, std::array<uint8_t, 16> link_key,
+ hci::KeyType key_type) {
+ hci_layer->IncomingEvent(hci::LinkKeyNotificationBuilder::Create(device.GetAddress(), link_key, key_type));
+}
+
hci::SecurityCommandView GetLastCommand(FakeHciLayer* hci_layer) {
auto last_command = std::move(hci_layer->GetLastCommand()->command);
auto command_packet = GetPacketView(std::move(last_command));
- auto command_packet_view = hci::CommandView::Create(command_packet);
+ auto command_packet_view = hci::CommandPacketView::Create(command_packet);
+ ASSERT(command_packet_view.IsValid());
auto security_command_view = hci::SecurityCommandView::Create(command_packet_view);
- if (!security_command_view.IsValid()) {
- LOG_ERROR("Invalid security command received");
- }
+ ASSERT(security_command_view.IsValid());
return security_command_view;
}
@@ -290,14 +224,14 @@ TEST_F(ClassicPairingHandlerTest, setup_teardown) {}
TEST_F(ClassicPairingHandlerTest, locally_initiatied_display_only_display_only_temp) {
hci::IoCapability injected_io_capability = hci::IoCapability::DISPLAY_ONLY;
hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing_handler_->Initiate(
- true, injected_io_capability, injected_authentication_requirements, pairing::OobData(), pairing::OobData());
- ReceiveLinkKeyRequest(device_);
+ pairing_handler_->Initiate(true, injected_io_capability, hci::OobDataPresent::NOT_PRESENT,
+ injected_authentication_requirements);
+ ReceiveLinkKeyRequest(hci_layer_, device_);
auto security_command_view = GetLastCommand(hci_layer_);
auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
ASSERT_TRUE(link_key_neg_reply.IsValid());
ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
+ ReceiveIoCapabilityRequest(hci_layer_, device_);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
@@ -305,22 +239,20 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_display_only_display_only_t
ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
ASSERT_EQ(hci::OobDataPresent::NOT_PRESENT, io_cap_request_reply.GetOobPresent());
ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(device_, hci::IoCapability::DISPLAY_ONLY, hci::OobDataPresent::NOT_PRESENT,
+ ReceiveIoCapabilityResponse(hci_layer_, device_, hci::IoCapability::DISPLAY_ONLY, hci::OobDataPresent::NOT_PRESENT,
hci::AuthenticationRequirements::NO_BONDING);
uint32_t numeric_value = 0x123;
- ReceiveUserConfirmationRequest(device_, numeric_value);
+ ReceiveUserConfirmationRequest(hci_layer_, device_, numeric_value);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::USER_CONFIRMATION_REQUEST_REPLY, security_command_view.GetOpCode());
auto user_conf_request_reply = hci::UserConfirmationRequestReplyView::Create(security_command_view);
ASSERT_TRUE(user_conf_request_reply.IsValid());
- ReceiveSimplePairingComplete(hci::ErrorCode::SUCCESS, device_);
+ ReceiveSimplePairingComplete(hci_layer_, hci::ErrorCode::SUCCESS, device_);
std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
hci::KeyType key_type = hci::KeyType::DEBUG_COMBINATION;
- ReceiveLinkKeyNotification(device_, link_key, key_type);
+ ReceiveLinkKeyNotification(hci_layer_, device_, link_key, key_type);
ASSERT_EQ(link_key, security_record_->GetLinkKey());
ASSERT_EQ(key_type, security_record_->GetKeyType());
- ASSERT_FALSE(security_record_->IsAuthenticated());
- ASSERT_FALSE(security_record_->RequiresMitmProtection());
}
// display_only + display_yes_no is JustWorks no confirmation
@@ -328,14 +260,14 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_display_only_display_only_t
TEST_F(ClassicPairingHandlerTest, locally_initiatied_display_only_display_yes_no_temp) {
hci::IoCapability injected_io_capability = hci::IoCapability::DISPLAY_ONLY;
hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing_handler_->Initiate(
- true, injected_io_capability, injected_authentication_requirements, pairing::OobData(), pairing::OobData());
- ReceiveLinkKeyRequest(device_);
+ pairing_handler_->Initiate(true, injected_io_capability, hci::OobDataPresent::NOT_PRESENT,
+ injected_authentication_requirements);
+ ReceiveLinkKeyRequest(hci_layer_, device_);
auto security_command_view = GetLastCommand(hci_layer_);
auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
ASSERT_TRUE(link_key_neg_reply.IsValid());
ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
+ ReceiveIoCapabilityRequest(hci_layer_, device_);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
@@ -343,22 +275,20 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_display_only_display_yes_no
ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
ASSERT_EQ(hci::OobDataPresent::NOT_PRESENT, io_cap_request_reply.GetOobPresent());
ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(device_, hci::IoCapability::DISPLAY_YES_NO, hci::OobDataPresent::NOT_PRESENT,
+ ReceiveIoCapabilityResponse(hci_layer_, device_, hci::IoCapability::DISPLAY_YES_NO, hci::OobDataPresent::NOT_PRESENT,
hci::AuthenticationRequirements::NO_BONDING);
uint32_t numeric_value = 0x123;
- ReceiveUserConfirmationRequest(device_, numeric_value);
+ ReceiveUserConfirmationRequest(hci_layer_, device_, numeric_value);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::USER_CONFIRMATION_REQUEST_REPLY, security_command_view.GetOpCode());
auto user_conf_request_reply = hci::UserConfirmationRequestReplyView::Create(security_command_view);
ASSERT_TRUE(user_conf_request_reply.IsValid());
- ReceiveSimplePairingComplete(hci::ErrorCode::SUCCESS, device_);
+ ReceiveSimplePairingComplete(hci_layer_, hci::ErrorCode::SUCCESS, device_);
std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
hci::KeyType key_type = hci::KeyType::DEBUG_COMBINATION;
- ReceiveLinkKeyNotification(device_, link_key, key_type);
+ ReceiveLinkKeyNotification(hci_layer_, device_, link_key, key_type);
ASSERT_EQ(link_key, security_record_->GetLinkKey());
ASSERT_EQ(key_type, security_record_->GetKeyType());
- ASSERT_TRUE(security_record_->IsAuthenticated());
- ASSERT_FALSE(security_record_->RequiresMitmProtection());
}
// display_only + no_input_no_output is JustWorks no confirmation
@@ -366,14 +296,14 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_display_only_display_yes_no
TEST_F(ClassicPairingHandlerTest, locally_initiatied_display_only_no_input_no_output_temp) {
hci::IoCapability injected_io_capability = hci::IoCapability::DISPLAY_ONLY;
hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing_handler_->Initiate(
- true, injected_io_capability, injected_authentication_requirements, pairing::OobData(), pairing::OobData());
- ReceiveLinkKeyRequest(device_);
+ pairing_handler_->Initiate(true, injected_io_capability, hci::OobDataPresent::NOT_PRESENT,
+ injected_authentication_requirements);
+ ReceiveLinkKeyRequest(hci_layer_, device_);
auto security_command_view = GetLastCommand(hci_layer_);
auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
ASSERT_TRUE(link_key_neg_reply.IsValid());
ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
+ ReceiveIoCapabilityRequest(hci_layer_, device_);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
@@ -381,22 +311,20 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_display_only_no_input_no_ou
ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
ASSERT_EQ(hci::OobDataPresent::NOT_PRESENT, io_cap_request_reply.GetOobPresent());
ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(device_, hci::IoCapability::NO_INPUT_NO_OUTPUT, hci::OobDataPresent::NOT_PRESENT,
- hci::AuthenticationRequirements::NO_BONDING);
+ ReceiveIoCapabilityResponse(hci_layer_, device_, hci::IoCapability::NO_INPUT_NO_OUTPUT,
+ hci::OobDataPresent::NOT_PRESENT, hci::AuthenticationRequirements::NO_BONDING);
uint32_t numeric_value = 0x123;
- ReceiveUserConfirmationRequest(device_, numeric_value);
+ ReceiveUserConfirmationRequest(hci_layer_, device_, numeric_value);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::USER_CONFIRMATION_REQUEST_REPLY, security_command_view.GetOpCode());
auto user_conf_request_reply = hci::UserConfirmationRequestReplyView::Create(security_command_view);
ASSERT_TRUE(user_conf_request_reply.IsValid());
- ReceiveSimplePairingComplete(hci::ErrorCode::SUCCESS, device_);
+ ReceiveSimplePairingComplete(hci_layer_, hci::ErrorCode::SUCCESS, device_);
std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
hci::KeyType key_type = hci::KeyType::DEBUG_COMBINATION;
- ReceiveLinkKeyNotification(device_, link_key, key_type);
+ ReceiveLinkKeyNotification(hci_layer_, device_, link_key, key_type);
ASSERT_EQ(link_key, security_record_->GetLinkKey());
ASSERT_EQ(key_type, security_record_->GetKeyType());
- ASSERT_TRUE(security_record_->IsAuthenticated());
- ASSERT_FALSE(security_record_->RequiresMitmProtection());
}
// keyboard_only + no_input_no_output is JustWorks no confirmation
@@ -404,14 +332,14 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_display_only_no_input_no_ou
TEST_F(ClassicPairingHandlerTest, locally_initiatied_keyboard_only_no_input_no_output_temp) {
hci::IoCapability injected_io_capability = hci::IoCapability::KEYBOARD_ONLY;
hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing_handler_->Initiate(
- true, injected_io_capability, injected_authentication_requirements, pairing::OobData(), pairing::OobData());
- ReceiveLinkKeyRequest(device_);
+ pairing_handler_->Initiate(true, injected_io_capability, hci::OobDataPresent::NOT_PRESENT,
+ injected_authentication_requirements);
+ ReceiveLinkKeyRequest(hci_layer_, device_);
auto security_command_view = GetLastCommand(hci_layer_);
auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
ASSERT_TRUE(link_key_neg_reply.IsValid());
ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
+ ReceiveIoCapabilityRequest(hci_layer_, device_);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
@@ -419,22 +347,20 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_keyboard_only_no_input_no_o
ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
ASSERT_EQ(hci::OobDataPresent::NOT_PRESENT, io_cap_request_reply.GetOobPresent());
ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(device_, hci::IoCapability::NO_INPUT_NO_OUTPUT, hci::OobDataPresent::NOT_PRESENT,
- hci::AuthenticationRequirements::NO_BONDING);
+ ReceiveIoCapabilityResponse(hci_layer_, device_, hci::IoCapability::NO_INPUT_NO_OUTPUT,
+ hci::OobDataPresent::NOT_PRESENT, hci::AuthenticationRequirements::NO_BONDING);
uint32_t numeric_value = 0x123;
- ReceiveUserConfirmationRequest(device_, numeric_value);
+ ReceiveUserConfirmationRequest(hci_layer_, device_, numeric_value);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::USER_CONFIRMATION_REQUEST_REPLY, security_command_view.GetOpCode());
auto user_conf_request_reply = hci::UserConfirmationRequestReplyView::Create(security_command_view);
ASSERT_TRUE(user_conf_request_reply.IsValid());
- ReceiveSimplePairingComplete(hci::ErrorCode::SUCCESS, device_);
+ ReceiveSimplePairingComplete(hci_layer_, hci::ErrorCode::SUCCESS, device_);
std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
hci::KeyType key_type = hci::KeyType::DEBUG_COMBINATION;
- ReceiveLinkKeyNotification(device_, link_key, key_type);
+ ReceiveLinkKeyNotification(hci_layer_, device_, link_key, key_type);
ASSERT_EQ(link_key, security_record_->GetLinkKey());
ASSERT_EQ(key_type, security_record_->GetKeyType());
- ASSERT_FALSE(security_record_->IsAuthenticated());
- ASSERT_FALSE(security_record_->RequiresMitmProtection());
}
// no_input_no_output + display_only is JustWorks no confirmation
@@ -442,14 +368,14 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_keyboard_only_no_input_no_o
TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_display_only_temp) {
hci::IoCapability injected_io_capability = hci::IoCapability::NO_INPUT_NO_OUTPUT;
hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing_handler_->Initiate(
- true, injected_io_capability, injected_authentication_requirements, pairing::OobData(), pairing::OobData());
- ReceiveLinkKeyRequest(device_);
+ pairing_handler_->Initiate(true, injected_io_capability, hci::OobDataPresent::NOT_PRESENT,
+ injected_authentication_requirements);
+ ReceiveLinkKeyRequest(hci_layer_, device_);
auto security_command_view = GetLastCommand(hci_layer_);
auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
ASSERT_TRUE(link_key_neg_reply.IsValid());
ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
+ ReceiveIoCapabilityRequest(hci_layer_, device_);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
@@ -457,22 +383,20 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_display_
ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
ASSERT_EQ(hci::OobDataPresent::NOT_PRESENT, io_cap_request_reply.GetOobPresent());
ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(device_, hci::IoCapability::DISPLAY_ONLY, hci::OobDataPresent::NOT_PRESENT,
+ ReceiveIoCapabilityResponse(hci_layer_, device_, hci::IoCapability::DISPLAY_ONLY, hci::OobDataPresent::NOT_PRESENT,
hci::AuthenticationRequirements::NO_BONDING);
uint32_t numeric_value = 0x123;
- ReceiveUserConfirmationRequest(device_, numeric_value);
+ ReceiveUserConfirmationRequest(hci_layer_, device_, numeric_value);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::USER_CONFIRMATION_REQUEST_REPLY, security_command_view.GetOpCode());
auto user_conf_request_reply = hci::UserConfirmationRequestReplyView::Create(security_command_view);
ASSERT_TRUE(user_conf_request_reply.IsValid());
- ReceiveSimplePairingComplete(hci::ErrorCode::SUCCESS, device_);
+ ReceiveSimplePairingComplete(hci_layer_, hci::ErrorCode::SUCCESS, device_);
std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
hci::KeyType key_type = hci::KeyType::DEBUG_COMBINATION;
- ReceiveLinkKeyNotification(device_, link_key, key_type);
+ ReceiveLinkKeyNotification(hci_layer_, device_, link_key, key_type);
ASSERT_EQ(link_key, security_record_->GetLinkKey());
ASSERT_EQ(key_type, security_record_->GetKeyType());
- ASSERT_FALSE(security_record_->IsAuthenticated());
- ASSERT_FALSE(security_record_->RequiresMitmProtection());
}
// no_input_no_output + display_yes_no is JustWorks no confirmation
@@ -480,14 +404,14 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_display_
TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_display_yes_no_temp) {
hci::IoCapability injected_io_capability = hci::IoCapability::NO_INPUT_NO_OUTPUT;
hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing_handler_->Initiate(
- true, injected_io_capability, injected_authentication_requirements, pairing::OobData(), pairing::OobData());
- ReceiveLinkKeyRequest(device_);
+ pairing_handler_->Initiate(true, injected_io_capability, hci::OobDataPresent::NOT_PRESENT,
+ injected_authentication_requirements);
+ ReceiveLinkKeyRequest(hci_layer_, device_);
auto security_command_view = GetLastCommand(hci_layer_);
auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
ASSERT_TRUE(link_key_neg_reply.IsValid());
ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
+ ReceiveIoCapabilityRequest(hci_layer_, device_);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
@@ -495,22 +419,20 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_display_
ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
ASSERT_EQ(hci::OobDataPresent::NOT_PRESENT, io_cap_request_reply.GetOobPresent());
ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(device_, hci::IoCapability::DISPLAY_YES_NO, hci::OobDataPresent::NOT_PRESENT,
+ ReceiveIoCapabilityResponse(hci_layer_, device_, hci::IoCapability::DISPLAY_YES_NO, hci::OobDataPresent::NOT_PRESENT,
hci::AuthenticationRequirements::NO_BONDING);
uint32_t numeric_value = 0x123;
- ReceiveUserConfirmationRequest(device_, numeric_value);
+ ReceiveUserConfirmationRequest(hci_layer_, device_, numeric_value);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::USER_CONFIRMATION_REQUEST_REPLY, security_command_view.GetOpCode());
auto user_conf_request_reply = hci::UserConfirmationRequestReplyView::Create(security_command_view);
ASSERT_TRUE(user_conf_request_reply.IsValid());
- ReceiveSimplePairingComplete(hci::ErrorCode::SUCCESS, device_);
+ ReceiveSimplePairingComplete(hci_layer_, hci::ErrorCode::SUCCESS, device_);
std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
hci::KeyType key_type = hci::KeyType::DEBUG_COMBINATION;
- ReceiveLinkKeyNotification(device_, link_key, key_type);
+ ReceiveLinkKeyNotification(hci_layer_, device_, link_key, key_type);
ASSERT_EQ(link_key, security_record_->GetLinkKey());
ASSERT_EQ(key_type, security_record_->GetKeyType());
- ASSERT_FALSE(security_record_->IsAuthenticated());
- ASSERT_FALSE(security_record_->RequiresMitmProtection());
}
// no_input_no_output + keyboard_only is JustWorks no confirmation
@@ -518,14 +440,14 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_display_
TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_keyboard_only_temp) {
hci::IoCapability injected_io_capability = hci::IoCapability::NO_INPUT_NO_OUTPUT;
hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing_handler_->Initiate(
- true, injected_io_capability, injected_authentication_requirements, pairing::OobData(), pairing::OobData());
- ReceiveLinkKeyRequest(device_);
+ pairing_handler_->Initiate(true, injected_io_capability, hci::OobDataPresent::NOT_PRESENT,
+ injected_authentication_requirements);
+ ReceiveLinkKeyRequest(hci_layer_, device_);
auto security_command_view = GetLastCommand(hci_layer_);
auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
ASSERT_TRUE(link_key_neg_reply.IsValid());
ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
+ ReceiveIoCapabilityRequest(hci_layer_, device_);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
@@ -533,22 +455,20 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_keyboard
ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
ASSERT_EQ(hci::OobDataPresent::NOT_PRESENT, io_cap_request_reply.GetOobPresent());
ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(device_, hci::IoCapability::KEYBOARD_ONLY, hci::OobDataPresent::NOT_PRESENT,
+ ReceiveIoCapabilityResponse(hci_layer_, device_, hci::IoCapability::KEYBOARD_ONLY, hci::OobDataPresent::NOT_PRESENT,
hci::AuthenticationRequirements::NO_BONDING);
uint32_t numeric_value = 0x123;
- ReceiveUserConfirmationRequest(device_, numeric_value);
+ ReceiveUserConfirmationRequest(hci_layer_, device_, numeric_value);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::USER_CONFIRMATION_REQUEST_REPLY, security_command_view.GetOpCode());
auto user_conf_request_reply = hci::UserConfirmationRequestReplyView::Create(security_command_view);
ASSERT_TRUE(user_conf_request_reply.IsValid());
- ReceiveSimplePairingComplete(hci::ErrorCode::SUCCESS, device_);
+ ReceiveSimplePairingComplete(hci_layer_, hci::ErrorCode::SUCCESS, device_);
std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
hci::KeyType key_type = hci::KeyType::DEBUG_COMBINATION;
- ReceiveLinkKeyNotification(device_, link_key, key_type);
+ ReceiveLinkKeyNotification(hci_layer_, device_, link_key, key_type);
ASSERT_EQ(link_key, security_record_->GetLinkKey());
ASSERT_EQ(key_type, security_record_->GetKeyType());
- ASSERT_FALSE(security_record_->IsAuthenticated());
- ASSERT_FALSE(security_record_->RequiresMitmProtection());
}
// no_input_no_output + no_input_no_output is JustWorks no confirmation
@@ -556,14 +476,14 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_keyboard
TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_no_input_no_output_temp) {
hci::IoCapability injected_io_capability = hci::IoCapability::NO_INPUT_NO_OUTPUT;
hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing_handler_->Initiate(
- true, injected_io_capability, injected_authentication_requirements, pairing::OobData(), pairing::OobData());
- ReceiveLinkKeyRequest(device_);
+ pairing_handler_->Initiate(true, injected_io_capability, hci::OobDataPresent::NOT_PRESENT,
+ injected_authentication_requirements);
+ ReceiveLinkKeyRequest(hci_layer_, device_);
auto security_command_view = GetLastCommand(hci_layer_);
auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
ASSERT_TRUE(link_key_neg_reply.IsValid());
ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
+ ReceiveIoCapabilityRequest(hci_layer_, device_);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
@@ -571,187 +491,20 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_no_input
ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
ASSERT_EQ(hci::OobDataPresent::NOT_PRESENT, io_cap_request_reply.GetOobPresent());
ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(device_, hci::IoCapability::NO_INPUT_NO_OUTPUT, hci::OobDataPresent::NOT_PRESENT,
- hci::AuthenticationRequirements::NO_BONDING);
+ ReceiveIoCapabilityResponse(hci_layer_, device_, hci::IoCapability::NO_INPUT_NO_OUTPUT,
+ hci::OobDataPresent::NOT_PRESENT, hci::AuthenticationRequirements::NO_BONDING);
uint32_t numeric_value = 0x123;
- ReceiveUserConfirmationRequest(device_, numeric_value);
+ ReceiveUserConfirmationRequest(hci_layer_, device_, numeric_value);
security_command_view = GetLastCommand(hci_layer_);
ASSERT_EQ(OpCode::USER_CONFIRMATION_REQUEST_REPLY, security_command_view.GetOpCode());
auto user_conf_request_reply = hci::UserConfirmationRequestReplyView::Create(security_command_view);
ASSERT_TRUE(user_conf_request_reply.IsValid());
- ReceiveSimplePairingComplete(hci::ErrorCode::SUCCESS, device_);
- std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
- hci::KeyType key_type = hci::KeyType::DEBUG_COMBINATION;
- ReceiveLinkKeyNotification(device_, link_key, key_type);
- ASSERT_EQ(link_key, security_record_->GetLinkKey());
- ASSERT_EQ(key_type, security_record_->GetKeyType());
- ASSERT_FALSE(security_record_->IsAuthenticated());
- ASSERT_FALSE(security_record_->RequiresMitmProtection());
-}
-
-TEST_F(ClassicPairingHandlerTest, remote_initiatied_no_input_no_output_no_input_no_output_with_missing_oob_data) {}
-
-// CreateBondOutOfBand no_input_no_output + no_input_no_output OOB Data missing when asked
-TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_no_input_no_output_with_missing_oob_data) {
- expect_success_ = false;
- hci::IoCapability injected_io_capability = hci::IoCapability::NO_INPUT_NO_OUTPUT;
- hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing_handler_->Initiate(
- true, injected_io_capability, injected_authentication_requirements, pairing::OobData(), pairing::OobData());
-
- ReceiveLinkKeyRequest(device_);
- auto security_command_view = GetLastCommand(hci_layer_);
- auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
- ASSERT_TRUE(link_key_neg_reply.IsValid());
- ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
- security_command_view = GetLastCommand(hci_layer_);
- ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
- auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
- ASSERT_TRUE(io_cap_request_reply.IsValid());
- ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
- ASSERT_EQ(hci::OobDataPresent::NOT_PRESENT, io_cap_request_reply.GetOobPresent());
- ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(
- device_,
- hci::IoCapability::NO_INPUT_NO_OUTPUT,
- hci::OobDataPresent::NOT_PRESENT,
- hci::AuthenticationRequirements::NO_BONDING);
- // At this point the pairing handler thinks it has NOT_PRESENT
- ReceiveOobDataRequest(device_);
- security_command_view = GetLastCommand(hci_layer_);
- auto oob_data_req_neg_reply = hci::RemoteOobDataRequestNegativeReplyView::Create(security_command_view);
- ASSERT_TRUE(oob_data_req_neg_reply.IsValid());
- ASSERT_EQ(OpCode::REMOTE_OOB_DATA_REQUEST_NEGATIVE_REPLY, oob_data_req_neg_reply.GetOpCode());
- ReceiveSimplePairingComplete(hci::ErrorCode::AUTHENTICATION_FAILURE, device_);
-}
-
-// CreateBondOutOfBand no_input_no_output + no_input_no_output OOB Data P192
-TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_no_input_no_output_p192_oob_data) {
- hci::IoCapability injected_io_capability = hci::IoCapability::NO_INPUT_NO_OUTPUT;
- hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing::OobData oob_data(
- {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0});
- pairing_handler_->Initiate(
- true, injected_io_capability, injected_authentication_requirements, oob_data, pairing::OobData());
-
- ReceiveLinkKeyRequest(device_);
- auto security_command_view = GetLastCommand(hci_layer_);
- auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
- ASSERT_TRUE(link_key_neg_reply.IsValid());
- ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
- security_command_view = GetLastCommand(hci_layer_);
- ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
- auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
- ASSERT_TRUE(io_cap_request_reply.IsValid());
- ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
- ASSERT_EQ(hci::OobDataPresent::P_192_PRESENT, io_cap_request_reply.GetOobPresent());
- ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(
- device_,
- hci::IoCapability::NO_INPUT_NO_OUTPUT,
- hci::OobDataPresent::NOT_PRESENT,
- hci::AuthenticationRequirements::NO_BONDING);
- // At this point the pairing handler thinks it has NOT_PRESENT
- ReceiveOobDataRequest(device_);
- security_command_view = GetLastCommand(hci_layer_);
- // NOTE(optedoblivion): Extended data is manually disabled in the pairing handler
- // since the controller doesn't seem to currently have support.
- auto oob_data_req_reply = hci::RemoteOobDataRequestReplyView::Create(security_command_view);
- ASSERT_TRUE(oob_data_req_reply.IsValid());
- ASSERT_EQ(OpCode::REMOTE_OOB_DATA_REQUEST_REPLY, oob_data_req_reply.GetOpCode());
- ReceiveSimplePairingComplete(hci::ErrorCode::SUCCESS, device_);
- std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
- hci::KeyType key_type = hci::KeyType::DEBUG_COMBINATION;
- ReceiveLinkKeyNotification(device_, link_key, key_type);
- ASSERT_EQ(link_key, security_record_->GetLinkKey());
- ASSERT_EQ(key_type, security_record_->GetKeyType());
- ASSERT_FALSE(security_record_->IsAuthenticated());
- ASSERT_FALSE(security_record_->RequiresMitmProtection());
-}
-
-// CreateBondOutOfBand no_input_no_output + no_input_no_output OOB Data P256
-TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_no_input_no_output_p256_oob_data) {
- hci::IoCapability injected_io_capability = hci::IoCapability::NO_INPUT_NO_OUTPUT;
- hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing::OobData oob_data(
- {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0});
- pairing_handler_->Initiate(
- true, injected_io_capability, injected_authentication_requirements, pairing::OobData(), oob_data);
- ReceiveLinkKeyRequest(device_);
- auto security_command_view = GetLastCommand(hci_layer_);
- auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
- ASSERT_TRUE(link_key_neg_reply.IsValid());
- ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
- security_command_view = GetLastCommand(hci_layer_);
- ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
- auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
- ASSERT_TRUE(io_cap_request_reply.IsValid());
- ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
- ASSERT_EQ(hci::OobDataPresent::P_256_PRESENT, io_cap_request_reply.GetOobPresent());
- ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(
- device_,
- hci::IoCapability::NO_INPUT_NO_OUTPUT,
- hci::OobDataPresent::NOT_PRESENT,
- hci::AuthenticationRequirements::NO_BONDING);
- // At this point the pairing handler thinks it has NOT_PRESENT
- ReceiveOobDataRequest(device_);
- security_command_view = GetLastCommand(hci_layer_);
- auto oob_data_req_reply = hci::RemoteOobExtendedDataRequestReplyView::Create(security_command_view);
- ASSERT_TRUE(oob_data_req_reply.IsValid());
- ASSERT_EQ(OpCode::REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY, oob_data_req_reply.GetOpCode());
- ReceiveSimplePairingComplete(hci::ErrorCode::SUCCESS, device_);
- std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
- hci::KeyType key_type = hci::KeyType::DEBUG_COMBINATION;
- ReceiveLinkKeyNotification(device_, link_key, key_type);
- ASSERT_EQ(link_key, security_record_->GetLinkKey());
- ASSERT_EQ(key_type, security_record_->GetKeyType());
- ASSERT_FALSE(security_record_->IsAuthenticated());
- ASSERT_FALSE(security_record_->RequiresMitmProtection());
-}
-
-// CreateBondOutOfBand no_input_no_output + no_input_no_output OOB Data P192 and 256
-TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_no_input_no_output_p192_and_256_oob_data) {
- hci::IoCapability injected_io_capability = hci::IoCapability::NO_INPUT_NO_OUTPUT;
- hci::AuthenticationRequirements injected_authentication_requirements = hci::AuthenticationRequirements::NO_BONDING;
- pairing::OobData oob_data(
- {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0}, {1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0});
- pairing_handler_->Initiate(true, injected_io_capability, injected_authentication_requirements, oob_data, oob_data);
- ReceiveLinkKeyRequest(device_);
- auto security_command_view = GetLastCommand(hci_layer_);
- auto link_key_neg_reply = hci::LinkKeyRequestNegativeReplyView::Create(security_command_view);
- ASSERT_TRUE(link_key_neg_reply.IsValid());
- ASSERT_EQ(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY, link_key_neg_reply.GetOpCode());
- ReceiveIoCapabilityRequest(device_);
- security_command_view = GetLastCommand(hci_layer_);
- ASSERT_EQ(OpCode::IO_CAPABILITY_REQUEST_REPLY, security_command_view.GetOpCode());
- auto io_cap_request_reply = hci::IoCapabilityRequestReplyView::Create(security_command_view);
- ASSERT_TRUE(io_cap_request_reply.IsValid());
- ASSERT_EQ(injected_io_capability, io_cap_request_reply.GetIoCapability());
- ASSERT_EQ(hci::OobDataPresent::P_192_AND_256_PRESENT, io_cap_request_reply.GetOobPresent());
- ASSERT_EQ(injected_authentication_requirements, io_cap_request_reply.GetAuthenticationRequirements());
- ReceiveIoCapabilityResponse(
- device_,
- hci::IoCapability::NO_INPUT_NO_OUTPUT,
- hci::OobDataPresent::NOT_PRESENT,
- hci::AuthenticationRequirements::NO_BONDING);
- // At this point the pairing handler thinks it has NOT_PRESENT
- ReceiveOobDataRequest(device_);
- security_command_view = GetLastCommand(hci_layer_);
- auto oob_data_req_reply = hci::RemoteOobExtendedDataRequestReplyView::Create(security_command_view);
- ASSERT_TRUE(oob_data_req_reply.IsValid());
- ASSERT_EQ(OpCode::REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY, oob_data_req_reply.GetOpCode());
- ReceiveSimplePairingComplete(hci::ErrorCode::SUCCESS, device_);
+ ReceiveSimplePairingComplete(hci_layer_, hci::ErrorCode::SUCCESS, device_);
std::array<uint8_t, 16> link_key = {0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, 1, 2, 3, 4, 5};
hci::KeyType key_type = hci::KeyType::DEBUG_COMBINATION;
- ReceiveLinkKeyNotification(device_, link_key, key_type);
+ ReceiveLinkKeyNotification(hci_layer_, device_, link_key, key_type);
ASSERT_EQ(link_key, security_record_->GetLinkKey());
ASSERT_EQ(key_type, security_record_->GetKeyType());
- ASSERT_FALSE(security_record_->IsAuthenticated());
- ASSERT_FALSE(security_record_->RequiresMitmProtection());
}
/*** Numeric Comparison ***/
@@ -771,6 +524,6 @@ TEST_F(ClassicPairingHandlerTest, locally_initiatied_no_input_no_output_no_input
// Collisions
} // namespace
-} // namespace pairing
+} // namespace channel
} // namespace security
} // namespace bluetooth
diff --git a/gd/security/pairing/oob_data.h b/gd/security/pairing/oob_data.h
deleted file mode 100644
index 79430a2d7..000000000
--- a/gd/security/pairing/oob_data.h
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- *
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License") override;
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-#pragma once
-
-namespace bluetooth {
-namespace security {
-namespace pairing {
-
-using SimplePairingHash = std::array<uint8_t, 16>;
-using SimplePairingRandomizer = std::array<uint8_t, 16>;
-
-class OobData {
- public:
- OobData() {}
- OobData(SimplePairingHash C, SimplePairingRandomizer R) : C_(C), R_(R) {}
-
- SimplePairingHash GetC() {
- return C_;
- }
-
- SimplePairingRandomizer GetR() {
- return R_;
- }
-
- bool IsValid() {
- return !std::all_of(C_.begin(), C_.end(), [](uint8_t b) { return b == 0; }) &&
- !std::all_of(R_.begin(), R_.end(), [](uint8_t b) { return b == 0; });
- }
-
- private:
- SimplePairingHash C_ = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
- SimplePairingRandomizer R_ = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
-};
-
-} // namespace pairing
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/pairing/pairing_handler.h b/gd/security/pairing/pairing_handler.h
index 3ad888387..8047147c8 100644
--- a/gd/security/pairing/pairing_handler.h
+++ b/gd/security/pairing/pairing_handler.h
@@ -17,14 +17,11 @@
*/
#pragma once
-#include <neighbor/name_db.h>
#include <utility>
#include "hci/address_with_type.h"
#include "hci/hci_packets.h"
-#include "neighbor/name_db.h"
#include "security/channel/security_manager_channel.h"
-#include "security/pairing/oob_data.h"
#include "security/record/security_record.h"
#include "security/smp_packets.h"
#include "security/ui.h"
@@ -40,25 +37,17 @@ namespace pairing {
*/
class PairingHandler : public UICallbacks {
public:
- PairingHandler(
- channel::SecurityManagerChannel* security_manager_channel,
- std::shared_ptr<record::SecurityRecord> record,
- neighbor::NameDbModule* name_db_module)
- : security_manager_channel_(security_manager_channel),
- record_(std::move(record)),
- name_db_module_(name_db_module) {}
- ~PairingHandler() = default;
+ PairingHandler(channel::SecurityManagerChannel* security_manager_channel,
+ std::shared_ptr<record::SecurityRecord> record)
+ : security_manager_channel_(security_manager_channel), record_(std::move(record)) {}
+ virtual ~PairingHandler() = default;
// Classic
- virtual void Initiate(
- bool locally_initiated,
- hci::IoCapability io_capability,
- hci::AuthenticationRequirements auth_requirements,
- OobData local_p192_oob_data,
- OobData local_p256_oob_data) = 0;
+ virtual void Initiate(bool locally_initiated, hci::IoCapability io_capability, hci::OobDataPresent oob_present,
+ hci::AuthenticationRequirements auth_requirements) = 0; // This is for local initiated only
virtual void Cancel() = 0;
virtual void OnReceive(hci::ChangeConnectionLinkKeyCompleteView packet) = 0;
- virtual void OnReceive(hci::CentralLinkKeyCompleteView packet) = 0;
+ virtual void OnReceive(hci::MasterLinkKeyCompleteView packet) = 0;
virtual void OnReceive(hci::PinCodeRequestView packet) = 0;
virtual void OnReceive(hci::LinkKeyRequestView packet) = 0;
virtual void OnReceive(hci::LinkKeyNotificationView packet) = 0;
@@ -77,7 +66,6 @@ class PairingHandler : public UICallbacks {
virtual void OnPairingPromptAccepted(const bluetooth::hci::AddressWithType& address, bool confirmed) = 0;
virtual void OnConfirmYesNo(const bluetooth::hci::AddressWithType& address, bool confirmed) = 0;
virtual void OnPasskeyEntry(const bluetooth::hci::AddressWithType& address, uint32_t passkey) = 0;
- virtual void OnPinEntry(const bluetooth::hci::AddressWithType& address, std::vector<uint8_t> pin) override = 0;
protected:
std::shared_ptr<record::SecurityRecord> GetRecord() {
@@ -86,14 +74,10 @@ class PairingHandler : public UICallbacks {
channel::SecurityManagerChannel* GetChannel() {
return security_manager_channel_;
}
- neighbor::NameDbModule* GetNameDbModule() {
- return name_db_module_;
- }
private:
channel::SecurityManagerChannel* security_manager_channel_ __attribute__((unused));
std::shared_ptr<record::SecurityRecord> record_ __attribute__((unused));
- neighbor::NameDbModule* name_db_module_;
};
} // namespace pairing
diff --git a/gd/security/pairing_failure.h b/gd/security/pairing_failure.h
index fc1a4f909..f7bbbae92 100644
--- a/gd/security/pairing_failure.h
+++ b/gd/security/pairing_failure.h
@@ -37,11 +37,11 @@ struct PairingFailure {
std::string message;
/* If failure is due to mismatch of received code, this contains the received opcode */
- Code received_code_{0};
+ Code received_code_;
/* if the failure is due to "SMP failure", this field contains the reson code
*/
- PairingFailedReason reason{0};
+ PairingFailedReason reason;
PairingFailure(/*const base::Location& location, */ const std::string& message)
: /*location(location), */ message(message) {}
diff --git a/gd/security/pairing_handler_le.cc b/gd/security/pairing_handler_le.cc
index 556de53c3..15acea998 100644
--- a/gd/security/pairing_handler_le.cc
+++ b/gd/security/pairing_handler_le.cc
@@ -18,20 +18,9 @@
#include "security/pairing_handler_le.h"
-#include "os/rand.h"
-
namespace bluetooth {
namespace security {
-MyOobData PairingHandlerLe::GenerateOobData() {
- MyOobData data{};
- std::tie(data.private_key, data.public_key) = GenerateECDHKeyPair();
-
- data.r = bluetooth::os::GenerateRandom<16>();
- data.c = crypto_toolbox::f4(data.public_key.x.data(), data.public_key.x.data(), data.r, 0);
- return data;
-}
-
void PairingHandlerLe::PairingMain(InitialInformations i) {
LOG_INFO("Pairing Started");
@@ -46,8 +35,7 @@ void PairingHandlerLe::PairingMain(InitialInformations i) {
std::optional<PairingEvent> pairingAccepted = WaitUiPairingAccept();
if (!pairingAccepted || pairingAccepted->ui_value == 0) {
LOG_INFO("User either did not accept the remote pairing, or the prompt timed out");
- // TODO: Uncomment this one once we find a way to attempt to send packet when the link is down
- // SendL2capPacket(i, PairingFailedBuilder::Create(PairingFailedReason::UNSPECIFIED_REASON));
+ SendL2capPacket(i, PairingFailedBuilder::Create(PairingFailedReason::UNSPECIFIED_REASON));
i.OnPairingFinished(PairingFailure("User either did not accept the remote pairing, or the prompt timed out"));
return;
}
@@ -68,18 +56,6 @@ void PairingHandlerLe::PairingMain(InitialInformations i) {
auto [pairing_request, pairing_response] = std::get<Phase1Result>(phase_1_result);
- uint8_t key_size =
- std::min(pairing_request.GetMaximumEncryptionKeySize(), pairing_response.GetMaximumEncryptionKeySize());
- if (key_size < 7 || key_size > 16) {
- LOG_WARN("Resulting key size is bad %d", key_size);
- SendL2capPacket(i, PairingFailedBuilder::Create(PairingFailedReason::ENCRYPTION_KEY_SIZE));
- i.OnPairingFinished(PairingFailure("Resulting key size is bad", PairingFailedReason::ENCRYPTION_KEY_SIZE));
- return;
- }
- if (key_size != 16) {
- LOG_WARN("Resulting key size is less than 16 octets!");
- }
-
/************************************************ PHASE 2 *********************************************************/
bool isSecureConnections = pairing_request.GetAuthReq() & pairing_response.GetAuthReq() & AuthReqMaskSc;
if (isSecureConnections) {
@@ -96,7 +72,7 @@ void PairingHandlerLe::PairingMain(InitialInformations i) {
*/
OobDataFlag remote_have_oob_data =
- IAmCentral(i) ? pairing_response.GetOobDataFlag() : pairing_request.GetOobDataFlag();
+ IAmMaster(i) ? pairing_response.GetOobDataFlag() : pairing_request.GetOobDataFlag();
auto key_exchange_result = ExchangePublicKeys(i, remote_have_oob_data);
if (std::holds_alternative<PairingFailure>(key_exchange_result)) {
@@ -122,16 +98,11 @@ void PairingHandlerLe::PairingMain(InitialInformations i) {
}
Octet16 ltk = std::get<Octet16>(stage_2_result);
- // Mask the key
- std::fill(ltk.begin() + key_size, ltk.end(), 0x00);
-
- if (IAmCentral(i)) {
+ if (IAmMaster(i)) {
LOG_INFO("Sending start encryption request");
SendHciLeStartEncryption(i, i.connection_handle, {0}, {0}, ltk);
- } else {
- auto ltk_req = WaitLeLongTermKeyRequest();
- SendHciLeLongTermKeyReply(i, i.connection_handle, ltk);
}
+
} else {
// 2.3.5.5 LE legacy pairing phase 2
LOG_INFO("Pairing Phase 2 LE legacy pairing Started");
@@ -152,14 +123,8 @@ void PairingHandlerLe::PairingMain(InitialInformations i) {
}
Octet16 stk = std::get<Octet16>(stage2result);
- // Mask the key
- std::fill(stk.begin() + key_size, stk.end(), 0x00);
- if (IAmCentral(i)) {
- LOG_INFO("Sending start encryption request");
+ if (IAmMaster(i)) {
SendHciLeStartEncryption(i, i.connection_handle, {0}, {0}, stk);
- } else {
- auto ltk_req = WaitLeLongTermKeyRequest();
- SendHciLeLongTermKeyReply(i, i.connection_handle, stk);
}
}
@@ -196,20 +161,11 @@ void PairingHandlerLe::PairingMain(InitialInformations i) {
return;
}
- // If it's secure connections pairing, do cross-transport key derivation
- DistributedKeys distributed_keys = std::get<DistributedKeys>(keyExchangeStatus);
- if ((pairing_response.GetAuthReq() & AuthReqMaskSc) && distributed_keys.remote_ltk.has_value()) {
- bool use_h7 = (pairing_response.GetAuthReq() & AuthReqMaskCt2);
- Octet16 link_key = crypto_toolbox::ltk_to_link_key(*(distributed_keys.remote_ltk), use_h7);
- distributed_keys.remote_link_key = link_key;
- }
-
// bool bonding = pairing_request.GetAuthReq() & pairing_response.GetAuthReq() & AuthReqMaskBondingFlag;
i.OnPairingFinished(PairingResult{
.connection_address = i.remote_connection_address,
- .distributed_keys = distributed_keys,
- .key_size = key_size,
+ .distributed_keys = std::get<DistributedKeys>(keyExchangeStatus),
});
LOG_INFO("Pairing finished successfully.");
@@ -218,7 +174,7 @@ void PairingHandlerLe::PairingMain(InitialInformations i) {
Phase1ResultOrFailure PairingHandlerLe::ExchangePairingFeature(const InitialInformations& i) {
LOG_INFO("Phase 1 start");
- if (IAmCentral(i)) {
+ if (IAmMaster(i)) {
// Send Pairing Request
const auto& x = i.myPairingCapabilities;
auto pairing_request_builder =
@@ -241,8 +197,8 @@ Phase1ResultOrFailure PairingHandlerLe::ExchangePairingFeature(const InitialInfo
LOG_INFO("Waiting for Pairing Response");
auto response = WaitPairingResponse();
- /* There is a potential collision where the peripheral initiates the pairing at the same time we initiate it, by
- * sending security request. */
+ /* There is a potential collision where the slave initiates the pairing at the same time we initiate it, by sending
+ * security request. */
if (std::holds_alternative<PairingFailure>(response) &&
std::get<PairingFailure>(response).received_code_ == Code::SECURITY_REQUEST) {
LOG_INFO("Received security request, waiting for Pairing Response again...");
@@ -266,7 +222,7 @@ Phase1ResultOrFailure PairingHandlerLe::ExchangePairingFeature(const InitialInfo
if (i.remotely_initiated) {
if (!i.pairing_request.has_value()) {
- return PairingFailure("You must pass PairingRequest as a initial information to peripheral!");
+ return PairingFailure("You must pass PairingRequest as a initial information to slave!");
}
pairing_request = i.pairing_request.value();
@@ -286,13 +242,6 @@ Phase1ResultOrFailure PairingHandlerLe::ExchangePairingFeature(const InitialInfo
pairing_request = std::get<PairingRequestView>(request);
}
- uint8_t key_size = pairing_request->GetMaximumEncryptionKeySize();
- if (key_size < 7 || key_size > 16) {
- LOG_WARN("Resulting key size is bad %d", key_size);
- SendL2capPacket(i, PairingFailedBuilder::Create(PairingFailedReason::ENCRYPTION_KEY_SIZE));
- return PairingFailure("Resulting key size is bad", PairingFailedReason::ENCRYPTION_KEY_SIZE);
- }
-
// Send Pairing Request
const auto& x = i.myPairingCapabilities;
// basically pairing_response_builder = my_first_packet;
@@ -324,9 +273,9 @@ DistributedKeysOrFailure PairingHandlerLe::DistributeKeys(const InitialInformati
const PairingResponseView& pairing_response,
bool isSecureConnections) {
uint8_t keys_i_receive =
- IAmCentral(i) ? pairing_response.GetResponderKeyDistribution() : pairing_response.GetInitiatorKeyDistribution();
+ IAmMaster(i) ? pairing_response.GetResponderKeyDistribution() : pairing_response.GetInitiatorKeyDistribution();
uint8_t keys_i_send =
- IAmCentral(i) ? pairing_response.GetInitiatorKeyDistribution() : pairing_response.GetResponderKeyDistribution();
+ IAmMaster(i) ? pairing_response.GetInitiatorKeyDistribution() : pairing_response.GetResponderKeyDistribution();
// In Secure Connections on the LE Transport, the EncKey field shall be ignored
if (isSecureConnections) {
@@ -334,20 +283,19 @@ DistributedKeysOrFailure PairingHandlerLe::DistributeKeys(const InitialInformati
keys_i_receive = (~KeyMaskEnc) & keys_i_receive;
}
- LOG_INFO("Key distribution start, keys_i_send=0x%02x, keys_i_receive=0x%02x", keys_i_send, keys_i_receive);
+ LOG_INFO("Key distribution start, keys_i_send=%02x, keys_i_receive=%02x", keys_i_send, keys_i_receive);
- // TODO: obtain actual values, and apply key_size to the LTK
- Octet16 my_ltk = bluetooth::os::GenerateRandom<16>();
- uint16_t my_ediv = bluetooth::os::GenerateRandom();
- std::array<uint8_t, 8> my_rand = bluetooth::os::GenerateRandom<8>();
+ // TODO: obtain actual values!
+ Octet16 my_ltk = {0};
+ uint16_t my_ediv{0};
+ std::array<uint8_t, 8> my_rand = {0};
- Octet16 my_irk = i.my_identity_resolving_key;
- Address my_identity_address = i.my_identity_address.GetAddress();
- AddrType my_identity_address_type =
- static_cast<bluetooth::security::AddrType>(i.my_identity_address.GetAddressType());
+ Octet16 my_irk = {0x01};
+ Address my_identity_address;
+ AddrType my_identity_address_type = AddrType::PUBLIC;
Octet16 my_signature_key{0};
- if (IAmCentral(i)) {
+ if (IAmMaster(i)) {
// EncKey is unused for LE Secure Connections
DistributedKeysOrFailure keys = ReceiveKeys(keys_i_receive);
if (std::holds_alternative<PairingFailure>(keys)) {
@@ -356,10 +304,6 @@ DistributedKeysOrFailure PairingHandlerLe::DistributeKeys(const InitialInformati
SendKeys(i, keys_i_send, my_ltk, my_ediv, my_rand, my_irk, my_identity_address, my_identity_address_type,
my_signature_key);
-
- std::get<DistributedKeys>(keys).local_ltk = my_ltk;
- std::get<DistributedKeys>(keys).local_ediv = my_ediv;
- std::get<DistributedKeys>(keys).local_rand = my_rand;
LOG_INFO("Key distribution finish");
return keys;
} else {
@@ -370,10 +314,6 @@ DistributedKeysOrFailure PairingHandlerLe::DistributeKeys(const InitialInformati
if (std::holds_alternative<PairingFailure>(keys)) {
return keys;
}
-
- std::get<DistributedKeys>(keys).local_ltk = my_ltk;
- std::get<DistributedKeys>(keys).local_ediv = my_ediv;
- std::get<DistributedKeys>(keys).local_rand = my_rand;
LOG_INFO("Key distribution finish");
return keys;
}
@@ -383,7 +323,8 @@ DistributedKeysOrFailure PairingHandlerLe::ReceiveKeys(const uint8_t& keys_i_rec
std::optional<Octet16> ltk; /* Legacy only */
std::optional<uint16_t> ediv; /* Legacy only */
std::optional<std::array<uint8_t, 8>> rand; /* Legacy only */
- std::optional<hci::AddressWithType> identity_address;
+ std::optional<Address> identity_address;
+ AddrType identity_address_type;
std::optional<Octet16> irk;
std::optional<Octet16> signature_key;
@@ -398,13 +339,13 @@ DistributedKeysOrFailure PairingHandlerLe::ReceiveKeys(const uint8_t& keys_i_rec
}
{
- auto packet = WaitCentralIdentification();
+ auto packet = WaitMasterIdentification();
if (std::holds_alternative<PairingFailure>(packet)) {
- LOG_ERROR(" Was expecting Central Identification but did not receive!");
+ LOG_ERROR(" Was expecting Master Identification but did not receive!");
return std::get<PairingFailure>(packet);
}
- ediv = std::get<CentralIdentificationView>(packet).GetEdiv();
- rand = std::get<CentralIdentificationView>(packet).GetRand();
+ ediv = std::get<MasterIdentificationView>(packet).GetEdiv();
+ rand = std::get<MasterIdentificationView>(packet).GetRand();
}
}
@@ -426,10 +367,8 @@ DistributedKeysOrFailure PairingHandlerLe::ReceiveKeys(const uint8_t& keys_i_rec
return std::get<PairingFailure>(iapacket);
}
LOG_INFO("Received Identity Address Information");
- auto iapacketview = std::get<IdentityAddressInformationView>(iapacket);
- identity_address = hci::AddressWithType(iapacketview.GetBdAddr(), iapacketview.GetAddrType() == AddrType::PUBLIC
- ? hci::AddressType::PUBLIC_DEVICE_ADDRESS
- : hci::AddressType::RANDOM_DEVICE_ADDRESS);
+ identity_address = std::get<IdentityAddressInformationView>(iapacket).GetBdAddr();
+ identity_address_type = std::get<IdentityAddressInformationView>(iapacket).GetAddrType();
}
if (keys_i_receive & KeyMaskSign) {
@@ -443,12 +382,7 @@ DistributedKeysOrFailure PairingHandlerLe::ReceiveKeys(const uint8_t& keys_i_rec
signature_key = std::get<SigningInformationView>(packet).GetSignatureKey();
}
- return DistributedKeys{.remote_ltk = ltk,
- .remote_ediv = ediv,
- .remote_rand = rand,
- .remote_identity_address = identity_address,
- .remote_irk = irk,
- .remote_signature_key = signature_key};
+ return DistributedKeys{ltk, ediv, rand, identity_address, identity_address_type, irk, signature_key};
}
void PairingHandlerLe::SendKeys(const InitialInformations& i, const uint8_t& keys_i_send, Octet16 ltk, uint16_t ediv,
@@ -457,8 +391,8 @@ void PairingHandlerLe::SendKeys(const InitialInformations& i, const uint8_t& key
if (keys_i_send & KeyMaskEnc) {
LOG_INFO("Sending Encryption Information");
SendL2capPacket(i, EncryptionInformationBuilder::Create(ltk));
- LOG_INFO("Sending Central Identification");
- SendL2capPacket(i, CentralIdentificationBuilder::Create(ediv, rand));
+ LOG_INFO("Sending Master Identification");
+ SendL2capPacket(i, MasterIdentificationBuilder::Create(ediv, rand));
}
if (keys_i_send & KeyMaskId) {
diff --git a/gd/security/pairing_handler_le.h b/gd/security/pairing_handler_le.h
index 051ce34c8..cbc87fabe 100644
--- a/gd/security/pairing_handler_le.h
+++ b/gd/security/pairing_handler_le.h
@@ -68,7 +68,7 @@ class PairingEvent {
std::optional<CommandView> l2cap_packet;
- std::optional<hci::EventView> hci_event;
+ std::optional<hci::EventPacketView> hci_event;
enum UI_ACTION_TYPE { PAIRING_ACCEPTED, CONFIRM_YESNO, PASSKEY };
UI_ACTION_TYPE ui_action;
@@ -77,7 +77,7 @@ class PairingEvent {
PairingEvent(TYPE type) : type(type) {}
PairingEvent(CommandView l2cap_packet) : type(L2CAP), l2cap_packet(l2cap_packet) {}
PairingEvent(UI_ACTION_TYPE ui_action, uint32_t ui_value) : type(UI), ui_action(ui_action), ui_value(ui_value) {}
- PairingEvent(hci::EventView hci_event) : type(HCI_EVENT), hci_event(hci_event) {}
+ PairingEvent(hci::EventPacketView hci_event) : type(HCI_EVENT), hci_event(hci_event) {}
};
constexpr int SMP_TIMEOUT = 30;
@@ -136,19 +136,14 @@ class PairingHandlerLe {
void SendHciLeStartEncryption(const InitialInformations& i, uint16_t conn_handle, const std::array<uint8_t, 8>& rand,
const uint16_t& ediv, const Octet16& ltk) {
i.le_security_interface->EnqueueCommand(hci::LeStartEncryptionBuilder::Create(conn_handle, rand, ediv, ltk),
- i.l2cap_handler->BindOnce([](hci::CommandStatusView) {
+ common::BindOnce([](hci::CommandStatusView) {
// TODO: handle command status. It's important - can show we are not
// connected any more.
// TODO: if anything useful must be done there, use some sort of proper
// handler, wait/notify, and execute on the handler thread
- }));
- }
-
- void SendHciLeLongTermKeyReply(const InitialInformations& i, uint16_t conn_handle, const Octet16& ltk) {
- i.le_security_interface->EnqueueCommand(
- hci::LeLongTermKeyRequestReplyBuilder::Create(conn_handle, ltk),
- i.l2cap_handler->BindOnce([](hci::CommandCompleteView) {}));
+ }),
+ i.l2cap_handler);
}
std::variant<PairingFailure, EncryptionChangeView, EncryptionKeyRefreshCompleteView> WaitEncryptionChanged() {
@@ -176,38 +171,20 @@ class PairingHandlerLe {
return PairingFailure("Was expecting Encryption Change or Key Refresh Complete but received something else");
}
- std::variant<PairingFailure, hci::LeLongTermKeyRequestView> WaitLeLongTermKeyRequest() {
- PairingEvent e = WaitForEvent();
- if (e.type != PairingEvent::HCI_EVENT) return PairingFailure("Was expecting HCI event but received something else");
-
- if (!e.hci_event->IsValid()) return PairingFailure("Received invalid HCI event");
-
- if (e.hci_event->GetEventCode() != hci::EventCode::LE_META_EVENT) return PairingFailure("Was expecting LE event");
-
- hci::LeMetaEventView le_event = hci::LeMetaEventView::Create(*e.hci_event);
- if (!le_event.IsValid()) {
- return PairingFailure("Invalid LE Event received");
- }
-
- if (le_event.GetSubeventCode() != hci::SubeventCode::LONG_TERM_KEY_REQUEST) {
- return PairingFailure("Was expecting Long Term Key Request");
- }
-
- hci::LeLongTermKeyRequestView ltk_req_packet = hci::LeLongTermKeyRequestView::Create(le_event);
- if (!ltk_req_packet.IsValid()) {
- return PairingFailure("Invalid LE Long Term Key Request received");
- }
-
- return ltk_req_packet;
- }
-
- inline bool IAmCentral(const InitialInformations& i) {
- return i.my_role == hci::Role::CENTRAL;
+ inline bool IAmMaster(const InitialInformations& i) {
+ return i.my_role == hci::Role::MASTER;
}
/* This function generates data that should be passed to remote device, except
the private key. */
- static MyOobData GenerateOobData();
+ static MyOobData GenerateOobData() {
+ MyOobData data;
+ std::tie(data.private_key, data.public_key) = GenerateECDHKeyPair();
+
+ data.r = GenerateRandom<16>();
+ data.c = crypto_toolbox::f4(data.public_key.x.data(), data.public_key.x.data(), data.r, 0);
+ return data;
+ }
std::variant<PairingFailure, KeyExchangeResult> ExchangePublicKeys(const InitialInformations& i,
OobDataFlag remote_have_oob_data);
@@ -273,7 +250,7 @@ class PairingHandlerLe {
}
/* SMP Command received from remote device */
- void OnHciEvent(hci::EventView hci_event) {
+ void OnHciEvent(hci::EventPacketView hci_event) {
{
std::unique_lock<std::mutex> lock(queue_guard);
queue.push(PairingEvent(std::move(hci_event)));
@@ -290,15 +267,6 @@ class PairingHandlerLe {
pairing_thread_blocker_.notify_one();
}
- /* HCI LE event received from remote device */
- void OnHciLeEvent(hci::LeMetaEventView hci_event) {
- {
- std::unique_lock<std::mutex> lock(queue_guard);
- queue.push(PairingEvent(std::move(hci_event)));
- }
- pairing_thread_blocker_.notify_one();
- }
-
/* Blocks the pairing process until some external interaction, or timeout happens */
PairingEvent WaitForEvent() {
std::unique_lock<std::mutex> lock(queue_guard);
@@ -336,32 +304,6 @@ class PairingHandlerLe {
std::optional<PairingEvent> WaitUiPasskey() {
PairingEvent e = WaitForEvent();
-
- // It's possible to receive PAIRING_CONFIRM from remote device while waiting for the passkey.
- // Store it until it's needed.
- if (e.type == PairingEvent::L2CAP) {
- auto l2cap_packet = e.l2cap_packet.value();
- if (!l2cap_packet.IsValid()) {
- LOG_WARN("Malformed L2CAP packet received!");
- return std::nullopt;
- }
-
- const auto& received_code = l2cap_packet.GetCode();
- if (received_code != Code::PAIRING_CONFIRM) {
- LOG_WARN("Was waiting for passkey, received bad packet instead!");
- return std::nullopt;
- }
-
- auto pkt = PairingConfirmView::Create(l2cap_packet);
- if (!pkt.IsValid()) {
- LOG_WARN("Malformed PAIRING_CONFIRM packet");
- return std::nullopt;
- }
-
- cached_pariring_confirm_view = std::make_unique<PairingConfirmView>(pkt);
- e = WaitForEvent();
- }
-
if (e.type == PairingEvent::UI & e.ui_action == PairingEvent::PASSKEY) {
return e;
} else {
@@ -396,8 +338,8 @@ class PairingHandlerLe {
typedef EncryptionInformationView type;
};
template <>
- struct CodeToPacketView<Code::CENTRAL_IDENTIFICATION> {
- typedef CentralIdentificationView type;
+ struct CodeToPacketView<Code::MASTER_IDENTIFICATION> {
+ typedef MasterIdentificationView type;
};
template <>
struct CodeToPacketView<Code::IDENTITY_INFORMATION> {
@@ -481,12 +423,7 @@ class PairingHandlerLe {
return WaitPacket<Code::PAIRING_RESPONSE>();
}
- std::variant<bluetooth::security::PairingConfirmView, bluetooth::security::PairingFailure> WaitPairingConfirm() {
- if (cached_pariring_confirm_view) {
- PairingConfirmView pkt = *cached_pariring_confirm_view;
- cached_pariring_confirm_view.release();
- return pkt;
- }
+ auto WaitPairingConfirm() {
return WaitPacket<Code::PAIRING_CONFIRM>();
}
@@ -510,8 +447,8 @@ class PairingHandlerLe {
return WaitPacket<Code::ENCRYPTION_INFORMATION>();
}
- auto WaitCentralIdentification() {
- return WaitPacket<Code::CENTRAL_IDENTIFICATION>();
+ auto WaitMasterIdentification() {
+ return WaitPacket<Code::MASTER_IDENTIFICATION>();
}
auto WaitIdentityInformation() {
@@ -526,6 +463,23 @@ class PairingHandlerLe {
return WaitPacket<Code::SIGNING_INFORMATION>();
}
+ template <size_t SIZE>
+ static std::array<uint8_t, SIZE> GenerateRandom() {
+ // TODO: We need a proper random number generator here.
+ // use current time as seed for random generator
+ std::srand(std::time(nullptr));
+ std::array<uint8_t, SIZE> r;
+ for (size_t i = 0; i < SIZE; i++) r[i] = std::rand();
+ return r;
+ }
+
+ uint32_t GenerateRandom() {
+ // TODO: We need a proper random number generator here.
+ // use current time as seed for random generator
+ std::srand(std::time(nullptr));
+ return std::rand();
+ }
+
/* This is just for test, never use in production code! */
void WaitUntilPairingFinished() {
thread_.join();
@@ -538,9 +492,6 @@ class PairingHandlerLe {
std::queue<PairingEvent> queue;
std::thread thread_;
-
- // holds pairing_confirm, if received out of order
- std::unique_ptr<PairingConfirmView> cached_pariring_confirm_view;
};
} // namespace security
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/gd/security/pairing_handler_le_legacy.cc b/gd/security/pairing_handler_le_legacy.cc
index 5d4a05b9f..93a1a8aeb 100644
--- a/gd/security/pairing_handler_le_legacy.cc
+++ b/gd/security/pairing_handler_le_legacy.cc
@@ -18,10 +18,6 @@
#include "security/pairing_handler_le.h"
-#include "os/rand.h"
-
-using bluetooth::os::GenerateRandom;
-
namespace bluetooth {
namespace security {
@@ -35,8 +31,8 @@ LegacyStage1ResultOrFailure PairingHandlerLe::DoLegacyStage1(const InitialInform
if (pairing_request.GetOobDataFlag() == OobDataFlag::PRESENT &&
pairing_response.GetOobDataFlag() == OobDataFlag::PRESENT) {
- // OobDataFlag remote_oob_flag = IAmCentral(i) ? pairing_response.GetOobDataFlag() :
- // pairing_request.GetOobDataFlag(); OobDataFlag my_oob_flag = IAmCentral(i) ? pairing_request.GetOobDataFlag() :
+ // OobDataFlag remote_oob_flag = IAmMaster(i) ? pairing_response.GetOobDataFlag() :
+ // pairing_request.GetOobDataFlag(); OobDataFlag my_oob_flag = IAmMaster(i) ? pairing_request.GetOobDataFlag() :
// pairing_response.GetOobDataFlag();
return LegacyOutOfBand(i);
}
@@ -56,8 +52,8 @@ LegacyStage1ResultOrFailure PairingHandlerLe::DoLegacyStage1(const InitialInform
// This if() should not be needed, these are only combinations left.
if (iom == IoCapability::KEYBOARD_DISPLAY || iom == IoCapability::KEYBOARD_ONLY ||
ios == IoCapability::KEYBOARD_DISPLAY || ios == IoCapability::KEYBOARD_ONLY) {
- IoCapability my_iocaps = IAmCentral(i) ? iom : ios;
- IoCapability remote_iocaps = IAmCentral(i) ? ios : iom;
+ IoCapability my_iocaps = IAmMaster(i) ? iom : ios;
+ IoCapability remote_iocaps = IAmMaster(i) ? ios : iom;
return LegacyPasskeyEntry(i, my_iocaps, remote_iocaps);
}
@@ -76,8 +72,8 @@ LegacyStage1ResultOrFailure PairingHandlerLe::LegacyPasskeyEntry(const InitialIn
bool i_am_displaying = false;
if (my_iocaps == IoCapability::DISPLAY_ONLY || my_iocaps == IoCapability::DISPLAY_YES_NO) {
i_am_displaying = true;
- } else if (
- IAmCentral(i) && remote_iocaps == IoCapability::KEYBOARD_DISPLAY && my_iocaps == IoCapability::KEYBOARD_DISPLAY) {
+ } else if (IAmMaster(i) && remote_iocaps == IoCapability::KEYBOARD_DISPLAY &&
+ my_iocaps == IoCapability::KEYBOARD_DISPLAY) {
i_am_displaying = true;
} else if (my_iocaps == IoCapability::KEYBOARD_DISPLAY && remote_iocaps == IoCapability::KEYBOARD_ONLY) {
i_am_displaying = true;
@@ -93,13 +89,12 @@ LegacyStage1ResultOrFailure PairingHandlerLe::LegacyPasskeyEntry(const InitialIn
constexpr uint32_t PASSKEY_MAX = 999999;
if (passkey > PASSKEY_MAX) passkey >>= 1;
- ConfirmationData data(i.remote_connection_address, i.remote_name, passkey);
- i.user_interface_handler->Post(
- common::BindOnce(&UI::DisplayConfirmValue, common::Unretained(i.user_interface), data));
+ i.user_interface_handler->Post(common::BindOnce(&UI::DisplayConfirmValue, common::Unretained(i.user_interface),
+ i.remote_connection_address, i.remote_name, passkey));
} else {
- ConfirmationData data(i.remote_connection_address, i.remote_name);
- i.user_interface_handler->Post(
- common::BindOnce(&UI::DisplayEnterPasskeyDialog, common::Unretained(i.user_interface), data));
+ i.user_interface_handler->Post(common::BindOnce(&UI::DisplayEnterPasskeyDialog,
+ common::Unretained(i.user_interface), i.remote_connection_address,
+ i.remote_name));
std::optional<PairingEvent> response = WaitUiPasskey();
if (!response) return PairingFailure("Passkey did not arrive!");
@@ -127,57 +122,47 @@ StkOrFailure PairingHandlerLe::DoLegacyStage2(const InitialInformations& i, cons
std::vector<uint8_t> pres(pairing_response.begin(), pairing_response.end());
Octet16 mrand, srand;
- if (IAmCentral(i)) {
+ if (IAmMaster(i)) {
mrand = GenerateRandom<16>();
- // LOG(INFO) << +(IAmCentral(i)) << " tk = " << base::HexEncode(tk.data(), tk.size());
- // LOG(INFO) << +(IAmCentral(i)) << " mrand = " << base::HexEncode(mrand.data(), mrand.size());
- // LOG(INFO) << +(IAmCentral(i)) << " pres = " << base::HexEncode(pres.data(), pres.size());
- // LOG(INFO) << +(IAmCentral(i)) << " preq = " << base::HexEncode(preq.data(), preq.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " tk = " << base::HexEncode(tk.data(), tk.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " mrand = " << base::HexEncode(mrand.data(), mrand.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " pres = " << base::HexEncode(pres.data(), pres.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " preq = " << base::HexEncode(preq.data(), preq.size());
Octet16 mconfirm = crypto_toolbox::c1(
- tk,
- mrand,
- preq.data(),
- pres.data(),
- (uint8_t)i.my_connection_address.GetAddressType(),
- i.my_connection_address.GetAddress().data(),
- (uint8_t)i.remote_connection_address.GetAddressType(),
- i.remote_connection_address.GetAddress().data());
-
- // LOG(INFO) << +(IAmCentral(i)) << " mconfirm = " << base::HexEncode(mconfirm.data(), mconfirm.size());
-
- LOG_INFO("Central sends Mconfirm");
+ tk, mrand, preq.data(), pres.data(), (uint8_t)i.my_connection_address.GetAddressType(),
+ i.my_connection_address.GetAddress().address, (uint8_t)i.remote_connection_address.GetAddressType(),
+ i.remote_connection_address.GetAddress().address);
+
+ // LOG(INFO) << +(IAmMaster(i)) << " mconfirm = " << base::HexEncode(mconfirm.data(), mconfirm.size());
+
+ LOG_INFO("Master sends Mconfirm");
SendL2capPacket(i, PairingConfirmBuilder::Create(mconfirm));
- LOG_INFO("Central waits for the Sconfirm");
+ LOG_INFO("Master waits for the Sconfirm");
auto sconfirm_pkt = WaitPairingConfirm();
if (std::holds_alternative<PairingFailure>(sconfirm_pkt)) {
return std::get<PairingFailure>(sconfirm_pkt);
}
Octet16 sconfirm = std::get<PairingConfirmView>(sconfirm_pkt).GetConfirmValue();
- LOG_INFO("Central sends Mrand");
+ LOG_INFO("Master sends Mrand");
SendL2capPacket(i, PairingRandomBuilder::Create(mrand));
- LOG_INFO("Central waits for Srand");
+ LOG_INFO("Master waits for Srand");
auto random_pkt = WaitPairingRandom();
if (std::holds_alternative<PairingFailure>(random_pkt)) {
return std::get<PairingFailure>(random_pkt);
}
srand = std::get<PairingRandomView>(random_pkt).GetRandomValue();
- // LOG(INFO) << +(IAmCentral(i)) << " srand = " << base::HexEncode(srand.data(), srand.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " srand = " << base::HexEncode(srand.data(), srand.size());
Octet16 sconfirm_generated = crypto_toolbox::c1(
- tk,
- srand,
- preq.data(),
- pres.data(),
- (uint8_t)i.my_connection_address.GetAddressType(),
- i.my_connection_address.GetAddress().data(),
- (uint8_t)i.remote_connection_address.GetAddressType(),
- i.remote_connection_address.GetAddress().data());
+ tk, srand, preq.data(), pres.data(), (uint8_t)i.my_connection_address.GetAddressType(),
+ i.my_connection_address.GetAddress().address, (uint8_t)i.remote_connection_address.GetAddressType(),
+ i.remote_connection_address.GetAddress().address);
if (sconfirm != sconfirm_generated) {
LOG_INFO("sconfirm does not match generated value");
@@ -192,26 +177,21 @@ StkOrFailure PairingHandlerLe::DoLegacyStage2(const InitialInformations& i, cons
std::vector<uint8_t> pres(pairing_response.begin(), pairing_response.end());
Octet16 sconfirm = crypto_toolbox::c1(
- tk,
- srand,
- preq.data(),
- pres.data(),
- (uint8_t)i.remote_connection_address.GetAddressType(),
- i.remote_connection_address.GetAddress().data(),
- (uint8_t)i.my_connection_address.GetAddressType(),
- i.my_connection_address.GetAddress().data());
-
- LOG_INFO("Peripheral waits for the Mconfirm");
+ tk, srand, preq.data(), pres.data(), (uint8_t)i.remote_connection_address.GetAddressType(),
+ i.remote_connection_address.GetAddress().address, (uint8_t)i.my_connection_address.GetAddressType(),
+ i.my_connection_address.GetAddress().address);
+
+ LOG_INFO("Slave waits for the Mconfirm");
auto mconfirm_pkt = WaitPairingConfirm();
if (std::holds_alternative<PairingFailure>(mconfirm_pkt)) {
return std::get<PairingFailure>(mconfirm_pkt);
}
Octet16 mconfirm = std::get<PairingConfirmView>(mconfirm_pkt).GetConfirmValue();
- LOG_INFO("Peripheral sends Sconfirm");
+ LOG_INFO("Slave sends Sconfirm");
SendL2capPacket(i, PairingConfirmBuilder::Create(sconfirm));
- LOG_INFO("Peripheral waits for Mrand");
+ LOG_INFO("Slave waits for Mrand");
auto random_pkt = WaitPairingRandom();
if (std::holds_alternative<PairingFailure>(random_pkt)) {
return std::get<PairingFailure>(random_pkt);
@@ -219,14 +199,9 @@ StkOrFailure PairingHandlerLe::DoLegacyStage2(const InitialInformations& i, cons
mrand = std::get<PairingRandomView>(random_pkt).GetRandomValue();
Octet16 mconfirm_generated = crypto_toolbox::c1(
- tk,
- mrand,
- preq.data(),
- pres.data(),
- (uint8_t)i.remote_connection_address.GetAddressType(),
- i.remote_connection_address.GetAddress().data(),
- (uint8_t)i.my_connection_address.GetAddressType(),
- i.my_connection_address.GetAddress().data());
+ tk, mrand, preq.data(), pres.data(), (uint8_t)i.remote_connection_address.GetAddressType(),
+ i.remote_connection_address.GetAddress().address, (uint8_t)i.my_connection_address.GetAddressType(),
+ i.my_connection_address.GetAddress().address);
if (mconfirm != mconfirm_generated) {
LOG_INFO("mconfirm does not match generated value");
@@ -234,7 +209,7 @@ StkOrFailure PairingHandlerLe::DoLegacyStage2(const InitialInformations& i, cons
return PairingFailure("mconfirm does not match generated value");
}
- LOG_INFO("Peripheral sends Srand");
+ LOG_INFO("Slave sends Srand");
SendL2capPacket(i, PairingRandomBuilder::Create(srand));
}
@@ -244,4 +219,4 @@ StkOrFailure PairingHandlerLe::DoLegacyStage2(const InitialInformations& i, cons
return crypto_toolbox::s1(tk, mrand, srand);
}
} // namespace security
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/gd/security/pairing_handler_le_secure_connections.cc b/gd/security/pairing_handler_le_secure_connections.cc
index 778c6438d..1aa7fae6e 100644
--- a/gd/security/pairing_handler_le_secure_connections.cc
+++ b/gd/security/pairing_handler_le_secure_connections.cc
@@ -18,10 +18,6 @@
#include "security/pairing_handler_le.h"
-#include "os/rand.h"
-
-using bluetooth::os::GenerateRandom;
-
namespace bluetooth {
namespace security {
@@ -40,9 +36,9 @@ std::variant<PairingFailure, KeyExchangeResult> PairingHandlerLe::ExchangePublic
return PairingFailure("Can't validate my own public key");
}
- if (IAmCentral(i)) {
+ if (IAmMaster(i)) {
// Send pairing public key
- LOG_INFO("Central sends out public key");
+ LOG_INFO("Master sends out public key");
SendL2capPacket(i, std::move(myPublicKey));
}
@@ -59,11 +55,6 @@ std::variant<PairingFailure, KeyExchangeResult> PairingHandlerLe::ExchangePublic
remote_public_key.y = ppkv.GetPublicKeyY();
LOG_INFO("Received Public key from remote");
- if (public_key.x == remote_public_key.x) {
- LOG_INFO("Remote and local public keys can't match");
- return PairingFailure("Remote and local public keys match");
- }
-
// validate received public key
if (!ValidateECDHPoint(remote_public_key)) {
// TODO: Spec is unclear what should happend when the point is not on
@@ -74,8 +65,8 @@ std::variant<PairingFailure, KeyExchangeResult> PairingHandlerLe::ExchangePublic
return PairingFailure("Can't validate remote public key");
}
- if (!IAmCentral(i)) {
- LOG_INFO("Peripheral sends out public key");
+ if (!IAmMaster(i)) {
+ LOG_INFO("Slave sends out public key");
// Send pairing public key
SendL2capPacket(i, std::move(myPublicKey));
}
@@ -84,8 +75,8 @@ std::variant<PairingFailure, KeyExchangeResult> PairingHandlerLe::ExchangePublic
std::array<uint8_t, 32> dhkey = ComputeDHKey(private_key, remote_public_key);
- const EcdhPublicKey& PKa = IAmCentral(i) ? public_key : remote_public_key;
- const EcdhPublicKey& PKb = IAmCentral(i) ? remote_public_key : public_key;
+ const EcdhPublicKey& PKa = IAmMaster(i) ? public_key : remote_public_key;
+ const EcdhPublicKey& PKb = IAmMaster(i) ? remote_public_key : public_key;
return KeyExchangeResult{PKa, PKb, dhkey};
}
@@ -94,16 +85,15 @@ Stage1ResultOrFailure PairingHandlerLe::DoSecureConnectionsStage1(const InitialI
const EcdhPublicKey& PKa, const EcdhPublicKey& PKb,
const PairingRequestView& pairing_request,
const PairingResponseView& pairing_response) {
- if (((pairing_request.GetAuthReq() & AuthReqMaskMitm) == 0) &&
- ((pairing_response.GetAuthReq() & AuthReqMaskMitm) == 0)) {
+ if ((pairing_request.GetAuthReq() & pairing_response.GetAuthReq() & AuthReqMaskMitm) == 0) {
// If both devices have not set MITM option, Just Works shall be used
return SecureConnectionsJustWorks(i, PKa, PKb);
}
if (pairing_request.GetOobDataFlag() == OobDataFlag::PRESENT ||
pairing_response.GetOobDataFlag() == OobDataFlag::PRESENT) {
- OobDataFlag remote_oob_flag = IAmCentral(i) ? pairing_response.GetOobDataFlag() : pairing_request.GetOobDataFlag();
- OobDataFlag my_oob_flag = IAmCentral(i) ? pairing_request.GetOobDataFlag() : pairing_response.GetOobDataFlag();
+ OobDataFlag remote_oob_flag = IAmMaster(i) ? pairing_response.GetOobDataFlag() : pairing_request.GetOobDataFlag();
+ OobDataFlag my_oob_flag = IAmMaster(i) ? pairing_request.GetOobDataFlag() : pairing_response.GetOobDataFlag();
return SecureConnectionsOutOfBand(i, PKa, PKb, my_oob_flag, remote_oob_flag);
}
@@ -124,8 +114,8 @@ Stage1ResultOrFailure PairingHandlerLe::DoSecureConnectionsStage1(const InitialI
return SecureConnectionsJustWorks(i, PKa, PKb);
}
- IoCapability my_iocaps = IAmCentral(i) ? iom : ios;
- IoCapability remote_iocaps = IAmCentral(i) ? ios : iom;
+ IoCapability my_iocaps = IAmMaster(i) ? iom : ios;
+ IoCapability remote_iocaps = IAmMaster(i) ? ios : iom;
return SecureConnectionsPasskeyEntry(i, PKa, PKb, my_iocaps, remote_iocaps);
}
@@ -143,15 +133,15 @@ Stage2ResultOrFailure PairingHandlerLe::DoSecureConnectionsStage2(const InitialI
uint8_t a[7];
uint8_t b[7];
- if (IAmCentral(i)) {
- memcpy(a, i.my_connection_address.GetAddress().data(), hci::Address::kLength);
+ if (IAmMaster(i)) {
+ memcpy(a, i.my_connection_address.GetAddress().address, 6);
a[6] = (uint8_t)i.my_connection_address.GetAddressType();
- memcpy(b, i.remote_connection_address.GetAddress().data(), hci::Address::kLength);
+ memcpy(b, i.remote_connection_address.GetAddress().address, 6);
b[6] = (uint8_t)i.remote_connection_address.GetAddressType();
} else {
- memcpy(a, i.remote_connection_address.GetAddress().data(), hci::Address::kLength);
+ memcpy(a, i.remote_connection_address.GetAddress().address, 6);
a[6] = (uint8_t)i.remote_connection_address.GetAddressType();
- memcpy(b, i.my_connection_address.GetAddress().data(), hci::Address::kLength);
+ memcpy(b, i.my_connection_address.GetAddress().address, 6);
b[6] = (uint8_t)i.my_connection_address.GetAddressType();
}
@@ -165,22 +155,22 @@ Stage2ResultOrFailure PairingHandlerLe::DoSecureConnectionsStage2(const InitialI
std::array<uint8_t, 3> iocapB{static_cast<uint8_t>(pairing_response.GetIoCapability()),
static_cast<uint8_t>(pairing_response.GetOobDataFlag()), pairing_response.GetAuthReq()};
- // LOG(INFO) << +(IAmCentral(i)) << " LTK = " << base::HexEncode(ltk.data(), ltk.size());
- // LOG(INFO) << +(IAmCentral(i)) << " MAC_KEY = " << base::HexEncode(mac_key.data(), mac_key.size());
- // LOG(INFO) << +(IAmCentral(i)) << " Na = " << base::HexEncode(Na.data(), Na.size());
- // LOG(INFO) << +(IAmCentral(i)) << " Nb = " << base::HexEncode(Nb.data(), Nb.size());
- // LOG(INFO) << +(IAmCentral(i)) << " ra = " << base::HexEncode(ra.data(), ra.size());
- // LOG(INFO) << +(IAmCentral(i)) << " rb = " << base::HexEncode(rb.data(), rb.size());
- // LOG(INFO) << +(IAmCentral(i)) << " iocapA = " << base::HexEncode(iocapA.data(), iocapA.size());
- // LOG(INFO) << +(IAmCentral(i)) << " iocapB = " << base::HexEncode(iocapB.data(), iocapB.size());
- // LOG(INFO) << +(IAmCentral(i)) << " a = " << base::HexEncode(a, 7);
- // LOG(INFO) << +(IAmCentral(i)) << " b = " << base::HexEncode(b, 7);
+ // LOG(INFO) << +(IAmMaster(i)) << " LTK = " << base::HexEncode(ltk.data(), ltk.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " MAC_KEY = " << base::HexEncode(mac_key.data(), mac_key.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " Na = " << base::HexEncode(Na.data(), Na.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " Nb = " << base::HexEncode(Nb.data(), Nb.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " ra = " << base::HexEncode(ra.data(), ra.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " rb = " << base::HexEncode(rb.data(), rb.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " iocapA = " << base::HexEncode(iocapA.data(), iocapA.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " iocapB = " << base::HexEncode(iocapB.data(), iocapB.size());
+ // LOG(INFO) << +(IAmMaster(i)) << " a = " << base::HexEncode(a, 7);
+ // LOG(INFO) << +(IAmMaster(i)) << " b = " << base::HexEncode(b, 7);
Octet16 Ea = crypto_toolbox::f6(mac_key, Na, Nb, rb, iocapA.data(), a, b);
Octet16 Eb = crypto_toolbox::f6(mac_key, Nb, Na, ra, iocapB.data(), b, a);
- if (IAmCentral(i)) {
+ if (IAmMaster(i)) {
// send Pairing DHKey Check
SendL2capPacket(i, PairingDhKeyCheckBuilder::Create(Ea));
@@ -233,7 +223,7 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsOutOfBand(const Initial
Octet16 remoteC = i.remote_oob_data->le_sc_c;
Octet16 remoteC2;
- if (IAmCentral(i)) {
+ if (IAmMaster(i)) {
remoteC2 = crypto_toolbox::f4((uint8_t*)Pkb.x.data(), (uint8_t*)Pkb.x.data(), remoteR, 0);
} else {
remoteC2 = crypto_toolbox::f4((uint8_t*)Pka.x.data(), (uint8_t*)Pka.x.data(), remoteR, 0);
@@ -246,14 +236,14 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsOutOfBand(const Initial
}
Octet16 Na, Nb, ra, rb;
- if (IAmCentral(i)) {
+ if (IAmMaster(i)) {
ra = localR;
rb = remoteR;
Na = GenerateRandom<16>();
// Send Pairing Random
SendL2capPacket(i, PairingRandomBuilder::Create(Na));
- LOG_INFO("Central waits for Nb");
+ LOG_INFO("Master waits for Nb");
auto random = WaitPairingRandom();
if (std::holds_alternative<PairingFailure>(random)) {
return std::get<PairingFailure>(random);
@@ -264,7 +254,7 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsOutOfBand(const Initial
rb = localR;
Nb = GenerateRandom<16>();
- LOG_INFO("Peripheral waits for random");
+ LOG_INFO("Slave waits for random");
auto random = WaitPairingRandom();
if (std::holds_alternative<PairingFailure>(random)) {
return std::get<PairingFailure>(random);
@@ -293,13 +283,13 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsPasskeyEntry(const Init
constexpr uint32_t PASSKEY_MAX = 999999;
while (passkey > PASSKEY_MAX) passkey >>= 1;
- ConfirmationData data(i.remote_connection_address, i.remote_name, passkey);
- i.user_interface_handler->Post(common::BindOnce(&UI::DisplayPasskey, common::Unretained(i.user_interface), data));
+ i.user_interface_handler->Post(common::BindOnce(&UI::DisplayPasskey, common::Unretained(i.user_interface),
+ i.remote_connection_address, i.remote_name, passkey));
} else if (my_iocaps == IoCapability::KEYBOARD_ONLY || remote_iocaps == IoCapability::DISPLAY_ONLY) {
- ConfirmationData data(i.remote_connection_address, i.remote_name);
- i.user_interface_handler->Post(
- common::BindOnce(&UI::DisplayEnterPasskeyDialog, common::Unretained(i.user_interface), data));
+ i.user_interface_handler->Post(common::BindOnce(&UI::DisplayEnterPasskeyDialog,
+ common::Unretained(i.user_interface), i.remote_connection_address,
+ i.remote_name));
std::optional<PairingEvent> response = WaitUiPasskey();
if (!response) return PairingFailure("Passkey did not arrive!");
@@ -320,16 +310,16 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsPasskeyEntry(const Init
uint8_t ri = bit_set ? 0x81 : 0x80;
Octet16 Cai, Cbi, Nai, Nbi;
- if (IAmCentral(i)) {
+ if (IAmMaster(i)) {
Nai = GenerateRandom<16>();
Cai = crypto_toolbox::f4((uint8_t*)PKa.x.data(), (uint8_t*)PKb.x.data(), Nai, ri);
// Send Pairing Confirm
- LOG_INFO("Central sends Cai");
+ LOG_INFO("Master sends Cai");
SendL2capPacket(i, PairingConfirmBuilder::Create(Cai));
- LOG_INFO("Central waits for the Cbi");
+ LOG_INFO("Master waits for the Cbi");
auto confirm = WaitPairingConfirm();
if (std::holds_alternative<PairingFailure>(confirm)) {
return std::get<PairingFailure>(confirm);
@@ -339,7 +329,7 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsPasskeyEntry(const Init
// Send Pairing Random
SendL2capPacket(i, PairingRandomBuilder::Create(Nai));
- LOG_INFO("Central waits for Nbi");
+ LOG_INFO("Master waits for Nbi");
auto random = WaitPairingRandom();
if (std::holds_alternative<PairingFailure>(random)) {
return std::get<PairingFailure>(random);
@@ -357,7 +347,7 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsPasskeyEntry(const Init
// Compute confirm
Cbi = crypto_toolbox::f4((uint8_t*)PKb.x.data(), (uint8_t*)PKa.x.data(), Nbi, ri);
- LOG_INFO("Peripheral waits for the Cai");
+ LOG_INFO("Slave waits for the Cai");
auto confirm = WaitPairingConfirm();
if (std::holds_alternative<PairingFailure>(confirm)) {
return std::get<PairingFailure>(confirm);
@@ -365,10 +355,10 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsPasskeyEntry(const Init
Cai = std::get<PairingConfirmView>(confirm).GetConfirmValue();
// Send Pairing Confirm
- LOG_INFO("Peripheral sends confirmation");
+ LOG_INFO("Slave sends confirmation");
SendL2capPacket(i, PairingConfirmBuilder::Create(Cbi));
- LOG_INFO("Peripheral waits for random");
+ LOG_INFO("Slave waits for random");
auto random = WaitPairingRandom();
if (std::holds_alternative<PairingFailure>(random)) {
return std::get<PairingFailure>(random);
@@ -414,9 +404,8 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsNumericComparison(const
uint32_t number_to_display = crypto_toolbox::g2((uint8_t*)PKa.x.data(), (uint8_t*)PKb.x.data(), Na, Nb);
- ConfirmationData data(i.remote_connection_address, i.remote_name, number_to_display);
- i.user_interface_handler->Post(
- common::BindOnce(&UI::DisplayConfirmValue, common::Unretained(i.user_interface), data));
+ i.user_interface_handler->Post(common::BindOnce(&UI::DisplayConfirmValue, common::Unretained(i.user_interface),
+ i.remote_connection_address, i.remote_name, number_to_display));
std::optional<PairingEvent> confirmyesno = WaitUiConfirmYesNo();
if (!confirmyesno || confirmyesno->ui_value == 0) {
@@ -433,9 +422,9 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsJustWorks(const Initial
ra = rb = {0};
- if (IAmCentral(i)) {
+ if (IAmMaster(i)) {
Na = GenerateRandom<16>();
- LOG_INFO("Central waits for confirmation");
+ LOG_INFO("Master waits for confirmation");
auto confirm = WaitPairingConfirm();
if (std::holds_alternative<PairingFailure>(confirm)) {
return std::get<PairingFailure>(confirm);
@@ -445,7 +434,7 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsJustWorks(const Initial
// Send Pairing Random
SendL2capPacket(i, PairingRandomBuilder::Create(Na));
- LOG_INFO("Central waits for Random");
+ LOG_INFO("Master waits for Random");
auto random = WaitPairingRandom();
if (std::holds_alternative<PairingFailure>(random)) {
return std::get<PairingFailure>(random);
@@ -466,10 +455,10 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsJustWorks(const Initial
Cb = crypto_toolbox::f4((uint8_t*)PKb.x.data(), (uint8_t*)PKa.x.data(), Nb, 0);
// Send Pairing Confirm
- LOG_INFO("Peripheral sends confirmation");
+ LOG_INFO("Slave sends confirmation");
SendL2capPacket(i, PairingConfirmBuilder::Create(Cb));
- LOG_INFO("Peripheral waits for random");
+ LOG_INFO("Slave waits for random");
auto random = WaitPairingRandom();
if (std::holds_alternative<PairingFailure>(random)) {
return std::get<PairingFailure>(random);
@@ -484,4 +473,4 @@ Stage1ResultOrFailure PairingHandlerLe::SecureConnectionsJustWorks(const Initial
}
} // namespace security
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/gd/security/pairing_handler_le_unittest.cc b/gd/security/pairing_handler_le_unittest.cc
index 690c080c0..1f585fe9c 100644
--- a/gd/security/pairing_handler_le_unittest.cc
+++ b/gd/security/pairing_handler_le_unittest.cc
@@ -21,7 +21,6 @@
#include <memory>
#include "os/log.h"
-#include "os/rand.h"
#include "security/pairing_handler_le.h"
#include "security/test/mocks.h"
@@ -30,7 +29,6 @@ using ::testing::Eq;
using ::testing::Field;
using ::testing::VariantWith;
-using bluetooth::os::GenerateRandom;
using bluetooth::security::CommandView;
namespace bluetooth {
@@ -47,6 +45,18 @@ CommandView BuilderToView(std::unique_ptr<BasePacketBuilder> builder) {
return CommandView::Create(temp_cmd_view);
}
+std::condition_variable outgoing_l2cap_blocker_;
+std::optional<bluetooth::security::CommandView> outgoing_l2cap_packet_;
+
+bool WaitForOutgoingL2capPacket() {
+ std::mutex mutex;
+ std::unique_lock<std::mutex> lock(mutex);
+ if (outgoing_l2cap_blocker_.wait_for(lock, std::chrono::seconds(5)) == std::cv_status::timeout) {
+ return false;
+ }
+ return true;
+}
+
class PairingResultHandlerMock {
public:
MOCK_CONST_METHOD1(OnPairingFinished, void(PairingResultOrFailure));
@@ -101,42 +111,16 @@ class PairingHandlerUnitTest : public testing::Test {
outgoing_l2cap_blocker_.notify_one();
}
- std::optional<bluetooth::security::CommandView> WaitForOutgoingL2capPacket() {
- std::mutex mutex;
- std::unique_lock<std::mutex> lock(mutex);
-
- // It is possible that we lost wakeup from condition_variable, check if data is already waiting to be processed
- if (outgoing_l2cap_packet_ != std::nullopt) {
- std::optional<bluetooth::security::CommandView> tmp = std::nullopt;
- outgoing_l2cap_packet_.swap(tmp);
- return tmp;
- }
-
- // Data not ready yet, wait for it.
- if (outgoing_l2cap_blocker_.wait_for(lock, std::chrono::seconds(5)) == std::cv_status::timeout) {
- return std::nullopt;
- }
-
- std::optional<bluetooth::security::CommandView> tmp = std::nullopt;
- outgoing_l2cap_packet_.swap(tmp);
- return tmp;
- }
-
public:
os::Thread* thread_;
os::Handler* handler_;
std::unique_ptr<common::BidiQueue<packet::PacketView<packet::kLittleEndian>, packet::BasePacketBuilder>> bidi_queue_;
std::unique_ptr<os::EnqueueBuffer<packet::BasePacketBuilder>> up_buffer_;
- std::condition_variable outgoing_l2cap_blocker_;
- std::optional<bluetooth::security::CommandView> outgoing_l2cap_packet_ = std::nullopt;
};
InitialInformations initial_informations{
- .my_role = hci::Role::CENTRAL,
+ .my_role = hci::Role::MASTER,
.my_connection_address = {{}, hci::AddressType::PUBLIC_DEVICE_ADDRESS},
- .my_identity_address = {{}, hci::AddressType::PUBLIC_DEVICE_ADDRESS},
- .my_identity_resolving_key =
- {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f},
.myPairingCapabilities = {.io_capability = IoCapability::NO_INPUT_NO_OUTPUT,
.oob_data_flag = OobDataFlag::NOT_PRESENT,
@@ -160,9 +144,8 @@ TEST_F(PairingHandlerUnitTest, test_phase_1_failure) {
std::unique_ptr<PairingHandlerLe> pairing_handler =
std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, initial_informations);
- std::optional<bluetooth::security::CommandView> pairing_request = WaitForOutgoingL2capPacket();
- EXPECT_TRUE(pairing_request.has_value());
- EXPECT_EQ(pairing_request->GetCode(), Code::PAIRING_REQUEST);
+ EXPECT_TRUE(WaitForOutgoingL2capPacket());
+ EXPECT_EQ(outgoing_l2cap_packet_->GetCode(), Code::PAIRING_REQUEST);
EXPECT_CALL(*pairingResult, OnPairingFinished(VariantWith<PairingFailure>(_))).Times(1);
@@ -171,9 +154,8 @@ TEST_F(PairingHandlerUnitTest, test_phase_1_failure) {
bad_pairing_response.IsValid();
pairing_handler->OnCommandView(bad_pairing_response);
- std::optional<bluetooth::security::CommandView> pairing_failure = WaitForOutgoingL2capPacket();
- EXPECT_TRUE(pairing_failure.has_value());
- EXPECT_EQ(pairing_failure->GetCode(), Code::PAIRING_FAILED);
+ EXPECT_TRUE(WaitForOutgoingL2capPacket());
+ EXPECT_EQ(outgoing_l2cap_packet_->GetCode(), Code::PAIRING_FAILED);
}
TEST_F(PairingHandlerUnitTest, test_secure_connections_just_works) {
@@ -186,10 +168,9 @@ TEST_F(PairingHandlerUnitTest, test_secure_connections_just_works) {
std::unique_ptr<PairingHandlerLe> pairing_handler =
std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, initial_informations);
- std::optional<bluetooth::security::CommandView> pairing_request_pkt = WaitForOutgoingL2capPacket();
- EXPECT_TRUE(pairing_request_pkt.has_value());
- EXPECT_EQ(pairing_request_pkt->GetCode(), Code::PAIRING_REQUEST);
- CommandView pairing_request = pairing_request_pkt.value();
+ EXPECT_TRUE(WaitForOutgoingL2capPacket());
+ EXPECT_EQ(outgoing_l2cap_packet_->GetCode(), Code::PAIRING_REQUEST);
+ CommandView pairing_request = outgoing_l2cap_packet_.value();
auto pairing_response = BuilderToView(
PairingResponseBuilder::Create(IoCapability::KEYBOARD_DISPLAY, OobDataFlag::NOT_PRESENT,
@@ -198,11 +179,10 @@ TEST_F(PairingHandlerUnitTest, test_secure_connections_just_works) {
// Phase 1 finished.
// pairing public key
- std::optional<bluetooth::security::CommandView> public_key_pkt = WaitForOutgoingL2capPacket();
- EXPECT_TRUE(public_key_pkt.has_value());
- EXPECT_EQ(Code::PAIRING_PUBLIC_KEY, public_key_pkt->GetCode());
+ EXPECT_TRUE(WaitForOutgoingL2capPacket());
+ EXPECT_EQ(Code::PAIRING_PUBLIC_KEY, outgoing_l2cap_packet_->GetCode());
EcdhPublicKey my_public_key;
- auto ppkv = PairingPublicKeyView::Create(public_key_pkt.value());
+ auto ppkv = PairingPublicKeyView::Create(outgoing_l2cap_packet_.value());
ppkv.IsValid();
my_public_key.x = ppkv.GetPublicKeyX();
my_public_key.y = ppkv.GetPublicKeyY();
@@ -217,7 +197,7 @@ TEST_F(PairingHandlerUnitTest, test_secure_connections_just_works) {
Octet16 ra, rb;
ra = rb = {0};
- Octet16 Nb = GenerateRandom<16>();
+ Octet16 Nb = PairingHandlerLe::GenerateRandom<16>();
// Compute confirm
Octet16 Cb = crypto_toolbox::f4((uint8_t*)public_key.x.data(), (uint8_t*)my_public_key.x.data(), Nb, 0);
@@ -225,10 +205,9 @@ TEST_F(PairingHandlerUnitTest, test_secure_connections_just_works) {
pairing_handler->OnCommandView(BuilderToView(PairingConfirmBuilder::Create(Cb)));
// random
- std::optional<bluetooth::security::CommandView> random_pkt = WaitForOutgoingL2capPacket();
- EXPECT_TRUE(random_pkt.has_value());
- EXPECT_EQ(Code::PAIRING_RANDOM, random_pkt->GetCode());
- auto prv = PairingRandomView::Create(random_pkt.value());
+ EXPECT_TRUE(WaitForOutgoingL2capPacket());
+ EXPECT_EQ(Code::PAIRING_RANDOM, outgoing_l2cap_packet_->GetCode());
+ auto prv = PairingRandomView::Create(outgoing_l2cap_packet_.value());
prv.IsValid();
Octet16 Na = prv.GetRandomValue();
@@ -237,9 +216,9 @@ TEST_F(PairingHandlerUnitTest, test_secure_connections_just_works) {
// Start of authentication stage 2
uint8_t a[7];
uint8_t b[7];
- memcpy(b, initial_informations.remote_connection_address.GetAddress().data(), hci::Address::kLength);
+ memcpy(b, initial_informations.remote_connection_address.GetAddress().address, 6);
b[6] = (uint8_t)initial_informations.remote_connection_address.GetAddressType();
- memcpy(a, initial_informations.my_connection_address.GetAddress().data(), hci::Address::kLength);
+ memcpy(a, initial_informations.my_connection_address.GetAddress().address, 6);
a[6] = (uint8_t)initial_informations.my_connection_address.GetAddressType();
Octet16 ltk, mac_key;
@@ -258,10 +237,9 @@ TEST_F(PairingHandlerUnitTest, test_secure_connections_just_works) {
Octet16 Ea = crypto_toolbox::f6(mac_key, Na, Nb, rb, iocapA.data(), a, b);
Octet16 Eb = crypto_toolbox::f6(mac_key, Nb, Na, ra, iocapB.data(), b, a);
- std::optional<bluetooth::security::CommandView> dh_key_pkt = WaitForOutgoingL2capPacket();
- EXPECT_TRUE(dh_key_pkt.has_value());
- EXPECT_EQ(Code::PAIRING_DH_KEY_CHECK, dh_key_pkt->GetCode());
- auto pdhkcv = PairingDhKeyCheckView::Create(dh_key_pkt.value());
+ EXPECT_TRUE(WaitForOutgoingL2capPacket());
+ EXPECT_EQ(Code::PAIRING_DH_KEY_CHECK, outgoing_l2cap_packet_->GetCode());
+ auto pdhkcv = PairingDhKeyCheckView::Create(outgoing_l2cap_packet_.value());
pdhkcv.IsValid();
EXPECT_EQ(pdhkcv.GetDhKeyCheck(), Ea);
@@ -272,11 +250,8 @@ TEST_F(PairingHandlerUnitTest, test_secure_connections_just_works) {
}
InitialInformations initial_informations_trsi{
- .my_role = hci::Role::CENTRAL,
+ .my_role = hci::Role::MASTER,
.my_connection_address = hci::AddressWithType(),
- .my_identity_address = {{}, hci::AddressType::PUBLIC_DEVICE_ADDRESS},
- .my_identity_resolving_key =
- {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f},
.myPairingCapabilities = {.io_capability = IoCapability::NO_INPUT_NO_OUTPUT,
.oob_data_flag = OobDataFlag::NOT_PRESENT,
@@ -292,9 +267,9 @@ InitialInformations initial_informations_trsi{
.OnPairingFinished = OnPairingFinished,
};
-/* This test verifies that when remote peripheral device sends security request , and user
+/* This test verifies that when remote slave device sends security request , and user
* does accept the prompt, we do send pairing request */
-TEST_F(PairingHandlerUnitTest, test_remote_peripheral_initiating) {
+TEST_F(PairingHandlerUnitTest, test_remote_slave_initiating) {
initial_informations_trsi.proper_l2cap_interface = up_buffer_.get();
initial_informations_trsi.l2cap_handler = handler_;
initial_informations_trsi.user_interface_handler = handler_;
@@ -305,20 +280,16 @@ TEST_F(PairingHandlerUnitTest, test_remote_peripheral_initiating) {
// Simulate user accepting the pairing in UI
pairing_handler->OnUiAction(PairingEvent::PAIRING_ACCEPTED, 0x01 /* Non-zero value means success */);
- std::optional<bluetooth::security::CommandView> pairing_request_pkt = WaitForOutgoingL2capPacket();
- EXPECT_TRUE(pairing_request_pkt.has_value());
- EXPECT_EQ(Code::PAIRING_REQUEST, pairing_request_pkt->GetCode());
+ EXPECT_TRUE(WaitForOutgoingL2capPacket());
+ EXPECT_EQ(Code::PAIRING_REQUEST, outgoing_l2cap_packet_->GetCode());
// We don't care for the rest of the flow, let it die.
pairing_handler.reset();
}
InitialInformations initial_informations_trmi{
- .my_role = hci::Role::PERIPHERAL,
+ .my_role = hci::Role::SLAVE,
.my_connection_address = hci::AddressWithType(),
- .my_identity_address = {{}, hci::AddressType::PUBLIC_DEVICE_ADDRESS},
- .my_identity_resolving_key =
- {0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f},
.myPairingCapabilities = {.io_capability = IoCapability::NO_INPUT_NO_OUTPUT,
.oob_data_flag = OobDataFlag::NOT_PRESENT,
@@ -329,13 +300,9 @@ InitialInformations initial_informations_trmi{
.remotely_initiated = true,
.remote_connection_address = hci::AddressWithType(),
- .pairing_request = PairingRequestView::Create(BuilderToView(PairingRequestBuilder::Create(
- IoCapability::NO_INPUT_NO_OUTPUT,
- OobDataFlag::NOT_PRESENT,
- AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
- 16,
- 0x03,
- 0x03))),
+ .pairing_request = PairingRequestView::Create(BuilderToView(
+ PairingRequestBuilder::Create(IoCapability::NO_INPUT_NO_OUTPUT, OobDataFlag::NOT_PRESENT,
+ AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc, 16, 0x03, 0x03))),
.user_interface = &uiMock,
.le_security_interface = &leSecurityMock,
@@ -344,7 +311,7 @@ InitialInformations initial_informations_trmi{
/* This test verifies that when remote device sends pairing request, and user does accept the prompt, we do send proper
* reply back */
-TEST_F(PairingHandlerUnitTest, test_remote_central_initiating) {
+TEST_F(PairingHandlerUnitTest, test_remote_master_initiating) {
initial_informations_trmi.proper_l2cap_interface = up_buffer_.get();
initial_informations_trmi.l2cap_handler = handler_;
initial_informations_trmi.user_interface_handler = handler_;
@@ -355,9 +322,8 @@ TEST_F(PairingHandlerUnitTest, test_remote_central_initiating) {
// Simulate user accepting the pairing in UI
pairing_handler->OnUiAction(PairingEvent::PAIRING_ACCEPTED, 0x01 /* Non-zero value means success */);
- std::optional<bluetooth::security::CommandView> pairing_response_pkt = WaitForOutgoingL2capPacket();
- EXPECT_TRUE(pairing_response_pkt.has_value());
- EXPECT_EQ(Code::PAIRING_RESPONSE, pairing_response_pkt->GetCode());
+ EXPECT_TRUE(WaitForOutgoingL2capPacket());
+ EXPECT_EQ(Code::PAIRING_RESPONSE, outgoing_l2cap_packet_->GetCode());
// Phase 1 finished.
// We don't care for the rest of the flow, it's handled in in other tests. let it die.
diff --git a/gd/security/record/Android.bp b/gd/security/record/Android.bp
deleted file mode 100644
index 76334644e..000000000
--- a/gd/security/record/Android.bp
+++ /dev/null
@@ -1,22 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-filegroup {
- name: "BluetoothSecurityRecordSources",
- srcs: [
- "security_record_storage.cc"
- ],
-}
-
-filegroup {
- name: "BluetoothSecurityRecordTestSources",
- srcs: [
- "security_record_storage_test.cc"
- ],
-}
diff --git a/gd/security/record/security_record.h b/gd/security/record/security_record.h
index 1de9f8f13..79f7154c9 100644
--- a/gd/security/record/security_record.h
+++ b/gd/security/record/security_record.h
@@ -18,13 +18,11 @@
#pragma once
-#include <storage/device.h>
#include <memory>
#include <utility>
#include "crypto_toolbox/crypto_toolbox.h"
#include "hci/address_with_type.h"
-#include "storage/device.h"
namespace bluetooth {
namespace security {
@@ -32,7 +30,7 @@ namespace record {
class SecurityRecord {
public:
- explicit SecurityRecord(hci::AddressWithType address) : pseudo_address_(address) {}
+ explicit SecurityRecord(hci::AddressWithType address) : pseudo_address_(address), pairing_(true) {}
SecurityRecord& operator=(const SecurityRecord& other) = default;
@@ -48,6 +46,20 @@ class SecurityRecord {
return IsClassicLinkKeyValid();
}
+ /**
+ * Returns true if Link Keys are stored persistently
+ */
+ bool IsBonded() const {
+ return IsPaired() && persisted_;
+ }
+
+ /**
+ * Called by storage manager once record has persisted
+ */
+ void SetPersisted(bool persisted) {
+ persisted_ = persisted;
+ }
+
void SetLinkKey(std::array<uint8_t, 16> link_key, hci::KeyType key_type) {
link_key_ = link_key;
key_type_ = key_type;
@@ -68,75 +80,32 @@ class SecurityRecord {
return key_type_;
}
- std::optional<hci::AddressWithType> GetPseudoAddress() {
+ hci::AddressWithType GetPseudoAddress() {
return pseudo_address_;
}
- void SetAuthenticated(bool is_authenticated) {
- this->is_authenticated_ = is_authenticated;
- }
-
- bool IsAuthenticated() {
- return this->is_authenticated_;
- }
-
- void SetRequiresMitmProtection(bool requires_mitm_protection) {
- this->requires_mitm_protection_ = requires_mitm_protection;
- }
-
- bool RequiresMitmProtection() {
- return this->requires_mitm_protection_;
- }
-
- void SetIsEncryptionRequired(bool is_encryption_required) {
- this->is_encryption_required_ = is_encryption_required;
- }
-
- bool IsEncryptionRequired() {
- return this->is_encryption_required_;
- }
-
- bool IsClassicLinkKeyValid() const {
- return !std::all_of(link_key_.begin(), link_key_.end(), [](uint8_t b) { return b == 0; });
- }
-
- void SetIsTemporary(bool is_temp) {
- this->is_temporary_ = is_temp;
- }
-
- bool IsTemporary() {
- return this->is_temporary_;
- }
-
private:
+ /* First address we have ever seen this device with, that we used to create bond */
+ hci::AddressWithType pseudo_address_;
std::array<uint8_t, 16> link_key_ = {0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0};
hci::KeyType key_type_ = hci::KeyType::DEBUG_COMBINATION;
- bool is_temporary_ = false;
+ bool IsClassicLinkKeyValid() const {
+ return !std::all_of(link_key_.begin(), link_key_.end(), [](uint8_t b) { return b == 0; });
+ }
+ bool persisted_ = false;
bool pairing_ = false;
- bool is_authenticated_ = false;
- bool requires_mitm_protection_ = false;
- bool is_encryption_required_ = false;
public:
- /* First address we have ever seen this device with, that we used to create bond */
- std::optional<hci::AddressWithType> pseudo_address_;
-
/* Identity Address */
std::optional<hci::AddressWithType> identity_address_;
- std::optional<crypto_toolbox::Octet16> remote_ltk;
- uint8_t key_size;
- uint8_t security_level;
- std::optional<uint16_t> remote_ediv;
- std::optional<std::array<uint8_t, 8>> remote_rand;
- std::optional<crypto_toolbox::Octet16> remote_irk;
- std::optional<crypto_toolbox::Octet16> remote_signature_key;
-
- std::optional<crypto_toolbox::Octet16> local_ltk;
- std::optional<uint16_t> local_ediv;
- std::optional<std::array<uint8_t, 8>> local_rand;
+ std::optional<crypto_toolbox::Octet16> ltk;
+ std::optional<uint16_t> ediv;
+ std::optional<std::array<uint8_t, 8>> rand;
+ std::optional<crypto_toolbox::Octet16> irk;
+ std::optional<crypto_toolbox::Octet16> signature_key;
};
} // namespace record
diff --git a/gd/security/record/security_record_database.h b/gd/security/record/security_record_database.h
deleted file mode 100644
index 0541c5358..000000000
--- a/gd/security/record/security_record_database.h
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <set>
-
-#include "hci/address_with_type.h"
-#include "security/record/security_record.h"
-#include "security/record/security_record_storage.h"
-
-namespace bluetooth {
-namespace security {
-namespace record {
-
-class SecurityRecordDatabase {
- public:
- SecurityRecordDatabase(record::SecurityRecordStorage security_record_storage)
- : security_record_storage_(security_record_storage) {}
-
- using iterator = std::set<std::shared_ptr<SecurityRecord>>::iterator;
-
- std::shared_ptr<SecurityRecord> FindOrCreate(hci::AddressWithType address) {
- auto it = Find(address);
- // Security record check
- if (it != records_.end()) return *it;
-
- // No security record, create one
- auto record_ptr = std::make_shared<SecurityRecord>(address);
- records_.insert(record_ptr);
- return record_ptr;
- }
-
- void Remove(const hci::AddressWithType& address) {
- auto it = Find(address);
-
- // No record exists
- if (it == records_.end()) return;
-
- records_.erase(it);
- security_record_storage_.RemoveDevice(address);
- }
-
- iterator Find(hci::AddressWithType address) {
- for (auto it = records_.begin(); it != records_.end(); ++it) {
- std::shared_ptr<SecurityRecord> record = *it;
- if (record->identity_address_.has_value() && record->identity_address_.value() == address) return it;
- if (record->GetPseudoAddress() == address) return it;
- if (record->remote_irk.has_value() && address.IsRpaThatMatchesIrk(record->remote_irk.value())) return it;
- }
- return records_.end();
- }
-
- void LoadRecordsFromStorage() {
- security_record_storage_.LoadSecurityRecords(&records_);
- }
-
- void SaveRecordsToStorage() {
- security_record_storage_.SaveSecurityRecords(&records_);
- }
-
- std::set<std::shared_ptr<SecurityRecord>> records_;
- record::SecurityRecordStorage security_record_storage_;
-};
-
-} // namespace record
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/record/security_record_storage.cc b/gd/security/record/security_record_storage.cc
deleted file mode 100644
index 257f60ac1..000000000
--- a/gd/security/record/security_record_storage.cc
+++ /dev/null
@@ -1,195 +0,0 @@
-/*
- *
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-#include "security/record/security_record_storage.h"
-
-#include "storage/mutation.h"
-
-namespace bluetooth {
-namespace security {
-namespace record {
-
-namespace {
-void SetClassicData(
- storage::Mutation& mutation, std::shared_ptr<record::SecurityRecord> record, storage::Device& device) {
- if (*device.GetDeviceType() == hci::DeviceType::LE) {
- return;
- }
- if (record->IsClassicLinkKeyValid()) {
- LOG_WARN("Type: %d", static_cast<int>(*device.GetDeviceType()));
- mutation.Add(device.Classic().SetLinkKey(record->GetLinkKey()));
- mutation.Add(device.Classic().SetLinkKeyType(record->GetKeyType()));
- }
-}
-
-void SetLeData(storage::Mutation& mutation, std::shared_ptr<record::SecurityRecord> record, storage::Device& device) {
- if (*device.GetDeviceType() == hci::DeviceType::BR_EDR) {
- return;
- }
-
- auto le_device = device.Le();
-
- if (record->identity_address_) {
- mutation.Add(le_device.SetAddressType(record->identity_address_->GetAddressType()));
- }
-
- if (record->remote_irk) {
- std::array<uint8_t, 23> peerid;
- std::copy_n(record->remote_irk->data(), record->remote_irk->size(), peerid.data());
- peerid[16] = static_cast<uint8_t>(record->identity_address_->GetAddressType());
- std::copy_n(record->identity_address_->GetAddress().data(), 6, peerid.data() + 17);
-
- common::ByteArray<23> byte_array(peerid);
- mutation.Add(le_device.SetPeerId(byte_array.ToString()));
- }
-
- if (record->pseudo_address_) {
- mutation.Add(le_device.SetLegacyPseudoAddress(record->pseudo_address_->GetAddress()));
- }
-
- if (record->remote_ltk) {
- std::array<uint8_t, 28> penc_keys;
-
- std::copy_n(record->remote_ltk->data(), record->remote_ltk->size(), penc_keys.data());
- std::copy_n(record->remote_rand->data(), record->remote_rand->size(), penc_keys.data() + 16);
- uint16_t* ediv_location = (uint16_t*)(penc_keys.data() + 24);
- *ediv_location = *record->remote_ediv;
- penc_keys[26] = record->security_level;
- penc_keys[27] = record->key_size;
-
- common::ByteArray<28> byte_array(penc_keys);
- mutation.Add(le_device.SetPeerEncryptionKeys(byte_array.ToString()));
- }
-
- if (record->remote_signature_key) {
- std::array<uint8_t, 21> psrk_keys;
-
- // four bytes counter, all zeros
- *psrk_keys.data() = 0;
- *(psrk_keys.data() + 1) = 0;
- *(psrk_keys.data() + 2) = 0;
- *(psrk_keys.data() + 3) = 0;
- std::copy_n(record->remote_signature_key->data(), record->remote_signature_key->size(), psrk_keys.data() + 4);
- *(psrk_keys.data() + 20) = record->security_level;
-
- common::ByteArray<21> byte_array(psrk_keys);
- mutation.Add(le_device.SetPeerSignatureResolvingKeys(byte_array.ToString()));
- }
-}
-
-void SetAuthenticationData(storage::Mutation& mutation, std::shared_ptr<record::SecurityRecord> record, storage::Device& device) {
- device.SetIsAuthenticated((record->IsAuthenticated() ? 1 : 0));
- device.SetIsEncryptionRequired((record->IsEncryptionRequired() ? 1 : 0));
- device.SetRequiresMitmProtection(record->RequiresMitmProtection() ? 1 : 0);
-}
-} // namespace
-
-SecurityRecordStorage::SecurityRecordStorage(storage::StorageModule* storage_module, os::Handler* handler)
- : storage_module_(storage_module), handler_(handler) {}
-
-void SecurityRecordStorage::SaveSecurityRecords(std::set<std::shared_ptr<record::SecurityRecord>>* records) {
- for (auto record : *records) {
- if (record->IsTemporary()) continue;
- storage::Device device = storage_module_->GetDeviceByClassicMacAddress(record->GetPseudoAddress()->GetAddress());
- auto mutation = storage_module_->Modify();
-
- if (record->IsClassicLinkKeyValid() && !record->identity_address_) {
- mutation.Add(device.SetDeviceType(hci::DeviceType::BR_EDR));
- } else if (record->IsClassicLinkKeyValid() && record->remote_ltk) {
- mutation.Add(device.SetDeviceType(hci::DeviceType::DUAL));
- } else if (!record->IsClassicLinkKeyValid() && record->remote_ltk) {
- mutation.Add(device.SetDeviceType(hci::DeviceType::LE));
- } else {
- LOG_ERROR(
- "Cannot determine device type from security record for '%s'; dropping!",
- record->GetPseudoAddress()->ToString().c_str());
- continue;
- }
- mutation.Commit();
- SetClassicData(mutation, record, device);
- SetLeData(mutation, record, device);
- SetAuthenticationData(mutation, record, device);
- mutation.Commit();
- }
-}
-
-void SecurityRecordStorage::LoadSecurityRecords(std::set<std::shared_ptr<record::SecurityRecord>>* records) {
- for (auto device : storage_module_->GetBondedDevices()) {
- auto address_type = (device.GetDeviceType() == hci::DeviceType::BR_EDR) ? hci::AddressType::PUBLIC_DEVICE_ADDRESS
- : device.Le().GetAddressType();
- auto address_with_type = hci::AddressWithType(device.GetAddress(), *address_type);
-
- auto record = std::make_shared<record::SecurityRecord>(address_with_type);
- if (device.GetDeviceType() != hci::DeviceType::LE) {
- record->SetLinkKey(device.Classic().GetLinkKey()->bytes, *device.Classic().GetLinkKeyType());
- }
- if (device.GetDeviceType() != hci::DeviceType::BR_EDR) {
- record->pseudo_address_ = std::make_optional<hci::AddressWithType>(
- *device.Le().GetLegacyPseudoAddress(), *device.Le().GetAddressType());
-
- if (device.Le().GetPeerId()) {
- auto peerid = common::ByteArray<23>::FromString(*device.Le().GetPeerId());
- record->remote_irk = std::make_optional<std::array<uint8_t, 16>>();
- std::copy_n(peerid->data(), record->remote_irk->size(), record->remote_irk->data());
-
- uint8_t idaddress_type;
- hci::Address idaddress;
- std::copy_n(peerid->data() + 16, 1, &idaddress_type);
- std::copy_n(peerid->data() + 17, 6, idaddress.data());
- record->identity_address_ =
- std::make_optional<hci::AddressWithType>(idaddress, static_cast<hci::AddressType>(idaddress_type));
- }
-
- if (device.Le().GetPeerEncryptionKeys()) {
- auto peer_encryption_keys = common::ByteArray<28>::FromString(*device.Le().GetPeerEncryptionKeys());
- record->remote_ltk = std::make_optional<std::array<uint8_t, 16>>();
- record->remote_rand = std::make_optional<std::array<uint8_t, 8>>();
- record->remote_ediv = std::make_optional(0);
-
- std::copy_n(peer_encryption_keys->data(), 16, record->remote_ltk->data());
- std::copy_n(peer_encryption_keys->data() + 16, 8, record->remote_rand->data());
- std::copy_n(peer_encryption_keys->data() + 24, 2, &(*record->remote_ediv));
- record->security_level = peer_encryption_keys->data()[26];
- record->key_size = peer_encryption_keys->data()[27];
- }
-
- if (device.Le().GetPeerSignatureResolvingKeys()) {
- auto peer_signature_resolving_keys =
- common::ByteArray<21>::FromString(*device.Le().GetPeerSignatureResolvingKeys());
- record->remote_signature_key = std::make_optional<std::array<uint8_t, 16>>();
-
- std::copy_n(peer_signature_resolving_keys->data() + 4, 16, record->remote_signature_key->data());
- record->security_level = peer_signature_resolving_keys->data()[20];
- }
- }
- record->SetIsEncryptionRequired(device.GetIsEncryptionRequired() == 1 ? true : false);
- record->SetAuthenticated(device.GetIsAuthenticated() == 1 ? true : false);
- record->SetRequiresMitmProtection(device.GetRequiresMitmProtection() == 1 ? true : false);
- records->insert(record);
- }
-}
-
-void SecurityRecordStorage::RemoveDevice(hci::AddressWithType address) {
- storage::Device device = storage_module_->GetDeviceByClassicMacAddress(address.GetAddress());
- auto mutation = storage_module_->Modify();
- mutation.Add(device.RemoveFromConfig());
- mutation.Commit();
-}
-
-} // namespace record
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/record/security_record_storage.h b/gd/security/record/security_record_storage.h
deleted file mode 100644
index 6ad4bad50..000000000
--- a/gd/security/record/security_record_storage.h
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- *
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-#pragma once
-
-#include <unordered_map>
-
-#include "hci/hci_packets.h"
-#include "os/handler.h"
-#include "os/utils.h"
-#include "security/record/security_record.h"
-#include "storage/classic_device.h"
-#include "storage/le_device.h"
-#include "storage/storage_module.h"
-
-namespace bluetooth {
-namespace security {
-namespace record {
-
-#if defined(OS_GENERIC)
-static const char* CONFIG_FILE_PATH = "bt_config.conf";
-#else // !defined(OS_GENERIC)
-static const char* CONFIG_FILE_PATH = "/data/misc/bluedroid/bt_config.conf";
-#endif // defined(OS_GENERIC)
-
-class SecurityRecordStorage {
- public:
- SecurityRecordStorage(storage::StorageModule* storage_module, os::Handler* handler);
-
- /**
- * Iterates through given vector and stores each record's metadata to disk.
- *
- * <p>Job gets posted to the Handler.
- *
- * @param records set of shared pointers to records.
- */
- void SaveSecurityRecords(std::set<std::shared_ptr<record::SecurityRecord>>* records);
-
- /**
- * Reads the record metadata from disk and converts each item into a SecurityRecord.
- *
- * <p>Job gets posted to the Handler.
- *
- * @param records set of shared pointers to records.
- */
- void LoadSecurityRecords(std::set<std::shared_ptr<record::SecurityRecord>>* records);
-
- /**
- * Removes a device from the storage
- *
- * @param address of device to remove
- */
- void RemoveDevice(hci::AddressWithType address);
-
- private:
- storage::StorageModule* storage_module_ __attribute__((unused));
- os::Handler* handler_ __attribute__((unused));
-};
-
-} // namespace record
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/record/security_record_storage_test.cc b/gd/security/record/security_record_storage_test.cc
deleted file mode 100644
index bd1b748dc..000000000
--- a/gd/security/record/security_record_storage_test.cc
+++ /dev/null
@@ -1,206 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-#include "security/record/security_record_storage.h"
-
-#include <gtest/gtest.h>
-
-#include "security/test/fake_storage_module.h"
-
-namespace bluetooth {
-namespace security {
-namespace record {
-namespace {
-
-class DISABLED_SecurityRecordStorageTest : public ::testing::Test {
- protected:
- void SetUp() override {
- // Make Fake storage module
- storage_module_ = new FakeStorageModule();
-
- // Inject
- fake_registry_.InjectTestModule(&storage::StorageModule::Factory, storage_module_);
-
- // Make storage
- record_storage_ = new record::SecurityRecordStorage(storage_module_, handler_);
- }
-
- void TearDown() override {
- synchronize();
- fake_registry_.StopAll();
- delete record_storage_;
- }
-
- void synchronize() {
- fake_registry_.SynchronizeModuleHandler(&FakeStorageModule::Factory, std::chrono::milliseconds(20));
- }
-
- TestModuleRegistry fake_registry_;
- os::Thread& thread_ = fake_registry_.GetTestThread();
- os::Handler* handler_ = nullptr;
- FakeStorageModule* storage_module_;
- record::SecurityRecordStorage* record_storage_;
-};
-
-TEST_F(DISABLED_SecurityRecordStorageTest, setup_teardown) {}
-
-TEST_F(DISABLED_SecurityRecordStorageTest, store_security_record) {
- hci::AddressWithType remote(
- hci::Address({0x01, 0x02, 0x03, 0x04, 0x05, 0x06}), hci::AddressType::PUBLIC_DEVICE_ADDRESS);
- std::array<uint8_t, 16> link_key = {
- 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0};
- std::shared_ptr<record::SecurityRecord> record = std::make_shared<record::SecurityRecord>(remote);
-
- record->SetLinkKey(link_key, hci::KeyType::DEBUG_COMBINATION);
- std::set<std::shared_ptr<record::SecurityRecord>> record_set;
- record_set.insert(record);
- record_storage_->SaveSecurityRecords(&record_set);
-
- auto device = storage_module_->GetDeviceByClassicMacAddress(remote.GetAddress());
- ASSERT_TRUE(device.GetDeviceType());
- ASSERT_EQ(device.Classic().GetLinkKeyType(), record->GetKeyType());
- int i = 0;
- for (i = 0; i < 16; ++i) {
- ASSERT_EQ(link_key[i], device.Classic().GetLinkKey()->bytes[i]);
- }
-}
-
-TEST_F(DISABLED_SecurityRecordStorageTest, store_le_security_record) {
- hci::AddressWithType identity_address(
- hci::Address({0x01, 0x02, 0x03, 0x04, 0x05, 0x06}), hci::AddressType::RANDOM_DEVICE_ADDRESS);
- std::array<uint8_t, 16> remote_ltk{
- 0x07, 0x0c, 0x0e, 0x16, 0x18, 0x55, 0xc6, 0x72, 0x64, 0x5a, 0xd8, 0xb1, 0xf6, 0x93, 0x94, 0xa7};
- uint16_t remote_ediv = 0x28;
- std::array<uint8_t, 8> remote_rand{0x48, 0xac, 0x91, 0xf4, 0xef, 0x6d, 0x41, 0x10};
- std::array<uint8_t, 16> remote_irk{
- 0x66, 0x90, 0x40, 0x76, 0x27, 0x69, 0x57, 0x71, 0x0d, 0x39, 0xf7, 0x80, 0x9e, 0x2f, 0x49, 0xcf};
- std::array<uint8_t, 16> remote_signature_key{
- 0x08, 0x83, 0xae, 0x44, 0xd6, 0x77, 0x9e, 0x90, 0x1d, 0x25, 0xcd, 0xd7, 0xb6, 0xf4, 0x57, 0x85};
- std::shared_ptr<record::SecurityRecord> record = std::make_shared<record::SecurityRecord>(identity_address);
-
- record->identity_address_ = identity_address;
- record->remote_ltk = remote_ltk;
- record->key_size = 16;
- record->security_level = 2;
- record->remote_ediv = remote_ediv;
- record->remote_rand = remote_rand;
- record->remote_irk = remote_irk;
- record->remote_signature_key = remote_signature_key;
-
- std::set<std::shared_ptr<record::SecurityRecord>> record_set;
- record_set.insert(record);
- record_storage_->SaveSecurityRecords(&record_set);
-
- auto device = storage_module_->GetDeviceByClassicMacAddress(identity_address.GetAddress());
- ASSERT_EQ(hci::DeviceType::LE, device.GetDeviceType());
- ASSERT_EQ(device.Le().GetAddressType(), identity_address.GetAddressType());
-
- // IRK, address type, and address glued together
- ASSERT_EQ(*device.Le().GetPeerId(), "66904076276957710d39f7809e2f49cf01010203040506");
-
- // LTK, RAND, EDIV and sec level glued together
- ASSERT_EQ(*device.Le().GetPeerEncryptionKeys(), "070c0e161855c672645ad8b1f69394a748ac91f4ef6d411028000210");
-
- // Counter, signature key, and security level glued together
- ASSERT_EQ(device.Le().GetPeerSignatureResolvingKeys(), "000000000883ae44d6779e901d25cdd7b6f4578502");
-}
-
-TEST_F(DISABLED_SecurityRecordStorageTest, load_security_record) {
- hci::AddressWithType remote(
- hci::Address({0x01, 0x02, 0x03, 0x04, 0x05, 0x06}), hci::AddressType::PUBLIC_DEVICE_ADDRESS);
- std::array<uint8_t, 16> link_key = {
- 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0};
- std::shared_ptr<record::SecurityRecord> record = std::make_shared<record::SecurityRecord>(remote);
-
- record->SetLinkKey(link_key, hci::KeyType::DEBUG_COMBINATION);
- std::set<std::shared_ptr<record::SecurityRecord>> record_set;
- record_set.insert(record);
- record_storage_->SaveSecurityRecords(&record_set);
-
- auto device = storage_module_->GetDeviceByClassicMacAddress(remote.GetAddress());
- ASSERT_TRUE(device.GetDeviceType());
-
- ASSERT_EQ(device.Classic().GetLinkKeyType(), record->GetKeyType());
- int i = 0;
- for (i = 0; i < 16; ++i) {
- ASSERT_EQ(link_key[i], device.Classic().GetLinkKey()->bytes[i]);
- }
-
- record_set.clear();
- record_storage_->LoadSecurityRecords(&record_set);
- record = *record_set.begin();
- link_key = record->GetLinkKey();
-
- ASSERT_EQ(device.Classic().GetLinkKeyType(), record->GetKeyType());
- ASSERT_TRUE(device.GetDeviceType());
- for (i = 0; i < 16; ++i) {
- ASSERT_EQ(link_key[i], device.Classic().GetLinkKey()->bytes[i]);
- }
-}
-
-TEST_F(DISABLED_SecurityRecordStorageTest, dont_save_temporary_records) {
- hci::AddressWithType remote(
- hci::Address({0x01, 0x02, 0x03, 0x04, 0x05, 0x06}), hci::AddressType::PUBLIC_DEVICE_ADDRESS);
- std::array<uint8_t, 16> link_key = {
- 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0};
- std::shared_ptr<record::SecurityRecord> record = std::make_shared<record::SecurityRecord>(remote);
-
- record->SetLinkKey(link_key, hci::KeyType::DEBUG_COMBINATION);
- record->SetIsTemporary(true);
- std::set<std::shared_ptr<record::SecurityRecord>> record_set;
- record_set.insert(record);
- record_storage_->SaveSecurityRecords(&record_set);
-
- auto device = storage_module_->GetDeviceByClassicMacAddress(remote.GetAddress());
- ASSERT_FALSE(device.GetDeviceType());
-
- record_set.clear();
- record_storage_->LoadSecurityRecords(&record_set);
- ASSERT_EQ(record_set.size(), 0);
-}
-
-TEST_F(DISABLED_SecurityRecordStorageTest, test_remove) {
- hci::AddressWithType remote(
- hci::Address({0x01, 0x02, 0x03, 0x04, 0x05, 0x06}), hci::AddressType::PUBLIC_DEVICE_ADDRESS);
- std::array<uint8_t, 16> link_key = {
- 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0x01, 0};
- std::shared_ptr<record::SecurityRecord> record = std::make_shared<record::SecurityRecord>(remote);
-
- record->SetLinkKey(link_key, hci::KeyType::DEBUG_COMBINATION);
- std::set<std::shared_ptr<record::SecurityRecord>> record_set;
- record_set.insert(record);
- record_storage_->SaveSecurityRecords(&record_set);
-
- auto device = storage_module_->GetDeviceByClassicMacAddress(remote.GetAddress());
- ASSERT_TRUE(device.GetDeviceType());
-
- ASSERT_EQ(device.Classic().GetLinkKeyType(), record->GetKeyType());
- int i = 0;
- for (i = 0; i < 16; ++i) {
- ASSERT_EQ(link_key[i], device.Classic().GetLinkKey()->bytes[i]);
- }
-
- record_storage_->RemoveDevice(remote);
-
- record_set.clear();
- record_storage_->LoadSecurityRecords(&record_set);
- ASSERT_EQ(record_set.size(), 0);
-}
-
-} // namespace
-} // namespace record
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/security_manager.cc b/gd/security/security_manager.cc
index 9e711aed0..34efbe2a9 100644
--- a/gd/security/security_manager.cc
+++ b/gd/security/security_manager.cc
@@ -36,23 +36,6 @@ void SecurityManager::CreateBond(hci::AddressWithType device) {
std::forward<hci::AddressWithType>(device)));
}
-void SecurityManager::CreateBondOutOfBand(
- hci::AddressWithType device, pairing::OobData remote_p192_oob_data, pairing::OobData remote_p256_oob_data) {
- security_handler_->Post(common::BindOnce(
- &internal::SecurityManagerImpl::CreateBondOutOfBand,
- common::Unretained(security_manager_impl_),
- std::forward<hci::AddressWithType>(device),
- remote_p192_oob_data,
- remote_p256_oob_data));
-}
-
-void SecurityManager::GetOutOfBandData(channel::SecurityCommandStatusCallback callback) {
- security_handler_->Post(common::BindOnce(
- &internal::SecurityManagerImpl::GetOutOfBandData,
- common::Unretained(security_manager_impl_),
- std::forward<channel::SecurityCommandStatusCallback>(callback)));
-}
-
void SecurityManager::CreateBondLe(hci::AddressWithType device) {
security_handler_->Post(common::BindOnce(&internal::SecurityManagerImpl::CreateBondLe,
common::Unretained(security_manager_impl_),
@@ -76,23 +59,6 @@ void SecurityManager::SetUserInterfaceHandler(UI* user_interface, os::Handler* h
common::Unretained(security_manager_impl_), user_interface, handler));
}
-// TODO(jpawlowski): remove once we have config file abstraction in cert tests
-void SecurityManager::SetLeInitiatorAddressPolicyForTest(
- hci::LeAddressManager::AddressPolicy address_policy,
- hci::AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time) {
- security_handler_->Post(common::BindOnce(
- &internal::SecurityManagerImpl::SetLeInitiatorAddressPolicyForTest,
- common::Unretained(security_manager_impl_),
- address_policy,
- fixed_address,
- rotation_irk,
- minimum_rotation_time,
- maximum_rotation_time));
-}
-
void SecurityManager::RegisterCallbackListener(ISecurityManagerListener* listener, os::Handler* handler) {
security_handler_->Post(common::BindOnce(&internal::SecurityManagerImpl::RegisterCallbackListener,
common::Unretained(security_manager_impl_), listener, handler));
@@ -107,21 +73,14 @@ void SecurityManager::OnPairingPromptAccepted(const bluetooth::hci::AddressWithT
security_handler_->Post(common::BindOnce(&internal::SecurityManagerImpl::OnPairingPromptAccepted,
common::Unretained(security_manager_impl_), address, confirmed));
}
-
void SecurityManager::OnConfirmYesNo(const bluetooth::hci::AddressWithType& address, bool confirmed) {
security_handler_->Post(common::BindOnce(&internal::SecurityManagerImpl::OnConfirmYesNo,
common::Unretained(security_manager_impl_), address, confirmed));
}
-
void SecurityManager::OnPasskeyEntry(const bluetooth::hci::AddressWithType& address, uint32_t passkey) {
security_handler_->Post(common::BindOnce(&internal::SecurityManagerImpl::OnPasskeyEntry,
common::Unretained(security_manager_impl_), address, passkey));
}
-void SecurityManager::OnPinEntry(const bluetooth::hci::AddressWithType& address, std::vector<uint8_t> pin) {
- security_handler_->Post(common::BindOnce(
- &internal::SecurityManagerImpl::OnPinEntry, common::Unretained(security_manager_impl_), address, std::move(pin)));
-}
-
} // namespace security
} // namespace bluetooth
diff --git a/gd/security/security_manager.h b/gd/security/security_manager.h
index 627cc2ac8..fc9dbcd4b 100644
--- a/gd/security/security_manager.h
+++ b/gd/security/security_manager.h
@@ -22,9 +22,7 @@
#include <vector>
#include "hci/address_with_type.h"
-#include "hci/le_address_manager.h"
#include "security/internal/security_manager_impl.h"
-#include "security/pairing/oob_data.h"
#include "security/security_manager_listener.h"
namespace bluetooth {
@@ -46,32 +44,11 @@ class SecurityManager : public UICallbacks {
/**
* Initiates bond over Classic transport with device, if not bonded yet.
*
- * This will initiate the Numeric Comparison bonding method
- *
* @param address device address we want to bond with
*/
void CreateBond(hci::AddressWithType address);
/**
- * Initiates bond over Classic transport with device, if not bonded yet.
- *
- * This will initiate the Out of Band bonding method
- *
- * @param address device address we want to bond with
- * @param remote_p192_oob_data comparison and random for p192
- * @param remote_p256_oob_data comparison and random for p256
- */
- void CreateBondOutOfBand(
- hci::AddressWithType address, pairing::OobData remote_p192_oob_data, pairing::OobData remote_p256_oob_data);
-
- /**
- * Get the out of band data from the controller to send to another device
- *
- * @param callback pointer to callback used for notifying that a security HCI command completed
- */
- void GetOutOfBandData(channel::SecurityCommandStatusCallback callback);
-
- /**
* Initiates bond over Low Energy transport with device, if not bonded yet.
*
* @param address device address we want to bond with
@@ -98,16 +75,6 @@ class SecurityManager : public UICallbacks {
void SetUserInterfaceHandler(UI* user_interface, os::Handler* handler);
/**
- * Specify the initiator address policy used for LE transport. Can only be called once.
- */
- void SetLeInitiatorAddressPolicyForTest(
- hci::LeAddressManager::AddressPolicy address_policy,
- hci::AddressWithType fixed_address,
- crypto_toolbox::Octet16 rotation_irk,
- std::chrono::milliseconds minimum_rotation_time,
- std::chrono::milliseconds maximum_rotation_time);
-
- /**
* Register to listen for callback events from SecurityManager
*
* @param listener ISecurityManagerListener instance to handle callbacks
@@ -124,7 +91,6 @@ class SecurityManager : public UICallbacks {
void OnPairingPromptAccepted(const bluetooth::hci::AddressWithType& address, bool confirmed) override;
void OnConfirmYesNo(const bluetooth::hci::AddressWithType& address, bool confirmed) override;
void OnPasskeyEntry(const bluetooth::hci::AddressWithType& address, uint32_t passkey) override;
- void OnPinEntry(const bluetooth::hci::AddressWithType& address, std::vector<uint8_t> pin) override;
protected:
SecurityManager(os::Handler* security_handler, internal::SecurityManagerImpl* security_manager_impl)
diff --git a/gd/security/security_manager_listener.h b/gd/security/security_manager_listener.h
index 206b2d77d..edc4e6b94 100644
--- a/gd/security/security_manager_listener.h
+++ b/gd/security/security_manager_listener.h
@@ -19,8 +19,6 @@
#pragma once
#include "common/callback.h"
-#include "hci/acl_manager.h"
-#include "security/pairing_failure.h"
namespace bluetooth {
namespace security {
@@ -51,14 +49,7 @@ class ISecurityManagerListener {
*
* @param address of the device that failed to bond
*/
- virtual void OnDeviceBondFailed(bluetooth::hci::AddressWithType device, PairingFailure status) = 0;
-
- /**
- * Called as a result of a failure during the bonding process.
- *
- * @param address of the device that failed to bond
- */
- virtual void OnEncryptionStateChanged(hci::EncryptionChangeView encryption_change_view) = 0;
+ virtual void OnDeviceBondFailed(bluetooth::hci::AddressWithType device) = 0;
};
} // namespace security
diff --git a/gd/security/security_module.cc b/gd/security/security_module.cc
index d75378064..eb0a54380 100644
--- a/gd/security/security_module.cc
+++ b/gd/security/security_module.cc
@@ -21,16 +21,11 @@
#include "os/handler.h"
#include "os/log.h"
-#include "hci/acl_manager.h"
#include "hci/hci_layer.h"
#include "l2cap/le/l2cap_le_module.h"
-#include "neighbor/name_db.h"
#include "security/channel/security_manager_channel.h"
-#include "security/facade_configuration_api.h"
#include "security/internal/security_manager_impl.h"
-#include "security/l2cap_security_module_interface.h"
#include "security/security_module.h"
-#include "storage/storage_module.h"
namespace bluetooth {
namespace security {
@@ -38,55 +33,22 @@ namespace security {
const ModuleFactory SecurityModule::Factory = ModuleFactory([]() { return new SecurityModule(); });
struct SecurityModule::impl {
- impl(
- os::Handler* security_handler,
- l2cap::le::L2capLeModule* l2cap_le_module,
- l2cap::classic::L2capClassicModule* l2cap_classic_module,
- hci::HciLayer* hci_layer,
- hci::AclManager* acl_manager,
- hci::Controller* controller,
- storage::StorageModule* storage_module,
- neighbor::NameDbModule* name_db_module)
- : security_handler_(security_handler),
+ impl(os::Handler* security_handler, l2cap::le::L2capLeModule* l2cap_le_module,
+ l2cap::classic::L2capClassicModule* l2cap_classic_module, hci::HciLayer* hci_layer)
+ : security_handler_(security_handler), l2cap_le_module_(l2cap_le_module),
l2cap_classic_module_(l2cap_classic_module),
- l2cap_le_module_(l2cap_le_module),
security_manager_channel_(new channel::SecurityManagerChannel(security_handler_, hci_layer)),
- hci_layer_(hci_layer),
- acl_manager_(acl_manager),
- controller_(controller),
- storage_module_(storage_module),
- l2cap_security_interface_(&security_manager_impl, security_handler),
- name_db_module_(name_db_module) {
- l2cap_classic_module->InjectSecurityEnforcementInterface(&l2cap_security_interface_);
- l2cap_le_module->InjectSecurityEnforcementInterface(&l2cap_security_interface_);
- security_manager_channel_->SetSecurityInterface(
- l2cap_classic_module->GetSecurityInterface(security_handler_, security_manager_channel_));
- }
+ hci_layer_(hci_layer) {}
os::Handler* security_handler_;
- l2cap::classic::L2capClassicModule* l2cap_classic_module_;
l2cap::le::L2capLeModule* l2cap_le_module_;
+ l2cap::classic::L2capClassicModule* l2cap_classic_module_;
channel::SecurityManagerChannel* security_manager_channel_;
hci::HciLayer* hci_layer_;
- hci::AclManager* acl_manager_;
- hci::Controller* controller_;
- storage::StorageModule* storage_module_;
- L2capSecurityModuleInterface l2cap_security_interface_;
- neighbor::NameDbModule* name_db_module_;
-
- internal::SecurityManagerImpl security_manager_impl{security_handler_,
- l2cap_le_module_,
- security_manager_channel_,
- hci_layer_,
- acl_manager_,
- controller_,
- storage_module_,
- name_db_module_};
-
+ internal::SecurityManagerImpl security_manager_impl{security_handler_, l2cap_le_module_, l2cap_classic_module_,
+ security_manager_channel_, hci_layer_};
~impl() {
delete security_manager_channel_;
- l2cap_classic_module_->InjectSecurityEnforcementInterface(nullptr);
- l2cap_le_module_->InjectSecurityEnforcementInterface(nullptr);
}
};
@@ -94,24 +56,11 @@ void SecurityModule::ListDependencies(ModuleList* list) {
list->add<l2cap::le::L2capLeModule>();
list->add<l2cap::classic::L2capClassicModule>();
list->add<hci::HciLayer>();
- list->add<hci::AclManager>();
- list->add<hci::Controller>();
- list->add<storage::StorageModule>();
- list->add<neighbor::NameDbModule>();
}
void SecurityModule::Start() {
- pimpl_ = std::make_unique<impl>(
- GetHandler(),
- GetDependency<l2cap::le::L2capLeModule>(),
- GetDependency<l2cap::classic::L2capClassicModule>(),
- GetDependency<hci::HciLayer>(),
- GetDependency<hci::AclManager>(),
- GetDependency<hci::Controller>(),
- GetDependency<storage::StorageModule>(),
- GetDependency<neighbor::NameDbModule>());
-
- GetDependency<hci::AclManager>()->SetSecurityModule(this);
+ pimpl_ = std::make_unique<impl>(GetHandler(), GetDependency<l2cap::le::L2capLeModule>(),
+ GetDependency<l2cap::classic::L2capClassicModule>(), GetDependency<hci::HciLayer>());
}
void SecurityModule::Stop() {
@@ -127,10 +76,5 @@ std::unique_ptr<SecurityManager> SecurityModule::GetSecurityManager() {
new SecurityManager(pimpl_->security_handler_, &pimpl_->security_manager_impl));
}
-std::unique_ptr<FacadeConfigurationApi> SecurityModule::GetFacadeConfigurationApi() {
- return std::unique_ptr<FacadeConfigurationApi>(
- new FacadeConfigurationApi(pimpl_->security_handler_, &pimpl_->security_manager_impl));
-}
-
} // namespace security
} // namespace bluetooth \ No newline at end of file
diff --git a/gd/security/security_module.h b/gd/security/security_module.h
index 18f25432d..2ec456de2 100644
--- a/gd/security/security_module.h
+++ b/gd/security/security_module.h
@@ -18,7 +18,6 @@
#include <memory>
#include "module.h"
-#include "security/facade_configuration_api.h"
#include "security/security_manager.h"
namespace bluetooth {
@@ -34,13 +33,6 @@ class SecurityModule : public bluetooth::Module {
*/
std::unique_ptr<SecurityManager> GetSecurityManager();
- /**
- * Facade configuration API.
- *
- * <p> This allows you to set thins like IO Capabilities, Authentication Requirements, and OOB Data.
- */
- std::unique_ptr<FacadeConfigurationApi> GetFacadeConfigurationApi();
-
static const ModuleFactory Factory;
protected:
diff --git a/gd/security/security_record_database.h b/gd/security/security_record_database.h
new file mode 100644
index 000000000..23604757f
--- /dev/null
+++ b/gd/security/security_record_database.h
@@ -0,0 +1,63 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#pragma once
+
+#include "security/record/security_record.h"
+
+namespace bluetooth {
+namespace security {
+
+class SecurityRecordDatabase {
+ public:
+ using iterator = std::vector<record::SecurityRecord>::iterator;
+
+ record::SecurityRecord& FindOrCreate(hci::AddressWithType address) {
+ auto it = Find(address);
+ // Security record check
+ if (it != records_.end()) return *it;
+
+ // No security record, create one
+ records_.emplace_back(address);
+ return records_.back();
+ }
+
+ void Remove(const hci::AddressWithType& address) {
+ auto it = Find(address);
+
+ // No record exists
+ if (it == records_.end()) return;
+
+ record::SecurityRecord& last = records_.back();
+ *it = std::move(last);
+ records_.pop_back();
+ }
+
+ iterator Find(hci::AddressWithType address) {
+ for (auto it = records_.begin(); it != records_.end(); ++it) {
+ record::SecurityRecord& record = *it;
+ if (record.identity_address_.has_value() && record.identity_address_.value() == address) return it;
+ if (record.GetPseudoAddress() == address) return it;
+ if (record.irk.has_value() && address.IsRpaThatMatchesIrk(record.irk.value())) return it;
+ }
+ return records_.end();
+ }
+
+ std::vector<record::SecurityRecord> records_;
+};
+
+} // namespace security
+} // namespace bluetooth \ No newline at end of file
diff --git a/gd/security/smp_packets.pdl b/gd/security/smp_packets.pdl
index a08b96daf..69269dd81 100644
--- a/gd/security/smp_packets.pdl
+++ b/gd/security/smp_packets.pdl
@@ -9,7 +9,7 @@ enum Code : 8 {
PAIRING_RANDOM = 0x04,
PAIRING_FAILED = 0x05,
ENCRYPTION_INFORMATION = 0x06,
- CENTRAL_IDENTIFICATION = 0x07,
+ MASTER_IDENTIFICATION = 0x07,
IDENTITY_INFORMATION = 0x08,
IDENTITY_ADDRESS_INFORMATION = 0x09,
SIGNING_INFORMATION = 0x0A,
@@ -93,7 +93,7 @@ packet EncryptionInformation : Command (code = ENCRYPTION_INFORMATION) {
long_term_key : 8[16],
}
-packet CentralIdentification : Command (code = CENTRAL_IDENTIFICATION) {
+packet MasterIdentification : Command (code = MASTER_IDENTIFICATION) {
ediv : 16,
rand : 8[8],
}
diff --git a/gd/security/test/fake_hci_layer.h b/gd/security/test/fake_hci_layer.h
index 6ffd1c2f5..6866b342d 100644
--- a/gd/security/test/fake_hci_layer.h
+++ b/gd/security/test/fake_hci_layer.h
@@ -22,13 +22,15 @@
namespace bluetooth {
namespace security {
-using common::ContextualOnceCallback;
+using common::OnceCallback;
using hci::CommandCompleteView;
+using hci::CommandPacketBuilder;
using hci::CommandStatusView;
-using hci::EventBuilder;
using hci::EventCode;
-using hci::EventView;
+using hci::EventPacketBuilder;
+using hci::EventPacketView;
using hci::HciLayer;
+using os::Handler;
namespace {
@@ -42,37 +44,36 @@ PacketView<kLittleEndian> GetPacketView(std::unique_ptr<packet::BasePacketBuilde
class CommandQueueEntry {
public:
- CommandQueueEntry(
- std::unique_ptr<hci::CommandBuilder> command_packet,
- ContextualOnceCallback<void(CommandCompleteView)> on_complete_function)
- : command(std::move(command_packet)), waiting_for_status_(false), on_complete(std::move(on_complete_function)) {}
+ CommandQueueEntry(std::unique_ptr<CommandPacketBuilder> command_packet,
+ OnceCallback<void(CommandCompleteView)> on_complete_function, Handler* handler)
+ : command(std::move(command_packet)), waiting_for_status_(false), on_complete(std::move(on_complete_function)),
+ caller_handler(handler) {}
- CommandQueueEntry(
- std::unique_ptr<hci::CommandBuilder> command_packet,
- ContextualOnceCallback<void(CommandStatusView)> on_status_function)
- : command(std::move(command_packet)), waiting_for_status_(true), on_status(std::move(on_status_function)) {}
+ CommandQueueEntry(std::unique_ptr<CommandPacketBuilder> command_packet,
+ OnceCallback<void(CommandStatusView)> on_status_function, Handler* handler)
+ : command(std::move(command_packet)), waiting_for_status_(true), on_status(std::move(on_status_function)),
+ caller_handler(handler) {}
- std::unique_ptr<hci::CommandBuilder> command;
+ std::unique_ptr<CommandPacketBuilder> command;
bool waiting_for_status_;
- ContextualOnceCallback<void(CommandStatusView)> on_status;
- ContextualOnceCallback<void(CommandCompleteView)> on_complete;
+ OnceCallback<void(CommandStatusView)> on_status;
+ OnceCallback<void(CommandCompleteView)> on_complete;
+ Handler* caller_handler;
};
} // namespace
class FakeHciLayer : public HciLayer {
public:
- void EnqueueCommand(
- std::unique_ptr<hci::CommandBuilder> command,
- ContextualOnceCallback<void(CommandStatusView)> on_status) override {
- auto command_queue_entry = std::make_unique<CommandQueueEntry>(std::move(command), std::move(on_status));
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command, OnceCallback<void(CommandStatusView)> on_status,
+ Handler* handler) override {
+ auto command_queue_entry = std::make_unique<CommandQueueEntry>(std::move(command), std::move(on_status), handler);
command_queue_.push(std::move(command_queue_entry));
}
- void EnqueueCommand(
- std::unique_ptr<hci::CommandBuilder> command,
- ContextualOnceCallback<void(CommandCompleteView)> on_complete) override {
- auto command_queue_entry = std::make_unique<CommandQueueEntry>(std::move(command), std::move(on_complete));
+ void EnqueueCommand(std::unique_ptr<CommandPacketBuilder> command,
+ OnceCallback<void(CommandCompleteView)> on_complete, Handler* handler) override {
+ auto command_queue_entry = std::make_unique<CommandQueueEntry>(std::move(command), std::move(on_complete), handler);
command_queue_.push(std::move(command_queue_entry));
}
@@ -83,7 +84,8 @@ class FakeHciLayer : public HciLayer {
return last;
}
- void RegisterEventHandler(EventCode event_code, common::ContextualCallback<void(EventView)> event_handler) override {
+ void RegisterEventHandler(EventCode event_code, common::Callback<void(EventPacketView)> event_handler,
+ Handler* handler) override {
registered_events_[event_code] = event_handler;
}
@@ -91,13 +93,13 @@ class FakeHciLayer : public HciLayer {
registered_events_.erase(event_code);
}
- void IncomingEvent(std::unique_ptr<EventBuilder> event_builder) {
+ void IncomingEvent(std::unique_ptr<EventPacketBuilder> event_builder) {
auto packet = GetPacketView(std::move(event_builder));
- EventView event = EventView::Create(packet);
+ EventPacketView event = EventPacketView::Create(packet);
ASSERT_TRUE(event.IsValid());
EventCode event_code = event.GetEventCode();
ASSERT_TRUE(registered_events_.find(event_code) != registered_events_.end());
- registered_events_[event_code].Invoke(event);
+ registered_events_[event_code].Run(event);
}
void ListDependencies(ModuleList* list) override {}
@@ -105,7 +107,7 @@ class FakeHciLayer : public HciLayer {
void Stop() override {}
private:
- std::map<EventCode, common::ContextualCallback<void(EventView)>> registered_events_;
+ std::map<EventCode, common::Callback<void(EventPacketView)>> registered_events_;
std::queue<std::unique_ptr<CommandQueueEntry>> command_queue_;
};
diff --git a/gd/security/test/fake_l2cap_test.cc b/gd/security/test/fake_l2cap_test.cc
index 23b2555fc..2d885e778 100644
--- a/gd/security/test/fake_l2cap_test.cc
+++ b/gd/security/test/fake_l2cap_test.cc
@@ -42,8 +42,8 @@ using bluetooth::hci::CommandStatusView;
using bluetooth::hci::EncryptionChangeBuilder;
using bluetooth::hci::EncryptionEnabled;
using bluetooth::hci::ErrorCode;
-using bluetooth::hci::EventBuilder;
-using bluetooth::hci::EventView;
+using bluetooth::hci::EventPacketBuilder;
+using bluetooth::hci::EventPacketView;
using bluetooth::hci::LeSecurityCommandBuilder;
namespace bluetooth {
diff --git a/gd/security/test/fake_name_db.h b/gd/security/test/fake_name_db.h
deleted file mode 100644
index 9a3409492..000000000
--- a/gd/security/test/fake_name_db.h
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- *
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#include "neighbor/name_db.h"
-
-namespace bluetooth {
-namespace security {
-
-class FakeNameDbModule : public neighbor::NameDbModule {
- public:
- FakeNameDbModule() {}
-
- void ListDependencies(ModuleList* list) override {}
- void Start() override {}
- void Stop() override {}
- std::string ToString() const override {
- return std::string("FakeNameDbModule");
- }
-
- void ReadRemoteNameRequest(
- hci::Address address, neighbor::ReadRemoteNameDbCallback callback, os::Handler* handler) override {
- handler->Call(std::move(callback), address, true);
- }
-
- bool IsNameCached(hci::Address address) const {
- return true;
- }
-
- neighbor::RemoteName ReadCachedRemoteName(hci::Address address) const {
- neighbor::RemoteName name = {'t', 'e', 's', 't'};
- return name;
- }
-};
-
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/test/fake_security_interface.h b/gd/security/test/fake_security_interface.h
deleted file mode 100644
index 822f15ea6..000000000
--- a/gd/security/test/fake_security_interface.h
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- *
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-#include "common/bind.h"
-#include "os/handler.h"
-
-namespace bluetooth {
-namespace security {
-
-class FakeLinkSecurityInterface : public l2cap::classic::LinkSecurityInterface {
- public:
- FakeLinkSecurityInterface(l2cap::classic::LinkSecurityInterfaceListener* listener, hci::Address address)
- : listener_(listener), address_(address) {}
-
- hci::Address GetRemoteAddress() {
- return address_;
- }
- void Hold() override {}
- void EnsureAuthenticated() override{};
-
- void EnsureEncrypted() override {}
-
- void Release() override {
- // TODO(optedoblivion): Simulate the delay
- listener_->OnLinkDisconnected(address_);
- }
- void Disconnect() override {
- listener_->OnLinkDisconnected(address_);
- }
- uint16_t GetAclHandle() override {
- return 0;
- }
-
- private:
- l2cap::classic::LinkSecurityInterfaceListener* listener_ = nullptr;
- hci::Address address_;
-};
-
-class FakeSecurityInterface : public l2cap::classic::SecurityInterface {
- public:
- FakeSecurityInterface(os::Handler* handler, l2cap::classic::LinkSecurityInterfaceListener* listener)
- : handler_(handler), listener_(listener) {}
- ~FakeSecurityInterface() {}
- void InitiateConnectionForSecurity(hci::Address remote) override {
- listener_->OnLinkConnected(std::make_unique<FakeLinkSecurityInterface>(listener_, remote));
- };
- void Unregister() override {}
-
- private:
- os::Handler* handler_ __attribute__((unused));
- l2cap::classic::LinkSecurityInterfaceListener* listener_ __attribute__((unused));
-};
-
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/test/fake_storage_module.h b/gd/security/test/fake_storage_module.h
deleted file mode 100644
index cf66a4bec..000000000
--- a/gd/security/test/fake_storage_module.h
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- *
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#include "storage/storage_module.h"
-
-#include <filesystem>
-
-namespace bluetooth {
-namespace security {
-
-static const std::chrono::milliseconds kTestConfigSaveDelay = std::chrono::milliseconds(100);
-
-class FakeStorageModule : public storage::StorageModule {
- public:
- FakeStorageModule() : storage::StorageModule("/tmp/temp_config.txt", kTestConfigSaveDelay, 100, false, false) {}
-
- storage::ConfigCache* GetConfigCachePublic() {
- return StorageModule::GetConfigCache();
- }
-
- void SaveImmediatelyPublic() {
- StorageModule::SaveImmediately();
- }
-};
-
-} // namespace security
-} // namespace bluetooth
diff --git a/gd/security/test/mocks.h b/gd/security/test/mocks.h
index 3ddc909f4..bbc3a2ccb 100644
--- a/gd/security/test/mocks.h
+++ b/gd/security/test/mocks.h
@@ -29,17 +29,15 @@ namespace security {
class UIMock : public UI {
public:
- UIMock() = default;
- ~UIMock() = default;
-
- // Convert these to accept ConfirmationData
- MOCK_METHOD2(DisplayPairingPrompt, void(const bluetooth::hci::AddressWithType& address, std::string name));
- MOCK_METHOD1(Cancel, void(const bluetooth::hci::AddressWithType& address));
- MOCK_METHOD1(DisplayConfirmValue, void(ConfirmationData));
- MOCK_METHOD1(DisplayYesNoDialog, void(ConfirmationData));
- MOCK_METHOD1(DisplayEnterPasskeyDialog, void(ConfirmationData));
- MOCK_METHOD1(DisplayPasskey, void(ConfirmationData));
- MOCK_METHOD1(DisplayEnterPinDialog, void(ConfirmationData));
+ UIMock() {}
+ ~UIMock() override = default;
+
+ MOCK_METHOD2(DisplayPairingPrompt, void(const bluetooth::hci::AddressWithType&, std::string));
+ MOCK_METHOD1(Cancel, void(const bluetooth::hci::AddressWithType&));
+ MOCK_METHOD3(DisplayConfirmValue, void(const bluetooth::hci::AddressWithType&, std::string, uint32_t));
+ MOCK_METHOD2(DisplayYesNoDialog, void(const bluetooth::hci::AddressWithType&, std::string));
+ MOCK_METHOD2(DisplayEnterPasskeyDialog, void(const bluetooth::hci::AddressWithType&, std::string));
+ MOCK_METHOD3(DisplayPasskey, void(const bluetooth::hci::AddressWithType&, std::string, uint32_t));
private:
DISALLOW_COPY_AND_ASSIGN(UIMock);
@@ -47,11 +45,13 @@ class UIMock : public UI {
class LeSecurityInterfaceMock : public hci::LeSecurityInterface {
public:
- MOCK_METHOD2(EnqueueCommand, void(std::unique_ptr<hci::LeSecurityCommandBuilder> command,
- common::ContextualOnceCallback<void(hci::CommandCompleteView)> on_complete));
- MOCK_METHOD2(EnqueueCommand, void(std::unique_ptr<hci::LeSecurityCommandBuilder> command,
- common::ContextualOnceCallback<void(hci::CommandStatusView)> on_status));
+ MOCK_METHOD3(EnqueueCommand,
+ void(std::unique_ptr<hci::LeSecurityCommandBuilder> command,
+ common::OnceCallback<void(hci::CommandCompleteView)> on_complete, os::Handler* handler));
+ MOCK_METHOD3(EnqueueCommand,
+ void(std::unique_ptr<hci::LeSecurityCommandBuilder> command,
+ common::OnceCallback<void(hci::CommandStatusView)> on_status, os::Handler* handler));
};
} // namespace security
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/gd/security/test/pairing_handler_le_pair_test.cc b/gd/security/test/pairing_handler_le_pair_test.cc
index 434e63809..36dc365e5 100644
--- a/gd/security/test/pairing_handler_le_pair_test.cc
+++ b/gd/security/test/pairing_handler_le_pair_test.cc
@@ -41,8 +41,8 @@ using bluetooth::hci::CommandStatusView;
using bluetooth::hci::EncryptionChangeBuilder;
using bluetooth::hci::EncryptionEnabled;
using bluetooth::hci::ErrorCode;
-using bluetooth::hci::EventBuilder;
-using bluetooth::hci::EventView;
+using bluetooth::hci::EventPacketBuilder;
+using bluetooth::hci::EventPacketView;
using bluetooth::hci::LeSecurityCommandBuilder;
// run:
@@ -61,20 +61,20 @@ CommandView CommandBuilderToView(std::unique_ptr<BasePacketBuilder> builder) {
return CommandView::Create(temp_cmd_view);
}
-EventView EventBuilderToView(std::unique_ptr<EventBuilder> builder) {
+EventPacketView EventBuilderToView(std::unique_ptr<EventPacketBuilder> builder) {
std::shared_ptr<std::vector<uint8_t>> packet_bytes = std::make_shared<std::vector<uint8_t>>();
BitInserter it(*packet_bytes);
builder->Serialize(it);
PacketView<kLittleEndian> packet_bytes_view(packet_bytes);
- auto temp_evt_view = EventView::Create(packet_bytes_view);
- return EventView::Create(temp_evt_view);
+ auto temp_evt_view = EventPacketView::Create(packet_bytes_view);
+ return EventPacketView::Create(temp_evt_view);
}
} // namespace security
} // namespace bluetooth
namespace {
-constexpr uint16_t CONN_HANDLE_CENTRAL = 0x31, CONN_HANDLE_PERIPHERAL = 0x32;
+constexpr uint16_t CONN_HANDLE_MASTER = 0x31, CONN_HANDLE_SLAVE = 0x32;
std::unique_ptr<bluetooth::security::PairingHandlerLe> pairing_handler_a, pairing_handler_b;
} // namespace
@@ -83,25 +83,17 @@ namespace bluetooth {
namespace security {
namespace {
-Address ADDRESS_CENTRAL{{0x26, 0x64, 0x76, 0x86, 0xab, 0xba}};
-AddressType ADDRESS_TYPE_CENTRAL = AddressType::RANDOM_DEVICE_ADDRESS;
-Address IDENTITY_ADDRESS_CENTRAL{{0x12, 0x34, 0x56, 0x78, 0x90, 0xaa}};
-AddressType IDENTITY_ADDRESS_TYPE_CENTRAL = AddressType::PUBLIC_DEVICE_ADDRESS;
-crypto_toolbox::Octet16 IRK_CENTRAL = {
- 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0a, 0x0b, 0x0c, 0x0d, 0x0e, 0x0f};
-
-Address ADDRESS_PERIPHERAL{{0x33, 0x58, 0x24, 0x76, 0x11, 0x89}};
-AddressType ADDRESS_TYPE_PERIPHERAL = AddressType::RANDOM_DEVICE_ADDRESS;
-Address IDENTITY_ADDRESS_PERIPHERAL{{0x21, 0x43, 0x65, 0x87, 0x09, 0x44}};
-AddressType IDENTITY_ADDRESS_TYPE_PERIPHERAL = AddressType::PUBLIC_DEVICE_ADDRESS;
-crypto_toolbox::Octet16 IRK_PERIPHERAL = {
- 0x0f, 0x0e, 0x0d, 0x0c, 0x0b, 0x0a, 0x09, 0x08, 0x07, 0x06, 0x05, 0x04, 0x03, 0x02, 0x01};
-
-std::optional<PairingResultOrFailure> pairing_result_central;
-std::optional<PairingResultOrFailure> pairing_result_peripheral;
-
-void OnPairingFinishedCentral(PairingResultOrFailure r) {
- pairing_result_central = r;
+Address ADDRESS_MASTER{{0x26, 0x64, 0x76, 0x86, 0xab, 0xba}};
+AddressType ADDRESS_TYPE_MASTER = AddressType::RANDOM_DEVICE_ADDRESS;
+
+Address ADDRESS_SLAVE{{0x33, 0x58, 0x24, 0x76, 0x11, 0x89}};
+AddressType ADDRESS_TYPE_SLAVE = AddressType::RANDOM_DEVICE_ADDRESS;
+
+std::optional<PairingResultOrFailure> pairing_result_master;
+std::optional<PairingResultOrFailure> pairing_result_slave;
+
+void OnPairingFinishedMaster(PairingResultOrFailure r) {
+ pairing_result_master = r;
if (std::holds_alternative<PairingResult>(r)) {
LOG_INFO("pairing finished successfully with %s", std::get<PairingResult>(r).connection_address.ToString().c_str());
} else {
@@ -109,8 +101,8 @@ void OnPairingFinishedCentral(PairingResultOrFailure r) {
}
}
-void OnPairingFinishedPeripheral(PairingResultOrFailure r) {
- pairing_result_peripheral = r;
+void OnPairingFinishedSlave(PairingResultOrFailure r) {
+ pairing_result_slave = r;
if (std::holds_alternative<PairingResult>(r)) {
LOG_INFO("pairing finished successfully with %s", std::get<PairingResult>(r).connection_address.ToString().c_str());
} else {
@@ -124,7 +116,7 @@ void OnPairingFinishedPeripheral(PairingResultOrFailure r) {
std::mutex handlers_initialization_guard;
class PairingHandlerPairTest : public testing::Test {
- void dequeue_callback_central() {
+ void dequeue_callback_master() {
auto packet_bytes_view = l2cap_->GetQueueAUpEnd()->TryDequeue();
if (!packet_bytes_view) LOG_ERROR("Received dequeue, but no data ready...");
@@ -135,12 +127,12 @@ class PairingHandlerPairTest : public testing::Test {
return;
}
- if (!pairing_handler_a) LOG_ALWAYS_FATAL("Peripheral handler not initlized yet!");
+ if (!pairing_handler_a) LOG_ALWAYS_FATAL("Slave handler not initlized yet!");
pairing_handler_a->OnCommandView(CommandView::Create(temp_cmd_view));
}
- void dequeue_callback_peripheral() {
+ void dequeue_callback_slave() {
auto packet_bytes_view = l2cap_->GetQueueBUpEnd()->TryDequeue();
if (!packet_bytes_view) LOG_ERROR("Received dequeue, but no data ready...");
@@ -151,7 +143,7 @@ class PairingHandlerPairTest : public testing::Test {
return;
}
- if (!pairing_handler_b) LOG_ALWAYS_FATAL("Central handler not initlized yet!");
+ if (!pairing_handler_b) LOG_ALWAYS_FATAL("Master handler not initlized yet!");
pairing_handler_b->OnCommandView(CommandView::Create(temp_cmd_view));
}
@@ -162,21 +154,19 @@ class PairingHandlerPairTest : public testing::Test {
handler_ = new os::Handler(thread_);
l2cap_ = new common::testing::WiredPairOfL2capQueues(handler_);
- // central sends it's packet into l2cap->down_buffer_b_
- // peripheral sends it's packet into l2cap->down_buffer_a_
+ // master sends it's packet into l2cap->down_buffer_b_
+ // slave sends it's packet into l2cap->down_buffer_a_
l2cap_->GetQueueAUpEnd()->RegisterDequeue(
- handler_, common::Bind(&PairingHandlerPairTest::dequeue_callback_central, common::Unretained(this)));
+ handler_, common::Bind(&PairingHandlerPairTest::dequeue_callback_master, common::Unretained(this)));
l2cap_->GetQueueBUpEnd()->RegisterDequeue(
- handler_, common::Bind(&PairingHandlerPairTest::dequeue_callback_peripheral, common::Unretained(this)));
+ handler_, common::Bind(&PairingHandlerPairTest::dequeue_callback_slave, common::Unretained(this)));
up_buffer_a_ = std::make_unique<os::EnqueueBuffer<packet::BasePacketBuilder>>(l2cap_->GetQueueAUpEnd());
up_buffer_b_ = std::make_unique<os::EnqueueBuffer<packet::BasePacketBuilder>>(l2cap_->GetQueueBUpEnd());
- central_setup = {
- .my_role = hci::Role::CENTRAL,
- .my_connection_address = {ADDRESS_CENTRAL, ADDRESS_TYPE_CENTRAL},
- .my_identity_address = {IDENTITY_ADDRESS_CENTRAL, IDENTITY_ADDRESS_TYPE_CENTRAL},
- .my_identity_resolving_key = IRK_CENTRAL,
+ master_setup = {
+ .my_role = hci::Role::MASTER,
+ .my_connection_address = {ADDRESS_MASTER, ADDRESS_TYPE_MASTER},
.myPairingCapabilities = {.io_capability = IoCapability::NO_INPUT_NO_OUTPUT,
.oob_data_flag = OobDataFlag::NOT_PRESENT,
@@ -186,23 +176,20 @@ class PairingHandlerPairTest : public testing::Test {
.responder_key_distribution = KeyMaskId | KeyMaskSign},
.remotely_initiated = false,
- .connection_handle = CONN_HANDLE_CENTRAL,
- .remote_connection_address = {ADDRESS_PERIPHERAL, ADDRESS_TYPE_PERIPHERAL},
- .user_interface = &central_user_interface,
+ .connection_handle = CONN_HANDLE_MASTER,
+ .remote_connection_address = {ADDRESS_SLAVE, ADDRESS_TYPE_SLAVE},
+ .user_interface = &master_user_interface,
.user_interface_handler = handler_,
- .le_security_interface = &central_le_security_mock,
+ .le_security_interface = &master_le_security_mock,
.proper_l2cap_interface = up_buffer_a_.get(),
.l2cap_handler = handler_,
- .OnPairingFinished = OnPairingFinishedCentral,
+ .OnPairingFinished = OnPairingFinishedMaster,
};
- peripheral_setup = {
- .my_role = hci::Role::PERIPHERAL,
-
- .my_connection_address = {ADDRESS_PERIPHERAL, ADDRESS_TYPE_PERIPHERAL},
- .my_identity_address = {IDENTITY_ADDRESS_PERIPHERAL, IDENTITY_ADDRESS_TYPE_PERIPHERAL},
- .my_identity_resolving_key = IRK_PERIPHERAL,
+ slave_setup = {
+ .my_role = hci::Role::SLAVE,
+ .my_connection_address = {ADDRESS_SLAVE, ADDRESS_TYPE_SLAVE},
.myPairingCapabilities = {.io_capability = IoCapability::NO_INPUT_NO_OUTPUT,
.oob_data_flag = OobDataFlag::NOT_PRESENT,
.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
@@ -210,29 +197,29 @@ class PairingHandlerPairTest : public testing::Test {
.initiator_key_distribution = KeyMaskId | KeyMaskSign,
.responder_key_distribution = KeyMaskId | KeyMaskSign},
.remotely_initiated = true,
- .connection_handle = CONN_HANDLE_PERIPHERAL,
- .remote_connection_address = {ADDRESS_CENTRAL, ADDRESS_TYPE_CENTRAL},
- .user_interface = &peripheral_user_interface,
+ .connection_handle = CONN_HANDLE_SLAVE,
+ .remote_connection_address = {ADDRESS_MASTER, ADDRESS_TYPE_MASTER},
+ .user_interface = &slave_user_interface,
.user_interface_handler = handler_,
- .le_security_interface = &peripheral_le_security_mock,
+ .le_security_interface = &slave_le_security_mock,
.proper_l2cap_interface = up_buffer_b_.get(),
.l2cap_handler = handler_,
- .OnPairingFinished = OnPairingFinishedPeripheral,
+ .OnPairingFinished = OnPairingFinishedSlave,
};
RecordSuccessfulEncryptionComplete();
}
void TearDown() {
- ::testing::Mock::VerifyAndClearExpectations(&peripheral_user_interface);
- ::testing::Mock::VerifyAndClearExpectations(&central_user_interface);
- ::testing::Mock::VerifyAndClearExpectations(&peripheral_le_security_mock);
- ::testing::Mock::VerifyAndClearExpectations(&central_le_security_mock);
+ ::testing::Mock::VerifyAndClearExpectations(&slave_user_interface);
+ ::testing::Mock::VerifyAndClearExpectations(&master_user_interface);
+ ::testing::Mock::VerifyAndClearExpectations(&slave_le_security_mock);
+ ::testing::Mock::VerifyAndClearExpectations(&master_le_security_mock);
pairing_handler_a.reset();
pairing_handler_b.reset();
- pairing_result_central.reset();
- pairing_result_peripheral.reset();
+ pairing_result_master.reset();
+ pairing_result_slave.reset();
first_command_sent = false;
first_command.reset();
@@ -264,22 +251,18 @@ class PairingHandlerPairTest : public testing::Test {
void RecordSuccessfulEncryptionComplete() {
// For now, all tests are succeeding to go through Encryption. Record that in the setup.
// Once we test failure cases, move this to each test
- EXPECT_CALL(
- central_le_security_mock,
- EnqueueCommand(_, Matcher<common::ContextualOnceCallback<void(CommandStatusView)>>(_)))
+ EXPECT_CALL(master_le_security_mock,
+ EnqueueCommand(_, Matcher<common::OnceCallback<void(CommandStatusView)>>(_), _))
.Times(1)
.WillOnce([](std::unique_ptr<LeSecurityCommandBuilder> command,
- common::ContextualOnceCallback<void(CommandStatusView)> on_status) {
+ common::OnceCallback<void(CommandStatusView)> on_status, os::Handler* handler) {
// TODO: on_status.Run();
pairing_handler_a->OnHciEvent(EventBuilderToView(
- EncryptionChangeBuilder::Create(ErrorCode::SUCCESS, CONN_HANDLE_CENTRAL, EncryptionEnabled::ON)));
-
- pairing_handler_b->OnHciEvent(EventBuilderToView(
- hci::LeLongTermKeyRequestBuilder::Create(CONN_HANDLE_PERIPHERAL, {0, 0, 0, 0, 0, 0, 0, 0}, 0)));
+ EncryptionChangeBuilder::Create(ErrorCode::SUCCESS, CONN_HANDLE_MASTER, EncryptionEnabled::ON)));
pairing_handler_b->OnHciEvent(EventBuilderToView(
- EncryptionChangeBuilder::Create(ErrorCode::SUCCESS, CONN_HANDLE_PERIPHERAL, EncryptionEnabled::ON)));
+ EncryptionChangeBuilder::Create(ErrorCode::SUCCESS, CONN_HANDLE_SLAVE, EncryptionEnabled::ON)));
});
}
@@ -293,12 +276,12 @@ class PairingHandlerPairTest : public testing::Test {
return std::move(first_command);
}
- InitialInformations central_setup;
- InitialInformations peripheral_setup;
- UIMock central_user_interface;
- UIMock peripheral_user_interface;
- LeSecurityInterfaceMock central_le_security_mock;
- LeSecurityInterfaceMock peripheral_le_security_mock;
+ InitialInformations master_setup;
+ InitialInformations slave_setup;
+ UIMock master_user_interface;
+ UIMock slave_user_interface;
+ LeSecurityInterfaceMock master_le_security_mock;
+ LeSecurityInterfaceMock slave_le_security_mock;
uint16_t first_command_sent = false;
std::unique_ptr<bluetooth::security::CommandView> first_command;
@@ -314,20 +297,20 @@ class PairingHandlerPairTest : public testing::Test {
/* This test verifies that Just Works pairing flow works.
* Both simulated devices specify capabilities as NO_INPUT_NO_OUTPUT, and secure connecitons support */
TEST_F(PairingHandlerPairTest, test_secure_connections_just_works) {
- central_setup.myPairingCapabilities.io_capability = IoCapability::NO_INPUT_NO_OUTPUT;
- central_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
- peripheral_setup.myPairingCapabilities.io_capability = IoCapability::NO_INPUT_NO_OUTPUT;
- peripheral_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
+ master_setup.myPairingCapabilities.io_capability = IoCapability::NO_INPUT_NO_OUTPUT;
+ master_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
+ slave_setup.myPairingCapabilities.io_capability = IoCapability::NO_INPUT_NO_OUTPUT;
+ slave_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
{
std::unique_lock<std::mutex> lock(handlers_initialization_guard);
- pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, central_setup);
+ pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, master_setup);
auto first_pkt = WaitFirstL2capCommand();
- peripheral_setup.pairing_request = PairingRequestView::Create(*first_pkt);
+ slave_setup.pairing_request = PairingRequestView::Create(*first_pkt);
- EXPECT_CALL(peripheral_user_interface, DisplayPairingPrompt(_, _)).Times(1).WillOnce(InvokeWithoutArgs([] {
+ EXPECT_CALL(slave_user_interface, DisplayPairingPrompt(_, _)).Times(1).WillOnce(InvokeWithoutArgs([] {
LOG_INFO("UI mock received pairing prompt");
{
@@ -341,34 +324,20 @@ TEST_F(PairingHandlerPairTest, test_secure_connections_just_works) {
pairing_handler_b->OnUiAction(PairingEvent::PAIRING_ACCEPTED, 0x01 /* Non-zero value means success */);
}));
- pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, peripheral_setup);
+ pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, slave_setup);
}
pairing_handler_a->WaitUntilPairingFinished();
pairing_handler_b->WaitUntilPairingFinished();
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_central.value()));
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_peripheral.value()));
-
- auto central_result = std::get<PairingResult>(pairing_result_central.value());
- ASSERT_EQ(central_result.distributed_keys.remote_identity_address->GetAddress(), IDENTITY_ADDRESS_PERIPHERAL);
- ASSERT_EQ(
- central_result.distributed_keys.remote_identity_address->GetAddressType(), IDENTITY_ADDRESS_TYPE_PERIPHERAL);
- ASSERT_EQ(*central_result.distributed_keys.remote_irk, IRK_PERIPHERAL);
-
- auto peripheral_result = std::get<PairingResult>(pairing_result_peripheral.value());
- ASSERT_EQ(peripheral_result.distributed_keys.remote_identity_address->GetAddress(), IDENTITY_ADDRESS_CENTRAL);
- ASSERT_EQ(
- peripheral_result.distributed_keys.remote_identity_address->GetAddressType(), IDENTITY_ADDRESS_TYPE_CENTRAL);
- ASSERT_EQ(*peripheral_result.distributed_keys.remote_irk, IRK_CENTRAL);
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_master.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_slave.value()));
}
-TEST_F(PairingHandlerPairTest, test_secure_connections_just_works_peripheral_initiated) {
- central_setup = {
- .my_role = hci::Role::CENTRAL,
- .my_connection_address = {ADDRESS_CENTRAL, ADDRESS_TYPE_CENTRAL},
- .my_identity_address = {IDENTITY_ADDRESS_CENTRAL, IDENTITY_ADDRESS_TYPE_CENTRAL},
- .my_identity_resolving_key = IRK_CENTRAL,
+TEST_F(PairingHandlerPairTest, test_secure_connections_just_works_slave_initiated) {
+ master_setup = {
+ .my_role = hci::Role::MASTER,
+ .my_connection_address = {ADDRESS_MASTER, ADDRESS_TYPE_MASTER},
.myPairingCapabilities = {.io_capability = IoCapability::NO_INPUT_NO_OUTPUT,
.oob_data_flag = OobDataFlag::NOT_PRESENT,
.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
@@ -376,21 +345,19 @@ TEST_F(PairingHandlerPairTest, test_secure_connections_just_works_peripheral_ini
.initiator_key_distribution = KeyMaskId | KeyMaskSign,
.responder_key_distribution = KeyMaskId | KeyMaskSign},
.remotely_initiated = true,
- .connection_handle = CONN_HANDLE_CENTRAL,
- .remote_connection_address = {ADDRESS_PERIPHERAL, ADDRESS_TYPE_PERIPHERAL},
- .user_interface = &central_user_interface,
+ .connection_handle = CONN_HANDLE_MASTER,
+ .remote_connection_address = {ADDRESS_SLAVE, ADDRESS_TYPE_SLAVE},
+ .user_interface = &master_user_interface,
.user_interface_handler = handler_,
- .le_security_interface = &central_le_security_mock,
+ .le_security_interface = &master_le_security_mock,
.proper_l2cap_interface = up_buffer_a_.get(),
.l2cap_handler = handler_,
- .OnPairingFinished = OnPairingFinishedCentral,
+ .OnPairingFinished = OnPairingFinishedMaster,
};
- peripheral_setup = {
- .my_role = hci::Role::PERIPHERAL,
- .my_connection_address = {ADDRESS_PERIPHERAL, ADDRESS_TYPE_PERIPHERAL},
- .my_identity_address = {IDENTITY_ADDRESS_PERIPHERAL, IDENTITY_ADDRESS_TYPE_PERIPHERAL},
- .my_identity_resolving_key = IRK_PERIPHERAL,
+ slave_setup = {
+ .my_role = hci::Role::SLAVE,
+ .my_connection_address = {ADDRESS_SLAVE, ADDRESS_TYPE_SLAVE},
.myPairingCapabilities = {.io_capability = IoCapability::NO_INPUT_NO_OUTPUT,
.oob_data_flag = OobDataFlag::NOT_PRESENT,
.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
@@ -398,24 +365,24 @@ TEST_F(PairingHandlerPairTest, test_secure_connections_just_works_peripheral_ini
.initiator_key_distribution = KeyMaskId | KeyMaskSign,
.responder_key_distribution = KeyMaskId | KeyMaskSign},
.remotely_initiated = false,
- .connection_handle = CONN_HANDLE_PERIPHERAL,
- .remote_connection_address = {ADDRESS_CENTRAL, ADDRESS_TYPE_CENTRAL},
- .user_interface = &peripheral_user_interface,
+ .connection_handle = CONN_HANDLE_SLAVE,
+ .remote_connection_address = {ADDRESS_MASTER, ADDRESS_TYPE_MASTER},
+ .user_interface = &slave_user_interface,
.user_interface_handler = handler_,
- .le_security_interface = &peripheral_le_security_mock,
+ .le_security_interface = &slave_le_security_mock,
.proper_l2cap_interface = up_buffer_b_.get(),
.l2cap_handler = handler_,
- .OnPairingFinished = OnPairingFinishedPeripheral,
+ .OnPairingFinished = OnPairingFinishedSlave,
};
std::unique_ptr<bluetooth::security::CommandView> first_pkt;
{
std::unique_lock<std::mutex> lock(handlers_initialization_guard);
- pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, peripheral_setup);
+ pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, slave_setup);
first_pkt = WaitFirstL2capCommand();
- EXPECT_CALL(central_user_interface, DisplayPairingPrompt(_, _))
+ EXPECT_CALL(master_user_interface, DisplayPairingPrompt(_, _))
.Times(1)
.WillOnce(InvokeWithoutArgs([&first_pkt, this] {
LOG_INFO("UI mock received pairing prompt");
@@ -428,256 +395,260 @@ TEST_F(PairingHandlerPairTest, test_secure_connections_just_works_peripheral_ini
// Simulate user accepting the pairing in UI
pairing_handler_a->OnUiAction(PairingEvent::PAIRING_ACCEPTED, 0x01 /* Non-zero value means success */);
- // Send the first packet from the peripheral to central
+ // Send the first packet from the slave to master
auto view_to_packet = std::make_unique<packet::RawBuilder>();
view_to_packet->AddOctets(std::vector(first_pkt->begin(), first_pkt->end()));
up_buffer_b_->Enqueue(std::move(view_to_packet), handler_);
}));
- pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, central_setup);
+ pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, master_setup);
}
pairing_handler_a->WaitUntilPairingFinished();
pairing_handler_b->WaitUntilPairingFinished();
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_central.value()));
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_peripheral.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_master.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_slave.value()));
}
TEST_F(PairingHandlerPairTest, test_secure_connections_numeric_comparison) {
- central_setup.myPairingCapabilities.io_capability = IoCapability::DISPLAY_YES_NO;
- central_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
- central_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc;
+ master_setup.myPairingCapabilities.io_capability = IoCapability::DISPLAY_YES_NO;
+ master_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
+ master_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc;
- peripheral_setup.myPairingCapabilities.io_capability = IoCapability::DISPLAY_YES_NO;
- peripheral_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
- peripheral_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc;
+ slave_setup.myPairingCapabilities.io_capability = IoCapability::DISPLAY_YES_NO;
+ slave_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
+ slave_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc;
- ConfirmationData data_peripheral;
+ uint32_t num_value_slave = 0;
{
std::unique_lock<std::mutex> lock(handlers_initialization_guard);
// Initiator must be initialized after the responder.
- pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, central_setup);
+ pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, master_setup);
while (!first_command_sent) {
std::this_thread::sleep_for(1ms);
LOG_INFO("waiting for first command...");
}
- peripheral_setup.pairing_request = PairingRequestView::Create(*first_command);
+ slave_setup.pairing_request = PairingRequestView::Create(*first_command);
- RecordPairingPromptHandling(peripheral_user_interface, &pairing_handler_b);
+ RecordPairingPromptHandling(slave_user_interface, &pairing_handler_b);
- EXPECT_CALL(peripheral_user_interface, DisplayConfirmValue(_)).WillOnce(SaveArg<0>(&data_peripheral));
- EXPECT_CALL(central_user_interface, DisplayConfirmValue(_)).WillOnce(Invoke([&](ConfirmationData data) {
- EXPECT_EQ(data_peripheral.GetNumericValue(), data.GetNumericValue());
- if (data_peripheral.GetNumericValue() == data.GetNumericValue()) {
- pairing_handler_a->OnUiAction(PairingEvent::CONFIRM_YESNO, 0x01);
- pairing_handler_b->OnUiAction(PairingEvent::CONFIRM_YESNO, 0x01);
- }
- }));
+ EXPECT_CALL(slave_user_interface, DisplayConfirmValue(_, _, _)).WillOnce(SaveArg<2>(&num_value_slave));
+ EXPECT_CALL(master_user_interface, DisplayConfirmValue(_, _, _))
+ .WillOnce(Invoke([&](const bluetooth::hci::AddressWithType&, std::string, uint32_t num_value) {
+ EXPECT_EQ(num_value_slave, num_value);
+ if (num_value_slave == num_value) {
+ pairing_handler_a->OnUiAction(PairingEvent::CONFIRM_YESNO, 0x01);
+ pairing_handler_b->OnUiAction(PairingEvent::CONFIRM_YESNO, 0x01);
+ }
+ }));
- pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, peripheral_setup);
+ pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, slave_setup);
}
pairing_handler_a->WaitUntilPairingFinished();
pairing_handler_b->WaitUntilPairingFinished();
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_central.value()));
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_peripheral.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_master.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_slave.value()));
}
TEST_F(PairingHandlerPairTest, test_secure_connections_passkey_entry) {
- central_setup.myPairingCapabilities.io_capability = IoCapability::KEYBOARD_ONLY;
- central_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
- central_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc;
+ master_setup.myPairingCapabilities.io_capability = IoCapability::KEYBOARD_ONLY;
+ master_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
+ master_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc;
- peripheral_setup.myPairingCapabilities.io_capability = IoCapability::DISPLAY_ONLY;
- peripheral_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
- peripheral_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc;
+ slave_setup.myPairingCapabilities.io_capability = IoCapability::DISPLAY_ONLY;
+ slave_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
+ slave_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc;
- // In this test either central or peripheral display the UI prompt first. This variable makes sure both prompts are
+ // In this test either master or slave display the UI prompt first. This variable makes sure both prompts are
// displayed before passkey is confirmed. Since both UI handlers are same thread, it's safe.
int ui_prompts_count = 0;
uint32_t passkey_ = std::numeric_limits<uint32_t>::max();
{
std::unique_lock<std::mutex> lock(handlers_initialization_guard);
- pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, central_setup);
+ pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, master_setup);
while (!first_command_sent) {
std::this_thread::sleep_for(1ms);
LOG_INFO("waiting for first command...");
}
- peripheral_setup.pairing_request = PairingRequestView::Create(*first_command);
+ slave_setup.pairing_request = PairingRequestView::Create(*first_command);
- RecordPairingPromptHandling(peripheral_user_interface, &pairing_handler_b);
+ RecordPairingPromptHandling(slave_user_interface, &pairing_handler_b);
- EXPECT_CALL(peripheral_user_interface, DisplayPasskey(_)).WillOnce(Invoke([&](ConfirmationData data) {
- passkey_ = data.GetNumericValue();
- ui_prompts_count++;
- if (ui_prompts_count == 2) {
- pairing_handler_a->OnUiAction(PairingEvent::PASSKEY, passkey_);
- }
- }));
+ EXPECT_CALL(slave_user_interface, DisplayPasskey(_, _, _))
+ .WillOnce(Invoke([&](const bluetooth::hci::AddressWithType& address, std::string name, uint32_t passkey) {
+ passkey_ = passkey;
+ ui_prompts_count++;
+ if (ui_prompts_count == 2) {
+ pairing_handler_a->OnUiAction(PairingEvent::PASSKEY, passkey);
+ }
+ }));
- EXPECT_CALL(central_user_interface, DisplayEnterPasskeyDialog(_)).WillOnce(Invoke([&](ConfirmationData data) {
- ui_prompts_count++;
- if (ui_prompts_count == 2) {
- pairing_handler_a->OnUiAction(PairingEvent::PASSKEY, passkey_);
- }
- }));
+ EXPECT_CALL(master_user_interface, DisplayEnterPasskeyDialog(_, _))
+ .WillOnce(Invoke([&](const bluetooth::hci::AddressWithType& address, std::string name) {
+ ui_prompts_count++;
+ if (ui_prompts_count == 2) {
+ pairing_handler_a->OnUiAction(PairingEvent::PASSKEY, passkey_);
+ }
+ }));
- pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, peripheral_setup);
+ pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, slave_setup);
}
// Initiator must be initialized after the responder.
pairing_handler_a->WaitUntilPairingFinished();
pairing_handler_b->WaitUntilPairingFinished();
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_central.value()));
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_peripheral.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_master.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_slave.value()));
}
TEST_F(PairingHandlerPairTest, test_secure_connections_out_of_band) {
- central_setup.myPairingCapabilities.io_capability = IoCapability::KEYBOARD_ONLY;
- central_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
- central_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
+ master_setup.myPairingCapabilities.io_capability = IoCapability::KEYBOARD_ONLY;
+ master_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
+ master_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
- peripheral_setup.myPairingCapabilities.io_capability = IoCapability::DISPLAY_ONLY;
- peripheral_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::PRESENT;
- peripheral_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
+ slave_setup.myPairingCapabilities.io_capability = IoCapability::DISPLAY_ONLY;
+ slave_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::PRESENT;
+ slave_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
- central_setup.my_oob_data = std::make_optional<MyOobData>(PairingHandlerLe::GenerateOobData());
- peripheral_setup.remote_oob_data =
+ master_setup.my_oob_data = std::make_optional<MyOobData>(PairingHandlerLe::GenerateOobData());
+ slave_setup.remote_oob_data =
std::make_optional<InitialInformations::out_of_band_data>(InitialInformations::out_of_band_data{
- .le_sc_c = central_setup.my_oob_data->c,
- .le_sc_r = central_setup.my_oob_data->r,
+ .le_sc_c = master_setup.my_oob_data->c,
+ .le_sc_r = master_setup.my_oob_data->r,
});
{
std::unique_lock<std::mutex> lock(handlers_initialization_guard);
- pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, central_setup);
+ pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, master_setup);
while (!first_command_sent) {
std::this_thread::sleep_for(1ms);
LOG_INFO("waiting for first command...");
}
- peripheral_setup.pairing_request = PairingRequestView::Create(*first_command);
+ slave_setup.pairing_request = PairingRequestView::Create(*first_command);
- RecordPairingPromptHandling(peripheral_user_interface, &pairing_handler_b);
+ RecordPairingPromptHandling(slave_user_interface, &pairing_handler_b);
- pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, peripheral_setup);
+ pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, slave_setup);
}
pairing_handler_a->WaitUntilPairingFinished();
pairing_handler_b->WaitUntilPairingFinished();
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_central.value()));
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_peripheral.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_master.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_slave.value()));
}
TEST_F(PairingHandlerPairTest, test_secure_connections_out_of_band_two_way) {
- central_setup.myPairingCapabilities.io_capability = IoCapability::KEYBOARD_ONLY;
- central_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::PRESENT;
- central_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
+ master_setup.myPairingCapabilities.io_capability = IoCapability::KEYBOARD_ONLY;
+ master_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::PRESENT;
+ master_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
- peripheral_setup.myPairingCapabilities.io_capability = IoCapability::DISPLAY_ONLY;
- peripheral_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::PRESENT;
- peripheral_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
+ slave_setup.myPairingCapabilities.io_capability = IoCapability::DISPLAY_ONLY;
+ slave_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::PRESENT;
+ slave_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm | AuthReqMaskSc,
- central_setup.my_oob_data = std::make_optional<MyOobData>(PairingHandlerLe::GenerateOobData());
- peripheral_setup.remote_oob_data =
+ master_setup.my_oob_data = std::make_optional<MyOobData>(PairingHandlerLe::GenerateOobData());
+ slave_setup.remote_oob_data =
std::make_optional<InitialInformations::out_of_band_data>(InitialInformations::out_of_band_data{
- .le_sc_c = central_setup.my_oob_data->c,
- .le_sc_r = central_setup.my_oob_data->r,
+ .le_sc_c = master_setup.my_oob_data->c,
+ .le_sc_r = master_setup.my_oob_data->r,
});
- peripheral_setup.my_oob_data = std::make_optional<MyOobData>(PairingHandlerLe::GenerateOobData());
- central_setup.remote_oob_data =
+ slave_setup.my_oob_data = std::make_optional<MyOobData>(PairingHandlerLe::GenerateOobData());
+ master_setup.remote_oob_data =
std::make_optional<InitialInformations::out_of_band_data>(InitialInformations::out_of_band_data{
- .le_sc_c = peripheral_setup.my_oob_data->c,
- .le_sc_r = peripheral_setup.my_oob_data->r,
+ .le_sc_c = slave_setup.my_oob_data->c,
+ .le_sc_r = slave_setup.my_oob_data->r,
});
{
std::unique_lock<std::mutex> lock(handlers_initialization_guard);
- pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, central_setup);
+ pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, master_setup);
while (!first_command_sent) {
std::this_thread::sleep_for(1ms);
LOG_INFO("waiting for first command...");
}
- peripheral_setup.pairing_request = PairingRequestView::Create(*first_command);
+ slave_setup.pairing_request = PairingRequestView::Create(*first_command);
- RecordPairingPromptHandling(peripheral_user_interface, &pairing_handler_b);
+ RecordPairingPromptHandling(slave_user_interface, &pairing_handler_b);
- pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, peripheral_setup);
+ pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, slave_setup);
}
pairing_handler_a->WaitUntilPairingFinished();
pairing_handler_b->WaitUntilPairingFinished();
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_central.value()));
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_peripheral.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_master.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_slave.value()));
}
TEST_F(PairingHandlerPairTest, test_legacy_just_works) {
- central_setup.myPairingCapabilities.io_capability = IoCapability::NO_INPUT_NO_OUTPUT;
- central_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
- central_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm,
+ master_setup.myPairingCapabilities.io_capability = IoCapability::NO_INPUT_NO_OUTPUT;
+ master_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
+ master_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm,
- peripheral_setup.myPairingCapabilities.io_capability = IoCapability::NO_INPUT_NO_OUTPUT;
- peripheral_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
- peripheral_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm;
+ slave_setup.myPairingCapabilities.io_capability = IoCapability::NO_INPUT_NO_OUTPUT;
+ slave_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
+ slave_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm;
{
std::unique_lock<std::mutex> lock(handlers_initialization_guard);
- pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, central_setup);
+ pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, master_setup);
while (!first_command_sent) {
std::this_thread::sleep_for(1ms);
LOG_INFO("waiting for first command...");
}
- peripheral_setup.pairing_request = PairingRequestView::Create(*first_command);
+ slave_setup.pairing_request = PairingRequestView::Create(*first_command);
- RecordPairingPromptHandling(peripheral_user_interface, &pairing_handler_b);
+ RecordPairingPromptHandling(slave_user_interface, &pairing_handler_b);
- pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, peripheral_setup);
+ pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, slave_setup);
}
pairing_handler_a->WaitUntilPairingFinished();
pairing_handler_b->WaitUntilPairingFinished();
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_central.value()));
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_peripheral.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_master.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_slave.value()));
}
TEST_F(PairingHandlerPairTest, test_legacy_passkey_entry) {
- central_setup.myPairingCapabilities.io_capability = IoCapability::KEYBOARD_DISPLAY;
- central_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
- central_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm,
+ master_setup.myPairingCapabilities.io_capability = IoCapability::KEYBOARD_DISPLAY;
+ master_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
+ master_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm,
- peripheral_setup.myPairingCapabilities.io_capability = IoCapability::KEYBOARD_ONLY;
- peripheral_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
- peripheral_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm;
+ slave_setup.myPairingCapabilities.io_capability = IoCapability::KEYBOARD_ONLY;
+ slave_setup.myPairingCapabilities.oob_data_flag = OobDataFlag::NOT_PRESENT;
+ slave_setup.myPairingCapabilities.auth_req = AuthReqMaskBondingFlag | AuthReqMaskMitm;
{
std::unique_lock<std::mutex> lock(handlers_initialization_guard);
- pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, central_setup);
+ pairing_handler_a = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, master_setup);
while (!first_command_sent) {
std::this_thread::sleep_for(1ms);
LOG_INFO("waiting for first command...");
}
- peripheral_setup.pairing_request = PairingRequestView::Create(*first_command);
+ slave_setup.pairing_request = PairingRequestView::Create(*first_command);
- RecordPairingPromptHandling(peripheral_user_interface, &pairing_handler_b);
+ RecordPairingPromptHandling(slave_user_interface, &pairing_handler_b);
- EXPECT_CALL(peripheral_user_interface, DisplayEnterPasskeyDialog(_));
- EXPECT_CALL(central_user_interface, DisplayConfirmValue(_)).WillOnce(Invoke([&](ConfirmationData data) {
- LOG_INFO("Passkey prompt displayed entering passkey: %08x", data.GetNumericValue());
- std::this_thread::sleep_for(1ms);
+ EXPECT_CALL(slave_user_interface, DisplayEnterPasskeyDialog(_, _));
+ EXPECT_CALL(master_user_interface, DisplayConfirmValue(_, _, _))
+ .WillOnce(Invoke([&](const bluetooth::hci::AddressWithType&, std::string, uint32_t passkey) {
+ LOG_INFO("Passkey prompt displayed entering passkey: %08x", passkey);
+ std::this_thread::sleep_for(1ms);
- // TODO: handle case where prompts are displayed in different order in the test!
- pairing_handler_b->OnUiAction(PairingEvent::PASSKEY, data.GetNumericValue());
- }));
+ // TODO: handle case where prompts are displayed in different order in the test!
+ pairing_handler_b->OnUiAction(PairingEvent::PASSKEY, passkey);
+ }));
- pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, peripheral_setup);
+ pairing_handler_b = std::make_unique<PairingHandlerLe>(PairingHandlerLe::PHASE1, slave_setup);
}
pairing_handler_a->WaitUntilPairingFinished();
pairing_handler_b->WaitUntilPairingFinished();
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_central.value()));
- EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_peripheral.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_master.value()));
+ EXPECT_TRUE(std::holds_alternative<PairingResult>(pairing_result_slave.value()));
}
} // namespace security
diff --git a/gd/security/ui.h b/gd/security/ui.h
index d4ead9a36..ceecd14b5 100644
--- a/gd/security/ui.h
+++ b/gd/security/ui.h
@@ -23,75 +23,10 @@
namespace bluetooth {
namespace security {
-class ConfirmationData {
- public:
- ConfirmationData() : address_with_type_(hci::AddressWithType()), name_("No name set") {}
- ConfirmationData(bluetooth::hci::AddressWithType address_with_type, std::string name)
- : address_with_type_(address_with_type), name_(name) {}
- ConfirmationData(bluetooth::hci::AddressWithType address_with_type, std::string name, uint32_t numeric_value)
- : address_with_type_(address_with_type), name_(name), numeric_value_(numeric_value) {}
-
- const bluetooth::hci::AddressWithType& GetAddressWithType() {
- return address_with_type_;
- }
-
- std::string GetName() {
- return name_;
- }
-
- uint32_t GetNumericValue() {
- return numeric_value_;
- }
-
- hci::IoCapability GetRemoteIoCaps() const {
- return remote_io_caps_;
- }
- void SetRemoteIoCaps(hci::IoCapability remote_io_caps) {
- remote_io_caps_ = remote_io_caps;
- }
-
- hci::AuthenticationRequirements GetRemoteAuthReqs() const {
- return remote_auth_reqs_;
- }
-
- void SetRemoteAuthReqs(hci::AuthenticationRequirements remote_auth_reqs) {
- remote_auth_reqs_ = remote_auth_reqs;
- }
-
- hci::OobDataPresent GetRemoteOobDataPresent() const {
- return remote_oob_data_present_;
- }
-
- void SetRemoteOobDataPresent(hci::OobDataPresent remote_oob_data_present) {
- remote_oob_data_present_ = remote_oob_data_present;
- }
-
- bool IsJustWorks() const {
- return just_works_;
- }
-
- void SetJustWorks(bool just_works) {
- just_works_ = just_works;
- }
-
- private:
- bluetooth::hci::AddressWithType address_with_type_;
- std::string name_;
- // Can either be the confirmation value or the passkey
- uint32_t numeric_value_ = 0;
-
- // TODO(optedoblivion): Revisit after shim/BTA layer is gone
- // Extra data is a hack to get data from the module to the shim
- hci::IoCapability remote_io_caps_ = hci::IoCapability::DISPLAY_YES_NO;
- hci::AuthenticationRequirements remote_auth_reqs_ = hci::AuthenticationRequirements::DEDICATED_BONDING;
- hci::OobDataPresent remote_oob_data_present_ = hci::OobDataPresent::NOT_PRESENT;
- bool just_works_ = false;
-};
-
// Through this interface we talk to the user, asking for confirmations/acceptance.
class UI {
public:
- virtual ~UI() = default;
+ virtual ~UI(){};
/* Remote LE device tries to initiate pairing, ask user to confirm */
virtual void DisplayPairingPrompt(const bluetooth::hci::AddressWithType& address, std::string name) = 0;
@@ -100,20 +35,18 @@ class UI {
* bond with this device */
virtual void Cancel(const bluetooth::hci::AddressWithType& address) = 0;
- /* Display value for Comparison, user responds yes/no */
- virtual void DisplayConfirmValue(ConfirmationData data) = 0;
+ /* Display value for Comprision, user responds yes/no */
+ virtual void DisplayConfirmValue(const bluetooth::hci::AddressWithType& address, std::string name,
+ uint32_t numeric_value) = 0;
/* Display Yes/No dialog, Classic pairing, numeric comparison with NoInputNoOutput device */
- virtual void DisplayYesNoDialog(ConfirmationData data) = 0;
+ virtual void DisplayYesNoDialog(const bluetooth::hci::AddressWithType& address, std::string name) = 0;
/* Display a dialog box that will let user enter the Passkey */
- virtual void DisplayEnterPasskeyDialog(ConfirmationData data) = 0;
+ virtual void DisplayEnterPasskeyDialog(const bluetooth::hci::AddressWithType& address, std::string name) = 0;
/* Present the passkey value to the user, user compares with other device */
- virtual void DisplayPasskey(ConfirmationData data) = 0;
-
- /* Ask the user to enter a PIN */
- virtual void DisplayEnterPinDialog(ConfirmationData data) = 0;
+ virtual void DisplayPasskey(const bluetooth::hci::AddressWithType& address, std::string name, uint32_t passkey) = 0;
};
/* Through this interface, UI provides us with user choices. */
@@ -129,9 +62,6 @@ class UICallbacks {
/* User typed the value displayed on the other device. This is either Passkey or the Confirm value */
virtual void OnPasskeyEntry(const bluetooth::hci::AddressWithType& address, uint32_t passkey) = 0;
-
- /* User typed the PIN for the other device. */
- virtual void OnPinEntry(const bluetooth::hci::AddressWithType& address, std::vector<uint8_t> pin) = 0;
};
} // namespace security
diff --git a/gd/setup.py b/gd/setup.py
deleted file mode 100644
index 1a8734af7..000000000
--- a/gd/setup.py
+++ /dev/null
@@ -1,113 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-from distutils import log
-from distutils.errors import DistutilsModuleError
-import os
-from setuptools import find_packages
-from setuptools import setup
-from setuptools.command.install import install
-import stat
-import subprocess
-import sys
-
-install_requires = [
- 'grpcio',
- 'psutil',
-]
-
-host_executables = [
- 'root-canal',
- 'bluetooth_stack_with_facade', # c++
- 'bluetooth_with_facades', # rust
-]
-
-
-# Need to verify acts is importable in a new Python context
-def is_acts_importable():
- cmd = [sys.executable, '-c', 'import acts']
- completed_process = subprocess.run(cmd, cwd=os.getcwd())
- return completed_process.returncode == 0
-
-
-def setup_acts_for_cmd_or_die(cmd_str):
- acts_framework_dir = os.path.abspath('acts_framework')
- acts_setup_bin = os.path.join(acts_framework_dir, 'setup.py')
- cmd = [sys.executable, acts_setup_bin, cmd_str]
- subprocess.run(cmd, cwd=acts_framework_dir, check=True)
-
-
-def set_permissions_for_host_executables(outputs):
- for file in outputs:
- if os.path.basename(file) in host_executables:
- current_mode = os.stat(file).st_mode
- new_mode = current_mode | stat.S_IEXEC
- os.chmod(file, new_mode)
- log.log(log.INFO, "Changed file mode of %s from %s to %s" % (file, oct(current_mode), oct(new_mode)))
-
-
-class InstallLocalPackagesForInstallation(install):
-
- user_options = install.user_options + [
- ('reuse-acts', None, "Skip ACTS installation if already installed"),
- ]
- boolean_options = install.boolean_options + ['reuse-acts']
-
- def initialize_options(self):
- install.initialize_options(self)
- self.reuse_acts = False
-
- def run(self):
- if self.reuse_acts and is_acts_importable():
- self.announce('Reusing existing ACTS installation', log.WARN)
- else:
- self.announce('Installing ACTS library', log.WARN)
- setup_acts_for_cmd_or_die("install")
- self.announce('ACTS installed.', log.WARN)
- if not is_acts_importable():
- raise DistutilsModuleError("Cannot import acts after installation")
- install.run(self)
- set_permissions_for_host_executables(self.get_outputs())
-
-
-def main():
- # Relative path from calling directory to this file
- our_dir = os.path.dirname(__file__)
- # Must cd into this dir for package resolution to work
- # This won't affect the calling shell
- os.chdir(our_dir)
- setup(
- name='bluetooth_cert_tests',
- version='1.0',
- author='Android Open Source Project',
- license='Apache2.0',
- description="""Bluetooth Cert Tests Package""",
- # Include root package so that bluetooth_packets_python3.so can be
- # included as well
- packages=[''] +
- find_packages(exclude=['acts_framework', 'acts_framework.*', 'llvm_binutils', 'llvm_binutils.*']),
- install_requires=install_requires,
- package_data={
- '': host_executables + ['*.so', 'lib64/*.so', 'target/*', 'llvm_binutils/bin/*', 'llvm_binutils/lib64/*'],
- 'cert': ['all_test_cases'],
- },
- cmdclass={
- 'install': InstallLocalPackagesForInstallation,
- })
-
-
-if __name__ == '__main__':
- main()
diff --git a/gd/shim/Android.bp b/gd/shim/Android.bp
index 48293bd48..a38272b5b 100644
--- a/gd/shim/Android.bp
+++ b/gd/shim/Android.bp
@@ -1,31 +1,17 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothShimSources",
srcs: [
"dumpsys.cc",
- "dumpsys_args.cc",
+ "l2cap.cc",
+ "stack.cc",
]
}
filegroup {
name: "BluetoothShimTestSources",
srcs: [
- "dumpsys_test.cc",
- "dumpsys_args_test.cc",
+ "l2cap_test.cc",
],
}
-filegroup {
- name: "BluetoothFacade_shim_layer",
- srcs: [
- "facade/facade.cc",
- ],
-}
+
diff --git a/gd/shim/BUILD.gn b/gd/shim/BUILD.gn
deleted file mode 100644
index 59dbb3721..000000000
--- a/gd/shim/BUILD.gn
+++ /dev/null
@@ -1,31 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-source_set("BluetoothShimSources") {
- sources = [
- "dumpsys.cc",
- "dumpsys_args.cc",
- ]
-
- deps = [
- "//bt/gd/dumpsys:BluetoothGeneratedDumpsysBundledSchema_h",
- "//bt/gd/dumpsys/bundler:BluetoothGeneratedBundlerSchema_h_bfbs",
- ]
-
- configs += [
- "//bt/gd:gd_defaults",
- "//bt:external_flatbuffers",
- ]
-}
diff --git a/gd/shim/cert/shim_test.py b/gd/shim/cert/shim_test.py
deleted file mode 100644
index bc2fca6c1..000000000
--- a/gd/shim/cert/shim_test.py
+++ /dev/null
@@ -1,37 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright 2020 - The Android Open Source Project
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-import os
-import sys
-import logging
-
-from cert.event_stream import EventStream
-from cert.gd_base_test import GdBaseTestClass
-from cert.truth import assertThat
-from facade import common_pb2 as common
-from facade import rootservice_pb2 as facade_rootservice
-from google.protobuf import empty_pb2 as empty_proto
-from shim.facade import facade_pb2 as shim_facade
-
-
-class ShimTest(GdBaseTestClass):
-
- def setup_class(self):
- super().setup_class(dut_module='SHIM', cert_module='SHIM')
-
- def test_dumpsys(self):
- result = self.cert.shim.Dump(empty_proto.Empty())
- result = self.dut.shim.Dump(empty_proto.Empty())
diff --git a/gd/shim/cert/stack_test.py b/gd/shim/cert/stack_test.py
index 3daecc0c8..ad4fb9b3d 100644
--- a/gd/shim/cert/stack_test.py
+++ b/gd/shim/cert/stack_test.py
@@ -17,13 +17,25 @@
import os
import sys
-from cert.gd_base_test import GdBaseTestClass
+from cert.gd_base_test_facade_only import GdFacadeOnlyBaseTestClass
+from google.protobuf import empty_pb2 as empty_proto
+from facade import rootservice_pb2 as facade_rootservice
+from hci.facade import controller_facade_pb2 as controller_facade
-class StackTest(GdBaseTestClass):
+class StackTest(GdFacadeOnlyBaseTestClass):
- def setup_class(self):
- super().setup_class(dut_module='SHIM', cert_module='SHIM')
+ def setup_test(self):
+ self.device_under_test.rootservice.StartStack(
+ facade_rootservice.StartStackRequest(
+ module_under_test=facade_rootservice.BluetoothModule.Value(
+ 'SHIM'),))
+
+ self.device_under_test.wait_channel_ready()
+
+ def teardown_test(self):
+ self.device_under_test.rootservice.StopStack(
+ facade_rootservice.StopStackRequest())
def test_test(self):
return True
diff --git a/gd/shim/dumpsys.cc b/gd/shim/dumpsys.cc
index 7148bb364..6f6677023 100644
--- a/gd/shim/dumpsys.cc
+++ b/gd/shim/dumpsys.cc
@@ -15,141 +15,72 @@
*/
#define LOG_TAG "bt_gd_shim"
+#include <algorithm>
+#include <functional>
#include <future>
+#include <memory>
#include <string>
+#include <unordered_map>
+#include <utility>
-#include "dumpsys/filter.h"
-#include "generated_dumpsys_bundled_schema.h"
#include "module.h"
+#include "os/handler.h"
#include "os/log.h"
-#include "os/system_properties.h"
#include "shim/dumpsys.h"
-#include "shim/dumpsys_args.h"
namespace bluetooth {
namespace shim {
-static const std::string kReadOnlyDebuggableProperty = "ro.debuggable";
-
namespace {
constexpr char kModuleName[] = "shim::Dumpsys";
-constexpr char kDumpsysTitle[] = "----- Gd Dumpsys ------";
} // namespace
struct Dumpsys::impl {
public:
- void DumpWithArgsSync(int fd, const char** args, std::promise<void> promise);
- int GetNumberOfBundledSchemas() const;
+ void Dump(int fd, std::promise<void> promise);
+ void RegisterDumpsysFunction(const void* token, DumpsysFunction func);
+ void UnregisterDumpsysFunction(const void* token);
- impl(const Dumpsys& dumpsys_module, const dumpsys::ReflectionSchema& reflection_schema);
~impl() = default;
- protected:
- void FilterAsUser(std::string* dumpsys_data);
- void FilterAsDeveloper(std::string* dumpsys_data);
- std::string PrintAsJson(std::string* dumpsys_data) const;
-
- bool IsDebuggable() const;
-
private:
- void DumpWithArgsAsync(int fd, const char** args);
-
- const Dumpsys& dumpsys_module_;
- const dumpsys::ReflectionSchema reflection_schema_;
+ std::unordered_map<const void*, DumpsysFunction> dumpsys_functions_;
};
-const ModuleFactory Dumpsys::Factory =
- ModuleFactory([]() { return new Dumpsys(bluetooth::dumpsys::GetBundledSchemaData()); });
-
-Dumpsys::impl::impl(const Dumpsys& dumpsys_module, const dumpsys::ReflectionSchema& reflection_schema)
- : dumpsys_module_(dumpsys_module), reflection_schema_(std::move(reflection_schema)) {}
-
-int Dumpsys::impl::GetNumberOfBundledSchemas() const {
- return reflection_schema_.GetNumberOfBundledSchemas();
-}
-
-bool Dumpsys::impl::IsDebuggable() const {
- return (os::GetSystemProperty(kReadOnlyDebuggableProperty) == "1");
-}
+const ModuleFactory Dumpsys::Factory = ModuleFactory([]() { return new Dumpsys(); });
-void Dumpsys::impl::FilterAsDeveloper(std::string* dumpsys_data) {
- ASSERT(dumpsys_data != nullptr);
- dumpsys::FilterInPlace(dumpsys::FilterType::AS_DEVELOPER, reflection_schema_, dumpsys_data);
+void Dumpsys::impl::Dump(int fd, std::promise<void> promise) {
+ dprintf(fd, "%s Registered submodules:%zd\n", kModuleName, dumpsys_functions_.size());
+ std::for_each(dumpsys_functions_.begin(), dumpsys_functions_.end(),
+ [fd](std::pair<const void*, DumpsysFunction> element) { element.second(fd); });
+ promise.set_value();
}
-void Dumpsys::impl::FilterAsUser(std::string* dumpsys_data) {
- ASSERT(dumpsys_data != nullptr);
- dumpsys::FilterInPlace(dumpsys::FilterType::AS_USER, reflection_schema_, dumpsys_data);
+void Dumpsys::impl::RegisterDumpsysFunction(const void* token, DumpsysFunction func) {
+ ASSERT(dumpsys_functions_.find(token) == dumpsys_functions_.end());
+ dumpsys_functions_[token] = func;
}
-std::string Dumpsys::impl::PrintAsJson(std::string* dumpsys_data) const {
- ASSERT(dumpsys_data != nullptr);
-
- const std::string root_name = reflection_schema_.GetRootName();
- if (root_name.empty()) {
- char buf[255];
- snprintf(buf, sizeof(buf), "ERROR: Unable to find root name in prebundled reflection schema\n");
- LOG_WARN("%s", buf);
- return std::string(buf);
- }
-
- const reflection::Schema* schema = reflection_schema_.FindInReflectionSchema(root_name);
- if (schema == nullptr) {
- char buf[255];
- snprintf(buf, sizeof(buf), "ERROR: Unable to find schema root name:%s\n", root_name.c_str());
- LOG_WARN("%s", buf);
- return std::string(buf);
- }
-
- flatbuffers::Parser parser;
- if (!parser.Deserialize(schema)) {
- char buf[255];
- snprintf(buf, sizeof(buf), "ERROR: Unable to deserialize bundle root name:%s\n", root_name.c_str());
- LOG_WARN("%s", buf);
- return std::string(buf);
- }
-
- std::string jsongen;
- flatbuffers::GenerateText(parser, dumpsys_data->data(), &jsongen);
- return jsongen;
+void Dumpsys::impl::UnregisterDumpsysFunction(const void* token) {
+ ASSERT(dumpsys_functions_.find(token) != dumpsys_functions_.end());
+ dumpsys_functions_.erase(token);
}
-void Dumpsys::impl::DumpWithArgsAsync(int fd, const char** args) {
- ParsedDumpsysArgs parsed_dumpsys_args(args);
- const auto registry = dumpsys_module_.GetModuleRegistry();
-
- ModuleDumper dumper(*registry, kDumpsysTitle);
- std::string dumpsys_data;
- dumper.DumpState(&dumpsys_data);
-
- if (parsed_dumpsys_args.IsDeveloper() || IsDebuggable()) {
- dprintf(fd, " ----- Filtering as Developer -----\n");
- FilterAsDeveloper(&dumpsys_data);
- } else {
- dprintf(fd, " ----- Filtering as User -----\n");
- FilterAsUser(&dumpsys_data);
- }
-
- dprintf(fd, "%s", PrintAsJson(&dumpsys_data).c_str());
-}
-
-void Dumpsys::impl::DumpWithArgsSync(int fd, const char** args, std::promise<void> promise) {
- DumpWithArgsAsync(fd, args);
- promise.set_value();
-}
-
-Dumpsys::Dumpsys(const std::string& pre_bundled_schema)
- : reflection_schema_(dumpsys::ReflectionSchema(pre_bundled_schema)) {}
-
-void Dumpsys::Dump(int fd, const char** args) {
+void Dumpsys::Dump(int fd) {
std::promise<void> promise;
auto future = promise.get_future();
- CallOn(pimpl_.get(), &Dumpsys::impl::DumpWithArgsSync, fd, args, std::move(promise));
+ GetHandler()->Post(common::BindOnce(&Dumpsys::impl::Dump, common::Unretained(pimpl_.get()), fd, std::move(promise)));
future.get();
}
-void Dumpsys::Dump(int fd, const char** args, std::promise<void> promise) {
- CallOn(pimpl_.get(), &Dumpsys::impl::DumpWithArgsSync, fd, args, std::move(promise));
+void Dumpsys::RegisterDumpsysFunction(const void* token, DumpsysFunction func) {
+ GetHandler()->Post(
+ common::BindOnce(&Dumpsys::impl::RegisterDumpsysFunction, common::Unretained(pimpl_.get()), token, func));
+}
+
+void Dumpsys::UnregisterDumpsysFunction(const void* token) {
+ GetHandler()->Post(
+ common::BindOnce(&Dumpsys::impl::UnregisterDumpsysFunction, common::Unretained(pimpl_.get()), token));
}
os::Handler* Dumpsys::GetGdShimHandler() {
@@ -162,36 +93,13 @@ os::Handler* Dumpsys::GetGdShimHandler() {
void Dumpsys::ListDependencies(ModuleList* list) {}
void Dumpsys::Start() {
- pimpl_ = std::make_unique<impl>(*this, reflection_schema_);
+ pimpl_ = std::make_unique<impl>();
}
void Dumpsys::Stop() {
pimpl_.reset();
}
-DumpsysDataFinisher Dumpsys::GetDumpsysData(flatbuffers::FlatBufferBuilder* fb_builder) const {
- auto name = fb_builder->CreateString("----- Shim Dumpsys -----");
- auto example_piecemeal_string = fb_builder->CreateString("Example Piecemeal String");
- auto example_instant_string = fb_builder->CreateString("Example Instant String");
-
- ExamplePiecemealTableBuilder example_piecemeal_table_builder(*fb_builder);
- example_piecemeal_table_builder.add_example_string(example_piecemeal_string);
- example_piecemeal_table_builder.add_example_int(123);
- example_piecemeal_table_builder.add_example_float(1.23);
- auto example_piecemeal_table = example_piecemeal_table_builder.Finish();
-
- auto example_instant_table = CreateExampleInstantTable(*fb_builder, example_instant_string, 246, 2.46);
-
- DumpsysModuleDataBuilder builder(*fb_builder);
- builder.add_title(name);
- builder.add_number_of_bundled_schemas(pimpl_->GetNumberOfBundledSchemas());
- builder.add_example_piecemeal_table(example_piecemeal_table);
- builder.add_example_instant_table(example_instant_table);
- auto dumpsys_data = builder.Finish();
-
- return [dumpsys_data](DumpsysDataBuilder* builder) { builder->add_shim_dumpsys_data(dumpsys_data); };
-}
-
std::string Dumpsys::ToString() const {
return kModuleName;
}
diff --git a/gd/shim/dumpsys.fbs b/gd/shim/dumpsys.fbs
deleted file mode 100644
index 40ca1f5f7..000000000
--- a/gd/shim/dumpsys.fbs
+++ /dev/null
@@ -1,25 +0,0 @@
-// shim::dumpsys data
-namespace bluetooth.shim;
-
-attribute "privacy";
-
-table ExamplePiecemealTable {
- example_string:string (privacy:"Any");
- example_int:int (privacy:"Any");
- example_float:float (privacy:"Any");
-}
-
-table ExampleInstantTable {
- example_string:string (privacy:"Any");
- example_int:int (privacy:"Any");
- example_float:float (privacy:"Any");
-}
-
-table DumpsysModuleData {
- title:string (privacy:"Any");
- number_of_bundled_schemas:int (privacy:"Any");
- example_piecemeal_table:ExamplePiecemealTable (privacy:"Any");
- example_instant_table:ExampleInstantTable (privacy:"Any");
-}
-
-root_type DumpsysModuleData;
diff --git a/gd/shim/dumpsys.h b/gd/shim/dumpsys.h
index e843db7de..197ad3e91 100644
--- a/gd/shim/dumpsys.h
+++ b/gd/shim/dumpsys.h
@@ -15,27 +15,26 @@
*/
#pragma once
-#include <future>
#include <memory>
#include <string>
-#include "dumpsys/reflection_schema.h"
#include "module.h"
namespace bluetooth {
namespace shim {
-constexpr char kArgumentDeveloper[] = "--dev";
+using DumpsysFunction = std::function<void(int fd)>;
class Dumpsys : public bluetooth::Module {
public:
- void Dump(int fd, const char** args);
- void Dump(int fd, const char** args, std::promise<void> promise);
+ void Dump(int fd);
+ void RegisterDumpsysFunction(const void* token, DumpsysFunction func);
+ void UnregisterDumpsysFunction(const void* token);
- // Convenience thread used by shim layer for task execution
+ /* This is not a dumpsys-specific method, we just must grab thread from of one modules */
os::Handler* GetGdShimHandler();
- Dumpsys(const std::string& pre_bundled_schema);
+ Dumpsys() = default;
~Dumpsys() = default;
static const ModuleFactory Factory;
@@ -45,12 +44,10 @@ class Dumpsys : public bluetooth::Module {
void Start() override; // Module
void Stop() override; // Module
std::string ToString() const override; // Module
- DumpsysDataFinisher GetDumpsysData(flatbuffers::FlatBufferBuilder* builder) const override; // Module
private:
struct impl;
std::unique_ptr<impl> pimpl_;
- const dumpsys::ReflectionSchema reflection_schema_;
DISALLOW_COPY_AND_ASSIGN(Dumpsys);
};
diff --git a/gd/shim/dumpsys_args.cc b/gd/shim/dumpsys_args.cc
deleted file mode 100644
index c196ed129..000000000
--- a/gd/shim/dumpsys_args.cc
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "shim/dumpsys_args.h"
-#include "shim/dumpsys.h"
-
-#include <cstring>
-
-using namespace bluetooth;
-
-shim::ParsedDumpsysArgs::ParsedDumpsysArgs(const char** args) {
- if (args == nullptr) return;
- const char* p = *args;
- while (p != nullptr) {
- num_args_++;
- if (!std::strcmp(p, kArgumentDeveloper)) {
- dev_arg_ = true;
- } else {
- // silently ignore unexpected option
- }
- if (++args == nullptr) break;
- p = *args;
- }
-}
-
-bool shim::ParsedDumpsysArgs::IsDeveloper() const {
- return dev_arg_;
-}
diff --git a/gd/shim/dumpsys_args.h b/gd/shim/dumpsys_args.h
deleted file mode 100644
index 0979799a1..000000000
--- a/gd/shim/dumpsys_args.h
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-namespace bluetooth {
-namespace shim {
-
-class ParsedDumpsysArgs {
- public:
- ParsedDumpsysArgs(const char** args);
- bool IsDeveloper() const;
-
- private:
- unsigned num_args_{0};
- bool dev_arg_{false};
-};
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/gd/shim/dumpsys_args_test.cc b/gd/shim/dumpsys_args_test.cc
deleted file mode 100644
index db98bacce..000000000
--- a/gd/shim/dumpsys_args_test.cc
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "shim/dumpsys_args.h"
-#include "shim/dumpsys.h"
-
-#include <gtest/gtest.h>
-
-using namespace bluetooth;
-
-namespace testing {
-
-TEST(DumpsysArgsTest, no_args) {
- shim::ParsedDumpsysArgs parsed_dumpsys_args(nullptr);
- ASSERT_FALSE(parsed_dumpsys_args.IsDeveloper());
-}
-
-TEST(DumpsysArgsTest, parsed_args_without_dev) {
- const char* args[]{
- nullptr,
- };
- shim::ParsedDumpsysArgs parsed_dumpsys_args(args);
- ASSERT_FALSE(parsed_dumpsys_args.IsDeveloper());
-}
-
-TEST(DumpsysArgsTest, parsed_args_with_dev) {
- const char* args[]{
- bluetooth::shim::kArgumentDeveloper,
- nullptr,
- };
- shim::ParsedDumpsysArgs parsed_dumpsys_args(args);
- ASSERT_TRUE(parsed_dumpsys_args.IsDeveloper());
-}
-
-} // namespace testing
diff --git a/gd/shim/dumpsys_test.cc b/gd/shim/dumpsys_test.cc
deleted file mode 100644
index 17e9b8e47..000000000
--- a/gd/shim/dumpsys_test.cc
+++ /dev/null
@@ -1,138 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gtest/gtest.h>
-#include <sys/socket.h>
-#include <sys/types.h>
-
-#include <future>
-
-#include "module.h"
-#include "os/thread.h"
-#include "shim/dumpsys.h"
-#include "shim/dumpsys_args.h"
-#include "test_data/dumpsys_test_data_bin.h"
-
-namespace testing {
-
-using bluetooth::TestModuleRegistry;
-using namespace bluetooth;
-
-namespace {
-
-bool SimpleJsonValidator(int fd, int* dumpsys_byte_cnt) {
- char buf{0};
- bool within_double_quotes{false};
- int left_bracket{0}, right_bracket{0};
- while (read(fd, &buf, 1) != -1) {
- switch (buf) {
- (*dumpsys_byte_cnt)++;
- case '"':
- within_double_quotes = !within_double_quotes;
- break;
- case '{':
- if (!within_double_quotes) {
- left_bracket++;
- }
- break;
- case '}':
- if (!within_double_quotes) {
- right_bracket++;
- }
- break;
- default:
- break;
- }
- }
- return left_bracket == right_bracket;
-}
-
-} // namespace
-
-// TODO(cmanton) maybe create in build
-// To create dumpsys_test_header_bin.h:
-// make bluetooth_flatbuffer_bundler
-// ${ANDROID_BUILD_TOP}/out/host/linux-x86/bin/bluetooth_flatbuffer_bundler -w -m bluetooth.DumpsysData -f
-// test_gen/dumpsys_test_data_bin -n bluetooth::test test_gen/*
-
-class DumpsysTest : public Test {
- protected:
- void SetUp() override {
- dumpsys_module_ = new bluetooth::shim::Dumpsys(bluetooth::test::GetBundledSchemaData());
- fake_registry_.InjectTestModule(&shim::Dumpsys::Factory, dumpsys_module_);
- }
-
- void TearDown() override {
- fake_registry_.StopAll();
- }
-
- void Print() {
- dumpsys_module_->Dump(0, nullptr);
- }
-
- int GetSocketBufferSize(int sockfd) {
- int socket_buffer_size;
- socklen_t optlen = sizeof(socket_buffer_size);
- getsockopt(sockfd, SOL_SOCKET, SO_RCVBUF, (void*)&socket_buffer_size, &optlen);
- return socket_buffer_size;
- }
-
- void SetSocketBufferSize(int sockfd, int socket_buffer_size) {
- socklen_t optlen = sizeof(socket_buffer_size);
- ASSERT_EQ(0, setsockopt(sockfd, SOL_SOCKET, SO_RCVBUF, (const void*)&socket_buffer_size, optlen));
- }
-
- TestModuleRegistry fake_registry_;
- os::Thread& thread_ = fake_registry_.GetTestThread();
- bluetooth::shim::Dumpsys* dumpsys_module_ = nullptr;
- os::Handler* client_handler_ = nullptr;
-};
-
-TEST_F(DumpsysTest, dump_as_developer) {
- const char* args[]{bluetooth::shim::kArgumentDeveloper, nullptr};
-
- int sv[2];
- ASSERT_EQ(0, socketpair(AF_LOCAL, SOCK_STREAM | SOCK_NONBLOCK, 0, sv));
- int socket_buffer_size = GetSocketBufferSize(sv[0]);
-
- std::promise<void> promise;
- std::future future = promise.get_future();
- dumpsys_module_->Dump(sv[0], args, std::move(promise));
- future.wait();
-
- int dumpsys_byte_cnt = 0;
- ASSERT_TRUE(SimpleJsonValidator(sv[1], &dumpsys_byte_cnt));
- ASSERT_TRUE(dumpsys_byte_cnt < socket_buffer_size);
-}
-
-TEST_F(DumpsysTest, dump_as_user) {
- const char* args[]{"not-a-developer-option", nullptr};
-
- int sv[2];
- ASSERT_EQ(0, socketpair(AF_LOCAL, SOCK_STREAM | SOCK_NONBLOCK, 0, sv));
- int socket_buffer_size = GetSocketBufferSize(sv[0]);
-
- std::promise<void> promise;
- std::future future = promise.get_future();
- dumpsys_module_->Dump(sv[0], args, std::move(promise));
- future.wait();
-
- int dumpsys_byte_cnt = 0;
- ASSERT_TRUE(SimpleJsonValidator(sv[1], &dumpsys_byte_cnt));
- ASSERT_TRUE(dumpsys_byte_cnt < socket_buffer_size);
-}
-
-} // namespace testing
diff --git a/gd/shim/facade/facade.cc b/gd/shim/facade/facade.cc
deleted file mode 100644
index a07329ad3..000000000
--- a/gd/shim/facade/facade.cc
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "shim/facade/facade.h"
-
-#include <memory>
-
-#include "common/bind.h"
-#include "flatbuffers/idl.h"
-#include "flatbuffers/reflection_generated.h"
-#include "grpc/grpc_event_queue.h"
-#include "os/log.h"
-#include "shim/dumpsys.h"
-#include "shim/facade/facade.grpc.pb.h"
-#include "shim/facade/facade.pb.h"
-
-using ::grpc::ServerAsyncResponseWriter;
-using ::grpc::ServerAsyncWriter;
-using ::grpc::ServerContext;
-
-namespace bluetooth {
-namespace shim {
-namespace facade {
-
-class ShimFacadeService : public ShimFacade::Service {
- public:
- ShimFacadeService(shim::Dumpsys* dumpsys_layer, ::bluetooth::os::Handler* facade_handler)
- : dumpsys_layer_(dumpsys_layer), facade_handler_(facade_handler) {}
-
- virtual ~ShimFacadeService() {}
-
- ::grpc::Status Dump(
- ::grpc::ServerContext* context,
- const ::google::protobuf::Empty* request,
- ::grpc::ServerWriter<DumpsysMsg>* writer) override {
- dumpsys_layer_->Dump(0, nullptr);
- return ::grpc::Status::OK;
- }
-
- private:
- shim::Dumpsys* dumpsys_layer_{nullptr};
- [[maybe_unused]] ::bluetooth::os::Handler* facade_handler_{nullptr};
-};
-
-void ShimFacadeModule::ListDependencies(ModuleList* list) {
- ::bluetooth::grpc::GrpcFacadeModule::ListDependencies(list);
- list->add<Dumpsys>();
-}
-
-void ShimFacadeModule::Start() {
- ::bluetooth::grpc::GrpcFacadeModule::Start();
- service_ = new ShimFacadeService(GetDependency<Dumpsys>(), GetHandler());
-}
-
-void ShimFacadeModule::Stop() {
- delete service_;
- ::bluetooth::grpc::GrpcFacadeModule::Stop();
-}
-
-::grpc::Service* ShimFacadeModule::GetService() const {
- return service_;
-}
-
-const ModuleFactory ShimFacadeModule::Factory = ::bluetooth::ModuleFactory([]() { return new ShimFacadeModule(); });
-
-} // namespace facade
-} // namespace shim
-} // namespace bluetooth
diff --git a/gd/shim/facade/facade.h b/gd/shim/facade/facade.h
deleted file mode 100644
index 253453200..000000000
--- a/gd/shim/facade/facade.h
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <grpc++/grpc++.h>
-
-#include "grpc/grpc_module.h"
-#include "shim/dumpsys.h"
-
-namespace bluetooth {
-namespace shim {
-namespace facade {
-
-class ShimFacadeService;
-
-class ShimFacadeModule : public ::bluetooth::grpc::GrpcFacadeModule {
- public:
- static const ModuleFactory Factory;
-
- void ListDependencies(ModuleList* list) override;
- void Start() override;
- void Stop() override;
- ::grpc::Service* GetService() const override;
-
- private:
- ShimFacadeService* service_;
-};
-
-} // namespace facade
-} // namespace shim
-} // namespace bluetooth
diff --git a/gd/shim/facade/facade.proto b/gd/shim/facade/facade.proto
deleted file mode 100644
index 18c034016..000000000
--- a/gd/shim/facade/facade.proto
+++ /dev/null
@@ -1,13 +0,0 @@
-syntax = "proto3";
-
-package bluetooth.shim.facade;
-
-import "google/protobuf/empty.proto";
-
-service ShimFacade {
- rpc Dump(google.protobuf.Empty) returns (stream DumpsysMsg) {}
-}
-
-message DumpsysMsg {
- bytes data = 1;
-}
diff --git a/gd/shim/l2cap.cc b/gd/shim/l2cap.cc
new file mode 100644
index 000000000..60ec5c86c
--- /dev/null
+++ b/gd/shim/l2cap.cc
@@ -0,0 +1,717 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#define LOG_TAG "bt_gd_shim"
+
+#include <cstdint>
+#include <functional>
+#include <memory>
+#include <queue>
+#include <set>
+#include <string>
+#include <unordered_map>
+#include <vector>
+
+#include "common/bind.h"
+#include "hci/address.h"
+#include "hci/hci_packets.h"
+#include "l2cap/classic/dynamic_channel_manager.h"
+#include "l2cap/classic/l2cap_classic_module.h"
+#include "l2cap/psm.h"
+#include "l2cap/security_policy.h"
+#include "module.h"
+#include "os/handler.h"
+#include "os/log.h"
+#include "packet/packet_view.h"
+#include "packet/raw_builder.h"
+#include "shim/dumpsys.h"
+#include "shim/l2cap.h"
+
+namespace bluetooth {
+namespace shim {
+
+namespace {
+
+constexpr char kModuleName[] = "shim::L2cap";
+
+constexpr bool kConnectionFailed = false;
+constexpr bool kConnectionOpened = true;
+constexpr bool kRegistrationFailed = false;
+constexpr bool kRegistrationSuccess = true;
+
+using ConnectionInterfaceDescriptor = uint16_t;
+constexpr ConnectionInterfaceDescriptor kInvalidConnectionInterfaceDescriptor = 0;
+constexpr ConnectionInterfaceDescriptor kStartConnectionInterfaceDescriptor = 64;
+constexpr ConnectionInterfaceDescriptor kMaxConnections = UINT16_MAX - kStartConnectionInterfaceDescriptor - 1;
+
+using PendingConnectionId = int;
+
+using ConnectionClosed = std::function<void(ConnectionInterfaceDescriptor)>;
+using PendingConnectionOpen = std::function<void(std::unique_ptr<l2cap::classic::DynamicChannel>)>;
+using PendingConnectionFail = std::function<void(l2cap::classic::DynamicChannelManager::ConnectionResult)>;
+using RegisterServiceComplete = std::function<void(l2cap::Psm, bool is_registered)>;
+using UnregisterServiceDone = std::function<void()>;
+using ServiceConnectionOpen =
+ std::function<void(ConnectionCompleteCallback, std::unique_ptr<l2cap::classic::DynamicChannel>)>;
+
+std::unique_ptr<packet::RawBuilder> MakeUniquePacket(const uint8_t* data, size_t len) {
+ packet::RawBuilder builder;
+ std::vector<uint8_t> bytes(data, data + len);
+ auto payload = std::make_unique<packet::RawBuilder>();
+ payload->AddOctets(bytes);
+ return payload;
+}
+
+} // namespace
+
+class ConnectionInterface {
+ public:
+ ConnectionInterface(ConnectionInterfaceDescriptor cid, std::unique_ptr<l2cap::classic::DynamicChannel> channel,
+ os::Handler* handler, ConnectionClosed on_closed)
+ : cid_(cid), channel_(std::move(channel)), handler_(handler), on_data_ready_callback_(nullptr),
+ on_connection_closed_callback_(nullptr), address_(channel_->GetDevice()), on_closed_(on_closed) {
+ channel_->RegisterOnCloseCallback(
+ handler_, common::BindOnce(&ConnectionInterface::OnConnectionClosed, common::Unretained(this)));
+ channel_->GetQueueUpEnd()->RegisterDequeue(
+ handler_, common::Bind(&ConnectionInterface::OnReadReady, common::Unretained(this)));
+ dequeue_registered_ = true;
+ }
+
+ ~ConnectionInterface() {
+ ASSERT(!dequeue_registered_);
+ }
+
+ void OnReadReady() {
+ std::unique_ptr<packet::PacketView<packet::kLittleEndian>> packet = channel_->GetQueueUpEnd()->TryDequeue();
+ if (packet == nullptr) {
+ LOG_WARN("Got read ready from gd l2cap but no packet is ready");
+ return;
+ }
+ std::vector<const uint8_t> data(packet->begin(), packet->end());
+ ASSERT(on_data_ready_callback_ != nullptr);
+ on_data_ready_callback_(cid_, data);
+ }
+
+ void SetReadDataReadyCallback(ReadDataReadyCallback on_data_ready) {
+ ASSERT(on_data_ready != nullptr);
+ ASSERT(on_data_ready_callback_ == nullptr);
+ on_data_ready_callback_ = on_data_ready;
+ }
+
+ std::unique_ptr<packet::BasePacketBuilder> WriteReady() {
+ auto data = std::move(write_queue_.front());
+ write_queue_.pop();
+ if (write_queue_.empty()) {
+ channel_->GetQueueUpEnd()->UnregisterEnqueue();
+ enqueue_registered_ = false;
+ }
+ return data;
+ }
+
+ void Write(std::unique_ptr<packet::RawBuilder> packet) {
+ LOG_DEBUG("Writing packet cid:%hd size:%zd", cid_, packet->size());
+ write_queue_.push(std::move(packet));
+ if (!enqueue_registered_) {
+ enqueue_registered_ = true;
+ channel_->GetQueueUpEnd()->RegisterEnqueue(
+ handler_, common::Bind(&ConnectionInterface::WriteReady, common::Unretained(this)));
+ }
+ }
+
+ void Close() {
+ if (dequeue_registered_) {
+ channel_->GetQueueUpEnd()->UnregisterDequeue();
+ dequeue_registered_ = false;
+ }
+ ASSERT(write_queue_.empty());
+ channel_->Close();
+ }
+
+ void OnConnectionClosed(hci::ErrorCode error_code) {
+ LOG_DEBUG("Channel interface closed reason:%s cid:%hd device:%s", hci::ErrorCodeText(error_code).c_str(), cid_,
+ address_.ToString().c_str());
+ if (dequeue_registered_) {
+ channel_->GetQueueUpEnd()->UnregisterDequeue();
+ dequeue_registered_ = false;
+ }
+ ASSERT(on_connection_closed_callback_ != nullptr);
+ on_connection_closed_callback_(cid_, static_cast<int>(error_code));
+ on_closed_(cid_);
+ }
+
+ void SetConnectionClosedCallback(::bluetooth::shim::ConnectionClosedCallback on_connection_closed) {
+ ASSERT(on_connection_closed != nullptr);
+ ASSERT(on_connection_closed_callback_ == nullptr);
+ on_connection_closed_callback_ = std::move(on_connection_closed);
+ }
+
+ hci::Address GetRemoteAddress() const {
+ return address_;
+ }
+
+ private:
+ const ConnectionInterfaceDescriptor cid_;
+ const std::unique_ptr<l2cap::classic::DynamicChannel> channel_;
+ os::Handler* handler_;
+
+ ReadDataReadyCallback on_data_ready_callback_;
+ ConnectionClosedCallback on_connection_closed_callback_;
+
+ const hci::Address address_;
+
+ ConnectionClosed on_closed_{};
+
+ std::queue<std::unique_ptr<packet::PacketBuilder<hci::kLittleEndian>>> write_queue_;
+
+ bool enqueue_registered_{false};
+ bool dequeue_registered_{false};
+
+ DISALLOW_COPY_AND_ASSIGN(ConnectionInterface);
+};
+
+class ConnectionInterfaceManager {
+ public:
+ void AddConnection(ConnectionInterfaceDescriptor cid, std::unique_ptr<l2cap::classic::DynamicChannel> channel);
+ void RemoveConnection(ConnectionInterfaceDescriptor cid);
+
+ void SetReadDataReadyCallback(ConnectionInterfaceDescriptor cid, ReadDataReadyCallback on_data_ready);
+ void SetConnectionClosedCallback(ConnectionInterfaceDescriptor cid, ConnectionClosedCallback on_closed);
+
+ bool Write(ConnectionInterfaceDescriptor cid, std::unique_ptr<packet::RawBuilder> packet);
+
+ size_t NumberOfActiveConnections() const {
+ return cid_to_interface_map_.size();
+ }
+
+ void ConnectionOpened(ConnectionCompleteCallback on_complete, l2cap::Psm psm, ConnectionInterfaceDescriptor cid) {
+ hci::Address address = cid_to_interface_map_[cid]->GetRemoteAddress();
+ LOG_DEBUG("Connection opened address:%s psm:%hd cid:%hd", address.ToString().c_str(), psm, cid);
+ on_complete(address.ToString(), static_cast<uint16_t>(psm), static_cast<uint16_t>(cid), kConnectionOpened);
+ }
+
+ void ConnectionFailed(ConnectionCompleteCallback on_complete, hci::Address address, l2cap::Psm psm,
+ ConnectionInterfaceDescriptor cid) {
+ LOG_DEBUG("Connection failed address:%s psm:%hd", address.ToString().c_str(), psm);
+ on_complete(address.ToString(), static_cast<uint16_t>(psm), static_cast<uint16_t>(cid), kConnectionFailed);
+ }
+
+ ConnectionInterfaceManager(os::Handler* handler);
+
+ ConnectionInterfaceDescriptor AllocateConnectionInterfaceDescriptor();
+ void FreeConnectionInterfaceDescriptor(ConnectionInterfaceDescriptor cid);
+
+ private:
+ os::Handler* handler_;
+ ConnectionInterfaceDescriptor current_connection_interface_descriptor_;
+
+ bool HasResources() const;
+ bool ConnectionExists(ConnectionInterfaceDescriptor id) const;
+ bool CidExists(ConnectionInterfaceDescriptor id) const;
+ void ConnectionClosed(ConnectionInterfaceDescriptor cid, std::unique_ptr<ConnectionInterface> connection);
+
+ std::unordered_map<ConnectionInterfaceDescriptor, std::unique_ptr<ConnectionInterface>> cid_to_interface_map_;
+ std::set<ConnectionInterfaceDescriptor> active_cid_set_;
+
+ ConnectionInterfaceManager() = delete;
+};
+
+ConnectionInterfaceManager::ConnectionInterfaceManager(os::Handler* handler)
+ : handler_(handler), current_connection_interface_descriptor_(kStartConnectionInterfaceDescriptor) {}
+
+bool ConnectionInterfaceManager::ConnectionExists(ConnectionInterfaceDescriptor cid) const {
+ return cid_to_interface_map_.find(cid) != cid_to_interface_map_.end();
+}
+
+bool ConnectionInterfaceManager::CidExists(ConnectionInterfaceDescriptor cid) const {
+ return active_cid_set_.find(cid) != active_cid_set_.end();
+}
+
+ConnectionInterfaceDescriptor ConnectionInterfaceManager::AllocateConnectionInterfaceDescriptor() {
+ ASSERT(HasResources());
+ while (CidExists(current_connection_interface_descriptor_)) {
+ if (++current_connection_interface_descriptor_ == kInvalidConnectionInterfaceDescriptor) {
+ current_connection_interface_descriptor_ = kStartConnectionInterfaceDescriptor;
+ }
+ }
+ active_cid_set_.insert(current_connection_interface_descriptor_);
+ return current_connection_interface_descriptor_++;
+}
+
+void ConnectionInterfaceManager::FreeConnectionInterfaceDescriptor(ConnectionInterfaceDescriptor cid) {
+ ASSERT(CidExists(cid));
+ active_cid_set_.erase(cid);
+}
+
+void ConnectionInterfaceManager::ConnectionClosed(ConnectionInterfaceDescriptor cid,
+ std::unique_ptr<ConnectionInterface> connection) {
+ cid_to_interface_map_.erase(cid);
+ FreeConnectionInterfaceDescriptor(cid);
+}
+
+void ConnectionInterfaceManager::AddConnection(ConnectionInterfaceDescriptor cid,
+ std::unique_ptr<l2cap::classic::DynamicChannel> channel) {
+ ASSERT(cid_to_interface_map_.count(cid) == 0);
+ cid_to_interface_map_.emplace(
+ cid, std::make_unique<ConnectionInterface>(
+ cid, std::move(channel), handler_, [this](ConnectionInterfaceDescriptor cid) {
+ LOG_DEBUG("Deleting connection interface cid:%hd", cid);
+ auto connection = std::move(cid_to_interface_map_.at(cid));
+ handler_->Post(common::BindOnce(&ConnectionInterfaceManager::ConnectionClosed,
+ common::Unretained(this), cid, std::move(connection)));
+ }));
+}
+
+void ConnectionInterfaceManager::RemoveConnection(ConnectionInterfaceDescriptor cid) {
+ if (cid_to_interface_map_.count(cid) == 1) {
+ cid_to_interface_map_.find(cid)->second->Close();
+ } else {
+ LOG_WARN("Closing a pending connection cid:%hd", cid);
+ }
+}
+
+bool ConnectionInterfaceManager::HasResources() const {
+ return cid_to_interface_map_.size() < kMaxConnections;
+}
+
+void ConnectionInterfaceManager::SetReadDataReadyCallback(ConnectionInterfaceDescriptor cid,
+ ReadDataReadyCallback on_data_ready) {
+ ASSERT(ConnectionExists(cid));
+ return cid_to_interface_map_[cid]->SetReadDataReadyCallback(on_data_ready);
+}
+
+void ConnectionInterfaceManager::SetConnectionClosedCallback(ConnectionInterfaceDescriptor cid,
+ ConnectionClosedCallback on_closed) {
+ ASSERT(ConnectionExists(cid));
+ return cid_to_interface_map_[cid]->SetConnectionClosedCallback(on_closed);
+}
+
+bool ConnectionInterfaceManager::Write(ConnectionInterfaceDescriptor cid, std::unique_ptr<packet::RawBuilder> packet) {
+ if (!ConnectionExists(cid)) {
+ return false;
+ }
+ cid_to_interface_map_[cid]->Write(std::move(packet));
+ return true;
+}
+
+class PendingConnection {
+ public:
+ PendingConnection(ConnectionInterfaceDescriptor cid, l2cap::Psm psm, hci::Address address,
+ ConnectionCompleteCallback on_complete, PendingConnectionOpen pending_open,
+ PendingConnectionFail pending_fail)
+ : cid_(cid), psm_(psm), address_(address), on_complete_(std::move(on_complete)), pending_open_(pending_open),
+ pending_fail_(pending_fail) {}
+
+ void OnConnectionOpen(std::unique_ptr<l2cap::classic::DynamicChannel> channel) {
+ LOG_DEBUG("Local initiated connection is open to device:%s for psm:%hd", address_.ToString().c_str(), psm_);
+ ASSERT_LOG(address_ == channel->GetDevice(), " Expected remote device does not match actual remote device");
+ pending_open_(std::move(channel));
+ }
+
+ void OnConnectionFailure(l2cap::classic::DynamicChannelManager::ConnectionResult result) {
+ LOG_DEBUG("Connection failed to device:%s for psm:%hd", address_.ToString().c_str(), psm_);
+ switch (result.connection_result_code) {
+ case l2cap::classic::DynamicChannelManager::ConnectionResultCode::SUCCESS:
+ LOG_WARN("Connection failed result:success hci:%s", hci::ErrorCodeText(result.hci_error).c_str());
+ break;
+ case l2cap::classic::DynamicChannelManager::ConnectionResultCode::FAIL_NO_SERVICE_REGISTERED:
+ LOG_DEBUG("Connection failed result:no service registered hci:%s",
+ hci::ErrorCodeText(result.hci_error).c_str());
+ break;
+ case l2cap::classic::DynamicChannelManager::ConnectionResultCode::FAIL_HCI_ERROR:
+ LOG_DEBUG("Connection failed result:hci error hci:%s", hci::ErrorCodeText(result.hci_error).c_str());
+ break;
+ case l2cap::classic::DynamicChannelManager::ConnectionResultCode::FAIL_L2CAP_ERROR:
+ LOG_DEBUG("Connection failed result:l2cap error hci:%s l2cap:%s", hci::ErrorCodeText(result.hci_error).c_str(),
+ l2cap::ConnectionResponseResultText(result.l2cap_connection_response_result).c_str());
+ break;
+ }
+ pending_fail_(result);
+ }
+
+ std::string ToString() const {
+ return address_.ToString() + "." + std::to_string(psm_);
+ }
+
+ const ConnectionInterfaceDescriptor cid_;
+ const l2cap::Psm psm_;
+ const hci::Address address_;
+ const ConnectionCompleteCallback on_complete_;
+
+ private:
+ const PendingConnectionOpen pending_open_;
+ const PendingConnectionFail pending_fail_;
+
+ DISALLOW_COPY_AND_ASSIGN(PendingConnection);
+};
+
+class ServiceInterface {
+ public:
+ ServiceInterface(l2cap::Psm psm, l2cap::SecurityPolicy security_policy, ConnectionCompleteCallback on_complete,
+ RegisterServiceComplete register_complete, ServiceConnectionOpen connection_open,
+ RegisterServicePromise register_promise)
+ : psm_(psm), security_policy_(security_policy), on_complete_(on_complete),
+ register_complete_(std::move(register_complete)), connection_open_(std::move(connection_open)),
+ register_promise_(std::move(register_promise)) {}
+
+ void NotifyRegistered(l2cap::Psm psm) {
+ register_promise_.set_value(psm);
+ }
+
+ void NotifyUnregistered() {
+ unregister_promise_.set_value();
+ }
+
+ void UnregisterService(os::Handler* handler, UnregisterServicePromise unregister_promise,
+ UnregisterServiceDone unregister_done) {
+ unregister_promise_ = std::move(unregister_promise);
+ unregister_done_ = std::move(unregister_done);
+
+ service_->Unregister(common::BindOnce(&ServiceInterface::OnUnregistrationComplete, common::Unretained(this)),
+ handler);
+ }
+
+ l2cap::SecurityPolicy GetSecurityPolicy() const {
+ return security_policy_;
+ }
+
+ void OnRegistrationComplete(l2cap::classic::DynamicChannelManager::RegistrationResult result,
+ std::unique_ptr<l2cap::classic::DynamicChannelService> service) {
+ ASSERT(service_ == nullptr);
+ ASSERT(service->GetPsm() == psm_);
+ service_ = std::move(service);
+
+ switch (result) {
+ case l2cap::classic::DynamicChannelManager::RegistrationResult::SUCCESS:
+ LOG_DEBUG("Service is registered for psm:%hd", psm_);
+ register_complete_(psm_, kRegistrationSuccess);
+ break;
+ case l2cap::classic::DynamicChannelManager::RegistrationResult::FAIL_DUPLICATE_SERVICE:
+ LOG_WARN("Failed to register duplicate service has psm:%hd", psm_);
+ register_complete_(l2cap::kDefaultPsm, kRegistrationFailed);
+ break;
+ case l2cap::classic::DynamicChannelManager::RegistrationResult::FAIL_INVALID_SERVICE:
+ LOG_WARN("Failed to register invalid service psm:%hd", psm_);
+ register_complete_(l2cap::kDefaultPsm, kRegistrationFailed);
+ break;
+ }
+ }
+
+ void OnUnregistrationComplete() {
+ LOG_DEBUG("Unregistered psm:%hd", psm_);
+ unregister_done_();
+ }
+
+ void OnConnectionOpen(std::unique_ptr<l2cap::classic::DynamicChannel> channel) {
+ LOG_DEBUG("Remote initiated connection is open from device:%s for psm:%hd", channel->GetDevice().ToString().c_str(),
+ psm_);
+ connection_open_(on_complete_, std::move(channel));
+ }
+
+ private:
+ const l2cap::Psm psm_;
+ const l2cap::SecurityPolicy security_policy_;
+ const ConnectionCompleteCallback on_complete_;
+ const RegisterServiceComplete register_complete_;
+ const ServiceConnectionOpen connection_open_;
+ RegisterServicePromise register_promise_;
+ UnregisterServicePromise unregister_promise_;
+ UnregisterServiceDone unregister_done_;
+
+ std::unique_ptr<l2cap::classic::DynamicChannelService> service_;
+
+ DISALLOW_COPY_AND_ASSIGN(ServiceInterface);
+};
+
+struct L2cap::impl {
+ void RegisterService(l2cap::Psm psm, l2cap::classic::DynamicChannelConfigurationOption option,
+ ConnectionCompleteCallback on_complete, RegisterServicePromise register_promise);
+ void UnregisterService(l2cap::Psm psm, UnregisterServicePromise unregister_promise);
+
+ void CreateConnection(l2cap::Psm psm, hci::Address address, ConnectionCompleteCallback on_complete,
+ CreateConnectionPromise create_promise);
+ void CloseConnection(ConnectionInterfaceDescriptor cid);
+
+ void SetReadDataReadyCallback(ConnectionInterfaceDescriptor cid, ReadDataReadyCallback on_data_ready);
+ void SetConnectionClosedCallback(ConnectionInterfaceDescriptor cid, ConnectionClosedCallback on_closed);
+
+ void Write(ConnectionInterfaceDescriptor cid, std::unique_ptr<packet::RawBuilder> packet);
+
+ void SendLoopbackResponse(std::function<void()> function);
+
+ void Dump(int fd);
+
+ impl(L2cap& module, l2cap::classic::L2capClassicModule* l2cap_module);
+
+ private:
+ L2cap& module_;
+ l2cap::classic::L2capClassicModule* l2cap_module_;
+ os::Handler* handler_;
+ ConnectionInterfaceManager connection_interface_manager_;
+
+ std::unique_ptr<l2cap::classic::DynamicChannelManager> dynamic_channel_manager_;
+
+ std::unordered_map<l2cap::Psm, std::unique_ptr<ServiceInterface>> psm_to_service_interface_map_;
+
+ PendingConnectionId pending_connection_id_{0};
+ std::unordered_map<PendingConnectionId, std::unique_ptr<PendingConnection>> pending_connection_map_;
+
+ void PendingConnectionOpen(PendingConnectionId id, std::unique_ptr<PendingConnection> connection,
+ std::unique_ptr<l2cap::classic::DynamicChannel> channel);
+ void PendingConnectionFail(PendingConnectionId id, std::unique_ptr<PendingConnection> connection,
+ l2cap::classic::DynamicChannelManager::ConnectionResult result);
+ void ServiceUnregistered(l2cap::Psm psm, std::unique_ptr<ServiceInterface> service);
+ const l2cap::SecurityPolicy GetSecurityPolicy(l2cap::Psm psm) const;
+};
+
+const ModuleFactory L2cap::Factory = ModuleFactory([]() { return new L2cap(); });
+
+L2cap::impl::impl(L2cap& module, l2cap::classic::L2capClassicModule* l2cap_module)
+ : module_(module), l2cap_module_(l2cap_module), handler_(module_.GetHandler()),
+ connection_interface_manager_(handler_) {
+ dynamic_channel_manager_ = l2cap_module_->GetDynamicChannelManager();
+}
+
+void L2cap::impl::Dump(int fd) {
+ if (psm_to_service_interface_map_.empty()) {
+ dprintf(fd, "%s no psms registered\n", kModuleName);
+ } else {
+ for (auto& service : psm_to_service_interface_map_) {
+ dprintf(fd, "%s psm registered:%hd\n", kModuleName, service.first);
+ }
+ }
+
+ if (pending_connection_map_.empty()) {
+ dprintf(fd, "%s no pending classic connections\n", kModuleName);
+ } else {
+ for (auto& pending : pending_connection_map_) {
+ if (pending.second != nullptr) {
+ dprintf(fd, "%s pending connection:%s\n", kModuleName, pending.second->ToString().c_str());
+ } else {
+ dprintf(fd, "%s old pending connection:%d\n", kModuleName, pending.first);
+ }
+ }
+ }
+}
+
+void L2cap::impl::ServiceUnregistered(l2cap::Psm psm, std::unique_ptr<ServiceInterface> service) {
+ LOG_INFO("Unregistered service psm:%hd", psm);
+ psm_to_service_interface_map_.erase(psm);
+ service->NotifyUnregistered();
+}
+
+const l2cap::SecurityPolicy L2cap::impl::GetSecurityPolicy(l2cap::Psm psm) const {
+ l2cap::SecurityPolicy security_policy;
+ if (psm == 1) {
+ security_policy.security_level_ = l2cap::SecurityPolicy::Level::LEVEL_0;
+ } else {
+ security_policy.security_level_ = l2cap::SecurityPolicy::Level::LEVEL_3;
+ }
+ return security_policy;
+}
+
+void L2cap::impl::RegisterService(l2cap::Psm psm, l2cap::classic::DynamicChannelConfigurationOption option,
+ ConnectionCompleteCallback on_complete, RegisterServicePromise register_promise) {
+ ASSERT(psm_to_service_interface_map_.find(psm) == psm_to_service_interface_map_.end());
+
+ const l2cap::SecurityPolicy security_policy = GetSecurityPolicy(psm);
+
+ psm_to_service_interface_map_.emplace(
+ psm,
+ std::make_unique<ServiceInterface>(
+ psm, security_policy, on_complete,
+ [this, psm](l2cap::Psm actual_psm, bool is_registered) {
+ psm_to_service_interface_map_.at(psm)->NotifyRegistered(actual_psm);
+ if (!is_registered) {
+ auto service = std::move(psm_to_service_interface_map_.at(psm));
+ }
+ },
+ [this, psm](ConnectionCompleteCallback on_complete, std::unique_ptr<l2cap::classic::DynamicChannel> channel) {
+ ConnectionInterfaceDescriptor cid = connection_interface_manager_.AllocateConnectionInterfaceDescriptor();
+ connection_interface_manager_.AddConnection(cid, std::move(channel));
+ connection_interface_manager_.ConnectionOpened(on_complete, psm, cid);
+ LOG_DEBUG("connection open");
+ },
+ std::move(register_promise)));
+
+ bool rc = dynamic_channel_manager_->RegisterService(
+ psm, option, security_policy,
+ common::BindOnce(&ServiceInterface::OnRegistrationComplete,
+ common::Unretained(psm_to_service_interface_map_.at(psm).get())),
+ common::Bind(&ServiceInterface::OnConnectionOpen,
+ common::Unretained(psm_to_service_interface_map_.at(psm).get())),
+ handler_);
+ ASSERT_LOG(rc == true, "Failed to register classic service");
+}
+
+void L2cap::impl::UnregisterService(l2cap::Psm psm, UnregisterServicePromise unregister_promise) {
+ ASSERT(psm_to_service_interface_map_.find(psm) != psm_to_service_interface_map_.end());
+ psm_to_service_interface_map_[psm]->UnregisterService(handler_, std::move(unregister_promise), [this, psm]() {
+ auto service = std::move(psm_to_service_interface_map_.at(psm));
+ handler_->Post(
+ common::BindOnce(&L2cap::impl::ServiceUnregistered, common::Unretained(this), psm, std::move(service)));
+ });
+}
+
+void L2cap::impl::PendingConnectionOpen(PendingConnectionId id, std::unique_ptr<PendingConnection> connection,
+ std::unique_ptr<l2cap::classic::DynamicChannel> channel) {
+ connection_interface_manager_.AddConnection(connection->cid_, std::move(channel));
+ connection_interface_manager_.ConnectionOpened(std::move(connection->on_complete_), connection->psm_,
+ connection->cid_);
+ pending_connection_map_.erase(id);
+}
+
+void L2cap::impl::PendingConnectionFail(PendingConnectionId id, std::unique_ptr<PendingConnection> connection,
+ l2cap::classic::DynamicChannelManager::ConnectionResult result) {
+ connection_interface_manager_.ConnectionFailed(std::move(connection->on_complete_), connection->address_,
+ connection->psm_, connection->cid_);
+ connection_interface_manager_.FreeConnectionInterfaceDescriptor(connection->cid_);
+ pending_connection_map_.erase(id);
+}
+
+void L2cap::impl::CreateConnection(l2cap::Psm psm, hci::Address address, ConnectionCompleteCallback on_complete,
+ CreateConnectionPromise create_promise) {
+ ConnectionInterfaceDescriptor cid = connection_interface_manager_.AllocateConnectionInterfaceDescriptor();
+ create_promise.set_value(cid);
+
+ if (cid == kInvalidConnectionInterfaceDescriptor) {
+ LOG_WARN("No resources to create a connection");
+ return;
+ }
+
+ PendingConnectionId id = ++pending_connection_id_;
+ pending_connection_map_.emplace(
+ id, std::make_unique<PendingConnection>(
+ cid, psm, address, on_complete,
+ [this, id](std::unique_ptr<l2cap::classic::DynamicChannel> channel) {
+ auto connection = std::move(pending_connection_map_.at(id));
+ handler_->Post(common::BindOnce(&L2cap::impl::PendingConnectionOpen, common::Unretained(this), id,
+ std::move(connection), std::move(channel)));
+ },
+ [this, id](l2cap::classic::DynamicChannelManager::ConnectionResult result) {
+ auto connection = std::move(pending_connection_map_.at(id));
+ handler_->Post(common::BindOnce(&L2cap::impl::PendingConnectionFail, common::Unretained(this), id,
+ std::move(connection), result));
+ }));
+
+ bool rc = dynamic_channel_manager_->ConnectChannel(
+ address, l2cap::classic::DynamicChannelConfigurationOption(), psm,
+ common::Bind(&PendingConnection::OnConnectionOpen, common::Unretained(pending_connection_map_.at(id).get())),
+ common::BindOnce(&PendingConnection::OnConnectionFailure,
+ common::Unretained(pending_connection_map_.at(id).get())),
+ handler_);
+ ASSERT_LOG(rc == true, "Failed to create classic connection");
+}
+
+void L2cap::impl::CloseConnection(ConnectionInterfaceDescriptor cid) {
+ connection_interface_manager_.RemoveConnection(cid);
+}
+
+void L2cap::impl::SetReadDataReadyCallback(ConnectionInterfaceDescriptor cid, ReadDataReadyCallback on_data_ready) {
+ connection_interface_manager_.SetReadDataReadyCallback(cid, on_data_ready);
+}
+
+void L2cap::impl::SetConnectionClosedCallback(ConnectionInterfaceDescriptor cid, ConnectionClosedCallback on_closed) {
+ connection_interface_manager_.SetConnectionClosedCallback(cid, std::move(on_closed));
+}
+
+void L2cap::impl::Write(ConnectionInterfaceDescriptor cid, std::unique_ptr<packet::RawBuilder> packet) {
+ connection_interface_manager_.Write(cid, std::move(packet));
+}
+
+void L2cap::impl::SendLoopbackResponse(std::function<void()> function) {
+ function();
+}
+
+void L2cap::RegisterService(uint16_t raw_psm, bool use_ertm, uint16_t mtu, ConnectionCompleteCallback on_complete,
+ RegisterServicePromise register_promise) {
+ l2cap::Psm psm{raw_psm};
+ l2cap::classic::DynamicChannelConfigurationOption option;
+ if (use_ertm) {
+ option.channel_mode =
+ l2cap::classic::DynamicChannelConfigurationOption::RetransmissionAndFlowControlMode::ENHANCED_RETRANSMISSION;
+ }
+ option.incoming_mtu = mtu;
+ GetHandler()->Post(common::BindOnce(&L2cap::impl::RegisterService, common::Unretained(pimpl_.get()), psm, option,
+ on_complete, std::move(register_promise)));
+}
+
+void L2cap::UnregisterService(uint16_t raw_psm, UnregisterServicePromise unregister_promise) {
+ l2cap::Psm psm{raw_psm};
+ GetHandler()->Post(common::BindOnce(&L2cap::impl::UnregisterService, common::Unretained(pimpl_.get()), psm,
+ std::move(unregister_promise)));
+}
+
+void L2cap::CreateConnection(uint16_t raw_psm, const std::string address_string, ConnectionCompleteCallback on_complete,
+ CreateConnectionPromise create_promise) {
+ l2cap::Psm psm{raw_psm};
+ hci::Address address;
+ hci::Address::FromString(address_string, address);
+
+ GetHandler()->Post(common::BindOnce(&L2cap::impl::CreateConnection, common::Unretained(pimpl_.get()), psm, address,
+ on_complete, std::move(create_promise)));
+}
+
+void L2cap::CloseConnection(uint16_t raw_cid) {
+ ConnectionInterfaceDescriptor cid(raw_cid);
+ GetHandler()->Post(common::Bind(&L2cap::impl::CloseConnection, common::Unretained(pimpl_.get()), cid));
+}
+
+void L2cap::SetReadDataReadyCallback(uint16_t raw_cid, ReadDataReadyCallback on_data_ready) {
+ ConnectionInterfaceDescriptor cid(raw_cid);
+ GetHandler()->Post(
+ common::Bind(&L2cap::impl::SetReadDataReadyCallback, common::Unretained(pimpl_.get()), cid, on_data_ready));
+}
+
+void L2cap::SetConnectionClosedCallback(uint16_t raw_cid, ConnectionClosedCallback on_closed) {
+ ConnectionInterfaceDescriptor cid(raw_cid);
+ GetHandler()->Post(common::Bind(&L2cap::impl::SetConnectionClosedCallback, common::Unretained(pimpl_.get()), cid,
+ std::move(on_closed)));
+}
+
+void L2cap::Write(uint16_t raw_cid, const uint8_t* data, size_t len) {
+ ConnectionInterfaceDescriptor cid(raw_cid);
+ auto packet = MakeUniquePacket(data, len);
+ GetHandler()->Post(common::BindOnce(&L2cap::impl::Write, common::Unretained(pimpl_.get()), cid, std::move(packet)));
+}
+
+void L2cap::SendLoopbackResponse(std::function<void()> function) {
+ GetHandler()->Post(common::BindOnce(&L2cap::impl::SendLoopbackResponse, common::Unretained(pimpl_.get()), function));
+}
+
+/**
+ * Module methods
+ */
+void L2cap::ListDependencies(ModuleList* list) {
+ list->add<shim::Dumpsys>();
+ list->add<l2cap::classic::L2capClassicModule>();
+}
+
+void L2cap::Start() {
+ pimpl_ = std::make_unique<impl>(*this, GetDependency<l2cap::classic::L2capClassicModule>());
+ GetDependency<shim::Dumpsys>()->RegisterDumpsysFunction(static_cast<void*>(this),
+ [this](int fd) { pimpl_->Dump(fd); });
+}
+
+void L2cap::Stop() {
+ GetDependency<shim::Dumpsys>()->UnregisterDumpsysFunction(static_cast<void*>(this));
+ pimpl_.reset();
+}
+
+std::string L2cap::ToString() const {
+ return kModuleName;
+}
+
+} // namespace shim
+} // namespace bluetooth
diff --git a/gd/shim/l2cap.h b/gd/shim/l2cap.h
new file mode 100644
index 000000000..61b4ededc
--- /dev/null
+++ b/gd/shim/l2cap.h
@@ -0,0 +1,73 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#pragma once
+
+#include <cstdint>
+#include <functional>
+#include <future>
+#include <memory>
+#include <string>
+
+#include "module.h"
+
+namespace bluetooth {
+namespace shim {
+
+using ConnectionClosedCallback = std::function<void(uint16_t cid, int error_code)>;
+using ConnectionCompleteCallback =
+ std::function<void(std::string string_address, uint16_t psm, uint16_t cid, bool is_connected)>;
+using ReadDataReadyCallback = std::function<void(uint16_t cid, std::vector<const uint8_t> data)>;
+
+using RegisterServicePromise = std::promise<uint16_t>;
+using UnregisterServicePromise = std::promise<void>;
+using CreateConnectionPromise = std::promise<uint16_t>;
+
+class L2cap : public bluetooth::Module {
+ public:
+ void RegisterService(uint16_t psm, bool use_ertm, uint16_t mtu, ConnectionCompleteCallback on_complete,
+ RegisterServicePromise register_promise);
+ void UnregisterService(uint16_t psm, UnregisterServicePromise unregister_promise);
+
+ void CreateConnection(uint16_t psm, const std::string address_string, ConnectionCompleteCallback on_complete,
+ CreateConnectionPromise create_promise);
+ void CloseConnection(uint16_t cid);
+
+ void SetReadDataReadyCallback(uint16_t cid, ReadDataReadyCallback on_data_ready);
+ void SetConnectionClosedCallback(uint16_t cid, ConnectionClosedCallback on_closed);
+
+ void Write(uint16_t cid, const uint8_t* data, size_t len);
+
+ void SendLoopbackResponse(std::function<void()>);
+
+ L2cap() = default;
+ ~L2cap() = default;
+
+ static const ModuleFactory Factory;
+
+ protected:
+ void ListDependencies(ModuleList* list) override; // Module
+ void Start() override; // Module
+ void Stop() override; // Module
+ std::string ToString() const override; // Module
+
+ private:
+ struct impl;
+ std::unique_ptr<impl> pimpl_;
+ DISALLOW_COPY_AND_ASSIGN(L2cap);
+};
+
+} // namespace shim
+} // namespace bluetooth
diff --git a/gd/shim/l2cap_test.cc b/gd/shim/l2cap_test.cc
new file mode 100644
index 000000000..9a24c11cd
--- /dev/null
+++ b/gd/shim/l2cap_test.cc
@@ -0,0 +1,459 @@
+/*
+ * Copyright 2020 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "shim/l2cap.h"
+
+#include <gtest/gtest.h>
+#include <future>
+#include <memory>
+
+#include "common/bind.h"
+#include "hci/address.h"
+#include "hci/address_with_type.h"
+#include "l2cap/classic/dynamic_channel_configuration_option.h"
+#include "l2cap/classic/dynamic_channel_manager.h"
+#include "l2cap/classic/internal/dynamic_channel_service_manager_impl_mock.h"
+#include "l2cap/classic/l2cap_classic_module.h"
+#include "l2cap/internal/ilink.h"
+#include "l2cap/psm.h"
+#include "l2cap/security_policy.h"
+#include "os/handler.h"
+
+namespace bluetooth {
+namespace shim {
+namespace {
+
+constexpr uint16_t kPsm = 123;
+constexpr uint16_t kPsm2 = kPsm + 2;
+constexpr uint16_t kCid = 456;
+constexpr uint16_t kCid2 = kCid + 1;
+constexpr char device_address[] = "11:22:33:44:55:66";
+constexpr char device_address2[] = "aa:bb:cc:dd:ee:ff";
+constexpr bool kNoUseErtm = false;
+constexpr uint16_t kMtu = 1000;
+
+class TestDynamicChannelService : public l2cap::classic::DynamicChannelService {
+ public:
+ TestDynamicChannelService(l2cap::Psm psm, l2cap::classic::internal::DynamicChannelServiceManagerImpl* manager,
+ os::Handler* handler)
+ : DynamicChannelService(psm, manager, handler) {}
+};
+
+class TestLink : public l2cap::internal::ILink {
+ public:
+ hci::AddressWithType GetDevice() {
+ return device_with_type_;
+ }
+ hci::AddressWithType device_with_type_;
+
+ void SendLeCredit(l2cap::Cid local_cid, uint16_t credit) {}
+
+ void SendDisconnectionRequest(l2cap::Cid cid, l2cap::Cid remote_cid) {
+ connection_closed_promise_.set_value();
+ }
+ std::promise<void> connection_closed_promise_;
+};
+
+class TestDynamicChannelManagerImpl {
+ public:
+ bool ConnectChannel(hci::Address device, l2cap::classic::DynamicChannelConfigurationOption configuration_option,
+ l2cap::Psm psm, l2cap::classic::DynamicChannelManager::OnConnectionOpenCallback on_open_callback,
+ l2cap::classic::DynamicChannelManager::OnConnectionFailureCallback on_fail_callback,
+ os::Handler* handler) {
+ connections_++;
+ on_open_callback_ = std::move(on_open_callback);
+ on_fail_callback_ = std::move(on_fail_callback);
+
+ connected_promise_.set_value();
+ return true;
+ }
+ int connections_{0};
+
+ bool RegisterService(l2cap::Psm psm, l2cap::classic::DynamicChannelConfigurationOption configuration_option,
+ const l2cap::SecurityPolicy& security_policy,
+ l2cap::classic::DynamicChannelManager::OnRegistrationCompleteCallback on_registration_complete,
+ l2cap::classic::DynamicChannelManager::OnConnectionOpenCallback on_open_callback,
+ os::Handler* handler) {
+ services_++;
+ on_registration_complete_ = std::move(on_registration_complete);
+ on_open_callback_ = std::move(on_open_callback);
+
+ register_promise_.set_value();
+ return true;
+ }
+ int services_{0};
+
+ void SetConnectionFuture() {
+ connected_promise_ = std::promise<void>();
+ }
+
+ void WaitConnectionFuture() {
+ connected_future_ = connected_promise_.get_future();
+ connected_future_.wait();
+ }
+
+ void SetRegistrationFuture() {
+ register_promise_ = std::promise<void>();
+ }
+
+ void WaitRegistrationFuture() {
+ register_future_ = register_promise_.get_future();
+ register_future_.wait();
+ }
+
+ void SetConnectionOnFail(l2cap::classic::DynamicChannelManager::ConnectionResult result, std::promise<void> promise) {
+ std::move(on_fail_callback_).Run(result);
+ promise.set_value();
+ }
+
+ void SetConnectionOnOpen(std::unique_ptr<l2cap::DynamicChannel> channel, std::promise<void> promise) {
+ std::move(on_open_callback_).Run(std::move(channel));
+ promise.set_value();
+ }
+
+ l2cap::classic::DynamicChannelManager::OnRegistrationCompleteCallback on_registration_complete_{};
+ l2cap::classic::DynamicChannelManager::OnConnectionOpenCallback on_open_callback_{};
+ l2cap::classic::DynamicChannelManager::OnConnectionFailureCallback on_fail_callback_{};
+
+ TestDynamicChannelManagerImpl() = default;
+ ~TestDynamicChannelManagerImpl() = default;
+
+ private:
+ std::promise<void> connected_promise_;
+ std::future<void> connected_future_;
+
+ std::promise<void> register_promise_;
+ std::future<void> register_future_;
+};
+
+class TestDynamicChannelManager : public l2cap::classic::DynamicChannelManager {
+ public:
+ bool ConnectChannel(hci::Address device, l2cap::classic::DynamicChannelConfigurationOption configuration_option,
+ l2cap::Psm psm, l2cap::classic::DynamicChannelManager::OnConnectionOpenCallback on_open_callback,
+ l2cap::classic::DynamicChannelManager::OnConnectionFailureCallback on_fail_callback,
+ os::Handler* handler) override {
+ return impl_.ConnectChannel(device, configuration_option, psm, std::move(on_open_callback),
+ std::move(on_fail_callback), handler);
+ }
+
+ bool RegisterService(l2cap::Psm psm, l2cap::classic::DynamicChannelConfigurationOption configuration_option,
+ const l2cap::SecurityPolicy& security_policy,
+ l2cap::classic::DynamicChannelManager::OnRegistrationCompleteCallback on_registration_complete,
+ l2cap::classic::DynamicChannelManager::OnConnectionOpenCallback on_open_callback,
+ os::Handler* handler) override {
+ return impl_.RegisterService(psm, configuration_option, security_policy, std::move(on_registration_complete),
+ std::move(on_open_callback), handler);
+ }
+ TestDynamicChannelManager(TestDynamicChannelManagerImpl& impl) : impl_(impl) {}
+ TestDynamicChannelManagerImpl& impl_;
+};
+
+class TestL2capClassicModule : public l2cap::classic::L2capClassicModule {
+ public:
+ std::unique_ptr<l2cap::classic::DynamicChannelManager> GetDynamicChannelManager() override {
+ ASSERT(impl_ != nullptr);
+ return std::make_unique<TestDynamicChannelManager>(*impl_);
+ }
+
+ void ListDependencies(ModuleList* list) override {}
+ void Start() override;
+ void Stop() override;
+
+ std::unique_ptr<TestDynamicChannelManagerImpl> impl_;
+};
+
+void TestL2capClassicModule::Start() {
+ impl_ = std::make_unique<TestDynamicChannelManagerImpl>();
+}
+
+void TestL2capClassicModule::Stop() {
+ impl_.reset();
+}
+
+class ShimL2capTest : public ::testing::Test {
+ public:
+ void OnConnectionComplete(std::string string_address, uint16_t psm, uint16_t cid, bool connected) {
+ connection_string_address_ = string_address;
+ connection_psm_ = psm;
+ connection_cid_ = cid;
+ connection_connected_ = connected;
+ connection_complete_promise_.set_value();
+ }
+
+ uint16_t CreateConnection(uint16_t psm, std::string device_address) {
+ std::promise<uint16_t> promise;
+ auto future = promise.get_future();
+
+ shim_l2cap_->CreateConnection(
+ psm, device_address,
+ std::bind(&bluetooth::shim::ShimL2capTest::OnConnectionComplete, this, std::placeholders::_1,
+ std::placeholders::_2, std::placeholders::_3, std::placeholders::_4),
+ std::move(promise));
+ return future.get();
+ }
+
+ void SetConnectionFuture() {
+ test_l2cap_classic_module_->impl_->SetConnectionFuture();
+ }
+
+ void WaitConnectionFuture() {
+ test_l2cap_classic_module_->impl_->WaitConnectionFuture();
+ }
+
+ void SetRegistrationFuture() {
+ test_l2cap_classic_module_->impl_->SetRegistrationFuture();
+ }
+
+ void WaitRegistrationFuture() {
+ test_l2cap_classic_module_->impl_->WaitRegistrationFuture();
+ }
+
+ int NumberOfConnections() const {
+ return test_l2cap_classic_module_->impl_->connections_;
+ }
+
+ int NumberOfServices() const {
+ return test_l2cap_classic_module_->impl_->services_;
+ }
+
+ std::string connection_string_address_;
+ uint16_t connection_psm_{0};
+ uint16_t connection_cid_{0};
+ bool connection_connected_{false};
+
+ shim::L2cap* shim_l2cap_ = nullptr;
+ TestL2capClassicModule* test_l2cap_classic_module_{nullptr};
+
+ TestLink test_link_;
+ std::promise<void> connection_complete_promise_;
+
+ protected:
+ void SetUp() override {
+ handler_ = new os::Handler(&thread_);
+
+ test_l2cap_classic_module_ = new TestL2capClassicModule();
+ test_l2cap_classic_module_->Start();
+ fake_registry_.InjectTestModule(&l2cap::classic::L2capClassicModule::Factory, test_l2cap_classic_module_);
+
+ fake_registry_.Start<shim::L2cap>(&thread_);
+ shim_l2cap_ = static_cast<shim::L2cap*>(fake_registry_.GetModuleUnderTest(&shim::L2cap::Factory));
+ }
+
+ void TearDown() override {
+ fake_registry_.StopAll();
+ handler_->Clear();
+ delete handler_;
+ }
+ os::Handler* handler_ = nullptr;
+ l2cap::classic::internal::testing::MockDynamicChannelServiceManagerImpl mock_;
+
+ private:
+ TestModuleRegistry fake_registry_;
+ os::Thread& thread_ = fake_registry_.GetTestThread();
+};
+
+TEST_F(ShimL2capTest, CreateThenDisconnectBeforeCompletion) {
+ SetConnectionFuture();
+
+ ASSERT(NumberOfConnections() == 0);
+ uint16_t cid = CreateConnection(kPsm, device_address);
+ ASSERT(cid != 0);
+
+ WaitConnectionFuture();
+ ASSERT(NumberOfConnections() == 1);
+
+ shim_l2cap_->CloseConnection(cid);
+}
+
+TEST_F(ShimL2capTest, MaxCreatedConnections) {
+ for (int i = 0; i < 65536 - 64; i++) {
+ SetConnectionFuture();
+ uint16_t cid = CreateConnection(kPsm, device_address);
+ ASSERT(cid != 0);
+ WaitConnectionFuture();
+
+ ASSERT(NumberOfConnections() == i + 1);
+ }
+ uint16_t cid = CreateConnection(kPsm, device_address);
+ ASSERT(cid == 0);
+
+ ASSERT(NumberOfConnections() == 65536 - 64);
+}
+
+TEST_F(ShimL2capTest, TwoDifferentCreatedConnections) {
+ {
+ SetConnectionFuture();
+ uint16_t cid = CreateConnection(kPsm, device_address);
+ ASSERT(cid != 0);
+ WaitConnectionFuture();
+
+ ASSERT(NumberOfConnections() == 1);
+ }
+
+ {
+ SetConnectionFuture();
+ uint16_t cid = CreateConnection(kPsm2, device_address2);
+ ASSERT(cid != 0);
+ WaitConnectionFuture();
+
+ ASSERT(NumberOfConnections() == 2);
+ }
+}
+
+TEST_F(ShimL2capTest, ConnectFail) {
+ SetConnectionFuture();
+ uint16_t cid = CreateConnection(kPsm, device_address);
+ ASSERT(cid != 0);
+ WaitConnectionFuture();
+
+ ASSERT(NumberOfConnections() == 1);
+
+ l2cap::classic::DynamicChannelManager::ConnectionResult result{
+ .connection_result_code = TestDynamicChannelManager::ConnectionResultCode::FAIL_NO_SERVICE_REGISTERED,
+ .hci_error = hci::ErrorCode::SUCCESS,
+ .l2cap_connection_response_result = l2cap::ConnectionResponseResult::SUCCESS,
+ };
+
+ std::promise<void> on_fail_promise;
+ auto on_fail_future = on_fail_promise.get_future();
+ handler_->Post(common::BindOnce(&TestDynamicChannelManagerImpl::SetConnectionOnFail,
+ common::Unretained(test_l2cap_classic_module_->impl_.get()), result,
+ std::move(on_fail_promise)));
+ on_fail_future.wait();
+
+ ASSERT(connection_connected_ == false);
+
+ shim_l2cap_->CloseConnection(cid);
+}
+
+TEST_F(ShimL2capTest, ConnectOpen) {
+ SetConnectionFuture();
+ uint16_t cid = CreateConnection(kPsm, device_address);
+ ASSERT(cid != 0);
+ WaitConnectionFuture();
+
+ ASSERT(NumberOfConnections() == 1);
+
+ hci::Address address;
+ hci::Address::FromString(device_address, address);
+ test_link_.device_with_type_ = hci::AddressWithType(address, hci::AddressType::PUBLIC_DEVICE_ADDRESS);
+
+ l2cap::Psm psm = kPsm;
+ l2cap::Cid local_cid = kCid;
+ l2cap::Cid remote_cid = kCid2;
+
+ std::shared_ptr<l2cap::internal::DynamicChannelImpl> impl =
+ std::make_shared<l2cap::internal::DynamicChannelImpl>(psm, local_cid, remote_cid, &test_link_, handler_);
+
+ auto channel = std::make_unique<l2cap::DynamicChannel>(impl, handler_);
+
+ std::promise<void> on_fail_promise;
+ auto on_fail_future = on_fail_promise.get_future();
+
+ auto connection_complete_future = connection_complete_promise_.get_future();
+ handler_->Post(common::BindOnce(&TestDynamicChannelManagerImpl::SetConnectionOnOpen,
+ common::Unretained(test_l2cap_classic_module_->impl_.get()), std::move(channel),
+ std::move(on_fail_promise)));
+ connection_complete_future.wait();
+
+ on_fail_future.wait();
+
+ ASSERT(connection_connected_ == true);
+
+ auto future = test_link_.connection_closed_promise_.get_future();
+ shim_l2cap_->CloseConnection(cid);
+ future.wait();
+}
+
+TEST_F(ShimL2capTest, RegisterService_Success) {
+ std::promise<uint16_t> registration_promise;
+ auto registration_pending = registration_promise.get_future();
+
+ SetRegistrationFuture();
+ shim_l2cap_->RegisterService(
+ kPsm, kNoUseErtm, kMtu,
+ std::bind(&bluetooth::shim::ShimL2capTest::OnConnectionComplete, this, std::placeholders::_1,
+ std::placeholders::_2, std::placeholders::_3, std::placeholders::_4),
+ std::move(registration_promise));
+ WaitRegistrationFuture();
+ ASSERT_LOG(test_l2cap_classic_module_->impl_->on_registration_complete_, "Synchronization failure");
+ ASSERT(test_l2cap_classic_module_->impl_->services_ == 1);
+
+ l2cap::classic::DynamicChannelManager::RegistrationResult result{
+ l2cap::classic::DynamicChannelManager::RegistrationResult::SUCCESS,
+ };
+ auto service = std::make_unique<TestDynamicChannelService>(kPsm, &mock_, handler_);
+
+ handler_->Post(common::BindOnce(std::move(test_l2cap_classic_module_->impl_->on_registration_complete_), result,
+ std::move(service)));
+ uint16_t psm = registration_pending.get();
+ ASSERT(psm == kPsm);
+}
+
+TEST_F(ShimL2capTest, RegisterService_Duplicate) {
+ std::promise<uint16_t> promise;
+ auto future = promise.get_future();
+
+ SetRegistrationFuture();
+ shim_l2cap_->RegisterService(
+ kPsm, kNoUseErtm, kMtu,
+ std::bind(&bluetooth::shim::ShimL2capTest::OnConnectionComplete, this, std::placeholders::_1,
+ std::placeholders::_2, std::placeholders::_3, std::placeholders::_4),
+ std::move(promise));
+ WaitRegistrationFuture();
+ ASSERT_LOG(test_l2cap_classic_module_->impl_->on_registration_complete_, "Synchronization failure");
+ ASSERT(test_l2cap_classic_module_->impl_->services_ == 1);
+
+ l2cap::classic::DynamicChannelManager::RegistrationResult result{
+ l2cap::classic::DynamicChannelManager::RegistrationResult::FAIL_DUPLICATE_SERVICE,
+ };
+ auto service = std::make_unique<TestDynamicChannelService>(kPsm, &mock_, handler_);
+
+ handler_->Post(common::BindOnce(std::move(test_l2cap_classic_module_->impl_->on_registration_complete_), result,
+ std::move(service)));
+ uint16_t psm = future.get();
+ ASSERT(psm == l2cap::kDefaultPsm);
+}
+
+TEST_F(ShimL2capTest, RegisterService_Invalid) {
+ std::promise<uint16_t> promise;
+ auto future = promise.get_future();
+
+ SetRegistrationFuture();
+
+ shim_l2cap_->RegisterService(
+ kPsm, kNoUseErtm, kMtu,
+ std::bind(&bluetooth::shim::ShimL2capTest::OnConnectionComplete, this, std::placeholders::_1,
+ std::placeholders::_2, std::placeholders::_3, std::placeholders::_4),
+ std::move(promise));
+
+ l2cap::classic::DynamicChannelManager::RegistrationResult result{
+ l2cap::classic::DynamicChannelManager::RegistrationResult::FAIL_INVALID_SERVICE,
+ };
+ auto service = std::make_unique<TestDynamicChannelService>(kPsm, &mock_, handler_);
+ WaitRegistrationFuture();
+
+ ASSERT_LOG(test_l2cap_classic_module_->impl_->on_registration_complete_, "Synchronization failure");
+ handler_->Post(common::BindOnce(std::move(test_l2cap_classic_module_->impl_->on_registration_complete_), result,
+ std::move(service)));
+ uint16_t psm = future.get();
+ ASSERT(psm == l2cap::kDefaultPsm);
+ ASSERT(test_l2cap_classic_module_->impl_->services_ == 1);
+}
+
+} // namespace
+} // namespace shim
+} // namespace bluetooth
diff --git a/main/shim/le_scanning_manager.h b/gd/shim/only_include_this_file_into_legacy_stack___ever.h
index 5f3b8d248..d1197e457 100644
--- a/main/shim/le_scanning_manager.h
+++ b/gd/shim/only_include_this_file_into_legacy_stack___ever.h
@@ -1,5 +1,5 @@
/*
- * Copyright 2020 The Android Open Source Project
+ * Copyright 2019 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -14,18 +14,19 @@
* limitations under the License.
*/
-/**
- * Gd shim layer to legacy le scanner
- */
#pragma once
-#include "include/hardware/ble_scanner.h"
-
+/**
+ * This common file provides the only visibility from the legacy stack into GD stack.
+ *
+ * Only interfaces or APIs should be exported.
+ *
+ * Only common data structures should be used to pass data between the stacks.
+ *
+ */
namespace bluetooth {
namespace shim {
-
-BleScannerInterface* get_ble_scanner_instance();
-void init_scanning_manager();
-
+class Dumpsys;
+class L2cap;
} // namespace shim
} // namespace bluetooth \ No newline at end of file
diff --git a/gd/shim/stack.cc b/gd/shim/stack.cc
new file mode 100644
index 000000000..8b7ebfe69
--- /dev/null
+++ b/gd/shim/stack.cc
@@ -0,0 +1,125 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#define LOG_TAG "bt_gd_shim"
+
+#include "shim/stack.h"
+#include "att/att_module.h"
+#include "hal/hci_hal.h"
+#include "hci/acl_manager.h"
+#include "hci/hci_layer.h"
+#include "hci/le_advertising_manager.h"
+#include "hci/le_scanning_manager.h"
+#include "l2cap/classic/l2cap_classic_module.h"
+#include "l2cap/le/l2cap_le_module.h"
+#include "neighbor/connectability.h"
+#include "neighbor/discoverability.h"
+#include "neighbor/inquiry.h"
+#include "neighbor/name.h"
+#include "neighbor/name_db.h"
+#include "neighbor/page.h"
+#include "neighbor/scan.h"
+#include "os/log.h"
+#include "os/thread.h"
+#include "security/security_module.h"
+#include "shim/dumpsys.h"
+#include "shim/l2cap.h"
+#include "stack_manager.h"
+#include "storage/legacy.h"
+
+using ::bluetooth::os::Thread;
+
+struct bluetooth::shim::Stack::impl {
+ void Start() {
+ if (is_running_) {
+ LOG_ERROR("%s Gd stack already running", __func__);
+ return;
+ }
+
+ LOG_INFO("%s Starting Gd stack", __func__);
+ ModuleList modules;
+ modules.add<::bluetooth::att::AttModule>();
+ modules.add<::bluetooth::hal::HciHal>();
+ modules.add<::bluetooth::hci::AclManager>();
+ modules.add<::bluetooth::hci::HciLayer>();
+ modules.add<::bluetooth::hci::LeAdvertisingManager>();
+ modules.add<::bluetooth::hci::LeScanningManager>();
+ modules.add<::bluetooth::l2cap::classic::L2capClassicModule>();
+ modules.add<::bluetooth::l2cap::le::L2capLeModule>();
+ modules.add<::bluetooth::neighbor::ConnectabilityModule>();
+ modules.add<::bluetooth::neighbor::DiscoverabilityModule>();
+ modules.add<::bluetooth::neighbor::InquiryModule>();
+ modules.add<::bluetooth::neighbor::NameModule>();
+ modules.add<::bluetooth::neighbor::NameDbModule>();
+ modules.add<::bluetooth::neighbor::PageModule>();
+ modules.add<::bluetooth::neighbor::ScanModule>();
+ modules.add<::bluetooth::security::SecurityModule>();
+ modules.add<::bluetooth::storage::LegacyModule>();
+ modules.add<::bluetooth::shim::Dumpsys>();
+ modules.add<::bluetooth::shim::L2cap>();
+
+ stack_thread_ = new Thread("gd_stack_thread", Thread::Priority::NORMAL);
+ stack_manager_.StartUp(&modules, stack_thread_);
+ // TODO(cmanton) Gd stack has spun up another thread with no
+ // ability to ascertain the completion
+ is_running_ = true;
+ LOG_INFO("%s Successfully toggled Gd stack", __func__);
+ }
+
+ void Stop() {
+ if (!is_running_) {
+ LOG_ERROR("%s Gd stack not running", __func__);
+ return;
+ }
+
+ stack_manager_.ShutDown();
+ delete stack_thread_;
+ is_running_ = false;
+ LOG_INFO("%s Successfully shut down Gd stack", __func__);
+ }
+
+ StackManager* GetStackManager() {
+ ASSERT(is_running_);
+ return &stack_manager_;
+ }
+
+ private:
+ os::Thread* stack_thread_ = nullptr;
+ bool is_running_ = false;
+ StackManager stack_manager_;
+};
+
+bluetooth::shim::Stack::Stack() {
+ pimpl_ = std::make_unique<impl>();
+ LOG_INFO("%s Created gd stack", __func__);
+}
+
+void bluetooth::shim::Stack::Start() {
+ pimpl_->Start();
+}
+
+void bluetooth::shim::Stack::Stop() {
+ pimpl_->Stop();
+}
+
+bluetooth::StackManager* bluetooth::shim::Stack::GetStackManager() {
+ return pimpl_->GetStackManager();
+}
+
+bluetooth::shim::Stack* bluetooth::shim::GetGabeldorscheStack() {
+ static Stack* instance = new Stack();
+ return instance;
+}
diff --git a/gd/iso/iso_module.h b/gd/shim/stack.h
index a7e24d3a5..e9ef3ffc7 100644
--- a/gd/iso/iso_module.h
+++ b/gd/shim/stack.h
@@ -1,5 +1,5 @@
/*
- * Copyright 2020 The Android Open Source Project
+ * Copyright 2019 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -13,42 +13,47 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
+
#pragma once
#include <memory>
-#include "iso/iso_manager.h"
-#include "module.h"
-
+#include "neighbor/connectability.h"
+#include "neighbor/discoverability.h"
+#include "neighbor/inquiry.h"
+#include "neighbor/name.h"
+#include "neighbor/page.h"
+#include "security/security_module.h"
+#include "shim/dumpsys.h"
+#include "shim/l2cap.h"
+#include "stack_manager.h"
+#include "storage/legacy.h"
+
+/**
+ * The shim layer implementation on the Gd stack side.
+ */
namespace bluetooth {
-namespace iso {
+namespace shim {
-class IsoModule : public bluetooth::Module {
+class Stack {
public:
- IsoModule() = default;
- ~IsoModule() = default;
-
- /**
- * Get the api to the IsoManager
- */
- std::unique_ptr<IsoManager> GetIsoManager();
-
- static const ModuleFactory Factory;
+ Stack();
+ ~Stack() = default;
- protected:
- void ListDependencies(ModuleList* list) override;
+ void Start();
+ void Stop();
- void Start() override;
-
- void Stop() override;
-
- std::string ToString() const override;
+ StackManager* GetStackManager();
private:
struct impl;
std::unique_ptr<impl> pimpl_;
- DISALLOW_COPY_AND_ASSIGN(IsoModule);
+
+ Stack(const Stack&) = delete;
+ void operator=(const Stack&) = delete;
};
-} // namespace iso
+Stack* GetGabeldorscheStack();
+
+} // namespace shim
} // namespace bluetooth
diff --git a/gd/shim/test_data/dumpsys_data.bfbs b/gd/shim/test_data/dumpsys_data.bfbs
deleted file mode 100644
index afe2ea540..000000000
--- a/gd/shim/test_data/dumpsys_data.bfbs
+++ /dev/null
Binary files differ
diff --git a/gd/shim/test_data/dumpsys_test_data_bin b/gd/shim/test_data/dumpsys_test_data_bin
deleted file mode 100644
index b9c410d5c..000000000
--- a/gd/shim/test_data/dumpsys_test_data_bin
+++ /dev/null
Binary files differ
diff --git a/gd/shim/test_data/dumpsys_test_data_bin.h b/gd/shim/test_data/dumpsys_test_data_bin.h
deleted file mode 100644
index 1a30dd2f3..000000000
--- a/gd/shim/test_data/dumpsys_test_data_bin.h
+++ /dev/null
@@ -1,67 +0,0 @@
-// Generated file by bluetooth_flatbuffer bundler
-#pragma once
-#include <sys/types.h>
-#include <string>
-namespace bluetooth {
-namespace test {
-extern const unsigned char* data;
-extern const size_t data_size;
-const std::string& GetBundledSchemaData();
-} // namespace test
-} // namespace bluetooth
-namespace {
-const unsigned char data_[] = {
- 0x10, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x10, 0x00, 0x04, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x0a, 0x00, 0x00,
- 0x00, 0x30, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x44, 0x00,
- 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x62, 0x6c, 0x75, 0x65, 0x74, 0x6f, 0x6f, 0x74, 0x68, 0x2e, 0x44, 0x75, 0x6d,
- 0x70, 0x73, 0x79, 0x73, 0x44, 0x61, 0x74, 0x61, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00, 0x00, 0x42, 0x75, 0x6e, 0x64,
- 0x6c, 0x65, 0x64, 0x20, 0x73, 0x63, 0x68, 0x65, 0x6d, 0x61, 0x20, 0x74, 0x61, 0x62, 0x6c, 0x65, 0x73, 0x00, 0x00,
- 0x00, 0x08, 0x00, 0x0c, 0x00, 0x04, 0x00, 0x08, 0x00, 0x08, 0x00, 0x00, 0x00, 0xec, 0x02, 0x00, 0x00, 0x04, 0x00,
- 0x00, 0x00, 0xe0, 0x02, 0x00, 0x00, 0x18, 0x00, 0x00, 0x00, 0x42, 0x46, 0x42, 0x53, 0x10, 0x00, 0x1c, 0x00, 0x04,
- 0x00, 0x08, 0x00, 0x0c, 0x00, 0x10, 0x00, 0x14, 0x00, 0x18, 0x00, 0x10, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00,
- 0x28, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0xd8, 0x01, 0x00, 0x00, 0x38,
- 0x01, 0x00, 0x00, 0x3c, 0xfe, 0xff, 0xff, 0x1c, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
- 0x03, 0x00, 0x00, 0x00, 0x34, 0x00, 0x00, 0x00, 0x80, 0x00, 0x00, 0x00, 0xf4, 0x00, 0x00, 0x00, 0x15, 0x00, 0x00,
- 0x00, 0x62, 0x6c, 0x75, 0x65, 0x74, 0x6f, 0x6f, 0x74, 0x68, 0x2e, 0x44, 0x75, 0x6d, 0x70, 0x73, 0x79, 0x73, 0x44,
- 0x61, 0x74, 0x61, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x10, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x04, 0x00, 0x06, 0x00, 0x0c,
- 0x00, 0x00, 0x00, 0x02, 0x00, 0x08, 0x00, 0x14, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x82, 0xff, 0xff, 0xff,
- 0x00, 0x00, 0x00, 0x0f, 0x01, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00, 0x6d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x5f,
- 0x75, 0x6e, 0x69, 0x74, 0x74, 0x65, 0x73, 0x74, 0x5f, 0x64, 0x61, 0x74, 0x61, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00,
- 0x14, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x04, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x00, 0x10, 0x00, 0x18, 0x00, 0x00, 0x00, 0x01, 0x00, 0x06, 0x00, 0x4c, 0x00, 0x00, 0x00, 0x3c, 0x00, 0x00, 0x00,
- 0x04, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x74, 0xfe, 0xff, 0xff, 0x10, 0x00, 0x00,
- 0x00, 0x04, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x41, 0x6e, 0x79, 0x00, 0x07, 0x00, 0x00, 0x00, 0x70, 0x72,
- 0x69, 0x76, 0x61, 0x63, 0x79, 0x00, 0x00, 0x00, 0x0a, 0x00, 0x0c, 0x00, 0x07, 0x00, 0x00, 0x00, 0x08, 0x00, 0x0a,
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0f, 0x02, 0x00, 0x00, 0x00, 0x11, 0x00, 0x00, 0x00, 0x73, 0x68, 0x69, 0x6d,
- 0x5f, 0x64, 0x75, 0x6d, 0x70, 0x73, 0x79, 0x73, 0x5f, 0x64, 0x61, 0x74, 0x61, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x10,
- 0x00, 0x08, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x06, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x10, 0x00,
- 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0xb6, 0xfe, 0xff, 0xff, 0x00, 0x00, 0x00, 0x0d, 0x05, 0x00, 0x00, 0x00, 0x74,
- 0x69, 0x74, 0x6c, 0x65, 0x00, 0x00, 0x00, 0x70, 0xff, 0xff, 0xff, 0x14, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00,
- 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x2c, 0x00, 0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x62, 0x6c, 0x75,
- 0x65, 0x74, 0x6f, 0x6f, 0x74, 0x68, 0x2e, 0x73, 0x68, 0x69, 0x6d, 0x2e, 0x44, 0x75, 0x6d, 0x70, 0x73, 0x79, 0x73,
- 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x44, 0x61, 0x74, 0x61, 0x00, 0x00, 0x00, 0x00, 0x68, 0xff, 0xff, 0xff, 0x00,
- 0x00, 0x04, 0x00, 0x3c, 0x00, 0x00, 0x00, 0x30, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
- 0x04, 0x00, 0x00, 0x00, 0x50, 0xff, 0xff, 0xff, 0x10, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00,
- 0x00, 0x41, 0x6e, 0x79, 0x00, 0x07, 0x00, 0x00, 0x00, 0x70, 0x72, 0x69, 0x76, 0x61, 0x63, 0x79, 0x00, 0x46, 0xff,
- 0xff, 0xff, 0x00, 0x00, 0x00, 0x0d, 0x05, 0x00, 0x00, 0x00, 0x74, 0x69, 0x74, 0x6c, 0x65, 0x00, 0x00, 0x00, 0x0c,
- 0x00, 0x10, 0x00, 0x04, 0x00, 0x08, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x14, 0x00, 0x00, 0x00,
- 0x08, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x1c, 0x00, 0x00,
- 0x00, 0x62, 0x6c, 0x75, 0x65, 0x74, 0x6f, 0x6f, 0x74, 0x68, 0x2e, 0x4d, 0x6f, 0x64, 0x75, 0x6c, 0x65, 0x55, 0x6e,
- 0x69, 0x74, 0x54, 0x65, 0x73, 0x74, 0x44, 0x61, 0x74, 0x61, 0x00, 0x00, 0x00, 0x00, 0x18, 0x00, 0x14, 0x00, 0x08,
- 0x00, 0x0c, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x10, 0x00,
- 0x18, 0x00, 0x00, 0x00, 0x00, 0x00, 0x04, 0x00, 0x4c, 0x00, 0x00, 0x00, 0x40, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00,
- 0x00, 0x01, 0x00, 0x00, 0x00, 0x0c, 0x00, 0x00, 0x00, 0x08, 0x00, 0x0c, 0x00, 0x04, 0x00, 0x08, 0x00, 0x08, 0x00,
- 0x00, 0x00, 0x10, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x41, 0x6e, 0x79, 0x00, 0x07,
- 0x00, 0x00, 0x00, 0x70, 0x72, 0x69, 0x76, 0x61, 0x63, 0x79, 0x00, 0x00, 0x00, 0x06, 0x00, 0x08, 0x00, 0x07, 0x00,
- 0x06, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x0d, 0x05, 0x00, 0x00, 0x00, 0x74, 0x69, 0x74, 0x6c, 0x65, 0x00, 0x00,
- 0x00, 0x15, 0x00, 0x00, 0x00, 0x62, 0x6c, 0x75, 0x65, 0x74, 0x6f, 0x6f, 0x74, 0x68, 0x2e, 0x44, 0x75, 0x6d, 0x70,
- 0x73, 0x79, 0x73, 0x44, 0x61, 0x74, 0x61, 0x00, 0x00, 0x00};
-const std::string string_data_(data_, data_ + sizeof(data_));
-} // namespace
-const unsigned char* bluetooth::test::data = data_;
-const size_t bluetooth::test::data_size = 884;
-const std::string& bluetooth::test::GetBundledSchemaData() {
- return string_data_;
-}
diff --git a/gd/stack_manager.cc b/gd/stack_manager.cc
index 5420b99de..9c01d5641 100644
--- a/gd/stack_manager.cc
+++ b/gd/stack_manager.cc
@@ -16,50 +16,33 @@
#include "stack_manager.h"
-#include <fcntl.h>
-#include <unistd.h>
#include <chrono>
#include <future>
#include <queue>
#include "common/bind.h"
+#include "hal/hci_hal.h"
#include "module.h"
#include "os/handler.h"
#include "os/log.h"
#include "os/thread.h"
-#include "os/wakelock_manager.h"
using ::bluetooth::os::Handler;
using ::bluetooth::os::Thread;
-using ::bluetooth::os::WakelockManager;
namespace bluetooth {
-constexpr char bluetooth_pid_file[] = "/var/run/bluetooth";
-
void StackManager::StartUp(ModuleList* modules, Thread* stack_thread) {
management_thread_ = new Thread("management_thread", Thread::Priority::NORMAL);
handler_ = new Handler(management_thread_);
- WakelockManager::Get().Acquire();
-
std::promise<void> promise;
auto future = promise.get_future();
handler_->Post(common::BindOnce(&StackManager::handle_start_up, common::Unretained(this), modules, stack_thread,
std::move(promise)));
auto init_status = future.wait_for(std::chrono::seconds(3));
-
- WakelockManager::Get().Release();
-
- ASSERT_LOG(
- init_status == std::future_status::ready,
- "Can't start stack, last instance: %s",
- registry_.last_instance_.c_str());
-
- pid_fd_ = open(bluetooth_pid_file, O_WRONLY | O_CREAT, 0644);
- pid_t my_pid = getpid();
- write(pid_fd_, &my_pid, sizeof(pid_t));
+ ASSERT_LOG(init_status == std::future_status::ready, "Can't start stack");
LOG_INFO("init complete");
}
@@ -70,29 +53,17 @@ void StackManager::handle_start_up(ModuleList* modules, Thread* stack_thread, st
}
void StackManager::ShutDown() {
- WakelockManager::Get().Acquire();
-
std::promise<void> promise;
auto future = promise.get_future();
handler_->Post(common::BindOnce(&StackManager::handle_shut_down, common::Unretained(this), std::move(promise)));
- auto stop_status = future.wait_for(std::chrono::seconds(5));
-
- WakelockManager::Get().Release();
- WakelockManager::Get().CleanUp();
-
- ASSERT_LOG(
- stop_status == std::future_status::ready,
- "Can't stop stack, last instance: %s",
- registry_.last_instance_.c_str());
+ auto stop_status = future.wait_for(std::chrono::seconds(3));
+ ASSERT_LOG(stop_status == std::future_status::ready, "Can't stop stack");
handler_->Clear();
- handler_->WaitUntilStopped(std::chrono::milliseconds(2000));
+ handler_->WaitUntilStopped(std::chrono::milliseconds(20));
delete handler_;
delete management_thread_;
-
- unlink(bluetooth_pid_file);
- close(pid_fd_);
}
void StackManager::handle_shut_down(std::promise<void> promise) {
diff --git a/gd/stack_manager.h b/gd/stack_manager.h
index 985bd0b73..9a86480e9 100644
--- a/gd/stack_manager.h
+++ b/gd/stack_manager.h
@@ -32,16 +32,10 @@ class StackManager {
return static_cast<T*>(registry_.Get(&T::Factory));
}
- template <class T>
- bool IsStarted() const {
- return registry_.IsStarted(&T::Factory);
- }
-
private:
os::Thread* management_thread_ = nullptr;
os::Handler* handler_ = nullptr;
ModuleRegistry registry_;
- int pid_fd_ = 0;
void handle_start_up(ModuleList* modules, os::Thread* stack_thread, std::promise<void> promise);
void handle_shut_down(std::promise<void> promise);
diff --git a/gd/stack_manager_unittest.cc b/gd/stack_manager_unittest.cc
index b82fe16ef..e79a94f14 100644
--- a/gd/stack_manager_unittest.cc
+++ b/gd/stack_manager_unittest.cc
@@ -38,9 +38,6 @@ class TestModuleNoDependency : public Module {
void ListDependencies(ModuleList* list) override {}
void Start() override {}
void Stop() override {}
- std::string ToString() const override {
- return std::string("TestModuleDep");
- }
};
const ModuleFactory TestModuleNoDependency::Factory = ModuleFactory([]() { return new TestModuleNoDependency(); });
diff --git a/gd/storage/Android.bp b/gd/storage/Android.bp
index 6644da1d4..a320f6a64 100644
--- a/gd/storage/Android.bp
+++ b/gd/storage/Android.bp
@@ -1,45 +1,16 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "BluetoothStorageSources",
srcs: [
- "adapter_config.cc",
- "classic_device.cc",
- "config_cache.cc",
- "config_cache_helper.cc",
- "device.cc",
- "le_device.cc",
- "legacy_config_file.cc",
- "mutation.cc",
- "mutation_entry.cc",
- "storage_module.cc",
- ],
-}
-
-filegroup {
- name: "BluetoothStorageUnitTestSources",
- srcs: [
- "adapter_config_test.cc",
- "classic_device_test.cc",
- "config_cache_test.cc",
- "config_cache_helper_test.cc",
- "device_test.cc",
- "le_device_test.cc",
- "legacy_config_file_test.cc",
- "mutation_test.cc",
+ "legacy.cc",
+ "legacy_osi_config.cc",
],
}
filegroup {
name: "BluetoothStorageTestSources",
srcs: [
- "storage_module_test.cc",
+ "legacy_test.cc",
+ "legacy_osi_config.cc",
],
}
+
diff --git a/gd/storage/BUILD.gn b/gd/storage/BUILD.gn
deleted file mode 100644
index c7864e4bd..000000000
--- a/gd/storage/BUILD.gn
+++ /dev/null
@@ -1,32 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-
-source_set("BluetoothStorageSources") {
- sources = [
- "adapter_config.cc",
- "classic_device.cc",
- "config_cache.cc",
- "config_cache_helper.cc",
- "device.cc",
- "le_device.cc",
- "legacy_config_file.cc",
- "mutation.cc",
- "mutation_entry.cc",
- "storage_module.cc",
- ]
-
- configs += [ "//bt/gd:gd_defaults" ]
- deps = [ "//bt/gd:gd_default_deps" ]
-}
diff --git a/gd/storage/adapter_config.cc b/gd/storage/adapter_config.cc
deleted file mode 100644
index 56620d124..000000000
--- a/gd/storage/adapter_config.cc
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/adapter_config.h"
-
-namespace bluetooth {
-namespace storage {
-
-AdapterConfig::AdapterConfig(ConfigCache* config, ConfigCache* memory_only_config, std::string section)
- : config_(config), memory_only_config_(memory_only_config), section_(std::move(section)) {}
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/adapter_config.h b/gd/storage/adapter_config.h
deleted file mode 100644
index 228a39486..000000000
--- a/gd/storage/adapter_config.h
+++ /dev/null
@@ -1,73 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <string>
-
-#include "common/byte_array.h"
-#include "hci/address.h"
-#include "storage/config_cache.h"
-#include "storage/device.h"
-
-namespace bluetooth {
-namespace storage {
-
-class AdapterConfig {
- public:
- AdapterConfig(ConfigCache* config, ConfigCache* memory_only_config, std::string section);
-
- // for move
- AdapterConfig(AdapterConfig&& other) noexcept = default;
- AdapterConfig& operator=(AdapterConfig&& other) noexcept = default;
-
- // for copy
- AdapterConfig(const AdapterConfig& other) noexcept = default;
- AdapterConfig& operator=(const AdapterConfig& other) noexcept = default;
-
- // operators
- bool operator==(const AdapterConfig& other) const {
- return config_ == other.config_ && memory_only_config_ == other.memory_only_config_ && section_ == other.section_;
- }
- bool operator!=(const AdapterConfig& other) const {
- return !(*this == other);
- }
- bool operator<(const AdapterConfig& other) const {
- return config_ < other.config_ && memory_only_config_ < other.memory_only_config_ && section_ < other.section_;
- }
- bool operator>(const AdapterConfig& rhs) const {
- return (rhs < *this);
- }
- bool operator<=(const AdapterConfig& rhs) const {
- return !(*this > rhs);
- }
- bool operator>=(const AdapterConfig& rhs) const {
- return !(*this < rhs);
- }
-
- private:
- ConfigCache* config_;
- ConfigCache* memory_only_config_;
- std::string section_;
-
- public:
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(Address, hci::Address, "Address");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(LeIdentityResolvingKey, common::ByteArray<16>, "LE_LOCAL_KEY_IRK");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(LegacyScanMode, hci::LegacyScanMode, "ScanMode");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(DiscoveryTimeoutSeconds, int, "DiscoveryTimeout");
-};
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/adapter_config_test.cc b/gd/storage/adapter_config_test.cc
deleted file mode 100644
index e3c3791c6..000000000
--- a/gd/storage/adapter_config_test.cc
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "storage/adapter_config.h"
-#include "storage/mutation.h"
-
-using bluetooth::common::ByteArray;
-using bluetooth::hci::Address;
-using bluetooth::hci::DeviceType;
-using bluetooth::storage::AdapterConfig;
-using bluetooth::storage::ConfigCache;
-using bluetooth::storage::Device;
-using bluetooth::storage::Mutation;
-using ::testing::Eq;
-using ::testing::Optional;
-
-TEST(AdapterConfigTest, create_new_adapter_config) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- AdapterConfig adapter_config(&config, &memory_only_config, "Adapter");
- ASSERT_FALSE(adapter_config.GetAddress());
-}
-
-TEST(AdapterConfigTest, set_property) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- AdapterConfig adapter_config(&config, &memory_only_config, "Adapter");
- ASSERT_FALSE(adapter_config.GetAddress());
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(adapter_config.SetAddress(address));
- mutation.Commit();
- ASSERT_THAT(adapter_config.GetAddress(), Optional(Eq(address)));
-}
-
-TEST(AdapterConfigTest, equality_test) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- bluetooth::hci::Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- AdapterConfig adapter_config_1(&config, &memory_only_config, "Adapter");
- AdapterConfig adapter_config_2(&config, &memory_only_config, "Adapter");
- ASSERT_EQ(adapter_config_1, adapter_config_2);
- ConfigCache memory_only_config_2(10, {});
- AdapterConfig adapter_config_3(&config, &memory_only_config_2, "Adapter");
- ASSERT_NE(adapter_config_1, adapter_config_3);
-}
-
diff --git a/gd/storage/classic_device.cc b/gd/storage/classic_device.cc
deleted file mode 100644
index f01abd6fa..000000000
--- a/gd/storage/classic_device.cc
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/classic_device.h"
-
-#include <algorithm>
-
-#include "common/strings.h"
-
-namespace bluetooth {
-namespace storage {
-
-const std::unordered_set<std::string_view> ClassicDevice::kLinkKeyProperties = {"LinkKey"};
-
-ClassicDevice::ClassicDevice(ConfigCache* config, ConfigCache* memory_only_config, std::string section)
- : config_(config), memory_only_config_(memory_only_config), section_(std::move(section)) {}
-
-Device ClassicDevice::Parent() {
- return Device(config_, memory_only_config_, section_);
-}
-
-std::string ClassicDevice::ToLogString() const {
- return section_;
-}
-
-hci::Address ClassicDevice::GetAddress() const {
- // section name of a classic device is its MAC address
- auto addr = hci::Address::FromString(section_);
- ASSERT(addr.has_value());
- return std::move(addr.value());
-}
-
-bool ClassicDevice::IsPaired() const {
- // This first check is here only to speed up the checking process
- if (!config_->IsPersistentSection(section_)) {
- return false;
- }
- return config_->HasAtLeastOneMatchingPropertiesInSection(section_, kLinkKeyProperties);
-}
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/classic_device.h b/gd/storage/classic_device.h
deleted file mode 100644
index 3e9874350..000000000
--- a/gd/storage/classic_device.h
+++ /dev/null
@@ -1,108 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <array>
-#include <optional>
-#include <string>
-#include <unordered_set>
-
-#include "hci/link_key.h"
-#include "hci/uuid.h"
-#include "storage/config_cache.h"
-#include "storage/config_cache_helper.h"
-#include "storage/device.h"
-
-namespace bluetooth {
-namespace storage {
-
-class ClassicDevice {
- public:
- ClassicDevice(ConfigCache* config, ConfigCache* memory_only_config, std::string section);
-
- // for move
- ClassicDevice(ClassicDevice&& other) noexcept = default;
- ClassicDevice& operator=(ClassicDevice&& other) noexcept = default;
-
- // for copy
- ClassicDevice(const ClassicDevice& other) noexcept = default;
- ClassicDevice& operator=(const ClassicDevice& other) noexcept = default;
-
- // operators
- bool operator==(const ClassicDevice& other) const {
- return config_ == other.config_ && memory_only_config_ == other.memory_only_config_ && section_ == other.section_;
- }
- bool operator!=(const ClassicDevice& other) const {
- return !(*this == other);
- }
- bool operator<(const ClassicDevice& other) const {
- return config_ < other.config_ && memory_only_config_ < other.memory_only_config_ && section_ < other.section_;
- }
- bool operator>(const ClassicDevice& rhs) const {
- return (rhs < *this);
- }
- bool operator<=(const ClassicDevice& rhs) const {
- return !(*this > rhs);
- }
- bool operator>=(const ClassicDevice& rhs) const {
- return !(*this < rhs);
- }
-
- // Get the parent device
- Device Parent();
-
- // For logging purpose only, you can't get a ClassicDevice object from parsing a std::string
- std::string ToLogString() const;
-
- // Get address of this classic device, it must exist
- hci::Address GetAddress() const;
-
- // Return true if device has a link key in one of |kLinkKeyProperties|
- bool IsPaired() const;
-
- // Property names that correspond to a link key used in Bluetooth classic device
- static const std::unordered_set<std::string_view> kLinkKeyProperties;
-
- private:
- ConfigCache* config_;
- ConfigCache* memory_only_config_;
- std::string section_;
- friend std::hash<ClassicDevice>;
-
- public:
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(LinkKey, hci::LinkKey, "LinkKey");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(LinkKeyType, hci::KeyType, "LinkKeyType");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(ServiceUuids, std::vector<hci::Uuid>, "Service");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(SdpDiManufacturer, uint16_t, "SdpDiManufacturer");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(SdpDiModel, uint16_t, "SdpDiModel");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(SdpDiHardwareVersion, uint16_t, "SdpDiHardwareVersion");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(SdpDiVendorIdSource, uint16_t, "SdpDiVendorIdSource");
-};
-
-} // namespace storage
-} // namespace bluetooth
-
-namespace std {
-template <>
-struct hash<bluetooth::storage::ClassicDevice> {
- std::size_t operator()(const bluetooth::storage::ClassicDevice& val) const noexcept {
- std::size_t pointer_hash_1 = std::hash<bluetooth::storage::ConfigCache*>{}(val.config_);
- std::size_t pointer_hash_2 = std::hash<bluetooth::storage::ConfigCache*>{}(val.config_);
- std::size_t addr_hash = std::hash<std::string>{}(val.section_);
- return addr_hash ^ (pointer_hash_1 << 1) ^ (pointer_hash_2 << 2);
- }
-};
-} // namespace std \ No newline at end of file
diff --git a/gd/storage/classic_device_test.cc b/gd/storage/classic_device_test.cc
deleted file mode 100644
index 751ee79c5..000000000
--- a/gd/storage/classic_device_test.cc
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "common/byte_array.h"
-#include "hci/link_key.h"
-#include "storage/classic_device.h"
-#include "storage/mutation.h"
-
-using bluetooth::common::ByteArray;
-using bluetooth::hci::Address;
-using bluetooth::hci::DeviceType;
-using bluetooth::hci::kExampleLinkKey;
-using bluetooth::storage::ClassicDevice;
-using bluetooth::storage::ConfigCache;
-using bluetooth::storage::Device;
-using bluetooth::storage::Mutation;
-using ::testing::Eq;
-using ::testing::Optional;
-
-TEST(ClassicDeviceTest, create_new_le_device) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- bluetooth::hci::Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- ClassicDevice device(&config, &memory_only_config, address.ToString());
- ASSERT_FALSE(device.GetLinkKey());
-}
-
-TEST(ClassicDeviceTest, set_property) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- ClassicDevice device(&config, &memory_only_config, address.ToString());
- ASSERT_FALSE(device.GetLinkKey());
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(device.SetLinkKey(kExampleLinkKey));
- mutation.Commit();
- ASSERT_THAT(device.GetLinkKey(), Optional(Eq(kExampleLinkKey)));
-}
-
-TEST(ClassicDeviceTest, equality_test) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- bluetooth::hci::Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- ClassicDevice device1(&config, &memory_only_config, address.ToString());
- ClassicDevice device2(&config, &memory_only_config, address.ToString());
- ASSERT_EQ(device1, device2);
- bluetooth::hci::Address address3 = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x07}};
- ClassicDevice device3(&config, &memory_only_config, address3.ToString());
- ASSERT_NE(device1, device3);
-}
-
diff --git a/gd/storage/config_cache.cc b/gd/storage/config_cache.cc
deleted file mode 100644
index fb897d5e8..000000000
--- a/gd/storage/config_cache.cc
+++ /dev/null
@@ -1,459 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/config_cache.h"
-
-#include <ios>
-#include <sstream>
-#include <utility>
-
-#include "hci/enum_helper.h"
-#include "storage/mutation.h"
-
-namespace {
-
-bool TrimAfterNewLine(std::string& value) {
- std::string value_no_newline;
- size_t newline_position = value.find_first_of('\n');
- if (newline_position != std::string::npos) {
- value.erase(newline_position);
- return true;
- }
- return false;
-}
-
-} // namespace
-
-namespace bluetooth {
-namespace storage {
-
-const std::unordered_set<std::string_view> kLePropertyNames = {
- "LE_KEY_PENC", "LE_KEY_PID", "LE_KEY_PCSRK", "LE_KEY_LENC", "LE_KEY_LCSRK"};
-
-const std::unordered_set<std::string_view> kClassicPropertyNames = {
- "LinkKey", "SdpDiMaufacturer", "SdpDiModel", "SdpDiHardwareVersion", "SdpDiVendorSource"};
-
-const std::string ConfigCache::kDefaultSectionName = "Global";
-
-ConfigCache::ConfigCache(size_t temp_device_capacity, std::unordered_set<std::string_view> persistent_property_names)
- : persistent_property_names_(std::move(persistent_property_names)),
- information_sections_(),
- persistent_devices_(),
- temporary_devices_(temp_device_capacity) {}
-
-void ConfigCache::SetPersistentConfigChangedCallback(std::function<void()> persistent_config_changed_callback) {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- persistent_config_changed_callback_ = std::move(persistent_config_changed_callback);
-}
-
-ConfigCache::ConfigCache(ConfigCache&& other) noexcept
- : persistent_config_changed_callback_(std::move(other.persistent_config_changed_callback_)),
- persistent_property_names_(std::move(other.persistent_property_names_)),
- information_sections_(std::move(other.information_sections_)),
- persistent_devices_(std::move(other.persistent_devices_)),
- temporary_devices_(std::move(other.temporary_devices_)) {
- // std::function will be in a valid but unspecified state after std::move(), hence resetting it
- other.persistent_config_changed_callback_ = {};
-}
-
-ConfigCache& ConfigCache::operator=(ConfigCache&& other) noexcept {
- if (&other == this) {
- return *this;
- }
- std::lock_guard<std::recursive_mutex> my_lock(mutex_);
- std::lock_guard<std::recursive_mutex> others_lock(other.mutex_);
- persistent_config_changed_callback_.swap(other.persistent_config_changed_callback_);
- other.persistent_config_changed_callback_ = {};
- persistent_property_names_ = std::move(other.persistent_property_names_);
- information_sections_ = std::move(other.information_sections_);
- persistent_devices_ = std::move(other.persistent_devices_);
- temporary_devices_ = std::move(other.temporary_devices_);
- return *this;
-}
-
-bool ConfigCache::operator==(const ConfigCache& rhs) const {
- std::lock_guard<std::recursive_mutex> my_lock(mutex_);
- std::lock_guard<std::recursive_mutex> others_lock(rhs.mutex_);
- return persistent_property_names_ == rhs.persistent_property_names_ &&
- information_sections_ == rhs.information_sections_ && persistent_devices_ == rhs.persistent_devices_ &&
- temporary_devices_ == rhs.temporary_devices_;
-}
-
-bool ConfigCache::operator!=(const ConfigCache& rhs) const {
- return !(*this == rhs);
-}
-
-void ConfigCache::Clear() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- if (information_sections_.size() > 0) {
- information_sections_.clear();
- PersistentConfigChangedCallback();
- }
- if (persistent_devices_.size() > 0) {
- persistent_devices_.clear();
- PersistentConfigChangedCallback();
- }
- if (temporary_devices_.size() > 0) {
- temporary_devices_.clear();
- }
-}
-
-bool ConfigCache::HasSection(const std::string& section) const {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- return information_sections_.contains(section) || persistent_devices_.contains(section) ||
- temporary_devices_.contains(section);
-}
-
-bool ConfigCache::HasProperty(const std::string& section, const std::string& property) const {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- auto section_iter = information_sections_.find(section);
- if (section_iter != information_sections_.end()) {
- return section_iter->second.find(property) != section_iter->second.end();
- }
- section_iter = persistent_devices_.find(section);
- if (section_iter != persistent_devices_.end()) {
- return section_iter->second.find(property) != section_iter->second.end();
- }
- section_iter = temporary_devices_.find(section);
- if (section_iter != temporary_devices_.end()) {
- return section_iter->second.find(property) != section_iter->second.end();
- }
- return false;
-}
-
-std::optional<std::string> ConfigCache::GetProperty(const std::string& section, const std::string& property) const {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- auto section_iter = information_sections_.find(section);
- if (section_iter != information_sections_.end()) {
- auto property_iter = section_iter->second.find(property);
- if (property_iter != section_iter->second.end()) {
- return property_iter->second;
- }
- }
- section_iter = persistent_devices_.find(section);
- if (section_iter != persistent_devices_.end()) {
- auto property_iter = section_iter->second.find(property);
- if (property_iter != section_iter->second.end()) {
- return property_iter->second;
- }
- }
- section_iter = temporary_devices_.find(section);
- if (section_iter != temporary_devices_.end()) {
- auto property_iter = section_iter->second.find(property);
- if (property_iter != section_iter->second.end()) {
- return property_iter->second;
- }
- }
- return std::nullopt;
-}
-
-void ConfigCache::SetProperty(std::string section, std::string property, std::string value) {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- if (TrimAfterNewLine(section) || TrimAfterNewLine(property) || TrimAfterNewLine(value)) {
- android_errorWriteLog(0x534e4554, "70808273");
- }
- ASSERT_LOG(!section.empty(), "Empty section name not allowed");
- ASSERT_LOG(!property.empty(), "Empty property name not allowed");
- if (!IsDeviceSection(section)) {
- auto section_iter = information_sections_.find(section);
- if (section_iter == information_sections_.end()) {
- section_iter = information_sections_.try_emplace_back(section, common::ListMap<std::string, std::string>{}).first;
- }
- section_iter->second.insert_or_assign(property, std::move(value));
- PersistentConfigChangedCallback();
- return;
- }
- auto section_iter = persistent_devices_.find(section);
- if (section_iter == persistent_devices_.end() && IsPersistentProperty(property)) {
- // move paired devices or create new paired device when a link key is set
- auto section_properties = temporary_devices_.extract(section);
- if (section_properties) {
- section_iter = persistent_devices_.try_emplace_back(section, std::move(section_properties->second)).first;
- } else {
- section_iter = persistent_devices_.try_emplace_back(section, common::ListMap<std::string, std::string>{}).first;
- }
- }
- if (section_iter != persistent_devices_.end()) {
- section_iter->second.insert_or_assign(property, std::move(value));
- PersistentConfigChangedCallback();
- return;
- }
- section_iter = temporary_devices_.find(section);
- if (section_iter == temporary_devices_.end()) {
- auto triple = temporary_devices_.try_emplace(section, common::ListMap<std::string, std::string>{});
- section_iter = std::get<0>(triple);
- }
- section_iter->second.insert_or_assign(property, std::move(value));
-}
-
-bool ConfigCache::RemoveSection(const std::string& section) {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- // sections are unique among all three maps, hence removing from one of them is enough
- if (information_sections_.extract(section) || persistent_devices_.extract(section)) {
- PersistentConfigChangedCallback();
- return true;
- } else {
- return temporary_devices_.extract(section).has_value();
- }
-}
-
-bool ConfigCache::RemoveProperty(const std::string& section, const std::string& property) {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- auto section_iter = information_sections_.find(section);
- if (section_iter != information_sections_.end()) {
- auto value = section_iter->second.extract(property);
- // if section is empty after removal, remove the whole section as empty section is not allowed
- if (section_iter->second.size() == 0) {
- information_sections_.erase(section_iter);
- }
- if (value.has_value()) {
- PersistentConfigChangedCallback();
- return true;
- } else {
- return false;
- }
- }
- section_iter = persistent_devices_.find(section);
- if (section_iter != persistent_devices_.end()) {
- auto value = section_iter->second.extract(property);
- // if section is empty after removal, remove the whole section as empty section is not allowed
- if (section_iter->second.size() == 0) {
- persistent_devices_.erase(section_iter);
- } else if (value && IsPersistentProperty(property)) {
- // move unpaired device
- auto section_properties = persistent_devices_.extract(section);
- temporary_devices_.insert_or_assign(section, std::move(section_properties->second));
- }
- if (value.has_value()) {
- PersistentConfigChangedCallback();
- return true;
- } else {
- return false;
- }
- }
- section_iter = temporary_devices_.find(section);
- if (section_iter != temporary_devices_.end()) {
- auto value = section_iter->second.extract(property);
- if (section_iter->second.size() == 0) {
- temporary_devices_.erase(section_iter);
- }
- return value.has_value();
- }
- return false;
-}
-
-bool ConfigCache::IsDeviceSection(const std::string& section) {
- return hci::Address::IsValidAddress(section);
-}
-
-bool ConfigCache::IsPersistentProperty(const std::string& property) const {
- return persistent_property_names_.find(property) != persistent_property_names_.end();
-}
-
-void ConfigCache::RemoveSectionWithProperty(const std::string& property) {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- size_t num_persistent_removed = 0;
- for (auto* config_section : {&information_sections_, &persistent_devices_}) {
- for (auto it = config_section->begin(); it != config_section->end();) {
- if (it->second.contains(property)) {
- LOG_INFO("Removing persistent section %s with property %s", it->first.c_str(), property.c_str());
- it = config_section->erase(it);
- num_persistent_removed++;
- continue;
- }
- it++;
- }
- }
- for (auto it = temporary_devices_.begin(); it != temporary_devices_.end();) {
- if (it->second.contains(property)) {
- LOG_INFO("Removing temporary section %s with property %s", it->first.c_str(), property.c_str());
- it = temporary_devices_.erase(it);
- continue;
- }
- it++;
- }
- if (num_persistent_removed > 0) {
- PersistentConfigChangedCallback();
- }
-}
-
-std::vector<std::string> ConfigCache::GetPersistentSections() const {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- std::vector<std::string> paired_devices;
- paired_devices.reserve(persistent_devices_.size());
- for (const auto& elem : persistent_devices_) {
- paired_devices.emplace_back(elem.first);
- }
- return paired_devices;
-}
-
-void ConfigCache::Commit(std::queue<MutationEntry>& mutation_entries) {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- while (!mutation_entries.empty()) {
- auto entry = std::move(mutation_entries.front());
- mutation_entries.pop();
- switch (entry.entry_type) {
- case MutationEntry::EntryType::SET:
- SetProperty(std::move(entry.section), std::move(entry.property), std::move(entry.value));
- break;
- case MutationEntry::EntryType::REMOVE_PROPERTY:
- RemoveProperty(entry.section, entry.property);
- break;
- case MutationEntry::EntryType::REMOVE_SECTION:
- RemoveSection(entry.section);
- break;
- // do not write a default case so that when a new enum is defined, compilation would fail automatically
- }
- }
-}
-
-std::string ConfigCache::SerializeToLegacyFormat() const {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- std::stringstream serialized;
- for (const auto* config_section : {&information_sections_, &persistent_devices_}) {
- for (const auto& section : *config_section) {
- serialized << "[" << section.first << "]" << std::endl;
- for (const auto& property : section.second) {
- serialized << property.first << " = " << property.second << std::endl;
- }
- serialized << std::endl;
- }
- }
- return serialized.str();
-}
-
-std::vector<ConfigCache::SectionAndPropertyValue> ConfigCache::GetSectionNamesWithProperty(
- const std::string& property) const {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- std::vector<SectionAndPropertyValue> result;
- for (auto* config_section : {&information_sections_, &persistent_devices_}) {
- for (const auto& elem : *config_section) {
- auto it = elem.second.find(property);
- if (it != elem.second.end()) {
- result.emplace_back(SectionAndPropertyValue{.section = elem.first, .property = it->second});
- continue;
- }
- }
- }
- for (const auto& elem : temporary_devices_) {
- auto it = elem.second.find(property);
- if (it != elem.second.end()) {
- result.emplace_back(SectionAndPropertyValue{.section = elem.first, .property = it->second});
- continue;
- }
- }
- return result;
-}
-
-namespace {
-
-bool FixDeviceTypeInconsistencyInSection(
- const std::string& section_name, common::ListMap<std::string, std::string>& device_section_entries) {
- if (!hci::Address::IsValidAddress(section_name)) {
- return false;
- }
- bool is_le = false;
- bool is_classic = false;
- // default
- hci::DeviceType device_type = hci::DeviceType::BR_EDR;
- for (const auto& entry : device_section_entries) {
- if (kLePropertyNames.find(entry.first) != kLePropertyNames.end()) {
- is_le = true;
- }
- if (kClassicPropertyNames.find(entry.first) != kClassicPropertyNames.end()) {
- is_classic = true;
- }
- }
- if (is_classic && is_le) {
- device_type = hci::DeviceType::DUAL;
- } else if (is_classic) {
- device_type = hci::DeviceType::BR_EDR;
- } else if (is_le) {
- device_type = hci::DeviceType::LE;
- }
- bool inconsistent = true;
- std::string device_type_str = std::to_string(device_type);
- auto it = device_section_entries.find("DevType");
- if (it != device_section_entries.end()) {
- inconsistent = device_type_str != it->second;
- if (inconsistent) {
- it->second = std::move(device_type_str);
- }
- } else {
- device_section_entries.insert_or_assign("DevType", std::move(device_type_str));
- }
- return inconsistent;
-}
-
-} // namespace
-
-bool ConfigCache::FixDeviceTypeInconsistencies() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- bool persistent_device_changed = false;
- for (auto* config_section : {&information_sections_, &persistent_devices_}) {
- for (auto& elem : *config_section) {
- if (FixDeviceTypeInconsistencyInSection(elem.first, elem.second)) {
- persistent_device_changed = true;
- }
- }
- }
- bool temp_device_changed = false;
- for (auto& elem : temporary_devices_) {
- if (FixDeviceTypeInconsistencyInSection(elem.first, elem.second)) {
- temp_device_changed = true;
- }
- }
- if (persistent_device_changed) {
- PersistentConfigChangedCallback();
- }
- return persistent_device_changed || temp_device_changed;
-}
-
-bool ConfigCache::HasAtLeastOneMatchingPropertiesInSection(
- const std::string& section, const std::unordered_set<std::string_view>& property_names) const {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- const common::ListMap<std::string, std::string>* section_ptr;
- if (!IsDeviceSection(section)) {
- auto section_iter = information_sections_.find(section);
- if (section_iter == information_sections_.end()) {
- return false;
- }
- section_ptr = &section_iter->second;
- } else {
- auto section_iter = persistent_devices_.find(section);
- if (section_iter == persistent_devices_.end()) {
- section_iter = temporary_devices_.find(section);
- if (section_iter == temporary_devices_.end()) {
- return false;
- }
- }
- section_ptr = &section_iter->second;
- }
- for (const auto& property : *section_ptr) {
- if (property_names.count(property.first) > 0) {
- return true;
- }
- }
- return false;
-}
-
-bool ConfigCache::IsPersistentSection(const std::string& section) const {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- return persistent_devices_.contains(section);
-}
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/config_cache.h b/gd/storage/config_cache.h
deleted file mode 100644
index 0d83b4125..000000000
--- a/gd/storage/config_cache.h
+++ /dev/null
@@ -1,147 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <functional>
-#include <list>
-#include <mutex>
-#include <optional>
-#include <queue>
-#include <string>
-#include <string_view>
-#include <unordered_set>
-#include <utility>
-#include <vector>
-
-#include "common/list_map.h"
-#include "common/lru_cache.h"
-#include "hci/address.h"
-#include "os/utils.h"
-#include "storage/mutation_entry.h"
-
-namespace bluetooth {
-namespace storage {
-
-class Mutation;
-
-// A memory operated section-key-value structured config
-//
-// A section can be either persistent or temporary. When a section becomes persistent, all its properties are
-// written to disk.
-//
-// A section becomes persistent when a property that is part of persistent_property_names_ is written to config cache;
-// A section becomes temporary when all properties that are part of persistent_property_names_ is removed
-//
-// The definition of persistent sections is up to the user and is defined through the |persistent_property_names|
-// argument. When these properties are link key properties, then persistent sections is equal to bonded devices
-//
-// This class is thread safe
-class ConfigCache {
- public:
- ConfigCache(size_t temp_device_capacity, std::unordered_set<std::string_view> persistent_property_names);
- virtual ~ConfigCache() = default;
-
- // no copy
- DISALLOW_COPY_AND_ASSIGN(ConfigCache);
-
- // can move
- ConfigCache(ConfigCache&& other) noexcept;
- ConfigCache& operator=(ConfigCache&& other) noexcept;
-
- // comparison operators, callback doesn't count
- bool operator==(const ConfigCache& rhs) const;
- bool operator!=(const ConfigCache& rhs) const;
-
- // observers
- virtual bool HasSection(const std::string& section) const;
- virtual bool HasProperty(const std::string& section, const std::string& property) const;
- // Get property, return std::nullopt if section or property does not exist
- virtual std::optional<std::string> GetProperty(const std::string& section, const std::string& property) const;
- // Returns a copy of persistent device MAC addresses
- virtual std::vector<std::string> GetPersistentSections() const;
- // Return true if a section is persistent
- virtual bool IsPersistentSection(const std::string& section) const;
- // Return true if a section has one of the properties in |property_names|
- virtual bool HasAtLeastOneMatchingPropertiesInSection(
- const std::string& section, const std::unordered_set<std::string_view>& property_names) const;
- // Return true if a property is part of persistent_property_names_
- virtual bool IsPersistentProperty(const std::string& property) const;
- // Serialize to legacy config format
- virtual std::string SerializeToLegacyFormat() const;
- // Return a copy of pair<section_name, property_value> with property
- struct SectionAndPropertyValue {
- std::string section;
- std::string property;
- bool operator==(const SectionAndPropertyValue& rhs) const {
- return section == rhs.section && property == rhs.property;
- }
- bool operator!=(const SectionAndPropertyValue& rhs) const {
- return !(*this == rhs);
- }
- };
- virtual std::vector<SectionAndPropertyValue> GetSectionNamesWithProperty(const std::string& property) const;
-
- // modifiers
- // Commit all mutation entries in sequence while holding the config mutex
- virtual void Commit(std::queue<MutationEntry>& mutation);
- virtual void SetProperty(std::string section, std::string property, std::string value);
- virtual bool RemoveSection(const std::string& section);
- virtual bool RemoveProperty(const std::string& section, const std::string& property);
- // TODO: have a systematic way of doing this instead of specialized methods
- // Remove sections with |property| set
- virtual void RemoveSectionWithProperty(const std::string& property);
- // remove all content in this config cache, restore it to the state after the explicit constructor
- virtual void Clear();
- // Set a callback to notify interested party that a persistent config change has just happened
- virtual void SetPersistentConfigChangedCallback(std::function<void()> persistent_config_changed_callback);
-
- // Device config specific methods
- // TODO: methods here should be moved to a device specific config cache if this config cache is supposed to be generic
- // Legacy stack has device type inconsistencies, this method is trying to fix it
- virtual bool FixDeviceTypeInconsistencies();
-
- // static methods
- // Check if section is formatted as a MAC address
- static bool IsDeviceSection(const std::string& section);
-
- // constants
- static const std::string kDefaultSectionName;
-
- private:
- mutable std::recursive_mutex mutex_;
- // A callback to notify interested party that a persistent config change has just happened, empty by default
- std::function<void()> persistent_config_changed_callback_;
- // A set of property names that if set would make a section persistent and if non of these properties are set, a
- // section would become temporary again
- std::unordered_set<std::string_view> persistent_property_names_;
- // Common section that does not relate to remote device, will be written to disk
- common::ListMap<std::string, common::ListMap<std::string, std::string>> information_sections_;
- // Information about persistent devices, normally paired, will be written to disk
- common::ListMap<std::string, common::ListMap<std::string, std::string>> persistent_devices_;
- // Information about temporary devices, normally unpaired, will not be written to disk, will be evicted automatically
- // if capacity exceeds given value during initialization
- common::LruCache<std::string, common::ListMap<std::string, std::string>> temporary_devices_;
-
- // Convenience method to check if the callback is valid before calling it
- inline void PersistentConfigChangedCallback() const {
- if (persistent_config_changed_callback_) {
- persistent_config_changed_callback_();
- }
- }
-};
-
-} // namespace storage
-} // namespace bluetooth
diff --git a/gd/storage/config_cache_helper.cc b/gd/storage/config_cache_helper.cc
deleted file mode 100644
index d97749af9..000000000
--- a/gd/storage/config_cache_helper.cc
+++ /dev/null
@@ -1,124 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/config_cache_helper.h"
-
-#include "common/numbers.h"
-#include "common/strings.h"
-
-namespace bluetooth {
-namespace storage {
-
-void ConfigCacheHelper::SetBool(const std::string& section, const std::string& property, bool value) {
- config_cache_.SetProperty(section, property, value ? "true" : "false");
-}
-
-std::optional<bool> ConfigCacheHelper::GetBool(const std::string& section, const std::string& property) const {
- auto value_str = config_cache_.GetProperty(section, property);
- if (!value_str) {
- return std::nullopt;
- }
- if (*value_str == "true") {
- return true;
- } else if (*value_str == "false") {
- return false;
- } else {
- return std::nullopt;
- }
-}
-
-void ConfigCacheHelper::SetUint64(const std::string& section, const std::string& property, uint64_t value) {
- config_cache_.SetProperty(section, property, std::to_string(value));
-}
-
-std::optional<uint64_t> ConfigCacheHelper::GetUint64(const std::string& section, const std::string& property) const {
- auto value_str = config_cache_.GetProperty(section, property);
- if (!value_str) {
- return std::nullopt;
- }
- return common::Uint64FromString(*value_str);
-}
-
-void ConfigCacheHelper::SetUint32(const std::string& section, const std::string& property, uint32_t value) {
- config_cache_.SetProperty(section, property, std::to_string(value));
-}
-
-std::optional<uint32_t> ConfigCacheHelper::GetUint32(const std::string& section, const std::string& property) const {
- auto value_str = config_cache_.GetProperty(section, property);
- if (!value_str) {
- return std::nullopt;
- }
- auto large_value = GetUint64(section, property);
- if (!large_value) {
- return std::nullopt;
- }
- if (!common::IsNumberInNumericLimits<uint32_t>(*large_value)) {
- return std::nullopt;
- }
- return static_cast<uint32_t>(*large_value);
-}
-
-void ConfigCacheHelper::SetInt64(const std::string& section, const std::string& property, int64_t value) {
- config_cache_.SetProperty(section, property, std::to_string(value));
-}
-
-std::optional<int64_t> ConfigCacheHelper::GetInt64(const std::string& section, const std::string& property) const {
- auto value_str = config_cache_.GetProperty(section, property);
- if (!value_str) {
- return std::nullopt;
- }
- return common::Int64FromString(*value_str);
-}
-
-void ConfigCacheHelper::SetInt(const std::string& section, const std::string& property, int value) {
- config_cache_.SetProperty(section, property, std::to_string(value));
-}
-
-std::optional<int> ConfigCacheHelper::GetInt(const std::string& section, const std::string& property) const {
- auto value_str = config_cache_.GetProperty(section, property);
- if (!value_str) {
- return std::nullopt;
- }
- auto large_value = GetInt64(section, property);
- if (!large_value) {
- return std::nullopt;
- }
- if (!common::IsNumberInNumericLimits<int>(*large_value)) {
- return std::nullopt;
- }
- return static_cast<uint32_t>(*large_value);
-}
-
-void ConfigCacheHelper::SetBin(
- const std::string& section, const std::string& property, const std::vector<uint8_t>& value) {
- config_cache_.SetProperty(section, property, common::ToHexString(value));
-}
-
-std::optional<std::vector<uint8_t>> ConfigCacheHelper::GetBin(
- const std::string& section, const std::string& property) const {
- auto value_str = config_cache_.GetProperty(section, property);
- if (!value_str) {
- return std::nullopt;
- }
- auto value = common::FromHexString(*value_str);
- if (!value) {
- LOG_WARN("value_str cannot be parsed to std::vector<uint8_t>");
- }
- return value;
-}
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/config_cache_helper.h b/gd/storage/config_cache_helper.h
deleted file mode 100644
index 87e0dfd3f..000000000
--- a/gd/storage/config_cache_helper.h
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <cstdint>
-#include <limits>
-#include <optional>
-#include <type_traits>
-
-#include "common/numbers.h"
-#include "common/strings.h"
-#include "common/type_helper.h"
-#include "hci/enum_helper.h"
-#include "storage/config_cache.h"
-#include "storage/mutation_entry.h"
-#include "storage/serializable.h"
-
-namespace bluetooth {
-namespace storage {
-
-// A thin wrapper around ConfigCache and implement more type supports other than std::string
-//
-// - all SetX methods accept value as copy and std::move() in encouraged
-// - all GetX methods return std::optional<X> and std::nullopt if not exist. std::optional<> can be treated as bool
-class ConfigCacheHelper {
- public:
- static ConfigCacheHelper FromConfigCache(ConfigCache& config_cache) {
- return ConfigCacheHelper(config_cache);
- }
- explicit ConfigCacheHelper(ConfigCache& config_cache) : config_cache_(config_cache) {}
- virtual ~ConfigCacheHelper() = default;
- virtual void SetBool(const std::string& section, const std::string& property, bool value);
- virtual std::optional<bool> GetBool(const std::string& section, const std::string& property) const;
- virtual void SetUint64(const std::string& section, const std::string& property, uint64_t value);
- virtual std::optional<uint64_t> GetUint64(const std::string& section, const std::string& property) const;
- virtual void SetUint32(const std::string& section, const std::string& property, uint32_t value);
- virtual std::optional<uint32_t> GetUint32(const std::string& section, const std::string& property) const;
- virtual void SetInt64(const std::string& section, const std::string& property, int64_t value);
- virtual std::optional<int64_t> GetInt64(const std::string& section, const std::string& property) const;
- virtual void SetInt(const std::string& section, const std::string& property, int value);
- virtual std::optional<int> GetInt(const std::string& section, const std::string& property) const;
- virtual void SetBin(const std::string& section, const std::string& property, const std::vector<uint8_t>& value);
- virtual std::optional<std::vector<uint8_t>> GetBin(const std::string& section, const std::string& property) const;
-
- template <typename T, typename std::enable_if<std::is_signed_v<T> && std::is_integral_v<T>, int>::type = 0>
- std::optional<T> Get(const std::string& section, const std::string& property) {
- auto value = GetInt64(section, property);
- if (!value) {
- return std::nullopt;
- }
- if (!common::IsNumberInNumericLimits<T>(*value)) {
- return std::nullopt;
- }
- return static_cast<T>(*value);
- }
-
- template <typename T, typename std::enable_if<std::is_unsigned_v<T> && std::is_integral_v<T>, int>::type = 0>
- std::optional<T> Get(const std::string& section, const std::string& property) {
- auto value = GetUint64(section, property);
- if (!value) {
- return std::nullopt;
- }
- if (!common::IsNumberInNumericLimits<T>(*value)) {
- return std::nullopt;
- }
- return static_cast<T>(*value);
- }
-
- template <typename T, typename std::enable_if<std::is_same_v<T, std::string>, int>::type = 0>
- std::optional<T> Get(const std::string& section, const std::string& property) {
- return config_cache_.GetProperty(section, property);
- }
-
- template <typename T, typename std::enable_if<std::is_same_v<T, std::vector<uint8_t>>, int>::type = 0>
- std::optional<T> Get(const std::string& section, const std::string& property) {
- return GetBin(section, property);
- }
-
- template <typename T, typename std::enable_if<std::is_same_v<T, bool>, int>::type = 0>
- std::optional<T> Get(const std::string& section, const std::string& property) {
- return GetBool(section, property);
- }
-
- template <typename T, typename std::enable_if<std::is_base_of_v<Serializable<T>, T>, int>::type = 0>
- std::optional<T> Get(const std::string& section, const std::string& property) {
- auto value = config_cache_.GetProperty(section, property);
- if (!value) {
- return std::nullopt;
- }
- return T::FromLegacyConfigString(*value);
- }
-
- template <typename T, typename std::enable_if<std::is_enum_v<T>, int>::type = 0>
- std::optional<T> Get(const std::string& section, const std::string& property) {
- auto value = config_cache_.GetProperty(section, property);
- if (!value) {
- return std::nullopt;
- }
- return bluetooth::FromLegacyConfigString<T>(*value);
- }
-
- template <
- typename T,
- typename std::enable_if<
- bluetooth::common::is_specialization_of<T, std::vector>::value &&
- std::is_base_of_v<Serializable<typename T::value_type>, typename T::value_type>,
- int>::type = 0>
- std::optional<T> Get(const std::string& section, const std::string& property) {
- auto value = config_cache_.GetProperty(section, property);
- if (!value) {
- return std::nullopt;
- }
- auto values = common::StringSplit(*value, " ");
- T result;
- result.reserve(values.size());
- for (const auto& str : values) {
- auto v = T::value_type::FromLegacyConfigString(str);
- if (!v) {
- return std::nullopt;
- }
- result.push_back(*v);
- }
- return result;
- }
-
- private:
- ConfigCache& config_cache_;
-};
-
-} // namespace storage
-} // namespace bluetooth
diff --git a/gd/storage/config_cache_helper_test.cc b/gd/storage/config_cache_helper_test.cc
deleted file mode 100644
index 7269a4ae8..000000000
--- a/gd/storage/config_cache_helper_test.cc
+++ /dev/null
@@ -1,136 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/config_cache_helper.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include <limits>
-#include <vector>
-
-#include "storage/device.h"
-
-namespace testing {
-
-using bluetooth::storage::ConfigCache;
-using bluetooth::storage::ConfigCacheHelper;
-using bluetooth::storage::Device;
-
-TEST(ConfigCacheHelperTest, set_get_bool_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- // true
- ConfigCacheHelper(config).SetBool("A", "B", true);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("true")));
- ASSERT_THAT(ConfigCacheHelper(config).GetBool("A", "B"), Optional(IsTrue()));
- // false
- ConfigCacheHelper(config).SetBool("A", "B", false);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("false")));
- ASSERT_THAT(ConfigCacheHelper(config).GetBool("A", "B"), Optional(IsFalse()));
-}
-
-TEST(ConfigCacheHelperTest, set_get_uint64_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- // small
- ConfigCacheHelper(config).SetUint64("A", "B", 123);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("123")));
- ASSERT_THAT(ConfigCacheHelper(config).GetUint64("A", "B"), Optional(Eq(uint64_t(123))));
- // big
- uint64_t num = std::numeric_limits<int>::max();
- num = num * 10;
- ConfigCacheHelper(config).SetUint64("A", "B", num);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq(std::to_string(std::numeric_limits<int>::max()) + "0")));
- ASSERT_THAT(ConfigCacheHelper(config).GetUint64("A", "B"), Optional(Eq(num)));
- // zero
- ConfigCacheHelper(config).SetUint64("A", "B", 0);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("0")));
- ASSERT_THAT(ConfigCacheHelper(config).GetUint64("A", "B"), Optional(Eq(0)));
-}
-
-TEST(ConfigCacheHelperTest, set_get_uint32_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- // small
- ConfigCacheHelper(config).SetUint32("A", "B", 123);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("123")));
- ASSERT_THAT(ConfigCacheHelper(config).GetUint64("A", "B"), Optional(Eq(uint32_t(123))));
- // big
- uint64_t num = std::numeric_limits<uint32_t>::max();
- num *= 10;
- ConfigCacheHelper(config).SetUint64("A", "B", num);
- ASSERT_THAT(
- config.GetProperty("A", "B"), Optional(StrEq(std::to_string(std::numeric_limits<uint32_t>::max()) + "0")));
- ASSERT_FALSE(ConfigCacheHelper(config).GetUint32("A", "B"));
- // zero
- ConfigCacheHelper(config).SetUint32("A", "B", 0);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("0")));
- ASSERT_THAT(ConfigCacheHelper(config).GetUint32("A", "B"), Optional(Eq(0)));
-}
-
-TEST(ConfigCacheHelperTest, set_get_int64_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- // positive
- int64_t num = std::numeric_limits<int32_t>::max();
- num *= 10;
- ConfigCacheHelper(config).SetInt64("A", "B", num);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq(std::to_string(std::numeric_limits<int32_t>::max()) + "0")));
- ASSERT_THAT(ConfigCacheHelper(config).GetInt64("A", "B"), Optional(Eq(int64_t(num))));
- // negative
- ConfigCacheHelper(config).SetInt64("A", "B", -1 * num);
- ASSERT_THAT(
- config.GetProperty("A", "B"), Optional(StrEq("-" + std::to_string(std::numeric_limits<int32_t>::max()) + "0")));
- ASSERT_THAT(ConfigCacheHelper(config).GetInt64("A", "B"), Optional(Eq(-1 * num)));
- // zero
- ConfigCacheHelper(config).SetInt("A", "B", 0);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("0")));
- ASSERT_THAT(ConfigCacheHelper(config).GetInt64("A", "B"), Optional(Eq(int64_t(0))));
-}
-
-TEST(ConfigCacheHelperTest, set_get_int_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- // positive
- ConfigCacheHelper(config).SetInt("A", "B", 123);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("123")));
- ASSERT_THAT(ConfigCacheHelper(config).GetInt("A", "B"), Optional(Eq(int(123))));
- // negative
- ConfigCacheHelper(config).SetInt("A", "B", -123);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("-123")));
- ASSERT_THAT(ConfigCacheHelper(config).GetInt("A", "B"), Optional(Eq(int(-123))));
- // zero
- ConfigCacheHelper(config).SetInt("A", "B", 0);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("0")));
- ASSERT_THAT(ConfigCacheHelper(config).GetInt("A", "B"), Optional(Eq(int(0))));
- // big
- int64_t num = std::numeric_limits<int32_t>::max();
- num *= 10;
- ConfigCacheHelper(config).SetInt64("A", "B", num);
- ASSERT_FALSE(ConfigCacheHelper(config).GetInt("A", "B"));
-}
-
-TEST(ConfigCacheHelperTest, set_get_bin_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- // empty
- std::vector<uint8_t> data;
- ConfigCacheHelper(config).SetBin("A", "B", data);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("")));
- ASSERT_THAT(ConfigCacheHelper(config).GetBin("A", "B"), Optional(ContainerEq(data)));
- // non-empty
- std::vector<uint8_t> data2 = {0xAB, 0x5D, 0x42};
- ConfigCacheHelper(config).SetBin("A", "B", data2);
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("ab5d42")));
- ASSERT_THAT(ConfigCacheHelper(config).GetBin("A", "B"), Optional(ContainerEq(data2)));
-}
-
-} // namespace testing \ No newline at end of file
diff --git a/gd/storage/config_cache_test.cc b/gd/storage/config_cache_test.cc
deleted file mode 100644
index bec056f70..000000000
--- a/gd/storage/config_cache_test.cc
+++ /dev/null
@@ -1,340 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/config_cache.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include <cstdio>
-
-#include "hci/enum_helper.h"
-#include "storage/device.h"
-
-namespace testing {
-
-namespace {
-std::string GetTestAddress(int i) {
- std::string res = "00:00:00:00:00:00";
- res.reserve(res.size() + 1);
- std::snprintf(res.data(), res.capacity(), "AA:BB:CC:DD:EE:%02d", i);
- return res;
-}
-} // namespace
-
-using bluetooth::storage::ConfigCache;
-using bluetooth::storage::Device;
-using SectionAndPropertyValue = bluetooth::storage::ConfigCache::SectionAndPropertyValue;
-
-TEST(ConfigCacheTest, simple_set_get_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- auto value = config.GetProperty("A", "B");
- ASSERT_TRUE(value);
- ASSERT_EQ(*value, "C");
-}
-
-TEST(ConfigCacheTest, empty_values_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- ASSERT_DEATH({ config.SetProperty("", "B", "C"); }, "Empty section name not allowed");
- ASSERT_DEATH({ config.SetProperty("A", "", "C"); }, "Empty property name not allowed");
- // empty value is allowed
- config.SetProperty("A", "B", "");
- auto value = config.GetProperty("A", "B");
- ASSERT_TRUE(value);
- ASSERT_EQ(*value, "");
-}
-
-TEST(ConfigCacheTest, insert_boundary_device_with_linkkey_test) {
- ConfigCache config(2, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("CC:DD:EE:FF:00:10", "Name", "Hello");
- config.SetProperty("CC:DD:EE:FF:00:09", "Name", "Hello 2");
- config.SetProperty("CC:DD:EE:FF:00:11", "LinkKey", "AABBAABBCCDDEE");
- ASSERT_TRUE(config.GetProperty("CC:DD:EE:FF:00:10", "Name"));
-}
-
-TEST(ConfigCacheTest, comparison_test) {
- ConfigCache config_1(2, Device::kLinkKeyProperties);
- config_1.SetProperty("A", "B", "C");
- config_1.SetProperty("CC:DD:EE:FF:00:10", "Name", "Hello");
- config_1.SetProperty("CC:DD:EE:FF:00:09", "Name", "Hello 2");
- config_1.SetProperty("CC:DD:EE:FF:00:11", "LinkKey", "AABBAABBCCDDEE");
- ConfigCache config_2(2, Device::kLinkKeyProperties);
- config_2.SetProperty("A", "B", "C");
- config_2.SetProperty("CC:DD:EE:FF:00:10", "Name", "Hello");
- config_2.SetProperty("CC:DD:EE:FF:00:09", "Name", "Hello 2");
- config_2.SetProperty("CC:DD:EE:FF:00:11", "LinkKey", "AABBAABBCCDDEE");
- ASSERT_EQ(config_1, config_2);
- // Config with different temp device order should not be equal
- ASSERT_TRUE(config_2.GetProperty("CC:DD:EE:FF:00:10", "Name"));
- ASSERT_NE(config_1, config_2);
- ASSERT_TRUE(config_1.GetProperty("CC:DD:EE:FF:00:10", "Name"));
- ASSERT_EQ(config_1, config_2);
- // Config with different persistent device order should not be equal
- config_1.SetProperty("CC:DD:EE:FF:00:12", "LinkKey", "AABBAABBCCDDEE");
- config_2.RemoveSection("CC:DD:EE:FF:00:11");
- config_2.SetProperty("CC:DD:EE:FF:00:12", "LinkKey", "AABBAABBCCDDEE");
- config_2.SetProperty("CC:DD:EE:FF:00:11", "LinkKey", "AABBAABBCCDDEE");
- ASSERT_NE(config_1, config_2);
- // Config with different capacity should not be equal
- ConfigCache config_3(3, Device::kLinkKeyProperties);
- config_3.SetProperty("A", "B", "C");
- config_3.SetProperty("CC:DD:EE:FF:00:10", "Name", "Hello");
- config_3.SetProperty("CC:DD:EE:FF:00:09", "Name", "Hello 2");
- config_3.SetProperty("CC:DD:EE:FF:00:11", "LinkKey", "AABBAABBCCDDEE");
- config_3.SetProperty("CC:DD:EE:FF:00:12", "LinkKey", "AABBAABBCCDDEE");
- ASSERT_NE(config_1, config_3);
- // Empty config should not be equal to non-empty ones
- ConfigCache config_4(2, Device::kLinkKeyProperties);
- ASSERT_NE(config_1, config_4);
- // Empty configs should be equal
- ConfigCache config_5(2, Device::kLinkKeyProperties);
- ASSERT_EQ(config_4, config_5);
- // Empty configs with different capacity should not be equal
- ConfigCache config_6(3, Device::kLinkKeyProperties);
- ASSERT_NE(config_4, config_6);
-}
-
-TEST(ConfigCacheTest, empty_string_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "");
- auto value = config.GetProperty("A", "B");
- ASSERT_TRUE(value);
- ASSERT_EQ(*value, "");
-}
-
-TEST(ConfigCacheTest, mac_address_set_get_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- auto value = config.GetProperty("A", "B");
- ASSERT_TRUE(value);
- ASSERT_EQ(*value, "C");
- value = config.GetProperty("AA:BB:CC:DD:EE:FF", "B");
- ASSERT_TRUE(value);
- ASSERT_EQ(*value, "C");
- ASSERT_FALSE(config.GetProperty("A", "BC"));
- ASSERT_FALSE(config.GetProperty("ABC", "B"));
-}
-
-TEST(ConfigCacheTest, has_section_and_property_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "C", "D");
- ASSERT_TRUE(config.HasSection("A"));
- ASSERT_TRUE(config.HasSection("AA:BB:CC:DD:EE:FF"));
- ASSERT_TRUE(config.HasProperty("A", "B"));
- ASSERT_TRUE(config.HasProperty("AA:BB:CC:DD:EE:FF", "B"));
- config.SetProperty("AA:BB:CC:DD:EE:FF", "C", "D");
- auto value = config.GetProperty("AA:BB:CC:DD:EE:FF", "C");
- ASSERT_TRUE(value);
- ASSERT_EQ(*value, "D");
- value = config.GetProperty("AA:BB:CC:DD:EE:FF", "B");
- ASSERT_TRUE(value);
- ASSERT_EQ(*value, "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "E");
- value = config.GetProperty("AA:BB:CC:DD:EE:FF", "B");
- ASSERT_TRUE(value);
- ASSERT_THAT(value, Optional(StrEq("E")));
- ASSERT_FALSE(config.HasSection("Ab"));
- ASSERT_FALSE(config.HasSection("AA:11:CC:DD:EE:FF"));
- ASSERT_FALSE(config.HasProperty("A", "bB"));
- ASSERT_FALSE(config.HasProperty("AA:BB:11:DD:EE:FF", "B"));
-}
-
-TEST(ConfigCacheTest, remove_section_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "C", "D");
- ASSERT_TRUE(config.HasSection("A"));
- ASSERT_TRUE(config.HasSection("AA:BB:CC:DD:EE:FF"));
- ASSERT_TRUE(config.HasProperty("A", "B"));
- ASSERT_TRUE(config.HasProperty("AA:BB:CC:DD:EE:FF", "B"));
- ASSERT_TRUE(config.RemoveSection("AA:BB:CC:DD:EE:FF"));
- ASSERT_TRUE(config.RemoveSection("A"));
- ASSERT_FALSE(config.HasProperty("A", "B"));
- ASSERT_FALSE(config.HasProperty("AA:BB:CC:DD:EE:FF", "B"));
-}
-
-TEST(ConfigCacheTest, remove_property_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "C", "D");
- ASSERT_TRUE(config.HasSection("A"));
- ASSERT_TRUE(config.HasSection("AA:BB:CC:DD:EE:FF"));
- ASSERT_TRUE(config.HasProperty("A", "B"));
- ASSERT_TRUE(config.HasProperty("AA:BB:CC:DD:EE:FF", "B"));
- ASSERT_TRUE(config.HasProperty("AA:BB:CC:DD:EE:FF", "C"));
- ASSERT_TRUE(config.RemoveProperty("AA:BB:CC:DD:EE:FF", "B"));
- ASSERT_FALSE(config.HasProperty("AA:BB:CC:DD:EE:FF", "B"));
- ASSERT_FALSE(config.GetProperty("AA:BB:CC:DD:EE:FF", "B"));
-}
-
-TEST(ConfigCacheTest, remove_all_properties_from_section_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "C", "D");
- ASSERT_TRUE(config.HasSection("A"));
- ASSERT_TRUE(config.HasSection("AA:BB:CC:DD:EE:FF"));
- ASSERT_TRUE(config.HasProperty("A", "B"));
- ASSERT_TRUE(config.HasProperty("AA:BB:CC:DD:EE:FF", "B"));
- ASSERT_TRUE(config.HasProperty("AA:BB:CC:DD:EE:FF", "C"));
- ASSERT_TRUE(config.RemoveSection("AA:BB:CC:DD:EE:FF"));
- ASSERT_FALSE(config.HasSection("AA:BB:CC:DD:EE:FF"));
- ASSERT_FALSE(config.HasProperty("AA:BB:CC:DD:EE:FF", "B"));
- ASSERT_FALSE(config.GetProperty("AA:BB:CC:DD:EE:FF", "C"));
-}
-
-TEST(ConfigCacheTest, get_persistent_devices_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "C", "D");
- config.SetProperty("CC:DD:EE:FF:00:11", "LinkKey", "AABBAABBCCDDEE");
- ASSERT_TRUE(config.HasProperty("CC:DD:EE:FF:00:11", "LinkKey"));
- ASSERT_THAT(config.GetPersistentSections(), ElementsAre("CC:DD:EE:FF:00:11"));
- config.SetProperty("AA:BB:CC:DD:EE:FF", "LinkKey", "DEERDEERDEER");
- ASSERT_THAT(config.GetPersistentSections(), ElementsAre("CC:DD:EE:FF:00:11", "AA:BB:CC:DD:EE:FF"));
- ASSERT_TRUE(config.RemoveProperty("CC:DD:EE:FF:00:11", "LinkKey"));
- ASSERT_THAT(config.GetPersistentSections(), ElementsAre("AA:BB:CC:DD:EE:FF"));
-}
-
-TEST(ConfigCacheTest, appoaching_temporary_config_limit_test) {
- ConfigCache config(2, Device::kLinkKeyProperties);
- for (int i = 0; i < 10; ++i) {
- config.SetProperty(GetTestAddress(i), "Name", "Hello" + std::to_string(i));
- if (i % 2 == 0) {
- config.SetProperty(GetTestAddress(i), "LinkKey", "Key" + std::to_string(i));
- }
- }
- for (int i = 0; i < 10; ++i) {
- if (i % 2 == 0) {
- ASSERT_TRUE(config.HasSection(GetTestAddress(i)));
- ASSERT_TRUE(config.HasProperty(GetTestAddress(i), "LinkKey"));
- ASSERT_THAT(config.GetProperty(GetTestAddress(i), "Name"), Optional(StrEq("Hello" + std::to_string(i))));
- } else if (i >= 7) {
- ASSERT_TRUE(config.HasSection(GetTestAddress(i)));
- ASSERT_THAT(config.GetProperty(GetTestAddress(i), "Name"), Optional(StrEq("Hello" + std::to_string(i))));
- } else {
- ASSERT_FALSE(config.HasSection(GetTestAddress(i)));
- }
- }
- ASSERT_THAT(
- config.GetPersistentSections(),
- ElementsAre(GetTestAddress(0), GetTestAddress(2), GetTestAddress(4), GetTestAddress(6), GetTestAddress(8)));
-}
-
-TEST(ConfigCacheTest, remove_section_with_property_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "C", "D");
- config.SetProperty("CC:DD:EE:FF:00:11", "B", "AABBAABBCCDDEE");
- config.SetProperty("CC:DD:EE:FF:00:11", "LinkKey", "AABBAABBCCDDEE");
- config.RemoveSectionWithProperty("B");
- ASSERT_FALSE(config.HasSection("A"));
- ASSERT_FALSE(config.HasSection("AA:BB:CC:DD:EE:FF"));
- ASSERT_FALSE(config.HasSection("CC:DD:EE:FF:00:11"));
-}
-
-TEST(ConfigCacheTest, persistent_config_changed_callback_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- int num_change = 0;
- config.SetPersistentConfigChangedCallback([&num_change] { num_change++; });
- config.SetProperty("A", "B", "C");
- ASSERT_EQ(num_change, 1);
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- ASSERT_EQ(num_change, 1);
- config.SetProperty("AA:BB:CC:DD:EE:FF", "C", "D");
- ASSERT_EQ(num_change, 1);
- config.SetProperty("CC:DD:EE:FF:00:11", "B", "AABBAABBCCDDEE");
- ASSERT_EQ(num_change, 1);
- config.SetProperty("CC:DD:EE:FF:00:11", "LinkKey", "AABBAABBCCDDEE");
- ASSERT_EQ(num_change, 2);
- config.RemoveProperty("CC:DD:EE:FF:00:11", "LinkKey");
- ASSERT_EQ(num_change, 3);
- config.RemoveSectionWithProperty("B");
- ASSERT_EQ(num_change, 4);
-}
-
-TEST(ConfigCacheTest, fix_device_type_inconsistency_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "C", "D");
- ASSERT_TRUE(config.FixDeviceTypeInconsistencies());
- ASSERT_THAT(
- config.GetProperty("AA:BB:CC:DD:EE:FF", "DevType"),
- Optional(StrEq(std::to_string(bluetooth::hci::DeviceType::BR_EDR))));
- config.SetProperty("CC:DD:EE:FF:00:11", "B", "AABBAABBCCDDEE");
- config.SetProperty("CC:DD:EE:FF:00:11", "DevType", std::to_string(bluetooth::hci::DeviceType::BR_EDR));
- config.SetProperty("CC:DD:EE:FF:00:11", "LinkKey", "AABBAABBCCDDEE");
- ASSERT_FALSE(config.FixDeviceTypeInconsistencies());
- ASSERT_THAT(
- config.GetProperty("CC:DD:EE:FF:00:11", "DevType"),
- Optional(StrEq(std::to_string(bluetooth::hci::DeviceType::BR_EDR))));
- config.SetProperty("CC:DD:EE:FF:00:11", "LE_KEY_PENC", "AABBAABBCCDDEE");
- ASSERT_TRUE(config.FixDeviceTypeInconsistencies());
- ASSERT_THAT(
- config.GetProperty("CC:DD:EE:FF:00:11", "DevType"),
- Optional(StrEq(std::to_string(bluetooth::hci::DeviceType::DUAL))));
- config.RemoveProperty("CC:DD:EE:FF:00:11", "LinkKey");
- ASSERT_TRUE(config.FixDeviceTypeInconsistencies());
- ASSERT_THAT(
- config.GetProperty("CC:DD:EE:FF:00:11", "DevType"),
- Optional(StrEq(std::to_string(bluetooth::hci::DeviceType::LE))));
-}
-
-TEST(ConfigCacheTest, test_get_section_with_property) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:EF", "C", "D");
- ASSERT_THAT(
- config.GetSectionNamesWithProperty("B"),
- ElementsAre(
- SectionAndPropertyValue{.section = "A", .property = "C"},
- SectionAndPropertyValue{.section = "AA:BB:CC:DD:EE:FF", .property = "C"}));
-}
-
-TEST(ConfigCacheTest, test_get_sections_matching_at_least_one_property) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:EF", "C", "D");
- ASSERT_TRUE(config.HasAtLeastOneMatchingPropertiesInSection("AA:BB:CC:DD:EE:FF", {"B", "C", "D"}));
- ASSERT_TRUE(config.HasAtLeastOneMatchingPropertiesInSection("A", {"B", "C", "D"}));
- ASSERT_FALSE(config.HasAtLeastOneMatchingPropertiesInSection("AA:BB:CC:DD:EE:FF", {"BC", "D"}));
-}
-
-TEST(ConfigCacheTest, test_empty_persistent_properties) {
- ConfigCache config(100, {});
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:EF", "C", "D");
- config.SetProperty("AA:BB:CC:DD:EE:EF", "LinkKey", "D");
- ASSERT_TRUE(config.HasAtLeastOneMatchingPropertiesInSection("AA:BB:CC:DD:EE:FF", {"B", "C", "D"}));
- ASSERT_TRUE(config.HasAtLeastOneMatchingPropertiesInSection("A", {"B", "C", "D"}));
- ASSERT_FALSE(config.HasAtLeastOneMatchingPropertiesInSection("AA:BB:CC:DD:EE:FF", {"BC", "D"}));
- ASSERT_THAT(config.GetPersistentSections(), ElementsAre());
-}
-
-} // namespace testing \ No newline at end of file
diff --git a/gd/storage/device.cc b/gd/storage/device.cc
deleted file mode 100644
index 7afb30f36..000000000
--- a/gd/storage/device.cc
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/device.h"
-
-#include <algorithm>
-#include <limits>
-
-#include "os/log.h"
-#include "storage/classic_device.h"
-#include "storage/config_cache_helper.h"
-#include "storage/le_device.h"
-
-namespace bluetooth {
-namespace storage {
-
-using hci::DeviceType;
-
-namespace {
-// TODO(siyuanh): also defined in storage/le_device.cc
-const std::string kLeIdentityAddressKey = "LeIdentityAddr";
-const std::string kLeLegacyPseudoAddr = "LeLegacyPseudoAddr";
-
-std::string GetConfigSection(
- ConfigCache* config, const hci::Address& key_address, Device::ConfigKeyAddressType key_address_type) {
- ASSERT_LOG(config != nullptr, "config cannot be null");
- ASSERT_LOG(!key_address.IsEmpty(), "key_address cannot be empty");
- // assume lower case
- auto key_address_string = key_address.ToString();
- switch (key_address_type) {
- case Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS:
- case Device::ConfigKeyAddressType::CLASSIC_ADDRESS:
- return key_address_string;
- case Device::ConfigKeyAddressType::LE_IDENTITY_ADDRESS:
- for (const auto& section_and_property : config->GetSectionNamesWithProperty(kLeIdentityAddressKey)) {
- if (section_and_property.property == key_address_string) {
- return section_and_property.section;
- }
- }
- return key_address_string;
- case Device::ConfigKeyAddressType::LE_LEGACY_PSEUDO_ADDRESS:
- for (const auto& section_and_property : config->GetSectionNamesWithProperty(kLeLegacyPseudoAddr)) {
- if (section_and_property.property == key_address_string) {
- return section_and_property.section;
- }
- }
- // One cannot create a new device just using LE legacy pseudo address
- [[fallthrough]];
- default:
- LOG_ALWAYS_FATAL("Unknown key_address_type %d", static_cast<int>(key_address_type));
- return "";
- }
-}
-
-} // namespace
-
-const std::unordered_set<std::string_view> Device::kLinkKeyProperties = {
- "LinkKey", "LE_KEY_PENC", "LE_KEY_PID", "LE_KEY_PCSRK", "LE_KEY_LENC", "LE_KEY_LCSRK"};
-
-Device::Device(
- ConfigCache* config,
- ConfigCache* memory_only_config,
- const hci::Address& key_address,
- ConfigKeyAddressType key_address_type)
- : Device(config, memory_only_config, GetConfigSection(config, key_address, key_address_type)) {}
-
-Device::Device(ConfigCache* config, ConfigCache* memory_only_config, std::string section)
- : config_(config), memory_only_config_(memory_only_config), section_(std::move(section)) {}
-
-bool Device::Exists() {
- return config_->HasSection(section_);
-}
-
-MutationEntry Device::RemoveFromConfig() {
- return MutationEntry::Remove(MutationEntry::PropertyType::NORMAL, section_);
-}
-
-MutationEntry Device::RemoveFromTempConfig() {
- return MutationEntry::Remove(MutationEntry::PropertyType::MEMORY_ONLY, section_);
-}
-
-LeDevice Device::Le() {
- auto device_type = GetDeviceType();
- ASSERT(device_type);
- ASSERT(device_type == DeviceType::LE || device_type == DeviceType::DUAL);
- return LeDevice(config_, memory_only_config_, section_);
-}
-
-ClassicDevice Device::Classic() {
- auto device_type = GetDeviceType();
- ASSERT(device_type);
- ASSERT(device_type == DeviceType::BR_EDR || device_type == DeviceType::DUAL);
- return ClassicDevice(config_, memory_only_config_, section_);
-}
-
-hci::Address Device::GetAddress() const {
- // section name of a device is its address
- auto addr = hci::Address::FromString(section_);
- ASSERT(addr.has_value());
- return addr.value();
-}
-
-std::string Device::ToLogString() const {
- return section_;
-}
-
-} // namespace storage
-} // namespace bluetooth
diff --git a/gd/storage/device.h b/gd/storage/device.h
deleted file mode 100644
index e610f57e2..000000000
--- a/gd/storage/device.h
+++ /dev/null
@@ -1,215 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <functional>
-#include <limits>
-#include <optional>
-#include <string>
-#include <type_traits>
-#include <unordered_set>
-#include <utility>
-
-#include "hci/address.h"
-#include "hci/address_with_type.h"
-#include "hci/class_of_device.h"
-#include "hci/enum_helper.h"
-#include "storage/config_cache.h"
-#include "storage/config_cache_helper.h"
-#include "storage/mutation_entry.h"
-#include "storage/serializable.h"
-
-namespace bluetooth {
-namespace storage {
-
-class LeDevice;
-class ClassicDevice;
-
-// Make sure our macro is used
-#ifdef GENERATE_PROPERTY_GETTER_SETTER_REMOVER
-static_assert(false, "GENERATE_PROPERTY_GETTER_SETTER_REMOVER() must be uniquely defined once in this file");
-#endif
-
-#define GENERATE_PROPERTY_GETTER_SETTER_REMOVER(NAME, RETURN_TYPE, PROPERTY_KEY) \
- public: \
- std::optional<RETURN_TYPE> Get##NAME() const { \
- return ConfigCacheHelper(*config_).Get<RETURN_TYPE>(section_, PROPERTY_KEY); \
- } \
- MutationEntry Set##NAME(const RETURN_TYPE& value) { \
- return MutationEntry::Set<RETURN_TYPE>(MutationEntry::PropertyType::NORMAL, section_, PROPERTY_KEY, value); \
- } \
- MutationEntry Remove##NAME() { \
- return MutationEntry::Remove(MutationEntry::PropertyType::NORMAL, section_, PROPERTY_KEY); \
- }
-
-// Make sure our macro is used
-#ifdef GENERATE_PROPERTY_GETTER_SETTER_REMOVER_WITH_CUSTOM_SETTER
-static_assert(
- false, "GENERATE_PROPERTY_GETTER_SETTER_REMOVER_WITH_CUSTOM_SETTER() must be uniquely defined once in this file");
-#endif
-
-// FUNC is bracketed function definition that takes a const RETURN_TYPE& value and return RETURN_TYPE
-// e.g. { return value + 1; }
-#define GENERATE_PROPERTY_GETTER_SETTER_REMOVER_WITH_CUSTOM_SETTER(NAME, RETURN_TYPE, PROPERTY_KEY, FUNC) \
- public: \
- std::optional<RETURN_TYPE> Get##NAME() const { \
- return ConfigCacheHelper(*config_).Get<RETURN_TYPE>(section_, PROPERTY_KEY); \
- } \
- MutationEntry Set##NAME(const RETURN_TYPE& value) { \
- auto new_value = [this](const RETURN_TYPE& value) -> RETURN_TYPE FUNC(value); \
- return MutationEntry::Set<RETURN_TYPE>(MutationEntry::PropertyType::NORMAL, section_, PROPERTY_KEY, new_value); \
- } \
- MutationEntry Remove##NAME() { \
- return MutationEntry::Remove(MutationEntry::PropertyType::NORMAL, section_, PROPERTY_KEY); \
- }
-
-// Make sure our macro is used
-#ifdef GENERATE_TEMP_PROPERTY_GETTER_SETTER_REMOVER
-static_assert(false, "GENERATE_TEMP_PROPERTY_GETTER_SETTER_REMOVER() must be uniquely defined once in this file");
-#endif
-
-// Macro to generate tempoarary property that exists in memory only
-// It is subjected to a limit of 10,000 devices
-// It will be cleared when the stack is restarted
-#define GENERATE_TEMP_PROPERTY_GETTER_SETTER_REMOVER(NAME, RETURN_TYPE, PROPERTY_KEY) \
- public: \
- std::optional<RETURN_TYPE> GetTemp##NAME() const { \
- return ConfigCacheHelper(*memory_only_config_).Get<RETURN_TYPE>(section_, PROPERTY_KEY); \
- } \
- MutationEntry SetTemp##NAME(const RETURN_TYPE& value) { \
- return MutationEntry::Set<RETURN_TYPE>(MutationEntry::PropertyType::MEMORY_ONLY, section_, PROPERTY_KEY, value); \
- } \
- MutationEntry RemoveTemp##NAME() { \
- return MutationEntry::Remove(MutationEntry::PropertyType::MEMORY_ONLY, section_, PROPERTY_KEY); \
- }
-
-// A think wrapper of device in ConfigCache, allowing easy access to various predefined properties of a Bluetooth device
-//
-// Device, LeDevice, and Classic device objects are fully copyable, comparable hashable
-//
-// A newly created device does not have any DeviceType information and user can only read or write the values in this
-// common Device abstraction layer.
-//
-// As soon as a user determines the type of device, they should call SetDeviceType() to assign device to a type
-// After that, Classic() or Le() will return interfaces that allows access to deeper layer properties
-class Device {
- public:
- enum ConfigKeyAddressType { LEGACY_KEY_ADDRESS, CLASSIC_ADDRESS, LE_IDENTITY_ADDRESS, LE_LEGACY_PSEUDO_ADDRESS };
-
- Device(
- ConfigCache* config,
- ConfigCache* memory_only_config,
- const hci::Address& key_address,
- ConfigKeyAddressType key_address_type);
- Device(ConfigCache* config, ConfigCache* memory_only_config, std::string section);
-
- // for move
- Device(Device&& other) noexcept = default;
- Device& operator=(Device&& other) noexcept = default;
-
- // for copy
- Device(const Device& other) noexcept = default;
- Device& operator=(const Device& other) noexcept = default;
-
- // operators
- bool operator==(const Device& other) const {
- return config_ == other.config_ && memory_only_config_ == other.memory_only_config_ && section_ == other.section_;
- }
- bool operator!=(const Device& other) const {
- return !(*this == other);
- }
- bool operator<(const Device& other) const {
- return config_ < other.config_ && memory_only_config_ < other.memory_only_config_ && section_ < other.section_;
- }
- bool operator>(const Device& rhs) const {
- return (rhs < *this);
- }
- bool operator<=(const Device& rhs) const {
- return !(*this > rhs);
- }
- bool operator>=(const Device& rhs) const {
- return !(*this < rhs);
- }
-
- // A newly created Device object may not be backed by any properties in the ConfigCache, where Exists() will return
- // false. As soon as a property value is added to the device. Exists() will become true.
- bool Exists();
-
- // Remove device and all its properties from config and memory-only temp config
- MutationEntry RemoveFromConfig();
- // Remove device and all its properties from memory-only temp config, but keep items in normal config
- MutationEntry RemoveFromTempConfig();
-
- // Only works when GetDeviceType() returns BR_EDR or DUAL, will crash otherwise
- // For first time use, please SetDeviceType() to the right value
- ClassicDevice Classic();
-
- // Only works when GetDeviceType() returns LE or DUAL, will crash otherwise
- // For first time use, please SetDeviceType() to the right value
- LeDevice Le();
-
- // For logging purpose only, you can't get a Device object from parsing a std::string
- std::string ToLogString() const;
-
- hci::Address GetAddress() const;
-
- // Property names that correspond to a link key used in Bluetooth Classic and LE device
- static const std::unordered_set<std::string_view> kLinkKeyProperties;
-
- private:
- ConfigCache* config_;
- ConfigCache* memory_only_config_;
- std::string section_;
- friend std::hash<Device>;
-
- public:
- // Macro generate getters, setters and removers
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(Name, std::string, "Name");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(ClassOfDevice, hci::ClassOfDevice, "DevClass");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER_WITH_CUSTOM_SETTER(DeviceType, hci::DeviceType, "DevType", {
- return static_cast<hci::DeviceType>(value | GetDeviceType().value_or(hci::DeviceType::UNKNOWN));
- });
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(ManufacturerCode, uint16_t, "Manufacturer");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(LmpVersion, uint8_t, "LmpVer");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(LmpSubVersion, uint16_t, "LmpSubVer");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(SdpDiManufacturer, uint16_t, "SdpDiManufacturer");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(SdpDiModel, uint16_t, "SdpDiModel");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(SdpDiHardwareVersion, uint16_t, "SdpDiHardwareVersion");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(SdpDiVendorIdSource, uint16_t, "SdpDiVendorIdSource");
-
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(MetricsId, int, "MetricsId");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(PinLength, int, "PinLength");
- // unix timestamp in seconds from epoch
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(CreationUnixTimestamp, int, "DevClass");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(IsAuthenticated, int, "IsAuthenticated");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(RequiresMitmProtection, int, "RequiresMitmProtection");
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(IsEncryptionRequired, int, "IsEncryptionRequired");
-};
-
-} // namespace storage
-} // namespace bluetooth
-
-namespace std {
-template <>
-struct hash<bluetooth::storage::Device> {
- std::size_t operator()(const bluetooth::storage::Device& val) const noexcept {
- std::size_t pointer_hash_1 = std::hash<bluetooth::storage::ConfigCache*>{}(val.config_);
- std::size_t pointer_hash_2 = std::hash<bluetooth::storage::ConfigCache*>{}(val.config_);
- std::size_t addr_hash = std::hash<std::string>{}(val.section_);
- return addr_hash ^ (pointer_hash_1 << 1) ^ (pointer_hash_2 << 2);
- }
-};
-} // namespace std \ No newline at end of file
diff --git a/gd/storage/device_test.cc b/gd/storage/device_test.cc
deleted file mode 100644
index 0706403ad..000000000
--- a/gd/storage/device_test.cc
+++ /dev/null
@@ -1,239 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/device.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "storage/classic_device.h"
-#include "storage/device.h"
-#include "storage/le_device.h"
-#include "storage/mutation.h"
-
-using bluetooth::hci::Address;
-using bluetooth::hci::DeviceType;
-using bluetooth::storage::ConfigCache;
-using bluetooth::storage::Device;
-using bluetooth::storage::Mutation;
-using ::testing::Eq;
-using ::testing::MatchesRegex;
-using ::testing::Optional;
-using ::testing::StrEq;
-
-TEST(DeviceTest, create_new_device_using_legacy_key_address) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
-
- // A new device
- Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- Device device(&config, &memory_only_config, address, Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
- ASSERT_FALSE(device.Exists());
- ASSERT_FALSE(device.GetClassOfDevice());
-
- // An existing device
- Address address2 = {{0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff}};
- config.SetProperty(address2.ToString(), "Name", "hello");
- Device device2(&config, &memory_only_config, address2, Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
- ASSERT_TRUE(device2.Exists());
- ASSERT_THAT(device2.GetName(), Optional(StrEq("hello")));
-
- // devices with the same key address and config pointer are the same
- Address address3 = {{0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff}};
- Device device3(&config, &memory_only_config, address3, Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
- ASSERT_EQ(device2, device3);
- ASSERT_TRUE(device3.Exists());
- ASSERT_THAT(device3.GetName(), Optional(StrEq("hello")));
-}
-
-TEST(DeviceTest, create_new_device_using_classic_address) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
-
- // A new device
- Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- Device device(&config, &memory_only_config, address, Device::ConfigKeyAddressType::CLASSIC_ADDRESS);
- ASSERT_FALSE(device.Exists());
- ASSERT_FALSE(device.GetClassOfDevice());
-
- // An existing device
- Address address2 = {{0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff}};
- config.SetProperty(address2.ToString(), "Name", "hello");
- Device device2(&config, &memory_only_config, address2, Device::ConfigKeyAddressType::CLASSIC_ADDRESS);
- ASSERT_TRUE(device2.Exists());
- ASSERT_THAT(device2.GetName(), Optional(StrEq("hello")));
-
- // devices with the same key address and config pointer are the same
- Address address3 = {{0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff}};
- Device device3(&config, &memory_only_config, address3, Device::ConfigKeyAddressType::CLASSIC_ADDRESS);
- ASSERT_EQ(device2, device3);
- ASSERT_TRUE(device3.Exists());
- ASSERT_THAT(device3.GetName(), Optional(StrEq("hello")));
-}
-
-TEST(DeviceTest, create_new_device_using_le_identity_address) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
-
- // A new device
- Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- Device device(&config, &memory_only_config, address, Device::ConfigKeyAddressType::LE_IDENTITY_ADDRESS);
- ASSERT_FALSE(device.Exists());
- ASSERT_FALSE(device.GetClassOfDevice());
-
- // An existing device
- Address pseudo_first_seen_address = {{0xab, 0xcd, 0xef, 0x12, 0x34, 0x56}};
- Address le_identity_address = {{0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff}};
- // first seen address used as key
- config.SetProperty(pseudo_first_seen_address.ToString(), "Name", "hello");
- config.SetProperty(pseudo_first_seen_address.ToString(), "LeIdentityAddr", le_identity_address.ToString());
- config.SetProperty(address.ToString(), "Name", "world");
- Device device2(&config, &memory_only_config, le_identity_address, Device::ConfigKeyAddressType::LE_IDENTITY_ADDRESS);
- ASSERT_TRUE(device2.Exists());
- ASSERT_THAT(device2.GetName(), Optional(StrEq("hello")));
-}
-
-TEST(DeviceTest, set_property) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- Device device(&config, &memory_only_config, address, Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
- ASSERT_FALSE(device.Exists());
- ASSERT_FALSE(device.GetName());
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(device.SetName("hello world!"));
- mutation.Commit();
- ASSERT_TRUE(device.Exists());
- ASSERT_THAT(device.GetName(), Optional(StrEq("hello world!")));
-}
-
-TEST(DeviceTest, set_device_type) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- Device device(&config, &memory_only_config, address, Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
- ASSERT_FALSE(device.Exists());
- ASSERT_FALSE(device.GetName());
- {
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(device.SetDeviceType(DeviceType::BR_EDR));
- mutation.Commit();
- }
- ASSERT_THAT(device.GetDeviceType(), Optional(Eq(DeviceType::BR_EDR)));
- {
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(device.SetDeviceType(DeviceType::LE));
- mutation.Commit();
- }
- ASSERT_THAT(device.GetDeviceType(), Optional(Eq(DeviceType::DUAL)));
-}
-
-TEST(DeviceTest, get_le_and_bredr) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- Device device(&config, &memory_only_config, address, Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
- ASSERT_FALSE(device.GetDeviceType());
- ASSERT_DEATH({ device.Le(); }, MatchesRegex(".*"));
- ASSERT_DEATH({ device.Classic(); }, MatchesRegex(".*"));
-
- // classic
- {
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(device.SetDeviceType(DeviceType::BR_EDR));
- mutation.Commit();
- }
- ASSERT_THAT(device.GetDeviceType(), Optional(Eq(DeviceType::BR_EDR)));
- auto classic_device = device.Classic();
- ASSERT_THAT(classic_device.Parent(), Eq(device));
-
- // le
- {
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(device.RemoveDeviceType());
- mutation.Commit();
- }
- ASSERT_FALSE(device.GetDeviceType());
- {
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(device.SetDeviceType(DeviceType::LE));
- mutation.Commit();
- }
- ASSERT_THAT(device.GetDeviceType(), Optional(Eq(DeviceType::LE)));
- auto le_device = device.Le();
- ASSERT_THAT(le_device.Parent(), Eq(device));
-
- // dual
- {
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(device.RemoveDeviceType());
- mutation.Commit();
- }
- ASSERT_FALSE(device.GetDeviceType());
- {
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(device.SetDeviceType(DeviceType::DUAL));
- mutation.Commit();
- }
- ASSERT_THAT(device.GetDeviceType(), Optional(Eq(DeviceType::DUAL)));
- classic_device = device.Classic();
- ASSERT_THAT(classic_device.Parent(), Eq(device));
- le_device = device.Le();
- ASSERT_THAT(le_device.Parent(), Eq(device));
-}
-
-TEST(DeviceTest, equality_test) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- Device device1(&config, &memory_only_config, address, Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
- Device device2(&config, &memory_only_config, address, Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
- ASSERT_EQ(device1, device2);
-
- // different config cache
- ConfigCache config_alt(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config_alt(10, {});
- Device device3(&config_alt, &memory_only_config_alt, address, Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
- ASSERT_NE(device1, device3);
-
- // different address
- Address address_alt = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x07}};
- Device device4(&config, &memory_only_config, address_alt, Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
- ASSERT_NE(device1, device4);
-
- Device device5 = std::move(device2);
- ASSERT_EQ(device1, device5);
-
- config.SetProperty(address.ToString(), "Name", "hello");
- ASSERT_THAT(device5.GetName(), Optional(StrEq("hello")));
- ASSERT_THAT(device1.GetName(), Optional(StrEq("hello")));
-}
-
-TEST(DeviceTest, remove_config_test) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- Address address = {{0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff}};
- config.SetProperty(address.ToString(), "Name", "hello");
- Device device(&config, &memory_only_config, address, Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
- ASSERT_TRUE(device.Exists());
- ASSERT_THAT(device.GetName(), Optional(StrEq("hello")));
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(device.RemoveFromConfig());
- mutation.Commit();
- ASSERT_FALSE(device.Exists());
- ASSERT_FALSE(config.GetProperty(address.ToString(), "Name"));
-}
-
diff --git a/gd/storage/le_device.cc b/gd/storage/le_device.cc
deleted file mode 100644
index d26a50344..000000000
--- a/gd/storage/le_device.cc
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/le_device.h"
-
-namespace bluetooth {
-namespace storage {
-
-namespace {
-const std::string kLeIdentityAddressKey = "LeIdentityAddr";
-// TODO(siyuanh): check if we still need these keys in GD
-// const std::string kLePencKey = "LE_KEY_PENC";
-// const std::string kLePidKey = "LE_KEY_PENC";
-// const std::string kLePsrkKey = "LE_KEY_PENC";
-// const std::string kLeLencKey = "LE_KEY_PENC";
-// const std::string kLeLcsrkKey = "LE_KEY_PENC";
-// const std::string kLeLidKey = "LE_KEY_PENC";
-} // namespace
-
-const std::unordered_set<std::string_view> LeDevice::kLinkKeyProperties = {
- "LE_KEY_PENC", "LE_KEY_PID", "LE_KEY_PCSRK", "LE_KEY_LENC", "LE_KEY_LCSRK"};
-
-LeDevice::LeDevice(ConfigCache* config, ConfigCache* memory_only_config, std::string section)
- : config_(config), memory_only_config_(memory_only_config), section_(std::move(section)) {}
-
-Device LeDevice::Parent() {
- return Device(config_, memory_only_config_, section_);
-}
-
-std::string LeDevice::ToLogString() const {
- return section_;
-}
-
-bool LeDevice::IsPaired() const {
- // This first check is here only to speed up the checking process
- if (!config_->IsPersistentSection(section_)) {
- return false;
- }
- return config_->HasAtLeastOneMatchingPropertiesInSection(section_, kLinkKeyProperties);
-}
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/le_device.h b/gd/storage/le_device.h
deleted file mode 100644
index 79e3045c5..000000000
--- a/gd/storage/le_device.h
+++ /dev/null
@@ -1,107 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <optional>
-#include <string>
-#include <unordered_set>
-
-#include "crypto_toolbox/crypto_toolbox.h"
-#include "hci/hci_packets.h"
-#include "storage/config_cache.h"
-#include "storage/config_cache_helper.h"
-#include "storage/device.h"
-
-namespace bluetooth {
-namespace storage {
-
-class LeDevice {
- public:
- LeDevice(ConfigCache* config, ConfigCache* memory_only_config, std::string section);
-
- // for move
- LeDevice(LeDevice&& other) noexcept = default;
- LeDevice& operator=(LeDevice&& other) noexcept = default;
-
- // for copy
- LeDevice(const LeDevice& other) noexcept = default;
- LeDevice& operator=(const LeDevice& other) noexcept = default;
-
- // operators
- bool operator==(const LeDevice& other) const {
- return config_ == other.config_ && memory_only_config_ == other.memory_only_config_ && section_ == other.section_;
- }
- bool operator!=(const LeDevice& other) const {
- return !(*this == other);
- }
- bool operator<(const LeDevice& other) const {
- return config_ < other.config_ && memory_only_config_ < other.memory_only_config_ && section_ < other.section_;
- }
- bool operator>(const LeDevice& rhs) const {
- return (rhs < *this);
- }
- bool operator<=(const LeDevice& rhs) const {
- return !(*this > rhs);
- }
- bool operator>=(const LeDevice& rhs) const {
- return !(*this < rhs);
- }
-
- // Get the parent device
- Device Parent();
-
- // For logging purpose only, you can't get a LeDevice object from parsing a std::string
- std::string ToLogString() const;
-
- // Return true if device has a link key in one of |kLinkKeyProperties|
- bool IsPaired() const;
-
- // Property names that correspond to a link key used in Bluetooth LE device
- static const std::unordered_set<std::string_view> kLinkKeyProperties;
-
- private:
- ConfigCache* config_;
- ConfigCache* memory_only_config_;
- std::string section_;
- friend std::hash<LeDevice>;
-
- public:
- // Get LE address type of the key address
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(AddressType, hci::AddressType, "AddrType");
- // IRK + Identity Address Type + Identity Address
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(PeerId, std::string, "LE_KEY_PID");
- // LTK + RAND + EDIV + Security Level + Key Length
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(PeerEncryptionKeys, std::string, "LE_KEY_PENC");
- // counter + CSRK (connection signature resolving key) + security level
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(PeerSignatureResolvingKeys, std::string, "LE_KEY_PCSRK");
-
- GENERATE_PROPERTY_GETTER_SETTER_REMOVER(LegacyPseudoAddress, hci::Address, "LeLegacyPseudoAddr");
-};
-
-} // namespace storage
-} // namespace bluetooth
-
-namespace std {
-template <>
-struct hash<bluetooth::storage::LeDevice> {
- std::size_t operator()(const bluetooth::storage::LeDevice& val) const noexcept {
- std::size_t pointer_hash_1 = std::hash<bluetooth::storage::ConfigCache*>{}(val.config_);
- std::size_t pointer_hash_2 = std::hash<bluetooth::storage::ConfigCache*>{}(val.config_);
- std::size_t addr_hash = std::hash<std::string>{}(val.section_);
- return addr_hash ^ (pointer_hash_1 << 1) ^ (pointer_hash_2 << 2);
- }
-};
-} // namespace std \ No newline at end of file
diff --git a/gd/storage/le_device_test.cc b/gd/storage/le_device_test.cc
deleted file mode 100644
index 407f489ec..000000000
--- a/gd/storage/le_device_test.cc
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/device.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "storage/classic_device.h"
-#include "storage/le_device.h"
-#include "storage/mutation.h"
-
-using bluetooth::hci::Address;
-using bluetooth::hci::AddressType;
-using bluetooth::hci::DeviceType;
-using bluetooth::storage::ConfigCache;
-using bluetooth::storage::Device;
-using bluetooth::storage::LeDevice;
-using bluetooth::storage::Mutation;
-using ::testing::Eq;
-using ::testing::Optional;
-
-TEST(LeDeviceTest, create_new_le_device) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- bluetooth::hci::Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- LeDevice device(&config, &memory_only_config, address.ToString());
- ASSERT_FALSE(device.GetAddressType());
-}
-
-TEST(LeDeviceTest, set_property) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- LeDevice device(&config, &memory_only_config, address.ToString());
- ASSERT_FALSE(device.GetAddressType());
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(device.SetAddressType(AddressType::RANDOM_DEVICE_ADDRESS));
- mutation.Commit();
- ASSERT_THAT(device.GetAddressType(), Optional(Eq(AddressType::RANDOM_DEVICE_ADDRESS)));
-}
-
-TEST(LeDeviceTest, equality_test) {
- ConfigCache config(10, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(10, {});
- bluetooth::hci::Address address = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x06}};
- LeDevice device1(&config, &memory_only_config, address.ToString());
- LeDevice device2(&config, &memory_only_config, address.ToString());
- ASSERT_EQ(device1, device2);
- bluetooth::hci::Address address3 = {{0x01, 0x02, 0x03, 0x04, 0x05, 0x07}};
- LeDevice device3(&config, &memory_only_config, address3.ToString());
- ASSERT_NE(device1, device3);
-}
-
diff --git a/gd/storage/legacy.cc b/gd/storage/legacy.cc
new file mode 100644
index 000000000..74d4992f6
--- /dev/null
+++ b/gd/storage/legacy.cc
@@ -0,0 +1,120 @@
+/*
+ * Copyright 2020 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#define LOG_TAG "bt_storage"
+
+#include "storage/legacy.h"
+#include "storage/legacy_osi_config.h"
+
+namespace bluetooth {
+namespace storage {
+
+struct LegacyModule::impl {
+ void config_read(const std::string filename, LegacyReadConfigCallback callback, os::Handler* handler) {
+ std::unique_ptr<config_t> config = legacy::osi::config::config_new(filename.c_str());
+ if (config && !legacy::osi::config::config_has_section(*config, "Adapter")) {
+ LOG_ERROR("Config is missing adapter section");
+ config = nullptr;
+ }
+ if (!config) {
+ config = legacy::osi::config::config_new_empty();
+ }
+ handler->Post(common::BindOnce(std::move(callback), filename, std::move(config)));
+ }
+
+ void config_write(const std::string filename, const config_t config, LegacyWriteConfigCallback callback,
+ os::Handler* handler) {
+ handler->Post(common::BindOnce(std::move(callback), filename, legacy::osi::config::config_save(config, filename)));
+ }
+
+ void checksum_read(const std::string filename, LegacyReadChecksumCallback callback, os::Handler* handler) {
+ handler->Post(
+ common::BindOnce(std::move(callback), filename, legacy::osi::config::checksum_read(filename.c_str())));
+ }
+
+ void checksum_write(const std::string filename, const std::string checksum, LegacyWriteChecksumCallback callback,
+ os::Handler* handler) {
+ handler->Post(
+ common::BindOnce(std::move(callback), filename, legacy::osi::config::checksum_save(checksum, filename)));
+ }
+
+ void Start();
+ void Stop();
+
+ impl(const LegacyModule& name_module);
+
+ private:
+ const LegacyModule& module_;
+ os::Handler* handler_;
+};
+
+const ModuleFactory storage::LegacyModule::Factory = ModuleFactory([]() { return new storage::LegacyModule(); });
+
+storage::LegacyModule::impl::impl(const storage::LegacyModule& module) : module_(module) {}
+
+void storage::LegacyModule::impl::Start() {
+ handler_ = module_.GetHandler();
+}
+
+void storage::LegacyModule::impl::Stop() {}
+
+void storage::LegacyModule::ConfigRead(const std::string filename, LegacyReadConfigCallback callback,
+ os::Handler* handler) {
+ GetHandler()->Post(common::BindOnce(&LegacyModule::impl::config_read, common::Unretained(pimpl_.get()), filename,
+ std::move(callback), handler));
+}
+
+void storage::LegacyModule::ConfigWrite(const std::string filename, const config_t& config,
+ LegacyWriteConfigCallback callback, os::Handler* handler) {
+ GetHandler()->Post(common::BindOnce(&LegacyModule::impl::config_write, common::Unretained(pimpl_.get()), filename,
+ config, std::move(callback), handler));
+}
+
+void storage::LegacyModule::ChecksumRead(const std::string filename, LegacyReadChecksumCallback callback,
+ os::Handler* handler) {
+ GetHandler()->Post(common::BindOnce(&LegacyModule::impl::checksum_read, common::Unretained(pimpl_.get()), filename,
+ std::move(callback), handler));
+}
+
+void storage::LegacyModule::ChecksumWrite(const std::string filename, const std::string checksum,
+ LegacyWriteChecksumCallback callback, os::Handler* handler) {
+ GetHandler()->Post(common::BindOnce(&LegacyModule::impl::checksum_write, common::Unretained(pimpl_.get()), filename,
+ checksum, std::move(callback), handler));
+}
+
+/**
+ * General API here
+ */
+storage::LegacyModule::LegacyModule() : pimpl_(std::make_unique<impl>(*this)) {}
+
+storage::LegacyModule::~LegacyModule() {
+ pimpl_.reset();
+}
+
+/**
+ * Module methods here
+ */
+void storage::LegacyModule::ListDependencies(ModuleList* list) {}
+
+void storage::LegacyModule::Start() {
+ pimpl_->Start();
+}
+
+void storage::LegacyModule::Stop() {
+ pimpl_->Stop();
+}
+
+} // namespace storage
+} // namespace bluetooth
diff --git a/gd/storage/legacy.h b/gd/storage/legacy.h
new file mode 100644
index 000000000..4a4a8c67e
--- /dev/null
+++ b/gd/storage/legacy.h
@@ -0,0 +1,66 @@
+/*
+ * Copyright 2020 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#pragma once
+
+#include <stdbool.h>
+#include <array>
+#include <cstdint>
+#include <list>
+#include <memory>
+#include <string>
+
+#include "common/bind.h"
+#include "hci/address.h"
+#include "hci/hci_packets.h"
+#include "module.h"
+#include "storage/legacy_osi_config.h"
+
+namespace bluetooth {
+namespace storage {
+
+using LegacyReadConfigCallback = common::OnceCallback<void(const std::string, std::unique_ptr<config_t>)>;
+using LegacyWriteConfigCallback = common::OnceCallback<void(const std::string, bool success)>;
+using LegacyReadChecksumCallback = common::OnceCallback<void(const std::string, std::string)>;
+using LegacyWriteChecksumCallback = common::OnceCallback<void(const std::string, bool success)>;
+
+class LegacyModule : public bluetooth::Module {
+ public:
+ void ConfigRead(const std::string filename, LegacyReadConfigCallback callback, os::Handler* handler);
+ void ConfigWrite(const std::string filename, const config_t& config, LegacyWriteConfigCallback callback,
+ os::Handler* handler);
+ void ChecksumRead(const std::string filename, LegacyReadChecksumCallback callback, os::Handler* handler);
+ void ChecksumWrite(const std::string filename, const std::string checksum, LegacyWriteChecksumCallback callback,
+ os::Handler* handler);
+
+ static const ModuleFactory Factory;
+
+ LegacyModule();
+ ~LegacyModule();
+
+ protected:
+ void ListDependencies(ModuleList* list) override;
+ void Start() override;
+ void Stop() override;
+
+ private:
+ struct impl;
+ std::unique_ptr<impl> pimpl_;
+
+ DISALLOW_COPY_AND_ASSIGN(LegacyModule);
+};
+
+} // namespace storage
+} // namespace bluetooth
diff --git a/gd/storage/legacy_config_file.cc b/gd/storage/legacy_config_file.cc
deleted file mode 100644
index 4a46dd596..000000000
--- a/gd/storage/legacy_config_file.cc
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/legacy_config_file.h"
-
-#include <cerrno>
-#include <fstream>
-#include <sstream>
-
-#include "common/strings.h"
-#include "os/files.h"
-#include "os/log.h"
-#include "storage/device.h"
-
-namespace bluetooth {
-namespace storage {
-
-LegacyConfigFile::LegacyConfigFile(std::string path) : path_(std::move(path)) {
- ASSERT(!path_.empty());
-};
-
-std::optional<ConfigCache> LegacyConfigFile::Read(size_t temp_devices_capacity) {
- ASSERT(!path_.empty());
- std::ifstream config_file(path_);
- if (!config_file || !config_file.is_open()) {
- LOG_ERROR("unable to open file '%s', error: %s", path_.c_str(), strerror(errno));
- return std::nullopt;
- }
- int line_num = 0;
- ConfigCache cache(temp_devices_capacity, Device::kLinkKeyProperties);
- std::string line;
- std::string section(ConfigCache::kDefaultSectionName);
- while (std::getline(config_file, line)) {
- ++line_num;
- line = common::StringTrim(std::move(line));
- if (line.front() == '\0' || line.front() == '#') {
- continue;
- }
- if (line.front() == '[') {
- if (line.back() != ']') {
- LOG_WARN("unterminated section name on line %d", line_num);
- return std::nullopt;
- }
- // Read 'test' from '[text]', hence -2
- section = line.substr(1, line.size() - 2);
- } else {
- auto tokens = common::StringSplit(line, "=", 2);
- if (tokens.size() != 2) {
- LOG_WARN("no key/value separator found on line %d", line_num);
- return std::nullopt;
- }
- tokens[0] = common::StringTrim(std::move(tokens[0]));
- tokens[1] = common::StringTrim(std::move(tokens[1]));
- cache.SetProperty(section, tokens[0], std::move(tokens[1]));
- }
- }
- return cache;
-}
-
-bool LegacyConfigFile::Write(const ConfigCache& cache) {
- return os::WriteToFile(path_, cache.SerializeToLegacyFormat());
-}
-
-bool LegacyConfigFile::Delete() {
- if (!os::FileExists(path_)) {
- LOG_WARN("Config file at \"%s\" does not exist", path_.c_str());
- return false;
- }
- return os::RemoveFile(path_);
-}
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/legacy_config_file.h b/gd/storage/legacy_config_file.h
deleted file mode 100644
index 2a319c93b..000000000
--- a/gd/storage/legacy_config_file.h
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <string>
-#include <utility>
-
-#include "storage/config_cache.h"
-
-namespace bluetooth {
-namespace storage {
-
-// similar to INI
-class LegacyConfigFile {
- public:
- static LegacyConfigFile FromPath(std::string path) {
- return LegacyConfigFile(std::move(path));
- }
- explicit LegacyConfigFile(std::string path);
- std::optional<ConfigCache> Read(size_t temp_devices_capacity);
- bool Write(const ConfigCache& cache);
- bool Delete();
-
- private:
- std::string path_;
-};
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/legacy_config_file_test.cc b/gd/storage/legacy_config_file_test.cc
deleted file mode 100644
index 6b82b7472..000000000
--- a/gd/storage/legacy_config_file_test.cc
+++ /dev/null
@@ -1,187 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/legacy_config_file.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include <filesystem>
-
-#include "os/files.h"
-#include "storage/device.h"
-
-namespace testing {
-
-using bluetooth::os::ReadSmallFile;
-using bluetooth::os::WriteToFile;
-using bluetooth::storage::ConfigCache;
-using bluetooth::storage::Device;
-using bluetooth::storage::LegacyConfigFile;
-
-TEST(LegacyConfigFileTest, write_and_read_loop_back_test) {
- auto temp_dir = std::filesystem::temp_directory_path();
- auto temp_config = temp_dir / "temp_config.txt";
-
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "C", "D");
- config.SetProperty("CC:DD:EE:FF:00:11", "LinkKey", "AABBAABBCCDDEE");
- EXPECT_TRUE(config.HasProperty("CC:DD:EE:FF:00:11", "LinkKey"));
- EXPECT_THAT(config.GetPersistentSections(), ElementsAre("CC:DD:EE:FF:00:11"));
-
- EXPECT_TRUE(LegacyConfigFile::FromPath(temp_config.string()).Write(config));
- auto config_read = LegacyConfigFile::FromPath(temp_config.string()).Read(100);
- EXPECT_TRUE(config_read);
- // Unpaired devices do not exist in persistent config file
- config.RemoveSection("AA:BB:CC:DD:EE:FF");
- EXPECT_EQ(config, *config_read);
- EXPECT_THAT(config_read->GetPersistentSections(), ElementsAre("CC:DD:EE:FF:00:11"));
- EXPECT_THAT(config_read->GetProperty("A", "B"), Optional(StrEq("C")));
- EXPECT_THAT(config_read->GetProperty("CC:DD:EE:FF:00:11", "LinkKey"), Optional(StrEq("AABBAABBCCDDEE")));
-
- EXPECT_TRUE(std::filesystem::remove(temp_config));
-}
-
-static const std::string kReadTestConfig =
- "[Info]\n"
- "FileSource = Empty\n"
- "TimeCreated = 2020-05-20 01:20:56\n"
- "\n"
- "[Metrics]\n"
- "Salt256Bit = 1234567890abcdef1234567890abcdef1234567890abcdef1234567890abcdef\n"
- "\n"
- "[Adapter]\n"
- "Address = 01:02:03:ab:cd:ef\n"
- "LE_LOCAL_KEY_IRK = fedcba0987654321fedcba0987654321\n"
- "LE_LOCAL_KEY_IR = fedcba0987654321fedcba0987654322\n"
- "LE_LOCAL_KEY_DHK = fedcba0987654321fedcba0987654323\n"
- "LE_LOCAL_KEY_ER = fedcba0987654321fedcba0987654324\n"
- "ScanMode = 2\n"
- "DiscoveryTimeout = 120\n"
- "\n"
- "[01:02:03:ab:cd:ea]\n"
- "name = hello world\n"
- "LinkKey = fedcba0987654321fedcba0987654328\n";
-
-TEST(LegacyConfigFileTest, read_test) {
- auto temp_dir = std::filesystem::temp_directory_path();
- auto temp_config = temp_dir / "temp_config.txt";
- EXPECT_TRUE(WriteToFile(temp_config.string(), kReadTestConfig));
-
- auto config_read = LegacyConfigFile::FromPath(temp_config.string()).Read(100);
- EXPECT_TRUE(config_read);
- EXPECT_THAT(config_read->GetPersistentSections(), ElementsAre("01:02:03:ab:cd:ea"));
- EXPECT_THAT(config_read->GetProperty("Info", "FileSource"), Optional(StrEq("Empty")));
- EXPECT_THAT(config_read->GetProperty("Info", "FileSource"), Optional(StrEq("Empty")));
- EXPECT_THAT(
- config_read->GetProperty("01:02:03:ab:cd:ea", "LinkKey"), Optional(StrEq("fedcba0987654321fedcba0987654328")));
-
- EXPECT_TRUE(std::filesystem::remove(temp_config));
-}
-
-static const std::string kWriteTestConfig =
- "[Info]\n"
- "FileSource = Empty\n"
- "TimeCreated = \n"
- "\n"
- "[Adapter]\n"
- "Address = 01:02:03:ab:cd:ef\n"
- "\n"
- "[01:02:03:ab:cd:ea]\n"
- "name = hello world\n"
- "LinkKey = fedcba0987654321fedcba0987654328\n"
- "\n";
-
-TEST(LegacyConfigFileTest, write_test) {
- auto temp_dir = std::filesystem::temp_directory_path();
- auto temp_config = temp_dir / "temp_config.txt";
-
- ConfigCache config(100, Device::kLinkKeyProperties);
- config.SetProperty("Info", "FileSource", "Empty");
- config.SetProperty("Info", "TimeCreated", "");
- config.SetProperty("Adapter", "Address", "01:02:03:ab:cd:ef");
- config.SetProperty("01:02:03:ab:cd:ea", "name", "hello world");
- config.SetProperty("01:02:03:ab:cd:ea", "LinkKey", "fedcba0987654321fedcba0987654328");
- EXPECT_TRUE(LegacyConfigFile::FromPath(temp_config.string()).Write(config));
-
- EXPECT_THAT(ReadSmallFile(temp_config.string()), Optional(StrEq(kWriteTestConfig)));
-
- EXPECT_TRUE(std::filesystem::remove(temp_config));
-}
-
-static const std::string kConfigWithDuplicateSectionAndKey =
- " \n\
-first_key=value \n\
- \n\
-# Device ID (DID) configuration \n\
-[DID] \n\
- \n\
-# Record Number: 1, 2 or 3 - maximum of 3 records \n\
-recordNumber = 1 \n\
- \n\
-# Primary Record - true or false (default) \n\
-# There can be only one primary record \n\
-primaryRecord = true \n\
- \n\
-# Vendor ID '0xFFFF' indicates no Device ID Service Record is present in the device \n\
-# 0x000F = Broadcom Corporation (default) \n\
-#vendorId = 0x000F \n\
- \n\
-# Vendor ID Source \n\
-# 0x0001 = Bluetooth SIG assigned Device ID Vendor ID value (default) \n\
-# 0x0002 = USB Implementer's Forum assigned Device ID Vendor ID value \n\
-#vendorIdSource = 0x0001 \n\
- \n\
-# Product ID & Product Version \n\
-# Per spec DID v1.3 0xJJMN for version is interpreted as JJ.M.N \n\
-# JJ: major version number, M: minor version number, N: sub-minor version number \n\
-# For example: 1200, v14.3.6 \n\
-productId = 0x1200 \n\
-version = 0x1111 \n\
- \n\
-# Optional attributes \n\
-#clientExecutableURL = \n\
-#serviceDescription = \n\
-#documentationURL = \n\
- \n\
-# Additional optional DID records. Bluedroid supports up to 3 records. \n\
-[DID] \n\
-[DID] \n\
-version = 0x1436 \n\
- \n\
-HiSyncId = 18446744073709551615 \n\
-HiSyncId2 = 15001900 \n\
-";
-
-TEST(LegacyConfigFileTest, duplicate_section_and_key_test) {
- auto temp_dir = std::filesystem::temp_directory_path();
- auto temp_config = temp_dir / "temp_config.txt";
- ASSERT_TRUE(WriteToFile(temp_config.string(), kConfigWithDuplicateSectionAndKey));
-
- auto config_read = LegacyConfigFile::FromPath(temp_config.string()).Read(100);
- ASSERT_TRUE(config_read);
- EXPECT_THAT(config_read->GetProperty(ConfigCache::kDefaultSectionName, "first_key"), Optional(StrEq("value")));
- // All sections with the same name merge into the same key-value pair
- EXPECT_THAT(config_read->GetProperty("DID", "primaryRecord"), Optional(StrEq("true")));
- // When keys are repeated, the later one wins
- EXPECT_THAT(config_read->GetProperty("DID", "version"), Optional(StrEq("0x1436")));
-
- EXPECT_TRUE(std::filesystem::remove(temp_config));
-}
-
-} // namespace testing \ No newline at end of file
diff --git a/gd/storage/legacy_osi_config.cc b/gd/storage/legacy_osi_config.cc
new file mode 100644
index 000000000..b75d96ce8
--- /dev/null
+++ b/gd/storage/legacy_osi_config.cc
@@ -0,0 +1,456 @@
+/*
+ * Copyright 2020 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "storage/legacy_osi_config.h"
+
+#include <base/files/file_util.h>
+#include <fcntl.h>
+#include <string>
+
+#include "os/log.h"
+
+namespace {
+
+bool config_parse(FILE* fp, config_t* config);
+
+template <typename T,
+ class = typename std::enable_if<std::is_same<config_t, typename std::remove_const<T>::type>::value>>
+auto section_find(T& config, const std::string& section) {
+ return std::find_if(config.sections.begin(), config.sections.end(),
+ [&section](const section_t& sec) { return sec.name == section; });
+}
+
+const entry_t* entry_find(const config_t& config, const std::string& section, const std::string& key) {
+ auto sec = section_find(config, section);
+ if (sec == config.sections.end()) return nullptr;
+
+ for (const entry_t& entry : sec->entries) {
+ if (entry.key == key) return &entry;
+ }
+
+ return nullptr;
+}
+
+char* trim(char* str) {
+ while (isspace(*str)) ++str;
+
+ if (!*str) return str;
+
+ char* end_str = str + strlen(str) - 1;
+ while (end_str > str && isspace(*end_str)) --end_str;
+
+ end_str[1] = '\0';
+ return str;
+}
+
+bool config_parse(FILE* fp, config_t* config) {
+ CHECK(fp != nullptr);
+ CHECK(config != nullptr);
+
+ int line_num = 0;
+ char line[1024];
+ char section[1024];
+ strcpy(section, CONFIG_DEFAULT_SECTION);
+
+ while (fgets(line, sizeof(line), fp)) {
+ char* line_ptr = trim(line);
+ ++line_num;
+
+ // Skip blank and comment lines.
+ if (*line_ptr == '\0' || *line_ptr == '#') continue;
+
+ if (*line_ptr == '[') {
+ size_t len = strlen(line_ptr);
+ if (line_ptr[len - 1] != ']') {
+ VLOG(1) << __func__ << ": unterminated section name on line " << line_num;
+ return false;
+ }
+ strncpy(section, line_ptr + 1, len - 2); // NOLINT (len < 1024)
+ section[len - 2] = '\0';
+ } else {
+ char* split = strchr(line_ptr, '=');
+ if (!split) {
+ VLOG(1) << __func__ << ": no key/value separator found on line " << line_num;
+ return false;
+ }
+
+ *split = '\0';
+ bluetooth::legacy::osi::config::config_set_string(config, section, trim(line_ptr), trim(split + 1));
+ }
+ }
+ return true;
+}
+
+} // namespace
+
+std::unique_ptr<config_t> bluetooth::legacy::osi::config::config_new_empty(void) {
+ return std::make_unique<config_t>();
+}
+
+std::unique_ptr<config_t> bluetooth::legacy::osi::config::config_new(const char* filename) {
+ CHECK(filename != nullptr);
+
+ std::unique_ptr<config_t> config = config_new_empty();
+
+ FILE* fp = fopen(filename, "rt");
+ if (!fp) {
+ LOG(ERROR) << __func__ << ": unable to open file '" << filename << "': " << strerror(errno);
+ return nullptr;
+ }
+
+ if (!config_parse(fp, config.get())) {
+ config.reset();
+ }
+
+ fclose(fp);
+ return config;
+}
+
+std::string bluetooth::legacy::osi::config::checksum_read(const char* filename) {
+ base::FilePath path(filename);
+ if (!base::PathExists(path)) {
+ LOG(ERROR) << __func__ << ": unable to locate file '" << filename << "'";
+ return "";
+ }
+ std::string encrypted_hash;
+ if (!base::ReadFileToString(path, &encrypted_hash)) {
+ LOG(ERROR) << __func__ << ": unable to read file '" << filename << "'";
+ }
+ return encrypted_hash;
+}
+
+std::unique_ptr<config_t> bluetooth::legacy::osi::config::config_new_clone(const config_t& src) {
+ std::unique_ptr<config_t> ret = config_new_empty();
+
+ for (const section_t& sec : src.sections) {
+ for (const entry_t& entry : sec.entries) {
+ legacy::osi::config::config_set_string(ret.get(), sec.name, entry.key, entry.value);
+ }
+ }
+
+ return ret;
+}
+
+bool bluetooth::legacy::osi::config::config_has_section(const config_t& config, const std::string& section) {
+ return (section_find(config, section) != config.sections.end());
+}
+
+bool bluetooth::legacy::osi::config::config_has_key(const config_t& config, const std::string& section,
+ const std::string& key) {
+ return (entry_find(config, section, key) != nullptr);
+}
+
+int bluetooth::legacy::osi::config::config_get_int(const config_t& config, const std::string& section,
+ const std::string& key, int def_value) {
+ const entry_t* entry = entry_find(config, section, key);
+ if (!entry) return def_value;
+
+ char* endptr;
+ int ret = strtol(entry->value.c_str(), &endptr, 0);
+ return (*endptr == '\0') ? ret : def_value;
+}
+
+uint64_t bluetooth::legacy::osi::config::config_get_uint64(const config_t& config, const std::string& section,
+ const std::string& key, uint64_t def_value) {
+ const entry_t* entry = entry_find(config, section, key);
+ if (!entry) return def_value;
+
+ char* endptr;
+ uint64_t ret = strtoull(entry->value.c_str(), &endptr, 0);
+ return (*endptr == '\0') ? ret : def_value;
+}
+
+bool bluetooth::legacy::osi::config::config_get_bool(const config_t& config, const std::string& section,
+ const std::string& key, bool def_value) {
+ const entry_t* entry = entry_find(config, section, key);
+ if (!entry) return def_value;
+
+ if (entry->value == "true") return true;
+ if (entry->value == "false") return false;
+
+ return def_value;
+}
+
+const std::string* bluetooth::legacy::osi::config::config_get_string(const config_t& config, const std::string& section,
+ const std::string& key,
+ const std::string* def_value) {
+ const entry_t* entry = entry_find(config, section, key);
+ if (!entry) return def_value;
+
+ return &entry->value;
+}
+
+void bluetooth::legacy::osi::config::config_set_int(config_t* config, const std::string& section,
+ const std::string& key, int value) {
+ legacy::osi::config::config_set_string(config, section, key, std::to_string(value));
+}
+
+void bluetooth::legacy::osi::config::config_set_uint64(config_t* config, const std::string& section,
+ const std::string& key, uint64_t value) {
+ legacy::osi::config::config_set_string(config, section, key, std::to_string(value));
+}
+
+void bluetooth::legacy::osi::config::config_set_bool(config_t* config, const std::string& section,
+ const std::string& key, bool value) {
+ legacy::osi::config::config_set_string(config, section, key, value ? "true" : "false");
+}
+
+void bluetooth::legacy::osi::config::config_set_string(config_t* config, const std::string& section,
+ const std::string& key, const std::string& value) {
+ CHECK(config);
+
+ auto sec = section_find(*config, section);
+ if (sec == config->sections.end()) {
+ config->sections.emplace_back(section_t{.name = section});
+ sec = std::prev(config->sections.end());
+ }
+
+ std::string value_no_newline;
+ size_t newline_position = value.find('\n');
+ if (newline_position != std::string::npos) {
+ LOG_WARN("%s", "android_errorWriteLog(0x534e4554, 70808273)");
+ value_no_newline = value.substr(0, newline_position);
+ } else {
+ value_no_newline = value;
+ }
+
+ for (entry_t& entry : sec->entries) {
+ if (entry.key == key) {
+ entry.value = value_no_newline;
+ return;
+ }
+ }
+
+ sec->entries.emplace_back(entry_t{.key = key, .value = value_no_newline});
+}
+
+bool bluetooth::legacy::osi::config::config_remove_section(config_t* config, const std::string& section) {
+ CHECK(config);
+
+ auto sec = section_find(*config, section);
+ if (sec == config->sections.end()) return false;
+
+ config->sections.erase(sec);
+ return true;
+}
+
+bool bluetooth::legacy::osi::config::config_remove_key(config_t* config, const std::string& section,
+ const std::string& key) {
+ CHECK(config);
+ auto sec = section_find(*config, section);
+ if (sec == config->sections.end()) return false;
+
+ for (auto entry = sec->entries.begin(); entry != sec->entries.end(); ++entry) {
+ if (entry->key == key) {
+ sec->entries.erase(entry);
+ return true;
+ }
+ }
+
+ return false;
+}
+
+bool bluetooth::legacy::osi::config::config_save(const config_t& config, const std::string& filename) {
+ CHECK(!filename.empty());
+
+ // Steps to ensure content of config file gets to disk:
+ //
+ // 1) Open and write to temp file (e.g. bt_config.conf.new).
+ // 2) Flush the stream buffer to the temp file.
+ // 3) Sync the temp file to disk with fsync().
+ // 4) Rename temp file to actual config file (e.g. bt_config.conf).
+ // This ensures atomic update.
+ // 5) Sync directory that has the conf file with fsync().
+ // This ensures directory entries are up-to-date.
+ int dir_fd = -1;
+ FILE* fp = nullptr;
+ std::stringstream serialized;
+
+ // Build temp config file based on config file (e.g. bt_config.conf.new).
+ const std::string temp_filename = filename + ".new";
+
+ // Extract directory from file path (e.g. /data/misc/bluedroid).
+ const std::string directoryname = base::FilePath(filename).DirName().value();
+ if (directoryname.empty()) {
+ LOG(ERROR) << __func__ << ": error extracting directory from '" << filename << "': " << strerror(errno);
+ goto error;
+ }
+
+ dir_fd = open(directoryname.c_str(), O_RDONLY);
+ if (dir_fd < 0) {
+ LOG(ERROR) << __func__ << ": unable to open dir '" << directoryname << "': " << strerror(errno);
+ goto error;
+ }
+
+ fp = fopen(temp_filename.c_str(), "wt");
+ if (!fp) {
+ LOG(ERROR) << __func__ << ": unable to write to file '" << temp_filename << "': " << strerror(errno);
+ goto error;
+ }
+
+ for (const section_t& section : config.sections) {
+ serialized << "[" << section.name << "]" << std::endl;
+
+ for (const entry_t& entry : section.entries) serialized << entry.key << " = " << entry.value << std::endl;
+
+ serialized << std::endl;
+ }
+
+ if (fprintf(fp, "%s", serialized.str().c_str()) < 0) {
+ LOG(ERROR) << __func__ << ": unable to write to file '" << temp_filename << "': " << strerror(errno);
+ goto error;
+ }
+
+ // Flush the stream buffer to the temp file.
+ if (fflush(fp) < 0) {
+ LOG(ERROR) << __func__ << ": unable to write flush buffer to file '" << temp_filename << "': " << strerror(errno);
+ goto error;
+ }
+
+ // Sync written temp file out to disk. fsync() is blocking until data makes it
+ // to disk.
+ if (fsync(fileno(fp)) < 0) {
+ LOG(WARNING) << __func__ << ": unable to fsync file '" << temp_filename << "': " << strerror(errno);
+ }
+
+ if (fclose(fp) == EOF) {
+ LOG(ERROR) << __func__ << ": unable to close file '" << temp_filename << "': " << strerror(errno);
+ goto error;
+ }
+ fp = nullptr;
+
+ // Change the file's permissions to Read/Write by User and Group
+ if (chmod(temp_filename.c_str(), S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP) == -1) {
+ LOG(ERROR) << __func__ << ": unable to change file permissions '" << filename << "': " << strerror(errno);
+ goto error;
+ }
+
+ // Rename written temp file to the actual config file.
+ if (rename(temp_filename.c_str(), filename.c_str()) == -1) {
+ LOG(ERROR) << __func__ << ": unable to commit file '" << filename << "': " << strerror(errno);
+ goto error;
+ }
+
+ // This should ensure the directory is updated as well.
+ if (fsync(dir_fd) < 0) {
+ LOG(WARNING) << __func__ << ": unable to fsync dir '" << directoryname << "': " << strerror(errno);
+ }
+
+ if (close(dir_fd) < 0) {
+ LOG(ERROR) << __func__ << ": unable to close dir '" << directoryname << "': " << strerror(errno);
+ goto error;
+ }
+
+ return true;
+
+error:
+ // This indicates there is a write issue. Unlink as partial data is not
+ // acceptable.
+ unlink(temp_filename.c_str());
+ if (fp) fclose(fp);
+ if (dir_fd != -1) close(dir_fd);
+ return false;
+}
+
+bool bluetooth::legacy::osi::config::checksum_save(const std::string& checksum, const std::string& filename) {
+ CHECK(!checksum.empty()) << __func__ << ": checksum cannot be empty";
+ CHECK(!filename.empty()) << __func__ << ": filename cannot be empty";
+
+ // Steps to ensure content of config checksum file gets to disk:
+ //
+ // 1) Open and write to temp file (e.g.
+ // bt_config.conf.encrypted-checksum.new). 2) Sync the temp file to disk with
+ // fsync(). 3) Rename temp file to actual config checksum file (e.g.
+ // bt_config.conf.encrypted-checksum).
+ // This ensures atomic update.
+ // 4) Sync directory that has the conf file with fsync().
+ // This ensures directory entries are up-to-date.
+ FILE* fp = nullptr;
+ int dir_fd = -1;
+
+ // Build temp config checksum file based on config checksum file (e.g.
+ // bt_config.conf.encrypted-checksum.new).
+ const std::string temp_filename = filename + ".new";
+ base::FilePath path(temp_filename);
+
+ // Extract directory from file path (e.g. /data/misc/bluedroid).
+ const std::string directoryname = base::FilePath(filename).DirName().value();
+ if (directoryname.empty()) {
+ LOG(ERROR) << __func__ << ": error extracting directory from '" << filename << "': " << strerror(errno);
+ goto error2;
+ }
+
+ dir_fd = open(directoryname.c_str(), O_RDONLY);
+ if (dir_fd < 0) {
+ LOG(ERROR) << __func__ << ": unable to open dir '" << directoryname << "': " << strerror(errno);
+ goto error2;
+ }
+
+ if (base::WriteFile(path, checksum.data(), checksum.size()) != (int)checksum.size()) {
+ LOG(ERROR) << __func__ << ": unable to write file '" << filename.c_str();
+ goto error2;
+ }
+
+ fp = fopen(temp_filename.c_str(), "rb");
+ if (!fp) {
+ LOG(ERROR) << __func__ << ": unable to write to file '" << temp_filename << "': " << strerror(errno);
+ goto error2;
+ }
+
+ // Sync written temp file out to disk. fsync() is blocking until data makes it
+ // to disk.
+ if (fsync(fileno(fp)) < 0) {
+ LOG(WARNING) << __func__ << ": unable to fsync file '" << temp_filename << "': " << strerror(errno);
+ }
+
+ if (fclose(fp) == EOF) {
+ LOG(ERROR) << __func__ << ": unable to close file '" << temp_filename << "': " << strerror(errno);
+ goto error2;
+ }
+ fp = nullptr;
+
+ // Change the file's permissions to Read/Write by User and Group
+ if (chmod(temp_filename.c_str(), S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP) == -1) {
+ LOG(ERROR) << __func__ << ": unable to change file permissions '" << filename << "': " << strerror(errno);
+ goto error2;
+ }
+
+ // Rename written temp file to the actual config file.
+ if (rename(temp_filename.c_str(), filename.c_str()) == -1) {
+ LOG(ERROR) << __func__ << ": unable to commit file '" << filename << "': " << strerror(errno);
+ goto error2;
+ }
+
+ // This should ensure the directory is updated as well.
+ if (fsync(dir_fd) < 0) {
+ LOG(WARNING) << __func__ << ": unable to fsync dir '" << directoryname << "': " << strerror(errno);
+ }
+
+ if (close(dir_fd) < 0) {
+ LOG(ERROR) << __func__ << ": unable to close dir '" << directoryname << "': " << strerror(errno);
+ goto error2;
+ }
+
+ return true;
+
+error2:
+ // This indicates there is a write issue. Unlink as partial data is not
+ // acceptable.
+ unlink(temp_filename.c_str());
+ if (fp) fclose(fp);
+ if (dir_fd != -1) close(dir_fd);
+ return false;
+}
diff --git a/gd/storage/legacy_osi_config.h b/gd/storage/legacy_osi_config.h
new file mode 100644
index 000000000..36f6deea1
--- /dev/null
+++ b/gd/storage/legacy_osi_config.h
@@ -0,0 +1,147 @@
+/*
+ * Copyright 2020 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#pragma once
+// This code wraps osi/include/config.h
+
+#include <stdbool.h>
+#include <list>
+#include <memory>
+#include <string>
+
+#ifndef CONFIG_DEFAULT_SECTION
+
+// The default section name to use if a key/value pair is not defined within
+// a section.
+#define CONFIG_DEFAULT_SECTION "Global"
+
+struct entry_t {
+ std::string key;
+ std::string value;
+};
+
+struct section_t {
+ std::string name;
+ std::list<entry_t> entries;
+};
+
+struct config_t {
+ std::list<section_t> sections;
+};
+
+#endif /* CONFIG_DEFAULT_SECTION */
+
+namespace bluetooth {
+namespace legacy {
+namespace osi {
+namespace config {
+
+// Creates a new config object with no entries (i.e. not backed by a file).
+// This function returns a unique pointer to config object.
+std::unique_ptr<config_t> config_new_empty(void);
+
+// Loads the specified file and returns a handle to the config file. If there
+// was a problem loading the file, this function returns
+// NULL. |filename| must not be NULL and must point to a readable
+// file on the filesystem.
+std::unique_ptr<config_t> config_new(const char* filename);
+
+// Read the checksum from the |filename|
+std::string checksum_read(const char* filename);
+
+// Clones |src|, including all of it's sections, keys, and values.
+// Returns a new config which is a copy and separated from the original;
+// changes to the new config are not reflected in any way in the original.
+//
+// This function will not return NULL.
+std::unique_ptr<config_t> config_new_clone(const config_t& src);
+
+// Returns true if the config file contains a section named |section|. If
+// the section has no key/value pairs in it, this function will return false.
+bool config_has_section(const config_t& config, const std::string& section);
+
+// Returns true if the config file has a key named |key| under |section|.
+// Returns false otherwise.
+bool config_has_key(const config_t& config, const std::string& section, const std::string& key);
+
+// Returns the integral value for a given |key| in |section|. If |section|
+// or |key| do not exist, or the value cannot be fully converted to an integer,
+// this function returns |def_value|.
+int config_get_int(const config_t& config, const std::string& section, const std::string& key, int def_value);
+
+// Returns the uint64_t value for a given |key| in |section|. If |section|
+// or |key| do not exist, or the value cannot be fully converted to an integer,
+// this function returns |def_value|.
+uint64_t config_get_uint64(const config_t& config, const std::string& section, const std::string& key,
+ uint64_t def_value);
+
+// Returns the boolean value for a given |key| in |section|. If |section|
+// or |key| do not exist, or the value cannot be converted to a boolean, this
+// function returns |def_value|.
+bool config_get_bool(const config_t& config, const std::string& section, const std::string& key, bool def_value);
+
+// Returns the string value for a given |key| in |section|. If |section| or
+// |key| do not exist, this function returns |def_value|. The returned string
+// is owned by the config module and must not be freed or modified. |def_value|
+// may be NULL.
+const std::string* config_get_string(const config_t& config, const std::string& section, const std::string& key,
+ const std::string* def_value);
+
+// Sets an integral value for the |key| in |section|. If |key| or |section| do
+// not already exist, this function creates them. |config| must not be NULL.
+void config_set_int(config_t* config, const std::string& section, const std::string& key, int value);
+
+// Sets a uint64_t value for the |key| in |section|. If |key| or |section| do
+// not already exist, this function creates them. |config| must not be NULL.
+void config_set_uint64(config_t* config, const std::string& section, const std::string& key, uint64_t value);
+
+// Sets a boolean value for the |key| in |section|. If |key| or |section| do
+// not already exist, this function creates them. |config| must not be NULL.
+void config_set_bool(config_t* config, const std::string& section, const std::string& key, bool value);
+
+// Sets a string value for the |key| in |section|. If |key| or |section| do
+// not already exist, this function creates them. |config| must not be NULL.
+void config_set_string(config_t* config, const std::string& section, const std::string& key, const std::string& value);
+
+// Removes |section| from the |config| (and, as a result, all keys in the
+// section).
+// Returns true if |section| was found and removed from |config|, false
+// otherwise.
+// |config| may be NULL.
+bool config_remove_section(config_t* config, const std::string& section);
+
+// Removes one specific |key| residing in |section| of the |config|. Returns
+// true
+// if the section and key were found and the key was removed, false otherwise.
+// |config|may not be NULL.
+bool config_remove_key(config_t* config, const std::string& section, const std::string& key);
+
+// Saves |config| to a file given by |filename|. Note that this could be a
+// destructive operation: if |filename| already exists, it will be overwritten.
+// The config module does not preserve comments or formatting so if a config
+// file was opened with |config_new| and subsequently overwritten with
+// |config_save|, all comments and special formatting in the original file will
+// be lost. Neither |config| nor |filename| may be NULL.
+bool config_save(const config_t& config, const std::string& filename);
+
+// Saves the encrypted |checksum| of config file to a given |filename| Note
+// that this could be a destructive operation: if |filename| already exists,
+// it will be overwritten.
+bool checksum_save(const std::string& checksum, const std::string& filename);
+
+} // namespace config
+} // namespace osi
+} // namespace legacy
+} // namespace bluetooth
diff --git a/gd/storage/legacy_test.cc b/gd/storage/legacy_test.cc
new file mode 100644
index 000000000..0d0c1df75
--- /dev/null
+++ b/gd/storage/legacy_test.cc
@@ -0,0 +1,287 @@
+/*
+ * Copyright 2020 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#include "storage/legacy.h"
+
+#include <gtest/gtest.h>
+
+#include "os/handler.h"
+#include "os/thread.h"
+
+#include <base/files/file_util.h>
+
+#ifdef OS_ANDROID
+constexpr char CONFIG_FILE[] = "/data/local/tmp/config_test.conf";
+#else
+constexpr char CONFIG_FILE[] = "/tmp/config_test.conf";
+#endif
+
+constexpr char CONFIG_FILE_CONTENT[] =
+ " \n\
+first_key=value \n\
+ \n\
+# Device ID (DID) configuration \n\
+[DID] \n\
+ \n\
+# Record Number: 1, 2 or 3 - maximum of 3 records \n\
+recordNumber = 1 \n\
+ \n\
+# Primary Record - true or false (default) \n\
+# There can be only one primary record \n\
+primaryRecord = true \n\
+ \n\
+# Vendor ID '0xFFFF' indicates no Device ID Service Record is present in the device \n\
+# 0x000F = Broadcom Corporation (default) \n\
+#vendorId = 0x000F \n\
+ \n\
+# Vendor ID Source \n\
+# 0x0001 = Bluetooth SIG assigned Device ID Vendor ID value (default) \n\
+# 0x0002 = USB Implementer's Forum assigned Device ID Vendor ID value \n\
+#vendorIdSource = 0x0001 \n\
+ \n\
+# Product ID & Product Version \n\
+# Per spec DID v1.3 0xJJMN for version is interpreted as JJ.M.N \n\
+# JJ: major version number, M: minor version number, N: sub-minor version number \n\
+# For example: 1200, v14.3.6 \n\
+productId = 0x1200 \n\
+version = 0x1111 \n\
+ \n\
+# Optional attributes \n\
+#clientExecutableURL = \n\
+#serviceDescription = \n\
+#documentationURL = \n\
+ \n\
+# Additional optional DID records. Bluedroid supports up to 3 records. \n\
+[DID] \n\
+[DID] \n\
+version = 0x1436 \n\
+ \n\
+HiSyncId = 18446744073709551615 \n\
+HiSyncId2 = 15001900 \n\
+";
+
+namespace bluetooth {
+namespace storage {
+namespace {
+
+class LegacyStorageTest : public ::testing::Test {
+ public:
+ void OnConfigRead(std::string filename, std::unique_ptr<config_t> config) {
+ promise.set_value();
+ }
+
+ void OnConfigWrite(std::string filename, bool success) {
+ promise.set_value();
+ }
+
+ void OnChecksumRead(std::string filename, std::string hash) {
+ promise.set_value();
+ }
+
+ void OnChecksumWrite(std::string filename, bool success) {
+ promise.set_value();
+ }
+
+ protected:
+ void SetUp() override {
+ handler_ = new os::Handler(&thread_);
+ fake_registry_.Start<LegacyModule>(&thread_);
+ legacy_module_ = static_cast<LegacyModule*>(fake_registry_.GetModuleUnderTest(&LegacyModule::Factory));
+ FILE* fp = fopen(CONFIG_FILE, "wt");
+ fwrite(CONFIG_FILE_CONTENT, 1, sizeof(CONFIG_FILE_CONTENT), fp);
+ fclose(fp);
+ }
+
+ void TearDown() override {
+ handler_->Clear();
+ fake_registry_.StopAll();
+ delete handler_;
+ }
+
+ TestModuleRegistry fake_registry_;
+ os::Thread& thread_ = fake_registry_.GetTestThread();
+
+ LegacyModule* legacy_module_ = nullptr;
+ os::Handler* handler_ = nullptr;
+ std::promise<void> promise;
+};
+
+TEST_F(LegacyStorageTest, Module) {}
+
+TEST_F(LegacyStorageTest, ConfigRead) {
+ std::string filename(CONFIG_FILE);
+ auto future = promise.get_future();
+ legacy_module_->ConfigRead(filename, common::BindOnce(&LegacyStorageTest::OnConfigRead, common::Unretained(this)),
+ handler_);
+ future.wait();
+}
+
+TEST_F(LegacyStorageTest, ConfigWrite) {
+ std::string filename(CONFIG_FILE);
+ config_t config;
+ auto future = promise.get_future();
+ legacy_module_->ConfigWrite(filename, config,
+ common::BindOnce(&LegacyStorageTest::OnConfigWrite, common::Unretained(this)), handler_);
+ future.wait();
+}
+
+TEST_F(LegacyStorageTest, ChecksumRead) {
+ std::string filename(CONFIG_FILE);
+ auto future = promise.get_future();
+ legacy_module_->ChecksumRead(filename, common::BindOnce(&LegacyStorageTest::OnChecksumRead, common::Unretained(this)),
+ handler_);
+ future.wait();
+}
+
+TEST_F(LegacyStorageTest, ChecksumWrite) {
+ std::string filename(CONFIG_FILE);
+ std::string hash("0123456789abcdef");
+ auto future = promise.get_future();
+ legacy_module_->ChecksumWrite(
+ filename, hash, common::BindOnce(&LegacyStorageTest::OnChecksumWrite, common::Unretained(this)), handler_);
+ future.wait();
+}
+
+TEST_F(LegacyStorageTest, config_new_empty) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new_empty();
+ EXPECT_TRUE(config.get() != NULL);
+}
+
+TEST_F(LegacyStorageTest, config_new_no_file) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new("/meow");
+ EXPECT_TRUE(config.get() == NULL);
+}
+
+TEST_F(LegacyStorageTest, config_new) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_TRUE(config.get() != NULL);
+}
+
+TEST_F(LegacyStorageTest, config_new_clone) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ std::unique_ptr<config_t> clone = bluetooth::legacy::osi::config::config_new_clone(*config);
+
+ bluetooth::legacy::osi::config::config_set_string(clone.get(), CONFIG_DEFAULT_SECTION, "first_key", "not_value");
+
+ std::string one = std::string("one");
+ EXPECT_STRNE(
+ bluetooth::legacy::osi::config::config_get_string(*config, CONFIG_DEFAULT_SECTION, "first_key", &one)->c_str(),
+ bluetooth::legacy::osi::config::config_get_string(*clone, CONFIG_DEFAULT_SECTION, "first_key", &one)->c_str());
+}
+
+TEST_F(LegacyStorageTest, config_has_section) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_TRUE(bluetooth::legacy::osi::config::config_has_section(*config, "DID"));
+}
+
+TEST_F(LegacyStorageTest, config_has_key_in_default_section) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_TRUE(bluetooth::legacy::osi::config::config_has_key(*config, CONFIG_DEFAULT_SECTION, "first_key"));
+ EXPECT_STREQ(
+ bluetooth::legacy::osi::config::config_get_string(*config, CONFIG_DEFAULT_SECTION, "first_key", nullptr)->c_str(),
+ "value");
+}
+
+TEST_F(LegacyStorageTest, config_has_keys) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_TRUE(bluetooth::legacy::osi::config::config_has_key(*config, "DID", "recordNumber"));
+ EXPECT_TRUE(bluetooth::legacy::osi::config::config_has_key(*config, "DID", "primaryRecord"));
+ EXPECT_TRUE(bluetooth::legacy::osi::config::config_has_key(*config, "DID", "productId"));
+ EXPECT_TRUE(bluetooth::legacy::osi::config::config_has_key(*config, "DID", "version"));
+}
+
+TEST_F(LegacyStorageTest, config_no_bad_keys) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_FALSE(bluetooth::legacy::osi::config::config_has_key(*config, "DID_BAD", "primaryRecord"));
+ EXPECT_FALSE(bluetooth::legacy::osi::config::config_has_key(*config, "DID", "primaryRecord_BAD"));
+ EXPECT_FALSE(bluetooth::legacy::osi::config::config_has_key(*config, CONFIG_DEFAULT_SECTION, "primaryRecord"));
+}
+
+TEST_F(LegacyStorageTest, config_get_int_version) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_EQ(bluetooth::legacy::osi::config::config_get_int(*config, "DID", "version", 0), 0x1436);
+}
+
+TEST_F(LegacyStorageTest, config_get_int_default) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_EQ(bluetooth::legacy::osi::config::config_get_int(*config, "DID", "primaryRecord", 123), 123);
+}
+
+TEST_F(LegacyStorageTest, config_get_uint64) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_EQ(bluetooth::legacy::osi::config::config_get_uint64(*config, "DID", "HiSyncId", 0), 0xFFFFFFFFFFFFFFFF);
+ EXPECT_EQ(bluetooth::legacy::osi::config::config_get_uint64(*config, "DID", "HiSyncId2", 0), uint64_t(15001900));
+}
+
+TEST_F(LegacyStorageTest, config_get_uint64_default) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_EQ(bluetooth::legacy::osi::config::config_get_uint64(*config, "DID", "primaryRecord", 123), uint64_t(123));
+}
+
+TEST_F(LegacyStorageTest, config_remove_section) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_TRUE(bluetooth::legacy::osi::config::config_remove_section(config.get(), "DID"));
+ EXPECT_FALSE(bluetooth::legacy::osi::config::config_has_section(*config, "DID"));
+ EXPECT_FALSE(bluetooth::legacy::osi::config::config_has_key(*config, "DID", "productId"));
+}
+
+TEST_F(LegacyStorageTest, config_remove_section_missing) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_FALSE(bluetooth::legacy::osi::config::config_remove_section(config.get(), "not a section"));
+}
+
+TEST_F(LegacyStorageTest, config_remove_key) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_EQ(bluetooth::legacy::osi::config::config_get_int(*config, "DID", "productId", 999), 0x1200);
+ EXPECT_TRUE(bluetooth::legacy::osi::config::config_remove_key(config.get(), "DID", "productId"));
+ EXPECT_FALSE(bluetooth::legacy::osi::config::config_has_key(*config, "DID", "productId"));
+}
+
+TEST_F(LegacyStorageTest, config_remove_key_missing) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_EQ(bluetooth::legacy::osi::config::config_get_int(*config, "DID", "productId", 999), 0x1200);
+ EXPECT_TRUE(bluetooth::legacy::osi::config::config_remove_key(config.get(), "DID", "productId"));
+ EXPECT_EQ(bluetooth::legacy::osi::config::config_get_int(*config, "DID", "productId", 999), 999);
+}
+
+TEST_F(LegacyStorageTest, config_save_basic) {
+ std::unique_ptr<config_t> config = bluetooth::legacy::osi::config::config_new(CONFIG_FILE);
+ EXPECT_TRUE(bluetooth::legacy::osi::config::config_save(*config, CONFIG_FILE));
+}
+
+TEST_F(LegacyStorageTest, checksum_read) {
+ std::string filename = "/tmp/test.checksum_read";
+ std::string checksum = "0x1234";
+ base::FilePath file_path(filename);
+
+ EXPECT_EQ(base::WriteFile(file_path, checksum.data(), checksum.size()), (int)checksum.size());
+
+ EXPECT_EQ(bluetooth::legacy::osi::config::checksum_read(filename.c_str()), checksum.c_str());
+}
+
+TEST_F(LegacyStorageTest, checksum_save) {
+ std::string filename = "/tmp/test.checksum_save";
+ std::string checksum = "0x1234";
+ base::FilePath file_path(filename);
+
+ EXPECT_TRUE(bluetooth::legacy::osi::config::checksum_save(checksum, filename));
+
+ EXPECT_TRUE(base::PathExists(file_path));
+}
+
+} // namespace
+} // namespace storage
+} // namespace bluetooth
diff --git a/gd/storage/mutation.cc b/gd/storage/mutation.cc
deleted file mode 100644
index 7b8e5607e..000000000
--- a/gd/storage/mutation.cc
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/mutation.h"
-
-#include "os/log.h"
-
-namespace bluetooth {
-namespace storage {
-
-Mutation::Mutation(ConfigCache* config, ConfigCache* memory_only_config)
- : config_(config), memory_only_config_(memory_only_config) {
- ASSERT(config_ != nullptr);
- ASSERT(memory_only_config_ != nullptr);
-}
-
-void Mutation::Add(MutationEntry entry) {
- switch (entry.property_type) {
- case MutationEntry::PropertyType::NORMAL:
- if (entry.entry_type != MutationEntry::EntryType::SET) {
- // When an item is removed from normal config, it must be removed from temp config as well
- memory_only_config_entries_.emplace(entry);
- }
- normal_config_entries_.emplace(std::move(entry));
- break;
- case MutationEntry::PropertyType::MEMORY_ONLY:
- memory_only_config_entries_.emplace(std::move(entry));
- break;
- // do not write a default case so that when a new enum is defined, compilation would fail automatically
- }
-}
-
-void Mutation::Commit() {
- config_->Commit(normal_config_entries_);
- memory_only_config_->Commit(memory_only_config_entries_);
-}
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/mutation.h b/gd/storage/mutation.h
deleted file mode 100644
index b2072f910..000000000
--- a/gd/storage/mutation.h
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <queue>
-
-#include "os/log.h"
-#include "storage/config_cache.h"
-#include "storage/mutation_entry.h"
-
-namespace bluetooth {
-namespace storage {
-
-class Mutation {
- public:
- Mutation(ConfigCache* config, ConfigCache* memory_only_config);
- void Add(MutationEntry entry);
- void Commit();
- friend ConfigCache;
-
- private:
- ConfigCache* config_;
- ConfigCache* memory_only_config_;
- std::queue<MutationEntry> normal_config_entries_;
- std::queue<MutationEntry> memory_only_config_entries_;
-};
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/mutation_entry.cc b/gd/storage/mutation_entry.cc
deleted file mode 100644
index e7bea5109..000000000
--- a/gd/storage/mutation_entry.cc
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/mutation_entry.h"
-
-#include "os/log.h"
-
-namespace bluetooth {
-namespace storage {
-
-MutationEntry::MutationEntry(
- EntryType entry_type_param,
- PropertyType property_type_param,
- std::string section_param,
- std::string property_param,
- std::string value_param)
- : entry_type(entry_type_param),
- property_type(property_type_param),
- section(std::move(section_param)),
- property(std::move(property_param)),
- value(std::move(value_param)) {
- switch (entry_type) {
- case EntryType::SET:
- ASSERT_LOG(!section.empty(), "section cannot be empty for EntryType::SET");
- ASSERT_LOG(!property.empty(), "property cannot be empty for EntryType::SET");
- ASSERT_LOG(!value.empty(), "value cannot be empty for EntryType::SET");
- break;
- case EntryType::REMOVE_PROPERTY:
- ASSERT_LOG(!section.empty(), "section cannot be empty for EntryType::REMOVE_PROPERTY");
- ASSERT_LOG(!property.empty(), "property cannot be empty for EntryType::REMOVE_PROPERTY");
- break;
- case EntryType::REMOVE_SECTION:
- ASSERT_LOG(!section.empty(), "section cannot be empty for EntryType::REMOVE_SECTION");
- break;
- // do not write a default case so that when a new enum is defined, compilation would fail automatically
- }
-}
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/mutation_entry.h b/gd/storage/mutation_entry.h
deleted file mode 100644
index fcb902c77..000000000
--- a/gd/storage/mutation_entry.h
+++ /dev/null
@@ -1,124 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <string>
-#include <type_traits>
-
-#include "common/strings.h"
-#include "common/type_helper.h"
-#include "storage/serializable.h"
-
-namespace bluetooth {
-namespace storage {
-
-class MutationEntry {
- public:
- enum EntryType { SET, REMOVE_PROPERTY, REMOVE_SECTION };
-
- enum PropertyType { NORMAL, MEMORY_ONLY };
-
- template <typename T, typename std::enable_if<std::is_integral_v<T>, int>::type = 0>
- static MutationEntry Set(
- PropertyType property_type, std::string section_param, std::string property_param, T value_param) {
- return MutationEntry::Set(
- property_type, std::move(section_param), std::move(property_param), std::to_string(value_param));
- }
-
- template <typename T, typename std::enable_if<std::is_enum_v<T>, int>::type = 0>
- static MutationEntry Set(
- PropertyType property_type, std::string section_param, std::string property_param, T value_param) {
- using EnumUnderlyingType = typename std::underlying_type_t<T>;
- return MutationEntry::Set<EnumUnderlyingType>(
- property_type,
- std::move(section_param),
- std::move(property_param),
- static_cast<EnumUnderlyingType>(value_param));
- }
-
- template <typename T, typename std::enable_if<std::is_same_v<T, bool>, int>::type = 0>
- static MutationEntry Set(
- PropertyType property_type, std::string section_param, std::string property_param, T value_param) {
- return MutationEntry::Set(
- property_type, std::move(section_param), std::move(property_param), common::ToString(value_param));
- }
-
- template <typename T, typename std::enable_if<std::is_same_v<T, std::string>, int>::type = 0>
- static MutationEntry Set(
- PropertyType property_type, std::string section_param, std::string property_param, T value_param) {
- return MutationEntry::Set(
- property_type, std::move(section_param), std::move(property_param), std::move(value_param));
- }
-
- template <typename T, typename std::enable_if<std::is_base_of_v<Serializable<T>, T>, int>::type = 0>
- static MutationEntry Set(
- PropertyType property_type, std::string section_param, std::string property_param, const T& value_param) {
- return MutationEntry::Set(
- property_type, std::move(section_param), std::move(property_param), value_param.ToLegacyConfigString());
- }
-
- template <
- typename T,
- typename std::enable_if<
- bluetooth::common::is_specialization_of<T, std::vector>::value &&
- std::is_base_of_v<Serializable<typename T::value_type>, typename T::value_type>,
- int>::type = 0>
- static MutationEntry Set(
- PropertyType property_type, std::string section_param, std::string property_param, const T& value_param) {
- std::vector<std::string> str_values;
- str_values.reserve(value_param.size());
- for (const auto& v : value_param) {
- str_values.push_back(v.ToLegacyConfigString());
- }
- return MutationEntry::Set(
- property_type, std::move(section_param), std::move(property_param), common::StringJoin(str_values, " "));
- }
-
- static MutationEntry Set(
- PropertyType property_type, std::string section_param, std::string property_param, std::string value_param) {
- return MutationEntry(
- EntryType::SET, property_type, std::move(section_param), std::move(property_param), std::move(value_param));
- }
-
- static MutationEntry Remove(PropertyType property_type, std::string section_param) {
- return MutationEntry(EntryType::REMOVE_SECTION, property_type, std::move(section_param));
- }
-
- static MutationEntry Remove(PropertyType property_type, std::string section_param, std::string property_param) {
- return MutationEntry(
- EntryType::REMOVE_PROPERTY, property_type, std::move(section_param), std::move(property_param));
- }
-
- private:
- friend class ConfigCache;
- friend class Mutation;
-
- MutationEntry(
- EntryType entry_type_param,
- PropertyType property_type_param,
- std::string section_param,
- std::string property_param = "",
- std::string value_param = "");
-
- EntryType entry_type;
- PropertyType property_type;
- std::string section;
- std::string property;
- std::string value;
-};
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/mutation_test.cc b/gd/storage/mutation_test.cc
deleted file mode 100644
index cd72c59b1..000000000
--- a/gd/storage/mutation_test.cc
+++ /dev/null
@@ -1,125 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/mutation.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "storage/config_cache.h"
-#include "storage/device.h"
-
-namespace testing {
-
-using bluetooth::storage::ConfigCache;
-using bluetooth::storage::Device;
-using bluetooth::storage::Mutation;
-using bluetooth::storage::MutationEntry;
-
-TEST(MutationTest, simple_sequence_test) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(100, {});
- config.SetProperty("A", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "B", "C");
- config.SetProperty("AA:BB:CC:DD:EE:FF", "C", "D");
- config.SetProperty("CC:DD:EE:FF:00:11", "LinkKey", "AABBAABBCCDDEE");
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(MutationEntry::Set(MutationEntry::PropertyType::NORMAL, "AA:BB:CC:DD:EE:FF", "LinkKey", "CCDDEEFFGG"));
- mutation.Add(MutationEntry::Remove(MutationEntry::PropertyType::NORMAL, "AA:BB:CC:DD:EE:FF", "LinkKey"));
- mutation.Commit();
- ASSERT_THAT(config.GetPersistentSections(), ElementsAre("CC:DD:EE:FF:00:11"));
- Mutation mutation2(&config, &memory_only_config);
- mutation2.Add(MutationEntry::Set(MutationEntry::PropertyType::NORMAL, "AA:BB:CC:DD:EE:FF", "LinkKey", "CCDDEEFFGG"));
- mutation2.Commit();
- ASSERT_THAT(config.GetPersistentSections(), ElementsAre("CC:DD:EE:FF:00:11", "AA:BB:CC:DD:EE:FF"));
-}
-
-TEST(MutationTest, remove_property_and_section) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(100, {});
- config.SetProperty("A", "B", "C");
- config.SetProperty("A", "C", "D");
- config.SetProperty("B", "B", "C");
- config.SetProperty("B", "C", "D");
- ASSERT_TRUE(config.HasSection("A"));
- ASSERT_TRUE(config.HasProperty("A", "B"));
- ASSERT_TRUE(config.HasProperty("A", "C"));
- ASSERT_TRUE(config.HasSection("B"));
- ASSERT_TRUE(config.HasProperty("B", "B"));
- ASSERT_TRUE(config.HasProperty("B", "C"));
- {
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(MutationEntry::Remove(MutationEntry::PropertyType::NORMAL, "A", "B"));
- mutation.Commit();
- }
- ASSERT_TRUE(config.HasSection("A"));
- ASSERT_FALSE(config.HasProperty("A", "B"));
- ASSERT_TRUE(config.HasProperty("A", "C"));
- ASSERT_TRUE(config.HasSection("B"));
- ASSERT_TRUE(config.HasProperty("B", "B"));
- ASSERT_TRUE(config.HasProperty("B", "C"));
- {
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(MutationEntry::Remove(MutationEntry::PropertyType::NORMAL, "B"));
- mutation.Commit();
- }
- ASSERT_TRUE(config.HasSection("A"));
- ASSERT_FALSE(config.HasProperty("A", "B"));
- ASSERT_TRUE(config.HasProperty("A", "C"));
- ASSERT_FALSE(config.HasSection("B"));
- ASSERT_FALSE(config.HasProperty("B", "B"));
- ASSERT_FALSE(config.HasProperty("B", "C"));
- {
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(MutationEntry::Remove(MutationEntry::PropertyType::NORMAL, "A", "C"));
- mutation.Commit();
- }
- ASSERT_FALSE(config.HasSection("A"));
- ASSERT_FALSE(config.HasProperty("A", "B"));
- ASSERT_FALSE(config.HasProperty("A", "C"));
- ASSERT_FALSE(config.HasSection("B"));
- ASSERT_FALSE(config.HasProperty("B", "B"));
- ASSERT_FALSE(config.HasProperty("B", "C"));
-}
-
-TEST(MutationTest, add_and_remove_cancel_each_other) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(100, {});
- ASSERT_FALSE(config.HasSection("A"));
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(MutationEntry::Set(MutationEntry::PropertyType::NORMAL, "A", "B", "C"));
- mutation.Add(MutationEntry::Remove(MutationEntry::PropertyType::NORMAL, "A", "B"));
- mutation.Commit();
- ASSERT_FALSE(config.HasSection("A"));
-}
-
-TEST(MutationTest, add_to_different_configs) {
- ConfigCache config(100, Device::kLinkKeyProperties);
- ConfigCache memory_only_config(100, {});
- ASSERT_FALSE(config.HasSection("A"));
- Mutation mutation(&config, &memory_only_config);
- mutation.Add(MutationEntry::Set(MutationEntry::PropertyType::NORMAL, "A", "B", "C"));
- mutation.Add(MutationEntry::Set(MutationEntry::PropertyType::MEMORY_ONLY, "A", "D", "Hello"));
- mutation.Commit();
- ASSERT_TRUE(config.HasProperty("A", "B"));
- ASSERT_FALSE(config.HasProperty("A", "D"));
- ASSERT_THAT(config.GetProperty("A", "B"), Optional(StrEq("C")));
- ASSERT_FALSE(memory_only_config.HasProperty("A", "B"));
- ASSERT_TRUE(memory_only_config.HasProperty("A", "D"));
- ASSERT_THAT(memory_only_config.GetProperty("A", "D"), Optional(StrEq("Hello")));
-}
-
-} // namespace testing \ No newline at end of file
diff --git a/gd/storage/serializable.h b/gd/storage/serializable.h
deleted file mode 100644
index 3a7dd93e4..000000000
--- a/gd/storage/serializable.h
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <optional>
-#include <string>
-#include <type_traits>
-
-namespace bluetooth {
-namespace storage {
-
-// A config serializable module
-template <typename T>
-class Serializable {
- public:
- Serializable() = default;
- virtual ~Serializable() = default;
-
- // GD stack code
-
- // Serialize to string used in GD stack
- virtual std::string ToString() const = 0;
- // T must implement FromString(const std::string&), otherwise, it will fail to compile
- // Parse string from GD stack
- static std::optional<T> FromString(const std::string& str) {
- return T::FromString(str);
- }
-
- // Legacy handling
-
- // Serialize to string used in legacy stack config, this may not be the same as ToString()
- virtual std::string ToLegacyConfigString() const = 0;
- // T must implement FromLegacyConfigString(const std::string&), otherwise, it will fail to compile
- // Parse string from legacy config
- static std::optional<T> FromLegacyConfigString(const std::string& str) {
- return T::FromLegacyConfigString(str);
- }
-};
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/storage_module.cc b/gd/storage/storage_module.cc
deleted file mode 100644
index 6b4e9bc30..000000000
--- a/gd/storage/storage_module.cc
+++ /dev/null
@@ -1,238 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/storage_module.h"
-
-#include <chrono>
-#include <ctime>
-#include <iomanip>
-#include <memory>
-#include <utility>
-
-#include "common/bind.h"
-#include "os/alarm.h"
-#include "os/files.h"
-#include "os/handler.h"
-#include "os/parameter_provider.h"
-#include "os/system_properties.h"
-#include "storage/config_cache.h"
-#include "storage/legacy_config_file.h"
-#include "storage/mutation.h"
-
-namespace bluetooth {
-namespace storage {
-
-using common::ListMap;
-using common::LruCache;
-using os::Alarm;
-using os::Handler;
-
-static const std::string kFactoryResetProperty = "persist.bluetooth.factoryreset";
-
-static const size_t kDefaultTempDeviceCapacity = 10000;
-// Save config whenever there is a change, but delay it by this value so that burst config change won't overwhelm disk
-static const std::chrono::milliseconds kDefaultConfigSaveDelay = std::chrono::milliseconds(3000);
-// Writing a config to disk takes a minimum 10 ms on a decent x86_64 machine, and 20 ms if including backup file
-// The config saving delay must be bigger than this value to avoid overwhelming the disk
-static const std::chrono::milliseconds kMinConfigSaveDelay = std::chrono::milliseconds(20);
-
-const std::string StorageModule::kInfoSection = "Info";
-const std::string StorageModule::kFileSourceProperty = "FileSource";
-const std::string StorageModule::kTimeCreatedProperty = "TimeCreated";
-const std::string StorageModule::kTimeCreatedFormat = "%Y-%m-%d %H:%M:%S";
-
-const std::string StorageModule::kAdapterSection = "Adapter";
-
-StorageModule::StorageModule(
- std::string config_file_path,
- std::chrono::milliseconds config_save_delay,
- size_t temp_devices_capacity,
- bool is_restricted_mode,
- bool is_single_user_mode)
- : config_file_path_(std::move(config_file_path)),
- config_save_delay_(config_save_delay),
- temp_devices_capacity_(temp_devices_capacity),
- is_restricted_mode_(is_restricted_mode),
- is_single_user_mode_(is_single_user_mode) {
- // e.g. "/data/misc/bluedroid/bt_config.conf" to "/data/misc/bluedroid/bt_config.bak"
- config_backup_path_ = config_file_path_.substr(0, config_file_path_.find_last_of('.')) + ".bak";
- ASSERT_LOG(
- config_save_delay > kMinConfigSaveDelay,
- "Config save delay of %lld ms is not enough, must be at least %lld ms to avoid overwhelming the disk",
- config_save_delay_.count(),
- kMinConfigSaveDelay.count());
-};
-
-StorageModule::~StorageModule() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- pimpl_.reset();
-}
-
-const ModuleFactory StorageModule::Factory = ModuleFactory([]() {
- return new StorageModule(
- os::ParameterProvider::ConfigFilePath(), kDefaultConfigSaveDelay, kDefaultTempDeviceCapacity, false, false);
-});
-
-struct StorageModule::impl {
- explicit impl(Handler* handler, ConfigCache cache, size_t in_memory_cache_size_limit)
- : config_save_alarm_(handler), cache_(std::move(cache)), memory_only_cache_(in_memory_cache_size_limit, {}) {}
- Alarm config_save_alarm_;
- ConfigCache cache_;
- ConfigCache memory_only_cache_;
- bool has_pending_config_save_ = false;
-};
-
-Mutation StorageModule::Modify() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- return Mutation(&pimpl_->cache_, &pimpl_->memory_only_cache_);
-}
-
-ConfigCache* StorageModule::GetConfigCache() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- return &pimpl_->cache_;
-}
-
-ConfigCache* StorageModule::GetMemoryOnlyConfigCache() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- return &pimpl_->memory_only_cache_;
-}
-
-void StorageModule::SaveDelayed() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- if (pimpl_->has_pending_config_save_) {
- return;
- }
- pimpl_->config_save_alarm_.Schedule(
- common::BindOnce(&StorageModule::SaveImmediately, common::Unretained(this)), config_save_delay_);
- pimpl_->has_pending_config_save_ = true;
-}
-
-void StorageModule::SaveImmediately() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- if (pimpl_->has_pending_config_save_) {
- pimpl_->config_save_alarm_.Cancel();
- pimpl_->has_pending_config_save_ = false;
- }
- // 1. rename old config to backup name
- if (os::FileExists(config_file_path_)) {
- ASSERT(os::RenameFile(config_file_path_, config_backup_path_));
- }
- // 2. write in-memory config to disk, if failed, backup can still be used
- ASSERT(LegacyConfigFile::FromPath(config_file_path_).Write(pimpl_->cache_));
- // 3. now write back up to disk as well
- ASSERT(LegacyConfigFile::FromPath(config_backup_path_).Write(pimpl_->cache_));
-}
-
-void StorageModule::ListDependencies(ModuleList* list) {
- // No dependencies
-}
-
-void StorageModule::Start() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- std::string file_source;
- if (os::GetSystemProperty(kFactoryResetProperty) == "true") {
- LegacyConfigFile::FromPath(config_file_path_).Delete();
- LegacyConfigFile::FromPath(config_backup_path_).Delete();
- }
- auto config = LegacyConfigFile::FromPath(config_file_path_).Read(temp_devices_capacity_);
- if (!config || !config->HasSection(kAdapterSection)) {
- LOG_WARN("cannot load config at %s, using backup at %s.", config_file_path_.c_str(), config_backup_path_.c_str());
- config = LegacyConfigFile::FromPath(config_backup_path_).Read(temp_devices_capacity_);
- file_source = "Backup";
- }
- if (!config || !config->HasSection(kAdapterSection)) {
- LOG_WARN("cannot load backup config at %s; creating new empty ones", config_backup_path_.c_str());
- config.emplace(temp_devices_capacity_, Device::kLinkKeyProperties);
- file_source = "Empty";
- }
- if (!file_source.empty()) {
- config->SetProperty(kInfoSection, kFileSourceProperty, std::move(file_source));
- }
- // Cleanup temporary pairings if we have left guest mode
- if (!is_restricted_mode_) {
- config->RemoveSectionWithProperty("Restricted");
- }
- // Read or set config file creation timestamp
- auto time_str = config->GetProperty(kInfoSection, kTimeCreatedProperty);
- if (!time_str) {
- std::stringstream ss;
- auto now = std::chrono::system_clock::now();
- auto now_time_t = std::chrono::system_clock::to_time_t(now);
- ss << std::put_time(std::localtime(&now_time_t), kTimeCreatedFormat.c_str());
- config->SetProperty(kInfoSection, kTimeCreatedProperty, ss.str());
- }
- config->FixDeviceTypeInconsistencies();
- config->SetPersistentConfigChangedCallback([this] { this->CallOn(this, &StorageModule::SaveDelayed); });
- // TODO (b/158035889) Migrate metrics module to GD
- pimpl_ = std::make_unique<impl>(GetHandler(), std::move(config.value()), temp_devices_capacity_);
- SaveDelayed();
-}
-
-void StorageModule::Stop() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- SaveImmediately();
- pimpl_.reset();
-}
-
-std::string StorageModule::ToString() const {
- return "Storage Module";
-}
-
-Device StorageModule::GetDeviceByLegacyKey(hci::Address legacy_key_address) {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- return Device(
- &pimpl_->cache_,
- &pimpl_->memory_only_cache_,
- std::move(legacy_key_address),
- Device::ConfigKeyAddressType::LEGACY_KEY_ADDRESS);
-}
-
-Device StorageModule::GetDeviceByClassicMacAddress(hci::Address classic_address) {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- return Device(
- &pimpl_->cache_,
- &pimpl_->memory_only_cache_,
- std::move(classic_address),
- Device::ConfigKeyAddressType::CLASSIC_ADDRESS);
-}
-
-Device StorageModule::GetDeviceByLeIdentityAddress(hci::Address le_identity_address) {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- return Device(
- &pimpl_->cache_,
- &pimpl_->memory_only_cache_,
- std::move(le_identity_address),
- Device::ConfigKeyAddressType::LE_IDENTITY_ADDRESS);
-}
-
-AdapterConfig StorageModule::GetAdapterConfig() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- return AdapterConfig(&pimpl_->cache_, &pimpl_->memory_only_cache_, kAdapterSection);
-}
-
-std::vector<Device> StorageModule::GetBondedDevices() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- auto persistent_sections = GetConfigCache()->GetPersistentSections();
- std::vector<Device> result;
- result.reserve(persistent_sections.size());
- for (const auto& section : persistent_sections) {
- result.emplace_back(&pimpl_->cache_, &pimpl_->memory_only_cache_, section);
- }
- return result;
-}
-
-} // namespace storage
-} // namespace bluetooth \ No newline at end of file
diff --git a/gd/storage/storage_module.h b/gd/storage/storage_module.h
deleted file mode 100644
index 082b6a5b2..000000000
--- a/gd/storage/storage_module.h
+++ /dev/null
@@ -1,153 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <array>
-#include <chrono>
-#include <cstdint>
-#include <list>
-#include <memory>
-#include <mutex>
-#include <string>
-
-#include "hci/address.h"
-#include "module.h"
-#include "storage/adapter_config.h"
-#include "storage/config_cache.h"
-#include "storage/device.h"
-#include "storage/mutation.h"
-
-namespace bluetooth {
-
-namespace shim {
-class BtifConfigInterface;
-}
-
-namespace storage {
-
-class StorageModule : public bluetooth::Module {
- public:
- static const std::string kInfoSection;
- static const std::string kFileSourceProperty;
- static const std::string kTimeCreatedProperty;
- static const std::string kTimeCreatedFormat;
-
- static const std::string kAdapterSection;
-
- ~StorageModule();
- static const ModuleFactory Factory;
-
- // Methods to access the storage layer via Device abstraction
- // - Devices will be lazily created when methods below are called. Hence, no std::optional<> nor nullptr is used in
- // the return type. User of the API can use the Device object's API to find out if the device has existed before
- // - Devices with no config values will not be saved to config cache
- // - Devices that are not paired will also be discarded when stack shutdown
-
- // Concept:
- //
- // BR/EDR Address:
- // -> Public static address only, begin with 3 byte IEEE assigned OUI number
- //
- // BLE Addresses
- // -> Public Address: begin with IEEE assigned OUI number
- // -> Static: static public address do not change
- // -> Private/Variable: We haven't seen private/variable public address yet
- // -> Random Address: randomly generated, does not begin with IEEE assigned OUI number
- // -> Static: static random address do not change
- // -> Private/Variable: private random address changes once so often
- // -> Resolvable: this address can be resolved into a static address using identity resolving key (IRK)
- // -> Non-resolvable: this address is for temporary use only, do not save this address
- //
- // MAC addresses are six bytes only and hence are only regionally unique
-
- // Get a device object using the |legacy_key_address|. In legacy config, each device's config is stored in a config
- // section keyed by a single MAC address. For BR/EDR device, this is straightforward as a BR/EDR device has only a
- // single public static MAC address. However, for LE devices using private addresses, we only learn its real static
- // address after pairing. Since we still need to store that device's information prior to pairing, we use the
- // first-seen address of that device, no matter random private or static public, as a "key" to store that device's
- // config. This method gives you a device object using this legacy key. If the key does not exist, the device will
- // be lazily created in the config
- Device GetDeviceByLegacyKey(hci::Address legacy_key_address);
-
- // A classic (BR/EDR) or dual mode device can be uniquely located by its classic (BR/EDR) MAC address
- Device GetDeviceByClassicMacAddress(hci::Address classic_address);
-
- // A LE or dual mode device can be uniquely located by its identity address that is either:
- // -> Public static address
- // -> Random static address
- // If remote device uses LE random private resolvable address, user of this API must resolve its identity address
- // before calling this method to get the device object
- //
- // Note: A dual mode device's identity address is normally the same as its BR/EDR address, but they can also be
- // different. Hence, please don't make such assumption and don't use GetDeviceByBrEdrMacAddress() interchangeably
- Device GetDeviceByLeIdentityAddress(hci::Address le_identity_address);
-
- // A think copyable, movable, comparable object that is used to access adapter level information
- AdapterConfig GetAdapterConfig();
-
- // Get a list of bonded devices from config
- std::vector<Device> GetBondedDevices();
-
- // Modify the underlying config by starting a mutation. All entries in the mutation will be applied atomically when
- // Commit() is called. User should never touch ConfigCache() directly.
- Mutation Modify();
-
- protected:
- void ListDependencies(ModuleList* list) override;
- void Start() override;
- void Stop() override;
- std::string ToString() const override;
-
- friend shim::BtifConfigInterface;
- // For shim layer only
- ConfigCache* GetConfigCache();
- // For unit test only
- ConfigCache* GetMemoryOnlyConfigCache();
- // Normally, underlying config will be saved at most 3 seconds after the first config change in a series of changes
- // This method triggers the delayed saving automatically, the delay is equal to |config_save_delay_|
- void SaveDelayed();
- // In some cases, one may want to save the config immediately to disk. Call this method with caution as it runs
- // immediately on the calling thread
- void SaveImmediately();
-
- // Create the storage module where:
- // - config_file_path is the path to the config file on disk, a .bak file will be created with the original
- // - config_save_delay is the duration after which to dump config to disk after SaveDelayed() is called
- // - temp_devices_capacity is the number of temporary, typically unpaired devices to hold in a memory based LRU
- // - is_restricted_mode and is_single_user_mode are flags from upper layer
- StorageModule(
- std::string config_file_path,
- std::chrono::milliseconds config_save_delay,
- size_t temp_devices_capacity,
- bool is_restricted_mode,
- bool is_single_user_mode);
-
- private:
- struct impl;
- mutable std::recursive_mutex mutex_;
- std::unique_ptr<impl> pimpl_;
- std::string config_file_path_;
- std::string config_backup_path_;
- std::chrono::milliseconds config_save_delay_;
- size_t temp_devices_capacity_;
- bool is_restricted_mode_;
- bool is_single_user_mode_;
-
- DISALLOW_COPY_AND_ASSIGN(StorageModule);
-};
-
-} // namespace storage
-} // namespace bluetooth
diff --git a/gd/storage/storage_module_test.cc b/gd/storage/storage_module_test.cc
deleted file mode 100644
index 1e85d91fe..000000000
--- a/gd/storage/storage_module_test.cc
+++ /dev/null
@@ -1,321 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "storage/storage_module.h"
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include <chrono>
-#include <cstdio>
-#include <ctime>
-#include <filesystem>
-#include <iomanip>
-#include <optional>
-#include <thread>
-
-#include "module.h"
-#include "os/files.h"
-#include "storage/config_cache.h"
-#include "storage/device.h"
-#include "storage/legacy_config_file.h"
-
-namespace testing {
-
-using bluetooth::TestModuleRegistry;
-using bluetooth::hci::Address;
-using bluetooth::storage::ConfigCache;
-using bluetooth::storage::Device;
-using bluetooth::storage::LegacyConfigFile;
-using bluetooth::storage::StorageModule;
-
-static const std::chrono::milliseconds kTestConfigSaveDelay = std::chrono::milliseconds(100);
-// Assume it takes at most 1 second to write the file
-static const std::chrono::milliseconds kTestConfigSaveWaitDelay =
- kTestConfigSaveDelay + std::chrono::milliseconds(1000);
-
-static std::optional<std::chrono::system_clock::time_point> ParseTimestamp(
- const std::string& timestamp, const std::string& format) {
- std::istringstream ss(timestamp);
- // 1. Parse to time_t from timestamp that may not contain day light saving information
- std::tm no_dst_tm = {};
- ss >> std::get_time(&no_dst_tm, format.c_str());
- if (ss.fail()) {
- return std::nullopt;
- }
- // 2. Make a copy of the parsed result so that we can set tm_isdst bit later
- auto dst_tm = no_dst_tm;
- auto no_dst_time_t = std::mktime(&no_dst_tm);
- if (no_dst_time_t == -1) {
- return std::nullopt;
- }
- // 3. Convert time_t to tm again, but let system decide if day light saving should be set at that date and time
- auto dst_tm_only = std::localtime(&no_dst_time_t);
- // 4. Set the correct tm_isdst bit
- dst_tm.tm_isdst = dst_tm_only->tm_isdst;
- auto dst_time_t = std::mktime(&dst_tm);
- if (dst_time_t == -1) {
- return std::nullopt;
- }
- // 5. Parse is to time point
- return std::chrono::system_clock::from_time_t(dst_time_t);
-}
-
-class TestStorageModule : public StorageModule {
- public:
- TestStorageModule(
- std::string config_file_path,
- std::chrono::milliseconds config_save_delay,
- size_t temp_devices_capacity,
- bool is_restricted_mode,
- bool is_single_user_mode)
- : StorageModule(
- std::move(config_file_path),
- config_save_delay,
- temp_devices_capacity,
- is_restricted_mode,
- is_single_user_mode) {}
-
- ConfigCache* GetConfigCachePublic() {
- return StorageModule::GetConfigCache();
- }
-
- ConfigCache* GetMemoryOnlyConfigCachePublic() {
- return StorageModule::GetMemoryOnlyConfigCache();
- }
-
- void SaveImmediatelyPublic() {
- StorageModule::SaveImmediately();
- }
-};
-
-class StorageModuleTest : public Test {
- protected:
- void SetUp() override {
- temp_dir_ = std::filesystem::temp_directory_path();
- temp_config_ = temp_dir_ / "temp_config.txt";
- temp_backup_config_ = temp_dir_ / "temp_config.bak";
- DeleteConfigFiles();
- ASSERT_FALSE(std::filesystem::exists(temp_config_));
- ASSERT_FALSE(std::filesystem::exists(temp_backup_config_));
- }
-
- void TearDown() override {
- DeleteConfigFiles();
- }
-
- void DeleteConfigFiles() {
- if (std::filesystem::exists(temp_config_)) {
- ASSERT_TRUE(std::filesystem::remove(temp_config_));
- }
- if (std::filesystem::exists(temp_backup_config_)) {
- ASSERT_TRUE(std::filesystem::remove(temp_backup_config_));
- }
- }
-
- std::filesystem::path temp_dir_;
- std::filesystem::path temp_config_;
- std::filesystem::path temp_backup_config_;
-};
-
-TEST_F(StorageModuleTest, empty_config_no_op_test) {
- // Actual test
- auto time_before = std::chrono::system_clock::now();
- auto* storage = new TestStorageModule(temp_config_.string(), kTestConfigSaveDelay, 10, false, false);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&StorageModule::Factory, storage);
- test_registry.StopAll();
- auto time_after = std::chrono::system_clock::now();
-
- // Verify states after test
- ASSERT_TRUE(std::filesystem::exists(temp_config_));
-
- // Verify config after test
- auto config = LegacyConfigFile::FromPath(temp_config_.string()).Read(10);
- ASSERT_TRUE(config);
- ASSERT_TRUE(config->HasSection(StorageModule::kInfoSection));
- ASSERT_THAT(
- config->GetProperty(StorageModule::kInfoSection, StorageModule::kFileSourceProperty), Optional(StrEq("Empty")));
-
- // Verify file creation timestamp falls between time_before and time_after
- auto timestamp = config->GetProperty(StorageModule::kInfoSection, StorageModule::kTimeCreatedProperty);
- ASSERT_TRUE(timestamp);
- auto file_time = ParseTimestamp(*timestamp, StorageModule::kTimeCreatedFormat);
- ASSERT_TRUE(file_time);
- ASSERT_GE(std::chrono::duration_cast<std::chrono::seconds>(time_after - *file_time).count(), 0);
- ASSERT_GE(std::chrono::duration_cast<std::chrono::seconds>(*file_time - time_before).count(), 0);
-}
-
-static const std::string kReadTestConfig =
- "[Info]\n"
- "FileSource = Empty\n"
- "TimeCreated = 2020-05-20 01:20:56\n"
- "\n"
- "[Metrics]\n"
- "Salt256Bit = 1234567890abcdef1234567890abcdef1234567890abcdef1234567890abcdef\n"
- "\n"
- "[Adapter]\n"
- "Address = 01:02:03:ab:cd:ef\n"
- "LE_LOCAL_KEY_IRK = fedcba0987654321fedcba0987654321\n"
- "LE_LOCAL_KEY_IR = fedcba0987654321fedcba0987654322\n"
- "LE_LOCAL_KEY_DHK = fedcba0987654321fedcba0987654323\n"
- "LE_LOCAL_KEY_ER = fedcba0987654321fedcba0987654324\n"
- "ScanMode = 2\n"
- "DiscoveryTimeout = 120\n"
- "\n"
- "[01:02:03:ab:cd:ea]\n"
- "name = hello world\n"
- "LinkKey = fedcba0987654321fedcba0987654328\n"
- "\n";
-
-static const std::string kReadTestConfigCorrected =
- "[Info]\n"
- "FileSource = Empty\n"
- "TimeCreated = 2020-05-20 01:20:56\n"
- "\n"
- "[Metrics]\n"
- "Salt256Bit = 1234567890abcdef1234567890abcdef1234567890abcdef1234567890abcdef\n"
- "\n"
- "[Adapter]\n"
- "Address = 01:02:03:ab:cd:ef\n"
- "LE_LOCAL_KEY_IRK = fedcba0987654321fedcba0987654321\n"
- "LE_LOCAL_KEY_IR = fedcba0987654321fedcba0987654322\n"
- "LE_LOCAL_KEY_DHK = fedcba0987654321fedcba0987654323\n"
- "LE_LOCAL_KEY_ER = fedcba0987654321fedcba0987654324\n"
- "ScanMode = 2\n"
- "DiscoveryTimeout = 120\n"
- "\n"
- "[01:02:03:ab:cd:ea]\n"
- "name = hello world\n"
- "LinkKey = fedcba0987654321fedcba0987654328\n"
- "DevType = 1\n"
- "\n";
-
-TEST_F(StorageModuleTest, read_existing_config_test) {
- ASSERT_TRUE(bluetooth::os::WriteToFile(temp_config_.string(), kReadTestConfig));
- // Actual test
-
- // Set up
- auto* storage = new TestStorageModule(temp_config_.string(), kTestConfigSaveDelay, 10, false, false);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&StorageModule::Factory, storage);
-
- // Test
- ASSERT_NE(storage->GetConfigCachePublic(), nullptr);
- ASSERT_TRUE(storage->GetConfigCachePublic()->HasSection("Metrics"));
- ASSERT_THAT(storage->GetConfigCachePublic()->GetPersistentSections(), ElementsAre("01:02:03:ab:cd:ea"));
- ASSERT_THAT(
- storage->GetConfigCachePublic()->GetProperty(StorageModule::kAdapterSection, "Address"),
- Optional(StrEq("01:02:03:ab:cd:ef")));
-
- // Tear down
- test_registry.StopAll();
-
- // Verify states after test
- ASSERT_TRUE(std::filesystem::exists(temp_config_));
-
- // Verify config after test
- auto config = bluetooth::os::ReadSmallFile(temp_config_.string());
- ASSERT_TRUE(config);
- ASSERT_EQ(*config, kReadTestConfigCorrected);
-}
-
-TEST_F(StorageModuleTest, save_config_test) {
- // Prepare config file
- ASSERT_TRUE(bluetooth::os::WriteToFile(temp_config_.string(), kReadTestConfig));
-
- // Set up
- auto* storage = new TestStorageModule(temp_config_.string(), kTestConfigSaveDelay, 10, false, false);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&StorageModule::Factory, storage);
-
- // Test
- ASSERT_NE(storage->GetConfigCachePublic(), nullptr);
-
- // Change a property
- ASSERT_THAT(
- storage->GetConfigCachePublic()->GetProperty("01:02:03:ab:cd:ea", "name"), Optional(StrEq("hello world")));
- storage->GetConfigCachePublic()->SetProperty("01:02:03:ab:cd:ea", "name", "foo");
- ASSERT_THAT(storage->GetConfigCachePublic()->GetProperty("01:02:03:ab:cd:ea", "name"), Optional(StrEq("foo")));
- std::this_thread::sleep_for(kTestConfigSaveWaitDelay);
- auto config = LegacyConfigFile::FromPath(temp_config_.string()).Read(10);
- ASSERT_TRUE(config);
- ASSERT_THAT(config->GetProperty("01:02:03:ab:cd:ea", "name"), Optional(StrEq("foo")));
-
- // Remove a property
- storage->GetConfigCachePublic()->RemoveProperty("01:02:03:ab:cd:ea", "name");
- std::this_thread::sleep_for(kTestConfigSaveWaitDelay);
- config = LegacyConfigFile::FromPath(temp_config_.string()).Read(10);
- ASSERT_TRUE(config);
- ASSERT_FALSE(config->HasProperty("01:02:03:ab:cd:ea", "name"));
-
- // Remove a section
- storage->GetConfigCachePublic()->RemoveSection("01:02:03:ab:cd:ea");
- std::this_thread::sleep_for(kTestConfigSaveWaitDelay);
- config = LegacyConfigFile::FromPath(temp_config_.string()).Read(10);
- ASSERT_TRUE(config);
- ASSERT_FALSE(config->HasSection("01:02:03:ab:cd:ea"));
-
- // Add a section and save immediately
- storage->GetConfigCachePublic()->SetProperty("01:02:03:ab:cd:eb", "LinkKey", "123456");
- storage->SaveImmediatelyPublic();
- config = LegacyConfigFile::FromPath(temp_config_.string()).Read(10);
- ASSERT_TRUE(config);
- ASSERT_TRUE(config->HasSection("01:02:03:ab:cd:eb"));
-
- // Tear down
- test_registry.StopAll();
-
- // Verify states after test
- ASSERT_TRUE(std::filesystem::exists(temp_config_));
-}
-
-TEST_F(StorageModuleTest, get_bonded_devices_test) {
- // Prepare config file
- ASSERT_TRUE(bluetooth::os::WriteToFile(temp_config_.string(), kReadTestConfig));
-
- // Set up
- auto* storage = new TestStorageModule(temp_config_.string(), kTestConfigSaveDelay, 10, false, false);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&StorageModule::Factory, storage);
-
- ASSERT_THAT(
- storage->GetBondedDevices(),
- ElementsAre(
- Device(storage->GetConfigCachePublic(), storage->GetMemoryOnlyConfigCachePublic(), "01:02:03:ab:cd:ea")));
-
- // Tear down
- test_registry.StopAll();
-}
-
-TEST_F(StorageModuleTest, get_adapter_config_test) {
- // Prepare config file
- ASSERT_TRUE(bluetooth::os::WriteToFile(temp_config_.string(), kReadTestConfig));
-
- // Set up
- auto* storage = new TestStorageModule(temp_config_.string(), kTestConfigSaveDelay, 10, false, false);
- TestModuleRegistry test_registry;
- test_registry.InjectTestModule(&StorageModule::Factory, storage);
-
- auto address = Address::FromString("01:02:03:ab:cd:ef");
- ASSERT_TRUE(address);
- ASSERT_THAT(storage->GetAdapterConfig().GetAddress(), Optional(Eq(address)));
-
- // Tear down
- test_registry.StopAll();
-}
-
-} // namespace testing \ No newline at end of file
diff --git a/hci/Android.bp b/hci/Android.bp
index 350d0e7d1..3fd2fec95 100644
--- a/hci/Android.bp
+++ b/hci/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_defaults {
name: "libbt-hci_defaults",
defaults: ["fluoride_defaults"],
@@ -46,16 +37,7 @@ cc_library_static {
"system/bt/bta/include",
"system/bt/btif/include",
"system/libhwbinder/include",
- "system/bt/gd/rust/shim",
- ],
- product_variables: {
- debuggable: {
- cflags: [
- "-DBT_NET_DEBUG=true",
- ],
- },
- },
- host_supported: true,
+ ],
}
// HCI unit tests for target
@@ -75,7 +57,6 @@ cc_test {
"system/bt/stack/include",
"system/bt/utils/include",
"system/libhwbinder/include",
- "system/bt/gd/rust/shim",
],
srcs: [
"test/packet_fragmenter_test.cc",
@@ -93,7 +74,6 @@ cc_test {
"libcutils",
"libbtcore",
"libbt-protos-lite",
- "libbluetooth-for-tests",
],
}
@@ -102,11 +82,8 @@ cc_test {
cc_test {
name: "net_test_hci_native",
test_suites: ["device-tests"],
- defaults: ["fluoride_defaults"],
+ defaults: ["libbt-hci_defaults"],
host_supported: true,
- test_options: {
- unit_test: true,
- },
local_include_dirs: [
"include",
],
@@ -141,9 +118,6 @@ cc_test {
test_suites: ["device-tests"],
defaults: ["fluoride_defaults"],
host_supported: true,
- test_options: {
- unit_test: true,
- },
local_include_dirs: [
"include",
],
diff --git a/hci/BUILD.gn b/hci/BUILD.gn
index 951537542..e29e2569e 100644
--- a/hci/BUILD.gn
+++ b/hci/BUILD.gn
@@ -30,54 +30,47 @@ static_library("hci") {
include_dirs = [
"include",
- "//bt/",
- "//bt/internal_include",
- "//bt/bta/include",
- "//bt/btcore/include",
- "//bt/stack/include",
+ "//",
+ "//internal_include",
+ "//bta/include",
+ "//btcore/include",
+ "//stack/include",
]
deps = [
- "//bt/common",
- ]
-
- configs += [
- "//bt:target_defaults",
+ "//common",
+ "//third_party/libchrome:base",
]
}
-if (use.test) {
- executable("net_test_hci") {
- sources = [
- "//bt/osi/test/AllocationTestHarness.cc",
- "//bt/osi/test/AlarmTestHarness.cc",
- "test/packet_fragmenter_test.cc",
- ]
-
- include_dirs = [
- "//bt/",
- "//bt/internal_include",
- "//bt/btcore/include",
- "//bt/hci/include",
- "//bt/osi/test",
- "//bt/stack/include",
- ]
+executable("net_test_hci") {
+ testonly = true
+ sources = [
+ "//osi/test/AllocationTestHarness.cc",
+ "//osi/test/AlarmTestHarness.cc",
+ "test/packet_fragmenter_test.cc",
+ ]
- deps = [
- "//bt/hci",
- "//bt/osi",
- "//bt/btcore",
- ]
+ include_dirs = [
+ "//",
+ "//internal_include",
+ "//btcore/include",
+ "//hci/include",
+ "//osi/test",
+ "//stack/include",
+ ]
- configs += [
- "//bt:target_defaults",
- "//bt:external_gtest_main",
- ]
+ deps = [
+ "//hci",
+ "//osi",
+ "//btcore",
+ "//third_party/googletest:gtest_main",
+ "//third_party/libchrome:base",
+ ]
- libs = [
- "pthread",
- "rt",
- "dl",
- ]
- }
+ libs = [
+ "-lpthread",
+ "-lrt",
+ "-ldl",
+ ]
}
diff --git a/hci/include/bt_hci_bdroid.h b/hci/include/bt_hci_bdroid.h
index 6b3969ebb..110354f05 100644
--- a/hci/include/bt_hci_bdroid.h
+++ b/hci/include/bt_hci_bdroid.h
@@ -58,6 +58,7 @@ typedef enum {
#define MSG_HC_TO_STACK_HCI_ERR 0x1300 /* eq. BT_EVT_TO_BTU_HCIT_ERR */
#define MSG_HC_TO_STACK_HCI_ISO 0x1700 /* eq. BT_EVT_TO_BTU_HCI_ISO */
#define MSG_HC_TO_STACK_HCI_EVT 0x1000 /* eq. BT_EVT_TO_BTU_HCI_EVT */
+#define MSG_HC_TO_STACK_L2C_SEG_XMIT 0x1900 /* BT_EVT_TO_BTU_L2C_SEG_XMIT */
/* Message event ID passed from stack to vendor lib */
#define MSG_STACK_TO_HC_HCI_ACL 0x2100 /* eq. BT_EVT_TO_LM_HCI_ACL */
diff --git a/hci/include/btsnoop.h b/hci/include/btsnoop.h
index 3b195f714..476c62d90 100644
--- a/hci/include/btsnoop.h
+++ b/hci/include/btsnoop.h
@@ -30,17 +30,17 @@ typedef struct btsnoop_t {
// as outgoing.
void (*capture)(const BT_HDR* packet, bool is_received);
- // Set a L2CAP channel as allowlisted, allowing packets with that L2CAP CID
+ // Set a L2CAP channel as whitelisted, allowing packets with that L2CAP CID
// to show up in the snoop logs.
- void (*allowlist_l2c_channel)(uint16_t conn_handle, uint16_t local_cid,
+ void (*whitelist_l2c_channel)(uint16_t conn_handle, uint16_t local_cid,
uint16_t remote_cid);
- // Set a RFCOMM dlci as allowlisted, allowing packets with that RFCOMM CID
+ // Set a RFCOMM dlci as whitelisted, allowing packets with that RFCOMM CID
// to show up in the snoop logs. The local_cid is used to associate it with
// its corrisponding ACL connection. The dlci is the channel with direction
// so there is no chance of a collision if two services are using the same
// channel but in different directions.
- void (*allowlist_rfc_dlci)(uint16_t local_cid, uint8_t dlci);
+ void (*whitelist_rfc_dlci)(uint16_t local_cid, uint8_t dlci);
// Indicate that the provided L2CAP channel is being used for RFCOMM.
// If packets with the provided L2CAP CID are encountered, they will be
@@ -49,7 +49,7 @@ typedef struct btsnoop_t {
uint16_t remote_cid);
// Clear an L2CAP channel from being filtered.
- void (*clear_l2cap_allowlist)(uint16_t conn_handle, uint16_t local_cid,
+ void (*clear_l2cap_whitelist)(uint16_t conn_handle, uint16_t local_cid,
uint16_t remote_cid);
} btsnoop_t;
diff --git a/hci/include/btsnoop_mem.h b/hci/include/btsnoop_mem.h
index 1d78a6278..42c322987 100644
--- a/hci/include/btsnoop_mem.h
+++ b/hci/include/btsnoop_mem.h
@@ -27,17 +27,10 @@
typedef void (*btsnoop_data_cb)(const uint16_t type, const uint8_t* p_data,
const size_t len, const uint64_t timestamp_us);
-// Callback invoked for each HCI packet when activity attribution is enabled.
-typedef void (*activity_attribution_cb)(const uint16_t type,
- const uint8_t* p_data, const size_t len,
- const uint64_t timestamp_us);
-
// This call sets the (one and only) callback that will
// be invoked once for each HCI packet/event.
void btsnoop_mem_set_callback(btsnoop_data_cb cb);
-void activity_attribution_set_callback(activity_attribution_cb cb);
-
// This function is invoked every time an HCI packet
// is sent/received. Packets will be filtered and then
// forwarded to the |btsnoop_data_cb|.
diff --git a/hci/include/hci_internals.h b/hci/include/hci_internals.h
index 6363d3c77..bf9430fdb 100644
--- a/hci/include/hci_internals.h
+++ b/hci/include/hci_internals.h
@@ -26,33 +26,5 @@
#define HCI_SCO_PREAMBLE_SIZE 3
// 1 byte for event code, 1 byte for parameter length (Volume 2, Part E, 5.4.4)
#define HCI_EVENT_PREAMBLE_SIZE 2
-
-// ISO
// 2 bytes for handle, 2 bytes for data length (Volume 2, Part E, 5.4.5)
-#define HCI_ISO_PREAMBLE_SIZE 4
-
-#define HCI_ISO_BF_FIRST_FRAGMENTED_PACKET (0)
-#define HCI_ISO_BF_CONTINUATION_FRAGMENT_PACKET (1)
-#define HCI_ISO_BF_COMPLETE_PACKET (2)
-#define HCI_ISO_BF_LAST_FRAGMENT_PACKET (3)
-
-#define HCI_ISO_HEADER_TIMESTAMP_SIZE (4)
-#define HCI_ISO_HEADER_ISO_LEN_SIZE (2)
-#define HCI_ISO_HEADER_PACKET_SEQ_SIZE (2)
-
-#define HCI_ISO_HEADER_LEN_WITHOUT_TS \
- (HCI_ISO_HEADER_ISO_LEN_SIZE + HCI_ISO_HEADER_PACKET_SEQ_SIZE)
-#define HCI_ISO_HEADER_LEN_WITH_TS \
- (HCI_ISO_HEADER_LEN_WITHOUT_TS + HCI_ISO_HEADER_TIMESTAMP_SIZE)
-
-#define HCI_ISO_SET_CONTINUATION_FLAG(handle) \
- (((handle)&0x4FFF) | (0x0001 << 12))
-#define HCI_ISO_SET_COMPLETE_FLAG(handle) (((handle)&0x4FFF) | (0x0002 << 12))
-#define HCI_ISO_SET_END_FRAG_FLAG(handle) (((handle)&0x4FFF) | (0x0003 << 12))
-#define HCI_ISO_SET_TIMESTAMP_FLAG(handle) (((handle)&0x3FFF) | (0x0001 << 14))
-
-#define HCI_ISO_GET_TS_FLAG(handle) (((handle) >> 14) & 0x0001)
-#define HCI_ISO_GET_PACKET_STATUS_FLAGS(iso_sdu_length) \
- (iso_sdu_length & 0xC000)
-
-#define HCI_ISO_SDU_LENGTH_MASK 0x0FFF
+#define HCI_ISO_PREAMBLE_SIZE 4 \ No newline at end of file
diff --git a/hci/include/hci_layer.h b/hci/include/hci_layer.h
index 7ff89ee55..401e90a58 100644
--- a/hci/include/hci_layer.h
+++ b/hci/include/hci_layer.h
@@ -42,6 +42,7 @@ static const char HCI_MODULE[] = "hci_module";
#define MSG_HC_TO_STACK_HCI_ERR 0x1300 /* eq. BT_EVT_TO_BTU_HCIT_ERR */
#define MSG_HC_TO_STACK_HCI_ISO 0x1700 /* eq. BT_EVT_TO_BTU_HCI_ISO */
#define MSG_HC_TO_STACK_HCI_EVT 0x1000 /* eq. BT_EVT_TO_BTU_HCI_EVT */
+#define MSG_HC_TO_STACK_L2C_SEG_XMIT 0x1900 /* BT_EVT_TO_BTU_L2C_SEG_XMIT */
/* Message event ID passed from stack to vendor lib */
#define MSG_STACK_TO_HC_HCI_ACL 0x2100 /* eq. BT_EVT_TO_LM_HCI_ACL */
@@ -84,6 +85,11 @@ typedef struct hci_t {
void (*transmit_downward)(uint16_t type, void* data);
} hci_t;
+namespace bluetooth {
+namespace legacy {
+const hci_t* hci_layer_get_interface();
+} // namespace legacy
+} // namespace bluetooth
const hci_t* hci_layer_get_interface();
const hci_t* hci_layer_get_test_interface(
diff --git a/hci/include/hci_packet_factory.h b/hci/include/hci_packet_factory.h
index 129693939..e7cb47b0b 100644
--- a/hci/include/hci_packet_factory.h
+++ b/hci/include/hci_packet_factory.h
@@ -19,7 +19,7 @@
#pragma once
#include "bt_types.h"
-#include "btcore/include/event_mask.h"
+#include "event_mask.h"
typedef struct {
BT_HDR* (*make_reset)(void);
@@ -35,9 +35,8 @@ typedef struct {
BT_HDR* (*make_set_event_mask)(const bt_event_mask_t* event_mask);
BT_HDR* (*make_ble_write_host_support)(uint8_t supported_host,
uint8_t simultaneous_host);
- BT_HDR* (*make_ble_read_acceptlist_size)(void);
+ BT_HDR* (*make_ble_read_white_list_size)(void);
BT_HDR* (*make_ble_read_buffer_size)(void);
- BT_HDR* (*make_ble_read_buffer_size_v2)(void);
BT_HDR* (*make_ble_read_supported_states)(void);
BT_HDR* (*make_ble_read_local_supported_features)(void);
BT_HDR* (*make_ble_read_resolving_list_size)(void);
@@ -45,9 +44,7 @@ typedef struct {
BT_HDR* (*make_ble_read_maximum_data_length)(void);
BT_HDR* (*make_ble_read_maximum_advertising_data_length)(void);
BT_HDR* (*make_ble_read_number_of_supported_advertising_sets)(void);
- BT_HDR* (*make_ble_read_periodic_advertiser_list_size)(void);
BT_HDR* (*make_ble_set_event_mask)(const bt_event_mask_t* event_mask);
- BT_HDR* (*make_ble_set_host_features)(uint8_t bit_number, uint8_t bit_value);
BT_HDR* (*make_read_local_supported_codecs)(void);
} hci_packet_factory_t;
diff --git a/hci/include/hci_packet_parser.h b/hci/include/hci_packet_parser.h
index bef7e207a..8878cb968 100644
--- a/hci/include/hci_packet_parser.h
+++ b/hci/include/hci_packet_parser.h
@@ -21,10 +21,10 @@
#include <stdint.h>
#include "bt_types.h"
-#include "btcore/include/device_features.h"
-#include "btcore/include/version.h"
+#include "device_features.h"
#include "features.h"
#include "osi/include/allocator.h"
+#include "version.h"
typedef struct {
void (*parse_generic_command_complete)(BT_HDR* response);
@@ -47,17 +47,12 @@ typedef struct {
BT_HDR* response, uint8_t* page_number_ptr, uint8_t* max_page_number_ptr,
bt_device_features_t* feature_pages, size_t feature_pages_count);
- void (*parse_ble_read_acceptlist_size_response)(BT_HDR* response,
- uint8_t* acceptlist_size_ptr);
+ void (*parse_ble_read_white_list_size_response)(BT_HDR* response,
+ uint8_t* white_list_size_ptr);
void (*parse_ble_read_buffer_size_response)(BT_HDR* response,
uint16_t* data_size_ptr,
uint8_t* acl_buffer_count_ptr);
- void (*parse_ble_read_buffer_size_v2_response)(BT_HDR* response,
- uint16_t* acl_data_size_ptr,
- uint8_t* acl_buffer_count_ptr,
- uint16_t* iso_data_size_ptr,
- uint8_t* iso_buffer_count_ptr);
void (*parse_ble_read_supported_states_response)(
BT_HDR* response, uint8_t* supported_states,
@@ -84,9 +79,6 @@ typedef struct {
void (*parse_ble_read_number_of_supported_advertising_sets)(
BT_HDR* response, uint8_t* ble_number_of_supported_advertising_sets_ptr);
- void (*parse_ble_read_size_of_advertiser_list)(
- BT_HDR* response, uint8_t* ble_size_of_advertiser_list_ptr);
-
void (*parse_read_local_supported_codecs_response)(
BT_HDR* response, uint8_t* number_of_local_supported_codecs,
uint8_t* local_supported_codecs);
diff --git a/hci/src/btsnoop.cc b/hci/src/btsnoop.cc
index dadb7dd46..ad06ac7a0 100644
--- a/hci/src/btsnoop.cc
+++ b/hci/src/btsnoop.cc
@@ -51,7 +51,6 @@
#include "stack/include/rfcdefs.h"
#include "stack/l2cap/l2c_int.h"
#include "stack_config.h"
-#include "main/shim/shim.h"
// The number of of packets per btsnoop file before we rotate to the next
// file. As of right now there are two snoop files that are rotated through.
@@ -75,11 +74,10 @@ typedef enum {
kCommandPacket = 1,
kAclPacket = 2,
kScoPacket = 3,
- kEventPacket = 4,
- kIsoPacket = 5,
+ kEventPacket = 4
} packet_type_t;
-// Epoch in microseconds since 01/01/0000
+// Epoch in microseconds since 01/01/0000.
static const uint64_t BTSNOOP_EPOCH_DELTA = 0x00dcddb30f2f8000ULL;
// Number of bytes into a packet where you can find the value for a channel.
@@ -111,7 +109,7 @@ class FilterTracker {
uint16_t rfc_remote_cid = 0;
std::unordered_set<uint16_t> rfc_channels = {0};
- // Adds L2C channel to allowlist.
+ // Adds L2C channel to whitelist.
void addL2cCid(uint16_t local_cid, uint16_t remote_cid) {
l2c_local_cid.insert(local_cid);
l2c_remote_cid.insert(remote_cid);
@@ -123,7 +121,7 @@ class FilterTracker {
rfc_remote_cid = remote_cid;
}
- // Remove L2C channel from allowlist.
+ // Remove L2C channel from whitelist.
void removeL2cCid(uint16_t local_cid, uint16_t remote_cid) {
if (rfc_local_cid == local_cid) {
rfc_channels.clear();
@@ -138,7 +136,7 @@ class FilterTracker {
void addRfcDlci(uint8_t channel) { rfc_channels.insert(channel); }
- bool isAllowlistedL2c(bool local, uint16_t cid) {
+ bool isWhitelistedL2c(bool local, uint16_t cid) {
const auto& set = local ? l2c_local_cid : l2c_remote_cid;
return (set.find(cid) != set.end());
}
@@ -148,7 +146,7 @@ class FilterTracker {
return cid == channel;
}
- bool isAllowlistedDlci(uint8_t dlci) {
+ bool isWhitelistedDlci(uint8_t dlci) {
return rfc_channels.find(dlci) != rfc_channels.end();
}
};
@@ -283,21 +281,14 @@ static void capture(const BT_HDR* buffer, bool is_received) {
case MSG_STACK_TO_HC_HCI_CMD:
btsnoop_write_packet(kCommandPacket, p, true, timestamp_us);
break;
- case MSG_HC_TO_STACK_HCI_ISO:
- case MSG_STACK_TO_HC_HCI_ISO:
- btsnoop_write_packet(kIsoPacket, p, is_received, timestamp_us);
- break;
}
}
-static void allowlist_l2c_channel(uint16_t conn_handle, uint16_t local_cid,
+static void whitelist_l2c_channel(uint16_t conn_handle, uint16_t local_cid,
uint16_t remote_cid) {
LOG(INFO) << __func__
- << ": Allowlisting l2cap channel. conn_handle=" << conn_handle
+ << ": Whitelisting l2cap channel. conn_handle=" << conn_handle
<< " cid=" << loghex(local_cid) << ":" << loghex(remote_cid);
- if (bluetooth::shim::is_any_gd_enabled()) {
- return;
- }
std::lock_guard lock(filter_list_mutex);
// This will create the entry if there is no associated filter with the
@@ -305,17 +296,14 @@ static void allowlist_l2c_channel(uint16_t conn_handle, uint16_t local_cid,
filter_list[conn_handle].addL2cCid(local_cid, remote_cid);
}
-static void allowlist_rfc_dlci(uint16_t local_cid, uint8_t dlci) {
+static void whitelist_rfc_dlci(uint16_t local_cid, uint8_t dlci) {
LOG(INFO) << __func__
- << ": Allowlisting rfcomm channel. L2CAP CID=" << loghex(local_cid)
+ << ": Whitelisting rfcomm channel. L2CAP CID=" << loghex(local_cid)
<< " DLCI=" << loghex(dlci);
- if (bluetooth::shim::is_any_gd_enabled()) {
- return;
- }
std::lock_guard lock(filter_list_mutex);
tL2C_CCB* p_ccb = l2cu_find_ccb_by_cid(nullptr, local_cid);
- filter_list[p_ccb->p_lcb->Handle()].addRfcDlci(dlci);
+ filter_list[p_ccb->p_lcb->handle].addRfcDlci(dlci);
}
static void add_rfc_l2c_channel(uint16_t conn_handle, uint16_t local_cid,
@@ -324,31 +312,25 @@ static void add_rfc_l2c_channel(uint16_t conn_handle, uint16_t local_cid,
<< ": rfcomm data going over l2cap channel. conn_handle="
<< conn_handle << " cid=" << loghex(local_cid) << ":"
<< loghex(remote_cid);
- if (bluetooth::shim::is_any_gd_enabled()) {
- return;
- }
std::lock_guard lock(filter_list_mutex);
filter_list[conn_handle].setRfcCid(local_cid, remote_cid);
local_cid_to_acl.insert({local_cid, conn_handle});
}
-static void clear_l2cap_allowlist(uint16_t conn_handle, uint16_t local_cid,
+static void clear_l2cap_whitelist(uint16_t conn_handle, uint16_t local_cid,
uint16_t remote_cid) {
LOG(INFO) << __func__
- << ": Clearing acceptlist from l2cap channel. conn_handle="
+ << ": Clearing whitelist from l2cap channel. conn_handle="
<< conn_handle << " cid=" << local_cid << ":" << remote_cid;
- if (bluetooth::shim::is_any_gd_enabled()) {
- return;
- }
std::lock_guard lock(filter_list_mutex);
filter_list[conn_handle].removeL2cCid(local_cid, remote_cid);
}
-static const btsnoop_t interface = {capture, allowlist_l2c_channel,
- allowlist_rfc_dlci, add_rfc_l2c_channel,
- clear_l2cap_allowlist};
+static const btsnoop_t interface = {capture, whitelist_l2c_channel,
+ whitelist_rfc_dlci, add_rfc_l2c_channel,
+ clear_l2cap_whitelist};
const btsnoop_t* btsnoop_get_interface() { return &interface; }
@@ -398,7 +380,7 @@ static void open_next_snoop_file() {
return;
}
- (void)write(logfile_fd, "btsnoop\0\0\0\0\1\0\0\x3\xea", 16);
+ write(logfile_fd, "btsnoop\0\0\0\0\1\0\0\x3\xea", 16);
}
typedef struct {
@@ -435,10 +417,10 @@ static bool should_filter_log(bool is_received, uint8_t* packet) {
}
uint8_t rfc_dlci = packet[RFC_CHANNEL_OFFSET] >> 2;
- if (!filters.isAllowlistedDlci(rfc_dlci)) {
+ if (!filters.isWhitelistedDlci(rfc_dlci)) {
return true;
}
- } else if (!filters.isAllowlistedL2c(is_received, l2c_channel)) {
+ } else if (!filters.isWhitelistedL2c(is_received, l2c_channel)) {
return true;
}
@@ -467,23 +449,19 @@ static void btsnoop_write_packet(packet_type_t type, uint8_t* packet,
length_he = packet[1] + 3;
flags = 3;
break;
- case kIsoPacket:
- length_he = ((packet[3] & 0x3f) << 8) + packet[2] + 5;
- flags = is_received;
- break;
}
btsnoop_header_t header;
header.length_original = htonl(length_he);
- bool rejectlisted = false;
+ bool blacklisted = false;
if (is_btsnoop_filtered && type == kAclPacket) {
- rejectlisted = should_filter_log(is_received, packet);
+ blacklisted = should_filter_log(is_received, packet);
}
header.length_captured =
- rejectlisted ? htonl(L2C_HEADER_SIZE) : header.length_original;
- if (rejectlisted) length_he = L2C_HEADER_SIZE;
+ blacklisted ? htonl(L2C_HEADER_SIZE) : header.length_original;
+ if (blacklisted) length_he = L2C_HEADER_SIZE;
header.flags = htonl(flags);
header.dropped_packets = 0;
header.timestamp = htonll(timestamp_us + BTSNOOP_EPOCH_DELTA);
diff --git a/hci/src/btsnoop_mem.cc b/hci/src/btsnoop_mem.cc
index a13eae583..17ce248ba 100644
--- a/hci/src/btsnoop_mem.cc
+++ b/hci/src/btsnoop_mem.cc
@@ -18,20 +18,14 @@
#include <base/logging.h>
-#include "gd/common/init_flags.h"
#include "hci/include/btsnoop_mem.h"
static btsnoop_data_cb data_callback = NULL;
-static activity_attribution_cb attribution_callback = NULL;
void btsnoop_mem_set_callback(btsnoop_data_cb cb) { data_callback = cb; }
-void activity_attribution_set_callback(activity_attribution_cb cb) {
- attribution_callback = cb;
-}
-
void btsnoop_mem_capture(const BT_HDR* packet, uint64_t timestamp_us) {
- if (!data_callback && !attribution_callback) return;
+ if (!data_callback) return;
CHECK(packet);
@@ -57,17 +51,7 @@ void btsnoop_mem_capture(const BT_HDR* packet, uint64_t timestamp_us) {
case BT_EVT_TO_BTU_HCI_SCO:
if (packet->len > 2) length = data[2] + 3;
break;
-
- case BT_EVT_TO_LM_HCI_ISO:
- case BT_EVT_TO_BTU_HCI_ISO:
- if (packet->len > 3) length = (data[2] | ((data[3] & 0x3f) << 8)) + 4;
- break;
}
- if (length && data_callback)
- (*data_callback)(type, data, length, timestamp_us);
- if (length && attribution_callback &&
- bluetooth::common::init_flags::btaa_hci_is_enabled()) {
- (*attribution_callback)(type, data, length, timestamp_us);
- }
+ if (length) (*data_callback)(type, data, length, timestamp_us);
}
diff --git a/hci/src/btsnoop_net.cc b/hci/src/btsnoop_net.cc
index f72c0850b..d0756e67f 100644
--- a/hci/src/btsnoop_net.cc
+++ b/hci/src/btsnoop_net.cc
@@ -50,18 +50,19 @@ static int listen_socket_ = -1;
static int client_socket_ = -1;
void btsnoop_net_open() {
-#if (BT_NET_DEBUG != true)
+#if (BT_NET_DEBUG != TRUE)
return; // Disable using network sockets for security reasons
#endif
listen_thread_valid_ =
(pthread_create(&listen_thread_, NULL, listen_fn_, NULL) == 0);
if (!listen_thread_valid_)
- LOG_ERROR("%s pthread_create failed: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s pthread_create failed: %s", __func__,
+ strerror(errno));
}
void btsnoop_net_close() {
-#if (BT_NET_DEBUG != true)
+#if (BT_NET_DEBUG != TRUE)
return; // Disable using network sockets for security reasons
#endif
@@ -74,7 +75,7 @@ void btsnoop_net_close() {
}
void btsnoop_net_write(const void* data, size_t length) {
-#if (BT_NET_DEBUG != true)
+#if (BT_NET_DEBUG != TRUE)
return; // Disable using network sockets for security reasons
#endif
@@ -96,13 +97,15 @@ static void* listen_fn_(UNUSED_ATTR void* context) {
listen_socket_ = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (listen_socket_ == -1) {
- LOG_ERROR("%s socket creation failed: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s socket creation failed: %s", __func__,
+ strerror(errno));
goto cleanup;
}
if (setsockopt(listen_socket_, SOL_SOCKET, SO_REUSEADDR, &enable,
sizeof(enable)) == -1) {
- LOG_ERROR("%s unable to set SO_REUSEADDR: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to set SO_REUSEADDR: %s", __func__,
+ strerror(errno));
goto cleanup;
}
@@ -111,12 +114,13 @@ static void* listen_fn_(UNUSED_ATTR void* context) {
addr.sin_addr.s_addr = htonl(LOCALHOST_);
addr.sin_port = htons(LISTEN_PORT_);
if (bind(listen_socket_, (struct sockaddr*)&addr, sizeof(addr)) == -1) {
- LOG_ERROR("%s unable to bind listen socket: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to bind listen socket: %s", __func__,
+ strerror(errno));
goto cleanup;
}
if (listen(listen_socket_, 10) == -1) {
- LOG_ERROR("%s unable to listen: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to listen: %s", __func__, strerror(errno));
goto cleanup;
}
@@ -127,7 +131,8 @@ static void* listen_fn_(UNUSED_ATTR void* context) {
if (errno == EINVAL || errno == EBADF) {
break;
}
- LOG_WARN("%s error accepting socket: %s", __func__, strerror(errno));
+ LOG_WARN(LOG_TAG, "%s error accepting socket: %s", __func__,
+ strerror(errno));
continue;
}
diff --git a/hci/src/hci_inject.cc b/hci/src/hci_inject.cc
index 1c39c10ea..6d3e8e07b 100644
--- a/hci/src/hci_inject.cc
+++ b/hci/src/hci_inject.cc
@@ -66,7 +66,7 @@ static thread_t* thread;
static list_t* clients;
static bool hci_inject_open(const hci_t* hci_interface) {
-#if (BT_NET_DEBUG != true)
+#if (BT_NET_DEBUG != TRUE)
return true; // Disable using network sockets for security reasons
#endif
@@ -98,7 +98,7 @@ error:;
}
static void hci_inject_close(void) {
-#if (BT_NET_DEBUG != true)
+#if (BT_NET_DEBUG != TRUE)
return; // Disable using network sockets for security reasons
#endif
@@ -122,7 +122,7 @@ static int hci_packet_to_event(hci_packet_t packet) {
case HCI_PACKET_ISO_DATA:
return MSG_STACK_TO_HC_HCI_ISO;
default:
- LOG_ERROR("%s unsupported packet type: %d", __func__, packet);
+ LOG_ERROR(LOG_TAG, "%s unsupported packet type: %d", __func__, packet);
return -1;
}
}
@@ -139,7 +139,7 @@ static void accept_ready(socket_t* socket, UNUSED_ATTR void* context) {
client->socket = socket;
if (!list_append(clients, client)) {
- LOG_ERROR("%s unable to add client to list.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to add client to list.", __func__);
client_free(client);
return;
}
@@ -183,7 +183,7 @@ static void read_ready(UNUSED_ATTR socket_t* socket, void* context) {
memcpy(buf->data, buffer + 3, packet_len);
hci->transmit_downward(buf->event, buf);
} else {
- LOG_ERROR("%s dropping injected packet of length %zu", __func__,
+ LOG_ERROR(LOG_TAG, "%s dropping injected packet of length %zu", __func__,
packet_len);
}
diff --git a/hci/src/hci_layer.cc b/hci/src/hci_layer.cc
index 1cd3a49a3..77f0ffee2 100644
--- a/hci/src/hci_layer.cc
+++ b/hci/src/hci_layer.cc
@@ -42,7 +42,6 @@
#include "common/message_loop_thread.h"
#include "common/metrics.h"
#include "common/once_timer.h"
-#include "common/stop_watch_legacy.h"
#include "hci_inject.h"
#include "hci_internals.h"
#include "hcidefs.h"
@@ -59,7 +58,6 @@
using bluetooth::common::MessageLoopThread;
using bluetooth::common::OnceTimer;
-using bluetooth::common::StopWatchLegacy;
extern void hci_initialize();
extern void hci_transmit(BT_HDR* packet);
@@ -91,8 +89,8 @@ static const uint32_t COMMAND_PENDING_TIMEOUT_MS = 2000;
static const uint32_t COMMAND_PENDING_MUTEX_ACQUIRE_TIMEOUT_MS = 500;
static const uint32_t COMMAND_TIMEOUT_RESTART_MS = 5000;
static const uint32_t ROOT_INFLAMMED_RESTART_MS = 5000;
-[[maybe_unused]] constexpr int HCI_UNKNOWN_COMMAND_TIMED_OUT = 0x00ffffff;
-[[maybe_unused]] constexpr int HCI_STARTUP_TIMED_OUT = 0x00eeeeee;
+static const int HCI_UNKNOWN_COMMAND_TIMED_OUT = 0x00ffffff;
+static const int HCI_STARTUP_TIMED_OUT = 0x00eeeeee;
// Our interface
static bool interface_created;
@@ -182,13 +180,13 @@ void iso_data_received(BT_HDR* packet) {
void hal_service_died() {
if (abort_timer.IsScheduled()) {
- hci_timeout_abort();
+ if (root_inflamed_vendor_error_code != 0 || root_inflamed_error_code != 0) {
+ hci_root_inflamed_abort();
+ } else {
+ hci_timeout_abort();
+ }
return;
}
- // The Bluetooth hal suddenly died and no root inflammation packet received.
- // Record it with "Default" code.
- bluetooth::common::LogBluetoothHalCrashReason(
- RawAddress::kEmpty, 0x00 /*Default*/, 0x00 /*Default*/);
abort();
}
@@ -197,7 +195,7 @@ void hal_service_died() {
static future_t* hci_module_shut_down();
static future_t* hci_module_start_up(void) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
// The host is only allowed to send at most one command initially,
// as per the Bluetooth spec, Volume 2, Part E, 4.4 (Command Flow Control)
@@ -217,29 +215,30 @@ static future_t* hci_module_start_up(void) {
startup_timer = alarm_new("hci.startup_timer");
if (!startup_timer) {
- LOG_ERROR("%s unable to create startup timer.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to create startup timer.", __func__);
goto error;
}
command_response_timer = alarm_new("hci.command_response_timer");
if (!command_response_timer) {
- LOG_ERROR("%s unable to create command response timer.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to create command response timer.", __func__);
goto error;
}
hci_thread.StartUp();
if (!hci_thread.IsRunning()) {
- LOG_ERROR("%s unable to start thread.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to start thread.", __func__);
goto error;
}
if (!hci_thread.EnableRealTimeScheduling()) {
- LOG_ERROR("%s unable to make thread RT.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to make thread RT.", __func__);
goto error;
}
commands_pending_response = list_new(NULL);
if (!commands_pending_response) {
- LOG_ERROR("%s unable to create list for commands pending response.",
+ LOG_ERROR(LOG_TAG,
+ "%s unable to create list for commands pending response.",
__func__);
goto error;
}
@@ -254,7 +253,7 @@ static future_t* hci_module_start_up(void) {
hci_thread.DoInThread(FROM_HERE, base::Bind(&hci_initialize));
- LOG_INFO("%s starting async portion", __func__);
+ LOG_DEBUG(LOG_TAG, "%s starting async portion", __func__);
return local_startup_future;
error:
@@ -263,7 +262,7 @@ error:
}
static future_t* hci_module_shut_down() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
// Free the timers
{
@@ -354,7 +353,8 @@ static void transmit_downward(uint16_t type, void* data) {
if (type == MSG_STACK_TO_HC_HCI_CMD) {
// TODO(zachoverflow): eliminate this call
transmit_command((BT_HDR*)data, NULL, NULL, NULL);
- LOG_WARN("%s legacy transmit of command. Use transmit_command instead.",
+ LOG_WARN(LOG_TAG,
+ "%s legacy transmit of command. Use transmit_command instead.",
__func__);
} else {
enqueue_packet(data);
@@ -364,7 +364,7 @@ static void transmit_downward(uint16_t type, void* data) {
// Start up functions
static void event_finish_startup(UNUSED_ATTR void* context) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
std::lock_guard<std::recursive_timed_mutex> lock(
commands_pending_response_mutex);
alarm_cancel(startup_timer);
@@ -376,15 +376,13 @@ static void event_finish_startup(UNUSED_ATTR void* context) {
}
static void startup_timer_expired(UNUSED_ATTR void* context) {
- LOG_ERROR("%s", __func__);
-
- StopWatchLegacy::DumpStopWatchLog();
+ LOG_ERROR(LOG_TAG, "%s", __func__);
LOG_EVENT_INT(BT_HCI_TIMEOUT_TAG_NUM, HCI_STARTUP_TIMED_OUT);
hci_close();
if (abort_timer.IsScheduled()) {
- LOG_ERROR("%s: waiting for abort_timer", __func__);
+ LOG_ERROR(LOG_TAG, "%s: waiting for abort_timer", __func__);
return;
}
@@ -470,12 +468,7 @@ static void fragmenter_transmit_finished(BT_HDR* packet,
// Abort. The chip has had time to write any debugging information.
static void hci_timeout_abort(void) {
- if (root_inflamed_vendor_error_code != 0 || root_inflamed_error_code != 0) {
- hci_root_inflamed_abort();
- return;
- }
-
- LOG_ERROR("%s restarting the Bluetooth process.", __func__);
+ LOG_ERROR(LOG_TAG, "%s restarting the Bluetooth process.", __func__);
hci_close_firmware_log_file(hci_firmware_log_fd);
// We shouldn't try to recover the stack from this command timeout.
@@ -491,7 +484,7 @@ static void hci_root_inflamed_abort() {
}
static void command_timed_out_log_info(void* original_wait_entry) {
- LOG_ERROR("%s: %d commands pending response", __func__,
+ LOG_ERROR(LOG_TAG, "%s: %d commands pending response", __func__,
get_num_waiting_commands());
for (const list_node_t* node = list_begin(commands_pending_response);
@@ -503,18 +496,18 @@ static void command_timed_out_log_info(void* original_wait_entry) {
std::chrono::duration_cast<std::chrono::milliseconds>(
std::chrono::steady_clock::now() - wait_entry->timestamp)
.count();
- LOG_ERROR("%s: Waited %d ms for a response to opcode: 0x%x %s", __func__,
- wait_time_ms, wait_entry->opcode,
+ LOG_ERROR(LOG_TAG, "%s: Waited %d ms for a response to opcode: 0x%x %s",
+ __func__, wait_time_ms, wait_entry->opcode,
(wait_entry == original_wait_entry) ? "*matches timer*" : "");
// Dump the length field and the first byte of the payload, if present.
uint8_t* command = wait_entry->command->data + wait_entry->command->offset;
if (wait_entry->command->len > 3) {
- LOG_ERROR("%s: Size %d Hex %02x %02x %02x %02x", __func__,
+ LOG_ERROR(LOG_TAG, "%s: Size %d Hex %02x %02x %02x %02x", __func__,
wait_entry->command->len, command[0], command[1], command[2],
command[3]);
} else {
- LOG_ERROR("%s: Size %d Hex %02x %02x %02x", __func__,
+ LOG_ERROR(LOG_TAG, "%s: Size %d Hex %02x %02x %02x", __func__,
wait_entry->command->len, command[0], command[1], command[2]);
}
@@ -525,13 +518,12 @@ static void command_timed_out_log_info(void* original_wait_entry) {
// Print debugging information and quit. Don't dereference original_wait_entry.
static void command_timed_out(void* original_wait_entry) {
- LOG_ERROR("%s", __func__);
- StopWatchLegacy::DumpStopWatchLog();
+ LOG_ERROR(LOG_TAG, "%s", __func__);
std::unique_lock<std::recursive_timed_mutex> lock(
commands_pending_response_mutex, std::defer_lock);
if (!lock.try_lock_for(std::chrono::milliseconds(
COMMAND_PENDING_MUTEX_ACQUIRE_TIMEOUT_MS))) {
- LOG_ERROR("%s: Cannot obtain the mutex", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Cannot obtain the mutex", __func__);
LOG_EVENT_INT(BT_HCI_TIMEOUT_TAG_NUM, HCI_UNKNOWN_COMMAND_TIMED_OUT);
bluetooth::common::LogHciTimeoutEvent(android::bluetooth::hci::CMD_UNKNOWN);
} else {
@@ -544,7 +536,7 @@ static void command_timed_out(void* original_wait_entry) {
return;
}
- LOG_ERROR("%s: requesting a firmware dump.", __func__);
+ LOG_ERROR(LOG_TAG, "%s: requesting a firmware dump.", __func__);
/* Allocate a buffer to hold the HCI command. */
BT_HDR* bt_hdr =
@@ -564,13 +556,13 @@ static void command_timed_out(void* original_wait_entry) {
transmit_fragment(bt_hdr, true);
osi_free(bt_hdr);
- LOG_ERROR("%s: Setting a timer to restart.", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Setting a timer to restart.", __func__);
// alarm_default_callbacks thread post to hci_thread.
if (!abort_timer.Schedule(
hci_thread.GetWeakPtr(), FROM_HERE, base::Bind(hci_timeout_abort),
base::TimeDelta::FromMilliseconds(COMMAND_TIMEOUT_RESTART_MS))) {
- LOG_ERROR("%s unable to create an abort timer.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to create an abort timer.", __func__);
abort();
}
}
@@ -601,14 +593,9 @@ bool hci_is_root_inflammation_event_received() {
}
void handle_root_inflammation_event() {
- LOG(ERROR)
- << __func__
- << ": Root inflammation event! setting timer to restart. error_code: "
- << loghex(root_inflamed_error_code)
- << " vendor _error_code: " << loghex(root_inflamed_vendor_error_code);
- bluetooth::common::LogBluetoothHalCrashReason(
- RawAddress::kEmpty, root_inflamed_error_code,
- root_inflamed_vendor_error_code);
+ LOG(ERROR) << __func__
+ << ": Root inflammation event! setting timer to restart.";
+ // TODO(ugoyu) Report to bluetooth metrics here
{
// Try to stop hci command and startup timers
std::unique_lock<std::recursive_timed_mutex> lock(
@@ -668,10 +655,10 @@ static bool filter_incoming_event(BT_HDR* packet) {
if (!wait_entry) {
if (opcode != HCI_COMMAND_NONE) {
- LOG_WARN(
- "%s command complete event with no matching command (opcode: "
- "0x%04x).",
- __func__, opcode);
+ LOG_WARN(LOG_TAG,
+ "%s command complete event with no matching command (opcode: "
+ "0x%04x).",
+ __func__, opcode);
}
} else {
update_command_response_timer();
@@ -685,8 +672,6 @@ static bool filter_incoming_event(BT_HDR* packet) {
goto intercepted;
} else if (event_code == HCI_COMMAND_STATUS_EVT) {
if (length < (sizeof(uint8_t) + sizeof(uint8_t) + sizeof(uint16_t))) {
- LOG_WARN("%s Unexpected hci command status event length:%hhd", __func__,
- length);
goto intercepted;
}
uint8_t status;
@@ -702,6 +687,7 @@ static bool filter_incoming_event(BT_HDR* packet) {
if (!wait_entry) {
LOG_WARN(
+ LOG_TAG,
"%s command status event with no matching command. opcode: 0x%04x",
__func__, opcode);
} else {
@@ -891,7 +877,15 @@ const hci_t* hci_layer_get_interface();
} // namespace shim
} // namespace bluetooth
-const hci_t* hci_layer_get_interface_legacy() {
+const hci_t* hci_layer_get_interface() {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::hci_layer_get_interface();
+ } else {
+ return bluetooth::legacy::hci_layer_get_interface();
+ }
+}
+
+const hci_t* bluetooth::legacy::hci_layer_get_interface() {
buffer_allocator = buffer_allocator_get_interface();
btsnoop = btsnoop_get_interface();
packet_fragmenter = packet_fragmenter_get_interface();
@@ -901,14 +895,6 @@ const hci_t* hci_layer_get_interface_legacy() {
return &interface;
}
-const hci_t* hci_layer_get_interface() {
- if (bluetooth::shim::is_gd_hci_enabled()) {
- return bluetooth::shim::hci_layer_get_interface();
- } else {
- return hci_layer_get_interface_legacy();
- }
-}
-
const hci_t* hci_layer_get_test_interface(
const allocator_t* buffer_allocator_interface,
const btsnoop_t* btsnoop_interface,
diff --git a/hci/src/hci_layer_android.cc b/hci/src/hci_layer_android.cc
index bba7834cd..d86a79bb2 100644
--- a/hci/src/hci_layer_android.cc
+++ b/hci/src/hci_layer_android.cc
@@ -20,35 +20,32 @@
#include "hci_layer.h"
-#include <iomanip>
-
#include <fcntl.h>
#include <sys/stat.h>
#include <sys/types.h>
+#include <base/location.h>
+#include <base/logging.h>
+#include "buffer_allocator.h"
+#include "osi/include/log.h"
+
#include <android/hardware/bluetooth/1.0/IBluetoothHci.h>
#include <android/hardware/bluetooth/1.0/IBluetoothHciCallbacks.h>
#include <android/hardware/bluetooth/1.0/types.h>
#include <android/hardware/bluetooth/1.1/IBluetoothHci.h>
#include <android/hardware/bluetooth/1.1/IBluetoothHciCallbacks.h>
-
-#include <base/location.h>
-#include <base/logging.h>
-
-#include "buffer_allocator.h"
-#include "common/stop_watch_legacy.h"
-#include "osi/include/log.h"
+#include <hwbinder/ProcessState.h>
#define LOG_PATH "/data/misc/bluetooth/logs/firmware_events.log"
#define LAST_LOG_PATH "/data/misc/bluetooth/logs/firmware_events.log.last"
using ::android::hardware::hidl_death_recipient;
using ::android::hardware::hidl_vec;
+using ::android::hardware::ProcessState;
using ::android::hardware::Return;
using ::android::hardware::Void;
using ::android::hardware::bluetooth::V1_0::HciPacket;
using ::android::hardware::bluetooth::V1_0::Status;
-using ::bluetooth::common::StopWatchLegacy;
using namespace ::android::hardware::bluetooth;
@@ -63,27 +60,10 @@ extern bool hci_is_root_inflammation_event_received();
android::sp<V1_0::IBluetoothHci> btHci;
android::sp<V1_1::IBluetoothHci> btHci_1_1;
-std::string GetTimerText(std::string func_name, const hidl_vec<uint8_t>& vec) {
- std::stringstream ss;
- const unsigned char* vec_char =
- reinterpret_cast<const unsigned char*>(vec.data());
- int length = 5;
- if ((int)vec.size() < 5) {
- length = vec.size();
- }
- for (int i = 0; i < length; i++) {
- ss << std::setw(2) << std::setfill('0') << std::hex << (int)vec_char[i];
- }
- std::string text = func_name + ": len " + std::to_string(vec.size()) +
- ", 1st 5 bytes '" + ss.str() + "'";
- return text;
-}
-
class BluetoothHciDeathRecipient : public hidl_death_recipient {
public:
virtual void serviceDied(uint64_t /*cookie*/, const android::wp<::android::hidl::base::V1_0::IBase>& /*who*/) {
- LOG_ERROR("Bluetooth HAL service died!");
- StopWatchLegacy::DumpStopWatchLog();
+ LOG_ERROR(LOG_TAG, "Bluetooth HAL service died!");
hal_service_died();
}
};
@@ -110,11 +90,11 @@ class BluetoothHciCallbacks : public V1_1::IBluetoothHciCallbacks {
}
Return<void> initializationComplete(Status status) override {
- StopWatchLegacy(__func__);
if (hci_is_root_inflammation_event_received()) {
// Ignore the initializationComplete here as we have already received
// root inflammation event earlier.
LOG_ERROR(
+ LOG_TAG,
"initializationComplete after root inflammation event! status=%d",
status);
return Void();
@@ -125,28 +105,24 @@ class BluetoothHciCallbacks : public V1_1::IBluetoothHciCallbacks {
}
Return<void> hciEventReceived(const hidl_vec<uint8_t>& event) override {
- StopWatchLegacy(GetTimerText(__func__, event));
BT_HDR* packet = WrapPacketAndCopy(MSG_HC_TO_STACK_HCI_EVT, event);
hci_event_received(FROM_HERE, packet);
return Void();
}
Return<void> aclDataReceived(const hidl_vec<uint8_t>& data) override {
- StopWatchLegacy(GetTimerText(__func__, data));
BT_HDR* packet = WrapPacketAndCopy(MSG_HC_TO_STACK_HCI_ACL, data);
acl_event_received(packet);
return Void();
}
Return<void> scoDataReceived(const hidl_vec<uint8_t>& data) override {
- StopWatchLegacy(GetTimerText(__func__, data));
BT_HDR* packet = WrapPacketAndCopy(MSG_HC_TO_STACK_HCI_SCO, data);
sco_data_received(packet);
return Void();
}
Return<void> isoDataReceived(const hidl_vec<uint8_t>& data) override {
- StopWatchLegacy(GetTimerText(__func__, data));
BT_HDR* packet = WrapPacketAndCopy(MSG_HC_TO_STACK_HCI_ISO, data);
iso_data_received(packet);
return Void();
@@ -156,7 +132,7 @@ class BluetoothHciCallbacks : public V1_1::IBluetoothHciCallbacks {
};
void hci_initialize() {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
btHci_1_1 = V1_1::IBluetoothHci::getService();
@@ -170,12 +146,11 @@ void hci_initialize() {
CHECK(btHci != nullptr);
auto death_link = btHci->linkToDeath(bluetoothHciDeathRecipient, 0);
if (!death_link.isOk()) {
- LOG_ERROR("%s: Unable to set the death recipient for the Bluetooth HAL",
- __func__);
+ LOG_ERROR(LOG_TAG, "%s: Unable to set the death recipient for the Bluetooth HAL", __func__);
abort();
}
- LOG_INFO("%s: IBluetoothHci::getService() returned %p (%s)", __func__,
- btHci.get(), (btHci->isRemote() ? "remote" : "local"));
+ LOG_INFO(LOG_TAG, "%s: IBluetoothHci::getService() returned %p (%s)",
+ __func__, btHci.get(), (btHci->isRemote() ? "remote" : "local"));
// Block allows allocation of a variable that might be bypassed by goto.
{
@@ -193,12 +168,11 @@ void hci_close() {
if (btHci != nullptr) {
auto death_unlink = btHci->unlinkToDeath(bluetoothHciDeathRecipient);
if (!death_unlink.isOk()) {
- LOG_ERROR("%s: Error unlinking death recipient from the Bluetooth HAL",
- __func__);
+ LOG_ERROR(LOG_TAG, "%s: Error unlinking death recipient from the Bluetooth HAL", __func__);
}
auto close_status = btHci->close();
if (!close_status.isOk()) {
- LOG_ERROR("%s: Error closing the Bluetooth HAL", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Error closing the Bluetooth HAL", __func__);
}
btHci = nullptr;
}
@@ -223,19 +197,19 @@ void hci_transmit(BT_HDR* packet) {
if (btHci_1_1 != nullptr) {
btHci_1_1->sendIsoData(data);
} else {
- LOG_ERROR("ISO is not supported in HAL v1.0");
+ LOG_ERROR(LOG_TAG, "ISO is not supported in HAL v1.0");
}
break;
default:
- LOG_ERROR("Unknown packet type (%d)", event);
+ LOG_ERROR(LOG_TAG, "Unknown packet type (%d)", event);
break;
}
}
int hci_open_firmware_log_file() {
if (rename(LOG_PATH, LAST_LOG_PATH) == -1 && errno != ENOENT) {
- LOG_ERROR("%s unable to rename '%s' to '%s': %s", __func__, LOG_PATH,
- LAST_LOG_PATH, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to rename '%s' to '%s': %s", __func__,
+ LOG_PATH, LAST_LOG_PATH, strerror(errno));
}
mode_t prevmask = umask(0);
@@ -243,7 +217,7 @@ int hci_open_firmware_log_file() {
S_IRUSR | S_IWUSR | S_IRGRP | S_IWGRP | S_IROTH);
umask(prevmask);
if (logfile_fd == INVALID_FD) {
- LOG_ERROR("%s unable to open '%s': %s", __func__, LOG_PATH,
+ LOG_ERROR(LOG_TAG, "%s unable to open '%s': %s", __func__, LOG_PATH,
strerror(errno));
}
diff --git a/hci/src/hci_packet_factory.cc b/hci/src/hci_packet_factory.cc
index d2c5749e2..ca0fb5fa6 100644
--- a/hci/src/hci_packet_factory.cc
+++ b/hci/src/hci_packet_factory.cc
@@ -118,18 +118,14 @@ static BT_HDR* make_ble_write_host_support(uint8_t supported_host,
return packet;
}
-static BT_HDR* make_ble_read_acceptlist_size(void) {
- return make_command_no_params(HCI_BLE_READ_ACCEPTLIST_SIZE);
+static BT_HDR* make_ble_read_white_list_size(void) {
+ return make_command_no_params(HCI_BLE_READ_WHITE_LIST_SIZE);
}
static BT_HDR* make_ble_read_buffer_size(void) {
return make_command_no_params(HCI_BLE_READ_BUFFER_SIZE);
}
-static BT_HDR* make_ble_read_buffer_size_v2(void) {
- return make_command_no_params(HCI_BLE_READ_BUFFER_SIZE_V2);
-}
-
static BT_HDR* make_ble_read_supported_states(void) {
return make_command_no_params(HCI_BLE_READ_SUPPORTED_STATES);
}
@@ -159,10 +155,6 @@ static BT_HDR* make_ble_read_number_of_supported_advertising_sets(void) {
HCI_LE_READ_NUMBER_OF_SUPPORTED_ADVERTISING_SETS);
}
-static BT_HDR* make_ble_read_periodic_advertiser_list_size(void) {
- return make_command_no_params(HCI_BLE_READ_PERIODIC_ADVERTISER_LIST_SIZE);
-}
-
static BT_HDR* make_read_local_supported_codecs(void) {
return make_command_no_params(HCI_READ_LOCAL_SUPPORTED_CODECS);
}
@@ -177,19 +169,6 @@ static BT_HDR* make_ble_set_event_mask(const bt_event_mask_t* event_mask) {
return packet;
}
-static BT_HDR* make_ble_set_host_features(uint8_t bit_number,
- uint8_t bit_value) {
- uint8_t* stream;
- uint8_t parameter_size = sizeof(bit_number) + sizeof(bit_value);
- BT_HDR* packet =
- make_command(HCI_LE_SET_HOST_FEATURE, parameter_size, &stream);
-
- UINT8_TO_STREAM(stream, bit_number);
- UINT8_TO_STREAM(stream, bit_value);
-
- return packet;
-}
-
// Internal functions
static BT_HDR* make_command_no_params(uint16_t opcode) {
@@ -231,9 +210,8 @@ static const hci_packet_factory_t interface = {
make_write_secure_connections_host_support,
make_set_event_mask,
make_ble_write_host_support,
- make_ble_read_acceptlist_size,
+ make_ble_read_white_list_size,
make_ble_read_buffer_size,
- make_ble_read_buffer_size_v2,
make_ble_read_supported_states,
make_ble_read_local_supported_features,
make_ble_read_resolving_list_size,
@@ -241,9 +219,7 @@ static const hci_packet_factory_t interface = {
make_ble_read_maximum_data_length,
make_ble_read_maximum_advertising_data_length,
make_ble_read_number_of_supported_advertising_sets,
- make_ble_read_periodic_advertiser_list_size,
make_ble_set_event_mask,
- make_ble_set_host_features,
make_read_local_supported_codecs};
const hci_packet_factory_t* hci_packet_factory_get_interface() {
diff --git a/hci/src/hci_packet_parser.cc b/hci/src/hci_packet_parser.cc
index 6bd6a5233..b1efd444d 100644
--- a/hci/src/hci_packet_parser.cc
+++ b/hci/src/hci_packet_parser.cc
@@ -126,12 +126,12 @@ static void parse_read_local_extended_features_response(
buffer_allocator->free(response);
}
-static void parse_ble_read_acceptlist_size_response(
- BT_HDR* response, uint8_t* acceptlist_size_ptr) {
+static void parse_ble_read_white_list_size_response(
+ BT_HDR* response, uint8_t* white_list_size_ptr) {
uint8_t* stream = read_command_complete_header(
- response, HCI_BLE_READ_ACCEPTLIST_SIZE, 1 /* byte after */);
+ response, HCI_BLE_READ_WHITE_LIST_SIZE, 1 /* byte after */);
CHECK(stream != NULL);
- STREAM_TO_UINT8(*acceptlist_size_ptr, stream);
+ STREAM_TO_UINT8(*white_list_size_ptr, stream);
buffer_allocator->free(response);
}
@@ -148,21 +148,6 @@ static void parse_ble_read_buffer_size_response(BT_HDR* response,
buffer_allocator->free(response);
}
-static void parse_ble_read_buffer_size_v2_response(
- BT_HDR* response, uint16_t* acl_data_size_ptr,
- uint8_t* acl_buffer_count_ptr, uint16_t* iso_data_size_ptr,
- uint8_t* iso_buffer_count_ptr) {
- uint8_t* stream = read_command_complete_header(
- response, HCI_BLE_READ_BUFFER_SIZE_V2, 6 /* bytes after */);
- CHECK(stream != NULL);
- STREAM_TO_UINT16(*acl_data_size_ptr, stream);
- STREAM_TO_UINT8(*acl_buffer_count_ptr, stream);
- STREAM_TO_UINT16(*iso_data_size_ptr, stream);
- STREAM_TO_UINT8(*iso_buffer_count_ptr, stream);
-
- buffer_allocator->free(response);
-}
-
static void parse_ble_read_supported_states_response(
BT_HDR* response, uint8_t* supported_states, size_t supported_states_size) {
uint8_t* stream =
@@ -190,9 +175,8 @@ static void parse_ble_read_resolving_list_size_response(
BT_HDR* response, uint8_t* resolving_list_size_ptr) {
uint8_t* stream = read_command_complete_header(
response, HCI_BLE_READ_RESOLVING_LIST_SIZE, 1 /* bytes after */);
- if (stream) {
- STREAM_TO_UINT8(*resolving_list_size_ptr, stream);
- }
+ STREAM_TO_UINT8(*resolving_list_size_ptr, stream);
+
buffer_allocator->free(response);
}
@@ -200,9 +184,8 @@ static void parse_ble_read_suggested_default_data_length_response(
BT_HDR* response, uint16_t* ble_default_packet_length_ptr) {
uint8_t* stream = read_command_complete_header(
response, HCI_BLE_READ_DEFAULT_DATA_LENGTH, 2 /* bytes after */);
- if (stream) {
- STREAM_TO_UINT16(*ble_default_packet_length_ptr, stream);
- }
+ STREAM_TO_UINT16(*ble_default_packet_length_ptr, stream);
+
buffer_allocator->free(response);
}
@@ -212,12 +195,11 @@ static void parse_ble_read_maximum_data_length_response(
uint16_t* ble_supported_max_rx_time) {
uint8_t* stream = read_command_complete_header(
response, HCI_BLE_READ_MAXIMUM_DATA_LENGTH, 8 /* bytes after */);
- if (stream) {
- STREAM_TO_UINT16(*ble_supported_max_tx_octets, stream);
- STREAM_TO_UINT16(*ble_supported_max_tx_time, stream);
- STREAM_TO_UINT16(*ble_supported_max_rx_octets, stream);
- STREAM_TO_UINT16(*ble_supported_max_rx_time, stream);
- }
+ STREAM_TO_UINT16(*ble_supported_max_tx_octets, stream);
+ STREAM_TO_UINT16(*ble_supported_max_tx_time, stream);
+ STREAM_TO_UINT16(*ble_supported_max_rx_octets, stream);
+ STREAM_TO_UINT16(*ble_supported_max_rx_time, stream);
+
buffer_allocator->free(response);
}
@@ -226,9 +208,8 @@ static void parse_ble_read_maximum_advertising_data_length(
uint8_t* stream = read_command_complete_header(
response, HCI_LE_READ_MAXIMUM_ADVERTISING_DATA_LENGTH,
2 /* bytes after */);
- if (stream) {
- STREAM_TO_UINT16(*ble_maximum_advertising_data_length_ptr, stream);
- }
+ STREAM_TO_UINT16(*ble_maximum_advertising_data_length_ptr, stream);
+
buffer_allocator->free(response);
}
@@ -237,20 +218,8 @@ static void parse_ble_read_number_of_supported_advertising_sets(
uint8_t* stream = read_command_complete_header(
response, HCI_LE_READ_NUMBER_OF_SUPPORTED_ADVERTISING_SETS,
1 /* bytes after */);
- if (stream) {
- STREAM_TO_UINT8(*ble_number_of_supported_advertising_sets_ptr, stream);
- }
- buffer_allocator->free(response);
-}
+ STREAM_TO_UINT8(*ble_number_of_supported_advertising_sets_ptr, stream);
-static void parse_ble_read_size_of_advertiser_list(
- BT_HDR* response, uint8_t* ble_size_of_advertiser_list_ptr) {
- uint8_t* stream = read_command_complete_header(
- response, HCI_BLE_READ_PERIODIC_ADVERTISER_LIST_SIZE,
- 1 /* bytes after */);
- if (stream) {
- STREAM_TO_UINT8(*ble_size_of_advertiser_list_ptr, stream);
- }
buffer_allocator->free(response);
}
@@ -289,7 +258,7 @@ static uint8_t* read_command_complete_header(BT_HDR* response,
STREAM_TO_UINT8(status, stream);
if (status != HCI_SUCCESS) {
- LOG_ERROR("%s: return status - 0x%x", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s: return status - 0x%x", __func__, status);
return NULL;
}
@@ -303,9 +272,8 @@ static const hci_packet_parser_t interface = {
parse_read_bd_addr_response,
parse_read_local_supported_commands_response,
parse_read_local_extended_features_response,
- parse_ble_read_acceptlist_size_response,
+ parse_ble_read_white_list_size_response,
parse_ble_read_buffer_size_response,
- parse_ble_read_buffer_size_v2_response,
parse_ble_read_supported_states_response,
parse_ble_read_local_supported_features_response,
parse_ble_read_resolving_list_size_response,
@@ -313,7 +281,6 @@ static const hci_packet_parser_t interface = {
parse_ble_read_maximum_data_length_response,
parse_ble_read_maximum_advertising_data_length,
parse_ble_read_number_of_supported_advertising_sets,
- parse_ble_read_size_of_advertiser_list,
parse_read_local_supported_codecs_response};
const hci_packet_parser_t* hci_packet_parser_get_interface() {
diff --git a/hci/src/packet_fragmenter.cc b/hci/src/packet_fragmenter.cc
index a7074d5af..4c235aee0 100644
--- a/hci/src/packet_fragmenter.cc
+++ b/hci/src/packet_fragmenter.cc
@@ -39,6 +39,7 @@
#define HANDLE_MASK 0x0FFF
#define START_PACKET_BOUNDARY 2
+#define CONTINUATION_PACKET_BOUNDARY 1
#define POINT_TO_POINT 0
#define L2CAP_HEADER_PDU_LEN_SIZE 2
#define L2CAP_HEADER_CID_SIZE 2
@@ -51,39 +52,25 @@ static const controller_t* controller;
static const packet_fragmenter_callbacks_t* callbacks;
static std::unordered_map<uint16_t /* handle */, BT_HDR*> partial_packets;
-static std::unordered_map<uint16_t /* handle */, BT_HDR*> partial_iso_packets;
static void init(const packet_fragmenter_callbacks_t* result_callbacks) {
callbacks = result_callbacks;
}
-static void cleanup() {
- partial_packets.clear();
- partial_iso_packets.clear();
-}
-
-static bool check_uint16_overflow(uint16_t a, uint16_t b) {
- return (UINT16_MAX - a) < b;
-}
-
-static void fragment_and_dispatch_acl(BT_HDR* packet);
-static void fragment_and_dispatch_iso(BT_HDR* packet);
+static void cleanup() { partial_packets.clear(); }
static void fragment_and_dispatch(BT_HDR* packet) {
CHECK(packet != NULL);
uint16_t event = packet->event & MSG_EVT_MASK;
+ uint8_t* stream = packet->data + packet->offset;
- if (event == MSG_STACK_TO_HC_HCI_ACL) {
- fragment_and_dispatch_acl(packet);
- } else if (event == MSG_STACK_TO_HC_HCI_ISO) {
- fragment_and_dispatch_iso(packet);
- } else {
+ // We only fragment ACL packets
+ if (event != MSG_STACK_TO_HC_HCI_ACL) {
callbacks->fragmented(packet, true);
+ return;
}
-}
-static void fragment_and_dispatch_acl(BT_HDR* packet) {
uint16_t max_data_size =
SUB_EVENT(packet->event) == LOCAL_BR_EDR_CONTROLLER_ID
? controller->get_acl_data_size_classic()
@@ -92,8 +79,6 @@ static void fragment_and_dispatch_acl(BT_HDR* packet) {
uint16_t max_packet_size = max_data_size + HCI_ACL_PREAMBLE_SIZE;
uint16_t remaining_length = packet->len;
- uint8_t* stream = packet->data + packet->offset;
-
uint16_t continuation_handle;
STREAM_TO_UINT16(continuation_handle, stream);
continuation_handle = APPLY_CONTINUATION_FLAG(continuation_handle);
@@ -122,7 +107,7 @@ static void fragment_and_dispatch_acl(BT_HDR* packet) {
packet->layer_specific--;
if (packet->layer_specific == 0) {
- packet->event = BT_EVT_TO_BTU_L2C_SEG_XMIT;
+ packet->event = MSG_HC_TO_STACK_L2C_SEG_XMIT;
callbacks->transmit_finished(packet, false);
return;
}
@@ -132,230 +117,8 @@ static void fragment_and_dispatch_acl(BT_HDR* packet) {
callbacks->fragmented(packet, true);
}
-static void fragment_and_dispatch_iso(BT_HDR* packet) {
- uint8_t* stream = packet->data + packet->offset;
- uint16_t max_data_size = controller->get_iso_data_size();
- uint16_t max_packet_size = max_data_size + HCI_ISO_PREAMBLE_SIZE;
- uint16_t remaining_length = packet->len;
-
- uint16_t handle;
- STREAM_TO_UINT16(handle, stream);
-
- if (packet->layer_specific & BT_ISO_HDR_CONTAINS_TS) {
- // First packet might have timestamp
- handle = HCI_ISO_SET_TIMESTAMP_FLAG(handle);
- }
-
- if (remaining_length <= max_packet_size) {
- stream = packet->data + packet->offset;
- UINT16_TO_STREAM(stream, HCI_ISO_SET_COMPLETE_FLAG(handle));
- } else {
- while (remaining_length > max_packet_size) {
- // Make sure we use the right ISO packet size
- stream = packet->data + packet->offset;
- STREAM_SKIP_UINT16(stream);
- UINT16_TO_STREAM(stream, max_data_size);
-
- packet->len = max_packet_size;
- callbacks->fragmented(packet, false);
-
- packet->offset += max_data_size;
- remaining_length -= max_data_size;
- packet->len = remaining_length;
-
- // Write the ISO header for the next fragment
- stream = packet->data + packet->offset;
- if (remaining_length > max_packet_size) {
- UINT16_TO_STREAM(stream,
- HCI_ISO_SET_CONTINUATION_FLAG(handle & HANDLE_MASK));
- } else {
- UINT16_TO_STREAM(stream,
- HCI_ISO_SET_END_FRAG_FLAG(handle & HANDLE_MASK));
- }
- UINT16_TO_STREAM(stream, remaining_length - HCI_ISO_PREAMBLE_SIZE);
- }
- }
- callbacks->fragmented(packet, true);
-}
-
-static void reassemble_and_dispatch_iso(UNUSED_ATTR BT_HDR* packet) {
- uint8_t* stream = packet->data;
- uint16_t handle;
- uint16_t iso_length;
- uint8_t iso_hdr_len = HCI_ISO_HEADER_LEN_WITHOUT_TS;
- BT_HDR* partial_packet;
- uint16_t iso_full_len;
-
- STREAM_TO_UINT16(handle, stream);
- STREAM_TO_UINT16(iso_length, stream);
- // last 2 bits is RFU
- iso_length = iso_length & 0x3FFF;
-
- CHECK(iso_length == packet->len - HCI_ISO_PREAMBLE_SIZE);
-
- uint8_t boundary_flag = GET_BOUNDARY_FLAG(handle);
- uint8_t ts_flag = HCI_ISO_GET_TS_FLAG(handle);
- handle = handle & HANDLE_MASK;
-
- auto map_iter = partial_iso_packets.find(handle);
-
- switch (boundary_flag) {
- case HCI_ISO_BF_COMPLETE_PACKET:
- case HCI_ISO_BF_FIRST_FRAGMENTED_PACKET:
- uint16_t iso_sdu_length;
- uint8_t packet_status_flags;
-
- if (map_iter != partial_iso_packets.end()) {
- LOG_WARN(
- "%s found unfinished packet for the iso handle with start packet. "
- "Dropping old.",
- __func__);
- BT_HDR* hdl = map_iter->second;
- partial_iso_packets.erase(map_iter);
- buffer_allocator->free(hdl);
- }
-
- if (ts_flag) {
- /* Skip timestamp u32 */
- STREAM_SKIP_UINT32(stream);
- packet->layer_specific |= BT_ISO_HDR_CONTAINS_TS;
- iso_hdr_len = HCI_ISO_HEADER_LEN_WITH_TS;
- }
-
- if (iso_length < iso_hdr_len) {
- LOG_WARN("%s ISO packet too small (%d < %d). Dropping it.", __func__,
- packet->len, iso_hdr_len);
- buffer_allocator->free(packet);
- return;
- }
-
- /* Skip packet_seq. */
- STREAM_SKIP_UINT16(stream);
- STREAM_TO_UINT16(iso_sdu_length, stream);
-
- /* Silently ignore empty report if there's no 'lost data' flag set. */
- if (iso_sdu_length == 0) {
- buffer_allocator->free(packet);
- return;
- }
-
- packet_status_flags = HCI_ISO_GET_PACKET_STATUS_FLAGS(iso_sdu_length);
- iso_sdu_length = iso_sdu_length & HCI_ISO_SDU_LENGTH_MASK;
-
- if (packet_status_flags)
- LOG_ERROR("%s packet status flags: 0x%02x", __func__,
- packet_status_flags);
-
- iso_full_len = iso_sdu_length + iso_hdr_len + HCI_ISO_PREAMBLE_SIZE;
- if ((iso_full_len + sizeof(BT_HDR)) > BT_DEFAULT_BUFFER_SIZE) {
- LOG_ERROR("%s Dropping ISO packet with invalid length (%d).", __func__,
- iso_sdu_length);
- buffer_allocator->free(packet);
- return;
- }
-
- if (((boundary_flag == HCI_ISO_BF_COMPLETE_PACKET) &&
- (iso_full_len != packet->len)) ||
- ((boundary_flag == HCI_ISO_BF_FIRST_FRAGMENTED_PACKET) &&
- (iso_full_len <= packet->len))) {
- LOG_ERROR("%s corrupted ISO frame", __func__);
- return;
- }
-
- partial_packet =
- (BT_HDR*)buffer_allocator->alloc(iso_full_len + sizeof(BT_HDR));
- if (!partial_packet) {
- LOG_ERROR("%s cannot allocate partial packet", __func__);
- buffer_allocator->free(packet);
- return;
- }
-
- partial_packet->event = packet->event;
- partial_packet->len = iso_full_len;
- partial_packet->layer_specific = packet->layer_specific;
-
- memcpy(partial_packet->data, packet->data, packet->len);
-
- // Update the ISO data size to indicate the full expected length
- stream = partial_packet->data;
- STREAM_SKIP_UINT16(stream); // skip the ISO handle
- UINT16_TO_STREAM(stream, iso_full_len - HCI_ISO_PREAMBLE_SIZE);
-
- if (boundary_flag == HCI_ISO_BF_FIRST_FRAGMENTED_PACKET) {
- partial_packet->offset = packet->len;
- partial_iso_packets[handle] = partial_packet;
- } else {
- packet->layer_specific |= BT_ISO_HDR_OFFSET_POINTS_DATA;
- partial_packet->offset = iso_hdr_len + HCI_ISO_PREAMBLE_SIZE;
- callbacks->reassembled(partial_packet);
- }
-
- buffer_allocator->free(packet);
- break;
-
- case HCI_ISO_BF_CONTINUATION_FRAGMENT_PACKET:
- // pass-through
- case HCI_ISO_BF_LAST_FRAGMENT_PACKET:
- if (map_iter == partial_iso_packets.end()) {
- LOG_WARN("%s got continuation for unknown packet. Dropping it.",
- __func__);
- buffer_allocator->free(packet);
- return;
- }
-
- partial_packet = map_iter->second;
- if (partial_packet->len <
- (partial_packet->offset + packet->len - HCI_ISO_PREAMBLE_SIZE)) {
- LOG_ERROR(
- "%s got packet which would exceed expected length of %d. "
- "dropping full packet",
- __func__, partial_packet->len);
- buffer_allocator->free(packet);
- partial_iso_packets.erase(map_iter);
- buffer_allocator->free(partial_packet);
- return;
- }
-
- memcpy(partial_packet->data + partial_packet->offset,
- packet->data + HCI_ISO_PREAMBLE_SIZE,
- packet->len - HCI_ISO_PREAMBLE_SIZE);
-
- if (boundary_flag == HCI_ISO_BF_CONTINUATION_FRAGMENT_PACKET) {
- partial_packet->offset += packet->len - HCI_ISO_PREAMBLE_SIZE;
- buffer_allocator->free(packet);
- return;
- }
-
- if (partial_packet->len !=
- partial_packet->offset + packet->len - HCI_ISO_PREAMBLE_SIZE) {
- LOG_ERROR(
- "%s got last fragment, but it doesn't fill up the whole packet of "
- "size %d",
- __func__, partial_packet->len);
- buffer_allocator->free(packet);
- partial_iso_packets.erase(map_iter);
- buffer_allocator->free(partial_packet);
- return;
- }
-
- partial_packet->layer_specific |= BT_ISO_HDR_OFFSET_POINTS_DATA;
- partial_packet->offset = HCI_ISO_PREAMBLE_SIZE;
- if (partial_packet->layer_specific & BT_ISO_HDR_CONTAINS_TS)
- partial_packet->offset += HCI_ISO_HEADER_LEN_WITH_TS;
- else
- partial_packet->offset += HCI_ISO_HEADER_LEN_WITHOUT_TS;
-
- buffer_allocator->free(packet);
-
- partial_iso_packets.erase(map_iter);
- callbacks->reassembled(partial_packet);
-
- break;
- default:
- LOG_ERROR("%s Unexpected packet, dropping full packet", __func__);
- buffer_allocator->free(packet);
- break;
- }
+static bool check_uint16_overflow(uint16_t a, uint16_t b) {
+ return (UINT16_MAX - a) < b;
}
static void reassemble_and_dispatch(BT_HDR* packet) {
@@ -374,7 +137,7 @@ static void reassemble_and_dispatch(BT_HDR* packet) {
handle = handle & HANDLE_MASK;
if (broadcast_flag != POINT_TO_POINT) {
- LOG_WARN("dropping broadcast packet");
+ LOG_WARN(LOG_TAG, "dropping broadcast packet");
android_errorWriteLog(0x534e4554, "169327567");
buffer_allocator->free(packet);
return;
@@ -382,7 +145,7 @@ static void reassemble_and_dispatch(BT_HDR* packet) {
if (boundary_flag == START_PACKET_BOUNDARY) {
if (acl_length < 2) {
- LOG_WARN("%s invalid acl_length %d", __func__, acl_length);
+ LOG_WARN(LOG_TAG, "%s invalid acl_length %d", __func__, acl_length);
buffer_allocator->free(packet);
return;
}
@@ -390,10 +153,10 @@ static void reassemble_and_dispatch(BT_HDR* packet) {
STREAM_TO_UINT16(l2cap_length, stream);
auto map_iter = partial_packets.find(handle);
if (map_iter != partial_packets.end()) {
- LOG_WARN(
- "%s found unfinished packet for handle with start packet. "
- "Dropping old.",
- __func__);
+ LOG_WARN(LOG_TAG,
+ "%s found unfinished packet for handle with start packet. "
+ "Dropping old.",
+ __func__);
BT_HDR* hdl = map_iter->second;
partial_packets.erase(map_iter);
@@ -401,8 +164,8 @@ static void reassemble_and_dispatch(BT_HDR* packet) {
}
if (acl_length < L2CAP_HEADER_PDU_LEN_SIZE) {
- LOG_WARN("%s L2CAP packet too small (%d < %d). Dropping it.", __func__,
- packet->len, L2CAP_HEADER_PDU_LEN_SIZE);
+ LOG_WARN(LOG_TAG, "%s L2CAP packet too small (%d < %d). Dropping it.",
+ __func__, packet->len, L2CAP_HEADER_PDU_LEN_SIZE);
buffer_allocator->free(packet);
return;
}
@@ -415,7 +178,7 @@ static void reassemble_and_dispatch(BT_HDR* packet) {
if (check_uint16_overflow(l2cap_length,
(L2CAP_HEADER_SIZE + HCI_ACL_PREAMBLE_SIZE)) ||
((full_length + sizeof(BT_HDR)) > BT_DEFAULT_BUFFER_SIZE)) {
- LOG_ERROR("%s Dropping L2CAP packet with invalid length (%d).",
+ LOG_ERROR(LOG_TAG, "%s Dropping L2CAP packet with invalid length (%d).",
__func__, l2cap_length);
buffer_allocator->free(packet);
return;
@@ -423,7 +186,8 @@ static void reassemble_and_dispatch(BT_HDR* packet) {
if (full_length <= packet->len) {
if (full_length < packet->len)
- LOG_WARN("%s found l2cap full length %d less than the hci length %d.",
+ LOG_WARN(LOG_TAG,
+ "%s found l2cap full length %d less than the hci length %d.",
__func__, l2cap_length, packet->len);
callbacks->reassembled(packet);
@@ -450,7 +214,8 @@ static void reassemble_and_dispatch(BT_HDR* packet) {
} else {
auto map_iter = partial_packets.find(handle);
if (map_iter == partial_packets.end()) {
- LOG_WARN("%s got continuation for unknown packet. Dropping it.",
+ LOG_WARN(LOG_TAG,
+ "%s got continuation for unknown packet. Dropping it.",
__func__);
buffer_allocator->free(packet);
return;
@@ -462,10 +227,10 @@ static void reassemble_and_dispatch(BT_HDR* packet) {
partial_packet->offset + (packet->len - HCI_ACL_PREAMBLE_SIZE);
if ((packet->len - packet->offset) >
(partial_packet->len - partial_packet->offset)) {
- LOG_WARN(
- "%s got packet which would exceed expected length of %d. "
- "Truncating.",
- __func__, partial_packet->len);
+ LOG_WARN(LOG_TAG,
+ "%s got packet which would exceed expected length of %d. "
+ "Truncating.",
+ __func__, partial_packet->len);
packet->len = (partial_packet->len - partial_packet->offset) + packet->offset;
projected_offset = partial_packet->len;
}
@@ -483,8 +248,6 @@ static void reassemble_and_dispatch(BT_HDR* packet) {
callbacks->reassembled(partial_packet);
}
}
- } else if ((packet->event & MSG_EVT_MASK) == MSG_HC_TO_STACK_HCI_ISO) {
- reassemble_and_dispatch_iso(packet);
} else {
callbacks->reassembled(packet);
}
diff --git a/hci/test/other_stack_stub.cc b/hci/test/other_stack_stub.cc
index b3be48912..4271fc0b2 100644
--- a/hci/test/other_stack_stub.cc
+++ b/hci/test/other_stack_stub.cc
@@ -24,7 +24,7 @@
const btsnoop_t* btsnoop_get_interface() { return nullptr; }
const packet_fragmenter_t* packet_fragmenter_get_interface() { return nullptr; }
-bluetooth::common::MessageLoopThread* get_main_thread() { return nullptr; }
+base::MessageLoop* get_main_message_loop() { return nullptr; }
namespace bluetooth {
namespace bqr {
@@ -36,7 +36,6 @@ void DumpBtScheduling(unsigned char, unsigned char*) {}
namespace shim {
-bool is_gd_hci_enabled() { return false; }
bool is_gd_shim_enabled() { return false; }
bool is_gd_stack_started_up() { return false; }
void Post(base::OnceClosure task) {}
diff --git a/hci/test/packet_fragmenter_test.cc b/hci/test/packet_fragmenter_test.cc
index 35e4acb61..ca83dfa02 100644
--- a/hci/test/packet_fragmenter_test.cc
+++ b/hci/test/packet_fragmenter_test.cc
@@ -32,8 +32,7 @@
DECLARE_TEST_MODES(init, set_data_sizes, no_fragmentation, fragmentation,
ble_no_fragmentation, ble_fragmentation,
non_acl_passthrough_fragmentation, no_reassembly, reassembly,
- non_acl_passthrough_reassembly, iso_no_reassembly,
- iso_reassembly, iso_fragmentation, iso_no_fragmentation);
+ non_acl_passthrough_reassembly);
#define LOCAL_BLE_CONTROLLER_ID 1
@@ -55,36 +54,17 @@ static const char* sample_data =
static const char* small_sample_data = "\"What giants?\" said Sancho Panza.";
static const uint16_t test_handle_start = (0x1992 & 0xCFFF) | 0x2000;
static const uint16_t test_handle_continuation = (0x1992 & 0xCFFF) | 0x1000;
-static const uint16_t test_iso_handle_complete_with_ts =
- (0x0666 | (0x0002 << 12) | (0x0001 << 14));
-static const uint16_t test_iso_handle_complete_without_ts =
- (0x0666 | (0x0002 << 12));
-static const uint16_t test_iso_handle_start_with_ts = (0x0666 | (0x0001 << 14));
-static const uint16_t test_iso_handle_start_without_ts =
- (0x0666); // Also base handle
-static const uint16_t test_iso_handle_continuation = (0x0666 | (0x0001 << 12));
-static const uint16_t test_iso_handle_end = (0x0666 | (0x0003 << 12));
-
static int packet_index;
static unsigned int data_size_sum;
static const packet_fragmenter_t* fragmenter;
-static uint32_t iso_timestamp = 0x32122321;
-static uint16_t iso_packet_seq = 0x1291;
-static bool iso_has_ts = true;
-
static BT_HDR* manufacture_packet_for_fragmentation(uint16_t event,
const char* data) {
uint16_t data_length = strlen(data);
uint16_t size = data_length;
if (event == MSG_STACK_TO_HC_HCI_ACL) {
size += 4; // 2 for the handle, 2 for the length;
- } else if (event == MSG_STACK_TO_HC_HCI_ISO) {
- size += 8; // handle (2), length (2), packet_seq (2), sdu_len(2)
- if (iso_has_ts) {
- size += 4;
- }
}
BT_HDR* packet = (BT_HDR*)osi_malloc(size + sizeof(BT_HDR));
@@ -97,18 +77,6 @@ static BT_HDR* manufacture_packet_for_fragmentation(uint16_t event,
if (event == MSG_STACK_TO_HC_HCI_ACL) {
UINT16_TO_STREAM(packet_data, test_handle_start);
UINT16_TO_STREAM(packet_data, data_length);
- } else if (event == MSG_STACK_TO_HC_HCI_ISO) {
- if (iso_has_ts) {
- packet->layer_specific |= BT_ISO_HDR_CONTAINS_TS;
- UINT16_TO_STREAM(packet_data, test_iso_handle_start_with_ts);
- UINT16_TO_STREAM(packet_data, data_length + 8);
- UINT32_TO_STREAM(packet_data, iso_timestamp);
- } else {
- UINT16_TO_STREAM(packet_data, test_iso_handle_start_without_ts);
- UINT16_TO_STREAM(packet_data, data_length + 4);
- }
- UINT16_TO_STREAM(packet_data, iso_packet_seq);
- UINT16_TO_STREAM(packet_data, data_length);
}
memcpy(packet_data, data, data_length);
@@ -143,67 +111,6 @@ static void expect_packet_fragmented(uint16_t event, int max_acl_data_size,
length_to_check = packet_data_length;
expected_data_offset = packet_index * max_acl_data_size;
packet_index++;
- } else if (event == MSG_STACK_TO_HC_HCI_ISO) {
- uint16_t handle;
- uint16_t length;
-
- STREAM_TO_UINT16(handle, data);
- STREAM_TO_UINT16(length, data);
-
- int length_remaining = strlen(expected_data) - data_size_sum;
- int packet_data_length = packet->len - HCI_ISO_PREAMBLE_SIZE;
-
- if (packet_index == 0) {
- uint8_t hdr_size = 8; // ts, packet_seq, len
-
- if (iso_has_ts) {
- uint32_t timestamp;
- STREAM_TO_UINT32(timestamp, data);
- ASSERT_EQ(timestamp, iso_timestamp);
-
- if (send_complete)
- ASSERT_EQ(test_iso_handle_complete_with_ts, handle);
- else
- ASSERT_EQ(test_iso_handle_start_with_ts, handle);
- } else {
- if (send_complete)
- ASSERT_EQ(test_iso_handle_complete_without_ts, handle);
- else
- ASSERT_EQ(test_iso_handle_start_without_ts, handle);
- hdr_size -= 4;
- }
-
- uint16_t packet_seq;
- STREAM_TO_UINT16(packet_seq, data);
- ASSERT_EQ(packet_seq, iso_packet_seq);
-
- uint16_t iso_sdu_length;
- STREAM_TO_UINT16(iso_sdu_length, data);
-
- ASSERT_EQ(iso_sdu_length, strlen(expected_data));
-
- length_to_check = packet_data_length - hdr_size;
- } else {
- if (!send_complete)
- ASSERT_EQ(test_iso_handle_continuation, handle);
- else
- ASSERT_EQ(test_iso_handle_end, handle);
-
- length_to_check = packet_data_length;
- }
-
- if (length_remaining > max_acl_data_size)
- ASSERT_EQ(max_acl_data_size, packet_data_length);
-
- expected_data_offset = packet_index * max_acl_data_size;
- if (expected_data_offset > 0) {
- if (iso_has_ts) {
- expected_data_offset -= 8;
- } else {
- expected_data_offset -= 4;
- }
- }
- packet_index++;
} else {
length_to_check = strlen(expected_data);
expected_data_offset = 0;
@@ -214,127 +121,49 @@ static void expect_packet_fragmented(uint16_t event, int max_acl_data_size,
data_size_sum++;
}
- if (event == MSG_STACK_TO_HC_HCI_ISO || event == MSG_STACK_TO_HC_HCI_ACL)
+ if (event == MSG_STACK_TO_HC_HCI_ACL)
EXPECT_TRUE(send_complete == (data_size_sum == strlen(expected_data)));
if (send_complete) osi_free(packet);
}
-static void manufacture_acl_packet_and_then_reassemble(uint16_t event,
- uint16_t acl_size,
- const char* data) {
- uint16_t data_length = strlen(data);
- uint16_t total_length = data_length + 2; // 2 for l2cap length;
- uint16_t length_sent = 0;
- uint16_t l2cap_length = data_length - 2; // l2cap length field, 2 for the
- // pretend channel id borrowed
- // from the data
-
- do {
- int length_to_send = (length_sent + (acl_size - 4) < total_length)
- ? (acl_size - 4)
- : (total_length - length_sent);
- BT_HDR* packet = (BT_HDR*)osi_malloc(length_to_send + 4 + sizeof(BT_HDR));
- packet->len = length_to_send + 4;
- packet->offset = 0;
- packet->event = event;
- packet->layer_specific = 0;
-
- uint8_t* packet_data = packet->data;
- if (length_sent == 0) { // first packet
- UINT16_TO_STREAM(packet_data, test_handle_start);
- UINT16_TO_STREAM(packet_data, length_to_send);
- UINT16_TO_STREAM(packet_data, l2cap_length);
- memcpy(packet_data, data, length_to_send - 2);
- } else {
- UINT16_TO_STREAM(packet_data, test_handle_continuation);
- UINT16_TO_STREAM(packet_data, length_to_send);
- memcpy(packet_data, data + length_sent - 2, length_to_send);
- }
-
- length_sent += length_to_send;
- fragmenter->reassemble_and_dispatch(packet);
- } while (length_sent < total_length);
-}
-
-static void manufacture_iso_packet_and_then_reassemble(uint16_t event,
- uint16_t iso_size,
- const char* data) {
- uint16_t data_length = strlen(data);
- uint16_t total_length;
- uint16_t length_sent = 0;
- uint16_t iso_length = data_length;
- BT_HDR* packet;
- uint8_t* packet_data;
- uint8_t hdr_size = 4; // packet seq, sdu len
-
- // ISO length (2), packet seq (2), optional timestamp (4)
- total_length = data_length + 4;
- if (iso_has_ts) total_length += 4;
-
- do {
- int length_to_send = (length_sent + (iso_size - 4) < total_length)
- ? (iso_size - 4)
- : (total_length - length_sent);
-
- packet = (BT_HDR*)osi_malloc(length_to_send + 4 + sizeof(BT_HDR));
- packet_data = packet->data;
- packet->len = length_to_send + 4;
- packet->offset = 0;
- packet->event = event;
- packet->layer_specific = 0;
-
- bool is_complete = length_to_send == total_length;
-
- if (length_sent == 0) { // first packet
- if (iso_has_ts) {
- hdr_size += 4;
- if (is_complete) {
- UINT16_TO_STREAM(packet_data, test_iso_handle_complete_with_ts);
- } else {
- UINT16_TO_STREAM(packet_data, test_iso_handle_start_with_ts);
- }
- } else {
- if (is_complete) {
- UINT16_TO_STREAM(packet_data, test_iso_handle_complete_without_ts);
- } else {
- UINT16_TO_STREAM(packet_data, test_iso_handle_start_without_ts);
- }
- }
-
- UINT16_TO_STREAM(packet_data, length_to_send);
-
- if (iso_has_ts) {
- UINT32_TO_STREAM(packet_data, iso_timestamp);
- }
-
- UINT16_TO_STREAM(packet_data, iso_packet_seq);
- UINT16_TO_STREAM(packet_data, iso_length);
- memcpy(packet_data, data, length_to_send - hdr_size);
- } else {
- if (length_sent + length_to_send == total_length) {
- UINT16_TO_STREAM(packet_data, test_iso_handle_end);
- } else {
- UINT16_TO_STREAM(packet_data, test_iso_handle_continuation);
- }
- UINT16_TO_STREAM(packet_data, length_to_send);
- memcpy(packet_data, data + length_sent - hdr_size, length_to_send);
- }
-
- length_sent += length_to_send;
- fragmenter->reassemble_and_dispatch(packet);
- } while (length_sent < total_length);
-}
-
static void manufacture_packet_and_then_reassemble(uint16_t event,
- uint16_t packet_size,
+ uint16_t acl_size,
const char* data) {
uint16_t data_length = strlen(data);
if (event == MSG_HC_TO_STACK_HCI_ACL) {
- manufacture_acl_packet_and_then_reassemble(event, packet_size, data);
- } else if (event == MSG_HC_TO_STACK_HCI_ISO) {
- manufacture_iso_packet_and_then_reassemble(event, packet_size, data);
+ uint16_t total_length = data_length + 2; // 2 for l2cap length;
+ uint16_t length_sent = 0;
+ uint16_t l2cap_length = data_length - 2; // l2cap length field, 2 for the
+ // pretend channel id borrowed
+ // from the data
+
+ do {
+ int length_to_send = (length_sent + (acl_size - 4) < total_length)
+ ? (acl_size - 4)
+ : (total_length - length_sent);
+ BT_HDR* packet = (BT_HDR*)osi_malloc(length_to_send + 4 + sizeof(BT_HDR));
+ packet->len = length_to_send + 4;
+ packet->offset = 0;
+ packet->event = event;
+ packet->layer_specific = 0;
+
+ uint8_t* packet_data = packet->data;
+ if (length_sent == 0) { // first packet
+ UINT16_TO_STREAM(packet_data, test_handle_start);
+ UINT16_TO_STREAM(packet_data, length_to_send);
+ UINT16_TO_STREAM(packet_data, l2cap_length);
+ memcpy(packet_data, data, length_to_send - 2);
+ } else {
+ UINT16_TO_STREAM(packet_data, test_handle_continuation);
+ UINT16_TO_STREAM(packet_data, length_to_send);
+ memcpy(packet_data, data + length_sent - 2, length_to_send);
+ }
+
+ length_sent += length_to_send;
+ fragmenter->reassemble_and_dispatch(packet);
+ } while (length_sent < total_length);
} else {
BT_HDR* packet = (BT_HDR*)osi_malloc(data_length + sizeof(BT_HDR));
packet->len = data_length;
@@ -374,55 +203,6 @@ static void expect_packet_reassembled(uint16_t event, BT_HDR* packet,
osi_free(packet);
}
-static void expect_packet_reassembled_iso(uint16_t event, BT_HDR* packet,
- const char* expected_data,
- uint32_t expected_timestamp,
- uint16_t expected_packet_seq,
- bool is_complete = false) {
- uint16_t expected_data_length = strlen(expected_data);
- uint8_t* data = packet->data;
- uint8_t hdr_size = 8;
- uint16_t handle;
- uint16_t length;
- uint16_t iso_length;
- uint32_t timestamp;
- uint16_t packet_seq;
-
- ASSERT_EQ(event, MSG_HC_TO_STACK_HCI_ISO);
-
- STREAM_TO_UINT16(handle, data);
- STREAM_TO_UINT16(length, data);
- if (iso_has_ts) {
- STREAM_TO_UINT32(timestamp, data);
- ASSERT_TRUE((packet->layer_specific & BT_ISO_HDR_CONTAINS_TS) != 0);
- ASSERT_EQ(timestamp, expected_timestamp);
- ASSERT_EQ(is_complete ? test_iso_handle_complete_with_ts
- : test_iso_handle_start_with_ts,
- handle);
- } else {
- ASSERT_TRUE((packet->layer_specific & BT_ISO_HDR_CONTAINS_TS) == 0);
- ASSERT_EQ(is_complete ? test_iso_handle_complete_without_ts
- : test_iso_handle_start_without_ts,
- handle);
- hdr_size -= 4;
- }
-
- ASSERT_EQ(expected_data_length + hdr_size, length);
-
- STREAM_TO_UINT16(packet_seq, data);
- ASSERT_EQ(packet_seq, expected_packet_seq);
-
- STREAM_TO_UINT16(iso_length, data);
- ASSERT_EQ(expected_data_length, iso_length);
-
- for (int i = 0; i < expected_data_length; i++) {
- ASSERT_EQ(expected_data[i], data[i]);
- data_size_sum++;
- }
-
- osi_free(packet);
-}
-
STUB_FUNCTION(void, fragmented_callback, (BT_HDR * packet, bool send_complete))
DURING(no_fragmentation) AT_CALL(0) {
expect_packet_fragmented(MSG_STACK_TO_HC_HCI_ACL, 42, packet,
@@ -448,18 +228,6 @@ DURING(ble_fragmentation) {
return;
}
-DURING(iso_fragmentation) {
- expect_packet_fragmented(MSG_STACK_TO_HC_HCI_ISO, 10, packet, sample_data,
- send_complete);
- return;
-}
-
-DURING(iso_no_fragmentation) {
- expect_packet_fragmented(MSG_STACK_TO_HC_HCI_ISO, 42, packet,
- small_sample_data, send_complete);
- return;
-}
-
DURING(non_acl_passthrough_fragmentation) AT_CALL(0) {
expect_packet_fragmented(MSG_STACK_TO_HC_HCI_CMD, 10, packet, sample_data,
send_complete);
@@ -480,19 +248,6 @@ DURING(reassembly) AT_CALL(0) {
return;
}
-DURING(iso_reassembly) AT_CALL(0) {
- expect_packet_reassembled_iso(MSG_HC_TO_STACK_HCI_ISO, packet, sample_data,
- iso_timestamp, iso_packet_seq);
- return;
-}
-
-DURING(iso_no_reassembly) AT_CALL(0) {
- expect_packet_reassembled_iso(MSG_HC_TO_STACK_HCI_ISO, packet,
- small_sample_data, iso_timestamp,
- iso_packet_seq, true);
- return;
-}
-
DURING(non_acl_passthrough_reassembly) AT_CALL(0) {
expect_packet_reassembled(MSG_HC_TO_STACK_HCI_EVT, packet, sample_data);
return;
@@ -525,21 +280,12 @@ UNEXPECTED_CALL;
return 0;
}
-STUB_FUNCTION(uint16_t, get_iso_data_size, (void))
-DURING(iso_no_fragmentation) return 42;
-DURING(iso_fragmentation) return 10;
-
-UNEXPECTED_CALL;
-return 0;
-}
-
static void reset_for(TEST_MODES_T next) {
RESET_CALL_COUNT(fragmented_callback);
RESET_CALL_COUNT(reassembled_callback);
RESET_CALL_COUNT(transmit_finished_callback);
RESET_CALL_COUNT(get_acl_data_size_classic);
RESET_CALL_COUNT(get_acl_data_size_ble);
- RESET_CALL_COUNT(get_iso_data_size);
CURRENT_TEST_MODE = next;
}
@@ -558,7 +304,6 @@ class PacketFragmenterTest : public AllocationTestHarness {
callbacks.transmit_finished = transmit_finished_callback;
controller.get_acl_data_size_classic = get_acl_data_size_classic;
controller.get_acl_data_size_ble = get_acl_data_size_ble;
- controller.get_iso_data_size = get_iso_data_size;
reset_for(init);
fragmenter->init(&callbacks);
@@ -649,89 +394,3 @@ TEST_F(PacketFragmenterTest, test_non_acl_passthrough_reasseembly) {
EXPECT_EQ(strlen(sample_data), data_size_sum);
EXPECT_CALL_COUNT(reassembled_callback, 1);
}
-
-TEST_F(PacketFragmenterTest, test_iso_fragment_necessary) {
- reset_for(iso_fragmentation);
- iso_has_ts = true;
-
- BT_HDR* packet = manufacture_packet_for_fragmentation(MSG_STACK_TO_HC_HCI_ISO,
- sample_data);
- packet->event |= LOCAL_BLE_CONTROLLER_ID;
- fragmenter->fragment_and_dispatch(packet);
-
- ASSERT_EQ(strlen(sample_data), data_size_sum);
-}
-
-TEST_F(PacketFragmenterTest, test_iso_no_fragment_necessary) {
- reset_for(iso_no_fragmentation);
- iso_has_ts = true;
-
- BT_HDR* packet = manufacture_packet_for_fragmentation(MSG_STACK_TO_HC_HCI_ISO,
- small_sample_data);
- packet->event |= LOCAL_BLE_CONTROLLER_ID;
- fragmenter->fragment_and_dispatch(packet);
-
- ASSERT_EQ(strlen(small_sample_data), data_size_sum);
-}
-
-TEST_F(PacketFragmenterTest, test_iso_fragment_necessary_no_ts) {
- reset_for(iso_fragmentation);
- iso_has_ts = false;
- BT_HDR* packet = manufacture_packet_for_fragmentation(MSG_STACK_TO_HC_HCI_ISO,
- sample_data);
- packet->event |= LOCAL_BLE_CONTROLLER_ID;
- fragmenter->fragment_and_dispatch(packet);
-
- ASSERT_EQ(strlen(sample_data), data_size_sum);
-}
-
-TEST_F(PacketFragmenterTest, test_iso_no_fragment_necessary_no_ts) {
- reset_for(iso_no_fragmentation);
- iso_has_ts = false;
- BT_HDR* packet = manufacture_packet_for_fragmentation(MSG_STACK_TO_HC_HCI_ISO,
- small_sample_data);
- packet->event |= LOCAL_BLE_CONTROLLER_ID;
- fragmenter->fragment_and_dispatch(packet);
-
- ASSERT_EQ(strlen(small_sample_data), data_size_sum);
-}
-
-TEST_F(PacketFragmenterTest, test_iso_no_reassembly_necessary) {
- reset_for(iso_no_reassembly);
- iso_has_ts = true;
- manufacture_packet_and_then_reassemble(MSG_HC_TO_STACK_HCI_ISO, 50,
- small_sample_data);
-
- ASSERT_EQ(strlen(small_sample_data), data_size_sum);
- EXPECT_CALL_COUNT(reassembled_callback, 1);
-}
-
-TEST_F(PacketFragmenterTest, test_iso_reassembly_necessary) {
- reset_for(iso_reassembly);
- iso_has_ts = true;
- manufacture_packet_and_then_reassemble(MSG_HC_TO_STACK_HCI_ISO, 42,
- sample_data);
-
- ASSERT_EQ(strlen(sample_data), data_size_sum);
- EXPECT_CALL_COUNT(reassembled_callback, 1);
-}
-
-TEST_F(PacketFragmenterTest, test_iso_no_reassembly_necessary_no_ts) {
- reset_for(iso_no_reassembly);
- iso_has_ts = false;
- manufacture_packet_and_then_reassemble(MSG_HC_TO_STACK_HCI_ISO, (42 + 4),
- small_sample_data);
-
- ASSERT_EQ(strlen(small_sample_data), data_size_sum);
- EXPECT_CALL_COUNT(reassembled_callback, 1);
-}
-
-TEST_F(PacketFragmenterTest, test_iso_reassembly_necessary_no_ts) {
- reset_for(iso_reassembly);
- iso_has_ts = false;
- manufacture_packet_and_then_reassemble(MSG_HC_TO_STACK_HCI_ISO, 42,
- sample_data);
-
- ASSERT_EQ(strlen(sample_data), data_size_sum);
- EXPECT_CALL_COUNT(reassembled_callback, 1);
-}
diff --git a/include/Android.bp b/include/Android.bp
index 83edf1594..1f35206cd 100644
--- a/include/Android.bp
+++ b/include/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_headers {
name: "avrcp_headers",
defaults: ["libchrome_support_defaults"],
@@ -20,10 +11,6 @@ cc_library_headers {
vendor_available: true,
host_supported: true,
- apex_available: [
- "//apex_available:platform",
- "com.android.bluetooth.updatable",
- ],
}
cc_library_headers {
diff --git a/include/abstract_message_loop.h b/include/abstract_message_loop.h
deleted file mode 100644
index dff65b167..000000000
--- a/include/abstract_message_loop.h
+++ /dev/null
@@ -1,85 +0,0 @@
-//
-// Copyright 2021 Google, Inc.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at:
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-//
-
-#pragma once
-
-#if defined(BASE_VER) && BASE_VER > 780000
-/* libchrome version < 780000 still has the old message loop. Android still uses
- * the old libchrome version so use the basic messageloop where that's required.
- * Elsewhere, use the SingleThreadTaskExecutor instead.
- */
-#if BASE_VER >= 822064
-#include <base/task/current_thread.h>
-#else
-#include <base/message_loop/message_loop_current.h>
-#endif
-#include <base/message_loop/message_pump.h>
-#include <base/task/single_thread_task_executor.h>
-#include <base/test/task_environment.h>
-#include <base/threading/thread.h>
-#include <base/threading/thread_task_runner_handle.h>
-#else
-#include <base/message_loop/message_loop.h>
-#include <base/threading/thread.h>
-#endif
-
-namespace btbase {
-
-#if defined(BASE_VER) && BASE_VER > 780000
-
-class AbstractMessageLoop : public base::SingleThreadTaskExecutor {
- public:
- static scoped_refptr<base::SingleThreadTaskRunner> current_task_runner() {
- return base::ThreadTaskRunnerHandle::Get();
- }
-};
-
-class AbstractTestMessageLoop : public base::test::TaskEnvironment {
- public:
- static scoped_refptr<base::SingleThreadTaskRunner> current_task_runner() {
- return base::ThreadTaskRunnerHandle::Get();
- }
-};
-
-// Initialize the test task environment
-#define DEFINE_TEST_TASK_ENV(var) \
- base::AbstractTestMessageLoop var { \
- base::test::TaskEnvironment::ThreadingMode::MAIN_THREAD_ONLY \
- }
-
-inline void set_message_loop_type_IO(base::Thread::Options& options) {
- options.message_pump_type = base::MessagePumpType::IO;
-}
-
-#else
-class AbstractMessageLoop : public base::MessageLoop {
- public:
- static scoped_refptr<base::SingleThreadTaskRunner> current_task_runner() {
- return base::MessageLoop::current()->task_runner();
- }
-};
-
-class AbstractTestMessageLoop : public AbstractMessageLoop {};
-
-#define DEFINE_TEST_TASK_ENV(var) base::AbstractTestMessageLoop* var
-
-inline void set_message_loop_type_IO(base::Thread::Options& options) {
- options.message_loop_type = base::MessageLoop::TYPE_IO;
-}
-
-#endif
-
-} // namespace btbase
diff --git a/include/abstract_observer_list.h b/include/abstract_observer_list.h
deleted file mode 100644
index 0f882599e..000000000
--- a/include/abstract_observer_list.h
+++ /dev/null
@@ -1,36 +0,0 @@
-//
-// Copyright 2021 Google, Inc.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at:
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-//
-
-#pragma once
-
-#include <base/observer_list.h>
-
-namespace btbase {
-#if defined(BASE_VER) && BASE_VER > 780000
-
-// Checked Observers aren't supported in the older libchrome so use unchecked
-// ones instead to preserve behavior.
-template <class ObserverType>
-class AbstractObserverList
- : public base::ObserverList<ObserverType>::Unchecked {};
-
-#else
-
-template <class ObserverType>
-class AbstractObserverList : public base::ObserverList<ObserverType> {};
-
-#endif
-} // namespace btbase
diff --git a/include/array_utils.h b/include/array_utils.h
deleted file mode 100644
index d669d0aba..000000000
--- a/include/array_utils.h
+++ /dev/null
@@ -1,20 +0,0 @@
-//
-// Copyright 2021 Google, Inc.
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at:
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-//
-#pragma once
-
-#ifndef ARRAY_SIZE
-#define ARRAY_SIZE(arr) (sizeof(arr) / sizeof(arr[0]))
-#endif
diff --git a/include/hardware/avrcp/avrcp.h b/include/hardware/avrcp/avrcp.h
index a78027d0c..577acb9f7 100644
--- a/include/hardware/avrcp/avrcp.h
+++ b/include/hardware/avrcp/avrcp.h
@@ -18,7 +18,6 @@
#include <set>
#include <string>
-#include <vector>
#include <base/callback_forward.h>
@@ -177,11 +176,8 @@ class ServiceInterface {
// Volume is disabled.
virtual void Init(MediaInterface* mediaInterface,
VolumeInterface* volumeInterface) = 0;
- virtual void RegisterBipServer(int psm) = 0;
- virtual void UnregisterBipServer() = 0;
virtual bool ConnectDevice(const RawAddress& bdaddr) = 0;
virtual bool DisconnectDevice(const RawAddress& bdaddr) = 0;
- virtual void SetBipClientStatus(const RawAddress& bdaddr, bool connected) = 0;
virtual bool Cleanup() = 0;
protected:
@@ -189,4 +185,4 @@ class ServiceInterface {
};
} // namespace avrcp
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/include/hardware/ble_advertiser.h b/include/hardware/ble_advertiser.h
index 72731b221..6055d8925 100644
--- a/include/hardware/ble_advertiser.h
+++ b/include/hardware/ble_advertiser.h
@@ -41,32 +41,6 @@ struct PeriodicAdvertisingParameters {
uint16_t periodic_advertising_properties;
};
-/**
- * LE Advertising related callbacks invoked from from the Bluetooth native stack
- * All callbacks are invoked on the JNI thread
- */
-class AdvertisingCallbacks {
- public:
- virtual ~AdvertisingCallbacks() = default;
- virtual void OnAdvertisingSetStarted(int reg_id, uint8_t advertiser_id,
- int8_t tx_power, uint8_t status) = 0;
- virtual void OnAdvertisingEnabled(uint8_t advertiser_id, bool enable,
- uint8_t status) = 0;
- virtual void OnAdvertisingDataSet(uint8_t advertiser_id, uint8_t status) = 0;
- virtual void OnScanResponseDataSet(uint8_t advertiser_id, uint8_t status) = 0;
- virtual void OnAdvertisingParametersUpdated(uint8_t advertiser_id,
- int8_t tx_power,
- uint8_t status) = 0;
- virtual void OnPeriodicAdvertisingParametersUpdated(uint8_t advertiser_id,
- uint8_t status) = 0;
- virtual void OnPeriodicAdvertisingDataSet(uint8_t advertiser_id,
- uint8_t status) = 0;
- virtual void OnPeriodicAdvertisingEnabled(uint8_t advertiser_id, bool enable,
- uint8_t status) = 0;
- virtual void OnOwnAddressRead(uint8_t advertiser_id, uint8_t address_type,
- RawAddress address) = 0;
-};
-
class BleAdvertiserInterface {
public:
virtual ~BleAdvertiserInterface() = default;
@@ -112,11 +86,10 @@ class BleAdvertiserInterface {
/** Start the advertising set. This include registering, setting all
* parameters and data, and enabling it. |register_cb| is called when the set
- * is advertising. |timeout_cb| is called when the timeout_s have passed.
- * |reg_id| is the callback id assigned from upper layer */
+ * is advertising. |timeout_cb| is called when the timeout_s have passed */
virtual void StartAdvertisingSet(
- int reg_id, IdTxPowerStatusCallback register_cb,
- AdvertiseParameters params, std::vector<uint8_t> advertise_data,
+ IdTxPowerStatusCallback register_cb, AdvertiseParameters params,
+ std::vector<uint8_t> advertise_data,
std::vector<uint8_t> scan_response_data,
PeriodicAdvertisingParameters periodic_params,
std::vector<uint8_t> periodic_data, uint16_t duration,
@@ -132,7 +105,6 @@ class BleAdvertiserInterface {
virtual void SetPeriodicAdvertisingEnable(int advertiser_id, bool enable,
StatusCallback cb) = 0;
- virtual void RegisterCallbacks(AdvertisingCallbacks* callbacks) = 0;
};
#endif /* ANDROID_INCLUDE_BLE_ADVERTISER_H */
diff --git a/include/hardware/ble_scanner.h b/include/hardware/ble_scanner.h
index 7f4ee855f..efa96627c 100644
--- a/include/hardware/ble_scanner.h
+++ b/include/hardware/ble_scanner.h
@@ -17,9 +17,7 @@
#ifndef ANDROID_INCLUDE_BLE_SCANNER_H
#define ANDROID_INCLUDE_BLE_SCANNER_H
-#include <bluetooth/uuid.h>
#include <stdint.h>
-#include <memory>
#include <vector>
#include "bt_common_types.h"
#include "bt_gatt_client.h"
@@ -52,69 +50,28 @@ typedef struct {
track_adv_event_callback track_adv_event_cb;
} btgatt_scanner_callbacks_t;
-class AdvertisingTrackInfo {
- public:
- uint8_t scanner_id;
- uint8_t filter_index;
- uint8_t advertiser_state;
- uint8_t advertiser_info_present;
- RawAddress advertiser_address;
- uint8_t advertiser_address_type;
- uint8_t tx_power;
- int8_t rssi;
- uint16_t time_stamp;
- uint8_t adv_packet_len;
- std::vector<uint8_t> adv_packet;
- uint8_t scan_response_len;
- std::vector<uint8_t> scan_response;
-};
-
-/**
- * LE Scanning related callbacks invoked from from the Bluetooth native stack
- * All callbacks are invoked on the JNI thread
- */
-class ScanningCallbacks {
- public:
- virtual ~ScanningCallbacks() = default;
- virtual void OnScannerRegistered(const bluetooth::Uuid app_uuid,
- uint8_t scannerId, uint8_t status) = 0;
- virtual void OnScanResult(uint16_t event_type, uint8_t addr_type,
- RawAddress bda, uint8_t primary_phy,
- uint8_t secondary_phy, uint8_t advertising_sid,
- int8_t tx_power, int8_t rssi,
- uint16_t periodic_adv_int,
- std::vector<uint8_t> adv_data) = 0;
- virtual void OnTrackAdvFoundLost(
- AdvertisingTrackInfo advertising_track_info) = 0;
- virtual void OnBatchScanReports(int client_if, int status, int report_format,
- int num_records,
- std::vector<uint8_t> data) = 0;
- virtual void OnBatchScanThresholdCrossed(int client_if) = 0;
-};
-
class BleScannerInterface {
public:
virtual ~BleScannerInterface() = default;
using RegisterCallback =
- base::Callback<void(uint8_t /* scanner_id */, uint8_t /* btm_status */)>;
+ base::Callback<void(uint8_t /* scanner_id */, uint8_t /* status */)>;
- using Callback = base::Callback<void(uint8_t /* btm_status */)>;
+ using Callback = base::Callback<void(uint8_t /* status */)>;
using EnableCallback =
- base::Callback<void(uint8_t /* action */, uint8_t /* btm_status */)>;
+ base::Callback<void(uint8_t /* action */, uint8_t /* status */)>;
using FilterParamSetupCallback =
base::Callback<void(uint8_t /* avbl_space */, uint8_t /* action_type */,
- uint8_t /* btm_status */)>;
+ uint8_t /* status */)>;
using FilterConfigCallback =
base::Callback<void(uint8_t /* filt_type */, uint8_t /* avbl_space */,
- uint8_t /* action */, uint8_t /* btm_status */)>;
+ uint8_t /* action */, uint8_t /* status */)>;
/** Registers a scanner with the stack */
- virtual void RegisterScanner(const bluetooth::Uuid& app_uuid,
- RegisterCallback) = 0;
+ virtual void RegisterScanner(RegisterCallback) = 0;
/** Unregister a scanner from the stack */
virtual void Unregister(int scanner_id) = 0;
@@ -171,8 +128,6 @@ class BleScannerInterface {
uint16_t timeout, StartSyncCb start_cb,
SyncReportCb report_cb, SyncLostCb lost_cb) = 0;
virtual void StopSync(uint16_t handle) = 0;
-
- virtual void RegisterCallbacks(ScanningCallbacks* callbacks) = 0;
};
-#endif /* ANDROID_INCLUDE_BLE_SCANNER_H */
+#endif /* ANDROID_INCLUDE_BLE_SCANNER_H */ \ No newline at end of file
diff --git a/include/hardware/bluetooth.h b/include/hardware/bluetooth.h
index 63f47e265..425100516 100644
--- a/include/hardware/bluetooth.h
+++ b/include/hardware/bluetooth.h
@@ -24,7 +24,6 @@
#include "avrcp/avrcp.h"
#include "bluetooth/uuid.h"
-#include "bt_transport.h"
#include "raw_address.h"
/**
@@ -49,10 +48,7 @@
#define BT_PROFILE_AV_RC_ID "avrcp"
#define BT_PROFILE_AV_RC_CTRL_ID "avrcp_ctrl"
#define BT_PROFILE_HEARING_AID_ID "hearing_aid"
-#define BT_PROFILE_LE_AUDIO_ID "le_audio"
#define BT_KEYSTORE_ID "bluetooth_keystore"
-#define BT_ACTIVITY_ATTRIBUTION_ID "activity_attribution"
-#define BT_PROFILE_VC_ID "volume_control"
/** Bluetooth Device Name */
typedef struct { uint8_t name[249]; } __attribute__((packed)) bt_bdname_t;
@@ -83,7 +79,7 @@ typedef enum {
/** We need to build on this */
typedef enum {
- BT_STATUS_SUCCESS = 0,
+ BT_STATUS_SUCCESS,
BT_STATUS_FAIL,
BT_STATUS_NOT_READY,
BT_STATUS_NOMEM,
@@ -100,47 +96,6 @@ typedef enum {
BT_STATUS_WAKELOCK_ERROR
} bt_status_t;
-inline std::string bt_status_text(const bt_status_t& status) {
- switch (status) {
- case BT_STATUS_SUCCESS:
- return std::string("success");
- case BT_STATUS_FAIL:
- return std::string("fail");
- case BT_STATUS_NOT_READY:
- return std::string("not_ready");
- case BT_STATUS_NOMEM:
- return std::string("no_memory");
- case BT_STATUS_BUSY:
- return std::string("busy");
- case BT_STATUS_DONE:
- return std::string("already_done");
- case BT_STATUS_UNSUPPORTED:
- return std::string("unsupported");
- case BT_STATUS_PARM_INVALID:
- return std::string("parameter_invalid");
- case BT_STATUS_UNHANDLED:
- return std::string("unhandled");
- case BT_STATUS_AUTH_FAILURE:
- return std::string("failure");
- case BT_STATUS_RMT_DEV_DOWN:
- return std::string("remote_device_down");
- case BT_STATUS_AUTH_REJECTED:
- return std::string("rejected");
- case BT_STATUS_JNI_ENVIRONMENT_ERROR:
- return std::string("jni_env_error");
- case BT_STATUS_JNI_THREAD_ATTACH_ERROR:
- return std::string("jni_thread_error");
- case BT_STATUS_WAKELOCK_ERROR:
- return std::string("wakelock_error");
- default:
- return std::string("UNKNOWN");
- }
-}
-
-/** Bluetooth HCI Error Codes */
-/** Corresponding to [Vol 2] Part D, "Error Codes" of Core_v5.1 specs */
-typedef uint8_t bt_hci_error_code_t;
-
/** Bluetooth PinKey Code */
typedef struct { uint8_t pin[16]; } __attribute__((packed)) bt_pin_code_t;
@@ -202,22 +157,8 @@ typedef struct {
bool le_extended_advertising_supported;
bool le_periodic_advertising_supported;
uint16_t le_maximum_advertising_data_length;
- uint32_t dynamic_audio_buffer_supported;
} bt_local_le_features_t;
-/* Stored the default/maximum/minimum buffer time for dynamic audio buffer.
- * For A2DP offload usage, the unit is millisecond.
- * For A2DP legacy usage, the unit is buffer queue size*/
-typedef struct {
- uint16_t default_buffer_time;
- uint16_t maximum_buffer_time;
- uint16_t minimum_buffer_time;
-} bt_dynamic_audio_buffer_type_t;
-
-typedef struct {
- bt_dynamic_audio_buffer_type_t dab_item[32];
-} bt_dynamic_audio_buffer_item_t;
-
/* Bluetooth Adapter and Remote Device property types */
typedef enum {
/* Properties common to both adapter and remote device */
@@ -322,8 +263,6 @@ typedef enum {
*/
BT_PROPERTY_LOCAL_IO_CAPS_BLE,
- BT_PROPERTY_DYNAMIC_AUDIO_BUFFER,
-
BT_PROPERTY_REMOTE_DEVICE_TIMESTAMP = 0xFF,
} bt_property_type_t;
@@ -334,26 +273,17 @@ typedef struct {
void* val;
} bt_property_t;
-/** Represents the actual Out of Band data itself */
+/** Bluetooth Out Of Band data for bonding */
typedef struct {
- // Both
- bool is_valid = false; /* Default to invalid data; force caller to verify */
- uint8_t address[7]; /* Bluetooth Device Address (6) plus Address Type (1) */
- uint8_t c[16]; /* Simple Pairing Hash C-192/256 (Classic or LE) */
- uint8_t r[16]; /* Simple Pairing Randomizer R-192/256 (Classic or LE) */
- uint8_t device_name[256]; /* Name of the device */
-
- // Classic
- uint8_t oob_data_length[2]; /* Classic only data Length. Value includes this
- in length */
- uint8_t class_of_device[2]; /* Class of Device (Classic or LE) */
-
- // LE
- uint8_t le_device_role; /* Supported and preferred role of device */
- uint8_t sm_tk[16]; /* Security Manager TK Value (LE Only) */
- uint8_t le_flags; /* LE Flags for discoverability and features */
- uint8_t le_appearance[2]; /* For the appearance of the device */
-} bt_oob_data_t;
+ uint8_t le_bt_dev_addr[7]; /* LE Bluetooth Device Address */
+ uint8_t c192[16]; /* Simple Pairing Hash C-192 */
+ uint8_t r192[16]; /* Simple Pairing Randomizer R-192 */
+ uint8_t c256[16]; /* Simple Pairing Hash C-256 */
+ uint8_t r256[16]; /* Simple Pairing Randomizer R-256 */
+ uint8_t sm_tk[16]; /* Security Manager TK Value */
+ uint8_t le_sc_c[16]; /* LE Secure Connections Confirmation Value */
+ uint8_t le_sc_r[16]; /* LE Secure Connections Random Value */
+} bt_out_of_band_data_t;
/** Bluetooth Device Type */
typedef enum {
@@ -361,7 +291,6 @@ typedef enum {
BT_DEVICE_DEVTYPE_BLE,
BT_DEVICE_DEVTYPE_DUAL
} bt_device_type_t;
-
/** Bluetooth Bond state */
typedef enum {
BT_BOND_STATE_NONE,
@@ -439,14 +368,7 @@ typedef void (*bond_state_changed_callback)(bt_status_t status,
/** Bluetooth ACL connection state changed callback */
typedef void (*acl_state_changed_callback)(bt_status_t status,
RawAddress* remote_bd_addr,
- bt_acl_state_t state,
- bt_hci_error_code_t hci_reason);
-
-/** Bluetooth link quality report callback */
-typedef void (*link_quality_report_callback)(
- uint64_t timestamp, int report_id, int rssi, int snr,
- int retransmission_count, int packets_not_receive_count,
- int negative_acknowledgement_count);
+ bt_acl_state_t state);
typedef enum { ASSOCIATE_JVM, DISASSOCIATE_JVM } bt_cb_thread_evt;
@@ -478,10 +400,6 @@ typedef void (*le_test_mode_callback)(bt_status_t status, uint16_t num_packets);
typedef void (*energy_info_callback)(bt_activity_energy_info* energy_info,
bt_uid_traffic_t* uid_data);
-/** Callback invoked when OOB data is returned from the controller */
-typedef void (*generate_local_oob_data_callback)(tBT_TRANSPORT transport,
- bt_oob_data_t oob_data);
-
/** TODO: Add callbacks for Link Up/Down and other generic
* notifications/callbacks */
@@ -502,8 +420,6 @@ typedef struct {
dut_mode_recv_callback dut_mode_recv_cb;
le_test_mode_callback le_test_mode_cb;
energy_info_callback energy_info_cb;
- link_quality_report_callback link_quality_report_cb;
- generate_local_oob_data_callback generate_local_oob_data_cb;
} bt_callbacks_t;
typedef void (*alarm_cb)(void* data);
@@ -554,15 +470,13 @@ typedef struct {
* The |start_restricted| flag inits the adapter in restricted mode. In
* restricted mode, bonds that are created are marked as restricted in the
* config file. These devices are deleted upon leaving restricted mode.
- * The |is_common_criteria_mode| flag inits the adapter in commom criteria
- * mode. The |config_compare_result| flag show the config checksum check
- * result if is in common criteria mode. The |init_flags| are config flags
- * that cannot change during run. The |is_atv| flag indicates whether the
- * local device is an Android TV
+ * The |is_niap_mode| flag inits the adapter in NIAP mode.
+ * The |config_compare_result| flag show the config checksum check result if
+ * is in NIAP mode.
+ * The |is_atv| flag indicates whether the local device is an Android TV
*/
- int (*init)(bt_callbacks_t* callbacks, bool guest_mode,
- bool is_common_criteria_mode, int config_compare_result,
- const char** init_flags, bool is_atv);
+ int (*init)(bt_callbacks_t* callbacks, bool guest_mode, bool is_niap_mode,
+ int config_compare_result, bool is_atv);
/** Enable Bluetooth. */
int (*enable)();
@@ -614,8 +528,7 @@ typedef struct {
/** Create Bluetooth Bond using out of band data */
int (*create_bond_out_of_band)(const RawAddress* bd_addr, int transport,
- const bt_oob_data_t* p192_data,
- const bt_oob_data_t* p256_data);
+ const bt_out_of_band_data_t* oob_data);
/** Remove Bond */
int (*remove_bond)(const RawAddress* bd_addr);
@@ -724,16 +637,6 @@ typedef struct {
* @return int incremental Bluetooth id
*/
int (*get_metric_id)(const RawAddress& address);
-
- /**
- * Set the dynamic audio buffer size to the Controller
- */
- int (*set_dynamic_audio_buffer_size)(int codec, int size);
-
- /**
- * Fetches the local Out of Band data.
- */
- int (*generate_local_oob_data)(tBT_TRANSPORT transport);
} bt_interface_t;
#define BLUETOOTH_INTERFACE_STRING "bluetoothInterface"
diff --git a/include/hardware/bluetooth_headset_interface.h b/include/hardware/bluetooth_headset_interface.h
index a1e78d2ad..8527919a9 100644
--- a/include/hardware/bluetooth_headset_interface.h
+++ b/include/hardware/bluetooth_headset_interface.h
@@ -72,24 +72,6 @@ class Interface {
*/
virtual bt_status_t DisconnectAudio(RawAddress* bd_addr) = 0;
- /**
- * Checks whether the device support echo cancellation and/or noise reduction
- * via the AT+BRSF bitmask
- *
- * @param bd_addr remote device address
- * @return BT_STATUS_SUCCESS on success
- */
- virtual bt_status_t isNoiseReductionSupported(RawAddress* bd_addr) = 0;
-
- /**
- * Checks whether the device supports voice recognition via the AT+BRSF
- * bitmask
- *
- * @param bd_addr remote device address
- * @return BT_STATUS_SUCCESS on success
- */
- virtual bt_status_t isVoiceRecognitionSupported(RawAddress* bd_addr) = 0;
-
/** start voice recognition */
/**
* Start voice recognition
diff --git a/include/hardware/bt_activity_attribution.h b/include/hardware/bt_activity_attribution.h
deleted file mode 100644
index 480427091..000000000
--- a/include/hardware/bt_activity_attribution.h
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef ANDROID_INCLUDE_BT_ACTIVITY_ATTRIBUTION_H
-#define ANDROID_INCLUDE_BT_ACTIVITY_ATTRIBUTION_H
-
-#include <vector>
-
-#include "raw_address.h"
-
-namespace bluetooth {
-namespace activity_attribution {
-
-class ActivityAttributionCallbacks {
- public:
- enum class Activity : uint8_t {
- UNKNOWN = 0,
- ACL,
- ADVERTISE,
- CONNECT,
- CONTROL,
- HFP,
- ISO,
- SCAN,
- VENDOR,
- };
-
- struct BtaaAggregationEntry {
- RawAddress address;
- Activity activity;
- uint16_t wakeup_count;
- uint32_t byte_count;
- uint32_t wakelock_duration;
- };
-
- virtual ~ActivityAttributionCallbacks() = default;
-
- /** Callback when Bluetooth woke up the system */
- virtual void OnWakeup(const Activity activity, const RawAddress& address) = 0;
-
- /** Callback when Bluetooth activity logs are ready to be moved */
- virtual void OnActivityLogsReady(
- const std::vector<BtaaAggregationEntry> logs) = 0;
-};
-
-class ActivityAttributionInterface {
- public:
- virtual ~ActivityAttributionInterface() = default;
-
- /** Init the interface. */
- virtual void Init(void) = 0;
-
- /** Register JNI callbacks with the interface. */
- virtual void RegisterCallbacks(ActivityAttributionCallbacks* callbacks) = 0;
-
- /** Closes the interface. */
- virtual void Cleanup(void) = 0;
-};
-
-} // namespace activity_attribution
-} // namespace bluetooth
-
-#endif /* ANDROID_INCLUDE_BT_ACTIVITY_ATTRIBUTION_H */
diff --git a/include/hardware/bt_av.h b/include/hardware/bt_av.h
index b3be7a234..c4c0ecc82 100644
--- a/include/hardware/bt_av.h
+++ b/include/hardware/bt_av.h
@@ -108,11 +108,6 @@ typedef enum {
BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO = 0x1 << 1
} btav_a2dp_codec_channel_mode_t;
-typedef enum {
- BTAV_A2DP_SCMST_DISABLED = 0x00,
- BTAV_A2DP_SCMST_ENABLED = 0x01
-} btav_a2dp_scmst_enable_status_t;
-
/*
* Structure for representing codec capability or configuration.
* It is used for configuring A2DP codec preference, and for reporting back
@@ -242,11 +237,6 @@ typedef struct {
}
} btav_a2dp_codec_config_t;
-typedef struct {
- btav_a2dp_scmst_enable_status_t enable_status;
- uint8_t cp_header;
-} btav_a2dp_scmst_info_t;
-
/** Callback for connection state change.
* state will have one of the values from btav_connection_state_t
*/
@@ -356,8 +346,7 @@ typedef struct {
/**
* Register the BtAv callbacks
*/
- bt_status_t (*init)(btav_sink_callbacks_t* callbacks,
- int max_connected_audio_devices);
+ bt_status_t (*init)(btav_sink_callbacks_t* callbacks);
/** connect to headset */
bt_status_t (*connect)(const RawAddress& bd_addr);
diff --git a/include/hardware/bt_common_types.h b/include/hardware/bt_common_types.h
index ee607e40f..0a315feda 100644
--- a/include/hardware/bt_common_types.h
+++ b/include/hardware/bt_common_types.h
@@ -71,8 +71,6 @@ typedef struct {
* the characteristic.
*/
uint8_t properties;
- uint16_t extended_properties;
-
uint16_t permissions;
} btgatt_db_element_t;
@@ -101,7 +99,6 @@ struct ApcfCommand {
uint16_t company_mask;
std::vector<uint8_t> data;
std::vector<uint8_t> data_mask;
- std::array<uint8_t, 16> irk; // 128 bit/16 octet IRK
};
#endif /* ANDROID_INCLUDE_BT_COMMON_TYPES_H */
diff --git a/include/hardware/bt_gatt_client.h b/include/hardware/bt_gatt_client.h
index 85d292546..6ea1c89c6 100644
--- a/include/hardware/bt_gatt_client.h
+++ b/include/hardware/bt_gatt_client.h
@@ -181,9 +181,6 @@ typedef void (*conn_updated_callback)(int conn_id, uint16_t interval,
uint16_t latency, uint16_t timeout,
uint8_t status);
-/** Callback when services are changed */
-typedef void (*service_changed_callback)(int conn_id);
-
typedef struct {
register_client_callback register_client_cb;
connect_callback open_cb;
@@ -204,15 +201,13 @@ typedef struct {
services_added_callback services_added_cb;
phy_updated_callback phy_updated_cb;
conn_updated_callback conn_updated_cb;
- service_changed_callback service_changed_cb;
} btgatt_client_callbacks_t;
/** Represents the standard BT-GATT client interface. */
typedef struct {
/** Registers a GATT client application with the stack */
- bt_status_t (*register_client)(const bluetooth::Uuid& uuid,
- bool eatt_support);
+ bt_status_t (*register_client)(const bluetooth::Uuid& uuid);
/** Unregister a client application from the stack */
bt_status_t (*unregister_client)(int client_if);
diff --git a/include/hardware/bt_gatt_server.h b/include/hardware/bt_gatt_server.h
index da2f04856..1b1db376c 100644
--- a/include/hardware/bt_gatt_server.h
+++ b/include/hardware/bt_gatt_server.h
@@ -138,8 +138,7 @@ typedef struct {
/** Represents the standard BT-GATT server interface. */
typedef struct {
/** Registers a GATT server application with the stack */
- bt_status_t (*register_server)(const bluetooth::Uuid& uuid,
- bool eatt_support);
+ bt_status_t (*register_server)(const bluetooth::Uuid& uuid);
/** Unregister a server application from the stack */
bt_status_t (*unregister_server)(int server_if);
diff --git a/include/hardware/bt_hearing_aid.h b/include/hardware/bt_hearing_aid.h
index 1bfb42270..191115947 100644
--- a/include/hardware/bt_hearing_aid.h
+++ b/include/hardware/bt_hearing_aid.h
@@ -59,8 +59,8 @@ class HearingAidInterface {
/** Disconnect from Hearing Aid */
virtual void Disconnect(const RawAddress& address) = 0;
- /** Add a hearing aid device to acceptlist */
- virtual void AddToAcceptlist(const RawAddress& address) = 0;
+ /** Add a hearing aid device to white list */
+ virtual void AddToWhiteList(const RawAddress& address) = 0;
/** Set the volume */
virtual void SetVolume(int8_t volume) = 0;
diff --git a/include/hardware/bt_hf_client.h b/include/hardware/bt_hf_client.h
index 048412153..d8f3a50e0 100644
--- a/include/hardware/bt_hf_client.h
+++ b/include/hardware/bt_hf_client.h
@@ -106,7 +106,7 @@ typedef enum {
BTHF_CLIENT_CMD_COMPLETE_ERROR_BUSY,
BTHF_CLIENT_CMD_COMPLETE_ERROR_NO_ANSWER,
BTHF_CLIENT_CMD_COMPLETE_ERROR_DELAYED,
- BTHF_CLIENT_CMD_COMPLETE_ERROR_REJECTLISTED,
+ BTHF_CLIENT_CMD_COMPLETE_ERROR_BLACKLISTED,
BTHF_CLIENT_CMD_COMPLETE_ERROR_CME
} bthf_client_cmd_complete_t;
diff --git a/include/hardware/bt_hh.h b/include/hardware/bt_hh.h
index 06272d2c9..b87b129bb 100644
--- a/include/hardware/bt_hh.h
+++ b/include/hardware/bt_hh.h
@@ -18,7 +18,6 @@
#define ANDROID_INCLUDE_BT_HH_H
#include <stdint.h>
-#include <string>
__BEGIN_DECLS
@@ -27,32 +26,17 @@ __BEGIN_DECLS
/* HH connection states */
typedef enum {
BTHH_CONN_STATE_CONNECTED = 0,
- BTHH_CONN_STATE_CONNECTING = 1,
- BTHH_CONN_STATE_DISCONNECTED = 2,
- BTHH_CONN_STATE_DISCONNECTING = 3,
- BTHH_CONN_STATE_UNKNOWN = 0xff,
+ BTHH_CONN_STATE_CONNECTING,
+ BTHH_CONN_STATE_DISCONNECTED,
+ BTHH_CONN_STATE_DISCONNECTING,
+ BTHH_CONN_STATE_FAILED_MOUSE_FROM_HOST,
+ BTHH_CONN_STATE_FAILED_KBD_FROM_HOST,
+ BTHH_CONN_STATE_FAILED_TOO_MANY_DEVICES,
+ BTHH_CONN_STATE_FAILED_NO_BTHID_DRIVER,
+ BTHH_CONN_STATE_FAILED_GENERIC,
+ BTHH_CONN_STATE_UNKNOWN
} bthh_connection_state_t;
-__END_DECLS
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string bthh_connection_state_text(
- const bthh_connection_state_t& state) {
- switch (state) {
- CASE_RETURN_TEXT(BTHH_CONN_STATE_CONNECTED);
- CASE_RETURN_TEXT(BTHH_CONN_STATE_CONNECTING);
- CASE_RETURN_TEXT(BTHH_CONN_STATE_DISCONNECTED);
- CASE_RETURN_TEXT(BTHH_CONN_STATE_DISCONNECTING);
- CASE_RETURN_TEXT(BTHH_CONN_STATE_UNKNOWN);
- default:
- return std::string("UNKNOWN[%u]", state);
- }
-}
-#undef CASE_RETURN_TEXT
-__BEGIN_DECLS
-
typedef enum {
BTHH_OK = 0,
BTHH_HS_HID_NOT_READY, /* handshake error : device not ready */
diff --git a/include/hardware/bt_le_audio.h b/include/hardware/bt_le_audio.h
deleted file mode 100644
index 01faa2c14..000000000
--- a/include/hardware/bt_le_audio.h
+++ /dev/null
@@ -1,94 +0,0 @@
-/*
- * Copyright 2019 HIMSA II K/S - www.himsa.com. Represented by EHIMA -
- * www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <array>
-#include <optional>
-
-#include "raw_address.h"
-
-namespace bluetooth {
-namespace le_audio {
-
-enum class ConnectionState {
- DISCONNECTED = 0,
- CONNECTING,
- CONNECTED,
- DISCONNECTING
-};
-
-enum class GroupStatus {
- IDLE = 0,
- STREAMING,
- SUSPENDED,
- RECONFIGURED,
- DESTROYED,
-};
-
-class LeAudioClientCallbacks {
- public:
- virtual ~LeAudioClientCallbacks() = default;
-
- /** Callback for profile connection state change */
- virtual void OnConnectionState(ConnectionState state,
- const RawAddress& address) = 0;
-
- /* Callback with group status update */
- virtual void OnGroupStatus(uint8_t group_id, GroupStatus group_status,
- uint8_t group_flags) = 0;
-
- /* Callback for newly recognized or reconfigured existing le audio device */
- virtual void OnAudioConf(const RawAddress& addr, uint8_t direction,
- uint8_t group_id, uint32_t snk_audio_location,
- uint32_t src_audio_location) = 0;
-
- /* Callback for available set member */
- virtual void OnSetMemberAvailable(const RawAddress& address,
- uint8_t group_id) = 0;
-};
-
-class LeAudioClientInterface {
- public:
- virtual ~LeAudioClientInterface() = default;
-
- /* Register the LeAudio callbacks */
- virtual void Initialize(LeAudioClientCallbacks* callbacks) = 0;
-
- /** Connect to LEAudio */
- virtual void Connect(const RawAddress& address) = 0;
-
- /** Disconnect from LEAudio */
- virtual void Disconnect(const RawAddress& address) = 0;
-
- /* Cleanup the LeAudio */
- virtual void Cleanup(void) = 0;
-
- /* Request to stream audio */
- virtual void GroupStream(uint8_t group_id, uint16_t content_type) = 0;
-
- /* Request to suspend audio */
- virtual void GroupSuspend(uint8_t group_id) = 0;
-
- /* Request to stop streaming audio */
- virtual void GroupStop(uint8_t group_id) = 0;
-};
-
-static constexpr uint8_t INSTANCE_ID_UNDEFINED = 0xFF;
-
-} /* namespace le_audio */
-} /* namespace bluetooth */
diff --git a/include/hardware/bt_mce.h b/include/hardware/bt_mce.h
new file mode 100644
index 000000000..0bb15d40d
--- /dev/null
+++ b/include/hardware/bt_mce.h
@@ -0,0 +1,54 @@
+/*
+ * Copyright (C) 2014 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef ANDROID_INCLUDE_BT_MCE_H
+#define ANDROID_INCLUDE_BT_MCE_H
+
+__BEGIN_DECLS
+
+/** MAS instance description */
+typedef struct {
+ int id;
+ int scn;
+ int msg_types;
+ char* p_name;
+} btmce_mas_instance_t;
+
+/** callback for get_remote_mas_instances */
+typedef void (*btmce_remote_mas_instances_callback)(
+ bt_status_t status, RawAddress* bd_addr, int num_instances,
+ btmce_mas_instance_t* instances);
+
+typedef struct {
+ /** set to sizeof(btmce_callbacks_t) */
+ size_t size;
+ btmce_remote_mas_instances_callback remote_mas_instances_cb;
+} btmce_callbacks_t;
+
+typedef struct {
+ /** set to size of this struct */
+ size_t size;
+
+ /** register BT MCE callbacks */
+ bt_status_t (*init)(btmce_callbacks_t* callbacks);
+
+ /** search for MAS instances on remote device */
+ bt_status_t (*get_remote_mas_instances)(RawAddress* bd_addr);
+} btmce_interface_t;
+
+__END_DECLS
+
+#endif /* ANDROID_INCLUDE_BT_MCE_H */
diff --git a/include/hardware/bt_sdp.h b/include/hardware/bt_sdp.h
index 93745bc2a..024ee40a1 100644
--- a/include/hardware/bt_sdp.h
+++ b/include/hardware/bt_sdp.h
@@ -32,8 +32,7 @@ typedef enum {
SDP_TYPE_PBAP_PSE, // Phone Book Profile - Server
SDP_TYPE_PBAP_PCE, // Phone Book Profile - Client
SDP_TYPE_OPP_SERVER, // Object Push Profile
- SDP_TYPE_SAP_SERVER, // SIM Access Profile
- SDP_TYPE_DIP // Device Identification Profile
+ SDP_TYPE_SAP_SERVER // SIM Access Profile
} bluetooth_sdp_types;
typedef struct _bluetooth_sdp_hdr {
@@ -98,16 +97,6 @@ typedef struct _bluetooth_sdp_sap_record {
bluetooth_sdp_hdr_overlay hdr;
} bluetooth_sdp_sap_record;
-typedef struct _bluetooth_sdp_dip_record {
- bluetooth_sdp_hdr_overlay hdr;
- uint16_t spec_id;
- uint16_t vendor;
- uint16_t vendor_id_source;
- uint16_t product;
- uint16_t version;
- bool primary_record;
-} bluetooth_sdp_dip_record;
-
typedef union {
bluetooth_sdp_hdr_overlay hdr;
bluetooth_sdp_mas_record mas;
@@ -116,7 +105,6 @@ typedef union {
bluetooth_sdp_pce_record pce;
bluetooth_sdp_ops_record ops;
bluetooth_sdp_sap_record sap;
- bluetooth_sdp_dip_record dip;
} bluetooth_sdp_record;
/** Callback for SDP search */
diff --git a/include/hardware/bt_sock.h b/include/hardware/bt_sock.h
index b0d32e6ef..04827aaf6 100644
--- a/include/hardware/bt_sock.h
+++ b/include/hardware/bt_sock.h
@@ -16,12 +16,6 @@
#pragma once
-#include <stddef.h>
-
-#include "bluetooth.h"
-#include "bluetooth/uuid.h"
-#include "raw_address.h"
-
__BEGIN_DECLS
#define BTSOCK_FLAG_ENCRYPT 1
diff --git a/include/hardware/bt_vc.h b/include/hardware/bt_vc.h
deleted file mode 100644
index f1a63d3dc..000000000
--- a/include/hardware/bt_vc.h
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright 2021 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <hardware/bluetooth.h>
-
-#include <variant>
-
-namespace bluetooth {
-namespace vc {
-
-enum class ConnectionState {
- DISCONNECTED = 0,
- CONNECTING,
- CONNECTED,
- DISCONNECTING
-};
-
-class VolumeControlCallbacks {
- public:
- virtual ~VolumeControlCallbacks() = default;
-
- /** Callback for profile connection state change */
- virtual void OnConnectionState(ConnectionState state,
- const RawAddress& address) = 0;
-
- /* Callback for the volume change changed on the device */
- virtual void OnVolumeStateChanged(const RawAddress& address, uint8_t volume,
- bool mute) = 0;
-
- /* Callback for the volume change changed on the group*/
- virtual void OnGroupVolumeStateChanged(int group_id, uint8_t volume,
- bool mute) = 0;
-};
-
-class VolumeControlInterface {
- public:
- virtual ~VolumeControlInterface() = default;
-
- /** Register the Volume Control callbacks */
- virtual void Init(VolumeControlCallbacks* callbacks) = 0;
-
- /** Closes the interface */
- virtual void Cleanup(void) = 0;
-
- /** Connect to Volume Control */
- virtual void Connect(const RawAddress& address) = 0;
-
- /** Disconnect from Volume Control */
- virtual void Disconnect(const RawAddress& address) = 0;
-
- /** Called when Volume control devices is unbonded */
- virtual void RemoveDevice(const RawAddress& address) = 0;
-
- /** Set the volume */
- virtual void SetVolume(std::variant<RawAddress, int> addr_or_group_id,
- uint8_t volume) = 0;
-};
-
-} /* namespace vc */
-} /* namespace bluetooth */
diff --git a/internal_include/Android.bp b/internal_include/Android.bp
index 825be2ac6..e55066067 100644
--- a/internal_include/Android.bp
+++ b/internal_include/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_headers {
name: "internal_include_headers",
export_include_dirs: ["./"],
diff --git a/internal_include/bt_target.h b/internal_include/bt_target.h
index 12f04d46a..4aca86822 100644
--- a/internal_include/bt_target.h
+++ b/internal_include/bt_target.h
@@ -35,14 +35,6 @@
#include "bt_types.h" /* This must be defined AFTER buildcfg.h */
-#ifndef FALSE
-#define FALSE false
-#endif
-
-#ifndef TRUE
-#define TRUE true
-#endif
-
//------------------Added from bdroid_buildcfg.h---------------------
#ifndef L2CAP_EXTFEA_SUPPORTED_MASK
#define L2CAP_EXTFEA_SUPPORTED_MASK \
@@ -72,7 +64,15 @@
#endif
#ifndef BTA_HH_ROLE
-#define BTA_HH_ROLE BTA_CENTRAL_ROLE_PREF
+#define BTA_HH_ROLE BTA_MASTER_ROLE_PREF
+#endif
+
+#ifndef BTA_HH_LE_INCLUDED
+#define BTA_HH_LE_INCLUDED TRUE
+#endif
+
+#ifndef BTA_AR_INCLUDED
+#define BTA_AR_INCLUDED TRUE
#endif
#ifndef BTA_AV_SINK_INCLUDED
@@ -176,6 +176,24 @@
#define L2CAP_CMD_BUF_SIZE BT_SMALL_BUFFER_SIZE
#endif
+#ifndef L2CAP_USER_TX_BUF_SIZE
+#define L2CAP_USER_TX_BUF_SIZE BT_DEFAULT_BUFFER_SIZE
+#endif
+
+#ifndef L2CAP_USER_RX_BUF_SIZE
+#define L2CAP_USER_RX_BUF_SIZE BT_DEFAULT_BUFFER_SIZE
+#endif
+
+/* Sends L2CAP segmented packets in ERTM mode */
+#ifndef L2CAP_FCR_TX_BUF_SIZE
+#define L2CAP_FCR_TX_BUF_SIZE BT_DEFAULT_BUFFER_SIZE
+#endif
+
+/* Receives L2CAP segmented packets in ERTM mode */
+#ifndef L2CAP_FCR_RX_BUF_SIZE
+#define L2CAP_FCR_RX_BUF_SIZE BT_DEFAULT_BUFFER_SIZE
+#endif
+
#ifndef L2CAP_FCR_ERTM_BUF_SIZE
#define L2CAP_FCR_ERTM_BUF_SIZE (10240 + 24)
#endif
@@ -198,6 +216,11 @@
#define OBX_LRG_DATA_BUF_SIZE (8080 + 26)
#endif
+/* Used to send data to L2CAP. */
+#ifndef GAP_DATA_BUF_SIZE
+#define GAP_DATA_BUF_SIZE BT_DEFAULT_BUFFER_SIZE
+#endif
+
/* BNEP data and protocol messages. */
#ifndef BNEP_BUF_SIZE
#define BNEP_BUF_SIZE BT_DEFAULT_BUFFER_SIZE
@@ -276,6 +299,16 @@
#define BTM_INQ_DB_SIZE 40
#endif
+/* The default scan mode */
+#ifndef BTM_DEFAULT_SCAN_TYPE
+#define BTM_DEFAULT_SCAN_TYPE BTM_SCAN_TYPE_INTERLACED
+#endif
+
+/* Should connections to unknown devices be allowed when not discoverable? */
+#ifndef BTM_ALLOW_CONN_IF_NONDISCOVER
+#define BTM_ALLOW_CONN_IF_NONDISCOVER TRUE
+#endif
+
/* Sets the Page_Scan_Window: the length of time that the device is performing
* a page scan. */
#ifndef BTM_DEFAULT_CONN_WINDOW
@@ -366,6 +399,11 @@
#define BTM_MAX_PM_RECORDS 2
#endif
+/* This is set to show debug trace messages for the power manager. */
+#ifndef BTM_PM_DEBUG
+#define BTM_PM_DEBUG FALSE
+#endif
+
/* If the user does not respond to security process requests within this many
* seconds, a negative response would be sent automatically.
* 30 is LMP response timeout value */
@@ -396,6 +434,19 @@
#define BTM_LOCAL_IO_CAPS_BLE BTM_IO_CAP_KBDISP
#endif
+/* The default MITM Protection Requirement (for Simple Pairing)
+ * Possible values are BTM_AUTH_SP_YES or BTM_AUTH_SP_NO */
+#ifndef BTM_DEFAULT_AUTH_REQ
+#define BTM_DEFAULT_AUTH_REQ BTM_AUTH_SP_NO
+#endif
+
+/* The default MITM Protection Requirement for dedicated bonding using Simple
+ * Pairing
+ * Possible values are BTM_AUTH_AP_YES or BTM_AUTH_AP_NO */
+#ifndef BTM_DEFAULT_DD_AUTH_REQ
+#define BTM_DEFAULT_DD_AUTH_REQ BTM_AUTH_AP_YES
+#endif
+
/* TRUE to include Sniff Subrating */
#ifndef BTM_SSR_INCLUDED
#define BTM_SSR_INCLUDED TRUE
@@ -481,6 +532,16 @@
#define L2CAP_WAKE_PARKED_LINK TRUE
#endif
+/* Whether link wants to be the master or the slave. */
+#ifndef L2CAP_DESIRED_LINK_ROLE
+#define L2CAP_DESIRED_LINK_ROLE HCI_ROLE_MASTER
+#endif
+
+/* Include Non-Flushable Packet Boundary Flag feature of Lisbon */
+#ifndef L2CAP_NON_FLUSHABLE_PB_INCLUDED
+#define L2CAP_NON_FLUSHABLE_PB_INCLUDED TRUE
+#endif
+
/* Minimum number of ACL credit for high priority link */
#ifndef L2CAP_HIGH_PRI_MIN_XMIT_QUOTA
#define L2CAP_HIGH_PRI_MIN_XMIT_QUOTA 5
@@ -513,6 +574,11 @@
#define L2CAP_ROUND_ROBIN_CHANNEL_SERVICE TRUE
#endif
+/* used for monitoring eL2CAP data flow */
+#ifndef L2CAP_ERTM_STATS
+#define L2CAP_ERTM_STATS FALSE
+#endif
+
/* Used for conformance testing ONLY: When TRUE lets scriptwrapper overwrite
* info response */
#ifndef L2CAP_CONFORMANCE_TESTING
@@ -571,6 +637,16 @@
* ATT/GATT Protocol/Profile Settings
*
*****************************************************************************/
+#ifndef BLE_LLT_INCLUDED
+#define BLE_LLT_INCLUDED TRUE
+#endif
+
+#ifndef BLE_DELAY_REQUEST_ENC
+/* This flag is to work around IPHONE problem, We need to wait for iPhone ready
+ before send encryption request to iPhone */
+#define BLE_DELAY_REQUEST_ENC FALSE
+#endif
+
#ifndef GATT_MAX_SR_PROFILES
#define GATT_MAX_SR_PROFILES 32 /* max is 32 */
#endif
@@ -627,6 +703,11 @@
*
*****************************************************************************/
+/* This is set to enable SDP server functionality. */
+#ifndef SDP_SERVER_ENABLED
+#define SDP_SERVER_ENABLED TRUE
+#endif
+
/* The maximum number of SDP records the server can support. */
#ifndef SDP_MAX_RECORDS
#define SDP_MAX_RECORDS 30
@@ -682,6 +763,11 @@
#define SDP_MTU_SIZE 1024
#endif
+/* The flush timeout for the L2CAP configuration. */
+#ifndef SDP_FLUSH_TO
+#define SDP_FLUSH_TO 0xFFFF
+#endif
+
/* The name for security authorization. */
#ifndef SDP_SERVICE_NAME
#define SDP_SERVICE_NAME "Service Discovery"
@@ -762,6 +848,88 @@
/******************************************************************************
*
+ * OBEX
+ *
+ *****************************************************************************/
+
+/*
+ * Buffer size to reassemble the SDU.
+ * It will allow buffers to be used that are larger than the L2CAP_MAX_MTU.
+ */
+#ifndef OBX_USER_RX_BUF_SIZE
+#define OBX_USER_RX_BUF_SIZE OBX_LRG_DATA_BUF_SIZE
+#endif
+
+/*
+ * Buffer size to hold the SDU.
+ * It will allow buffers to be used that are larger than the L2CAP_MAX_MTU.
+ */
+#ifndef OBX_USER_TX_BUF_SIZE
+#define OBX_USER_TX_BUF_SIZE OBX_LRG_DATA_BUF_SIZE
+#endif
+
+/* Buffer size used to hold MPS segments during SDU reassembly. */
+#ifndef OBX_FCR_RX_BUF_SIZE
+#define OBX_FCR_RX_BUF_SIZE BT_DEFAULT_BUFFER_SIZE
+#endif
+
+/*
+ * Buffer size used to hold MPS segments used in (re)transmissions.
+ * The size of each buffer must be able to hold the maximum MPS segment size
+ * passed in L2CA_SetFCROptions plus BT_HDR (8) + HCI preamble (4) +
+ * L2CAP_MIN_OFFSET (11 - as of BT 2.1 + EDR Spec).
+ */
+#ifndef OBX_FCR_TX_BUF_SIZE
+#define OBX_FCR_TX_BUF_SIZE BT_DEFAULT_BUFFER_SIZE
+#endif
+
+/*
+ * Size of the transmission window when using enhanced retransmission mode.
+ * Not used in basic and streaming modes. Range: 1 - 63
+ */
+#ifndef OBX_FCR_OPT_TX_WINDOW_SIZE_BR_EDR
+#define OBX_FCR_OPT_TX_WINDOW_SIZE_BR_EDR 20
+#endif
+
+/*
+ * Number of transmission attempts for a single I-Frame before taking
+ * Down the connection. Used In ERTM mode only. Value is Ignored in basic and
+ * Streaming modes.
+ * Range: 0, 1-0xFF
+ * 0 - infinite retransmissions
+ * 1 - single transmission
+ */
+#ifndef OBX_FCR_OPT_MAX_TX_B4_DISCNT
+#define OBX_FCR_OPT_MAX_TX_B4_DISCNT 20
+#endif
+
+/*
+ * Retransmission Timeout
+ * Range: Minimum 2000 (2 secs) on BR/EDR when supporting PBF.
+ */
+#ifndef OBX_FCR_OPT_RETX_TOUT
+#define OBX_FCR_OPT_RETX_TOUT 2000
+#endif
+
+/*
+ * Monitor Timeout
+ * Range: Minimum 12000 (12 secs) on BR/EDR when supporting PBF.
+ */
+#ifndef OBX_FCR_OPT_MONITOR_TOUT
+#define OBX_FCR_OPT_MONITOR_TOUT 12000
+#endif
+
+/*
+ * Maximum PDU payload size.
+ * Suggestion: The maximum amount of data that will fit into a 3-DH5 packet.
+ * Range: 2 octets
+ */
+#ifndef OBX_FCR_OPT_MAX_PDU_SIZE
+#define OBX_FCR_OPT_MAX_PDU_SIZE L2CAP_MPS_OVER_BR_EDR
+#endif
+
+/******************************************************************************
+ *
* BNEP
*
*****************************************************************************/
@@ -775,6 +943,14 @@
#define BNEP_SUPPORTS_STATUS_API TRUE
#endif
+/*
+ * When BNEP connection changes roles after the connection is established
+ * we will do an authentication check again on the new role
+*/
+#ifndef BNEP_DO_AUTH_FOR_ROLE_SWITCH
+#define BNEP_DO_AUTH_FOR_ROLE_SWITCH TRUE
+#endif
+
/* Maximum number of protocol filters supported. */
#ifndef BNEP_MAX_PROT_FILTERS
#define BNEP_MAX_PROT_FILTERS 5
@@ -785,9 +961,14 @@
#define BNEP_MAX_MULTI_FILTERS 5
#endif
+/* Minimum MTU size. */
+#ifndef BNEP_MIN_MTU_SIZE
+#define BNEP_MIN_MTU_SIZE L2CAP_MTU_SIZE
+#endif
+
/* Preferred MTU size. */
#ifndef BNEP_MTU_SIZE
-#define BNEP_MTU_SIZE L2CAP_MTU_SIZE
+#define BNEP_MTU_SIZE BNEP_MIN_MTU_SIZE
#endif
/* Maximum number of buffers allowed in transmit data queue. */
@@ -826,11 +1007,6 @@
#define AVDT_PROTECT_SIZE 90
#endif
-/* Default sink delay value in ms. */
-#ifndef AVDT_SINK_DELAY_MS
-#define AVDT_SINK_DELAY_MS 300
-#endif
-
/******************************************************************************
*
* PAN
@@ -854,6 +1030,11 @@
#define PAN_SUPPORTS_ROLE_PANU TRUE
#endif
+/* This will enable the GN role */
+#ifndef PAN_SUPPORTS_ROLE_GN
+#define PAN_SUPPORTS_ROLE_GN TRUE
+#endif
+
/* This will enable the NAP role */
#ifndef PAN_SUPPORTS_ROLE_NAP
#define PAN_SUPPORTS_ROLE_NAP TRUE
@@ -874,6 +1055,11 @@
#define PAN_NAP_DEFAULT_SERVICE_NAME "Network Access Point Service"
#endif
+/* Default service name for GN role */
+#ifndef PAN_GN_DEFAULT_SERVICE_NAME
+#define PAN_GN_DEFAULT_SERVICE_NAME "Group Network Service"
+#endif
+
/* Default service name for PANU role */
#ifndef PAN_PANU_DEFAULT_SERVICE_NAME
#define PAN_PANU_DEFAULT_SERVICE_NAME "PAN User Service"
@@ -884,11 +1070,31 @@
#define PAN_NAP_DEFAULT_DESCRIPTION "NAP"
#endif
+/* Default description for GN role service */
+#ifndef PAN_GN_DEFAULT_DESCRIPTION
+#define PAN_GN_DEFAULT_DESCRIPTION "GN"
+#endif
+
/* Default description for PANU role service */
#ifndef PAN_PANU_DEFAULT_DESCRIPTION
#define PAN_PANU_DEFAULT_DESCRIPTION "PANU"
#endif
+/* Default Security level for PANU role. */
+#ifndef PAN_PANU_SECURITY_LEVEL
+#define PAN_PANU_SECURITY_LEVEL 0
+#endif
+
+/* Default Security level for GN role. */
+#ifndef PAN_GN_SECURITY_LEVEL
+#define PAN_GN_SECURITY_LEVEL 0
+#endif
+
+/* Default Security level for NAP role. */
+#ifndef PAN_NAP_SECURITY_LEVEL
+#define PAN_NAP_SECURITY_LEVEL 0
+#endif
+
/******************************************************************************
*
* GAP
@@ -934,7 +1140,11 @@
#endif
#ifndef HID_DEV_MTU_SIZE
-#define HID_DEV_MTU_SIZE 512
+#define HID_DEV_MTU_SIZE 64
+#endif
+
+#ifndef HID_DEV_FLUSH_TO
+#define HID_DEV_FLUSH_TO 0xffff
#endif
/*************************************************************************
@@ -967,6 +1177,10 @@
#define HID_HOST_MTU 640
#endif
+#ifndef HID_HOST_FLUSH_TO
+#define HID_HOST_FLUSH_TO 0xffff
+#endif
+
#ifndef HID_HOST_MAX_CONN_RETRY
#define HID_HOST_MAX_CONN_RETRY 1
#endif
@@ -1036,6 +1250,10 @@
"5)),(\"roam\",(0,1)),(\"battchg\",(0-5)),(\"callheld\",(0-2))"
#endif
+#ifndef BTA_DM_AVOID_A2DP_ROLESWITCH_ON_INQUIRY
+#define BTA_DM_AVOID_A2DP_ROLESWITCH_ON_INQUIRY TRUE
+#endif
+
/******************************************************************************
*
* Tracing: Include trace header file here.
diff --git a/internal_include/bt_trace.h b/internal_include/bt_trace.h
index 50681ae24..f27563dea 100644
--- a/internal_include/bt_trace.h
+++ b/internal_include/bt_trace.h
@@ -24,55 +24,6 @@
extern "C" {
#endif
-/*****************************************************************************/
-
-/* Define trace levels */
-typedef enum {
- BT_TRACE_LEVEL_NONE = 0, /* No trace messages to be generated */
- BT_TRACE_LEVEL_ERROR = 1, /* Error condition trace messages */
- BT_TRACE_LEVEL_WARNING = 2, /* Warning condition trace messages */
- BT_TRACE_LEVEL_API = 3, /* API traces */
- BT_TRACE_LEVEL_EVENT = 4, /* Debug messages for events */
- BT_TRACE_LEVEL_DEBUG = 5, /* Full debug messages */
- BT_TRACE_LEVEL_VERBOSE = 6, /* Verbose debug messages */
-} tLEGACY_TRACE_LEVEL;
-
-#define TRACE_CTRL_GENERAL 0x00000000
-
-#define TRACE_LAYER_MASK 0x00ff0000
-#define TRACE_GET_LAYER(x) ((((uint32_t)(x)) & TRACE_LAYER_MASK) >> 16)
-
-#define TRACE_LAYER_NONE 0x00000000
-#define TRACE_LAYER_HCI 0x00070000
-#define TRACE_LAYER_L2CAP 0x00080000
-#define TRACE_LAYER_RFCOMM 0x00090000
-#define TRACE_LAYER_SDP 0x000a0000
-#define TRACE_LAYER_BTM 0x000d0000
-#define TRACE_LAYER_BNEP 0x001b0000
-#define TRACE_LAYER_PAN 0x001c0000
-#define TRACE_LAYER_HID 0x001e0000
-#define TRACE_LAYER_AVP 0x00200000
-#define TRACE_LAYER_A2DP 0x00210000
-#define TRACE_LAYER_SMP 0x00260000
-
-#define TRACE_LAYER_MAX_NUM 0x0031
-
-#define TRACE_ORG_MASK 0x0000ff00
-#define TRACE_GET_ORG(x) ((((uint32_t)(x)) & TRACE_ORG_MASK) >> 8)
-
-#define TRACE_ORG_STACK 0x00000000
-#define TRACE_ORG_APPL 0x00000500
-#define TRACE_ORG_USER_SCR 0x00000800
-
-#define TRACE_TYPE_MASK 0x000000ff
-#define TRACE_GET_TYPE(x) (((uint32_t)(x)) & TRACE_TYPE_MASK)
-
-#define TRACE_TYPE_ERROR 0x00000000
-#define TRACE_TYPE_WARNING 0x00000001
-#define TRACE_TYPE_API 0x00000002
-#define TRACE_TYPE_EVENT 0x00000003
-#define TRACE_TYPE_DEBUG 0x00000004
-
static const char BTE_LOGMSG_MODULE[] = "bte_logmsg_module";
/* BTE tracing IDs for debug purposes */
@@ -203,6 +154,10 @@ static const char BTE_LOGMSG_MODULE[] = "bte_logmsg_module";
#define RFCOMM_INITIAL_TRACE_LEVEL BT_TRACE_LEVEL_WARNING
#endif
+#ifndef SDP_INITIAL_TRACE_LEVEL
+#define SDP_INITIAL_TRACE_LEVEL BT_TRACE_LEVEL_WARNING
+#endif
+
#ifndef BNEP_INITIAL_TRACE_LEVEL
#define BNEP_INITIAL_TRACE_LEVEL BT_TRACE_LEVEL_WARNING
#endif
diff --git a/internal_include/bte.h b/internal_include/bte.h
index 7839babb0..754cf53b5 100644
--- a/internal_include/bte.h
+++ b/internal_include/bte.h
@@ -98,7 +98,7 @@ void bte_get_startup_options(
#define BTE_HCISU_USERIAL_OK 1
typedef void(tUSERIAL_MSG_CBACK)(int status);
typedef struct tHCISU_USERIAL_MSG_tag {
- BT_HDR_RIGID hdr;
+ BT_HDR hdr;
tUSERIAL_MSG_CBACK* p_cback;
uint8_t port; /* port number */
uint8_t op;
diff --git a/main/Android.bp b/main/Android.bp
index 67cb3eca4..90490ef48 100644
--- a/main/Android.bp
+++ b/main/Android.bp
@@ -1,18 +1,10 @@
// Bluetooth main HW module / shared library for target
// ========================================================
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "LibBluetoothSources",
srcs: [
"bte_conf.cc",
+ "bte_init.cc",
"bte_init_cpp_logging.cc",
"bte_logmsg.cc",
"bte_main.cc",
@@ -30,7 +22,6 @@ cc_library_static {
include_dirs: [
"system/bt",
"system/bt/gd",
- "system/bt/gd/rust/shim",
"system/bt/bta/include",
"system/bt/bta/sys",
"system/bt/bta/dm",
@@ -52,15 +43,9 @@ cc_library_static {
"system/security/keystore/include",
"hardware/interfaces/keymaster/4.0/support/include",
],
- shared_libs: [
- "libflatbuffers-cpp",
- ],
generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- "BluetoothGeneratedDumpsysDataSchema_h",
"BluetoothGeneratedPackets_h",
],
- header_libs: ["libbt_callbacks_cxx_headers"],
host_supported: true,
}
@@ -94,22 +79,22 @@ cc_library_shared {
],
logtags: ["../EventLogTags.logtags"],
shared_libs: [
- "android.hardware.bluetooth.a2dp@1.0",
- "android.hardware.bluetooth.audio@2.0",
- "android.hardware.bluetooth.audio@2.1",
"android.hardware.bluetooth@1.0",
"android.hardware.bluetooth@1.1",
- "libbinder_ndk",
- "libcrypto",
+ "android.hardware.bluetooth.a2dp@1.0",
+ "android.hardware.bluetooth.audio@2.0",
+ "libaaudio",
"libcutils",
- "libflatbuffers-cpp",
+ "libdl",
+ "libfmq",
"libhidlbase",
"liblog",
"libprocessgroup",
"libprotobuf-cpp-lite",
- "libtinyxml2",
"libutils",
+ "libtinyxml2",
"libz",
+ "libcrypto",
],
static_libs: [
"libbte",
@@ -119,7 +104,6 @@ cc_library_shared {
"libg722codec",
"libudrv-uipc",
"libbluetooth_gd", // Gabeldorsche
- "libbluetooth_rust_interop",
],
whole_static_libs: [
"libbt-bta",
@@ -133,20 +117,6 @@ cc_library_shared {
"libosi",
"libbt-protos-lite",
],
- target: {
- android: {
- shared_libs: [
- "android.system.suspend.control-V1-ndk",
- "android.system.suspend@1.0",
- "libaaudio",
- "libfmq",
- ],
- required: [
- "libldacBT_enc",
- "libldacBT_abr",
- ],
- },
- },
// Shared library link options.
// References to global symbols and functions should bind to the library
// itself. This is to avoid issues with some of the unit/system tests
@@ -156,14 +126,15 @@ cc_library_shared {
required: [
"bt_did.conf",
"bt_stack.conf",
+ "libldacBT_enc",
+ "libldacBT_abr",
],
cflags: [
"-DBUILDCFG",
],
sanitize: {
- never: true,
+ scs: true,
},
- host_supported: true,
}
cc_library_static {
@@ -178,7 +149,6 @@ cc_library_static {
include_dirs: [
"system/bt",
"system/bt/gd",
- "system/bt/gd/rust/shim",
"system/bt/bta/include",
"system/bt/btcore/include",
"system/bt/btif/include",
@@ -188,86 +158,12 @@ cc_library_static {
"system/bt/utils/include",
],
generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
"BluetoothGeneratedPackets_h",
- "BluetoothGeneratedDumpsysDataSchema_h",
],
cflags: [
"-DBUILDCFG",
],
- shared_libs: [
- "libflatbuffers-cpp",
- ],
whole_static_libs: [
"libbluetooth_gd", // Gabeldorsche
],
}
-
-cc_test {
- name: "net_test_main_shim",
- test_suites: ["device-tests"],
- host_supported: true,
- test_options: {
- unit_test: true,
- },
- defaults: ["fluoride_defaults"],
- include_dirs: [
- "system/bt",
- "system/bt/gd",
- "system/bt/stack/include",
- ],
- srcs: [
- ":TestMockBta",
- ":TestMockBtif",
- ":TestMockLegacyHciCommands",
- ":TestMockMainShimEntry",
- ":TestMockStack",
- "shim/acl_api.cc",
- "shim/acl.cc",
- "shim/acl_legacy_interface.cc",
- "shim/btm_api.cc",
- "shim/btm.cc",
- "shim/config.cc",
- "shim/controller.cc",
- "shim/dumpsys.cc",
- "shim/hci_layer.cc",
- "shim/l2c_api.cc",
- "shim/le_advertising_manager.cc",
- "shim/le_scanning_manager.cc",
- "shim/link_policy.cc",
- "shim/metric_id_api.cc",
- "shim/metrics_api.cc",
- "shim/shim.cc",
- "shim/stack.cc",
- "test/main_shim_test.cc",
- ],
- static_libs: [
- "libbt-common",
- "libbt-protos-lite",
- "libgmock",
- "liblog",
- "libosi",
- "libbtdevice",
- ],
- shared_libs: [
- "libcrypto",
- "libflatbuffers-cpp",
- "libprotobuf-cpp-lite",
- ],
- sanitize: {
- address: true,
- all_undefined: true,
- cfi: true,
- integer_overflow: true,
- scs: true,
- diag: {
- undefined : true
- },
- },
- generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- "BluetoothGeneratedDumpsysDataSchema_h",
- "BluetoothGeneratedDumpsysBundledSchema_h",
- "BluetoothGeneratedPackets_h",
- ],
-}
diff --git a/main/BUILD.gn b/main/BUILD.gn
index 9604f597b..8152e3b91 100644
--- a/main/BUILD.gn
+++ b/main/BUILD.gn
@@ -15,39 +15,22 @@
#
config("libbluetooth_config") {
- include_dirs = [ "../include" ]
+ include_dirs = [
+ "../include",
+ ]
}
-# Complete static library for linking with Rust
-static_library("bluetooth-static") {
- complete_static_lib = true
+shared_library("bluetooth") {
+ # HAL layer
sources = [
- "//bt/service/hal/bluetooth_interface.cc",
- "//bt/service/logging_helpers.cc",
- ]
-
- configs += [
- "//bt:target_defaults"
+ "//btif/src/bluetooth.cc",
]
- deps = [
- ":bluetooth",
- ]
-}
-
-# Configure libbluetooth as either dynamic or static library
-if (defined(use.bt_dynlib) && use.bt_dynlib) {
- lib_type = "shared_library"
-} else {
- lib_type = "static_library"
-}
-
-target(lib_type, "bluetooth") {
-
- # Platform specific
- sources = [
+ # platform specific
+ sources += [
"bte_conf.cc",
+ "bte_init.cc",
"bte_init_cpp_logging.cc",
"bte_logmsg.cc",
"bte_main.cc",
@@ -57,68 +40,58 @@ target(lib_type, "bluetooth") {
public_configs = [ ":libbluetooth_config" ]
include_dirs = [
- "//bt/",
- "//bt/bta/include",
- "//bt/bta/sys",
- "//bt/bta/dm",
- "//bt/btcore/include",
- "//bt/internal_include",
- "//bt/stack/include",
- "//bt/stack/l2cap",
- "//bt/stack/a2dp",
- "//bt/stack/btm",
- "//bt/stack/avdt",
- "//bt/hci",
- "//bt/hci/include",
- "//bt/udrv/include",
- "//bt/btif/include",
- "//bt/btif/co",
- "//bt/hci/includ",
- "//bt/vnd/include",
- "//bt/brcm/include",
- "//bt/embdrv/sbc/encoder/include",
- "//bt/embdrv/sbc/decoder/include",
- "//bt/utils/include",
- "//bt/test/suite",
+ "//",
+ "//bta/include",
+ "//bta/sys",
+ "//bta/dm",
+ "//btcore/include",
+ "//internal_include",
+ "//stack/include",
+ "//stack/l2cap",
+ "//stack/a2dp",
+ "//stack/btm",
+ "//stack/avdt",
+ "//hci",
+ "//hci/include",
+ "//udrv/include",
+ "//btif/include",
+ "//btif/co",
+ "//hci/includ",
+ "//vnd/include",
+ "//brcm/include",
+ "//embdrv/sbc/encoder/include",
+ "//embdrv/sbc/decoder/include",
+ "//utils/include",
+ "//test/suite",
]
deps = [
- "//bt/audio_hal_interface",
- "//bt/bta",
- "//bt/btcore",
- "//bt/btif",
- "//bt/device",
- "//bt/embdrv/g722",
- "//bt/embdrv/sbc",
- "//bt/gd:libbluetooth_gd",
- "//bt/hci",
- "//bt/main/shim:LibBluetoothShimSources",
- "//bt/osi",
- "//bt/packet",
- "//bt/stack",
- "//bt/udrv",
- "//bt/utils",
- ]
-
- configs += [
- "//bt:target_defaults",
- "//bt:external_tinyxml2",
- "//bt:external_flatbuffers",
+ "//bta",
+ "//btcore",
+ "//btif",
+ "//device",
+ "//embdrv/g722",
+ "//embdrv/sbc",
+ "//hci",
+ "//osi",
+ "//packet",
+ "//stack",
+ "//third_party/libchrome:base",
+ "//third_party/tinyxml2",
+ "//udrv",
+ "//utils",
]
cflags_c = [
"-Lobj/osi",
"-losi",
]
-
libs = [
- "dl",
- "pthread",
- "resolv",
- "rt",
- "z",
- "bt_shim_ffi",
+ "-ldl",
+ "-lpthread",
+ "-lresolv",
+ "-lrt",
+ "-lz",
+ "-latomic",
]
-
- lib_dirs = [ "${root_out_dir}/rust" ]
}
diff --git a/main/bte_conf.cc b/main/bte_conf.cc
index 4634ccec1..a60015a4e 100644
--- a/main/bte_conf.cc
+++ b/main/bte_conf.cc
@@ -35,7 +35,7 @@ void bte_load_did_conf(const char* p_path) {
std::unique_ptr<config_t> config = config_new(p_path);
if (!config) {
- LOG_ERROR("%s unable to load DID config '%s'.", __func__, p_path);
+ LOG_ERROR(LOG_TAG, "%s unable to load DID config '%s'.", __func__, p_path);
return;
}
@@ -44,11 +44,11 @@ void bte_load_did_conf(const char* p_path) {
snprintf(section_name, sizeof(section_name), "DID%d", i);
if (!config_has_section(*config, section_name)) {
- LOG_INFO("%s no section named %s.", __func__, section_name);
+ LOG_DEBUG(LOG_TAG, "%s no section named %s.", __func__, section_name);
break;
}
- tSDP_DI_RECORD record;
+ tBTA_DI_RECORD record;
record.vendor =
config_get_int(*config, section_name, "vendorId", LMP_COMPID_GOOGLE);
record.vendor_id_source = config_get_int(
@@ -75,26 +75,29 @@ void bte_load_did_conf(const char* p_path) {
if (record.vendor_id_source != DI_VENDOR_ID_SOURCE_BTSIG &&
record.vendor_id_source != DI_VENDOR_ID_SOURCE_USBIF) {
- LOG_ERROR("%s invalid vendor id source %d; ignoring DID record %d.",
+ LOG_ERROR(LOG_TAG,
+ "%s invalid vendor id source %d; ignoring DID record %d.",
__func__, record.vendor_id_source, i);
continue;
}
- LOG_INFO("Device ID record %d : %s", i,
- (record.primary_record ? "primary" : "not primary"));
- LOG_INFO(" vendorId = %04x", record.vendor);
- LOG_INFO(" vendorIdSource = %04x", record.vendor_id_source);
- LOG_INFO(" product = %04x", record.product);
- LOG_INFO(" version = %04x", record.version);
- LOG_INFO(" clientExecutableURL = %s", record.client_executable_url);
- LOG_INFO(" serviceDescription = %s", record.service_description);
- LOG_INFO(" documentationURL = %s", record.documentation_url);
+ LOG_DEBUG(LOG_TAG, "Device ID record %d : %s", i,
+ (record.primary_record ? "primary" : "not primary"));
+ LOG_DEBUG(LOG_TAG, " vendorId = %04x", record.vendor);
+ LOG_DEBUG(LOG_TAG, " vendorIdSource = %04x", record.vendor_id_source);
+ LOG_DEBUG(LOG_TAG, " product = %04x", record.product);
+ LOG_DEBUG(LOG_TAG, " version = %04x", record.version);
+ LOG_DEBUG(LOG_TAG, " clientExecutableURL = %s",
+ record.client_executable_url);
+ LOG_DEBUG(LOG_TAG, " serviceDescription = %s",
+ record.service_description);
+ LOG_DEBUG(LOG_TAG, " documentationURL = %s", record.documentation_url);
uint32_t record_handle;
tBTA_STATUS status = BTA_DmSetLocalDiRecord(&record, &record_handle);
if (status != BTA_SUCCESS) {
- LOG_ERROR("%s unable to set device ID record %d: error %d.", __func__, i,
- status);
+ LOG_ERROR(LOG_TAG, "%s unable to set device ID record %d: error %d.",
+ __func__, i, status);
}
}
}
diff --git a/main/bte_init.cc b/main/bte_init.cc
new file mode 100644
index 000000000..7addb18e7
--- /dev/null
+++ b/main/bte_init.cc
@@ -0,0 +1,103 @@
+/******************************************************************************
+ *
+ * Copyright 2000-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+/******************************************************************************
+ *
+ * This module contains the routines that initialize the stack components.
+ * It must be called before the BTU task is started.
+ *
+ ******************************************************************************/
+
+#include <string.h>
+#include "bt_target.h"
+
+#include "bte.h"
+
+/* Include initialization functions definitions */
+#include "port_api.h"
+
+#if (BNEP_INCLUDED == TRUE)
+#include "bnep_api.h"
+#endif
+
+#include "gap_api.h"
+
+#if (PAN_INCLUDED == TRUE)
+#include "pan_api.h"
+#endif
+
+#include "avrc_api.h"
+#include "a2dp_api.h"
+
+#if (HID_HOST_INCLUDED == TRUE)
+#include "hidh_api.h"
+#endif
+
+#include "gatt_api.h"
+#include "smp_api.h"
+
+/*****************************************************************************
+ * F U N C T I O N S *
+ *****************************************************************************/
+
+/*****************************************************************************
+ *
+ * Function BTE_InitStack
+ *
+ * Description Initialize control block memory for each component.
+ *
+ * Note: The core stack components must be called
+ * before creating the BTU Task. The rest of the
+ * components can be initialized at a later time if desired
+ * as long as the component's init function is called
+ * before accessing any of its functions.
+ *
+ * Returns void
+ *
+ *****************************************************************************/
+void BTE_InitStack(void) {
+ /* Initialize the optional stack components */
+ RFCOMM_Init();
+
+/**************************
+ * BNEP and its profiles **
+ **************************/
+#if (BNEP_INCLUDED == TRUE)
+ BNEP_Init();
+
+#if (PAN_INCLUDED == TRUE)
+ PAN_Init();
+#endif /* PAN */
+#endif /* BNEP Included */
+
+/**************************
+ * AVDT and its profiles **
+ **************************/
+ A2DP_Init();
+
+ AVRC_Init();
+
+ /***********
+ * Others **
+ ***********/
+ GAP_Init();
+
+#if (HID_HOST_INCLUDED == TRUE)
+ HID_HostInit();
+#endif
+}
diff --git a/main/bte_logmsg.cc b/main/bte_logmsg.cc
index fbdfb51f4..22c357dc3 100644
--- a/main/bte_logmsg.cc
+++ b/main/bte_logmsg.cc
@@ -57,8 +57,6 @@
#include "smp_api.h"
-#include "gd/common/init_flags.h"
-
#ifndef DEFAULT_CONF_TRACE_LEVEL
#define DEFAULT_CONF_TRACE_LEVEL BT_TRACE_LEVEL_WARNING
#endif
@@ -183,31 +181,26 @@ void LogMsg(uint32_t trace_set_mask, const char* fmt_str, ...) {
vsnprintf(&buffer[MSG_BUFFER_OFFSET], BTE_LOG_MAX_SIZE, fmt_str, ap);
va_end(ap);
-#undef LOG_TAG
-#define LOG_TAG bt_layer_tags[trace_layer]
-
switch (TRACE_GET_TYPE(trace_set_mask)) {
case TRACE_TYPE_ERROR:
- LOG_ERROR("%s", buffer);
+ LOG_ERROR(bt_layer_tags[trace_layer], "%s", buffer);
break;
case TRACE_TYPE_WARNING:
- LOG_WARN("%s", buffer);
+ LOG_WARN(bt_layer_tags[trace_layer], "%s", buffer);
break;
case TRACE_TYPE_API:
case TRACE_TYPE_EVENT:
- LOG_INFO("%s", buffer);
+ LOG_INFO(bt_layer_tags[trace_layer], "%s", buffer);
break;
case TRACE_TYPE_DEBUG:
- LOG_INFO("%s", buffer);
+ LOG_DEBUG(bt_layer_tags[trace_layer], "%s", buffer);
break;
default:
/* we should never get this */
- LOG_ERROR("!BAD TRACE TYPE! %s", buffer);
+ LOG_ERROR(bt_layer_tags[trace_layer], "!BAD TRACE TYPE! %s", buffer);
CHECK(TRACE_GET_TYPE(trace_set_mask) == TRACE_TYPE_ERROR);
break;
}
-#undef LOG_TAG
-#define LOG_TAG "bt_bte"
}
/* this function should go into BTAPP_DM for example */
@@ -236,16 +229,9 @@ static void load_levels_from_config(const config_t* config) {
functions->trc_name; ++functions) {
int value = config_get_int(*config, CONFIG_DEFAULT_SECTION,
functions->trc_name, -1);
- if (value != -1) {
- functions->trace_level = value;
- }
- if (bluetooth::common::InitFlags::IsDebugLoggingEnabledForAll()) {
- LOG_INFO("Enable logging for %s because all debug logs are enabled",
- functions->trc_name);
- functions->trace_level = BT_TRACE_LEVEL_VERBOSE;
- }
- LOG_INFO("BTE_InitTraceLevels -- %s : Level %d", functions->trc_name,
- functions->trace_level);
+ if (value != -1) functions->trace_level = value;
+ LOG_INFO(LOG_TAG, "BTE_InitTraceLevels -- %s : Level %d",
+ functions->trc_name, functions->trace_level);
if (functions->p_f) functions->p_f(functions->trace_level);
}
}
@@ -253,7 +239,7 @@ static void load_levels_from_config(const config_t* config) {
static future_t* init(void) {
const stack_config_t* stack_config = stack_config_get_interface();
if (!stack_config->get_trace_config_enabled()) {
- LOG_INFO("using compile default trace settings");
+ LOG_INFO(LOG_TAG, "using compile default trace settings");
return NULL;
}
diff --git a/main/bte_main.cc b/main/bte_main.cc
index ee484002d..16289769e 100644
--- a/main/bte_main.cc
+++ b/main/bte_main.cc
@@ -27,16 +27,30 @@
#define LOG_TAG "bt_main"
#include <base/logging.h>
+#include <base/threading/thread.h>
+#include <fcntl.h>
+#include <pthread.h>
+#include <signal.h>
+#include <stdlib.h>
+#include <time.h>
+
#include <hardware/bluetooth.h>
#include "bt_common.h"
+#include "bt_hci_bdroid.h"
+#include "bt_utils.h"
+#include "bta_api.h"
#include "btcore/include/module.h"
#include "bte.h"
-#include "btif/include/btif_config.h"
+#include "btif_common.h"
#include "btsnoop.h"
#include "btu.h"
#include "device/include/interop.h"
#include "hci_layer.h"
+#include "hcimsgs.h"
+#include "osi/include/alarm.h"
+#include "osi/include/fixed_queue.h"
+#include "osi/include/future.h"
#include "osi/include/log.h"
#include "osi/include/osi.h"
#include "shim/hci_layer.h"
@@ -44,6 +58,24 @@
#include "stack_config.h"
/*******************************************************************************
+ * Constants & Macros
+ ******************************************************************************/
+
+/* Run-time configuration file for BLE*/
+#ifndef BTE_BLE_STACK_CONF_FILE
+// TODO(armansito): Find a better way than searching by a hardcoded path.
+#if defined(OS_GENERIC)
+#define BTE_BLE_STACK_CONF_FILE "ble_stack.conf"
+#else // !defined(OS_GENERIC)
+#define BTE_BLE_STACK_CONF_FILE "/etc/bluetooth/ble_stack.conf"
+#endif // defined(OS_GENERIC)
+#endif // BT_BLE_STACK_CONF_FILE
+
+/******************************************************************************
+ * Variables
+ *****************************************************************************/
+
+/*******************************************************************************
* Static variables
******************************************************************************/
static const hci_t* hci;
@@ -74,14 +106,105 @@ void post_to_main_message_loop(const base::Location& from_here, BT_HDR* p_msg) {
}
}
-void bte_main_init(void) {
+/******************************************************************************
+ *
+ * Function bte_main_boot_entry
+ *
+ * Description BTE MAIN API - Entry point for BTE chip/stack initialization
+ *
+ * Returns None
+ *
+ *****************************************************************************/
+void bte_main_boot_entry(void) {
+ module_init(get_module(INTEROP_MODULE));
+
hci = hci_layer_get_interface();
if (!hci) {
- LOG_ERROR("%s could not get hci layer interface.", __func__);
+ LOG_ERROR(LOG_TAG, "%s could not get hci layer interface.", __func__);
return;
}
hci->set_data_cb(base::Bind(&post_to_main_message_loop));
+
+ module_init(get_module(STACK_CONFIG_MODULE));
+}
+
+/******************************************************************************
+ *
+ * Function bte_main_cleanup
+ *
+ * Description BTE MAIN API - Cleanup code for BTE chip/stack
+ *
+ * Returns None
+ *
+ *****************************************************************************/
+void bte_main_cleanup() {
+ module_clean_up(get_module(STACK_CONFIG_MODULE));
+
+ module_clean_up(get_module(INTEROP_MODULE));
+}
+
+/******************************************************************************
+ *
+ * Function bte_main_enable
+ *
+ * Description BTE MAIN API - Creates all the BTE tasks. Should be called
+ * part of the Bluetooth stack enable sequence
+ *
+ * Returns None
+ *
+ *****************************************************************************/
+void bte_main_enable() {
+ APPL_TRACE_DEBUG("%s", __func__);
+
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ LOG_INFO(LOG_TAG, "%s Gd shim module enabled", __func__);
+ module_start_up(get_module(GD_SHIM_MODULE));
+ module_start_up(get_module(GD_HCI_MODULE));
+ } else {
+ module_start_up(get_module(BTSNOOP_MODULE));
+ module_start_up(get_module(HCI_MODULE));
+ }
+
+ BTU_StartUp();
+}
+
+/******************************************************************************
+ *
+ * Function bte_main_disable
+ *
+ * Description BTE MAIN API - Destroys all the BTE tasks. Should be called
+ * part of the Bluetooth stack disable sequence
+ *
+ * Returns None
+ *
+ *****************************************************************************/
+void bte_main_disable(void) {
+ APPL_TRACE_DEBUG("%s", __func__);
+
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ LOG_INFO(LOG_TAG, "%s Gd shim module enabled", __func__);
+ module_shut_down(get_module(GD_HCI_MODULE));
+ module_shut_down(get_module(GD_SHIM_MODULE));
+ } else {
+ module_shut_down(get_module(HCI_MODULE));
+ module_shut_down(get_module(BTSNOOP_MODULE));
+ }
+
+ BTU_ShutDown();
+}
+
+/******************************************************************************
+ *
+ * Function bte_main_postload_cfg
+ *
+ * Description BTE MAIN API - Stack postload configuration
+ *
+ * Returns None
+ *
+ *****************************************************************************/
+void bte_main_postload_cfg(void) {
+ // TODO(eisenbach): [HIDL] DEPRECATE?
}
/******************************************************************************
diff --git a/main/shim/Android.bp b/main/shim/Android.bp
index b8aca32fa..9b21e8b43 100644
--- a/main/shim/Android.bp
+++ b/main/shim/Android.bp
@@ -1,33 +1,16 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
filegroup {
name: "LibBluetoothShimSources",
srcs: [
- "acl.cc",
- "acl_api.cc",
- "acl_legacy_interface.cc",
- "activity_attribution.cc",
"btm.cc",
"btm_api.cc",
- "config.cc",
"controller.cc",
+ "config.cc",
"dumpsys.cc",
"entry.cc",
"hci_layer.cc",
"l2c_api.cc",
- "le_advertising_manager.cc",
- "le_scanning_manager.cc",
- "link_policy.cc",
- "metric_id_api.cc",
- "metrics_api.cc",
+ "l2cap.cc",
"shim.cc",
- "stack.cc",
+ "timer.cc",
]
}
diff --git a/main/shim/BUILD.gn b/main/shim/BUILD.gn
deleted file mode 100644
index 5e6485898..000000000
--- a/main/shim/BUILD.gn
+++ /dev/null
@@ -1,66 +0,0 @@
-#
-# Copyright 2021 Google, Inc.
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-source_set("LibBluetoothShimSources") {
- sources = [
- "acl.cc",
- "acl_api.cc",
- "acl_legacy_interface.cc",
- "activity_attribution.cc",
- "btm.cc",
- "btm_api.cc",
- "config.cc",
- "controller.cc",
- "dumpsys.cc",
- "entry.cc",
- "hci_layer.cc",
- "l2c_api.cc",
- "le_advertising_manager.cc",
- "le_scanning_manager.cc",
- "link_policy.cc",
- "metric_id_api.cc",
- "metrics_api.cc",
- "shim.cc",
- "stack.cc",
- ]
-
- include_dirs = [
- "//bt",
- "//bt/btif/include",
- "//bt/gd",
- "//bt/gd/rust/shim",
- "//bt/internal_include",
- "//bt/stack/include",
- "//bt/types",
- ]
-
- deps = [
- "//bt/gd:BluetoothGeneratedDumpsysDataSchema_h",
- "//bt/gd:BluetoothGeneratedPackets_h",
- "//bt/gd/common:BluetoothCommonSources",
- "//bt/gd/dumpsys/bundler:BluetoothGeneratedBundlerSchema_h_bfbs",
- "//bt/gd/hci:BluetoothHciSources",
- "//bt/gd/os:BluetoothOsSources_linux_generic",
- "//bt/gd/packet:BluetoothPacketSources",
- "//bt/gd/rust/shim:libbluetooth_rust_interop",
- "//bt/gd/rust/topshim:libbluetooth_topshim",
- "//bt/osi",
- "//bt/stack",
- "//bt/types",
- ]
-
- configs += [ "//bt:target_defaults" ]
-}
diff --git a/main/shim/acl.cc b/main/shim/acl.cc
deleted file mode 100644
index 2e5044640..000000000
--- a/main/shim/acl.cc
+++ /dev/null
@@ -1,1471 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "main/shim/acl.h"
-
-#include <base/location.h>
-#include <base/strings/stringprintf.h>
-#include <time.h>
-#include <unordered_set>
-
-#include <chrono>
-#include <cstdint>
-#include <functional>
-#include <future>
-#include <map>
-#include <memory>
-#include <string>
-
-#include "btif/include/btif_hh.h"
-#include "device/include/controller.h"
-#include "gd/common/bidi_queue.h"
-#include "gd/common/bind.h"
-#include "gd/common/strings.h"
-#include "gd/hci/acl_manager.h"
-#include "gd/hci/acl_manager/acl_connection.h"
-#include "gd/hci/acl_manager/classic_acl_connection.h"
-#include "gd/hci/acl_manager/connection_management_callbacks.h"
-#include "gd/hci/acl_manager/le_acl_connection.h"
-#include "gd/hci/acl_manager/le_connection_management_callbacks.h"
-#include "gd/hci/address.h"
-#include "gd/hci/class_of_device.h"
-#include "gd/hci/controller.h"
-#include "gd/os/handler.h"
-#include "gd/os/queue.h"
-#include "main/shim/btm.h"
-#include "main/shim/dumpsys.h"
-#include "main/shim/entry.h"
-#include "main/shim/helpers.h"
-#include "main/shim/stack.h"
-#include "stack/acl/acl.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/acl_hci_link_interface.h"
-#include "stack/include/ble_acl_interface.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_status.h"
-#include "stack/include/sec_hci_link_interface.h"
-#include "stack/l2cap/l2c_int.h"
-
-extern tBTM_CB btm_cb;
-
-bt_status_t do_in_main_thread(const base::Location& from_here,
- base::OnceClosure task);
-
-using namespace bluetooth;
-
-namespace {
-
-using HciHandle = uint16_t;
-using PageNumber = uint8_t;
-
-using CreationTime = std::chrono::time_point<std::chrono::system_clock>;
-using TeardownTime = std::chrono::time_point<std::chrono::system_clock>;
-
-constexpr char kBtmLogTag[] = "ACL";
-
-using SendDataUpwards = void (*const)(BT_HDR*);
-using OnDisconnect = std::function<void(HciHandle, hci::ErrorCode reason)>;
-
-constexpr char kConnectionDescriptorTimeFormat[] = "%Y-%m-%d %H:%M:%S";
-
-class ShadowAcceptlist {
- public:
- ShadowAcceptlist(uint8_t max_acceptlist_size)
- : max_acceptlist_size_(max_acceptlist_size) {}
-
- bool Add(const hci::AddressWithType& address_with_type) {
- if (acceptlist_set_.size() == max_acceptlist_size_) {
- LOG_ERROR("Acceptlist is full size:%zu", acceptlist_set_.size());
- return false;
- }
- if (!acceptlist_set_.insert(address_with_type).second) {
- LOG_WARN("Attempted to add duplicate le address to acceptlist:%s",
- PRIVATE_ADDRESS(address_with_type));
- }
- return true;
- }
-
- bool Remove(const hci::AddressWithType& address_with_type) {
- auto iter = acceptlist_set_.find(address_with_type);
- if (iter == acceptlist_set_.end()) {
- LOG_WARN("Unknown device being removed from acceptlist:%s",
- PRIVATE_ADDRESS(address_with_type));
- return false;
- }
- acceptlist_set_.erase(iter);
- return true;
- }
-
- std::unordered_set<hci::AddressWithType> GetCopy() const {
- return acceptlist_set_;
- }
-
- bool IsFull() const {
- return acceptlist_set_.size() == static_cast<size_t>(max_acceptlist_size_);
- }
-
- void Clear() { acceptlist_set_.clear(); }
-
- private:
- uint8_t max_acceptlist_size_{0};
- std::unordered_set<hci::AddressWithType> acceptlist_set_;
-};
-
-struct ConnectionDescriptor {
- CreationTime creation_time_;
- TeardownTime teardown_time_;
- uint16_t handle_;
- bool is_locally_initiated_;
- hci::ErrorCode disconnect_reason_;
- ConnectionDescriptor(CreationTime creation_time, TeardownTime teardown_time,
- uint16_t handle, bool is_locally_initiated,
- hci::ErrorCode disconnect_reason)
- : creation_time_(creation_time),
- teardown_time_(teardown_time),
- handle_(handle),
- is_locally_initiated_(is_locally_initiated),
- disconnect_reason_(disconnect_reason) {}
- virtual std::string GetPrivateRemoteAddress() const = 0;
- virtual ~ConnectionDescriptor() {}
- std::string ToString() const {
- return base::StringPrintf(
- "peer:%s handle:0x%04x is_locally_initiated:%s"
- " creation_time:%s teardown_time:%s disconnect_reason:%s",
- GetPrivateRemoteAddress().c_str(), handle_,
- logbool(is_locally_initiated_).c_str(),
- common::StringFormatTimeWithMilliseconds(
- kConnectionDescriptorTimeFormat, creation_time_)
- .c_str(),
- common::StringFormatTimeWithMilliseconds(
- kConnectionDescriptorTimeFormat, teardown_time_)
- .c_str(),
- hci::ErrorCodeText(disconnect_reason_).c_str());
- }
-};
-
-struct ClassicConnectionDescriptor : public ConnectionDescriptor {
- const hci::Address remote_address_;
- ClassicConnectionDescriptor(const hci::Address& remote_address,
- CreationTime creation_time,
- TeardownTime teardown_time, uint16_t handle,
- bool is_locally_initiated,
- hci::ErrorCode disconnect_reason)
- : ConnectionDescriptor(creation_time, teardown_time, handle,
- is_locally_initiated, disconnect_reason),
- remote_address_(remote_address) {}
- virtual std::string GetPrivateRemoteAddress() const {
- return PRIVATE_ADDRESS(remote_address_);
- }
-};
-
-struct LeConnectionDescriptor : public ConnectionDescriptor {
- const hci::AddressWithType remote_address_with_type_;
- LeConnectionDescriptor(hci::AddressWithType& remote_address_with_type,
- CreationTime creation_time, TeardownTime teardown_time,
- uint16_t handle, bool is_locally_initiated,
- hci::ErrorCode disconnect_reason)
- : ConnectionDescriptor(creation_time, teardown_time, handle,
- is_locally_initiated, disconnect_reason),
- remote_address_with_type_(remote_address_with_type) {}
- std::string GetPrivateRemoteAddress() const {
- return PRIVATE_ADDRESS(remote_address_with_type_);
- }
-};
-
-template <typename T>
-class FixedQueue {
- public:
- explicit FixedQueue(size_t max_size) : max_size_(max_size) {}
- void Push(T element) {
- if (queue_.size() == max_size_) {
- queue_.pop_front();
- }
- queue_.push_back(std::move(element));
- }
-
- std::vector<std::string> ReadElementsAsString() const {
- std::vector<std::string> vector;
- for (auto& entry : queue_) {
- vector.push_back(entry->ToString());
- }
- return vector;
- }
-
- private:
- size_t max_size_{1};
- std::deque<T> queue_;
-};
-
-constexpr size_t kConnectionHistorySize = 40;
-
-inline uint8_t LowByte(uint16_t val) { return val & 0xff; }
-inline uint8_t HighByte(uint16_t val) { return val >> 8; }
-
-void ValidateAclInterface(const shim::legacy::acl_interface_t& acl_interface) {
- ASSERT_LOG(acl_interface.on_send_data_upwards != nullptr,
- "Must provide to receive data on acl links");
- ASSERT_LOG(acl_interface.on_packets_completed != nullptr,
- "Must provide to receive completed packet indication");
-
- ASSERT_LOG(acl_interface.connection.classic.on_connected != nullptr,
- "Must provide to respond to successful classic connections");
- ASSERT_LOG(acl_interface.connection.classic.on_failed != nullptr,
- "Must provide to respond when classic connection attempts fail");
- ASSERT_LOG(
- acl_interface.connection.classic.on_disconnected != nullptr,
- "Must provide to respond when active classic connection disconnects");
-
- ASSERT_LOG(acl_interface.connection.le.on_connected != nullptr,
- "Must provide to respond to successful le connections");
- ASSERT_LOG(acl_interface.connection.le.on_failed != nullptr,
- "Must provide to respond when le connection attempts fail");
- ASSERT_LOG(acl_interface.connection.le.on_disconnected != nullptr,
- "Must provide to respond when active le connection disconnects");
-}
-
-} // namespace
-
-#define TRY_POSTING_ON_MAIN(cb, ...) \
- do { \
- if (cb == nullptr) { \
- LOG_WARN("Dropping ACL event with no callback"); \
- } else { \
- do_in_main_thread(FROM_HERE, base::Bind(cb, ##__VA_ARGS__)); \
- } \
- } while (0)
-
-constexpr HciHandle kInvalidHciHandle = 0xffff;
-
-class ShimAclConnection {
- public:
- ShimAclConnection(const HciHandle handle, SendDataUpwards send_data_upwards,
- os::Handler* handler,
- hci::acl_manager::AclConnection::QueueUpEnd* queue_up_end,
- CreationTime creation_time)
- : handle_(handle),
- handler_(handler),
- send_data_upwards_(send_data_upwards),
- queue_up_end_(queue_up_end),
- creation_time_(creation_time) {
- queue_up_end_->RegisterDequeue(
- handler_, common::Bind(&ShimAclConnection::data_ready_callback,
- common::Unretained(this)));
- }
-
- virtual ~ShimAclConnection() {
- if (!queue_.empty())
- LOG_ERROR(
- "ACL cleaned up with non-empty queue handle:0x%04x stranded_pkts:%zu",
- handle_, queue_.size());
- ASSERT_LOG(is_disconnected_,
- "Shim Acl was not properly disconnected handle:0x%04x", handle_);
- }
-
- void EnqueuePacket(std::unique_ptr<packet::RawBuilder> packet) {
- // TODO Handle queue size exceeds some threshold
- queue_.push(std::move(packet));
- RegisterEnqueue();
- }
-
- std::unique_ptr<packet::BasePacketBuilder> handle_enqueue() {
- auto packet = std::move(queue_.front());
- queue_.pop();
- if (queue_.empty()) {
- UnregisterEnqueue();
- }
- return packet;
- }
-
- void data_ready_callback() {
- auto packet = queue_up_end_->TryDequeue();
- uint16_t length = packet->size();
- std::vector<uint8_t> preamble;
- preamble.push_back(LowByte(handle_));
- preamble.push_back(HighByte(handle_));
- preamble.push_back(LowByte(length));
- preamble.push_back(HighByte(length));
- BT_HDR* p_buf = MakeLegacyBtHdrPacket(std::move(packet), preamble);
- ASSERT_LOG(p_buf != nullptr,
- "Unable to allocate BT_HDR legacy packet handle:%04x", handle_);
- if (send_data_upwards_ == nullptr) {
- LOG_WARN("Dropping ACL data with no callback");
- osi_free(p_buf);
- } else if (do_in_main_thread(FROM_HERE,
- base::Bind(send_data_upwards_, p_buf)) !=
- BT_STATUS_SUCCESS) {
- osi_free(p_buf);
- }
- }
-
- virtual void InitiateDisconnect(hci::DisconnectReason reason) = 0;
- virtual bool IsLocallyInitiated() const = 0;
-
- CreationTime GetCreationTime() const { return creation_time_; }
- uint16_t Handle() const { return handle_; }
-
- void Shutdown() {
- Disconnect();
- LOG_INFO("Shutdown and disconnect ACL connection handle:0x%04x", handle_);
- }
-
- protected:
- const uint16_t handle_{kInvalidHciHandle};
- os::Handler* handler_;
-
- void UnregisterEnqueue() {
- if (!is_enqueue_registered_) return;
- is_enqueue_registered_ = false;
- queue_up_end_->UnregisterEnqueue();
- }
-
- void Disconnect() {
- ASSERT_LOG(!is_disconnected_,
- "Cannot disconnect ACL multiple times handle:%04x", handle_);
- is_disconnected_ = true;
- UnregisterEnqueue();
- queue_up_end_->UnregisterDequeue();
- if (!queue_.empty())
- LOG_WARN(
- "ACL disconnect with non-empty queue handle:%04x stranded_pkts::%zu",
- handle_, queue_.size());
- }
-
- virtual void ReadRemoteControllerInformation() = 0;
-
- private:
- SendDataUpwards send_data_upwards_;
- hci::acl_manager::AclConnection::QueueUpEnd* queue_up_end_;
-
- std::queue<std::unique_ptr<packet::RawBuilder>> queue_;
- bool is_enqueue_registered_{false};
- bool is_disconnected_{false};
- CreationTime creation_time_;
-
- void RegisterEnqueue() {
- ASSERT_LOG(!is_disconnected_,
- "Unable to send data over disconnected channel handle:%04x",
- handle_);
- if (is_enqueue_registered_) return;
- is_enqueue_registered_ = true;
- queue_up_end_->RegisterEnqueue(
- handler_, common::Bind(&ShimAclConnection::handle_enqueue,
- common::Unretained(this)));
- }
-
- virtual void RegisterCallbacks() = 0;
-};
-
-class ClassicShimAclConnection
- : public ShimAclConnection,
- public hci::acl_manager::ConnectionManagementCallbacks {
- public:
- ClassicShimAclConnection(
- SendDataUpwards send_data_upwards, OnDisconnect on_disconnect,
- const shim::legacy::acl_classic_link_interface_t& interface,
- os::Handler* handler,
- std::unique_ptr<hci::acl_manager::ClassicAclConnection> connection,
- CreationTime creation_time)
- : ShimAclConnection(connection->GetHandle(), send_data_upwards, handler,
- connection->GetAclQueueEnd(), creation_time),
- on_disconnect_(on_disconnect),
- interface_(interface),
- connection_(std::move(connection)) {}
-
- void RegisterCallbacks() override {
- connection_->RegisterCallbacks(this, handler_);
- }
-
- void ReadRemoteControllerInformation() override {
- connection_->ReadRemoteVersionInformation();
- connection_->ReadRemoteSupportedFeatures();
- }
-
- void OnConnectionPacketTypeChanged(uint16_t packet_type) override {
- TRY_POSTING_ON_MAIN(interface_.on_packet_type_changed, packet_type);
- }
-
- void OnAuthenticationComplete(hci::ErrorCode hci_status) override {
- TRY_POSTING_ON_MAIN(interface_.on_authentication_complete, handle_,
- ToLegacyHciErrorCode(hci_status));
- }
-
- void OnEncryptionChange(hci::EncryptionEnabled enabled) override {
- bool is_enabled = (enabled == hci::EncryptionEnabled::ON ||
- enabled == hci::EncryptionEnabled::BR_EDR_AES_CCM);
- TRY_POSTING_ON_MAIN(interface_.on_encryption_change, is_enabled);
- }
-
- void OnChangeConnectionLinkKeyComplete() override {
- TRY_POSTING_ON_MAIN(interface_.on_change_connection_link_key_complete);
- }
-
- void OnReadClockOffsetComplete(uint16_t clock_offset) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnModeChange(hci::ErrorCode status, hci::Mode current_mode,
- uint16_t interval) override {
- TRY_POSTING_ON_MAIN(interface_.on_mode_change, ToLegacyHciErrorCode(status),
- handle_, ToLegacyHciMode(current_mode), interval);
- }
-
- void OnSniffSubrating(hci::ErrorCode hci_status,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) {
- TRY_POSTING_ON_MAIN(interface_.on_sniff_subrating,
- ToLegacyHciErrorCode(hci_status), handle_,
- maximum_transmit_latency, maximum_receive_latency,
- minimum_remote_timeout, minimum_local_timeout);
- }
-
- void OnQosSetupComplete(hci::ServiceType service_type, uint32_t token_rate,
- uint32_t peak_bandwidth, uint32_t latency,
- uint32_t delay_variation) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnFlowSpecificationComplete(hci::FlowDirection flow_direction,
- hci::ServiceType service_type,
- uint32_t token_rate,
- uint32_t token_bucket_size,
- uint32_t peak_bandwidth,
- uint32_t access_latency) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnFlushOccurred() override { LOG_INFO("UNIMPLEMENTED"); }
-
- void OnRoleDiscoveryComplete(hci::Role current_role) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnReadLinkPolicySettingsComplete(
- uint16_t link_policy_settings) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnReadAutomaticFlushTimeoutComplete(uint16_t flush_timeout) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnReadTransmitPowerLevelComplete(uint8_t transmit_power_level) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnReadLinkSupervisionTimeoutComplete(
- uint16_t link_supervision_timeout) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnReadFailedContactCounterComplete(
- uint16_t failed_contact_counter) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnReadLinkQualityComplete(uint8_t link_quality) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnReadAfhChannelMapComplete(
- hci::AfhMode afh_mode, std::array<uint8_t, 10> afh_channel_map) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnReadRssiComplete(uint8_t rssi) override { LOG_INFO("UNIMPLEMENTED"); }
-
- void OnReadClockComplete(uint32_t clock, uint16_t accuracy) override {
- LOG_INFO("UNIMPLEMENTED");
- }
-
- void OnCentralLinkKeyComplete(hci::KeyFlag key_flag) override {
- LOG_INFO("%s UNIMPLEMENTED", __func__);
- }
-
- void OnRoleChange(hci::ErrorCode hci_status, hci::Role new_role) override {
- TRY_POSTING_ON_MAIN(
- interface_.on_role_change, ToLegacyHciErrorCode(hci_status),
- ToRawAddress(connection_->GetAddress()), ToLegacyRole(new_role));
- BTM_LogHistory(kBtmLogTag, ToRawAddress(connection_->GetAddress()),
- "Role change",
- base::StringPrintf("classic status:%s new_role:%s",
- hci::ErrorCodeText(hci_status).c_str(),
- hci::RoleText(new_role).c_str()));
- }
-
- void OnDisconnection(hci::ErrorCode reason) override {
- Disconnect();
- on_disconnect_(handle_, reason);
- }
-
- void OnReadRemoteVersionInformationComplete(hci::ErrorCode hci_status,
- uint8_t lmp_version,
- uint16_t manufacturer_name,
- uint16_t sub_version) override {
- TRY_POSTING_ON_MAIN(interface_.on_read_remote_version_information_complete,
- ToLegacyHciErrorCode(hci_status), handle_, lmp_version,
- manufacturer_name, sub_version);
- }
-
- void OnReadRemoteSupportedFeaturesComplete(uint64_t features) override {
- TRY_POSTING_ON_MAIN(interface_.on_read_remote_supported_features_complete,
- handle_, features);
-
- if (features & ((uint64_t(1) << 63))) {
- connection_->ReadRemoteExtendedFeatures(1);
- return;
- }
- LOG_DEBUG("Device does not support extended features");
- }
-
- void OnReadRemoteExtendedFeaturesComplete(uint8_t page_number,
- uint8_t max_page_number,
- uint64_t features) override {
- TRY_POSTING_ON_MAIN(interface_.on_read_remote_extended_features_complete,
- handle_, page_number, max_page_number, features);
-
- // Supported features aliases to extended features page 0
- if (page_number == 0 && !(features & ((uint64_t(1) << 63)))) {
- LOG_DEBUG("Device does not support extended features");
- return;
- }
-
- if (page_number != max_page_number)
- connection_->ReadRemoteExtendedFeatures(page_number + 1);
- }
-
- hci::Address GetRemoteAddress() const { return connection_->GetAddress(); }
-
- void InitiateDisconnect(hci::DisconnectReason reason) override {
- connection_->Disconnect(reason);
- }
-
- void HoldMode(uint16_t max_interval, uint16_t min_interval) {
- ASSERT(connection_->HoldMode(max_interval, min_interval));
- }
-
- void SniffMode(uint16_t max_interval, uint16_t min_interval, uint16_t attempt,
- uint16_t timeout) {
- ASSERT(
- connection_->SniffMode(max_interval, min_interval, attempt, timeout));
- }
-
- void ExitSniffMode() { ASSERT(connection_->ExitSniffMode()); }
-
- void SniffSubrating(uint16_t maximum_latency, uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) {
- ASSERT(connection_->SniffSubrating(maximum_latency, minimum_remote_timeout,
- minimum_local_timeout));
- }
-
- void SetConnectionEncryption(hci::Enable is_encryption_enabled) {
- ASSERT(connection_->SetConnectionEncryption(is_encryption_enabled));
- }
-
- bool IsLocallyInitiated() const override {
- return connection_->locally_initiated_;
- }
-
- private:
- OnDisconnect on_disconnect_;
- const shim::legacy::acl_classic_link_interface_t interface_;
- std::unique_ptr<hci::acl_manager::ClassicAclConnection> connection_;
-};
-
-class LeShimAclConnection
- : public ShimAclConnection,
- public hci::acl_manager::LeConnectionManagementCallbacks {
- public:
- LeShimAclConnection(
- SendDataUpwards send_data_upwards, OnDisconnect on_disconnect,
- const shim::legacy::acl_le_link_interface_t& interface,
- os::Handler* handler,
- std::unique_ptr<hci::acl_manager::LeAclConnection> connection,
- std::chrono::time_point<std::chrono::system_clock> creation_time)
- : ShimAclConnection(connection->GetHandle(), send_data_upwards, handler,
- connection->GetAclQueueEnd(), creation_time),
- on_disconnect_(on_disconnect),
- interface_(interface),
- connection_(std::move(connection)) {}
-
- void RegisterCallbacks() override {
- connection_->RegisterCallbacks(this, handler_);
- }
-
- void ReadRemoteControllerInformation() override {
- // TODO Issue LeReadRemoteFeatures Command
- }
-
- bluetooth::hci::AddressWithType GetLocalAddressWithType() {
- return connection_->GetLocalAddress();
- }
-
- void OnConnectionUpdate(hci::ErrorCode hci_status,
- uint16_t connection_interval,
- uint16_t connection_latency,
- uint16_t supervision_timeout) {
- TRY_POSTING_ON_MAIN(
- interface_.on_connection_update, ToLegacyHciErrorCode(hci_status),
- handle_, connection_interval, connection_latency, supervision_timeout);
- }
- void OnDataLengthChange(uint16_t tx_octets, uint16_t tx_time,
- uint16_t rx_octets, uint16_t rx_time) {
- TRY_POSTING_ON_MAIN(interface_.on_data_length_change, tx_octets, tx_time,
- rx_octets, rx_time);
- }
-
- void OnReadRemoteVersionInformationComplete(hci::ErrorCode hci_status,
- uint8_t lmp_version,
- uint16_t manufacturer_name,
- uint16_t sub_version) override {
- TRY_POSTING_ON_MAIN(interface_.on_read_remote_version_information_complete,
- ToLegacyHciErrorCode(hci_status), handle_, lmp_version,
- manufacturer_name, sub_version);
- }
-
- void OnPhyUpdate(hci::ErrorCode hci_status, uint8_t tx_phy,
- uint8_t rx_phy) override {
- TRY_POSTING_ON_MAIN(interface_.on_phy_update,
- ToLegacyHciErrorCode(hci_status), handle_, tx_phy,
- rx_phy);
- }
-
- void OnLocalAddressUpdate(hci::AddressWithType address_with_type) override {
- connection_->UpdateLocalAddress(address_with_type);
- }
-
- void OnDisconnection(hci::ErrorCode reason) {
- Disconnect();
- on_disconnect_(handle_, reason);
- }
-
- hci::AddressWithType GetRemoteAddressWithType() const {
- return connection_->GetRemoteAddress();
- }
-
- void InitiateDisconnect(hci::DisconnectReason reason) override {
- connection_->Disconnect(reason);
- }
-
- bool IsLocallyInitiated() const override {
- return connection_->locally_initiated_;
- }
-
- private:
- OnDisconnect on_disconnect_;
- const shim::legacy::acl_le_link_interface_t interface_;
- std::unique_ptr<hci::acl_manager::LeAclConnection> connection_;
-};
-
-struct shim::legacy::Acl::impl {
- impl(uint8_t max_acceptlist_size)
- : shadow_acceptlist_(ShadowAcceptlist(max_acceptlist_size)) {}
-
- std::map<HciHandle, std::unique_ptr<ClassicShimAclConnection>>
- handle_to_classic_connection_map_;
- std::map<HciHandle, std::unique_ptr<LeShimAclConnection>>
- handle_to_le_connection_map_;
-
- FixedQueue<std::unique_ptr<ConnectionDescriptor>> connection_history_ =
- FixedQueue<std::unique_ptr<ConnectionDescriptor>>(kConnectionHistorySize);
-
- ShadowAcceptlist shadow_acceptlist_;
-
- bool IsClassicAcl(HciHandle handle) {
- return handle_to_classic_connection_map_.find(handle) !=
- handle_to_classic_connection_map_.end();
- }
-
- void EnqueueClassicPacket(HciHandle handle,
- std::unique_ptr<packet::RawBuilder> packet) {
- ASSERT_LOG(IsClassicAcl(handle), "handle %d is not a classic connection",
- handle);
- handle_to_classic_connection_map_[handle]->EnqueuePacket(std::move(packet));
- }
-
- bool IsLeAcl(HciHandle handle) {
- return handle_to_le_connection_map_.find(handle) !=
- handle_to_le_connection_map_.end();
- }
-
- void EnqueueLePacket(HciHandle handle,
- std::unique_ptr<packet::RawBuilder> packet) {
- ASSERT_LOG(IsLeAcl(handle), "handle %d is not a LE connection", handle);
- handle_to_le_connection_map_[handle]->EnqueuePacket(std::move(packet));
- }
-
- void ShutdownClassicConnections(std::promise<void> promise) {
- LOG_INFO("Shutdown gd acl shim classic connections");
- for (auto& connection : handle_to_classic_connection_map_) {
- connection.second->Shutdown();
- }
- handle_to_classic_connection_map_.clear();
- promise.set_value();
- }
-
- void ShutdownLeConnections(std::promise<void> promise) {
- LOG_INFO("Shutdown gd acl shim le connections");
- for (auto& connection : handle_to_le_connection_map_) {
- connection.second->Shutdown();
- }
- handle_to_le_connection_map_.clear();
- promise.set_value();
- }
-
- void FinalShutdown(std::promise<void> promise) {
- if (!handle_to_classic_connection_map_.empty()) {
- for (auto& connection : handle_to_classic_connection_map_) {
- connection.second->Shutdown();
- }
- handle_to_classic_connection_map_.clear();
- LOG_INFO("Cleared all classic connections count:%zu",
- handle_to_classic_connection_map_.size());
- }
-
- if (!handle_to_le_connection_map_.empty()) {
- for (auto& connection : handle_to_le_connection_map_) {
- connection.second->Shutdown();
- }
- handle_to_le_connection_map_.clear();
- LOG_INFO("Cleared all le connections count:%zu",
- handle_to_le_connection_map_.size());
- }
- promise.set_value();
- }
-
- void HoldMode(HciHandle handle, uint16_t max_interval,
- uint16_t min_interval) {
- ASSERT_LOG(IsClassicAcl(handle), "handle %d is not a classic connection",
- handle);
- handle_to_classic_connection_map_[handle]->HoldMode(max_interval,
- min_interval);
- }
-
- void ExitSniffMode(HciHandle handle) {
- ASSERT_LOG(IsClassicAcl(handle), "handle %d is not a classic connection",
- handle);
- handle_to_classic_connection_map_[handle]->ExitSniffMode();
- }
-
- void SniffMode(HciHandle handle, uint16_t max_interval, uint16_t min_interval,
- uint16_t attempt, uint16_t timeout) {
- ASSERT_LOG(IsClassicAcl(handle), "handle %d is not a classic connection",
- handle);
- handle_to_classic_connection_map_[handle]->SniffMode(
- max_interval, min_interval, attempt, timeout);
- }
-
- void SniffSubrating(HciHandle handle, uint16_t maximum_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) {
- ASSERT_LOG(IsClassicAcl(handle), "handle %d is not a classic connection",
- handle);
- handle_to_classic_connection_map_[handle]->SniffSubrating(
- maximum_latency, minimum_remote_timeout, minimum_local_timeout);
- }
-
- void SetConnectionEncryption(HciHandle handle, hci::Enable enable) {
- ASSERT_LOG(IsClassicAcl(handle), "handle %d is not a classic connection",
- handle);
- handle_to_classic_connection_map_[handle]->SetConnectionEncryption(enable);
- }
-
- void disconnect_classic(uint16_t handle, tHCI_STATUS reason) {
- auto connection = handle_to_classic_connection_map_.find(handle);
- if (connection != handle_to_classic_connection_map_.end()) {
- auto remote_address = connection->second->GetRemoteAddress();
- connection->second->InitiateDisconnect(
- ToDisconnectReasonFromLegacy(reason));
- LOG_DEBUG("Disconnection initiated classic remote:%s handle:%hu",
- PRIVATE_ADDRESS(remote_address), handle);
- BTM_LogHistory(kBtmLogTag, ToRawAddress(remote_address),
- "Disconnection initiated", "classic");
- } else {
- LOG_WARN("Unable to disconnect unknown classic connection handle:0x%04x",
- handle);
- }
- }
-
- void disconnect_le(uint16_t handle, tHCI_STATUS reason) {
- auto connection = handle_to_le_connection_map_.find(handle);
- if (connection != handle_to_le_connection_map_.end()) {
- auto remote_address_with_type =
- connection->second->GetRemoteAddressWithType();
- connection->second->InitiateDisconnect(
- ToDisconnectReasonFromLegacy(reason));
- LOG_DEBUG("Disconnection initiated le remote:%s handle:%hu",
- PRIVATE_ADDRESS(remote_address_with_type), handle);
- BTM_LogHistory(kBtmLogTag,
- ToLegacyAddressWithType(remote_address_with_type),
- "Disconnection initiated", "Le");
- } else {
- LOG_WARN("Unable to disconnect unknown le connection handle:0x%04x",
- handle);
- }
- }
-
- void accept_le_connection_from(const hci::AddressWithType& address_with_type,
- bool is_direct, std::promise<bool> promise) {
- if (shadow_acceptlist_.IsFull()) {
- LOG_ERROR("Acceptlist is full preventing new Le connection");
- promise.set_value(false);
- return;
- }
- shadow_acceptlist_.Add(address_with_type);
- promise.set_value(true);
- GetAclManager()->CreateLeConnection(address_with_type, is_direct);
- LOG_DEBUG("Allow Le connection from remote:%s",
- PRIVATE_ADDRESS(address_with_type));
- BTM_LogHistory(kBtmLogTag, ToLegacyAddressWithType(address_with_type),
- "Allow connection from", "Le");
- }
-
- void ignore_le_connection_from(
- const hci::AddressWithType& address_with_type) {
- shadow_acceptlist_.Remove(address_with_type);
- GetAclManager()->CancelLeConnect(address_with_type);
- LOG_DEBUG("Ignore Le connection from remote:%s",
- PRIVATE_ADDRESS(address_with_type));
- BTM_LogHistory(kBtmLogTag, ToLegacyAddressWithType(address_with_type),
- "Ignore connection from", "Le");
- }
-
- void clear_acceptlist() {
- auto shadow_acceptlist = shadow_acceptlist_.GetCopy();
- size_t count = shadow_acceptlist.size();
- for (auto address_with_type : shadow_acceptlist) {
- ignore_le_connection_from(address_with_type);
- }
- shadow_acceptlist_.Clear();
- LOG_DEBUG("Cleared entire Le address acceptlist count:%zu", count);
- }
-
- void DumpConnectionHistory() const {
- std::vector<std::string> history =
- connection_history_.ReadElementsAsString();
- for (auto& entry : history) {
- LOG_DEBUG("%s", entry.c_str());
- }
- const auto acceptlist = shadow_acceptlist_.GetCopy();
- LOG_DEBUG("Shadow le accept list size:%-3zu controller_max_size:%hhu",
- acceptlist.size(),
- controller_get_interface()->get_ble_acceptlist_size());
- for (auto& entry : acceptlist) {
- LOG_DEBUG("acceptlist:%s", entry.ToString().c_str());
- }
- }
-
-#define DUMPSYS_TAG "shim::acl"
- void DumpConnectionHistory(int fd) const {
- std::vector<std::string> history =
- connection_history_.ReadElementsAsString();
- for (auto& entry : history) {
- LOG_DUMPSYS(fd, "%s", entry.c_str());
- }
- auto acceptlist = shadow_acceptlist_.GetCopy();
- LOG_DUMPSYS(fd,
- "Shadow le accept list size:%-3zu controller_max_size:%hhu",
- acceptlist.size(),
- controller_get_interface()->get_ble_acceptlist_size());
- unsigned cnt = 0;
- for (auto& entry : acceptlist) {
- LOG_DUMPSYS(fd, "%03u le acceptlist:%s", ++cnt, entry.ToString().c_str());
- }
- }
-#undef DUMPSYS_TAG
-};
-
-#define DUMPSYS_TAG "shim::legacy::l2cap"
-extern tL2C_CB l2cb;
-void DumpsysL2cap(int fd) {
- LOG_DUMPSYS_TITLE(fd, DUMPSYS_TAG);
- for (int i = 0; i < MAX_L2CAP_LINKS; i++) {
- const tL2C_LCB& lcb = l2cb.lcb_pool[i];
- if (!lcb.in_use) continue;
- LOG_DUMPSYS(fd, "link_state:%s", link_state_text(lcb.link_state).c_str());
- LOG_DUMPSYS(fd, "handle:0x%04x", lcb.Handle());
-
- const tL2C_CCB* ccb = lcb.ccb_queue.p_first_ccb;
- while (ccb != nullptr) {
- LOG_DUMPSYS(
- fd, " active channel lcid:0x%04x rcid:0x%04x is_ecoc:%s in_use:%s",
- ccb->local_cid, ccb->remote_cid, common::ToString(ccb->ecoc).c_str(),
- common::ToString(ccb->in_use).c_str());
- ccb = ccb->p_next_ccb;
- }
- }
-}
-
-#undef DUMPSYS_TAG
-#define DUMPSYS_TAG "shim::legacy::acl"
-void DumpsysAcl(int fd) {
- const tACL_CB& acl_cb = btm_cb.acl_cb_;
-
- LOG_DUMPSYS_TITLE(fd, DUMPSYS_TAG);
-
- shim::Stack::GetInstance()->GetAcl()->DumpConnectionHistory(fd);
-
- for (int i = 0; i < MAX_L2CAP_LINKS; i++) {
- const tACL_CONN& link = acl_cb.acl_db[i];
- if (!link.in_use) continue;
-
- LOG_DUMPSYS(fd, "remote_addr:%s handle:0x%04x transport:%s",
- link.remote_addr.ToString().c_str(), link.hci_handle,
- bt_transport_text(link.transport).c_str());
- LOG_DUMPSYS(fd, " link_up_issued:%5s",
- (link.link_up_issued) ? "true" : "false");
- LOG_DUMPSYS(fd, " flush_timeout:0x%04x", link.flush_timeout_in_ticks);
- LOG_DUMPSYS(fd, " link_supervision_timeout:%.3f sec",
- ticks_to_seconds(link.link_super_tout));
- LOG_DUMPSYS(fd, " disconnect_reason:0x%02x", link.disconnect_reason);
-
- if (link.is_transport_br_edr()) {
- for (int j = 0; j < HCI_EXT_FEATURES_PAGE_MAX + 1; j++) {
- LOG_DUMPSYS(fd, " peer_lmp_features[%d] valid:%s data:%s", j,
- common::ToString(link.peer_lmp_feature_valid[j]).c_str(),
- bd_features_text(link.peer_lmp_feature_pages[j]).c_str());
- }
- LOG_DUMPSYS(fd, " [classic] link_policy:%s",
- link_policy_text(static_cast<tLINK_POLICY>(link.link_policy))
- .c_str());
- LOG_DUMPSYS(fd, " [classic] sniff_subrating:%s",
- common::ToString(HCI_SNIFF_SUB_RATE_SUPPORTED(
- link.peer_lmp_feature_pages[0]))
- .c_str());
-
- LOG_DUMPSYS(fd, " pkt_types_mask:0x%04x", link.pkt_types_mask);
- LOG_DUMPSYS(fd, " role:%s", RoleText(link.link_role).c_str());
- } else if (link.is_transport_ble()) {
- LOG_DUMPSYS(fd, " [le] peer_features valid:%s data:%s",
- common::ToString(link.peer_le_features_valid).c_str(),
- bd_features_text(link.peer_le_features).c_str());
-
- LOG_DUMPSYS(fd, " [le] active_remote_addr:%s",
- link.active_remote_addr.ToString().c_str());
- LOG_DUMPSYS(fd, " [le] conn_addr:%s",
- link.conn_addr.ToString().c_str());
- }
- }
-}
-#undef DUMPSYS_TAG
-
-using Record = common::TimestampedEntry<std::string>;
-const std::string kTimeFormat("%Y-%m-%d %H:%M:%S");
-
-#define DUMPSYS_TAG "shim::legacy::hid"
-extern btif_hh_cb_t btif_hh_cb;
-
-void DumpsysHid(int fd) {
- LOG_DUMPSYS_TITLE(fd, DUMPSYS_TAG);
- LOG_DUMPSYS(fd, "status:%s num_devices:%u",
- btif_hh_status_text(btif_hh_cb.status).c_str(),
- btif_hh_cb.device_num);
- LOG_DUMPSYS(fd, "status:%s", btif_hh_status_text(btif_hh_cb.status).c_str());
- for (unsigned i = 0; i < BTIF_HH_MAX_HID; i++) {
- const btif_hh_device_t* p_dev = &btif_hh_cb.devices[i];
- if (p_dev->bd_addr != RawAddress::kEmpty) {
- LOG_DUMPSYS(fd, " %u: addr:%s fd:%d state:%s ready:%s thread_id:%d", i,
- PRIVATE_ADDRESS(p_dev->bd_addr), p_dev->fd,
- bthh_connection_state_text(p_dev->dev_status).c_str(),
- (p_dev->ready_for_data) ? ("T") : ("F"),
- static_cast<int>(p_dev->hh_poll_thread_id));
- }
- }
- for (unsigned i = 0; i < BTIF_HH_MAX_ADDED_DEV; i++) {
- const btif_hh_added_device_t* p_dev = &btif_hh_cb.added_devices[i];
- if (p_dev->bd_addr != RawAddress::kEmpty) {
- LOG_DUMPSYS(fd, " %u: addr:%s", i, PRIVATE_ADDRESS(p_dev->bd_addr));
- }
- }
-}
-#undef DUMPSYS_TAG
-
-#define DUMPSYS_TAG "shim::legacy::btm"
-void DumpsysBtm(int fd) {
- LOG_DUMPSYS_TITLE(fd, DUMPSYS_TAG);
- if (btm_cb.history_ != nullptr) {
- std::vector<Record> history = btm_cb.history_->Pull();
- for (auto& record : history) {
- time_t then = record.timestamp / 1000;
- struct tm tm;
- localtime_r(&then, &tm);
- auto s2 = common::StringFormatTime(kTimeFormat, tm);
- LOG_DUMPSYS(fd, " %s.%03u %s", s2.c_str(),
- static_cast<unsigned int>(record.timestamp % 1000),
- record.entry.c_str());
- }
- }
-}
-#undef DUMPSYS_TAG
-
-#define DUMPSYS_TAG "shim::legacy::record"
-void DumpsysRecord(int fd) {
- LOG_DUMPSYS_TITLE(fd, DUMPSYS_TAG);
-
- if (btm_cb.sec_dev_rec == nullptr) {
- LOG_DUMPSYS(fd, "Record is empty - no devices");
- return;
- }
-
- unsigned cnt = 0;
- list_node_t* end = list_end(btm_cb.sec_dev_rec);
- for (list_node_t* node = list_begin(btm_cb.sec_dev_rec); node != end;
- node = list_next(node)) {
- tBTM_SEC_DEV_REC* p_dev_rec =
- static_cast<tBTM_SEC_DEV_REC*>(list_node(node));
- LOG_DUMPSYS(fd, "%03u %s", ++cnt, p_dev_rec->ToString().c_str());
- }
-}
-#undef DUMPSYS_TAG
-
-void shim::legacy::Acl::Dump(int fd) const {
- DumpsysHid(fd);
- DumpsysRecord(fd);
- DumpsysAcl(fd);
- DumpsysL2cap(fd);
- DumpsysBtm(fd);
-}
-
-shim::legacy::Acl::Acl(os::Handler* handler,
- const acl_interface_t& acl_interface,
- uint8_t max_acceptlist_size)
- : handler_(handler), acl_interface_(acl_interface) {
- ASSERT(handler_ != nullptr);
- ValidateAclInterface(acl_interface_);
- pimpl_ = std::make_unique<Acl::impl>(max_acceptlist_size);
- GetAclManager()->RegisterCallbacks(this, handler_);
- GetAclManager()->RegisterLeCallbacks(this, handler_);
- GetController()->RegisterCompletedMonitorAclPacketsCallback(
- handler->BindOn(this, &Acl::on_incoming_acl_credits));
- shim::RegisterDumpsysFunction(static_cast<void*>(this),
- [this](int fd) { Dump(fd); });
-
- GetAclManager()->HACK_SetScoDisconnectCallback(
- [this](uint16_t handle, uint8_t reason) {
- TRY_POSTING_ON_MAIN(acl_interface_.connection.sco.on_disconnected,
- handle, static_cast<tHCI_REASON>(reason));
- });
-}
-
-shim::legacy::Acl::~Acl() {
- shim::UnregisterDumpsysFunction(static_cast<void*>(this));
- GetController()->UnregisterCompletedMonitorAclPacketsCallback();
-
- if (CheckForOrphanedAclConnections()) {
- pimpl_->DumpConnectionHistory();
- }
-}
-
-bool shim::legacy::Acl::CheckForOrphanedAclConnections() const {
- bool orphaned_acl_connections = false;
-
- if (!pimpl_->handle_to_classic_connection_map_.empty()) {
- LOG_ERROR("About to destroy classic active ACL");
- for (const auto& connection : pimpl_->handle_to_classic_connection_map_) {
- LOG_ERROR(" Orphaned classic ACL handle:0x%04x bd_addr:%s created:%s",
- connection.second->Handle(),
- PRIVATE_ADDRESS(connection.second->GetRemoteAddress()),
- common::StringFormatTimeWithMilliseconds(
- kConnectionDescriptorTimeFormat,
- connection.second->GetCreationTime())
- .c_str());
- }
- orphaned_acl_connections = true;
- }
-
- if (!pimpl_->handle_to_le_connection_map_.empty()) {
- LOG_ERROR("About to destroy le active ACL");
- for (const auto& connection : pimpl_->handle_to_le_connection_map_) {
- LOG_ERROR(" Orphaned le ACL handle:0x%04x bd_addr:%s created:%s",
- connection.second->Handle(),
- PRIVATE_ADDRESS(connection.second->GetRemoteAddressWithType()),
- common::StringFormatTimeWithMilliseconds(
- kConnectionDescriptorTimeFormat,
- connection.second->GetCreationTime())
- .c_str());
- }
- orphaned_acl_connections = true;
- }
- return orphaned_acl_connections;
-}
-
-void shim::legacy::Acl::on_incoming_acl_credits(uint16_t handle,
- uint16_t credits) {
- TRY_POSTING_ON_MAIN(acl_interface_.on_packets_completed, handle, credits);
-}
-
-void shim::legacy::Acl::write_data_sync(
- HciHandle handle, std::unique_ptr<packet::RawBuilder> packet) {
- if (pimpl_->IsClassicAcl(handle)) {
- pimpl_->EnqueueClassicPacket(handle, std::move(packet));
- } else if (pimpl_->IsLeAcl(handle)) {
- pimpl_->EnqueueLePacket(handle, std::move(packet));
- } else {
- LOG_ERROR("Unable to find destination to write data\n");
- }
-}
-
-void shim::legacy::Acl::WriteData(HciHandle handle,
- std::unique_ptr<packet::RawBuilder> packet) {
- handler_->Post(common::BindOnce(&Acl::write_data_sync,
- common::Unretained(this), handle,
- std::move(packet)));
-}
-
-void shim::legacy::Acl::CreateClassicConnection(const hci::Address& address) {
- GetAclManager()->CreateConnection(address);
- LOG_DEBUG("Connection initiated for classic to remote:%s",
- PRIVATE_ADDRESS(address));
- BTM_LogHistory(kBtmLogTag, ToRawAddress(address), "Initiated connection",
- "classic");
-}
-
-void shim::legacy::Acl::CancelClassicConnection(const hci::Address& address) {
- GetAclManager()->CancelConnect(address);
- LOG_DEBUG("Connection cancelled for classic to remote:%s",
- PRIVATE_ADDRESS(address));
- BTM_LogHistory(kBtmLogTag, ToRawAddress(address), "Cancelled connection",
- "classic");
-}
-
-void shim::legacy::Acl::AcceptLeConnectionFrom(
- const hci::AddressWithType& address_with_type, bool is_direct,
- std::promise<bool> promise) {
- handler_->CallOn(pimpl_.get(), &Acl::impl::accept_le_connection_from,
- address_with_type, is_direct, std::move(promise));
-}
-
-void shim::legacy::Acl::IgnoreLeConnectionFrom(
- const hci::AddressWithType& address_with_type) {
- handler_->CallOn(pimpl_.get(), &Acl::impl::ignore_le_connection_from,
- address_with_type);
-}
-
-void shim::legacy::Acl::OnClassicLinkDisconnected(HciHandle handle,
- hci::ErrorCode reason) {
- hci::Address remote_address =
- pimpl_->handle_to_classic_connection_map_[handle]->GetRemoteAddress();
- CreationTime creation_time =
- pimpl_->handle_to_classic_connection_map_[handle]->GetCreationTime();
- bool is_locally_initiated =
- pimpl_->handle_to_classic_connection_map_[handle]->IsLocallyInitiated();
-
- TeardownTime teardown_time = std::chrono::system_clock::now();
-
- pimpl_->handle_to_classic_connection_map_.erase(handle);
- TRY_POSTING_ON_MAIN(acl_interface_.connection.classic.on_disconnected,
- ToLegacyHciErrorCode(hci::ErrorCode::SUCCESS), handle,
- ToLegacyHciErrorCode(reason));
- LOG_DEBUG("Disconnected classic link remote:%s handle:%hu reason:%s",
- PRIVATE_ADDRESS(remote_address), handle,
- ErrorCodeText(reason).c_str());
- BTM_LogHistory(
- kBtmLogTag, ToRawAddress(remote_address), "Disconnected",
- base::StringPrintf("classic reason:%s", ErrorCodeText(reason).c_str()));
- pimpl_->connection_history_.Push(
- std::move(std::make_unique<ClassicConnectionDescriptor>(
- remote_address, creation_time, teardown_time, handle,
- is_locally_initiated, reason)));
-}
-
-bluetooth::hci::AddressWithType shim::legacy::Acl::GetConnectionLocalAddress(
- const RawAddress& remote_bda) {
- bluetooth::hci::AddressWithType address_with_type;
- auto remote_address = ToGdAddress(remote_bda);
- for (auto& [handle, connection] : pimpl_->handle_to_le_connection_map_) {
- if (connection->GetRemoteAddressWithType().GetAddress() == remote_address) {
- return connection->GetLocalAddressWithType();
- }
- }
- LOG_WARN("address not found!");
- return address_with_type;
-}
-
-void shim::legacy::Acl::OnLeLinkDisconnected(HciHandle handle,
- hci::ErrorCode reason) {
- hci::AddressWithType remote_address_with_type =
- pimpl_->handle_to_le_connection_map_[handle]->GetRemoteAddressWithType();
- CreationTime creation_time =
- pimpl_->handle_to_le_connection_map_[handle]->GetCreationTime();
- bool is_locally_initiated =
- pimpl_->handle_to_le_connection_map_[handle]->IsLocallyInitiated();
-
- TeardownTime teardown_time = std::chrono::system_clock::now();
-
- pimpl_->handle_to_le_connection_map_.erase(handle);
- TRY_POSTING_ON_MAIN(acl_interface_.connection.le.on_disconnected,
- ToLegacyHciErrorCode(hci::ErrorCode::SUCCESS), handle,
- ToLegacyHciErrorCode(reason));
- LOG_DEBUG("Disconnected le link remote:%s handle:%hu reason:%s",
- PRIVATE_ADDRESS(remote_address_with_type), handle,
- ErrorCodeText(reason).c_str());
- BTM_LogHistory(
- kBtmLogTag, ToLegacyAddressWithType(remote_address_with_type),
- "Disconnected",
- base::StringPrintf("Le reason:%s", ErrorCodeText(reason).c_str()));
- pimpl_->connection_history_.Push(
- std::move(std::make_unique<LeConnectionDescriptor>(
- remote_address_with_type, creation_time, teardown_time, handle,
- is_locally_initiated, reason)));
-}
-
-void shim::legacy::Acl::OnConnectSuccess(
- std::unique_ptr<hci::acl_manager::ClassicAclConnection> connection) {
- ASSERT(connection != nullptr);
- auto handle = connection->GetHandle();
- bool locally_initiated = connection->locally_initiated_;
- const hci::Address remote_address = connection->GetAddress();
- const RawAddress bd_addr = ToRawAddress(remote_address);
-
- pimpl_->handle_to_classic_connection_map_.emplace(
- handle, std::make_unique<ClassicShimAclConnection>(
- acl_interface_.on_send_data_upwards,
- std::bind(&shim::legacy::Acl::OnClassicLinkDisconnected, this,
- std::placeholders::_1, std::placeholders::_2),
- acl_interface_.link.classic, handler_, std::move(connection),
- std::chrono::system_clock::now()));
- pimpl_->handle_to_classic_connection_map_[handle]->RegisterCallbacks();
- pimpl_->handle_to_classic_connection_map_[handle]
- ->ReadRemoteControllerInformation();
-
- TRY_POSTING_ON_MAIN(acl_interface_.connection.classic.on_connected, bd_addr,
- handle, false);
- LOG_DEBUG("Connection successful classic remote:%s handle:%hu initiator:%s",
- PRIVATE_ADDRESS(remote_address), handle,
- (locally_initiated) ? "local" : "remote");
- BTM_LogHistory(kBtmLogTag, ToRawAddress(remote_address),
- "Connection successful",
- (locally_initiated) ? "Local initiated" : "Remote initiated");
-}
-
-void shim::legacy::Acl::OnConnectFail(hci::Address address,
- hci::ErrorCode reason) {
- const RawAddress bd_addr = ToRawAddress(address);
- TRY_POSTING_ON_MAIN(acl_interface_.connection.classic.on_failed, bd_addr,
- ToLegacyHciErrorCode(reason));
- LOG_WARN("Connection failed classic remote:%s reason:%s",
- PRIVATE_ADDRESS(address), hci::ErrorCodeText(reason).c_str());
- BTM_LogHistory(kBtmLogTag, ToRawAddress(address), "Connection failed",
- base::StringPrintf("classic reason:%s",
- hci::ErrorCodeText(reason).c_str()));
-}
-
-void shim::legacy::Acl::HACK_OnEscoConnectRequest(hci::Address address,
- hci::ClassOfDevice cod) {
- const RawAddress bd_addr = ToRawAddress(address);
- types::ClassOfDevice legacy_cod;
- types::ClassOfDevice::FromString(cod.ToLegacyConfigString(), legacy_cod);
-
- TRY_POSTING_ON_MAIN(acl_interface_.connection.sco.on_esco_connect_request,
- bd_addr, legacy_cod);
- LOG_DEBUG("Received ESCO connect request remote:%s",
- PRIVATE_ADDRESS(address));
- BTM_LogHistory(kBtmLogTag, ToRawAddress(address), "ESCO Connection request");
-}
-
-void shim::legacy::Acl::HACK_OnScoConnectRequest(hci::Address address,
- hci::ClassOfDevice cod) {
- const RawAddress bd_addr = ToRawAddress(address);
- types::ClassOfDevice legacy_cod;
- types::ClassOfDevice::FromString(cod.ToLegacyConfigString(), legacy_cod);
-
- TRY_POSTING_ON_MAIN(acl_interface_.connection.sco.on_sco_connect_request,
- bd_addr, legacy_cod);
- LOG_DEBUG("Received SCO connect request remote:%s", PRIVATE_ADDRESS(address));
- BTM_LogHistory(kBtmLogTag, ToRawAddress(address), "SCO Connection request");
-}
-
-void shim::legacy::Acl::OnLeConnectSuccess(
- hci::AddressWithType address_with_type,
- std::unique_ptr<hci::acl_manager::LeAclConnection> connection) {
- ASSERT(connection != nullptr);
- auto handle = connection->GetHandle();
-
- hci::Role connection_role = connection->GetRole();
- bool locally_initiated = connection->locally_initiated_;
-
- pimpl_->handle_to_le_connection_map_.emplace(
- handle, std::make_unique<LeShimAclConnection>(
- acl_interface_.on_send_data_upwards,
- std::bind(&shim::legacy::Acl::OnLeLinkDisconnected, this,
- std::placeholders::_1, std::placeholders::_2),
- acl_interface_.link.le, handler_, std::move(connection),
- std::chrono::system_clock::now()));
- pimpl_->handle_to_le_connection_map_[handle]->RegisterCallbacks();
-
- pimpl_->handle_to_le_connection_map_[handle]
- ->ReadRemoteControllerInformation();
-
- tBLE_BD_ADDR legacy_address_with_type =
- ToLegacyAddressWithType(address_with_type);
-
- uint16_t conn_interval = 36; /* TODO Default to 45 msec*/
- uint16_t conn_latency = 0; /* TODO Default to zero events */
- uint16_t conn_timeout = 500; /* TODO Default to 5s */
-
- RawAddress local_rpa = RawAddress::kEmpty; /* TODO enhanced */
- RawAddress peer_rpa = RawAddress::kEmpty; /* TODO enhanced */
- uint8_t peer_addr_type = 0; /* TODO public */
-
- // Once an le connection has successfully been established
- // the device address is removed from the controller accept list.
- pimpl_->shadow_acceptlist_.Remove(address_with_type);
-
- TRY_POSTING_ON_MAIN(
- acl_interface_.connection.le.on_connected, legacy_address_with_type,
- handle, ToLegacyRole(connection_role), conn_interval, conn_latency,
- conn_timeout, local_rpa, peer_rpa, peer_addr_type);
-
- LOG_DEBUG("Connection successful le remote:%s handle:%hu initiator:%s",
- PRIVATE_ADDRESS(address_with_type), handle,
- (locally_initiated) ? "local" : "remote");
- BTM_LogHistory(kBtmLogTag, ToLegacyAddressWithType(address_with_type),
- "Connection successful", "Le");
-}
-
-void shim::legacy::Acl::OnLeConnectFail(hci::AddressWithType address_with_type,
- hci::ErrorCode reason) {
- tBLE_BD_ADDR legacy_address_with_type =
- ToLegacyAddressWithType(address_with_type);
-
- uint16_t handle = 0; /* TODO Unneeded */
- bool enhanced = true; /* TODO logging metrics only */
- tHCI_STATUS status = ToLegacyHciErrorCode(reason);
-
- TRY_POSTING_ON_MAIN(acl_interface_.connection.le.on_failed,
- legacy_address_with_type, handle, enhanced, status);
- LOG_WARN("Connection failed le remote:%s",
- PRIVATE_ADDRESS(address_with_type));
- BTM_LogHistory(
- kBtmLogTag, ToLegacyAddressWithType(address_with_type),
- "Connection failed",
- base::StringPrintf("le reason:%s", hci::ErrorCodeText(reason).c_str()));
-}
-
-void shim::legacy::Acl::ConfigureLePrivacy(bool is_le_privacy_enabled) {
- LOG_INFO("Configuring Le privacy:%s",
- (is_le_privacy_enabled) ? "true" : "false");
- ASSERT_LOG(is_le_privacy_enabled,
- "Gd shim does not support unsecure le privacy");
-
- // TODO(b/161543441): read the privacy policy from device-specific
- // configuration, and IRK from config file.
- hci::LeAddressManager::AddressPolicy address_policy =
- hci::LeAddressManager::AddressPolicy::USE_RESOLVABLE_ADDRESS;
- hci::AddressWithType empty_address_with_type(
- hci::Address{}, hci::AddressType::RANDOM_DEVICE_ADDRESS);
- /* 7 minutes minimum, 15 minutes maximum for random address refreshing */
- auto minimum_rotation_time = std::chrono::minutes(7);
- auto maximum_rotation_time = std::chrono::minutes(15);
-
- GetAclManager()->SetPrivacyPolicyForInitiatorAddress(
- address_policy, empty_address_with_type, minimum_rotation_time,
- maximum_rotation_time);
-}
-
-void shim::legacy::Acl::DisconnectClassic(uint16_t handle, tHCI_STATUS reason) {
- handler_->CallOn(pimpl_.get(), &Acl::impl::disconnect_classic, handle,
- reason);
-}
-
-void shim::legacy::Acl::DisconnectLe(uint16_t handle, tHCI_STATUS reason) {
- handler_->CallOn(pimpl_.get(), &Acl::impl::disconnect_le, handle, reason);
-}
-
-bool shim::legacy::Acl::HoldMode(uint16_t hci_handle, uint16_t max_interval,
- uint16_t min_interval) {
- handler_->CallOn(pimpl_.get(), &Acl::impl::HoldMode, hci_handle, max_interval,
- min_interval);
- return false; // TODO void
-}
-
-bool shim::legacy::Acl::SniffMode(uint16_t hci_handle, uint16_t max_interval,
- uint16_t min_interval, uint16_t attempt,
- uint16_t timeout) {
- handler_->CallOn(pimpl_.get(), &Acl::impl::SniffMode, hci_handle,
- max_interval, min_interval, attempt, timeout);
- return false;
-}
-
-bool shim::legacy::Acl::ExitSniffMode(uint16_t hci_handle) {
- handler_->CallOn(pimpl_.get(), &Acl::impl::ExitSniffMode, hci_handle);
- return false;
-}
-
-bool shim::legacy::Acl::SniffSubrating(uint16_t hci_handle,
- uint16_t maximum_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) {
- handler_->CallOn(pimpl_.get(), &Acl::impl::SniffSubrating, hci_handle,
- maximum_latency, minimum_remote_timeout,
- minimum_local_timeout);
- return false;
-}
-
-void shim::legacy::Acl::HACK_OnScoDisconnected(uint16_t handle,
- uint8_t reason) {
- TRY_POSTING_ON_MAIN(acl_interface_.connection.sco.on_disconnected, handle,
- static_cast<tHCI_REASON>(reason));
-}
-
-void shim::legacy::Acl::DumpConnectionHistory(int fd) const {
- pimpl_->DumpConnectionHistory(fd);
-}
-
-void shim::legacy::Acl::Shutdown() {
- if (CheckForOrphanedAclConnections()) {
- std::promise<void> shutdown_promise;
- auto shutdown_future = shutdown_promise.get_future();
- handler_->CallOn(pimpl_.get(), &Acl::impl::ShutdownClassicConnections,
- std::move(shutdown_promise));
- shutdown_future.wait();
-
- shutdown_promise = std::promise<void>();
-
- shutdown_future = shutdown_promise.get_future();
- handler_->CallOn(pimpl_.get(), &Acl::impl::ShutdownLeConnections,
- std::move(shutdown_promise));
- shutdown_future.wait();
- LOG_WARN("Flushed open ACL connections");
- } else {
- LOG_INFO("All ACL connections have been previously closed");
- }
-}
-
-void shim::legacy::Acl::FinalShutdown() {
- std::promise<void> promise;
- auto future = promise.get_future();
- GetAclManager()->UnregisterCallbacks(this, std::move(promise));
- future.wait();
- LOG_DEBUG("Unregistered classic callbacks from gd acl manager");
-
- promise = std::promise<void>();
- future = promise.get_future();
- GetAclManager()->UnregisterLeCallbacks(this, std::move(promise));
- future.wait();
- LOG_DEBUG("Unregistered le callbacks from gd acl manager");
-
- promise = std::promise<void>();
- future = promise.get_future();
- handler_->CallOn(pimpl_.get(), &Acl::impl::FinalShutdown, std::move(promise));
- future.wait();
- LOG_INFO("Unregistered and cleared any orphaned ACL connections");
-}
-
-void shim::legacy::Acl::ClearAcceptList() {
- handler_->CallOn(pimpl_.get(), &Acl::impl::clear_acceptlist);
-}
diff --git a/main/shim/acl.h b/main/shim/acl.h
deleted file mode 100644
index bb62b2ac1..000000000
--- a/main/shim/acl.h
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <future>
-#include <memory>
-
-#include "gd/hci/acl_manager/connection_callbacks.h"
-#include "gd/hci/acl_manager/le_connection_callbacks.h"
-#include "gd/hci/address.h"
-#include "gd/hci/address_with_type.h"
-#include "gd/hci/class_of_device.h"
-#include "gd/os/handler.h"
-#include "gd/packet/raw_builder.h"
-#include "main/shim/acl_legacy_interface.h"
-#include "main/shim/link_connection_interface.h"
-#include "main/shim/link_policy_interface.h"
-#include "stack/include/bt_types.h"
-
-namespace bluetooth {
-namespace shim {
-namespace legacy {
-
-class Acl : public hci::acl_manager::ConnectionCallbacks,
- public hci::acl_manager::LeConnectionCallbacks,
- public LinkConnectionInterface,
- public LinkPolicyInterface {
- public:
- Acl(os::Handler* handler, const acl_interface_t& acl_interface,
- uint8_t max_acceptlist_size);
- ~Acl();
-
- // hci::acl_manager::ConnectionCallbacks
- void OnConnectSuccess(
- std::unique_ptr<hci::acl_manager::ClassicAclConnection>) override;
- void OnConnectFail(hci::Address, hci::ErrorCode reason) override;
-
- void HACK_OnEscoConnectRequest(hci::Address, hci::ClassOfDevice) override;
- void HACK_OnScoConnectRequest(hci::Address, hci::ClassOfDevice) override;
-
- void OnClassicLinkDisconnected(uint16_t handle, hci::ErrorCode reason);
-
- // hci::acl_manager::LeConnectionCallbacks
- void OnLeConnectSuccess(
- hci::AddressWithType,
- std::unique_ptr<hci::acl_manager::LeAclConnection>) override;
- void OnLeConnectFail(hci::AddressWithType, hci::ErrorCode reason) override;
- void OnLeLinkDisconnected(uint16_t handle, hci::ErrorCode reason);
- bluetooth::hci::AddressWithType GetConnectionLocalAddress(
- const RawAddress& remote_bda);
-
- // LinkConnectionInterface
- void CreateClassicConnection(const hci::Address& address) override;
- void CancelClassicConnection(const hci::Address& address) override;
- void AcceptLeConnectionFrom(const hci::AddressWithType& address_with_type,
- bool is_direct,
- std::promise<bool> promise) override;
- void IgnoreLeConnectionFrom(
- const hci::AddressWithType& address_with_type) override;
- void DisconnectClassic(uint16_t handle, tHCI_REASON reason) override;
- void DisconnectLe(uint16_t handle, tHCI_REASON reason) override;
-
- // LinkPolicyInterface
- bool HoldMode(uint16_t hci_handle, uint16_t max_interval,
- uint16_t min_interval) override;
- bool SniffMode(uint16_t hci_handle, uint16_t max_interval,
- uint16_t min_interval, uint16_t attempt,
- uint16_t timeout) override;
- bool ExitSniffMode(uint16_t hci_handle) override;
- bool SniffSubrating(uint16_t hci_handle, uint16_t maximum_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) override;
-
- void HACK_OnScoDisconnected(uint16_t handle, uint8_t reason);
-
- void WriteData(uint16_t hci_handle,
- std::unique_ptr<packet::RawBuilder> packet);
-
- void ConfigureLePrivacy(bool is_le_privacy_enabled);
-
- void Dump(int fd) const;
- void DumpConnectionHistory(int fd) const;
-
- void Shutdown();
- void FinalShutdown();
-
- void ClearAcceptList();
-
- protected:
- void on_incoming_acl_credits(uint16_t handle, uint16_t credits);
- void write_data_sync(uint16_t hci_handle,
- std::unique_ptr<packet::RawBuilder> packet);
-
- private:
- os::Handler* handler_;
- const acl_interface_t acl_interface_;
-
- bool CheckForOrphanedAclConnections() const;
-
- struct impl;
- std::unique_ptr<impl> pimpl_;
- DISALLOW_COPY_AND_ASSIGN(Acl);
-};
-
-} // namespace legacy
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/acl_api.cc b/main/shim/acl_api.cc
deleted file mode 100644
index c105a69de..000000000
--- a/main/shim/acl_api.cc
+++ /dev/null
@@ -1,106 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <cstddef>
-#include <cstdint>
-#include <future>
-
-#include "gd/hci/acl_manager.h"
-#include "main/shim/acl_api.h"
-#include "main/shim/dumpsys.h"
-#include "main/shim/helpers.h"
-#include "main/shim/stack.h"
-#include "types/ble_address_with_type.h"
-#include "types/raw_address.h"
-
-void bluetooth::shim::ACL_CreateClassicConnection(
- const RawAddress& raw_address) {
- auto address = ToGdAddress(raw_address);
- Stack::GetInstance()->GetAcl()->CreateClassicConnection(address);
-}
-
-void bluetooth::shim::ACL_CancelClassicConnection(
- const RawAddress& raw_address) {
- auto address = ToGdAddress(raw_address);
- Stack::GetInstance()->GetAcl()->CancelClassicConnection(address);
-}
-
-bool bluetooth::shim::ACL_AcceptLeConnectionFrom(
- const tBLE_BD_ADDR& legacy_address_with_type, bool is_direct) {
- std::promise<bool> promise;
- auto future = promise.get_future();
- Stack::GetInstance()->GetAcl()->AcceptLeConnectionFrom(
- ToAddressWithTypeFromLegacy(legacy_address_with_type), is_direct,
- std::move(promise));
- return future.get();
-}
-
-void bluetooth::shim::ACL_IgnoreLeConnectionFrom(
- const tBLE_BD_ADDR& legacy_address_with_type) {
- Stack::GetInstance()->GetAcl()->IgnoreLeConnectionFrom(
- ToAddressWithTypeFromLegacy(legacy_address_with_type));
-}
-
-void bluetooth::shim::ACL_WriteData(uint16_t handle, BT_HDR* p_buf) {
- std::unique_ptr<bluetooth::packet::RawBuilder> packet = MakeUniquePacket(
- p_buf->data + p_buf->offset + HCI_DATA_PREAMBLE_SIZE,
- p_buf->len - HCI_DATA_PREAMBLE_SIZE, IsPacketFlushable(p_buf));
- Stack::GetInstance()->GetAcl()->WriteData(handle, std::move(packet));
- osi_free(p_buf);
-}
-
-void bluetooth::shim::ACL_ConfigureLePrivacy(bool is_le_privacy_enabled) {
- hci::LeAddressManager::AddressPolicy address_policy =
- is_le_privacy_enabled
- ? hci::LeAddressManager::AddressPolicy::USE_RESOLVABLE_ADDRESS
- : hci::LeAddressManager::AddressPolicy::USE_PUBLIC_ADDRESS;
- hci::AddressWithType empty_address_with_type(
- hci::Address{}, hci::AddressType::RANDOM_DEVICE_ADDRESS);
- /* 7 minutes minimum, 15 minutes maximum for random address refreshing */
- auto minimum_rotation_time = std::chrono::minutes(7);
- auto maximum_rotation_time = std::chrono::minutes(15);
-
- Stack::GetInstance()
- ->GetStackManager()
- ->GetInstance<bluetooth::hci::AclManager>()
- ->SetPrivacyPolicyForInitiatorAddress(
- address_policy, empty_address_with_type, minimum_rotation_time,
- maximum_rotation_time);
-}
-
-void bluetooth::shim::ACL_Disconnect(uint16_t handle, bool is_classic,
- tHCI_STATUS reason) {
- (is_classic)
- ? Stack::GetInstance()->GetAcl()->DisconnectClassic(handle, reason)
- : Stack::GetInstance()->GetAcl()->DisconnectLe(handle, reason);
-}
-
-void bluetooth::shim::ACL_Shutdown() {
- Stack::GetInstance()->GetAcl()->Shutdown();
-}
-
-void bluetooth::shim::ACL_IgnoreAllLeConnections() {
- return Stack::GetInstance()->GetAcl()->ClearAcceptList();
-}
-
-void bluetooth::shim::ACL_ReadConnectionAddress(const RawAddress& pseudo_addr,
- RawAddress& conn_addr,
- uint8_t* p_addr_type) {
- auto local_address =
- Stack::GetInstance()->GetAcl()->GetConnectionLocalAddress(pseudo_addr);
- conn_addr = ToRawAddress(local_address.GetAddress());
- *p_addr_type = static_cast<uint8_t>(local_address.GetAddressType());
-}
diff --git a/main/shim/acl_api.h b/main/shim/acl_api.h
deleted file mode 100644
index 008f970b0..000000000
--- a/main/shim/acl_api.h
+++ /dev/null
@@ -1,43 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "stack/include/bt_types.h"
-#include "stack/include/hci_error_code.h"
-#include "types/ble_address_with_type.h"
-#include "types/raw_address.h"
-
-namespace bluetooth {
-namespace shim {
-
-void ACL_CreateClassicConnection(const RawAddress& raw_address);
-void ACL_CancelClassicConnection(const RawAddress& raw_address);
-bool ACL_AcceptLeConnectionFrom(const tBLE_BD_ADDR& legacy_address_with_type,
- bool is_direct);
-void ACL_IgnoreLeConnectionFrom(const tBLE_BD_ADDR& legacy_address_with_type);
-
-void ACL_Disconnect(uint16_t handle, bool is_classic, tHCI_STATUS reason);
-void ACL_WriteData(uint16_t handle, BT_HDR* p_buf);
-void ACL_ConfigureLePrivacy(bool is_le_privacy_enabled);
-void ACL_Shutdown();
-void ACL_IgnoreAllLeConnections();
-
-void ACL_ReadConnectionAddress(const RawAddress& pseudo_addr,
- RawAddress& conn_addr, uint8_t* p_addr_type);
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/acl_legacy_interface.cc b/main/shim/acl_legacy_interface.cc
deleted file mode 100644
index 4c4389034..000000000
--- a/main/shim/acl_legacy_interface.cc
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "main/shim/acl_legacy_interface.h"
-#include "stack/include/acl_hci_link_interface.h"
-#include "stack/include/ble_acl_interface.h"
-#include "stack/include/sco_hci_link_interface.h"
-#include "stack/include/sec_hci_link_interface.h"
-
-struct tBTM_ESCO_DATA;
-
-namespace bluetooth {
-namespace shim {
-namespace legacy {
-
-const acl_interface_t GetAclInterface() {
- acl_interface_t acl_interface{
- .on_send_data_upwards = acl_rcv_acl_data,
- .on_packets_completed = acl_packets_completed,
-
- .connection.classic.on_connected = on_acl_br_edr_connected,
- .connection.classic.on_failed = on_acl_br_edr_failed,
- .connection.classic.on_disconnected = btm_acl_disconnected,
-
- .connection.le.on_connected =
- acl_ble_enhanced_connection_complete_from_shim,
- .connection.le.on_failed = acl_ble_connection_fail,
- .connection.le.on_disconnected = btm_acl_disconnected,
-
- .connection.sco.on_esco_connect_request = btm_sco_on_esco_connect_request,
- .connection.sco.on_sco_connect_request = btm_sco_on_sco_connect_request,
- .connection.sco.on_disconnected = btm_sco_on_disconnected,
-
- .link.classic.on_authentication_complete = btm_sec_auth_complete,
- .link.classic.on_central_link_key_complete = nullptr,
- .link.classic.on_change_connection_link_key_complete = nullptr,
- .link.classic.on_encryption_change = nullptr,
- .link.classic.on_flow_specification_complete = nullptr,
- .link.classic.on_flush_occurred = nullptr,
- .link.classic.on_mode_change = btm_pm_on_mode_change,
- .link.classic.on_packet_type_changed = nullptr,
- .link.classic.on_qos_setup_complete = nullptr,
- .link.classic.on_read_afh_channel_map_complete = nullptr,
- .link.classic.on_read_automatic_flush_timeout_complete = nullptr,
- .link.classic.on_sniff_subrating = btm_pm_on_sniff_subrating,
- .link.classic.on_read_clock_complete = nullptr,
- .link.classic.on_read_clock_offset_complete = nullptr,
- .link.classic.on_read_failed_contact_counter_complete = nullptr,
- .link.classic.on_read_link_policy_settings_complete = nullptr,
- .link.classic.on_read_link_quality_complete = nullptr,
- .link.classic.on_read_link_supervision_timeout_complete = nullptr,
- .link.classic.on_read_remote_version_information_complete =
- btm_read_remote_version_complete,
- .link.classic.on_read_remote_supported_features_complete =
- acl_process_supported_features,
- .link.classic.on_read_remote_extended_features_complete =
- acl_process_extended_features,
- .link.classic.on_read_rssi_complete = nullptr,
- .link.classic.on_read_transmit_power_level_complete = nullptr,
- .link.classic.on_role_change = btm_acl_role_changed,
- .link.classic.on_role_discovery_complete = nullptr,
-
- .link.le.on_connection_update = acl_ble_update_event_received,
- .link.le.on_data_length_change = nullptr,
- .link.le.on_read_remote_version_information_complete =
- btm_read_remote_version_complete,
- };
- return acl_interface;
-}
-
-} // namespace legacy
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/acl_legacy_interface.h b/main/shim/acl_legacy_interface.h
deleted file mode 100644
index 85dcbd059..000000000
--- a/main/shim/acl_legacy_interface.h
+++ /dev/null
@@ -1,146 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include "stack/include/bt_types.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcidefs.h"
-#include "types/ble_address_with_type.h"
-#include "types/class_of_device.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
-
-namespace bluetooth {
-namespace shim {
-namespace legacy {
-
-typedef struct {
- void (*on_connected)(const RawAddress& bda, uint16_t handle,
- uint8_t enc_mode);
- void (*on_failed)(const RawAddress& bda, tHCI_STATUS status);
- void (*on_disconnected)(tHCI_STATUS status, uint16_t handle,
- tHCI_STATUS reason);
-} acl_classic_connection_interface_t;
-
-typedef struct {
- void (*on_connected)(const tBLE_BD_ADDR& address_with_type, uint16_t handle,
- tHCI_ROLE role, uint16_t conn_interval,
- uint16_t conn_latency, uint16_t conn_timeout,
- const RawAddress& local_rpa, const RawAddress& peer_rpa,
- uint8_t peer_addr_type);
- void (*on_failed)(const tBLE_BD_ADDR& address_with_type, uint16_t handle,
- bool enhanced, tHCI_STATUS status);
- void (*on_disconnected)(tHCI_STATUS status, uint16_t handle,
- tHCI_STATUS reason);
-} acl_le_connection_interface_t;
-
-typedef struct {
- void (*on_esco_connect_request)(const RawAddress&,
- const types::ClassOfDevice&);
- void (*on_sco_connect_request)(const RawAddress&,
- const types::ClassOfDevice&);
- void (*on_disconnected)(uint16_t handle, tHCI_REASON reason);
-} acl_sco_connection_interface_t;
-
-typedef struct {
- void (*on_authentication_complete)(uint16_t handle, tHCI_STATUS status);
- void (*on_change_connection_link_key_complete)();
- void (*on_encryption_change)(bool enabled);
- void (*on_flow_specification_complete)(uint16_t flow_direction,
- uint16_t service_type,
- uint32_t token_rate,
- uint32_t token_bucket_size,
- uint32_t peak_bandwidth,
- uint32_t access_latency);
- void (*on_flush_occurred)();
- void (*on_central_link_key_complete)(uint8_t key_flag);
- void (*on_mode_change)(tHCI_STATUS status, uint16_t handle,
- tHCI_MODE current_mode, uint16_t interval);
- void (*on_sniff_subrating)(tHCI_STATUS status, uint16_t handle,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout);
- void (*on_packet_type_changed)(uint16_t packet_type);
- void (*on_qos_setup_complete)(uint16_t service_type, uint32_t token_rate,
- uint32_t peak_bandwidth, uint32_t latency,
- uint32_t delay_variation);
- void (*on_read_afh_channel_map_complete)(uint8_t afh_mode,
- uint8_t afh_channel_map[]);
- void (*on_read_automatic_flush_timeout_complete)(uint16_t flush_timeout);
- void (*on_read_clock_complete)(uint32_t clock, uint16_t accuracy);
- void (*on_read_clock_offset_complete)(uint16_t clock_offset);
- void (*on_read_failed_contact_counter_complete)(
- uint16_t failed_contact_counter);
- void (*on_read_link_policy_settings_complete)(uint16_t link_policy_settings);
- void (*on_read_link_quality_complete)(uint8_t link_quality);
- void (*on_read_link_supervision_timeout_complete)(
- uint16_t link_supervision_timeout);
- void (*on_read_remote_supported_features_complete)(uint16_t handle,
- uint64_t features);
- void (*on_read_remote_extended_features_complete)(uint16_t handle,
- uint8_t current_page_number,
- uint8_t max_page_number,
- uint64_t features);
- void (*on_read_remote_version_information_complete)(
- tHCI_STATUS status, uint16_t handle, uint8_t lmp_version,
- uint16_t manufacturer_name, uint16_t sub_version);
- void (*on_read_rssi_complete)(uint8_t rssi);
- void (*on_read_transmit_power_level_complete)(uint8_t transmit_power_level);
- void (*on_role_change)(tHCI_STATUS status, const RawAddress& bd_addr,
- tHCI_ROLE new_role);
- void (*on_role_discovery_complete)(tHCI_ROLE current_role);
-} acl_classic_link_interface_t;
-
-typedef struct {
- void (*on_connection_update)(tHCI_STATUS status, uint16_t handle,
- uint16_t connection_interval,
- uint16_t connection_latency,
- uint16_t supervision_timeout);
- void (*on_data_length_change)(uint16_t tx_octets, uint16_t tx_time,
- uint16_t rx_octets, uint16_t rx_time);
- void (*on_read_remote_version_information_complete)(
- tHCI_STATUS status, uint16_t handle, uint8_t lmp_version,
- uint16_t manufacturer_name, uint16_t sub_version);
- void (*on_phy_update)(tHCI_STATUS status, uint16_t handle, uint8_t tx_phy,
- uint8_t rx_phy);
-} acl_le_link_interface_t;
-
-typedef struct {
- acl_classic_connection_interface_t classic;
- acl_le_connection_interface_t le;
- acl_sco_connection_interface_t sco;
-} acl_connection_interface_t;
-
-typedef struct {
- acl_classic_link_interface_t classic;
- acl_le_link_interface_t le;
-} acl_link_interface_t;
-
-typedef struct {
- void (*on_send_data_upwards)(BT_HDR*);
- void (*on_packets_completed)(uint16_t handle, uint16_t num_packets);
- acl_connection_interface_t connection;
- acl_link_interface_t link;
-} acl_interface_t;
-
-const acl_interface_t GetAclInterface();
-
-} // namespace legacy
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/activity_attribution.cc b/main/shim/activity_attribution.cc
deleted file mode 100644
index 5b51fa963..000000000
--- a/main/shim/activity_attribution.cc
+++ /dev/null
@@ -1,88 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "bt_shim_activity_attribution"
-#include "activity_attribution.h"
-
-#include "btif/include/btif_common.h"
-#include "gd/btaa/activity_attribution.h"
-#include "helpers.h"
-#include "main/shim/entry.h"
-
-class ActivityAttributionInterfaceImpl
- : public ActivityAttributionInterface,
- public bluetooth::activity_attribution::ActivityAttributionCallback {
- public:
- ~ActivityAttributionInterfaceImpl() override = default;
-
- static ActivityAttributionInterfaceImpl* GetInstance() {
- static ActivityAttributionInterfaceImpl* instance =
- new ActivityAttributionInterfaceImpl();
- return instance;
- }
-
- void Init() override {
- bluetooth::shim::GetActivityAttribution()
- ->RegisterActivityAttributionCallback(this);
- }
-
- void RegisterCallbacks(ActivityAttributionCallbacks* callbacks) override {
- this->callbacks = callbacks;
- }
-
- void Cleanup(void) override{};
-
- void OnWakeup(const Activity activity,
- const bluetooth::hci::Address& address) override {
- do_in_jni_thread(
- FROM_HERE, base::Bind(&ActivityAttributionCallbacks::OnWakeup,
- base::Unretained(callbacks),
- (ActivityAttributionCallbacks::Activity)activity,
- bluetooth::ToRawAddress(address)));
- }
-
- void OnActivityLogsReady(
- const std::vector<BtaaAggregationEntry> logs) override {
- std::vector<ActivityAttributionCallbacks::BtaaAggregationEntry>
- callback_logs;
- for (auto& it : logs) {
- ActivityAttributionCallbacks::BtaaAggregationEntry entry{
- bluetooth::ToRawAddress(it.address),
- (ActivityAttributionCallbacks::Activity)it.activity, it.wakeup_count,
- it.byte_count, it.wakelock_duration_ms};
- callback_logs.push_back(entry);
- }
- do_in_jni_thread(
- FROM_HERE,
- base::Bind(&ActivityAttributionCallbacks::OnActivityLogsReady,
- base::Unretained(callbacks), callback_logs));
- }
-
- private:
- // Private constructor to prevent construction.
- ActivityAttributionInterfaceImpl() {}
-
- ActivityAttributionCallbacks* callbacks;
-};
-
-ActivityAttributionInterface*
-bluetooth::shim::get_activity_attribution_instance() {
- return ActivityAttributionInterfaceImpl::GetInstance();
-}
-
-void bluetooth::shim::init_activity_attribution() {
- bluetooth::shim::get_activity_attribution_instance()->Init();
-}
diff --git a/main/shim/activity_attribution.h b/main/shim/activity_attribution.h
deleted file mode 100644
index 00d809997..000000000
--- a/main/shim/activity_attribution.h
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/**
- * Gd shim layer to activity attribution
- */
-#pragma once
-
-#include "include/hardware/bt_activity_attribution.h"
-
-using namespace bluetooth::activity_attribution;
-
-namespace bluetooth {
-namespace shim {
-
-ActivityAttributionInterface* get_activity_attribution_instance();
-
-void init_activity_attribution();
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/btm.cc b/main/shim/btm.cc
index b6a213504..12d73e447 100644
--- a/main/shim/btm.cc
+++ b/main/shim/btm.cc
@@ -17,36 +17,39 @@
#define LOG_TAG "bt_shim_btm"
#include <algorithm>
-#include <chrono>
#include <cstddef>
#include <cstdint>
#include <cstring>
#include <mutex>
-#include "bta/include/bta_api.h"
#include "main/shim/btm.h"
#include "main/shim/controller.h"
#include "main/shim/entry.h"
-#include "main/shim/helpers.h"
#include "main/shim/shim.h"
-#include "stack/btm/btm_dev.h"
+#include "osi/include/log.h"
#include "stack/btm/btm_int_types.h"
-#include "types/bt_transport.h"
+#include "types/class_of_device.h"
#include "types/raw_address.h"
-#include "gd/hci/le_advertising_manager.h"
-#include "gd/hci/le_scanning_manager.h"
-#include "gd/neighbor/connectability.h"
-#include "gd/neighbor/discoverability.h"
-#include "gd/neighbor/inquiry.h"
-#include "gd/neighbor/name.h"
-#include "gd/neighbor/page.h"
-#include "gd/security/security_module.h"
+#include "hci/le_advertising_manager.h"
+#include "hci/le_scanning_manager.h"
+#include "main/shim/helpers.h"
+#include "neighbor/connectability.h"
+#include "neighbor/discoverability.h"
+#include "neighbor/inquiry.h"
+#include "neighbor/name.h"
+#include "neighbor/page.h"
+#include "security/security_module.h"
+#include "shim/controller.h"
extern tBTM_CB btm_cb;
static constexpr size_t kRemoteDeviceNameLength = 248;
+static constexpr uint8_t kAdvDataInfoNotPresent = 0xff;
+static constexpr uint8_t kTxPowerInformationNotPresent = 0x7f;
+static constexpr uint8_t kNotPeriodicAdvertisement = 0x00;
+
static constexpr bool kActiveScanning = true;
static constexpr bool kPassiveScanning = false;
@@ -55,7 +58,7 @@ using BtmRemoteDeviceName = tBTM_REMOTE_DEV_NAME;
extern void btm_process_cancel_complete(uint8_t status, uint8_t mode);
extern void btm_process_inq_complete(uint8_t status, uint8_t result_type);
extern void btm_ble_process_adv_addr(RawAddress& raw_address,
- tBLE_ADDR_TYPE* address_type);
+ uint8_t* address_type);
extern void btm_ble_process_adv_pkt_cont(
uint16_t event_type, uint8_t address_type, const RawAddress& raw_address,
uint8_t primary_phy, uint8_t secondary_phy, uint8_t advertising_sid,
@@ -78,112 +81,48 @@ extern void btm_api_process_extended_inquiry_result(
uint16_t clock_offset, int8_t rssi, const uint8_t* eir_data,
size_t eir_len);
-namespace bluetooth {
-
-namespace shim {
+void bluetooth::shim::Btm::StartUp(bluetooth::shim::Btm* btm) {
+ CHECK(btm != nullptr);
+ std::unique_lock<std::mutex> lock(btm->sync_mutex_);
+ CHECK(btm->observing_timer_ == nullptr);
+ CHECK(btm->scanning_timer_ == nullptr);
+ btm->observing_timer_ = new bluetooth::shim::Timer("observing_timer");
+ btm->scanning_timer_ = new bluetooth::shim::Timer("scanning_timer");
-bool Btm::ReadRemoteName::Start(RawAddress raw_address) {
- std::unique_lock<std::mutex> lock(mutex_);
- if (in_progress_) {
- return false;
- }
- raw_address_ = raw_address;
- in_progress_ = true;
- return true;
-}
-
-void Btm::ReadRemoteName::Stop() {
- std::unique_lock<std::mutex> lock(mutex_);
- raw_address_ = RawAddress::kEmpty;
- in_progress_ = false;
}
-bool Btm::ReadRemoteName::IsInProgress() const { return in_progress_; }
-std::string Btm::ReadRemoteName::AddressString() const {
- return raw_address_.ToString();
+void bluetooth::shim::Btm::ShutDown(bluetooth::shim::Btm* btm) {
+ CHECK(btm != nullptr);
+ std::unique_lock<std::mutex> lock(btm->sync_mutex_);
+ CHECK(btm->observing_timer_ != nullptr);
+ CHECK(btm->scanning_timer_ != nullptr);
+ delete btm->scanning_timer_;
+ delete btm->observing_timer_;
+ btm->scanning_timer_ = nullptr;
+ btm->observing_timer_ = nullptr;
}
-void Btm::ScanningCallbacks::OnScannerRegistered(
- const bluetooth::hci::Uuid app_uuid, bluetooth::hci::ScannerId scanner_id,
- ScanningStatus status){};
-
-void Btm::ScanningCallbacks::OnScanResult(
- uint16_t event_type, uint8_t address_type, bluetooth::hci::Address address,
- uint8_t primary_phy, uint8_t secondary_phy, uint8_t advertising_sid,
- int8_t tx_power, int8_t rssi, uint16_t periodic_advertising_interval,
- std::vector<uint8_t> advertising_data) {
- tBLE_ADDR_TYPE ble_address_type = static_cast<tBLE_ADDR_TYPE>(address_type);
- uint16_t extended_event_type = 0;
-
- RawAddress raw_address;
- RawAddress::FromString(address.ToString(), raw_address);
-
- if (ble_address_type != BLE_ADDR_ANONYMOUS) {
- btm_ble_process_adv_addr(raw_address, &ble_address_type);
- }
-
- btm_ble_process_adv_addr(raw_address, &ble_address_type);
- btm_ble_process_adv_pkt_cont(extended_event_type, ble_address_type,
- raw_address, primary_phy, secondary_phy,
- advertising_sid, tx_power, rssi,
- periodic_advertising_interval,
- advertising_data.size(), &advertising_data[0]);
-}
-
-void Btm::ScanningCallbacks::OnTrackAdvFoundLost(
- bluetooth::hci::AdvertisingFilterOnFoundOnLostInfo on_found_on_lost_info){};
-void Btm::ScanningCallbacks::OnBatchScanReports(int client_if, int status,
- int report_format,
- int num_records,
- std::vector<uint8_t> data){};
-
-void Btm::ScanningCallbacks::OnBatchScanThresholdCrossed(int client_if){};
-void Btm::ScanningCallbacks::OnTimeout(){};
-void Btm::ScanningCallbacks::OnFilterEnable(bluetooth::hci::Enable enable,
- uint8_t status){};
-void Btm::ScanningCallbacks::OnFilterParamSetup(
- uint8_t available_spaces, bluetooth::hci::ApcfAction action,
- uint8_t status){};
-void Btm::ScanningCallbacks::OnFilterConfigCallback(
- bluetooth::hci::ApcfFilterType filter_type, uint8_t available_spaces,
- bluetooth::hci::ApcfAction action, uint8_t status){};
-
-Btm::Btm(os::Handler* handler, neighbor::InquiryModule* inquiry)
- : scanning_timer_(handler), observing_timer_(handler) {
- ASSERT(handler != nullptr);
- ASSERT(inquiry != nullptr);
- bluetooth::neighbor::InquiryCallbacks inquiry_callbacks = {
- .result = std::bind(&Btm::OnInquiryResult, this, std::placeholders::_1),
- .result_with_rssi =
- std::bind(&Btm::OnInquiryResultWithRssi, this, std::placeholders::_1),
- .extended_result =
- std::bind(&Btm::OnExtendedInquiryResult, this, std::placeholders::_1),
- .complete =
- std::bind(&Btm::OnInquiryComplete, this, std::placeholders::_1)};
- inquiry->RegisterCallbacks(std::move(inquiry_callbacks));
-}
-
-void Btm::OnInquiryResult(bluetooth::hci::InquiryResultView view) {
+void bluetooth::shim::Btm::OnInquiryResult(
+ bluetooth::hci::InquiryResultView view) {
for (auto& response : view.GetInquiryResults()) {
btm_api_process_inquiry_result(
- ToRawAddress(response.bd_addr_),
+ RawAddress(response.bd_addr_.address),
static_cast<uint8_t>(response.page_scan_repetition_mode_),
- response.class_of_device_.data(), response.clock_offset_);
+ response.class_of_device_.cod, response.clock_offset_);
}
}
-void Btm::OnInquiryResultWithRssi(
+void bluetooth::shim::Btm::OnInquiryResultWithRssi(
bluetooth::hci::InquiryResultWithRssiView view) {
for (auto& response : view.GetInquiryResults()) {
btm_api_process_inquiry_result_with_rssi(
- ToRawAddress(response.address_),
+ RawAddress(response.address_.address),
static_cast<uint8_t>(response.page_scan_repetition_mode_),
- response.class_of_device_.data(), response.clock_offset_,
- response.rssi_);
+ response.class_of_device_.cod, response.clock_offset_, response.rssi_);
}
}
-void Btm::OnExtendedInquiryResult(
+void bluetooth::shim::Btm::OnExtendedInquiryResult(
bluetooth::hci::ExtendedInquiryResultView view) {
constexpr size_t kMaxExtendedInquiryResponse = 240;
uint8_t gap_data_buffer[kMaxExtendedInquiryResponse];
@@ -204,13 +143,13 @@ void Btm::OnExtendedInquiryResult(
}
btm_api_process_extended_inquiry_result(
- ToRawAddress(view.GetAddress()),
+ RawAddress(view.GetAddress().address),
static_cast<uint8_t>(view.GetPageScanRepetitionMode()),
- view.GetClassOfDevice().data(), view.GetClockOffset(), view.GetRssi(),
- data, data_len);
+ view.GetClassOfDevice().cod, view.GetClockOffset(), view.GetRssi(), data,
+ data_len);
}
-void Btm::OnInquiryComplete(bluetooth::hci::ErrorCode status) {
+void bluetooth::shim::Btm::OnInquiryComplete(bluetooth::hci::ErrorCode status) {
limited_inquiry_active_ = false;
general_inquiry_active_ = false;
legacy_inquiry_complete_callback_((static_cast<uint16_t>(status) == 0)
@@ -221,37 +160,71 @@ void Btm::OnInquiryComplete(bluetooth::hci::ErrorCode status) {
active_inquiry_mode_ = kInquiryModeOff;
}
-void Btm::SetStandardInquiryResultMode() {
- GetInquiry()->SetStandardInquiryResultMode();
+bool bluetooth::shim::Btm::SetInquiryFilter(uint8_t mode, uint8_t type,
+ tBTM_INQ_FILT_COND data) {
+ switch (mode) {
+ case kInquiryModeOff:
+ break;
+ case kLimitedInquiryMode:
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ break;
+ case kGeneralInquiryMode:
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ break;
+ default:
+ LOG_WARN(LOG_TAG, "%s Unknown inquiry mode:%d", __func__, mode);
+ return false;
+ }
+ return true;
+}
+
+void bluetooth::shim::Btm::SetFilterInquiryOnAddress() {
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+}
+
+void bluetooth::shim::Btm::SetFilterInquiryOnDevice() {
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+}
+
+void bluetooth::shim::Btm::ClearInquiryFilter() {
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
-void Btm::SetInquiryWithRssiResultMode() {
- GetInquiry()->SetInquiryWithRssiResultMode();
+void bluetooth::shim::Btm::SetStandardInquiryResultMode() {
+ bluetooth::shim::GetInquiry()->SetStandardInquiryResultMode();
}
-void Btm::SetExtendedInquiryResultMode() {
- GetInquiry()->SetExtendedInquiryResultMode();
+void bluetooth::shim::Btm::SetInquiryWithRssiResultMode() {
+ bluetooth::shim::GetInquiry()->SetInquiryWithRssiResultMode();
}
-void Btm::SetInterlacedInquiryScan() { GetInquiry()->SetInterlacedScan(); }
+void bluetooth::shim::Btm::SetExtendedInquiryResultMode() {
+ bluetooth::shim::GetInquiry()->SetExtendedInquiryResultMode();
+}
-void Btm::SetStandardInquiryScan() { GetInquiry()->SetStandardScan(); }
+void bluetooth::shim::Btm::SetInterlacedInquiryScan() {
+ bluetooth::shim::GetInquiry()->SetInterlacedScan();
+}
-bool Btm::IsInterlacedScanSupported() const {
+void bluetooth::shim::Btm::SetStandardInquiryScan() {
+ bluetooth::shim::GetInquiry()->SetStandardScan();
+}
+
+bool bluetooth::shim::Btm::IsInterlacedScanSupported() const {
return controller_get_interface()->supports_interlaced_inquiry_scan();
}
/**
* One shot inquiry
*/
-bool Btm::StartInquiry(
+bool bluetooth::shim::Btm::StartInquiry(
uint8_t mode, uint8_t duration, uint8_t max_responses,
LegacyInquiryCompleteCallback legacy_inquiry_complete_callback) {
switch (mode) {
case kInquiryModeOff:
- LOG_INFO("%s Stopping inquiry mode", __func__);
+ LOG_DEBUG(LOG_TAG, "%s Stopping inquiry mode", __func__);
if (limited_inquiry_active_ || general_inquiry_active_) {
- GetInquiry()->StopInquiry();
+ bluetooth::shim::GetInquiry()->StopInquiry();
limited_inquiry_active_ = false;
general_inquiry_active_ = false;
}
@@ -261,89 +234,102 @@ bool Btm::StartInquiry(
case kLimitedInquiryMode:
case kGeneralInquiryMode: {
if (mode == kLimitedInquiryMode) {
- LOG_INFO(
-
+ LOG_DEBUG(
+ LOG_TAG,
"%s Starting limited inquiry mode duration:%hhd max responses:%hhd",
__func__, duration, max_responses);
limited_inquiry_active_ = true;
- GetInquiry()->StartLimitedInquiry(duration, max_responses);
+ bluetooth::shim::GetInquiry()->StartLimitedInquiry(duration,
+ max_responses);
active_inquiry_mode_ = kLimitedInquiryMode;
} else {
- LOG_INFO(
-
+ LOG_DEBUG(
+ LOG_TAG,
"%s Starting general inquiry mode duration:%hhd max responses:%hhd",
__func__, duration, max_responses);
general_inquiry_active_ = true;
- GetInquiry()->StartGeneralInquiry(duration, max_responses);
+ bluetooth::shim::GetInquiry()->StartGeneralInquiry(duration,
+ max_responses);
legacy_inquiry_complete_callback_ = legacy_inquiry_complete_callback;
}
} break;
default:
- LOG_WARN("%s Unknown inquiry mode:%d", __func__, mode);
+ LOG_WARN(LOG_TAG, "%s Unknown inquiry mode:%d", __func__, mode);
return false;
}
return true;
}
-void Btm::CancelInquiry() {
- LOG_INFO("%s", __func__);
+void bluetooth::shim::Btm::CancelInquiry() {
+ LOG_DEBUG(LOG_TAG, "%s", __func__);
if (limited_inquiry_active_ || general_inquiry_active_) {
- GetInquiry()->StopInquiry();
+ bluetooth::shim::GetInquiry()->StopInquiry();
limited_inquiry_active_ = false;
general_inquiry_active_ = false;
}
}
-bool Btm::IsInquiryActive() const {
+bool bluetooth::shim::Btm::IsInquiryActive() const {
return IsGeneralInquiryActive() || IsLimitedInquiryActive();
}
-bool Btm::IsGeneralInquiryActive() const { return general_inquiry_active_; }
+bool bluetooth::shim::Btm::IsGeneralInquiryActive() const {
+ return general_inquiry_active_;
+}
-bool Btm::IsLimitedInquiryActive() const { return limited_inquiry_active_; }
+bool bluetooth::shim::Btm::IsLimitedInquiryActive() const {
+ return limited_inquiry_active_;
+}
/**
* Periodic
*/
-bool Btm::StartPeriodicInquiry(uint8_t mode, uint8_t duration,
- uint8_t max_responses, uint16_t max_delay,
- uint16_t min_delay,
- tBTM_INQ_RESULTS_CB* p_results_cb) {
+bool bluetooth::shim::Btm::StartPeriodicInquiry(
+ uint8_t mode, uint8_t duration, uint8_t max_responses, uint16_t max_delay,
+ uint16_t min_delay, tBTM_INQ_RESULTS_CB* p_results_cb) {
switch (mode) {
case kInquiryModeOff:
limited_periodic_inquiry_active_ = false;
general_periodic_inquiry_active_ = false;
- GetInquiry()->StopPeriodicInquiry();
+ bluetooth::shim::GetInquiry()->StopPeriodicInquiry();
break;
case kLimitedInquiryMode:
case kGeneralInquiryMode: {
if (mode == kLimitedInquiryMode) {
- LOG_INFO("%s Starting limited periodic inquiry mode", __func__);
+ LOG_DEBUG(LOG_TAG, "%s Starting limited periodic inquiry mode",
+ __func__);
limited_periodic_inquiry_active_ = true;
- GetInquiry()->StartLimitedPeriodicInquiry(duration, max_responses,
- max_delay, min_delay);
+ bluetooth::shim::GetInquiry()->StartLimitedPeriodicInquiry(
+ duration, max_responses, max_delay, min_delay);
} else {
- LOG_INFO("%s Starting general periodic inquiry mode", __func__);
+ LOG_DEBUG(LOG_TAG, "%s Starting general periodic inquiry mode",
+ __func__);
general_periodic_inquiry_active_ = true;
- GetInquiry()->StartGeneralPeriodicInquiry(duration, max_responses,
- max_delay, min_delay);
+ bluetooth::shim::GetInquiry()->StartGeneralPeriodicInquiry(
+ duration, max_responses, max_delay, min_delay);
}
} break;
default:
- LOG_WARN("%s Unknown inquiry mode:%d", __func__, mode);
+ LOG_WARN(LOG_TAG, "%s Unknown inquiry mode:%d", __func__, mode);
return false;
}
return true;
}
-bool Btm::IsGeneralPeriodicInquiryActive() const {
+void bluetooth::shim::Btm::CancelPeriodicInquiry() {
+ limited_periodic_inquiry_active_ = false;
+ general_periodic_inquiry_active_ = false;
+ bluetooth::shim::GetInquiry()->StopPeriodicInquiry();
+}
+
+bool bluetooth::shim::Btm::IsGeneralPeriodicInquiryActive() const {
return general_periodic_inquiry_active_;
}
-bool Btm::IsLimitedPeriodicInquiryActive() const {
+bool bluetooth::shim::Btm::IsLimitedPeriodicInquiryActive() const {
return limited_periodic_inquiry_active_;
}
@@ -351,79 +337,100 @@ bool Btm::IsLimitedPeriodicInquiryActive() const {
* Discoverability
*/
+void bluetooth::shim::Btm::RegisterInquiryCallbacks() {
+ bluetooth::neighbor::InquiryCallbacks inquiry_callbacks;
+ inquiry_callbacks.result =
+ std::bind(&Btm::OnInquiryResult, this, std::placeholders::_1);
+ inquiry_callbacks.result_with_rssi =
+ std::bind(&Btm::OnInquiryResultWithRssi, this, std::placeholders::_1);
+ inquiry_callbacks.extended_result =
+ std::bind(&Btm::OnExtendedInquiryResult, this, std::placeholders::_1);
+ inquiry_callbacks.complete =
+ std::bind(&Btm::OnInquiryComplete, this, std::placeholders::_1);
+ bluetooth::shim::GetInquiry()->RegisterCallbacks(inquiry_callbacks);
+}
+
bluetooth::neighbor::ScanParameters params_{
.interval = 0,
.window = 0,
};
-void Btm::SetClassicGeneralDiscoverability(uint16_t window, uint16_t interval) {
+void bluetooth::shim::Btm::SetClassicGeneralDiscoverability(uint16_t window,
+ uint16_t interval) {
params_.window = window;
params_.interval = interval;
- GetInquiry()->SetScanActivity(params_);
- GetDiscoverability()->StartGeneralDiscoverability();
+ bluetooth::shim::GetInquiry()->SetScanActivity(params_);
+ bluetooth::shim::GetDiscoverability()->StartGeneralDiscoverability();
}
-void Btm::SetClassicLimitedDiscoverability(uint16_t window, uint16_t interval) {
+void bluetooth::shim::Btm::SetClassicLimitedDiscoverability(uint16_t window,
+ uint16_t interval) {
params_.window = window;
params_.interval = interval;
- GetInquiry()->SetScanActivity(params_);
- GetDiscoverability()->StartLimitedDiscoverability();
+ bluetooth::shim::GetInquiry()->SetScanActivity(params_);
+ bluetooth::shim::GetDiscoverability()->StartLimitedDiscoverability();
}
-void Btm::SetClassicDiscoverabilityOff() {
- GetDiscoverability()->StopDiscoverability();
+void bluetooth::shim::Btm::SetClassicDiscoverabilityOff() {
+ bluetooth::shim::GetDiscoverability()->StopDiscoverability();
}
-DiscoverabilityState Btm::GetClassicDiscoverabilityState() const {
+DiscoverabilityState bluetooth::shim::Btm::GetClassicDiscoverabilityState()
+ const {
DiscoverabilityState state{.mode = BTM_NON_DISCOVERABLE,
.interval = params_.interval,
.window = params_.window};
- if (GetDiscoverability()->IsGeneralDiscoverabilityEnabled()) {
+ if (bluetooth::shim::GetDiscoverability()
+ ->IsGeneralDiscoverabilityEnabled()) {
state.mode = BTM_GENERAL_DISCOVERABLE;
- } else if (GetDiscoverability()->IsLimitedDiscoverabilityEnabled()) {
+ } else if (bluetooth::shim::GetDiscoverability()
+ ->IsLimitedDiscoverabilityEnabled()) {
state.mode = BTM_LIMITED_DISCOVERABLE;
}
return state;
}
-void Btm::SetLeGeneralDiscoverability() {
- LOG_WARN("UNIMPLEMENTED %s", __func__);
+void bluetooth::shim::Btm::SetLeGeneralDiscoverability() {
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
-void Btm::SetLeLimitedDiscoverability() {
- LOG_WARN("UNIMPLEMENTED %s", __func__);
+void bluetooth::shim::Btm::SetLeLimitedDiscoverability() {
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
-void Btm::SetLeDiscoverabilityOff() { LOG_WARN("UNIMPLEMENTED %s", __func__); }
+void bluetooth::shim::Btm::SetLeDiscoverabilityOff() {
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+}
-DiscoverabilityState Btm::GetLeDiscoverabilityState() const {
+DiscoverabilityState bluetooth::shim::Btm::GetLeDiscoverabilityState() const {
DiscoverabilityState state{
.mode = kDiscoverableModeOff,
.interval = 0,
.window = 0,
};
- LOG_WARN("UNIMPLEMENTED %s", __func__);
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
return state;
}
/**
* Connectability
*/
-void Btm::SetClassicConnectibleOn() {
- GetConnectability()->StartConnectability();
+void bluetooth::shim::Btm::SetClassicConnectibleOn() {
+ bluetooth::shim::GetConnectability()->StartConnectability();
}
-void Btm::SetClassicConnectibleOff() {
- GetConnectability()->StopConnectability();
+void bluetooth::shim::Btm::SetClassicConnectibleOff() {
+ bluetooth::shim::GetConnectability()->StopConnectability();
}
-ConnectabilityState Btm::GetClassicConnectabilityState() const {
+ConnectabilityState bluetooth::shim::Btm::GetClassicConnectabilityState()
+ const {
ConnectabilityState state{.interval = params_.interval,
.window = params_.window};
- if (GetConnectability()->IsConnectable()) {
+ if (bluetooth::shim::GetConnectability()->IsConnectable()) {
state.mode = BTM_CONNECTABLE;
} else {
state.mode = BTM_NON_CONNECTABLE;
@@ -431,59 +438,64 @@ ConnectabilityState Btm::GetClassicConnectabilityState() const {
return state;
}
-void Btm::SetInterlacedPageScan() { GetPage()->SetInterlacedScan(); }
+void bluetooth::shim::Btm::SetInterlacedPageScan() {
+ bluetooth::shim::GetPage()->SetInterlacedScan();
+}
-void Btm::SetStandardPageScan() { GetPage()->SetStandardScan(); }
+void bluetooth::shim::Btm::SetStandardPageScan() {
+ bluetooth::shim::GetPage()->SetStandardScan();
+}
-void Btm::SetLeConnectibleOn() { LOG_WARN("UNIMPLEMENTED %s", __func__); }
+void bluetooth::shim::Btm::SetLeConnectibleOn() {
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+}
-void Btm::SetLeConnectibleOff() { LOG_WARN("UNIMPLEMENTED %s", __func__); }
+void bluetooth::shim::Btm::SetLeConnectibleOff() {
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+}
-ConnectabilityState Btm::GetLeConnectabilityState() const {
+ConnectabilityState bluetooth::shim::Btm::GetLeConnectabilityState() const {
ConnectabilityState state{
.mode = kConnectibleModeOff,
.interval = 0,
.window = 0,
};
- LOG_WARN("UNIMPLEMENTED %s", __func__);
+ LOG_WARN(LOG_TAG, "UNIMPLEMENTED %s", __func__);
return state;
}
-bool Btm::UseLeLink(const RawAddress& raw_address) const {
- if (GetAclManager()->HACK_GetHandle(ToGdAddress(raw_address)) != 0xFFFF) {
- return false;
- }
- if (GetAclManager()->HACK_GetLeHandle(ToGdAddress(raw_address)) != 0xFFFF) {
- return true;
- }
- // TODO(hsz): use correct transport by using storage records. For now assume
- // LE for GATT and HID.
- return true;
+bool bluetooth::shim::Btm::IsLeAclConnected(
+ const RawAddress& raw_address) const {
+ // TODO(cmanton) Check current acl's for this address and indicate if there is
+ // an LE option. For now ignore and default to classic.
+ LOG_INFO(LOG_TAG, "%s Le acl connection check is temporarily unsupported",
+ __func__);
+ return false;
}
-BtmStatus Btm::ReadClassicRemoteDeviceName(const RawAddress& raw_address,
- tBTM_CMPL_CB* callback) {
+bluetooth::shim::BtmStatus bluetooth::shim::Btm::ReadClassicRemoteDeviceName(
+ const RawAddress& raw_address, tBTM_CMPL_CB* callback) {
if (!CheckClassicAclLink(raw_address)) {
- return BTM_UNKNOWN_ADDR;
+ return bluetooth::shim::BTM_UNKNOWN_ADDR;
}
if (!classic_read_remote_name_.Start(raw_address)) {
- LOG_INFO("%s Read remote name is currently busy address:%s", __func__,
- raw_address.ToString().c_str());
- return BTM_BUSY;
+ LOG_INFO(LOG_TAG, "%s Read remote name is currently busy address:%s",
+ __func__, raw_address.ToString().c_str());
+ return bluetooth::shim::BTM_BUSY;
}
- LOG_INFO("%s Start read name from address:%s", __func__,
- raw_address.ToString().c_str());
- GetName()->ReadRemoteNameRequest(
- ToGdAddress(raw_address), hci::PageScanRepetitionMode::R1,
+ LOG_DEBUG(LOG_TAG, "%s Start read name from address:%s", __func__,
+ raw_address.ToString().c_str());
+ bluetooth::shim::GetName()->ReadRemoteNameRequest(
+ hci::Address(raw_address.address), hci::PageScanRepetitionMode::R1,
0 /* clock_offset */, hci::ClockOffsetValid::INVALID,
base::Bind(
- [](tBTM_CMPL_CB* callback, ReadRemoteName* classic_read_remote_name,
+ [](tBTM_CMPL_CB* callback, ReadRemoteName* classic_read_remote_name_,
hci::ErrorCode status, hci::Address address,
std::array<uint8_t, kRemoteDeviceNameLength> remote_name) {
- RawAddress raw_address = ToRawAddress(address);
+ RawAddress raw_address(address.address);
BtmRemoteDeviceName name{
.status = (static_cast<uint8_t>(status) == 0)
@@ -494,31 +506,33 @@ BtmStatus Btm::ReadClassicRemoteDeviceName(const RawAddress& raw_address,
};
std::copy(remote_name.begin(), remote_name.end(),
name.remote_bd_name);
- LOG_INFO("%s Finish read name from address:%s name:%s", __func__,
- address.ToString().c_str(), name.remote_bd_name);
+ LOG_DEBUG(LOG_TAG, "%s Finish read name from address:%s name:%s",
+ __func__, address.ToString().c_str(),
+ name.remote_bd_name);
callback(&name);
- classic_read_remote_name->Stop();
+ classic_read_remote_name_->Stop();
},
callback, &classic_read_remote_name_),
- GetGdShimHandler());
- return BTM_CMD_STARTED;
+ bluetooth::shim::GetGdShimHandler());
+ return bluetooth::shim::BTM_CMD_STARTED;
}
-BtmStatus Btm::ReadLeRemoteDeviceName(const RawAddress& raw_address,
- tBTM_CMPL_CB* callback) {
+bluetooth::shim::BtmStatus bluetooth::shim::Btm::ReadLeRemoteDeviceName(
+ const RawAddress& raw_address, tBTM_CMPL_CB* callback) {
if (!CheckLeAclLink(raw_address)) {
- return BTM_UNKNOWN_ADDR;
+ return bluetooth::shim::BTM_UNKNOWN_ADDR;
}
if (!le_read_remote_name_.Start(raw_address)) {
- return BTM_BUSY;
+ return bluetooth::shim::BTM_BUSY;
}
- LOG_INFO("UNIMPLEMENTED %s need access to GATT module", __func__);
- return BTM_UNKNOWN_ADDR;
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s need access to GATT module", __func__);
+ return bluetooth::shim::BTM_UNKNOWN_ADDR;
}
-BtmStatus Btm::CancelAllReadRemoteDeviceName() {
+bluetooth::shim::BtmStatus
+bluetooth::shim::Btm::CancelAllReadRemoteDeviceName() {
if (classic_read_remote_name_.IsInProgress() ||
le_read_remote_name_.IsInProgress()) {
if (classic_read_remote_name_.IsInProgress()) {
@@ -526,160 +540,291 @@ BtmStatus Btm::CancelAllReadRemoteDeviceName() {
hci::Address::FromString(classic_read_remote_name_.AddressString(),
address);
- GetName()->CancelRemoteNameRequest(
+ bluetooth::shim::GetName()->CancelRemoteNameRequest(
address,
common::BindOnce(
- [](ReadRemoteName* classic_read_remote_name,
+ [](ReadRemoteName* classic_read_remote_name_,
hci::ErrorCode status,
- hci::Address address) { classic_read_remote_name->Stop(); },
+ hci::Address address) { classic_read_remote_name_->Stop(); },
&classic_read_remote_name_),
- GetGdShimHandler());
+ bluetooth::shim::GetGdShimHandler());
}
if (le_read_remote_name_.IsInProgress()) {
- LOG_INFO("UNIMPLEMENTED %s need access to GATT module", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s need access to GATT module",
+ __func__);
}
- return BTM_UNKNOWN_ADDR;
+ return bluetooth::shim::BTM_UNKNOWN_ADDR;
}
- LOG_WARN("%s Cancelling classic remote device name without one in progress",
+ LOG_WARN(LOG_TAG,
+ "%s Cancelling classic remote device name without one in progress",
__func__);
- return BTM_WRONG_MODE;
+ return bluetooth::shim::BTM_WRONG_MODE;
}
-void Btm::StartAdvertising() {
+void bluetooth::shim::Btm::StartAdvertising() {
if (advertiser_id_ == hci::LeAdvertisingManager::kInvalidId) {
- LOG_WARN("%s Already advertising; please stop prior to starting again",
+ LOG_WARN(LOG_TAG,
+ "%s Already advertising; please stop prior to starting again",
__func__);
return;
}
- hci::ExtendedAdvertisingConfig config = {};
- advertiser_id_ = GetAdvertising()->ExtendedCreateAdvertiser(
- 0x00, config,
- common::Bind([](hci::Address, hci::AddressType) { /*OnScan*/ }),
+ hci::AdvertisingConfig config;
+ advertiser_id_ = bluetooth::shim::GetAdvertising()->CreateAdvertiser(
+ config, common::Bind([](hci::Address, hci::AddressType) { /*OnScan*/ }),
common::Bind([](hci::ErrorCode, uint8_t, uint8_t) { /*OnTerminated*/ }),
- 0, 0, GetGdShimHandler());
+ bluetooth::shim::GetGdShimHandler());
if (advertiser_id_ == hci::LeAdvertisingManager::kInvalidId) {
- LOG_WARN("%s Unable to start advertising", __func__);
+ LOG_WARN(LOG_TAG, "%s Unable to start advertising", __func__);
return;
}
- LOG_INFO("%s Started advertising", __func__);
+ LOG_DEBUG(LOG_TAG, "%s Started advertising", __func__);
}
-void Btm::StopAdvertising() {
+void bluetooth::shim::Btm::StopAdvertising() {
if (advertiser_id_ == hci::LeAdvertisingManager::kInvalidId) {
- LOG_WARN("%s No active advertising", __func__);
+ LOG_WARN(LOG_TAG, "%s No active advertising", __func__);
return;
}
- GetAdvertising()->RemoveAdvertiser(advertiser_id_);
+ bluetooth::shim::GetAdvertising()->RemoveAdvertiser(advertiser_id_);
advertiser_id_ = hci::LeAdvertisingManager::kInvalidId;
- LOG_INFO("%s Stopped advertising", __func__);
+ LOG_DEBUG(LOG_TAG, "%s Stopped advertising", __func__);
}
-void Btm::StartConnectability() { StartAdvertising(); }
+void bluetooth::shim::Btm::StartConnectability() { StartAdvertising(); }
-void Btm::StopConnectability() { StopAdvertising(); }
+void bluetooth::shim::Btm::StopConnectability() { StopAdvertising(); }
-void Btm::StartActiveScanning() { StartScanning(kActiveScanning); }
+void bluetooth::shim::Btm::StartActiveScanning() {
+ StartScanning(kActiveScanning);
+}
-void Btm::StopActiveScanning() { GetScanning()->Scan(false); }
+void bluetooth::shim::Btm::StopActiveScanning() {
+ bluetooth::shim::GetScanning()->StopScan(base::Bind([]() {}));
+}
-void Btm::SetScanningTimer(uint64_t duration_ms,
- common::OnceCallback<void()> callback) {
- scanning_timer_.Schedule(std::move(callback),
- std::chrono::milliseconds(duration_ms));
+void bluetooth::shim::Btm::SetScanningTimer(uint64_t duration_ms,
+ std::function<void()> func) {
+ scanning_timer_->Set(duration_ms, func);
}
-void Btm::CancelScanningTimer() { scanning_timer_.Cancel(); }
+void bluetooth::shim::Btm::CancelScanningTimer() { scanning_timer_->Cancel(); }
-void Btm::StartObserving() { StartScanning(kPassiveScanning); }
+void bluetooth::shim::Btm::StartObserving() { StartScanning(kPassiveScanning); }
-void Btm::StopObserving() { StopActiveScanning(); }
+void bluetooth::shim::Btm::StopObserving() { StopActiveScanning(); }
-void Btm::SetObservingTimer(uint64_t duration_ms,
- common::OnceCallback<void()> callback) {
- observing_timer_.Schedule(std::move(callback),
- std::chrono::milliseconds(duration_ms));
+void bluetooth::shim::Btm::SetObservingTimer(uint64_t duration_ms,
+ std::function<void()> func) {
+ observing_timer_->Set(duration_ms, func);
}
-void Btm::CancelObservingTimer() { observing_timer_.Cancel(); }
-
-void Btm::StartScanning(bool use_active_scanning) {
- GetScanning()->RegisterScanningCallback(&scanning_callbacks_);
- GetScanning()->Scan(true);
+void bluetooth::shim::Btm::CancelObservingTimer() {
+ observing_timer_->Cancel();
}
-size_t Btm::GetNumberOfAdvertisingInstances() const {
- return GetAdvertising()->GetNumberOfAdvertisingInstances();
-}
+namespace bluetooth {
+namespace hci {
+
+constexpr int kAdvertisingReportBufferSize = 1024;
+
+struct ExtendedEventTypeOptions {
+ bool connectable{false};
+ bool scannable{false};
+ bool directed{false};
+ bool scan_response{false};
+ bool legacy{false};
+ bool continuing{false};
+ bool truncated{false};
+};
-tBTM_STATUS Btm::CreateBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type) {
- if (transport == BT_TRANSPORT_UNKNOWN) {
- if (device_type & BT_DEVICE_TYPE_BLE) {
- transport = BT_TRANSPORT_LE;
- } else if (device_type & BT_DEVICE_TYPE_BREDR) {
- transport = BT_TRANSPORT_BR_EDR;
+constexpr uint16_t kBleEventConnectableBit =
+ (0x0001 << 0); // BLE_EVT_CONNECTABLE_BIT
+constexpr uint16_t kBleEventScannableBit =
+ (0x0001 << 1); // BLE_EVT_SCANNABLE_BIT
+constexpr uint16_t kBleEventDirectedBit =
+ (0x0001 << 2); // BLE_EVT_DIRECTED_BIT
+constexpr uint16_t kBleEventScanResponseBit =
+ (0x0001 << 3); // BLE_EVT_SCAN_RESPONSE_BIT
+constexpr uint16_t kBleEventLegacyBit = (0x0001 << 4); // BLE_EVT_LEGACY_BIT
+constexpr uint16_t kBleEventIncompleteContinuing = (0x0001 << 5);
+constexpr uint16_t kBleEventIncompleteTruncated = (0x0001 << 6);
+
+static void TransformToExtendedEventType(uint16_t* extended_event_type,
+ ExtendedEventTypeOptions o) {
+ ASSERT(extended_event_type != nullptr);
+ *extended_event_type = (o.connectable ? kBleEventConnectableBit : 0) |
+ (o.scannable ? kBleEventScannableBit : 0) |
+ (o.directed ? kBleEventDirectedBit : 0) |
+ (o.scan_response ? kBleEventScanResponseBit : 0) |
+ (o.legacy ? kBleEventLegacyBit : 0) |
+ (o.continuing ? kBleEventIncompleteContinuing : 0) |
+ (o.truncated ? kBleEventIncompleteTruncated : 0);
+}
+
+class BtmScanningCallbacks : public bluetooth::hci::LeScanningManagerCallbacks {
+ public:
+ virtual void on_advertisements(
+ std::vector<std::shared_ptr<LeReport>> reports) {
+ for (auto le_report : reports) {
+ uint8_t address_type = static_cast<uint8_t>(le_report->address_type_);
+ uint16_t extended_event_type = 0;
+ uint8_t* report_data = nullptr;
+ size_t report_len = 0;
+
+ uint8_t advertising_data_buffer[kAdvertisingReportBufferSize];
+ // Copy gap data, if any, into temporary buffer as payload for legacy
+ // stack.
+ if (!le_report->gap_data_.empty()) {
+ bzero(advertising_data_buffer, kAdvertisingReportBufferSize);
+ uint8_t* p = advertising_data_buffer;
+ for (auto gap_data : le_report->gap_data_) {
+ *p++ = gap_data.data_.size() + sizeof(gap_data.data_type_);
+ *p++ = static_cast<uint8_t>(gap_data.data_type_);
+ p = (uint8_t*)memcpy(p, &gap_data.data_[0], gap_data.data_.size()) +
+ gap_data.data_.size();
+ }
+ report_data = advertising_data_buffer;
+ report_len = p - report_data;
+ }
+
+ switch (le_report->GetReportType()) {
+ case hci::LeReport::ReportType::ADVERTISING_EVENT: {
+ switch (le_report->advertising_event_type_) {
+ case hci::AdvertisingEventType::ADV_IND:
+ TransformToExtendedEventType(
+ &extended_event_type,
+ {.connectable = true, .scannable = true, .legacy = true});
+ break;
+ case hci::AdvertisingEventType::ADV_DIRECT_IND:
+ TransformToExtendedEventType(
+ &extended_event_type,
+ {.connectable = true, .directed = true, .legacy = true});
+ break;
+ case hci::AdvertisingEventType::ADV_SCAN_IND:
+ TransformToExtendedEventType(&extended_event_type,
+ {.scannable = true, .legacy = true});
+ break;
+ case hci::AdvertisingEventType::ADV_NONCONN_IND:
+ TransformToExtendedEventType(&extended_event_type,
+ {.legacy = true});
+ break;
+ case hci::AdvertisingEventType::
+ ADV_DIRECT_IND_LOW: // SCAN_RESPONSE
+ TransformToExtendedEventType(&extended_event_type,
+ {.connectable = true,
+ .scannable = true,
+ .scan_response = true,
+ .legacy = true});
+ break;
+ default:
+ LOG_WARN(
+ LOG_TAG, "%s Unsupported event type:%s", __func__,
+ AdvertisingEventTypeText(le_report->advertising_event_type_)
+ .c_str());
+ return;
+ }
+
+ RawAddress raw_address(le_report->address_.address);
+
+ btm_ble_process_adv_addr(raw_address, &address_type);
+ btm_ble_process_adv_pkt_cont(
+ extended_event_type, address_type, raw_address,
+ kPhyConnectionLe1M, kPhyConnectionNone, kAdvDataInfoNotPresent,
+ kTxPowerInformationNotPresent, le_report->rssi_,
+ kNotPeriodicAdvertisement, report_len, report_data);
+ } break;
+
+ case hci::LeReport::ReportType::DIRECTED_ADVERTISING_EVENT:
+ LOG_WARN(LOG_TAG,
+ "%s Directed advertising is unsupported from device:%s",
+ __func__, le_report->address_.ToString().c_str());
+ break;
+
+ case hci::LeReport::ReportType::EXTENDED_ADVERTISING_EVENT: {
+ std::shared_ptr<hci::ExtendedLeReport> extended_le_report =
+ std::static_pointer_cast<hci::ExtendedLeReport>(le_report);
+ TransformToExtendedEventType(
+ &extended_event_type,
+ {.connectable = extended_le_report->connectable_,
+ .scannable = extended_le_report->scannable_,
+ .directed = extended_le_report->directed_,
+ .scan_response = extended_le_report->scan_response_,
+ .legacy = false,
+ .continuing = !extended_le_report->complete_,
+ .truncated = extended_le_report->truncated_});
+ RawAddress raw_address(le_report->address_.address);
+ if (address_type != BLE_ADDR_ANONYMOUS) {
+ btm_ble_process_adv_addr(raw_address, &address_type);
+ }
+ btm_ble_process_adv_pkt_cont(
+ extended_event_type, address_type, raw_address,
+ kPhyConnectionLe1M, kPhyConnectionNone, kAdvDataInfoNotPresent,
+ kTxPowerInformationNotPresent, le_report->rssi_,
+ kNotPeriodicAdvertisement, report_len, report_data);
+
+ } break;
+ }
}
- LOG_INFO("%s guessing transport as %02x ", __func__, transport);
}
- auto security_manager = GetSecurityModule()->GetSecurityManager();
+ virtual void on_timeout() {
+ LOG_WARN(LOG_TAG, "%s Scanning timeout", __func__);
+ }
+ os::Handler* Handler() { return bluetooth::shim::GetGdShimHandler(); }
+};
+} // namespace hci
+} // namespace bluetooth
+
+bluetooth::hci::BtmScanningCallbacks btm_scanning_callbacks;
+
+void bluetooth::shim::Btm::StartScanning(bool use_active_scanning) {
+ bluetooth::shim::GetScanning()->StartScan(&btm_scanning_callbacks);
+}
+
+size_t bluetooth::shim::Btm::GetNumberOfAdvertisingInstances() const {
+ return bluetooth::shim::GetAdvertising()->GetNumberOfAdvertisingInstances();
+}
+
+tBTM_STATUS bluetooth::shim::Btm::CreateBond(const RawAddress& bd_addr,
+ tBLE_ADDR_TYPE addr_type,
+ tBT_TRANSPORT transport,
+ uint8_t pin_len, uint8_t* p_pin,
+ uint32_t trusted_mask[]) {
+ auto security_manager =
+ bluetooth::shim::GetSecurityModule()->GetSecurityManager();
switch (transport) {
case BT_TRANSPORT_BR_EDR:
- security_manager->CreateBond(ToAddressWithType(bd_addr, BLE_ADDR_PUBLIC));
+ security_manager->CreateBond(
+ ToAddressWithType(bd_addr.address, BLE_ADDR_PUBLIC));
break;
case BT_TRANSPORT_LE:
security_manager->CreateBondLe(ToAddressWithType(bd_addr, addr_type));
break;
default:
- return BTM_ILLEGAL_VALUE;
+ return bluetooth::shim::BTM_ILLEGAL_VALUE;
}
- return BTM_CMD_STARTED;
+ return bluetooth::shim::BTM_SUCCESS;
}
-bool Btm::CancelBond(const RawAddress& bd_addr) {
- auto security_manager = GetSecurityModule()->GetSecurityManager();
+bool bluetooth::shim::Btm::CancelBond(const RawAddress& bd_addr) {
+ auto security_manager =
+ bluetooth::shim::GetSecurityModule()->GetSecurityManager();
security_manager->CancelBond(ToAddressWithType(bd_addr, BLE_ADDR_PUBLIC));
return true;
}
-bool Btm::RemoveBond(const RawAddress& bd_addr) {
+bool bluetooth::shim::Btm::RemoveBond(const RawAddress& bd_addr) {
// TODO(cmanton) Check if acl is connected
- auto security_manager = GetSecurityModule()->GetSecurityManager();
+ auto security_manager =
+ bluetooth::shim::GetSecurityModule()->GetSecurityManager();
security_manager->RemoveBond(ToAddressWithType(bd_addr, BLE_ADDR_PUBLIC));
return true;
}
-uint16_t Btm::GetAclHandle(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- auto acl_manager = GetAclManager();
- if (transport == BT_TRANSPORT_BR_EDR) {
- return acl_manager->HACK_GetHandle(ToGdAddress(remote_bda));
- } else {
- return acl_manager->HACK_GetLeHandle(ToGdAddress(remote_bda));
- }
-}
-
-hci::AddressWithType Btm::GetAddressAndType(const RawAddress& bd_addr) {
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
- if (p_dev_rec != NULL && p_dev_rec->device_type & BT_DEVICE_TYPE_BLE) {
- if (!p_dev_rec->ble.identity_address_with_type.bda.IsEmpty()) {
- return ToAddressWithType(p_dev_rec->ble.identity_address_with_type.bda,
- p_dev_rec->ble.identity_address_with_type.type);
- } else {
- return ToAddressWithType(p_dev_rec->ble.pseudo_addr,
- p_dev_rec->ble.ble_addr_type);
- }
- }
- LOG(ERROR) << "Unknown bd_addr. Use public address";
- return ToAddressWithType(bd_addr, BLE_ADDR_PUBLIC);
-}
-
-void Btm::Register_HACK_SetScoDisconnectCallback(
- HACK_ScoDisconnectCallback callback) {
- GetAclManager()->HACK_SetScoDisconnectCallback(callback);
+void bluetooth::shim::Btm::SetSimplePairingCallback(
+ tBTM_SP_CALLBACK* callback) {
+ auto security_manager =
+ bluetooth::shim::GetSecurityModule()->GetSecurityManager();
+ simple_pairing_callback_ = callback;
}
-
-} // namespace shim
-
-} // namespace bluetooth
diff --git a/main/shim/btm.h b/main/shim/btm.h
index d303896b9..6058e29dc 100644
--- a/main/shim/btm.h
+++ b/main/shim/btm.h
@@ -23,17 +23,14 @@
#include <unordered_map>
#include <vector>
-#include "hci/hci_packets.h"
-
-#include "stack/btm/neighbor_inquiry.h"
+#include "main/shim/timer.h"
+#include "osi/include/alarm.h"
+#include "osi/include/future.h"
+#include "osi/include/log.h"
#include "stack/include/btm_api_types.h"
-#include "types/raw_address.h"
-#include "gd/common/callback.h"
-#include "gd/hci/le_advertising_manager.h"
-#include "gd/hci/le_scanning_manager.h"
-#include "gd/neighbor/inquiry.h"
-#include "gd/os/alarm.h"
+#include "hci/hci_packets.h"
+#include "hci/le_advertising_manager.h"
//
// NOTE: limited and general constants for inquiry and discoverable are swapped
@@ -62,13 +59,18 @@ static constexpr int kStandardInquiryResult = 0;
static constexpr int kInquiryResultWithRssi = 1;
static constexpr int kExtendedInquiryResult = 2;
+/* Inquiry filter types */
+static constexpr int kClearInquiryFilter = 0;
+static constexpr int kFilterOnDeviceClass = 1;
+static constexpr int kFilterOnAddress = 2;
+
static constexpr uint8_t kPhyConnectionNone = 0x00;
static constexpr uint8_t kPhyConnectionLe1M = 0x01;
static constexpr uint8_t kPhyConnectionLe2M = 0x02;
static constexpr uint8_t kPhyConnectionLeCoded = 0x03;
using LegacyInquiryCompleteCallback =
- std::function<void(tBTM_STATUS status, uint8_t inquiry_mode)>;
+ std::function<void(uint16_t status, uint8_t inquiry_mode)>;
using DiscoverabilityState = struct {
int mode;
@@ -77,17 +79,68 @@ using DiscoverabilityState = struct {
};
using ConnectabilityState = DiscoverabilityState;
-using HACK_ScoDisconnectCallback = std::function<void(uint16_t, uint8_t)>;
-
-using BtmStatus = tBTM_STATUS;
-
namespace bluetooth {
namespace shim {
+using BtmStatus = enum : uint16_t {
+ BTM_SUCCESS = 0, /* Command succeeded */
+ BTM_CMD_STARTED = 1, /* Command started OK. */
+ BTM_BUSY = 2, /* Device busy with another command */
+ BTM_NO_RESOURCES = 3, /* No resources to issue command */
+ BTM_MODE_UNSUPPORTED = 4, /* Request for 1 or more unsupported modes */
+ BTM_ILLEGAL_VALUE = 5, /* Illegal parameter value */
+ BTM_WRONG_MODE = 6, /* Device in wrong mode for request */
+ BTM_UNKNOWN_ADDR = 7, /* Unknown remote BD address */
+ BTM_DEVICE_TIMEOUT = 8, /* Device timeout */
+ BTM_BAD_VALUE_RET = 9, /* A bad value was received from HCI */
+ BTM_ERR_PROCESSING = 10, /* Generic error */
+ BTM_NOT_AUTHORIZED = 11, /* Authorization failed */
+ BTM_DEV_RESET = 12, /* Device has been reset */
+ BTM_CMD_STORED = 13, /* request is stored in control block */
+ BTM_ILLEGAL_ACTION = 14, /* state machine gets illegal command */
+ BTM_DELAY_CHECK = 15, /* delay the check on encryption */
+ BTM_SCO_BAD_LENGTH = 16, /* Bad SCO over HCI data length */
+ BTM_SUCCESS_NO_SECURITY = 17, /* security passed, no security set */
+ BTM_FAILED_ON_SECURITY = 18, /* security failed */
+ BTM_REPEATED_ATTEMPTS = 19, /* repeated attempts for LE security requests */
+ BTM_MODE4_LEVEL4_NOT_SUPPORTED = 20, /* Secure Connections Only Mode can't be
+ supported */
+ BTM_DEV_BLACKLISTED = 21, /* The device is Blacklisted */
+};
+
+class ReadRemoteName {
+ public:
+ bool Start(RawAddress raw_address) {
+ std::unique_lock<std::mutex> lock(mutex_);
+ if (in_progress_) {
+ return false;
+ }
+ raw_address_ = raw_address;
+ in_progress_ = true;
+ return true;
+ }
+
+ void Stop() {
+ std::unique_lock<std::mutex> lock(mutex_);
+ raw_address_ = RawAddress::kEmpty;
+ in_progress_ = false;
+ }
+
+ bool IsInProgress() const { return in_progress_; }
+
+ std::string AddressString() const { return raw_address_.ToString(); }
+
+ ReadRemoteName() : in_progress_{false}, raw_address_(RawAddress::kEmpty) {}
+
+ private:
+ bool in_progress_;
+ RawAddress raw_address_;
+ std::mutex mutex_;
+};
+
class Btm {
public:
- // |handler| is used to run timer tasks and scan callbacks
- Btm(os::Handler* handler, neighbor::InquiryModule* inquiry);
+ Btm() = default;
~Btm() = default;
// Inquiry result callbacks
@@ -96,6 +149,12 @@ class Btm {
void OnExtendedInquiryResult(bluetooth::hci::ExtendedInquiryResultView view);
void OnInquiryComplete(bluetooth::hci::ErrorCode status);
+ // Inquiry API
+ bool SetInquiryFilter(uint8_t mode, uint8_t type, tBTM_INQ_FILT_COND data);
+ void SetFilterInquiryOnAddress();
+ void SetFilterInquiryOnDevice();
+ void ClearInquiryFilter();
+
void SetStandardInquiryResultMode();
void SetInquiryWithRssiResultMode();
void SetExtendedInquiryResultMode();
@@ -124,6 +183,7 @@ class Btm {
bool limited_inquiry_active_{false};
bool general_periodic_inquiry_active_{false};
bool limited_periodic_inquiry_active_{false};
+ void RegisterInquiryCallbacks();
void SetClassicGeneralDiscoverability(uint16_t window, uint16_t interval);
void SetClassicLimitedDiscoverability(uint16_t window, uint16_t interval);
void SetClassicDiscoverabilityOff();
@@ -144,7 +204,7 @@ class Btm {
void SetLeConnectibleOff();
ConnectabilityState GetLeConnectabilityState() const;
- bool UseLeLink(const RawAddress& raw_address) const;
+ bool IsLeAclConnected(const RawAddress& raw_address) const;
// Remote device name API
BtmStatus ReadClassicRemoteDeviceName(const RawAddress& raw_address,
@@ -169,73 +229,37 @@ class Btm {
size_t GetNumberOfAdvertisingInstances() const;
- void SetObservingTimer(uint64_t duration_ms,
- common::OnceCallback<void()> callback);
+ void SetObservingTimer(uint64_t duration_ms, std::function<void()>);
void CancelObservingTimer();
- void SetScanningTimer(uint64_t duration_ms,
- common::OnceCallback<void()> callback);
+ void SetScanningTimer(uint64_t duration_ms, std::function<void()>);
void CancelScanningTimer();
+ // Lifecycle
+ static void StartUp(Btm* btm);
+ static void ShutDown(Btm* btm);
+
tBTM_STATUS CreateBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type);
+ tBT_TRANSPORT transport, uint8_t pin_len,
+ uint8_t* p_pin, uint32_t trusted_mask[]);
bool CancelBond(const RawAddress& bd_addr);
bool RemoveBond(const RawAddress& bd_addr);
- uint16_t GetAclHandle(const RawAddress& remote_bda, tBT_TRANSPORT transport);
+ void SetSimplePairingCallback(tBTM_SP_CALLBACK* callback);
- void Register_HACK_SetScoDisconnectCallback(
- HACK_ScoDisconnectCallback callback);
+ private:
+ ReadRemoteName le_read_remote_name_;
+ ReadRemoteName classic_read_remote_name_;
- static hci::AddressWithType GetAddressAndType(const RawAddress& bd_addr);
+ Timer* observing_timer_{nullptr};
+ Timer* scanning_timer_{nullptr};
- private:
- os::Alarm scanning_timer_;
- os::Alarm observing_timer_;
+ std::mutex sync_mutex_;
LegacyInquiryCompleteCallback legacy_inquiry_complete_callback_{};
- uint8_t active_inquiry_mode_ = 0;
- class ReadRemoteName {
- public:
- ReadRemoteName() = default;
- bool Start(RawAddress raw_address);
- void Stop();
- bool IsInProgress() const;
- std::string AddressString() const;
-
- private:
- std::mutex mutex_;
- bool in_progress_ = false;
- RawAddress raw_address_ = RawAddress::kEmpty;
- };
- ReadRemoteName le_read_remote_name_;
- ReadRemoteName classic_read_remote_name_;
+ tBTM_SP_CALLBACK* simple_pairing_callback_{nullptr};
- class ScanningCallbacks : public hci::ScanningCallback {
- void OnScannerRegistered(const bluetooth::hci::Uuid app_uuid,
- bluetooth::hci::ScannerId scanner_id,
- ScanningStatus status);
- void OnScanResult(uint16_t event_type, uint8_t address_type,
- bluetooth::hci::Address address, uint8_t primary_phy,
- uint8_t secondary_phy, uint8_t advertising_sid,
- int8_t tx_power, int8_t rssi,
- uint16_t periodic_advertising_interval,
- std::vector<uint8_t> advertising_data);
- void OnTrackAdvFoundLost(bluetooth::hci::AdvertisingFilterOnFoundOnLostInfo
- on_found_on_lost_info);
- void OnBatchScanReports(int client_if, int status, int report_format,
- int num_records, std::vector<uint8_t> data);
- void OnBatchScanThresholdCrossed(int client_if);
- void OnTimeout();
- void OnFilterEnable(bluetooth::hci::Enable enable, uint8_t status);
- void OnFilterParamSetup(uint8_t available_spaces,
- bluetooth::hci::ApcfAction action, uint8_t status);
- void OnFilterConfigCallback(bluetooth::hci::ApcfFilterType filter_type,
- uint8_t available_spaces,
- bluetooth::hci::ApcfAction action,
- uint8_t status);
- };
- ScanningCallbacks scanning_callbacks_;
+ uint8_t active_inquiry_mode_ = 0;
// TODO(cmanton) abort if there is no classic acl link up
bool CheckClassicAclLink(const RawAddress& raw_address) { return true; }
diff --git a/main/shim/btm_api.cc b/main/shim/btm_api.cc
index f7576648c..cc4408ff3 100644
--- a/main/shim/btm_api.cc
+++ b/main/shim/btm_api.cc
@@ -20,28 +20,19 @@
#include <mutex>
-#include "common/metric_id_allocator.h"
#include "common/time_util.h"
#include "device/include/controller.h"
-#include "gd/common/callback.h"
-#include "gd/neighbor/name.h"
-#include "gd/os/log.h"
-#include "gd/security/security_module.h"
-#include "gd/security/ui.h"
#include "main/shim/btm.h"
#include "main/shim/btm_api.h"
#include "main/shim/controller.h"
-#include "main/shim/helpers.h"
-#include "main/shim/metric_id_api.h"
#include "main/shim/shim.h"
-#include "main/shim/stack.h"
+#include "main/shim/timer.h"
+#include "osi/include/log.h"
#include "stack/btm/btm_int_types.h"
+#include "types/class_of_device.h"
#include "types/raw_address.h"
-using bluetooth::common::MetricIdAllocator;
-
-#define BTIF_DM_DEFAULT_INQ_MAX_RESULTS 0
-#define BTIF_DM_DEFAULT_INQ_MAX_DURATION 10
+bluetooth::shim::Btm shim_btm;
/**
* Legacy bluetooth module global control block state
@@ -61,13 +52,45 @@ extern tINQ_DB_ENT* btm_inq_db_new(const RawAddress& p_bda);
/**
* Legacy bluetooth btm stack entry points
*/
-extern void btm_acl_update_inquiry_status(uint8_t status);
+extern void btm_acl_update_busy_level(tBTM_BLI_EVENT event);
extern void btm_clear_all_pending_le_entry(void);
extern void btm_clr_inq_result_flt(void);
extern void btm_set_eir_uuid(uint8_t* p_eir, tBTM_INQ_RESULTS* p_results);
extern void btm_sort_inq_result(void);
extern void btm_process_inq_complete(uint8_t status, uint8_t result_type);
+static future_t* btm_module_start_up(void) {
+ bluetooth::shim::Btm::StartUp(&shim_btm);
+ return kReturnImmediate;
+}
+
+static future_t* btm_module_shut_down(void) {
+ bluetooth::shim::Btm::ShutDown(&shim_btm);
+ return kReturnImmediate;
+}
+
+EXPORT_SYMBOL extern const module_t gd_shim_btm_module = {
+ .name = GD_SHIM_BTM_MODULE,
+ .init = kUnusedModuleApi,
+ .start_up = btm_module_start_up,
+ .shut_down = btm_module_shut_down,
+ .clean_up = kUnusedModuleApi,
+ .dependencies = {kUnusedModuleDependencies}};
+
+static bool max_responses_reached() {
+ return (btm_cb.btm_inq_vars.inqparms.max_resps &&
+ btm_cb.btm_inq_vars.inq_cmpl_info.num_resp >=
+ btm_cb.btm_inq_vars.inqparms.max_resps);
+}
+
+static bool is_periodic_inquiry_active() {
+ return btm_cb.btm_inq_vars.inq_active & BTM_PERIODIC_INQUIRY_ACTIVE;
+}
+
+static bool has_le_device(tBT_DEVICE_TYPE device_type) {
+ return device_type & BT_DEVICE_TYPE_BLE;
+}
+
static bool is_classic_device(tBT_DEVICE_TYPE device_type) {
return device_type == BT_DEVICE_TYPE_BREDR;
}
@@ -76,11 +99,36 @@ static bool has_classic_device(tBT_DEVICE_TYPE device_type) {
return device_type & BT_DEVICE_TYPE_BREDR;
}
+static bool is_dual_mode_device(tBT_DEVICE_TYPE device_type) {
+ return device_type == BT_DEVICE_TYPE_DUMO;
+}
+
+static bool is_observing_or_active_scanning() {
+ return btm_cb.btm_inq_vars.inqparms.mode & BTM_BLE_INQUIRY_MASK;
+}
+
+static void check_exceeded_responses(tBT_DEVICE_TYPE device_type,
+ bool scan_rsp) {
+ if (!is_periodic_inquiry_active() && max_responses_reached() &&
+ ((is_observing_or_active_scanning() && is_dual_mode_device(device_type) &&
+ scan_rsp) ||
+ (is_observing_or_active_scanning()))) {
+ LOG_INFO(LOG_TAG,
+ "UNIMPLEMENTED %s Device max responses found...cancelling inquiry",
+ __func__);
+ }
+}
+
void btm_api_process_inquiry_result(const RawAddress& raw_address,
uint8_t page_scan_rep_mode,
DEV_CLASS device_class,
uint16_t clock_offset) {
tINQ_DB_ENT* p_i = btm_inq_db_find(raw_address);
+ if (max_responses_reached()) {
+ if (p_i == nullptr || !has_le_device(p_i->inq_info.results.device_type)) {
+ return;
+ }
+ }
if (p_i == nullptr) {
p_i = btm_inq_db_new(raw_address);
@@ -112,6 +160,7 @@ void btm_api_process_inquiry_result(const RawAddress& raw_address,
p_i->inq_info.results.device_type |= BT_DEVICE_TYPE_BREDR;
}
+ check_exceeded_responses(p_i->inq_info.results.device_type, p_i->scan_rsp);
if (btm_cb.btm_inq_vars.p_inq_results_cb == nullptr) {
return;
}
@@ -125,10 +174,15 @@ void btm_api_process_inquiry_result_with_rssi(RawAddress raw_address,
uint16_t clock_offset,
int8_t rssi) {
tINQ_DB_ENT* p_i = btm_inq_db_find(raw_address);
+ if (max_responses_reached()) {
+ if (p_i == nullptr || !has_le_device(p_i->inq_info.results.device_type)) {
+ return;
+ }
+ }
bool update = false;
if (btm_inq_find_bdaddr(raw_address)) {
- if (p_i != nullptr &&
+ if (btm_cb.btm_inq_vars.inqparms.report_dup && p_i != nullptr &&
(rssi > p_i->inq_info.results.rssi || p_i->inq_info.results.rssi == 0 ||
has_classic_device(p_i->inq_info.results.device_type))) {
update = true;
@@ -169,6 +223,7 @@ void btm_api_process_inquiry_result_with_rssi(RawAddress raw_address,
}
}
+ check_exceeded_responses(p_i->inq_info.results.device_type, p_i->scan_rsp);
if (btm_cb.btm_inq_vars.p_inq_results_cb == nullptr) {
return;
}
@@ -184,6 +239,11 @@ void btm_api_process_extended_inquiry_result(RawAddress raw_address,
const uint8_t* eir_data,
size_t eir_len) {
tINQ_DB_ENT* p_i = btm_inq_db_find(raw_address);
+ if (max_responses_reached()) {
+ if (p_i == nullptr || !has_le_device(p_i->inq_info.results.device_type)) {
+ return;
+ }
+ }
bool update = false;
if (btm_inq_find_bdaddr(raw_address) && p_i != nullptr) {
@@ -223,6 +283,7 @@ void btm_api_process_extended_inquiry_result(RawAddress raw_address,
}
}
+ check_exceeded_responses(p_i->inq_info.results.device_type, p_i->scan_rsp);
if (btm_cb.btm_inq_vars.p_inq_results_cb == nullptr) {
return;
}
@@ -237,323 +298,45 @@ void btm_api_process_extended_inquiry_result(RawAddress raw_address,
}
}
-namespace {
-std::unordered_map<bluetooth::hci::AddressWithType, bt_bdname_t>
- address_name_map_;
-
-std::unordered_map<bluetooth::hci::IoCapability, int> gd_legacy_io_caps_map_ = {
- {bluetooth::hci::IoCapability::DISPLAY_ONLY, BTM_IO_CAP_OUT},
- {bluetooth::hci::IoCapability::DISPLAY_YES_NO, BTM_IO_CAP_IO},
- {bluetooth::hci::IoCapability::KEYBOARD_ONLY, BTM_IO_CAP_IN},
- {bluetooth::hci::IoCapability::NO_INPUT_NO_OUTPUT, BTM_IO_CAP_NONE},
-};
-
-std::unordered_map<bluetooth::hci::AuthenticationRequirements, int>
- gd_legacy_auth_reqs_map_ = {
- {bluetooth::hci::AuthenticationRequirements::NO_BONDING,
- BTM_AUTH_SP_NO},
- {bluetooth::hci::AuthenticationRequirements::NO_BONDING_MITM_PROTECTION,
- BTM_AUTH_SP_YES},
- {bluetooth::hci::AuthenticationRequirements::DEDICATED_BONDING,
- BTM_AUTH_AP_NO},
- {bluetooth::hci::AuthenticationRequirements::
- DEDICATED_BONDING_MITM_PROTECTION,
- BTM_AUTH_AP_YES},
- {bluetooth::hci::AuthenticationRequirements::GENERAL_BONDING,
- BTM_AUTH_SPGB_NO},
- {bluetooth::hci::AuthenticationRequirements::
- GENERAL_BONDING_MITM_PROTECTION,
- BTM_AUTH_SPGB_YES},
-};
-}
-
-class ShimUi : public bluetooth::security::UI {
- public:
- static ShimUi* GetInstance() {
- static ShimUi instance;
- return &instance;
- }
-
- ShimUi(const ShimUi&) = delete;
- ShimUi& operator=(const ShimUi&) = delete;
-
- void SetBtaCallbacks(const tBTM_APPL_INFO* bta_callbacks) {
- bta_callbacks_ = bta_callbacks;
- if (bta_callbacks->p_pin_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s pin_callback", __func__);
- }
-
- if (bta_callbacks->p_link_key_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s link_key_callback", __func__);
- }
-
- if (bta_callbacks->p_auth_complete_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s auth_complete_callback", __func__);
- }
-
- if (bta_callbacks->p_bond_cancel_cmpl_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s bond_cancel_complete_callback", __func__);
- }
-
- if (bta_callbacks->p_le_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s le_callback", __func__);
- }
-
- if (bta_callbacks->p_le_key_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s le_key_callback", __func__);
- }
- }
-
- void DisplayPairingPrompt(const bluetooth::hci::AddressWithType& address,
- std::string name) {
- waiting_for_pairing_prompt_ = true;
- bt_bdname_t legacy_name{0};
- memcpy(legacy_name.name, name.data(), name.length());
- // TODO(optedoblivion): Handle callback to BTA for BLE
- }
-
- void Cancel(const bluetooth::hci::AddressWithType& address) {
- LOG(WARNING) << " â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â– â–  " << __func__;
- }
-
- void HandleConfirm(bluetooth::security::ConfirmationData data) {
- const bluetooth::hci::AddressWithType& address = data.GetAddressWithType();
- uint32_t numeric_value = data.GetNumericValue();
- bt_bdname_t legacy_name{0};
- memcpy(legacy_name.name, data.GetName().data(), data.GetName().length());
-
- if (bta_callbacks_->p_sp_callback) {
- // Call sp_cback for IO_REQ
- tBTM_SP_IO_REQ io_req_evt_data;
- io_req_evt_data.bd_addr = bluetooth::ToRawAddress(address.GetAddress());
- // Local IO Caps (Phone is always DisplayYesNo)
- io_req_evt_data.io_cap = BTM_IO_CAP_IO;
- // Local Auth Reqs (Phone is always DEDICATED_BONDING)
- io_req_evt_data.auth_req = BTM_AUTH_AP_NO;
- io_req_evt_data.oob_data = BTM_OOB_NONE;
- (*bta_callbacks_->p_sp_callback)(BTM_SP_IO_REQ_EVT,
- (tBTM_SP_EVT_DATA*)&io_req_evt_data);
-
- // Call sp_cback for IO_RSP
- tBTM_SP_IO_RSP io_rsp_evt_data;
- io_rsp_evt_data.bd_addr = bluetooth::ToRawAddress(address.GetAddress());
- io_rsp_evt_data.io_cap = gd_legacy_io_caps_map_[data.GetRemoteIoCaps()];
- io_rsp_evt_data.auth_req =
- gd_legacy_auth_reqs_map_[data.GetRemoteAuthReqs()];
- io_rsp_evt_data.auth_req = BTM_AUTH_AP_YES;
- io_rsp_evt_data.oob_data = BTM_OOB_NONE;
- (*bta_callbacks_->p_sp_callback)(BTM_SP_IO_RSP_EVT,
- (tBTM_SP_EVT_DATA*)&io_rsp_evt_data);
-
- // Call sp_cback for USER_CONFIRMATION
- tBTM_SP_EVT_DATA user_cfm_req_evt_data;
- user_cfm_req_evt_data.cfm_req.bd_addr =
- bluetooth::ToRawAddress(address.GetAddress());
- user_cfm_req_evt_data.cfm_req.num_val = numeric_value;
- // If we pop a dialog then it isn't just_works
- user_cfm_req_evt_data.cfm_req.just_works = data.IsJustWorks();
-
- address_name_map_.emplace(address, legacy_name);
- memcpy((char*)user_cfm_req_evt_data.cfm_req.bd_name, legacy_name.name,
- BD_NAME_LEN);
-
- (*bta_callbacks_->p_sp_callback)(BTM_SP_CFM_REQ_EVT,
- &user_cfm_req_evt_data);
- }
- }
-
- void DisplayConfirmValue(bluetooth::security::ConfirmationData data) {
- waiting_for_pairing_prompt_ = false;
- data.SetJustWorks(false);
- HandleConfirm(data);
- }
-
- void DisplayYesNoDialog(bluetooth::security::ConfirmationData data) {
- waiting_for_pairing_prompt_ = false;
- data.SetJustWorks(true);
- HandleConfirm(data);
- }
-
- void DisplayEnterPasskeyDialog(bluetooth::security::ConfirmationData data) {
- waiting_for_pairing_prompt_ = false;
- LOG_WARN("UNIMPLEMENTED, Passkey not supported in GD");
- }
-
- void DisplayPasskey(bluetooth::security::ConfirmationData data) {
- waiting_for_pairing_prompt_ = false;
- LOG_WARN("UNIMPLEMENTED, Passkey not supported in GD");
- }
-
- void DisplayEnterPinDialog(bluetooth::security::ConfirmationData data) {
- waiting_for_pairing_prompt_ = false;
- LOG_WARN("UNIMPLEMENTED, PIN not supported in GD");
- }
-
- bool waiting_for_pairing_prompt_ = false;
-
- private:
- ShimUi() : bta_callbacks_(nullptr) {}
- ~ShimUi() {}
- const tBTM_APPL_INFO* bta_callbacks_;
-};
-
-ShimUi* shim_ui_ = nullptr;
-
-class ShimBondListener : public bluetooth::security::ISecurityManagerListener {
- public:
- static ShimBondListener* GetInstance() {
- static ShimBondListener instance;
- return &instance;
- }
-
- ShimBondListener(const ShimBondListener&) = delete;
- ShimBondListener& operator=(const ShimBondListener&) = delete;
-
- void SetBtaCallbacks(const tBTM_APPL_INFO* bta_callbacks) {
- bta_callbacks_ = bta_callbacks;
- if (bta_callbacks->p_pin_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s pin_callback", __func__);
- }
-
- if (bta_callbacks->p_link_key_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s link_key_callback", __func__);
- }
-
- if (bta_callbacks->p_auth_complete_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s auth_complete_callback", __func__);
- }
-
- if (bta_callbacks->p_bond_cancel_cmpl_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s bond_cancel_complete_callback", __func__);
- }
-
- if (bta_callbacks->p_le_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s le_callback", __func__);
- }
-
- if (bta_callbacks->p_le_key_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s le_key_callback", __func__);
- }
- }
-
- void OnDeviceBonded(bluetooth::hci::AddressWithType device) override {
- // Call sp_cback for LINK_KEY_NOTIFICATION
- // Call AUTHENTICATION_COMPLETE callback
- if (device.GetAddressType() ==
- bluetooth::hci::AddressType::PUBLIC_DEVICE_ADDRESS) {
- auto it = address_name_map_.find(device);
- bt_bdname_t tmp_name;
- if (it != address_name_map_.end()) {
- tmp_name = it->second;
- }
- BD_NAME name;
- memcpy((char*)name, tmp_name.name, BD_NAME_LEN);
-
- if (*bta_callbacks_->p_link_key_callback) {
- LinkKey key; // Never want to send the key to the stack
- (*bta_callbacks_->p_link_key_callback)(
- bluetooth::ToRawAddress(device.GetAddress()), 0, name, key,
- BTM_LKEY_TYPE_COMBINATION);
- }
- if (*bta_callbacks_->p_auth_complete_callback) {
- (*bta_callbacks_->p_auth_complete_callback)(
- bluetooth::ToRawAddress(device.GetAddress()), 0, name, HCI_SUCCESS);
- }
- }
- bool is_gd_enabled = bluetooth::shim::is_any_gd_enabled();
- if (is_gd_enabled) {
- bluetooth::shim::AllocateIdFromMetricIdAllocator(
- bluetooth::ToRawAddress(device.GetAddress()));
- } else {
- MetricIdAllocator::GetInstance().AllocateId(
- bluetooth::ToRawAddress(device.GetAddress()));
- }
- bool is_saving_successful =
- is_gd_enabled ? bluetooth::shim::SaveDeviceOnMetricIdAllocator(
- bluetooth::ToRawAddress(device.GetAddress()))
- : MetricIdAllocator::GetInstance().SaveDevice(
- bluetooth::ToRawAddress(device.GetAddress()));
- if (!is_saving_successful) {
- LOG(FATAL) << __func__ << ": Fail to save metric id for device "
- << bluetooth::ToRawAddress(device.GetAddress());
- }
- }
-
- void OnDeviceUnbonded(bluetooth::hci::AddressWithType device) override {
- if (bta_callbacks_->p_bond_cancel_cmpl_callback) {
- (*bta_callbacks_->p_bond_cancel_cmpl_callback)(BTM_SUCCESS);
- }
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::ForgetDeviceFromMetricIdAllocator(
- bluetooth::ToRawAddress(device.GetAddress()));
- } else {
- MetricIdAllocator::GetInstance().ForgetDevice(
- bluetooth::ToRawAddress(device.GetAddress()));
- }
- }
-
- void OnDeviceBondFailed(bluetooth::hci::AddressWithType device,
- bluetooth::security::PairingFailure status) override {
- auto it = address_name_map_.find(device);
- bt_bdname_t tmp_name;
- if (it != address_name_map_.end()) {
- tmp_name = it->second;
- }
- BD_NAME name;
- memcpy((char*)name, tmp_name.name, BD_NAME_LEN);
-
- if (bta_callbacks_->p_auth_complete_callback) {
- (*bta_callbacks_->p_auth_complete_callback)(
- bluetooth::ToRawAddress(device.GetAddress()), 0, name,
- HCI_ERR_AUTH_FAILURE);
- }
- }
-
- void OnEncryptionStateChanged(
- bluetooth::hci::EncryptionChangeView encryption_change_view) override {
- // TODO(optedoblivion): Find BTA callback for this to call
- }
-
- private:
- ShimBondListener() : bta_callbacks_(nullptr) {}
- ~ShimBondListener() {}
- const tBTM_APPL_INFO* bta_callbacks_;
-};
-
-tBTM_STATUS bluetooth::shim::BTM_StartInquiry(tBTM_INQ_RESULTS_CB* p_results_cb,
+tBTM_STATUS bluetooth::shim::BTM_StartInquiry(tBTM_INQ_PARMS* p_inqparms,
+ tBTM_INQ_RESULTS_CB* p_results_cb,
tBTM_CMPL_CB* p_cmpl_cb) {
+ CHECK(p_inqparms != nullptr);
CHECK(p_results_cb != nullptr);
CHECK(p_cmpl_cb != nullptr);
- tBTM_INQ_PARMS inqparms = {};
- inqparms.mode = BTM_GENERAL_INQUIRY | BTM_BLE_GENERAL_INQUIRY;
- inqparms.duration = BTIF_DM_DEFAULT_INQ_MAX_DURATION;
-
std::lock_guard<std::mutex> lock(btm_cb_mutex_);
btm_cb.btm_inq_vars.inq_cmpl_info.num_resp = 0;
-
- Stack::GetInstance()->GetBtm()->StartActiveScanning();
- if (inqparms.duration != 0) {
- Stack::GetInstance()->GetBtm()->SetScanningTimer(
- inqparms.duration * 1000, common::BindOnce([]() {
- LOG_INFO("%s scanning timeout popped", __func__);
- std::lock_guard<std::mutex> lock(btm_cb_mutex_);
- Stack::GetInstance()->GetBtm()->StopActiveScanning();
- }));
+ btm_cb.btm_inq_vars.scan_type = INQ_GENERAL;
+
+ shim_btm.StartActiveScanning();
+ if (p_inqparms->duration != 0) {
+ shim_btm.SetScanningTimer(p_inqparms->duration * 1000, []() {
+ LOG_INFO(LOG_TAG, "%s scanning timeout popped", __func__);
+ std::lock_guard<std::mutex> lock(btm_cb_mutex_);
+ shim_btm.StopActiveScanning();
+ });
}
- Stack::GetInstance()->GetBtm()->StartActiveScanning();
+ shim_btm.StartActiveScanning();
+
+ uint8_t classic_mode = p_inqparms->mode & 0x0f;
+ if (!shim_btm.SetInquiryFilter(classic_mode, p_inqparms->filter_cond_type,
+ p_inqparms->filter_cond)) {
+ LOG_WARN(LOG_TAG, "%s Unable to set inquiry filter", __func__);
+ return BTM_ERR_PROCESSING;
+ }
- uint8_t classic_mode = inqparms.mode & 0x0f;
- if (!Stack::GetInstance()->GetBtm()->StartInquiry(
- classic_mode, inqparms.duration, 0,
- [](tBTM_STATUS status, uint8_t inquiry_mode) {
- LOG_INFO("%s Inquiry is complete status:%hd inquiry_mode:%hhd",
- __func__, status, inquiry_mode);
+ if (!shim_btm.StartInquiry(
+ classic_mode, p_inqparms->duration, p_inqparms->max_resps,
+ [](uint16_t status, uint8_t inquiry_mode) {
+ LOG_DEBUG(LOG_TAG,
+ "%s Inquiry is complete status:%hd inquiry_mode:%hhd",
+ __func__, status, inquiry_mode);
btm_cb.btm_inq_vars.inqparms.mode &= ~(inquiry_mode);
- btm_acl_update_inquiry_status(BTM_INQUIRY_COMPLETE);
+ btm_acl_update_busy_level(BTM_BLI_INQ_DONE_EVT);
if (btm_cb.btm_inq_vars.inq_active) {
btm_cb.btm_inq_vars.inq_cmpl_info.status = status;
btm_clear_all_pending_le_entry();
@@ -575,24 +358,29 @@ tBTM_STATUS bluetooth::shim::BTM_StartInquiry(tBTM_INQ_RESULTS_CB* p_results_cb,
btm_cb.btm_inq_vars.p_inq_cmpl_cb = nullptr;
if (btm_cb.btm_inq_vars.p_inq_cmpl_cb != nullptr) {
- LOG_INFO("%s Sending inquiry completion to upper layer",
- __func__);
+ LOG_DEBUG(LOG_TAG,
+ "%s Sending inquiry completion to upper layer",
+ __func__);
(btm_cb.btm_inq_vars.p_inq_cmpl_cb)(
(tBTM_INQUIRY_CMPL*)&btm_cb.btm_inq_vars.inq_cmpl_info);
btm_cb.btm_inq_vars.p_inq_cmpl_cb = nullptr;
}
}
+ if (btm_cb.btm_inq_vars.inqparms.mode == BTM_INQUIRY_NONE &&
+ btm_cb.btm_inq_vars.scan_type == INQ_GENERAL) {
+ btm_cb.btm_inq_vars.scan_type = INQ_NONE;
+ }
})) {
- LOG_WARN("%s Unable to start inquiry", __func__);
+ LOG_WARN(LOG_TAG, "%s Unable to start inquiry", __func__);
return BTM_ERR_PROCESSING;
}
btm_cb.btm_inq_vars.state = BTM_INQ_ACTIVE_STATE;
btm_cb.btm_inq_vars.p_inq_cmpl_cb = p_cmpl_cb;
btm_cb.btm_inq_vars.p_inq_results_cb = p_results_cb;
- btm_cb.btm_inq_vars.inq_active = inqparms.mode;
+ btm_cb.btm_inq_vars.inq_active = p_inqparms->mode;
- btm_acl_update_inquiry_status(BTM_INQUIRY_STARTED);
+ btm_acl_update_busy_level(BTM_BLI_INQ_EVT);
return BTM_CMD_STARTED;
}
@@ -608,38 +396,48 @@ tBTM_STATUS bluetooth::shim::BTM_SetDiscoverability(uint16_t discoverable_mode,
switch (le_discoverable_mode) {
case kDiscoverableModeOff:
- Stack::GetInstance()->GetBtm()->StopAdvertising();
+ shim_btm.StopAdvertising();
break;
case kLimitedDiscoverableMode:
case kGeneralDiscoverableMode:
- Stack::GetInstance()->GetBtm()->StartAdvertising();
+ shim_btm.StartAdvertising();
break;
default:
- LOG_WARN("%s Unexpected le discoverability mode:%d", __func__,
+ LOG_WARN(LOG_TAG, "%s Unexpected le discoverability mode:%d", __func__,
le_discoverable_mode);
}
switch (classic_discoverable_mode) {
case kDiscoverableModeOff:
- Stack::GetInstance()->GetBtm()->SetClassicDiscoverabilityOff();
+ shim_btm.SetClassicDiscoverabilityOff();
break;
case kLimitedDiscoverableMode:
- Stack::GetInstance()->GetBtm()->SetClassicLimitedDiscoverability(
- window, interval);
+ shim_btm.SetClassicLimitedDiscoverability(window, interval);
break;
case kGeneralDiscoverableMode:
- Stack::GetInstance()->GetBtm()->SetClassicGeneralDiscoverability(
- window, interval);
+ shim_btm.SetClassicGeneralDiscoverability(window, interval);
break;
default:
- LOG_WARN("%s Unexpected classic discoverability mode:%d", __func__,
- classic_discoverable_mode);
+ LOG_WARN(LOG_TAG, "%s Unexpected classic discoverability mode:%d",
+ __func__, classic_discoverable_mode);
}
return BTM_SUCCESS;
}
-void bluetooth::shim::BTM_EnableInterlacedInquiryScan() {
- Stack::GetInstance()->GetBtm()->SetInterlacedInquiryScan();
+tBTM_STATUS bluetooth::shim::BTM_SetInquiryScanType(uint16_t scan_type) {
+ switch (scan_type) {
+ case kInterlacedScanType:
+ shim_btm.SetInterlacedInquiryScan();
+ return BTM_SUCCESS;
+ break;
+ case kStandardScanType:
+ shim_btm.SetStandardInquiryScan();
+ return BTM_SUCCESS;
+ break;
+ default:
+ return BTM_ILLEGAL_VALUE;
+ }
+ return BTM_WRONG_MODE;
}
tBTM_STATUS bluetooth::shim::BTM_BleObserve(bool start, uint8_t duration_sec,
@@ -651,66 +449,65 @@ tBTM_STATUS bluetooth::shim::BTM_BleObserve(bool start, uint8_t duration_sec,
std::lock_guard<std::mutex> lock(btm_cb_mutex_);
- if (btm_cb.ble_ctr_cb.is_ble_observe_active()) {
- LOG_WARN("%s Observing already active", __func__);
+ if (btm_cb.ble_ctr_cb.scan_activity & BTM_LE_OBSERVE_ACTIVE) {
+ LOG_WARN(LOG_TAG, "%s Observing already active", __func__);
return BTM_WRONG_MODE;
}
btm_cb.ble_ctr_cb.p_obs_results_cb = p_results_cb;
btm_cb.ble_ctr_cb.p_obs_cmpl_cb = p_cmpl_cb;
- Stack::GetInstance()->GetBtm()->StartObserving();
- btm_cb.ble_ctr_cb.set_ble_observe_active();
+ shim_btm.StartObserving();
+ btm_cb.ble_ctr_cb.scan_activity |= BTM_LE_OBSERVE_ACTIVE;
if (duration_sec != 0) {
- Stack::GetInstance()->GetBtm()->SetObservingTimer(
- duration_sec * 1000, common::BindOnce([]() {
- LOG_INFO("%s observing timeout popped", __func__);
+ shim_btm.SetObservingTimer(duration_sec * 1000, []() {
+ LOG_DEBUG(LOG_TAG, "%s observing timeout popped", __func__);
- Stack::GetInstance()->GetBtm()->CancelObservingTimer();
- Stack::GetInstance()->GetBtm()->StopObserving();
+ shim_btm.CancelObservingTimer();
+ shim_btm.StopObserving();
- std::lock_guard<std::mutex> lock(btm_cb_mutex_);
- btm_cb.ble_ctr_cb.reset_ble_observe();
+ std::lock_guard<std::mutex> lock(btm_cb_mutex_);
+ btm_cb.ble_ctr_cb.scan_activity &= ~BTM_LE_OBSERVE_ACTIVE;
- if (btm_cb.ble_ctr_cb.p_obs_cmpl_cb) {
- (btm_cb.ble_ctr_cb.p_obs_cmpl_cb)(
- &btm_cb.btm_inq_vars.inq_cmpl_info);
- }
- btm_cb.ble_ctr_cb.p_obs_results_cb = nullptr;
- btm_cb.ble_ctr_cb.p_obs_cmpl_cb = nullptr;
+ if (btm_cb.ble_ctr_cb.p_obs_cmpl_cb) {
+ (btm_cb.ble_ctr_cb.p_obs_cmpl_cb)(&btm_cb.btm_inq_vars.inq_cmpl_info);
+ }
+ btm_cb.ble_ctr_cb.p_obs_results_cb = nullptr;
+ btm_cb.ble_ctr_cb.p_obs_cmpl_cb = nullptr;
- btm_cb.btm_inq_vars.inqparms.mode &= ~(BTM_BLE_INQUIRY_MASK);
+ btm_cb.btm_inq_vars.inqparms.mode &= ~(BTM_BLE_INQUIRY_MASK);
+ btm_cb.btm_inq_vars.scan_type = INQ_NONE;
- btm_acl_update_inquiry_status(BTM_INQUIRY_COMPLETE);
+ btm_acl_update_busy_level(BTM_BLI_INQ_DONE_EVT);
- btm_clear_all_pending_le_entry();
- btm_cb.btm_inq_vars.state = BTM_INQ_INACTIVE_STATE;
+ btm_clear_all_pending_le_entry();
+ btm_cb.btm_inq_vars.state = BTM_INQ_INACTIVE_STATE;
- btm_cb.btm_inq_vars.inq_counter++;
- btm_clr_inq_result_flt();
- btm_sort_inq_result();
+ btm_cb.btm_inq_vars.inq_counter++;
+ btm_clr_inq_result_flt();
+ btm_sort_inq_result();
- btm_cb.btm_inq_vars.inq_active = BTM_INQUIRY_INACTIVE;
- btm_cb.btm_inq_vars.p_inq_results_cb = NULL;
- btm_cb.btm_inq_vars.p_inq_cmpl_cb = NULL;
+ btm_cb.btm_inq_vars.inq_active = BTM_INQUIRY_INACTIVE;
+ btm_cb.btm_inq_vars.p_inq_results_cb = NULL;
+ btm_cb.btm_inq_vars.p_inq_cmpl_cb = NULL;
- if (btm_cb.btm_inq_vars.p_inq_cmpl_cb) {
- (btm_cb.btm_inq_vars.p_inq_cmpl_cb)(
- (tBTM_INQUIRY_CMPL*)&btm_cb.btm_inq_vars.inq_cmpl_info);
- btm_cb.btm_inq_vars.p_inq_cmpl_cb = nullptr;
- }
- }));
+ if (btm_cb.btm_inq_vars.p_inq_cmpl_cb) {
+ (btm_cb.btm_inq_vars.p_inq_cmpl_cb)(
+ (tBTM_INQUIRY_CMPL*)&btm_cb.btm_inq_vars.inq_cmpl_info);
+ btm_cb.btm_inq_vars.p_inq_cmpl_cb = nullptr;
+ }
+ });
}
} else {
std::lock_guard<std::mutex> lock(btm_cb_mutex_);
- if (!btm_cb.ble_ctr_cb.is_ble_observe_active()) {
- LOG_WARN("%s Observing already inactive", __func__);
+ if (!(btm_cb.ble_ctr_cb.scan_activity & BTM_LE_OBSERVE_ACTIVE)) {
+ LOG_WARN(LOG_TAG, "%s Observing already inactive", __func__);
}
- Stack::GetInstance()->GetBtm()->CancelObservingTimer();
- Stack::GetInstance()->GetBtm()->StopObserving();
- btm_cb.ble_ctr_cb.reset_ble_observe();
- Stack::GetInstance()->GetBtm()->StopObserving();
+ shim_btm.CancelObservingTimer();
+ shim_btm.StopObserving();
+ btm_cb.ble_ctr_cb.scan_activity &= ~BTM_LE_OBSERVE_ACTIVE;
+ shim_btm.StopObserving();
if (btm_cb.ble_ctr_cb.p_obs_cmpl_cb) {
(btm_cb.ble_ctr_cb.p_obs_cmpl_cb)(&btm_cb.btm_inq_vars.inq_cmpl_info);
}
@@ -720,20 +517,35 @@ tBTM_STATUS bluetooth::shim::BTM_BleObserve(bool start, uint8_t duration_sec,
return BTM_CMD_STARTED;
}
-void bluetooth::shim::BTM_EnableInterlacedPageScan() {
- Stack::GetInstance()->GetBtm()->SetInterlacedPageScan();
+tBTM_STATUS bluetooth::shim::BTM_SetPageScanType(uint16_t scan_type) {
+ switch (scan_type) {
+ case kInterlacedScanType:
+ if (!shim_btm.IsInterlacedScanSupported()) {
+ return BTM_MODE_UNSUPPORTED;
+ }
+ shim_btm.SetInterlacedPageScan();
+ return BTM_SUCCESS;
+ break;
+ case kStandardScanType:
+ shim_btm.SetStandardPageScan();
+ return BTM_SUCCESS;
+ break;
+ default:
+ return BTM_ILLEGAL_VALUE;
+ }
+ return BTM_WRONG_MODE;
}
tBTM_STATUS bluetooth::shim::BTM_SetInquiryMode(uint8_t inquiry_mode) {
switch (inquiry_mode) {
case kStandardInquiryResult:
- Stack::GetInstance()->GetBtm()->SetStandardInquiryResultMode();
+ shim_btm.SetStandardInquiryResultMode();
break;
case kInquiryResultWithRssi:
- Stack::GetInstance()->GetBtm()->SetInquiryWithRssiResultMode();
+ shim_btm.SetInquiryWithRssiResultMode();
break;
case kExtendedInquiryResult:
- Stack::GetInstance()->GetBtm()->SetExtendedInquiryResultMode();
+ shim_btm.SetExtendedInquiryResultMode();
break;
default:
return BTM_ILLEGAL_VALUE;
@@ -741,6 +553,21 @@ tBTM_STATUS bluetooth::shim::BTM_SetInquiryMode(uint8_t inquiry_mode) {
return BTM_SUCCESS;
}
+uint16_t bluetooth::shim::BTM_ReadDiscoverability(uint16_t* p_window,
+ uint16_t* p_interval) {
+ DiscoverabilityState state = shim_btm.GetClassicDiscoverabilityState();
+
+ if (p_interval) *p_interval = state.interval;
+ if (p_window) *p_window = state.window;
+
+ return state.mode;
+}
+
+tBTM_STATUS bluetooth::shim::BTM_CancelPeriodicInquiry(void) {
+ shim_btm.CancelPeriodicInquiry();
+ return BTM_SUCCESS;
+}
+
tBTM_STATUS bluetooth::shim::BTM_SetConnectability(uint16_t page_mode,
uint16_t window,
uint16_t interval) {
@@ -752,10 +579,10 @@ tBTM_STATUS bluetooth::shim::BTM_SetConnectability(uint16_t page_mode,
switch (le_connectible_mode) {
case kConnectibleModeOff:
- Stack::GetInstance()->GetBtm()->StopConnectability();
+ shim_btm.StopConnectability();
break;
case kConnectibleModeOn:
- Stack::GetInstance()->GetBtm()->StartConnectability();
+ shim_btm.StartConnectability();
break;
default:
return BTM_ILLEGAL_VALUE;
@@ -764,10 +591,10 @@ tBTM_STATUS bluetooth::shim::BTM_SetConnectability(uint16_t page_mode,
switch (classic_connectible_mode) {
case kConnectibleModeOff:
- Stack::GetInstance()->GetBtm()->SetClassicConnectibleOff();
+ shim_btm.SetClassicConnectibleOff();
break;
case kConnectibleModeOn:
- Stack::GetInstance()->GetBtm()->SetClassicConnectibleOn();
+ shim_btm.SetClassicConnectibleOn();
break;
default:
return BTM_ILLEGAL_VALUE;
@@ -776,29 +603,44 @@ tBTM_STATUS bluetooth::shim::BTM_SetConnectability(uint16_t page_mode,
return BTM_SUCCESS;
}
+uint16_t bluetooth::shim::BTM_ReadConnectability(uint16_t* p_window,
+ uint16_t* p_interval) {
+ ConnectabilityState state = shim_btm.GetClassicConnectabilityState();
+
+ if (p_window) *p_window = state.window;
+ if (p_interval) *p_interval = state.interval;
+
+ return state.mode;
+}
+
uint16_t bluetooth::shim::BTM_IsInquiryActive(void) {
- if (Stack::GetInstance()->GetBtm()->IsGeneralInquiryActive()) {
+ if (shim_btm.IsLimitedInquiryActive()) {
+ return BTM_LIMITED_INQUIRY_ACTIVE;
+ } else if (shim_btm.IsGeneralInquiryActive()) {
return BTM_GENERAL_INQUIRY_ACTIVE;
+ } else if (shim_btm.IsGeneralPeriodicInquiryActive() ||
+ shim_btm.IsLimitedPeriodicInquiryActive()) {
+ return BTM_PERIODIC_INQUIRY_ACTIVE;
}
return BTM_INQUIRY_INACTIVE;
}
-void bluetooth::shim::BTM_CancelInquiry(void) {
- LOG_INFO("%s Cancel inquiry", __func__);
- Stack::GetInstance()->GetBtm()->CancelInquiry();
+tBTM_STATUS bluetooth::shim::BTM_CancelInquiry(void) {
+ LOG_DEBUG(LOG_TAG, "%s Cancel inquiry", __func__);
+ shim_btm.CancelInquiry();
btm_cb.btm_inq_vars.state = BTM_INQ_INACTIVE_STATE;
btm_clr_inq_result_flt();
- Stack::GetInstance()->GetBtm()->CancelScanningTimer();
- Stack::GetInstance()->GetBtm()->StopActiveScanning();
+ shim_btm.CancelScanningTimer();
+ shim_btm.StopActiveScanning();
- btm_cb.ble_ctr_cb.reset_ble_inquiry();
+ btm_cb.ble_ctr_cb.scan_activity &= ~BTM_BLE_INQUIRY_MASK;
btm_cb.btm_inq_vars.inqparms.mode &=
~(btm_cb.btm_inq_vars.inqparms.mode & BTM_BLE_INQUIRY_MASK);
- btm_acl_update_inquiry_status(BTM_INQUIRY_COMPLETE);
+ btm_acl_update_busy_level(BTM_BLI_INQ_DONE_EVT);
/* Ignore any stray or late complete messages if the inquiry is not active */
if (btm_cb.btm_inq_vars.inq_active) {
btm_cb.btm_inq_vars.inq_cmpl_info.status = BTM_SUCCESS;
@@ -814,12 +656,18 @@ void bluetooth::shim::BTM_CancelInquiry(void) {
btm_cb.btm_inq_vars.inq_counter++;
if (btm_cb.btm_inq_vars.p_inq_cmpl_cb != nullptr) {
- LOG_INFO("%s Sending cancel inquiry completion to upper layer", __func__);
+ LOG_DEBUG(LOG_TAG, "%s Sending cancel inquiry completion to upper layer",
+ __func__);
(btm_cb.btm_inq_vars.p_inq_cmpl_cb)(
(tBTM_INQUIRY_CMPL*)&btm_cb.btm_inq_vars.inq_cmpl_info);
btm_cb.btm_inq_vars.p_inq_cmpl_cb = nullptr;
}
}
+ if (btm_cb.btm_inq_vars.inqparms.mode == BTM_INQUIRY_NONE &&
+ btm_cb.btm_inq_vars.scan_type == INQ_GENERAL) {
+ btm_cb.btm_inq_vars.scan_type = INQ_NONE;
+ }
+ return BTM_SUCCESS;
}
tBTM_STATUS bluetooth::shim::BTM_ReadRemoteDeviceName(
@@ -830,42 +678,40 @@ tBTM_STATUS bluetooth::shim::BTM_ReadRemoteDeviceName(
switch (transport) {
case BT_TRANSPORT_LE:
- status = Stack::GetInstance()->GetBtm()->ReadLeRemoteDeviceName(
- raw_address, callback);
+ status = shim_btm.ReadLeRemoteDeviceName(raw_address, callback);
break;
case BT_TRANSPORT_BR_EDR:
- status = Stack::GetInstance()->GetBtm()->ReadClassicRemoteDeviceName(
- raw_address, callback);
+ status = shim_btm.ReadClassicRemoteDeviceName(raw_address, callback);
break;
default:
- LOG_WARN("%s Unspecified transport:%d", __func__, transport);
+ LOG_WARN(LOG_TAG, "%s Unspecified transport:%d", __func__, transport);
break;
}
return status;
}
tBTM_STATUS bluetooth::shim::BTM_CancelRemoteDeviceName(void) {
- return Stack::GetInstance()->GetBtm()->CancelAllReadRemoteDeviceName();
+ return shim_btm.CancelAllReadRemoteDeviceName();
}
tBTM_INQ_INFO* bluetooth::shim::BTM_InqDbRead(const RawAddress& p_bda) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
return nullptr;
}
tBTM_INQ_INFO* bluetooth::shim::BTM_InqDbFirst(void) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
return nullptr;
}
tBTM_INQ_INFO* bluetooth::shim::BTM_InqDbNext(tBTM_INQ_INFO* p_cur) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_cur != nullptr);
return nullptr;
}
tBTM_STATUS bluetooth::shim::BTM_ClearInqDb(const RawAddress* p_bda) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
if (p_bda == nullptr) {
// clear all entries
} else {
@@ -875,34 +721,33 @@ tBTM_STATUS bluetooth::shim::BTM_ClearInqDb(const RawAddress* p_bda) {
}
tBTM_STATUS bluetooth::shim::BTM_WriteEIR(BT_HDR* p_buff) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_buff != nullptr);
- osi_free(p_buff);
return BTM_NO_RESOURCES;
}
bool bluetooth::shim::BTM_HasEirService(const uint32_t* p_eir_uuid,
uint16_t uuid16) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_eir_uuid != nullptr);
return false;
}
tBTM_EIR_SEARCH_RESULT bluetooth::shim::BTM_HasInquiryEirService(
tBTM_INQ_RESULTS* p_results, uint16_t uuid16) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_results != nullptr);
return BTM_EIR_UNKNOWN;
}
void bluetooth::shim::BTM_AddEirService(uint32_t* p_eir_uuid, uint16_t uuid16) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_eir_uuid != nullptr);
}
void bluetooth::shim::BTM_RemoveEirService(uint32_t* p_eir_uuid,
uint16_t uuid16) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_eir_uuid != nullptr);
}
@@ -910,7 +755,7 @@ uint8_t bluetooth::shim::BTM_GetEirSupportedServices(uint32_t* p_eir_uuid,
uint8_t** p,
uint8_t max_num_uuid16,
uint8_t* p_num_uuid16) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_eir_uuid != nullptr);
CHECK(p != nullptr);
CHECK(*p != nullptr);
@@ -923,29 +768,32 @@ uint8_t bluetooth::shim::BTM_GetEirUuidList(uint8_t* p_eir, size_t eir_len,
uint8_t* p_num_uuid,
uint8_t* p_uuid_list,
uint8_t max_num_uuid) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_eir != nullptr);
CHECK(p_num_uuid != nullptr);
CHECK(p_uuid_list != nullptr);
return 0;
}
-void bluetooth::shim::BTM_SecAddBleDevice(const RawAddress& bd_addr,
+bool bluetooth::shim::BTM_SecAddBleDevice(const RawAddress& bd_addr,
+ BD_NAME bd_name,
tBT_DEVICE_TYPE dev_type,
tBLE_ADDR_TYPE addr_type) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-void bluetooth::shim::BTM_SecAddBleKey(const RawAddress& bd_addr,
+bool bluetooth::shim::BTM_SecAddBleKey(const RawAddress& bd_addr,
tBTM_LE_KEY_VALUE* p_le_key,
tBTM_LE_KEY_TYPE key_type) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_le_key != nullptr);
+ return false;
}
void bluetooth::shim::BTM_BleLoadLocalKeys(uint8_t key_type,
tBTM_BLE_LOCAL_KEYS* p_key) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_key != nullptr);
}
@@ -953,87 +801,102 @@ static Octet16 bogus_root;
/** Returns local device encryption root (ER) */
const Octet16& bluetooth::shim::BTM_GetDeviceEncRoot() {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
return bogus_root;
}
/** Returns local device identity root (IR). */
const Octet16& bluetooth::shim::BTM_GetDeviceIDRoot() {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
return bogus_root;
}
/** Return local device DHK. */
const Octet16& bluetooth::shim::BTM_GetDeviceDHK() {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
return bogus_root;
}
void bluetooth::shim::BTM_ReadConnectionAddr(const RawAddress& remote_bda,
RawAddress& local_conn_addr,
tBLE_ADDR_TYPE* p_addr_type) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_addr_type != nullptr);
}
+bool bluetooth::shim::BTM_IsBleConnection(uint16_t conn_handle) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
+}
+
bool bluetooth::shim::BTM_ReadRemoteConnectionAddr(
const RawAddress& pseudo_addr, RawAddress& conn_addr,
tBLE_ADDR_TYPE* p_addr_type) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_addr_type != nullptr);
return false;
}
void bluetooth::shim::BTM_SecurityGrant(const RawAddress& bd_addr,
uint8_t res) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+}
+
+void bluetooth::shim::BTM_BlePasskeyReply(const RawAddress& bd_addr,
+ uint8_t res, uint32_t passkey) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+}
+
+void bluetooth::shim::BTM_BleConfirmReply(const RawAddress& bd_addr,
+ uint8_t res) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_BleOobDataReply(const RawAddress& bd_addr,
uint8_t res, uint8_t len,
uint8_t* p_data) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_data != nullptr);
}
void bluetooth::shim::BTM_BleSecureConnectionOobDataReply(
const RawAddress& bd_addr, uint8_t* p_c, uint8_t* p_r) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_c != nullptr);
CHECK(p_r != nullptr);
}
void bluetooth::shim::BTM_BleSetConnScanParams(uint32_t scan_interval,
uint32_t scan_window) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_BleSetPrefConnParams(const RawAddress& bd_addr,
uint16_t min_conn_int,
uint16_t max_conn_int,
- uint16_t peripheral_latency,
+ uint16_t slave_latency,
uint16_t supervision_tout) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_ReadDevInfo(const RawAddress& remote_bda,
tBT_DEVICE_TYPE* p_dev_type,
tBLE_ADDR_TYPE* p_addr_type) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_dev_type != nullptr);
CHECK(p_addr_type != nullptr);
}
bool bluetooth::shim::BTM_ReadConnectedTransportAddress(
RawAddress* remote_bda, tBT_TRANSPORT transport) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(remote_bda != nullptr);
return false;
}
void bluetooth::shim::BTM_BleReceiverTest(uint8_t rx_freq,
tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_cmd_cmpl_cback != nullptr);
}
@@ -1041,34 +904,47 @@ void bluetooth::shim::BTM_BleTransmitterTest(uint8_t tx_freq,
uint8_t test_data_len,
uint8_t packet_payload,
tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_cmd_cmpl_cback != nullptr);
}
void bluetooth::shim::BTM_BleTestEnd(tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_cmd_cmpl_cback != nullptr);
}
bool bluetooth::shim::BTM_UseLeLink(const RawAddress& raw_address) {
- return Stack::GetInstance()->GetBtm()->UseLeLink(raw_address);
+ return shim_btm.IsLeAclConnected(raw_address);
+}
+
+tBTM_STATUS bluetooth::shim::BTM_SetBleDataLength(const RawAddress& bd_addr,
+ uint16_t tx_pdu_length) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return BTM_NO_RESOURCES;
}
void bluetooth::shim::BTM_BleReadPhy(
const RawAddress& bd_addr,
base::Callback<void(uint8_t tx_phy, uint8_t rx_phy, uint8_t status)> cb) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+}
+
+tBTM_STATUS bluetooth::shim::BTM_BleSetDefaultPhy(uint8_t all_phys,
+ uint8_t tx_phys,
+ uint8_t rx_phys) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return BTM_NO_RESOURCES;
}
void bluetooth::shim::BTM_BleSetPhy(const RawAddress& bd_addr, uint8_t tx_phys,
uint8_t rx_phys, uint16_t phy_options) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
bool bluetooth::shim::BTM_BleDataSignature(const RawAddress& bd_addr,
uint8_t* p_text, uint16_t len,
BLE_SIGNATURE signature) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_text != nullptr);
return false;
}
@@ -1077,7 +953,7 @@ bool bluetooth::shim::BTM_BleVerifySignature(const RawAddress& bd_addr,
uint8_t* p_orig, uint16_t len,
uint32_t counter,
uint8_t* p_comp) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_orig != nullptr);
CHECK(p_comp != nullptr);
return false;
@@ -1086,7 +962,7 @@ bool bluetooth::shim::BTM_BleVerifySignature(const RawAddress& bd_addr,
bool bluetooth::shim::BTM_GetLeSecurityState(const RawAddress& bd_addr,
uint8_t* p_le_dev_sec_flags,
uint8_t* p_le_key_size) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
CHECK(p_le_dev_sec_flags != nullptr);
CHECK(p_le_key_size != nullptr);
return false;
@@ -1094,12 +970,12 @@ bool bluetooth::shim::BTM_GetLeSecurityState(const RawAddress& bd_addr,
bool bluetooth::shim::BTM_BleSecurityProcedureIsRunning(
const RawAddress& bd_addr) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
return false;
}
uint8_t bluetooth::shim::BTM_BleGetSupportedKeySize(const RawAddress& bd_addr) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
return 0;
}
@@ -1111,33 +987,33 @@ void bluetooth::shim::BTM_LE_PF_local_name(tBTM_BLE_SCAN_COND_OP action,
tBTM_BLE_PF_FILT_INDEX filt_index,
std::vector<uint8_t> name,
tBTM_BLE_PF_CFG_CBACK cb) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_LE_PF_srvc_data(tBTM_BLE_SCAN_COND_OP action,
tBTM_BLE_PF_FILT_INDEX filt_index) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_LE_PF_manu_data(
tBTM_BLE_SCAN_COND_OP action, tBTM_BLE_PF_FILT_INDEX filt_index,
uint16_t company_id, uint16_t company_id_mask, std::vector<uint8_t> data,
std::vector<uint8_t> data_mask, tBTM_BLE_PF_CFG_CBACK cb) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_LE_PF_srvc_data_pattern(
tBTM_BLE_SCAN_COND_OP action, tBTM_BLE_PF_FILT_INDEX filt_index,
std::vector<uint8_t> data, std::vector<uint8_t> data_mask,
tBTM_BLE_PF_CFG_CBACK cb) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_LE_PF_addr_filter(tBTM_BLE_SCAN_COND_OP action,
tBTM_BLE_PF_FILT_INDEX filt_index,
tBLE_BD_ADDR addr,
tBTM_BLE_PF_CFG_CBACK cb) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_LE_PF_uuid_filter(tBTM_BLE_SCAN_COND_OP action,
@@ -1147,38 +1023,38 @@ void bluetooth::shim::BTM_LE_PF_uuid_filter(tBTM_BLE_SCAN_COND_OP action,
tBTM_BLE_PF_LOGIC_TYPE cond_logic,
const bluetooth::Uuid& uuid_mask,
tBTM_BLE_PF_CFG_CBACK cb) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_LE_PF_set(tBTM_BLE_PF_FILT_INDEX filt_index,
std::vector<ApcfCommand> commands,
tBTM_BLE_PF_CFG_CBACK cb) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_LE_PF_clear(tBTM_BLE_PF_FILT_INDEX filt_index,
tBTM_BLE_PF_CFG_CBACK cb) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_BleAdvFilterParamSetup(
int action, tBTM_BLE_PF_FILT_INDEX filt_index,
std::unique_ptr<btgatt_filt_param_setup_t> p_filt_params,
tBTM_BLE_PF_PARAM_CB cb) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_BleUpdateAdvFilterPolicy(tBTM_BLE_AFP adv_policy) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
void bluetooth::shim::BTM_BleEnableDisableFilterFeature(
uint8_t enable, tBTM_BLE_PF_STATUS_CBACK p_stat_cback) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
}
uint8_t bluetooth::shim::BTM_BleMaxMultiAdvInstanceCount() {
- return Stack::GetInstance()->GetBtm()->GetNumberOfAdvertisingInstances();
+ return shim_btm.GetNumberOfAdvertisingInstances();
}
bool bluetooth::shim::BTM_BleLocalPrivacyEnabled(void) {
@@ -1188,174 +1064,57 @@ bool bluetooth::shim::BTM_BleLocalPrivacyEnabled(void) {
tBTM_STATUS bluetooth::shim::BTM_SecBond(const RawAddress& bd_addr,
tBLE_ADDR_TYPE addr_type,
tBT_TRANSPORT transport,
- int device_type) {
- return Stack::GetInstance()->GetBtm()->CreateBond(bd_addr, addr_type,
- transport, device_type);
+ uint8_t pin_len, uint8_t* p_pin,
+ uint32_t trusted_mask[]) {
+ return shim_btm.CreateBond(bd_addr, addr_type, transport, pin_len, p_pin,
+ trusted_mask);
}
-bool bluetooth::shim::BTM_SecRegister(const tBTM_APPL_INFO* bta_callbacks) {
- CHECK(bta_callbacks != nullptr);
- LOG_INFO("%s Registering security application", __func__);
+bool bluetooth::shim::BTM_SecRegister(const tBTM_APPL_INFO* p_cb_info) {
+ CHECK(p_cb_info != nullptr);
+ LOG_DEBUG(LOG_TAG, "%s Registering security application", __func__);
- if (bta_callbacks->p_pin_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s pin_callback", __func__);
+ if (p_cb_info->p_authorize_callback == nullptr) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s authorize_callback", __func__);
}
- if (bta_callbacks->p_link_key_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s link_key_callback", __func__);
+ if (p_cb_info->p_pin_callback == nullptr) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s pin_callback", __func__);
}
- if (bta_callbacks->p_auth_complete_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s auth_complete_callback", __func__);
+ if (p_cb_info->p_link_key_callback == nullptr) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s link_key_callback", __func__);
}
- if (bta_callbacks->p_bond_cancel_cmpl_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s bond_cancel_complete_callback", __func__);
+ if (p_cb_info->p_auth_complete_callback == nullptr) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s auth_complete_callback", __func__);
}
- if (bta_callbacks->p_le_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s le_callback", __func__);
+ if (p_cb_info->p_bond_cancel_cmpl_callback == nullptr) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s bond_cancel_complete_callback",
+ __func__);
}
- if (bta_callbacks->p_le_key_callback == nullptr) {
- LOG_INFO("UNIMPLEMENTED %s le_key_callback", __func__);
+ if (p_cb_info->p_le_callback == nullptr) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s le_callback", __func__);
}
- ShimBondListener::GetInstance()->SetBtaCallbacks(bta_callbacks);
-
- bluetooth::shim::GetSecurityModule()
- ->GetSecurityManager()
- ->RegisterCallbackListener(ShimBondListener::GetInstance(),
- bluetooth::shim::GetGdShimHandler());
-
- ShimUi::GetInstance()->SetBtaCallbacks(bta_callbacks);
-
- bluetooth::shim::GetSecurityModule()
- ->GetSecurityManager()
- ->SetUserInterfaceHandler(ShimUi::GetInstance(),
- bluetooth::shim::GetGdShimHandler());
+ if (p_cb_info->p_le_key_callback == nullptr) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s le_key_callback", __func__);
+ }
+ shim_btm.SetSimplePairingCallback(p_cb_info->p_sp_callback);
return true;
}
tBTM_STATUS bluetooth::shim::BTM_SecBondCancel(const RawAddress& bd_addr) {
- if (Stack::GetInstance()->GetBtm()->CancelBond(bd_addr)) {
+ if (shim_btm.CancelBond(bd_addr)) {
return BTM_SUCCESS;
} else {
return BTM_UNKNOWN_ADDR;
}
}
-bool bluetooth::shim::BTM_SecAddDevice(const RawAddress& bd_addr,
- DEV_CLASS dev_class, BD_NAME bd_name,
- uint8_t* features, LinkKey* link_key,
- uint8_t key_type, uint8_t pin_length) {
- // Check if GD has a security record for the device
- return BTM_SUCCESS;
-}
-
bool bluetooth::shim::BTM_SecDeleteDevice(const RawAddress& bd_addr) {
- return Stack::GetInstance()->GetBtm()->RemoveBond(bd_addr);
-}
-
-void bluetooth::shim::BTM_ConfirmReqReply(tBTM_STATUS res,
- const RawAddress& bd_addr) {
- // Send for both Classic and LE until we can determine the type
- bool accept = res == BTM_SUCCESS;
- hci::AddressWithType address = ToAddressWithType(bd_addr, 0);
- hci::AddressWithType address2 = ToAddressWithType(bd_addr, 1);
- auto security_manager =
- bluetooth::shim::GetSecurityModule()->GetSecurityManager();
- if (ShimUi::GetInstance()->waiting_for_pairing_prompt_) {
- LOG(INFO) << "interpreting confirmation as pairing accept " << address;
- security_manager->OnPairingPromptAccepted(address, accept);
- security_manager->OnPairingPromptAccepted(address2, accept);
- ShimUi::GetInstance()->waiting_for_pairing_prompt_ = false;
- } else {
- LOG(INFO) << "interpreting confirmation as yes/no confirmation " << address;
- security_manager->OnConfirmYesNo(address, accept);
- security_manager->OnConfirmYesNo(address2, accept);
- }
-}
-
-uint16_t bluetooth::shim::BTM_GetHCIConnHandle(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- return Stack::GetInstance()->GetBtm()->GetAclHandle(remote_bda, transport);
-}
-
-static void remote_name_request_complete_noop(void* p_name){
- // Should notify BTM_Sec, but we should use GD SMP.
-};
-
-void bluetooth::shim::SendRemoteNameRequest(const RawAddress& raw_address) {
- Stack::GetInstance()->GetBtm()->ReadClassicRemoteDeviceName(
- raw_address, remote_name_request_complete_noop);
-}
-
-tBTM_STATUS bluetooth::shim::btm_sec_mx_access_request(
- const RawAddress& bd_addr, bool is_originator,
- uint16_t security_requirement, tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data) {
- // Security has already been fulfilled by the l2cap connection, so reply back
- // that everything is totally fine and legit and definitely not two kids in a
- // trenchcoat
-
- if (p_callback) {
- (*p_callback)(&bd_addr, false, p_ref_data, BTM_SUCCESS);
- }
- return BTM_SUCCESS;
-}
-
-tBTM_STATUS bluetooth::shim::BTM_SetEncryption(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data,
- tBTM_BLE_SEC_ACT sec_act) {
- // When we just bond a device, encryption is already done
- (*p_callback)(&bd_addr, transport, p_ref_data, BTM_SUCCESS);
-
- // TODO(hsz): Re-encrypt the link after first bonded
-
- return BTM_SUCCESS;
-}
-
-void bluetooth::shim::BTM_SecClearSecurityFlags(const RawAddress& bd_addr) {
- // TODO(optedoblivion): Call RemoveBond on device address
-}
-
-char* bluetooth::shim::BTM_SecReadDevName(const RawAddress& address) {
- static char name[] = "TODO: See if this is needed";
- return name;
-}
-
-bool bluetooth::shim::BTM_SecAddRmtNameNotifyCallback(
- tBTM_RMT_NAME_CALLBACK* p_callback) {
- // TODO(optedoblivion): keep track of callback
- LOG_WARN("Unimplemented");
- return true;
-}
-
-bool bluetooth::shim::BTM_SecDeleteRmtNameNotifyCallback(
- tBTM_RMT_NAME_CALLBACK* p_callback) {
- // TODO(optedoblivion): stop keeping track of callback
- LOG_WARN("Unimplemented");
- return true;
-}
-
-void bluetooth::shim::BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res,
- uint8_t pin_len, uint8_t* p_pin) {
- ASSERT_LOG(!bluetooth::shim::is_gd_shim_enabled(), "Unreachable code path");
-}
-
-void bluetooth::shim::BTM_RemoteOobDataReply(tBTM_STATUS res,
- const RawAddress& bd_addr,
- const Octet16& c,
- const Octet16& r) {
- ASSERT_LOG(!bluetooth::shim::is_gd_shim_enabled(), "Unreachable code path");
-}
-
-tBTM_STATUS bluetooth::shim::BTM_SetDeviceClass(DEV_CLASS dev_class) {
- // TODO(optedoblivion): see if we need this, I don't think we do
- LOG_WARN("Unimplemented");
- return BTM_SUCCESS;
+ return shim_btm.RemoveBond(bd_addr);
}
diff --git a/main/shim/btm_api.h b/main/shim/btm_api.h
index be5521ecc..70dbace91 100644
--- a/main/shim/btm_api.h
+++ b/main/shim/btm_api.h
@@ -16,12 +16,8 @@
#pragma once
-#include "stack/btm/btm_sec.h"
-#include "stack/btm/neighbor_inquiry.h"
-#include "stack/include/acl_api_types.h"
#include "stack/include/btm_api_types.h"
#include "stack/include/btm_ble_api_types.h"
-#include "types/hci_role.h"
namespace bluetooth {
namespace shim {
@@ -36,6 +32,8 @@ namespace shim {
* mode - GENERAL or LIMITED inquiry
* duration - length in 1.28 sec intervals (If '0', the
* inquiry is CANCELLED)
+ * max_resps - maximum amount of devices to search for
+ * before ending the inquiry
* filter_cond_type - BTM_CLR_INQUIRY_FILTER,
* BTM_FILTER_COND_DEVICE_CLASS, or
* BTM_FILTER_COND_BD_ADDR
@@ -60,7 +58,8 @@ namespace shim {
* BTM_WRONG_MODE if the device is not up.
*
******************************************************************************/
-tBTM_STATUS BTM_StartInquiry(tBTM_INQ_RESULTS_CB* p_results_cb,
+tBTM_STATUS BTM_StartInquiry(tBTM_INQ_PARMS* p_inqparms,
+ tBTM_INQ_RESULTS_CB* p_results_cb,
tBTM_CMPL_CB* p_cmpl_cb);
/*******************************************************************************
@@ -84,6 +83,22 @@ tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode, uint16_t window,
/*******************************************************************************
*
+ * Function BTM_SetInquiryScanType
+ *
+ * Description This function is called to set the iquiry scan-type to
+ * standard or interlaced.
+ *
+ * Input Params: BTM_SCAN_TYPE_STANDARD or BTM_SCAN_TYPE_INTERLACED
+ *
+ * Returns BTM_SUCCESS if successful
+ * BTM_MODE_UNSUPPORTED if not a 1.2 device
+ * BTM_WRONG_MODE if the device is not up.
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SetInquiryScanType(uint16_t scan_type);
+
+/*******************************************************************************
+ *
* Function BTM_BleObserve
*
* Description This procedure keep the device listening for advertising
@@ -98,9 +113,21 @@ tBTM_STATUS BTM_BleObserve(bool start, uint8_t duration,
tBTM_INQ_RESULTS_CB* p_results_cb,
tBTM_CMPL_CB* p_cmpl_cb);
-void BTM_EnableInterlacedInquiryScan();
-
-void BTM_EnableInterlacedPageScan();
+/*******************************************************************************
+ *
+ * Function BTM_SetPageScanType
+ *
+ * Description This function is called to set the page scan-type to
+ * standard or interlaced.
+ *
+ * Input Params: BTM_SCAN_TYPE_STANDARD or BTM_SCAN_TYPE_INTERLACED
+ *
+ * Returns BTM_SUCCESS if successful
+ * BTM_MODE_UNSUPPORTED if not a 1.2 device
+ * BTM_WRONG_MODE if the device is not up.
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SetPageScanType(uint16_t scan_type);
/*******************************************************************************
*
@@ -122,6 +149,36 @@ tBTM_STATUS BTM_SetInquiryMode(uint8_t mode);
/*******************************************************************************
*
+ * Function BTM_ReadDiscoverability
+ *
+ * Description This function is called to read the current discoverability
+ * mode of the device.
+ *
+ * Output Params: p_window - current inquiry scan duration
+ * p_interval - current inquiry scan interval
+ *
+ * Returns BTM_NON_DISCOVERABLE, BTM_LIMITED_DISCOVERABLE, or
+ * BTM_GENERAL_DISCOVERABLE
+ *
+ ******************************************************************************/
+uint16_t BTM_ReadDiscoverability(uint16_t* p_window, uint16_t* p_interval);
+
+/*******************************************************************************
+ *
+ * Function BTM_CancelPeriodicInquiry
+ *
+ * Description This function cancels a periodic inquiry
+ *
+ * Returns
+ * BTM_NO_RESOURCES if could not allocate a message buffer
+ * BTM_SUCCESS - if cancelling the periodic inquiry
+ * BTM_WRONG_MODE if the device is not up.
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_CancelPeriodicInquiry(void);
+
+/*******************************************************************************
+ *
* Function BTM_SetConnectability
*
* Description This function is called to set the device into or out of
@@ -139,12 +196,28 @@ tBTM_STATUS BTM_SetConnectability(uint16_t page_mode, uint16_t window,
/*******************************************************************************
*
+ * Function BTM_ReadConnectability
+ *
+ * Description This function is called to read the current discoverability
+ * mode of the device.
+ * Output Params p_window - current page scan duration
+ * p_interval - current time between page scans
+ *
+ * Returns BTM_NON_CONNECTABLE or BTM_CONNECTABLE
+ *
+ ******************************************************************************/
+uint16_t BTM_ReadConnectability(uint16_t* p_window, uint16_t* p_interval);
+
+/*******************************************************************************
+ *
* Function BTM_IsInquiryActive
*
* Description Return a bit mask of the current inquiry state
*
* Returns BTM_INQUIRY_INACTIVE if inactive (0)
+ * BTM_LIMITED_INQUIRY_ACTIVE if a limted inquiry is active
* BTM_GENERAL_INQUIRY_ACTIVE if a general inquiry is active
+ * BTM_PERIODIC_INQUIRY_ACTIVE if a periodic inquiry is active
*
******************************************************************************/
uint16_t BTM_IsInquiryActive(void);
@@ -155,8 +228,12 @@ uint16_t BTM_IsInquiryActive(void);
*
* Description This function cancels an inquiry if active
*
+ * Returns BTM_SUCCESS if successful
+ * BTM_NO_RESOURCES if could not allocate a message buffer
+ * BTM_WRONG_MODE if the device is not up.
+ *
******************************************************************************/
-void BTM_CancelInquiry(void);
+tBTM_STATUS BTM_CancelInquiry(void);
/*******************************************************************************
*
@@ -395,12 +472,15 @@ uint8_t BTM_GetEirUuidList(uint8_t* p_eir, size_t eir_len, uint8_t uuid_size,
* for a LE device stored in the NVRAM.
*
* Parameters: bd_addr - BD address of the peer
+ * bd_name - Name of the peer device. NULL if unknown.
* dev_type - Remote device's device type.
* addr_type - LE device address type.
*
+ * Returns true if added OK, else false
+ *
******************************************************************************/
-void BTM_SecAddBleDevice(const RawAddress& bd_addr, tBT_DEVICE_TYPE dev_type,
- tBLE_ADDR_TYPE addr_type);
+bool BTM_SecAddBleDevice(const RawAddress& bd_addr, BD_NAME bd_name,
+ tBT_DEVICE_TYPE dev_type, tBLE_ADDR_TYPE addr_type);
/*******************************************************************************
*
@@ -414,8 +494,10 @@ void BTM_SecAddBleDevice(const RawAddress& bd_addr, tBT_DEVICE_TYPE dev_type,
* p_le_key - LE key values.
* key_type - LE SMP key type.
*
+ * Returns true if added OK, else false
+ *
******************************************************************************/
-void BTM_SecAddBleKey(const RawAddress& bd_addr, tBTM_LE_KEY_VALUE* p_le_key,
+bool BTM_SecAddBleKey(const RawAddress& bd_addr, tBTM_LE_KEY_VALUE* p_le_key,
tBTM_LE_KEY_TYPE key_type);
/*******************************************************************************
@@ -458,6 +540,18 @@ void BTM_ReadConnectionAddr(const RawAddress& remote_bda,
/*******************************************************************************
*
+ * Function BTM_IsBleConnection
+ *
+ * Description This function is called to check if the connection handle
+ * for an LE link
+ *
+ * Returns true if connection is LE link, otherwise false.
+ *
+ ******************************************************************************/
+bool BTM_IsBleConnection(uint16_t conn_handle);
+
+/*******************************************************************************
+ *
* Function BTM_ReadRemoteConnectionAddr
*
* Description Read the remote device address currently used.
@@ -487,6 +581,38 @@ void BTM_SecurityGrant(const RawAddress& bd_addr, uint8_t res);
/*******************************************************************************
*
+ * Function BTM_BlePasskeyReply
+ *
+ * Description This function is called after Security Manager submitted
+ * passkey request to the application.
+ *
+ * Parameters: bd_addr - Address of the device for which passkey was
+ * requested
+ * res - result of the operation SMP_SUCCESS if success
+ * passkey - numeric value in the range of
+ * BTM_MIN_PASSKEY_VAL(0) -
+ * BTM_MAX_PASSKEY_VAL(999999(0xF423F)).
+ *
+ ******************************************************************************/
+void BTM_BlePasskeyReply(const RawAddress& bd_addr, uint8_t res,
+ uint32_t passkey);
+
+/*******************************************************************************
+ *
+ * Function BTM_BleConfirmReply
+ *
+ * Description This function is called after Security Manager submitted
+ * numeric comparison request to the application.
+ *
+ * Parameters: bd_addr - Address of the device with which numeric
+ * comparison was requested
+ * res - comparison result BTM_SUCCESS if success
+ *
+ ******************************************************************************/
+void BTM_BleConfirmReply(const RawAddress& bd_addr, uint8_t res);
+
+/*******************************************************************************
+ *
* Function BTM_LeOobDataReply
*
* Description This function is called to provide the OOB data for
@@ -542,15 +668,14 @@ void BTM_BleSetConnScanParams(uint32_t scan_interval, uint32_t scan_window);
* Parameters: bd_addr - BD address of the peripheral
* min_conn_int - minimum preferred connection interval
* max_conn_int - maximum preferred connection interval
- * peripheral_latency - preferred peripheral latency
+ * slave_latency - preferred slave latency
* supervision_tout - preferred supervision timeout
*
* Returns void
*
******************************************************************************/
void BTM_BleSetPrefConnParams(const RawAddress& bd_addr, uint16_t min_conn_int,
- uint16_t max_conn_int,
- uint16_t peripheral_latency,
+ uint16_t max_conn_int, uint16_t slave_latency,
uint16_t supervision_tout);
/*******************************************************************************
@@ -638,6 +763,18 @@ bool BTM_UseLeLink(const RawAddress& bd_addr);
/*******************************************************************************
*
+ * Function BTM_SetBleDataLength
+ *
+ * Description Set the maximum BLE transmission packet size
+ *
+ * Returns BTM_SUCCESS if success; otherwise failed.
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SetBleDataLength(const RawAddress& bd_addr,
+ uint16_t tx_pdu_length);
+
+/*******************************************************************************
+ *
* Function BTM_BleReadPhy
*
* Description To read the current PHYs for specified LE connection
@@ -652,6 +789,19 @@ void BTM_BleReadPhy(
/*******************************************************************************
*
+ * Function BTM_BleSetDefaultPhy
+ *
+ * Description To set preferred PHY for ensuing LE connections
+ *
+ *
+ * Returns BTM_SUCCESS if success; otherwise failed.
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_BleSetDefaultPhy(uint8_t all_phys, uint8_t tx_phys,
+ uint8_t rx_phys);
+
+/*******************************************************************************
+ *
* Function BTM_BleSetPhy
*
* Description To set PHY preferences for specified LE connection
@@ -829,7 +979,18 @@ void BTM_BleEnableDisableFilterFeature(uint8_t enable,
******************************************************************************/
uint8_t BTM_BleMaxMultiAdvInstanceCount();
-void BTM_reset_complete();
+/*******************************************************************************
+ *
+ * Function BTM_DeviceReset
+ *
+ * Description This function is called to reset the controller. The
+ * Callback function if provided is called when startup of the
+ * device has completed.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_DeviceReset(tBTM_CMPL_CB* p_cb);
/*******************************************************************************
*
@@ -905,6 +1066,30 @@ uint8_t* BTM_ReadDeviceClass(void);
/*******************************************************************************
*
+ * Function BTM_ReadLocalFeatures
+ *
+ * Description This function is called to read the local features
+ *
+ * Returns pointer to the local features string
+ *
+ ******************************************************************************/
+uint8_t* BTM_ReadLocalFeatures(void);
+
+/*******************************************************************************
+ *
+ * Function BTM_RegisterForDeviceStatusNotif
+ *
+ * Description This function is called to register for device status
+ * change notifications.
+ *
+ * Returns pointer to previous caller's callback function or NULL if
+ * first registration.
+ *
+ ******************************************************************************/
+tBTM_DEV_STATUS_CB* BTM_RegisterForDeviceStatusNotif(tBTM_DEV_STATUS_CB* p_cb);
+
+/*******************************************************************************
+ *
* Function BTM_RegisterForVSEvents
*
* Description This function is called to register/deregister for vendor
@@ -1018,11 +1203,12 @@ tBTM_STATUS BTM_EnableTestMode(void);
*
* Description This function is called to read a remote device's version
*
- * Returns true if valid, false otherwise
+ * Returns BTM_SUCCESS if successful, otherwise an error
*
******************************************************************************/
-bool BTM_ReadRemoteVersion(const RawAddress& addr, uint8_t* lmp_version,
- uint16_t* manufacturer, uint16_t* lmp_sub_version);
+tBTM_STATUS BTM_ReadRemoteVersion(const RawAddress& addr, uint8_t* lmp_version,
+ uint16_t* manufacturer,
+ uint16_t* lmp_sub_version);
/*******************************************************************************
*
@@ -1031,9 +1217,10 @@ bool BTM_ReadRemoteVersion(const RawAddress& addr, uint8_t* lmp_version,
* Description This function is called to read a remote device's
* supported features mask (features mask located at page 0)
*
+ * Note: The size of device features mask page is
+ * BTM_FEATURE_BYTES_PER_PAGE bytes.
+ *
* Returns pointer to the remote supported features mask
- * The size of device features mask page is
- * HCI_FEATURE_BYTES_PER_PAGE bytes.
*
******************************************************************************/
uint8_t* BTM_ReadRemoteFeatures(const RawAddress& addr);
@@ -1041,13 +1228,28 @@ uint8_t* BTM_ReadRemoteFeatures(const RawAddress& addr);
/*****************************************************************************
* ACL CHANNEL MANAGEMENT FUNCTIONS
****************************************************************************/
-void BTM_unblock_sniff_mode_for(const RawAddress& peer_addr);
-void BTM_block_sniff_mode_for(const RawAddress& peer_addr);
-void BTM_unblock_role_switch_for(const RawAddress& peer_addr);
-void BTM_block_role_switch_for(const RawAddress& peer_addr);
+/*******************************************************************************
+ *
+ * Function BTM_SetLinkPolicy
+ *
+ * Description Create and send HCI "Write Policy Set" command
+ *
+ * Returns BTM_CMD_STARTED if successfully initiated, otherwise error
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SetLinkPolicy(const RawAddress& remote_bda, uint16_t* settings);
-void BTM_default_unblock_role_switch();
-void BTM_default_block_role_switch();
+/*******************************************************************************
+ *
+ * Function BTM_SetDefaultLinkPolicy
+ *
+ * Description Set the default value for HCI "Write Policy Set" command
+ * to use when an ACL link is created.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_SetDefaultLinkPolicy(uint16_t settings);
/*******************************************************************************
*
@@ -1108,14 +1310,16 @@ bool BTM_IsAclConnectionUp(const RawAddress& remote_bda,
* BTM_UNKNOWN_ADDR if no active link with bd addr specified
*
******************************************************************************/
-tBTM_STATUS BTM_GetRole(const RawAddress& remote_bd_addr, tHCI_ROLE* p_role);
+tBTM_STATUS BTM_GetRole(const RawAddress& remote_bd_addr, uint8_t* p_role);
/*******************************************************************************
*
* Function BTM_SwitchRole
*
- * Description This function is called to switch role between central and
- * peripheral. If role is already set it will do nothing.
+ * Description This function is called to switch role between master and
+ * slave. If role is already set it will do nothing. If the
+ * command was initiated, the callback function is called upon
+ * completion.
*
* Returns BTM_SUCCESS if already in specified role.
* BTM_CMD_STARTED if command issued to controller.
@@ -1126,7 +1330,8 @@ tBTM_STATUS BTM_GetRole(const RawAddress& remote_bd_addr, tHCI_ROLE* p_role);
* role switching
*
******************************************************************************/
-tBTM_STATUS BTM_SwitchRole(const RawAddress& remote_bd_addr, uint8_t new_role);
+tBTM_STATUS BTM_SwitchRole(const RawAddress& remote_bd_addr, uint8_t new_role,
+ tBTM_CMPL_CB* p_cb);
/*******************************************************************************
*
@@ -1200,6 +1405,31 @@ tBTM_STATUS BTM_ReadAutomaticFlushTimeout(const RawAddress& remote_bda,
tBTM_STATUS BTM_ReadTxPower(const RawAddress& remote_bda,
tBT_TRANSPORT transport, tBTM_CMPL_CB* p_cb);
+/*******************************************************************************
+ *
+ * Function BTM_RegBusyLevelNotif
+ *
+ * Description This function is called to register a callback to receive
+ * busy level change events.
+ *
+ * Returns BTM_SUCCESS if successfully registered, otherwise error
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_RegBusyLevelNotif(tBTM_BL_CHANGE_CB* p_cb, uint8_t* p_level,
+ tBTM_BL_EVENT_MASK evt_mask);
+
+/*******************************************************************************
+ *
+ * Function BTM_GetNumAclLinks
+ *
+ * Description This function is called to count the number of
+ * ACL links that are active.
+ *
+ * Returns uint16_t Number of active ACL links
+ *
+ ******************************************************************************/
+uint16_t BTM_GetNumAclLinks(void);
+
/*****************************************************************************
* (e)SCO CHANNEL MANAGEMENT FUNCTIONS
****************************************************************************/
@@ -1405,6 +1635,18 @@ bool BTM_GetSecurityFlagsByTransport(const RawAddress& bd_addr,
/*******************************************************************************
*
+ * Function BTM_ReadTrustedMask
+ *
+ * Description Get trusted mask for the device
+ *
+ * Returns NULL, if the device record is not found.
+ * otherwise, the trusted mask
+ *
+ ******************************************************************************/
+uint32_t* BTM_ReadTrustedMask(const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
* Function BTM_SetPinType
*
* Description Set PIN type for the device.
@@ -1416,6 +1658,22 @@ void BTM_SetPinType(uint8_t pin_type, PIN_CODE pin_code, uint8_t pin_code_len);
/*******************************************************************************
*
+ * Function BTM_SetPairableMode
+ *
+ * Description Enable or disable pairing
+ *
+ * Parameters allow_pairing - (true or false) whether or not the device
+ * allows pairing.
+ * connect_only_paired - (true or false) whether or not to
+ * only allow paired devices to connect.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_SetPairableMode(bool allow_pairing, bool connect_only_paired);
+
+/*******************************************************************************
+ *
* Function BTM_SetSecurityLevel
*
* Description Register service security level with Security Manager. Each
@@ -1432,6 +1690,19 @@ bool BTM_SetSecurityLevel(bool is_originator, const char* p_name,
/*******************************************************************************
*
+ * Function BTM_SetOutService
+ *
+ * Description This function is called to set the service for
+ * outgoing connection.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_SetOutService(const RawAddress& bd_addr, uint8_t service_id,
+ uint32_t mx_chan_id);
+
+/*******************************************************************************
+ *
* Function BTM_SecClrService
*
* Description Removes specified service record(s) from the security
@@ -1458,8 +1729,9 @@ uint8_t BTM_SecClrService(uint8_t service_id);
*
******************************************************************************/
bool BTM_SecAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
- BD_NAME bd_name, uint8_t* features, LinkKey* link_key,
- uint8_t key_type, uint8_t pin_length);
+ BD_NAME bd_name, uint8_t* features,
+ uint32_t trusted_mask[], LinkKey* link_key,
+ uint8_t key_type, tBTM_IO_CAP io_cap, uint8_t pin_length);
/** Free resources associated with the device associated with |bd_addr| address.
*
@@ -1512,12 +1784,14 @@ tBTM_LINK_KEY_TYPE BTM_SecGetDeviceLinkKeyType(const RawAddress& bd_addr);
* success
* pin_len - length in bytes of the PIN Code
* p_pin - pointer to array with the PIN Code
+ * trusted_mask - bitwise OR of trusted services
+ * (array of uint32_t)
*
* Returns void
*
******************************************************************************/
void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res, uint8_t pin_len,
- uint8_t* p_pin);
+ uint8_t* p_pin, uint32_t trusted_mask[]);
/*******************************************************************************
*
@@ -1529,6 +1803,8 @@ void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res, uint8_t pin_len,
* addr_type - address type for LE transport
* pin_len - length in bytes of the PIN Code
* p_pin - pointer to array with the PIN Code
+ * trusted_mask - bitwise OR of trusted services
+ * (array of uint32_t)
* transport : Physical transport to use for bonding
* (BR/EDR or LE)
*
@@ -1536,7 +1812,8 @@ void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res, uint8_t pin_len,
*
******************************************************************************/
tBTM_STATUS BTM_SecBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type);
+ tBT_TRANSPORT transport, uint8_t pin_len,
+ uint8_t* p_pin, uint32_t trusted_mask[]);
/*******************************************************************************
*
@@ -1580,7 +1857,7 @@ tBTM_STATUS BTM_SecBondCancel(const RawAddress& bd_addr);
******************************************************************************/
tBTM_STATUS BTM_SetEncryption(const RawAddress& bd_addr,
tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback, void* p_ref_data,
+ tBTM_SEC_CBACK* p_callback, void* p_ref_data,
tBTM_BLE_SEC_ACT sec_act);
/*******************************************************************************
@@ -1616,6 +1893,22 @@ void BTM_PasskeyReqReply(tBTM_STATUS res, const RawAddress& bd_addr,
/*******************************************************************************
*
+ * Function BTM_SendKeypressNotif
+ *
+ * Description This function is used during the passkey entry model
+ * by a device with KeyboardOnly IO capabilities
+ * (very likely to be a HID Device).
+ * It is called by a HID Device to inform the remote device
+ * when a key has been entered or erased.
+ *
+ * Parameters: bd_addr - Address of the peer device
+ * type - notification type
+ *
+ ******************************************************************************/
+void BTM_SendKeypressNotif(const RawAddress& bd_addr, tBTM_SP_KEY_TYPE type);
+
+/*******************************************************************************
+ *
* Function BTM_IoCapRsp
*
* Description This function is called in response to BTM_SP_IO_REQ_EVT
@@ -1691,32 +1984,90 @@ bool BTM_PeerSupportsSecureConnections(const RawAddress& bd_addr);
/*******************************************************************************
*
- * Function BTM_GetPeerDeviceTypeFromFeatures
+ * Function BTM_SecReadDevName
*
- * Description This function is called to retrieve the peer device type
- * by referencing the remote features.
+ * Description Looks for the device name in the security database for the
+ * specified BD address.
*
- * Parameters: bd_addr - address of the peer
+ * Returns Pointer to the name or NULL
*
- * Returns BT_DEVICE_TYPE_DUMO if both BR/EDR and BLE transports are
- * supported by the peer,
- * BT_DEVICE_TYPE_BREDR if only BR/EDR transport is supported,
- * BT_DEVICE_TYPE_BLE if only BLE transport is supported.
+ ******************************************************************************/
+char* BTM_SecReadDevName(const RawAddress& bd_addr);
+
+/*****************************************************************************
+ * POWER MANAGEMENT FUNCTIONS
+ ****************************************************************************/
+/*******************************************************************************
+ *
+ * Function BTM_PmRegister
+ *
+ * Description register or deregister with power manager
+ *
+ * Returns BTM_SUCCESS if successful,
+ * BTM_NO_RESOURCES if no room to hold registration
+ * BTM_ILLEGAL_VALUE
*
******************************************************************************/
-tBT_DEVICE_TYPE BTM_GetPeerDeviceTypeFromFeatures(const RawAddress& bd_addr);
+tBTM_STATUS BTM_PmRegister(uint8_t mask, uint8_t* p_pm_id,
+ tBTM_PM_STATUS_CBACK* p_cb);
/*******************************************************************************
*
- * Function BTM_SecReadDevName
+ * Function BTM_SetPowerMode
*
- * Description Looks for the device name in the security database for the
- * specified BD address.
+ * Description store the mode in control block or
+ * alter ACL connection behavior.
*
- * Returns Pointer to the name or NULL
+ * Returns BTM_SUCCESS if successful,
+ * BTM_UNKNOWN_ADDR if bd addr is not active or bad
*
******************************************************************************/
-char* BTM_SecReadDevName(const RawAddress& bd_addr);
+tBTM_STATUS BTM_SetPowerMode(uint8_t pm_id, const RawAddress& remote_bda,
+ const tBTM_PM_PWR_MD* p_mode);
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadPowerMode
+ *
+ * Description This returns the current mode for a specific
+ * ACL connection.
+ *
+ * Input Param remote_bda - device address of desired ACL connection
+ *
+ * Output Param p_mode - address where the current mode is copied into.
+ * BTM_ACL_MODE_NORMAL
+ * BTM_ACL_MODE_HOLD
+ * BTM_ACL_MODE_SNIFF
+ * BTM_ACL_MODE_PARK
+ * (valid only if return code is BTM_SUCCESS)
+ *
+ * Returns BTM_SUCCESS if successful,
+ * BTM_UNKNOWN_ADDR if bd addr is not active or bad
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_ReadPowerMode(const RawAddress& remote_bda,
+ tBTM_PM_MODE* p_mode);
+
+/*******************************************************************************
+ *
+ * Function BTM_SetSsrParams
+ *
+ * Description This sends the given SSR parameters for the given ACL
+ * connection if it is in ACTIVE mode.
+ *
+ * Input Param remote_bda - device address of desired ACL connection
+ * max_lat - maximum latency (in 0.625ms)(0-0xFFFE)
+ * min_rmt_to - minimum remote timeout
+ * min_loc_to - minimum local timeout
+ *
+ *
+ * Returns BTM_SUCCESS if the HCI command is issued successful,
+ * BTM_UNKNOWN_ADDR if bd addr is not active or bad
+ * BTM_CMD_STORED if the command is stored
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SetSsrParams(const RawAddress& remote_bda, uint16_t max_lat,
+ uint16_t min_rmt_to, uint16_t min_loc_to);
/*******************************************************************************
*
@@ -1753,6 +2104,18 @@ tBTM_CONTRL_STATE BTM_PM_ReadControllerState(void);
*
* BLE API
*/
+/*******************************************************************************
+ *
+ * Function BTM_BleObtainVendorCapabilities
+ *
+ * Description This function is called to obatin vendor capabilties
+ *
+ * Parameters p_cmn_vsc_cb - Returns the vednor capabilities
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_BleObtainVendorCapabilities(tBTM_BLE_VSC_CB* p_cmn_vsc_cb);
/**
* This function is called to set scan parameters. |cb| is called with operation
@@ -1815,6 +2178,20 @@ void BTM_BleReadScanReports(tBLE_SCAN_MODE scan_mode,
void BTM_BleTrackAdvertiser(tBTM_BLE_TRACK_ADV_CBACK* p_track_cback,
tBTM_BLE_REF_VALUE ref_value);
+/*******************************************************************************
+ *
+ * Function BTM_BleWriteScanRsp
+ *
+ * Description This function is called to write LE scan response.
+ *
+ * Parameters: p_scan_rsp: scan response.
+ *
+ * Returns status
+ *
+ ******************************************************************************/
+void BTM_BleWriteScanRsp(uint8_t* data, uint8_t length,
+ tBTM_BLE_ADV_DATA_CMPL_CBACK* p_adv_data_cback);
+
/******************************************************************************
*
* Function BTM_BleReadControllerFeatures
@@ -1879,6 +2256,68 @@ bool BTM_BleConfigPrivacy(bool enable);
******************************************************************************/
bool BTM_BleLocalPrivacyEnabled(void);
+/*******************************************************************************
+ *
+ * Function BTM_BleEnableMixedPrivacyMode
+ *
+ * Description This function is called to enabled Mixed mode if privacy 1.2
+ * is applicable in controller.
+ *
+ * Parameters mixed_on: mixed mode to be used or not.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_BleEnableMixedPrivacyMode(bool mixed_on);
+
+/*******************************************************************************
+ *
+ * Function BTM_BleSetConnectableMode
+ *
+ * Description This function is called to set BLE connectable mode for a
+ * peripheral device.
+ *
+ * Parameters connectable_mode: directed connectable mode, or
+ * non-directed. It can be
+ * BTM_BLE_CONNECT_EVT,
+ * BTM_BLE_CONNECT_DIR_EVT or
+ * BTM_BLE_CONNECT_LO_DUTY_DIR_EVT
+ *
+ * Returns BTM_ILLEGAL_VALUE if controller does not support BLE.
+ * BTM_SUCCESS is status set successfully; otherwise failure.
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_BleSetConnectableMode(tBTM_BLE_CONN_MODE connectable_mode);
+
+/*******************************************************************************
+ *
+ * Function BTM_BleTurnOnPrivacyOnRemote
+ *
+ * Description This function is called to enable or disable the privacy on
+ * the remote device.
+ *
+ * Parameters bd_addr: remote device address.
+ * privacy_on: true to enable it; false to disable it.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_BleTurnOnPrivacyOnRemote(const RawAddress& bd_addr, bool privacy_on);
+
+/*******************************************************************************
+ *
+ * Function BTM_BleStackEnable
+ *
+ * Description Enable/Disable BLE functionality on stack regardless of
+ * controller capability.
+ *
+ * Parameters: enable: true to enable, false to disable.
+ *
+ * Returns true if added OK, else false
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_BleStackEnable(bool enable);
+
/**
* This functions are called to configure the adv data payload filter condition
*/
@@ -1895,16 +2334,53 @@ bool BTM_BleLocalPrivacyEnabled(void);
******************************************************************************/
tBTM_STATUS BTM_BleGetEnergyInfo(tBTM_BLE_ENERGY_INFO_CBACK* p_ener_cback);
-/**
- * Send remote name request to GD shim Name module
- */
-void SendRemoteNameRequest(const RawAddress& raw_address);
+/*******************************************************************************
+ *
+ * Function BTM_SecBond
+ *
+ * Description This function is called to perform bonding with peer device.
+ * If the connection is already up, but not secure, pairing
+ * is attempted. If already paired BTM_SUCCESS is returned.
+ *
+ * Parameters: bd_addr - Address of the device to bond
+ * addr_type - address type for LE transport
+ * transport - doing SSP over BR/EDR or SMP over LE
+ * pin_len - length in bytes of the PIN Code
+ * p_pin - pointer to array with the PIN Code
+ * trusted_mask - bitwise OR of trusted services
+ * (array of uint32_t)
+ *
+ * Note: After 2.1 parameters are not used and preserved here not to change API
+ ******************************************************************************/
+tBTM_STATUS BTM_SecBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
+ tBT_TRANSPORT transport, uint8_t pin_len,
+ uint8_t* p_pin, uint32_t trusted_mask[]);
+
+/*******************************************************************************
+ *
+ * Function BTM_SecRegister
+ *
+ * Description Application manager calls this function to register for
+ * security services. There can be one and only one
+ * application saving link keys. BTM allows only first
+ * registration.
+ *
+ * Returns true if registered OK, else false
+ *
+ ******************************************************************************/
+bool BTM_SecRegister(const tBTM_APPL_INFO* p_cb_info);
-tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
- bool is_originator,
- uint16_t security_requirement,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data);
+/** Free resources associated with the device associated with |bd_addr| address.
+ *
+ * *** WARNING ***
+ * tBTM_SEC_DEV_REC associated with bd_addr becomes invalid after this function
+ * is called, also any of it's fields. i.e. if you use p_dev_rec->bd_addr, it is
+ * no longer valid!
+ * *** WARNING ***
+ *
+ * Returns true if removed OK, false if not found or ACL link is active.
+ */
+bool BTM_SecDeleteDevice(const RawAddress& bd_addr);
} // namespace shim
} // namespace bluetooth
diff --git a/main/shim/config.cc b/main/shim/config.cc
index a2ee4adf0..ac8fa376a 100644
--- a/main/shim/config.cc
+++ b/main/shim/config.cc
@@ -16,151 +16,104 @@
#define LOG_TAG "bt_shim_storage"
-#include <algorithm>
#include <cstdint>
#include <cstring>
+#include <future>
#include <memory>
-#include "gd/os/log.h"
-#include "gd/storage/config_cache_helper.h"
-#include "gd/storage/storage_module.h"
+#include "btif/include/btif_config.h"
#include "main/shim/config.h"
#include "main/shim/entry.h"
+#include "storage/legacy.h"
+
using ::bluetooth::shim::GetStorage;
-using ::bluetooth::storage::ConfigCacheHelper;
namespace bluetooth {
namespace shim {
-bool BtifConfigInterface::HasSection(const std::string& section) {
- return GetStorage()->GetConfigCache()->HasSection(section);
-}
-
-bool BtifConfigInterface::HasProperty(const std::string& section,
- const std::string& property) {
- return GetStorage()->GetConfigCache()->HasProperty(section, property);
+std::string checksum_read(const char* filename) {
+ CHECK(filename != nullptr);
+
+ std::promise<std::string> promise;
+ auto future = promise.get_future();
+ GetStorage()->ChecksumRead(
+ std::string(filename),
+ common::BindOnce(
+ [](std::promise<std::string>* promise, std::string,
+ std::string hash_value) { promise->set_value(hash_value); },
+ &promise),
+ bluetooth::shim::GetGdShimHandler());
+ return future.get();
}
-bool BtifConfigInterface::GetInt(const std::string& section,
- const std::string& property, int* value) {
- ASSERT(value != nullptr);
- auto ret = ConfigCacheHelper::FromConfigCache(*GetStorage()->GetConfigCache())
- .GetInt(section, property);
- if (ret) {
- *value = *ret;
- }
- return ret.has_value();
+bool checksum_save(const std::string& checksum, const std::string& filename) {
+ std::promise<bool> promise;
+ auto future = promise.get_future();
+ GetStorage()->ChecksumWrite(
+ filename, checksum,
+ common::BindOnce([](std::promise<bool>* promise, std::string,
+ bool success) { promise->set_value(success); },
+ &promise),
+ bluetooth::shim::GetGdShimHandler());
+ return future.get();
}
-bool BtifConfigInterface::SetInt(const std::string& section,
- const std::string& property, int value) {
- ConfigCacheHelper::FromConfigCache(*GetStorage()->GetConfigCache())
- .SetInt(section, property, value);
- return true;
+std::unique_ptr<config_t> config_new(const char* filename) {
+ CHECK(filename != nullptr);
+
+ std::promise<std::unique_ptr<config_t>> promise;
+ auto future = promise.get_future();
+ GetStorage()->ConfigRead(
+ std::string(filename),
+ common::BindOnce(
+ [](std::promise<std::unique_ptr<config_t>>* promise, std::string,
+ std::unique_ptr<config_t> config) {
+ promise->set_value(std::move(config));
+ },
+ &promise),
+ bluetooth::shim::GetGdShimHandler());
+ return future.get();
}
-bool BtifConfigInterface::GetUint64(const std::string& section,
- const std::string& property,
- uint64_t* value) {
- ASSERT(value != nullptr);
- auto ret = ConfigCacheHelper::FromConfigCache(*GetStorage()->GetConfigCache())
- .GetUint64(section, property);
- if (ret) {
- *value = *ret;
- }
- return ret.has_value();
+bool config_save(const config_t& config, const std::string& filename) {
+ std::promise<bool> promise;
+ auto future = promise.get_future();
+ GetStorage()->ConfigWrite(
+ filename, config,
+ common::BindOnce([](std::promise<bool>* promise, std::string,
+ bool success) { promise->set_value(success); },
+ &promise),
+ bluetooth::shim::GetGdShimHandler());
+ return future.get();
}
-bool BtifConfigInterface::SetUint64(const std::string& section,
- const std::string& property,
- uint64_t value) {
- ConfigCacheHelper::FromConfigCache(*GetStorage()->GetConfigCache())
- .SetUint64(section, property, value);
- return true;
-}
-
-bool BtifConfigInterface::GetStr(const std::string& section,
- const std::string& property, char* value,
- int* size_bytes) {
- ASSERT(value != nullptr);
- ASSERT(size_bytes != nullptr);
- auto str = GetStorage()->GetConfigCache()->GetProperty(section, property);
- if (!str) {
- return false;
- }
- if (*size_bytes == 0) {
- return true;
- }
- // std::string::copy does not null-terminate resultant string by default
- // avoided using strlcpy to prevent extra dependency
- *size_bytes = str->copy(value, (*size_bytes - 1));
- value[*size_bytes] = '\0';
- *size_bytes += 1;
- return true;
-}
-
-std::optional<std::string> BtifConfigInterface::GetStr(
- const std::string& section, const std::string& property) {
- return GetStorage()->GetConfigCache()->GetProperty(section, property);
-}
-
-bool BtifConfigInterface::SetStr(const std::string& section,
- const std::string& property,
- const std::string& value) {
- GetStorage()->GetConfigCache()->SetProperty(section, property, value);
- return true;
-}
+} // namespace shim
+} // namespace bluetooth
-// TODO: implement encrypted read
-bool BtifConfigInterface::GetBin(const std::string& section,
- const std::string& property, uint8_t* value,
- size_t* length) {
- ASSERT(value != nullptr);
- ASSERT(length != nullptr);
- auto value_vec =
- ConfigCacheHelper::FromConfigCache(*GetStorage()->GetConfigCache())
- .GetBin(section, property);
- if (!value_vec) {
- return false;
- }
- *length = std::min(value_vec->size(), *length);
- std::memcpy(value, value_vec->data(), *length);
- return true;
-}
-size_t BtifConfigInterface::GetBinLength(const std::string& section,
- const std::string& property) {
- auto value_vec =
- ConfigCacheHelper::FromConfigCache(*GetStorage()->GetConfigCache())
- .GetBin(section, property);
- if (!value_vec) {
- return 0;
- }
- return value_vec->size();
-}
-bool BtifConfigInterface::SetBin(const std::string& section,
- const std::string& property,
- const uint8_t* value, size_t length) {
- ASSERT(value != nullptr);
- std::vector<uint8_t> value_vec(value, value + length);
- ConfigCacheHelper::FromConfigCache(*GetStorage()->GetConfigCache())
- .SetBin(section, property, value_vec);
- return true;
-}
-bool BtifConfigInterface::RemoveProperty(const std::string& section,
- const std::string& property) {
- return GetStorage()->GetConfigCache()->RemoveProperty(section, property);
+namespace {
+const storage_config_t interface = {
+ bluetooth::shim::checksum_read,
+ bluetooth::shim::checksum_save,
+ config_get_bool,
+ config_get_int,
+ config_get_string,
+ config_get_uint64,
+ config_has_key,
+ config_has_section,
+ bluetooth::shim::config_new,
+ config_new_clone,
+ config_new_empty,
+ config_remove_key,
+ config_remove_section,
+ bluetooth::shim::config_save,
+ config_set_bool,
+ config_set_int,
+ config_set_string,
+ config_set_uint64,
+};
}
-std::vector<std::string> BtifConfigInterface::GetPersistentDevices() {
- return GetStorage()->GetConfigCache()->GetPersistentSections();
+const storage_config_t* bluetooth::shim::storage_config_get_interface() {
+ return &interface;
}
-
-void BtifConfigInterface::Save() { GetStorage()->SaveDelayed(); }
-
-void BtifConfigInterface::Flush() { GetStorage()->SaveImmediately(); }
-
-void BtifConfigInterface::Clear() { GetStorage()->GetConfigCache()->Clear(); }
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/config.h b/main/shim/config.h
index 6402bbf74..abbbf70e3 100644
--- a/main/shim/config.h
+++ b/main/shim/config.h
@@ -16,47 +16,12 @@
#pragma once
-#include <list>
-#include <optional>
-#include <string>
-#include <vector>
+#include "btif/include/btif_config.h"
namespace bluetooth {
namespace shim {
-class BtifConfigInterface {
- public:
- ~BtifConfigInterface() = default;
- static bool HasSection(const std::string& section);
- static bool HasProperty(const std::string& section,
- const std::string& property);
- static bool GetInt(const std::string& section, const std::string& key,
- int* value);
- static bool SetInt(const std::string& section, const std::string& key,
- int value);
- static bool GetUint64(const std::string& section, const std::string& key,
- uint64_t* value);
- static bool SetUint64(const std::string& section, const std::string& key,
- uint64_t value);
- static bool GetStr(const std::string& section, const std::string& key,
- char* value, int* size_bytes);
- static std::optional<std::string> GetStr(const std::string& section,
- const std::string& key);
- static bool SetStr(const std::string& section, const std::string& key,
- const std::string& value);
- static bool GetBin(const std::string& section, const std::string& key,
- uint8_t* value, size_t* length);
- static size_t GetBinLength(const std::string& section,
- const std::string& key);
- static bool SetBin(const std::string& section, const std::string& key,
- const uint8_t* value, size_t length);
- static bool RemoveProperty(const std::string& section,
- const std::string& key);
- static std::vector<std::string> GetPersistentDevices();
- static void Save();
- static void Flush();
- static void Clear();
-};
+const storage_config_t* storage_config_get_interface();
} // namespace shim
} // namespace bluetooth
diff --git a/main/shim/controller.cc b/main/shim/controller.cc
index 6cc08972a..cd39b8467 100644
--- a/main/shim/controller.cc
+++ b/main/shim/controller.cc
@@ -18,19 +18,20 @@
#include "main/shim/controller.h"
#include "btcore/include/module.h"
-#include "gd/common/init_flags.h"
#include "main/shim/entry.h"
#include "main/shim/shim.h"
-#include "main/shim/stack.h"
#include "osi/include/future.h"
#include "osi/include/log.h"
#include "hci/controller.h"
-#include "src/bridge.rs.h"
-using ::bluetooth::common::init_flags::gd_rust_is_enabled;
using ::bluetooth::shim::GetController;
+constexpr uint8_t kPageZero = 0;
+constexpr uint8_t kPageOne = 1;
+constexpr uint8_t kPageTwo = 2;
+constexpr uint8_t kMaxFeaturePage = 3;
+
constexpr int kMaxSupportedCodecs = 8; // MAX_LOCAL_SUPPORTED_CODECS_SIZE
constexpr uint8_t kPhyLe1M = 0x01;
@@ -59,6 +60,8 @@ EXPORT_SYMBOL extern const module_t gd_controller_module = {
struct {
bool ready;
+ uint64_t feature[kMaxFeaturePage];
+ uint64_t le_feature[kMaxFeaturePage];
RawAddress raw_address;
bt_version_t bt_version;
uint8_t local_supported_codecs[kMaxSupportedCodecs];
@@ -68,41 +71,17 @@ struct {
} data_;
static future_t* start_up(void) {
- LOG_INFO("%s Starting up", __func__);
+ LOG_INFO(LOG_TAG, "%s Starting up", __func__);
data_.ready = true;
- if (gd_rust_is_enabled()) {
- auto controller =
- bluetooth::shim::Stack::GetInstance()->GetRustController();
- auto rust_string_address =
- bluetooth::shim::rust::controller_get_address(**controller);
- auto string_address =
- std::string(rust_string_address.data(), rust_string_address.length());
- RawAddress::FromString(string_address, data_.raw_address);
-
- data_.le_supported_states =
- bluetooth::shim::rust::controller_get_le_supported_states(**controller);
-
- LOG_INFO("Mac address:%s", string_address.c_str());
- } else {
- std::string string_address = GetController()->GetMacAddress().ToString();
- RawAddress::FromString(string_address, data_.raw_address);
-
- data_.le_supported_states =
- bluetooth::shim::GetController()->GetLeSupportedStates();
-
- auto local_version_info =
- bluetooth::shim::GetController()->GetLocalVersionInformation();
- data_.bt_version.hci_version =
- static_cast<uint8_t>(local_version_info.hci_version_);
- data_.bt_version.hci_revision = local_version_info.hci_revision_;
- data_.bt_version.lmp_version =
- static_cast<uint8_t>(local_version_info.lmp_version_);
- data_.bt_version.lmp_subversion = local_version_info.lmp_subversion_;
- data_.bt_version.manufacturer = local_version_info.manufacturer_name_;
-
- LOG_INFO("Mac address:%s", string_address.c_str());
- }
+ std::string string_address =
+ GetController()->GetControllerMacAddress().ToString();
+ RawAddress::FromString(string_address, data_.raw_address);
+
+ data_.le_supported_states =
+ bluetooth::shim::GetController()->GetControllerLeSupportedStates();
+
+ LOG_INFO(LOG_TAG, "Mac address:%s", string_address.c_str());
data_.phy = kPhyLe1M;
@@ -117,6 +96,7 @@ static future_t* shut_down(void) {
/**
* Module methods
*/
+#define BIT(x) (0x1ULL << (x))
static bool get_is_ready(void) { return data_.ready; }
@@ -124,6 +104,19 @@ static const RawAddress* get_address(void) { return &data_.raw_address; }
static const bt_version_t* get_bt_version(void) { return &data_.bt_version; }
+static const bt_device_features_t* get_features_classic(int index) {
+ CHECK(index >= 0 && index < kMaxFeaturePage);
+ data_.feature[index] =
+ bluetooth::shim::GetController()->GetControllerLocalExtendedFeatures(
+ index);
+ return (const bt_device_features_t*)&data_.feature[index];
+}
+
+static uint8_t get_last_features_classic_index(void) {
+ return bluetooth::shim::GetController()
+ ->GetControllerLocalExtendedFeaturesMaxPageNumber();
+}
+
static uint8_t* get_local_supported_codecs(uint8_t* number_of_codecs) {
CHECK(number_of_codecs != nullptr);
if (data_.number_of_local_supported_codecs != 0) {
@@ -133,174 +126,159 @@ static uint8_t* get_local_supported_codecs(uint8_t* number_of_codecs) {
return (uint8_t*)nullptr;
}
+static const bt_device_features_t* get_features_ble(void) {
+ return (const bt_device_features_t*)&data_.le_feature[0];
+}
+
static const uint8_t* get_ble_supported_states(void) {
return (const uint8_t*)&data_.le_supported_states;
}
-#define MAP_TO_GD(legacy, gd) \
- static bool legacy(void) { \
- if (gd_rust_is_enabled()) { \
- return bluetooth::shim::rust::controller_##legacy( \
- **bluetooth::shim::Stack::GetInstance()->GetRustController()); \
- } else { \
- return GetController()->gd(); \
- } \
- }
+static bool supports_simple_pairing(void) {
+ return GetController()->GetControllerLocalExtendedFeatures(kPageOne) &
+ BIT(51);
+}
-MAP_TO_GD(supports_simple_pairing, SupportsSimplePairing)
-MAP_TO_GD(supports_secure_connections, SupportsSecureConnections)
-MAP_TO_GD(supports_simultaneous_le_bredr, SupportsSimultaneousLeBrEdr)
-MAP_TO_GD(supports_interlaced_inquiry_scan, SupportsInterlacedInquiryScan)
-MAP_TO_GD(supports_rssi_with_inquiry_results, SupportsRssiWithInquiryResults)
-MAP_TO_GD(supports_extended_inquiry_response, SupportsExtendedInquiryResponse)
-MAP_TO_GD(supports_three_slot_packets, Supports3SlotPackets)
-MAP_TO_GD(supports_five_slot_packets, Supports5SlotPackets)
-MAP_TO_GD(supports_classic_2m_phy, SupportsClassic2mPhy)
-MAP_TO_GD(supports_classic_3m_phy, SupportsClassic3mPhy)
-MAP_TO_GD(supports_three_slot_edr_packets, Supports3SlotEdrPackets)
-MAP_TO_GD(supports_five_slot_edr_packets, Supports5SlotEdrPackets)
-MAP_TO_GD(supports_sco, SupportsSco)
-MAP_TO_GD(supports_hv2_packets, SupportsHv2Packets)
-MAP_TO_GD(supports_hv3_packets, SupportsHv3Packets)
-MAP_TO_GD(supports_ev3_packets, SupportsEv3Packets)
-MAP_TO_GD(supports_ev4_packets, SupportsEv4Packets)
-MAP_TO_GD(supports_ev5_packets, SupportsEv5Packets)
-MAP_TO_GD(supports_esco_2m_phy, SupportsEsco2mPhy)
-MAP_TO_GD(supports_esco_3m_phy, SupportsEsco3mPhy)
-MAP_TO_GD(supports_three_slot_esco_edr_packets, Supports3SlotEscoEdrPackets)
-MAP_TO_GD(supports_role_switch, SupportsRoleSwitch)
-MAP_TO_GD(supports_hold_mode, SupportsHoldMode)
-MAP_TO_GD(supports_sniff_mode, SupportsSniffMode)
-MAP_TO_GD(supports_park_mode, SupportsParkMode)
-MAP_TO_GD(supports_non_flushable_pb, SupportsNonFlushablePb)
-MAP_TO_GD(supports_sniff_subrating, SupportsSniffSubrating)
-MAP_TO_GD(supports_encryption_pause, SupportsEncryptionPause)
-
-MAP_TO_GD(supports_ble, SupportsBle)
-MAP_TO_GD(supports_privacy, SupportsBlePrivacy)
-MAP_TO_GD(supports_packet_extension, SupportsBlePacketExtension)
-MAP_TO_GD(supports_connection_parameters_request,
- SupportsBleConnectionParametersRequest)
-MAP_TO_GD(supports_ble_2m_phy, SupportsBle2mPhy)
-MAP_TO_GD(supports_ble_coded_phy, SupportsBleCodedPhy)
-MAP_TO_GD(supports_extended_advertising, SupportsBleExtendedAdvertising)
-MAP_TO_GD(supports_periodic_advertising, SupportsBlePeriodicAdvertising)
-MAP_TO_GD(supports_peripheral_initiated_feature_exchange,
- SupportsBlePeripheralInitiatedFeatureExchange)
-MAP_TO_GD(supports_connection_parameter_request,
- SupportsBleConnectionParameterRequest)
-
-MAP_TO_GD(supports_periodic_advertising_sync_transfer_sender,
- SupportsBlePeriodicAdvertisingSyncTransferSender)
-MAP_TO_GD(supports_periodic_advertising_sync_transfer_recipient,
- SupportsBlePeriodicAdvertisingSyncTransferRecipient)
-MAP_TO_GD(supports_connected_iso_stream_central,
- SupportsBleConnectedIsochronousStreamCentral)
-MAP_TO_GD(supports_connected_iso_stream_peripheral,
- SupportsBleConnectedIsochronousStreamPeripheral)
-MAP_TO_GD(supports_iso_broadcaster, SupportsBleIsochronousBroadcaster)
-MAP_TO_GD(supports_synchronized_receiver, SupportsBleSynchronizedReceiver)
-
-#define FORWARD_IF_RUST(legacy, gd) \
- static bool legacy(void) { \
- if (gd_rust_is_enabled()) { \
- return bluetooth::shim::rust::controller_##legacy( \
- **bluetooth::shim::Stack::GetInstance()->GetRustController()); \
- } else { \
- return gd; \
- } \
- }
+static bool supports_secure_connections(void) {
+ return GetController()->GetControllerLocalExtendedFeatures(kPageTwo) & BIT(8);
+}
-FORWARD_IF_RUST(supports_reading_remote_extended_features,
- GetController()->IsSupported((bluetooth::hci::OpCode)
- kReadRemoteExtendedFeatures))
-FORWARD_IF_RUST(supports_enhanced_setup_synchronous_connection,
- GetController()->IsSupported((
- bluetooth::hci::OpCode)kEnhancedSetupSynchronousConnection))
-FORWARD_IF_RUST(
- supports_enhanced_accept_synchronous_connection,
- GetController()->IsSupported((bluetooth::hci::OpCode)
- kEnhancedAcceptSynchronousConnection))
-FORWARD_IF_RUST(
- supports_ble_set_privacy_mode,
- GetController()->IsSupported((bluetooth::hci::OpCode)kLeSetPrivacyMode))
-
-#define FORWARD_GETTER_IF_RUST(type, legacy, gd) \
- static type legacy(void) { \
- if (gd_rust_is_enabled()) { \
- return bluetooth::shim::rust::controller_##legacy( \
- **bluetooth::shim::Stack::GetInstance()->GetRustController()); \
- } else { \
- return gd; \
- } \
- }
+static bool supports_simultaneous_le_bredr(void) {
+ return GetController()->GetControllerLocalExtendedFeatures(kPageZero) &
+ BIT(49);
+}
+
+static bool supports_reading_remote_extended_features(void) {
+ return GetController()->IsSupported(
+ (bluetooth::hci::OpCode)kReadRemoteExtendedFeatures);
+}
+
+static bool supports_interlaced_inquiry_scan(void) {
+ return GetController()->GetControllerLocalExtendedFeatures(kPageZero) &
+ BIT(28);
+}
+
+static bool supports_rssi_with_inquiry_results(void) {
+ return GetController()->GetControllerLocalExtendedFeatures(kPageZero) &
+ BIT(28);
+}
+
+static bool supports_extended_inquiry_response(void) {
+ return GetController()->GetControllerLocalExtendedFeatures(kPageZero) &
+ BIT(48);
+}
+
+static bool supports_master_slave_role_switch(void) {
+ return GetController()->GetControllerLocalExtendedFeatures(kPageZero) &
+ BIT(5);
+}
+
+static bool supports_enhanced_setup_synchronous_connection(void) {
+ return GetController()->IsSupported(
+ (bluetooth::hci::OpCode)kEnhancedSetupSynchronousConnection);
+}
+
+static bool supports_enhanced_accept_synchronous_connection(void) {
+ return GetController()->IsSupported(
+ (bluetooth::hci::OpCode)kEnhancedAcceptSynchronousConnection);
+}
-FORWARD_GETTER_IF_RUST(uint16_t, get_acl_buffer_length,
- GetController()->GetAclPacketLength())
-FORWARD_GETTER_IF_RUST(
- uint16_t, get_le_buffer_length,
- GetController()->GetLeBufferSize().le_data_packet_length_)
-FORWARD_GETTER_IF_RUST(
- uint16_t, get_iso_buffer_length,
- GetController()->GetControllerIsoBufferSize().le_data_packet_length_)
+static bool supports_ble(void) {
+ return GetController()->GetControllerLocalExtendedFeatures(kPageOne) & BIT(1);
+}
+
+static bool supports_ble_privacy(void) {
+ return GetController()->GetControllerLeLocalSupportedFeatures() & BIT(6);
+}
+
+static bool supports_ble_set_privacy_mode() {
+ return GetController()->IsSupported(
+ (bluetooth::hci::OpCode)kLeSetPrivacyMode);
+}
+
+static bool supports_ble_packet_extension(void) {
+ return GetController()->GetControllerLeLocalSupportedFeatures() & BIT(5);
+}
+
+static bool supports_ble_connection_parameters_request(void) {
+ return GetController()->GetControllerLeLocalSupportedFeatures() & BIT(2);
+}
+
+static bool supports_ble_2m_phy(void) {
+ return GetController()->GetControllerLeLocalSupportedFeatures() & BIT(8);
+}
+
+static bool supports_ble_coded_phy(void) {
+ return GetController()->GetControllerLeLocalSupportedFeatures() & BIT(11);
+}
+
+static bool supports_ble_extended_advertising(void) {
+ return GetController()->GetControllerLeLocalSupportedFeatures() & BIT(12);
+}
+
+static bool supports_ble_periodic_advertising(void) {
+ return GetController()->GetControllerLeLocalSupportedFeatures() & BIT(13);
+}
+
+static uint16_t get_acl_data_size_classic(void) {
+ return GetController()->GetControllerAclPacketLength();
+}
+
+static uint16_t get_acl_data_size_ble(void) {
+ ::bluetooth::hci::LeBufferSize le_buffer_size =
+ GetController()->GetControllerLeBufferSize();
+ return le_buffer_size.le_data_packet_length_;
+}
static uint16_t get_acl_packet_size_classic(void) {
- return get_acl_buffer_length() + kHciDataPreambleSize;
+ return get_acl_data_size_classic() + kHciDataPreambleSize;
}
static uint16_t get_acl_packet_size_ble(void) {
- return get_le_buffer_length() + kHciDataPreambleSize;
+ return get_acl_data_size_ble() + kHciDataPreambleSize;
}
-static uint16_t get_iso_packet_size(void) {
- return get_iso_buffer_length() + kHciDataPreambleSize;
+static uint16_t get_ble_suggested_default_data_length(void) {
+ LOG_WARN(LOG_TAG, "%s TODO Unimplemented", __func__);
+ return 0;
}
-FORWARD_GETTER_IF_RUST(uint16_t, get_le_suggested_default_data_length,
- GetController()->GetLeSuggestedDefaultDataLength())
+static uint16_t get_ble_maximum_tx_data_length(void) {
+ ::bluetooth::hci::LeMaximumDataLength le_maximum_data_length =
+ GetController()->GetControllerLeMaximumDataLength();
+ return le_maximum_data_length.supported_max_tx_octets_;
+}
-static uint16_t get_le_maximum_tx_data_length(void) {
- if (gd_rust_is_enabled()) {
- return bluetooth::shim::rust::controller_get_le_maximum_tx_data_length(
- **bluetooth::shim::Stack::GetInstance()->GetRustController());
- } else {
- ::bluetooth::hci::LeMaximumDataLength le_maximum_data_length =
- GetController()->GetLeMaximumDataLength();
- return le_maximum_data_length.supported_max_tx_octets_;
- }
+static uint16_t get_ble_maxium_advertising_data_length(void) {
+ LOG_WARN(LOG_TAG, "%s TODO Unimplemented", __func__);
+ return 0;
}
-static uint16_t get_le_maximum_tx_time(void) {
- if (gd_rust_is_enabled()) {
- return bluetooth::shim::rust::controller_get_le_maximum_tx_time(
- **bluetooth::shim::Stack::GetInstance()->GetRustController());
- } else {
- ::bluetooth::hci::LeMaximumDataLength le_maximum_data_length =
- GetController()->GetLeMaximumDataLength();
- return le_maximum_data_length.supported_max_tx_time_;
- }
+static uint8_t get_ble_number_of_supported_advertising_sets(void) {
+ return GetController()->GetControllerLeNumberOfSupportedAdverisingSets();
+}
+
+static uint16_t get_acl_buffer_count_classic(void) {
+ return GetController()->GetControllerNumAclPacketBuffers();
+}
+
+static uint8_t get_acl_buffer_count_ble(void) {
+ LOG_WARN(LOG_TAG, "%s TODO Unimplemented", __func__);
+ return 0;
+}
+
+static uint8_t get_ble_white_list_size(void) {
+ LOG_WARN(LOG_TAG, "%s TODO Unimplemented", __func__);
+ return 0;
}
-FORWARD_GETTER_IF_RUST(uint16_t, get_le_max_advertising_data_length,
- GetController()->GetLeMaximumAdvertisingDataLength())
-FORWARD_GETTER_IF_RUST(uint8_t, get_le_supported_advertising_sets,
- GetController()->GetLeNumberOfSupportedAdverisingSets())
-FORWARD_GETTER_IF_RUST(uint8_t, get_le_periodic_advertiser_list_size,
- GetController()->GetLePeriodicAdvertiserListSize())
-FORWARD_GETTER_IF_RUST(uint16_t, get_acl_buffers,
- GetController()->GetNumAclPacketBuffers())
-FORWARD_GETTER_IF_RUST(uint8_t, get_le_buffers,
- GetController()->GetLeBufferSize().total_num_le_packets_)
-FORWARD_GETTER_IF_RUST(
- uint8_t, get_iso_buffers,
- GetController()->GetControllerIsoBufferSize().total_num_le_packets_)
-FORWARD_GETTER_IF_RUST(uint8_t, get_le_connect_list_size,
- GetController()->GetLeConnectListSize())
-FORWARD_GETTER_IF_RUST(uint8_t, get_le_resolving_list_size,
- GetController()->GetLeResolvingListSize())
+static uint8_t get_ble_resolving_list_max_size(void) {
+ LOG_WARN(LOG_TAG, "%s TODO Unimplemented", __func__);
+ return 0;
+}
static void set_ble_resolving_list_max_size(int resolving_list_max_size) {
- LOG_WARN("%s TODO Unimplemented", __func__);
+ LOG_WARN(LOG_TAG, "%s TODO Unimplemented", __func__);
}
static uint8_t get_le_all_initiating_phys() { return data_.phy; }
@@ -311,6 +289,10 @@ static const controller_t interface = {
get_address,
get_bt_version,
+ get_features_classic,
+ get_last_features_classic_index,
+
+ get_features_ble,
get_ble_supported_states,
supports_simple_pairing,
@@ -320,71 +302,36 @@ static const controller_t interface = {
supports_interlaced_inquiry_scan,
supports_rssi_with_inquiry_results,
supports_extended_inquiry_response,
- supports_role_switch,
+ supports_master_slave_role_switch,
supports_enhanced_setup_synchronous_connection,
supports_enhanced_accept_synchronous_connection,
- supports_three_slot_packets,
- supports_five_slot_packets,
- supports_classic_2m_phy,
- supports_classic_3m_phy,
- supports_three_slot_edr_packets,
- supports_five_slot_edr_packets,
- supports_sco,
- supports_hv2_packets,
- supports_hv3_packets,
- supports_ev3_packets,
- supports_ev4_packets,
- supports_ev5_packets,
- supports_esco_2m_phy,
- supports_esco_3m_phy,
- supports_three_slot_esco_edr_packets,
- supports_role_switch,
- supports_hold_mode,
- supports_sniff_mode,
- supports_park_mode,
- supports_non_flushable_pb,
- supports_sniff_subrating,
- supports_encryption_pause,
supports_ble,
- supports_packet_extension,
- supports_connection_parameters_request,
- supports_privacy,
+ supports_ble_packet_extension,
+ supports_ble_connection_parameters_request,
+ supports_ble_privacy,
supports_ble_set_privacy_mode,
supports_ble_2m_phy,
supports_ble_coded_phy,
- supports_extended_advertising,
- supports_periodic_advertising,
- supports_peripheral_initiated_feature_exchange,
- supports_connection_parameter_request,
- supports_periodic_advertising_sync_transfer_sender,
- supports_periodic_advertising_sync_transfer_recipient,
- supports_connected_iso_stream_central,
- supports_connected_iso_stream_peripheral,
- supports_iso_broadcaster,
- supports_synchronized_receiver,
-
- get_acl_buffer_length,
- get_le_buffer_length,
- get_iso_buffer_length,
+ supports_ble_extended_advertising,
+ supports_ble_periodic_advertising,
+
+ get_acl_data_size_classic,
+ get_acl_data_size_ble,
get_acl_packet_size_classic,
get_acl_packet_size_ble,
- get_iso_packet_size,
- get_le_suggested_default_data_length,
- get_le_maximum_tx_data_length,
- get_le_maximum_tx_time,
- get_le_max_advertising_data_length,
- get_le_supported_advertising_sets,
- get_le_periodic_advertiser_list_size,
+ get_ble_suggested_default_data_length,
+ get_ble_maximum_tx_data_length,
+ get_ble_maxium_advertising_data_length,
+ get_ble_number_of_supported_advertising_sets,
- get_acl_buffers,
- get_le_buffers,
- get_iso_buffers,
+ get_acl_buffer_count_classic,
+ get_acl_buffer_count_ble,
- get_le_connect_list_size,
+ get_ble_white_list_size,
- get_le_resolving_list_size,
+ get_ble_resolving_list_max_size,
set_ble_resolving_list_max_size,
get_local_supported_codecs,
get_le_all_initiating_phys};
diff --git a/main/shim/dumpsys.cc b/main/shim/dumpsys.cc
index b251caa6b..7f7b10e8d 100644
--- a/main/shim/dumpsys.cc
+++ b/main/shim/dumpsys.cc
@@ -23,42 +23,33 @@
#include "shim/dumpsys.h"
namespace {
-
constexpr char kModuleName[] = "shim::legacy::dumpsys";
-static std::unordered_map<const void*, bluetooth::shim::DumpsysFunction>
+static std::unordered_map<const void*, bluetooth::shim::DumpsysFunction>*
dumpsys_functions_;
-
} // namespace
void bluetooth::shim::RegisterDumpsysFunction(const void* token,
DumpsysFunction func) {
- CHECK(dumpsys_functions_.find(token) == dumpsys_functions_.end());
- dumpsys_functions_.insert({token, func});
+ dumpsys_functions_ =
+ new std::unordered_map<const void*, bluetooth::shim::DumpsysFunction>();
+ CHECK(dumpsys_functions_->find(token) == dumpsys_functions_->end());
+ dumpsys_functions_->insert({token, func});
}
void bluetooth::shim::UnregisterDumpsysFunction(const void* token) {
- CHECK(dumpsys_functions_.find(token) != dumpsys_functions_.end());
- dumpsys_functions_.erase(token);
+ CHECK(dumpsys_functions_->find(token) != dumpsys_functions_->end());
+ dumpsys_functions_->erase(token);
}
-void bluetooth::shim::Dump(int fd, const char** args) {
- if (dumpsys_functions_.empty()) {
- dprintf(fd, "%s No registered dumpsys shim legacy targets\n", kModuleName);
- } else {
- dprintf(fd, "%s Dumping shim legacy targets:%zd\n", kModuleName,
- dumpsys_functions_.size());
- for (auto& dumpsys : dumpsys_functions_) {
- dumpsys.second(fd);
- }
+void bluetooth::shim::Dump(int fd) {
+ dprintf(fd, "%s Dumping shim legacy targets:%zd\n", kModuleName,
+ dumpsys_functions_->size());
+ for (auto& dumpsys : *dumpsys_functions_) {
+ dumpsys.second(fd);
}
if (bluetooth::shim::is_gd_stack_started_up()) {
- if (bluetooth::shim::is_gd_dumpsys_module_started()) {
- bluetooth::shim::GetDumpsys()->Dump(fd, args);
- } else {
- dprintf(fd, "%s NOTE: gd dumpsys module not loaded or started\n",
- kModuleName);
- }
+ bluetooth::shim::GetDumpsys()->Dump(fd);
} else {
- dprintf(fd, "%s gd stack is enabled but not started\n", kModuleName);
+ dprintf(fd, "%s gd stack has not started up\n", kModuleName);
}
}
diff --git a/main/shim/dumpsys.h b/main/shim/dumpsys.h
index a37c60df6..91c4ea746 100644
--- a/main/shim/dumpsys.h
+++ b/main/shim/dumpsys.h
@@ -18,37 +18,6 @@
#include <functional>
#include <list>
-#include <string>
-
-#define LOG_DUMPSYS(fd, fmt, args...) \
- do { \
- dprintf(fd, "%s " fmt "\n", DUMPSYS_TAG, ##args); \
- } while (false)
-
-#define LOG_DUMPSYS_TITLE(fd, title) \
- do { \
- dprintf(fd, " ----- %s -----\n", title); \
- } while (false)
-
-constexpr char kPrivateAddressPrefix[] = "xx:xx:xx:xx";
-#define PRIVATE_ADDRESS(addr) \
- (addr.ToString() \
- .replace(0, strlen(kPrivateAddressPrefix), kPrivateAddressPrefix) \
- .c_str())
-
-#define PRIVATE_CELL(number) \
- (number \
- .replace(0, (number.size() > 2) ? number.size() - 2 : 0, \
- (number.size() > 2) ? number.size() - 2 : 0, '*') \
- .c_str())
-
-inline double ticks_to_seconds(uint16_t ticks) {
- return (static_cast<double>(ticks) * 0.625 * 0.001);
-}
-
-inline double supervision_timeout_to_seconds(uint16_t timeout) {
- return (static_cast<double>(timeout) * 0.01);
-}
namespace bluetooth {
namespace shim {
@@ -59,7 +28,7 @@ using DumpsysFunction = std::function<void(int fd)>;
* Entrypoint from legacy stack to provide dumpsys functionality
* for both the legacy shim and the Gabeldorsche stack.
*/
-void Dump(int fd, const char** args);
+void Dump(int fd);
/**
* Dumpsys access for legacy shim modules.
diff --git a/main/shim/entry.cc b/main/shim/entry.cc
index a0d07e329..7bc5f0fdc 100644
--- a/main/shim/entry.cc
+++ b/main/shim/entry.cc
@@ -14,129 +14,123 @@
* limitations under the License.
*/
-#include "gd/btaa/activity_attribution.h"
-#include "gd/hci/controller.h"
-#include "gd/hci/hci_layer.h"
-#include "gd/hci/le_advertising_manager.h"
-#include "gd/hci/le_scanning_manager.h"
-#include "gd/hci/vendor_specific_event_manager.h"
-#include "gd/neighbor/connectability.h"
-#include "gd/neighbor/discoverability.h"
-#include "gd/neighbor/inquiry.h"
-#include "gd/neighbor/name.h"
-#include "gd/neighbor/page.h"
-#include "gd/os/handler.h"
-#include "gd/security/security_module.h"
-#include "gd/shim/dumpsys.h"
-#include "gd/storage/storage_module.h"
-
-#include "hci/acl_manager.h"
-
#include "main/shim/entry.h"
-#include "main/shim/stack.h"
+#include "osi/include/future.h"
+#include "osi/include/log.h"
-namespace bluetooth {
-namespace shim {
+#include "hci/controller.h"
+#include "hci/hci_layer.h"
+#include "hci/le_advertising_manager.h"
+#include "hci/le_scanning_manager.h"
+#include "main/shim/btm.h"
+#include "neighbor/connectability.h"
+#include "neighbor/discoverability.h"
+#include "neighbor/inquiry.h"
+#include "neighbor/name.h"
+#include "neighbor/page.h"
+#include "os/handler.h"
+#include "security/security_module.h"
+#include "shim/dumpsys.h"
+#include "shim/l2cap.h"
+#include "shim/stack.h"
+#include "stack_manager.h"
+#include "storage/legacy.h"
-os::Handler* GetGdShimHandler() { return Stack::GetInstance()->GetHandler(); }
+using bluetooth::shim::GetGabeldorscheStack;
-hci::LeAdvertisingManager* GetAdvertising() {
- return Stack::GetInstance()
- ->GetStackManager()
- ->GetInstance<hci::LeAdvertisingManager>();
-}
+extern bluetooth::shim::Btm shim_btm;
-hci::Controller* GetController() {
- return Stack::GetInstance()
- ->GetStackManager()
- ->GetInstance<hci::Controller>();
+future_t* bluetooth::shim::StartGabeldorscheStack() {
+ GetGabeldorscheStack()->Start();
+ shim_btm.RegisterInquiryCallbacks();
+ return (future_t*)nullptr;
}
-neighbor::ConnectabilityModule* GetConnectability() {
- return Stack::GetInstance()
- ->GetStackManager()
- ->GetInstance<neighbor::ConnectabilityModule>();
+future_t* bluetooth::shim::StopGabeldorscheStack() {
+ GetGabeldorscheStack()->Stop();
+ return (future_t*)nullptr;
}
-neighbor::DiscoverabilityModule* GetDiscoverability() {
- return Stack::GetInstance()
- ->GetStackManager()
- ->GetInstance<neighbor::DiscoverabilityModule>();
+bluetooth::os::Handler* bluetooth::shim::GetGdShimHandler() {
+ return bluetooth::shim::GetDumpsys()->GetGdShimHandler();
}
-Dumpsys* GetDumpsys() {
- return Stack::GetInstance()->GetStackManager()->GetInstance<Dumpsys>();
+bluetooth::hci::LeAdvertisingManager* bluetooth::shim::GetAdvertising() {
+ return GetGabeldorscheStack()
+ ->GetStackManager()
+ ->GetInstance<bluetooth::hci::LeAdvertisingManager>();
}
-neighbor::InquiryModule* GetInquiry() {
- return Stack::GetInstance()
+bluetooth::hci::Controller* bluetooth::shim::GetController() {
+ return GetGabeldorscheStack()
->GetStackManager()
- ->GetInstance<neighbor::InquiryModule>();
+ ->GetInstance<bluetooth::hci::Controller>();
}
-hci::HciLayer* GetHciLayer() {
- return Stack::GetInstance()->GetStackManager()->GetInstance<hci::HciLayer>();
+bluetooth::neighbor::ConnectabilityModule*
+bluetooth::shim::GetConnectability() {
+ return GetGabeldorscheStack()
+ ->GetStackManager()
+ ->GetInstance<bluetooth::neighbor::ConnectabilityModule>();
}
-l2cap::classic::L2capClassicModule* GetL2capClassicModule() {
- return Stack::GetInstance()
+bluetooth::neighbor::DiscoverabilityModule*
+bluetooth::shim::GetDiscoverability() {
+ return GetGabeldorscheStack()
->GetStackManager()
- ->GetInstance<bluetooth::l2cap::classic::L2capClassicModule>();
+ ->GetInstance<bluetooth::neighbor::DiscoverabilityModule>();
}
-bluetooth::l2cap::le::L2capLeModule* GetL2capLeModule() {
- return Stack::GetInstance()
+bluetooth::shim::Dumpsys* bluetooth::shim::GetDumpsys() {
+ return GetGabeldorscheStack()
->GetStackManager()
- ->GetInstance<bluetooth::l2cap::le::L2capLeModule>();
+ ->GetInstance<bluetooth::shim::Dumpsys>();
}
-neighbor::NameModule* GetName() {
- return Stack::GetInstance()
+bluetooth::neighbor::InquiryModule* bluetooth::shim::GetInquiry() {
+ return GetGabeldorscheStack()
->GetStackManager()
- ->GetInstance<neighbor::NameModule>();
+ ->GetInstance<bluetooth::neighbor::InquiryModule>();
}
-neighbor::PageModule* GetPage() {
- return Stack::GetInstance()
+bluetooth::hci::HciLayer* bluetooth::shim::GetHciLayer() {
+ return GetGabeldorscheStack()
->GetStackManager()
- ->GetInstance<neighbor::PageModule>();
+ ->GetInstance<bluetooth::hci::HciLayer>();
}
-hci::LeScanningManager* GetScanning() {
- return Stack::GetInstance()
+bluetooth::shim::L2cap* bluetooth::shim::GetL2cap() {
+ return GetGabeldorscheStack()
->GetStackManager()
- ->GetInstance<hci::LeScanningManager>();
+ ->GetInstance<bluetooth::shim::L2cap>();
}
-security::SecurityModule* GetSecurityModule() {
- return Stack::GetInstance()
+bluetooth::neighbor::NameModule* bluetooth::shim::GetName() {
+ return GetGabeldorscheStack()
->GetStackManager()
- ->GetInstance<security::SecurityModule>();
+ ->GetInstance<bluetooth::neighbor::NameModule>();
}
-storage::StorageModule* GetStorage() {
- return Stack::GetInstance()
+bluetooth::neighbor::PageModule* bluetooth::shim::GetPage() {
+ return GetGabeldorscheStack()
->GetStackManager()
- ->GetInstance<storage::StorageModule>();
+ ->GetInstance<bluetooth::neighbor::PageModule>();
}
-hci::AclManager* GetAclManager() {
- return Stack::GetInstance()
+bluetooth::hci::LeScanningManager* bluetooth::shim::GetScanning() {
+ return GetGabeldorscheStack()
->GetStackManager()
- ->GetInstance<hci::AclManager>();
+ ->GetInstance<bluetooth::hci::LeScanningManager>();
}
-hci::VendorSpecificEventManager* GetVendorSpecificEventManager() {
- return Stack::GetInstance()
+bluetooth::security::SecurityModule* bluetooth::shim::GetSecurityModule() {
+ return GetGabeldorscheStack()
->GetStackManager()
- ->GetInstance<hci::VendorSpecificEventManager>();
+ ->GetInstance<bluetooth::security::SecurityModule>();
}
-activity_attribution::ActivityAttribution* GetActivityAttribution() {
- return Stack::GetInstance()
+bluetooth::storage::LegacyModule* bluetooth::shim::GetStorage() {
+ return GetGabeldorscheStack()
->GetStackManager()
- ->GetInstance<activity_attribution::ActivityAttribution>();
+ ->GetInstance<bluetooth::storage::LegacyModule>();
}
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/entry.h b/main/shim/entry.h
index 714c95cde..28cac166b 100644
--- a/main/shim/entry.h
+++ b/main/shim/entry.h
@@ -29,15 +29,13 @@
* interfaces may be made here
*/
+#include "gd/shim/only_include_this_file_into_legacy_stack___ever.h"
#include "osi/include/future.h"
namespace bluetooth {
namespace os {
class Handler;
}
-namespace activity_attribution {
-class ActivityAttribution;
-}
namespace neighbor {
class ConnectabilityModule;
class DiscoverabilityModule;
@@ -48,30 +46,20 @@ class PageModule;
namespace hci {
class Controller;
class HciLayer;
-class AclManager;
class LeAdvertisingManager;
class LeScanningManager;
-class VendorSpecificEventManager;
}
-namespace l2cap {
-namespace classic {
-class L2capClassicModule;
-} // namespace classic
-namespace le {
-class L2capLeModule;
-} // namespace le
-} // namespace l2cap
-
namespace security {
class SecurityModule;
}
namespace storage {
-class StorageModule;
+class LegacyModule;
}
namespace shim {
-class Dumpsys;
+future_t* StartGabeldorscheStack();
+future_t* StopGabeldorscheStack();
/* This returns a handler that might be used in shim to receive callbacks from
* within the stack. */
@@ -83,16 +71,12 @@ neighbor::ConnectabilityModule* GetConnectability();
Dumpsys* GetDumpsys();
neighbor::InquiryModule* GetInquiry();
hci::HciLayer* GetHciLayer();
-l2cap::classic::L2capClassicModule* GetL2capClassicModule();
-l2cap::le::L2capLeModule* GetL2capLeModule();
+L2cap* GetL2cap();
neighbor::NameModule* GetName();
neighbor::PageModule* GetPage();
hci::LeScanningManager* GetScanning();
bluetooth::security::SecurityModule* GetSecurityModule();
-storage::StorageModule* GetStorage();
-hci::AclManager* GetAclManager();
-hci::VendorSpecificEventManager* GetVendorSpecificEventManager();
-activity_attribution::ActivityAttribution* GetActivityAttribution();
+storage::LegacyModule* GetStorage();
} // namespace shim
} // namespace bluetooth
diff --git a/main/shim/hci_layer.cc b/main/shim/hci_layer.cc
index 0068f487c..a2dae0f02 100644
--- a/main/shim/hci_layer.cc
+++ b/main/shim/hci_layer.cc
@@ -16,26 +16,18 @@
#define LOG_TAG "bt_shim_hci"
-#include "hci/hci_layer.h"
-
#include <base/bind.h>
-
+#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
#include <algorithm>
#include <cstdint>
-#include "callbacks/callbacks.h"
-#include "gd/common/init_flags.h"
-#include "hci/hci_packets.h"
-#include "hci/include/packet_fragmenter.h"
-#include "hci/le_acl_connection_interface.h"
-#include "hci/vendor_specific_event_manager.h"
+#include "btcore/include/module.h"
+#include "hci/hci_layer.h"
#include "main/shim/hci_layer.h"
#include "main/shim/shim.h"
-#include "main/shim/stack.h"
#include "osi/include/allocator.h"
#include "osi/include/future.h"
#include "packet/raw_builder.h"
-#include "src/bridge.rs.h"
#include "stack/include/bt_types.h"
/**
@@ -45,261 +37,62 @@
* Upon completion a token for a corresponding command transmit.
* request is returned from the Gd layer.
*/
-using CommandCallbackData = struct { void* context; };
+using CommandCallbackData = struct {
+ void* context;
+};
constexpr size_t kBtHdrSize = sizeof(BT_HDR);
constexpr size_t kCommandLengthSize = sizeof(uint8_t);
constexpr size_t kCommandOpcodeSize = sizeof(uint16_t);
+static hci_t interface;
static base::Callback<void(const base::Location&, BT_HDR*)> send_data_upwards;
-static const packet_fragmenter_t* packet_fragmenter;
namespace {
-bool is_valid_event_code(bluetooth::hci::EventCode event_code) {
- switch (event_code) {
- case bluetooth::hci::EventCode::INQUIRY_COMPLETE:
- case bluetooth::hci::EventCode::INQUIRY_RESULT:
- case bluetooth::hci::EventCode::CONNECTION_COMPLETE:
- case bluetooth::hci::EventCode::CONNECTION_REQUEST:
- case bluetooth::hci::EventCode::DISCONNECTION_COMPLETE:
- case bluetooth::hci::EventCode::AUTHENTICATION_COMPLETE:
- case bluetooth::hci::EventCode::REMOTE_NAME_REQUEST_COMPLETE:
- case bluetooth::hci::EventCode::ENCRYPTION_CHANGE:
- case bluetooth::hci::EventCode::CHANGE_CONNECTION_LINK_KEY_COMPLETE:
- case bluetooth::hci::EventCode::CENTRAL_LINK_KEY_COMPLETE:
- case bluetooth::hci::EventCode::READ_REMOTE_SUPPORTED_FEATURES_COMPLETE:
- case bluetooth::hci::EventCode::READ_REMOTE_VERSION_INFORMATION_COMPLETE:
- case bluetooth::hci::EventCode::QOS_SETUP_COMPLETE:
- case bluetooth::hci::EventCode::COMMAND_COMPLETE:
- case bluetooth::hci::EventCode::COMMAND_STATUS:
- case bluetooth::hci::EventCode::HARDWARE_ERROR:
- case bluetooth::hci::EventCode::FLUSH_OCCURRED:
- case bluetooth::hci::EventCode::ROLE_CHANGE:
- case bluetooth::hci::EventCode::NUMBER_OF_COMPLETED_PACKETS:
- case bluetooth::hci::EventCode::MODE_CHANGE:
- case bluetooth::hci::EventCode::RETURN_LINK_KEYS:
- case bluetooth::hci::EventCode::PIN_CODE_REQUEST:
- case bluetooth::hci::EventCode::LINK_KEY_REQUEST:
- case bluetooth::hci::EventCode::LINK_KEY_NOTIFICATION:
- case bluetooth::hci::EventCode::LOOPBACK_COMMAND:
- case bluetooth::hci::EventCode::DATA_BUFFER_OVERFLOW:
- case bluetooth::hci::EventCode::MAX_SLOTS_CHANGE:
- case bluetooth::hci::EventCode::READ_CLOCK_OFFSET_COMPLETE:
- case bluetooth::hci::EventCode::CONNECTION_PACKET_TYPE_CHANGED:
- case bluetooth::hci::EventCode::QOS_VIOLATION:
- case bluetooth::hci::EventCode::PAGE_SCAN_REPETITION_MODE_CHANGE:
- case bluetooth::hci::EventCode::FLOW_SPECIFICATION_COMPLETE:
- case bluetooth::hci::EventCode::INQUIRY_RESULT_WITH_RSSI:
- case bluetooth::hci::EventCode::READ_REMOTE_EXTENDED_FEATURES_COMPLETE:
- case bluetooth::hci::EventCode::SYNCHRONOUS_CONNECTION_COMPLETE:
- case bluetooth::hci::EventCode::SYNCHRONOUS_CONNECTION_CHANGED:
- case bluetooth::hci::EventCode::SNIFF_SUBRATING:
- case bluetooth::hci::EventCode::EXTENDED_INQUIRY_RESULT:
- case bluetooth::hci::EventCode::ENCRYPTION_KEY_REFRESH_COMPLETE:
- case bluetooth::hci::EventCode::IO_CAPABILITY_REQUEST:
- case bluetooth::hci::EventCode::IO_CAPABILITY_RESPONSE:
- case bluetooth::hci::EventCode::USER_CONFIRMATION_REQUEST:
- case bluetooth::hci::EventCode::USER_PASSKEY_REQUEST:
- case bluetooth::hci::EventCode::REMOTE_OOB_DATA_REQUEST:
- case bluetooth::hci::EventCode::SIMPLE_PAIRING_COMPLETE:
- case bluetooth::hci::EventCode::LINK_SUPERVISION_TIMEOUT_CHANGED:
- case bluetooth::hci::EventCode::ENHANCED_FLUSH_COMPLETE:
- case bluetooth::hci::EventCode::USER_PASSKEY_NOTIFICATION:
- case bluetooth::hci::EventCode::KEYPRESS_NOTIFICATION:
- case bluetooth::hci::EventCode::REMOTE_HOST_SUPPORTED_FEATURES_NOTIFICATION:
- case bluetooth::hci::EventCode::NUMBER_OF_COMPLETED_DATA_BLOCKS:
- return true;
- case bluetooth::hci::EventCode::VENDOR_SPECIFIC:
- case bluetooth::hci::EventCode::LE_META_EVENT: // Private to hci
- return false;
- }
- return false;
-};
-
-bool is_valid_subevent_code(bluetooth::hci::SubeventCode subevent_code) {
- switch (subevent_code) {
- case bluetooth::hci::SubeventCode::CONNECTION_COMPLETE:
- case bluetooth::hci::SubeventCode::CONNECTION_UPDATE_COMPLETE:
- case bluetooth::hci::SubeventCode::DATA_LENGTH_CHANGE:
- case bluetooth::hci::SubeventCode::ENHANCED_CONNECTION_COMPLETE:
- case bluetooth::hci::SubeventCode::PHY_UPDATE_COMPLETE:
- case bluetooth::hci::SubeventCode::READ_REMOTE_FEATURES_COMPLETE:
- case bluetooth::hci::SubeventCode::REMOTE_CONNECTION_PARAMETER_REQUEST:
- case bluetooth::hci::SubeventCode::READ_LOCAL_P256_PUBLIC_KEY_COMPLETE:
- case bluetooth::hci::SubeventCode::GENERATE_DHKEY_COMPLETE:
- case bluetooth::hci::SubeventCode::DIRECTED_ADVERTISING_REPORT:
- case bluetooth::hci::SubeventCode::EXTENDED_ADVERTISING_REPORT:
- case bluetooth::hci::SubeventCode::PERIODIC_ADVERTISING_SYNC_ESTABLISHED:
- case bluetooth::hci::SubeventCode::PERIODIC_ADVERTISING_REPORT:
- case bluetooth::hci::SubeventCode::PERIODIC_ADVERTISING_SYNC_LOST:
- case bluetooth::hci::SubeventCode::SCAN_TIMEOUT:
- case bluetooth::hci::SubeventCode::ADVERTISING_SET_TERMINATED:
- case bluetooth::hci::SubeventCode::SCAN_REQUEST_RECEIVED:
- case bluetooth::hci::SubeventCode::CHANNEL_SELECTION_ALGORITHM:
- case bluetooth::hci::SubeventCode::CONNECTIONLESS_IQ_REPORT:
- case bluetooth::hci::SubeventCode::CONNECTION_IQ_REPORT:
- case bluetooth::hci::SubeventCode::CTE_REQUEST_FAILED:
- case bluetooth::hci::SubeventCode::
- PERIODIC_ADVERTISING_SYNC_TRANSFER_RECEIVED:
- case bluetooth::hci::SubeventCode::CIS_ESTABLISHED:
- case bluetooth::hci::SubeventCode::CIS_REQUEST:
- case bluetooth::hci::SubeventCode::CREATE_BIG_COMPLETE:
- case bluetooth::hci::SubeventCode::TERMINATE_BIG_COMPLETE:
- case bluetooth::hci::SubeventCode::BIG_SYNC_ESTABLISHED:
- case bluetooth::hci::SubeventCode::BIG_SYNC_LOST:
- case bluetooth::hci::SubeventCode::REQUEST_PEER_SCA_COMPLETE:
- case bluetooth::hci::SubeventCode::PATH_LOSS_THRESHOLD:
- case bluetooth::hci::SubeventCode::TRANSMIT_POWER_REPORTING:
- case bluetooth::hci::SubeventCode::BIG_INFO_ADVERTISING_REPORT:
- case bluetooth::hci::SubeventCode::ADVERTISING_REPORT:
- case bluetooth::hci::SubeventCode::LONG_TERM_KEY_REQUEST:
+bool IsCommandStatusOpcode(bluetooth::hci::OpCode op_code) {
+ switch (op_code) {
+ case bluetooth::hci::OpCode::INQUIRY:
+ case bluetooth::hci::OpCode::CREATE_CONNECTION:
+ case bluetooth::hci::OpCode::DISCONNECT:
+ case bluetooth::hci::OpCode::ACCEPT_CONNECTION_REQUEST:
+ case bluetooth::hci::OpCode::REJECT_CONNECTION_REQUEST:
+ case bluetooth::hci::OpCode::CHANGE_CONNECTION_PACKET_TYPE:
+ case bluetooth::hci::OpCode::AUTHENTICATION_REQUESTED:
+ case bluetooth::hci::OpCode::SET_CONNECTION_ENCRYPTION:
+ case bluetooth::hci::OpCode::CHANGE_CONNECTION_LINK_KEY:
+ case bluetooth::hci::OpCode::MASTER_LINK_KEY:
+ case bluetooth::hci::OpCode::REMOTE_NAME_REQUEST:
+ case bluetooth::hci::OpCode::READ_REMOTE_SUPPORTED_FEATURES:
+ case bluetooth::hci::OpCode::READ_REMOTE_EXTENDED_FEATURES:
+ case bluetooth::hci::OpCode::READ_REMOTE_VERSION_INFORMATION:
+ case bluetooth::hci::OpCode::READ_CLOCK_OFFSET:
+ case bluetooth::hci::OpCode::SETUP_SYNCHRONOUS_CONNECTION:
+ case bluetooth::hci::OpCode::ACCEPT_SYNCHRONOUS_CONNECTION:
+ case bluetooth::hci::OpCode::REJECT_SYNCHRONOUS_CONNECTION:
+ case bluetooth::hci::OpCode::ENHANCED_SETUP_SYNCHRONOUS_CONNECTION:
+ case bluetooth::hci::OpCode::ENHANCED_ACCEPT_SYNCHRONOUS_CONNECTION:
+ case bluetooth::hci::OpCode::HOLD_MODE:
+ case bluetooth::hci::OpCode::SNIFF_MODE:
+ case bluetooth::hci::OpCode::EXIT_SNIFF_MODE:
+ case bluetooth::hci::OpCode::QOS_SETUP:
+ case bluetooth::hci::OpCode::SWITCH_ROLE:
+ case bluetooth::hci::OpCode::FLOW_SPECIFICATION:
+ case bluetooth::hci::OpCode::REFRESH_ENCRYPTION_KEY:
+ case bluetooth::hci::OpCode::LE_CREATE_CONNECTION:
+ case bluetooth::hci::OpCode::LE_CONNECTION_UPDATE:
+ case bluetooth::hci::OpCode::LE_READ_REMOTE_FEATURES:
+ case bluetooth::hci::OpCode::LE_READ_LOCAL_P_256_PUBLIC_KEY_COMMAND:
+ case bluetooth::hci::OpCode::LE_GENERATE_DHKEY_COMMAND:
+ case bluetooth::hci::OpCode::LE_SET_PHY:
+ case bluetooth::hci::OpCode::LE_EXTENDED_CREATE_CONNECTION:
+ case bluetooth::hci::OpCode::LE_PERIODIC_ADVERTISING_CREATE_SYNC:
return true;
default:
return false;
}
}
-static bool event_already_registered_in_hci_layer(
- bluetooth::hci::EventCode event_code) {
- switch (event_code) {
- case bluetooth::hci::EventCode::COMMAND_COMPLETE:
- case bluetooth::hci::EventCode::COMMAND_STATUS:
- case bluetooth::hci::EventCode::PAGE_SCAN_REPETITION_MODE_CHANGE:
- case bluetooth::hci::EventCode::MAX_SLOTS_CHANGE:
- case bluetooth::hci::EventCode::LE_META_EVENT:
- return bluetooth::shim::is_gd_hci_enabled() ||
- bluetooth::shim::is_gd_acl_enabled() ||
- bluetooth::shim::is_gd_l2cap_enabled();
- case bluetooth::hci::EventCode::DISCONNECTION_COMPLETE:
- case bluetooth::hci::EventCode::READ_REMOTE_VERSION_INFORMATION_COMPLETE:
- return bluetooth::shim::is_gd_acl_enabled() ||
- bluetooth::shim::is_gd_l2cap_enabled();
- default:
- return false;
- }
-}
-
-static bool event_already_registered_in_controller_layer(
- bluetooth::hci::EventCode event_code) {
- switch (event_code) {
- case bluetooth::hci::EventCode::NUMBER_OF_COMPLETED_PACKETS:
- return bluetooth::shim::is_gd_acl_enabled() ||
- bluetooth::shim::is_gd_l2cap_enabled();
- default:
- return false;
- }
-}
-
-static bool event_already_registered_in_acl_layer(
- bluetooth::hci::EventCode event_code) {
- for (auto event : bluetooth::hci::AclConnectionEvents) {
- if (event == event_code) {
- return bluetooth::shim::is_gd_acl_enabled() ||
- bluetooth::shim::is_gd_l2cap_enabled();
- }
- }
- return false;
-}
-
-static bool subevent_already_registered_in_le_hci_layer(
- bluetooth::hci::SubeventCode subevent_code) {
- switch (subevent_code) {
- case bluetooth::hci::SubeventCode::CONNECTION_COMPLETE:
- case bluetooth::hci::SubeventCode::CONNECTION_UPDATE_COMPLETE:
- case bluetooth::hci::SubeventCode::DATA_LENGTH_CHANGE:
- case bluetooth::hci::SubeventCode::ENHANCED_CONNECTION_COMPLETE:
- case bluetooth::hci::SubeventCode::PHY_UPDATE_COMPLETE:
- case bluetooth::hci::SubeventCode::REMOTE_CONNECTION_PARAMETER_REQUEST:
- return bluetooth::shim::is_gd_acl_enabled() ||
- bluetooth::shim::is_gd_l2cap_enabled() ||
- bluetooth::shim::is_gd_advertising_enabled() ||
- bluetooth::shim::is_gd_scanning_enabled();
- case bluetooth::hci::SubeventCode::ADVERTISING_SET_TERMINATED:
- case bluetooth::hci::SubeventCode::SCAN_REQUEST_RECEIVED:
- return bluetooth::shim::is_gd_acl_enabled() ||
- bluetooth::shim::is_gd_l2cap_enabled() ||
- bluetooth::shim::is_gd_advertising_enabled();
- case bluetooth::hci::SubeventCode::SCAN_TIMEOUT:
- case bluetooth::hci::SubeventCode::ADVERTISING_REPORT:
- case bluetooth::hci::SubeventCode::DIRECTED_ADVERTISING_REPORT:
- case bluetooth::hci::SubeventCode::EXTENDED_ADVERTISING_REPORT:
- case bluetooth::hci::SubeventCode::PERIODIC_ADVERTISING_REPORT:
- case bluetooth::hci::SubeventCode::PERIODIC_ADVERTISING_SYNC_ESTABLISHED:
- case bluetooth::hci::SubeventCode::PERIODIC_ADVERTISING_SYNC_LOST:
- return bluetooth::shim::is_gd_scanning_enabled();
- case bluetooth::hci::SubeventCode::READ_REMOTE_FEATURES_COMPLETE:
- case bluetooth::hci::SubeventCode::READ_LOCAL_P256_PUBLIC_KEY_COMPLETE:
- case bluetooth::hci::SubeventCode::GENERATE_DHKEY_COMPLETE:
- case bluetooth::hci::SubeventCode::CHANNEL_SELECTION_ALGORITHM:
- case bluetooth::hci::SubeventCode::CONNECTIONLESS_IQ_REPORT:
- case bluetooth::hci::SubeventCode::CONNECTION_IQ_REPORT:
- case bluetooth::hci::SubeventCode::CTE_REQUEST_FAILED:
- case bluetooth::hci::SubeventCode::
- PERIODIC_ADVERTISING_SYNC_TRANSFER_RECEIVED:
- case bluetooth::hci::SubeventCode::CIS_ESTABLISHED:
- case bluetooth::hci::SubeventCode::CIS_REQUEST:
- case bluetooth::hci::SubeventCode::CREATE_BIG_COMPLETE:
- case bluetooth::hci::SubeventCode::TERMINATE_BIG_COMPLETE:
- case bluetooth::hci::SubeventCode::BIG_SYNC_ESTABLISHED:
- case bluetooth::hci::SubeventCode::BIG_SYNC_LOST:
- case bluetooth::hci::SubeventCode::REQUEST_PEER_SCA_COMPLETE:
- case bluetooth::hci::SubeventCode::PATH_LOSS_THRESHOLD:
- case bluetooth::hci::SubeventCode::TRANSMIT_POWER_REPORTING:
- case bluetooth::hci::SubeventCode::BIG_INFO_ADVERTISING_REPORT:
- case bluetooth::hci::SubeventCode::LONG_TERM_KEY_REQUEST:
- default:
- return false;
- }
-}
-
-static bool event_already_registered_in_le_advertising_manager(
- bluetooth::hci::EventCode event_code) {
- for (auto event : bluetooth::hci::AclConnectionEvents) {
- if (event == event_code) {
- return bluetooth::shim::is_gd_advertising_enabled();
- }
- }
- return false;
-}
-
-static bool event_already_registered_in_le_scanning_manager(
- bluetooth::hci::EventCode event_code) {
- for (auto event : bluetooth::hci::AclConnectionEvents) {
- if (event == event_code) {
- return bluetooth::shim::is_gd_scanning_enabled();
- }
- }
- return false;
-}
-
-class OsiObject {
- public:
- OsiObject(void* ptr) : ptr_(ptr) {}
- ~OsiObject() {
- if (ptr_ != nullptr) {
- osi_free(ptr_);
- }
- }
- void* Release() {
- void* ptr = ptr_;
- ptr_ = nullptr;
- return ptr;
- }
-
- private:
- void* ptr_;
-};
-
-} // namespace
-
-namespace cpp {
-bluetooth::common::BidiQueueEnd<bluetooth::hci::AclBuilder,
- bluetooth::hci::AclView>* hci_queue_end =
- nullptr;
-static bluetooth::os::EnqueueBuffer<bluetooth::hci::AclBuilder>* pending_data =
- nullptr;
-
-static std::unique_ptr<bluetooth::packet::RawBuilder> MakeUniquePacket(
+std::unique_ptr<bluetooth::packet::RawBuilder> MakeUniquePacket(
const uint8_t* data, size_t len) {
bluetooth::packet::RawBuilder builder;
std::vector<uint8_t> bytes(data, data + len);
@@ -309,67 +102,59 @@ static std::unique_ptr<bluetooth::packet::RawBuilder> MakeUniquePacket(
return payload;
}
+} // namespace
-static BT_HDR* WrapPacketAndCopy(
- uint16_t event,
- bluetooth::hci::PacketView<bluetooth::hci::kLittleEndian>* data) {
- size_t packet_size = data->size() + kBtHdrSize;
- BT_HDR* packet = reinterpret_cast<BT_HDR*>(osi_malloc(packet_size));
- packet->offset = 0;
- packet->len = data->size();
- packet->layer_specific = 0;
- packet->event = event;
- std::copy(data->begin(), data->end(), packet->data);
- return packet;
-}
+static future_t* hci_module_shut_down(void);
+static future_t* hci_module_start_up(void);
-static void event_callback(bluetooth::hci::EventView event_packet_view) {
- if (!send_data_upwards) {
- return;
- }
- send_data_upwards.Run(FROM_HERE, WrapPacketAndCopy(MSG_HC_TO_STACK_HCI_EVT,
- &event_packet_view));
+EXPORT_SYMBOL extern const module_t gd_hci_module = {
+ .name = GD_HCI_MODULE,
+ .init = nullptr,
+ .start_up = hci_module_start_up,
+ .shut_down = hci_module_shut_down,
+ .clean_up = nullptr,
+ .dependencies = {GD_SHIM_MODULE, nullptr}};
+
+static future_t* hci_module_start_up(void) {
+ return nullptr;
}
-static void subevent_callback(
- bluetooth::hci::LeMetaEventView le_meta_event_view) {
- if (!send_data_upwards) {
- return;
- }
- send_data_upwards.Run(FROM_HERE, WrapPacketAndCopy(MSG_HC_TO_STACK_HCI_EVT,
- &le_meta_event_view));
+static future_t* hci_module_shut_down(void) {
+ return nullptr;
}
-static void vendor_specific_event_callback(
- bluetooth::hci::VendorSpecificEventView vendor_specific_event_view) {
- if (!send_data_upwards) {
- return;
- }
- send_data_upwards.Run(
- FROM_HERE,
- WrapPacketAndCopy(MSG_HC_TO_STACK_HCI_EVT, &vendor_specific_event_view));
+static void set_data_cb(
+ base::Callback<void(const base::Location&, BT_HDR*)> send_data_cb) {
+ send_data_upwards = std::move(send_data_cb);
}
void OnTransmitPacketCommandComplete(command_complete_cb complete_callback,
void* context,
bluetooth::hci::CommandCompleteView view) {
- LOG_DEBUG("Received cmd complete for %s",
- bluetooth::hci::OpCodeText(view.GetCommandOpCode()).c_str());
- std::vector<uint8_t> data(view.begin(), view.end());
- BT_HDR* response = WrapPacketAndCopy(MSG_HC_TO_STACK_HCI_EVT, &view);
+ std::vector<const uint8_t> data(view.begin(), view.end());
+
+ BT_HDR* response = static_cast<BT_HDR*>(osi_calloc(data.size() + kBtHdrSize));
+ std::copy(data.begin(), data.end(), response->data);
+ response->len = data.size();
+
complete_callback(response, context);
}
void OnTransmitPacketStatus(command_status_cb status_callback, void* context,
- std::unique_ptr<OsiObject> command,
bluetooth::hci::CommandStatusView view) {
- LOG_DEBUG("Received cmd status %s for %s",
- bluetooth::hci::ErrorCodeText(view.GetStatus()).c_str(),
- bluetooth::hci::OpCodeText(view.GetCommandOpCode()).c_str());
+ std::vector<const uint8_t> data(view.begin(), view.end());
+
+ BT_HDR* response = static_cast<BT_HDR*>(osi_calloc(data.size() + kBtHdrSize));
+ std::copy(data.begin(), data.end(), response->data);
+ response->len = data.size();
+
uint8_t status = static_cast<uint8_t>(view.GetStatus());
- status_callback(status, static_cast<BT_HDR*>(command->Release()), context);
+ status_callback(status, response, context);
}
+using bluetooth::common::BindOnce;
+using bluetooth::common::Unretained;
+
static void transmit_command(BT_HDR* command,
command_complete_cb complete_callback,
command_status_cb status_callback, void* context) {
@@ -385,411 +170,34 @@ static void transmit_command(BT_HDR* command,
data += (kCommandOpcodeSize + kCommandLengthSize);
len -= (kCommandOpcodeSize + kCommandLengthSize);
- auto op_code = static_cast<const bluetooth::hci::OpCode>(command_op_code);
+ const bluetooth::hci::OpCode op_code =
+ static_cast<const bluetooth::hci::OpCode>(command_op_code);
auto payload = MakeUniquePacket(data, len);
auto packet =
- bluetooth::hci::CommandBuilder::Create(op_code, std::move(payload));
-
- LOG_DEBUG("Sending command %s", bluetooth::hci::OpCodeText(op_code).c_str());
+ bluetooth::hci::CommandPacketBuilder::Create(op_code, std::move(payload));
- if (bluetooth::hci::Checker::IsCommandStatusOpcode(op_code)) {
- auto command_unique = std::make_unique<OsiObject>(command);
+ if (IsCommandStatusOpcode(op_code)) {
bluetooth::shim::GetHciLayer()->EnqueueCommand(
- std::move(packet), bluetooth::shim::GetGdShimHandler()->BindOnce(
- OnTransmitPacketStatus, status_callback, context,
- std::move(command_unique)));
+ std::move(packet),
+ BindOnce(OnTransmitPacketStatus, status_callback, context),
+ bluetooth::shim::GetGdShimHandler());
} else {
bluetooth::shim::GetHciLayer()->EnqueueCommand(
std::move(packet),
- bluetooth::shim::GetGdShimHandler()->BindOnce(
- OnTransmitPacketCommandComplete, complete_callback, context));
- osi_free(command);
- }
-}
-
-static void transmit_fragment(const uint8_t* stream, size_t length) {
- uint16_t handle_with_flags;
- STREAM_TO_UINT16(handle_with_flags, stream);
- auto pb_flag = static_cast<bluetooth::hci::PacketBoundaryFlag>(
- handle_with_flags >> 12 & 0b11);
- auto bc_flag =
- static_cast<bluetooth::hci::BroadcastFlag>(handle_with_flags >> 14);
- uint16_t handle = handle_with_flags & 0xEFF;
- length -= 2;
- // skip data total length
- stream += 2;
- length -= 2;
- auto payload = MakeUniquePacket(stream, length);
- auto acl_packet = bluetooth::hci::AclBuilder::Create(handle, pb_flag, bc_flag,
- std::move(payload));
- pending_data->Enqueue(std::move(acl_packet),
- bluetooth::shim::GetGdShimHandler());
-}
-
-static void register_event(bluetooth::hci::EventCode event_code) {
- auto handler = bluetooth::shim::GetGdShimHandler();
- bluetooth::shim::GetHciLayer()->RegisterEventHandler(
- event_code, handler->Bind(event_callback));
-}
-
-static void register_le_event(bluetooth::hci::SubeventCode subevent_code) {
- auto handler = bluetooth::shim::GetGdShimHandler();
- bluetooth::shim::GetHciLayer()->RegisterLeEventHandler(
- subevent_code, handler->Bind(subevent_callback));
-}
-
-static void acl_data_callback() {
- if (hci_queue_end == nullptr) {
- return;
- }
- auto packet = hci_queue_end->TryDequeue();
- ASSERT(packet != nullptr);
- if (!packet->IsValid()) {
- LOG_INFO("Dropping invalid packet of size %zu", packet->size());
- return;
- }
- if (!send_data_upwards) {
- return;
- }
- auto data = WrapPacketAndCopy(MSG_HC_TO_STACK_HCI_ACL, packet.get());
- packet_fragmenter->reassemble_and_dispatch(data);
-}
-
-static void register_for_acl() {
- hci_queue_end = bluetooth::shim::GetHciLayer()->GetAclQueueEnd();
-
- // if gd advertising/scanning enabled, hci_queue_end will be register in
- // AclManager::impl::Start
- if (!bluetooth::shim::is_gd_advertising_enabled() &&
- !bluetooth::shim::is_gd_scanning_enabled() &&
- !bluetooth::shim::is_gd_l2cap_enabled()) {
- hci_queue_end->RegisterDequeue(bluetooth::shim::GetGdShimHandler(),
- bluetooth::common::Bind(acl_data_callback));
- }
-
- pending_data = new bluetooth::os::EnqueueBuffer<bluetooth::hci::AclBuilder>(
- hci_queue_end);
-}
-
-static void on_shutting_down() {
- if (pending_data != nullptr) {
- pending_data->Clear();
- delete pending_data;
- pending_data = nullptr;
- }
- if (hci_queue_end != nullptr) {
- if (!bluetooth::shim::is_gd_advertising_enabled() &&
- !bluetooth::shim::is_gd_l2cap_enabled()) {
- hci_queue_end->UnregisterDequeue();
- }
- for (uint16_t event_code_raw = 0; event_code_raw < 0x100;
- event_code_raw++) {
- auto event_code = static_cast<bluetooth::hci::EventCode>(event_code_raw);
- if (!is_valid_event_code(event_code)) {
- continue;
- }
- if (event_already_registered_in_hci_layer(event_code)) {
- continue;
- } else if (event_already_registered_in_le_advertising_manager(
- event_code)) {
- continue;
- } else if (event_already_registered_in_le_scanning_manager(event_code)) {
- continue;
- }
- bluetooth::shim::GetHciLayer()->UnregisterEventHandler(event_code);
- }
- hci_queue_end = nullptr;
- }
-}
-
-} // namespace cpp
-
-using bluetooth::common::Bind;
-using bluetooth::common::BindOnce;
-using bluetooth::common::Unretained;
-
-namespace rust {
-
-using bluetooth::shim::rust::u8SliceCallback;
-using bluetooth::shim::rust::u8SliceOnceCallback;
-
-static BT_HDR* WrapRustPacketAndCopy(uint16_t event,
- ::rust::Slice<const uint8_t>* data) {
- size_t packet_size = data->length() + kBtHdrSize;
- BT_HDR* packet = reinterpret_cast<BT_HDR*>(osi_malloc(packet_size));
- packet->offset = 0;
- packet->len = data->length();
- packet->layer_specific = 0;
- packet->event = event;
- std::copy(data->data(), data->data() + data->length(), packet->data);
- return packet;
-}
-
-static void on_acl(::rust::Slice<const uint8_t> data) {
- if (!send_data_upwards) {
- return;
- }
- auto legacy_data = WrapRustPacketAndCopy(MSG_HC_TO_STACK_HCI_ACL, &data);
- packet_fragmenter->reassemble_and_dispatch(legacy_data);
-}
-
-static void on_event(::rust::Slice<const uint8_t> data) {
- if (!send_data_upwards) {
- return;
- }
- send_data_upwards.Run(FROM_HERE,
- WrapRustPacketAndCopy(MSG_HC_TO_STACK_HCI_EVT, &data));
-}
-
-void OnRustTransmitPacketCommandComplete(command_complete_cb complete_callback,
- void* context,
- ::rust::Slice<const uint8_t> data) {
- BT_HDR* response = WrapRustPacketAndCopy(MSG_HC_TO_STACK_HCI_EVT, &data);
- complete_callback(response, context);
-}
-
-void OnRustTransmitPacketStatus(command_status_cb status_callback,
- void* context,
- std::unique_ptr<OsiObject> command,
- ::rust::Slice<const uint8_t> data) {
- ASSERT(data.length() >= 3);
- uint8_t status = data.data()[2];
- status_callback(status, static_cast<BT_HDR*>(command->Release()), context);
-}
-
-static void transmit_command(BT_HDR* command,
- command_complete_cb complete_callback,
- command_status_cb status_callback, void* context) {
- CHECK(command != nullptr);
- const uint8_t* data = command->data + command->offset;
- size_t len = command->len;
- CHECK(len >= (kCommandOpcodeSize + kCommandLengthSize));
-
- // little endian command opcode
- uint16_t command_op_code = (data[1] << 8 | data[0]);
- auto op_code = static_cast<const bluetooth::hci::OpCode>(command_op_code);
-
- LOG_DEBUG("Sending command %s", bluetooth::hci::OpCodeText(op_code).c_str());
-
- if (bluetooth::hci::Checker::IsCommandStatusOpcode(op_code)) {
- auto command_unique = std::make_unique<OsiObject>(command);
- bluetooth::shim::rust::hci_send_command(
- **bluetooth::shim::Stack::Stack::GetInstance()->GetRustHci(),
- ::rust::Slice(data, len),
- std::make_unique<u8SliceOnceCallback>(
- BindOnce(OnRustTransmitPacketStatus, status_callback, context,
- std::move(command_unique))));
- } else {
- bluetooth::shim::rust::hci_send_command(
- **bluetooth::shim::Stack::Stack::GetInstance()->GetRustHci(),
- ::rust::Slice(data, len),
- std::make_unique<u8SliceOnceCallback>(BindOnce(
- OnRustTransmitPacketCommandComplete, complete_callback, context)));
- osi_free(command);
- }
-}
-
-static void transmit_fragment(const uint8_t* stream, size_t length) {
- bluetooth::shim::rust::hci_send_acl(
- **bluetooth::shim::Stack::Stack::GetInstance()->GetRustHci(),
- ::rust::Slice(stream, length));
-}
-
-static void register_event(bluetooth::hci::EventCode event_code) {
- bluetooth::shim::rust::hci_register_event(
- **bluetooth::shim::Stack::GetInstance()->GetRustHci(),
- static_cast<uint8_t>(event_code));
-}
-
-static void register_le_event(bluetooth::hci::SubeventCode subevent_code) {
- bluetooth::shim::rust::hci_register_le_event(
- **bluetooth::shim::Stack::Stack::GetInstance()->GetRustHci(),
- static_cast<uint8_t>(subevent_code));
-}
-
-static void hci_on_reset_complete() {
- bluetooth::shim::rust::hci_set_evt_callback(
- **bluetooth::shim::Stack::GetInstance()->GetRustHci(),
- std::make_unique<u8SliceCallback>(Bind(rust::on_event)));
- bluetooth::shim::rust::hci_set_le_evt_callback(
- **bluetooth::shim::Stack::GetInstance()->GetRustHci(),
- std::make_unique<u8SliceCallback>(Bind(rust::on_event)));
-}
-
-static void register_for_acl() {
- bluetooth::shim::rust::hci_set_acl_callback(
- **bluetooth::shim::Stack::GetInstance()->GetRustHci(),
- std::make_unique<u8SliceCallback>(Bind(rust::on_acl)));
-}
-
-static void on_shutting_down() {}
-
-} // namespace rust
-
-static void set_data_cb(
- base::Callback<void(const base::Location&, BT_HDR*)> send_data_cb) {
- send_data_upwards = std::move(send_data_cb);
-}
-
-static void transmit_command(BT_HDR* command,
- command_complete_cb complete_callback,
- command_status_cb status_callback, void* context) {
- if (bluetooth::common::init_flags::gd_rust_is_enabled()) {
- rust::transmit_command(command, complete_callback, status_callback,
- context);
- } else {
- cpp::transmit_command(command, complete_callback, status_callback, context);
+ BindOnce(OnTransmitPacketCommandComplete, complete_callback, context),
+ bluetooth::shim::GetGdShimHandler());
}
}
-static void command_complete_callback(BT_HDR* response, void* context) {
- auto future = static_cast<future_t*>(context);
- future_ready(future, response);
-}
-
-static void command_status_callback(uint8_t status, BT_HDR* command,
- void* context) {
- LOG_ALWAYS_FATAL(
- "transmit_command_futured should only send command complete opcode");
-}
-
-static future_t* transmit_command_futured(BT_HDR* command) {
- future_t* future = future_new();
- transmit_command(command, command_complete_callback, command_status_callback,
- future);
- return future;
-}
-
-static void transmit_fragment(BT_HDR* packet, bool send_transmit_finished) {
- // HCI command packets are freed on a different thread when the matching
- // event is received. Check packet->event before sending to avoid a race.
- bool free_after_transmit =
- (packet->event & MSG_EVT_MASK) != MSG_STACK_TO_HC_HCI_CMD &&
- send_transmit_finished;
-
- const uint8_t* stream = packet->data + packet->offset;
- size_t length = packet->len;
- if (bluetooth::common::init_flags::gd_rust_is_enabled()) {
- rust::transmit_fragment(stream, length);
- } else {
- cpp::transmit_fragment(stream, length);
- }
- if (free_after_transmit) {
- osi_free(packet);
- }
-}
-static void dispatch_reassembled(BT_HDR* packet) {
- // Events should already have been dispatched before this point
- CHECK((packet->event & MSG_EVT_MASK) != MSG_HC_TO_STACK_HCI_EVT);
- CHECK(!send_data_upwards.is_null());
- send_data_upwards.Run(FROM_HERE, packet);
-}
-static void fragmenter_transmit_finished(BT_HDR* packet,
- bool all_fragments_sent) {
- if (all_fragments_sent) {
- osi_free(packet);
- } else {
- // This is kind of a weird case, since we're dispatching a partially sent
- // packet up to a higher layer.
- // TODO(zachoverflow): rework upper layer so this isn't necessary.
- send_data_upwards.Run(FROM_HERE, packet);
- }
-}
-
-static const packet_fragmenter_callbacks_t packet_fragmenter_callbacks = {
- transmit_fragment, dispatch_reassembled, fragmenter_transmit_finished};
-
-static void transmit_downward(uint16_t type, void* raw_data) {
- if (bluetooth::common::init_flags::gd_rust_is_enabled()) {
- packet_fragmenter->fragment_and_dispatch(static_cast<BT_HDR*>(raw_data));
- } else {
- bluetooth::shim::GetGdShimHandler()->Call(
- packet_fragmenter->fragment_and_dispatch,
- static_cast<BT_HDR*>(raw_data));
- }
-}
-
-static hci_t interface = {.set_data_cb = set_data_cb,
- .transmit_command = transmit_command,
- .transmit_command_futured = transmit_command_futured,
- .transmit_downward = transmit_downward};
-
const hci_t* bluetooth::shim::hci_layer_get_interface() {
- packet_fragmenter = packet_fragmenter_get_interface();
- packet_fragmenter->init(&packet_fragmenter_callbacks);
- return &interface;
-}
-
-void bluetooth::shim::hci_on_reset_complete() {
- ASSERT(send_data_upwards);
- if (bluetooth::common::init_flags::gd_rust_is_enabled()) {
- ::rust::hci_on_reset_complete();
- }
-
- for (uint16_t event_code_raw = 0; event_code_raw < 0x100; event_code_raw++) {
- auto event_code = static_cast<bluetooth::hci::EventCode>(event_code_raw);
- if (!is_valid_event_code(event_code)) {
- continue;
- }
- if (event_already_registered_in_acl_layer(event_code)) {
- continue;
- } else if (event_already_registered_in_controller_layer(event_code)) {
- continue;
- } else if (event_already_registered_in_hci_layer(event_code)) {
- continue;
- } else if (event_already_registered_in_le_advertising_manager(event_code)) {
- continue;
- } else if (event_already_registered_in_le_scanning_manager(event_code)) {
- continue;
- }
-
- if (bluetooth::common::init_flags::gd_rust_is_enabled()) {
- ::rust::register_event(event_code);
- } else {
- cpp::register_event(event_code);
- }
- }
-
- for (uint16_t subevent_code_raw = 0; subevent_code_raw < 0x100;
- subevent_code_raw++) {
- auto subevent_code =
- static_cast<bluetooth::hci::SubeventCode>(subevent_code_raw);
- if (!is_valid_subevent_code(subevent_code)) {
- continue;
- }
- if (subevent_already_registered_in_le_hci_layer(subevent_code)) {
- continue;
- }
-
- if (bluetooth::common::init_flags::gd_rust_is_enabled()) {
- ::rust::register_le_event(subevent_code);
- } else {
- cpp::register_le_event(subevent_code);
- }
- }
-
- // TODO handle BQR event in GD
- auto handler = bluetooth::shim::GetGdShimHandler();
- bluetooth::shim::GetVendorSpecificEventManager()->RegisterEventHandler(
- bluetooth::hci::VseSubeventCode::BQR_EVENT,
- handler->Bind(cpp::vendor_specific_event_callback));
-
- if (bluetooth::shim::is_gd_acl_enabled()) {
- return;
- }
-
- if (bluetooth::common::init_flags::gd_rust_is_enabled()) {
- ::rust::register_for_acl();
- } else {
- cpp::register_for_acl();
- }
-}
-
-void bluetooth::shim::hci_on_shutting_down() {
- if (bluetooth::common::init_flags::gd_rust_is_enabled()) {
- ::rust::on_shutting_down();
- } else {
- cpp::on_shutting_down();
+ static bool loaded = false;
+ if (!loaded) {
+ loaded = true;
+ interface.set_data_cb = set_data_cb;
+ interface.transmit_command = transmit_command;
+ interface.transmit_command_futured = nullptr;
+ interface.transmit_downward = nullptr;
}
+ return &interface;
}
diff --git a/main/shim/hci_layer.h b/main/shim/hci_layer.h
index b9a29e9f1..6b0bbcc76 100644
--- a/main/shim/hci_layer.h
+++ b/main/shim/hci_layer.h
@@ -21,14 +21,12 @@
#include "hci/include/hci_layer.h"
+static const char GD_HCI_MODULE[] = "gd_hci_module";
+
namespace bluetooth {
namespace shim {
const hci_t* hci_layer_get_interface();
-void hci_on_reset_complete();
-
-void hci_on_shutting_down();
-
} // namespace shim
} // namespace bluetooth
diff --git a/main/shim/helpers.h b/main/shim/helpers.h
index d2416b3b8..5beb09fce 100644
--- a/main/shim/helpers.h
+++ b/main/shim/helpers.h
@@ -13,46 +13,15 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-#pragma once
#include "hci/address_with_type.h"
-#include "gd/common/init_flags.h"
-#include "gd/packet/raw_builder.h"
-#include "osi/include/allocator.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcidefs.h"
-#include "types/ble_address_with_type.h"
-#include "types/hci_role.h"
-
namespace bluetooth {
-inline RawAddress ToRawAddress(const hci::Address& address) {
- RawAddress ret;
- ret.address[0] = address.address[5];
- ret.address[1] = address.address[4];
- ret.address[2] = address.address[3];
- ret.address[3] = address.address[2];
- ret.address[4] = address.address[1];
- ret.address[5] = address.address[0];
- return ret;
-}
-
-inline hci::Address ToGdAddress(const RawAddress& address) {
- hci::Address ret;
- ret.address[0] = address.address[5];
- ret.address[1] = address.address[4];
- ret.address[2] = address.address[3];
- ret.address[3] = address.address[2];
- ret.address[4] = address.address[1];
- ret.address[5] = address.address[0];
- return ret;
-}
-
-inline hci::AddressWithType ToAddressWithType(
- const RawAddress& legacy_address, const tBLE_ADDR_TYPE& legacy_type) {
- hci::Address address = ToGdAddress(legacy_address);
+hci::AddressWithType ToAddressWithType(const RawAddress& legacy_address,
+ tBLE_ADDR_TYPE legacy_type) {
+ // Address and RawAddress are binary equivalent;
+ hci::Address address(legacy_address.address);
hci::AddressType type;
if (legacy_type == BLE_ADDR_PUBLIC)
@@ -64,209 +33,11 @@ inline hci::AddressWithType ToAddressWithType(
else if (legacy_type == BLE_ADDR_RANDOM_ID)
type = hci::AddressType::RANDOM_IDENTITY_ADDRESS;
else {
- LOG_ALWAYS_FATAL("Bad address type %02x", legacy_type);
+ LOG_ALWAYS_FATAL("Bad address type");
return hci::AddressWithType{address,
hci::AddressType::PUBLIC_DEVICE_ADDRESS};
}
return hci::AddressWithType{address, type};
}
-
-inline hci::AddressWithType ToAddressWithTypeFromLegacy(
- const tBLE_BD_ADDR& legacy_address_with_type) {
- return ToAddressWithType(legacy_address_with_type.bda,
- legacy_address_with_type.type);
-}
-
-inline tBLE_BD_ADDR ToLegacyAddressWithType(
- const hci::AddressWithType& address_with_type) {
- tBLE_BD_ADDR legacy_address_with_type;
- legacy_address_with_type.bda = ToRawAddress(address_with_type.GetAddress());
-
- if (address_with_type.GetAddressType() ==
- hci::AddressType::PUBLIC_DEVICE_ADDRESS) {
- legacy_address_with_type.type = BLE_ADDR_PUBLIC;
- } else if (address_with_type.GetAddressType() ==
- hci::AddressType::RANDOM_DEVICE_ADDRESS) {
- legacy_address_with_type.type = BLE_ADDR_RANDOM;
- } else if (address_with_type.GetAddressType() ==
- hci::AddressType::PUBLIC_IDENTITY_ADDRESS) {
- legacy_address_with_type.type = BLE_ADDR_PUBLIC_ID;
- } else if (address_with_type.GetAddressType() ==
- hci::AddressType::RANDOM_IDENTITY_ADDRESS) {
- legacy_address_with_type.type = BLE_ADDR_RANDOM_ID;
- } else {
- LOG_ALWAYS_FATAL("%s Bad address type %02x", __func__,
- static_cast<uint8_t>(address_with_type.GetAddressType()));
- legacy_address_with_type.type = BLE_ADDR_PUBLIC;
- }
- return legacy_address_with_type;
-}
-
-inline std::unique_ptr<bluetooth::packet::RawBuilder> MakeUniquePacket(
- const uint8_t* data, size_t len, bool is_flushable) {
- bluetooth::packet::RawBuilder builder;
- std::vector<uint8_t> bytes(data, data + len);
- auto payload = std::make_unique<bluetooth::packet::RawBuilder>();
- payload->AddOctets(bytes);
- payload->SetFlushable(is_flushable);
- return payload;
-}
-
-inline BT_HDR* MakeLegacyBtHdrPacket(
- std::unique_ptr<bluetooth::hci::PacketView<bluetooth::hci::kLittleEndian>>
- packet,
- const std::vector<uint8_t>& preamble) {
- std::vector<uint8_t> packet_vector(packet->begin(), packet->end());
- BT_HDR* buffer = static_cast<BT_HDR*>(
- osi_calloc(packet_vector.size() + preamble.size() + sizeof(BT_HDR)));
- std::copy(preamble.begin(), preamble.end(), buffer->data);
- std::copy(packet_vector.begin(), packet_vector.end(),
- buffer->data + preamble.size());
- buffer->len = preamble.size() + packet_vector.size();
- return buffer;
-}
-
-inline tHCI_ROLE ToLegacyRole(hci::Role role) {
- return to_hci_role(static_cast<uint8_t>(role));
-}
-
-inline hci::Role ToHciRole(const hci_role_t& role) {
- switch (role) {
- case HCI_ROLE_CENTRAL:
- return hci::Role::CENTRAL;
- case HCI_ROLE_PERIPHERAL:
- return hci::Role::PERIPHERAL;
- default:
- ASSERT_LOG(false, "Unable to determine legacy role:%u", role);
- }
-}
-
-inline tHCI_STATUS ToLegacyHciErrorCode(const hci::ErrorCode& reason) {
- switch (reason) {
- case hci::ErrorCode::SUCCESS:
- return HCI_SUCCESS;
- case hci::ErrorCode::UNKNOWN_HCI_COMMAND:
- return HCI_ERR_ILLEGAL_COMMAND;
- case hci::ErrorCode::UNKNOWN_CONNECTION:
- return HCI_ERR_NO_CONNECTION;
- case hci::ErrorCode::HARDWARE_FAILURE:
- return HCI_ERR_HW_FAILURE;
- case hci::ErrorCode::PAGE_TIMEOUT:
- return HCI_ERR_PAGE_TIMEOUT;
- case hci::ErrorCode::AUTHENTICATION_FAILURE:
- return HCI_ERR_AUTH_FAILURE;
- case hci::ErrorCode::PIN_OR_KEY_MISSING:
- return HCI_ERR_KEY_MISSING;
- case hci::ErrorCode::MEMORY_CAPACITY_EXCEEDED:
- return HCI_ERR_MEMORY_FULL;
- case hci::ErrorCode::CONNECTION_TIMEOUT:
- return HCI_ERR_CONNECTION_TOUT;
- case hci::ErrorCode::CONNECTION_LIMIT_EXCEEDED:
- return HCI_ERR_MAX_NUM_OF_CONNECTIONS;
- case hci::ErrorCode::SYNCHRONOUS_CONNECTION_LIMIT_EXCEEDED:
- return HCI_ERR_MAX_NUM_OF_SCOS;
- case hci::ErrorCode::CONNECTION_ALREADY_EXISTS:
- return HCI_ERR_CONNECTION_EXISTS;
- case hci::ErrorCode::COMMAND_DISALLOWED:
- return HCI_ERR_COMMAND_DISALLOWED;
- case hci::ErrorCode::CONNECTION_REJECTED_LIMITED_RESOURCES:
- return HCI_ERR_HOST_REJECT_RESOURCES;
- case hci::ErrorCode::CONNECTION_REJECTED_SECURITY_REASONS:
- return HCI_ERR_HOST_REJECT_SECURITY;
- case hci::ErrorCode::CONNECTION_REJECTED_UNACCEPTABLE_BD_ADDR:
- return HCI_ERR_HOST_REJECT_DEVICE;
- case hci::ErrorCode::CONNECTION_ACCEPT_TIMEOUT:
- return HCI_ERR_HOST_TIMEOUT;
- case hci::ErrorCode::UNSUPORTED_FEATURE_OR_PARAMETER_VALUE:
- return static_cast<tHCI_STATUS>(
- hci::ErrorCode::UNSUPORTED_FEATURE_OR_PARAMETER_VALUE);
- case hci::ErrorCode::INVALID_HCI_COMMAND_PARAMETERS:
- return HCI_ERR_ILLEGAL_PARAMETER_FMT;
- case hci::ErrorCode::REMOTE_USER_TERMINATED_CONNECTION:
- return HCI_ERR_PEER_USER;
- case hci::ErrorCode::REMOTE_DEVICE_TERMINATED_CONNECTION_LOW_RESOURCES:
- return static_cast<tHCI_STATUS>(
- hci::ErrorCode::REMOTE_DEVICE_TERMINATED_CONNECTION_LOW_RESOURCES);
- case hci::ErrorCode::REMOTE_DEVICE_TERMINATED_CONNECTION_POWER_OFF:
- return static_cast<tHCI_STATUS>(
- hci::ErrorCode::REMOTE_DEVICE_TERMINATED_CONNECTION_POWER_OFF);
- case hci::ErrorCode::CONNECTION_TERMINATED_BY_LOCAL_HOST:
- return HCI_ERR_CONN_CAUSE_LOCAL_HOST;
- case hci::ErrorCode::REPEATED_ATTEMPTS:
- return HCI_ERR_REPEATED_ATTEMPTS;
- case hci::ErrorCode::PAIRING_NOT_ALLOWED:
- return HCI_ERR_PAIRING_NOT_ALLOWED;
- case hci::ErrorCode::UNKNOWN_LMP_PDU:
- return static_cast<tHCI_STATUS>(hci::ErrorCode::UNKNOWN_LMP_PDU);
- case hci::ErrorCode::UNSUPPORTED_REMOTE_OR_LMP_FEATURE:
- return HCI_ERR_UNSUPPORTED_REM_FEATURE;
- case hci::ErrorCode::SCO_OFFSET_REJECTED:
- return static_cast<tHCI_STATUS>(hci::ErrorCode::SCO_OFFSET_REJECTED);
- case hci::ErrorCode::SCO_INTERVAL_REJECTED:
- return static_cast<tHCI_STATUS>(hci::ErrorCode::SCO_INTERVAL_REJECTED);
- case hci::ErrorCode::SCO_AIR_MODE_REJECTED:
- return static_cast<tHCI_STATUS>(hci::ErrorCode::SCO_AIR_MODE_REJECTED);
- case hci::ErrorCode::INVALID_LMP_OR_LL_PARAMETERS:
- return static_cast<tHCI_STATUS>(
- hci::ErrorCode::INVALID_LMP_OR_LL_PARAMETERS);
- case hci::ErrorCode::UNSPECIFIED_ERROR:
- return HCI_ERR_UNSPECIFIED;
- case hci::ErrorCode::UNSUPPORTED_LMP_OR_LL_PARAMETER:
- return static_cast<tHCI_STATUS>(
- hci::ErrorCode::UNSUPPORTED_LMP_OR_LL_PARAMETER);
- case hci::ErrorCode::ROLE_CHANGE_NOT_ALLOWED:
- return static_cast<tHCI_STATUS>(hci::ErrorCode::ROLE_CHANGE_NOT_ALLOWED);
- case hci::ErrorCode::LINK_LAYER_COLLISION:
- return HCI_ERR_LMP_ERR_TRANS_COLLISION;
- case hci::ErrorCode::ENCRYPTION_MODE_NOT_ACCEPTABLE:
- return HCI_ERR_ENCRY_MODE_NOT_ACCEPTABLE;
- case hci::ErrorCode::ROLE_SWITCH_FAILED:
- return static_cast<tHCI_STATUS>(hci::ErrorCode::ROLE_SWITCH_FAILED);
- case hci::ErrorCode::CONTROLLER_BUSY:
- return static_cast<tHCI_STATUS>(hci::ErrorCode::CONTROLLER_BUSY);
- case hci::ErrorCode::CONNECTION_FAILED_ESTABLISHMENT:
- return static_cast<tHCI_STATUS>(
- hci::ErrorCode::CONNECTION_FAILED_ESTABLISHMENT);
- case hci::ErrorCode::STATUS_UNKNOWN:
- return HCI_ERR_UNDEFINED;
- default:
- return static_cast<tHCI_REASON>(reason);
- }
-}
-
-inline tHCI_MODE ToLegacyHciMode(const hci::Mode& mode) {
- return static_cast<tHCI_MODE>(mode);
-}
-
-inline hci::DisconnectReason ToDisconnectReasonFromLegacy(
- const tHCI_STATUS& reason) {
- return static_cast<hci::DisconnectReason>(reason);
-}
-
-inline bool IsPacketFlushable(const BT_HDR* p_buf) {
- ASSERT(p_buf != nullptr);
- return ToPacketData<const HciDataPreamble>(p_buf)->IsFlushable();
-}
-
-namespace debug {
-
-inline void DumpBtHdr(const BT_HDR* p_buf, const char* token) {
- uint16_t len = p_buf->len;
- char buf[255];
- const uint8_t* data = p_buf->data + p_buf->offset;
- int cnt = 0;
- while (len > 0) {
- memset(buf, 0, sizeof(buf));
- char* pbuf = buf;
- pbuf += sprintf(pbuf, "len:%5u %5d: ", p_buf->len, cnt);
- for (int j = 0; j < 16; j++, --len, data++, cnt++) {
- if (len == 0) break;
- pbuf += sprintf(pbuf, "0x%02x ", *data);
- }
- LOG_DEBUG("%s %s", token, buf);
- }
-}
-
-} // namespace debug
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/main/shim/l2c_api.cc b/main/shim/l2c_api.cc
index 370784484..e333e9cd1 100644
--- a/main/shim/l2c_api.cc
+++ b/main/shim/l2c_api.cc
@@ -16,1579 +16,292 @@
#define LOG_TAG "bt_shim_l2cap"
-#include <future>
-#include <unordered_map>
-#include <unordered_set>
-
-#include "bta/include/bta_dm_acl.h"
-#include "gd/l2cap/classic/l2cap_classic_module.h"
-#include "gd/l2cap/le/l2cap_le_module.h"
-#include "gd/os/log.h"
-#include "gd/os/queue.h"
-#include "main/shim/acl_api.h"
-#include "main/shim/btm.h"
-#include "main/shim/entry.h"
-#include "main/shim/helpers.h"
#include "main/shim/l2c_api.h"
-#include "main/shim/stack.h"
-#include "osi/include/allocator.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/acl_hci_link_interface.h"
-#include "stack/include/ble_acl_interface.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btu.h"
-#include "stack/include/gatt_api.h"
-#include "stack/include/sco_hci_link_interface.h"
-
-extern void gatt_notify_conn_update(const RawAddress& remote, uint16_t interval,
- uint16_t latency, uint16_t timeout,
- tHCI_STATUS status);
-extern void gatt_notify_phy_updated(tGATT_STATUS status, uint16_t handle,
- uint8_t tx_phy, uint8_t rx_phy);
-
-void process_ssr_event(tHCI_STATUS status, uint16_t handle, uint16_t max_tx_lat,
- uint16_t max_rx_lat);
-
-namespace bluetooth {
-namespace shim {
-
-using bluetooth::hci::AddressWithType;
-using namespace bluetooth::l2cap;
-
-// Classic Dynamic Channel Shim Helper
-
-namespace {
-uint16_t classic_cid_token_counter_ = 0x41;
-constexpr uint64_t kBrEdrNotSupportedMask = 0x0000002000000000; // Bit 37
-constexpr uint64_t kLeSupportedControllerMask = 0x0000004000000000; // Bit 38
-constexpr uint64_t kLeSupportedHostMask = 0x0000000000000002; // Bit 1
-
-std::unordered_map<uint16_t /* token */, uint16_t /* psm */>
- classic_cid_token_to_channel_map_;
-
-uint16_t add_classic_cid_token_entry(uint16_t psm) {
- uint16_t new_token = classic_cid_token_counter_;
- classic_cid_token_to_channel_map_[new_token] = psm;
- classic_cid_token_counter_++;
- if (classic_cid_token_counter_ == 0) classic_cid_token_counter_ = 0x41;
- return new_token;
-}
-
-void remove_classic_cid_token_entry(uint16_t cid_token) {
- classic_cid_token_to_channel_map_.erase(cid_token);
-}
-
-void remove_classic_dynamic_channel_helper(uint16_t psm);
-
-struct ClassicDynamicChannelHelper {
- ClassicDynamicChannelHelper(uint16_t psm, tL2CAP_APPL_INFO appl_info,
- classic::DynamicChannelConfigurationOption config,
- classic::SecurityPolicy policy)
- : psm_(psm), appl_info_(appl_info), config_(config), policy_(policy) {}
-
- uint16_t psm_;
- tL2CAP_APPL_INFO appl_info_;
- classic::DynamicChannelConfigurationOption config_;
- classic::SecurityPolicy policy_;
-
- void Register() {
- GetL2capClassicModule()->GetDynamicChannelManager()->RegisterService(
- psm_, config_, policy_,
- GetGdShimHandler()->BindOnceOn(
- this, &ClassicDynamicChannelHelper::on_registration_complete),
- GetGdShimHandler()->BindOn(
- this, &ClassicDynamicChannelHelper::on_channel_open, 0));
- }
-
- void on_registration_complete(
- classic::DynamicChannelManager::RegistrationResult result,
- std::unique_ptr<classic::DynamicChannelService> service) {
- if (result != classic::DynamicChannelManager::RegistrationResult::SUCCESS) {
- LOG(ERROR) << "Channel is not registered. psm=" << +psm_ << (int)result;
- return;
- }
- channel_service_ = std::move(service);
- }
-
- std::unique_ptr<classic::DynamicChannelService> channel_service_ = nullptr;
-
- void Connect(uint16_t cid_token, bluetooth::hci::AddressWithType device) {
- if (channel_service_ == nullptr) {
- return;
- }
- initiated_by_us_[cid_token] = true;
- GetL2capClassicModule()->GetDynamicChannelManager()->ConnectChannel(
- device.GetAddress(), config_, psm_,
- GetGdShimHandler()->BindOn(
- this, &ClassicDynamicChannelHelper::on_channel_open, cid_token),
- GetGdShimHandler()->BindOnceOn(
- this, &ClassicDynamicChannelHelper::on_outgoing_connection_fail));
- }
-
- void Disconnect(uint16_t cid_token) {
- if (channel_service_ == nullptr) {
- return;
- }
- if (channels_.count(cid_token) == 0) {
- return;
- }
- channels_[cid_token]->Close();
- }
-
- void Unregister() {
- if (channel_service_ != nullptr) {
- channel_service_->Unregister(GetGdShimHandler()->BindOnceOn(
- this, &ClassicDynamicChannelHelper::on_unregistered));
- channel_service_ = nullptr;
- }
- }
-
- void on_unregistered() {
- for (const auto& device : channels_) {
- device.second->Close();
- }
- remove_classic_dynamic_channel_helper(psm_);
- }
-
- void on_channel_close(uint16_t cid_token,
- bluetooth::hci::ErrorCode error_code) {
- channel_enqueue_buffer_[cid_token] = nullptr;
- channel_enqueue_buffer_.erase(cid_token);
- channels_[cid_token]->GetQueueUpEnd()->UnregisterDequeue();
- channels_.erase(cid_token);
- do_in_main_thread(FROM_HERE, base::Bind(appl_info_.pL2CA_DisconnectInd_Cb,
- cid_token, false));
-
- remove_classic_cid_token_entry(cid_token);
- initiated_by_us_.erase(cid_token);
-
- if (channel_service_ == nullptr && channels_.empty()) {
- // Try again
- L2CA_Deregister(psm_);
- }
- }
-
- void on_channel_open(uint16_t cid_token,
- std::unique_ptr<classic::DynamicChannel> channel) {
- auto device = channel->GetDevice();
- auto address = bluetooth::ToRawAddress(device.GetAddress());
- bool initiator_local = (cid_token != 0);
- if (cid_token == 0) {
- cid_token = add_classic_cid_token_entry(psm_);
- }
-
- channel->RegisterOnCloseCallback(GetGdShimHandler()->BindOnceOn(
- this, &ClassicDynamicChannelHelper::on_channel_close, cid_token));
-
- channel_enqueue_buffer_[cid_token] = std::make_unique<
- bluetooth::os::EnqueueBuffer<bluetooth::packet::BasePacketBuilder>>(
- channel->GetQueueUpEnd());
-
- if (initiator_local) {
- do_in_main_thread(
- FROM_HERE, base::Bind(appl_info_.pL2CA_ConnectCfm_Cb, cid_token, 0));
-
- tL2CAP_CFG_INFO cfg_info{};
- do_in_main_thread(FROM_HERE, base::Bind(appl_info_.pL2CA_ConfigCfm_Cb,
- cid_token, L2CAP_INITIATOR_LOCAL,
- base::Unretained(&cfg_info)));
- } else {
- if (appl_info_.pL2CA_ConnectInd_Cb == nullptr) {
- Disconnect(cid_token);
- return;
- }
- do_in_main_thread(FROM_HERE, base::Bind(appl_info_.pL2CA_ConnectInd_Cb,
- address, cid_token, psm_, 0));
-
- tL2CAP_CFG_INFO cfg_info{};
- do_in_main_thread(FROM_HERE, base::Bind(appl_info_.pL2CA_ConfigCfm_Cb,
- cid_token, L2CAP_INITIATOR_LOCAL,
- base::Unretained(&cfg_info)));
- }
-
- channel->GetQueueUpEnd()->RegisterDequeue(
- GetGdShimHandler(),
- bluetooth::common::Bind(&ClassicDynamicChannelHelper::on_incoming_data,
- bluetooth::common::Unretained(this),
- cid_token));
-
- channels_[cid_token] = std::move(channel);
- }
-
- void on_incoming_data(uint16_t cid_token) {
- auto channel = channels_.find(cid_token);
- if (channel == channels_.end()) {
- LOG_ERROR("Channel is not open");
- return;
- }
- auto packet = channel->second->GetQueueUpEnd()->TryDequeue();
- std::vector<uint8_t> packet_vector(packet->begin(), packet->end());
- BT_HDR* buffer =
- static_cast<BT_HDR*>(osi_calloc(packet_vector.size() + sizeof(BT_HDR)));
- std::copy(packet_vector.begin(), packet_vector.end(), buffer->data);
- buffer->len = packet_vector.size();
- if (do_in_main_thread(FROM_HERE,
- base::Bind(appl_info_.pL2CA_DataInd_Cb, cid_token,
- base::Unretained(buffer))) !=
- BT_STATUS_SUCCESS) {
- osi_free(buffer);
- }
- }
-
- void on_outgoing_connection_fail(
- classic::DynamicChannelManager::ConnectionResult result) {
- LOG(ERROR) << "Outgoing connection failed: "
- << static_cast<int>(result.connection_result_code);
- }
-
- bool send(uint16_t cid,
- std::unique_ptr<bluetooth::packet::BasePacketBuilder> packet) {
- auto buffer = channel_enqueue_buffer_.find(cid);
- if (buffer == channel_enqueue_buffer_.end() || buffer->second == nullptr) {
- LOG(ERROR) << "Channel is not open";
- return false;
- }
- buffer->second->Enqueue(std::move(packet), GetGdShimHandler());
- return true;
- }
-
- uint16_t GetRemoteCid(uint16_t cid) {
- auto channel = channels_.find(cid);
- if (channel == channels_.end()) {
- LOG_ERROR("Channel is not open");
- return 0;
- }
- return channel->second->HACK_GetRemoteCid();
- }
-
- bool SetChannelTxPriority(uint16_t cid, bool high_priority) {
- auto channel = channels_.find(cid);
- if (channel == channels_.end()) {
- LOG_ERROR("Channel is not open");
- return false;
- }
- channel->second->HACK_SetChannelTxPriority(high_priority);
- return true;
- }
-
- void FlushChannel(uint16_t cid) {
- auto buffer = channel_enqueue_buffer_.find(cid);
- if (buffer == channel_enqueue_buffer_.end()) {
- LOG_ERROR("Channel is not open");
- return;
- }
- buffer->second->Clear();
- }
-
- uint16_t GetNumBufferedPackets(uint16_t cid) {
- auto buffer = channel_enqueue_buffer_.find(cid);
- if (buffer == channel_enqueue_buffer_.end()) {
- LOG_ERROR("Channel is not open");
- return 0;
- }
- return buffer->second->Size();
- }
-
- std::unordered_map<uint16_t, std::unique_ptr<classic::DynamicChannel>>
- channels_;
- std::unordered_map<uint16_t, std::unique_ptr<bluetooth::os::EnqueueBuffer<
- bluetooth::packet::BasePacketBuilder>>>
- channel_enqueue_buffer_;
- std::unordered_map<uint16_t, bool> initiated_by_us_;
-};
-
-std::unordered_map<uint16_t, std::unique_ptr<ClassicDynamicChannelHelper>>
- classic_dynamic_channel_helper_map_;
-
-void remove_classic_dynamic_channel_helper(uint16_t psm) {
- if (classic_dynamic_channel_helper_map_.count(psm) != 0 &&
- classic_dynamic_channel_helper_map_[psm]->channels_.empty()) {
- classic_dynamic_channel_helper_map_.erase(psm);
- }
-}
-
-// Helper: L2cap security enforcement shim
-
-std::unordered_map<intptr_t,
- bluetooth::common::ContextualOnceCallback<void(bool)>>
- security_enforce_callback_map = {};
-
-class ClassicSecurityEnforcementShim
- : public bluetooth::l2cap::classic::SecurityEnforcementInterface {
- public:
- static void security_enforce_result_callback(const RawAddress* bd_addr,
- tBT_TRANSPORT trasnport,
- void* p_ref_data,
- tBTM_STATUS result) {
- intptr_t counter = (intptr_t)p_ref_data;
- if (security_enforce_callback_map.count(counter) == 0) {
- LOG_ERROR("Received unexpected callback");
- return;
- }
-
- auto& callback = security_enforce_callback_map[counter];
- std::move(callback).Invoke(result == BTM_SUCCESS);
- security_enforce_callback_map.erase(counter);
- }
-
- void Enforce(bluetooth::hci::AddressWithType remote,
- bluetooth::l2cap::classic::SecurityPolicy policy,
- ResultCallback result_callback) override {
- uint16_t sec_mask = 0;
- switch (policy) {
- case bluetooth::l2cap::classic::SecurityPolicy::
- _SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK:
- result_callback.Invoke(true);
- return;
- case bluetooth::l2cap::classic::SecurityPolicy::ENCRYPTED_TRANSPORT:
- sec_mask = BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT |
- BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT;
- break;
- case bluetooth::l2cap::classic::SecurityPolicy::BEST:
- case bluetooth::l2cap::classic::SecurityPolicy::
- AUTHENTICATED_ENCRYPTED_TRANSPORT:
- sec_mask = BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT |
- BTM_SEC_IN_MITM | BTM_SEC_OUT_AUTHENTICATE |
- BTM_SEC_OUT_ENCRYPT | BTM_SEC_OUT_MITM;
- break;
- }
- auto bd_addr = bluetooth::ToRawAddress(remote.GetAddress());
- security_enforce_callback_map[security_enforce_callback_counter_] =
- std::move(result_callback);
- btm_sec_l2cap_access_req_by_requirement(
- bd_addr, sec_mask, true, security_enforce_result_callback,
- (void*)security_enforce_callback_counter_);
- security_enforce_callback_counter_++;
- }
-
- intptr_t security_enforce_callback_counter_ = 100;
-} security_enforcement_shim_;
-
-struct RemoteFeature {
- uint8_t lmp_version = 0;
- uint16_t manufacturer_name = 0;
- uint16_t sub_version = 0;
- uint8_t raw_remote_features[8];
- bool version_info_received = false;
- bool role_switch_supported = false;
- bool br_edr_supported = false;
- bool le_supported_controller = false;
- bool le_supported_host = false;
- bool ssp_supported = false;
- bool sc_supported = false;
- bool received_page_0 = false;
- bool received_page_1 = false;
-};
-
-std::unordered_map<RawAddress, RemoteFeature> remote_feature_map_;
-
-struct LinkPropertyListenerShim
- : public bluetooth::l2cap::classic::LinkPropertyListener {
- std::unordered_map<hci::Address, uint16_t> address_to_handle_;
-
- void OnLinkConnected(hci::Address remote, uint16_t handle) override {
- address_to_handle_[remote] = handle;
- }
-
- void OnLinkDisconnected(hci::Address remote) override {
- address_to_handle_.erase(remote);
- }
-
- void OnReadRemoteVersionInformation(hci::ErrorCode error_code,
- hci::Address remote, uint8_t lmp_version,
- uint16_t manufacturer_name,
- uint16_t sub_version) override {
- auto bda = bluetooth::ToRawAddress(remote);
- auto& entry = remote_feature_map_[bda];
- entry.lmp_version = lmp_version;
- entry.manufacturer_name = manufacturer_name;
- entry.sub_version = sub_version;
- entry.version_info_received = true;
- }
-
- void OnReadRemoteExtendedFeatures(hci::Address remote, uint8_t page_number,
- uint8_t max_page_number,
- uint64_t features) override {
- auto bda = bluetooth::ToRawAddress(remote);
- auto& entry = remote_feature_map_[bda];
- if (page_number == 0) {
- entry.received_page_0 = true;
- if (features & 0x20) entry.role_switch_supported = true;
- entry.br_edr_supported = !(features & kBrEdrNotSupportedMask);
- entry.le_supported_controller = features & kLeSupportedControllerMask;
- std::memcpy(entry.raw_remote_features, &features, 8);
- }
- if (page_number == 1) {
- entry.received_page_1 = true;
- if (features & 0x01) entry.ssp_supported = true;
- entry.le_supported_host = features & kLeSupportedHostMask;
- }
- if (entry.received_page_0 && entry.received_page_1) {
- const bool le_supported =
- entry.le_supported_controller && entry.le_supported_host;
- btm_sec_set_peer_sec_caps(address_to_handle_[remote], entry.ssp_supported,
- false, entry.role_switch_supported,
- entry.br_edr_supported, le_supported);
- }
- }
-
- void OnRoleChange(hci::ErrorCode error_code, hci::Address remote,
- hci::Role role) override {
- btm_rejectlist_role_change_device(ToRawAddress(remote),
- ToLegacyHciErrorCode(error_code));
- btm_acl_role_changed(ToLegacyHciErrorCode(error_code), ToRawAddress(remote),
- ToLegacyRole(role));
- }
-
- void OnReadClockOffset(hci::Address remote, uint16_t clock_offset) override {
- btm_sec_update_clock_offset(address_to_handle_[remote], clock_offset);
- }
+#include "main/shim/l2cap.h"
+#include "main/shim/shim.h"
+#include "osi/include/log.h"
- void OnModeChange(hci::ErrorCode error_code, hci::Address remote,
- hci::Mode mode, uint16_t interval) override {
- btm_sco_chk_pend_unpark(ToLegacyHciErrorCode(error_code),
- address_to_handle_[remote]);
- btm_pm_proc_mode_change(ToLegacyHciErrorCode(error_code),
- address_to_handle_[remote], ToLegacyHciMode(mode),
- interval);
- }
-
- void OnSniffSubrating(hci::ErrorCode error_code, hci::Address remote,
- uint16_t max_tx_lat, uint16_t max_rx_lat,
- uint16_t min_remote_timeout,
- uint16_t min_local_timeout) override {
- process_ssr_event(ToLegacyHciErrorCode(error_code),
- address_to_handle_[remote], max_tx_lat, max_rx_lat);
- }
-
-} link_property_listener_shim_;
-
-class SecurityListenerShim
- : public bluetooth::l2cap::classic::LinkSecurityInterfaceListener {
- public:
- void OnLinkConnected(
- std::unique_ptr<bluetooth::l2cap::classic::LinkSecurityInterface>
- interface) override {
- auto bda = bluetooth::ToRawAddress(interface->GetRemoteAddress());
-
- uint16_t handle = interface->GetAclHandle();
- address_to_handle_[bda] = handle;
- btm_sec_connected(bda, handle, HCI_SUCCESS, 0);
- BTM_PM_OnConnected(handle, bda);
- BTA_dm_acl_up(bda, BT_TRANSPORT_BR_EDR);
- address_to_interface_[bda] = std::move(interface);
- }
-
- void OnAuthenticationComplete(hci::ErrorCode hci_status,
- bluetooth::hci::Address remote) override {
- // Note: if gd security is not enabled, we should use btu_hcif.cc path
- auto bda = bluetooth::ToRawAddress(remote);
- uint16_t handle = address_to_handle_[bda];
- btm_sec_auth_complete(handle, ToLegacyHciErrorCode(hci_status));
- }
-
- void OnLinkDisconnected(bluetooth::hci::Address remote) override {
- auto bda = bluetooth::ToRawAddress(remote);
- uint16_t handle = address_to_handle_[bda];
- address_to_handle_.erase(bda);
- address_to_interface_.erase(bda);
- btm_sec_disconnected(handle, HCI_ERR_PEER_USER);
- BTA_dm_acl_down(bda, BT_TRANSPORT_BR_EDR);
- BTM_PM_OnDisconnected(handle);
- }
-
- void OnEncryptionChange(bluetooth::hci::Address remote,
- bool encrypted) override {
- // Note: if gd security is not enabled, we should use btu_hcif.cc path
- auto bda = bluetooth::ToRawAddress(remote);
- uint16_t handle = address_to_handle_[bda];
- btm_sec_encrypt_change(handle, HCI_SUCCESS, encrypted);
- }
-
- void UpdateLinkHoldForSecurity(RawAddress remote, bool is_bonding) {
- if (address_to_interface_.count(remote) == 0) {
- return;
- }
- if (is_bonding) {
- address_to_interface_[remote]->Hold();
- } else {
- address_to_interface_[remote]->Release();
- }
- }
-
- bool IsRoleCentral(RawAddress remote) {
- if (address_to_interface_.count(remote) == 0) {
- return false;
- }
- return address_to_interface_[remote]->GetRole() ==
- bluetooth::hci::Role::CENTRAL;
- }
-
- void Disconnect(RawAddress remote) {
- if (address_to_interface_.count(remote) == 0) {
- return;
- }
- return address_to_interface_[remote]->Disconnect();
- }
-
- uint16_t GetNumAclLinks() { return address_to_handle_.size(); }
-
- bool IsLinkUp(RawAddress remote) {
- return address_to_interface_.count(remote) != 0;
- }
-
- std::unordered_map<RawAddress, uint16_t> address_to_handle_;
- std::unordered_map<
- RawAddress,
- std::unique_ptr<bluetooth::l2cap::classic::LinkSecurityInterface>>
- address_to_interface_;
-} security_listener_shim_;
-
-bluetooth::l2cap::classic::SecurityInterface* security_interface_ = nullptr;
-
-struct LeLinkPropertyListenerShim
- : public bluetooth::l2cap::le::LinkPropertyListener {
- struct ConnectionInfo {
- uint16_t handle;
- hci::Role role;
- AddressWithType address_with_type;
- };
- std::unordered_map<hci::Address, ConnectionInfo> info_;
-
- void OnLinkConnected(AddressWithType remote, uint16_t handle,
- hci::Role role) override {
- info_[remote.GetAddress()] = {handle, role, remote};
- btm_ble_connected(ToRawAddress(remote.GetAddress()), handle,
- HCI_ENCRYPT_MODE_DISABLED, static_cast<uint8_t>(role),
- static_cast<tBLE_ADDR_TYPE>(remote.GetAddressType()),
- false);
- }
+static bluetooth::shim::legacy::L2cap shim_l2cap;
- void OnLinkDisconnected(hci::AddressWithType remote) override {
- info_.erase(remote.GetAddress());
- }
-
- void OnReadRemoteVersionInformation(hci::ErrorCode hci_status,
- hci::AddressWithType remote,
- uint8_t lmp_version,
- uint16_t manufacturer_name,
- uint16_t sub_version) override {
- auto bda = bluetooth::ToRawAddress(remote.GetAddress());
- auto& entry = remote_feature_map_[bda];
- entry.lmp_version = lmp_version;
- entry.manufacturer_name = manufacturer_name;
- entry.sub_version = sub_version;
- entry.version_info_received = true;
- }
-
- void OnConnectionUpdate(hci::AddressWithType remote,
- uint16_t connection_interval,
- uint16_t connection_latency,
- uint16_t supervision_timeout) override {
- acl_ble_update_event_received(
- HCI_SUCCESS, info_[remote.GetAddress()].handle, connection_interval,
- connection_latency, supervision_timeout);
- }
-
- void OnPhyUpdate(hci::AddressWithType remote, uint8_t tx_phy,
- uint8_t rx_phy) override {
- gatt_notify_phy_updated(GATT_SUCCESS, info_[remote.GetAddress()].handle,
- tx_phy, rx_phy);
+/**
+ * Classic Service Registration APIs
+ */
+uint16_t bluetooth::shim::L2CA_Register(uint16_t client_psm,
+ tL2CAP_APPL_INFO* callbacks,
+ bool enable_snoop,
+ tL2CAP_ERTM_INFO* p_ertm_info) {
+ CHECK(callbacks != nullptr);
+
+ if (L2C_INVALID_PSM(client_psm)) {
+ LOG_ERROR(LOG_TAG, "%s Invalid classic psm:%hd", __func__, client_psm);
+ return 0;
}
- void OnDataLengthChange(hci::AddressWithType remote, uint16_t tx_octets,
- uint16_t tx_time, uint16_t rx_octets,
- uint16_t rx_time) override {
- // Used by L2cap internal only.
+ if ((callbacks->pL2CA_ConfigCfm_Cb == nullptr) ||
+ (callbacks->pL2CA_ConfigInd_Cb == nullptr) ||
+ (callbacks->pL2CA_DataInd_Cb == nullptr) ||
+ (callbacks->pL2CA_DisconnectInd_Cb == nullptr)) {
+ LOG_ERROR(LOG_TAG, "%s Invalid classic callbacks psm:%hd", __func__,
+ client_psm);
+ return 0;
}
-} le_link_property_listener_shim_;
-
-std::unordered_map<intptr_t,
- bluetooth::common::ContextualOnceCallback<void(bool)>>
- le_security_enforce_callback_map = {};
-class LeSecurityEnforcementShim
- : public bluetooth::l2cap::le::SecurityEnforcementInterface {
- public:
- static void le_security_enforce_result_callback(const RawAddress* bd_addr,
- tBT_TRANSPORT trasnport,
- void* p_ref_data,
- tBTM_STATUS result) {
- intptr_t counter = (intptr_t)p_ref_data;
- if (le_security_enforce_callback_map.count(counter) == 0) {
- LOG_ERROR("Received unexpected callback");
- return;
- }
- auto& callback = le_security_enforce_callback_map[counter];
- std::move(callback).Invoke(result == BTM_SUCCESS);
- le_security_enforce_callback_map.erase(counter);
- }
+ /**
+ * Check if this is a registration for an outgoing-only connection.
+ */
+ bool is_outgoing_connection_only = callbacks->pL2CA_ConnectInd_Cb == nullptr;
+ uint16_t psm = shim_l2cap.ConvertClientToRealPsm(client_psm,
+ is_outgoing_connection_only);
- void Enforce(bluetooth::hci::AddressWithType remote,
- bluetooth::l2cap::le::SecurityPolicy policy,
- ResultCallback result_callback) override {
- tBTM_BLE_SEC_ACT sec_act = BTM_BLE_SEC_NONE;
- switch (policy) {
- case bluetooth::l2cap::le::SecurityPolicy::
- NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK:
- result_callback.Invoke(true);
- return;
- case bluetooth::l2cap::le::SecurityPolicy::ENCRYPTED_TRANSPORT:
- sec_act = BTM_BLE_SEC_ENCRYPT;
- break;
- case bluetooth::l2cap::le::SecurityPolicy::BEST:
- case bluetooth::l2cap::le::SecurityPolicy::
- AUTHENTICATED_ENCRYPTED_TRANSPORT:
- sec_act = BTM_BLE_SEC_ENCRYPT_MITM;
- break;
- default:
- result_callback.Invoke(false);
- }
- auto bd_addr = bluetooth::ToRawAddress(remote.GetAddress());
- le_security_enforce_callback_map[security_enforce_callback_counter_] =
- std::move(result_callback);
- BTM_SetEncryption(bd_addr, BT_TRANSPORT_LE,
- le_security_enforce_result_callback,
- (void*)security_enforce_callback_counter_, sec_act);
- security_enforce_callback_counter_++;
+ if (shim_l2cap.Classic().IsPsmRegistered(psm)) {
+ LOG_ERROR(LOG_TAG, "%s Already registered classic client_psm:%hd psm:%hd",
+ __func__, client_psm, psm);
+ return 0;
}
+ LOG_INFO(LOG_TAG, "%s classic client_psm:%hd psm:%hd", __func__, client_psm,
+ psm);
- intptr_t security_enforce_callback_counter_ = 100;
-} le_security_enforcement_shim_;
-} // namespace
-
-bool L2CA_ReadRemoteVersion(const RawAddress& addr, uint8_t* lmp_version,
- uint16_t* manufacturer, uint16_t* lmp_sub_version) {
- auto& entry = remote_feature_map_[addr];
- if (!entry.version_info_received) {
- return false;
- }
- if (lmp_version != nullptr) *lmp_version = entry.lmp_version;
- if (manufacturer != nullptr) *manufacturer = entry.manufacturer_name;
- if (lmp_sub_version != nullptr) *lmp_sub_version = entry.sub_version;
- return true;
+ return shim_l2cap.RegisterService(psm, callbacks, enable_snoop, p_ertm_info);
}
-uint8_t* L2CA_ReadRemoteFeatures(const RawAddress& addr) {
- auto& entry = remote_feature_map_[addr];
- if (!entry.received_page_0) {
- return nullptr;
+void bluetooth::shim::L2CA_Deregister(uint16_t client_psm) {
+ if (L2C_INVALID_PSM(client_psm)) {
+ LOG_ERROR(LOG_TAG, "%s Invalid classic client_psm:%hd", __func__,
+ client_psm);
+ return;
}
- return entry.raw_remote_features;
-}
+ uint16_t psm = shim_l2cap.ConvertClientToRealPsm(client_psm);
-static void on_sco_disconnect(uint16_t handle, uint8_t reason) {
- GetGdShimHandler()->Post(base::BindOnce(base::IgnoreResult(&btm_sco_removed),
- handle,
- static_cast<tHCI_REASON>(reason)));
+ shim_l2cap.UnregisterService(psm);
+ shim_l2cap.RemoveClientPsm(psm);
}
-void L2CA_UseLegacySecurityModule() {
- LOG_INFO("GD L2cap is using legacy security module");
- GetL2capClassicModule()->SetLinkPropertyListener(
- GetGdShimHandler(), &link_property_listener_shim_);
-
- GetL2capClassicModule()->InjectSecurityEnforcementInterface(
- &security_enforcement_shim_);
- security_interface_ = GetL2capClassicModule()->GetSecurityInterface(
- GetGdShimHandler(), &security_listener_shim_);
-
- GetL2capLeModule()->SetLinkPropertyListener(GetGdShimHandler(),
- &le_link_property_listener_shim_);
- GetL2capLeModule()->InjectSecurityEnforcementInterface(
- &le_security_enforcement_shim_);
-
- GetAclManager()->HACK_SetScoDisconnectCallback(on_sco_disconnect);
+uint16_t bluetooth::shim::L2CA_AllocatePSM(void) {
+ return shim_l2cap.GetNextDynamicClassicPsm();
}
-/**
- * Classic Service Registration APIs
- */
-uint16_t L2CA_Register(uint16_t client_psm, const tL2CAP_APPL_INFO& callbacks,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level) {
- if (classic_dynamic_channel_helper_map_.count(client_psm) != 0) {
- LOG(ERROR) << __func__ << "Already registered psm: " << client_psm;
- return 0;
- }
-
- classic::DynamicChannelConfigurationOption config;
- config.minimal_remote_mtu = std::max<uint16_t>(required_remote_mtu, 48);
- config.incoming_mtu = my_mtu;
- config.channel_mode =
- (p_ertm_info != nullptr &&
- p_ertm_info->preferred_mode == L2CAP_FCR_ERTM_MODE
- ? classic::DynamicChannelConfigurationOption::
- RetransmissionAndFlowControlMode::ENHANCED_RETRANSMISSION
- : classic::DynamicChannelConfigurationOption::
- RetransmissionAndFlowControlMode::L2CAP_BASIC);
-
- classic::SecurityPolicy policy =
- (client_psm == 1
- ? classic::SecurityPolicy::
- _SDP_ONLY_NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK
- : classic::SecurityPolicy::ENCRYPTED_TRANSPORT);
- if (sec_level & (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_OUT_AUTHENTICATE)) {
- policy = classic::SecurityPolicy::BEST;
- }
-
- classic_dynamic_channel_helper_map_[client_psm] =
- std::make_unique<ClassicDynamicChannelHelper>(client_psm, callbacks,
- config, policy);
-
- classic_dynamic_channel_helper_map_[client_psm]->Register();
- return client_psm;
+uint16_t bluetooth::shim::L2CA_AllocateLePSM(void) {
+ return shim_l2cap.GetNextDynamicLePsm();
}
-void L2CA_Deregister(uint16_t psm) {
- if (classic_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
+void bluetooth::shim::L2CA_FreeLePSM(uint16_t psm) {
+ if (!shim_l2cap.Le().IsPsmRegistered(psm)) {
+ LOG_ERROR(LOG_TAG, "%s Not previously registered le psm:%hd", __func__,
+ psm);
return;
}
- classic_dynamic_channel_helper_map_[psm]->Unregister();
+ shim_l2cap.Le().UnregisterPsm(psm);
}
/**
* Classic Connection Oriented Channel APIS
*/
-uint16_t L2CA_ConnectReq(uint16_t psm, const RawAddress& raw_address) {
- if (classic_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
- return 0;
- }
- uint16_t cid_token = add_classic_cid_token_entry(psm);
- classic_dynamic_channel_helper_map_[psm]->Connect(
- cid_token, ToAddressWithType(raw_address, BLE_ADDR_PUBLIC));
- return cid_token;
+uint16_t bluetooth::shim::L2CA_ErtmConnectReq(uint16_t psm,
+ const RawAddress& raw_address,
+ tL2CAP_ERTM_INFO* p_ertm_info) {
+ return shim_l2cap.CreateConnection(psm, raw_address);
}
-bool L2CA_DisconnectReq(uint16_t cid) {
- auto psm = classic_cid_token_to_channel_map_[cid];
- if (classic_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
- return false;
- }
- classic_dynamic_channel_helper_map_[psm]->Disconnect(cid);
- return true;
+uint16_t bluetooth::shim::L2CA_ConnectReq(uint16_t psm,
+ const RawAddress& raw_address) {
+ return shim_l2cap.CreateConnection(psm, raw_address);
}
-uint8_t L2CA_DataWrite(uint16_t cid, BT_HDR* p_data) {
- if (classic_cid_token_to_channel_map_.count(cid) == 0) {
- LOG(ERROR) << __func__ << "Invalid cid: " << cid;
- osi_free(p_data);
- return 0;
- }
- auto psm = classic_cid_token_to_channel_map_[cid];
- if (classic_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
- osi_free(p_data);
- return 0;
- }
- auto len = p_data->len;
- auto* data = p_data->data + p_data->offset;
- uint8_t sent_length =
- classic_dynamic_channel_helper_map_[psm]->send(
- cid, MakeUniquePacket(data, len, IsPacketFlushable(p_data))) *
- len;
- osi_free(p_data);
- return sent_length;
+bool bluetooth::shim::L2CA_ErtmConnectRsp(const RawAddress& p_bd_addr,
+ uint8_t id, uint16_t lcid,
+ uint16_t result, uint16_t status,
+ tL2CAP_ERTM_INFO* p_ertm_info) {
+ return shim_l2cap.ConnectResponse(p_bd_addr, id, lcid, result, status,
+ p_ertm_info);
}
-bool L2CA_ReconfigCreditBasedConnsReq(const RawAddress& bd_addr,
- std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- LOG_INFO("UNIMPLEMENTED %s addr: %s cfg:%p", __func__,
- bd_addr.ToString().c_str(), p_cfg);
- return false;
+bool bluetooth::shim::L2CA_ConnectRsp(const RawAddress& p_bd_addr, uint8_t id,
+ uint16_t lcid, uint16_t result,
+ uint16_t status) {
+ return bluetooth::shim::L2CA_ErtmConnectRsp(p_bd_addr, id, lcid, result,
+ status, nullptr);
}
-std::vector<uint16_t> L2CA_ConnectCreditBasedReq(uint16_t psm,
- const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- LOG_INFO("UNIMPLEMENTED %s addr:%s", __func__, p_bd_addr.ToString().c_str());
- std::vector<uint16_t> result;
- return result;
+bool bluetooth::shim::L2CA_ConfigReq(uint16_t cid, tL2CAP_CFG_INFO* cfg_info) {
+ return shim_l2cap.ConfigRequest(cid, cfg_info);
}
-bool L2CA_ConnectCreditBasedRsp(const RawAddress& bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids,
- uint16_t result, tL2CAP_LE_CFG_INFO* p_cfg) {
- LOG_INFO("UNIMPLEMENTED %s addr:%s", __func__, bd_addr.ToString().c_str());
- return false;
+bool bluetooth::shim::L2CA_ConfigRsp(uint16_t cid, tL2CAP_CFG_INFO* cfg_info) {
+ return shim_l2cap.ConfigResponse(cid, cfg_info);
}
-/**
- * Link APIs
- */
-bool L2CA_SetIdleTimeoutByBdAddr(const RawAddress& bd_addr, uint16_t timeout,
- tBT_TRANSPORT transport) {
- if (transport == BT_TRANSPORT_BR_EDR) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
- return false;
- }
- if (timeout == 0 || timeout == GATT_LINK_IDLE_TIMEOUT_WHEN_NO_APP) {
- bluetooth::shim::L2CA_RemoveFixedChnl(kLeAttributeCid, bd_addr);
- return true;
- } else {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
- return false;
- }
+bool bluetooth::shim::L2CA_DisconnectReq(uint16_t cid) {
+ return shim_l2cap.DisconnectRequest(cid);
}
-bool L2CA_SetAclPriority(uint16_t handle, bool high_priority) {
- GetAclManager()->HACK_SetAclTxPriority(handle, high_priority);
- return true;
+bool bluetooth::shim::L2CA_DisconnectRsp(uint16_t cid) {
+ return shim_l2cap.DisconnectResponse(cid);
}
-bool L2CA_SetAclPriority(const RawAddress& bd_addr, tL2CAP_PRIORITY priority) {
- uint16_t handle = security_listener_shim_.address_to_handle_[bd_addr];
- return L2CA_SetAclPriority(handle, priority == L2CAP_PRIORITY_HIGH);
+/**
+ * Le Connection Oriented Channel APIs
+ */
+uint16_t bluetooth::shim::L2CA_RegisterLECoc(uint16_t psm,
+ tL2CAP_APPL_INFO* callbacks) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s psm:%hd callbacks:%p", __func__, psm,
+ callbacks);
+ return 0;
+}
+
+void bluetooth::shim::L2CA_DeregisterLECoc(uint16_t psm) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s psm:%hd", __func__, psm);
+}
+
+uint16_t bluetooth::shim::L2CA_ConnectLECocReq(uint16_t psm,
+ const RawAddress& p_bd_addr,
+ tL2CAP_LE_CFG_INFO* p_cfg) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s psm:%hd addr:%s p_cfg:%p", __func__, psm,
+ p_bd_addr.ToString().c_str(), p_cfg);
+ return 0;
+}
+
+bool bluetooth::shim::L2CA_ConnectLECocRsp(const RawAddress& p_bd_addr,
+ uint8_t id, uint16_t lcid,
+ uint16_t result, uint16_t status,
+ tL2CAP_LE_CFG_INFO* p_cfg) {
+ LOG_INFO(LOG_TAG,
+ "UNIMPLEMENTED %s addr:%s id:%hhd lcid:%hd result:%hd status:%hd "
+ "p_cfg:%p",
+ __func__, p_bd_addr.ToString().c_str(), id, lcid, result, status,
+ p_cfg);
+ return false;
}
-bool L2CA_GetPeerFeatures(const RawAddress& bd_addr, uint32_t* p_ext_feat,
- uint8_t* p_chnl_mask) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+bool bluetooth::shim::L2CA_GetPeerLECocConfig(uint16_t lcid,
+ tL2CAP_LE_CFG_INFO* peer_cfg) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s lcid:%hd peer_cfg:%p", __func__, lcid,
+ peer_cfg);
return false;
}
-static constexpr uint16_t kAttCid = 4;
-
-struct LeFixedChannelHelper {
- LeFixedChannelHelper(uint16_t cid) : cid_(cid) {}
-
- uint16_t cid_;
-
- void on_registration_complete(
- le::FixedChannelManager::RegistrationResult result,
- std::unique_ptr<le::FixedChannelService> service) {
- if (result != le::FixedChannelManager::RegistrationResult::SUCCESS) {
- LOG(ERROR) << "Channel is not registered. cid=" << +cid_;
- return;
- }
- channel_service_ = std::move(service);
- }
-
- std::unique_ptr<le::FixedChannelService> channel_service_ = nullptr;
-
- void on_channel_close(bluetooth::hci::Address device,
- bluetooth::hci::ErrorCode error_code) {
- auto address = bluetooth::ToRawAddress(device);
- channel_enqueue_buffer_[device] = nullptr;
- channels_[device]->GetQueueUpEnd()->UnregisterDequeue();
- channels_[device] = nullptr;
- conn_parameters_.erase(device);
- uint8_t error = static_cast<uint8_t>(error_code);
- (freg_.pL2CA_FixedConn_Cb)(cid_, address, false, error, BT_TRANSPORT_LE);
- }
-
- void on_channel_open(std::unique_ptr<le::FixedChannel> channel) {
- auto remote = channel->GetDevice();
- auto device = remote.GetAddress();
- channel->RegisterOnCloseCallback(
- GetGdShimHandler(), bluetooth::common::BindOnce(
- &LeFixedChannelHelper::on_channel_close,
- bluetooth::common::Unretained(this), device));
- if (cid_ == kAttCid) {
- channel->Acquire();
- }
- channel_enqueue_buffer_[device] = std::make_unique<
- bluetooth::os::EnqueueBuffer<bluetooth::packet::BasePacketBuilder>>(
- channel->GetQueueUpEnd());
- channel->GetQueueUpEnd()->RegisterDequeue(
- GetGdShimHandler(),
- bluetooth::common::Bind(&LeFixedChannelHelper::on_incoming_data,
- bluetooth::common::Unretained(this), device));
- channels_[device] = std::move(channel);
- conn_parameters_[device] = {};
-
- auto address = bluetooth::ToRawAddress(device);
-
- (freg_.pL2CA_FixedConn_Cb)(cid_, address, true, 0, BT_TRANSPORT_LE);
- }
-
- void on_incoming_data(bluetooth::hci::Address device) {
- auto channel = channels_.find(device);
- if (channel == channels_.end()) {
- LOG_ERROR("Channel is not open");
- return;
- }
- auto packet = channel->second->GetQueueUpEnd()->TryDequeue();
- std::vector<uint8_t> packet_vector(packet->begin(), packet->end());
- BT_HDR* buffer =
- static_cast<BT_HDR*>(osi_calloc(packet_vector.size() + sizeof(BT_HDR)));
- std::copy(packet_vector.begin(), packet_vector.end(), buffer->data);
- buffer->len = packet_vector.size();
- auto address = bluetooth::ToRawAddress(device);
- freg_.pL2CA_FixedData_Cb(cid_, address, buffer);
- }
-
- void on_outgoing_connection_fail(
- RawAddress remote, le::FixedChannelManager::ConnectionResult result) {
- LOG(ERROR) << "Outgoing connection failed";
- freg_.pL2CA_FixedConn_Cb(cid_, remote, true, 0, BT_TRANSPORT_LE);
- }
-
- bool send(hci::Address remote,
- std::unique_ptr<bluetooth::packet::BasePacketBuilder> packet) {
- auto buffer = channel_enqueue_buffer_.find(remote);
- if (buffer == channel_enqueue_buffer_.end() || buffer->second == nullptr) {
- LOG(ERROR) << "Channel is not open for cid " << cid_;
- return false;
- }
- buffer->second->Enqueue(std::move(packet), GetGdShimHandler());
- return true;
- }
-
- std::unordered_map<hci::Address, std::unique_ptr<le::FixedChannel>> channels_;
- std::unordered_map<hci::Address, std::unique_ptr<bluetooth::os::EnqueueBuffer<
- bluetooth::packet::BasePacketBuilder>>>
- channel_enqueue_buffer_;
-
- struct ConnectionParameter {
- // Default values are from GD HCI_ACL le_impl.
- uint16_t min_int = 0x0018;
- uint16_t max_int = 0x0028;
- uint16_t latency = 0x0000;
- uint16_t timeout = 0x001f4;
- uint16_t min_ce_len = 0x0000;
- uint16_t max_ce_len = 0x0000;
- bool update_allowed = true;
- };
- std::unordered_map<hci::Address, ConnectionParameter> conn_parameters_;
- tL2CAP_FIXED_CHNL_REG freg_;
-};
-
-static LeFixedChannelHelper att_helper{4};
-static LeFixedChannelHelper smp_helper{6};
-static std::unordered_map<uint16_t, LeFixedChannelHelper&>
- le_fixed_channel_helper_{
- {4, att_helper},
- {6, smp_helper},
- };
-
/**
- * Fixed Channel APIs. Note: Classic fixed channel (connectionless and BR SMP)
- * is not supported
+ * Channel Data Writes
*/
-bool L2CA_RegisterFixedChannel(uint16_t cid, tL2CAP_FIXED_CHNL_REG* p_freg) {
- if (cid != kAttCid && cid != kSmpCid) {
- LOG(ERROR) << "Invalid cid: " << cid;
- return false;
- }
- auto* helper = &le_fixed_channel_helper_.find(cid)->second;
- if (helper == nullptr) {
- LOG(ERROR) << "Can't register cid " << cid;
- return false;
- }
- GetL2capLeModule()->GetFixedChannelManager()->RegisterService(
- cid,
- common::BindOnce(&LeFixedChannelHelper::on_registration_complete,
- common::Unretained(helper)),
- common::Bind(&LeFixedChannelHelper::on_channel_open,
- common::Unretained(helper)),
- GetGdShimHandler());
- helper->freg_ = *p_freg;
- return true;
-}
-
-bool L2CA_ConnectFixedChnl(uint16_t cid, const RawAddress& rem_bda) {
- if (cid != kAttCid && cid != kSmpCid) {
- LOG(ERROR) << "Invalid cid " << cid;
- return false;
- }
-
- auto* helper = &le_fixed_channel_helper_.find(cid)->second;
- auto remote = Btm::GetAddressAndType(rem_bda);
- auto record =
- le_link_property_listener_shim_.info_.find(ToGdAddress(rem_bda));
- if (record != le_link_property_listener_shim_.info_.end()) {
- remote = record->second.address_with_type;
- }
- LOG(ERROR) << __func__ << remote.ToString();
- auto manager = GetL2capLeModule()->GetFixedChannelManager();
- manager->ConnectServices(
- remote,
- common::BindOnce(&LeFixedChannelHelper::on_outgoing_connection_fail,
- common::Unretained(helper), rem_bda),
- GetGdShimHandler());
- return true;
-}
-
-uint16_t L2CA_SendFixedChnlData(uint16_t cid, const RawAddress& rem_bda,
- BT_HDR* p_buf) {
- if (cid != kAttCid && cid != kSmpCid) {
- LOG(ERROR) << "Invalid cid " << cid;
- osi_free(p_buf);
- return L2CAP_DW_FAILED;
- }
- auto* helper = &le_fixed_channel_helper_.find(cid)->second;
- auto len = p_buf->len;
- auto* data = p_buf->data + p_buf->offset;
- bool sent =
- helper->send(ToGdAddress(rem_bda),
- MakeUniquePacket(data, len, IsPacketFlushable(p_buf)));
- osi_free(p_buf);
- return sent ? L2CAP_DW_SUCCESS : L2CAP_DW_FAILED;
-}
-
-bool L2CA_RemoveFixedChnl(uint16_t cid, const RawAddress& rem_bda) {
- if (cid != kAttCid && cid != kSmpCid) {
- LOG(ERROR) << "Invalid cid " << cid;
- return false;
- }
- auto* helper = &le_fixed_channel_helper_.find(cid)->second;
- auto channel = helper->channels_.find(ToGdAddress(rem_bda));
- if (channel == helper->channels_.end() || channel->second == nullptr) {
- LOG(ERROR) << "Channel is not open";
- return false;
- }
- channel->second->Release();
- return true;
-}
-
-uint16_t L2CA_GetLeHandle(const RawAddress& rem_bda) {
- auto addr = ToGdAddress(rem_bda);
- if (le_link_property_listener_shim_.info_.count(addr) == 0) {
- return 0;
- }
- return le_link_property_listener_shim_.info_[addr].handle;
-}
-
-void L2CA_LeConnectionUpdate(const RawAddress& rem_bda, uint16_t min_int,
- uint16_t max_int, uint16_t latency,
- uint16_t timeout, uint16_t min_ce_len,
- uint16_t max_ce_len) {
- auto* helper = &le_fixed_channel_helper_.find(kAttCid)->second;
- auto channel = helper->channels_.find(ToGdAddress(rem_bda));
- if (channel == helper->channels_.end() || channel->second == nullptr) {
- LOG(ERROR) << "Channel is not open";
- return;
- }
-
- auto& parameter = helper->conn_parameters_[ToGdAddress(rem_bda)];
-
- parameter.min_int = min_int;
- parameter.max_int = max_int;
- parameter.latency = latency;
- parameter.timeout = timeout;
- parameter.min_ce_len = min_ce_len;
- parameter.max_ce_len = max_ce_len;
-
- if (parameter.update_allowed) {
- channel->second->GetLinkOptions()->UpdateConnectionParameter(
- min_int, max_int, latency, timeout, min_ce_len, max_ce_len);
- }
- // If update not allowed, don't update; instead cache the value, and update
- // when update is allowed.
+bool bluetooth::shim::L2CA_SetConnectionCallbacks(
+ uint16_t cid, const tL2CAP_APPL_INFO* callbacks) {
+ LOG_INFO(LOG_TAG, "Unsupported API %s", __func__);
+ return false;
}
-bool L2CA_EnableUpdateBleConnParams(const RawAddress& rem_bda, bool enable) {
- // When enable is false, we disallow remote connection update request, and
- // we use default parameters temporarily.
- auto* helper = &le_fixed_channel_helper_.find(kAttCid)->second;
- auto channel = helper->channels_.find(ToGdAddress(rem_bda));
- if (channel == helper->channels_.end() || channel->second == nullptr) {
- LOG(ERROR) << "Channel is not open";
- return false;
- }
-
- auto& parameter = helper->conn_parameters_[ToGdAddress(rem_bda)];
- parameter.update_allowed = enable;
- // TODO(hsz): Notify HCI_ACL LE to allow/disallow remote request.
-
- if (parameter.update_allowed) {
- // Use cached values
- uint16_t min_int = parameter.min_int;
- uint16_t max_int = parameter.max_int;
- uint16_t latency = parameter.latency;
- uint16_t timeout = parameter.timeout;
- uint16_t min_ce_len = parameter.min_ce_len;
- uint16_t max_ce_len = parameter.max_ce_len;
- channel->second->GetLinkOptions()->UpdateConnectionParameter(
- min_int, max_int, latency, timeout, min_ce_len, max_ce_len);
- } else {
- // Use the value from legacy l2cble_start_conn_update
- uint16_t min_int = BTM_BLE_CONN_INT_MIN;
- uint16_t max_int = BTM_BLE_CONN_INT_MIN;
- L2CA_AdjustConnectionIntervals(&min_int, &max_int, BTM_BLE_CONN_INT_MIN);
- uint16_t latency = BTM_BLE_CONN_PERIPHERAL_LATENCY_DEF;
- uint16_t timeout = BTM_BLE_CONN_TIMEOUT_DEF;
- uint16_t min_ce_len = 0x0000;
- uint16_t max_ce_len = 0x0000;
- channel->second->GetLinkOptions()->UpdateConnectionParameter(
- min_int, max_int, latency, timeout, min_ce_len, max_ce_len);
- }
- return true;
+uint8_t bluetooth::shim::L2CA_DataWrite(uint16_t cid, BT_HDR* p_data) {
+ bool write_success = shim_l2cap.Write(cid, p_data);
+ return write_success ? L2CAP_DW_SUCCESS : L2CAP_DW_FAILED;
}
/**
- * Channel hygiene APIs
+ * L2cap Layer APIs
*/
-bool L2CA_GetRemoteCid(uint16_t lcid, uint16_t* rcid) {
- auto psm = classic_cid_token_to_channel_map_[lcid];
- if (classic_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
- return false;
- }
- *rcid = classic_dynamic_channel_helper_map_[psm]->GetRemoteCid(lcid);
- return *rcid != 0;
+uint8_t bluetooth::shim::L2CA_SetDesireRole(uint8_t new_role) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return 0;
}
-bool L2CA_SetTxPriority(uint16_t cid, tL2CAP_CHNL_PRIORITY priority) {
- auto psm = classic_cid_token_to_channel_map_[cid];
- if (classic_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
- return false;
- }
- bool high_priority = priority == L2CAP_CHNL_PRIORITY_HIGH;
- return classic_dynamic_channel_helper_map_[psm]->SetChannelTxPriority(
- cid, high_priority);
-}
-
-bool L2CA_SetLeGattTimeout(const RawAddress& rem_bda, uint16_t idle_tout) {
- if (idle_tout == 0xffff) {
- bluetooth::shim::L2CA_ConnectFixedChnl(kLeAttributeCid, rem_bda);
- } else {
- bluetooth::shim::L2CA_RemoveFixedChnl(kLeAttributeCid, rem_bda);
- }
- return true;
-}
-
-bool L2CA_SetChnlFlushability(uint16_t cid, bool is_flushable) {
- LOG_INFO("UNIMPLEMENTED %s", __func__);
+/**
+ * Link APIs
+ */
+bool bluetooth::shim::L2CA_SetIdleTimeoutByBdAddr(const RawAddress& bd_addr,
+ uint16_t timeout,
+ tBT_TRANSPORT transport) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
return false;
}
-uint16_t L2CA_FlushChannel(uint16_t lcid, uint16_t num_to_flush) {
- auto psm = classic_cid_token_to_channel_map_[lcid];
- if (classic_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
- return 0;
- }
- if (num_to_flush == L2CAP_FLUSH_CHANS_GET) {
- return classic_dynamic_channel_helper_map_[psm]->GetNumBufferedPackets(
- lcid);
- } else {
- classic_dynamic_channel_helper_map_[psm]->FlushChannel(lcid);
- return 1; // Client doesn't care
- }
- // TODO: Implement LE part
-}
-
-bool L2CA_IsLinkEstablished(const RawAddress& bd_addr,
- tBT_TRANSPORT transport) {
- if (transport == BT_TRANSPORT_BR_EDR) {
- return security_listener_shim_.IsLinkUp(bd_addr);
- } else {
- return bluetooth::shim::L2CA_GetLeHandle(bd_addr) != 0;
- }
-}
-
-bool L2CA_IsLeLink(uint16_t acl_handle) {
- for (const auto& entry : le_link_property_listener_shim_.info_) {
- if (entry.second.handle == acl_handle) return true;
- }
+bool bluetooth::shim::L2CA_SetAclPriority(const RawAddress& bd_addr,
+ uint8_t priority) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
return false;
}
-void L2CA_ReadConnectionAddr(const RawAddress& pseudo_addr,
- RawAddress& conn_addr, uint8_t* p_addr_type) {
- auto* helper = &le_fixed_channel_helper_.find(kSmpCid)->second;
- auto channel = helper->channels_.find(ToGdAddress(pseudo_addr));
- if (channel == helper->channels_.end() || channel->second == nullptr) {
- LOG(ERROR) << "Channel is not open!";
- return;
- }
- auto local = channel->second->GetLinkOptions()->GetLocalAddress();
- conn_addr = ToRawAddress(local.GetAddress());
- *p_addr_type = static_cast<uint8_t>(local.GetAddressType());
-}
-
-bool L2CA_ReadRemoteConnectionAddr(const RawAddress& pseudo_addr,
- RawAddress& conn_addr,
- uint8_t* p_addr_type) {
- auto remote = ToGdAddress(pseudo_addr);
- if (le_link_property_listener_shim_.info_.count(remote) == 0) {
- LOG(ERROR) << __func__ << ": Unknown address";
- return false;
- }
- auto info = le_link_property_listener_shim_.info_[remote].address_with_type;
- conn_addr = ToRawAddress(info.GetAddress());
- *p_addr_type = static_cast<tBLE_ADDR_TYPE>(info.GetAddressType());
- return true;
-}
-
-hci_role_t L2CA_GetBleConnRole(const RawAddress& bd_addr) {
- auto remote = ToGdAddress(bd_addr);
- if (le_link_property_listener_shim_.info_.count(remote) == 0) {
- return HCI_ROLE_UNKNOWN;
- }
- return static_cast<hci_role_t>(
- le_link_property_listener_shim_.info_[remote].role);
+bool bluetooth::shim::L2CA_SetFlushTimeout(const RawAddress& bd_addr,
+ uint16_t flush_tout) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-void L2CA_ConnectForSecurity(const RawAddress& bd_addr) {
- security_interface_->InitiateConnectionForSecurity(
- bluetooth::ToGdAddress(bd_addr));
+bool bluetooth::shim::L2CA_GetPeerFeatures(const RawAddress& bd_addr,
+ uint32_t* p_ext_feat,
+ uint8_t* p_chnl_mask) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-void L2CA_SetBondingState(const RawAddress& bd_addr, bool is_bonding) {
- security_listener_shim_.UpdateLinkHoldForSecurity(bd_addr, is_bonding);
+/**
+ * Fixed Channel APIs. Note: Classic fixed channel (connectionless and BR SMP)
+ * is not supported
+ */
+bool bluetooth::shim::L2CA_RegisterFixedChannel(uint16_t fixed_cid,
+ tL2CAP_FIXED_CHNL_REG* p_freg) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-void L2CA_DisconnectLink(const RawAddress& remote) {
- security_listener_shim_.Disconnect(remote);
+bool bluetooth::shim::L2CA_ConnectFixedChnl(uint16_t fixed_cid,
+ const RawAddress& rem_bda) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-uint16_t L2CA_GetNumLinks() { return security_listener_shim_.GetNumAclLinks(); }
-
-// LE COC Shim Helper
-
-namespace {
-
-uint16_t le_cid_token_counter_ = 0x41;
-
-std::unordered_map<uint16_t /* token */, uint16_t /* psm */>
- le_cid_token_to_channel_map_;
-
-uint16_t add_le_cid_token_entry(uint16_t psm) {
- uint16_t new_token = le_cid_token_counter_;
- le_cid_token_to_channel_map_[new_token] = psm;
- le_cid_token_counter_++;
- if (le_cid_token_counter_ == 0) le_cid_token_counter_ = 0x41;
- return new_token;
+bool bluetooth::shim::L2CA_ConnectFixedChnl(uint16_t fixed_cid,
+ const RawAddress& rem_bda,
+ uint8_t initiating_phys) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-void remove_le_cid_token_entry(uint16_t cid_token) {
- le_cid_token_to_channel_map_.erase(cid_token);
+uint16_t bluetooth::shim::L2CA_SendFixedChnlData(uint16_t fixed_cid,
+ const RawAddress& rem_bda,
+ BT_HDR* p_buf) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return 0;
}
-void remove_le_dynamic_channel_helper(uint16_t psm);
-
-struct LeDynamicChannelHelper {
- LeDynamicChannelHelper(uint16_t psm, tL2CAP_APPL_INFO appl_info,
- le::DynamicChannelConfigurationOption config,
- le::SecurityPolicy policy)
- : psm_(psm), appl_info_(appl_info), config_(config), policy_(policy) {}
-
- uint16_t psm_;
- tL2CAP_APPL_INFO appl_info_;
- le::DynamicChannelConfigurationOption config_;
- le::SecurityPolicy policy_;
-
- void Register() {
- std::promise<void> promise;
- auto future = promise.get_future();
- GetL2capLeModule()->GetDynamicChannelManager()->RegisterService(
- psm_, config_, policy_,
- base::BindOnce(&LeDynamicChannelHelper::on_registration_complete,
- base::Unretained(this), std::move(promise)),
- base::Bind(&LeDynamicChannelHelper::on_channel_open,
- base::Unretained(this), 0),
- GetGdShimHandler());
- future.wait_for(std::chrono::milliseconds(300));
- }
-
- void on_registration_complete(
- std::promise<void> promise,
- le::DynamicChannelManager::RegistrationResult result,
- std::unique_ptr<le::DynamicChannelService> service) {
- if (result != le::DynamicChannelManager::RegistrationResult::SUCCESS) {
- LOG(ERROR) << "Channel is not registered. psm=" << +psm_ << (int)result;
- promise.set_value();
- return;
- }
- channel_service_ = std::move(service);
- promise.set_value();
- }
-
- std::unique_ptr<le::DynamicChannelService> channel_service_ = nullptr;
-
- void Connect(uint16_t cid_token, bluetooth::hci::AddressWithType device) {
- if (channel_service_ == nullptr) {
- LOG(ERROR) << __func__ << "Not registered";
- return;
- }
- initiated_by_us_[cid_token] = true;
- GetL2capLeModule()->GetDynamicChannelManager()->ConnectChannel(
- device, config_, psm_,
- base::Bind(&LeDynamicChannelHelper::on_channel_open,
- base::Unretained(this), cid_token),
- base::BindOnce(&LeDynamicChannelHelper::on_outgoing_connection_fail,
- base::Unretained(this)),
- GetGdShimHandler());
- }
-
- void Disconnect(uint16_t cid_token) {
- if (channel_service_ == nullptr) {
- return;
- }
- if (channels_.count(cid_token) == 0) {
- return;
- }
- channels_[cid_token]->Close();
- }
-
- void Unregister() {
- if (channel_service_ != nullptr) {
- channel_service_->Unregister(
- base::BindOnce(&LeDynamicChannelHelper::on_unregistered,
- base::Unretained(this)),
- GetGdShimHandler());
- channel_service_ = nullptr;
- }
- }
-
- void on_unregistered() {
- for (const auto& device : channels_) {
- device.second->Close();
- }
- remove_le_dynamic_channel_helper(psm_);
- }
-
- void on_channel_close(uint16_t cid_token,
- bluetooth::hci::ErrorCode error_code) {
- channel_enqueue_buffer_[cid_token] = nullptr;
- channel_enqueue_buffer_.erase(cid_token);
- channels_[cid_token]->GetQueueUpEnd()->UnregisterDequeue();
- channels_.erase(cid_token);
- do_in_main_thread(FROM_HERE, base::Bind(appl_info_.pL2CA_DisconnectInd_Cb,
- cid_token, false));
-
- remove_le_cid_token_entry(cid_token);
- initiated_by_us_.erase(cid_token);
-
- if (channel_service_ == nullptr && channels_.empty()) {
- // Try again
- L2CA_Deregister(psm_);
- }
- }
-
- void on_channel_open(uint16_t cid_token,
- std::unique_ptr<le::DynamicChannel> channel) {
- auto device = channel->GetDevice();
- auto address = bluetooth::ToRawAddress(device.GetAddress());
- bool initiator_local = (cid_token != 0);
- if (cid_token == 0) {
- cid_token = add_le_cid_token_entry(psm_);
- }
-
- channel->RegisterOnCloseCallback(GetGdShimHandler()->BindOnceOn(
- this, &LeDynamicChannelHelper::on_channel_close, cid_token));
-
- channel->GetQueueUpEnd()->RegisterDequeue(
- GetGdShimHandler(),
- bluetooth::common::Bind(&LeDynamicChannelHelper::on_incoming_data,
- bluetooth::common::Unretained(this),
- cid_token));
-
- channel_enqueue_buffer_[cid_token] = std::make_unique<
- bluetooth::os::EnqueueBuffer<bluetooth::packet::BasePacketBuilder>>(
- channel->GetQueueUpEnd());
-
- channels_[cid_token] = std::move(channel);
-
- if (initiator_local) {
- do_in_main_thread(
- FROM_HERE, base::Bind(appl_info_.pL2CA_ConnectCfm_Cb, cid_token, 0));
-
- } else {
- if (appl_info_.pL2CA_ConnectInd_Cb == nullptr) {
- Disconnect(cid_token);
- return;
- }
- do_in_main_thread(FROM_HERE, base::Bind(appl_info_.pL2CA_ConnectInd_Cb,
- address, cid_token, psm_, 0));
- }
- }
-
- void on_incoming_data(uint16_t cid_token) {
- auto channel = channels_.find(cid_token);
- if (channel == channels_.end()) {
- LOG_ERROR("Channel is not open");
- return;
- }
- auto packet = channel->second->GetQueueUpEnd()->TryDequeue();
- std::vector<uint8_t> packet_vector(packet->begin(), packet->end());
- BT_HDR* buffer =
- static_cast<BT_HDR*>(osi_calloc(packet_vector.size() + sizeof(BT_HDR)));
- std::copy(packet_vector.begin(), packet_vector.end(), buffer->data);
- buffer->len = packet_vector.size();
- if (do_in_main_thread(FROM_HERE,
- base::Bind(appl_info_.pL2CA_DataInd_Cb, cid_token,
- base::Unretained(buffer))) !=
- BT_STATUS_SUCCESS) {
- osi_free(buffer);
- }
- }
-
- void on_outgoing_connection_fail(
- le::DynamicChannelManager::ConnectionResult result) {
- LOG(ERROR) << "Outgoing connection failed";
- }
-
- bool send(uint16_t cid,
- std::unique_ptr<bluetooth::packet::BasePacketBuilder> packet) {
- auto buffer = channel_enqueue_buffer_.find(cid);
- if (buffer == channel_enqueue_buffer_.end() || buffer->second == nullptr) {
- LOG(ERROR) << "Channel is not open";
- return false;
- }
- buffer->second->Enqueue(std::move(packet), GetGdShimHandler());
- return true;
- }
-
- uint16_t GetMtu(uint16_t cid_token) {
- if (channels_.count(cid_token) == 0) {
- return 0;
- }
- return static_cast<uint16_t>(channels_[cid_token]->GetMtu());
- }
-
- std::unordered_map<uint16_t, std::unique_ptr<le::DynamicChannel>> channels_;
- std::unordered_map<uint16_t, std::unique_ptr<bluetooth::os::EnqueueBuffer<
- bluetooth::packet::BasePacketBuilder>>>
- channel_enqueue_buffer_;
- std::unordered_map<uint16_t, bool> initiated_by_us_;
-};
-
-std::unordered_map<uint16_t, std::unique_ptr<LeDynamicChannelHelper>>
- le_dynamic_channel_helper_map_;
-
-void remove_le_dynamic_channel_helper(uint16_t psm) {
- if (le_dynamic_channel_helper_map_.count(psm) != 0 &&
- le_dynamic_channel_helper_map_[psm]->channels_.empty()) {
- le_dynamic_channel_helper_map_.erase(psm);
- }
+bool bluetooth::shim::L2CA_RemoveFixedChnl(uint16_t fixed_cid,
+ const RawAddress& rem_bda) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-std::unordered_set<uint16_t> assigned_dynamic_le_psm_;
-uint16_t next_assigned_dynamic_le_psm_ = 0x80;
-} // namespace
-
/**
- * Le Connection Oriented Channel APIs
+ * Channel hygiene APIs
*/
-
-uint16_t L2CA_AllocateLePSM() {
- if (le_dynamic_channel_helper_map_.size() > 100) {
- LOG_ERROR("Why do we need more than 100 dynamic channel PSMs?");
- return 0;
- }
- while (le_dynamic_channel_helper_map_.count(next_assigned_dynamic_le_psm_)) {
- next_assigned_dynamic_le_psm_++;
- if (next_assigned_dynamic_le_psm_ > 0xff) {
- next_assigned_dynamic_le_psm_ = 0x80;
- }
- }
- assigned_dynamic_le_psm_.emplace(next_assigned_dynamic_le_psm_);
- return next_assigned_dynamic_le_psm_;
-}
-
-void L2CA_FreeLePSM(uint16_t psm) { assigned_dynamic_le_psm_.erase(psm); }
-
-uint16_t L2CA_RegisterLECoc(uint16_t psm, const tL2CAP_APPL_INFO& callbacks,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg) {
- if (le_dynamic_channel_helper_map_.count(psm) != 0) {
- LOG(ERROR) << __func__ << "Already registered psm: " << psm;
- return 0;
- }
-
- le::DynamicChannelConfigurationOption config;
- config.mtu = cfg.mtu;
- le::SecurityPolicy policy =
- le::SecurityPolicy::NO_SECURITY_WHATSOEVER_PLAINTEXT_TRANSPORT_OK;
- if (sec_level & (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_OUT_AUTHENTICATE)) {
- policy = le::SecurityPolicy::AUTHENTICATED_ENCRYPTED_TRANSPORT;
- }
-
- le_dynamic_channel_helper_map_[psm] =
- std::make_unique<LeDynamicChannelHelper>(psm, callbacks, config, policy);
- le_dynamic_channel_helper_map_[psm]->Register();
- return psm;
-}
-
-void L2CA_DeregisterLECoc(uint16_t psm) {
- if (le_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
- return;
- }
- le_dynamic_channel_helper_map_[psm]->Unregister();
+bool bluetooth::shim::L2CA_GetIdentifiers(uint16_t lcid, uint16_t* rcid,
+ uint16_t* handle) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-uint16_t L2CA_ConnectLECocReq(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- if (le_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
- return 0;
- }
- uint16_t cid_token = add_le_cid_token_entry(psm);
- auto remote = Btm::GetAddressAndType(p_bd_addr);
- auto record =
- le_link_property_listener_shim_.info_.find(ToGdAddress(p_bd_addr));
- if (record != le_link_property_listener_shim_.info_.end()) {
- remote = record->second.address_with_type;
- }
- le_dynamic_channel_helper_map_[psm]->Connect(cid_token, remote);
- return cid_token;
+bool bluetooth::shim::L2CA_SetIdleTimeout(uint16_t cid, uint16_t timeout,
+ bool is_global) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-bool L2CA_GetPeerLECocConfig(uint16_t cid, tL2CAP_LE_CFG_INFO* peer_cfg) {
- if (le_cid_token_to_channel_map_.count(cid) == 0) {
- LOG(ERROR) << __func__ << "Invalid cid: " << cid;
- return false;
- }
- auto psm = le_cid_token_to_channel_map_[cid];
- if (le_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
- return false;
- }
- auto mtu = le_dynamic_channel_helper_map_[psm]->GetMtu(cid);
- peer_cfg->mtu = mtu;
- return mtu;
+bool bluetooth::shim::L2CA_SetTxPriority(uint16_t cid,
+ tL2CAP_CHNL_PRIORITY priority) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-bool L2CA_DisconnectLECocReq(uint16_t cid) {
- if (le_cid_token_to_channel_map_.count(cid) == 0) {
- LOG(ERROR) << __func__ << "Invalid cid: " << cid;
- return false;
- }
- auto psm = le_cid_token_to_channel_map_[cid];
- if (le_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
- return false;
- }
- le_dynamic_channel_helper_map_[psm]->Disconnect(cid);
- return true;
+bool bluetooth::shim::L2CA_SetFixedChannelTout(const RawAddress& rem_bda,
+ uint16_t fixed_cid,
+ uint16_t idle_tout) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-uint8_t L2CA_LECocDataWrite(uint16_t cid, BT_HDR* p_data) {
- if (le_cid_token_to_channel_map_.count(cid) == 0) {
- LOG(ERROR) << __func__ << "Invalid cid: " << cid;
- osi_free(p_data);
- return 0;
- }
- auto psm = le_cid_token_to_channel_map_[cid];
- if (le_dynamic_channel_helper_map_.count(psm) == 0) {
- LOG(ERROR) << __func__ << "Not registered psm: " << psm;
- osi_free(p_data);
- return 0;
- }
- auto len = p_data->len;
- auto* data = p_data->data + p_data->offset;
- uint8_t sent_length =
- le_dynamic_channel_helper_map_[psm]->send(
- cid, MakeUniquePacket(data, len, IsPacketFlushable(p_data))) *
- len;
- osi_free(p_data);
- return sent_length;
+bool bluetooth::shim::L2CA_SetChnlFlushability(uint16_t cid,
+ bool is_flushable) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return false;
}
-void L2CA_SwitchRoleToCentral(const RawAddress& addr) {
- GetAclManager()->SwitchRole(ToGdAddress(addr), bluetooth::hci::Role::CENTRAL);
+uint16_t bluetooth::shim::L2CA_FlushChannel(uint16_t lcid,
+ uint16_t num_to_flush) {
+ LOG_INFO(LOG_TAG, "UNIMPLEMENTED %s", __func__);
+ return 0;
}
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/l2c_api.h b/main/shim/l2c_api.h
index de9d2e945..fc45560f1 100644
--- a/main/shim/l2c_api.h
+++ b/main/shim/l2c_api.h
@@ -18,10 +18,9 @@
#include <set>
#include <unordered_map>
-#include <vector>
#include "stack/include/l2c_api.h"
-#include "types/hci_role.h"
+#include "stack/l2cap/l2c_int.h"
namespace bluetooth {
namespace shim {
@@ -40,10 +39,8 @@ namespace shim {
* BTM_SetSecurityLevel().
*
******************************************************************************/
-uint16_t L2CA_Register(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level);
+uint16_t L2CA_Register(uint16_t psm, tL2CAP_APPL_INFO* p_cb_info,
+ bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info);
/*******************************************************************************
*
@@ -59,6 +56,18 @@ void L2CA_Deregister(uint16_t psm);
/*******************************************************************************
*
+ * Function L2CA_AllocatePSM
+ *
+ * Description Other layers call this function to find an unused PSM for
+ * L2CAP services.
+ *
+ * Returns PSM to use.
+ *
+ ******************************************************************************/
+uint16_t L2CA_AllocatePSM(void);
+
+/*******************************************************************************
+ *
* Function L2CA_AllocateLePSM
*
* Description Other layers call this function to find an unused LE PSM for
@@ -97,6 +106,36 @@ uint16_t L2CA_ConnectReq(uint16_t psm, const RawAddress& p_bd_addr);
/*******************************************************************************
*
+ * Function L2CA_ConnectRsp
+ *
+ * Description Higher layers call this function to accept an incoming
+ * L2CAP connection, for which they had gotten an connect
+ * indication callback.
+ *
+ * Returns true for success, false for failure
+ *
+ ******************************************************************************/
+bool L2CA_ConnectRsp(const RawAddress& p_bd_addr, uint8_t id, uint16_t lcid,
+ uint16_t result, uint16_t status);
+
+/*******************************************************************************
+ *
+ * Function L2CA_ErtmConnectReq
+ *
+ * Description Higher layers call this function to create an L2CAP
+ * connection that needs to use Enhanced Retransmission Mode.
+ * Note that the connection is not established at this time,
+ * but connection establishment gets started. The callback
+ * will be invoked when connection establishes or fails.
+ *
+ * Returns the CID of the connection, or 0 if it failed to start
+ *
+ ******************************************************************************/
+uint16_t L2CA_ErtmConnectReq(uint16_t psm, const RawAddress& p_bd_addr,
+ tL2CAP_ERTM_INFO* p_ertm_info);
+
+/*******************************************************************************
+ *
* Function L2CA_RegisterLECoc
*
* Description Other layers call this function to register for L2CAP
@@ -109,8 +148,7 @@ uint16_t L2CA_ConnectReq(uint16_t psm, const RawAddress& p_bd_addr);
* and BTM_SetSecurityLevel().
*
******************************************************************************/
-uint16_t L2CA_RegisterLECoc(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg);
+uint16_t L2CA_RegisterLECoc(uint16_t psm, tL2CAP_APPL_INFO* p_cb_info);
/*******************************************************************************
*
@@ -141,6 +179,21 @@ uint16_t L2CA_ConnectLECocReq(uint16_t psm, const RawAddress& p_bd_addr,
/*******************************************************************************
*
+ * Function L2CA_ConnectLECocRsp
+ *
+ * Description Higher layers call this function to accept an incoming
+ * L2CAP LE COC connection, for which they had gotten a connect
+ * indication callback.
+ *
+ * Returns true for success, false for failure
+ *
+ ******************************************************************************/
+bool L2CA_ConnectLECocRsp(const RawAddress& p_bd_addr, uint8_t id,
+ uint16_t lcid, uint16_t result, uint16_t status,
+ tL2CAP_LE_CFG_INFO* p_cfg);
+
+/*******************************************************************************
+ *
* Function L2CA_GetPeerLECocConfig
*
* Description Get peers configuration for LE Connection Oriented Channel.
@@ -150,52 +203,52 @@ uint16_t L2CA_ConnectLECocReq(uint16_t psm, const RawAddress& p_bd_addr,
******************************************************************************/
bool L2CA_GetPeerLECocConfig(uint16_t lcid, tL2CAP_LE_CFG_INFO* peer_cfg);
+// This function sets the callback routines for the L2CAP connection referred to
+// by |local_cid|. The callback routines can only be modified for outgoing
+// connections established by |L2CA_ConnectReq| or accepted incoming
+// connections. |callbacks| must not be NULL. This function returns true if the
+// callbacks could be updated, false if not (e.g. |local_cid| was not found).
+bool L2CA_SetConnectionCallbacks(uint16_t local_cid,
+ const tL2CAP_APPL_INFO* callbacks);
+
/*******************************************************************************
*
- * Function L2CA_ReconfigCreditBasedConnsReq
+ * Function L2CA_ErtmConnectRsp
*
- * Description Start reconfigure procedure on Credit Based Connection Oriented
- * Channels.
+ * Description Higher layers call this function to accept an incoming
+ * L2CAP connection, for which they had gotten an connect
+ * indication callback, and for which the higher layer wants
+ * to use Enhanced Retransmission Mode.
*
- * Return value: true if peer is connected
+ * Returns true for success, false for failure
*
******************************************************************************/
-
-bool L2CA_ReconfigCreditBasedConnsReq(const RawAddress& bd_addr,
- std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg);
+bool L2CA_ErtmConnectRsp(const RawAddress& p_bd_addr, uint8_t id, uint16_t lcid,
+ uint16_t result, uint16_t status,
+ tL2CAP_ERTM_INFO* p_ertm_info);
/*******************************************************************************
*
- * Function L2CA_ConnectCreditBasedReq
+ * Function L2CA_ConfigReq
*
- * Description With this function L2CAP will initiate setup of up to 5 credit
- * based connections for given psm using provided configuration.
- * L2CAP will notify user on the connection result, by calling
- * pL2CA_CreditBasedConnectCfm_Cb for each cid with a result.
+ * Description Higher layers call this function to send configuration.
*
- * Return value: vector of allocated local cids for the connection
+ * Returns true if configuration sent, else false
*
******************************************************************************/
-
-extern std::vector<uint16_t> L2CA_ConnectCreditBasedReq(
- uint16_t psm, const RawAddress& p_bd_addr, tL2CAP_LE_CFG_INFO* p_cfg);
+bool L2CA_ConfigReq(uint16_t cid, tL2CAP_CFG_INFO* p_cfg);
/*******************************************************************************
*
- * Function L2CA_ConnectCreditBasedRsp
+ * Function L2CA_ConfigRsp
*
- * Description Response for the pL2CA_CreditBasedConnectInd_Cb which is the
- * indication for peer requesting credit based connection.
+ * Description Higher layers call this function to send a configuration
+ * response.
*
- * Return value: true if peer is connected
+ * Returns true if configuration response sent, else false
*
******************************************************************************/
-
-extern bool L2CA_ConnectCreditBasedRsp(const RawAddress& p_bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids,
- uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg);
+bool L2CA_ConfigRsp(uint16_t cid, tL2CAP_CFG_INFO* p_cfg);
/*******************************************************************************
*
@@ -208,7 +261,17 @@ extern bool L2CA_ConnectCreditBasedRsp(const RawAddress& p_bd_addr, uint8_t id,
******************************************************************************/
bool L2CA_DisconnectReq(uint16_t cid);
-bool L2CA_DisconnectLECocReq(uint16_t cid);
+/*******************************************************************************
+ *
+ * Function L2CA_DisconnectRsp
+ *
+ * Description Higher layers call this function to acknowledge the
+ * disconnection of a channel.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+bool L2CA_DisconnectRsp(uint16_t cid);
/*******************************************************************************
*
@@ -224,13 +287,29 @@ bool L2CA_DisconnectLECocReq(uint16_t cid);
******************************************************************************/
uint8_t L2CA_DataWrite(uint16_t cid, BT_HDR* p_data);
-uint8_t L2CA_LECocDataWrite(uint16_t cid, BT_HDR* p_data);
-
// Given a local channel identifier, |lcid|, this function returns the bound
-// remote channel identifier, |rcid|. If
+// remote channel identifier, |rcid|, and the ACL link handle, |handle|. If
// |lcid| is not known or is invalid, this function returns false and does not
-// modify the value pointed at by |rcid|. |rcid| may be NULL.
-bool L2CA_GetRemoteCid(uint16_t lcid, uint16_t* rcid);
+// modify the values pointed at by |rcid| and |handle|. |rcid| and |handle| may
+// be NULL.
+bool L2CA_GetIdentifiers(uint16_t lcid, uint16_t* rcid, uint16_t* handle);
+
+/*******************************************************************************
+ *
+ * Function L2CA_SetIdleTimeout
+ *
+ * Description Higher layers call this function to set the idle timeout for
+ * a connection, or for all future connections. The "idle
+ * timeout" is the amount of time that a connection can remain
+ * up with no L2CAP channels on it. A timeout of zero means
+ * that the connection will be torn down immediately when the
+ * last channel is removed. A timeout of 0xFFFF means no
+ * timeout. Values are in seconds.
+ *
+ * Returns true if command succeeded, false if failed
+ *
+ ******************************************************************************/
+bool L2CA_SetIdleTimeout(uint16_t cid, uint16_t timeout, bool is_global);
/*******************************************************************************
*
@@ -268,6 +347,25 @@ uint8_t L2CA_SetTraceLevel(uint8_t trace_level);
/*******************************************************************************
*
+ * Function L2CA_SetDesireRole
+ *
+ * Description This function sets the desire role for L2CAP.
+ * If the new role is L2CAP_ROLE_ALLOW_SWITCH, allow switch on
+ * HciCreateConnection.
+ * If the new role is L2CAP_ROLE_DISALLOW_SWITCH, do not allow
+ * switch on HciCreateConnection.
+ *
+ * If the new role is a valid role (HCI_ROLE_MASTER or
+ * HCI_ROLE_SLAVE), the desire role is set to the new value.
+ * Otherwise, it is not changed.
+ *
+ * Returns the new (current) role
+ *
+ ******************************************************************************/
+uint8_t L2CA_SetDesireRole(uint8_t new_role);
+
+/*******************************************************************************
+ *
* Function L2CA_FlushChannel
*
* Description This function flushes none, some or all buffers queued up
@@ -293,7 +391,7 @@ uint16_t L2CA_FlushChannel(uint16_t lcid, uint16_t num_to_flush);
* Returns true if a valid channel, else false
*
******************************************************************************/
-bool L2CA_SetAclPriority(const RawAddress& bd_addr, tL2CAP_PRIORITY priority);
+bool L2CA_SetAclPriority(const RawAddress& bd_addr, uint8_t priority);
/*******************************************************************************
*
@@ -308,6 +406,32 @@ bool L2CA_SetTxPriority(uint16_t cid, tL2CAP_CHNL_PRIORITY priority);
/*******************************************************************************
*
+ * Function L2CA_SetFlushTimeout
+ *
+ * Description This function set the automatic flush time out in Baseband
+ * for ACL-U packets.
+ * BdAddr : the remote BD address of ACL link. If it is
+ * BT_DB_ANY then the flush time out will be applied
+ * to all ACL link.
+ * FlushTimeout: flush time out in ms
+ * 0x0000 : No automatic flush
+ * L2CAP_NO_RETRANSMISSION : No retransmission
+ * 0x0002 - 0xFFFE : flush time out, if
+ * (flush_tout * 8) + 3 / 5) <=
+ * HCI_MAX_AUTOMATIC_FLUSH_TIMEOUT
+ * (in 625us slot).
+ * Otherwise, return false.
+ * L2CAP_NO_AUTOMATIC_FLUSH : No automatic flush
+ *
+ * Returns true if command succeeded, false if failed
+ *
+ * NOTE This flush timeout applies to all logical channels active on
+ * the ACL link.
+ ******************************************************************************/
+bool L2CA_SetFlushTimeout(const RawAddress& bd_addr, uint16_t flush_tout);
+
+/*******************************************************************************
+ *
* Function L2CA_SetChnlFlushability
*
* Description Higher layers call this function to set a channels
@@ -361,6 +485,8 @@ bool L2CA_RegisterFixedChannel(uint16_t fixed_cid,
*
******************************************************************************/
bool L2CA_ConnectFixedChnl(uint16_t fixed_cid, const RawAddress& bd_addr);
+bool L2CA_ConnectFixedChnl(uint16_t fixed_cid, const RawAddress& bd_addr,
+ uint8_t initiating_phys);
/*******************************************************************************
*
@@ -394,21 +520,9 @@ uint16_t L2CA_SendFixedChnlData(uint16_t fixed_cid, const RawAddress& rem_bda,
******************************************************************************/
bool L2CA_RemoveFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda);
-uint16_t L2CA_GetLeHandle(const RawAddress& rem_bda);
-hci_role_t L2CA_GetBleConnRole(const RawAddress& bd_addr);
-
-void L2CA_LeConnectionUpdate(const RawAddress& rem_bda, uint16_t min_int,
- uint16_t max_int, uint16_t latency,
- uint16_t timeout, uint16_t min_ce_len,
- uint16_t max_ce_len);
-
-// When GATT discovery is in progress, use the minimal connection interval, and
-// reject remote connection updates, until done.
-bool L2CA_EnableUpdateBleConnParams(const RawAddress& rem_bda, bool enable);
-
/*******************************************************************************
*
- * Function L2CA_SetLeGattTimeout
+ * Function L2CA_SetFixedChannelTout
*
* Description Higher layers call this function to set the idle timeout for
* a fixed channel. The "idle timeout" is the amount of time
@@ -423,8 +537,36 @@ bool L2CA_EnableUpdateBleConnParams(const RawAddress& rem_bda, bool enable);
* Returns true if command succeeded, false if failed
*
******************************************************************************/
-bool L2CA_SetLeGattTimeout(const RawAddress& rem_bda, uint16_t idle_tout);
+bool L2CA_SetFixedChannelTout(const RawAddress& rem_bda, uint16_t fixed_cid,
+ uint16_t idle_tout);
+
+/*******************************************************************************
+ *
+ * Function L2CA_CancelBleConnectReq
+ *
+ * Description Cancel a pending connection attempt to a BLE device.
+ *
+ * Parameters: BD Address of remote
+ *
+ * Return value: true if connection was cancelled
+ *
+ ******************************************************************************/
+bool L2CA_CancelBleConnectReq(const RawAddress& rem_bda);
+/*******************************************************************************
+ *
+ * Function L2CA_UpdateBleConnParams
+ *
+ * Description Update BLE connection parameters.
+ *
+ * Parameters: BD Address of remote
+ *
+ * Return value: true if update started
+ *
+ ******************************************************************************/
+bool L2CA_UpdateBleConnParams(const RawAddress& rem_bdRa, uint16_t min_int,
+ uint16_t max_int, uint16_t latency,
+ uint16_t timeout);
bool L2CA_UpdateBleConnParams(const RawAddress& rem_bda, uint16_t min_int,
uint16_t max_int, uint16_t latency,
uint16_t timeout, uint16_t min_ce_len,
@@ -453,39 +595,26 @@ bool L2CA_EnableUpdateBleConnParams(const RawAddress& rem_bda, bool enable);
* Returns link role.
*
******************************************************************************/
-hci_role_t L2CA_GetBleConnRole(const RawAddress& bd_addr);
-
-/**
- * Check whether an ACL or LE link to the remote device is established
- */
-bool L2CA_IsLinkEstablished(const RawAddress& bd_addr, tBT_TRANSPORT transport);
-
-void L2CA_ConnectForSecurity(const RawAddress& bd_addr);
-
-// Set bonding state to acquire/release link refcount
-void L2CA_SetBondingState(const RawAddress& p_bd_addr, bool is_bonding);
-
-// Indicated by shim stack manager that GD L2cap is enabled but Security is not
-void L2CA_UseLegacySecurityModule();
+uint8_t L2CA_GetBleConnRole(const RawAddress& bd_addr);
-void L2CA_SwitchRoleToCentral(const RawAddress& addr);
-
-bool L2CA_ReadRemoteVersion(const RawAddress& addr, uint8_t* lmp_version,
- uint16_t* manufacturer, uint16_t* lmp_sub_version);
-
-uint8_t* L2CA_ReadRemoteFeatures(const RawAddress& addr);
-
-void L2CA_DisconnectLink(const RawAddress& remote);
-
-uint16_t L2CA_GetNumLinks();
-
-bool L2CA_IsLeLink(uint16_t acl_handle);
-
-void L2CA_ReadConnectionAddr(const RawAddress& pseudo_addr,
- RawAddress& conn_addr, uint8_t* p_addr_type);
+/*******************************************************************************
+ *
+ * Function L2CA_GetDisconnectReason
+ *
+ * Description This function returns the disconnect reason code.
+ *
+ * Parameters: BD Address of remote
+ * Physical transport for the L2CAP connection (BR/EDR or LE)
+ *
+ * Returns disconnect reason
+ *
+ ******************************************************************************/
+uint16_t L2CA_GetDisconnectReason(const RawAddress& remote_bda,
+ tBT_TRANSPORT transport);
-bool L2CA_ReadRemoteConnectionAddr(const RawAddress& pseudo_addr,
- RawAddress& conn_addr, uint8_t* p_addr_type);
+void L2CA_AdjustConnectionIntervals(uint16_t* min_interval,
+ uint16_t* max_interval,
+ uint16_t floor_interval);
} // namespace shim
} // namespace bluetooth
diff --git a/main/shim/l2cap.cc b/main/shim/l2cap.cc
new file mode 100644
index 000000000..3bd011cdc
--- /dev/null
+++ b/main/shim/l2cap.cc
@@ -0,0 +1,420 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#define LOG_TAG "bt_shim_l2cap"
+
+#include <cstdint>
+
+#include "main/shim/dumpsys.h"
+#include "main/shim/entry.h"
+#include "main/shim/l2cap.h"
+#include "main/shim/shim.h"
+#include "osi/include/allocator.h"
+#include "osi/include/log.h"
+
+#include "shim/l2cap.h"
+
+namespace {
+constexpr char kModuleName[] = "shim::legacy::L2cap";
+constexpr bool kDisconnectResponseRequired = false;
+constexpr size_t kBtHdrSize = sizeof(BT_HDR);
+constexpr uint16_t kConnectionFail = 1;
+constexpr uint16_t kConnectionSuccess = 0;
+constexpr uint16_t kInvalidConnectionInterfaceDescriptor = 0;
+constexpr uint8_t kUnusedId = 0;
+constexpr uint16_t kUnusedResult = 0;
+} // namespace
+
+bool bluetooth::shim::legacy::PsmManager::IsPsmRegistered(uint16_t psm) const {
+ return psm_to_callback_map_.find(psm) != psm_to_callback_map_.end();
+}
+
+bool bluetooth::shim::legacy::PsmManager::HasClient(uint16_t psm) const {
+ return IsPsmRegistered(psm) && psm_to_callback_map_.at(psm) != nullptr;
+}
+
+void bluetooth::shim::legacy::PsmManager::RegisterPsm(
+ uint16_t psm, const tL2CAP_APPL_INFO* callbacks) {
+ CHECK(!HasClient(psm));
+ psm_to_callback_map_[psm] = callbacks;
+}
+
+void bluetooth::shim::legacy::PsmManager::RegisterPsm(uint16_t psm) {
+ RegisterPsm(psm, nullptr);
+}
+
+void bluetooth::shim::legacy::PsmManager::UnregisterPsm(uint16_t psm) {
+ CHECK(IsPsmRegistered(psm));
+ psm_to_callback_map_.erase(psm);
+}
+
+const tL2CAP_APPL_INFO* bluetooth::shim::legacy::PsmManager::Callbacks(
+ uint16_t psm) {
+ CHECK(HasClient(psm));
+ return psm_to_callback_map_[psm];
+}
+
+bluetooth::shim::legacy::L2cap::L2cap()
+ : classic_dynamic_psm_(kInitialClassicDynamicPsm),
+ le_dynamic_psm_(kInitialLeDynamicPsm),
+ classic_virtual_psm_(kInitialClassicVirtualPsm) {
+ bluetooth::shim::RegisterDumpsysFunction(static_cast<void*>(this),
+ [this](int fd) { Dump(fd); });
+}
+
+bluetooth::shim::legacy::L2cap::~L2cap() {
+ bluetooth::shim::UnregisterDumpsysFunction(static_cast<void*>(this));
+}
+
+bluetooth::shim::legacy::PsmManager& bluetooth::shim::legacy::L2cap::Le() {
+ return le_;
+}
+
+bluetooth::shim::legacy::PsmManager& bluetooth::shim::legacy::L2cap::Classic() {
+ return classic_;
+}
+
+bool bluetooth::shim::legacy::L2cap::ConnectionExists(uint16_t cid) const {
+ return cid_to_psm_map_.find(cid) != cid_to_psm_map_.end();
+}
+
+uint16_t bluetooth::shim::legacy::L2cap::CidToPsm(uint16_t cid) const {
+ CHECK(ConnectionExists(cid));
+ return cid_to_psm_map_.at(cid);
+}
+
+uint16_t bluetooth::shim::legacy::L2cap::ConvertClientToRealPsm(
+ uint16_t client_psm, bool is_outgoing_only_connection) {
+ if (!is_outgoing_only_connection) {
+ return client_psm;
+ }
+ return GetNextVirtualPsm(client_psm);
+}
+
+uint16_t bluetooth::shim::legacy::L2cap::ConvertClientToRealPsm(
+ uint16_t client_psm) {
+ if (client_psm_to_real_psm_map_.find(client_psm) ==
+ client_psm_to_real_psm_map_.end()) {
+ return client_psm;
+ }
+ return client_psm_to_real_psm_map_.at(client_psm);
+}
+
+void bluetooth::shim::legacy::L2cap::RemoveClientPsm(uint16_t client_psm) {
+ if (client_psm_to_real_psm_map_.find(client_psm) !=
+ client_psm_to_real_psm_map_.end()) {
+ client_psm_to_real_psm_map_.erase(client_psm);
+ }
+}
+
+uint16_t bluetooth::shim::legacy::L2cap::GetNextVirtualPsm(uint16_t real_psm) {
+ if (real_psm < kInitialClassicDynamicPsm) {
+ return real_psm;
+ }
+
+ while (Classic().IsPsmRegistered(classic_virtual_psm_)) {
+ classic_virtual_psm_ += 2;
+ if (classic_virtual_psm_ >= kFinalClassicVirtualPsm) {
+ classic_virtual_psm_ = kInitialClassicVirtualPsm;
+ }
+ }
+ return classic_virtual_psm_;
+}
+
+uint16_t bluetooth::shim::legacy::L2cap::GetNextDynamicLePsm() {
+ while (Le().IsPsmRegistered(le_dynamic_psm_)) {
+ le_dynamic_psm_++;
+ if (le_dynamic_psm_ > kFinalLeDynamicPsm) {
+ le_dynamic_psm_ = kInitialLeDynamicPsm;
+ }
+ }
+ return le_dynamic_psm_;
+}
+
+uint16_t bluetooth::shim::legacy::L2cap::GetNextDynamicClassicPsm() {
+ while (Classic().IsPsmRegistered(classic_dynamic_psm_)) {
+ classic_dynamic_psm_ += 2;
+ if (classic_dynamic_psm_ > kFinalClassicDynamicPsm) {
+ classic_dynamic_psm_ = kInitialClassicDynamicPsm;
+ } else if (classic_dynamic_psm_ & 0x0100) {
+ /* the upper byte must be even */
+ classic_dynamic_psm_ += 0x0100;
+ }
+
+ /* if psm is in range of reserved BRCM Aware features */
+ if ((BRCM_RESERVED_PSM_START <= classic_dynamic_psm_) &&
+ (classic_dynamic_psm_ <= BRCM_RESERVED_PSM_END)) {
+ classic_dynamic_psm_ = BRCM_RESERVED_PSM_END + 2;
+ }
+ }
+ return classic_dynamic_psm_;
+}
+
+uint16_t bluetooth::shim::legacy::L2cap::RegisterService(
+ uint16_t psm, const tL2CAP_APPL_INFO* callbacks, bool enable_snoop,
+ tL2CAP_ERTM_INFO* p_ertm_info) {
+ if (Classic().IsPsmRegistered(psm)) {
+ LOG_WARN(LOG_TAG, "Service is already registered psm:%hd", psm);
+ return 0;
+ }
+ if (!enable_snoop) {
+ LOG_INFO(LOG_TAG, "Disable snooping on psm basis unsupported psm:%d", psm);
+ }
+
+ LOG_DEBUG(LOG_TAG, "Registering service on psm:%hd", psm);
+ RegisterServicePromise register_promise;
+ auto service_registered = register_promise.get_future();
+ bool use_ertm = false;
+ if (p_ertm_info != nullptr &&
+ p_ertm_info->preferred_mode == L2CAP_FCR_ERTM_MODE) {
+ use_ertm = true;
+ }
+ constexpr auto mtu = 1000; // TODO: Let client decide
+ bluetooth::shim::GetL2cap()->RegisterService(
+ psm, use_ertm, mtu,
+ std::bind(
+ &bluetooth::shim::legacy::L2cap::OnRemoteInitiatedConnectionCreated,
+ this, std::placeholders::_1, std::placeholders::_2,
+ std::placeholders::_3),
+ std::move(register_promise));
+
+ uint16_t registered_psm = service_registered.get();
+ if (registered_psm != psm) {
+ LOG_WARN(LOG_TAG, "Unable to register psm:%hd", psm);
+ } else {
+ LOG_DEBUG(LOG_TAG, "Successfully registered psm:%hd", psm);
+ Classic().RegisterPsm(registered_psm, callbacks);
+ }
+ return registered_psm;
+}
+
+void bluetooth::shim::legacy::L2cap::UnregisterService(uint16_t psm) {
+ if (!Classic().IsPsmRegistered(psm)) {
+ LOG_WARN(LOG_TAG,
+ "Service must be registered in order to unregister psm:%hd", psm);
+ return;
+ }
+ for (auto& entry : cid_to_psm_map_) {
+ if (entry.second == psm) {
+ LOG_WARN(LOG_TAG,
+ " Unregistering service with active channels psm:%hd cid:%hd",
+ psm, entry.first);
+ }
+ }
+
+ LOG_DEBUG(LOG_TAG, "Unregistering service on psm:%hd", psm);
+ UnregisterServicePromise unregister_promise;
+ auto service_unregistered = unregister_promise.get_future();
+ bluetooth::shim::GetL2cap()->UnregisterService(psm,
+ std::move(unregister_promise));
+ service_unregistered.wait();
+ Classic().UnregisterPsm(psm);
+}
+
+uint16_t bluetooth::shim::legacy::L2cap::CreateConnection(
+ uint16_t psm, const RawAddress& raw_address) {
+ if (!Classic().IsPsmRegistered(psm)) {
+ LOG_WARN(LOG_TAG, "Service must be registered in order to connect psm:%hd",
+ psm);
+ return kInvalidConnectionInterfaceDescriptor;
+ }
+
+ CreateConnectionPromise create_promise;
+ auto created = create_promise.get_future();
+ LOG_DEBUG(LOG_TAG, "Initiating local connection to psm:%hd address:%s", psm,
+ raw_address.ToString().c_str());
+
+ bluetooth::shim::GetL2cap()->CreateConnection(
+ psm, raw_address.ToString(),
+ std::bind(
+ &bluetooth::shim::legacy::L2cap::OnLocalInitiatedConnectionCreated,
+ this, std::placeholders::_1, std::placeholders::_2,
+ std::placeholders::_3, std::placeholders::_4),
+ std::move(create_promise));
+
+ uint16_t cid = created.get();
+ if (cid == kInvalidConnectionInterfaceDescriptor) {
+ LOG_WARN(LOG_TAG,
+ "Failed to initiate connection interface to psm:%hd address:%s",
+ psm, raw_address.ToString().c_str());
+ } else {
+ LOG_DEBUG(LOG_TAG,
+ "Successfully initiated connection to psm:%hd address:%s"
+ " connection_interface_descriptor:%hd",
+ psm, raw_address.ToString().c_str(), cid);
+ CHECK(!ConnectionExists(cid));
+ cid_to_psm_map_[cid] = psm;
+ }
+ return cid;
+}
+
+void bluetooth::shim::legacy::L2cap::OnLocalInitiatedConnectionCreated(
+ std::string string_address, uint16_t psm, uint16_t cid, bool connected) {
+ if (cid_closing_set_.count(cid) == 0) {
+ if (connected) {
+ SetDownstreamCallbacks(cid);
+ } else {
+ LOG_WARN(LOG_TAG,
+ "Failed intitiating connection remote:%s psm:%hd cid:%hd",
+ string_address.c_str(), psm, cid);
+ }
+ Classic().Callbacks(psm)->pL2CA_ConnectCfm_Cb(
+ cid, connected ? (kConnectionSuccess) : (kConnectionFail));
+ } else {
+ LOG_DEBUG(LOG_TAG, "Connection Closed before presentation to upper layer");
+ if (connected) {
+ SetDownstreamCallbacks(cid);
+ bluetooth::shim::GetL2cap()->CloseConnection(cid);
+ } else {
+ LOG_DEBUG(LOG_TAG, "Connection failed after initiator closed");
+ }
+ }
+}
+
+void bluetooth::shim::legacy::L2cap::OnRemoteInitiatedConnectionCreated(
+ std::string string_address, uint16_t psm, uint16_t cid) {
+ RawAddress raw_address;
+ RawAddress::FromString(string_address, raw_address);
+
+ LOG_DEBUG(LOG_TAG,
+ "Sending connection indicator to upper stack from device:%s "
+ "psm:%hd cid:%hd",
+ string_address.c_str(), psm, cid);
+
+ CHECK(!ConnectionExists(cid));
+ cid_to_psm_map_[cid] = psm;
+ SetDownstreamCallbacks(cid);
+ Classic().Callbacks(psm)->pL2CA_ConnectInd_Cb(raw_address, cid, psm,
+ kUnusedId);
+}
+
+bool bluetooth::shim::legacy::L2cap::Write(uint16_t cid, BT_HDR* bt_hdr) {
+ CHECK(bt_hdr != nullptr);
+ const uint8_t* data = bt_hdr->data + bt_hdr->offset;
+ size_t len = bt_hdr->len;
+ if (!ConnectionExists(cid) || len == 0) {
+ return false;
+ }
+ LOG_DEBUG(LOG_TAG, "Writing data cid:%hd len:%zd", cid, len);
+ bluetooth::shim::GetL2cap()->Write(cid, data, len);
+ return true;
+}
+
+void bluetooth::shim::legacy::L2cap::SetDownstreamCallbacks(uint16_t cid) {
+ bluetooth::shim::GetL2cap()->SetReadDataReadyCallback(
+ cid, [this](uint16_t cid, std::vector<const uint8_t> data) {
+ LOG_DEBUG(LOG_TAG, "OnDataReady cid:%hd len:%zd", cid, data.size());
+ BT_HDR* bt_hdr =
+ static_cast<BT_HDR*>(osi_calloc(data.size() + kBtHdrSize));
+ std::copy(data.begin(), data.end(), bt_hdr->data);
+ bt_hdr->len = data.size();
+ classic_.Callbacks(CidToPsm(cid))->pL2CA_DataInd_Cb(cid, bt_hdr);
+ });
+
+ bluetooth::shim::GetL2cap()->SetConnectionClosedCallback(
+ cid, [this](uint16_t cid, int error_code) {
+ LOG_DEBUG(LOG_TAG, "OnChannel closed callback cid:%hd", cid);
+ if (!ConnectionExists(cid)) {
+ LOG_WARN(LOG_TAG, "%s Unexpected channel closure cid:%hd", __func__,
+ cid);
+ return;
+ }
+ if (cid_closing_set_.count(cid) == 1) {
+ cid_closing_set_.erase(cid);
+ classic_.Callbacks(CidToPsm(cid))
+ ->pL2CA_DisconnectCfm_Cb(cid, kUnusedResult);
+ } else {
+ classic_.Callbacks(CidToPsm(cid))
+ ->pL2CA_DisconnectInd_Cb(cid, kDisconnectResponseRequired);
+ }
+ cid_to_psm_map_.erase(cid);
+ });
+}
+
+bool bluetooth::shim::legacy::L2cap::ConnectResponse(
+ const RawAddress& raw_address, uint8_t signal_id, uint16_t cid,
+ uint16_t result, uint16_t status, tL2CAP_ERTM_INFO* ertm_info) {
+ CHECK(ConnectionExists(cid));
+ LOG_DEBUG(LOG_TAG,
+ "%s Silently dropping client connect response as channel is "
+ "already connected",
+ __func__);
+ return true;
+}
+
+bool bluetooth::shim::legacy::L2cap::ConfigRequest(
+ uint16_t cid, const tL2CAP_CFG_INFO* config_info) {
+ LOG_INFO(LOG_TAG, "Received config request from upper layer cid:%hd", cid);
+ CHECK(ConnectionExists(cid));
+
+ bluetooth::shim::GetL2cap()->SendLoopbackResponse([this, cid]() {
+ CHECK(ConnectionExists(cid));
+ tL2CAP_CFG_INFO cfg_info{
+ .result = L2CAP_CFG_OK,
+ .mtu_present = false,
+ .qos_present = false,
+ .flush_to_present = false,
+ .fcr_present = false,
+ .fcs_present = false,
+ .ext_flow_spec_present = false,
+ .flags = 0,
+ };
+ classic_.Callbacks(CidToPsm(cid))->pL2CA_ConfigCfm_Cb(cid, &cfg_info);
+ classic_.Callbacks(CidToPsm(cid))->pL2CA_ConfigInd_Cb(cid, &cfg_info);
+ });
+ return true;
+}
+
+bool bluetooth::shim::legacy::L2cap::ConfigResponse(
+ uint16_t cid, const tL2CAP_CFG_INFO* config_info) {
+ CHECK(ConnectionExists(cid));
+ LOG_DEBUG(
+ LOG_TAG,
+ "%s Silently dropping client config response as channel is already open",
+ __func__);
+ return true;
+}
+
+bool bluetooth::shim::legacy::L2cap::DisconnectRequest(uint16_t cid) {
+ CHECK(ConnectionExists(cid));
+ if (cid_closing_set_.find(cid) != cid_closing_set_.end()) {
+ LOG_WARN(LOG_TAG, "%s Channel already in closing state cid:%hu", __func__,
+ cid);
+ return false;
+ }
+ LOG_DEBUG(LOG_TAG, "%s initiated locally cid:%hu", __func__, cid);
+ cid_closing_set_.insert(cid);
+ bluetooth::shim::GetL2cap()->CloseConnection(cid);
+ return true;
+}
+
+bool bluetooth::shim::legacy::L2cap::DisconnectResponse(uint16_t cid) {
+ LOG_DEBUG(LOG_TAG,
+ "%s Silently dropping client disconnect response as channel is "
+ "already disconnected",
+ __func__);
+ return true;
+}
+
+void bluetooth::shim::legacy::L2cap::Dump(int fd) {
+ if (cid_to_psm_map_.empty()) {
+ dprintf(fd, "%s No active l2cap channels\n", kModuleName);
+ } else {
+ for (auto& connection : cid_to_psm_map_) {
+ dprintf(fd, "%s active l2cap channel cid:%hd psm:%hd\n", kModuleName,
+ connection.first, connection.second);
+ }
+ }
+}
diff --git a/main/shim/l2cap.h b/main/shim/l2cap.h
new file mode 100644
index 000000000..b1e3755d3
--- /dev/null
+++ b/main/shim/l2cap.h
@@ -0,0 +1,126 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#pragma once
+
+#include <cstdint>
+#include <set>
+#include <unordered_map>
+
+#include "main/shim/dumpsys.h"
+#include "stack/include/l2c_api.h"
+
+namespace bluetooth {
+namespace shim {
+namespace legacy {
+
+static constexpr uint16_t kInitialClassicDynamicPsm = 0x1001;
+static constexpr uint16_t kFinalClassicDynamicPsm = 0xfeff;
+static constexpr uint16_t kInitialClassicVirtualPsm = kInitialClassicDynamicPsm;
+static constexpr uint16_t kFinalClassicVirtualPsm = 0x8000;
+static constexpr uint16_t kInitialLeDynamicPsm = 0x0080;
+static constexpr uint16_t kFinalLeDynamicPsm = 0x00ff;
+
+class PsmManager {
+ public:
+ bool IsPsmRegistered(uint16_t psm) const;
+ bool HasClient(uint16_t psm) const;
+ void RegisterPsm(uint16_t psm, const tL2CAP_APPL_INFO* callbacks);
+ void RegisterPsm(uint16_t psm);
+ void UnregisterPsm(uint16_t psm);
+ const tL2CAP_APPL_INFO* Callbacks(uint16_t psm);
+
+ private:
+ /**
+ * Mapping of psm to client callback.
+ *
+ * The current API allows a client may reserve a psm but not
+ * provide a callback which is reflected in a mapping of a
+ * valid psm key entry but a nullptr value.
+ *
+ * A valid client is indicated with a valid psm key entry and a
+ * non-nullptr value.
+ */
+ std::unordered_map<uint16_t, const tL2CAP_APPL_INFO*> psm_to_callback_map_;
+};
+
+class L2cap {
+ public:
+ uint16_t RegisterService(uint16_t psm, const tL2CAP_APPL_INFO* callbacks,
+ bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info);
+ void UnregisterService(uint16_t psm);
+
+ uint16_t CreateConnection(uint16_t psm, const RawAddress& raw_address);
+
+ bool Write(uint16_t cid, BT_HDR* bt_hdr);
+
+ void OnLocalInitiatedConnectionCreated(std::string string_address,
+ uint16_t psm, uint16_t cid,
+ bool connected);
+ void OnRemoteInitiatedConnectionCreated(std::string string_addresss,
+ uint16_t psm, uint16_t cid);
+
+ uint16_t GetNextDynamicClassicPsm();
+ uint16_t GetNextDynamicLePsm();
+
+ uint16_t ConvertClientToRealPsm(uint16_t psm,
+ bool is_outgoing_only_connection);
+ uint16_t ConvertClientToRealPsm(uint16_t psm);
+ void RemoveClientPsm(uint16_t client_psm);
+
+ // Legacy API entry points
+ bool ConnectResponse(const RawAddress& raw_address, uint8_t signal_id,
+ uint16_t cid, uint16_t result, uint16_t status,
+ tL2CAP_ERTM_INFO* ertm_info);
+ bool ConfigRequest(uint16_t cid, const tL2CAP_CFG_INFO* config_info);
+ bool ConfigResponse(uint16_t cid, const tL2CAP_CFG_INFO* config_info);
+ bool DisconnectRequest(uint16_t cid);
+ bool DisconnectResponse(uint16_t cid);
+
+ L2cap();
+ ~L2cap();
+
+ PsmManager& Classic();
+ PsmManager& Le();
+
+ private:
+ uint16_t GetNextVirtualPsm(uint16_t real_psm);
+ void SetDownstreamCallbacks(uint16_t cid);
+
+ void Dump(int fd);
+
+ PsmManager classic_;
+ PsmManager le_;
+
+ bool ConnectionExists(uint16_t cid) const;
+ uint16_t CidToPsm(uint16_t cid) const;
+
+ uint16_t classic_dynamic_psm_;
+ uint16_t le_dynamic_psm_;
+ uint16_t classic_virtual_psm_;
+
+ std::unordered_map<uint16_t,
+ std::function<void(std::function<void(uint16_t c)>)>>
+ cid_to_postable_map_;
+ std::set<uint16_t> cid_closing_set_;
+
+ std::unordered_map<uint16_t, uint16_t> cid_to_psm_map_;
+ std::unordered_map<uint16_t, uint16_t> client_psm_to_real_psm_map_;
+};
+
+} // namespace legacy
+} // namespace shim
+} // namespace bluetooth
diff --git a/main/shim/le_advertising_manager.cc b/main/shim/le_advertising_manager.cc
deleted file mode 100644
index a91f7426b..000000000
--- a/main/shim/le_advertising_manager.cc
+++ /dev/null
@@ -1,365 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "bt_shim_advertiser"
-
-#include "le_advertising_manager.h"
-
-#include <hardware/bluetooth.h>
-#include <hardware/bt_gatt.h>
-
-#include <vector>
-#include "gd/common/init_flags.h"
-#include "gd/hci/acl_manager.h"
-#include "gd/hci/controller.h"
-#include "gd/hci/le_advertising_manager.h"
-#include "gd/packet/packet_view.h"
-#include "gd/storage/storage_module.h"
-#include "main/shim/entry.h"
-
-#include "btif/include/btif_common.h"
-#include "stack/include/ble_advertiser.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btu.h"
-
-using bluetooth::hci::Address;
-using bluetooth::hci::AddressType;
-using bluetooth::hci::ErrorCode;
-using bluetooth::hci::GapData;
-using bluetooth::hci::OwnAddressType;
-using std::vector;
-
-class BleAdvertiserInterfaceImpl : public BleAdvertiserInterface,
- public bluetooth::hci::AdvertisingCallback {
- public:
- ~BleAdvertiserInterfaceImpl() override{};
-
- void Init() {
- // Register callback
- bluetooth::shim::GetAdvertising()->RegisterAdvertisingCallback(this);
- }
-
- // nobody use this function
- void RegisterAdvertiser(IdStatusCallback cb) override {
- LOG(INFO) << __func__ << " in shim layer";
- }
-
- void Unregister(uint8_t advertiser_id) override {
- LOG(INFO) << __func__ << " in shim layer";
- bluetooth::shim::GetAdvertising()->RemoveAdvertiser(advertiser_id);
- }
-
- // only for PTS test
- void GetOwnAddress(uint8_t advertiser_id, GetAddressCallback cb) override {
- LOG(INFO) << __func__ << " in shim layer";
- }
-
- void SetParameters(uint8_t advertiser_id, AdvertiseParameters params,
- ParametersCallback cb) override {
- LOG(INFO) << __func__ << " in shim layer";
- bluetooth::hci::ExtendedAdvertisingConfig config{};
- parse_parameter(config, params);
- bluetooth::shim::GetAdvertising()->SetParameters(advertiser_id, config);
- }
-
- void SetData(int advertiser_id, bool set_scan_rsp, vector<uint8_t> data,
- StatusCallback cb) override {
- LOG(INFO) << __func__ << " in shim layer";
-
- size_t offset = 0;
- std::vector<GapData> advertising_data = {};
-
- while (offset < data.size()) {
- GapData gap_data;
- uint8_t len = data[offset];
- auto begin = data.begin() + offset;
- auto end = begin + len + 1; // 1 byte for len
- auto data_copy = std::make_shared<std::vector<uint8_t>>(begin, end);
- bluetooth::packet::PacketView<bluetooth::packet::kLittleEndian> packet(
- data_copy);
- GapData::Parse(&gap_data, packet.begin());
- advertising_data.push_back(gap_data);
- offset += len + 1; // 1 byte for len
- }
-
- bluetooth::shim::GetAdvertising()->SetData(advertiser_id, set_scan_rsp,
- advertising_data);
- }
-
- void Enable(uint8_t advertiser_id, bool enable, StatusCallback cb,
- uint16_t duration, uint8_t maxExtAdvEvents,
- StatusCallback timeout_cb) override {
- LOG(INFO) << __func__ << " in shim layer";
- bluetooth::shim::GetAdvertising()->EnableAdvertiser(
- advertiser_id, enable, duration, maxExtAdvEvents);
- }
-
- // nobody use this function
- void StartAdvertising(uint8_t advertiser_id, StatusCallback cb,
- AdvertiseParameters params,
- std::vector<uint8_t> advertise_data,
- std::vector<uint8_t> scan_response_data, int timeout_s,
- MultiAdvCb timeout_cb) override {
- LOG(INFO) << __func__ << " in shim layer";
- }
-
- void StartAdvertisingSet(int reg_id, IdTxPowerStatusCallback register_cb,
- AdvertiseParameters params,
- std::vector<uint8_t> advertise_data,
- std::vector<uint8_t> scan_response_data,
- PeriodicAdvertisingParameters periodic_params,
- std::vector<uint8_t> periodic_data,
- uint16_t duration, uint8_t maxExtAdvEvents,
- IdStatusCallback timeout_cb) {
- LOG(INFO) << __func__ << " in shim layer";
-
- bluetooth::hci::ExtendedAdvertisingConfig config{};
- parse_parameter(config, params);
- bluetooth::hci::PeriodicAdvertisingParameters periodic_parameters;
- periodic_parameters.max_interval = periodic_params.max_interval;
- periodic_parameters.min_interval = periodic_params.min_interval;
- periodic_parameters.properties =
- periodic_params.periodic_advertising_properties;
- config.periodic_advertising_parameters = periodic_parameters;
-
- size_t offset = 0;
- while (offset < advertise_data.size()) {
- GapData gap_data;
- uint8_t len = advertise_data[offset];
- auto begin = advertise_data.begin() + offset;
- auto end = begin + len + 1; // 1 byte for len
- auto data_copy = std::make_shared<std::vector<uint8_t>>(begin, end);
- bluetooth::packet::PacketView<bluetooth::packet::kLittleEndian> packet(
- data_copy);
- GapData::Parse(&gap_data, packet.begin());
- config.advertisement.push_back(gap_data);
- offset += len + 1; // 1 byte for len
- }
-
- offset = 0;
- while (offset < scan_response_data.size()) {
- GapData gap_data;
- uint8_t len = scan_response_data[offset];
- auto begin = scan_response_data.begin() + offset;
- auto end = begin + len + 1; // 1 byte for len
- auto data_copy = std::make_shared<std::vector<uint8_t>>(begin, end);
- bluetooth::packet::PacketView<bluetooth::packet::kLittleEndian> packet(
- data_copy);
- GapData::Parse(&gap_data, packet.begin());
- config.scan_response.push_back(gap_data);
- offset += len + 1; // 1 byte for len
- }
-
- offset = 0;
- while (offset < periodic_data.size()) {
- GapData gap_data;
- uint8_t len = periodic_data[offset];
- auto begin = periodic_data.begin() + offset;
- auto end = begin + len + 1; // 1 byte for len
- auto data_copy = std::make_shared<std::vector<uint8_t>>(begin, end);
- bluetooth::packet::PacketView<bluetooth::packet::kLittleEndian> packet(
- data_copy);
- GapData::Parse(&gap_data, packet.begin());
- config.periodic_data.push_back(gap_data);
- offset += len + 1; // 1 byte for len
- }
-
- bluetooth::hci::AdvertiserId id =
- bluetooth::shim::GetAdvertising()->ExtendedCreateAdvertiser(
- reg_id, config, scan_callback, set_terminated_callback, duration,
- maxExtAdvEvents, bluetooth::shim::GetGdShimHandler());
-
- LOG(INFO) << "create advertising set, reg_id:" << reg_id
- << ", id:" << (uint16_t)id;
- }
-
- void SetPeriodicAdvertisingParameters(
- int advertiser_id, PeriodicAdvertisingParameters periodic_params,
- StatusCallback cb) override {
- LOG(INFO) << __func__ << " in shim layer";
- bluetooth::hci::PeriodicAdvertisingParameters parameters;
- parameters.max_interval = periodic_params.max_interval;
- parameters.min_interval = periodic_params.min_interval;
- parameters.properties = periodic_params.periodic_advertising_properties;
- bluetooth::shim::GetAdvertising()->SetPeriodicParameters(advertiser_id,
- parameters);
- }
-
- void SetPeriodicAdvertisingData(int advertiser_id, std::vector<uint8_t> data,
- StatusCallback cb) override {
- LOG(INFO) << __func__ << " in shim layer";
-
- size_t offset = 0;
- std::vector<GapData> advertising_data = {};
-
- while (offset < data.size()) {
- GapData gap_data;
- uint8_t len = data[offset];
- auto begin = data.begin() + offset;
- auto end = begin + len + 1; // 1 byte for len
- auto data_copy = std::make_shared<std::vector<uint8_t>>(begin, end);
- bluetooth::packet::PacketView<bluetooth::packet::kLittleEndian> packet(
- data_copy);
- GapData::Parse(&gap_data, packet.begin());
- advertising_data.push_back(gap_data);
- offset += len + 1; // 1 byte for len
- }
-
- bluetooth::shim::GetAdvertising()->SetPeriodicData(advertiser_id,
- advertising_data);
- }
-
- void SetPeriodicAdvertisingEnable(int advertiser_id, bool enable,
- StatusCallback cb) override {
- LOG(INFO) << __func__ << " in shim layer";
- bluetooth::shim::GetAdvertising()->EnablePeriodicAdvertising(advertiser_id,
- enable);
- }
-
- void RegisterCallbacks(AdvertisingCallbacks* callbacks) {
- advertising_callbacks_ = callbacks;
- }
-
- void on_scan(Address address, AddressType address_type) {
- LOG(INFO) << __func__ << " in shim layer";
- }
-
- void on_set_terminated(ErrorCode error_code, uint8_t, uint8_t) {
- LOG(INFO) << __func__ << " in shim layer";
- }
-
- const bluetooth::common::Callback<void(Address, AddressType)> scan_callback =
- bluetooth::common::Bind(&BleAdvertiserInterfaceImpl::on_scan,
- bluetooth::common::Unretained(this));
-
- const bluetooth::common::Callback<void(ErrorCode, uint8_t, uint8_t)>
- set_terminated_callback = bluetooth::common::Bind(
- &BleAdvertiserInterfaceImpl::on_set_terminated,
- bluetooth::common::Unretained(this));
-
- // AdvertisingCallback
- void OnAdvertisingSetStarted(int reg_id, uint8_t advertiser_id,
- int8_t tx_power,
- AdvertisingStatus status) override {
- do_in_jni_thread(
- FROM_HERE, base::Bind(&AdvertisingCallbacks::OnAdvertisingSetStarted,
- base::Unretained(advertising_callbacks_), reg_id,
- advertiser_id, tx_power, status));
- }
-
- void OnAdvertisingEnabled(uint8_t advertiser_id, bool enable,
- uint8_t status) {
- do_in_jni_thread(FROM_HERE,
- base::Bind(&AdvertisingCallbacks::OnAdvertisingEnabled,
- base::Unretained(advertising_callbacks_),
- advertiser_id, enable, status));
- }
-
- void OnAdvertisingDataSet(uint8_t advertiser_id, uint8_t status) {
- do_in_jni_thread(FROM_HERE,
- base::Bind(&AdvertisingCallbacks::OnAdvertisingDataSet,
- base::Unretained(advertising_callbacks_),
- advertiser_id, status));
- }
- void OnScanResponseDataSet(uint8_t advertiser_id, uint8_t status) {
- do_in_jni_thread(FROM_HERE,
- base::Bind(&AdvertisingCallbacks::OnScanResponseDataSet,
- base::Unretained(advertising_callbacks_),
- advertiser_id, status));
- }
-
- void OnAdvertisingParametersUpdated(uint8_t advertiser_id, int8_t tx_power,
- uint8_t status) {
- do_in_jni_thread(
- FROM_HERE,
- base::Bind(&AdvertisingCallbacks::OnAdvertisingParametersUpdated,
- base::Unretained(advertising_callbacks_), advertiser_id,
- tx_power, status));
- }
-
- void OnPeriodicAdvertisingParametersUpdated(uint8_t advertiser_id,
- uint8_t status) {
- do_in_jni_thread(
- FROM_HERE,
- base::Bind(
- &AdvertisingCallbacks::OnPeriodicAdvertisingParametersUpdated,
- base::Unretained(advertising_callbacks_), advertiser_id, status));
- }
-
- void OnPeriodicAdvertisingDataSet(uint8_t advertiser_id, uint8_t status) {
- do_in_jni_thread(
- FROM_HERE,
- base::Bind(&AdvertisingCallbacks::OnPeriodicAdvertisingDataSet,
- base::Unretained(advertising_callbacks_), advertiser_id,
- status));
- }
-
- void OnPeriodicAdvertisingEnabled(uint8_t advertiser_id, bool enable,
- uint8_t status) {
- do_in_jni_thread(
- FROM_HERE,
- base::Bind(&AdvertisingCallbacks::OnPeriodicAdvertisingEnabled,
- base::Unretained(advertising_callbacks_), advertiser_id,
- enable, status));
- }
-
- void OnOwnAddressRead(uint8_t advertiser_id, uint8_t address_type,
- RawAddress address) {
- do_in_jni_thread(FROM_HERE,
- base::Bind(&AdvertisingCallbacks::OnOwnAddressRead,
- base::Unretained(advertising_callbacks_),
- advertiser_id, address_type, address));
- }
-
- AdvertisingCallbacks* advertising_callbacks_;
-
- private:
- void parse_parameter(bluetooth::hci::ExtendedAdvertisingConfig& config,
- AdvertiseParameters params) {
- config.connectable = params.advertising_event_properties & 0x01;
- config.scannable = params.advertising_event_properties & 0x02;
- config.legacy_pdus = params.advertising_event_properties & 0x10;
- config.anonymous = params.advertising_event_properties & 0x20;
- config.include_tx_power = params.advertising_event_properties & 0x40;
- config.interval_min = params.min_interval;
- config.interval_max = params.max_interval;
- config.channel_map = params.channel_map;
- config.tx_power = params.tx_power;
- config.use_le_coded_phy = params.primary_advertising_phy == 0x03;
- config.secondary_advertising_phy =
- static_cast<bluetooth::hci::SecondaryPhyType>(
- params.secondary_advertising_phy);
- config.enable_scan_request_notifications =
- static_cast<bluetooth::hci::Enable>(
- params.scan_request_notification_enable);
-
- // TODO set own_address_type based on address policy
- config.own_address_type = OwnAddressType::RANDOM_DEVICE_ADDRESS;
- }
-};
-
-BleAdvertiserInterfaceImpl* bt_le_advertiser_instance = nullptr;
-
-BleAdvertiserInterface* bluetooth::shim::get_ble_advertiser_instance() {
- if (bt_le_advertiser_instance == nullptr) {
- bt_le_advertiser_instance = new BleAdvertiserInterfaceImpl();
- }
- return bt_le_advertiser_instance;
-};
-
-void bluetooth::shim::init_advertising_manager() {
- bt_le_advertiser_instance->Init();
-}
diff --git a/main/shim/le_advertising_manager.h b/main/shim/le_advertising_manager.h
deleted file mode 100644
index d53c795ca..000000000
--- a/main/shim/le_advertising_manager.h
+++ /dev/null
@@ -1,32 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/**
- * Gd shim layer to legacy le advertiser
- */
-#pragma once
-
-#include "ble_advertiser.h"
-#include "include/hardware/ble_advertiser.h"
-
-namespace bluetooth {
-namespace shim {
-
-BleAdvertiserInterface* get_ble_advertiser_instance();
-void init_advertising_manager();
-
-} // namespace shim
-} // namespace bluetooth \ No newline at end of file
diff --git a/main/shim/le_scanning_manager.cc b/main/shim/le_scanning_manager.cc
deleted file mode 100644
index ce987531f..000000000
--- a/main/shim/le_scanning_manager.cc
+++ /dev/null
@@ -1,513 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "bt_shim_scanner"
-
-#include "le_scanning_manager.h"
-
-#include <base/bind.h>
-#include <base/threading/thread.h>
-#include <hardware/bluetooth.h>
-#include <stdio.h>
-#include <unordered_set>
-
-#include "btif/include/btif_common.h"
-#include "gd/hci/address.h"
-#include "gd/hci/le_scanning_manager.h"
-#include "gd/storage/device.h"
-#include "gd/storage/le_device.h"
-#include "gd/storage/storage_module.h"
-#include "main/shim/entry.h"
-#include "main/shim/helpers.h"
-#include "main/shim/shim.h"
-
-#include "advertise_data_parser.h"
-#include "stack/btm/btm_int_types.h"
-
-using bluetooth::ToRawAddress;
-using bluetooth::ToGdAddress;
-
-extern void btm_ble_process_adv_pkt_cont_for_inquiry(
- uint16_t event_type, uint8_t address_type, const RawAddress& raw_address,
- uint8_t primary_phy, uint8_t secondary_phy, uint8_t advertising_sid,
- int8_t tx_power, int8_t rssi, uint16_t periodic_adv_int,
- std::vector<uint8_t> advertising_data);
-
-extern void btif_dm_update_ble_remote_properties(const RawAddress& bd_addr,
- BD_NAME bd_name,
- tBT_DEVICE_TYPE dev_type);
-
-class BleScannerInterfaceImpl : public BleScannerInterface,
- public bluetooth::hci::ScanningCallback {
- public:
- ~BleScannerInterfaceImpl() override{};
-
- void Init() {
- LOG_INFO("init BleScannerInterfaceImpl");
- bluetooth::shim::GetScanning()->RegisterScanningCallback(this);
- }
-
- /** Registers a scanner with the stack */
- void RegisterScanner(const bluetooth::Uuid& uuid, RegisterCallback) {
- LOG(INFO) << __func__ << " in shim layer";
- auto app_uuid = bluetooth::hci::Uuid::From128BitBE(uuid.To128BitBE());
- bluetooth::shim::GetScanning()->RegisterScanner(app_uuid);
- }
-
- /** Unregister a scanner from the stack */
- void Unregister(int scanner_id) {
- LOG(INFO) << __func__ << " in shim layer, scanner_id:" << scanner_id;
- bluetooth::shim::GetScanning()->Unregister(scanner_id);
- }
-
- /** Start or stop LE device scanning */
- void Scan(bool start) {
- LOG(INFO) << __func__ << " in shim layer";
- bluetooth::shim::GetScanning()->Scan(start);
- init_address_cache();
- }
-
- /** Setup scan filter params */
- void ScanFilterParamSetup(
- uint8_t client_if, uint8_t action, uint8_t filter_index,
- std::unique_ptr<btgatt_filt_param_setup_t> filt_param,
- FilterParamSetupCallback cb) {
- LOG(INFO) << __func__ << " in shim layer";
-
- auto apcf_action = static_cast<bluetooth::hci::ApcfAction>(action);
- bluetooth::hci::AdvertisingFilterParameter advertising_filter_parameter;
-
- if (filt_param != nullptr) {
- if (filt_param && filt_param->dely_mode == 1) {
- bluetooth::shim::GetScanning()->TrackAdvertiser(client_if);
- }
- advertising_filter_parameter.feature_selection = filt_param->feat_seln;
- advertising_filter_parameter.list_logic_type =
- filt_param->list_logic_type;
- advertising_filter_parameter.filter_logic_type =
- filt_param->filt_logic_type;
- advertising_filter_parameter.rssi_high_thresh =
- filt_param->rssi_high_thres;
- advertising_filter_parameter.delivery_mode =
- static_cast<bluetooth::hci::DeliveryMode>(filt_param->dely_mode);
- if (filt_param && filt_param->dely_mode == 1) {
- advertising_filter_parameter.onfound_timeout =
- filt_param->found_timeout;
- advertising_filter_parameter.onfound_timeout_cnt =
- filt_param->found_timeout_cnt;
- advertising_filter_parameter.rssi_low_thres =
- filt_param->rssi_low_thres;
- advertising_filter_parameter.onlost_timeout = filt_param->lost_timeout;
- advertising_filter_parameter.num_of_tracking_entries =
- filt_param->num_of_tracking_entries;
- }
- }
-
- bluetooth::shim::GetScanning()->ScanFilterParameterSetup(
- apcf_action, filter_index, advertising_filter_parameter);
- // TODO refactor callback mechanism
- do_in_jni_thread(FROM_HERE,
- base::Bind(cb, 0, 0, btm_status_value(BTM_SUCCESS)));
- }
-
- /** Configure a scan filter condition */
- void ScanFilterAdd(int filter_index, std::vector<ApcfCommand> filters,
- FilterConfigCallback cb) {
- LOG(INFO) << __func__ << " in shim layer";
- std::vector<bluetooth::hci::AdvertisingPacketContentFilterCommand>
- new_filters = {};
- for (size_t i = 0; i < filters.size(); i++) {
- bluetooth::hci::AdvertisingPacketContentFilterCommand command{};
- if (!parse_filter_command(command, filters[i])) {
- LOG_ERROR("invalid apcf command");
- return;
- }
- new_filters.push_back(command);
- }
- bluetooth::shim::GetScanning()->ScanFilterAdd(filter_index, new_filters);
- do_in_jni_thread(FROM_HERE,
- base::Bind(cb, 0, 0, 0, btm_status_value(BTM_SUCCESS)));
- }
-
- /** Clear all scan filter conditions for specific filter index*/
- void ScanFilterClear(int filter_index, FilterConfigCallback cb) {
- LOG(INFO) << __func__ << " in shim layer";
- // This function doesn't used in java layer
- }
-
- /** Enable / disable scan filter feature*/
- void ScanFilterEnable(bool enable, EnableCallback cb) {
- LOG(INFO) << __func__ << " in shim layer";
- bluetooth::shim::GetScanning()->ScanFilterEnable(enable);
-
- uint8_t action = enable ? 1 : 0;
- do_in_jni_thread(FROM_HERE,
- base::Bind(cb, action, btm_status_value(BTM_SUCCESS)));
- }
-
- /** Sets the LE scan interval and window in units of N*0.625 msec */
- void SetScanParameters(int scan_interval, int scan_window, Callback cb) {
- LOG(INFO) << __func__ << " in shim layer";
- // use active scan
- auto scan_type = static_cast<bluetooth::hci::LeScanType>(0x01);
- bluetooth::shim::GetScanning()->SetScanParameters(scan_type, scan_interval,
- scan_window);
- do_in_jni_thread(FROM_HERE, base::Bind(cb, 0));
- }
-
- /* Configure the batchscan storage */
- void BatchscanConfigStorage(int client_if, int batch_scan_full_max,
- int batch_scan_trunc_max,
- int batch_scan_notify_threshold, Callback cb) {
- LOG(INFO) << __func__ << " in shim layer";
- bluetooth::shim::GetScanning()->BatchScanConifgStorage(
- batch_scan_full_max, batch_scan_trunc_max, batch_scan_notify_threshold,
- client_if);
- do_in_jni_thread(FROM_HERE, base::Bind(cb, btm_status_value(BTM_SUCCESS)));
- }
-
- /* Enable batchscan */
- virtual void BatchscanEnable(int scan_mode, int scan_interval,
- int scan_window, int addr_type, int discard_rule,
- Callback cb) {
- LOG(INFO) << __func__ << " in shim layer";
- auto batch_scan_mode =
- static_cast<bluetooth::hci::BatchScanMode>(scan_mode);
- auto batch_scan_discard_rule =
- static_cast<bluetooth::hci::BatchScanDiscardRule>(discard_rule);
- bluetooth::shim::GetScanning()->BatchScanEnable(
- batch_scan_mode, scan_window, scan_interval, batch_scan_discard_rule);
- do_in_jni_thread(FROM_HERE, base::Bind(cb, btm_status_value(BTM_SUCCESS)));
- }
-
- /* Disable batchscan */
- virtual void BatchscanDisable(Callback cb) {
- LOG(INFO) << __func__ << " in shim layer";
- bluetooth::shim::GetScanning()->BatchScanDisable();
- do_in_jni_thread(FROM_HERE, base::Bind(cb, btm_status_value(BTM_SUCCESS)));
- }
-
- /* Read out batchscan reports */
- void BatchscanReadReports(int client_if, int scan_mode) {
- LOG(INFO) << __func__ << " in shim layer";
- auto batch_scan_mode =
- static_cast<bluetooth::hci::BatchScanMode>(scan_mode);
- auto scanner_id = static_cast<bluetooth::hci::ScannerId>(client_if);
- bluetooth::shim::GetScanning()->BatchScanReadReport(scanner_id,
- batch_scan_mode);
- }
-
- void StartSync(uint8_t sid, RawAddress address, uint16_t skip,
- uint16_t timeout, StartSyncCb start_cb, SyncReportCb report_cb,
- SyncLostCb lost_cb) {
- LOG(INFO) << __func__ << " in shim layer";
- // This function doesn't implement in the old stack
- }
-
- void StopSync(uint16_t handle) {
- LOG(INFO) << __func__ << " in shim layer";
- // This function doesn't implement in the old stack
- }
-
- void RegisterCallbacks(ScanningCallbacks* callbacks) {
- LOG(INFO) << __func__ << " in shim layer";
- scanning_callbacks_ = callbacks;
- }
-
- void OnScannerRegistered(const bluetooth::hci::Uuid app_uuid,
- bluetooth::hci::ScannerId scanner_id,
- ScanningStatus status) {
- auto uuid = bluetooth::Uuid::From128BitBE(app_uuid.To128BitBE());
- do_in_jni_thread(FROM_HERE,
- base::Bind(&ScanningCallbacks::OnScannerRegistered,
- base::Unretained(scanning_callbacks_), uuid,
- scanner_id, status));
- }
-
- void OnScanResult(uint16_t event_type, uint8_t address_type,
- bluetooth::hci::Address address, uint8_t primary_phy,
- uint8_t secondary_phy, uint8_t advertising_sid,
- int8_t tx_power, int8_t rssi,
- uint16_t periodic_advertising_interval,
- std::vector<uint8_t> advertising_data) {
- RawAddress raw_address = ToRawAddress(address);
-
- do_in_jni_thread(
- FROM_HERE,
- base::BindOnce(&BleScannerInterfaceImpl::handle_remote_properties,
- base::Unretained(this), raw_address, address_type,
- advertising_data));
-
- do_in_jni_thread(
- FROM_HERE,
- base::BindOnce(&ScanningCallbacks::OnScanResult,
- base::Unretained(scanning_callbacks_), event_type,
- address_type, raw_address, primary_phy, secondary_phy,
- advertising_sid, tx_power, rssi,
- periodic_advertising_interval, advertising_data));
-
- // TODO: Remove when StartInquiry in GD part implemented
- btm_ble_process_adv_pkt_cont_for_inquiry(
- event_type, address_type, raw_address, primary_phy, secondary_phy,
- advertising_sid, tx_power, rssi, periodic_advertising_interval,
- advertising_data);
- }
-
- void OnTrackAdvFoundLost(bluetooth::hci::AdvertisingFilterOnFoundOnLostInfo
- on_found_on_lost_info) {
- AdvertisingTrackInfo track_info = {};
- RawAddress raw_address =
- ToRawAddress(on_found_on_lost_info.advertiser_address);
- track_info.advertiser_address = raw_address;
- track_info.advertiser_address_type =
- on_found_on_lost_info.advertiser_address_type;
- track_info.scanner_id = on_found_on_lost_info.scanner_id;
- track_info.filter_index = on_found_on_lost_info.filter_index;
- track_info.advertiser_state = on_found_on_lost_info.advertiser_state;
- track_info.advertiser_info_present =
- static_cast<uint8_t>(on_found_on_lost_info.advertiser_info_present);
- if (on_found_on_lost_info.advertiser_info_present ==
- bluetooth::hci::AdvtInfoPresent::ADVT_INFO_PRESENT) {
- track_info.tx_power = on_found_on_lost_info.tx_power;
- track_info.rssi = on_found_on_lost_info.rssi;
- track_info.time_stamp = on_found_on_lost_info.time_stamp;
- auto adv_data = on_found_on_lost_info.adv_packet;
- track_info.adv_packet_len = (uint8_t)adv_data.size();
- track_info.adv_packet.reserve(adv_data.size());
- track_info.adv_packet.insert(track_info.adv_packet.end(),
- adv_data.begin(), adv_data.end());
- auto scan_rsp_data = on_found_on_lost_info.scan_response;
- track_info.scan_response_len = (uint8_t)scan_rsp_data.size();
- track_info.scan_response.reserve(adv_data.size());
- track_info.scan_response.insert(track_info.scan_response.end(),
- scan_rsp_data.begin(),
- scan_rsp_data.end());
- }
- do_in_jni_thread(
- FROM_HERE,
- base::BindOnce(&ScanningCallbacks::OnTrackAdvFoundLost,
- base::Unretained(scanning_callbacks_), track_info));
- }
-
- void OnBatchScanReports(int client_if, int status, int report_format,
- int num_records, std::vector<uint8_t> data) {
- do_in_jni_thread(
- FROM_HERE,
- base::BindOnce(&ScanningCallbacks::OnBatchScanReports,
- base::Unretained(scanning_callbacks_), client_if, status,
- report_format, num_records, data));
- }
-
- void OnBatchScanThresholdCrossed(int client_if) {
- do_in_jni_thread(
- FROM_HERE,
- base::BindOnce(&ScanningCallbacks::OnBatchScanThresholdCrossed,
- base::Unretained(scanning_callbacks_), client_if));
- }
-
- void OnTimeout() {}
-
- void OnFilterEnable(bluetooth::hci::Enable enable, uint8_t status){};
-
- void OnFilterParamSetup(uint8_t available_spaces,
- bluetooth::hci::ApcfAction action, uint8_t status){};
-
- void OnFilterConfigCallback(bluetooth::hci::ApcfFilterType filter_type,
- uint8_t available_spaces,
- bluetooth::hci::ApcfAction action,
- uint8_t status){};
-
- ScanningCallbacks* scanning_callbacks_;
-
- private:
- bool parse_filter_command(
- bluetooth::hci::AdvertisingPacketContentFilterCommand&
- advertising_packet_content_filter_command,
- ApcfCommand apcf_command) {
- advertising_packet_content_filter_command.filter_type =
- static_cast<bluetooth::hci::ApcfFilterType>(apcf_command.type);
- bluetooth::hci::Address address = ToGdAddress(apcf_command.address);
- advertising_packet_content_filter_command.address = address;
- advertising_packet_content_filter_command.application_address_type =
- static_cast<bluetooth::hci::ApcfApplicationAddressType>(
- apcf_command.addr_type);
-
- if (!apcf_command.uuid.IsEmpty()) {
- uint8_t uuid_len = apcf_command.uuid.GetShortestRepresentationSize();
- switch (uuid_len) {
- case bluetooth::Uuid::kNumBytes16: {
- advertising_packet_content_filter_command.uuid =
- bluetooth::hci::Uuid::From16Bit(apcf_command.uuid.As16Bit());
- } break;
- case bluetooth::Uuid::kNumBytes32: {
- advertising_packet_content_filter_command.uuid =
- bluetooth::hci::Uuid::From32Bit(apcf_command.uuid.As32Bit());
- } break;
- case bluetooth::Uuid::kNumBytes128: {
- advertising_packet_content_filter_command.uuid =
- bluetooth::hci::Uuid::From128BitBE(
- apcf_command.uuid.To128BitBE());
- } break;
- default:
- LOG_WARN("illegal UUID length %d", (uint16_t)uuid_len);
- return false;
- }
- }
-
- if (!apcf_command.uuid_mask.IsEmpty()) {
- uint8_t uuid_len = apcf_command.uuid.GetShortestRepresentationSize();
- switch (uuid_len) {
- case bluetooth::Uuid::kNumBytes16: {
- advertising_packet_content_filter_command.uuid_mask =
- bluetooth::hci::Uuid::From16Bit(apcf_command.uuid_mask.As16Bit());
- } break;
- case bluetooth::Uuid::kNumBytes32: {
- advertising_packet_content_filter_command.uuid_mask =
- bluetooth::hci::Uuid::From32Bit(apcf_command.uuid_mask.As32Bit());
- } break;
- case bluetooth::Uuid::kNumBytes128: {
- advertising_packet_content_filter_command.uuid_mask =
- bluetooth::hci::Uuid::From128BitBE(
- apcf_command.uuid_mask.To128BitBE());
- } break;
- default:
- LOG_WARN("illegal UUID length %d", (uint16_t)uuid_len);
- return false;
- }
- }
-
- advertising_packet_content_filter_command.name.assign(
- apcf_command.name.begin(), apcf_command.name.end());
- advertising_packet_content_filter_command.company = apcf_command.company;
- advertising_packet_content_filter_command.company_mask =
- apcf_command.company_mask;
- advertising_packet_content_filter_command.data.assign(
- apcf_command.data.begin(), apcf_command.data.end());
- advertising_packet_content_filter_command.data_mask.assign(
- apcf_command.data_mask.begin(), apcf_command.data_mask.end());
- return true;
- }
-
- void handle_remote_properties(RawAddress bd_addr, tBLE_ADDR_TYPE addr_type,
- std::vector<uint8_t> advertising_data) {
- // skip anonymous advertisment
- if (addr_type == BLE_ADDR_ANONYMOUS) {
- return;
- }
-
- auto device_type = bluetooth::hci::DeviceType::LE;
- uint8_t flag_len;
- const uint8_t* p_flag = AdvertiseDataParser::GetFieldByType(
- advertising_data, BTM_BLE_AD_TYPE_FLAG, &flag_len);
- if (p_flag != NULL && flag_len != 0) {
- if ((BTM_BLE_BREDR_NOT_SPT & *p_flag) == 0) {
- device_type = bluetooth::hci::DeviceType::DUAL;
- }
- }
-
- uint8_t remote_name_len;
- const uint8_t* p_eir_remote_name = AdvertiseDataParser::GetFieldByType(
- advertising_data, BTM_EIR_COMPLETE_LOCAL_NAME_TYPE, &remote_name_len);
-
- if (p_eir_remote_name == NULL) {
- p_eir_remote_name = AdvertiseDataParser::GetFieldByType(
- advertising_data, BT_EIR_SHORTENED_LOCAL_NAME_TYPE, &remote_name_len);
- }
-
- // update device name
- if ((addr_type != BLE_ADDR_RANDOM) || (p_eir_remote_name)) {
- if (!find_address_cache(bd_addr)) {
- add_address_cache(bd_addr);
-
- if (p_eir_remote_name) {
- if (remote_name_len > BD_NAME_LEN + 1 ||
- (remote_name_len == BD_NAME_LEN + 1 &&
- p_eir_remote_name[BD_NAME_LEN] != '\0')) {
- LOG_INFO("%s dropping invalid packet - device name too long: %d",
- __func__, remote_name_len);
- return;
- }
-
- bt_bdname_t bdname;
- memcpy(bdname.name, p_eir_remote_name, remote_name_len);
- if (remote_name_len < BD_NAME_LEN + 1)
- bdname.name[remote_name_len] = '\0';
-
- btif_dm_update_ble_remote_properties(bd_addr, bdname.name,
- device_type);
- }
- }
- }
- if (!bluetooth::shim::is_gd_stack_started_up()) {
- LOG_WARN("Gd stack is stopped, return");
- return;
- }
- auto* storage_module = bluetooth::shim::GetStorage();
- bluetooth::hci::Address address = ToGdAddress(bd_addr);
-
- // update device type
- auto mutation = storage_module->Modify();
- bluetooth::storage::Device device =
- storage_module->GetDeviceByLegacyKey(address);
- mutation.Add(device.SetDeviceType(device_type));
- mutation.Commit();
-
- // update address type
- auto mutation2 = storage_module->Modify();
- bluetooth::storage::LeDevice le_device = device.Le();
- mutation2.Add(
- le_device.SetAddressType((bluetooth::hci::AddressType)addr_type));
- mutation2.Commit();
- }
-
- void add_address_cache(const RawAddress& p_bda) {
- // Remove the oldest entries
- while (remote_bdaddr_cache_.size() >= remote_bdaddr_cache_max_size_) {
- const RawAddress& raw_address = remote_bdaddr_cache_ordered_.front();
- remote_bdaddr_cache_.erase(raw_address);
- remote_bdaddr_cache_ordered_.pop();
- }
- remote_bdaddr_cache_.insert(p_bda);
- remote_bdaddr_cache_ordered_.push(p_bda);
- }
-
- bool find_address_cache(const RawAddress& p_bda) {
- return (remote_bdaddr_cache_.find(p_bda) != remote_bdaddr_cache_.end());
- }
-
- void init_address_cache(void) {
- remote_bdaddr_cache_.clear();
- remote_bdaddr_cache_ordered_ = {};
- }
-
- // all access to this variable should be done on the jni thread
- std::set<RawAddress> remote_bdaddr_cache_;
- std::queue<RawAddress> remote_bdaddr_cache_ordered_;
- const size_t remote_bdaddr_cache_max_size_ = 1024;
-};
-
-BleScannerInterfaceImpl* bt_le_scanner_instance = nullptr;
-
-BleScannerInterface* bluetooth::shim::get_ble_scanner_instance() {
- if (bt_le_scanner_instance == nullptr) {
- bt_le_scanner_instance = new BleScannerInterfaceImpl();
- }
- return bt_le_scanner_instance;
-}
-
-void bluetooth::shim::init_scanning_manager() {
- bt_le_scanner_instance->Init();
-}
diff --git a/main/shim/link_connection_interface.h b/main/shim/link_connection_interface.h
deleted file mode 100644
index f38f9e23d..000000000
--- a/main/shim/link_connection_interface.h
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include <future>
-
-#include "gd/hci/address.h"
-#include "gd/hci/address_with_type.h"
-#include "stack/include/hci_error_code.h"
-
-namespace bluetooth {
-namespace shim {
-
-class LinkConnectionInterface {
- public:
- virtual ~LinkConnectionInterface() {}
-
- virtual void CreateClassicConnection(
- const bluetooth::hci::Address& address) = 0;
- virtual void CancelClassicConnection(
- const bluetooth::hci::Address& address) = 0;
- virtual void AcceptLeConnectionFrom(
- const bluetooth::hci::AddressWithType& address_with_type, bool is_direct,
- std::promise<bool>) = 0;
- virtual void IgnoreLeConnectionFrom(
- const bluetooth::hci::AddressWithType& address_with_type) = 0;
-
- virtual void DisconnectClassic(uint16_t handle, tHCI_REASON reason) = 0;
- virtual void DisconnectLe(uint16_t handle, tHCI_REASON reason) = 0;
-};
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/link_policy.cc b/main/shim/link_policy.cc
deleted file mode 100644
index 048fee58f..000000000
--- a/main/shim/link_policy.cc
+++ /dev/null
@@ -1,290 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <base/bind.h>
-#include <base/location.h>
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <memory>
-
-#include "device/include/interop.h"
-#include "hci/controller.h"
-#include "main/shim/controller.h"
-#include "main/shim/dumpsys.h"
-#include "main/shim/link_policy.h"
-#include "main/shim/stack.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/btm_ble_api_types.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcidefs.h"
-
-bt_status_t do_in_main_thread(const base::Location& from_here,
- base::OnceClosure task);
-
-void btm_cont_rswitch_from_handle(uint16_t hci_handle);
-void btm_pm_proc_mode_change(tHCI_STATUS hci_status, uint16_t hci_handle,
- tHCI_MODE mode, uint16_t interval);
-void btm_sco_chk_pend_unpark(tHCI_STATUS hci_status, uint16_t hci_handle);
-void l2c_OnHciModeChangeSendPendingPackets(RawAddress remote);
-void process_ssr_event(tHCI_STATUS status, uint16_t handle,
- UNUSED_ATTR uint16_t max_tx_lat, uint16_t max_rx_lat);
-tACL_CONN* acl_get_connection_from_handle(uint16_t handle);
-
-extern tBTM_CB btm_cb;
-
-namespace {
-
-tBTM_STATUS set_active_mode(tACL_CONN& p_acl) {
- bluetooth::shim::Stack::GetInstance()->LinkPolicy()->ExitSniffMode(
- p_acl.hci_handle);
- return BTM_SUCCESS;
-}
-
-tBTM_STATUS set_hold_mode(tACL_CONN& p_acl, uint16_t max, uint16_t min) {
- bluetooth::shim::Stack::GetInstance()->LinkPolicy()->HoldMode(
- p_acl.hci_handle, max, min);
- return BTM_SUCCESS;
-}
-
-tBTM_STATUS set_sniff_mode(tACL_CONN& p_acl, uint16_t max_interval,
- uint16_t min_interval, uint16_t attempt,
- uint16_t timeout) {
- bluetooth::shim::Stack::GetInstance()->LinkPolicy()->SniffMode(
- p_acl.hci_handle, max_interval, min_interval, attempt, timeout);
- return BTM_SUCCESS;
-}
-
-bool controller_supports_link_policy_mode(const tBTM_PM_MODE& mode,
- bool interop_check) {
- switch (mode) {
- case BTM_PM_MD_ACTIVE: // Active mode is always supported
- break;
- case BTM_PM_MD_PARK: // Park mode no longer supported
- return false;
- case BTM_PM_MD_SNIFF:
- if (!controller_get_interface()->supports_sniff_mode() || interop_check)
- return false;
- break;
- case BTM_PM_MD_HOLD:
- if (!controller_get_interface()->supports_hold_mode() || interop_check)
- return false;
- break;
- default:
- LOG_ERROR("Unknown mode:%u", mode);
- return false;
- }
- return true;
-}
-
-} // namespace
-
-bool bluetooth::shim::RegisterLinkPolicyClient(tBTM_PM_STATUS_CBACK* p_cb) {
- if (std::find(btm_cb.acl_cb_.link_policy.clients.begin(),
- btm_cb.acl_cb_.link_policy.clients.end(),
- p_cb) != btm_cb.acl_cb_.link_policy.clients.end()) {
- LOG_ERROR("Link policy client already registered");
- return false;
- }
- btm_cb.acl_cb_.link_policy.clients.push_back(p_cb);
- return true;
-}
-
-bool bluetooth::shim::UnregisterLinkPolicyClient(tBTM_PM_STATUS_CBACK* p_cb) {
- auto cb = std::find(btm_cb.acl_cb_.link_policy.clients.begin(),
- btm_cb.acl_cb_.link_policy.clients.end(), p_cb);
- if (cb == btm_cb.acl_cb_.link_policy.clients.end()) {
- LOG_ERROR("Link policy client already unregistered");
- return false;
- }
- btm_cb.acl_cb_.link_policy.clients.erase(cb);
- return true;
-}
-
-tBTM_STATUS bluetooth::shim::BTM_SetPowerMode(uint16_t handle,
- const tBTM_PM_PWR_MD& new_mode) {
- tACL_CONN* p_acl = acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- return BTM_UNKNOWN_ADDR;
- }
-
- if (!controller_supports_link_policy_mode(
- new_mode.mode,
- interop_match_addr(INTEROP_DISABLE_SNIFF, &p_acl->remote_addr))) {
- return BTM_MODE_UNSUPPORTED;
- }
-
- if (p_acl->policy.Mode() == new_mode.mode) {
- LOG_INFO("Controller already in mode:%s[0x%02x]",
- power_mode_state_text(p_acl->policy.Mode()).c_str(),
- p_acl->policy.Mode());
- }
-
- if (p_acl->policy.mode.IsPending()) {
- LOG_INFO("Link policy mode is pending");
- }
-
- LOG_INFO("Switching mode from %s(0x%x) to %s(0x%x)",
- power_mode_state_text(p_acl->policy.Mode()).c_str(),
- p_acl->policy.Mode(), power_mode_state_text(new_mode.mode).c_str(),
- new_mode.mode);
-
- p_acl->policy.mode.pending_ = new_mode.mode;
- switch (new_mode.mode) {
- case BTM_PM_MD_ACTIVE:
- set_active_mode(*p_acl);
- return BTM_SUCCESS;
- break;
- case BTM_PM_MD_SNIFF:
- set_sniff_mode(*p_acl, new_mode.max, new_mode.min, new_mode.attempt,
- new_mode.timeout);
- return BTM_SUCCESS;
- break;
- case BTM_PM_MD_HOLD:
- return set_hold_mode(*p_acl, new_mode.max, new_mode.min);
- break;
- }
- return BTM_MODE_UNSUPPORTED;
-}
-
-static bool is_encryption_pause_supported(const tACL_CONN& p_acl) {
- CHECK(p_acl.peer_lmp_feature_valid[0])
- << "Checked before remote feature read has complete";
- return HCI_ATOMIC_ENCRYPT_SUPPORTED(p_acl.peer_lmp_feature_pages[0]) &&
- controller_get_interface()->supports_encryption_pause();
-}
-
-void bluetooth::shim::btm_pm_on_mode_change(tHCI_STATUS status, uint16_t handle,
- tHCI_MODE hci_mode,
- uint16_t interval) {
- tBTM_PM_MODE new_mode = HCI_TO_BTM_POWER_MODE(hci_mode);
-
- LOG_DEBUG(
- "For now pointing back again to legacy status:%s handle:0x%04x "
- "new_mode:%u interval:%u",
- hci_error_code_text(status).c_str(), handle, new_mode, interval);
-
- tACL_CONN* p_acl = acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- LOG_ERROR("Received mode change for unknown acl handle:0x%04x", handle);
- return;
- }
-
- tBTM_PM_MODE pending = p_acl->policy.mode.Pending();
- p_acl->policy.mode.pending_ = BTM_PM_MD_UNKNOWN;
-
- if (status == HCI_SUCCESS) {
- BTM_LogHistory(
- "Power", p_acl->remote_addr, "Mode change",
- base::StringPrintf("%s[0x%02x] ==> %s[0x%02x] pending:%s",
- power_mode_state_text(p_acl->policy.Mode()).c_str(),
- p_acl->policy.Mode(),
- power_mode_state_text(new_mode).c_str(), new_mode,
- power_mode_state_text(pending).c_str()));
- LOG_INFO("Power mode switched from %s[%hhu] to %s[%hhu] pending:%s",
- power_mode_state_text(p_acl->policy.Mode()).c_str(),
- p_acl->policy.Mode(), power_mode_state_text(new_mode).c_str(),
- new_mode, power_mode_state_text(pending).c_str());
- p_acl->policy.mode.mode_ = new_mode;
-
- if (new_mode == (BTM_PM_ST_ACTIVE) || new_mode == (BTM_PM_ST_SNIFF)) {
- l2c_OnHciModeChangeSendPendingPackets(p_acl->remote_addr);
- }
-
- /*check if sco disconnect is waiting for the mode change */
- btm_sco_disc_chk_pend_for_modechange(handle);
-
- if (p_acl->is_switch_role_mode_change()) {
- if (p_acl->is_encrypted && !is_encryption_pause_supported(*p_acl)) {
- p_acl->set_encryption_off();
- p_acl->set_switch_role_encryption_off();
- } else {
- p_acl->set_switch_role_in_progress();
- p_acl->rs_disc_pending = BTM_SEC_RS_PENDING;
- bluetooth::legacy::hci::GetInterface().StartRoleSwitch(
- p_acl->remote_addr, HCI_ROLE_CENTRAL);
- }
- }
- }
-
- btm_sco_chk_pend_unpark(status, handle);
- // btm_pm_proc_mode_change(status, handle, new_mode, interval);
-
- for (auto client_callback : btm_cb.acl_cb_.link_policy.clients) {
- (*client_callback)(p_acl->remote_addr, new_mode, interval, status);
- }
-
- LOG_DEBUG(
- "Notified mode change registered clients cnt:%zu peer:%s "
- "status:%s",
- btm_cb.acl_cb_.link_policy.clients.size(),
- PRIVATE_ADDRESS(p_acl->remote_addr), hci_error_code_text(status).c_str());
-}
-
-tBTM_STATUS bluetooth::shim::BTM_SetSsrParams(uint16_t handle, uint16_t max_lat,
- uint16_t min_rmt_to,
- uint16_t min_loc_to) {
- LOG_DEBUG("Sending gd power mode SSR Params");
- tACL_CONN* p_acl = acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- return BTM_UNKNOWN_ADDR;
- }
-
- p_acl->policy.sniff_subrating.pending_ = true;
- bluetooth::shim::Stack::GetInstance()->LinkPolicy()->SniffSubrating(
- handle, max_lat, min_rmt_to, min_loc_to);
- return BTM_SUCCESS;
-}
-
-void bluetooth::shim::btm_pm_on_sniff_subrating(
- tHCI_STATUS status, uint16_t handle, uint16_t maximum_transmit_latency,
- UNUSED_ATTR uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout, uint16_t minimum_local_timeout) {
- LOG_DEBUG("For now pointing back again to legacy");
- tACL_CONN* p_acl = acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- LOG_ERROR("Received mode change for unknown acl handle:0x%04x", handle);
- return;
- }
-
- p_acl->policy.sniff_subrating.pending_ = false;
- if (status == HCI_SUCCESS) {
- BTM_LogHistory(
- "Power", p_acl->remote_addr, "Sniff Subrating",
- base::StringPrintf(
- "max_xmit_latency:%.2fs remote_timeout:%.2fs local_timeout:%.2fs",
- ticks_to_seconds(maximum_transmit_latency),
- ticks_to_seconds(minimum_remote_timeout),
- ticks_to_seconds(minimum_local_timeout)));
- }
-
- const bool use_ssr =
- (p_acl->policy.mode.Interval() != maximum_receive_latency) ? true : false;
-
- for (auto client_callback : btm_cb.acl_cb_.link_policy.clients) {
- (*client_callback)(p_acl->remote_addr, BTM_PM_STS_SSR, (use_ssr) ? 1 : 0,
- status);
- }
-
- LOG_DEBUG(
- "Notified sniff subrating registered clients cnt:%zu peer:%s use_ssr:%s "
- "status:%s",
- btm_cb.acl_cb_.link_policy.clients.size(),
- PRIVATE_ADDRESS(p_acl->remote_addr), logbool(use_ssr).c_str(),
- hci_error_code_text(status).c_str());
-}
diff --git a/main/shim/link_policy.h b/main/shim/link_policy.h
deleted file mode 100644
index f96fd0766..000000000
--- a/main/shim/link_policy.h
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include "stack/acl/acl.h"
-#include "stack/include/btm_api_types.h" // tBTM_PM_PWR_MD
-#include "types/raw_address.h"
-
-namespace bluetooth {
-namespace shim {
-
-bool RegisterLinkPolicyClient(tBTM_PM_STATUS_CBACK* p_cb);
-bool UnregisterLinkPolicyClient(tBTM_PM_STATUS_CBACK* p_cb);
-
-bool SetHoldMode(uint16_t handle, uint16_t max_interval, uint16_t min_interval);
-bool SetSniffMode(uint16_t handle, uint16_t max_interval, uint16_t min_interval,
- uint16_t attempt, uint16_t timeout);
-bool ExitSniffMode(uint16_t handle);
-bool SetSniffSubrating(uint16_t handle, uint16_t maximum_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout);
-
-tBTM_STATUS BTM_SetPowerMode(uint16_t handle, const tBTM_PM_PWR_MD& mode);
-void btm_pm_on_mode_change(tHCI_STATUS status, uint16_t handle,
- tHCI_MODE current_mode, uint16_t interval);
-
-tBTM_STATUS BTM_SetSsrParams(uint16_t handle, uint16_t max_lat,
- uint16_t min_rmt_to, uint16_t min_loc_to);
-void btm_pm_on_sniff_subrating(tHCI_STATUS status, uint16_t handle,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout);
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/link_policy_interface.h b/main/shim/link_policy_interface.h
deleted file mode 100644
index 41423a16e..000000000
--- a/main/shim/link_policy_interface.h
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-
-namespace bluetooth {
-namespace shim {
-
-class LinkPolicyInterface {
- public:
- virtual bool HoldMode(uint16_t handle, uint16_t max_interval,
- uint16_t min_interval) = 0;
- virtual bool SniffMode(uint16_t handle, uint16_t max_interval,
- uint16_t min_interval, uint16_t attempt,
- uint16_t timeout) = 0;
- virtual bool ExitSniffMode(uint16_t handle) = 0;
- virtual bool SniffSubrating(uint16_t handle, uint16_t maximum_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) = 0;
- virtual ~LinkPolicyInterface() = default;
-};
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/metric_id_api.cc b/main/shim/metric_id_api.cc
deleted file mode 100644
index fa912bc32..000000000
--- a/main/shim/metric_id_api.cc
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <mutex>
-
-#include "gd/common/metric_id_manager.h"
-#include "gd/hci/address.h"
-#include "main/shim/helpers.h"
-#include "main/shim/metric_id_api.h"
-#include "main/shim/shim.h"
-#include "types/raw_address.h"
-
-using bluetooth::common::MetricIdManager;
-using bluetooth::hci::Address;
-
-namespace bluetooth {
-namespace shim {
-using CallbackGd = std::function<bool(const Address& address, const int id)>;
-
-bool InitMetricIdAllocator(
- const std::unordered_map<RawAddress, int>& paired_device_map,
- CallbackLegacy save_id_callback, CallbackLegacy forget_device_callback) {
- std::unordered_map<Address, int> paired_device_map_gd;
- for (const auto& device : paired_device_map) {
- Address address = bluetooth::ToGdAddress(device.first);
- paired_device_map_gd[address] = device.second;
- }
-
- CallbackGd save_id_callback_gd = [save_id_callback](const Address& address,
- const int id) {
- return save_id_callback(bluetooth::ToRawAddress(address), id);
- };
- CallbackGd forget_device_callback_gd =
- [forget_device_callback](const Address& address, const int id) {
- return forget_device_callback(bluetooth::ToRawAddress(address), id);
- };
- return MetricIdManager::GetInstance().Init(
- paired_device_map_gd, save_id_callback_gd, forget_device_callback_gd);
-}
-
-bool CloseMetricIdAllocator() { return MetricIdManager::GetInstance().Close(); }
-
-bool IsEmptyMetricIdAllocator() {
- return MetricIdManager::GetInstance().IsEmpty();
-}
-
-int AllocateIdFromMetricIdAllocator(const RawAddress& raw_address) {
- Address address = bluetooth::ToGdAddress(raw_address);
- return MetricIdManager::GetInstance().AllocateId(address);
-}
-
-bool SaveDeviceOnMetricIdAllocator(const RawAddress& raw_address) {
- Address address = bluetooth::ToGdAddress(raw_address);
- return MetricIdManager::GetInstance().SaveDevice(address);
-}
-
-void ForgetDeviceFromMetricIdAllocator(const RawAddress& raw_address) {
- Address address = bluetooth::ToGdAddress(raw_address);
- return MetricIdManager::GetInstance().ForgetDevice(address);
-}
-
-bool IsValidIdFromMetricIdAllocator(const int id) {
- return MetricIdManager::GetInstance().IsValidId(id);
-}
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/metric_id_api.h b/main/shim/metric_id_api.h
deleted file mode 100644
index e1645e732..000000000
--- a/main/shim/metric_id_api.h
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <unordered_map>
-#include "types/raw_address.h"
-
-namespace bluetooth {
-namespace shim {
-using CallbackLegacy =
- std::function<bool(const RawAddress& address, const int id)>;
-/**
- * Initialize the allocator
- *
- * @param paired_device_map map from mac_address to id already saved
- * in the disk before init
- * @param save_id_callback a callback that will be called after successfully
- * saving id for a paired device
- * @param forget_device_callback a callback that will be called after
- * successful id deletion for forgotten device,
- * @return true if successfully initialized
- */
-bool InitMetricIdAllocator(
- const std::unordered_map<RawAddress, int>& paired_device_map,
- CallbackLegacy save_id_callback, CallbackLegacy forget_device_callback);
-
-/**
- * Close the allocator. should be called when Bluetooth process is killed
- *
- * @return true if successfully close
- */
-bool CloseMetricIdAllocator();
-
-/**
- * Check if no id saved in memory
- *
- * @return true if no id is saved
- */
-bool IsEmptyMetricIdAllocator();
-
-/**
- * Allocate an id for a scanned device, or return the id if there is already
- * one
- *
- * @param raw_address mac address of Bluetooth device
- * @return the id of device
- */
-int AllocateIdFromMetricIdAllocator(const RawAddress& raw_address);
-
-/**
- * Save the id for a paired device
- *
- * @param raw_address mac address of Bluetooth device
- * @return true if save successfully
- */
-bool SaveDeviceOnMetricIdAllocator(const RawAddress& raw_address);
-
-/**
- * Delete the id for a device to be forgotten
- *
- * @param raw_address mac address of Bluetooth device
- */
-void ForgetDeviceFromMetricIdAllocator(const RawAddress& raw_address);
-
-/**
- * Check if an id is valid.
- * The id should be less than or equal to kMaxId and bigger than or equal to
- * kMinId
- *
- * @param mac_address mac address of Bluetooth device
- * @return true if delete successfully
- */
-bool IsValidIdFromMetricIdAllocator(const int id);
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/metrics_api.cc b/main/shim/metrics_api.cc
deleted file mode 100644
index 2660e23cb..000000000
--- a/main/shim/metrics_api.cc
+++ /dev/null
@@ -1,139 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "main/shim/metrics_api.h"
-#include "gd/hci/address.h"
-#include "gd/os/metrics.h"
-#include "main/shim/helpers.h"
-#include "types/raw_address.h"
-
-using bluetooth::hci::Address;
-
-namespace bluetooth {
-namespace shim {
-void LogMetricLinkLayerConnectionEvent(
- const RawAddress* raw_address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction, uint16_t link_type,
- uint32_t hci_cmd, uint16_t hci_event, uint16_t hci_ble_event,
- uint16_t cmd_status, uint16_t reason_code) {
- Address address = Address::kEmpty;
- if (raw_address != nullptr) {
- address = bluetooth::ToGdAddress(*raw_address);
- }
- bluetooth::os::LogMetricLinkLayerConnectionEvent(
- raw_address == nullptr ? nullptr : &address, connection_handle, direction,
- link_type, hci_cmd, hci_event, hci_ble_event, cmd_status, reason_code);
-}
-
-void LogMetricA2dpAudioUnderrunEvent(const RawAddress& raw_address,
- uint64_t encoding_interval_millis,
- int num_missing_pcm_bytes) {
- Address address = bluetooth::ToGdAddress(raw_address);
- bluetooth::os::LogMetricA2dpAudioUnderrunEvent(
- address, encoding_interval_millis, num_missing_pcm_bytes);
-}
-
-void LogMetricA2dpAudioOverrunEvent(const RawAddress& raw_address,
- uint64_t encoding_interval_millis,
- int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes) {
- Address address = bluetooth::ToGdAddress(raw_address);
- bluetooth::os::LogMetricA2dpAudioOverrunEvent(
- address, encoding_interval_millis, num_dropped_buffers,
- num_dropped_encoded_frames, num_dropped_encoded_bytes);
-}
-
-void LogMetricA2dpPlaybackEvent(const RawAddress& raw_address,
- int playback_state, int audio_coding_mode) {
- Address address = bluetooth::ToGdAddress(raw_address);
- bluetooth::os::LogMetricA2dpPlaybackEvent(address, playback_state,
- audio_coding_mode);
-}
-
-void LogMetricReadRssiResult(const RawAddress& raw_address, uint16_t handle,
- uint32_t cmd_status, int8_t rssi) {
- Address address = bluetooth::ToGdAddress(raw_address);
- bluetooth::os::LogMetricReadRssiResult(address, handle, cmd_status, rssi);
-}
-
-void LogMetricReadFailedContactCounterResult(const RawAddress& raw_address,
- uint16_t handle,
- uint32_t cmd_status,
- int32_t failed_contact_counter) {
- Address address = bluetooth::ToGdAddress(raw_address);
- bluetooth::os::LogMetricReadFailedContactCounterResult(
- address, handle, cmd_status, failed_contact_counter);
-}
-
-void LogMetricReadTxPowerLevelResult(const RawAddress& raw_address,
- uint16_t handle, uint32_t cmd_status,
- int32_t transmit_power_level) {
- Address address = bluetooth::ToGdAddress(raw_address);
- bluetooth::os::LogMetricReadTxPowerLevelResult(address, handle, cmd_status,
- transmit_power_level);
-}
-
-void LogMetricSmpPairingEvent(const RawAddress& raw_address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason) {
- Address address = bluetooth::ToGdAddress(raw_address);
- bluetooth::os::LogMetricSmpPairingEvent(address, smp_cmd, direction,
- smp_fail_reason);
-}
-
-void LogMetricClassicPairingEvent(const RawAddress& raw_address,
- uint16_t handle, uint32_t hci_cmd,
- uint16_t hci_event, uint16_t cmd_status,
- uint16_t reason_code, int64_t event_value) {
- Address address = bluetooth::ToGdAddress(raw_address);
- bluetooth::os::LogMetricClassicPairingEvent(address, handle, hci_cmd,
- hci_event, cmd_status,
- reason_code, event_value);
-}
-
-void LogMetricSdpAttribute(const RawAddress& raw_address,
- uint16_t protocol_uuid, uint16_t attribute_id,
- size_t attribute_size, const char* attribute_value) {
- Address address = bluetooth::ToGdAddress(raw_address);
- bluetooth::os::LogMetricSdpAttribute(address, protocol_uuid, attribute_id,
- attribute_size, attribute_value);
-}
-
-void LogMetricSocketConnectionState(
- const RawAddress& raw_address, int port, int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes, int64_t rx_bytes, int uid, int server_port,
- android::bluetooth::SocketRoleEnum socket_role) {
- Address address = bluetooth::ToGdAddress(raw_address);
- bluetooth::os::LogMetricSocketConnectionState(
- address, port, type, connection_state, tx_bytes, rx_bytes, uid,
- server_port, socket_role);
-}
-
-void LogMetricManufacturerInfo(
- const RawAddress& raw_address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name, const std::string& manufacturer,
- const std::string& model, const std::string& hardware_version,
- const std::string& software_version) {
- Address address = bluetooth::ToGdAddress(raw_address);
- bluetooth::os::LogMetricManufacturerInfo(address, source_type, source_name,
- manufacturer, model,
- hardware_version, software_version);
-}
-} // namespace shim
-} // namespace bluetooth \ No newline at end of file
diff --git a/main/shim/metrics_api.h b/main/shim/metrics_api.h
deleted file mode 100644
index 818cfe9c2..000000000
--- a/main/shim/metrics_api.h
+++ /dev/null
@@ -1,212 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
-
-#include <unordered_map>
-#include "types/raw_address.h"
-
-namespace bluetooth {
-namespace shim {
-
-/**
- * Log link layer connection event
- *
- * @param address Stack wide consistent Bluetooth address of this event,
- * nullptr if unknown
- * @param connection_handle connection handle of this event,
- * {@link kUnknownConnectionHandle} if unknown
- * @param direction direction of this connection
- * @param link_type type of the link
- * @param hci_cmd HCI command opecode associated with this event, if any
- * @param hci_event HCI event code associated with this event, if any
- * @param hci_ble_event HCI BLE event code associated with this event, if any
- * @param cmd_status Command status associated with this event, if any
- * @param reason_code Reason code associated with this event, if any
- */
-void LogMetricLinkLayerConnectionEvent(
- const RawAddress* address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction, uint16_t link_type,
- uint32_t hci_cmd, uint16_t hci_event, uint16_t hci_ble_event,
- uint16_t cmd_status, uint16_t reason_code);
-
-/**
- * Log A2DP audio buffer underrun event
- *
- * @param address A2DP device associated with this event
- * @param encoding_interval_millis encoding interval in milliseconds
- * @param num_missing_pcm_bytes number of PCM bytes that cannot be read from
- * the source
- */
-void LogMetricA2dpAudioUnderrunEvent(const RawAddress& address,
- uint64_t encoding_interval_millis,
- int num_missing_pcm_bytes);
-
-/**
- * Log A2DP audio buffer overrun event
- *
- * @param address A2DP device associated with this event
- * @param encoding_interval_millis encoding interval in milliseconds
- * @param num_dropped_buffers number of encoded buffers dropped from Tx queue
- * @param num_dropped_encoded_frames number of encoded frames dropped from Tx
- * queue
- * @param num_dropped_encoded_bytes number of encoded bytes dropped from Tx
- * queue
- */
-void LogMetricA2dpAudioOverrunEvent(const RawAddress& address,
- uint64_t encoding_interval_millis,
- int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes);
-
-/**
- * Log A2DP audio playback state changed event
- *
- * @param address A2DP device associated with this event
- * @param playback_state A2DP audio playback state, on/off
- * @param audio_coding_mode A2DP audio codec encoding mode, hw/sw
- */
-void LogMetricA2dpPlaybackEvent(const RawAddress& raw_address,
- int playback_state, int audio_coding_mode);
-
-/**
- * Log read RSSI result
- *
- * @param address device associated with this event
- * @param handle connection handle of this event,
- * {@link kUnknownConnectionHandle} if unknown
- * @param cmd_status command status from read RSSI command
- * @param rssi rssi value in dBm
- */
-void LogMetricReadRssiResult(const RawAddress& address, uint16_t handle,
- uint32_t cmd_status, int8_t rssi);
-
-/**
- * Log failed contact counter report
- *
- * @param address device associated with this event
- * @param handle connection handle of this event,
- * {@link kUnknownConnectionHandle} if unknown
- * @param cmd_status command status from read failed contact counter command
- * @param failed_contact_counter Number of consecutive failed contacts for a
- * connection corresponding to the Handle
- */
-void LogMetricReadFailedContactCounterResult(const RawAddress& address,
- uint16_t handle,
- uint32_t cmd_status,
- int32_t failed_contact_counter);
-
-/**
- * Log transmit power level for a particular device after read
- *
- * @param address device associated with this event
- * @param handle connection handle of this event,
- * {@link kUnknownConnectionHandle} if unknown
- * @param cmd_status command status from read failed contact counter command
- * @param transmit_power_level transmit power level for connection to this
- * device
- */
-void LogMetricReadTxPowerLevelResult(const RawAddress& address, uint16_t handle,
- uint32_t cmd_status,
- int32_t transmit_power_level);
-
-/**
- * Logs when there is an event related to Bluetooth Security Manager Protocol
- *
- * @param address address of associated device
- * @param smp_cmd SMP command code associated with this event
- * @param direction direction of this SMP command
- * @param smp_fail_reason SMP pairing failure reason code from SMP spec
- */
-void LogMetricSmpPairingEvent(const RawAddress& address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason);
-
-/**
- * Logs there is an event related Bluetooth classic pairing
- *
- * @param address address of associated device
- * @param handle connection handle of this event,
- * {@link kUnknownConnectionHandle} if unknown
- * @param hci_cmd HCI command associated with this event
- * @param hci_event HCI event associated with this event
- * @param cmd_status Command status associated with this event
- * @param reason_code Reason code associated with this event
- * @param event_value A status value related to this specific event
- */
-void LogMetricClassicPairingEvent(const RawAddress& address, uint16_t handle,
- uint32_t hci_cmd, uint16_t hci_event,
- uint16_t cmd_status, uint16_t reason_code,
- int64_t event_value);
-
-/**
- * Logs when certain Bluetooth SDP attributes are discovered
- *
- * @param address address of associated device
- * @param protocol_uuid 16 bit protocol UUID from Bluetooth Assigned Numbers
- * @param attribute_id 16 bit attribute ID from Bluetooth Assigned Numbers
- * @param attribute_size size of this attribute
- * @param attribute_value pointer to the attribute data, must be larger than
- * attribute_size
- */
-void LogMetricSdpAttribute(const RawAddress& address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value);
-
-/**
- * Logs when there is a change in Bluetooth socket connection state
- *
- * @param address address of associated device, empty if this is a server port
- * @param port port of this socket connection
- * @param type type of socket
- * @param connection_state socket connection state
- * @param tx_bytes number of bytes transmitted
- * @param rx_bytes number of bytes received
- * @param server_port server port of this socket, if any. When both
- * |server_port| and |port| fields are populated, |port| must be spawned
- * by |server_port|
- * @param socket_role role of this socket, server or connection
- * @param uid socket owner's uid
- */
-void LogMetricSocketConnectionState(
- const RawAddress& address, int port, int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes, int64_t rx_bytes, int uid, int server_port,
- android::bluetooth::SocketRoleEnum socket_role);
-
-/**
- * Logs when a Bluetooth device's manufacturer information is learnt
- *
- * @param address address of associated device
- * @param source_type where is this device info obtained from
- * @param source_name name of the data source, internal or external
- * @param manufacturer name of the manufacturer of this device
- * @param model model of this device
- * @param hardware_version hardware version of this device
- * @param software_version software version of this device
- */
-void LogMetricManufacturerInfo(
- const RawAddress& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name, const std::string& manufacturer,
- const std::string& model, const std::string& hardware_version,
- const std::string& software_version);
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/shim.cc b/main/shim/shim.cc
index f89d6e125..fe08aad44 100644
--- a/main/shim/shim.cc
+++ b/main/shim/shim.cc
@@ -14,94 +14,60 @@
* limitations under the License.
*/
+#include <cstdint>
+
#define LOG_TAG "bt_shim"
-#include "main/shim/shim.h"
+#include "common/message_loop_thread.h"
#include "main/shim/entry.h"
-#include "main/shim/stack.h"
+#include "main/shim/shim.h"
+#include "osi/include/log.h"
+#include "osi/include/properties.h"
-#include "gd/common/init_flags.h"
-#include "gd/os/log.h"
+static const char* kPropertyKey = "bluetooth.gd.enabled";
-future_t* IdleModuleStartUp() {
- bluetooth::shim::Stack::GetInstance()->StartIdleMode();
- return kReturnImmediate;
-}
+static bluetooth::common::MessageLoopThread bt_shim_thread("bt_shim_thread");
+
+static bool gd_shim_enabled_ = false;
+static bool gd_shim_property_checked_ = false;
+static bool gd_stack_started_up_ = false;
future_t* ShimModuleStartUp() {
- bluetooth::shim::Stack::GetInstance()->StartEverything();
+ bt_shim_thread.StartUp();
+ CHECK(bt_shim_thread.IsRunning())
+ << "Unable to start bt shim message loop thread.";
+ module_start_up(get_module(GD_SHIM_BTM_MODULE));
+ bluetooth::shim::StartGabeldorscheStack();
+ gd_stack_started_up_ = true;
return kReturnImmediate;
}
-future_t* GeneralShutDown() {
- bluetooth::shim::Stack::GetInstance()->Stop();
+future_t* ShimModuleShutDown() {
+ gd_stack_started_up_ = false;
+ bluetooth::shim::StopGabeldorscheStack();
+ module_shut_down(get_module(GD_SHIM_BTM_MODULE));
+ bt_shim_thread.ShutDown();
return kReturnImmediate;
}
-EXPORT_SYMBOL extern const module_t gd_idle_module = {
- .name = GD_IDLE_MODULE,
- .init = kUnusedModuleApi,
- .start_up = IdleModuleStartUp,
- .shut_down = GeneralShutDown,
- .clean_up = kUnusedModuleApi,
- .dependencies = {kUnusedModuleDependencies}};
-
EXPORT_SYMBOL extern const module_t gd_shim_module = {
.name = GD_SHIM_MODULE,
.init = kUnusedModuleApi,
.start_up = ShimModuleStartUp,
- .shut_down = GeneralShutDown,
+ .shut_down = ShimModuleShutDown,
.clean_up = kUnusedModuleApi,
.dependencies = {kUnusedModuleDependencies}};
-bool bluetooth::shim::is_gd_advertising_enabled() {
- return bluetooth::common::init_flags::gd_advertising_is_enabled();
-}
-
-bool bluetooth::shim::is_gd_scanning_enabled() {
- return bluetooth::common::init_flags::gd_scanning_is_enabled();
-}
-
-bool bluetooth::shim::is_gd_security_enabled() {
- return bluetooth::common::init_flags::gd_security_is_enabled();
-}
-
-bool bluetooth::shim::is_gd_acl_enabled() {
- return bluetooth::common::init_flags::gd_acl_is_enabled();
-}
-
-bool bluetooth::shim::is_gd_link_policy_enabled() {
- return bluetooth::common::init_flags::gd_link_policy_is_enabled();
-}
-
-bool bluetooth::shim::is_gd_hci_enabled() {
- return bluetooth::common::init_flags::gd_hci_is_enabled();
-}
-
-bool bluetooth::shim::is_gd_controller_enabled() {
- return bluetooth::common::init_flags::gd_controller_is_enabled();
-}
-
-bool bluetooth::shim::is_gd_l2cap_enabled() {
- return bluetooth::common::init_flags::gd_l2cap_is_enabled();
+void bluetooth::shim::Post(base::OnceClosure task) {
+ bt_shim_thread.DoInThread(FROM_HERE, std::move(task));
}
bool bluetooth::shim::is_gd_shim_enabled() {
- return bluetooth::common::init_flags::gd_core_is_enabled();
+ if (!gd_shim_property_checked_) {
+ gd_shim_property_checked_ = true;
+ gd_shim_enabled_ = osi_property_get_bool(kPropertyKey, false);
+ }
+ return gd_shim_enabled_;
}
-bool bluetooth::shim::is_any_gd_enabled() {
- return bluetooth::common::init_flags::gd_hci_is_enabled();
-}
-
-bool bluetooth::shim::is_gd_stack_started_up() {
- return bluetooth::shim::Stack::GetInstance()->IsRunning();
-}
-
-bool bluetooth::shim::is_gd_dumpsys_module_started() {
- return bluetooth::shim::Stack::GetInstance()->IsDumpsysModuleStarted();
-}
-
-bool bluetooth::shim::is_gd_btaa_enabled() {
- return bluetooth::common::init_flags::btaa_hci_is_enabled();
-}
+bool bluetooth::shim::is_gd_stack_started_up() { return gd_stack_started_up_; }
diff --git a/main/shim/shim.h b/main/shim/shim.h
index dd993c0a0..6b64ddb70 100644
--- a/main/shim/shim.h
+++ b/main/shim/shim.h
@@ -19,12 +19,13 @@
/**
* Gabeldorsche related legacy-only-stack-side expansion and support code.
*/
+#include "base/bind.h"
#include "btcore/include/module.h"
#include "main/shim/entry.h"
#include "osi/include/future.h"
-static const char GD_IDLE_MODULE[] = "gd_idle_module";
static const char GD_SHIM_MODULE[] = "gd_shim_module";
+static const char GD_SHIM_BTM_MODULE[] = "gd_shim_btm_module";
constexpr future_t* kReturnImmediate = nullptr;
constexpr module_lifecycle_fn kUnusedModuleApi = nullptr;
@@ -45,17 +46,7 @@ namespace shim {
*
* @return true if using gd shim core, false if using legacy.
*/
-bool is_gd_advertising_enabled();
-bool is_gd_scanning_enabled();
-bool is_gd_security_enabled();
-bool is_gd_acl_enabled();
-bool is_gd_link_policy_enabled();
-bool is_gd_hci_enabled();
-bool is_gd_controller_enabled();
-bool is_gd_l2cap_enabled();
bool is_gd_shim_enabled();
-bool is_gd_btaa_enabled();
-bool is_any_gd_enabled();
/**
* Checks if the bluetooth gd stack has been started up.
@@ -65,11 +56,11 @@ bool is_any_gd_enabled();
bool is_gd_stack_started_up();
/**
- * Checks if the dumpsys module has been started.
+ * Posts a task on the shim message queue.
*
- * @return true if specified module has started, false otherwise.
+ * @param task Task to be posted onto the message queue.
*/
-bool is_gd_dumpsys_module_started();
+void Post(base::OnceClosure task);
} // namespace shim
} // namespace bluetooth
diff --git a/main/shim/stack.cc b/main/shim/stack.cc
deleted file mode 100644
index e4cd6fdd5..000000000
--- a/main/shim/stack.cc
+++ /dev/null
@@ -1,275 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "bt_gd_shim"
-
-#include "device/include/controller.h"
-
-#include "gd/att/att_module.h"
-#include "gd/btaa/activity_attribution.h"
-#include "gd/common/init_flags.h"
-#include "gd/hal/hci_hal.h"
-#include "gd/hci/acl_manager.h"
-#include "gd/hci/controller.h"
-#include "gd/hci/hci_layer.h"
-#include "gd/hci/le_advertising_manager.h"
-#include "gd/hci/le_scanning_manager.h"
-#include "gd/hci/vendor_specific_event_manager.h"
-#include "gd/l2cap/classic/l2cap_classic_module.h"
-#include "gd/l2cap/le/l2cap_le_module.h"
-#include "gd/neighbor/connectability.h"
-#include "gd/neighbor/discoverability.h"
-#include "gd/neighbor/inquiry.h"
-#include "gd/neighbor/name.h"
-#include "gd/neighbor/name_db.h"
-#include "gd/neighbor/page.h"
-#include "gd/neighbor/scan.h"
-#include "gd/os/log.h"
-#include "gd/security/security_module.h"
-#include "gd/shim/dumpsys.h"
-#include "gd/storage/storage_module.h"
-
-#include "main/shim/acl_legacy_interface.h"
-#include "main/shim/activity_attribution.h"
-#include "main/shim/hci_layer.h"
-#include "main/shim/helpers.h"
-#include "main/shim/l2c_api.h"
-#include "main/shim/le_advertising_manager.h"
-#include "main/shim/le_scanning_manager.h"
-#include "main/shim/shim.h"
-#include "main/shim/stack.h"
-
-namespace bluetooth {
-namespace shim {
-
-Stack* Stack::GetInstance() {
- static Stack instance;
- return &instance;
-}
-
-void Stack::StartIdleMode() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- ASSERT_LOG(!is_running_, "%s Gd stack already running", __func__);
- LOG_INFO("%s Starting Gd stack", __func__);
- ModuleList modules;
- modules.add<storage::StorageModule>();
- Start(&modules);
- // Make sure the leaf modules are started
- ASSERT(stack_manager_.GetInstance<storage::StorageModule>() != nullptr);
- is_running_ = true;
-}
-
-void Stack::StartEverything() {
- if (common::init_flags::gd_rust_is_enabled()) {
- if (rust_stack_ == nullptr) {
- rust_stack_ = new ::rust::Box<rust::Stack>(rust::stack_create());
- }
- rust::stack_start(**rust_stack_);
-
- if (common::init_flags::gd_hci_is_enabled()) {
- rust_hci_ = new ::rust::Box<rust::Hci>(rust::get_hci(**rust_stack_));
- }
- if (common::init_flags::gd_controller_is_enabled()) {
- rust_controller_ = new ::rust::Box<rust::Controller>(
- rust::get_controller(**rust_stack_));
- }
- bluetooth::shim::hci_on_reset_complete();
- return;
- }
-
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- ASSERT_LOG(!is_running_, "%s Gd stack already running", __func__);
- LOG_INFO("%s Starting Gd stack", __func__);
- ModuleList modules;
- if (common::init_flags::gd_hci_is_enabled()) {
- modules.add<hal::HciHal>();
- modules.add<hci::HciLayer>();
- modules.add<storage::StorageModule>();
- modules.add<shim::Dumpsys>();
- modules.add<hci::VendorSpecificEventManager>();
- }
- if (common::init_flags::gd_controller_is_enabled()) {
- modules.add<hci::Controller>();
- }
- if (common::init_flags::gd_acl_is_enabled()) {
- modules.add<hci::AclManager>();
- }
- if (common::init_flags::gd_l2cap_is_enabled()) {
- modules.add<l2cap::classic::L2capClassicModule>();
- modules.add<l2cap::le::L2capLeModule>();
- modules.add<hci::LeAdvertisingManager>();
- }
- if (common::init_flags::gd_security_is_enabled()) {
- modules.add<security::SecurityModule>();
- }
- if (common::init_flags::gd_advertising_is_enabled()) {
- modules.add<hci::LeAdvertisingManager>();
- }
- if (common::init_flags::gd_scanning_is_enabled()) {
- modules.add<hci::LeScanningManager>();
- }
- if (common::init_flags::btaa_hci_is_enabled()) {
- modules.add<activity_attribution::ActivityAttribution>();
- }
- if (common::init_flags::gd_core_is_enabled()) {
- modules.add<att::AttModule>();
- modules.add<neighbor::ConnectabilityModule>();
- modules.add<neighbor::DiscoverabilityModule>();
- modules.add<neighbor::InquiryModule>();
- modules.add<neighbor::NameModule>();
- modules.add<neighbor::NameDbModule>();
- modules.add<neighbor::PageModule>();
- modules.add<neighbor::ScanModule>();
- modules.add<storage::StorageModule>();
- }
- Start(&modules);
- is_running_ = true;
- // Make sure the leaf modules are started
- ASSERT(stack_manager_.GetInstance<storage::StorageModule>() != nullptr);
- ASSERT(stack_manager_.GetInstance<shim::Dumpsys>() != nullptr);
- if (common::init_flags::gd_core_is_enabled()) {
- btm_ = new Btm(stack_handler_,
- stack_manager_.GetInstance<neighbor::InquiryModule>());
- }
- if (common::init_flags::gd_acl_is_enabled()) {
- if (!common::init_flags::gd_core_is_enabled()) {
- acl_ = new legacy::Acl(
- stack_handler_, legacy::GetAclInterface(),
- controller_get_interface()->get_ble_acceptlist_size());
- }
- }
- if (!common::init_flags::gd_core_is_enabled()) {
- bluetooth::shim::hci_on_reset_complete();
- }
-
- if (common::init_flags::gd_advertising_is_enabled()) {
- bluetooth::shim::init_advertising_manager();
- }
- if (common::init_flags::gd_scanning_is_enabled()) {
- bluetooth::shim::init_scanning_manager();
- }
- if (common::init_flags::gd_l2cap_is_enabled() &&
- !common::init_flags::gd_core_is_enabled()) {
- L2CA_UseLegacySecurityModule();
- }
- if (common::init_flags::btaa_hci_is_enabled()) {
- bluetooth::shim::init_activity_attribution();
- }
-}
-
-void Stack::Start(ModuleList* modules) {
- ASSERT_LOG(!is_running_, "%s Gd stack already running", __func__);
- LOG_INFO("%s Starting Gd stack", __func__);
-
- stack_thread_ =
- new os::Thread("gd_stack_thread", os::Thread::Priority::NORMAL);
- stack_manager_.StartUp(modules, stack_thread_);
-
- stack_handler_ = new os::Handler(stack_thread_);
-
- LOG_INFO("%s Successfully toggled Gd stack", __func__);
-}
-
-void Stack::Stop() {
- if (common::init_flags::gd_rust_is_enabled()) {
- if (rust_stack_ != nullptr) {
- rust::stack_stop(**rust_stack_);
- }
- return;
- }
-
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- if (!common::init_flags::gd_core_is_enabled()) {
- bluetooth::shim::hci_on_shutting_down();
- }
-
- // Make sure gd acl flag is enabled and we started it up
- if (common::init_flags::gd_acl_is_enabled() && acl_ != nullptr) {
- acl_->FinalShutdown();
- delete acl_;
- acl_ = nullptr;
- }
-
- ASSERT_LOG(is_running_, "%s Gd stack not running", __func__);
- is_running_ = false;
-
- delete btm_;
- btm_ = nullptr;
-
- stack_handler_->Clear();
-
- stack_manager_.ShutDown();
-
- delete stack_handler_;
- stack_handler_ = nullptr;
-
- stack_thread_->Stop();
- delete stack_thread_;
- stack_thread_ = nullptr;
-
- LOG_INFO("%s Successfully shut down Gd stack", __func__);
-}
-
-bool Stack::IsRunning() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- return is_running_;
-}
-
-StackManager* Stack::GetStackManager() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- ASSERT(is_running_);
- return &stack_manager_;
-}
-
-const StackManager* Stack::GetStackManager() const {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- ASSERT(is_running_);
- return &stack_manager_;
-}
-
-legacy::Acl* Stack::GetAcl() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- ASSERT(is_running_);
- ASSERT_LOG(acl_ != nullptr, "Acl shim layer has not been created");
- return acl_;
-}
-
-LinkPolicyInterface* Stack::LinkPolicy() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- ASSERT(is_running_);
- ASSERT_LOG(acl_ != nullptr, "Acl shim layer has not been created");
- return acl_;
-}
-
-Btm* Stack::GetBtm() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- ASSERT(is_running_);
- return btm_;
-}
-
-os::Handler* Stack::GetHandler() {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- ASSERT(is_running_);
- return stack_handler_;
-}
-
-bool Stack::IsDumpsysModuleStarted() const {
- std::lock_guard<std::recursive_mutex> lock(mutex_);
- return GetStackManager()->IsStarted<Dumpsys>();
-}
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/stack.h b/main/shim/stack.h
deleted file mode 100644
index b105866b1..000000000
--- a/main/shim/stack.h
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <mutex>
-
-#include "main/shim/acl.h"
-#include "main/shim/btm.h"
-#include "main/shim/link_policy_interface.h"
-
-#include "gd/module.h"
-#include "gd/os/handler.h"
-#include "gd/os/thread.h"
-#include "gd/os/utils.h"
-#include "gd/stack_manager.h"
-#include "src/bridge.rs.h"
-
-// The shim layer implementation on the Gd stack side.
-namespace bluetooth {
-namespace shim {
-
-// GD shim stack, having modes corresponding to legacy stack
-class Stack {
- public:
- static Stack* GetInstance();
-
- Stack() = default;
- ~Stack() = default;
-
- // Idle mode, config is loaded, but controller is not enabled
- void StartIdleMode();
- // Running mode, everything is up
- void StartEverything();
-
- void Stop();
- bool IsRunning();
- bool IsDumpsysModuleStarted() const;
-
- StackManager* GetStackManager();
- const StackManager* GetStackManager() const;
-
- legacy::Acl* GetAcl();
- LinkPolicyInterface* LinkPolicy();
-
- Btm* GetBtm();
- os::Handler* GetHandler();
-
- ::rust::Box<rust::Hci>* GetRustHci() { return rust_hci_; }
- ::rust::Box<rust::Controller>* GetRustController() {
- return rust_controller_;
- }
-
- DISALLOW_COPY_AND_ASSIGN(Stack);
-
- private:
- mutable std::recursive_mutex mutex_;
- StackManager stack_manager_;
- bool is_running_ = false;
- os::Thread* stack_thread_ = nullptr;
- os::Handler* stack_handler_ = nullptr;
- legacy::Acl* acl_ = nullptr;
- Btm* btm_ = nullptr;
- ::rust::Box<rust::Stack>* rust_stack_ = nullptr;
- ::rust::Box<rust::Hci>* rust_hci_ = nullptr;
- ::rust::Box<rust::Controller>* rust_controller_ = nullptr;
-
- void Start(ModuleList* modules);
-};
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/main/shim/timer.cc b/main/shim/timer.cc
new file mode 100644
index 000000000..7e21deb25
--- /dev/null
+++ b/main/shim/timer.cc
@@ -0,0 +1,59 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#define LOG_TAG "bt_shim_timer"
+
+#include <base/bind.h>
+#include <cstdint>
+#include <functional>
+
+#include "main/shim/shim.h"
+#include "main/shim/timer.h"
+#include "osi/include/alarm.h"
+#include "osi/include/log.h"
+
+static void timer_timeout(void* data) {
+ CHECK(data != nullptr);
+ bluetooth::shim::Timer* timeout = static_cast<bluetooth::shim::Timer*>(data);
+ bluetooth::shim::Post(
+ base::Bind(&bluetooth::shim::Timer::Pop, base::Unretained(timeout)));
+}
+
+void bluetooth::shim::Timer::Set(uint64_t duration_ms,
+ std::function<void()> func) {
+ CHECK(duration_ms != 0);
+ callback_ = func;
+ alarm_set_on_mloop(timer_, duration_ms, timer_timeout, (void*)this);
+}
+
+void bluetooth::shim::Timer::Cancel() {
+ alarm_cancel(timer_);
+ callback_ = {};
+}
+
+bool bluetooth::shim::Timer::IsActive() { return callback_ != nullptr; }
+
+bluetooth::shim::Timer::Timer(const char* name) {
+ timer_ = alarm_new(name);
+ CHECK(timer_ != nullptr);
+}
+
+bluetooth::shim::Timer::~Timer() { alarm_free(timer_); }
+
+void bluetooth::shim::Timer::Pop(Timer* timer) {
+ timer->callback_();
+ timer->callback_ = {};
+}
diff --git a/main/shim/timer.h b/main/shim/timer.h
new file mode 100644
index 000000000..16d35c44d
--- /dev/null
+++ b/main/shim/timer.h
@@ -0,0 +1,74 @@
+/*
+ * Copyright 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#pragma once
+
+#include <cstdint>
+#include <functional>
+#include "osi/include/alarm.h"
+
+namespace bluetooth {
+namespace shim {
+
+class Timer {
+ public:
+ /**
+ * Set this timer using the osi timer alarm functionality.
+ *
+ * The alarm duration *must not* be zero. The timer is set
+ * on the bluetooth main message loop thread.
+ *
+ * @param duration_ms Duration in milliseconds (>0) before alarm pops
+ * @param func Function to execute upon alarm pop.
+ */
+ void Set(uint64_t duration_ms, std::function<void()> func);
+
+ /**
+ * Cancel this previously set timer.
+ *
+ * The associated function call will *not* be executed.
+ */
+ void Cancel();
+
+ /**
+ * Determine if a given timer has been set or not.
+ *
+ * @return |true| if timer has been set, |false| otherwise.
+ */
+ bool IsActive();
+
+ /**
+ * @param name Arbitrary name passed to the osi module.
+ */
+ Timer(const char* name);
+ ~Timer();
+
+ /**
+ * Pop this timer.
+ *
+ * Called from an internal trampoline timeout global function registered
+ * with osi alarm. This trampoline function will then post
+ * the execution of the callback function onto the shim thread.
+ */
+ static void Pop(Timer* timer);
+
+ private:
+ std::function<void()> callback_{};
+ alarm_t* timer_{nullptr};
+};
+
+} // namespace shim
+} // namespace bluetooth
diff --git a/main/stack_config.cc b/main/stack_config.cc
index d4faae13d..0e5625005 100644
--- a/main/stack_config.cc
+++ b/main/stack_config.cc
@@ -41,18 +41,18 @@ static std::unique_ptr<config_t> config;
static future_t* init() {
// TODO(armansito): Find a better way than searching by a hardcoded path.
-#if defined(OS_GENERIC) && !defined(TARGET_FLOSS)
+#if defined(OS_GENERIC)
const char* path = "bt_stack.conf";
#else // !defined(OS_GENERIC)
const char* path = "/etc/bluetooth/bt_stack.conf";
#endif // defined(OS_GENERIC)
CHECK(path != NULL);
- LOG_INFO("%s attempt to load stack conf from %s", __func__, path);
+ LOG_INFO(LOG_TAG, "%s attempt to load stack conf from %s", __func__, path);
config = config_new(path);
if (!config) {
- LOG_INFO("%s file >%s< not found", __func__, path);
+ LOG_INFO(LOG_TAG, "%s file >%s< not found", __func__, path);
config = config_new_empty();
}
diff --git a/main/test/main_shim_test.cc b/main/test/main_shim_test.cc
deleted file mode 100644
index d4a481cae..000000000
--- a/main/test/main_shim_test.cc
+++ /dev/null
@@ -1,420 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-#include <condition_variable>
-#include <future>
-#include <map>
-#include <thread>
-
-#include "btif/include/btif_hh.h"
-#include "device/include/controller.h"
-#include "gd/btaa/activity_attribution.h"
-#include "gd/hal/hci_hal.h"
-#include "gd/hci/acl_manager_mock.h"
-#include "gd/hci/controller_mock.h"
-#include "gd/module.h"
-#include "gd/os/mock_queue.h"
-#include "gd/os/queue.h"
-#include "gd/packet/packet_view.h"
-#include "hci/acl_manager.h"
-#include "hci/acl_manager/classic_acl_connection.h"
-#include "hci/acl_manager/connection_callbacks.h"
-#include "hci/acl_manager/connection_management_callbacks.h"
-#include "hci/acl_manager/le_acl_connection.h"
-#include "hci/acl_manager/le_connection_callbacks.h"
-#include "hci/acl_manager/le_connection_management_callbacks.h"
-#include "hci/include/hci_layer.h"
-#include "hci/include/hci_packet_factory.h"
-#include "hci/include/hci_packet_parser.h"
-#include "hci/include/packet_fragmenter.h"
-#include "include/hardware/bt_activity_attribution.h"
-#include "main/shim/acl.h"
-#include "main/shim/acl_legacy_interface.h"
-#include "main/shim/helpers.h"
-#include "os/handler.h"
-#include "os/thread.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/btu.h"
-#include "stack/l2cap/l2c_int.h"
-#include "test/common/main_handler.h"
-#include "test/mock/mock_main_shim_entry.h"
-
-using namespace bluetooth;
-using namespace testing;
-
-namespace test = bluetooth::hci::testing;
-
-const uint8_t kMaxLeAcceptlistSize = 16;
-std::map<std::string, int> mock_function_count_map;
-tL2C_CB l2cb;
-tBTM_CB btm_cb;
-btif_hh_cb_t btif_hh_cb;
-
-namespace {
-std::map<std::string, std::promise<uint16_t>> mock_function_handle_promise_map;
-}
-
-uint8_t mock_get_ble_acceptlist_size() { return 123; }
-
-struct controller_t mock_controller {
- .get_ble_acceptlist_size = mock_get_ble_acceptlist_size,
-};
-
-const controller_t* controller_get_interface() { return &mock_controller; }
-
-void mock_on_send_data_upwards(BT_HDR*) { mock_function_count_map[__func__]++; }
-
-void mock_on_packets_completed(uint16_t handle, uint16_t num_packets) {
- mock_function_count_map[__func__]++;
-}
-
-void mock_connection_classic_on_connected(const RawAddress& bda,
- uint16_t handle, uint8_t enc_mode) {
- mock_function_count_map[__func__]++;
-}
-
-void mock_connection_classic_on_failed(const RawAddress& bda,
- tHCI_STATUS status) {
- mock_function_count_map[__func__]++;
-}
-
-void mock_connection_classic_on_disconnected(tHCI_STATUS status,
- uint16_t handle,
- tHCI_STATUS reason) {
- mock_function_count_map[__func__]++;
- ASSERT_TRUE(mock_function_handle_promise_map.find(__func__) !=
- mock_function_handle_promise_map.end());
- mock_function_handle_promise_map[__func__].set_value(handle);
-}
-void mock_connection_le_on_connected(
- const tBLE_BD_ADDR& address_with_type, uint16_t handle, tHCI_ROLE role,
- uint16_t conn_interval, uint16_t conn_latency, uint16_t conn_timeout,
- const RawAddress& local_rpa, const RawAddress& peer_rpa,
- uint8_t peer_addr_type) {
- mock_function_count_map[__func__]++;
-}
-void mock_connection_le_on_failed(const tBLE_BD_ADDR& address_with_type,
- uint16_t handle, bool enhanced,
- tHCI_STATUS status) {
- mock_function_count_map[__func__]++;
-}
-void mock_connection_le_on_disconnected(tHCI_STATUS status, uint16_t handle,
- tHCI_STATUS reason) {
- mock_function_count_map[__func__]++;
-}
-
-const shim::legacy::acl_interface_t GetMockAclInterface() {
- shim::legacy::acl_interface_t acl_interface{
- .on_send_data_upwards = mock_on_send_data_upwards,
- .on_packets_completed = mock_on_packets_completed,
-
- .connection.classic.on_connected = mock_connection_classic_on_connected,
- .connection.classic.on_failed = mock_connection_classic_on_failed,
- .connection.classic.on_disconnected =
- mock_connection_classic_on_disconnected,
-
- .connection.le.on_connected = mock_connection_le_on_connected,
- .connection.le.on_failed = mock_connection_le_on_failed,
- .connection.le.on_disconnected = mock_connection_le_on_disconnected,
-
- .connection.sco.on_esco_connect_request = nullptr,
- .connection.sco.on_sco_connect_request = nullptr,
- .connection.sco.on_disconnected = nullptr,
-
- .link.classic.on_authentication_complete = nullptr,
- .link.classic.on_central_link_key_complete = nullptr,
- .link.classic.on_change_connection_link_key_complete = nullptr,
- .link.classic.on_encryption_change = nullptr,
- .link.classic.on_flow_specification_complete = nullptr,
- .link.classic.on_flush_occurred = nullptr,
- .link.classic.on_mode_change = nullptr,
- .link.classic.on_packet_type_changed = nullptr,
- .link.classic.on_qos_setup_complete = nullptr,
- .link.classic.on_read_afh_channel_map_complete = nullptr,
- .link.classic.on_read_automatic_flush_timeout_complete = nullptr,
- .link.classic.on_sniff_subrating = nullptr,
- .link.classic.on_read_clock_complete = nullptr,
- .link.classic.on_read_clock_offset_complete = nullptr,
- .link.classic.on_read_failed_contact_counter_complete = nullptr,
- .link.classic.on_read_link_policy_settings_complete = nullptr,
- .link.classic.on_read_link_quality_complete = nullptr,
- .link.classic.on_read_link_supervision_timeout_complete = nullptr,
- .link.classic.on_read_remote_version_information_complete = nullptr,
- .link.classic.on_read_remote_extended_features_complete = nullptr,
- .link.classic.on_read_rssi_complete = nullptr,
- .link.classic.on_read_transmit_power_level_complete = nullptr,
- .link.classic.on_role_change = nullptr,
- .link.classic.on_role_discovery_complete = nullptr,
-
- .link.le.on_connection_update = nullptr,
- .link.le.on_data_length_change = nullptr,
- .link.le.on_read_remote_version_information_complete = nullptr,
- };
- return acl_interface;
-}
-
-const hci_packet_factory_t* hci_packet_factory_get_interface() {
- return nullptr;
-}
-const hci_packet_parser_t* hci_packet_parser_get_interface() { return nullptr; }
-const hci_t* hci_layer_get_interface() { return nullptr; }
-const packet_fragmenter_t* packet_fragmenter_get_interface() { return nullptr; }
-void LogMsg(uint32_t trace_set_mask, const char* fmt_str, ...) {}
-
-template <typename T>
-class MockEnQueue : public os::IQueueEnqueue<T> {
- using EnqueueCallback = base::Callback<std::unique_ptr<T>()>;
-
- void RegisterEnqueue(os::Handler* handler,
- EnqueueCallback callback) override {}
- void UnregisterEnqueue() override {}
-};
-
-template <typename T>
-class MockDeQueue : public os::IQueueDequeue<T> {
- using DequeueCallback = base::Callback<void()>;
-
- void RegisterDequeue(os::Handler* handler,
- DequeueCallback callback) override {}
- void UnregisterDequeue() override {}
- std::unique_ptr<T> TryDequeue() override { return nullptr; }
-};
-
-class MockClassicAclConnection
- : public bluetooth::hci::acl_manager::ClassicAclConnection {
- public:
- MockClassicAclConnection(const hci::Address& address, uint16_t handle) {
- address_ = address; // ClassicAclConnection
- handle_ = handle; // AclConnection
- }
-
- void RegisterCallbacks(
- hci::acl_manager::ConnectionManagementCallbacks* callbacks,
- os::Handler* handler) override {
- callbacks_ = callbacks;
- handler_ = handler;
- }
-
- // Returns the bidi queue for this mock connection
- AclConnection::QueueUpEnd* GetAclQueueEnd() const override {
- return &mock_acl_queue_;
- }
-
- mutable common::BidiQueueEnd<hci::BasePacketBuilder,
- packet::PacketView<hci::kLittleEndian>>
- mock_acl_queue_{&tx_, &rx_};
-
- MockEnQueue<hci::BasePacketBuilder> tx_;
- MockDeQueue<packet::PacketView<hci::kLittleEndian>> rx_;
-
- bool ReadRemoteVersionInformation() override { return true; }
- bool ReadRemoteSupportedFeatures() override { return true; }
-
- bool Disconnect(hci::DisconnectReason reason) override {
- disconnect_cnt_++;
- disconnect_promise_.set_value(handle_);
- return true;
- }
-
- std::promise<uint16_t> disconnect_promise_;
-
- hci::acl_manager::ConnectionManagementCallbacks* callbacks_{nullptr};
- os::Handler* handler_{nullptr};
-
- int disconnect_cnt_{0};
-};
-
-namespace bluetooth {
-namespace shim {
-void init_activity_attribution() {}
-
-namespace testing {
-extern os::Handler* mock_handler_;
-
-} // namespace testing
-} // namespace shim
-
-namespace activity_attribution {
-ActivityAttributionInterface* get_activity_attribution_instance() {
- return nullptr;
-}
-
-const ModuleFactory ActivityAttribution::Factory =
- ModuleFactory([]() { return nullptr; });
-} // namespace activity_attribution
-
-namespace hal {
-const ModuleFactory HciHal::Factory = ModuleFactory([]() { return nullptr; });
-} // namespace hal
-
-} // namespace bluetooth
-
-class MainShimTest : public testing::Test {
- public:
- protected:
- void SetUp() override {
- main_thread_start_up();
-
- thread_ = new os::Thread("acl_thread", os::Thread::Priority::NORMAL);
- handler_ = new os::Handler(thread_);
-
- /* extern */ test::mock_controller_ =
- new bluetooth::hci::testing::MockController();
- /* extern */ test::mock_acl_manager_ =
- new bluetooth::hci::testing::MockAclManager();
- }
- void TearDown() override {
- delete test::mock_controller_;
- test::mock_controller_ = nullptr;
- delete test::mock_acl_manager_;
- test::mock_acl_manager_ = nullptr;
-
- handler_->Clear();
- delete handler_;
- delete thread_;
-
- main_thread_shut_down();
- }
- os::Thread* thread_{nullptr};
- os::Handler* handler_{nullptr};
-
- // Convenience method to create ACL objects
- std::unique_ptr<shim::legacy::Acl> MakeAcl() {
- EXPECT_CALL(*test::mock_acl_manager_, RegisterCallbacks(_, _)).Times(1);
- EXPECT_CALL(*test::mock_acl_manager_, RegisterLeCallbacks(_, _)).Times(1);
- EXPECT_CALL(*test::mock_controller_,
- RegisterCompletedMonitorAclPacketsCallback(_))
- .Times(1);
- EXPECT_CALL(*test::mock_acl_manager_, HACK_SetScoDisconnectCallback(_))
- .Times(1);
- EXPECT_CALL(*test::mock_controller_,
- UnregisterCompletedMonitorAclPacketsCallback)
- .Times(1);
- return std::make_unique<shim::legacy::Acl>(handler_, GetMockAclInterface(),
- kMaxLeAcceptlistSize);
- }
-};
-
-TEST_F(MainShimTest, Nop) {}
-
-TEST_F(MainShimTest, Acl_Lifecycle) {
- auto acl = MakeAcl();
- acl.reset();
- acl = MakeAcl();
-}
-
-TEST_F(MainShimTest, helpers) {
- uint8_t reason = 0;
- do {
- hci::ErrorCode gd_error_code = static_cast<hci::ErrorCode>(reason);
- tHCI_STATUS legacy_code = ToLegacyHciErrorCode(gd_error_code);
- ASSERT_EQ(reason,
- static_cast<uint8_t>(ToLegacyHciErrorCode(gd_error_code)));
- ASSERT_EQ(reason, static_cast<uint8_t>(legacy_code));
- } while (++reason != 0);
-}
-
-TEST_F(MainShimTest, connect_and_disconnect) {
- hci::Address address({0x11, 0x22, 0x33, 0x44, 0x55, 0x66});
-
- auto acl = MakeAcl();
-
- // Create connection
- EXPECT_CALL(*test::mock_acl_manager_, CreateConnection(_)).Times(1);
- acl->CreateClassicConnection(address);
-
- // Respond with a mock connection created
- auto connection = std::make_unique<MockClassicAclConnection>(address, 123);
- ASSERT_EQ(123, connection->GetHandle());
- ASSERT_EQ(hci::Address({0x11, 0x22, 0x33, 0x44, 0x55, 0x66}),
- connection->GetAddress());
- MockClassicAclConnection* raw_connection = connection.get();
-
- acl->OnConnectSuccess(std::move(connection));
- ASSERT_EQ(nullptr, connection);
-
- // Specify local disconnect request
- auto tx_disconnect_future = raw_connection->disconnect_promise_.get_future();
- acl->DisconnectClassic(123, HCI_SUCCESS);
-
- // Wait for disconnect to be received
- uint16_t result = tx_disconnect_future.get();
- ASSERT_EQ(123, result);
-
- // Now emulate the remote disconnect response
- auto handle_promise = std::promise<uint16_t>();
- auto rx_disconnect_future = handle_promise.get_future();
- mock_function_handle_promise_map["mock_connection_classic_on_disconnected"] =
- std::move(handle_promise);
- raw_connection->callbacks_->OnDisconnection(hci::ErrorCode::SUCCESS);
-
- result = rx_disconnect_future.get();
- ASSERT_EQ(123, result);
-
- // *Our* task completing indicates reactor is done
- std::promise<void> done;
- auto future = done.get_future();
- handler_->Call([](std::promise<void> done) { done.set_value(); },
- std::move(done));
- future.wait();
-}
-
-TEST_F(MainShimTest, is_flushable) {
- {
- BT_HDR* bt_hdr =
- (BT_HDR*)calloc(1, sizeof(BT_HDR) + sizeof(HciDataPreamble));
-
- ASSERT_TRUE(!IsPacketFlushable(bt_hdr));
- HciDataPreamble* hci = ToPacketData<HciDataPreamble>(bt_hdr);
- hci->SetFlushable();
- ASSERT_TRUE(IsPacketFlushable(bt_hdr));
-
- free(bt_hdr);
- }
-
- {
- size_t offset = 1024;
- BT_HDR* bt_hdr =
- (BT_HDR*)calloc(1, sizeof(BT_HDR) + sizeof(HciDataPreamble) + offset);
- bt_hdr->offset = offset;
-
- ASSERT_TRUE(!IsPacketFlushable(bt_hdr));
- HciDataPreamble* hci = ToPacketData<HciDataPreamble>(bt_hdr);
- hci->SetFlushable();
- ASSERT_TRUE(IsPacketFlushable(bt_hdr));
-
- free(bt_hdr);
- }
-
- {
- size_t offset = 1024;
- BT_HDR* bt_hdr =
- (BT_HDR*)calloc(1, sizeof(BT_HDR) + sizeof(HciDataPreamble) + offset);
-
- uint8_t* p = ToPacketData<uint8_t>(bt_hdr, L2CAP_SEND_CMD_OFFSET);
- UINT16_TO_STREAM(
- p, 0x123 | (L2CAP_PKT_START_NON_FLUSHABLE << L2CAP_PKT_TYPE_SHIFT));
- ASSERT_TRUE(!IsPacketFlushable(bt_hdr));
-
- p = ToPacketData<uint8_t>(bt_hdr, L2CAP_SEND_CMD_OFFSET);
- UINT16_TO_STREAM(p, 0x123 | (L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT));
- ASSERT_TRUE(IsPacketFlushable(bt_hdr));
-
- free(bt_hdr);
- }
-}
diff --git a/osi/Android.bp b/osi/Android.bp
index 7a979cfe1..3f652f4ef 100644
--- a/osi/Android.bp
+++ b/osi/Android.bp
@@ -1,13 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- // SPDX-license-identifier-MIT
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_defaults {
name: "fluoride_osi_defaults",
defaults: ["fluoride_defaults"],
diff --git a/osi/BUILD.gn b/osi/BUILD.gn
index 75470b62c..c4fb0cb10 100644
--- a/osi/BUILD.gn
+++ b/osi/BUILD.gn
@@ -44,61 +44,53 @@ static_library("osi") {
]
include_dirs = [
- "//bt/",
- "//bt/linux_include",
- "//bt/internal_include",
- "//bt/utils/include",
- "//bt/stack/include",
+ "//",
+ "//linux_include",
+ "//internal_include",
+ "//utils/include",
+ "//stack/include",
]
deps = [
- "//bt/common",
- "//bt/gd/rust/shim:init_flags_bridge_header",
- ]
-
- configs += [
- "//bt:target_defaults",
+ "//common",
+ "//third_party/libchrome:base",
]
}
-if (use.test) {
- executable("net_test_osi") {
- sources = [
- "test/AlarmTestHarness.cc",
- "test/AllocationTestHarness.cc",
- "test/alarm_test.cc",
- "test/allocation_tracker_test.cc",
- "test/allocator_test.cc",
- "test/array_test.cc",
- "test/config_test.cc",
- "test/future_test.cc",
- "test/hash_map_utils_test.cc",
- "test/list_test.cc",
- "test/properties_test.cc",
- "test/rand_test.cc",
- "test/reactor_test.cc",
- "test/ringbuffer_test.cc",
- "test/thread_test.cc",
- ]
-
- include_dirs = [
- "//bt/",
- "//bt/osi/test",
- ]
+executable("net_test_osi") {
+ testonly = true
+ sources = [
+ "test/AlarmTestHarness.cc",
+ "test/AllocationTestHarness.cc",
+ "test/alarm_test.cc",
+ "test/allocation_tracker_test.cc",
+ "test/allocator_test.cc",
+ "test/array_test.cc",
+ "test/config_test.cc",
+ "test/future_test.cc",
+ "test/hash_map_utils_test.cc",
+ "test/list_test.cc",
+ "test/properties_test.cc",
+ "test/rand_test.cc",
+ "test/reactor_test.cc",
+ "test/ringbuffer_test.cc",
+ "test/thread_test.cc",
+ ]
- deps = [
- "//bt/osi",
- ]
+ include_dirs = [
+ "//",
+ "//osi/test",
+ ]
- configs += [
- "//bt:external_gtest_main",
- "//bt:external_gmock_main",
- "//bt:target_defaults",
- ]
+ deps = [
+ "//osi",
+ "//third_party/googletest:gtest_main",
+ "//third_party/googletest:gmock_main",
+ "//third_party/libchrome:base",
+ ]
- libs = [
- "pthread",
- "rt",
- ]
- }
+ libs = [
+ "-lpthread",
+ "-lrt",
+ ]
}
diff --git a/osi/include/compat.h b/osi/include/compat.h
index 1d19a590d..95fe0373e 100644
--- a/osi/include/compat.h
+++ b/osi/include/compat.h
@@ -26,7 +26,7 @@
#include <unistd.h>
/* Get thread identification. */
-pid_t gettid(void) throw();
+pid_t gettid(void);
/* Copy src to string dst of size siz. */
size_t strlcpy(char* dst, const char* src, size_t siz);
diff --git a/osi/include/log.h b/osi/include/log.h
index 5aeb316f4..1c2e96dd9 100644
--- a/osi/include/log.h
+++ b/osi/include/log.h
@@ -18,12 +18,69 @@
#pragma once
-#include "gd/common/init_flags.h"
+/*
+ * TODO(armansito): Work-around until we figure out a way to generate logs in a
+ * platform-independent manner.
+ */
+#if defined(OS_GENERIC)
-#ifndef OSI_INCLUDE_LOG_H
-#define OSI_INCLUDE_LOG_H
-#endif
+/* syslog didn't work well here since we would be redefining LOG_DEBUG. */
+#include <stdio.h>
-#include "gd/os/log.h"
+#define LOGWRAPPER(tag, fmt, args...) \
+ fprintf(stderr, "%s: " fmt "\n", tag, ##args)
-#undef OSI_INCLUDE_LOG_H \ No newline at end of file
+#define LOG_VERBOSE(...) LOGWRAPPER(__VA_ARGS__)
+#define LOG_DEBUG(...) LOGWRAPPER(__VA_ARGS__)
+#define LOG_INFO(...) LOGWRAPPER(__VA_ARGS__)
+#define LOG_WARN(...) LOGWRAPPER(__VA_ARGS__)
+#define LOG_ERROR(...) LOGWRAPPER(__VA_ARGS__)
+
+#define LOG_EVENT_INT(...)
+
+#else /* !defined(OS_GENERIC) */
+
+#include <log/log.h>
+
+/**
+ * These log statements are effectively executing only ALOG(_________, tag, fmt,
+ * ## args ).
+ * fprintf is only to cause compilation error when LOG_TAG is not provided,
+ * which breaks build on Linux (for OS_GENERIC).
+ */
+
+#if LOG_NDEBUG
+#define LOG_VERBOSE(tag, fmt, args...) \
+ do { \
+ (true) ? ((int)0) : fprintf(stderr, "%s" fmt, tag, ##args); \
+ } while (0)
+#else // LOG_NDEBUG
+#define LOG_VERBOSE(tag, fmt, args...) \
+ do { \
+ (true) ? ALOG(LOG_VERBOSE, tag, fmt, ##args) \
+ : fprintf(stderr, "%s" fmt, tag, ##args); \
+ } while (0)
+#endif // !LOG_NDEBUG
+
+#define LOG_DEBUG(tag, fmt, args...) \
+ do { \
+ (true) ? ALOG(LOG_DEBUG, tag, fmt, ##args) \
+ : fprintf(stderr, "%s" fmt, tag, ##args); \
+ } while (0)
+#define LOG_INFO(tag, fmt, args...) \
+ do { \
+ (true) ? ALOG(LOG_INFO, tag, fmt, ##args) \
+ : fprintf(stderr, "%s" fmt, tag, ##args); \
+ } while (0)
+#define LOG_WARN(tag, fmt, args...) \
+ do { \
+ (true) ? ALOG(LOG_WARN, tag, fmt, ##args) \
+ : fprintf(stderr, "%s" fmt, tag, ##args); \
+ } while (0)
+#define LOG_ERROR(tag, fmt, args...) \
+ do { \
+ (true) ? ALOG(LOG_ERROR, tag, fmt, ##args) \
+ : fprintf(stderr, "%s" fmt, tag, ##args); \
+ } while (0)
+
+#endif /* defined(OS_GENERIC) */
diff --git a/osi/include/osi.h b/osi/include/osi.h
index f5a21de28..a39d56ceb 100644
--- a/osi/include/osi.h
+++ b/osi/include/osi.h
@@ -56,7 +56,3 @@ int osi_rand(void);
#define OSI_NO_INTR(fn) \
do { \
} while ((fn) == -1 && errno == EINTR)
-
-#ifndef FALLTHROUGH_INTENDED
-#define FALLTHROUGH_INTENDED [[clang::fallthrough]] // NOLINT
-#endif
diff --git a/osi/src/alarm.cc b/osi/src/alarm.cc
index 6e5d22f43..bc1eee54b 100644
--- a/osi/src/alarm.cc
+++ b/osi/src/alarm.cc
@@ -24,6 +24,7 @@
#include <base/cancelable_callback.h>
#include <base/logging.h>
+#include <base/message_loop/message_loop.h>
#include <errno.h>
#include <fcntl.h>
#include <inttypes.h>
@@ -49,6 +50,7 @@
using base::Bind;
using base::CancelableClosure;
+using base::MessageLoop;
// Callback and timer threads should run at RT priority in order to ensure they
// meet audio deadlines. Use this priority for all audio/timer related thread.
@@ -193,7 +195,6 @@ void alarm_free(alarm_t* alarm) {
osi_free((void*)alarm->stats.name);
alarm->closure.~CancelableClosureInStruct();
- alarm->callback_mutex.reset();
osi_free(alarm);
}
@@ -316,7 +317,7 @@ static bool lazy_initialize(void) {
alarms = list_new(NULL);
if (!alarms) {
- LOG_ERROR("%s unable to allocate alarm list.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to allocate alarm list.", __func__);
goto error;
}
@@ -332,20 +333,22 @@ static bool lazy_initialize(void) {
alarm_expired = semaphore_new(0);
if (!alarm_expired) {
- LOG_ERROR("%s unable to create alarm expired semaphore", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to create alarm expired semaphore", __func__);
goto error;
}
default_callback_thread =
thread_new_sized("alarm_default_callbacks", SIZE_MAX);
if (default_callback_thread == NULL) {
- LOG_ERROR("%s unable to create default alarm callbacks thread.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to create default alarm callbacks thread.",
+ __func__);
goto error;
}
thread_set_rt_priority(default_callback_thread, THREAD_RT_PRIORITY);
default_callback_queue = fixed_queue_new(SIZE_MAX);
if (default_callback_queue == NULL) {
- LOG_ERROR("%s unable to create default alarm callbacks queue.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to create default alarm callbacks queue.",
+ __func__);
goto error;
}
alarm_register_processing_queue(default_callback_queue,
@@ -354,7 +357,7 @@ static bool lazy_initialize(void) {
dispatcher_thread_active = true;
dispatcher_thread = thread_new("alarm_dispatcher");
if (!dispatcher_thread) {
- LOG_ERROR("%s unable to create alarm callback thread.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to create alarm callback thread.", __func__);
goto error;
}
thread_set_rt_priority(dispatcher_thread, THREAD_RT_PRIORITY);
@@ -390,7 +393,8 @@ static uint64_t now_ms(void) {
struct timespec ts;
if (clock_gettime(CLOCK_ID, &ts) == -1) {
- LOG_ERROR("%s unable to get current time: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to get current time: %s", __func__,
+ strerror(errno));
return 0;
}
@@ -472,7 +476,7 @@ static void reschedule_root_alarm(void) {
if (next_expiration < TIMER_INTERVAL_FOR_WAKELOCK_IN_MS) {
if (!timer_set) {
if (!wakelock_acquire()) {
- LOG_ERROR("%s unable to acquire wake lock", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to acquire wake lock", __func__);
goto done;
}
}
@@ -506,7 +510,8 @@ static void reschedule_root_alarm(void) {
wakeup_time.it_value.tv_sec = (next->deadline_ms / 1000);
wakeup_time.it_value.tv_nsec = (next->deadline_ms % 1000) * 1000000LL;
if (timer_settime(wakeup_timer, TIMER_ABSTIME, &wakeup_time, NULL) == -1)
- LOG_ERROR("%s unable to set wakeup timer: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to set wakeup timer: %s", __func__,
+ strerror(errno));
}
done:
@@ -517,7 +522,7 @@ done:
}
if (timer_settime(timer, TIMER_ABSTIME, &timer_time, NULL) == -1)
- LOG_ERROR("%s unable to set timer: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to set timer: %s", __func__, strerror(errno));
// If next expiration was in the past (e.g. short timer that got context
// switched) then the timer might have diarmed itself. Detect this case and
@@ -534,8 +539,8 @@ done:
timer_gettime(timer, &time_to_expire);
if (time_to_expire.it_value.tv_sec == 0 &&
time_to_expire.it_value.tv_nsec == 0) {
- LOG_INFO(
-
+ LOG_DEBUG(
+ LOG_TAG,
"%s alarm expiration too close for posix timers, switching to guns",
__func__);
semaphore_post(alarm_expired);
@@ -646,20 +651,21 @@ static void callback_dispatch(UNUSED_ATTR void* context) {
// Enqueue the alarm for processing
if (alarm->for_msg_loop) {
- if (!get_main_thread()) {
- LOG_ERROR("%s: message loop already NULL. Alarm: %s", __func__,
+ if (!get_main_message_loop()) {
+ LOG_ERROR(LOG_TAG, "%s: message loop already NULL. Alarm: %s", __func__,
alarm->stats.name);
continue;
}
alarm->closure.i.Reset(Bind(alarm_ready_mloop, alarm));
- get_main_thread()->DoInThread(FROM_HERE, alarm->closure.i.callback());
+ get_main_message_loop()->task_runner()->PostTask(
+ FROM_HERE, alarm->closure.i.callback());
} else {
fixed_queue_enqueue(alarm->queue, alarm);
}
}
- LOG_INFO("%s Callback thread exited", __func__);
+ LOG_DEBUG(LOG_TAG, "%s Callback thread exited", __func__);
}
static bool timer_create_internal(const clockid_t clock_id, timer_t* timer) {
@@ -679,17 +685,17 @@ static bool timer_create_internal(const clockid_t clock_id, timer_t* timer) {
sigevent.sigev_notify_function = (void (*)(union sigval))timer_callback;
sigevent.sigev_notify_attributes = &thread_attr;
if (timer_create(clock_id, &sigevent, timer) == -1) {
- LOG_ERROR("%s unable to create timer with clock %d: %s", __func__, clock_id,
- strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to create timer with clock %d: %s", __func__,
+ clock_id, strerror(errno));
if (clock_id == CLOCK_BOOTTIME_ALARM) {
- LOG_ERROR(
- "The kernel might not have support for "
- "timer_create(CLOCK_BOOTTIME_ALARM): "
- "https://lwn.net/Articles/429925/");
- LOG_ERROR(
- "See following patches: "
- "https://git.kernel.org/cgit/linux/kernel/git/torvalds/"
- "linux.git/log/?qt=grep&q=CLOCK_BOOTTIME_ALARM");
+ LOG_ERROR(LOG_TAG,
+ "The kernel might not have support for "
+ "timer_create(CLOCK_BOOTTIME_ALARM): "
+ "https://lwn.net/Articles/429925/");
+ LOG_ERROR(LOG_TAG,
+ "See following patches: "
+ "https://git.kernel.org/cgit/linux/kernel/git/torvalds/"
+ "linux.git/log/?qt=grep&q=CLOCK_BOOTTIME_ALARM");
}
return false;
}
diff --git a/osi/src/allocation_tracker.cc b/osi/src/allocation_tracker.cc
index 4d8e4a152..ba6b7f1d1 100644
--- a/osi/src/allocation_tracker.cc
+++ b/osi/src/allocation_tracker.cc
@@ -56,7 +56,7 @@ void allocation_tracker_init(void) {
// randomize the canary contents
for (size_t i = 0; i < canary_size; i++) canary[i] = (char)osi_rand();
- LOG_INFO("canary initialized");
+ LOG_DEBUG(LOG_TAG, "canary initialized");
enabled = true;
}
@@ -88,7 +88,8 @@ size_t allocation_tracker_expect_no_allocations(void) {
if (!allocation->freed) {
unfreed_memory_size +=
allocation->size; // Report back the unfreed byte count
- LOG_ERROR("%s found unfreed allocation. address: 0x%zx size: %zd bytes",
+ LOG_ERROR(LOG_TAG,
+ "%s found unfreed allocation. address: 0x%zx size: %zd bytes",
__func__, (uintptr_t)allocation->ptr, allocation->size);
}
}
diff --git a/osi/src/array.cc b/osi/src/array.cc
index 6ec419c9e..f28a70c68 100644
--- a/osi/src/array.cc
+++ b/osi/src/array.cc
@@ -81,10 +81,10 @@ bool array_append_ptr(array_t* array, void* data) {
CHECK(data != NULL);
if (array->length == array->capacity && !grow(array)) {
- LOG_ERROR(
- "%s unable to grow array past current capacity of %zu elements "
- "of size %zu.",
- __func__, array->capacity, array->element_size);
+ LOG_ERROR(LOG_TAG,
+ "%s unable to grow array past current capacity of %zu elements "
+ "of size %zu.",
+ __func__, array->capacity, array->element_size);
return false;
}
diff --git a/osi/src/compat.cc b/osi/src/compat.cc
index e5b41a528..069964c22 100644
--- a/osi/src/compat.cc
+++ b/osi/src/compat.cc
@@ -35,7 +35,7 @@
#include "osi/include/osi.h"
#if __GLIBC__
-pid_t gettid(void) throw() { return syscall(SYS_gettid); }
+pid_t gettid(void) { return syscall(SYS_gettid); }
#endif
/* These functions from bionic
diff --git a/osi/src/future.cc b/osi/src/future.cc
index 203dbe5a5..e5347a411 100644
--- a/osi/src/future.cc
+++ b/osi/src/future.cc
@@ -40,7 +40,8 @@ future_t* future_new(void) {
ret->semaphore = semaphore_new(0);
if (!ret->semaphore) {
- LOG_ERROR("%s unable to allocate memory for the semaphore.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to allocate memory for the semaphore.",
+ __func__);
goto error;
}
diff --git a/osi/src/hash_map_utils.cc b/osi/src/hash_map_utils.cc
index eb1e0519e..6cd58de47 100644
--- a/osi/src/hash_map_utils.cc
+++ b/osi/src/hash_map_utils.cc
@@ -35,7 +35,7 @@ hash_map_utils_new_from_string_params(const char* params) {
char* str = osi_strdup(params);
if (!str) return map;
- LOG_VERBOSE("%s: source string: '%s'", __func__, str);
+ LOG_VERBOSE(LOG_TAG, "%s: source string: '%s'", __func__, str);
// Parse |str| and add extracted key-and-value pair(s) in |map|.
int items = 0;
@@ -69,7 +69,7 @@ hash_map_utils_new_from_string_params(const char* params) {
kvpair = strtok_r(NULL, ";", &tmpstr);
}
- if (!items) LOG_VERBOSE("%s: no items found in string\n", __func__);
+ if (!items) LOG_VERBOSE(LOG_TAG, "%s: no items found in string\n", __func__);
osi_free(str);
return map;
@@ -78,6 +78,7 @@ hash_map_utils_new_from_string_params(const char* params) {
void hash_map_utils_dump_string_keys_string_values(
std::unordered_map<std::string, std::string>& map) {
for (const auto& ptr : map) {
- LOG_INFO("key: '%s' value: '%s'\n", ptr.first.c_str(), ptr.second.c_str());
+ LOG_INFO(LOG_TAG, "key: '%s' value: '%s'\n", ptr.first.c_str(),
+ ptr.second.c_str());
}
}
diff --git a/osi/src/osi.cc b/osi/src/osi.cc
index 11c2c4b42..73d6c1aca 100644
--- a/osi/src/osi.cc
+++ b/osi/src/osi.cc
@@ -37,7 +37,7 @@ int osi_rand(void) {
int rand_fd = open(RANDOM_PATH, O_RDONLY);
if (rand_fd == INVALID_FD) {
- LOG_ERROR("%s can't open rand fd %s: %s ", __func__, RANDOM_PATH,
+ LOG_ERROR(LOG_TAG, "%s can't open rand fd %s: %s ", __func__, RANDOM_PATH,
strerror(errno));
CHECK(rand_fd != INVALID_FD);
}
diff --git a/osi/src/properties.cc b/osi/src/properties.cc
index 4202479a1..c20b39f59 100644
--- a/osi/src/properties.cc
+++ b/osi/src/properties.cc
@@ -67,4 +67,4 @@ bool osi_property_get_bool(const char* key, bool default_value) {
#else
return property_get_bool(key, default_value);
#endif // defined(OS_GENERIC)
-}
+} \ No newline at end of file
diff --git a/osi/src/reactor.cc b/osi/src/reactor.cc
index e7ed23f9a..7898170d3 100644
--- a/osi/src/reactor.cc
+++ b/osi/src/reactor.cc
@@ -74,21 +74,23 @@ reactor_t* reactor_new(void) {
ret->epoll_fd = epoll_create1(EPOLL_CLOEXEC);
if (ret->epoll_fd == INVALID_FD) {
- LOG_ERROR("%s unable to create epoll instance: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s unable to create epoll instance: %s", __func__,
strerror(errno));
goto error;
}
ret->event_fd = eventfd(0, 0);
if (ret->event_fd == INVALID_FD) {
- LOG_ERROR("%s unable to create eventfd: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to create eventfd: %s", __func__,
+ strerror(errno));
goto error;
}
ret->list_mutex = new std::mutex;
ret->invalidation_list = list_new(NULL);
if (!ret->invalidation_list) {
- LOG_ERROR("%s unable to allocate object invalidation list.", __func__);
+ LOG_ERROR(LOG_TAG, "%s unable to allocate object invalidation list.",
+ __func__);
goto error;
}
@@ -97,8 +99,8 @@ reactor_t* reactor_new(void) {
event.events = EPOLLIN;
event.data.ptr = NULL;
if (epoll_ctl(ret->epoll_fd, EPOLL_CTL_ADD, ret->event_fd, &event) == -1) {
- LOG_ERROR("%s unable to register eventfd with epoll set: %s", __func__,
- strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to register eventfd with epoll set: %s",
+ __func__, strerror(errno));
goto error;
}
@@ -157,8 +159,8 @@ reactor_object_t* reactor_register(reactor_t* reactor, int fd, void* context,
event.data.ptr = object;
if (epoll_ctl(reactor->epoll_fd, EPOLL_CTL_ADD, fd, &event) == -1) {
- LOG_ERROR("%s unable to register fd %d to epoll set: %s", __func__, fd,
- strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to register fd %d to epoll set: %s", __func__,
+ fd, strerror(errno));
delete object->mutex;
osi_free(object);
return NULL;
@@ -180,8 +182,8 @@ bool reactor_change_registration(reactor_object_t* object,
if (epoll_ctl(object->reactor->epoll_fd, EPOLL_CTL_MOD, object->fd, &event) ==
-1) {
- LOG_ERROR("%s unable to modify interest set for fd %d: %s", __func__,
- object->fd, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to modify interest set for fd %d: %s",
+ __func__, object->fd, strerror(errno));
return false;
}
@@ -198,8 +200,8 @@ void reactor_unregister(reactor_object_t* obj) {
reactor_t* reactor = obj->reactor;
if (epoll_ctl(reactor->epoll_fd, EPOLL_CTL_DEL, obj->fd, NULL) == -1)
- LOG_ERROR("%s unable to unregister fd %d from epoll set: %s", __func__,
- obj->fd, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to unregister fd %d from epoll set: %s",
+ __func__, obj->fd, strerror(errno));
if (reactor->is_running &&
pthread_equal(pthread_self(), reactor->run_thread)) {
@@ -245,7 +247,8 @@ static reactor_status_t run_reactor(reactor_t* reactor, int iterations) {
int ret;
OSI_NO_INTR(ret = epoll_wait(reactor->epoll_fd, events, MAX_EVENTS, -1));
if (ret == -1) {
- LOG_ERROR("%s error in epoll_wait: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s error in epoll_wait: %s", __func__,
+ strerror(errno));
reactor->is_running = false;
return REACTOR_STATUS_ERROR;
}
diff --git a/osi/src/semaphore.cc b/osi/src/semaphore.cc
index 4175f9ce2..a943aa765 100644
--- a/osi/src/semaphore.cc
+++ b/osi/src/semaphore.cc
@@ -44,7 +44,8 @@ semaphore_t* semaphore_new(unsigned int value) {
semaphore_t* ret = static_cast<semaphore_t*>(osi_malloc(sizeof(semaphore_t)));
ret->fd = eventfd(value, EFD_SEMAPHORE);
if (ret->fd == INVALID_FD) {
- LOG_ERROR("%s unable to allocate semaphore: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to allocate semaphore: %s", __func__,
+ strerror(errno));
osi_free(ret);
ret = NULL;
}
@@ -64,7 +65,8 @@ void semaphore_wait(semaphore_t* semaphore) {
eventfd_t value;
if (eventfd_read(semaphore->fd, &value) == -1)
- LOG_ERROR("%s unable to wait on semaphore: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to wait on semaphore: %s", __func__,
+ strerror(errno));
}
bool semaphore_try_wait(semaphore_t* semaphore) {
@@ -73,13 +75,13 @@ bool semaphore_try_wait(semaphore_t* semaphore) {
int flags = fcntl(semaphore->fd, F_GETFL);
if (flags == -1) {
- LOG_ERROR("%s unable to get flags for semaphore fd: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s unable to get flags for semaphore fd: %s", __func__,
strerror(errno));
return false;
}
if (fcntl(semaphore->fd, F_SETFL, flags | O_NONBLOCK) == -1) {
- LOG_ERROR("%s unable to set O_NONBLOCK for semaphore fd: %s", __func__,
- strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to set O_NONBLOCK for semaphore fd: %s",
+ __func__, strerror(errno));
return false;
}
@@ -88,8 +90,8 @@ bool semaphore_try_wait(semaphore_t* semaphore) {
if (eventfd_read(semaphore->fd, &value) == -1) rc = false;
if (fcntl(semaphore->fd, F_SETFL, flags) == -1)
- LOG_ERROR("%s unable to restore flags for semaphore fd: %s", __func__,
- strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to restore flags for semaphore fd: %s",
+ __func__, strerror(errno));
return rc;
}
@@ -98,7 +100,8 @@ void semaphore_post(semaphore_t* semaphore) {
CHECK(semaphore->fd != INVALID_FD);
if (eventfd_write(semaphore->fd, 1ULL) == -1)
- LOG_ERROR("%s unable to post to semaphore: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to post to semaphore: %s", __func__,
+ strerror(errno));
}
int semaphore_get_fd(const semaphore_t* semaphore) {
diff --git a/osi/src/socket.cc b/osi/src/socket.cc
index e26381a99..3f9366f40 100644
--- a/osi/src/socket.cc
+++ b/osi/src/socket.cc
@@ -54,13 +54,15 @@ socket_t* socket_new(void) {
ret->fd = socket(AF_INET, SOCK_STREAM, IPPROTO_TCP);
if (ret->fd == INVALID_FD) {
- LOG_ERROR("%s unable to create socket: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to create socket: %s", __func__,
+ strerror(errno));
goto error;
}
if (setsockopt(ret->fd, SOL_SOCKET, SO_REUSEADDR, &enable, sizeof(enable)) ==
-1) {
- LOG_ERROR("%s unable to set SO_REUSEADDR: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to set SO_REUSEADDR: %s", __func__,
+ strerror(errno));
goto error;
}
@@ -97,13 +99,13 @@ bool socket_listen(const socket_t* socket, port_t port) {
addr.sin_addr.s_addr = htonl(LOCALHOST_);
addr.sin_port = htons(port);
if (bind(socket->fd, (struct sockaddr*)&addr, sizeof(addr)) == -1) {
- LOG_ERROR("%s unable to bind socket to port %u: %s", __func__, port,
- strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to bind socket to port %u: %s", __func__,
+ port, strerror(errno));
return false;
}
if (listen(socket->fd, 10) == -1) {
- LOG_ERROR("%s unable to listen on port %u: %s", __func__, port,
+ LOG_ERROR(LOG_TAG, "%s unable to listen on port %u: %s", __func__, port,
strerror(errno));
return false;
}
@@ -117,7 +119,8 @@ socket_t* socket_accept(const socket_t* socket) {
int fd;
OSI_NO_INTR(fd = accept(socket->fd, NULL, NULL));
if (fd == INVALID_FD) {
- LOG_ERROR("%s unable to accept socket: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to accept socket: %s", __func__,
+ strerror(errno));
return NULL;
}
diff --git a/osi/src/thread.cc b/osi/src/thread.cc
index 514913ead..e164083d3 100644
--- a/osi/src/thread.cc
+++ b/osi/src/thread.cc
@@ -150,7 +150,8 @@ bool thread_set_priority(thread_t* thread, int priority) {
const int rc = setpriority(PRIO_PROCESS, thread->tid, priority);
if (rc < 0) {
- LOG_ERROR("%s unable to set thread priority %d for tid %d, error %d",
+ LOG_ERROR(LOG_TAG,
+ "%s unable to set thread priority %d for tid %d, error %d",
__func__, priority, thread->tid, rc);
return false;
}
@@ -166,7 +167,8 @@ bool thread_set_rt_priority(thread_t* thread, int priority) {
const int rc = sched_setscheduler(thread->tid, SCHED_FIFO, &rt_params);
if (rc != 0) {
- LOG_ERROR("%s unable to set SCHED_FIFO priority %d for tid %d, error %s",
+ LOG_ERROR(LOG_TAG,
+ "%s unable to set SCHED_FIFO priority %d for tid %d, error %s",
__func__, priority, thread->tid, strerror(errno));
return false;
}
@@ -198,15 +200,16 @@ static void* run_thread(void* start_arg) {
CHECK(thread != NULL);
if (prctl(PR_SET_NAME, (unsigned long)thread->name) == -1) {
- LOG_ERROR("%s unable to set thread name: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to set thread name: %s", __func__,
+ strerror(errno));
start->error = errno;
semaphore_post(start->start_sem);
return NULL;
}
thread->tid = gettid();
- LOG_INFO("%s: thread id %d, thread name %s started", __func__, thread->tid,
- thread->name);
+ LOG_INFO(LOG_TAG, "%s: thread id %d, thread name %s started", __func__,
+ thread->tid, thread->name);
semaphore_post(start->start_sem);
@@ -233,10 +236,10 @@ static void* run_thread(void* start_arg) {
}
if (count > fixed_queue_capacity(thread->work_queue))
- LOG_INFO("%s growing event queue on shutdown.", __func__);
+ LOG_DEBUG(LOG_TAG, "%s growing event queue on shutdown.", __func__);
- LOG_WARN("%s: thread id %d, thread name %s exited", __func__, thread->tid,
- thread->name);
+ LOG_WARN(LOG_TAG, "%s: thread id %d, thread name %s exited", __func__,
+ thread->tid, thread->name);
return NULL;
}
diff --git a/osi/src/wakelock.cc b/osi/src/wakelock.cc
index 51fb3fcbe..0f9a51b7d 100644
--- a/osi/src/wakelock.cc
+++ b/osi/src/wakelock.cc
@@ -95,7 +95,8 @@ static void update_wakelock_released_stats(bt_status_t released_status);
void wakelock_set_os_callouts(bt_os_callouts_t* callouts) {
wakelock_os_callouts = callouts;
is_native = (wakelock_os_callouts == NULL);
- LOG_INFO("%s set to %s", __func__, (is_native) ? "native" : "non-native");
+ LOG_INFO(LOG_TAG, "%s set to %s", __func__,
+ (is_native) ? "native" : "non-native");
}
bool wakelock_acquire(void) {
@@ -111,7 +112,7 @@ bool wakelock_acquire(void) {
update_wakelock_acquired_stats(status);
if (status != BT_STATUS_SUCCESS)
- LOG_ERROR("%s unable to acquire wake lock: %d", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s unable to acquire wake lock: %d", __func__, status);
return (status == BT_STATUS_SUCCESS);
}
@@ -123,23 +124,25 @@ static bt_status_t wakelock_acquire_callout(void) {
static bt_status_t wakelock_acquire_native(void) {
if (wake_lock_fd == INVALID_FD) {
- LOG_ERROR("%s lock not acquired, invalid fd", __func__);
+ LOG_ERROR(LOG_TAG, "%s lock not acquired, invalid fd", __func__);
return BT_STATUS_PARM_INVALID;
}
if (wake_unlock_fd == INVALID_FD) {
- LOG_ERROR("%s not acquiring lock: can't release lock", __func__);
+ LOG_ERROR(LOG_TAG, "%s not acquiring lock: can't release lock", __func__);
return BT_STATUS_PARM_INVALID;
}
long lock_name_len = strlen(WAKE_LOCK_ID);
locked_id_len = write(wake_lock_fd, WAKE_LOCK_ID, lock_name_len);
if (locked_id_len == -1) {
- LOG_ERROR("%s wake lock not acquired: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s wake lock not acquired: %s", __func__,
+ strerror(errno));
return BT_STATUS_FAIL;
} else if (locked_id_len < lock_name_len) {
// TODO (jamuraa): this is weird. maybe we should release and retry.
- LOG_WARN("%s wake lock truncated to %zd chars", __func__, locked_id_len);
+ LOG_WARN(LOG_TAG, "%s wake lock truncated to %zd chars", __func__,
+ locked_id_len);
}
return BT_STATUS_SUCCESS;
}
@@ -166,16 +169,17 @@ static bt_status_t wakelock_release_callout(void) {
static bt_status_t wakelock_release_native(void) {
if (wake_unlock_fd == INVALID_FD) {
- LOG_ERROR("%s lock not released, invalid fd", __func__);
+ LOG_ERROR(LOG_TAG, "%s lock not released, invalid fd", __func__);
return BT_STATUS_PARM_INVALID;
}
ssize_t wrote_name_len = write(wake_unlock_fd, WAKE_LOCK_ID, locked_id_len);
if (wrote_name_len == -1) {
- LOG_ERROR("%s can't release wake lock: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s can't release wake lock: %s", __func__,
+ strerror(errno));
} else if (wrote_name_len < locked_id_len) {
- LOG_ERROR("%s lock release only wrote %zd, assuming released", __func__,
- wrote_name_len);
+ LOG_ERROR(LOG_TAG, "%s lock release only wrote %zd, assuming released",
+ __func__, wrote_name_len);
}
return BT_STATUS_SUCCESS;
}
@@ -187,13 +191,13 @@ static void wakelock_initialize(void) {
}
static void wakelock_initialize_native(void) {
- LOG_INFO("%s opening wake locks", __func__);
+ LOG_DEBUG(LOG_TAG, "%s opening wake locks", __func__);
if (wake_lock_path.empty()) wake_lock_path = DEFAULT_WAKE_LOCK_PATH;
wake_lock_fd = open(wake_lock_path.c_str(), O_RDWR | O_CLOEXEC);
if (wake_lock_fd == INVALID_FD) {
- LOG_ERROR("%s can't open wake lock %s: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s can't open wake lock %s: %s", __func__,
wake_lock_path.c_str(), strerror(errno));
CHECK(wake_lock_fd != INVALID_FD);
}
@@ -202,7 +206,7 @@ static void wakelock_initialize_native(void) {
wake_unlock_fd = open(wake_unlock_path.c_str(), O_RDWR | O_CLOEXEC);
if (wake_unlock_fd == INVALID_FD) {
- LOG_ERROR("%s can't open wake unlock %s: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s can't open wake unlock %s: %s", __func__,
wake_unlock_path.c_str(), strerror(errno));
CHECK(wake_unlock_fd != INVALID_FD);
}
@@ -210,7 +214,7 @@ static void wakelock_initialize_native(void) {
void wakelock_cleanup(void) {
if (wakelock_stats.is_acquired) {
- LOG_ERROR("%s releasing wake lock as part of cleanup", __func__);
+ LOG_ERROR(LOG_TAG, "%s releasing wake lock as part of cleanup", __func__);
wakelock_release();
}
wake_lock_path.clear();
@@ -227,7 +231,8 @@ void wakelock_set_paths(const char* lock_path, const char* unlock_path) {
static uint64_t now_ms(void) {
struct timespec ts;
if (clock_gettime(CLOCK_ID, &ts) == -1) {
- LOG_ERROR("%s unable to get current time: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s unable to get current time: %s", __func__,
+ strerror(errno));
return 0;
}
diff --git a/osi/test/alarm_test.cc b/osi/test/alarm_test.cc
index 7c30bf353..fb55dc711 100644
--- a/osi/test/alarm_test.cc
+++ b/osi/test/alarm_test.cc
@@ -16,6 +16,7 @@
*
******************************************************************************/
+#include <base/message_loop/message_loop.h>
#include <base/run_loop.h>
#include <gtest/gtest.h>
@@ -39,9 +40,9 @@ static const uint64_t EPSILON_MS = 50;
static void msleep(uint64_t ms) { usleep(ms * 1000); }
-static MessageLoopThread* thread_;
+static base::MessageLoop* message_loop_;
-bluetooth::common::MessageLoopThread* get_main_thread() { return thread_; }
+base::MessageLoop* get_main_message_loop() { return message_loop_; }
class AlarmTest : public AlarmTestHarness {
protected:
@@ -307,7 +308,7 @@ TEST_F(AlarmTest, test_callback_ordering_on_mloop) {
if (!message_loop_thread.IsRunning()) {
FAIL() << "unable to create btu message loop thread.";
}
- thread_ = &message_loop_thread;
+ message_loop_ = message_loop_thread.message_loop();
for (int i = 0; i < 100; i++) {
const std::string alarm_name =
diff --git a/osi/test/fuzzers/Android.bp b/osi/test/fuzzers/Android.bp
deleted file mode 100644
index 86f7f82dd..000000000
--- a/osi/test/fuzzers/Android.bp
+++ /dev/null
@@ -1,17 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_defaults {
- name: "libosi_fuzz_defaults",
- defaults: ["fluoride_osi_defaults"],
- host_supported: true,
- static_libs: [
- "libosi",
- ],
-}
diff --git a/osi/test/fuzzers/alarm/Android.bp b/osi/test/fuzzers/alarm/Android.bp
deleted file mode 100644
index 341282459..000000000
--- a/osi/test/fuzzers/alarm/Android.bp
+++ /dev/null
@@ -1,30 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "libosi_fuzz_alarm",
- defaults: ["libosi_fuzz_defaults"],
- host_supported: false,
- srcs: [
- "fuzz_alarm.cc",
- ],
- shared_libs: [
- "liblog",
- "libprotobuf-cpp-lite",
- "libcutils",
- "libcrypto",
- ],
- static_libs: [
- "libbt-common",
- "libbt-protos-lite",
- "libgmock",
- "libosi",
- ],
- cflags: [ "-Wno-unused-function" ],
-}
diff --git a/osi/test/fuzzers/alarm/fuzz_alarm.cc b/osi/test/fuzzers/alarm/fuzz_alarm.cc
deleted file mode 100644
index c432f8c5c..000000000
--- a/osi/test/fuzzers/alarm/fuzz_alarm.cc
+++ /dev/null
@@ -1,151 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fcntl.h>
-#include <fuzzer/FuzzedDataProvider.h>
-#include "osi/include/alarm.h"
-#include "osi/include/semaphore.h"
-
-#include "common/message_loop_thread.h"
-
-using base::Closure;
-using base::TimeDelta;
-using bluetooth::common::MessageLoopThread;
-
-#define MAX_CONCURRENT_ALARMS 25
-#define MAX_BUFFER_LEN 4096
-#define MAX_ALARM_DURATION 25
-
-static semaphore_t* semaphore;
-static int cb_counter;
-static MessageLoopThread* thread = new MessageLoopThread("fake main thread");
-
-bluetooth::common::MessageLoopThread* get_main_thread() { return thread; }
-
-static void cb(void* data) {
- ++cb_counter;
- semaphore_post(semaphore);
-}
-
-void setup() {
- cb_counter = 0;
- semaphore = semaphore_new(0);
-}
-void teardown() { semaphore_free(semaphore); }
-
-alarm_t* fuzz_init_alarm(FuzzedDataProvider* dataProvider) {
- size_t name_len =
- dataProvider->ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_LEN);
- std::vector<char> alarm_name_vect =
- dataProvider->ConsumeBytesWithTerminator<char>(name_len, '\0');
- char* alarm_name = alarm_name_vect.data();
-
- // Determine if our alarm will be periodic
- if (dataProvider->ConsumeBool()) {
- return alarm_new_periodic(alarm_name);
- } else {
- return alarm_new(alarm_name);
- }
-}
-
-bool fuzz_set_alarm(alarm_t* alarm, uint64_t interval, alarm_callback_t cb,
- FuzzedDataProvider* dataProvider) {
- // Generate a random buffer (or null)
- void* data_buffer = nullptr;
- size_t buff_len =
- dataProvider->ConsumeIntegralInRange<size_t>(1, MAX_BUFFER_LEN);
- if (buff_len == 0) {
- return false;
- }
-
- // allocate our space
- std::vector<uint8_t> data_vector =
- dataProvider->ConsumeBytes<uint8_t>(buff_len);
- data_buffer = data_vector.data();
-
- // Make sure alarm is non-null
- if (alarm) {
- // Should this alarm be regular or on mloop?
- if (dataProvider->ConsumeBool()) {
- alarm_set_on_mloop(alarm, interval, cb, data_buffer);
- } else {
- alarm_set(alarm, interval, cb, data_buffer);
- }
- }
-
- return true;
-}
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Perform setup
- setup();
-
- alarm_t* alarm = nullptr;
- // Should our alarm be valid or null?
- if (dataProvider.ConsumeBool()) {
- // Init our alarm
- alarm = fuzz_init_alarm(&dataProvider);
- }
-
- // Set up the alarm & cancel
- // Alarm must be non-null, or set() will trigger assert
- if (alarm) {
- if (!fuzz_set_alarm(alarm, MAX_ALARM_DURATION, cb, &dataProvider)) {
- return 0;
- }
- alarm_cancel(alarm);
- }
-
- // Check if scheduled
- alarm_is_scheduled(alarm);
-
- if (alarm) {
- // Set up another set of alarms & let these ones run
- int num_alarms =
- dataProvider.ConsumeIntegralInRange<uint8_t>(0, MAX_CONCURRENT_ALARMS);
- for (int i = 0; i < num_alarms; i++) {
- uint64_t interval =
- dataProvider.ConsumeIntegralInRange<uint64_t>(0, MAX_ALARM_DURATION);
- if (fuzz_set_alarm(alarm, interval, cb, &dataProvider)) {
- return 0;
- }
- alarm_get_remaining_ms(alarm);
- }
-
- // Wait for them to complete
- for (int i = 1; i <= num_alarms; i++) {
- semaphore_wait(semaphore);
- }
- }
-
- // Free the alarm object
- alarm_free(alarm);
-
- // dump debug data to /dev/null
- int debug_fd = open("/dev/null", O_RDWR);
- alarm_debug_dump(debug_fd);
-
- // Cleanup
- alarm_cleanup();
-
- // Perform teardown
- teardown();
-
- return 0;
-}
diff --git a/osi/test/fuzzers/allocation_tracker/Android.bp b/osi/test/fuzzers/allocation_tracker/Android.bp
deleted file mode 100644
index c07af5520..000000000
--- a/osi/test/fuzzers/allocation_tracker/Android.bp
+++ /dev/null
@@ -1,26 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "libosi_fuzz_allocation_tracker",
- defaults: ["libosi_fuzz_defaults"],
- host_supported: true,
- srcs: [
- "fuzz_allocation_tracker.cc",
- ],
- shared_libs: [
- "liblog",
- ],
- static_libs: [
- "libosi",
- ],
- corpus: [
- "corpus/checkfail-regression-156805580",
- ],
-}
diff --git a/osi/test/fuzzers/allocation_tracker/corpus/checkfail-regression-156805580 b/osi/test/fuzzers/allocation_tracker/corpus/checkfail-regression-156805580
deleted file mode 100644
index 044c5b0f5..000000000
--- a/osi/test/fuzzers/allocation_tracker/corpus/checkfail-regression-156805580
+++ /dev/null
@@ -1 +0,0 @@
-þÿÿÿÿ¸
diff --git a/osi/test/fuzzers/allocation_tracker/fuzz_allocation_tracker.cc b/osi/test/fuzzers/allocation_tracker/fuzz_allocation_tracker.cc
deleted file mode 100644
index 966e87cc5..000000000
--- a/osi/test/fuzzers/allocation_tracker/fuzz_allocation_tracker.cc
+++ /dev/null
@@ -1,142 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "osi/include/allocation_tracker.h"
-
-#define MAX_NUM_FUNCTIONS 512
-#define MAX_BUF_SIZE 256
-
-// Add a tracker_initialized bool to track if we initialized or not
-// (This is to handle a call to allocation_tracker_notify_alloc immediately
-// returning the provided pointer if the allocator is not ready, and
-// notify_free on the same ptr failing as the allocator did not
-// track that allocation)
-bool tracker_initialized = false;
-
-struct alloc_struct {
- allocator_id_t alloc_id;
- void* ptr;
-};
-
-void freeAllocationVector(std::vector<alloc_struct>* alloc_vector) {
- // Free our allocated buffers
- for (const auto& alloc : *alloc_vector) {
- void* real_ptr = allocation_tracker_notify_free(alloc.alloc_id, alloc.ptr);
- if (real_ptr) {
- free(real_ptr);
- }
- }
- alloc_vector->clear();
-}
-
-void callArbitraryFunction(std::vector<alloc_struct>* alloc_vector,
- FuzzedDataProvider* dataProvider) {
- // Get our function identifier
- switch (dataProvider->ConsumeIntegralInRange<char>(0, 6)) {
- // Let 0 be a NO-OP, as ConsumeIntegral will return 0 on an empty buffer
- // (This will likely bias whatever action is here to run more often)
- case 0:
- return;
- // Init
- case 1:
- allocation_tracker_init();
- tracker_initialized = true;
- return;
- case 2:
- // NOTE: This will print to stderr if allocations exist. May clutter logs
- allocation_tracker_expect_no_allocations();
- return;
- case 3: {
- alloc_struct alloc;
- // Determine allocator ID & buffer size (without canaries)
- alloc.alloc_id = dataProvider->ConsumeIntegral<allocator_id_t>();
- size_t size =
- dataProvider->ConsumeIntegralInRange<size_t>(1, MAX_BUF_SIZE);
- if (size == 0) {
- return;
- }
- // Get our size with canaries & allocate
- size_t real_size = allocation_tracker_resize_for_canary(size);
- void* tmp_ptr = malloc(real_size);
- if (tmp_ptr == nullptr) {
- return;
- }
- alloc.ptr =
- allocation_tracker_notify_alloc(alloc.alloc_id, tmp_ptr, size);
- // Put our id/ptr pair in our tracking vector to be freed later
- if (tracker_initialized && alloc.ptr) {
- alloc_vector->push_back(alloc);
- } else {
- free(tmp_ptr);
- }
- }
- return;
- case 4: {
- // Grab a ptr from our tracking vector & free it
- if (!alloc_vector->empty()) {
- size_t index = dataProvider->ConsumeIntegralInRange<size_t>(
- 0, alloc_vector->size() - 1);
- alloc_struct alloc = alloc_vector->at(index);
- void* real_ptr =
- allocation_tracker_notify_free(alloc.alloc_id, alloc.ptr);
- if (real_ptr) {
- free(real_ptr);
- }
- alloc_vector->erase(alloc_vector->begin() + index);
- }
- }
- return;
- case 5: {
- size_t size =
- dataProvider->ConsumeIntegralInRange<size_t>(0, MAX_BUF_SIZE);
- allocation_tracker_resize_for_canary(size);
- }
- return;
- // Reset
- // NOTE: Should this be exempted from fuzzing? Header says to not call this,
- // but it's still exposed. It also doesn't perform a full reset.
- case 6:
- // Have to actually free the mem first as reset doesn't do it
- freeAllocationVector(alloc_vector);
- allocation_tracker_reset();
- return;
- default:
- return;
- }
-}
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Keep a vector of our allocated pointers
- std::vector<alloc_struct> alloc_vector;
-
- // How many functions are we going to call?
- size_t num_functions =
- dataProvider.ConsumeIntegralInRange<size_t>(0, MAX_NUM_FUNCTIONS);
- for (size_t i = 0; i < num_functions; i++) {
- callArbitraryFunction(&alloc_vector, &dataProvider);
- }
-
- // Free anything we've allocated over the course of the fuzzer loop
- freeAllocationVector(&alloc_vector);
-
- // Reset our tracker for the next run
- allocation_tracker_reset();
- return 0;
-}
diff --git a/osi/test/fuzzers/allocator/Android.bp b/osi/test/fuzzers/allocator/Android.bp
deleted file mode 100644
index 708d6152c..000000000
--- a/osi/test/fuzzers/allocator/Android.bp
+++ /dev/null
@@ -1,21 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "libosi_fuzz_allocator",
- defaults: ["libosi_fuzz_defaults"],
- host_supported: true,
- srcs: [
- "fuzz_allocator.cc",
- ],
- static_libs: [
- "libosi",
- "liblog",
- ],
-}
diff --git a/osi/test/fuzzers/allocator/fuzz_allocator.cc b/osi/test/fuzzers/allocator/fuzz_allocator.cc
deleted file mode 100644
index bdfd99a1d..000000000
--- a/osi/test/fuzzers/allocator/fuzz_allocator.cc
+++ /dev/null
@@ -1,119 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "osi/include/allocator.h"
-#include "osi/test/fuzzers/include/libosiFuzzHelperFunctions.h"
-
-#define MAX_NUM_FUNCTIONS 512
-#define MAX_BUF_SIZE 256
-
-void callArbitraryFunction(std::vector<void*>* alloc_vector,
- FuzzedDataProvider* dataProvider) {
- // Get our function identifier
- char func_id = dataProvider->ConsumeIntegralInRange<char>(0, 6);
-
- switch (func_id) {
- // Let 0 be a NO-OP, as ConsumeIntegral will return 0 on an empty buffer
- // (This will likely bias whatever action is here to run more often)
- case 0:
- return;
- // Let case 1 be osi_malloc, and 2 be osi_calloc
- case 1:
- case 2: {
- size_t size =
- dataProvider->ConsumeIntegralInRange<size_t>(0, MAX_BUF_SIZE);
- void* ptr = nullptr;
- if (size == 0) {
- return;
- }
- if (func_id == 1) {
- ptr = osi_malloc(size);
- } else {
- ptr = osi_calloc(size);
- }
- if (ptr) {
- alloc_vector->push_back(ptr);
- }
- }
- return;
- // Let case 3 be osi_free, and 4 be osi_free_and_reset
- case 3:
- case 4: {
- if (alloc_vector->size() == 0) {
- return;
- }
- size_t index = dataProvider->ConsumeIntegralInRange<size_t>(
- 0, alloc_vector->size() - 1);
- void* ptr = alloc_vector->at(index);
- if (ptr) {
- if (func_id == 3) {
- osi_free(ptr);
- } else {
- osi_free_and_reset(&ptr);
- }
- }
- alloc_vector->erase(alloc_vector->begin() + index);
- }
- return;
- // Let case 5 be osi_strdup, and 6 be osi_strdup
- case 5:
- case 6: {
- // Make a src buffer
- char* buf = generateBuffer(dataProvider, MAX_BUF_SIZE, true);
- char* str = nullptr;
- if (buf == nullptr) {
- return;
- }
- if (func_id == 5) {
- str = osi_strdup(buf);
- } else {
- size_t size =
- dataProvider->ConsumeIntegralInRange<size_t>(1, MAX_BUF_SIZE);
- str = osi_strndup(buf, size);
- }
- free(buf);
- if (str) {
- alloc_vector->push_back(str);
- }
- }
- return;
- default:
- return;
- }
-}
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Keep a vector of our allocated objects for freeing later
- std::vector<void*> alloc_vector;
- // Call some functions, create some buffers
- size_t num_functions =
- dataProvider.ConsumeIntegralInRange<size_t>(0, MAX_NUM_FUNCTIONS);
- for (size_t i = 0; i < num_functions; i++) {
- callArbitraryFunction(&alloc_vector, &dataProvider);
- }
- // Free anything we've allocated
- for (const auto& alloc : alloc_vector) {
- if (alloc != nullptr) {
- osi_free(alloc);
- }
- }
- alloc_vector.clear();
- return 0;
-}
diff --git a/osi/test/fuzzers/array/Android.bp b/osi/test/fuzzers/array/Android.bp
deleted file mode 100644
index 733a3afd4..000000000
--- a/osi/test/fuzzers/array/Android.bp
+++ /dev/null
@@ -1,23 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "libosi_fuzz_array",
- defaults: ["libosi_fuzz_defaults"],
- host_supported: true,
- srcs: [
- "fuzz_array.cc",
- ],
- shared_libs: [
- "liblog",
- ],
- static_libs: [
- "libosi",
- ],
-}
diff --git a/osi/test/fuzzers/array/fuzz_array.cc b/osi/test/fuzzers/array/fuzz_array.cc
deleted file mode 100644
index eeabf952d..000000000
--- a/osi/test/fuzzers/array/fuzz_array.cc
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "osi/include/array.h"
-
-// Capping the element size at sizeof(uint32_t)+1
-// because it looks like there's a buffer overread
-#define MAX_ELEMENT_SIZE sizeof(uint32_t)
-#define MAX_ARRAY_LEN 1024
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Attempt to init an array
- size_t element_size =
- dataProvider.ConsumeIntegralInRange<size_t>(1, MAX_ELEMENT_SIZE);
- array_t* arr = array_new(element_size);
-
- // Functions can only be called on a non-null array_t, according to the .h
- if (arr != nullptr) {
- // How large do we want our array?
- size_t arr_len =
- dataProvider.ConsumeIntegralInRange<size_t>(0, MAX_ARRAY_LEN);
- if (arr_len > 0) {
- for (size_t i = 0; i < arr_len; i++) {
- uint32_t new_val = dataProvider.ConsumeIntegral<uint32_t>();
- // append_value() just derefs and calls append_ptr(),
- // so no need to fuzz separately
- array_append_value(arr, new_val);
- }
-
- // Pull the ptr to an element in the array
- size_t get_index =
- dataProvider.ConsumeIntegralInRange<size_t>(0, array_length(arr) - 1);
- array_at(arr, get_index);
-
- // Grab the array pointer
- array_ptr(arr);
- }
- }
-
- // Free the array (this can be performed on a nullptr)
- array_free(arr);
-
- return 0;
-}
diff --git a/osi/test/fuzzers/buffer/Android.bp b/osi/test/fuzzers/buffer/Android.bp
deleted file mode 100644
index 940b07a4e..000000000
--- a/osi/test/fuzzers/buffer/Android.bp
+++ /dev/null
@@ -1,23 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "libosi_fuzz_buffer",
- defaults: ["libosi_fuzz_defaults"],
- host_supported: true,
- srcs: [
- "fuzz_buffer.cc",
- ],
- shared_libs: [
- "liblog",
- ],
- static_libs: [
- "libosi",
- ],
-}
diff --git a/osi/test/fuzzers/buffer/fuzz_buffer.cc b/osi/test/fuzzers/buffer/fuzz_buffer.cc
deleted file mode 100644
index b781a3171..000000000
--- a/osi/test/fuzzers/buffer/fuzz_buffer.cc
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "osi/include/buffer.h"
-
-#define MAX_BUFFER_SIZE 4096
-#define MAX_NUM_SLICES 100
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Create our buffer
- size_t buf_size =
- dataProvider.ConsumeIntegralInRange<size_t>(1, MAX_BUFFER_SIZE);
- buffer_t* buf = buffer_new(buf_size);
-
- // These functions require a non-null buffer, according to the header
- // The size also needs to be over 1 to make slices
- if (buf != nullptr && buf_size > 1) {
- std::vector<buffer_t*> slices;
-
- // Make a bunch of refs to various slices of the buffer
- size_t num_slices =
- dataProvider.ConsumeIntegralInRange<size_t>(0, MAX_NUM_SLICES);
- for (size_t i = 0; i < num_slices; i++) {
- // If slice_size is zero or GT buf_size, lib throws an exception
- size_t slice_size =
- dataProvider.ConsumeIntegralInRange<size_t>(1, buf_size - 1);
- if (slice_size > 0) {
- buffer_t* new_slice = nullptr;
- if (slice_size == buf_size) {
- new_slice = buffer_new_ref(buf);
- } else {
- new_slice = buffer_new_slice(buf, slice_size);
- }
-
- // Add the slice to our vector so we can free it later
- slices.push_back(new_slice);
- }
- }
-
- // Retrieve the buffer ptr
- buffer_ptr(buf);
-
- // Free the slices
- for (const auto& slice : slices) {
- buffer_free(slice);
- }
- }
-
- // Free the root buffer
- buffer_free(buf);
-
- return 0;
-}
diff --git a/osi/test/fuzzers/compat/Android.bp b/osi/test/fuzzers/compat/Android.bp
deleted file mode 100644
index 97e8b2bf4..000000000
--- a/osi/test/fuzzers/compat/Android.bp
+++ /dev/null
@@ -1,24 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "libosi_fuzz_compat",
- defaults: ["libosi_fuzz_defaults"],
- host_supported: true,
- srcs: [
- "fuzz_compat.cc",
- ],
- shared_libs: [
- "liblog",
- "libcutils",
- ],
- static_libs: [
- "libosi",
- ],
-}
diff --git a/osi/test/fuzzers/compat/fuzz_compat.cc b/osi/test/fuzzers/compat/fuzz_compat.cc
deleted file mode 100644
index 3feeaeb1c..000000000
--- a/osi/test/fuzzers/compat/fuzz_compat.cc
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#include <fuzzer/FuzzedDataProvider.h>
-#include "osi/include/compat.h"
-
-#define MAX_BUFFER_SIZE 4096
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
-// Our functions are only defined with __GLIBC__
-#if __GLIBC__
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- size_t buf_size =
- dataProvider.ConsumeIntegralInRange<size_t>(0, MAX_BUFFER_SIZE);
- if (buf_size == 0) {
- return 0;
- }
-
- // Set up our buffers
- // NOTE: If the src buffer is not NULL-terminated, the strlcpy will
- // overread regardless of the len arg. Force null-term for now.
- std::vector<char> bytes =
- dataProvider.ConsumeBytesWithTerminator<char>(buf_size, '\0');
- if (bytes.empty()) {
- return 0;
- }
- buf_size = bytes.size();
- void* dst_buf = malloc(buf_size);
- if (dst_buf == nullptr) {
- return 0;
- }
-
- // Call the getId fn just to ensure things don't crash
- gettid();
-
- // Copy, then concat
- size_t len_to_cpy = dataProvider.ConsumeIntegralInRange<size_t>(0, buf_size);
- strlcpy(reinterpret_cast<char*>(dst_buf),
- reinterpret_cast<char*>(bytes.data()), len_to_cpy);
- strlcat(reinterpret_cast<char*>(dst_buf),
- reinterpret_cast<char*>(bytes.data()), len_to_cpy);
-
- // Clear out our dest buffer
- free(dst_buf);
-#endif
-
- return 0;
-}
diff --git a/osi/test/fuzzers/fixed_queue/Android.bp b/osi/test/fuzzers/fixed_queue/Android.bp
deleted file mode 100644
index 5231552c3..000000000
--- a/osi/test/fuzzers/fixed_queue/Android.bp
+++ /dev/null
@@ -1,24 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "libosi_fuzz_fixed_queue",
- defaults: ["libosi_fuzz_defaults"],
- host_supported: true,
- srcs: [
- "fuzz_fixed_queue.cc",
- ],
- shared_libs: [
- "liblog",
- "libcutils",
- ],
- static_libs: [
- "libosi",
- ],
-}
diff --git a/osi/test/fuzzers/fixed_queue/fuzz_fixed_queue.cc b/osi/test/fuzzers/fixed_queue/fuzz_fixed_queue.cc
deleted file mode 100644
index f8a426a6a..000000000
--- a/osi/test/fuzzers/fixed_queue/fuzz_fixed_queue.cc
+++ /dev/null
@@ -1,240 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <sys/select.h>
-#include "osi/include/fixed_queue.h"
-#include "osi/include/future.h"
-#include "osi/include/thread.h"
-#include "osi/test/fuzzers/include/libosiFuzzHelperFunctions.h"
-
-#define MAX_START_SIZE 2048
-#define MAX_NUM_FUNCTIONS 512
-#define MAX_BUF_SIZE 512
-
-static future_t* received_message_future = nullptr;
-
-// Empty callback function
-void fqFreeCb(void* data) {}
-void fqCb(fixed_queue_t* queue, void* data) {
- void* msg = fixed_queue_try_dequeue(queue);
- future_ready(received_message_future, msg);
-}
-
-// Returns either a nullptr or a function ptr to the placeholder cb function
-fixed_queue_free_cb cbOrNull(FuzzedDataProvider* dataProvider) {
- bool null_cb = dataProvider->ConsumeBool();
- if (null_cb) {
- return nullptr;
- } else {
- return fqFreeCb;
- }
-}
-
-bool fdIsAvailable(int fd) {
- int nfds = 1;
- fd_set readfds, writefds, exceptfds;
- timeval timeout;
-
- FD_ZERO(&readfds);
- FD_ZERO(&writefds);
- FD_ZERO(&exceptfds);
- FD_SET(fd, &readfds);
- timeout.tv_sec = 0;
- timeout.tv_usec = 50;
-
- return select(nfds, &readfds, &writefds, &exceptfds, &timeout) > 0;
-}
-
-void createNewFuture() {
- // Free the existing future if it exists
- if (received_message_future != nullptr) {
- future_ready(received_message_future, nullptr);
- future_await(received_message_future);
- }
-
- // Create a new one
- received_message_future = future_new();
-}
-
-void callArbitraryFunction(fixed_queue_t* fixed_queue,
- std::vector<void*>* live_buffer_vector,
- std::vector<thread_t*>* live_thread_vector,
- FuzzedDataProvider* dataProvider) {
- void* buf_ptr = nullptr;
- size_t index = 0;
- int fd = 0;
- // Get our function identifier
- switch (dataProvider->ConsumeIntegralInRange<char>(0, 17)) {
- // Let 0 be a NO-OP, as ConsumeIntegral will return 0 on an empty buffer
- // (This will likely bias whatever action is here to run more often)
- case 0:
- return;
- // Clear the queue
- case 1:
- fixed_queue_flush(fixed_queue, cbOrNull(dataProvider));
- return;
- // Check if empty
- case 2:
- fixed_queue_is_empty(fixed_queue);
- return;
- // Check length
- case 3:
- fixed_queue_length(fixed_queue);
- return;
- // Check capacity (Cannot be null)
- case 4:
- if (fixed_queue) {
- fixed_queue_capacity(fixed_queue);
- }
- return;
- // Add to the queue (Cannot be null)
- case 5:
- if (fixed_queue) {
- buf_ptr = generateBuffer(dataProvider, MAX_BUF_SIZE, false);
- live_buffer_vector->push_back(buf_ptr);
- if (buf_ptr) {
- // Make sure we won't block
- fd = fixed_queue_get_enqueue_fd(fixed_queue);
- if (fdIsAvailable(fd)) {
- fixed_queue_enqueue(fixed_queue, buf_ptr);
- }
- }
- }
- return;
- case 6:
- if (fixed_queue) {
- buf_ptr = generateBuffer(dataProvider, MAX_BUF_SIZE, false);
- live_buffer_vector->push_back(buf_ptr);
- if (buf_ptr) {
- fixed_queue_try_enqueue(fixed_queue, buf_ptr);
- }
- }
- return;
- // Remove from the queue (Cannot be null)
- case 7:
- if (fixed_queue && fixed_queue_length(fixed_queue) > 0) {
- fixed_queue_dequeue(fixed_queue);
- }
- return;
- case 8:
- if (fixed_queue) {
- fixed_queue_try_dequeue(fixed_queue);
- }
- return;
- // Peeks
- case 9:
- fixed_queue_try_peek_first(fixed_queue);
- return;
- case 10:
- fixed_queue_try_peek_last(fixed_queue);
- return;
- // Try to remove existing specific element
- case 11:
- if (live_buffer_vector->empty()) {
- return;
- }
- // Grab an existing buffer
- index = dataProvider->ConsumeIntegralInRange<size_t>(
- 0, live_buffer_vector->size() - 1);
- buf_ptr = live_buffer_vector->at(index);
- if (buf_ptr != nullptr) {
- fixed_queue_try_remove_from_queue(fixed_queue, buf_ptr);
- }
- return;
- // Try to remove nonexistant element
- case 12:
- buf_ptr =
- reinterpret_cast<void*>(dataProvider->ConsumeIntegral<uint64_t>());
- if (buf_ptr != nullptr) {
- fixed_queue_try_remove_from_queue(fixed_queue, buf_ptr);
- }
- return;
- // Convert the queue to a list (Cannot be null)
- case 13:
- if (fixed_queue) {
- fixed_queue_get_list(fixed_queue);
- }
- return;
- // Check if enqueue is blocking
- case 14:
- fixed_queue_get_enqueue_fd(fixed_queue);
- return;
- // Check if dequeue is blocking
- case 15:
- fixed_queue_get_dequeue_fd(fixed_queue);
- return;
- // NOTE: thread appears to have a memleak, disabling this for now.
- case 16:
- // if (fixed_queue) {
- // createNewFuture();
- // // Start up a thread and register with it.
- // thread_t* tmp_thread = thread_new(
- // dataProvider->ConsumeRandomLengthString().c_str());
- // if (tmp_thread == nullptr) {
- // return;
- // }
- // live_thread_vector->push_back(tmp_thread);
- // reactor_t* reactor = thread_get_reactor(tmp_thread);
- // if (reactor == nullptr) {
- // return;
- // }
- // fixed_queue_register_dequeue(fixed_queue, reactor, fqCb, nullptr);
- // fixed_queue_enqueue(fixed_queue, (void*)"test");
- // future_await(received_message_future);
- // }
- return;
- case 17:
- fixed_queue_unregister_dequeue(fixed_queue);
- return;
- default:
- return;
- }
-}
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Make vectors to keep track of objects we generate, for freeing
- std::vector<void*> live_buffer_vector;
- std::vector<thread_t*> live_thread_vector;
-
- size_t start_capacity =
- dataProvider.ConsumeIntegralInRange<size_t>(0, MAX_START_SIZE);
- fixed_queue_t* fixed_queue = fixed_queue_new(start_capacity);
-
- // How many functions are we going to call?
- size_t num_functions =
- dataProvider.ConsumeIntegralInRange<size_t>(0, MAX_NUM_FUNCTIONS);
- for (size_t i = 0; i < num_functions; i++) {
- callArbitraryFunction(fixed_queue, &live_buffer_vector, &live_thread_vector,
- &dataProvider);
- }
-
- // Free our queue (with either a null or placeholder callback)
- fixed_queue_free(fixed_queue, cbOrNull(&dataProvider));
-
- // Free buffers we've created through fn calls during this fuzzer loop.
- for (const auto& buffer : live_buffer_vector) {
- free(buffer);
- }
- for (const auto& thread : live_thread_vector) {
- thread_free(thread);
- }
-
- return 0;
-}
diff --git a/osi/test/fuzzers/future/Android.bp b/osi/test/fuzzers/future/Android.bp
deleted file mode 100644
index c3ac34e42..000000000
--- a/osi/test/fuzzers/future/Android.bp
+++ /dev/null
@@ -1,24 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "libosi_fuzz_future",
- defaults: ["libosi_fuzz_defaults"],
- host_supported: true,
- srcs: [
- "fuzz_future.cc",
- ],
- shared_libs: [
- "liblog",
- "libcutils",
- ],
- static_libs: [
- "libosi",
- ],
-}
diff --git a/osi/test/fuzzers/future/fuzz_future.cc b/osi/test/fuzzers/future/fuzz_future.cc
deleted file mode 100644
index 1df3e7da0..000000000
--- a/osi/test/fuzzers/future/fuzz_future.cc
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "osi/include/future.h"
-
-#define MAX_BUFFER_SIZE 8
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // The value of this result ptr shouldn't matter, but make a buffer to be safe
- size_t buf_size =
- dataProvider.ConsumeIntegralInRange<size_t>(1, MAX_BUFFER_SIZE);
- void* buf = malloc(buf_size);
- if (buf == nullptr) {
- return 0;
- }
- std::vector<uint8_t> bytes = dataProvider.ConsumeBytes<uint8_t>(buf_size);
- memcpy(buf, bytes.data(), bytes.size());
-
- // Is our future an immediate?
- future_t* future = nullptr;
- bool is_immediate = dataProvider.ConsumeBool();
- if (is_immediate) {
- future = future_new_immediate(buf);
- } else {
- future = future_new();
- }
-
- // These functions require a non-null object, according to the header
- if (future != nullptr) {
- // If we need to, specify that the future is ready
- if (!is_immediate) {
- future_ready(future, buf);
- }
-
- // Free the object
- future_await(future);
- }
-
- free(buf);
- return 0;
-}
diff --git a/osi/test/fuzzers/include/libosiFuzzHelperFunctions.h b/osi/test/fuzzers/include/libosiFuzzHelperFunctions.h
deleted file mode 100644
index 395b85ec7..000000000
--- a/osi/test/fuzzers/include/libosiFuzzHelperFunctions.h
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef LIBOSI_FUZZ_HELPERS_H_
-#define LIBOSI_FUZZ_HELPERS_H_
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <vector>
-
-char* generateBuffer(FuzzedDataProvider* dataProvider, size_t max_buffer_size,
- bool null_terminate) {
- // Get our buffer size
- size_t buf_size =
- dataProvider->ConsumeIntegralInRange<size_t>(0, max_buffer_size);
- if (buf_size == 0) {
- return nullptr;
- }
-
- // Allocate and copy in data
- char* buf = reinterpret_cast<char*>(malloc(buf_size));
- std::vector<char> bytes = dataProvider->ConsumeBytes<char>(buf_size);
- memcpy(buf, bytes.data(), bytes.size());
-
- if (null_terminate) {
- // Force a null-termination
- buf[buf_size - 1] = 0x00;
- }
-
- return buf;
-}
-
-#endif // LIBOSI_FUZZ_HELPERS_H_
diff --git a/osi/test/fuzzers/list/Android.bp b/osi/test/fuzzers/list/Android.bp
deleted file mode 100644
index a4475358c..000000000
--- a/osi/test/fuzzers/list/Android.bp
+++ /dev/null
@@ -1,21 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "libosi_fuzz_list",
- defaults: ["libosi_fuzz_defaults"],
- host_supported: true,
- srcs: [
- "fuzz_list.cc",
- ],
- static_libs: [
- "libosi",
- "liblog",
- ],
-}
diff --git a/osi/test/fuzzers/list/fuzz_list.cc b/osi/test/fuzzers/list/fuzz_list.cc
deleted file mode 100644
index a5814740a..000000000
--- a/osi/test/fuzzers/list/fuzz_list.cc
+++ /dev/null
@@ -1,277 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "osi/include/list.h"
-#include "osi/test/fuzzers/include/libosiFuzzHelperFunctions.h"
-
-#define MAX_NUM_FUNCTIONS 512
-#define MAX_BUF_SIZE 256
-
-struct list_node_t {
- struct list_node_t* next;
- void* data;
-};
-
-void cb(void* data) {}
-// Pass a ptr to FuzzedDataProvider in context
-bool list_iter_cb_impl(void* data, void* context) {
- FuzzedDataProvider* dataProvider =
- reinterpret_cast<FuzzedDataProvider*>(context);
- return dataProvider->ConsumeBool();
-}
-
-list_t* createList(FuzzedDataProvider* dataProvider) {
- bool should_callback = dataProvider->ConsumeBool();
- if (should_callback) {
- return list_new(cb);
- } else {
- return list_new(nullptr);
- }
-}
-
-void* getArbitraryElement(std::vector<void*>* vector,
- FuzzedDataProvider* dataProvider) {
- if (vector->size() == 0) {
- return nullptr;
- }
- // Get an index
- size_t index =
- dataProvider->ConsumeIntegralInRange<size_t>(0, vector->size() - 1);
- return vector->at(index);
-}
-
-list_node_t* getArbitraryNode(list_t* list, FuzzedDataProvider* dataProvider) {
- if (list == nullptr || list_is_empty(list)) {
- return nullptr;
- }
- size_t index =
- dataProvider->ConsumeIntegralInRange<size_t>(0, list_length(list) - 1);
- list_node_t* node = list_begin(list);
- for (size_t i = 0; i < index; i++) {
- node = node->next;
- }
-
- return node;
-}
-
-void callArbitraryFunction(std::vector<void*>* list_vector,
- std::vector<void*>* alloc_vector,
- FuzzedDataProvider* dataProvider) {
- list_t* list = nullptr;
- // Get our function identifier
- switch (dataProvider->ConsumeIntegralInRange<char>(0, 18)) {
- // Let 0 be a NO-OP, as ConsumeIntegral will return 0 on an empty buffer
- // (This will likely bias whatever action is here to run more often)
- case 0:
- return;
- // Create a new list
- case 1:
- list = createList(dataProvider);
- list_vector->push_back(list);
- return;
- // Free a list
- case 2: {
- size_t index = 0;
- if (list_vector->size() > 0) {
- // Get an index
- index = dataProvider->ConsumeIntegralInRange<size_t>(
- 0, list_vector->size() - 1);
- list = reinterpret_cast<list_t*>(list_vector->at(index));
- }
- list_free(list);
- // Otherwise free a valid list
- if (list != nullptr) {
- list_vector->erase(list_vector->begin() + index);
- }
- return;
- }
- case 3:
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list != nullptr) {
- list_is_empty(list);
- }
- return;
- case 4:
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list != nullptr) {
- void* search_buf = getArbitraryElement(alloc_vector, dataProvider);
- if (search_buf != nullptr) {
- list_contains(list, search_buf);
- }
- }
- return;
- case 5:
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list != nullptr) {
- list_length(list);
- }
- return;
- case 6:
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list != nullptr && !list_is_empty(list)) {
- list_front(list);
- }
- return;
- case 7:
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list != nullptr && !list_is_empty(list)) {
- list_back(list);
- }
- return;
- case 8:
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list != nullptr && !list_is_empty(list)) {
- list_back_node(list);
- }
- return;
- case 9: {
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list == nullptr) {
- return;
- }
- void* buf = generateBuffer(dataProvider, MAX_BUF_SIZE, false);
- alloc_vector->push_back(buf);
- list_node_t* node = getArbitraryNode(list, dataProvider);
- if (node != nullptr && buf != nullptr) {
- list_insert_after(list, node, buf);
- }
- return;
- }
- case 10: {
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- void* buf = generateBuffer(dataProvider, MAX_BUF_SIZE, false);
- alloc_vector->push_back(buf);
- if (list != nullptr && buf != nullptr) {
- list_prepend(list, buf);
- }
- return;
- }
- case 11: {
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- void* buf = generateBuffer(dataProvider, MAX_BUF_SIZE, false);
- alloc_vector->push_back(buf);
- if (list != nullptr && buf != nullptr) {
- list_append(list, buf);
- }
- return;
- }
- case 12: {
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- // The buffer will be valid, but may be for a different list
- void* buf = getArbitraryElement(alloc_vector, dataProvider);
- if (list != nullptr && buf != nullptr) {
- list_remove(list, buf);
- }
- return;
- }
- case 13:
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list != nullptr) {
- list_clear(list);
- }
- return;
- case 14:
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list != nullptr) {
- list_foreach(list, list_iter_cb_impl, dataProvider);
- }
- return;
- case 15:
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list != nullptr) {
- list_begin(list);
- }
- return;
- case 16:
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list != nullptr) {
- list_end(list);
- }
- return;
- case 17: {
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list == nullptr) {
- return;
- }
- list_node_t* node = getArbitraryNode(list, dataProvider);
- if (node != nullptr) {
- list_next(node);
- }
- return;
- }
- case 18: {
- list = reinterpret_cast<list_t*>(
- getArbitraryElement(list_vector, dataProvider));
- if (list == nullptr) {
- return;
- }
- list_node_t* node = getArbitraryNode(list, dataProvider);
- if (node != nullptr && node != list_end(list)) {
- list_node(node);
- }
- return;
- }
- default:
- return;
- }
-}
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Keep a vector of our allocated objects for freeing later
- std::vector<void*> list_vector;
- std::vector<void*> alloc_vector;
-
- // Call some functions, create some buffers
- size_t num_functions =
- dataProvider.ConsumeIntegralInRange<size_t>(0, MAX_NUM_FUNCTIONS);
- for (size_t i = 0; i < num_functions; i++) {
- callArbitraryFunction(&list_vector, &alloc_vector, &dataProvider);
- }
-
- // Free anything we've allocated
- for (const auto& list : list_vector) {
- if (list != nullptr) {
- list_free(reinterpret_cast<list_t*>(list));
- }
- }
- for (const auto& alloc : alloc_vector) {
- if (alloc != nullptr) {
- free(alloc);
- }
- }
- list_vector.clear();
-
- return 0;
-}
diff --git a/osi/test/fuzzers/ringbuffer/Android.bp b/osi/test/fuzzers/ringbuffer/Android.bp
deleted file mode 100644
index 6fef439b9..000000000
--- a/osi/test/fuzzers/ringbuffer/Android.bp
+++ /dev/null
@@ -1,21 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "libosi_fuzz_ringbuffer",
- defaults: ["libosi_fuzz_defaults"],
- host_supported: true,
- srcs: [
- "fuzz_ringbuffer.cc",
- ],
- static_libs: [
- "libosi",
- "liblog",
- ],
-}
diff --git a/osi/test/fuzzers/ringbuffer/fuzz_ringbuffer.cc b/osi/test/fuzzers/ringbuffer/fuzz_ringbuffer.cc
deleted file mode 100644
index adc219c22..000000000
--- a/osi/test/fuzzers/ringbuffer/fuzz_ringbuffer.cc
+++ /dev/null
@@ -1,167 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "osi/include/ringbuffer.h"
-
-#define MAX_NUM_FUNCTIONS 512
-#define MAX_BUF_SIZE 2048
-
-ringbuffer_t* getArbitraryRingBuf(std::vector<ringbuffer_t*>* ringbuf_vector,
- FuzzedDataProvider* dataProvider) {
- if (ringbuf_vector->empty()) {
- return nullptr;
- }
-
- size_t index = dataProvider->ConsumeIntegralInRange<size_t>(
- 0, ringbuf_vector->size() - 1);
- return ringbuf_vector->at(index);
-}
-
-void callArbitraryFunction(std::vector<ringbuffer_t*>* ringbuf_vector,
- FuzzedDataProvider* dataProvider) {
- // Get our function identifier
- char func_id = dataProvider->ConsumeIntegralInRange<char>(0, 8);
-
- ringbuffer_t* buf = nullptr;
- switch (func_id) {
- // Let 0 be a NO-OP, as ConsumeIntegral will return 0 on an empty buffer
- // (This will likely bias whatever action is here to run more often)
- case 0:
- return;
- case 1: {
- size_t size =
- dataProvider->ConsumeIntegralInRange<size_t>(0, MAX_BUF_SIZE);
- buf = ringbuffer_init(size);
- if (buf) {
- ringbuf_vector->push_back(buf);
- }
- }
- return;
- case 2: {
- if (ringbuf_vector->empty()) {
- return;
- }
- size_t index = dataProvider->ConsumeIntegralInRange<size_t>(
- 0, ringbuf_vector->size() - 1);
- buf = ringbuf_vector->at(index);
- if (buf) {
- ringbuffer_free(buf);
- ringbuf_vector->erase(ringbuf_vector->begin() + index);
- }
- }
- return;
- case 3:
- buf = getArbitraryRingBuf(ringbuf_vector, dataProvider);
- if (buf) {
- ringbuffer_available(buf);
- }
- return;
- case 4:
- buf = getArbitraryRingBuf(ringbuf_vector, dataProvider);
- if (buf) {
- ringbuffer_size(buf);
- }
- return;
- case 5: {
- buf = getArbitraryRingBuf(ringbuf_vector, dataProvider);
- size_t size =
- dataProvider->ConsumeIntegralInRange<size_t>(1, MAX_BUF_SIZE);
- if (buf == nullptr || size == 0) {
- return;
- }
- void* src_buf = malloc(size);
- if (src_buf == nullptr) {
- return;
- }
- std::vector<uint8_t> bytes = dataProvider->ConsumeBytes<uint8_t>(size);
- memcpy(src_buf, bytes.data(), bytes.size());
-
- ringbuffer_insert(buf, reinterpret_cast<uint8_t*>(src_buf), size);
- free(src_buf);
- }
- return;
- case 6:
- case 7: {
- buf = getArbitraryRingBuf(ringbuf_vector, dataProvider);
- if (buf == nullptr) {
- return;
- }
- size_t max_size = ringbuffer_size(buf);
- if (max_size == 0) {
- return;
- }
- size_t size = dataProvider->ConsumeIntegralInRange<size_t>(1, max_size);
-
- // NOTE: 0-size may be a valid case, that crashes currently.
- if (size == 0) {
- return;
- }
-
- void* dst_buf = malloc(size);
- if (dst_buf == nullptr) {
- return;
- }
- if (func_id == 6) {
- off_t offset = dataProvider->ConsumeIntegral<off_t>();
- if (offset >= 0 &&
- static_cast<size_t>(offset) <= ringbuffer_size(buf)) {
- ringbuffer_peek(buf, offset, reinterpret_cast<uint8_t*>(dst_buf),
- size);
- }
- } else {
- ringbuffer_pop(buf, reinterpret_cast<uint8_t*>(dst_buf), size);
- }
- free(dst_buf);
- }
- return;
- case 8: {
- buf = getArbitraryRingBuf(ringbuf_vector, dataProvider);
- size_t size =
- dataProvider->ConsumeIntegralInRange<size_t>(0, MAX_BUF_SIZE);
- if (buf) {
- ringbuffer_delete(buf, size);
- }
- }
- return;
- default:
- return;
- }
-}
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Keep a vector of our allocated objects for freeing later
- std::vector<ringbuffer_t*> ringbuf_vector;
-
- // Call some functions, create some buffers
- size_t num_functions =
- dataProvider.ConsumeIntegralInRange<size_t>(0, MAX_NUM_FUNCTIONS);
- for (size_t i = 0; i < num_functions; i++) {
- callArbitraryFunction(&ringbuf_vector, &dataProvider);
- }
-
- // Free anything we've allocated
- for (const auto& ringbuf : ringbuf_vector) {
- if (ringbuf != nullptr) {
- ringbuffer_free(ringbuf);
- }
- }
- ringbuf_vector.clear();
- return 0;
-}
diff --git a/osi/test/properties_test.cc b/osi/test/properties_test.cc
index 0d4553daa..499f6f3f3 100644
--- a/osi/test/properties_test.cc
+++ b/osi/test/properties_test.cc
@@ -31,7 +31,6 @@ TEST_F(PropertiesTest, test_default_value) {
}
TEST_F(PropertiesTest, test_successfull_set_and_get_value) {
-#if !defined(OS_GENERIC)
char value[PROPERTY_VALUE_MAX] = "nothing_interesting";
int ret = osi_property_set("very.useful.set.test", value);
ASSERT_EQ(0, ret);
@@ -39,7 +38,6 @@ TEST_F(PropertiesTest, test_successfull_set_and_get_value) {
char received[PROPERTY_VALUE_MAX];
osi_property_get("very.useful.set.test", received, NULL);
ASSERT_STREQ(received, "nothing_interesting");
-#endif
}
TEST_F(PropertiesTest, test_default_value_int32) {
@@ -49,12 +47,10 @@ TEST_F(PropertiesTest, test_default_value_int32) {
}
TEST_F(PropertiesTest, test_successfull_set_and_get_value_int32) {
-#if !defined(OS_GENERIC)
char value[PROPERTY_VALUE_MAX] = "42";
int ret = osi_property_set("very.useful.set.test", value);
ASSERT_EQ(0, ret);
int32_t received = osi_property_get_int32("very.useful.set.test", 84);
ASSERT_EQ(received, 42);
-#endif
-}
+} \ No newline at end of file
diff --git a/packet/Android.bp b/packet/Android.bp
index a6be2b1aa..44d062594 100644
--- a/packet/Android.bp
+++ b/packet/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "lib-bt-packets",
defaults: ["libchrome_support_defaults"],
@@ -19,10 +10,6 @@ cc_library_static {
"lib-bt-packets-base",
"lib-bt-packets-avrcp",
],
- apex_available: [
- "//apex_available:platform",
- "com.android.bluetooth.updatable",
- ],
}
cc_test {
@@ -30,9 +17,6 @@ cc_test {
defaults: ["fluoride_defaults"],
test_suites: ["device-tests"],
host_supported: true,
- test_options: {
- unit_test: true,
- },
local_include_dirs: ["tests"],
include_dirs: [
"system/bt/",
diff --git a/packet/BUILD.gn b/packet/BUILD.gn
index cc2c0d850..37d6ca494 100644
--- a/packet/BUILD.gn
+++ b/packet/BUILD.gn
@@ -14,18 +14,6 @@
# limitations under the License.
#
-config("packet_config") {
- include_dirs = [
- "//bt/",
- "//bt/include",
- "//bt/internal_include",
- "//bt/stack/include",
- "//bt/profile/avrcp",
- ]
-
- configs = [ "//bt:target_defaults" ]
-}
-
static_library("packet") {
sources = [
"avrcp/get_folder_items.cc",
@@ -51,51 +39,14 @@ static_library("packet") {
"base/packet_builder.cc",
]
- configs += [":packet_config"]
-}
-
-if (use.test) {
- executable("net_test_btpackets") {
- sources = [
- "tests/avrcp/avrcp_browse_packet_test.cc",
- "tests/avrcp/avrcp_packet_test.cc",
- "tests/avrcp/avrcp_reject_packet_test.cc",
- "tests/avrcp/change_path_packet_test.cc",
- "tests/avrcp/general_reject_packet_test.cc",
- "tests/avrcp/get_capabilities_packet_test.cc",
- "tests/avrcp/get_element_attributes_packet_test.cc",
- "tests/avrcp/get_folder_items_packet_test.cc",
- "tests/avrcp/get_item_attributes_packet_test.cc",
- "tests/avrcp/get_play_status_packet_test.cc",
- "tests/avrcp/get_total_number_of_items_packet_test.cc",
- "tests/avrcp/pass_through_packet_test.cc",
- "tests/avrcp/play_item_packet_test.cc",
- "tests/avrcp/register_notification_packet_test.cc",
- "tests/avrcp/set_absolute_volume_packet_test.cc",
- "tests/avrcp/set_addressed_player_packet_test.cc",
- "tests/avrcp/set_browsed_player_packet_test.cc",
- "tests/avrcp/vendor_packet_test.cc",
- "tests/base/iterator_test.cc",
- "tests/base/packet_builder_test.cc",
- "tests/base/packet_test.cc",
- ]
-
- include_dirs = [
- "//bt/packet/avrcp",
- "//bt/packet/base",
- "//bt/packet/include",
- "//bt/packet/tests",
- "//bt/packet/tests/avrcp",
- "//bt/packet/tests/base",
- ]
-
- deps = [
- ":packet",
- ]
+ include_dirs = [
+ "//",
+ "//internal_include",
+ "//stack/include",
+ "//profile/avrcp",
+ ]
- configs += [
- ":packet_config",
- "//bt:external_gmock_main",
- ]
- }
+ deps = [
+ "//third_party/libchrome:base"
+ ]
}
diff --git a/packet/avrcp/Android.bp b/packet/avrcp/Android.bp
index fd6aa979a..b54288f68 100644
--- a/packet/avrcp/Android.bp
+++ b/packet/avrcp/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "lib-bt-packets-avrcp",
defaults: ["libchrome_support_defaults"],
@@ -41,8 +32,4 @@ cc_library_static {
static_libs: [
"lib-bt-packets-base",
],
- apex_available: [
- "//apex_available:platform",
- "com.android.bluetooth.updatable",
- ],
}
diff --git a/packet/base/Android.bp b/packet/base/Android.bp
index 1f47c54b8..67f77d6b2 100644
--- a/packet/base/Android.bp
+++ b/packet/base/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "lib-bt-packets-base",
defaults: ["libchrome_support_defaults"],
@@ -17,8 +8,4 @@ cc_library_static {
"iterator.cc",
"packet_builder.cc",
],
- apex_available: [
- "//apex_available:platform",
- "com.android.bluetooth.updatable",
- ],
}
diff --git a/packet/base/packet.h b/packet/base/packet.h
index 2de22abac..8c8f22962 100644
--- a/packet/base/packet.h
+++ b/packet/base/packet.h
@@ -17,7 +17,6 @@
#pragma once
#include <cstdint>
-#include <memory>
#include <type_traits>
#include <utility>
#include <vector>
@@ -97,4 +96,4 @@ class Packet : public std::enable_shared_from_this<Packet> {
virtual std::pair<size_t, size_t> GetPayloadIndecies() const = 0;
};
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/packet/tests/avrcp/avrcp_test_packets.h b/packet/tests/avrcp/avrcp_test_packets.h
index c0ac161ee..14e30e7ac 100644
--- a/packet/tests/avrcp/avrcp_test_packets.h
+++ b/packet/tests/avrcp/avrcp_test_packets.h
@@ -58,17 +58,6 @@ std::vector<uint8_t> get_element_attributes_request_full = {
0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x04, 0x00,
0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x06};
-
-// AVRCP Get Element Attributes request for current playing song and attributes
-// Title, Artist, Album, Media Number, Playing Time, Total Number of Media,
-// Genre, and Cover Art
-std::vector<uint8_t> get_element_attributes_request_full_cover_art = {
- 0x01, 0x48, 0x00, 0x00, 0x19, 0x58, 0x20, 0x00, 0x00, 0x29, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x01, 0x00,
- 0x00, 0x00, 0x02, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x04, 0x00,
- 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x05, 0x00, 0x00, 0x00, 0x06, 0x00,
- 0x00, 0x00, 0x08};
-
// AVRCP Get Element Attributes response with attribute values as follows
// Title: "Test Song"
// Artist: "Test Artist"
@@ -292,20 +281,6 @@ std::vector<uint8_t> get_item_attributes_request_all_attributes = {
// AVRCP Get Item Attributes request with all attributes requested
// with the following fields:
// scope = 0x03 (Now Playing List)
-// uid_counter = 0x0000
-// uid = 0x0000000000000001
-// attributes = Title, Artist, Album, Media Number, Playing Time,
-// Total Number of Media, Genre, and Cover Art
-std::vector<uint8_t> get_item_attributes_request_all_attributes_with_cover_art = {
- 0x73, 0x00, 0x2C, 0x03, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
- 0x01, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00,
- 0x02, 0x00, 0x00, 0x00, 0x03, 0x00, 0x00, 0x00, 0x04, 0x00, 0x00,
- 0x00, 0x05, 0x00, 0x00, 0x00, 0x06, 0x00, 0x00, 0x00, 0x07, 0x00,
- 0x00, 0x00, 0x08};
-
-// AVRCP Get Item Attributes request with all attributes requested
-// with the following fields:
-// scope = 0x03 (Now Playing List)
// uid_counter = 0x0001
// uid = 0x0000000000000001
std::vector<uint8_t> get_item_attributes_request_all_attributes_invalid = {
@@ -341,10 +316,6 @@ std::vector<uint8_t> set_addressed_player_response = {
std::vector<uint8_t> set_browsed_player_request = {0x70, 0x00, 0x02, 0x00,
0x02};
-// AVRCP Set Browsed Player Request with player_id = 0
-std::vector<uint8_t> set_browsed_player_id_0_request = {0x70, 0x00, 0x02, 0x00,
- 0x00};
-
// AVRCP Set Browsed Player Response with num items = 4 and depth = 0
std::vector<uint8_t> set_browsed_player_response = {
0x70, 0x00, 0x0a, 0x04, 0x00, 0x00, 0x00,
diff --git a/packet/tests/fuzzers/Android.bp b/packet/tests/fuzzers/Android.bp
deleted file mode 100644
index d038ce870..000000000
--- a/packet/tests/fuzzers/Android.bp
+++ /dev/null
@@ -1,757 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "avrcp_browse_packet_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
- srcs: [
- "avrcp_browse_packet_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/avrcp_browse_packets_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "change_path_req_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
- //system/libbase/include/android-base"
- srcs: [
- "change_path_req_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/change_path_req_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_capabilities_req_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_capabilities_req_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/get_capabilities_req_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_capabilities_res_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_capabilities_res_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/get_capabilities_res_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_item_attributes_req_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_item_attributes_req_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/get_item_attributes_req_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_play_status_req_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_play_status_req_fuzzer.cc",
-
- ],
-
- corpus: ["get_play_status_req_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_total_number_of_items_req_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_total_number_of_items_req_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/get_total_number_of_items_req_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "pass_through_packet_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "pass_through_packet_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/pass_through_packet_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "play_item_packet_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "play_item_packet_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/play_item_packet_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "register_notification_packet_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "register_notification_packet_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/register_notification_packet_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "set_absolute_volume_packet_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "set_absolute_volume_packet_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/set_absolute_volume_packet_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "set_addressed_player_packet_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "set_addressed_player_packet_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/set_addressed_player_packet_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "set_browsed_player_req_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "set_browsed_player_req_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/set_browsed_player_req_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "vendor_packet_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "vendor_packet_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/vendor_packet_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "avrcp_packet_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "avrcp_packet_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/avrcp_packet_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "reject_packet_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "reject_packet_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/reject_packet_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_element_attributes_req_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_element_attributes_req_packet_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/get_element_attributes_req_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "change_path_res_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "change_path_res_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/change_path_res_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_element_attributes_res_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_element_attributes_res_packet_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/get_element_attributes_res_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_folder_items_res_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_folder_items_res_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/get_folder_items_res_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_folder_items_req_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_folder_items_req_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/get_folder_items_req_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_item_attributes_res_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_item_attributes_res_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/get_item_attributes_res_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_play_status_res_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_play_status_res_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/get_play_status_res_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "get_total_number_of_items_res_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "get_total_number_of_items_res_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/get_total_number_of_items_res_corpus/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
-
-cc_fuzz {
- name: "set_browsed_player_res_fuzzer",
- defaults: ["fluoride_defaults"],
- host_supported: true,
-
- include_dirs: [
- "system/bt/",
- "system/bt/include",
- "system/bt/packet/include",
- "system/bt/packet/tests",
- "system/bt/packet/tests/avrcp",
- "system/bt/packet/base",
- ],
-
- srcs: [
- "set_browsed_player_res_fuzzer.cc",
-
- ],
-
- corpus: ["corpus/set_browsed_player_res_fuzzer/*"],
-
- static_libs: [
- "libgmock",
- "lib-bt-packets",
- ],
- cflags: [
- "-DBUILDCFG",
- ],
-}
diff --git a/packet/tests/fuzzers/avrcp_browse_packet_fuzzer.cc b/packet/tests/fuzzers/avrcp_browse_packet_fuzzer.cc
deleted file mode 100644
index f2b84b35b..000000000
--- a/packet/tests/fuzzers/avrcp_browse_packet_fuzzer.cc
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from AVRCP Browse Packet Test
-
-#include <gtest/gtest.h>
-
-#include "avrcp_browse_packet.h"
-#include "avrcp_test_packets.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-
-namespace avrcp {
-
-using TestBrowsePacket = TestPacketType<BrowsePacket>;
-
-// buildpacket test
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> get_folder_items_request;
-
- // Expected packet size by the library is ~8
- if (size > 10) {
- for (size_t x = 0; x < size; x++) {
- get_folder_items_request.push_back(data[x]);
- }
-
- auto test_packet = TestBrowsePacket::Make(get_folder_items_request);
-
- test_packet->GetPdu();
- test_packet->GetLength();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/avrcp_packet_fuzzer.cc b/packet/tests/fuzzers/avrcp_packet_fuzzer.cc
deleted file mode 100644
index a63ac7049..000000000
--- a/packet/tests/fuzzers/avrcp_packet_fuzzer.cc
+++ /dev/null
@@ -1,87 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from avrcp_packet_test.cc
-#include <stddef.h>
-#include <stdint.h>
-#include "avrcp_packet.h"
-#include "avrcp_test_packets.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-
-// A helper class that has public accessors to protected methods
-class TestPacketBuilder : public PacketBuilder {
- public:
- static std::unique_ptr<TestPacketBuilder> MakeBuilder(
- std::vector<uint8_t> data) {
- std::unique_ptr<TestPacketBuilder> builder(new TestPacketBuilder(data));
- return builder;
- }
-
- // Make all the utility functions public
- using PacketBuilder::AddPayloadOctets1;
- using PacketBuilder::AddPayloadOctets2;
- using PacketBuilder::AddPayloadOctets3;
- using PacketBuilder::AddPayloadOctets4;
- using PacketBuilder::AddPayloadOctets6;
- using PacketBuilder::AddPayloadOctets8;
- using PacketBuilder::ReserveSpace;
-
- size_t size() const override { return data_.size(); };
-
- bool Serialize(const std::shared_ptr<Packet>& pkt) override {
- ReserveSpace(pkt, size());
-
- for (uint8_t byte : data_) {
- AddPayloadOctets1(pkt, byte);
- }
-
- return true;
- }
-
- explicit TestPacketBuilder(std::vector<uint8_t> data) : data_(data) {}
-
- std::vector<uint8_t> data_;
-};
-
-namespace avrcp {
-
-using TestAvrcpPacket = TestPacketType<Packet>;
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> get_capabilities_request_payload;
-
- if (size >= 8) {
- get_capabilities_request.push_back(0);
- for (int x = 0; x < 6; x++) {
- get_capabilities_request_payload.push_back(data[x]);
- }
-
- auto cap_req_builder =
- TestPacketBuilder::MakeBuilder(get_capabilities_request_payload);
-
- auto builder = PacketBuilder::MakeBuilder(
- CType::STATUS, 0x09, 0x00, Opcode::VENDOR, std::move(cap_req_builder));
-
- auto test_packet = TestAvrcpPacket::Make();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/change_path_req_fuzzer.cc b/packet/tests/fuzzers/change_path_req_fuzzer.cc
deleted file mode 100644
index 8ca88b2c6..000000000
--- a/packet/tests/fuzzers/change_path_req_fuzzer.cc
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from change_path_packet_test.cc
-
-#include <base/logging.h>
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "change_path.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestChangePathReqPacket = TestPacketType<ChangePathRequest>;
-
-// Getter
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> change_path_request_data;
-
- // Minimum for this type of packet appears to be 14 bytes.
- if (size > 14) {
- for (size_t x = 0; x < size; x++) {
- change_path_request_data.push_back(data[x]);
- }
-
- auto test_packet = TestChangePathReqPacket::Make(change_path_request_data);
-
- test_packet->GetUidCounter();
- test_packet->GetDirection();
- test_packet->GetUid();
- test_packet->IsValid();
- test_packet->ToString();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/change_path_res_fuzzer.cc b/packet/tests/fuzzers/change_path_res_fuzzer.cc
deleted file mode 100644
index 127ff07df..000000000
--- a/packet/tests/fuzzers/change_path_res_fuzzer.cc
+++ /dev/null
@@ -1,47 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from change_path_packet_test.cc
-
-#include <base/logging.h>
-#include <fuzzer/FuzzedDataProvider.h>
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-#include <string.h>
-
-#include "avrcp_test_packets.h"
-#include "change_path.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestChangePathReqPacket = TestPacketType<ChangePathRequest>;
-
-// Getter
-extern "C" int LLVMFuzzerTestOneInput(uint8_t* data, size_t size) {
- FuzzedDataProvider data_provider(data, size);
- auto builder = ChangePathResponseBuilder::MakeBuilder(
- Status::NO_ERROR, data_provider.ConsumeIntegral<uint32_t>());
-
- auto test_packet = TestChangePathReqPacket::Make();
- builder->Serialize(test_packet);
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/corpus/avrcp_browse_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/avrcp_browse_packet_corpus/validpacket
deleted file mode 100644
index 1fa87a802..000000000
--- a/packet/tests/fuzzers/corpus/avrcp_browse_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/avrcp_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/avrcp_packet_corpus/validpacket
deleted file mode 100644
index c7c5b3372..000000000
--- a/packet/tests/fuzzers/corpus/avrcp_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/avrcp_test_packets_corpus/validpacket b/packet/tests/fuzzers/corpus/avrcp_test_packets_corpus/validpacket
deleted file mode 100644
index 581327a4e..000000000
--- a/packet/tests/fuzzers/corpus/avrcp_test_packets_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/change_path_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/change_path_packet_corpus/validpacket
deleted file mode 100644
index 581327a4e..000000000
--- a/packet/tests/fuzzers/corpus/change_path_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/generate_corpus.sh b/packet/tests/fuzzers/corpus/generate_corpus.sh
deleted file mode 100644
index 954857549..000000000
--- a/packet/tests/fuzzers/corpus/generate_corpus.sh
+++ /dev/null
@@ -1,52 +0,0 @@
-mkdir avrcp_browse_packet_corpus
-mkdir change_path_req_corpus
-mkdir get_capabilities_req_corpus
-mkdir get_item_attributes_req_corpus
-mkdir get_play_status_req_corpus
-mkdir get_total_number_of_items_req_corpus
-mkdir pass_through_packet_corpus
-mkdir play_item_packet_corpus
-mkdir register_notification_packet_corpus
-mkdir set_absolute_volume_packet_corpus
-mkdir set_addressed_player_packet_corpus
-mkdir set_browsed_player_req_corpus
-mkdir vendor_packet_corpus
-mkdir avrcp_packet_corpus
-mkdir reject_packet_corpus
-#New ones
-mkdir change_path_res_corpus
-mkdir get_element_attributes_req_packet_corpus
-mkdir get_element_attributes_res_packet_corpus
-mkdir get_folder_items_res_corpus
-mkdir get_folder_items_req_corpus
-mkdir get_item_attributes_res_corpus
-mkdir get_play_status_res_corpus
-mkdir get_total_number_of_items_res_corpus
-mkdir set_browsed_player_res_corpus
-
-echo -n -e '\x71,\x00,\x0a,\x00,\x00,\x00,\x00,\x00,\x00,\x00,\x00,\x03,\x00' > avrcp_browse_packet_corpus/validpacket
-echo -n -e '\x72\x00\x0b\x00\x00\x01\x00\x00\x00\x00\x00\x00\x00\x02' > change_path_packet_corpus/validpacket
-echo -n -e '\x72\x00\x0b\x00\x00\x01\x00\x00\x00\x00\x00\x00\x00\x02' > get_capabilities_req_corpus/validpacket
-echo -n -e '\x73\x00\x28\x03\x00\x00\x00\x00\x00\x00\x00\x01\x00\x00\x07\x00\x00\x00\x01\x00\x00\x00\x02\x00\x00\x00\x03\x00\x00\x00\x04\x00\x00\x00\x05\x00\x00\x00\x06\x00\x00\x00\x07' > get_item_attributes_req_corpus/validpacket
-echo -n -e '\x01\x48\x00\x00\x19\x58\x30\x00\x00\x00' > get_play_status_req_corpus/validpacket
-echo -n -e '\x75\x00\x00' > get_total_number_of_items_req_corpus/validpacket
-echo -n -e '\x00\x48\x7c\x44\x00' > pass_through_packet_corpus/validpacket
-echo -n -e '\x00\x48\x00\x00\x19\x58\x74\x00\x00\x0b\x03\x00\x00\x00\x00\x00\x00\x00\x03\x00\x00' > play_item_req_corpus/validpacket
-echo -n -e '\x03\x48\x00\x00\x19\x58\x31\x00\x00\x04\x00\x00\x00\x00' > register_notification_packet_corpus/validpacket
-echo -n -e '\x00\x48\x00\x00\x19\x58\x50\x00\x00\x01\x48' > set_absolute_volume_packet_corpus/validpacket
-echo -n -e '\x00\x48\x00\x00\x19\x58\x60\x00\x00\x00' > set_addressed_player_packet_corpus/validpacket
-echo -n -e '\x70\x00\x02\x00\x02' > set_browsed_player_req_corpus/validpacket
-echo -n -e '\x01\x48\x00\x00\x19\x58\x10\x00\x00\x01' > vendor_packet_corpus/validpacket
-echo -n -e '\x01\x48\x00\x00\x19\x58\x10\x00\x00\x00' > avrcp_packet_corpus/validpacket
-
-#new ones
-
-echo -n -e '0x01, 0x48, 0x00, 0x00, 0x19, 0x58, 0x20, 0x00, 0x00, 0x00' > get_element_attributes_req_packet_corpus/validpacket
-echo -n -e '0x01, 0x48, 0x00, 0x00, 0x19, 0x58, 0x20, 0x00, 0x00, 0x00' > get_element_attributes_res_packet_corpus/validpacket
-echo -n -e '0x01, 0x48, 0x00, 0x00, 0x19, 0x58, 0x20, 0x00, 0x00, 0x00' > get_folder_items_res_corpus/validpacket
-echo -n -e '0x01, 0x48, 0x00, 0x00, 0x19, 0x58, 0x20, 0x00, 0x00, 0x00' > get_folder_items_req_corpus/validpacket
-echo -n -e '0x01, 0x48, 0x00, 0x00, 0x19, 0x58, 0x20, 0x00, 0x00, 0x00' > get_item_attributes_res_corpus/validpacket
-echo -n -e '0x01, 0x48, 0x00, 0x00, 0x19, 0x58, 0x20, 0x00, 0x00, 0x00' > get_play_status_res_corpus/validpacket
-echo -n -e '0x01, 0x48, 0x00, 0x00, 0x19, 0x58, 0x20, 0x00, 0x00, 0x00' > get_total_number_of_items_res_corpus/validpacket
-echo -n -e '0x01, 0x48, 0x00, 0x00, 0x19, 0x58, 0x20, 0x00, 0x00, 0x00' > set_browsed_player_res_corpus/validpacket
-echo -n -e '0x01, 0x48, 0x00, 0x00, 0x19, 0x58, 0x20, 0x00, 0x00, 0x00' > change_path_res_corpus/validpacket \ No newline at end of file
diff --git a/packet/tests/fuzzers/corpus/get_capabilities_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/get_capabilities_packet_corpus/validpacket
deleted file mode 100644
index 581327a4e..000000000
--- a/packet/tests/fuzzers/corpus/get_capabilities_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/get_item_attributes_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/get_item_attributes_packet_corpus/validpacket
deleted file mode 100644
index 7d706b8f0..000000000
--- a/packet/tests/fuzzers/corpus/get_item_attributes_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/get_play_status_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/get_play_status_packet_corpus/validpacket
deleted file mode 100644
index 2311a4775..000000000
--- a/packet/tests/fuzzers/corpus/get_play_status_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/get_total_number_of_items_corpus/validpacket b/packet/tests/fuzzers/corpus/get_total_number_of_items_corpus/validpacket
deleted file mode 100644
index bc634e2b3..000000000
--- a/packet/tests/fuzzers/corpus/get_total_number_of_items_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/pass_through_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/pass_through_packet_corpus/validpacket
deleted file mode 100644
index 9e002d211..000000000
--- a/packet/tests/fuzzers/corpus/pass_through_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/play_item_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/play_item_packet_corpus/validpacket
deleted file mode 100644
index 538a7c046..000000000
--- a/packet/tests/fuzzers/corpus/play_item_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/register_notification_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/register_notification_packet_corpus/validpacket
deleted file mode 100644
index 2a213f0f2..000000000
--- a/packet/tests/fuzzers/corpus/register_notification_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/set_absolute_volume_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/set_absolute_volume_packet_corpus/validpacket
deleted file mode 100644
index 5403b843d..000000000
--- a/packet/tests/fuzzers/corpus/set_absolute_volume_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/set_addressed_player_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/set_addressed_player_packet_corpus/validpacket
deleted file mode 100644
index 4872d6b05..000000000
--- a/packet/tests/fuzzers/corpus/set_addressed_player_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/set_browsed_player_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/set_browsed_player_packet_corpus/validpacket
deleted file mode 100644
index 667137b52..000000000
--- a/packet/tests/fuzzers/corpus/set_browsed_player_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/corpus/vendor_packet_corpus/validpacket b/packet/tests/fuzzers/corpus/vendor_packet_corpus/validpacket
deleted file mode 100644
index 0c2a66e27..000000000
--- a/packet/tests/fuzzers/corpus/vendor_packet_corpus/validpacket
+++ /dev/null
Binary files differ
diff --git a/packet/tests/fuzzers/get_capabilities_req_fuzzer.cc b/packet/tests/fuzzers/get_capabilities_req_fuzzer.cc
deleted file mode 100644
index 1243d0c17..000000000
--- a/packet/tests/fuzzers/get_capabilities_req_fuzzer.cc
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from get_capabilities_packet_test
-
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "capabilities_packet.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using GetCapRequestTestPacket = TestPacketType<GetCapabilitiesRequest>;
-
-// Test parsing a GetCapabilities Request
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> get_capabilities_request;
- // We will use stability testing to see the sensible max size for fuzzing.
- // Max BT packet size = 251
- // Expected packet size by the library is ~ 10
- if (size >= 12) {
- get_capabilities_request.push_back(0);
- for (size_t x = 0; x < size; x++) {
- get_capabilities_request.push_back(data[x]);
- }
-
- auto test_packet = GetCapRequestTestPacket::Make(get_capabilities_request);
- test_packet->GetCapabilityRequested();
- test_packet->IsValid();
- test_packet->ToString();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/get_capabilities_res_fuzzer.cc b/packet/tests/fuzzers/get_capabilities_res_fuzzer.cc
deleted file mode 100644
index a01cda138..000000000
--- a/packet/tests/fuzzers/get_capabilities_res_fuzzer.cc
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <gtest/gtest.h>
-#include <stdlib.h>
-#include <string.h>
-
-#include "avrcp_test_packets.h"
-#include "capabilities_packet.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-// Test parsing a GetCapabilities Request
-extern "C" int LLVMFuzzerTestOneInput(uint8_t* data, size_t size) {
- FuzzedDataProvider data_provider(data, size);
- auto builder = GetCapabilitiesResponseBuilder::MakeCompanyIdBuilder(
- data_provider.ConsumeIntegral<uint32_t>());
- builder->AddCompanyId(data_provider.ConsumeIntegral<uint32_t>());
- builder->AddCompanyId(data_provider.ConsumeIntegral<uint32_t>());
-
- builder = GetCapabilitiesResponseBuilder::MakeEventsSupportedBuilder(
- Event::PLAYBACK_STATUS_CHANGED);
- builder->AddEvent(Event::TRACK_CHANGED);
- builder->AddEvent(Event::PLAYBACK_POS_CHANGED);
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/get_element_attributes_req_packet_fuzzer.cc b/packet/tests/fuzzers/get_element_attributes_req_packet_fuzzer.cc
deleted file mode 100644
index 68c038f9c..000000000
--- a/packet/tests/fuzzers/get_element_attributes_req_packet_fuzzer.cc
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "get_element_attributes_packet.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestGetElemAttrReqPacket = TestPacketType<GetElementAttributesRequest>;
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> get_element_attributes_request_full;
-
- // Expected packet size by the library is ~10
- if (size >= 10) {
- get_element_attributes_request_full.push_back(0);
- for (size_t x = 0; x < size; x++) {
- get_element_attributes_request_full.push_back(data[x]);
- }
-
- auto test_packet =
- TestGetElemAttrReqPacket::Make(get_element_attributes_request_full);
- if (!test_packet->IsValid()) return 0;
- test_packet->GetIdentifier();
- auto tpString = test_packet->ToString();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/get_element_attributes_res_packet_fuzzer.cc b/packet/tests/fuzzers/get_element_attributes_res_packet_fuzzer.cc
deleted file mode 100644
index fa90eaa36..000000000
--- a/packet/tests/fuzzers/get_element_attributes_res_packet_fuzzer.cc
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "get_element_attributes_packet.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestGetElemAttrReqPacket = TestPacketType<GetElementAttributesRequest>;
-
-extern "C" int LLVMFuzzerTestOneInput(uint8_t* data, size_t size) {
- auto builder = GetElementAttributesResponseBuilder::MakeBuilder(0xFFFF);
- FuzzedDataProvider data_provider(data, size);
- std::string s = data_provider.ConsumeRemainingBytesAsString();
- builder->AddAttributeEntry(Attribute::TITLE, s);
- builder->AddAttributeEntry(Attribute::ARTIST_NAME, s);
- builder->AddAttributeEntry(Attribute::ALBUM_NAME, s);
- builder->AddAttributeEntry(Attribute::TRACK_NUMBER, s);
- builder->AddAttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, s);
- builder->AddAttributeEntry(Attribute::GENRE, s);
- builder->AddAttributeEntry(Attribute::PLAYING_TIME, s);
-
- auto test_packet = TestGetElemAttrReqPacket::Make();
- builder->Serialize(test_packet);
- test_packet->GetData();
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/get_folder_items_req_fuzzer.cc b/packet/tests/fuzzers/get_folder_items_req_fuzzer.cc
deleted file mode 100644
index fe2478cfd..000000000
--- a/packet/tests/fuzzers/get_folder_items_req_fuzzer.cc
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from get_folder_items_packet_test
-
-#include "avrcp_test_packets.h"
-#include "get_folder_items.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestGetFolderItemsReqPacket = TestPacketType<GetFolderItemsRequest>;
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> get_folder_items_request_vfs;
-
- // Starts large to avoid throwing exceptions
- if (size >= 34) {
- for (size_t x = 0; x < size; x++) {
- get_folder_items_request_vfs.push_back(data[x]);
- }
-
- auto test_packet =
- TestGetFolderItemsReqPacket::Make(get_folder_items_request_vfs);
-
- test_packet->GetScope();
- test_packet->GetStartItem();
- test_packet->GetEndItem();
- test_packet->GetNumAttributes();
- test_packet->IsValid();
- test_packet->ToString();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/get_folder_items_res_fuzzer.cc b/packet/tests/fuzzers/get_folder_items_res_fuzzer.cc
deleted file mode 100644
index 09e525282..000000000
--- a/packet/tests/fuzzers/get_folder_items_res_fuzzer.cc
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from get_folder_items_packet_test
-
-#include <fuzzer/FuzzedDataProvider.h>
-
-#include "avrcp_test_packets.h"
-#include "get_folder_items.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestGetFolderItemsReqPacket = TestPacketType<GetFolderItemsRequest>;
-
-extern "C" int LLVMFuzzerTestOneInput(uint8_t* data, size_t size) {
- auto builder = GetFolderItemsResponseBuilder::MakeNowPlayingBuilder(
- Status::NO_ERROR, 0x0000, 0xFFFF);
- std::set<AttributeEntry> attributes;
- FuzzedDataProvider data_provider(data, size);
- std::string s = data_provider.ConsumeRemainingBytesAsString();
- attributes.insert(AttributeEntry(Attribute::TITLE, s));
- auto song = MediaElementItem(0x02, s, attributes);
- builder->AddSong(song);
-
- auto test_packet = TestGetFolderItemsReqPacket::Make();
- builder->Serialize(test_packet);
- test_packet->GetData();
-
- // Second test with the same data.
- auto builder2 = GetFolderItemsResponseBuilder::MakeVFSBuilder(
- Status::NO_ERROR, 0x0000, 0xFFFF);
- auto folder = FolderItem(0x0000000000000001, 0x00, true, s);
- builder2->AddFolder(folder);
-
- test_packet = TestGetFolderItemsReqPacket::Make();
- builder2->Serialize(test_packet);
- test_packet->GetData();
-
- // Third test with the same data.
- MediaPlayerItem player1(1, s, true);
-
- // Browsing Header + Status field + UID Counter field + Number of Items
- // field
- auto packet_size = BrowsePacket::kMinSize() + 5;
- packet_size += player1.size();
-
- auto builder3 = GetFolderItemsResponseBuilder::MakePlayerListBuilder(
- Status::NO_ERROR, 0x0000, packet_size);
-
- builder3->AddMediaPlayer(player1);
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/get_item_attributes_req_fuzzer.cc b/packet/tests/fuzzers/get_item_attributes_req_fuzzer.cc
deleted file mode 100644
index 88fdcd38e..000000000
--- a/packet/tests/fuzzers/get_item_attributes_req_fuzzer.cc
+++ /dev/null
@@ -1,47 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from get_item_attributes_packet_test
-
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "get_item_attributes.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestGetItemAttrsReqPacket = TestPacketType<GetItemAttributesRequest>;
-
-// Builder packet.
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> get_item_attributes_request;
-
- if (size > 44) {
- for (size_t x = 0; x < size; x++) {
- get_item_attributes_request.push_back(data[x]);
- }
- auto test_packet =
- TestGetItemAttrsReqPacket::Make(get_item_attributes_request);
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/get_item_attributes_res_fuzzer.cc b/packet/tests/fuzzers/get_item_attributes_res_fuzzer.cc
deleted file mode 100644
index ca50fb50f..000000000
--- a/packet/tests/fuzzers/get_item_attributes_res_fuzzer.cc
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from get_item_attributes_packet_test
-#include <fuzzer/FuzzedDataProvider.h>
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "get_item_attributes.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestGetItemAttrsReqPacket = TestPacketType<GetItemAttributesRequest>;
-
-// Builder packet.
-
-extern "C" int LLVMFuzzerTestOneInput(uint8_t* data, size_t size) {
- FuzzedDataProvider data_provider(data, size);
- std::string s = data_provider.ConsumeRemainingBytesAsString();
- auto builder =
- GetItemAttributesResponseBuilder::MakeBuilder(Status::NO_ERROR, 0xFFFF);
- builder->AddAttributeEntry(Attribute::TITLE, s);
- builder->AddAttributeEntry(Attribute::ARTIST_NAME, s);
- builder->AddAttributeEntry(Attribute::ALBUM_NAME, s);
-
- auto test_packet = TestGetItemAttrsReqPacket::Make();
- builder->Serialize(test_packet);
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/get_play_status_req_fuzzer.cc b/packet/tests/fuzzers/get_play_status_req_fuzzer.cc
deleted file mode 100644
index 25c549e88..000000000
--- a/packet/tests/fuzzers/get_play_status_req_fuzzer.cc
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from get_play_status_packet_test.cc
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <gtest/gtest.h>
-#include <string.h>
-
-#include "avrcp_test_packets.h"
-#include "get_play_status_packet.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestGetPlayStatusRspPacket = TestPacketType<Packet>;
-
-extern "C" int LLVMFuzzerTestOneInput(uint8_t* data, size_t size) {
- FuzzedDataProvider data_provider(data, size);
-
- auto builder = GetPlayStatusResponseBuilder::MakeBuilder(
- 0, data_provider.ConsumeIntegral<uint32_t>(), 0);
- auto test_packet = TestGetPlayStatusRspPacket::Make();
- builder->Serialize(test_packet);
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/get_play_status_res_fuzzer.cc b/packet/tests/fuzzers/get_play_status_res_fuzzer.cc
deleted file mode 100644
index cfadfb307..000000000
--- a/packet/tests/fuzzers/get_play_status_res_fuzzer.cc
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from get_play_status_packet_test.cc
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "get_play_status_packet.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestGetPlayStatusRspPacket = TestPacketType<Packet>;
-
-extern "C" int LLVMFuzzerTestOneInput(uint8_t* data, size_t size) {
- FuzzedDataProvider data_provider(data, size);
- auto builder = GetPlayStatusResponseBuilder::MakeBuilder(
- 0, data_provider.ConsumeIntegral<uint32_t>(), 0);
- auto test_packet = TestGetPlayStatusRspPacket::Make();
- builder->Serialize(test_packet);
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/get_total_number_of_items_req_fuzzer.cc b/packet/tests/fuzzers/get_total_number_of_items_req_fuzzer.cc
deleted file mode 100644
index ef290b0e3..000000000
--- a/packet/tests/fuzzers/get_total_number_of_items_req_fuzzer.cc
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from get_total_number_of_items_test
-
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "get_total_number_of_items.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestGetTotalNumItemsReqPacket =
- TestPacketType<GetTotalNumberOfItemsRequest>;
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> get_total_number_of_items_request_now_playing;
-
- // Expected packet size by the library is ~4
- if (size >= 8) {
- for (size_t x = 0; x < size; x++) {
- get_total_number_of_items_request_now_playing.push_back(data[x]);
- }
-
- auto test_packet = TestGetTotalNumItemsReqPacket::Make(
- get_total_number_of_items_request_now_playing);
- test_packet->GetScope();
- test_packet->IsValid();
- test_packet->GetData();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/get_total_number_of_items_res_fuzzer.cc b/packet/tests/fuzzers/get_total_number_of_items_res_fuzzer.cc
deleted file mode 100644
index b456d3230..000000000
--- a/packet/tests/fuzzers/get_total_number_of_items_res_fuzzer.cc
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from get_total_number_of_items_test
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <gtest/gtest.h>
-#include <stdlib.h>
-
-#include "avrcp_test_packets.h"
-#include "get_total_number_of_items.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestGetTotalNumItemsReqPacket =
- TestPacketType<GetTotalNumberOfItemsRequest>;
-
-extern "C" int LLVMFuzzerTestOneInput(uint8_t* data, size_t size) {
- FuzzedDataProvider data_provider(data, size);
- auto builder = GetTotalNumberOfItemsResponseBuilder::MakeBuilder(
- Status::NO_ERROR, data_provider.ConsumeIntegral<uint32_t>(),
- data_provider.ConsumeIntegral<uint32_t>());
-
- auto test_packet = TestGetTotalNumItemsReqPacket::Make();
- builder->Serialize(test_packet);
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/pass_through_packet_fuzzer.cc b/packet/tests/fuzzers/pass_through_packet_fuzzer.cc
deleted file mode 100644
index 52b48bf28..000000000
--- a/packet/tests/fuzzers/pass_through_packet_fuzzer.cc
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from pass_through_packet_fuzzer.cc
-
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "packet_test_helper.h"
-#include "pass_through_packet.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestPassThroughPacket = TestPacketType<PassThroughPacket>;
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> pass_through_command_play_pushed;
-
- // Expected packet size by the library is ~5
- if (size >= 10) {
- for (size_t x = 0; x < size; x++) {
- pass_through_command_play_pushed.push_back(data[x]);
- }
-
- auto test_packet =
- TestPassThroughPacket::Make(pass_through_command_play_pushed);
- test_packet->GetKeyState();
- test_packet->GetOperationId();
-
- test_packet =
- TestPassThroughPacket::Make(pass_through_command_play_released);
- test_packet->GetKeyState();
- test_packet->GetOperationId();
- test_packet->GetData();
- test_packet->IsValid();
- test_packet->ToString();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/play_item_packet_fuzzer.cc b/packet/tests/fuzzers/play_item_packet_fuzzer.cc
deleted file mode 100644
index 90057b3dd..000000000
--- a/packet/tests/fuzzers/play_item_packet_fuzzer.cc
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from play_item_packet_test.cc
-
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "packet_test_helper.h"
-#include "play_item.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestPlayItemReqPacket = TestPacketType<PlayItemRequest>;
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> play_item_request;
-
- // We will use stability testing to see the sensible max size for fuzzing.
- // Max BT packet size = 251
- // Expected packet size by the library is ~21 but previous tests account for
- // as low as 4
- if (size >= 21) {
- for (size_t x = 0; x < size; x++) {
- play_item_request.push_back(data[x]);
- }
-
- auto test_packet = TestPlayItemReqPacket::Make(play_item_request);
-
- test_packet->GetScope();
- test_packet->GetUid();
- test_packet->GetUidCounter();
- test_packet->IsValid();
- test_packet->GetData();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/register_notification_packet_fuzzer.cc b/packet/tests/fuzzers/register_notification_packet_fuzzer.cc
deleted file mode 100644
index 70328d034..000000000
--- a/packet/tests/fuzzers/register_notification_packet_fuzzer.cc
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from register_notification_packet_test.cc
-
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "packet_test_helper.h"
-#include "register_notification_packet.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestRegNotifReqPacket = TestPacketType<RegisterNotificationRequest>;
-using TestRegNotifRspPacket = TestPacketType<RegisterNotificationResponse>;
-// as small as 4
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> register_play_status_notification;
-
- // We will use stability testing to see the sensible max size for fuzzing.
- // Max BT packet size = 251
- // Expected packet size by the library is as small as 4.
- // Seems to raise exceptions below 15.
-
- if (size >= 15) {
- for (size_t x = 0; x < size; x++) {
- register_play_status_notification.push_back(data[x]);
- }
-
- auto test_packet =
- TestRegNotifReqPacket::Make(register_play_status_notification);
-
- test_packet->GetEventRegistered();
- test_packet->GetInterval();
- test_packet->GetData();
- test_packet->ToString();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/reject_packet_fuzzer.cc b/packet/tests/fuzzers/reject_packet_fuzzer.cc
deleted file mode 100644
index 8ef77472a..000000000
--- a/packet/tests/fuzzers/reject_packet_fuzzer.cc
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from avrcp_reject_fuzzer.cc
-
-#include <gtest/gtest.h>
-
-#include "avrcp_reject_packet.h"
-#include "avrcp_test_packets.h"
-#include "packet_test_helper.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestAvrcpPacket = TestPacketType<Packet>;
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- // Minimum size is 13.
- std::vector<uint8_t> rejected_volume_changed_notification;
-
- if (size > 13) {
- for (size_t x = 0; x < size; x++) {
- rejected_volume_changed_notification.push_back(data[x]);
- }
-
- auto test_packet =
- TestAvrcpPacket::Make(rejected_volume_changed_notification);
-
- test_packet->GetData();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/set_absolute_volume_packet_fuzzer.cc b/packet/tests/fuzzers/set_absolute_volume_packet_fuzzer.cc
deleted file mode 100644
index 28713a9d2..000000000
--- a/packet/tests/fuzzers/set_absolute_volume_packet_fuzzer.cc
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from set_absolute_volume_packet_test.cc
-
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "packet_test_helper.h"
-#include "set_absolute_volume.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestSetVolumeRspPacket = TestPacketType<SetAbsoluteVolumeResponse>;
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> set_absolute_volume_response;
-
- // We will use stability testing to see the sensible max size for fuzzing.
- // Max BT packet size = 251
- // Expected packet size by the library is ~5
- if (size >= 12) {
- for (size_t x = 0; x < size; x++) {
- set_absolute_volume_response.push_back(data[x]);
- }
- auto test_packet =
- TestSetVolumeRspPacket::Make(set_absolute_volume_response);
-
- test_packet->IsValid();
- test_packet->GetVolume();
- test_packet->GetData();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/set_addressed_player_packet_fuzzer.cc b/packet/tests/fuzzers/set_addressed_player_packet_fuzzer.cc
deleted file mode 100644
index 83277b65f..000000000
--- a/packet/tests/fuzzers/set_addressed_player_packet_fuzzer.cc
+++ /dev/null
@@ -1,47 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// set_addressed_player_packet_test.cc
-
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "packet_test_helper.h"
-#include "set_addressed_player.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestSetAddrPlayerPacket = TestPacketType<SetAddressedPlayerRequest>;
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> short_set_addressed_player_request;
- // Expected packet size by the library is ~9
- if (size >= 9) {
- for (size_t x = 0; x < size; x++) {
- short_set_addressed_player_request.push_back(data[x]);
- }
- auto test_packet =
- TestSetAddrPlayerPacket::Make(set_addressed_player_request);
-
- test_packet->GetPlayerId();
- test_packet->GetData();
- }
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/set_browsed_player_req_fuzzer.cc b/packet/tests/fuzzers/set_browsed_player_req_fuzzer.cc
deleted file mode 100644
index 0586d3f68..000000000
--- a/packet/tests/fuzzers/set_browsed_player_req_fuzzer.cc
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from set_browsed_player_packet.cc
-
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "packet_test_helper.h"
-#include "set_browsed_player.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestSetBrowsedPlayerPacket = TestPacketType<SetBrowsedPlayerRequest>;
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> set_browsed_player_response;
-
- // Expected packet size by the library is ~5
- if (size >= 5) {
- for (size_t x = 0; x < size; x++) {
- set_browsed_player_response.push_back(data[x]);
- }
-
- auto test_packet =
- TestSetBrowsedPlayerPacket::Make(set_browsed_player_response);
-
- test_packet->GetPlayerId();
- test_packet->GetData();
- test_packet->IsValid();
- test_packet->ToString();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/set_browsed_player_res_fuzzer.cc b/packet/tests/fuzzers/set_browsed_player_res_fuzzer.cc
deleted file mode 100644
index e26e2c5ac..000000000
--- a/packet/tests/fuzzers/set_browsed_player_res_fuzzer.cc
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gtest/gtest.h>
-
-#include "avrcp_test_packets.h"
-#include "packet_test_helper.h"
-#include "set_browsed_player.h"
-
-namespace bluetooth {
-namespace avrcp {
-
-using TestSetBrowsedPlayerPacket = TestPacketType<SetBrowsedPlayerRequest>;
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> set_browsed_player_request;
-
- // Expected packet size by the library is ~5
- if (size >= 5) {
- for (size_t x = 0; x < size; x++) {
- set_browsed_player_request.push_back(data[x]);
- }
-
- auto test_packet =
- TestSetBrowsedPlayerPacket::Make(set_browsed_player_request);
-
- test_packet->GetPlayerId();
- test_packet->GetData();
- test_packet->IsValid();
- }
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/packet/tests/fuzzers/vendor_packet_fuzzer.cc b/packet/tests/fuzzers/vendor_packet_fuzzer.cc
deleted file mode 100644
index 50a8c5d0d..000000000
--- a/packet/tests/fuzzers/vendor_packet_fuzzer.cc
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// Adapted from vendor_packet_test.cc
-
-#include <gtest/gtest.h>
-#include <tuple>
-
-#include "avrcp_test_packets.h"
-#include "packet_test_helper.h"
-#include "vendor_packet.h"
-
-namespace bluetooth {
-
-namespace avrcp {
-
-using TestVendorPacket = TestPacketType<VendorPacket>;
-
-using TestParam = std::tuple<std::vector<uint8_t>, CommandPdu>;
-class VendorPacketTest : public ::testing::TestWithParam<TestParam> {
- public:
- std::vector<uint8_t> GetPacketData() { return std::get<0>(GetParam()); }
- CommandPdu GetCommandPdu() { return std::get<1>(GetParam()); }
-};
-
-extern "C" int LLVMFuzzerTestOneInput(const char* data, size_t size) {
- std::vector<uint8_t> short_vendor_packet;
-
- // Expected packet size by the library is > 19
- if (size >= 19) {
- for (size_t x = 0; x < size; x++) {
- short_vendor_packet.push_back(data[x]);
- }
-
- } else {
- return 0;
- }
-
- auto test_packet = TestVendorPacket::Make(short_vendor_packet);
-
- test_packet->GetCompanyId();
- test_packet->GetCommandPdu();
- test_packet->GetPacketType();
- test_packet->GetParameterLength();
- test_packet->IsValid();
- test_packet->ToString();
-
- return 0;
-}
-
-} // namespace avrcp
-} // namespace bluetooth
diff --git a/profile/avrcp/Android.bp b/profile/avrcp/Android.bp
index b2acb6d1c..515f513e1 100644
--- a/profile/avrcp/Android.bp
+++ b/profile/avrcp/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "avrcp-target-service",
defaults: [
@@ -19,7 +10,6 @@ cc_library_static {
"system/bt/btcore/include",
"system/bt/internal_include",
"system/bt/stack/include",
- "system/bt/gd/rust/shim",
],
export_include_dirs: ["./"],
srcs: [
@@ -34,10 +24,6 @@ cc_library_static {
shared_libs: [
"libchrome",
],
- apex_available: [
- "//apex_available:platform",
- "com.android.bluetooth.updatable",
- ],
}
cc_test {
@@ -48,9 +34,6 @@ cc_test {
"clang_coverage_bin",
],
host_supported: true,
- test_options: {
- unit_test: true,
- },
include_dirs: [
"system/bt",
"system/bt/btcore/include",
@@ -67,7 +50,6 @@ cc_test {
"libosi",
"liblog",
"libcutils",
- "libbase",
"libbtdevice",
"avrcp-target-service",
],
@@ -111,9 +93,4 @@ cc_fuzz {
corpus: [
"tests/avrcp_device_fuzz/corpus/*",
],
- target: {
- darwin: {
- enabled: false,
- },
- },
}
diff --git a/profile/avrcp/BUILD.gn b/profile/avrcp/BUILD.gn
index 5e54fff60..c37e0a7aa 100644
--- a/profile/avrcp/BUILD.gn
+++ b/profile/avrcp/BUILD.gn
@@ -14,54 +14,21 @@
# limitations under the License.
#
-config("avrcp_config") {
- include_dirs = [
- "//bt/",
- "//bt/btcore/include",
- "//bt/internal_include",
- "//bt/stack/include",
- "//bt/profile/avrcp",
- "//bt/packet",
- "//bt/packet/include",
- "//bt/include/hardware/avrcp",
- ]
-
- configs = ["//bt:target_defaults"]
-}
-
static_library("profile_avrcp") {
sources = [
"connection_handler.cc",
"device.cc",
]
- deps = [
- "//bt/gd/rust/shim:message_loop_thread_bridge_header",
+ include_dirs = [
+ "//",
+ "//btcore/include",
+ "//internal_include",
+ "//stack/include",
+ "//profile/avrcp",
]
- configs += [
- ":avrcp_config"
+ deps = [
+ "//third_party/libchrome:base"
]
}
-
-if (use.test) {
- executable("net_test_avrcp") {
- sources = [
- "tests/avrcp_connection_handler_test.cc",
- "tests/avrcp_device_test.cc",
- ]
-
- deps = [
- ":profile_avrcp",
- "//bt/device:device",
- "//bt/osi:osi",
- "//bt/packet:packet",
- "//bt/types:types",
- ]
-
- configs += [
- "//bt:external_gmock_main",
- ":avrcp_config",
- ]
- }
-}
diff --git a/profile/avrcp/avrcp_config.h b/profile/avrcp/avrcp_config.h
deleted file mode 100644
index f6a872443..000000000
--- a/profile/avrcp/avrcp_config.h
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "stack/include/avrc_api.h"
-
-// Supported Features for AVRCP Version 1.6
-#ifndef AVRCP_SUPF_TG_1_6
-#define AVRCP_SUPF_TG_1_6 \
- (AVRC_SUPF_TG_CAT1 | AVRC_SUPF_TG_MULTI_PLAYER | \
- AVRC_SUPF_TG_BROWSE) /* TODO: | AVRC_SUPF_TG_APP_SETTINGS) */
-#endif
-
-// Supported Features for AVRCP Version 1.5
-#ifndef AVRCP_SUPF_TG_1_5
-#define AVRCP_SUPF_TG_1_5 \
- (AVRC_SUPF_TG_CAT1 | AVRC_SUPF_TG_MULTI_PLAYER | \
- AVRC_SUPF_TG_BROWSE)
-#endif
-
-// Supported Features for AVRCP Version 1.4
-#ifndef AVRCP_SUPF_TG_1_4
-#define AVRCP_SUPF_TG_1_4 \
- (AVRC_SUPF_TG_CAT1 | AVRC_SUPF_TG_MULTI_PLAYER | \
- AVRC_SUPF_TG_BROWSE)
-#endif
-
-// Supported Features for AVRCP Version 1.3 "Compatibility Mode"
-#ifndef AVRCP_SUPF_TG_1_3
-#define AVRCP_SUPF_TG_1_3 AVRC_SUPF_TG_CAT1
-#endif
-
-/**
- * Default Supported Feature bits for AVRCP Controller
- */
-#ifndef AVRCP_SUPF_TG
-#define AVRCP_SUPF_TG_DEFAULT AVRCP_SUPF_TG_1_4
-#endif
diff --git a/profile/avrcp/avrcp_internal.h b/profile/avrcp/avrcp_internal.h
index ef957d8de..4aeffdf06 100644
--- a/profile/avrcp/avrcp_internal.h
+++ b/profile/avrcp/avrcp_internal.h
@@ -18,7 +18,6 @@
#include "stack/include/avrc_api.h"
#include "stack/include/sdp_api.h"
-#include "avrcp_config.h"
/**
* Wrapper classes for the API functions currently defined in "system/bt/stack".
@@ -31,15 +30,10 @@
// required
class AvrcpInterface {
public:
- virtual uint16_t GetAvrcpVersion() = 0;
-
virtual uint16_t AddRecord(uint16_t service_uuid, const char* p_service_name,
const char* p_provider_name, uint16_t categories,
uint32_t sdp_handle, bool browse_supported,
- uint16_t profile_version,
- uint16_t cover_art_psm) = 0;
-
- virtual uint16_t RemoveRecord(uint32_t sdp_handle) = 0;
+ uint16_t profile_version) = 0;
virtual uint16_t FindService(uint16_t service_uuid, const RawAddress& bd_addr,
tAVRC_SDP_DB_PARAMS* p_db,
diff --git a/profile/avrcp/avrcp_message_converter.h b/profile/avrcp/avrcp_message_converter.h
index 5f5212aad..8de704b54 100644
--- a/profile/avrcp/avrcp_message_converter.h
+++ b/profile/avrcp/avrcp_message_converter.h
@@ -76,7 +76,7 @@ class AvrcpMessageConverter {
for (int i = 2; i >= 0; i--) {
data.push_back((uint8_t)((msg->company_id >> i * 8) & 0xff));
}
- for (int i = 0; i < msg->vendor_len; i++) {
+ for (uint8_t i = 0; i < msg->vendor_len; i++) {
data.push_back(msg->p_vendor_data[i]);
}
} break;
@@ -103,4 +103,4 @@ class AvrcpMessageConverter {
return VectorPacket::Make(data);
}
-};
+}; \ No newline at end of file
diff --git a/profile/avrcp/connection_handler.cc b/profile/avrcp/connection_handler.cc
index 7a2b44bda..06c61b3ba 100644
--- a/profile/avrcp/connection_handler.cc
+++ b/profile/avrcp/connection_handler.cc
@@ -85,12 +85,9 @@ bool ConnectionHandler::CleanUp() {
CHECK(instance_ != nullptr);
// TODO (apanicke): Cleanup the SDP Entries here
- for (auto entry = instance_->device_map_.begin();
- entry != instance_->device_map_.end();) {
- auto curr = entry;
- entry++;
- curr->second->DeviceDisconnected();
- instance_->avrc_->Close(curr->first);
+ for (const auto& entry : instance_->device_map_) {
+ entry.second->DeviceDisconnected();
+ instance_->avrc_->Close(entry.first);
}
instance_->device_map_.clear();
instance_->feature_map_.clear();
@@ -149,16 +146,6 @@ bool ConnectionHandler::DisconnectDevice(const RawAddress& bdaddr) {
return false;
}
-void ConnectionHandler::SetBipClientStatus(const RawAddress& bdaddr,
- bool connected) {
- for (auto it = device_map_.begin(); it != device_map_.end(); it++) {
- if (bdaddr == it->second->GetAddress()) {
- it->second->SetBipClientStatus(connected);
- return;
- }
- }
-}
-
std::vector<std::shared_ptr<Device>> ConnectionHandler::GetListOfDevices()
const {
std::vector<std::shared_ptr<Device>> list;
@@ -211,8 +198,7 @@ bool ConnectionHandler::AvrcpConnect(bool initiator, const RawAddress& bdaddr) {
: AVRC_CONN_ACP; // 0 if initiator, 1 if acceptor
// TODO (apanicke): We shouldn't need RCCT to do absolute volume. The current
// AVRC_API requires it though.
- open_cb.control = BTA_AV_FEAT_RCTG | BTA_AV_FEAT_RCCT | BTA_AV_FEAT_METADATA
- | AVRC_CT_PASSIVE;
+ open_cb.control = BTA_AV_FEAT_RCTG | BTA_AV_FEAT_RCCT | BTA_AV_FEAT_METADATA;
uint8_t handle = 0;
uint16_t status = avrc_->Open(&handle, &open_cb, bdaddr);
@@ -423,7 +409,7 @@ void ConnectionHandler::MessageCb(uint8_t handle, uint8_t label, uint8_t opcode,
void ConnectionHandler::SdpCb(RawAddress bdaddr, SdpCallback cb,
tSDP_DISCOVERY_DB* disc_db, bool retry,
uint16_t status) {
- VLOG(1) << __PRETTY_FUNCTION__ << ": SDP lookup callback received";
+ LOG(INFO) << __PRETTY_FUNCTION__ << ": SDP lookup callback received";
if (status == SDP_CONN_FAILED and !retry) {
LOG(WARNING) << __PRETTY_FUNCTION__ << ": SDP Failure retry again";
@@ -455,35 +441,35 @@ void ConnectionHandler::SdpCb(RawAddress bdaddr, SdpCallback cb,
/* get profile version (if failure, version parameter is not updated) */
sdp_->FindProfileVersionInRec(
sdp_record, UUID_SERVCLASS_AV_REMOTE_CONTROL, &peer_avrcp_version);
- VLOG(1) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
- << " peer avrcp version=" << loghex(peer_avrcp_version);
+ LOG(INFO) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
+ << " peer avrcp version=" << loghex(peer_avrcp_version);
if (peer_avrcp_version >= AVRC_REV_1_3) {
// These are the standard features, another way to check this is to
// search for CAT1 on the remote device
- VLOG(1) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
- << " supports metadata";
+ LOG(INFO) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
+ << " supports metadata";
peer_features |= (BTA_AV_FEAT_VENDOR | BTA_AV_FEAT_METADATA);
}
if (peer_avrcp_version >= AVRC_REV_1_4) {
/* get supported categories */
- VLOG(1) << __PRETTY_FUNCTION__ << " Get Supported categories";
+ LOG(INFO) << __PRETTY_FUNCTION__ << " Get Supported categories";
tSDP_DISC_ATTR* sdp_attribute =
sdp_->FindAttributeInRec(sdp_record, ATTR_ID_SUPPORTED_FEATURES);
if (sdp_attribute != NULL) {
- VLOG(1) << __PRETTY_FUNCTION__
- << "Get Supported categories SDP ATTRIBUTES != null";
+ LOG(INFO) << __PRETTY_FUNCTION__
+ << "Get Supported categories SDP ATTRIBUTES != null";
uint16_t categories = sdp_attribute->attr_value.v.u16;
if (categories & AVRC_SUPF_CT_CAT2) {
- VLOG(1) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
- << " supports advanced control";
+ LOG(INFO) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
+ << " supports advanced control";
if (IsAbsoluteVolumeEnabled(&bdaddr)) {
peer_features |= (BTA_AV_FEAT_ADV_CTRL);
}
}
if (categories & AVRC_SUPF_CT_BROWSE) {
- VLOG(1) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
- << " supports browsing";
+ LOG(INFO) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
+ << " supports browsing";
peer_features |= (BTA_AV_FEAT_BROWSE);
}
}
@@ -494,30 +480,30 @@ void ConnectionHandler::SdpCb(RawAddress bdaddr, SdpCallback cb,
sdp_record = sdp_->FindServiceInDb(disc_db, UUID_SERVCLASS_AV_REM_CTRL_TARGET,
nullptr);
if (sdp_record != nullptr) {
- VLOG(1) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
- << " supports remote control target";
+ LOG(INFO) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
+ << " supports remote control target";
uint16_t peer_avrcp_target_version = 0;
sdp_->FindProfileVersionInRec(sdp_record, UUID_SERVCLASS_AV_REMOTE_CONTROL,
&peer_avrcp_target_version);
- VLOG(1) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
- << " peer avrcp target version="
- << loghex(peer_avrcp_target_version);
+ LOG(INFO) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
+ << " peer avrcp target version="
+ << loghex(peer_avrcp_target_version);
if ((sdp_->FindAttributeInRec(sdp_record, ATTR_ID_BT_PROFILE_DESC_LIST)) !=
NULL) {
if (peer_avrcp_target_version >= AVRC_REV_1_4) {
/* get supported categories */
- VLOG(1) << __PRETTY_FUNCTION__ << " Get Supported categories";
+ LOG(INFO) << __PRETTY_FUNCTION__ << " Get Supported categories";
tSDP_DISC_ATTR* sdp_attribute =
sdp_->FindAttributeInRec(sdp_record, ATTR_ID_SUPPORTED_FEATURES);
if (sdp_attribute != NULL) {
- VLOG(1) << __PRETTY_FUNCTION__
- << "Get Supported categories SDP ATTRIBUTES != null";
+ LOG(INFO) << __PRETTY_FUNCTION__
+ << "Get Supported categories SDP ATTRIBUTES != null";
uint16_t categories = sdp_attribute->attr_value.v.u16;
if (categories & AVRC_SUPF_CT_CAT2) {
- VLOG(1) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
- << " supports advanced control";
+ LOG(INFO) << __PRETTY_FUNCTION__ << ": Device " << bdaddr.ToString()
+ << " supports advanced control";
if (IsAbsoluteVolumeEnabled(&bdaddr)) {
peer_features |= (BTA_AV_FEAT_ADV_CTRL);
}
diff --git a/profile/avrcp/connection_handler.h b/profile/avrcp/connection_handler.h
index 5320b63a4..a5029cfc9 100644
--- a/profile/avrcp/connection_handler.h
+++ b/profile/avrcp/connection_handler.h
@@ -110,14 +110,6 @@ class ConnectionHandler {
*/
virtual bool DisconnectDevice(const RawAddress& bdaddr);
- /**
- * Indicates the connection status of a device on the BIP OBEX server.
- *
- * This status is used to determine whether we should include image handles
- * when building responses for media item metadata queries.
- */
- virtual void SetBipClientStatus(const RawAddress& bdaddr, bool connected);
-
virtual std::vector<std::shared_ptr<Device>> GetListOfDevices() const;
/**
diff --git a/profile/avrcp/device.cc b/profile/avrcp/device.cc
index f31d736b1..a7e0e9a05 100644
--- a/profile/avrcp/device.cc
+++ b/profile/avrcp/device.cc
@@ -15,7 +15,8 @@
*/
#include "device.h"
-#include "abstract_message_loop.h"
+#include <base/message_loop/message_loop.h>
+
#include "connection_handler.h"
#include "packet/avrcp/avrcp_reject_packet.h"
#include "packet/avrcp/general_reject_packet.h"
@@ -45,8 +46,7 @@ Device::Device(
avrcp13_compatibility_(avrcp13_compatibility),
send_message_cb_(send_msg_cb),
ctrl_mtu_(ctrl_mtu),
- browse_mtu_(browse_mtu),
- has_bip_client_(false) {}
+ browse_mtu_(browse_mtu) {}
void Device::RegisterInterfaces(MediaInterface* media_interface,
A2dpInterface* a2dp_interface,
@@ -67,24 +67,6 @@ void Device::SetBrowseMtu(uint16_t browse_mtu) {
browse_mtu_ = browse_mtu;
}
-void Device::SetBipClientStatus(bool connected) {
- DEVICE_LOG(INFO) << __PRETTY_FUNCTION__ << ": connected = " << connected;
- has_bip_client_ = connected;
-}
-
-bool Device::HasBipClient() const {
- return has_bip_client_;
-}
-
-void filter_cover_art(SongInfo& s) {
- for (auto it = s.attributes.begin(); it != s.attributes.end(); it++) {
- if (it->attribute() == Attribute::DEFAULT_COVER_ART) {
- s.attributes.erase(it);
- break;
- }
- }
-}
-
bool Device::IsActive() const {
return address_ == a2dp_interface_->active_peer();
}
@@ -169,7 +151,6 @@ void Device::VendorPacketHandler(uint8_t label,
DEVICE_LOG(WARNING) << __func__ << ": Request packet is not valid";
auto response = RejectBuilder::MakeBuilder(pkt->GetCommandPdu(), Status::INVALID_PARAMETER);
send_message(label, false, std::move(response));
- return;
}
media_interface_->GetSongInfo(base::Bind(&Device::GetElementAttributesResponse, weak_ptr_factory_.GetWeakPtr(),
label, get_element_attributes_request_pkt));
@@ -539,7 +520,7 @@ void Device::PlaybackPosNotificationResponse(uint8_t label, bool interim,
DEVICE_VLOG(0) << __func__ << ": Queue next play position update";
play_pos_update_cb_.Reset(base::Bind(&Device::HandlePlayPosUpdate,
weak_ptr_factory_.GetWeakPtr()));
- btbase::AbstractMessageLoop::current_task_runner()->PostDelayedTask(
+ base::MessageLoop::current()->task_runner()->PostDelayedTask(
FROM_HERE, play_pos_update_cb_.callback(),
base::TimeDelta::FromSeconds(play_pos_interval_));
}
@@ -606,17 +587,14 @@ void Device::GetPlayStatusResponse(uint8_t label, PlayStatus status) {
void Device::GetElementAttributesResponse(
uint8_t label, std::shared_ptr<GetElementAttributesRequest> pkt,
SongInfo info) {
+ DEVICE_VLOG(2) << __func__;
+
auto get_element_attributes_pkt = pkt;
auto attributes_requested =
get_element_attributes_pkt->GetAttributesRequested();
auto response = GetElementAttributesResponseBuilder::MakeBuilder(ctrl_mtu_);
- // Filter out DEFAULT_COVER_ART handle if this device has no client
- if (!HasBipClient()) {
- filter_cover_art(info);
- }
-
last_song_info_ = info;
if (attributes_requested.size() != 0) {
@@ -1030,11 +1008,6 @@ void Device::GetItemAttributesNowPlayingResponse(
}
}
- // Filter out DEFAULT_COVER_ART handle if this device has no client
- if (!HasBipClient()) {
- filter_cover_art(info);
- }
-
auto attributes_requested = pkt->GetAttributesRequested();
if (attributes_requested.size() != 0) {
for (const auto& attribute : attributes_requested) {
@@ -1078,11 +1051,6 @@ void Device::GetItemAttributesVFSResponse(
}
}
- // Filter out DEFAULT_COVER_ART handle if this device has no client
- if (item_requested.type == ListItem::SONG && !HasBipClient()) {
- filter_cover_art(item_requested.song);
- }
-
// TODO (apanicke): Add a helper function or allow adding a map
// of attributes to GetItemAttributesResponseBuilder
auto attributes_requested = pkt->GetAttributesRequested();
@@ -1202,12 +1170,6 @@ void Device::GetVFSListResponse(uint8_t label,
if (!builder->AddFolder(folder_item)) break;
} else if (items[i].type == ListItem::SONG) {
auto song = items[i].song;
-
- // Filter out DEFAULT_COVER_ART handle if this device has no client
- if (!HasBipClient()) {
- filter_cover_art(song);
- }
-
auto title =
song.attributes.find(Attribute::TITLE) != song.attributes.end()
? song.attributes.find(Attribute::TITLE)->value()
@@ -1246,12 +1208,6 @@ void Device::GetNowPlayingListResponse(
for (size_t i = pkt->GetStartItem();
i <= pkt->GetEndItem() && i < song_list.size(); i++) {
auto song = song_list[i];
-
- // Filter out DEFAULT_COVER_ART handle if this device has no client
- if (!HasBipClient()) {
- filter_cover_art(song);
- }
-
auto title = song.attributes.find(Attribute::TITLE) != song.attributes.end()
? song.attributes.find(Attribute::TITLE)->value()
: "No Song Info";
@@ -1301,14 +1257,6 @@ void Device::SetBrowsedPlayerResponse(
return;
}
- if (pkt->GetPlayerId() == 0 && num_items == 0) {
- // Response fail if no browsable player in Bluetooth Player
- auto response = SetBrowsedPlayerResponseBuilder::MakeBuilder(
- Status::PLAYER_NOT_BROWSABLE, 0x0000, num_items, 0, "");
- send_message(label, true, std::move(response));
- return;
- }
-
curr_browsed_player_id_ = pkt->GetPlayerId();
// Clear the path and push the new root.
diff --git a/profile/avrcp/device.h b/profile/avrcp/device.h
index fc5d7364b..18bfc98be 100644
--- a/profile/avrcp/device.h
+++ b/profile/avrcp/device.h
@@ -81,16 +81,6 @@ class Device {
bool Disconnect();
/**
- * Set the status of the BIP obex client
- */
- void SetBipClientStatus(bool connected);
-
- /**
- * Returns true if the current device has a BIP OBEX client.
- */
- bool HasBipClient() const;
-
- /**
* Returns true if the current device is silenced.
*/
bool IsInSilenceMode() const;
@@ -305,7 +295,6 @@ class Device {
send_message_cb_;
uint16_t ctrl_mtu_;
uint16_t browse_mtu_;
- bool has_bip_client_;
int curr_browsed_player_id_ = -1;
diff --git a/profile/avrcp/tests/avrcp_connection_handler_test.cc b/profile/avrcp/tests/avrcp_connection_handler_test.cc
index e2765fab7..5a811b27c 100644
--- a/profile/avrcp/tests/avrcp_connection_handler_test.cc
+++ b/profile/avrcp/tests/avrcp_connection_handler_test.cc
@@ -16,6 +16,7 @@
#include <base/bind.h>
#include <base/logging.h>
+#include <base/message_loop/message_loop.h>
#include <gmock/gmock.h>
#include <gtest/gtest.h>
diff --git a/profile/avrcp/tests/avrcp_device_test.cc b/profile/avrcp/tests/avrcp_device_test.cc
index 516949291..d221e1be3 100644
--- a/profile/avrcp/tests/avrcp_device_test.cc
+++ b/profile/avrcp/tests/avrcp_device_test.cc
@@ -84,19 +84,6 @@ class AvrcpDeviceTest : public ::testing::Test {
test_device->BrowseMessageReceived(label, message);
}
- void SetBipClientStatus(bool connected) {
- test_device->SetBipClientStatus(connected);
- }
-
- void FilterCoverArt(SongInfo& s) {
- for (auto it = s.attributes.begin(); it != s.attributes.end(); it++) {
- if (it->attribute() == Attribute::DEFAULT_COVER_ART) {
- s.attributes.erase(it);
- break;
- }
- }
- }
-
MockFunction<void(uint8_t, bool, const AvrcpResponse&)> response_cb;
Device* test_device;
};
@@ -111,14 +98,6 @@ TEST_F(AvrcpDeviceTest, addressTest) {
ASSERT_EQ(device.GetAddress(), RawAddress::kAny);
}
-TEST_F(AvrcpDeviceTest, setBipClientStatusTest) {
- ASSERT_EQ(test_device->HasBipClient(), false);
- SetBipClientStatus(true);
- ASSERT_EQ(test_device->HasBipClient(), true);
- SetBipClientStatus(false);
- ASSERT_EQ(test_device->HasBipClient(), false);
-}
-
TEST_F(AvrcpDeviceTest, trackChangedTest) {
MockMediaInterface interface;
NiceMock<MockA2dpInterface> a2dp_interface;
@@ -133,8 +112,7 @@ TEST_F(AvrcpDeviceTest, trackChangedTest) {
AttributeEntry(Attribute::TRACK_NUMBER, "1"),
AttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2"),
AttributeEntry(Attribute::GENRE, "Test Genre"),
- AttributeEntry(Attribute::PLAYING_TIME, "1000"),
- AttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001")}};
+ AttributeEntry(Attribute::PLAYING_TIME, "1000")}};
std::vector<SongInfo> list = {info};
EXPECT_CALL(interface, GetNowPlayingList(_))
@@ -268,8 +246,7 @@ TEST_F(AvrcpDeviceTest, trackChangedBeforeInterimTest) {
AttributeEntry(Attribute::TRACK_NUMBER, "1"),
AttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2"),
AttributeEntry(Attribute::GENRE, "Test Genre"),
- AttributeEntry(Attribute::PLAYING_TIME, "1000"),
- AttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001")}};
+ AttributeEntry(Attribute::PLAYING_TIME, "1000")}};
std::vector<SongInfo> list = {info};
MediaInterface::NowPlayingCallback interim_cb;
@@ -434,8 +411,7 @@ TEST_F(AvrcpDeviceTest, nowPlayingChangedBeforeInterim) {
AttributeEntry(Attribute::TRACK_NUMBER, "1"),
AttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2"),
AttributeEntry(Attribute::GENRE, "Test Genre"),
- AttributeEntry(Attribute::PLAYING_TIME, "1000"),
- AttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001")}};
+ AttributeEntry(Attribute::PLAYING_TIME, "1000")}};
std::vector<SongInfo> list = {info};
MediaInterface::NowPlayingCallback interim_cb;
@@ -549,8 +525,7 @@ TEST_F(AvrcpDeviceTest, nowPlayingTest) {
AttributeEntry(Attribute::TRACK_NUMBER, "1"),
AttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2"),
AttributeEntry(Attribute::GENRE, "Test Genre"),
- AttributeEntry(Attribute::PLAYING_TIME, "1000"),
- AttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001")}};
+ AttributeEntry(Attribute::PLAYING_TIME, "1000")}};
std::vector<SongInfo> list = {info};
EXPECT_CALL(interface, GetNowPlayingList(_))
.Times(2)
@@ -618,8 +593,7 @@ TEST_F(AvrcpDeviceTest, getElementAttributesTest) {
AttributeEntry(Attribute::TRACK_NUMBER, "1"),
AttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2"),
AttributeEntry(Attribute::GENRE, "Test Genre"),
- AttributeEntry(Attribute::PLAYING_TIME, "1000"),
- AttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001")}};
+ AttributeEntry(Attribute::PLAYING_TIME, "1000")}};
EXPECT_CALL(interface, GetSongInfo(_)).WillRepeatedly(InvokeCb<0>(info));
@@ -646,60 +620,6 @@ TEST_F(AvrcpDeviceTest, getElementAttributesTest) {
SendMessage(3, TestAvrcpPacket::Make(get_element_attributes_request_full));
}
-TEST_F(AvrcpDeviceTest, getElementAttributesWithCoverArtTest) {
- MockMediaInterface interface;
- NiceMock<MockA2dpInterface> a2dp_interface;
-
- test_device->RegisterInterfaces(&interface, &a2dp_interface, nullptr);
-
- SongInfo info = {"test_id",
- {// The attribute map
- AttributeEntry(Attribute::TITLE, "Test Song"),
- AttributeEntry(Attribute::ARTIST_NAME, "Test Artist"),
- AttributeEntry(Attribute::ALBUM_NAME, "Test Album"),
- AttributeEntry(Attribute::TRACK_NUMBER, "1"),
- AttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2"),
- AttributeEntry(Attribute::GENRE, "Test Genre"),
- AttributeEntry(Attribute::PLAYING_TIME, "1000"),
- AttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001")}};
-
- EXPECT_CALL(interface, GetSongInfo(_)).WillRepeatedly(InvokeCb<0>(info));
- SetBipClientStatus(false);
-
- auto compare_to_no_art =
- GetElementAttributesResponseBuilder::MakeBuilder(0xFFFF);
- compare_to_no_art->AddAttributeEntry(Attribute::TITLE, "Test Song");
- compare_to_no_art->AddAttributeEntry(Attribute::ARTIST_NAME, "Test Artist");
- compare_to_no_art->AddAttributeEntry(Attribute::ALBUM_NAME, "Test Album");
- compare_to_no_art->AddAttributeEntry(Attribute::TRACK_NUMBER, "1");
- compare_to_no_art->AddAttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2");
- compare_to_no_art->AddAttributeEntry(Attribute::GENRE, "Test Genre");
- compare_to_no_art->AddAttributeEntry(Attribute::PLAYING_TIME, "1000");
- EXPECT_CALL(response_cb,
- Call(3, false, matchPacket(std::move(compare_to_no_art))))
- .Times(1);
- SendMessage(3,
- TestAvrcpPacket::Make(get_element_attributes_request_full_cover_art));
-
- SetBipClientStatus(true);
-
- auto compare_to_full =
- GetElementAttributesResponseBuilder::MakeBuilder(0xFFFF);
- compare_to_full->AddAttributeEntry(Attribute::TITLE, "Test Song");
- compare_to_full->AddAttributeEntry(Attribute::ARTIST_NAME, "Test Artist");
- compare_to_full->AddAttributeEntry(Attribute::ALBUM_NAME, "Test Album");
- compare_to_full->AddAttributeEntry(Attribute::TRACK_NUMBER, "1");
- compare_to_full->AddAttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2");
- compare_to_full->AddAttributeEntry(Attribute::GENRE, "Test Genre");
- compare_to_full->AddAttributeEntry(Attribute::PLAYING_TIME, "1000");
- compare_to_full->AddAttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001");
- EXPECT_CALL(response_cb,
- Call(3, false, matchPacket(std::move(compare_to_full))))
- .Times(1);
- SendMessage(3,
- TestAvrcpPacket::Make(get_element_attributes_request_full_cover_art));
-}
-
TEST_F(AvrcpDeviceTest, getElementAttributesMtuTest) {
auto truncated_packet =
GetElementAttributesResponseBuilder::MakeBuilder(0xFFFF);
@@ -830,7 +750,6 @@ TEST_F(AvrcpDeviceTest, getNowPlayingListTest) {
NiceMock<MockA2dpInterface> a2dp_interface;
test_device->RegisterInterfaces(&interface, &a2dp_interface, nullptr);
- SetBipClientStatus(false);
SongInfo info = {"test_id",
{// The attribute map
@@ -840,53 +759,19 @@ TEST_F(AvrcpDeviceTest, getNowPlayingListTest) {
AttributeEntry(Attribute::TRACK_NUMBER, "1"),
AttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2"),
AttributeEntry(Attribute::GENRE, "Test Genre"),
- AttributeEntry(Attribute::PLAYING_TIME, "1000"),
- AttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001")}};
+ AttributeEntry(Attribute::PLAYING_TIME, "1000")}};
std::vector<SongInfo> list = {info};
EXPECT_CALL(interface, GetNowPlayingList(_))
.WillRepeatedly(InvokeCb<0>("test_id", list));
- FilterCoverArt(info);
auto expected_response = GetFolderItemsResponseBuilder::MakeNowPlayingBuilder(
Status::NO_ERROR, 0x0000, 0xFFFF);
expected_response->AddSong(MediaElementItem(1, "Test Song", info.attributes));
EXPECT_CALL(response_cb,
Call(1, true, matchPacket(std::move(expected_response))))
.Times(1);
- auto request = TestBrowsePacket::Make(get_folder_items_request_now_playing);
- SendBrowseMessage(1, request);
-}
-
-TEST_F(AvrcpDeviceTest, getNowPlayingListWithCoverArtTest) {
- MockMediaInterface interface;
- NiceMock<MockA2dpInterface> a2dp_interface;
-
- test_device->RegisterInterfaces(&interface, &a2dp_interface, nullptr);
- SetBipClientStatus(true);
-
- SongInfo info = {"test_id",
- {// The attribute map
- AttributeEntry(Attribute::TITLE, "Test Song"),
- AttributeEntry(Attribute::ARTIST_NAME, "Test Artist"),
- AttributeEntry(Attribute::ALBUM_NAME, "Test Album"),
- AttributeEntry(Attribute::TRACK_NUMBER, "1"),
- AttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2"),
- AttributeEntry(Attribute::GENRE, "Test Genre"),
- AttributeEntry(Attribute::PLAYING_TIME, "1000"),
- AttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001")}};
- std::vector<SongInfo> list = {info};
-
- EXPECT_CALL(interface, GetNowPlayingList(_))
- .WillRepeatedly(InvokeCb<0>("test_id", list));
- auto expected_response = GetFolderItemsResponseBuilder::MakeNowPlayingBuilder(
- Status::NO_ERROR, 0x0000, 0xFFFF);
- expected_response->AddSong(MediaElementItem(1, "Test Song", info.attributes));
-
- EXPECT_CALL(response_cb,
- Call(1, true, matchPacket(std::move(expected_response))))
- .Times(1);
auto request = TestBrowsePacket::Make(get_folder_items_request_now_playing);
SendBrowseMessage(1, request);
}
@@ -1065,15 +950,12 @@ TEST_F(AvrcpDeviceTest, getItemAttributesNowPlayingTest) {
AttributeEntry(Attribute::TRACK_NUMBER, "1"),
AttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2"),
AttributeEntry(Attribute::GENRE, "Test Genre"),
- AttributeEntry(Attribute::PLAYING_TIME, "1000"),
- AttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001")}};
+ AttributeEntry(Attribute::PLAYING_TIME, "1000")}};
std::vector<SongInfo> list = {info};
EXPECT_CALL(interface, GetNowPlayingList(_))
.WillRepeatedly(InvokeCb<0>("test_id", list));
- SetBipClientStatus(false);
-
auto compare_to_full =
GetItemAttributesResponseBuilder::MakeBuilder(Status::NO_ERROR, 0xFFFF);
compare_to_full->AddAttributeEntry(Attribute::TITLE, "Test Song");
@@ -1092,70 +974,7 @@ TEST_F(AvrcpDeviceTest, getItemAttributesNowPlayingTest) {
SendBrowseMessage(1, request);
}
-TEST_F(AvrcpDeviceTest, getItemAttributesNowPlayingWithCoverArtTest) {
- MockMediaInterface interface;
- NiceMock<MockA2dpInterface> a2dp_interface;
-
- test_device->RegisterInterfaces(&interface, &a2dp_interface, nullptr);
-
- SongInfo info = {"test_id",
- {// The attribute map
- AttributeEntry(Attribute::TITLE, "Test Song"),
- AttributeEntry(Attribute::ARTIST_NAME, "Test Artist"),
- AttributeEntry(Attribute::ALBUM_NAME, "Test Album"),
- AttributeEntry(Attribute::TRACK_NUMBER, "1"),
- AttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2"),
- AttributeEntry(Attribute::GENRE, "Test Genre"),
- AttributeEntry(Attribute::PLAYING_TIME, "1000"),
- AttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001")}};
- std::vector<SongInfo> list = {info};
-
- EXPECT_CALL(interface, GetNowPlayingList(_))
- .WillRepeatedly(InvokeCb<0>("test_id", list));
-
- SetBipClientStatus(true);
-
- auto compare_to_full =
- GetItemAttributesResponseBuilder::MakeBuilder(Status::NO_ERROR, 0xFFFF);
- compare_to_full->AddAttributeEntry(Attribute::TITLE,"Test Song");
- compare_to_full->AddAttributeEntry(Attribute::ARTIST_NAME, "Test Artist");
- compare_to_full->AddAttributeEntry(Attribute::ALBUM_NAME, "Test Album");
- compare_to_full->AddAttributeEntry(Attribute::TRACK_NUMBER, "1");
- compare_to_full->AddAttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2");
- compare_to_full->AddAttributeEntry(Attribute::GENRE, "Test Genre");
- compare_to_full->AddAttributeEntry(Attribute::PLAYING_TIME, "1000");
- compare_to_full->AddAttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001");
- EXPECT_CALL(response_cb,
- Call(1, true, matchPacket(std::move(compare_to_full))))
- .Times(1);
-
- auto requestWithBip =
- TestBrowsePacket::Make(
- get_item_attributes_request_all_attributes_with_cover_art);
- SendBrowseMessage(1, requestWithBip);
-
- SetBipClientStatus(false);
-
- auto compare_to_no_art =
- GetItemAttributesResponseBuilder::MakeBuilder(Status::NO_ERROR, 0xFFFF);
- compare_to_no_art->AddAttributeEntry(Attribute::TITLE, "Test Song");
- compare_to_no_art->AddAttributeEntry(Attribute::ARTIST_NAME, "Test Artist");
- compare_to_no_art->AddAttributeEntry(Attribute::ALBUM_NAME, "Test Album");
- compare_to_no_art->AddAttributeEntry(Attribute::TRACK_NUMBER, "1");
- compare_to_no_art->AddAttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2");
- compare_to_no_art->AddAttributeEntry(Attribute::GENRE, "Test Genre");
- compare_to_no_art->AddAttributeEntry(Attribute::PLAYING_TIME, "1000");
- EXPECT_CALL(response_cb,
- Call(1, true, matchPacket(std::move(compare_to_no_art))))
- .Times(1);
-
- auto requestWithoutBip =
- TestBrowsePacket::Make(
- get_item_attributes_request_all_attributes_with_cover_art);
- SendBrowseMessage(1, requestWithoutBip);
-}
-
-TEST_F(AvrcpDeviceTest, getItemAttributesMtuTest) {
+TEST_F(AvrcpDeviceTest, geItemAttributesMtuTest) {
auto truncated_packet =
GetItemAttributesResponseBuilder::MakeBuilder(Status::NO_ERROR, 0xFFFF);
truncated_packet->AddAttributeEntry(Attribute::TITLE, "1234");
@@ -1216,44 +1035,6 @@ TEST_F(AvrcpDeviceTest, setAddressedPlayerTest) {
SendMessage(1, request);
}
-TEST_F(AvrcpDeviceTest, setBrowsedPlayerTest) {
- MockMediaInterface interface;
- NiceMock<MockA2dpInterface> a2dp_interface;
-
- test_device->RegisterInterfaces(&interface, &a2dp_interface, nullptr);
-
- EXPECT_CALL(interface, SetBrowsedPlayer(_, _))
- .Times(3)
- .WillOnce(InvokeCb<1>(true, "", 0))
- .WillOnce(InvokeCb<1>(false, "", 0))
- .WillOnce(InvokeCb<1>(true, "", 2));
-
- auto not_browsable_rsp = SetBrowsedPlayerResponseBuilder::MakeBuilder(
- Status::PLAYER_NOT_BROWSABLE, 0x0000, 0, 0, "");
- EXPECT_CALL(response_cb,
- Call(1, true, matchPacket(std::move(not_browsable_rsp))))
- .Times(1);
-
- auto player_id_0_request =
- TestBrowsePacket::Make(set_browsed_player_id_0_request);
- SendBrowseMessage(1, player_id_0_request);
-
- auto invalid_id_rsp = SetBrowsedPlayerResponseBuilder::MakeBuilder(
- Status::INVALID_PLAYER_ID, 0x0000, 0, 0, "");
- EXPECT_CALL(response_cb,
- Call(2, true, matchPacket(std::move(invalid_id_rsp))))
- .Times(1);
-
- SendBrowseMessage(2, player_id_0_request);
-
- auto response = SetBrowsedPlayerResponseBuilder::MakeBuilder(
- Status::NO_ERROR, 0x0000, 2, 0, "");
- EXPECT_CALL(response_cb, Call(3, true, matchPacket(std::move(response))))
- .Times(1);
-
- SendBrowseMessage(3, player_id_0_request);
-}
-
TEST_F(AvrcpDeviceTest, volumeChangedTest) {
MockMediaInterface interface;
NiceMock<MockA2dpInterface> a2dp_interface;
@@ -1552,7 +1333,6 @@ TEST_F(AvrcpDeviceTest, getInvalidItemAttributesTest) {
compare_to_full->AddAttributeEntry(Attribute::TOTAL_NUMBER_OF_TRACKS, "2");
compare_to_full->AddAttributeEntry(Attribute::GENRE, "Test Genre");
compare_to_full->AddAttributeEntry(Attribute::PLAYING_TIME, "1000");
- compare_to_full->AddAttributeEntry(Attribute::DEFAULT_COVER_ART, "0000001");
EXPECT_CALL(response_cb,
Call(1, true, matchPacket(std::move(compare_to_full))))
.Times(1);
diff --git a/profile/avrcp/tests/avrcp_test_helper.h b/profile/avrcp/tests/avrcp_test_helper.h
index a5411241a..edf35927e 100644
--- a/profile/avrcp/tests/avrcp_test_helper.h
+++ b/profile/avrcp/tests/avrcp_test_helper.h
@@ -58,10 +58,8 @@ class MockVolumeInterface : public VolumeInterface {
class MockAvrcpInterface : public AvrcpInterface {
public:
- MOCK_METHOD0(GetAvrcpVersion, uint16_t(void));
- MOCK_METHOD8(AddRecord, uint16_t(uint16_t, const char*, const char*, uint16_t,
- uint32_t, bool, uint16_t, uint16_t));
- MOCK_METHOD1(RemoveRecord, uint16_t(uint32_t));
+ MOCK_METHOD7(AddRecord, uint16_t(uint16_t, const char*, const char*, uint16_t,
+ uint32_t, bool, uint16_t));
MOCK_METHOD4(FindService, uint16_t(uint16_t, const RawAddress&,
tAVRC_SDP_DB_PARAMS*, tAVRC_FIND_CBACK));
MOCK_METHOD3(Open, uint16_t(uint8_t*, tAVRC_CONN_CB*, const RawAddress&));
diff --git a/profile/sdp/Android.bp b/profile/sdp/Android.bp
index 2811d5389..5abd77b53 100644
--- a/profile/sdp/Android.bp
+++ b/profile/sdp/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "sdp_service",
defaults: [
diff --git a/proto/Android.bp b/proto/Android.bp
new file mode 100644
index 000000000..ccd2b3b3b
--- /dev/null
+++ b/proto/Android.bp
@@ -0,0 +1,24 @@
+java_library_static {
+ name: "bluetooth-protos-lite",
+ host_supported: true,
+ proto: {
+ type: "lite",
+ },
+ srcs: [
+ "bluetooth/metrics/bluetooth.proto",
+ "bluetooth/bluetoothKeystore/keystore.proto",
+ ],
+}
+
+cc_library_static {
+ name: "libbt-protos-lite",
+ host_supported: true,
+ proto: {
+ export_proto_headers: true,
+ type: "lite",
+ },
+ srcs: [
+ "bluetooth/metrics/bluetooth.proto",
+ "bluetooth/bluetoothKeystore/keystore.proto",
+ ],
+}
diff --git a/gd/proto/bluetooth/bluetoothKeystore/keystore.proto b/proto/bluetooth/bluetoothKeystore/keystore.proto
index d0e418bd2..fd4416d1f 100644
--- a/gd/proto/bluetooth/bluetoothKeystore/keystore.proto
+++ b/proto/bluetooth/bluetoothKeystore/keystore.proto
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2018 The Android Open Source Project
+ * Copyright (C) 2020 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -16,6 +16,8 @@
syntax = "proto2";
+option optimize_for = LITE_RUNTIME;
+
// C++ namespace: bluetooth::metrics::BluetoothMetricsProto
package bluetooth.keystore.BluetoothKeystoreProto;
diff --git a/gd/proto/bluetooth/metrics/bluetooth.proto b/proto/bluetooth/metrics/bluetooth.proto
index 676798782..b1e28c3b2 100644
--- a/gd/proto/bluetooth/metrics/bluetooth.proto
+++ b/proto/bluetooth/metrics/bluetooth.proto
@@ -16,6 +16,8 @@
syntax = "proto2";
+option optimize_for = LITE_RUNTIME;
+
// C++ namespace: bluetooth::metrics::BluetoothMetricsProto
package bluetooth.metrics.BluetoothMetricsProto;
@@ -179,7 +181,8 @@ message PairEvent {
optional int32 disconnect_reason = 1;
// Pair event time
- optional int64 event_time_millis = 2; // [(datapol.semantic_type) = ST_TIMESTAMP];
+ optional int64 event_time_millis =
+ 2; // [(datapol.semantic_type) = ST_TIMESTAMP];
// The information about the device which it is paired to.
optional DeviceInfo device_paired_with = 3;
@@ -206,7 +209,8 @@ message WakeEvent {
optional string name = 3;
// Time of the event.
- optional int64 event_time_millis = 4; // [(datapol.semantic_type) = ST_TIMESTAMP];
+ optional int64 event_time_millis =
+ 4; // [(datapol.semantic_type) = ST_TIMESTAMP];
}
message ScanEvent {
@@ -243,7 +247,8 @@ message ScanEvent {
optional int32 number_results = 4;
// Time of the event.
- optional int64 event_time_millis = 5; // [(datapol.semantic_type) = ST_TIMESTAMP];
+ optional int64 event_time_millis =
+ 5; // [(datapol.semantic_type) = ST_TIMESTAMP];
}
// Profile IDs defined in BluetoothProfile API class
diff --git a/rustfmt.toml b/rustfmt.toml
deleted file mode 100644
index 98f92fbb1..000000000
--- a/rustfmt.toml
+++ /dev/null
@@ -1 +0,0 @@
-../../build/soong/scripts/rustfmt.toml
diff --git a/service/Android.bp b/service/Android.bp
index 130b65309..2760b5bcc 100644
--- a/service/Android.bp
+++ b/service/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
subdirs = [
"common",
]
@@ -139,9 +130,6 @@ cc_test {
],
host_supported: true,
- test_options: {
- unit_test: true,
- },
target: {
// This includes Binder related tests that can only be run
// on target.
diff --git a/service/BUILD.gn b/service/BUILD.gn
index 83f92d348..59acb167c 100644
--- a/service/BUILD.gn
+++ b/service/BUILD.gn
@@ -14,70 +14,13 @@
# limitations under the License.
#
-config("service_config") {
- include_dirs = [
- "//bt/",
- "//bt/linux_include",
- "//bt/include",
- "//bt/service",
- "//bt/service/common",
- ]
-
- configs = [ "//bt:target_defaults" ]
-}
-
-source_set("service_daemon_src") {
+source_set("service") {
sources = [
"a2dp_sink.cc",
"a2dp_source.cc",
"adapter.cc",
"avrcp_control.cc",
"avrcp_target.cc",
- "daemon.cc",
- "gatt_client.cc",
- "gatt_server.cc",
- "gatt_server_old.cc",
- "hal/bluetooth_av_interface.cc",
- "hal/bluetooth_avrcp_interface.cc",
- "hal/bluetooth_gatt_interface.cc",
- "hal/bluetooth_interface.cc",
- "ipc/ipc_handler.cc",
- "ipc/ipc_manager.cc",
- "logging_helpers.cc",
- "low_energy_advertiser.cc",
- "low_energy_client.cc",
- "low_energy_scanner.cc",
- "settings.cc",
- ]
-
- deps = [
- "//bt/gd/rust/shim:init_flags_bridge_header",
- "//bt/osi",
- "//bt/types",
- ]
-
- configs += [ ":service_config" ]
-}
-
-source_set("service_linux_src") {
- sources = [
- "ipc/ipc_handler_linux.cc",
- "ipc/linux_ipc_host.cc",
- "ipc/dbus/ipc_handler_dbus.cc",
- "ipc/dbus/bluetooth_adapter.cc",
- ]
-
- deps = [
- "//bt/gd/rust/shim:init_flags_bridge_header",
- "//bt/osi",
- "//bt/types",
- ]
-
- configs += [ ":service_config" ]
-}
-
-static_library("service") {
- sources = [
"common/bluetooth/a2dp_codec_config.cc",
"common/bluetooth/adapter_state.cc",
"common/bluetooth/advertise_data.cc",
@@ -93,79 +36,78 @@ static_library("service") {
"common/bluetooth/scan_settings.cc",
"common/bluetooth/service.cc",
"common/bluetooth/util/atomic_string.cc",
+ "daemon.cc",
+ "gatt_client.cc",
+ "gatt_server.cc",
+ "gatt_server_old.cc",
+ "hal/bluetooth_gatt_interface.cc",
+ "hal/bluetooth_interface.cc",
+ "ipc/dbus/bluetooth_adapter.cc",
+ "ipc/dbus/ipc_handler_dbus.cc",
+ "hal/bluetooth_av_interface.cc",
+ "hal/bluetooth_avrcp_interface.cc",
+ "hal/fake_bluetooth_gatt_interface.cc",
+ "hal/fake_bluetooth_interface.cc",
+ "ipc/ipc_handler.cc",
+ "ipc/ipc_handler_linux.cc",
+ "ipc/ipc_manager.cc",
+ "ipc/linux_ipc_host.cc",
+ "logging_helpers.cc",
+ "low_energy_advertiser.cc",
+ "low_energy_scanner.cc",
+ "low_energy_client.cc",
+ "settings.cc",
]
- deps = [
- ":service_daemon_src",
- ":service_linux_src",
- "//bt/gd/rust/shim:init_flags_bridge_header",
- "//bt/osi",
- "//bt/types",
+ include_dirs = [
+ "//",
+ "//linux_include",
+ "//include",
+ "//service/common",
+ "//third_party/modp_b64/modp64",
]
- configs += [ ":service_config" ]
+ deps = [
+ "//types",
+ "//osi",
+ "//third_party/libchrome:base",
+ ]
}
executable("bluetoothtbd") {
- sources = [ "main.cc" ]
+ sources = [
+ "main.cc",
+ ]
deps = [
":service",
- "//bt/btcore",
- "//bt/main:bluetooth",
+ "//btcore",
+ "//third_party/libchrome:base",
+ "//third_party/modp_b64",
]
- configs += [ ":service_config" ]
+ include_dirs = [ "//" ]
libs = [
- "dl",
- "pthread",
- "rt",
- "bt_shim_ffi",
- "ssl",
- "crypto",
- ]
-
- lib_dirs = [
- "${root_out_dir}/rust"
+ "-ldl",
+ "-lpthread",
+ "-lrt",
]
}
-if (use.test) {
- source_set("service_base_test_src") {
- sources = [
- "hal/fake_bluetooth_av_interface.cc",
- "hal/fake_bluetooth_gatt_interface.cc",
- "hal/fake_bluetooth_interface.cc",
- "test/a2dp_sink_unittest.cc",
- "test/a2dp_source_unittest.cc",
- "test/adapter_unittest.cc",
- "test/advertise_data_unittest.cc",
- "test/fake_hal_util.cc",
- "test/gatt_client_unittest.cc",
- "test/gatt_server_unittest.cc",
- "test/low_energy_advertiser_unittest.cc",
- "test/low_energy_client_unittest.cc",
- "test/low_energy_scanner_unittest.cc",
- "test/settings_unittest.cc",
- ]
-
- configs += [ ":service_config" ]
- }
-
- executable("bluetoothtbd_test") {
- sources = [ "test/main.cc" ]
+executable("service_unittests") {
+ testonly = true
+ sources = [
+ "test/fake_hal_util.cc",
+ "test/settings_unittest.cc",
+ ]
- deps = [
- ":service_base_test_src",
- ":service_daemon_src",
- ":service_linux_src",
- "//bt/service/common:libbluetooth_common",
- ]
+ include_dirs = [ "//" ]
- configs += [
- "//bt:external_gmock_main",
- ":service_config",
- ]
- }
+ deps = [
+ ":service",
+ "//third_party/googletest:gmock_main",
+ "//third_party/libchrome:base",
+ "//third_party/modp_b64",
+ ]
}
diff --git a/service/adapter.cc b/service/adapter.cc
index 65e58e878..4d414dddc 100644
--- a/service/adapter.cc
+++ b/service/adapter.cc
@@ -24,7 +24,6 @@
#include <base/logging.h>
#include <base/observer_list.h>
-#include "abstract_observer_list.h"
#include "service/a2dp_sink.h"
#include "service/a2dp_source.h"
#include "service/avrcp_control.h"
@@ -552,11 +551,9 @@ class AdapterImpl : public Adapter, public hal::BluetoothInterface::Observer {
}
case BT_PROPERTY_BDNAME: {
bt_bdname_t* hal_name = reinterpret_cast<bt_bdname_t*>(property->val);
- if (hal_name) {
- std::string name = reinterpret_cast<char*>(hal_name->name);
- LOG(INFO) << "Adapter name changed: " << name;
- name_.Set(name);
- }
+ std::string name = reinterpret_cast<char*>(hal_name->name);
+ LOG(INFO) << "Adapter name changed: " << name;
+ name_.Set(name);
break;
}
case BT_PROPERTY_LOCAL_LE_FEATURES: {
@@ -685,8 +682,7 @@ class AdapterImpl : public Adapter, public hal::BluetoothInterface::Observer {
void AclStateChangedCallback(bt_status_t status,
const RawAddress& remote_bdaddr,
- bt_acl_state_t state,
- bt_hci_error_code_t hci_reason) override {
+ bt_acl_state_t state) override {
std::string device_address = BtAddrString(&remote_bdaddr);
bool connected = (state == BT_ACL_STATE_CONNECTED);
LOG(INFO) << "ACL state changed: " << device_address
@@ -765,7 +761,7 @@ class AdapterImpl : public Adapter, public hal::BluetoothInterface::Observer {
// List of observers that are interested in notifications from us.
std::mutex observers_lock_;
- btbase::AbstractObserverList<Adapter::Observer> observers_;
+ base::ObserverList<Adapter::Observer> observers_;
// List of devices addresses that are currently connected.
std::mutex connected_devices_lock_;
diff --git a/service/avrcp_target.cc b/service/avrcp_target.cc
index 264945a51..fb63fba38 100644
--- a/service/avrcp_target.cc
+++ b/service/avrcp_target.cc
@@ -26,7 +26,6 @@
#include "base/memory/ptr_util.h"
#include "service/logging_helpers.h"
-#include "array_utils.h"
#include "stack/include/avrc_defs.h"
#define PARSE_ADDR(str) \
@@ -158,7 +157,7 @@ bool AvrcpTarget::GetPlayerAppValueResponse(
const std::string& str_addr, const std::vector<AvrcpIntValue>& values) {
RawAddress addr = PARSE_ADDR(str_addr);
btrc_player_settings_t btrc_values;
- if (values.size() >= ARRAY_SIZE(btrc_values.attr_ids)) {
+ if (values.size() >= arraysize(btrc_values.attr_ids)) {
LOG(ERROR) << "Too many attribute values";
return false;
}
diff --git a/service/common/Android.bp b/service/common/Android.bp
index 4d5b70592..e3bde74af 100644
--- a/service/common/Android.bp
+++ b/service/common/Android.bp
@@ -1,13 +1,4 @@
// Bluetooth types
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "libbluetooth-common",
defaults: ["fluoride_defaults"],
diff --git a/service/common/BUILD.gn b/service/common/BUILD.gn
deleted file mode 100644
index 2aee90b64..000000000
--- a/service/common/BUILD.gn
+++ /dev/null
@@ -1,42 +0,0 @@
-#
-# Copyright 2021 Google
-#
-# Licensed under the Apache License, Version 2.0 (the "License");
-# you may not use this file except in compliance with the License.
-# You may obtain a copy of the License at:
-#
-# http://www.apache.org/licenses/LICENSE-2.0
-#
-# Unless required by applicable law or agreed to in writing, software
-# distributed under the License is distributed on an "AS IS" BASIS,
-# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-# See the License for the specific language governing permissions and
-# limitations under the License.
-#
-
-source_set("libbluetooth_common") {
- sources = [
- "bluetooth/a2dp_codec_config.cc",
- "bluetooth/adapter_state.cc",
- "bluetooth/advertise_data.cc",
- "bluetooth/advertise_settings.cc",
- "bluetooth/avrcp_int_value.cc",
- "bluetooth/avrcp_media_attr.cc",
- "bluetooth/avrcp_register_notification_response.cc",
- "bluetooth/characteristic.cc",
- "bluetooth/descriptor.cc",
- "bluetooth/remote_device_props.cc",
- "bluetooth/scan_filter.cc",
- "bluetooth/scan_result.cc",
- "bluetooth/scan_settings.cc",
- "bluetooth/service.cc",
- "bluetooth/util/atomic_string.cc",
- ]
-
- include_dirs = [
- ".",
- "//bt",
- ]
-
- configs += ["//bt:target_defaults"]
-}
diff --git a/service/common/android/bluetooth/scan_filter.cc b/service/common/android/bluetooth/scan_filter.cc
index ad8bea64b..12d248af6 100644
--- a/service/common/android/bluetooth/scan_filter.cc
+++ b/service/common/android/bluetooth/scan_filter.cc
@@ -41,19 +41,28 @@ status_t ScanFilter::writeToParcel(Parcel* parcel) const {
// TODO(jpawlowski) make type casting nicer
// uuid won't really keep ownership, it's just for type casting
- std::optional<UUID> uuid;
+ std::unique_ptr<UUID> uuid;
+ UUID tmp;
if (service_uuid_) {
- uuid = *service_uuid_;
+ tmp = *service_uuid_;
+ uuid.reset(&tmp);
+ } else {
+ uuid.reset(nullptr);
}
status = parcel->writeNullableParcelable(uuid);
+ uuid.release();
if (status != OK) return status;
- uuid.reset();
if (service_uuid_mask_) {
- uuid = *service_uuid_mask_;
+ tmp = *service_uuid_mask_;
+ uuid.reset(&tmp);
+ } else {
+ uuid.reset(nullptr);
}
status = parcel->writeNullableParcelable(uuid);
+ uuid.release();
+
return status;
}
diff --git a/service/daemon.cc b/service/daemon.cc
index 4cd384285..439c2c2fa 100644
--- a/service/daemon.cc
+++ b/service/daemon.cc
@@ -21,7 +21,6 @@
#include <base/logging.h>
#include <base/run_loop.h>
-#include "abstract_message_loop.h"
#include "service/adapter.h"
#include "service/hal/bluetooth_av_interface.h"
#include "service/hal/bluetooth_avrcp_interface.h"
@@ -52,7 +51,7 @@ class DaemonImpl : public Daemon, public ipc::IPCManager::Delegate {
Settings* GetSettings() const override { return settings_.get(); }
- btbase::AbstractMessageLoop* GetMessageLoop() const override {
+ base::MessageLoop* GetMessageLoop() const override {
return message_loop_.get();
}
@@ -129,7 +128,7 @@ class DaemonImpl : public Daemon, public ipc::IPCManager::Delegate {
bool Init() override {
CHECK(!initialized_);
- message_loop_.reset(new btbase::AbstractMessageLoop());
+ message_loop_.reset(new base::MessageLoop());
settings_.reset(new Settings());
if (!settings_->Init()) {
@@ -157,7 +156,7 @@ class DaemonImpl : public Daemon, public ipc::IPCManager::Delegate {
}
bool initialized_;
- std::unique_ptr<btbase::AbstractMessageLoop> message_loop_;
+ std::unique_ptr<base::MessageLoop> message_loop_;
std::unique_ptr<Settings> settings_;
std::unique_ptr<Adapter> adapter_;
std::unique_ptr<ipc::IPCManager> ipc_manager_;
diff --git a/service/daemon.h b/service/daemon.h
index 06afe9100..0d6474b65 100644
--- a/service/daemon.h
+++ b/service/daemon.h
@@ -17,7 +17,7 @@
#pragma once
#include <base/macros.h>
-#include "abstract_message_loop.h"
+#include <base/message_loop/message_loop.h>
namespace ipc {
class IPCManager;
@@ -55,7 +55,7 @@ class Daemon {
// The main event loop. This should be used for any events and delayed tasks
// that should be executed on the daemon's main thread.
- virtual btbase::AbstractMessageLoop* GetMessageLoop() const = 0;
+ virtual base::MessageLoop* GetMessageLoop() const = 0;
// Starts the daemon's main loop.
virtual void StartMainLoop() = 0;
diff --git a/service/example/heart_rate/server_main.cc b/service/example/heart_rate/server_main.cc
index f8953f16a..7423462f0 100644
--- a/service/example/heart_rate/server_main.cc
+++ b/service/example/heart_rate/server_main.cc
@@ -19,6 +19,7 @@
#include <base/command_line.h>
#include <base/location.h>
#include <base/logging.h>
+#include <base/message_loop/message_loop.h>
#include <base/run_loop.h>
#include <binder/IPCThreadState.h>
@@ -27,7 +28,6 @@
#include <android/bluetooth/IBluetooth.h>
-#include "abstract_message_loop.h"
#include "heart_rate_server.h"
using android::sp;
@@ -85,7 +85,7 @@ int main(int argc, char* argv[]) {
// Set up a message loop so that we can schedule timed Heart Rate
// notifications.
- btbase::AbstractMessageLoop main_loop;
+ base::MessageLoop main_loop;
LOG(INFO) << "Starting GATT Heart Rate Service sample";
diff --git a/service/gatt_client.cc b/service/gatt_client.cc
index 2c09fa5e0..629b82af9 100644
--- a/service/gatt_client.cc
+++ b/service/gatt_client.cc
@@ -67,8 +67,7 @@ bool GattClientFactory::RegisterInstance(const Uuid& uuid,
const btgatt_client_interface_t* hal_iface =
hal::BluetoothGattInterface::Get()->GetClientHALInterface();
- if (hal_iface->register_client(uuid, false) != BT_STATUS_SUCCESS)
- return false;
+ if (hal_iface->register_client(uuid) != BT_STATUS_SUCCESS) return false;
pending_calls_[uuid] = callback;
diff --git a/service/gatt_server.cc b/service/gatt_server.cc
index ac2996bf0..f911f548c 100644
--- a/service/gatt_server.cc
+++ b/service/gatt_server.cc
@@ -590,8 +590,7 @@ bool GattServerFactory::RegisterInstance(const Uuid& uuid,
const btgatt_server_interface_t* hal_iface =
hal::BluetoothGattInterface::Get()->GetServerHALInterface();
- if (hal_iface->register_server(uuid, false) != BT_STATUS_SUCCESS)
- return false;
+ if (hal_iface->register_server(uuid) != BT_STATUS_SUCCESS) return false;
pending_calls_[uuid] = callback;
diff --git a/service/gatt_server_old.cc b/service/gatt_server_old.cc
index d72be583c..cfc394c34 100644
--- a/service/gatt_server_old.cc
+++ b/service/gatt_server_old.cc
@@ -131,7 +131,7 @@ namespace {
/** Callback invoked in response to register_server */
void RegisterServerCallback(int status, int server_if,
const bluetooth::Uuid& app_uuid) {
- LOG_INFO("%s: status:%d server_if:%d app_uuid:%p", __func__, status,
+ LOG_INFO(LOG_TAG, "%s: status:%d server_if:%d app_uuid:%p", __func__, status,
server_if, &app_uuid);
g_internal->server_if = server_if;
@@ -144,8 +144,9 @@ void RegisterServerCallback(int status, int server_if,
void ServiceAddedCallback(int status, int server_if,
std::vector<btgatt_db_element_t> service) {
- LOG_INFO("%s: status:%d server_if:%d count:%zu svc_handle:%d", __func__,
- status, server_if, service.size(), service[0].attribute_handle);
+ LOG_INFO(LOG_TAG, "%s: status:%d server_if:%d count:%zu svc_handle:%d",
+ __func__, status, server_if, service.size(),
+ service[0].attribute_handle);
std::lock_guard<std::mutex> lock(g_internal->lock);
g_internal->server_if = server_if;
@@ -157,12 +158,12 @@ void ServiceAddedCallback(int status, int server_if,
for (size_t i = 1; i < service.size(); i++) {
const btgatt_db_element_t& el = service[i];
if (el.type == BTGATT_DB_DESCRIPTOR) {
- LOG_INFO("%s: descr_handle:%d", __func__, el.attribute_handle);
+ LOG_INFO(LOG_TAG, "%s: descr_handle:%d", __func__, el.attribute_handle);
} else if (el.type == BTGATT_DB_CHARACTERISTIC) {
bluetooth::Uuid id(el.uuid);
uint16_t char_handle = el.attribute_handle;
- LOG_INFO("%s: char_handle:%d", __func__, char_handle);
+ LOG_INFO(LOG_TAG, "%s: char_handle:%d", __func__, char_handle);
g_internal->uuid_to_attribute[id] = char_handle;
g_internal->characteristics[char_handle].uuid = id;
@@ -199,10 +200,9 @@ void ServiceAddedCallback(int status, int server_if,
// It must be different than any other registered Uuid.
bluetooth::Uuid client_id = bluetooth::Uuid::GetRandom();
- bt_status_t btstat =
- g_internal->gatt->client->register_client(client_id, false);
+ bt_status_t btstat = g_internal->gatt->client->register_client(client_id);
if (btstat != BT_STATUS_SUCCESS) {
- LOG_ERROR("%s: Failed to register client", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Failed to register client", __func__);
}
}
@@ -227,11 +227,11 @@ void RequestReadCallback(int conn_id, int trans_id, const RawAddress& bda,
const size_t attribute_size = std::min(kMaxGattAttributeSize, blob_remaining);
std::string addr(BtAddrString(&bda));
- LOG_INFO(
- "%s: connection:%d (%s) reading attr:%d attribute_offset_octets:%d "
- "blob_section:%u (is_long:%u)",
- __func__, conn_id, addr.c_str(), attr_handle, attribute_offset_octets,
- ch.blob_section, is_long);
+ LOG_INFO(LOG_TAG,
+ "%s: connection:%d (%s) reading attr:%d attribute_offset_octets:%d "
+ "blob_section:%u (is_long:%u)",
+ __func__, conn_id, addr.c_str(), attr_handle,
+ attribute_offset_octets, ch.blob_section, is_long);
btgatt_response_t response;
response.attr_value.len = 0;
@@ -253,12 +253,12 @@ void RequestWriteCallback(int conn_id, int trans_id, const RawAddress& bda,
int attr_handle, int attribute_offset, bool need_rsp,
bool is_prep, std::vector<uint8_t> value) {
std::string addr(BtAddrString(&bda));
- LOG_INFO(
- "%s: connection:%d (%s:trans:%d) write attr:%d attribute_offset:%d "
- "length:%zu "
- "need_resp:%u is_prep:%u",
- __func__, conn_id, addr.c_str(), trans_id, attr_handle, attribute_offset,
- value.size(), need_rsp, is_prep);
+ LOG_INFO(LOG_TAG,
+ "%s: connection:%d (%s:trans:%d) write attr:%d attribute_offset:%d "
+ "length:%zu "
+ "need_resp:%u is_prep:%u",
+ __func__, conn_id, addr.c_str(), trans_id, attr_handle,
+ attribute_offset, value.size(), need_rsp, is_prep);
std::lock_guard<std::mutex> lock(g_internal->lock);
@@ -274,7 +274,7 @@ void RequestWriteCallback(int conn_id, int trans_id, const RawAddress& bda,
if (target_blob != g_internal->controlled_blobs.end() &&
ch.blob.size() == 1u) {
g_internal->characteristics[target_blob->second].blob_section = ch.blob[0];
- LOG_INFO("%s: updating attribute %d blob_section to %u", __func__,
+ LOG_INFO(LOG_TAG, "%s: updating attribute %d blob_section to %u", __func__,
target_blob->second, ch.blob[0]);
} else if (!is_prep) {
// This is a single frame characteristic write.
@@ -284,7 +284,7 @@ void RequestWriteCallback(int conn_id, int trans_id, const RawAddress& bda,
OSI_NO_INTR(status = write(g_internal->pipefd[kPipeWriteEnd],
attr_uuid.data(), attr_uuid.size()));
if (-1 == status)
- LOG_ERROR("%s: write failed: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s: write failed: %s", __func__, strerror(errno));
} else {
// This is a multi-frame characteristic write.
// Wait for an 'RequestExecWriteCallback' to notify completion.
@@ -308,8 +308,8 @@ void RequestWriteCallback(int conn_id, int trans_id, const RawAddress& bda,
void RequestExecWriteCallback(int conn_id, int trans_id, const RawAddress& bda,
int exec_write) {
std::string addr(BtAddrString(&bda));
- LOG_INFO("%s: connection:%d (%s:trans:%d) exec_write:%d", __func__, conn_id,
- addr.c_str(), trans_id, exec_write);
+ LOG_INFO(LOG_TAG, "%s: connection:%d (%s:trans:%d) exec_write:%d", __func__,
+ conn_id, addr.c_str(), trans_id, exec_write);
// This 'response' data is unused for ExecWriteResponses.
// It is only used to pass BlueDroid argument validation.
@@ -325,14 +325,14 @@ void RequestExecWriteCallback(int conn_id, int trans_id, const RawAddress& bda,
OSI_NO_INTR(status = write(g_internal->pipefd[kPipeWriteEnd], uuid.data(),
uuid.size()));
if (-1 == status)
- LOG_ERROR("%s: write failed: %s", __func__, strerror(errno));
+ LOG_ERROR(LOG_TAG, "%s: write failed: %s", __func__, strerror(errno));
}
void ConnectionCallback(int conn_id, int server_if, int connected,
const RawAddress& bda) {
std::string addr(BtAddrString(&bda));
- LOG_INFO("%s: connection:%d server_if:%d connected:%d addr:%s", __func__,
- conn_id, server_if, connected, addr.c_str());
+ LOG_INFO(LOG_TAG, "%s: connection:%d server_if:%d connected:%d addr:%s",
+ __func__, conn_id, server_if, connected, addr.c_str());
if (connected == 1) {
g_internal->connections.insert(conn_id);
} else if (connected == 0) {
@@ -341,7 +341,7 @@ void ConnectionCallback(int conn_id, int server_if, int connected,
}
void EnableAdvertisingCallback(uint8_t status) {
- LOG_INFO("%s: status:%d", __func__, status);
+ LOG_INFO(LOG_TAG, "%s: status:%d", __func__, status);
// This terminates a Start call.
std::lock_guard<std::mutex> lock(g_internal->lock);
g_internal->api_synchronize.notify_one();
@@ -349,8 +349,8 @@ void EnableAdvertisingCallback(uint8_t status) {
void RegisterClientCallback(int status, int client_if,
const bluetooth::Uuid& app_uuid) {
- LOG_INFO("%s: status:%d client_if:%d uuid[0]:%s", __func__, status, client_if,
- app_uuid.ToString().c_str());
+ LOG_INFO(LOG_TAG, "%s: status:%d client_if:%d uuid[0]:%s", __func__, status,
+ client_if, app_uuid.ToString().c_str());
g_internal->client_if = client_if;
// Setup our advertisement. This has no callback.
@@ -364,8 +364,8 @@ void RegisterClientCallback(int status, int client_if,
}
void ServiceStoppedCallback(int status, int server_if, int srvc_handle) {
- LOG_INFO("%s: status:%d server_if:%d srvc_handle:%d", __func__, status,
- server_if, srvc_handle);
+ LOG_INFO(LOG_TAG, "%s: status:%d server_if:%d srvc_handle:%d", __func__,
+ status, server_if, srvc_handle);
// This terminates a Stop call.
// TODO(icoolidge): make this symmetric with start
std::lock_guard<std::mutex> lock(g_internal->lock);
@@ -386,15 +386,15 @@ void ScanResultCallback(uint16_t ble_evt_type, uint8_t addr_type,
void ClientConnectCallback(int conn_id, int status, int client_if,
const RawAddress& bda) {
std::string addr(BtAddrString(&bda));
- LOG_INFO("%s: conn_id:%d status:%d client_if:%d %s", __func__, conn_id,
- status, client_if, addr.c_str());
+ LOG_INFO(LOG_TAG, "%s: conn_id:%d status:%d client_if:%d %s", __func__,
+ conn_id, status, client_if, addr.c_str());
}
void ClientDisconnectCallback(int conn_id, int status, int client_if,
const RawAddress& bda) {
std::string addr(BtAddrString(&bda));
- LOG_INFO("%s: conn_id:%d status:%d client_if:%d %s", __func__, conn_id,
- status, client_if, addr.c_str());
+ LOG_INFO(LOG_TAG, "%s: conn_id:%d status:%d client_if:%d %s", __func__,
+ conn_id, status, client_if, addr.c_str());
}
void IndicationSentCallback(UNUSED_ATTR int conn_id, UNUSED_ATTR int status) {
@@ -447,7 +447,6 @@ const btgatt_client_callbacks_t gatt_client_callbacks = {
nullptr, /* services_added_cb */
nullptr, /* phy_update_cb */
nullptr, /* conn_update_cb */
- nullptr, /* service_changed_cb*/
};
const btgatt_scanner_callbacks_t gatt_scanner_callbacks = {
@@ -483,19 +482,19 @@ int ServerInternals::Initialize() {
gatt = reinterpret_cast<const btgatt_interface_t*>(
bt_iface->get_profile_interface(BT_PROFILE_GATT_ID));
if (!gatt) {
- LOG_ERROR("Error getting GATT interface");
+ LOG_ERROR(LOG_TAG, "Error getting GATT interface");
return -1;
}
bt_status_t btstat = gatt->init(&gatt_callbacks);
if (btstat != BT_STATUS_SUCCESS) {
- LOG_ERROR("Failed to initialize gatt interface");
+ LOG_ERROR(LOG_TAG, "Failed to initialize gatt interface");
return -1;
}
int status = pipe(pipefd);
if (status == -1) {
- LOG_ERROR("pipe creation failed: %s", strerror(errno));
+ LOG_ERROR(LOG_TAG, "pipe creation failed: %s", strerror(errno));
return -1;
}
@@ -535,7 +534,7 @@ Server::~Server() {}
bool Server::Initialize(const Uuid& service_id, int* gatt_pipe) {
internal_.reset(new ServerInternals);
if (!internal_) {
- LOG_ERROR("Error creating internals");
+ LOG_ERROR(LOG_TAG, "Error creating internals");
return false;
}
g_internal = internal_.get();
@@ -543,26 +542,25 @@ bool Server::Initialize(const Uuid& service_id, int* gatt_pipe) {
std::unique_lock<std::mutex> lock(internal_->lock);
int status = internal_->Initialize();
if (status) {
- LOG_ERROR("Error initializing internals");
+ LOG_ERROR(LOG_TAG, "Error initializing internals");
return false;
}
- bt_status_t btstat =
- internal_->gatt->server->register_server(service_id, false);
+ bt_status_t btstat = internal_->gatt->server->register_server(service_id);
if (btstat != BT_STATUS_SUCCESS) {
- LOG_ERROR("Failed to register server");
+ LOG_ERROR(LOG_TAG, "Failed to register server");
return false;
}
internal_->api_synchronize.wait(lock);
// TODO(icoolidge): Better error handling.
if (internal_->server_if == 0) {
- LOG_ERROR("Initialization of server failed");
+ LOG_ERROR(LOG_TAG, "Initialization of server failed");
return false;
}
*gatt_pipe = internal_->pipefd[kPipeReadEnd];
- LOG_INFO("Server Initialize succeeded");
+ LOG_INFO(LOG_TAG, "Server Initialize succeeded");
return true;
}
@@ -626,7 +624,7 @@ bool Server::AddCharacteristic(const Uuid& id, int properties,
bt_status_t btstat =
internal_->AddCharacteristic(id, properties, permissions);
if (btstat != BT_STATUS_SUCCESS) {
- LOG_ERROR("Failed to add characteristic to service: 0x%04x",
+ LOG_ERROR(LOG_TAG, "Failed to add characteristic to service: 0x%04x",
internal_->service_handle);
return false;
}
@@ -644,7 +642,7 @@ bool Server::AddBlob(const Uuid& id, const Uuid& control_id, int properties,
bt_status_t btstat =
internal_->AddCharacteristic(id, properties, permissions);
if (btstat != BT_STATUS_SUCCESS) {
- LOG_ERROR("Failed to set scan response data");
+ LOG_ERROR(LOG_TAG, "Failed to set scan response data");
return false;
}
@@ -664,7 +662,7 @@ bool Server::Start() {
bt_status_t btstat = internal_->gatt->server->add_service(
internal_->server_if, pending_svc_decl);
if (btstat != BT_STATUS_SUCCESS) {
- LOG_ERROR("Failed to start service with handle: 0x%04x",
+ LOG_ERROR(LOG_TAG, "Failed to start service with handle: 0x%04x",
internal_->service_handle);
return false;
}
@@ -677,7 +675,7 @@ bool Server::Stop() {
bt_status_t btstat = internal_->gatt->server->stop_service(
internal_->server_if, internal_->service_handle);
if (btstat != BT_STATUS_SUCCESS) {
- LOG_ERROR("Failed to stop service with handle: 0x%04x",
+ LOG_ERROR(LOG_TAG, "Failed to stop service with handle: 0x%04x",
internal_->service_handle);
return false;
}
diff --git a/service/hal/bluetooth_av_interface.cc b/service/hal/bluetooth_av_interface.cc
index 8dc868622..4700cce4e 100644
--- a/service/hal/bluetooth_av_interface.cc
+++ b/service/hal/bluetooth_av_interface.cc
@@ -22,7 +22,6 @@
#include <base/memory/ptr_util.h>
#include <base/observer_list.h>
-#include "abstract_observer_list.h"
#include "service/hal/bluetooth_interface.h"
namespace bluetooth {
@@ -42,9 +41,9 @@ using shared_mutex_impl = std::shared_timed_mutex;
// use unique_lock. If only accessing |g_interface| use shared lock.
shared_mutex_impl g_instance_lock;
-btbase::AbstractObserverList<BluetoothAvInterface::A2dpSourceObserver>*
+base::ObserverList<BluetoothAvInterface::A2dpSourceObserver>*
GetA2dpSourceObservers();
-btbase::AbstractObserverList<BluetoothAvInterface::A2dpSinkObserver>*
+base::ObserverList<BluetoothAvInterface::A2dpSinkObserver>*
GetA2dpSinkObservers();
#define VERIFY_INTERFACE_OR_RETURN(...) \
@@ -184,12 +183,7 @@ class BluetoothAvInterfaceImpl : public BluetoothAvInterface {
if (sink_enabled_) {
return true;
}
-
- // Right now we only support one connected audio device.
- int max_connected_audio_devices = 1;
- if (hal_sink_iface_->init(&av_sink_callbacks,
- max_connected_audio_devices) !=
- BT_STATUS_SUCCESS) {
+ if (hal_sink_iface_->init(&av_sink_callbacks) != BT_STATUS_SUCCESS) {
LOG(ERROR) << "Failed to initialize HAL A2DP sink interface";
return false;
}
@@ -256,17 +250,17 @@ class BluetoothAvInterfaceImpl : public BluetoothAvInterface {
return A2dpSinkEnable();
}
- btbase::AbstractObserverList<A2dpSourceObserver>* source_observers() {
+ base::ObserverList<A2dpSourceObserver>* source_observers() {
return &a2dp_source_observers_;
}
- btbase::AbstractObserverList<A2dpSinkObserver>* sink_observers() {
+ base::ObserverList<A2dpSinkObserver>* sink_observers() {
return &a2dp_sink_observers_;
}
private:
- btbase::AbstractObserverList<A2dpSourceObserver> a2dp_source_observers_;
- btbase::AbstractObserverList<A2dpSinkObserver> a2dp_sink_observers_;
+ base::ObserverList<A2dpSourceObserver> a2dp_source_observers_;
+ base::ObserverList<A2dpSinkObserver> a2dp_sink_observers_;
const btav_source_interface_t* hal_source_iface_ = nullptr;
const btav_sink_interface_t* hal_sink_iface_ = nullptr;
@@ -279,14 +273,14 @@ class BluetoothAvInterfaceImpl : public BluetoothAvInterface {
namespace {
-btbase::AbstractObserverList<BluetoothAvInterface::A2dpSourceObserver>*
+base::ObserverList<BluetoothAvInterface::A2dpSourceObserver>*
GetA2dpSourceObservers() {
CHECK(g_interface);
return static_cast<BluetoothAvInterfaceImpl*>(g_interface)
->source_observers();
}
-btbase::AbstractObserverList<BluetoothAvInterface::A2dpSinkObserver>*
+base::ObserverList<BluetoothAvInterface::A2dpSinkObserver>*
GetA2dpSinkObservers() {
CHECK(g_interface);
return static_cast<BluetoothAvInterfaceImpl*>(g_interface)->sink_observers();
diff --git a/service/hal/bluetooth_avrcp_interface.cc b/service/hal/bluetooth_avrcp_interface.cc
index 68746aec0..02e7316b1 100644
--- a/service/hal/bluetooth_avrcp_interface.cc
+++ b/service/hal/bluetooth_avrcp_interface.cc
@@ -22,7 +22,6 @@
#include <base/logging.h>
#include <base/observer_list.h>
-#include "abstract_observer_list.h"
#include "service/hal/bluetooth_interface.h"
#include "service/logging_helpers.h"
@@ -52,10 +51,10 @@ shared_mutex_impl g_instance_lock;
// Helper for obtaining the observer lists. This is forward declared here
// and defined below since it depends on BluetoothInterfaceImpl.
-btbase::AbstractObserverList<BluetoothAvrcpInterface::TargetObserver>*
+base::ObserverList<BluetoothAvrcpInterface::TargetObserver>*
GetTargetObservers();
-btbase::AbstractObserverList<BluetoothAvrcpInterface::ControlObserver>*
+base::ObserverList<BluetoothAvrcpInterface::ControlObserver>*
GetControlObservers();
#define VERIFY_INTERFACE_OR_RETURN() \
@@ -590,11 +589,11 @@ class BluetoothAvrcpInterfaceImpl : public BluetoothAvrcpInterface {
return AvrcpControlEnable();
}
- btbase::AbstractObserverList<TargetObserver>* target_observers() {
+ base::ObserverList<TargetObserver>* target_observers() {
return &target_observers_;
}
- btbase::AbstractObserverList<ControlObserver>* control_observers() {
+ base::ObserverList<ControlObserver>* control_observers() {
return &control_observers_;
}
@@ -603,8 +602,8 @@ class BluetoothAvrcpInterfaceImpl : public BluetoothAvrcpInterface {
// We're not using a base::ObserverListThreadSafe, which it posts observer
// events automatically on the origin threads, as we want to avoid that
// overhead and simply forward the events to the upper layer.
- btbase::AbstractObserverList<TargetObserver> target_observers_;
- btbase::AbstractObserverList<ControlObserver> control_observers_;
+ base::ObserverList<TargetObserver> target_observers_;
+ base::ObserverList<ControlObserver> control_observers_;
// The HAL handle obtained from the shared library. We hold a weak reference
// to this since the actual data resides in the shared Bluetooth library.
@@ -619,14 +618,14 @@ class BluetoothAvrcpInterfaceImpl : public BluetoothAvrcpInterface {
namespace {
-btbase::AbstractObserverList<BluetoothAvrcpInterface::TargetObserver>*
+base::ObserverList<BluetoothAvrcpInterface::TargetObserver>*
GetTargetObservers() {
CHECK(g_interface);
return static_cast<BluetoothAvrcpInterfaceImpl*>(g_interface)
->target_observers();
}
-btbase::AbstractObserverList<BluetoothAvrcpInterface::ControlObserver>*
+base::ObserverList<BluetoothAvrcpInterface::ControlObserver>*
GetControlObservers() {
CHECK(g_interface);
return static_cast<BluetoothAvrcpInterfaceImpl*>(g_interface)
diff --git a/service/hal/bluetooth_gatt_interface.cc b/service/hal/bluetooth_gatt_interface.cc
index 505f3fc1e..d61a2384e 100644
--- a/service/hal/bluetooth_gatt_interface.cc
+++ b/service/hal/bluetooth_gatt_interface.cc
@@ -22,7 +22,6 @@
#include <base/logging.h>
#include <base/observer_list.h>
-#include "abstract_observer_list.h"
#include "service/hal/bluetooth_interface.h"
#include "service/logging_helpers.h"
@@ -52,11 +51,11 @@ shared_mutex_impl g_instance_lock;
// Helper for obtaining the observer lists. This is forward declared here
// and defined below since it depends on BluetoothInterfaceImpl.
-btbase::AbstractObserverList<BluetoothGattInterface::ScannerObserver>*
+base::ObserverList<BluetoothGattInterface::ScannerObserver>*
GetScannerObservers();
-btbase::AbstractObserverList<BluetoothGattInterface::ClientObserver>*
+base::ObserverList<BluetoothGattInterface::ClientObserver>*
GetClientObservers();
-btbase::AbstractObserverList<BluetoothGattInterface::ServerObserver>*
+base::ObserverList<BluetoothGattInterface::ServerObserver>*
GetServerObservers();
#define FOR_EACH_SCANNER_OBSERVER(func) \
@@ -404,7 +403,6 @@ const btgatt_client_callbacks_t gatt_client_callbacks = {
ServicesAddedCallback,
nullptr,
nullptr,
- nullptr, // service_changed_cb
};
const btgatt_server_callbacks_t gatt_server_callbacks = {
@@ -507,15 +505,15 @@ class BluetoothGattInterfaceImpl : public BluetoothGattInterface {
return true;
}
- btbase::AbstractObserverList<ScannerObserver>* scanner_observers() {
+ base::ObserverList<ScannerObserver>* scanner_observers() {
return &scanner_observers_;
}
- btbase::AbstractObserverList<ClientObserver>* client_observers() {
+ base::ObserverList<ClientObserver>* client_observers() {
return &client_observers_;
}
- btbase::AbstractObserverList<ServerObserver>* server_observers() {
+ base::ObserverList<ServerObserver>* server_observers() {
return &server_observers_;
}
@@ -524,9 +522,9 @@ class BluetoothGattInterfaceImpl : public BluetoothGattInterface {
// We're not using a base::ObserverListThreadSafe, which it posts observer
// events automatically on the origin threads, as we want to avoid that
// overhead and simply forward the events to the upper layer.
- btbase::AbstractObserverList<ScannerObserver> scanner_observers_;
- btbase::AbstractObserverList<ClientObserver> client_observers_;
- btbase::AbstractObserverList<ServerObserver> server_observers_;
+ base::ObserverList<ScannerObserver> scanner_observers_;
+ base::ObserverList<ClientObserver> client_observers_;
+ base::ObserverList<ServerObserver> server_observers_;
// The HAL handle obtained from the shared library. We hold a weak reference
// to this since the actual data resides in the shared Bluetooth library.
@@ -537,21 +535,21 @@ class BluetoothGattInterfaceImpl : public BluetoothGattInterface {
namespace {
-btbase::AbstractObserverList<BluetoothGattInterface::ScannerObserver>*
+base::ObserverList<BluetoothGattInterface::ScannerObserver>*
GetScannerObservers() {
CHECK(g_interface);
return static_cast<BluetoothGattInterfaceImpl*>(g_interface)
->scanner_observers();
}
-btbase::AbstractObserverList<BluetoothGattInterface::ClientObserver>*
+base::ObserverList<BluetoothGattInterface::ClientObserver>*
GetClientObservers() {
CHECK(g_interface);
return static_cast<BluetoothGattInterfaceImpl*>(g_interface)
->client_observers();
}
-btbase::AbstractObserverList<BluetoothGattInterface::ServerObserver>*
+base::ObserverList<BluetoothGattInterface::ServerObserver>*
GetServerObservers() {
CHECK(g_interface);
return static_cast<BluetoothGattInterfaceImpl*>(g_interface)
diff --git a/service/hal/bluetooth_interface.cc b/service/hal/bluetooth_interface.cc
index 84a17859e..42eeb002a 100644
--- a/service/hal/bluetooth_interface.cc
+++ b/service/hal/bluetooth_interface.cc
@@ -22,7 +22,6 @@
#include <base/logging.h>
#include <base/observer_list.h>
-#include "abstract_observer_list.h"
#include "service/logging_helpers.h"
#include "btcore/include/hal_util.h"
@@ -53,7 +52,7 @@ shared_mutex_impl g_instance_lock;
// Helper for obtaining the observer list. This is forward declared here and
// defined below since it depends on BluetoothInterfaceImpl.
-btbase::AbstractObserverList<BluetoothInterface::Observer>* GetObservers();
+base::ObserverList<BluetoothInterface::Observer>* GetObservers();
#define FOR_EACH_BLUETOOTH_OBSERVER(func) \
for (auto& observer : *GetObservers()) { \
@@ -147,17 +146,16 @@ void BondStateChangedCallback(bt_status_t status, RawAddress* remote_bd_addr,
}
void AclStateChangedCallback(bt_status_t status, RawAddress* remote_bd_addr,
- bt_acl_state_t state, bt_hci_error_code_t hci_reason) {
+ bt_acl_state_t state) {
shared_lock<shared_mutex_impl> lock(g_instance_lock);
VERIFY_INTERFACE_OR_RETURN();
CHECK(remote_bd_addr);
VLOG(1) << "Remote device ACL state changed - status: "
<< BtStatusText(status)
<< " - BD_ADDR: " << BtAddrString(remote_bd_addr) << " - state: "
- << ((state == BT_ACL_STATE_CONNECTED) ? "CONNECTED" : "DISCONNECTED")
- << " - HCI_REASON: " << std::to_string(hci_reason);
+ << ((state == BT_ACL_STATE_CONNECTED) ? "CONNECTED" : "DISCONNECTED");
FOR_EACH_BLUETOOTH_OBSERVER(
- AclStateChangedCallback(status, *remote_bd_addr, state, hci_reason));
+ AclStateChangedCallback(status, *remote_bd_addr, state));
}
void ThreadEventCallback(bt_cb_thread_evt evt) {
@@ -193,23 +191,6 @@ int ReleaseWakeLockCallout(const char* /* lock_name */) {
return BT_STATUS_SUCCESS;
}
-void LinkQualityReportCallback(uint64_t timestamp, int report_id, int rssi,
- int snr, int retransmission_count, int packets_not_receive_count,
- int negative_acknowledgement_count) {
- shared_lock<shared_mutex_impl> lock(g_instance_lock);
- VERIFY_INTERFACE_OR_RETURN();
- LOG(WARNING) << __func__ << " - timestamp: " << timestamp
- << " - report_id: " << report_id << " - rssi: " << rssi
- << " - snr: " << snr
- << " - retransmission_count: " << retransmission_count
- << " - packets_not_receive_count: " << packets_not_receive_count
- << " - negative_acknowledgement_count: "
- << negative_acknowledgement_count;
- FOR_EACH_BLUETOOTH_OBSERVER(LinkQualityReportCallback(
- timestamp, report_id, rssi, snr, retransmission_count,
- packets_not_receive_count, negative_acknowledgement_count));
-}
-
// The HAL Bluetooth DM callbacks.
bt_callbacks_t bt_callbacks = {
sizeof(bt_callbacks_t),
@@ -225,9 +206,7 @@ bt_callbacks_t bt_callbacks = {
ThreadEventCallback,
nullptr, /* dut_mode_recv_cb */
nullptr, /* le_test_mode_cb */
- nullptr, /* energy_info_cb */
- LinkQualityReportCallback,
- nullptr /* generate_local_oob_data_cb */
+ nullptr /* energy_info_cb */
};
bt_os_callouts_t bt_os_callouts = {sizeof(bt_os_callouts_t),
@@ -275,7 +254,7 @@ class BluetoothInterfaceImpl : public BluetoothInterface {
// Initialize the Bluetooth interface. Set up the adapter (Bluetooth DM) API
// callbacks.
- status = hal_iface_->init(&bt_callbacks, false, false, 0, nullptr, false);
+ status = hal_iface_->init(&bt_callbacks, false, false, 0, false);
if (status != BT_STATUS_SUCCESS) {
LOG(ERROR) << "Failed to initialize Bluetooth stack";
return false;
@@ -290,14 +269,14 @@ class BluetoothInterfaceImpl : public BluetoothInterface {
return true;
}
- btbase::AbstractObserverList<Observer>* observers() { return &observers_; }
+ base::ObserverList<Observer>* observers() { return &observers_; }
private:
// List of observers that are interested in notifications from us. We're not
// using a base::ObserverListThreadSafe, which it posts observer events
// automatically on the origin threads, as we want to avoid that overhead and
// simply forward the events to the upper layer.
- btbase::AbstractObserverList<Observer> observers_;
+ base::ObserverList<Observer> observers_;
// The HAL handle obtained from the shared library. We hold a weak reference
// to this since the actual data resides in the shared Bluetooth library.
@@ -310,7 +289,7 @@ namespace {
// Helper for obtaining the observer list from the global instance. This
// function is NOT thread safe.
-btbase::AbstractObserverList<BluetoothInterface::Observer>* GetObservers() {
+base::ObserverList<BluetoothInterface::Observer>* GetObservers() {
CHECK(g_bluetooth_interface);
return static_cast<BluetoothInterfaceImpl*>(g_bluetooth_interface)
->observers();
@@ -366,15 +345,7 @@ void BluetoothInterface::Observer::BondStateChangedCallback(
void BluetoothInterface::Observer::AclStateChangedCallback(
bt_status_t /* status */, const RawAddress& /* remote_bdaddr */,
- bt_acl_state_t /* state */, bt_hci_error_code_t /* hci_reason */) {
- // Do nothing.
-}
-
-void BluetoothInterface::Observer::LinkQualityReportCallback(
- uint64_t /* timestamp */, int /* report_id */, int /* rssi */,
- int /* snr */, int /* retransmission_count */,
- int /* packets_not_receive_count */,
- int /* negative_acknowledgement_count */) {
+ bt_acl_state_t /* state */) {
// Do nothing.
}
diff --git a/service/hal/bluetooth_interface.h b/service/hal/bluetooth_interface.h
index aa4125cc9..a1c8e62b4 100644
--- a/service/hal/bluetooth_interface.h
+++ b/service/hal/bluetooth_interface.h
@@ -72,12 +72,7 @@ class BluetoothInterface {
bt_bond_state_t state);
virtual void AclStateChangedCallback(bt_status_t status,
const RawAddress& remote_bdaddr,
- bt_acl_state_t state,
- bt_hci_error_code_t hci_reason);
- virtual void LinkQualityReportCallback(
- uint64_t timestamp, int report_id, int rssi, int snr,
- int retransmission_count, int packets_not_receive_count,
- int negative_acknowledgement_count);
+ bt_acl_state_t state);
// TODO(armansito): Complete the list of callbacks.
};
diff --git a/service/hal/fake_bluetooth_av_interface.cc b/service/hal/fake_bluetooth_av_interface.cc
index 2607a665c..01c8ebef7 100644
--- a/service/hal/fake_bluetooth_av_interface.cc
+++ b/service/hal/fake_bluetooth_av_interface.cc
@@ -35,8 +35,7 @@ bt_status_t FakeSourceInit(
return BT_STATUS_SUCCESS;
}
-bt_status_t FakeSinkInit(btav_sink_callbacks_t* callbacks,
- int max_connected_audio_devices) {
+bt_status_t FakeSinkInit(btav_sink_callbacks_t* callbacks) {
return BT_STATUS_SUCCESS;
}
diff --git a/service/hal/fake_bluetooth_av_interface.h b/service/hal/fake_bluetooth_av_interface.h
index ee431b077..34aeac872 100644
--- a/service/hal/fake_bluetooth_av_interface.h
+++ b/service/hal/fake_bluetooth_av_interface.h
@@ -19,7 +19,6 @@
#include <base/macros.h>
#include <base/observer_list.h>
-#include "abstract_observer_list.h"
#include "service/hal/bluetooth_av_interface.h"
namespace bluetooth {
@@ -89,8 +88,8 @@ class FakeBluetoothAvInterface : public BluetoothAvInterface {
const btav_sink_interface_t* GetA2dpSinkHALInterface() override;
private:
- btbase::AbstractObserverList<A2dpSourceObserver> a2dp_source_observers_;
- btbase::AbstractObserverList<A2dpSinkObserver> a2dp_sink_observers_;
+ base::ObserverList<A2dpSourceObserver> a2dp_source_observers_;
+ base::ObserverList<A2dpSinkObserver> a2dp_sink_observers_;
DISALLOW_COPY_AND_ASSIGN(FakeBluetoothAvInterface);
};
diff --git a/service/hal/fake_bluetooth_gatt_interface.cc b/service/hal/fake_bluetooth_gatt_interface.cc
index f351f93c3..dbbbcaa0a 100644
--- a/service/hal/fake_bluetooth_gatt_interface.cc
+++ b/service/hal/fake_bluetooth_gatt_interface.cc
@@ -28,10 +28,8 @@ std::shared_ptr<BleScannerInterface> g_scanner_handler;
std::shared_ptr<FakeBluetoothGattInterface::TestClientHandler> g_client_handler;
std::shared_ptr<FakeBluetoothGattInterface::TestServerHandler> g_server_handler;
-bt_status_t FakeRegisterClient(const bluetooth::Uuid& app_uuid,
- bool eatt_support) {
- if (g_client_handler)
- return g_client_handler->RegisterClient(app_uuid, false);
+bt_status_t FakeRegisterClient(const bluetooth::Uuid& app_uuid) {
+ if (g_client_handler) return g_client_handler->RegisterClient(app_uuid);
return BT_STATUS_FAIL;
}
@@ -59,10 +57,8 @@ bt_status_t FakeDisconnect(int client_if, const RawAddress& bd_addr,
return BT_STATUS_FAIL;
}
-bt_status_t FakeRegisterServer(const bluetooth::Uuid& app_uuid,
- bool eatt_support) {
- if (g_server_handler)
- return g_server_handler->RegisterServer(app_uuid, false);
+bt_status_t FakeRegisterServer(const bluetooth::Uuid& app_uuid) {
+ if (g_server_handler) return g_server_handler->RegisterServer(app_uuid);
return BT_STATUS_FAIL;
}
diff --git a/service/hal/fake_bluetooth_gatt_interface.h b/service/hal/fake_bluetooth_gatt_interface.h
index b71d5f43b..a991a21fd 100644
--- a/service/hal/fake_bluetooth_gatt_interface.h
+++ b/service/hal/fake_bluetooth_gatt_interface.h
@@ -21,7 +21,6 @@
#include <base/macros.h>
#include <base/observer_list.h>
-#include "abstract_observer_list.h"
#include "service/hal/bluetooth_gatt_interface.h"
namespace bluetooth {
@@ -36,8 +35,7 @@ class FakeBluetoothGattInterface : public BluetoothGattInterface {
public:
virtual ~TestClientHandler() = default;
- virtual bt_status_t RegisterClient(const bluetooth::Uuid& app_uuid,
- bool eatt_support) = 0;
+ virtual bt_status_t RegisterClient(const bluetooth::Uuid& app_uuid) = 0;
virtual bt_status_t UnregisterClient(int client_if) = 0;
virtual bt_status_t Connect(int client_if, const RawAddress& bd_addr,
@@ -53,8 +51,7 @@ class FakeBluetoothGattInterface : public BluetoothGattInterface {
public:
virtual ~TestServerHandler() = default;
- virtual bt_status_t RegisterServer(const bluetooth::Uuid& app_uuid,
- bool eatt_support) = 0;
+ virtual bt_status_t RegisterServer(const bluetooth::Uuid& app_uuid) = 0;
virtual bt_status_t UnregisterServer(int server_if) = 0;
virtual bt_status_t AddService(
int server_if, std::vector<btgatt_db_element_t> service) = 0;
@@ -141,9 +138,9 @@ class FakeBluetoothGattInterface : public BluetoothGattInterface {
const btgatt_server_interface_t* GetServerHALInterface() const override;
private:
- btbase::AbstractObserverList<ScannerObserver> scanner_observers_;
- btbase::AbstractObserverList<ClientObserver> client_observers_;
- btbase::AbstractObserverList<ServerObserver> server_observers_;
+ base::ObserverList<ScannerObserver> scanner_observers_;
+ base::ObserverList<ClientObserver> client_observers_;
+ base::ObserverList<ServerObserver> server_observers_;
std::shared_ptr<BleScannerInterface> scanner_handler_;
std::shared_ptr<TestClientHandler> client_handler_;
std::shared_ptr<TestServerHandler> server_handler_;
diff --git a/service/hal/fake_bluetooth_interface.cc b/service/hal/fake_bluetooth_interface.cc
index 5e7d5e8e8..4af8bc60d 100644
--- a/service/hal/fake_bluetooth_interface.cc
+++ b/service/hal/fake_bluetooth_interface.cc
@@ -76,8 +76,6 @@ bt_interface_t fake_bt_iface = {
nullptr, /* get_avrcp_service */
nullptr, /* obfuscate_address */
nullptr, /* get_metric_id */
- nullptr, /* set_dynamic_audio_buffer_size */
- nullptr, /* generate_local_oob_data */
};
} // namespace
@@ -142,10 +140,9 @@ void FakeBluetoothInterface::NotifyAdapterLocalLeFeaturesPropertyChanged(
}
void FakeBluetoothInterface::NotifyAclStateChangedCallback(
- bt_status_t status, const RawAddress& remote_bdaddr, bt_acl_state_t state,
- bt_hci_error_code_t hci_reason) {
+ bt_status_t status, const RawAddress& remote_bdaddr, bt_acl_state_t state) {
for (auto& observer : observers_) {
- observer.AclStateChangedCallback(status, remote_bdaddr, state, hci_reason);
+ observer.AclStateChangedCallback(status, remote_bdaddr, state);
}
}
diff --git a/service/hal/fake_bluetooth_interface.h b/service/hal/fake_bluetooth_interface.h
index 0fc0aa197..b7dc83259 100644
--- a/service/hal/fake_bluetooth_interface.h
+++ b/service/hal/fake_bluetooth_interface.h
@@ -17,7 +17,6 @@
#include <base/macros.h>
#include <base/observer_list.h>
-#include "abstract_observer_list.h"
#include "service/hal/bluetooth_interface.h"
namespace bluetooth {
@@ -57,8 +56,7 @@ class FakeBluetoothInterface : public BluetoothInterface {
const bt_local_le_features_t* features);
void NotifyAclStateChangedCallback(bt_status_t status,
const RawAddress& remote_bdaddr,
- bt_acl_state_t state,
- bt_hci_error_code_t hci_reason);
+ bt_acl_state_t state);
// hal::BluetoothInterface overrides:
void AddObserver(Observer* observer) override;
@@ -67,7 +65,7 @@ class FakeBluetoothInterface : public BluetoothInterface {
bt_callbacks_t* GetHALCallbacks() const override;
private:
- btbase::AbstractObserverList<Observer> observers_;
+ base::ObserverList<Observer> observers_;
DISALLOW_COPY_AND_ASSIGN(FakeBluetoothInterface);
};
diff --git a/service/ipc/binder/ipc_handler_binder.cc b/service/ipc/binder/ipc_handler_binder.cc
index 11ff66fc6..becd6e82c 100644
--- a/service/ipc/binder/ipc_handler_binder.cc
+++ b/service/ipc/binder/ipc_handler_binder.cc
@@ -18,11 +18,11 @@
#include <base/bind.h>
#include <base/logging.h>
+#include <base/message_loop/message_loop.h>
#include <binder/IPCThreadState.h>
#include <binder/IServiceManager.h>
#include <binder/ProcessState.h>
-#include "abstract_message_loop.h"
#include "service/ipc/binder/bluetooth_binder_server.h"
using android::defaultServiceManager;
@@ -56,7 +56,7 @@ bool IPCHandlerBinder::Run() {
// Notify the delegate. We do this in the message loop to avoid reentrancy.
if (delegate()) {
- btbase::AbstractMessageLoop::current_task_runner()->PostTask(
+ base::MessageLoop::current()->task_runner()->PostTask(
FROM_HERE, base::Bind(&IPCHandlerBinder::NotifyStarted, this));
}
diff --git a/service/ipc/dbus/bluetooth_adapter.cc b/service/ipc/dbus/bluetooth_adapter.cc
index 6831c1b93..fd6688a94 100644
--- a/service/ipc/dbus/bluetooth_adapter.cc
+++ b/service/ipc/dbus/bluetooth_adapter.cc
@@ -46,20 +46,6 @@ const char kDBusIntrospectMethod[] = "Introspect";
namespace ipc {
namespace dbus {
-#if defined(BASE_VER) && BASE_VER > 780000
-// New libchrome treats ResponseSender as base::OnceCallback so we need to move
-// ownership before calling ::Run()
-inline void RunResponse(std::unique_ptr<Response> response,
- ExportedObject::ResponseSender& response_sender) {
- std::move(response_sender).Run(std::move(response));
-}
-#else
-inline void RunResponse(std::unique_ptr<Response> response,
- ExportedObject::ResponseSender& response_sender) {
- response_sender.Run(std::move(response));
-}
-#endif
-
BluetoothAdapter::BluetoothAdapter(scoped_refptr<Bus> bus,
bluetooth::Adapter* adapter)
: adapter_(adapter) {
@@ -86,15 +72,15 @@ BluetoothAdapter::BluetoothAdapter(scoped_refptr<Bus> bus,
void BluetoothAdapter::Enable(MethodCall* method_call,
ExportedObject::ResponseSender response_sender) {
VLOG(1) << __func__;
- adapter_->Enable();
- RunResponse(Response::FromMethodCall(method_call), response_sender);
+ adapter_->Enable(false);
+ response_sender.Run(Response::FromMethodCall(method_call));
}
void BluetoothAdapter::Disable(MethodCall* method_call,
ExportedObject::ResponseSender response_sender) {
VLOG(1) << __func__;
adapter_->Disable();
- RunResponse(Response::FromMethodCall(method_call), response_sender);
+ response_sender.Run(Response::FromMethodCall(method_call));
}
void BluetoothAdapter::Introspect(
@@ -104,16 +90,14 @@ void BluetoothAdapter::Introspect(
std::string output;
if (!base::ReadFileToString(base::FilePath(kBindingsPath), &output)) {
PLOG(ERROR) << "Can't read XML bindings from disk:";
- RunResponse(ErrorResponse::FromMethodCall(
- method_call, "Can't read XML bindings from disk.", ""),
- response_sender);
+ response_sender.Run(ErrorResponse::FromMethodCall(
+ method_call, "Can't read XML bindings from disk.", ""));
}
-
std::unique_ptr<Response> response(Response::FromMethodCall(method_call));
MessageWriter writer(response.get());
writer.AppendString(output);
- RunResponse(std::move(response), response_sender);
+ response_sender.Run(std::move(response));
}
BluetoothAdapter::~BluetoothAdapter() {}
diff --git a/service/ipc/dbus/ipc_handler_dbus.cc b/service/ipc/dbus/ipc_handler_dbus.cc
index 8abd2449d..c8922d32e 100644
--- a/service/ipc/dbus/ipc_handler_dbus.cc
+++ b/service/ipc/dbus/ipc_handler_dbus.cc
@@ -37,7 +37,7 @@ bool IPCHandlerDBus::Run() {
dbus_thread_ = new base::Thread("D-Bus Thread");
base::Thread::Options thread_options;
- btbase::set_message_loop_type_IO(thread_options);
+ thread_options.message_loop_type = base::MessageLoop::TYPE_IO;
dbus_thread_->StartWithOptions(thread_options);
dbus_thread_->task_runner()->PostTask(
diff --git a/service/ipc/ipc_handler_linux.cc b/service/ipc/ipc_handler_linux.cc
index fa7727a87..ebfae1294 100644
--- a/service/ipc/ipc_handler_linux.cc
+++ b/service/ipc/ipc_handler_linux.cc
@@ -21,7 +21,6 @@
#include <base/bind.h>
-#include "abstract_message_loop.h"
#include "osi/include/socket_utils/sockets.h"
#include "service/daemon.h"
#include "service/ipc/linux_ipc_host.h"
@@ -57,9 +56,8 @@ bool IPCHandlerLinux::Run() {
return false;
}
- // An origin event loop is required.
- CHECK(btbase::AbstractMessageLoop::current_task_runner());
- origin_task_runner_ = btbase::AbstractMessageLoop::current_task_runner();
+ CHECK(base::MessageLoop::current()); // An origin event loop is required.
+ origin_task_runner_ = base::MessageLoop::current()->task_runner();
if (!android_suffix.empty()) {
int server_fd = osi_android_get_control_socket(android_suffix.c_str());
@@ -104,8 +102,7 @@ bool IPCHandlerLinux::Run() {
running_ = true; // Set this here before launching the thread.
// Start an IO thread and post the listening task.
- base::Thread::Options options;
- btbase::set_message_loop_type_IO(options);
+ base::Thread::Options options(base::MessageLoop::TYPE_IO, 0);
if (!thread_.StartWithOptions(options)) {
LOG(ERROR) << "Failed to start IPCHandlerLinux thread";
running_ = false;
diff --git a/service/ipc/linux_ipc_host.cc b/service/ipc/linux_ipc_host.cc
index ebd41f05a..705748fa1 100644
--- a/service/ipc/linux_ipc_host.cc
+++ b/service/ipc/linux_ipc_host.cc
@@ -82,7 +82,7 @@ bool LinuxIPCHost::EventLoop() {
int status =
TEMP_FAILURE_RETRY(ppoll(pfds_.data(), pfds_.size(), nullptr, nullptr));
if (status < 1) {
- LOG_ERROR("ppoll error");
+ LOG_ERROR(LOG_TAG, "ppoll error");
return false;
}
@@ -111,7 +111,7 @@ bool LinuxIPCHost::OnCreateService(const std::string& service_uuid) {
bool status = gatt_servers_[service_uuid]->Initialize(
Uuid::FromString(service_uuid), &gattfd);
if (!status) {
- LOG_ERROR("Failed to initialize bluetooth");
+ LOG_ERROR(LOG_TAG, "Failed to initialize bluetooth");
return false;
}
pfds_.resize(kPossibleFds);
@@ -181,8 +181,9 @@ bool LinuxIPCHost::OnSetAdvertisement(const std::string& service_uuid,
const std::string& advertise_data,
const std::string& manufacturer_data,
const std::string& transmit_name) {
- LOG_INFO("%s: service:%s uuids:%s data:%s", __func__, service_uuid.c_str(),
- advertise_uuids.c_str(), advertise_data.c_str());
+ LOG_INFO(LOG_TAG, "%s: service:%s uuids:%s data:%s", __func__,
+ service_uuid.c_str(), advertise_uuids.c_str(),
+ advertise_data.c_str());
std::vector<std::string> advertise_uuid_tokens = base::SplitString(
advertise_uuids, ".", base::TRIM_WHITESPACE, base::SPLIT_WANT_ALL);
@@ -250,20 +251,20 @@ bool LinuxIPCHost::OnMessage() {
OSI_NO_INTR(size =
recv(pfds_[kFdIpc].fd, &ipc_msg[0], 0, MSG_PEEK | MSG_TRUNC));
if (-1 == size) {
- LOG_ERROR("Error reading datagram size: %s", strerror(errno));
+ LOG_ERROR(LOG_TAG, "Error reading datagram size: %s", strerror(errno));
return false;
} else if (0 == size) {
- LOG_INFO("%s:%d: Connection closed", __func__, __LINE__);
+ LOG_INFO(LOG_TAG, "%s:%d: Connection closed", __func__, __LINE__);
return false;
}
ipc_msg.resize(size);
OSI_NO_INTR(size = read(pfds_[kFdIpc].fd, &ipc_msg[0], ipc_msg.size()));
if (-1 == size) {
- LOG_ERROR("Error reading IPC: %s", strerror(errno));
+ LOG_ERROR(LOG_TAG, "Error reading IPC: %s", strerror(errno));
return false;
} else if (0 == size) {
- LOG_INFO("%s:%d: Connection closed", __func__, __LINE__);
+ LOG_INFO(LOG_TAG, "%s:%d: Connection closed", __func__, __LINE__);
return false;
}
@@ -299,7 +300,7 @@ bool LinuxIPCHost::OnMessage() {
break;
}
- LOG_ERROR("Malformed IPC message: %s", ipc_msg.c_str());
+ LOG_ERROR(LOG_TAG, "Malformed IPC message: %s", ipc_msg.c_str());
return false;
}
@@ -309,7 +310,7 @@ bool LinuxIPCHost::OnGattWrite() {
OSI_NO_INTR(r = read(pfds_[kFdGatt].fd, id.data(), id.size()));
if (r != id.size()) {
- LOG_ERROR("Error reading GATT attribute ID");
+ LOG_ERROR(LOG_TAG, "Error reading GATT attribute ID");
return false;
}
@@ -328,7 +329,7 @@ bool LinuxIPCHost::OnGattWrite() {
OSI_NO_INTR(r = write(pfds_[kFdIpc].fd, transmit.data(), transmit.size()));
if (-1 == r) {
- LOG_ERROR("Error replying to IPC: %s", strerror(errno));
+ LOG_ERROR(LOG_TAG, "Error replying to IPC: %s", strerror(errno));
return false;
}
diff --git a/service/logging_helpers.cc b/service/logging_helpers.cc
index 03d9370b0..70f8720c6 100644
--- a/service/logging_helpers.cc
+++ b/service/logging_helpers.cc
@@ -15,7 +15,7 @@
//
#include "logging_helpers.h"
-#include "types/bt_transport.h"
+#include <string.h>
#include <string>
@@ -46,9 +46,9 @@ const char* BtAvAudioStateText(const btav_audio_state_t state) {
const char* BtTransportText(const btgatt_transport_t t) {
switch (t) {
- CASE_RETURN_TEXT(BT_TRANSPORT_AUTO);
- CASE_RETURN_TEXT(BT_TRANSPORT_BR_EDR);
- CASE_RETURN_TEXT(BT_TRANSPORT_LE);
+ CASE_RETURN_TEXT(GATT_TRANSPORT_AUTO);
+ CASE_RETURN_TEXT(GATT_TRANSPORT_BREDR);
+ CASE_RETURN_TEXT(GATT_TRANSPORT_LE);
default:
return "unknown transport";
}
diff --git a/service/low_energy_client.cc b/service/low_energy_client.cc
index bbc130fe8..cb8bcf132 100644
--- a/service/low_energy_client.cc
+++ b/service/low_energy_client.cc
@@ -22,13 +22,10 @@
#include "service/logging_helpers.h"
#include "stack/include/bt_types.h"
#include "stack/include/hcidefs.h"
-#include "types/bt_transport.h"
using std::lock_guard;
using std::mutex;
-constexpr int kPhyLe1MbMask = 1;
-
namespace bluetooth {
// LowEnergyClient implementation
@@ -61,7 +58,7 @@ bool LowEnergyClient::Connect(const std::string& address, bool is_direct) {
bt_status_t status =
hal::BluetoothGattInterface::Get()->GetClientHALInterface()->connect(
- client_id_, bda, is_direct, BT_TRANSPORT_LE, false, kPhyLe1MbMask);
+ client_id_, bda, is_direct, BT_TRANSPORT_LE, false, PHY_LE_1M_MASK);
if (status != BT_STATUS_SUCCESS) {
LOG(ERROR) << "HAL call to connect failed";
return false;
@@ -221,8 +218,7 @@ bool LowEnergyClientFactory::RegisterInstance(
const btgatt_client_interface_t* hal_iface =
hal::BluetoothGattInterface::Get()->GetClientHALInterface();
- if (hal_iface->register_client(uuid, false) != BT_STATUS_SUCCESS)
- return false;
+ if (hal_iface->register_client(uuid) != BT_STATUS_SUCCESS) return false;
pending_calls_[uuid] = callback;
diff --git a/service/low_energy_scanner.cc b/service/low_energy_scanner.cc
index fe65a7a77..82f3ab402 100644
--- a/service/low_energy_scanner.cc
+++ b/service/low_energy_scanner.cc
@@ -184,11 +184,9 @@ bool LowEnergyScannerFactory::RegisterInstance(
BleScannerInterface* hal_iface =
hal::BluetoothGattInterface::Get()->GetScannerHALInterface();
- Uuid uuid_empty = Uuid::kEmpty;
-
hal_iface->RegisterScanner(
- uuid_empty, base::Bind(&LowEnergyScannerFactory::RegisterScannerCallback,
- base::Unretained(this), callback, uuid));
+ base::Bind(&LowEnergyScannerFactory::RegisterScannerCallback,
+ base::Unretained(this), callback, uuid));
pending_calls_.insert(uuid);
diff --git a/service/settings.cc b/service/settings.cc
index b3dc20143..af67fbe97 100644
--- a/service/settings.cc
+++ b/service/settings.cc
@@ -16,6 +16,7 @@
#include "service/settings.h"
+#include <base/base_switches.h>
#include <base/command_line.h>
#include <base/logging.h>
@@ -23,12 +24,6 @@
namespace bluetooth {
-namespace switches {
-// Verbose switch that should be part of base_switches but doesn't seem to be
-// exported as part of libbase.
-const char kV[] = "v";
-}; // namespace switches
-
Settings::Settings() : initialized_(false), enable_on_start_(false) {}
Settings::~Settings() {}
@@ -72,7 +67,7 @@ bool Settings::Init() {
}
// Check for libbase logging switches. These get processed by
// logging::InitLogging directly.
- else if (iter.first != switches::kV) {
+ else if (iter.first != ::switches::kV) {
LOG(ERROR) << "Unexpected command-line switches found: " << iter.first;
return false;
}
diff --git a/service/test/adapter_unittest.cc b/service/test/adapter_unittest.cc
index 5abd08eee..b1cedc19c 100644
--- a/service/test/adapter_unittest.cc
+++ b/service/test/adapter_unittest.cc
@@ -259,24 +259,21 @@ TEST_F(AdapterTest, IsDeviceConnected) {
// status != BT_STATUS_SUCCESS should be ignored
fake_hal_iface_->NotifyAclStateChangedCallback(BT_STATUS_FAIL, hal_addr,
- BT_ACL_STATE_CONNECTED,
- 0xff); // HCI_ERR_UNDEFINED
+ BT_ACL_STATE_CONNECTED);
EXPECT_FALSE(adapter_->IsDeviceConnected(kDeviceAddr));
EXPECT_TRUE(observer.last_connection_state_address().empty());
EXPECT_FALSE(observer.last_device_connected_state());
// Connected
fake_hal_iface_->NotifyAclStateChangedCallback(BT_STATUS_SUCCESS, hal_addr,
- BT_ACL_STATE_CONNECTED,
- 0x00); // HCI_SUCCESS
+ BT_ACL_STATE_CONNECTED);
EXPECT_TRUE(adapter_->IsDeviceConnected(kDeviceAddr));
EXPECT_EQ(kDeviceAddr, observer.last_connection_state_address());
EXPECT_TRUE(observer.last_device_connected_state());
// Disconnected
fake_hal_iface_->NotifyAclStateChangedCallback(BT_STATUS_SUCCESS, hal_addr,
- BT_ACL_STATE_DISCONNECTED,
- 0x16); // HCI_ERR_CONN_CAUSE_LOCAL_HOST
+ BT_ACL_STATE_DISCONNECTED);
EXPECT_FALSE(adapter_->IsDeviceConnected(kDeviceAddr));
EXPECT_EQ(kDeviceAddr, observer.last_connection_state_address());
EXPECT_FALSE(observer.last_device_connected_state());
diff --git a/service/test/advertise_data_unittest.cc b/service/test/advertise_data_unittest.cc
index a481c8ce3..28c27bf37 100644
--- a/service/test/advertise_data_unittest.cc
+++ b/service/test/advertise_data_unittest.cc
@@ -85,12 +85,12 @@ TEST(AdvertiseDataTest, DisallowedFields) {
AdvertiseData adv2(data2);
EXPECT_FALSE(adv2.IsValid());
- // Check all rejectlisted fields
- uint8_t rejectlist[] = {HCI_EIR_FLAGS_TYPE, HCI_EIR_OOB_BD_ADDR_TYPE,
- HCI_EIR_OOB_COD_TYPE, HCI_EIR_OOB_SSP_HASH_C_TYPE,
- HCI_EIR_OOB_SSP_RAND_R_TYPE};
- for (size_t i = 0; i < sizeof(rejectlist); i++) {
- const std::vector<uint8_t> data{0x02, rejectlist[i], 0x00};
+ // Check all blacklisted fields
+ uint8_t blacklist[] = {HCI_EIR_FLAGS_TYPE, HCI_EIR_OOB_BD_ADDR_TYPE,
+ HCI_EIR_OOB_COD_TYPE, HCI_EIR_OOB_SSP_HASH_C_TYPE,
+ HCI_EIR_OOB_SSP_RAND_R_TYPE};
+ for (size_t i = 0; i < sizeof(blacklist); i++) {
+ const std::vector<uint8_t> data{0x02, blacklist[i], 0x00};
AdvertiseData adv(data);
EXPECT_FALSE(adv.IsValid());
}
diff --git a/service/test/gatt_client_unittest.cc b/service/test/gatt_client_unittest.cc
index a7d7e470d..310e4b929 100644
--- a/service/test/gatt_client_unittest.cc
+++ b/service/test/gatt_client_unittest.cc
@@ -33,8 +33,7 @@ class MockGattHandler
MockGattHandler() = default;
~MockGattHandler() override = default;
- MOCK_METHOD2(RegisterClient,
- bt_status_t(const bluetooth::Uuid&, bool eatt_support));
+ MOCK_METHOD1(RegisterClient, bt_status_t(const bluetooth::Uuid&));
MOCK_METHOD1(UnregisterClient, bt_status_t(int));
MOCK_METHOD1(Scan, bt_status_t(bool));
MOCK_METHOD4(Connect, bt_status_t(int, const RawAddress&, bool, int));
@@ -78,7 +77,7 @@ class GattClientTest : public ::testing::Test {
};
TEST_F(GattClientTest, RegisterInstance) {
- EXPECT_CALL(*mock_handler_, RegisterClient(_, _))
+ EXPECT_CALL(*mock_handler_, RegisterClient(_))
.Times(2)
.WillOnce(Return(BT_STATUS_FAIL))
.WillOnce(Return(BT_STATUS_SUCCESS));
@@ -117,7 +116,7 @@ TEST_F(GattClientTest, RegisterInstance) {
// Call with a different Uuid while one is pending.
Uuid uuid1 = Uuid::GetRandom();
- EXPECT_CALL(*mock_handler_, RegisterClient(_, _))
+ EXPECT_CALL(*mock_handler_, RegisterClient(_))
.Times(1)
.WillOnce(Return(BT_STATUS_SUCCESS));
EXPECT_TRUE(factory_->RegisterInstance(uuid1, callback));
diff --git a/service/test/gatt_server_unittest.cc b/service/test/gatt_server_unittest.cc
index 962697d09..e19742da5 100644
--- a/service/test/gatt_server_unittest.cc
+++ b/service/test/gatt_server_unittest.cc
@@ -32,8 +32,7 @@ class MockGattHandler
MockGattHandler() = default;
~MockGattHandler() override = default;
- MOCK_METHOD2(RegisterServer,
- bt_status_t(const bluetooth::Uuid&, bool eatt_support));
+ MOCK_METHOD1(RegisterServer, bt_status_t(const bluetooth::Uuid&));
MOCK_METHOD1(UnregisterServer, bt_status_t(int));
MOCK_METHOD2(AddService, bt_status_t(int, std::vector<btgatt_db_element_t>));
MOCK_METHOD5(AddCharacteristic,
@@ -224,7 +223,7 @@ class GattServerPostRegisterTest : public GattServerTest {
static_cast<GattServer*>(in_client.release()));
};
- EXPECT_CALL(*mock_handler_, RegisterServer(_, _))
+ EXPECT_CALL(*mock_handler_, RegisterServer(_))
.Times(1)
.WillOnce(Return(BT_STATUS_SUCCESS));
@@ -299,7 +298,7 @@ class GattServerPostRegisterTest : public GattServerTest {
};
TEST_F(GattServerTest, RegisterServer) {
- EXPECT_CALL(*mock_handler_, RegisterServer(_, _))
+ EXPECT_CALL(*mock_handler_, RegisterServer(_))
.Times(2)
.WillOnce(Return(BT_STATUS_FAIL))
.WillOnce(Return(BT_STATUS_SUCCESS));
@@ -338,7 +337,7 @@ TEST_F(GattServerTest, RegisterServer) {
// Call with a different Uuid while one is pending.
Uuid uuid1 = Uuid::GetRandom();
- EXPECT_CALL(*mock_handler_, RegisterServer(_, _))
+ EXPECT_CALL(*mock_handler_, RegisterServer(_))
.Times(1)
.WillOnce(Return(BT_STATUS_SUCCESS));
EXPECT_TRUE(factory_->RegisterInstance(uuid1, callback));
diff --git a/service/test/ipc_linux_unittest.cc b/service/test/ipc_linux_unittest.cc
index 176cd6a32..4a347ae36 100644
--- a/service/test/ipc_linux_unittest.cc
+++ b/service/test/ipc_linux_unittest.cc
@@ -27,8 +27,6 @@
#include <base/strings/stringprintf.h>
#include <gtest/gtest.h>
-#include "abstract_message_loop"
-#include "array_utils.h"
#include "service/adapter.h"
#include "service/hal/fake_bluetooth_gatt_interface.h"
#include "service/hal/fake_bluetooth_interface.h"
@@ -84,7 +82,7 @@ class IPCLinuxTest : public ::testing::Test {
const base::CommandLine::CharType* argv[] = {
"program", ipc_socket_arg.c_str(),
};
- base::CommandLine::Init(ARRAY_SIZE(argv), argv);
+ base::CommandLine::Init(arraysize(argv), argv);
}
void ConnectToTestSocket() {
@@ -103,7 +101,7 @@ class IPCLinuxTest : public ::testing::Test {
protected:
base::AtExitManager exit_manager_;
- DEFINE_TEST_TASK_ENV(message_loop_);
+ base::MessageLoop message_loop_;
bluetooth::Settings settings_;
std::unique_ptr<bluetooth::Adapter> adapter_;
@@ -121,7 +119,7 @@ class IPCLinuxTestDisabled : public IPCLinuxTest {
void SetUpCommandLine() override {
// Set up with no --ipc-socket-path
const base::CommandLine::CharType* argv[] = {"program"};
- base::CommandLine::Init(ARRAY_SIZE(argv), argv);
+ base::CommandLine::Init(arraysize(argv), argv);
}
private:
@@ -136,13 +134,13 @@ class TestDelegate : public ipc::IPCManager::Delegate,
void OnIPCHandlerStarted(ipc::IPCManager::Type type) override {
ASSERT_EQ(ipc::IPCManager::TYPE_LINUX, type);
started_count_++;
- btbase::AbstractTestMessageLoop::currentIO()->QuitWhenIdle();
+ base::MessageLoop::current()->QuitWhenIdle();
}
void OnIPCHandlerStopped(ipc::IPCManager::Type type) override {
ASSERT_EQ(ipc::IPCManager::TYPE_LINUX, type);
stopped_count_++;
- btbase::AbstractTestMessageLoop::currentIO()->QuitWhenIdle();
+ base::MessageLoop::current()->QuitWhenIdle();
}
int started_count() const { return started_count_; }
diff --git a/service/test/low_energy_advertiser_unittest.cc b/service/test/low_energy_advertiser_unittest.cc
index 751eb2b59..ad76d8275 100644
--- a/service/test/low_energy_advertiser_unittest.cc
+++ b/service/test/low_energy_advertiser_unittest.cc
@@ -57,20 +57,18 @@ class MockAdvertiserHandler : public BleAdvertiserInterface {
void(uint8_t advertiser_id, StatusCallback cb,
AdvertiseParameters, std::vector<uint8_t>,
std::vector<uint8_t>, int, StatusCallback));
- MOCK_METHOD10(StartAdvertisingSet,
- void(int reg_id, IdTxPowerStatusCallback cb,
- AdvertiseParameters params,
- std::vector<uint8_t> advertise_data,
- std::vector<uint8_t> scan_response_data,
- PeriodicAdvertisingParameters periodic_params,
- std::vector<uint8_t> periodic_data, uint16_t duration,
- uint8_t maxExtAdvEvents, IdStatusCallback timeout_cb));
+ MOCK_METHOD9(StartAdvertisingSet,
+ void(IdTxPowerStatusCallback cb, AdvertiseParameters params,
+ std::vector<uint8_t> advertise_data,
+ std::vector<uint8_t> scan_response_data,
+ PeriodicAdvertisingParameters periodic_params,
+ std::vector<uint8_t> periodic_data, uint16_t duration,
+ uint8_t maxExtAdvEvents, IdStatusCallback timeout_cb));
MOCK_METHOD3(SetPeriodicAdvertisingParameters,
void(int, PeriodicAdvertisingParameters, StatusCallback));
MOCK_METHOD3(SetPeriodicAdvertisingData,
void(int, std::vector<uint8_t>, StatusCallback));
MOCK_METHOD3(SetPeriodicAdvertisingEnable, void(int, bool, StatusCallback));
- MOCK_METHOD1(RegisterCallbacks, void(AdvertisingCallbacks* callbacks));
private:
DISALLOW_COPY_AND_ASSIGN(MockAdvertiserHandler);
diff --git a/service/test/low_energy_client_unittest.cc b/service/test/low_energy_client_unittest.cc
index b3fc204ae..ce3c7c0ab 100644
--- a/service/test/low_energy_client_unittest.cc
+++ b/service/test/low_energy_client_unittest.cc
@@ -24,7 +24,6 @@
#include "stack/include/bt_types.h"
#include "stack/include/hcidefs.h"
#include "test/mock_adapter.h"
-#include "types/bt_transport.h"
using ::testing::_;
using ::testing::Return;
@@ -41,8 +40,7 @@ class MockGattHandler
MockGattHandler(){};
~MockGattHandler() override = default;
- MOCK_METHOD2(RegisterClient,
- bt_status_t(const bluetooth::Uuid&, bool eatt_support));
+ MOCK_METHOD1(RegisterClient, bt_status_t(const bluetooth::Uuid&));
MOCK_METHOD1(UnregisterClient, bt_status_t(int));
MOCK_METHOD4(Connect, bt_status_t(int, const RawAddress&, bool, int));
MOCK_METHOD3(Disconnect, bt_status_t(int, const RawAddress&, int));
@@ -147,7 +145,7 @@ class LowEnergyClientPostRegisterTest : public LowEnergyClientTest {
static_cast<LowEnergyClient*>(in_client.release())));
};
- EXPECT_CALL(*mock_handler_, RegisterClient(_, _))
+ EXPECT_CALL(*mock_handler_, RegisterClient(_))
.Times(1)
.WillOnce(Return(BT_STATUS_SUCCESS));
@@ -168,7 +166,7 @@ class LowEnergyClientPostRegisterTest : public LowEnergyClientTest {
};
TEST_F(LowEnergyClientTest, RegisterInstance) {
- EXPECT_CALL(*mock_handler_, RegisterClient(_, _))
+ EXPECT_CALL(*mock_handler_, RegisterClient(_))
.Times(2)
.WillOnce(Return(BT_STATUS_FAIL))
.WillOnce(Return(BT_STATUS_SUCCESS));
@@ -207,7 +205,7 @@ TEST_F(LowEnergyClientTest, RegisterInstance) {
// Call with a different Uuid while one is pending.
Uuid uuid1 = Uuid::GetRandom();
- EXPECT_CALL(*mock_handler_, RegisterClient(_, _))
+ EXPECT_CALL(*mock_handler_, RegisterClient(_))
.Times(1)
.WillOnce(Return(BT_STATUS_SUCCESS));
EXPECT_TRUE(ble_factory_->RegisterInstance(uuid1, callback));
diff --git a/service/test/low_energy_scanner_unittest.cc b/service/test/low_energy_scanner_unittest.cc
index 53fc29390..9a7875dc3 100644
--- a/service/test/low_energy_scanner_unittest.cc
+++ b/service/test/low_energy_scanner_unittest.cc
@@ -41,8 +41,7 @@ class MockScannerHandler : public BleScannerInterface {
MockScannerHandler() {}
~MockScannerHandler() override = default;
- MOCK_METHOD2(RegisterScanner, void(const bluetooth::Uuid& app_uuid,
- BleScannerInterface::RegisterCallback));
+ MOCK_METHOD1(RegisterScanner, void(BleScannerInterface::RegisterCallback));
MOCK_METHOD1(Unregister, void(int));
MOCK_METHOD1(Scan, void(bool));
@@ -72,8 +71,6 @@ class MockScannerHandler : public BleScannerInterface {
StartSyncCb, SyncReportCb, SyncLostCb));
MOCK_METHOD1(StopSync, void(uint16_t));
- MOCK_METHOD1(RegisterCallbacks, void(ScanningCallbacks* callbacks));
-
void ScanFilterAdd(int filter_index, std::vector<ApcfCommand> filters,
FilterConfigCallback cb) override{};
@@ -174,10 +171,9 @@ class LowEnergyScannerPostRegisterTest : public LowEnergyScannerTest {
};
BleScannerInterface::RegisterCallback reg_scanner_cb;
- Uuid uuid_empty;
- EXPECT_CALL(*mock_handler_, RegisterScanner(_, _))
+ EXPECT_CALL(*mock_handler_, RegisterScanner(_))
.Times(1)
- .WillOnce(DoAll(SaveArg<0>(&uuid_empty), SaveArg<1>(&reg_scanner_cb)));
+ .WillOnce(SaveArg<0>(&reg_scanner_cb));
ble_factory_->RegisterInstance(uuid, api_callback);
@@ -196,10 +192,9 @@ class LowEnergyScannerPostRegisterTest : public LowEnergyScannerTest {
TEST_F(LowEnergyScannerTest, RegisterInstance) {
BleScannerInterface::RegisterCallback reg_scanner_cb1;
- Uuid uuid_empty1;
- EXPECT_CALL(*mock_handler_, RegisterScanner(_, _))
+ EXPECT_CALL(*mock_handler_, RegisterScanner(_))
.Times(1)
- .WillOnce(DoAll(SaveArg<0>(&uuid_empty1), SaveArg<1>(&reg_scanner_cb1)));
+ .WillOnce(SaveArg<0>(&reg_scanner_cb1));
// These will be asynchronously populated with a result when the callback
// executes.
@@ -232,10 +227,9 @@ TEST_F(LowEnergyScannerTest, RegisterInstance) {
// Call with a different Uuid while one is pending.
Uuid uuid1 = Uuid::GetRandom();
BleScannerInterface::RegisterCallback reg_scanner_cb2;
- Uuid uuid_empty2;
- EXPECT_CALL(*mock_handler_, RegisterScanner(_, _))
+ EXPECT_CALL(*mock_handler_, RegisterScanner(_))
.Times(1)
- .WillOnce(DoAll(SaveArg<0>(&uuid_empty2), SaveArg<1>(&reg_scanner_cb2)));
+ .WillOnce(SaveArg<0>(&reg_scanner_cb2));
EXPECT_TRUE(ble_factory_->RegisterInstance(uuid1, callback));
// |uuid0| succeeds.
diff --git a/service/test/mock_daemon.h b/service/test/mock_daemon.h
index 1c026221d..9947915bc 100644
--- a/service/test/mock_daemon.h
+++ b/service/test/mock_daemon.h
@@ -18,7 +18,6 @@
#include <gmock/gmock.h>
-#include "abstract_message_loop.h"
#include "service/daemon.h"
namespace bluetooth {
@@ -30,7 +29,7 @@ class MockDaemon : public Daemon {
~MockDaemon() override = default;
MOCK_CONST_METHOD0(GetSettings, Settings*());
- MOCK_CONST_METHOD0(GetMessageLoop, btbase::AbstractMessageLoop*());
+ MOCK_CONST_METHOD0(GetMessageLoop, base::MessageLoop*());
MOCK_METHOD0(StartMainLoop, void());
MOCK_METHOD0(Init, bool());
diff --git a/service/test/settings_unittest.cc b/service/test/settings_unittest.cc
index 60d372e37..551c1e053 100644
--- a/service/test/settings_unittest.cc
+++ b/service/test/settings_unittest.cc
@@ -19,7 +19,6 @@
#include <base/macros.h>
#include <gtest/gtest.h>
-#include "array_utils.h"
#include "service/settings.h"
#include "service/switches.h"
@@ -46,33 +45,33 @@ class SettingsTest : public ::testing::Test {
TEST_F(SettingsTest, EmptyCommandLine) {
const base::CommandLine::CharType* argv[] = {"program"};
- EXPECT_TRUE(base::CommandLine::Init(ARRAY_SIZE(argv), argv));
+ EXPECT_TRUE(base::CommandLine::Init(arraysize(argv), argv));
EXPECT_TRUE(settings_.Init());
}
TEST_F(SettingsTest, UnexpectedSwitches1) {
const base::CommandLine::CharType* argv[] = {
"program", "--create-ipc-socket=foobar", "--foobarbaz"};
- EXPECT_TRUE(base::CommandLine::Init(ARRAY_SIZE(argv), argv));
+ EXPECT_TRUE(base::CommandLine::Init(arraysize(argv), argv));
EXPECT_FALSE(settings_.Init());
}
TEST_F(SettingsTest, UnexpectedSwitches2) {
const base::CommandLine::CharType* argv[] = {"program", "--foobarbaz"};
- EXPECT_TRUE(base::CommandLine::Init(ARRAY_SIZE(argv), argv));
+ EXPECT_TRUE(base::CommandLine::Init(arraysize(argv), argv));
EXPECT_FALSE(settings_.Init());
}
TEST_F(SettingsTest, UnexpectedArguments1) {
const base::CommandLine::CharType* argv[] = {"program", "foobarbaz"};
- EXPECT_TRUE(base::CommandLine::Init(ARRAY_SIZE(argv), argv));
+ EXPECT_TRUE(base::CommandLine::Init(arraysize(argv), argv));
EXPECT_FALSE(settings_.Init());
}
TEST_F(SettingsTest, UnexpectedArguments2) {
const base::CommandLine::CharType* argv[] = {
"program", "--create-ipc-socket=foobar", "foobarbaz"};
- EXPECT_TRUE(base::CommandLine::Init(ARRAY_SIZE(argv), argv));
+ EXPECT_TRUE(base::CommandLine::Init(arraysize(argv), argv));
EXPECT_FALSE(settings_.Init());
}
@@ -80,21 +79,21 @@ TEST_F(SettingsTest, TooManyIpcOptions) {
const base::CommandLine::CharType* argv[] = {
"program", "--create-ipc-socket=foobar",
"--android-ipc-socket-suffix=foobar"};
- EXPECT_TRUE(base::CommandLine::Init(ARRAY_SIZE(argv), argv));
+ EXPECT_TRUE(base::CommandLine::Init(arraysize(argv), argv));
EXPECT_FALSE(settings_.Init());
}
TEST_F(SettingsTest, GoodArgumentsCreateIpc) {
const base::CommandLine::CharType* argv[] = {"program",
"--create-ipc-socket=foobar"};
- EXPECT_TRUE(base::CommandLine::Init(ARRAY_SIZE(argv), argv));
+ EXPECT_TRUE(base::CommandLine::Init(arraysize(argv), argv));
EXPECT_TRUE(settings_.Init());
}
TEST_F(SettingsTest, GoodArgumentsAndroidIpc) {
const base::CommandLine::CharType* argv[] = {
"program", "--android-ipc-socket-suffix=foobar"};
- EXPECT_TRUE(base::CommandLine::Init(ARRAY_SIZE(argv), argv));
+ EXPECT_TRUE(base::CommandLine::Init(arraysize(argv), argv));
EXPECT_TRUE(settings_.Init());
}
diff --git a/stack/Android.bp b/stack/Android.bp
index 9a5be5f67..2f3d12c15 100644
--- a/stack/Android.bp
+++ b/stack/Android.bp
@@ -1,29 +1,9 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- // SPDX-license-identifier-BSD
- default_applicable_licenses: ["system_bt_license"],
-}
-
crypto_toolbox_srcs = [
"crypto_toolbox/aes.cc",
"crypto_toolbox/aes_cmac.cc",
"crypto_toolbox/crypto_toolbox.cc",
]
-cc_test_library {
- name: "crypto_toolbox_for_tests",
- defaults: ["fluoride_defaults"],
- host_supported: true,
- include_dirs: [
- "system/bt",
- ],
- srcs: crypto_toolbox_srcs
-}
-
// Bluetooth stack static library for target
// ========================================================
cc_library_static {
@@ -36,13 +16,11 @@ cc_library_static {
"avrc",
"l2cap",
"avdt",
- "eatt",
"gatt",
"gap",
"pan",
"bnep",
"hid",
- "metrics",
"sdp",
"smp",
"srvc",
@@ -67,7 +45,6 @@ cc_library_static {
"system/bt/bta/include",
"system/bt/bta/sys",
"system/bt/utils/include",
- "system/bt/gd/rust/shim",
],
srcs: crypto_toolbox_srcs + [
"a2dp/a2dp_aac.cc",
@@ -115,33 +92,27 @@ cc_library_static {
"bnep/bnep_main.cc",
"bnep/bnep_utils.cc",
"btm/ble_advertiser_hci_interface.cc",
- "acl/acl.cc",
- "acl/btm_acl.cc",
- "acl/ble_acl.cc",
- "btm/ble_scanner_hci_interface.cc",
+ "btm/btm_acl.cc",
"btm/btm_ble.cc",
"btm/btm_ble_addr.cc",
"btm/btm_ble_adv_filter.cc",
"btm/btm_ble_batchscan.cc",
"btm/btm_ble_bgconn.cc",
- "acl/btm_ble_connection_establishment.cc",
+ "btm/btm_ble_connection_establishment.cc",
"btm/btm_ble_cont_energy.cc",
"btm/btm_ble_gap.cc",
"btm/btm_ble_multi_adv.cc",
"btm/btm_ble_privacy.cc",
- "btm/btm_client_interface.cc",
"btm/btm_dev.cc",
"btm/btm_devctl.cc",
"btm/btm_inq.cc",
"btm/btm_main.cc",
- "acl/btm_pm.cc",
+ "btm/btm_pm.cc",
"btm/btm_sco.cc",
- "btm/btm_iso.cc",
"btm/btm_sec.cc",
- "btm/btm_scn.cc",
"btu/btu_hcif.cc",
+ "btu/btu_init.cc",
"btu/btu_task.cc",
- "eatt/eatt.cc",
"gap/gap_ble.cc",
"gap/gap_conn.cc",
"gatt/att_protocol.cc",
@@ -153,7 +124,6 @@ cc_library_static {
"gatt/gatt_db.cc",
"gatt/gatt_main.cc",
"gatt/gatt_sr.cc",
- "gatt/gatt_sr_hash.cc",
"gatt/gatt_utils.cc",
"hcic/hciblecmds.cc",
"hcic/hcicmds.cc",
@@ -168,7 +138,6 @@ cc_library_static {
"l2cap/l2c_link.cc",
"l2cap/l2c_main.cc",
"l2cap/l2c_utils.cc",
- "metrics/stack_metrics_logging.cc",
"pan/pan_api.cc",
"pan/pan_main.cc",
"pan/pan_utils.cc",
@@ -207,13 +176,11 @@ cc_library_static {
shared_libs: [
"libcutils",
"liblog",
- "libcrypto",
],
required: [
"libldacBT_enc",
"libldacBT_abr",
],
- host_supported: true,
}
// Bluetooth stack unit tests for target
@@ -238,10 +205,7 @@ cc_test {
"android.hardware.bluetooth@1.1",
"android.hardware.bluetooth.a2dp@1.0",
"android.hardware.bluetooth.audio@2.0",
- "android.hardware.bluetooth.audio@2.1",
- "android.system.suspend.control-V1-ndk",
"libaaudio",
- "libbinder_ndk",
"libcutils",
"libdl",
"libfmq",
@@ -253,6 +217,12 @@ cc_test {
"libtinyxml2",
"libz",
"libcrypto",
+ "android.hardware.keymaster@4.0",
+ "android.hardware.keymaster@3.0",
+ "libkeymaster4support",
+ "libkeystore_aidl",
+ "libkeystore_binder",
+ "libkeystore_parcelables",
],
static_libs: [
"libbt-audio-hal-interface",
@@ -366,7 +336,6 @@ cc_test {
],
shared_libs: [
"libcutils",
- "libcrypto",
],
static_libs: [
"liblog",
@@ -429,125 +398,102 @@ cc_test {
],
}
-// Bluetooth stack connection multiplexing
+// Bluetooth stack message loop tests for target
// ========================================================
cc_test {
- name: "net_test_gatt_conn_multiplexing",
+ name: "net_test_btu_message_loop",
defaults: ["fluoride_defaults"],
local_include_dirs: [
"include",
"btm",
],
include_dirs: [
- "system/bt",
+ "system/bt/",
"system/bt/internal_include",
"system/bt/btcore/include",
- "system/bt/hci/include",
- "system/bt/internal_include",
- "system/bt/utils/include",
+ "system/bt/bta/include",
],
srcs: [
- "gatt/connection_manager.cc",
- "test/gatt_connection_manager_test.cc",
+ "btu/btu_task.cc",
+ "test/stack_btu_test.cc",
],
shared_libs: [
+ "liblog",
"libcutils",
+ "libprotobuf-cpp-lite",
],
static_libs: [
+ "libbt-common",
"libbluetooth-types",
- "liblog",
"libgmock",
+ "libosi",
+ "libbt-protos-lite",
],
sanitize: {
cfi: false,
},
}
+// Bluetooth stack connection multiplexing
+// ========================================================
cc_test {
- name: "net_test_stack_gatt_native",
+ name: "net_test_gatt_conn_multiplexing",
defaults: ["fluoride_defaults"],
- test_suites: ["device-tests"],
- host_supported: true,
- test_options: {
- unit_test: true,
- },
+ local_include_dirs: [
+ "include",
+ "btm",
+ ],
include_dirs: [
"system/bt",
- "system/bt/stack/include",
- "system/bt/stack/eatt",
- "system/bt/stack/l2cap",
- "system/bt/stack/btm",
+ "system/bt/internal_include",
+ "system/bt/btcore/include",
+ "system/bt/hci/include",
+ "system/bt/internal_include",
"system/bt/utils/include",
],
srcs: [
- "gatt/gatt_utils.cc",
- "test/common/mock_acl.cc",
- "test/common/mock_eatt.cc",
- "test/common/mock_gatt_layer.cc",
- "test/common/mock_main_shim.cc",
- "test/gatt/gatt_sr_test.cc",
+ "gatt/connection_manager.cc",
+ "test/gatt_connection_manager_test.cc",
],
shared_libs: [
"libcutils",
- "libprotobuf-cpp-lite",
- "libcrypto",
],
static_libs: [
+ "libbluetooth-types",
"liblog",
- "libosi",
- "libbt-common",
- "libbt-protos-lite",
"libgmock",
- "libosi-AllocationTestHarness",
],
sanitize: {
- address: true,
- cfi: true,
- misc_undefined: ["bounds"],
+ cfi: false,
},
}
cc_test {
- name: "net_test_stack_avdtp",
+ name: "net_test_stack_gatt_native",
defaults: ["fluoride_defaults"],
test_suites: ["device-tests"],
host_supported: true,
- test_options: {
- unit_test: true,
- },
include_dirs: [
- "external/libldac/inc",
"system/bt",
"system/bt/stack/include",
+ "system/bt/stack/l2cap",
+ "system/bt/stack/btm",
"system/bt/utils/include",
],
srcs: [
- "test/stack_avdtp_test.cc",
- "avdt/avdt_ad.cc",
- "avdt/avdt_api.cc",
- "avdt/avdt_ccb.cc",
- "avdt/avdt_ccb_act.cc",
- "avdt/avdt_l2c.cc",
- "avdt/avdt_scb.cc",
- "avdt/avdt_scb_act.cc",
- "test/common/mock_btu_layer.cc",
- "test/common/mock_stack_avdt_msg.cc",
- ":TestMockStackL2cap",
- ":TestMockStackAcl",
- ":TestMockStackA2dp",
- ":TestMockBta",
- ":TestMockDevice",
+ "test/gatt/gatt_sr_test.cc",
+ "gatt/gatt_utils.cc",
],
shared_libs: [
- "libcrypto",
"libcutils",
"libprotobuf-cpp-lite",
+ "libcrypto",
],
static_libs: [
- "libbt-common",
- "libbt-protos-lite",
"liblog",
"libosi",
+ "libbt-common",
+ "libbt-protos-lite",
"libosi-AllocationTestHarness",
],
sanitize: {
@@ -562,9 +508,6 @@ cc_test {
defaults: ["fluoride_defaults"],
test_suites: ["device-tests"],
host_supported: true,
- test_options: {
- unit_test: true,
- },
include_dirs: [
"external/libldac/inc",
"system/bt",
@@ -592,446 +535,3 @@ cc_test {
misc_undefined: ["bounds"],
},
}
-
-// gatt sr hash test
-cc_test {
- name: "net_test_stack_gatt_sr_hash_native",
- defaults: ["fluoride_defaults"],
- test_suites: ["device-tests"],
- host_supported: true,
- include_dirs: [
- "system/bt",
- "system/bt/stack/btm",
- "system/bt/stack/eatt",
- "system/bt/stack/include",
- "system/bt/utils/include",
- ],
- srcs: crypto_toolbox_srcs + [
- "gatt/gatt_db.cc",
- "gatt/gatt_sr_hash.cc",
- "gatt/gatt_utils.cc",
- "test/common/mock_acl.cc",
- "test/common/mock_eatt.cc",
- "test/common/mock_gatt_layer.cc",
- "test/common/mock_main_shim.cc",
- "test/gatt/mock_gatt_utils_ref.cc",
- "test/stack_gatt_sr_hash_test.cc",
- ],
- shared_libs: [
- "libcutils",
- "libcrypto",
- "libprotobuf-cpp-lite",
- ],
- static_libs: [
- "libbt-common",
- "libbt-protos-lite",
- "liblog",
- "libgmock",
- "libosi",
- ],
-}
-
-// Iso manager unit tests
-cc_test {
- name: "net_test_btm_iso",
- test_suites: ["device-tests"],
- host_supported: true,
- test_options: {
- unit_test: true,
- },
- defaults: ["fluoride_defaults"],
- local_include_dirs: [
- "btm",
- "include",
- "test/common",
- ],
- include_dirs: [
- "system/bt",
- "system/bt/btcore/include",
- ],
- srcs: [
- "btm/btm_iso.cc",
- "test/btm_iso_test.cc",
- "test/common/mock_controller.cc",
- "test/common/mock_gatt_layer.cc",
- "test/common/mock_hcic_layer.cc",
- ],
- static_libs: [
- "libbt-common",
- "libgmock",
- "liblog",
- "libosi",
- ],
- sanitize: {
- cfi: true,
- scs: true,
- address: true,
- all_undefined: true,
- integer_overflow: true,
- diag: {
- undefined : true
- },
- },
-}
-
-// EATT unit tests
-cc_test {
- name: "net_test_eatt",
- test_suites: ["device-tests"],
- host_supported: true,
- test_options: {
- unit_test: true,
- },
- defaults: [
- "fluoride_defaults",
- "clang_coverage_bin",
- ],
- local_include_dirs: [
- "include",
- "btm",
- "eatt",
- "gatt",
- "l2cap",
- "test/common",
- ],
- include_dirs:[
- "system/bt",
- "system/bt/btcore/include",
- ],
- srcs: [
- "eatt/eatt.cc",
- "test/common/mock_btm_api_layer.cc",
- "test/common/mock_btif_storage.cc",
- "test/common/mock_controller.cc",
- "test/common/mock_gatt_layer.cc",
- "test/common/mock_l2cap_layer.cc",
- "test/gatt/mock_gatt_utils_ref.cc",
- "test/eatt/eatt_test.cc",
- ],
- shared_libs: [
- "libcutils",
- "libcrypto",
- "libprotobuf-cpp-lite",
- ],
- static_libs: [
- "libbt-common",
- "libbt-protos-lite",
- "liblog",
- "libgmock",
- "libosi",
- ],
- sanitize: {
- cfi: false,
- },
-}
-
-cc_test {
- name: "net_test_stack_btm",
- test_suites: ["device-tests"],
- host_supported: true,
- test_options: {
- unit_test: true,
- },
- defaults: ["fluoride_defaults"],
- local_include_dirs: [
- "include",
- "btm",
- "test/common",
- ],
- include_dirs: [
- "system/bt",
- "system/bt/gd",
- "system/bt/vnd/ble",
- ],
- generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- "BluetoothGeneratedDumpsysDataSchema_h",
- "BluetoothGeneratedPackets_h",
- ],
- srcs: crypto_toolbox_srcs + [
- ":BluetoothBtaaSources_host",
- ":BluetoothHalSources_hci_host",
- ":BluetoothOsSources_host",
- ":TestMockBta",
- ":TestMockBtif",
- ":TestMockDevice",
- ":TestMockLegacyHciCommands",
- ":TestMockMainBte",
- ":TestMockMainShim",
- ":TestMockStackBtu",
- ":TestMockStackGap",
- ":TestMockStackGatt",
- ":TestMockStackSmp",
- ":TestStackL2cap",
- "acl/acl.cc",
- "acl/ble_acl.cc",
- "acl/btm_acl.cc",
- "acl/btm_ble_connection_establishment.cc",
- "acl/btm_pm.cc",
- "btm/ble_advertiser_hci_interface.cc",
- "btm/btm_ble.cc",
- "btm/btm_ble_addr.cc",
- "btm/btm_ble_adv_filter.cc",
- "btm/btm_ble_batchscan.cc",
- "btm/btm_ble_bgconn.cc",
- "btm/btm_ble_cont_energy.cc",
- "btm/btm_ble_gap.cc",
- "btm/btm_ble_multi_adv.cc",
- "btm/btm_ble_privacy.cc",
- "btm/btm_client_interface.cc",
- "btm/btm_dev.cc",
- "btm/btm_devctl.cc",
- "btm/btm_inq.cc",
- "btm/btm_iso.cc",
- "btm/btm_main.cc",
- "btm/btm_sco.cc",
- "btm/btm_scn.cc",
- "btm/btm_sec.cc",
- "metrics/stack_metrics_logging.cc",
- "test/btm/stack_btm_test.cc",
- "test/btm/peer_packet_types_test.cc",
- ],
- static_libs: [
- "libbt-common",
- "libbt-protos-lite",
- "libbtdevice",
- "libgmock",
- "liblog",
- "libosi",
- ],
- shared_libs: [
- "libcrypto",
- "libflatbuffers-cpp",
- "libprotobuf-cpp-lite",
- ],
- sanitize: {
- address: true,
- all_undefined: true,
- cfi: true,
- integer_overflow: true,
- scs: true,
- diag: {
- undefined : true
- },
- },
-}
-
-cc_test {
- name: "net_test_stack_hci",
- test_suites: ["device-tests"],
- host_supported: true,
- defaults: ["fluoride_defaults"],
- local_include_dirs: [
- "include",
- "btm",
- "test/common",
- ],
- include_dirs: [
- "system/bt",
- "system/bt/vnd/ble",
- ],
- srcs: crypto_toolbox_srcs + [
- "test/hci/stack_hci_test.cc",
- ],
- static_libs: [
- "libbt-common",
- "libbt-protos-lite",
- "libbte",
- "libgmock",
- "liblog",
- "libosi",
- "libbtdevice",
- ],
- shared_libs: [
- "libprotobuf-cpp-lite",
- "libcrypto",
- ],
- sanitize: {
- address: true,
- all_undefined: true,
- cfi: true,
- integer_overflow: true,
- scs: true,
- diag: {
- undefined : true
- },
- },
-}
-
-cc_test {
- name: "net_test_stack_hid",
- test_suites: ["device-tests"],
- host_supported: true,
- defaults: ["fluoride_defaults"],
- local_include_dirs: [
- "include",
- "test/common",
- ],
- include_dirs: [
- "system/bt",
- ],
- srcs: crypto_toolbox_srcs + [
- ":TestStackL2cap",
- ":TestStackSdp",
- ":TestStackBtm",
- ":TestStubLegacyTrace",
- "hid/hidd_api.cc",
- "hid/hidd_conn.cc",
- "hid/hidh_api.cc",
- "hid/hidh_conn.cc",
- "test/hid/stack_hid_test.cc",
- ],
- static_libs: [
- "libbt-common",
- "libbt-protos-lite",
- "libbtdevice",
- "libbte",
- "libgmock",
- "liblog",
- "libosi",
- ],
- shared_libs: [
- "libcrypto",
- "libprotobuf-cpp-lite",
- ],
- sanitize: {
- address: true,
- all_undefined: true,
- cfi: true,
- integer_overflow: true,
- scs: true,
- diag: {
- undefined : true
- },
- },
-}
-
-cc_test {
- name: "net_test_stack_btu",
- test_suites: ["device-tests"],
- host_supported: true,
- defaults: ["fluoride_defaults"],
- local_include_dirs: [
- "include",
- "test/common",
- ],
- include_dirs: [
- "system/bt",
- "system/bt/gd",
- ],
- generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- "BluetoothGeneratedDumpsysDataSchema_h",
- "BluetoothGeneratedPackets_h",
- ],
- srcs: [
- ":TestMockBta",
- ":TestMockBtif",
- ":TestMockHci",
- ":TestMockLegacyHciCommands",
- ":TestMockMainShim",
- ":TestMockStackAcl",
- ":TestMockStackSmp",
- ":TestStackBtm",
- ":TestStackL2cap",
- ":TestMockStackMetrics",
- "btu/btu_hcif.cc",
- "btu/btu_task.cc",
- "test/stack_btu_test.cc",
- ],
- static_libs: [
- "libbt-common",
- "libbt-protos-lite",
- "libbtdevice",
- "libgmock",
- "liblog",
- "libosi",
- ],
- shared_libs: [
- "libbinder_ndk",
- "libcrypto",
- "libflatbuffers-cpp",
- "libprotobuf-cpp-lite",
- ],
- sanitize: {
- address: true,
- all_undefined: true,
- cfi: true,
- integer_overflow: true,
- scs: true,
- diag: {
- undefined : true
- },
- },
-}
-
-cc_test {
- name: "net_test_stack_gatt",
- test_suites: ["device-tests"],
- host_supported: true,
- defaults: ["fluoride_defaults"],
- local_include_dirs: [
- "include",
- "test/common",
- ],
- include_dirs: [
- "system/bt",
- "system/bt/gd",
- "system/bt/utils/include",
- ],
- generated_headers: [
- "BluetoothGeneratedBundlerSchema_h_bfbs",
- "BluetoothGeneratedDumpsysDataSchema_h",
- "BluetoothGeneratedPackets_h",
- ],
- srcs: [
- ":TestMockBta",
- ":TestMockBtif",
- ":TestMockHci",
- ":TestMockLegacyHciCommands",
- ":TestMockMainShim",
- ":TestMockStackAcl",
- ":TestMockStackCryptotoolbox",
- ":TestMockStackSmp",
- ":TestStackBtm",
- ":TestStackL2cap",
- ":TestStackSdp",
- "eatt/eatt.cc",
- "gatt/att_protocol.cc",
- "gatt/connection_manager.cc",
- "gatt/gatt_api.cc",
- "gatt/gatt_attr.cc",
- "gatt/gatt_auth.cc",
- "gatt/gatt_cl.cc",
- "gatt/gatt_db.cc",
- "gatt/gatt_main.cc",
- "gatt/gatt_sr.cc",
- "gatt/gatt_sr_hash.cc",
- "gatt/gatt_utils.cc",
- "test/gatt/stack_gatt_test.cc",
- ],
- static_libs: [
- "libbt-common",
- "libbt-protos-lite",
- "libbtdevice",
- "libgmock",
- "liblog",
- "libosi",
- ],
- shared_libs: [
- "libbinder_ndk",
- "libcrypto",
- "libflatbuffers-cpp",
- "libprotobuf-cpp-lite",
- ],
- sanitize: {
- address: true,
- all_undefined: true,
- cfi: true,
- integer_overflow: true,
- scs: true,
- diag: {
- undefined : true
- },
- },
-}
diff --git a/stack/BUILD.gn b/stack/BUILD.gn
index 09756297a..8b39594a0 100644
--- a/stack/BUILD.gn
+++ b/stack/BUILD.gn
@@ -16,65 +16,40 @@
static_library("crypto_toolbox") {
sources = [
+ "crypto_toolbox/crypto_toolbox.cc",
"crypto_toolbox/aes.cc",
"crypto_toolbox/aes_cmac.cc",
- "crypto_toolbox/crypto_toolbox.cc",
]
- include_dirs = [ "//bt/" ]
-
- configs += [ "//bt:target_defaults" ]
-}
-
-source_set("nonstandard_codecs") {
- if (defined(use.bt_nonstandard_codecs) && use.bt_nonstandard_codecs) {
- sources = [
- "a2dp/a2dp_aac.cc",
- "a2dp/a2dp_aac_decoder.cc",
- "a2dp/a2dp_aac_encoder.cc",
- "a2dp/a2dp_vendor.cc",
- "a2dp/a2dp_vendor_aptx.cc",
- "a2dp/a2dp_vendor_aptx_encoder.cc",
- "a2dp/a2dp_vendor_aptx_hd.cc",
- "a2dp/a2dp_vendor_aptx_hd_encoder.cc",
- "a2dp/a2dp_vendor_ldac.cc",
- "a2dp/a2dp_vendor_ldac_abr.cc",
- "a2dp/a2dp_vendor_ldac_decoder.cc",
- "a2dp/a2dp_vendor_ldac_encoder.cc",
- ]
-
- include_dirs = [
- "//bt",
- "//bt/bta/include",
- "//bt/btif/include",
- "//bt/internal_include",
- "//bt/stack/include",
- "//bt/utils/include",
- ]
-
- deps = [ "//bt/gd/rust/shim:init_flags_bridge_header" ]
+ include_dirs = [
+ "//",
+ ]
- configs += [
- "//bt:target_defaults",
- "//bt:external_libldac",
- "//bt:external_aac",
- ]
- }
+ deps = [
+ "//third_party/libchrome:base",
+ ]
}
-source_set("stack") {
+static_library("stack") {
sources = [
+ "a2dp/a2dp_aac.cc",
+ "a2dp/a2dp_aac_decoder.cc",
+ "a2dp/a2dp_aac_encoder.cc",
"a2dp/a2dp_api.cc",
"a2dp/a2dp_codec_config.cc",
"a2dp/a2dp_sbc.cc",
"a2dp/a2dp_sbc_decoder.cc",
"a2dp/a2dp_sbc_encoder.cc",
"a2dp/a2dp_sbc_up_sample.cc",
- "acl/acl.cc",
- "acl/ble_acl.cc",
- "acl/btm_acl.cc",
- "acl/btm_ble_connection_establishment.cc",
- "acl/btm_pm.cc",
+ "a2dp/a2dp_vendor.cc",
+ "a2dp/a2dp_vendor_aptx.cc",
+ "a2dp/a2dp_vendor_aptx_encoder.cc",
+ "a2dp/a2dp_vendor_aptx_hd.cc",
+ "a2dp/a2dp_vendor_aptx_hd_encoder.cc",
+ "a2dp/a2dp_vendor_ldac.cc",
+ "a2dp/a2dp_vendor_ldac_abr.cc",
+ "a2dp/a2dp_vendor_ldac_decoder.cc",
+ "a2dp/a2dp_vendor_ldac_encoder.cc",
"avct/avct_api.cc",
"avct/avct_bcb_act.cc",
"avct/avct_ccb.cc",
@@ -102,7 +77,7 @@ source_set("stack") {
"bnep/bnep_main.cc",
"bnep/bnep_utils.cc",
"btm/ble_advertiser_hci_interface.cc",
- "btm/ble_scanner_hci_interface.cc",
+ "btm/btm_acl.cc",
"btm/btm_ble.cc",
"btm/btm_ble_addr.cc",
"btm/btm_ble_adv_filter.cc",
@@ -112,18 +87,16 @@ source_set("stack") {
"btm/btm_ble_gap.cc",
"btm/btm_ble_multi_adv.cc",
"btm/btm_ble_privacy.cc",
- "btm/btm_client_interface.cc",
"btm/btm_dev.cc",
"btm/btm_devctl.cc",
"btm/btm_inq.cc",
- "btm/btm_iso.cc",
"btm/btm_main.cc",
- "btm/btm_scn.cc",
+ "btm/btm_pm.cc",
"btm/btm_sco.cc",
"btm/btm_sec.cc",
"btu/btu_hcif.cc",
+ "btu/btu_init.cc",
"btu/btu_task.cc",
- "eatt/eatt.cc",
"gap/gap_ble.cc",
"gap/gap_conn.cc",
"gatt/att_protocol.cc",
@@ -135,14 +108,13 @@ source_set("stack") {
"gatt/gatt_db.cc",
"gatt/gatt_main.cc",
"gatt/gatt_sr.cc",
- "gatt/gatt_sr_hash.cc",
"gatt/gatt_utils.cc",
"hcic/hciblecmds.cc",
"hcic/hcicmds.cc",
- "hid/hidd_api.cc",
- "hid/hidd_conn.cc",
"hid/hidh_api.cc",
"hid/hidh_conn.cc",
+ "hid/hidd_api.cc",
+ "hid/hidd_conn.cc",
"l2cap/l2c_api.cc",
"l2cap/l2c_ble.cc",
"l2cap/l2c_csm.cc",
@@ -150,7 +122,6 @@ source_set("stack") {
"l2cap/l2c_link.cc",
"l2cap/l2c_main.cc",
"l2cap/l2c_utils.cc",
- "metrics/stack_metrics_logging.cc",
"pan/pan_api.cc",
"pan/pan_main.cc",
"pan/pan_utils.cc",
@@ -184,7 +155,6 @@ source_set("stack") {
]
include_dirs = [
- ".",
"include",
"avct",
"btm",
@@ -195,220 +165,187 @@ source_set("stack") {
"gap",
"pan",
"bnep",
- "eatt",
"hid",
- "metrics",
"sdp",
"smp",
"srvc",
- "//bt/types",
- "//bt/linux_include",
- "//bt/internal_include",
- "//bt/btcore/include",
- "//bt/vnd/include",
- "//bt/vnd/ble",
- "//bt/btif/include",
- "//bt/hci/include",
- "//bt/udrv/include",
- "//bt/rpc/include",
- "//bt/hcis",
- "//bt/ctrlr/include",
- "//bt/bta/include",
- "//bt/bta/sys",
- "//bt/utils/include",
- "//bt/",
+ "//linux_include",
+ "//internal_include",
+ "//btcore/include",
+ "//vnd/include",
+ "//vnd/ble",
+ "//btif/include",
+ "//hci/include",
+ "//internal_include",
+ "//udrv/include",
+ "//rpc/include",
+ "//hcis",
+ "//ctrlr/include",
+ "//bta/include",
+ "//bta/sys",
+ "//utils/include",
+ "//",
]
deps = [
":crypto_toolbox",
- ":nonstandard_codecs",
- "//bt:libbt-platform-protos-lite",
- "//bt/gd/rust/shim:init_flags_bridge_header",
- "//bt/types",
- "//bt/types",
+ "//types",
+ "//third_party/libchrome:base",
+ "//third_party/libldac:libldacBT_enc",
+ "//third_party/libldac:libldacBT_abr",
+ "//third_party/aac:libFraunhoferAAC",
]
-
- configs += [ "//bt:target_defaults" ]
}
-if (use.test) {
- executable("net_test_btm_iso") {
- sources = [
- "btm/btm_iso.cc",
- "test/btm_iso_test.cc",
- "test/common/mock_controller.cc",
- "test/common/mock_gatt_layer.cc",
- "test/common/mock_hcic_layer.cc",
- ]
+executable("stack_unittests") {
+ testonly = true
+ sources = [
+ "test/stack_a2dp_test.cc",
+ "test/stack_avrcp_test.cc",
+ ]
- include_dirs = [
- "btm",
- "include",
- "test/common",
- "//bt/internal_include",
- "//bt/packet/tests",
- ]
+ include_dirs = [
+ "include",
+ "//",
+ "//bta/include",
+ "//bta/sys",
+ "//btcore/include",
+ "//embdrv/sbc/encoder/include",
+ "//hci/include",
+ "//internal_include",
+ "//stack/a2dp",
+ "//stack/btm",
+ "//stack/include",
+ "//third_party/tinyxml2",
+ "//udrv/include",
+ "//utils/include",
+ "//vnd/include"
+ ]
- deps = [
- "//bt/common",
- "//bt/osi",
- ]
+ libs = [
+ "-ldl",
+ "-lpthread",
+ "-lresolv",
+ "-lrt",
+ "-lz",
+ "-latomic",
+ ]
- configs += [
- "//bt:external_gmock_main",
- "//bt:target_defaults",
- ]
- }
+ deps = [
+ ":stack",
+ "//osi",
+ "//btcore",
+ "//device",
+ "//embdrv/sbc",
+ "//embdrv/g722",
+ "//hci",
+ "//types",
+ "//main:bluetooth",
+ "//third_party/googletest:gmock_main",
+ "//third_party/libchrome:base",
+ ]
}
-if (defined(use.android) && use.android) {
- executable("stack_unittests") {
- sources = [
- "test/stack_a2dp_test.cc",
- "test/stack_avrcp_test.cc",
- ]
-
- include_dirs = [
- "include",
- "//bt/",
- "//bt/bta/eatt",
- "//bt/bta/include",
- "//bt/bta/sys",
- "//bt/btcore/include",
- "//bt/embdrv/sbc/encoder/include",
- "//bt/hci/include",
- "//bt/internal_include",
- "//bt/stack/a2dp",
- "//bt/stack/btm",
- "//bt/stack/include",
- "//bt/udrv/include",
- "//bt/utils/include",
- "//bt/vnd/include",
- ]
-
- libs = [
- "dl",
- "pthread",
- "resolv",
- "rt",
- "z",
- ]
-
- deps = [
- ":stack",
- "//bt/btcore",
- "//bt/device",
- "//bt/embdrv/g722",
- "//bt/embdrv/sbc",
- "//bt/hci",
- "//bt/main:bluetooth",
- "//bt/osi",
- "//bt/types",
- ]
-
- configs += [
- "//bt:external_tinyxml2",
- "//bt:external_gmock_main",
- "//bt:target_defaults",
- ]
- }
-
- executable("net_test_stack_crypto_toolbox") {
- sources = [ "test/crypto_toolbox_test.cc" ]
-
- include_dirs = [ "//bt/" ]
-
- deps = [ ":crypto_toolbox" ]
-
- configs += [
- "//bt:external_gmock_main",
- "//bt:target_defaults",
- ]
- }
+executable("net_test_stack_crypto_toolbox") {
+ testonly = true
+ sources = [
+ "test/crypto_toolbox_test.cc",
+ ]
- executable("net_test_stack_smp") {
- sources = [
- "smp/p_256_curvepara.cc",
- "smp/p_256_ecc_pp.cc",
- "smp/p_256_multprecision.cc",
- "smp/smp_api.cc",
- "smp/smp_keys.cc",
- "smp/smp_main.cc",
- "smp/smp_utils.cc",
- "test/stack_smp_test.cc",
- ]
+ include_dirs = [
+ "//",
+ ]
- include_dirs = [
- "//bt/",
- "//bt/linux_include",
- "//bt/internal_include",
- "//bt/btcore/include",
- "//bt/hci/include",
- "//bt/utils/include",
- "//bt/bta/include",
- "//bt/bta/sys",
- "//bt/btcore/include",
- "//bt/embdrv/sbc/encoder/include",
- "//bt/hci/include",
- "//bt/internal_include",
- "//bt/stack/a2dp",
- "//bt/stack/l2cap",
- "//bt/stack/btm",
- "//bt/stack/include",
- "//bt/udrv/include",
- "//bt/utils/include",
- "//bt/vnd/include",
- ]
+ deps = [
+ ":crypto_toolbox",
+ "//third_party/googletest:gmock_main",
+ "//third_party/libchrome:base",
+ ]
+}
- libs = [
- "dl",
- "pthread",
- "resolv",
- "rt",
- "z",
- ]
+executable("net_test_stack_smp") {
+ testonly = true
+ sources = [
+ "smp/p_256_curvepara.cc",
+ "smp/p_256_ecc_pp.cc",
+ "smp/p_256_multprecision.cc",
+ "smp/smp_keys.cc",
+ "smp/smp_api.cc",
+ "smp/smp_main.cc",
+ "smp/smp_utils.cc",
+ "test/stack_smp_test.cc",
+ ]
- deps = [
- ":crypto_toolbox",
- "//bt/osi",
- "//bt/types",
- ]
+ include_dirs = [
+ "//",
+ "//linux_include",
+ "//internal_include",
+ "//btcore/include",
+ "//hci/include",
+ "//utils/include",
+ "//bta/include",
+ "//bta/sys",
+ "//btcore/include",
+ "//embdrv/sbc/encoder/include",
+ "//hci/include",
+ "//internal_include",
+ "//stack/a2dp",
+ "//stack/l2cap",
+ "//stack/btm",
+ "//stack/include",
+ "//third_party/tinyxml2",
+ "//udrv/include",
+ "//utils/include",
+ "//vnd/include"
+ ]
- configs += [
- "//bt:external_tinyxml2",
- "//bt:external_gmock_main",
- "//bt:target_defaults",
- ]
- }
+ libs = [
+ "-ldl",
+ "-lpthread",
+ "-lresolv",
+ "-lrt",
+ "-lz",
+ "-latomic",
+ ]
- executable("net_test_stack_multi_adv") {
- sources = [
- "btm/btm_ble_multi_adv.cc",
- "test/ble_advertiser_test.cc",
- ]
+ deps = [
+ ":crypto_toolbox",
+ "//osi",
+ "//types",
+ "//third_party/googletest:gmock_main",
+ "//third_party/libchrome:base",
+ ]
+}
- include_dirs = [
- "include",
- "//bt/",
- "//bt/btcore/include",
- "//bt/hci/include",
- "//bt/internal_include",
- "//bt/stack/btm",
- ]
+executable("net_test_stack_multi_adv") {
+ testonly = true
+ sources = [
+ "btm/btm_ble_multi_adv.cc",
+ "test/ble_advertiser_test.cc",
+ ]
- libs = [
- "dl",
- "pthread",
- "resolv",
- "rt",
- "z",
- ]
+ include_dirs = [
+ "include",
+ "//",
+ "//btcore/include",
+ "//hci/include",
+ "//internal_include",
+ "//stack/btm",
+ ]
- deps = [ "//bt/types" ]
+ libs = [
+ "-ldl",
+ "-lpthread",
+ "-lresolv",
+ "-lrt",
+ "-lz",
+ "-latomic",
+ ]
- configs += [
- "//bt:external_gmock_main",
- "//bt:target_defaults",
- ]
- }
+ deps = [
+ "//types",
+ "//third_party/googletest:gmock_main",
+ "//third_party/libchrome:base",
+ ]
}
+
diff --git a/stack/a2dp/a2dp_aac.cc b/stack/a2dp/a2dp_aac.cc
index e58d7bdf2..a7b72181e 100644
--- a/stack/a2dp/a2dp_aac.cc
+++ b/stack/a2dp/a2dp_aac.cc
@@ -35,7 +35,6 @@
#include "bt_utils.h"
#include "osi/include/log.h"
#include "osi/include/osi.h"
-#include "osi/include/properties.h"
#define A2DP_AAC_DEFAULT_BITRATE 320000 // 320 kbps
#define A2DP_AAC_MIN_BITRATE 64000 // 64 kbps
@@ -51,11 +50,8 @@ typedef struct {
btav_a2dp_codec_bits_per_sample_t bits_per_sample;
} tA2DP_AAC_CIE;
-static bool aac_source_caps_configured = false;
-static tA2DP_AAC_CIE a2dp_aac_source_caps = {};
-
/* AAC Source codec capabilities */
-static const tA2DP_AAC_CIE a2dp_aac_cbr_source_caps = {
+static const tA2DP_AAC_CIE a2dp_aac_source_caps = {
// objectType
A2DP_AAC_OBJECT_TYPE_MPEG2_LC,
// sampleRate
@@ -70,22 +66,6 @@ static const tA2DP_AAC_CIE a2dp_aac_cbr_source_caps = {
// bits_per_sample
BTAV_A2DP_CODEC_BITS_PER_SAMPLE_16};
-/* AAC Source codec capabilities */
-static const tA2DP_AAC_CIE a2dp_aac_vbr_source_caps = {
- // objectType
- A2DP_AAC_OBJECT_TYPE_MPEG2_LC,
- // sampleRate
- // TODO: AAC 48.0kHz sampling rate should be added back - see b/62301376
- A2DP_AAC_SAMPLING_FREQ_44100,
- // channelMode
- A2DP_AAC_CHANNEL_MODE_STEREO,
- // variableBitRateSupport
- A2DP_AAC_VARIABLE_BIT_RATE_ENABLED,
- // bitRate
- A2DP_AAC_DEFAULT_BITRATE,
- // bits_per_sample
- BTAV_A2DP_CODEC_BITS_PER_SAMPLE_16};
-
/* AAC Sink codec capabilities */
static const tA2DP_AAC_CIE a2dp_aac_sink_caps = {
// objectType
@@ -295,23 +275,23 @@ static tA2DP_STATUS A2DP_CodecInfoMatchesCapabilityAac(
/* parse configuration */
status = A2DP_ParseInfoAac(&cfg_cie, p_codec_info, is_capability);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: parsing failed %d", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s: parsing failed %d", __func__, status);
return status;
}
/* verify that each parameter is in range */
- LOG_VERBOSE("%s: Object Type peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: Object Type peer: 0x%x, capability 0x%x", __func__,
cfg_cie.objectType, p_cap->objectType);
- LOG_VERBOSE("%s: Sample Rate peer: %u, capability %u", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: Sample Rate peer: %u, capability %u", __func__,
cfg_cie.sampleRate, p_cap->sampleRate);
- LOG_VERBOSE("%s: Channel Mode peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: Channel Mode peer: 0x%x, capability 0x%x", __func__,
cfg_cie.channelMode, p_cap->channelMode);
- LOG_VERBOSE("%s: Variable Bit Rate Support peer: 0x%x, capability 0x%x",
- __func__, cfg_cie.variableBitRateSupport,
- p_cap->variableBitRateSupport);
- LOG_VERBOSE("%s: Bit Rate peer: %u, capability %u", __func__, cfg_cie.bitRate,
- p_cap->bitRate);
+ LOG_VERBOSE(
+ LOG_TAG, "%s: Variable Bit Rate Support peer: 0x%x, capability 0x%x",
+ __func__, cfg_cie.variableBitRateSupport, p_cap->variableBitRateSupport);
+ LOG_VERBOSE(LOG_TAG, "%s: Bit Rate peer: %u, capability %u", __func__,
+ cfg_cie.bitRate, p_cap->bitRate);
/* Object Type */
if ((cfg_cie.objectType & p_cap->objectType) == 0) return A2DP_BAD_OBJ_TYPE;
@@ -343,12 +323,14 @@ bool A2DP_CodecTypeEqualsAac(const uint8_t* p_codec_info_a,
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoAac(&aac_cie_a, p_codec_info_a, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
a2dp_status = A2DP_ParseInfoAac(&aac_cie_b, p_codec_info_b, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
@@ -364,12 +346,14 @@ bool A2DP_CodecEqualsAac(const uint8_t* p_codec_info_a,
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoAac(&aac_cie_a, p_codec_info_a, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
a2dp_status = A2DP_ParseInfoAac(&aac_cie_b, p_codec_info_b, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
@@ -387,7 +371,8 @@ int A2DP_GetTrackSampleRateAac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAac(&aac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -427,7 +412,8 @@ int A2DP_GetTrackBitsPerSampleAac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAac(&aac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -441,7 +427,8 @@ int A2DP_GetTrackChannelCountAac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAac(&aac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -461,7 +448,8 @@ int A2DP_GetSinkTrackChannelTypeAac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAac(&aac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -481,7 +469,8 @@ int A2DP_GetObjectTypeCodeAac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAac(&aac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -504,7 +493,8 @@ int A2DP_GetChannelModeCodeAac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAac(&aac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -525,7 +515,8 @@ int A2DP_GetVariableBitRateSupportAac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAac(&aac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -546,7 +537,8 @@ int A2DP_GetBitRateAac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAac(&aac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -559,7 +551,8 @@ int A2DP_ComputeMaxBitRateAac(const uint8_t* p_codec_info, uint16_t mtu) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAac(&aac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -715,19 +708,7 @@ const char* A2DP_CodecIndexStrAac(void) { return "AAC"; }
const char* A2DP_CodecIndexStrAacSink(void) { return "AAC SINK"; }
-void aac_source_caps_initialize() {
- if (aac_source_caps_configured) {
- return;
- }
- a2dp_aac_source_caps =
- osi_property_get_bool("persist.bluetooth.a2dp_aac.vbr_supported", false)
- ? a2dp_aac_vbr_source_caps
- : a2dp_aac_cbr_source_caps;
- aac_source_caps_configured = true;
-}
-
bool A2DP_InitCodecConfigAac(AvdtpSepConfig* p_cfg) {
- aac_source_caps_initialize();
if (A2DP_BuildInfoAac(AVDT_MEDIA_TYPE_AUDIO, &a2dp_aac_source_caps,
p_cfg->codec_info) != A2DP_SUCCESS) {
return false;
@@ -773,7 +754,6 @@ A2dpCodecConfigAacSource::A2dpCodecConfigAacSource(
btav_a2dp_codec_priority_t codec_priority)
: A2dpCodecConfigAacBase(BTAV_A2DP_CODEC_INDEX_SOURCE_AAC,
A2DP_CodecIndexStrAac(), codec_priority, true) {
- aac_source_caps_initialize();
// Compute the local capability
if (a2dp_aac_source_caps.sampleRate & A2DP_AAC_SAMPLING_FREQ_44100) {
codec_local_capability_.sample_rate |= BTAV_A2DP_CODEC_SAMPLE_RATE_44100;
@@ -804,7 +784,7 @@ bool A2dpCodecConfigAacSource::init() {
// Load the encoder
if (!A2DP_LoadEncoderAac()) {
- LOG_ERROR("%s: cannot load the encoder", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot load the encoder", __func__);
return false;
}
@@ -1040,8 +1020,8 @@ bool A2dpCodecConfigAacBase::setCodecConfig(const uint8_t* p_peer_codec_info,
tA2DP_STATUS status =
A2DP_ParseInfoAac(&peer_info_cie, p_peer_codec_info, is_capability);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: can't parse peer's capabilities: error = %d", __func__,
- status);
+ LOG_ERROR(LOG_TAG, "%s: can't parse peer's capabilities: error = %d",
+ __func__, status);
goto fail;
}
@@ -1056,14 +1036,6 @@ bool A2dpCodecConfigAacBase::setCodecConfig(const uint8_t* p_peer_codec_info,
result_config_cie.variableBitRateSupport =
p_a2dp_aac_caps->variableBitRateSupport &
peer_info_cie.variableBitRateSupport;
- if (result_config_cie.variableBitRateSupport !=
- A2DP_AAC_VARIABLE_BIT_RATE_DISABLED) {
- codec_config_.codec_specific_1 =
- static_cast<int64_t>(AacEncoderBitrateMode::AACENC_BR_MODE_VBR_5);
- } else {
- codec_config_.codec_specific_1 =
- static_cast<int64_t>(AacEncoderBitrateMode::AACENC_BR_MODE_CBR);
- }
// Set the bit rate as follows:
// 1. If the remote device reports a bogus bit rate
@@ -1178,10 +1150,10 @@ bool A2dpCodecConfigAacBase::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.sample_rate == BTAV_A2DP_CODEC_SAMPLE_RATE_NONE) {
- LOG_ERROR(
- "%s: cannot match sample frequency: source caps = 0x%x "
- "peer info = 0x%x",
- __func__, p_a2dp_aac_caps->sampleRate, peer_info_cie.sampleRate);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match sample frequency: source caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, p_a2dp_aac_caps->sampleRate, peer_info_cie.sampleRate);
goto fail;
}
@@ -1253,11 +1225,11 @@ bool A2dpCodecConfigAacBase::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.bits_per_sample == BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE) {
- LOG_ERROR(
- "%s: cannot match bits per sample: default = 0x%x "
- "user preference = 0x%x",
- __func__, a2dp_aac_default_config.bits_per_sample,
- codec_user_config_.bits_per_sample);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match bits per sample: default = 0x%x "
+ "user preference = 0x%x",
+ __func__, a2dp_aac_default_config.bits_per_sample,
+ codec_user_config_.bits_per_sample);
goto fail;
}
@@ -1328,48 +1300,24 @@ bool A2dpCodecConfigAacBase::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.channel_mode == BTAV_A2DP_CODEC_CHANNEL_MODE_NONE) {
- LOG_ERROR(
- "%s: cannot match channel mode: source caps = 0x%x "
- "peer info = 0x%x",
- __func__, p_a2dp_aac_caps->channelMode, peer_info_cie.channelMode);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match channel mode: source caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, p_a2dp_aac_caps->channelMode,
+ peer_info_cie.channelMode);
+ goto fail;
+ }
+
+ if (A2DP_BuildInfoAac(AVDT_MEDIA_TYPE_AUDIO, &result_config_cie,
+ p_result_codec_config) != A2DP_SUCCESS) {
goto fail;
}
//
// Copy the codec-specific fields if they are not zero
//
- if (codec_user_config_.codec_specific_1 != 0) {
- if (result_config_cie.variableBitRateSupport !=
- A2DP_AAC_VARIABLE_BIT_RATE_DISABLED) {
- auto user_bitrate_mode = codec_user_config_.codec_specific_1;
- switch (static_cast<AacEncoderBitrateMode>(user_bitrate_mode)) {
- case AacEncoderBitrateMode::AACENC_BR_MODE_VBR_C:
- // VBR is supported, and is disabled by the user preference
- result_config_cie.variableBitRateSupport =
- A2DP_AAC_VARIABLE_BIT_RATE_DISABLED;
- [[fallthrough]];
- case AacEncoderBitrateMode::AACENC_BR_MODE_VBR_1:
- [[fallthrough]];
- case AacEncoderBitrateMode::AACENC_BR_MODE_VBR_2:
- [[fallthrough]];
- case AacEncoderBitrateMode::AACENC_BR_MODE_VBR_3:
- [[fallthrough]];
- case AacEncoderBitrateMode::AACENC_BR_MODE_VBR_4:
- [[fallthrough]];
- case AacEncoderBitrateMode::AACENC_BR_MODE_VBR_5:
- codec_config_.codec_specific_1 = codec_user_config_.codec_specific_1;
- break;
- default:
- codec_config_.codec_specific_1 =
- static_cast<int64_t>(AacEncoderBitrateMode::AACENC_BR_MODE_VBR_5);
- }
- } else {
- // It is no needed to check the user preference when Variable Bitrate
- // unsupported by one of source or sink
- codec_config_.codec_specific_1 =
- static_cast<int64_t>(AacEncoderBitrateMode::AACENC_BR_MODE_CBR);
- }
- }
+ if (codec_user_config_.codec_specific_1 != 0)
+ codec_config_.codec_specific_1 = codec_user_config_.codec_specific_1;
if (codec_user_config_.codec_specific_2 != 0)
codec_config_.codec_specific_2 = codec_user_config_.codec_specific_2;
if (codec_user_config_.codec_specific_3 != 0)
@@ -1377,11 +1325,6 @@ bool A2dpCodecConfigAacBase::setCodecConfig(const uint8_t* p_peer_codec_info,
if (codec_user_config_.codec_specific_4 != 0)
codec_config_.codec_specific_4 = codec_user_config_.codec_specific_4;
- if (A2DP_BuildInfoAac(AVDT_MEDIA_TYPE_AUDIO, &result_config_cie,
- p_result_codec_config) != A2DP_SUCCESS) {
- goto fail;
- }
-
// Create a local copy of the peer codec capability/config, and the
// result codec config.
if (is_capability) {
@@ -1418,7 +1361,6 @@ bool A2dpCodecConfigAacBase::setPeerCodecCapabilities(
tA2DP_AAC_CIE peer_info_cie;
uint8_t channelMode;
uint16_t sampleRate;
- uint8_t variableBitRateSupport;
const tA2DP_AAC_CIE* p_a2dp_aac_caps =
(is_source_) ? &a2dp_aac_source_caps : &a2dp_aac_sink_caps;
@@ -1432,8 +1374,8 @@ bool A2dpCodecConfigAacBase::setPeerCodecCapabilities(
tA2DP_STATUS status =
A2DP_ParseInfoAac(&peer_info_cie, p_peer_codec_capabilities, true);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: can't parse peer's capabilities: error = %d", __func__,
- status);
+ LOG_ERROR(LOG_TAG, "%s: can't parse peer's capabilities: error = %d",
+ __func__, status);
goto fail;
}
@@ -1471,17 +1413,6 @@ bool A2dpCodecConfigAacBase::setPeerCodecCapabilities(
BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO;
}
- // Compute the selectable capability - variable bitrate mode
- variableBitRateSupport = p_a2dp_aac_caps->variableBitRateSupport &
- peer_info_cie.variableBitRateSupport;
- if (variableBitRateSupport != A2DP_AAC_VARIABLE_BIT_RATE_DISABLED) {
- codec_selectable_capability_.codec_specific_1 =
- static_cast<int64_t>(AacEncoderBitrateMode::AACENC_BR_MODE_VBR_5);
- } else {
- codec_selectable_capability_.codec_specific_1 =
- static_cast<int64_t>(AacEncoderBitrateMode::AACENC_BR_MODE_CBR);
- }
-
status = A2DP_BuildInfoAac(AVDT_MEDIA_TYPE_AUDIO, &peer_info_cie,
ota_codec_peer_capability_);
CHECK(status == A2DP_SUCCESS);
@@ -1508,7 +1439,7 @@ bool A2dpCodecConfigAacSink::init() {
// Load the decoder
if (!A2DP_LoadDecoderAac()) {
- LOG_ERROR("%s: cannot load the decoder", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot load the decoder", __func__);
return false;
}
diff --git a/stack/a2dp/a2dp_aac_decoder.cc b/stack/a2dp/a2dp_aac_decoder.cc
index 55c020d04..d998d7d47 100644
--- a/stack/a2dp/a2dp_aac_decoder.cc
+++ b/stack/a2dp/a2dp_aac_decoder.cc
@@ -70,7 +70,7 @@ bool a2dp_aac_decoder_decode_packet(BT_HDR* p_buf) {
AAC_DECODER_ERROR err = aacDecoder_Fill(a2dp_aac_decoder_cb.aac_handle,
&pBuffer, &bufferSize, &bytesValid);
if (err != AAC_DEC_OK) {
- LOG_ERROR("%s: aacDecoder_Fill failed: 0x%x", __func__,
+ LOG_ERROR(LOG_TAG, "%s: aacDecoder_Fill failed: 0x%x", __func__,
static_cast<unsigned>(err));
return false;
}
@@ -83,7 +83,7 @@ bool a2dp_aac_decoder_decode_packet(BT_HDR* p_buf) {
break;
}
if (err != AAC_DEC_OK) {
- LOG_ERROR("%s: aacDecoder_DecodeFrame failed: 0x%x", __func__,
+ LOG_ERROR(LOG_TAG, "%s: aacDecoder_DecodeFrame failed: 0x%x", __func__,
static_cast<int>(err));
break;
}
@@ -91,7 +91,7 @@ bool a2dp_aac_decoder_decode_packet(BT_HDR* p_buf) {
CStreamInfo* info =
aacDecoder_GetStreamInfo(a2dp_aac_decoder_cb.aac_handle);
if (!info || info->sampleRate <= 0) {
- LOG_ERROR("%s: Invalid stream info", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Invalid stream info", __func__);
break;
}
diff --git a/stack/a2dp/a2dp_aac_encoder.cc b/stack/a2dp/a2dp_aac_encoder.cc
index 3f2d4d648..665bb04aa 100644
--- a/stack/a2dp/a2dp_aac_encoder.cc
+++ b/stack/a2dp/a2dp_aac_encoder.cc
@@ -19,6 +19,7 @@
#include "a2dp_aac_encoder.h"
#include <inttypes.h>
+#include <math.h>
#include <stdio.h>
#include <string.h>
@@ -55,9 +56,9 @@ typedef struct {
} tA2DP_AAC_ENCODER_PARAMS;
typedef struct {
- float counter;
- uint32_t bytes_per_tick; /* pcm bytes read each media task tick */
- uint64_t last_frame_us;
+ uint32_t counter;
+ uint32_t bytes_per_tick; // pcm bytes read each media task tick
+ uint64_t last_frame_timestamp_100ns; // values in 1/10 microseconds
} tA2DP_AAC_FEEDING_STATE;
typedef struct {
@@ -161,10 +162,10 @@ bool A2dpCodecConfigAacSource::updateEncoderUserConfig(
a2dp_aac_encoder_cb.timestamp = 0;
if (a2dp_aac_encoder_cb.peer_mtu == 0) {
- LOG_ERROR(
- "%s: Cannot update the codec encoder for %s: "
- "invalid peer MTU",
- __func__, name().c_str());
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot update the codec encoder for %s: "
+ "invalid peer MTU",
+ __func__, name().c_str());
return false;
}
@@ -195,18 +196,18 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
AACENC_ERROR aac_error = aacEncOpen(&a2dp_aac_encoder_cb.aac_handle, 0,
2 /* max 2 channels: stereo */);
if (aac_error != AACENC_OK) {
- LOG_ERROR("%s: Cannot open AAC encoder handle: AAC error 0x%x", __func__,
- aac_error);
+ LOG_ERROR(LOG_TAG, "%s: Cannot open AAC encoder handle: AAC error 0x%x",
+ __func__, aac_error);
return; // TODO: Return an error?
}
a2dp_aac_encoder_cb.has_aac_handle = true;
}
if (!a2dp_codec_config->copyOutOtaCodecConfig(codec_info)) {
- LOG_ERROR(
- "%s: Cannot update the codec encoder for %s: "
- "invalid codec config",
- __func__, a2dp_codec_config->name().c_str());
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot update the codec encoder for %s: "
+ "invalid codec config",
+ __func__, a2dp_codec_config->name().c_str());
return;
}
const uint8_t* p_codec_info = codec_info;
@@ -217,27 +218,28 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
p_feeding_params->bits_per_sample =
a2dp_codec_config->getAudioBitsPerSample();
p_feeding_params->channel_count = A2DP_GetTrackChannelCountAac(p_codec_info);
- LOG_INFO("%s: sample_rate=%u bits_per_sample=%u channel_count=%u", __func__,
- p_feeding_params->sample_rate, p_feeding_params->bits_per_sample,
- p_feeding_params->channel_count);
+ LOG_DEBUG(LOG_TAG, "%s: sample_rate=%u bits_per_sample=%u channel_count=%u",
+ __func__, p_feeding_params->sample_rate,
+ p_feeding_params->bits_per_sample, p_feeding_params->channel_count);
// The codec parameters
p_encoder_params->sample_rate =
a2dp_aac_encoder_cb.feeding_params.sample_rate;
p_encoder_params->channel_mode = A2DP_GetChannelModeCodeAac(p_codec_info);
- LOG_VERBOSE("%s: original AVDTP MTU size: %d", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: original AVDTP MTU size: %d", __func__,
a2dp_aac_encoder_cb.TxAaMtuSize);
if (a2dp_aac_encoder_cb.is_peer_edr &&
!a2dp_aac_encoder_cb.peer_supports_3mbps) {
// This condition would be satisfied only if the remote device is
// EDR and supports only 2 Mbps, but the effective AVDTP MTU size
// exceeds the 2DH5 packet size.
- LOG_VERBOSE("%s: The remote device is EDR but does not support 3 Mbps",
+ LOG_VERBOSE(LOG_TAG,
+ "%s: The remote device is EDR but does not support 3 Mbps",
__func__);
if (peer_mtu > MAX_2MBPS_AVDTP_MTU) {
- LOG_WARN("%s: Restricting AVDTP MTU size from %d to %d", __func__,
- peer_mtu, MAX_2MBPS_AVDTP_MTU);
+ LOG_WARN(LOG_TAG, "%s: Restricting AVDTP MTU size from %d to %d",
+ __func__, peer_mtu, MAX_2MBPS_AVDTP_MTU);
peer_mtu = MAX_2MBPS_AVDTP_MTU;
}
}
@@ -248,10 +250,10 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
a2dp_aac_encoder_cb.TxAaMtuSize = peer_mtu;
}
- LOG_INFO("%s: MTU=%d, peer_mtu=%d", __func__, a2dp_aac_encoder_cb.TxAaMtuSize,
- peer_mtu);
- LOG_INFO("%s: sample_rate: %d channel_mode: %d ", __func__,
- p_encoder_params->sample_rate, p_encoder_params->channel_mode);
+ LOG_DEBUG(LOG_TAG, "%s: MTU=%d, peer_mtu=%d", __func__,
+ a2dp_aac_encoder_cb.TxAaMtuSize, peer_mtu);
+ LOG_DEBUG(LOG_TAG, "%s: sample_rate: %d channel_mode: %d ", __func__,
+ p_encoder_params->sample_rate, p_encoder_params->channel_mode);
// Set the encoder's parameters: Audio Object Type - MANDATORY
// A2DP_AAC_OBJECT_TYPE_MPEG2_LC -> AOT_AAC_LC
@@ -274,19 +276,19 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
aac_param_value = AOT_AAC_SCAL;
break;
default:
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_AOT: "
- "invalid object type %d",
- __func__, object_type);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_AOT: "
+ "invalid object type %d",
+ __func__, object_type);
return; // TODO: Return an error?
}
aac_error = aacEncoder_SetParam(a2dp_aac_encoder_cb.aac_handle, AACENC_AOT,
aac_param_value);
if (aac_error != AACENC_OK) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_AOT to %d: "
- "AAC error 0x%x",
- __func__, aac_param_value, aac_error);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_AOT to %d: "
+ "AAC error 0x%x",
+ __func__, aac_param_value, aac_error);
return; // TODO: Return an error?
}
@@ -295,10 +297,10 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
aac_error = aacEncoder_SetParam(a2dp_aac_encoder_cb.aac_handle,
AACENC_AUDIOMUXVER, aac_param_value);
if (aac_error != AACENC_OK) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_AUDIOMUXVER to %d: "
- "AAC error 0x%x",
- __func__, aac_param_value, aac_error);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_AUDIOMUXVER to %d: "
+ "AAC error 0x%x",
+ __func__, aac_param_value, aac_error);
return; // TODO: Return an error?
}
@@ -307,10 +309,10 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
aac_error = aacEncoder_SetParam(a2dp_aac_encoder_cb.aac_handle,
AACENC_SIGNALING_MODE, aac_param_value);
if (aac_error != AACENC_OK) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_SIGNALING_MODE to %d: "
- "AAC error 0x%x",
- __func__, aac_param_value, aac_error);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_SIGNALING_MODE to %d: "
+ "AAC error 0x%x",
+ __func__, aac_param_value, aac_error);
return; // TODO: Return an error?
}
@@ -319,10 +321,10 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
aac_error = aacEncoder_SetParam(a2dp_aac_encoder_cb.aac_handle,
AACENC_SAMPLERATE, aac_param_value);
if (aac_error != AACENC_OK) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_SAMPLERATE to %d: "
- "AAC error 0x%x",
- __func__, aac_param_value, aac_error);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_SAMPLERATE to %d: "
+ "AAC error 0x%x",
+ __func__, aac_param_value, aac_error);
return; // TODO: Return an error?
}
aac_sampling_freq = aac_param_value; // Save for extra usage below
@@ -333,22 +335,23 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
aac_peak_bit_rate =
A2DP_ComputeMaxBitRateAac(p_codec_info, a2dp_aac_encoder_cb.TxAaMtuSize);
aac_param_value = std::min(aac_param_value, aac_peak_bit_rate);
- LOG_INFO("%s: MTU = %d Sampling Frequency = %d Bit Rate = %d", __func__,
- a2dp_aac_encoder_cb.TxAaMtuSize, aac_sampling_freq, aac_param_value);
+ LOG_DEBUG(LOG_TAG, "%s: MTU = %d Sampling Frequency = %d Bit Rate = %d",
+ __func__, a2dp_aac_encoder_cb.TxAaMtuSize, aac_sampling_freq,
+ aac_param_value);
if (aac_param_value == -1) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_BITRATE: "
- "invalid codec bit rate",
- __func__);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_BITRATE: "
+ "invalid codec bit rate",
+ __func__);
return; // TODO: Return an error?
}
aac_error = aacEncoder_SetParam(a2dp_aac_encoder_cb.aac_handle,
AACENC_BITRATE, aac_param_value);
if (aac_error != AACENC_OK) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_BITRATE to %d: "
- "AAC error 0x%x",
- __func__, aac_param_value, aac_error);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_BITRATE to %d: "
+ "AAC error 0x%x",
+ __func__, aac_param_value, aac_error);
return; // TODO: Return an error?
}
@@ -356,10 +359,10 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
aac_error = aacEncoder_SetParam(a2dp_aac_encoder_cb.aac_handle,
AACENC_PEAK_BITRATE, aac_peak_bit_rate);
if (aac_error != AACENC_OK) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_PEAK_BITRATE to %d: "
- "AAC error 0x%x",
- __func__, aac_peak_bit_rate, aac_error);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_PEAK_BITRATE to %d: "
+ "AAC error 0x%x",
+ __func__, aac_peak_bit_rate, aac_error);
return; // TODO: Return an error?
}
@@ -372,10 +375,10 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
aac_error = aacEncoder_SetParam(a2dp_aac_encoder_cb.aac_handle,
AACENC_CHANNELMODE, aac_param_value);
if (aac_error != AACENC_OK) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_CHANNELMODE to %d: "
- "AAC error 0x%x",
- __func__, aac_param_value, aac_error);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_CHANNELMODE to %d: "
+ "AAC error 0x%x",
+ __func__, aac_param_value, aac_error);
return; // TODO: Return an error?
}
@@ -384,10 +387,10 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
aac_error = aacEncoder_SetParam(a2dp_aac_encoder_cb.aac_handle,
AACENC_TRANSMUX, aac_param_value);
if (aac_error != AACENC_OK) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_TRANSMUX to %d: "
- "AAC error 0x%x",
- __func__, aac_param_value, aac_error);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_TRANSMUX to %d: "
+ "AAC error 0x%x",
+ __func__, aac_param_value, aac_error);
return; // TODO: Return an error?
}
@@ -396,51 +399,29 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
aac_error = aacEncoder_SetParam(a2dp_aac_encoder_cb.aac_handle,
AACENC_HEADER_PERIOD, aac_param_value);
if (aac_error != AACENC_OK) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_HEADER_PERIOD to %d: "
- "AAC error 0x%x",
- __func__, aac_param_value, aac_error);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_HEADER_PERIOD to %d: "
+ "AAC error 0x%x",
+ __func__, aac_param_value, aac_error);
return; // TODO: Return an error?
}
// Set the encoder's parameters: Variable Bit Rate Support
aac_param_value = A2DP_GetVariableBitRateSupportAac(p_codec_info);
if (aac_param_value == -1) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_BITRATEMODE: "
- "invalid codec bit rate mode",
- __func__);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_BITRATEMODE: "
+ "invalid codec bit rate mode",
+ __func__);
return; // TODO: Return an error?
- } else if (aac_param_value == A2DP_AAC_VARIABLE_BIT_RATE_ENABLED) {
- // VBR has 5 modes defined in external/aac/libAACenc/src/aacenc.h
- // A2DP_AAC_VARIABLE_BIT_RATE_DISABLED is equal to AACENC_BR_MODE_CBR
- auto bitrate_mode = a2dp_codec_config->getCodecConfig().codec_specific_1;
- switch (static_cast<AacEncoderBitrateMode>(bitrate_mode)) {
- case AacEncoderBitrateMode::AACENC_BR_MODE_VBR_1:
- [[fallthrough]];
- case AacEncoderBitrateMode::AACENC_BR_MODE_VBR_2:
- [[fallthrough]];
- case AacEncoderBitrateMode::AACENC_BR_MODE_VBR_3:
- [[fallthrough]];
- case AacEncoderBitrateMode::AACENC_BR_MODE_VBR_4:
- [[fallthrough]];
- case AacEncoderBitrateMode::AACENC_BR_MODE_VBR_5:
- break;
- default:
- bitrate_mode =
- static_cast<int64_t>(AacEncoderBitrateMode::AACENC_BR_MODE_VBR_5);
- }
- aac_param_value =
- static_cast<uint8_t>(bitrate_mode) & ~A2DP_AAC_VARIABLE_BIT_RATE_MASK;
}
- LOG_INFO("%s: AACENC_BITRATEMODE: %d", __func__, aac_param_value);
aac_error = aacEncoder_SetParam(a2dp_aac_encoder_cb.aac_handle,
AACENC_BITRATEMODE, aac_param_value);
if (aac_error != AACENC_OK) {
- LOG_ERROR(
- "%s: Cannot set AAC parameter AACENC_BITRATEMODE to %d: "
- "AAC error 0x%x",
- __func__, aac_param_value, aac_error);
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot set AAC parameter AACENC_BITRATEMODE to %d: "
+ "AAC error 0x%x",
+ __func__, aac_param_value, aac_error);
return; // TODO: Return an error?
}
@@ -448,7 +429,8 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
aac_error =
aacEncEncode(a2dp_aac_encoder_cb.aac_handle, NULL, NULL, NULL, NULL);
if (aac_error != AACENC_OK) {
- LOG_ERROR("%s: Cannot complete setting the AAC parameters: AAC error 0x%x",
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot complete setting the AAC parameters: AAC error 0x%x",
__func__, aac_error);
return; // TODO: Return an error?
}
@@ -457,19 +439,20 @@ static void a2dp_aac_encoder_update(uint16_t peer_mtu,
AACENC_InfoStruct aac_info;
aac_error = aacEncInfo(a2dp_aac_encoder_cb.aac_handle, &aac_info);
if (aac_error != AACENC_OK) {
- LOG_ERROR("%s: Cannot retrieve the AAC encoder info: AAC error 0x%x",
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot retrieve the AAC encoder info: AAC error 0x%x",
__func__, aac_error);
return; // TODO: Return an error?
}
p_encoder_params->frame_length = aac_info.frameLength;
p_encoder_params->input_channels_n = aac_info.inputChannels;
p_encoder_params->max_encoded_buffer_bytes = aac_info.maxOutBufBytes;
- LOG_INFO(
- "%s: AAC frame_length = %u input_channels_n = %u "
- "max_encoded_buffer_bytes = %d",
- __func__, p_encoder_params->frame_length,
- p_encoder_params->input_channels_n,
- p_encoder_params->max_encoded_buffer_bytes);
+ LOG_DEBUG(LOG_TAG,
+ "%s: AAC frame_length = %u input_channels_n = %u "
+ "max_encoded_buffer_bytes = %d",
+ __func__, p_encoder_params->frame_length,
+ p_encoder_params->input_channels_n,
+ p_encoder_params->max_encoded_buffer_bytes);
// After encoder params ready, reset the feeding state and its interval.
a2dp_aac_feeding_reset();
@@ -485,7 +468,7 @@ void a2dp_aac_feeding_reset(void) {
auto frame_length = a2dp_aac_encoder_cb.aac_encoder_params.frame_length;
auto sample_rate = a2dp_aac_encoder_cb.feeding_params.sample_rate;
if (frame_length == 0 || sample_rate == 0) {
- LOG_WARN("%s: AAC encoder is not configured", __func__);
+ LOG_WARN(LOG_TAG, "%s: AAC encoder is not configured", __func__);
a2dp_aac_encoder_interval_ms = A2DP_AAC_ENCODER_INTERVAL_MS;
} else {
// PCM data size per AAC frame (bits)
@@ -510,13 +493,13 @@ void a2dp_aac_feeding_reset(void) {
a2dp_aac_encoder_interval_ms) /
1000;
- LOG_INFO("%s: PCM bytes %u per tick %u ms", __func__,
+ LOG_INFO(LOG_TAG, "%s: PCM bytes %u per tick %u ms", __func__,
a2dp_aac_encoder_cb.aac_feeding_state.bytes_per_tick,
a2dp_aac_encoder_interval_ms);
}
void a2dp_aac_feeding_flush(void) {
- a2dp_aac_encoder_cb.aac_feeding_state.counter = 0.0f;
+ a2dp_aac_encoder_cb.aac_feeding_state.counter = 0;
}
uint64_t a2dp_aac_get_encoder_interval_ms(void) {
@@ -528,8 +511,8 @@ void a2dp_aac_send_frames(uint64_t timestamp_us) {
uint8_t nb_iterations = 0;
a2dp_aac_get_num_frame_iteration(&nb_iterations, &nb_frame, timestamp_us);
- LOG_VERBOSE("%s: Sending %d frames per iteration, %d iterations", __func__,
- nb_frame, nb_iterations);
+ LOG_VERBOSE(LOG_TAG, "%s: Sending %d frames per iteration, %d iterations",
+ __func__, nb_frame, nb_iterations);
if (nb_frame == 0) return;
for (uint8_t counter = 0; counter < nb_iterations; counter++) {
@@ -552,25 +535,40 @@ static void a2dp_aac_get_num_frame_iteration(uint8_t* num_of_iterations,
a2dp_aac_encoder_cb.aac_encoder_params.frame_length *
a2dp_aac_encoder_cb.feeding_params.channel_count *
a2dp_aac_encoder_cb.feeding_params.bits_per_sample / 8;
- LOG_VERBOSE("%s: pcm_bytes_per_frame %u", __func__, pcm_bytes_per_frame);
-
- uint32_t us_this_tick = a2dp_aac_encoder_interval_ms * 1000;
- uint64_t now_us = timestamp_us;
- if (a2dp_aac_encoder_cb.aac_feeding_state.last_frame_us != 0)
- us_this_tick =
- (now_us - a2dp_aac_encoder_cb.aac_feeding_state.last_frame_us);
- a2dp_aac_encoder_cb.aac_feeding_state.last_frame_us = now_us;
-
- a2dp_aac_encoder_cb.aac_feeding_state.counter +=
- (float)a2dp_aac_encoder_cb.aac_feeding_state.bytes_per_tick *
- us_this_tick / (a2dp_aac_encoder_interval_ms * 1000);
+ LOG_VERBOSE(LOG_TAG, "%s: pcm_bytes_per_frame %u", __func__,
+ pcm_bytes_per_frame);
+
+ uint32_t hecto_ns_this_tick = a2dp_aac_encoder_interval_ms * 10000;
+ uint64_t* last_100ns =
+ &a2dp_aac_encoder_cb.aac_feeding_state.last_frame_timestamp_100ns;
+ uint64_t now_100ns = timestamp_us * 10;
+ if (*last_100ns != 0) {
+ hecto_ns_this_tick = (now_100ns - *last_100ns);
+ }
+ *last_100ns = now_100ns;
+
+ uint32_t bytes_this_tick =
+ a2dp_aac_encoder_cb.aac_feeding_state.bytes_per_tick *
+ hecto_ns_this_tick / (a2dp_aac_encoder_interval_ms * 10000);
+ a2dp_aac_encoder_cb.aac_feeding_state.counter += bytes_this_tick;
+ // Without this erratum, there was a three microseocnd shift per tick which
+ // would cause one frame mismatched after every 180 seconds
+ uint32_t erratum_100ns =
+ ceil(1.0f * bytes_this_tick * a2dp_aac_encoder_interval_ms * 10000 /
+ a2dp_aac_encoder_cb.aac_feeding_state.bytes_per_tick);
+ if (erratum_100ns < hecto_ns_this_tick) {
+ LOG_VERBOSE(LOG_TAG,
+ "%s: hecto_ns_this_tick=%d, bytes=%d, erratum_100ns=%d",
+ __func__, hecto_ns_this_tick, bytes_this_tick, erratum_100ns);
+ *last_100ns -= hecto_ns_this_tick - erratum_100ns;
+ }
result = a2dp_aac_encoder_cb.aac_feeding_state.counter / pcm_bytes_per_frame;
a2dp_aac_encoder_cb.aac_feeding_state.counter -= result * pcm_bytes_per_frame;
nof = result;
- LOG_VERBOSE("%s: effective num of frames %u, iterations %u", __func__, nof,
- noi);
+ LOG_VERBOSE(LOG_TAG, "%s: effective num of frames %u, iterations %u",
+ __func__, nof, noi);
*num_of_frames = nof;
*num_of_iterations = noi;
@@ -642,7 +640,7 @@ static void a2dp_aac_encode_frames(uint8_t nb_frame) {
if (a2dp_aac_read_feeding(read_buffer, &bytes_read)) {
uint8_t* packet = (uint8_t*)(p_buf + 1) + p_buf->offset + p_buf->len;
if (!a2dp_aac_encoder_cb.has_aac_handle) {
- LOG_ERROR("%s: invalid AAC handle", __func__);
+ LOG_ERROR(LOG_TAG, "%s: invalid AAC handle", __func__);
a2dp_aac_encoder_cb.stats.media_read_total_dropped_packets++;
osi_free(p_buf);
return;
@@ -653,7 +651,8 @@ static void a2dp_aac_encode_frames(uint8_t nb_frame) {
aacEncEncode(a2dp_aac_encoder_cb.aac_handle, &in_buf_desc,
&out_buf_desc, &aac_in_args, &aac_out_args);
if (aac_error != AACENC_OK) {
- LOG_ERROR("%s: AAC encoding error: 0x%x", __func__, aac_error);
+ LOG_ERROR(LOG_TAG, "%s: AAC encoding error: 0x%x", __func__,
+ aac_error);
a2dp_aac_encoder_cb.stats.media_read_total_dropped_packets++;
osi_free(p_buf);
return;
@@ -664,7 +663,7 @@ static void a2dp_aac_encode_frames(uint8_t nb_frame) {
nb_frame--;
p_buf->layer_specific++; // added a frame to the buffer
} else {
- LOG_WARN("%s: underflow %d", __func__, nb_frame);
+ LOG_WARN(LOG_TAG, "%s: underflow %d", __func__, nb_frame);
a2dp_aac_encoder_cb.aac_feeding_state.counter +=
nb_frame * p_encoder_params->frame_length *
p_feeding_params->channel_count *
@@ -741,14 +740,6 @@ void A2dpCodecConfigAacSource::debug_codec_dump(int fd) {
A2dpCodecConfig::debug_codec_dump(fd);
- auto codec_specific_1 = getCodecConfig().codec_specific_1;
- dprintf(
- fd,
- " AAC bitrate mode : %s "
- "(0x%" PRIx64 ")\n",
- ((codec_specific_1 & ~A2DP_AAC_VARIABLE_BIT_RATE_MASK) == 0 ? "Constant"
- : "Variable"),
- codec_specific_1);
dprintf(fd,
" Packet counts (expected/dropped) : %zu / "
"%zu\n",
diff --git a/stack/a2dp/a2dp_api.cc b/stack/a2dp/a2dp_api.cc
index fb3abf169..cc7d01e98 100644
--- a/stack/a2dp/a2dp_api.cc
+++ b/stack/a2dp/a2dp_api.cc
@@ -62,7 +62,7 @@ static uint16_t a2dp_attr_list[] = {
* Returns Nothing.
*
*****************************************************************************/
-static void a2dp_sdp_cback(tSDP_STATUS status) {
+static void a2dp_sdp_cback(uint16_t status) {
tSDP_DISC_REC* p_rec = NULL;
tSDP_DISC_ATTR* p_attr;
bool found = false;
@@ -70,7 +70,7 @@ static void a2dp_sdp_cback(tSDP_STATUS status) {
tSDP_PROTOCOL_ELEM elem;
RawAddress peer_address = RawAddress::kEmpty;
- LOG_INFO("%s: status: %d", __func__, status);
+ LOG_INFO(LOG_TAG, "%s: status: %d", __func__, status);
if (status == SDP_SUCCESS) {
/* loop through all records we found */
@@ -106,7 +106,7 @@ static void a2dp_sdp_cback(tSDP_STATUS status) {
/* get AVDTP version */
if (SDP_FindProtocolListElemInRec(p_rec, UUID_PROTOCOL_AVDTP, &elem)) {
a2dp_svc.avdt_version = elem.params[0];
- LOG_VERBOSE("avdt_version: 0x%x", a2dp_svc.avdt_version);
+ LOG_VERBOSE(LOG_TAG, "avdt_version: 0x%x", a2dp_svc.avdt_version);
}
/* we've got everything, we're done */
@@ -179,7 +179,7 @@ tA2DP_STATUS A2DP_AddRecord(uint16_t service_uuid, char* p_service_name,
uint8_t* p;
tSDP_PROTOCOL_ELEM proto_list[A2DP_NUM_PROTO_ELEMS];
- LOG_VERBOSE("%s: uuid: 0x%x", __func__, service_uuid);
+ LOG_VERBOSE(LOG_TAG, "%s: uuid: 0x%x", __func__, service_uuid);
if ((sdp_handle == 0) || (service_uuid != UUID_SERVCLASS_AUDIO_SOURCE &&
service_uuid != UUID_SERVCLASS_AUDIO_SINK))
@@ -275,22 +275,22 @@ tA2DP_STATUS A2DP_FindService(uint16_t service_uuid, const RawAddress& bd_addr,
tA2DP_FIND_CBACK* p_cback) {
bool result = true;
- LOG_INFO("%s: peer: %s UUID: 0x%x", __func__, bd_addr.ToString().c_str(),
- service_uuid);
+ LOG_INFO(LOG_TAG, "%s: peer: %s UUID: 0x%x", __func__,
+ bd_addr.ToString().c_str(), service_uuid);
if ((service_uuid != UUID_SERVCLASS_AUDIO_SOURCE &&
service_uuid != UUID_SERVCLASS_AUDIO_SINK) ||
p_db == NULL || p_cback == NULL) {
- LOG_ERROR(
- "%s: cannot find service for peer %s UUID 0x%x: "
- "invalid parameters",
- __func__, bd_addr.ToString().c_str(), service_uuid);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find service for peer %s UUID 0x%x: "
+ "invalid parameters",
+ __func__, bd_addr.ToString().c_str(), service_uuid);
return A2DP_INVALID_PARAMS;
}
if (a2dp_cb.find.service_uuid == UUID_SERVCLASS_AUDIO_SOURCE ||
a2dp_cb.find.service_uuid == UUID_SERVCLASS_AUDIO_SINK) {
- LOG_ERROR("%s: cannot find service for peer %s UUID 0x%x: busy", __func__,
- bd_addr.ToString().c_str(), service_uuid);
+ LOG_ERROR(LOG_TAG, "%s: cannot find service for peer %s UUID 0x%x: busy",
+ __func__, bd_addr.ToString().c_str(), service_uuid);
return A2DP_BUSY;
}
@@ -319,10 +319,10 @@ tA2DP_STATUS A2DP_FindService(uint16_t service_uuid, const RawAddress& bd_addr,
}
}
if (!result) {
- LOG_ERROR(
- "%s: cannot find service for peer %s UUID 0x%x: "
- "SDP error",
- __func__, bd_addr.ToString().c_str(), service_uuid);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find service for peer %s UUID 0x%x: "
+ "SDP error",
+ __func__, bd_addr.ToString().c_str(), service_uuid);
return A2DP_FAIL;
}
diff --git a/stack/a2dp/a2dp_codec_config.cc b/stack/a2dp/a2dp_codec_config.cc
index a90c88108..edf7e0c46 100644
--- a/stack/a2dp/a2dp_codec_config.cc
+++ b/stack/a2dp/a2dp_codec_config.cc
@@ -28,13 +28,9 @@
#include "a2dp_aac.h"
#include "a2dp_sbc.h"
#include "a2dp_vendor.h"
-
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
#include "a2dp_vendor_aptx.h"
#include "a2dp_vendor_aptx_hd.h"
#include "a2dp_vendor_ldac.h"
-#endif
-
#include "bta/av/bta_av_int.h"
#include "osi/include/log.h"
#include "osi/include/properties.h"
@@ -110,7 +106,7 @@ void A2dpCodecConfig::setDefaultCodecPriority() {
A2dpCodecConfig* A2dpCodecConfig::createCodec(
btav_a2dp_codec_index_t codec_index,
btav_a2dp_codec_priority_t codec_priority) {
- LOG_INFO("%s: codec %s", __func__, A2DP_CodecIndexStr(codec_index));
+ LOG_DEBUG(LOG_TAG, "%s: codec %s", __func__, A2DP_CodecIndexStr(codec_index));
A2dpCodecConfig* codec_config = nullptr;
switch (codec_index) {
@@ -120,7 +116,6 @@ A2dpCodecConfig* A2dpCodecConfig::createCodec(
case BTAV_A2DP_CODEC_INDEX_SINK_SBC:
codec_config = new A2dpCodecConfigSbcSink(codec_priority);
break;
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case BTAV_A2DP_CODEC_INDEX_SOURCE_AAC:
codec_config = new A2dpCodecConfigAacSource(codec_priority);
break;
@@ -139,9 +134,7 @@ A2dpCodecConfig* A2dpCodecConfig::createCodec(
case BTAV_A2DP_CODEC_INDEX_SINK_LDAC:
codec_config = new A2dpCodecConfigLdacSink(codec_priority);
break;
-#endif
case BTAV_A2DP_CODEC_INDEX_MAX:
- default:
break;
}
@@ -160,22 +153,20 @@ int A2dpCodecConfig::getTrackBitRate() const {
memcpy(p_codec_info, ota_codec_config_, sizeof(ota_codec_config_));
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_GetBitrateSbc();
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_GetBitRateAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorGetBitRate(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return -1;
}
@@ -203,7 +194,6 @@ bool A2dpCodecConfig::getCodecSpecificConfig(tBT_A2DP_OFFLOAD* p_a2dp_offload) {
p_a2dp_offload->codec_info[3] =
codec_config[3]; // Sample freq | channel mode
break;
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
p_a2dp_offload->codec_info[0] = codec_config[3]; // object type
p_a2dp_offload->codec_info[1] = codec_config[6]; // VBR | BR
@@ -245,11 +235,10 @@ bool A2dpCodecConfig::getCodecSpecificConfig(tBT_A2DP_OFFLOAD* p_a2dp_offload) {
}
p_a2dp_offload->codec_info[7] =
codec_config[10]; // LDAC specific channel mode
- LOG_VERBOSE("%s: Ldac specific channelmode =%d", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: Ldac specific channelmode =%d", __func__,
p_a2dp_offload->codec_info[7]);
}
break;
-#endif
default:
break;
}
@@ -566,7 +555,7 @@ A2dpCodecs::~A2dpCodecs() {
}
bool A2dpCodecs::init() {
- LOG_INFO("%s", __func__);
+ LOG_DEBUG(LOG_TAG, "%s", __func__);
std::lock_guard<std::recursive_mutex> lock(codec_mutex_);
char* tok = NULL;
char* tmp_token = NULL;
@@ -585,22 +574,20 @@ bool A2dpCodecs::init() {
tok = strtok_r((char*)value_cap, "-", &tmp_token);
while (tok != NULL) {
if (strcmp(tok, "sbc") == 0) {
- LOG_INFO("%s: SBC offload supported", __func__);
+ LOG_INFO(LOG_TAG, "%s: SBC offload supported", __func__);
offload_codec_support[BTAV_A2DP_CODEC_INDEX_SOURCE_SBC] = true;
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
} else if (strcmp(tok, "aac") == 0) {
- LOG_INFO("%s: AAC offload supported", __func__);
+ LOG_INFO(LOG_TAG, "%s: AAC offload supported", __func__);
offload_codec_support[BTAV_A2DP_CODEC_INDEX_SOURCE_AAC] = true;
} else if (strcmp(tok, "aptx") == 0) {
- LOG_INFO("%s: APTX offload supported", __func__);
+ LOG_INFO(LOG_TAG, "%s: APTX offload supported", __func__);
offload_codec_support[BTAV_A2DP_CODEC_INDEX_SOURCE_APTX] = true;
} else if (strcmp(tok, "aptxhd") == 0) {
- LOG_INFO("%s: APTXHD offload supported", __func__);
+ LOG_INFO(LOG_TAG, "%s: APTXHD offload supported", __func__);
offload_codec_support[BTAV_A2DP_CODEC_INDEX_SOURCE_APTX_HD] = true;
} else if (strcmp(tok, "ldac") == 0) {
- LOG_INFO("%s: LDAC offload supported", __func__);
+ LOG_INFO(LOG_TAG, "%s: LDAC offload supported", __func__);
offload_codec_support[BTAV_A2DP_CODEC_INDEX_SOURCE_LDAC] = true;
-#endif
}
tok = strtok_r(NULL, "-", &tmp_token);
};
@@ -629,7 +616,7 @@ bool A2dpCodecs::init() {
if (codec_config == nullptr) continue;
if (codec_priority != BTAV_A2DP_CODEC_PRIORITY_DEFAULT) {
- LOG_INFO("%s: updated %s codec priority to %d", __func__,
+ LOG_INFO(LOG_TAG, "%s: updated %s codec priority to %d", __func__,
codec_config->name().c_str(), codec_priority);
}
@@ -651,18 +638,19 @@ bool A2dpCodecs::init() {
}
if (ordered_source_codecs_.empty()) {
- LOG_ERROR("%s: no Source codecs were initialized", __func__);
+ LOG_ERROR(LOG_TAG, "%s: no Source codecs were initialized", __func__);
} else {
for (auto iter : ordered_source_codecs_) {
- LOG_INFO("%s: initialized Source codec %s", __func__,
+ LOG_INFO(LOG_TAG, "%s: initialized Source codec %s", __func__,
iter->name().c_str());
}
}
if (ordered_sink_codecs_.empty()) {
- LOG_ERROR("%s: no Sink codecs were initialized", __func__);
+ LOG_ERROR(LOG_TAG, "%s: no Sink codecs were initialized", __func__);
} else {
for (auto iter : ordered_sink_codecs_) {
- LOG_INFO("%s: initialized Sink codec %s", __func__, iter->name().c_str());
+ LOG_INFO(LOG_TAG, "%s: initialized Sink codec %s", __func__,
+ iter->name().c_str());
}
}
@@ -742,8 +730,8 @@ bool A2dpCodecs::setCodecUserConfig(
*p_restart_output = false;
*p_config_updated = false;
- LOG_INFO("%s: Configuring: %s", __func__,
- codec_user_config.ToString().c_str());
+ LOG_DEBUG(LOG_TAG, "%s: Configuring: %s", __func__,
+ codec_user_config.ToString().c_str());
if (codec_user_config.codec_type < BTAV_A2DP_CODEC_INDEX_MAX) {
auto iter = indexed_codecs_.find(codec_user_config.codec_type);
@@ -822,10 +810,10 @@ bool A2dpCodecs::setCodecUserConfig(
if (*p_restart_input || *p_restart_output) *p_config_updated = true;
- LOG_INFO(
- "%s: Configured: restart_input = %d restart_output = %d "
- "config_updated = %d",
- __func__, *p_restart_input, *p_restart_output, *p_config_updated);
+ LOG_DEBUG(LOG_TAG,
+ "%s: Configured: restart_input = %d restart_output = %d "
+ "config_updated = %d",
+ __func__, *p_restart_input, *p_restart_output, *p_config_updated);
return true;
@@ -880,11 +868,11 @@ bool A2dpCodecs::setCodecOtaConfig(
if (current_codec_config_ != nullptr) {
codec_user_config = current_codec_config_->getCodecUserConfig();
if (!A2dpCodecConfig::isCodecConfigEmpty(codec_user_config)) {
- LOG_WARN(
- "%s: ignoring peer OTA configuration for codec %s: "
- "existing user configuration for current codec %s",
- __func__, A2DP_CodecName(p_ota_codec_config),
- current_codec_config_->name().c_str());
+ LOG_WARN(LOG_TAG,
+ "%s: ignoring peer OTA configuration for codec %s: "
+ "existing user configuration for current codec %s",
+ __func__, A2DP_CodecName(p_ota_codec_config),
+ current_codec_config_->name().c_str());
goto fail;
}
}
@@ -894,15 +882,16 @@ bool A2dpCodecs::setCodecOtaConfig(
// ignored.
codec_type = A2DP_SourceCodecIndex(p_ota_codec_config);
if (codec_type == BTAV_A2DP_CODEC_INDEX_MAX) {
- LOG_WARN(
- "%s: ignoring peer OTA codec configuration: "
- "invalid codec",
- __func__);
+ LOG_WARN(LOG_TAG,
+ "%s: ignoring peer OTA codec configuration: "
+ "invalid codec",
+ __func__);
goto fail; // Invalid codec
} else {
auto iter = indexed_codecs_.find(codec_type);
if (iter == indexed_codecs_.end()) {
- LOG_WARN("%s: cannot find codec configuration for peer OTA codec %s",
+ LOG_WARN(LOG_TAG,
+ "%s: cannot find codec configuration for peer OTA codec %s",
__func__, A2DP_CodecName(p_ota_codec_config));
goto fail;
}
@@ -911,10 +900,10 @@ bool A2dpCodecs::setCodecOtaConfig(
if (a2dp_codec_config == nullptr) goto fail;
codec_user_config = a2dp_codec_config->getCodecUserConfig();
if (!A2dpCodecConfig::isCodecConfigEmpty(codec_user_config)) {
- LOG_WARN(
- "%s: ignoring peer OTA configuration for codec %s: "
- "existing user configuration for same codec",
- __func__, A2DP_CodecName(p_ota_codec_config));
+ LOG_WARN(LOG_TAG,
+ "%s: ignoring peer OTA configuration for codec %s: "
+ "existing user configuration for same codec",
+ __func__, A2DP_CodecName(p_ota_codec_config));
goto fail;
}
current_codec_config_ = a2dp_codec_config;
@@ -925,7 +914,8 @@ bool A2dpCodecs::setCodecOtaConfig(
codec_user_config, codec_audio_config, p_peer_params,
p_ota_codec_config, false, p_result_codec_config, p_restart_input,
p_restart_output, p_config_updated)) {
- LOG_WARN("%s: cannot set codec configuration for peer OTA codec %s",
+ LOG_WARN(LOG_TAG,
+ "%s: cannot set codec configuration for peer OTA codec %s",
__func__, A2DP_CodecName(p_ota_codec_config));
goto fail;
}
@@ -1024,17 +1014,15 @@ tA2DP_CODEC_TYPE A2DP_GetCodecType(const uint8_t* p_codec_info) {
bool A2DP_IsSourceCodecValid(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_IsSourceCodecValidSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_IsSourceCodecValidAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_IsVendorSourceCodecValid(p_codec_info);
-#endif
default:
break;
}
@@ -1045,17 +1033,15 @@ bool A2DP_IsSourceCodecValid(const uint8_t* p_codec_info) {
bool A2DP_IsSinkCodecValid(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_IsSinkCodecValidSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_IsSinkCodecValidAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_IsVendorSinkCodecValid(p_codec_info);
-#endif
default:
break;
}
@@ -1066,17 +1052,15 @@ bool A2DP_IsSinkCodecValid(const uint8_t* p_codec_info) {
bool A2DP_IsPeerSourceCodecValid(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_IsPeerSourceCodecValidSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_IsPeerSourceCodecValidAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_IsVendorPeerSourceCodecValid(p_codec_info);
-#endif
default:
break;
}
@@ -1087,17 +1071,15 @@ bool A2DP_IsPeerSourceCodecValid(const uint8_t* p_codec_info) {
bool A2DP_IsPeerSinkCodecValid(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_IsPeerSinkCodecValidSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_IsPeerSinkCodecValidAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_IsVendorPeerSinkCodecValid(p_codec_info);
-#endif
default:
break;
}
@@ -1108,44 +1090,40 @@ bool A2DP_IsPeerSinkCodecValid(const uint8_t* p_codec_info) {
bool A2DP_IsSinkCodecSupported(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_IsSinkCodecSupportedSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_IsSinkCodecSupportedAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_IsVendorSinkCodecSupported(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return false;
}
bool A2DP_IsPeerSourceCodecSupported(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_IsPeerSourceCodecSupportedSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_IsPeerSourceCodecSupportedAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_IsVendorPeerSourceCodecSupported(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return false;
}
@@ -1159,11 +1137,7 @@ bool A2DP_UsesRtpHeader(bool content_protection_enabled,
if (codec_type != A2DP_MEDIA_CT_NON_A2DP) return true;
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
return A2DP_VendorUsesRtpHeader(content_protection_enabled, p_codec_info);
-#else
- return true;
-#endif
}
uint8_t A2DP_GetMediaType(const uint8_t* p_codec_info) {
@@ -1174,22 +1148,20 @@ uint8_t A2DP_GetMediaType(const uint8_t* p_codec_info) {
const char* A2DP_CodecName(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_CodecNameSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_CodecNameAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorCodecName(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return "UNKNOWN CODEC";
}
@@ -1203,17 +1175,15 @@ bool A2DP_CodecTypeEquals(const uint8_t* p_codec_info_a,
switch (codec_type_a) {
case A2DP_MEDIA_CT_SBC:
return A2DP_CodecTypeEqualsSbc(p_codec_info_a, p_codec_info_b);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_CodecTypeEqualsAac(p_codec_info_a, p_codec_info_b);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorCodecTypeEquals(p_codec_info_a, p_codec_info_b);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type_a);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type_a);
return false;
}
@@ -1227,105 +1197,95 @@ bool A2DP_CodecEquals(const uint8_t* p_codec_info_a,
switch (codec_type_a) {
case A2DP_MEDIA_CT_SBC:
return A2DP_CodecEqualsSbc(p_codec_info_a, p_codec_info_b);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_CodecEqualsAac(p_codec_info_a, p_codec_info_b);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorCodecEquals(p_codec_info_a, p_codec_info_b);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type_a);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type_a);
return false;
}
int A2DP_GetTrackSampleRate(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_GetTrackSampleRateSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_GetTrackSampleRateAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorGetTrackSampleRate(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return -1;
}
int A2DP_GetTrackBitsPerSample(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_GetTrackBitsPerSampleSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_GetTrackBitsPerSampleAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorGetTrackBitsPerSample(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return -1;
}
int A2DP_GetTrackChannelCount(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_GetTrackChannelCountSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_GetTrackChannelCountAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorGetTrackChannelCount(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return -1;
}
int A2DP_GetSinkTrackChannelType(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_GetSinkTrackChannelTypeSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_GetSinkTrackChannelTypeAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorGetSinkTrackChannelType(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return -1;
}
@@ -1336,17 +1296,15 @@ bool A2DP_GetPacketTimestamp(const uint8_t* p_codec_info, const uint8_t* p_data,
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_GetPacketTimestampSbc(p_codec_info, p_data, p_timestamp);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_GetPacketTimestampAac(p_codec_info, p_data, p_timestamp);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorGetPacketTimestamp(p_codec_info, p_data, p_timestamp);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return false;
}
@@ -1357,18 +1315,16 @@ bool A2DP_BuildCodecHeader(const uint8_t* p_codec_info, BT_HDR* p_buf,
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_BuildCodecHeaderSbc(p_codec_info, p_buf, frames_per_packet);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_BuildCodecHeaderAac(p_codec_info, p_buf, frames_per_packet);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorBuildCodecHeader(p_codec_info, p_buf,
frames_per_packet);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return false;
}
@@ -1376,22 +1332,20 @@ const tA2DP_ENCODER_INTERFACE* A2DP_GetEncoderInterface(
const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_GetEncoderInterfaceSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_GetEncoderInterfaceAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorGetEncoderInterface(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return NULL;
}
@@ -1399,22 +1353,20 @@ const tA2DP_DECODER_INTERFACE* A2DP_GetDecoderInterface(
const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_GetDecoderInterfaceSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_GetDecoderInterfaceAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorGetDecoderInterface(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return NULL;
}
@@ -1424,61 +1376,55 @@ bool A2DP_AdjustCodec(uint8_t* p_codec_info) {
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_AdjustCodecSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_AdjustCodecAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorAdjustCodec(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return false;
}
btav_a2dp_codec_index_t A2DP_SourceCodecIndex(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_SourceCodecIndexSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_SourceCodecIndexAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorSourceCodecIndex(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return BTAV_A2DP_CODEC_INDEX_MAX;
}
btav_a2dp_codec_index_t A2DP_SinkCodecIndex(const uint8_t* p_codec_info) {
tA2DP_CODEC_TYPE codec_type = A2DP_GetCodecType(p_codec_info);
- LOG_VERBOSE("%s: codec_type = 0x%x", __func__, codec_type);
+ LOG_VERBOSE(LOG_TAG, "%s: codec_type = 0x%x", __func__, codec_type);
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_SinkCodecIndexSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_SinkCodecIndexAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorSinkCodecIndex(p_codec_info);
-#endif
default:
break;
}
- LOG_ERROR("%s: unsupported codec type 0x%x", __func__, codec_type);
+ LOG_ERROR(LOG_TAG, "%s: unsupported codec type 0x%x", __func__, codec_type);
return BTAV_A2DP_CODEC_INDEX_MAX;
}
@@ -1488,27 +1434,24 @@ const char* A2DP_CodecIndexStr(btav_a2dp_codec_index_t codec_index) {
return A2DP_CodecIndexStrSbc();
case BTAV_A2DP_CODEC_INDEX_SINK_SBC:
return A2DP_CodecIndexStrSbcSink();
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case BTAV_A2DP_CODEC_INDEX_SOURCE_AAC:
return A2DP_CodecIndexStrAac();
case BTAV_A2DP_CODEC_INDEX_SINK_AAC:
return A2DP_CodecIndexStrAacSink();
-#endif
default:
break;
}
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
if (codec_index < BTAV_A2DP_CODEC_INDEX_MAX)
return A2DP_VendorCodecIndexStr(codec_index);
-#endif
return "UNKNOWN CODEC INDEX";
}
bool A2DP_InitCodecConfig(btav_a2dp_codec_index_t codec_index,
AvdtpSepConfig* p_cfg) {
- LOG_VERBOSE("%s: codec %s", __func__, A2DP_CodecIndexStr(codec_index));
+ LOG_VERBOSE(LOG_TAG, "%s: codec %s", __func__,
+ A2DP_CodecIndexStr(codec_index));
/* Default: no content protection info */
p_cfg->num_protect = 0;
@@ -1519,20 +1462,16 @@ bool A2DP_InitCodecConfig(btav_a2dp_codec_index_t codec_index,
return A2DP_InitCodecConfigSbc(p_cfg);
case BTAV_A2DP_CODEC_INDEX_SINK_SBC:
return A2DP_InitCodecConfigSbcSink(p_cfg);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case BTAV_A2DP_CODEC_INDEX_SOURCE_AAC:
return A2DP_InitCodecConfigAac(p_cfg);
case BTAV_A2DP_CODEC_INDEX_SINK_AAC:
return A2DP_InitCodecConfigAacSink(p_cfg);
-#endif
default:
break;
}
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
if (codec_index < BTAV_A2DP_CODEC_INDEX_MAX)
return A2DP_VendorInitCodecConfig(codec_index, p_cfg);
-#endif
return false;
}
@@ -1543,12 +1482,10 @@ std::string A2DP_CodecInfoString(const uint8_t* p_codec_info) {
switch (codec_type) {
case A2DP_MEDIA_CT_SBC:
return A2DP_CodecInfoStringSbc(p_codec_info);
-#if !defined(EXCLUDE_NONSTANDARD_CODECS)
case A2DP_MEDIA_CT_AAC:
return A2DP_CodecInfoStringAac(p_codec_info);
case A2DP_MEDIA_CT_NON_A2DP:
return A2DP_VendorCodecInfoString(p_codec_info);
-#endif
default:
break;
}
diff --git a/stack/a2dp/a2dp_sbc.cc b/stack/a2dp/a2dp_sbc.cc
index de55883d2..388419b1f 100644
--- a/stack/a2dp/a2dp_sbc.cc
+++ b/stack/a2dp/a2dp_sbc.cc
@@ -334,7 +334,7 @@ bool A2DP_IsPeerSourceCodecSupportedSbc(const uint8_t* p_codec_info) {
void A2DP_InitDefaultCodecSbc(uint8_t* p_codec_info) {
if (A2DP_BuildInfoSbc(AVDT_MEDIA_TYPE_AUDIO, &a2dp_sbc_default_config,
p_codec_info) != A2DP_SUCCESS) {
- LOG_ERROR("%s: A2DP_BuildInfoSbc failed", __func__);
+ LOG_ERROR(LOG_TAG, "%s: A2DP_BuildInfoSbc failed", __func__);
}
}
@@ -353,25 +353,25 @@ static tA2DP_STATUS A2DP_CodecInfoMatchesCapabilitySbc(
/* parse configuration */
status = A2DP_ParseInfoSbc(&cfg_cie, p_codec_info, is_capability);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: parsing failed %d", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s: parsing failed %d", __func__, status);
return status;
}
/* verify that each parameter is in range */
- LOG_VERBOSE("%s: FREQ peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: FREQ peer: 0x%x, capability 0x%x", __func__,
cfg_cie.samp_freq, p_cap->samp_freq);
- LOG_VERBOSE("%s: CH_MODE peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: CH_MODE peer: 0x%x, capability 0x%x", __func__,
cfg_cie.ch_mode, p_cap->ch_mode);
- LOG_VERBOSE("%s: BLOCK_LEN peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: BLOCK_LEN peer: 0x%x, capability 0x%x", __func__,
cfg_cie.block_len, p_cap->block_len);
- LOG_VERBOSE("%s: SUB_BAND peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: SUB_BAND peer: 0x%x, capability 0x%x", __func__,
cfg_cie.num_subbands, p_cap->num_subbands);
- LOG_VERBOSE("%s: ALLOC_METHOD peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: ALLOC_METHOD peer: 0x%x, capability 0x%x", __func__,
cfg_cie.alloc_method, p_cap->alloc_method);
- LOG_VERBOSE("%s: MIN_BitPool peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: MIN_BitPool peer: 0x%x, capability 0x%x", __func__,
cfg_cie.min_bitpool, p_cap->min_bitpool);
- LOG_VERBOSE("%s: MAX_BitPool peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: MAX_BitPool peer: 0x%x, capability 0x%x", __func__,
cfg_cie.max_bitpool, p_cap->max_bitpool);
/* sampling frequency */
@@ -409,12 +409,14 @@ bool A2DP_CodecTypeEqualsSbc(const uint8_t* p_codec_info_a,
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoSbc(&sbc_cie_a, p_codec_info_a, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
a2dp_status = A2DP_ParseInfoSbc(&sbc_cie_b, p_codec_info_b, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
@@ -433,12 +435,14 @@ bool A2DP_CodecEqualsSbc(const uint8_t* p_codec_info_a,
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoSbc(&sbc_cie_a, p_codec_info_a, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
a2dp_status = A2DP_ParseInfoSbc(&sbc_cie_b, p_codec_info_b, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
@@ -462,7 +466,8 @@ int A2DP_GetTrackSampleRateSbc(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status = A2DP_ParseInfoSbc(&sbc_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -487,7 +492,8 @@ int A2DP_GetTrackBitsPerSampleSbc(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status = A2DP_ParseInfoSbc(&sbc_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -500,7 +506,8 @@ int A2DP_GetTrackChannelCountSbc(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status = A2DP_ParseInfoSbc(&sbc_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -523,7 +530,8 @@ int A2DP_GetNumberOfSubbandsSbc(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status = A2DP_ParseInfoSbc(&sbc_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -544,7 +552,8 @@ int A2DP_GetNumberOfBlocksSbc(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status = A2DP_ParseInfoSbc(&sbc_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -569,7 +578,8 @@ int A2DP_GetAllocationMethodCodeSbc(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status = A2DP_ParseInfoSbc(&sbc_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -590,7 +600,8 @@ int A2DP_GetChannelModeCodeSbc(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status = A2DP_ParseInfoSbc(&sbc_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -615,7 +626,8 @@ int A2DP_GetSamplingFrequencyCodeSbc(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status = A2DP_ParseInfoSbc(&sbc_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -640,7 +652,8 @@ int A2DP_GetMinBitpoolSbc(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status = A2DP_ParseInfoSbc(&sbc_cie, p_codec_info, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -652,7 +665,8 @@ int A2DP_GetMaxBitpoolSbc(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status = A2DP_ParseInfoSbc(&sbc_cie, p_codec_info, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -665,7 +679,8 @@ int A2DP_GetSinkTrackChannelTypeSbc(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status = A2DP_ParseInfoSbc(&sbc_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -691,13 +706,10 @@ bool A2DP_GetPacketTimestampSbc(UNUSED_ATTR const uint8_t* p_codec_info,
bool A2DP_BuildCodecHeaderSbc(UNUSED_ATTR const uint8_t* p_codec_info,
BT_HDR* p_buf, uint16_t frames_per_packet) {
- // this doesn't happen in real life, but keeps fuzzer happy
- if (p_buf->len - p_buf->offset < A2DP_SBC_MPL_HDR_LEN) {
- return false;
- }
+ uint8_t* p;
p_buf->offset -= A2DP_SBC_MPL_HDR_LEN;
- uint8_t* p = (uint8_t*)(p_buf + 1) + p_buf->offset;
+ p = (uint8_t*)(p_buf + 1) + p_buf->offset;
p_buf->len += A2DP_SBC_MPL_HDR_LEN;
A2DP_BuildMediaPayloadHeaderSbc(p, false, false, false,
(uint8_t)frames_per_packet);
@@ -792,8 +804,8 @@ bool A2DP_AdjustCodecSbc(uint8_t* p_codec_info) {
// Updated the max bitpool
if (cfg_cie.max_bitpool > A2DP_SBC_MAX_BITPOOL) {
- LOG_WARN("%s: Updated the SBC codec max bitpool from %d to %d", __func__,
- cfg_cie.max_bitpool, A2DP_SBC_MAX_BITPOOL);
+ LOG_WARN(LOG_TAG, "%s: Updated the SBC codec max bitpool from %d to %d",
+ __func__, cfg_cie.max_bitpool, A2DP_SBC_MAX_BITPOOL);
cfg_cie.max_bitpool = A2DP_SBC_MAX_BITPOOL;
}
@@ -893,7 +905,7 @@ bool A2dpCodecConfigSbcSource::init() {
// Load the encoder
if (!A2DP_LoadEncoderSbc()) {
- LOG_ERROR("%s: cannot load the encoder", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot load the encoder", __func__);
return false;
}
@@ -1094,8 +1106,8 @@ bool A2dpCodecConfigSbcBase::setCodecConfig(const uint8_t* p_peer_codec_info,
tA2DP_STATUS status =
A2DP_ParseInfoSbc(&peer_info_cie, p_peer_codec_info, is_capability);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: can't parse peer's capabilities: error = %d", __func__,
- status);
+ LOG_ERROR(LOG_TAG, "%s: can't parse peer's capabilities: error = %d",
+ __func__, status);
goto fail;
}
// Try using the prefered peer codec config (if valid), instead of the peer
@@ -1197,10 +1209,10 @@ bool A2dpCodecConfigSbcBase::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.sample_rate == BTAV_A2DP_CODEC_SAMPLE_RATE_NONE) {
- LOG_ERROR(
- "%s: cannot match sample frequency: local caps = 0x%x "
- "peer info = 0x%x",
- __func__, p_a2dp_sbc_caps->samp_freq, peer_info_cie.samp_freq);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match sample frequency: local caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, p_a2dp_sbc_caps->samp_freq, peer_info_cie.samp_freq);
goto fail;
}
@@ -1252,7 +1264,8 @@ bool A2dpCodecConfigSbcBase::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.bits_per_sample == BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE) {
- LOG_ERROR("%s: cannot match bits per sample: user preference = 0x%x",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match bits per sample: user preference = 0x%x",
__func__, codec_user_config_.bits_per_sample);
goto fail;
}
@@ -1345,10 +1358,10 @@ bool A2dpCodecConfigSbcBase::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.channel_mode == BTAV_A2DP_CODEC_CHANNEL_MODE_NONE) {
- LOG_ERROR(
- "%s: cannot match channel mode: local caps = 0x%x "
- "peer info = 0x%x",
- __func__, p_a2dp_sbc_caps->ch_mode, peer_info_cie.ch_mode);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match channel mode: local caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, p_a2dp_sbc_caps->ch_mode, peer_info_cie.ch_mode);
goto fail;
}
@@ -1365,10 +1378,10 @@ bool A2dpCodecConfigSbcBase::setCodecConfig(const uint8_t* p_peer_codec_info,
} else if (block_len & A2DP_SBC_IE_BLOCKS_4) {
result_config_cie.block_len = A2DP_SBC_IE_BLOCKS_4;
} else {
- LOG_ERROR(
- "%s: cannot match block length: local caps = 0x%x "
- "peer info = 0x%x",
- __func__, p_a2dp_sbc_caps->block_len, peer_info_cie.block_len);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match block length: local caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, p_a2dp_sbc_caps->block_len, peer_info_cie.block_len);
goto fail;
}
@@ -1381,10 +1394,11 @@ bool A2dpCodecConfigSbcBase::setCodecConfig(const uint8_t* p_peer_codec_info,
} else if (num_subbands & A2DP_SBC_IE_SUBBAND_4) {
result_config_cie.num_subbands = A2DP_SBC_IE_SUBBAND_4;
} else {
- LOG_ERROR(
- "%s: cannot match number of sub-bands: local caps = 0x%x "
- "peer info = 0x%x",
- __func__, p_a2dp_sbc_caps->num_subbands, peer_info_cie.num_subbands);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match number of sub-bands: local caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, p_a2dp_sbc_caps->num_subbands,
+ peer_info_cie.num_subbands);
goto fail;
}
@@ -1397,10 +1411,11 @@ bool A2dpCodecConfigSbcBase::setCodecConfig(const uint8_t* p_peer_codec_info,
} else if (alloc_method & A2DP_SBC_IE_ALLOC_MD_S) {
result_config_cie.alloc_method = A2DP_SBC_IE_ALLOC_MD_S;
} else {
- LOG_ERROR(
- "%s: cannot match allocation method: local caps = 0x%x "
- "peer info = 0x%x",
- __func__, p_a2dp_sbc_caps->alloc_method, peer_info_cie.alloc_method);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match allocation method: local caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, p_a2dp_sbc_caps->alloc_method,
+ peer_info_cie.alloc_method);
goto fail;
}
@@ -1414,11 +1429,12 @@ bool A2dpCodecConfigSbcBase::setCodecConfig(const uint8_t* p_peer_codec_info,
if (result_config_cie.max_bitpool > peer_info_cie.max_bitpool)
result_config_cie.max_bitpool = peer_info_cie.max_bitpool;
if (result_config_cie.min_bitpool > result_config_cie.max_bitpool) {
- LOG_ERROR(
- "%s: cannot match min/max bitpool: "
- "local caps min/max = 0x%x/0x%x peer info min/max = 0x%x/0x%x",
- __func__, p_a2dp_sbc_caps->min_bitpool, p_a2dp_sbc_caps->max_bitpool,
- peer_info_cie.min_bitpool, peer_info_cie.max_bitpool);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match min/max bitpool: "
+ "local caps min/max = 0x%x/0x%x peer info min/max = 0x%x/0x%x",
+ __func__, p_a2dp_sbc_caps->min_bitpool,
+ p_a2dp_sbc_caps->max_bitpool, peer_info_cie.min_bitpool,
+ peer_info_cie.max_bitpool);
goto fail;
}
@@ -1488,8 +1504,8 @@ bool A2dpCodecConfigSbcBase::setPeerCodecCapabilities(
tA2DP_STATUS status =
A2DP_ParseInfoSbc(&peer_info_cie, p_peer_codec_capabilities, true);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: can't parse peer's capabilities: error = %d", __func__,
- status);
+ LOG_ERROR(LOG_TAG, "%s: can't parse peer's capabilities: error = %d",
+ __func__, status);
goto fail;
}
@@ -1553,7 +1569,7 @@ bool A2dpCodecConfigSbcSink::init() {
// Load the decoder
if (!A2DP_LoadDecoderSbc()) {
- LOG_ERROR("%s: cannot load the decoder", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot load the decoder", __func__);
return false;
}
diff --git a/stack/a2dp/a2dp_sbc_decoder.cc b/stack/a2dp/a2dp_sbc_decoder.cc
index b275c74ca..bc64513cb 100644
--- a/stack/a2dp/a2dp_sbc_decoder.cc
+++ b/stack/a2dp/a2dp_sbc_decoder.cc
@@ -45,7 +45,8 @@ bool a2dp_sbc_decoder_init(decoded_data_callback_t decode_callback) {
&a2dp_sbc_decoder_cb.decoder_context, a2dp_sbc_decoder_cb.context_data,
sizeof(a2dp_sbc_decoder_cb.context_data), 2, 2, false);
if (!OI_SUCCESS(status)) {
- LOG_ERROR("%s: OI_CODEC_SBC_DecoderReset failed with error code %d",
+ LOG_ERROR(LOG_TAG,
+ "%s: OI_CODEC_SBC_DecoderReset failed with error code %d",
__func__, status);
return false;
}
@@ -63,7 +64,7 @@ bool a2dp_sbc_decoder_decode_packet(BT_HDR* p_buf) {
size_t data_size = p_buf->len;
if (data_size == 0) {
- LOG_ERROR("%s: Empty packet", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Empty packet", __func__);
return false;
}
size_t num_frames = data[0] & 0xf;
@@ -81,7 +82,7 @@ bool a2dp_sbc_decoder_decode_packet(BT_HDR* p_buf) {
OI_CODEC_SBC_DecodeFrame(&a2dp_sbc_decoder_cb.decoder_context, &oi_data,
&oi_size, out_ptr, &out_size);
if (!OI_SUCCESS(status)) {
- LOG_ERROR("%s: Decoding failure: %d", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s: Decoding failure: %d", __func__, status);
return false;
}
out_avail -= out_size;
diff --git a/stack/a2dp/a2dp_sbc_encoder.cc b/stack/a2dp/a2dp_sbc_encoder.cc
index 2de3fad42..577346212 100644
--- a/stack/a2dp/a2dp_sbc_encoder.cc
+++ b/stack/a2dp/a2dp_sbc_encoder.cc
@@ -22,6 +22,7 @@
#include "a2dp_sbc_encoder.h"
#include <limits.h>
+#include <math.h>
#include <stdio.h>
#include <string.h>
@@ -70,9 +71,9 @@ typedef struct {
uint32_t aa_frame_counter;
int32_t aa_feed_counter;
int32_t aa_feed_residue;
- float counter;
- uint32_t bytes_per_tick; /* pcm bytes read each media task tick */
- uint64_t last_frame_us;
+ uint32_t counter;
+ uint32_t bytes_per_tick; // pcm bytes read each media task tick
+ uint64_t last_frame_timestamp_100ns; // values in 1/10 microseconds
} tA2DP_SBC_FEEDING_STATE;
typedef struct {
@@ -166,10 +167,10 @@ bool A2dpCodecConfigSbcSource::updateEncoderUserConfig(
a2dp_sbc_encoder_cb.timestamp = 0;
if (a2dp_sbc_encoder_cb.peer_mtu == 0) {
- LOG_ERROR(
- "%s: Cannot update the codec encoder for %s: "
- "invalid peer MTU",
- __func__, name().c_str());
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot update the codec encoder for %s: "
+ "invalid peer MTU",
+ __func__, name().c_str());
return false;
}
@@ -200,10 +201,10 @@ static void a2dp_sbc_encoder_update(uint16_t peer_mtu,
*p_restart_output = false;
*p_config_updated = false;
if (!a2dp_codec_config->copyOutOtaCodecConfig(codec_info)) {
- LOG_ERROR(
- "%s: Cannot update the codec encoder for %s: "
- "invalid codec config",
- __func__, a2dp_codec_config->name().c_str());
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot update the codec encoder for %s: "
+ "invalid codec config",
+ __func__, a2dp_codec_config->name().c_str());
return;
}
const uint8_t* p_codec_info = codec_info;
@@ -216,9 +217,9 @@ static void a2dp_sbc_encoder_update(uint16_t peer_mtu,
p_feeding_params->bits_per_sample =
a2dp_codec_config->getAudioBitsPerSample();
p_feeding_params->channel_count = A2DP_GetTrackChannelCountSbc(p_codec_info);
- LOG_INFO("%s: sample_rate=%u bits_per_sample=%u channel_count=%u", __func__,
- p_feeding_params->sample_rate, p_feeding_params->bits_per_sample,
- p_feeding_params->channel_count);
+ LOG_DEBUG(LOG_TAG, "%s: sample_rate=%u bits_per_sample=%u channel_count=%u",
+ __func__, p_feeding_params->sample_rate,
+ p_feeding_params->bits_per_sample, p_feeding_params->channel_count);
a2dp_sbc_feeding_reset();
// The codec parameters
@@ -235,18 +236,18 @@ static void a2dp_sbc_encoder_update(uint16_t peer_mtu,
// Reset invalid parameters
if (!p_encoder_params->s16NumOfSubBands) {
- LOG_WARN("%s: SubBands are set to 0, resetting to max (%d)", __func__,
- SBC_MAX_NUM_OF_SUBBANDS);
+ LOG_WARN(LOG_TAG, "%s: SubBands are set to 0, resetting to max (%d)",
+ __func__, SBC_MAX_NUM_OF_SUBBANDS);
p_encoder_params->s16NumOfSubBands = SBC_MAX_NUM_OF_SUBBANDS;
}
if (!p_encoder_params->s16NumOfBlocks) {
- LOG_WARN("%s: Blocks are set to 0, resetting to max (%d)", __func__,
- SBC_MAX_NUM_OF_BLOCKS);
+ LOG_WARN(LOG_TAG, "%s: Blocks are set to 0, resetting to max (%d)",
+ __func__, SBC_MAX_NUM_OF_BLOCKS);
p_encoder_params->s16NumOfBlocks = SBC_MAX_NUM_OF_BLOCKS;
}
if (!p_encoder_params->s16NumOfChannels) {
- LOG_WARN("%s: Channels are set to 0, resetting to max (%d)", __func__,
- SBC_MAX_NUM_OF_CHANNELS);
+ LOG_WARN(LOG_TAG, "%s: Channels are set to 0, resetting to max (%d)",
+ __func__, SBC_MAX_NUM_OF_CHANNELS);
p_encoder_params->s16NumOfChannels = SBC_MAX_NUM_OF_CHANNELS;
}
@@ -269,15 +270,17 @@ static void a2dp_sbc_encoder_update(uint16_t peer_mtu,
// Set the initial target bit rate
p_encoder_params->u16BitRate = a2dp_sbc_source_rate();
- LOG_INFO("%s: MTU=%d, peer_mtu=%d min_bitpool=%d max_bitpool=%d", __func__,
- a2dp_sbc_encoder_cb.TxAaMtuSize, peer_mtu, min_bitpool, max_bitpool);
- LOG_INFO(
- "%s: ChannelMode=%d, NumOfSubBands=%d, NumOfBlocks=%d, "
- "AllocationMethod=%d, BitRate=%d, SamplingFreq=%d BitPool=%d",
- __func__, p_encoder_params->s16ChannelMode,
- p_encoder_params->s16NumOfSubBands, p_encoder_params->s16NumOfBlocks,
- p_encoder_params->s16AllocationMethod, p_encoder_params->u16BitRate,
- s16SamplingFreq, p_encoder_params->s16BitPool);
+ LOG_DEBUG(LOG_TAG, "%s: MTU=%d, peer_mtu=%d min_bitpool=%d max_bitpool=%d",
+ __func__, a2dp_sbc_encoder_cb.TxAaMtuSize, peer_mtu, min_bitpool,
+ max_bitpool);
+ LOG_DEBUG(LOG_TAG,
+ "%s: ChannelMode=%d, NumOfSubBands=%d, NumOfBlocks=%d, "
+ "AllocationMethod=%d, BitRate=%d, SamplingFreq=%d BitPool=%d",
+ __func__, p_encoder_params->s16ChannelMode,
+ p_encoder_params->s16NumOfSubBands,
+ p_encoder_params->s16NumOfBlocks,
+ p_encoder_params->s16AllocationMethod, p_encoder_params->u16BitRate,
+ s16SamplingFreq, p_encoder_params->s16BitPool);
do {
if ((p_encoder_params->s16ChannelMode == SBC_JOINT_STEREO) ||
@@ -327,17 +330,19 @@ static void a2dp_sbc_encoder_update(uint16_t peer_mtu,
if (s16BitPool < 0) s16BitPool = 0;
- LOG_VERBOSE("%s: bitpool candidate: %d (%d kbps)", __func__, s16BitPool,
- p_encoder_params->u16BitRate);
+ LOG_DEBUG(LOG_TAG, "%s: bitpool candidate: %d (%d kbps)", __func__,
+ s16BitPool, p_encoder_params->u16BitRate);
if (s16BitPool > max_bitpool) {
- LOG_VERBOSE("%s: computed bitpool too large (%d)", __func__, s16BitPool);
+ LOG_DEBUG(LOG_TAG, "%s: computed bitpool too large (%d)", __func__,
+ s16BitPool);
/* Decrease bitrate */
p_encoder_params->u16BitRate -= A2DP_SBC_BITRATE_STEP;
/* Record that we have decreased the bitrate */
protect |= 1;
} else if (s16BitPool < min_bitpool) {
- LOG_WARN("%s: computed bitpool too small (%d)", __func__, s16BitPool);
+ LOG_WARN(LOG_TAG, "%s: computed bitpool too small (%d)", __func__,
+ s16BitPool);
/* Increase bitrate */
uint16_t previous_u16BitRate = p_encoder_params->u16BitRate;
@@ -351,7 +356,7 @@ static void a2dp_sbc_encoder_update(uint16_t peer_mtu,
}
/* In case we have already increased and decreased the bitrate, just stop */
if (protect == 3) {
- LOG_ERROR("%s: could not find bitpool in range", __func__);
+ LOG_ERROR(LOG_TAG, "%s: could not find bitpool in range", __func__);
break;
}
} while (true);
@@ -359,8 +364,8 @@ static void a2dp_sbc_encoder_update(uint16_t peer_mtu,
/* Finally update the bitpool in the encoder structure */
p_encoder_params->s16BitPool = s16BitPool;
- LOG_INFO("%s: final bit rate %d, final bit pool %d", __func__,
- p_encoder_params->u16BitRate, p_encoder_params->s16BitPool);
+ LOG_DEBUG(LOG_TAG, "%s: final bit rate %d, final bit pool %d", __func__,
+ p_encoder_params->u16BitRate, p_encoder_params->s16BitPool);
/* Reset the SBC encoder */
SBC_Encoder_Init(&a2dp_sbc_encoder_cb.sbc_encoder_params);
@@ -383,12 +388,12 @@ void a2dp_sbc_feeding_reset(void) {
A2DP_SBC_ENCODER_INTERVAL_MS) /
1000;
- LOG_INFO("%s: PCM bytes per tick %u", __func__,
- a2dp_sbc_encoder_cb.feeding_state.bytes_per_tick);
+ LOG_DEBUG(LOG_TAG, "%s: PCM bytes per tick %u", __func__,
+ a2dp_sbc_encoder_cb.feeding_state.bytes_per_tick);
}
void a2dp_sbc_feeding_flush(void) {
- a2dp_sbc_encoder_cb.feeding_state.counter = 0.0f;
+ a2dp_sbc_encoder_cb.feeding_state.counter = 0;
a2dp_sbc_encoder_cb.feeding_state.aa_feed_residue = 0;
}
@@ -401,8 +406,8 @@ void a2dp_sbc_send_frames(uint64_t timestamp_us) {
uint8_t nb_iterations = 0;
a2dp_sbc_get_num_frame_iteration(&nb_iterations, &nb_frame, timestamp_us);
- LOG_VERBOSE("%s: Sending %d frames per iteration, %d iterations", __func__,
- nb_frame, nb_iterations);
+ LOG_VERBOSE(LOG_TAG, "%s: Sending %d frames per iteration, %d iterations",
+ __func__, nb_frame, nb_iterations);
if (nb_frame == 0) return;
for (uint8_t counter = 0; counter < nb_iterations; counter++) {
@@ -426,17 +431,33 @@ static void a2dp_sbc_get_num_frame_iteration(uint8_t* num_of_iterations,
a2dp_sbc_encoder_cb.sbc_encoder_params.s16NumOfBlocks *
a2dp_sbc_encoder_cb.feeding_params.channel_count *
a2dp_sbc_encoder_cb.feeding_params.bits_per_sample / 8;
- LOG_VERBOSE("%s: pcm_bytes_per_frame %u", __func__, pcm_bytes_per_frame);
-
- uint32_t us_this_tick = A2DP_SBC_ENCODER_INTERVAL_MS * 1000;
- uint64_t now_us = timestamp_us;
- if (a2dp_sbc_encoder_cb.feeding_state.last_frame_us != 0)
- us_this_tick = (now_us - a2dp_sbc_encoder_cb.feeding_state.last_frame_us);
- a2dp_sbc_encoder_cb.feeding_state.last_frame_us = now_us;
-
- a2dp_sbc_encoder_cb.feeding_state.counter +=
- (float)a2dp_sbc_encoder_cb.feeding_state.bytes_per_tick * us_this_tick /
- (A2DP_SBC_ENCODER_INTERVAL_MS * 1000);
+ LOG_VERBOSE(LOG_TAG, "%s: pcm_bytes_per_frame %u", __func__,
+ pcm_bytes_per_frame);
+
+ uint32_t hecto_ns_this_tick = A2DP_SBC_ENCODER_INTERVAL_MS * 10000;
+ uint64_t* last_100ns =
+ &a2dp_sbc_encoder_cb.feeding_state.last_frame_timestamp_100ns;
+ uint64_t now_100ns = timestamp_us * 10;
+ if (*last_100ns != 0) {
+ hecto_ns_this_tick = (now_100ns - *last_100ns);
+ }
+ *last_100ns = now_100ns;
+
+ uint32_t bytes_this_tick = a2dp_sbc_encoder_cb.feeding_state.bytes_per_tick *
+ hecto_ns_this_tick /
+ (A2DP_SBC_ENCODER_INTERVAL_MS * 10000);
+ a2dp_sbc_encoder_cb.feeding_state.counter += bytes_this_tick;
+ // Without this erratum, there was a three microseocnd shift per tick which
+ // would cause one SBC frame mismatched after every 20 seconds
+ uint32_t erratum_100ns =
+ ceil(1.0f * A2DP_SBC_ENCODER_INTERVAL_MS * 10000 * bytes_this_tick /
+ a2dp_sbc_encoder_cb.feeding_state.bytes_per_tick);
+ if (erratum_100ns < hecto_ns_this_tick) {
+ LOG_VERBOSE(LOG_TAG,
+ "%s: hecto_ns_this_tick=%d, bytes=%d, erratum_100ns=%d",
+ __func__, hecto_ns_this_tick, bytes_this_tick, erratum_100ns);
+ *last_100ns -= hecto_ns_this_tick - erratum_100ns;
+ }
/* Calculate the number of frames pending for this media tick */
projected_nof =
@@ -445,7 +466,7 @@ static void a2dp_sbc_get_num_frame_iteration(uint8_t* num_of_iterations,
a2dp_sbc_encoder_cb.stats.media_read_total_expected_frames += projected_nof;
if (projected_nof > MAX_PCM_FRAME_NUM_PER_TICK) {
- LOG_WARN("%s: limiting frames to be sent from %d to %d", __func__,
+ LOG_WARN(LOG_TAG, "%s: limiting frames to be sent from %d to %d", __func__,
projected_nof, MAX_PCM_FRAME_NUM_PER_TICK);
// Update the stats
@@ -455,17 +476,20 @@ static void a2dp_sbc_get_num_frame_iteration(uint8_t* num_of_iterations,
projected_nof = MAX_PCM_FRAME_NUM_PER_TICK;
}
- LOG_VERBOSE("%s: frames for available PCM data %u", __func__, projected_nof);
+ LOG_VERBOSE(LOG_TAG, "%s: frames for available PCM data %u", __func__,
+ projected_nof);
if (a2dp_sbc_encoder_cb.is_peer_edr) {
if (!a2dp_sbc_encoder_cb.tx_sbc_frames) {
- LOG_ERROR("%s: tx_sbc_frames not updated, update from here", __func__);
+ LOG_ERROR(LOG_TAG, "%s: tx_sbc_frames not updated, update from here",
+ __func__);
a2dp_sbc_encoder_cb.tx_sbc_frames = calculate_max_frames_per_packet();
}
nof = a2dp_sbc_encoder_cb.tx_sbc_frames;
if (!nof) {
- LOG_ERROR("%s: number of frames not updated, set calculated values",
+ LOG_ERROR(LOG_TAG,
+ "%s: number of frames not updated, set calculated values",
__func__);
nof = projected_nof;
noi = 1;
@@ -473,8 +497,8 @@ static void a2dp_sbc_get_num_frame_iteration(uint8_t* num_of_iterations,
if (nof < projected_nof) {
noi = projected_nof / nof; // number of iterations would vary
if (noi > A2DP_SBC_MAX_PCM_ITER_NUM_PER_TICK) {
- LOG_ERROR("%s: Audio Congestion (iterations:%d > max (%d))", __func__,
- noi, A2DP_SBC_MAX_PCM_ITER_NUM_PER_TICK);
+ LOG_ERROR(LOG_TAG, "%s: Audio Congestion (iterations:%d > max (%d))",
+ __func__, noi, A2DP_SBC_MAX_PCM_ITER_NUM_PER_TICK);
noi = A2DP_SBC_MAX_PCM_ITER_NUM_PER_TICK;
a2dp_sbc_encoder_cb.feeding_state.counter =
noi * nof * pcm_bytes_per_frame;
@@ -482,16 +506,17 @@ static void a2dp_sbc_get_num_frame_iteration(uint8_t* num_of_iterations,
projected_nof = nof;
} else {
noi = 1; // number of iterations is 1
- LOG_VERBOSE("%s: reducing frames for available PCM data", __func__);
+ LOG_VERBOSE(LOG_TAG, "%s: reducing frames for available PCM data",
+ __func__);
nof = projected_nof;
}
}
} else {
// For BR cases nof will be same as the value retrieved at projected_nof
- LOG_VERBOSE("%s: headset BR, number of frames %u", __func__, nof);
+ LOG_VERBOSE(LOG_TAG, "%s: headset BR, number of frames %u", __func__, nof);
if (projected_nof > MAX_PCM_FRAME_NUM_PER_TICK) {
- LOG_ERROR("%s: Audio Congestion (frames: %d > max (%d))", __func__,
- projected_nof, MAX_PCM_FRAME_NUM_PER_TICK);
+ LOG_ERROR(LOG_TAG, "%s: Audio Congestion (frames: %d > max (%d))",
+ __func__, projected_nof, MAX_PCM_FRAME_NUM_PER_TICK);
// Update the stats
size_t delta = projected_nof - MAX_PCM_FRAME_NUM_PER_TICK;
@@ -504,8 +529,8 @@ static void a2dp_sbc_get_num_frame_iteration(uint8_t* num_of_iterations,
nof = projected_nof;
}
a2dp_sbc_encoder_cb.feeding_state.counter -= noi * nof * pcm_bytes_per_frame;
- LOG_VERBOSE("%s: effective num of frames %u, iterations %u", __func__, nof,
- noi);
+ LOG_VERBOSE(LOG_TAG, "%s: effective num of frames %u, iterations %u",
+ __func__, nof, noi);
*num_of_frames = nof;
*num_of_iterations = noi;
@@ -549,7 +574,7 @@ static void a2dp_sbc_encode_frames(uint8_t nb_frame) {
bytes_read += num_bytes;
} else {
- LOG_WARN("%s: underflow %d, %d", __func__, nb_frame,
+ LOG_WARN(LOG_TAG, "%s: underflow %d, %d", __func__, nb_frame,
a2dp_sbc_encoder_cb.feeding_state.aa_feed_residue);
a2dp_sbc_encoder_cb.feeding_state.counter +=
nb_frame * p_encoder_params->s16NumOfSubBands *
@@ -748,18 +773,19 @@ static uint8_t calculate_max_frames_per_packet(void) {
uint16_t result = 0;
uint32_t frame_len;
- LOG_VERBOSE("%s: original AVDTP MTU size: %d", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: original AVDTP MTU size: %d", __func__,
a2dp_sbc_encoder_cb.TxAaMtuSize);
if (a2dp_sbc_encoder_cb.is_peer_edr &&
!a2dp_sbc_encoder_cb.peer_supports_3mbps) {
// This condition would be satisfied only if the remote device is
// EDR and supports only 2 Mbps, but the effective AVDTP MTU size
// exceeds the 2DH5 packet size.
- LOG_VERBOSE("%s: The remote device is EDR but does not support 3 Mbps",
+ LOG_VERBOSE(LOG_TAG,
+ "%s: The remote device is EDR but does not support 3 Mbps",
__func__);
if (effective_mtu_size > MAX_2MBPS_AVDTP_MTU) {
- LOG_WARN("%s: Restricting AVDTP MTU size to %d", __func__,
+ LOG_WARN(LOG_TAG, "%s: Restricting AVDTP MTU size to %d", __func__,
MAX_2MBPS_AVDTP_MTU);
effective_mtu_size = MAX_2MBPS_AVDTP_MTU;
a2dp_sbc_encoder_cb.TxAaMtuSize = effective_mtu_size;
@@ -767,49 +793,53 @@ static uint8_t calculate_max_frames_per_packet(void) {
}
if (!p_encoder_params->s16NumOfSubBands) {
- LOG_ERROR("%s: SubBands are set to 0, resetting to %d", __func__,
+ LOG_ERROR(LOG_TAG, "%s: SubBands are set to 0, resetting to %d", __func__,
SBC_MAX_NUM_OF_SUBBANDS);
p_encoder_params->s16NumOfSubBands = SBC_MAX_NUM_OF_SUBBANDS;
}
if (!p_encoder_params->s16NumOfBlocks) {
- LOG_ERROR("%s: Blocks are set to 0, resetting to %d", __func__,
+ LOG_ERROR(LOG_TAG, "%s: Blocks are set to 0, resetting to %d", __func__,
SBC_MAX_NUM_OF_BLOCKS);
p_encoder_params->s16NumOfBlocks = SBC_MAX_NUM_OF_BLOCKS;
}
if (!p_encoder_params->s16NumOfChannels) {
- LOG_ERROR("%s: Channels are set to 0, resetting to %d", __func__,
+ LOG_ERROR(LOG_TAG, "%s: Channels are set to 0, resetting to %d", __func__,
SBC_MAX_NUM_OF_CHANNELS);
p_encoder_params->s16NumOfChannels = SBC_MAX_NUM_OF_CHANNELS;
}
frame_len = a2dp_sbc_frame_length();
- LOG_VERBOSE("%s: Effective Tx MTU to be considered: %d", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: Effective Tx MTU to be considered: %d", __func__,
effective_mtu_size);
switch (p_encoder_params->s16SamplingFreq) {
case SBC_sf44100:
if (frame_len == 0) {
- LOG_ERROR("%s: Calculating frame length, resetting it to default %d",
+ LOG_ERROR(LOG_TAG,
+ "%s: Calculating frame length, resetting it to default %d",
__func__, A2DP_SBC_MAX_HQ_FRAME_SIZE_44_1);
frame_len = A2DP_SBC_MAX_HQ_FRAME_SIZE_44_1;
}
result = (effective_mtu_size - A2DP_HDR_SIZE) / frame_len;
- LOG_VERBOSE("%s: Max number of SBC frames: %d", __func__, result);
+ LOG_VERBOSE(LOG_TAG, "%s: Max number of SBC frames: %d", __func__,
+ result);
break;
case SBC_sf48000:
if (frame_len == 0) {
- LOG_ERROR("%s: Calculating frame length, resetting it to default %d",
+ LOG_ERROR(LOG_TAG,
+ "%s: Calculating frame length, resetting it to default %d",
__func__, A2DP_SBC_MAX_HQ_FRAME_SIZE_48);
frame_len = A2DP_SBC_MAX_HQ_FRAME_SIZE_48;
}
result = (effective_mtu_size - A2DP_HDR_SIZE) / frame_len;
- LOG_VERBOSE("%s: Max number of SBC frames: %d", __func__, result);
+ LOG_VERBOSE(LOG_TAG, "%s: Max number of SBC frames: %d", __func__,
+ result);
break;
default:
- LOG_ERROR("%s: Max number of SBC frames: %d", __func__, result);
+ LOG_ERROR(LOG_TAG, "%s: Max number of SBC frames: %d", __func__, result);
break;
}
return result;
@@ -821,8 +851,8 @@ static uint16_t a2dp_sbc_source_rate() {
/* restrict bitrate if a2dp link is non-edr */
if (!a2dp_sbc_encoder_cb.is_peer_edr) {
rate = A2DP_SBC_NON_EDR_MAX_RATE;
- LOG_VERBOSE("%s: non-edr a2dp sink detected, restrict rate to %d", __func__,
- rate);
+ LOG_VERBOSE(LOG_TAG, "%s: non-edr a2dp sink detected, restrict rate to %d",
+ __func__, rate);
}
return rate;
@@ -832,13 +862,14 @@ static uint32_t a2dp_sbc_frame_length(void) {
SBC_ENC_PARAMS* p_encoder_params = &a2dp_sbc_encoder_cb.sbc_encoder_params;
uint32_t frame_len = 0;
- LOG_VERBOSE(
- "%s: channel mode: %d, sub-band: %d, number of block: %d, "
- "bitpool: %d, sampling frequency: %d, num channels: %d",
- __func__, p_encoder_params->s16ChannelMode,
- p_encoder_params->s16NumOfSubBands, p_encoder_params->s16NumOfBlocks,
- p_encoder_params->s16BitPool, p_encoder_params->s16SamplingFreq,
- p_encoder_params->s16NumOfChannels);
+ LOG_VERBOSE(LOG_TAG,
+ "%s: channel mode: %d, sub-band: %d, number of block: %d, "
+ "bitpool: %d, sampling frequency: %d, num channels: %d",
+ __func__, p_encoder_params->s16ChannelMode,
+ p_encoder_params->s16NumOfSubBands,
+ p_encoder_params->s16NumOfBlocks, p_encoder_params->s16BitPool,
+ p_encoder_params->s16SamplingFreq,
+ p_encoder_params->s16NumOfChannels);
switch (p_encoder_params->s16ChannelMode) {
case SBC_MONO:
@@ -876,17 +907,18 @@ static uint32_t a2dp_sbc_frame_length(void) {
CHAR_BIT);
break;
default:
- LOG_VERBOSE("%s: Invalid channel number: %d", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: Invalid channel number: %d", __func__,
p_encoder_params->s16ChannelMode);
break;
}
- LOG_VERBOSE("%s: calculated frame length: %d", __func__, frame_len);
+ LOG_VERBOSE(LOG_TAG, "%s: calculated frame length: %d", __func__, frame_len);
return frame_len;
}
uint32_t a2dp_sbc_get_bitrate() {
SBC_ENC_PARAMS* p_encoder_params = &a2dp_sbc_encoder_cb.sbc_encoder_params;
- LOG_INFO("%s: bit rate %d ", __func__, p_encoder_params->u16BitRate);
+ LOG_DEBUG(LOG_TAG, "%s: bit rate %d ", __func__,
+ p_encoder_params->u16BitRate);
return p_encoder_params->u16BitRate * 1000;
}
@@ -903,23 +935,6 @@ void A2dpCodecConfigSbcSource::debug_codec_dump(int fd) {
A2dpCodecConfig::debug_codec_dump(fd);
- uint8_t codec_info[AVDT_CODEC_SIZE];
- if (copyOutOtaCodecConfig(codec_info)) {
- dprintf(fd,
- " Block length : %d\n",
- A2DP_GetNumberOfBlocksSbc(codec_info));
- dprintf(fd,
- " Number of subbands : %d\n",
- A2DP_GetNumberOfSubbandsSbc(codec_info));
- dprintf(fd,
- " Allocation method : %d\n",
- A2DP_GetAllocationMethodCodeSbc(codec_info));
- dprintf(
- fd,
- " Bitpool (min/max) : %d / %d\n",
- A2DP_GetMinBitpoolSbc(codec_info), A2DP_GetMaxBitpoolSbc(codec_info));
- }
-
dprintf(fd,
" Packet counts (expected/dropped) : %zu / "
"%zu\n",
diff --git a/stack/a2dp/a2dp_vendor_aptx.cc b/stack/a2dp/a2dp_vendor_aptx.cc
index d256b76a0..e3e844d73 100644
--- a/stack/a2dp/a2dp_vendor_aptx.cc
+++ b/stack/a2dp/a2dp_vendor_aptx.cc
@@ -208,15 +208,15 @@ static tA2DP_STATUS A2DP_CodecInfoMatchesCapabilityAptx(
/* parse configuration */
status = A2DP_ParseInfoAptx(&cfg_cie, p_codec_info, is_capability);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: parsing failed %d", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s: parsing failed %d", __func__, status);
return status;
}
/* verify that each parameter is in range */
- LOG_VERBOSE("%s: FREQ peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: FREQ peer: 0x%x, capability 0x%x", __func__,
cfg_cie.sampleRate, p_cap->sampleRate);
- LOG_VERBOSE("%s: CH_MODE peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: CH_MODE peer: 0x%x, capability 0x%x", __func__,
cfg_cie.channelMode, p_cap->channelMode);
/* sampling frequency */
@@ -251,12 +251,14 @@ bool A2DP_VendorCodecTypeEqualsAptx(const uint8_t* p_codec_info_a,
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoAptx(&aptx_cie_a, p_codec_info_a, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
a2dp_status = A2DP_ParseInfoAptx(&aptx_cie_b, p_codec_info_b, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
@@ -272,12 +274,14 @@ bool A2DP_VendorCodecEqualsAptx(const uint8_t* p_codec_info_a,
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoAptx(&aptx_cie_a, p_codec_info_a, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
a2dp_status = A2DP_ParseInfoAptx(&aptx_cie_b, p_codec_info_b, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
@@ -298,7 +302,8 @@ int A2DP_VendorGetTrackSampleRateAptx(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAptx(&aptx_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -314,7 +319,8 @@ int A2DP_VendorGetTrackBitsPerSampleAptx(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAptx(&aptx_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -328,7 +334,8 @@ int A2DP_VendorGetTrackChannelCountAptx(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoAptx(&aptx_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -462,7 +469,7 @@ bool A2dpCodecConfigAptx::init() {
// Load the encoder
if (!A2DP_VendorLoadEncoderAptx()) {
- LOG_ERROR("%s: cannot load the encoder", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot load the encoder", __func__);
return false;
}
@@ -639,8 +646,8 @@ bool A2dpCodecConfigAptx::setCodecConfig(const uint8_t* p_peer_codec_info,
tA2DP_STATUS status =
A2DP_ParseInfoAptx(&peer_info_cie, p_peer_codec_info, is_capability);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: can't parse peer's capabilities: error = %d", __func__,
- status);
+ LOG_ERROR(LOG_TAG, "%s: can't parse peer's capabilities: error = %d",
+ __func__, status);
goto fail;
}
@@ -723,10 +730,11 @@ bool A2dpCodecConfigAptx::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.sample_rate == BTAV_A2DP_CODEC_SAMPLE_RATE_NONE) {
- LOG_ERROR(
- "%s: cannot match sample frequency: local caps = 0x%x "
- "peer info = 0x%x",
- __func__, a2dp_aptx_source_caps.sampleRate, peer_info_cie.sampleRate);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match sample frequency: local caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, a2dp_aptx_source_caps.sampleRate,
+ peer_info_cie.sampleRate);
goto fail;
}
@@ -778,7 +786,8 @@ bool A2dpCodecConfigAptx::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.bits_per_sample == BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE) {
- LOG_ERROR("%s: cannot match bits per sample: user preference = 0x%x",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match bits per sample: user preference = 0x%x",
__func__, codec_user_config_.bits_per_sample);
goto fail;
}
@@ -849,10 +858,11 @@ bool A2dpCodecConfigAptx::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.channel_mode == BTAV_A2DP_CODEC_CHANNEL_MODE_NONE) {
- LOG_ERROR(
- "%s: cannot match channel mode: local caps = 0x%x "
- "peer info = 0x%x",
- __func__, a2dp_aptx_source_caps.channelMode, peer_info_cie.channelMode);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match channel mode: local caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, a2dp_aptx_source_caps.channelMode,
+ peer_info_cie.channelMode);
goto fail;
}
@@ -929,8 +939,8 @@ bool A2dpCodecConfigAptx::setPeerCodecCapabilities(
tA2DP_STATUS status =
A2DP_ParseInfoAptx(&peer_info_cie, p_peer_codec_capabilities, true);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: can't parse peer's capabilities: error = %d", __func__,
- status);
+ LOG_ERROR(LOG_TAG, "%s: can't parse peer's capabilities: error = %d",
+ __func__, status);
goto fail;
}
diff --git a/stack/a2dp/a2dp_vendor_aptx_encoder.cc b/stack/a2dp/a2dp_vendor_aptx_encoder.cc
index bc8752117..0d605c057 100644
--- a/stack/a2dp/a2dp_vendor_aptx_encoder.cc
+++ b/stack/a2dp/a2dp_vendor_aptx_encoder.cc
@@ -119,7 +119,7 @@ bool A2DP_VendorLoadEncoderAptx(void) {
// Open the encoder library
aptx_encoder_lib_handle = dlopen(APTX_ENCODER_LIB_NAME, RTLD_NOW);
if (aptx_encoder_lib_handle == NULL) {
- LOG_ERROR("%s: cannot open aptX encoder library %s: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s: cannot open aptX encoder library %s: %s", __func__,
APTX_ENCODER_LIB_NAME, dlerror());
return false;
}
@@ -127,7 +127,8 @@ bool A2DP_VendorLoadEncoderAptx(void) {
aptx_encoder_init_func = (tAPTX_ENCODER_INIT)dlsym(aptx_encoder_lib_handle,
APTX_ENCODER_INIT_NAME);
if (aptx_encoder_init_func == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the encoder library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the encoder library: %s",
__func__, APTX_ENCODER_INIT_NAME, dlerror());
A2DP_VendorUnloadEncoderAptx();
return false;
@@ -136,7 +137,8 @@ bool A2DP_VendorLoadEncoderAptx(void) {
aptx_encoder_encode_stereo_func = (tAPTX_ENCODER_ENCODE_STEREO)dlsym(
aptx_encoder_lib_handle, APTX_ENCODER_ENCODE_STEREO_NAME);
if (aptx_encoder_encode_stereo_func == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the encoder library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the encoder library: %s",
__func__, APTX_ENCODER_ENCODE_STEREO_NAME, dlerror());
A2DP_VendorUnloadEncoderAptx();
return false;
@@ -145,7 +147,8 @@ bool A2DP_VendorLoadEncoderAptx(void) {
aptx_encoder_sizeof_params_func = (tAPTX_ENCODER_SIZEOF_PARAMS)dlsym(
aptx_encoder_lib_handle, APTX_ENCODER_SIZEOF_PARAMS_NAME);
if (aptx_encoder_sizeof_params_func == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the encoder library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the encoder library: %s",
__func__, APTX_ENCODER_SIZEOF_PARAMS_NAME, dlerror());
A2DP_VendorUnloadEncoderAptx();
return false;
@@ -193,7 +196,7 @@ void a2dp_vendor_aptx_encoder_init(
if (a2dp_aptx_encoder_cb.aptx_encoder_state != NULL) {
aptx_encoder_init_func(a2dp_aptx_encoder_cb.aptx_encoder_state, 0);
} else {
- LOG_ERROR("%s: Cannot allocate aptX encoder state", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Cannot allocate aptX encoder state", __func__);
// TODO: Return an error?
}
@@ -216,10 +219,10 @@ bool A2dpCodecConfigAptx::updateEncoderUserConfig(
a2dp_aptx_encoder_cb.timestamp = 0;
if (a2dp_aptx_encoder_cb.peer_mtu == 0) {
- LOG_ERROR(
- "%s: Cannot update the codec encoder for %s: "
- "invalid peer MTU",
- __func__, name().c_str());
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot update the codec encoder for %s: "
+ "invalid peer MTU",
+ __func__, name().c_str());
return false;
}
@@ -243,10 +246,10 @@ static void a2dp_vendor_aptx_encoder_update(uint16_t peer_mtu,
*p_restart_output = false;
*p_config_updated = false;
if (!a2dp_codec_config->copyOutOtaCodecConfig(codec_info)) {
- LOG_ERROR(
- "%s: Cannot update the codec encoder for %s: "
- "invalid codec config",
- __func__, a2dp_codec_config->name().c_str());
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot update the codec encoder for %s: "
+ "invalid codec config",
+ __func__, a2dp_codec_config->name().c_str());
return;
}
const uint8_t* p_codec_info = codec_info;
@@ -259,9 +262,9 @@ static void a2dp_vendor_aptx_encoder_update(uint16_t peer_mtu,
a2dp_codec_config->getAudioBitsPerSample();
p_feeding_params->channel_count =
A2DP_VendorGetTrackChannelCountAptx(p_codec_info);
- LOG_INFO("%s: sample_rate=%u bits_per_sample=%u channel_count=%u", __func__,
- p_feeding_params->sample_rate, p_feeding_params->bits_per_sample,
- p_feeding_params->channel_count);
+ LOG_DEBUG(LOG_TAG, "%s: sample_rate=%u bits_per_sample=%u channel_count=%u",
+ __func__, p_feeding_params->sample_rate,
+ p_feeding_params->bits_per_sample, p_feeding_params->channel_count);
a2dp_vendor_aptx_feeding_reset();
}
@@ -296,8 +299,8 @@ static void aptx_init_framing_params(tAPTX_FRAMING_PARAMS* framing_params) {
}
}
- LOG_INFO("%s: sleep_time_ns = %" PRIu64, __func__,
- framing_params->sleep_time_ns);
+ LOG_DEBUG(LOG_TAG, "%s: sleep_time_ns = %" PRIu64, __func__,
+ framing_params->sleep_time_ns);
}
//
@@ -351,7 +354,8 @@ static void aptx_update_framing_params(tAPTX_FRAMING_PARAMS* framing_params) {
}
}
- LOG_VERBOSE("%s: sleep_time_ns = %" PRIu64
+ LOG_VERBOSE(LOG_TAG,
+ "%s: sleep_time_ns = %" PRIu64
" aptx_bytes = %u "
"pcm_bytes_per_read = %u pcm_reads = %u frame_size_counter = %u",
__func__, framing_params->sleep_time_ns,
@@ -400,12 +404,14 @@ void a2dp_vendor_aptx_send_frames(uint64_t timestamp_us) {
a2dp_aptx_encoder_cb.stats.media_read_total_expected_read_bytes +=
expected_read_bytes;
- LOG_VERBOSE("%s: PCM read of size %u", __func__, expected_read_bytes);
+ LOG_VERBOSE(LOG_TAG, "%s: PCM read of size %u", __func__,
+ expected_read_bytes);
bytes_read = a2dp_aptx_encoder_cb.read_callback((uint8_t*)read_buffer16,
expected_read_bytes);
a2dp_aptx_encoder_cb.stats.media_read_total_actual_read_bytes += bytes_read;
if (bytes_read < expected_read_bytes) {
- LOG_WARN("%s: underflow at PCM reading: read %u bytes instead of %u",
+ LOG_WARN(LOG_TAG,
+ "%s: underflow at PCM reading: read %u bytes instead of %u",
__func__, bytes_read, expected_read_bytes);
a2dp_aptx_encoder_cb.stats.media_read_total_dropped_packets++;
osi_free(p_buf);
@@ -424,8 +430,8 @@ void a2dp_vendor_aptx_send_frames(uint64_t timestamp_us) {
const int COMPRESSION_RATIO = 4;
size_t encoded_bytes = pcm_bytes_encoded / COMPRESSION_RATIO;
p_buf->len += encoded_bytes;
- LOG_VERBOSE("%s: encoded %zu PCM bytes to %zu", __func__, pcm_bytes_encoded,
- encoded_bytes);
+ LOG_VERBOSE(LOG_TAG, "%s: encoded %zu PCM bytes to %zu", __func__,
+ pcm_bytes_encoded, encoded_bytes);
// Update the RTP timestamp
*((uint32_t*)(p_buf + 1)) = a2dp_aptx_encoder_cb.timestamp;
diff --git a/stack/a2dp/a2dp_vendor_aptx_hd.cc b/stack/a2dp/a2dp_vendor_aptx_hd.cc
index 0b5916b5d..9e19d5fee 100644
--- a/stack/a2dp/a2dp_vendor_aptx_hd.cc
+++ b/stack/a2dp/a2dp_vendor_aptx_hd.cc
@@ -226,15 +226,15 @@ static tA2DP_STATUS A2DP_CodecInfoMatchesCapabilityAptxHd(
/* parse configuration */
status = A2DP_ParseInfoAptxHd(&cfg_cie, p_codec_info, is_capability);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: parsing failed %d", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s: parsing failed %d", __func__, status);
return status;
}
/* verify that each parameter is in range */
- LOG_VERBOSE("%s: FREQ peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: FREQ peer: 0x%x, capability 0x%x", __func__,
cfg_cie.sampleRate, p_cap->sampleRate);
- LOG_VERBOSE("%s: CH_MODE peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: CH_MODE peer: 0x%x, capability 0x%x", __func__,
cfg_cie.channelMode, p_cap->channelMode);
/* sampling frequency */
@@ -265,12 +265,14 @@ bool A2DP_VendorCodecTypeEqualsAptxHd(const uint8_t* p_codec_info_a,
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoAptxHd(&aptx_hd_cie_a, p_codec_info_a, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
a2dp_status = A2DP_ParseInfoAptxHd(&aptx_hd_cie_b, p_codec_info_b, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
@@ -286,12 +288,14 @@ bool A2DP_VendorCodecEqualsAptxHd(const uint8_t* p_codec_info_a,
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoAptxHd(&aptx_hd_cie_a, p_codec_info_a, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
a2dp_status = A2DP_ParseInfoAptxHd(&aptx_hd_cie_b, p_codec_info_b, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
@@ -313,7 +317,8 @@ int A2DP_VendorGetTrackSampleRateAptxHd(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoAptxHd(&aptx_hd_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -330,7 +335,8 @@ int A2DP_VendorGetTrackBitsPerSampleAptxHd(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoAptxHd(&aptx_hd_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -345,7 +351,8 @@ int A2DP_VendorGetTrackChannelCountAptxHd(const uint8_t* p_codec_info) {
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoAptxHd(&aptx_hd_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -480,7 +487,7 @@ bool A2dpCodecConfigAptxHd::init() {
// Load the encoder
if (!A2DP_VendorLoadEncoderAptxHd()) {
- LOG_ERROR("%s: cannot load the encoder", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot load the encoder", __func__);
return false;
}
@@ -657,8 +664,8 @@ bool A2dpCodecConfigAptxHd::setCodecConfig(const uint8_t* p_peer_codec_info,
tA2DP_STATUS status =
A2DP_ParseInfoAptxHd(&peer_info_cie, p_peer_codec_info, is_capability);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: can't parse peer's capabilities: error = %d", __func__,
- status);
+ LOG_ERROR(LOG_TAG, "%s: can't parse peer's capabilities: error = %d",
+ __func__, status);
goto fail;
}
@@ -741,11 +748,11 @@ bool A2dpCodecConfigAptxHd::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.sample_rate == BTAV_A2DP_CODEC_SAMPLE_RATE_NONE) {
- LOG_ERROR(
- "%s: cannot match sample frequency: local caps = 0x%x "
- "peer info = 0x%x",
- __func__, a2dp_aptx_hd_source_caps.sampleRate,
- peer_info_cie.sampleRate);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match sample frequency: local caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, a2dp_aptx_hd_source_caps.sampleRate,
+ peer_info_cie.sampleRate);
goto fail;
}
@@ -797,7 +804,8 @@ bool A2dpCodecConfigAptxHd::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.bits_per_sample == BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE) {
- LOG_ERROR("%s: cannot match bits per sample: user preference = 0x%x",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match bits per sample: user preference = 0x%x",
__func__, codec_user_config_.bits_per_sample);
goto fail;
}
@@ -869,11 +877,11 @@ bool A2dpCodecConfigAptxHd::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.channel_mode == BTAV_A2DP_CODEC_CHANNEL_MODE_NONE) {
- LOG_ERROR(
- "%s: cannot match channel mode: local caps = 0x%x "
- "peer info = 0x%x",
- __func__, a2dp_aptx_hd_source_caps.channelMode,
- peer_info_cie.channelMode);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match channel mode: local caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, a2dp_aptx_hd_source_caps.channelMode,
+ peer_info_cie.channelMode);
goto fail;
}
@@ -957,8 +965,8 @@ bool A2dpCodecConfigAptxHd::setPeerCodecCapabilities(
tA2DP_STATUS status =
A2DP_ParseInfoAptxHd(&peer_info_cie, p_peer_codec_capabilities, true);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: can't parse peer's capabilities: error = %d", __func__,
- status);
+ LOG_ERROR(LOG_TAG, "%s: can't parse peer's capabilities: error = %d",
+ __func__, status);
goto fail;
}
diff --git a/stack/a2dp/a2dp_vendor_aptx_hd_encoder.cc b/stack/a2dp/a2dp_vendor_aptx_hd_encoder.cc
index 5856e0827..fb782dd8d 100644
--- a/stack/a2dp/a2dp_vendor_aptx_hd_encoder.cc
+++ b/stack/a2dp/a2dp_vendor_aptx_hd_encoder.cc
@@ -119,15 +119,16 @@ bool A2DP_VendorLoadEncoderAptxHd(void) {
// Open the encoder library
aptx_hd_encoder_lib_handle = dlopen(APTX_HD_ENCODER_LIB_NAME, RTLD_NOW);
if (aptx_hd_encoder_lib_handle == NULL) {
- LOG_ERROR("%s: cannot open aptX-HD encoder library %s: %s", __func__,
- APTX_HD_ENCODER_LIB_NAME, dlerror());
+ LOG_ERROR(LOG_TAG, "%s: cannot open aptX-HD encoder library %s: %s",
+ __func__, APTX_HD_ENCODER_LIB_NAME, dlerror());
return false;
}
aptx_hd_encoder_init_func = (tAPTX_HD_ENCODER_INIT)dlsym(
aptx_hd_encoder_lib_handle, APTX_HD_ENCODER_INIT_NAME);
if (aptx_hd_encoder_init_func == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the encoder library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the encoder library: %s",
__func__, APTX_HD_ENCODER_INIT_NAME, dlerror());
A2DP_VendorUnloadEncoderAptxHd();
return false;
@@ -136,7 +137,8 @@ bool A2DP_VendorLoadEncoderAptxHd(void) {
aptx_hd_encoder_encode_stereo_func = (tAPTX_HD_ENCODER_ENCODE_STEREO)dlsym(
aptx_hd_encoder_lib_handle, APTX_HD_ENCODER_ENCODE_STEREO_NAME);
if (aptx_hd_encoder_encode_stereo_func == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the encoder library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the encoder library: %s",
__func__, APTX_HD_ENCODER_ENCODE_STEREO_NAME, dlerror());
A2DP_VendorUnloadEncoderAptxHd();
return false;
@@ -145,7 +147,8 @@ bool A2DP_VendorLoadEncoderAptxHd(void) {
aptx_hd_encoder_sizeof_params_func = (tAPTX_HD_ENCODER_SIZEOF_PARAMS)dlsym(
aptx_hd_encoder_lib_handle, APTX_HD_ENCODER_SIZEOF_PARAMS_NAME);
if (aptx_hd_encoder_sizeof_params_func == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the encoder library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the encoder library: %s",
__func__, APTX_HD_ENCODER_SIZEOF_PARAMS_NAME, dlerror());
A2DP_VendorUnloadEncoderAptxHd();
return false;
@@ -194,7 +197,7 @@ void a2dp_vendor_aptx_hd_encoder_init(
if (a2dp_aptx_hd_encoder_cb.aptx_hd_encoder_state != NULL) {
aptx_hd_encoder_init_func(a2dp_aptx_hd_encoder_cb.aptx_hd_encoder_state, 0);
} else {
- LOG_ERROR("%s: Cannot allocate aptX-HD encoder state", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Cannot allocate aptX-HD encoder state", __func__);
// TODO: Return an error?
}
@@ -218,10 +221,10 @@ bool A2dpCodecConfigAptxHd::updateEncoderUserConfig(
a2dp_aptx_hd_encoder_cb.timestamp = 0;
if (a2dp_aptx_hd_encoder_cb.peer_mtu == 0) {
- LOG_ERROR(
- "%s: Cannot update the codec encoder for %s: "
- "invalid peer MTU",
- __func__, name().c_str());
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot update the codec encoder for %s: "
+ "invalid peer MTU",
+ __func__, name().c_str());
return false;
}
@@ -243,10 +246,10 @@ static void a2dp_vendor_aptx_hd_encoder_update(
*p_restart_output = false;
*p_config_updated = false;
if (!a2dp_codec_config->copyOutOtaCodecConfig(codec_info)) {
- LOG_ERROR(
- "%s: Cannot update the codec encoder for %s: "
- "invalid codec config",
- __func__, a2dp_codec_config->name().c_str());
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot update the codec encoder for %s: "
+ "invalid codec config",
+ __func__, a2dp_codec_config->name().c_str());
return;
}
const uint8_t* p_codec_info = codec_info;
@@ -260,9 +263,9 @@ static void a2dp_vendor_aptx_hd_encoder_update(
a2dp_codec_config->getAudioBitsPerSample();
p_feeding_params->channel_count =
A2DP_VendorGetTrackChannelCountAptxHd(p_codec_info);
- LOG_INFO("%s: sample_rate=%u bits_per_sample=%u channel_count=%u", __func__,
- p_feeding_params->sample_rate, p_feeding_params->bits_per_sample,
- p_feeding_params->channel_count);
+ LOG_DEBUG(LOG_TAG, "%s: sample_rate=%u bits_per_sample=%u channel_count=%u",
+ __func__, p_feeding_params->sample_rate,
+ p_feeding_params->bits_per_sample, p_feeding_params->channel_count);
a2dp_vendor_aptx_hd_feeding_reset();
}
@@ -285,8 +288,8 @@ static void aptx_hd_init_framing_params(
framing_params->sleep_time_ns = 9000000;
- LOG_INFO("%s: sleep_time_ns = %" PRIu64, __func__,
- framing_params->sleep_time_ns);
+ LOG_DEBUG(LOG_TAG, "%s: sleep_time_ns = %" PRIu64, __func__,
+ framing_params->sleep_time_ns);
}
//
@@ -335,7 +338,8 @@ static void aptx_hd_update_framing_params(
framing_params->frame_size_counter = 0;
}
- LOG_VERBOSE("%s: sleep_time_ns = %" PRIu64
+ LOG_VERBOSE(LOG_TAG,
+ "%s: sleep_time_ns = %" PRIu64
" aptx_hd_bytes = %u "
"pcm_bytes_per_read = %u pcm_reads = %u frame_size_counter = %u",
__func__, framing_params->sleep_time_ns,
@@ -386,13 +390,15 @@ void a2dp_vendor_aptx_hd_send_frames(uint64_t timestamp_us) {
a2dp_aptx_hd_encoder_cb.stats.media_read_total_expected_read_bytes +=
expected_read_bytes;
- LOG_VERBOSE("%s: PCM read of size %u", __func__, expected_read_bytes);
+ LOG_VERBOSE(LOG_TAG, "%s: PCM read of size %u", __func__,
+ expected_read_bytes);
bytes_read = a2dp_aptx_hd_encoder_cb.read_callback((uint8_t*)read_buffer32,
expected_read_bytes);
a2dp_aptx_hd_encoder_cb.stats.media_read_total_actual_read_bytes +=
bytes_read;
if (bytes_read < expected_read_bytes) {
- LOG_WARN("%s: underflow at PCM reading: read %u bytes instead of %u",
+ LOG_WARN(LOG_TAG,
+ "%s: underflow at PCM reading: read %u bytes instead of %u",
__func__, bytes_read, expected_read_bytes);
a2dp_aptx_hd_encoder_cb.stats.media_read_total_dropped_packets++;
osi_free(p_buf);
@@ -412,8 +418,8 @@ void a2dp_vendor_aptx_hd_send_frames(uint64_t timestamp_us) {
const int COMPRESSION_RATIO = 4;
size_t encoded_bytes = pcm_bytes_encoded / COMPRESSION_RATIO;
p_buf->len += encoded_bytes;
- LOG_VERBOSE("%s: encoded %zu PCM bytes to %zu", __func__, pcm_bytes_encoded,
- encoded_bytes);
+ LOG_VERBOSE(LOG_TAG, "%s: encoded %zu PCM bytes to %zu", __func__,
+ pcm_bytes_encoded, encoded_bytes);
// Update the RTP timestamp
*((uint32_t*)(p_buf + 1)) = a2dp_aptx_hd_encoder_cb.timestamp;
diff --git a/stack/a2dp/a2dp_vendor_ldac.cc b/stack/a2dp/a2dp_vendor_ldac.cc
index b9e5f5a21..0a1017cc7 100644
--- a/stack/a2dp/a2dp_vendor_ldac.cc
+++ b/stack/a2dp/a2dp_vendor_ldac.cc
@@ -280,15 +280,15 @@ static tA2DP_STATUS A2DP_CodecInfoMatchesCapabilityLdac(
/* parse configuration */
status = A2DP_ParseInfoLdac(&cfg_cie, p_codec_info, is_capability);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: parsing failed %d", __func__, status);
+ LOG_ERROR(LOG_TAG, "%s: parsing failed %d", __func__, status);
return status;
}
/* verify that each parameter is in range */
- LOG_VERBOSE("%s: FREQ peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: FREQ peer: 0x%x, capability 0x%x", __func__,
cfg_cie.sampleRate, p_cap->sampleRate);
- LOG_VERBOSE("%s: CH_MODE peer: 0x%x, capability 0x%x", __func__,
+ LOG_VERBOSE(LOG_TAG, "%s: CH_MODE peer: 0x%x, capability 0x%x", __func__,
cfg_cie.channelMode, p_cap->channelMode);
/* sampling frequency */
@@ -319,12 +319,14 @@ bool A2DP_VendorCodecTypeEqualsLdac(const uint8_t* p_codec_info_a,
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoLdac(&ldac_cie_a, p_codec_info_a, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
a2dp_status = A2DP_ParseInfoLdac(&ldac_cie_b, p_codec_info_b, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
@@ -340,12 +342,14 @@ bool A2DP_VendorCodecEqualsLdac(const uint8_t* p_codec_info_a,
tA2DP_STATUS a2dp_status =
A2DP_ParseInfoLdac(&ldac_cie_a, p_codec_info_a, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
a2dp_status = A2DP_ParseInfoLdac(&ldac_cie_b, p_codec_info_b, true);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return false;
}
@@ -389,7 +393,8 @@ int A2DP_VendorGetTrackSampleRateLdac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoLdac(&ldac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -417,7 +422,8 @@ int A2DP_VendorGetTrackBitsPerSampleLdac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoLdac(&ldac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -445,7 +451,8 @@ int A2DP_VendorGetTrackChannelCountLdac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoLdac(&ldac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -467,7 +474,8 @@ int A2DP_VendorGetSinkTrackChannelTypeLdac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoLdac(&ldac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -489,7 +497,8 @@ int A2DP_VendorGetChannelModeCodeLdac(const uint8_t* p_codec_info) {
// Check whether the codec info contains valid data
tA2DP_STATUS a2dp_status = A2DP_ParseInfoLdac(&ldac_cie, p_codec_info, false);
if (a2dp_status != A2DP_SUCCESS) {
- LOG_ERROR("%s: cannot decode codec information: %d", __func__, a2dp_status);
+ LOG_ERROR(LOG_TAG, "%s: cannot decode codec information: %d", __func__,
+ a2dp_status);
return -1;
}
@@ -703,7 +712,7 @@ bool A2dpCodecConfigLdacSource::init() {
// Load the encoder
if (!A2DP_VendorLoadEncoderLdac()) {
- LOG_ERROR("%s: cannot load the encoder", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot load the encoder", __func__);
return false;
}
@@ -971,8 +980,8 @@ bool A2dpCodecConfigLdacBase::setCodecConfig(const uint8_t* p_peer_codec_info,
tA2DP_STATUS status =
A2DP_ParseInfoLdac(&peer_info_cie, p_peer_codec_info, is_capability);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: can't parse peer's capabilities: error = %d", __func__,
- status);
+ LOG_ERROR(LOG_TAG, "%s: can't parse peer's capabilities: error = %d",
+ __func__, status);
goto fail;
}
@@ -1103,10 +1112,10 @@ bool A2dpCodecConfigLdacBase::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.sample_rate == BTAV_A2DP_CODEC_SAMPLE_RATE_NONE) {
- LOG_ERROR(
- "%s: cannot match sample frequency: local caps = 0x%x "
- "peer info = 0x%x",
- __func__, p_a2dp_ldac_caps->sampleRate, peer_info_cie.sampleRate);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match sample frequency: local caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, p_a2dp_ldac_caps->sampleRate, peer_info_cie.sampleRate);
goto fail;
}
@@ -1178,11 +1187,11 @@ bool A2dpCodecConfigLdacBase::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.bits_per_sample == BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE) {
- LOG_ERROR(
- "%s: cannot match bits per sample: default = 0x%x "
- "user preference = 0x%x",
- __func__, a2dp_ldac_default_config.bits_per_sample,
- codec_user_config_.bits_per_sample);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match bits per sample: default = 0x%x "
+ "user preference = 0x%x",
+ __func__, a2dp_ldac_default_config.bits_per_sample,
+ codec_user_config_.bits_per_sample);
goto fail;
}
@@ -1265,10 +1274,11 @@ bool A2dpCodecConfigLdacBase::setCodecConfig(const uint8_t* p_peer_codec_info,
}
} while (false);
if (codec_config_.channel_mode == BTAV_A2DP_CODEC_CHANNEL_MODE_NONE) {
- LOG_ERROR(
- "%s: cannot match channel mode: local caps = 0x%x "
- "peer info = 0x%x",
- __func__, p_a2dp_ldac_caps->channelMode, peer_info_cie.channelMode);
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot match channel mode: local caps = 0x%x "
+ "peer info = 0x%x",
+ __func__, p_a2dp_ldac_caps->channelMode,
+ peer_info_cie.channelMode);
goto fail;
}
@@ -1338,8 +1348,8 @@ bool A2dpCodecConfigLdacBase::setPeerCodecCapabilities(
tA2DP_STATUS status =
A2DP_ParseInfoLdac(&peer_info_cie, p_peer_codec_capabilities, true);
if (status != A2DP_SUCCESS) {
- LOG_ERROR("%s: can't parse peer's capabilities: error = %d", __func__,
- status);
+ LOG_ERROR(LOG_TAG, "%s: can't parse peer's capabilities: error = %d",
+ __func__, status);
goto fail;
}
@@ -1415,7 +1425,7 @@ bool A2dpCodecConfigLdacSink::init() {
// Load the decoder
if (!A2DP_VendorLoadDecoderLdac()) {
- LOG_ERROR("%s: cannot load the decoder", __func__);
+ LOG_ERROR(LOG_TAG, "%s: cannot load the decoder", __func__);
return false;
}
diff --git a/stack/a2dp/a2dp_vendor_ldac_abr.cc b/stack/a2dp/a2dp_vendor_ldac_abr.cc
index 635c6eea0..7715af4d1 100644
--- a/stack/a2dp/a2dp_vendor_ldac_abr.cc
+++ b/stack/a2dp/a2dp_vendor_ldac_abr.cc
@@ -68,7 +68,7 @@ bool A2DP_VendorLoadLdacAbr(void) {
// Open the LDAC ABR library
ldac_abr_lib_handle = dlopen(LDAC_ABR_LIB_NAME, RTLD_NOW);
if (ldac_abr_lib_handle == NULL) {
- LOG_ERROR("%s: cannot open LDAC ABR library %s: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s: cannot open LDAC ABR library %s: %s", __func__,
LDAC_ABR_LIB_NAME, dlerror());
A2DP_VendorUnloadLdacAbr();
return false;
@@ -78,7 +78,8 @@ bool A2DP_VendorLoadLdacAbr(void) {
ldac_abr_get_handle_func = (tLDAC_ABR_GET_HANDLE)dlsym(
ldac_abr_lib_handle, LDAC_ABR_GET_HANDLE_NAME);
if (ldac_abr_get_handle_func == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the LDAC ABR library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the LDAC ABR library: %s",
__func__, LDAC_ABR_GET_HANDLE_NAME, dlerror());
A2DP_VendorUnloadLdacAbr();
return false;
@@ -87,7 +88,8 @@ bool A2DP_VendorLoadLdacAbr(void) {
ldac_abr_free_handle_func = (tLDAC_ABR_FREE_HANDLE)dlsym(
ldac_abr_lib_handle, LDAC_ABR_FREE_HANDLE_NAME);
if (ldac_abr_free_handle_func == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the LDAC ABR library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the LDAC ABR library: %s",
__func__, LDAC_ABR_FREE_HANDLE_NAME, dlerror());
A2DP_VendorUnloadLdacAbr();
return false;
@@ -96,7 +98,8 @@ bool A2DP_VendorLoadLdacAbr(void) {
ldac_abr_init_func =
(tLDAC_ABR_INIT)dlsym(ldac_abr_lib_handle, LDAC_ABR_INIT_NAME);
if (ldac_abr_init_func == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the LDAC ABR library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the LDAC ABR library: %s",
__func__, LDAC_ABR_INIT_NAME, dlerror());
A2DP_VendorUnloadLdacAbr();
return false;
@@ -105,7 +108,8 @@ bool A2DP_VendorLoadLdacAbr(void) {
ldac_abr_set_thresholds_func = (tLDAC_ABR_SET_THRESHOLDS)dlsym(
ldac_abr_lib_handle, LDAC_ABR_SET_THRESHOLDS_NAME);
if (ldac_abr_set_thresholds_func == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the LDAC ABR library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the LDAC ABR library: %s",
__func__, LDAC_ABR_SET_THRESHOLDS_NAME, dlerror());
A2DP_VendorUnloadLdacAbr();
return false;
@@ -114,7 +118,8 @@ bool A2DP_VendorLoadLdacAbr(void) {
ldac_abr_proc_func =
(tLDAC_ABR_PROC)dlsym(ldac_abr_lib_handle, LDAC_ABR_PROC_NAME);
if (ldac_abr_proc_func == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the LDAC ABR library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the LDAC ABR library: %s",
__func__, LDAC_ABR_PROC_NAME, dlerror());
A2DP_VendorUnloadLdacAbr();
return false;
diff --git a/stack/a2dp/a2dp_vendor_ldac_decoder.cc b/stack/a2dp/a2dp_vendor_ldac_decoder.cc
index e95ce9b41..feace36fe 100644
--- a/stack/a2dp/a2dp_vendor_ldac_decoder.cc
+++ b/stack/a2dp/a2dp_vendor_ldac_decoder.cc
@@ -111,7 +111,8 @@ static tA2DP_LDAC_DECODER_CB a2dp_ldac_decoder_cb;
static void* load_func(const char* func_name) {
void* func_ptr = dlsym(ldac_bco_lib_handle, func_name);
if (func_ptr == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the decoder library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the decoder library: %s",
__func__, func_name, dlerror());
A2DP_VendorUnloadDecoderLdac();
return NULL;
@@ -130,7 +131,7 @@ bool A2DP_VendorLoadDecoderLdac(void) {
// Open the decoder library
ldac_bco_lib_handle = dlopen(LDAC_BCO_LIB_NAME, RTLD_NOW);
if (ldac_bco_lib_handle == NULL) {
- LOG_ERROR("%s: cannot open LDAC decoder library %s: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s: cannot open LDAC decoder library %s: %s", __func__,
LDAC_BCO_LIB_NAME, dlerror());
return false;
}
@@ -203,20 +204,22 @@ void a2dp_vendor_ldac_decoder_cleanup(void) {
bool a2dp_vendor_ldac_decoder_decode_packet(BT_HDR* p_buf) {
if (p_buf == nullptr) {
- LOG_ERROR("%s Dropping packet with nullptr", __func__);
+ LOG(ERROR) << __func__ << "Dropping packet with nullptr";
return false;
}
- pthread_mutex_lock(&(a2dp_ldac_decoder_cb.mutex));
+
unsigned char* pBuffer =
reinterpret_cast<unsigned char*>(p_buf->data + p_buf->offset);
// unsigned int bufferSize = p_buf->len;
unsigned int bytesValid = p_buf->len;
+
if (bytesValid == 0) {
- pthread_mutex_unlock(&(a2dp_ldac_decoder_cb.mutex));
- LOG_WARN("%s Dropping packet with zero length", __func__);
+ LOG(WARNING) << __func__ << "Dropping packet with zero length";
return false;
}
+ pthread_mutex_lock(&(a2dp_ldac_decoder_cb.mutex));
+
LDACBT_SMPL_FMT_T fmt;
int bs_bytes, frame_number;
@@ -224,7 +227,8 @@ bool a2dp_vendor_ldac_decoder_decode_packet(BT_HDR* p_buf) {
frame_number = (int)pBuffer[0];
bs_bytes = (int)bytesValid;
bytesValid -= 1;
- LOG_INFO("%s:INPUT size : %d, frame : %d", __func__, bs_bytes, frame_number);
+ LOG_DEBUG(LOG_TAG, "%s:INPUT size : %d, frame : %d", __func__, bs_bytes,
+ frame_number);
if (a2dp_ldac_decoder_cb.has_ldac_handle)
ldac_BCO_decode_packet_func(a2dp_ldac_decoder_cb.ldac_handle_bco, pBuffer,
@@ -236,7 +240,7 @@ bool a2dp_vendor_ldac_decoder_decode_packet(BT_HDR* p_buf) {
void a2dp_vendor_ldac_decoder_start(void) {
pthread_mutex_lock(&(a2dp_ldac_decoder_cb.mutex));
- LOG_INFO("%s", __func__);
+ LOG_DEBUG(LOG_TAG, "%s", __func__);
if (a2dp_ldac_decoder_cb.has_ldac_handle)
ldac_BCO_start_func(a2dp_ldac_decoder_cb.ldac_handle_bco);
pthread_mutex_unlock(&(a2dp_ldac_decoder_cb.mutex));
@@ -244,7 +248,7 @@ void a2dp_vendor_ldac_decoder_start(void) {
void a2dp_vendor_ldac_decoder_suspend(void) {
pthread_mutex_lock(&(a2dp_ldac_decoder_cb.mutex));
- LOG_INFO("%s", __func__);
+ LOG_DEBUG(LOG_TAG, "%s", __func__);
if (a2dp_ldac_decoder_cb.has_ldac_handle)
ldac_BCO_suspend_func(a2dp_ldac_decoder_cb.ldac_handle_bco);
pthread_mutex_unlock(&(a2dp_ldac_decoder_cb.mutex));
@@ -256,7 +260,7 @@ void a2dp_vendor_ldac_decoder_configure(const uint8_t* p_codec_info) {
int32_t channel_mode;
if (p_codec_info == NULL) {
- LOG_ERROR("%s: p_codec_info is NULL", __func__);
+ LOG_ERROR(LOG_TAG, "%s: p_codec_info is NULL", __func__);
return;
}
@@ -265,8 +269,8 @@ void a2dp_vendor_ldac_decoder_configure(const uint8_t* p_codec_info) {
bits_per_sample = A2DP_VendorGetTrackBitsPerSampleLdac(p_codec_info);
channel_mode = A2DP_VendorGetChannelModeCodeLdac(p_codec_info);
- LOG_INFO("%s , sample_rate=%d, bits_per_sample=%d, channel_mode=%d", __func__,
- sample_rate, bits_per_sample, channel_mode);
+ LOG_DEBUG(LOG_TAG, "%s , sample_rate=%d, bits_per_sample=%d, channel_mode=%d",
+ __func__, sample_rate, bits_per_sample, channel_mode);
if (a2dp_ldac_decoder_cb.has_ldac_handle)
ldac_BCO_configure_func(a2dp_ldac_decoder_cb.ldac_handle_bco, sample_rate,
diff --git a/stack/a2dp/a2dp_vendor_ldac_encoder.cc b/stack/a2dp/a2dp_vendor_ldac_encoder.cc
index 62d2d9e43..ca6c2fc98 100644
--- a/stack/a2dp/a2dp_vendor_ldac_encoder.cc
+++ b/stack/a2dp/a2dp_vendor_ldac_encoder.cc
@@ -124,7 +124,7 @@ typedef struct {
} tA2DP_LDAC_ENCODER_PARAMS;
typedef struct {
- float counter;
+ uint32_t counter;
uint32_t bytes_per_tick; /* pcm bytes read each media task tick */
uint64_t last_frame_us;
} tA2DP_LDAC_FEEDING_STATE;
@@ -187,7 +187,8 @@ static std::string quality_mode_index_to_name(int quality_mode_index);
static void* load_func(const char* func_name) {
void* func_ptr = dlsym(ldac_encoder_lib_handle, func_name);
if (func_ptr == NULL) {
- LOG_ERROR("%s: cannot find function '%s' in the encoder library: %s",
+ LOG_ERROR(LOG_TAG,
+ "%s: cannot find function '%s' in the encoder library: %s",
__func__, func_name, dlerror());
A2DP_VendorUnloadEncoderLdac();
return NULL;
@@ -204,7 +205,7 @@ bool A2DP_VendorLoadEncoderLdac(void) {
// Open the encoder library
ldac_encoder_lib_handle = dlopen(LDAC_ENCODER_LIB_NAME, RTLD_NOW);
if (ldac_encoder_lib_handle == NULL) {
- LOG_ERROR("%s: cannot open LDAC encoder library %s: %s", __func__,
+ LOG_ERROR(LOG_TAG, "%s: cannot open LDAC encoder library %s: %s", __func__,
LDAC_ENCODER_LIB_NAME, dlerror());
return false;
}
@@ -241,7 +242,7 @@ bool A2DP_VendorLoadEncoderLdac(void) {
if (ldac_get_error_code_func == NULL) return false;
if (!A2DP_VendorLoadLdacAbr()) {
- LOG_WARN("%s: cannot load the LDAC ABR library", __func__);
+ LOG_WARN(LOG_TAG, "%s: cannot load the LDAC ABR library", __func__);
ldac_abr_loaded = false;
} else {
ldac_abr_loaded = true;
@@ -323,10 +324,10 @@ bool A2dpCodecConfigLdacSource::updateEncoderUserConfig(
a2dp_ldac_encoder_cb.timestamp = 0;
if (a2dp_ldac_encoder_cb.peer_mtu == 0) {
- LOG_ERROR(
- "%s: Cannot update the codec encoder for %s: "
- "invalid peer MTU",
- __func__, name().c_str());
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot update the codec encoder for %s: "
+ "invalid peer MTU",
+ __func__, name().c_str());
return false;
}
@@ -355,7 +356,7 @@ static void a2dp_vendor_ldac_encoder_update(uint16_t peer_mtu,
if (!a2dp_ldac_encoder_cb.has_ldac_handle) {
a2dp_ldac_encoder_cb.ldac_handle = ldac_get_handle_func();
if (a2dp_ldac_encoder_cb.ldac_handle == NULL) {
- LOG_ERROR("%s: Cannot get LDAC encoder handle", __func__);
+ LOG_ERROR(LOG_TAG, "%s: Cannot get LDAC encoder handle", __func__);
return; // TODO: Return an error?
}
a2dp_ldac_encoder_cb.has_ldac_handle = true;
@@ -363,10 +364,10 @@ static void a2dp_vendor_ldac_encoder_update(uint16_t peer_mtu,
CHECK(a2dp_ldac_encoder_cb.ldac_handle != nullptr);
if (!a2dp_codec_config->copyOutOtaCodecConfig(codec_info)) {
- LOG_ERROR(
- "%s: Cannot update the codec encoder for %s: "
- "invalid codec config",
- __func__, a2dp_codec_config->name().c_str());
+ LOG_ERROR(LOG_TAG,
+ "%s: Cannot update the codec encoder for %s: "
+ "invalid codec config",
+ __func__, a2dp_codec_config->name().c_str());
return;
}
const uint8_t* p_codec_info = codec_info;
@@ -380,9 +381,9 @@ static void a2dp_vendor_ldac_encoder_update(uint16_t peer_mtu,
a2dp_codec_config->getAudioBitsPerSample();
p_feeding_params->channel_count =
A2DP_VendorGetTrackChannelCountLdac(p_codec_info);
- LOG_INFO("%s: sample_rate=%u bits_per_sample=%u channel_count=%u", __func__,
- p_feeding_params->sample_rate, p_feeding_params->bits_per_sample,
- p_feeding_params->channel_count);
+ LOG_DEBUG(LOG_TAG, "%s: sample_rate=%u bits_per_sample=%u channel_count=%u",
+ __func__, p_feeding_params->sample_rate,
+ p_feeding_params->bits_per_sample, p_feeding_params->channel_count);
a2dp_vendor_ldac_feeding_reset();
// The codec parameters
@@ -403,14 +404,14 @@ static void a2dp_vendor_ldac_encoder_update(uint16_t peer_mtu,
int old_quality_mode_index = p_encoder_params->quality_mode_index;
if (codec_config.codec_specific_1 != 0) {
p_encoder_params->quality_mode_index = codec_config.codec_specific_1 % 10;
- LOG_INFO("%s: setting quality mode to %s", __func__,
- quality_mode_index_to_name(p_encoder_params->quality_mode_index)
- .c_str());
+ LOG_DEBUG(LOG_TAG, "%s: setting quality mode to %s", __func__,
+ quality_mode_index_to_name(p_encoder_params->quality_mode_index)
+ .c_str());
} else {
p_encoder_params->quality_mode_index = A2DP_LDAC_QUALITY_ABR;
- LOG_INFO("%s: setting quality mode to default %s", __func__,
- quality_mode_index_to_name(p_encoder_params->quality_mode_index)
- .c_str());
+ LOG_DEBUG(LOG_TAG, "%s: setting quality mode to default %s", __func__,
+ quality_mode_index_to_name(p_encoder_params->quality_mode_index)
+ .c_str());
}
int ldac_eqmid = LDAC_ABR_MODE_EQMID;
@@ -418,20 +419,21 @@ static void a2dp_vendor_ldac_encoder_update(uint16_t peer_mtu,
if (!ldac_abr_loaded) {
p_encoder_params->quality_mode_index = A2DP_LDAC_QUALITY_MID;
LOG_WARN(
-
+ LOG_TAG,
"%s: LDAC ABR library is not loaded, resetting quality mode to %s",
__func__,
quality_mode_index_to_name(p_encoder_params->quality_mode_index)
.c_str());
} else {
- LOG_INFO("%s: changing mode from %s to %s", __func__,
- quality_mode_index_to_name(old_quality_mode_index).c_str(),
- quality_mode_index_to_name(p_encoder_params->quality_mode_index)
- .c_str());
+ LOG_DEBUG(LOG_TAG, "%s: changing mode from %s to %s", __func__,
+ quality_mode_index_to_name(old_quality_mode_index).c_str(),
+ quality_mode_index_to_name(p_encoder_params->quality_mode_index)
+ .c_str());
if (a2dp_ldac_encoder_cb.ldac_abr_handle != NULL) {
- LOG_INFO("%s: already in LDAC ABR mode, do nothing.", __func__);
+ LOG_DEBUG(LOG_TAG, "%s: already in LDAC ABR mode, do nothing.",
+ __func__);
} else {
- LOG_INFO("%s: get and init LDAC ABR handle.", __func__);
+ LOG_DEBUG(LOG_TAG, "%s: get and init LDAC ABR handle.", __func__);
a2dp_ldac_encoder_cb.ldac_abr_handle = a2dp_ldac_abr_get_handle();
if (a2dp_ldac_encoder_cb.ldac_abr_handle != NULL) {
a2dp_ldac_encoder_cb.has_ldac_abr_handle = true;
@@ -441,8 +443,8 @@ static void a2dp_vendor_ldac_encoder_update(uint16_t peer_mtu,
A2DP_LDAC_ENCODER_INTERVAL_MS);
} else {
p_encoder_params->quality_mode_index = A2DP_LDAC_QUALITY_MID;
- LOG_INFO(
-
+ LOG_DEBUG(
+ LOG_TAG,
"%s: get LDAC ABR handle failed, resetting quality mode to %s.",
__func__,
quality_mode_index_to_name(p_encoder_params->quality_mode_index)
@@ -452,8 +454,8 @@ static void a2dp_vendor_ldac_encoder_update(uint16_t peer_mtu,
}
} else {
ldac_eqmid = p_encoder_params->quality_mode_index;
- LOG_INFO("%s: in %s mode, free LDAC ABR handle.", __func__,
- quality_mode_index_to_name(ldac_eqmid).c_str());
+ LOG_DEBUG(LOG_TAG, "%s: in %s mode, free LDAC ABR handle.", __func__,
+ quality_mode_index_to_name(ldac_eqmid).c_str());
if (a2dp_ldac_encoder_cb.has_ldac_abr_handle) {
a2dp_ldac_abr_free_handle(a2dp_ldac_encoder_cb.ldac_abr_handle);
a2dp_ldac_encoder_cb.ldac_abr_handle = NULL;
@@ -477,14 +479,15 @@ static void a2dp_vendor_ldac_encoder_update(uint16_t peer_mtu,
else if (p_encoder_params->pcm_wlength == 4)
p_encoder_params->pcm_fmt = LDACBT_SMPL_FMT_S32;
- LOG_INFO("%s: MTU=%d, peer_mtu=%d", __func__,
- a2dp_ldac_encoder_cb.TxAaMtuSize, peer_mtu);
- LOG_INFO(
- "%s: sample_rate: %d channel_mode: %d "
- "quality_mode_index: %d pcm_wlength: %d pcm_fmt: %d",
- __func__, p_encoder_params->sample_rate, p_encoder_params->channel_mode,
- p_encoder_params->quality_mode_index, p_encoder_params->pcm_wlength,
- p_encoder_params->pcm_fmt);
+ LOG_DEBUG(LOG_TAG, "%s: MTU=%d, peer_mtu=%d", __func__,
+ a2dp_ldac_encoder_cb.TxAaMtuSize, peer_mtu);
+ LOG_DEBUG(LOG_TAG,
+ "%s: sample_rate: %d channel_mode: %d "
+ "quality_mode_index: %d pcm_wlength: %d pcm_fmt: %d",
+ __func__, p_encoder_params->sample_rate,
+ p_encoder_params->channel_mode,
+ p_encoder_params->quality_mode_index, p_encoder_params->pcm_wlength,
+ p_encoder_params->pcm_fmt);
// Initialize the encoder.
// NOTE: MTU in the initialization must include the AVDT media header size.
@@ -495,11 +498,12 @@ static void a2dp_vendor_ldac_encoder_update(uint16_t peer_mtu,
p_encoder_params->sample_rate);
if (result != 0) {
int err_code = ldac_get_error_code_func(a2dp_ldac_encoder_cb.ldac_handle);
- LOG_ERROR(
- "%s: error initializing the LDAC encoder: %d api_error = %d "
- "handle_error = %d block_error = %d error_code = 0x%x",
- __func__, result, LDACBT_API_ERR(err_code), LDACBT_HANDLE_ERR(err_code),
- LDACBT_BLOCK_ERR(err_code), err_code);
+ LOG_ERROR(LOG_TAG,
+ "%s: error initializing the LDAC encoder: %d api_error = %d "
+ "handle_error = %d block_error = %d error_code = 0x%x",
+ __func__, result, LDACBT_API_ERR(err_code),
+ LDACBT_HANDLE_ERR(err_code), LDACBT_BLOCK_ERR(err_code),
+ err_code);
}
}
@@ -523,12 +527,12 @@ void a2dp_vendor_ldac_feeding_reset(void) {
A2DP_LDAC_ENCODER_INTERVAL_MS) /
1000;
- LOG_INFO("%s: PCM bytes per tick %u", __func__,
- a2dp_ldac_encoder_cb.ldac_feeding_state.bytes_per_tick);
+ LOG_DEBUG(LOG_TAG, "%s: PCM bytes per tick %u", __func__,
+ a2dp_ldac_encoder_cb.ldac_feeding_state.bytes_per_tick);
}
void a2dp_vendor_ldac_feeding_flush(void) {
- a2dp_ldac_encoder_cb.ldac_feeding_state.counter = 0.0f;
+ a2dp_ldac_encoder_cb.ldac_feeding_state.counter = 0;
}
uint64_t a2dp_vendor_ldac_get_encoder_interval_ms(void) {
@@ -540,8 +544,8 @@ void a2dp_vendor_ldac_send_frames(uint64_t timestamp_us) {
uint8_t nb_iterations = 0;
a2dp_ldac_get_num_frame_iteration(&nb_iterations, &nb_frame, timestamp_us);
- LOG_VERBOSE("%s: Sending %d frames per iteration, %d iterations", __func__,
- nb_frame, nb_iterations);
+ LOG_VERBOSE(LOG_TAG, "%s: Sending %d frames per iteration, %d iterations",
+ __func__, nb_frame, nb_iterations);
if (nb_frame == 0) return;
for (uint8_t counter = 0; counter < nb_iterations; counter++) {
@@ -577,7 +581,8 @@ static void a2dp_ldac_get_num_frame_iteration(uint8_t* num_of_iterations,
A2DP_LDAC_MEDIA_BYTES_PER_FRAME *
a2dp_ldac_encoder_cb.feeding_params.channel_count *
a2dp_ldac_encoder_cb.feeding_params.bits_per_sample / 8;
- LOG_VERBOSE("%s: pcm_bytes_per_frame %u", __func__, pcm_bytes_per_frame);
+ LOG_VERBOSE(LOG_TAG, "%s: pcm_bytes_per_frame %u", __func__,
+ pcm_bytes_per_frame);
uint32_t us_this_tick = A2DP_LDAC_ENCODER_INTERVAL_MS * 1000;
uint64_t now_us = timestamp_us;
@@ -587,7 +592,7 @@ static void a2dp_ldac_get_num_frame_iteration(uint8_t* num_of_iterations,
a2dp_ldac_encoder_cb.ldac_feeding_state.last_frame_us = now_us;
a2dp_ldac_encoder_cb.ldac_feeding_state.counter +=
- (float)a2dp_ldac_encoder_cb.ldac_feeding_state.bytes_per_tick * us_this_tick /
+ a2dp_ldac_encoder_cb.ldac_feeding_state.bytes_per_tick * us_this_tick /
(A2DP_LDAC_ENCODER_INTERVAL_MS * 1000);
result =
@@ -596,8 +601,8 @@ static void a2dp_ldac_get_num_frame_iteration(uint8_t* num_of_iterations,
result * pcm_bytes_per_frame;
nof = result;
- LOG_VERBOSE("%s: effective num of frames %u, iterations %u", __func__, nof,
- noi);
+ LOG_VERBOSE(LOG_TAG, "%s: effective num of frames %u, iterations %u",
+ __func__, nof, noi);
*num_of_frames = nof;
*num_of_iterations = noi;
@@ -649,7 +654,7 @@ static void a2dp_ldac_encode_frames(uint8_t nb_frame) {
bytes_read += temp_bytes_read;
uint8_t* packet = (uint8_t*)(p_buf + 1) + p_buf->offset + p_buf->len;
if (a2dp_ldac_encoder_cb.ldac_handle == NULL) {
- LOG_ERROR("%s: invalid LDAC handle", __func__);
+ LOG_ERROR(LOG_TAG, "%s: invalid LDAC handle", __func__);
a2dp_ldac_encoder_cb.stats.media_read_total_dropped_packets++;
osi_free(p_buf);
return;
@@ -660,12 +665,12 @@ static void a2dp_ldac_encode_frames(uint8_t nb_frame) {
if (result != 0) {
int err_code =
ldac_get_error_code_func(a2dp_ldac_encoder_cb.ldac_handle);
- LOG_ERROR(
- "%s: LDAC encoding error: %d api_error = %d "
- "handle_error = %d block_error = %d error_code = 0x%x",
- __func__, result, LDACBT_API_ERR(err_code),
- LDACBT_HANDLE_ERR(err_code), LDACBT_BLOCK_ERR(err_code),
- err_code);
+ LOG_ERROR(LOG_TAG,
+ "%s: LDAC encoding error: %d api_error = %d "
+ "handle_error = %d block_error = %d error_code = 0x%x",
+ __func__, result, LDACBT_API_ERR(err_code),
+ LDACBT_HANDLE_ERR(err_code), LDACBT_BLOCK_ERR(err_code),
+ err_code);
a2dp_ldac_encoder_cb.stats.media_read_total_dropped_packets++;
osi_free(p_buf);
return;
@@ -675,7 +680,7 @@ static void a2dp_ldac_encode_frames(uint8_t nb_frame) {
nb_frame--;
p_buf->layer_specific += out_frames; // added a frame to the buffer
} else {
- LOG_WARN("%s: underflow %d", __func__, nb_frame);
+ LOG_WARN(LOG_TAG, "%s: underflow %d", __func__, nb_frame);
a2dp_ldac_encoder_cb.ldac_feeding_state.counter +=
nb_frame * LDACBT_ENC_LSU *
a2dp_ldac_encoder_cb.feeding_params.channel_count *
diff --git a/stack/acl/acl.cc b/stack/acl/acl.cc
deleted file mode 100644
index 6613a6464..000000000
--- a/stack/acl/acl.cc
+++ /dev/null
@@ -1,72 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <unordered_set>
-
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "stack/acl/acl.h"
-#include "types/raw_address.h"
-
-void tACL_CONN::Reset() {
- memset(peer_le_features, 0, sizeof(peer_le_features));
- peer_le_features_valid = false;
- memset(peer_lmp_feature_pages, 0, sizeof(peer_lmp_feature_pages));
- memset(peer_lmp_feature_valid, 0, sizeof(peer_lmp_feature_valid));
- active_remote_addr = RawAddress::kEmpty;
- conn_addr = RawAddress::kEmpty;
- remote_addr = RawAddress::kEmpty;
- link_up_issued = false;
- transport = BT_TRANSPORT_INVALID;
- flush_timeout_in_ticks = 0;
- hci_handle = 0;
- link_super_tout = 0;
- pkt_types_mask = 0;
- active_remote_addr_type = BLE_ADDR_PUBLIC;
- conn_addr_type = BLE_ADDR_PUBLIC;
- disconnect_reason = 0;
- encrypt_state_ = BTM_ACL_ENCRYPT_STATE_IDLE;
- is_encrypted = false;
- link_role = HCI_ROLE_CENTRAL;
- switch_role_failed_attempts = 0;
- memset(&remote_version_info, 0, sizeof(remote_version_info));
- rs_disc_pending = BTM_SEC_RS_NOT_PENDING;
- switch_role_state_ = BTM_ACL_SWKEY_STATE_IDLE;
- sca = 0;
-}
-
-// When the local device initiates an le ACL disconnect the address
-// should not be re-added to the acceptlist.
-void tACL_CB::AddToIgnoreAutoConnectAfterDisconnect(const RawAddress& bd_addr) {
- if (!ignore_auto_connect_after_disconnect_set_.insert(bd_addr).second) {
- LOG_WARN(
- "Unexpectedly found device address already in ignore auto connect "
- "device:%s",
- PRIVATE_ADDRESS(bd_addr));
- }
-}
-
-// A check and clear mechanism used to determine if the address should be
-// re-added to the acceptlist after an le ACL disconnect is received from a
-// peer.
-bool tACL_CB::CheckAndClearIgnoreAutoConnectAfterDisconnect(
- const RawAddress& bd_addr) {
- return (ignore_auto_connect_after_disconnect_set_.erase(bd_addr) > 0);
-}
-
-void tACL_CB::ClearAllIgnoreAutoConnectAfterDisconnect() {
- ignore_auto_connect_after_disconnect_set_.clear();
-}
diff --git a/stack/acl/acl.h b/stack/acl/acl.h
deleted file mode 100644
index 8b62881c7..000000000
--- a/stack/acl/acl.h
+++ /dev/null
@@ -1,423 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include <string>
-#include <unordered_set>
-#include <vector>
-
-#include "stack/include/acl_api_types.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/hcidefs.h"
-#include "stack/include/hcimsgs.h"
-#include "types/bt_transport.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
-
-enum btm_acl_encrypt_state_t {
- BTM_ACL_ENCRYPT_STATE_IDLE = 0,
- BTM_ACL_ENCRYPT_STATE_ENCRYPT_OFF = 1,
- BTM_ACL_ENCRYPT_STATE_TEMP_FUNC = 2,
- BTM_ACL_ENCRYPT_STATE_ENCRYPT_ON = 3,
-};
-
-enum btm_acl_swkey_state_t {
- BTM_ACL_SWKEY_STATE_IDLE = 0,
- BTM_ACL_SWKEY_STATE_MODE_CHANGE = 1,
- BTM_ACL_SWKEY_STATE_ENCRYPTION_OFF = 2,
- BTM_ACL_SWKEY_STATE_SWITCHING = 3,
- BTM_ACL_SWKEY_STATE_ENCRYPTION_ON = 4,
- BTM_ACL_SWKEY_STATE_IN_PROGRESS = 5,
-};
-
-/* Policy settings status */
-typedef enum : uint16_t {
- HCI_DISABLE_ALL_LM_MODES = 0,
- HCI_ENABLE_CENTRAL_PERIPHERAL_SWITCH = (1u << 0),
- HCI_ENABLE_HOLD_MODE = (1u << 1),
- HCI_ENABLE_SNIFF_MODE = (1u << 2),
- HCI_ENABLE_PARK_MODE = (1u << 3),
-} tLINK_POLICY_BITMASK;
-typedef uint16_t tLINK_POLICY;
-
-constexpr tLINK_POLICY kAllLinkPoliciesEnabled =
- (HCI_ENABLE_CENTRAL_PERIPHERAL_SWITCH | HCI_ENABLE_HOLD_MODE |
- HCI_ENABLE_SNIFF_MODE);
-
-static const char* link_policy_string[] = {
- " role_switch ",
- " hold_mode ",
- " sniff_mode ",
- " park_mode ",
-};
-
-inline std::string link_policy_text(tLINK_POLICY policy) {
- std::ostringstream os;
- os << "0x" << loghex(static_cast<uint16_t>(policy)) << " :";
- std::string s = os.str();
- for (uint16_t i = 0; i < 4; i++) {
- if (policy & (0x1 << i)) s += link_policy_string[i];
- }
- return s;
-}
-
-// Power mode states.
-// Used as both value and bitmask
-enum : uint8_t {
- BTM_PM_ST_ACTIVE = HCI_MODE_ACTIVE, // 0x00
- BTM_PM_ST_HOLD = HCI_MODE_HOLD, // 0x01
- BTM_PM_ST_SNIFF = HCI_MODE_SNIFF, // 0x02
- BTM_PM_ST_PARK = HCI_MODE_PARK, // 0x03
- BTM_PM_ST_UNUSED, // 0x04
- BTM_PM_ST_PENDING = BTM_PM_STS_PENDING, // 0x05
- BTM_PM_ST_INVALID = 0x7F,
- BTM_PM_STORED_MASK = 0x80, /* set this mask if the command is stored */
-};
-typedef uint8_t tBTM_PM_STATE;
-
-inline std::string power_mode_state_text(tBTM_PM_STATE state) {
- std::string s =
- std::string((state & BTM_PM_STORED_MASK) ? "stored:" : "immediate:");
- switch (state & ~BTM_PM_STORED_MASK) {
- case BTM_PM_ST_ACTIVE:
- return s + std::string("active");
- case BTM_PM_ST_HOLD:
- return s + std::string("hold");
- case BTM_PM_ST_SNIFF:
- return s + std::string("sniff");
- case BTM_PM_ST_PARK:
- return s + std::string("park");
- case BTM_PM_ST_UNUSED:
- return s + std::string("WARN:UNUSED");
- case BTM_PM_ST_PENDING:
- return s + std::string("pending");
- case BTM_PM_ST_INVALID:
- return s + std::string("invalid");
- default:
- return s + std::string("UNKNOWN");
- }
-}
-
-namespace bluetooth {
-namespace shim {
-tBTM_STATUS BTM_SetPowerMode(uint16_t handle, const tBTM_PM_PWR_MD& new_mode);
-tBTM_STATUS BTM_SetSsrParams(uint16_t handle, uint16_t max_lat,
- uint16_t min_rmt_to, uint16_t min_loc_to);
-void btm_pm_on_mode_change(tHCI_STATUS status, uint16_t handle,
- tHCI_MODE hci_mode, uint16_t interval);
-void btm_pm_on_sniff_subrating(tHCI_STATUS status, uint16_t handle,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout);
-} // namespace shim
-} // namespace bluetooth
-
-typedef struct {
- uint16_t max_xmit_latency;
- uint16_t max_recv_latency;
- uint16_t min_remote_timeout;
- uint16_t min_local_timeout;
-} tSSR_PARAMS;
-
-#define BTM_PM_REC_NOT_USED 0
-typedef struct {
- tBTM_PM_STATUS_CBACK* cback =
- nullptr; /* to notify the registered party of mode change event */
- uint8_t mask = 0; /* registered request mask. 0, if this entry is not used */
-} tBTM_PM_RCB;
-
-/* Structure returned with Role Switch information (in tBTM_CMPL_CB callback
- * function) in response to BTM_SwitchRoleToCentral call.
- */
-typedef struct {
- RawAddress remote_bd_addr; /* Remote BD addr involved with the switch */
- tHCI_STATUS hci_status; /* HCI status returned with the event */
- tHCI_ROLE role; /* HCI_ROLE_CENTRAL or HCI_ROLE_PERIPHERAL */
-} tBTM_ROLE_SWITCH_CMPL;
-
-struct tBTM_PM_MCB {
- bool chg_ind = false;
- tBTM_PM_PWR_MD req_mode;
- tBTM_PM_PWR_MD set_mode;
- tBTM_PM_STATE state = BTM_PM_ST_ACTIVE; // 0
- uint16_t interval = 0;
- uint16_t max_lat = 0;
- uint16_t min_loc_to = 0;
- uint16_t min_rmt_to = 0;
- void Init(RawAddress bda, uint16_t handle) {
- bda_ = bda;
- handle_ = handle;
- }
- RawAddress bda_;
- uint16_t handle_;
-};
-
-struct tACL_CONN {
- BD_FEATURES peer_le_features;
- bool peer_le_features_valid;
- BD_FEATURES peer_lmp_feature_pages[HCI_EXT_FEATURES_PAGE_MAX + 1];
- bool peer_lmp_feature_valid[HCI_EXT_FEATURES_PAGE_MAX + 1];
-
- RawAddress active_remote_addr;
- RawAddress conn_addr;
- RawAddress remote_addr;
- bool in_use{false};
-
- public:
- bool InUse() const { return in_use; }
- const RawAddress RemoteAddress() const { return remote_addr; }
-
- bool link_up_issued;
- tBT_TRANSPORT transport;
- bool is_transport_br_edr() const { return transport == BT_TRANSPORT_BR_EDR; }
- bool is_transport_ble() const { return transport == BT_TRANSPORT_LE; }
- bool is_transport_valid() const {
- return is_transport_ble() || is_transport_br_edr();
- }
-
- uint16_t flush_timeout_in_ticks;
- uint16_t hci_handle;
- tLINK_POLICY link_policy;
-
- public:
- uint16_t Handle() const { return hci_handle; }
- uint16_t link_super_tout;
- uint16_t pkt_types_mask;
- tBLE_ADDR_TYPE active_remote_addr_type;
- tBLE_ADDR_TYPE conn_addr_type;
- uint8_t disconnect_reason;
-
- private:
- btm_acl_encrypt_state_t encrypt_state_;
-
- public:
- void set_encryption_off() {
- if (encrypt_state_ != BTM_ACL_ENCRYPT_STATE_ENCRYPT_OFF) {
- btsnd_hcic_set_conn_encrypt(hci_handle, false);
- encrypt_state_ = BTM_ACL_ENCRYPT_STATE_ENCRYPT_OFF;
- }
- }
- void set_encryption_on() {
- if (encrypt_state_ != BTM_ACL_ENCRYPT_STATE_ENCRYPT_ON) {
- btsnd_hcic_set_conn_encrypt(hci_handle, true);
- encrypt_state_ = BTM_ACL_ENCRYPT_STATE_ENCRYPT_ON;
- }
- }
- void set_encryption_idle() { encrypt_state_ = BTM_ACL_ENCRYPT_STATE_IDLE; }
-
- void set_encryption_switching() {
- encrypt_state_ = BTM_ACL_ENCRYPT_STATE_TEMP_FUNC;
- }
-
- public:
- bool is_encrypted = false;
- tHCI_ROLE link_role;
- uint8_t switch_role_failed_attempts;
-
- tREMOTE_VERSION_INFO remote_version_info;
-
-#define BTM_SEC_RS_NOT_PENDING 0 /* Role Switch not in progress */
-#define BTM_SEC_RS_PENDING 1 /* Role Switch in progress */
-#define BTM_SEC_DISC_PENDING 2 /* Disconnect is pending */
- private:
- uint8_t rs_disc_pending = BTM_SEC_RS_NOT_PENDING;
- friend struct StackAclBtmAcl;
- friend tBTM_STATUS btm_remove_acl(const RawAddress& bd_addr,
- tBT_TRANSPORT transport);
- friend void acl_disconnect_after_role_switch(uint16_t conn_handle,
- tHCI_STATUS reason);
- friend void bluetooth::shim::btm_pm_on_mode_change(tHCI_STATUS status,
- uint16_t handle,
- tHCI_MODE hci_mode,
- uint16_t interval);
- friend void btm_acl_encrypt_change(uint16_t handle, uint8_t status,
- uint8_t encr_enable);
-
- public:
- bool is_disconnect_pending() const {
- return rs_disc_pending == BTM_SEC_DISC_PENDING;
- }
- bool is_role_switch_pending() const {
- return rs_disc_pending == BTM_SEC_RS_PENDING;
- }
-
- private:
- uint8_t switch_role_state_;
-
- public:
- void reset_switch_role() { switch_role_state_ = BTM_ACL_SWKEY_STATE_IDLE; }
- void set_switch_role_changing() {
- switch_role_state_ = BTM_ACL_SWKEY_STATE_MODE_CHANGE;
- }
- void set_switch_role_encryption_off() {
- switch_role_state_ = BTM_ACL_SWKEY_STATE_ENCRYPTION_OFF;
- }
- void set_switch_role_encryption_on() {
- switch_role_state_ = BTM_ACL_SWKEY_STATE_ENCRYPTION_ON;
- }
- void set_switch_role_in_progress() {
- switch_role_state_ = BTM_ACL_SWKEY_STATE_IN_PROGRESS;
- }
- void set_switch_role_switching() {
- switch_role_state_ = BTM_ACL_SWKEY_STATE_SWITCHING;
- }
-
- bool is_switch_role_idle() const {
- return switch_role_state_ == BTM_ACL_SWKEY_STATE_IDLE;
- }
- bool is_switch_role_encryption_off() const {
- return switch_role_state_ == BTM_ACL_SWKEY_STATE_ENCRYPTION_OFF;
- }
- bool is_switch_role_encryption_on() const {
- return switch_role_state_ == BTM_ACL_SWKEY_STATE_ENCRYPTION_ON;
- }
- bool is_switch_role_switching() const {
- return switch_role_state_ == BTM_ACL_SWKEY_STATE_SWITCHING;
- }
- bool is_switch_role_in_progress() const {
- return switch_role_state_ == BTM_ACL_SWKEY_STATE_IN_PROGRESS;
- }
- bool is_switch_role_mode_change() const {
- return switch_role_state_ == BTM_ACL_SWKEY_STATE_MODE_CHANGE;
- }
- bool is_switch_role_switching_or_in_progress() const {
- return is_switch_role_switching() || is_switch_role_in_progress();
- }
-
- friend void DumpsysL2cap(int fd);
-
- public:
- uint8_t sca; /* Sleep clock accuracy */
-
- void Reset();
-
- struct tPolicy {
- tBTM_PM_MODE Mode() const { return this->mode.mode_; }
- struct {
- bool IsPending() const { return pending_ != BTM_PM_MD_UNKNOWN; }
- tBTM_PM_MODE Pending() const { return pending_; }
- uint16_t Interval() const { return interval_; }
-
- private:
- tBTM_PM_MODE mode_{BTM_PM_MD_ACTIVE};
- tBTM_PM_MODE pending_{BTM_PM_MD_UNKNOWN};
- uint16_t interval_{0};
- friend tBTM_STATUS bluetooth::shim::BTM_SetPowerMode(
- uint16_t, const tBTM_PM_PWR_MD& new_mode);
- friend void bluetooth::shim::btm_pm_on_mode_change(tHCI_STATUS status,
- uint16_t handle,
- tHCI_MODE hci_mode,
- uint16_t interval);
- friend void tACL_CONN::Reset();
- friend tBTM_PM_MODE tACL_CONN::tPolicy::Mode() const;
- } mode;
-
- hci_role_t Role() const { return this->role.role_; }
- struct {
- unsigned RoleSwitchFailedCount() const { return role_switch_failed_cnt_; }
-
- private:
- hci_role_t role_{HCI_ROLE_CENTRAL};
- unsigned role_switch_failed_cnt_{0};
- friend void tACL_CONN::Reset();
- friend hci_role_t tACL_CONN::tPolicy::Role() const;
- } role;
-
- struct {
- bool IsPending() const { return pending_; }
-
- private:
- bool pending_{false};
- friend tBTM_STATUS bluetooth::shim::BTM_SetSsrParams(uint16_t handle,
- uint16_t max_lat,
- uint16_t min_rmt_to,
- uint16_t min_loc_to);
- friend void bluetooth::shim::btm_pm_on_sniff_subrating(
- tHCI_STATUS status, uint16_t handle,
- uint16_t maximum_transmit_latency, uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout, uint16_t minimum_local_timeout);
- friend void tACL_CONN::Reset();
- } sniff_subrating;
-
- tLINK_POLICY Settings() const { return settings_; }
-
- private:
- tLINK_POLICY settings_{kAllLinkPoliciesEnabled};
- friend void btm_set_link_policy(tACL_CONN* conn, tLINK_POLICY policy);
- friend void tACL_CONN::Reset();
- } policy;
-};
-
-struct controller_t;
-
-/****************************************************
- ** ACL Management API
- ****************************************************/
-constexpr uint16_t kDefaultPacketTypeMask =
- HCI_PKT_TYPES_MASK_DH1 | HCI_PKT_TYPES_MASK_DM1 | HCI_PKT_TYPES_MASK_DH3 |
- HCI_PKT_TYPES_MASK_DM3 | HCI_PKT_TYPES_MASK_DH5 | HCI_PKT_TYPES_MASK_DM5;
-
-struct tACL_CB {
- private:
- friend uint8_t btm_handle_to_acl_index(uint16_t hci_handle);
- friend void btm_acl_device_down(void);
- friend void btm_acl_encrypt_change(uint16_t handle, uint8_t status,
- uint8_t encr_enable);
-
- friend void DumpsysL2cap(int fd);
- friend void DumpsysAcl(int fd);
- friend struct StackAclBtmAcl;
-
- tACL_CONN acl_db[MAX_L2CAP_LINKS];
- tBTM_ROLE_SWITCH_CMPL switch_role_ref_data;
- uint16_t btm_acl_pkt_types_supported = kDefaultPacketTypeMask;
- uint16_t btm_def_link_policy;
- tHCI_STATUS acl_disc_reason = HCI_ERR_UNDEFINED;
-
- public:
- void SetDefaultPacketTypeMask(uint16_t packet_type_mask) {
- btm_acl_pkt_types_supported = packet_type_mask;
- }
-
- tHCI_STATUS get_disconnect_reason() const { return acl_disc_reason; }
- void set_disconnect_reason(tHCI_STATUS reason) { acl_disc_reason = reason; }
- uint16_t DefaultPacketTypes() const { return btm_acl_pkt_types_supported; }
- uint16_t DefaultLinkPolicy() const { return btm_def_link_policy; }
-
- struct {
- std::vector<tBTM_PM_STATUS_CBACK*> clients;
- } link_policy;
-
- unsigned NumberOfActiveLinks() const {
- unsigned cnt = 0;
- for (int i = 0; i < MAX_L2CAP_LINKS; i++) {
- if (acl_db[i].InUse()) ++cnt;
- }
- return cnt;
- }
-
- private:
- std::unordered_set<RawAddress> ignore_auto_connect_after_disconnect_set_;
-
- public:
- void AddToIgnoreAutoConnectAfterDisconnect(const RawAddress& bd_addr);
- bool CheckAndClearIgnoreAutoConnectAfterDisconnect(const RawAddress& bd_addr);
- void ClearAllIgnoreAutoConnectAfterDisconnect();
-};
diff --git a/stack/acl/ble_acl.cc b/stack/acl/ble_acl.cc
deleted file mode 100644
index 5ec27ad99..000000000
--- a/stack/acl/ble_acl.cc
+++ /dev/null
@@ -1,173 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <cstdint>
-
-#include "osi/include/log.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/gatt/connection_manager.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/hcidefs.h"
-#include "stack/include/l2cap_hci_link_interface.h"
-
-extern tBTM_CB btm_cb;
-
-void btm_ble_advertiser_notify_terminated_legacy(uint8_t status,
- uint16_t connection_handle);
-void btm_ble_increment_link_topology_mask(uint8_t link_role);
-
-bool maybe_resolve_address(RawAddress* bda, tBLE_ADDR_TYPE* bda_type);
-
-static bool acl_ble_common_connection(const tBLE_BD_ADDR& address_with_type,
- uint16_t handle, tHCI_ROLE role,
- bool is_in_security_db,
- uint16_t conn_interval,
- uint16_t conn_latency,
- uint16_t conn_timeout) {
- if (role == HCI_ROLE_CENTRAL) {
- btm_cb.ble_ctr_cb.set_connection_state_idle();
- btm_ble_clear_topology_mask(BTM_BLE_STATE_INIT_BIT);
- }
-
- // Inform any applications that a connection has completed.
- connection_manager::on_connection_complete(address_with_type.bda);
-
- // Allocate or update the security device record for this device
- btm_ble_connected(address_with_type.bda, handle, HCI_ENCRYPT_MODE_DISABLED,
- role, address_with_type.type, is_in_security_db);
-
- // Update the link topology information for our device
- btm_ble_increment_link_topology_mask(role);
-
- // Inform l2cap of a potential connection.
- if (!l2cble_conn_comp(handle, role, address_with_type.bda,
- address_with_type.type, conn_interval, conn_latency,
- conn_timeout)) {
- btm_sec_disconnect(handle, HCI_ERR_NO_CONNECTION);
- LOG_WARN("Unable to complete l2cap connection");
- return false;
- }
-
- btm_ble_disable_resolving_list(BTM_BLE_RL_INIT, true);
-
- /* Tell BTM Acl management about the link */
- btm_acl_created(address_with_type.bda, handle, role, BT_TRANSPORT_LE);
-
- return true;
-}
-
-void acl_ble_connection_complete(const tBLE_BD_ADDR& address_with_type,
- uint16_t handle, tHCI_ROLE role, bool match,
- uint16_t conn_interval, uint16_t conn_latency,
- uint16_t conn_timeout) {
- if (!acl_ble_common_connection(address_with_type, handle, role, match,
- conn_interval, conn_latency, conn_timeout)) {
- LOG_WARN("Unable to create non enhanced ble acl connection");
- return;
- }
-
- btm_ble_update_mode_operation(role, &address_with_type.bda, HCI_SUCCESS);
-
- if (role == HCI_ROLE_PERIPHERAL)
- btm_ble_advertiser_notify_terminated_legacy(HCI_SUCCESS, handle);
-}
-
-void acl_ble_enhanced_connection_complete(
- const tBLE_BD_ADDR& address_with_type, uint16_t handle, tHCI_ROLE role,
- bool match, uint16_t conn_interval, uint16_t conn_latency,
- uint16_t conn_timeout, const RawAddress& local_rpa,
- const RawAddress& peer_rpa, uint8_t peer_addr_type) {
- if (!acl_ble_common_connection(address_with_type, handle, role, match,
- conn_interval, conn_latency, conn_timeout)) {
- LOG_WARN("Unable to create enhanced ble acl connection");
- return;
- }
-
- btm_ble_refresh_local_resolvable_private_addr(address_with_type.bda,
- local_rpa);
-
- if (peer_addr_type & BLE_ADDR_TYPE_ID_BIT)
- btm_ble_refresh_peer_resolvable_private_addr(
- address_with_type.bda, peer_rpa, tBTM_SEC_BLE::BTM_BLE_ADDR_RRA);
- btm_ble_update_mode_operation(role, &address_with_type.bda, HCI_SUCCESS);
-
- if (role == HCI_ROLE_PERIPHERAL)
- btm_ble_advertiser_notify_terminated_legacy(HCI_SUCCESS, handle);
-}
-
-static bool maybe_resolve_received_address(
- const tBLE_BD_ADDR& address_with_type,
- tBLE_BD_ADDR* resolved_address_with_type) {
- ASSERT(resolved_address_with_type != nullptr);
-
- *resolved_address_with_type = address_with_type;
- return maybe_resolve_address(&resolved_address_with_type->bda,
- &resolved_address_with_type->type);
-}
-
-void acl_ble_enhanced_connection_complete_from_shim(
- const tBLE_BD_ADDR& address_with_type, uint16_t handle, tHCI_ROLE role,
- uint16_t conn_interval, uint16_t conn_latency, uint16_t conn_timeout,
- const RawAddress& local_rpa, const RawAddress& peer_rpa,
- uint8_t peer_addr_type) {
- tBLE_BD_ADDR resolved_address_with_type;
- const bool is_in_security_db = maybe_resolve_received_address(
- address_with_type, &resolved_address_with_type);
-
- acl_ble_enhanced_connection_complete(resolved_address_with_type, handle, role,
- is_in_security_db, conn_interval,
- conn_latency, conn_timeout, local_rpa,
- peer_rpa, peer_addr_type);
-
- // The legacy stack continues the LE connection after the read remote version
- // complete has been received.
- l2cble_notify_le_connection(address_with_type.bda);
- l2cble_use_preferred_conn_params(address_with_type.bda);
-}
-
-void acl_ble_connection_fail(const tBLE_BD_ADDR& address_with_type,
- uint16_t handle, bool enhanced,
- tHCI_STATUS status) {
- if (status != HCI_ERR_ADVERTISING_TIMEOUT) {
- btm_cb.ble_ctr_cb.set_connection_state_idle();
- btm_ble_clear_topology_mask(BTM_BLE_STATE_INIT_BIT);
- btm_ble_disable_resolving_list(BTM_BLE_RL_INIT, true);
- } else {
- btm_cb.ble_ctr_cb.inq_var.adv_mode = BTM_BLE_ADV_DISABLE;
- btm_ble_disable_resolving_list(BTM_BLE_RL_ADV, true);
- }
- btm_ble_update_mode_operation(HCI_ROLE_UNKNOWN, &address_with_type.bda,
- status);
-}
-
-void gatt_notify_conn_update(const RawAddress& remote, uint16_t interval,
- uint16_t latency, uint16_t timeout,
- tHCI_STATUS status);
-void acl_ble_update_event_received(tHCI_STATUS status, uint16_t handle,
- uint16_t interval, uint16_t latency,
- uint16_t timeout) {
- l2cble_process_conn_update_evt(handle, status, interval, latency, timeout);
-
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev_by_handle(handle);
-
- if (!p_dev_rec) return;
-
- gatt_notify_conn_update(p_dev_rec->ble.pseudo_addr, interval, latency,
- timeout, status);
-}
diff --git a/stack/acl/btm_acl.cc b/stack/acl/btm_acl.cc
deleted file mode 100644
index 62a69870a..000000000
--- a/stack/acl/btm_acl.cc
+++ /dev/null
@@ -1,2966 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2000-2012 Broadcom Corporation
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-/*****************************************************************************
- *
- * Name: btm_acl.cc
- *
- * Description: This file contains functions that handle ACL connections.
- * This includes operations such as hold and sniff modes,
- * supported packet types.
- *
- * This module contains both internal and external (API)
- * functions. External (API) functions are distinguishable
- * by their names beginning with uppercase BTM.
- *
- *
- *****************************************************************************/
-
-#define LOG_TAG "btm_acl"
-
-#include <cstdint>
-
-#include "bta/include/bta_dm_acl.h"
-#include "bta/sys/bta_sys.h"
-#include "btif/include/btif_acl.h"
-#include "common/metrics.h"
-#include "device/include/controller.h"
-#include "device/include/interop.h"
-#include "include/l2cap_hci_link_interface.h"
-#include "main/shim/acl_api.h"
-#include "main/shim/btm_api.h"
-#include "main/shim/dumpsys.h"
-#include "main/shim/l2c_api.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "stack/acl/acl.h"
-#include "stack/acl/peer_packet_types.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/btm/security_device_record.h"
-#include "stack/gatt/connection_manager.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/acl_hci_link_interface.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_iso_api.h"
-#include "stack/include/btu.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcimsgs.h"
-#include "stack/include/l2cap_acl_interface.h"
-#include "stack/include/sco_hci_link_interface.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
-
-void BTM_update_version_info(const RawAddress& bd_addr,
- const remote_version_info& remote_version_info);
-
-void gatt_find_in_device_record(const RawAddress& bd_addr,
- tBLE_BD_ADDR* address_with_type);
-void l2c_link_hci_conn_comp(tHCI_STATUS status, uint16_t handle,
- const RawAddress& p_bda);
-
-void BTM_db_reset(void);
-
-extern tBTM_CB btm_cb;
-
-struct StackAclBtmAcl {
- tACL_CONN* acl_allocate_connection();
- tACL_CONN* acl_get_connection_from_handle(uint16_t handle);
- tACL_CONN* btm_bda_to_acl(const RawAddress& bda, tBT_TRANSPORT transport);
- bool change_connection_packet_types(tACL_CONN& link,
- const uint16_t new_packet_type_bitmask);
- void btm_establish_continue(tACL_CONN* p_acl_cb);
- void btm_read_remote_features(uint16_t handle);
- void btm_set_default_link_policy(tLINK_POLICY settings);
- void btm_acl_role_changed(tHCI_STATUS hci_status, const RawAddress& bd_addr,
- tHCI_ROLE new_role);
- void hci_start_role_switch_to_central(tACL_CONN& p_acl);
- void set_default_packet_types_supported(uint16_t packet_types_supported) {
- btm_cb.acl_cb_.btm_acl_pkt_types_supported = packet_types_supported;
- }
-};
-
-struct RoleChangeView {
- tHCI_ROLE new_role = HCI_ROLE_UNKNOWN;
- RawAddress bd_addr;
-};
-
-namespace {
-StackAclBtmAcl internal_;
-std::unique_ptr<RoleChangeView> delayed_role_change_ = nullptr;
-const bluetooth::legacy::hci::Interface& GetLegacyHciInterface() {
- return bluetooth::legacy::hci::GetInterface();
-}
-}
-
-typedef struct {
- uint16_t handle;
- uint16_t hci_len;
-} __attribute__((packed)) acl_header_t;
-
-constexpr uint8_t BTM_MAX_SW_ROLE_FAILED_ATTEMPTS = 3;
-
-/* Define masks for supported and exception 2.0 ACL packet types
- */
-constexpr uint16_t BTM_ACL_SUPPORTED_PKTS_MASK =
- (HCI_PKT_TYPES_MASK_DM1 | HCI_PKT_TYPES_MASK_DH1 | HCI_PKT_TYPES_MASK_DM3 |
- HCI_PKT_TYPES_MASK_DH3 | HCI_PKT_TYPES_MASK_DM5 | HCI_PKT_TYPES_MASK_DH5);
-
-constexpr uint16_t BTM_ACL_EXCEPTION_PKTS_MASK =
- (HCI_PKT_TYPES_MASK_NO_2_DH1 | HCI_PKT_TYPES_MASK_NO_3_DH1 |
- HCI_PKT_TYPES_MASK_NO_2_DH3 | HCI_PKT_TYPES_MASK_NO_3_DH3 |
- HCI_PKT_TYPES_MASK_NO_2_DH5 | HCI_PKT_TYPES_MASK_NO_3_DH5);
-
-inline bool IsEprAvailable(const tACL_CONN& p_acl) {
- if (!p_acl.peer_lmp_feature_valid[0]) {
- LOG_WARN("Checking incomplete feature page read");
- return false;
- }
- return HCI_ATOMIC_ENCRYPT_SUPPORTED(p_acl.peer_lmp_feature_pages[0]) &&
- controller_get_interface()->supports_encryption_pause();
-}
-
-static void btm_process_remote_ext_features(tACL_CONN* p_acl_cb,
- uint8_t max_page_number);
-static void btm_read_failed_contact_counter_timeout(void* data);
-static void btm_read_remote_ext_features(uint16_t handle, uint8_t page_number);
-static void btm_read_rssi_timeout(void* data);
-static void btm_read_tx_power_timeout(void* data);
-static void check_link_policy(tLINK_POLICY* settings);
-void btm_set_link_policy(tACL_CONN* conn, tLINK_POLICY policy);
-
-namespace {
-void NotifyAclLinkUp(tACL_CONN& p_acl) {
- if (p_acl.link_up_issued) {
- LOG_INFO("Already notified BTA layer that the link is up");
- return;
- }
- p_acl.link_up_issued = true;
- BTA_dm_acl_up(p_acl.remote_addr, p_acl.transport);
-}
-
-void NotifyAclLinkDown(tACL_CONN& p_acl) {
- /* Only notify if link up has had a chance to be issued */
- if (p_acl.link_up_issued) {
- p_acl.link_up_issued = false;
- BTA_dm_acl_down(p_acl.remote_addr, p_acl.transport);
- }
-}
-
-void NotifyAclRoleSwitchComplete(const RawAddress& bda, tHCI_ROLE new_role,
- tHCI_STATUS hci_status) {
- BTA_dm_report_role_change(bda, new_role, hci_status);
-}
-
-void NotifyAclFeaturesReadComplete(tACL_CONN& p_acl,
- UNUSED_ATTR uint8_t max_page_number) {
- ASSERT_LOG(bluetooth::shim::is_gd_acl_enabled(),
- "For right now only called with gd_acl support");
- btm_process_remote_ext_features(&p_acl, max_page_number);
- btm_set_link_policy(&p_acl, btm_cb.acl_cb_.DefaultLinkPolicy());
- BTA_dm_notify_remote_features_complete(p_acl.remote_addr);
-}
-
-} // namespace
-
-static void hci_btsnd_hcic_disconnect(tACL_CONN& p_acl, tHCI_STATUS reason) {
- LOG_INFO("Disconnecting peer:%s reason:%s",
- PRIVATE_ADDRESS(p_acl.remote_addr),
- hci_error_code_text(reason).c_str());
- p_acl.disconnect_reason = reason;
-
- if (bluetooth::shim::is_gd_acl_enabled()) {
- return bluetooth::shim::ACL_Disconnect(p_acl.hci_handle,
- p_acl.is_transport_br_edr(), reason);
- } else {
- GetLegacyHciInterface().Disconnect(p_acl.hci_handle,
- static_cast<uint16_t>(reason));
- }
-}
-
-void StackAclBtmAcl::hci_start_role_switch_to_central(tACL_CONN& p_acl) {
- GetLegacyHciInterface().StartRoleSwitch(
- p_acl.remote_addr, static_cast<uint8_t>(HCI_ROLE_CENTRAL));
- p_acl.set_switch_role_in_progress();
- p_acl.rs_disc_pending = BTM_SEC_RS_PENDING;
-}
-
-void hci_btm_set_link_supervision_timeout(tACL_CONN& link, uint16_t timeout) {
- if (link.link_role != HCI_ROLE_CENTRAL) {
- /* Only send if current role is Central; 2.0 spec requires this */
- LOG_WARN("Can only set link supervision timeout if central role:%s",
- RoleText(link.link_role).c_str());
- return;
- }
-
- LOG_DEBUG("Setting link supervision timeout:%.2fs peer:%s",
- double(timeout) * 0.01, PRIVATE_ADDRESS(link.RemoteAddress()));
- link.link_super_tout = timeout;
- btsnd_hcic_write_link_super_tout(LOCAL_BR_EDR_CONTROLLER_ID, link.Handle(),
- timeout);
-}
-
-/* 3 seconds timeout waiting for responses */
-#define BTM_DEV_REPLY_TIMEOUT_MS (3 * 1000)
-
-void BTM_acl_after_controller_started(const controller_t* controller) {
- internal_.btm_set_default_link_policy(
- HCI_ENABLE_CENTRAL_PERIPHERAL_SWITCH | HCI_ENABLE_HOLD_MODE |
- HCI_ENABLE_SNIFF_MODE | HCI_ENABLE_PARK_MODE);
-
- /* Create ACL supported packet types mask */
- uint16_t btm_acl_pkt_types_supported =
- (HCI_PKT_TYPES_MASK_DH1 + HCI_PKT_TYPES_MASK_DM1);
-
- if (controller->supports_3_slot_packets())
- btm_acl_pkt_types_supported |=
- (HCI_PKT_TYPES_MASK_DH3 + HCI_PKT_TYPES_MASK_DM3);
-
- if (controller->supports_5_slot_packets())
- btm_acl_pkt_types_supported |=
- (HCI_PKT_TYPES_MASK_DH5 + HCI_PKT_TYPES_MASK_DM5);
-
- /* Add in EDR related ACL types */
- if (!controller->supports_classic_2m_phy()) {
- btm_acl_pkt_types_supported |=
- (HCI_PKT_TYPES_MASK_NO_2_DH1 + HCI_PKT_TYPES_MASK_NO_2_DH3 +
- HCI_PKT_TYPES_MASK_NO_2_DH5);
- }
-
- if (!controller->supports_classic_3m_phy()) {
- btm_acl_pkt_types_supported |=
- (HCI_PKT_TYPES_MASK_NO_3_DH1 + HCI_PKT_TYPES_MASK_NO_3_DH3 +
- HCI_PKT_TYPES_MASK_NO_3_DH5);
- }
-
- /* Check to see if 3 and 5 slot packets are available */
- if (controller->supports_classic_2m_phy() ||
- controller->supports_classic_3m_phy()) {
- if (!controller->supports_3_slot_edr_packets())
- btm_acl_pkt_types_supported |=
- (HCI_PKT_TYPES_MASK_NO_2_DH3 + HCI_PKT_TYPES_MASK_NO_3_DH3);
-
- if (!controller->supports_5_slot_edr_packets())
- btm_acl_pkt_types_supported |=
- (HCI_PKT_TYPES_MASK_NO_2_DH5 + HCI_PKT_TYPES_MASK_NO_3_DH5);
- }
- internal_.set_default_packet_types_supported(btm_acl_pkt_types_supported);
-}
-
-/*******************************************************************************
- *
- * Function btm_bda_to_acl
- *
- * Description This function returns the FIRST acl_db entry for the passed
- * BDA.
- *
- * Parameters bda : BD address of the remote device
- * transport : Physical transport used for ACL connection
- * (BR/EDR or LE)
- *
- * Returns Returns pointer to the ACL DB for the requested BDA if found.
- * nullptr if not found.
- *
- ******************************************************************************/
-tACL_CONN* StackAclBtmAcl::btm_bda_to_acl(const RawAddress& bda,
- tBT_TRANSPORT transport) {
- tACL_CONN* p_acl = &btm_cb.acl_cb_.acl_db[0];
- for (uint8_t index = 0; index < MAX_L2CAP_LINKS; index++, p_acl++) {
- if ((p_acl->in_use) && p_acl->remote_addr == bda &&
- p_acl->transport == transport) {
- return p_acl;
- }
- }
- return nullptr;
-}
-
-tACL_CONN* acl_get_connection_from_address(const RawAddress& bd_addr,
- tBT_TRANSPORT transport) {
- return internal_.btm_bda_to_acl(bd_addr, transport);
-}
-
-/*******************************************************************************
- *
- * Function btm_handle_to_acl_index
- *
- * Description This function returns the FIRST acl_db entry for the passed
- * hci_handle.
- *
- * Returns index to the acl_db or MAX_L2CAP_LINKS.
- *
- ******************************************************************************/
-uint8_t btm_handle_to_acl_index(uint16_t hci_handle) {
- tACL_CONN* p = &btm_cb.acl_cb_.acl_db[0];
- uint8_t xx;
- for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p++) {
- if ((p->in_use) && (p->hci_handle == hci_handle)) {
- break;
- }
- }
-
- /* If here, no BD Addr found */
- return (xx);
-}
-
-tACL_CONN* StackAclBtmAcl::acl_get_connection_from_handle(uint16_t hci_handle) {
- uint8_t index = btm_handle_to_acl_index(hci_handle);
- if (index >= MAX_L2CAP_LINKS) return nullptr;
- return &btm_cb.acl_cb_.acl_db[index];
-}
-
-tACL_CONN* acl_get_connection_from_handle(uint16_t handle) {
- return internal_.acl_get_connection_from_handle(handle);
-}
-
-void btm_acl_process_sca_cmpl_pkt(uint8_t len, uint8_t* data) {
- uint16_t handle;
- uint8_t sca;
- uint8_t status;
-
- STREAM_TO_UINT8(status, data);
-
- if (status != HCI_SUCCESS) {
- LOG_WARN("Peer SCA Command complete failed:%s",
- hci_error_code_text(static_cast<tHCI_STATUS>(status)).c_str());
- return;
- }
-
- STREAM_TO_UINT16(handle, data);
- STREAM_TO_UINT8(sca, data);
-
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
- p_acl->sca = sca;
-}
-
-tACL_CONN* StackAclBtmAcl::acl_allocate_connection() {
- tACL_CONN* p_acl = &btm_cb.acl_cb_.acl_db[0];
- for (uint8_t xx = 0; xx < MAX_L2CAP_LINKS; xx++, p_acl++) {
- if (!p_acl->in_use) {
- return p_acl;
- }
- }
- return nullptr;
-}
-
-void btm_acl_created(const RawAddress& bda, uint16_t hci_handle,
- tHCI_ROLE link_role, tBT_TRANSPORT transport) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(bda, transport);
- if (p_acl != (tACL_CONN*)NULL) {
- p_acl->hci_handle = hci_handle;
- p_acl->link_role = link_role;
- p_acl->transport = transport;
- btm_set_link_policy(p_acl, btm_cb.acl_cb_.DefaultLinkPolicy());
- LOG_WARN(
- "Unable to create duplicate acl when one already exists handle:%hu"
- " role:%s transport:%s",
- hci_handle, RoleText(link_role).c_str(),
- bt_transport_text(transport).c_str());
- return;
- }
-
- p_acl = internal_.acl_allocate_connection();
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
-
- p_acl->in_use = true;
- p_acl->hci_handle = hci_handle;
- p_acl->link_role = link_role;
- p_acl->link_up_issued = false;
- p_acl->remote_addr = bda;
- p_acl->sca = 0xFF;
- p_acl->transport = transport;
- p_acl->switch_role_failed_attempts = 0;
- p_acl->reset_switch_role();
- BTM_PM_OnConnected(hci_handle, bda);
-
- LOG_DEBUG(
- "Created new ACL connection peer:%s role:%s handle:0x%04x transport:%s",
- PRIVATE_ADDRESS(bda), RoleText(p_acl->link_role).c_str(), hci_handle,
- bt_transport_text(transport).c_str());
- btm_set_link_policy(p_acl, btm_cb.acl_cb_.DefaultLinkPolicy());
-
- if (transport == BT_TRANSPORT_LE) {
- btm_ble_refresh_local_resolvable_private_addr(
- bda, btm_cb.ble_ctr_cb.addr_mgnt_cb.private_addr);
- }
- /* if BR/EDR do something more */
- if (transport == BT_TRANSPORT_BR_EDR) {
- btsnd_hcic_read_rmt_clk_offset(hci_handle);
- if (!bluetooth::shim::is_gd_l2cap_enabled() &&
- !bluetooth::shim::is_gd_acl_enabled()) {
- // GD L2cap and GD Acl read this automatically
- btsnd_hcic_rmt_ver_req(hci_handle);
- }
- }
-
- if (transport == BT_TRANSPORT_LE) {
- btm_ble_get_acl_remote_addr(hci_handle, p_acl->active_remote_addr,
- &p_acl->active_remote_addr_type);
-
- if (controller_get_interface()
- ->supports_ble_peripheral_initiated_feature_exchange() ||
- link_role == HCI_ROLE_CENTRAL) {
- btsnd_hcic_ble_read_remote_feat(p_acl->hci_handle);
- } else {
- internal_.btm_establish_continue(p_acl);
- }
- }
-}
-
-void btm_acl_update_conn_addr(uint16_t handle, const RawAddress& address) {
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
- p_acl->conn_addr = address;
-}
-
-/*******************************************************************************
- *
- * Function btm_acl_removed
- *
- * Description This function is called by L2CAP when an ACL connection
- * is removed. Since only L2CAP creates ACL links, we use
- * the L2CAP link index as our index into the control blocks.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_acl_removed(uint16_t handle) {
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
- p_acl->in_use = false;
- NotifyAclLinkDown(*p_acl);
- p_acl->Reset();
- BTM_PM_OnDisconnected(handle);
-}
-
-/*******************************************************************************
- *
- * Function btm_acl_device_down
- *
- * Description This function is called when the local device is deemed
- * to be down. It notifies L2CAP of the failure.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_acl_device_down(void) {
- tACL_CONN* p = &btm_cb.acl_cb_.acl_db[0];
- uint16_t xx;
- for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p++) {
- if (p->in_use) {
- l2c_link_hci_disc_comp(p->hci_handle, HCI_ERR_HW_FAILURE);
- }
- }
- BTM_db_reset();
-}
-
-void btm_acl_set_paging(bool value) { btm_cb.is_paging = value; }
-
-void btm_acl_update_inquiry_status(uint8_t status) {
- btm_cb.is_inquiry = status == BTM_INQUIRY_STARTED;
- BTIF_dm_report_inquiry_status_change(status);
-}
-
-tBTM_STATUS BTM_GetRole(const RawAddress& remote_bd_addr, tHCI_ROLE* p_role) {
- if (p_role == nullptr) {
- return BTM_ILLEGAL_VALUE;
- }
- *p_role = HCI_ROLE_UNKNOWN;
-
- tACL_CONN* p_acl =
- internal_.btm_bda_to_acl(remote_bd_addr, BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return BTM_UNKNOWN_ADDR;
- }
- *p_role = p_acl->link_role;
- return BTM_SUCCESS;
-}
-
-/*******************************************************************************
- *
- * Function BTM_SwitchRoleToCentral
- *
- * Description This function is called to switch role between central and
- * peripheral. If role is already set it will do nothing.
- *
- * Returns BTM_SUCCESS if already in specified role.
- * BTM_CMD_STARTED if command issued to controller.
- * BTM_NO_RESOURCES if couldn't allocate memory to issue
- * command
- * BTM_UNKNOWN_ADDR if no active link with bd addr specified
- * BTM_MODE_UNSUPPORTED if local device does not support role
- * switching
- * BTM_BUSY if the previous command is not completed
- *
- ******************************************************************************/
-tBTM_STATUS BTM_SwitchRoleToCentral(const RawAddress& remote_bd_addr) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- bluetooth::shim::L2CA_SwitchRoleToCentral(remote_bd_addr);
- return BTM_SUCCESS;
- }
- if (!controller_get_interface()->supports_central_peripheral_role_switch()) {
- LOG_INFO("Local controller does not support role switching");
- return BTM_MODE_UNSUPPORTED;
- }
-
- tACL_CONN* p_acl =
- internal_.btm_bda_to_acl(remote_bd_addr, BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return BTM_UNKNOWN_ADDR;
- }
-
- if (p_acl->link_role == HCI_ROLE_CENTRAL) {
- LOG_INFO("Requested role is already in effect");
- return BTM_SUCCESS;
- }
-
- if (interop_match_addr(INTEROP_DISABLE_ROLE_SWITCH, &remote_bd_addr)) {
- LOG_INFO("Remote device is on list preventing role switch");
- return BTM_DEV_RESTRICT_LISTED;
- }
-
- if (BTM_IsScoActiveByBdaddr(remote_bd_addr)) {
- LOG_INFO("An active SCO to device prevents role switch at this time");
- return BTM_NO_RESOURCES;
- }
-
- if (!p_acl->is_switch_role_idle()) {
- LOG_INFO("Role switch is already progress");
- return BTM_BUSY;
- }
-
- tBTM_PM_MODE pwr_mode;
- if (!BTM_ReadPowerMode(p_acl->remote_addr, &pwr_mode)) {
- LOG_WARN(
- "Unable to find device to read current power mode prior to role "
- "switch");
- return BTM_UNKNOWN_ADDR;
- };
-
- if (pwr_mode == BTM_PM_MD_PARK || pwr_mode == BTM_PM_MD_SNIFF) {
- if (!BTM_SetLinkPolicyActiveMode(p_acl->remote_addr)) {
- LOG_WARN("Unable to set link policy active before attempting switch");
- return BTM_WRONG_MODE;
- }
- p_acl->set_switch_role_changing();
- }
- /* some devices do not support switch while encryption is on */
- else {
- if (p_acl->is_encrypted && !IsEprAvailable(*p_acl)) {
- /* bypass turning off encryption if change link key is already doing it */
- p_acl->set_encryption_off();
- p_acl->set_switch_role_encryption_off();
- } else {
- internal_.hci_start_role_switch_to_central(*p_acl);
- }
- }
-
- return BTM_CMD_STARTED;
-}
-
-/*******************************************************************************
- *
- * Function btm_acl_encrypt_change
- *
- * Description This function is when encryption of the connection is
- * completed by the LM. Checks to see if a role switch or
- * change of link key was active and initiates or continues
- * process if needed.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_acl_encrypt_change(uint16_t handle, uint8_t status,
- uint8_t encr_enable) {
- tACL_CONN* p = internal_.acl_get_connection_from_handle(handle);
- if (p == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
-
- p->is_encrypted = encr_enable;
-
- /* Process Role Switch if active */
- if (p->is_switch_role_encryption_off()) {
- /* if encryption turn off failed we still will try to switch role */
- if (encr_enable) {
- p->set_encryption_idle();
- p->reset_switch_role();
- } else {
- p->set_encryption_switching();
- p->set_switch_role_switching();
- }
- internal_.hci_start_role_switch_to_central(*p);
- }
- /* Finished enabling Encryption after role switch */
- else if (p->is_switch_role_encryption_on()) {
- p->reset_switch_role();
- p->set_encryption_idle();
- NotifyAclRoleSwitchComplete(
- btm_cb.acl_cb_.switch_role_ref_data.remote_bd_addr,
- btm_cb.acl_cb_.switch_role_ref_data.role,
- btm_cb.acl_cb_.switch_role_ref_data.hci_status);
-
- /* If a disconnect is pending, issue it now that role switch has completed
- */
- if (p->rs_disc_pending == BTM_SEC_DISC_PENDING) {
- hci_btsnd_hcic_disconnect(*p, HCI_ERR_PEER_USER);
- }
- p->rs_disc_pending = BTM_SEC_RS_NOT_PENDING; /* reset flag */
- }
-}
-
-static void check_link_policy(tLINK_POLICY* settings) {
- const controller_t* controller = controller_get_interface();
-
- if ((*settings & HCI_ENABLE_CENTRAL_PERIPHERAL_SWITCH) &&
- (!controller->supports_role_switch())) {
- *settings &= (~HCI_ENABLE_CENTRAL_PERIPHERAL_SWITCH);
- LOG_INFO("Role switch not supported (settings: 0x%04x)", *settings);
- }
- if ((*settings & HCI_ENABLE_HOLD_MODE) &&
- (!controller->supports_hold_mode())) {
- *settings &= (~HCI_ENABLE_HOLD_MODE);
- LOG_INFO("hold not supported (settings: 0x%04x)", *settings);
- }
- if ((*settings & HCI_ENABLE_SNIFF_MODE) &&
- (!controller->supports_sniff_mode())) {
- *settings &= (~HCI_ENABLE_SNIFF_MODE);
- LOG_INFO("sniff not supported (settings: 0x%04x)", *settings);
- }
- if ((*settings & HCI_ENABLE_PARK_MODE) &&
- (!controller->supports_park_mode())) {
- *settings &= (~HCI_ENABLE_PARK_MODE);
- LOG_INFO("park not supported (settings: 0x%04x)", *settings);
- }
-}
-
-void btm_set_link_policy(tACL_CONN* conn, tLINK_POLICY policy) {
- conn->link_policy = policy;
- check_link_policy(&conn->link_policy);
- if ((conn->link_policy & HCI_ENABLE_CENTRAL_PERIPHERAL_SWITCH) &&
- interop_match_addr(INTEROP_DISABLE_SNIFF, &(conn->remote_addr))) {
- conn->link_policy &= (~HCI_ENABLE_SNIFF_MODE);
- }
- btsnd_hcic_write_policy_set(conn->hci_handle,
- static_cast<uint16_t>(conn->link_policy));
-}
-
-static void btm_toggle_policy_on_for(const RawAddress& peer_addr,
- uint16_t flag) {
- auto conn = internal_.btm_bda_to_acl(peer_addr, BT_TRANSPORT_BR_EDR);
- if (!conn) {
- LOG_WARN("Unable to find active acl");
- return;
- }
- btm_set_link_policy(conn, conn->link_policy | flag);
-}
-
-static void btm_toggle_policy_off_for(const RawAddress& peer_addr,
- uint16_t flag) {
- auto conn = internal_.btm_bda_to_acl(peer_addr, BT_TRANSPORT_BR_EDR);
- if (!conn) {
- LOG_WARN("Unable to find active acl");
- return;
- }
- btm_set_link_policy(conn, conn->link_policy & ~flag);
-}
-
-bool BTM_is_sniff_allowed_for(const RawAddress& peer_addr) {
- auto conn = internal_.btm_bda_to_acl(peer_addr, BT_TRANSPORT_BR_EDR);
- if (!conn) {
- LOG_WARN("Unable to find active acl");
- return false;
- }
- return conn->link_policy & HCI_ENABLE_SNIFF_MODE;
-}
-
-void BTM_unblock_sniff_mode_for(const RawAddress& peer_addr) {
- btm_toggle_policy_on_for(peer_addr, HCI_ENABLE_SNIFF_MODE);
-}
-
-void BTM_block_sniff_mode_for(const RawAddress& peer_addr) {
- btm_toggle_policy_off_for(peer_addr, HCI_ENABLE_SNIFF_MODE);
-}
-
-void BTM_unblock_role_switch_for(const RawAddress& peer_addr) {
- btm_toggle_policy_on_for(peer_addr, HCI_ENABLE_CENTRAL_PERIPHERAL_SWITCH);
-}
-
-void BTM_block_role_switch_for(const RawAddress& peer_addr) {
- btm_toggle_policy_off_for(peer_addr, HCI_ENABLE_CENTRAL_PERIPHERAL_SWITCH);
-}
-
-void StackAclBtmAcl::btm_set_default_link_policy(tLINK_POLICY settings) {
- check_link_policy(&settings);
- btm_cb.acl_cb_.btm_def_link_policy = settings;
- btsnd_hcic_write_def_policy_set(settings);
-}
-
-void BTM_default_unblock_role_switch() {
- internal_.btm_set_default_link_policy(btm_cb.acl_cb_.DefaultLinkPolicy() |
- HCI_ENABLE_CENTRAL_PERIPHERAL_SWITCH);
-}
-
-void BTM_default_block_role_switch() {
- internal_.btm_set_default_link_policy(btm_cb.acl_cb_.DefaultLinkPolicy() &
- ~HCI_ENABLE_CENTRAL_PERIPHERAL_SWITCH);
-}
-
-/*******************************************************************************
- *
- * Function btm_read_remote_version_complete
- *
- * Description This function is called when the command complete message
- * is received from the HCI for the remote version info.
- *
- * Returns void
- *
- ******************************************************************************/
-static void maybe_chain_more_commands_after_read_remote_version_complete(
- uint8_t status, uint16_t handle) {
- tACL_CONN* p_acl_cb = internal_.acl_get_connection_from_handle(handle);
- if (p_acl_cb == nullptr) {
- LOG_WARN("Received remote version complete for unknown device");
- return;
- }
-
- switch (p_acl_cb->transport) {
- case BT_TRANSPORT_LE:
- l2cble_notify_le_connection(p_acl_cb->remote_addr);
- l2cble_use_preferred_conn_params(p_acl_cb->remote_addr);
- break;
- case BT_TRANSPORT_BR_EDR:
- /**
- * When running legacy stack continue chain of executing various
- * read commands. Skip when gd_acl is enabled because that
- * module handles all remote read functionality.
- */
- if (!bluetooth::shim::is_gd_acl_enabled()) {
- if (status == HCI_SUCCESS) {
- internal_.btm_read_remote_features(p_acl_cb->hci_handle);
- }
- }
- }
-}
-
-void btm_process_remote_version_complete(uint8_t status, uint16_t handle,
- uint8_t lmp_version,
- uint16_t manufacturer,
- uint16_t lmp_subversion) {
- tACL_CONN* p_acl_cb = internal_.acl_get_connection_from_handle(handle);
- if (p_acl_cb == nullptr) {
- LOG_WARN("Received remote version complete for unknown acl");
- return;
- }
-
- if (status == HCI_SUCCESS) {
- p_acl_cb->remote_version_info.lmp_version = lmp_version;
- p_acl_cb->remote_version_info.manufacturer = manufacturer;
- p_acl_cb->remote_version_info.lmp_subversion = lmp_subversion;
- p_acl_cb->remote_version_info.valid = true;
- BTM_update_version_info(p_acl_cb->RemoteAddress(),
- p_acl_cb->remote_version_info);
-
- bluetooth::common::LogRemoteVersionInfo(handle, status, lmp_version,
- manufacturer, lmp_subversion);
- } else {
- bluetooth::common::LogRemoteVersionInfo(handle, status, 0, 0, 0);
- }
-}
-
-void btm_read_remote_version_complete_raw(uint8_t* p) {
- uint8_t status;
- uint16_t handle;
- uint8_t lmp_version;
- uint16_t manufacturer;
- uint16_t lmp_subversion;
-
- STREAM_TO_UINT8(status, p);
- STREAM_TO_UINT16(handle, p);
- STREAM_TO_UINT8(lmp_version, p);
- STREAM_TO_UINT16(manufacturer, p);
- STREAM_TO_UINT16(lmp_subversion, p);
-
- ASSERT_LOG(!bluetooth::shim::is_gd_acl_enabled(),
- "gd acl layer should be receiving this completion");
- btm_read_remote_version_complete(static_cast<tHCI_STATUS>(status), handle,
- lmp_version, manufacturer, lmp_version);
-}
-
-void btm_read_remote_version_complete(tHCI_STATUS status, uint16_t handle,
- uint8_t lmp_version,
- uint16_t manufacturer,
- uint16_t lmp_subversion) {
- btm_process_remote_version_complete(status, handle, lmp_version, manufacturer,
- lmp_subversion);
- maybe_chain_more_commands_after_read_remote_version_complete(status, handle);
-}
-
-/*******************************************************************************
- *
- * Function btm_process_remote_ext_features
- *
- * Description Local function called to process all extended features pages
- * read from a remote device.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_process_remote_ext_features(tACL_CONN* p_acl_cb,
- uint8_t max_page_number) {
- CHECK(p_acl_cb != nullptr);
- if (!p_acl_cb->peer_lmp_feature_valid[max_page_number]) {
- LOG_WARN(
- "Checking remote features but remote feature read is "
- "incomplete");
- }
-
- bool ssp_supported =
- HCI_SSP_HOST_SUPPORTED(p_acl_cb->peer_lmp_feature_pages[1]);
- bool secure_connections_supported =
- HCI_SC_HOST_SUPPORTED(p_acl_cb->peer_lmp_feature_pages[1]);
- bool role_switch_supported =
- HCI_SWITCH_SUPPORTED(p_acl_cb->peer_lmp_feature_pages[0]);
- bool br_edr_supported =
- !HCI_BREDR_NOT_SPT_SUPPORTED(p_acl_cb->peer_lmp_feature_pages[0]);
- bool le_supported =
- HCI_LE_SPT_SUPPORTED(p_acl_cb->peer_lmp_feature_pages[0]) &&
- HCI_LE_HOST_SUPPORTED(p_acl_cb->peer_lmp_feature_pages[1]);
- btm_sec_set_peer_sec_caps(p_acl_cb->hci_handle, ssp_supported,
- secure_connections_supported, role_switch_supported,
- br_edr_supported, le_supported);
-}
-
-/*******************************************************************************
- *
- * Function btm_read_remote_features
- *
- * Description Local function called to send a read remote supported
- * features/remote extended features page[0].
- *
- * Returns void
- *
- ******************************************************************************/
-void StackAclBtmAcl::btm_read_remote_features(uint16_t handle) {
- uint8_t acl_idx;
- tACL_CONN* p_acl_cb;
-
- acl_idx = btm_handle_to_acl_index(handle);
- if (acl_idx >= MAX_L2CAP_LINKS) {
- LOG_WARN("Unable to find active acl");
- return;
- }
-
- p_acl_cb = &btm_cb.acl_cb_.acl_db[acl_idx];
- memset(p_acl_cb->peer_lmp_feature_pages, 0,
- sizeof(p_acl_cb->peer_lmp_feature_pages));
-
- /* first send read remote supported features HCI command */
- /* because we don't know whether the remote support extended feature command
- */
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- // GD L2cap reads this automatically
- return;
- }
- btsnd_hcic_rmt_features_req(handle);
-}
-
-/*******************************************************************************
- *
- * Function btm_read_remote_ext_features
- *
- * Description Local function called to send a read remote extended
- * features
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_remote_ext_features(uint16_t handle, uint8_t page_number) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- // GD L2cap reads this automatically
- return;
- }
- btsnd_hcic_rmt_ext_features(handle, page_number);
-}
-
-/*******************************************************************************
- *
- * Function btm_read_remote_features_complete
- *
- * Description This function is called when the remote supported features
- * complete event is received from the HCI.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_remote_features_complete_raw(uint8_t* p) {
- uint8_t status;
- uint16_t handle;
-
- STREAM_TO_UINT8(status, p);
-
- if (status != HCI_SUCCESS) {
- LOG_WARN("Uanble to read remote features status:%s",
- hci_error_code_text(static_cast<tHCI_STATUS>(status)).c_str());
- return;
- }
-
- STREAM_TO_UINT16(handle, p);
-
- btm_read_remote_features_complete(handle, p);
-}
-
-void btm_read_remote_features_complete(uint16_t handle, uint8_t* features) {
- tACL_CONN* p_acl_cb = internal_.acl_get_connection_from_handle(handle);
- if (p_acl_cb == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
-
- /* Copy the received features page */
- STREAM_TO_ARRAY(p_acl_cb->peer_lmp_feature_pages[0], features,
- HCI_FEATURE_BYTES_PER_PAGE);
- p_acl_cb->peer_lmp_feature_valid[0] = true;
-
- if ((HCI_LMP_EXTENDED_SUPPORTED(p_acl_cb->peer_lmp_feature_pages[0])) &&
- (controller_get_interface()
- ->supports_reading_remote_extended_features())) {
- /* if the remote controller has extended features and local controller
- supports HCI_Read_Remote_Extended_Features command then start reading
- these feature starting with extended features page 1 */
- LOG_DEBUG("Start reading remote extended features");
- btm_read_remote_ext_features(handle, 1);
- return;
- }
-
- /* Remote controller has no extended features. Process remote controller
- supported features (features page 0). */
- btm_process_remote_ext_features(p_acl_cb, 0);
-
- /* Continue with HCI connection establishment */
- internal_.btm_establish_continue(p_acl_cb);
-}
-
-/*******************************************************************************
- *
- * Function btm_read_remote_ext_features_complete
- *
- * Description This function is called when the remote extended features
- * complete event is received from the HCI.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_remote_ext_features_complete_raw(uint8_t* p, uint8_t evt_len) {
- uint8_t page_num, max_page;
- uint16_t handle;
-
- if (evt_len < HCI_EXT_FEATURES_SUCCESS_EVT_LEN) {
- android_errorWriteLog(0x534e4554, "141552859");
- LOG_WARN("Remote extended feature length too short. length=%d", evt_len);
- return;
- }
-
- ++p;
- STREAM_TO_UINT16(handle, p);
- STREAM_TO_UINT8(page_num, p);
- STREAM_TO_UINT8(max_page, p);
-
- if (max_page > HCI_EXT_FEATURES_PAGE_MAX) {
- LOG_WARN("Too many max pages read page=%d unknown", max_page);
- return;
- }
-
- if (page_num > HCI_EXT_FEATURES_PAGE_MAX) {
- android_errorWriteLog(0x534e4554, "141552859");
- LOG_WARN("Too many received pages num_page=%d invalid", page_num);
- return;
- }
-
- if (page_num > max_page) {
- LOG_WARN("num_page=%d, max_page=%d invalid", page_num, max_page);
- }
-
- btm_read_remote_ext_features_complete(handle, page_num, max_page, p);
-}
-
-void btm_read_remote_ext_features_complete(uint16_t handle, uint8_t page_num,
- uint8_t max_page,
- uint8_t* features) {
- /* Validate parameters */
- auto* p_acl_cb = internal_.acl_get_connection_from_handle(handle);
- if (p_acl_cb == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
-
- /* Copy the received features page */
- STREAM_TO_ARRAY(p_acl_cb->peer_lmp_feature_pages[page_num], features,
- HCI_FEATURE_BYTES_PER_PAGE);
- p_acl_cb->peer_lmp_feature_valid[page_num] = true;
-
- /* If there is the next remote features page and
- * we have space to keep this page data - read this page */
- if ((page_num < max_page) && (page_num < HCI_EXT_FEATURES_PAGE_MAX)) {
- page_num++;
- LOG_DEBUG("BTM reads next remote extended features page (%d)", page_num);
- btm_read_remote_ext_features(handle, page_num);
- return;
- }
-
- /* Reading of remote feature pages is complete */
- LOG_DEBUG("BTM reached last remote extended features page (%d)", page_num);
-
- /* Process the pages */
- btm_process_remote_ext_features(p_acl_cb, max_page);
-
- /* Continue with HCI connection establishment */
- internal_.btm_establish_continue(p_acl_cb);
-}
-
-/*******************************************************************************
- *
- * Function btm_read_remote_ext_features_failed
- *
- * Description This function is called when the remote extended features
- * complete event returns a failed status.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_remote_ext_features_failed(uint8_t status, uint16_t handle) {
- LOG_WARN("status 0x%02x for handle %d", status, handle);
-
- tACL_CONN* p_acl_cb = internal_.acl_get_connection_from_handle(handle);
- if (p_acl_cb == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
-
- /* Process supported features only */
- btm_process_remote_ext_features(p_acl_cb, 0);
-
- /* Continue HCI connection establishment */
- internal_.btm_establish_continue(p_acl_cb);
-}
-
-/*******************************************************************************
- *
- * Function btm_establish_continue
- *
- * Description This function is called when the command complete message
- * is received from the HCI for the read local link policy
- * request.
- *
- * Returns void
- *
- ******************************************************************************/
-void StackAclBtmAcl::btm_establish_continue(tACL_CONN* p_acl) {
- CHECK(p_acl != nullptr);
-
- if (p_acl->is_transport_br_edr()) {
- /* For now there are a some devices that do not like sending */
- /* commands events and data at the same time. */
- /* Set the packet types to the default allowed by the device */
- const uint16_t default_packet_type_mask =
- btm_cb.acl_cb_.DefaultPacketTypes();
- if (!internal_.change_connection_packet_types(*p_acl,
- default_packet_type_mask)) {
- LOG_ERROR("Unable to change connection packet type types:%04x address:%s",
- default_packet_type_mask,
- PRIVATE_ADDRESS(p_acl->RemoteAddress()));
- }
- btm_set_link_policy(p_acl, btm_cb.acl_cb_.DefaultLinkPolicy());
- }
- NotifyAclLinkUp(*p_acl);
-}
-
-void btm_establish_continue_from_address(const RawAddress& bda,
- tBT_TRANSPORT transport) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(bda, transport);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
- internal_.btm_establish_continue(p_acl);
-}
-
-/*******************************************************************************
- *
- * Function BTM_GetLinkSuperTout
- *
- * Description Read the link supervision timeout value of the connection
- *
- * Returns status of the operation
- *
- ******************************************************************************/
-tBTM_STATUS BTM_GetLinkSuperTout(const RawAddress& remote_bda,
- uint16_t* p_timeout) {
- CHECK(p_timeout != nullptr);
- const tACL_CONN* p_acl =
- internal_.btm_bda_to_acl(remote_bda, BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return BTM_UNKNOWN_ADDR;
- }
- *p_timeout = p_acl->link_super_tout;
- return BTM_SUCCESS;
-}
-
-/*******************************************************************************
- *
- * Function BTM_SetLinkSuperTout
- *
- * Description Create and send HCI "Write Link Supervision Timeout" command
- *
- * Returns status of the operation
- *
- ******************************************************************************/
-tBTM_STATUS BTM_SetLinkSuperTout(const RawAddress& remote_bda,
- uint16_t timeout) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(remote_bda, BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return BTM_UNKNOWN_ADDR;
- }
-
- /* Only send if current role is Central; 2.0 spec requires this */
- if (p_acl->link_role == HCI_ROLE_CENTRAL) {
- p_acl->link_super_tout = timeout;
- btsnd_hcic_write_link_super_tout(LOCAL_BR_EDR_CONTROLLER_ID,
- p_acl->hci_handle, timeout);
- LOG_DEBUG("Set supervision timeout:%.2fms bd_addr:%s",
- supervision_timeout_to_seconds(timeout),
- PRIVATE_ADDRESS(remote_bda));
- return BTM_CMD_STARTED;
- } else {
- LOG_WARN(
- "Role is peripheral so unable to set supervision timeout:%.2fms "
- "bd_addr:%s",
- supervision_timeout_to_seconds(timeout), PRIVATE_ADDRESS(remote_bda));
- return BTM_SUCCESS;
- }
-}
-
-bool BTM_IsAclConnectionUp(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_IsLinkEstablished(remote_bda, transport);
- }
-
- return internal_.btm_bda_to_acl(remote_bda, transport) != nullptr;
-}
-
-bool BTM_IsAclConnectionUpAndHandleValid(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_IsLinkEstablished(remote_bda, transport);
- }
-
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(remote_bda, transport);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return false;
- }
- return p_acl->hci_handle != HCI_INVALID_HANDLE;
-}
-
-bool BTM_IsAclConnectionUpFromHandle(uint16_t hci_handle) {
- return internal_.acl_get_connection_from_handle(hci_handle) != nullptr;
-}
-
-/*******************************************************************************
- *
- * Function BTM_GetNumAclLinks
- *
- * Description This function is called to count the number of
- * ACL links that are active.
- *
- * Returns uint16_t Number of active ACL links
- *
- ******************************************************************************/
-uint16_t BTM_GetNumAclLinks(void) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_GetNumLinks();
- }
- return static_cast<uint16_t>(btm_cb.acl_cb_.NumberOfActiveLinks());
-}
-
-/*******************************************************************************
- *
- * Function btm_get_acl_disc_reason_code
- *
- * Description This function is called to get the disconnection reason code
- * returned by the HCI at disconnection complete event.
- *
- * Returns true if connection is up, else false.
- *
- ******************************************************************************/
-tHCI_REASON btm_get_acl_disc_reason_code(void) {
- return btm_cb.acl_cb_.get_disconnect_reason();
-}
-
-/*******************************************************************************
- *
- * Function BTM_GetHCIConnHandle
- *
- * Description This function is called to get the handle for an ACL
- * connection to a specific remote BD Address.
- *
- * Returns the handle of the connection, or HCI_INVALID_HANDLE if none.
- *
- ******************************************************************************/
-uint16_t BTM_GetHCIConnHandle(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::BTM_GetHCIConnHandle(remote_bda, transport);
- }
-
- tACL_CONN* p;
- p = internal_.btm_bda_to_acl(remote_bda, transport);
- if (p != (tACL_CONN*)NULL) {
- return (p->hci_handle);
- }
-
- /* If here, no BD Addr found */
- return HCI_INVALID_HANDLE;
-}
-
-/*******************************************************************************
- *
- * Function BTM_IsPhy2mSupported
- *
- * Description This function is called to check PHY 2M support
- * from peer device
- * Returns True when PHY 2M supported false otherwise
- *
- ******************************************************************************/
-bool BTM_IsPhy2mSupported(const RawAddress& remote_bda, tBT_TRANSPORT transport) {
- tACL_CONN* p;
- BTM_TRACE_DEBUG("BTM_IsPhy2mSupported");
- p = internal_.btm_bda_to_acl(remote_bda, transport);
- if (p == (tACL_CONN*)NULL) {
- BTM_TRACE_DEBUG("BTM_IsPhy2mSupported: no connection");
- return false;
- }
-
- if (!p->peer_le_features_valid) {
- LOG_WARN(
- "Checking remote features but remote feature read is "
- "incomplete");
- }
- return HCI_LE_2M_PHY_SUPPORTED(p->peer_le_features);
-}
-
-/*******************************************************************************
- *
- * Function BTM_RequestPeerSCA
- *
- * Description This function is called to request sleep clock accuracy
- * from peer device
- *
- ******************************************************************************/
-void BTM_RequestPeerSCA(const RawAddress& remote_bda, tBT_TRANSPORT transport) {
- tACL_CONN* p;
- p = internal_.btm_bda_to_acl(remote_bda, transport);
- if (p == (tACL_CONN*)NULL) {
- LOG_WARN("Unable to find active acl");
- return;
- }
-
- btsnd_hcic_req_peer_sca(p->hci_handle);
-}
-
-/*******************************************************************************
- *
- * Function BTM_GetPeerSCA
- *
- * Description This function is called to get peer sleep clock accuracy
- *
- * Returns SCA or 0xFF if SCA was never previously requested, request
- * is not supported by peer device or ACL does not exist
- *
- ******************************************************************************/
-uint8_t BTM_GetPeerSCA(const RawAddress& remote_bda, tBT_TRANSPORT transport) {
- tACL_CONN* p;
- p = internal_.btm_bda_to_acl(remote_bda, transport);
- if (p != (tACL_CONN*)NULL) {
- return (p->sca);
- }
- LOG_WARN("Unable to find active acl");
-
- /* If here, no BD Addr found */
- return (0xFF);
-}
-
-/*******************************************************************************
- *
- * Function btm_rejectlist_role_change_device
- *
- * Description This function is used to rejectlist the device if the role
- * switch fails for maximum number of times. It also removes
- * the device from the black list if the role switch succeeds.
- *
- * Input Parms bd_addr - remote BD addr
- * hci_status - role switch status
- *
- * Returns void
- *
- *******************************************************************************/
-void btm_rejectlist_role_change_device(const RawAddress& bd_addr,
- uint8_t hci_status) {
- tACL_CONN* p = internal_.btm_bda_to_acl(bd_addr, BT_TRANSPORT_BR_EDR);
-
- if (!p) {
- LOG_WARN("Unable to find active acl");
- return;
- }
- if (hci_status == HCI_SUCCESS) {
- p->switch_role_failed_attempts = 0;
- return;
- }
-
- /* check for carkits */
- const uint32_t cod_audio_device =
- (BTM_COD_SERVICE_AUDIO | BTM_COD_MAJOR_AUDIO) << 8;
- const uint8_t* dev_class = btm_get_dev_class(bd_addr);
- if (dev_class == nullptr) return;
- const uint32_t cod =
- ((dev_class[0] << 16) | (dev_class[1] << 8) | dev_class[2]) & 0xffffff;
- if ((hci_status != HCI_SUCCESS) &&
- (p->is_switch_role_switching_or_in_progress()) &&
- ((cod & cod_audio_device) == cod_audio_device) &&
- (!interop_match_addr(INTEROP_DYNAMIC_ROLE_SWITCH, &bd_addr))) {
- p->switch_role_failed_attempts++;
- if (p->switch_role_failed_attempts == BTM_MAX_SW_ROLE_FAILED_ATTEMPTS) {
- LOG_WARN(
- "Device %s rejectlisted for role switching - "
- "multiple role switch failed attempts: %u",
- bd_addr.ToString().c_str(), p->switch_role_failed_attempts);
- interop_database_add(INTEROP_DYNAMIC_ROLE_SWITCH, &bd_addr, 3);
- }
- }
-}
-
-/*******************************************************************************
- *
- * Function btm_acl_role_changed
- *
- * Description This function is called whan a link's central/peripheral
- *role change event or command status event (with error) is received. It updates
- *the link control block, and calls the registered callback with status and role
- *(if registered).
- *
- * Returns void
- *
- ******************************************************************************/
-void StackAclBtmAcl::btm_acl_role_changed(tHCI_STATUS hci_status,
- const RawAddress& bd_addr,
- tHCI_ROLE new_role) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(bd_addr, BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- // If we get a role change before connection complete, we cache the new
- // role here and then propagate it when ACL Link is created.
- RoleChangeView role_change;
- role_change.new_role = new_role;
- role_change.bd_addr = bd_addr;
- delayed_role_change_ =
- std::make_unique<RoleChangeView>(std::move(role_change));
- LOG_WARN("Unable to find active acl");
- return;
- }
-
- tBTM_ROLE_SWITCH_CMPL* p_switch_role = &btm_cb.acl_cb_.switch_role_ref_data;
- LOG_DEBUG("Role change event received peer:%s hci_status:%s new_role:%s",
- PRIVATE_ADDRESS(bd_addr), hci_error_code_text(hci_status).c_str(),
- RoleText(new_role).c_str());
-
- p_switch_role->hci_status = hci_status;
- if (hci_status == HCI_SUCCESS) {
- p_switch_role->role = new_role;
- p_switch_role->remote_bd_addr = bd_addr;
-
- /* Update cached value */
- p_acl->link_role = new_role;
-
- /* Reload LSTO: link supervision timeout is reset in the LM after a role
- * switch */
- if (new_role == HCI_ROLE_CENTRAL) {
- constexpr uint16_t link_supervision_timeout = 8000;
- BTM_SetLinkSuperTout(bd_addr, link_supervision_timeout);
- }
- } else {
- new_role = p_acl->link_role;
- }
-
- /* Check if any SCO req is pending for role change */
- btm_sco_chk_pend_rolechange(p_acl->hci_handle);
-
- /* if switching state is switching we need to turn encryption on */
- /* if idle, we did not change encryption */
- if (p_acl->is_switch_role_switching()) {
- p_acl->set_encryption_on();
- p_acl->set_switch_role_encryption_on();
- return;
- }
-
- /* Set the switch_role_state to IDLE since the reply received from HCI */
- /* regardless of its result either success or failed. */
- if (p_acl->is_switch_role_in_progress()) {
- p_acl->set_encryption_idle();
- p_acl->reset_switch_role();
- }
-
- BTA_dm_report_role_change(bd_addr, new_role, hci_status);
-
- /* If a disconnect is pending, issue it now that role switch has completed */
- if (p_acl->rs_disc_pending == BTM_SEC_DISC_PENDING) {
- hci_btsnd_hcic_disconnect(*p_acl, HCI_ERR_PEER_USER);
- }
- p_acl->rs_disc_pending = BTM_SEC_RS_NOT_PENDING; /* reset flag */
-}
-
-void btm_acl_role_changed(tHCI_STATUS hci_status, const RawAddress& bd_addr,
- tHCI_ROLE new_role) {
- if (hci_status == HCI_SUCCESS) {
- l2c_link_role_changed(&bd_addr, new_role, hci_status);
- } else {
- l2c_link_role_changed(nullptr, HCI_ROLE_UNKNOWN,
- HCI_ERR_COMMAND_DISALLOWED);
- }
- internal_.btm_acl_role_changed(hci_status, bd_addr, new_role);
-}
-
-/*******************************************************************************
- *
- * Function change_connection_packet_types
- *
- * Description This function sets the packet types used for a specific
- * ACL connection. It is called internally by btm_acl_created
- * or by an application/profile by BTM_SetPacketTypes.
- *
- * Returns status of the operation
- *
- ******************************************************************************/
-bool StackAclBtmAcl::change_connection_packet_types(
- tACL_CONN& link, const uint16_t new_packet_type_mask) {
- // Start with the default configured packet types
- const uint16_t default_packet_type_mask = btm_cb.acl_cb_.DefaultPacketTypes();
-
- uint16_t packet_type_mask =
- default_packet_type_mask &
- (new_packet_type_mask & BTM_ACL_SUPPORTED_PKTS_MASK);
-
- /* OR in any exception packet types if at least 2.0 version of spec */
- packet_type_mask |=
- ((new_packet_type_mask & BTM_ACL_EXCEPTION_PKTS_MASK) |
- (BTM_ACL_EXCEPTION_PKTS_MASK & default_packet_type_mask));
-
- /* Exclude packet types not supported by the peer */
- if (link.peer_lmp_feature_valid[0]) {
- PeerPacketTypes peer_packet_types(link.peer_lmp_feature_pages[0]);
- packet_type_mask &= peer_packet_types.acl.supported;
- packet_type_mask |= peer_packet_types.acl.unsupported;
- } else {
- LOG_INFO(
- "Unable to include remote supported packet types as read feature "
- "incomplete");
- LOG_INFO("TIP: Maybe wait until read feature complete beforehand");
- }
-
- if (packet_type_mask == 0) {
- LOG_WARN("Unable to send controller illegal change packet mask:0x%04x",
- packet_type_mask);
- return false;
- }
-
- link.pkt_types_mask = packet_type_mask;
- bluetooth::legacy::hci::GetInterface().ChangeConnectionPacketType(
- link.Handle(), link.pkt_types_mask);
- LOG_DEBUG("Started change connection packet type:0x%04x address:%s",
- link.pkt_types_mask, PRIVATE_ADDRESS(link.RemoteAddress()));
- return true;
-}
-
-void btm_set_packet_types_from_address(const RawAddress& bd_addr,
- uint16_t pkt_types) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(bd_addr, BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
-
- if (!internal_.change_connection_packet_types(*p_acl, pkt_types)) {
- LOG_ERROR("Unable to change connection packet type types:%04x address:%s",
- pkt_types, PRIVATE_ADDRESS(bd_addr));
- }
-}
-
-/*******************************************************************************
- *
- * Function BTM_GetMaxPacketSize
- *
- * Returns Returns maximum packet size that can be used for current
- * connection, 0 if connection is not established
- *
- ******************************************************************************/
-uint16_t BTM_GetMaxPacketSize(const RawAddress& addr) {
- tACL_CONN* p = internal_.btm_bda_to_acl(addr, BT_TRANSPORT_BR_EDR);
- uint16_t pkt_types = 0;
- uint16_t pkt_size = 0;
- if (p != NULL) {
- pkt_types = p->pkt_types_mask;
- } else {
- /* Special case for when info for the local device is requested */
- if (addr == *controller_get_interface()->get_address()) {
- pkt_types = btm_cb.acl_cb_.DefaultPacketTypes();
- }
- }
-
- if (pkt_types) {
- if (!(pkt_types & HCI_PKT_TYPES_MASK_NO_3_DH5))
- pkt_size = HCI_EDR3_DH5_PACKET_SIZE;
- else if (!(pkt_types & HCI_PKT_TYPES_MASK_NO_2_DH5))
- pkt_size = HCI_EDR2_DH5_PACKET_SIZE;
- else if (!(pkt_types & HCI_PKT_TYPES_MASK_NO_3_DH3))
- pkt_size = HCI_EDR3_DH3_PACKET_SIZE;
- else if (pkt_types & HCI_PKT_TYPES_MASK_DH5)
- pkt_size = HCI_DH5_PACKET_SIZE;
- else if (!(pkt_types & HCI_PKT_TYPES_MASK_NO_2_DH3))
- pkt_size = HCI_EDR2_DH3_PACKET_SIZE;
- else if (pkt_types & HCI_PKT_TYPES_MASK_DM5)
- pkt_size = HCI_DM5_PACKET_SIZE;
- else if (pkt_types & HCI_PKT_TYPES_MASK_DH3)
- pkt_size = HCI_DH3_PACKET_SIZE;
- else if (pkt_types & HCI_PKT_TYPES_MASK_DM3)
- pkt_size = HCI_DM3_PACKET_SIZE;
- else if (!(pkt_types & HCI_PKT_TYPES_MASK_NO_3_DH1))
- pkt_size = HCI_EDR3_DH1_PACKET_SIZE;
- else if (!(pkt_types & HCI_PKT_TYPES_MASK_NO_2_DH1))
- pkt_size = HCI_EDR2_DH1_PACKET_SIZE;
- else if (pkt_types & HCI_PKT_TYPES_MASK_DH1)
- pkt_size = HCI_DH1_PACKET_SIZE;
- else if (pkt_types & HCI_PKT_TYPES_MASK_DM1)
- pkt_size = HCI_DM1_PACKET_SIZE;
- }
-
- return (pkt_size);
-}
-
-/*******************************************************************************
- *
- * Function BTM_ReadRemoteVersion
- *
- * Returns If connected report peer device info
- *
- ******************************************************************************/
-bool BTM_ReadRemoteVersion(const RawAddress& addr, uint8_t* lmp_version,
- uint16_t* manufacturer, uint16_t* lmp_sub_version) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_ReadRemoteVersion(
- addr, lmp_version, manufacturer, lmp_sub_version);
- }
-
- const tACL_CONN* p_acl = internal_.btm_bda_to_acl(addr, BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- p_acl = internal_.btm_bda_to_acl(addr, BT_TRANSPORT_LE);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return false;
- }
- }
-
- if (!p_acl->remote_version_info.valid) {
- LOG_WARN("Remote version information is invalid");
- return false;
- }
-
- if (lmp_version) *lmp_version = p_acl->remote_version_info.lmp_version;
-
- if (manufacturer) *manufacturer = p_acl->remote_version_info.manufacturer;
-
- if (lmp_sub_version)
- *lmp_sub_version = p_acl->remote_version_info.lmp_subversion;
-
- return true;
-}
-
-/*******************************************************************************
- *
- * Function BTM_ReadRemoteFeatures
- *
- * Returns pointer to the remote supported features mask (8 bytes)
- *
- ******************************************************************************/
-uint8_t* BTM_ReadRemoteFeatures(const RawAddress& addr) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_ReadRemoteFeatures(addr);
- }
- tACL_CONN* p = internal_.btm_bda_to_acl(addr, BT_TRANSPORT_BR_EDR);
- if (p == NULL) {
- LOG_WARN("Unable to find active acl");
- return (NULL);
- }
-
- return (p->peer_lmp_feature_pages[0]);
-}
-
-/*******************************************************************************
- *
- * Function BTM_ReadRSSI
- *
- * Description This function is called to read the link policy settings.
- * The address of link policy results are returned in the
- * callback.
- * (tBTM_RSSI_RESULT)
- *
- * Returns BTM_CMD_STARTED if successfully initiated or error code
- *
- ******************************************************************************/
-tBTM_STATUS BTM_ReadRSSI(const RawAddress& remote_bda, tBTM_CMPL_CB* p_cb) {
- tACL_CONN* p = NULL;
- tBT_DEVICE_TYPE dev_type;
- tBLE_ADDR_TYPE addr_type;
-
- /* If someone already waiting on the version, do not allow another */
- if (btm_cb.devcb.p_rssi_cmpl_cb) return (BTM_BUSY);
-
- BTM_ReadDevInfo(remote_bda, &dev_type, &addr_type);
-
- if (dev_type & BT_DEVICE_TYPE_BLE) {
- p = internal_.btm_bda_to_acl(remote_bda, BT_TRANSPORT_LE);
- }
-
- if (p == NULL && dev_type & BT_DEVICE_TYPE_BREDR) {
- p = internal_.btm_bda_to_acl(remote_bda, BT_TRANSPORT_BR_EDR);
- }
-
- if (p) {
- btm_cb.devcb.p_rssi_cmpl_cb = p_cb;
- alarm_set_on_mloop(btm_cb.devcb.read_rssi_timer, BTM_DEV_REPLY_TIMEOUT_MS,
- btm_read_rssi_timeout, NULL);
-
- btsnd_hcic_read_rssi(p->hci_handle);
- return (BTM_CMD_STARTED);
- }
- LOG_WARN("Unable to find active acl");
-
- /* If here, no BD Addr found */
- return (BTM_UNKNOWN_ADDR);
-}
-
-/*******************************************************************************
- *
- * Function BTM_ReadFailedContactCounter
- *
- * Description This function is called to read the failed contact counter.
- * The result is returned in the callback.
- * (tBTM_FAILED_CONTACT_COUNTER_RESULT)
- *
- * Returns BTM_CMD_STARTED if successfully initiated or error code
- *
- ******************************************************************************/
-tBTM_STATUS BTM_ReadFailedContactCounter(const RawAddress& remote_bda,
- tBTM_CMPL_CB* p_cb) {
- tACL_CONN* p;
- tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
- tBT_DEVICE_TYPE dev_type;
- tBLE_ADDR_TYPE addr_type;
-
- /* If someone already waiting on the result, do not allow another */
- if (btm_cb.devcb.p_failed_contact_counter_cmpl_cb) return (BTM_BUSY);
-
- BTM_ReadDevInfo(remote_bda, &dev_type, &addr_type);
- if (dev_type == BT_DEVICE_TYPE_BLE) transport = BT_TRANSPORT_LE;
-
- p = internal_.btm_bda_to_acl(remote_bda, transport);
- if (p != (tACL_CONN*)NULL) {
- btm_cb.devcb.p_failed_contact_counter_cmpl_cb = p_cb;
- alarm_set_on_mloop(btm_cb.devcb.read_failed_contact_counter_timer,
- BTM_DEV_REPLY_TIMEOUT_MS,
- btm_read_failed_contact_counter_timeout, NULL);
-
- btsnd_hcic_read_failed_contact_counter(p->hci_handle);
- return (BTM_CMD_STARTED);
- }
- LOG_WARN("Unable to find active acl");
-
- /* If here, no BD Addr found */
- return (BTM_UNKNOWN_ADDR);
-}
-
-/*******************************************************************************
- *
- * Function BTM_ReadTxPower
- *
- * Description This function is called to read the current
- * TX power of the connection. The tx power level results
- * are returned in the callback.
- * (tBTM_RSSI_RESULT)
- *
- * Returns BTM_CMD_STARTED if successfully initiated or error code
- *
- ******************************************************************************/
-tBTM_STATUS BTM_ReadTxPower(const RawAddress& remote_bda,
- tBT_TRANSPORT transport, tBTM_CMPL_CB* p_cb) {
- tACL_CONN* p;
-#define BTM_READ_RSSI_TYPE_CUR 0x00
-#define BTM_READ_RSSI_TYPE_MAX 0X01
-
- VLOG(2) << __func__ << ": RemBdAddr: " << remote_bda;
-
- /* If someone already waiting on the version, do not allow another */
- if (btm_cb.devcb.p_tx_power_cmpl_cb) return (BTM_BUSY);
-
- p = internal_.btm_bda_to_acl(remote_bda, transport);
- if (p != (tACL_CONN*)NULL) {
- btm_cb.devcb.p_tx_power_cmpl_cb = p_cb;
- alarm_set_on_mloop(btm_cb.devcb.read_tx_power_timer,
- BTM_DEV_REPLY_TIMEOUT_MS, btm_read_tx_power_timeout,
- NULL);
-
- if (p->transport == BT_TRANSPORT_LE) {
- btm_cb.devcb.read_tx_pwr_addr = remote_bda;
- btsnd_hcic_ble_read_adv_chnl_tx_power();
- } else {
- btsnd_hcic_read_tx_power(p->hci_handle, BTM_READ_RSSI_TYPE_CUR);
- }
-
- return (BTM_CMD_STARTED);
- }
-
- LOG_WARN("Unable to find active acl");
-
- /* If here, no BD Addr found */
- return (BTM_UNKNOWN_ADDR);
-}
-
-/*******************************************************************************
- *
- * Function btm_read_tx_power_timeout
- *
- * Description Callback when reading the tx power times out.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_tx_power_timeout(UNUSED_ATTR void* data) {
- tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_tx_power_cmpl_cb;
- btm_cb.devcb.p_tx_power_cmpl_cb = NULL;
- if (p_cb) (*p_cb)((void*)NULL);
-}
-
-/*******************************************************************************
- *
- * Function btm_read_tx_power_complete
- *
- * Description This function is called when the command complete message
- * is received from the HCI for the read tx power request.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_tx_power_complete(uint8_t* p, bool is_ble) {
- tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_tx_power_cmpl_cb;
- tBTM_TX_POWER_RESULT result;
-
- alarm_cancel(btm_cb.devcb.read_tx_power_timer);
- btm_cb.devcb.p_tx_power_cmpl_cb = NULL;
-
- /* If there was a registered callback, call it */
- if (p_cb) {
- STREAM_TO_UINT8(result.hci_status, p);
-
- if (result.hci_status == HCI_SUCCESS) {
- result.status = BTM_SUCCESS;
-
- if (!is_ble) {
- uint16_t handle;
- STREAM_TO_UINT16(handle, p);
- STREAM_TO_UINT8(result.tx_power, p);
-
- tACL_CONN* p_acl_cb = internal_.acl_get_connection_from_handle(handle);
- if (p_acl_cb != nullptr) {
- result.rem_bda = p_acl_cb->remote_addr;
- }
- } else {
- STREAM_TO_UINT8(result.tx_power, p);
- result.rem_bda = btm_cb.devcb.read_tx_pwr_addr;
- }
- LOG_DEBUG("Transmit power complete: tx_power:%d hci status:%s",
- result.tx_power,
- hci_error_code_text(static_cast<tHCI_STATUS>(result.hci_status))
- .c_str());
- } else {
- result.status = BTM_ERR_PROCESSING;
- }
-
- (*p_cb)(&result);
- }
-}
-
-/*******************************************************************************
- *
- * Function btm_read_rssi_timeout
- *
- * Description Callback when reading the RSSI times out.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_rssi_timeout(UNUSED_ATTR void* data) {
- tBTM_RSSI_RESULT result;
- tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_rssi_cmpl_cb;
- btm_cb.devcb.p_rssi_cmpl_cb = NULL;
- result.status = BTM_DEVICE_TIMEOUT;
- if (p_cb) (*p_cb)(&result);
-}
-
-/*******************************************************************************
- *
- * Function btm_read_rssi_complete
- *
- * Description This function is called when the command complete message
- * is received from the HCI for the read rssi request.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_rssi_complete(uint8_t* p) {
- tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_rssi_cmpl_cb;
- tBTM_RSSI_RESULT result;
-
- alarm_cancel(btm_cb.devcb.read_rssi_timer);
- btm_cb.devcb.p_rssi_cmpl_cb = NULL;
-
- /* If there was a registered callback, call it */
- if (p_cb) {
- STREAM_TO_UINT8(result.hci_status, p);
- result.status = BTM_ERR_PROCESSING;
-
- if (result.hci_status == HCI_SUCCESS) {
- uint16_t handle;
- STREAM_TO_UINT16(handle, p);
-
- STREAM_TO_UINT8(result.rssi, p);
- LOG_DEBUG("Read rrsi complete rssi:%hhd hci status:%s", result.rssi,
- hci_error_code_text(static_cast<tHCI_STATUS>(result.hci_status))
- .c_str());
-
- tACL_CONN* p_acl_cb = internal_.acl_get_connection_from_handle(handle);
- if (p_acl_cb != nullptr) {
- result.rem_bda = p_acl_cb->remote_addr;
- result.status = BTM_SUCCESS;
- }
- }
- (*p_cb)(&result);
- }
-}
-
-/*******************************************************************************
- *
- * Function btm_read_failed_contact_counter_timeout
- *
- * Description Callback when reading the failed contact counter times out.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_failed_contact_counter_timeout(UNUSED_ATTR void* data) {
- tBTM_FAILED_CONTACT_COUNTER_RESULT result;
- tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_failed_contact_counter_cmpl_cb;
- btm_cb.devcb.p_failed_contact_counter_cmpl_cb = NULL;
- result.status = BTM_DEVICE_TIMEOUT;
- if (p_cb) (*p_cb)(&result);
-}
-
-/*******************************************************************************
- *
- * Function btm_read_failed_contact_counter_complete
- *
- * Description This function is called when the command complete message
- * is received from the HCI for the read failed contact
- * counter request.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_failed_contact_counter_complete(uint8_t* p) {
- tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_failed_contact_counter_cmpl_cb;
- tBTM_FAILED_CONTACT_COUNTER_RESULT result;
-
- alarm_cancel(btm_cb.devcb.read_failed_contact_counter_timer);
- btm_cb.devcb.p_failed_contact_counter_cmpl_cb = NULL;
-
- /* If there was a registered callback, call it */
- if (p_cb) {
- uint16_t handle;
- STREAM_TO_UINT8(result.hci_status, p);
-
- if (result.hci_status == HCI_SUCCESS) {
- result.status = BTM_SUCCESS;
-
- STREAM_TO_UINT16(handle, p);
-
- STREAM_TO_UINT16(result.failed_contact_counter, p);
- LOG_DEBUG(
- "Failed contact counter complete: counter %u, hci status:%s",
- result.failed_contact_counter,
- hci_status_code_text(to_hci_status_code(result.hci_status)).c_str());
-
- tACL_CONN* p_acl_cb = internal_.acl_get_connection_from_handle(handle);
- if (p_acl_cb != nullptr) {
- result.rem_bda = p_acl_cb->remote_addr;
- }
- } else {
- result.status = BTM_ERR_PROCESSING;
- }
-
- (*p_cb)(&result);
- }
-}
-
-/*******************************************************************************
- *
- * Function btm_read_automatic_flush_timeout_complete
- *
- * Description This function is called when the command complete message
- * is received from the HCI for the read automatic flush
- * timeout request.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_automatic_flush_timeout_complete(uint8_t* p) {
- tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_automatic_flush_timeout_cmpl_cb;
- tBTM_AUTOMATIC_FLUSH_TIMEOUT_RESULT result;
-
- alarm_cancel(btm_cb.devcb.read_automatic_flush_timeout_timer);
- btm_cb.devcb.p_automatic_flush_timeout_cmpl_cb = nullptr;
-
- /* If there was a registered callback, call it */
- if (p_cb) {
- uint16_t handle;
- STREAM_TO_UINT8(result.hci_status, p);
- result.status = BTM_ERR_PROCESSING;
-
- if (result.hci_status == HCI_SUCCESS) {
- result.status = BTM_SUCCESS;
-
- STREAM_TO_UINT16(handle, p);
- STREAM_TO_UINT16(result.automatic_flush_timeout, p);
- LOG_DEBUG(
- "Read automatic flush timeout complete timeout:%hu hci_status:%s",
- result.automatic_flush_timeout,
- hci_error_code_text(static_cast<tHCI_STATUS>(result.hci_status))
- .c_str());
-
- tACL_CONN* p_acl_cb = internal_.acl_get_connection_from_handle(handle);
- if (p_acl_cb != nullptr) {
- result.rem_bda = p_acl_cb->remote_addr;
- }
- }
- (*p_cb)(&result);
- }
-}
-
-/*******************************************************************************
- *
- * Function btm_read_link_quality_timeout
- *
- * Description Callback when reading the link quality times out.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_link_quality_timeout(UNUSED_ATTR void* data) {
- tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_link_qual_cmpl_cb;
- btm_cb.devcb.p_link_qual_cmpl_cb = NULL;
- if (p_cb) (*p_cb)((void*)NULL);
-}
-
-/*******************************************************************************
- *
- * Function btm_read_link_quality_complete
- *
- * Description This function is called when the command complete message
- * is received from the HCI for the read link quality.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_link_quality_complete(uint8_t* p) {
- tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_link_qual_cmpl_cb;
- tBTM_LINK_QUALITY_RESULT result;
-
- alarm_cancel(btm_cb.devcb.read_link_quality_timer);
- btm_cb.devcb.p_link_qual_cmpl_cb = NULL;
-
- /* If there was a registered callback, call it */
- if (p_cb) {
- STREAM_TO_UINT8(result.hci_status, p);
-
- if (result.hci_status == HCI_SUCCESS) {
- uint16_t handle;
- result.status = BTM_SUCCESS;
-
- STREAM_TO_UINT16(handle, p);
-
- STREAM_TO_UINT8(result.link_quality, p);
- LOG_DEBUG("BTM Link Quality Complete: Link Quality %d, hci status:%s",
- result.link_quality,
- hci_error_code_text(static_cast<tHCI_STATUS>(result.hci_status))
- .c_str());
-
- tACL_CONN* p_acl_cb = internal_.acl_get_connection_from_handle(handle);
- if (p_acl_cb != nullptr) {
- result.rem_bda = p_acl_cb->remote_addr;
- }
- } else {
- result.status = BTM_ERR_PROCESSING;
- }
-
- (*p_cb)(&result);
- }
-}
-
-/*******************************************************************************
- *
- * Function btm_remove_acl
- *
- * Description This function is called to disconnect an ACL connection
- *
- * Returns BTM_SUCCESS if successfully initiated, otherwise
- * BTM_NO_RESOURCES.
- *
- ******************************************************************************/
-tBTM_STATUS btm_remove_acl(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- if (transport == BT_TRANSPORT_LE) {
- LOG(ERROR) << __func__ << ": Unsupported";
- }
- bluetooth::shim::L2CA_DisconnectLink(bd_addr);
- return BTM_SUCCESS;
- }
-
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(bd_addr, transport);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return BTM_UNKNOWN_ADDR;
- }
-
- if (p_acl->Handle() == HCI_INVALID_HANDLE) {
- LOG_WARN("Cannot remove unknown acl bd_addr:%s transport:%s",
- PRIVATE_ADDRESS(bd_addr), bt_transport_text(transport).c_str());
- return BTM_UNKNOWN_ADDR;
- }
-
- if (p_acl->rs_disc_pending == BTM_SEC_RS_PENDING) {
- LOG_DEBUG(
- "Delay disconnect until role switch is complete bd_addr:%s "
- "transport:%s",
- PRIVATE_ADDRESS(bd_addr), bt_transport_text(transport).c_str());
- p_acl->rs_disc_pending = BTM_SEC_DISC_PENDING;
- return BTM_SUCCESS;
- }
-
- hci_btsnd_hcic_disconnect(*p_acl, HCI_ERR_PEER_USER);
- return BTM_SUCCESS;
-}
-
-/*******************************************************************************
- *
- * Function BTM_SetTraceLevel
- *
- * Description This function sets the trace level for BTM. If called with
- * a value of 0xFF, it simply returns the current trace level.
- *
- * Returns The new or current trace level
- *
- ******************************************************************************/
-uint8_t BTM_SetTraceLevel(uint8_t new_level) {
- if (new_level != 0xFF) btm_cb.trace_level = new_level;
-
- return (btm_cb.trace_level);
-}
-
-void btm_cont_rswitch_from_handle(uint16_t hci_handle) {
- tACL_CONN* p = internal_.acl_get_connection_from_handle(hci_handle);
- if (p == nullptr) {
- LOG_WARN("Role switch received but with no active ACL");
- return;
- }
-
- /* Check to see if encryption needs to be turned off if pending
- change of link key or role switch */
- if (p->is_switch_role_mode_change()) {
- /* Must turn off Encryption first if necessary */
- /* Some devices do not support switch or change of link key while encryption
- * is on */
- if (p->is_encrypted && !IsEprAvailable(*p)) {
- p->set_encryption_off();
- if (p->is_switch_role_mode_change()) {
- p->set_switch_role_encryption_off();
- }
- } else /* Encryption not used or EPR supported, continue with switch
- and/or change of link key */
- {
- if (p->is_switch_role_mode_change()) {
- internal_.hci_start_role_switch_to_central(*p);
- }
- }
- }
-}
-
-/*******************************************************************************
- *
- * Function btm_acl_resubmit_page
- *
- * Description send pending page request
- *
- ******************************************************************************/
-void btm_acl_resubmit_page(void) {
- BT_HDR* p_buf;
- uint8_t* pp;
- /* If there were other page request schedule can start the next one */
- p_buf = (BT_HDR*)fixed_queue_try_dequeue(btm_cb.page_queue);
- if (p_buf != NULL) {
- /* skip 3 (2 bytes opcode and 1 byte len) to get to the bd_addr
- * for both create_conn and rmt_name */
- pp = (uint8_t*)(p_buf + 1) + p_buf->offset + 3;
-
- RawAddress bda;
- STREAM_TO_BDADDR(bda, pp);
-
- btm_cb.connecting_bda = bda;
- memcpy(btm_cb.connecting_dc, btm_get_dev_class(bda), DEV_CLASS_LEN);
-
- btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p_buf);
- } else {
- btm_cb.paging = false;
- }
-}
-
-/*******************************************************************************
- *
- * Function btm_acl_reset_paging
- *
- * Description set paging to false and free the page queue - called at
- * hci_reset
- *
- ******************************************************************************/
-void btm_acl_reset_paging(void) {
- BT_HDR* p;
- /* If we sent reset we are definitely not paging any more */
- while ((p = (BT_HDR*)fixed_queue_try_dequeue(btm_cb.page_queue)) != NULL)
- osi_free(p);
-
- btm_cb.paging = false;
-}
-
-/*******************************************************************************
- *
- * Function btm_acl_paging
- *
- * Description send a paging command or queue it in btm_cb
- *
- ******************************************************************************/
-void btm_acl_paging(BT_HDR* p, const RawAddress& bda) {
- // This function is called by the device initiating the connection.
- // If no role change is requested from the remote device, we want
- // to classify the connection initiator as the central device.
- if (delayed_role_change_ == nullptr) {
- RoleChangeView role_change;
- role_change.bd_addr = bda;
- role_change.new_role = HCI_ROLE_CENTRAL;
- delayed_role_change_ =
- std::make_unique<RoleChangeView>(std::move(role_change));
- }
- if (!BTM_IsAclConnectionUp(bda, BT_TRANSPORT_BR_EDR)) {
- VLOG(1) << "connecting_bda: " << btm_cb.connecting_bda;
- if (btm_cb.paging && bda == btm_cb.connecting_bda) {
- fixed_queue_enqueue(btm_cb.page_queue, p);
- } else {
- btm_cb.connecting_bda = bda;
- memcpy(btm_cb.connecting_dc, btm_get_dev_class(bda), DEV_CLASS_LEN);
-
- btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
- }
-
- btm_cb.paging = true;
- } else /* ACL is already up */
- {
- btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
- }
-}
-
-/*******************************************************************************
- *
- * Function btm_acl_notif_conn_collision
- *
- * Description Send connection collision event to upper layer if registered
- *
- *
- ******************************************************************************/
-void btm_acl_notif_conn_collision(const RawAddress& bda) {
- do_in_main_thread(FROM_HERE, base::Bind(bta_sys_notify_collision, bda));
-}
-
-bool BTM_BLE_IS_RESOLVE_BDA(const RawAddress& x) {
- return ((x.address)[0] & BLE_RESOLVE_ADDR_MASK) == BLE_RESOLVE_ADDR_MSB;
-}
-
-bool acl_refresh_remote_address(const RawAddress& identity_address,
- tBLE_ADDR_TYPE identity_address_type,
- const RawAddress& bda, tBLE_ADDR_TYPE rra_type,
- const RawAddress& rpa) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(bda, BT_TRANSPORT_LE);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return false;
- }
-
- if (rra_type == tBTM_SEC_BLE::BTM_BLE_ADDR_PSEUDO) {
- /* use identity address, resolvable_private_addr is empty */
- if (rpa.IsEmpty()) {
- p_acl->active_remote_addr_type = identity_address_type;
- p_acl->active_remote_addr = identity_address;
- } else {
- p_acl->active_remote_addr_type = BLE_ADDR_RANDOM;
- p_acl->active_remote_addr = rpa;
- }
- } else {
- p_acl->active_remote_addr_type = rra_type;
- p_acl->active_remote_addr = rpa;
- }
-
- LOG_DEBUG("active_remote_addr_type: %d ", p_acl->active_remote_addr_type);
- return true;
-}
-
-bool acl_peer_supports_ble_connection_parameters_request(
- const RawAddress& remote_bda) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(remote_bda, BT_TRANSPORT_LE);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return false;
- }
- if (!p_acl->peer_le_features_valid) {
- LOG_WARN(
- "Checking remote features but remote feature read is "
- "incomplete");
- }
- return HCI_LE_CONN_PARAM_REQ_SUPPORTED(p_acl->peer_le_features);
-}
-
-bool acl_peer_supports_sniff_subrating(const RawAddress& remote_bda) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(remote_bda, BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return false;
- }
- if (!p_acl->peer_lmp_feature_valid[0]) {
- LOG_WARN(
- "Checking remote features but remote feature read is "
- "incomplete");
- }
- return HCI_SNIFF_SUB_RATE_SUPPORTED(p_acl->peer_lmp_feature_pages[0]);
-}
-
-/*******************************************************************************
- *
- * Function BTM_ReadConnectionAddr
- *
- * Description This function is called to get the local device address
- * information.
- *
- * Returns void
- *
- ******************************************************************************/
-void BTM_ReadConnectionAddr(const RawAddress& remote_bda,
- RawAddress& local_conn_addr,
- tBLE_ADDR_TYPE* p_addr_type) {
- if (bluetooth::shim::is_gd_shim_enabled()) {
- return bluetooth::shim::BTM_ReadConnectionAddr(remote_bda, local_conn_addr,
- p_addr_type);
- }
-
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- bluetooth::shim::L2CA_ReadConnectionAddr(remote_bda, local_conn_addr,
- p_addr_type);
- return;
- } else if (bluetooth::shim::is_gd_scanning_enabled()) {
- bluetooth::shim::ACL_ReadConnectionAddress(remote_bda, local_conn_addr,
- p_addr_type);
- return;
- }
-
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(remote_bda, BT_TRANSPORT_LE);
-
- if (p_acl == NULL) {
- LOG_WARN("Unable to find active acl");
- return;
- }
- local_conn_addr = p_acl->conn_addr;
- *p_addr_type = p_acl->conn_addr_type;
-
- LOG_DEBUG("BTM_ReadConnectionAddr address type: %d addr: 0x%02x",
- p_acl->conn_addr_type, p_acl->conn_addr.address[0]);
-}
-
-/*******************************************************************************
- *
- * Function BTM_IsBleConnection
- *
- * Description This function is called to check if the connection handle
- * for an LE link
- *
- * Returns true if connection is LE link, otherwise false.
- *
- ******************************************************************************/
-bool BTM_IsBleConnection(uint16_t hci_handle) {
- if (bluetooth::shim::is_gd_shim_enabled()) {
- ASSERT_LOG(false, "This should not be invoked from code path");
- }
-
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_IsLeLink(hci_handle);
- }
-
- const tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(hci_handle);
- if (p_acl == nullptr) return false;
- return p_acl->is_transport_ble();
-}
-
-const RawAddress acl_address_from_handle(uint16_t handle) {
- tACL_CONN* p_acl = acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- return RawAddress::kEmpty;
- }
- return p_acl->remote_addr;
-}
-
-/*******************************************************************************
- *
- * Function btm_ble_refresh_local_resolvable_private_addr
- *
- * Description This function refresh the currently used resolvable private
- * address for the active link to the remote device
- *
- ******************************************************************************/
-void btm_ble_refresh_local_resolvable_private_addr(
- const RawAddress& pseudo_addr, const RawAddress& local_rpa) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(pseudo_addr, BT_TRANSPORT_LE);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
-
- if (btm_cb.ble_ctr_cb.privacy_mode == BTM_PRIVACY_NONE) {
- p_acl->conn_addr_type = BLE_ADDR_PUBLIC;
- p_acl->conn_addr = *controller_get_interface()->get_address();
- } else {
- p_acl->conn_addr_type = BLE_ADDR_RANDOM;
- if (local_rpa.IsEmpty()) {
- p_acl->conn_addr = btm_cb.ble_ctr_cb.addr_mgnt_cb.private_addr;
- } else {
- p_acl->conn_addr = local_rpa;
- }
- }
-}
-
-bool sco_peer_supports_esco_2m_phy(const RawAddress& remote_bda) {
- uint8_t* features = BTM_ReadRemoteFeatures(remote_bda);
- if (features == nullptr) {
- LOG_WARN(
- "Checking remote features but remote feature read is "
- "incomplete");
- return false;
- }
- return HCI_EDR_ESCO_2MPS_SUPPORTED(features);
-}
-
-bool sco_peer_supports_esco_3m_phy(const RawAddress& remote_bda) {
- uint8_t* features = BTM_ReadRemoteFeatures(remote_bda);
- if (features == nullptr) {
- LOG_WARN(
- "Checking remote features but remote feature read is "
- "incomplete");
- return false;
- }
- return HCI_EDR_ESCO_3MPS_SUPPORTED(features);
-}
-
-bool acl_is_switch_role_idle(const RawAddress& bd_addr,
- tBT_TRANSPORT transport) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(bd_addr, transport);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return false;
- }
- return p_acl->is_switch_role_idle();
-}
-
-/*******************************************************************************
- *
- * Function BTM_ReadRemoteConnectionAddr
- *
- * Description This function is read the remote device address currently used
- *
- * Parameters pseudo_addr: pseudo random address available
- * conn_addr:connection address used
- * p_addr_type : BD Address type, Public or Random of the address
- * used
- *
- * Returns bool, true if connection to remote device exists, else false
- *
- ******************************************************************************/
-bool BTM_ReadRemoteConnectionAddr(const RawAddress& pseudo_addr,
- RawAddress& conn_addr,
- tBLE_ADDR_TYPE* p_addr_type) {
- if (bluetooth::shim::is_gd_shim_enabled()) {
- return bluetooth::shim::BTM_ReadRemoteConnectionAddr(pseudo_addr, conn_addr,
- p_addr_type);
- }
-
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_ReadRemoteConnectionAddr(
- pseudo_addr, conn_addr, p_addr_type);
- }
-
- bool st = true;
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(pseudo_addr, BT_TRANSPORT_LE);
-
- if (p_acl == NULL) {
- LOG_WARN("Unable to find active acl");
- return false;
- }
-
- conn_addr = p_acl->active_remote_addr;
- *p_addr_type = p_acl->active_remote_addr_type;
- return st;
-}
-
-uint8_t acl_link_role_from_handle(uint16_t handle) {
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- return HCI_ROLE_UNKNOWN;
- }
- return p_acl->link_role;
-}
-
-bool acl_peer_supports_ble_packet_extension(uint16_t hci_handle) {
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(hci_handle);
- if (p_acl == nullptr) {
- return false;
- }
- if (!p_acl->peer_le_features_valid) {
- LOG_WARN(
- "Checking remote features but remote feature read is "
- "incomplete");
- }
- return HCI_LE_DATA_LEN_EXT_SUPPORTED(p_acl->peer_le_features);
-}
-
-bool acl_peer_supports_ble_2m_phy(uint16_t hci_handle) {
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(hci_handle);
- if (p_acl == nullptr) {
- return false;
- }
- if (!p_acl->peer_le_features_valid) {
- LOG_WARN(
- "Checking remote features but remote feature read is "
- "incomplete");
- }
- return HCI_LE_2M_PHY_SUPPORTED(p_acl->peer_le_features);
-}
-
-bool acl_peer_supports_ble_coded_phy(uint16_t hci_handle) {
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(hci_handle);
- if (p_acl == nullptr) {
- return false;
- }
- if (!p_acl->peer_le_features_valid) {
- LOG_WARN(
- "Checking remote features but remote feature read is "
- "incomplete");
- return false;
- }
- return HCI_LE_CODED_PHY_SUPPORTED(p_acl->peer_le_features);
-}
-
-void acl_set_disconnect_reason(tHCI_STATUS acl_disc_reason) {
- btm_cb.acl_cb_.set_disconnect_reason(acl_disc_reason);
-}
-
-bool acl_is_role_switch_allowed() {
- return btm_cb.acl_cb_.DefaultLinkPolicy() &
- HCI_ENABLE_CENTRAL_PERIPHERAL_SWITCH;
-}
-
-uint16_t acl_get_supported_packet_types() {
- return btm_cb.acl_cb_.DefaultPacketTypes();
-}
-
-bool acl_set_peer_le_features_from_handle(uint16_t hci_handle,
- const uint8_t* p) {
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(hci_handle);
- if (p_acl == nullptr) {
- return false;
- }
- STREAM_TO_ARRAY(p_acl->peer_le_features, p, BD_FEATURES_LEN);
- p_acl->peer_le_features_valid = true;
- LOG_DEBUG("Completed le feature read request");
- return true;
-}
-
-void on_acl_br_edr_connected(const RawAddress& bda, uint16_t handle,
- uint8_t enc_mode) {
- if (delayed_role_change_ != nullptr && delayed_role_change_->bd_addr == bda) {
- btm_sec_connected(bda, handle, HCI_SUCCESS, enc_mode,
- delayed_role_change_->new_role);
- } else {
- btm_sec_connected(bda, handle, HCI_SUCCESS, enc_mode);
- }
- delayed_role_change_ = nullptr;
- btm_acl_set_paging(false);
- l2c_link_hci_conn_comp(HCI_SUCCESS, handle, bda);
- constexpr uint16_t link_supervision_timeout = 8000;
- BTM_SetLinkSuperTout(bda, link_supervision_timeout);
-
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
-
- /*
- * The legacy code path informs the upper layer via the BTA
- * layer after all relevant read_remote_ commands are complete.
- * The GD code path has ownership of the read_remote_ commands
- * and thus may inform the upper layers about the connection.
- */
- if (bluetooth::shim::is_gd_acl_enabled()) {
- NotifyAclLinkUp(*p_acl);
- }
-}
-
-void on_acl_br_edr_failed(const RawAddress& bda, tHCI_STATUS status) {
- ASSERT_LOG(status != HCI_SUCCESS,
- "Successful connection entering failing code path");
- if (delayed_role_change_ != nullptr && delayed_role_change_->bd_addr == bda) {
- btm_sec_connected(bda, HCI_INVALID_HANDLE, status, false,
- delayed_role_change_->new_role);
- } else {
- btm_sec_connected(bda, HCI_INVALID_HANDLE, status, false);
- }
- delayed_role_change_ = nullptr;
- btm_acl_set_paging(false);
- l2c_link_hci_conn_comp(status, HCI_INVALID_HANDLE, bda);
-}
-
-void btm_acl_connected(const RawAddress& bda, uint16_t handle,
- tHCI_STATUS status, uint8_t enc_mode) {
- switch (status) {
- case HCI_SUCCESS:
- return on_acl_br_edr_connected(bda, handle, enc_mode);
- default:
- return on_acl_br_edr_failed(bda, status);
- }
-}
-
-void btm_acl_disconnected(tHCI_STATUS status, uint16_t handle,
- tHCI_REASON reason) {
- if (status != HCI_SUCCESS) {
- LOG_WARN("Received disconnect with error:%s",
- hci_error_code_text(status).c_str());
- }
-
- /* There can be a case when we rejected PIN code authentication */
- /* otherwise save a new reason */
- if (btm_get_acl_disc_reason_code() != HCI_ERR_HOST_REJECT_SECURITY) {
- acl_set_disconnect_reason(static_cast<tHCI_STATUS>(reason));
- }
-
- /* If L2CAP or SCO doesn't know about it, send it to ISO */
- if (!l2c_link_hci_disc_comp(handle, reason) &&
- !btm_sco_removed(handle, reason)) {
- bluetooth::hci::IsoManager::GetInstance()->HandleDisconnect(handle, reason);
- }
-
- /* Notify security manager */
- btm_sec_disconnected(handle, reason);
-}
-
-constexpr uint16_t kDefaultPacketTypes =
- HCI_PKT_TYPES_MASK_DM1 | HCI_PKT_TYPES_MASK_DH1 | HCI_PKT_TYPES_MASK_DM3 |
- HCI_PKT_TYPES_MASK_DH3 | HCI_PKT_TYPES_MASK_DM5 | HCI_PKT_TYPES_MASK_DH5;
-
-void acl_create_classic_connection(const RawAddress& bd_addr,
- bool there_are_high_priority_channels,
- bool is_bonding) {
- if (bluetooth::shim::is_gd_acl_enabled()) {
- return bluetooth::shim::ACL_CreateClassicConnection(bd_addr);
- }
-
- const bool controller_supports_role_switch =
- controller_get_interface()->supports_role_switch();
- const bool acl_allows_role_switch = acl_is_role_switch_allowed();
-
- /* FW team says that we can participant in 4 piconets
- * typically 3 piconet + 1 for scanning.
- * We can enhance the code to count the number of piconets later. */
- uint8_t allow_role_switch = HCI_CR_CONN_NOT_ALLOW_SWITCH;
- if (((acl_allows_role_switch && (BTM_GetNumAclLinks() < 3)) ||
- (is_bonding && !there_are_high_priority_channels &&
- controller_supports_role_switch)))
- allow_role_switch = HCI_CR_CONN_ALLOW_SWITCH;
-
- /* Check with the BT manager if details about remote device are known */
- uint8_t page_scan_rep_mode{HCI_PAGE_SCAN_REP_MODE_R1};
- uint8_t page_scan_mode{HCI_MANDATARY_PAGE_SCAN_MODE};
- uint16_t clock_offset = BTM_GetClockOffset(bd_addr);
-
- tBTM_INQ_INFO* p_inq_info = BTM_InqDbRead(bd_addr);
- if (p_inq_info != nullptr &&
- (p_inq_info->results.inq_result_type & BTM_INQ_RESULT_BR)) {
- page_scan_rep_mode = p_inq_info->results.page_scan_rep_mode;
- page_scan_mode = p_inq_info->results.page_scan_mode;
- clock_offset = p_inq_info->results.clock_offset;
- }
-
- btsnd_hcic_create_conn(bd_addr, kDefaultPacketTypes, page_scan_rep_mode,
- page_scan_mode, clock_offset, allow_role_switch);
- btm_acl_set_paging(true);
-}
-
-void btm_acl_connection_request(const RawAddress& bda, uint8_t* dc) {
- btm_sec_conn_req(bda, dc);
- l2c_link_hci_conn_req(bda);
-}
-
-void acl_accept_connection_request(const RawAddress& bd_addr, uint8_t role) {
- btsnd_hcic_accept_conn(bd_addr, role);
-}
-
-void acl_reject_connection_request(const RawAddress& bd_addr, uint8_t reason) {
- btsnd_hcic_reject_conn(bd_addr, reason);
-}
-
-void acl_disconnect_from_handle(uint16_t handle, tHCI_STATUS reason) {
- acl_disconnect_after_role_switch(handle, reason);
-}
-
-void acl_disconnect_after_role_switch(uint16_t conn_handle,
- tHCI_STATUS reason) {
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(conn_handle);
- if (p_acl == nullptr) {
- LOG_ERROR("Sending disconnect for unknown acl:%hu PLEASE FIX", conn_handle);
- GetLegacyHciInterface().Disconnect(conn_handle, reason);
- return;
- }
-
- /* If a role switch is in progress, delay the HCI Disconnect to avoid
- * controller problem */
- if (p_acl->rs_disc_pending == BTM_SEC_RS_PENDING) {
- LOG_DEBUG(
- "Role switch in progress - Set DISC Pending flag in "
- "btm_sec_send_hci_disconnect "
- "to delay disconnect");
- p_acl->rs_disc_pending = BTM_SEC_DISC_PENDING;
- } else {
- LOG_DEBUG("Sending acl disconnect reason:%s [%hu]",
- hci_error_code_text(reason).c_str(), reason);
- hci_btsnd_hcic_disconnect(*p_acl, reason);
- }
-}
-
-constexpr uint16_t kDataPacketEventBrEdr = (BT_EVT_TO_LM_HCI_ACL);
-constexpr uint16_t kDataPacketEventBle =
- (BT_EVT_TO_LM_HCI_ACL | LOCAL_BLE_CONTROLLER_ID);
-
-void acl_send_data_packet_br_edr(const RawAddress& bd_addr, BT_HDR* p_buf) {
- if (bluetooth::shim::is_gd_acl_enabled()) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(bd_addr, BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- LOG_WARN("Acl br_edr data write for unknown device:%s",
- PRIVATE_ADDRESS(bd_addr));
- osi_free(p_buf);
- return;
- }
- return bluetooth::shim::ACL_WriteData(p_acl->hci_handle, p_buf);
- }
- bte_main_hci_send(p_buf, kDataPacketEventBrEdr);
-}
-
-void acl_send_data_packet_ble(const RawAddress& bd_addr, BT_HDR* p_buf) {
- if (bluetooth::shim::is_gd_acl_enabled()) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(bd_addr, BT_TRANSPORT_LE);
- if (p_acl == nullptr) {
- LOG_WARN("Acl le data write for unknown device:%s",
- PRIVATE_ADDRESS(bd_addr));
- osi_free(p_buf);
- return;
- }
- return bluetooth::shim::ACL_WriteData(p_acl->hci_handle, p_buf);
- }
- bte_main_hci_send(p_buf, kDataPacketEventBle);
-}
-
-void acl_write_automatic_flush_timeout(const RawAddress& bd_addr,
- uint16_t flush_timeout_in_ticks) {
- tACL_CONN* p_acl = internal_.btm_bda_to_acl(bd_addr, BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
- if (p_acl->flush_timeout_in_ticks == flush_timeout_in_ticks) {
- LOG_INFO(
- "Ignoring since cached value is same as requested flush_timeout:%hd",
- flush_timeout_in_ticks);
- return;
- }
- flush_timeout_in_ticks &= HCI_MAX_AUTOMATIC_FLUSH_TIMEOUT;
- p_acl->flush_timeout_in_ticks = flush_timeout_in_ticks;
- btsnd_hcic_write_auto_flush_tout(p_acl->hci_handle, flush_timeout_in_ticks);
-}
-
-bool acl_create_le_connection_with_id(uint8_t id, const RawAddress& bd_addr) {
- if (bluetooth::shim::is_gd_acl_enabled()) {
- tBLE_BD_ADDR address_with_type{
- .bda = bd_addr,
- .type = BLE_ADDR_RANDOM,
- };
- gatt_find_in_device_record(bd_addr, &address_with_type);
- LOG_DEBUG("Creating le connection to:%s",
- address_with_type.ToString().c_str());
- bluetooth::shim::ACL_AcceptLeConnectionFrom(address_with_type,
- /* is_direct */ true);
- return true;
- }
- return connection_manager::direct_connect_add(id, bd_addr);
-}
-
-bool acl_create_le_connection(const RawAddress& bd_addr) {
- return acl_create_le_connection_with_id(CONN_MGR_ID_L2CAP, bd_addr);
-}
-
-void acl_rcv_acl_data(BT_HDR* p_msg) {
- acl_header_t acl_header{
- .handle = HCI_INVALID_HANDLE,
- .hci_len = 0,
- };
- const uint8_t* p = (uint8_t*)(p_msg + 1) + p_msg->offset;
-
- STREAM_TO_UINT16(acl_header.handle, p);
- acl_header.handle = HCID_GET_HANDLE(acl_header.handle);
-
- STREAM_TO_UINT16(acl_header.hci_len, p);
- if (acl_header.hci_len < L2CAP_PKT_OVERHEAD ||
- acl_header.hci_len != p_msg->len - sizeof(acl_header)) {
- LOG_WARN("Received mismatched hci header length:%u data_len:%zu",
- acl_header.hci_len, p_msg->len - sizeof(acl_header));
- osi_free(p_msg);
- return;
- }
- l2c_rcv_acl_data(p_msg);
-}
-
-void acl_link_segments_xmitted(BT_HDR* p_msg) {
- l2c_link_segments_xmitted(p_msg);
-}
-
-void acl_packets_completed(uint16_t handle, uint16_t credits) {
- l2c_packets_completed(handle, credits);
-}
-
-static void acl_parse_num_completed_pkts(uint8_t* p, uint8_t evt_len) {
- if (evt_len == 0) {
- LOG_ERROR("Received num completed packets with zero length");
- return;
- }
-
- uint8_t num_handles{0};
- STREAM_TO_UINT8(num_handles, p);
-
- if (num_handles > evt_len / (2 * sizeof(uint16_t))) {
- android_errorWriteLog(0x534e4554, "141617601");
- num_handles = evt_len / (2 * sizeof(uint16_t));
- }
-
- for (uint8_t xx = 0; xx < num_handles; xx++) {
- uint16_t handle{0};
- uint16_t num_packets{0};
- STREAM_TO_UINT16(handle, p);
- handle = HCID_GET_HANDLE(handle);
- STREAM_TO_UINT16(num_packets, p);
- acl_packets_completed(handle, num_packets);
- }
-}
-
-void acl_process_num_completed_pkts(uint8_t* p, uint8_t evt_len) {
- if (bluetooth::shim::is_gd_acl_enabled()) {
- acl_parse_num_completed_pkts(p, evt_len);
- } else {
- l2c_link_process_num_completed_pkts(p, evt_len);
- }
- bluetooth::hci::IsoManager::GetInstance()->HandleNumComplDataPkts(p, evt_len);
-}
-
-void acl_process_supported_features(uint16_t handle, uint64_t features) {
- ASSERT_LOG(bluetooth::shim::is_gd_acl_enabled(),
- "Should only be called when gd_acl enabled");
-
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
- const uint8_t current_page_number = 0;
-
- memcpy(p_acl->peer_lmp_feature_pages[current_page_number],
- (uint8_t*)&features, sizeof(uint64_t));
- p_acl->peer_lmp_feature_valid[current_page_number] = true;
-
- LOG_DEBUG(
- "Copied supported feature pages handle:%hu current_page_number:%hhu "
- "features:%s",
- handle, current_page_number,
- bd_features_text(p_acl->peer_lmp_feature_pages[current_page_number])
- .c_str());
-
- if ((HCI_LMP_EXTENDED_SUPPORTED(p_acl->peer_lmp_feature_pages[0])) &&
- (controller_get_interface()
- ->supports_reading_remote_extended_features())) {
- LOG_DEBUG("Waiting for remote extended feature response to arrive");
- } else {
- LOG_DEBUG("No more remote features outstanding so notify upper layer");
- NotifyAclFeaturesReadComplete(*p_acl, current_page_number);
- }
-}
-
-void acl_process_extended_features(uint16_t handle, uint8_t current_page_number,
- uint8_t max_page_number, uint64_t features) {
- ASSERT_LOG(bluetooth::shim::is_gd_acl_enabled(),
- "Should only be called when gd_acl enabled");
-
- if (current_page_number > HCI_EXT_FEATURES_PAGE_MAX) {
- LOG_WARN("Unable to process current_page_number:%hhu", current_page_number);
- return;
- }
- tACL_CONN* p_acl = internal_.acl_get_connection_from_handle(handle);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return;
- }
- memcpy(p_acl->peer_lmp_feature_pages[current_page_number],
- (uint8_t*)&features, sizeof(uint64_t));
- p_acl->peer_lmp_feature_valid[current_page_number] = true;
-
- LOG_DEBUG(
- "Copied extended feature pages handle:%hu current_page_number:%hhu "
- "max_page_number:%hhu features:%s",
- handle, current_page_number, max_page_number,
- bd_features_text(p_acl->peer_lmp_feature_pages[current_page_number])
- .c_str());
-
- if (max_page_number == current_page_number) {
- NotifyAclFeaturesReadComplete(*p_acl, max_page_number);
- }
-}
-
-void ACL_RegisterClient(struct acl_client_callback_s* callbacks) {
- LOG_DEBUG("UNIMPLEMENTED");
-}
-
-void ACL_UnregisterClient(struct acl_client_callback_s* callbacks) {
- LOG_DEBUG("UNIMPLEMENTED");
-}
-
-bool ACL_SupportTransparentSynchronousData(const RawAddress& bd_addr) {
- const tACL_CONN* p_acl =
- internal_.btm_bda_to_acl(bd_addr, BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl");
- return false;
- }
-
- return HCI_LMP_TRANSPNT_SUPPORTED(p_acl->peer_lmp_feature_pages[0]);
-}
-
-void acl_add_to_ignore_auto_connect_after_disconnect(
- const RawAddress& bd_addr) {
- btm_cb.acl_cb_.AddToIgnoreAutoConnectAfterDisconnect(bd_addr);
-}
-
-bool acl_check_and_clear_ignore_auto_connect_after_disconnect(
- const RawAddress& bd_addr) {
- return btm_cb.acl_cb_.CheckAndClearIgnoreAutoConnectAfterDisconnect(bd_addr);
-}
-
-void acl_clear_all_ignore_auto_connect_after_disconnect() {
- btm_cb.acl_cb_.ClearAllIgnoreAutoConnectAfterDisconnect();
-}
-
-/**
- * Confusingly, immutable device features are stored in the
- * ephemeral connection data structure while connection security
- * is stored in the device record.
- *
- * This HACK allows legacy security protocols to work as intended under
- * those conditions.
- */
-void HACK_acl_check_sm4(tBTM_SEC_DEV_REC& record) {
- // Return if we already know this info
- if ((record.sm4 & BTM_SM4_TRUE) != BTM_SM4_UNKNOWN) return;
-
- tACL_CONN* p_acl =
- internal_.btm_bda_to_acl(record.RemoteAddress(), BT_TRANSPORT_BR_EDR);
- if (p_acl == nullptr) {
- LOG_WARN("Unable to find active acl for authentication device:%s",
- PRIVATE_ADDRESS(record.RemoteAddress()));
- }
-
- // If we have not received the SSP feature record
- // we have to wait
- if (!p_acl->peer_lmp_feature_valid[1]) {
- LOG_WARN(
- "Authentication started without extended feature page 1 request "
- "response");
- return;
- }
- record.sm4 = (HCI_SSP_HOST_SUPPORTED(p_acl->peer_lmp_feature_pages[1]))
- ? BTM_SM4_TRUE
- : BTM_SM4_KNOWN;
-}
diff --git a/stack/acl/btm_pm.cc b/stack/acl/btm_pm.cc
deleted file mode 100644
index a45708db9..000000000
--- a/stack/acl/btm_pm.cc
+++ /dev/null
@@ -1,919 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2000-2012 Broadcom Corporation
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-/*****************************************************************************
- *
- * This file contains functions that manages ACL link modes.
- * This includes operations such as active, hold,
- * park and sniff modes.
- *
- * This module contains both internal and external (API)
- * functions. External (API) functions are distinguishable
- * by their names beginning with uppercase BTM.
- *
- *****************************************************************************/
-
-#define LOG_TAG "bt_btm_pm"
-
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <unordered_map>
-
-#include "bt_target.h"
-#include "device/include/controller.h"
-#include "device/include/interop.h"
-#include "main/shim/dumpsys.h"
-#include "main/shim/link_policy.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/btm_status.h"
-#include "types/raw_address.h"
-
-void l2c_OnHciModeChangeSendPendingPackets(RawAddress remote);
-void btm_sco_chk_pend_unpark(tHCI_STATUS status, uint16_t handle);
-void btm_cont_rswitch_from_handle(uint16_t hci_handle);
-extern tBTM_CB btm_cb;
-
-namespace {
-uint16_t pm_pend_link = 0;
-
-std::unordered_map<uint16_t /* handle */, tBTM_PM_MCB> pm_mode_db;
-
-tBTM_PM_MCB* btm_pm_get_power_manager_from_address(const RawAddress& bda) {
- for (auto& entry : pm_mode_db) {
- if (entry.second.bda_ == bda) {
- return &entry.second;
- }
- }
- return nullptr;
-}
-
-tBTM_PM_RCB pm_reg_db; /* per application/module */
-
-uint8_t pm_pend_id = 0; /* the id pf the module, which has a pending PM cmd */
-
-constexpr char kBtmLogTag[] = "ACL";
-}
-
-/*****************************************************************************/
-/* to handle different modes */
-/*****************************************************************************/
-#define BTM_PM_NUM_SET_MODES 3 /* only hold, sniff & park */
-
-#define BTM_PM_GET_MD1 1
-#define BTM_PM_GET_MD2 2
-#define BTM_PM_GET_COMP 3
-
-const uint8_t
- btm_pm_md_comp_matrix[BTM_PM_NUM_SET_MODES * BTM_PM_NUM_SET_MODES] = {
- BTM_PM_GET_COMP, BTM_PM_GET_MD2, BTM_PM_GET_MD2,
-
- BTM_PM_GET_MD1, BTM_PM_GET_COMP, BTM_PM_GET_MD1,
-
- BTM_PM_GET_MD1, BTM_PM_GET_MD2, BTM_PM_GET_COMP};
-
-static void send_sniff_subrating(uint16_t handle, const RawAddress& addr,
- uint16_t max_lat, uint16_t min_rmt_to,
- uint16_t min_loc_to) {
- btsnd_hcic_sniff_sub_rate(handle, max_lat, min_rmt_to, min_loc_to);
- BTM_LogHistory(kBtmLogTag, addr, "Sniff subrating",
- base::StringPrintf(
- "max_latency:%.2f peer_timeout:%.2f local_timeout:%.2f",
- ticks_to_seconds(max_lat), ticks_to_seconds(min_rmt_to),
- ticks_to_seconds(min_loc_to)));
-}
-
-static tBTM_STATUS btm_pm_snd_md_req(uint16_t handle, uint8_t pm_id,
- int link_ind,
- const tBTM_PM_PWR_MD* p_mode);
-
-/*****************************************************************************/
-/* P U B L I C F U N C T I O N S */
-/*****************************************************************************/
-/*******************************************************************************
- *
- * Function BTM_PmRegister
- *
- * Description register or deregister with power manager
- *
- * Returns BTM_SUCCESS if successful,
- * BTM_NO_RESOURCES if no room to hold registration
- * BTM_ILLEGAL_VALUE
- *
- ******************************************************************************/
-tBTM_STATUS BTM_PmRegister(uint8_t mask, uint8_t* p_pm_id,
- tBTM_PM_STATUS_CBACK* p_cb) {
- if (bluetooth::shim::is_gd_link_policy_enabled()) {
- ASSERT(p_pm_id != nullptr);
- ASSERT(p_cb != nullptr);
- if (mask & BTM_PM_DEREG) {
- return (bluetooth::shim::UnregisterLinkPolicyClient(p_cb))
- ? (BTM_SUCCESS)
- : (BTM_NO_RESOURCES);
- } else {
- *p_pm_id = 0;
- return (bluetooth::shim::RegisterLinkPolicyClient(p_cb))
- ? (BTM_SUCCESS)
- : (BTM_NO_RESOURCES);
- }
- }
-
- /* de-register */
- if (mask & BTM_PM_DEREG) {
- if (*p_pm_id >= BTM_MAX_PM_RECORDS) return BTM_ILLEGAL_VALUE;
- pm_reg_db.mask = BTM_PM_REC_NOT_USED;
- return BTM_SUCCESS;
- }
-
- if (pm_reg_db.mask == BTM_PM_REC_NOT_USED) {
- /* if register for notification, should provide callback routine */
- if (p_cb == NULL) return BTM_ILLEGAL_VALUE;
- pm_reg_db.cback = p_cb;
- pm_reg_db.mask = mask;
- *p_pm_id = 0;
- return BTM_SUCCESS;
- }
-
- return BTM_NO_RESOURCES;
-}
-
-void BTM_PM_OnConnected(uint16_t handle, const RawAddress& remote_bda) {
- pm_mode_db[handle] = {};
- pm_mode_db[handle].Init(remote_bda, handle);
-}
-
-void BTM_PM_OnDisconnected(uint16_t handle) {
- pm_mode_db.erase(handle);
- if (handle == pm_pend_link) {
- pm_pend_link = 0;
- }
-}
-
-/*******************************************************************************
- *
- * Function BTM_SetPowerMode
- *
- * Description store the mode in control block or
- * alter ACL connection behavior.
- *
- * Returns BTM_SUCCESS if successful,
- * BTM_UNKNOWN_ADDR if bd addr is not active or bad
- *
- ******************************************************************************/
-tBTM_STATUS BTM_SetPowerMode(uint8_t pm_id, const RawAddress& remote_bda,
- const tBTM_PM_PWR_MD* p_mode) {
- if (pm_id >= BTM_MAX_PM_RECORDS) {
- pm_id = BTM_PM_SET_ONLY_ID;
- }
-
- if (!p_mode) {
- LOG_ERROR("pm_id: %u, p_mode is null for %s", unsigned(pm_id),
- PRIVATE_ADDRESS(remote_bda));
- return BTM_ILLEGAL_VALUE;
- }
-
- // per ACL link
- auto* p_cb = btm_pm_get_power_manager_from_address(remote_bda);
- if (p_cb == nullptr) {
- LOG_WARN("Unable to find power manager for peer: %s",
- PRIVATE_ADDRESS(remote_bda));
- return BTM_UNKNOWN_ADDR;
- }
- uint16_t handle = p_cb->handle_;
-
- tBTM_PM_MODE mode = p_mode->mode;
- if (!is_legal_power_mode(mode)) {
- LOG_ERROR("Unable to set illegal power mode value:0x%02x", mode);
- return BTM_ILLEGAL_VALUE;
- }
-
- if (p_mode->mode & BTM_PM_MD_FORCE) {
- LOG_INFO("Attempting to force into this power mode");
- /* take out the force bit */
- mode &= (~BTM_PM_MD_FORCE);
- }
-
- if (bluetooth::shim::is_gd_link_policy_enabled()) {
- tBTM_PM_PWR_MD power_mode_request = *p_mode;
- power_mode_request.mode &= (~BTM_PM_MD_FORCE);
- return bluetooth::shim::BTM_SetPowerMode(handle, power_mode_request);
- }
-
- if (mode != BTM_PM_MD_ACTIVE) {
- const controller_t* controller = controller_get_interface();
- if ((mode == BTM_PM_MD_HOLD && !controller->supports_hold_mode()) ||
- (mode == BTM_PM_MD_SNIFF && !controller->supports_sniff_mode()) ||
- (mode == BTM_PM_MD_PARK && !controller->supports_park_mode()) ||
- interop_match_addr(INTEROP_DISABLE_SNIFF, &remote_bda)) {
- LOG_ERROR("pm_id %u mode %u is not supported for %s", pm_id, mode,
- PRIVATE_ADDRESS(remote_bda));
- return BTM_MODE_UNSUPPORTED;
- }
- }
-
- if (mode == p_cb->state) {
- /* already in the requested mode and the current interval has less latency
- * than the max */
- if ((mode == BTM_PM_MD_ACTIVE) ||
- ((p_mode->mode & BTM_PM_MD_FORCE) && (p_mode->max >= p_cb->interval) &&
- (p_mode->min <= p_cb->interval)) ||
- ((p_mode->mode & BTM_PM_MD_FORCE) == 0 &&
- (p_mode->max >= p_cb->interval))) {
- LOG_INFO(
- "Device is already in requested mode %d, interval: %d, max: %d, min: "
- "%d",
- p_mode->mode, p_cb->interval, p_mode->max, p_mode->min);
- return BTM_SUCCESS;
- }
- }
-
- int temp_pm_id = pm_id;
- if (pm_id == BTM_PM_SET_ONLY_ID) {
- temp_pm_id = BTM_MAX_PM_RECORDS;
- }
-
- /* update mode database */
- if (((pm_id != BTM_PM_SET_ONLY_ID) && (pm_reg_db.mask & BTM_PM_REG_SET)) ||
- ((pm_id == BTM_PM_SET_ONLY_ID) && (pm_pend_link != 0))) {
- /* Make sure mask is set to BTM_PM_REG_SET */
- pm_reg_db.mask |= BTM_PM_REG_SET;
- *(&p_cb->req_mode) = *p_mode;
- p_cb->chg_ind = true;
- }
-
- /* if mode == hold or pending, return */
- if ((p_cb->state == BTM_PM_STS_HOLD) || (p_cb->state == BTM_PM_STS_PENDING) ||
- (pm_pend_link != 0)) {
- LOG_INFO(
- "Current power mode is hold or pending status or pending links"
- " state:%s[%hhu] pm_pending_link:%hu",
- power_mode_state_text(p_cb->state).c_str(), p_cb->state, pm_pend_link);
- /* command pending */
- if (handle != pm_pend_link) {
- p_cb->state |= BTM_PM_STORED_MASK;
- LOG_INFO("Setting stored bitmask for peer:%s",
- PRIVATE_ADDRESS(remote_bda));
- }
- return BTM_CMD_STORED;
- }
-
- LOG_INFO(
- "Setting power mode for peer:%s current_mode:%s[%hhu] new_mode:%s[%hhu]",
- PRIVATE_ADDRESS(remote_bda), power_mode_state_text(p_cb->state).c_str(),
- p_cb->state, power_mode_text(p_mode->mode).c_str(), p_mode->mode);
-
- return btm_pm_snd_md_req(p_cb->handle_, pm_id, p_cb->handle_, p_mode);
-}
-
-bool BTM_SetLinkPolicyActiveMode(const RawAddress& remote_bda) {
- tBTM_PM_PWR_MD settings;
- memset((void*)&settings, 0, sizeof(settings));
- settings.mode = BTM_PM_MD_ACTIVE;
-
- switch (BTM_SetPowerMode(BTM_PM_SET_ONLY_ID, remote_bda, &settings)) {
- case BTM_CMD_STORED:
- case BTM_SUCCESS:
- return true;
- default:
- return false;
- }
-}
-
-bool BTM_ReadPowerMode(const RawAddress& remote_bda, tBTM_PM_MODE* p_mode) {
- if (p_mode == nullptr) {
- LOG_ERROR("power mode is nullptr");
- return false;
- }
- tBTM_PM_MCB* p_mcb = btm_pm_get_power_manager_from_address(remote_bda);
- if (p_mcb == nullptr) {
- LOG_WARN("Unknown device:%s", PRIVATE_ADDRESS(remote_bda));
- return false;
- }
- *p_mode = static_cast<tBTM_PM_MODE>(p_mcb->state);
- return true;
-}
-
-/*******************************************************************************
- *
- * Function BTM_SetSsrParams
- *
- * Description This sends the given SSR parameters for the given ACL
- * connection if it is in ACTIVE mode.
- *
- * Input Param remote_bda - device address of desired ACL connection
- * max_lat - maximum latency (in 0.625ms)(0-0xFFFE)
- * min_rmt_to - minimum remote timeout
- * min_loc_to - minimum local timeout
- *
- *
- * Returns BTM_SUCCESS if the HCI command is issued successful,
- * BTM_UNKNOWN_ADDR if bd addr is not active or bad
- * BTM_CMD_STORED if the command is stored
- *
- ******************************************************************************/
-tBTM_STATUS BTM_SetSsrParams(const RawAddress& remote_bda, uint16_t max_lat,
- uint16_t min_rmt_to, uint16_t min_loc_to) {
- tBTM_PM_MCB* p_cb = btm_pm_get_power_manager_from_address(remote_bda);
- if (p_cb == nullptr) {
- LOG_WARN("Unable to find power manager for peer:%s",
- PRIVATE_ADDRESS(remote_bda));
- return BTM_UNKNOWN_ADDR;
- }
-
- if (bluetooth::shim::is_gd_link_policy_enabled()) {
- return bluetooth::shim::BTM_SetSsrParams(p_cb->handle_, max_lat, min_rmt_to,
- min_loc_to);
- }
-
- if (p_cb->state == BTM_PM_ST_ACTIVE || p_cb->state == BTM_PM_ST_SNIFF) {
- LOG_INFO(
- "Set sniff subrating state:%s[%d] max_latency:0x%04x "
- "min_remote_timeout:0x%04x"
- " min_local_timeout:0x%04x",
- power_mode_state_text(p_cb->state).c_str(), p_cb->state, max_lat,
- min_rmt_to, min_loc_to);
- send_sniff_subrating(p_cb->handle_, remote_bda, max_lat, min_rmt_to,
- min_loc_to);
- return BTM_SUCCESS;
- }
- LOG_INFO("pm_mode_db state: %d", p_cb->state);
- p_cb->max_lat = max_lat;
- p_cb->min_rmt_to = min_rmt_to;
- p_cb->min_loc_to = min_loc_to;
- return BTM_CMD_STORED;
-}
-
-/*******************************************************************************
- *
- * Function btm_pm_reset
- *
- * Description as a part of the BTM reset process.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_pm_reset(void) {
- tBTM_PM_STATUS_CBACK* cb = NULL;
-
- /* clear the pending request for application */
- if ((pm_pend_id != BTM_PM_SET_ONLY_ID) && (pm_reg_db.mask & BTM_PM_REG_SET)) {
- cb = pm_reg_db.cback;
- }
-
- pm_reg_db.mask = BTM_PM_REC_NOT_USED;
-
- if (cb != NULL && pm_pend_link != 0) {
- const RawAddress raw_address = pm_mode_db[pm_pend_link].bda_;
- (*cb)(raw_address, BTM_PM_STS_ERROR, BTM_DEV_RESET, HCI_SUCCESS);
- }
- /* no command pending */
- pm_pend_link = 0;
- pm_mode_db.clear();
- pm_pend_id = 0;
- memset(&pm_reg_db, 0, sizeof(pm_reg_db));
- LOG_INFO("reset pm");
-}
-
-/*******************************************************************************
- *
- * Function btm_pm_compare_modes
- * Description get the "more active" mode of the 2
- * Returns void
- *
- ******************************************************************************/
-static tBTM_PM_PWR_MD* btm_pm_compare_modes(const tBTM_PM_PWR_MD* p_md1,
- const tBTM_PM_PWR_MD* p_md2,
- tBTM_PM_PWR_MD* p_res) {
- uint8_t res;
-
- if (p_md1 == NULL) {
- *p_res = *p_md2;
- p_res->mode &= ~BTM_PM_MD_FORCE;
-
- return p_res;
- }
-
- if (p_md2->mode == BTM_PM_MD_ACTIVE || p_md1->mode == BTM_PM_MD_ACTIVE) {
- return NULL;
- }
-
- /* check if force bit is involved */
- if (p_md1->mode & BTM_PM_MD_FORCE) {
- *p_res = *p_md1;
- p_res->mode &= ~BTM_PM_MD_FORCE;
- return p_res;
- }
-
- if (p_md2->mode & BTM_PM_MD_FORCE) {
- *p_res = *p_md2;
- p_res->mode &= ~BTM_PM_MD_FORCE;
- return p_res;
- }
-
- res = (p_md1->mode - 1) * BTM_PM_NUM_SET_MODES + (p_md2->mode - 1);
- res = btm_pm_md_comp_matrix[res];
- switch (res) {
- case BTM_PM_GET_MD1:
- *p_res = *p_md1;
- return p_res;
-
- case BTM_PM_GET_MD2:
- *p_res = *p_md2;
- return p_res;
-
- case BTM_PM_GET_COMP:
- p_res->mode = p_md1->mode;
- /* min of the two */
- p_res->max = (p_md1->max < p_md2->max) ? (p_md1->max) : (p_md2->max);
- /* max of the two */
- p_res->min = (p_md1->min > p_md2->min) ? (p_md1->min) : (p_md2->min);
-
- /* the intersection is NULL */
- if (p_res->max < p_res->min) return NULL;
-
- if (p_res->mode == BTM_PM_MD_SNIFF) {
- /* max of the two */
- p_res->attempt = (p_md1->attempt > p_md2->attempt) ? (p_md1->attempt)
- : (p_md2->attempt);
- p_res->timeout = (p_md1->timeout > p_md2->timeout) ? (p_md1->timeout)
- : (p_md2->timeout);
- }
- return p_res;
- }
- return NULL;
-}
-
-/*******************************************************************************
- *
- * Function btm_pm_get_set_mode
- * Description get the resulting mode from the registered parties, then compare
- * it with the requested mode, if the command is from an
- * unregistered party.
- *
- * Returns void
- *
- ******************************************************************************/
-static tBTM_PM_MODE btm_pm_get_set_mode(uint8_t pm_id, tBTM_PM_MCB* p_cb,
- const tBTM_PM_PWR_MD* p_mode,
- tBTM_PM_PWR_MD* p_res) {
- tBTM_PM_PWR_MD* p_md = NULL;
-
- if (p_mode != NULL && p_mode->mode & BTM_PM_MD_FORCE) {
- *p_res = *p_mode;
- p_res->mode &= ~BTM_PM_MD_FORCE;
- return p_res->mode;
- }
-
- /* g through all the registered "set" parties */
- if (pm_reg_db.mask & BTM_PM_REG_SET) {
- if (p_cb->req_mode.mode == BTM_PM_MD_ACTIVE) {
- /* if at least one registered (SET) party says ACTIVE, stay active */
- return BTM_PM_MD_ACTIVE;
- } else {
- /* if registered parties give conflicting information, stay active */
- if ((btm_pm_compare_modes(p_md, &p_cb->req_mode, p_res)) == NULL)
- return BTM_PM_MD_ACTIVE;
- p_md = p_res;
- }
- }
-
- /* if the resulting mode is NULL(nobody registers SET), use the requested mode
- */
- if (p_md == NULL) {
- if (p_mode)
- *p_res = *((tBTM_PM_PWR_MD*)p_mode);
- else /* p_mode is NULL when btm_pm_snd_md_req is called from
- btm_pm_proc_mode_change */
- return BTM_PM_MD_ACTIVE;
- } else {
- /* if the command is from unregistered party,
- compare the resulting mode from registered party*/
- if ((pm_id == BTM_PM_SET_ONLY_ID) &&
- ((btm_pm_compare_modes(p_mode, p_md, p_res)) == NULL))
- return BTM_PM_MD_ACTIVE;
- }
-
- return p_res->mode;
-}
-
-/*******************************************************************************
- *
- * Function btm_pm_snd_md_req
- * Description get the resulting mode and send the resuest to host controller
- * Returns tBTM_STATUS
- *, bool *p_chg_ind
- ******************************************************************************/
-static tBTM_STATUS btm_pm_snd_md_req(uint16_t handle, uint8_t pm_id,
- int link_ind,
- const tBTM_PM_PWR_MD* p_mode) {
- ASSERT_LOG(pm_mode_db.count(handle) != 0,
- "Unable to find active acl for handle %d", handle);
- tBTM_PM_PWR_MD md_res;
- tBTM_PM_MODE mode;
- tBTM_PM_MCB* p_cb = &pm_mode_db[handle];
- bool chg_ind = false;
-
- mode = btm_pm_get_set_mode(pm_id, p_cb, p_mode, &md_res);
- md_res.mode = mode;
-
- LOG_DEBUG("Found controller in mode:%s", power_mode_text(mode).c_str());
-
- if (p_cb->state == mode) {
- LOG_INFO(
- "Link already in requested mode pm_id:%hhu link_ind:%d mode:%s[%hhu]",
- pm_id, link_ind, power_mode_text(mode).c_str(), mode);
-
- /* already in the resulting mode */
- if ((mode == BTM_PM_MD_ACTIVE) ||
- ((md_res.max >= p_cb->interval) && (md_res.min <= p_cb->interval))) {
- LOG_DEBUG("Storing command");
- return BTM_CMD_STORED;
- }
- LOG_DEBUG("Need to wake then sleep");
- chg_ind = true;
- }
- p_cb->chg_ind = chg_ind;
-
- /* cannot go directly from current mode to resulting mode. */
- if (mode != BTM_PM_MD_ACTIVE && p_cb->state != BTM_PM_MD_ACTIVE) {
- LOG_DEBUG("Power mode change delay required");
- p_cb->chg_ind = true; /* needs to wake, then sleep */
- }
-
- if (p_cb->chg_ind) {
- LOG_DEBUG("Need to wake first");
- md_res.mode = BTM_PM_MD_ACTIVE;
- } else if (BTM_PM_MD_SNIFF == md_res.mode && p_cb->max_lat) {
- LOG_DEBUG("Sending sniff subrating to controller");
- send_sniff_subrating(handle, p_cb->bda_, p_cb->max_lat, p_cb->min_rmt_to,
- p_cb->min_loc_to);
- p_cb->max_lat = 0;
- }
- /* Default is failure */
- pm_pend_link = 0;
-
- /* send the appropriate HCI command */
- pm_pend_id = pm_id;
-
- LOG_INFO("Switching from %s[0x%02x] to %s[0x%02x]",
- power_mode_state_text(p_cb->state).c_str(), p_cb->state,
- power_mode_state_text(md_res.mode).c_str(), md_res.mode);
- BTM_LogHistory(kBtmLogTag, p_cb->bda_, "Power mode change",
- base::StringPrintf(
- "%s[0x%02x] ==> %s[0x%02x]",
- power_mode_state_text(p_cb->state).c_str(), p_cb->state,
- power_mode_state_text(md_res.mode).c_str(), md_res.mode));
-
- switch (md_res.mode) {
- case BTM_PM_MD_ACTIVE:
- switch (p_cb->state) {
- case BTM_PM_MD_SNIFF:
- btsnd_hcic_exit_sniff_mode(handle);
- pm_pend_link = handle;
- break;
- case BTM_PM_MD_PARK:
- btsnd_hcic_exit_park_mode(handle);
- pm_pend_link = handle;
- break;
- default:
- /* Failure pm_pend_link = MAX_L2CAP_LINKS */
- break;
- }
- break;
-
- case BTM_PM_MD_HOLD:
- btsnd_hcic_hold_mode(handle, md_res.max, md_res.min);
- pm_pend_link = handle;
- break;
-
- case BTM_PM_MD_SNIFF:
- btsnd_hcic_sniff_mode(handle, md_res.max, md_res.min, md_res.attempt,
- md_res.timeout);
- pm_pend_link = handle;
- break;
-
- case BTM_PM_MD_PARK:
- btsnd_hcic_park_mode(handle, md_res.max, md_res.min);
- pm_pend_link = handle;
- break;
- default:
- /* Failure pm_pend_link = MAX_L2CAP_LINKS */
- break;
- }
-
- if (pm_pend_link == 0) {
- /* the command was not sent */
- LOG_ERROR("pm_pending_link maxed out");
- return (BTM_NO_RESOURCES);
- }
-
- return BTM_CMD_STARTED;
-}
-
-static void btm_pm_continue_pending_mode_changes() {
- for (auto& entry : pm_mode_db) {
- if (entry.second.state & BTM_PM_STORED_MASK) {
- entry.second.state &= ~BTM_PM_STORED_MASK;
- LOG_INFO("Found another link requiring power mode change:%s",
- PRIVATE_ADDRESS(entry.second.bda_));
- btm_pm_snd_md_req(entry.second.handle_, BTM_PM_SET_ONLY_ID,
- entry.second.handle_, NULL);
- return;
- }
- }
-}
-
-/*******************************************************************************
- *
- * Function btm_pm_proc_cmd_status
- *
- * Description This function is called when an HCI command status event
- * occurs for power manager related commands.
- *
- * Input Parms status - status of the event (HCI_SUCCESS if no errors)
- *
- * Returns none.
- *
- ******************************************************************************/
-void btm_pm_proc_cmd_status(tHCI_STATUS status) {
- if (pm_pend_link == 0) {
- LOG_ERROR(
- "There are no links pending power mode changes; try to find other "
- "pending changes");
- btm_pm_continue_pending_mode_changes();
- return;
- }
- if (pm_mode_db.count(pm_pend_link) == 0) {
- LOG_ERROR(
- "Got PM change status for disconnected link %d; forgot to clean up "
- "pm_pend_link?",
- pm_pend_link);
- btm_pm_continue_pending_mode_changes();
- return;
- }
-
- tBTM_PM_MCB* p_cb = &pm_mode_db[pm_pend_link];
-
- // if the command was not successful. Stay in the same state
- tBTM_PM_STATUS pm_status = BTM_PM_STS_ERROR;
-
- if (status == HCI_SUCCESS) {
- p_cb->state = BTM_PM_ST_PENDING;
- pm_status = BTM_PM_STS_PENDING;
- }
-
- /* notify the caller is appropriate */
- if ((pm_pend_id != BTM_PM_SET_ONLY_ID) && (pm_reg_db.mask & BTM_PM_REG_SET)) {
- const RawAddress bd_addr = pm_mode_db[pm_pend_link].bda_;
- LOG_DEBUG("Notifying callback that link power mode is complete peer:%s",
- PRIVATE_ADDRESS(bd_addr));
- (*pm_reg_db.cback)(bd_addr, pm_status, 0, status);
- }
-
- LOG_INFO("Clearing pending power mode link state:%s",
- power_mode_state_text(p_cb->state).c_str());
- pm_pend_link = 0;
-
- btm_pm_continue_pending_mode_changes();
-}
-
-/*******************************************************************************
- *
- * Function btm_process_mode_change
- *
- * Description This function is called when an HCI mode change event
- * occurs.
- *
- * Input Parms hci_status - status of the event (HCI_SUCCESS if no errors)
- * hci_handle - connection handle associated with the change
- * mode - HCI_MODE_ACTIVE, HCI_MODE_HOLD, HCI_MODE_SNIFF, or
- * HCI_MODE_PARK
- * interval - number of baseband slots (meaning depends on
- * mode)
- *
- * Returns none.
- *
- ******************************************************************************/
-void btm_pm_proc_mode_change(tHCI_STATUS hci_status, uint16_t hci_handle,
- tHCI_MODE hci_mode, uint16_t interval) {
- tBTM_PM_STATUS mode = static_cast<tBTM_PM_STATUS>(hci_mode);
- tBTM_PM_STATE old_state;
-
- /* update control block */
- if (pm_mode_db.count(hci_handle) == 0) {
- LOG_WARN("Unable to find active acl for handle %d", hci_handle);
- return;
- }
- tBTM_PM_MCB* p_cb = &pm_mode_db[hci_handle];
-
- old_state = p_cb->state;
- p_cb->state = mode;
- p_cb->interval = interval;
-
- LOG_INFO("Power mode switched from %s[%hhu] to %s[%hhu]",
- power_mode_state_text(old_state).c_str(), old_state,
- power_mode_state_text(p_cb->state).c_str(), p_cb->state);
-
- if ((p_cb->state == BTM_PM_ST_ACTIVE) || (p_cb->state == BTM_PM_ST_SNIFF)) {
- l2c_OnHciModeChangeSendPendingPackets(p_cb->bda_);
- }
-
- /* set req_mode HOLD mode->ACTIVE */
- if ((mode == BTM_PM_MD_ACTIVE) && (p_cb->req_mode.mode == BTM_PM_MD_HOLD))
- p_cb->req_mode.mode = BTM_PM_MD_ACTIVE;
-
- /* new request has been made. - post a message to BTU task */
- if (old_state & BTM_PM_STORED_MASK) {
- btm_pm_snd_md_req(hci_handle, BTM_PM_SET_ONLY_ID, hci_handle, NULL);
- } else {
- for (auto& entry : pm_mode_db) {
- if (entry.second.chg_ind) {
- btm_pm_snd_md_req(entry.second.handle_, BTM_PM_SET_ONLY_ID,
- entry.second.handle_, NULL);
- break;
- }
- }
- }
-
- /* notify registered parties */
- if (pm_reg_db.mask & BTM_PM_REG_SET) {
- (*pm_reg_db.cback)(p_cb->bda_, mode, interval, hci_status);
- }
- /*check if sco disconnect is waiting for the mode change */
- btm_sco_disc_chk_pend_for_modechange(hci_handle);
-
- /* If mode change was because of an active role switch or change link key */
- btm_cont_rswitch_from_handle(hci_handle);
-}
-
-/*******************************************************************************
- *
- * Function btm_pm_proc_ssr_evt
- *
- * Description This function is called when an HCI sniff subrating event
- * occurs.
- *
- * Returns none.
- *
- ******************************************************************************/
-void process_ssr_event(tHCI_STATUS status, uint16_t handle,
- UNUSED_ATTR uint16_t max_tx_lat, uint16_t max_rx_lat) {
- if (pm_mode_db.count(handle) == 0) {
- LOG_WARN("Received sniff subrating event with no active ACL");
- return;
- }
- tBTM_PM_MCB* p_cb = &pm_mode_db[handle];
- auto bd_addr = p_cb->bda_;
-
- bool use_ssr = true;
- if (p_cb->interval == max_rx_lat) {
- LOG_DEBUG("Sniff subrating unsupported so dropping to legacy sniff mode");
- use_ssr = false;
- } else {
- LOG_DEBUG("Sniff subrating enabled");
- }
-
- int cnt = 0;
- if (pm_reg_db.mask & BTM_PM_REG_SET) {
- (*pm_reg_db.cback)(bd_addr, BTM_PM_STS_SSR, (use_ssr) ? 1 : 0, status);
- cnt++;
- }
- LOG_DEBUG(
- "Notified sniff subrating registered clients cnt:%d peer:%s use_ssr:%s "
- "status:%s",
- cnt, PRIVATE_ADDRESS(bd_addr), logbool(use_ssr).c_str(),
- hci_error_code_text(status).c_str());
-}
-
-void btm_pm_on_sniff_subrating(tHCI_STATUS status, uint16_t handle,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) {
- if (bluetooth::shim::is_gd_link_policy_enabled()) {
- return bluetooth::shim::btm_pm_on_sniff_subrating(
- status, handle, maximum_transmit_latency, maximum_receive_latency,
- minimum_remote_timeout, minimum_local_timeout);
- }
- process_ssr_event(status, handle, maximum_transmit_latency,
- maximum_receive_latency);
-}
-
-void btm_pm_proc_ssr_evt(uint8_t* p, UNUSED_ATTR uint16_t evt_len) {
- uint8_t status;
- uint16_t handle;
- uint16_t max_tx_lat;
- uint16_t max_rx_lat;
-
- STREAM_TO_UINT8(status, p);
- STREAM_TO_UINT16(handle, p);
- STREAM_TO_UINT16(max_tx_lat, p);
- STREAM_TO_UINT16(max_rx_lat, p);
-
- process_ssr_event(static_cast<tHCI_STATUS>(status), handle, max_tx_lat,
- max_rx_lat);
-}
-
-/*******************************************************************************
- *
- * Function btm_pm_device_in_active_or_sniff_mode
- *
- * Description This function is called to check if in active or sniff mode
- *
- * Returns true, if in active or sniff mode
- *
- ******************************************************************************/
-static bool btm_pm_device_in_active_or_sniff_mode(void) {
- /* The active state is the highest state-includes connected device and sniff
- * mode*/
-
- /* Covers active and sniff modes */
- if (!pm_mode_db.empty()) {
- return true;
- }
-
- /* Check BLE states */
- if (!btm_cb.ble_ctr_cb.is_connection_state_idle()) {
- BTM_TRACE_DEBUG("%s - BLE state is not idle", __func__);
- return true;
- }
-
- return false;
-}
-
-/*******************************************************************************
- *
- * Function btm_pm_device_in_scan_state
- *
- * Description This function is called to check if in paging, inquiry or
- * connecting mode
- *
- * Returns true, if in paging, inquiry or connecting mode
- *
- ******************************************************************************/
-static bool btm_pm_device_in_scan_state(void) {
- /* Scan state-paging, inquiry, and trying to connect */
-
- /* Check for paging */
- if (btm_cb.is_paging || !fixed_queue_is_empty(btm_cb.page_queue)) {
- BTM_TRACE_DEBUG("btm_pm_device_in_scan_state- paging");
- return true;
- }
-
- /* Check for inquiry */
- if ((btm_cb.btm_inq_vars.inq_active &
- (BTM_BR_INQ_ACTIVE_MASK | BTM_BLE_INQ_ACTIVE_MASK)) != 0) {
- BTM_TRACE_DEBUG("btm_pm_device_in_scan_state- Inq active");
- return true;
- }
-
- return false;
-}
-
-/*******************************************************************************
- *
- * Function BTM_PM_ReadControllerState
- *
- * Description This function is called to obtain the controller state
- *
- * Returns Controller State-BTM_CONTRL_ACTIVE, BTM_CONTRL_SCAN, and
- * BTM_CONTRL_IDLE
- *
- ******************************************************************************/
-tBTM_CONTRL_STATE BTM_PM_ReadControllerState(void) {
- if (btm_pm_device_in_active_or_sniff_mode())
- return BTM_CONTRL_ACTIVE;
- else if (btm_pm_device_in_scan_state())
- return BTM_CONTRL_SCAN;
- else
- return BTM_CONTRL_IDLE;
-}
-
-void btm_pm_on_mode_change(tHCI_STATUS status, uint16_t handle,
- tHCI_MODE current_mode, uint16_t interval) {
- if (bluetooth::shim::is_gd_link_policy_enabled()) {
- return bluetooth::shim::btm_pm_on_mode_change(status, handle, current_mode,
- interval);
- }
-
- btm_sco_chk_pend_unpark(status, handle);
- btm_pm_proc_mode_change(status, handle, current_mode, interval);
-}
diff --git a/stack/acl/peer_packet_types.h b/stack/acl/peer_packet_types.h
deleted file mode 100644
index a16a18bc0..000000000
--- a/stack/acl/peer_packet_types.h
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "stack/include/bt_types.h"
-#include "stack/include/hcidefs.h"
-
-/**
- * Create a bitmask of packet types from the remote feature
- */
-class PeerPacketTypes {
- public:
- struct {
- uint16_t supported{0};
- uint16_t unsupported{0};
- } acl, sco;
-
- PeerPacketTypes(const BD_FEATURES& features) {
- /* 3 and 5 slot packets? */
- if (HCI_3_SLOT_PACKETS_SUPPORTED(features))
- acl.supported |= (HCI_PKT_TYPES_MASK_DH3 | HCI_PKT_TYPES_MASK_DM3);
-
- if (HCI_5_SLOT_PACKETS_SUPPORTED(features))
- acl.supported |= HCI_PKT_TYPES_MASK_DH5 | HCI_PKT_TYPES_MASK_DM5;
-
- /* 2 and 3 MPS support? */
- if (!HCI_EDR_ACL_2MPS_SUPPORTED(features))
- /* Not supported. Add 'not_supported' mask for all 2MPS packet types */
- acl.unsupported |=
- (HCI_PKT_TYPES_MASK_NO_2_DH1 | HCI_PKT_TYPES_MASK_NO_2_DH3 |
- HCI_PKT_TYPES_MASK_NO_2_DH5);
-
- if (!HCI_EDR_ACL_3MPS_SUPPORTED(features))
- /* Not supported. Add 'not_supported' mask for all 3MPS packet types */
- acl.unsupported |=
- (HCI_PKT_TYPES_MASK_NO_3_DH1 | HCI_PKT_TYPES_MASK_NO_3_DH3 |
- HCI_PKT_TYPES_MASK_NO_3_DH5);
-
- /* EDR 3 and 5 slot support? */
- if (HCI_EDR_ACL_2MPS_SUPPORTED(features) ||
- HCI_EDR_ACL_3MPS_SUPPORTED(features)) {
- if (!HCI_3_SLOT_EDR_ACL_SUPPORTED(features))
- /* Not supported. Add 'not_supported' mask for all 3-slot EDR packet
- * types
- */
- acl.unsupported |=
- (HCI_PKT_TYPES_MASK_NO_2_DH3 | HCI_PKT_TYPES_MASK_NO_3_DH3);
-
- if (!HCI_5_SLOT_EDR_ACL_SUPPORTED(features))
- /* Not supported. Add 'not_supported' mask for all 5-slot EDR packet
- * types
- */
- acl.unsupported |=
- (HCI_PKT_TYPES_MASK_NO_2_DH5 | HCI_PKT_TYPES_MASK_NO_3_DH5);
- }
- }
-};
diff --git a/stack/avct/avct_api.cc b/stack/avct/avct_api.cc
index da4c90427..68dfec26a 100644
--- a/stack/avct/avct_api.cc
+++ b/stack/avct/avct_api.cc
@@ -29,12 +29,10 @@
#include "bt_target.h"
#include "bt_types.h"
#include "bt_utils.h"
-#include "bta/include/bta_api.h"
#include "btm_api.h"
#include "l2c_api.h"
#include "l2cdefs.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_sec.h"
/* Control block for AVCT */
tAVCT_CB avct_cb;
@@ -53,29 +51,53 @@ tAVCT_CB avct_cb;
* Returns void
*
******************************************************************************/
-void AVCT_Register() {
+void AVCT_Register(uint16_t mtu, UNUSED_ATTR uint16_t mtu_br,
+ uint8_t sec_mask) {
AVCT_TRACE_API("AVCT_Register");
+ /* register PSM with L2CAP */
+ L2CA_Register(AVCT_PSM, (tL2CAP_APPL_INFO*)&avct_l2c_appl,
+ true /* enable_snoop */, nullptr);
+
+ /* set security level */
+ BTM_SetSecurityLevel(true, "", BTM_SEC_SERVICE_AVCTP, sec_mask, AVCT_PSM, 0,
+ 0);
+ BTM_SetSecurityLevel(false, "", BTM_SEC_SERVICE_AVCTP, sec_mask, AVCT_PSM, 0,
+ 0);
+
/* initialize AVCTP data structures */
memset(&avct_cb, 0, sizeof(tAVCT_CB));
- /* register PSM with L2CAP */
- L2CA_Register2(AVCT_PSM, avct_l2c_appl, true /* enable_snoop */, nullptr,
- kAvrcMtu, 0, BTA_SEC_AUTHENTICATE);
-
/* Include the browsing channel which uses eFCR */
tL2CAP_ERTM_INFO ertm_info;
- ertm_info.preferred_mode = L2CAP_FCR_ERTM_MODE;
-
- L2CA_Register2(AVCT_BR_PSM, avct_l2c_br_appl, true /*enable_snoop*/,
- &ertm_info, kAvrcBrMtu, AVCT_MIN_BROWSE_MTU,
- BTA_SEC_AUTHENTICATE);
+ ertm_info.preferred_mode = avct_l2c_br_fcr_opts_def.mode;
+ ertm_info.allowed_modes = L2CAP_FCR_CHAN_OPT_ERTM;
+ ertm_info.user_rx_buf_size = BT_DEFAULT_BUFFER_SIZE;
+ ertm_info.user_tx_buf_size = BT_DEFAULT_BUFFER_SIZE;
+ ertm_info.fcr_rx_buf_size = BT_DEFAULT_BUFFER_SIZE;
+ ertm_info.fcr_tx_buf_size = BT_DEFAULT_BUFFER_SIZE;
+ L2CA_Register(AVCT_BR_PSM, (tL2CAP_APPL_INFO*)&avct_l2c_br_appl,
+ true /*enable_snoop*/, &ertm_info);
+
+ /* AVCTP browsing channel uses the same security service as AVCTP control
+ * channel */
+ BTM_SetSecurityLevel(true, "", BTM_SEC_SERVICE_AVCTP, sec_mask, AVCT_BR_PSM,
+ 0, 0);
+ BTM_SetSecurityLevel(false, "", BTM_SEC_SERVICE_AVCTP, sec_mask, AVCT_BR_PSM,
+ 0, 0);
+
+ if (mtu_br < AVCT_MIN_BROWSE_MTU) mtu_br = AVCT_MIN_BROWSE_MTU;
+ avct_cb.mtu_br = mtu_br;
#if defined(AVCT_INITIAL_TRACE_LEVEL)
avct_cb.trace_level = AVCT_INITIAL_TRACE_LEVEL;
#else
avct_cb.trace_level = BT_TRACE_LEVEL_NONE;
#endif
+
+ if (mtu < AVCT_MIN_CONTROL_MTU) mtu = AVCT_MIN_CONTROL_MTU;
+ /* store mtu */
+ avct_cb.mtu = mtu;
}
/*******************************************************************************
diff --git a/stack/avct/avct_bcb_act.cc b/stack/avct/avct_bcb_act.cc
index ebb92e381..aca7349a6 100644
--- a/stack/avct/avct_bcb_act.cc
+++ b/stack/avct/avct_bcb_act.cc
@@ -25,18 +25,14 @@
*
*****************************************************************************/
-#define LOG_TAG "bluetooth"
-
+#include <log/log.h>
#include <string.h>
#include "avct_api.h"
#include "avct_int.h"
#include "bt_target.h"
#include "bt_utils.h"
-#include "bta/include/bta_api.h"
#include "btm_api.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_sec.h"
/* action function list */
const tAVCT_BCB_ACTION avct_bcb_action[] = {
@@ -107,13 +103,20 @@ void avct_bcb_chnl_open(tAVCT_BCB* p_bcb, UNUSED_ATTR tAVCT_LCB_EVT* p_data) {
tAVCT_LCB* p_lcb = avct_lcb_by_bcb(p_bcb);
tL2CAP_ERTM_INFO ertm_info;
+ BTM_SetOutService(p_lcb->peer_addr, BTM_SEC_SERVICE_AVCTP_BROWSE, 0);
+
/* Set the FCR options: Browsing channel mandates ERTM */
ertm_info.preferred_mode = L2CAP_FCR_ERTM_MODE;
+ ertm_info.allowed_modes = L2CAP_FCR_CHAN_OPT_ERTM;
+ ertm_info.user_rx_buf_size = BT_DEFAULT_BUFFER_SIZE;
+ ertm_info.user_tx_buf_size = BT_DEFAULT_BUFFER_SIZE;
+ ertm_info.fcr_rx_buf_size = BT_DEFAULT_BUFFER_SIZE;
+ ertm_info.fcr_tx_buf_size = BT_DEFAULT_BUFFER_SIZE;
/* call l2cap connect req */
p_bcb->ch_state = AVCT_CH_CONN;
p_bcb->ch_lcid =
- L2CA_ConnectReq2(AVCT_BR_PSM, p_lcb->peer_addr, BTA_SEC_AUTHENTICATE);
+ L2CA_ErtmConnectReq(AVCT_BR_PSM, p_lcb->peer_addr, &ertm_info);
if (p_bcb->ch_lcid == 0) {
/* if connect req failed, send ourselves close event */
tAVCT_LCB_EVT avct_lcb_evt;
@@ -346,7 +349,7 @@ void avct_bcb_chk_disc(tAVCT_BCB* p_bcb, tAVCT_LCB_EVT* p_data) {
*
******************************************************************************/
void avct_bcb_chnl_disc(tAVCT_BCB* p_bcb, UNUSED_ATTR tAVCT_LCB_EVT* p_data) {
- avct_l2c_br_disconnect(p_bcb->ch_lcid, 0);
+ L2CA_DisconnectReq(p_bcb->ch_lcid);
}
/*******************************************************************************
diff --git a/stack/avct/avct_int.h b/stack/avct/avct_int.h
index 3377d1e77..ff1bba250 100644
--- a/stack/avct/avct_int.h
+++ b/stack/avct/avct_int.h
@@ -66,6 +66,7 @@ typedef struct {
uint8_t allocated; /* 0, not allocated. index+1, otherwise. */
uint8_t state; /* The state machine state */
uint8_t ch_state; /* L2CAP channel state */
+ uint8_t ch_flags; /* L2CAP configuration flags */
} tAVCT_SCB;
/* link control block type */
@@ -76,6 +77,7 @@ typedef struct {
uint8_t allocated; /* 0, not allocated. index+1, otherwise. */
uint8_t state; /* The state machine state */
uint8_t ch_state; /* L2CAP channel state */
+ uint8_t ch_flags; /* L2CAP configuration flags */
BT_HDR* p_rx_msg; /* Message being reassembled */
uint16_t conflict_lcid; /* L2CAP channel LCID */
RawAddress peer_addr; /* BD address of peer */
@@ -91,6 +93,7 @@ typedef struct {
uint8_t allocated; /* 0, not allocated. index+1, otherwise. */
uint8_t state; /* The state machine state */
uint8_t ch_state; /* L2CAP channel state */
+ uint8_t ch_flags; /* L2CAP configuration flags */
BT_HDR* p_tx_msg; /* Message to be sent - in case the browsing channel is not
open when MsgReg is called */
uint8_t ch_close; /* CCB index+1, if CCB initiated channel close */
@@ -131,6 +134,8 @@ typedef struct {
tAVCT_LCB lcb[AVCT_NUM_LINKS]; /* link control blocks */
tAVCT_BCB bcb[AVCT_NUM_LINKS]; /* browse control blocks */
tAVCT_CCB ccb[AVCT_NUM_CONN]; /* connection control blocks */
+ uint16_t mtu; /* our L2CAP MTU */
+ uint16_t mtu_br; /* our L2CAP MTU for the Browsing channel */
uint8_t trace_level; /* trace level */
} tAVCT_CB;
@@ -195,6 +200,7 @@ extern void avct_bcb_dealloc(tAVCT_BCB* p_bcb, tAVCT_LCB_EVT* p_data);
extern const tAVCT_BCB_ACTION avct_bcb_action[];
extern const uint8_t avct_lcb_pkt_type_len[];
+extern const tL2CAP_FCR_OPTS avct_l2c_br_fcr_opts_def;
/* CCB function declarations */
extern tAVCT_CCB* avct_ccb_alloc(tAVCT_CC* p_cc);
@@ -214,10 +220,4 @@ extern tAVCT_CB avct_cb;
extern const tL2CAP_APPL_INFO avct_l2c_appl;
extern const tL2CAP_APPL_INFO avct_l2c_br_appl;
-void avct_l2c_disconnect(uint16_t lcid, uint16_t result);
-void avct_l2c_br_disconnect(uint16_t lcid, uint16_t result);
-
-constexpr uint16_t kAvrcMtu = 512;
-constexpr uint16_t kAvrcBrMtu = 1008;
-
#endif /* AVCT_INT_H */
diff --git a/stack/avct/avct_l2c.cc b/stack/avct/avct_l2c.cc
index 40005e128..718a9c9c2 100644
--- a/stack/avct/avct_l2c.cc
+++ b/stack/avct/avct_l2c.cc
@@ -22,35 +22,44 @@
*
******************************************************************************/
+#include <string.h>
#include "avct_api.h"
#include "avct_int.h"
#include "bt_target.h"
#include "bt_types.h"
+#include "bt_utils.h"
#include "l2c_api.h"
#include "l2cdefs.h"
#include "osi/include/osi.h"
+/* Configuration flags. */
+#define AVCT_L2C_CFG_IND_DONE (1 << 0)
+#define AVCT_L2C_CFG_CFM_DONE (1 << 1)
+
/* callback function declarations */
void avct_l2c_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
uint16_t psm, uint8_t id);
void avct_l2c_connect_cfm_cback(uint16_t lcid, uint16_t result);
-void avct_l2c_config_cfm_cback(uint16_t lcid, uint16_t result,
- tL2CAP_CFG_INFO* p_cfg);
+void avct_l2c_config_cfm_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg);
void avct_l2c_config_ind_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg);
void avct_l2c_disconnect_ind_cback(uint16_t lcid, bool ack_needed);
+void avct_l2c_disconnect_cfm_cback(uint16_t lcid, uint16_t result);
void avct_l2c_congestion_ind_cback(uint16_t lcid, bool is_congested);
void avct_l2c_data_ind_cback(uint16_t lcid, BT_HDR* p_buf);
-static void avct_on_l2cap_error(uint16_t lcid, uint16_t result);
/* L2CAP callback function structure */
-const tL2CAP_APPL_INFO avct_l2c_appl = {
- avct_l2c_connect_ind_cback, avct_l2c_connect_cfm_cback,
- avct_l2c_config_ind_cback, avct_l2c_config_cfm_cback,
- avct_l2c_disconnect_ind_cback, avct_l2c_data_ind_cback,
- avct_l2c_congestion_ind_cback, NULL,
- avct_on_l2cap_error, NULL,
- NULL, NULL,
-};
+const tL2CAP_APPL_INFO avct_l2c_appl = {avct_l2c_connect_ind_cback,
+ avct_l2c_connect_cfm_cback,
+ NULL,
+ avct_l2c_config_ind_cback,
+ avct_l2c_config_cfm_cback,
+ avct_l2c_disconnect_ind_cback,
+ avct_l2c_disconnect_cfm_cback,
+ NULL,
+ avct_l2c_data_ind_cback,
+ avct_l2c_congestion_ind_cback,
+ NULL, /* tL2CA_TX_COMPLETE_CB */
+ NULL /* tL2CA_CREDITS_RECEIVED_CB */};
/*******************************************************************************
*
@@ -93,6 +102,7 @@ void avct_l2c_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
UNUSED_ATTR uint16_t psm, uint8_t id) {
tAVCT_LCB* p_lcb;
uint16_t result = L2CAP_CONN_OK;
+ tL2CAP_CFG_INFO cfg;
/* do we already have a channel for this peer? */
p_lcb = avct_lcb_by_bd(bd_addr);
@@ -122,11 +132,8 @@ void avct_l2c_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
AVCT_TRACE_DEBUG("avct_l2c_connect_ind_cback: 0x%x, res: %d, ch_state: %d",
lcid, result, p_lcb->ch_state);
}
-
- /* If we reject the connection, send DisconnectReq */
- if (result != L2CAP_CONN_OK) {
- L2CA_DisconnectReq(lcid);
- }
+ /* Send L2CAP connect rsp */
+ L2CA_ConnectRsp(bd_addr, id, lcid, result, 0);
/* if result ok, proceed with connection */
if (result == L2CAP_CONN_OK) {
@@ -135,35 +142,18 @@ void avct_l2c_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
/* transition to configuration state */
p_lcb->ch_state = AVCT_CH_CFG;
+
+ /* Send L2CAP config req */
+ memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ cfg.mtu_present = true;
+ cfg.mtu = avct_cb.mtu;
+ L2CA_ConfigReq(lcid, &cfg);
+ AVCT_TRACE_DEBUG("avct_l2c snd Cfg Req");
}
if (p_lcb) AVCT_TRACE_DEBUG("ch_state cni: %d ", p_lcb->ch_state);
}
-static void avct_on_l2cap_error(uint16_t lcid, uint16_t result) {
- tAVCT_LCB* p_lcb = avct_lcb_by_lcid(lcid);
- if (p_lcb == nullptr) return;
- if (p_lcb->ch_state == AVCT_CH_CONN) {
- AVCT_TRACE_DEBUG("avct_l2c_connect_cfm_cback conflict_lcid:0x%x",
- p_lcb->conflict_lcid);
- if (p_lcb->conflict_lcid == lcid) {
- p_lcb->conflict_lcid = 0;
- } else {
- tAVCT_LCB_EVT avct_lcb_evt;
- avct_lcb_evt.result = result;
- avct_lcb_event(p_lcb, AVCT_LCB_LL_CLOSE_EVT, &avct_lcb_evt);
- }
- } else if (p_lcb->ch_state == AVCT_CH_CFG) {
- AVCT_TRACE_DEBUG("ERROR avct_l2c_config_cfm_cback L2CA_DisconnectReq %d ",
- p_lcb->ch_state);
- /* store result value */
- p_lcb->ch_result = result;
-
- /* Send L2CAP disconnect req */
- L2CA_DisconnectReq(lcid);
- }
-}
-
/*******************************************************************************
*
* Function avct_l2c_connect_cfm_cback
@@ -176,6 +166,7 @@ static void avct_on_l2cap_error(uint16_t lcid, uint16_t result) {
******************************************************************************/
void avct_l2c_connect_cfm_cback(uint16_t lcid, uint16_t result) {
tAVCT_LCB* p_lcb;
+ tL2CAP_CFG_INFO cfg;
/* look up lcb for this channel */
p_lcb = avct_lcb_by_lcid(lcid);
@@ -190,10 +181,25 @@ void avct_l2c_connect_cfm_cback(uint16_t lcid, uint16_t result) {
if (result == L2CAP_CONN_OK) {
/* set channel state */
p_lcb->ch_state = AVCT_CH_CFG;
+
+ /* Send L2CAP config req */
+ memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ cfg.mtu_present = true;
+ cfg.mtu = avct_cb.mtu;
+ L2CA_ConfigReq(lcid, &cfg);
+ AVCT_TRACE_DEBUG("avct_l2c snd Cfg Req");
}
/* else failure */
else {
- LOG(ERROR) << __func__ << ": invoked with non OK status";
+ AVCT_TRACE_DEBUG("avct_l2c_connect_cfm_cback conflict_lcid:0x%x",
+ p_lcb->conflict_lcid);
+ if (p_lcb->conflict_lcid == lcid) {
+ p_lcb->conflict_lcid = 0;
+ } else {
+ tAVCT_LCB_EVT avct_lcb_evt;
+ avct_lcb_evt.result = result;
+ avct_lcb_event(p_lcb, AVCT_LCB_LL_CLOSE_EVT, &avct_lcb_evt);
+ }
}
} else if (p_lcb->conflict_lcid == lcid) {
/* we must be in AVCT_CH_CFG state for the ch_lcid channel */
@@ -221,21 +227,38 @@ void avct_l2c_connect_cfm_cback(uint16_t lcid, uint16_t result) {
* Returns void
*
******************************************************************************/
-void avct_l2c_config_cfm_cback(uint16_t lcid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
- avct_l2c_config_ind_cback(lcid, p_cfg);
-
+void avct_l2c_config_cfm_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
tAVCT_LCB* p_lcb;
/* look up lcb for this channel */
p_lcb = avct_lcb_by_lcid(lcid);
if (p_lcb != NULL) {
- AVCT_TRACE_DEBUG("avct_l2c_config_cfm_cback: 0x%x, ch_state: %d,", lcid,
- p_lcb->ch_state);
+ AVCT_TRACE_DEBUG("avct_l2c_config_cfm_cback: 0x%x, ch_state: %d, res: %d",
+ lcid, p_lcb->ch_state, p_cfg->result);
/* if in correct state */
if (p_lcb->ch_state == AVCT_CH_CFG) {
- p_lcb->ch_state = AVCT_CH_OPEN;
- avct_lcb_event(p_lcb, AVCT_LCB_LL_OPEN_EVT, NULL);
+ /* if result successful */
+ if (p_cfg->result == L2CAP_CFG_OK) {
+ /* update flags */
+ p_lcb->ch_flags |= AVCT_L2C_CFG_CFM_DONE;
+
+ /* if configuration complete */
+ if (p_lcb->ch_flags & AVCT_L2C_CFG_IND_DONE) {
+ p_lcb->ch_state = AVCT_CH_OPEN;
+ avct_lcb_event(p_lcb, AVCT_LCB_LL_OPEN_EVT, NULL);
+ }
+ }
+ /* else failure */
+ else {
+ AVCT_TRACE_DEBUG(
+ "ERROR avct_l2c_config_cfm_cback L2CA_DisconnectReq %d ",
+ p_lcb->ch_state);
+ /* store result value */
+ p_lcb->ch_result = p_cfg->result;
+
+ /* Send L2CAP disconnect req */
+ L2CA_DisconnectReq(lcid);
+ }
}
AVCT_TRACE_DEBUG("ch_state cfc: %d ", p_lcb->ch_state);
}
@@ -265,6 +288,24 @@ void avct_l2c_config_ind_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
} else {
p_lcb->peer_mtu = L2CAP_DEFAULT_MTU;
}
+
+ /* send L2CAP configure response */
+ memset(p_cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ p_cfg->result = L2CAP_CFG_OK;
+ L2CA_ConfigRsp(lcid, p_cfg);
+
+ /* if first config ind */
+ if ((p_lcb->ch_flags & AVCT_L2C_CFG_IND_DONE) == 0) {
+ /* update flags */
+ p_lcb->ch_flags |= AVCT_L2C_CFG_IND_DONE;
+
+ /* if configuration complete */
+ if (p_lcb->ch_flags & AVCT_L2C_CFG_CFM_DONE) {
+ p_lcb->ch_state = AVCT_CH_OPEN;
+ avct_lcb_event(p_lcb, AVCT_LCB_LL_OPEN_EVT, NULL);
+ }
+ }
+ AVCT_TRACE_DEBUG("ch_state cfi: %d ", p_lcb->ch_state);
}
}
@@ -287,6 +328,11 @@ void avct_l2c_disconnect_ind_cback(uint16_t lcid, bool ack_needed) {
if (p_lcb != NULL) {
AVCT_TRACE_DEBUG("avct_l2c_disconnect_ind_cback: 0x%x, ch_state: %d", lcid,
p_lcb->ch_state);
+ if (ack_needed) {
+ /* send L2CAP disconnect response */
+ L2CA_DisconnectRsp(lcid);
+ }
+
tAVCT_LCB_EVT avct_lcb_evt;
avct_lcb_evt.result = result;
avct_lcb_event(p_lcb, AVCT_LCB_LL_CLOSE_EVT, &avct_lcb_evt);
@@ -294,9 +340,17 @@ void avct_l2c_disconnect_ind_cback(uint16_t lcid, bool ack_needed) {
}
}
-void avct_l2c_disconnect(uint16_t lcid, uint16_t result) {
- L2CA_DisconnectReq(lcid);
-
+/*******************************************************************************
+ *
+ * Function avct_l2c_disconnect_cfm_cback
+ *
+ * Description This is the L2CAP disconnect confirm callback function.
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void avct_l2c_disconnect_cfm_cback(uint16_t lcid, uint16_t result) {
tAVCT_LCB* p_lcb;
uint16_t res;
diff --git a/stack/avct/avct_l2c_br.cc b/stack/avct/avct_l2c_br.cc
index 1f2781ac4..1be8a7b84 100644
--- a/stack/avct/avct_l2c_br.cc
+++ b/stack/avct/avct_l2c_br.cc
@@ -24,33 +24,86 @@
*
*****************************************************************************/
+#include <string.h>
#include "avct_api.h"
#include "avct_int.h"
#include "bt_target.h"
+#include "bt_utils.h"
#include "l2c_api.h"
#include "l2cdefs.h"
#include "osi/include/osi.h"
+/* Configuration flags. */
+#define AVCT_L2C_CFG_IND_DONE (1 << 0)
+#define AVCT_L2C_CFG_CFM_DONE (1 << 1)
+
+/* AVCTP Browsing channel FCR Option:
+ * Size of the transmission window when using enhanced retransmission mode. Not
+ * used in basic and streaming modes. Range: 1 - 63
+ */
+#define AVCT_BR_FCR_OPT_TX_WINDOW_SIZE 10
+
+/* AVCTP Browsing channel FCR Option:
+ * Number of transmission attempts for a single I-Frame before taking
+ * Down the connection. Used In ERTM mode only. Value is Ignored in basic and
+ * Streaming modes.
+ * Range: 0, 1-0xFF
+ * 0 - infinite retransmissions
+ * 1 - single transmission
+ */
+#define AVCT_BR_FCR_OPT_MAX_TX_B4_DISCNT 20
+
+/* AVCTP Browsing channel FCR Option: Retransmission Timeout
+ * The AVRCP specification set a value in the range of 300 - 2000 ms
+ * Timeout (in msecs) to detect Lost I-Frames. Only used in Enhanced
+ * retransmission mode.
+ * Range: Minimum 2000 (2 secs) when supporting PBF.
+ */
+#define AVCT_BR_FCR_OPT_RETX_TOUT 2000
+
+/* AVCTP Browsing channel FCR Option: Monitor Timeout
+ * The AVRCP specification set a value in the range of 300 - 2000 ms
+ * Timeout (in msecs) to detect Lost S-Frames. Only used in Enhanced
+ * retransmission mode.
+ * Range: Minimum 12000 (12 secs) when supporting PBF.
+ */
+#define AVCT_BR_FCR_OPT_MONITOR_TOUT 12000
+
/* callback function declarations */
void avct_l2c_br_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
uint16_t psm, uint8_t id);
void avct_l2c_br_connect_cfm_cback(uint16_t lcid, uint16_t result);
-void avct_l2c_br_config_cfm_cback(uint16_t lcid, uint16_t result,
- tL2CAP_CFG_INFO* p_cfg);
+void avct_l2c_br_config_cfm_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg);
void avct_l2c_br_config_ind_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg);
void avct_l2c_br_disconnect_ind_cback(uint16_t lcid, bool ack_needed);
+void avct_l2c_br_disconnect_cfm_cback(uint16_t lcid, uint16_t result);
void avct_l2c_br_congestion_ind_cback(uint16_t lcid, bool is_congested);
void avct_l2c_br_data_ind_cback(uint16_t lcid, BT_HDR* p_buf);
-void avct_br_on_l2cap_error(uint16_t lcid, uint16_t result);
/* L2CAP callback function structure */
const tL2CAP_APPL_INFO avct_l2c_br_appl = {
- avct_l2c_br_connect_ind_cback, avct_l2c_br_connect_cfm_cback,
- avct_l2c_br_config_ind_cback, avct_l2c_br_config_cfm_cback,
- avct_l2c_br_disconnect_ind_cback, avct_l2c_br_data_ind_cback,
- avct_l2c_br_congestion_ind_cback, NULL,
- avct_br_on_l2cap_error, NULL,
- NULL, NULL
+ avct_l2c_br_connect_ind_cback,
+ avct_l2c_br_connect_cfm_cback,
+ NULL,
+ avct_l2c_br_config_ind_cback,
+ avct_l2c_br_config_cfm_cback,
+ avct_l2c_br_disconnect_ind_cback,
+ avct_l2c_br_disconnect_cfm_cback,
+ NULL,
+ avct_l2c_br_data_ind_cback,
+ avct_l2c_br_congestion_ind_cback,
+ NULL, /* tL2CA_TX_COMPLETE_CB */
+ NULL /* tL2CA_CREDITS_RECEIVED_CB */};
+
+/* Browsing channel eL2CAP default options */
+const tL2CAP_FCR_OPTS avct_l2c_br_fcr_opts_def = {
+ L2CAP_FCR_ERTM_MODE, /* Mandatory for Browsing channel */
+ AVCT_BR_FCR_OPT_TX_WINDOW_SIZE, /* Tx window size */
+ AVCT_BR_FCR_OPT_MAX_TX_B4_DISCNT, /* Maximum transmissions before
+ disconnecting */
+ AVCT_BR_FCR_OPT_RETX_TOUT, /* Retransmission timeout (2 secs) */
+ AVCT_BR_FCR_OPT_MONITOR_TOUT, /* Monitor timeout (12 secs) */
+ L2CAP_DEFAULT_ERM_MPS /* MPS segment size */
};
/*******************************************************************************
@@ -67,9 +120,13 @@ void avct_l2c_br_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
UNUSED_ATTR uint16_t psm, uint8_t id) {
tAVCT_LCB* p_lcb;
uint16_t result = L2CAP_CONN_NO_RESOURCES;
+ tL2CAP_CFG_INFO cfg;
tAVCT_BCB* p_bcb;
tL2CAP_ERTM_INFO ertm_info;
+ memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ cfg.mtu_present = true;
+
p_lcb = avct_lcb_by_bd(bd_addr);
if (p_lcb != NULL) {
/* control channel exists */
@@ -83,17 +140,24 @@ void avct_l2c_br_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
p_bcb->allocated = p_lcb->allocated; /* copy the index from lcb */
result = L2CAP_CONN_OK;
+ cfg.mtu = avct_cb.mtu_br;
+
+ cfg.fcr_present = true;
+ cfg.fcr = avct_l2c_br_fcr_opts_def;
}
}
/* else no control channel yet, reject */
/* Set the FCR options: Browsing channel mandates ERTM */
- ertm_info.preferred_mode = L2CAP_FCR_ERTM_MODE;
+ ertm_info.preferred_mode = cfg.fcr.mode;
+ ertm_info.allowed_modes = L2CAP_FCR_CHAN_OPT_ERTM;
+ ertm_info.user_rx_buf_size = BT_DEFAULT_BUFFER_SIZE;
+ ertm_info.user_tx_buf_size = BT_DEFAULT_BUFFER_SIZE;
+ ertm_info.fcr_rx_buf_size = BT_DEFAULT_BUFFER_SIZE;
+ ertm_info.fcr_tx_buf_size = BT_DEFAULT_BUFFER_SIZE;
- /* If we reject the connection, send DisconnectReq */
- if (result != L2CAP_CONN_OK) {
- L2CA_DisconnectReq(lcid);
- }
+ /* Send L2CAP connect rsp */
+ L2CA_ErtmConnectRsp(bd_addr, id, lcid, result, 0, &ertm_info);
/* if result ok, proceed with connection */
if (result == L2CAP_CONN_OK) {
@@ -102,18 +166,10 @@ void avct_l2c_br_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
/* transition to configuration state */
p_bcb->ch_state = AVCT_CH_CFG;
- }
-}
-
-void avct_br_on_l2cap_error(uint16_t lcid, uint16_t result) {
- tAVCT_BCB* p_lcb = avct_bcb_by_lcid(lcid);
- if (p_lcb == nullptr) return;
- /* store result value */
- p_lcb->ch_result = result;
-
- /* Send L2CAP disconnect req */
- avct_l2c_br_disconnect(lcid, 0);
+ /* Send L2CAP config req */
+ L2CA_ConfigReq(lcid, &cfg);
+ }
}
/*******************************************************************************
@@ -128,19 +184,34 @@ void avct_br_on_l2cap_error(uint16_t lcid, uint16_t result) {
******************************************************************************/
void avct_l2c_br_connect_cfm_cback(uint16_t lcid, uint16_t result) {
tAVCT_BCB* p_lcb;
+ tL2CAP_CFG_INFO cfg;
/* look up lcb for this channel */
p_lcb = avct_bcb_by_lcid(lcid);
if ((p_lcb == NULL) || (p_lcb->ch_state != AVCT_CH_CONN)) return;
if (result != L2CAP_CONN_OK) {
- LOG(ERROR) << __func__ << ": invoked with non OK status";
+ /* failure */
+ tAVCT_LCB_EVT avct_lcb_evt;
+ avct_lcb_evt.result = result;
+ avct_bcb_event(p_lcb, AVCT_LCB_LL_CLOSE_EVT, &avct_lcb_evt);
return;
}
/* result is successful */
/* set channel state */
p_lcb->ch_state = AVCT_CH_CFG;
+
+ /* Send L2CAP config req */
+ memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
+
+ cfg.mtu_present = true;
+ cfg.mtu = avct_cb.mtu_br;
+
+ cfg.fcr_present = true;
+ cfg.fcr = avct_l2c_br_fcr_opts_def;
+
+ L2CA_ConfigReq(lcid, &cfg);
}
/*******************************************************************************
@@ -153,18 +224,32 @@ void avct_l2c_br_connect_cfm_cback(uint16_t lcid, uint16_t result) {
* Returns void
*
******************************************************************************/
-void avct_l2c_br_config_cfm_cback(uint16_t lcid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
- avct_l2c_br_config_ind_cback(lcid, p_cfg);
-
+void avct_l2c_br_config_cfm_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
tAVCT_BCB* p_lcb;
/* look up lcb for this channel */
p_lcb = avct_bcb_by_lcid(lcid);
if ((p_lcb == NULL) || (p_lcb->ch_state != AVCT_CH_CFG)) return;
- p_lcb->ch_state = AVCT_CH_OPEN;
- avct_bcb_event(p_lcb, AVCT_LCB_LL_OPEN_EVT, NULL);
+ /* if result successful */
+ if (p_cfg->result == L2CAP_CFG_OK) {
+ /* update flags */
+ p_lcb->ch_flags |= AVCT_L2C_CFG_CFM_DONE;
+
+ /* if configuration complete */
+ if (p_lcb->ch_flags & AVCT_L2C_CFG_IND_DONE) {
+ p_lcb->ch_state = AVCT_CH_OPEN;
+ avct_bcb_event(p_lcb, AVCT_LCB_LL_OPEN_EVT, NULL);
+ }
+ }
+ /* else failure */
+ else {
+ /* store result value */
+ p_lcb->ch_result = p_cfg->result;
+
+ /* Send L2CAP disconnect req */
+ L2CA_DisconnectReq(lcid);
+ }
}
/*******************************************************************************
@@ -181,6 +266,13 @@ void avct_l2c_br_config_ind_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
tAVCT_BCB* p_lcb;
uint16_t max_mtu = BT_DEFAULT_BUFFER_SIZE - L2CAP_MIN_OFFSET - BT_HDR_SIZE;
+ /* Don't include QoS nor flush timeout in the response since we
+ currently always accept these values. Note: fcr_present is left
+ untouched since l2cap negotiates this internally
+ */
+ p_cfg->flush_to_present = false;
+ p_cfg->qos_present = false;
+
/* look up lcb for this channel */
p_lcb = avct_bcb_by_lcid(lcid);
if (p_lcb == NULL) return;
@@ -192,10 +284,41 @@ void avct_l2c_br_config_ind_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
}
if (p_lcb->peer_mtu > max_mtu) {
- p_lcb->peer_mtu = max_mtu;
- }
+ p_lcb->peer_mtu = p_cfg->mtu = max_mtu;
+
+ /* Must tell the peer what the adjusted value is */
+ p_cfg->mtu_present = true;
+ } else /* Don't include in the response */
+ p_cfg->mtu_present = false;
AVCT_TRACE_DEBUG("%s peer_mtu:%d use:%d", __func__, p_lcb->peer_mtu, max_mtu);
+
+ if (p_lcb->peer_mtu >= AVCT_MIN_BROWSE_MTU)
+ p_cfg->result = L2CAP_CFG_OK;
+ else {
+ p_cfg->result = L2CAP_CFG_UNACCEPTABLE_PARAMS;
+ p_cfg->mtu_present = true;
+ p_cfg->mtu = AVCT_MIN_BROWSE_MTU;
+ }
+
+ /* send L2CAP configure response */
+ L2CA_ConfigRsp(lcid, p_cfg);
+
+ if (p_cfg->result != L2CAP_CFG_OK) {
+ return;
+ }
+
+ /* if first config ind */
+ if ((p_lcb->ch_flags & AVCT_L2C_CFG_IND_DONE) == 0) {
+ /* update flags */
+ p_lcb->ch_flags |= AVCT_L2C_CFG_IND_DONE;
+
+ /* if configuration complete */
+ if (p_lcb->ch_flags & AVCT_L2C_CFG_CFM_DONE) {
+ p_lcb->ch_state = AVCT_CH_OPEN;
+ avct_bcb_event(p_lcb, AVCT_LCB_LL_OPEN_EVT, NULL);
+ }
+ }
}
/*******************************************************************************
@@ -216,14 +339,27 @@ void avct_l2c_br_disconnect_ind_cback(uint16_t lcid, bool ack_needed) {
p_lcb = avct_bcb_by_lcid(lcid);
if (p_lcb == NULL) return;
+ if (ack_needed) {
+ /* send L2CAP disconnect response */
+ L2CA_DisconnectRsp(lcid);
+ }
+
tAVCT_LCB_EVT avct_lcb_evt;
avct_lcb_evt.result = result;
avct_bcb_event(p_lcb, AVCT_LCB_LL_CLOSE_EVT, &avct_lcb_evt);
}
-void avct_l2c_br_disconnect(uint16_t lcid, uint16_t result) {
- L2CA_DisconnectReq(lcid);
-
+/*******************************************************************************
+ *
+ * Function avct_l2c_br_disconnect_cfm_cback
+ *
+ * Description This is the L2CAP disconnect confirm callback function.
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void avct_l2c_br_disconnect_cfm_cback(uint16_t lcid, uint16_t result) {
tAVCT_BCB* p_lcb;
uint16_t res;
diff --git a/stack/avct/avct_lcb.cc b/stack/avct/avct_lcb.cc
index 1cd62191f..8a9c8eec2 100644
--- a/stack/avct/avct_lcb.cc
+++ b/stack/avct/avct_lcb.cc
@@ -271,7 +271,6 @@ tAVCT_LCB* avct_lcb_alloc(const RawAddress& bd_addr) {
p_lcb->peer_addr = bd_addr;
AVCT_TRACE_DEBUG("avct_lcb_alloc %d", p_lcb->allocated);
p_lcb->tx_q = fixed_queue_new(SIZE_MAX);
- p_lcb->peer_mtu = L2CAP_LE_MIN_MTU;
break;
}
}
diff --git a/stack/avct/avct_lcb_act.cc b/stack/avct/avct_lcb_act.cc
index 9e32ee4e9..eec049df9 100644
--- a/stack/avct/avct_lcb_act.cc
+++ b/stack/avct/avct_lcb_act.cc
@@ -29,11 +29,8 @@
#include "bt_target.h"
#include "bt_types.h"
#include "bt_utils.h"
-#include "bta/include/bta_api.h"
#include "btm_api.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_sec.h"
/* packet header length lookup table */
const uint8_t avct_lcb_pkt_type_len[] = {AVCT_HDR_LEN_SINGLE,
@@ -176,9 +173,10 @@ static BT_HDR* avct_lcb_msg_asmbl(tAVCT_LCB* p_lcb, BT_HDR* p_buf) {
void avct_lcb_chnl_open(tAVCT_LCB* p_lcb, UNUSED_ATTR tAVCT_LCB_EVT* p_data) {
uint16_t result = AVCT_RESULT_FAIL;
+ BTM_SetOutService(p_lcb->peer_addr, BTM_SEC_SERVICE_AVCTP, 0);
+ /* call l2cap connect req */
p_lcb->ch_state = AVCT_CH_CONN;
- p_lcb->ch_lcid =
- L2CA_ConnectReq2(AVCT_PSM, p_lcb->peer_addr, BTA_SEC_AUTHENTICATE);
+ p_lcb->ch_lcid = L2CA_ConnectReq(AVCT_PSM, p_lcb->peer_addr);
if (p_lcb->ch_lcid == 0) {
/* if connect req failed, send ourselves close event */
tAVCT_LCB_EVT avct_lcb_evt;
@@ -361,17 +359,20 @@ void avct_lcb_bind_conn(tAVCT_LCB* p_lcb, tAVCT_LCB_EVT* p_data) {
* close channel. Otherwise just deallocate and call
* callback.
*
+ *
* Returns Nothing.
*
******************************************************************************/
void avct_lcb_chk_disc(tAVCT_LCB* p_lcb, tAVCT_LCB_EVT* p_data) {
+ AVCT_TRACE_WARNING("%s", __func__);
+
avct_close_bcb(p_lcb, p_data);
if (avct_lcb_last_ccb(p_lcb, p_data->p_ccb)) {
- LOG_INFO("Closing last avct channel to device");
+ AVCT_TRACE_WARNING("%s: closing", __func__);
p_data->p_ccb->ch_close = true;
avct_lcb_event(p_lcb, AVCT_LCB_INT_CLOSE_EVT, p_data);
} else {
- LOG_INFO("Closing avct channel with active remaining channels");
+ AVCT_TRACE_WARNING("%s: dealloc ccb", __func__);
avct_lcb_unbind_disc(p_lcb, p_data);
}
}
@@ -387,7 +388,7 @@ void avct_lcb_chk_disc(tAVCT_LCB* p_lcb, tAVCT_LCB_EVT* p_data) {
*
******************************************************************************/
void avct_lcb_chnl_disc(tAVCT_LCB* p_lcb, UNUSED_ATTR tAVCT_LCB_EVT* p_data) {
- avct_l2c_disconnect(p_lcb->ch_lcid, 0);
+ L2CA_DisconnectReq(p_lcb->ch_lcid);
}
/*******************************************************************************
diff --git a/stack/avdt/avdt_ad.cc b/stack/avdt/avdt_ad.cc
index ff102548f..cc994b0a9 100644
--- a/stack/avdt/avdt_ad.cc
+++ b/stack/avdt/avdt_ad.cc
@@ -34,7 +34,6 @@
#include "l2c_api.h"
#include "l2cdefs.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_sec.h"
AvdtpScb* AvdtpAdaptationLayer::LookupAvdtpScb(
const AvdtpTransportChannel& tc) {
@@ -193,11 +192,14 @@ AvdtpTransportChannel* avdt_ad_tc_tbl_by_st(uint8_t type, AvdtpCcb* p_ccb,
*
******************************************************************************/
AvdtpTransportChannel* avdt_ad_tc_tbl_by_lcid(uint16_t lcid) {
- if (avdtp_cb.ad.lcid_tbl.count(lcid) != 0) {
- uint8_t idx = avdtp_cb.ad.lcid_tbl[lcid];
+ uint8_t idx;
+
+ idx = avdtp_cb.ad.lcid_tbl[lcid - L2CAP_BASE_APPL_CID];
+
+ if (idx < AVDT_NUM_TC_TBL) {
return &avdtp_cb.ad.tc_tbl[idx];
} else {
- return nullptr;
+ return NULL;
}
}
@@ -295,7 +297,8 @@ uint8_t avdt_ad_tc_tbl_to_idx(AvdtpTransportChannel* p_tbl) {
* Returns Nothing.
*
******************************************************************************/
-void avdt_ad_tc_close_ind(AvdtpTransportChannel* p_tbl) {
+void avdt_ad_tc_close_ind(AvdtpTransportChannel* p_tbl,
+ UNUSED_ATTR uint16_t reason) {
AvdtpCcb* p_ccb;
AvdtpScb* p_scb;
tAVDT_SCB_TC_CLOSE close;
@@ -524,10 +527,12 @@ void avdt_ad_open_req(uint8_t type, AvdtpCcb* p_ccb, AvdtpScb* p_scb,
if (type == AVDT_CHAN_SIG) {
/* if signaling, get mtu from registration control block */
- p_tbl->my_mtu = kAvdtpMtu;
+ p_tbl->my_mtu = avdtp_cb.rcb.ctrl_mtu;
+ p_tbl->my_flush_to = L2CAP_DEFAULT_FLUSH_TO;
} else {
/* otherwise get mtu from scb */
- p_tbl->my_mtu = kAvdtpMtu;
+ p_tbl->my_mtu = p_scb->stream_config.mtu;
+ p_tbl->my_flush_to = p_scb->stream_config.flush_to;
/* also set scb_hdl in rt_tbl */
avdtp_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][p_tbl->tcid].scb_hdl =
@@ -546,12 +551,13 @@ void avdt_ad_open_req(uint8_t type, AvdtpCcb* p_ccb, AvdtpScb* p_scb,
p_tbl->state = AVDT_AD_ST_CONN;
/* call l2cap connect req */
- lcid =
- L2CA_ConnectReq2(AVDT_PSM, p_ccb->peer_addr, BTM_SEC_OUT_AUTHENTICATE);
+ lcid = L2CA_ConnectReq(AVDT_PSM, p_ccb->peer_addr);
if (lcid != 0) {
/* if connect req ok, store tcid in lcid table */
- avdtp_cb.ad.lcid_tbl[lcid] = avdt_ad_tc_tbl_to_idx(p_tbl);
- AVDT_TRACE_DEBUG("avdtp_cb.ad.lcid_tbl[%d] = %d", (lcid),
+ avdtp_cb.ad.lcid_tbl[lcid - L2CAP_BASE_APPL_CID] =
+ avdt_ad_tc_tbl_to_idx(p_tbl);
+ AVDT_TRACE_DEBUG("avdtp_cb.ad.lcid_tbl[%d] = %d",
+ (lcid - L2CAP_BASE_APPL_CID),
avdt_ad_tc_tbl_to_idx(p_tbl));
avdtp_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][p_tbl->tcid].lcid = lcid;
@@ -559,7 +565,7 @@ void avdt_ad_open_req(uint8_t type, AvdtpCcb* p_ccb, AvdtpScb* p_scb,
avdt_ccb_to_idx(p_ccb), p_tbl->tcid, lcid);
} else {
/* if connect req failed, call avdt_ad_tc_close_ind() */
- avdt_ad_tc_close_ind(p_tbl);
+ avdt_ad_tc_close_ind(p_tbl, 0);
}
}
}
@@ -589,14 +595,13 @@ void avdt_ad_close_req(uint8_t type, AvdtpCcb* p_ccb, AvdtpScb* p_scb) {
break;
case AVDT_AD_ST_ACP:
/* if we're listening on this channel, send ourselves a close ind */
- avdt_ad_tc_close_ind(p_tbl);
+ avdt_ad_tc_close_ind(p_tbl, 0);
break;
default:
/* get tcid from type, scb */
tcid = avdt_ad_type_to_tcid(type, p_scb);
/* call l2cap disconnect req */
- avdt_l2c_disconnect(
- avdtp_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][tcid].lcid);
+ L2CA_DisconnectReq(avdtp_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][tcid].lcid);
}
}
diff --git a/stack/avdt/avdt_api.cc b/stack/avdt/avdt_api.cc
index 9bc6f5a16..8a1079f45 100644
--- a/stack/avdt/avdt_api.cc
+++ b/stack/avdt/avdt_api.cc
@@ -29,13 +29,9 @@
#include "avdtc_api.h"
#include "bt_target.h"
#include "bt_types.h"
-#include "bta/include/bta_api.h"
#include "btm_api.h"
#include "btu.h"
#include "l2c_api.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_sec.h"
#include "stack/include/a2dp_codec_api.h"
/* Control block for AVDTP */
@@ -94,8 +90,26 @@ void avdt_scb_transport_channel_timer_timeout(void* data) {
******************************************************************************/
void AVDT_Register(AvdtpRcb* p_reg, tAVDT_CTRL_CBACK* p_cback) {
/* register PSM with L2CAP */
- L2CA_Register2(AVDT_PSM, avdt_l2c_appl, true /* enable_snoop */, nullptr,
- kAvdtpMtu, 0, BTA_SEC_AUTHENTICATE);
+ L2CA_Register(AVDT_PSM, (tL2CAP_APPL_INFO*)&avdt_l2c_appl,
+ true /* enable_snoop */, nullptr);
+
+ /* set security level */
+ BTM_SetSecurityLevel(true, "", BTM_SEC_SERVICE_AVDTP, p_reg->sec_mask,
+ AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_SIG);
+ BTM_SetSecurityLevel(false, "", BTM_SEC_SERVICE_AVDTP, p_reg->sec_mask,
+ AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_SIG);
+
+ /* do not use security on the media channel */
+ BTM_SetSecurityLevel(true, "", BTM_SEC_SERVICE_AVDTP_NOSEC, BTM_SEC_NONE,
+ AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_MEDIA);
+ BTM_SetSecurityLevel(false, "", BTM_SEC_SERVICE_AVDTP_NOSEC, BTM_SEC_NONE,
+ AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_MEDIA);
+
+ /* do not use security on the reporting channel */
+ BTM_SetSecurityLevel(true, "", BTM_SEC_SERVICE_AVDTP_NOSEC, BTM_SEC_NONE,
+ AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_REPORT);
+ BTM_SetSecurityLevel(false, "", BTM_SEC_SERVICE_AVDTP_NOSEC, BTM_SEC_NONE,
+ AVDT_PSM, BTM_SEC_PROTO_AVDT, AVDT_CHAN_REPORT);
/* initialize AVDTP data structures */
avdt_scb_init();
@@ -154,31 +168,32 @@ void AVDT_AbortReq(uint8_t handle) {
******************************************************************************/
uint16_t AVDT_CreateStream(uint8_t peer_id, uint8_t* p_handle,
const AvdtpStreamConfig& avdtp_stream_config) {
- tAVDT_RESULT result = AVDT_SUCCESS;
+ uint16_t result = AVDT_SUCCESS;
AvdtpScb* p_scb;
+ AVDT_TRACE_DEBUG("%s: peer_id=%d", __func__, peer_id);
+
/* Verify parameters; if invalid, return failure */
if (((avdtp_stream_config.cfg.psc_mask & (~AVDT_PSC)) != 0) ||
(avdtp_stream_config.p_avdt_ctrl_cback == NULL)) {
result = AVDT_BAD_PARAMS;
- LOG_ERROR("Invalid AVDT stream endpoint parameters peer_id=%d scb_index=%d",
- peer_id, avdtp_stream_config.scb_index);
}
-
/* Allocate scb; if no scbs, return failure */
else {
p_scb = avdt_scb_alloc(peer_id, avdtp_stream_config);
if (p_scb == NULL) {
- LOG_ERROR("Unable to create AVDT stream endpoint peer_id=%d scb_index=%d",
- peer_id, avdtp_stream_config.scb_index);
result = AVDT_NO_RESOURCES;
} else {
*p_handle = avdt_scb_to_hdl(p_scb);
- LOG_DEBUG("Created stream endpoint peer_id=%d handle=%hhu", peer_id,
- *p_handle);
}
}
- return static_cast<uint16_t>(result);
+
+ if (result != AVDT_SUCCESS) {
+ AVDT_TRACE_ERROR("%s: result=%d peer_id=%d scb_index=%d", __func__, result,
+ peer_id, avdtp_stream_config.scb_index);
+ }
+
+ return result;
}
/*******************************************************************************
@@ -742,6 +757,46 @@ uint16_t AVDT_ReconfigReq(uint8_t handle, AvdtpSepConfig* p_cfg) {
/*******************************************************************************
*
+ * Function AVDT_ReconfigRsp
+ *
+ * Description Respond to a reconfigure request from the peer device.
+ * This function must be called if the application receives
+ * an AVDT_RECONFIG_IND_EVT through its control callback.
+ *
+ *
+ * Returns AVDT_SUCCESS if successful, otherwise error.
+ *
+ ******************************************************************************/
+uint16_t AVDT_ReconfigRsp(uint8_t handle, uint8_t label, uint8_t error_code,
+ uint8_t category) {
+ AvdtpScb* p_scb;
+ tAVDT_SCB_EVT evt;
+ uint16_t result = AVDT_SUCCESS;
+
+ AVDT_TRACE_DEBUG("%s: avdt_handle=%d label=%d error_code=0x%x category=%d",
+ __func__, handle, label, error_code, category);
+
+ /* map handle to scb */
+ p_scb = avdt_scb_by_hdl(handle);
+ if (p_scb == NULL) {
+ result = AVDT_BAD_HANDLE;
+ }
+ /* send event to scb */
+ else {
+ evt.msg.hdr.err_code = error_code;
+ evt.msg.hdr.err_param = category;
+ evt.msg.hdr.label = label;
+ avdt_scb_event(p_scb, AVDT_SCB_API_RECONFIG_RSP_EVT, &evt);
+ }
+
+ if (result != AVDT_SUCCESS) {
+ AVDT_TRACE_ERROR("%s: result=%d avdt_handle=%d", __func__, result, handle);
+ }
+ return result;
+}
+
+/*******************************************************************************
+ *
* Function AVDT_SecurityReq
*
* Description Send a security request to the peer device. When the
@@ -886,6 +941,45 @@ uint16_t AVDT_WriteReqOpt(uint8_t handle, BT_HDR* p_pkt, uint32_t time_stamp,
/*******************************************************************************
*
+ * Function AVDT_WriteReq
+ *
+ * Description Send a media packet to the peer device. The stream must
+ * be started before this function is called. Also, this
+ * function can only be called if the stream is a SRC.
+ *
+ * When AVDTP has sent the media packet and is ready for the
+ * next packet, an AVDT_WRITE_CFM_EVT is sent to the
+ * application via the control callback. The application must
+ * wait for the AVDT_WRITE_CFM_EVT before it makes the next
+ * call to AVDT_WriteReq(). If the applications calls
+ * AVDT_WriteReq() before it receives the event the packet
+ * will not be sent. The application may make its first call
+ * to AVDT_WriteReq() after it receives an AVDT_START_CFM_EVT
+ * or AVDT_START_IND_EVT.
+ *
+ * The application passes the packet using the BT_HDR
+ * structure.
+ * This structure is described in section 2.1. The offset
+ * field must be equal to or greater than AVDT_MEDIA_OFFSET.
+ * This allows enough space in the buffer for the L2CAP and
+ * AVDTP headers.
+ *
+ * The memory pointed to by p_pkt must be a GKI buffer
+ * allocated by the application. This buffer will be freed
+ * by the protocol stack; the application must not free
+ * this buffer.
+ *
+ *
+ * Returns AVDT_SUCCESS if successful, otherwise error.
+ *
+ ******************************************************************************/
+uint16_t AVDT_WriteReq(uint8_t handle, BT_HDR* p_pkt, uint32_t time_stamp,
+ uint8_t m_pt) {
+ return AVDT_WriteReqOpt(handle, p_pkt, time_stamp, m_pt, AVDT_DATA_OPT_NONE);
+}
+
+/*******************************************************************************
+ *
* Function AVDT_ConnectReq
*
* Description This function initiates an AVDTP signaling connection
@@ -900,13 +994,13 @@ uint16_t AVDT_WriteReqOpt(uint8_t handle, BT_HDR* p_pkt, uint32_t time_stamp,
*
******************************************************************************/
uint16_t AVDT_ConnectReq(const RawAddress& bd_addr, uint8_t channel_index,
- tAVDT_CTRL_CBACK* p_cback) {
+ uint8_t sec_mask, tAVDT_CTRL_CBACK* p_cback) {
AvdtpCcb* p_ccb = NULL;
uint16_t result = AVDT_SUCCESS;
tAVDT_CCB_EVT evt;
- AVDT_TRACE_WARNING("%s: address=%s channel_index=%d", __func__,
- bd_addr.ToString().c_str(), channel_index);
+ AVDT_TRACE_WARNING("%s: address=%s channel_index=%d sec_mask=0x%x", __func__,
+ bd_addr.ToString().c_str(), channel_index, sec_mask);
/* find channel control block for this bd addr; if none, allocate one */
p_ccb = avdt_ccb_by_bd(bd_addr);
@@ -926,6 +1020,7 @@ uint16_t AVDT_ConnectReq(const RawAddress& bd_addr, uint8_t channel_index,
if (result == AVDT_SUCCESS) {
/* send event to ccb */
evt.connect.p_cback = p_cback;
+ evt.connect.sec_mask = sec_mask;
avdt_ccb_event(p_ccb, AVDT_CCB_API_CONNECT_REQ_EVT, &evt);
}
@@ -950,22 +1045,27 @@ uint16_t AVDT_ConnectReq(const RawAddress& bd_addr, uint8_t channel_index,
uint16_t AVDT_DisconnectReq(const RawAddress& bd_addr,
tAVDT_CTRL_CBACK* p_cback) {
AvdtpCcb* p_ccb = NULL;
- tAVDT_RESULT result = AVDT_SUCCESS;
+ uint16_t result = AVDT_SUCCESS;
tAVDT_CCB_EVT evt;
+ AVDT_TRACE_WARNING("%s: address=%s", __func__, bd_addr.ToString().c_str());
+
/* find channel control block for this bd addr; if none, error */
p_ccb = avdt_ccb_by_bd(bd_addr);
if (p_ccb == NULL) {
- LOG_ERROR("Unable to find AVDT stream endpoint peer:%s",
- PRIVATE_ADDRESS(bd_addr));
result = AVDT_BAD_PARAMS;
- } else {
- LOG_DEBUG("Sending disconnect request to ccb peer:%s",
- PRIVATE_ADDRESS(bd_addr));
+ }
+
+ if (result == AVDT_SUCCESS) {
+ /* send event to ccb */
evt.disconnect.p_cback = p_cback;
avdt_ccb_event(p_ccb, AVDT_CCB_API_DISCONNECT_REQ_EVT, &evt);
+ } else {
+ AVDT_TRACE_ERROR("%s: address=%s result=%d", __func__,
+ bd_addr.ToString().c_str(), result);
}
- return static_cast<uint16_t>(result);
+
+ return result;
}
/*******************************************************************************
@@ -995,6 +1095,135 @@ uint16_t AVDT_GetL2CapChannel(uint8_t handle) {
return (lcid);
}
+/*******************************************************************************
+ *
+ * Function AVDT_GetSignalChannel
+ *
+ * Description Get the L2CAP CID used by the signal channel of the given
+ * handle.
+ *
+ * Returns CID if successful, otherwise 0.
+ *
+ ******************************************************************************/
+uint16_t AVDT_GetSignalChannel(uint8_t handle, const RawAddress& bd_addr) {
+ AvdtpScb* p_scb;
+ AvdtpCcb* p_ccb;
+ uint8_t tcid = 0; /* tcid is always 0 for signal channel */
+ uint16_t lcid = 0;
+
+ /* map handle to scb */
+ if (((p_scb = avdt_scb_by_hdl(handle)) != NULL) &&
+ ((p_ccb = p_scb->p_ccb) != NULL)) {
+ lcid = avdtp_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][tcid].lcid;
+ } else {
+ p_ccb = avdt_ccb_by_bd(bd_addr);
+ if (p_ccb != NULL) {
+ lcid = avdtp_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][tcid].lcid;
+ }
+ }
+
+ return (lcid);
+}
+
+/*******************************************************************************
+ *
+ * Function AVDT_SendReport
+ *
+ * Description
+ *
+ *
+ *
+ * Returns
+ *
+ ******************************************************************************/
+uint16_t AVDT_SendReport(uint8_t handle, AVDT_REPORT_TYPE type,
+ tAVDT_REPORT_DATA* p_data) {
+ AvdtpScb* p_scb;
+ uint16_t result = AVDT_BAD_PARAMS;
+ AvdtpTransportChannel* p_tbl;
+ uint8_t *p, *plen, *pm1, *p_end;
+ uint32_t ssrc;
+ uint16_t len;
+
+ AVDT_TRACE_DEBUG("%s: avdt_handle=%d type=%d", __func__, handle, type);
+
+ /* map handle to scb && verify parameters */
+ if (((p_scb = avdt_scb_by_hdl(handle)) != NULL) && (p_scb->p_ccb != NULL) &&
+ (((type == AVDT_RTCP_PT_SR) &&
+ (p_scb->stream_config.tsep == AVDT_TSEP_SRC)) ||
+ ((type == AVDT_RTCP_PT_RR) &&
+ (p_scb->stream_config.tsep == AVDT_TSEP_SNK)) ||
+ (type == AVDT_RTCP_PT_SDES))) {
+ result = AVDT_NO_RESOURCES;
+
+ /* build SR - assume fit in one packet */
+ p_tbl = avdt_ad_tc_tbl_by_type(AVDT_CHAN_REPORT, p_scb->p_ccb, p_scb);
+ if (p_tbl->state == AVDT_AD_ST_OPEN) {
+ BT_HDR* p_pkt = (BT_HDR*)osi_malloc(p_tbl->peer_mtu + sizeof(BT_HDR));
+
+ p_pkt->offset = L2CAP_MIN_OFFSET;
+ p = (uint8_t*)(p_pkt + 1) + p_pkt->offset;
+ pm1 = p;
+ *p++ = AVDT_MEDIA_OCTET1 | 1;
+ *p++ = type;
+ /* save the location for length */
+ plen = p;
+ p += 2;
+ ssrc = avdt_scb_gen_ssrc(p_scb);
+ UINT32_TO_BE_STREAM(p, ssrc);
+
+ switch (type) {
+ case AVDT_RTCP_PT_SR: /* Sender Report */
+ *pm1 = AVDT_MEDIA_OCTET1;
+ UINT32_TO_BE_STREAM(p, p_data->sr.ntp_sec);
+ UINT32_TO_BE_STREAM(p, p_data->sr.ntp_frac);
+ UINT32_TO_BE_STREAM(p, p_data->sr.rtp_time);
+ UINT32_TO_BE_STREAM(p, p_data->sr.pkt_count);
+ UINT32_TO_BE_STREAM(p, p_data->sr.octet_count);
+ break;
+
+ case AVDT_RTCP_PT_RR: /* Receiver Report */
+ *p++ = p_data->rr.frag_lost;
+ AVDT_TRACE_API("packet_lost: %d", p_data->rr.packet_lost);
+ p_data->rr.packet_lost &= 0xFFFFFF;
+ AVDT_TRACE_API("packet_lost: %d", p_data->rr.packet_lost);
+ UINT24_TO_BE_STREAM(p, p_data->rr.packet_lost);
+ UINT32_TO_BE_STREAM(p, p_data->rr.seq_num_rcvd);
+ UINT32_TO_BE_STREAM(p, p_data->rr.jitter);
+ UINT32_TO_BE_STREAM(p, p_data->rr.lsr);
+ UINT32_TO_BE_STREAM(p, p_data->rr.dlsr);
+ break;
+
+ case AVDT_RTCP_PT_SDES: /* Source Description */
+ *p++ = AVDT_RTCP_SDES_CNAME;
+ len = strlen((char*)p_data->cname);
+ if (len > AVDT_MAX_CNAME_SIZE) len = AVDT_MAX_CNAME_SIZE;
+ *p++ = (uint8_t)len;
+ strlcpy((char*)p, (char*)p_data->cname, len + 1);
+ p += len;
+ break;
+ }
+ p_end = p;
+ len = p - pm1 - 1;
+ UINT16_TO_BE_STREAM(plen, len);
+
+ /* set the actual payload length */
+ p_pkt->len = p_end - p;
+ /* send the packet */
+ if (L2CAP_DW_FAILED !=
+ avdt_ad_write_req(AVDT_CHAN_REPORT, p_scb->p_ccb, p_scb, p_pkt))
+ result = AVDT_SUCCESS;
+ }
+ }
+
+ if (result != AVDT_SUCCESS) {
+ AVDT_TRACE_WARNING("%s: result=%d avdt_handle=%d", __func__, result,
+ handle);
+ }
+
+ return result;
+}
+
/******************************************************************************
*
* Function AVDT_SetTraceLevel
@@ -1028,6 +1257,7 @@ void stack_debug_avdtp_api_dump(int fd) {
dprintf(fd, "\nAVDTP Stack State:\n");
dprintf(fd, " AVDTP signalling L2CAP channel MTU: %d\n",
avdtp_cb.rcb.ctrl_mtu);
+ dprintf(fd, " Security mask: 0x%x\n", avdtp_cb.rcb.sec_mask);
for (size_t i = 0; i < AVDT_NUM_LINKS; i++) {
const AvdtpCcb& ccb = avdtp_cb.ccb[i];
diff --git a/stack/avdt/avdt_ccb_act.cc b/stack/avdt/avdt_ccb_act.cc
index 48b7cbcf2..3059d8ace 100644
--- a/stack/avdt/avdt_ccb_act.cc
+++ b/stack/avdt/avdt_ccb_act.cc
@@ -34,7 +34,6 @@
#include "btm_api.h"
#include "btu.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_sec.h"
/*******************************************************************************
*
@@ -77,6 +76,7 @@ static void avdt_ccb_clear_ccb(AvdtpCcb* p_ccb) {
*
******************************************************************************/
void avdt_ccb_chan_open(AvdtpCcb* p_ccb, UNUSED_ATTR tAVDT_CCB_EVT* p_data) {
+ BTM_SetOutService(p_ccb->peer_addr, BTM_SEC_SERVICE_AVDTP, AVDT_CHAN_SIG);
avdt_ad_open_req(AVDT_CHAN_SIG, p_ccb, NULL, AVDT_INT);
}
@@ -205,16 +205,10 @@ void avdt_ccb_hdl_discover_rsp(AvdtpCcb* p_ccb, tAVDT_CCB_EVT* p_data) {
*
******************************************************************************/
void avdt_ccb_hdl_getcap_cmd(AvdtpCcb* p_ccb, tAVDT_CCB_EVT* p_data) {
- /* look up scb for seid sent to us */
- AvdtpScb* p_scb = avdt_scb_by_hdl(p_data->msg.single.seid);
+ AvdtpScb* p_scb;
- if (p_scb == nullptr) {
- /* not ok, send reject */
- p_data->msg.hdr.err_code = AVDT_ERR_BAD_STATE;
- p_data->msg.hdr.err_param = p_data->msg.single.seid;
- avdt_msg_send_rej(p_ccb, AVDT_SIG_START, &p_data->msg);
- return;
- }
+ /* look up scb for seid sent to us */
+ p_scb = avdt_scb_by_hdl(p_data->msg.single.seid);
p_data->msg.svccap.p_cfg = &p_scb->stream_config.cfg;
@@ -946,6 +940,11 @@ void avdt_ccb_chk_timer(AvdtpCcb* p_ccb, UNUSED_ATTR tAVDT_CCB_EVT* p_data) {
void avdt_ccb_set_conn(AvdtpCcb* p_ccb, tAVDT_CCB_EVT* p_data) {
/* save callback */
p_ccb->p_conn_cback = p_data->connect.p_cback;
+
+ /* set security level */
+ BTM_SetSecurityLevel(true, "", BTM_SEC_SERVICE_AVDTP,
+ p_data->connect.sec_mask, AVDT_PSM, BTM_SEC_PROTO_AVDT,
+ AVDT_CHAN_SIG);
}
/*******************************************************************************
diff --git a/stack/avdt/avdt_defs.h b/stack/avdt/avdt_defs.h
index 2fed92e3d..5e3c0bdf3 100644
--- a/stack/avdt/avdt_defs.h
+++ b/stack/avdt/avdt_defs.h
@@ -62,6 +62,10 @@
/* used for general reject */
#define AVDT_SIG_NONE 0
+/* some maximum and minimum sizes of signalling messages */
+#define AVDT_DISCOVER_REQ_MIN 1
+#define AVDT_DISCOVER_REQ_MAX 124
+
/* service category information element field values */
#define AVDT_CAT_TRANS 1 /* Media Transport */
#define AVDT_CAT_REPORT 2 /* Reporting */
@@ -129,6 +133,21 @@
/* first byte of media packet header */
#define AVDT_MEDIA_OCTET1 0x80
+/* for adaptation layer header */
+/* coding of length field */
+#define AVDT_ALH_LCODE_MASK 0x03
+/* No length field present. Take length from l2cap */
+#define AVDT_ALH_LCODE_NONE 0x00
+/* 16bit length field */
+#define AVDT_ALH_LCODE_16BIT 0x01
+/* 9 bit length field, MSB = 0, 8 LSBs in 1 octet following */
+#define AVDT_ALH_LCODE_9BITM0 0x02
+/* 9 bit length field, MSB = 1, 8 LSBs in 1 octet following */
+#define AVDT_ALH_LCODE_9BITM1 0x03
+
+/* set this for continuation packet */
+#define AVDT_ALH_FRAG_MASK 0x04
+
/*****************************************************************************
* message parsing and building macros
****************************************************************************/
diff --git a/stack/avdt/avdt_int.h b/stack/avdt/avdt_int.h
index fcbdcac10..1c35448d7 100644
--- a/stack/avdt/avdt_int.h
+++ b/stack/avdt/avdt_int.h
@@ -24,8 +24,6 @@
#ifndef AVDT_INT_H
#define AVDT_INT_H
-#include <unordered_map>
-
#include "avdt_api.h"
#include "avdt_defs.h"
#include "avdtc_api.h"
@@ -100,7 +98,7 @@ enum {
};
/* state machine action enumeration list */
-enum : uint8_t {
+enum {
AVDT_CCB_CHAN_OPEN,
AVDT_CCB_CHAN_CLOSE,
AVDT_CCB_CHK_CLOSE,
@@ -234,7 +232,6 @@ enum {
AVDT_SCB_SND_SETCONFIG_REQ,
AVDT_SCB_SND_SETCONFIG_REJ,
AVDT_SCB_SND_SETCONFIG_RSP,
- AVDT_SCB_SND_SNK_DELAY_RPT_REQ,
AVDT_SCB_SND_TC_CLOSE,
AVDT_SCB_CB_ERR,
AVDT_SCB_CONG_STATE,
@@ -316,6 +313,7 @@ enum {
#define AVDT_AD_ST_UNUSED 0 /* Unused - unallocated */
#define AVDT_AD_ST_IDLE 1 /* No connection */
#define AVDT_AD_ST_ACP 2 /* Waiting to accept a connection */
+#define AVDT_AD_ST_INT 3 /* Initiating a connection */
#define AVDT_AD_ST_CONN 4 /* Waiting for connection confirm */
#define AVDT_AD_ST_CFG 5 /* Waiting for configuration complete */
#define AVDT_AD_ST_OPEN 6 /* Channel opened */
@@ -323,9 +321,16 @@ enum {
#define AVDT_AD_ST_SEC_ACP 8 /* Security process as ACP */
/* Configuration flags. AvdtpTransportChannel.cfg_flags */
+#define AVDT_L2C_CFG_IND_DONE (1 << 0)
+#define AVDT_L2C_CFG_CFM_DONE (1 << 1)
#define AVDT_L2C_CFG_CONN_INT (1 << 2)
#define AVDT_L2C_CFG_CONN_ACP (1 << 3)
+/* result code for avdt_ad_write_req() (L2CA_DataWrite()) */
+#define AVDT_AD_FAILED L2CAP_DW_FAILED /* FALSE */
+#define AVDT_AD_SUCCESS L2CAP_DW_SUCCESS /* TRUE */
+#define AVDT_AD_CONGESTED L2CAP_DW_CONGESTED /* 2 */
+
/*****************************************************************************
* data types
****************************************************************************/
@@ -361,6 +366,7 @@ typedef struct {
/* data type for AVDT_CCB_API_CONNECT_REQ_EVT */
typedef struct {
tAVDT_CTRL_CBACK* p_cback;
+ uint8_t sec_mask;
} tAVDT_CCB_API_CONNECT;
/* data type for AVDT_CCB_API_DISCONNECT_REQ_EVT */
@@ -497,7 +503,6 @@ class AvdtpScb {
uint8_t curr_evt; // current event; set only by the state machine
bool cong; // True if the media transport channel is congested
uint8_t close_code; // Error code received in close response
- bool curr_stream; // True if the SCB is the current stream, False otherwise
private:
uint8_t scb_handle_; // Unique handle for this AvdtpScb entry
@@ -643,29 +648,35 @@ class AvdtpTransportChannel {
AvdtpTransportChannel()
: peer_mtu(0),
my_mtu(0),
+ my_flush_to(0),
lcid(0),
tcid(0),
ccb_idx(0),
state(0),
- cfg_flags(0) {}
+ cfg_flags(0),
+ id(0) {}
void Reset() {
peer_mtu = 0;
my_mtu = 0;
+ my_flush_to = 0;
lcid = 0;
tcid = 0;
ccb_idx = 0;
state = 0;
cfg_flags = 0;
+ id = 0;
}
uint16_t peer_mtu; // L2CAP MTU of the peer device
uint16_t my_mtu; // Our MTU for this channel
+ uint16_t my_flush_to; // Our flush timeout for this channel
uint16_t lcid;
uint8_t tcid; // Transport channel ID
uint8_t ccb_idx; // Channel control block for with this transport channel
uint8_t state; // Transport channel state
uint8_t cfg_flags; // L2CAP configuration flags
+ uint8_t id;
};
/**
@@ -690,7 +701,7 @@ class AvdtpRoutingEntry {
*/
class AvdtpAdaptationLayer {
public:
- AvdtpAdaptationLayer() {}
+ AvdtpAdaptationLayer() : lcid_tbl{} {}
void Reset() {
for (size_t i = 0; i < AVDT_NUM_LINKS; i++) {
@@ -701,7 +712,7 @@ class AvdtpAdaptationLayer {
for (size_t i = 0; i < AVDT_NUM_TC_TBL; i++) {
tc_tbl[i].Reset();
}
- lcid_tbl.clear();
+ memset(lcid_tbl, 0, sizeof(lcid_tbl));
}
/**
@@ -715,8 +726,7 @@ class AvdtpAdaptationLayer {
AvdtpRoutingEntry rt_tbl[AVDT_NUM_LINKS][AVDT_NUM_RT_TBL];
AvdtpTransportChannel tc_tbl[AVDT_NUM_TC_TBL];
-
- std::unordered_map<uint16_t, uint8_t> lcid_tbl; // Map LCID to tc_tbl index
+ uint8_t lcid_tbl[MAX_L2CAP_CHANNELS]; // Map LCID to tc_tbl index
};
/**
@@ -912,7 +922,6 @@ extern void avdt_scb_snd_security_rsp(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data);
extern void avdt_scb_snd_setconfig_req(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data);
extern void avdt_scb_snd_setconfig_rej(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data);
extern void avdt_scb_snd_setconfig_rsp(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data);
-extern void avdt_scb_snd_snk_delay_rpt_req(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data);
extern void avdt_scb_snd_tc_close(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data);
extern void avdt_scb_cb_err(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data);
extern void avdt_scb_cong_state(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data);
@@ -948,7 +957,7 @@ extern AvdtpTransportChannel* avdt_ad_tc_tbl_by_st(uint8_t type,
extern AvdtpTransportChannel* avdt_ad_tc_tbl_by_lcid(uint16_t lcid);
extern AvdtpTransportChannel* avdt_ad_tc_tbl_alloc(AvdtpCcb* p_ccb);
extern uint8_t avdt_ad_tc_tbl_to_idx(AvdtpTransportChannel* p_tbl);
-extern void avdt_ad_tc_close_ind(AvdtpTransportChannel* p_tbl);
+extern void avdt_ad_tc_close_ind(AvdtpTransportChannel* p_tbl, uint16_t reason);
extern void avdt_ad_tc_open_ind(AvdtpTransportChannel* p_tbl);
extern void avdt_ad_tc_cong_ind(AvdtpTransportChannel* p_tbl,
bool is_congested);
@@ -995,8 +1004,4 @@ extern const tL2CAP_APPL_INFO avdt_l2c_appl;
/* reject message event lookup table */
extern const uint8_t avdt_msg_rej_2_evt[];
-void avdt_l2c_disconnect(uint16_t lcid);
-
-constexpr uint16_t kAvdtpMtu = 1024;
-
#endif /* AVDT_INT_H */
diff --git a/stack/avdt/avdt_l2c.cc b/stack/avdt/avdt_l2c.cc
index 287f25efa..db1bf2f00 100644
--- a/stack/avdt/avdt_l2c.cc
+++ b/stack/avdt/avdt_l2c.cc
@@ -22,38 +22,45 @@
*
******************************************************************************/
+#include <string.h>
+#include "avdt_api.h"
#include "avdt_int.h"
+#include "avdtc_api.h"
#include "bt_target.h"
#include "bt_types.h"
+#include "bt_utils.h"
#include "bta/include/bta_av_api.h"
#include "btm_api.h"
+#include "btm_int.h"
#include "device/include/interop.h"
#include "l2c_api.h"
#include "l2cdefs.h"
#include "osi/include/osi.h"
-#include "stack/include/acl_api.h"
/* callback function declarations */
void avdt_l2c_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
uint16_t psm, uint8_t id);
void avdt_l2c_connect_cfm_cback(uint16_t lcid, uint16_t result);
-void avdt_l2c_config_cfm_cback(uint16_t lcid, uint16_t result,
- tL2CAP_CFG_INFO* p_cfg);
+void avdt_l2c_config_cfm_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg);
void avdt_l2c_config_ind_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg);
void avdt_l2c_disconnect_ind_cback(uint16_t lcid, bool ack_needed);
+void avdt_l2c_disconnect_cfm_cback(uint16_t lcid, uint16_t result);
void avdt_l2c_congestion_ind_cback(uint16_t lcid, bool is_congested);
void avdt_l2c_data_ind_cback(uint16_t lcid, BT_HDR* p_buf);
-static void avdt_on_l2cap_error(uint16_t lcid, uint16_t result);
/* L2CAP callback function structure */
-const tL2CAP_APPL_INFO avdt_l2c_appl = {
- avdt_l2c_connect_ind_cback, avdt_l2c_connect_cfm_cback,
- avdt_l2c_config_ind_cback, avdt_l2c_config_cfm_cback,
- avdt_l2c_disconnect_ind_cback, avdt_l2c_data_ind_cback,
- avdt_l2c_congestion_ind_cback, NULL,
- avdt_on_l2cap_error, NULL,
- NULL, NULL
-};
+const tL2CAP_APPL_INFO avdt_l2c_appl = {avdt_l2c_connect_ind_cback,
+ avdt_l2c_connect_cfm_cback,
+ NULL,
+ avdt_l2c_config_ind_cback,
+ avdt_l2c_config_cfm_cback,
+ avdt_l2c_disconnect_ind_cback,
+ avdt_l2c_disconnect_cfm_cback,
+ NULL,
+ avdt_l2c_data_ind_cback,
+ avdt_l2c_congestion_ind_cback,
+ NULL, /* tL2CA_TX_COMPLETE_CB */
+ NULL /* tL2CA_CREDITS_RECEIVED_CB */};
/*******************************************************************************
*
@@ -67,21 +74,43 @@ const tL2CAP_APPL_INFO avdt_l2c_appl = {
******************************************************************************/
static void avdt_sec_check_complete_term(const RawAddress* bd_addr,
tBT_TRANSPORT transport,
- void* p_ref_data) {
+ UNUSED_ATTR void* p_ref_data,
+ uint8_t res) {
AvdtpCcb* p_ccb = NULL;
+ tL2CAP_CFG_INFO cfg;
AvdtpTransportChannel* p_tbl;
+ AVDT_TRACE_DEBUG("avdt_sec_check_complete_term res: %d", res);
p_ccb = avdt_ccb_by_bd(*bd_addr);
p_tbl = avdt_ad_tc_tbl_by_st(AVDT_CHAN_SIG, p_ccb, AVDT_AD_ST_SEC_ACP);
if (p_tbl == NULL) return;
- /* store idx in LCID table, store LCID in routing table */
- avdtp_cb.ad.lcid_tbl[p_tbl->lcid] = avdt_ad_tc_tbl_to_idx(p_tbl);
- avdtp_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][p_tbl->tcid].lcid = p_tbl->lcid;
+ if (res == BTM_SUCCESS) {
+ /* Send response to the L2CAP layer. */
+ L2CA_ConnectRsp(*bd_addr, p_tbl->id, p_tbl->lcid, L2CAP_CONN_OK,
+ L2CAP_CONN_OK);
+
+ /* store idx in LCID table, store LCID in routing table */
+ avdtp_cb.ad.lcid_tbl[p_tbl->lcid - L2CAP_BASE_APPL_CID] =
+ avdt_ad_tc_tbl_to_idx(p_tbl);
+ avdtp_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][p_tbl->tcid].lcid = p_tbl->lcid;
+
+ /* transition to configuration state */
+ p_tbl->state = AVDT_AD_ST_CFG;
- /* transition to configuration state */
- p_tbl->state = AVDT_AD_ST_CFG;
+ /* Send L2CAP config req */
+ memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ cfg.mtu_present = true;
+ cfg.mtu = p_tbl->my_mtu;
+ cfg.flush_to_present = true;
+ cfg.flush_to = p_tbl->my_flush_to;
+ L2CA_ConfigReq(p_tbl->lcid, &cfg);
+ } else {
+ L2CA_ConnectRsp(*bd_addr, p_tbl->id, p_tbl->lcid, L2CAP_CONN_SECURITY_BLOCK,
+ L2CAP_CONN_OK);
+ avdt_ad_tc_close_ind(p_tbl, L2CAP_CONN_SECURITY_BLOCK);
+ }
}
/*******************************************************************************
@@ -99,6 +128,7 @@ static void avdt_sec_check_complete_orig(const RawAddress* bd_addr,
UNUSED_ATTR void* p_ref_data,
uint8_t res) {
AvdtpCcb* p_ccb = NULL;
+ tL2CAP_CFG_INFO cfg;
AvdtpTransportChannel* p_tbl;
AVDT_TRACE_DEBUG("avdt_sec_check_complete_orig res: %d", res);
@@ -109,9 +139,17 @@ static void avdt_sec_check_complete_orig(const RawAddress* bd_addr,
if (res == BTM_SUCCESS) {
/* set channel state */
p_tbl->state = AVDT_AD_ST_CFG;
+
+ /* Send L2CAP config req */
+ memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ cfg.mtu_present = true;
+ cfg.mtu = p_tbl->my_mtu;
+ cfg.flush_to_present = true;
+ cfg.flush_to = p_tbl->my_flush_to;
+ L2CA_ConfigReq(p_tbl->lcid, &cfg);
} else {
- avdt_l2c_disconnect(p_tbl->lcid);
- avdt_ad_tc_close_ind(p_tbl);
+ L2CA_DisconnectReq(p_tbl->lcid);
+ avdt_ad_tc_close_ind(p_tbl, L2CAP_CONN_SECURITY_BLOCK);
}
}
/*******************************************************************************
@@ -129,6 +167,8 @@ void avdt_l2c_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
AvdtpCcb* p_ccb;
AvdtpTransportChannel* p_tbl = NULL;
uint16_t result;
+ tL2CAP_CFG_INFO cfg;
+ tBTM_STATUS rc;
/* do we already have a control channel for this peer? */
p_ccb = avdt_ccb_by_bd(bd_addr);
@@ -147,22 +187,31 @@ void avdt_l2c_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
} else {
/* allocate and set up entry; first channel is always signaling */
p_tbl = avdt_ad_tc_tbl_alloc(p_ccb);
- p_tbl->my_mtu = kAvdtpMtu;
+ p_tbl->my_mtu = avdtp_cb.rcb.ctrl_mtu;
+ p_tbl->my_flush_to = L2CAP_DEFAULT_FLUSH_TO;
p_tbl->tcid = AVDT_CHAN_SIG;
p_tbl->lcid = lcid;
+ p_tbl->id = id;
p_tbl->state = AVDT_AD_ST_SEC_ACP;
p_tbl->cfg_flags = AVDT_L2C_CFG_CONN_ACP;
if (interop_match_addr(INTEROP_2MBPS_LINK_ONLY, &bd_addr)) {
// Disable 3DH packets for AVDT ACL to improve sensitivity on HS
- btm_set_packet_types_from_address(
- bd_addr,
- (acl_get_supported_packet_types() | HCI_PKT_TYPES_MASK_NO_3_DH1 |
+ tACL_CONN* p_acl_cb = btm_bda_to_acl(bd_addr, BT_TRANSPORT_BR_EDR);
+ btm_set_packet_types(
+ p_acl_cb,
+ (btm_cb.btm_acl_pkt_types_supported | HCI_PKT_TYPES_MASK_NO_3_DH1 |
HCI_PKT_TYPES_MASK_NO_3_DH3 | HCI_PKT_TYPES_MASK_NO_3_DH5));
}
- /* Assume security check is complete */
- avdt_sec_check_complete_term(&p_ccb->peer_addr, BT_TRANSPORT_BR_EDR,
- nullptr);
+
+ /* Check the security */
+ rc = btm_sec_mx_access_request(bd_addr, AVDT_PSM, false,
+ BTM_SEC_PROTO_AVDT, AVDT_CHAN_SIG,
+ &avdt_sec_check_complete_term, NULL);
+ if (rc == BTM_CMD_STARTED) {
+ L2CA_ConnectRsp(p_ccb->peer_addr, p_tbl->id, lcid, L2CAP_CONN_PENDING,
+ L2CAP_CONN_OK);
+ }
return;
}
} else {
@@ -195,23 +244,27 @@ void avdt_l2c_connect_ind_cback(const RawAddress& bd_addr, uint16_t lcid,
}
}
- /* If we reject the connection, send DisconnectReq */
- if (result != L2CAP_CONN_OK) {
- L2CA_DisconnectReq(lcid);
- return;
- }
+ /* Send L2CAP connect rsp */
+ L2CA_ConnectRsp(bd_addr, id, lcid, result, 0);
/* if result ok, proceed with connection */
- /* store idx in LCID table, store LCID in routing table */
- avdtp_cb.ad.lcid_tbl[lcid] = avdt_ad_tc_tbl_to_idx(p_tbl);
- avdtp_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][p_tbl->tcid].lcid = lcid;
+ if (result == L2CAP_CONN_OK) {
+ /* store idx in LCID table, store LCID in routing table */
+ avdtp_cb.ad.lcid_tbl[lcid - L2CAP_BASE_APPL_CID] =
+ avdt_ad_tc_tbl_to_idx(p_tbl);
+ avdtp_cb.ad.rt_tbl[avdt_ccb_to_idx(p_ccb)][p_tbl->tcid].lcid = lcid;
- /* transition to configuration state */
- p_tbl->state = AVDT_AD_ST_CFG;
-}
+ /* transition to configuration state */
+ p_tbl->state = AVDT_AD_ST_CFG;
-static void avdt_on_l2cap_error(uint16_t lcid, uint16_t result) {
- avdt_l2c_disconnect(lcid);
+ /* Send L2CAP config req */
+ memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ cfg.mtu_present = true;
+ cfg.mtu = p_tbl->my_mtu;
+ cfg.flush_to_present = true;
+ cfg.flush_to = p_tbl->my_flush_to;
+ L2CA_ConfigReq(lcid, &cfg);
+ }
}
/*******************************************************************************
@@ -226,6 +279,7 @@ static void avdt_on_l2cap_error(uint16_t lcid, uint16_t result) {
******************************************************************************/
void avdt_l2c_connect_cfm_cback(uint16_t lcid, uint16_t result) {
AvdtpTransportChannel* p_tbl;
+ tL2CAP_CFG_INFO cfg;
AvdtpCcb* p_ccb;
AVDT_TRACE_DEBUG("avdt_l2c_connect_cfm_cback lcid: %d, result: %d", lcid,
@@ -240,6 +294,14 @@ void avdt_l2c_connect_cfm_cback(uint16_t lcid, uint16_t result) {
if (p_tbl->tcid != AVDT_CHAN_SIG) {
/* set channel state */
p_tbl->state = AVDT_AD_ST_CFG;
+
+ /* Send L2CAP config req */
+ memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ cfg.mtu_present = true;
+ cfg.mtu = p_tbl->my_mtu;
+ cfg.flush_to_present = true;
+ cfg.flush_to = p_tbl->my_flush_to;
+ L2CA_ConfigReq(lcid, &cfg);
} else {
p_ccb = avdt_ccb_by_idx(p_tbl->ccb_idx);
if (p_ccb == NULL) {
@@ -253,23 +315,26 @@ void avdt_l2c_connect_cfm_cback(uint16_t lcid, uint16_t result) {
if (interop_match_addr(INTEROP_2MBPS_LINK_ONLY,
(const RawAddress*)&p_ccb->peer_addr)) {
// Disable 3DH packets for AVDT ACL to improve sensitivity on HS
- btm_set_packet_types_from_address(
- p_ccb->peer_addr,
- (acl_get_supported_packet_types() |
+ tACL_CONN* p_acl_cb =
+ btm_bda_to_acl(p_ccb->peer_addr, BT_TRANSPORT_BR_EDR);
+ btm_set_packet_types(
+ p_acl_cb,
+ (btm_cb.btm_acl_pkt_types_supported |
HCI_PKT_TYPES_MASK_NO_3_DH1 | HCI_PKT_TYPES_MASK_NO_3_DH3 |
HCI_PKT_TYPES_MASK_NO_3_DH5));
}
- /* Assume security check is complete */
- avdt_sec_check_complete_orig(&p_ccb->peer_addr, BT_TRANSPORT_BR_EDR,
- nullptr, BTM_SUCCESS);
+ /* Check the security */
+ btm_sec_mx_access_request(p_ccb->peer_addr, AVDT_PSM, true,
+ BTM_SEC_PROTO_AVDT, AVDT_CHAN_SIG,
+ &avdt_sec_check_complete_orig, NULL);
}
}
}
/* failure; notify adaption that channel closed */
if (result != L2CAP_CONN_OK) {
- LOG(ERROR) << __func__ << ": invoked with non OK status";
+ avdt_ad_tc_close_ind(p_tbl, result);
}
}
}
@@ -285,10 +350,7 @@ void avdt_l2c_connect_cfm_cback(uint16_t lcid, uint16_t result) {
* Returns void
*
******************************************************************************/
-void avdt_l2c_config_cfm_cback(uint16_t lcid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
- avdt_l2c_config_ind_cback(lcid, p_cfg);
-
+void avdt_l2c_config_cfm_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
AvdtpTransportChannel* p_tbl;
AVDT_TRACE_DEBUG("%s: lcid: %d", __func__, lcid);
@@ -300,7 +362,21 @@ void avdt_l2c_config_cfm_cback(uint16_t lcid, uint16_t initiator,
/* if in correct state */
if (p_tbl->state == AVDT_AD_ST_CFG) {
- avdt_ad_tc_open_ind(p_tbl);
+ /* if result successful */
+ if (p_cfg->result == L2CAP_CONN_OK) {
+ /* update cfg_flags */
+ p_tbl->cfg_flags |= AVDT_L2C_CFG_CFM_DONE;
+
+ /* if configuration complete */
+ if (p_tbl->cfg_flags & AVDT_L2C_CFG_IND_DONE) {
+ avdt_ad_tc_open_ind(p_tbl);
+ }
+ }
+ /* else failure */
+ else {
+ /* Send L2CAP disconnect req */
+ L2CA_DisconnectReq(lcid);
+ }
}
}
}
@@ -331,6 +407,22 @@ void avdt_l2c_config_ind_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
}
AVDT_TRACE_DEBUG("%s: peer_mtu: %d, lcid: %d", __func__, p_tbl->peer_mtu,
lcid);
+
+ /* send L2CAP configure response */
+ memset(p_cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ p_cfg->result = L2CAP_CFG_OK;
+ L2CA_ConfigRsp(lcid, p_cfg);
+
+ /* if first config ind */
+ if ((p_tbl->cfg_flags & AVDT_L2C_CFG_IND_DONE) == 0) {
+ /* update cfg_flags */
+ p_tbl->cfg_flags |= AVDT_L2C_CFG_IND_DONE;
+
+ /* if configuration complete */
+ if (p_tbl->cfg_flags & AVDT_L2C_CFG_CFM_DONE) {
+ avdt_ad_tc_open_ind(p_tbl);
+ }
+ }
}
}
@@ -352,19 +444,34 @@ void avdt_l2c_disconnect_ind_cback(uint16_t lcid, bool ack_needed) {
/* look up info for this channel */
p_tbl = avdt_ad_tc_tbl_by_lcid(lcid);
if (p_tbl != NULL) {
- avdt_ad_tc_close_ind(p_tbl);
+ if (ack_needed) {
+ /* send L2CAP disconnect response */
+ L2CA_DisconnectRsp(lcid);
+ }
+
+ avdt_ad_tc_close_ind(p_tbl, 0);
}
}
-void avdt_l2c_disconnect(uint16_t lcid) {
- L2CA_DisconnectReq(lcid);
+/*******************************************************************************
+ *
+ * Function avdt_l2c_disconnect_cfm_cback
+ *
+ * Description This is the L2CAP disconnect confirm callback function.
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void avdt_l2c_disconnect_cfm_cback(uint16_t lcid, uint16_t result) {
AvdtpTransportChannel* p_tbl;
- AVDT_TRACE_DEBUG("avdt_l2c_disconnect_cfm_cback lcid: %d", lcid);
+ AVDT_TRACE_DEBUG("avdt_l2c_disconnect_cfm_cback lcid: %d, result: %d", lcid,
+ result);
/* look up info for this channel */
p_tbl = avdt_ad_tc_tbl_by_lcid(lcid);
if (p_tbl != NULL) {
- avdt_ad_tc_close_ind(p_tbl);
+ avdt_ad_tc_close_ind(p_tbl, result);
}
}
diff --git a/stack/avdt/avdt_msg.cc b/stack/avdt/avdt_msg.cc
index bb49ede3e..33fbfa744 100644
--- a/stack/avdt/avdt_msg.cc
+++ b/stack/avdt/avdt_msg.cc
@@ -26,8 +26,7 @@
*
******************************************************************************/
-#define LOG_TAG "bluetooth"
-
+#include <log/log.h>
#include <string.h>
#include "avdt_api.h"
#include "avdt_int.h"
@@ -37,7 +36,6 @@
#include "bt_types.h"
#include "bt_utils.h"
#include "btu.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
/*****************************************************************************
@@ -1002,7 +1000,9 @@ static uint8_t avdt_msg_prs_rej(tAVDT_MSG* p_msg, uint8_t* p, uint16_t len,
}
if (len < 1) {
- android_errorWriteLog(0x534e4554, "79702484");
+ char error_info[] = "AVDT rejected response length mismatch";
+ android_errorWriteWithInfoLog(0x534e4554, "79702484", -1, error_info,
+ strlen(error_info));
error = AVDT_ERR_LENGTH;
} else {
p_msg->hdr.err_code = *p;
diff --git a/stack/avdt/avdt_scb.cc b/stack/avdt/avdt_scb.cc
index e83c3fa39..c1c0de437 100644
--- a/stack/avdt/avdt_scb.cc
+++ b/stack/avdt/avdt_scb.cc
@@ -112,7 +112,6 @@ const tAVDT_SCB_ACTION avdt_scb_action[] = {avdt_scb_hdl_abort_cmd,
avdt_scb_snd_setconfig_req,
avdt_scb_snd_setconfig_rej,
avdt_scb_snd_setconfig_rsp,
- avdt_scb_snd_snk_delay_rpt_req,
avdt_scb_snd_tc_close,
avdt_scb_cb_err,
avdt_scb_cong_state,
@@ -159,7 +158,7 @@ const uint8_t avdt_scb_st_idle[][AVDT_SCB_NUM_COLS] = {
/* API_GETCONFIG_RSP_EVT */
{AVDT_SCB_IGNORE, AVDT_SCB_IGNORE, AVDT_SCB_IDLE_ST},
/* API_SETCONFIG_RSP_EVT */
- {AVDT_SCB_SND_SETCONFIG_RSP, AVDT_SCB_SND_SNK_DELAY_RPT_REQ, AVDT_SCB_CONF_ST},
+ {AVDT_SCB_SND_SETCONFIG_RSP, AVDT_SCB_IGNORE, AVDT_SCB_CONF_ST},
/* API_SETCONFIG_REJ_EVT */
{AVDT_SCB_SND_SETCONFIG_REJ, AVDT_SCB_IGNORE, AVDT_SCB_IDLE_ST},
/* API_OPEN_RSP_EVT */
@@ -759,6 +758,7 @@ const tAVDT_SCB_ST_TBL avdt_scb_st_tbl[] = {
void avdt_scb_event(AvdtpScb* p_scb, uint8_t event, tAVDT_SCB_EVT* p_data) {
tAVDT_SCB_ST_TBL state_table;
uint8_t action;
+ int i;
#if (AVDT_DEBUG == TRUE)
AVDT_TRACE_EVENT(
@@ -766,36 +766,6 @@ void avdt_scb_event(AvdtpScb* p_scb, uint8_t event, tAVDT_SCB_EVT* p_data) {
__func__, avdt_scb_to_hdl(p_scb), event, avdt_scb_evt_str[event],
avdt_scb_st_str[p_scb->state], p_scb, p_scb->stream_config.scb_index);
#endif
-
- /* Check that we only send AVDT_SCB_API_WRITE_REQ_EVT to the active stream
- * device */
- uint8_t num_st_streams = 0;
- int ccb_index = -1;
- int scb_index = -1;
-
- for (int i = 0; i < AVDT_NUM_LINKS; i++) {
- for (int j = 0; j < AVDT_NUM_SEPS; j++) {
- AvdtpScb* p_avdt_scb = &avdtp_cb.ccb[i].scb[j];
- if (p_avdt_scb->allocated &&
- avdt_scb_st_tbl[p_avdt_scb->state] == avdt_scb_st_stream) {
- num_st_streams++;
- ccb_index = i;
- scb_index = j;
- } else {
- p_avdt_scb->curr_stream = false;
- }
- }
- }
-
- if (num_st_streams == 1) {
- avdtp_cb.ccb[ccb_index].scb[scb_index].curr_stream = true;
- } else if (num_st_streams > 1 && !p_scb->curr_stream &&
- event == AVDT_SCB_API_WRITE_REQ_EVT) {
- AVDT_TRACE_ERROR("%s: ignore AVDT_SCB_API_WRITE_REQ_EVT", __func__);
- avdt_scb_free_pkt(p_scb, p_data);
- return;
- }
-
/* set current event */
p_scb->curr_evt = event;
@@ -808,7 +778,7 @@ void avdt_scb_event(AvdtpScb* p_scb, uint8_t event, tAVDT_SCB_EVT* p_data) {
}
/* execute action functions */
- for (int i = 0; i < AVDT_SCB_ACTIONS; i++) {
+ for (i = 0; i < AVDT_SCB_ACTIONS; i++) {
action = state_table[event][i];
if (action != AVDT_SCB_IGNORE) {
(*avdtp_cb.p_scb_act[action])(p_scb, p_data);
@@ -951,54 +921,51 @@ AvdtpScb* avdt_scb_by_hdl(uint8_t hdl) {
******************************************************************************/
uint8_t avdt_scb_verify(AvdtpCcb* p_ccb, uint8_t state, uint8_t* p_seid,
uint16_t num_seid, uint8_t* p_err_code) {
+ int i;
+ AvdtpScb* p_scb;
+ uint8_t nsc_mask;
+ uint8_t ret = 0;
+
AVDT_TRACE_DEBUG("avdt_scb_verify state %d", state);
/* set nonsupported command mask */
/* translate public state into private state */
- uint8_t nsc_mask = 0;
+ nsc_mask = 0;
if (state == AVDT_VERIFY_SUSPEND) {
nsc_mask = AvdtpStreamConfig::AVDT_NSC_SUSPEND;
}
/* verify every scb */
- *p_err_code = 0;
- for (int i = 0; (i < num_seid) && (i < AVDT_NUM_SEPS); i++) {
- AvdtpScb* p_scb = avdt_scb_by_hdl(p_seid[i]);
- if (p_scb == NULL) {
+ for (i = 0, *p_err_code = 0;
+ (i < num_seid) && (*p_err_code == 0) && (i < AVDT_NUM_SEPS); i++) {
+ p_scb = avdt_scb_by_hdl(p_seid[i]);
+ if (p_scb == NULL)
*p_err_code = AVDT_ERR_BAD_STATE;
- return p_seid[i];
- }
-
- if (p_scb->p_ccb != p_ccb) {
+ else if (p_scb->p_ccb != p_ccb)
*p_err_code = AVDT_ERR_BAD_STATE;
- return p_seid[i];
- }
-
- if (p_scb->stream_config.nsc_mask & nsc_mask) {
+ else if (p_scb->stream_config.nsc_mask & nsc_mask)
*p_err_code = AVDT_ERR_NSC;
- return p_seid[i];
- }
switch (state) {
case AVDT_VERIFY_OPEN:
case AVDT_VERIFY_START:
if (p_scb->state != AVDT_SCB_OPEN_ST &&
- p_scb->state != AVDT_SCB_STREAM_ST) {
+ p_scb->state != AVDT_SCB_STREAM_ST)
*p_err_code = AVDT_ERR_BAD_STATE;
- return p_seid[i];
- }
break;
case AVDT_VERIFY_SUSPEND:
case AVDT_VERIFY_STREAMING:
- if (p_scb->state != AVDT_SCB_STREAM_ST) {
+ if (p_scb->state != AVDT_SCB_STREAM_ST)
*p_err_code = AVDT_ERR_BAD_STATE;
- return p_seid[i];
- }
break;
}
}
- return 0;
+ if ((i != num_seid) && (i < AVDT_NUM_SEPS)) {
+ ret = p_seid[i];
+ }
+
+ return ret;
}
/*******************************************************************************
diff --git a/stack/avdt/avdt_scb_act.cc b/stack/avdt/avdt_scb_act.cc
index 81293444b..9ff926509 100644
--- a/stack/avdt/avdt_scb_act.cc
+++ b/stack/avdt/avdt_scb_act.cc
@@ -23,8 +23,7 @@
*
******************************************************************************/
-#define LOG_TAG "bluetooth"
-
+#include <cutils/log.h>
#include <string.h>
#include "a2dp_codec_api.h"
#include "avdt_api.h"
@@ -35,7 +34,6 @@
#include "bt_types.h"
#include "bt_utils.h"
#include "btu.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
/* This table is used to lookup the callback event that matches a particular
@@ -644,56 +642,22 @@ void avdt_scb_hdl_setconfig_rej(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data) {
/*******************************************************************************
*
- * Function avdt_scb_snd_snk_delay_rpt_req
- *
- * Description This function sends the delay report request once it is sink
- *
- * Returns Nothing.
- *
- ******************************************************************************/
-void avdt_scb_snd_snk_delay_rpt_req(AvdtpScb* p_scb,
- UNUSED_ATTR tAVDT_SCB_EVT* p_data) {
- if (p_scb->p_ccb == NULL) {
- return;
- }
-
- // In sink mode, report a fixed delay value when this device is the sink
- // side. Delay value in this function is in unit of 1/10ms.
- if (p_scb->stream_config.tsep != AVDT_TSEP_SNK) {
- return;
- }
-
- tAVDT_SCB_EVT evt;
- evt.apidelay.hdr.seid = p_scb->peer_seid;
- evt.apidelay.delay = AVDT_SINK_DELAY_MS * 10;
- avdt_scb_event(p_scb, AVDT_SCB_API_DELAY_RPT_REQ_EVT, &evt);
-}
-
-/*******************************************************************************
- *
* Function avdt_scb_hdl_setconfig_rsp
*
* Description This function sends the SCB an AVDT_SCB_API_OPEN_REQ_EVT
* to initiate sending of an open command message.
*
- * This function sends the SCB an AVDT_SCB_API_DELAY_RPT_REQ_EVT
- * to initiate sending of delay report command message only
- * when the endpoint takes sink role.
- *
* Returns Nothing.
*
******************************************************************************/
-void avdt_scb_hdl_setconfig_rsp(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data) {
+void avdt_scb_hdl_setconfig_rsp(AvdtpScb* p_scb,
+ UNUSED_ATTR tAVDT_SCB_EVT* p_data) {
tAVDT_EVT_HDR single;
if (p_scb->p_ccb != NULL) {
/* save configuration */
p_scb->curr_cfg = p_scb->req_cfg;
- // In sink mode, report delay value when this device initiates the connection.
- // Delay reporting is sent before open request (i.e., in configured state).
- avdt_scb_snd_snk_delay_rpt_req(p_scb, p_data);
-
/* initiate open */
single.seid = p_scb->peer_seid;
tAVDT_SCB_EVT avdt_scb_evt;
@@ -839,10 +803,8 @@ void avdt_scb_hdl_tc_close(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data) {
*
******************************************************************************/
void avdt_scb_snd_delay_rpt_req(AvdtpScb* p_scb, tAVDT_SCB_EVT* p_data) {
- if (p_scb->stream_config.cfg.psc_mask & AVDT_PSC_DELAY_RPT) {
- avdt_msg_send_cmd(p_scb->p_ccb, p_scb, AVDT_SIG_DELAY_RPT,
- (tAVDT_MSG*)&p_data->apidelay);
- }
+ avdt_msg_send_cmd(p_scb->p_ccb, p_scb, AVDT_SIG_DELAY_RPT,
+ (tAVDT_MSG*)&p_data->apidelay);
}
/*******************************************************************************
diff --git a/stack/avrc/avrc_api.cc b/stack/avrc/avrc_api.cc
index 432cae04f..41454110c 100644
--- a/stack/avrc/avrc_api.cc
+++ b/stack/avrc/avrc_api.cc
@@ -24,12 +24,13 @@
#include <base/logging.h>
#include <string.h>
+#include <log/log.h>
+
#include "avrc_api.h"
#include "avrc_int.h"
#include "bt_common.h"
#include "btu.h"
#include "osi/include/fixed_queue.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
#include "osi/include/properties.h"
@@ -315,7 +316,7 @@ static uint16_t avrc_send_continue_frag(uint8_t handle, uint8_t label) {
if (p_pkt->len > AVRC_MAX_CTRL_DATA_LEN) {
int offset_len = MAX(AVCT_MSG_OFFSET, p_pkt->offset);
p_pkt_old = p_fcb->p_fmsg;
- p_pkt = (BT_HDR*)osi_calloc(AVRC_PACKET_LEN + offset_len + BT_HDR_SIZE);
+ p_pkt = (BT_HDR*)osi_malloc(AVRC_PACKET_LEN + offset_len + BT_HDR_SIZE);
p_pkt->len = AVRC_MAX_CTRL_DATA_LEN;
p_pkt->offset = AVCT_MSG_OFFSET;
p_pkt->layer_specific = p_pkt_old->layer_specific;
@@ -425,7 +426,7 @@ static BT_HDR* avrc_proc_vendor_command(uint8_t handle, uint8_t label,
}
if (status != AVRC_STS_NO_ERROR) {
- p_rsp = (BT_HDR*)osi_calloc(BT_DEFAULT_BUFFER_SIZE);
+ p_rsp = (BT_HDR*)osi_malloc(BT_DEFAULT_BUFFER_SIZE);
p_rsp->offset = p_pkt->offset;
p_data = (uint8_t*)(p_rsp + 1) + p_pkt->offset;
*p_data++ = AVRC_RSP_REJ;
@@ -486,7 +487,7 @@ static uint8_t avrc_proc_far_msg(uint8_t handle, uint8_t label, uint8_t cr,
if (pkt_type == AVRC_PKT_START) {
/* Allocate buffer for re-assembly */
p_rcb->rasm_pdu = *p_data;
- p_rcb->p_rmsg = (BT_HDR*)osi_calloc(BT_DEFAULT_BUFFER_SIZE);
+ p_rcb->p_rmsg = (BT_HDR*)osi_malloc(BT_DEFAULT_BUFFER_SIZE);
/* Copy START packet to buffer for re-assembling fragments */
memcpy(p_rcb->p_rmsg, p_pkt, sizeof(BT_HDR)); /* Copy bt hdr */
@@ -922,7 +923,7 @@ static BT_HDR* avrc_pass_msg(tAVRC_MSG_PASS* p_msg) {
CHECK(p_msg != NULL);
CHECK(AVRC_CMD_BUF_SIZE > (AVRC_MIN_CMD_LEN + p_msg->pass_len));
- BT_HDR* p_cmd = (BT_HDR*)osi_calloc(AVRC_CMD_BUF_SIZE);
+ BT_HDR* p_cmd = (BT_HDR*)osi_malloc(AVRC_CMD_BUF_SIZE);
p_cmd->offset = AVCT_MSG_OFFSET;
p_cmd->layer_specific = AVCT_DATA_CTRL;
@@ -951,33 +952,6 @@ static BT_HDR* avrc_pass_msg(tAVRC_MSG_PASS* p_msg) {
/******************************************************************************
*
- * Function ARVC_GetProfileVersion
- *
- * Description Get the user assigned AVRCP profile version
- *
- * Returns The AVRCP profile version
- *
- *****************************************************************************/
-uint16_t AVRC_GetProfileVersion() {
- uint16_t profile_version = AVRC_REV_1_4;
- char avrcp_version[PROPERTY_VALUE_MAX] = {0};
- osi_property_get(AVRC_VERSION_PROPERTY, avrcp_version, AVRC_DEFAULT_VERSION);
-
- if (!strncmp(AVRC_1_6_STRING, avrcp_version, sizeof(AVRC_1_6_STRING))) {
- profile_version = AVRC_REV_1_6;
- } else if (!strncmp(AVRC_1_5_STRING, avrcp_version,
- sizeof(AVRC_1_5_STRING))) {
- profile_version = AVRC_REV_1_5;
- } else if (!strncmp(AVRC_1_3_STRING, avrcp_version,
- sizeof(AVRC_1_3_STRING))) {
- profile_version = AVRC_REV_1_3;
- }
-
- return profile_version;
-}
-
-/******************************************************************************
- *
* Function AVRC_Open
*
* Description This function is called to open a connection to AVCTP.
@@ -1217,7 +1191,7 @@ uint16_t AVRC_MsgReq(uint8_t handle, uint8_t label, uint8_t ctype,
if (p_pkt->len > AVRC_MAX_CTRL_DATA_LEN) {
int offset_len = MAX(AVCT_MSG_OFFSET, p_pkt->offset);
BT_HDR* p_pkt_new =
- (BT_HDR*)osi_calloc(AVRC_PACKET_LEN + offset_len + BT_HDR_SIZE);
+ (BT_HDR*)osi_malloc(AVRC_PACKET_LEN + offset_len + BT_HDR_SIZE);
if (p_start != NULL) {
p_fcb->frag_enabled = true;
p_fcb->p_fmsg = p_pkt;
diff --git a/stack/avrc/avrc_bld_ct.cc b/stack/avrc/avrc_bld_ct.cc
index 4d85d1797..384ae6091 100644
--- a/stack/avrc/avrc_bld_ct.cc
+++ b/stack/avrc/avrc_bld_ct.cc
@@ -536,7 +536,7 @@ static BT_HDR* avrc_bld_init_cmd_buffer(tAVRC_COMMAND* p_cmd) {
}
/* allocate and initialize the buffer */
- BT_HDR* p_pkt = (BT_HDR*)osi_calloc(AVRC_META_CMD_BUF_SIZE);
+ BT_HDR* p_pkt = (BT_HDR*)osi_malloc(AVRC_META_CMD_BUF_SIZE);
uint8_t *p_data, *p_start;
p_pkt->layer_specific = chnl;
diff --git a/stack/avrc/avrc_bld_tg.cc b/stack/avrc/avrc_bld_tg.cc
index 73da3456e..1dac160f0 100644
--- a/stack/avrc/avrc_bld_tg.cc
+++ b/stack/avrc/avrc_bld_tg.cc
@@ -1322,7 +1322,7 @@ static BT_HDR* avrc_bld_init_rsp_buffer(tAVRC_RESPONSE* p_rsp) {
}
/* allocate and initialize the buffer */
- BT_HDR* p_pkt = (BT_HDR*)osi_calloc(BT_DEFAULT_BUFFER_SIZE);
+ BT_HDR* p_pkt = (BT_HDR*)osi_malloc(BT_DEFAULT_BUFFER_SIZE);
uint8_t *p_data, *p_start;
p_pkt->layer_specific = chnl;
diff --git a/stack/avrc/avrc_int.h b/stack/avrc/avrc_int.h
index d3fbc768e..779a90af6 100644
--- a/stack/avrc/avrc_int.h
+++ b/stack/avrc/avrc_int.h
@@ -25,10 +25,10 @@
#ifndef AVRC_INT_H
#define AVRC_INT_H
+#include "avct_defs.h"
+#include "avrc_api.h"
#include "osi/include/alarm.h"
#include "osi/include/fixed_queue.h"
-#include "stack/avct/avct_defs.h"
-#include "stack/include/avrc_api.h"
/* DEBUG FLAGS
*
diff --git a/stack/avrc/avrc_opt.cc b/stack/avrc/avrc_opt.cc
index a9ad908d3..de42e15f1 100644
--- a/stack/avrc/avrc_opt.cc
+++ b/stack/avrc/avrc_opt.cc
@@ -51,7 +51,7 @@ static BT_HDR* avrc_vendor_msg(tAVRC_MSG_VENDOR* p_msg) {
CHECK(p_msg != NULL);
CHECK(AVRC_META_CMD_BUF_SIZE > (AVRC_MIN_CMD_LEN + p_msg->vendor_len));
- p_cmd = (BT_HDR*)osi_calloc(AVRC_META_CMD_BUF_SIZE);
+ p_cmd = (BT_HDR*)osi_malloc(AVRC_META_CMD_BUF_SIZE);
p_cmd->offset = AVCT_MSG_OFFSET;
p_data = (uint8_t*)(p_cmd + 1) + p_cmd->offset;
@@ -91,7 +91,7 @@ static BT_HDR* avrc_vendor_msg(tAVRC_MSG_VENDOR* p_msg) {
*
*****************************************************************************/
uint16_t AVRC_UnitCmd(uint8_t handle, uint8_t label) {
- BT_HDR* p_cmd = (BT_HDR*)osi_calloc(AVRC_CMD_BUF_SIZE);
+ BT_HDR* p_cmd = (BT_HDR*)osi_malloc(AVRC_CMD_BUF_SIZE);
uint8_t* p_data;
p_cmd->offset = AVCT_MSG_OFFSET;
@@ -134,7 +134,7 @@ uint16_t AVRC_UnitCmd(uint8_t handle, uint8_t label) {
*
*****************************************************************************/
uint16_t AVRC_SubCmd(uint8_t handle, uint8_t label, uint8_t page) {
- BT_HDR* p_cmd = (BT_HDR*)osi_calloc(AVRC_CMD_BUF_SIZE);
+ BT_HDR* p_cmd = (BT_HDR*)osi_malloc(AVRC_CMD_BUF_SIZE);
uint8_t* p_data;
p_cmd->offset = AVCT_MSG_OFFSET;
diff --git a/stack/avrc/avrc_pars_ct.cc b/stack/avrc/avrc_pars_ct.cc
index 2141bf179..619aace9a 100644
--- a/stack/avrc/avrc_pars_ct.cc
+++ b/stack/avrc/avrc_pars_ct.cc
@@ -22,7 +22,7 @@
#include "avrc_int.h"
#include "bt_common.h"
#include "bt_utils.h"
-#include "osi/include/log.h"
+#include "log/log.h"
#include "osi/include/osi.h"
/*****************************************************************************
@@ -308,7 +308,7 @@ static tAVRC_STS avrc_pars_browse_rsp(tAVRC_MSG_BROWSE* p_msg,
BE_STREAM_TO_UINT16(player->name.str_len, p);
min_len += player->name.str_len;
if (pkt_len < min_len) goto browse_length_error;
- player->name.p_str = (uint8_t*)osi_calloc(
+ player->name.p_str = (uint8_t*)osi_malloc(
(player->name.str_len + 1) * sizeof(uint8_t));
BE_STREAM_TO_ARRAY(p, player->name.p_str, player->name.str_len);
AVRC_TRACE_DEBUG(
@@ -336,7 +336,7 @@ static tAVRC_STS avrc_pars_browse_rsp(tAVRC_MSG_BROWSE* p_msg,
BE_STREAM_TO_UINT16(folder->name.str_len, p);
min_len += folder->name.str_len;
if (pkt_len < min_len) goto browse_length_error;
- folder->name.p_str = (uint8_t*)osi_calloc(
+ folder->name.p_str = (uint8_t*)osi_malloc(
(folder->name.str_len + 1) * sizeof(uint8_t));
BE_STREAM_TO_ARRAY(p, folder->name.p_str, folder->name.str_len);
AVRC_TRACE_DEBUG("%s type %d playable %d cs %d name len %d",
@@ -495,7 +495,7 @@ static tAVRC_STS avrc_pars_browse_rsp(tAVRC_MSG_BROWSE* p_msg,
AVRC_TRACE_DEBUG("%s AVRC_PDU_SET_BROWSED_PLAYER item: %d len: %d",
__func__, i, folder_name->str_len);
folder_name->p_str =
- (uint8_t*)osi_calloc((folder_name->str_len + 1) * sizeof(uint8_t));
+ (uint8_t*)osi_malloc((folder_name->str_len + 1) * sizeof(uint8_t));
BE_STREAM_TO_ARRAY(p, folder_name->p_str, folder_name->str_len);
}
break;
diff --git a/stack/avrc/avrc_pars_tg.cc b/stack/avrc/avrc_pars_tg.cc
index c59c18dee..190a88d75 100644
--- a/stack/avrc/avrc_pars_tg.cc
+++ b/stack/avrc/avrc_pars_tg.cc
@@ -21,8 +21,7 @@
#include "avrc_defs.h"
#include "avrc_int.h"
#include "bt_common.h"
-
-#include "osi/include/log.h"
+#include "log/log.h"
/*****************************************************************************
* Global data
@@ -119,13 +118,6 @@ static tAVRC_STS avrc_pars_vendor_cmd(tAVRC_MSG_VENDOR* p_msg,
if (p_msg->vendor_len == 0) return AVRC_STS_NO_ERROR;
if (p_msg->p_vendor_data == NULL) return AVRC_STS_INTERNAL_ERR;
- if (p_msg->vendor_len < 4) {
- android_errorWriteLog(0x534e4554, "168712382");
- AVRC_TRACE_WARNING("%s: message length %d too short: must be at least 4",
- __func__, p_msg->vendor_len);
- return AVRC_STS_INTERNAL_ERR;
- }
-
p = p_msg->p_vendor_data;
p_result->pdu = *p++;
AVRC_TRACE_DEBUG("%s pdu:0x%x", __func__, p_result->pdu);
diff --git a/stack/avrc/avrc_sdp.cc b/stack/avrc/avrc_sdp.cc
index a07b03640..860a8d0df 100644
--- a/stack/avrc/avrc_sdp.cc
+++ b/stack/avrc/avrc_sdp.cc
@@ -54,7 +54,7 @@ static uint16_t a2dp_attr_list_sdp[] = {
* Returns Nothing.
*
*****************************************************************************/
-static void avrc_sdp_cback(tSDP_STATUS status) {
+static void avrc_sdp_cback(uint16_t status) {
AVRC_TRACE_API("%s status: %d", __func__, status);
/* reset service_uuid, so can start another find service */
@@ -174,9 +174,6 @@ uint16_t AVRC_FindService(uint16_t service_uuid, const RawAddress& bd_addr,
*
* profile_version: profile version of avrcp record.
*
- * cover_art_psm: The PSM of a cover art service, if
- * supported. Use 0 Otherwise. Ignored on controller
- *
* Output Parameters:
* None.
*
@@ -188,7 +185,7 @@ uint16_t AVRC_FindService(uint16_t service_uuid, const RawAddress& bd_addr,
uint16_t AVRC_AddRecord(uint16_t service_uuid, const char* p_service_name,
const char* p_provider_name, uint16_t categories,
uint32_t sdp_handle, bool browse_supported,
- uint16_t profile_version, uint16_t cover_art_psm) {
+ uint16_t profile_version) {
uint16_t browse_list[1];
bool result = true;
uint8_t temp[8];
@@ -197,9 +194,7 @@ uint16_t AVRC_AddRecord(uint16_t service_uuid, const char* p_service_name,
uint8_t index = 0;
uint16_t class_list[2];
- AVRC_TRACE_API("%s: Add AVRCP SDP record, uuid: %x, profile_version: 0x%x, "
- "supported_features: 0x%x, psm: 0x%x", __func__, service_uuid,
- profile_version, categories, cover_art_psm);
+ AVRC_TRACE_API("%s uuid: %x", __func__, service_uuid);
if (service_uuid != UUID_SERVCLASS_AV_REM_CTRL_TARGET &&
service_uuid != UUID_SERVCLASS_AV_REMOTE_CONTROL)
@@ -240,58 +235,20 @@ uint16_t AVRC_AddRecord(uint16_t service_uuid, const char* p_service_name,
&avrc_proto_desc_list[0]);
/* additional protocal descriptor, required only for version > 1.3 */
- if (profile_version > AVRC_REV_1_3) {
- int num_additional_protocols = 0;
- int i = 0;
- tSDP_PROTO_LIST_ELEM avrc_add_proto_desc_lists[2];
-
- /* If we support browsing then add the list */
- if (browse_supported) {
- AVRC_TRACE_API("%s: Add Browsing PSM to additonal protocol descriptor"
- " lists", __func__);
- num_additional_protocols++;
- avrc_add_proto_desc_lists[i].num_elems = 2;
- avrc_add_proto_desc_lists[i].list_elem[0].num_params = 1;
- avrc_add_proto_desc_lists[i].list_elem[0].protocol_uuid =
- UUID_PROTOCOL_L2CAP;
- avrc_add_proto_desc_lists[i].list_elem[0].params[0] = AVCT_BR_PSM;
- avrc_add_proto_desc_lists[i].list_elem[0].params[1] = 0;
- avrc_add_proto_desc_lists[i].list_elem[1].num_params = 1;
- avrc_add_proto_desc_lists[i].list_elem[1].protocol_uuid =
- UUID_PROTOCOL_AVCTP;
- avrc_add_proto_desc_lists[i].list_elem[1].params[0] =
- protocol_reported_version;
- avrc_add_proto_desc_lists[i].list_elem[1].params[1] = 0;
- i++;
- }
-
- /* Add the BIP PSM for cover art on 1.6+ target devices that support it */
- if (profile_version >= AVRC_REV_1_6 &&
- service_uuid == UUID_SERVCLASS_AV_REM_CTRL_TARGET &&
- cover_art_psm > 0) {
- AVRC_TRACE_API("%s: Add AVRCP BIP PSM to additonal protocol descriptor"
- " lists, psm: 0x%x", __func__, cover_art_psm);
- num_additional_protocols++;
- avrc_add_proto_desc_lists[i].num_elems = 2;
- avrc_add_proto_desc_lists[i].list_elem[0].num_params = 1;
- avrc_add_proto_desc_lists[i].list_elem[0].protocol_uuid =
- UUID_PROTOCOL_L2CAP;
- avrc_add_proto_desc_lists[i].list_elem[0].params[0] = cover_art_psm;
- avrc_add_proto_desc_lists[i].list_elem[0].params[1] = 0;
- avrc_add_proto_desc_lists[i].list_elem[1].num_params = 0;
- avrc_add_proto_desc_lists[i].list_elem[1].protocol_uuid =
- UUID_PROTOCOL_OBEX;
- avrc_add_proto_desc_lists[i].list_elem[1].params[0] = 0;
- i++;
- }
-
- /* Add the additional lists if we support any */
- if (num_additional_protocols > 0) {
- AVRC_TRACE_API("%s: Add %d additonal protocol descriptor lists",
- __func__, num_additional_protocols);
- result &= SDP_AddAdditionProtoLists(sdp_handle, num_additional_protocols,
- avrc_add_proto_desc_lists);
- }
+ if ((profile_version > AVRC_REV_1_3) && (browse_supported)) {
+ tSDP_PROTO_LIST_ELEM avrc_add_proto_desc_list;
+ avrc_add_proto_desc_list.num_elems = 2;
+ avrc_add_proto_desc_list.list_elem[0].num_params = 1;
+ avrc_add_proto_desc_list.list_elem[0].protocol_uuid = UUID_PROTOCOL_L2CAP;
+ avrc_add_proto_desc_list.list_elem[0].params[0] = AVCT_BR_PSM;
+ avrc_add_proto_desc_list.list_elem[0].params[1] = 0;
+ avrc_add_proto_desc_list.list_elem[1].num_params = 1;
+ avrc_add_proto_desc_list.list_elem[1].protocol_uuid = UUID_PROTOCOL_AVCTP;
+ avrc_add_proto_desc_list.list_elem[1].params[0] = protocol_reported_version;
+ avrc_add_proto_desc_list.list_elem[1].params[1] = 0;
+
+ result &=
+ SDP_AddAdditionProtoLists(sdp_handle, 1, &avrc_add_proto_desc_list);
}
/* add profile descriptor list */
result &= SDP_AddProfileDescriptorList(
@@ -325,25 +282,6 @@ uint16_t AVRC_AddRecord(uint16_t service_uuid, const char* p_service_name,
return (result ? AVRC_SUCCESS : AVRC_FAIL);
}
-/*******************************************************************************
- *
- * Function AVRC_RemoveRecord
- *
- * Description This function is called to remove an AVRCP SDP record.
- *
- * Input Parameters:
- * sdp_handle: Handle you used with AVRC_AddRecord
- *
- * Returns AVRC_SUCCESS if successful.
- * AVRC_FAIL otherwise
- *
- *******************************************************************************/
-uint16_t AVRC_RemoveRecord(uint32_t sdp_handle) {
- AVRC_TRACE_API("%s: remove AVRCP SDP record", __func__);
- bool result = SDP_DeleteRecord(sdp_handle);
- return (result ? AVRC_SUCCESS : AVRC_FAIL);
-}
-
/******************************************************************************
*
* Function AVRC_SetTraceLevel
diff --git a/stack/bnep/bnep_api.cc b/stack/bnep/bnep_api.cc
index 455dc168d..809d0b237 100644
--- a/stack/bnep/bnep_api.cc
+++ b/stack/bnep/bnep_api.cc
@@ -25,8 +25,6 @@
#include "bnep_api.h"
#include <string.h>
#include "bnep_int.h"
-#include "bta/include/bta_api.h"
-#include "stack/btm/btm_sec.h"
using bluetooth::Uuid;
@@ -128,8 +126,7 @@ void BNEP_Deregister(void) {
*
******************************************************************************/
tBNEP_RESULT BNEP_Connect(const RawAddress& p_rem_bda, const Uuid& src_uuid,
- const Uuid& dst_uuid, uint16_t* p_handle,
- uint32_t mx_chan_id) {
+ const Uuid& dst_uuid, uint16_t* p_handle) {
uint16_t cid;
tBNEP_CONN* p_bcb = bnepu_find_bcb_by_bd_addr(p_rem_bda);
@@ -162,14 +159,20 @@ tBNEP_RESULT BNEP_Connect(const RawAddress& p_rem_bda, const Uuid& src_uuid,
BNEP_TRACE_API("BNEP initiating security procedures for src uuid %s",
p_bcb->src_uuid.ToString().c_str());
- bnep_sec_check_complete(&p_bcb->rem_bda, BT_TRANSPORT_BR_EDR, p_bcb);
+#if (BNEP_DO_AUTH_FOR_ROLE_SWITCH == TRUE)
+ btm_sec_mx_access_request(p_bcb->rem_bda, BT_PSM_BNEP, true,
+ BTM_SEC_PROTO_BNEP, src_uuid.As32Bit(),
+ &bnep_sec_check_complete, p_bcb);
+#else
+ bnep_sec_check_complete(p_bcb->rem_bda, p_bcb, BTM_SUCCESS);
+#endif
+
} else {
/* Transition to the next appropriate state, waiting for connection confirm.
*/
p_bcb->con_state = BNEP_STATE_CONN_START;
- cid = L2CA_ConnectReq2(BT_PSM_BNEP, p_bcb->rem_bda,
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT);
+ cid = L2CA_ConnectReq(BT_PSM_BNEP, p_bcb->rem_bda);
if (cid != 0) {
p_bcb->l2cap_cid = cid;
@@ -643,3 +646,51 @@ uint8_t BNEP_SetTraceLevel(uint8_t new_level) {
return (bnep_cb.trace_level);
}
+/*******************************************************************************
+ *
+ * Function BNEP_GetStatus
+ *
+ * Description This function gets the status information for BNEP
+ * connection
+ *
+ * Returns BNEP_SUCCESS - if the status is available
+ * BNEP_NO_RESOURCES - if no structure is passed for
+ * output
+ * BNEP_WRONG_HANDLE - if the handle is invalid
+ * BNEP_WRONG_STATE - if not in connected state
+ *
+ ******************************************************************************/
+tBNEP_RESULT BNEP_GetStatus(uint16_t handle, tBNEP_STATUS* p_status) {
+#if (BNEP_SUPPORTS_STATUS_API == TRUE)
+ tBNEP_CONN* p_bcb;
+
+ if (!p_status) return BNEP_NO_RESOURCES;
+
+ if ((!handle) || (handle > BNEP_MAX_CONNECTIONS)) return (BNEP_WRONG_HANDLE);
+
+ p_bcb = &(bnep_cb.bcb[handle - 1]);
+
+ memset(p_status, 0, sizeof(tBNEP_STATUS));
+ if ((p_bcb->con_state != BNEP_STATE_CONNECTED) &&
+ (!(p_bcb->con_flags & BNEP_FLAGS_CONN_COMPLETED)))
+ return BNEP_WRONG_STATE;
+
+ /* Read the status parameters from the connection control block */
+ p_status->con_status = BNEP_STATUS_CONNECTED;
+ p_status->l2cap_cid = p_bcb->l2cap_cid;
+ p_status->rem_mtu_size = p_bcb->rem_mtu_size;
+ p_status->xmit_q_depth = fixed_queue_length(p_bcb->xmit_q);
+ p_status->sent_num_filters = p_bcb->sent_num_filters;
+ p_status->sent_mcast_filters = p_bcb->sent_mcast_filters;
+ p_status->rcvd_num_filters = p_bcb->rcvd_num_filters;
+ p_status->rcvd_mcast_filters = p_bcb->rcvd_mcast_filters;
+
+ p_status->rem_bda = p_bcb->rem_bda;
+ p_status->src_uuid = p_bcb->src_uuid;
+ p_status->dst_uuid = p_bcb->dst_uuid;
+
+ return BNEP_SUCCESS;
+#else
+ return (BNEP_IGNORE_CMD);
+#endif
+}
diff --git a/stack/bnep/bnep_int.h b/stack/bnep/bnep_int.h
index bce8a7601..5bba15da8 100644
--- a/stack/bnep/bnep_int.h
+++ b/stack/bnep/bnep_int.h
@@ -28,8 +28,8 @@
#include "bnep_api.h"
#include "bt_common.h"
#include "bt_target.h"
+#include "btm_int.h"
#include "btu.h"
-#include "osi/include/fixed_queue.h"
/* BNEP frame types
*/
@@ -79,6 +79,26 @@
#define BNEP_HOST_TIMEOUT_MS (200 * 1000)
#define BNEP_FILTER_SET_TIMEOUT_MS (10 * 1000)
+/* Define the Out-Flow default values. */
+#define BNEP_OFLOW_QOS_FLAG 0
+#define BNEP_OFLOW_SERV_TYPE 0
+#define BNEP_OFLOW_TOKEN_RATE 0
+#define BNEP_OFLOW_TOKEN_BUCKET_SIZE 0
+#define BNEP_OFLOW_PEAK_BANDWIDTH 0
+#define BNEP_OFLOW_LATENCY 0
+#define BNEP_OFLOW_DELAY_VARIATION 0
+
+/* Define the In-Flow default values. */
+#define BNEP_IFLOW_QOS_FLAG 0
+#define BNEP_IFLOW_SERV_TYPE 0
+#define BNEP_IFLOW_TOKEN_RATE 0
+#define BNEP_IFLOW_TOKEN_BUCKET_SIZE 0
+#define BNEP_IFLOW_PEAK_BANDWIDTH 0
+#define BNEP_IFLOW_LATENCY 0
+#define BNEP_IFLOW_DELAY_VARIATION 0
+
+#define BNEP_FLUSH_TO 0xFFFF
+
#define BNEP_MAX_RETRANSMITS 3
/* Define the BNEP Connection Control Block
@@ -106,6 +126,7 @@ typedef struct {
uint16_t l2cap_cid;
RawAddress rem_bda;
+ uint16_t rem_mtu_size;
alarm_t* conn_timer;
fixed_queue_t* xmit_q;
@@ -203,7 +224,8 @@ extern void bnep_process_setup_conn_responce(tBNEP_CONN* p_bcb,
extern uint8_t* bnep_process_control_packet(tBNEP_CONN* p_bcb, uint8_t* p,
uint16_t* len, bool is_ext);
extern void bnep_sec_check_complete(const RawAddress* bd_addr,
- tBT_TRANSPORT trasnport, void* p_ref_data);
+ tBT_TRANSPORT trasnport, void* p_ref_data,
+ uint8_t result);
extern tBNEP_RESULT bnep_is_packet_allowed(tBNEP_CONN* p_bcb,
const RawAddress& p_dest_addr,
uint16_t protocol,
diff --git a/stack/bnep/bnep_main.cc b/stack/bnep/bnep_main.cc
index 1651498fa..99124cf7d 100644
--- a/stack/bnep/bnep_main.cc
+++ b/stack/bnep/bnep_main.cc
@@ -22,25 +22,28 @@
*
******************************************************************************/
-#define LOG_TAG "bluetooth"
-
+#include <stdio.h>
+#include <stdlib.h>
#include <string.h>
#include "bt_target.h"
#include "bt_common.h"
#include "bt_types.h"
+#include "hcidefs.h"
+#include "hcimsgs.h"
#include "l2c_api.h"
#include "l2cdefs.h"
+#include "log/log.h"
#include "btm_api.h"
+#include "btu.h"
#include "bnep_api.h"
#include "bnep_int.h"
+#include "bt_utils.h"
-#include "bta/include/bta_api.h"
#include "device/include/controller.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
/******************************************************************************/
@@ -56,12 +59,13 @@ const uint16_t bnep_frame_hdr_sizes[] = {14, 1, 2, 8, 8};
static void bnep_connect_ind(const RawAddress& bd_addr, uint16_t l2cap_cid,
uint16_t psm, uint8_t l2cap_id);
static void bnep_connect_cfm(uint16_t l2cap_cid, uint16_t result);
-static void bnep_config_cfm(uint16_t l2cap_cid, uint16_t result,
- tL2CAP_CFG_INFO* p_cfg);
+static void bnep_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg);
+static void bnep_config_cfm(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg);
static void bnep_disconnect_ind(uint16_t l2cap_cid, bool ack_needed);
+static void bnep_disconnect_cfm(uint16_t l2cap_cid, uint16_t result);
static void bnep_data_ind(uint16_t l2cap_cid, BT_HDR* p_msg);
static void bnep_congestion_ind(uint16_t lcid, bool is_congested);
-static void bnep_on_l2cap_error(uint16_t l2cap_cid, uint16_t result);
+
/*******************************************************************************
*
* Function bnep_register_with_l2cap
@@ -77,20 +81,21 @@ tBNEP_RESULT bnep_register_with_l2cap(void) {
bnep_cb.l2cap_my_cfg.mtu_present = true;
bnep_cb.l2cap_my_cfg.mtu = BNEP_MTU_SIZE;
+ bnep_cb.l2cap_my_cfg.flush_to_present = true;
+ bnep_cb.l2cap_my_cfg.flush_to = BNEP_FLUSH_TO;
bnep_cb.reg_info.pL2CA_ConnectInd_Cb = bnep_connect_ind;
bnep_cb.reg_info.pL2CA_ConnectCfm_Cb = bnep_connect_cfm;
- bnep_cb.reg_info.pL2CA_ConfigInd_Cb = nullptr;
+ bnep_cb.reg_info.pL2CA_ConfigInd_Cb = bnep_config_ind;
bnep_cb.reg_info.pL2CA_ConfigCfm_Cb = bnep_config_cfm;
bnep_cb.reg_info.pL2CA_DisconnectInd_Cb = bnep_disconnect_ind;
+ bnep_cb.reg_info.pL2CA_DisconnectCfm_Cb = bnep_disconnect_cfm;
bnep_cb.reg_info.pL2CA_DataInd_Cb = bnep_data_ind;
bnep_cb.reg_info.pL2CA_CongestionStatus_Cb = bnep_congestion_ind;
- bnep_cb.reg_info.pL2CA_Error_Cb = bnep_on_l2cap_error;
/* Now, register with L2CAP */
- if (!L2CA_Register2(BT_PSM_BNEP, bnep_cb.reg_info, false /* enable_snoop */,
- nullptr, BNEP_MTU_SIZE, BNEP_MTU_SIZE,
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT)) {
+ if (!L2CA_Register(BT_PSM_BNEP, &bnep_cb.reg_info, false /* enable_snoop */,
+ nullptr)) {
BNEP_TRACE_ERROR("BNEP - Registration failed");
return BNEP_SECURITY_FAIL;
}
@@ -117,7 +122,7 @@ static void bnep_connect_ind(const RawAddress& bd_addr, uint16_t l2cap_cid,
/* no more resources to handle the connection, reject the connection. */
if (!(bnep_cb.profile_registered) || (p_bcb) ||
((p_bcb = bnepu_allocate_bcb(bd_addr)) == NULL)) {
- L2CA_DisconnectReq(l2cap_cid);
+ L2CA_ConnectRsp(bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_NO_PSM, 0);
return;
}
@@ -127,6 +132,12 @@ static void bnep_connect_ind(const RawAddress& bd_addr, uint16_t l2cap_cid,
/* Save the L2CAP Channel ID. */
p_bcb->l2cap_cid = l2cap_cid;
+ /* Send response to the L2CAP layer. */
+ L2CA_ConnectRsp(bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_OK, L2CAP_CONN_OK);
+
+ /* Send a Configuration Request. */
+ L2CA_ConfigReq(l2cap_cid, &bnep_cb.l2cap_my_cfg);
+
/* Start timer waiting for config setup */
alarm_set_on_mloop(p_bcb->conn_timer, BNEP_CONN_TIMEOUT_MS,
bnep_conn_timer_timeout, p_bcb);
@@ -134,21 +145,6 @@ static void bnep_connect_ind(const RawAddress& bd_addr, uint16_t l2cap_cid,
BNEP_TRACE_EVENT("BNEP - Rcvd L2CAP conn ind, CID: 0x%x", p_bcb->l2cap_cid);
}
-static void bnep_on_l2cap_error(uint16_t l2cap_cid, uint16_t result) {
- tBNEP_CONN* p_bcb = bnepu_find_bcb_by_cid(l2cap_cid);
- if (p_bcb == nullptr) return;
-
- /* Tell the upper layer, if there is a callback */
- if ((p_bcb->con_flags & BNEP_FLAGS_IS_ORIG) && (bnep_cb.p_conn_state_cb)) {
- (*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda, BNEP_CONN_FAILED,
- false);
- }
-
- L2CA_DisconnectReq(p_bcb->l2cap_cid);
-
- bnepu_release_bcb(p_bcb);
-}
-
/*******************************************************************************
*
* Function bnep_connect_cfm
@@ -176,6 +172,9 @@ static void bnep_connect_cfm(uint16_t l2cap_cid, uint16_t result) {
(p_bcb->con_state == BNEP_STATE_CONN_START)) {
p_bcb->con_state = BNEP_STATE_CFG_SETUP;
+ /* Send a Configuration Request. */
+ L2CA_ConfigReq(l2cap_cid, &bnep_cb.l2cap_my_cfg);
+
/* Start timer waiting for config results */
alarm_set_on_mloop(p_bcb->conn_timer, BNEP_CONN_TIMEOUT_MS,
bnep_conn_timer_timeout, p_bcb);
@@ -183,7 +182,84 @@ static void bnep_connect_cfm(uint16_t l2cap_cid, uint16_t result) {
BNEP_TRACE_EVENT("BNEP - got conn cnf, sent cfg req, CID: 0x%x",
p_bcb->l2cap_cid);
} else {
- LOG(ERROR) << __func__ << ": invoked with non OK status";
+ BNEP_TRACE_WARNING("BNEP - Rcvd conn cnf with error: 0x%x CID 0x%x",
+ result, p_bcb->l2cap_cid);
+
+ /* Tell the upper layer, if he has a callback */
+ if (bnep_cb.p_conn_state_cb && p_bcb->con_flags & BNEP_FLAGS_IS_ORIG) {
+ (*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda,
+ BNEP_CONN_FAILED, false);
+ }
+
+ bnepu_release_bcb(p_bcb);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function bnep_config_ind
+ *
+ * Description This function processes the L2CAP configuration indication
+ * event.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void bnep_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
+ tBNEP_CONN* p_bcb;
+ uint16_t result, mtu = 0;
+
+ /* Find CCB based on CID */
+ p_bcb = bnepu_find_bcb_by_cid(l2cap_cid);
+ if (p_bcb == NULL) {
+ BNEP_TRACE_WARNING("BNEP - Rcvd L2CAP cfg ind, unknown CID: 0x%x",
+ l2cap_cid);
+ return;
+ }
+
+ BNEP_TRACE_EVENT("BNEP - Rcvd cfg ind, CID: 0x%x", l2cap_cid);
+
+ /* Remember the remote MTU size */
+ if ((!p_cfg->mtu_present) || (p_cfg->mtu < BNEP_MIN_MTU_SIZE)) {
+ mtu = p_cfg->mtu;
+ p_cfg->flush_to_present = false;
+ p_cfg->mtu_present = true;
+ p_cfg->mtu = BNEP_MIN_MTU_SIZE;
+ p_cfg->result = result = L2CAP_CFG_UNACCEPTABLE_PARAMS;
+ } else {
+ if (p_cfg->mtu > BNEP_MTU_SIZE)
+ p_bcb->rem_mtu_size = BNEP_MTU_SIZE;
+ else
+ p_bcb->rem_mtu_size = p_cfg->mtu;
+
+ /* For now, always accept configuration from the other side */
+ p_cfg->flush_to_present = false;
+ p_cfg->mtu_present = false;
+ p_cfg->result = result = L2CAP_CFG_OK;
+ }
+
+ L2CA_ConfigRsp(l2cap_cid, p_cfg);
+
+ if (result != L2CAP_CFG_OK) {
+ BNEP_TRACE_EVENT("BNEP - Rcvd cfg ind with bad MTU %d, CID: 0x%x", mtu,
+ l2cap_cid);
+ return;
+ }
+
+ p_bcb->con_flags |= BNEP_FLAGS_HIS_CFG_DONE;
+
+ if (p_bcb->con_flags & BNEP_FLAGS_MY_CFG_DONE) {
+ p_bcb->con_state = BNEP_STATE_SEC_CHECKING;
+
+ /* Start timer waiting for setup or response */
+ alarm_set_on_mloop(p_bcb->conn_timer, BNEP_HOST_TIMEOUT_MS,
+ bnep_conn_timer_timeout, p_bcb);
+
+ if (p_bcb->con_flags & BNEP_FLAGS_IS_ORIG) {
+ btm_sec_mx_access_request(p_bcb->rem_bda, BT_PSM_BNEP, true,
+ BTM_SEC_PROTO_BNEP, p_bcb->src_uuid.As32Bit(),
+ &bnep_sec_check_complete, p_bcb);
+ }
}
}
@@ -197,11 +273,11 @@ static void bnep_connect_cfm(uint16_t l2cap_cid, uint16_t result) {
* Returns void
*
******************************************************************************/
-static void bnep_config_cfm(uint16_t l2cap_cid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
+static void bnep_config_cfm(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
tBNEP_CONN* p_bcb;
- BNEP_TRACE_EVENT("BNEP - Rcvd cfg cfm, CID: 0x%x", l2cap_cid);
+ BNEP_TRACE_EVENT("BNEP - Rcvd cfg cfm, CID: 0x%x Result: %d", l2cap_cid,
+ p_cfg->result);
/* Find CCB based on CID */
p_bcb = bnepu_find_bcb_by_cid(l2cap_cid);
@@ -212,14 +288,32 @@ static void bnep_config_cfm(uint16_t l2cap_cid, uint16_t initiator,
}
/* For now, always accept configuration from the other side */
- p_bcb->con_state = BNEP_STATE_SEC_CHECKING;
+ if (p_cfg->result == L2CAP_CFG_OK) {
+ p_bcb->con_flags |= BNEP_FLAGS_MY_CFG_DONE;
- /* Start timer waiting for setup or response */
- alarm_set_on_mloop(p_bcb->conn_timer, BNEP_HOST_TIMEOUT_MS,
- bnep_conn_timer_timeout, p_bcb);
+ if (p_bcb->con_flags & BNEP_FLAGS_HIS_CFG_DONE) {
+ p_bcb->con_state = BNEP_STATE_SEC_CHECKING;
+
+ /* Start timer waiting for setup or response */
+ alarm_set_on_mloop(p_bcb->conn_timer, BNEP_HOST_TIMEOUT_MS,
+ bnep_conn_timer_timeout, p_bcb);
- if (p_bcb->con_flags & BNEP_FLAGS_IS_ORIG) {
- bnep_sec_check_complete(&p_bcb->rem_bda, BT_TRANSPORT_BR_EDR, p_bcb);
+ if (p_bcb->con_flags & BNEP_FLAGS_IS_ORIG) {
+ btm_sec_mx_access_request(p_bcb->rem_bda, BT_PSM_BNEP, true,
+ BTM_SEC_PROTO_BNEP, p_bcb->src_uuid.As32Bit(),
+ &bnep_sec_check_complete, p_bcb);
+ }
+ }
+ } else {
+ /* Tell the upper layer, if he has a callback */
+ if ((p_bcb->con_flags & BNEP_FLAGS_IS_ORIG) && (bnep_cb.p_conn_state_cb)) {
+ (*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda,
+ BNEP_CONN_FAILED_CFG, false);
+ }
+
+ L2CA_DisconnectReq(p_bcb->l2cap_cid);
+
+ bnepu_release_bcb(p_bcb);
}
}
@@ -236,6 +330,8 @@ static void bnep_config_cfm(uint16_t l2cap_cid, uint16_t initiator,
static void bnep_disconnect_ind(uint16_t l2cap_cid, bool ack_needed) {
tBNEP_CONN* p_bcb;
+ if (ack_needed) L2CA_DisconnectRsp(l2cap_cid);
+
/* Find CCB based on CID */
p_bcb = bnepu_find_bcb_by_cid(l2cap_cid);
if (p_bcb == NULL) {
@@ -245,7 +341,7 @@ static void bnep_disconnect_ind(uint16_t l2cap_cid, bool ack_needed) {
BNEP_TRACE_EVENT("BNEP - Rcvd L2CAP disc, CID: 0x%x", l2cap_cid);
- /* Tell the user if there is a callback */
+ /* Tell the user if he has a callback */
if (p_bcb->con_state == BNEP_STATE_CONNECTED) {
if (bnep_cb.p_conn_state_cb)
(*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda,
@@ -263,6 +359,20 @@ static void bnep_disconnect_ind(uint16_t l2cap_cid, bool ack_needed) {
/*******************************************************************************
*
+ * Function bnep_disconnect_cfm
+ *
+ * Description This function gets the disconnect confirm event from L2CAP
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void bnep_disconnect_cfm(uint16_t l2cap_cid, uint16_t result) {
+ BNEP_TRACE_EVENT("BNEP - Rcvd L2CAP disc cfm, CID: 0x%x, Result 0x%x",
+ l2cap_cid, result);
+}
+
+/*******************************************************************************
+ *
* Function bnep_congestion_ind
*
* Description This is a callback function called by L2CAP when
@@ -570,7 +680,7 @@ void bnep_conn_timer_timeout(void* data) {
L2CA_DisconnectReq(p_bcb->l2cap_cid);
- /* Tell the user if there is a callback */
+ /* Tell the user if he has a callback */
if ((p_bcb->con_flags & BNEP_FLAGS_IS_ORIG) && (bnep_cb.p_conn_state_cb))
(*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda,
BNEP_CONN_FAILED, false);
@@ -584,7 +694,7 @@ void bnep_conn_timer_timeout(void* data) {
} else {
L2CA_DisconnectReq(p_bcb->l2cap_cid);
- /* Tell the user if there is a callback */
+ /* Tell the user if he has a callback */
if (bnep_cb.p_conn_state_cb)
(*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda,
BNEP_SET_FILTER_FAIL, false);
@@ -600,7 +710,7 @@ void bnep_conn_timer_timeout(void* data) {
} else {
L2CA_DisconnectReq(p_bcb->l2cap_cid);
- /* Tell the user if there is a callback */
+ /* Tell the user if he has a callback */
if (bnep_cb.p_conn_state_cb)
(*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda,
BNEP_SET_FILTER_FAIL, false);
@@ -637,7 +747,7 @@ void bnep_connected(tBNEP_CONN* p_bcb) {
alarm_cancel(p_bcb->conn_timer);
p_bcb->re_transmits = 0;
- /* Tell the upper layer, if there is a callback */
+ /* Tell the upper layer, if he has a callback */
if (bnep_cb.p_conn_state_cb)
(*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda, BNEP_SUCCESS,
is_role_change);
diff --git a/stack/bnep/bnep_utils.cc b/stack/bnep/bnep_utils.cc
index 37f088c2f..ac74ce016 100644
--- a/stack/bnep/bnep_utils.cc
+++ b/stack/bnep/bnep_utils.cc
@@ -22,6 +22,7 @@
*
******************************************************************************/
+#include <log/log.h>
#include <stdio.h>
#include <string.h>
@@ -29,9 +30,9 @@
#include "bt_common.h"
#include "bt_types.h"
#include "bt_utils.h"
+#include "btm_int.h"
#include "btu.h"
#include "device/include/controller.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
using bluetooth::Uuid;
@@ -606,7 +607,16 @@ void bnep_process_setup_conn_req(tBNEP_CONN* p_bcb, uint8_t* p_setup,
BNEP_TRACE_EVENT(
"BNEP initiating security check for incoming call for uuid %s",
p_bcb->src_uuid.ToString().c_str());
- bnep_sec_check_complete(&p_bcb->rem_bda, BT_TRANSPORT_BR_EDR, p_bcb);
+#if (BNEP_DO_AUTH_FOR_ROLE_SWITCH == FALSE)
+ if (p_bcb->con_flags & BNEP_FLAGS_CONN_COMPLETED)
+ bnep_sec_check_complete(p_bcb->rem_bda, p_bcb, BTM_SUCCESS);
+ else
+#endif
+ btm_sec_mx_access_request(p_bcb->rem_bda, BT_PSM_BNEP, false,
+ BTM_SEC_PROTO_BNEP, p_bcb->src_uuid.As32Bit(),
+ &bnep_sec_check_complete, p_bcb);
+
+ return;
}
/*******************************************************************************
@@ -675,7 +685,7 @@ void bnep_process_setup_conn_responce(tBNEP_CONN* p_bcb, uint8_t* p_setup) {
alarm_cancel(p_bcb->conn_timer);
p_bcb->re_transmits = 0;
- /* Tell the user if there is a callback */
+ /* Tell the user if he has a callback */
if (bnep_cb.p_conn_state_cb)
(*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda, resp, true);
@@ -685,7 +695,7 @@ void bnep_process_setup_conn_responce(tBNEP_CONN* p_bcb, uint8_t* p_setup) {
L2CA_DisconnectReq(p_bcb->l2cap_cid);
- /* Tell the user if there is a callback */
+ /* Tell the user if he has a callback */
if ((p_bcb->con_flags & BNEP_FLAGS_IS_ORIG) && (bnep_cb.p_conn_state_cb))
(*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda, resp, false);
@@ -1146,12 +1156,14 @@ void bnepu_send_peer_multicast_filter_rsp(tBNEP_CONN* p_bcb,
* Returns void
*
******************************************************************************/
-void bnep_sec_check_complete(const RawAddress* bd_addr, tBT_TRANSPORT trasnport,
- void* p_ref_data) {
+void bnep_sec_check_complete(UNUSED_ATTR const RawAddress* bd_addr,
+ UNUSED_ATTR tBT_TRANSPORT trasnport,
+ void* p_ref_data, uint8_t result) {
tBNEP_CONN* p_bcb = (tBNEP_CONN*)p_ref_data;
uint16_t resp_code = BNEP_SETUP_CONN_OK;
bool is_role_change;
+ BNEP_TRACE_EVENT("BNEP security callback returned result %d", result);
if (p_bcb->con_flags & BNEP_FLAGS_CONN_COMPLETED)
is_role_change = true;
else
@@ -1167,6 +1179,30 @@ void bnep_sec_check_complete(const RawAddress* bd_addr, tBT_TRANSPORT trasnport,
/* if it is outgoing call and result is FAILURE return security fail error */
if (!(p_bcb->con_flags & BNEP_FLAGS_SETUP_RCVD)) {
+ if (result != BTM_SUCCESS) {
+ if (p_bcb->con_flags & BNEP_FLAGS_CONN_COMPLETED) {
+ /* Tell the user that role change is failed because of security */
+ if (bnep_cb.p_conn_state_cb)
+ (*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda,
+ BNEP_SECURITY_FAIL, is_role_change);
+
+ p_bcb->con_state = BNEP_STATE_CONNECTED;
+ p_bcb->src_uuid = p_bcb->prv_src_uuid;
+ p_bcb->dst_uuid = p_bcb->prv_dst_uuid;
+ return;
+ }
+
+ L2CA_DisconnectReq(p_bcb->l2cap_cid);
+
+ /* Tell the user if he has a callback */
+ if (bnep_cb.p_conn_state_cb)
+ (*bnep_cb.p_conn_state_cb)(p_bcb->handle, p_bcb->rem_bda,
+ BNEP_SECURITY_FAIL, is_role_change);
+
+ bnepu_release_bcb(p_bcb);
+ return;
+ }
+
/* Transition to the next appropriate state, waiting for connection confirm.
*/
p_bcb->con_state = BNEP_STATE_CONN_SETUP;
@@ -1177,6 +1213,25 @@ void bnep_sec_check_complete(const RawAddress* bd_addr, tBT_TRANSPORT trasnport,
return;
}
+ /* it is an incoming call respond appropriately */
+ if (result != BTM_SUCCESS) {
+ bnep_send_conn_responce(p_bcb, BNEP_SETUP_CONN_NOT_ALLOWED);
+ if (p_bcb->con_flags & BNEP_FLAGS_CONN_COMPLETED) {
+ /* Role change is failed because of security. Revert back to connected
+ * state */
+ p_bcb->con_state = BNEP_STATE_CONNECTED;
+ p_bcb->con_flags &= (~BNEP_FLAGS_SETUP_RCVD);
+ p_bcb->src_uuid = p_bcb->prv_src_uuid;
+ p_bcb->dst_uuid = p_bcb->prv_dst_uuid;
+ return;
+ }
+
+ L2CA_DisconnectReq(p_bcb->l2cap_cid);
+
+ bnepu_release_bcb(p_bcb);
+ return;
+ }
+
if (bnep_cb.p_conn_ind_cb) {
p_bcb->con_state = BNEP_STATE_CONN_SETUP;
(*bnep_cb.p_conn_ind_cb)(p_bcb->handle, p_bcb->rem_bda, p_bcb->dst_uuid,
@@ -1186,6 +1241,8 @@ void bnep_sec_check_complete(const RawAddress* bd_addr, tBT_TRANSPORT trasnport,
bnep_send_conn_responce(p_bcb, resp_code);
bnep_connected(p_bcb);
}
+
+ return;
}
/*******************************************************************************
diff --git a/stack/btm/ble_advertiser_hci_interface.cc b/stack/btm/ble_advertiser_hci_interface.cc
index cd71e35a0..fbf8d27d2 100644
--- a/stack/btm/ble_advertiser_hci_interface.cc
+++ b/stack/btm/ble_advertiser_hci_interface.cc
@@ -22,8 +22,7 @@
#include "btm_int_types.h"
#include "device/include/controller.h"
#include "hcidefs.h"
-
-#include "osi/include/log.h"
+#include "log/log.h"
#include <queue>
#include <utility>
diff --git a/stack/btm/ble_scanner_hci_interface.cc b/stack/btm/ble_scanner_hci_interface.cc
deleted file mode 100644
index b18bbc8fb..000000000
--- a/stack/btm/ble_scanner_hci_interface.cc
+++ /dev/null
@@ -1,428 +0,0 @@
-/*
- * Copyright 2019 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "ble_scanner_hci_interface.h"
-
-#include <base/bind.h>
-
-#include "acl_api.h"
-#include "btm_api.h"
-#include "device/include/controller.h"
-#include "hcidefs.h"
-#include "hcimsgs.h"
-
-#include "osi/include/log.h"
-
-namespace {
-BleScannerHciInterface* instance = nullptr;
-
-static void status_callback(base::Callback<void(uint8_t)> cb, uint8_t* data,
- uint16_t len) {
- uint8_t status;
-
- LOG_ASSERT(len == 1) << "Received bad response length: " << len;
- STREAM_TO_UINT8(status, data);
-
- DVLOG(1) << __func__ << " Received status_cb";
- cb.Run(status);
-}
-
-static void status_handle_callback(base::Callback<void(uint8_t, uint16_t)> cb,
- uint8_t* data, uint16_t len) {
- uint8_t status;
- uint16_t handle = HCI_INVALID_HANDLE;
-
- LOG_ASSERT((len > 0) && (len < 4)) << "Received bad response length: " << len;
- uint8_t* pp = data;
- STREAM_TO_UINT8(status, pp);
-
- if (status == HCI_SUCCESS) {
- LOG_ASSERT(len == 3) << "Received bad response length: " << len;
-
- STREAM_TO_UINT16(handle, pp);
- handle = handle & 0x0EFF;
-
- DVLOG(1) << __func__ << " Received status_handle_callback";
- } else {
- DVLOG(1) << __func__ << " hci response error code: " << int{status};
- }
- cb.Run(status, handle);
-}
-
-/**
- * BleScannerHciInterface allows the caller to sync to a periodic advertising
- * train and receive periodic advertising data events through a registered
- * observer's callbacks. It also provides a synchronisation transfer API,
- * including in-controller allow list support. The right feature-complete
- * interface implementation is chosen during the init phase based on the
- * controller's list of supported features.
- */
-class BleScannerImplBase : public BleScannerHciInterface {
- public:
- void SetScanEventObserver(ScanEventObserver* observer) override {
- VLOG(1) << __func__;
- // TODO: Support multiple observers if ever needed.
- scan_event_observer = observer;
- }
-
- void PeriodicScanStart(uint8_t options, uint8_t set_id, uint8_t adv_addr_type,
- const RawAddress& adv_addr, uint16_t skip_num,
- uint16_t sync_timeout,
- uint8_t sync_cte_type) override {
- VLOG(1) << __func__;
- btsnd_hcic_ble_periodic_advertising_create_sync(
- options, set_id, adv_addr_type, adv_addr, skip_num, sync_timeout,
- sync_cte_type);
- }
-
- void PeriodicScanCancelStart(status_cb command_complete) override {
- VLOG(1) << __func__;
- btsnd_hcic_ble_periodic_advertising_create_sync_cancel(
- base::Bind(&status_callback, std::move(command_complete)));
- }
-
- void PeriodicScanTerminate(uint16_t sync_handle,
- status_cb command_complete) override {
- VLOG(1) << __func__;
- btsnd_hcic_ble_periodic_advertising_terminate_sync(
- sync_handle, base::Bind(&status_callback, std::move(command_complete)));
- }
-
- void PeriodicScanResultEvtEnable(uint16_t sync_handle, bool enable,
- status_cb command_complete) override {
- VLOG(1) << __func__;
- btsnd_hcic_ble_set_periodic_advertising_receive_enable(
- sync_handle, enable,
- base::Bind(&status_callback, std::move(command_complete)));
- }
-
- void PeriodicAdvertiserListGetSize(
- BleScannerHciInterface::list_size_cb command_complete) override {
- VLOG(1) << __func__;
- command_complete.Run(
- controller_get_interface()->get_ble_periodic_advertiser_list_size());
- }
-
- void PeriodicAdvertiserListAddDevice(uint8_t adv_addr_type,
- RawAddress& adv_addr, uint8_t set_id,
- status_cb command_complete) override {
- VLOG(1) << __func__;
- btsnd_hci_ble_add_device_to_periodic_advertiser_list(
- adv_addr_type, adv_addr, set_id,
- base::Bind(&status_callback, std::move(command_complete)));
- }
-
- void PeriodicAdvertiserListRemoveDevice(uint8_t adv_addr_type,
- RawAddress& adv_addr, uint8_t set_id,
- status_cb command_complete) override {
- VLOG(1) << __func__;
- btsnd_hci_ble_remove_device_from_periodic_advertiser_list(
- adv_addr_type, adv_addr, set_id,
- base::Bind(&status_callback, std::move(command_complete)));
- }
-
- void PeriodicAdvertiserListClear(status_cb command_complete) override {
- VLOG(1) << __func__;
- btsnd_hci_ble_clear_periodic_advertiser_list(
- base::Bind(&status_callback, std::move(command_complete)));
- };
-
- void PeriodicAdvSyncTransfer(
- const RawAddress& bd_addr, uint16_t service_data, uint16_t sync_handle,
- BleScannerHciInterface::handle_cb command_complete) override {
- VLOG(1) << __func__;
- uint16_t acl_handle = BTM_GetHCIConnHandle(bd_addr, BT_TRANSPORT_LE);
-
- if (acl_handle == HCI_INVALID_HANDLE) {
- LOG(ERROR) << __func__
- << ": Wrong mode: no LE link exist or LE not supported";
- return;
- }
-
- btsnd_hcic_ble_periodic_advertising_sync_transfer(
- acl_handle, service_data, sync_handle,
- base::Bind(&status_handle_callback, std::move(command_complete)));
- }
-
- void PeriodicAdvSetInfoTransfer(const RawAddress& bd_addr,
- uint16_t service_data, uint8_t adv_handle,
- handle_cb command_complete) override {
- VLOG(1) << __func__;
- uint16_t acl_handle = BTM_GetHCIConnHandle(bd_addr, BT_TRANSPORT_LE);
-
- if (acl_handle == HCI_INVALID_HANDLE) {
- LOG(ERROR) << __func__
- << ": Wrong mode: no LE link exist or LE not supported";
- return;
- }
-
- btsnd_hcic_ble_periodic_advertising_set_info_transfer(
- acl_handle, service_data, adv_handle,
- base::Bind(&status_handle_callback, std::move(command_complete)));
- }
-
- void SetPeriodicAdvSyncTransferParams(const RawAddress& bd_addr, uint8_t mode,
- uint16_t skip, uint16_t sync_timeout,
- uint8_t cte_type, bool set_defaults,
- status_cb command_complete) override {
- VLOG(1) << __func__;
- uint16_t acl_handle = BTM_GetHCIConnHandle(bd_addr, BT_TRANSPORT_LE);
-
- if (acl_handle == HCI_INVALID_HANDLE) {
- LOG(ERROR) << __func__
- << ": Wrong mode: no LE link exist or LE not supported";
- return;
- }
-
- if (set_defaults)
- btsnd_hcic_ble_set_default_periodic_advertising_sync_transfer_params(
- acl_handle, mode, skip, sync_timeout, cte_type,
- base::Bind(&status_callback, std::move(command_complete)));
- else
- btsnd_hcic_ble_set_periodic_advertising_sync_transfer_params(
- acl_handle, mode, skip, sync_timeout, cte_type,
- base::Bind(&status_callback, std::move(command_complete)));
- }
-
- void OnPeriodicAdvSyncEstablished(uint8_t status, uint16_t sync_handle,
- uint8_t adv_sid, uint8_t adv_addr_type,
- RawAddress adv_addr, uint8_t adv_phy,
- uint16_t adv_interval,
- uint8_t adv_clock_accuracy) {
- if (scan_event_observer) {
- scan_event_observer->OnPeriodicScanEstablished(
- status, sync_handle, adv_sid, adv_addr_type, adv_addr, adv_phy,
- adv_interval, adv_clock_accuracy);
- }
- }
-
- void OnPeriodicScanResult(uint16_t sync_handle, uint8_t tx_power, int8_t rssi,
- uint8_t cte_type, uint8_t pkt_data_status,
- uint8_t pkt_data_len, uint8_t* p_pkt_data) {
- // The observer should handle the caching and reassembly of the fragmented
- // packet.
- if (scan_event_observer) {
- scan_event_observer->OnPeriodicScanResult(sync_handle, tx_power, rssi,
- cte_type, pkt_data_status,
- pkt_data_len, p_pkt_data);
- }
- }
-
- void OnPeriodicSyncLost(uint16_t sync_handle) {
- if (scan_event_observer)
- scan_event_observer->OnPeriodicScanLost(sync_handle);
- }
-
- private:
- ScanEventObserver* scan_event_observer = nullptr;
-};
-
-class BleScannerListImpl : public virtual BleScannerImplBase {
- void PeriodicAdvertiserListAddDevice(uint8_t adv_addr_type,
- RawAddress& adv_addr, uint8_t set_id,
- status_cb command_complete) override {
- VLOG(1) << __func__;
- btsnd_hci_ble_add_device_to_periodic_advertiser_list(
- adv_addr_type, adv_addr, set_id,
- base::Bind(&status_callback, std::move(command_complete)));
- }
-
- void PeriodicAdvertiserListRemoveDevice(uint8_t adv_addr_type,
- RawAddress& adv_addr, uint8_t set_id,
- status_cb command_complete) override {
- VLOG(1) << __func__;
- btsnd_hci_ble_remove_device_from_periodic_advertiser_list(
- adv_addr_type, adv_addr, set_id,
- base::Bind(&status_callback, std::move(command_complete)));
- }
-
- void PeriodicAdvertiserListClear(status_cb command_complete) override {
- VLOG(1) << __func__;
- btsnd_hci_ble_clear_periodic_advertiser_list(
- base::Bind(&status_callback, std::move(command_complete)));
- };
-};
-
-class BleScannerSyncTransferImpl : public virtual BleScannerImplBase {
- void PeriodicAdvSyncTransfer(
- const RawAddress& bd_addr, uint16_t service_data, uint16_t sync_handle,
- BleScannerHciInterface::handle_cb command_complete) override {
- uint16_t acl_handle = BTM_GetHCIConnHandle(bd_addr, BT_TRANSPORT_LE);
-
- if (acl_handle == HCI_INVALID_HANDLE) {
- LOG(ERROR) << __func__
- << ": Wrong mode: no LE link exist or LE not supported";
- return;
- }
-
- btsnd_hcic_ble_periodic_advertising_sync_transfer(
- acl_handle, service_data, sync_handle,
- base::Bind(&status_handle_callback, std::move(command_complete)));
- }
-
- void PeriodicAdvSetInfoTransfer(const RawAddress& bd_addr,
- uint16_t service_data, uint8_t adv_handle,
- handle_cb command_complete) override {
- uint16_t acl_handle = BTM_GetHCIConnHandle(bd_addr, BT_TRANSPORT_LE);
-
- if (acl_handle == HCI_INVALID_HANDLE) {
- LOG(ERROR) << __func__
- << ": Wrong mode: no LE link exist or LE not supported";
- return;
- }
-
- btsnd_hcic_ble_periodic_advertising_set_info_transfer(
- acl_handle, service_data, adv_handle,
- base::Bind(&status_handle_callback, std::move(command_complete)));
- }
-
- void SetPeriodicAdvSyncTransferParams(const RawAddress& bd_addr, uint8_t mode,
- uint16_t skip, uint16_t sync_timeout,
- uint8_t cte_type, bool set_defaults,
- status_cb command_complete) override {
- uint16_t acl_handle = BTM_GetHCIConnHandle(bd_addr, BT_TRANSPORT_LE);
-
- if (acl_handle == HCI_INVALID_HANDLE) {
- LOG(ERROR) << __func__
- << ": Wrong mode: no LE link exist or LE not supported";
- return;
- }
-
- if (set_defaults)
- btsnd_hcic_ble_set_default_periodic_advertising_sync_transfer_params(
- acl_handle, mode, skip, sync_timeout, cte_type,
- base::Bind(&status_callback, std::move(command_complete)));
- else
- btsnd_hcic_ble_set_periodic_advertising_sync_transfer_params(
- acl_handle, mode, skip, sync_timeout, cte_type,
- base::Bind(&status_callback, std::move(command_complete)));
- }
-};
-
-class BleScannerCompleteImpl : public BleScannerListImpl,
- public BleScannerSyncTransferImpl {
- // Not much to do here :)
-};
-
-} // namespace
-
-void BleScannerHciInterface::Initialize() {
- VLOG(1) << __func__;
- LOG_ASSERT(instance == nullptr) << "Was already initialized.";
-
- if ((controller_get_interface()->get_ble_periodic_advertiser_list_size()) &&
- (controller_get_interface()
- ->supports_ble_periodic_advertising_sync_transfer_sender())) {
- LOG(INFO) << "Advertiser list in controller can be used";
- LOG(INFO) << "Periodic Adv Sync Transfer Sender role is supported";
- instance = new BleScannerCompleteImpl();
- } else if (controller_get_interface()
- ->supports_ble_periodic_advertising_sync_transfer_sender()) {
- LOG(INFO) << "Periodic Adv Sync Transfer Sender role is supported";
- instance = new BleScannerSyncTransferImpl();
- } else if (controller_get_interface()
- ->get_ble_periodic_advertiser_list_size()) {
- LOG(INFO) << "Periodic Adv Sync Transfer Recipient role is supported";
- instance = new BleScannerListImpl();
- }
- // TODO: Implement periodic adv. sync. recipient role if ever needed.
-}
-
-BleScannerHciInterface* BleScannerHciInterface::Get() { return instance; }
-
-void BleScannerHciInterface::CleanUp() {
- VLOG(1) << __func__;
-
- delete instance;
- instance = nullptr;
-}
-
-void btm_ble_process_periodic_adv_sync_est_evt(uint8_t data_len,
- uint8_t* data) {
- uint16_t sync_handle, adv_interval;
- uint8_t status, adv_sid, adv_addr_type, adv_phy, adv_clock_accuracy;
- RawAddress adv_addr;
-
- VLOG(1) << __func__;
-
- LOG_ASSERT(data_len == 15)
- << "Malformed LE Periodic Advertising Sync Est. Event from controller";
-
- STREAM_TO_UINT8(status, data);
- STREAM_TO_UINT16(sync_handle, data);
- STREAM_TO_UINT8(adv_sid, data);
- STREAM_TO_UINT8(adv_addr_type, data);
- STREAM_TO_BDADDR(adv_addr, data);
- STREAM_TO_UINT8(adv_phy, data);
- STREAM_TO_UINT16(adv_interval, data);
- STREAM_TO_UINT8(adv_clock_accuracy, data);
-
- if (BleScannerHciInterface::Get()) {
- static_cast<BleScannerImplBase*>(BleScannerHciInterface::Get())
- ->OnPeriodicAdvSyncEstablished(status, sync_handle, adv_sid,
- adv_addr_type, adv_addr, adv_phy,
- adv_interval, adv_clock_accuracy);
- }
-}
-
-void btm_ble_process_periodic_adv_pkt(uint8_t data_len, uint8_t* data) {
- uint8_t* p = data;
- uint16_t sync_handle;
- uint8_t tx_power, cte_type, pkt_data_status, pkt_data_len;
- int8_t rssi;
-
- LOG_ASSERT(data_len >= 7)
- << "Malformed LE Periodic Advertising Report Event from controller";
-
- STREAM_TO_UINT16(sync_handle, p);
- STREAM_TO_UINT8(tx_power, p);
- STREAM_TO_INT8(rssi, p);
- STREAM_TO_UINT8(cte_type, p);
- STREAM_TO_UINT8(pkt_data_status, p);
- STREAM_TO_UINT8(pkt_data_len, p);
-
- uint8_t* pkt_data = p;
- p += pkt_data_len;
-
- if (p > data + data_len) {
- LOG(ERROR) << __func__ << " Invalid pkt_data_len: " << int{pkt_data_len};
- return;
- }
-
- if (rssi >= 21 && rssi <= 126) {
- LOG(ERROR) << __func__
- << " bad rssi value in advertising report: " << int{rssi};
- }
-
- if (BleScannerHciInterface::Get()) {
- static_cast<BleScannerImplBase*>(BleScannerHciInterface::Get())
- ->OnPeriodicScanResult(sync_handle, tx_power, rssi, cte_type,
- pkt_data_status, pkt_data_len, pkt_data);
- }
-}
-
-void btm_ble_process_periodic_adv_sync_lost_evt(uint8_t data_len,
- uint8_t* data) {
- uint16_t sync_handle;
-
- STREAM_TO_UINT16(sync_handle, data);
-
- if (BleScannerHciInterface::Get()) {
- static_cast<BleScannerImplBase*>(BleScannerHciInterface::Get())
- ->OnPeriodicSyncLost(sync_handle);
- }
-}
diff --git a/stack/btm/ble_scanner_hci_interface.h b/stack/btm/ble_scanner_hci_interface.h
deleted file mode 100644
index f7b233c70..000000000
--- a/stack/btm/ble_scanner_hci_interface.h
+++ /dev/null
@@ -1,230 +0,0 @@
-/*
- * Copyright 2019 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BLE_SCANNER_HCI_INTERFACE_H
-#define BLE_SCANNER_HCI_INTERFACE_H
-
-#include <base/callback.h>
-
-#include <vector>
-
-#include "stack/include/bt_types.h"
-
-class BleScannerHciInterface {
- public:
- using status_cb = base::Callback<void(uint8_t /* status */)>;
- using list_size_cb = base::Callback<void(int8_t /* list_size */)>;
- using handle_cb =
- base::Callback<void(uint8_t /* status */, uint16_t /* adv_handle */)>;
-
- static void Initialize();
- static BleScannerHciInterface* Get();
- static void CleanUp();
-
- virtual ~BleScannerHciInterface() = default;
-
- class ScanEventObserver {
- public:
- virtual ~ScanEventObserver() = default;
- virtual void OnPeriodicScanResult(uint16_t sync_handle, uint8_t tx_power,
- int8_t rssi, uint8_t cte_type,
- uint8_t pkt_data_status,
- uint8_t pkt_data_len,
- const uint8_t* pkt_data) = 0;
- virtual void OnPeriodicScanEstablished(
- uint8_t status, uint16_t sync_handle, uint8_t set_id,
- uint8_t adv_addr_type, const RawAddress& adv_addr, uint8_t adv_phy,
- uint16_t adv_interval, uint8_t adv_clock_accuracy) = 0;
- virtual void OnPeriodicScanLost(uint16_t sync_handle) = 0;
- };
-
- virtual void SetScanEventObserver(ScanEventObserver* observer) = 0;
-
- /**
- * Used to synchronize with a periodic advertising train from an advertiser
- * and begin receiving periodic advertising packets.
- *
- * @param options bit 0: whether to use advertiser list, adv_sid,
- * adv_addr_type and adv_addr parameters are being used otherwise, bit 1:
- * whether reporting is initially disabled, all other bits: Reserved for
- * future use
- * @param adv_sid advertising set ID
- * @param adv_addr_type advertiser device address type
- * @param adv_addr advertiser device address
- * @param skip_num the maximum number of periodic advertising events that can
- * be skipped after a successful receive. Range: 0x0000 to 0x01F3.
- * @param sync_timeout synchronization timeout for the periodic advertising
- * train, Range: 0x000A to 0x4000, Time = N*10 ms, Range: 100 ms to 163.84s
- * @param sync_cte_type bit 0: do not sync to packets with an AoA Constant
- * Tone Extension, bit 1: do not sync to packets with an AoD Constant Tone
- * Extension with 1 μs slots, bit 2: do not sync to packets with an AoD
- * Constant Tone Extension with 2 μs slots, bit 3: do not sync to packets with
- * a type 3 Constant Tone Extension (currently reserved for future use),
- * bit 4: do not sync to packets without a Constant Tone Extension, all other
- * bits: reserved for future use.
- */
- virtual void PeriodicScanStart(uint8_t options, uint8_t set_id,
- uint8_t adv_addr_type,
- const RawAddress& adv_addr, uint16_t skip_num,
- uint16_t sync_timeout,
- uint8_t sync_cte_type) = 0;
-
- /**
- * Used to cancel the HCI_LE_Periodic_Advertising_Create_Sync command while it
- * is pending.
- *
- * @param cb status callback
- */
- virtual void PeriodicScanCancelStart(status_cb cb) = 0;
-
- /**
- * Used to stop reception of the periodic advertising train identified by the
- * Sync_Handle parameter.
- *
- * @param sync_handle synced advertising handle
- * @param cb status callback
- */
- virtual void PeriodicScanTerminate(uint16_t sync_handle, status_cb cb) = 0;
-
- /**
- * Enable or disable reports for the periodic advertising train defined by the
- * sync_handle.
- *
- * @param sync_handle synced advewrtising handle
- * @param enable whether enable or disable the advertising reports
- * @param cb status callback
- */
- virtual void PeriodicScanResultEvtEnable(uint16_t sync_handle, bool enable,
- status_cb cb) = 0;
-
- /**
- * Used to add an entry, consisting of a single device address and SID, to the
- * Periodic Advertiser list stored in the Controller. Any additions to the
- * Periodic Advertiser list take effect immediately. If the entry is already
- * on the list, the Controller shall return the error code Invalid HCI Command
- * Parameters (0x12).
- *
- * @param adv_addr_type advertiser device address type
- * @param adv_addr advertiser device address
- * @param adv_sid advertising set ID
- * @param cb status callback
- */
- virtual void PeriodicAdvertiserListAddDevice(uint8_t adv_addr_type,
- RawAddress& adv_addr,
- uint8_t adv_sid,
- status_cb cb) = 0;
- /**
- * Remove one entry from the list of Periodic Advertisers stored in the
- * Controller. Removals from the Periodic Advertisers List take effect
- * immediately.
- *
- * @param adv_addr_type advertiser device address type
- * @param adv_addr advertiser device address
- * @param adv_sid advertising set ID
- * @param cb status callback
- */
- virtual void PeriodicAdvertiserListRemoveDevice(uint8_t adv_addr_type,
- RawAddress& adv_addr,
- uint8_t adv_sid,
- status_cb cb) = 0;
-
- /**
- * Remove all entries from the list of Periodic Advertisers in the Controller.
- *
- * @param cb status callback
- */
- virtual void PeriodicAdvertiserListClear(status_cb cb) = 0;
-
- /**
- * Read the total number of Periodic Advertiser list entries that can be
- * stored in the Controller.
- *
- * @param cb status and advertiser list size callback
- */
- virtual void PeriodicAdvertiserListGetSize(list_size_cb cb) = 0;
-
- /**
- * Send synchronization information about the periodic advertising train
- * identified by the sync_handle parameter to a connected device.
- *
- * @param bd_addr connected peer device address to whom sync data is
- * transferred
- * @param service_data a value provided by the Host
- * @param sync_handle synced advewrtising handle
- * @param cb status and connection handle callback
- */
- virtual void PeriodicAdvSyncTransfer(const RawAddress& bd_addr,
- uint16_t service_data,
- uint16_t sync_handle, handle_cb cb) = 0;
-
- /**
- * Send synchronization information about the periodic advertising in an
- * advertising set to a connected device.
- *
- * @param bd_addr connected peer device address to whom set info is
- * transferred
- * @param service_data a value provided by the Host
- * @param sync_handle synced advertising handle
- * @param cb status and connection handle callback
- */
- virtual void PeriodicAdvSetInfoTransfer(const RawAddress& bd_addr,
- uint16_t service_data,
- uint8_t sync_handle,
- handle_cb cb) = 0;
-
- /**
- * Specify how the Controller will process periodic advertising
- * synchronization information received from the device identified by the
- * bd_addr
- *
- * @param bd_addr connected peer device address who transfers the sync data
- * @param mode 0x00: No attempt is made to synchronize to the periodic
- * advertising and no HCI_LE_Periodic_Advertising_Sync_Transfer_Received event
- * is sent to the Host. 0x01: An
- * HCI_LE_Periodic_Advertising_Sync_Transfer_Received event is sent to the
- * Host. HCI_LE_Periodic_Advertising_Report events will be disabled. 0x02: An
- * HCI_LE_Periodic_Advertising_Sync_Transfer_Received event is sent to the
- * Host. HCI_LE_Periodic_Advertising_Report events will be enabled. All other
- * values: Reserved for future use.
- * @param skip The number of periodic advertising packets that can be skipped
- * after a successful receive, Range: 0x0000 to 0x01F3
- * @param sync_timeout Synchronization timeout for the periodic advertising
- * train. Range: 0x000A to 0x4000. Time = N*10 ms. Time Range: 100 ms to
- * 163.84 s
- * @param cte_type bit 0: do not sync to packets with an AoA Constant Tone
- * Extension, bit 1: do not sync to packets with an AoD Constant Tone
- * Extension with 1 μs slots, bit 2: do not sync to packets with an AoD
- * Constant Tone Extension with 2 μs slots, bit 4: do not sync to packets
- * without a Constant Tone Extension, all other values: reserved for future
- * use.
- * @param set_defaults whether to send
- * HCI_LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAM or
- * HCI_LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAM.
- * @param cb status callback
- */
- virtual void SetPeriodicAdvSyncTransferParams(const RawAddress& bd_addr,
- uint8_t mode, uint16_t skip,
- uint16_t sync_timeout,
- uint8_t cte_type,
- bool set_defaults,
- status_cb cb) = 0;
-
- static constexpr uint8_t kOptUseAdvertiserList = 0x01;
- static constexpr uint8_t kOptReportsInitiallyEnabled = 0x02;
-};
-
-#endif // BLE_SCANNER_HCI_INTERFACE_H
diff --git a/stack/btm/btm_acl.cc b/stack/btm/btm_acl.cc
new file mode 100644
index 000000000..e132f6fb1
--- /dev/null
+++ b/stack/btm/btm_acl.cc
@@ -0,0 +1,2594 @@
+/******************************************************************************
+ *
+ * Copyright 2000-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+/*****************************************************************************
+ *
+ * Name: btm_acl.cc
+ *
+ * Description: This file contains functions that handle ACL connections.
+ * This includes operations such as hold and sniff modes,
+ * supported packet types.
+ *
+ * This module contains both internal and external (API)
+ * functions. External (API) functions are distinguishable
+ * by their names beginning with uppercase BTM.
+ *
+ *
+ *****************************************************************************/
+
+#define LOG_TAG "btm_acl"
+
+#include <stddef.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "bt_common.h"
+#include "bt_target.h"
+#include "bt_types.h"
+#include "bt_utils.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
+#include "common/metrics.h"
+#include "device/include/controller.h"
+#include "device/include/interop.h"
+#include "hcidefs.h"
+#include "hcimsgs.h"
+#include "l2c_int.h"
+#include "osi/include/log.h"
+#include "osi/include/osi.h"
+
+static void btm_read_remote_features(uint16_t handle);
+static void btm_read_remote_ext_features(uint16_t handle, uint8_t page_number);
+static void btm_process_remote_ext_features(tACL_CONN* p_acl_cb,
+ uint8_t num_read_pages);
+
+/* 3 seconds timeout waiting for responses */
+#define BTM_DEV_REPLY_TIMEOUT_MS (3 * 1000)
+
+/*******************************************************************************
+ *
+ * Function btm_acl_init
+ *
+ * Description This function is called at BTM startup to initialize
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_acl_init(void) {
+ BTM_TRACE_DEBUG("btm_acl_init");
+ /* Initialize nonzero defaults */
+ btm_cb.btm_def_link_super_tout = HCI_DEFAULT_INACT_TOUT;
+ btm_cb.acl_disc_reason = 0xff;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_bda_to_acl
+ *
+ * Description This function returns the FIRST acl_db entry for the passed
+ * BDA.
+ *
+ * Parameters bda : BD address of the remote device
+ * transport : Physical transport used for ACL connection
+ * (BR/EDR or LE)
+ *
+ * Returns Returns pointer to the ACL DB for the requested BDA if found.
+ * NULL if not found.
+ *
+ ******************************************************************************/
+tACL_CONN* btm_bda_to_acl(const RawAddress& bda, tBT_TRANSPORT transport) {
+ tACL_CONN* p = &btm_cb.acl_db[0];
+ uint16_t xx;
+ for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p++) {
+ if ((p->in_use) && p->remote_addr == bda && p->transport == transport) {
+ BTM_TRACE_DEBUG("btm_bda_to_acl found");
+ return (p);
+ }
+ }
+
+ /* If here, no BD Addr found */
+ return ((tACL_CONN*)NULL);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_handle_to_acl_index
+ *
+ * Description This function returns the FIRST acl_db entry for the passed
+ * hci_handle.
+ *
+ * Returns index to the acl_db or MAX_L2CAP_LINKS.
+ *
+ ******************************************************************************/
+uint8_t btm_handle_to_acl_index(uint16_t hci_handle) {
+ tACL_CONN* p = &btm_cb.acl_db[0];
+ uint8_t xx;
+ BTM_TRACE_DEBUG("btm_handle_to_acl_index");
+ for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p++) {
+ if ((p->in_use) && (p->hci_handle == hci_handle)) {
+ break;
+ }
+ }
+
+ /* If here, no BD Addr found */
+ return (xx);
+}
+
+#if (BLE_PRIVACY_SPT == TRUE)
+/*******************************************************************************
+ *
+ * Function btm_ble_get_acl_remote_addr
+ *
+ * Description This function reads the active remote address used for the
+ * connection.
+ *
+ * Returns success return true, otherwise false.
+ *
+ ******************************************************************************/
+bool btm_ble_get_acl_remote_addr(tBTM_SEC_DEV_REC* p_dev_rec,
+ RawAddress& conn_addr,
+ tBLE_ADDR_TYPE* p_addr_type) {
+ bool st = true;
+
+ if (p_dev_rec == NULL) {
+ BTM_TRACE_ERROR("%s can not find device with matching address", __func__);
+ return false;
+ }
+
+ switch (p_dev_rec->ble.active_addr_type) {
+ case BTM_BLE_ADDR_PSEUDO:
+ conn_addr = p_dev_rec->bd_addr;
+ *p_addr_type = p_dev_rec->ble.ble_addr_type;
+ break;
+
+ case BTM_BLE_ADDR_RRA:
+ conn_addr = p_dev_rec->ble.cur_rand_addr;
+ *p_addr_type = BLE_ADDR_RANDOM;
+ break;
+
+ case BTM_BLE_ADDR_STATIC:
+ conn_addr = p_dev_rec->ble.identity_addr;
+ *p_addr_type = p_dev_rec->ble.identity_addr_type;
+ break;
+
+ default:
+ BTM_TRACE_ERROR("Unknown active address: %d",
+ p_dev_rec->ble.active_addr_type);
+ st = false;
+ break;
+ }
+
+ return st;
+}
+#endif
+/*******************************************************************************
+ *
+ * Function btm_acl_created
+ *
+ * Description This function is called by L2CAP when an ACL connection
+ * is created.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_acl_created(const RawAddress& bda, DEV_CLASS dc, BD_NAME bdn,
+ uint16_t hci_handle, uint8_t link_role,
+ tBT_TRANSPORT transport) {
+ tBTM_SEC_DEV_REC* p_dev_rec = NULL;
+ tACL_CONN* p;
+ uint8_t xx;
+
+ BTM_TRACE_DEBUG("%s: peer %s hci_handle=%d link_role=%d transport=%d",
+ __func__, bda.ToString().c_str(), hci_handle, link_role,
+ transport);
+ /* Ensure we don't have duplicates */
+ p = btm_bda_to_acl(bda, transport);
+ if (p != (tACL_CONN*)NULL) {
+ p->hci_handle = hci_handle;
+ p->link_role = link_role;
+ p->transport = transport;
+ VLOG(1) << "Duplicate btm_acl_created: RemBdAddr: " << bda;
+ BTM_SetLinkPolicy(p->remote_addr, &btm_cb.btm_def_link_policy);
+ return;
+ }
+
+ /* Allocate acl_db entry */
+ for (xx = 0, p = &btm_cb.acl_db[0]; xx < MAX_L2CAP_LINKS; xx++, p++) {
+ if (!p->in_use) {
+ p->in_use = true;
+ p->hci_handle = hci_handle;
+ p->link_role = link_role;
+ p->link_up_issued = false;
+ p->remote_addr = bda;
+
+ p->transport = transport;
+#if (BLE_PRIVACY_SPT == TRUE)
+ if (transport == BT_TRANSPORT_LE)
+ btm_ble_refresh_local_resolvable_private_addr(
+ bda, btm_cb.ble_ctr_cb.addr_mgnt_cb.private_addr);
+#else
+ p->conn_addr_type = BLE_ADDR_PUBLIC;
+ p->conn_addr = *controller_get_interface()->get_address();
+
+#endif
+ p->switch_role_failed_attempts = 0;
+ p->switch_role_state = BTM_ACL_SWKEY_STATE_IDLE;
+
+ btm_pm_sm_alloc(xx);
+
+ if (dc) memcpy(p->remote_dc, dc, DEV_CLASS_LEN);
+
+ if (bdn) memcpy(p->remote_name, bdn, BTM_MAX_REM_BD_NAME_LEN);
+
+ /* if BR/EDR do something more */
+ if (transport == BT_TRANSPORT_BR_EDR) {
+ btsnd_hcic_read_rmt_clk_offset(p->hci_handle);
+ btsnd_hcic_rmt_ver_req(p->hci_handle);
+ }
+ p_dev_rec = btm_find_dev_by_handle(hci_handle);
+
+ if (p_dev_rec) {
+ BTM_TRACE_DEBUG("%s: peer %s device_type=0x%x", __func__,
+ bda.ToString().c_str(), p_dev_rec->device_type);
+ }
+
+ if (p_dev_rec && !(transport == BT_TRANSPORT_LE)) {
+ /* If remote features already known, copy them and continue connection
+ * setup */
+ if ((p_dev_rec->num_read_pages) &&
+ (p_dev_rec->num_read_pages <= (HCI_EXT_FEATURES_PAGE_MAX + 1))) {
+ memcpy(p->peer_lmp_feature_pages, p_dev_rec->feature_pages,
+ (HCI_FEATURE_BYTES_PER_PAGE * p_dev_rec->num_read_pages));
+ p->num_read_pages = p_dev_rec->num_read_pages;
+
+ const uint8_t req_pend = (p_dev_rec->sm4 & BTM_SM4_REQ_PEND);
+
+ /* Store the Peer Security Capabilites (in SM4 and rmt_sec_caps) */
+ btm_sec_set_peer_sec_caps(p, p_dev_rec);
+
+ BTM_TRACE_API("%s: pend:%d", __func__, req_pend);
+ if (req_pend) {
+ /* Request for remaining Security Features (if any) */
+ l2cu_resubmit_pending_sec_req(&p_dev_rec->bd_addr);
+ }
+ btm_establish_continue(p);
+ return;
+ }
+ }
+
+ /* If here, features are not known yet */
+ if (p_dev_rec && transport == BT_TRANSPORT_LE) {
+#if (BLE_PRIVACY_SPT == TRUE)
+ btm_ble_get_acl_remote_addr(p_dev_rec, p->active_remote_addr,
+ &p->active_remote_addr_type);
+#endif
+
+ if (HCI_LE_SLAVE_INIT_FEAT_EXC_SUPPORTED(
+ controller_get_interface()->get_features_ble()->as_array) ||
+ link_role == HCI_ROLE_MASTER) {
+ btsnd_hcic_ble_read_remote_feat(p->hci_handle);
+ } else {
+ btm_establish_continue(p);
+ }
+ }
+
+ /* read page 1 - on rmt feature event for buffer reasons */
+ return;
+ }
+ }
+}
+
+void btm_acl_update_conn_addr(uint16_t conn_handle, const RawAddress& address) {
+ uint8_t idx = btm_handle_to_acl_index(conn_handle);
+ if (idx != MAX_L2CAP_LINKS) {
+ btm_cb.acl_db[idx].conn_addr = address;
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_acl_report_role_change
+ *
+ * Description This function is called when the local device is deemed
+ * to be down. It notifies L2CAP of the failure.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_acl_report_role_change(uint8_t hci_status, const RawAddress* bda) {
+ tBTM_ROLE_SWITCH_CMPL ref_data;
+ BTM_TRACE_DEBUG("btm_acl_report_role_change");
+ if (btm_cb.devcb.p_switch_role_cb &&
+ (bda && btm_cb.devcb.switch_role_ref_data.remote_bd_addr == *bda)) {
+ memcpy(&ref_data, &btm_cb.devcb.switch_role_ref_data,
+ sizeof(tBTM_ROLE_SWITCH_CMPL));
+ ref_data.hci_status = hci_status;
+ (*btm_cb.devcb.p_switch_role_cb)(&ref_data);
+ memset(&btm_cb.devcb.switch_role_ref_data, 0,
+ sizeof(tBTM_ROLE_SWITCH_CMPL));
+ btm_cb.devcb.p_switch_role_cb = NULL;
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_acl_removed
+ *
+ * Description This function is called by L2CAP when an ACL connection
+ * is removed. Since only L2CAP creates ACL links, we use
+ * the L2CAP link index as our index into the control blocks.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_acl_removed(const RawAddress& bda, tBT_TRANSPORT transport) {
+ tACL_CONN* p;
+ tBTM_SEC_DEV_REC* p_dev_rec = NULL;
+ BTM_TRACE_DEBUG("btm_acl_removed");
+ p = btm_bda_to_acl(bda, transport);
+ if (p != (tACL_CONN*)NULL) {
+ p->in_use = false;
+
+ /* if the disconnected channel has a pending role switch, clear it now */
+ btm_acl_report_role_change(HCI_ERR_NO_CONNECTION, &bda);
+
+ /* Only notify if link up has had a chance to be issued */
+ if (p->link_up_issued) {
+ p->link_up_issued = false;
+
+ /* If anyone cares, indicate the database changed */
+ if (btm_cb.p_bl_changed_cb) {
+ tBTM_BL_EVENT_DATA evt_data;
+ evt_data.event = BTM_BL_DISCN_EVT;
+ evt_data.discn.p_bda = &bda;
+ evt_data.discn.handle = p->hci_handle;
+ evt_data.discn.transport = p->transport;
+ (*btm_cb.p_bl_changed_cb)(&evt_data);
+ }
+
+ btm_acl_update_busy_level(BTM_BLI_ACL_DOWN_EVT);
+ }
+
+ BTM_TRACE_DEBUG(
+ "acl hci_handle=%d transport=%d connectable_mode=0x%0x link_role=%d",
+ p->hci_handle, p->transport, btm_cb.ble_ctr_cb.inq_var.connectable_mode,
+ p->link_role);
+
+ p_dev_rec = btm_find_dev(bda);
+ if (p_dev_rec) {
+ BTM_TRACE_DEBUG("before update p_dev_rec->sec_flags=0x%x",
+ p_dev_rec->sec_flags);
+ if (p->transport == BT_TRANSPORT_LE) {
+ BTM_TRACE_DEBUG("LE link down");
+ p_dev_rec->sec_flags &= ~(BTM_SEC_LE_ENCRYPTED | BTM_SEC_ROLE_SWITCHED);
+ if ((p_dev_rec->sec_flags & BTM_SEC_LE_LINK_KEY_KNOWN) == 0) {
+ BTM_TRACE_DEBUG("Not Bonded");
+ p_dev_rec->sec_flags &=
+ ~(BTM_SEC_LE_LINK_KEY_AUTHED | BTM_SEC_LE_AUTHENTICATED);
+ } else {
+ BTM_TRACE_DEBUG("Bonded");
+ }
+ } else {
+ BTM_TRACE_DEBUG("Bletooth link down");
+ p_dev_rec->sec_flags &= ~(BTM_SEC_AUTHORIZED | BTM_SEC_AUTHENTICATED |
+ BTM_SEC_ENCRYPTED | BTM_SEC_ROLE_SWITCHED);
+ }
+ BTM_TRACE_DEBUG("after update p_dev_rec->sec_flags=0x%x",
+ p_dev_rec->sec_flags);
+ } else {
+ BTM_TRACE_ERROR("Device not found");
+ }
+
+ /* Clear the ACL connection data */
+ memset(p, 0, sizeof(tACL_CONN));
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_acl_device_down
+ *
+ * Description This function is called when the local device is deemed
+ * to be down. It notifies L2CAP of the failure.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_acl_device_down(void) {
+ tACL_CONN* p = &btm_cb.acl_db[0];
+ uint16_t xx;
+ BTM_TRACE_DEBUG("btm_acl_device_down");
+ for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p++) {
+ if (p->in_use) {
+ BTM_TRACE_DEBUG("hci_handle=%d HCI_ERR_HW_FAILURE ", p->hci_handle);
+ l2c_link_hci_disc_comp(p->hci_handle, HCI_ERR_HW_FAILURE);
+ }
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_acl_update_busy_level
+ *
+ * Description This function is called to update the busy level of the
+ * system.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_acl_update_busy_level(tBTM_BLI_EVENT event) {
+ bool old_inquiry_state = btm_cb.is_inquiry;
+ tBTM_BL_UPDATE_DATA evt;
+ evt.busy_level_flags = 0;
+ switch (event) {
+ case BTM_BLI_ACL_UP_EVT:
+ BTM_TRACE_DEBUG("BTM_BLI_ACL_UP_EVT");
+ break;
+ case BTM_BLI_ACL_DOWN_EVT:
+ BTM_TRACE_DEBUG("BTM_BLI_ACL_DOWN_EVT");
+ break;
+ case BTM_BLI_PAGE_EVT:
+ BTM_TRACE_DEBUG("BTM_BLI_PAGE_EVT");
+ btm_cb.is_paging = true;
+ evt.busy_level_flags = BTM_BL_PAGING_STARTED;
+ break;
+ case BTM_BLI_PAGE_DONE_EVT:
+ BTM_TRACE_DEBUG("BTM_BLI_PAGE_DONE_EVT");
+ btm_cb.is_paging = false;
+ evt.busy_level_flags = BTM_BL_PAGING_COMPLETE;
+ break;
+ case BTM_BLI_INQ_EVT:
+ BTM_TRACE_DEBUG("BTM_BLI_INQ_EVT");
+ btm_cb.is_inquiry = true;
+ evt.busy_level_flags = BTM_BL_INQUIRY_STARTED;
+ break;
+ case BTM_BLI_INQ_CANCEL_EVT:
+ BTM_TRACE_DEBUG("BTM_BLI_INQ_CANCEL_EVT");
+ btm_cb.is_inquiry = false;
+ evt.busy_level_flags = BTM_BL_INQUIRY_CANCELLED;
+ break;
+ case BTM_BLI_INQ_DONE_EVT:
+ BTM_TRACE_DEBUG("BTM_BLI_INQ_DONE_EVT");
+ btm_cb.is_inquiry = false;
+ evt.busy_level_flags = BTM_BL_INQUIRY_COMPLETE;
+ break;
+ }
+
+ uint8_t busy_level;
+ if (btm_cb.is_paging || btm_cb.is_inquiry)
+ busy_level = 10;
+ else
+ busy_level = BTM_GetNumAclLinks();
+
+ if ((busy_level != btm_cb.busy_level) ||
+ (old_inquiry_state != btm_cb.is_inquiry)) {
+ evt.event = BTM_BL_UPDATE_EVT;
+ evt.busy_level = busy_level;
+ btm_cb.busy_level = busy_level;
+ if (btm_cb.p_bl_changed_cb && (btm_cb.bl_evt_mask & BTM_BL_UPDATE_MASK)) {
+ tBTM_BL_EVENT_DATA btm_bl_event_data;
+ btm_bl_event_data.update = evt;
+ (*btm_cb.p_bl_changed_cb)(&btm_bl_event_data);
+ }
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_GetRole
+ *
+ * Description This function is called to get the role of the local device
+ * for the ACL connection with the specified remote device
+ *
+ * Returns BTM_SUCCESS if connection exists.
+ * BTM_UNKNOWN_ADDR if no active link with bd addr specified
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_GetRole(const RawAddress& remote_bd_addr, uint8_t* p_role) {
+ tACL_CONN* p;
+ BTM_TRACE_DEBUG("BTM_GetRole");
+ p = btm_bda_to_acl(remote_bd_addr, BT_TRANSPORT_BR_EDR);
+ if (p == NULL) {
+ *p_role = BTM_ROLE_UNDEFINED;
+ return (BTM_UNKNOWN_ADDR);
+ }
+
+ /* Get the current role */
+ *p_role = p->link_role;
+ return (BTM_SUCCESS);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_SwitchRole
+ *
+ * Description This function is called to switch role between master and
+ * slave. If role is already set it will do nothing. If the
+ * command was initiated, the callback function is called upon
+ * completion.
+ *
+ * Returns BTM_SUCCESS if already in specified role.
+ * BTM_CMD_STARTED if command issued to controller.
+ * BTM_NO_RESOURCES if couldn't allocate memory to issue
+ * command
+ * BTM_UNKNOWN_ADDR if no active link with bd addr specified
+ * BTM_MODE_UNSUPPORTED if local device does not support role
+ * switching
+ * BTM_BUSY if the previous command is not completed
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SwitchRole(const RawAddress& remote_bd_addr, uint8_t new_role,
+ tBTM_CMPL_CB* p_cb) {
+ tACL_CONN* p;
+ tBTM_SEC_DEV_REC* p_dev_rec = NULL;
+ bool is_sco_active;
+ tBTM_STATUS status;
+ tBTM_PM_MODE pwr_mode;
+ tBTM_PM_PWR_MD settings;
+
+ LOG_INFO(LOG_TAG, "%s: peer %s new_role=0x%x p_cb=%p p_switch_role_cb=%p",
+ __func__, remote_bd_addr.ToString().c_str(), new_role, p_cb,
+ btm_cb.devcb.p_switch_role_cb);
+
+ /* Make sure the local device supports switching */
+ if (!controller_get_interface()->supports_master_slave_role_switch())
+ return (BTM_MODE_UNSUPPORTED);
+
+ if (btm_cb.devcb.p_switch_role_cb && p_cb) {
+ VLOG(2) << "Role switch on other device is in progress "
+ << btm_cb.devcb.switch_role_ref_data.remote_bd_addr;
+ return (BTM_BUSY);
+ }
+
+ p = btm_bda_to_acl(remote_bd_addr, BT_TRANSPORT_BR_EDR);
+ if (p == NULL) return (BTM_UNKNOWN_ADDR);
+
+ /* Finished if already in desired role */
+ if (p->link_role == new_role) return (BTM_SUCCESS);
+
+ if (interop_match_addr(INTEROP_DISABLE_ROLE_SWITCH, &remote_bd_addr))
+ return BTM_DEV_BLACKLISTED;
+
+ /* Check if there is any SCO Active on this BD Address */
+ is_sco_active = btm_is_sco_active_by_bdaddr(remote_bd_addr);
+
+ if (is_sco_active) return (BTM_NO_RESOURCES);
+
+ /* Ignore role switch request if the previous request was not completed */
+ if (p->switch_role_state != BTM_ACL_SWKEY_STATE_IDLE) {
+ BTM_TRACE_DEBUG("BTM_SwitchRole busy: %d", p->switch_role_state);
+ return (BTM_BUSY);
+ }
+
+ if (interop_match_addr(INTEROP_DYNAMIC_ROLE_SWITCH, &remote_bd_addr)) {
+ BTM_TRACE_DEBUG("%s, Device blacklisted under INTEROP_DYNAMIC_ROLE_SWITCH.",
+ __func__);
+ return BTM_DEV_BLACKLISTED;
+ }
+
+ status = BTM_ReadPowerMode(p->remote_addr, &pwr_mode);
+ if (status != BTM_SUCCESS) return (status);
+
+ /* Wake up the link if in sniff or park before attempting switch */
+ if (pwr_mode == BTM_PM_MD_PARK || pwr_mode == BTM_PM_MD_SNIFF) {
+ memset((void*)&settings, 0, sizeof(settings));
+ settings.mode = BTM_PM_MD_ACTIVE;
+ status = BTM_SetPowerMode(BTM_PM_SET_ONLY_ID, p->remote_addr, &settings);
+ if (status != BTM_CMD_STARTED) return (BTM_WRONG_MODE);
+
+ p->switch_role_state = BTM_ACL_SWKEY_STATE_MODE_CHANGE;
+ }
+ /* some devices do not support switch while encryption is on */
+ else {
+ p_dev_rec = btm_find_dev(remote_bd_addr);
+ if ((p_dev_rec != NULL) &&
+ ((p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED) != 0) &&
+ !BTM_EPR_AVAILABLE(p)) {
+ /* bypass turning off encryption if change link key is already doing it */
+ if (p->encrypt_state != BTM_ACL_ENCRYPT_STATE_ENCRYPT_OFF) {
+ btsnd_hcic_set_conn_encrypt(p->hci_handle, false);
+ p->encrypt_state = BTM_ACL_ENCRYPT_STATE_ENCRYPT_OFF;
+ }
+
+ p->switch_role_state = BTM_ACL_SWKEY_STATE_ENCRYPTION_OFF;
+ } else {
+ btsnd_hcic_switch_role(remote_bd_addr, new_role);
+ p->switch_role_state = BTM_ACL_SWKEY_STATE_IN_PROGRESS;
+
+#if (BTM_DISC_DURING_RS == TRUE)
+ if (p_dev_rec) p_dev_rec->rs_disc_pending = BTM_SEC_RS_PENDING;
+#endif
+ }
+ }
+
+ /* Initialize return structure in case request fails */
+ if (p_cb) {
+ btm_cb.devcb.switch_role_ref_data.remote_bd_addr = remote_bd_addr;
+ btm_cb.devcb.switch_role_ref_data.role = new_role;
+ /* initialized to an error code */
+ btm_cb.devcb.switch_role_ref_data.hci_status = HCI_ERR_UNSUPPORTED_VALUE;
+ btm_cb.devcb.p_switch_role_cb = p_cb;
+ }
+ return (BTM_CMD_STARTED);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_acl_encrypt_change
+ *
+ * Description This function is when encryption of the connection is
+ * completed by the LM. Checks to see if a role switch or
+ * change of link key was active and initiates or continues
+ * process if needed.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_acl_encrypt_change(uint16_t handle, uint8_t status,
+ uint8_t encr_enable) {
+ tACL_CONN* p;
+ uint8_t xx;
+ tBTM_SEC_DEV_REC* p_dev_rec;
+
+ BTM_TRACE_DEBUG("btm_acl_encrypt_change handle=%d status=%d encr_enabl=%d",
+ handle, status, encr_enable);
+ xx = btm_handle_to_acl_index(handle);
+ /* don't assume that we can never get a bad hci_handle */
+ if (xx < MAX_L2CAP_LINKS)
+ p = &btm_cb.acl_db[xx];
+ else
+ return;
+
+ /* Process Role Switch if active */
+ if (p->switch_role_state == BTM_ACL_SWKEY_STATE_ENCRYPTION_OFF) {
+ /* if encryption turn off failed we still will try to switch role */
+ if (encr_enable) {
+ p->switch_role_state = BTM_ACL_SWKEY_STATE_IDLE;
+ p->encrypt_state = BTM_ACL_ENCRYPT_STATE_IDLE;
+ } else {
+ p->switch_role_state = BTM_ACL_SWKEY_STATE_SWITCHING;
+ p->encrypt_state = BTM_ACL_ENCRYPT_STATE_TEMP_FUNC;
+ }
+
+ btsnd_hcic_switch_role(p->remote_addr, (uint8_t)!p->link_role);
+#if (BTM_DISC_DURING_RS == TRUE)
+ p_dev_rec = btm_find_dev(p->remote_addr);
+ if (p_dev_rec != NULL) p_dev_rec->rs_disc_pending = BTM_SEC_RS_PENDING;
+#endif
+
+ }
+ /* Finished enabling Encryption after role switch */
+ else if (p->switch_role_state == BTM_ACL_SWKEY_STATE_ENCRYPTION_ON) {
+ p->switch_role_state = BTM_ACL_SWKEY_STATE_IDLE;
+ p->encrypt_state = BTM_ACL_ENCRYPT_STATE_IDLE;
+ btm_acl_report_role_change(btm_cb.devcb.switch_role_ref_data.hci_status,
+ &p->remote_addr);
+
+ /* if role change event is registered, report it now */
+ if (btm_cb.p_bl_changed_cb && (btm_cb.bl_evt_mask & BTM_BL_ROLE_CHG_MASK)) {
+ tBTM_BL_ROLE_CHG_DATA evt;
+ evt.event = BTM_BL_ROLE_CHG_EVT;
+ evt.new_role = btm_cb.devcb.switch_role_ref_data.role;
+ evt.p_bda = &btm_cb.devcb.switch_role_ref_data.remote_bd_addr;
+ evt.hci_status = btm_cb.devcb.switch_role_ref_data.hci_status;
+ tBTM_BL_EVENT_DATA btm_bl_event_data;
+ btm_bl_event_data.role_chg = evt;
+ (*btm_cb.p_bl_changed_cb)(&btm_bl_event_data);
+
+ BTM_TRACE_DEBUG(
+ "%s: Role Switch Event: new_role 0x%02x, HCI Status 0x%02x, rs_st:%d",
+ __func__, evt.new_role, evt.hci_status, p->switch_role_state);
+ }
+
+#if (BTM_DISC_DURING_RS == TRUE)
+ /* If a disconnect is pending, issue it now that role switch has completed
+ */
+ p_dev_rec = btm_find_dev(p->remote_addr);
+ if (p_dev_rec != NULL) {
+ if (p_dev_rec->rs_disc_pending == BTM_SEC_DISC_PENDING) {
+ BTM_TRACE_WARNING(
+ "btm_acl_encrypt_change -> Issuing delayed HCI_Disconnect!!!");
+ btsnd_hcic_disconnect(p_dev_rec->hci_handle, HCI_ERR_PEER_USER);
+ }
+ BTM_TRACE_ERROR(
+ "btm_acl_encrypt_change: tBTM_SEC_DEV:0x%x rs_disc_pending=%d",
+ PTR_TO_UINT(p_dev_rec), p_dev_rec->rs_disc_pending);
+ p_dev_rec->rs_disc_pending = BTM_SEC_RS_NOT_PENDING; /* reset flag */
+ }
+#endif
+ }
+}
+/*******************************************************************************
+ *
+ * Function BTM_SetLinkPolicy
+ *
+ * Description Create and send HCI "Write Policy Set" command
+ *
+ * Returns status of the operation
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SetLinkPolicy(const RawAddress& remote_bda,
+ uint16_t* settings) {
+ tACL_CONN* p;
+ uint8_t* localFeatures = BTM_ReadLocalFeatures();
+ BTM_TRACE_DEBUG("%s", __func__);
+ /* BTM_TRACE_API ("%s: requested settings: 0x%04x", __func__, *settings ); */
+
+ /* First, check if hold mode is supported */
+ if (*settings != HCI_DISABLE_ALL_LM_MODES) {
+ if ((*settings & HCI_ENABLE_MASTER_SLAVE_SWITCH) &&
+ (!HCI_SWITCH_SUPPORTED(localFeatures))) {
+ *settings &= (~HCI_ENABLE_MASTER_SLAVE_SWITCH);
+ BTM_TRACE_API("BTM_SetLinkPolicy switch not supported (settings: 0x%04x)",
+ *settings);
+ }
+ if ((*settings & HCI_ENABLE_HOLD_MODE) &&
+ (!HCI_HOLD_MODE_SUPPORTED(localFeatures))) {
+ *settings &= (~HCI_ENABLE_HOLD_MODE);
+ BTM_TRACE_API("BTM_SetLinkPolicy hold not supported (settings: 0x%04x)",
+ *settings);
+ }
+ if ((*settings & HCI_ENABLE_SNIFF_MODE) &&
+ (!HCI_SNIFF_MODE_SUPPORTED(localFeatures))) {
+ *settings &= (~HCI_ENABLE_SNIFF_MODE);
+ BTM_TRACE_API("BTM_SetLinkPolicy sniff not supported (settings: 0x%04x)",
+ *settings);
+ }
+ if ((*settings & HCI_ENABLE_PARK_MODE) &&
+ (!HCI_PARK_MODE_SUPPORTED(localFeatures))) {
+ *settings &= (~HCI_ENABLE_PARK_MODE);
+ BTM_TRACE_API("BTM_SetLinkPolicy park not supported (settings: 0x%04x)",
+ *settings);
+ }
+ }
+
+ p = btm_bda_to_acl(remote_bda, BT_TRANSPORT_BR_EDR);
+ if (p != NULL) {
+ btsnd_hcic_write_policy_set(p->hci_handle, *settings);
+ return BTM_CMD_STARTED;
+ }
+
+ /* If here, no BD Addr found */
+ return (BTM_UNKNOWN_ADDR);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_SetDefaultLinkPolicy
+ *
+ * Description Set the default value for HCI "Write Policy Set" command
+ * to use when an ACL link is created.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_SetDefaultLinkPolicy(uint16_t settings) {
+ uint8_t* localFeatures = BTM_ReadLocalFeatures();
+
+ BTM_TRACE_DEBUG("BTM_SetDefaultLinkPolicy setting:0x%04x", settings);
+
+ if ((settings & HCI_ENABLE_MASTER_SLAVE_SWITCH) &&
+ (!HCI_SWITCH_SUPPORTED(localFeatures))) {
+ settings &= ~HCI_ENABLE_MASTER_SLAVE_SWITCH;
+ BTM_TRACE_DEBUG(
+ "BTM_SetDefaultLinkPolicy switch not supported (settings: 0x%04x)",
+ settings);
+ }
+ if ((settings & HCI_ENABLE_HOLD_MODE) &&
+ (!HCI_HOLD_MODE_SUPPORTED(localFeatures))) {
+ settings &= ~HCI_ENABLE_HOLD_MODE;
+ BTM_TRACE_DEBUG(
+ "BTM_SetDefaultLinkPolicy hold not supported (settings: 0x%04x)",
+ settings);
+ }
+ if ((settings & HCI_ENABLE_SNIFF_MODE) &&
+ (!HCI_SNIFF_MODE_SUPPORTED(localFeatures))) {
+ settings &= ~HCI_ENABLE_SNIFF_MODE;
+ BTM_TRACE_DEBUG(
+ "BTM_SetDefaultLinkPolicy sniff not supported (settings: 0x%04x)",
+ settings);
+ }
+ if ((settings & HCI_ENABLE_PARK_MODE) &&
+ (!HCI_PARK_MODE_SUPPORTED(localFeatures))) {
+ settings &= ~HCI_ENABLE_PARK_MODE;
+ BTM_TRACE_DEBUG(
+ "BTM_SetDefaultLinkPolicy park not supported (settings: 0x%04x)",
+ settings);
+ }
+ BTM_TRACE_DEBUG("Set DefaultLinkPolicy:0x%04x", settings);
+
+ btm_cb.btm_def_link_policy = settings;
+
+ /* Set the default Link Policy of the controller */
+ btsnd_hcic_write_def_policy_set(settings);
+}
+
+void btm_use_preferred_conn_params(const RawAddress& bda) {
+ tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(bda, BT_TRANSPORT_LE);
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_or_alloc_dev(bda);
+
+ /* If there are any preferred connection parameters, set them now */
+ if ((p_lcb != NULL) && (p_dev_rec != NULL) &&
+ (p_dev_rec->conn_params.min_conn_int >= BTM_BLE_CONN_INT_MIN) &&
+ (p_dev_rec->conn_params.min_conn_int <= BTM_BLE_CONN_INT_MAX) &&
+ (p_dev_rec->conn_params.max_conn_int >= BTM_BLE_CONN_INT_MIN) &&
+ (p_dev_rec->conn_params.max_conn_int <= BTM_BLE_CONN_INT_MAX) &&
+ (p_dev_rec->conn_params.slave_latency <= BTM_BLE_CONN_LATENCY_MAX) &&
+ (p_dev_rec->conn_params.supervision_tout >= BTM_BLE_CONN_SUP_TOUT_MIN) &&
+ (p_dev_rec->conn_params.supervision_tout <= BTM_BLE_CONN_SUP_TOUT_MAX) &&
+ ((p_lcb->min_interval < p_dev_rec->conn_params.min_conn_int &&
+ p_dev_rec->conn_params.min_conn_int != BTM_BLE_CONN_PARAM_UNDEF) ||
+ (p_lcb->min_interval > p_dev_rec->conn_params.max_conn_int) ||
+ (p_lcb->latency > p_dev_rec->conn_params.slave_latency) ||
+ (p_lcb->timeout > p_dev_rec->conn_params.supervision_tout))) {
+ BTM_TRACE_DEBUG(
+ "%s: HANDLE=%d min_conn_int=%d max_conn_int=%d slave_latency=%d "
+ "supervision_tout=%d",
+ __func__, p_lcb->handle, p_dev_rec->conn_params.min_conn_int,
+ p_dev_rec->conn_params.max_conn_int,
+ p_dev_rec->conn_params.slave_latency,
+ p_dev_rec->conn_params.supervision_tout);
+
+ p_lcb->min_interval = p_dev_rec->conn_params.min_conn_int;
+ p_lcb->max_interval = p_dev_rec->conn_params.max_conn_int;
+ p_lcb->timeout = p_dev_rec->conn_params.supervision_tout;
+ p_lcb->latency = p_dev_rec->conn_params.slave_latency;
+
+ btsnd_hcic_ble_upd_ll_conn_params(
+ p_lcb->handle, p_dev_rec->conn_params.min_conn_int,
+ p_dev_rec->conn_params.max_conn_int,
+ p_dev_rec->conn_params.slave_latency,
+ p_dev_rec->conn_params.supervision_tout, 0, 0);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_remote_version_complete
+ *
+ * Description This function is called when the command complete message
+ * is received from the HCI for the remote version info.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_remote_version_complete(uint8_t* p) {
+ tACL_CONN* p_acl_cb = &btm_cb.acl_db[0];
+ uint8_t status;
+ uint16_t handle;
+ int xx;
+ BTM_TRACE_DEBUG("btm_read_remote_version_complete");
+
+ STREAM_TO_UINT8(status, p);
+ STREAM_TO_UINT16(handle, p);
+
+ /* Look up the connection by handle and copy features */
+ for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p_acl_cb++) {
+ if ((p_acl_cb->in_use) && (p_acl_cb->hci_handle == handle)) {
+ if (status == HCI_SUCCESS) {
+ STREAM_TO_UINT8(p_acl_cb->lmp_version, p);
+ STREAM_TO_UINT16(p_acl_cb->manufacturer, p);
+ STREAM_TO_UINT16(p_acl_cb->lmp_subversion, p);
+
+ if (p_acl_cb->transport == BT_TRANSPORT_BR_EDR) {
+ btm_read_remote_features(p_acl_cb->hci_handle);
+ }
+ bluetooth::common::LogRemoteVersionInfo(
+ handle, status, p_acl_cb->lmp_version, p_acl_cb->manufacturer,
+ p_acl_cb->lmp_subversion);
+ } else {
+ bluetooth::common::LogRemoteVersionInfo(handle, status, 0, 0, 0);
+ }
+
+ if (p_acl_cb->transport == BT_TRANSPORT_LE) {
+ l2cble_notify_le_connection(p_acl_cb->remote_addr);
+ btm_use_preferred_conn_params(p_acl_cb->remote_addr);
+ }
+ break;
+ }
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_process_remote_ext_features
+ *
+ * Description Local function called to process all extended features pages
+ * read from a remote device.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_process_remote_ext_features(tACL_CONN* p_acl_cb,
+ uint8_t num_read_pages) {
+ uint16_t handle = p_acl_cb->hci_handle;
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev_by_handle(handle);
+ uint8_t page_idx;
+
+ BTM_TRACE_DEBUG("btm_process_remote_ext_features");
+
+ /* Make sure we have the record to save remote features information */
+ if (p_dev_rec == NULL) {
+ /* Get a new device; might be doing dedicated bonding */
+ p_dev_rec = btm_find_or_alloc_dev(p_acl_cb->remote_addr);
+ }
+
+ p_acl_cb->num_read_pages = num_read_pages;
+ p_dev_rec->num_read_pages = num_read_pages;
+
+ /* Move the pages to placeholder */
+ for (page_idx = 0; page_idx < num_read_pages; page_idx++) {
+ if (page_idx > HCI_EXT_FEATURES_PAGE_MAX) {
+ BTM_TRACE_ERROR("%s: page=%d unexpected", __func__, page_idx);
+ break;
+ }
+ memcpy(p_dev_rec->feature_pages[page_idx],
+ p_acl_cb->peer_lmp_feature_pages[page_idx],
+ HCI_FEATURE_BYTES_PER_PAGE);
+ }
+
+ if (!(p_dev_rec->sec_flags & BTM_SEC_NAME_KNOWN) ||
+ p_dev_rec->is_originator) {
+ BTM_TRACE_DEBUG("%s: Calling Next Security Procedure", __func__);
+ uint8_t status = btm_sec_execute_procedure(p_dev_rec);
+ if (status != BTM_CMD_STARTED) {
+ BTM_TRACE_ERROR("%s: Security procedure not started! status %d", __func__,
+ status);
+ btm_sec_dev_rec_cback_event(p_dev_rec, status, false);
+ }
+ }
+ const uint8_t req_pend = (p_dev_rec->sm4 & BTM_SM4_REQ_PEND);
+
+ /* Store the Peer Security Capabilites (in SM4 and rmt_sec_caps) */
+ btm_sec_set_peer_sec_caps(p_acl_cb, p_dev_rec);
+
+ BTM_TRACE_API("%s: pend:%d", __func__, req_pend);
+ if (req_pend) {
+ /* Request for remaining Security Features (if any) */
+ l2cu_resubmit_pending_sec_req(&p_dev_rec->bd_addr);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_remote_features
+ *
+ * Description Local function called to send a read remote supported
+ * features/remote extended features page[0].
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_remote_features(uint16_t handle) {
+ uint8_t acl_idx;
+ tACL_CONN* p_acl_cb;
+
+ BTM_TRACE_DEBUG("btm_read_remote_features() handle: %d", handle);
+
+ acl_idx = btm_handle_to_acl_index(handle);
+ if (acl_idx >= MAX_L2CAP_LINKS) {
+ BTM_TRACE_ERROR("btm_read_remote_features handle=%d invalid", handle);
+ return;
+ }
+
+ p_acl_cb = &btm_cb.acl_db[acl_idx];
+ p_acl_cb->num_read_pages = 0;
+ memset(p_acl_cb->peer_lmp_feature_pages, 0,
+ sizeof(p_acl_cb->peer_lmp_feature_pages));
+
+ /* first send read remote supported features HCI command */
+ /* because we don't know whether the remote support extended feature command
+ */
+ btsnd_hcic_rmt_features_req(handle);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_remote_ext_features
+ *
+ * Description Local function called to send a read remote extended
+ * features
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_remote_ext_features(uint16_t handle, uint8_t page_number) {
+ BTM_TRACE_DEBUG("btm_read_remote_ext_features() handle: %d page: %d", handle,
+ page_number);
+
+ btsnd_hcic_rmt_ext_features(handle, page_number);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_remote_features_complete
+ *
+ * Description This function is called when the remote supported features
+ * complete event is received from the HCI.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_remote_features_complete(uint8_t* p) {
+ tACL_CONN* p_acl_cb;
+ uint8_t status;
+ uint16_t handle;
+ uint8_t acl_idx;
+
+ BTM_TRACE_DEBUG("btm_read_remote_features_complete");
+ STREAM_TO_UINT8(status, p);
+
+ if (status != HCI_SUCCESS) {
+ BTM_TRACE_ERROR("btm_read_remote_features_complete failed (status 0x%02x)",
+ status);
+ return;
+ }
+
+ STREAM_TO_UINT16(handle, p);
+
+ acl_idx = btm_handle_to_acl_index(handle);
+ if (acl_idx >= MAX_L2CAP_LINKS) {
+ BTM_TRACE_ERROR("btm_read_remote_features_complete handle=%d invalid",
+ handle);
+ return;
+ }
+
+ p_acl_cb = &btm_cb.acl_db[acl_idx];
+
+ /* Copy the received features page */
+ STREAM_TO_ARRAY(p_acl_cb->peer_lmp_feature_pages[0], p,
+ HCI_FEATURE_BYTES_PER_PAGE);
+
+ if ((HCI_LMP_EXTENDED_SUPPORTED(p_acl_cb->peer_lmp_feature_pages[0])) &&
+ (controller_get_interface()
+ ->supports_reading_remote_extended_features())) {
+ /* if the remote controller has extended features and local controller
+ supports HCI_Read_Remote_Extended_Features command then start reading
+ these feature starting with extended features page 1 */
+ BTM_TRACE_DEBUG("Start reading remote extended features");
+ btm_read_remote_ext_features(handle, 1);
+ return;
+ }
+
+ /* Remote controller has no extended features. Process remote controller
+ supported features (features page 0). */
+ btm_process_remote_ext_features(p_acl_cb, 1);
+
+ /* Continue with HCI connection establishment */
+ btm_establish_continue(p_acl_cb);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_remote_ext_features_complete
+ *
+ * Description This function is called when the remote extended features
+ * complete event is received from the HCI.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_remote_ext_features_complete(uint8_t* p, uint8_t evt_len) {
+ tACL_CONN* p_acl_cb;
+ uint8_t page_num, max_page;
+ uint16_t handle;
+ uint8_t acl_idx;
+
+ BTM_TRACE_DEBUG("btm_read_remote_ext_features_complete");
+
+ if (evt_len < HCI_EXT_FEATURES_SUCCESS_EVT_LEN) {
+ android_errorWriteLog(0x534e4554, "141552859");
+ BTM_TRACE_ERROR(
+ "btm_read_remote_ext_features_complete evt length too short. length=%d",
+ evt_len);
+ return;
+ }
+
+ ++p;
+ STREAM_TO_UINT16(handle, p);
+ STREAM_TO_UINT8(page_num, p);
+ STREAM_TO_UINT8(max_page, p);
+
+ /* Validate parameters */
+ acl_idx = btm_handle_to_acl_index(handle);
+ if (acl_idx >= MAX_L2CAP_LINKS) {
+ BTM_TRACE_ERROR("btm_read_remote_ext_features_complete handle=%d invalid",
+ handle);
+ return;
+ }
+
+ if (max_page > HCI_EXT_FEATURES_PAGE_MAX) {
+ BTM_TRACE_ERROR("btm_read_remote_ext_features_complete page=%d unknown",
+ max_page);
+ return;
+ }
+
+ if (page_num > HCI_EXT_FEATURES_PAGE_MAX) {
+ android_errorWriteLog(0x534e4554, "141552859");
+ BTM_TRACE_ERROR("btm_read_remote_ext_features_complete num_page=%d invalid",
+ page_num);
+ return;
+ }
+
+ if (page_num > max_page) {
+ BTM_TRACE_WARNING(
+ "btm_read_remote_ext_features_complete num_page=%d, max_page=%d "
+ "invalid", page_num, max_page);
+ }
+
+ p_acl_cb = &btm_cb.acl_db[acl_idx];
+
+ /* Copy the received features page */
+ STREAM_TO_ARRAY(p_acl_cb->peer_lmp_feature_pages[page_num], p,
+ HCI_FEATURE_BYTES_PER_PAGE);
+
+ /* If there is the next remote features page and
+ * we have space to keep this page data - read this page */
+ if ((page_num < max_page) && (page_num < HCI_EXT_FEATURES_PAGE_MAX)) {
+ page_num++;
+ BTM_TRACE_DEBUG("BTM reads next remote extended features page (%d)",
+ page_num);
+ btm_read_remote_ext_features(handle, page_num);
+ return;
+ }
+
+ /* Reading of remote feature pages is complete */
+ BTM_TRACE_DEBUG("BTM reached last remote extended features page (%d)",
+ page_num);
+
+ /* Process the pages */
+ btm_process_remote_ext_features(p_acl_cb, (uint8_t)(page_num + 1));
+
+ /* Continue with HCI connection establishment */
+ btm_establish_continue(p_acl_cb);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_remote_ext_features_failed
+ *
+ * Description This function is called when the remote extended features
+ * complete event returns a failed status.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_remote_ext_features_failed(uint8_t status, uint16_t handle) {
+ tACL_CONN* p_acl_cb;
+ uint8_t acl_idx;
+
+ BTM_TRACE_WARNING(
+ "btm_read_remote_ext_features_failed (status 0x%02x) for handle %d",
+ status, handle);
+
+ acl_idx = btm_handle_to_acl_index(handle);
+ if (acl_idx >= MAX_L2CAP_LINKS) {
+ BTM_TRACE_ERROR("btm_read_remote_ext_features_failed handle=%d invalid",
+ handle);
+ return;
+ }
+
+ p_acl_cb = &btm_cb.acl_db[acl_idx];
+
+ /* Process supported features only */
+ btm_process_remote_ext_features(p_acl_cb, 1);
+
+ /* Continue HCI connection establishment */
+ btm_establish_continue(p_acl_cb);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_establish_continue
+ *
+ * Description This function is called when the command complete message
+ * is received from the HCI for the read local link policy
+ * request.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_establish_continue(tACL_CONN* p_acl_cb) {
+ tBTM_BL_EVENT_DATA evt_data;
+ BTM_TRACE_DEBUG("btm_establish_continue");
+#if (BTM_BYPASS_EXTRA_ACL_SETUP == FALSE)
+ if (p_acl_cb->transport == BT_TRANSPORT_BR_EDR) {
+ /* For now there are a some devices that do not like sending */
+ /* commands events and data at the same time. */
+ /* Set the packet types to the default allowed by the device */
+ btm_set_packet_types(p_acl_cb, btm_cb.btm_acl_pkt_types_supported);
+
+ if (btm_cb.btm_def_link_policy)
+ BTM_SetLinkPolicy(p_acl_cb->remote_addr, &btm_cb.btm_def_link_policy);
+ }
+#endif
+ if (p_acl_cb->link_up_issued) {
+ BTM_TRACE_ERROR("%s: Already link is up ", __func__);
+ return;
+ }
+ p_acl_cb->link_up_issued = true;
+
+ /* If anyone cares, tell him database changed */
+ if (btm_cb.p_bl_changed_cb) {
+ evt_data.event = BTM_BL_CONN_EVT;
+ evt_data.conn.p_bda = &p_acl_cb->remote_addr;
+ evt_data.conn.p_bdn = p_acl_cb->remote_name;
+ evt_data.conn.p_dc = p_acl_cb->remote_dc;
+ evt_data.conn.p_features = p_acl_cb->peer_lmp_feature_pages[0];
+ evt_data.conn.handle = p_acl_cb->hci_handle;
+ evt_data.conn.transport = p_acl_cb->transport;
+
+ (*btm_cb.p_bl_changed_cb)(&evt_data);
+ }
+ btm_acl_update_busy_level(BTM_BLI_ACL_UP_EVT);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_SetDefaultLinkSuperTout
+ *
+ * Description Set the default value for HCI "Write Link Supervision
+ * Timeout"
+ * command to use when an ACL link is created.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_SetDefaultLinkSuperTout(uint16_t timeout) {
+ BTM_TRACE_DEBUG("BTM_SetDefaultLinkSuperTout");
+ btm_cb.btm_def_link_super_tout = timeout;
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_GetLinkSuperTout
+ *
+ * Description Read the link supervision timeout value of the connection
+ *
+ * Returns status of the operation
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_GetLinkSuperTout(const RawAddress& remote_bda,
+ uint16_t* p_timeout) {
+ tACL_CONN* p = btm_bda_to_acl(remote_bda, BT_TRANSPORT_BR_EDR);
+
+ BTM_TRACE_DEBUG("BTM_GetLinkSuperTout");
+ if (p != (tACL_CONN*)NULL) {
+ *p_timeout = p->link_super_tout;
+ return (BTM_SUCCESS);
+ }
+ /* If here, no BD Addr found */
+ return (BTM_UNKNOWN_ADDR);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_SetLinkSuperTout
+ *
+ * Description Create and send HCI "Write Link Supervision Timeout" command
+ *
+ * Returns status of the operation
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SetLinkSuperTout(const RawAddress& remote_bda,
+ uint16_t timeout) {
+ tACL_CONN* p = btm_bda_to_acl(remote_bda, BT_TRANSPORT_BR_EDR);
+
+ BTM_TRACE_DEBUG("BTM_SetLinkSuperTout");
+ if (p != (tACL_CONN*)NULL) {
+ p->link_super_tout = timeout;
+
+ /* Only send if current role is Master; 2.0 spec requires this */
+ if (p->link_role == BTM_ROLE_MASTER) {
+ btsnd_hcic_write_link_super_tout(LOCAL_BR_EDR_CONTROLLER_ID,
+ p->hci_handle, timeout);
+ return (BTM_CMD_STARTED);
+ } else {
+ return (BTM_SUCCESS);
+ }
+ }
+
+ /* If here, no BD Addr found */
+ return (BTM_UNKNOWN_ADDR);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_IsAclConnectionUp
+ *
+ * Description This function is called to check if an ACL connection exists
+ * to a specific remote BD Address.
+ *
+ * Returns true if connection is up, else false.
+ *
+ ******************************************************************************/
+bool BTM_IsAclConnectionUp(const RawAddress& remote_bda,
+ tBT_TRANSPORT transport) {
+ tACL_CONN* p;
+
+ VLOG(2) << __func__ << " RemBdAddr: " << remote_bda;
+
+ p = btm_bda_to_acl(remote_bda, transport);
+ if (p != (tACL_CONN*)NULL) {
+ return (true);
+ }
+
+ /* If here, no BD Addr found */
+ return (false);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_GetNumAclLinks
+ *
+ * Description This function is called to count the number of
+ * ACL links that are active.
+ *
+ * Returns uint16_t Number of active ACL links
+ *
+ ******************************************************************************/
+uint16_t BTM_GetNumAclLinks(void) {
+ uint16_t num_acl = 0;
+
+ for (uint16_t i = 0; i < MAX_L2CAP_LINKS; ++i) {
+ if (btm_cb.acl_db[i].in_use) ++num_acl;
+ }
+
+ return num_acl;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_get_acl_disc_reason_code
+ *
+ * Description This function is called to get the disconnection reason code
+ * returned by the HCI at disconnection complete event.
+ *
+ * Returns true if connection is up, else false.
+ *
+ ******************************************************************************/
+uint16_t btm_get_acl_disc_reason_code(void) {
+ uint8_t res = btm_cb.acl_disc_reason;
+ BTM_TRACE_DEBUG("btm_get_acl_disc_reason_code");
+ return (res);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_GetHCIConnHandle
+ *
+ * Description This function is called to get the handle for an ACL
+ * connection to a specific remote BD Address.
+ *
+ * Returns the handle of the connection, or 0xFFFF if none.
+ *
+ ******************************************************************************/
+uint16_t BTM_GetHCIConnHandle(const RawAddress& remote_bda,
+ tBT_TRANSPORT transport) {
+ tACL_CONN* p;
+ BTM_TRACE_DEBUG("BTM_GetHCIConnHandle");
+ p = btm_bda_to_acl(remote_bda, transport);
+ if (p != (tACL_CONN*)NULL) {
+ return (p->hci_handle);
+ }
+
+ /* If here, no BD Addr found */
+ return (0xFFFF);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_process_clk_off_comp_evt
+ *
+ * Description This function is called when clock offset command completes.
+ *
+ * Input Parms hci_handle - connection handle associated with the change
+ * clock offset
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_process_clk_off_comp_evt(uint16_t hci_handle, uint16_t clock_offset) {
+ uint8_t xx;
+ BTM_TRACE_DEBUG("btm_process_clk_off_comp_evt");
+ /* Look up the connection by handle and set the current mode */
+ xx = btm_handle_to_acl_index(hci_handle);
+ if (xx < MAX_L2CAP_LINKS) btm_cb.acl_db[xx].clock_offset = clock_offset;
+}
+
+/*******************************************************************************
+*
+* Function btm_blacklist_role_change_device
+*
+* Description This function is used to blacklist the device if the role
+* switch fails for maximum number of times. It also removes
+* the device from the black list if the role switch succeeds.
+*
+* Input Parms bd_addr - remote BD addr
+* hci_status - role switch status
+*
+* Returns void
+*
+*******************************************************************************/
+void btm_blacklist_role_change_device(const RawAddress& bd_addr,
+ uint8_t hci_status) {
+ tACL_CONN* p = btm_bda_to_acl(bd_addr, BT_TRANSPORT_BR_EDR);
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
+
+ if (!p || !p_dev_rec) {
+ return;
+ }
+ if (hci_status == HCI_SUCCESS) {
+ p->switch_role_failed_attempts = 0;
+ return;
+ }
+
+ /* check for carkits */
+ const uint32_t cod_audio_device =
+ (BTM_COD_SERVICE_AUDIO | BTM_COD_MAJOR_AUDIO) << 8;
+ const uint32_t cod =
+ ((p_dev_rec->dev_class[0] << 16) | (p_dev_rec->dev_class[1] << 8) |
+ p_dev_rec->dev_class[2]) &
+ 0xffffff;
+ if ((hci_status != HCI_SUCCESS) &&
+ ((p->switch_role_state == BTM_ACL_SWKEY_STATE_SWITCHING) ||
+ (p->switch_role_state == BTM_ACL_SWKEY_STATE_IN_PROGRESS)) &&
+ ((cod & cod_audio_device) == cod_audio_device) &&
+ (!interop_match_addr(INTEROP_DYNAMIC_ROLE_SWITCH, &bd_addr))) {
+ p->switch_role_failed_attempts++;
+ if (p->switch_role_failed_attempts == BTM_MAX_SW_ROLE_FAILED_ATTEMPTS) {
+ BTM_TRACE_WARNING(
+ "%s: Device %s blacklisted for role switching - "
+ "multiple role switch failed attempts: %u",
+ __func__, bd_addr.ToString().c_str(), p->switch_role_failed_attempts);
+ interop_database_add(INTEROP_DYNAMIC_ROLE_SWITCH, &bd_addr, 3);
+ }
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_acl_role_changed
+ *
+ * Description This function is called whan a link's master/slave role
+ * change event or command status event (with error) is
+ * received. It updates the link control block, and calls the
+ * registered callback with status and role (if registered).
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_acl_role_changed(uint8_t hci_status, const RawAddress* bd_addr,
+ uint8_t new_role) {
+ const RawAddress* p_bda =
+ (bd_addr) ? bd_addr : &btm_cb.devcb.switch_role_ref_data.remote_bd_addr;
+ tACL_CONN* p = btm_bda_to_acl(*p_bda, BT_TRANSPORT_BR_EDR);
+ tBTM_ROLE_SWITCH_CMPL* p_data = &btm_cb.devcb.switch_role_ref_data;
+ tBTM_SEC_DEV_REC* p_dev_rec;
+
+ BTM_TRACE_DEBUG("%s: peer %s hci_status:0x%x new_role:%d", __func__,
+ (p_bda != nullptr) ? bd_addr->ToString().c_str() : "nullptr",
+ hci_status, new_role);
+ /* Ignore any stray events */
+ if (p == NULL) {
+ /* it could be a failure */
+ if (hci_status != HCI_SUCCESS)
+ btm_acl_report_role_change(hci_status, bd_addr);
+ return;
+ }
+
+ p_data->hci_status = hci_status;
+
+ if (hci_status == HCI_SUCCESS) {
+ p_data->role = new_role;
+ p_data->remote_bd_addr = *p_bda;
+
+ /* Update cached value */
+ p->link_role = new_role;
+
+ /* Reload LSTO: link supervision timeout is reset in the LM after a role
+ * switch */
+ if (new_role == BTM_ROLE_MASTER) {
+ BTM_SetLinkSuperTout(p->remote_addr, p->link_super_tout);
+ }
+ } else {
+ /* so the BTM_BL_ROLE_CHG_EVT uses the old role */
+ new_role = p->link_role;
+ }
+
+ /* Check if any SCO req is pending for role change */
+ btm_sco_chk_pend_rolechange(p->hci_handle);
+
+ /* if switching state is switching we need to turn encryption on */
+ /* if idle, we did not change encryption */
+ if (p->switch_role_state == BTM_ACL_SWKEY_STATE_SWITCHING) {
+ btsnd_hcic_set_conn_encrypt(p->hci_handle, true);
+ p->encrypt_state = BTM_ACL_ENCRYPT_STATE_ENCRYPT_ON;
+ p->switch_role_state = BTM_ACL_SWKEY_STATE_ENCRYPTION_ON;
+ return;
+ }
+
+ /* Set the switch_role_state to IDLE since the reply received from HCI */
+ /* regardless of its result either success or failed. */
+ if (p->switch_role_state == BTM_ACL_SWKEY_STATE_IN_PROGRESS) {
+ p->switch_role_state = BTM_ACL_SWKEY_STATE_IDLE;
+ p->encrypt_state = BTM_ACL_ENCRYPT_STATE_IDLE;
+ }
+
+ /* if role switch complete is needed, report it now */
+ btm_acl_report_role_change(hci_status, bd_addr);
+
+ /* if role change event is registered, report it now */
+ if (btm_cb.p_bl_changed_cb && (btm_cb.bl_evt_mask & BTM_BL_ROLE_CHG_MASK)) {
+ tBTM_BL_ROLE_CHG_DATA evt;
+ evt.event = BTM_BL_ROLE_CHG_EVT;
+ evt.new_role = new_role;
+ evt.p_bda = p_bda;
+ evt.hci_status = hci_status;
+ tBTM_BL_EVENT_DATA btm_bl_event_data;
+ btm_bl_event_data.role_chg = evt;
+ (*btm_cb.p_bl_changed_cb)(&btm_bl_event_data);
+ }
+
+ BTM_TRACE_DEBUG(
+ "%s: peer %s Role Switch Event: new_role 0x%02x, HCI Status 0x%02x, "
+ "rs_st:%d",
+ __func__, (p_bda != nullptr) ? p_bda->ToString().c_str() : "nullptr",
+ p_data->role, p_data->hci_status, p->switch_role_state);
+
+#if (BTM_DISC_DURING_RS == TRUE)
+ /* If a disconnect is pending, issue it now that role switch has completed */
+ p_dev_rec = btm_find_dev(*p_bda);
+ if (p_dev_rec != NULL) {
+ if (p_dev_rec->rs_disc_pending == BTM_SEC_DISC_PENDING) {
+ BTM_TRACE_WARNING(
+ "%s peer %s Issuing delayed HCI_Disconnect!!!", __func__,
+ (p_bda != nullptr) ? p_bda->ToString().c_str() : "nullptr");
+ btsnd_hcic_disconnect(p_dev_rec->hci_handle, HCI_ERR_PEER_USER);
+ }
+ BTM_TRACE_ERROR("%s: peer %s tBTM_SEC_DEV:0x%x rs_disc_pending=%d",
+ __func__,
+ (p_bda != nullptr) ? p_bda->ToString().c_str() : "nullptr",
+ PTR_TO_UINT(p_dev_rec), p_dev_rec->rs_disc_pending);
+ p_dev_rec->rs_disc_pending = BTM_SEC_RS_NOT_PENDING; /* reset flag */
+ }
+
+#endif
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_AllocateSCN
+ *
+ * Description Look through the Server Channel Numbers for a free one.
+ *
+ * Returns Allocated SCN number or 0 if none.
+ *
+ ******************************************************************************/
+
+uint8_t BTM_AllocateSCN(void) {
+ uint8_t x;
+ BTM_TRACE_DEBUG("BTM_AllocateSCN");
+
+ // stack reserves scn 1 for HFP, HSP we still do the correct way
+ for (x = 1; x < BTM_MAX_SCN; x++) {
+ if (!btm_cb.btm_scn[x]) {
+ btm_cb.btm_scn[x] = true;
+ return (x + 1);
+ }
+ }
+
+ return (0); /* No free ports */
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_TryAllocateSCN
+ *
+ * Description Try to allocate a fixed server channel
+ *
+ * Returns Returns true if server channel was available
+ *
+ ******************************************************************************/
+
+bool BTM_TryAllocateSCN(uint8_t scn) {
+ /* Make sure we don't exceed max port range.
+ * Stack reserves scn 1 for HFP, HSP we still do the correct way.
+ */
+ if ((scn >= BTM_MAX_SCN) || (scn == 1) || (scn == 0)) return false;
+
+ /* check if this port is available */
+ if (!btm_cb.btm_scn[scn - 1]) {
+ btm_cb.btm_scn[scn - 1] = true;
+ return true;
+ }
+
+ return (false); /* Port was busy */
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_FreeSCN
+ *
+ * Description Free the specified SCN.
+ *
+ * Returns true or false
+ *
+ ******************************************************************************/
+bool BTM_FreeSCN(uint8_t scn) {
+ BTM_TRACE_DEBUG("BTM_FreeSCN ");
+ if (scn <= BTM_MAX_SCN && scn > 0) {
+ btm_cb.btm_scn[scn - 1] = false;
+ return (true);
+ } else {
+ return (false); /* Illegal SCN passed in */
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_set_packet_types
+ *
+ * Description This function sets the packet types used for a specific
+ * ACL connection. It is called internally by btm_acl_created
+ * or by an application/profile by BTM_SetPacketTypes.
+ *
+ * Returns status of the operation
+ *
+ ******************************************************************************/
+tBTM_STATUS btm_set_packet_types(tACL_CONN* p, uint16_t pkt_types) {
+ uint16_t temp_pkt_types;
+ BTM_TRACE_DEBUG("btm_set_packet_types");
+ /* Save in the ACL control blocks, types that we support */
+ temp_pkt_types = (pkt_types & BTM_ACL_SUPPORTED_PKTS_MASK &
+ btm_cb.btm_acl_pkt_types_supported);
+
+ /* OR in any exception packet types if at least 2.0 version of spec */
+ temp_pkt_types |=
+ ((pkt_types & BTM_ACL_EXCEPTION_PKTS_MASK) |
+ (btm_cb.btm_acl_pkt_types_supported & BTM_ACL_EXCEPTION_PKTS_MASK));
+
+ /* Exclude packet types not supported by the peer */
+ btm_acl_chk_peer_pkt_type_support(p, &temp_pkt_types);
+
+ BTM_TRACE_DEBUG("SetPacketType Mask -> 0x%04x", temp_pkt_types);
+
+ btsnd_hcic_change_conn_type(p->hci_handle, temp_pkt_types);
+ p->pkt_types_mask = temp_pkt_types;
+
+ return (BTM_CMD_STARTED);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_get_max_packet_size
+ *
+ * Returns Returns maximum packet size that can be used for current
+ * connection, 0 if connection is not established
+ *
+ ******************************************************************************/
+uint16_t btm_get_max_packet_size(const RawAddress& addr) {
+ tACL_CONN* p = btm_bda_to_acl(addr, BT_TRANSPORT_BR_EDR);
+ uint16_t pkt_types = 0;
+ uint16_t pkt_size = 0;
+ BTM_TRACE_DEBUG("btm_get_max_packet_size");
+ if (p != NULL) {
+ pkt_types = p->pkt_types_mask;
+ } else {
+ /* Special case for when info for the local device is requested */
+ if (addr == *controller_get_interface()->get_address()) {
+ pkt_types = btm_cb.btm_acl_pkt_types_supported;
+ }
+ }
+
+ if (pkt_types) {
+ if (!(pkt_types & BTM_ACL_PKT_TYPES_MASK_NO_3_DH5))
+ pkt_size = HCI_EDR3_DH5_PACKET_SIZE;
+ else if (!(pkt_types & BTM_ACL_PKT_TYPES_MASK_NO_2_DH5))
+ pkt_size = HCI_EDR2_DH5_PACKET_SIZE;
+ else if (!(pkt_types & BTM_ACL_PKT_TYPES_MASK_NO_3_DH3))
+ pkt_size = HCI_EDR3_DH3_PACKET_SIZE;
+ else if (pkt_types & BTM_ACL_PKT_TYPES_MASK_DH5)
+ pkt_size = HCI_DH5_PACKET_SIZE;
+ else if (!(pkt_types & BTM_ACL_PKT_TYPES_MASK_NO_2_DH3))
+ pkt_size = HCI_EDR2_DH3_PACKET_SIZE;
+ else if (pkt_types & BTM_ACL_PKT_TYPES_MASK_DM5)
+ pkt_size = HCI_DM5_PACKET_SIZE;
+ else if (pkt_types & BTM_ACL_PKT_TYPES_MASK_DH3)
+ pkt_size = HCI_DH3_PACKET_SIZE;
+ else if (pkt_types & BTM_ACL_PKT_TYPES_MASK_DM3)
+ pkt_size = HCI_DM3_PACKET_SIZE;
+ else if (!(pkt_types & BTM_ACL_PKT_TYPES_MASK_NO_3_DH1))
+ pkt_size = HCI_EDR3_DH1_PACKET_SIZE;
+ else if (!(pkt_types & BTM_ACL_PKT_TYPES_MASK_NO_2_DH1))
+ pkt_size = HCI_EDR2_DH1_PACKET_SIZE;
+ else if (pkt_types & BTM_ACL_PKT_TYPES_MASK_DH1)
+ pkt_size = HCI_DH1_PACKET_SIZE;
+ else if (pkt_types & BTM_ACL_PKT_TYPES_MASK_DM1)
+ pkt_size = HCI_DM1_PACKET_SIZE;
+ }
+
+ return (pkt_size);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadRemoteVersion
+ *
+ * Returns If connected report peer device info
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_ReadRemoteVersion(const RawAddress& addr, uint8_t* lmp_version,
+ uint16_t* manufacturer,
+ uint16_t* lmp_sub_version) {
+ tACL_CONN* p = btm_bda_to_acl(addr, BT_TRANSPORT_BR_EDR);
+ BTM_TRACE_DEBUG("BTM_ReadRemoteVersion");
+ if (p == NULL) return (BTM_UNKNOWN_ADDR);
+
+ if (lmp_version) *lmp_version = p->lmp_version;
+
+ if (manufacturer) *manufacturer = p->manufacturer;
+
+ if (lmp_sub_version) *lmp_sub_version = p->lmp_subversion;
+
+ return (BTM_SUCCESS);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadRemoteFeatures
+ *
+ * Returns pointer to the remote supported features mask (8 bytes)
+ *
+ ******************************************************************************/
+uint8_t* BTM_ReadRemoteFeatures(const RawAddress& addr) {
+ tACL_CONN* p = btm_bda_to_acl(addr, BT_TRANSPORT_BR_EDR);
+ BTM_TRACE_DEBUG("BTM_ReadRemoteFeatures");
+ if (p == NULL) {
+ return (NULL);
+ }
+
+ return (p->peer_lmp_feature_pages[0]);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_RegBusyLevelNotif
+ *
+ * Description This function is called to register a callback to receive
+ * busy level change events.
+ *
+ * Returns BTM_SUCCESS if successfully registered, otherwise error
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_RegBusyLevelNotif(tBTM_BL_CHANGE_CB* p_cb, uint8_t* p_level,
+ tBTM_BL_EVENT_MASK evt_mask) {
+ BTM_TRACE_DEBUG("BTM_RegBusyLevelNotif");
+ if (p_level) *p_level = btm_cb.busy_level;
+
+ btm_cb.bl_evt_mask = evt_mask;
+
+ if (!p_cb)
+ btm_cb.p_bl_changed_cb = NULL;
+ else if (btm_cb.p_bl_changed_cb)
+ return (BTM_BUSY);
+ else
+ btm_cb.p_bl_changed_cb = p_cb;
+
+ return (BTM_SUCCESS);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_qos_setup_timeout
+ *
+ * Description Callback when QoS setup times out.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_qos_setup_timeout(UNUSED_ATTR void* data) {
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_qos_setup_cmpl_cb;
+ btm_cb.devcb.p_qos_setup_cmpl_cb = NULL;
+ if (p_cb) (*p_cb)((void*)NULL);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_qos_setup_complete
+ *
+ * Description This function is called when the command complete message
+ * is received from the HCI for the qos setup request.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_qos_setup_complete(uint8_t status, uint16_t handle,
+ FLOW_SPEC* p_flow) {
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_qos_setup_cmpl_cb;
+ tBTM_QOS_SETUP_CMPL qossu;
+
+ BTM_TRACE_DEBUG("%s", __func__);
+ alarm_cancel(btm_cb.devcb.qos_setup_timer);
+ btm_cb.devcb.p_qos_setup_cmpl_cb = NULL;
+
+ /* If there was a registered callback, call it */
+ if (p_cb) {
+ memset(&qossu, 0, sizeof(tBTM_QOS_SETUP_CMPL));
+ qossu.status = status;
+ qossu.handle = handle;
+ if (p_flow != NULL) {
+ qossu.flow.qos_flags = p_flow->qos_flags;
+ qossu.flow.service_type = p_flow->service_type;
+ qossu.flow.token_rate = p_flow->token_rate;
+ qossu.flow.peak_bandwidth = p_flow->peak_bandwidth;
+ qossu.flow.latency = p_flow->latency;
+ qossu.flow.delay_variation = p_flow->delay_variation;
+ }
+ BTM_TRACE_DEBUG("BTM: p_flow->delay_variation: 0x%02x",
+ qossu.flow.delay_variation);
+ (*p_cb)(&qossu);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadRSSI
+ *
+ * Description This function is called to read the link policy settings.
+ * The address of link policy results are returned in the
+ * callback.
+ * (tBTM_RSSI_RESULT)
+ *
+ * Returns BTM_CMD_STARTED if successfully initiated or error code
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_ReadRSSI(const RawAddress& remote_bda, tBTM_CMPL_CB* p_cb) {
+ tACL_CONN* p = NULL;
+ tBT_DEVICE_TYPE dev_type;
+ tBLE_ADDR_TYPE addr_type;
+
+ /* If someone already waiting on the version, do not allow another */
+ if (btm_cb.devcb.p_rssi_cmpl_cb) return (BTM_BUSY);
+
+ BTM_ReadDevInfo(remote_bda, &dev_type, &addr_type);
+
+ if (dev_type & BT_DEVICE_TYPE_BLE) {
+ p = btm_bda_to_acl(remote_bda, BT_TRANSPORT_LE);
+ }
+
+ if (p == NULL && dev_type & BT_DEVICE_TYPE_BREDR) {
+ p = btm_bda_to_acl(remote_bda, BT_TRANSPORT_BR_EDR);
+ }
+
+ if (p) {
+ btm_cb.devcb.p_rssi_cmpl_cb = p_cb;
+ alarm_set_on_mloop(btm_cb.devcb.read_rssi_timer, BTM_DEV_REPLY_TIMEOUT_MS,
+ btm_read_rssi_timeout, NULL);
+
+ btsnd_hcic_read_rssi(p->hci_handle);
+ return (BTM_CMD_STARTED);
+ }
+
+ /* If here, no BD Addr found */
+ return (BTM_UNKNOWN_ADDR);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadFailedContactCounter
+ *
+ * Description This function is called to read the failed contact counter.
+ * The result is returned in the callback.
+ * (tBTM_FAILED_CONTACT_COUNTER_RESULT)
+ *
+ * Returns BTM_CMD_STARTED if successfully initiated or error code
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_ReadFailedContactCounter(const RawAddress& remote_bda,
+ tBTM_CMPL_CB* p_cb) {
+ tACL_CONN* p;
+ tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
+ tBT_DEVICE_TYPE dev_type;
+ tBLE_ADDR_TYPE addr_type;
+
+ /* If someone already waiting on the result, do not allow another */
+ if (btm_cb.devcb.p_failed_contact_counter_cmpl_cb) return (BTM_BUSY);
+
+ BTM_ReadDevInfo(remote_bda, &dev_type, &addr_type);
+ if (dev_type == BT_DEVICE_TYPE_BLE) transport = BT_TRANSPORT_LE;
+
+ p = btm_bda_to_acl(remote_bda, transport);
+ if (p != (tACL_CONN*)NULL) {
+ btm_cb.devcb.p_failed_contact_counter_cmpl_cb = p_cb;
+ alarm_set_on_mloop(btm_cb.devcb.read_failed_contact_counter_timer,
+ BTM_DEV_REPLY_TIMEOUT_MS,
+ btm_read_failed_contact_counter_timeout, NULL);
+
+ btsnd_hcic_read_failed_contact_counter(p->hci_handle);
+ return (BTM_CMD_STARTED);
+ }
+
+ /* If here, no BD Addr found */
+ return (BTM_UNKNOWN_ADDR);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadAutomaticFlushTimeout
+ *
+ * Description This function is called to read the automatic flush timeout.
+ * The result is returned in the callback.
+ * (tBTM_AUTOMATIC_FLUSH_TIMEOUT_RESULT)
+ *
+ * Returns BTM_CMD_STARTED if successfully initiated or error code
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_ReadAutomaticFlushTimeout(const RawAddress& remote_bda,
+ tBTM_CMPL_CB* p_cb) {
+ tACL_CONN* p;
+ tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
+ tBT_DEVICE_TYPE dev_type;
+ tBLE_ADDR_TYPE addr_type;
+
+ /* If someone already waiting on the result, do not allow another */
+ if (btm_cb.devcb.p_automatic_flush_timeout_cmpl_cb) return (BTM_BUSY);
+
+ BTM_ReadDevInfo(remote_bda, &dev_type, &addr_type);
+ if (dev_type == BT_DEVICE_TYPE_BLE) transport = BT_TRANSPORT_LE;
+
+ p = btm_bda_to_acl(remote_bda, transport);
+ if (!p) return BTM_UNKNOWN_ADDR;
+
+ btm_cb.devcb.p_automatic_flush_timeout_cmpl_cb = p_cb;
+ alarm_set_on_mloop(btm_cb.devcb.read_automatic_flush_timeout_timer,
+ BTM_DEV_REPLY_TIMEOUT_MS,
+ btm_read_automatic_flush_timeout_timeout, nullptr);
+
+ btsnd_hcic_read_automatic_flush_timeout(p->hci_handle);
+ return BTM_CMD_STARTED;
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadTxPower
+ *
+ * Description This function is called to read the current
+ * TX power of the connection. The tx power level results
+ * are returned in the callback.
+ * (tBTM_RSSI_RESULT)
+ *
+ * Returns BTM_CMD_STARTED if successfully initiated or error code
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_ReadTxPower(const RawAddress& remote_bda,
+ tBT_TRANSPORT transport, tBTM_CMPL_CB* p_cb) {
+ tACL_CONN* p;
+#define BTM_READ_RSSI_TYPE_CUR 0x00
+#define BTM_READ_RSSI_TYPE_MAX 0X01
+
+ VLOG(2) << __func__ << ": RemBdAddr: " << remote_bda;
+
+ /* If someone already waiting on the version, do not allow another */
+ if (btm_cb.devcb.p_tx_power_cmpl_cb) return (BTM_BUSY);
+
+ p = btm_bda_to_acl(remote_bda, transport);
+ if (p != (tACL_CONN*)NULL) {
+ btm_cb.devcb.p_tx_power_cmpl_cb = p_cb;
+ alarm_set_on_mloop(btm_cb.devcb.read_tx_power_timer,
+ BTM_DEV_REPLY_TIMEOUT_MS, btm_read_tx_power_timeout,
+ NULL);
+
+ if (p->transport == BT_TRANSPORT_LE) {
+ btm_cb.devcb.read_tx_pwr_addr = remote_bda;
+ btsnd_hcic_ble_read_adv_chnl_tx_power();
+ } else {
+ btsnd_hcic_read_tx_power(p->hci_handle, BTM_READ_RSSI_TYPE_CUR);
+ }
+
+ return (BTM_CMD_STARTED);
+ }
+
+ /* If here, no BD Addr found */
+ return (BTM_UNKNOWN_ADDR);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_tx_power_timeout
+ *
+ * Description Callback when reading the tx power times out.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_tx_power_timeout(UNUSED_ATTR void* data) {
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_tx_power_cmpl_cb;
+ btm_cb.devcb.p_tx_power_cmpl_cb = NULL;
+ if (p_cb) (*p_cb)((void*)NULL);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_tx_power_complete
+ *
+ * Description This function is called when the command complete message
+ * is received from the HCI for the read tx power request.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_tx_power_complete(uint8_t* p, bool is_ble) {
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_tx_power_cmpl_cb;
+ tBTM_TX_POWER_RESULT result;
+ tACL_CONN* p_acl_cb = &btm_cb.acl_db[0];
+
+ BTM_TRACE_DEBUG("%s", __func__);
+ alarm_cancel(btm_cb.devcb.read_tx_power_timer);
+ btm_cb.devcb.p_tx_power_cmpl_cb = NULL;
+
+ /* If there was a registered callback, call it */
+ if (p_cb) {
+ STREAM_TO_UINT8(result.hci_status, p);
+
+ if (result.hci_status == HCI_SUCCESS) {
+ result.status = BTM_SUCCESS;
+
+ if (!is_ble) {
+ uint16_t handle;
+ STREAM_TO_UINT16(handle, p);
+ STREAM_TO_UINT8(result.tx_power, p);
+
+ /* Search through the list of active channels for the correct BD Addr */
+ for (uint16_t index = 0; index < MAX_L2CAP_LINKS; index++, p_acl_cb++) {
+ if ((p_acl_cb->in_use) && (handle == p_acl_cb->hci_handle)) {
+ result.rem_bda = p_acl_cb->remote_addr;
+ break;
+ }
+ }
+ } else {
+ STREAM_TO_UINT8(result.tx_power, p);
+ result.rem_bda = btm_cb.devcb.read_tx_pwr_addr;
+ }
+ BTM_TRACE_DEBUG("BTM TX power Complete: tx_power %d, hci status 0x%02x",
+ result.tx_power, result.hci_status);
+ } else {
+ result.status = BTM_ERR_PROCESSING;
+ }
+
+ (*p_cb)(&result);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_rssi_timeout
+ *
+ * Description Callback when reading the RSSI times out.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_rssi_timeout(UNUSED_ATTR void* data) {
+ tBTM_RSSI_RESULT result;
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_rssi_cmpl_cb;
+ btm_cb.devcb.p_rssi_cmpl_cb = NULL;
+ result.status = BTM_DEVICE_TIMEOUT;
+ if (p_cb) (*p_cb)(&result);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_rssi_complete
+ *
+ * Description This function is called when the command complete message
+ * is received from the HCI for the read rssi request.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_rssi_complete(uint8_t* p) {
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_rssi_cmpl_cb;
+ tBTM_RSSI_RESULT result;
+ tACL_CONN* p_acl_cb = &btm_cb.acl_db[0];
+
+ BTM_TRACE_DEBUG("%s", __func__);
+ alarm_cancel(btm_cb.devcb.read_rssi_timer);
+ btm_cb.devcb.p_rssi_cmpl_cb = NULL;
+
+ /* If there was a registered callback, call it */
+ if (p_cb) {
+ STREAM_TO_UINT8(result.hci_status, p);
+
+ if (result.hci_status == HCI_SUCCESS) {
+ uint16_t handle;
+ result.status = BTM_SUCCESS;
+
+ STREAM_TO_UINT16(handle, p);
+
+ STREAM_TO_UINT8(result.rssi, p);
+ BTM_TRACE_DEBUG("BTM RSSI Complete: rssi %d, hci status 0x%02x",
+ result.rssi, result.hci_status);
+
+ /* Search through the list of active channels for the correct BD Addr */
+ for (uint16_t index = 0; index < MAX_L2CAP_LINKS; index++, p_acl_cb++) {
+ if ((p_acl_cb->in_use) && (handle == p_acl_cb->hci_handle)) {
+ result.rem_bda = p_acl_cb->remote_addr;
+ break;
+ }
+ }
+ } else {
+ result.status = BTM_ERR_PROCESSING;
+ }
+
+ (*p_cb)(&result);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_failed_contact_counter_timeout
+ *
+ * Description Callback when reading the failed contact counter times out.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_failed_contact_counter_timeout(UNUSED_ATTR void* data) {
+ tBTM_FAILED_CONTACT_COUNTER_RESULT result;
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_failed_contact_counter_cmpl_cb;
+ btm_cb.devcb.p_failed_contact_counter_cmpl_cb = NULL;
+ result.status = BTM_DEVICE_TIMEOUT;
+ if (p_cb) (*p_cb)(&result);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_failed_contact_counter_complete
+ *
+ * Description This function is called when the command complete message
+ * is received from the HCI for the read failed contact
+ * counter request.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_failed_contact_counter_complete(uint8_t* p) {
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_failed_contact_counter_cmpl_cb;
+ tBTM_FAILED_CONTACT_COUNTER_RESULT result;
+ tACL_CONN* p_acl_cb = &btm_cb.acl_db[0];
+
+ BTM_TRACE_DEBUG("%s", __func__);
+ alarm_cancel(btm_cb.devcb.read_failed_contact_counter_timer);
+ btm_cb.devcb.p_failed_contact_counter_cmpl_cb = NULL;
+
+ /* If there was a registered callback, call it */
+ if (p_cb) {
+ uint16_t handle;
+ STREAM_TO_UINT8(result.hci_status, p);
+
+ if (result.hci_status == HCI_SUCCESS) {
+ result.status = BTM_SUCCESS;
+
+ STREAM_TO_UINT16(handle, p);
+
+ STREAM_TO_UINT16(result.failed_contact_counter, p);
+ BTM_TRACE_DEBUG(
+ "BTM Failed Contact Counter Complete: counter %u, hci status 0x%02x",
+ result.failed_contact_counter, result.hci_status);
+
+ /* Search through the list of active channels for the correct BD Addr */
+ for (uint16_t index = 0; index < MAX_L2CAP_LINKS; index++, p_acl_cb++) {
+ if ((p_acl_cb->in_use) && (handle == p_acl_cb->hci_handle)) {
+ result.rem_bda = p_acl_cb->remote_addr;
+ break;
+ }
+ }
+ } else {
+ result.status = BTM_ERR_PROCESSING;
+ }
+
+ (*p_cb)(&result);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_automatic_flush_timeout_timeout
+ *
+ * Description Callback when reading the automatic flush timeout times out.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_automatic_flush_timeout_timeout(UNUSED_ATTR void* data) {
+ tBTM_AUTOMATIC_FLUSH_TIMEOUT_RESULT result;
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_automatic_flush_timeout_cmpl_cb;
+ btm_cb.devcb.p_automatic_flush_timeout_cmpl_cb = nullptr;
+ result.status = BTM_DEVICE_TIMEOUT;
+ if (p_cb) (*p_cb)(&result);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_automatic_flush_timeout_complete
+ *
+ * Description This function is called when the command complete message
+ * is received from the HCI for the read automatic flush
+ * timeout request.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_automatic_flush_timeout_complete(uint8_t* p) {
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_automatic_flush_timeout_cmpl_cb;
+ tBTM_AUTOMATIC_FLUSH_TIMEOUT_RESULT result;
+ tACL_CONN* p_acl_cb = &btm_cb.acl_db[0];
+
+ BTM_TRACE_DEBUG("%s", __func__);
+ alarm_cancel(btm_cb.devcb.read_automatic_flush_timeout_timer);
+ btm_cb.devcb.p_automatic_flush_timeout_cmpl_cb = nullptr;
+
+ /* If there was a registered callback, call it */
+ if (p_cb) {
+ uint16_t handle;
+ STREAM_TO_UINT8(result.hci_status, p);
+
+ if (result.hci_status == HCI_SUCCESS) {
+ result.status = BTM_SUCCESS;
+
+ STREAM_TO_UINT16(handle, p);
+
+ STREAM_TO_UINT16(result.automatic_flush_timeout, p);
+ BTM_TRACE_DEBUG(
+ "BTM Automatic Flush Timeout Complete: timeout %u, hci status 0x%02x",
+ result.automatic_flush_timeout, result.hci_status);
+
+ /* Search through the list of active channels for the correct BD Addr */
+ for (uint16_t index = 0; index < MAX_L2CAP_LINKS; index++, p_acl_cb++) {
+ if ((p_acl_cb->in_use) && (handle == p_acl_cb->hci_handle)) {
+ result.rem_bda = p_acl_cb->remote_addr;
+ break;
+ }
+ }
+ } else {
+ result.status = BTM_ERR_PROCESSING;
+ }
+
+ (*p_cb)(&result);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_link_quality_timeout
+ *
+ * Description Callback when reading the link quality times out.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_link_quality_timeout(UNUSED_ATTR void* data) {
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_link_qual_cmpl_cb;
+ btm_cb.devcb.p_link_qual_cmpl_cb = NULL;
+ if (p_cb) (*p_cb)((void*)NULL);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_link_quality_complete
+ *
+ * Description This function is called when the command complete message
+ * is received from the HCI for the read link quality.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_link_quality_complete(uint8_t* p) {
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_link_qual_cmpl_cb;
+ tBTM_LINK_QUALITY_RESULT result;
+ tACL_CONN* p_acl_cb = &btm_cb.acl_db[0];
+
+ BTM_TRACE_DEBUG("%s", __func__);
+ alarm_cancel(btm_cb.devcb.read_link_quality_timer);
+ btm_cb.devcb.p_link_qual_cmpl_cb = NULL;
+
+ /* If there was a registered callback, call it */
+ if (p_cb) {
+ STREAM_TO_UINT8(result.hci_status, p);
+
+ if (result.hci_status == HCI_SUCCESS) {
+ uint16_t handle;
+ result.status = BTM_SUCCESS;
+
+ STREAM_TO_UINT16(handle, p);
+
+ STREAM_TO_UINT8(result.link_quality, p);
+ BTM_TRACE_DEBUG(
+ "BTM Link Quality Complete: Link Quality %d, hci status 0x%02x",
+ result.link_quality, result.hci_status);
+
+ /* Search through the list of active channels for the correct BD Addr */
+ for (uint16_t index = 0; index < MAX_L2CAP_LINKS; index++, p_acl_cb++) {
+ if ((p_acl_cb->in_use) && (handle == p_acl_cb->hci_handle)) {
+ result.rem_bda = p_acl_cb->remote_addr;
+ break;
+ }
+ }
+ } else {
+ result.status = BTM_ERR_PROCESSING;
+ }
+
+ (*p_cb)(&result);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_remove_acl
+ *
+ * Description This function is called to disconnect an ACL connection
+ *
+ * Returns BTM_SUCCESS if successfully initiated, otherwise
+ * BTM_NO_RESOURCES.
+ *
+ ******************************************************************************/
+tBTM_STATUS btm_remove_acl(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
+ uint16_t hci_handle = BTM_GetHCIConnHandle(bd_addr, transport);
+ tBTM_STATUS status = BTM_SUCCESS;
+
+ BTM_TRACE_DEBUG("btm_remove_acl");
+#if (BTM_DISC_DURING_RS == TRUE)
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
+
+ /* Role Switch is pending, postpone until completed */
+ if (p_dev_rec && (p_dev_rec->rs_disc_pending == BTM_SEC_RS_PENDING)) {
+ p_dev_rec->rs_disc_pending = BTM_SEC_DISC_PENDING;
+ } else /* otherwise can disconnect right away */
+#endif
+ {
+ if (hci_handle != 0xFFFF && p_dev_rec &&
+ p_dev_rec->sec_state != BTM_SEC_STATE_DISCONNECTING) {
+ btsnd_hcic_disconnect(hci_handle, HCI_ERR_PEER_USER);
+ } else {
+ status = BTM_UNKNOWN_ADDR;
+ }
+ }
+
+ return status;
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_SetTraceLevel
+ *
+ * Description This function sets the trace level for BTM. If called with
+ * a value of 0xFF, it simply returns the current trace level.
+ *
+ * Returns The new or current trace level
+ *
+ ******************************************************************************/
+uint8_t BTM_SetTraceLevel(uint8_t new_level) {
+ BTM_TRACE_DEBUG("BTM_SetTraceLevel");
+ if (new_level != 0xFF) btm_cb.trace_level = new_level;
+
+ return (btm_cb.trace_level);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_cont_rswitch
+ *
+ * Description This function is called to continue processing an active
+ * role switch. It first disables encryption if enabled and
+ * EPR is not supported
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_cont_rswitch(tACL_CONN* p, tBTM_SEC_DEV_REC* p_dev_rec,
+ uint8_t hci_status) {
+ BTM_TRACE_DEBUG("btm_cont_rswitch");
+ /* Check to see if encryption needs to be turned off if pending
+ change of link key or role switch */
+ if (p->switch_role_state == BTM_ACL_SWKEY_STATE_MODE_CHANGE) {
+ /* Must turn off Encryption first if necessary */
+ /* Some devices do not support switch or change of link key while encryption
+ * is on */
+ if (p_dev_rec != NULL &&
+ ((p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED) != 0) &&
+ !BTM_EPR_AVAILABLE(p)) {
+ btsnd_hcic_set_conn_encrypt(p->hci_handle, false);
+ p->encrypt_state = BTM_ACL_ENCRYPT_STATE_ENCRYPT_OFF;
+ if (p->switch_role_state == BTM_ACL_SWKEY_STATE_MODE_CHANGE)
+ p->switch_role_state = BTM_ACL_SWKEY_STATE_ENCRYPTION_OFF;
+ } else /* Encryption not used or EPR supported, continue with switch
+ and/or change of link key */
+ {
+ if (p->switch_role_state == BTM_ACL_SWKEY_STATE_MODE_CHANGE) {
+ p->switch_role_state = BTM_ACL_SWKEY_STATE_IN_PROGRESS;
+#if (BTM_DISC_DURING_RS == TRUE)
+ if (p_dev_rec) p_dev_rec->rs_disc_pending = BTM_SEC_RS_PENDING;
+#endif
+ btsnd_hcic_switch_role(p->remote_addr, (uint8_t)!p->link_role);
+ }
+ }
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_acl_resubmit_page
+ *
+ * Description send pending page request
+ *
+ ******************************************************************************/
+void btm_acl_resubmit_page(void) {
+ tBTM_SEC_DEV_REC* p_dev_rec;
+ BT_HDR* p_buf;
+ uint8_t* pp;
+ BTM_TRACE_DEBUG("btm_acl_resubmit_page");
+ /* If there were other page request schedule can start the next one */
+ p_buf = (BT_HDR*)fixed_queue_try_dequeue(btm_cb.page_queue);
+ if (p_buf != NULL) {
+ /* skip 3 (2 bytes opcode and 1 byte len) to get to the bd_addr
+ * for both create_conn and rmt_name */
+ pp = (uint8_t*)(p_buf + 1) + p_buf->offset + 3;
+
+ RawAddress bda;
+ STREAM_TO_BDADDR(bda, pp);
+
+ p_dev_rec = btm_find_or_alloc_dev(bda);
+
+ btm_cb.connecting_bda = p_dev_rec->bd_addr;
+ memcpy(btm_cb.connecting_dc, p_dev_rec->dev_class, DEV_CLASS_LEN);
+
+ btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p_buf);
+ } else {
+ btm_cb.paging = false;
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_acl_reset_paging
+ *
+ * Description set paging to false and free the page queue - called at
+ * hci_reset
+ *
+ ******************************************************************************/
+void btm_acl_reset_paging(void) {
+ BT_HDR* p;
+ BTM_TRACE_DEBUG("btm_acl_reset_paging");
+ /* If we sent reset we are definitely not paging any more */
+ while ((p = (BT_HDR*)fixed_queue_try_dequeue(btm_cb.page_queue)) != NULL)
+ osi_free(p);
+
+ btm_cb.paging = false;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_acl_paging
+ *
+ * Description send a paging command or queue it in btm_cb
+ *
+ ******************************************************************************/
+void btm_acl_paging(BT_HDR* p, const RawAddress& bda) {
+ tBTM_SEC_DEV_REC* p_dev_rec;
+
+ VLOG(2) << __func__ << ":" << btm_cb.discing << " , paging:" << btm_cb.paging
+ << " BDA: " << bda;
+
+ if (btm_cb.discing) {
+ btm_cb.paging = true;
+ fixed_queue_enqueue(btm_cb.page_queue, p);
+ } else {
+ if (!BTM_ACL_IS_CONNECTED(bda)) {
+ VLOG(1) << "connecting_bda: " << btm_cb.connecting_bda;
+ if (btm_cb.paging && bda == btm_cb.connecting_bda) {
+ fixed_queue_enqueue(btm_cb.page_queue, p);
+ } else {
+ p_dev_rec = btm_find_or_alloc_dev(bda);
+ btm_cb.connecting_bda = p_dev_rec->bd_addr;
+ memcpy(btm_cb.connecting_dc, p_dev_rec->dev_class, DEV_CLASS_LEN);
+
+ btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
+ }
+
+ btm_cb.paging = true;
+ } else /* ACL is already up */
+ {
+ btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
+ }
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_acl_notif_conn_collision
+ *
+ * Description Send connection collision event to upper layer if registered
+ *
+ * Returns true if sent out to upper layer,
+ * false if no one needs the notification.
+ *
+ ******************************************************************************/
+bool btm_acl_notif_conn_collision(const RawAddress& bda) {
+ /* Report possible collision to the upper layer. */
+ if (btm_cb.p_bl_changed_cb) {
+ VLOG(1) << __func__ << " RemBdAddr: " << bda;
+
+ tBTM_BL_EVENT_DATA evt_data;
+ evt_data.event = BTM_BL_COLLISION_EVT;
+ evt_data.conn.p_bda = &bda;
+ evt_data.conn.transport = BT_TRANSPORT_BR_EDR;
+ evt_data.conn.handle = BTM_INVALID_HCI_HANDLE;
+ (*btm_cb.p_bl_changed_cb)(&evt_data);
+ return true;
+ } else {
+ return false;
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_acl_chk_peer_pkt_type_support
+ *
+ * Description Check if peer supports requested packets
+ *
+ ******************************************************************************/
+void btm_acl_chk_peer_pkt_type_support(tACL_CONN* p, uint16_t* p_pkt_type) {
+ /* 3 and 5 slot packets? */
+ if (!HCI_3_SLOT_PACKETS_SUPPORTED(p->peer_lmp_feature_pages[0]))
+ *p_pkt_type &= ~(BTM_ACL_PKT_TYPES_MASK_DH3 + BTM_ACL_PKT_TYPES_MASK_DM3);
+
+ if (!HCI_5_SLOT_PACKETS_SUPPORTED(p->peer_lmp_feature_pages[0]))
+ *p_pkt_type &= ~(BTM_ACL_PKT_TYPES_MASK_DH5 + BTM_ACL_PKT_TYPES_MASK_DM5);
+
+ /* 2 and 3 MPS support? */
+ if (!HCI_EDR_ACL_2MPS_SUPPORTED(p->peer_lmp_feature_pages[0]))
+ /* Not supported. Add 'not_supported' mask for all 2MPS packet types */
+ *p_pkt_type |=
+ (BTM_ACL_PKT_TYPES_MASK_NO_2_DH1 + BTM_ACL_PKT_TYPES_MASK_NO_2_DH3 +
+ BTM_ACL_PKT_TYPES_MASK_NO_2_DH5);
+
+ if (!HCI_EDR_ACL_3MPS_SUPPORTED(p->peer_lmp_feature_pages[0]))
+ /* Not supported. Add 'not_supported' mask for all 3MPS packet types */
+ *p_pkt_type |=
+ (BTM_ACL_PKT_TYPES_MASK_NO_3_DH1 + BTM_ACL_PKT_TYPES_MASK_NO_3_DH3 +
+ BTM_ACL_PKT_TYPES_MASK_NO_3_DH5);
+
+ /* EDR 3 and 5 slot support? */
+ if (HCI_EDR_ACL_2MPS_SUPPORTED(p->peer_lmp_feature_pages[0]) ||
+ HCI_EDR_ACL_3MPS_SUPPORTED(p->peer_lmp_feature_pages[0])) {
+ if (!HCI_3_SLOT_EDR_ACL_SUPPORTED(p->peer_lmp_feature_pages[0]))
+ /* Not supported. Add 'not_supported' mask for all 3-slot EDR packet types
+ */
+ *p_pkt_type |=
+ (BTM_ACL_PKT_TYPES_MASK_NO_2_DH3 + BTM_ACL_PKT_TYPES_MASK_NO_3_DH3);
+
+ if (!HCI_5_SLOT_EDR_ACL_SUPPORTED(p->peer_lmp_feature_pages[0]))
+ /* Not supported. Add 'not_supported' mask for all 5-slot EDR packet types
+ */
+ *p_pkt_type |=
+ (BTM_ACL_PKT_TYPES_MASK_NO_2_DH5 + BTM_ACL_PKT_TYPES_MASK_NO_3_DH5);
+ }
+}
diff --git a/stack/btm/btm_ble.cc b/stack/btm/btm_ble.cc
index ae7b9ba59..06a597a77 100644
--- a/stack/btm/btm_ble.cc
+++ b/stack/btm/btm_ble.cc
@@ -25,40 +25,55 @@
#define LOG_TAG "bt_btm_ble"
-#include <cstdint>
+#include "bt_target.h"
+#include <base/bind.h>
+#include <string.h>
+
+#include "bt_types.h"
+#include "bt_utils.h"
+#include "btm_ble_api.h"
+#include "btm_int.h"
+#include "btu.h"
#include "device/include/controller.h"
+#include "gap_api.h"
+#include "gatt_api.h"
+#include "hcimsgs.h"
+#include "l2c_int.h"
+#include "log/log.h"
#include "main/shim/btm_api.h"
-#include "main/shim/l2c_api.h"
#include "main/shim/shim.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/btm/security_device_record.h"
+#include "osi/include/log.h"
+#include "osi/include/osi.h"
#include "stack/crypto_toolbox/crypto_toolbox.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btu.h"
-#include "stack/include/gatt_api.h"
-#include "stack/include/l2cap_security_interface.h"
-#include "stack/include/l2cdefs.h"
-#include "stack/include/smp_api.h"
-#include "types/raw_address.h"
-
-extern tBTM_CB btm_cb;
-
-extern bool btm_ble_init_pseudo_addr(tBTM_SEC_DEV_REC* p_dev_rec,
- const RawAddress& new_pseudo_addr);
-extern void gatt_notify_phy_updated(tGATT_STATUS status, uint16_t handle,
+
+extern void gatt_notify_phy_updated(uint8_t status, uint16_t handle,
uint8_t tx_phy, uint8_t rx_phy);
/******************************************************************************/
/* External Function to be called by other modules */
/******************************************************************************/
-void BTM_SecAddBleDevice(const RawAddress& bd_addr, tBT_DEVICE_TYPE dev_type,
- tBLE_ADDR_TYPE addr_type) {
+/********************************************************
+ *
+ * Function BTM_SecAddBleDevice
+ *
+ * Description Add/modify device. This function will be normally called
+ * during host startup to restore all required information
+ * for a LE device stored in the NVRAM.
+ *
+ * Parameters: bd_addr - BD address of the peer
+ * bd_name - Name of the peer device. NULL if unknown.
+ * dev_type - Remote device's device type.
+ * addr_type - LE device address type.
+ *
+ * Returns true if added OK, else false
+ *
+ ******************************************************************************/
+bool BTM_SecAddBleDevice(const RawAddress& bd_addr, BD_NAME bd_name,
+ tBT_DEVICE_TYPE dev_type, tBLE_ADDR_TYPE addr_type) {
if (bluetooth::shim::is_gd_shim_enabled()) {
- return bluetooth::shim::BTM_SecAddBleDevice(bd_addr, dev_type, addr_type);
+ return bluetooth::shim::BTM_SecAddBleDevice(bd_addr, bd_name, dev_type,
+ addr_type);
}
BTM_TRACE_DEBUG("%s: dev_type=0x%x", __func__, dev_type);
@@ -75,7 +90,7 @@ void BTM_SecAddBleDevice(const RawAddress& bd_addr, tBT_DEVICE_TYPE dev_type,
p_dev_rec->conn_params.min_conn_int = BTM_BLE_CONN_PARAM_UNDEF;
p_dev_rec->conn_params.max_conn_int = BTM_BLE_CONN_PARAM_UNDEF;
p_dev_rec->conn_params.supervision_tout = BTM_BLE_CONN_PARAM_UNDEF;
- p_dev_rec->conn_params.peripheral_latency = BTM_BLE_CONN_PARAM_UNDEF;
+ p_dev_rec->conn_params.slave_latency = BTM_BLE_CONN_PARAM_UNDEF;
BTM_TRACE_DEBUG("%s: Device added, handle=0x%x, p_dev_rec=%p, bd_addr=%s",
__func__, p_dev_rec->ble_hci_handle, p_dev_rec,
@@ -84,6 +99,11 @@ void BTM_SecAddBleDevice(const RawAddress& bd_addr, tBT_DEVICE_TYPE dev_type,
memset(p_dev_rec->sec_bd_name, 0, sizeof(tBTM_BD_NAME));
+ if (bd_name && bd_name[0]) {
+ p_dev_rec->sec_flags |= BTM_SEC_NAME_KNOWN;
+ strlcpy((char*)p_dev_rec->sec_bd_name, (char*)bd_name,
+ BTM_MAX_REM_BD_NAME_LEN);
+ }
p_dev_rec->device_type |= dev_type;
p_dev_rec->ble.ble_addr_type = addr_type;
@@ -96,6 +116,8 @@ void BTM_SecAddBleDevice(const RawAddress& bd_addr, tBT_DEVICE_TYPE dev_type,
BTM_TRACE_DEBUG("InqDb device_type =0x%x addr_type=0x%x",
p_info->results.device_type, p_info->results.ble_addr_type);
}
+
+ return true;
}
/*******************************************************************************
@@ -113,7 +135,7 @@ void BTM_SecAddBleDevice(const RawAddress& bd_addr, tBT_DEVICE_TYPE dev_type,
* Returns true if added OK, else false
*
******************************************************************************/
-void BTM_SecAddBleKey(const RawAddress& bd_addr, tBTM_LE_KEY_VALUE* p_le_key,
+bool BTM_SecAddBleKey(const RawAddress& bd_addr, tBTM_LE_KEY_VALUE* p_le_key,
tBTM_LE_KEY_TYPE key_type) {
if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::BTM_SecAddBleKey(bd_addr, p_le_key, key_type);
@@ -129,16 +151,19 @@ void BTM_SecAddBleKey(const RawAddress& bd_addr, tBTM_LE_KEY_VALUE* p_le_key,
LOG(WARNING) << __func__
<< " Wrong Type, or No Device record for bdaddr: " << bd_addr
<< ", Type: " << key_type;
- return;
+ return (false);
}
VLOG(1) << __func__ << " BDA: " << bd_addr << ", Type: " << key_type;
btm_sec_save_le_key(bd_addr, key_type, p_le_key, false);
- if (key_type == BTM_LE_KEY_PID || key_type == BTM_LE_KEY_LID) {
+#if (BLE_PRIVACY_SPT == TRUE)
+ if (key_type == BTM_LE_KEY_PID || key_type == BTM_LE_KEY_LID)
btm_ble_resolving_list_load_dev(p_dev_rec);
- }
+#endif
+
+ return (true);
}
/*******************************************************************************
@@ -204,9 +229,109 @@ const Octet16& BTM_GetDeviceDHK() {
return btm_cb.devcb.id_keys.dhk;
}
+/*******************************************************************************
+ *
+ * Function BTM_ReadConnectionAddr
+ *
+ * Description This function is called to get the local device address
+ * information.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_ReadConnectionAddr(const RawAddress& remote_bda,
+ RawAddress& local_conn_addr,
+ tBLE_ADDR_TYPE* p_addr_type) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_ReadConnectionAddr(remote_bda, local_conn_addr,
+ p_addr_type);
+ }
+ tACL_CONN* p_acl = btm_bda_to_acl(remote_bda, BT_TRANSPORT_LE);
+
+ if (p_acl == NULL) {
+ BTM_TRACE_ERROR("No connection exist!");
+ return;
+ }
+ local_conn_addr = p_acl->conn_addr;
+ *p_addr_type = p_acl->conn_addr_type;
+
+ BTM_TRACE_DEBUG("BTM_ReadConnectionAddr address type: %d addr: 0x%02x",
+ p_acl->conn_addr_type, p_acl->conn_addr.address[0]);
+}
/*******************************************************************************
*
+ * Function BTM_IsBleConnection
+ *
+ * Description This function is called to check if the connection handle
+ * for an LE link
+ *
+ * Returns true if connection is LE link, otherwise false.
+ *
+ ******************************************************************************/
+bool BTM_IsBleConnection(uint16_t conn_handle) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_IsBleConnection(conn_handle);
+ }
+ uint8_t xx;
+ tACL_CONN* p;
+
+ BTM_TRACE_API("BTM_IsBleConnection: conn_handle: %d", conn_handle);
+
+ xx = btm_handle_to_acl_index(conn_handle);
+ if (xx >= MAX_L2CAP_LINKS) return false;
+
+ p = &btm_cb.acl_db[xx];
+
+ return (p->transport == BT_TRANSPORT_LE);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadRemoteConnectionAddr
+ *
+ * Description This function is read the remote device address currently used
+ *
+ * Parameters pseudo_addr: pseudo random address available
+ * conn_addr:connection address used
+ * p_addr_type : BD Address type, Public or Random of the address
+ * used
+ *
+ * Returns bool, true if connection to remote device exists, else false
+ *
+ ******************************************************************************/
+bool BTM_ReadRemoteConnectionAddr(const RawAddress& pseudo_addr,
+ RawAddress& conn_addr,
+ tBLE_ADDR_TYPE* p_addr_type) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_ReadRemoteConnectionAddr(pseudo_addr, conn_addr,
+ p_addr_type);
+ }
+ bool st = true;
+#if (BLE_PRIVACY_SPT == TRUE)
+ tACL_CONN* p = btm_bda_to_acl(pseudo_addr, BT_TRANSPORT_LE);
+
+ if (p == NULL) {
+ BTM_TRACE_ERROR(
+ "BTM_ReadRemoteConnectionAddr can not find connection"
+ " with matching address");
+ return false;
+ }
+
+ conn_addr = p->active_remote_addr;
+ *p_addr_type = p->active_remote_addr_type;
+#else
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(pseudo_addr);
+
+ conn_addr = pseudo_addr;
+ if (p_dev_rec != NULL) {
+ *p_addr_type = p_dev_rec->ble.ble_addr_type;
+ }
+#endif
+ return st;
+}
+/*******************************************************************************
+ *
* Function BTM_SecurityGrant
*
* Description This function is called to grant security process.
@@ -241,12 +366,14 @@ void BTM_SecurityGrant(const RawAddress& bd_addr, uint8_t res) {
* res - result of the operation BTM_SUCCESS if success
* key_len - length in bytes of the Passkey
* p_passkey - pointer to array with the passkey
+ * trusted_mask - bitwise OR of trusted services (array of
+ * uint32_t)
*
******************************************************************************/
void BTM_BlePasskeyReply(const RawAddress& bd_addr, uint8_t res,
uint32_t passkey) {
if (bluetooth::shim::is_gd_shim_enabled()) {
- ASSERT_LOG(false, "This should not be invoked from code path");
+ return bluetooth::shim::BTM_BlePasskeyReply(bd_addr, res, passkey);
}
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
tSMP_STATUS res_smp =
@@ -276,7 +403,7 @@ void BTM_BlePasskeyReply(const RawAddress& bd_addr, uint8_t res,
******************************************************************************/
void BTM_BleConfirmReply(const RawAddress& bd_addr, uint8_t res) {
if (bluetooth::shim::is_gd_shim_enabled()) {
- ASSERT_LOG(false, "This should not be invoked from code path");
+ return bluetooth::shim::BTM_BleConfirmReply(bd_addr, res);
}
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
tSMP_STATUS res_smp =
@@ -368,6 +495,48 @@ void BTM_BleSecureConnectionOobDataReply(const RawAddress& bd_addr,
SMP_SecureConnectionOobDataReply((uint8_t*)&oob);
}
+/******************************************************************************
+ *
+ * Function BTM_BleSetConnScanParams
+ *
+ * Description Set scan parameter used in BLE connection request
+ *
+ * Parameters: scan_interval: scan interval
+ * scan_window: scan window
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_BleSetConnScanParams(uint32_t scan_interval, uint32_t scan_window) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_BleSetConnScanParams(scan_interval,
+ scan_window);
+ }
+ tBTM_BLE_CB* p_ble_cb = &btm_cb.ble_ctr_cb;
+ bool new_param = false;
+
+ if (BTM_BLE_ISVALID_PARAM(scan_interval, BTM_BLE_SCAN_INT_MIN,
+ BTM_BLE_SCAN_INT_MAX) &&
+ BTM_BLE_ISVALID_PARAM(scan_window, BTM_BLE_SCAN_WIN_MIN,
+ BTM_BLE_SCAN_WIN_MAX)) {
+ if (p_ble_cb->scan_int != scan_interval) {
+ p_ble_cb->scan_int = scan_interval;
+ new_param = true;
+ }
+
+ if (p_ble_cb->scan_win != scan_window) {
+ p_ble_cb->scan_win = scan_window;
+ new_param = true;
+ }
+
+ if (new_param && btm_ble_get_conn_st() == BLE_CONNECTING) {
+ btm_ble_suspend_bg_conn();
+ }
+ } else {
+ BTM_TRACE_ERROR("Illegal Connection Scan Parameters");
+ }
+}
+
/********************************************************
*
* Function BTM_BleSetPrefConnParams
@@ -379,27 +548,25 @@ void BTM_BleSecureConnectionOobDataReply(const RawAddress& bd_addr,
* scan_window: scan window
* min_conn_int - minimum preferred connection interval
* max_conn_int - maximum preferred connection interval
- * peripheral_latency - preferred peripheral latency
+ * slave_latency - preferred slave latency
* supervision_tout - preferred supervision timeout
*
* Returns void
*
******************************************************************************/
void BTM_BleSetPrefConnParams(const RawAddress& bd_addr, uint16_t min_conn_int,
- uint16_t max_conn_int,
- uint16_t peripheral_latency,
+ uint16_t max_conn_int, uint16_t slave_latency,
uint16_t supervision_tout) {
if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::BTM_BleSetPrefConnParams(
- bd_addr, min_conn_int, max_conn_int, peripheral_latency,
- supervision_tout);
+ bd_addr, min_conn_int, max_conn_int, slave_latency, supervision_tout);
}
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
BTM_TRACE_API(
"BTM_BleSetPrefConnParams min: %u max: %u latency: %u \
tout: %u",
- min_conn_int, max_conn_int, peripheral_latency, supervision_tout);
+ min_conn_int, max_conn_int, slave_latency, supervision_tout);
if (BTM_BLE_ISVALID_PARAM(min_conn_int, BTM_BLE_CONN_INT_MIN,
BTM_BLE_CONN_INT_MAX) &&
@@ -407,11 +574,10 @@ void BTM_BleSetPrefConnParams(const RawAddress& bd_addr, uint16_t min_conn_int,
BTM_BLE_CONN_INT_MAX) &&
BTM_BLE_ISVALID_PARAM(supervision_tout, BTM_BLE_CONN_SUP_TOUT_MIN,
BTM_BLE_CONN_SUP_TOUT_MAX) &&
- (peripheral_latency <= BTM_BLE_CONN_LATENCY_MAX ||
- peripheral_latency == BTM_BLE_CONN_PARAM_UNDEF)) {
+ (slave_latency <= BTM_BLE_CONN_LATENCY_MAX ||
+ slave_latency == BTM_BLE_CONN_PARAM_UNDEF)) {
if (p_dev_rec) {
- /* expect conn int and stout and peripheral latency to be updated all
- * together
+ /* expect conn int and stout and slave latency to be updated all together
*/
if (min_conn_int != BTM_BLE_CONN_PARAM_UNDEF ||
max_conn_int != BTM_BLE_CONN_PARAM_UNDEF) {
@@ -425,11 +591,10 @@ void BTM_BleSetPrefConnParams(const RawAddress& bd_addr, uint16_t min_conn_int,
else
p_dev_rec->conn_params.max_conn_int = min_conn_int;
- if (peripheral_latency != BTM_BLE_CONN_PARAM_UNDEF)
- p_dev_rec->conn_params.peripheral_latency = peripheral_latency;
+ if (slave_latency != BTM_BLE_CONN_PARAM_UNDEF)
+ p_dev_rec->conn_params.slave_latency = slave_latency;
else
- p_dev_rec->conn_params.peripheral_latency =
- BTM_BLE_CONN_PERIPHERAL_LATENCY_DEF;
+ p_dev_rec->conn_params.slave_latency = BTM_BLE_CONN_SLAVE_LATENCY_DEF;
if (supervision_tout != BTM_BLE_CONN_PARAM_UNDEF)
p_dev_rec->conn_params.supervision_tout = supervision_tout;
@@ -525,7 +690,7 @@ bool BTM_ReadConnectedTransportAddress(RawAddress* remote_bda,
if (p_dev_rec == NULL) return false;
if (transport == BT_TRANSPORT_BR_EDR) {
- if (BTM_IsAclConnectionUp(p_dev_rec->bd_addr, transport)) {
+ if (btm_bda_to_acl(p_dev_rec->bd_addr, transport) != NULL) {
*remote_bda = p_dev_rec->bd_addr;
return true;
} else if (p_dev_rec->device_type & BT_DEVICE_TYPE_BREDR) {
@@ -537,7 +702,7 @@ bool BTM_ReadConnectedTransportAddress(RawAddress* remote_bda,
if (transport == BT_TRANSPORT_LE) {
*remote_bda = p_dev_rec->ble.pseudo_addr;
- if (BTM_IsAclConnectionUp(p_dev_rec->ble.pseudo_addr, transport))
+ if (btm_bda_to_acl(p_dev_rec->ble.pseudo_addr, transport) != NULL)
return true;
else
return false;
@@ -635,63 +800,70 @@ bool BTM_UseLeLink(const RawAddress& bd_addr) {
if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::BTM_UseLeLink(bd_addr);
}
-
- if (BTM_IsAclConnectionUp(bd_addr, BT_TRANSPORT_BR_EDR)) {
- return false;
- } else if (BTM_IsAclConnectionUp(bd_addr, BT_TRANSPORT_LE)) {
- return true;
- }
-
+ tACL_CONN* p;
tBT_DEVICE_TYPE dev_type;
tBLE_ADDR_TYPE addr_type;
- BTM_ReadDevInfo(bd_addr, &dev_type, &addr_type);
- return (dev_type == BT_DEVICE_TYPE_BLE);
+ bool use_le = false;
+
+ p = btm_bda_to_acl(bd_addr, BT_TRANSPORT_BR_EDR);
+ if (p != NULL) {
+ return use_le;
+ } else {
+ p = btm_bda_to_acl(bd_addr, BT_TRANSPORT_LE);
+ if (p != NULL) {
+ use_le = true;
+ } else {
+ BTM_ReadDevInfo(bd_addr, &dev_type, &addr_type);
+ use_le = (dev_type == BT_DEVICE_TYPE_BLE);
+ }
+ }
+ return use_le;
}
+/*******************************************************************************
+ *
+ * Function BTM_SetBleDataLength
+ *
+ * Description This function is to set maximum BLE transmission packet size
+ *
+ * Returns BTM_SUCCESS if success; otherwise failed.
+ *
+ ******************************************************************************/
tBTM_STATUS BTM_SetBleDataLength(const RawAddress& bd_addr,
uint16_t tx_pdu_length) {
- if (!controller_get_interface()->supports_ble_packet_extension()) {
- LOG_INFO("Local controller unable to support le packet extension");
- return BTM_ILLEGAL_VALUE;
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_SetBleDataLength(bd_addr, tx_pdu_length);
}
-
- if (tx_pdu_length > BTM_BLE_DATA_SIZE_MAX)
- tx_pdu_length = BTM_BLE_DATA_SIZE_MAX;
- else if (tx_pdu_length < BTM_BLE_DATA_SIZE_MIN)
- tx_pdu_length = BTM_BLE_DATA_SIZE_MIN;
-
+ tACL_CONN* p_acl = btm_bda_to_acl(bd_addr, BT_TRANSPORT_LE);
uint16_t tx_time = BTM_BLE_DATA_TX_TIME_MAX_LEGACY;
- if (controller_get_interface()->get_bt_version()->hci_version >=
- HCI_PROTO_VERSION_5_0)
- tx_time = BTM_BLE_DATA_TX_TIME_MAX;
-
- if (!BTM_IsAclConnectionUp(bd_addr, BT_TRANSPORT_LE)) {
- LOG_INFO(
- "Unable to set data length because no le acl link connected to device");
+ if (p_acl == NULL) {
+ BTM_TRACE_ERROR("%s: Wrong mode: no LE link exist or LE not supported",
+ __func__);
return BTM_WRONG_MODE;
}
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- uint16_t handle = bluetooth::shim::L2CA_GetLeHandle(bd_addr);
- btsnd_hcic_ble_set_data_length(handle, tx_pdu_length, tx_time);
- return BTM_SUCCESS;
- }
+ BTM_TRACE_DEBUG("%s: tx_pdu_length =%d", __func__, tx_pdu_length);
- uint16_t hci_handle = BTM_GetHCIConnHandle(bd_addr, BT_TRANSPORT_LE);
+ if (!controller_get_interface()->supports_ble_packet_extension()) {
+ BTM_TRACE_ERROR("%s failed, request not supported", __func__);
+ return BTM_ILLEGAL_VALUE;
+ }
- if (!acl_peer_supports_ble_packet_extension(hci_handle)) {
- LOG_INFO("Remote device unable to support le packet extension");
+ if (!HCI_LE_DATA_LEN_EXT_SUPPORTED(p_acl->peer_le_features)) {
+ BTM_TRACE_ERROR("%s failed, peer does not support request", __func__);
return BTM_ILLEGAL_VALUE;
}
- tx_pdu_length = std::min<uint16_t>(
- tx_pdu_length,
- controller_get_interface()->get_ble_maximum_tx_data_length());
- tx_time = std::min<uint16_t>(
- tx_time, controller_get_interface()->get_ble_maximum_tx_time());
+ if (tx_pdu_length > BTM_BLE_DATA_SIZE_MAX)
+ tx_pdu_length = BTM_BLE_DATA_SIZE_MAX;
+ else if (tx_pdu_length < BTM_BLE_DATA_SIZE_MIN)
+ tx_pdu_length = BTM_BLE_DATA_SIZE_MIN;
- btsnd_hcic_ble_set_data_length(hci_handle, tx_pdu_length, tx_time);
+ if (controller_get_interface()->get_bt_version()->hci_version >= HCI_PROTO_VERSION_5_0)
+ tx_time = BTM_BLE_DATA_TX_TIME_MAX;
+
+ btsnd_hcic_ble_set_data_length(p_acl->hci_handle, tx_pdu_length, tx_time);
return BTM_SUCCESS;
}
@@ -735,7 +907,9 @@ void BTM_BleReadPhy(
}
BTM_TRACE_DEBUG("%s", __func__);
- if (!BTM_IsAclConnectionUp(bd_addr, BT_TRANSPORT_LE)) {
+ tACL_CONN* p_acl = btm_bda_to_acl(bd_addr, BT_TRANSPORT_LE);
+
+ if (p_acl == NULL) {
BTM_TRACE_ERROR("%s: Wrong mode: no LE link exist or LE not supported",
__func__);
cb.Run(0, 0, HCI_ERR_NO_CONNECTION);
@@ -751,7 +925,7 @@ void BTM_BleReadPhy(
return;
}
- uint16_t handle = BTM_GetHCIConnHandle(bd_addr, BT_TRANSPORT_LE);
+ uint16_t handle = p_acl->hci_handle;
const uint8_t len = HCIC_PARAM_SIZE_BLE_READ_PHY;
uint8_t data[len];
@@ -764,16 +938,71 @@ void BTM_BleReadPhy(
void doNothing(uint8_t* data, uint16_t len) {}
+/*******************************************************************************
+ *
+ * Function BTM_BleSetDefaultPhy
+ *
+ * Description To set preferred PHY for ensuing LE connections
+ *
+ *
+ * Returns BTM_SUCCESS if command successfully sent to controller,
+ * BTM_MODE_UNSUPPORTED if local controller doesn't support LE
+ * 2M or LE Coded PHY
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_BleSetDefaultPhy(uint8_t all_phys, uint8_t tx_phys,
+ uint8_t rx_phys) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_BleSetDefaultPhy(all_phys, tx_phys, rx_phys);
+ }
+ BTM_TRACE_DEBUG("%s: all_phys = 0x%02x, tx_phys = 0x%02x, rx_phys = 0x%02x",
+ __func__, all_phys, tx_phys, rx_phys);
+
+ // checking if local controller supports it!
+ if (!controller_get_interface()->supports_ble_2m_phy() &&
+ !controller_get_interface()->supports_ble_coded_phy()) {
+ BTM_TRACE_ERROR("%s failed, request not supported in local controller!",
+ __func__);
+ return BTM_MODE_UNSUPPORTED;
+ }
+
+ const uint8_t len = HCIC_PARAM_SIZE_BLE_SET_DEFAULT_PHY;
+ uint8_t data[len];
+ uint8_t* pp = data;
+ UINT8_TO_STREAM(pp, all_phys);
+ UINT8_TO_STREAM(pp, tx_phys);
+ UINT8_TO_STREAM(pp, rx_phys);
+ btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_BLE_SET_DEFAULT_PHY, data, len,
+ base::Bind(doNothing));
+ return BTM_SUCCESS;
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_BleSetPhy
+ *
+ * Description To set PHY preferences for specified LE connection
+ *
+ *
+ * Returns BTM_SUCCESS if command successfully sent to controller,
+ * BTM_MODE_UNSUPPORTED if local controller doesn't support LE
+ * 2M or LE Coded PHY,
+ * BTM_ILLEGAL_VALUE if specified remote doesn't support LE 2M
+ * or LE Coded PHY,
+ * BTM_WRONG_MODE if Device in wrong mode for request.
+ *
+ ******************************************************************************/
void BTM_BleSetPhy(const RawAddress& bd_addr, uint8_t tx_phys, uint8_t rx_phys,
uint16_t phy_options) {
if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::BTM_BleSetPhy(bd_addr, tx_phys, rx_phys,
phy_options);
}
- if (!BTM_IsAclConnectionUp(bd_addr, BT_TRANSPORT_LE)) {
- LOG_INFO(
- "Unable to set phy preferences because no le acl is connected to "
- "device");
+ tACL_CONN* p_acl = btm_bda_to_acl(bd_addr, BT_TRANSPORT_LE);
+
+ if (p_acl == NULL) {
+ BTM_TRACE_ERROR("%s: Wrong mode: no LE link exist or LE not supported",
+ __func__);
return;
}
@@ -781,19 +1010,25 @@ void BTM_BleSetPhy(const RawAddress& bd_addr, uint8_t tx_phys, uint8_t rx_phys,
if (tx_phys == 0) all_phys &= 0x01;
if (rx_phys == 0) all_phys &= 0x02;
- uint16_t handle = BTM_GetHCIConnHandle(bd_addr, BT_TRANSPORT_LE);
+ BTM_TRACE_DEBUG(
+ "%s: all_phys = 0x%02x, tx_phys = 0x%02x, rx_phys = 0x%02x, phy_options "
+ "= 0x%04x",
+ __func__, all_phys, tx_phys, rx_phys, phy_options);
+
+ uint16_t handle = p_acl->hci_handle;
// checking if local controller supports it!
if (!controller_get_interface()->supports_ble_2m_phy() &&
!controller_get_interface()->supports_ble_coded_phy()) {
- LOG_INFO("Local controller unable to support setting of le phy parameters");
+ BTM_TRACE_ERROR("%s failed, request not supported in local controller!",
+ __func__);
gatt_notify_phy_updated(GATT_REQ_NOT_SUPPORTED, handle, tx_phys, rx_phys);
return;
}
- if (!acl_peer_supports_ble_2m_phy(handle) &&
- !acl_peer_supports_ble_coded_phy(handle)) {
- LOG_INFO("Remote device unable to support setting of le phy parameter");
+ if (!HCI_LE_2M_PHY_SUPPORTED(p_acl->peer_le_features) &&
+ !HCI_LE_CODED_PHY_SUPPORTED(p_acl->peer_le_features)) {
+ BTM_TRACE_ERROR("%s failed, peer does not support request", __func__);
gatt_notify_phy_updated(GATT_REQ_NOT_SUPPORTED, handle, tx_phys, rx_phys);
return;
}
@@ -859,8 +1094,16 @@ tBTM_SEC_ACTION btm_ble_determine_security_act(bool is_originator,
if (ble_sec_act == BTM_BLE_SEC_REQ_ACT_NONE) return BTM_SEC_OK;
- bool is_link_encrypted = BTM_IsEncrypted(bdaddr, BT_TRANSPORT_LE);
- bool is_key_mitm = BTM_IsLinkKeyAuthed(bdaddr, BT_TRANSPORT_LE);
+ uint8_t sec_flag = 0;
+ BTM_GetSecurityFlagsByTransport(bdaddr, &sec_flag, BT_TRANSPORT_LE);
+
+ bool is_link_encrypted = false;
+ bool is_key_mitm = false;
+ if (sec_flag & (BTM_SEC_FLAG_ENCRYPTED | BTM_SEC_FLAG_LKEY_KNOWN)) {
+ if (sec_flag & BTM_SEC_FLAG_ENCRYPTED) is_link_encrypted = true;
+
+ if (sec_flag & BTM_SEC_FLAG_LKEY_AUTHED) is_key_mitm = true;
+ }
if (auth_req & BTM_LE_AUTH_REQ_MITM) {
if (!is_key_mitm) {
@@ -907,28 +1150,30 @@ tL2CAP_LE_RESULT_CODE btm_ble_start_sec_check(const RawAddress& bd_addr,
/* If there is no application registered with this PSM do not allow connection
*/
if (!p_serv_rec) {
- LOG_WARN("PSM: %d no application registered", psm);
+ BTM_TRACE_WARNING("%s PSM: %d no application registerd", __func__, psm);
(*p_callback)(&bd_addr, BT_TRANSPORT_LE, p_ref_data, BTM_MODE_UNSUPPORTED);
return L2CAP_LE_RESULT_NO_PSM;
}
-
- bool is_encrypted = BTM_IsEncrypted(bd_addr, BT_TRANSPORT_LE);
- bool is_link_key_authed = BTM_IsLinkKeyAuthed(bd_addr, BT_TRANSPORT_LE);
- bool is_authenticated = BTM_IsAuthenticated(bd_addr, BT_TRANSPORT_LE);
+ uint8_t sec_flag = 0;
+ BTM_GetSecurityFlagsByTransport(bd_addr, &sec_flag, BT_TRANSPORT_LE);
if (!is_originator) {
- if ((p_serv_rec->security_flags & BTM_SEC_IN_ENCRYPT) && !is_encrypted) {
- LOG_ERROR(
- "L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP. service "
- "security_flags=0x%x, ",
- p_serv_rec->security_flags);
+ if ((p_serv_rec->security_flags & BTM_SEC_IN_ENCRYPT) &&
+ !(sec_flag & BTM_SEC_ENCRYPTED)) {
+ BTM_TRACE_ERROR(
+ "%s: L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP. service "
+ "security_flags=0x%x, "
+ "sec_flag=0x%x",
+ __func__, p_serv_rec->security_flags, sec_flag);
return L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP;
} else if ((p_serv_rec->security_flags & BTM_SEC_IN_AUTHENTICATE) &&
- !(is_link_key_authed || is_authenticated)) {
- LOG_ERROR(
- "L2CAP_LE_RESULT_INSUFFICIENT_AUTHENTICATION. service "
- "security_flags=0x%x, ",
- p_serv_rec->security_flags);
+ !(sec_flag &
+ (BTM_SEC_LINK_KEY_AUTHED | BTM_SEC_AUTHENTICATED))) {
+ BTM_TRACE_ERROR(
+ "%s: L2CAP_LE_RESULT_INSUFFICIENT_AUTHENTICATION. service "
+ "security_flags=0x%x, "
+ "sec_flag=0x%x",
+ __func__, p_serv_rec->security_flags, sec_flag);
return L2CAP_LE_RESULT_INSUFFICIENT_AUTHENTICATION;
}
/* TODO: When security is required, then must check that the key size of our
@@ -943,36 +1188,35 @@ tL2CAP_LE_RESULT_CODE btm_ble_start_sec_check(const RawAddress& bd_addr,
switch (sec_act) {
case BTM_SEC_OK:
- LOG_DEBUG("Security met");
+ BTM_TRACE_DEBUG("%s Security met", __func__);
p_callback(&bd_addr, BT_TRANSPORT_LE, p_ref_data, BTM_SUCCESS);
result = L2CAP_LE_RESULT_CONN_OK;
break;
case BTM_SEC_ENCRYPT:
- LOG_DEBUG("Encryption needs to be done");
+ BTM_TRACE_DEBUG("%s Encryption needs to be done", __func__);
ble_sec_act = BTM_BLE_SEC_ENCRYPT;
break;
case BTM_SEC_ENCRYPT_MITM:
- LOG_DEBUG("Pairing with MITM needs to be done");
+ BTM_TRACE_DEBUG("%s Pairing with MITM needs to be done", __func__);
ble_sec_act = BTM_BLE_SEC_ENCRYPT_MITM;
break;
case BTM_SEC_ENCRYPT_NO_MITM:
- LOG_DEBUG("Pairing with No MITM needs to be done");
+ BTM_TRACE_DEBUG("%s Pairing with No MITM needs to be done", __func__);
ble_sec_act = BTM_BLE_SEC_ENCRYPT_NO_MITM;
break;
case BTM_SEC_ENC_PENDING:
- LOG_DEBUG("Ecryption pending");
+ BTM_TRACE_DEBUG("%s Ecryption pending", __func__);
break;
}
- if (ble_sec_act == BTM_BLE_SEC_NONE) {
- return result;
- }
+ if (ble_sec_act == BTM_BLE_SEC_NONE) return result;
- l2cble_update_sec_act(bd_addr, sec_act);
+ tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(bd_addr, BT_TRANSPORT_LE);
+ p_lcb->sec_act = sec_act;
BTM_SetEncryption(bd_addr, BT_TRANSPORT_LE, p_callback, p_ref_data,
ble_sec_act);
@@ -1142,10 +1386,8 @@ void btm_sec_save_le_key(const RawAddress& bd_addr, tBTM_LE_KEY_TYPE key_type,
case BTM_LE_KEY_PID:
p_rec->ble.keys.irk = p_keys->pid_key.irk;
- p_rec->ble.identity_address_with_type.bda =
- p_keys->pid_key.identity_addr;
- p_rec->ble.identity_address_with_type.type =
- p_keys->pid_key.identity_addr_type;
+ p_rec->ble.identity_addr = p_keys->pid_key.identity_addr;
+ p_rec->ble.identity_addr_type = p_keys->pid_key.identity_addr_type;
p_rec->ble.key_type |= BTM_LE_KEY_PID;
BTM_TRACE_DEBUG(
"%s: BTM_LE_KEY_PID key_type=0x%x save peer IRK, change bd_addr=%s "
@@ -1302,7 +1544,7 @@ void btm_ble_link_sec_check(const RawAddress& bd_addr,
if (p_dev_rec->sec_state == BTM_SEC_STATE_ENCRYPTING ||
p_dev_rec->sec_state == BTM_SEC_STATE_AUTHENTICATING) {
- /* race condition: discard the security request while central is encrypting
+ /* race condition: discard the security request while master is encrypting
* the link */
*p_sec_req_act = BTM_BLE_SEC_REQ_ACT_DISCARD;
} else {
@@ -1369,8 +1611,8 @@ tBTM_STATUS btm_ble_set_encryption(const RawAddress& bd_addr,
return (BTM_WRONG_MODE);
}
- BTM_TRACE_DEBUG("btm_ble_set_encryption sec_act=0x%x role_central=%d",
- sec_act, p_rec->role_central);
+ BTM_TRACE_DEBUG("btm_ble_set_encryption sec_act=0x%x role_master=%d", sec_act,
+ p_rec->role_master);
if (sec_act == BTM_BLE_SEC_ENCRYPT_MITM) {
p_rec->security_required |= BTM_SEC_IN_MITM;
@@ -1378,13 +1620,13 @@ tBTM_STATUS btm_ble_set_encryption(const RawAddress& bd_addr,
switch (sec_act) {
case BTM_BLE_SEC_ENCRYPT:
- if (link_role == HCI_ROLE_CENTRAL) {
+ if (link_role == BTM_ROLE_MASTER) {
/* start link layer encryption using the security info stored */
cmd = btm_ble_start_encrypt(bd_addr, false, NULL);
break;
}
- /* if salve role then fall through to call SMP_Pair below which will send
- a sec_request to request the central to encrypt the link */
+ /* if salve role then fall through to call SMP_Pair below which will send a
+ sec_request to request the master to encrypt the link */
FALLTHROUGH_INTENDED; /* FALLTHROUGH */
case BTM_BLE_SEC_ENCRYPT_NO_MITM:
case BTM_BLE_SEC_ENCRYPT_MITM:
@@ -1398,7 +1640,7 @@ tBTM_STATUS btm_ble_set_encryption(const RawAddress& bd_addr,
cmd = BTM_SUCCESS;
break;
}
- if (link_role == HCI_ROLE_CENTRAL) {
+ if (link_role == BTM_ROLE_MASTER) {
if (sec_req_act == BTM_BLE_SEC_REQ_ACT_ENCRYPT) {
cmd = btm_ble_start_encrypt(bd_addr, false, NULL);
break;
@@ -1423,7 +1665,7 @@ tBTM_STATUS btm_ble_set_encryption(const RawAddress& bd_addr,
* Function btm_ble_ltk_request
*
* Description This function is called when encryption request is received
- * on a peripheral device.
+ * on a slave device.
*
*
* Returns void
@@ -1523,7 +1765,7 @@ void btm_ble_link_encrypted(const RawAddress& bd_addr, uint8_t encr_enable) {
btm_sec_dev_rec_cback_event(p_dev_rec, BTM_SUCCESS, true);
else if (p_dev_rec->sec_flags & ~BTM_SEC_LE_LINK_KEY_KNOWN) {
btm_sec_dev_rec_cback_event(p_dev_rec, BTM_FAILED_ON_SECURITY, true);
- } else if (p_dev_rec->role_central)
+ } else if (p_dev_rec->role_master)
btm_sec_dev_rec_cback_event(p_dev_rec, BTM_ERR_PROCESSING, true);
}
/* to notify GATT to send data if any request is pending */
@@ -1535,7 +1777,7 @@ void btm_ble_link_encrypted(const RawAddress& bd_addr, uint8_t encr_enable) {
* Function btm_ble_ltk_request_reply
*
* Description This function is called to send a LTK request reply on a
- * peripheral
+ * slave
* device.
*
* Returns void
@@ -1686,41 +1928,56 @@ uint8_t btm_ble_br_keys_req(tBTM_SEC_DEV_REC* p_dev_rec,
******************************************************************************/
void btm_ble_connected(const RawAddress& bda, uint16_t handle, uint8_t enc_mode,
uint8_t role, tBLE_ADDR_TYPE addr_type,
- bool addr_matched) {
+ UNUSED_ATTR bool addr_matched) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bda);
+ tBTM_BLE_CB* p_cb = &btm_cb.ble_ctr_cb;
+
+ BTM_TRACE_EVENT("btm_ble_connected");
+
+ /* Commenting out trace due to obf/compilation problems.
+ */
+ if (p_dev_rec) {
+ VLOG(1) << __func__ << " Security Manager: handle:" << handle
+ << " enc_mode:" << loghex(enc_mode) << " bda: " << bda
+ << " RName: " << p_dev_rec->sec_bd_name
+ << " p_dev_rec:" << p_dev_rec;
+
+ BTM_TRACE_DEBUG("btm_ble_connected sec_flags=0x%x", p_dev_rec->sec_flags);
+ } else {
+ VLOG(1) << __func__ << " Security Manager: handle:" << handle
+ << " enc_mode:" << loghex(enc_mode) << " bda: " << bda
+ << " p_dev_rec:" << p_dev_rec;
+ }
+
if (!p_dev_rec) {
- LOG_INFO("Creating new device record for new ble connection");
+ /* There is no device record for new connection. Allocate one */
p_dev_rec = btm_sec_alloc_dev(bda);
- if (p_dev_rec == nullptr) {
- LOG_WARN("Unable to create device record for new ble connection");
- return;
- }
- } else {
- LOG_INFO("Updating device record timestamp for existing ble connection");
- // TODO() Why is timestamp a counter ?
+ if (p_dev_rec == NULL) return;
+ } else /* Update the timestamp for this device */
+ {
p_dev_rec->timestamp = btm_cb.dev_rec_count++;
}
+ /* update device information */
+ p_dev_rec->device_type |= BT_DEVICE_TYPE_BLE;
+ p_dev_rec->ble_hci_handle = handle;
p_dev_rec->ble.ble_addr_type = addr_type;
+ /* update pseudo address */
p_dev_rec->ble.pseudo_addr = bda;
- p_dev_rec->ble_hci_handle = handle;
- p_dev_rec->device_type |= BT_DEVICE_TYPE_BLE;
- p_dev_rec->role_central = (role == HCI_ROLE_CENTRAL) ? true : false;
- if (!addr_matched) {
- p_dev_rec->ble.active_addr_type = tBTM_SEC_BLE::BTM_BLE_ADDR_PSEUDO;
- if (p_dev_rec->ble.ble_addr_type == BLE_ADDR_RANDOM) {
- p_dev_rec->ble.cur_rand_addr = bda;
- }
- }
- btm_cb.ble_ctr_cb.inq_var.directed_conn = BTM_BLE_ADV_IND_EVT;
-}
+ p_dev_rec->role_master = false;
+ if (role == HCI_ROLE_MASTER) p_dev_rec->role_master = true;
+
+#if (BLE_PRIVACY_SPT == TRUE)
+ if (!addr_matched) p_dev_rec->ble.active_addr_type = BTM_BLE_ADDR_PSEUDO;
+
+ if (p_dev_rec->ble.ble_addr_type == BLE_ADDR_RANDOM && !addr_matched)
+ p_dev_rec->ble.cur_rand_addr = bda;
+#endif
-void btm_ble_connected_from_address_with_type(
- const tBLE_BD_ADDR& address_with_type, uint16_t handle, uint8_t enc_mode,
- uint8_t role, bool addr_matched) {
- btm_ble_connected(address_with_type.bda, handle, enc_mode, role,
- address_with_type.type, addr_matched);
+ p_cb->inq_var.directed_conn = BTM_BLE_CONNECT_EVT;
+
+ return;
}
/*****************************************************************************
@@ -1729,10 +1986,10 @@ void btm_ble_connected_from_address_with_type(
* Description This function is the SMP callback handler.
*
*****************************************************************************/
-tBTM_STATUS btm_proc_smp_cback(tSMP_EVT event, const RawAddress& bd_addr,
- tSMP_EVT_DATA* p_data) {
+uint8_t btm_proc_smp_cback(tSMP_EVT event, const RawAddress& bd_addr,
+ tSMP_EVT_DATA* p_data) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
- tBTM_STATUS res = BTM_SUCCESS;
+ uint8_t res = 0;
BTM_TRACE_DEBUG("btm_proc_smp_cback event = %d", event);
@@ -1784,7 +2041,7 @@ tBTM_STATUS btm_proc_smp_cback(tSMP_EVT event, const RawAddress& bd_addr,
if (p_dev_rec == NULL) {
BTM_TRACE_ERROR("%s: p_dev_rec is NULL", __func__);
android_errorWriteLog(0x534e4554, "120612744");
- return BTM_SUCCESS;
+ return 0;
}
BTM_TRACE_DEBUG(
"evt=SMP_COMPLT_EVT before update sec_level=0x%x sec_flags=0x%x",
@@ -1835,8 +2092,10 @@ tBTM_STATUS btm_proc_smp_cback(tSMP_EVT event, const RawAddress& bd_addr,
if (res == BTM_SUCCESS) {
p_dev_rec->sec_state = BTM_SEC_STATE_IDLE;
+#if (BLE_PRIVACY_SPT == TRUE)
/* add all bonded device into resolving list if IRK is available*/
btm_ble_resolving_list_load_dev(p_dev_rec);
+#endif
}
btm_sec_dev_rec_cback_event(p_dev_rec, res, true);
@@ -1848,16 +2107,10 @@ tBTM_STATUS btm_proc_smp_cback(tSMP_EVT event, const RawAddress& bd_addr,
break;
}
} else {
- // If we are being paired with via OOB we haven't created a dev rec for
- // the device yet
- if (event == SMP_SC_LOC_OOB_DATA_UP_EVT) {
- btm_sec_cr_loc_oob_data_cback_event(bd_addr, p_data->loc_oob_data);
- } else {
- LOG_WARN("Unexpected event '%d' without p_dev_rec", event);
- }
+ BTM_TRACE_ERROR("btm_proc_smp_cback received for unknown device");
}
- return BTM_SUCCESS;
+ return 0;
}
/*******************************************************************************
@@ -1969,6 +2222,141 @@ bool BTM_BleVerifySignature(const RawAddress& bd_addr, uint8_t* p_orig,
}
/*******************************************************************************
+ *
+ * Function BTM_GetLeSecurityState
+ *
+ * Description This function is called to get security mode 1 flags and
+ * encryption key size for LE peer.
+ *
+ * Returns bool true if LE device is found, false otherwise.
+ *
+ ******************************************************************************/
+bool BTM_GetLeSecurityState(const RawAddress& bd_addr,
+ uint8_t* p_le_dev_sec_flags,
+ uint8_t* p_le_key_size) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_GetLeSecurityState(bd_addr, p_le_dev_sec_flags,
+ p_le_key_size);
+ }
+ tBTM_SEC_DEV_REC* p_dev_rec;
+ uint16_t dev_rec_sec_flags;
+
+ *p_le_dev_sec_flags = 0;
+ *p_le_key_size = 0;
+
+ p_dev_rec = btm_find_dev(bd_addr);
+ if (p_dev_rec == NULL) {
+ BTM_TRACE_ERROR("%s fails", __func__);
+ return (false);
+ }
+
+ if (p_dev_rec->ble_hci_handle == BTM_SEC_INVALID_HANDLE) {
+ BTM_TRACE_ERROR("%s-this is not LE device", __func__);
+ return (false);
+ }
+
+ dev_rec_sec_flags = p_dev_rec->sec_flags;
+
+ if (dev_rec_sec_flags & BTM_SEC_LE_ENCRYPTED) {
+ /* link is encrypted with LTK or STK */
+ *p_le_key_size = p_dev_rec->enc_key_size;
+ *p_le_dev_sec_flags |= BTM_SEC_LE_LINK_ENCRYPTED;
+
+ *p_le_dev_sec_flags |=
+ (dev_rec_sec_flags & BTM_SEC_LE_AUTHENTICATED)
+ ? BTM_SEC_LE_LINK_PAIRED_WITH_MITM /* set auth LTK flag */
+ : BTM_SEC_LE_LINK_PAIRED_WITHOUT_MITM; /* set unauth LTK flag */
+ } else if (p_dev_rec->ble.key_type & BTM_LE_KEY_PENC) {
+ /* link is unencrypted, still LTK is available */
+ *p_le_key_size = p_dev_rec->ble.keys.key_size;
+
+ *p_le_dev_sec_flags |=
+ (dev_rec_sec_flags & BTM_SEC_LE_LINK_KEY_AUTHED)
+ ? BTM_SEC_LE_LINK_PAIRED_WITH_MITM /* set auth LTK flag */
+ : BTM_SEC_LE_LINK_PAIRED_WITHOUT_MITM; /* set unauth LTK flag */
+ }
+
+ BTM_TRACE_DEBUG("%s - le_dev_sec_flags: 0x%02x, le_key_size: %d", __func__,
+ *p_le_dev_sec_flags, *p_le_key_size);
+
+ return true;
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_BleSecurityProcedureIsRunning
+ *
+ * Description This function indicates if LE security procedure is
+ * currently running with the peer.
+ *
+ * Returns bool true if security procedure is running, false
+ * otherwise.
+ *
+ ******************************************************************************/
+bool BTM_BleSecurityProcedureIsRunning(const RawAddress& bd_addr) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_BleSecurityProcedureIsRunning(bd_addr);
+ }
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
+
+ if (p_dev_rec == NULL) {
+ LOG(ERROR) << __func__ << " device with BDA: " << bd_addr
+ << " is not found";
+ return false;
+ }
+
+ return (p_dev_rec->sec_state == BTM_SEC_STATE_ENCRYPTING ||
+ p_dev_rec->sec_state == BTM_SEC_STATE_AUTHENTICATING);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_BleGetSupportedKeySize
+ *
+ * Description This function gets the maximum encryption key size in bytes
+ * the local device can suport.
+ * record.
+ *
+ * Returns the key size or 0 if the size can't be retrieved.
+ *
+ ******************************************************************************/
+extern uint8_t BTM_BleGetSupportedKeySize(const RawAddress& bd_addr) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_BleGetSupportedKeySize(bd_addr);
+ }
+#if (L2CAP_LE_COC_INCLUDED == TRUE)
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
+ tBTM_LE_EVT_DATA btm_le_evt_data;
+ uint8_t callback_rc;
+
+ if (!p_dev_rec) {
+ LOG(ERROR) << __func__ << " device with BDA: " << bd_addr
+ << " is not found";
+ return 0;
+ }
+
+ if (btm_cb.api.p_le_callback == NULL) {
+ BTM_TRACE_ERROR("%s can't access supported key size", __func__);
+ return 0;
+ }
+
+ callback_rc = (*btm_cb.api.p_le_callback)(
+ BTM_LE_IO_REQ_EVT, p_dev_rec->bd_addr, &btm_le_evt_data);
+
+ if (callback_rc != BTM_SUCCESS) {
+ BTM_TRACE_ERROR("%s can't access supported key size", __func__);
+ return 0;
+ }
+
+ BTM_TRACE_DEBUG("%s device supports key size = %d", __func__,
+ btm_le_evt_data.io_req.max_key_size);
+ return (btm_le_evt_data.io_req.max_key_size);
+#else
+ return 0;
+#endif
+}
+
+/*******************************************************************************
* Utility functions for LE device IR/ER generation
******************************************************************************/
/** This function is to notify application new keys have been generated. */
@@ -2016,10 +2404,12 @@ static void btm_ble_reset_id_impl(const Octet16& rand1, const Octet16& rand2) {
btm_notify_new_key(BTM_BLE_KEY_TYPE_ID);
+#if (BLE_PRIVACY_SPT == TRUE)
/* if privacy is enabled, new RPA should be calculated */
if (btm_cb.ble_ctr_cb.privacy_mode != BTM_PRIVACY_NONE) {
btm_gen_resolvable_private_addr(base::Bind(&btm_gen_resolve_paddr_low));
}
+#endif
/* proceed generate ER */
btm_cb.devcb.ble_encryption_key_value = rand2;
@@ -2066,74 +2456,24 @@ void btm_ble_reset_id(void) {
void btm_ble_set_random_address(const RawAddress& random_bda) {
tBTM_LE_RANDOM_CB* p_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
tBTM_BLE_CB* p_ble_cb = &btm_cb.ble_ctr_cb;
- const bool adv_mode = btm_cb.ble_ctr_cb.inq_var.adv_mode;
+ bool adv_mode = btm_cb.ble_ctr_cb.inq_var.adv_mode;
+
+ BTM_TRACE_DEBUG("%s", __func__);
if (adv_mode == BTM_BLE_ADV_ENABLE)
btsnd_hcic_ble_set_adv_enable(BTM_BLE_ADV_DISABLE);
- if (p_ble_cb->is_ble_scan_active()) {
- btm_ble_stop_scan();
- }
+ if (BTM_BLE_IS_SCAN_ACTIVE(p_ble_cb->scan_activity)) btm_ble_stop_scan();
btm_ble_suspend_bg_conn();
p_cb->private_addr = random_bda;
btsnd_hcic_ble_set_random_addr(p_cb->private_addr);
- LOG_DEBUG("Updating local random address:%s", PRIVATE_ADDRESS(random_bda));
if (adv_mode == BTM_BLE_ADV_ENABLE)
btsnd_hcic_ble_set_adv_enable(BTM_BLE_ADV_ENABLE);
- if (p_ble_cb->is_ble_scan_active()) {
- btm_ble_start_scan();
- }
+ if (BTM_BLE_IS_SCAN_ACTIVE(p_ble_cb->scan_activity)) btm_ble_start_scan();
btm_ble_resume_bg_conn();
}
-/*******************************************************************************
- *
- * Function btm_ble_get_acl_remote_addr
- *
- * Description This function reads the active remote address used for the
- * connection.
- *
- * Returns success return true, otherwise false.
- *
- ******************************************************************************/
-bool btm_ble_get_acl_remote_addr(uint16_t hci_handle, RawAddress& conn_addr,
- tBLE_ADDR_TYPE* p_addr_type) {
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev_by_handle(hci_handle);
- if (p_dev_rec == nullptr) {
- LOG_WARN("Unable to find security device record hci_handle:%hu",
- hci_handle);
- // TODO Release acl resource
- return false;
- }
-
- bool st = true;
-
- switch (p_dev_rec->ble.active_addr_type) {
- case tBTM_SEC_BLE::BTM_BLE_ADDR_PSEUDO:
- conn_addr = p_dev_rec->bd_addr;
- *p_addr_type = p_dev_rec->ble.ble_addr_type;
- break;
-
- case tBTM_SEC_BLE::BTM_BLE_ADDR_RRA:
- conn_addr = p_dev_rec->ble.cur_rand_addr;
- *p_addr_type = BLE_ADDR_RANDOM;
- break;
-
- case tBTM_SEC_BLE::BTM_BLE_ADDR_STATIC:
- conn_addr = p_dev_rec->ble.identity_address_with_type.bda;
- *p_addr_type = p_dev_rec->ble.identity_address_with_type.type;
- break;
-
- default:
- LOG_WARN("Unable to find record with active address type: %d",
- p_dev_rec->ble.active_addr_type);
- st = false;
- break;
- }
- return st;
-}
-
#if BTM_BLE_CONFORMANCE_TESTING == TRUE
/*******************************************************************************
*
diff --git a/stack/btm/btm_ble_addr.cc b/stack/btm/btm_ble_addr.cc
index c61fac6c9..678dd76af 100644
--- a/stack/btm/btm_ble_addr.cc
+++ b/stack/btm/btm_ble_addr.cc
@@ -26,25 +26,19 @@
#include <string.h>
#include "bt_types.h"
+#include "btm_int.h"
#include "btu.h"
#include "device/include/controller.h"
#include "gap_api.h"
#include "hcimsgs.h"
#include "btm_ble_int.h"
-#include "main/shim/shim.h"
-#include "stack/btm/btm_dev.h"
#include "stack/crypto_toolbox/crypto_toolbox.h"
-#include "stack/include/acl_api.h"
-
-extern tBTM_CB btm_cb;
-
-void btm_ble_set_random_address(const RawAddress& random_bda);
/* This function generates Resolvable Private Address (RPA) from Identity
* Resolving Key |irk| and |random|*/
-static RawAddress generate_rpa_from_irk_and_rand(const Octet16& irk,
- BT_OCTET8 random) {
+RawAddress generate_rpa_from_irk_and_rand(const Octet16& irk,
+ BT_OCTET8 random) {
random[2] &= (~BLE_RESOLVE_ADDR_MASK);
random[2] |= BLE_RESOLVE_ADDR_MSB;
@@ -63,25 +57,13 @@ static RawAddress generate_rpa_from_irk_and_rand(const Octet16& irk,
return address;
}
-static void btm_ble_refresh_raddr_timer_timeout(UNUSED_ATTR void* data) {
- if (btm_cb.ble_ctr_cb.addr_mgnt_cb.own_addr_type == BLE_ADDR_RANDOM) {
- /* refresh the random addr */
- btm_gen_resolvable_private_addr(base::Bind(&btm_gen_resolve_paddr_low));
- }
-}
-
/** This function is called when random address for local controller was
* generated */
void btm_gen_resolve_paddr_low(const RawAddress& address) {
- /* when GD advertising and scanning modules are enabled, set random address
- * via address manager in GD */
- if (bluetooth::shim::is_gd_advertising_enabled() &&
- bluetooth::shim::is_gd_scanning_enabled()) {
- LOG_INFO("GD advertising and scanning modules are enabled, skip");
- return;
- }
-
tBTM_LE_RANDOM_CB* p_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
+
+ BTM_TRACE_EVENT("btm_gen_resolve_paddr_low");
+
p_cb->private_addr = address;
/* set it to controller */
@@ -101,6 +83,7 @@ void btm_gen_resolve_paddr_low(const RawAddress& address) {
/** This function generate a resolvable private address using local IRK */
void btm_gen_resolvable_private_addr(
base::Callback<void(const RawAddress&)> cb) {
+ BTM_TRACE_EVENT("%s", __func__);
/* generate 3B rand as BD LSB, SRK with it, get BD MSB */
btsnd_hcic_ble_rand(base::Bind(
[](base::Callback<void(const RawAddress&)> cb, BT_OCTET8 random) {
@@ -119,6 +102,57 @@ uint64_t btm_get_next_private_addrress_interval_ms() {
}
/*******************************************************************************
+ *
+ * Function btm_gen_non_resolve_paddr_cmpl
+ *
+ * Description This is the callback function when non-resolvable private
+ * function is generated and write to controller.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btm_gen_non_resolve_paddr_cmpl(BT_OCTET8 rand) {
+ tBTM_LE_RANDOM_CB* p_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
+ tBTM_BLE_ADDR_CBACK* p_cback = p_cb->p_generate_cback;
+ void* p_data = p_cb->p;
+ uint8_t* pp;
+ RawAddress static_random;
+
+ BTM_TRACE_EVENT("btm_gen_non_resolve_paddr_cmpl");
+
+ p_cb->p_generate_cback = NULL;
+ pp = rand;
+ STREAM_TO_BDADDR(static_random, pp);
+ /* mask off the 2 MSB */
+ static_random.address[0] &= BLE_STATIC_PRIVATE_MSB_MASK;
+
+ /* report complete */
+ if (p_cback) (*p_cback)(static_random, p_data);
+}
+/*******************************************************************************
+ *
+ * Function btm_gen_non_resolvable_private_addr
+ *
+ * Description This function generate a non-resolvable private address.
+ *
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_gen_non_resolvable_private_addr(tBTM_BLE_ADDR_CBACK* p_cback,
+ void* p) {
+ tBTM_LE_RANDOM_CB* p_mgnt_cb = &btm_cb.ble_ctr_cb.addr_mgnt_cb;
+
+ BTM_TRACE_EVENT("btm_gen_non_resolvable_private_addr");
+
+ if (p_mgnt_cb->p_generate_cback != NULL) return;
+
+ p_mgnt_cb->p_generate_cback = p_cback;
+ p_mgnt_cb->p = p;
+ btsnd_hcic_ble_rand(base::Bind(&btm_gen_non_resolve_paddr_cmpl));
+}
+
+/*******************************************************************************
* Utility functions for Random address resolving
******************************************************************************/
@@ -189,20 +223,25 @@ bool btm_ble_addr_resolvable(const RawAddress& rpa,
* starting from calculating IRK. If the record index exceeds the maximum record
* number, matching failed and send a callback. */
static bool btm_ble_match_random_bda(void* data, void* context) {
+ BTM_TRACE_EVENT("%s next iteration", __func__);
+ RawAddress* random_bda = (RawAddress*)context;
+
tBTM_SEC_DEV_REC* p_dev_rec = static_cast<tBTM_SEC_DEV_REC*>(data);
- RawAddress* random_bda = static_cast<RawAddress*>(context);
+
+ BTM_TRACE_DEBUG("sec_flags = %02x device_type = %d", p_dev_rec->sec_flags,
+ p_dev_rec->device_type);
if (!(p_dev_rec->device_type & BT_DEVICE_TYPE_BLE) ||
!(p_dev_rec->ble.key_type & BTM_LE_KEY_PID))
- // Match fails preconditions
return true;
if (rpa_matches_irk(*random_bda, p_dev_rec->ble.keys.irk)) {
- // Matched
+ BTM_TRACE_EVENT("match is found");
+ // if it was match, finish iteration, otherwise continue
return false;
}
- // This item not a match, continue iteration
+ // not a match, continue iteration
return true;
}
@@ -211,35 +250,45 @@ static bool btm_ble_match_random_bda(void* data, void* context) {
* matched to.
*/
tBTM_SEC_DEV_REC* btm_ble_resolve_random_addr(const RawAddress& random_bda) {
+ BTM_TRACE_EVENT("%s", __func__);
+
+ /* start to resolve random address */
+ /* check for next security record */
+
list_node_t* n = list_foreach(btm_cb.sec_dev_rec, btm_ble_match_random_bda,
(void*)&random_bda);
- return (n == nullptr) ? (nullptr)
- : (static_cast<tBTM_SEC_DEV_REC*>(list_node(n)));
+ tBTM_SEC_DEV_REC* p_dev_rec = nullptr;
+ if (n != nullptr) p_dev_rec = static_cast<tBTM_SEC_DEV_REC*>(list_node(n));
+
+ BTM_TRACE_EVENT("%s: %sresolved", __func__,
+ (p_dev_rec == nullptr ? "not " : ""));
+ return p_dev_rec;
}
/*******************************************************************************
* address mapping between pseudo address and real connection address
******************************************************************************/
/** Find the security record whose LE identity address is matching */
-static tBTM_SEC_DEV_REC* btm_find_dev_by_identity_addr(
- const RawAddress& bd_addr, uint8_t addr_type) {
+tBTM_SEC_DEV_REC* btm_find_dev_by_identity_addr(const RawAddress& bd_addr,
+ uint8_t addr_type) {
+#if (BLE_PRIVACY_SPT == TRUE)
list_node_t* end = list_end(btm_cb.sec_dev_rec);
for (list_node_t* node = list_begin(btm_cb.sec_dev_rec); node != end;
node = list_next(node)) {
tBTM_SEC_DEV_REC* p_dev_rec =
static_cast<tBTM_SEC_DEV_REC*>(list_node(node));
- if (p_dev_rec->ble.identity_address_with_type.bda == bd_addr) {
- if ((p_dev_rec->ble.identity_address_with_type.type &
- (~BLE_ADDR_TYPE_ID_BIT)) != (addr_type & (~BLE_ADDR_TYPE_ID_BIT)))
+ if (p_dev_rec->ble.identity_addr == bd_addr) {
+ if ((p_dev_rec->ble.identity_addr_type & (~BLE_ADDR_TYPE_ID_BIT)) !=
+ (addr_type & (~BLE_ADDR_TYPE_ID_BIT)))
BTM_TRACE_WARNING(
"%s find pseudo->random match with diff addr type: %d vs %d",
- __func__, p_dev_rec->ble.identity_address_with_type.type,
- addr_type);
+ __func__, p_dev_rec->ble.identity_addr_type, addr_type);
/* found the match */
return p_dev_rec;
}
}
+#endif
return NULL;
}
@@ -254,32 +303,27 @@ static tBTM_SEC_DEV_REC* btm_find_dev_by_identity_addr(
******************************************************************************/
bool btm_identity_addr_to_random_pseudo(RawAddress* bd_addr,
uint8_t* p_addr_type, bool refresh) {
+#if (BLE_PRIVACY_SPT == TRUE)
tBTM_SEC_DEV_REC* p_dev_rec =
btm_find_dev_by_identity_addr(*bd_addr, *p_addr_type);
- if (p_dev_rec == nullptr) {
- return false;
- }
+ BTM_TRACE_EVENT("%s", __func__);
/* evt reported on static address, map static address to random pseudo */
- /* if RPA offloading is supported, or 4.2 controller, do RPA refresh */
- if (refresh &&
- controller_get_interface()->get_ble_resolving_list_max_size() != 0) {
- btm_ble_read_resolving_list_entry(p_dev_rec);
- }
-
- /* assign the original address to be the current report address */
- if (!btm_ble_init_pseudo_addr(p_dev_rec, *bd_addr)) {
- *bd_addr = p_dev_rec->ble.pseudo_addr;
- }
+ if (p_dev_rec != NULL) {
+ /* if RPA offloading is supported, or 4.2 controller, do RPA refresh */
+ if (refresh &&
+ controller_get_interface()->get_ble_resolving_list_max_size() != 0)
+ btm_ble_read_resolving_list_entry(p_dev_rec);
- *p_addr_type = p_dev_rec->ble.ble_addr_type;
- return true;
-}
+ /* assign the original address to be the current report address */
+ if (!btm_ble_init_pseudo_addr(p_dev_rec, *bd_addr))
+ *bd_addr = p_dev_rec->ble.pseudo_addr;
-bool btm_identity_addr_to_random_pseudo_from_address_with_type(
- tBLE_BD_ADDR* address_with_type, bool refresh) {
- return btm_identity_addr_to_random_pseudo(
- &(address_with_type->bda), &(address_with_type->type), refresh);
+ *p_addr_type = p_dev_rec->ble.ble_addr_type;
+ return true;
+ }
+#endif
+ return false;
}
/*******************************************************************************
@@ -292,17 +336,19 @@ bool btm_identity_addr_to_random_pseudo_from_address_with_type(
******************************************************************************/
bool btm_random_pseudo_to_identity_addr(RawAddress* random_pseudo,
uint8_t* p_identity_addr_type) {
+#if (BLE_PRIVACY_SPT == TRUE)
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(*random_pseudo);
if (p_dev_rec != NULL) {
if (p_dev_rec->ble.in_controller_list & BTM_RESOLVING_LIST_BIT) {
- *p_identity_addr_type = p_dev_rec->ble.identity_address_with_type.type;
- *random_pseudo = p_dev_rec->ble.identity_address_with_type.bda;
+ *p_identity_addr_type = p_dev_rec->ble.identity_addr_type;
+ *random_pseudo = p_dev_rec->ble.identity_addr;
if (controller_get_interface()->supports_ble_privacy())
*p_identity_addr_type |= BLE_ADDR_TYPE_ID_BIT;
return true;
}
}
+#endif
return false;
}
@@ -315,36 +361,83 @@ bool btm_random_pseudo_to_identity_addr(RawAddress* random_pseudo,
* connection address.
*
******************************************************************************/
-void btm_ble_refresh_peer_resolvable_private_addr(
- const RawAddress& pseudo_bda, const RawAddress& rpa,
- tBTM_SEC_BLE::tADDRESS_TYPE rra_type) {
+void btm_ble_refresh_peer_resolvable_private_addr(const RawAddress& pseudo_bda,
+ const RawAddress& rpa,
+ uint8_t rra_type) {
+#if (BLE_PRIVACY_SPT == TRUE)
+ uint8_t rra_dummy = false;
+ if (rpa.IsEmpty()) rra_dummy = true;
+
+ /* update security record here, in adv event or connection complete process */
tBTM_SEC_DEV_REC* p_sec_rec = btm_find_dev(pseudo_bda);
- if (p_sec_rec == nullptr) {
- LOG_WARN("%s No matching known device in record", __func__);
+ if (p_sec_rec != NULL) {
+ p_sec_rec->ble.cur_rand_addr = rpa;
+
+ /* unknown, if dummy address, set to static */
+ if (rra_type == BTM_BLE_ADDR_PSEUDO)
+ p_sec_rec->ble.active_addr_type =
+ rra_dummy ? BTM_BLE_ADDR_STATIC : BTM_BLE_ADDR_RRA;
+ else
+ p_sec_rec->ble.active_addr_type = rra_type;
+ } else {
+ BTM_TRACE_ERROR("No matching known device in record");
return;
}
- p_sec_rec->ble.cur_rand_addr = rpa;
+ BTM_TRACE_DEBUG("%s: active_addr_type: %d ", __func__,
+ p_sec_rec->ble.active_addr_type);
- if (rra_type == tBTM_SEC_BLE::BTM_BLE_ADDR_PSEUDO) {
- p_sec_rec->ble.active_addr_type = rpa.IsEmpty()
- ? tBTM_SEC_BLE::BTM_BLE_ADDR_STATIC
- : tBTM_SEC_BLE::BTM_BLE_ADDR_RRA;
- } else {
- p_sec_rec->ble.active_addr_type = rra_type;
+ /* connection refresh remote address */
+ tACL_CONN* p_acl = btm_bda_to_acl(p_sec_rec->bd_addr, BT_TRANSPORT_LE);
+ if (p_acl == NULL)
+ p_acl = btm_bda_to_acl(p_sec_rec->ble.pseudo_addr, BT_TRANSPORT_LE);
+
+ if (p_acl != NULL) {
+ if (rra_type == BTM_BLE_ADDR_PSEUDO) {
+ /* use identity address, resolvable_private_addr is empty */
+ if (rra_dummy) {
+ p_acl->active_remote_addr_type = p_sec_rec->ble.identity_addr_type;
+ p_acl->active_remote_addr = p_sec_rec->ble.identity_addr;
+ } else {
+ p_acl->active_remote_addr_type = BLE_ADDR_RANDOM;
+ p_acl->active_remote_addr = rpa;
+ }
+ } else {
+ p_acl->active_remote_addr_type = rra_type;
+ p_acl->active_remote_addr = rpa;
+ }
+
+ BTM_TRACE_DEBUG("p_acl->active_remote_addr_type: %d ",
+ p_acl->active_remote_addr_type);
+ VLOG(1) << __func__ << " conn_addr: " << p_acl->active_remote_addr;
}
+#endif
+}
- /* connection refresh remote address */
- const auto& identity_address = p_sec_rec->ble.identity_address_with_type.bda;
- auto identity_address_type = p_sec_rec->ble.identity_address_with_type.type;
-
- if (!acl_refresh_remote_address(identity_address, identity_address_type,
- p_sec_rec->bd_addr, rra_type, rpa)) {
- // Try looking up the pseudo random address
- if (!acl_refresh_remote_address(identity_address, identity_address_type,
- p_sec_rec->ble.pseudo_addr, rra_type,
- rpa)) {
- LOG_ERROR("%s Unknown device to refresh remote device", __func__);
+/*******************************************************************************
+ *
+ * Function btm_ble_refresh_local_resolvable_private_addr
+ *
+ * Description This function refresh the currently used resolvable private
+ * address for the active link to the remote device
+ *
+ ******************************************************************************/
+void btm_ble_refresh_local_resolvable_private_addr(
+ const RawAddress& pseudo_addr, const RawAddress& local_rpa) {
+#if (BLE_PRIVACY_SPT == TRUE)
+ tACL_CONN* p = btm_bda_to_acl(pseudo_addr, BT_TRANSPORT_LE);
+
+ if (p != NULL) {
+ if (btm_cb.ble_ctr_cb.privacy_mode != BTM_PRIVACY_NONE) {
+ p->conn_addr_type = BLE_ADDR_RANDOM;
+ if (!local_rpa.IsEmpty())
+ p->conn_addr = local_rpa;
+ else
+ p->conn_addr = btm_cb.ble_ctr_cb.addr_mgnt_cb.private_addr;
+ } else {
+ p->conn_addr_type = BLE_ADDR_PUBLIC;
+ p->conn_addr = *controller_get_interface()->get_address();
}
}
+#endif
}
diff --git a/stack/btm/btm_ble_adv_filter.cc b/stack/btm/btm_ble_adv_filter.cc
index 08773ab48..708e7c299 100644
--- a/stack/btm/btm_ble_adv_filter.cc
+++ b/stack/btm/btm_ble_adv_filter.cc
@@ -21,16 +21,13 @@
#include "bt_target.h"
#include "bt_types.h"
+#include "bt_utils.h"
#include "btm_ble_api.h"
-#include "btm_dev.h"
#include "btm_int.h"
#include "btu.h"
#include "device/include/controller.h"
#include "hcidefs.h"
#include "hcimsgs.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_int_types.h"
-#include "utils/include/bt_utils.h"
#include <string.h>
#include <algorithm>
@@ -39,8 +36,6 @@
#include <base/bind.h>
#include <base/bind_helpers.h>
-extern tBTM_CB btm_cb;
-
using base::Bind;
using bluetooth::Uuid;
@@ -83,16 +78,49 @@ static uint8_t btm_ble_cs_update_pf_counter(tBTM_BLE_SCAN_COND_OP action,
#define BTM_BLE_ADV_FILT_CB_EVT_MASK 0xF0
#define BTM_BLE_ADV_FILT_SUBCODE_MASK 0x0F
-static bool is_filtering_supported() {
+bool is_filtering_supported() {
return cmn_ble_vsc_cb.filter_support != 0 && cmn_ble_vsc_cb.max_filter != 0;
}
-static bool is_empty_128bit(const std::array<uint8_t, 16> data) {
- int i, len = 16;
- for (i = 0; i < len; i++) {
- if (data[i] != (uint8_t)0) return false;
+/*******************************************************************************
+ *
+ * Function btm_ble_condtype_to_ocf
+ *
+ * Description Convert cond_type to OCF
+ *
+ * Returns Returns ocf value
+ *
+ ******************************************************************************/
+uint8_t btm_ble_condtype_to_ocf(uint8_t cond_type) {
+ uint8_t ocf = 0;
+
+ switch (cond_type) {
+ case BTM_BLE_PF_ADDR_FILTER:
+ ocf = BTM_BLE_META_PF_ADDR;
+ break;
+ case BTM_BLE_PF_SRVC_UUID:
+ ocf = BTM_BLE_META_PF_UUID;
+ break;
+ case BTM_BLE_PF_SRVC_SOL_UUID:
+ ocf = BTM_BLE_META_PF_SOL_UUID;
+ break;
+ case BTM_BLE_PF_LOCAL_NAME:
+ ocf = BTM_BLE_META_PF_LOCAL_NAME;
+ break;
+ case BTM_BLE_PF_MANU_DATA:
+ ocf = BTM_BLE_META_PF_MANU_DATA;
+ break;
+ case BTM_BLE_PF_SRVC_DATA_PATTERN:
+ ocf = BTM_BLE_META_PF_SRVC_DATA;
+ break;
+ case BTM_BLE_PF_TYPE_ALL:
+ ocf = BTM_BLE_META_PF_ALL;
+ break;
+ default:
+ ocf = BTM_BLE_PF_TYPE_MAX;
+ break;
}
- return true;
+ return ocf;
}
/*******************************************************************************
@@ -104,7 +132,7 @@ static bool is_empty_128bit(const std::array<uint8_t, 16> data) {
* Returns Returns condtype value
*
******************************************************************************/
-static uint8_t btm_ble_ocf_to_condtype(uint8_t ocf) {
+uint8_t btm_ble_ocf_to_condtype(uint8_t ocf) {
uint8_t cond_type = 0;
switch (ocf) {
@@ -139,8 +167,8 @@ static uint8_t btm_ble_ocf_to_condtype(uint8_t ocf) {
return cond_type;
}
-static void btm_flt_update_cb(uint8_t expected_ocf, tBTM_BLE_PF_CFG_CBACK cb,
- uint8_t* p, uint16_t evt_len) {
+void btm_flt_update_cb(uint8_t expected_ocf, tBTM_BLE_PF_CFG_CBACK cb,
+ uint8_t* p, uint16_t evt_len) {
if (evt_len != 4) {
BTM_TRACE_ERROR("%s: bad length: %d", __func__, evt_len);
return;
@@ -158,10 +186,8 @@ static void btm_flt_update_cb(uint8_t expected_ocf, tBTM_BLE_PF_CFG_CBACK cb,
return;
}
- tBTM_STATUS btm_status = (status == 0) ? BTM_SUCCESS : BTM_ERR_PROCESSING;
-
if (op_subcode == BTM_BLE_META_PF_FEAT_SEL) {
- cb.Run(num_avail, action, btm_status);
+ cb.Run(num_avail, action, status);
return;
}
@@ -179,7 +205,7 @@ static void btm_flt_update_cb(uint8_t expected_ocf, tBTM_BLE_PF_CFG_CBACK cb,
/* send ADV PF operation complete */
btm_ble_adv_filt_cb.op_type = 0;
- cb.Run(num_avail, action, btm_status);
+ cb.Run(num_avail, action, status);
}
/*******************************************************************************
@@ -192,8 +218,7 @@ static void btm_flt_update_cb(uint8_t expected_ocf, tBTM_BLE_PF_CFG_CBACK cb,
* Returns pointer to the counter if found; NULL otherwise.
*
******************************************************************************/
-static tBTM_BLE_PF_COUNT* btm_ble_find_addr_filter_counter(
- tBLE_BD_ADDR* p_le_bda) {
+tBTM_BLE_PF_COUNT* btm_ble_find_addr_filter_counter(tBLE_BD_ADDR* p_le_bda) {
uint8_t i;
tBTM_BLE_PF_COUNT* p_addr_filter =
&btm_ble_adv_filt_cb.p_addr_filter_count[1];
@@ -218,7 +243,7 @@ static tBTM_BLE_PF_COUNT* btm_ble_find_addr_filter_counter(
* otherwise.
*
******************************************************************************/
-static tBTM_BLE_PF_COUNT* btm_ble_alloc_addr_filter_counter(
+tBTM_BLE_PF_COUNT* btm_ble_alloc_addr_filter_counter(
const RawAddress& bd_addr) {
uint8_t i;
tBTM_BLE_PF_COUNT* p_addr_filter =
@@ -242,8 +267,8 @@ static tBTM_BLE_PF_COUNT* btm_ble_alloc_addr_filter_counter(
* Returns true if deallocation succeed; false otherwise.
*
******************************************************************************/
-static bool btm_ble_dealloc_addr_filter_counter(tBLE_BD_ADDR* p_bd_addr,
- uint8_t filter_type) {
+bool btm_ble_dealloc_addr_filter_counter(tBLE_BD_ADDR* p_bd_addr,
+ uint8_t filter_type) {
uint8_t i;
tBTM_BLE_PF_COUNT* p_addr_filter =
&btm_ble_adv_filt_cb.p_addr_filter_count[1];
@@ -269,10 +294,9 @@ static bool btm_ble_dealloc_addr_filter_counter(tBLE_BD_ADDR* p_bd_addr,
* This function update(add,delete or clear) the adv local name filtering
* condition.
*/
-static void BTM_LE_PF_local_name(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index,
- std::vector<uint8_t> name,
- tBTM_BLE_PF_CFG_CBACK cb) {
+void BTM_LE_PF_local_name(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ std::vector<uint8_t> name, tBTM_BLE_PF_CFG_CBACK cb) {
uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH;
uint8_t len_max = len + BTM_BLE_PF_STR_LEN_MAX;
@@ -301,8 +325,8 @@ static void BTM_LE_PF_local_name(tBTM_BLE_SCAN_COND_OP action,
/**
* this function update(add/remove) service data change filter.
*/
-static void BTM_LE_PF_srvc_data(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index) {
+void BTM_LE_PF_srvc_data(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index) {
uint8_t num_avail = (action == BTM_BLE_SCAN_COND_ADD) ? 0 : 1;
btm_ble_cs_update_pf_counter(action, BTM_BLE_PF_SRVC_DATA, nullptr,
@@ -313,12 +337,11 @@ static void BTM_LE_PF_srvc_data(tBTM_BLE_SCAN_COND_OP action,
* This function update(add,delete or clear) the adv manufacturer data filtering
* condition.
*/
-static void BTM_LE_PF_manu_data(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index,
- uint16_t company_id, uint16_t company_id_mask,
- std::vector<uint8_t> data,
- std::vector<uint8_t> data_mask,
- tBTM_BLE_PF_CFG_CBACK cb) {
+void BTM_LE_PF_manu_data(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index, uint16_t company_id,
+ uint16_t company_id_mask, std::vector<uint8_t> data,
+ std::vector<uint8_t> data_mask,
+ tBTM_BLE_PF_CFG_CBACK cb) {
uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH;
int len_max = len + BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_PF_STR_LEN_MAX;
@@ -366,11 +389,11 @@ static void BTM_LE_PF_manu_data(tBTM_BLE_SCAN_COND_OP action,
* This function update(add,delete or clear) the service data filtering
* condition.
**/
-static void BTM_LE_PF_srvc_data_pattern(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index,
- std::vector<uint8_t> data,
- std::vector<uint8_t> data_mask,
- tBTM_BLE_PF_CFG_CBACK cb) {
+void BTM_LE_PF_srvc_data_pattern(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ std::vector<uint8_t> data,
+ std::vector<uint8_t> data_mask,
+ tBTM_BLE_PF_CFG_CBACK cb) {
uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH;
int len_max = len + BTM_BLE_PF_STR_LEN_MAX + BTM_BLE_PF_STR_LEN_MAX;
@@ -411,10 +434,9 @@ static void BTM_LE_PF_srvc_data_pattern(tBTM_BLE_SCAN_COND_OP action,
* counter update failed.
*
******************************************************************************/
-static uint8_t btm_ble_cs_update_pf_counter(tBTM_BLE_SCAN_COND_OP action,
- uint8_t cond_type,
- tBLE_BD_ADDR* p_bd_addr,
- uint8_t num_available) {
+uint8_t btm_ble_cs_update_pf_counter(tBTM_BLE_SCAN_COND_OP action,
+ uint8_t cond_type, tBLE_BD_ADDR* p_bd_addr,
+ uint8_t num_available) {
tBTM_BLE_PF_COUNT* p_addr_filter = NULL;
uint8_t* p_counter = NULL;
@@ -465,9 +487,9 @@ static uint8_t btm_ble_cs_update_pf_counter(tBTM_BLE_SCAN_COND_OP action,
/**
* This function updates the address filter of adv.
*/
-static void BTM_LE_PF_addr_filter(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index,
- tBLE_BD_ADDR addr, tBTM_BLE_PF_CFG_CBACK cb) {
+void BTM_LE_PF_addr_filter(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index, tBLE_BD_ADDR addr,
+ tBTM_BLE_PF_CFG_CBACK cb) {
const uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH + BTM_BLE_META_ADDR_LEN;
uint8_t param[len];
@@ -479,6 +501,7 @@ static void BTM_LE_PF_addr_filter(tBTM_BLE_SCAN_COND_OP action,
UINT8_TO_STREAM(p, filt_index);
if (action != BTM_BLE_SCAN_COND_CLEAR) {
+#if (BLE_PRIVACY_SPT == TRUE)
if (addr.type == BLE_ADDR_PUBLIC_ID) {
LOG(INFO) << __func__ << " Filter address " << addr.bda
<< " has type PUBLIC_ID, try to get identity address";
@@ -486,6 +509,7 @@ static void BTM_LE_PF_addr_filter(tBTM_BLE_SCAN_COND_OP action,
* this call will have no effect. */
btm_random_pseudo_to_identity_addr(&addr.bda, &addr.type);
}
+#endif
LOG(INFO) << __func__
<< " Adding scan filter with peer address: " << addr.bda;
@@ -505,13 +529,13 @@ static void BTM_LE_PF_addr_filter(tBTM_BLE_SCAN_COND_OP action,
/**
* This function updates(adds, deletes or clears) the service UUID filter.
*/
-static void BTM_LE_PF_uuid_filter(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index,
- tBTM_BLE_PF_COND_TYPE filter_type,
- const bluetooth::Uuid& uuid,
- tBTM_BLE_PF_LOGIC_TYPE cond_logic,
- const bluetooth::Uuid& uuid_mask,
- tBTM_BLE_PF_CFG_CBACK cb) {
+void BTM_LE_PF_uuid_filter(tBTM_BLE_SCAN_COND_OP action,
+ tBTM_BLE_PF_FILT_INDEX filt_index,
+ tBTM_BLE_PF_COND_TYPE filter_type,
+ const bluetooth::Uuid& uuid,
+ tBTM_BLE_PF_LOGIC_TYPE cond_logic,
+ const bluetooth::Uuid& uuid_mask,
+ tBTM_BLE_PF_CFG_CBACK cb) {
uint8_t evt_type;
if (BTM_BLE_PF_SRVC_UUID == filter_type) {
@@ -544,7 +568,7 @@ static void BTM_LE_PF_uuid_filter(tBTM_BLE_SCAN_COND_OP action,
len += Uuid::kNumBytes128;
} else {
BTM_TRACE_ERROR("illegal UUID length: %d", uuid_len);
- cb.Run(0, BTM_BLE_PF_CONFIG, BTM_ILLEGAL_VALUE);
+ cb.Run(0, BTM_BLE_PF_CONFIG, 1 /*BTA_FAILURE*/);
return;
}
@@ -572,24 +596,11 @@ static void BTM_LE_PF_uuid_filter(tBTM_BLE_SCAN_COND_OP action,
memset(&btm_ble_adv_filt_cb.cur_filter_target, 0, sizeof(tBLE_BD_ADDR));
}
-/*
- * Used to remove device records for devices setting scan filters with address,
- * type and IRK. Flow:
- * - ScanFilter comes in with IRK.
- * - Check IRK for empty, if empty ignore setting to resolving list.
- * - Otherwise we set it to the resolving list via BTM_SecAddBleKey.
- * - Then on clear we need to check if the device is paired and if it isn't we
- * remove it referencing this map.
- *
- */
-static std::unordered_map<tBTM_BLE_PF_FILT_INDEX, RawAddress>
- remove_me_later_map;
-
void BTM_LE_PF_set(tBTM_BLE_PF_FILT_INDEX filt_index,
std::vector<ApcfCommand> commands,
tBTM_BLE_PF_CFG_CBACK cb) {
if (!is_filtering_supported()) {
- cb.Run(0, BTM_BLE_PF_ENABLE, BTM_MODE_UNSUPPORTED);
+ cb.Run(0, BTM_BLE_PF_ENABLE, 1 /* BTA_FAILURE */);
return;
}
@@ -611,48 +622,6 @@ void BTM_LE_PF_set(tBTM_BLE_PF_FILT_INDEX filt_index,
BTM_LE_PF_addr_filter(action, filt_index, target_addr,
base::DoNothing());
- if (!is_empty_128bit(cmd.irk)) {
- // Save index and addr
- auto entry = remove_me_later_map.find(filt_index);
- if (entry != remove_me_later_map.end()) {
- LOG_WARN("Replacing existing filter index entry with new address");
- // If device is not bonded, then try removing the device
- // If the device doesn't get removed then it is currently connected
- // (may be pairing?) If we do delete the device we want to erase the
- // filter index so we can replace it If the device is bonded, we
- // want to erase the filter index so we don't delete it in the later
- // BTM_LE_PF_clear call.
- if (!btm_sec_is_a_bonded_dev(entry->second)) {
- if (!BTM_SecDeleteDevice(entry->second)) {
- LOG_WARN("Unable to remove device, still connected.");
- return;
- }
- }
- remove_me_later_map.erase(filt_index);
- }
- if (btm_find_dev(cmd.address) != nullptr) {
- // Unless the user tries to bond with a device in between the
- // scanner app starting a scan, then crashing, then being restarted
- // and we get to this same point with the same filt_index (whose
- // value is managed by the Java layer) then we might have a device
- // record here, in which case something else is managing the device
- // and we do not want to interfere with that experience.
- LOG_WARN("Address record already exists...this is unexpected...");
- return;
- }
- // Allocate a new "temporary" device record
- btm_sec_alloc_dev(cmd.address);
- remove_me_later_map.emplace(filt_index, cmd.address);
- // Set the IRK
- tBTM_LE_PID_KEYS pid_keys;
- pid_keys.irk = cmd.irk;
- pid_keys.identity_addr_type = cmd.addr_type;
- pid_keys.identity_addr = cmd.address;
- // Add it to the union to pass to SecAddBleKey
- tBTM_LE_KEY_VALUE le_key;
- le_key.pid_key = pid_keys;
- BTM_SecAddBleKey(cmd.address, &le_key, BTM_LE_KEY_PID);
- }
break;
}
@@ -690,7 +659,7 @@ void BTM_LE_PF_set(tBTM_BLE_PF_FILT_INDEX filt_index,
break;
}
}
- cb.Run(0, 0, BTM_SUCCESS);
+ cb.Run(0, 0, 0);
}
/**
@@ -699,7 +668,7 @@ void BTM_LE_PF_set(tBTM_BLE_PF_FILT_INDEX filt_index,
void BTM_LE_PF_clear(tBTM_BLE_PF_FILT_INDEX filt_index,
tBTM_BLE_PF_CFG_CBACK cb) {
if (!is_filtering_supported()) {
- cb.Run(0, BTM_BLE_PF_ENABLE, BTM_MODE_UNSUPPORTED);
+ cb.Run(0, BTM_BLE_PF_ENABLE, 1 /* BTA_FAILURE */);
return;
}
@@ -729,15 +698,6 @@ void BTM_LE_PF_clear(tBTM_BLE_PF_FILT_INDEX filt_index,
/* clear service data filter */
BTM_LE_PF_srvc_data_pattern(BTM_BLE_SCAN_COND_CLEAR, filt_index, {}, {},
fDoNothing);
-
- // If we have an entry, lets remove the device if it isn't bonded
- auto entry = remove_me_later_map.find(filt_index);
- if (entry != remove_me_later_map.end()) {
- auto entry = remove_me_later_map.find(filt_index);
- if (!btm_sec_is_a_bonded_dev(entry->second)) {
- BTM_SecDeleteDevice(entry->second);
- }
- }
}
uint8_t len = BTM_BLE_ADV_FILT_META_HDR_LENGTH + BTM_BLE_PF_FEAT_SEL_LEN;
@@ -785,7 +745,7 @@ void BTM_BleAdvFilterParamSetup(
uint8_t param[len], *p;
if (!is_filtering_supported()) {
- cb.Run(0, BTM_BLE_PF_ENABLE, btm_status_value(BTM_MODE_UNSUPPORTED));
+ cb.Run(0, BTM_BLE_PF_ENABLE, 1 /* BTA_FAILURE */);
return;
}
@@ -797,7 +757,7 @@ void BTM_BleAdvFilterParamSetup(
p_bda_filter = btm_ble_find_addr_filter_counter(nullptr);
if (NULL == p_bda_filter) {
BTM_TRACE_ERROR("BD Address not found!");
- cb.Run(0, BTM_BLE_PF_ENABLE, btm_status_value(BTM_UNKNOWN_ADDR));
+ cb.Run(0, BTM_BLE_PF_ENABLE, 1 /* BTA_FAILURE */);
return;
}
@@ -854,25 +814,6 @@ void BTM_BleAdvFilterParamSetup(
FROM_HERE, HCI_BLE_ADV_FILTER, param,
(uint8_t)(BTM_BLE_ADV_FILT_META_HDR_LENGTH),
base::Bind(&btm_flt_update_cb, BTM_BLE_META_PF_FEAT_SEL, cb));
-
- auto entry = remove_me_later_map.find(filt_index);
- if (entry != remove_me_later_map.end()) {
- LOG_WARN("Replacing existing filter index entry with new address");
- // If device is not bonded, then try removing the device
- // If the device doesn't get removed then it is currently connected
- // (may be pairing?) If we do delete the device we want to erase the
- // filter index so we can replace it If the device is bonded, we
- // want to erase the filter index so we don't delete it in the later
- // BTM_LE_PF_clear call.
- if (!btm_sec_is_a_bonded_dev(entry->second)) {
- if (!BTM_SecDeleteDevice(entry->second)) {
- LOG_WARN("Unable to remove device, still connected.");
- return;
- }
- }
- remove_me_later_map.erase(filt_index);
- }
-
} else if (BTM_BLE_SCAN_COND_CLEAR == action) {
/* Deallocate all filters here */
btm_ble_dealloc_addr_filter_counter(NULL, BTM_BLE_PF_TYPE_ALL);
@@ -888,8 +829,8 @@ void BTM_BleAdvFilterParamSetup(
}
}
-static void enable_cmpl_cback(tBTM_BLE_PF_STATUS_CBACK p_stat_cback, uint8_t* p,
- uint16_t evt_len) {
+void enable_cmpl_cback(tBTM_BLE_PF_STATUS_CBACK p_stat_cback, uint8_t* p,
+ uint16_t evt_len) {
uint8_t status, op_subcode, action;
if (evt_len != 3) {
@@ -906,8 +847,7 @@ static void enable_cmpl_cback(tBTM_BLE_PF_STATUS_CBACK p_stat_cback, uint8_t* p,
return;
}
- tBTM_STATUS btm_status = (status == 0) ? BTM_SUCCESS : BTM_ERR_PROCESSING;
- p_stat_cback.Run(action, btm_status);
+ p_stat_cback.Run(action, status);
}
/*******************************************************************************
@@ -923,9 +863,7 @@ static void enable_cmpl_cback(tBTM_BLE_PF_STATUS_CBACK p_stat_cback, uint8_t* p,
void BTM_BleEnableDisableFilterFeature(uint8_t enable,
tBTM_BLE_PF_STATUS_CBACK p_stat_cback) {
if (!is_filtering_supported()) {
- if (p_stat_cback)
- p_stat_cback.Run(BTM_BLE_PF_ENABLE,
- BTM_MODE_UNSUPPORTED /* BTA_FAILURE */);
+ if (p_stat_cback) p_stat_cback.Run(BTM_BLE_PF_ENABLE, 1 /* BTA_FAILURE */);
return;
}
@@ -964,3 +902,18 @@ void btm_ble_adv_filter_init(void) {
sizeof(tBTM_BLE_PF_COUNT) * cmn_ble_vsc_cb.max_filter);
}
}
+
+/*******************************************************************************
+ *
+ * Function btm_ble_adv_filter_cleanup
+ *
+ * Description This function de-initializes the adv filter control block
+ *
+ * Parameters
+ *
+ * Returns status
+ *
+ ******************************************************************************/
+void btm_ble_adv_filter_cleanup(void) {
+ osi_free_and_reset((void**)&btm_ble_adv_filt_cb.p_addr_filter_count);
+}
diff --git a/stack/btm/btm_ble_batchscan.cc b/stack/btm/btm_ble_batchscan.cc
index 8515f01f7..3d8935828 100644
--- a/stack/btm/btm_ble_batchscan.cc
+++ b/stack/btm/btm_ble_batchscan.cc
@@ -23,15 +23,12 @@
#include "bt_target.h"
#include "bt_types.h"
+#include "bt_utils.h"
#include "btm_ble_api.h"
#include "btm_int.h"
#include "btu.h"
#include "device/include/controller.h"
#include "hcimsgs.h"
-#include "stack/btm/btm_int_types.h"
-#include "utils/include/bt_utils.h"
-
-extern tBTM_CB btm_cb;
using base::Bind;
using base::Callback;
@@ -104,7 +101,6 @@ void btm_ble_batchscan_filter_track_adv_vse_cback(uint8_t len, uint8_t* p) {
adv_data.p_adv_pkt_data =
static_cast<uint8_t*>(osi_malloc(adv_data.adv_pkt_len));
memcpy(adv_data.p_adv_pkt_data, p, adv_data.adv_pkt_len);
- p += adv_data.adv_pkt_len;
}
STREAM_TO_UINT8(adv_data.scan_rsp_len, p);
@@ -127,7 +123,7 @@ void btm_ble_batchscan_filter_track_adv_vse_cback(uint8_t len, uint8_t* p) {
adv_data.advertiser_state);
// Make sure the device is known
- BTM_SecAddBleDevice(adv_data.bd_addr, BT_DEVICE_TYPE_BLE,
+ BTM_SecAddBleDevice(adv_data.bd_addr, NULL, BT_DEVICE_TYPE_BLE,
adv_data.addr_type);
ble_advtrack_cb.p_track_cback(&adv_data);
@@ -269,11 +265,6 @@ void read_reports_cb(std::vector<uint8_t> data_all, uint8_t num_records_all,
return;
}
- if (len < 4) {
- BTM_TRACE_ERROR("%s: wrong length", __func__);
- return;
- }
-
uint8_t report_format, num_records;
STREAM_TO_UINT8(report_format, p);
STREAM_TO_UINT8(num_records, p);
@@ -282,7 +273,7 @@ void read_reports_cb(std::vector<uint8_t> data_all, uint8_t num_records_all,
num_records);
if (num_records == 0) {
- cb.Run(BTM_SUCCESS, report_format, num_records_all, data_all);
+ cb.Run(status, report_format, num_records_all, data_all);
return;
}
@@ -551,3 +542,13 @@ void btm_ble_batchscan_init(void) {
memset(&ble_advtrack_cb, 0, sizeof(tBTM_BLE_ADV_TRACK_CB));
BTM_RegisterForVSEvents(btm_ble_batchscan_filter_track_adv_vse_cback, true);
}
+
+/**
+ * This function cleans the batch scan control block.
+ **/
+void btm_ble_batchscan_cleanup(void) {
+ BTM_TRACE_EVENT("%s", __func__);
+
+ memset(&ble_batchscan_cb, 0, sizeof(tBTM_BLE_BATCH_SCAN_CB));
+ memset(&ble_advtrack_cb, 0, sizeof(tBTM_BLE_ADV_TRACK_CB));
+}
diff --git a/stack/btm/btm_ble_bgconn.cc b/stack/btm/btm_ble_bgconn.cc
index 3607cda83..dbeb10374 100644
--- a/stack/btm/btm_ble_bgconn.cc
+++ b/stack/btm/btm_ble_bgconn.cc
@@ -18,25 +18,19 @@
/******************************************************************************
*
- * This file contains functions for BLE acceptlist operation.
+ * This file contains functions for BLE whitelist operation.
*
******************************************************************************/
-#include <base/bind.h>
-#include <cstdint>
+#include <base/logging.h>
#include <unordered_map>
+#include "bt_types.h"
+#include "btm_int.h"
+#include "btu.h"
#include "device/include/controller.h"
-#include "main/shim/acl_api.h"
-#include "main/shim/shim.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/btm/security_device_record.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/hcimsgs.h"
-#include "types/raw_address.h"
-
-extern tBTM_CB btm_cb;
+#include "hcimsgs.h"
+#include "l2c_int.h"
extern void btm_send_hci_create_connection(
uint16_t scan_int, uint16_t scan_win, uint8_t init_filter_policy,
@@ -45,18 +39,11 @@ extern void btm_send_hci_create_connection(
uint16_t conn_timeout, uint16_t min_ce_len, uint16_t max_ce_len,
uint8_t phy);
extern void btm_ble_create_conn_cancel();
+void wl_remove_complete(uint8_t* p_data, uint16_t /* evt_len */);
-namespace {
-
-constexpr char kAcceptlistAdd[] = "AcceptlistAdd";
-constexpr char kAcceptlistRemove[] = "AcceptlistRemove";
-constexpr char kAcceptlistClear[] = "AcceptlistClear";
-
-} // namespace
-
-// Unfortunately (for now?) we have to maintain a copy of the device acceptlist
+// Unfortunately (for now?) we have to maintain a copy of the device whitelist
// on the host to determine if a device is pending to be connected or not. This
-// controls whether the host should keep trying to scan for acceptlisted
+// controls whether the host should keep trying to scan for whitelisted
// peripherals or not.
// TODO: Move all of this to controller/le/background_list or similar?
struct BackgroundConnection {
@@ -78,67 +65,6 @@ struct BgConnHash {
static std::unordered_map<RawAddress, BackgroundConnection, BgConnHash>
background_connections;
-static void acceptlist_command_complete(tHCI_STATUS status, const char* msg) {
- switch (status) {
- case HCI_SUCCESS:
- return;
- default:
- LOG_WARN(
- "Received unexpected accept list completion command:%s status:%s",
- msg, hci_error_code_text(status).c_str());
- }
-}
-
-static void acceptlist_add_command_complete(uint8_t* p_data, uint16_t evt_len) {
- if (evt_len < sizeof(uint8_t)) {
- LOG_ERROR("Received bogus acceptlist add complete length:%hu", evt_len);
- return;
- }
- uint8_t status;
- STREAM_TO_UINT8(status, p_data);
- acceptlist_command_complete(static_cast<tHCI_STATUS>(status), kAcceptlistAdd);
-}
-
-static void acceptlist_remove_command_complete(uint8_t* p_data,
- uint16_t evt_len) {
- if (evt_len < sizeof(uint8_t)) {
- LOG_ERROR("Received bogus acceptlist remove complete length:%hu", evt_len);
- return;
- }
- uint8_t status;
- STREAM_TO_UINT8(status, p_data);
- acceptlist_command_complete(static_cast<tHCI_STATUS>(status),
- kAcceptlistRemove);
-}
-
-static void acceptlist_clear_command_complete(uint8_t* p_data,
- uint16_t evt_len) {
- if (evt_len < sizeof(uint8_t)) {
- LOG_ERROR("Received bogus acceptlist remove complete length:%hu", evt_len);
- return;
- }
- uint8_t status;
- STREAM_TO_UINT8(status, p_data);
- acceptlist_command_complete(static_cast<tHCI_STATUS>(status),
- kAcceptlistClear);
-}
-
-/** This function is to stop auto connection procedure */
-static bool btm_ble_stop_auto_conn() {
- BTM_TRACE_EVENT("%s", __func__);
-
- if (!btm_cb.ble_ctr_cb.is_connection_state_connecting()) {
- LOG_DEBUG(
- "No need to stop auto connection procedure that is not connecting");
- return false;
- }
-
- btm_ble_create_conn_cancel();
-
- btm_cb.ble_ctr_cb.reset_acceptlist_process_in_progress();
- return true;
-}
-
static void background_connection_add(uint8_t addr_type,
const RawAddress& address) {
auto map_iter = background_connections.find(address);
@@ -149,9 +75,9 @@ static void background_connection_add(uint8_t addr_type,
BackgroundConnection* connection = &map_iter->second;
if (addr_type != connection->addr_type) {
LOG(INFO) << __func__ << " Addr type mismatch " << address;
- btsnd_hcic_ble_remove_from_acceptlist(
- connection->addr_type_in_wl, connection->address,
- base::Bind(&acceptlist_remove_command_complete));
+ btsnd_hcic_ble_remove_from_white_list(
+ connection->addr_type_in_wl, connection->address,
+ base::Bind(&wl_remove_complete));
connection->addr_type = addr_type;
connection->in_controller_wl = false;
}
@@ -193,110 +119,160 @@ static int background_connections_count() {
return count;
}
-const tBLE_BD_ADDR convert_to_address_with_type(
- const RawAddress& bd_addr, const tBTM_SEC_DEV_REC* p_dev_rec) {
- if (p_dev_rec == nullptr || !p_dev_rec->is_device_type_has_ble()) {
- return {
- .type = BLE_ADDR_PUBLIC,
- .bda = bd_addr,
- };
+/*******************************************************************************
+ *
+ * Function btm_update_scanner_filter_policy
+ *
+ * Description This function updates the filter policy of scanner
+ ******************************************************************************/
+void btm_update_scanner_filter_policy(tBTM_BLE_SFP scan_policy) {
+ tBTM_BLE_INQ_CB* p_inq = &btm_cb.ble_ctr_cb.inq_var;
+
+ uint32_t scan_interval =
+ !p_inq->scan_interval ? BTM_BLE_GAP_DISC_SCAN_INT : p_inq->scan_interval;
+ uint32_t scan_window =
+ !p_inq->scan_window ? BTM_BLE_GAP_DISC_SCAN_WIN : p_inq->scan_window;
+
+ BTM_TRACE_EVENT("%s", __func__);
+
+ p_inq->sfp = scan_policy;
+ p_inq->scan_type = p_inq->scan_type == BTM_BLE_SCAN_MODE_NONE
+ ? BTM_BLE_SCAN_MODE_ACTI
+ : p_inq->scan_type;
+
+ btm_send_hci_set_scan_params(
+ p_inq->scan_type, (uint16_t)scan_interval, (uint16_t)scan_window,
+ btm_cb.ble_ctr_cb.addr_mgnt_cb.own_addr_type, scan_policy);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_ble_bgconn_cancel_if_disconnected
+ *
+ * Description If a device has been disconnected, it must be re-added to
+ * the white list. If needed, this function cancels a pending
+ * initiate command in order to trigger restart of the initiate
+ * command which in turn updates the white list.
+ *
+ * Parameters bd_addr: updated device
+ *
+ ******************************************************************************/
+void btm_ble_bgconn_cancel_if_disconnected(const RawAddress& bd_addr) {
+ if (btm_ble_get_conn_st() != BLE_CONNECTING) return;
+
+ auto map_it = background_connections.find(bd_addr);
+ if (map_it != background_connections.end()) {
+ BackgroundConnection* connection = &map_it->second;
+ if (!connection->in_controller_wl && !connection->pending_removal &&
+ !BTM_IsAclConnectionUp(bd_addr, BT_TRANSPORT_LE)) {
+ btm_ble_stop_auto_conn();
+ }
}
+}
- if (p_dev_rec->ble.identity_address_with_type.bda.IsEmpty()) {
- return {
- .type = p_dev_rec->ble.ble_addr_type,
- .bda = bd_addr,
- };
- } else {
- return p_dev_rec->ble.identity_address_with_type;
+bool BTM_BackgroundConnectAddressKnown(const RawAddress& address) {
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(address);
+
+ // not a known device, or a classic device, we assume public address
+ if (p_dev_rec == NULL || (p_dev_rec->device_type & BT_DEVICE_TYPE_BLE) == 0)
+ return true;
+
+ // bonded device with identity address known
+ if (!p_dev_rec->ble.identity_addr.IsEmpty()) {
+ return true;
+ }
+
+ // Public address, Random Static, or Random Non-Resolvable Address known
+ if (p_dev_rec->ble.ble_addr_type == BLE_ADDR_PUBLIC ||
+ !BTM_BLE_IS_RESOLVE_BDA(address)) {
+ return true;
}
+
+ // Only Resolvable Private Address (RPA) is known, we don't allow it into
+ // the background connection procedure.
+ return false;
}
/*******************************************************************************
*
* Function btm_add_dev_to_controller
*
- * Description This function load the device into controller acceptlist
+ * Description This function load the device into controller white list
******************************************************************************/
-static bool btm_add_dev_to_controller(bool to_add, const RawAddress& bd_addr) {
+bool btm_add_dev_to_controller(bool to_add, const RawAddress& bd_addr) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
if (p_dev_rec != NULL && p_dev_rec->device_type & BT_DEVICE_TYPE_BLE) {
if (to_add) {
- if (!p_dev_rec->ble.identity_address_with_type.bda.IsEmpty()) {
- LOG_DEBUG(
- "Adding known device record into acceptlist with identity "
- "device:%s",
- PRIVATE_ADDRESS(p_dev_rec->ble.identity_address_with_type));
- background_connection_add(
- p_dev_rec->ble.identity_address_with_type.type,
- p_dev_rec->ble.identity_address_with_type.bda);
+ if (!p_dev_rec->ble.identity_addr.IsEmpty()) {
+ background_connection_add(p_dev_rec->ble.identity_addr_type,
+ p_dev_rec->ble.identity_addr);
} else {
- LOG_DEBUG(
- "Adding known device record into acceptlist without identity "
- "device:%s",
- PRIVATE_ADDRESS(bd_addr));
background_connection_add(p_dev_rec->ble.ble_addr_type, bd_addr);
if (p_dev_rec->ble.ble_addr_type == BLE_ADDR_RANDOM &&
BTM_BLE_IS_RESOLVE_BDA(bd_addr)) {
- LOG(INFO) << __func__ << " adding RPA into acceptlist";
+ LOG(INFO) << __func__ << " addig RPA into white list";
}
}
- p_dev_rec->ble.in_controller_list |= BTM_ACCEPTLIST_BIT;
+ p_dev_rec->ble.in_controller_list |= BTM_WHITE_LIST_BIT;
} else {
- if (!p_dev_rec->ble.identity_address_with_type.bda.IsEmpty()) {
- LOG_DEBUG(
- "Removing known device record into acceptlist with identity "
- "device:%s",
- PRIVATE_ADDRESS(p_dev_rec->ble.identity_address_with_type));
- background_connection_remove(
- p_dev_rec->ble.identity_address_with_type.bda);
+ if (!p_dev_rec->ble.identity_addr.IsEmpty()) {
+ background_connection_remove(p_dev_rec->ble.identity_addr);
} else {
- LOG_DEBUG(
- "Removing known device record into acceptlist without identity "
- "device:%s",
- PRIVATE_ADDRESS(bd_addr));
background_connection_remove(bd_addr);
if (p_dev_rec->ble.ble_addr_type == BLE_ADDR_RANDOM &&
BTM_BLE_IS_RESOLVE_BDA(bd_addr)) {
- LOG(INFO) << __func__ << " removing RPA from acceptlist";
+ LOG(INFO) << __func__ << " removing RPA from white list";
}
}
- p_dev_rec->ble.in_controller_list &= ~BTM_ACCEPTLIST_BIT;
+ p_dev_rec->ble.in_controller_list &= ~BTM_WHITE_LIST_BIT;
}
} else {
/* not a known device, i.e. attempt to connect to device never seen before
*/
- if (to_add) {
+ if (to_add)
background_connection_add(BLE_ADDR_PUBLIC, bd_addr);
- } else {
+ else
background_connection_remove(bd_addr);
- }
}
return true;
}
+/** White list add complete */
+void wl_add_complete(uint8_t* p_data, uint16_t /* evt_len */) {
+ uint8_t status;
+ STREAM_TO_UINT8(status, p_data);
+ VLOG(2) << __func__ << ": status=" << loghex(status);
+}
+
+/** White list element remove complete */
+void wl_remove_complete(uint8_t* p_data, uint16_t /* evt_len */) {
+ uint8_t status;
+ STREAM_TO_UINT8(status, p_data);
+ VLOG(2) << __func__ << ": status=" << loghex(status);
+}
+
/*******************************************************************************
*
* Function btm_execute_wl_dev_operation
*
- * Description execute the pending acceptlist device operation (loading or
+ * Description execute the pending whitelist device operation (loading or
* removing)
******************************************************************************/
-static bool btm_execute_wl_dev_operation(void) {
- // handle removals first to avoid filling up controller's acceptlist
+bool btm_execute_wl_dev_operation(void) {
+ // handle removals first to avoid filling up controller's white list
for (auto map_it = background_connections.begin();
map_it != background_connections.end();) {
BackgroundConnection* connection = &map_it->second;
if (connection->pending_removal) {
- btsnd_hcic_ble_remove_from_acceptlist(
+ btsnd_hcic_ble_remove_from_white_list(
connection->addr_type_in_wl, connection->address,
- base::BindOnce(&acceptlist_remove_command_complete));
+ base::BindOnce(&wl_remove_complete));
map_it = background_connections.erase(map_it);
} else
++map_it;
@@ -306,36 +282,81 @@ static bool btm_execute_wl_dev_operation(void) {
const bool connected =
BTM_IsAclConnectionUp(connection->address, BT_TRANSPORT_LE);
if (!connection->in_controller_wl && !connected) {
- btsnd_hcic_ble_add_acceptlist(
- connection->addr_type, connection->address,
- base::BindOnce(&acceptlist_add_command_complete));
+ btsnd_hcic_ble_add_white_list(connection->addr_type, connection->address,
+ base::BindOnce(&wl_add_complete));
connection->in_controller_wl = true;
connection->addr_type_in_wl = connection->addr_type;
} else if (connection->in_controller_wl && connected) {
/* Bluetooth Core 4.2 as well as ESR08 disallows more than one
connection between two LE addresses. Not all controllers handle this
correctly, therefore we must make sure connected devices are not in
- the acceptlist when bg connection attempt is active. */
- btsnd_hcic_ble_remove_from_acceptlist(
+ the white list when bg connection attempt is active. */
+ btsnd_hcic_ble_remove_from_white_list(
connection->addr_type_in_wl, connection->address,
- base::BindOnce(&acceptlist_remove_command_complete));
+ base::BindOnce(&wl_remove_complete));
connection->in_controller_wl = false;
}
}
return true;
}
+/*******************************************************************************
+ *
+ * Function btm_ble_white_list_init
+ *
+ * Description Initialize white list size
+ *
+ ******************************************************************************/
+void btm_ble_white_list_init(uint8_t white_list_size) {
+ BTM_TRACE_DEBUG("%s white_list_size = %d", __func__, white_list_size);
+}
+
+uint8_t BTM_GetWhiteListSize() {
+ const controller_t* controller = controller_get_interface();
+ if (!controller->supports_ble()) {
+ return 0;
+ }
+ return controller->get_ble_white_list_size();
+}
+
+bool BTM_SetLeConnectionModeToFast() {
+ VLOG(2) << __func__;
+ tBTM_BLE_CB* p_cb = &btm_cb.ble_ctr_cb;
+ if ((p_cb->scan_int == BTM_BLE_SCAN_PARAM_UNDEF &&
+ p_cb->scan_win == BTM_BLE_SCAN_PARAM_UNDEF) ||
+ (p_cb->scan_int == BTM_BLE_SCAN_SLOW_INT_1 &&
+ p_cb->scan_win == BTM_BLE_SCAN_SLOW_WIN_1)) {
+ p_cb->scan_int = BTM_BLE_SCAN_FAST_INT;
+ p_cb->scan_win = BTM_BLE_SCAN_FAST_WIN;
+ return true;
+ }
+ return false;
+}
+
+void BTM_SetLeConnectionModeToSlow() {
+ VLOG(2) << __func__;
+ tBTM_BLE_CB* p_cb = &btm_cb.ble_ctr_cb;
+ if ((p_cb->scan_int == BTM_BLE_SCAN_PARAM_UNDEF &&
+ p_cb->scan_win == BTM_BLE_SCAN_PARAM_UNDEF) ||
+ (p_cb->scan_int == BTM_BLE_SCAN_FAST_INT &&
+ p_cb->scan_win == BTM_BLE_SCAN_FAST_WIN)) {
+ p_cb->scan_int = BTM_BLE_SCAN_SLOW_INT_1;
+ p_cb->scan_win = BTM_BLE_SCAN_SLOW_WIN_1;
+ }
+}
+
/** This function is to start auto connection procedure */
-static bool btm_ble_start_auto_conn() {
+bool btm_ble_start_auto_conn() {
tBTM_BLE_CB* p_cb = &btm_cb.ble_ctr_cb;
- ASSERT(p_cb != nullptr);
-
- const uint16_t scan_int = (p_cb->scan_int == BTM_BLE_SCAN_PARAM_UNDEF)
- ? BTM_BLE_SCAN_SLOW_INT_1
- : p_cb->scan_int;
- const uint16_t scan_win = (p_cb->scan_win == BTM_BLE_SCAN_PARAM_UNDEF)
- ? BTM_BLE_SCAN_SLOW_WIN_1
- : p_cb->scan_win;
+
+ BTM_TRACE_EVENT("%s", __func__);
+
+ uint16_t scan_int = (p_cb->scan_int == BTM_BLE_SCAN_PARAM_UNDEF)
+ ? BTM_BLE_SCAN_SLOW_INT_1
+ : p_cb->scan_int;
+ uint16_t scan_win = (p_cb->scan_win == BTM_BLE_SCAN_PARAM_UNDEF)
+ ? BTM_BLE_SCAN_SLOW_WIN_1
+ : p_cb->scan_win;
uint8_t own_addr_type = p_cb->addr_mgnt_cb.own_addr_type;
uint8_t peer_addr_type = BLE_ADDR_PUBLIC;
@@ -344,40 +365,38 @@ static bool btm_ble_start_auto_conn() {
if (controller_get_interface()->supports_ble_coded_phy()) phy |= PHY_LE_CODED;
if (!btm_ble_topology_check(BTM_BLE_STATE_INIT)) {
- LOG_INFO(
- "Unable to initiate background connection due to topology limitation");
+ LOG(INFO) << "initate background connection fail, topology limitation";
return false;
}
- if (!btm_cb.ble_ctr_cb.is_connection_state_idle() ||
- !background_connections_pending()) {
- LOG_DEBUG(
- "Connection state not idle or already have background connection "
- "pending");
+ if (btm_ble_get_conn_st() != BLE_CONN_IDLE ||
+ !background_connections_pending() || !l2cu_can_allocate_lcb()) {
return false;
}
- p_cb->wl_state |= BTM_BLE_ACCEPTLIST_INIT;
+ p_cb->wl_state |= BTM_BLE_WL_INIT;
btm_execute_wl_dev_operation();
+#if (BLE_PRIVACY_SPT == TRUE)
btm_ble_enable_resolving_list_for_platform(BTM_BLE_RL_INIT);
if (btm_cb.ble_ctr_cb.rl_state != BTM_BLE_RL_IDLE &&
controller_get_interface()->supports_ble_privacy()) {
own_addr_type |= BLE_ADDR_TYPE_ID_BIT;
peer_addr_type |= BLE_ADDR_TYPE_ID_BIT;
}
+#endif
btm_send_hci_create_connection(
scan_int, /* uint16_t scan_int */
scan_win, /* uint16_t scan_win */
- 0x01, /* uint8_t acceptlist */
+ 0x01, /* uint8_t white_list */
peer_addr_type, /* uint8_t addr_type_peer */
RawAddress::kEmpty, /* BD_ADDR bda_peer */
own_addr_type, /* uint8_t addr_type_own */
BTM_BLE_CONN_INT_MIN_DEF, /* uint16_t conn_int_min */
BTM_BLE_CONN_INT_MAX_DEF, /* uint16_t conn_int_max */
- BTM_BLE_CONN_PERIPHERAL_LATENCY_DEF, /* uint16_t conn_latency */
+ BTM_BLE_CONN_SLAVE_LATENCY_DEF, /* uint16_t conn_latency */
BTM_BLE_CONN_TIMEOUT_DEF, /* uint16_t conn_timeout */
0, /* uint16_t min_len */
0, /* uint16_t max_len */
@@ -385,55 +404,20 @@ static bool btm_ble_start_auto_conn() {
return true;
}
-/*******************************************************************************
- *
- * Function btm_update_scanner_filter_policy
- *
- * Description This function updates the filter policy of scanner
- ******************************************************************************/
-void btm_update_scanner_filter_policy(tBTM_BLE_SFP scan_policy) {
- tBTM_BLE_INQ_CB* p_inq = &btm_cb.ble_ctr_cb.inq_var;
-
- uint32_t scan_interval =
- !p_inq->scan_interval ? BTM_BLE_GAP_DISC_SCAN_INT : p_inq->scan_interval;
- uint32_t scan_window =
- !p_inq->scan_window ? BTM_BLE_GAP_DISC_SCAN_WIN : p_inq->scan_window;
-
+/** This function is to stop auto connection procedure */
+bool btm_ble_stop_auto_conn() {
BTM_TRACE_EVENT("%s", __func__);
- p_inq->sfp = scan_policy;
- p_inq->scan_type = p_inq->scan_type == BTM_BLE_SCAN_MODE_NONE
- ? BTM_BLE_SCAN_MODE_ACTI
- : p_inq->scan_type;
-
- btm_send_hci_set_scan_params(
- p_inq->scan_type, (uint16_t)scan_interval, (uint16_t)scan_window,
- btm_cb.ble_ctr_cb.addr_mgnt_cb.own_addr_type, scan_policy);
-}
+ if (btm_ble_get_conn_st() != BLE_CONNECTING) {
+ BTM_TRACE_DEBUG("conn_st = %d, not in auto conn state, cannot stop",
+ btm_ble_get_conn_st());
+ return false;
+ }
-/*******************************************************************************
- *
- * Function btm_ble_bgconn_cancel_if_disconnected
- *
- * Description If a device has been disconnected, it must be re-added to
- * the acceptlist. If needed, this function cancels a pending
- * initiate command in order to trigger restart of the initiate
- * command which in turn updates the acceptlist.
- *
- * Parameters bd_addr: updated device
- *
- ******************************************************************************/
-void btm_ble_bgconn_cancel_if_disconnected(const RawAddress& bd_addr) {
- if (!btm_cb.ble_ctr_cb.is_connection_state_connecting()) return;
+ btm_ble_create_conn_cancel();
- auto map_it = background_connections.find(bd_addr);
- if (map_it != background_connections.end()) {
- BackgroundConnection* connection = &map_it->second;
- if (!connection->in_controller_wl && !connection->pending_removal &&
- !BTM_IsAclConnectionUp(bd_addr, BT_TRANSPORT_LE)) {
- btm_ble_stop_auto_conn();
- }
- }
+ btm_cb.ble_ctr_cb.wl_state &= ~BTM_BLE_WL_INIT;
+ return true;
}
/*******************************************************************************
@@ -449,10 +433,7 @@ void btm_ble_bgconn_cancel_if_disconnected(const RawAddress& bd_addr) {
*
******************************************************************************/
bool btm_ble_suspend_bg_conn(void) {
- if (bluetooth::shim::is_gd_acl_enabled()) {
- LOG_DEBUG("Gd acl_manager handles sync of background connections");
- return true;
- }
+ BTM_TRACE_EVENT("%s", __func__);
return btm_ble_stop_auto_conn();
}
@@ -468,135 +449,49 @@ bool btm_ble_suspend_bg_conn(void) {
* Returns none.
*
******************************************************************************/
-bool btm_ble_resume_bg_conn(void) {
- if (bluetooth::shim::is_gd_acl_enabled()) {
- LOG_DEBUG("Gd acl_manager handles sync of background connections");
- return true;
- }
- return btm_ble_start_auto_conn();
-}
-
-bool BTM_BackgroundConnectAddressKnown(const RawAddress& address) {
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(address);
-
- // not a known device, or a classic device, we assume public address
- if (p_dev_rec == NULL || (p_dev_rec->device_type & BT_DEVICE_TYPE_BLE) == 0)
- return true;
-
- // bonded device with identity address known
- if (!p_dev_rec->ble.identity_address_with_type.bda.IsEmpty()) {
- return true;
- }
-
- // Public address, Random Static, or Random Non-Resolvable Address known
- if (p_dev_rec->ble.ble_addr_type == BLE_ADDR_PUBLIC ||
- !BTM_BLE_IS_RESOLVE_BDA(address)) {
- return true;
- }
-
- // Only Resolvable Private Address (RPA) is known, we don't allow it into
- // the background connection procedure.
- return false;
-}
-
-bool BTM_SetLeConnectionModeToFast() {
- VLOG(2) << __func__;
- tBTM_BLE_CB* p_cb = &btm_cb.ble_ctr_cb;
- if ((p_cb->scan_int == BTM_BLE_SCAN_PARAM_UNDEF &&
- p_cb->scan_win == BTM_BLE_SCAN_PARAM_UNDEF) ||
- (p_cb->scan_int == BTM_BLE_SCAN_SLOW_INT_1 &&
- p_cb->scan_win == BTM_BLE_SCAN_SLOW_WIN_1)) {
- p_cb->scan_int = BTM_BLE_SCAN_FAST_INT;
- p_cb->scan_win = BTM_BLE_SCAN_FAST_WIN;
- return true;
- }
- return false;
-}
+bool btm_ble_resume_bg_conn(void) { return btm_ble_start_auto_conn(); }
-void BTM_SetLeConnectionModeToSlow() {
- VLOG(2) << __func__;
- tBTM_BLE_CB* p_cb = &btm_cb.ble_ctr_cb;
- if ((p_cb->scan_int == BTM_BLE_SCAN_PARAM_UNDEF &&
- p_cb->scan_win == BTM_BLE_SCAN_PARAM_UNDEF) ||
- (p_cb->scan_int == BTM_BLE_SCAN_FAST_INT &&
- p_cb->scan_win == BTM_BLE_SCAN_FAST_WIN)) {
- p_cb->scan_int = BTM_BLE_SCAN_SLOW_INT_1;
- p_cb->scan_win = BTM_BLE_SCAN_SLOW_WIN_1;
- }
-}
-
-/** Adds the device into acceptlist. Returns false if acceptlist is full and
+/** Adds the device into white list. Returns false if white list is full and
* device can't be added, true otherwise. */
-bool BTM_AcceptlistAdd(const RawAddress& address) {
- if (!controller_get_interface()->supports_ble()) {
- LOG_WARN("Controller does not support Le");
- return false;
- }
-
- if (bluetooth::shim::is_gd_acl_enabled()) {
- if (acl_check_and_clear_ignore_auto_connect_after_disconnect(address)) {
- LOG_WARN(
- "Unexpectedly found device address already in ignore auto connect "
- "device:%s",
- PRIVATE_ADDRESS(address));
- }
- return bluetooth::shim::ACL_AcceptLeConnectionFrom(
- convert_to_address_with_type(address, btm_find_dev(address)),
- /* is_direct */ false);
- }
+bool BTM_WhiteListAdd(const RawAddress& address) {
+ VLOG(1) << __func__ << ": " << address;
if (background_connections_count() ==
- controller_get_interface()->get_ble_acceptlist_size()) {
- LOG_ERROR("Unable to add device to acceptlist since it is full");
+ controller_get_interface()->get_ble_white_list_size()) {
+ BTM_TRACE_ERROR("%s Whitelist full, unable to add device", __func__);
return false;
}
- if (btm_cb.ble_ctr_cb.wl_state & BTM_BLE_ACCEPTLIST_INIT) {
+ if (btm_cb.ble_ctr_cb.wl_state & BTM_BLE_WL_INIT) {
btm_ble_stop_auto_conn();
}
btm_add_dev_to_controller(true, address);
btm_ble_resume_bg_conn();
- LOG_DEBUG("Added to Le acceptlist device:%s", PRIVATE_ADDRESS(address));
return true;
}
-/** Removes the device from acceptlist */
-void BTM_AcceptlistRemove(const RawAddress& address) {
- if (!controller_get_interface()->supports_ble()) {
- LOG_WARN("Controller does not support Le");
- return;
- }
-
- if (bluetooth::shim::is_gd_acl_enabled()) {
- bluetooth::shim::ACL_IgnoreLeConnectionFrom(
- convert_to_address_with_type(address, btm_find_dev(address)));
- return;
- }
-
- if (btm_cb.ble_ctr_cb.wl_state & BTM_BLE_ACCEPTLIST_INIT) {
+/** Removes the device from white list */
+void BTM_WhiteListRemove(const RawAddress& address) {
+ VLOG(1) << __func__ << ": " << address;
+ if (btm_cb.ble_ctr_cb.wl_state & BTM_BLE_WL_INIT) {
btm_ble_stop_auto_conn();
}
btm_add_dev_to_controller(false, address);
btm_ble_resume_bg_conn();
- LOG_DEBUG("Removed from Le acceptlist device:%s", PRIVATE_ADDRESS(address));
}
-/** Clear the acceptlist, end any pending acceptlist connections */
-void BTM_AcceptlistClear() {
- if (!controller_get_interface()->supports_ble()) {
- LOG_WARN("Controller does not support Le");
- return;
- }
-
- if (bluetooth::shim::is_gd_acl_enabled()) {
- acl_clear_all_ignore_auto_connect_after_disconnect();
- bluetooth::shim::ACL_IgnoreAllLeConnections();
- return;
- }
+/** clear white list complete */
+void wl_clear_complete(uint8_t* p_data, uint16_t /* evt_len */) {
+ uint8_t status;
+ STREAM_TO_UINT8(status, p_data);
+ VLOG(2) << __func__ << ": status=" << loghex(status);
+}
+/** Clear the whitelist, end any pending whitelist connections */
+void BTM_WhiteListClear() {
+ VLOG(1) << __func__;
+ if (!controller_get_interface()->supports_ble()) return;
btm_ble_stop_auto_conn();
- btsnd_hcic_ble_clear_acceptlist(
- base::BindOnce(&acceptlist_clear_command_complete));
+ btsnd_hcic_ble_clear_white_list(base::BindOnce(&wl_clear_complete));
background_connections_clear();
- LOG_DEBUG("Cleared Le acceptlist");
}
diff --git a/stack/btm/btm_ble_bgconn.h b/stack/btm/btm_ble_bgconn.h
index cb0ac9469..407f5132b 100644
--- a/stack/btm/btm_ble_bgconn.h
+++ b/stack/btm/btm_ble_bgconn.h
@@ -18,15 +18,18 @@
#include "types/raw_address.h"
-/** Adds the device into acceptlist. Returns false if acceptlist is full and
+/** Adds the device into white list. Returns false if white list is full and
* device can't be added, true otherwise. */
-extern bool BTM_AcceptlistAdd(const RawAddress& address);
+extern bool BTM_WhiteListAdd(const RawAddress& address);
-/** Removes the device from acceptlist */
-extern void BTM_AcceptlistRemove(const RawAddress& address);
+/** Removes the device from white list */
+extern void BTM_WhiteListRemove(const RawAddress& address);
-/** Clear the acceptlist, end any pending acceptlist connections */
-extern void BTM_AcceptlistClear();
+/** Get max white list size supports of the Bluetooth controller */
+extern uint8_t BTM_GetWhiteListSize();
+
+/** Clear the whitelist, end any pending whitelist connections */
+extern void BTM_WhiteListClear();
/* Use fast scan window/interval for LE connection establishment.
* This does not send any requests to controller, instead it changes the
diff --git a/stack/acl/btm_ble_connection_establishment.cc b/stack/btm/btm_ble_connection_establishment.cc
index cec64146c..7582727fb 100644
--- a/stack/acl/btm_ble_connection_establishment.cc
+++ b/stack/btm/btm_ble_connection_establishment.cc
@@ -19,39 +19,38 @@
#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
-#include <bitset>
-
#include "bt_types.h"
#include "btm_int.h"
#include "common/metrics.h"
#include "device/include/controller.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_ble_int.h"
+#include "l2c_int.h"
#include "stack/gatt/connection_manager.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/ble_acl_interface.h"
-#include "stack/include/ble_hci_link_interface.h"
#include "stack/include/hcimsgs.h"
-#include "stack/include/l2cap_hci_link_interface.h"
-#include "stack/include/stack_metrics_logging.h"
-
-extern tBTM_CB btm_cb;
extern void btm_ble_advertiser_notify_terminated_legacy(
uint8_t status, uint16_t connection_handle);
-extern bool btm_ble_init_pseudo_addr(tBTM_SEC_DEV_REC* p_dev_rec,
- const RawAddress& new_pseudo_addr);
+/** This function get BLE connection state */
+tBTM_BLE_CONN_ST btm_ble_get_conn_st(void) {
+ return btm_cb.ble_ctr_cb.conn_state;
+}
+
+/** This function set BLE connection state */
+void btm_ble_set_conn_st(tBTM_BLE_CONN_ST new_st) {
+ btm_cb.ble_ctr_cb.conn_state = new_st;
+
+ if (new_st == BLE_CONNECTING)
+ btm_ble_set_topology_mask(BTM_BLE_STATE_INIT_BIT);
+ else
+ btm_ble_clear_topology_mask(BTM_BLE_STATE_INIT_BIT);
+}
+
void btm_send_hci_create_connection(
uint16_t scan_int, uint16_t scan_win, uint8_t init_filter_policy,
uint8_t addr_type_peer, const RawAddress& bda_peer, uint8_t addr_type_own,
uint16_t conn_int_min, uint16_t conn_int_max, uint16_t conn_latency,
uint16_t conn_timeout, uint16_t min_ce_len, uint16_t max_ce_len,
uint8_t initiating_phys) {
- ASSERT_LOG(!bluetooth::shim::is_gd_acl_enabled(),
- "When gd_acl enabled this code path should not be exercised");
-
if (controller_get_interface()->supports_ble_extended_advertising()) {
EXT_CONN_PHY_CFG phy_cfg[3]; // maximum three phys
@@ -83,79 +82,41 @@ void btm_send_hci_create_connection(
conn_timeout, min_ce_len, max_ce_len);
}
- btm_cb.ble_ctr_cb.set_connection_state_connecting();
- btm_ble_set_topology_mask(BTM_BLE_STATE_INIT_BIT);
+ btm_ble_set_conn_st(BLE_CONNECTING);
}
/** LE connection complete. */
-void btm_ble_create_ll_conn_complete(tHCI_STATUS status) {
+void btm_ble_create_ll_conn_complete(uint8_t status) {
if (status == HCI_SUCCESS) return;
LOG(WARNING) << "LE Create Connection attempt failed, status="
- << hci_error_code_text(status);
+ << loghex(status);
if (status == HCI_ERR_COMMAND_DISALLOWED) {
- btm_cb.ble_ctr_cb.set_connection_state_connecting();
- btm_ble_set_topology_mask(BTM_BLE_STATE_INIT_BIT);
+ btm_ble_set_conn_st(BLE_CONNECTING);
LOG(ERROR) << "LE Create Connection - command disallowed";
} else {
- btm_cb.ble_ctr_cb.set_connection_state_idle();
- btm_ble_clear_topology_mask(BTM_BLE_STATE_INIT_BIT);
+ btm_ble_set_conn_st(BLE_CONN_IDLE);
btm_ble_update_mode_operation(HCI_ROLE_UNKNOWN, NULL, status);
}
}
-bool maybe_resolve_address(RawAddress* bda, tBLE_ADDR_TYPE* bda_type) {
- bool is_in_security_db = false;
- tBLE_ADDR_TYPE peer_addr_type = *bda_type;
- bool addr_is_rpa =
- (peer_addr_type == BLE_ADDR_RANDOM && BTM_BLE_IS_RESOLVE_BDA(*bda));
-
- /* We must translate whatever address we received into the "pseudo" address.
- * i.e. if we bonded with device that was using RPA for first connection,
- * "pseudo" address is equal to this RPA. If it later decides to use Public
- * address, or Random Static Address, we convert it into the "pseudo"
- * address here. */
- if (!addr_is_rpa || peer_addr_type & BLE_ADDR_TYPE_ID_BIT) {
- is_in_security_db = btm_identity_addr_to_random_pseudo(bda, bda_type, true);
- }
-
- /* possiblly receive connection complete with resolvable random while
- the device has been paired */
- if (!is_in_security_db && addr_is_rpa) {
- tBTM_SEC_DEV_REC* match_rec = btm_ble_resolve_random_addr(*bda);
- if (match_rec) {
- LOG(INFO) << __func__ << ": matched and resolved random address";
- is_in_security_db = true;
- match_rec->ble.active_addr_type = tBTM_SEC_BLE::BTM_BLE_ADDR_RRA;
- match_rec->ble.cur_rand_addr = *bda;
- if (!btm_ble_init_pseudo_addr(match_rec, *bda)) {
- /* assign the original address to be the current report address */
- *bda = match_rec->ble.pseudo_addr;
- *bda_type = match_rec->ble.ble_addr_type;
- } else {
- *bda = match_rec->bd_addr;
- }
- } else {
- LOG(INFO) << __func__ << ": unable to match and resolve random address";
- }
- }
- return is_in_security_db;
-}
-
/** LE connection complete. */
void btm_ble_conn_complete(uint8_t* p, UNUSED_ATTR uint16_t evt_len,
bool enhanced) {
+#if (BLE_PRIVACY_SPT == TRUE)
+ uint8_t peer_addr_type;
+#endif
RawAddress local_rpa, peer_rpa;
- uint8_t raw_role, status;
- tBLE_ADDR_TYPE bda_type;
+ uint8_t role, status, bda_type;
uint16_t handle;
RawAddress bda;
uint16_t conn_interval, conn_latency, conn_timeout;
+ bool match = false;
STREAM_TO_UINT8(status, p);
STREAM_TO_UINT16(handle, p);
- STREAM_TO_UINT8(raw_role, p);
+ STREAM_TO_UINT8(role, p);
STREAM_TO_UINT8(bda_type, p);
STREAM_TO_BDADDR(bda, p);
if (enhanced) {
@@ -172,56 +133,107 @@ void btm_ble_conn_complete(uint8_t* p, UNUSED_ATTR uint16_t evt_len,
: android::bluetooth::hci::BLE_EVT_CONN_COMPLETE_EVT;
if (status == HCI_SUCCESS) {
- tBLE_ADDR_TYPE peer_addr_type = bda_type;
- bool is_in_security_db = maybe_resolve_address(&bda, &bda_type);
+#if (BLE_PRIVACY_SPT == TRUE)
+ peer_addr_type = bda_type;
+ bool addr_is_rpa =
+ (peer_addr_type == BLE_ADDR_RANDOM && BTM_BLE_IS_RESOLVE_BDA(bda));
+
+ /* We must translate whatever address we received into the "pseudo" address.
+ * i.e. if we bonded with device that was using RPA for first connection,
+ * "pseudo" address is equal to this RPA. If it later decides to use Public
+ * address, or Random Static Address, we convert it into the "pseudo"
+ * address here. */
+ if (!addr_is_rpa || peer_addr_type & BLE_ADDR_TYPE_ID_BIT) {
+ match = btm_identity_addr_to_random_pseudo(&bda, &bda_type, true);
+ }
- // Log for the HCI success case after maybe resolving Bluetooth address
- log_link_layer_connection_event(
+ /* possiblly receive connection complete with resolvable random while
+ the device has been paired */
+ if (!match && addr_is_rpa) {
+ tBTM_SEC_DEV_REC* match_rec = btm_ble_resolve_random_addr(bda);
+ if (match_rec) {
+ LOG(INFO) << __func__ << ": matched and resolved random address";
+ match = true;
+ match_rec->ble.active_addr_type = BTM_BLE_ADDR_RRA;
+ match_rec->ble.cur_rand_addr = bda;
+ if (!btm_ble_init_pseudo_addr(match_rec, bda)) {
+ /* assign the original address to be the current report address */
+ bda = match_rec->ble.pseudo_addr;
+ bda_type = match_rec->ble.ble_addr_type;
+ } else {
+ bda = match_rec->bd_addr;
+ }
+ } else {
+ LOG(INFO) << __func__ << ": unable to match and resolve random address";
+ }
+ }
+#endif
+ // Log for the HCI success case after resolving Bluetooth address
+ bluetooth::common::LogLinkLayerConnectionEvent(
&bda, handle, android::bluetooth::DIRECTION_UNKNOWN,
android::bluetooth::LINK_TYPE_ACL, android::bluetooth::hci::CMD_UNKNOWN,
android::bluetooth::hci::EVT_BLE_META, hci_ble_event, status,
android::bluetooth::hci::STATUS_UNKNOWN);
- tBLE_BD_ADDR address_with_type{.bda = bda, .type = bda_type};
- tHCI_ROLE role = to_hci_role(raw_role);
+ if (role == HCI_ROLE_MASTER) {
+ btm_ble_set_conn_st(BLE_CONN_IDLE);
+ }
+
+ connection_manager::on_connection_complete(bda);
+ btm_ble_connected(bda, handle, HCI_ENCRYPT_MODE_DISABLED, role, bda_type,
+ match);
+
+ l2cble_conn_comp(handle, role, bda, bda_type, conn_interval, conn_latency,
+ conn_timeout);
+
+#if (BLE_PRIVACY_SPT == TRUE)
if (enhanced) {
- acl_ble_enhanced_connection_complete(
- address_with_type, handle, role, is_in_security_db, conn_interval,
- conn_latency, conn_timeout, local_rpa, peer_rpa, peer_addr_type);
+ btm_ble_refresh_local_resolvable_private_addr(bda, local_rpa);
- } else {
- acl_ble_connection_complete(address_with_type, handle, role,
- is_in_security_db, conn_interval,
- conn_latency, conn_timeout);
+ if (peer_addr_type & BLE_ADDR_TYPE_ID_BIT)
+ btm_ble_refresh_peer_resolvable_private_addr(bda, peer_rpa,
+ BLE_ADDR_RANDOM);
}
+#endif
} else {
- log_link_layer_connection_event(
+ // Log for non HCI success case
+ bluetooth::common::LogLinkLayerConnectionEvent(
&bda, handle, android::bluetooth::DIRECTION_UNKNOWN,
android::bluetooth::LINK_TYPE_ACL, android::bluetooth::hci::CMD_UNKNOWN,
android::bluetooth::hci::EVT_BLE_META, hci_ble_event, status,
android::bluetooth::hci::STATUS_UNKNOWN);
- tBLE_BD_ADDR address_with_type{.bda = bda, .type = bda_type};
- acl_ble_connection_fail(address_with_type, handle, enhanced,
- static_cast<tHCI_STATUS>(status));
+ role = HCI_ROLE_UNKNOWN;
+ if (status != HCI_ERR_ADVERTISING_TIMEOUT) {
+ btm_ble_set_conn_st(BLE_CONN_IDLE);
+#if (BLE_PRIVACY_SPT == TRUE)
+ btm_ble_disable_resolving_list(BTM_BLE_RL_INIT, true);
+#endif
+ } else {
+#if (BLE_PRIVACY_SPT == TRUE)
+ btm_cb.ble_ctr_cb.inq_var.adv_mode = BTM_BLE_ADV_DISABLE;
+ btm_ble_disable_resolving_list(BTM_BLE_RL_ADV, true);
+#endif
+ }
}
+
+ btm_ble_update_mode_operation(role, &bda, status);
+
+ if (role == HCI_ROLE_SLAVE)
+ btm_ble_advertiser_notify_terminated_legacy(status, handle);
}
void btm_ble_create_conn_cancel() {
- ASSERT_LOG(!bluetooth::shim::is_gd_acl_enabled(),
- "When gd_acl enabled this code path should not be exercised");
-
btsnd_hcic_ble_create_conn_cancel();
- btm_cb.ble_ctr_cb.set_connection_state_cancelled();
- btm_ble_clear_topology_mask(BTM_BLE_STATE_INIT_BIT);
+ btm_ble_set_conn_st(BLE_CONN_CANCEL);
}
void btm_ble_create_conn_cancel_complete(uint8_t* p) {
uint8_t status;
STREAM_TO_UINT8(status, p);
if (status != HCI_SUCCESS) {
- // Only log errors to prevent log spam due to acceptlist connections
- log_link_layer_connection_event(
+ // Only log errors to prevent log spam due to whitelist connections
+ bluetooth::common::LogLinkLayerConnectionEvent(
nullptr, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_OUTGOING,
android::bluetooth::LINK_TYPE_ACL,
@@ -235,11 +247,9 @@ void btm_ble_create_conn_cancel_complete(uint8_t* p) {
/* This is a sign that logic around keeping connection state is broken */
LOG(ERROR)
<< "Attempt to cancel LE connection, when no connection is pending.";
- if (btm_cb.ble_ctr_cb.is_connection_state_cancelled()) {
- btm_cb.ble_ctr_cb.set_connection_state_idle();
- btm_ble_clear_topology_mask(BTM_BLE_STATE_INIT_BIT);
- btm_ble_update_mode_operation(HCI_ROLE_UNKNOWN, nullptr,
- static_cast<tHCI_STATUS>(status));
+ if (btm_ble_get_conn_st() == BLE_CONN_CANCEL) {
+ btm_ble_set_conn_st(BLE_CONN_IDLE);
+ btm_ble_update_mode_operation(HCI_ROLE_UNKNOWN, nullptr, status);
}
}
}
diff --git a/stack/btm/btm_ble_cont_energy.cc b/stack/btm/btm_ble_cont_energy.cc
index e23d63cd5..23fe70910 100644
--- a/stack/btm/btm_ble_cont_energy.cc
+++ b/stack/btm/btm_ble_cont_energy.cc
@@ -20,15 +20,12 @@
#include "bt_target.h"
#include "bt_types.h"
+#include "bt_utils.h"
#include "btm_ble_api.h"
#include "btm_int.h"
#include "btu.h"
#include "hcidefs.h"
#include "hcimsgs.h"
-#include "stack/btm/btm_int_types.h"
-#include "utils/include/bt_utils.h"
-
-extern tBTM_CB btm_cb;
tBTM_BLE_ENERGY_INFO_CB ble_energy_info_cb;
@@ -43,9 +40,10 @@ tBTM_BLE_ENERGY_INFO_CB ble_energy_info_cb;
* Returns void
*
******************************************************************************/
-static void btm_ble_cont_energy_cmpl_cback(tBTM_VSC_CMPL* p_params) {
+void btm_ble_cont_energy_cmpl_cback(tBTM_VSC_CMPL* p_params) {
uint8_t* p = p_params->p_param_buf;
uint16_t len = p_params->param_len;
+ uint8_t status = 0;
uint32_t total_tx_time = 0, total_rx_time = 0, total_idle_time = 0,
total_energy_used = 0;
@@ -54,9 +52,7 @@ static void btm_ble_cont_energy_cmpl_cback(tBTM_VSC_CMPL* p_params) {
return;
}
- uint8_t raw_status;
- STREAM_TO_UINT8(raw_status, p);
- tHCI_STATUS status = to_hci_status_code(raw_status);
+ STREAM_TO_UINT8(status, p);
STREAM_TO_UINT32(total_tx_time, p);
STREAM_TO_UINT32(total_rx_time, p);
STREAM_TO_UINT32(total_idle_time, p);
@@ -68,8 +64,7 @@ static void btm_ble_cont_energy_cmpl_cback(tBTM_VSC_CMPL* p_params) {
if (NULL != ble_energy_info_cb.p_ener_cback)
ble_energy_info_cb.p_ener_cback(total_tx_time, total_rx_time,
- total_idle_time, total_energy_used,
- static_cast<tHCI_STATUS>(status));
+ total_idle_time, total_energy_used, status);
return;
}
diff --git a/stack/btm/btm_ble_gap.cc b/stack/btm/btm_ble_gap.cc
index 9f8f7b0b7..37cfeb592 100644
--- a/stack/btm/btm_ble_gap.cc
+++ b/stack/btm/btm_ble_gap.cc
@@ -25,46 +25,40 @@
#define LOG_TAG "bt_btm_ble"
#include <base/bind.h>
+#include <base/callback.h>
#include <base/strings/string_number_conversions.h>
-#include <cstdint>
+#include <stddef.h>
+#include <stdio.h>
+#include <string.h>
#include <list>
-#include <memory>
#include <vector>
-#include "common/time_util.h"
+#include "bt_types.h"
+#include "bt_utils.h"
+#include "btm_ble_api.h"
+#include "btm_int.h"
+#include "btu.h"
#include "device/include/controller.h"
-#include "main/shim/acl_api.h"
+#include "gap_api.h"
+#include "hcimsgs.h"
+#include "osi/include/osi.h"
+
+#include "advertise_data_parser.h"
+#include "btm_ble_int.h"
+#include "gatt_int.h"
+#include "gattdefs.h"
+#include "l2c_int.h"
+#include "osi/include/log.h"
+#include "common/time_util.h"
+
#include "main/shim/btm_api.h"
#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_ble_int_types.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/gatt/gatt_int.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/advertise_data_parser.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/gap_api.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcimsgs.h"
-#include "stack/include/inq_hci_link_interface.h"
-#include "types/raw_address.h"
-
-extern tBTM_CB btm_cb;
-
-extern void btm_inq_remote_name_timer_timeout(void* data);
-extern bool btm_ble_init_pseudo_addr(tBTM_SEC_DEV_REC* p_dev_rec,
- const RawAddress& new_pseudo_addr);
-extern bool btm_identity_addr_to_random_pseudo(RawAddress* bd_addr,
- uint8_t* p_addr_type,
- bool refresh);
-extern void btm_ble_batchscan_init(void);
-extern void btm_ble_adv_filter_init(void);
-extern void btm_clear_all_pending_le_entry(void);
-extern const tBLE_BD_ADDR convert_to_address_with_type(
- const RawAddress& bd_addr, const tBTM_SEC_DEV_REC* p_dev_rec);
+
+#define BTM_BLE_NAME_SHORT 0x01
+#define BTM_BLE_NAME_CMPL 0x02
+
+#define BTM_BLE_FILTER_TARGET_UNKNOWN 0xff
+#define BTM_BLE_POLICY_UNKNOWN 0xff
#define BTM_EXT_BLE_RMT_NAME_TIMEOUT_MS (30 * 1000)
#define MIN_ADV_LENGTH 2
@@ -72,7 +66,6 @@ extern const tBLE_BD_ADDR convert_to_address_with_type(
#define BTM_VSC_CHIP_CAPABILITY_RSP_LEN_L_RELEASE \
BTM_VSC_CHIP_CAPABILITY_RSP_LEN
#define BTM_VSC_CHIP_CAPABILITY_RSP_LEN_M_RELEASE 15
-#define BTM_VSC_CHIP_CAPABILITY_RSP_LEN_S_RELEASE 25
namespace {
@@ -95,14 +88,6 @@ class AdvertisingCache {
return items.front().data;
}
- bool Exist(uint8_t addr_type, const RawAddress& addr) {
- auto it = Find(addr_type, addr);
- if (it != items.end()) {
- return true;
- }
- return false;
- }
-
/* Append |data| for device |addr_type, addr| */
const std::vector<uint8_t>& Append(uint8_t addr_type, const RawAddress& addr,
std::vector<uint8_t> data) {
@@ -128,10 +113,6 @@ class AdvertisingCache {
}
}
- void ClearAll() {
- items.clear();
- }
-
private:
struct Item {
uint8_t addr_type;
@@ -176,7 +157,8 @@ void btm_ble_process_adv_pkt_cont(uint16_t evt_type, uint8_t addr_type,
uint8_t advertising_sid, int8_t tx_power,
int8_t rssi, uint16_t periodic_adv_int,
uint8_t data_len, uint8_t* data);
-static uint8_t btm_set_conn_mode_adv_init_addr(RawAddress& p_peer_addr_ptr,
+static uint8_t btm_set_conn_mode_adv_init_addr(tBTM_BLE_INQ_CB* p_cb,
+ RawAddress& p_peer_addr_ptr,
tBLE_ADDR_TYPE* p_peer_addr_type,
tBLE_ADDR_TYPE* p_own_addr_type);
static void btm_ble_stop_observe(void);
@@ -186,33 +168,30 @@ static void btm_ble_inquiry_timer_gap_limited_discovery_timeout(void* data);
static void btm_ble_inquiry_timer_timeout(void* data);
static void btm_ble_observer_timer_timeout(void* data);
-enum : uint8_t {
- BTM_BLE_NOT_SCANNING = 0x00,
- BTM_BLE_INQ_RESULT = 0x01,
- BTM_BLE_OBS_RESULT = 0x02,
-};
+#define BTM_BLE_INQ_RESULT 0x01
+#define BTM_BLE_OBS_RESULT 0x02
-static bool ble_evt_type_is_connectable(uint16_t evt_type) {
+bool ble_evt_type_is_connectable(uint16_t evt_type) {
return evt_type & (1 << BLE_EVT_CONNECTABLE_BIT);
}
-static bool ble_evt_type_is_scannable(uint16_t evt_type) {
+bool ble_evt_type_is_scannable(uint16_t evt_type) {
return evt_type & (1 << BLE_EVT_SCANNABLE_BIT);
}
-static bool ble_evt_type_is_directed(uint16_t evt_type) {
+bool ble_evt_type_is_directed(uint16_t evt_type) {
return evt_type & (1 << BLE_EVT_DIRECTED_BIT);
}
-static bool ble_evt_type_is_scan_resp(uint16_t evt_type) {
+bool ble_evt_type_is_scan_resp(uint16_t evt_type) {
return evt_type & (1 << BLE_EVT_SCAN_RESPONSE_BIT);
}
-static bool ble_evt_type_is_legacy(uint16_t evt_type) {
+bool ble_evt_type_is_legacy(uint16_t evt_type) {
return evt_type & (1 << BLE_EVT_LEGACY_BIT);
}
-static uint8_t ble_evt_type_data_status(uint16_t evt_type) {
+uint8_t ble_evt_type_data_status(uint16_t evt_type) {
return (evt_type >> 5) & 3;
}
@@ -222,11 +201,11 @@ constexpr uint8_t UNSUPPORTED = 255;
const uint8_t btm_le_state_combo_tbl[BTM_BLE_STATE_MAX][BTM_BLE_STATE_MAX] = {
{
/* single state support */
- HCI_LE_STATES_CONN_ADV_BIT, /* conn_adv */
- HCI_LE_STATES_INIT_BIT, /* init */
- HCI_LE_STATES_INIT_BIT, /* central */
- HCI_LE_STATES_PERIPHERAL_BIT, /* peripheral */
- UNSUPPORTED, /* todo: lo du dir adv, not covered ? */
+ HCI_LE_STATES_CONN_ADV_BIT, /* conn_adv */
+ HCI_LE_STATES_INIT_BIT, /* init */
+ HCI_LE_STATES_INIT_BIT, /* master */
+ HCI_LE_STATES_SLAVE_BIT, /* slave */
+ UNSUPPORTED, /* todo: lo du dir adv, not covered ? */
HCI_LE_STATES_HI_DUTY_DIR_ADV_BIT, /* hi duty dir adv */
HCI_LE_STATES_NON_CONN_ADV_BIT, /* non connectable adv */
HCI_LE_STATES_PASS_SCAN_BIT, /* passive scan */
@@ -237,8 +216,8 @@ const uint8_t btm_le_state_combo_tbl[BTM_BLE_STATE_MAX][BTM_BLE_STATE_MAX] = {
/* conn_adv =0 */
UNSUPPORTED, /* conn_adv */
HCI_LE_STATES_CONN_ADV_INIT_BIT, /* init: 32 */
- HCI_LE_STATES_CONN_ADV_CENTRAL_BIT, /* central: 35 */
- HCI_LE_STATES_CONN_ADV_PERIPHERAL_BIT, /* peripheral: 38,*/
+ HCI_LE_STATES_CONN_ADV_MASTER_BIT, /* master: 35 */
+ HCI_LE_STATES_CONN_ADV_SLAVE_BIT, /* slave: 38,*/
UNSUPPORTED, /* lo du dir adv */
UNSUPPORTED, /* hi duty dir adv */
UNSUPPORTED, /* non connectable adv */
@@ -248,69 +227,69 @@ const uint8_t btm_le_state_combo_tbl[BTM_BLE_STATE_MAX][BTM_BLE_STATE_MAX] = {
},
{
/* init */
- HCI_LE_STATES_CONN_ADV_INIT_BIT, /* conn_adv: 32 */
- UNSUPPORTED, /* init */
- HCI_LE_STATES_INIT_CENTRAL_BIT, /* central 28 */
- HCI_LE_STATES_INIT_CENTRAL_PERIPHERAL_BIT, /* peripheral 41 */
- HCI_LE_STATES_LO_DUTY_DIR_ADV_INIT_BIT, /* lo du dir adv 34 */
- HCI_LE_STATES_HI_DUTY_DIR_ADV_INIT_BIT, /* hi duty dir adv 33 */
- HCI_LE_STATES_NON_CONN_INIT_BIT, /* non connectable adv */
- HCI_LE_STATES_PASS_SCAN_INIT_BIT, /* passive scan */
- HCI_LE_STATES_ACTIVE_SCAN_INIT_BIT, /* active scan */
- HCI_LE_STATES_SCAN_ADV_INIT_BIT /* scanable adv */
+ HCI_LE_STATES_CONN_ADV_INIT_BIT, /* conn_adv: 32 */
+ UNSUPPORTED, /* init */
+ HCI_LE_STATES_INIT_MASTER_BIT, /* master 28 */
+ HCI_LE_STATES_INIT_MASTER_SLAVE_BIT, /* slave 41 */
+ HCI_LE_STATES_LO_DUTY_DIR_ADV_INIT_BIT, /* lo du dir adv 34 */
+ HCI_LE_STATES_HI_DUTY_DIR_ADV_INIT_BIT, /* hi duty dir adv 33 */
+ HCI_LE_STATES_NON_CONN_INIT_BIT, /* non connectable adv */
+ HCI_LE_STATES_PASS_SCAN_INIT_BIT, /* passive scan */
+ HCI_LE_STATES_ACTIVE_SCAN_INIT_BIT, /* active scan */
+ HCI_LE_STATES_SCAN_ADV_INIT_BIT /* scanable adv */
},
{
- /* central */
- HCI_LE_STATES_CONN_ADV_CENTRAL_BIT, /* conn_adv: 35 */
- HCI_LE_STATES_INIT_CENTRAL_BIT, /* init 28 */
- HCI_LE_STATES_INIT_CENTRAL_BIT, /* central 28 */
- HCI_LE_STATES_CONN_ADV_INIT_BIT, /* peripheral: 32 */
- HCI_LE_STATES_LO_DUTY_DIR_ADV_CENTRAL_BIT, /* lo duty cycle adv 37 */
- HCI_LE_STATES_HI_DUTY_DIR_ADV_CENTRAL_BIT, /* hi duty cycle adv 36 */
- HCI_LE_STATES_NON_CONN_ADV_CENTRAL_BIT, /* non connectable adv*/
- HCI_LE_STATES_PASS_SCAN_CENTRAL_BIT, /* passive scan */
- HCI_LE_STATES_ACTIVE_SCAN_CENTRAL_BIT, /* active scan */
- HCI_LE_STATES_SCAN_ADV_CENTRAL_BIT /* scanable adv */
+ /* master */
+ HCI_LE_STATES_CONN_ADV_MASTER_BIT, /* conn_adv: 35 */
+ HCI_LE_STATES_INIT_MASTER_BIT, /* init 28 */
+ HCI_LE_STATES_INIT_MASTER_BIT, /* master 28 */
+ HCI_LE_STATES_CONN_ADV_INIT_BIT, /* slave: 32 */
+ HCI_LE_STATES_LO_DUTY_DIR_ADV_MASTER_BIT, /* lo duty cycle adv 37 */
+ HCI_LE_STATES_HI_DUTY_DIR_ADV_MASTER_BIT, /* hi duty cycle adv 36 */
+ HCI_LE_STATES_NON_CONN_ADV_MASTER_BIT, /* non connectable adv*/
+ HCI_LE_STATES_PASS_SCAN_MASTER_BIT, /* passive scan */
+ HCI_LE_STATES_ACTIVE_SCAN_MASTER_BIT, /* active scan */
+ HCI_LE_STATES_SCAN_ADV_MASTER_BIT /* scanable adv */
},
{
- /* peripheral */
- HCI_LE_STATES_CONN_ADV_PERIPHERAL_BIT, /* conn_adv: 38,*/
- HCI_LE_STATES_INIT_CENTRAL_PERIPHERAL_BIT, /* init 41 */
- HCI_LE_STATES_INIT_CENTRAL_PERIPHERAL_BIT, /* central 41 */
- HCI_LE_STATES_CONN_ADV_PERIPHERAL_BIT, /* peripheral: 38,*/
- HCI_LE_STATES_LO_DUTY_DIR_ADV_PERIPHERAL_BIT, /* lo duty cycle adv 40 */
- HCI_LE_STATES_HI_DUTY_DIR_ADV_PERIPHERAL_BIT, /* hi duty cycle adv 39 */
- HCI_LE_STATES_NON_CONN_ADV_PERIPHERAL_BIT, /* non connectable adv */
- HCI_LE_STATES_PASS_SCAN_PERIPHERAL_BIT, /* passive scan */
- HCI_LE_STATES_ACTIVE_SCAN_PERIPHERAL_BIT, /* active scan */
- HCI_LE_STATES_SCAN_ADV_PERIPHERAL_BIT /* scanable adv */
+ /* slave */
+ HCI_LE_STATES_CONN_ADV_SLAVE_BIT, /* conn_adv: 38,*/
+ HCI_LE_STATES_INIT_MASTER_SLAVE_BIT, /* init 41 */
+ HCI_LE_STATES_INIT_MASTER_SLAVE_BIT, /* master 41 */
+ HCI_LE_STATES_CONN_ADV_SLAVE_BIT, /* slave: 38,*/
+ HCI_LE_STATES_LO_DUTY_DIR_ADV_SLAVE_BIT, /* lo duty cycle adv 40 */
+ HCI_LE_STATES_HI_DUTY_DIR_ADV_SLAVE_BIT, /* hi duty cycle adv 39 */
+ HCI_LE_STATES_NON_CONN_ADV_SLAVE_BIT, /* non connectable adv */
+ HCI_LE_STATES_PASS_SCAN_SLAVE_BIT, /* passive scan */
+ HCI_LE_STATES_ACTIVE_SCAN_SLAVE_BIT, /* active scan */
+ HCI_LE_STATES_SCAN_ADV_SLAVE_BIT /* scanable adv */
},
{
/* lo duty cycle adv */
- UNSUPPORTED, /* conn_adv: 38,*/
- HCI_LE_STATES_LO_DUTY_DIR_ADV_INIT_BIT, /* init 34 */
- HCI_LE_STATES_LO_DUTY_DIR_ADV_CENTRAL_BIT, /* central 37 */
- HCI_LE_STATES_LO_DUTY_DIR_ADV_PERIPHERAL_BIT, /* peripheral: 40 */
- UNSUPPORTED, /* lo duty cycle adv 40 */
- UNSUPPORTED, /* hi duty cycle adv 39 */
- UNSUPPORTED, /* non connectable adv */
+ UNSUPPORTED, /* conn_adv: 38,*/
+ HCI_LE_STATES_LO_DUTY_DIR_ADV_INIT_BIT, /* init 34 */
+ HCI_LE_STATES_LO_DUTY_DIR_ADV_MASTER_BIT, /* master 37 */
+ HCI_LE_STATES_LO_DUTY_DIR_ADV_SLAVE_BIT, /* slave: 40 */
+ UNSUPPORTED, /* lo duty cycle adv 40 */
+ UNSUPPORTED, /* hi duty cycle adv 39 */
+ UNSUPPORTED, /* non connectable adv */
UNSUPPORTED, /* TODO: passive scan, not covered? */
UNSUPPORTED, /* TODO: active scan, not covered? */
UNSUPPORTED /* scanable adv */
},
{
/* hi duty cycle adv */
- UNSUPPORTED, /* conn_adv: 38,*/
- HCI_LE_STATES_HI_DUTY_DIR_ADV_INIT_BIT, /* init 33 */
- HCI_LE_STATES_HI_DUTY_DIR_ADV_CENTRAL_BIT, /* central 36 */
- HCI_LE_STATES_HI_DUTY_DIR_ADV_PERIPHERAL_BIT, /* peripheral: 39*/
- UNSUPPORTED, /* lo duty cycle adv 40 */
- UNSUPPORTED, /* hi duty cycle adv 39 */
- UNSUPPORTED, /* non connectable adv */
- HCI_LE_STATES_HI_DUTY_DIR_ADV_PASS_SCAN_BIT, /* passive scan */
+ UNSUPPORTED, /* conn_adv: 38,*/
+ HCI_LE_STATES_HI_DUTY_DIR_ADV_INIT_BIT, /* init 33 */
+ HCI_LE_STATES_HI_DUTY_DIR_ADV_MASTER_BIT, /* master 36 */
+ HCI_LE_STATES_HI_DUTY_DIR_ADV_SLAVE_BIT, /* slave: 39*/
+ UNSUPPORTED, /* lo duty cycle adv 40 */
+ UNSUPPORTED, /* hi duty cycle adv 39 */
+ UNSUPPORTED, /* non connectable adv */
+ HCI_LE_STATES_HI_DUTY_DIR_ADV_PASS_SCAN_BIT, /* passive scan */
HCI_LE_STATES_HI_DUTY_DIR_ADV_ACTIVE_SCAN_BIT, /* active scan */
UNSUPPORTED /* scanable adv */
},
@@ -318,8 +297,8 @@ const uint8_t btm_le_state_combo_tbl[BTM_BLE_STATE_MAX][BTM_BLE_STATE_MAX] = {
/* non connectable adv */
UNSUPPORTED, /* conn_adv: */
HCI_LE_STATES_NON_CONN_INIT_BIT, /* init */
- HCI_LE_STATES_NON_CONN_ADV_CENTRAL_BIT, /* central */
- HCI_LE_STATES_NON_CONN_ADV_PERIPHERAL_BIT, /* peripheral: */
+ HCI_LE_STATES_NON_CONN_ADV_MASTER_BIT, /* master */
+ HCI_LE_STATES_NON_CONN_ADV_SLAVE_BIT, /* slave: */
UNSUPPORTED, /* lo duty cycle adv */
UNSUPPORTED, /* hi duty cycle adv */
UNSUPPORTED, /* non connectable adv */
@@ -331,8 +310,8 @@ const uint8_t btm_le_state_combo_tbl[BTM_BLE_STATE_MAX][BTM_BLE_STATE_MAX] = {
/* passive scan */
HCI_LE_STATES_CONN_ADV_PASS_SCAN_BIT, /* conn_adv: */
HCI_LE_STATES_PASS_SCAN_INIT_BIT, /* init */
- HCI_LE_STATES_PASS_SCAN_CENTRAL_BIT, /* central */
- HCI_LE_STATES_PASS_SCAN_PERIPHERAL_BIT, /* peripheral: */
+ HCI_LE_STATES_PASS_SCAN_MASTER_BIT, /* master */
+ HCI_LE_STATES_PASS_SCAN_SLAVE_BIT, /* slave: */
UNSUPPORTED, /* lo duty cycle adv */
HCI_LE_STATES_HI_DUTY_DIR_ADV_PASS_SCAN_BIT, /* hi duty cycle adv */
HCI_LE_STATES_NON_CONN_ADV_PASS_SCAN_BIT, /* non connectable adv */
@@ -344,8 +323,8 @@ const uint8_t btm_le_state_combo_tbl[BTM_BLE_STATE_MAX][BTM_BLE_STATE_MAX] = {
/* active scan */
HCI_LE_STATES_CONN_ADV_ACTIVE_SCAN_BIT, /* conn_adv: */
HCI_LE_STATES_ACTIVE_SCAN_INIT_BIT, /* init */
- HCI_LE_STATES_ACTIVE_SCAN_CENTRAL_BIT, /* central */
- HCI_LE_STATES_ACTIVE_SCAN_PERIPHERAL_BIT, /* peripheral: */
+ HCI_LE_STATES_ACTIVE_SCAN_MASTER_BIT, /* master */
+ HCI_LE_STATES_ACTIVE_SCAN_SLAVE_BIT, /* slave: */
UNSUPPORTED, /* lo duty cycle adv */
HCI_LE_STATES_HI_DUTY_DIR_ADV_ACTIVE_SCAN_BIT, /* hi duty cycle adv */
HCI_LE_STATES_NON_CONN_ADV_ACTIVE_SCAN_BIT, /* non connectable adv */
@@ -357,8 +336,8 @@ const uint8_t btm_le_state_combo_tbl[BTM_BLE_STATE_MAX][BTM_BLE_STATE_MAX] = {
/* scanable adv */
UNSUPPORTED, /* conn_adv: */
HCI_LE_STATES_SCAN_ADV_INIT_BIT, /* init */
- HCI_LE_STATES_SCAN_ADV_CENTRAL_BIT, /* central */
- HCI_LE_STATES_SCAN_ADV_PERIPHERAL_BIT, /* peripheral: */
+ HCI_LE_STATES_SCAN_ADV_MASTER_BIT, /* master */
+ HCI_LE_STATES_SCAN_ADV_SLAVE_BIT, /* slave: */
UNSUPPORTED, /* lo duty cycle adv */
UNSUPPORTED, /* hi duty cycle adv */
UNSUPPORTED, /* non connectable adv */
@@ -376,13 +355,59 @@ inline bool BTM_LE_STATES_SUPPORTED(const uint8_t* x, uint8_t bit_num) {
/*******************************************************************************
*
+ * Function BTM_BleUpdateAdvFilterPolicy
+ *
+ * Description This function update the filter policy of advertiser.
+ *
+ * Parameter adv_policy: advertising filter policy
+ *
+ * Return void
+ ******************************************************************************/
+void BTM_BleUpdateAdvFilterPolicy(tBTM_BLE_AFP adv_policy) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_BleUpdateAdvFilterPolicy(adv_policy);
+ }
+
+ tBTM_BLE_INQ_CB* p_cb = &btm_cb.ble_ctr_cb.inq_var;
+ tBLE_ADDR_TYPE init_addr_type = BLE_ADDR_PUBLIC;
+ RawAddress adv_address = RawAddress::kEmpty;
+ uint8_t adv_mode = p_cb->adv_mode;
+
+ BTM_TRACE_EVENT("BTM_BleUpdateAdvFilterPolicy");
+
+ if (!controller_get_interface()->supports_ble()) return;
+
+ if (p_cb->afp != adv_policy) {
+ p_cb->afp = adv_policy;
+
+ /* if adv active, stop and restart */
+ btm_ble_stop_adv();
+
+ if (p_cb->connectable_mode & BTM_BLE_CONNECTABLE)
+ p_cb->evt_type = btm_set_conn_mode_adv_init_addr(
+ p_cb, adv_address, &init_addr_type, &p_cb->adv_addr_type);
+
+ btsnd_hcic_ble_write_adv_params(
+ (uint16_t)(p_cb->adv_interval_min ? p_cb->adv_interval_min
+ : BTM_BLE_GAP_ADV_SLOW_INT),
+ (uint16_t)(p_cb->adv_interval_max ? p_cb->adv_interval_max
+ : BTM_BLE_GAP_ADV_SLOW_INT),
+ p_cb->evt_type, p_cb->adv_addr_type, init_addr_type, adv_address,
+ p_cb->adv_chnl_map, p_cb->afp);
+
+ if (adv_mode == BTM_BLE_ADV_ENABLE) btm_ble_start_adv();
+ }
+}
+
+/*******************************************************************************
+ *
* Function BTM_BleObserve
*
* Description This procedure keep the device listening for advertising
* events from a broadcast device.
*
* Parameters start: start or stop observe.
- * acceptlist: use acceptlist in observer mode or not.
+ * white_list: use white list in observer mode or not.
*
* Returns void
*
@@ -403,14 +428,15 @@ tBTM_STATUS BTM_BleObserve(bool start, uint8_t duration,
uint32_t scan_window =
!p_inq->scan_window ? BTM_BLE_GAP_DISC_SCAN_WIN : p_inq->scan_window;
- BTM_TRACE_EVENT("%s : scan_type:%d, %d, %d", __func__, p_inq->scan_type,
- p_inq->scan_interval, p_inq->scan_window);
+ BTM_TRACE_EVENT("%s : scan_type:%d, %d, %d", __func__,
+ btm_cb.btm_inq_vars.scan_type, p_inq->scan_interval,
+ p_inq->scan_window);
if (!controller_get_interface()->supports_ble()) return BTM_ILLEGAL_VALUE;
if (start) {
/* shared inquiry database, do not allow observe if any inquiry is active */
- if (btm_cb.ble_ctr_cb.is_ble_observe_active()) {
+ if (BTM_BLE_IS_OBS_ACTIVE(btm_cb.ble_ctr_cb.scan_activity)) {
BTM_TRACE_ERROR("%s Observe Already Active", __func__);
return status;
}
@@ -420,25 +446,27 @@ tBTM_STATUS BTM_BleObserve(bool start, uint8_t duration,
status = BTM_CMD_STARTED;
/* scan is not started */
- if (!btm_cb.ble_ctr_cb.is_ble_scan_active()) {
+ if (!BTM_BLE_IS_SCAN_ACTIVE(btm_cb.ble_ctr_cb.scan_activity)) {
/* allow config of scan type */
- cache.ClearAll();
p_inq->scan_type = (p_inq->scan_type == BTM_BLE_SCAN_MODE_NONE)
? BTM_BLE_SCAN_MODE_ACTI
: p_inq->scan_type;
- /* assume observe always not using acceptlist */
+/* assume observe always not using white list */
+#if (defined BLE_PRIVACY_SPT && BLE_PRIVACY_SPT == TRUE)
/* enable resolving list */
btm_ble_enable_resolving_list_for_platform(BTM_BLE_RL_SCAN);
+#endif
btm_send_hci_set_scan_params(
p_inq->scan_type, (uint16_t)scan_interval, (uint16_t)scan_window,
btm_cb.ble_ctr_cb.addr_mgnt_cb.own_addr_type, BTM_BLE_DEFAULT_SFP);
- btm_ble_start_scan();
+ p_inq->scan_duplicate_filter = BTM_BLE_DUPLICATE_DISABLE;
+ status = btm_ble_start_scan();
}
if (status == BTM_CMD_STARTED) {
- btm_cb.ble_ctr_cb.set_ble_observe_active();
+ btm_cb.ble_ctr_cb.scan_activity |= BTM_LE_OBSERVE_ACTIVE;
if (duration != 0) {
/* start observer timer */
uint64_t duration_ms = duration * 1000;
@@ -446,7 +474,7 @@ tBTM_STATUS BTM_BleObserve(bool start, uint8_t duration,
btm_ble_observer_timer_timeout, NULL);
}
}
- } else if (btm_cb.ble_ctr_cb.is_ble_observe_active()) {
+ } else if (BTM_BLE_IS_OBS_ACTIVE(btm_cb.ble_ctr_cb.scan_activity)) {
status = BTM_CMD_STARTED;
btm_ble_stop_observe();
} else {
@@ -457,60 +485,6 @@ tBTM_STATUS BTM_BleObserve(bool start, uint8_t duration,
}
#if (BLE_VND_INCLUDED == TRUE)
-
-static void btm_get_dynamic_audio_buffer_vsc_cmpl_cback(
- tBTM_VSC_CMPL* p_vsc_cmpl_params) {
- LOG(INFO) << __func__;
-
- if (p_vsc_cmpl_params->param_len < 1) {
- LOG(ERROR) << __func__
- << ": The length of returned parameters is less than 1";
- return;
- }
- uint8_t* p_event_param_buf = p_vsc_cmpl_params->p_param_buf;
- uint8_t status = 0xff;
- uint8_t opcode = 0xff;
- uint32_t codec_mask = 0xffffffff;
-
- // [Return Parameter] | [Size] | [Purpose]
- // Status | 1 octet | Command complete status
- // Dynamic_Audio_Buffer_opcode| 1 octet | 0x01 - Get buffer time
- // Audio_Codedc_Type_Supported| 4 octet | Bit masks for selected codec types
- // Audio_Codec_Buffer_Time | 192 octet| Default/Max/Min buffer time
- STREAM_TO_UINT8(status, p_event_param_buf);
- if (status != HCI_SUCCESS) {
- LOG(ERROR) << __func__
- << ": Fail to configure DFTB. status: " << loghex(status);
- return;
- }
-
- if (p_vsc_cmpl_params->param_len != 198) {
- LOG(FATAL) << __func__
- << ": The length of returned parameters is not equal to 198: "
- << std::to_string(p_vsc_cmpl_params->param_len);
- return;
- }
-
- STREAM_TO_UINT8(opcode, p_event_param_buf);
- LOG(INFO) << __func__ << ": opcode = " << loghex(opcode);
-
- if (opcode == 0x01) {
- STREAM_TO_UINT32(codec_mask, p_event_param_buf);
- LOG(INFO) << __func__ << ": codec_mask = " << loghex(codec_mask);
-
- for (int i = 0; i < BTM_CODEC_TYPE_MAX_RECORDS; i++) {
- STREAM_TO_UINT16(btm_cb.dynamic_audio_buffer_cb[i].default_buffer_time,
- p_event_param_buf);
- STREAM_TO_UINT16(btm_cb.dynamic_audio_buffer_cb[i].maximum_buffer_time,
- p_event_param_buf);
- STREAM_TO_UINT16(btm_cb.dynamic_audio_buffer_cb[i].minimum_buffer_time,
- p_event_param_buf);
- }
-
- LOG(INFO) << __func__ << ": Succeed to receive Media Tx Buffer.";
- }
-}
-
/*******************************************************************************
*
* Function btm_vsc_brcm_features_complete
@@ -522,6 +496,8 @@ static void btm_get_dynamic_audio_buffer_vsc_cmpl_cback(
******************************************************************************/
static void btm_ble_vendor_capability_vsc_cmpl_cback(
tBTM_VSC_CMPL* p_vcs_cplt_params) {
+ uint8_t status = 0xFF;
+ uint8_t* p;
BTM_TRACE_DEBUG("%s", __func__);
@@ -529,10 +505,8 @@ static void btm_ble_vendor_capability_vsc_cmpl_cback(
CHECK(p_vcs_cplt_params->opcode == HCI_BLE_VENDOR_CAP);
CHECK(p_vcs_cplt_params->param_len > 0);
- const uint8_t* p = p_vcs_cplt_params->p_param_buf;
- uint8_t raw_status;
- STREAM_TO_UINT8(raw_status, p);
- tHCI_STATUS status = to_hci_status_code(raw_status);
+ p = p_vcs_cplt_params->p_param_buf;
+ STREAM_TO_UINT8(status, p);
if (status != HCI_SUCCESS) {
BTM_TRACE_DEBUG("%s: Status = 0x%02x (0 is success)", __func__, status);
@@ -561,28 +535,6 @@ static void btm_ble_vendor_capability_vsc_cmpl_cback(
STREAM_TO_UINT8(btm_cb.cmn_ble_vsc_cb.extended_scan_support, p);
STREAM_TO_UINT8(btm_cb.cmn_ble_vsc_cb.debug_logging_supported, p);
}
-
- if (btm_cb.cmn_ble_vsc_cb.version_supported >=
- BTM_VSC_CHIP_CAPABILITY_S_VERSION) {
- if (p_vcs_cplt_params->param_len >=
- BTM_VSC_CHIP_CAPABILITY_RSP_LEN_S_RELEASE) {
- STREAM_TO_UINT8(
- btm_cb.cmn_ble_vsc_cb.le_address_generation_offloading_support, p);
- STREAM_TO_UINT32(
- btm_cb.cmn_ble_vsc_cb.a2dp_source_offload_capability_mask, p);
- STREAM_TO_UINT8(btm_cb.cmn_ble_vsc_cb.quality_report_support, p);
- STREAM_TO_UINT32(btm_cb.cmn_ble_vsc_cb.dynamic_audio_buffer_support, p);
-
- if (btm_cb.cmn_ble_vsc_cb.dynamic_audio_buffer_support != 0) {
- uint8_t param[3] = {0};
- uint8_t* p_param = param;
-
- UINT8_TO_STREAM(p_param, HCI_CONTROLLER_DAB_GET_BUFFER_TIME);
- BTM_VendorSpecificCommand(HCI_CONTROLLER_DAB, p_param - param, param,
- btm_get_dynamic_audio_buffer_vsc_cmpl_cback);
- }
- }
- }
btm_cb.cmn_ble_vsc_cb.values_read = true;
BTM_TRACE_DEBUG(
@@ -596,15 +548,17 @@ static void btm_ble_vendor_capability_vsc_cmpl_cback(
if (btm_cb.cmn_ble_vsc_cb.max_filter > 0) btm_ble_adv_filter_init();
+#if (BLE_PRIVACY_SPT == TRUE)
/* VS capability included and non-4.2 device */
if (btm_cb.cmn_ble_vsc_cb.max_irk_list_sz > 0 &&
controller_get_interface()->get_ble_resolving_list_max_size() == 0)
btm_ble_resolving_list_init(btm_cb.cmn_ble_vsc_cb.max_irk_list_sz);
+#endif /* (BLE_PRIVACY_SPT == TRUE) */
if (btm_cb.cmn_ble_vsc_cb.tot_scan_results_strg > 0) btm_ble_batchscan_init();
if (p_ctrl_le_feature_rd_cmpl_cback != NULL)
- p_ctrl_le_feature_rd_cmpl_cback(static_cast<tHCI_STATUS>(status));
+ p_ctrl_le_feature_rd_cmpl_cback(status);
}
#endif /* (BLE_VND_INCLUDED == TRUE) */
@@ -619,23 +573,14 @@ static void btm_ble_vendor_capability_vsc_cmpl_cback(
* Returns void
*
******************************************************************************/
-void BTM_BleGetVendorCapabilities(tBTM_BLE_VSC_CB* p_cmn_vsc_cb) {
+extern void BTM_BleGetVendorCapabilities(tBTM_BLE_VSC_CB* p_cmn_vsc_cb) {
+ BTM_TRACE_DEBUG("BTM_BleGetVendorCapabilities");
+
if (NULL != p_cmn_vsc_cb) {
*p_cmn_vsc_cb = btm_cb.cmn_ble_vsc_cb;
}
}
-void BTM_BleGetDynamicAudioBuffer(
- tBTM_BT_DYNAMIC_AUDIO_BUFFER_CB p_dynamic_audio_buffer_cb[]) {
- BTM_TRACE_DEBUG("BTM_BleGetDynamicAudioBuffer");
-
- if (NULL != p_dynamic_audio_buffer_cb) {
- for (int i = 0; i < 32; i++) {
- p_dynamic_audio_buffer_cb[i] = btm_cb.dynamic_audio_buffer_cb[i];
- }
- }
-}
-
/******************************************************************************
*
* Function BTM_BleReadControllerFeatures
@@ -649,7 +594,8 @@ void BTM_BleGetDynamicAudioBuffer(
*
******************************************************************************/
#if (BLE_VND_INCLUDED == TRUE)
-void BTM_BleReadControllerFeatures(tBTM_BLE_CTRL_FEATURES_CBACK* p_vsc_cback) {
+extern void BTM_BleReadControllerFeatures(
+ tBTM_BLE_CTRL_FEATURES_CBACK* p_vsc_cback) {
if (btm_cb.cmn_ble_vsc_cb.values_read) return;
BTM_TRACE_DEBUG("BTM_BleReadControllerFeatures");
@@ -659,12 +605,32 @@ void BTM_BleReadControllerFeatures(tBTM_BLE_CTRL_FEATURES_CBACK* p_vsc_cback) {
btm_ble_vendor_capability_vsc_cmpl_cback);
}
#else
-void BTM_BleReadControllerFeatures(
+extern void BTM_BleReadControllerFeatures(
UNUSED_ATTR tBTM_BLE_CTRL_FEATURES_CBACK* p_vsc_cback) {}
#endif
/*******************************************************************************
*
+ * Function BTM_BleEnableMixedPrivacyMode
+ *
+ * Description This function is called to enabled Mixed mode if privacy 1.2
+ * is applicable in controller.
+ *
+ * Parameters mixed_on: mixed mode to be used or not.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_BleEnableMixedPrivacyMode(bool mixed_on) {
+#if (BLE_PRIVACY_SPT == TRUE)
+ btm_cb.ble_ctr_cb.mixed_mode = mixed_on;
+
+/* TODO: send VSC to enabled mixed mode */
+#endif
+}
+
+/*******************************************************************************
+ *
* Function BTM_BleConfigPrivacy
*
* Description This function is called to enable or disable the privacy in
@@ -676,6 +642,7 @@ void BTM_BleReadControllerFeatures(
*
******************************************************************************/
bool BTM_BleConfigPrivacy(bool privacy_mode) {
+#if (BLE_PRIVACY_SPT == TRUE)
tBTM_BLE_CB* p_cb = &btm_cb.ble_ctr_cb;
BTM_TRACE_EVENT("%s", __func__);
@@ -700,18 +667,19 @@ bool BTM_BleConfigPrivacy(bool privacy_mode) {
* address in controller */
if (controller_get_interface()->supports_ble_privacy()) {
gap_ble_attr_value.addr_resolution = 1;
- p_cb->privacy_mode = BTM_PRIVACY_1_2;
+ /* check vendor specific capability */
+ p_cb->privacy_mode =
+ btm_cb.ble_ctr_cb.mixed_mode ? BTM_PRIVACY_MIXED : BTM_PRIVACY_1_2;
} else /* 4.1/4.0 controller */
p_cb->privacy_mode = BTM_PRIVACY_1_1;
}
GAP_BleAttrDBUpdate(GATT_UUID_GAP_CENTRAL_ADDR_RESOL, &gap_ble_attr_value);
- if (bluetooth::shim::is_gd_acl_enabled() ||
- bluetooth::shim::is_gd_l2cap_enabled()) {
- bluetooth::shim::ACL_ConfigureLePrivacy(privacy_mode);
- }
return true;
+#else
+ return false;
+#endif
}
/*******************************************************************************
@@ -724,7 +692,7 @@ bool BTM_BleConfigPrivacy(bool privacy_mode) {
* Returns Max multi adv instance count
*
******************************************************************************/
-uint8_t BTM_BleMaxMultiAdvInstanceCount(void) {
+extern uint8_t BTM_BleMaxMultiAdvInstanceCount(void) {
if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::BTM_BleMaxMultiAdvInstanceCount();
}
@@ -743,12 +711,43 @@ uint8_t BTM_BleMaxMultiAdvInstanceCount(void) {
*
******************************************************************************/
bool BTM_BleLocalPrivacyEnabled(void) {
+#if (BLE_PRIVACY_SPT == TRUE)
if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::BTM_BleLocalPrivacyEnabled();
}
return (btm_cb.ble_ctr_cb.privacy_mode != BTM_PRIVACY_NONE);
+#else
+ return false;
+#endif
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_BleSetConnectableMode
+ *
+ * Description This function is called to set BLE connectable mode for a
+ * peripheral device.
+ *
+ * Parameters conn_mode: directed connectable mode, or non-directed. It
+ * can be BTM_BLE_CONNECT_EVT,
+ * BTM_BLE_CONNECT_DIR_EVT or
+ * BTM_BLE_CONNECT_LO_DUTY_DIR_EVT
+ *
+ * Returns BTM_ILLEGAL_VALUE if controller does not support BLE.
+ * BTM_SUCCESS is status set successfully; otherwise failure.
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_BleSetConnectableMode(tBTM_BLE_CONN_MODE connectable_mode) {
+ tBTM_BLE_INQ_CB* p_cb = &btm_cb.ble_ctr_cb.inq_var;
+
+ BTM_TRACE_EVENT("%s connectable_mode = %d ", __func__, connectable_mode);
+ if (!controller_get_interface()->supports_ble()) return BTM_ILLEGAL_VALUE;
+
+ p_cb->directed_conn = connectable_mode;
+ return btm_ble_set_connectability(p_cb->connectable_mode);
}
+#if (BLE_PRIVACY_SPT == TRUE)
static bool is_resolving_list_bit_set(void* data, void* context) {
tBTM_SEC_DEV_REC* p_dev_rec = static_cast<tBTM_SEC_DEV_REC*>(data);
@@ -757,6 +756,7 @@ static bool is_resolving_list_bit_set(void* data, void* context) {
return true;
}
+#endif
/*******************************************************************************
*
@@ -768,27 +768,24 @@ static bool is_resolving_list_bit_set(void* data, void* context) {
*
******************************************************************************/
static uint8_t btm_set_conn_mode_adv_init_addr(
- RawAddress& p_peer_addr_ptr, tBLE_ADDR_TYPE* p_peer_addr_type,
- tBLE_ADDR_TYPE* p_own_addr_type) {
- tBTM_BLE_INQ_CB* p_cb = &btm_cb.ble_ctr_cb.inq_var;
+ tBTM_BLE_INQ_CB* p_cb, RawAddress& p_peer_addr_ptr,
+ tBLE_ADDR_TYPE* p_peer_addr_type, tBLE_ADDR_TYPE* p_own_addr_type) {
uint8_t evt_type;
+#if (BLE_PRIVACY_SPT == TRUE)
tBTM_SEC_DEV_REC* p_dev_rec;
+#endif
- if (p_cb->connectable_mode == BTM_BLE_NON_CONNECTABLE) {
- if (p_cb->scan_rsp) {
- evt_type = BTM_BLE_DISCOVER_EVT;
- } else {
- evt_type = BTM_BLE_NON_CONNECT_EVT;
- }
- } else {
- evt_type = BTM_BLE_CONNECT_EVT;
- }
+ evt_type =
+ (p_cb->connectable_mode == BTM_BLE_NON_CONNECTABLE)
+ ? ((p_cb->scan_rsp) ? BTM_BLE_DISCOVER_EVT : BTM_BLE_NON_CONNECT_EVT)
+ : BTM_BLE_CONNECT_EVT;
if (evt_type == BTM_BLE_CONNECT_EVT) {
evt_type = p_cb->directed_conn;
if (p_cb->directed_conn == BTM_BLE_CONNECT_DIR_EVT ||
p_cb->directed_conn == BTM_BLE_CONNECT_LO_DUTY_DIR_EVT) {
+#if (BLE_PRIVACY_SPT == TRUE)
/* for privacy 1.2, convert peer address as static, own address set as ID
* addr */
if (btm_cb.ble_ctr_cb.privacy_mode == BTM_PRIVACY_1_2 ||
@@ -797,8 +794,8 @@ static uint8_t btm_set_conn_mode_adv_init_addr(
if ((p_dev_rec = btm_find_or_alloc_dev(p_cb->direct_bda.bda)) != NULL &&
p_dev_rec->ble.in_controller_list & BTM_RESOLVING_LIST_BIT) {
btm_ble_enable_resolving_list(BTM_BLE_RL_ADV);
- p_peer_addr_ptr = p_dev_rec->ble.identity_address_with_type.bda;
- *p_peer_addr_type = p_dev_rec->ble.identity_address_with_type.type;
+ p_peer_addr_ptr = p_dev_rec->ble.identity_addr;
+ *p_peer_addr_type = p_dev_rec->ble.identity_addr_type;
*p_own_addr_type = BLE_ADDR_RANDOM_ID;
return evt_type;
}
@@ -807,6 +804,7 @@ static uint8_t btm_set_conn_mode_adv_init_addr(
btm_ble_disable_resolving_list(BTM_BLE_RL_ADV, true);
}
}
+#endif
/* direct adv mode does not have privacy, if privacy is not enabled */
*p_peer_addr_type = p_cb->direct_bda.type;
p_peer_addr_ptr = p_cb->direct_bda.bda;
@@ -815,6 +813,7 @@ static uint8_t btm_set_conn_mode_adv_init_addr(
}
/* undirect adv mode or non-connectable mode*/
+#if (BLE_PRIVACY_SPT == TRUE)
/* when privacy 1.2 privacy only mode is used, or mixed mode */
if ((btm_cb.ble_ctr_cb.privacy_mode == BTM_PRIVACY_1_2 &&
p_cb->afp != AP_SCAN_CONN_ALL) ||
@@ -826,8 +825,8 @@ static uint8_t btm_set_conn_mode_adv_init_addr(
* peer */
tBTM_SEC_DEV_REC* p_dev_rec =
static_cast<tBTM_SEC_DEV_REC*>(list_node(n));
- p_peer_addr_ptr = p_dev_rec->ble.identity_address_with_type.bda;
- *p_peer_addr_type = p_dev_rec->ble.identity_address_with_type.type;
+ p_peer_addr_ptr = p_dev_rec->ble.identity_addr;
+ *p_peer_addr_type = p_dev_rec->ble.identity_addr_type;
*p_own_addr_type = BLE_ADDR_RANDOM_ID;
} else {
@@ -841,6 +840,7 @@ static uint8_t btm_set_conn_mode_adv_init_addr(
else if (btm_cb.ble_ctr_cb.privacy_mode != BTM_PRIVACY_NONE) {
*p_own_addr_type = BLE_ADDR_RANDOM;
}
+#endif
/* if no privacy,do not set any peer address,*/
/* local address type go by global privacy setting */
@@ -854,19 +854,25 @@ static uint8_t btm_set_conn_mode_adv_init_addr(
void BTM_BleSetScanParams(uint32_t scan_interval, uint32_t scan_window,
tBLE_SCAN_MODE scan_mode,
base::Callback<void(uint8_t)> cb) {
- if (!controller_get_interface()->supports_ble()) {
- LOG_INFO("Controller does not support ble");
- return;
- }
+ tBTM_BLE_INQ_CB* p_cb = &btm_cb.ble_ctr_cb.inq_var;
+ uint32_t max_scan_interval;
+ uint32_t max_scan_window;
+
+ BTM_TRACE_EVENT("%s", __func__);
+ if (!controller_get_interface()->supports_ble()) return;
- uint32_t max_scan_interval = BTM_BLE_EXT_SCAN_INT_MAX;
- uint32_t max_scan_window = BTM_BLE_EXT_SCAN_WIN_MAX;
+ /* If not supporting extended scan support, use the older range for checking
+ */
if (btm_cb.cmn_ble_vsc_cb.extended_scan_support == 0) {
max_scan_interval = BTM_BLE_SCAN_INT_MAX;
max_scan_window = BTM_BLE_SCAN_WIN_MAX;
+ } else {
+ /* If supporting extended scan support, use the new extended range for
+ * checking */
+ max_scan_interval = BTM_BLE_EXT_SCAN_INT_MAX;
+ max_scan_window = BTM_BLE_EXT_SCAN_WIN_MAX;
}
- tBTM_BLE_INQ_CB* p_cb = &btm_cb.ble_ctr_cb.inq_var;
if (BTM_BLE_ISVALID_PARAM(scan_interval, BTM_BLE_SCAN_INT_MIN,
max_scan_interval) &&
BTM_BLE_ISVALID_PARAM(scan_window, BTM_BLE_SCAN_WIN_MIN,
@@ -880,13 +886,43 @@ void BTM_BleSetScanParams(uint32_t scan_interval, uint32_t scan_window,
cb.Run(BTM_SUCCESS);
} else {
cb.Run(BTM_ILLEGAL_VALUE);
- LOG_WARN("Illegal params: scan_interval = %d scan_window = %d",
- scan_interval, scan_window);
+
+ BTM_TRACE_ERROR("Illegal params: scan_interval = %d scan_window = %d",
+ scan_interval, scan_window);
}
}
/*******************************************************************************
*
+ * Function BTM_BleWriteScanRsp
+ *
+ * Description This function is called to write LE scan response.
+ *
+ * Parameters: p_scan_rsp: scan response information.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_BleWriteScanRsp(uint8_t* data, uint8_t length,
+ tBTM_BLE_ADV_DATA_CMPL_CBACK* p_adv_data_cback) {
+ BTM_TRACE_EVENT("%s: length: %d", __func__, length);
+ if (!controller_get_interface()->supports_ble()) {
+ p_adv_data_cback(BTM_ILLEGAL_VALUE);
+ return;
+ }
+
+ btsnd_hcic_ble_set_scan_rsp_data(length, data);
+
+ if (length != 0)
+ btm_cb.ble_ctr_cb.inq_var.scan_rsp = true;
+ else
+ btm_cb.ble_ctr_cb.inq_var.scan_rsp = false;
+
+ p_adv_data_cback(BTM_SUCCESS);
+}
+
+/*******************************************************************************
+ *
* Function BTM__BLEReadDiscoverability
*
* Description This function is called to read the current LE
@@ -927,30 +963,36 @@ uint16_t BTM_BleReadConnectability() {
* Returns void
*
******************************************************************************/
-static void btm_ble_select_adv_interval(uint8_t evt_type,
- uint16_t* p_adv_int_min,
- uint16_t* p_adv_int_max) {
- switch (evt_type) {
- case BTM_BLE_CONNECT_EVT:
- case BTM_BLE_CONNECT_LO_DUTY_DIR_EVT:
- *p_adv_int_min = *p_adv_int_max = BTM_BLE_GAP_ADV_FAST_INT_1;
- break;
+void btm_ble_select_adv_interval(tBTM_BLE_INQ_CB* p_cb, uint8_t evt_type,
+ uint16_t* p_adv_int_min,
+ uint16_t* p_adv_int_max) {
+ if (p_cb->adv_interval_min && p_cb->adv_interval_max) {
+ *p_adv_int_min = p_cb->adv_interval_min;
+ *p_adv_int_max = p_cb->adv_interval_max;
+ } else {
+ switch (evt_type) {
+ case BTM_BLE_CONNECT_EVT:
+ case BTM_BLE_CONNECT_LO_DUTY_DIR_EVT:
+ *p_adv_int_min = *p_adv_int_max = BTM_BLE_GAP_ADV_FAST_INT_1;
+ break;
- case BTM_BLE_NON_CONNECT_EVT:
- case BTM_BLE_DISCOVER_EVT:
- *p_adv_int_min = *p_adv_int_max = BTM_BLE_GAP_ADV_FAST_INT_2;
- break;
+ case BTM_BLE_NON_CONNECT_EVT:
+ case BTM_BLE_DISCOVER_EVT:
+ *p_adv_int_min = *p_adv_int_max = BTM_BLE_GAP_ADV_FAST_INT_2;
+ break;
/* connectable directed event */
- case BTM_BLE_CONNECT_DIR_EVT:
- *p_adv_int_min = BTM_BLE_GAP_ADV_DIR_MIN_INT;
- *p_adv_int_max = BTM_BLE_GAP_ADV_DIR_MAX_INT;
- break;
-
- default:
- *p_adv_int_min = *p_adv_int_max = BTM_BLE_GAP_ADV_SLOW_INT;
- break;
+ case BTM_BLE_CONNECT_DIR_EVT:
+ *p_adv_int_min = BTM_BLE_GAP_ADV_DIR_MIN_INT;
+ *p_adv_int_max = BTM_BLE_GAP_ADV_DIR_MAX_INT;
+ break;
+
+ default:
+ *p_adv_int_min = *p_adv_int_max = BTM_BLE_GAP_ADV_SLOW_INT;
+ break;
+ }
}
+ return;
}
/*******************************************************************************
@@ -1007,7 +1049,7 @@ void btm_ble_set_adv_flag(uint16_t connect_mode, uint16_t disc_mode) {
btm_ble_update_dmt_flag_bits(&flag, connect_mode, disc_mode);
- LOG_INFO("disc_mode %04x", disc_mode);
+ LOG_DEBUG(LOG_TAG, "disc_mode %04x", disc_mode);
/* update discoverable flag */
if (disc_mode & BTM_BLE_LIMITED_DISCOVERABLE) {
flag &= ~BTM_BLE_GEN_DISC_FLAG;
@@ -1055,14 +1097,14 @@ tBTM_STATUS btm_ble_set_discoverability(uint16_t combined_mode) {
p_cb->discoverable_mode = mode;
- evt_type =
- btm_set_conn_mode_adv_init_addr(address, &init_addr_type, &own_addr_type);
+ evt_type = btm_set_conn_mode_adv_init_addr(p_cb, address, &init_addr_type,
+ &own_addr_type);
if (p_cb->connectable_mode == BTM_BLE_NON_CONNECTABLE &&
mode == BTM_BLE_NON_DISCOVERABLE)
new_mode = BTM_BLE_ADV_DISABLE;
- btm_ble_select_adv_interval(evt_type, &adv_int_min, &adv_int_max);
+ btm_ble_select_adv_interval(p_cb, evt_type, &adv_int_min, &adv_int_max);
alarm_cancel(p_cb->fast_adv_timer);
@@ -1099,7 +1141,9 @@ tBTM_STATUS btm_ble_set_discoverability(uint16_t combined_mode) {
alarm_set_on_mloop(p_cb->fast_adv_timer, BTM_BLE_GAP_FAST_ADV_TIMEOUT_MS,
btm_ble_fast_adv_timer_timeout, NULL);
} else {
+#if (BLE_PRIVACY_SPT == TRUE)
btm_ble_disable_resolving_list(BTM_BLE_RL_ADV, true);
+#endif
}
/* set up stop advertising timer */
@@ -1145,14 +1189,14 @@ tBTM_STATUS btm_ble_set_connectability(uint16_t combined_mode) {
p_cb->connectable_mode = mode;
- evt_type =
- btm_set_conn_mode_adv_init_addr(address, &peer_addr_type, &own_addr_type);
+ evt_type = btm_set_conn_mode_adv_init_addr(p_cb, address, &peer_addr_type,
+ &own_addr_type);
if (mode == BTM_BLE_NON_CONNECTABLE &&
p_cb->discoverable_mode == BTM_BLE_NON_DISCOVERABLE)
new_mode = BTM_BLE_ADV_DISABLE;
- btm_ble_select_adv_interval(evt_type, &adv_int_min, &adv_int_max);
+ btm_ble_select_adv_interval(p_cb, evt_type, &adv_int_min, &adv_int_max);
alarm_cancel(p_cb->fast_adv_timer);
/* update adv params if needed */
@@ -1184,13 +1228,14 @@ tBTM_STATUS btm_ble_set_connectability(uint16_t combined_mode) {
alarm_set_on_mloop(p_cb->fast_adv_timer, BTM_BLE_GAP_FAST_ADV_TIMEOUT_MS,
btm_ble_fast_adv_timer_timeout, NULL);
} else {
+#if (BLE_PRIVACY_SPT == TRUE)
btm_ble_disable_resolving_list(BTM_BLE_RL_ADV, true);
+#endif
}
return status;
}
-static void btm_send_hci_scan_enable(uint8_t enable,
- uint8_t filter_duplicates) {
+void btm_send_hci_scan_enable(uint8_t enable, uint8_t filter_duplicates) {
if (controller_get_interface()->supports_ble_extended_advertising()) {
btsnd_hcic_ble_set_extended_scan_enable(enable, filter_duplicates, 0x0000,
0x0000);
@@ -1237,31 +1282,33 @@ void btm_send_hci_set_scan_params(uint8_t scan_type, uint16_t scan_int,
* BTM_BUSY - if an inquiry is already active
*
******************************************************************************/
-tBTM_STATUS btm_ble_start_inquiry(uint8_t duration) {
+tBTM_STATUS btm_ble_start_inquiry(uint8_t mode, uint8_t duration) {
tBTM_STATUS status = BTM_CMD_STARTED;
tBTM_BLE_CB* p_ble_cb = &btm_cb.ble_ctr_cb;
tBTM_INQUIRY_VAR_ST* p_inq = &btm_cb.btm_inq_vars;
- BTM_TRACE_DEBUG("btm_ble_start_inquiry: inq_active = 0x%02x",
- btm_cb.btm_inq_vars.inq_active);
+ BTM_TRACE_DEBUG("btm_ble_start_inquiry: mode = %02x inq_active = 0x%02x",
+ mode, btm_cb.btm_inq_vars.inq_active);
/* if selective connection is active, or inquiry is already active, reject it
*/
- if (p_ble_cb->is_ble_inquiry_active()) {
+ if (BTM_BLE_IS_INQ_ACTIVE(p_ble_cb->scan_activity)) {
BTM_TRACE_ERROR("LE Inquiry is active, can not start inquiry");
return (BTM_BUSY);
}
- if (!p_ble_cb->is_ble_scan_active()) {
- cache.ClearAll();
+ if (!BTM_BLE_IS_SCAN_ACTIVE(p_ble_cb->scan_activity)) {
btm_send_hci_set_scan_params(
BTM_BLE_SCAN_MODE_ACTI, BTM_BLE_LOW_LATENCY_SCAN_INT,
BTM_BLE_LOW_LATENCY_SCAN_WIN,
btm_cb.ble_ctr_cb.addr_mgnt_cb.own_addr_type, SP_ADV_ALL);
+#if (BLE_PRIVACY_SPT == TRUE)
/* enable IRK list */
btm_ble_enable_resolving_list_for_platform(BTM_BLE_RL_SCAN);
+#endif
p_ble_cb->inq_var.scan_type = BTM_BLE_SCAN_MODE_ACTI;
- btm_ble_start_scan();
+ p_ble_cb->inq_var.scan_duplicate_filter = BTM_BLE_DUPLICATE_DISABLE;
+ status = btm_ble_start_scan();
} else if ((p_ble_cb->inq_var.scan_interval !=
BTM_BLE_LOW_LATENCY_SCAN_INT) ||
(p_ble_cb->inq_var.scan_window != BTM_BLE_LOW_LATENCY_SCAN_WIN)) {
@@ -1276,8 +1323,8 @@ tBTM_STATUS btm_ble_start_inquiry(uint8_t duration) {
}
if (status == BTM_CMD_STARTED) {
- p_inq->inq_active |= BTM_BLE_GENERAL_INQUIRY;
- p_ble_cb->set_ble_inquiry_active();
+ p_inq->inq_active |= mode;
+ p_ble_cb->scan_activity |= mode;
BTM_TRACE_DEBUG("btm_ble_start_inquiry inq_active = 0x%02x",
p_inq->inq_active);
@@ -1304,7 +1351,7 @@ tBTM_STATUS btm_ble_start_inquiry(uint8_t duration) {
******************************************************************************/
void btm_ble_read_remote_name_cmpl(bool status, const RawAddress& bda,
uint16_t length, char* p_name) {
- tHCI_STATUS hci_status = HCI_SUCCESS;
+ uint8_t hci_status = HCI_SUCCESS;
BD_NAME bd_name;
memset(bd_name, 0, (BD_NAME_LEN + 1));
@@ -1432,17 +1479,24 @@ static void btm_ble_update_adv_flag(uint8_t flag) {
* Check ADV flag to make sure device is discoverable and match the search
* condition
*/
-static uint8_t btm_ble_is_discoverable(const RawAddress& bda,
- std::vector<uint8_t> const& adv_data) {
- uint8_t scan_state = BTM_BLE_NOT_SCANNING;
+uint8_t btm_ble_is_discoverable(const RawAddress& bda,
+ std::vector<uint8_t> const& adv_data) {
+ uint8_t flag = 0, rt = 0;
+ uint8_t data_len;
+ tBTM_INQ_PARMS* p_cond = &btm_cb.btm_inq_vars.inqparms;
/* for observer, always "discoverable */
- if (btm_cb.ble_ctr_cb.is_ble_observe_active())
- scan_state |= BTM_BLE_OBS_RESULT;
+ if (BTM_BLE_IS_OBS_ACTIVE(btm_cb.ble_ctr_cb.scan_activity))
+ rt |= BTM_BLE_OBS_RESULT;
+
+ /* does not match filter condition */
+ if (p_cond->filter_cond_type == BTM_FILTER_COND_BD_ADDR &&
+ bda != p_cond->filter_cond.bdaddr_cond) {
+ BTM_TRACE_DEBUG("BD ADDR does not meet filter condition");
+ return rt;
+ }
if (!adv_data.empty()) {
- uint8_t flag = 0;
- uint8_t data_len;
const uint8_t* p_flag = AdvertiseDataParser::GetFieldByType(
adv_data, BTM_BLE_AD_TYPE_FLAG, &data_len);
if (p_flag != NULL && data_len != 0) {
@@ -1450,11 +1504,18 @@ static uint8_t btm_ble_is_discoverable(const RawAddress& bda,
if ((btm_cb.btm_inq_vars.inq_active & BTM_BLE_GENERAL_INQUIRY) &&
(flag & (BTM_BLE_LIMIT_DISC_FLAG | BTM_BLE_GEN_DISC_FLAG)) != 0) {
- scan_state |= BTM_BLE_INQ_RESULT;
+ BTM_TRACE_DEBUG("Find Generable Discoverable device");
+ rt |= BTM_BLE_INQ_RESULT;
+ }
+
+ else if (btm_cb.btm_inq_vars.inq_active & BTM_BLE_LIMITED_INQUIRY &&
+ (flag & BTM_BLE_LIMIT_DISC_FLAG) != 0) {
+ BTM_TRACE_DEBUG("Find limited discoverable device");
+ rt |= BTM_BLE_INQ_RESULT;
}
}
}
- return scan_state;
+ return rt;
}
static void btm_ble_appearance_to_cod(uint16_t appearance, uint8_t* dev_class) {
@@ -1597,7 +1658,7 @@ void btm_ble_update_inq_result(tINQ_DB_ENT* p_i, uint8_t addr_type,
/* Save the info */
p_cur->inq_result_type |= BTM_INQ_RESULT_BLE;
- p_cur->ble_addr_type = static_cast<tBLE_ADDR_TYPE>(addr_type);
+ p_cur->ble_addr_type = addr_type;
p_cur->rssi = rssi;
p_cur->ble_primary_phy = primary_phy;
p_cur->ble_secondary_phy = secondary_phy;
@@ -1659,16 +1720,17 @@ void btm_ble_update_inq_result(tINQ_DB_ENT* p_i, uint8_t addr_type,
}
}
+ /* if BR/EDR not supported is not set, assume is a DUMO device */
if ((p_cur->flag & BTM_BLE_BREDR_NOT_SPT) == 0 &&
!ble_evt_type_is_directed(evt_type)) {
if (p_cur->ble_addr_type != BLE_ADDR_RANDOM) {
- LOG_VERBOSE("NOT_BR_EDR support bit not set, treat device as DUMO");
+ BTM_TRACE_DEBUG("BR/EDR NOT support bit not set, treat as DUMO");
p_cur->device_type |= BT_DEVICE_TYPE_DUMO;
} else {
- LOG_VERBOSE("Random address, treat device as LE only");
+ BTM_TRACE_DEBUG("Random address, treating device as LE only");
}
} else {
- LOG_VERBOSE("NOT_BR/EDR support bit set, treat device as LE only");
+ BTM_TRACE_DEBUG("BR/EDR NOT SUPPORT bit set, LE only device");
}
}
@@ -1697,6 +1759,7 @@ void btm_clear_all_pending_le_entry(void) {
}
void btm_ble_process_adv_addr(RawAddress& bda, uint8_t* addr_type) {
+#if (BLE_PRIVACY_SPT == TRUE)
/* map address to security record */
bool match = btm_identity_addr_to_random_pseudo(&bda, addr_type, false);
@@ -1705,7 +1768,7 @@ void btm_ble_process_adv_addr(RawAddress& bda, uint8_t* addr_type) {
if (!match && BTM_BLE_IS_RESOLVE_BDA(bda)) {
tBTM_SEC_DEV_REC* match_rec = btm_ble_resolve_random_addr(bda);
if (match_rec) {
- match_rec->ble.active_addr_type = tBTM_SEC_BLE::BTM_BLE_ADDR_RRA;
+ match_rec->ble.active_addr_type = BTM_BLE_ADDR_RRA;
match_rec->ble.cur_rand_addr = bda;
if (btm_ble_init_pseudo_addr(match_rec, bda)) {
@@ -1717,6 +1780,7 @@ void btm_ble_process_adv_addr(RawAddress& bda, uint8_t* addr_type) {
}
}
}
+#endif
}
/**
@@ -1733,14 +1797,13 @@ void btm_ble_process_ext_adv_pkt(uint8_t data_len, uint8_t* data) {
uint16_t event_type, periodic_adv_int, direct_address_type;
/* Only process the results if the inquiry is still active */
- if (!btm_cb.ble_ctr_cb.is_ble_scan_active()) return;
+ if (!BTM_BLE_IS_SCAN_ACTIVE(btm_cb.ble_ctr_cb.scan_activity)) return;
/* Extract the number of reports in this event. */
STREAM_TO_UINT8(num_reports, p);
- constexpr int extended_report_header_size = 24;
while (num_reports--) {
- if (p + extended_report_header_size > data + data_len) {
+ if (p > data + data_len) {
// TODO(jpawlowski): we should crash the stack here
BTM_TRACE_ERROR(
"Malformed LE Extended Advertising Report Event from controller - "
@@ -1796,14 +1859,13 @@ void btm_ble_process_adv_pkt(uint8_t data_len, uint8_t* data) {
int8_t rssi;
/* Only process the results if the inquiry is still active */
- if (!btm_cb.ble_ctr_cb.is_ble_scan_active()) return;
+ if (!BTM_BLE_IS_SCAN_ACTIVE(btm_cb.ble_ctr_cb.scan_activity)) return;
/* Extract the number of reports in this event. */
STREAM_TO_UINT8(num_reports, p);
- constexpr int report_header_size = 10;
while (num_reports--) {
- if (p + report_header_size > data + data_len) {
+ if (p > data + data_len) {
// TODO(jpawlowski): we should crash the stack here
BTM_TRACE_ERROR("Malformed LE Advertising Report Event from controller");
return;
@@ -1882,19 +1944,11 @@ void btm_ble_process_adv_pkt_cont(uint16_t evt_type, uint8_t addr_type,
bool is_scannable = ble_evt_type_is_scannable(evt_type);
bool is_scan_resp = ble_evt_type_is_scan_resp(evt_type);
- bool is_legacy = ble_evt_type_is_legacy(evt_type);
-
- // We might receive a legacy scan response without receving a ADV_IND
- // or ADV_SCAN_IND before. Only parsing the scan response data which
- // has no ad flag, the device will be set to DUMO mode. The createbond
- // procedure will use the wrong device mode.
- // In such case no necessary to report scan response
- if(is_legacy && is_scan_resp && !cache.Exist(addr_type, bda))
- return;
- bool is_start = is_legacy && is_scannable && !is_scan_resp;
+ bool is_start =
+ ble_evt_type_is_legacy(evt_type) && is_scannable && !is_scan_resp;
- if (is_legacy)
+ if (ble_evt_type_is_legacy(evt_type))
AdvertiseDataParser::RemoveTrailingZeros(tmp);
// We might have send scan request to this device before, but didn't get the
@@ -1923,7 +1977,6 @@ void btm_ble_process_adv_pkt_cont(uint16_t evt_type, uint8_t addr_type,
if (!AdvertiseDataParser::IsValid(adv_data)) {
DVLOG(1) << __func__ << "Dropping bad advertisement packet: "
<< base::HexEncode(adv_data.data(), adv_data.size());
- cache.Clear(addr_type, bda);
return;
}
@@ -1933,14 +1986,13 @@ void btm_ble_process_adv_pkt_cont(uint16_t evt_type, uint8_t addr_type,
if (btm_inq_find_bdaddr(bda)) {
/* never been report as an LE device */
if (p_i && (!(p_i->inq_info.results.device_type & BT_DEVICE_TYPE_BLE) ||
- /* scan response to be updated */
+ /* scan repsonse to be updated */
(!p_i->scan_rsp))) {
update = true;
- } else if (btm_cb.ble_ctr_cb.is_ble_observe_active()) {
+ } else if (BTM_BLE_IS_OBS_ACTIVE(btm_cb.ble_ctr_cb.scan_activity)) {
update = false;
} else {
/* if yes, skip it */
- cache.Clear(addr_type, bda);
return; /* assumption: one result per event */
}
}
@@ -1967,12 +2019,37 @@ void btm_ble_process_adv_pkt_cont(uint16_t evt_type, uint8_t addr_type,
uint8_t result = btm_ble_is_discoverable(bda, adv_data);
if (result == 0) {
- // Device no longer discoverable so discard outstanding advertising packet
cache.Clear(addr_type, bda);
+ LOG_WARN(LOG_TAG,
+ "%s device no longer discoverable, discarding advertising packet",
+ __func__);
return;
}
if (!update) result &= ~BTM_BLE_INQ_RESULT;
+ /* If the number of responses found and limited, issue a cancel inquiry */
+ if (p_inq->inqparms.max_resps &&
+ p_inq->inq_cmpl_info.num_resp == p_inq->inqparms.max_resps) {
+ /* new device */
+ if (p_i == NULL ||
+ /* assume a DUMO device, BR/EDR inquiry is always active */
+ (p_i &&
+ (p_i->inq_info.results.device_type & BT_DEVICE_TYPE_BLE) ==
+ BT_DEVICE_TYPE_BLE &&
+ p_i->scan_rsp)) {
+ BTM_TRACE_WARNING(
+ "INQ RES: Extra Response Received...cancelling inquiry..");
+
+ /* if is non-periodic inquiry active, cancel now */
+ if ((p_inq->inq_active & BTM_BR_INQ_ACTIVE_MASK) != 0 &&
+ (p_inq->inq_active & BTM_PERIODIC_INQUIRY_ACTIVE) == 0)
+ btsnd_hcic_inq_cancel();
+
+ btm_ble_stop_inquiry();
+
+ btm_acl_update_busy_level(BTM_BLI_INQ_DONE_EVT);
+ }
+ }
tBTM_INQ_RESULTS_CB* p_inq_results_cb = p_inq->p_inq_results_cb;
if (p_inq_results_cb && (result & BTM_BLE_INQ_RESULT)) {
@@ -1989,71 +2066,6 @@ void btm_ble_process_adv_pkt_cont(uint16_t evt_type, uint8_t addr_type,
cache.Clear(addr_type, bda);
}
-/**
- * This function copy from btm_ble_process_adv_pkt_cont to process adv packet
- * from gd scanning module to handle inquiry result callback.
- */
-void btm_ble_process_adv_pkt_cont_for_inquiry(
- uint16_t evt_type, uint8_t addr_type, const RawAddress& bda,
- uint8_t primary_phy, uint8_t secondary_phy, uint8_t advertising_sid,
- int8_t tx_power, int8_t rssi, uint16_t periodic_adv_int,
- std::vector<uint8_t> advertising_data) {
- tBTM_INQUIRY_VAR_ST* p_inq = &btm_cb.btm_inq_vars;
- bool update = true;
-
- tINQ_DB_ENT* p_i = btm_inq_db_find(bda);
-
- /* Check if this address has already been processed for this inquiry */
- if (btm_inq_find_bdaddr(bda)) {
- /* never been report as an LE device */
- if (p_i && (!(p_i->inq_info.results.device_type & BT_DEVICE_TYPE_BLE) ||
- /* scan response to be updated */
- (!p_i->scan_rsp))) {
- update = true;
- } else if (btm_cb.ble_ctr_cb.is_ble_observe_active()) {
- update = false;
- } else {
- /* if yes, skip it */
- return; /* assumption: one result per event */
- }
- }
-
- /* If existing entry, use that, else get a new one (possibly reusing the
- * oldest) */
- if (p_i == NULL) {
- p_i = btm_inq_db_new(bda);
- if (p_i != NULL) {
- p_inq->inq_cmpl_info.num_resp++;
- p_i->time_of_resp = bluetooth::common::time_get_os_boottime_ms();
- } else
- return;
- } else if (p_i->inq_count !=
- p_inq->inq_counter) /* first time seen in this inquiry */
- {
- p_i->time_of_resp = bluetooth::common::time_get_os_boottime_ms();
- p_inq->inq_cmpl_info.num_resp++;
- }
-
- /* update the LE device information in inquiry database */
- btm_ble_update_inq_result(p_i, addr_type, bda, evt_type, primary_phy,
- secondary_phy, advertising_sid, tx_power, rssi,
- periodic_adv_int, advertising_data);
-
- uint8_t result = btm_ble_is_discoverable(bda, advertising_data);
- if (result == 0) {
- return;
- }
-
- if (!update) result &= ~BTM_BLE_INQ_RESULT;
-
- tBTM_INQ_RESULTS_CB* p_inq_results_cb = p_inq->p_inq_results_cb;
- if (p_inq_results_cb && (result & BTM_BLE_INQ_RESULT)) {
- (p_inq_results_cb)((tBTM_INQ_RESULTS*)&p_i->inq_info.results,
- const_cast<uint8_t*>(advertising_data.data()),
- advertising_data.size());
- }
-}
-
void btm_ble_process_phy_update_pkt(uint8_t len, uint8_t* data) {
uint8_t status, tx_phy, rx_phy;
uint16_t handle;
@@ -2066,8 +2078,7 @@ void btm_ble_process_phy_update_pkt(uint8_t len, uint8_t* data) {
STREAM_TO_UINT8(tx_phy, p);
STREAM_TO_UINT8(rx_phy, p);
- gatt_notify_phy_updated(static_cast<tGATT_STATUS>(status), handle, tx_phy,
- rx_phy);
+ gatt_notify_phy_updated(status, handle, tx_phy, rx_phy);
}
/*******************************************************************************
@@ -2079,15 +2090,17 @@ void btm_ble_process_phy_update_pkt(uint8_t len, uint8_t* data) {
* Returns void
*
******************************************************************************/
-void btm_ble_start_scan() {
+tBTM_STATUS btm_ble_start_scan(void) {
tBTM_BLE_INQ_CB* p_inq = &btm_cb.ble_ctr_cb.inq_var;
/* start scan, disable duplicate filtering */
- btm_send_hci_scan_enable(BTM_BLE_SCAN_ENABLE, BTM_BLE_DUPLICATE_DISABLE);
+ btm_send_hci_scan_enable(BTM_BLE_SCAN_ENABLE, p_inq->scan_duplicate_filter);
if (p_inq->scan_type == BTM_BLE_SCAN_MODE_ACTI)
btm_ble_set_topology_mask(BTM_BLE_STATE_ACTIVE_SCAN_BIT);
else
btm_ble_set_topology_mask(BTM_BLE_STATE_PASSIVE_SCAN_BIT);
+
+ return BTM_CMD_STARTED;
}
/*******************************************************************************
@@ -2130,14 +2143,13 @@ void btm_ble_stop_inquiry(void) {
alarm_cancel(p_ble_cb->inq_var.inquiry_timer);
- p_ble_cb->reset_ble_inquiry();
+ p_ble_cb->scan_activity &= ~BTM_BLE_INQUIRY_MASK;
/* If no more scan activity, stop LE scan now */
- if (!p_ble_cb->is_ble_scan_active()) {
+ if (!BTM_BLE_IS_SCAN_ACTIVE(p_ble_cb->scan_activity))
btm_ble_stop_scan();
- } else if ((p_ble_cb->inq_var.scan_interval !=
- BTM_BLE_LOW_LATENCY_SCAN_INT) ||
- (p_ble_cb->inq_var.scan_window != BTM_BLE_LOW_LATENCY_SCAN_WIN)) {
+ else if ((p_ble_cb->inq_var.scan_interval != BTM_BLE_LOW_LATENCY_SCAN_INT) ||
+ (p_ble_cb->inq_var.scan_window != BTM_BLE_LOW_LATENCY_SCAN_WIN)) {
BTM_TRACE_DEBUG("%s: setting default params for ongoing observe", __func__);
btm_ble_stop_scan();
btm_ble_start_scan();
@@ -2166,14 +2178,12 @@ static void btm_ble_stop_observe(void) {
alarm_cancel(p_ble_cb->observer_timer);
- p_ble_cb->reset_ble_observe();
+ p_ble_cb->scan_activity &= ~BTM_LE_OBSERVE_ACTIVE;
p_ble_cb->p_obs_results_cb = NULL;
p_ble_cb->p_obs_cmpl_cb = NULL;
- if (!p_ble_cb->is_ble_scan_active()) {
- btm_ble_stop_scan();
- }
+ if (!BTM_BLE_IS_SCAN_ACTIVE(p_ble_cb->scan_activity)) btm_ble_stop_scan();
if (p_obs_cb) (p_obs_cb)(&btm_cb.btm_inq_vars.inq_cmpl_info);
}
@@ -2234,12 +2244,14 @@ tBTM_STATUS btm_ble_start_adv(void) {
if (!btm_ble_adv_states_operation(btm_ble_topology_check, p_cb->evt_type))
return BTM_WRONG_MODE;
+#if (BLE_PRIVACY_SPT == TRUE)
/* To relax resolving list, always have resolving list enabled, unless
* directed adv */
if (p_cb->evt_type != BTM_BLE_CONNECT_LO_DUTY_DIR_EVT &&
p_cb->evt_type != BTM_BLE_CONNECT_DIR_EVT)
/* enable resolving list is desired */
btm_ble_enable_resolving_list_for_platform(BTM_BLE_RL_ADV);
+#endif
btsnd_hcic_ble_set_adv_enable(BTM_BLE_ADV_ENABLE);
p_cb->adv_mode = BTM_BLE_ADV_ENABLE;
@@ -2296,8 +2308,8 @@ static void btm_ble_start_slow_adv(void) {
btm_ble_stop_adv();
- p_cb->evt_type = btm_set_conn_mode_adv_init_addr(address, &init_addr_type,
- &own_addr_type);
+ p_cb->evt_type = btm_set_conn_mode_adv_init_addr(
+ p_cb, address, &init_addr_type, &own_addr_type);
/* slow adv mode never goes into directed adv */
btsnd_hcic_ble_write_adv_params(
@@ -2324,6 +2336,13 @@ static void btm_ble_observer_timer_timeout(UNUSED_ATTR void* data) {
btm_ble_stop_observe();
}
+void btm_ble_refresh_raddr_timer_timeout(UNUSED_ATTR void* data) {
+ if (btm_cb.ble_ctr_cb.addr_mgnt_cb.own_addr_type == BLE_ADDR_RANDOM) {
+ /* refresh the random addr */
+ btm_gen_resolvable_private_addr(base::Bind(&btm_gen_resolve_paddr_low));
+ }
+}
+
/*******************************************************************************
*
* Function btm_ble_read_remote_features_complete
@@ -2336,6 +2355,8 @@ static void btm_ble_observer_timer_timeout(UNUSED_ATTR void* data) {
*
******************************************************************************/
void btm_ble_read_remote_features_complete(uint8_t* p) {
+ BTM_TRACE_EVENT("%s", __func__);
+
uint16_t handle;
uint8_t status;
STREAM_TO_UINT8(status, p);
@@ -2343,20 +2364,19 @@ void btm_ble_read_remote_features_complete(uint8_t* p) {
handle = handle & 0x0FFF; // only 12 bits meaningful
if (status != HCI_SUCCESS) {
- if (status != HCI_ERR_UNSUPPORTED_REM_FEATURE) {
- LOG_ERROR("Failed to read remote features status:%s",
- hci_error_code_text(static_cast<tHCI_STATUS>(status)).c_str());
- return;
- }
- LOG_WARN("Remote does not support reading remote feature");
+ BTM_TRACE_ERROR("%s: failed for handle: 0x%04d, status 0x%02x", __func__,
+ handle, status);
+ if (status != HCI_ERR_UNSUPPORTED_REM_FEATURE) return;
+ }
+
+ int idx = btm_handle_to_acl_index(handle);
+ if (idx == MAX_L2CAP_LINKS) {
+ BTM_TRACE_ERROR("%s: can't find acl for handle: 0x%04d", __func__, handle);
+ return;
}
if (status == HCI_SUCCESS) {
- if (!acl_set_peer_le_features_from_handle(handle, p)) {
- LOG_ERROR(
- "Unable to find existing connection after read remote features");
- return;
- }
+ STREAM_TO_ARRAY(btm_cb.acl_db[idx].peer_le_features, p, BD_FEATURES_LEN);
}
btsnd_hcic_rmt_ver_req(handle);
@@ -2394,7 +2414,7 @@ void btm_ble_dir_adv_tout(void) {
btm_cb.ble_ctr_cb.inq_var.adv_mode = BTM_BLE_ADV_DISABLE;
/* make device fall back into undirected adv mode by default */
- btm_cb.ble_ctr_cb.inq_var.directed_conn = BTM_BLE_ADV_IND_EVT;
+ btm_cb.ble_ctr_cb.inq_var.directed_conn = false;
}
/*******************************************************************************
@@ -2436,8 +2456,7 @@ bool btm_ble_clear_topology_mask(tBTM_BLE_STATE_MASK request_state_mask) {
* Returns void
*
******************************************************************************/
-static void btm_ble_update_link_topology_mask(uint8_t link_role,
- bool increase) {
+void btm_ble_update_link_topology_mask(uint8_t link_role, bool increase) {
btm_ble_clear_topology_mask(BTM_BLE_STATE_ALL_CONN_MASK);
if (increase)
@@ -2445,29 +2464,21 @@ static void btm_ble_update_link_topology_mask(uint8_t link_role,
else if (btm_cb.ble_ctr_cb.link_count[link_role] > 0)
btm_cb.ble_ctr_cb.link_count[link_role]--;
- if (btm_cb.ble_ctr_cb.link_count[HCI_ROLE_CENTRAL])
- btm_ble_set_topology_mask(BTM_BLE_STATE_CENTRAL_BIT);
+ if (btm_cb.ble_ctr_cb.link_count[HCI_ROLE_MASTER])
+ btm_ble_set_topology_mask(BTM_BLE_STATE_MASTER_BIT);
- if (btm_cb.ble_ctr_cb.link_count[HCI_ROLE_PERIPHERAL])
- btm_ble_set_topology_mask(BTM_BLE_STATE_PERIPHERAL_BIT);
+ if (btm_cb.ble_ctr_cb.link_count[HCI_ROLE_SLAVE])
+ btm_ble_set_topology_mask(BTM_BLE_STATE_SLAVE_BIT);
- if (link_role == HCI_ROLE_PERIPHERAL && increase) {
+ if (link_role == HCI_ROLE_SLAVE && increase) {
btm_cb.ble_ctr_cb.inq_var.adv_mode = BTM_BLE_ADV_DISABLE;
/* make device fall back into undirected adv mode by default */
- btm_cb.ble_ctr_cb.inq_var.directed_conn = BTM_BLE_ADV_IND_EVT;
+ btm_cb.ble_ctr_cb.inq_var.directed_conn = BTM_BLE_CONNECT_EVT;
/* clear all adv states */
btm_ble_clear_topology_mask(BTM_BLE_STATE_ALL_ADV_MASK);
}
}
-void btm_ble_increment_link_topology_mask(uint8_t link_role) {
- btm_ble_update_link_topology_mask(link_role, true);
-}
-
-void btm_ble_decrement_link_topology_mask(uint8_t link_role) {
- btm_ble_update_link_topology_mask(link_role, false);
-}
-
/*******************************************************************************
*
* Function btm_ble_update_mode_operation
@@ -2479,11 +2490,11 @@ void btm_ble_decrement_link_topology_mask(uint8_t link_role) {
*
******************************************************************************/
void btm_ble_update_mode_operation(uint8_t link_role, const RawAddress* bd_addr,
- tHCI_STATUS status) {
+ uint8_t status) {
if (status == HCI_ERR_ADVERTISING_TIMEOUT) {
btm_cb.ble_ctr_cb.inq_var.adv_mode = BTM_BLE_ADV_DISABLE;
/* make device fall back into undirected adv mode by default */
- btm_cb.ble_ctr_cb.inq_var.directed_conn = BTM_BLE_ADV_IND_EVT;
+ btm_cb.ble_ctr_cb.inq_var.directed_conn = BTM_BLE_CONNECT_EVT;
/* clear all adv states */
btm_ble_clear_topology_mask(BTM_BLE_STATE_ALL_ADV_MASK);
}
@@ -2494,37 +2505,17 @@ void btm_ble_update_mode_operation(uint8_t link_role, const RawAddress* bd_addr,
}
/* in case of disconnected, we must cancel bgconn and restart
- in order to add back device to acceptlist in order to reconnect */
- if (bd_addr != nullptr) {
- const RawAddress bda(*bd_addr);
- if (bluetooth::shim::is_gd_acl_enabled()) {
- if (acl_check_and_clear_ignore_auto_connect_after_disconnect(bda)) {
- LOG_DEBUG(
- "Local disconnect initiated so skipping re-add to acceptlist "
- "device:%s",
- PRIVATE_ADDRESS(bda));
- } else {
- if (!bluetooth::shim::ACL_AcceptLeConnectionFrom(
- convert_to_address_with_type(bda, btm_find_dev(bda)),
- /* is_direct */ false)) {
- LOG_ERROR("Unable to add to acceptlist as it is full:%s",
- PRIVATE_ADDRESS(bda));
- }
- }
- } else {
- btm_ble_bgconn_cancel_if_disconnected(bda);
- }
- }
+ in order to add back device to white list in order to reconnect */
+ if (bd_addr) btm_ble_bgconn_cancel_if_disconnected(*bd_addr);
/* when no connection is attempted, and controller is not rejecting last
request
due to resource limitation, start next direct connection or background
connection
now in order */
- if (btm_cb.ble_ctr_cb.is_connection_state_idle() &&
+ if (btm_ble_get_conn_st() == BLE_CONN_IDLE &&
status != HCI_ERR_HOST_REJECT_RESOURCES &&
status != HCI_ERR_MAX_NUM_OF_CONNECTIONS) {
- LOG_DEBUG("Resuming le background connections");
btm_ble_resume_bg_conn();
}
}
@@ -2575,12 +2566,6 @@ void btm_ble_init(void) {
#endif
}
-// Clean up btm ble control block
-void btm_ble_free() {
- tBTM_BLE_CB* p_cb = &btm_cb.ble_ctr_cb;
- alarm_free(p_cb->addr_mgnt_cb.refresh_raddr_timer);
-}
-
/*******************************************************************************
*
* Function btm_ble_topology_check
diff --git a/stack/btm/btm_ble_int.h b/stack/btm/btm_ble_int.h
index e5ac28d28..b2702feda 100644
--- a/stack/btm/btm_ble_int.h
+++ b/stack/btm/btm_ble_int.h
@@ -30,33 +30,49 @@
#include "bt_target.h"
#include "btm_ble_api.h"
#include "btm_ble_int_types.h"
+#include "btm_int.h"
#include "btm_int_types.h"
#include "hcidefs.h"
#include "smp_api.h"
-#include "stack/include/hci_error_code.h"
-extern void btm_ble_process_periodic_adv_sync_est_evt(uint8_t len, uint8_t* p);
-extern void btm_ble_process_periodic_adv_pkt(uint8_t len, uint8_t* p);
-extern void btm_ble_process_periodic_adv_sync_lost_evt(uint8_t len, uint8_t* p);
+extern bool ble_evt_type_is_connectable(uint16_t evt_type);
+extern void btm_ble_refresh_raddr_timer_timeout(void* data);
+extern void btm_ble_process_adv_pkt(uint8_t len, uint8_t* p);
+extern void btm_ble_process_phy_update_pkt(uint8_t len, uint8_t* p);
+extern void btm_ble_process_ext_adv_pkt(uint8_t len, uint8_t* p);
+extern void btm_ble_proc_scan_rsp_rpt(uint8_t* p);
+extern tBTM_STATUS btm_ble_read_remote_name(const RawAddress& remote_bda,
+ tBTM_CMPL_CB* p_cb);
+extern bool btm_ble_cancel_remote_name(const RawAddress& remote_bda);
+
+extern tBTM_STATUS btm_ble_set_discoverability(uint16_t combined_mode);
+extern tBTM_STATUS btm_ble_set_connectability(uint16_t combined_mode);
+extern void btm_send_hci_scan_enable(uint8_t enable, uint8_t filter_duplicates);
extern void btm_send_hci_set_scan_params(uint8_t scan_type, uint16_t scan_int,
uint16_t scan_win,
uint8_t addr_type_own,
uint8_t scan_filter_policy);
+extern tBTM_STATUS btm_ble_start_inquiry(uint8_t mode, uint8_t duration);
extern void btm_ble_stop_scan(void);
extern void btm_clear_all_pending_le_entry(void);
+extern void btm_ble_stop_scan();
+extern void btm_ble_stop_inquiry(void);
extern void btm_ble_init(void);
-extern void btm_ble_free();
extern void btm_ble_connected(const RawAddress& bda, uint16_t handle,
uint8_t enc_mode, uint8_t role,
tBLE_ADDR_TYPE addr_type, bool addr_matched);
-extern void btm_ble_connected_from_address_with_type(
- const tBLE_BD_ADDR& address_with_type, uint16_t handle, uint8_t enc_mode,
- uint8_t role, bool addr_matched);
-
+extern void btm_ble_read_remote_features_complete(uint8_t* p);
+extern void btm_ble_write_adv_enable_complete(uint8_t* p);
+extern void btm_ble_conn_complete(uint8_t* p, uint16_t evt_len, bool enhanced);
+extern void btm_read_ble_local_supported_states_complete(uint8_t* p,
+ uint16_t evt_len);
+extern tBTM_BLE_CONN_ST btm_ble_get_conn_st(void);
extern tBTM_STATUS btm_ble_start_adv(void);
extern tBTM_STATUS btm_ble_stop_adv(void);
-extern void btm_ble_start_scan(void);
+extern void btm_le_on_advertising_set_terminated(uint8_t* p, uint16_t length);
+extern tBTM_STATUS btm_ble_start_scan(void);
+extern void btm_ble_create_ll_conn_complete(uint8_t status);
/* LE security function from btm_sec.cc */
extern void btm_ble_link_sec_check(const RawAddress& bd_addr,
@@ -64,11 +80,13 @@ extern void btm_ble_link_sec_check(const RawAddress& bd_addr,
tBTM_BLE_SEC_REQ_ACT* p_sec_req_act);
extern void btm_ble_ltk_request_reply(const RawAddress& bda, bool use_stk,
const Octet16& stk);
-extern tBTM_STATUS btm_proc_smp_cback(tSMP_EVT event, const RawAddress& bd_addr,
- tSMP_EVT_DATA* p_data);
+extern uint8_t btm_proc_smp_cback(tSMP_EVT event, const RawAddress& bd_addr,
+ tSMP_EVT_DATA* p_data);
extern tBTM_STATUS btm_ble_set_encryption(const RawAddress& bd_addr,
tBTM_BLE_SEC_ACT sec_act,
uint8_t link_role);
+extern void btm_ble_ltk_request(uint16_t handle, uint8_t rand[8],
+ uint16_t ediv);
extern tBTM_STATUS btm_ble_start_encrypt(const RawAddress& bda, bool use_stk,
Octet16* p_stk);
extern void btm_ble_link_encrypted(const RawAddress& bd_addr,
@@ -77,10 +95,17 @@ extern void btm_ble_link_encrypted(const RawAddress& bd_addr,
/* LE device management functions */
extern void btm_ble_reset_id(void);
+/* security related functions */
+extern void btm_ble_increment_sign_ctr(const RawAddress& bd_addr,
+ bool is_local);
extern bool btm_get_local_div(const RawAddress& bd_addr, uint16_t* p_div);
extern bool btm_ble_get_enc_key_type(const RawAddress& bd_addr,
uint8_t* p_key_types);
+extern void btm_ble_test_command_complete(uint8_t* p);
+extern void btm_ble_rand_enc_complete(uint8_t* p, uint16_t op_code,
+ tBTM_RAND_ENC_CB* p_enc_cplt_cback);
+
extern void btm_sec_save_le_key(const RawAddress& bd_addr,
tBTM_LE_KEY_TYPE key_type,
tBTM_LE_KEY_VALUE* p_keys,
@@ -89,49 +114,68 @@ extern void btm_ble_update_sec_key_size(const RawAddress& bd_addr,
uint8_t enc_key_size);
extern uint8_t btm_ble_read_sec_key_size(const RawAddress& bd_addr);
-/* acceptlist function */
+/* white list function */
extern void btm_update_scanner_filter_policy(tBTM_BLE_SFP scan_policy);
+extern void btm_update_adv_filter_policy(tBTM_BLE_AFP adv_policy);
+extern void btm_ble_white_list_init(uint8_t white_list_size);
/* background connection function */
extern bool btm_ble_suspend_bg_conn(void);
extern bool btm_ble_resume_bg_conn(void);
+extern bool btm_ble_start_auto_conn();
+extern bool btm_ble_stop_auto_conn();
extern void btm_ble_update_mode_operation(uint8_t link_role,
const RawAddress* bda,
- tHCI_STATUS status);
+ uint8_t status);
+extern bool btm_execute_wl_dev_operation(void);
+extern void btm_ble_update_link_topology_mask(uint8_t role, bool increase);
extern void btm_ble_bgconn_cancel_if_disconnected(const RawAddress& bd_addr);
/* BLE address management */
extern void btm_gen_resolvable_private_addr(
base::Callback<void(const RawAddress& rpa)> cb);
-
+extern void btm_gen_non_resolvable_private_addr(tBTM_BLE_ADDR_CBACK* p_cback,
+ void* p);
extern tBTM_SEC_DEV_REC* btm_ble_resolve_random_addr(
const RawAddress& random_bda);
extern void btm_gen_resolve_paddr_low(const RawAddress& address);
extern uint64_t btm_get_next_private_addrress_interval_ms();
/* privacy function */
+#if (BLE_PRIVACY_SPT == TRUE)
/* BLE address mapping with CS feature */
+extern bool btm_identity_addr_to_random_pseudo(RawAddress* bd_addr,
+ uint8_t* p_addr_type,
+ bool refresh);
extern bool btm_random_pseudo_to_identity_addr(RawAddress* random_pseudo,
uint8_t* p_identity_addr_type);
extern void btm_ble_refresh_peer_resolvable_private_addr(
- const RawAddress& pseudo_bda, const RawAddress& rra,
- tBTM_SEC_BLE::tADDRESS_TYPE type);
-extern bool btm_ble_read_resolving_list_entry(tBTM_SEC_DEV_REC* p_dev_rec);
-
-extern bool btm_ble_addr_resolvable(const RawAddress& rpa,
- tBTM_SEC_DEV_REC* p_dev_rec);
-
-extern bool btm_ble_resolving_list_load_dev(tBTM_SEC_DEV_REC* p_dev_rec);
-extern void btm_ble_resolving_list_remove_dev(tBTM_SEC_DEV_REC* p_dev_rec);
+ const RawAddress& pseudo_bda, const RawAddress& rra, uint8_t rra_type);
+extern void btm_ble_refresh_local_resolvable_private_addr(
+ const RawAddress& pseudo_addr, const RawAddress& local_rpa);
+extern void btm_ble_read_resolving_list_entry_complete(uint8_t* p,
+ uint16_t evt_len);
+extern void btm_ble_remove_resolving_list_entry_complete(uint8_t* p,
+ uint16_t evt_len);
+extern void btm_ble_add_resolving_list_entry_complete(uint8_t* p,
+ uint16_t evt_len);
+extern void btm_ble_clear_resolving_list_complete(uint8_t* p, uint16_t evt_len);
+extern void btm_read_ble_resolving_list_size_complete(uint8_t* p,
+ uint16_t evt_len);
extern void btm_ble_enable_resolving_list(uint8_t);
extern bool btm_ble_disable_resolving_list(uint8_t rl_mask, bool to_resume);
extern void btm_ble_enable_resolving_list_for_platform(uint8_t rl_mask);
extern void btm_ble_resolving_list_init(uint8_t max_irk_list_sz);
+extern void btm_ble_resolving_list_cleanup(void);
+#endif
extern void btm_ble_adv_init(void);
+extern void* btm_ble_multi_adv_get_ref(uint8_t inst_id);
extern void btm_ble_multi_adv_cleanup(void);
extern void btm_ble_batchscan_init(void);
+extern void btm_ble_batchscan_cleanup(void);
extern void btm_ble_adv_filter_init(void);
+extern void btm_ble_adv_filter_cleanup(void);
extern bool btm_ble_topology_check(tBTM_BLE_STATE_MASK request);
extern bool btm_ble_clear_topology_mask(tBTM_BLE_STATE_MASK request_state);
extern bool btm_ble_set_topology_mask(tBTM_BLE_STATE_MASK request_state);
diff --git a/stack/btm/btm_ble_int_types.h b/stack/btm/btm_ble_int_types.h
index 4d87ded0b..375c2b3a8 100644
--- a/stack/btm/btm_ble_int_types.h
+++ b/stack/btm/btm_ble_int_types.h
@@ -20,8 +20,6 @@
#define BTM_BLE_INT_TYPES_H
#include "osi/include/alarm.h"
-#include "stack/btm/neighbor_inquiry.h"
-#include "stack/include/btm_ble_api_types.h"
/* scanning enable status */
#define BTM_BLE_SCAN_ENABLE 0x01
@@ -31,8 +29,16 @@
#define BTM_BLE_ADV_ENABLE 0x01
#define BTM_BLE_ADV_DISABLE 0x00
+/* use the high 4 bits unused by inquiry mode */
+#define BTM_BLE_SELECT_SCAN 0x20
+#define BTM_BLE_NAME_REQUEST 0x40
+#define BTM_BLE_OBSERVE 0x80
+
+#define BTM_BLE_MAX_WL_ENTRY 1
#define BTM_BLE_AD_DATA_LEN 31
+#define BTM_BLE_ENC_MASK 0x03
+
#define BTM_BLE_DUPLICATE_ENABLE 1
#define BTM_BLE_DUPLICATE_DISABLE 0
@@ -62,18 +68,37 @@
#define BTM_BLE_GAP_FAST_ADV_TIMEOUT_MS (30 * 1000)
-typedef enum : uint8_t {
- BTM_BLE_SEC_REQ_ACT_NONE = 0,
- /* encrypt the link using current key or key refresh */
- BTM_BLE_SEC_REQ_ACT_ENCRYPT = 1,
- BTM_BLE_SEC_REQ_ACT_PAIR = 2,
- /* discard the sec request while encryption is started but not completed */
- BTM_BLE_SEC_REQ_ACT_DISCARD = 3,
-} tBTM_BLE_SEC_REQ_ACT;
+#define BTM_BLE_SEC_REQ_ACT_NONE 0
+/* encrypt the link using current key or key refresh */
+#define BTM_BLE_SEC_REQ_ACT_ENCRYPT 1
+#define BTM_BLE_SEC_REQ_ACT_PAIR 2
+/* discard the sec request while encryption is started but not completed */
+#define BTM_BLE_SEC_REQ_ACT_DISCARD 3
+typedef uint8_t tBTM_BLE_SEC_REQ_ACT;
+
+#define BLE_STATIC_PRIVATE_MSB_MASK 0x3f
+/* most significant bit, bit7, bit6 is 01 to be resolvable random */
+#define BLE_RESOLVE_ADDR_MSB 0x40
+/* bit 6, and bit7 */
+#define BLE_RESOLVE_ADDR_MASK 0xc0
+inline bool BTM_BLE_IS_RESOLVE_BDA(const RawAddress& x) {
+ return ((x.address)[0] & BLE_RESOLVE_ADDR_MASK) == BLE_RESOLVE_ADDR_MSB;
+}
+
+/* LE scan activity bit mask, continue with LE inquiry bits */
+/* observe is in progress */
+#define BTM_LE_OBSERVE_ACTIVE 0x80
+
+/* BLE scan activity mask checking */
+#define BTM_BLE_IS_SCAN_ACTIVE(x) ((x)&BTM_BLE_SCAN_ACTIVE_MASK)
+#define BTM_BLE_IS_INQ_ACTIVE(x) ((x)&BTM_BLE_INQUIRY_MASK)
+#define BTM_BLE_IS_OBS_ACTIVE(x) ((x)&BTM_LE_OBSERVE_ACTIVE)
+
+/* BLE ADDR type ID bit */
+#define BLE_ADDR_TYPE_ID_BIT 0x02
#define BTM_VSC_CHIP_CAPABILITY_L_VERSION 55
#define BTM_VSC_CHIP_CAPABILITY_M_VERSION 95
-#define BTM_VSC_CHIP_CAPABILITY_S_VERSION 98
typedef struct {
uint16_t data_mask;
@@ -82,6 +107,15 @@ typedef struct {
uint8_t* p_pad;
} tBTM_BLE_LOCAL_ADV_DATA;
+typedef struct {
+ /* Used for determining if a response has already been received for the
+ * current inquiry operation. (We do not want to flood the caller with
+ * multiple responses from the same device. */
+ uint32_t inq_count;
+ bool scan_rsp;
+ tBLE_BD_ADDR le_bda;
+} tINQ_LE_BDADDR;
+
#define BTM_BLE_ISVALID_PARAM(x, min, max) \
(((x) >= (min) && (x) <= (max)) || ((x) == BTM_BLE_CONN_PARAM_UNDEF))
@@ -91,32 +125,30 @@ typedef struct {
uint32_t scan_window;
uint32_t scan_interval;
uint8_t scan_type; /* current scan type: active or passive */
-
+ uint8_t scan_duplicate_filter; /* duplicate filter enabled for scan */
+ uint16_t adv_interval_min;
+ uint16_t adv_interval_max;
tBTM_BLE_AFP afp; /* advertising filter policy */
tBTM_BLE_SFP sfp; /* scanning filter policy */
tBLE_ADDR_TYPE adv_addr_type;
uint8_t evt_type;
-
uint8_t adv_mode;
- void enable_advertising_mode() { adv_mode = BTM_BLE_ADV_ENABLE; }
- void disable_advertising_mode() { adv_mode = BTM_BLE_ADV_DISABLE; }
- bool is_advertising_mode_enabled() const {
- return (adv_mode == BTM_BLE_ADV_ENABLE);
- }
-
tBLE_BD_ADDR direct_bda;
tBTM_BLE_EVT directed_conn;
bool fast_adv_on;
alarm_t* fast_adv_timer;
/* inquiry BD addr database */
+ uint8_t num_bd_entries;
+ uint8_t max_bd_entries;
tBTM_BLE_LOCAL_ADV_DATA adv_data;
tBTM_BLE_ADV_CHNL_MAP adv_chnl_map;
alarm_t* inquiry_timer;
bool scan_rsp;
uint8_t state; /* Current state that the inquiry process is in */
+ int8_t tx_power;
} tBTM_BLE_INQ_CB;
/* random address resolving complete callback */
@@ -128,33 +160,65 @@ typedef void(tBTM_BLE_ADDR_CBACK)(const RawAddress& static_random, void* p);
typedef struct {
tBLE_ADDR_TYPE own_addr_type; /* local device LE address type */
RawAddress private_addr;
+ RawAddress random_bda;
+ tBTM_BLE_ADDR_CBACK* p_generate_cback;
+ void* p;
alarm_t* refresh_raddr_timer;
} tBTM_LE_RANDOM_CB;
-/* acceptlist using state as a bit mask */
+typedef struct {
+ uint16_t min_conn_int;
+ uint16_t max_conn_int;
+ uint16_t slave_latency;
+ uint16_t supervision_tout;
+
+} tBTM_LE_CONN_PRAMS;
+
+typedef struct {
+ RawAddress bd_addr;
+ uint8_t attr;
+ bool is_connected;
+ bool in_use;
+} tBTM_LE_BG_CONN_DEV;
+
+/* white list using state as a bit mask */
constexpr uint8_t BTM_BLE_WL_IDLE = 0;
-constexpr uint8_t BTM_BLE_ACCEPTLIST_INIT = 1;
+constexpr uint8_t BTM_BLE_WL_INIT = 1;
/* resolving list using state as a bit mask */
-enum : uint8_t {
- BTM_BLE_RL_IDLE = 0,
- BTM_BLE_RL_INIT = (1 << 0),
- BTM_BLE_RL_SCAN = (1 << 1),
- BTM_BLE_RL_ADV = (1 << 2),
-};
+#define BTM_BLE_RL_IDLE 0
+#define BTM_BLE_RL_INIT 1
+#define BTM_BLE_RL_SCAN 2
+#define BTM_BLE_RL_ADV 4
typedef uint8_t tBTM_BLE_RL_STATE;
+/* BLE connection state */
+#define BLE_CONN_IDLE 0
+#define BLE_CONNECTING 2
+#define BLE_CONN_CANCEL 3
+typedef uint8_t tBTM_BLE_CONN_ST;
+
typedef struct { void* p_param; } tBTM_BLE_CONN_REQ;
/* LE state request */
#define BTM_BLE_STATE_INVALID 0
+#define BTM_BLE_STATE_CONN_ADV 1
#define BTM_BLE_STATE_INIT 2
+#define BTM_BLE_STATE_MASTER 3
+#define BTM_BLE_STATE_SLAVE 4
+#define BTM_BLE_STATE_LO_DUTY_DIR_ADV 5
+#define BTM_BLE_STATE_HI_DUTY_DIR_ADV 6
+#define BTM_BLE_STATE_NON_CONN_ADV 7
+#define BTM_BLE_STATE_PASSIVE_SCAN 8
+#define BTM_BLE_STATE_ACTIVE_SCAN 9
+#define BTM_BLE_STATE_SCAN_ADV 10
#define BTM_BLE_STATE_MAX 11
+typedef uint8_t tBTM_BLE_STATE;
#define BTM_BLE_STATE_CONN_ADV_BIT 0x0001
#define BTM_BLE_STATE_INIT_BIT 0x0002
-#define BTM_BLE_STATE_CENTRAL_BIT 0x0004
-#define BTM_BLE_STATE_PERIPHERAL_BIT 0x0008
+#define BTM_BLE_STATE_MASTER_BIT 0x0004
+#define BTM_BLE_STATE_SLAVE_BIT 0x0008
#define BTM_BLE_STATE_LO_DUTY_DIR_ADV_BIT 0x0010
#define BTM_BLE_STATE_HI_DUTY_DIR_ADV_BIT 0x0020
#define BTM_BLE_STATE_NON_CONN_ADV_BIT 0x0040
@@ -167,8 +231,14 @@ typedef uint16_t tBTM_BLE_STATE_MASK;
#define BTM_BLE_STATE_ALL_ADV_MASK \
(BTM_BLE_STATE_CONN_ADV_BIT | BTM_BLE_STATE_LO_DUTY_DIR_ADV_BIT | \
BTM_BLE_STATE_HI_DUTY_DIR_ADV_BIT | BTM_BLE_STATE_SCAN_ADV_BIT)
+#define BTM_BLE_STATE_ALL_SCAN_MASK \
+ (BTM_BLE_STATE_PASSIVE_SCAN_BIT | BTM_BLE_STATE_ACTIVE_SCAN_BIT)
#define BTM_BLE_STATE_ALL_CONN_MASK \
- (BTM_BLE_STATE_CENTRAL_BIT | BTM_BLE_STATE_PERIPHERAL_BIT)
+ (BTM_BLE_STATE_MASTER_BIT | BTM_BLE_STATE_SLAVE_BIT)
+
+#ifndef BTM_LE_RESOLVING_LIST_MAX
+#define BTM_LE_RESOLVING_LIST_MAX 0x20
+#endif
typedef struct {
RawAddress* resolve_q_random_pseudo;
@@ -177,6 +247,13 @@ typedef struct {
uint8_t q_pending;
} tBTM_BLE_RESOLVE_Q;
+typedef struct {
+ bool in_use;
+ bool to_add;
+ RawAddress bd_addr;
+ uint8_t attr;
+} tBTM_BLE_WL_OP;
+
/* BLE privacy mode */
#define BTM_PRIVACY_NONE 0 /* BLE no privacy */
#define BTM_PRIVACY_1_1 1 /* BLE privacy 1.1, do not support privacy 1.0 */
@@ -185,33 +262,14 @@ typedef struct {
3 /* BLE privacy mixed mode, broadcom propietary mode */
typedef uint8_t tBTM_PRIVACY_MODE;
+/* data length change event callback */
+typedef void(tBTM_DATA_LENGTH_CHANGE_CBACK)(uint16_t max_tx_length,
+ uint16_t max_rx_length);
+
/* Define BLE Device Management control structure
*/
-constexpr uint8_t kBTM_BLE_INQUIRY_ACTIVE = 0x10;
-constexpr uint8_t kBTM_BLE_OBSERVE_ACTIVE = 0x80;
-constexpr size_t kCentralAndPeripheralCount = 2;
-
typedef struct {
- private:
- uint8_t scan_activity_; /* LE scan activity mask */
-
- public:
- bool is_ble_inquiry_active() const {
- return (scan_activity_ & kBTM_BLE_INQUIRY_ACTIVE);
- }
- bool is_ble_observe_active() const {
- return (scan_activity_ & kBTM_BLE_OBSERVE_ACTIVE);
- }
-
- void set_ble_inquiry_active() { scan_activity_ |= kBTM_BLE_INQUIRY_ACTIVE; }
- void set_ble_observe_active() { scan_activity_ |= kBTM_BLE_OBSERVE_ACTIVE; }
-
- void reset_ble_inquiry() { scan_activity_ &= ~kBTM_BLE_INQUIRY_ACTIVE; }
- void reset_ble_observe() { scan_activity_ &= ~kBTM_BLE_OBSERVE_ACTIVE; }
-
- bool is_ble_scan_active() const {
- return (is_ble_inquiry_active() || is_ble_observe_active());
- }
+ uint8_t scan_activity; /* LE scan activity mask */
/*****************************************************
** BLE Inquiry
@@ -227,52 +285,29 @@ typedef struct {
uint16_t scan_int;
uint16_t scan_win;
- /* acceptlist information */
+ /* white list information */
uint8_t wl_state;
- void set_acceptlist_process_in_progress() {
- wl_state |= BTM_BLE_ACCEPTLIST_INIT;
- }
- void reset_acceptlist_process_in_progress() {
- wl_state &= ~BTM_BLE_ACCEPTLIST_INIT;
- }
- bool is_acceptlist_in_progress() const {
- return wl_state & BTM_BLE_ACCEPTLIST_INIT;
- }
-
- private:
- enum : uint8_t { /* BLE connection state */
- BLE_CONN_IDLE = 0,
- BLE_CONNECTING = 2,
- BLE_CONN_CANCEL = 3,
- } conn_state_{BLE_CONN_IDLE};
-
- public:
- bool is_connection_state_idle() const { return conn_state_ == BLE_CONN_IDLE; }
- bool is_connection_state_connecting() const {
- return conn_state_ == BLE_CONNECTING;
- }
- bool is_connection_state_cancelled() const {
- return conn_state_ == BLE_CONN_CANCEL;
- }
- void set_connection_state_idle() { conn_state_ = BLE_CONN_IDLE; }
- void set_connection_state_connecting() { conn_state_ = BLE_CONNECTING; }
- void set_connection_state_cancelled() { conn_state_ = BLE_CONN_CANCEL; }
+
+ tBTM_BLE_CONN_ST conn_state;
/* random address management control block */
tBTM_LE_RANDOM_CB addr_mgnt_cb;
+ bool enabled;
+
+#if (BLE_PRIVACY_SPT == TRUE)
+ bool mixed_mode; /* privacy 1.2 mixed mode is on or not */
tBTM_PRIVACY_MODE privacy_mode; /* privacy mode */
uint8_t resolving_list_avail_size; /* resolving list available size */
tBTM_BLE_RESOLVE_Q resolving_list_pend_q; /* Resolving list queue */
tBTM_BLE_RL_STATE suspended_rl_state; /* Suspended resolving list state */
uint8_t* irk_list_mask; /* IRK list availability mask, up to max entry bits */
tBTM_BLE_RL_STATE rl_state; /* Resolving list state */
+#endif
/* current BLE link state */
tBTM_BLE_STATE_MASK cur_states; /* bit mask of tBTM_BLE_STATE */
-
- uint8_t link_count[kCentralAndPeripheralCount]; /* total link count central
- and peripheral*/
+ uint8_t link_count[2]; /* total link count master and slave*/
} tBTM_BLE_CB;
#endif // BTM_BLE_INT_TYPES_H
diff --git a/stack/btm/btm_ble_multi_adv.cc b/stack/btm/btm_ble_multi_adv.cc
index ce8f7ba0d..e58d00d4f 100644
--- a/stack/btm/btm_ble_multi_adv.cc
+++ b/stack/btm/btm_ble_multi_adv.cc
@@ -129,8 +129,8 @@ static void alarm_closure_cb(void* p) {
}
// Periodic alarms are not supported, because we clean up data in callback
-static void alarm_set_closure(const base::Location& posted_from, alarm_t* alarm,
- uint64_t interval_ms, base::Closure user_task) {
+void alarm_set_closure(const base::Location& posted_from, alarm_t* alarm,
+ uint64_t interval_ms, base::Closure user_task) {
closure_data* data = new closure_data;
data->posted_from = posted_from;
data->user_task = std::move(user_task);
@@ -693,17 +693,13 @@ class BleAdvertisingManagerImpl
p_inst->advertising_interval = p_params->adv_int_min;
const RawAddress& peer_address = RawAddress::kEmpty;
- // sid must be in range 0x00 to 0x0F. Since no controller supports more than
- // 16 advertisers, it's safe to make sid equal to inst_id.
- uint8_t sid = p_inst->inst_id % 0x0F;
-
GetHciInterface()->SetParameters(
p_inst->inst_id, p_params->advertising_event_properties,
p_params->adv_int_min, p_params->adv_int_max, p_params->channel_map,
p_inst->own_address_type, p_inst->own_address, 0x00, peer_address,
p_params->adv_filter_policy, p_inst->tx_power,
p_params->primary_advertising_phy, 0x00,
- p_params->secondary_advertising_phy, sid,
+ p_params->secondary_advertising_phy, 0x01 /* TODO: proper SID */,
p_params->scan_request_notification_enable, cb);
// TODO: re-enable only if it was enabled, properly call
diff --git a/stack/btm/btm_ble_privacy.cc b/stack/btm/btm_ble_privacy.cc
index 790bffbed..4f1d386c1 100644
--- a/stack/btm/btm_ble_privacy.cc
+++ b/stack/btm/btm_ble_privacy.cc
@@ -24,17 +24,15 @@
#include <string.h>
#include "bt_target.h"
+#if (BLE_PRIVACY_SPT == TRUE)
#include "ble_advertiser.h"
#include "bt_types.h"
#include "btm_int.h"
#include "btu.h"
#include "device/include/controller.h"
#include "hcimsgs.h"
-#include "stack/btm/btm_dev.h"
#include "vendor_hcidefs.h"
-extern tBTM_CB btm_cb;
-
/* RPA offload VSC specifics */
#define BTM_BLE_META_IRK_ENABLE 0x01
#define BTM_BLE_META_ADD_IRK_ENTRY 0x02
@@ -65,8 +63,8 @@ extern tBTM_CB btm_cb;
* Returns void
*
******************************************************************************/
-static void btm_ble_enq_resolving_list_pending(const RawAddress& pseudo_bda,
- uint8_t op_code) {
+void btm_ble_enq_resolving_list_pending(const RawAddress& pseudo_bda,
+ uint8_t op_code) {
tBTM_BLE_RESOLVE_Q* p_q = &btm_cb.ble_ctr_cb.resolving_list_pend_q;
p_q->resolve_q_random_pseudo[p_q->q_next] = pseudo_bda;
@@ -87,8 +85,8 @@ static void btm_ble_enq_resolving_list_pending(const RawAddress& pseudo_bda,
* Returns void
*
******************************************************************************/
-static bool btm_ble_brcm_find_resolving_pending_entry(
- const RawAddress& pseudo_addr, uint8_t action) {
+bool btm_ble_brcm_find_resolving_pending_entry(const RawAddress& pseudo_addr,
+ uint8_t action) {
tBTM_BLE_RESOLVE_Q* p_q = &btm_cb.ble_ctr_cb.resolving_list_pend_q;
for (uint8_t i = p_q->q_pending; i != p_q->q_next;) {
@@ -114,7 +112,7 @@ static bool btm_ble_brcm_find_resolving_pending_entry(
* Returns void
*
******************************************************************************/
-static bool btm_ble_deq_resolving_pending(RawAddress& pseudo_addr) {
+bool btm_ble_deq_resolving_pending(RawAddress& pseudo_addr) {
tBTM_BLE_RESOLVE_Q* p_q = &btm_cb.ble_ctr_cb.resolving_list_pend_q;
if (p_q->q_next != p_q->q_pending) {
@@ -138,7 +136,7 @@ static bool btm_ble_deq_resolving_pending(RawAddress& pseudo_addr) {
* Returns none
*
******************************************************************************/
-static void btm_ble_clear_irk_index(uint8_t index) {
+void btm_ble_clear_irk_index(uint8_t index) {
uint8_t byte;
uint8_t bit;
@@ -158,7 +156,7 @@ static void btm_ble_clear_irk_index(uint8_t index) {
* Returns index from 0 ~ max (127 default)
*
******************************************************************************/
-static uint8_t btm_ble_find_irk_index(void) {
+uint8_t btm_ble_find_irk_index(void) {
uint8_t i = 0;
uint8_t byte;
uint8_t bit;
@@ -187,8 +185,7 @@ static uint8_t btm_ble_find_irk_index(void) {
* Returns void
*
******************************************************************************/
-static void btm_ble_update_resolving_list(const RawAddress& pseudo_bda,
- bool add) {
+void btm_ble_update_resolving_list(const RawAddress& pseudo_bda, bool add) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(pseudo_bda);
if (p_dev_rec == NULL) return;
@@ -206,7 +203,7 @@ static void btm_ble_update_resolving_list(const RawAddress& pseudo_bda,
}
}
-static bool clear_resolving_list_bit(void* data, void* context) {
+bool clear_resolving_list_bit(void* data, void* context) {
tBTM_SEC_DEV_REC* p_dev_rec = static_cast<tBTM_SEC_DEV_REC*>(data);
p_dev_rec->ble.in_controller_list &= ~BTM_RESOLVING_LIST_BIT;
return true;
@@ -339,7 +336,7 @@ void btm_ble_remove_resolving_list_entry_complete(uint8_t* p,
*
******************************************************************************/
void btm_ble_read_resolving_list_entry_complete(uint8_t* p, uint16_t evt_len) {
- uint8_t status;
+ uint8_t status, rra_type = BTM_BLE_ADDR_PSEUDO;
RawAddress rra, pseudo_bda;
STREAM_TO_UINT8(status, p);
@@ -362,8 +359,7 @@ void btm_ble_read_resolving_list_entry_complete(uint8_t* p, uint16_t evt_len) {
} else {
STREAM_TO_BDADDR(rra, p);
}
- btm_ble_refresh_peer_resolvable_private_addr(
- pseudo_bda, rra, tBTM_SEC_BLE::tADDRESS_TYPE::BTM_BLE_ADDR_PSEUDO);
+ btm_ble_refresh_peer_resolvable_private_addr(pseudo_bda, rra, rra_type);
}
}
/*******************************************************************************
@@ -380,7 +376,7 @@ void btm_ble_read_resolving_list_entry_complete(uint8_t* p, uint16_t evt_len) {
* Returns void
*
******************************************************************************/
-static void btm_ble_resolving_list_vsc_op_cmpl(tBTM_VSC_CMPL* p_params) {
+void btm_ble_resolving_list_vsc_op_cmpl(tBTM_VSC_CMPL* p_params) {
uint8_t *p = p_params->p_param_buf, op_subcode;
uint16_t evt_len = p_params->param_len;
@@ -419,16 +415,15 @@ tBTM_STATUS btm_ble_remove_resolving_list_entry(tBTM_SEC_DEV_REC* p_dev_rec) {
return BTM_WRONG_MODE;
if (controller_get_interface()->supports_ble_privacy()) {
- btsnd_hcic_ble_rm_device_resolving_list(
- p_dev_rec->ble.identity_address_with_type.type,
- p_dev_rec->ble.identity_address_with_type.bda);
+ btsnd_hcic_ble_rm_device_resolving_list(p_dev_rec->ble.identity_addr_type,
+ p_dev_rec->ble.identity_addr);
} else {
uint8_t param[20] = {0};
uint8_t* p = param;
UINT8_TO_STREAM(p, BTM_BLE_META_REMOVE_IRK_ENTRY);
- UINT8_TO_STREAM(p, p_dev_rec->ble.identity_address_with_type.type);
- BDADDR_TO_STREAM(p, p_dev_rec->ble.identity_address_with_type.bda);
+ UINT8_TO_STREAM(p, p_dev_rec->ble.identity_addr_type);
+ BDADDR_TO_STREAM(p, p_dev_rec->ble.identity_addr);
BTM_VendorSpecificCommand(HCI_VENDOR_BLE_RPA_VSC,
BTM_BLE_META_REMOVE_IRK_LEN, param,
@@ -471,20 +466,16 @@ void btm_ble_clear_resolving_list(void) {
*
* Parameters entry index.
*
- * Returns true if command successfully sent, false otherwise
+ * Returns status
*
******************************************************************************/
-bool btm_ble_read_resolving_list_entry(tBTM_SEC_DEV_REC* p_dev_rec) {
- if (!(p_dev_rec->ble.in_controller_list & BTM_RESOLVING_LIST_BIT)) {
- LOG_INFO("%s Unable to read resolving list entry as resolving bit not set",
- __func__);
- return false;
- }
+tBTM_STATUS btm_ble_read_resolving_list_entry(tBTM_SEC_DEV_REC* p_dev_rec) {
+ if (!(p_dev_rec->ble.in_controller_list & BTM_RESOLVING_LIST_BIT))
+ return BTM_WRONG_MODE;
if (controller_get_interface()->supports_ble_privacy()) {
- btsnd_hcic_ble_read_resolvable_addr_peer(
- p_dev_rec->ble.identity_address_with_type.type,
- p_dev_rec->ble.identity_address_with_type.bda);
+ btsnd_hcic_ble_read_resolvable_addr_peer(p_dev_rec->ble.identity_addr_type,
+ p_dev_rec->ble.identity_addr);
} else {
uint8_t param[20] = {0};
uint8_t* p = param;
@@ -499,7 +490,7 @@ bool btm_ble_read_resolving_list_entry(tBTM_SEC_DEV_REC* p_dev_rec) {
btm_ble_enq_resolving_list_pending(p_dev_rec->bd_addr,
BTM_BLE_META_READ_IRK_ENTRY);
- return true;
+ return BTM_CMD_STARTED;
}
/*******************************************************************************
@@ -515,7 +506,7 @@ bool btm_ble_read_resolving_list_entry(tBTM_SEC_DEV_REC* p_dev_rec) {
* Returns true if suspended; false otherwise
*
******************************************************************************/
-static bool btm_ble_suspend_resolving_list_activity(void) {
+bool btm_ble_suspend_resolving_list_activity(void) {
tBTM_BLE_CB* p_ble_cb = &btm_cb.ble_ctr_cb;
/* if resolving list is not enabled, do not need to terminate any activity */
@@ -537,7 +528,7 @@ static bool btm_ble_suspend_resolving_list_activity(void) {
BleAdvertisingManager::Get()->Suspend();
}
- if (p_ble_cb->is_ble_scan_active()) {
+ if (BTM_BLE_IS_SCAN_ACTIVE(p_ble_cb->scan_activity)) {
btm_ble_stop_scan();
p_ble_cb->suspended_rl_state |= BTM_BLE_RL_SCAN;
}
@@ -559,31 +550,21 @@ static bool btm_ble_suspend_resolving_list_activity(void) {
* Returns none
*
******************************************************************************/
-static void btm_ble_resume_resolving_list_activity(void) {
+void btm_ble_resume_resolving_list_activity(void) {
tBTM_BLE_CB* p_ble_cb = &btm_cb.ble_ctr_cb;
- if (p_ble_cb->suspended_rl_state & BTM_BLE_RL_ADV) {
- btm_ble_start_adv();
- LOG_DEBUG("Started ble advertising");
- }
+ if (p_ble_cb->suspended_rl_state & BTM_BLE_RL_ADV) btm_ble_start_adv();
// If it's non-VSC implementation, resume
if (BleAdvertisingManager::IsInitialized() &&
(controller_get_interface()->supports_ble_extended_advertising() ||
BTM_BleMaxMultiAdvInstanceCount() == 0)) {
BleAdvertisingManager::Get()->Resume();
- LOG_DEBUG("Resumed ble advertising manager");
}
- if (p_ble_cb->suspended_rl_state & BTM_BLE_RL_SCAN) {
- btm_ble_start_scan();
- LOG_DEBUG("Started resolving list scan");
- }
+ if (p_ble_cb->suspended_rl_state & BTM_BLE_RL_SCAN) btm_ble_start_scan();
- if (p_ble_cb->suspended_rl_state & BTM_BLE_RL_INIT) {
- btm_ble_resume_bg_conn();
- LOG_DEBUG("Resumed background connections");
- }
+ if (p_ble_cb->suspended_rl_state & BTM_BLE_RL_INIT) btm_ble_resume_bg_conn();
p_ble_cb->suspended_rl_state = BTM_BLE_RL_IDLE;
}
@@ -598,7 +579,7 @@ static void btm_ble_resume_resolving_list_activity(void) {
* Parameters enable: enable or disable the RRA offloading feature
*
******************************************************************************/
-static void btm_ble_vendor_enable_irk_feature(bool enable) {
+void btm_ble_vendor_enable_irk_feature(bool enable) {
uint8_t param[20], *p;
p = param;
@@ -621,7 +602,7 @@ static void btm_ble_vendor_enable_irk_feature(bool enable) {
* Returns none
*
******************************************************************************/
-static bool btm_ble_exe_disable_resolving_list(void) {
+bool btm_ble_exe_disable_resolving_list(void) {
if (!btm_ble_suspend_resolving_list_activity()) return false;
if (!controller_get_interface()->supports_ble_privacy())
@@ -641,7 +622,7 @@ static bool btm_ble_exe_disable_resolving_list(void) {
* Returns none
*
******************************************************************************/
-static void btm_ble_exe_enable_resolving_list(void) {
+void btm_ble_exe_enable_resolving_list(void) {
if (!btm_ble_suspend_resolving_list_activity()) return;
if (!controller_get_interface()->supports_ble_privacy())
@@ -686,7 +667,7 @@ bool btm_ble_disable_resolving_list(uint8_t rl_mask, bool to_resume) {
* Function btm_ble_resolving_list_load_dev
*
* Description This function adds a device which is using RPA into the
- * acceptlist.
+ * white list.
*
* Parameters pointer to device security record
*
@@ -744,26 +725,23 @@ bool btm_ble_resolving_list_load_dev(tBTM_SEC_DEV_REC* p_dev_rec) {
const Octet16& peer_irk = p_dev_rec->ble.keys.irk;
const Octet16& local_irk = btm_cb.devcb.id_keys.irk;
- if (p_dev_rec->ble.identity_address_with_type.bda.IsEmpty()) {
- p_dev_rec->ble.identity_address_with_type.bda = p_dev_rec->bd_addr;
- p_dev_rec->ble.identity_address_with_type.type =
- p_dev_rec->ble.ble_addr_type;
+ if (p_dev_rec->ble.identity_addr.IsEmpty()) {
+ p_dev_rec->ble.identity_addr = p_dev_rec->bd_addr;
+ p_dev_rec->ble.identity_addr_type = p_dev_rec->ble.ble_addr_type;
}
- BTM_TRACE_DEBUG(
- "%s: adding device %s to controller resolving list", __func__,
- p_dev_rec->ble.identity_address_with_type.bda.ToString().c_str());
+ BTM_TRACE_DEBUG("%s: adding device %s to controller resolving list",
+ __func__, p_dev_rec->ble.identity_addr.ToString().c_str());
// use identical IRK for now
- btsnd_hcic_ble_add_device_resolving_list(
- p_dev_rec->ble.identity_address_with_type.type,
- p_dev_rec->ble.identity_address_with_type.bda, peer_irk, local_irk);
+ btsnd_hcic_ble_add_device_resolving_list(p_dev_rec->ble.identity_addr_type,
+ p_dev_rec->ble.identity_addr,
+ peer_irk, local_irk);
if (controller_get_interface()->supports_ble_set_privacy_mode()) {
BTM_TRACE_DEBUG("%s: adding device privacy mode", __func__);
- btsnd_hcic_ble_set_privacy_mode(
- p_dev_rec->ble.identity_address_with_type.type,
- p_dev_rec->ble.identity_address_with_type.bda, 0x01);
+ btsnd_hcic_ble_set_privacy_mode(p_dev_rec->ble.identity_addr_type,
+ p_dev_rec->ble.identity_addr, 0x01);
}
} else {
uint8_t param[40] = {0};
@@ -771,8 +749,8 @@ bool btm_ble_resolving_list_load_dev(tBTM_SEC_DEV_REC* p_dev_rec) {
UINT8_TO_STREAM(p, BTM_BLE_META_ADD_IRK_ENTRY);
ARRAY_TO_STREAM(p, p_dev_rec->ble.keys.irk, OCTET16_LEN);
- UINT8_TO_STREAM(p, p_dev_rec->ble.identity_address_with_type.type);
- BDADDR_TO_STREAM(p, p_dev_rec->ble.identity_address_with_type.bda);
+ UINT8_TO_STREAM(p, p_dev_rec->ble.identity_addr_type);
+ BDADDR_TO_STREAM(p, p_dev_rec->ble.identity_addr);
BTM_VendorSpecificCommand(HCI_VENDOR_BLE_RPA_VSC, BTM_BLE_META_ADD_IRK_LEN,
param, btm_ble_resolving_list_vsc_op_cmpl);
@@ -843,10 +821,24 @@ void btm_ble_enable_resolving_list(uint8_t rl_mask) {
}
}
-static bool is_on_resolving_list(void* data, void* context) {
+/*******************************************************************************
+ *
+ * Function btm_ble_resolving_list_empty
+ *
+ * Description check to see if resoving list is empty or not
+ *
+ * Returns true: empty; false non-empty
+ *
+ ******************************************************************************/
+bool btm_ble_resolving_list_empty(void) {
+ return (controller_get_interface()->get_ble_resolving_list_max_size() ==
+ btm_cb.ble_ctr_cb.resolving_list_avail_size);
+}
+
+bool is_on_resolving_list(void* data, void* context) {
tBTM_SEC_DEV_REC* p_dev = static_cast<tBTM_SEC_DEV_REC*>(data);
if ((p_dev->ble.in_controller_list & BTM_RESOLVING_LIST_BIT) &&
- (p_dev->ble.in_controller_list & BTM_ACCEPTLIST_BIT))
+ (p_dev->ble.in_controller_list & BTM_WHITE_LIST_BIT))
return false;
return true;
@@ -857,7 +849,7 @@ static bool is_on_resolving_list(void* data, void* context) {
* Function btm_ble_enable_resolving_list_for_platform
*
* Description enable/disable resolving list feature depending on if any
- * resolving list is empty and acceptlist is involoved in the
+ * resolving list is empty and whitelist is involoved in the
* operation.
*
* Returns none
@@ -916,3 +908,26 @@ void btm_ble_resolving_list_init(uint8_t max_irk_list_sz) {
btm_ble_clear_resolving_list();
btm_cb.ble_ctr_cb.resolving_list_avail_size = max_irk_list_sz;
}
+
+/*******************************************************************************
+ *
+ * Function btm_ble_resolving_list_cleanup
+ *
+ * Description Cleanup resolving list dynamic memory
+ *
+ * Parameters
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_ble_resolving_list_cleanup(void) {
+ tBTM_BLE_RESOLVE_Q* p_q = &btm_cb.ble_ctr_cb.resolving_list_pend_q;
+
+ osi_free_and_reset((void**)&p_q->resolve_q_random_pseudo);
+ osi_free_and_reset((void**)&p_q->resolve_q_action);
+
+ controller_get_interface()->set_ble_resolving_list_max_size(0);
+
+ osi_free_and_reset((void**)&btm_cb.ble_ctr_cb.irk_list_mask);
+}
+#endif
diff --git a/stack/btm/btm_client_interface.cc b/stack/btm/btm_client_interface.cc
deleted file mode 100644
index d8a3284e4..000000000
--- a/stack/btm/btm_client_interface.cc
+++ /dev/null
@@ -1,183 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "stack/include/btm_client_interface.h"
-#include <cstdint>
-#include "main/shim/btm_api.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_ble_api.h"
-#include "stack/include/btm_client_interface.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcidefs.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
-
-struct btm_client_interface_s btm_client_interface = {
- .lifecycle =
- {
- .BTM_GetHCIConnHandle = BTM_GetHCIConnHandle,
- .BTM_PmRegister = BTM_PmRegister,
- .BTM_VendorSpecificCommand = BTM_VendorSpecificCommand,
- .ACL_RegisterClient = ACL_RegisterClient,
- .ACL_UnregisterClient = ACL_UnregisterClient,
- .btm_init = btm_init,
- .btm_free = btm_free,
- .btm_ble_init = btm_ble_init,
- .btm_ble_free = btm_ble_free,
- .BTM_reset_complete = BTM_reset_complete,
- },
-
- .scn =
- {
- .BTM_AllocateSCN = BTM_AllocateSCN,
- .BTM_TryAllocateSCN = BTM_TryAllocateSCN,
- .BTM_FreeSCN = BTM_FreeSCN,
- },
-
- .neighbor =
- {
- .BTM_CancelInquiry = BTM_CancelInquiry,
- .BTM_ClearInqDb = BTM_ClearInqDb,
- .BTM_InqDbNext = BTM_InqDbNext,
- .BTM_SetConnectability = BTM_SetConnectability,
- .BTM_SetDiscoverability = BTM_SetDiscoverability,
- .BTM_StartInquiry = BTM_StartInquiry,
- .BTM_IsInquiryActive = BTM_IsInquiryActive,
- .BTM_SetInquiryMode = BTM_SetInquiryMode,
- .BTM_EnableInterlacedInquiryScan = BTM_EnableInterlacedInquiryScan,
- .BTM_EnableInterlacedPageScan = BTM_EnableInterlacedPageScan,
- },
-
- // Acl peer and lifecycle
- .peer =
- {
- .features =
- {
- .SupportTransparentSynchronousData =
- ACL_SupportTransparentSynchronousData,
- },
-
- .BTM_CancelRemoteDeviceName = BTM_CancelRemoteDeviceName,
- .BTM_IsAclConnectionUp = BTM_IsAclConnectionUp,
- .BTM_ReadConnectedTransportAddress =
- BTM_ReadConnectedTransportAddress,
- .BTM_ReadDevInfo = BTM_ReadDevInfo,
- .BTM_ReadRemoteDeviceName = BTM_ReadRemoteDeviceName,
- .BTM_ReadRemoteFeatures = BTM_ReadRemoteFeatures,
- .BTM_GetMaxPacketSize = BTM_GetMaxPacketSize,
- .BTM_ReadRemoteVersion = BTM_ReadRemoteVersion,
- },
-
- .link_policy =
- {
- .BTM_GetRole = BTM_GetRole,
- .BTM_SetPowerMode = BTM_SetPowerMode,
- .BTM_SetSsrParams = BTM_SetSsrParams,
- .BTM_SwitchRoleToCentral = BTM_SwitchRoleToCentral,
- .BTM_WritePageTimeout = BTM_WritePageTimeout,
- .BTM_block_role_switch_for = BTM_block_role_switch_for,
- .BTM_block_sniff_mode_for = BTM_block_sniff_mode_for,
- .BTM_default_unblock_role_switch = BTM_default_unblock_role_switch,
- .BTM_unblock_role_switch_for = BTM_unblock_role_switch_for,
- .BTM_unblock_sniff_mode_for = BTM_unblock_sniff_mode_for,
- },
-
- .link_controller =
- {
- .BTM_GetLinkSuperTout = BTM_GetLinkSuperTout,
- .BTM_ReadRSSI = BTM_ReadRSSI,
- },
-
- .security =
- {
- .BTM_ConfirmReqReply = BTM_ConfirmReqReply,
- .BTM_PINCodeReply = BTM_PINCodeReply,
- .BTM_RemoteOobDataReply = BTM_RemoteOobDataReply,
- .BTM_SecAddBleDevice = BTM_SecAddBleDevice,
- .BTM_SecAddBleKey = BTM_SecAddBleKey,
- .BTM_SecAddDevice = BTM_SecAddDevice,
- .BTM_SecAddRmtNameNotifyCallback = BTM_SecAddRmtNameNotifyCallback,
- .BTM_SecBond = BTM_SecBond,
- .BTM_SecBondCancel = BTM_SecBondCancel,
- .BTM_SecClearSecurityFlags = BTM_SecClearSecurityFlags,
- .BTM_SecClrService = BTM_SecClrService,
- .BTM_SecClrServiceByPsm = BTM_SecClrServiceByPsm,
- .BTM_SecDeleteDevice = BTM_SecDeleteDevice,
- .BTM_SecDeleteRmtNameNotifyCallback =
- BTM_SecDeleteRmtNameNotifyCallback,
- .BTM_SecReadDevName = BTM_SecReadDevName,
- .BTM_SecRegister = BTM_SecRegister,
- .BTM_SetEncryption = BTM_SetEncryption,
- .BTM_IsEncrypted = BTM_IsEncrypted,
- .BTM_SecIsSecurityPending = BTM_SecIsSecurityPending,
- .BTM_IsLinkKeyKnown = BTM_IsLinkKeyKnown,
- },
-
- .ble =
- {
- .BTM_BleConfirmReply = BTM_BleConfirmReply,
- .BTM_BleGetEnergyInfo = BTM_BleGetEnergyInfo,
- .BTM_BleLoadLocalKeys = BTM_BleLoadLocalKeys,
- .BTM_BleObserve = BTM_BleObserve,
- .BTM_BlePasskeyReply = BTM_BlePasskeyReply,
- .BTM_BleReadControllerFeatures = BTM_BleReadControllerFeatures,
- .BTM_BleSetPhy = BTM_BleSetPhy,
- .BTM_BleSetPrefConnParams = BTM_BleSetPrefConnParams,
- .BTM_SetBleDataLength = BTM_SetBleDataLength,
- .BTM_UseLeLink = BTM_UseLeLink,
- },
-
- .sco =
- {
- .BTM_CreateSco = BTM_CreateSco,
- .BTM_EScoConnRsp = BTM_EScoConnRsp,
- .BTM_GetNumScoLinks = BTM_GetNumScoLinks,
- .BTM_RegForEScoEvts = BTM_RegForEScoEvts,
- .BTM_RemoveSco = BTM_RemoveSco,
- .BTM_SetEScoMode = BTM_SetEScoMode,
- .BTM_WriteVoiceSettings = BTM_WriteVoiceSettings,
- },
-
- .local =
- {
- .BTM_ReadLocalDeviceNameFromController =
- BTM_ReadLocalDeviceNameFromController,
- .BTM_SetDeviceClass = BTM_SetDeviceClass,
- .BTM_SetLocalDeviceName = BTM_SetLocalDeviceName,
- .BTM_IsDeviceUp = BTM_IsDeviceUp,
- .BTM_ReadDeviceClass = BTM_ReadDeviceClass,
- },
-
- .eir =
- {
- .BTM_GetEirSupportedServices = BTM_GetEirSupportedServices,
- .BTM_GetEirUuidList = BTM_GetEirUuidList,
- .BTM_RemoveEirService = BTM_RemoveEirService,
- .BTM_WriteEIR = BTM_WriteEIR,
- },
- .db =
- {
- .BTM_InqDbRead = BTM_InqDbRead,
- .BTM_InqDbFirst = BTM_InqDbFirst,
- .BTM_InqDbNext = BTM_InqDbNext,
- .BTM_ClearInqDb = BTM_ClearInqDb,
- },
-};
-
-struct btm_client_interface_s& get_btm_client_interface() {
- return btm_client_interface;
-}
diff --git a/stack/btm/btm_dev.cc b/stack/btm/btm_dev.cc
index c64ca190e..0d9f737f9 100644
--- a/stack/btm/btm_dev.cc
+++ b/stack/btm/btm_dev.cc
@@ -30,6 +30,7 @@
#include "bt_common.h"
#include "bt_types.h"
#include "btm_api.h"
+#include "btm_int.h"
#include "btu.h"
#include "device/include/controller.h"
#include "hcidefs.h"
@@ -37,10 +38,6 @@
#include "l2c_api.h"
#include "main/shim/btm_api.h"
#include "main/shim/shim.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/include/acl_api.h"
-
-extern tBTM_CB btm_cb;
/*******************************************************************************
*
@@ -55,14 +52,19 @@ extern tBTM_CB btm_cb;
* bd_name - Name of the peer device. NULL if unknown.
* features - Remote device's features (up to 3 pages).
* NULL if not known
+ * trusted_mask - Bitwise OR of services that do not
+ * require authorization.
+ * (array of uint32_t)
* link_key - Connection link key. NULL if unknown.
*
* Returns true if added OK, else false
*
******************************************************************************/
bool BTM_SecAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
- BD_NAME bd_name, uint8_t* features, LinkKey* p_link_key,
- uint8_t key_type, uint8_t pin_length) {
+ BD_NAME bd_name, uint8_t* features,
+ uint32_t trusted_mask[], LinkKey* p_link_key,
+ uint8_t key_type, tBTM_IO_CAP io_cap,
+ uint8_t pin_length) {
BTM_TRACE_API("%s: link key type:%x", __func__, key_type);
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
@@ -87,7 +89,7 @@ bool BTM_SecAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
* bond state for an existing device here? This logic should be verified
* as part of a larger refactor.
*/
- p_dev_rec->bond_type = tBTM_SEC_DEV_REC::BOND_TYPE_UNKNOWN;
+ p_dev_rec->bond_type = BOND_TYPE_UNKNOWN;
}
if (dev_class) memcpy(p_dev_rec->dev_class, dev_class, DEV_CLASS_LEN);
@@ -97,9 +99,29 @@ bool BTM_SecAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
if (bd_name && bd_name[0]) {
p_dev_rec->sec_flags |= BTM_SEC_NAME_KNOWN;
strlcpy((char*)p_dev_rec->sec_bd_name, (char*)bd_name,
- BTM_MAX_REM_BD_NAME_LEN + 1);
+ BTM_MAX_REM_BD_NAME_LEN);
+ }
+
+ p_dev_rec->num_read_pages = 0;
+ if (features) {
+ bool found = false;
+ memcpy(p_dev_rec->feature_pages, features,
+ sizeof(p_dev_rec->feature_pages));
+ for (int i = HCI_EXT_FEATURES_PAGE_MAX; !found && i >= 0; i--) {
+ for (int j = 0; j < HCI_FEATURE_BYTES_PER_PAGE; j++) {
+ if (p_dev_rec->feature_pages[i][j] != 0) {
+ found = true;
+ p_dev_rec->num_read_pages = i + 1;
+ break;
+ }
+ }
+ }
+ } else {
+ memset(p_dev_rec->feature_pages, 0, sizeof(p_dev_rec->feature_pages));
}
+ BTM_SEC_COPY_TRUSTED_DEVICE(trusted_mask, p_dev_rec->trusted_mask);
+
if (p_link_key) {
VLOG(2) << __func__ << ": BDA: " << bd_addr;
p_dev_rec->sec_flags |= BTM_SEC_LINK_KEY_KNOWN;
@@ -116,7 +138,14 @@ bool BTM_SecAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
}
}
- p_dev_rec->rmt_io_caps = BTM_IO_CAP_OUT;
+#if (BTIF_MIXED_MODE_INCLUDED == TRUE)
+ if (key_type < BTM_MAX_PRE_SM4_LKEY_TYPE)
+ p_dev_rec->sm4 = BTM_SM4_KNOWN;
+ else
+ p_dev_rec->sm4 = BTM_SM4_TRUE;
+#endif
+
+ p_dev_rec->rmt_io_caps = io_cap;
p_dev_rec->device_type |= BT_DEVICE_TYPE_BREDR;
return true;
@@ -172,7 +201,7 @@ bool BTM_SecDeleteDevice(const RawAddress& bd_addr) {
* remove device.
*
******************************************************************************/
-void BTM_SecClearSecurityFlags(const RawAddress& bd_addr) {
+extern void BTM_SecClearSecurityFlags(const RawAddress& bd_addr) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
if (p_dev_rec == NULL) return;
@@ -216,7 +245,8 @@ tBTM_SEC_DEV_REC* btm_sec_alloc_dev(const RawAddress& bd_addr) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_sec_allocate_dev_rec();
- LOG_DEBUG("Allocated device record bd_addr:%s", PRIVATE_ADDRESS(bd_addr));
+ BTM_TRACE_EVENT("%s: allocated p_dev_rec=%p, bd_addr=%s", __func__, p_dev_rec,
+ bd_addr.ToString().c_str());
/* Check with the BT manager if details about remote device are known */
/* outgoing connection */
@@ -242,7 +272,7 @@ tBTM_SEC_DEV_REC* btm_sec_alloc_dev(const RawAddress& bd_addr) {
/*******************************************************************************
*
- * Function btm_dev_support_role_switch
+ * Function btm_dev_support_switch
*
* Description This function is called by the L2CAP to check if remote
* device supports role switch
@@ -250,41 +280,40 @@ tBTM_SEC_DEV_REC* btm_sec_alloc_dev(const RawAddress& bd_addr) {
* Parameters: bd_addr - Address of the peer device
*
* Returns true if device is known and role switch is supported
- * for the link.
*
******************************************************************************/
-bool btm_dev_support_role_switch(const RawAddress& bd_addr) {
- if (BTM_IsScoActiveByBdaddr(bd_addr)) {
- BTM_TRACE_DEBUG("%s Role switch is not allowed if a SCO is up", __func__);
- return false;
- }
-
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
- if (p_dev_rec == nullptr) {
- BTM_TRACE_DEBUG("%s Unknown address for role switch", __func__);
- return false;
- }
+bool btm_dev_support_switch(const RawAddress& bd_addr) {
+ tBTM_SEC_DEV_REC* p_dev_rec;
+ uint8_t xx;
+ bool feature_empty = true;
- if (!controller_get_interface()->supports_central_peripheral_role_switch()) {
- BTM_TRACE_DEBUG("%s Local controller does not support role switch",
- __func__);
- return false;
- }
+ /* Role switch is not allowed if a SCO is up */
+ if (btm_is_sco_active_by_bdaddr(bd_addr)) return (false);
+ p_dev_rec = btm_find_dev(bd_addr);
+ if (p_dev_rec &&
+ controller_get_interface()->supports_master_slave_role_switch()) {
+ if (HCI_SWITCH_SUPPORTED(p_dev_rec->feature_pages[0])) {
+ BTM_TRACE_DEBUG("btm_dev_support_switch return true (feature found)");
+ return (true);
+ }
- if (p_dev_rec->remote_supports_hci_role_switch) {
- BTM_TRACE_DEBUG("%s Peer controller supports role switch", __func__);
- return true;
- }
+ /* If the feature field is all zero, we never received them */
+ for (xx = 0; xx < BD_FEATURES_LEN; xx++) {
+ if (p_dev_rec->feature_pages[0][xx] != 0x00) {
+ feature_empty = false; /* at least one is != 0 */
+ break;
+ }
+ }
- if (!p_dev_rec->remote_feature_received) {
- BTM_TRACE_DEBUG(
- "%s Unknown peer capabilities, assuming peer supports role switch",
- __func__);
- return true;
+ /* If we don't know peer's capabilities, assume it supports Role-switch */
+ if (feature_empty) {
+ BTM_TRACE_DEBUG("btm_dev_support_switch return true (feature empty)");
+ return (true);
+ }
}
- BTM_TRACE_DEBUG("%s Peer controller does not support role switch", __func__);
- return false;
+ BTM_TRACE_DEBUG("btm_dev_support_switch return false");
+ return (false);
}
bool is_handle_equal(void* data, void* context) {
@@ -380,6 +409,7 @@ void btm_consolidate_dev(tBTM_SEC_DEV_REC* p_target_rec) {
p_target_rec->new_encryption_key_is_p256 =
temp_rec.new_encryption_key_is_p256;
+ p_target_rec->no_smp_on_br = temp_rec.no_smp_on_br;
p_target_rec->bond_type = temp_rec.bond_type;
/* remove the combined record */
@@ -493,7 +523,7 @@ tBTM_SEC_DEV_REC* btm_sec_allocate_dev_rec(void) {
// Initialize defaults
p_dev_rec->sec_flags = BTM_SEC_IN_USE;
- p_dev_rec->bond_type = tBTM_SEC_DEV_REC::BOND_TYPE_UNKNOWN;
+ p_dev_rec->bond_type = BOND_TYPE_UNKNOWN;
p_dev_rec->timestamp = btm_cb.dev_rec_count++;
p_dev_rec->rmt_io_caps = BTM_IO_CAP_UNKNOWN;
@@ -510,11 +540,10 @@ tBTM_SEC_DEV_REC* btm_sec_allocate_dev_rec(void) {
* Returns The device bond type if known, otherwise BOND_TYPE_UNKNOWN
*
******************************************************************************/
-tBTM_SEC_DEV_REC::tBTM_BOND_TYPE btm_get_bond_type_dev(
- const RawAddress& bd_addr) {
+tBTM_BOND_TYPE btm_get_bond_type_dev(const RawAddress& bd_addr) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
- if (p_dev_rec == NULL) return tBTM_SEC_DEV_REC::BOND_TYPE_UNKNOWN;
+ if (p_dev_rec == NULL) return BOND_TYPE_UNKNOWN;
return p_dev_rec->bond_type;
}
@@ -530,7 +559,7 @@ tBTM_SEC_DEV_REC::tBTM_BOND_TYPE btm_get_bond_type_dev(
*
******************************************************************************/
bool btm_set_bond_type_dev(const RawAddress& bd_addr,
- tBTM_SEC_DEV_REC::tBTM_BOND_TYPE bond_type) {
+ tBTM_BOND_TYPE bond_type) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
if (p_dev_rec == NULL) return false;
diff --git a/stack/btm/btm_dev.h b/stack/btm/btm_dev.h
deleted file mode 100644
index 985d0343f..000000000
--- a/stack/btm/btm_dev.h
+++ /dev/null
@@ -1,194 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "osi/include/log.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/security_device_record.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/hcimsgs.h"
-#include "types/raw_address.h"
-
-/*******************************************************************************
- *
- * Function BTM_SecAddDevice
- *
- * Description Add/modify device. This function will be normally called
- * during host startup to restore all required information
- * stored in the NVRAM.
- *
- * Parameters: bd_addr - BD address of the peer
- * dev_class - Device Class
- * bd_name - Name of the peer device. NULL if unknown.
- * features - Remote device's features (up to 3 pages).
- * NULL if not known
- * link_key - Connection link key. NULL if unknown.
- *
- * Returns true if added OK, else false
- *
- ******************************************************************************/
-bool BTM_SecAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
- BD_NAME bd_name, uint8_t* features, LinkKey* p_link_key,
- uint8_t key_type, uint8_t pin_length);
-void wipe_secrets_and_remove(tBTM_SEC_DEV_REC* p_dev_rec);
-
-/** Free resources associated with the device associated with |bd_addr| address.
- *
- * *** WARNING ***
- * tBTM_SEC_DEV_REC associated with bd_addr becomes invalid after this function
- * is called, also any of it's fields. i.e. if you use p_dev_rec->bd_addr, it is
- * no longer valid!
- * *** WARNING ***
- *
- * Returns true if removed OK, false if not found or ACL link is active.
- */
-bool BTM_SecDeleteDevice(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function BTM_SecClearSecurityFlags
- *
- * Description Reset the security flags (mark as not-paired) for a given
- * remove device.
- *
- ******************************************************************************/
-void BTM_SecClearSecurityFlags(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function BTM_SecReadDevName
- *
- * Description Looks for the device name in the security database for the
- * specified BD address.
- *
- * Returns Pointer to the name or NULL
- *
- ******************************************************************************/
-char* BTM_SecReadDevName(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function btm_sec_alloc_dev
- *
- * Description Look for the record in the device database for the record
- * with specified address
- *
- * Returns Pointer to the record or NULL
- *
- ******************************************************************************/
-tBTM_SEC_DEV_REC* btm_sec_alloc_dev(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function btm_dev_support_role_switch
- *
- * Description This function is called by the L2CAP to check if remote
- * device supports role switch
- *
- * Parameters: bd_addr - Address of the peer device
- *
- * Returns true if device is known and role switch is supported
- *
- ******************************************************************************/
-bool btm_dev_support_role_switch(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function btm_find_dev_by_handle
- *
- * Description Look for the record in the device database for the record
- * with specified handle
- *
- * Returns Pointer to the record or NULL
- *
- ******************************************************************************/
-tBTM_SEC_DEV_REC* btm_find_dev_by_handle(uint16_t handle);
-
-bool is_address_equal(void* data, void* context);
-
-/*******************************************************************************
- *
- * Function btm_find_dev
- *
- * Description Look for the record in the device database for the record
- * with specified BD address
- *
- * Returns Pointer to the record or NULL
- *
- ******************************************************************************/
-tBTM_SEC_DEV_REC* btm_find_dev(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function btm_consolidate_dev
-5**
- * Description combine security records if identified as same peer
- *
- * Returns none
- *
- ******************************************************************************/
-void btm_consolidate_dev(tBTM_SEC_DEV_REC* p_target_rec);
-
-/*******************************************************************************
- *
- * Function btm_find_or_alloc_dev
- *
- * Description Look for the record in the device database for the record
- * with specified BD address
- *
- * Returns Pointer to the record or NULL
- *
- ******************************************************************************/
-tBTM_SEC_DEV_REC* btm_find_or_alloc_dev(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function btm_sec_allocate_dev_rec
- *
- * Description Attempts to allocate a new device record. If we have
- * exceeded the maximum number of allowable records to
- * allocate, the oldest record will be deleted to make room
- * for the new record.
- *
- * Returns Pointer to the newly allocated record
- *
- ******************************************************************************/
-tBTM_SEC_DEV_REC* btm_sec_allocate_dev_rec(void);
-
-/*******************************************************************************
- *
- * Function btm_get_bond_type_dev
- *
- * Description Get the bond type for a device in the device database
- * with specified BD address
- *
- * Returns The device bond type if known, otherwise BOND_TYPE_UNKNOWN
- *
- ******************************************************************************/
-tBTM_SEC_DEV_REC::tBTM_BOND_TYPE btm_get_bond_type_dev(
- const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function btm_set_bond_type_dev
- *
- * Description Set the bond type for a device in the device database
- * with specified BD address
- *
- * Returns true on success, otherwise false
- *
- ******************************************************************************/
-bool btm_set_bond_type_dev(const RawAddress& bd_addr,
- tBTM_SEC_DEV_REC::tBTM_BOND_TYPE bond_type);
diff --git a/stack/btm/btm_devctl.cc b/stack/btm/btm_devctl.cc
index 598c64fc6..52b66b410 100644
--- a/stack/btm/btm_devctl.cc
+++ b/stack/btm/btm_devctl.cc
@@ -25,33 +25,30 @@
#include <base/logging.h>
#include <stddef.h>
+#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include "bt_types.h"
-#include "bta/dm/bta_dm_int.h"
-#include "bta/sys/bta_sys.h"
+#include "bt_utils.h"
#include "btcore/include/module.h"
-#include "btif/include/btif_bqr.h"
#include "btm_int.h"
#include "btu.h"
#include "common/message_loop_thread.h"
#include "device/include/controller.h"
-#include "hci/include/hci_layer.h"
+#include "hci_layer.h"
#include "hcimsgs.h"
+#include "l2c_int.h"
+#include "osi/include/osi.h"
+#include "stack/gatt/connection_manager.h"
+
+#include "gatt_int.h"
#include "main/shim/btm_api.h"
#include "main/shim/controller.h"
#include "main/shim/shim.h"
-#include "osi/include/osi.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/gatt/connection_manager.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/l2cap_controller_interface.h"
-extern tBTM_CB btm_cb;
+extern bluetooth::common::MessageLoopThread bt_startup_thread;
-extern void btm_inq_db_reset(void);
-extern void btm_pm_reset(void);
/******************************************************************************/
/* L O C A L D A T A D E F I N I T I O N S */
/******************************************************************************/
@@ -71,7 +68,8 @@ extern void btm_pm_reset(void);
/* L O C A L F U N C T I O N P R O T O T Y P E S */
/******************************************************************************/
-static void decode_controller_support();
+static void btm_decode_ext_features_page(uint8_t page_number,
+ const BD_FEATURES p_features);
static void BTM_BT_Quality_Report_VSE_CBack(uint8_t length, uint8_t* p_stream);
/*******************************************************************************
@@ -95,26 +93,34 @@ void btm_dev_init() {
alarm_new("btm.read_automatic_flush_timeout_timer");
btm_cb.devcb.read_link_quality_timer =
alarm_new("btm.read_link_quality_timer");
+ btm_cb.devcb.read_inq_tx_power_timer =
+ alarm_new("btm.read_inq_tx_power_timer");
+ btm_cb.devcb.qos_setup_timer = alarm_new("btm.qos_setup_timer");
btm_cb.devcb.read_tx_power_timer = alarm_new("btm.read_tx_power_timer");
-}
-void btm_dev_free() {
- alarm_free(btm_cb.devcb.read_local_name_timer);
- alarm_free(btm_cb.devcb.read_rssi_timer);
- alarm_free(btm_cb.devcb.read_failed_contact_counter_timer);
- alarm_free(btm_cb.devcb.read_automatic_flush_timeout_timer);
- alarm_free(btm_cb.devcb.read_link_quality_timer);
- alarm_free(btm_cb.devcb.read_tx_power_timer);
+ btm_cb.btm_acl_pkt_types_supported =
+ BTM_ACL_PKT_TYPES_MASK_DH1 + BTM_ACL_PKT_TYPES_MASK_DM1 +
+ BTM_ACL_PKT_TYPES_MASK_DH3 + BTM_ACL_PKT_TYPES_MASK_DM3 +
+ BTM_ACL_PKT_TYPES_MASK_DH5 + BTM_ACL_PKT_TYPES_MASK_DM5;
+
+ btm_cb.btm_sco_pkt_types_supported =
+ ESCO_PKT_TYPES_MASK_HV1 + ESCO_PKT_TYPES_MASK_HV2 +
+ ESCO_PKT_TYPES_MASK_HV3 + ESCO_PKT_TYPES_MASK_EV3 +
+ ESCO_PKT_TYPES_MASK_EV4 + ESCO_PKT_TYPES_MASK_EV5;
}
/*******************************************************************************
*
* Function btm_db_reset
*
+ * Description This function is called by BTM_DeviceReset and clears out
+ * any pending callbacks for inquiries, discoveries, other
+ * pending functions that may be in progress.
+ *
* Returns void
*
******************************************************************************/
-void BTM_db_reset(void) {
+static void btm_db_reset(void) {
tBTM_CMPL_CB* p_cb;
btm_inq_db_reset();
@@ -160,13 +166,14 @@ void BTM_db_reset(void) {
}
}
-static bool set_sec_state_idle(void* data, void* context) {
+bool set_sec_state_idle(void* data, void* context) {
tBTM_SEC_DEV_REC* p_dev_rec = static_cast<tBTM_SEC_DEV_REC*>(data);
p_dev_rec->sec_state = BTM_SEC_STATE_IDLE;
return true;
}
-void BTM_reset_complete() {
+static void reset_complete(void* result) {
+ CHECK(result == FUTURE_SUCCESS);
const controller_t* controller = controller_get_interface();
/* Tell L2CAP that all connections are gone */
@@ -185,16 +192,17 @@ void BTM_reset_complete() {
btm_cb.btm_inq_vars.page_scan_period = HCI_DEF_PAGESCAN_INTERVAL;
btm_cb.btm_inq_vars.page_scan_type = HCI_DEF_SCAN_TYPE;
- btm_cb.ble_ctr_cb.set_connection_state_idle();
+ btm_cb.ble_ctr_cb.conn_state = BLE_CONN_IDLE;
connection_manager::reset(true);
btm_pm_reset();
- l2c_link_init();
+ l2c_link_processs_num_bufs(controller->get_acl_buffer_count_classic());
// setup the random number generator
std::srand(std::time(nullptr));
+#if (BLE_PRIVACY_SPT == TRUE)
/* Set up the BLE privacy settings */
if (controller->supports_ble() && controller->supports_ble_privacy() &&
controller->get_ble_resolving_list_max_size() > 0) {
@@ -203,15 +211,39 @@ void BTM_reset_complete() {
btsnd_hcic_ble_set_rand_priv_addr_timeout(
btm_get_next_private_addrress_interval_ms() / 1000);
}
+#endif
if (controller->supports_ble()) {
+ btm_ble_white_list_init(controller->get_ble_white_list_size());
l2c_link_processs_ble_num_bufs(controller->get_acl_buffer_count_ble());
}
BTM_SetPinType(btm_cb.cfg.pin_type, btm_cb.cfg.pin_code,
btm_cb.cfg.pin_code_len);
- decode_controller_support();
+ for (int i = 0; i <= controller->get_last_features_classic_index(); i++) {
+ btm_decode_ext_features_page(i,
+ controller->get_features_classic(i)->as_array);
+ }
+
+ btm_report_device_status(BTM_DEV_STATUS_UP);
+}
+
+// TODO(zachoverflow): remove this function
+void BTM_DeviceReset(UNUSED_ATTR tBTM_CMPL_CB* p_cb) {
+ /* Flush all ACL connections */
+ btm_acl_device_down();
+
+ /* Clear the callback, so application would not hang on reset */
+ btm_db_reset();
+
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ module_start_up_callbacked_wrapper(get_module(GD_CONTROLLER_MODULE),
+ &bt_startup_thread, reset_complete);
+ } else {
+ module_start_up_callbacked_wrapper(get_module(CONTROLLER_MODULE),
+ &bt_startup_thread, reset_complete);
+ }
}
/*******************************************************************************
@@ -234,74 +266,161 @@ bool BTM_IsDeviceUp(void) { return controller_get_interface()->get_is_ready(); }
* Returns void
*
******************************************************************************/
-static void btm_read_local_name_timeout(UNUSED_ATTR void* data) {
+void btm_read_local_name_timeout(UNUSED_ATTR void* data) {
tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_rln_cmpl_cb;
btm_cb.devcb.p_rln_cmpl_cb = NULL;
if (p_cb) (*p_cb)((void*)NULL);
}
-static void decode_controller_support() {
- const controller_t* controller = controller_get_interface();
-
- /* Create (e)SCO supported packet types mask */
- btm_cb.btm_sco_pkt_types_supported = 0;
- btm_cb.sco_cb.esco_supported = false;
- if (controller->supports_sco()) {
- btm_cb.btm_sco_pkt_types_supported = ESCO_PKT_TYPES_MASK_HV1;
+/*******************************************************************************
+ *
+ * Function btm_decode_ext_features_page
+ *
+ * Description This function is decodes a features page.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btm_decode_ext_features_page(uint8_t page_number,
+ const uint8_t* p_features) {
+ CHECK(p_features != nullptr);
+ BTM_TRACE_DEBUG("btm_decode_ext_features_page page: %d", page_number);
+ switch (page_number) {
+ /* Extended (Legacy) Page 0 */
+ case 0:
+
+ /* Create ACL supported packet types mask */
+ btm_cb.btm_acl_pkt_types_supported =
+ (BTM_ACL_PKT_TYPES_MASK_DH1 + BTM_ACL_PKT_TYPES_MASK_DM1);
+
+ if (HCI_3_SLOT_PACKETS_SUPPORTED(p_features))
+ btm_cb.btm_acl_pkt_types_supported |=
+ (BTM_ACL_PKT_TYPES_MASK_DH3 + BTM_ACL_PKT_TYPES_MASK_DM3);
+
+ if (HCI_5_SLOT_PACKETS_SUPPORTED(p_features))
+ btm_cb.btm_acl_pkt_types_supported |=
+ (BTM_ACL_PKT_TYPES_MASK_DH5 + BTM_ACL_PKT_TYPES_MASK_DM5);
+
+ /* Add in EDR related ACL types */
+ if (!HCI_EDR_ACL_2MPS_SUPPORTED(p_features)) {
+ btm_cb.btm_acl_pkt_types_supported |=
+ (BTM_ACL_PKT_TYPES_MASK_NO_2_DH1 + BTM_ACL_PKT_TYPES_MASK_NO_2_DH3 +
+ BTM_ACL_PKT_TYPES_MASK_NO_2_DH5);
+ }
- if (controller->supports_hv2_packets())
- btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_HV2;
+ if (!HCI_EDR_ACL_3MPS_SUPPORTED(p_features)) {
+ btm_cb.btm_acl_pkt_types_supported |=
+ (BTM_ACL_PKT_TYPES_MASK_NO_3_DH1 + BTM_ACL_PKT_TYPES_MASK_NO_3_DH3 +
+ BTM_ACL_PKT_TYPES_MASK_NO_3_DH5);
+ }
- if (controller->supports_hv3_packets())
- btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_HV3;
- }
+ /* Check to see if 3 and 5 slot packets are available */
+ if (HCI_EDR_ACL_2MPS_SUPPORTED(p_features) ||
+ HCI_EDR_ACL_3MPS_SUPPORTED(p_features)) {
+ if (!HCI_3_SLOT_EDR_ACL_SUPPORTED(p_features))
+ btm_cb.btm_acl_pkt_types_supported |=
+ (BTM_ACL_PKT_TYPES_MASK_NO_2_DH3 +
+ BTM_ACL_PKT_TYPES_MASK_NO_3_DH3);
+
+ if (!HCI_5_SLOT_EDR_ACL_SUPPORTED(p_features))
+ btm_cb.btm_acl_pkt_types_supported |=
+ (BTM_ACL_PKT_TYPES_MASK_NO_2_DH5 +
+ BTM_ACL_PKT_TYPES_MASK_NO_3_DH5);
+ }
- if (controller->supports_ev3_packets())
- btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_EV3;
+ BTM_TRACE_DEBUG("Local supported ACL packet types: 0x%04x",
+ btm_cb.btm_acl_pkt_types_supported);
- if (controller->supports_ev4_packets())
- btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_EV4;
+ /* Create (e)SCO supported packet types mask */
+ btm_cb.btm_sco_pkt_types_supported = 0;
+ btm_cb.sco_cb.esco_supported = false;
+ if (HCI_SCO_LINK_SUPPORTED(p_features)) {
+ btm_cb.btm_sco_pkt_types_supported = ESCO_PKT_TYPES_MASK_HV1;
- if (controller->supports_ev5_packets())
- btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_EV5;
+ if (HCI_HV2_PACKETS_SUPPORTED(p_features))
+ btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_HV2;
- if (btm_cb.btm_sco_pkt_types_supported & BTM_ESCO_LINK_ONLY_MASK) {
- btm_cb.sco_cb.esco_supported = true;
+ if (HCI_HV3_PACKETS_SUPPORTED(p_features))
+ btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_HV3;
+ }
- /* Add in EDR related eSCO types */
- if (controller->supports_esco_2m_phy()) {
- if (!controller->supports_3_slot_edr_packets())
- btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_NO_2_EV5;
- } else {
- btm_cb.btm_sco_pkt_types_supported |=
- (ESCO_PKT_TYPES_MASK_NO_2_EV3 + ESCO_PKT_TYPES_MASK_NO_2_EV5);
- }
+ if (HCI_ESCO_EV3_SUPPORTED(p_features))
+ btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_EV3;
+
+ if (HCI_ESCO_EV4_SUPPORTED(p_features))
+ btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_EV4;
+
+ if (HCI_ESCO_EV5_SUPPORTED(p_features))
+ btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_EV5;
+ if (btm_cb.btm_sco_pkt_types_supported & BTM_ESCO_LINK_ONLY_MASK) {
+ btm_cb.sco_cb.esco_supported = true;
+
+ /* Add in EDR related eSCO types */
+ if (HCI_EDR_ESCO_2MPS_SUPPORTED(p_features)) {
+ if (!HCI_3_SLOT_EDR_ESCO_SUPPORTED(p_features))
+ btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_NO_2_EV5;
+ } else {
+ btm_cb.btm_sco_pkt_types_supported |=
+ (ESCO_PKT_TYPES_MASK_NO_2_EV3 + ESCO_PKT_TYPES_MASK_NO_2_EV5);
+ }
+
+ if (HCI_EDR_ESCO_3MPS_SUPPORTED(p_features)) {
+ if (!HCI_3_SLOT_EDR_ESCO_SUPPORTED(p_features))
+ btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_NO_3_EV5;
+ } else {
+ btm_cb.btm_sco_pkt_types_supported |=
+ (ESCO_PKT_TYPES_MASK_NO_3_EV3 + ESCO_PKT_TYPES_MASK_NO_3_EV5);
+ }
+ }
- if (controller->supports_esco_3m_phy()) {
- if (!controller->supports_3_slot_edr_packets())
- btm_cb.btm_sco_pkt_types_supported |= ESCO_PKT_TYPES_MASK_NO_3_EV5;
- } else {
- btm_cb.btm_sco_pkt_types_supported |=
- (ESCO_PKT_TYPES_MASK_NO_3_EV3 + ESCO_PKT_TYPES_MASK_NO_3_EV5);
- }
- }
+ BTM_TRACE_DEBUG("Local supported SCO packet types: 0x%04x",
+ btm_cb.btm_sco_pkt_types_supported);
+
+ /* Create Default Policy Settings */
+ if (HCI_SWITCH_SUPPORTED(p_features))
+ btm_cb.btm_def_link_policy |= HCI_ENABLE_MASTER_SLAVE_SWITCH;
+ else
+ btm_cb.btm_def_link_policy &= ~HCI_ENABLE_MASTER_SLAVE_SWITCH;
+
+ if (HCI_HOLD_MODE_SUPPORTED(p_features))
+ btm_cb.btm_def_link_policy |= HCI_ENABLE_HOLD_MODE;
+ else
+ btm_cb.btm_def_link_policy &= ~HCI_ENABLE_HOLD_MODE;
+
+ if (HCI_SNIFF_MODE_SUPPORTED(p_features))
+ btm_cb.btm_def_link_policy |= HCI_ENABLE_SNIFF_MODE;
+ else
+ btm_cb.btm_def_link_policy &= ~HCI_ENABLE_SNIFF_MODE;
+
+ if (HCI_PARK_MODE_SUPPORTED(p_features))
+ btm_cb.btm_def_link_policy |= HCI_ENABLE_PARK_MODE;
+ else
+ btm_cb.btm_def_link_policy &= ~HCI_ENABLE_PARK_MODE;
+
+ btm_sec_dev_reset();
+
+ if (HCI_LMP_INQ_RSSI_SUPPORTED(p_features)) {
+ if (HCI_EXT_INQ_RSP_SUPPORTED(p_features))
+ BTM_SetInquiryMode(BTM_INQ_RESULT_EXTENDED);
+ else
+ BTM_SetInquiryMode(BTM_INQ_RESULT_WITH_RSSI);
+ }
- BTM_TRACE_DEBUG("Local supported SCO packet types: 0x%04x",
- btm_cb.btm_sco_pkt_types_supported);
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
+ if (HCI_NON_FLUSHABLE_PB_SUPPORTED(p_features))
+ l2cu_set_non_flushable_pbf(true);
+ else
+ l2cu_set_non_flushable_pbf(false);
+#endif
+ BTM_SetPageScanType(BTM_DEFAULT_SCAN_TYPE);
+ BTM_SetInquiryScanType(BTM_DEFAULT_SCAN_TYPE);
- BTM_acl_after_controller_started(controller_get_interface());
- btm_sec_dev_reset();
+ break;
- if (controller->supports_rssi_with_inquiry_results()) {
- if (controller->supports_extended_inquiry_response())
- BTM_SetInquiryMode(BTM_INQ_RESULT_EXTENDED);
- else
- BTM_SetInquiryMode(BTM_INQ_RESULT_WITH_RSSI);
+ default:
+ BTM_TRACE_WARNING("%s: feature page %d ignored", __func__, page_number);
+ break;
}
-
- l2cu_set_non_flushable_pbf(controller->supports_non_flushable_pb());
- BTM_EnableInterlacedPageScan();
- BTM_EnableInterlacedInquiryScan();
}
/*******************************************************************************
@@ -323,7 +442,7 @@ tBTM_STATUS BTM_SetLocalDeviceName(char* p_name) {
/* Save the device name if local storage is enabled */
p = (uint8_t*)btm_cb.cfg.bd_name;
if (p != (uint8_t*)p_name)
- strlcpy(btm_cb.cfg.bd_name, p_name, BTM_MAX_LOC_BD_NAME_LEN + 1);
+ strlcpy(btm_cb.cfg.bd_name, p_name, BTM_MAX_LOC_BD_NAME_LEN);
btsnd_hcic_change_name(p);
return (BTM_CMD_STARTED);
@@ -439,6 +558,44 @@ uint8_t* BTM_ReadDeviceClass(void) {
/*******************************************************************************
*
+ * Function BTM_ReadLocalFeatures
+ *
+ * Description This function is called to read the local features
+ *
+ * Returns pointer to the local features string
+ *
+ ******************************************************************************/
+// TODO(zachoverflow): get rid of this function
+uint8_t* BTM_ReadLocalFeatures(void) {
+ // Discarding const modifier for now, until this function dies
+ return (uint8_t*)controller_get_interface()
+ ->get_features_classic(0)
+ ->as_array;
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_RegisterForDeviceStatusNotif
+ *
+ * Description This function is called to register for device status
+ * change notifications.
+ *
+ * If one registration is already there calling function should
+ * save the pointer to the function that is return and
+ * call it when processing of the event is complete
+ *
+ * Returns status of the operation
+ *
+ ******************************************************************************/
+tBTM_DEV_STATUS_CB* BTM_RegisterForDeviceStatusNotif(tBTM_DEV_STATUS_CB* p_cb) {
+ tBTM_DEV_STATUS_CB* p_prev = btm_cb.devcb.p_dev_status_cb;
+
+ btm_cb.devcb.p_dev_status_cb = p_cb;
+ return (p_prev);
+}
+
+/*******************************************************************************
+ *
* Function BTM_VendorSpecificCommand
*
* Description Send a vendor specific HCI command to the controller.
@@ -542,6 +699,9 @@ tBTM_STATUS BTM_RegisterForVSEvents(tBTM_VS_EVT_CB* p_cb, bool is_register) {
*
* Description Process event HCI_VENDOR_SPECIFIC_EVT
*
+ * Note: Some controllers do not send command complete, so
+ * the callback and busy flag are cleared here also.
+ *
* Returns void
*
******************************************************************************/
@@ -550,46 +710,6 @@ void btm_vendor_specific_evt(uint8_t* p, uint8_t evt_len) {
BTM_TRACE_DEBUG("BTM Event: Vendor Specific event from controller");
- // Handle BQR events
- uint8_t* bqr_ptr = p;
- uint8_t event_code;
- uint8_t len;
- STREAM_TO_UINT8(event_code, bqr_ptr);
- STREAM_TO_UINT8(len, bqr_ptr);
- // Check if there's at least a subevent code
- if (len > 1 && evt_len > 1 && event_code == HCI_VENDOR_SPECIFIC_EVT) {
- uint8_t sub_event_code;
- STREAM_TO_UINT8(sub_event_code, bqr_ptr);
- if (sub_event_code == HCI_VSE_SUBCODE_BQR_SUB_EVT) {
- // Excluding the HCI Event packet header and 1 octet sub-event code
- int16_t bqr_parameter_length = evt_len - HCIE_PREAMBLE_SIZE - 1;
- uint8_t* p_bqr_event = bqr_ptr;
- // The stream currently points to the BQR sub-event parameters
- switch (sub_event_code) {
- case bluetooth::bqr::QUALITY_REPORT_ID_LMP_LL_MESSAGE_TRACE:
- if (bqr_parameter_length >= bluetooth::bqr::kLogDumpParamTotalLen) {
- bluetooth::bqr::DumpLmpLlMessage(bqr_parameter_length, p_bqr_event);
- } else {
- LOG_INFO("Malformed LMP event of length %hd", bqr_parameter_length);
- }
-
- break;
-
- case bluetooth::bqr::QUALITY_REPORT_ID_BT_SCHEDULING_TRACE:
- if (bqr_parameter_length >= bluetooth::bqr::kLogDumpParamTotalLen) {
- bluetooth::bqr::DumpBtScheduling(bqr_parameter_length, p_bqr_event);
- } else {
- LOG_INFO("Malformed TRACE event of length %hd",
- bqr_parameter_length);
- }
- break;
-
- default:
- LOG_INFO("Unhandled BQR subevent 0x%02hxx", sub_event_code);
- }
- }
- }
-
for (i = 0; i < BTM_MAX_VSE_CALLBACKS; i++) {
if (btm_cb.devcb.p_vend_spec_cb[i])
(*btm_cb.devcb.p_vend_spec_cb[i])(evt_len, p);
@@ -652,12 +772,14 @@ tBTM_STATUS BTM_EnableTestMode(void) {
HCI_FILTER_COND_NEW_DEVICE, &cond, sizeof(cond));
/* put device to connectable mode */
- if (BTM_SetConnectability(BTM_CONNECTABLE) != BTM_SUCCESS) {
+ if (BTM_SetConnectability(BTM_CONNECTABLE, BTM_DEFAULT_CONN_WINDOW,
+ BTM_DEFAULT_CONN_INTERVAL) != BTM_SUCCESS) {
return BTM_NO_RESOURCES;
}
/* put device to discoverable mode */
- if (BTM_SetDiscoverability(BTM_GENERAL_DISCOVERABLE) != BTM_SUCCESS) {
+ if (BTM_SetDiscoverability(BTM_GENERAL_DISCOVERABLE, BTM_DEFAULT_DISC_WINDOW,
+ BTM_DEFAULT_DISC_INTERVAL) != BTM_SUCCESS) {
return BTM_NO_RESOURCES;
}
@@ -741,6 +863,24 @@ void btm_delete_stored_link_key_complete(uint8_t* p) {
/*******************************************************************************
*
+ * Function btm_report_device_status
+ *
+ * Description This function is called when there is a change in the device
+ * status. This function will report the new device status to
+ * the application
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_report_device_status(tBTM_DEV_STATUS status) {
+ tBTM_DEV_STATUS_CB* p_cb = btm_cb.devcb.p_dev_status_cb;
+
+ /* Call the call back to pass the device status to application */
+ if (p_cb) (*p_cb)(status);
+}
+
+/*******************************************************************************
+ *
* Function BTM_BT_Quality_Report_VSE_CBack
*
* Description Callback invoked on receiving of Vendor Specific Events.
diff --git a/stack/btm/btm_inq.cc b/stack/btm/btm_inq.cc
index 890cd3a0d..800025c39 100644
--- a/stack/btm/btm_inq.cc
+++ b/stack/btm/btm_inq.cc
@@ -25,8 +25,7 @@
*
******************************************************************************/
-#define LOG_TAG "bluetooth"
-
+#include <log/log.h>
#include <stddef.h>
#include <stdio.h>
#include <stdlib.h>
@@ -34,36 +33,18 @@
#include "common/time_util.h"
#include "device/include/controller.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
#include "advertise_data_parser.h"
#include "bt_common.h"
#include "bt_types.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
#include "hcidefs.h"
+#include "hcimsgs.h"
#include "main/shim/btm_api.h"
#include "main/shim/shim.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_int.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_ble_api.h"
-#include "stack/include/btu.h"
-#include "stack/include/hcimsgs.h"
-#include "stack/include/inq_hci_link_interface.h"
-
-extern tBTM_CB btm_cb;
-
-extern void btm_inq_remote_name_timer_timeout(void* data);
-extern tBTM_STATUS btm_ble_read_remote_name(const RawAddress& remote_bda,
- tBTM_CMPL_CB* p_cb);
-extern bool btm_ble_cancel_remote_name(const RawAddress& remote_bda);
-extern tBTM_STATUS btm_ble_set_discoverability(uint16_t combined_mode);
-extern tBTM_STATUS btm_ble_set_connectability(uint16_t combined_mode);
-
-extern tBTM_STATUS btm_ble_start_inquiry(uint8_t duration);
-extern void btm_ble_stop_inquiry(void);
using bluetooth::Uuid;
@@ -75,8 +56,6 @@ using bluetooth::Uuid;
#define BTM_INQ_DEBUG FALSE
#endif
-#define BTIF_DM_DEFAULT_INQ_MAX_DURATION 10
-
/******************************************************************************/
/* L O C A L D A T A D E F I N I T I O N S */
/******************************************************************************/
@@ -136,12 +115,10 @@ const uint16_t BTM_EIR_UUID_LKUP_TBL[BTM_EIR_MAX_SERVICES] = {
/******************************************************************************/
/* L O C A L F U N C T I O N P R O T O T Y P E S */
/******************************************************************************/
-static void btm_clr_inq_db(const RawAddress* p_bda);
+static void btm_initiate_inquiry(tBTM_INQUIRY_VAR_ST* p_inq);
+static tBTM_STATUS btm_set_inq_event_filter(uint8_t filter_cond_type,
+ tBTM_INQ_FILT_COND* p_filt_cond);
void btm_clr_inq_result_flt(void);
-static void btm_inq_rmt_name_failed_cancelled(void);
-static tBTM_STATUS btm_initiate_rem_name(const RawAddress& remote_bda,
- uint8_t origin, uint64_t timeout_ms,
- tBTM_CMPL_CB* p_cb);
static uint8_t btm_convert_uuid_to_eir_service(uint16_t uuid16);
void btm_set_eir_uuid(uint8_t* p_eir, tBTM_INQ_RESULTS* p_results);
@@ -150,14 +127,6 @@ static const uint8_t* btm_eir_get_uuid_list(uint8_t* p_eir, size_t eir_len,
uint8_t* p_num_uuid,
uint8_t* p_uuid_list_type);
-void SendRemoteNameRequest(const RawAddress& raw_address) {
- if (bluetooth::shim::is_gd_shim_enabled()) {
- return bluetooth::shim::SendRemoteNameRequest(raw_address);
- } else {
- btsnd_hcic_rmt_name_req(raw_address, HCI_PAGE_SCAN_REP_MODE_R1,
- HCI_MANDATARY_PAGE_SCAN_MODE, 0);
- }
-}
/*******************************************************************************
*
* Function BTM_SetDiscoverability
@@ -174,9 +143,10 @@ void SendRemoteNameRequest(const RawAddress& raw_address) {
* BTM_WRONG_MODE if the device is not up.
*
******************************************************************************/
-tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode) {
+tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode, uint16_t window,
+ uint16_t interval) {
if (bluetooth::shim::is_gd_shim_enabled()) {
- return bluetooth::shim::BTM_SetDiscoverability(inq_mode, 0, 0);
+ return bluetooth::shim::BTM_SetDiscoverability(inq_mode, window, interval);
}
uint8_t scan_mode = 0;
@@ -187,8 +157,6 @@ tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode) {
LAP temp_lap[2];
bool is_limited;
bool cod_limited;
- uint16_t window = BTM_DEFAULT_DISC_WINDOW;
- uint16_t interval = BTM_DEFAULT_DISC_INTERVAL;
BTM_TRACE_API("BTM_SetDiscoverability");
if (controller_get_interface()->supports_ble()) {
@@ -207,8 +175,26 @@ tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode) {
if (!controller_get_interface()->get_is_ready()) return (BTM_DEV_RESET);
/* If the window and/or interval is '0', set to default values */
- BTM_TRACE_API("BTM_SetDiscoverability: mode %d [NonDisc-0, Lim-1, Gen-2]",
- inq_mode);
+ if (!window) window = BTM_DEFAULT_DISC_WINDOW;
+
+ if (!interval) interval = BTM_DEFAULT_DISC_INTERVAL;
+
+ BTM_TRACE_API(
+ "BTM_SetDiscoverability: mode %d [NonDisc-0, Lim-1, Gen-2], window "
+ "0x%04x, interval 0x%04x",
+ inq_mode, window, interval);
+
+ /*** Check for valid window and interval parameters ***/
+ /*** Only check window and duration if mode is connectable ***/
+ if (inq_mode != BTM_NON_DISCOVERABLE) {
+ /* window must be less than or equal to interval */
+ if (window < HCI_MIN_INQUIRYSCAN_WINDOW ||
+ window > HCI_MAX_INQUIRYSCAN_WINDOW ||
+ interval < HCI_MIN_INQUIRYSCAN_INTERVAL ||
+ interval > HCI_MAX_INQUIRYSCAN_INTERVAL || window > interval) {
+ return (BTM_ILLEGAL_VALUE);
+ }
+ }
/* Set the IAC if needed */
if (inq_mode != BTM_NON_DISCOVERABLE) {
@@ -260,35 +246,78 @@ tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode) {
return (BTM_SUCCESS);
}
-void BTM_EnableInterlacedInquiryScan() {
+/*******************************************************************************
+ *
+ * Function BTM_SetInquiryScanType
+ *
+ * Description This function is called to set the iquiry scan-type to
+ * standard or interlaced.
+ *
+ * Returns BTM_SUCCESS if successful
+ * BTM_MODE_UNSUPPORTED if not a 1.2 device
+ * BTM_WRONG_MODE if the device is not up.
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SetInquiryScanType(uint16_t scan_type) {
if (bluetooth::shim::is_gd_shim_enabled()) {
- bluetooth::shim::BTM_EnableInterlacedInquiryScan();
+ return bluetooth::shim::BTM_SetInquiryScanType(scan_type);
}
- BTM_TRACE_API("BTM_EnableInterlacedInquiryScan");
- if (!controller_get_interface()->supports_interlaced_inquiry_scan() ||
- btm_cb.btm_inq_vars.inq_scan_type == BTM_SCAN_TYPE_INTERLACED) {
- return;
- }
+ BTM_TRACE_API("BTM_SetInquiryScanType");
+ if (scan_type != BTM_SCAN_TYPE_STANDARD &&
+ scan_type != BTM_SCAN_TYPE_INTERLACED)
+ return (BTM_ILLEGAL_VALUE);
+
+ /* whatever app wants if device is not 1.2 scan type should be STANDARD */
+ if (!controller_get_interface()->supports_interlaced_inquiry_scan())
+ return (BTM_MODE_UNSUPPORTED);
- btsnd_hcic_write_inqscan_type(BTM_SCAN_TYPE_INTERLACED);
- btm_cb.btm_inq_vars.inq_scan_type = BTM_SCAN_TYPE_INTERLACED;
+ /* Check for scan type if configuration has been changed */
+ if (scan_type != btm_cb.btm_inq_vars.inq_scan_type) {
+ if (BTM_IsDeviceUp()) {
+ btsnd_hcic_write_inqscan_type((uint8_t)scan_type);
+ btm_cb.btm_inq_vars.inq_scan_type = scan_type;
+ } else
+ return (BTM_WRONG_MODE);
+ }
+ return (BTM_SUCCESS);
}
-void BTM_EnableInterlacedPageScan() {
+/*******************************************************************************
+ *
+ * Function BTM_SetPageScanType
+ *
+ * Description This function is called to set the page scan-type to
+ * standard or interlaced.
+ *
+ * Returns BTM_SUCCESS if successful
+ * BTM_MODE_UNSUPPORTED if not a 1.2 device
+ * BTM_WRONG_MODE if the device is not up.
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SetPageScanType(uint16_t scan_type) {
if (bluetooth::shim::is_gd_shim_enabled()) {
- bluetooth::shim::BTM_EnableInterlacedPageScan();
- return;
+ return bluetooth::shim::BTM_SetPageScanType(scan_type);
}
- BTM_TRACE_API("BTM_EnableInterlacedPageScan");
- if (!controller_get_interface()->supports_interlaced_inquiry_scan() ||
- btm_cb.btm_inq_vars.page_scan_type == BTM_SCAN_TYPE_INTERLACED) {
- return;
- }
+ BTM_TRACE_API("BTM_SetPageScanType");
+ if (scan_type != BTM_SCAN_TYPE_STANDARD &&
+ scan_type != BTM_SCAN_TYPE_INTERLACED)
+ return (BTM_ILLEGAL_VALUE);
- btsnd_hcic_write_pagescan_type(BTM_SCAN_TYPE_INTERLACED);
- btm_cb.btm_inq_vars.page_scan_type = BTM_SCAN_TYPE_INTERLACED;
+ /* whatever app wants if device is not 1.2 scan type should be STANDARD */
+ if (!controller_get_interface()->supports_interlaced_inquiry_scan())
+ return (BTM_MODE_UNSUPPORTED);
+
+ /* Check for scan type if configuration has been changed */
+ if (scan_type != btm_cb.btm_inq_vars.page_scan_type) {
+ if (BTM_IsDeviceUp()) {
+ btsnd_hcic_write_pagescan_type((uint8_t)scan_type);
+ btm_cb.btm_inq_vars.page_scan_type = scan_type;
+ } else
+ return (BTM_WRONG_MODE);
+ }
+ return (BTM_SUCCESS);
}
/*******************************************************************************
@@ -333,6 +362,76 @@ tBTM_STATUS BTM_SetInquiryMode(uint8_t mode) {
/*******************************************************************************
*
+ * Function BTM_ReadDiscoverability
+ *
+ * Description This function is called to read the current discoverability
+ * mode of the device.
+ *
+ * Output Params: p_window - current inquiry scan duration
+ * p_interval - current inquiry scan interval
+ *
+ * Returns BTM_NON_DISCOVERABLE, BTM_LIMITED_DISCOVERABLE, or
+ * BTM_GENERAL_DISCOVERABLE
+ *
+ ******************************************************************************/
+uint16_t BTM_ReadDiscoverability(uint16_t* p_window, uint16_t* p_interval) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_ReadDiscoverability(p_window, p_interval);
+ }
+
+ BTM_TRACE_API("BTM_ReadDiscoverability");
+ if (p_window) *p_window = btm_cb.btm_inq_vars.inq_scan_window;
+
+ if (p_interval) *p_interval = btm_cb.btm_inq_vars.inq_scan_period;
+
+ return (btm_cb.btm_inq_vars.discoverable_mode);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_CancelPeriodicInquiry
+ *
+ * Description This function cancels a periodic inquiry
+ *
+ * Returns
+ * BTM_NO_RESOURCES if could not allocate a message buffer
+ * BTM_SUCCESS - if cancelling the periodic inquiry
+ * BTM_WRONG_MODE if the device is not up.
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_CancelPeriodicInquiry(void) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_CancelPeriodicInquiry();
+ }
+
+ tBTM_INQUIRY_VAR_ST* p_inq = &btm_cb.btm_inq_vars;
+ tBTM_STATUS status = BTM_SUCCESS;
+ BTM_TRACE_API("BTM_CancelPeriodicInquiry called");
+
+ /*** Make sure the device is ready ***/
+ if (!BTM_IsDeviceUp()) return (BTM_WRONG_MODE);
+
+ /* Only cancel if one is active */
+ if (btm_cb.btm_inq_vars.inq_active & BTM_PERIODIC_INQUIRY_ACTIVE) {
+ btm_cb.btm_inq_vars.inq_active = BTM_INQUIRY_INACTIVE;
+ btm_cb.btm_inq_vars.p_inq_results_cb = NULL;
+
+ btsnd_hcic_exit_per_inq();
+
+ /* If the event filter is in progress, mark it so that the processing of the
+ return
+ event will be ignored */
+ if (p_inq->inqfilt_active) p_inq->pending_filt_complete_event++;
+
+ p_inq->inqfilt_active = false;
+ p_inq->inq_counter++;
+ }
+
+ return (status);
+}
+
+/*******************************************************************************
+ *
* Function BTM_SetConnectability
*
* Description This function is called to set the device into or out of
@@ -345,14 +444,13 @@ tBTM_STATUS BTM_SetInquiryMode(uint8_t mode) {
* BTM_WRONG_MODE if the device is not up.
*
******************************************************************************/
-tBTM_STATUS BTM_SetConnectability(uint16_t page_mode) {
+tBTM_STATUS BTM_SetConnectability(uint16_t page_mode, uint16_t window,
+ uint16_t interval) {
if (bluetooth::shim::is_gd_shim_enabled()) {
- return bluetooth::shim::BTM_SetConnectability(page_mode, 0, 0);
+ return bluetooth::shim::BTM_SetConnectability(page_mode, window, interval);
}
uint8_t scan_mode = 0;
- uint16_t window = BTM_DEFAULT_CONN_WINDOW;
- uint16_t interval = BTM_DEFAULT_CONN_INTERVAL;
tBTM_INQUIRY_VAR_ST* p_inq = &btm_cb.btm_inq_vars;
BTM_TRACE_API("BTM_SetConnectability");
@@ -373,11 +471,26 @@ tBTM_STATUS BTM_SetConnectability(uint16_t page_mode) {
/* Make sure the controller is active */
if (!controller_get_interface()->get_is_ready()) return (BTM_DEV_RESET);
- BTM_TRACE_API("BTM_SetConnectability: mode %d [NonConn-0, Conn-1]",
- page_mode);
+ /* If the window and/or interval is '0', set to default values */
+ if (!window) window = BTM_DEFAULT_CONN_WINDOW;
+
+ if (!interval) interval = BTM_DEFAULT_CONN_INTERVAL;
+
+ BTM_TRACE_API(
+ "BTM_SetConnectability: mode %d [NonConn-0, Conn-1], window 0x%04x, "
+ "interval 0x%04x",
+ page_mode, window, interval);
+ /*** Check for valid window and interval parameters ***/
/*** Only check window and duration if mode is connectable ***/
if (page_mode == BTM_CONNECTABLE) {
+ /* window must be less than or equal to interval */
+ if (window < HCI_MIN_PAGESCAN_WINDOW || window > HCI_MAX_PAGESCAN_WINDOW ||
+ interval < HCI_MIN_PAGESCAN_INTERVAL ||
+ interval > HCI_MAX_PAGESCAN_INTERVAL || window > interval) {
+ return (BTM_ILLEGAL_VALUE);
+ }
+
scan_mode |= HCI_PAGE_SCAN_ENABLED;
}
@@ -400,13 +513,40 @@ tBTM_STATUS BTM_SetConnectability(uint16_t page_mode) {
/*******************************************************************************
*
+ * Function BTM_ReadConnectability
+ *
+ * Description This function is called to read the current discoverability
+ * mode of the device.
+ * Output Params p_window - current page scan duration
+ * p_interval - current time between page scans
+ *
+ * Returns BTM_NON_CONNECTABLE or BTM_CONNECTABLE
+ *
+ ******************************************************************************/
+uint16_t BTM_ReadConnectability(uint16_t* p_window, uint16_t* p_interval) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::BTM_ReadConnectability(p_window, p_interval);
+ }
+
+ BTM_TRACE_API("BTM_ReadConnectability");
+ if (p_window) *p_window = btm_cb.btm_inq_vars.page_scan_window;
+
+ if (p_interval) *p_interval = btm_cb.btm_inq_vars.page_scan_period;
+
+ return (btm_cb.btm_inq_vars.connectable_mode);
+}
+
+/*******************************************************************************
+ *
* Function BTM_IsInquiryActive
*
* Description This function returns a bit mask of the current inquiry
* state
*
* Returns BTM_INQUIRY_INACTIVE if inactive (0)
+ * BTM_LIMITED_INQUIRY_ACTIVE if a limted inquiry is active
* BTM_GENERAL_INQUIRY_ACTIVE if a general inquiry is active
+ * BTM_PERIODIC_INQUIRY_ACTIVE if a periodic inquiry is active
*
******************************************************************************/
uint16_t BTM_IsInquiryActive(void) {
@@ -425,37 +565,58 @@ uint16_t BTM_IsInquiryActive(void) {
*
* Description This function cancels an inquiry if active
*
+ * Returns BTM_SUCCESS if successful
+ * BTM_NO_RESOURCES if could not allocate a message buffer
+ * BTM_WRONG_MODE if the device is not up.
+ *
******************************************************************************/
-void BTM_CancelInquiry(void) {
+tBTM_STATUS BTM_CancelInquiry(void) {
if (bluetooth::shim::is_gd_shim_enabled()) {
- bluetooth::shim::BTM_CancelInquiry();
- return;
+ return bluetooth::shim::BTM_CancelInquiry();
}
- btm_cb.history_->Push("%-32s", "Inquiry scan stopped");
-
+ tBTM_STATUS status = BTM_SUCCESS;
tBTM_INQUIRY_VAR_ST* p_inq = &btm_cb.btm_inq_vars;
BTM_TRACE_API("BTM_CancelInquiry called");
- CHECK(BTM_IsDeviceUp());
+ /*** Make sure the device is ready ***/
+ if (!BTM_IsDeviceUp()) return (BTM_WRONG_MODE);
/* Only cancel if not in periodic mode, otherwise the caller should call
* BTM_CancelPeriodicMode */
- if ((p_inq->inq_active & BTM_INQUIRY_ACTIVE_MASK) != 0) {
+ if ((p_inq->inq_active & BTM_INQUIRY_ACTIVE_MASK) != 0 &&
+ (!(p_inq->inq_active & BTM_PERIODIC_INQUIRY_ACTIVE))) {
p_inq->inq_active = BTM_INQUIRY_INACTIVE;
p_inq->state = BTM_INQ_INACTIVE_STATE;
p_inq->p_inq_results_cb = NULL; /* Do not notify caller anymore */
p_inq->p_inq_cmpl_cb = NULL; /* Do not notify caller anymore */
- if ((p_inq->inqparms.mode & BTM_BR_INQUIRY_MASK) != 0) {
- bluetooth::legacy::hci::GetInterface().InquiryCancel();
+ /* If the event filter is in progress, mark it so that the processing of the
+ return
+ event will be ignored */
+ if (p_inq->inqfilt_active) {
+ p_inq->inqfilt_active = false;
+ p_inq->pending_filt_complete_event++;
+ }
+ /* Initiate the cancel inquiry */
+ else {
+ if ((p_inq->inqparms.mode & BTM_BR_INQUIRY_MASK) != 0) {
+ btsnd_hcic_inq_cancel();
+ }
+ if ((p_inq->inqparms.mode & BTM_BLE_INQUIRY_MASK) != 0)
+ btm_ble_stop_inquiry();
}
- if ((p_inq->inqparms.mode & BTM_BLE_INQUIRY_MASK) != 0)
- btm_ble_stop_inquiry();
+
+ /* Do not send the BUSY_LEVEL event yet. Wait for the cancel_complete event
+ * and then send the BUSY_LEVEL event
+ * btm_acl_update_busy_level (BTM_BLI_INQ_DONE_EVT);
+ */
p_inq->inq_counter++;
btm_clr_inq_result_flt();
}
+
+ return (status);
}
/*******************************************************************************
@@ -469,6 +630,8 @@ void BTM_CancelInquiry(void) {
* seperately
* duration - length in 1.28 sec intervals (If '0', the
* inquiry is CANCELLED)
+ * max_resps - maximum amount of devices to search for
+ * before ending the inquiry
* filter_cond_type - BTM_CLR_INQUIRY_FILTER,
* BTM_FILTER_COND_DEVICE_CLASS, or
* BTM_FILTER_COND_BD_ADDR
@@ -493,19 +656,27 @@ void BTM_CancelInquiry(void) {
* BTM_WRONG_MODE if the device is not up.
*
******************************************************************************/
-tBTM_STATUS BTM_StartInquiry(tBTM_INQ_RESULTS_CB* p_results_cb,
+tBTM_STATUS BTM_StartInquiry(tBTM_INQ_PARMS* p_inqparms,
+ tBTM_INQ_RESULTS_CB* p_results_cb,
tBTM_CMPL_CB* p_cmpl_cb) {
tBTM_INQUIRY_VAR_ST* p_inq = &btm_cb.btm_inq_vars;
if (bluetooth::shim::is_gd_shim_enabled()) {
- return bluetooth::shim::BTM_StartInquiry(p_results_cb, p_cmpl_cb);
+ return bluetooth::shim::BTM_StartInquiry(p_inqparms, p_results_cb,
+ p_cmpl_cb);
}
+ BTM_TRACE_API("BTM_StartInquiry: mode: %d, dur: %d, rsps: %d, flt: %d",
+ p_inqparms->mode, p_inqparms->duration, p_inqparms->max_resps,
+ p_inqparms->filter_cond_type);
+
/* Only one active inquiry is allowed in this implementation.
Also do not allow an inquiry if the inquiry filter is being updated */
- if (p_inq->inq_active) {
+ if (p_inq->inq_active || p_inq->inqfilt_active) {
LOG(ERROR) << __func__ << ": BTM_BUSY";
return (BTM_BUSY);
+ } else {
+ p_inq->scan_type = INQ_GENERAL;
}
/*** Make sure the device is ready ***/
@@ -514,48 +685,93 @@ tBTM_STATUS BTM_StartInquiry(tBTM_INQ_RESULTS_CB* p_results_cb,
return BTM_WRONG_MODE;
}
- btm_cb.history_->Push("%-32s", "Inquiry scan started");
+ if ((p_inqparms->mode & BTM_BR_INQUIRY_MASK) != BTM_GENERAL_INQUIRY &&
+ (p_inqparms->mode & BTM_BR_INQUIRY_MASK) != BTM_LIMITED_INQUIRY &&
+ (p_inqparms->mode & BTM_BLE_INQUIRY_MASK) != BTM_BLE_GENERAL_INQUIRY &&
+ (p_inqparms->mode & BTM_BLE_INQUIRY_MASK) != BTM_BLE_LIMITED_INQUIRY) {
+ LOG(ERROR) << __func__ << ": illegal inquiry mode "
+ << std::to_string(p_inqparms->mode);
+ return (BTM_ILLEGAL_VALUE);
+ }
/* Save the inquiry parameters to be used upon the completion of
* setting/clearing the inquiry filter */
- p_inq->inqparms = {};
- p_inq->inqparms.mode = BTM_GENERAL_INQUIRY | BTM_BLE_GENERAL_INQUIRY;
- p_inq->inqparms.duration = BTIF_DM_DEFAULT_INQ_MAX_DURATION;
+ p_inq->inqparms = *p_inqparms;
/* Initialize the inquiry variables */
p_inq->state = BTM_INQ_ACTIVE_STATE;
p_inq->p_inq_cmpl_cb = p_cmpl_cb;
p_inq->p_inq_results_cb = p_results_cb;
p_inq->inq_cmpl_info.num_resp = 0; /* Clear the results counter */
- p_inq->inq_active = p_inq->inqparms.mode;
+ p_inq->inq_active = p_inqparms->mode;
BTM_TRACE_DEBUG("BTM_StartInquiry: p_inq->inq_active = 0x%02x",
p_inq->inq_active);
- if (controller_get_interface()->supports_ble()) {
- btm_ble_start_inquiry(p_inq->inqparms.duration);
- } else {
- LOG_WARN("Trying to do LE scan on a non-LE adapter");
- p_inq->inqparms.mode &= ~BTM_BLE_INQUIRY_MASK;
- }
+ tBTM_STATUS status = BTM_CMD_STARTED;
+ /* start LE inquiry here if requested */
+ if ((p_inqparms->mode & BTM_BLE_INQUIRY_MASK)) {
+ if (!controller_get_interface()->supports_ble()) {
+ LOG(ERROR) << __func__ << ": trying to do LE scan on a non-LE adapter";
+ p_inq->inqparms.mode &= ~BTM_BLE_INQUIRY_MASK;
+ status = BTM_ILLEGAL_VALUE;
+ } else {
+ /* BLE for now does not support filter condition for inquiry */
+ status = btm_ble_start_inquiry(
+ (uint8_t)(p_inqparms->mode & BTM_BLE_INQUIRY_MASK),
+ p_inqparms->duration);
+ if (status != BTM_CMD_STARTED) {
+ LOG(ERROR) << __func__ << ": Error Starting LE Inquiry";
+ p_inq->inqparms.mode &= ~BTM_BLE_INQUIRY_MASK;
+ }
+ }
+ p_inqparms->mode &= ~BTM_BLE_INQUIRY_MASK;
- btm_acl_update_inquiry_status(BTM_INQUIRY_STARTED);
+ BTM_TRACE_DEBUG("BTM_StartInquiry: mode = %02x", p_inqparms->mode);
+ }
- if (p_inq->inq_active & BTM_SSP_INQUIRY_ACTIVE) {
- btm_process_inq_complete(BTM_NO_RESOURCES, BTM_GENERAL_INQUIRY);
- return BTM_CMD_STARTED;
+ /* we're done with this routine if BR/EDR inquiry is not desired. */
+ if ((p_inqparms->mode & BTM_BR_INQUIRY_MASK) == BTM_INQUIRY_NONE) {
+ return status;
}
- btm_clr_inq_result_flt();
+ /* BR/EDR inquiry portion */
+ /* If a filter is specified, then save it for later and clear the current
+ filter.
+ The setting of the filter is done upon completion of clearing of the
+ previous
+ filter.
+ */
+ switch (p_inqparms->filter_cond_type) {
+ case BTM_CLR_INQUIRY_FILTER:
+ p_inq->state = BTM_INQ_SET_FILT_STATE;
+ break;
+
+ case BTM_FILTER_COND_DEVICE_CLASS:
+ case BTM_FILTER_COND_BD_ADDR:
+ /* The filter is not being used so simply clear it;
+ the inquiry can start after this operation */
+ p_inq->state = BTM_INQ_CLR_FILT_STATE;
+ p_inqparms->filter_cond_type = BTM_CLR_INQUIRY_FILTER;
+ /* =============>>>> adding LE filtering here ????? */
+ break;
+
+ default:
+ LOG(ERROR) << __func__ << ": invalid filter condition type "
+ << std::to_string(p_inqparms->filter_cond_type);
+ return (BTM_ILLEGAL_VALUE);
+ }
- /* Allocate memory to hold bd_addrs responding */
- p_inq->p_bd_db = (tINQ_BDADDR*)osi_calloc(BT_DEFAULT_BUFFER_SIZE);
- p_inq->max_bd_entries =
- (uint16_t)(BT_DEFAULT_BUFFER_SIZE / sizeof(tINQ_BDADDR));
+ /* Before beginning the inquiry the current filter must be cleared, so
+ * initiate the command */
+ status = btm_set_inq_event_filter(p_inqparms->filter_cond_type,
+ &p_inqparms->filter_cond);
+ if (status != BTM_CMD_STARTED) {
+ LOG(ERROR) << __func__ << ": failed to set inquiry event filter";
+ p_inq->state = BTM_INQ_INACTIVE_STATE;
+ }
- bluetooth::legacy::hci::GetInterface().StartInquiry(
- general_inq_lap, p_inq->inqparms.duration, 0);
- return BTM_CMD_STARTED;
+ return (status);
}
/*******************************************************************************
@@ -730,7 +946,8 @@ tBTM_STATUS BTM_ClearInqDb(const RawAddress* p_bda) {
tBTM_INQUIRY_VAR_ST* p_inq = &btm_cb.btm_inq_vars;
/* If an inquiry or remote name is in progress return busy */
- if (p_inq->inq_active != BTM_INQUIRY_INACTIVE) return (BTM_BUSY);
+ if (p_inq->inq_active != BTM_INQUIRY_INACTIVE || p_inq->inqfilt_active)
+ return (BTM_BUSY);
btm_clr_inq_db(p_bda);
@@ -759,6 +976,7 @@ void btm_inq_db_reset(void) {
tBTM_INQUIRY_VAR_ST* p_inq = &btm_cb.btm_inq_vars;
uint8_t num_responses;
uint8_t temp_inq_active;
+ tBTM_STATUS status;
/* If an inquiry or periodic inquiry is active, reset the mode to inactive */
if (p_inq->inq_active != BTM_INQUIRY_INACTIVE) {
@@ -768,7 +986,8 @@ void btm_inq_db_reset(void) {
/* If not a periodic inquiry, the complete callback must be called to notify
* caller */
- if (temp_inq_active == BTM_GENERAL_INQUIRY_ACTIVE) {
+ if (temp_inq_active == BTM_LIMITED_INQUIRY_ACTIVE ||
+ temp_inq_active == BTM_GENERAL_INQUIRY_ACTIVE) {
if (p_inq->p_inq_cmpl_cb) {
num_responses = 0;
(*p_inq->p_inq_cmpl_cb)(&num_responses);
@@ -791,7 +1010,19 @@ void btm_inq_db_reset(void) {
}
}
+ /* Cancel an inquiry filter request if active, and notify the caller (if
+ * waiting) */
+ if (p_inq->inqfilt_active) {
+ p_inq->inqfilt_active = false;
+
+ if (p_inq->p_inqfilter_cmpl_cb) {
+ status = BTM_DEV_RESET;
+ (*p_inq->p_inqfilter_cmpl_cb)(&status);
+ }
+ }
+
p_inq->state = BTM_INQ_INACTIVE_STATE;
+ p_inq->pending_filt_complete_event = 0;
p_inq->p_inq_results_cb = NULL;
btm_clr_inq_db(NULL); /* Clear out all the entries in the database */
btm_clr_inq_result_flt();
@@ -823,10 +1054,6 @@ void btm_inq_db_init(void) {
btm_cb.btm_inq_vars.no_inc_ssp = BTM_NO_SSP_ON_INQUIRY;
}
-void btm_inq_db_free(void) {
- alarm_free(btm_cb.btm_inq_vars.remote_name_timer);
-}
-
/*******************************************************************************
*
* Function btm_inq_stop_on_ssp
@@ -837,20 +1064,24 @@ void btm_inq_db_free(void) {
*
******************************************************************************/
void btm_inq_stop_on_ssp(void) {
- uint8_t normal_active = (BTM_GENERAL_INQUIRY_ACTIVE);
+ uint8_t normal_active =
+ (BTM_GENERAL_INQUIRY_ACTIVE | BTM_LIMITED_INQUIRY_ACTIVE);
#if (BTM_INQ_DEBUG == TRUE)
BTM_TRACE_DEBUG(
- "btm_inq_stop_on_ssp: no_inc_ssp=%d inq_active:0x%x state:%d ",
+ "btm_inq_stop_on_ssp: no_inc_ssp=%d inq_active:0x%x state:%d "
+ "inqfilt_active:%d",
btm_cb.btm_inq_vars.no_inc_ssp, btm_cb.btm_inq_vars.inq_active,
- btm_cb.btm_inq_vars.state);
+ btm_cb.btm_inq_vars.state, btm_cb.btm_inq_vars.inqfilt_active);
#endif
if (btm_cb.btm_inq_vars.no_inc_ssp) {
if (btm_cb.btm_inq_vars.state == BTM_INQ_ACTIVE_STATE) {
- if (btm_cb.btm_inq_vars.inq_active & normal_active) {
+ if (btm_cb.btm_inq_vars.inq_active & BTM_PERIODIC_INQUIRY_ACTIVE) {
+ BTM_CancelPeriodicInquiry();
+ } else if (btm_cb.btm_inq_vars.inq_active & normal_active) {
/* can not call BTM_CancelInquiry() here. We need to report inquiry
* complete evt */
- bluetooth::legacy::hci::GetInterface().InquiryCancel();
+ btsnd_hcic_inq_cancel();
}
}
/* do not allow inquiry to start */
@@ -941,7 +1172,8 @@ bool btm_inq_find_bdaddr(const RawAddress& p_bda) {
uint16_t xx;
/* Don't bother searching, database doesn't exist or periodic mode */
- if (!p_db) return (false);
+ if ((p_inq->inq_active & BTM_PERIODIC_INQUIRY_ACTIVE) || !p_db)
+ return (false);
for (xx = 0; xx < p_inq->num_bd_entries; xx++, p_db++) {
if (p_db->bd_addr == p_bda && p_db->inq_count == p_inq->inq_counter)
@@ -1024,6 +1256,243 @@ tINQ_DB_ENT* btm_inq_db_new(const RawAddress& p_bda) {
/*******************************************************************************
*
+ * Function btm_set_inq_event_filter
+ *
+ * Description This function is called to set the inquiry event filter.
+ * It is called by either internally, or by the external API
+ * function (BTM_SetInqEventFilter). It is used internally as
+ * part of the inquiry processing.
+ *
+ * Input Params:
+ * filter_cond_type - this is the type of inquiry filter to
+ * apply:
+ * BTM_FILTER_COND_DEVICE_CLASS,
+ * BTM_FILTER_COND_BD_ADDR, or
+ * BTM_CLR_INQUIRY_FILTER
+ *
+ * p_filt_cond - this is either a BD_ADDR or DEV_CLASS
+ * depending on the filter_cond_type
+ * (See section 4.7.3 of Core Spec 1.0b).
+ *
+ * Returns BTM_CMD_STARTED if successfully initiated
+ * BTM_NO_RESOURCES if couldn't get a memory pool buffer
+ * BTM_ILLEGAL_VALUE if a bad parameter was detected
+ *
+ ******************************************************************************/
+static tBTM_STATUS btm_set_inq_event_filter(uint8_t filter_cond_type,
+ tBTM_INQ_FILT_COND* p_filt_cond) {
+ uint8_t condition_length = DEV_CLASS_LEN * 2;
+ uint8_t condition_buf[DEV_CLASS_LEN * 2];
+ uint8_t* p_cond = condition_buf; /* points to the condition to pass to HCI */
+
+#if (BTM_INQ_DEBUG == TRUE)
+ BTM_TRACE_DEBUG(
+ "btm_set_inq_event_filter: filter type %d [Clear-0, COD-1, BDADDR-2]",
+ filter_cond_type);
+ VLOG(2) << "condition " << p_filt_cond->bdaddr_cond;
+#endif
+
+ /* Load the correct filter condition to pass to the lower layer */
+ switch (filter_cond_type) {
+ case BTM_FILTER_COND_DEVICE_CLASS:
+ /* copy the device class and device class fields into contiguous memory to
+ * send to HCI */
+ memcpy(condition_buf, p_filt_cond->cod_cond.dev_class, DEV_CLASS_LEN);
+ memcpy(&condition_buf[DEV_CLASS_LEN],
+ p_filt_cond->cod_cond.dev_class_mask, DEV_CLASS_LEN);
+
+ /* condition length should already be set as the default */
+ break;
+
+ case BTM_FILTER_COND_BD_ADDR:
+ p_cond = (uint8_t*)&p_filt_cond->bdaddr_cond;
+
+ /* condition length should already be set as the default */
+ break;
+
+ case BTM_CLR_INQUIRY_FILTER:
+ condition_length = 0;
+ break;
+
+ default:
+ return (BTM_ILLEGAL_VALUE); /* Bad parameter was passed in */
+ }
+
+ btm_cb.btm_inq_vars.inqfilt_active = true;
+
+ /* Filter the inquiry results for the specified condition type and value */
+ btsnd_hcic_set_event_filter(HCI_FILTER_INQUIRY_RESULT, filter_cond_type,
+ p_cond, condition_length);
+ return (BTM_CMD_STARTED);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_event_filter_complete
+ *
+ * Description This function is called when a set event filter has
+ * completed.
+ * Note: This routine currently only handles inquiry filters.
+ * Connection filters are ignored for now.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_event_filter_complete(uint8_t* p) {
+ uint8_t hci_status;
+ tBTM_STATUS status;
+ tBTM_INQUIRY_VAR_ST* p_inq = &btm_cb.btm_inq_vars;
+ tBTM_CMPL_CB* p_cb = p_inq->p_inqfilter_cmpl_cb;
+
+#if (BTM_INQ_DEBUG == TRUE)
+ BTM_TRACE_DEBUG(
+ "btm_event_filter_complete: inq_active:0x%x state:%d inqfilt_active:%d",
+ btm_cb.btm_inq_vars.inq_active, btm_cb.btm_inq_vars.state,
+ btm_cb.btm_inq_vars.inqfilt_active);
+#endif
+ /* If the filter complete event is from an old or cancelled request, ignore it
+ */
+ if (p_inq->pending_filt_complete_event) {
+ p_inq->pending_filt_complete_event--;
+ return;
+ }
+
+ /* Only process the inquiry filter; Ignore the connection filter until it
+ is used by the upper layers */
+ if (p_inq->inqfilt_active) {
+ /* Extract the returned status from the buffer */
+ STREAM_TO_UINT8(hci_status, p);
+ if (hci_status != HCI_SUCCESS) {
+ /* If standalone operation, return the error status; if embedded in the
+ * inquiry, continue the inquiry */
+ BTM_TRACE_WARNING(
+ "BTM Warning: Set Event Filter Failed (HCI returned 0x%x)",
+ hci_status);
+ status = BTM_ERR_PROCESSING;
+ } else
+ status = BTM_SUCCESS;
+
+ /* If the set filter was initiated externally (via BTM_SetInqEventFilter),
+ call the
+ callback function to notify the initiator that it has completed */
+ if (p_inq->state == BTM_INQ_INACTIVE_STATE) {
+ p_inq->inqfilt_active = false;
+ if (p_cb) (*p_cb)(&status);
+ } else /* An inquiry is active (the set filter command was internally
+ generated),
+ process the next state of the process (Set a new filter or start
+ the inquiry). */
+ {
+ if (status != BTM_SUCCESS) {
+ /* Process the inquiry complete (Error Status) */
+ btm_process_inq_complete(
+ BTM_ERR_PROCESSING,
+ (uint8_t)(p_inq->inqparms.mode & BTM_BR_INQUIRY_MASK));
+
+ /* btm_process_inq_complete() does not restore the following settings on
+ * periodic inquiry */
+ p_inq->inqfilt_active = false;
+ p_inq->inq_active = BTM_INQUIRY_INACTIVE;
+ p_inq->state = BTM_INQ_INACTIVE_STATE;
+
+ return;
+ }
+
+ /* Check to see if a new filter needs to be set up */
+ if (p_inq->state == BTM_INQ_CLR_FILT_STATE) {
+ status = btm_set_inq_event_filter(p_inq->inqparms.filter_cond_type,
+ &p_inq->inqparms.filter_cond);
+ if (status == BTM_CMD_STARTED) {
+ p_inq->state = BTM_INQ_SET_FILT_STATE;
+ } else /* Error setting the filter: Call the initiator's callback
+ function to indicate a failure */
+ {
+ p_inq->inqfilt_active = false;
+
+ /* Process the inquiry complete (Error Status) */
+ btm_process_inq_complete(
+ BTM_ERR_PROCESSING,
+ (uint8_t)(p_inq->inqparms.mode & BTM_BR_INQUIRY_MASK));
+ }
+ } else /* Initiate the Inquiry or Periodic Inquiry */
+ {
+ p_inq->state = BTM_INQ_ACTIVE_STATE;
+ p_inq->inqfilt_active = false;
+ btm_initiate_inquiry(p_inq);
+ }
+ }
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_initiate_inquiry
+ *
+ * Description This function is called to start an inquiry or periodic
+ * inquiry upon completion of the setting and/or clearing of
+ * the inquiry filter.
+ *
+ * Inputs: p_inq (btm_cb.btm_inq_vars) - pointer to saved inquiry
+ * information
+ * mode - GENERAL or LIMITED inquiry
+ * duration - length in 1.28 sec intervals
+ * (If '0', the inquiry is CANCELLED)
+ * max_resps - maximum amount of devices to search for
+ * before ending the inquiry
+ * filter_cond_type - BTM_CLR_INQUIRY_FILTER,
+ * BTM_FILTER_COND_DEVICE_CLASS, or
+ * BTM_FILTER_COND_BD_ADDR
+ * filter_cond - value for the filter
+ * (based on filter_cond_type)
+ *
+ * Returns If an error occurs the initiator's callback is called with
+ * the error status.
+ *
+ ******************************************************************************/
+static void btm_initiate_inquiry(tBTM_INQUIRY_VAR_ST* p_inq) {
+ const LAP* lap;
+ tBTM_INQ_PARMS* p_inqparms = &p_inq->inqparms;
+
+#if (BTM_INQ_DEBUG == TRUE)
+ BTM_TRACE_DEBUG(
+ "btm_initiate_inquiry: inq_active:0x%x state:%d inqfilt_active:%d",
+ btm_cb.btm_inq_vars.inq_active, btm_cb.btm_inq_vars.state,
+ btm_cb.btm_inq_vars.inqfilt_active);
+#endif
+ btm_acl_update_busy_level(BTM_BLI_INQ_EVT);
+
+ if (p_inq->inq_active & BTM_SSP_INQUIRY_ACTIVE) {
+ btm_process_inq_complete(BTM_NO_RESOURCES,
+ (uint8_t)(p_inqparms->mode & BTM_BR_INQUIRY_MASK));
+ return;
+ }
+
+ /* Make sure the number of responses doesn't overflow the database
+ * configuration */
+ p_inqparms->max_resps = (uint8_t)((p_inqparms->max_resps <= BTM_INQ_DB_SIZE)
+ ? p_inqparms->max_resps
+ : BTM_INQ_DB_SIZE);
+
+ lap = (p_inq->inq_active & BTM_LIMITED_INQUIRY_ACTIVE) ? &limited_inq_lap
+ : &general_inq_lap;
+
+ if (p_inq->inq_active & BTM_PERIODIC_INQUIRY_ACTIVE) {
+ btsnd_hcic_per_inq_mode(p_inq->per_max_delay, p_inq->per_min_delay, *lap,
+ p_inqparms->duration, p_inqparms->max_resps);
+ } else {
+ btm_clr_inq_result_flt();
+
+ /* Allocate memory to hold bd_addrs responding */
+ p_inq->p_bd_db = (tINQ_BDADDR*)osi_calloc(BT_DEFAULT_BUFFER_SIZE);
+ p_inq->max_bd_entries =
+ (uint16_t)(BT_DEFAULT_BUFFER_SIZE / sizeof(tINQ_BDADDR));
+
+ btsnd_hcic_inquiry(*lap, p_inqparms->duration, 0);
+ }
+}
+
+/*******************************************************************************
+ *
* Function btm_process_inq_results
*
* Description This function is called when inquiry results are received
@@ -1057,8 +1526,10 @@ void btm_process_inq_results(uint8_t* p, uint8_t hci_evt_len,
uint8_t* p_eir_data = NULL;
#if (BTM_INQ_DEBUG == TRUE)
- BTM_TRACE_DEBUG("btm_process_inq_results inq_active:0x%x state:%d",
- btm_cb.btm_inq_vars.inq_active, btm_cb.btm_inq_vars.state);
+ BTM_TRACE_DEBUG(
+ "btm_process_inq_results inq_active:0x%x state:%d inqfilt_active:%d",
+ btm_cb.btm_inq_vars.inq_active, btm_cb.btm_inq_vars.state,
+ btm_cb.btm_inq_vars.inqfilt_active);
#endif
/* Only process the results if the BR inquiry is still active */
if (!(p_inq->inq_active & BTM_BR_INQ_ACTIVE_MASK)) return;
@@ -1108,6 +1579,22 @@ void btm_process_inq_results(uint8_t* p, uint8_t hci_evt_len,
}
p_i = btm_inq_db_find(bda);
+ /* Only process the num_resp is smaller than max_resps.
+ If results are queued to BTU task while canceling inquiry,
+ or when more than one result is in this response, > max_resp
+ responses could be processed which can confuse some apps
+ */
+ if (p_inq->inqparms.max_resps &&
+ p_inq->inq_cmpl_info.num_resp >= p_inq->inqparms.max_resps
+ /* new device response */
+ &&
+ (p_i == NULL ||
+ /* exisiting device with BR/EDR info */
+ (p_i &&
+ (p_i->inq_info.results.device_type & BT_DEVICE_TYPE_BREDR) != 0))) {
+ /* BTM_TRACE_WARNING("INQ RES: Extra Response Received...ignoring"); */
+ return;
+ }
/* Check if this address has already been processed for this inquiry */
if (btm_inq_find_bdaddr(bda)) {
@@ -1117,7 +1604,7 @@ void btm_process_inq_results(uint8_t* p, uint8_t hci_evt_len,
i_rssi = (int8_t)rssi;
/* If this new RSSI is higher than the last one */
- if ((rssi != 0) && p_i &&
+ if (p_inq->inqparms.report_dup && (rssi != 0) && p_i &&
(i_rssi > p_i->inq_info.results.rssi ||
p_i->inq_info.results.rssi == 0
/* BR/EDR inquiry information update */
@@ -1187,6 +1674,23 @@ void btm_process_inq_results(uint8_t* p, uint8_t hci_evt_len,
p_cur->device_type |= BT_DEVICE_TYPE_BREDR;
p_i->inq_count = p_inq->inq_counter; /* Mark entry for current inquiry */
+ /* If the number of responses found and not unlimited, issue a cancel
+ * inquiry */
+ if (!(p_inq->inq_active & BTM_PERIODIC_INQUIRY_ACTIVE) &&
+ p_inq->inqparms.max_resps &&
+ p_inq->inq_cmpl_info.num_resp == p_inq->inqparms.max_resps &&
+ /* BLE scanning is active and received adv */
+ ((((p_inq->inqparms.mode & BTM_BLE_INQUIRY_MASK) != 0) &&
+ p_cur->device_type == BT_DEVICE_TYPE_DUMO && p_i->scan_rsp) ||
+ (p_inq->inqparms.mode & BTM_BLE_INQUIRY_MASK) == 0)) {
+ /* BTM_TRACE_DEBUG("BTMINQ: Found devices, cancelling
+ * inquiry..."); */
+ btsnd_hcic_inq_cancel();
+
+ if ((p_inq->inqparms.mode & BTM_BLE_INQUIRY_MASK) != 0)
+ btm_ble_stop_inquiry();
+ btm_acl_update_busy_level(BTM_BLI_INQ_DONE_EVT);
+ }
/* Initialize flag to false. This flag is set/used by application */
p_i->inq_info.appl_knows_rem_name = false;
}
@@ -1269,10 +1773,12 @@ void btm_process_inq_complete(uint8_t status, uint8_t mode) {
p_inq->inqparms.mode &= ~(mode);
#if (BTM_INQ_DEBUG == TRUE)
- BTM_TRACE_DEBUG("btm_process_inq_complete inq_active:0x%x state:%d",
- btm_cb.btm_inq_vars.inq_active, btm_cb.btm_inq_vars.state);
+ BTM_TRACE_DEBUG(
+ "btm_process_inq_complete inq_active:0x%x state:%d inqfilt_active:%d",
+ btm_cb.btm_inq_vars.inq_active, btm_cb.btm_inq_vars.state,
+ btm_cb.btm_inq_vars.inqfilt_active);
#endif
- btm_acl_update_inquiry_status(BTM_INQUIRY_COMPLETE);
+ btm_acl_update_busy_level(BTM_BLI_INQ_DONE_EVT);
/* Ignore any stray or late complete messages if the inquiry is not active */
if (p_inq->inq_active) {
p_inq->inq_cmpl_info.status = (tBTM_STATUS)(
@@ -1280,7 +1786,8 @@ void btm_process_inq_complete(uint8_t status, uint8_t mode) {
/* Notify caller that the inquiry has completed; (periodic inquiries do not
* send completion events */
- if (p_inq->inqparms.mode == 0) {
+ if (!(p_inq->inq_active & BTM_PERIODIC_INQUIRY_ACTIVE) &&
+ p_inq->inqparms.mode == 0) {
btm_clear_all_pending_le_entry();
p_inq->state = BTM_INQ_INACTIVE_STATE;
@@ -1307,9 +1814,15 @@ void btm_process_inq_complete(uint8_t status, uint8_t mode) {
if (p_inq_cb) (p_inq_cb)((tBTM_INQUIRY_CMPL*)&p_inq->inq_cmpl_info);
}
}
+ if (p_inq->inqparms.mode == 0 &&
+ p_inq->scan_type == INQ_GENERAL) // this inquiry is complete
+ {
+ p_inq->scan_type = INQ_NONE;
+ }
#if (BTM_INQ_DEBUG == TRUE)
- BTM_TRACE_DEBUG("inq_active:0x%x state:%d", btm_cb.btm_inq_vars.inq_active,
- btm_cb.btm_inq_vars.state);
+ BTM_TRACE_DEBUG("inq_active:0x%x state:%d inqfilt_active:%d",
+ btm_cb.btm_inq_vars.inq_active, btm_cb.btm_inq_vars.state,
+ btm_cb.btm_inq_vars.inqfilt_active);
#endif
}
@@ -1326,7 +1839,7 @@ void btm_process_inq_complete(uint8_t status, uint8_t mode) {
*
******************************************************************************/
void btm_process_cancel_complete(uint8_t status, uint8_t mode) {
- btm_acl_update_inquiry_status(BTM_INQUIRY_CANCELLED);
+ btm_acl_update_busy_level(BTM_BLI_INQ_CANCEL_EVT);
btm_process_inq_complete(status, mode);
}
/*******************************************************************************
@@ -1356,7 +1869,15 @@ tBTM_STATUS btm_initiate_rem_name(const RawAddress& remote_bda, uint8_t origin,
/*** Make sure the device is ready ***/
if (!BTM_IsDeviceUp()) return (BTM_WRONG_MODE);
- if (origin == BTM_RMT_NAME_EXT) {
+
+ if (origin == BTM_RMT_NAME_SEC) {
+ btsnd_hcic_rmt_name_req(remote_bda, HCI_PAGE_SCAN_REP_MODE_R1,
+ HCI_MANDATARY_PAGE_SCAN_MODE, 0);
+ return BTM_CMD_STARTED;
+ }
+ /* Make sure there are no two remote name requests from external API in
+ progress */
+ else if (origin == BTM_RMT_NAME_EXT) {
if (p_inq->remname_active) {
return (BTM_BUSY);
} else {
@@ -1480,16 +2001,67 @@ void btm_inq_rmt_name_failed_cancelled(void) {
BTM_TRACE_ERROR("btm_inq_rmt_name_failed_cancelled() remname_active=%d",
btm_cb.btm_inq_vars.remname_active);
- if (btm_cb.btm_inq_vars.remname_active) {
+ if (btm_cb.btm_inq_vars.remname_active)
btm_process_remote_name(&btm_cb.btm_inq_vars.remname_bda, NULL, 0,
HCI_ERR_UNSPECIFIED);
- }
+ else
+ btm_process_remote_name(NULL, NULL, 0, HCI_ERR_UNSPECIFIED);
btm_sec_rmt_name_request_complete(NULL, NULL, HCI_ERR_UNSPECIFIED);
}
/*******************************************************************************
*
+ * Function btm_read_inq_tx_power_timeout
+ *
+ * Description Callback when reading the inquiry tx power times out.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_inq_tx_power_timeout(UNUSED_ATTR void* data) {
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_inq_tx_power_cmpl_cb;
+ btm_cb.devcb.p_inq_tx_power_cmpl_cb = NULL;
+ if (p_cb) (*p_cb)((void*)NULL);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_inq_tx_power_complete
+ *
+ * Description read inquiry tx power level complete callback function.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_read_inq_tx_power_complete(uint8_t* p) {
+ tBTM_CMPL_CB* p_cb = btm_cb.devcb.p_inq_tx_power_cmpl_cb;
+ tBTM_INQ_TXPWR_RESULT result;
+
+ BTM_TRACE_DEBUG("%s", __func__);
+ alarm_cancel(btm_cb.devcb.read_inq_tx_power_timer);
+ btm_cb.devcb.p_inq_tx_power_cmpl_cb = NULL;
+
+ /* If there was a registered callback, call it */
+ if (p_cb) {
+ STREAM_TO_UINT8(result.hci_status, p);
+
+ if (result.hci_status == HCI_SUCCESS) {
+ result.status = BTM_SUCCESS;
+
+ STREAM_TO_UINT8(result.tx_power, p);
+ BTM_TRACE_EVENT(
+ "BTM INQ TX POWER Complete: tx_power %d, hci status 0x%02x",
+ result.tx_power, result.hci_status);
+ } else {
+ result.status = BTM_ERR_PROCESSING;
+ }
+
+ (*p_cb)(&result);
+ }
+}
+/*******************************************************************************
+ *
* Function BTM_WriteEIR
*
* Description This function is called to write EIR data to controller.
@@ -1824,7 +2396,7 @@ static uint16_t btm_convert_uuid_to_uuid16(const uint8_t* p_uuid,
if (uuid32 < 0x10000) uuid16 = (uint16_t)uuid32;
break;
case Uuid::kNumBytes128:
- /* See if we can compress the UUID down to 16 or 32bit UUIDs */
+ /* See if we can compress his UUID down to 16 or 32bit UUIDs */
is_base_uuid = true;
for (xx = 0; xx < Uuid::kNumBytes128 - 4; xx++) {
if (p_uuid[xx] != base_uuid[xx]) {
diff --git a/stack/btm/btm_int.h b/stack/btm/btm_int.h
index e69de29bb..05180db5e 100644
--- a/stack/btm/btm_int.h
+++ b/stack/btm/btm_int.h
@@ -0,0 +1,288 @@
+/******************************************************************************
+ *
+ * Copyright 1999-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+/******************************************************************************
+ *
+ * this file contains the main Bluetooth Manager (BTM) internal
+ * definitions.
+ *
+ ******************************************************************************/
+#ifndef BTM_INT_H
+#define BTM_INT_H
+
+#include "bt_common.h"
+#include "bt_target.h"
+#include "hcidefs.h"
+
+#include "osi/include/alarm.h"
+#include "osi/include/fixed_queue.h"
+#include "osi/include/list.h"
+#include "rfcdefs.h"
+
+#include "btm_api.h"
+#include "device/include/esco_parameters.h"
+
+#include "btm_ble_int.h"
+#include "btm_int_types.h"
+#include "l2cdefs.h"
+#include "smp_api.h"
+
+extern tBTM_CB btm_cb;
+
+/* Internal functions provided by btm_main.cc
+ *******************************************
+*/
+extern void btm_init(void);
+extern void btm_free(void);
+
+/* Internal functions provided by btm_inq.cc
+ ******************************************
+*/
+extern tBTM_STATUS btm_initiate_rem_name(const RawAddress& remote_bda,
+ uint8_t origin, uint64_t timeout_ms,
+ tBTM_CMPL_CB* p_cb);
+
+extern void btm_process_remote_name(const RawAddress* bda, BD_NAME name,
+ uint16_t evt_len, uint8_t hci_status);
+extern void btm_inq_rmt_name_failed_cancelled(void);
+extern void btm_inq_remote_name_timer_timeout(void* data);
+
+/* Inquiry related functions */
+extern void btm_clr_inq_db(const RawAddress* p_bda);
+extern void btm_inq_db_init(void);
+extern void btm_process_inq_results(uint8_t* p, uint8_t hci_evt_len,
+ uint8_t inq_res_mode);
+extern void btm_process_inq_complete(uint8_t status, uint8_t mode);
+extern void btm_process_cancel_complete(uint8_t status, uint8_t mode);
+extern void btm_event_filter_complete(uint8_t* p);
+extern void btm_inq_stop_on_ssp(void);
+extern void btm_inq_clear_ssp(void);
+extern tINQ_DB_ENT* btm_inq_db_find(const RawAddress& p_bda);
+extern bool btm_inq_find_bdaddr(const RawAddress& p_bda);
+
+/* Internal functions provided by btm_acl.cc
+ *******************************************
+*/
+extern void btm_acl_init(void);
+extern void btm_acl_created(const RawAddress& bda, DEV_CLASS dc, BD_NAME bdn,
+ uint16_t hci_handle, uint8_t link_role,
+ tBT_TRANSPORT transport);
+extern void btm_acl_removed(const RawAddress& bda, tBT_TRANSPORT transport);
+extern void btm_acl_device_down(void);
+extern void btm_acl_update_busy_level(tBTM_BLI_EVENT event);
+
+extern void btm_cont_rswitch(tACL_CONN* p, tBTM_SEC_DEV_REC* p_dev_rec,
+ uint8_t hci_status);
+
+extern uint8_t btm_handle_to_acl_index(uint16_t hci_handle);
+extern void btm_read_link_policy_complete(uint8_t* p);
+
+extern void btm_read_rssi_timeout(void* data);
+extern void btm_read_rssi_complete(uint8_t* p);
+
+extern void btm_read_failed_contact_counter_timeout(void* data);
+extern void btm_read_failed_contact_counter_complete(uint8_t* p);
+
+extern void btm_read_automatic_flush_timeout_timeout(void* data);
+extern void btm_read_automatic_flush_timeout_complete(uint8_t* p);
+
+extern void btm_read_tx_power_timeout(void* data);
+extern void btm_read_tx_power_complete(uint8_t* p, bool is_ble);
+
+extern void btm_read_link_quality_timeout(void* data);
+extern void btm_read_link_quality_complete(uint8_t* p);
+
+extern tBTM_STATUS btm_set_packet_types(tACL_CONN* p, uint16_t pkt_types);
+extern void btm_process_clk_off_comp_evt(uint16_t hci_handle,
+ uint16_t clock_offset);
+extern void btm_acl_role_changed(uint8_t hci_status, const RawAddress* bd_addr,
+ uint8_t new_role);
+extern void btm_blacklist_role_change_device(const RawAddress& bd_addr,
+ uint8_t hci_status);
+extern void btm_acl_encrypt_change(uint16_t handle, uint8_t status,
+ uint8_t encr_enable);
+extern uint16_t btm_get_acl_disc_reason_code(void);
+extern tBTM_STATUS btm_remove_acl(const RawAddress& bd_addr,
+ tBT_TRANSPORT transport);
+extern void btm_read_remote_features_complete(uint8_t* p);
+extern void btm_read_remote_ext_features_complete(uint8_t* p, uint8_t evt_len);
+extern void btm_read_remote_ext_features_failed(uint8_t status,
+ uint16_t handle);
+extern void btm_read_remote_version_complete(uint8_t* p);
+extern void btm_establish_continue(tACL_CONN* p_acl_cb);
+
+extern void btm_acl_chk_peer_pkt_type_support(tACL_CONN* p,
+ uint16_t* p_pkt_type);
+/* Read maximum data packet that can be sent over current connection */
+extern uint16_t btm_get_max_packet_size(const RawAddress& addr);
+extern tACL_CONN* btm_bda_to_acl(const RawAddress& bda,
+ tBT_TRANSPORT transport);
+extern bool btm_acl_notif_conn_collision(const RawAddress& bda);
+extern void btm_acl_update_conn_addr(uint16_t conn_handle,
+ const RawAddress& address);
+
+extern void btm_pm_reset(void);
+extern void btm_pm_sm_alloc(uint8_t ind);
+extern void btm_pm_proc_cmd_status(uint8_t status);
+extern void btm_pm_proc_mode_change(uint8_t hci_status, uint16_t hci_handle,
+ uint8_t mode, uint16_t interval);
+extern void btm_pm_proc_ssr_evt(uint8_t* p, uint16_t evt_len);
+extern tBTM_STATUS btm_read_power_mode_state(const RawAddress& remote_bda,
+ tBTM_PM_STATE* pmState);
+extern void btm_sco_chk_pend_unpark(uint8_t hci_status, uint16_t hci_handle);
+extern void btm_qos_setup_timeout(void* data);
+extern void btm_qos_setup_complete(uint8_t status, uint16_t handle,
+ FLOW_SPEC* p_flow);
+
+/* Internal functions provided by btm_sco.cc
+ *******************************************
+*/
+extern void btm_sco_init(void);
+extern void btm_sco_connected(uint8_t hci_status, const RawAddress* bda,
+ uint16_t hci_handle, tBTM_ESCO_DATA* p_esco_data);
+extern void btm_esco_proc_conn_chg(uint8_t status, uint16_t handle,
+ uint8_t tx_interval, uint8_t retrans_window,
+ uint16_t rx_pkt_len, uint16_t tx_pkt_len);
+extern void btm_sco_conn_req(const RawAddress& bda, DEV_CLASS dev_class,
+ uint8_t link_type);
+extern void btm_sco_removed(uint16_t hci_handle, uint8_t reason);
+extern void btm_sco_acl_removed(const RawAddress* bda);
+extern void btm_route_sco_data(BT_HDR* p_msg);
+extern bool btm_is_sco_active(uint16_t handle);
+extern void btm_remove_sco_links(const RawAddress& bda);
+extern bool btm_is_sco_active_by_bdaddr(const RawAddress& remote_bda);
+
+extern void btm_read_def_esco_mode(enh_esco_params_t* p_parms);
+extern uint16_t btm_find_scb_by_handle(uint16_t handle);
+extern void btm_sco_flush_sco_data(uint16_t sco_inx);
+
+/* Internal functions provided by btm_devctl.cc
+ *********************************************
+*/
+extern void btm_dev_init(void);
+extern void btm_read_local_name_timeout(void* data);
+extern void btm_read_local_name_complete(uint8_t* p, uint16_t evt_len);
+
+extern void btm_ble_create_conn_cancel_complete(uint8_t* p);
+extern bool btm_ble_addr_resolvable(const RawAddress& rpa,
+ tBTM_SEC_DEV_REC* p_dev_rec);
+extern tBTM_STATUS btm_ble_read_resolving_list_entry(
+ tBTM_SEC_DEV_REC* p_dev_rec);
+extern bool btm_ble_resolving_list_load_dev(tBTM_SEC_DEV_REC* p_dev_rec);
+extern void btm_ble_resolving_list_remove_dev(tBTM_SEC_DEV_REC* p_dev_rec);
+
+/* Vendor Specific Command complete evt handler */
+extern void btm_vsc_complete(uint8_t* p, uint16_t cc_opcode, uint16_t evt_len,
+ tBTM_VSC_CMPL_CB* p_vsc_cplt_cback);
+extern void btm_inq_db_reset(void);
+extern void btm_vendor_specific_evt(uint8_t* p, uint8_t evt_len);
+extern void btm_delete_stored_link_key_complete(uint8_t* p);
+extern void btm_report_device_status(tBTM_DEV_STATUS status);
+extern tBTM_STATUS BTM_BT_Quality_Report_VSE_Register(
+ bool is_register, tBTM_BT_QUALITY_REPORT_RECEIVER* p_bqr_report_receiver);
+
+/* Internal functions provided by btm_dev.cc
+ *********************************************
+*/
+extern bool btm_dev_support_switch(const RawAddress& bd_addr);
+
+extern tBTM_SEC_DEV_REC* btm_sec_allocate_dev_rec(void);
+extern tBTM_SEC_DEV_REC* btm_sec_alloc_dev(const RawAddress& bd_addr);
+extern void wipe_secrets_and_remove(tBTM_SEC_DEV_REC* p_dev_rec);
+extern tBTM_SEC_DEV_REC* btm_find_dev(const RawAddress& bd_addr);
+extern tBTM_SEC_DEV_REC* btm_find_or_alloc_dev(const RawAddress& bd_addr);
+extern tBTM_SEC_DEV_REC* btm_find_dev_by_handle(uint16_t handle);
+extern tBTM_BOND_TYPE btm_get_bond_type_dev(const RawAddress& bd_addr);
+extern bool btm_set_bond_type_dev(const RawAddress& bd_addr,
+ tBTM_BOND_TYPE bond_type);
+
+/* Internal functions provided by btm_sec.cc
+ *********************************************
+*/
+extern bool btm_dev_support_switch(const RawAddress& bd_addr);
+extern tBTM_STATUS btm_sec_l2cap_access_req(const RawAddress& bd_addr,
+ uint16_t psm, uint16_t handle,
+ CONNECTION_TYPE conn_type,
+ tBTM_SEC_CALLBACK* p_callback,
+ void* p_ref_data);
+extern tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
+ uint16_t psm, bool is_originator,
+ uint32_t mx_proto_id,
+ uint32_t mx_chan_id,
+ tBTM_SEC_CALLBACK* p_callback,
+ void* p_ref_data);
+extern void btm_sec_conn_req(const RawAddress& bda, uint8_t* dc);
+extern void btm_create_conn_cancel_complete(uint8_t* p);
+
+extern void btm_read_inq_tx_power_timeout(void* data);
+extern void btm_read_inq_tx_power_complete(uint8_t* p);
+
+extern void btm_sec_init(uint8_t sec_mode);
+extern void btm_sec_dev_reset(void);
+extern void btm_sec_abort_access_req(const RawAddress& bd_addr);
+extern void btm_sec_auth_complete(uint16_t handle, uint8_t status);
+extern void btm_sec_encrypt_change(uint16_t handle, uint8_t status,
+ uint8_t encr_enable);
+extern void btm_sec_connected(const RawAddress& bda, uint16_t handle,
+ uint8_t status, uint8_t enc_mode);
+extern tBTM_STATUS btm_sec_disconnect(uint16_t handle, uint8_t reason);
+extern void btm_sec_disconnected(uint16_t handle, uint8_t reason);
+extern void btm_sec_rmt_name_request_complete(const RawAddress* bd_addr,
+ uint8_t* bd_name, uint8_t status);
+extern void btm_sec_rmt_host_support_feat_evt(uint8_t* p);
+extern void btm_io_capabilities_req(const RawAddress& p);
+extern void btm_io_capabilities_rsp(uint8_t* p);
+extern void btm_proc_sp_req_evt(tBTM_SP_EVT event, uint8_t* p);
+extern void btm_keypress_notif_evt(uint8_t* p);
+extern void btm_simple_pair_complete(uint8_t* p);
+extern void btm_sec_link_key_notification(const RawAddress& p_bda,
+ const Octet16& link_key,
+ uint8_t key_type);
+extern void btm_sec_link_key_request(const RawAddress& p_bda);
+extern void btm_sec_pin_code_request(const RawAddress& p_bda);
+extern void btm_sec_update_clock_offset(uint16_t handle, uint16_t clock_offset);
+extern void btm_sec_dev_rec_cback_event(tBTM_SEC_DEV_REC* p_dev_rec,
+ uint8_t res, bool is_le_trasnport);
+extern void btm_sec_set_peer_sec_caps(tACL_CONN* p_acl_cb,
+ tBTM_SEC_DEV_REC* p_dev_rec);
+
+extern void btm_sec_clear_ble_keys(tBTM_SEC_DEV_REC* p_dev_rec);
+extern bool btm_sec_is_a_bonded_dev(const RawAddress& bda);
+extern void btm_consolidate_dev(tBTM_SEC_DEV_REC* p_target_rec);
+extern bool btm_sec_is_le_capable_dev(const RawAddress& bda);
+extern bool btm_ble_init_pseudo_addr(tBTM_SEC_DEV_REC* p_dev_rec,
+ const RawAddress& new_pseudo_addr);
+extern tBTM_SEC_SERV_REC* btm_sec_find_first_serv(CONNECTION_TYPE conn_type,
+ uint16_t psm);
+extern tL2CAP_LE_RESULT_CODE btm_ble_start_sec_check(
+ const RawAddress& bd_addr, uint16_t psm, bool is_originator,
+ tBTM_SEC_CALLBACK* p_callback, void* p_ref_data);
+
+extern tINQ_DB_ENT* btm_inq_db_new(const RawAddress& p_bda);
+
+extern void btm_rem_oob_req(uint8_t* p);
+extern void btm_read_local_oob_complete(uint8_t* p);
+
+extern void btm_acl_resubmit_page(void);
+extern void btm_acl_reset_paging(void);
+extern void btm_acl_paging(BT_HDR* p, const RawAddress& dest);
+extern uint8_t btm_sec_clr_service_by_psm(uint16_t psm);
+extern void btm_sec_clr_temp_auth_service(const RawAddress& bda);
+extern tBTM_STATUS btm_sec_execute_procedure(tBTM_SEC_DEV_REC* p_dev_rec);
+
+#endif
diff --git a/stack/btm/btm_int_types.h b/stack/btm/btm_int_types.h
index 0622ddd51..1cd6cfa9f 100644
--- a/stack/btm/btm_int_types.h
+++ b/stack/btm/btm_int_types.h
@@ -18,55 +18,655 @@
#ifndef BTM_INT_TYPES_H
#define BTM_INT_TYPES_H
-#include <cstdint>
-#include <memory>
-#include <string>
-
-#include "gd/common/circular_buffer.h"
-#include "osi/include/allocator.h"
-#include "osi/include/fixed_queue.h"
+#include "btif/include/btif_bqr.h"
+#include "btm_api_types.h"
+#include "btm_ble_api_types.h"
+#include "btm_ble_int_types.h"
+#include "hcidefs.h"
+#include "osi/include/alarm.h"
#include "osi/include/list.h"
-#include "stack/acl/acl.h"
-#include "stack/btm/btm_ble_int_types.h"
-#include "stack/btm/btm_sco.h"
-#include "stack/btm/neighbor_inquiry.h"
-#include "stack/btm/security_device_record.h"
-#include "stack/include/btm_ble_api_types.h"
-#include "stack/include/security_client_callbacks.h"
-
-#define BTM_MAX_SCN_ 31 // PORT_MAX_RFC_PORTS system/bt/stack/include/rfcdefs.h
-
-constexpr size_t kMaxLogSize = 255;
-class TimestampedStringCircularBuffer
- : public bluetooth::common::TimestampedCircularBuffer<std::string> {
- public:
- explicit TimestampedStringCircularBuffer(size_t size)
- : bluetooth::common::TimestampedCircularBuffer<std::string>(size) {}
-
- void Push(std::string s) {
- bluetooth::common::TimestampedCircularBuffer<std::string>::Push(
- s.substr(0, kMaxLogSize));
- }
-
- template <typename... Args>
- void Push(Args... args) {
- char buf[kMaxLogSize];
- std::snprintf(buf, sizeof(buf), args...);
- bluetooth::common::TimestampedCircularBuffer<std::string>::Push(
- std::string(buf));
- }
-};
+#include "rfcdefs.h"
+
+typedef char tBTM_LOC_BD_NAME[BTM_MAX_LOC_BD_NAME_LEN + 1];
+
+#define BTM_ACL_IS_CONNECTED(bda) \
+ (btm_bda_to_acl(bda, BT_TRANSPORT_BR_EDR) != NULL)
+
+/* Definitions for Server Channel Number (SCN) management
+*/
+#define BTM_MAX_SCN PORT_MAX_RFC_PORTS
+
+/* Define masks for supported and exception 2.0 ACL packet types
+*/
+#define BTM_ACL_SUPPORTED_PKTS_MASK \
+ (HCI_PKT_TYPES_MASK_DM1 | HCI_PKT_TYPES_MASK_DH1 | HCI_PKT_TYPES_MASK_DM3 | \
+ HCI_PKT_TYPES_MASK_DH3 | HCI_PKT_TYPES_MASK_DM5 | HCI_PKT_TYPES_MASK_DH5)
+
+#define BTM_ACL_EXCEPTION_PKTS_MASK \
+ (HCI_PKT_TYPES_MASK_NO_2_DH1 | HCI_PKT_TYPES_MASK_NO_3_DH1 | \
+ HCI_PKT_TYPES_MASK_NO_2_DH3 | HCI_PKT_TYPES_MASK_NO_3_DH3 | \
+ HCI_PKT_TYPES_MASK_NO_2_DH5 | HCI_PKT_TYPES_MASK_NO_3_DH5)
+
+#define BTM_EPR_AVAILABLE(p) \
+ ((HCI_ATOMIC_ENCRYPT_SUPPORTED((p)->peer_lmp_feature_pages[0]) && \
+ HCI_ATOMIC_ENCRYPT_SUPPORTED( \
+ controller_get_interface()->get_features_classic(0)->as_array)) \
+ ? true \
+ : false)
+
+#define BTM_IS_BRCM_CONTROLLER() \
+ (controller_get_interface()->get_bt_version()->manufacturer == \
+ LMP_COMPID_BROADCOM)
+
+/* Define the ACL Management control structure
+*/
+typedef struct {
+ uint16_t hci_handle;
+ uint16_t pkt_types_mask;
+ uint16_t clock_offset;
+ RawAddress remote_addr;
+ DEV_CLASS remote_dc;
+ BD_NAME remote_name;
+
+ uint16_t manufacturer;
+ uint16_t lmp_subversion;
+ uint16_t link_super_tout;
+ BD_FEATURES
+ peer_lmp_feature_pages[HCI_EXT_FEATURES_PAGE_MAX + 1]; /* Peer LMP Extended
+ features mask table
+ for the device */
+ uint8_t num_read_pages;
+ uint8_t lmp_version;
+
+ bool in_use;
+ uint8_t link_role;
+ bool link_up_issued; /* True if busy_level link up has been issued */
+
+#define BTM_ACL_SWKEY_STATE_IDLE 0
+#define BTM_ACL_SWKEY_STATE_MODE_CHANGE 1
+#define BTM_ACL_SWKEY_STATE_ENCRYPTION_OFF 2
+#define BTM_ACL_SWKEY_STATE_SWITCHING 3
+#define BTM_ACL_SWKEY_STATE_ENCRYPTION_ON 4
+#define BTM_ACL_SWKEY_STATE_IN_PROGRESS 5
+ uint8_t switch_role_state;
+
+#define BTM_MAX_SW_ROLE_FAILED_ATTEMPTS 3
+ uint8_t switch_role_failed_attempts;
+
+#define BTM_ACL_ENCRYPT_STATE_IDLE 0
+#define BTM_ACL_ENCRYPT_STATE_ENCRYPT_OFF 1 /* encryption turning off */
+#define BTM_ACL_ENCRYPT_STATE_TEMP_FUNC \
+ 2 /* temporarily off for change link key or role switch */
+#define BTM_ACL_ENCRYPT_STATE_ENCRYPT_ON 3 /* encryption turning on */
+ uint8_t encrypt_state; /* overall BTM encryption state */
+
+ tBT_TRANSPORT transport;
+ RawAddress conn_addr; /* local device address used for this connection */
+ uint8_t conn_addr_type; /* local device address type for this connection */
+ RawAddress active_remote_addr; /* remote address used on this connection */
+ uint8_t active_remote_addr_type; /* local device address type for this
+ connection */
+ BD_FEATURES peer_le_features; /* Peer LE Used features mask for the device */
+
+} tACL_CONN;
+
+/* Define the Device Management control structure
+*/
+typedef struct {
+ tBTM_DEV_STATUS_CB* p_dev_status_cb; /* Device status change callback */
+ tBTM_VS_EVT_CB* p_vend_spec_cb
+ [BTM_MAX_VSE_CALLBACKS]; /* Register for vendor specific events */
+
+ tBTM_CMPL_CB*
+ p_stored_link_key_cmpl_cb; /* Read/Write/Delete stored link key */
+
+ alarm_t* read_local_name_timer; /* Read local name timer */
+ tBTM_CMPL_CB* p_rln_cmpl_cb; /* Callback function to be called when */
+ /* read local name function complete */
+
+ alarm_t* read_rssi_timer; /* Read RSSI timer */
+ tBTM_CMPL_CB* p_rssi_cmpl_cb; /* Callback function to be called when */
+ /* read RSSI function completes */
+
+ alarm_t* read_failed_contact_counter_timer; /* Read Failed Contact Counter */
+ /* timer */
+ tBTM_CMPL_CB* p_failed_contact_counter_cmpl_cb; /* Callback function to be */
+ /* called when read Failed Contact Counter function completes */
+
+ alarm_t*
+ read_automatic_flush_timeout_timer; /* Read Automatic Flush Timeout */
+ /* timer */
+ tBTM_CMPL_CB* p_automatic_flush_timeout_cmpl_cb; /* Callback function to be */
+ /* called when read Automatic Flush Timeout function completes */
+
+ alarm_t* read_link_quality_timer;
+ tBTM_CMPL_CB* p_link_qual_cmpl_cb; /* Callback function to be called when */
+ /* read link quality function completes */
+
+ alarm_t* read_inq_tx_power_timer;
+ tBTM_CMPL_CB*
+ p_inq_tx_power_cmpl_cb; /* Callback function to be called when */
+ /* read inq tx power function completes */
+
+ alarm_t* qos_setup_timer; /* QoS setup timer */
+ tBTM_CMPL_CB* p_qos_setup_cmpl_cb; /* Callback function to be called when */
+ /* qos setup function completes */
+
+ tBTM_ROLE_SWITCH_CMPL switch_role_ref_data;
+ tBTM_CMPL_CB* p_switch_role_cb; /* Callback function to be called when */
+ /* requested switch role is completed */
+
+ alarm_t* read_tx_power_timer; /* Read tx power timer */
+ tBTM_CMPL_CB* p_tx_power_cmpl_cb; /* Callback function to be called */
+
+ DEV_CLASS dev_class; /* Local device class */
+
+ tBTM_CMPL_CB*
+ p_le_test_cmd_cmpl_cb; /* Callback function to be called when
+ LE test mode command has been sent successfully */
+
+ RawAddress read_tx_pwr_addr; /* read TX power target address */
+
+#define BTM_LE_SUPPORT_STATE_SIZE 8
+ uint8_t le_supported_states[BTM_LE_SUPPORT_STATE_SIZE];
+
+ tBTM_BLE_LOCAL_ID_KEYS id_keys; /* local BLE ID keys */
+ Octet16 ble_encryption_key_value; /* BLE encryption key */
+
+#if (BTM_BLE_CONFORMANCE_TESTING == TRUE)
+ bool no_disc_if_pair_fail;
+ bool enable_test_mac_val;
+ BT_OCTET8 test_mac;
+ bool enable_test_local_sign_cntr;
+ uint32_t test_local_sign_cntr;
+#endif
+
+ tBTM_IO_CAP loc_io_caps; /* IO capability of the local device */
+ tBTM_AUTH_REQ loc_auth_req; /* the auth_req flag */
+ bool secure_connections_only; /* Rejects service level 0 connections if */
+ /* itself or peer device doesn't support */
+ /* secure connections */
+} tBTM_DEVCB;
+
+/* Define the structures and constants used for inquiry
+*/
+
+/* Definitions of limits for inquiries */
+#define BTM_PER_INQ_MIN_MAX_PERIOD HCI_PER_INQ_MIN_MAX_PERIOD
+#define BTM_PER_INQ_MAX_MAX_PERIOD HCI_PER_INQ_MAX_MAX_PERIOD
+#define BTM_PER_INQ_MIN_MIN_PERIOD HCI_PER_INQ_MIN_MIN_PERIOD
+#define BTM_PER_INQ_MAX_MIN_PERIOD HCI_PER_INQ_MAX_MIN_PERIOD
+#define BTM_MAX_INQUIRY_LENGTH HCI_MAX_INQUIRY_LENGTH
+#define BTM_MIN_INQUIRY_LEN 0x01
+
+#define BTM_MIN_INQ_TX_POWER (-70)
+#define BTM_MAX_INQ_TX_POWER 20
+
+typedef struct {
+ uint32_t inq_count; /* Used for determining if a response has already been */
+ /* received for the current inquiry operation. (We do not */
+ /* want to flood the caller with multiple responses from */
+ /* the same device. */
+ RawAddress bd_addr;
+} tINQ_BDADDR;
+
+typedef struct {
+ uint64_t time_of_resp;
+ uint32_t
+ inq_count; /* "timestamps" the entry with a particular inquiry count */
+ /* Used for determining if a response has already been */
+ /* received for the current inquiry operation. (We do not */
+ /* want to flood the caller with multiple responses from */
+ /* the same device. */
+ tBTM_INQ_INFO inq_info;
+ bool in_use;
+ bool scan_rsp;
+} tINQ_DB_ENT;
+
+enum { INQ_NONE, INQ_GENERAL };
+typedef uint8_t tBTM_INQ_TYPE;
+
+typedef struct {
+ tBTM_CMPL_CB* p_remname_cmpl_cb;
+
+#define BTM_EXT_RMT_NAME_TIMEOUT_MS (40 * 1000) /* 40 seconds */
+
+ alarm_t* remote_name_timer;
+
+ uint16_t discoverable_mode;
+ uint16_t connectable_mode;
+ uint16_t page_scan_window;
+ uint16_t page_scan_period;
+ uint16_t inq_scan_window;
+ uint16_t inq_scan_period;
+ uint16_t inq_scan_type;
+ uint16_t page_scan_type; /* current page scan type */
+ tBTM_INQ_TYPE scan_type;
+
+ RawAddress remname_bda; /* Name of bd addr for active remote name request */
+#define BTM_RMT_NAME_INACTIVE 0
+#define BTM_RMT_NAME_EXT 0x1 /* Initiated through API */
+#define BTM_RMT_NAME_SEC 0x2 /* Initiated internally by security manager */
+#define BTM_RMT_NAME_INQ 0x4 /* Remote name initiated internally by inquiry */
+ bool remname_active; /* State of a remote name request by external API */
+
+ tBTM_CMPL_CB* p_inq_cmpl_cb;
+ tBTM_INQ_RESULTS_CB* p_inq_results_cb;
+ tBTM_CMPL_CB* p_inqfilter_cmpl_cb; /* Called (if not NULL) after inquiry
+ filter completed */
+ uint32_t inq_counter; /* Counter incremented each time an inquiry completes */
+ /* Used for determining whether or not duplicate devices */
+ /* have responded to the same inquiry */
+ tINQ_BDADDR* p_bd_db; /* Pointer to memory that holds bdaddrs */
+ uint16_t num_bd_entries; /* Number of entries in database */
+ uint16_t max_bd_entries; /* Maximum number of entries that can be stored */
+ tINQ_DB_ENT inq_db[BTM_INQ_DB_SIZE];
+ tBTM_INQ_PARMS inqparms; /* Contains the parameters for the current inquiry */
+ tBTM_INQUIRY_CMPL
+ inq_cmpl_info; /* Status and number of responses from the last inquiry */
+
+ uint16_t per_min_delay; /* Current periodic minimum delay */
+ uint16_t per_max_delay; /* Current periodic maximum delay */
+ bool inqfilt_active;
+ uint8_t pending_filt_complete_event; /* to take care of
+ btm_event_filter_complete
+ corresponding to */
+ /* inquiry that has been cancelled*/
+ uint8_t inqfilt_type; /* Contains the inquiry filter type (BD ADDR, COD, or
+ Clear) */
+
+#define BTM_INQ_INACTIVE_STATE 0
+#define BTM_INQ_CLR_FILT_STATE \
+ 1 /* Currently clearing the inquiry filter preceeding the inquiry request */
+ /* (bypassed if filtering is not used) */
+#define BTM_INQ_SET_FILT_STATE \
+ 2 /* Sets the new filter (or turns off filtering) in this state */
+#define BTM_INQ_ACTIVE_STATE \
+ 3 /* Actual inquiry or periodic inquiry is in progress */
+#define BTM_INQ_REMNAME_STATE 4 /* Remote name requests are active */
+
+ uint8_t state; /* Current state that the inquiry process is in */
+ uint8_t inq_active; /* Bit Mask indicating type of inquiry is active */
+ bool no_inc_ssp; /* true, to stop inquiry on incoming SSP */
+} tBTM_INQUIRY_VAR_ST;
+
+/* The MSB of the clock offset field indicates whether the offset is valid. */
+#define BTM_CLOCK_OFFSET_VALID 0x8000
+
+/* Define the structures needed by security management
+*/
+
+#define BTM_SEC_INVALID_HANDLE 0xFFFF
+
+typedef uint8_t* BTM_BD_NAME_PTR; /* Pointer to Device name */
+
+/* Security callback is called by this unit when security
+ * procedures are completed. Parameters are
+ * BD Address of remote
+ * Result of the operation
+*/
+typedef tBTM_SEC_CBACK tBTM_SEC_CALLBACK;
+
+typedef void(tBTM_SCO_IND_CBACK)(uint16_t sco_inx);
+
+/* MACROs to convert from SCO packet types mask to ESCO and back */
+#define BTM_SCO_PKT_TYPE_MASK \
+ (HCI_PKT_TYPES_MASK_HV1 | HCI_PKT_TYPES_MASK_HV2 | HCI_PKT_TYPES_MASK_HV3)
+
+/* Mask defining only the SCO types of an esco packet type */
+#define BTM_ESCO_PKT_TYPE_MASK \
+ (ESCO_PKT_TYPES_MASK_HV1 | ESCO_PKT_TYPES_MASK_HV2 | ESCO_PKT_TYPES_MASK_HV3)
+
+#define BTM_SCO_2_ESCO(scotype) \
+ ((uint16_t)(((scotype)&BTM_SCO_PKT_TYPE_MASK) >> 5))
+#define BTM_ESCO_2_SCO(escotype) \
+ ((uint16_t)(((escotype)&BTM_ESCO_PKT_TYPE_MASK) << 5))
+
+/* Define masks for supported and exception 2.0 SCO packet types
+*/
+#define BTM_SCO_SUPPORTED_PKTS_MASK \
+ (ESCO_PKT_TYPES_MASK_HV1 | ESCO_PKT_TYPES_MASK_HV2 | \
+ ESCO_PKT_TYPES_MASK_HV3 | ESCO_PKT_TYPES_MASK_EV3 | \
+ ESCO_PKT_TYPES_MASK_EV4 | ESCO_PKT_TYPES_MASK_EV5)
+
+#define BTM_SCO_EXCEPTION_PKTS_MASK \
+ (ESCO_PKT_TYPES_MASK_NO_2_EV3 | ESCO_PKT_TYPES_MASK_NO_3_EV3 | \
+ ESCO_PKT_TYPES_MASK_NO_2_EV5 | ESCO_PKT_TYPES_MASK_NO_3_EV5)
+
+#define BTM_SCO_ROUTE_UNKNOWN 0xff
+
+/* Define the structure that contains (e)SCO data */
+typedef struct {
+ tBTM_ESCO_CBACK* p_esco_cback; /* Callback for eSCO events */
+ enh_esco_params_t setup;
+ tBTM_ESCO_DATA data; /* Connection complete information */
+ uint8_t hci_status;
+} tBTM_ESCO_INFO;
+
+/* Define the structure used for SCO Management
+*/
+typedef struct {
+ tBTM_ESCO_INFO esco; /* Current settings */
+ tBTM_SCO_CB* p_conn_cb; /* Callback for when connected */
+ tBTM_SCO_CB* p_disc_cb; /* Callback for when disconnect */
+ uint16_t state; /* The state of the SCO link */
+ uint16_t hci_handle; /* HCI Handle */
+ bool is_orig; /* true if the originator */
+ bool rem_bd_known; /* true if remote BD addr known */
+
+} tSCO_CONN;
+
+/* SCO Management control block */
+typedef struct {
+ tBTM_SCO_IND_CBACK* app_sco_ind_cb;
+ tSCO_CONN sco_db[BTM_MAX_SCO_LINKS];
+ enh_esco_params_t def_esco_parms;
+ uint16_t sco_disc_reason;
+ bool esco_supported; /* true if 1.2 cntlr AND supports eSCO links */
+ esco_data_path_t sco_route; /* HCI, PCM, or TEST */
+} tSCO_CB;
+
+extern void btm_set_sco_ind_cback(tBTM_SCO_IND_CBACK* sco_ind_cb);
+extern void btm_accept_sco_link(uint16_t sco_inx, enh_esco_params_t* p_setup,
+ tBTM_SCO_CB* p_conn_cb, tBTM_SCO_CB* p_disc_cb);
+extern void btm_reject_sco_link(uint16_t sco_inx);
+extern void btm_sco_chk_pend_rolechange(uint16_t hci_handle);
+extern void btm_sco_disc_chk_pend_for_modechange(uint16_t hci_handle);
+
+/*
+ * Define structure for Security Service Record.
+ * A record exists for each service registered with the Security Manager
+*/
+#define BTM_SEC_OUT_FLAGS \
+ (BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT | BTM_SEC_OUT_AUTHORIZE)
+#define BTM_SEC_IN_FLAGS \
+ (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT | BTM_SEC_IN_AUTHORIZE)
+
+#define BTM_SEC_OUT_LEVEL4_FLAGS \
+ (BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT | BTM_SEC_OUT_MITM | \
+ BTM_SEC_MODE4_LEVEL4)
+
+#define BTM_SEC_IN_LEVEL4_FLAGS \
+ (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT | BTM_SEC_IN_MITM | \
+ BTM_SEC_MODE4_LEVEL4)
+typedef struct {
+ uint32_t mx_proto_id; /* Service runs over this multiplexer protocol */
+ uint32_t orig_mx_chan_id; /* Channel on the multiplexer protocol */
+ uint32_t term_mx_chan_id; /* Channel on the multiplexer protocol */
+ uint16_t psm; /* L2CAP PSM value */
+ uint16_t security_flags; /* Bitmap of required security features */
+ uint8_t service_id; /* Passed in authorization callback */
+#if BTM_SEC_SERVICE_NAME_LEN > 0
+ uint8_t orig_service_name[BTM_SEC_SERVICE_NAME_LEN + 1];
+ uint8_t term_service_name[BTM_SEC_SERVICE_NAME_LEN + 1];
+#endif
+} tBTM_SEC_SERV_REC;
+
+/* LE Security information of device in Slave Role */
+typedef struct {
+ Octet16 irk; /* peer diverified identity root */
+ Octet16 pltk; /* peer long term key */
+ Octet16 pcsrk; /* peer SRK peer device used to secured sign local data */
+
+ Octet16 lltk; /* local long term key */
+ Octet16 lcsrk; /* local SRK peer device used to secured sign local data */
+
+ BT_OCTET8 rand; /* random vector for LTK generation */
+ uint16_t ediv; /* LTK diversifier of this slave device */
+ uint16_t div; /* local DIV to generate local LTK=d1(ER,DIV,0) and
+ CSRK=d1(ER,DIV,1) */
+ uint8_t sec_level; /* local pairing security level */
+ uint8_t key_size; /* key size of the LTK delivered to peer device */
+ uint8_t srk_sec_level; /* security property of peer SRK for this device */
+ uint8_t local_csrk_sec_level; /* security property of local CSRK for this
+ device */
+
+ uint32_t counter; /* peer sign counter for verifying rcv signed cmd */
+ uint32_t local_counter; /* local sign counter for sending signed write cmd*/
+} tBTM_SEC_BLE_KEYS;
+
+typedef struct {
+ RawAddress pseudo_addr; /* LE pseudo address of the device if different from
+ device address */
+ tBLE_ADDR_TYPE ble_addr_type; /* LE device type: public or random address */
+ tBLE_ADDR_TYPE identity_addr_type; /* identity address type */
+ RawAddress identity_addr; /* identity address */
+
+#define BTM_WHITE_LIST_BIT 0x01
+#define BTM_RESOLVING_LIST_BIT 0x02
+ uint8_t in_controller_list; /* in controller resolving list or not */
+ uint8_t resolving_list_index;
+#if (BLE_PRIVACY_SPT == TRUE)
+ RawAddress cur_rand_addr; /* current random address */
+
+#define BTM_BLE_ADDR_PSEUDO 0 /* address index device record */
+#define BTM_BLE_ADDR_RRA 1 /* cur_rand_addr */
+#define BTM_BLE_ADDR_STATIC 2 /* static_addr */
+ uint8_t active_addr_type;
+#endif
+
+ tBTM_LE_KEY_TYPE key_type; /* bit mask of valid key types in record */
+ tBTM_SEC_BLE_KEYS keys; /* LE device security info in slave rode */
+} tBTM_SEC_BLE;
+
+/* Peering bond type */
+enum { BOND_TYPE_UNKNOWN, BOND_TYPE_PERSISTENT, BOND_TYPE_TEMPORARY };
+typedef uint8_t tBTM_BOND_TYPE;
/*
- * Local device configuration
- */
+ * Define structure for Security Device Record.
+ * A record exists for each device authenticated with this device
+*/
+typedef struct {
+ tBTM_SEC_SERV_REC* p_cur_service;
+ tBTM_SEC_CALLBACK* p_callback;
+ void* p_ref_data;
+ uint32_t timestamp; /* Timestamp of the last connection */
+ uint32_t trusted_mask[BTM_SEC_SERVICE_ARRAY_SIZE]; /* Bitwise OR of trusted
+ services */
+ uint16_t hci_handle; /* Handle to connection when exists */
+ uint16_t clock_offset; /* Latest known clock offset */
+ RawAddress bd_addr; /* BD_ADDR of the device */
+ DEV_CLASS dev_class; /* DEV_CLASS of the device */
+ LinkKey link_key; /* Device link key */
+ uint8_t pin_code_length; /* Length of the pin_code used for paring */
+
+#define BTM_SEC_AUTHORIZED BTM_SEC_FLAG_AUTHORIZED /* 0x01 */
+#define BTM_SEC_AUTHENTICATED BTM_SEC_FLAG_AUTHENTICATED /* 0x02 */
+#define BTM_SEC_ENCRYPTED BTM_SEC_FLAG_ENCRYPTED /* 0x04 */
+#define BTM_SEC_NAME_KNOWN 0x08
+#define BTM_SEC_LINK_KEY_KNOWN BTM_SEC_FLAG_LKEY_KNOWN /* 0x10 */
+#define BTM_SEC_LINK_KEY_AUTHED BTM_SEC_FLAG_LKEY_AUTHED /* 0x20 */
+#define BTM_SEC_ROLE_SWITCHED 0x40
+#define BTM_SEC_IN_USE 0x80
+/* LE link security flag */
+#define BTM_SEC_LE_AUTHENTICATED \
+ 0x0200 /* LE link is encrypted after pairing with MITM */
+#define BTM_SEC_LE_ENCRYPTED 0x0400 /* LE link is encrypted */
+#define BTM_SEC_LE_NAME_KNOWN 0x0800 /* not used */
+#define BTM_SEC_LE_LINK_KEY_KNOWN \
+ 0x1000 /* bonded with peer (peer LTK and/or SRK is saved) */
+#define BTM_SEC_LE_LINK_KEY_AUTHED 0x2000 /* pairing is done with MITM */
+#define BTM_SEC_16_DIGIT_PIN_AUTHED \
+ 0x4000 /* pairing is done with 16 digit pin */
+
+ uint16_t sec_flags; /* Current device security state */
+
+ tBTM_BD_NAME sec_bd_name; /* User friendly name of the device. (may be
+ truncated to save space in dev_rec table) */
+ BD_FEATURES feature_pages[HCI_EXT_FEATURES_PAGE_MAX +
+ 1]; /* Features supported by the device */
+ uint8_t num_read_pages;
+
+#define BTM_SEC_STATE_IDLE 0
+#define BTM_SEC_STATE_AUTHENTICATING 1
+#define BTM_SEC_STATE_ENCRYPTING 2
+#define BTM_SEC_STATE_GETTING_NAME 3
+#define BTM_SEC_STATE_AUTHORIZING 4
+#define BTM_SEC_STATE_SWITCHING_ROLE 5
+#define BTM_SEC_STATE_DISCONNECTING 6 /* disconnecting BR/EDR */
+#define BTM_SEC_STATE_DELAY_FOR_ENC \
+ 7 /* delay to check for encryption to work around */
+ /* controller problems */
+#define BTM_SEC_STATE_DISCONNECTING_BLE 8 /* disconnecting BLE */
+#define BTM_SEC_STATE_DISCONNECTING_BOTH 9 /* disconnecting BR/EDR and BLE */
+
+ uint8_t sec_state; /* Operating state */
+ bool is_originator; /* true if device is originating connection */
+ bool role_master; /* true if current mode is master */
+ uint16_t security_required; /* Security required for connection */
+ bool link_key_not_sent; /* link key notification has not been sent waiting for
+ name */
+ uint8_t link_key_type; /* Type of key used in pairing */
+ bool link_key_changed; /* Changed link key during current connection */
+
+#define BTM_MAX_PRE_SM4_LKEY_TYPE \
+ BTM_LKEY_TYPE_REMOTE_UNIT /* the link key type used by legacy pairing */
+
+#define BTM_SM4_UNKNOWN 0x00
+#define BTM_SM4_KNOWN 0x10
+#define BTM_SM4_TRUE 0x11
+#define BTM_SM4_REQ_PEND 0x08 /* set this bit when getting remote features */
+#define BTM_SM4_UPGRADE 0x04 /* set this bit when upgrading link key */
+#define BTM_SM4_RETRY \
+ 0x02 /* set this bit to retry on HCI_ERR_KEY_MISSING or \
+ HCI_ERR_LMP_ERR_TRANS_COLLISION */
+#define BTM_SM4_DD_ACP \
+ 0x20 /* set this bit to indicate peer initiated dedicated bonding */
+#define BTM_SM4_CONN_PEND \
+ 0x40 /* set this bit to indicate accepting acl conn; to be cleared on \
+ btm_acl_created */
+ uint8_t sm4; /* BTM_SM4_TRUE, if the peer supports SM4 */
+ tBTM_IO_CAP rmt_io_caps; /* IO capability of the peer device */
+ tBTM_AUTH_REQ rmt_auth_req; /* the auth_req flag as in the IO caps rsp evt */
+ bool remote_supports_secure_connections;
+ bool remote_features_needed; /* set to true if the local device is in */
+ /* "Secure Connections Only" mode and it receives */
+ /* HCI_IO_CAPABILITY_REQUEST_EVT from the peer before */
+ /* it knows peer's support for Secure Connections */
+
+ uint16_t ble_hci_handle; /* use in DUMO connection */
+ uint8_t enc_key_size; /* current link encryption key size */
+ tBT_DEVICE_TYPE device_type;
+ bool new_encryption_key_is_p256; /* Set to true when the newly generated LK
+ ** is generated from P-256.
+ ** Link encrypted with such LK can be used
+ ** for SM over BR/EDR.
+ */
+ bool no_smp_on_br; /* if set to true then SMP on BR/EDR doesn't */
+ /* work, i.e. link keys crosspairing */
+ /* SC BR/EDR->SC LE doesn't happen */
+ tBTM_BOND_TYPE bond_type; /* peering bond type */
+
+ tBTM_SEC_BLE ble;
+ tBTM_LE_CONN_PRAMS conn_params;
+
+#if (BTM_DISC_DURING_RS == TRUE)
+#define BTM_SEC_RS_NOT_PENDING 0 /* Role Switch not in progress */
+#define BTM_SEC_RS_PENDING 1 /* Role Switch in progress */
+#define BTM_SEC_DISC_PENDING 2 /* Disconnect is pending */
+ uint8_t rs_disc_pending;
+#endif
+#define BTM_SEC_NO_LAST_SERVICE_ID 0
+ uint8_t last_author_service_id; /* ID of last serviced authorized: Reset after
+ each l2cap connection */
+
+} tBTM_SEC_DEV_REC;
+
+#define BTM_SEC_IS_SM4(sm) ((bool)(BTM_SM4_TRUE == ((sm)&BTM_SM4_TRUE)))
+#define BTM_SEC_IS_SM4_LEGACY(sm) ((bool)(BTM_SM4_KNOWN == ((sm)&BTM_SM4_TRUE)))
+#define BTM_SEC_IS_SM4_UNKNOWN(sm) \
+ ((bool)(BTM_SM4_UNKNOWN == ((sm)&BTM_SM4_TRUE)))
+
+#define BTM_SEC_LE_MASK \
+ (BTM_SEC_LE_AUTHENTICATED | BTM_SEC_LE_ENCRYPTED | \
+ BTM_SEC_LE_LINK_KEY_KNOWN | BTM_SEC_LE_LINK_KEY_AUTHED)
+
+/*
+ * Define device configuration structure
+*/
typedef struct {
tBTM_LOC_BD_NAME bd_name; /* local Bluetooth device name */
bool pin_type; /* true if PIN type is fixed */
uint8_t pin_code_len; /* Bonding information */
PIN_CODE pin_code; /* PIN CODE if pin type is fixed */
+ bool connectable; /* If true page scan should be enabled */
+ uint8_t def_inq_scan_mode; /* ??? limited/general/none */
} tBTM_CFG;
+enum {
+ BTM_PM_ST_ACTIVE = BTM_PM_STS_ACTIVE,
+ BTM_PM_ST_HOLD = BTM_PM_STS_HOLD,
+ BTM_PM_ST_SNIFF = BTM_PM_STS_SNIFF,
+ BTM_PM_ST_PARK = BTM_PM_STS_PARK,
+ BTM_PM_ST_PENDING = BTM_PM_STS_PENDING,
+ BTM_PM_ST_INVALID = 0xFF
+};
+typedef uint8_t tBTM_PM_STATE;
+
+enum {
+ BTM_PM_SET_MODE_EVT, /* Set power mode API is called. */
+ BTM_PM_UPDATE_EVT,
+ BTM_PM_RD_MODE_EVT /* Read power mode API is called. */
+};
+typedef uint8_t tBTM_PM_EVENT;
+
+typedef struct {
+ uint16_t event;
+ uint16_t len;
+ uint8_t link_ind;
+} tBTM_PM_MSG_DATA;
+
+typedef struct {
+ uint8_t hci_status;
+ uint8_t mode;
+ uint16_t interval;
+} tBTM_PM_MD_CHG_DATA;
+
+typedef struct {
+ uint8_t pm_id; /* the entity that calls SetPowerMode API */
+ tBTM_PM_PWR_MD* p_pmd;
+} tBTM_PM_SET_MD_DATA;
+
+typedef struct {
+ void* p_data;
+ uint8_t link_ind;
+} tBTM_PM_SM_DATA;
+
+typedef struct {
+ tBTM_PM_PWR_MD req_mode[BTM_MAX_PM_RECORDS + 1]; /* the desired mode and
+ parameters of the
+ connection*/
+ tBTM_PM_PWR_MD
+ set_mode; /* the mode and parameters sent down to the host controller. */
+ uint16_t interval; /* the interval from last mode change event. */
+#if (BTM_SSR_INCLUDED == TRUE)
+ uint16_t max_lat; /* stored SSR maximum latency */
+ uint16_t min_rmt_to; /* stored SSR minimum remote timeout */
+ uint16_t min_loc_to; /* stored SSR minimum local timeout */
+#endif
+ tBTM_PM_STATE state; /* contains the current mode of the connection */
+ bool chg_ind; /* a request change indication */
+} tBTM_PM_MCB;
+
+#define BTM_PM_REC_NOT_USED 0
+typedef struct {
+ tBTM_PM_STATUS_CBACK*
+ cback; /* to notify the registered party of mode change event */
+ uint8_t mask; /* registered request mask. 0, if this entry is not used */
+} tBTM_PM_RCB;
+
+enum {
+ BTM_BLI_ACL_UP_EVT,
+ BTM_BLI_ACL_DOWN_EVT,
+ BTM_BLI_PAGE_EVT,
+ BTM_BLI_PAGE_DONE_EVT,
+ BTM_BLI_INQ_EVT,
+ BTM_BLI_INQ_CANCEL_EVT,
+ BTM_BLI_INQ_DONE_EVT
+};
+typedef uint8_t tBTM_BLI_EVENT;
+
/* Pairing State */
enum {
BTM_PAIR_STATE_IDLE, /* Idle */
@@ -111,11 +711,16 @@ typedef struct {
bool is_orig;
tBTM_SEC_CALLBACK* p_callback;
void* p_ref_data;
- uint16_t rfcomm_security_requirement;
+ uint32_t mx_proto_id;
+ uint32_t mx_chan_id;
tBT_TRANSPORT transport;
tBTM_BLE_SEC_ACT sec_act;
} tBTM_SEC_QUEUE_ENTRY;
+#define CONN_ORIENT_TERM false
+#define CONN_ORIENT_ORIG true
+typedef bool CONNECTION_TYPE;
+
// Bluetooth Quality Report - Report receiver
typedef void(tBTM_BT_QUALITY_REPORT_RECEIVER)(uint8_t len, uint8_t* p_stream);
@@ -124,87 +729,28 @@ typedef void(tBTM_BT_QUALITY_REPORT_RECEIVER)(uint8_t len, uint8_t* p_stream);
#define BTM_STATE_BUFFER_SIZE 5 /* size of state buffer */
-/* Define the Device Management control structure
- */
-typedef struct tBTM_DEVCB {
- tBTM_VS_EVT_CB* p_vend_spec_cb[BTM_MAX_VSE_CALLBACKS]; /* Register for vendor
- specific events */
-
- tBTM_CMPL_CB*
- p_stored_link_key_cmpl_cb; /* Read/Write/Delete stored link key */
-
- alarm_t* read_local_name_timer; /* Read local name timer */
- tBTM_CMPL_CB* p_rln_cmpl_cb; /* Callback function to be called when */
- /* read local name function complete */
-
- alarm_t* read_rssi_timer; /* Read RSSI timer */
- tBTM_CMPL_CB* p_rssi_cmpl_cb; /* Callback function to be called when */
- /* read RSSI function completes */
-
- alarm_t* read_failed_contact_counter_timer; /* Read Failed Contact Counter */
- /* timer */
- tBTM_CMPL_CB* p_failed_contact_counter_cmpl_cb; /* Callback function to be */
- /* called when read Failed Contact Counter function completes */
-
- alarm_t*
- read_automatic_flush_timeout_timer; /* Read Automatic Flush Timeout */
- /* timer */
- tBTM_CMPL_CB* p_automatic_flush_timeout_cmpl_cb; /* Callback function to be */
- /* called when read Automatic Flush Timeout function completes */
-
- alarm_t* read_link_quality_timer;
- tBTM_CMPL_CB* p_link_qual_cmpl_cb; /* Callback function to be called when */
- /* read link quality function completes */
-
- alarm_t* read_tx_power_timer; /* Read tx power timer */
- tBTM_CMPL_CB* p_tx_power_cmpl_cb; /* Callback function to be called */
-
- DEV_CLASS dev_class; /* Local device class */
-
- tBTM_CMPL_CB*
- p_le_test_cmd_cmpl_cb; /* Callback function to be called when
- LE test mode command has been sent successfully */
-
- RawAddress read_tx_pwr_addr; /* read TX power target address */
-
- tBTM_BLE_LOCAL_ID_KEYS id_keys; /* local BLE ID keys */
- Octet16 ble_encryption_key_value; /* BLE encryption key */
-
-#if (BTM_BLE_CONFORMANCE_TESTING == TRUE)
- bool no_disc_if_pair_fail;
- bool enable_test_mac_val;
- BT_OCTET8 test_mac;
- bool enable_test_local_sign_cntr;
- uint32_t test_local_sign_cntr;
-#endif
-
- tBTM_IO_CAP loc_io_caps; /* IO capability of the local device */
- tBTM_AUTH_REQ loc_auth_req; /* the auth_req flag */
-
- void Init() {
- read_local_name_timer = alarm_new("btm.read_local_name_timer");
- read_rssi_timer = alarm_new("btm.read_rssi_timer");
- read_failed_contact_counter_timer =
- alarm_new("btm.read_failed_contact_counter_timer");
- read_automatic_flush_timeout_timer =
- alarm_new("btm.read_automatic_flush_timeout_timer");
- read_link_quality_timer = alarm_new("btm.read_link_quality_timer");
- read_tx_power_timer = alarm_new("btm.read_tx_power_timer");
- }
-
- void Free() {
- alarm_free(read_local_name_timer);
- alarm_free(read_rssi_timer);
- alarm_free(read_failed_contact_counter_timer);
- alarm_free(read_automatic_flush_timeout_timer);
- alarm_free(read_link_quality_timer);
- alarm_free(read_tx_power_timer);
- }
-} tBTM_DEVCB;
-
-typedef struct tBTM_CB {
+typedef struct {
tBTM_CFG cfg; /* Device configuration */
+ /****************************************************
+ ** ACL Management
+ ****************************************************/
+ tACL_CONN acl_db[MAX_L2CAP_LINKS];
+ uint8_t btm_scn[BTM_MAX_SCN]; /* current SCNs: true if SCN is in use */
+ uint16_t btm_def_link_policy;
+ uint16_t btm_def_link_super_tout;
+
+ tBTM_BL_EVENT_MASK bl_evt_mask;
+ tBTM_BL_CHANGE_CB* p_bl_changed_cb; /* Callback for when Busy Level changed */
+
+ /****************************************************
+ ** Power Management
+ ****************************************************/
+ tBTM_PM_MCB pm_mode_db[MAX_L2CAP_LINKS]; /* per ACL link */
+ tBTM_PM_RCB pm_reg_db[BTM_MAX_PM_RECORDS + 1]; /* per application/module */
+ uint8_t pm_pend_link; /* the index of acl_db, which has a pending PM cmd */
+ uint8_t pm_pend_id; /* the id pf the module, which has a pending PM cmd */
+
/*****************************************************
** Device control
*****************************************************/
@@ -215,28 +761,15 @@ typedef struct tBTM_CB {
*****************************************************/
tBTM_BLE_CB ble_ctr_cb;
- private:
- friend void btm_ble_ltk_request_reply(const RawAddress& bda, bool use_stk,
- const Octet16& stk);
- friend tBTM_STATUS btm_ble_start_encrypt(const RawAddress& bda, bool use_stk,
- Octet16* p_stk);
- friend void btm_ble_ltk_request_reply(const RawAddress& bda, bool use_stk,
- const Octet16& stk);
- uint16_t enc_handle{0};
-
- friend void btm_ble_ltk_request(uint16_t handle, uint8_t rand[8],
- uint16_t ediv);
+ uint16_t enc_handle;
BT_OCTET8 enc_rand; /* received rand value from LTK request*/
-
- uint16_t ediv{0}; /* received ediv value from LTK request */
-
- uint8_t key_size{0};
-
- public:
+ uint16_t ediv; /* received ediv value from LTK request */
+ uint8_t key_size;
tBTM_BLE_VSC_CB cmn_ble_vsc_cb;
/* Packet types supported by the local device */
- uint16_t btm_sco_pkt_types_supported{0};
+ uint16_t btm_acl_pkt_types_supported;
+ uint16_t btm_sco_pkt_types_supported;
/*****************************************************
** Inquiry
@@ -256,128 +789,47 @@ typedef struct tBTM_CB {
#define BTM_SEC_MAX_RMT_NAME_CALLBACKS 2
tBTM_RMT_NAME_CALLBACK* p_rmt_name_callback[BTM_SEC_MAX_RMT_NAME_CALLBACKS];
- tBTM_SEC_DEV_REC* p_collided_dev_rec{nullptr};
- alarm_t* sec_collision_timer{nullptr};
- uint64_t collision_start_time{0};
- uint32_t dev_rec_count{0}; /* Counter used for device record timestamp */
- uint8_t security_mode{0};
- bool pairing_disabled{false};
- bool security_mode_changed{false}; /* mode changed during bonding */
- bool pin_type_changed{false}; /* pin type changed during bonding */
- bool sec_req_pending{false}; /* true if a request is pending */
-
- uint8_t pin_code_len{0}; /* for legacy devices */
+ tBTM_SEC_DEV_REC* p_collided_dev_rec;
+ alarm_t* sec_collision_timer;
+ uint64_t collision_start_time;
+ uint32_t dev_rec_count; /* Counter used for device record timestamp */
+ uint8_t security_mode;
+ bool pairing_disabled;
+ bool connect_only_paired;
+ bool security_mode_changed; /* mode changed during bonding */
+ bool pin_type_changed; /* pin type changed during bonding */
+ bool sec_req_pending; /* true if a request is pending */
+
+ uint8_t pin_code_len; /* for legacy devices */
PIN_CODE pin_code; /* for legacy devices */
- tBTM_PAIRING_STATE pairing_state{
- BTM_PAIR_STATE_IDLE}; /* The current pairing state */
- uint8_t pairing_flags{0}; /* The current pairing flags */
+ tBTM_PAIRING_STATE pairing_state; /* The current pairing state */
+ uint8_t pairing_flags; /* The current pairing flags */
RawAddress pairing_bda; /* The device currently pairing */
- alarm_t* pairing_timer{nullptr}; /* Timer for pairing process */
- uint16_t disc_handle{0}; /* for legacy devices */
- uint8_t disc_reason{0}; /* for legacy devices */
+ alarm_t* pairing_timer; /* Timer for pairing process */
+ uint16_t disc_handle; /* for legacy devices */
+ uint8_t disc_reason; /* for legacy devices */
tBTM_SEC_SERV_REC sec_serv_rec[BTM_SEC_MAX_SERVICE_RECORDS];
- list_t* sec_dev_rec{nullptr}; /* list of tBTM_SEC_DEV_REC */
- tBTM_SEC_SERV_REC* p_out_serv{nullptr};
- tBTM_MKEY_CALLBACK* mkey_cback{nullptr};
+ list_t* sec_dev_rec; /* list of tBTM_SEC_DEV_REC */
+ tBTM_SEC_SERV_REC* p_out_serv;
+ tBTM_MKEY_CALLBACK* mkey_cback;
RawAddress connecting_bda;
DEV_CLASS connecting_dc;
- uint8_t trace_level;
- bool is_paging{false}; /* true, if paging is in progess */
- bool is_inquiry{false}; /* true, if inquiry is in progess */
- fixed_queue_t* page_queue{nullptr};
-
- bool paging{false};
- void set_paging() { paging = true; }
- void reset_paging() { paging = false; }
- bool is_paging_active() const {
- return paging;
- } // TODO remove all this paging state
-
- fixed_queue_t* sec_pending_q{nullptr}; /* pending sequrity requests in
- tBTM_SEC_QUEUE_ENTRY format */
+ uint8_t acl_disc_reason;
+ uint8_t trace_level;
+ uint8_t busy_level; /* the current busy level */
+ bool is_paging; /* true, if paging is in progess */
+ bool is_inquiry; /* true, if inquiry is in progess */
+ fixed_queue_t* page_queue;
+ bool paging;
+ bool discing;
+ fixed_queue_t* sec_pending_q; /* pending sequrity requests in
+ tBTM_SEC_QUEUE_ENTRY format */
+
+ char state_temp_buffer[BTM_STATE_BUFFER_SIZE];
// BQR Receiver
- tBTM_BT_QUALITY_REPORT_RECEIVER* p_bqr_report_receiver{nullptr};
-
-#define BTM_CODEC_TYPE_MAX_RECORDS 32
- tBTM_BT_DYNAMIC_AUDIO_BUFFER_CB
- dynamic_audio_buffer_cb[BTM_CODEC_TYPE_MAX_RECORDS];
-
- tACL_CB acl_cb_;
-
- std::shared_ptr<TimestampedStringCircularBuffer> history_{nullptr};
-
- void Init(uint8_t initial_security_mode) {
- memset(&cfg, 0, sizeof(cfg));
- memset(&devcb, 0, sizeof(devcb));
- memset(&ble_ctr_cb, 0, sizeof(ble_ctr_cb));
- memset(&enc_rand, 0, sizeof(enc_rand));
- memset(&cmn_ble_vsc_cb, 0, sizeof(cmn_ble_vsc_cb));
- memset(&btm_inq_vars, 0, sizeof(btm_inq_vars));
- memset(&sco_cb, 0, sizeof(sco_cb));
- memset(&api, 0, sizeof(api));
- memset(p_rmt_name_callback, 0, sizeof(p_rmt_name_callback));
- memset(&pin_code, 0, sizeof(pin_code));
- memset(sec_serv_rec, 0, sizeof(sec_serv_rec));
-
- connecting_bda = RawAddress::kEmpty;
- memset(&connecting_dc, 0, sizeof(connecting_dc));
-
- memset(&acl_cb_, 0, sizeof(acl_cb_));
-
- page_queue = fixed_queue_new(SIZE_MAX);
- sec_pending_q = fixed_queue_new(SIZE_MAX);
- sec_collision_timer = alarm_new("btm.sec_collision_timer");
- pairing_timer = alarm_new("btm.pairing_timer");
-
-#if defined(BTM_INITIAL_TRACE_LEVEL)
- trace_level = BTM_INITIAL_TRACE_LEVEL;
-#else
- trace_level = BT_TRACE_LEVEL_NONE; /* No traces */
-#endif
- security_mode = initial_security_mode;
- pairing_bda = RawAddress::kAny;
- sec_dev_rec = list_new(osi_free);
-
- /* Initialize BTM component structures */
- btm_inq_vars.Init(); /* Inquiry Database and Structures */
- acl_cb_ = {};
- sco_cb.Init(); /* SCO Database and Structures (If included) */
- devcb.Init();
-
- history_ = std::make_shared<TimestampedStringCircularBuffer>(40);
- CHECK(history_ != nullptr);
- history_->Push(std::string("Initialized btm history"));
- }
-
- void Free() {
- history_.reset();
-
- devcb.Free();
- btm_inq_vars.Free();
-
- fixed_queue_free(page_queue, nullptr);
- page_queue = nullptr;
-
- fixed_queue_free(sec_pending_q, nullptr);
- sec_pending_q = nullptr;
-
- list_free(sec_dev_rec);
- sec_dev_rec = nullptr;
-
- alarm_free(sec_collision_timer);
- sec_collision_timer = nullptr;
-
- alarm_free(pairing_timer);
- pairing_timer = nullptr;
- }
-
- private:
- friend uint8_t BTM_AllocateSCN(void);
- friend bool BTM_TryAllocateSCN(uint8_t scn);
- friend bool BTM_FreeSCN(uint8_t scn);
- uint8_t btm_scn[BTM_MAX_SCN_];
+ tBTM_BT_QUALITY_REPORT_RECEIVER* p_bqr_report_receiver;
} tBTM_CB;
/* security action for L2CAP COC channels */
diff --git a/stack/btm/btm_iso.cc b/stack/btm/btm_iso.cc
deleted file mode 100644
index 8ba9bb2eb..000000000
--- a/stack/btm/btm_iso.cc
+++ /dev/null
@@ -1,144 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <memory>
-
-#include "btm_iso_api.h"
-#include "btm_iso_impl.h"
-#include "btu.h"
-
-using bluetooth::hci::iso_manager::BigCallbacks;
-using bluetooth::hci::iso_manager::CigCallbacks;
-using bluetooth::hci::iso_manager::iso_impl;
-
-namespace bluetooth {
-namespace hci {
-
-struct IsoManager::impl {
- impl(const IsoManager& iso_manager) : iso_manager_(iso_manager) {}
-
- void Start() {
- LOG_ASSERT(!iso_impl_);
- iso_impl_ = std::make_unique<iso_impl>();
- }
-
- void Stop() {
- LOG_ASSERT(iso_impl_);
- iso_impl_.reset();
- }
-
- bool IsRunning() { return iso_impl_ ? true : false; }
-
- const IsoManager& iso_manager_;
- std::unique_ptr<iso_impl> iso_impl_;
-};
-
-IsoManager::IsoManager() : pimpl_(std::make_unique<impl>(*this)) {}
-
-void IsoManager::RegisterCigCallbacks(CigCallbacks* callbacks) const {
- pimpl_->iso_impl_->handle_register_cis_callbacks(callbacks);
-}
-
-void IsoManager::RegisterBigCallbacks(BigCallbacks* callbacks) const {
- pimpl_->iso_impl_->handle_register_big_callbacks(callbacks);
-}
-
-void IsoManager::CreateCig(uint8_t cig_id,
- struct iso_manager::cig_create_params cig_params) {
- pimpl_->iso_impl_->create_cig(cig_id, std::move(cig_params));
-}
-
-void IsoManager::ReconfigureCig(
- uint8_t cig_id, struct iso_manager::cig_create_params cig_params) {
- pimpl_->iso_impl_->reconfigure_cig(cig_id, std::move(cig_params));
-}
-
-void IsoManager::RemoveCig(uint8_t cig_id) {
- pimpl_->iso_impl_->remove_cig(cig_id);
-}
-
-void IsoManager::EstablishCis(
- struct iso_manager::cis_establish_params conn_params) {
- pimpl_->iso_impl_->establish_cis(std::move(conn_params));
-}
-
-void IsoManager::DisconnectCis(uint16_t cis_handle, uint8_t reason) {
- pimpl_->iso_impl_->disconnect_cis(cis_handle, reason);
-}
-
-void IsoManager::SetupIsoDataPath(
- uint16_t iso_handle, struct iso_manager::iso_data_path_params path_params) {
- pimpl_->iso_impl_->setup_iso_data_path(iso_handle, std::move(path_params));
-}
-
-void IsoManager::RemoveIsoDataPath(uint16_t iso_handle, uint8_t data_path_dir) {
- pimpl_->iso_impl_->remove_iso_data_path(iso_handle, data_path_dir);
-}
-
-void IsoManager::ReadIsoLinkQuality(uint16_t iso_handle) {
- pimpl_->iso_impl_->read_iso_link_quality(iso_handle);
-}
-
-void IsoManager::SendIsoData(uint16_t iso_handle, const uint8_t* data,
- uint16_t data_len) {
- pimpl_->iso_impl_->send_iso_data(iso_handle, data, data_len);
-}
-
-void IsoManager::CreateBig(uint8_t big_id,
- struct iso_manager::big_create_params big_params) {
- pimpl_->iso_impl_->create_big(big_id, std::move(big_params));
-}
-
-void IsoManager::TerminateBig(uint8_t big_id, uint8_t reason) {
- pimpl_->iso_impl_->terminate_big(big_id, reason);
-}
-
-void IsoManager::HandleIsoData(void* p_msg) {
- if (pimpl_->IsRunning())
- pimpl_->iso_impl_->handle_iso_data(static_cast<BT_HDR*>(p_msg));
-}
-
-void IsoManager::HandleDisconnect(uint16_t handle, uint8_t reason) {
- if (pimpl_->IsRunning())
- pimpl_->iso_impl_->disconnection_complete(handle, reason);
-}
-
-void IsoManager::HandleNumComplDataPkts(uint8_t* p, uint8_t evt_len) {
- if (pimpl_->IsRunning())
- pimpl_->iso_impl_->handle_num_completed_pkts(p, evt_len);
-}
-
-void IsoManager::HandleHciEvent(uint8_t sub_code, uint8_t* params,
- uint16_t length) {
- if (pimpl_->IsRunning())
- pimpl_->iso_impl_->on_iso_event(sub_code, params, length);
-}
-
-void IsoManager::Start() {
- if (!pimpl_->IsRunning())
- pimpl_->Start();
-}
-
-void IsoManager::Stop() {
- if (pimpl_->IsRunning())
- pimpl_->Stop();
-}
-
-IsoManager::~IsoManager() = default;
-
-} // namespace hci
-} // namespace bluetooth
diff --git a/stack/btm/btm_iso_impl.h b/stack/btm/btm_iso_impl.h
deleted file mode 100644
index c0b6a1ca9..000000000
--- a/stack/btm/btm_iso_impl.h
+++ /dev/null
@@ -1,706 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <map>
-#include <memory>
-#include <set>
-
-#include "base/bind.h"
-#include "base/bind_helpers.h"
-#include "base/callback.h"
-#include "bt_types.h"
-#include "btm_iso_api.h"
-#include "btu.h"
-#include "common/time_util.h"
-#include "device/include/controller.h"
-#include "osi/include/log.h"
-
-namespace bluetooth {
-namespace hci {
-namespace iso_manager {
-static constexpr uint8_t kIsoDataInTsBtHdrOffset = 0x0C;
-static constexpr uint8_t kIsoHeaderWithTsLen = 12;
-static constexpr uint8_t kIsoHeaderWithoutTsLen = 8;
-
-static constexpr uint8_t kStateFlagsNone = 0x00;
-static constexpr uint8_t kStateFlagIsConnected = 0x01;
-static constexpr uint8_t kStateFlagHasDataPathSet = 0x02;
-static constexpr uint8_t kStateFlagIsBroadcast = 0x04;
-
-struct iso_sync_info {
- uint32_t first_sync_ts;
- uint16_t seq_nb;
-};
-
-struct iso_base {
- union {
- uint8_t cig_id;
- uint8_t big_handle;
- };
-
- struct iso_sync_info sync_info;
- uint8_t state_flags;
- uint32_t sdu_itv;
-};
-
-typedef iso_base iso_cis;
-typedef iso_base iso_bis;
-
-struct iso_impl {
- iso_impl() {
- iso_credits_ = controller_get_interface()->get_iso_buffer_count();
- iso_buffer_size_ = controller_get_interface()->get_iso_data_size();
- }
-
- ~iso_impl() {}
-
- void handle_register_cis_callbacks(CigCallbacks* callbacks) {
- LOG_ASSERT(callbacks != nullptr) << "Invalid CIG callbacks";
- cig_callbacks_ = callbacks;
- }
-
- void handle_register_big_callbacks(BigCallbacks* callbacks) {
- LOG_ASSERT(callbacks != nullptr) << "Invalid BIG callbacks";
- big_callbacks_ = callbacks;
- }
-
- void on_set_cig_params(uint8_t cig_id, uint32_t sdu_itv_mtos, uint8_t* stream,
- uint16_t len) {
- uint8_t cis_cnt;
- uint16_t conn_handle;
- cig_create_cmpl_evt evt;
-
- LOG_ASSERT(cig_callbacks_ != nullptr) << "Invalid CIG callbacks";
- LOG_ASSERT(len >= 3) << "Invalid packet length.";
-
- STREAM_TO_UINT8(evt.status, stream);
- STREAM_TO_UINT8(evt.cig_id, stream);
- STREAM_TO_UINT8(cis_cnt, stream);
-
- uint8_t evt_code = IsCigKnown(cig_id) ? kIsoEventCigOnReconfigureCmpl
- : kIsoEventCigOnCreateCmpl;
-
- if (evt.status == HCI_SUCCESS) {
- LOG_ASSERT(len >= (3) + (cis_cnt * sizeof(uint16_t)))
- << "Invalid CIS count.";
-
- /* Remove entries for the reconfigured CIG */
- if (evt_code == kIsoEventCigOnReconfigureCmpl) {
- auto cis_it = conn_hdl_to_cis_map_.cbegin();
- while (cis_it != conn_hdl_to_cis_map_.cend()) {
- if (cis_it->second->cig_id == evt.cig_id)
- cis_it = conn_hdl_to_cis_map_.erase(cis_it);
- else
- ++cis_it;
- }
- }
-
- evt.conn_handles.reserve(cis_cnt);
- for (int i = 0; i < cis_cnt; i++) {
- STREAM_TO_UINT16(conn_handle, stream);
-
- evt.conn_handles.push_back(conn_handle);
- conn_hdl_to_cis_map_[conn_handle] = std::unique_ptr<iso_cis>(
- new iso_cis({.sync_info = {.first_sync_ts = 0, .seq_nb = 0},
- .cig_id = cig_id,
- .state_flags = kStateFlagsNone,
- .sdu_itv = sdu_itv_mtos}));
- }
- }
-
- cig_callbacks_->OnCigEvent(evt_code, &evt);
- }
-
- void create_cig(uint8_t cig_id,
- struct iso_manager::cig_create_params cig_params) {
- LOG_ASSERT(!IsCigKnown(cig_id)) << "Invalid cig - already exists.";
-
- btsnd_hcic_set_cig_params(
- cig_id, cig_params.sdu_itv_mtos, cig_params.sdu_itv_stom,
- cig_params.sca, cig_params.packing, cig_params.framing,
- cig_params.max_trans_lat_stom, cig_params.max_trans_lat_mtos,
- cig_params.cis_cfgs.size(), cig_params.cis_cfgs.data(),
- base::BindOnce(&iso_impl::on_set_cig_params, base::Unretained(this),
- cig_id, cig_params.sdu_itv_mtos));
- }
-
- void reconfigure_cig(uint8_t cig_id,
- struct iso_manager::cig_create_params cig_params) {
- LOG_ASSERT(IsCigKnown(cig_id)) << "No such cig";
-
- btsnd_hcic_set_cig_params(
- cig_id, cig_params.sdu_itv_mtos, cig_params.sdu_itv_stom,
- cig_params.sca, cig_params.packing, cig_params.framing,
- cig_params.max_trans_lat_stom, cig_params.max_trans_lat_mtos,
- cig_params.cis_cfgs.size(), cig_params.cis_cfgs.data(),
- base::BindOnce(&iso_impl::on_set_cig_params, base::Unretained(this),
- cig_id, cig_params.sdu_itv_mtos));
- }
-
- void on_remove_cig(uint8_t* stream, uint16_t len) {
- cig_remove_cmpl_evt evt;
-
- LOG_ASSERT(cig_callbacks_ != nullptr) << "Invalid CIG callbacks";
- LOG_ASSERT(len == 2) << "Invalid packet length.";
-
- STREAM_TO_UINT8(evt.status, stream);
- STREAM_TO_UINT8(evt.cig_id, stream);
-
- if (evt.status == HCI_SUCCESS) {
- auto cis_it = conn_hdl_to_cis_map_.cbegin();
- while (cis_it != conn_hdl_to_cis_map_.cend()) {
- if (cis_it->second->cig_id == evt.cig_id)
- cis_it = conn_hdl_to_cis_map_.erase(cis_it);
- else
- ++cis_it;
- }
- }
-
- cig_callbacks_->OnCigEvent(kIsoEventCigOnRemoveCmpl, &evt);
- }
-
- void remove_cig(uint8_t cig_id) {
- LOG_ASSERT(IsCigKnown(cig_id)) << "No such cig";
-
- btsnd_hcic_remove_cig(cig_id, base::BindOnce(&iso_impl::on_remove_cig,
- base::Unretained(this)));
- }
-
- void on_status_establish_cis(
- struct iso_manager::cis_establish_params conn_params, uint8_t* stream,
- uint16_t len) {
- uint8_t status;
-
- LOG_ASSERT(len == 2) << "Invalid packet length: " << len;
-
- STREAM_TO_UINT16(status, stream);
- if (status == HCI_SUCCESS) {
- /* Wait for connection established event */
- return;
- }
-
- for (auto cis : conn_params.conn_pairs) {
- cis_establish_cmpl_evt evt;
-
- evt.status = status;
- evt.cis_conn_hdl = cis.cis_conn_handle;
- evt.cig_id = 0xFF;
- cig_callbacks_->OnCisEvent(kIsoEventCisEstablishCmpl, &evt);
- }
- }
-
- void establish_cis(struct iso_manager::cis_establish_params conn_params) {
- for (auto& el : conn_params.conn_pairs) {
- auto cis = GetCisIfKnown(el.cis_conn_handle);
- LOG_ASSERT(cis) << "No such cis";
- LOG_ASSERT(!(cis->state_flags & kStateFlagIsConnected))
- << "Already connected";
- }
- btsnd_hcic_create_cis(conn_params.conn_pairs.size(),
- conn_params.conn_pairs.data(),
- base::BindOnce(&iso_impl::on_status_establish_cis,
- base::Unretained(this), conn_params));
- }
-
- void disconnect_cis(uint16_t cis_handle, uint8_t reason) {
- auto cis = GetCisIfKnown(cis_handle);
- LOG_ASSERT(cis) << "No such cis";
- LOG_ASSERT(cis->state_flags & kStateFlagIsConnected) << "Not connected";
- bluetooth::legacy::hci::GetInterface().Disconnect(
- cis_handle, static_cast<tHCI_STATUS>(reason));
- }
-
- void on_setup_iso_data_path(uint8_t* stream, uint16_t len) {
- uint8_t status;
- uint16_t conn_handle;
-
- STREAM_TO_UINT8(status, stream);
- STREAM_TO_UINT16(conn_handle, stream);
-
- iso_base* iso = GetIsoIfKnown(conn_handle);
- LOG_ASSERT(iso != nullptr) << "Invalid connection handle: " << +conn_handle;
-
- if (status == HCI_SUCCESS) iso->state_flags |= kStateFlagHasDataPathSet;
- if (iso->state_flags & kStateFlagIsBroadcast) {
- LOG_ASSERT(big_callbacks_ != nullptr) << "Invalid BIG callbacks";
- big_callbacks_->OnSetupIsoDataPath(status, conn_handle, iso->big_handle);
- } else {
- LOG_ASSERT(cig_callbacks_ != nullptr) << "Invalid CIG callbacks";
- cig_callbacks_->OnSetupIsoDataPath(status, conn_handle, iso->cig_id);
- }
- }
-
- void setup_iso_data_path(
- uint16_t conn_handle,
- struct iso_manager::iso_data_path_params path_params) {
- iso_base* iso = GetIsoIfKnown(conn_handle);
- LOG_ASSERT(iso != nullptr) << "No such iso connection: " << +conn_handle;
-
- if (!(iso->state_flags & kStateFlagIsBroadcast)) {
- LOG_ASSERT(iso->state_flags & kStateFlagIsConnected)
- << "CIS not established";
- }
-
- btsnd_hcic_setup_iso_data_path(
- conn_handle, path_params.data_path_dir, path_params.data_path_id,
- path_params.codec_id_format, path_params.codec_id_company,
- path_params.codec_id_vendor, path_params.controller_delay,
- std::move(path_params.codec_conf),
- base::BindOnce(&iso_impl::on_setup_iso_data_path,
- base::Unretained(this)));
- }
-
- void on_remove_iso_data_path(uint8_t* stream, uint16_t len) {
- uint8_t status;
- uint16_t conn_handle;
-
- STREAM_TO_UINT8(status, stream);
- STREAM_TO_UINT16(conn_handle, stream);
-
- iso_base* iso = GetIsoIfKnown(conn_handle);
- LOG_ASSERT(iso != nullptr) << "Invalid connection handle: " << +conn_handle;
-
- if (status == HCI_SUCCESS) iso->state_flags &= ~kStateFlagHasDataPathSet;
-
- if (iso->state_flags & kStateFlagIsBroadcast) {
- LOG_ASSERT(big_callbacks_ != nullptr) << "Invalid BIG callbacks";
- big_callbacks_->OnRemoveIsoDataPath(status, conn_handle, iso->big_handle);
- } else {
- LOG_ASSERT(cig_callbacks_ != nullptr) << "Invalid CIG callbacks";
- cig_callbacks_->OnRemoveIsoDataPath(status, conn_handle, iso->cig_id);
- }
- }
-
- void remove_iso_data_path(uint16_t iso_handle, uint8_t data_path_dir) {
- iso_base* iso = GetIsoIfKnown(iso_handle);
- LOG_ASSERT(iso != nullptr) << "No such iso connection";
- LOG_ASSERT((iso->state_flags & kStateFlagHasDataPathSet) ==
- kStateFlagHasDataPathSet)
- << "Data path not set";
-
- btsnd_hcic_remove_iso_data_path(
- iso_handle, data_path_dir,
- base::BindOnce(&iso_impl::on_remove_iso_data_path,
- base::Unretained(this)));
- }
-
- void on_iso_link_quality_read(uint8_t* stream, uint16_t len) {
- uint8_t status;
- uint16_t conn_handle;
- uint32_t txUnackedPackets;
- uint32_t txFlushedPackets;
- uint32_t txLastSubeventPackets;
- uint32_t retransmittedPackets;
- uint32_t crcErrorPackets;
- uint32_t rxUnreceivedPackets;
- uint32_t duplicatePackets;
-
- STREAM_TO_UINT8(status, stream);
- if (status != HCI_SUCCESS) {
- LOG(ERROR) << "Failed to Read ISO Link Quality, status: "
- << loghex(status);
- return;
- }
-
- STREAM_TO_UINT16(conn_handle, stream);
-
- iso_base* iso = GetIsoIfKnown(conn_handle);
- LOG_ASSERT(iso != nullptr) << "Invalid connection handle: " << +conn_handle;
-
- STREAM_TO_UINT32(txUnackedPackets, stream);
- STREAM_TO_UINT32(txFlushedPackets, stream);
- STREAM_TO_UINT32(txLastSubeventPackets, stream);
- STREAM_TO_UINT32(retransmittedPackets, stream);
- STREAM_TO_UINT32(crcErrorPackets, stream);
- STREAM_TO_UINT32(rxUnreceivedPackets, stream);
- STREAM_TO_UINT32(duplicatePackets, stream);
-
- LOG_ASSERT(cig_callbacks_ != nullptr) << "Invalid CIG callbacks";
- cig_callbacks_->OnIsoLinkQualityRead(
- conn_handle, iso->cig_id, txUnackedPackets, txFlushedPackets,
- txLastSubeventPackets, retransmittedPackets, crcErrorPackets,
- rxUnreceivedPackets, duplicatePackets);
- }
-
- void read_iso_link_quality(uint16_t iso_handle) {
- iso_base* iso = GetIsoIfKnown(iso_handle);
- LOG_ASSERT(iso != nullptr) << "No such iso connection";
-
- btsnd_hcic_read_iso_link_quality(
- iso_handle, base::BindOnce(&iso_impl::on_iso_link_quality_read,
- base::Unretained(this)));
- }
-
- BT_HDR* prepare_ts_hci_packet(uint16_t iso_handle, uint32_t ts,
- uint16_t seq_nb, uint16_t data_len) {
- /* Add 2 for packet seq., 2 for length, 4 for the timestamp */
- uint16_t iso_data_load_len = data_len + 8;
-
- /* Add 2 for handle, 2 for length */
- uint16_t iso_full_len = iso_data_load_len + 4;
- BT_HDR* packet = (BT_HDR*)osi_malloc(iso_full_len + sizeof(BT_HDR));
- packet->len = iso_full_len;
- packet->offset = 0;
- packet->event = MSG_STACK_TO_HC_HCI_ISO;
- packet->layer_specific = 0;
-
- uint8_t* packet_data = packet->data;
- UINT16_TO_STREAM(packet_data, iso_handle);
- UINT16_TO_STREAM(packet_data, iso_data_load_len);
-
- packet->layer_specific |= BT_ISO_HDR_CONTAINS_TS;
- UINT32_TO_STREAM(packet_data, ts);
-
- UINT16_TO_STREAM(packet_data, seq_nb);
- UINT16_TO_STREAM(packet_data, data_len);
-
- return packet;
- }
-
- void send_iso_data_hci_packet(BT_HDR* packet) {
- bte_main_hci_send(packet, MSG_STACK_TO_HC_HCI_ISO | 0x0001);
- }
-
- void send_iso_data(uint16_t iso_handle, const uint8_t* data,
- uint16_t data_len) {
- iso_base* iso = GetIsoIfKnown(iso_handle);
- LOG_ASSERT(iso != nullptr)
- << "No such iso connection handle: " << +iso_handle;
-
- if (!(iso->state_flags & kStateFlagIsBroadcast)) {
- LOG_ASSERT(iso->state_flags & kStateFlagIsConnected)
- << "CIS not established";
- }
- LOG_ASSERT(iso->state_flags & kStateFlagHasDataPathSet)
- << "Data path not set for handle: " << +iso_handle;
-
- /* Calculate sequence number for the ISO data packet.
- * It should be incremented by 1 every SDU Interval.
- */
- uint32_t ts = bluetooth::common::time_get_os_boottime_us();
- iso->sync_info.seq_nb = (ts - iso->sync_info.first_sync_ts) / iso->sdu_itv;
-
- if (iso_credits_ == 0 || data_len > iso_buffer_size_) {
- LOG(WARNING) << __func__ << ", dropping ISO packet, len: "
- << static_cast<int>(data_len)
- << ", iso credits: " << static_cast<int>(iso_credits_);
- return;
- }
-
- iso_credits_--;
-
- BT_HDR* packet =
- prepare_ts_hci_packet(iso_handle, ts, iso->sync_info.seq_nb, data_len);
- memcpy(packet->data + kIsoDataInTsBtHdrOffset, data, data_len);
- send_iso_data_hci_packet(packet);
- }
-
- void process_cis_est_pkt(uint8_t len, uint8_t* data) {
- cis_establish_cmpl_evt evt;
-
- LOG_ASSERT(len == 28) << "Invalid packet length";
- LOG_ASSERT(cig_callbacks_ != nullptr) << "Invalid CIG callbacks";
-
- STREAM_TO_UINT8(evt.status, data);
- STREAM_TO_UINT16(evt.cis_conn_hdl, data);
-
- auto cis = GetCisIfKnown(evt.cis_conn_hdl);
- LOG_ASSERT(cis != nullptr) << "No such cis";
-
- cis->sync_info.first_sync_ts = bluetooth::common::time_get_os_boottime_us();
-
- STREAM_TO_UINT24(evt.cig_sync_delay, data);
- STREAM_TO_UINT24(evt.cis_sync_delay, data);
- STREAM_TO_UINT24(evt.trans_lat_mtos, data);
- STREAM_TO_UINT24(evt.trans_lat_stom, data);
- STREAM_TO_UINT8(evt.phy_mtos, data);
- STREAM_TO_UINT8(evt.phy_stom, data);
- STREAM_TO_UINT8(evt.nse, data);
- STREAM_TO_UINT8(evt.bn_mtos, data);
- STREAM_TO_UINT8(evt.bn_stom, data);
- STREAM_TO_UINT8(evt.ft_mtos, data);
- STREAM_TO_UINT8(evt.ft_stom, data);
- STREAM_TO_UINT16(evt.max_pdu_mtos, data);
- STREAM_TO_UINT16(evt.max_pdu_stom, data);
- STREAM_TO_UINT16(evt.iso_itv, data);
-
- if (evt.status == HCI_SUCCESS) cis->state_flags |= kStateFlagIsConnected;
-
- evt.cig_id = cis->cig_id;
- cig_callbacks_->OnCisEvent(kIsoEventCisEstablishCmpl, &evt);
- }
-
- void disconnection_complete(uint16_t handle, uint8_t reason) {
- /* Check if this is an ISO handle */
- auto cis = GetCisIfKnown(handle);
- if (cis == nullptr) return;
-
- LOG_ASSERT(cig_callbacks_ != nullptr) << "Invalid CIG callbacks";
-
- LOG_INFO("%s flags: %d", __func__, +cis->state_flags);
- if (cis->state_flags & kStateFlagIsConnected) {
- cis_disconnected_evt evt = {
- .reason = reason,
- .cis_conn_hdl = handle,
- .cig_id = cis->cig_id,
- };
-
- cig_callbacks_->OnCisEvent(kIsoEventCisDisconnected, &evt);
- cis->state_flags &= ~kStateFlagIsConnected;
- /* Data path is considered still valid, but can be reconfigured only once
- * CIS is reestablished.
- */
- }
- }
-
- void handle_num_completed_pkts(uint8_t* p, uint8_t evt_len) {
- uint8_t num_handles;
-
- STREAM_TO_UINT8(num_handles, p);
-
- LOG_ASSERT(evt_len == num_handles * 4 + 1);
-
- for (int i = 0; i < num_handles; i++) {
- uint16_t handle, num_sent;
-
- STREAM_TO_UINT16(handle, p);
- STREAM_TO_UINT16(num_sent, p);
-
- if ((conn_hdl_to_cis_map_.find(handle) == conn_hdl_to_cis_map_.end()) &&
- (conn_hdl_to_bis_map_.find(handle) == conn_hdl_to_bis_map_.end()))
- continue;
-
- iso_credits_ += num_sent;
- }
- }
-
- void process_create_big_cmpl_pkt(uint8_t len, uint8_t* data) {
- struct big_create_cmpl_evt evt;
-
- LOG_ASSERT(len >= 18) << "Invalid packet length";
- LOG_ASSERT(big_callbacks_ != nullptr) << "Invalid BIG callbacks";
-
- STREAM_TO_UINT8(evt.status, data);
- STREAM_TO_UINT8(evt.big_id, data);
- STREAM_TO_UINT24(evt.big_sync_delay, data);
- STREAM_TO_UINT24(evt.transport_latency_big, data);
- STREAM_TO_UINT8(evt.phy, data);
- STREAM_TO_UINT8(evt.nse, data);
- STREAM_TO_UINT8(evt.bn, data);
- STREAM_TO_UINT8(evt.pto, data);
- STREAM_TO_UINT8(evt.irc, data);
- STREAM_TO_UINT16(evt.max_pdu, data);
- STREAM_TO_UINT16(evt.iso_interval, data);
-
- uint8_t num_bis;
- STREAM_TO_UINT8(num_bis, data);
-
- LOG_ASSERT(num_bis != 0) << "Invalid bis count";
- LOG_ASSERT(len == (18 + num_bis * sizeof(uint16_t)))
- << "Invalid packet length";
-
- uint32_t ts = bluetooth::common::time_get_os_boottime_us();
- for (auto i = 0; i < num_bis; ++i) {
- uint16_t conn_handle;
- STREAM_TO_UINT16(conn_handle, data);
- evt.conn_handles.push_back(conn_handle);
- LOG_INFO(" received BIS conn_hdl %d", +conn_handle);
-
- if (evt.status == HCI_SUCCESS) {
- conn_hdl_to_bis_map_[conn_handle] = std::unique_ptr<iso_bis>(
- new iso_bis({.sync_info = {.first_sync_ts = ts, .seq_nb = 0},
- .big_handle = evt.big_id,
- .state_flags = kStateFlagIsBroadcast,
- .sdu_itv = last_big_create_req_sdu_itv_}));
- }
- }
-
- big_callbacks_->OnBigEvent(kIsoEventBigOnCreateCmpl, &evt);
- }
-
- void process_terminate_big_cmpl_pkt(uint8_t len, uint8_t* data) {
- struct big_terminate_cmpl_evt evt;
-
- LOG_ASSERT(len == 2) << "Invalid packet length";
- LOG_ASSERT(big_callbacks_ != nullptr) << "Invalid BIG callbacks";
-
- STREAM_TO_UINT8(evt.big_id, data);
- STREAM_TO_UINT8(evt.reason, data);
-
- bool is_known_handle = false;
- auto bis_it = conn_hdl_to_bis_map_.cbegin();
- while (bis_it != conn_hdl_to_bis_map_.cend()) {
- if (bis_it->second->big_handle == evt.big_id) {
- bis_it = conn_hdl_to_bis_map_.erase(bis_it);
- is_known_handle = true;
- } else {
- ++bis_it;
- }
- }
-
- LOG_ASSERT(is_known_handle) << "No such big";
- big_callbacks_->OnBigEvent(kIsoEventBigOnTerminateCmpl, &evt);
- }
-
- void create_big(uint8_t big_id, struct big_create_params big_params) {
- LOG_ASSERT(!IsBigKnown(big_id)) << "Invalid big - already exists";
-
- last_big_create_req_sdu_itv_ = big_params.sdu_itv;
- btsnd_hcic_create_big(
- big_id, big_params.adv_handle, big_params.num_bis, big_params.sdu_itv,
- big_params.max_sdu_size, big_params.max_transport_latency,
- big_params.rtn, big_params.phy, big_params.packing, big_params.framing,
- big_params.enc, big_params.enc_code);
- }
-
- void terminate_big(uint8_t big_id, uint8_t reason) {
- LOG_ASSERT(IsBigKnown(big_id)) << "No such big";
-
- btsnd_hcic_term_big(big_id, reason);
- }
-
- void on_iso_event(uint8_t code, uint8_t* packet, uint16_t packet_len) {
- switch (code) {
- case HCI_BLE_CIS_EST_EVT:
- process_cis_est_pkt(packet_len, packet);
- break;
- case HCI_BLE_CREATE_BIG_CPL_EVT:
- process_create_big_cmpl_pkt(packet_len, packet);
- break;
- case HCI_BLE_TERM_BIG_CPL_EVT:
- process_terminate_big_cmpl_pkt(packet_len, packet);
- break;
- case HCI_BLE_CIS_REQ_EVT:
- /* Not supported */
- break;
- case HCI_BLE_BIG_SYNC_EST_EVT:
- /* Not supported */
- break;
- case HCI_BLE_BIG_SYNC_LOST_EVT:
- /* Not supported */
- break;
- default:
- LOG_ERROR("Unhandled event code %d", +code);
- }
- }
-
- void handle_iso_data(BT_HDR* p_msg) {
- const uint8_t* stream = p_msg->data;
- cis_data_evt evt;
- uint16_t handle, seq_nb;
-
- if (p_msg->len <= ((p_msg->layer_specific & BT_ISO_HDR_CONTAINS_TS)
- ? kIsoHeaderWithTsLen
- : kIsoHeaderWithoutTsLen))
- return;
-
- LOG_ASSERT(cig_callbacks_ != nullptr) << "Invalid CIG callbacks";
-
- STREAM_TO_UINT16(handle, stream);
- evt.cis_conn_hdl = HCID_GET_HANDLE(handle);
-
- iso_base* iso = GetCisIfKnown(evt.cis_conn_hdl);
- if (iso == nullptr) {
- LOG(ERROR) << __func__ << ", received data for the non-registered CIS!";
- return;
- }
-
- STREAM_SKIP_UINT16(stream);
- if (p_msg->layer_specific & BT_ISO_HDR_CONTAINS_TS)
- STREAM_TO_UINT32(evt.ts, stream);
-
- STREAM_TO_UINT16(seq_nb, stream);
-
- uint32_t ts = bluetooth::common::time_get_os_boottime_us();
- uint32_t new_calc_seq_nb =
- (ts - iso->sync_info.first_sync_ts) / iso->sdu_itv;
- if (new_calc_seq_nb <= iso->sync_info.seq_nb)
- new_calc_seq_nb = iso->sync_info.seq_nb + 1;
-
- if (iso->sync_info.seq_nb == 0) {
- evt.evt_lost = 0;
- } else {
- evt.evt_lost = new_calc_seq_nb - iso->sync_info.seq_nb - 1;
- if (evt.evt_lost > 0) {
- LOG(WARNING) << evt.evt_lost << " packets possibly lost.";
- }
-
- if (new_calc_seq_nb != seq_nb) {
- LOG(WARNING) << "Sequence number mismatch. "
- "Adjusting own time reference point.";
- iso->sync_info.first_sync_ts = ts - (seq_nb * iso->sdu_itv);
- new_calc_seq_nb = seq_nb;
- }
- }
- iso->sync_info.seq_nb = new_calc_seq_nb;
-
- evt.p_msg = p_msg;
- evt.cig_id = iso->cig_id;
- cig_callbacks_->OnCisEvent(kIsoEventCisDataAvailable, &evt);
- }
-
- iso_cis* GetCisIfKnown(uint16_t cis_conn_handle) {
- auto cis_it = conn_hdl_to_cis_map_.find(cis_conn_handle);
- return (cis_it != conn_hdl_to_cis_map_.end()) ? cis_it->second.get()
- : nullptr;
- }
-
- iso_bis* GetBisIfKnown(uint16_t bis_conn_handle) {
- auto bis_it = conn_hdl_to_bis_map_.find(bis_conn_handle);
- return (bis_it != conn_hdl_to_bis_map_.end()) ? bis_it->second.get()
- : nullptr;
- }
-
- iso_base* GetIsoIfKnown(uint16_t iso_handle) {
- struct iso_base* iso = GetCisIfKnown(iso_handle);
- return (iso != nullptr) ? iso : GetBisIfKnown(iso_handle);
- }
-
- bool IsCigKnown(uint8_t cig_id) const {
- auto const cis_it =
- std::find_if(conn_hdl_to_cis_map_.cbegin(), conn_hdl_to_cis_map_.cend(),
- [&cig_id](auto& kv_pair) {
- return (kv_pair.second->cig_id == cig_id);
- });
- return (cis_it != conn_hdl_to_cis_map_.cend());
- }
-
- bool IsBigKnown(uint8_t big_id) const {
- auto bis_it =
- std::find_if(conn_hdl_to_bis_map_.cbegin(), conn_hdl_to_bis_map_.cend(),
- [&big_id](auto& kv_pair) {
- return (kv_pair.second->big_handle == big_id);
- });
- return (bis_it != conn_hdl_to_bis_map_.cend());
- }
-
- std::map<uint16_t, std::unique_ptr<iso_cis>> conn_hdl_to_cis_map_;
- std::map<uint16_t, std::unique_ptr<iso_bis>> conn_hdl_to_bis_map_;
-
- uint16_t iso_credits_;
- uint16_t iso_buffer_size_;
- uint32_t last_big_create_req_sdu_itv_;
-
- CigCallbacks* cig_callbacks_ = nullptr;
- BigCallbacks* big_callbacks_ = nullptr;
-};
-
-} // namespace iso_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/stack/btm/btm_main.cc b/stack/btm/btm_main.cc
index 0862df9ca..f58f44421 100644
--- a/stack/btm/btm_main.cc
+++ b/stack/btm/btm_main.cc
@@ -22,13 +22,10 @@
*
******************************************************************************/
-#include <memory>
-#include <string>
+#include <string.h>
#include "bt_target.h"
#include "bt_types.h"
-#include "main/shim/dumpsys.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/btm_client_interface.h"
+#include "btm_int.h"
#include "stack_config.h"
/* Global BTM control block structure
@@ -48,42 +45,58 @@ tBTM_CB btm_cb;
*
******************************************************************************/
void btm_init(void) {
- btm_cb.Init(stack_config_get_interface()->get_pts_secure_only_mode()
- ? BTM_SEC_MODE_SC
- : BTM_SEC_MODE_SP);
+ /* All fields are cleared; nonzero fields are reinitialized in appropriate
+ * function */
+ memset(&btm_cb, 0, sizeof(tBTM_CB));
+ btm_cb.page_queue = fixed_queue_new(SIZE_MAX);
+ btm_cb.sec_pending_q = fixed_queue_new(SIZE_MAX);
+ btm_cb.sec_collision_timer = alarm_new("btm.sec_collision_timer");
+ btm_cb.pairing_timer = alarm_new("btm.pairing_timer");
+
+#if defined(BTM_INITIAL_TRACE_LEVEL)
+ btm_cb.trace_level = BTM_INITIAL_TRACE_LEVEL;
+#else
+ btm_cb.trace_level = BT_TRACE_LEVEL_NONE; /* No traces */
+#endif
+ /* Initialize BTM component structures */
+ btm_inq_db_init(); /* Inquiry Database and Structures */
+ btm_acl_init(); /* ACL Database and Structures */
+ /* Security Manager Database and Structures */
+ if (stack_config_get_interface()->get_pts_secure_only_mode())
+ btm_sec_init(BTM_SEC_MODE_SC);
+ else
+ btm_sec_init(BTM_SEC_MODE_SP);
+ btm_sco_init(); /* SCO Database and Structures (If included) */
+
+ btm_cb.sec_dev_rec = list_new(osi_free);
+
+ btm_dev_init(); /* Device Manager Structures & HCI_Reset */
}
/** This function is called to free dynamic memory and system resource allocated by btm_init */
void btm_free(void) {
- btm_cb.Free();
-}
+ fixed_queue_free(btm_cb.page_queue, NULL);
+ btm_cb.page_queue = NULL;
-constexpr size_t kMaxLogHistoryTagLength = 6;
-constexpr size_t kMaxLogHistoryMsgLength = 25;
+ fixed_queue_free(btm_cb.sec_pending_q, NULL);
+ btm_cb.sec_pending_q = NULL;
-static void btm_log_history(const std::string& tag, const char* addr,
- const std::string& msg, const std::string& extra) {
- btm_cb.history_->Push(
- "%-6s %-25s: %s %s", tag.substr(0, kMaxLogHistoryTagLength).c_str(),
- msg.substr(0, kMaxLogHistoryMsgLength).c_str(), addr, extra.c_str());
-}
+ list_node_t* end = list_end(btm_cb.sec_dev_rec);
+ list_node_t* node = list_begin(btm_cb.sec_dev_rec);
+ while (node != end) {
+ tBTM_SEC_DEV_REC* p_dev_rec = static_cast<tBTM_SEC_DEV_REC*>(list_node(node));
-void BTM_LogHistory(const std::string& tag, const RawAddress& bd_addr,
- const std::string& msg, const std::string& extra) {
- btm_log_history(tag, PRIVATE_ADDRESS(bd_addr), msg, extra);
-}
+ // we do list_remove in, must grab next before removing
+ node = list_next(node);
+ wipe_secrets_and_remove(p_dev_rec);
+ }
-void BTM_LogHistory(const std::string& tag, const RawAddress& bd_addr,
- const std::string& msg) {
- BTM_LogHistory(tag, bd_addr, msg, std::string());
-}
+ list_free(btm_cb.sec_dev_rec);
+ btm_cb.sec_dev_rec = NULL;
-void BTM_LogHistory(const std::string& tag, const tBLE_BD_ADDR& ble_bd_addr,
- const std::string& msg, const std::string& extra) {
- btm_log_history(tag, PRIVATE_ADDRESS(ble_bd_addr), msg, extra);
-}
+ alarm_free(btm_cb.sec_collision_timer);
+ btm_cb.sec_collision_timer = NULL;
-void BTM_LogHistory(const std::string& tag, const tBLE_BD_ADDR& ble_bd_addr,
- const std::string& msg) {
- BTM_LogHistory(tag, ble_bd_addr, msg, std::string());
+ alarm_free(btm_cb.pairing_timer);
+ btm_cb.pairing_timer = NULL;
}
diff --git a/stack/btm/btm_pm.cc b/stack/btm/btm_pm.cc
new file mode 100644
index 000000000..793c85436
--- /dev/null
+++ b/stack/btm/btm_pm.cc
@@ -0,0 +1,962 @@
+/******************************************************************************
+ *
+ * Copyright 2000-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+/*****************************************************************************
+ *
+ * This file contains functions that manages ACL link modes.
+ * This includes operations such as active, hold,
+ * park and sniff modes.
+ *
+ * This module contains both internal and external (API)
+ * functions. External (API) functions are distinguishable
+ * by their names beginning with uppercase BTM.
+ *
+ *****************************************************************************/
+
+#define LOG_TAG "bt_btm_pm"
+
+#include <stddef.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "bt_common.h"
+#include "bt_types.h"
+#include "bt_utils.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btm_int_types.h"
+#include "btu.h"
+#include "hcidefs.h"
+#include "hcimsgs.h"
+#include "l2c_int.h"
+#include "osi/include/log.h"
+#include "osi/include/osi.h"
+
+/*****************************************************************************/
+/* to handle different modes */
+/*****************************************************************************/
+#define BTM_PM_STORED_MASK 0x80 /* set this mask if the command is stored */
+#define BTM_PM_NUM_SET_MODES 3 /* only hold, sniff & park */
+
+/* Usage: (ptr_features[ offset ] & mask )?true:false */
+/* offset to supported feature */
+const uint8_t btm_pm_mode_off[BTM_PM_NUM_SET_MODES] = {0, 0, 1};
+/* mask to supported feature */
+const uint8_t btm_pm_mode_msk[BTM_PM_NUM_SET_MODES] = {0x40, 0x80, 0x01};
+
+#define BTM_PM_GET_MD1 1
+#define BTM_PM_GET_MD2 2
+#define BTM_PM_GET_COMP 3
+
+const uint8_t
+ btm_pm_md_comp_matrix[BTM_PM_NUM_SET_MODES * BTM_PM_NUM_SET_MODES] = {
+ BTM_PM_GET_COMP, BTM_PM_GET_MD2, BTM_PM_GET_MD2,
+
+ BTM_PM_GET_MD1, BTM_PM_GET_COMP, BTM_PM_GET_MD1,
+
+ BTM_PM_GET_MD1, BTM_PM_GET_MD2, BTM_PM_GET_COMP};
+
+/* function prototype */
+static int btm_pm_find_acl_ind(const RawAddress& remote_bda);
+static tBTM_STATUS btm_pm_snd_md_req(uint8_t pm_id, int link_ind,
+ const tBTM_PM_PWR_MD* p_mode);
+static const char* mode_to_string(const tBTM_PM_MODE mode);
+
+#if (BTM_PM_DEBUG == TRUE)
+const char* btm_pm_state_str[] = {"pm_active_state", "pm_hold_state",
+ "pm_sniff_state", "pm_park_state",
+ "pm_pend_state"};
+
+const char* btm_pm_event_str[] = {"pm_set_mode_event", "pm_hci_sts_event",
+ "pm_mod_chg_event", "pm_update_event"};
+
+const char* btm_pm_action_str[] = {"pm_set_mode_action", "pm_update_db_action",
+ "pm_mod_chg_action", "pm_hci_sts_action",
+ "pm_update_action"};
+#endif // BTM_PM_DEBUG
+
+/*****************************************************************************/
+/* P U B L I C F U N C T I O N S */
+/*****************************************************************************/
+/*******************************************************************************
+ *
+ * Function BTM_PmRegister
+ *
+ * Description register or deregister with power manager
+ *
+ * Returns BTM_SUCCESS if successful,
+ * BTM_NO_RESOURCES if no room to hold registration
+ * BTM_ILLEGAL_VALUE
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_PmRegister(uint8_t mask, uint8_t* p_pm_id,
+ tBTM_PM_STATUS_CBACK* p_cb) {
+ int xx;
+
+ /* de-register */
+ if (mask & BTM_PM_DEREG) {
+ if (*p_pm_id >= BTM_MAX_PM_RECORDS) return BTM_ILLEGAL_VALUE;
+ btm_cb.pm_reg_db[*p_pm_id].mask = BTM_PM_REC_NOT_USED;
+ return BTM_SUCCESS;
+ }
+
+ for (xx = 0; xx < BTM_MAX_PM_RECORDS; xx++) {
+ /* find an unused entry */
+ if (btm_cb.pm_reg_db[xx].mask == BTM_PM_REC_NOT_USED) {
+ /* if register for notification, should provide callback routine */
+ if (mask & BTM_PM_REG_NOTIF) {
+ if (p_cb == NULL) return BTM_ILLEGAL_VALUE;
+ btm_cb.pm_reg_db[xx].cback = p_cb;
+ }
+ btm_cb.pm_reg_db[xx].mask = mask;
+ *p_pm_id = xx;
+ return BTM_SUCCESS;
+ }
+ }
+
+ return BTM_NO_RESOURCES;
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_SetPowerMode
+ *
+ * Description store the mode in control block or
+ * alter ACL connection behavior.
+ *
+ * Returns BTM_SUCCESS if successful,
+ * BTM_UNKNOWN_ADDR if bd addr is not active or bad
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SetPowerMode(uint8_t pm_id, const RawAddress& remote_bda,
+ const tBTM_PM_PWR_MD* p_mode) {
+ uint8_t* p_features;
+ int ind, acl_ind;
+ tBTM_PM_MCB* p_cb = nullptr; /* per ACL link */
+ tBTM_PM_MODE mode;
+ int temp_pm_id;
+
+ if (pm_id >= BTM_MAX_PM_RECORDS) {
+ pm_id = BTM_PM_SET_ONLY_ID;
+ }
+
+ if (!p_mode) {
+ LOG(ERROR) << __func__ << ": pm_id " << unsigned(pm_id)
+ << " p_mode is null for " << remote_bda;
+ return BTM_ILLEGAL_VALUE;
+ }
+
+ VLOG(2) << __func__ << " pm_id " << pm_id << " BDA: " << remote_bda
+ << " mode:" << std::to_string(p_mode->mode);
+
+ /* take out the force bit */
+ mode = p_mode->mode & ~BTM_PM_MD_FORCE;
+
+ acl_ind = btm_pm_find_acl_ind(remote_bda);
+ if (acl_ind == MAX_L2CAP_LINKS) return (BTM_UNKNOWN_ADDR);
+
+ p_cb = &(btm_cb.pm_mode_db[acl_ind]);
+
+ if (mode != BTM_PM_MD_ACTIVE) {
+ /* check if the requested mode is supported */
+ ind = mode - BTM_PM_MD_HOLD; /* make it base 0 */
+ p_features = BTM_ReadLocalFeatures();
+ if (!(p_features[btm_pm_mode_off[ind]] & btm_pm_mode_msk[ind])) {
+ LOG(ERROR) << __func__ << ": pm_id " << unsigned(pm_id) << " mode "
+ << unsigned(mode) << " is not supported for " << remote_bda;
+ return BTM_MODE_UNSUPPORTED;
+ }
+ }
+
+ if (mode == p_cb->state) {
+ /* already in the requested mode and the current interval has less latency
+ * than the max */
+ if ((mode == BTM_PM_MD_ACTIVE) ||
+ ((p_mode->mode & BTM_PM_MD_FORCE) && (p_mode->max >= p_cb->interval) &&
+ (p_mode->min <= p_cb->interval)) ||
+ ((p_mode->mode & BTM_PM_MD_FORCE) == 0 &&
+ (p_mode->max >= p_cb->interval))) {
+ VLOG(1) << __func__ << " already in requested mode "
+ << std::to_string(p_mode->mode) << ", interval " << p_cb->interval
+ << " max " << p_mode->max << " min " << p_mode->min;
+ return BTM_SUCCESS;
+ }
+ }
+
+ temp_pm_id = pm_id;
+ if (pm_id == BTM_PM_SET_ONLY_ID) {
+ temp_pm_id = BTM_MAX_PM_RECORDS;
+ }
+
+ /* update mode database */
+ if (((pm_id != BTM_PM_SET_ONLY_ID) &&
+ (btm_cb.pm_reg_db[pm_id].mask & BTM_PM_REG_SET)) ||
+ ((pm_id == BTM_PM_SET_ONLY_ID) &&
+ (btm_cb.pm_pend_link != MAX_L2CAP_LINKS))) {
+#if (BTM_PM_DEBUG == TRUE)
+ BTM_TRACE_DEBUG("BTM_SetPowerMode: Saving cmd acl_ind %d temp_pm_id %d",
+ acl_ind, temp_pm_id);
+#endif // BTM_PM_DEBUG
+ /* Make sure mask is set to BTM_PM_REG_SET */
+ btm_cb.pm_reg_db[temp_pm_id].mask |= BTM_PM_REG_SET;
+ *(&p_cb->req_mode[temp_pm_id]) = *p_mode;
+ p_cb->chg_ind = true;
+ }
+
+#if (BTM_PM_DEBUG == TRUE)
+ BTM_TRACE_DEBUG("btm_pm state:0x%x, pm_pend_link: %d", p_cb->state,
+ btm_cb.pm_pend_link);
+#endif // BTM_PM_DEBUG
+ /* if mode == hold or pending, return */
+ if ((p_cb->state == BTM_PM_STS_HOLD) || (p_cb->state == BTM_PM_STS_PENDING) ||
+ (btm_cb.pm_pend_link != MAX_L2CAP_LINKS)) {
+ /* command pending */
+ if (acl_ind != btm_cb.pm_pend_link) {
+ /* set the stored mask */
+ p_cb->state |= BTM_PM_STORED_MASK;
+ BTM_TRACE_DEBUG("%s: btm_pm state stored:%d", __func__, acl_ind);
+ }
+ return BTM_CMD_STORED;
+ }
+
+ return btm_pm_snd_md_req(pm_id, acl_ind, p_mode);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadPowerMode
+ *
+ * Description This returns the current mode for a specific
+ * ACL connection.
+ *
+ * Input Param remote_bda - device address of desired ACL connection
+ *
+ * Output Param p_mode - address where the current mode is copied into.
+ * BTM_ACL_MODE_NORMAL
+ * BTM_ACL_MODE_HOLD
+ * BTM_ACL_MODE_SNIFF
+ * BTM_ACL_MODE_PARK
+ * (valid only if return code is BTM_SUCCESS)
+ *
+ * Returns BTM_SUCCESS if successful,
+ * BTM_UNKNOWN_ADDR if bd addr is not active or bad
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_ReadPowerMode(const RawAddress& remote_bda,
+ tBTM_PM_MODE* p_mode) {
+ int acl_ind;
+
+ acl_ind = btm_pm_find_acl_ind(remote_bda);
+ if (acl_ind == MAX_L2CAP_LINKS) return (BTM_UNKNOWN_ADDR);
+
+ *p_mode = btm_cb.pm_mode_db[acl_ind].state;
+ return BTM_SUCCESS;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_power_mode_state
+ *
+ * Description This returns the current pm state for a specific
+ * ACL connection.
+ *
+ * Input Param remote_bda - device address of desired ACL connection
+ *
+ * Output Param pmState - address where the current pm state is copied.
+ * BTM_PM_ST_ACTIVE
+ * BTM_PM_ST_HOLD
+ * BTM_PM_ST_SNIFF
+ * BTM_PM_ST_PARK
+ * BTM_PM_ST_PENDING
+ * (valid only if return code is BTM_SUCCESS)
+ *
+ * Returns BTM_SUCCESS if successful,
+ * BTM_UNKNOWN_ADDR if bd addr is not active or bad
+ *
+ ******************************************************************************/
+tBTM_STATUS btm_read_power_mode_state(const RawAddress& remote_bda,
+ tBTM_PM_STATE* pmState) {
+ int acl_ind = btm_pm_find_acl_ind(remote_bda);
+
+ if (acl_ind == MAX_L2CAP_LINKS) return (BTM_UNKNOWN_ADDR);
+
+ *pmState = btm_cb.pm_mode_db[acl_ind].state;
+ return BTM_SUCCESS;
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_SetSsrParams
+ *
+ * Description This sends the given SSR parameters for the given ACL
+ * connection if it is in ACTIVE mode.
+ *
+ * Input Param remote_bda - device address of desired ACL connection
+ * max_lat - maximum latency (in 0.625ms)(0-0xFFFE)
+ * min_rmt_to - minimum remote timeout
+ * min_loc_to - minimum local timeout
+ *
+ *
+ * Returns BTM_SUCCESS if the HCI command is issued successful,
+ * BTM_UNKNOWN_ADDR if bd addr is not active or bad
+ * BTM_CMD_STORED if the command is stored
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_SetSsrParams(const RawAddress& remote_bda, uint16_t max_lat,
+ uint16_t min_rmt_to, uint16_t min_loc_to) {
+#if (BTM_SSR_INCLUDED == TRUE)
+ int acl_ind;
+ tBTM_PM_MCB* p_cb;
+
+ acl_ind = btm_pm_find_acl_ind(remote_bda);
+ if (acl_ind == MAX_L2CAP_LINKS) return (BTM_UNKNOWN_ADDR);
+
+ if (BTM_PM_STS_ACTIVE == btm_cb.pm_mode_db[acl_ind].state ||
+ BTM_PM_STS_SNIFF == btm_cb.pm_mode_db[acl_ind].state) {
+ btsnd_hcic_sniff_sub_rate(btm_cb.acl_db[acl_ind].hci_handle, max_lat,
+ min_rmt_to, min_loc_to);
+ return BTM_SUCCESS;
+ }
+ p_cb = &btm_cb.pm_mode_db[acl_ind];
+ p_cb->max_lat = max_lat;
+ p_cb->min_rmt_to = min_rmt_to;
+ p_cb->min_loc_to = min_loc_to;
+ return BTM_CMD_STORED;
+#else
+ return BTM_ILLEGAL_ACTION;
+#endif // BTM_SSR_INCLUDED
+}
+
+/*******************************************************************************
+ *
+ * Function btm_pm_reset
+ *
+ * Description as a part of the BTM reset process.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_pm_reset(void) {
+ int xx;
+ tBTM_PM_STATUS_CBACK* cb = NULL;
+
+ /* clear the pending request for application */
+ if ((btm_cb.pm_pend_id != BTM_PM_SET_ONLY_ID) &&
+ (btm_cb.pm_reg_db[btm_cb.pm_pend_id].mask & BTM_PM_REG_NOTIF)) {
+ cb = btm_cb.pm_reg_db[btm_cb.pm_pend_id].cback;
+ }
+
+ /* clear the register record */
+ for (xx = 0; xx < BTM_MAX_PM_RECORDS; xx++) {
+ btm_cb.pm_reg_db[xx].mask = BTM_PM_REC_NOT_USED;
+ }
+
+ if (cb != NULL && btm_cb.pm_pend_link < MAX_L2CAP_LINKS)
+ (*cb)(btm_cb.acl_db[btm_cb.pm_pend_link].remote_addr, BTM_PM_STS_ERROR,
+ BTM_DEV_RESET, 0);
+
+ /* no command pending */
+ btm_cb.pm_pend_link = MAX_L2CAP_LINKS;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_pm_sm_alloc
+ *
+ * Description This function initializes the control block of an ACL link.
+ * It is called when an ACL connection is created.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_pm_sm_alloc(uint8_t ind) {
+ tBTM_PM_MCB* p_db = &btm_cb.pm_mode_db[ind]; /* per ACL link */
+ memset(p_db, 0, sizeof(tBTM_PM_MCB));
+ p_db->state = BTM_PM_ST_ACTIVE;
+#if (BTM_PM_DEBUG == TRUE)
+ BTM_TRACE_DEBUG("btm_pm_sm_alloc ind:%d st:%d", ind, p_db->state);
+#endif // BTM_PM_DEBUG
+}
+
+/*******************************************************************************
+ *
+ * Function btm_pm_find_acl_ind
+ *
+ * Description This function initializes the control block of an ACL link.
+ * It is called when an ACL connection is created.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static int btm_pm_find_acl_ind(const RawAddress& remote_bda) {
+ tACL_CONN* p = &btm_cb.acl_db[0];
+ uint8_t xx;
+
+ for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p++) {
+ if (p->in_use && p->remote_addr == remote_bda &&
+ p->transport == BT_TRANSPORT_BR_EDR) {
+#if (BTM_PM_DEBUG == TRUE)
+ BTM_TRACE_DEBUG("btm_pm_find_acl_ind ind:%d, st:%d", xx,
+ btm_cb.pm_mode_db[xx].state);
+#endif // BTM_PM_DEBUG
+ break;
+ }
+ }
+ return xx;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_pm_compare_modes
+ * Description get the "more active" mode of the 2
+ * Returns void
+ *
+ ******************************************************************************/
+static tBTM_PM_PWR_MD* btm_pm_compare_modes(const tBTM_PM_PWR_MD* p_md1,
+ const tBTM_PM_PWR_MD* p_md2,
+ tBTM_PM_PWR_MD* p_res) {
+ uint8_t res;
+
+ if (p_md1 == NULL) {
+ *p_res = *p_md2;
+ p_res->mode &= ~BTM_PM_MD_FORCE;
+
+ return p_res;
+ }
+
+ if (p_md2->mode == BTM_PM_MD_ACTIVE || p_md1->mode == BTM_PM_MD_ACTIVE) {
+ return NULL;
+ }
+
+ /* check if force bit is involved */
+ if (p_md1->mode & BTM_PM_MD_FORCE) {
+ *p_res = *p_md1;
+ p_res->mode &= ~BTM_PM_MD_FORCE;
+ return p_res;
+ }
+
+ if (p_md2->mode & BTM_PM_MD_FORCE) {
+ *p_res = *p_md2;
+ p_res->mode &= ~BTM_PM_MD_FORCE;
+ return p_res;
+ }
+
+ res = (p_md1->mode - 1) * BTM_PM_NUM_SET_MODES + (p_md2->mode - 1);
+ res = btm_pm_md_comp_matrix[res];
+ switch (res) {
+ case BTM_PM_GET_MD1:
+ *p_res = *p_md1;
+ return p_res;
+
+ case BTM_PM_GET_MD2:
+ *p_res = *p_md2;
+ return p_res;
+
+ case BTM_PM_GET_COMP:
+ p_res->mode = p_md1->mode;
+ /* min of the two */
+ p_res->max = (p_md1->max < p_md2->max) ? (p_md1->max) : (p_md2->max);
+ /* max of the two */
+ p_res->min = (p_md1->min > p_md2->min) ? (p_md1->min) : (p_md2->min);
+
+ /* the intersection is NULL */
+ if (p_res->max < p_res->min) return NULL;
+
+ if (p_res->mode == BTM_PM_MD_SNIFF) {
+ /* max of the two */
+ p_res->attempt = (p_md1->attempt > p_md2->attempt) ? (p_md1->attempt)
+ : (p_md2->attempt);
+ p_res->timeout = (p_md1->timeout > p_md2->timeout) ? (p_md1->timeout)
+ : (p_md2->timeout);
+ }
+ return p_res;
+ }
+ return NULL;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_pm_get_set_mode
+ * Description get the resulting mode from the registered parties, then compare
+ * it with the requested mode, if the command is from an
+ * unregistered party.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static tBTM_PM_MODE btm_pm_get_set_mode(uint8_t pm_id, tBTM_PM_MCB* p_cb,
+ const tBTM_PM_PWR_MD* p_mode,
+ tBTM_PM_PWR_MD* p_res) {
+ int xx, loop_max;
+ tBTM_PM_PWR_MD* p_md = NULL;
+
+ if (p_mode != NULL && p_mode->mode & BTM_PM_MD_FORCE) {
+ *p_res = *p_mode;
+ p_res->mode &= ~BTM_PM_MD_FORCE;
+ return p_res->mode;
+ }
+
+ if (!p_mode)
+ loop_max = BTM_MAX_PM_RECORDS + 1;
+ else
+ loop_max = BTM_MAX_PM_RECORDS;
+
+ for (xx = 0; xx < loop_max; xx++) {
+ /* g through all the registered "set" parties */
+ if (btm_cb.pm_reg_db[xx].mask & BTM_PM_REG_SET) {
+ if (p_cb->req_mode[xx].mode == BTM_PM_MD_ACTIVE) {
+ /* if at least one registered (SET) party says ACTIVE, stay active */
+ return BTM_PM_MD_ACTIVE;
+ } else {
+ /* if registered parties give conflicting information, stay active */
+ if ((btm_pm_compare_modes(p_md, &p_cb->req_mode[xx], p_res)) == NULL)
+ return BTM_PM_MD_ACTIVE;
+ p_md = p_res;
+ }
+ }
+ }
+
+ /* if the resulting mode is NULL(nobody registers SET), use the requested mode
+ */
+ if (p_md == NULL) {
+ if (p_mode)
+ *p_res = *((tBTM_PM_PWR_MD*)p_mode);
+ else /* p_mode is NULL when btm_pm_snd_md_req is called from
+ btm_pm_proc_mode_change */
+ return BTM_PM_MD_ACTIVE;
+ } else {
+ /* if the command is from unregistered party,
+ compare the resulting mode from registered party*/
+ if ((pm_id == BTM_PM_SET_ONLY_ID) &&
+ ((btm_pm_compare_modes(p_mode, p_md, p_res)) == NULL))
+ return BTM_PM_MD_ACTIVE;
+ }
+
+ return p_res->mode;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_pm_snd_md_req
+ * Description get the resulting mode and send the resuest to host controller
+ * Returns tBTM_STATUS
+ *, bool *p_chg_ind
+ ******************************************************************************/
+static tBTM_STATUS btm_pm_snd_md_req(uint8_t pm_id, int link_ind,
+ const tBTM_PM_PWR_MD* p_mode) {
+ tBTM_PM_PWR_MD md_res;
+ tBTM_PM_MODE mode;
+ tBTM_PM_MCB* p_cb = &btm_cb.pm_mode_db[link_ind];
+ bool chg_ind = false;
+
+ mode = btm_pm_get_set_mode(pm_id, p_cb, p_mode, &md_res);
+ md_res.mode = mode;
+
+#if (BTM_PM_DEBUG == TRUE)
+ BTM_TRACE_DEBUG("btm_pm_snd_md_req link_ind:%d, mode: %d", link_ind, mode);
+#endif // BTM_PM_DEBUG
+
+ if (p_cb->state == mode) {
+ /* already in the resulting mode */
+ if ((mode == BTM_PM_MD_ACTIVE) ||
+ ((md_res.max >= p_cb->interval) && (md_res.min <= p_cb->interval)))
+ return BTM_CMD_STORED;
+ /* Otherwise, needs to wake, then sleep */
+ chg_ind = true;
+ }
+ p_cb->chg_ind = chg_ind;
+
+ /* cannot go directly from current mode to resulting mode. */
+ if (mode != BTM_PM_MD_ACTIVE && p_cb->state != BTM_PM_MD_ACTIVE)
+ p_cb->chg_ind = true; /* needs to wake, then sleep */
+
+ if (p_cb->chg_ind) /* needs to wake first */
+ md_res.mode = BTM_PM_MD_ACTIVE;
+#if (BTM_SSR_INCLUDED == TRUE)
+ else if (BTM_PM_MD_SNIFF == md_res.mode && p_cb->max_lat) {
+ btsnd_hcic_sniff_sub_rate(btm_cb.acl_db[link_ind].hci_handle, p_cb->max_lat,
+ p_cb->min_rmt_to, p_cb->min_loc_to);
+ p_cb->max_lat = 0;
+ }
+#endif // BTM_SSR_INCLUDED
+ /* Default is failure */
+ btm_cb.pm_pend_link = MAX_L2CAP_LINKS;
+
+ /* send the appropriate HCI command */
+ btm_cb.pm_pend_id = pm_id;
+
+#if (BTM_PM_DEBUG == TRUE)
+ BTM_TRACE_DEBUG("btm_pm_snd_md_req state:0x%x, link_ind: %d", p_cb->state,
+ link_ind);
+#endif // BTM_PM_DEBUG
+
+ BTM_TRACE_DEBUG("%s switching from %s to %s.", __func__,
+ mode_to_string(p_cb->state), mode_to_string(md_res.mode));
+ switch (md_res.mode) {
+ case BTM_PM_MD_ACTIVE:
+ switch (p_cb->state) {
+ case BTM_PM_MD_SNIFF:
+ btsnd_hcic_exit_sniff_mode(btm_cb.acl_db[link_ind].hci_handle);
+ btm_cb.pm_pend_link = link_ind;
+ break;
+ case BTM_PM_MD_PARK:
+ btsnd_hcic_exit_park_mode(btm_cb.acl_db[link_ind].hci_handle);
+ btm_cb.pm_pend_link = link_ind;
+ break;
+ default:
+ /* Failure btm_cb.pm_pend_link = MAX_L2CAP_LINKS */
+ break;
+ }
+ break;
+
+ case BTM_PM_MD_HOLD:
+ btsnd_hcic_hold_mode(btm_cb.acl_db[link_ind].hci_handle, md_res.max,
+ md_res.min);
+ btm_cb.pm_pend_link = link_ind;
+ break;
+
+ case BTM_PM_MD_SNIFF:
+ btsnd_hcic_sniff_mode(btm_cb.acl_db[link_ind].hci_handle, md_res.max,
+ md_res.min, md_res.attempt, md_res.timeout);
+ btm_cb.pm_pend_link = link_ind;
+ break;
+
+ case BTM_PM_MD_PARK:
+ btsnd_hcic_park_mode(btm_cb.acl_db[link_ind].hci_handle, md_res.max,
+ md_res.min);
+ btm_cb.pm_pend_link = link_ind;
+ break;
+ default:
+ /* Failure btm_cb.pm_pend_link = MAX_L2CAP_LINKS */
+ break;
+ }
+
+ if (btm_cb.pm_pend_link == MAX_L2CAP_LINKS) {
+/* the command was not sent */
+#if (BTM_PM_DEBUG == TRUE)
+ BTM_TRACE_DEBUG("pm_pend_link: %d", btm_cb.pm_pend_link);
+#endif // BTM_PM_DEBUG
+ return (BTM_NO_RESOURCES);
+ }
+
+ return BTM_CMD_STARTED;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_pm_check_stored
+ *
+ * Description This function is called when an HCI command status event
+ * occurs to check if there's any PM command issued while
+ * waiting for HCI command status.
+ *
+ * Returns none.
+ *
+ ******************************************************************************/
+static void btm_pm_check_stored(void) {
+ int xx;
+ for (xx = 0; xx < MAX_L2CAP_LINKS; xx++) {
+ if (btm_cb.pm_mode_db[xx].state & BTM_PM_STORED_MASK) {
+ btm_cb.pm_mode_db[xx].state &= ~BTM_PM_STORED_MASK;
+ BTM_TRACE_DEBUG("btm_pm_check_stored :%d", xx);
+ btm_pm_snd_md_req(BTM_PM_SET_ONLY_ID, xx, NULL);
+ break;
+ }
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_pm_proc_cmd_status
+ *
+ * Description This function is called when an HCI command status event
+ * occurs for power manager related commands.
+ *
+ * Input Parms status - status of the event (HCI_SUCCESS if no errors)
+ *
+ * Returns none.
+ *
+ ******************************************************************************/
+void btm_pm_proc_cmd_status(uint8_t status) {
+ tBTM_PM_MCB* p_cb;
+ tBTM_PM_STATUS pm_status;
+
+ if (btm_cb.pm_pend_link >= MAX_L2CAP_LINKS) return;
+
+ p_cb = &btm_cb.pm_mode_db[btm_cb.pm_pend_link];
+
+ if (status == HCI_SUCCESS) {
+ p_cb->state = BTM_PM_ST_PENDING;
+ pm_status = BTM_PM_STS_PENDING;
+#if (BTM_PM_DEBUG == TRUE)
+ BTM_TRACE_DEBUG("btm_pm_proc_cmd_status new state:0x%x", p_cb->state);
+#endif // BTM_PM_DEBUG
+ } else /* the command was not successfull. Stay in the same state */
+ {
+ pm_status = BTM_PM_STS_ERROR;
+ }
+
+ /* notify the caller is appropriate */
+ if ((btm_cb.pm_pend_id != BTM_PM_SET_ONLY_ID) &&
+ (btm_cb.pm_reg_db[btm_cb.pm_pend_id].mask & BTM_PM_REG_NOTIF)) {
+ (*btm_cb.pm_reg_db[btm_cb.pm_pend_id].cback)(
+ btm_cb.acl_db[btm_cb.pm_pend_link].remote_addr, pm_status, 0, status);
+ }
+
+/* no pending cmd now */
+#if (BTM_PM_DEBUG == TRUE)
+ BTM_TRACE_DEBUG(
+ "btm_pm_proc_cmd_status state:0x%x, pm_pend_link: %d(new: %d)",
+ p_cb->state, btm_cb.pm_pend_link, MAX_L2CAP_LINKS);
+#endif // BTM_PM_DEBUG
+ btm_cb.pm_pend_link = MAX_L2CAP_LINKS;
+
+ btm_pm_check_stored();
+}
+
+/*******************************************************************************
+ *
+ * Function btm_process_mode_change
+ *
+ * Description This function is called when an HCI mode change event
+ * occurs.
+ *
+ * Input Parms hci_status - status of the event (HCI_SUCCESS if no errors)
+ * hci_handle - connection handle associated with the change
+ * mode - HCI_MODE_ACTIVE, HCI_MODE_HOLD, HCI_MODE_SNIFF, or
+ * HCI_MODE_PARK
+ * interval - number of baseband slots (meaning depends on
+ * mode)
+ *
+ * Returns none.
+ *
+ ******************************************************************************/
+void btm_pm_proc_mode_change(uint8_t hci_status, uint16_t hci_handle,
+ uint8_t mode, uint16_t interval) {
+ tACL_CONN* p;
+ tBTM_PM_MCB* p_cb = NULL;
+ int xx, yy, zz;
+ tBTM_PM_STATE old_state;
+ tL2C_LCB* p_lcb;
+
+ /* get the index to acl_db */
+ xx = btm_handle_to_acl_index(hci_handle);
+ if (xx >= MAX_L2CAP_LINKS) return;
+
+ p = &btm_cb.acl_db[xx];
+
+ /* update control block */
+ p_cb = &(btm_cb.pm_mode_db[xx]);
+ old_state = p_cb->state;
+ p_cb->state = mode;
+ p_cb->interval = interval;
+
+ BTM_TRACE_DEBUG("%s switched from %s to %s.", __func__,
+ mode_to_string(old_state), mode_to_string(p_cb->state));
+
+ p_lcb = l2cu_find_lcb_by_bd_addr(p->remote_addr, BT_TRANSPORT_BR_EDR);
+ if (p_lcb != NULL) {
+ if ((p_cb->state == BTM_PM_ST_ACTIVE) || (p_cb->state == BTM_PM_ST_SNIFF)) {
+ /* There might be any pending packets due to SNIFF or PENDING state */
+ /* Trigger L2C to start transmission of the pending packets. */
+ BTM_TRACE_DEBUG(
+ "btm mode change to active; check l2c_link for outgoing packets");
+ l2c_link_check_send_pkts(p_lcb, NULL, NULL);
+ }
+ }
+
+ /* notify registered parties */
+ for (yy = 0; yy <= BTM_MAX_PM_RECORDS; yy++) {
+ /* set req_mode HOLD mode->ACTIVE */
+ if ((mode == BTM_PM_MD_ACTIVE) &&
+ (p_cb->req_mode[yy].mode == BTM_PM_MD_HOLD))
+ p_cb->req_mode[yy].mode = BTM_PM_MD_ACTIVE;
+ }
+
+ /* new request has been made. - post a message to BTU task */
+ if (old_state & BTM_PM_STORED_MASK) {
+#if (BTM_PM_DEBUG == TRUE)
+ BTM_TRACE_DEBUG("btm_pm_proc_mode_change: Sending stored req:%d", xx);
+#endif // BTM_PM_DEBUG
+ btm_pm_snd_md_req(BTM_PM_SET_ONLY_ID, xx, NULL);
+ } else {
+ for (zz = 0; zz < MAX_L2CAP_LINKS; zz++) {
+ if (btm_cb.pm_mode_db[zz].chg_ind) {
+#if (BTM_PM_DEBUG == TRUE)
+ BTM_TRACE_DEBUG("btm_pm_proc_mode_change: Sending PM req :%d", zz);
+#endif // BTM_PM_DEBUG
+ btm_pm_snd_md_req(BTM_PM_SET_ONLY_ID, zz, NULL);
+ break;
+ }
+ }
+ }
+
+ /* notify registered parties */
+ for (yy = 0; yy < BTM_MAX_PM_RECORDS; yy++) {
+ if (btm_cb.pm_reg_db[yy].mask & BTM_PM_REG_NOTIF) {
+ (*btm_cb.pm_reg_db[yy].cback)(p->remote_addr, mode, interval, hci_status);
+ }
+ }
+ /*check if sco disconnect is waiting for the mode change */
+ btm_sco_disc_chk_pend_for_modechange(hci_handle);
+
+ /* If mode change was because of an active role switch or change link key */
+ btm_cont_rswitch(p, btm_find_dev(p->remote_addr), hci_status);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_pm_proc_ssr_evt
+ *
+ * Description This function is called when an HCI sniff subrating event
+ * occurs.
+ *
+ * Returns none.
+ *
+ ******************************************************************************/
+#if (BTM_SSR_INCLUDED == TRUE)
+void btm_pm_proc_ssr_evt(uint8_t* p, UNUSED_ATTR uint16_t evt_len) {
+ uint8_t status;
+ uint16_t handle;
+ uint16_t max_rx_lat;
+ int xx, yy;
+ tBTM_PM_MCB* p_cb;
+ tACL_CONN* p_acl = NULL;
+ uint16_t use_ssr = true;
+
+ STREAM_TO_UINT8(status, p);
+
+ STREAM_TO_UINT16(handle, p);
+ /* get the index to acl_db */
+ xx = btm_handle_to_acl_index(handle);
+ if (xx >= MAX_L2CAP_LINKS) return;
+
+ p += 2;
+ STREAM_TO_UINT16(max_rx_lat, p);
+ p_cb = &(btm_cb.pm_mode_db[xx]);
+
+ p_acl = &btm_cb.acl_db[xx];
+ if (p_cb->interval == max_rx_lat) {
+ /* using legacy sniff */
+ use_ssr = false;
+ }
+
+ /* notify registered parties */
+ for (yy = 0; yy < BTM_MAX_PM_RECORDS; yy++) {
+ if (btm_cb.pm_reg_db[yy].mask & BTM_PM_REG_NOTIF) {
+ if (p_acl) {
+ (*btm_cb.pm_reg_db[yy].cback)(p_acl->remote_addr, BTM_PM_STS_SSR,
+ use_ssr, status);
+ }
+ }
+ }
+}
+#endif // BTM_SSR_INCLUDED
+
+/*******************************************************************************
+ *
+ * Function btm_pm_device_in_active_or_sniff_mode
+ *
+ * Description This function is called to check if in active or sniff mode
+ *
+ * Returns true, if in active or sniff mode
+ *
+ ******************************************************************************/
+bool btm_pm_device_in_active_or_sniff_mode(void) {
+ /* The active state is the highest state-includes connected device and sniff
+ * mode*/
+
+ /* Covers active and sniff modes */
+ if (BTM_GetNumAclLinks() > 0) {
+ BTM_TRACE_DEBUG("%s - ACL links: %d", __func__, BTM_GetNumAclLinks());
+ return true;
+ }
+
+ /* Check BLE states */
+ if (btm_ble_get_conn_st() != BLE_CONN_IDLE) {
+ BTM_TRACE_DEBUG("%s - BLE state: %x", __func__, btm_ble_get_conn_st());
+ return true;
+ }
+
+ return false;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_pm_device_in_scan_state
+ *
+ * Description This function is called to check if in paging, inquiry or
+ * connecting mode
+ *
+ * Returns true, if in paging, inquiry or connecting mode
+ *
+ ******************************************************************************/
+bool btm_pm_device_in_scan_state(void) {
+ /* Scan state-paging, inquiry, and trying to connect */
+
+ /* Check for paging */
+ if (btm_cb.is_paging || (!fixed_queue_is_empty(btm_cb.page_queue)) ||
+ BTM_BL_PAGING_STARTED == btm_cb.busy_level) {
+ BTM_TRACE_DEBUG("btm_pm_device_in_scan_state- paging");
+ return true;
+ }
+
+ /* Check for inquiry */
+ if ((btm_cb.btm_inq_vars.inq_active &
+ (BTM_BR_INQ_ACTIVE_MASK | BTM_BLE_INQ_ACTIVE_MASK)) != 0) {
+ BTM_TRACE_DEBUG("btm_pm_device_in_scan_state- Inq active");
+ return true;
+ }
+
+ return false;
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_PM_ReadControllerState
+ *
+ * Description This function is called to obtain the controller state
+ *
+ * Returns Controller State-BTM_CONTRL_ACTIVE, BTM_CONTRL_SCAN, and
+ * BTM_CONTRL_IDLE
+ *
+ ******************************************************************************/
+tBTM_CONTRL_STATE BTM_PM_ReadControllerState(void) {
+ if (btm_pm_device_in_active_or_sniff_mode())
+ return BTM_CONTRL_ACTIVE;
+ else if (btm_pm_device_in_scan_state())
+ return BTM_CONTRL_SCAN;
+ else
+ return BTM_CONTRL_IDLE;
+}
+
+static const char* mode_to_string(const tBTM_PM_MODE mode) {
+ switch (mode) {
+ case BTM_PM_MD_ACTIVE:
+ return "ACTIVE";
+ case BTM_PM_MD_SNIFF:
+ return "SNIFF";
+ case BTM_PM_MD_PARK:
+ return "PARK";
+ case BTM_PM_MD_HOLD:
+ return "HOLD";
+ default:
+ return "UNKNOWN";
+ }
+}
diff --git a/stack/btm/btm_scn.cc b/stack/btm/btm_scn.cc
deleted file mode 100644
index 19ac67694..000000000
--- a/stack/btm/btm_scn.cc
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "btm"
-
-#include <cstdint>
-#include "stack/btm/btm_int_types.h" // tBTM_CB
-#include "stack/include/rfcdefs.h" // PORT_MAX_RFC_PORTS
-
-extern tBTM_CB btm_cb;
-
-/*******************************************************************************
- *
- * Function BTM_AllocateSCN
- *
- * Description Look through the Server Channel Numbers for a free one.
- *
- * Returns Allocated SCN number or 0 if none.
- *
- ******************************************************************************/
-uint8_t BTM_AllocateSCN(void) {
- uint8_t x;
- BTM_TRACE_DEBUG("BTM_AllocateSCN");
-
- // stack reserves scn 1 for HFP, HSP we still do the correct way
- for (x = 1; x < PORT_MAX_RFC_PORTS; x++) {
- if (!btm_cb.btm_scn[x]) {
- btm_cb.btm_scn[x] = true;
- return (x + 1);
- }
- }
-
- return (0); /* No free ports */
-}
-
-/*******************************************************************************
- *
- * Function BTM_TryAllocateSCN
- *
- * Description Try to allocate a fixed server channel
- *
- * Returns Returns true if server channel was available
- *
- ******************************************************************************/
-
-bool BTM_TryAllocateSCN(uint8_t scn) {
- /* Make sure we don't exceed max port range.
- * Stack reserves scn 1 for HFP, HSP we still do the correct way.
- */
- if ((scn >= PORT_MAX_RFC_PORTS) || (scn == 1) || (scn == 0)) return false;
-
- /* check if this port is available */
- if (!btm_cb.btm_scn[scn - 1]) {
- btm_cb.btm_scn[scn - 1] = true;
- return true;
- }
-
- return (false); /* Port was busy */
-}
-
-/*******************************************************************************
- *
- * Function BTM_FreeSCN
- *
- * Description Free the specified SCN.
- *
- * Returns true or false
- *
- ******************************************************************************/
-bool BTM_FreeSCN(uint8_t scn) {
- BTM_TRACE_DEBUG("BTM_FreeSCN ");
- if (scn <= PORT_MAX_RFC_PORTS && scn > 0) {
- btm_cb.btm_scn[scn - 1] = false;
- return (true);
- } else {
- return (false); /* Illegal SCN passed in */
- }
-}
diff --git a/stack/btm/btm_scn.h b/stack/btm/btm_scn.h
deleted file mode 100644
index fe9dcb7ad..000000000
--- a/stack/btm/btm_scn.h
+++ /dev/null
@@ -1,23 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-
-bool BTM_FreeSCN(uint8_t scn);
-bool BTM_TryAllocateSCN(uint8_t scn);
-bool BTM_TryAllocateSCN(uint8_t scn);
diff --git a/stack/btm/btm_sco.cc b/stack/btm/btm_sco.cc
index 5d0f376be..b8e0c9a3e 100644
--- a/stack/btm/btm_sco.cc
+++ b/stack/btm/btm_sco.cc
@@ -23,63 +23,36 @@
*
******************************************************************************/
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <string>
-
+#include <device/include/esco_parameters.h>
+#include <stack/include/btm_api_types.h>
+#include <string.h>
+#include "bt_common.h"
+#include "bt_target.h"
+#include "bt_types.h"
+#include "bt_utils.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btm_int_types.h"
+#include "btu.h"
#include "device/include/controller.h"
#include "device/include/esco_parameters.h"
-#include "osi/include/log.h"
+#include "hcidefs.h"
+#include "hcimsgs.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/btm/security_device_record.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcimsgs.h"
-#include "types/class_of_device.h"
-#include "types/raw_address.h"
-
-extern tBTM_CB btm_cb;
-
-namespace {
-constexpr char kBtmLogTag[] = "SCO";
-
-const bluetooth::legacy::hci::Interface& GetLegacyHciInterface() {
- return bluetooth::legacy::hci::GetInterface();
-}
-
-}; // namespace
/******************************************************************************/
/* L O C A L D A T A D E F I N I T I O N S */
/******************************************************************************/
-#define BTM_SCO_PKT_TYPE_MASK \
- (HCI_PKT_TYPES_MASK_HV1 | HCI_PKT_TYPES_MASK_HV2 | HCI_PKT_TYPES_MASK_HV3)
-
-/* MACROs to convert from SCO packet types mask to ESCO and back */
-#define BTM_SCO_PKT_TYPE_MASK \
- (HCI_PKT_TYPES_MASK_HV1 | HCI_PKT_TYPES_MASK_HV2 | HCI_PKT_TYPES_MASK_HV3)
-
-/* Mask defining only the SCO types of an esco packet type */
-#define BTM_ESCO_PKT_TYPE_MASK \
- (ESCO_PKT_TYPES_MASK_HV1 | ESCO_PKT_TYPES_MASK_HV2 | ESCO_PKT_TYPES_MASK_HV3)
-
-#define BTM_ESCO_2_SCO(escotype) \
- ((uint16_t)(((escotype)&BTM_ESCO_PKT_TYPE_MASK) << 5))
-
-/* Define masks for supported and exception 2.0 SCO packet types
- */
-#define BTM_SCO_SUPPORTED_PKTS_MASK \
- (ESCO_PKT_TYPES_MASK_HV1 | ESCO_PKT_TYPES_MASK_HV2 | \
- ESCO_PKT_TYPES_MASK_HV3 | ESCO_PKT_TYPES_MASK_EV3 | \
- ESCO_PKT_TYPES_MASK_EV4 | ESCO_PKT_TYPES_MASK_EV5)
-
-#define BTM_SCO_EXCEPTION_PKTS_MASK \
- (ESCO_PKT_TYPES_MASK_NO_2_EV3 | ESCO_PKT_TYPES_MASK_NO_3_EV3 | \
- ESCO_PKT_TYPES_MASK_NO_2_EV5 | ESCO_PKT_TYPES_MASK_NO_3_EV5)
+#define SCO_ST_UNUSED 0
+#define SCO_ST_LISTENING 1
+#define SCO_ST_W4_CONN_RSP 2
+#define SCO_ST_CONNECTING 3
+#define SCO_ST_CONNECTED 4
+#define SCO_ST_DISCONNECTING 5
+#define SCO_ST_PEND_UNPARK 6
+#define SCO_ST_PEND_ROLECHANGE 7
+#define SCO_ST_PEND_MODECHANGE 8
/******************************************************************************/
/* L O C A L F U N C T I O N P R O T O T Y P E S */
@@ -97,7 +70,24 @@ static uint16_t btm_sco_voice_settings_to_legacy(enh_esco_params_t* p_parms);
* Returns void
*
******************************************************************************/
-static void btm_sco_flush_sco_data(UNUSED_ATTR uint16_t sco_inx) {}
+void btm_sco_flush_sco_data(UNUSED_ATTR uint16_t sco_inx) {}
+
+/*******************************************************************************
+ *
+ * Function btm_sco_init
+ *
+ * Description This function is called at BTM startup to initialize
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_sco_init(void) {
+ /* Initialize nonzero defaults */
+ btm_cb.sco_cb.sco_disc_reason = BTM_INVALID_SCO_DISC_REASON;
+ btm_cb.sco_cb.def_esco_parms = esco_parameters_for_codec(ESCO_CODEC_CVSD);
+ btm_cb.sco_cb.def_esco_parms.max_latency_ms = 12;
+ btm_cb.sco_cb.sco_route = ESCO_DATA_PATH_PCM;
+}
/*******************************************************************************
*
@@ -118,10 +108,9 @@ static void btm_sco_flush_sco_data(UNUSED_ATTR uint16_t sco_inx) {}
static void btm_esco_conn_rsp(uint16_t sco_inx, uint8_t hci_status,
const RawAddress& bda,
enh_esco_params_t* p_parms) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CONN* p_sco = NULL;
- if (BTM_MAX_SCO_LINKS == 0) return;
-
if (sco_inx < BTM_MAX_SCO_LINKS) p_sco = &btm_cb.sco_cb.sco_db[sco_inx];
/* Reject the connect request if refused by caller or wrong state */
@@ -147,6 +136,31 @@ static void btm_esco_conn_rsp(uint16_t sco_inx, uint8_t hci_status,
*p_setup = btm_cb.sco_cb.def_esco_parms;
}
+ uint16_t temp_packet_types =
+ (p_setup->packet_types & BTM_SCO_SUPPORTED_PKTS_MASK &
+ btm_cb.btm_sco_pkt_types_supported);
+
+ /* Make sure at least one eSCO packet type is sent, else might confuse peer
+ */
+ /* Taking this out to confirm with BQB tests
+ ** Real application would like to include this though, as many devices
+ ** do not retry with SCO only if an eSCO connection fails.
+ if (!(temp_packet_types & BTM_ESCO_LINK_ONLY_MASK))
+ {
+ temp_packet_types |= BTM_SCO_PKT_TYPES_MASK_EV3;
+ }
+ */
+ /* If SCO request, remove eSCO packet types (conformance) */
+ if (p_sco->esco.data.link_type == BTM_LINK_TYPE_SCO) {
+ temp_packet_types &= BTM_SCO_LINK_ONLY_MASK;
+ temp_packet_types |= BTM_SCO_EXCEPTION_PKTS_MASK;
+ } else {
+ /* OR in any exception packet types */
+ temp_packet_types |=
+ ((p_setup->packet_types & BTM_SCO_EXCEPTION_PKTS_MASK) |
+ (btm_cb.btm_sco_pkt_types_supported & BTM_SCO_EXCEPTION_PKTS_MASK));
+ }
+
/* Use Enhanced Synchronous commands if supported */
if (controller_get_interface()
->supports_enhanced_setup_synchronous_connection()) {
@@ -172,6 +186,7 @@ static void btm_esco_conn_rsp(uint16_t sco_inx, uint8_t hci_status,
p_setup->retransmission_effort, p_setup->packet_types);
}
}
+#endif
}
/*******************************************************************************
@@ -189,6 +204,33 @@ void btm_route_sco_data(BT_HDR* p_msg) {
/*******************************************************************************
*
+ * Function BTM_WriteScoData
+ *
+ * Description This function write SCO data to a specified instance. The
+ * data to be written p_buf needs to carry an offset of
+ * HCI_SCO_PREAMBLE_SIZE bytes, and the data length can not
+ * exceed BTM_SCO_DATA_SIZE_MAX bytes, whose default value is
+ * set to 60 and is configurable. Data longer than the maximum
+ * bytes will be truncated.
+ *
+ * Returns BTM_SUCCESS: data write is successful
+ * BTM_ILLEGAL_VALUE: SCO data contains illegal offset value.
+ * BTM_SCO_BAD_LENGTH: SCO data length exceeds the max SCO
+ * packet size.
+ * BTM_NO_RESOURCES: no resources.
+ * BTM_UNKNOWN_ADDR: unknown SCO connection handle, or SCO is
+ * not routed via HCI.
+ *
+ *
+ ******************************************************************************/
+tBTM_STATUS BTM_WriteScoData(UNUSED_ATTR uint16_t sco_inx,
+ UNUSED_ATTR BT_HDR* p_buf) {
+ return (BTM_NO_RESOURCES);
+}
+
+#if (BTM_MAX_SCO_LINKS > 0)
+/*******************************************************************************
+ *
* Function btm_send_connect_request
*
* Description This function is called to respond to SCO connect
@@ -199,6 +241,8 @@ void btm_route_sco_data(BT_HDR* p_msg) {
******************************************************************************/
static tBTM_STATUS btm_send_connect_request(uint16_t acl_handle,
enh_esco_params_t* p_setup) {
+ tACL_CONN* p_acl;
+
/* Send connect request depending on version of spec */
if (!btm_cb.sco_cb.esco_supported) {
LOG(INFO) << __func__ << ": sending non-eSCO request for handle="
@@ -217,14 +261,16 @@ static tBTM_STATUS btm_send_connect_request(uint16_t acl_handle,
/* Finally, remove EDR eSCO if the remote device doesn't support it */
/* UPF25: Only SCO was brought up in this case */
- const RawAddress bd_addr = acl_address_from_handle(acl_handle);
- if (bd_addr != RawAddress::kEmpty) {
- if (!sco_peer_supports_esco_2m_phy(bd_addr)) {
+ btm_handle_to_acl_index(acl_handle);
+ uint8_t acl_index = btm_handle_to_acl_index(acl_handle);
+ if (acl_index < MAX_L2CAP_LINKS) {
+ p_acl = &btm_cb.acl_db[acl_index];
+ if (!HCI_EDR_ESCO_2MPS_SUPPORTED(p_acl->peer_lmp_feature_pages[0])) {
BTM_TRACE_DEBUG("BTM Remote does not support 2-EDR eSCO");
temp_packet_types |=
(ESCO_PKT_TYPES_MASK_NO_2_EV3 | ESCO_PKT_TYPES_MASK_NO_2_EV5);
}
- if (!sco_peer_supports_esco_3m_phy(bd_addr)) {
+ if (!HCI_EDR_ESCO_3MPS_SUPPORTED(p_acl->peer_lmp_feature_pages[0])) {
BTM_TRACE_DEBUG("BTM Remote does not support 3-EDR eSCO");
temp_packet_types |=
(ESCO_PKT_TYPES_MASK_NO_3_EV3 | ESCO_PKT_TYPES_MASK_NO_3_EV5);
@@ -233,44 +279,28 @@ static tBTM_STATUS btm_send_connect_request(uint16_t acl_handle,
/* Check to see if BR/EDR Secure Connections is being used
** If so, we cannot use SCO-only packet types (HFP 1.7)
*/
- const bool local_supports_sc =
- controller_get_interface()->supports_secure_connections();
- const bool remote_supports_sc =
- BTM_PeerSupportsSecureConnections(bd_addr);
-
- if (local_supports_sc && remote_supports_sc) {
+ if (BTM_BothEndsSupportSecureConnections(p_acl->remote_addr)) {
temp_packet_types &= ~(BTM_SCO_PKT_TYPE_MASK);
+ BTM_TRACE_DEBUG("%s: SCO Conn: pkt_types after removing SCO (0x%04x)",
+ __func__, temp_packet_types);
+
+ /* Return error if no packet types left */
if (temp_packet_types == 0) {
- LOG_ERROR(
- "SCO connection cannot support any packet types for "
- "acl_handle:0x%04x",
- acl_handle);
- return BTM_WRONG_MODE;
+ LOG(ERROR) << __func__
+ << ": SCO Conn (BR/EDR SC): No packet types available for "
+ "acl_handle "
+ << unsigned(acl_handle);
+ return (BTM_WRONG_MODE);
}
- LOG_DEBUG(
- "Both local and remote controllers support SCO secure connections "
- "handle:0x%04x pkt_types:0x%04x",
- acl_handle, temp_packet_types);
-
- } else if (!local_supports_sc && !remote_supports_sc) {
- LOG_DEBUG(
- "Both local and remote controllers do not support secure "
- "connections for handle:0x%04x",
- acl_handle);
- } else if (remote_supports_sc) {
- LOG_DEBUG(
- "Only remote controller supports secure connections for "
- "handle:0x%04x",
- acl_handle);
} else {
- LOG_DEBUG(
- "Only local controller supports secure connections for "
- "handle:0x%04x",
- acl_handle);
+ LOG(WARNING) << __func__
+ << ": SCO Conn(BR/EDR SC):local or peer does not support "
+ "BR/EDR SC for acl_handle "
+ << unsigned(acl_handle);
}
} else {
- LOG_ERROR("Received SCO connect from unknown peer:%s",
- PRIVATE_ADDRESS(bd_addr));
+ LOG(ERROR) << __func__ << ": acl_index " << unsigned(acl_index)
+ << " out of range for acl_handle " << unsigned(acl_handle);
}
/* Save the previous types in case command fails */
@@ -280,8 +310,6 @@ static tBTM_STATUS btm_send_connect_request(uint16_t acl_handle,
/* Use Enhanced Synchronous commands if supported */
if (controller_get_interface()
->supports_enhanced_setup_synchronous_connection()) {
- LOG_INFO("Sending enhanced SCO connect request over handle:0x%04x",
- acl_handle);
/* Use the saved SCO routing */
p_setup->input_data_path = p_setup->output_data_path =
btm_cb.sco_cb.sco_route;
@@ -296,7 +324,6 @@ static tBTM_STATUS btm_send_connect_request(uint16_t acl_handle,
btsnd_hcic_enhanced_set_up_synchronous_connection(acl_handle, p_setup);
p_setup->packet_types = saved_packet_types;
} else { /* Use older command */
- LOG_INFO("Sending eSCO connect request over handle:0x%04x", acl_handle);
uint16_t voice_content_format = btm_sco_voice_settings_to_legacy(p_setup);
LOG(INFO) << __func__ << std::hex << ": legacy parameter list"
<< " txbw=0x" << unsigned(p_setup->transmit_bandwidth)
@@ -315,6 +342,71 @@ static tBTM_STATUS btm_send_connect_request(uint16_t acl_handle,
return (BTM_CMD_STARTED);
}
+#endif
+
+/*******************************************************************************
+ *
+ * Function btm_set_sco_ind_cback
+ *
+ * Description This function is called to register for TCS SCO connect
+ * indications.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_set_sco_ind_cback(tBTM_SCO_IND_CBACK* sco_ind_cb) {
+ btm_cb.sco_cb.app_sco_ind_cb = sco_ind_cb;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_accept_sco_link
+ *
+ * Description This function is called to respond to TCS SCO connect
+ * indications
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_accept_sco_link(uint16_t sco_inx, enh_esco_params_t* p_setup,
+ tBTM_SCO_CB* p_conn_cb, tBTM_SCO_CB* p_disc_cb) {
+#if (BTM_MAX_SCO_LINKS > 0)
+ tSCO_CONN* p_sco;
+
+ if (sco_inx >= BTM_MAX_SCO_LINKS) {
+ BTM_TRACE_ERROR("btm_accept_sco_link: Invalid sco_inx(%d)", sco_inx);
+ return;
+ }
+
+ /* Link role is ignored in for this message */
+ p_sco = &btm_cb.sco_cb.sco_db[sco_inx];
+ p_sco->p_conn_cb = p_conn_cb;
+ p_sco->p_disc_cb = p_disc_cb;
+ p_sco->esco.data.link_type =
+ BTM_LINK_TYPE_ESCO; /* Accept with all supported types */
+
+ BTM_TRACE_DEBUG("TCS accept SCO: Packet Types 0x%04x", p_setup->packet_types);
+
+ btm_esco_conn_rsp(sco_inx, HCI_SUCCESS, p_sco->esco.data.bd_addr, p_setup);
+#else
+ btm_reject_sco_link(sco_inx);
+#endif
+}
+
+/*******************************************************************************
+ *
+ * Function btm_reject_sco_link
+ *
+ * Description This function is called to respond to SCO connect
+ * indications
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_reject_sco_link(uint16_t sco_inx) {
+ btm_esco_conn_rsp(sco_inx, HCI_ERR_HOST_REJECT_RESOURCES,
+ btm_cb.sco_cb.sco_db[sco_inx].esco.data.bd_addr, NULL);
+}
/*******************************************************************************
*
@@ -339,16 +431,14 @@ static tBTM_STATUS btm_send_connect_request(uint16_t acl_handle,
tBTM_STATUS BTM_CreateSco(const RawAddress* remote_bda, bool is_orig,
uint16_t pkt_types, uint16_t* p_sco_inx,
tBTM_SCO_CB* p_conn_cb, tBTM_SCO_CB* p_disc_cb) {
+#if (BTM_MAX_SCO_LINKS > 0)
enh_esco_params_t* p_setup;
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
uint16_t xx;
- uint16_t acl_handle = HCI_INVALID_HANDLE;
+ uint16_t acl_handle = 0;
+ tACL_CONN* p_acl;
*p_sco_inx = BTM_INVALID_SCO_INDEX;
- if (BTM_MAX_SCO_LINKS == 0) {
- return BTM_NO_RESOURCES;
- }
-
/* If originating, ensure that there is an ACL connection to the BD Address */
if (is_orig) {
@@ -357,7 +447,7 @@ tBTM_STATUS BTM_CreateSco(const RawAddress* remote_bda, bool is_orig,
return BTM_ILLEGAL_VALUE;
}
acl_handle = BTM_GetHCIConnHandle(*remote_bda, BT_TRANSPORT_BR_EDR);
- if (acl_handle == HCI_INVALID_HANDLE) {
+ if (acl_handle == 0xFFFF) {
LOG(ERROR) << __func__ << ": cannot find ACL handle for remote device "
<< remote_bda;
return BTM_UNKNOWN_ADDR;
@@ -395,15 +485,15 @@ tBTM_STATUS BTM_CreateSco(const RawAddress* remote_bda, bool is_orig,
if (is_orig) {
// can not create SCO link if in park mode
tBTM_PM_STATE state;
- if (BTM_ReadPowerMode(*remote_bda, &state)) {
+ if ((btm_read_power_mode_state(*remote_bda, &state) == BTM_SUCCESS)) {
if (state == BTM_PM_ST_SNIFF || state == BTM_PM_ST_PARK ||
state == BTM_PM_ST_PENDING) {
LOG(INFO) << __func__ << ": " << *remote_bda
<< " in sniff, park or pending mode "
<< unsigned(state);
- if (!BTM_SetLinkPolicyActiveMode(*remote_bda)) {
- LOG_WARN("Unable to set link policy active");
- }
+ tBTM_PM_PWR_MD pm = {};
+ pm.mode = BTM_PM_MD_ACTIVE;
+ BTM_SetPowerMode(BTM_PM_SET_ONLY_ID, *remote_bda, &pm);
p->state = SCO_ST_PEND_UNPARK;
}
} else {
@@ -432,14 +522,15 @@ tBTM_STATUS BTM_CreateSco(const RawAddress* remote_bda, bool is_orig,
p->p_conn_cb = p_conn_cb;
p->p_disc_cb = p_disc_cb;
- p->hci_handle = HCI_INVALID_HANDLE;
+ p->hci_handle = BTM_INVALID_HCI_HANDLE;
p->is_orig = is_orig;
if (p->state != SCO_ST_PEND_UNPARK) {
if (is_orig) {
/* If role change is in progress, do not proceed with SCO setup
* Wait till role change is complete */
- if (!acl_is_switch_role_idle(*remote_bda, BT_TRANSPORT_BR_EDR)) {
+ p_acl = btm_bda_to_acl(*remote_bda, BT_TRANSPORT_BR_EDR);
+ if (p_acl && p_acl->switch_role_state != BTM_ACL_SWKEY_STATE_IDLE) {
BTM_TRACE_API("Role Change is in progress for ACL handle 0x%04x",
acl_handle);
p->state = SCO_ST_PEND_ROLECHANGE;
@@ -450,7 +541,8 @@ tBTM_STATUS BTM_CreateSco(const RawAddress* remote_bda, bool is_orig,
if (p->state != SCO_ST_PEND_UNPARK &&
p->state != SCO_ST_PEND_ROLECHANGE) {
if (is_orig) {
- LOG_DEBUG("Initiating (e)SCO link for ACL handle:0x%04x", acl_handle);
+ BTM_TRACE_API("%s:(e)SCO Link for ACL handle 0x%04x", __func__,
+ acl_handle);
if ((btm_send_connect_request(acl_handle, p_setup)) !=
BTM_CMD_STARTED) {
@@ -461,22 +553,19 @@ tBTM_STATUS BTM_CreateSco(const RawAddress* remote_bda, bool is_orig,
p->state = SCO_ST_CONNECTING;
} else {
- LOG_DEBUG("Listening for (e)SCO on ACL handle:0x%04x", acl_handle);
+ BTM_TRACE_API("%s:(e)SCO listening for ACL handle 0x%04x", __func__,
+ acl_handle);
p->state = SCO_ST_LISTENING;
}
}
*p_sco_inx = xx;
- LOG_DEBUG("SCO connection successfully requested");
- if (p->state == SCO_ST_CONNECTING) {
- BTM_LogHistory(
- kBtmLogTag, *remote_bda, "Connecting",
- base::StringPrintf("local initiated acl:0x%04x", acl_handle));
- }
+ BTM_TRACE_API("%s: BTM_CreateSco succeeded", __func__);
return BTM_CMD_STARTED;
}
}
+#endif
/* If here, all SCO blocks in use */
LOG(ERROR) << __func__ << ": all SCO control blocks are in use";
return BTM_NO_RESOURCES;
@@ -493,7 +582,8 @@ tBTM_STATUS BTM_CreateSco(const RawAddress* remote_bda, bool is_orig,
* Returns void
*
******************************************************************************/
-void btm_sco_chk_pend_unpark(tHCI_STATUS hci_status, uint16_t hci_handle) {
+void btm_sco_chk_pend_unpark(uint8_t hci_status, uint16_t hci_handle) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
for (uint16_t xx = 0; xx < BTM_MAX_SCO_LINKS; xx++, p++) {
uint16_t acl_handle =
@@ -512,6 +602,7 @@ void btm_sco_chk_pend_unpark(tHCI_STATUS hci_status, uint16_t hci_handle) {
}
}
}
+#endif // BTM_MAX_SCO_LINKS
}
/*******************************************************************************
@@ -526,6 +617,7 @@ void btm_sco_chk_pend_unpark(tHCI_STATUS hci_status, uint16_t hci_handle) {
*
******************************************************************************/
void btm_sco_chk_pend_rolechange(uint16_t hci_handle) {
+#if (BTM_MAX_SCO_LINKS > 0)
uint16_t xx;
uint16_t acl_handle;
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
@@ -545,6 +637,7 @@ void btm_sco_chk_pend_rolechange(uint16_t hci_handle) {
p->state = SCO_ST_CONNECTING;
}
}
+#endif
}
/*******************************************************************************
@@ -559,12 +652,11 @@ void btm_sco_chk_pend_rolechange(uint16_t hci_handle) {
*
******************************************************************************/
void btm_sco_disc_chk_pend_for_modechange(uint16_t hci_handle) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
- LOG_DEBUG(
- "Checking for SCO pending mode change events hci_handle:0x%04x "
- "p->state:%s",
- hci_handle, sco_state_text(p->state).c_str());
+ BTM_TRACE_DEBUG("%s: hci_handle 0x%04x, p->state 0x%02x", __func__,
+ hci_handle, p->state);
for (uint16_t xx = 0; xx < BTM_MAX_SCO_LINKS; xx++, p++) {
if ((p->state == SCO_ST_PEND_MODECHANGE) &&
@@ -572,10 +664,11 @@ void btm_sco_disc_chk_pend_for_modechange(uint16_t hci_handle) {
hci_handle)
{
- LOG_DEBUG("Removing SCO Link handle 0x%04x", p->hci_handle);
+ BTM_TRACE_DEBUG("%s: SCO Link handle 0x%04x", __func__, p->hci_handle);
BTM_RemoveSco(xx);
}
}
+#endif
}
/*******************************************************************************
@@ -588,8 +681,9 @@ void btm_sco_disc_chk_pend_for_modechange(uint16_t hci_handle) {
* Returns void
*
******************************************************************************/
-void btm_sco_conn_req(const RawAddress& bda, const DEV_CLASS& dev_class,
+void btm_sco_conn_req(const RawAddress& bda, DEV_CLASS dev_class,
uint8_t link_type) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CB* p_sco = &btm_cb.sco_cb;
tSCO_CONN* p = &p_sco->sco_db[0];
tBTM_ESCO_CONN_REQ_EVT_DATA evt_data = {};
@@ -604,7 +698,7 @@ void btm_sco_conn_req(const RawAddress& bda, const DEV_CLASS& dev_class,
if (((p->state == SCO_ST_CONNECTING) && rem_bd_matches) ||
((p->state == SCO_ST_LISTENING) &&
(rem_bd_matches || !p->rem_bd_known))) {
- /* If this was a wildcard, it is not one any more */
+ /* If this guy was a wildcard, he is not one any more */
p->rem_bd_known = true;
p->esco.data.link_type = link_type;
p->state = SCO_ST_W4_CONN_RSP;
@@ -665,6 +759,7 @@ void btm_sco_conn_req(const RawAddress& bda, const DEV_CLASS& dev_class,
}
}
+#endif
/* If here, no one wants the SCO connection. Reject it */
BTM_TRACE_WARNING("%s: rejecting SCO for %s", __func__,
bda.ToString().c_str());
@@ -682,82 +777,54 @@ void btm_sco_conn_req(const RawAddress& bda, const DEV_CLASS& dev_class,
* Returns void
*
******************************************************************************/
-void btm_sco_connected(tHCI_STATUS hci_status, const RawAddress& bda,
+void btm_sco_connected(uint8_t hci_status, const RawAddress* bda,
uint16_t hci_handle, tBTM_ESCO_DATA* p_esco_data) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
uint16_t xx;
bool spt = false;
tBTM_CHG_ESCO_PARAMS parms = {};
+#endif
+ btm_cb.sco_cb.sco_disc_reason = hci_status;
+
+#if (BTM_MAX_SCO_LINKS > 0)
for (xx = 0; xx < BTM_MAX_SCO_LINKS; xx++, p++) {
if (((p->state == SCO_ST_CONNECTING) || (p->state == SCO_ST_LISTENING) ||
(p->state == SCO_ST_W4_CONN_RSP)) &&
- (p->rem_bd_known) && (p->esco.data.bd_addr == bda)) {
+ (p->rem_bd_known) && (!bda || p->esco.data.bd_addr == *bda)) {
if (hci_status != HCI_SUCCESS) {
/* Report the error if originator, otherwise remain in Listen mode */
if (p->is_orig) {
- LOG_DEBUG("SCO initiating connection failed handle:0x%04x reason:%s",
- hci_handle, hci_error_code_text(hci_status).c_str());
- switch (hci_status) {
- case HCI_ERR_ROLE_SWITCH_PENDING:
- /* If role switch is pending, we need try again after role switch
- * is complete */
- p->state = SCO_ST_PEND_ROLECHANGE;
- break;
- case HCI_ERR_LMP_ERR_TRANS_COLLISION:
- /* Avoid calling disconnect callback because of sco creation race
- */
- break;
- default: /* Notify client about SCO failure */
- p->state = SCO_ST_UNUSED;
- (*p->p_disc_cb)(xx);
+ /* If role switch is pending, we need try again after role switch is
+ * complete */
+ if (hci_status == HCI_ERR_ROLE_SWITCH_PENDING) {
+ BTM_TRACE_API("Role Change pending for HCI handle 0x%04x",
+ hci_handle);
+ p->state = SCO_ST_PEND_ROLECHANGE;
+ }
+ /* avoid calling disconnect callback because of sco creation race */
+ else if (hci_status != HCI_ERR_LMP_ERR_TRANS_COLLISION) {
+ p->state = SCO_ST_UNUSED;
+ (*p->p_disc_cb)(xx);
}
- BTM_LogHistory(
- kBtmLogTag, bda, "Connection failed",
- base::StringPrintf(
- "locally_initiated reason:%s",
- hci_reason_code_text(static_cast<tHCI_REASON>(hci_status))
- .c_str()));
} else {
- LOG_DEBUG("SCO terminating connection failed handle:0x%04x reason:%s",
- hci_handle, hci_error_code_text(hci_status).c_str());
+ /* Notify the upper layer that incoming sco connection has failed. */
if (p->state == SCO_ST_CONNECTING) {
p->state = SCO_ST_UNUSED;
(*p->p_disc_cb)(xx);
} else
p->state = SCO_ST_LISTENING;
- BTM_LogHistory(
- kBtmLogTag, bda, "Connection failed",
- base::StringPrintf(
- "remote_initiated reason:%s",
- hci_reason_code_text(static_cast<tHCI_REASON>(hci_status))
- .c_str()));
}
+
return;
}
- BTM_LogHistory(
- kBtmLogTag, bda, "Connection created",
- base::StringPrintf("sco_idx:%hu handle:0x%04x ", xx, hci_handle));
-
if (p->state == SCO_ST_LISTENING) spt = true;
p->state = SCO_ST_CONNECTED;
p->hci_handle = hci_handle;
- if (hci_status == HCI_SUCCESS) {
- BTM_LogHistory(kBtmLogTag, bda, "Connection success",
- base::StringPrintf("handle:0x%04x %s", hci_handle,
- (spt) ? "listener" : "initiator"));
- } else {
- BTM_LogHistory(
- kBtmLogTag, bda, "Connection failed",
- base::StringPrintf(
- "reason:%s",
- hci_reason_code_text(static_cast<tHCI_REASON>(hci_status))
- .c_str()));
- }
-
if (!btm_cb.sco_cb.esco_supported) {
p->esco.data.link_type = BTM_LINK_TYPE_SCO;
if (spt) {
@@ -777,6 +844,32 @@ void btm_sco_connected(tHCI_STATUS hci_status, const RawAddress& bda,
return;
}
}
+#endif
+}
+
+/*******************************************************************************
+ *
+ * Function btm_find_scb_by_handle
+ *
+ * Description Look through all active SCO connection for a match based on
+ * the HCI handle.
+ *
+ * Returns index to matched SCO connection CB, or BTM_MAX_SCO_LINKS if
+ * no match.
+ *
+ ******************************************************************************/
+uint16_t btm_find_scb_by_handle(uint16_t handle) {
+ int xx;
+ tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
+
+ for (xx = 0; xx < BTM_MAX_SCO_LINKS; xx++, p++) {
+ if ((p->state == SCO_ST_CONNECTED) && (p->hci_handle == handle)) {
+ return (xx);
+ }
+ }
+
+ /* If here, no match found */
+ return (xx);
}
/*******************************************************************************
@@ -789,50 +882,58 @@ void btm_sco_connected(tHCI_STATUS hci_status, const RawAddress& bda,
*
******************************************************************************/
tBTM_STATUS BTM_RemoveSco(uint16_t sco_inx) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[sco_inx];
+ uint16_t tempstate;
tBTM_PM_STATE state = BTM_PM_ST_INVALID;
BTM_TRACE_DEBUG("%s", __func__);
- if (BTM_MAX_SCO_LINKS == 0) {
- return BTM_NO_RESOURCES;
- }
-
/* Validity check */
if ((sco_inx >= BTM_MAX_SCO_LINKS) || (p->state == SCO_ST_UNUSED))
return (BTM_UNKNOWN_ADDR);
/* If no HCI handle, simply drop the connection and return */
- if (p->hci_handle == HCI_INVALID_HANDLE || p->state == SCO_ST_PEND_UNPARK) {
- p->hci_handle = HCI_INVALID_HANDLE;
+ if (p->hci_handle == BTM_INVALID_HCI_HANDLE ||
+ p->state == SCO_ST_PEND_UNPARK) {
+ p->hci_handle = BTM_INVALID_HCI_HANDLE;
p->state = SCO_ST_UNUSED;
p->esco.p_esco_cback = NULL; /* Deregister the eSCO event callback */
return (BTM_SUCCESS);
}
- if (BTM_ReadPowerMode(p->esco.data.bd_addr, &state) &&
- (state == BTM_PM_ST_PENDING)) {
+ if ((btm_read_power_mode_state(p->esco.data.bd_addr, &state) ==
+ BTM_SUCCESS) &&
+ state == BTM_PM_ST_PENDING) {
BTM_TRACE_DEBUG("%s: BTM_PM_ST_PENDING for ACL mapped with SCO Link 0x%04x",
__func__, p->hci_handle);
p->state = SCO_ST_PEND_MODECHANGE;
return (BTM_CMD_STARTED);
}
- tSCO_STATE old_state = p->state;
+ tempstate = p->state;
p->state = SCO_ST_DISCONNECTING;
- GetLegacyHciInterface().Disconnect(p->Handle(), HCI_ERR_PEER_USER);
+ btsnd_hcic_disconnect(p->hci_handle, HCI_ERR_PEER_USER);
- LOG_DEBUG("Disconnecting link sco_handle:0x%04x peer:%s", p->Handle(),
- PRIVATE_ADDRESS(p->esco.data.bd_addr));
- BTM_LogHistory(
- kBtmLogTag, p->esco.data.bd_addr, "Disconnecting",
- base::StringPrintf("local initiated handle:0x%04x previous_state:%s",
- p->Handle(), sco_state_text(old_state).c_str()));
return (BTM_CMD_STARTED);
+#else
+ return (BTM_NO_RESOURCES);
+#endif
}
-void BTM_RemoveSco(const RawAddress& bda) {
+/*******************************************************************************
+ *
+ * Function btm_remove_sco_links
+ *
+ * Description This function is called to remove all sco links for an ACL
+ * link.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_remove_sco_links(const RawAddress& bda) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
uint16_t xx;
@@ -841,22 +942,28 @@ void BTM_RemoveSco(const RawAddress& bda) {
BTM_RemoveSco(xx);
}
}
+#endif
}
/*******************************************************************************
*
* Function btm_sco_removed
*
- * Description This function is called by lower layers when an
- * disconnect is received.
+ * Description This function is called by BTIF when an SCO connection
+ * is removed.
*
- * Returns true if the link is known about, else false
+ * Returns void
*
******************************************************************************/
-bool btm_sco_removed(uint16_t hci_handle, tHCI_REASON reason) {
+void btm_sco_removed(uint16_t hci_handle, uint8_t reason) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
uint16_t xx;
+#endif
+ btm_cb.sco_cb.sco_disc_reason = reason;
+
+#if (BTM_MAX_SCO_LINKS > 0)
p = &btm_cb.sco_cb.sco_db[0];
for (xx = 0; xx < BTM_MAX_SCO_LINKS; xx++, p++) {
if ((p->state != SCO_ST_UNUSED) && (p->state != SCO_ST_LISTENING) &&
@@ -864,63 +971,15 @@ bool btm_sco_removed(uint16_t hci_handle, tHCI_REASON reason) {
btm_sco_flush_sco_data(xx);
p->state = SCO_ST_UNUSED;
- p->hci_handle = HCI_INVALID_HANDLE;
+ p->hci_handle = BTM_INVALID_HCI_HANDLE;
p->rem_bd_known = false;
p->esco.p_esco_cback = NULL; /* Deregister eSCO callback */
(*p->p_disc_cb)(xx);
- LOG_DEBUG("Disconnected SCO link handle:%hu reason:%s", hci_handle,
- hci_reason_code_text(reason).c_str());
- return true;
- }
- }
- return false;
-}
-
-void btm_sco_on_esco_connect_request(
- const RawAddress& bda, const bluetooth::types::ClassOfDevice& cod) {
- LOG_DEBUG("Remote ESCO connect request remote:%s cod:%s",
- PRIVATE_ADDRESS(bda), cod.ToString().c_str());
- btm_sco_conn_req(bda, cod.cod, BTM_LINK_TYPE_ESCO);
-}
-void btm_sco_on_sco_connect_request(
- const RawAddress& bda, const bluetooth::types::ClassOfDevice& cod) {
- LOG_DEBUG("Remote SCO connect request remote:%s cod:%s", PRIVATE_ADDRESS(bda),
- cod.ToString().c_str());
- btm_sco_conn_req(bda, cod.cod, BTM_LINK_TYPE_SCO);
-}
-
-void btm_sco_on_disconnected(uint16_t hci_handle, tHCI_REASON reason) {
- tSCO_CONN* p_sco = btm_cb.sco_cb.get_sco_connection_from_handle(hci_handle);
- if (p_sco == nullptr) {
- LOG_ERROR("Unable to find sco connection");
- return;
- }
-
- if (!p_sco->is_active()) {
- LOG_ERROR("Connection is not active handle:0x%04x reason:%s", hci_handle,
- hci_reason_code_text(reason).c_str());
- return;
- }
-
- if (p_sco->state == SCO_ST_LISTENING) {
- LOG_ERROR("Connection is in listening state handle:0x%04x reason:%s",
- hci_handle, hci_reason_code_text(reason).c_str());
- return;
+ return;
+ }
}
-
- const RawAddress bd_addr(p_sco->esco.data.bd_addr);
-
- p_sco->state = SCO_ST_UNUSED;
- p_sco->hci_handle = HCI_INVALID_HANDLE;
- p_sco->rem_bd_known = false;
- p_sco->esco.p_esco_cback = NULL; /* Deregister eSCO callback */
- (*p_sco->p_disc_cb)(btm_cb.sco_cb.get_index(p_sco));
- LOG_DEBUG("Disconnected SCO link handle:%hu reason:%s", hci_handle,
- hci_reason_code_text(reason).c_str());
- BTM_LogHistory(kBtmLogTag, bd_addr, "Disconnected",
- base::StringPrintf("handle:0x%04x reason:%s", hci_handle,
- hci_reason_code_text(reason).c_str()));
+#endif
}
/*******************************************************************************
@@ -937,6 +996,7 @@ void btm_sco_on_disconnected(uint16_t hci_handle, tHCI_REASON reason) {
*
******************************************************************************/
void btm_sco_acl_removed(const RawAddress* bda) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
uint16_t xx;
@@ -951,6 +1011,7 @@ void btm_sco_acl_removed(const RawAddress* bda) {
}
}
}
+#endif
}
/*******************************************************************************
@@ -964,6 +1025,7 @@ void btm_sco_acl_removed(const RawAddress* bda) {
*
******************************************************************************/
const RawAddress* BTM_ReadScoBdAddr(uint16_t sco_inx) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[sco_inx];
/* Validity check */
@@ -971,6 +1033,9 @@ const RawAddress* BTM_ReadScoBdAddr(uint16_t sco_inx) {
return &(p->esco.data.bd_addr);
else
return (NULL);
+#else
+ return (NULL);
+#endif
}
/*******************************************************************************
@@ -991,28 +1056,25 @@ const RawAddress* BTM_ReadScoBdAddr(uint16_t sco_inx) {
*
******************************************************************************/
tBTM_STATUS BTM_SetEScoMode(enh_esco_params_t* p_parms) {
- ASSERT_LOG(p_parms != nullptr, "eSCO parameters must have a value");
enh_esco_params_t* p_def = &btm_cb.sco_cb.def_esco_parms;
if (btm_cb.sco_cb.esco_supported) {
*p_def = *p_parms;
- LOG_DEBUG(
- "Setting eSCO mode parameters txbw:0x%08x rxbw:0x%08x max_lat:0x%04x"
- " pkt:0x%04x rtx_effort:0x%02x",
- p_def->transmit_bandwidth, p_def->receive_bandwidth,
- p_def->max_latency_ms, p_def->packet_types,
- p_def->retransmission_effort);
} else {
/* Load defaults for SCO only */
- *p_def = esco_parameters_for_codec(SCO_CODEC_CVSD_D1);
- LOG_WARN("eSCO not supported so setting SCO parameters instead");
- LOG_DEBUG(
- "Setting SCO mode parameters txbw:0x%08x rxbw:0x%08x max_lat:0x%04x"
- " pkt:0x%04x rtx_effort:0x%02x",
- p_def->transmit_bandwidth, p_def->receive_bandwidth,
- p_def->max_latency_ms, p_def->packet_types,
- p_def->retransmission_effort);
+ *p_def = esco_parameters_for_codec(ESCO_CODEC_CVSD);
+ p_def->packet_types &= BTM_SCO_LINK_ONLY_MASK;
+ p_def->retransmission_effort = ESCO_RETRANSMISSION_OFF;
+ p_def->max_latency_ms = 12;
+ BTM_TRACE_WARNING("%s: eSCO not supported", __func__);
}
+
+ BTM_TRACE_API(
+ "%s: txbw 0x%08x, rxbw 0x%08x, max_lat 0x%04x, "
+ "pkt 0x%04x, rtx effort 0x%02x",
+ __func__, p_def->transmit_bandwidth, p_def->receive_bandwidth,
+ p_def->max_latency_ms, p_def->packet_types, p_def->retransmission_effort);
+
return BTM_SUCCESS;
}
@@ -1033,10 +1095,7 @@ tBTM_STATUS BTM_SetEScoMode(enh_esco_params_t* p_parms) {
******************************************************************************/
tBTM_STATUS BTM_RegForEScoEvts(uint16_t sco_inx,
tBTM_ESCO_CBACK* p_esco_cback) {
- if (BTM_MAX_SCO_LINKS == 0) {
- return BTM_MODE_UNSUPPORTED;
- }
-
+#if (BTM_MAX_SCO_LINKS > 0)
if (!btm_cb.sco_cb.esco_supported) {
btm_cb.sco_cb.sco_db[sco_inx].esco.p_esco_cback = NULL;
return (BTM_MODE_UNSUPPORTED);
@@ -1048,6 +1107,9 @@ tBTM_STATUS BTM_RegForEScoEvts(uint16_t sco_inx,
return (BTM_SUCCESS);
}
return (BTM_ILLEGAL_VALUE);
+#else
+ return (BTM_MODE_UNSUPPORTED);
+#endif
}
/*******************************************************************************
@@ -1072,9 +1134,7 @@ tBTM_STATUS BTM_RegForEScoEvts(uint16_t sco_inx,
******************************************************************************/
tBTM_STATUS BTM_ChangeEScoLinkParms(uint16_t sco_inx,
tBTM_CHG_ESCO_PARAMS* p_parms) {
- if (BTM_MAX_SCO_LINKS == 0) {
- return BTM_WRONG_MODE;
- }
+#if (BTM_MAX_SCO_LINKS > 0)
/* Make sure sco handle is valid and on an active link */
if (sco_inx >= BTM_MAX_SCO_LINKS ||
@@ -1151,6 +1211,9 @@ tBTM_STATUS BTM_ChangeEScoLinkParms(uint16_t sco_inx,
}
return (BTM_CMD_STARTED);
+#else
+ return (BTM_WRONG_MODE);
+#endif
}
/*******************************************************************************
@@ -1173,11 +1236,29 @@ tBTM_STATUS BTM_ChangeEScoLinkParms(uint16_t sco_inx,
******************************************************************************/
void BTM_EScoConnRsp(uint16_t sco_inx, uint8_t hci_status,
enh_esco_params_t* p_parms) {
+#if (BTM_MAX_SCO_LINKS > 0)
if (sco_inx < BTM_MAX_SCO_LINKS &&
btm_cb.sco_cb.sco_db[sco_inx].state == SCO_ST_W4_CONN_RSP) {
btm_esco_conn_rsp(sco_inx, hci_status,
btm_cb.sco_cb.sco_db[sco_inx].esco.data.bd_addr, p_parms);
}
+#endif
+}
+
+/*******************************************************************************
+ *
+ * Function btm_read_def_esco_mode
+ *
+ * Description This function copies the current default esco settings into
+ * the return buffer.
+ *
+ * Returns tBTM_SCO_TYPE
+ *
+ ******************************************************************************/
+void btm_read_def_esco_mode(enh_esco_params_t* p_parms) {
+#if (BTM_MAX_SCO_LINKS > 0)
+ *p_parms = btm_cb.sco_cb.def_esco_parms;
+#endif
}
/*******************************************************************************
@@ -1193,6 +1274,7 @@ void BTM_EScoConnRsp(uint16_t sco_inx, uint8_t hci_status,
void btm_esco_proc_conn_chg(uint8_t status, uint16_t handle,
uint8_t tx_interval, uint8_t retrans_window,
uint16_t rx_pkt_len, uint16_t tx_pkt_len) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
tBTM_CHG_ESCO_EVT_DATA data;
uint16_t xx;
@@ -1219,6 +1301,7 @@ void btm_esco_proc_conn_chg(uint8_t status, uint16_t handle,
return;
}
}
+#endif
}
/*******************************************************************************
@@ -1232,12 +1315,14 @@ void btm_esco_proc_conn_chg(uint8_t status, uint16_t handle,
*
******************************************************************************/
bool btm_is_sco_active(uint16_t handle) {
+#if (BTM_MAX_SCO_LINKS > 0)
uint16_t xx;
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
for (xx = 0; xx < BTM_MAX_SCO_LINKS; xx++, p++) {
if (handle == p->hci_handle && p->state == SCO_ST_CONNECTED) return (true);
}
+#endif
return (false);
}
@@ -1251,6 +1336,7 @@ bool btm_is_sco_active(uint16_t handle) {
*
******************************************************************************/
uint8_t BTM_GetNumScoLinks(void) {
+#if (BTM_MAX_SCO_LINKS > 0)
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
uint16_t xx;
uint8_t num_scos = 0;
@@ -1263,17 +1349,17 @@ uint8_t BTM_GetNumScoLinks(void) {
case SCO_ST_DISCONNECTING:
case SCO_ST_PEND_UNPARK:
num_scos++;
- break;
- default:
- break;
}
}
return (num_scos);
+#else
+ return (0);
+#endif
}
/*******************************************************************************
*
- * Function BTM_IsScoActiveByBdaddr
+ * Function btm_is_sco_active_by_bdaddr
*
* Description This function is called to see if a SCO connection is active
* for a bd address.
@@ -1281,7 +1367,8 @@ uint8_t BTM_GetNumScoLinks(void) {
* Returns bool
*
******************************************************************************/
-bool BTM_IsScoActiveByBdaddr(const RawAddress& remote_bda) {
+bool btm_is_sco_active_by_bdaddr(const RawAddress& remote_bda) {
+#if (BTM_MAX_SCO_LINKS > 0)
uint8_t xx;
tSCO_CONN* p = &btm_cb.sco_cb.sco_db[0];
@@ -1291,6 +1378,7 @@ bool BTM_IsScoActiveByBdaddr(const RawAddress& remote_bda) {
return (true);
}
}
+#endif
return (false);
}
diff --git a/stack/btm/btm_sco.h b/stack/btm/btm_sco.h
deleted file mode 100644
index b6b0af1ab..000000000
--- a/stack/btm/btm_sco.h
+++ /dev/null
@@ -1,134 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include <string>
-
-#include "device/include/esco_parameters.h"
-#include "stack/include/btm_api_types.h"
-
-constexpr uint16_t kMaxScoLinks = static_cast<uint16_t>(BTM_MAX_SCO_LINKS);
-
-/* Define the structures needed by sco
- */
-
-typedef enum : uint16_t {
- SCO_ST_UNUSED = 0,
- SCO_ST_LISTENING = 1,
- SCO_ST_W4_CONN_RSP = 2,
- SCO_ST_CONNECTING = 3,
- SCO_ST_CONNECTED = 4,
- SCO_ST_DISCONNECTING = 5,
- SCO_ST_PEND_UNPARK = 6,
- SCO_ST_PEND_ROLECHANGE = 7,
- SCO_ST_PEND_MODECHANGE = 8,
-} tSCO_STATE;
-
-inline std::string sco_state_text(const tSCO_STATE& state) {
- switch (state) {
- case SCO_ST_UNUSED:
- return std::string("unused");
- case SCO_ST_LISTENING:
- return std::string("listening");
- case SCO_ST_W4_CONN_RSP:
- return std::string("connect_response");
- case SCO_ST_CONNECTING:
- return std::string("connecting");
- case SCO_ST_CONNECTED:
- return std::string("connected");
- case SCO_ST_DISCONNECTING:
- return std::string("disconnecting");
- case SCO_ST_PEND_UNPARK:
- return std::string("pending_unpark");
- case SCO_ST_PEND_ROLECHANGE:
- return std::string("pending_role_change");
- case SCO_ST_PEND_MODECHANGE:
- return std::string("pending_mode_change");
- }
-}
-
-typedef void(tBTM_SCO_IND_CBACK)(uint16_t sco_inx);
-
-/* Define the structure that contains (e)SCO data */
-typedef struct {
- tBTM_ESCO_CBACK* p_esco_cback; /* Callback for eSCO events */
- enh_esco_params_t setup;
- tBTM_ESCO_DATA data; /* Connection complete information */
- uint8_t hci_status;
-} tBTM_ESCO_INFO;
-
-/* Define the structure used for SCO Management
- */
-typedef struct {
- tBTM_ESCO_INFO esco; /* Current settings */
- tBTM_SCO_CB* p_conn_cb; /* Callback for when connected */
- tBTM_SCO_CB* p_disc_cb; /* Callback for when disconnect */
- tSCO_STATE state; /* The state of the SCO link */
-
- uint16_t hci_handle; /* HCI Handle */
- public:
- bool is_active() const { return state != SCO_ST_UNUSED; }
- uint16_t Handle() const { return hci_handle; }
-
- bool is_orig; /* true if the originator */
- bool rem_bd_known; /* true if remote BD addr known */
-
-} tSCO_CONN;
-
-/* SCO Management control block */
-typedef struct {
- tBTM_SCO_IND_CBACK* app_sco_ind_cb;
- tSCO_CONN sco_db[BTM_MAX_SCO_LINKS];
- enh_esco_params_t def_esco_parms;
- bool esco_supported; /* true if 1.2 cntlr AND supports eSCO links */
- esco_data_path_t sco_route; /* HCI, PCM, or TEST */
-
- tSCO_CONN* get_sco_connection_from_index(uint16_t index) {
- return (index < kMaxScoLinks) ? (&sco_db[index]) : nullptr;
- }
-
- tSCO_CONN* get_sco_connection_from_handle(uint16_t handle) {
- tSCO_CONN* p_sco = sco_db;
- for (uint16_t xx = 0; xx < kMaxScoLinks; xx++, p_sco++) {
- if (p_sco->hci_handle == handle) {
- return p_sco;
- }
- }
- return nullptr;
- }
-
- void Init() {
- def_esco_parms = esco_parameters_for_codec(ESCO_CODEC_CVSD_S3);
- sco_route = ESCO_DATA_PATH_PCM;
- }
-
- uint16_t get_index(const tSCO_CONN* p_sco) const {
- CHECK(p_sco != nullptr);
- const tSCO_CONN* p = sco_db;
- for (uint16_t xx = 0; xx < kMaxScoLinks; xx++, p++) {
- if (p_sco == p) {
- return xx;
- }
- }
- return 0xffff;
- }
-
-} tSCO_CB;
-
-extern void btm_sco_chk_pend_rolechange(uint16_t hci_handle);
-extern void btm_sco_disc_chk_pend_for_modechange(uint16_t hci_handle);
diff --git a/stack/btm/btm_sec.cc b/stack/btm/btm_sec.cc
index 50bd604b0..c4ce28f45 100644
--- a/stack/btm/btm_sec.cc
+++ b/stack/btm/btm_sec.cc
@@ -24,70 +24,55 @@
#define LOG_TAG "bt_btm_sec"
-#include "stack/btm/btm_sec.h"
-
-#include <base/strings/stringprintf.h>
#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
+#include <log/log.h>
+#include <stdarg.h>
+#include <stdio.h>
#include <string.h>
-#include "bt_types.h"
-#include "btif/include/btif_storage.h"
#include "common/metrics.h"
#include "common/time_util.h"
#include "device/include/controller.h"
-#include "hcimsgs.h"
-#include "l2c_api.h"
#include "main/shim/btm_api.h"
-#include "main/shim/dumpsys.h"
#include "main/shim/shim.h"
#include "osi/include/log.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/security_device_record.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/acl_hci_link_interface.h"
-#include "stack/include/btm_status.h"
-#include "stack/include/l2cap_security_interface.h"
-#include "stack/include/stack_metrics_logging.h"
-#include "stack/smp/smp_int.h"
-
-namespace {
-constexpr char kBtmLogTag[] = "SEC";
-
-}
+#include "bt_types.h"
+#include "bt_utils.h"
+#include "btif_storage.h"
+#include "btm_int.h"
+#include "btu.h"
+#include "hcimsgs.h"
+#include "l2c_int.h"
-extern tBTM_CB btm_cb;
+#include "gatt_int.h"
#define BTM_SEC_MAX_COLLISION_DELAY (5000)
-#define BTM_SEC_IS_SM4(sm) ((bool)(BTM_SM4_TRUE == ((sm)&BTM_SM4_TRUE)))
-#define BTM_SEC_IS_SM4_LEGACY(sm) ((bool)(BTM_SM4_KNOWN == ((sm)&BTM_SM4_TRUE)))
-#define BTM_SEC_IS_SM4_UNKNOWN(sm) \
- ((bool)(BTM_SM4_UNKNOWN == ((sm)&BTM_SM4_TRUE)))
-
-#define BTM_SEC_LE_MASK \
- (BTM_SEC_LE_AUTHENTICATED | BTM_SEC_LE_ENCRYPTED | \
- BTM_SEC_LE_LINK_KEY_KNOWN | BTM_SEC_LE_LINK_KEY_AUTHED)
+#ifdef APPL_AUTH_WRITE_EXCEPTION
+bool(APPL_AUTH_WRITE_EXCEPTION)(const RawAddress& bd_addr);
+#endif
-void btm_inq_stop_on_ssp(void);
extern void btm_ble_advertiser_notify_terminated_legacy(
uint8_t status, uint16_t connection_handle);
-extern bool btm_ble_init_pseudo_addr(tBTM_SEC_DEV_REC* p_dev_rec,
- const RawAddress& new_pseudo_addr);
extern void bta_dm_remove_device(const RawAddress& bd_addr);
extern void bta_dm_process_remove_device(const RawAddress& bd_addr);
-extern void btm_inq_clear_ssp(void);
-extern void HACK_acl_check_sm4(tBTM_SEC_DEV_REC& p_dev_rec);
/*******************************************************************************
* L O C A L F U N C T I O N P R O T O T Y P E S *
******************************************************************************/
tBTM_SEC_SERV_REC* btm_sec_find_first_serv(bool is_originator, uint16_t psm);
+static tBTM_SEC_SERV_REC* btm_sec_find_next_serv(tBTM_SEC_SERV_REC* p_cur);
+static tBTM_SEC_SERV_REC* btm_sec_find_mx_serv(uint8_t is_originator,
+ uint16_t psm,
+ uint32_t mx_proto_id,
+ uint32_t mx_chan_id);
static bool btm_sec_start_get_name(tBTM_SEC_DEV_REC* p_dev_rec);
static void btm_sec_start_authentication(tBTM_SEC_DEV_REC* p_dev_rec);
+static void btm_sec_start_encryption(tBTM_SEC_DEV_REC* p_dev_rec);
static void btm_sec_collision_timeout(void* data);
static void btm_restore_mode(void);
static void btm_sec_pairing_timeout(void* data);
@@ -106,13 +91,27 @@ static void btm_sec_bond_cancel_complete(void);
static void btm_send_link_key_notif(tBTM_SEC_DEV_REC* p_dev_rec);
static bool btm_sec_check_prefetch_pin(tBTM_SEC_DEV_REC* p_dev_rec);
+static uint8_t btm_sec_start_authorization(tBTM_SEC_DEV_REC* p_dev_rec);
+bool btm_sec_are_all_trusted(uint32_t p_mask[]);
+
static tBTM_STATUS btm_sec_send_hci_disconnect(tBTM_SEC_DEV_REC* p_dev_rec,
- tHCI_STATUS reason,
+ uint8_t reason,
uint16_t conn_handle);
+uint8_t btm_sec_start_role_switch(tBTM_SEC_DEV_REC* p_dev_rec);
tBTM_SEC_DEV_REC* btm_sec_find_dev_by_sec_state(uint8_t state);
+static bool btm_sec_set_security_level(CONNECTION_TYPE conn_type,
+ const char* p_name, uint8_t service_id,
+ uint16_t sec_level, uint16_t psm,
+ uint32_t mx_proto_id,
+ uint32_t mx_chan_id);
+
static bool btm_dev_authenticated(tBTM_SEC_DEV_REC* p_dev_rec);
static bool btm_dev_encrypted(tBTM_SEC_DEV_REC* p_dev_rec);
+static bool btm_dev_authorized(tBTM_SEC_DEV_REC* p_dev_rec);
+static bool btm_serv_trusted(tBTM_SEC_DEV_REC* p_dev_rec,
+ tBTM_SEC_SERV_REC* p_serv_rec);
+static bool btm_sec_is_serv_level0(uint16_t psm);
static uint16_t btm_sec_set_serv_level4_flags(uint16_t cur_security,
bool is_originator);
@@ -126,6 +125,7 @@ static void btm_sec_check_pending_enc_req(tBTM_SEC_DEV_REC* p_dev_rec,
uint8_t encr_enable);
static bool btm_sec_use_smp_br_chnl(tBTM_SEC_DEV_REC* p_dev_rec);
+static bool btm_sec_is_master(tBTM_SEC_DEV_REC* p_dev_rec);
/* true - authenticated link key is possible */
static const bool btm_sec_io_map[BTM_IO_CAP_MAX][BTM_IO_CAP_MAX] = {
@@ -139,21 +139,6 @@ static const bool btm_sec_io_map[BTM_IO_CAP_MAX][BTM_IO_CAP_MAX] = {
/* BTM_IO_CAP_IN 2 KeyboardOnly */
/* BTM_IO_CAP_NONE 3 NoInputNoOutput */
-static void NotifyBondingChange(tBTM_SEC_DEV_REC& p_dev_rec,
- tHCI_STATUS status) {
- if (btm_cb.api.p_auth_complete_callback != nullptr) {
- (*btm_cb.api.p_auth_complete_callback)(
- p_dev_rec.bd_addr, static_cast<uint8_t*>(p_dev_rec.dev_class),
- p_dev_rec.sec_bd_name, status);
- }
-}
-
-void NotifyBondingCanceled(tBTM_STATUS btm_status) {
- if (btm_cb.api.p_bond_cancel_cmpl_callback) {
- btm_cb.api.p_bond_cancel_cmpl_callback(BTM_SUCCESS);
- }
-}
-
/*******************************************************************************
*
* Function btm_dev_authenticated
@@ -188,6 +173,22 @@ static bool btm_dev_encrypted(tBTM_SEC_DEV_REC* p_dev_rec) {
/*******************************************************************************
*
+ * Function btm_dev_authorized
+ *
+ * Description check device is authorized
+ *
+ * Returns bool true or false
+ *
+ ******************************************************************************/
+static bool btm_dev_authorized(tBTM_SEC_DEV_REC* p_dev_rec) {
+ if (p_dev_rec->sec_flags & BTM_SEC_AUTHORIZED) {
+ return (true);
+ }
+ return (false);
+}
+
+/*******************************************************************************
+ *
* Function btm_dev_16_digit_authenticated
*
* Description check device is authenticated by using 16 digit pin or MITM
@@ -205,6 +206,24 @@ static bool btm_dev_16_digit_authenticated(tBTM_SEC_DEV_REC* p_dev_rec) {
/*******************************************************************************
*
+ * Function btm_serv_trusted
+ *
+ * Description check service is trusted
+ *
+ * Returns bool true or false
+ *
+ ******************************************************************************/
+static bool btm_serv_trusted(tBTM_SEC_DEV_REC* p_dev_rec,
+ tBTM_SEC_SERV_REC* p_serv_rec) {
+ if (BTM_SEC_IS_SERVICE_TRUSTED(p_dev_rec->trusted_mask,
+ p_serv_rec->service_id)) {
+ return (true);
+ }
+ return (false);
+}
+
+/*******************************************************************************
+ *
* Function BTM_SecRegister
*
* Description Application manager calls this function to register for
@@ -222,7 +241,7 @@ bool BTM_SecRegister(const tBTM_APPL_INFO* p_cb_info) {
BTM_TRACE_EVENT("%s application registered", __func__);
- LOG_INFO("%s p_cb_info->p_le_callback == 0x%p", __func__,
+ LOG_INFO(LOG_TAG, "%s p_cb_info->p_le_callback == 0x%p", __func__,
p_cb_info->p_le_callback);
if (p_cb_info->p_le_callback) {
BTM_TRACE_EVENT("%s SMP_Register( btm_proc_smp_cback )", __func__);
@@ -233,11 +252,11 @@ bool BTM_SecRegister(const tBTM_APPL_INFO* p_cb_info) {
btm_ble_reset_id();
}
} else {
- LOG_WARN("%s p_cb_info->p_le_callback == NULL", __func__);
+ LOG_WARN(LOG_TAG, "%s p_cb_info->p_le_callback == NULL", __func__);
}
btm_cb.api = *p_cb_info;
- LOG_INFO("%s btm_cb.api.p_le_callback = 0x%p ", __func__,
+ LOG_INFO(LOG_TAG, "%s btm_cb.api.p_le_callback = 0x%p ", __func__,
btm_cb.api.p_le_callback);
BTM_TRACE_EVENT("%s application registered", __func__);
return (true);
@@ -310,30 +329,6 @@ bool BTM_GetSecurityFlags(const RawAddress& bd_addr, uint8_t* p_sec_flags) {
return (false);
}
-bool BTM_IsEncrypted(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- uint8_t flags = 0;
- BTM_GetSecurityFlagsByTransport(bd_addr, &flags, transport);
- return (flags & BTM_SEC_FLAG_ENCRYPTED) != 0;
-}
-
-bool BTM_IsLinkKeyAuthed(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- uint8_t flags = 0;
- BTM_GetSecurityFlagsByTransport(bd_addr, &flags, transport);
- return (flags & BTM_SEC_FLAG_LKEY_AUTHED) != 0;
-}
-
-bool BTM_IsLinkKeyKnown(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- uint8_t flags = 0;
- BTM_GetSecurityFlagsByTransport(bd_addr, &flags, transport);
- return (flags & BTM_SEC_FLAG_LKEY_KNOWN) != 0;
-}
-
-bool BTM_IsAuthenticated(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- uint8_t flags = 0;
- BTM_GetSecurityFlagsByTransport(bd_addr, &flags, transport);
- return (flags & BTM_SEC_AUTHENTICATED) != 0;
-}
-
/*******************************************************************************
*
* Function BTM_GetSecurityFlagsByTransport
@@ -386,6 +381,29 @@ void BTM_SetPinType(uint8_t pin_type, PIN_CODE pin_code, uint8_t pin_code_len) {
memcpy(btm_cb.cfg.pin_code, pin_code, pin_code_len);
}
+/*******************************************************************************
+ *
+ * Function BTM_SetPairableMode
+ *
+ * Description Enable or disable pairing
+ *
+ * Parameters allow_pairing - (true or false) whether or not the device
+ * allows pairing.
+ * connect_only_paired - (true or false) whether or not to
+ * only allow paired devices to connect.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void BTM_SetPairableMode(bool allow_pairing, bool connect_only_paired) {
+ BTM_TRACE_API(
+ "BTM_SetPairableMode() allow_pairing: %u connect_only_paired: %u",
+ allow_pairing, connect_only_paired);
+
+ btm_cb.pairing_disabled = !allow_pairing;
+ btm_cb.connect_only_paired = connect_only_paired;
+}
+
#define BTM_NO_AVAIL_SEC_SERVICES ((uint16_t)0xffff)
/*******************************************************************************
@@ -397,7 +415,7 @@ void BTM_SetPinType(uint8_t pin_type, PIN_CODE pin_code, uint8_t pin_code_len) {
* Parameters: is_originator - true if originating the connection
* p_name - Name of the service relevant only if
* authorization will show this name to user.
- * Ignored if BT_MAX_SERVICE_NAME_LEN is 0.
+ * Ignored if BTM_SEC_SERVICE_NAME_LEN is 0.
* service_id - service ID for the service passed to
* authorization callback
* sec_level - bit mask of the security features
@@ -411,10 +429,41 @@ void BTM_SetPinType(uint8_t pin_type, PIN_CODE pin_code, uint8_t pin_code_len) {
bool BTM_SetSecurityLevel(bool is_originator, const char* p_name,
uint8_t service_id, uint16_t sec_level, uint16_t psm,
uint32_t mx_proto_id, uint32_t mx_chan_id) {
+ return (btm_sec_set_security_level(is_originator, p_name, service_id,
+ sec_level, psm, mx_proto_id, mx_chan_id));
+}
+
+/*******************************************************************************
+ *
+ * Function btm_sec_set_security_level
+ *
+ * Description Register service security level with Security Manager
+ *
+ * Parameters: conn_type - true if originating the connection
+ * p_name - Name of the service relevant only if
+ * authorization will show this name to user.
+ * Ignored if BTM_SEC_SERVICE_NAME_LEN is 0.
+ * service_id - service ID for the service passed to
+ * authorization callback
+ * sec_level - bit mask of the security features
+ * psm - L2CAP PSM
+ * mx_proto_id - protocol ID of multiplexing proto below
+ * mx_chan_id - channel ID of multiplexing proto below
+ *
+ * Returns true if registered OK, else false
+ *
+ ******************************************************************************/
+static bool btm_sec_set_security_level(CONNECTION_TYPE conn_type,
+ const char* p_name, uint8_t service_id,
+ uint16_t sec_level, uint16_t psm,
+ uint32_t mx_proto_id,
+ uint32_t mx_chan_id) {
tBTM_SEC_SERV_REC* p_srec;
uint16_t index;
uint16_t first_unused_record = BTM_NO_AVAIL_SEC_SERVICES;
bool record_allocated = false;
+ bool is_originator;
+ is_originator = conn_type;
BTM_TRACE_API("%s : sec: 0x%x", __func__, sec_level);
@@ -426,14 +475,20 @@ bool BTM_SetSecurityLevel(bool is_originator, const char* p_name,
for (index = 0; index < BTM_SEC_MAX_SERVICE_RECORDS; index++, p_srec++) {
/* Check if there is already a record for this service */
if (p_srec->security_flags & BTM_SEC_IN_USE) {
+#if BTM_SEC_SERVICE_NAME_LEN > 0
if (p_srec->psm == psm && p_srec->mx_proto_id == mx_proto_id &&
service_id == p_srec->service_id && p_name &&
(!strncmp(p_name, (char*)p_srec->orig_service_name,
/* strlcpy replaces end char with termination char*/
- BT_MAX_SERVICE_NAME_LEN - 1) ||
+ BTM_SEC_SERVICE_NAME_LEN - 1) ||
!strncmp(p_name, (char*)p_srec->term_service_name,
/* strlcpy replaces end char with termination char*/
- BT_MAX_SERVICE_NAME_LEN - 1))) {
+ BTM_SEC_SERVICE_NAME_LEN - 1)))
+#else
+ if (p_srec->psm == psm && p_srec->mx_proto_id == mx_proto_id &&
+ service_id == p_srec->service_id)
+#endif
+ {
record_allocated = true;
break;
}
@@ -465,20 +520,26 @@ bool BTM_SetSecurityLevel(bool is_originator, const char* p_name,
if (is_originator) {
p_srec->orig_mx_chan_id = mx_chan_id;
+#if BTM_SEC_SERVICE_NAME_LEN > 0
strlcpy((char*)p_srec->orig_service_name, p_name,
- BT_MAX_SERVICE_NAME_LEN + 1);
- /* clear out the old setting, just in case it exists */
+ BTM_SEC_SERVICE_NAME_LEN + 1);
+#endif
+/* clear out the old setting, just in case it exists */
{
- p_srec->security_flags &=
- ~(BTM_SEC_OUT_ENCRYPT | BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_MITM);
+ p_srec->security_flags &= ~(
+ BTM_SEC_OUT_AUTHORIZE | BTM_SEC_OUT_ENCRYPT |
+ BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_MITM | BTM_SEC_FORCE_MASTER |
+ BTM_SEC_ATTEMPT_MASTER | BTM_SEC_FORCE_SLAVE | BTM_SEC_ATTEMPT_SLAVE);
}
/* Parameter validation. Originator should not set requirements for
* incoming connections */
- sec_level &= ~(BTM_SEC_IN_ENCRYPT | BTM_SEC_IN_AUTHENTICATE |
- BTM_SEC_IN_MITM | BTM_SEC_IN_MIN_16_DIGIT_PIN);
+ sec_level &=
+ ~(BTM_SEC_IN_AUTHORIZE | BTM_SEC_IN_ENCRYPT | BTM_SEC_IN_AUTHENTICATE |
+ BTM_SEC_IN_MITM | BTM_SEC_IN_MIN_16_DIGIT_PIN);
if (btm_cb.security_mode == BTM_SEC_MODE_SP ||
+ btm_cb.security_mode == BTM_SEC_MODE_SP_DEBUG ||
btm_cb.security_mode == BTM_SEC_MODE_SC) {
if (sec_level & BTM_SEC_OUT_AUTHENTICATE) sec_level |= BTM_SEC_OUT_MITM;
}
@@ -486,27 +547,32 @@ bool BTM_SetSecurityLevel(bool is_originator, const char* p_name,
/* Make sure the authenticate bit is set, when encrypt bit is set */
if (sec_level & BTM_SEC_OUT_ENCRYPT) sec_level |= BTM_SEC_OUT_AUTHENTICATE;
- /* outgoing connections usually set the security level right before
- * the connection is initiated.
- * set it to be the outgoing service */
- btm_cb.p_out_serv = p_srec;
+/* outgoing connections usually set the security level right before
+ * the connection is initiated.
+ * set it to be the outgoing service */
+ btm_cb.p_out_serv = p_srec;
} else {
p_srec->term_mx_chan_id = mx_chan_id;
+#if BTM_SEC_SERVICE_NAME_LEN > 0
strlcpy((char*)p_srec->term_service_name, p_name,
- BT_MAX_SERVICE_NAME_LEN + 1);
- /* clear out the old setting, just in case it exists */
+ BTM_SEC_SERVICE_NAME_LEN + 1);
+#endif
+/* clear out the old setting, just in case it exists */
{
p_srec->security_flags &=
- ~(BTM_SEC_IN_ENCRYPT | BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_MITM |
- BTM_SEC_IN_MIN_16_DIGIT_PIN);
+ ~(BTM_SEC_IN_AUTHORIZE | BTM_SEC_IN_ENCRYPT |
+ BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_MITM | BTM_SEC_FORCE_MASTER |
+ BTM_SEC_ATTEMPT_MASTER | BTM_SEC_FORCE_SLAVE |
+ BTM_SEC_ATTEMPT_SLAVE | BTM_SEC_IN_MIN_16_DIGIT_PIN);
}
/* Parameter validation. Acceptor should not set requirements for outgoing
* connections */
- sec_level &=
- ~(BTM_SEC_OUT_ENCRYPT | BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_MITM);
+ sec_level &= ~(BTM_SEC_OUT_AUTHORIZE | BTM_SEC_OUT_ENCRYPT |
+ BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_MITM);
if (btm_cb.security_mode == BTM_SEC_MODE_SP ||
+ btm_cb.security_mode == BTM_SEC_MODE_SP_DEBUG ||
btm_cb.security_mode == BTM_SEC_MODE_SC) {
if (sec_level & BTM_SEC_IN_AUTHENTICATE) sec_level |= BTM_SEC_IN_MITM;
}
@@ -517,11 +583,15 @@ bool BTM_SetSecurityLevel(bool is_originator, const char* p_name,
p_srec->security_flags |= (uint16_t)(sec_level | BTM_SEC_IN_USE);
- LOG_DEBUG(
- "[%d]: id:%d, is_orig:%s psm:0x%04x proto_id:%d chan_id:%d"
- " : sec:0x%x service_name:[%s] (up to %d chars saved)",
- index, service_id, logbool(is_originator).c_str(), psm, mx_proto_id,
- mx_chan_id, p_srec->security_flags, p_name, BT_MAX_SERVICE_NAME_LEN);
+ BTM_TRACE_API(
+ "BTM_SEC_REG[%d]: id %d, is_orig %d, psm 0x%04x, proto_id %d, chan_id %d",
+ index, service_id, is_originator, psm, mx_proto_id, mx_chan_id);
+
+#if BTM_SEC_SERVICE_NAME_LEN > 0
+ BTM_TRACE_API(
+ " : sec: 0x%x, service name [%s] (up to %d chars saved)",
+ p_srec->security_flags, p_name, BTM_SEC_SERVICE_NAME_LEN);
+#endif
return (record_allocated);
}
@@ -565,7 +635,7 @@ uint8_t BTM_SecClrService(uint8_t service_id) {
/*******************************************************************************
*
- * Function BTM_SecClrServiceByPsm
+ * Function btm_sec_clr_service_by_psm
*
* Description Removes specified service record from the security database.
* All service records with the specified psm are removed.
@@ -579,7 +649,7 @@ uint8_t BTM_SecClrService(uint8_t service_id) {
* Returns Number of records that were freed.
*
******************************************************************************/
-uint8_t BTM_SecClrServiceByPsm(uint16_t psm) {
+uint8_t btm_sec_clr_service_by_psm(uint16_t psm) {
tBTM_SEC_SERV_REC* p_srec = &btm_cb.sec_serv_rec[0];
uint8_t num_freed = 0;
int i;
@@ -592,13 +662,45 @@ uint8_t BTM_SecClrServiceByPsm(uint16_t psm) {
num_freed++;
}
}
- BTM_TRACE_API("BTM_SecClrServiceByPsm psm:0x%x num_freed:%d", psm, num_freed);
+ BTM_TRACE_API("btm_sec_clr_service_by_psm psm:0x%x num_freed:%d", psm,
+ num_freed);
return (num_freed);
}
/*******************************************************************************
*
+ * Function btm_sec_clr_temp_auth_service
+ *
+ * Description Removes specified device record's temporary authorization
+ * flag from the security database.
+ *
+ * Parameters Device address to be cleared
+ *
+ * Returns void.
+ *
+ ******************************************************************************/
+void btm_sec_clr_temp_auth_service(const RawAddress& bda) {
+ tBTM_SEC_DEV_REC* p_dev_rec;
+
+ p_dev_rec = btm_find_dev(bda);
+ if (p_dev_rec == NULL) {
+ BTM_TRACE_WARNING("btm_sec_clr_temp_auth_service() - no dev CB");
+ return;
+ }
+
+ /* Reset the temporary authorized flag so that next time (untrusted) service
+ * is accessed autorization will take place */
+ if (p_dev_rec->last_author_service_id != BTM_SEC_NO_LAST_SERVICE_ID &&
+ p_dev_rec->p_cur_service) {
+ VLOG(1) << __func__ << " clearing device: " << bda;
+
+ p_dev_rec->last_author_service_id = BTM_SEC_NO_LAST_SERVICE_ID;
+ }
+}
+
+/*******************************************************************************
+ *
* Function BTM_PINCodeReply
*
* Description This function is called after Security Manager submitted
@@ -610,10 +712,12 @@ uint8_t BTM_SecClrServiceByPsm(uint16_t psm) {
* if success
* pin_len - length in bytes of the PIN Code
* p_pin - pointer to array with the PIN Code
+ * trusted_mask - bitwise OR of trusted services
+ * (array of uint32_t)
*
******************************************************************************/
void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res, uint8_t pin_len,
- uint8_t* p_pin) {
+ uint8_t* p_pin, uint32_t trusted_mask[]) {
tBTM_SEC_DEV_REC* p_dev_rec;
BTM_TRACE_API(
@@ -652,7 +756,7 @@ void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res, uint8_t pin_len,
/* use BTM_PAIR_STATE_WAIT_AUTH_COMPLETE to report authentication failed
* event */
btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
- acl_set_disconnect_reason(HCI_ERR_HOST_REJECT_SECURITY);
+ btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
btsnd_hcic_pin_code_neg_reply(bd_addr);
} else {
@@ -661,6 +765,8 @@ void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res, uint8_t pin_len,
}
return;
}
+ if (trusted_mask)
+ BTM_SEC_COPY_TRUSTED_DEVICE(trusted_mask, p_dev_rec->trusted_mask);
p_dev_rec->sec_flags |= BTM_SEC_LINK_KEY_AUTHED;
p_dev_rec->pin_code_length = pin_len;
if (pin_len >= 16) {
@@ -668,16 +774,19 @@ void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res, uint8_t pin_len,
}
if ((btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD) &&
- (p_dev_rec->hci_handle == HCI_INVALID_HANDLE) &&
+ (p_dev_rec->hci_handle == BTM_SEC_INVALID_HANDLE) &&
(!btm_cb.security_mode_changed)) {
/* This is start of the dedicated bonding if local device is 2.0 */
btm_cb.pin_code_len = pin_len;
memcpy(btm_cb.pin_code, p_pin, pin_len);
btm_cb.security_mode_changed = true;
- btsnd_hcic_write_auth_enable(true);
+#ifdef APPL_AUTH_WRITE_EXCEPTION
+ if (!(APPL_AUTH_WRITE_EXCEPTION)(p_dev_rec->bd_addr))
+#endif
+ btsnd_hcic_write_auth_enable(true);
- acl_set_disconnect_reason(HCI_ERR_UNDEFINED);
+ btm_cb.acl_disc_reason = 0xff;
/* if we rejected incoming connection request, we have to wait
* HCI_Connection_Complete event */
@@ -701,13 +810,16 @@ void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res, uint8_t pin_len,
btm_sec_change_pairing_state(BTM_PAIR_STATE_IDLE);
p_dev_rec->sec_flags &= ~BTM_SEC_LINK_KEY_AUTHED;
- NotifyBondingChange(*p_dev_rec, HCI_ERR_AUTH_FAILURE);
+ if (btm_cb.api.p_auth_complete_callback)
+ (*btm_cb.api.p_auth_complete_callback)(
+ p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
+ HCI_ERR_AUTH_FAILURE);
}
return;
}
btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
- acl_set_disconnect_reason(HCI_SUCCESS);
+ btm_cb.acl_disc_reason = HCI_SUCCESS;
btsnd_hcic_pin_code_req_reply(bd_addr, pin_len, p_pin);
}
@@ -721,14 +833,19 @@ void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res, uint8_t pin_len,
* Parameters: bd_addr - Address of the device to bond
* pin_len - length in bytes of the PIN Code
* p_pin - pointer to array with the PIN Code
+ * trusted_mask - bitwise OR of trusted services
+ * (array of uint32_t)
*
* Note: After 2.1 parameters are not used and preserved here not to change API
******************************************************************************/
tBTM_STATUS btm_sec_bond_by_transport(const RawAddress& bd_addr,
tBT_TRANSPORT transport, uint8_t pin_len,
- uint8_t* p_pin) {
+ uint8_t* p_pin, uint32_t trusted_mask[]) {
tBTM_SEC_DEV_REC* p_dev_rec;
tBTM_STATUS status;
+ uint8_t* p_features;
+ uint8_t ii;
+ tACL_CONN* p = btm_bda_to_acl(bd_addr, transport);
VLOG(1) << __func__ << " BDA: " << bd_addr;
BTM_TRACE_DEBUG("%s: Transport used %d, bd_addr=%s", __func__, transport,
@@ -754,10 +871,10 @@ tBTM_STATUS btm_sec_bond_by_transport(const RawAddress& bd_addr,
BTM_TRACE_DEBUG("before update sec_flags=0x%x", p_dev_rec->sec_flags);
/* Finished if connection is active and already paired */
- if (((p_dev_rec->hci_handle != HCI_INVALID_HANDLE) &&
+ if (((p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE) &&
transport == BT_TRANSPORT_BR_EDR &&
(p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED)) ||
- ((p_dev_rec->ble_hci_handle != HCI_INVALID_HANDLE) &&
+ ((p_dev_rec->ble_hci_handle != BTM_SEC_INVALID_HANDLE) &&
transport == BT_TRANSPORT_LE &&
(p_dev_rec->sec_flags & BTM_SEC_LE_AUTHENTICATED))) {
BTM_TRACE_WARNING("BTM_SecBond -> Already Paired");
@@ -781,9 +898,8 @@ tBTM_STATUS btm_sec_bond_by_transport(const RawAddress& bd_addr,
p_dev_rec->security_required = BTM_SEC_OUT_AUTHENTICATE;
p_dev_rec->is_originator = true;
-
- BTM_LogHistory(kBtmLogTag, bd_addr, "Bonding initiated",
- bt_transport_text(transport));
+ if (trusted_mask)
+ BTM_SEC_COPY_TRUSTED_DEVICE(trusted_mask, p_dev_rec->trusted_mask);
if (transport == BT_TRANSPORT_LE) {
btm_ble_init_pseudo_addr(p_dev_rec, bd_addr);
@@ -818,6 +934,14 @@ tBTM_STATUS btm_sec_bond_by_transport(const RawAddress& bd_addr,
}
}
+ for (ii = 0; ii <= HCI_EXT_FEATURES_PAGE_MAX; ii++) {
+ p_features = p_dev_rec->feature_pages[ii];
+ BTM_TRACE_EVENT(" remote_features page[%1d] = %02x-%02x-%02x-%02x", ii,
+ p_features[0], p_features[1], p_features[2], p_features[3]);
+ BTM_TRACE_EVENT(" %02x-%02x-%02x-%02x",
+ p_features[4], p_features[5], p_features[6], p_features[7]);
+ }
+
BTM_TRACE_EVENT("BTM_SecBond: Remote sm4: 0x%x HCI Handle: 0x%04x",
p_dev_rec->sm4, p_dev_rec->hci_handle);
@@ -826,7 +950,7 @@ tBTM_STATUS btm_sec_bond_by_transport(const RawAddress& bd_addr,
#endif
/* If connection already exists... */
- if (BTM_IsAclConnectionUpAndHandleValid(bd_addr, transport)) {
+ if (p && p->hci_handle != BTM_SEC_INVALID_HANDLE) {
btm_sec_start_authentication(p_dev_rec);
btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_PIN_REQ);
@@ -842,6 +966,7 @@ tBTM_STATUS btm_sec_bond_by_transport(const RawAddress& bd_addr,
if (btm_sec_check_prefetch_pin(p_dev_rec)) return (BTM_CMD_STARTED);
}
if ((btm_cb.security_mode == BTM_SEC_MODE_SP ||
+ btm_cb.security_mode == BTM_SEC_MODE_SP_DEBUG ||
btm_cb.security_mode == BTM_SEC_MODE_SC) &&
BTM_SEC_IS_SM4_UNKNOWN(p_dev_rec->sm4)) {
/* local is 2.1 and peer is unknown */
@@ -886,15 +1011,17 @@ tBTM_STATUS btm_sec_bond_by_transport(const RawAddress& bd_addr,
* transport - doing SSP over BR/EDR or SMP over LE
* pin_len - length in bytes of the PIN Code
* p_pin - pointer to array with the PIN Code
+ * trusted_mask - bitwise OR of trusted services
+ * (array of uint32_t)
*
* Note: After 2.1 parameters are not used and preserved here not to change API
******************************************************************************/
tBTM_STATUS BTM_SecBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type,
- uint8_t pin_len, uint8_t* p_pin) {
+ tBT_TRANSPORT transport, uint8_t pin_len,
+ uint8_t* p_pin, uint32_t trusted_mask[]) {
if (bluetooth::shim::is_gd_shim_enabled()) {
- return bluetooth::shim::BTM_SecBond(bd_addr, addr_type, transport,
- device_type);
+ return bluetooth::shim::BTM_SecBond(bd_addr, addr_type, transport, pin_len,
+ p_pin, trusted_mask);
}
if (transport == BT_TRANSPORT_INVALID)
@@ -909,7 +1036,8 @@ tBTM_STATUS BTM_SecBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
(dev_type & BT_DEVICE_TYPE_BREDR) == 0)) {
return BTM_ILLEGAL_ACTION;
}
- return btm_sec_bond_by_transport(bd_addr, transport, pin_len, p_pin);
+ return btm_sec_bond_by_transport(bd_addr, transport, pin_len, p_pin,
+ trusted_mask);
}
/*******************************************************************************
@@ -961,7 +1089,7 @@ tBTM_STATUS BTM_SecBondCancel(const RawAddress& bd_addr) {
if ((btm_cb.pairing_state != BTM_PAIR_STATE_IDLE) &&
(btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)) {
/* If the HCI link is up */
- if (p_dev_rec->hci_handle != HCI_INVALID_HANDLE) {
+ if (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE) {
/* If some other thread disconnecting, we do not send second command */
if ((p_dev_rec->sec_state == BTM_SEC_STATE_DISCONNECTING) ||
(p_dev_rec->sec_state == BTM_SEC_STATE_DISCONNECTING_BOTH))
@@ -1046,21 +1174,16 @@ tBTM_LINK_KEY_TYPE BTM_SecGetDeviceLinkKeyType(const RawAddress& bd_addr) {
******************************************************************************/
tBTM_STATUS BTM_SetEncryption(const RawAddress& bd_addr,
tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback, void* p_ref_data,
+ tBTM_SEC_CBACK* p_callback, void* p_ref_data,
tBTM_BLE_SEC_ACT sec_act) {
- if (bluetooth::shim::is_gd_shim_enabled()) {
- return bluetooth::shim::BTM_SetEncryption(bd_addr, transport, p_callback,
- p_ref_data, sec_act);
- }
-
- tBTM_STATUS rc = BTM_SUCCESS;
+ tBTM_STATUS rc = 0;
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
if (!p_dev_rec ||
(transport == BT_TRANSPORT_BR_EDR &&
- p_dev_rec->hci_handle == HCI_INVALID_HANDLE) ||
+ p_dev_rec->hci_handle == BTM_SEC_INVALID_HANDLE) ||
(transport == BT_TRANSPORT_LE &&
- p_dev_rec->ble_hci_handle == HCI_INVALID_HANDLE)) {
+ p_dev_rec->ble_hci_handle == BTM_SEC_INVALID_HANDLE)) {
/* Connection should be up and runnning */
BTM_TRACE_WARNING("Security Manager: BTM_SetEncryption not connected");
@@ -1108,9 +1231,9 @@ tBTM_STATUS BTM_SetEncryption(const RawAddress& bd_addr,
p_dev_rec->security_required, p_dev_rec, p_callback);
if (transport == BT_TRANSPORT_LE) {
- if (BTM_IsAclConnectionUp(bd_addr, BT_TRANSPORT_LE)) {
- rc = btm_ble_set_encryption(bd_addr, sec_act,
- L2CA_GetBleConnRole(bd_addr));
+ tACL_CONN* p = btm_bda_to_acl(bd_addr, transport);
+ if (p) {
+ rc = btm_ble_set_encryption(bd_addr, sec_act, p->link_role);
} else {
rc = BTM_WRONG_MODE;
BTM_TRACE_WARNING("%s: cannot call btm_ble_set_encryption, p is NULL",
@@ -1135,44 +1258,33 @@ tBTM_STATUS BTM_SetEncryption(const RawAddress& bd_addr,
return (rc);
}
-bool BTM_SecIsSecurityPending(const RawAddress& bd_addr) {
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
- return p_dev_rec && (p_dev_rec->sec_state == BTM_SEC_STATE_ENCRYPTING ||
- p_dev_rec->sec_state == BTM_SEC_STATE_AUTHENTICATING);
-}
-
/*******************************************************************************
* disconnect the ACL link, if it's not done yet.
******************************************************************************/
static tBTM_STATUS btm_sec_send_hci_disconnect(tBTM_SEC_DEV_REC* p_dev_rec,
- tHCI_STATUS reason,
+ uint8_t reason,
uint16_t conn_handle) {
- const tSECURITY_STATE old_state =
- static_cast<tSECURITY_STATE>(p_dev_rec->sec_state);
- const tBTM_STATUS status = BTM_CMD_STARTED;
+ uint8_t old_state = p_dev_rec->sec_state;
+ tBTM_STATUS status = BTM_CMD_STARTED;
+
+ BTM_TRACE_EVENT("btm_sec_send_hci_disconnect: handle:0x%x, reason=0x%x",
+ conn_handle, reason);
/* send HCI_Disconnect on a transport only once */
switch (old_state) {
case BTM_SEC_STATE_DISCONNECTING:
- if (conn_handle == p_dev_rec->hci_handle) {
- // Already sent classic disconnect
- return status;
- }
- // Prepare to send disconnect on le transport
+ if (conn_handle == p_dev_rec->hci_handle) return status;
+
p_dev_rec->sec_state = BTM_SEC_STATE_DISCONNECTING_BOTH;
break;
case BTM_SEC_STATE_DISCONNECTING_BLE:
- if (conn_handle == p_dev_rec->ble_hci_handle) {
- // Already sent ble disconnect
- return status;
- }
- // Prepare to send disconnect on classic transport
+ if (conn_handle == p_dev_rec->ble_hci_handle) return status;
+
p_dev_rec->sec_state = BTM_SEC_STATE_DISCONNECTING_BOTH;
break;
case BTM_SEC_STATE_DISCONNECTING_BOTH:
- // Already sent disconnect on both transports
return status;
default:
@@ -1183,9 +1295,20 @@ static tBTM_STATUS btm_sec_send_hci_disconnect(tBTM_SEC_DEV_REC* p_dev_rec,
break;
}
- LOG_DEBUG("Send hci disconnect handle:0x%04x reason:%s", conn_handle,
- hci_reason_code_text(reason).c_str());
- acl_disconnect_after_role_switch(conn_handle, reason);
+ /* If a role switch is in progress, delay the HCI Disconnect to avoid
+ * controller problem */
+ if (p_dev_rec->rs_disc_pending == BTM_SEC_RS_PENDING &&
+ p_dev_rec->hci_handle == conn_handle) {
+ BTM_TRACE_DEBUG(
+ "RS in progress - Set DISC Pending flag in btm_sec_send_hci_disconnect "
+ "to delay disconnect");
+ p_dev_rec->rs_disc_pending = BTM_SEC_DISC_PENDING;
+ status = BTM_SUCCESS;
+ }
+ /* Tear down the HCI link */
+ else {
+ btsnd_hcic_disconnect(conn_handle, reason);
+ }
return status;
}
@@ -1203,7 +1326,7 @@ static tBTM_STATUS btm_sec_send_hci_disconnect(tBTM_SEC_DEV_REC* p_dev_rec,
*
******************************************************************************/
void BTM_ConfirmReqReply(tBTM_STATUS res, const RawAddress& bd_addr) {
- ASSERT_LOG(!bluetooth::shim::is_gd_shim_enabled(), "Unreachable code path");
+ tBTM_SEC_DEV_REC* p_dev_rec;
BTM_TRACE_EVENT("BTM_ConfirmReqReply() State: %s Res: %u",
btm_pair_state_descr(btm_cb.pairing_state), res);
@@ -1216,13 +1339,21 @@ void BTM_ConfirmReqReply(tBTM_STATUS res, const RawAddress& bd_addr) {
btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_AUTH_COMPLETE);
if ((res == BTM_SUCCESS) || (res == BTM_SUCCESS_NO_SECURITY)) {
- acl_set_disconnect_reason(HCI_SUCCESS);
+ btm_cb.acl_disc_reason = HCI_SUCCESS;
+
+ if (res == BTM_SUCCESS) {
+ p_dev_rec = btm_find_dev(bd_addr);
+ if (p_dev_rec != NULL) {
+ p_dev_rec->sec_flags |= BTM_SEC_LINK_KEY_AUTHED;
+ p_dev_rec->sec_flags |= BTM_SEC_16_DIGIT_PIN_AUTHED;
+ }
+ }
btsnd_hcic_user_conf_reply(bd_addr, true);
} else {
/* Report authentication failed event from state
* BTM_PAIR_STATE_WAIT_AUTH_COMPLETE */
- acl_set_disconnect_reason(HCI_ERR_HOST_REJECT_SECURITY);
+ btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
btsnd_hcic_user_conf_reply(bd_addr, false);
}
}
@@ -1243,8 +1374,6 @@ void BTM_ConfirmReqReply(tBTM_STATUS res, const RawAddress& bd_addr) {
******************************************************************************/
void BTM_PasskeyReqReply(tBTM_STATUS res, const RawAddress& bd_addr,
uint32_t passkey) {
- ASSERT_LOG(!bluetooth::shim::is_gd_shim_enabled(), "Unreachable code path");
-
BTM_TRACE_API("BTM_PasskeyReqReply: State: %s res:%d",
btm_pair_state_descr(btm_cb.pairing_state), res);
@@ -1258,9 +1387,9 @@ void BTM_PasskeyReqReply(tBTM_STATUS res, const RawAddress& bd_addr,
(res != BTM_SUCCESS)) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
if (p_dev_rec != NULL) {
- acl_set_disconnect_reason(HCI_ERR_HOST_REJECT_SECURITY);
+ btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
- if (p_dev_rec->hci_handle != HCI_INVALID_HANDLE)
+ if (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE)
btm_sec_send_hci_disconnect(p_dev_rec, HCI_ERR_AUTH_FAILURE,
p_dev_rec->hci_handle);
else
@@ -1282,16 +1411,71 @@ void BTM_PasskeyReqReply(tBTM_STATUS res, const RawAddress& bd_addr,
if (res != BTM_SUCCESS) {
/* use BTM_PAIR_STATE_WAIT_AUTH_COMPLETE to report authentication failed
* event */
- acl_set_disconnect_reason(HCI_ERR_HOST_REJECT_SECURITY);
+ btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
btsnd_hcic_user_passkey_neg_reply(bd_addr);
} else {
- acl_set_disconnect_reason(HCI_SUCCESS);
+ btm_cb.acl_disc_reason = HCI_SUCCESS;
btsnd_hcic_user_passkey_reply(bd_addr, passkey);
}
}
/*******************************************************************************
*
+ * Function BTM_SendKeypressNotif
+ *
+ * Description This function is used during the passkey entry model
+ * by a device with KeyboardOnly IO capabilities
+ * (very likely to be a HID Device).
+ * It is called by a HID Device to inform the remote device
+ * when a key has been entered or erased.
+ *
+ * Parameters: bd_addr - Address of the peer device
+ * type - notification type
+ *
+ ******************************************************************************/
+void BTM_SendKeypressNotif(const RawAddress& bd_addr, tBTM_SP_KEY_TYPE type) {
+ /* This API only make sense between PASSKEY_REQ and SP complete */
+ if (btm_cb.pairing_state == BTM_PAIR_STATE_KEY_ENTRY)
+ btsnd_hcic_send_keypress_notif(bd_addr, type);
+}
+
+/*******************************************************************************
+ *
+ * Function BTM_IoCapRsp
+ *
+ * Description This function is called in response to BTM_SP_IO_REQ_EVT
+ * When the event data io_req.oob_data is set to
+ * BTM_OOB_UNKNOWN by the tBTM_SP_CALLBACK implementation,
+ * this function is called to provide the actual response
+ *
+ * Parameters: bd_addr - Address of the peer device
+ * io_cap - The IO capability of local device.
+ * oob - BTM_OOB_NONE or BTM_OOB_PRESENT.
+ * auth_req- MITM protection required or not.
+ *
+ ******************************************************************************/
+void BTM_IoCapRsp(const RawAddress& bd_addr, tBTM_IO_CAP io_cap,
+ tBTM_OOB_DATA oob, tBTM_AUTH_REQ auth_req) {
+ BTM_TRACE_EVENT("BTM_IoCapRsp: state: %s oob: %d io_cap: %d",
+ btm_pair_state_descr(btm_cb.pairing_state), oob, io_cap);
+
+ if ((btm_cb.pairing_state != BTM_PAIR_STATE_WAIT_LOCAL_IOCAPS) ||
+ (btm_cb.pairing_bda != bd_addr))
+ return;
+
+ if (oob < BTM_OOB_UNKNOWN && io_cap < BTM_IO_CAP_MAX) {
+ btm_cb.devcb.loc_auth_req = auth_req;
+ btm_cb.devcb.loc_io_caps = io_cap;
+
+ if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
+ auth_req = (BTM_AUTH_DD_BOND | (auth_req & BTM_AUTH_YN_BIT));
+
+ btsnd_hcic_io_cap_req_reply(bd_addr, io_cap, oob, auth_req);
+ }
+}
+
+/*******************************************************************************
+ *
* Function BTM_ReadLocalOobData
*
* Description This function is called to read the local OOB data from
@@ -1325,10 +1509,10 @@ void BTM_RemoteOobDataReply(tBTM_STATUS res, const RawAddress& bd_addr,
if (res != BTM_SUCCESS) {
/* use BTM_PAIR_STATE_WAIT_AUTH_COMPLETE to report authentication failed
* event */
- acl_set_disconnect_reason(HCI_ERR_HOST_REJECT_SECURITY);
+ btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
btsnd_hcic_rem_oob_neg_reply(bd_addr);
} else {
- acl_set_disconnect_reason(HCI_SUCCESS);
+ btm_cb.acl_disc_reason = HCI_SUCCESS;
btsnd_hcic_rem_oob_reply(bd_addr, c, r);
}
}
@@ -1374,41 +1558,45 @@ bool BTM_PeerSupportsSecureConnections(const RawAddress& bd_addr) {
return false;
}
- return (p_dev_rec->SupportsSecureConnections());
+ return (p_dev_rec->remote_supports_secure_connections);
}
/*******************************************************************************
*
- * Function BTM_GetPeerDeviceTypeFromFeatures
+ * Function BTM_SetOutService
*
- * Description This function is called to retrieve the peer device type
- * by referencing the remote features.
+ * Description This function is called to set the service for
+ * outgoing connections.
*
- * Parameters: bd_addr - address of the peer
+ * If the profile/application calls BTM_SetSecurityLevel
+ * before initiating a connection, this function does not
+ * need to be called.
*
- * Returns BT_DEVICE_TYPE_DUMO if both BR/EDR and BLE transports are
- * supported by the peer,
- * BT_DEVICE_TYPE_BREDR if only BR/EDR transport is supported,
- * BT_DEVICE_TYPE_BLE if only BLE transport is supported.
+ * Returns void
*
******************************************************************************/
-tBT_DEVICE_TYPE BTM_GetPeerDeviceTypeFromFeatures(const RawAddress& bd_addr) {
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
- if (p_dev_rec == nullptr) {
- LOG_WARN("Unknown BDA:%s", PRIVATE_ADDRESS(bd_addr));
- } else {
- if (p_dev_rec->remote_supports_ble && p_dev_rec->remote_supports_bredr) {
- return BT_DEVICE_TYPE_DUMO;
- } else if (p_dev_rec->remote_supports_bredr) {
- return BT_DEVICE_TYPE_BREDR;
- } else if (p_dev_rec->remote_supports_ble) {
- return BT_DEVICE_TYPE_BLE;
- } else {
- LOG_WARN("Device features does not support BR/EDR and BLE:%s",
- PRIVATE_ADDRESS(bd_addr));
+void BTM_SetOutService(const RawAddress& bd_addr, uint8_t service_id,
+ uint32_t mx_chan_id) {
+ tBTM_SEC_DEV_REC* p_dev_rec;
+ tBTM_SEC_SERV_REC* p_serv_rec = &btm_cb.sec_serv_rec[0];
+
+ btm_cb.p_out_serv = p_serv_rec;
+ p_dev_rec = btm_find_dev(bd_addr);
+
+ for (int i = 0; i < BTM_SEC_MAX_SERVICE_RECORDS; i++, p_serv_rec++) {
+ if ((p_serv_rec->security_flags & BTM_SEC_IN_USE) &&
+ (p_serv_rec->service_id == service_id) &&
+ (p_serv_rec->orig_mx_chan_id == mx_chan_id)) {
+ BTM_TRACE_API(
+ "BTM_SetOutService p_out_serv id %d, psm 0x%04x, proto_id %d, "
+ "chan_id %d",
+ p_serv_rec->service_id, p_serv_rec->psm, p_serv_rec->mx_proto_id,
+ p_serv_rec->orig_mx_chan_id);
+ btm_cb.p_out_serv = p_serv_rec;
+ if (p_dev_rec) p_dev_rec->p_cur_service = p_serv_rec;
+ break;
}
}
- return BT_DEVICE_TYPE_BREDR;
}
/************************************************************************
@@ -1431,6 +1619,18 @@ static bool btm_sec_is_upgrade_possible(tBTM_SEC_DEV_REC* p_dev_rec,
if (p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_KNOWN) {
is_possible = false;
+ if (p_dev_rec->p_cur_service) {
+ BTM_TRACE_DEBUG(
+ "%s() id: %d, link_key_typet: %d, rmt_io_caps: %d, chk flags: 0x%x, "
+ "flags: 0x%x",
+ __func__, p_dev_rec->p_cur_service->service_id,
+ p_dev_rec->link_key_type, p_dev_rec->rmt_io_caps, mtm_check,
+ p_dev_rec->p_cur_service->security_flags);
+ } else {
+ BTM_TRACE_DEBUG(
+ "%s() link_key_typet: %d, rmt_io_caps: %d, chk flags: 0x%x", __func__,
+ p_dev_rec->link_key_type, p_dev_rec->rmt_io_caps, mtm_check);
+ }
/* Already have a link key to the connected peer. Is the link key secure
*enough?
** Is a link key upgrade even possible?
@@ -1476,50 +1676,115 @@ static void btm_sec_check_upgrade(tBTM_SEC_DEV_REC* p_dev_rec,
if (btm_sec_is_upgrade_possible(p_dev_rec, is_originator)) {
BTM_TRACE_DEBUG("need upgrade!! sec_flags:0x%x", p_dev_rec->sec_flags);
- /* if the application confirms the upgrade, set the upgrade bit */
- p_dev_rec->sm4 |= BTM_SM4_UPGRADE;
+ /* upgrade is possible: check if the application wants the upgrade.
+ * If the application is configured to use a global MITM flag,
+ * it probably would not want to upgrade the link key based on the security
+ * level database */
+ tBTM_SP_UPGRADE evt_data;
+ evt_data.bd_addr = p_dev_rec->bd_addr;
+ evt_data.upgrade = true;
+ if (btm_cb.api.p_sp_callback)
+ (*btm_cb.api.p_sp_callback)(BTM_SP_UPGRADE_EVT,
+ (tBTM_SP_EVT_DATA*)&evt_data);
- /* Clear the link key known to go through authentication/pairing again */
- p_dev_rec->sec_flags &= ~(BTM_SEC_LINK_KEY_KNOWN | BTM_SEC_LINK_KEY_AUTHED);
- p_dev_rec->sec_flags &= ~BTM_SEC_AUTHENTICATED;
- BTM_TRACE_DEBUG("sec_flags:0x%x", p_dev_rec->sec_flags);
+ BTM_TRACE_DEBUG("evt_data.upgrade:0x%x", evt_data.upgrade);
+ if (evt_data.upgrade) {
+ /* if the application confirms the upgrade, set the upgrade bit */
+ p_dev_rec->sm4 |= BTM_SM4_UPGRADE;
+
+ /* Clear the link key known to go through authentication/pairing again */
+ p_dev_rec->sec_flags &=
+ ~(BTM_SEC_LINK_KEY_KNOWN | BTM_SEC_LINK_KEY_AUTHED);
+ p_dev_rec->sec_flags &= ~BTM_SEC_AUTHENTICATED;
+ BTM_TRACE_DEBUG("sec_flags:0x%x", p_dev_rec->sec_flags);
+ }
}
}
-tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
- const RawAddress& bd_addr, uint16_t security_required, bool is_originator,
- tBTM_SEC_CALLBACK* p_callback, void* p_ref_data) {
- LOG_DEBUG(
- "Checking l2cap access requirements peer:%s security:0x%x "
- "is_initiator:%s",
- PRIVATE_ADDRESS(bd_addr), security_required,
- logbool(is_originator).c_str());
-
+/*******************************************************************************
+ *
+ * Function btm_sec_l2cap_access_req
+ *
+ * Description This function is called by the L2CAP to grant permission to
+ * establish L2CAP connection to or from the peer device.
+ *
+ * Parameters: bd_addr - Address of the peer device
+ * psm - L2CAP PSM
+ * is_originator - true if protocol above L2CAP originates
+ * connection
+ * p_callback - Pointer to callback function called if
+ * this function returns PENDING after required
+ * procedures are complete. MUST NOT BE NULL.
+ *
+ * Returns tBTM_STATUS
+ *
+ ******************************************************************************/
+tBTM_STATUS btm_sec_l2cap_access_req(const RawAddress& bd_addr, uint16_t psm,
+ uint16_t handle, CONNECTION_TYPE conn_type,
+ tBTM_SEC_CALLBACK* p_callback,
+ void* p_ref_data) {
+ tBTM_SEC_DEV_REC* p_dev_rec;
+ tBTM_SEC_SERV_REC* p_serv_rec;
+ uint16_t security_required;
+ uint16_t old_security_required;
+ bool old_is_originator;
tBTM_STATUS rc = BTM_SUCCESS;
bool chk_acp_auth_done = false;
- /* should check PSM range in LE connection oriented L2CAP connection */
- constexpr tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
+ const bool is_originator = conn_type;
+ constexpr tBT_TRANSPORT transport =
+ BT_TRANSPORT_BR_EDR; /* should check PSM range in LE connection oriented
+ L2CAP connection */
+
+ BTM_TRACE_DEBUG("%s() is_originator:%d, 0x%x, psm=0x%04x", __func__,
+ is_originator, p_ref_data, psm);
/* Find or get oldest record */
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_or_alloc_dev(bd_addr);
+ p_dev_rec = btm_find_or_alloc_dev(bd_addr);
+
+ p_dev_rec->hci_handle = handle;
- p_dev_rec->hci_handle = BTM_GetHCIConnHandle(bd_addr, BT_TRANSPORT_BR_EDR);
+ /* Find the service record for the PSM */
+ p_serv_rec = btm_sec_find_first_serv(conn_type, psm);
+
+ /* If there is no application registered with this PSM do not allow connection
+ */
+ if (!p_serv_rec) {
+ BTM_TRACE_WARNING("%s() PSM: %d no application registerd", __func__, psm);
+ (*p_callback)(&bd_addr, transport, p_ref_data, BTM_MODE_UNSUPPORTED);
+ return (BTM_MODE_UNSUPPORTED);
+ }
+
+ /* Services level0 by default have no security */
+ if ((btm_sec_is_serv_level0(psm)) &&
+ (!btm_cb.devcb.secure_connections_only)) {
+ (*p_callback)(&bd_addr, transport, p_ref_data, BTM_SUCCESS_NO_SECURITY);
+ return (BTM_SUCCESS);
+ }
+ if (btm_cb.security_mode == BTM_SEC_MODE_SC) {
+ security_required = btm_sec_set_serv_level4_flags(
+ p_serv_rec->security_flags, is_originator);
+ } else {
+ security_required = p_serv_rec->security_flags;
+ }
+
+ BTM_TRACE_DEBUG(
+ "%s: security_required 0x%04x, is_originator 0x%02x, psm 0x%04x",
+ __func__, security_required, is_originator, psm);
if ((!is_originator) && (security_required & BTM_SEC_MODE4_LEVEL4)) {
bool local_supports_sc =
controller_get_interface()->supports_secure_connections();
/* acceptor receives L2CAP Channel Connect Request for Secure Connections
* Only service */
- if (!local_supports_sc || !p_dev_rec->SupportsSecureConnections()) {
- LOG_WARN(
- "Policy requires mode 4 level 4, but local_support_for_sc=%d, "
- "rmt_support_for_sc=%s, failing connection",
- local_supports_sc,
- logbool(p_dev_rec->SupportsSecureConnections()).c_str());
- if (p_callback) {
+ if (!(local_supports_sc) ||
+ !(p_dev_rec->remote_supports_secure_connections)) {
+ BTM_TRACE_DEBUG("%s: SC only service, local_support_for_sc %d",
+ "rmt_support_for_sc : %d -> fail pairing", __func__,
+ local_supports_sc,
+ p_dev_rec->remote_supports_secure_connections);
+ if (p_callback)
(*p_callback)(&bd_addr, transport, (void*)p_ref_data,
BTM_MODE4_LEVEL4_NOT_SUPPORTED);
- }
return (BTM_MODE4_LEVEL4_NOT_SUPPORTED);
}
@@ -1530,10 +1795,16 @@ tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
/* we will process one after another */
if ((p_dev_rec->p_callback) ||
(btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)) {
- LOG_DEBUG("security_flags:x%x, sec_flags:x%x", security_required,
- p_dev_rec->sec_flags);
+ BTM_TRACE_EVENT("%s() - busy - PSM:%d delayed state: %s mode:%d, sm4:0x%x",
+ __func__, psm, btm_pair_state_descr(btm_cb.pairing_state),
+ btm_cb.security_mode, p_dev_rec->sm4);
+ BTM_TRACE_EVENT("security_flags:x%x, sec_flags:x%x", security_required,
+ p_dev_rec->sec_flags);
rc = BTM_CMD_STARTED;
- if ((btm_cb.security_mode == BTM_SEC_MODE_SERVICE) ||
+ if ((btm_cb.security_mode == BTM_SEC_MODE_UNDEFINED ||
+ btm_cb.security_mode == BTM_SEC_MODE_NONE ||
+ btm_cb.security_mode == BTM_SEC_MODE_SERVICE ||
+ btm_cb.security_mode == BTM_SEC_MODE_LINK) ||
(BTM_SM4_KNOWN == p_dev_rec->sm4) ||
(BTM_SEC_IS_SM4(p_dev_rec->sm4) &&
(!btm_sec_is_upgrade_possible(p_dev_rec, is_originator)))) {
@@ -1546,7 +1817,9 @@ tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
btm_dev_authenticated(p_dev_rec))) ||
((((security_required & BTM_SEC_OUT_FLAGS) ==
(BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT)) &&
- btm_dev_encrypted(p_dev_rec)))) {
+ btm_dev_encrypted(p_dev_rec))) ||
+ ((((security_required & BTM_SEC_OUT_FLAGS) == BTM_SEC_OUT_FLAGS) &&
+ btm_dev_authorized(p_dev_rec) && btm_dev_encrypted(p_dev_rec)))) {
rc = BTM_SUCCESS;
}
} else {
@@ -1556,7 +1829,24 @@ tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
btm_dev_authenticated(p_dev_rec)) ||
(((security_required & BTM_SEC_IN_FLAGS) ==
(BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT)) &&
- btm_dev_encrypted(p_dev_rec))) {
+ btm_dev_encrypted(p_dev_rec)) ||
+ (((security_required & BTM_SEC_IN_FLAGS) == BTM_SEC_IN_AUTHORIZE) &&
+ (btm_dev_authorized(p_dev_rec) ||
+ btm_serv_trusted(p_dev_rec, p_serv_rec))) ||
+ (((security_required & BTM_SEC_IN_FLAGS) ==
+ (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_AUTHORIZE)) &&
+ ((btm_dev_authorized(p_dev_rec) ||
+ btm_serv_trusted(p_dev_rec, p_serv_rec)) &&
+ btm_dev_authenticated(p_dev_rec))) ||
+ (((security_required & BTM_SEC_IN_FLAGS) ==
+ (BTM_SEC_IN_ENCRYPT | BTM_SEC_IN_AUTHORIZE)) &&
+ ((btm_dev_authorized(p_dev_rec) ||
+ btm_serv_trusted(p_dev_rec, p_serv_rec)) &&
+ btm_dev_encrypted(p_dev_rec))) ||
+ (((security_required & BTM_SEC_IN_FLAGS) == BTM_SEC_IN_FLAGS) &&
+ btm_dev_encrypted(p_dev_rec) &&
+ (btm_dev_authorized(p_dev_rec) ||
+ btm_serv_trusted(p_dev_rec, p_serv_rec)))) {
// Check for 16 digits (or MITM)
if (((security_required & BTM_SEC_IN_MIN_16_DIGIT_PIN) == 0) ||
(((security_required & BTM_SEC_IN_MIN_16_DIGIT_PIN) ==
@@ -1583,11 +1873,12 @@ tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
return (BTM_CMD_STARTED);
}
- /* Save the security requirements in case a pairing is needed */
- p_dev_rec->required_security_flags_for_pairing = security_required;
+ /* Save pointer to service record */
+ p_dev_rec->p_cur_service = p_serv_rec;
/* Modify security_required in btm_sec_l2cap_access_req for Lisbon */
if (btm_cb.security_mode == BTM_SEC_MODE_SP ||
+ btm_cb.security_mode == BTM_SEC_MODE_SP_DEBUG ||
btm_cb.security_mode == BTM_SEC_MODE_SC) {
if (BTM_SEC_IS_SM4(p_dev_rec->sm4)) {
if (is_originator) {
@@ -1603,9 +1894,9 @@ tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
}
} else if (!(BTM_SM4_KNOWN & p_dev_rec->sm4)) {
/* the remote features are not known yet */
- LOG_DEBUG(
- "Remote features have not yet been received sec_flags:0x%02x %s",
- p_dev_rec->sec_flags, (is_originator) ? "initiator" : "acceptor");
+ BTM_TRACE_DEBUG("%s: (%s) remote features unknown!!sec_flags:0x%02x",
+ __func__, (is_originator) ? "initiator" : "acceptor",
+ p_dev_rec->sec_flags);
p_dev_rec->sm4 |= BTM_SM4_REQ_PEND;
return (BTM_CMD_STARTED);
@@ -1617,10 +1908,54 @@ tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
p_dev_rec->sm4, p_dev_rec->sec_flags, security_required,
chk_acp_auth_done);
+ old_security_required = p_dev_rec->security_required;
+ old_is_originator = p_dev_rec->is_originator;
p_dev_rec->security_required = security_required;
p_dev_rec->p_ref_data = p_ref_data;
p_dev_rec->is_originator = is_originator;
+/* If there are multiple service records used through the same PSM */
+/* leave security decision for the multiplexor on the top */
+ if ((btm_sec_find_next_serv(p_serv_rec)) != NULL) {
+ BTM_TRACE_DEBUG("no next_serv sm4:0x%x, chk:%d", p_dev_rec->sm4,
+ chk_acp_auth_done);
+ if (!BTM_SEC_IS_SM4(p_dev_rec->sm4)) {
+ BTM_TRACE_EVENT(
+ "Security Manager: l2cap_access_req PSM:%d postponed for multiplexer",
+ psm);
+ /* pre-Lisbon: restore the old settings */
+ p_dev_rec->security_required = old_security_required;
+ p_dev_rec->is_originator = old_is_originator;
+
+ (*p_callback)(&bd_addr, transport, p_ref_data, BTM_SUCCESS);
+
+ return (BTM_SUCCESS);
+ }
+ }
+
+ /* if the originator is using dynamic PSM in legacy mode, do not start any
+ * security process now
+ * The layer above L2CAP needs to carry out the security requirement after
+ * L2CAP connect
+ * response is received */
+ if (is_originator &&
+ ((btm_cb.security_mode == BTM_SEC_MODE_UNDEFINED ||
+ btm_cb.security_mode == BTM_SEC_MODE_NONE ||
+ btm_cb.security_mode == BTM_SEC_MODE_SERVICE ||
+ btm_cb.security_mode == BTM_SEC_MODE_LINK) ||
+ !BTM_SEC_IS_SM4(p_dev_rec->sm4)) &&
+ (psm >= 0x1001)) {
+ BTM_TRACE_EVENT(
+ "dynamic PSM:0x%x in legacy mode - postponed for upper layer", psm);
+ /* restore the old settings */
+ p_dev_rec->security_required = old_security_required;
+ p_dev_rec->is_originator = old_is_originator;
+
+ (*p_callback)(&bd_addr, transport, p_ref_data, BTM_SUCCESS);
+
+ return (BTM_SUCCESS);
+ }
+
if (chk_acp_auth_done) {
BTM_TRACE_DEBUG(
"(SM4 to SM4) btm_sec_l2cap_access_req rspd. authenticated: x%x, enc: "
@@ -1638,7 +1973,7 @@ tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
because of data path issues. Delay this disconnect a little bit
*/
LOG_INFO(
-
+ LOG_TAG,
"%s peer should have initiated security process by now (SM4 to SM4)",
__func__);
p_dev_rec->p_callback = p_callback;
@@ -1651,6 +1986,17 @@ tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
p_dev_rec->p_callback = p_callback;
+ if (p_dev_rec->last_author_service_id == BTM_SEC_NO_LAST_SERVICE_ID ||
+ p_dev_rec->last_author_service_id !=
+ p_dev_rec->p_cur_service->service_id) {
+ /* Although authentication and encryption are per connection
+ ** authorization is per access request. For example when serial connection
+ ** is up and authorized and client requests to read file (access to other
+ ** scn), we need to request user's permission again.
+ */
+ p_dev_rec->sec_flags &= ~BTM_SEC_AUTHORIZED;
+ }
+
if (BTM_SEC_IS_SM4(p_dev_rec->sm4)) {
if ((p_dev_rec->security_required & BTM_SEC_MODE4_LEVEL4) &&
(p_dev_rec->link_key_type != BTM_LKEY_TYPE_AUTH_COMB_P_256)) {
@@ -1670,12 +2016,17 @@ tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
}
}
+ BTM_TRACE_EVENT(
+ "%s() PSM:%d Handle:%d State:%d Flags: 0x%x Required: 0x%x Service ID:%d",
+ __func__, psm, handle, p_dev_rec->sec_state, p_dev_rec->sec_flags,
+ p_dev_rec->security_required, p_dev_rec->p_cur_service->service_id);
+
rc = btm_sec_execute_procedure(p_dev_rec);
if (rc != BTM_CMD_STARTED) {
BTM_TRACE_DEBUG("%s: p_dev_rec=%p, clearing callback. old p_callback=%p",
__func__, p_dev_rec, p_dev_rec->p_callback);
p_dev_rec->p_callback = NULL;
- (*p_callback)(&bd_addr, transport, p_dev_rec->p_ref_data, rc);
+ (*p_callback)(&bd_addr, transport, p_dev_rec->p_ref_data, (uint8_t)rc);
}
return (rc);
@@ -1683,62 +2034,6 @@ tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
/*******************************************************************************
*
- * Function btm_sec_l2cap_access_req
- *
- * Description This function is called by the L2CAP to grant permission to
- * establish L2CAP connection to or from the peer device.
- *
- * Parameters: bd_addr - Address of the peer device
- * psm - L2CAP PSM
- * is_originator - true if protocol above L2CAP originates
- * connection
- * p_callback - Pointer to callback function called if
- * this function returns PENDING after required
- * procedures are complete. MUST NOT BE NULL.
- *
- * Returns tBTM_STATUS
- *
- ******************************************************************************/
-tBTM_STATUS btm_sec_l2cap_access_req(const RawAddress& bd_addr, uint16_t psm,
- bool is_originator,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data) {
- // should check PSM range in LE connection oriented L2CAP connection
- constexpr tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
-
- LOG_DEBUG("is_originator:%d, psm=0x%04x", is_originator, psm);
-
- // Find the service record for the PSM
- tBTM_SEC_SERV_REC* p_serv_rec = btm_sec_find_first_serv(is_originator, psm);
-
- // If there is no application registered with this PSM do not allow connection
- if (!p_serv_rec) {
- LOG_WARN("PSM: 0x%04x no application registered", psm);
- (*p_callback)(&bd_addr, transport, p_ref_data, BTM_MODE_UNSUPPORTED);
- return (BTM_MODE_UNSUPPORTED);
- }
-
- /* Services level0 by default have no security */
- if (psm == BT_PSM_SDP) {
- LOG_DEBUG("No security required for SDP");
- (*p_callback)(&bd_addr, transport, p_ref_data, BTM_SUCCESS_NO_SECURITY);
- return (BTM_SUCCESS);
- }
-
- uint16_t security_required;
- if (btm_cb.security_mode == BTM_SEC_MODE_SC) {
- security_required = btm_sec_set_serv_level4_flags(
- p_serv_rec->security_flags, is_originator);
- } else {
- security_required = p_serv_rec->security_flags;
- }
-
- return btm_sec_l2cap_access_req_by_requirement(
- bd_addr, security_required, is_originator, p_callback, p_ref_data);
-}
-
-/*******************************************************************************
- *
* Function btm_sec_mx_access_request
*
* Description This function is called by all Multiplexing Protocols during
@@ -1760,34 +2055,61 @@ tBTM_STATUS btm_sec_l2cap_access_req(const RawAddress& bd_addr, uint16_t psm,
* Returns BTM_CMD_STARTED
*
******************************************************************************/
-tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
- bool is_originator,
- uint16_t security_required,
+tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr, uint16_t psm,
+ bool is_originator, uint32_t mx_proto_id,
+ uint32_t mx_chan_id,
tBTM_SEC_CALLBACK* p_callback,
void* p_ref_data) {
tBTM_SEC_DEV_REC* p_dev_rec;
+ tBTM_SEC_SERV_REC* p_serv_rec;
tBTM_STATUS rc;
+ uint16_t security_required;
bool transport = false; /* should check PSM range in LE connection oriented
L2CAP connection */
- if (bluetooth::shim::is_gd_shim_enabled()) {
- return bluetooth::shim::btm_sec_mx_access_request(
- bd_addr, is_originator, security_required, p_callback, p_ref_data);
- }
+ BTM_TRACE_DEBUG("%s() is_originator: %d", __func__, is_originator);
/* Find or get oldest record */
p_dev_rec = btm_find_or_alloc_dev(bd_addr);
+ /* Find the service record for the PSM */
+ p_serv_rec =
+ btm_sec_find_mx_serv(is_originator, psm, mx_proto_id, mx_chan_id);
+
+ /* If there is no application registered with this PSM do not allow connection
+ */
+ if (!p_serv_rec) {
+ if (p_callback)
+ (*p_callback)(&bd_addr, transport, p_ref_data, BTM_MODE_UNSUPPORTED);
+
+ BTM_TRACE_ERROR(
+ "Security Manager: MX service not found PSM:%d Proto:%d SCN:%d", psm,
+ mx_proto_id, mx_chan_id);
+ return BTM_NO_RESOURCES;
+ }
+
+ if ((btm_cb.security_mode == BTM_SEC_MODE_SC) &&
+ (!btm_sec_is_serv_level0(psm))) {
+ security_required = btm_sec_set_serv_level4_flags(
+ p_serv_rec->security_flags, is_originator);
+ } else {
+ security_required = p_serv_rec->security_flags;
+ }
+
/* there are some devices (moto phone) which connects to several services at
* the same time */
/* we will process one after another */
if ((p_dev_rec->p_callback) ||
(btm_cb.pairing_state != BTM_PAIR_STATE_IDLE)) {
- LOG_DEBUG("Pairing in progress pairing_state:%s",
- btm_pair_state_descr(btm_cb.pairing_state));
+ BTM_TRACE_EVENT("%s() service PSM:%d Proto:%d SCN:%d delayed state: %s",
+ __func__, psm, mx_proto_id, mx_chan_id,
+ btm_pair_state_descr(btm_cb.pairing_state));
rc = BTM_CMD_STARTED;
- if ((btm_cb.security_mode == BTM_SEC_MODE_SERVICE) ||
+ if ((btm_cb.security_mode == BTM_SEC_MODE_UNDEFINED ||
+ btm_cb.security_mode == BTM_SEC_MODE_NONE ||
+ btm_cb.security_mode == BTM_SEC_MODE_SERVICE ||
+ btm_cb.security_mode == BTM_SEC_MODE_LINK) ||
(BTM_SM4_KNOWN == p_dev_rec->sm4) ||
(BTM_SEC_IS_SM4(p_dev_rec->sm4) &&
(!btm_sec_is_upgrade_possible(p_dev_rec, is_originator)))) {
@@ -1808,6 +2130,19 @@ tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
((((security_required & BTM_SEC_IN_FLAGS) ==
BTM_SEC_IN_AUTHENTICATE) &&
btm_dev_authenticated(p_dev_rec))) ||
+ (((security_required & BTM_SEC_IN_FLAGS) == BTM_SEC_IN_AUTHORIZE) &&
+ (btm_dev_authorized(p_dev_rec) ||
+ btm_serv_trusted(p_dev_rec, p_serv_rec))) ||
+ (((security_required & BTM_SEC_IN_FLAGS) ==
+ (BTM_SEC_IN_AUTHORIZE | BTM_SEC_IN_AUTHENTICATE)) &&
+ ((btm_dev_authorized(p_dev_rec) ||
+ btm_serv_trusted(p_dev_rec, p_serv_rec)) &&
+ btm_dev_authenticated(p_dev_rec))) ||
+ (((security_required & BTM_SEC_IN_FLAGS) ==
+ (BTM_SEC_IN_AUTHORIZE | BTM_SEC_IN_ENCRYPT)) &&
+ ((btm_dev_authorized(p_dev_rec) ||
+ btm_serv_trusted(p_dev_rec, p_serv_rec)) &&
+ btm_dev_encrypted(p_dev_rec))) ||
((((security_required & BTM_SEC_IN_FLAGS) ==
(BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT)) &&
btm_dev_encrypted(p_dev_rec)))) {
@@ -1826,22 +2161,41 @@ tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
}
}
+ if (rc == BTM_SUCCESS) {
+ BTM_TRACE_EVENT("%s: allow to bypass, checking authorization", __func__);
+ /* the security in BTM_SEC_IN_FLAGS is fullfilled so far, check the
+ * requirements in */
+ /* btm_sec_execute_procedure */
+ if ((is_originator &&
+ (p_serv_rec->security_flags & BTM_SEC_OUT_AUTHORIZE)) ||
+ (!is_originator &&
+ (p_serv_rec->security_flags & BTM_SEC_IN_AUTHORIZE))) {
+ BTM_TRACE_EVENT("%s: still need authorization", __func__);
+ rc = BTM_CMD_STARTED;
+ }
+ }
+
+ /* Check whether there is a pending security procedure, if so we should
+ * always queue */
/* the new security request */
if (p_dev_rec->sec_state != BTM_SEC_STATE_IDLE) {
- LOG_DEBUG("A pending security procedure in progress");
+ BTM_TRACE_EVENT("%s: There is a pending security procedure", __func__);
rc = BTM_CMD_STARTED;
}
if (rc == BTM_CMD_STARTED) {
- btm_sec_queue_mx_request(bd_addr, BT_PSM_RFCOMM, is_originator,
- BTM_SEC_PROTO_RFCOMM, security_required,
- p_callback, p_ref_data);
+ BTM_TRACE_EVENT("%s: call btm_sec_queue_mx_request", __func__);
+ btm_sec_queue_mx_request(bd_addr, psm, is_originator, mx_proto_id,
+ mx_chan_id, p_callback, p_ref_data);
} else /* rc == BTM_SUCCESS */
{
+ /* access granted */
if (p_callback) {
- LOG_DEBUG("Notifying client that security access has been granted");
- (*p_callback)(&bd_addr, transport, p_ref_data, rc);
+ (*p_callback)(&bd_addr, transport, p_ref_data, (uint8_t)rc);
}
}
+
+ BTM_TRACE_EVENT("%s: return with rc = 0x%02x in delayed state %s", __func__,
+ rc, btm_pair_state_descr(btm_cb.pairing_state));
return rc;
}
@@ -1851,12 +2205,13 @@ tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
controller_get_interface()->supports_secure_connections();
/* acceptor receives service connection establishment Request for */
/* Secure Connections Only service */
- if (!(local_supports_sc) || !(p_dev_rec->SupportsSecureConnections())) {
- LOG_DEBUG(
- "Secure Connection only mode unsupported local_SC_support:%s"
- " remote_SC_support:%s",
- logbool(local_supports_sc).c_str(),
- logbool(p_dev_rec->SupportsSecureConnections()).c_str());
+ if (!(local_supports_sc) ||
+ !(p_dev_rec->remote_supports_secure_connections)) {
+ BTM_TRACE_DEBUG("%s: SC only service,local_support_for_sc %d,",
+ "remote_support_for_sc %d: fail pairing", __func__,
+ local_supports_sc,
+ p_dev_rec->remote_supports_secure_connections);
+
if (p_callback)
(*p_callback)(&bd_addr, transport, (void*)p_ref_data,
BTM_MODE4_LEVEL4_NOT_SUPPORTED);
@@ -1865,17 +2220,11 @@ tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
}
}
- if (security_required & BTM_SEC_OUT_AUTHENTICATE) {
- security_required |= BTM_SEC_OUT_MITM;
- }
- if (security_required & BTM_SEC_IN_AUTHENTICATE) {
- security_required |= BTM_SEC_IN_MITM;
- }
-
- p_dev_rec->required_security_flags_for_pairing = security_required;
+ p_dev_rec->p_cur_service = p_serv_rec;
p_dev_rec->security_required = security_required;
if (btm_cb.security_mode == BTM_SEC_MODE_SP ||
+ btm_cb.security_mode == BTM_SEC_MODE_SP_DEBUG ||
btm_cb.security_mode == BTM_SEC_MODE_SC) {
if (BTM_SEC_IS_SM4(p_dev_rec->sm4)) {
if ((p_dev_rec->security_required & BTM_SEC_MODE4_LEVEL4) &&
@@ -1891,7 +2240,8 @@ tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
BTM_SEC_AUTHENTICATED);
BTM_TRACE_DEBUG("%s: sec_flags:0x%x", __func__, p_dev_rec->sec_flags);
} else {
- LOG_DEBUG("Already have link key; checking if link key is sufficient");
+ /* If we already have a link key, check if that link key is good enough
+ */
btm_sec_check_upgrade(p_dev_rec, is_originator);
}
}
@@ -1901,14 +2251,24 @@ tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
p_dev_rec->p_callback = p_callback;
p_dev_rec->p_ref_data = p_ref_data;
+ /* Although authentication and encryption are per connection */
+ /* authorization is per access request. For example when serial connection */
+ /* is up and authorized and client requests to read file (access to other */
+ /* scn, we need to request user's permission again. */
+ p_dev_rec->sec_flags &= ~(BTM_SEC_AUTHORIZED);
+
+ BTM_TRACE_EVENT(
+ "%s() proto_id:%d chan_id:%d State:%d Flags:0x%x Required:0x%x Service "
+ "ID:%d",
+ __func__, mx_proto_id, mx_chan_id, p_dev_rec->sec_state,
+ p_dev_rec->sec_flags, p_dev_rec->security_required,
+ p_dev_rec->p_cur_service->service_id);
+
rc = btm_sec_execute_procedure(p_dev_rec);
- LOG_DEBUG("Started security procedure peer:%s btm_status:%s",
- PRIVATE_ADDRESS(p_dev_rec->RemoteAddress()),
- btm_status_text(rc).c_str());
if (rc != BTM_CMD_STARTED) {
if (p_callback) {
p_dev_rec->p_callback = NULL;
- (*p_callback)(&bd_addr, transport, p_ref_data, rc);
+ (*p_callback)(&bd_addr, transport, p_ref_data, (uint8_t)rc);
}
}
@@ -1936,6 +2296,30 @@ void btm_sec_conn_req(const RawAddress& bda, uint8_t* dc) {
return;
}
+ /* Security guys wants us not to allow connection from not paired devices */
+
+ /* Check if connection is allowed for only paired devices */
+ if (btm_cb.connect_only_paired) {
+ if (!p_dev_rec || !(p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_AUTHED)) {
+ BTM_TRACE_EVENT(
+ "Security Manager: connect request from non-paired device");
+ btsnd_hcic_reject_conn(bda, HCI_ERR_HOST_REJECT_DEVICE);
+ return;
+ }
+ }
+
+#if (BTM_ALLOW_CONN_IF_NONDISCOVER == FALSE)
+ /* If non-discoverable, only allow known devices to connect */
+ if (btm_cb.btm_inq_vars.discoverable_mode == BTM_NON_DISCOVERABLE) {
+ if (!p_dev_rec) {
+ BTM_TRACE_EVENT(
+ "Security Manager: connect request from not paired device");
+ btsnd_hcic_reject_conn(bda, HCI_ERR_HOST_REJECT_DEVICE);
+ return;
+ }
+ }
+#endif
+
if ((btm_cb.pairing_state != BTM_PAIR_STATE_IDLE) &&
(btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD) &&
(btm_cb.pairing_bda == bda)) {
@@ -1953,11 +2337,15 @@ void btm_sec_conn_req(const RawAddress& bda, uint8_t* dc) {
btm_cb.connecting_bda = bda;
memcpy(btm_cb.connecting_dc, dc, DEV_CLASS_LEN);
- if (!p_dev_rec) {
- /* accept the connection -> allocate a device record */
- p_dev_rec = btm_sec_alloc_dev(bda);
+ if (l2c_link_hci_conn_req(bda)) {
+ if (!p_dev_rec) {
+ /* accept the connection -> allocate a device record */
+ p_dev_rec = btm_sec_alloc_dev(bda);
+ }
+ if (p_dev_rec) {
+ p_dev_rec->sm4 |= BTM_SM4_CONN_PEND;
+ }
}
- p_dev_rec->sm4 |= BTM_SM4_CONN_PEND;
}
/*******************************************************************************
@@ -2015,7 +2403,7 @@ void btm_create_conn_cancel_complete(uint8_t* p) {
STREAM_TO_BDADDR(bd_addr, p);
BTM_TRACE_EVENT("btm_create_conn_cancel_complete(): in State: %s status:%d",
btm_pair_state_descr(btm_cb.pairing_state), status);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
&bd_addr, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_OUTGOING, android::bluetooth::LINK_TYPE_ACL,
android::bluetooth::hci::CMD_CREATE_CONNECTION_CANCEL,
@@ -2067,13 +2455,14 @@ void btm_sec_check_pending_reqs(void) {
tBTM_SEC_QUEUE_ENTRY* p_e;
while ((p_e = (tBTM_SEC_QUEUE_ENTRY*)fixed_queue_try_dequeue(bq)) != NULL) {
/* Check that the ACL is still up before starting security procedures */
- if (BTM_IsAclConnectionUp(p_e->bd_addr, p_e->transport)) {
+ if (btm_bda_to_acl(p_e->bd_addr, p_e->transport) != NULL) {
if (p_e->psm != 0) {
- BTM_TRACE_EVENT("%s PSM:0x%04x Is_Orig:%u", __func__, p_e->psm,
- p_e->is_orig);
+ BTM_TRACE_EVENT(
+ "%s PSM:0x%04x Is_Orig:%u mx_proto_id:%u mx_chan_id:%u", __func__,
+ p_e->psm, p_e->is_orig, p_e->mx_proto_id, p_e->mx_chan_id);
- btm_sec_mx_access_request(p_e->bd_addr, p_e->is_orig,
- p_e->rfcomm_security_requirement,
+ btm_sec_mx_access_request(p_e->bd_addr, p_e->psm, p_e->is_orig,
+ p_e->mx_proto_id, p_e->mx_chan_id,
p_e->p_callback, p_e->p_ref_data);
} else {
BTM_SetEncryption(p_e->bd_addr, p_e->transport, p_e->p_callback,
@@ -2089,6 +2478,36 @@ void btm_sec_check_pending_reqs(void) {
/*******************************************************************************
*
+ * Function btm_sec_init
+ *
+ * Description This function is on the SEC startup
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_sec_init(uint8_t sec_mode) {
+ btm_cb.security_mode = sec_mode;
+ btm_cb.pairing_bda = RawAddress::kAny;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_sec_device_down
+ *
+ * Description This function should be called when device is disabled or
+ * turned off
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_sec_device_down(void) {
+ BTM_TRACE_EVENT("%s() State: %s", __func__,
+ btm_pair_state_descr(btm_cb.pairing_state));
+ btm_sec_change_pairing_state(BTM_PAIR_STATE_IDLE);
+}
+
+/*******************************************************************************
+ *
* Function btm_sec_dev_reset
*
* Description This function should be called after device reset
@@ -2103,8 +2522,6 @@ void btm_sec_dev_reset(void) {
/* add mx service to use no security */
BTM_SetSecurityLevel(false, "RFC_MUX", BTM_SEC_SERVICE_RFC_MUX,
BTM_SEC_NONE, BT_PSM_RFCOMM, BTM_SEC_PROTO_RFCOMM, 0);
- BTM_SetSecurityLevel(true, "RFC_MUX", BTM_SEC_SERVICE_RFC_MUX, BTM_SEC_NONE,
- BT_PSM_RFCOMM, BTM_SEC_PROTO_RFCOMM, 0);
} else {
btm_cb.security_mode = BTM_SEC_MODE_SERVICE;
}
@@ -2151,17 +2568,37 @@ void btm_sec_abort_access_req(const RawAddress& bd_addr) {
*
******************************************************************************/
static tBTM_STATUS btm_sec_dd_create_conn(tBTM_SEC_DEV_REC* p_dev_rec) {
- tBTM_STATUS status = l2cu_ConnectAclForSecurity(p_dev_rec->bd_addr);
- if (status == BTM_CMD_STARTED) {
+ tL2C_LCB* p_lcb =
+ l2cu_find_lcb_by_bd_addr(p_dev_rec->bd_addr, BT_TRANSPORT_BR_EDR);
+ if (p_lcb && (p_lcb->link_state == LST_CONNECTED ||
+ p_lcb->link_state == LST_CONNECTING)) {
+ BTM_TRACE_WARNING("%s Connection already exists", __func__);
btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_PIN_REQ);
return BTM_CMD_STARTED;
- } else if (status == BTM_NO_RESOURCES) {
- return BTM_NO_RESOURCES;
+ }
+
+ /* Make sure an L2cap link control block is available */
+ if (!p_lcb && (p_lcb = l2cu_allocate_lcb(p_dev_rec->bd_addr, true,
+ BT_TRANSPORT_BR_EDR)) == NULL) {
+ LOG(WARNING) << "Security Manager: failed allocate LCB "
+ << p_dev_rec->bd_addr;
+
+ return (BTM_NO_RESOURCES);
}
/* set up the control block to indicated dedicated bonding */
btm_cb.pairing_flags |= BTM_PAIR_FLAGS_DISC_WHEN_DONE;
+ if (!l2cu_create_conn_br_edr(p_lcb)) {
+ LOG(WARNING) << "Security Manager: failed create allocate LCB "
+ << p_dev_rec->bd_addr;
+
+ l2cu_release_lcb(p_lcb);
+ return (BTM_NO_RESOURCES);
+ }
+
+ btm_acl_update_busy_level(BTM_BLI_PAGE_EVT);
+
VLOG(1) << "Security Manager: " << p_dev_rec->bd_addr;
btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_PIN_REQ);
@@ -2189,16 +2626,15 @@ bool is_state_getting_name(void* data, void* context) {
*
******************************************************************************/
void btm_sec_rmt_name_request_complete(const RawAddress* p_bd_addr,
- uint8_t* p_bd_name, tHCI_STATUS status) {
+ uint8_t* p_bd_name, uint8_t status) {
tBTM_SEC_DEV_REC* p_dev_rec;
int i;
DEV_CLASS dev_class;
uint8_t old_sec_state;
BTM_TRACE_EVENT("btm_sec_rmt_name_request_complete");
- if ((!p_bd_addr &&
- !BTM_IsAclConnectionUp(btm_cb.connecting_bda, BT_TRANSPORT_BR_EDR)) ||
- (p_bd_addr && !BTM_IsAclConnectionUp(*p_bd_addr, BT_TRANSPORT_BR_EDR))) {
+ if ((!p_bd_addr && !BTM_ACL_IS_CONNECTED(btm_cb.connecting_bda)) ||
+ (p_bd_addr && !BTM_ACL_IS_CONNECTED(*p_bd_addr))) {
btm_acl_resubmit_page();
}
@@ -2237,7 +2673,7 @@ void btm_sec_rmt_name_request_complete(const RawAddress* p_bd_addr,
old_sec_state = p_dev_rec->sec_state;
if (status == HCI_SUCCESS) {
strlcpy((char*)p_dev_rec->sec_bd_name, (char*)p_bd_name,
- BTM_MAX_REM_BD_NAME_LEN + 1);
+ BTM_MAX_REM_BD_NAME_LEN);
p_dev_rec->sec_flags |= BTM_SEC_NAME_KNOWN;
BTM_TRACE_EVENT("setting BTM_SEC_NAME_KNOWN sec_flags:0x%x",
p_dev_rec->sec_flags);
@@ -2286,8 +2722,10 @@ void btm_sec_rmt_name_request_complete(const RawAddress* p_bd_addr,
btm_cb.pairing_flags |= BTM_PAIR_FLAGS_PIN_REQD;
(*btm_cb.api.p_pin_callback)(
p_dev_rec->bd_addr, p_dev_rec->dev_class, p_bd_name,
- (p_dev_rec->required_security_flags_for_pairing &
- BTM_SEC_IN_MIN_16_DIGIT_PIN));
+ (p_dev_rec->p_cur_service == NULL)
+ ? false
+ : (p_dev_rec->p_cur_service->security_flags &
+ BTM_SEC_IN_MIN_16_DIGIT_PIN));
}
/* Set the same state again to force the timer to be restarted */
@@ -2308,7 +2746,11 @@ void btm_sec_rmt_name_request_complete(const RawAddress* p_bd_addr,
if (status != HCI_SUCCESS) {
btm_sec_change_pairing_state(BTM_PAIR_STATE_IDLE);
- return NotifyBondingChange(*p_dev_rec, status);
+ if (btm_cb.api.p_auth_complete_callback)
+ (*btm_cb.api.p_auth_complete_callback)(
+ p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
+ status);
+ return;
}
/* if peer is very old legacy devices, HCI_RMT_HOST_SUP_FEAT_NOTIFY_EVT is
@@ -2350,7 +2792,11 @@ void btm_sec_rmt_name_request_complete(const RawAddress* p_bd_addr,
btm_sec_change_pairing_state(BTM_PAIR_STATE_IDLE);
- NotifyBondingChange(*p_dev_rec, HCI_ERR_MEMORY_FULL);
+ if (btm_cb.api.p_auth_complete_callback) {
+ (*btm_cb.api.p_auth_complete_callback)(
+ p_dev_rec->bd_addr, p_dev_rec->dev_class,
+ p_dev_rec->sec_bd_name, HCI_ERR_MEMORY_FULL);
+ }
}
}
return;
@@ -2359,7 +2805,11 @@ void btm_sec_rmt_name_request_complete(const RawAddress* p_bd_addr,
if (BTM_ReadRemoteDeviceName(btm_cb.pairing_bda, NULL,
BT_TRANSPORT_BR_EDR) != BTM_CMD_STARTED) {
BTM_TRACE_ERROR("%s: failed to start remote name request", __func__);
- NotifyBondingChange(*p_dev_rec, HCI_ERR_MEMORY_FULL);
+ if (btm_cb.api.p_auth_complete_callback) {
+ (*btm_cb.api.p_auth_complete_callback)(
+ p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
+ HCI_ERR_MEMORY_FULL);
+ }
};
return;
}
@@ -2369,10 +2819,21 @@ void btm_sec_rmt_name_request_complete(const RawAddress* p_bd_addr,
*/
if (p_dev_rec->link_key_not_sent) {
/* If HCI connection complete has not arrived, wait for it */
- if (p_dev_rec->hci_handle == HCI_INVALID_HANDLE) return;
+ if (p_dev_rec->hci_handle == BTM_SEC_INVALID_HANDLE) return;
p_dev_rec->link_key_not_sent = false;
btm_send_link_key_notif(p_dev_rec);
+
+ /* If its not us who perform authentication, we should tell stackserver */
+ /* that some authentication has been completed */
+ /* This is required when different entities receive link notification and
+ * auth complete */
+ if (!(p_dev_rec->security_required & BTM_SEC_OUT_AUTHENTICATE)) {
+ if (btm_cb.api.p_auth_complete_callback)
+ (*btm_cb.api.p_auth_complete_callback)(
+ p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
+ HCI_SUCCESS);
+ }
}
/* If this is a bonding procedure can disconnect the link now */
@@ -2398,14 +2859,14 @@ void btm_sec_rmt_name_request_complete(const RawAddress* p_bd_addr,
}
/* Remote Name succeeded, execute the next security procedure, if any */
- tBTM_STATUS btm_status = btm_sec_execute_procedure(p_dev_rec);
+ status = (uint8_t)btm_sec_execute_procedure(p_dev_rec);
/* If result is pending reply from the user or from the device is pending */
- if (btm_status == BTM_CMD_STARTED) return;
+ if (status == BTM_CMD_STARTED) return;
/* There is no next procedure or start of procedure failed, notify the waiting
* layer */
- btm_sec_dev_rec_cback_event(p_dev_rec, btm_status, false);
+ btm_sec_dev_rec_cback_event(p_dev_rec, status, false);
}
/*******************************************************************************
@@ -2453,6 +2914,24 @@ void btm_sec_rmt_host_support_feat_evt(uint8_t* p) {
*
******************************************************************************/
void btm_io_capabilities_req(const RawAddress& p) {
+ tBTM_SP_IO_REQ evt_data;
+ uint8_t err_code = 0;
+ tBTM_SEC_DEV_REC* p_dev_rec;
+ bool is_orig = true;
+ uint8_t callback_rc = BTM_SUCCESS;
+
+ evt_data.bd_addr = p;
+
+ /* setup the default response according to compile options */
+ /* assume that the local IO capability does not change
+ * loc_io_caps is initialized with the default value */
+ evt_data.io_cap = btm_cb.devcb.loc_io_caps;
+ evt_data.oob_data = BTM_OOB_NONE;
+ evt_data.auth_req = BTM_DEFAULT_AUTH_REQ;
+
+ BTM_TRACE_EVENT("%s: State: %s", __func__,
+ btm_pair_state_descr(btm_cb.pairing_state));
+
if (btm_sec_is_a_bonded_dev(p)) {
BTM_TRACE_WARNING(
"%s: Incoming bond request, but %s is already bonded (removing)",
@@ -2460,42 +2939,32 @@ void btm_io_capabilities_req(const RawAddress& p) {
bta_dm_process_remove_device(p);
}
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_or_alloc_dev(p);
+ p_dev_rec = btm_find_or_alloc_dev(evt_data.bd_addr);
+
+ BTM_TRACE_DEBUG("%s:Security mode: %d, Num Read Remote Feat pages: %d",
+ __func__, btm_cb.security_mode, p_dev_rec->num_read_pages);
if ((btm_cb.security_mode == BTM_SEC_MODE_SC) &&
- (!p_dev_rec->remote_feature_received)) {
+ (p_dev_rec->num_read_pages == 0)) {
BTM_TRACE_EVENT("%s: Device security mode is SC only.",
"To continue need to know remote features.", __func__);
- // ACL calls back to btm_sec_set_peer_sec_caps after it gets data
p_dev_rec->remote_features_needed = true;
return;
}
- tBTM_SP_IO_REQ evt_data;
- evt_data.bd_addr = p;
-
- /* setup the default response according to compile options */
- /* assume that the local IO capability does not change
- * loc_io_caps is initialized with the default value */
- evt_data.io_cap = btm_cb.devcb.loc_io_caps;
- // TODO(optedoblivion): Inject OOB_DATA_PRESENT Flag
- evt_data.oob_data = BTM_OOB_NONE;
- evt_data.auth_req = BTM_AUTH_SP_NO;
-
- BTM_TRACE_EVENT("%s: State: %s", __func__,
- btm_pair_state_descr(btm_cb.pairing_state));
-
- BTM_TRACE_DEBUG("%s:Security mode: %d", __func__, btm_cb.security_mode);
-
p_dev_rec->sm4 |= BTM_SM4_TRUE;
- BTM_TRACE_EVENT("%s: State: %s Flags: 0x%04x", __func__,
- btm_pair_state_descr(btm_cb.pairing_state),
- btm_cb.pairing_flags);
+ BTM_TRACE_EVENT("%s: State: %s Flags: 0x%04x p_cur_service: 0x%08x",
+ __func__, btm_pair_state_descr(btm_cb.pairing_state),
+ btm_cb.pairing_flags, p_dev_rec->p_cur_service);
+
+ if (p_dev_rec->p_cur_service) {
+ BTM_TRACE_EVENT("%s: cur_service psm: 0x%04x, security_flags: 0x%04x",
+ __func__, p_dev_rec->p_cur_service->psm,
+ p_dev_rec->p_cur_service->security_flags);
+ }
- uint8_t err_code = 0;
- bool is_orig = true;
switch (btm_cb.pairing_state) {
/* initiator connecting */
case BTM_PAIR_STATE_IDLE:
@@ -2509,7 +2978,7 @@ void btm_io_capabilities_req(const RawAddress& p) {
if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_PEER_STARTED_DD) {
/* acceptor in dedicated bonding */
- evt_data.auth_req = BTM_AUTH_AP_YES;
+ evt_data.auth_req = BTM_DEFAULT_DD_AUTH_REQ;
}
break;
@@ -2517,7 +2986,7 @@ void btm_io_capabilities_req(const RawAddress& p) {
initiated by local device */
case BTM_PAIR_STATE_WAIT_PIN_REQ:
if (evt_data.bd_addr == btm_cb.pairing_bda) {
- evt_data.auth_req = BTM_AUTH_AP_YES;
+ evt_data.auth_req = BTM_DEFAULT_DD_AUTH_REQ;
} else {
err_code = HCI_ERR_HOST_BUSY_PAIRING;
}
@@ -2539,12 +3008,13 @@ void btm_io_capabilities_req(const RawAddress& p) {
bool local_supports_sc =
controller_get_interface()->supports_secure_connections();
/* device in Secure Connections Only mode */
- if (!(local_supports_sc) || !(p_dev_rec->SupportsSecureConnections())) {
- LOG_DEBUG(
- "SC only service, local_support_for_sc:%s,"
- " remote_support_for_sc:%s -> fail pairing",
- logbool(local_supports_sc).c_str(),
- logbool(p_dev_rec->SupportsSecureConnections()).c_str());
+ if (!(local_supports_sc) ||
+ !(p_dev_rec->remote_supports_secure_connections)) {
+ BTM_TRACE_DEBUG("%s: SC only service, local_support_for_sc %d,",
+ " remote_support_for_sc 0x%02x -> fail pairing", __func__,
+ local_supports_sc,
+ p_dev_rec->remote_supports_secure_connections);
+
err_code = HCI_ERR_PAIRING_NOT_ALLOWED;
}
}
@@ -2557,17 +3027,16 @@ void btm_io_capabilities_req(const RawAddress& p) {
evt_data.is_orig = is_orig;
if (is_orig) {
- /* local device initiated the pairing non-bonding -> use
- * required_security_flags_for_pairing */
+ /* local device initiated the pairing non-bonding -> use p_cur_service */
if (!(btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD) &&
- (p_dev_rec->required_security_flags_for_pairing &
- BTM_SEC_OUT_AUTHENTICATE)) {
+ p_dev_rec->p_cur_service &&
+ (p_dev_rec->p_cur_service->security_flags & BTM_SEC_OUT_AUTHENTICATE)) {
if (btm_cb.security_mode == BTM_SEC_MODE_SC) {
/* SC only mode device requires MITM protection */
evt_data.auth_req = BTM_AUTH_SP_YES;
} else {
evt_data.auth_req =
- (p_dev_rec->required_security_flags_for_pairing & BTM_SEC_OUT_MITM)
+ (p_dev_rec->p_cur_service->security_flags & BTM_SEC_OUT_MITM)
? BTM_AUTH_SP_YES
: BTM_AUTH_SP_NO;
}
@@ -2584,7 +3053,7 @@ void btm_io_capabilities_req(const RawAddress& p) {
btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_LOCAL_IOCAPS);
- uint8_t callback_rc = BTM_SUCCESS;
+ callback_rc = BTM_SUCCESS;
if (p_dev_rec->sm4 & BTM_SM4_UPGRADE) {
p_dev_rec->sm4 &= ~BTM_SM4_UPGRADE;
@@ -2597,32 +3066,35 @@ void btm_io_capabilities_req(const RawAddress& p) {
(tBTM_SP_EVT_DATA*)&evt_data);
}
- if ((btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)) {
- evt_data.auth_req =
- (BTM_AUTH_DD_BOND | (evt_data.auth_req & BTM_AUTH_YN_BIT));
- }
+ if ((callback_rc == BTM_SUCCESS) || (BTM_OOB_UNKNOWN != evt_data.oob_data)) {
+ if ((btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)) {
+ evt_data.auth_req =
+ (BTM_AUTH_DD_BOND | (evt_data.auth_req & BTM_AUTH_YN_BIT));
+ }
- if (btm_cb.security_mode == BTM_SEC_MODE_SC) {
- /* At this moment we know that both sides are SC capable, device in */
- /* SC only mode requires MITM for any service so let's set MITM bit */
- evt_data.auth_req |= BTM_AUTH_YN_BIT;
- BTM_TRACE_DEBUG("%s: for device in \"SC only\" mode set auth_req to 0x%02x",
- __func__, evt_data.auth_req);
- }
-
- /* if the user does not indicate "reply later" by setting the oob_data to
- * unknown */
- /* send the response right now. Save the current IO capability in the
- * control block */
- btm_cb.devcb.loc_auth_req = evt_data.auth_req;
- btm_cb.devcb.loc_io_caps = evt_data.io_cap;
-
- BTM_TRACE_EVENT("%s: State: %s IO_CAP:%d oob_data:%d auth_req:%d", __func__,
- btm_pair_state_descr(btm_cb.pairing_state), evt_data.io_cap,
- evt_data.oob_data, evt_data.auth_req);
-
- btsnd_hcic_io_cap_req_reply(evt_data.bd_addr, evt_data.io_cap,
- evt_data.oob_data, evt_data.auth_req);
+ if (btm_cb.security_mode == BTM_SEC_MODE_SC) {
+ /* At this moment we know that both sides are SC capable, device in */
+ /* SC only mode requires MITM for any service so let's set MITM bit */
+ evt_data.auth_req |= BTM_AUTH_YN_BIT;
+ BTM_TRACE_DEBUG(
+ "%s: for device in \"SC only\" mode set auth_req to 0x%02x", __func__,
+ evt_data.auth_req);
+ }
+
+ /* if the user does not indicate "reply later" by setting the oob_data to
+ * unknown */
+ /* send the response right now. Save the current IO capability in the
+ * control block */
+ btm_cb.devcb.loc_auth_req = evt_data.auth_req;
+ btm_cb.devcb.loc_io_caps = evt_data.io_cap;
+
+ BTM_TRACE_EVENT("%s: State: %s IO_CAP:%d oob_data:%d auth_req:%d",
+ __func__, btm_pair_state_descr(btm_cb.pairing_state),
+ evt_data.io_cap, evt_data.oob_data, evt_data.auth_req);
+
+ btsnd_hcic_io_cap_req_reply(evt_data.bd_addr, evt_data.io_cap,
+ evt_data.oob_data, evt_data.auth_req);
+ }
}
/*******************************************************************************
@@ -2653,6 +3125,9 @@ void btm_io_capabilities_rsp(uint8_t* p) {
btm_sec_change_pairing_state(BTM_PAIR_STATE_INCOMING_SSP);
+ /* Make sure we reset the trusted mask to help against attacks */
+ BTM_SEC_CLR_TRUSTED_DEVICE(p_dev_rec->trusted_mask);
+
/* work around for FW bug */
btm_inq_stop_on_ssp();
}
@@ -2715,7 +3190,7 @@ void btm_proc_sp_req_evt(tBTM_SP_EVT event, uint8_t* p) {
memcpy(evt_data.cfm_req.dev_class, p_dev_rec->dev_class, DEV_CLASS_LEN);
strlcpy((char*)evt_data.cfm_req.bd_name, (char*)p_dev_rec->sec_bd_name,
- BTM_MAX_REM_BD_NAME_LEN + 1);
+ BTM_MAX_REM_BD_NAME_LEN);
switch (event) {
case BTM_SP_CFM_REQ_EVT:
@@ -2803,7 +3278,7 @@ void btm_proc_sp_req_evt(tBTM_SP_EVT event, uint8_t* p) {
}
/* Something bad. we can only fail this connection */
- acl_set_disconnect_reason(HCI_ERR_HOST_REJECT_SECURITY);
+ btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
if (BTM_SP_CFM_REQ_EVT == event) {
btsnd_hcic_user_conf_reply(p_bda, false);
@@ -2826,6 +3301,31 @@ void btm_proc_sp_req_evt(tBTM_SP_EVT event, uint8_t* p) {
/*******************************************************************************
*
+ * Function btm_keypress_notif_evt
+ *
+ * Description This function is called when a key press notification is
+ * received
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_keypress_notif_evt(uint8_t* p) {
+ tBTM_SP_KEYPRESS evt_data;
+
+ /* parse & report BTM_SP_KEYPRESS_EVT */
+ if (btm_cb.api.p_sp_callback) {
+ RawAddress& p_bda = evt_data.bd_addr;
+
+ STREAM_TO_BDADDR(p_bda, p);
+ evt_data.notif_type = *p;
+
+ (*btm_cb.api.p_sp_callback)(BTM_SP_KEYPRESS_EVT,
+ (tBTM_SP_EVT_DATA*)&evt_data);
+ }
+}
+
+/*******************************************************************************
+ *
* Function btm_simple_pair_complete
*
* Description This function is called when simple pairing process is
@@ -2835,17 +3335,17 @@ void btm_proc_sp_req_evt(tBTM_SP_EVT event, uint8_t* p) {
*
******************************************************************************/
void btm_simple_pair_complete(uint8_t* p) {
- RawAddress bd_addr;
+ tBTM_SP_COMPLT evt_data;
tBTM_SEC_DEV_REC* p_dev_rec;
uint8_t status;
bool disc = false;
status = *p++;
- STREAM_TO_BDADDR(bd_addr, p);
+ STREAM_TO_BDADDR(evt_data.bd_addr, p);
- p_dev_rec = btm_find_dev(bd_addr);
+ p_dev_rec = btm_find_dev(evt_data.bd_addr);
if (p_dev_rec == NULL) {
- LOG(ERROR) << __func__ << " with unknown BDA: " << bd_addr;
+ LOG(ERROR) << __func__ << " with unknown BDA: " << evt_data.bd_addr;
return;
}
@@ -2853,28 +3353,40 @@ void btm_simple_pair_complete(uint8_t* p) {
"btm_simple_pair_complete() Pair State: %s Status:%d sec_state: %u",
btm_pair_state_descr(btm_cb.pairing_state), status, p_dev_rec->sec_state);
+ evt_data.status = BTM_ERR_PROCESSING;
if (status == HCI_SUCCESS) {
+ evt_data.status = BTM_SUCCESS;
p_dev_rec->sec_flags |= BTM_SEC_AUTHENTICATED;
- } else if (status == HCI_ERR_PAIRING_NOT_ALLOWED) {
- /* The test spec wants the peer device to get this failure code. */
- btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_DISCONNECT);
-
- /* Change the timer to 1 second */
- alarm_set_on_mloop(btm_cb.pairing_timer, BT_1SEC_TIMEOUT_MS,
- btm_sec_pairing_timeout, NULL);
- } else if (btm_cb.pairing_bda == bd_addr) {
- /* stop the timer */
- alarm_cancel(btm_cb.pairing_timer);
-
- if (p_dev_rec->sec_state != BTM_SEC_STATE_AUTHENTICATING) {
- /* the initiating side: will receive auth complete event. disconnect ACL
- * at that time */
- disc = true;
- }
} else {
- disc = true;
+ if (status == HCI_ERR_PAIRING_NOT_ALLOWED) {
+ /* The test spec wants the peer device to get this failure code. */
+ btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_DISCONNECT);
+
+ /* Change the timer to 1 second */
+ alarm_set_on_mloop(btm_cb.pairing_timer, BT_1SEC_TIMEOUT_MS,
+ btm_sec_pairing_timeout, NULL);
+ } else if (btm_cb.pairing_bda == evt_data.bd_addr) {
+ /* stop the timer */
+ alarm_cancel(btm_cb.pairing_timer);
+
+ if (p_dev_rec->sec_state != BTM_SEC_STATE_AUTHENTICATING) {
+ /* the initiating side: will receive auth complete event. disconnect ACL
+ * at that time */
+ disc = true;
+ }
+ } else
+ disc = true;
}
+ /* Let the pairing state stay active, p_auth_complete_callback will report the
+ * failure */
+ evt_data.bd_addr = p_dev_rec->bd_addr;
+ memcpy(evt_data.dev_class, p_dev_rec->dev_class, DEV_CLASS_LEN);
+
+ if (btm_cb.api.p_sp_callback)
+ (*btm_cb.api.p_sp_callback)(BTM_SP_COMPLT_EVT,
+ (tBTM_SP_EVT_DATA*)&evt_data);
+
if (disc) {
/* simple pairing failed */
/* Avoid sending disconnect on HCI_ERR_PEER_USER */
@@ -2912,19 +3424,19 @@ void btm_rem_oob_req(uint8_t* p) {
evt_data.bd_addr = p_dev_rec->bd_addr;
memcpy(evt_data.dev_class, p_dev_rec->dev_class, DEV_CLASS_LEN);
strlcpy((char*)evt_data.bd_name, (char*)p_dev_rec->sec_bd_name,
- BTM_MAX_REM_BD_NAME_LEN + 1);
+ BTM_MAX_REM_BD_NAME_LEN);
btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_LOCAL_OOB_RSP);
if ((*btm_cb.api.p_sp_callback)(BTM_SP_RMT_OOB_EVT,
(tBTM_SP_EVT_DATA*)&evt_data) ==
BTM_NOT_AUTHORIZED) {
- BTM_RemoteOobDataReply(static_cast<tBTM_STATUS>(true), p_bda, c, r);
+ BTM_RemoteOobDataReply(true, p_bda, c, r);
}
return;
}
/* something bad. we can only fail this connection */
- acl_set_disconnect_reason(HCI_ERR_HOST_REJECT_SECURITY);
+ btm_cb.acl_disc_reason = HCI_ERR_HOST_REJECT_SECURITY;
btsnd_hcic_rem_oob_neg_reply(p_bda);
}
@@ -2975,7 +3487,7 @@ static void btm_sec_auth_collision(uint16_t handle) {
if ((bluetooth::common::time_get_os_boottime_ms() -
btm_cb.collision_start_time) < BTM_SEC_MAX_COLLISION_DELAY) {
- if (handle == HCI_INVALID_HANDLE) {
+ if (handle == BTM_SEC_INVALID_HANDLE) {
p_dev_rec = btm_sec_find_dev_by_sec_state(BTM_SEC_STATE_AUTHENTICATING);
if (p_dev_rec == NULL)
p_dev_rec = btm_sec_find_dev_by_sec_state(BTM_SEC_STATE_ENCRYPTING);
@@ -3042,7 +3554,17 @@ static bool btm_sec_auth_retry(uint16_t handle, uint8_t status) {
return false;
}
-void btm_sec_auth_complete(uint16_t handle, tHCI_STATUS status) {
+/*******************************************************************************
+ *
+ * Function btm_sec_auth_complete
+ *
+ * Description This function is when authentication of the connection is
+ * completed by the LM
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_sec_auth_complete(uint16_t handle, uint8_t status) {
tBTM_PAIRING_STATE old_state = btm_cb.pairing_state;
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev_by_handle(handle);
bool are_bonding = false;
@@ -3062,7 +3584,7 @@ void btm_sec_auth_complete(uint16_t handle, tHCI_STATUS status) {
}
/* For transaction collision we need to wait and repeat. There is no need */
- /* for random timeout because only peripheral should receive the result */
+ /* for random timeout because only slave should receive the result */
if ((status == HCI_ERR_LMP_ERR_TRANS_COLLISION) ||
(status == HCI_ERR_DIFF_TRANSACTION_COLLISION)) {
btm_sec_auth_collision(handle);
@@ -3116,14 +3638,17 @@ void btm_sec_auth_complete(uint16_t handle, tHCI_STATUS status) {
}
if (was_authenticating == false) {
- if (status != HCI_SUCCESS && old_state != BTM_PAIR_STATE_IDLE) {
- NotifyBondingChange(*p_dev_rec, status);
+ if ((btm_cb.api.p_auth_complete_callback && status != HCI_SUCCESS) &&
+ (old_state != BTM_PAIR_STATE_IDLE)) {
+ (*btm_cb.api.p_auth_complete_callback)(p_dev_rec->bd_addr,
+ p_dev_rec->dev_class,
+ p_dev_rec->sec_bd_name, status);
}
return;
}
/* Currently we do not notify user if it is a keyboard which connects */
- /* User probably Disabled the keyboard while it was asleap. Let them try */
+ /* User probably Disabled the keyboard while it was asleap. Let her try */
if (btm_cb.api.p_auth_complete_callback) {
/* report the suthentication status */
if ((old_state != BTM_PAIR_STATE_IDLE) || (status != HCI_SUCCESS))
@@ -3142,8 +3667,6 @@ void btm_sec_auth_complete(uint16_t handle, tHCI_STATUS status) {
btm_sec_send_hci_disconnect(p_dev_rec, HCI_ERR_PEER_USER,
p_dev_rec->hci_handle);
} else {
- BTM_LogHistory(kBtmLogTag, p_dev_rec->bd_addr, "Bonding completed",
- hci_error_code_text(status));
BTM_TRACE_DEBUG("TRYING TO DECIDE IF CAN USE SMP_BR_CHNL");
if (p_dev_rec->new_encryption_key_is_p256 &&
(btm_sec_use_smp_br_chnl(p_dev_rec))
@@ -3155,13 +3678,11 @@ void btm_sec_auth_complete(uint16_t handle, tHCI_STATUS status) {
BTM_TRACE_DEBUG(
"link encrypted afer dedic bonding can use SMP_BR_CHNL");
- tHCI_ROLE role = HCI_ROLE_UNKNOWN;
- BTM_GetRole(p_dev_rec->bd_addr, &role);
- if (role == HCI_ROLE_CENTRAL) {
+ if (btm_sec_is_master(p_dev_rec)) {
// Encryption is required to start SM over BR/EDR
// indicate that this is encryption after authentication
BTM_SetEncryption(p_dev_rec->bd_addr, BT_TRANSPORT_BR_EDR, NULL, NULL,
- BTM_BLE_SEC_NONE);
+ 0);
}
}
l2cu_start_post_bond_timer(p_dev_rec->hci_handle);
@@ -3190,12 +3711,12 @@ void btm_sec_auth_complete(uint16_t handle, tHCI_STATUS status) {
}
/* Authentication succeeded, execute the next security procedure, if any */
- tBTM_STATUS btm_status = btm_sec_execute_procedure(p_dev_rec);
+ status = btm_sec_execute_procedure(p_dev_rec);
/* If there is no next procedure, or procedure failed to start, notify the
* caller */
- if (btm_status != BTM_CMD_STARTED)
- btm_sec_dev_rec_cback_event(p_dev_rec, btm_status, false);
+ if (status != BTM_CMD_STARTED)
+ btm_sec_dev_rec_cback_event(p_dev_rec, status, false);
}
/*******************************************************************************
@@ -3208,9 +3729,11 @@ void btm_sec_auth_complete(uint16_t handle, tHCI_STATUS status) {
* Returns void
*
******************************************************************************/
-void btm_sec_encrypt_change(uint16_t handle, tHCI_STATUS status,
+void btm_sec_encrypt_change(uint16_t handle, uint8_t status,
uint8_t encr_enable) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev_by_handle(handle);
+ tACL_CONN* p_acl = NULL;
+ uint8_t acl_idx = btm_handle_to_acl_index(handle);
BTM_TRACE_EVENT(
"Security Manager: encrypt_change status:%d State:%d, encr_enable = %d",
status, (p_dev_rec) ? p_dev_rec->sec_state : 0, encr_enable);
@@ -3218,7 +3741,7 @@ void btm_sec_encrypt_change(uint16_t handle, tHCI_STATUS status,
(p_dev_rec) ? p_dev_rec->sec_flags : 0);
/* For transaction collision we need to wait and repeat. There is no need */
- /* for random timeout because only peripheral should receive the result */
+ /* for random timeout because only slave should receive the result */
if ((status == HCI_ERR_LMP_ERR_TRANS_COLLISION) ||
(status == HCI_ERR_DIFF_TRANSACTION_COLLISION)) {
btm_sec_auth_collision(handle);
@@ -3254,11 +3777,12 @@ void btm_sec_encrypt_change(uint16_t handle, tHCI_STATUS status,
BTM_TRACE_DEBUG("after update p_dev_rec->sec_flags=0x%x",
p_dev_rec->sec_flags);
- auto transport =
- BTM_IsBleConnection(handle) ? BT_TRANSPORT_LE : BT_TRANSPORT_BR_EDR;
- btm_sec_check_pending_enc_req(p_dev_rec, transport, encr_enable);
+ if (acl_idx != MAX_L2CAP_LINKS) p_acl = &btm_cb.acl_db[acl_idx];
+
+ if (p_acl != NULL)
+ btm_sec_check_pending_enc_req(p_dev_rec, p_acl->transport, encr_enable);
- if (BTM_IsBleConnection(handle)) {
+ if (p_acl && p_acl->transport == BT_TRANSPORT_LE) {
if (status == HCI_ERR_KEY_MISSING || status == HCI_ERR_AUTH_FAILURE ||
status == HCI_ERR_ENCRY_MODE_NOT_ACCEPTABLE) {
p_dev_rec->sec_flags &= ~(BTM_SEC_LE_LINK_KEY_KNOWN);
@@ -3284,10 +3808,8 @@ void btm_sec_encrypt_change(uint16_t handle, tHCI_STATUS status,
BTM_TRACE_DEBUG("%s: BR key is temporary, skip derivation of LE LTK",
__func__);
}
- tHCI_ROLE role = HCI_ROLE_UNKNOWN;
- BTM_GetRole(p_dev_rec->bd_addr, &role);
if (p_dev_rec->new_encryption_key_is_p256) {
- if (btm_sec_use_smp_br_chnl(p_dev_rec) && role == HCI_ROLE_CENTRAL &&
+ if (btm_sec_use_smp_br_chnl(p_dev_rec) && btm_sec_is_master(p_dev_rec) &&
/* if LE key is not known, do deriving */
(!(p_dev_rec->sec_flags & BTM_SEC_LE_LINK_KEY_KNOWN) ||
/* or BR key is higher security than existing LE keys */
@@ -3297,8 +3819,12 @@ void btm_sec_encrypt_change(uint16_t handle, tHCI_STATUS status,
/* BR/EDR is encrypted with LK that can be used to derive LE LTK */
p_dev_rec->new_encryption_key_is_p256 = false;
- BTM_TRACE_DEBUG("%s start SM over BR/EDR", __func__);
- SMP_BR_PairWith(p_dev_rec->bd_addr);
+ if (p_dev_rec->no_smp_on_br) {
+ BTM_TRACE_DEBUG("%s NO SM over BR/EDR", __func__);
+ } else {
+ BTM_TRACE_DEBUG("%s start SM over BR/EDR", __func__);
+ SMP_BR_PairWith(p_dev_rec->bd_addr);
+ }
}
} else {
// BR/EDR is successfully encrypted. Correct LK type if needed
@@ -3339,11 +3865,11 @@ void btm_sec_encrypt_change(uint16_t handle, tHCI_STATUS status,
}
/* Encryption setup succeeded, execute the next security procedure, if any */
- tBTM_STATUS btm_status = btm_sec_execute_procedure(p_dev_rec);
+ status = (uint8_t)btm_sec_execute_procedure(p_dev_rec);
/* If there is no next procedure, or procedure failed to start, notify the
* caller */
if (status != BTM_CMD_STARTED)
- btm_sec_dev_rec_cback_event(p_dev_rec, btm_status, false);
+ btm_sec_dev_rec_cback_event(p_dev_rec, status, false);
}
/*******************************************************************************
@@ -3368,7 +3894,10 @@ static void btm_sec_connect_after_reject_timeout(UNUSED_ATTR void* data) {
btm_sec_change_pairing_state(BTM_PAIR_STATE_IDLE);
- NotifyBondingChange(*p_dev_rec, HCI_ERR_MEMORY_FULL);
+ if (btm_cb.api.p_auth_complete_callback)
+ (*btm_cb.api.p_auth_complete_callback)(
+ p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
+ HCI_ERR_MEMORY_FULL);
}
}
@@ -3382,51 +3911,48 @@ static void btm_sec_connect_after_reject_timeout(UNUSED_ATTR void* data) {
* Returns void
*
******************************************************************************/
-void btm_sec_connected(const RawAddress& bda, uint16_t handle,
- tHCI_STATUS status, uint8_t enc_mode,
- tHCI_ROLE assigned_role) {
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bda);
- tBTM_STATUS res;
+void btm_sec_connected(const RawAddress& bda, uint16_t handle, uint8_t status,
+ uint8_t enc_mode) {
+ uint8_t res;
bool is_pairing_device = false;
bool addr_matched;
+ tACL_CONN* p_acl_cb;
uint8_t bit_shift = 0;
btm_acl_resubmit_page();
- if (!p_dev_rec) {
- LOG_DEBUG(
- "Connected to new device state:%s handle:0x%04x status:%s "
- "enc_mode:%hhu bda:%s",
- btm_pair_state_descr(btm_cb.pairing_state), handle,
- hci_status_code_text(status).c_str(), enc_mode, PRIVATE_ADDRESS(bda));
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bda);
+ if (p_dev_rec) {
+ VLOG(2) << __func__ << ": Security Manager: in state: "
+ << btm_pair_state_descr(btm_cb.pairing_state)
+ << " handle:" << handle << " status:" << loghex(status)
+ << " enc_mode:" << loghex(enc_mode) << " bda:" << bda
+ << " RName:" << p_dev_rec->sec_bd_name;
+ } else {
+ VLOG(2) << __func__ << ": Security Manager: in state: "
+ << btm_pair_state_descr(btm_cb.pairing_state)
+ << " handle:" << handle << " status:" << loghex(status)
+ << " enc_mode:" << loghex(enc_mode) << " bda:" << bda;
+ }
+ if (!p_dev_rec) {
+ /* There is no device record for new connection. Allocate one */
if (status == HCI_SUCCESS) {
p_dev_rec = btm_sec_alloc_dev(bda);
- LOG_DEBUG("Allocated new device record for new connection peer:%s",
- PRIVATE_ADDRESS(bda));
} else {
/* If the device matches with stored paring address
* reset the paring state to idle */
if ((btm_cb.pairing_state != BTM_PAIR_STATE_IDLE) &&
btm_cb.pairing_bda == bda) {
- LOG_WARN("Connection failed during bonding attempt peer:%s reason:%s",
- PRIVATE_ADDRESS(bda), hci_error_code_text(status).c_str());
btm_sec_change_pairing_state(BTM_PAIR_STATE_IDLE);
}
- LOG_DEBUG("Ignoring failed device connection peer:%s reason:%s",
- PRIVATE_ADDRESS(bda), hci_error_code_text(status).c_str());
+ /* can not find the device record and the status is error,
+ * just ignore it */
return;
}
} else /* Update the timestamp for this device */
{
- LOG_DEBUG(
- "Connected to known device state:%s handle:0x%04x status:%s "
- "enc_mode:%hhu bda:%s RName:%s",
- btm_pair_state_descr(btm_cb.pairing_state), handle,
- hci_status_code_text(status).c_str(), enc_mode, PRIVATE_ADDRESS(bda),
- p_dev_rec->sec_bd_name);
-
bit_shift = (handle == p_dev_rec->ble_hci_handle) ? 8 : 0;
p_dev_rec->timestamp = btm_cb.dev_rec_count++;
if (p_dev_rec->sm4 & BTM_SM4_CONN_PEND) {
@@ -3459,6 +3985,9 @@ void btm_sec_connected(const RawAddress& bda, uint16_t handle,
btm_sec_change_pairing_state(BTM_PAIR_STATE_IDLE);
}
}
+#if (BTM_DISC_DURING_RS == TRUE)
+ p_dev_rec->rs_disc_pending = BTM_SEC_RS_NOT_PENDING; /* reset flag */
+#endif
return;
} else {
l2cu_update_lcb_4_bonding(p_dev_rec->bd_addr, true);
@@ -3471,6 +4000,12 @@ void btm_sec_connected(const RawAddress& bda, uint16_t handle,
p_dev_rec->device_type |= BT_DEVICE_TYPE_BREDR;
+#if (BTM_DISC_DURING_RS == TRUE)
+ p_dev_rec->rs_disc_pending = BTM_SEC_RS_NOT_PENDING; /* reset flag */
+#endif
+
+ p_dev_rec->rs_disc_pending = BTM_SEC_RS_NOT_PENDING; /* reset flag */
+
addr_matched = (btm_cb.pairing_bda == bda);
if ((btm_cb.pairing_state != BTM_PAIR_STATE_IDLE) && addr_matched) {
@@ -3530,7 +4065,11 @@ void btm_sec_connected(const RawAddress& bda, uint16_t handle,
btm_sec_change_pairing_state(BTM_PAIR_STATE_IDLE);
/* We need to notify host that the key is not known any more */
- NotifyBondingChange(*p_dev_rec, status);
+ if (btm_cb.api.p_auth_complete_callback) {
+ (*btm_cb.api.p_auth_complete_callback)(p_dev_rec->bd_addr,
+ p_dev_rec->dev_class,
+ p_dev_rec->sec_bd_name, status);
+ }
}
/*
Do not send authentication failure, if following conditions hold good
@@ -3552,13 +4091,17 @@ void btm_sec_connected(const RawAddress& bda, uint16_t handle,
#ifdef BRCM_NOT_4_BTE
/* If we rejected pairing, pass this special result code */
- if (acl_set_disconnect_reason(HCI_ERR_HOST_REJECT_SECURITY)) {
+ if (btm_cb.acl_disc_reason == HCI_ERR_HOST_REJECT_SECURITY) {
status = HCI_ERR_HOST_REJECT_SECURITY;
}
#endif
/* We need to notify host that the key is not known any more */
- NotifyBondingChange(*p_dev_rec, status);
+ if (btm_cb.api.p_auth_complete_callback) {
+ (*btm_cb.api.p_auth_complete_callback)(p_dev_rec->bd_addr,
+ p_dev_rec->dev_class,
+ p_dev_rec->sec_bd_name, status);
+ }
}
/* p_auth_complete_callback might have freed the p_dev_rec, ensure it exists
@@ -3595,15 +4138,19 @@ void btm_sec_connected(const RawAddress& bda, uint16_t handle,
p_dev_rec->security_required &= ~BTM_SEC_OUT_AUTHENTICATE;
/* remember flag before it is initialized */
- bool is_pair_flags_we_started_dd = false;
if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
- is_pair_flags_we_started_dd = true;
+ res = true;
else
- is_pair_flags_we_started_dd = false;
+ res = false;
+
+ if (btm_cb.api.p_auth_complete_callback)
+ (*btm_cb.api.p_auth_complete_callback)(
+ p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
+ HCI_SUCCESS);
btm_sec_change_pairing_state(BTM_PAIR_STATE_IDLE);
- if (is_pair_flags_we_started_dd) {
+ if (res) {
/* Let l2cap start bond timer */
l2cu_update_lcb_4_bonding(p_dev_rec->bd_addr, true);
}
@@ -3612,41 +4159,54 @@ void btm_sec_connected(const RawAddress& bda, uint16_t handle,
}
p_dev_rec->hci_handle = handle;
- btm_acl_created(bda, handle, assigned_role, BT_TRANSPORT_BR_EDR);
/* role may not be correct here, it will be updated by l2cap, but we need to
*/
/* notify btm_acl that link is up, so starting of rmt name request will not */
/* set paging flag up */
- /* whatever is in btm_establish_continue() without reporting the
- * BTM_BL_CONN_EVT event */
- /* For now there are a some devices that do not like sending */
- /* commands events and data at the same time. */
- /* Set the packet types to the default allowed by the device */
- btm_set_packet_types_from_address(bda, acl_get_supported_packet_types());
+ p_acl_cb = btm_bda_to_acl(bda, BT_TRANSPORT_BR_EDR);
+ if (p_acl_cb) {
+/* whatever is in btm_establish_continue() without reporting the BTM_BL_CONN_EVT
+ * event */
+#if (BTM_BYPASS_EXTRA_ACL_SETUP == FALSE)
+ /* For now there are a some devices that do not like sending */
+ /* commands events and data at the same time. */
+ /* Set the packet types to the default allowed by the device */
+ btm_set_packet_types(p_acl_cb, btm_cb.btm_acl_pkt_types_supported);
+
+ if (btm_cb.btm_def_link_policy)
+ BTM_SetLinkPolicy(p_acl_cb->remote_addr, &btm_cb.btm_def_link_policy);
+#endif
+ }
+ btm_acl_created(bda, p_dev_rec->dev_class, p_dev_rec->sec_bd_name, handle,
+ HCI_ROLE_SLAVE, BT_TRANSPORT_BR_EDR);
/* Initialize security flags. We need to do that because some */
/* authorization complete could have come after the connection is dropped */
/* and that would set wrong flag that link has been authorized already */
- p_dev_rec->sec_flags &=
- ~((BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED | BTM_SEC_ROLE_SWITCHED)
- << bit_shift);
+ p_dev_rec->sec_flags &= ~((BTM_SEC_AUTHORIZED | BTM_SEC_AUTHENTICATED |
+ BTM_SEC_ENCRYPTED | BTM_SEC_ROLE_SWITCHED)
+ << bit_shift);
if (enc_mode != HCI_ENCRYPT_MODE_DISABLED)
p_dev_rec->sec_flags |=
((BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED) << bit_shift);
+ if (btm_cb.security_mode == BTM_SEC_MODE_LINK)
+ p_dev_rec->sec_flags |= (BTM_SEC_AUTHENTICATED << bit_shift);
+
if (p_dev_rec->pin_code_length >= 16 ||
p_dev_rec->link_key_type == BTM_LKEY_TYPE_AUTH_COMB ||
p_dev_rec->link_key_type == BTM_LKEY_TYPE_AUTH_COMB_P_256) {
p_dev_rec->sec_flags |= (BTM_SEC_16_DIGIT_PIN_AUTHED << bit_shift);
}
+ p_dev_rec->link_key_changed = false;
+
/* After connection is established we perform security if we do not know */
/* the name, or if we are originator because some procedure can have */
/* been scheduled while connection was down */
- LOG_DEBUG("Is connection locally initiated:%s",
- logbool(p_dev_rec->is_originator).c_str());
+ BTM_TRACE_DEBUG("is_originator:%d ", p_dev_rec->is_originator);
if (!(p_dev_rec->sec_flags & BTM_SEC_NAME_KNOWN) ||
p_dev_rec->is_originator) {
res = btm_sec_execute_procedure(p_dev_rec);
@@ -3656,12 +4216,21 @@ void btm_sec_connected(const RawAddress& bda, uint16_t handle,
return;
}
-tBTM_STATUS btm_sec_disconnect(uint16_t handle, tHCI_STATUS reason) {
+/*******************************************************************************
+ *
+ * Function btm_sec_disconnect
+ *
+ * Description This function is called to disconnect HCI link
+ *
+ * Returns btm status
+ *
+ ******************************************************************************/
+tBTM_STATUS btm_sec_disconnect(uint16_t handle, uint8_t reason) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev_by_handle(handle);
/* In some weird race condition we may not have a record */
if (!p_dev_rec) {
- acl_disconnect_from_handle(handle, reason);
+ btsnd_hcic_disconnect(handle, reason);
return (BTM_SUCCESS);
}
@@ -3678,93 +4247,104 @@ tBTM_STATUS btm_sec_disconnect(uint16_t handle, tHCI_STATUS reason) {
return (btm_sec_send_hci_disconnect(p_dev_rec, reason, handle));
}
-void btm_sec_disconnected(uint16_t handle, tHCI_REASON reason) {
- if ((reason != HCI_ERR_CONN_CAUSE_LOCAL_HOST) &&
- (reason != HCI_ERR_PEER_USER)) {
- LOG_WARN("Got uncommon disconnection reason:%s handle:0x%04x",
- hci_error_code_text(reason).c_str(), handle);
- }
+/*******************************************************************************
+ *
+ * Function btm_sec_disconnected
+ *
+ * Description This function is when a connection to the peer device is
+ * dropped
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_sec_disconnected(uint16_t handle, uint8_t reason) {
+ uint8_t old_pairing_flags = btm_cb.pairing_flags;
+ int result = HCI_ERR_AUTH_FAILURE;
+ tBTM_SEC_CALLBACK* p_callback = NULL;
+ tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
+
+ /* If page was delayed for disc complete, can do it now */
+ btm_cb.discing = false;
btm_acl_resubmit_page();
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev_by_handle(handle);
- if (p_dev_rec == nullptr) {
- LOG_WARN("Got disconnect for unknown device record handle:0x%04x", handle);
- return;
- }
+ if (!p_dev_rec) return;
- const tBT_TRANSPORT transport =
+ transport =
(handle == p_dev_rec->hci_handle) ? BT_TRANSPORT_BR_EDR : BT_TRANSPORT_LE;
+ p_dev_rec->rs_disc_pending = BTM_SEC_RS_NOT_PENDING; /* reset flag */
+
+#if (BTM_DISC_DURING_RS == TRUE)
+ LOG_INFO(LOG_TAG, "%s clearing pending flag handle:%d reason:%d", __func__,
+ handle, reason);
+ p_dev_rec->rs_disc_pending = BTM_SEC_RS_NOT_PENDING; /* reset flag */
+#endif
+
/* clear unused flags */
p_dev_rec->sm4 &= BTM_SM4_TRUE;
+ VLOG(2) << __func__ << " bd_addr: " << p_dev_rec->bd_addr
+ << " name: " << p_dev_rec->sec_bd_name
+ << " state: " << btm_pair_state_descr(btm_cb.pairing_state)
+ << " reason: " << reason << " sec_req: " << std::hex
+ << p_dev_rec->security_required;
+
+ BTM_TRACE_EVENT("%s before update sec_flags=0x%x", __func__,
+ p_dev_rec->sec_flags);
+
/* If we are in the process of bonding we need to tell client that auth failed
*/
- const uint8_t old_pairing_flags = btm_cb.pairing_flags;
if ((btm_cb.pairing_state != BTM_PAIR_STATE_IDLE) &&
(btm_cb.pairing_bda == p_dev_rec->bd_addr)) {
- LOG_DEBUG("Disconnected while pairing process active handle:0x%04x",
- handle);
btm_sec_change_pairing_state(BTM_PAIR_STATE_IDLE);
p_dev_rec->sec_flags &= ~BTM_SEC_LINK_KEY_KNOWN;
+ if (btm_cb.api.p_auth_complete_callback) {
+ /* If the disconnection reason is REPEATED_ATTEMPTS,
+ send this error message to complete callback function
+ to display the error message of Repeated attempts.
+ All others, send HCI_ERR_AUTH_FAILURE. */
+ if (reason == HCI_ERR_REPEATED_ATTEMPTS) {
+ result = HCI_ERR_REPEATED_ATTEMPTS;
+ } else if (old_pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD) {
+ result = HCI_ERR_HOST_REJECT_SECURITY;
+ }
+ (*btm_cb.api.p_auth_complete_callback)(p_dev_rec->bd_addr,
+ p_dev_rec->dev_class,
+ p_dev_rec->sec_bd_name, result);
- /* If the disconnection reason is REPEATED_ATTEMPTS,
- send this error message to complete callback function
- to display the error message of Repeated attempts.
- All others, send HCI_ERR_AUTH_FAILURE. */
- tHCI_STATUS status = HCI_ERR_AUTH_FAILURE;
- if (reason == HCI_ERR_REPEATED_ATTEMPTS) {
- status = HCI_ERR_REPEATED_ATTEMPTS;
- } else if (old_pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD) {
- status = HCI_ERR_HOST_REJECT_SECURITY;
- }
- NotifyBondingChange(*p_dev_rec, status);
-
- p_dev_rec = btm_find_dev_by_handle(handle);
- if (p_dev_rec == nullptr) {
// |btm_cb.api.p_auth_complete_callback| may cause |p_dev_rec| to be
// deallocated.
- LOG_WARN("Device record was deallocated after user callback");
- return;
+ p_dev_rec = btm_find_dev_by_handle(handle);
+ if (!p_dev_rec) {
+ return;
+ }
}
}
- LOG_DEBUG(
- "Disconnection complete device:%s name:%s state:%s reason:%s sec_req:%x",
- PRIVATE_ADDRESS(p_dev_rec->bd_addr), p_dev_rec->sec_bd_name,
- btm_pair_state_descr(btm_cb.pairing_state),
- hci_reason_code_text(reason).c_str(), p_dev_rec->security_required);
-
- // TODO Should this be gated by the transport check below ?
btm_ble_update_mode_operation(HCI_ROLE_UNKNOWN, &p_dev_rec->bd_addr,
HCI_SUCCESS);
/* see sec_flags processing in btm_acl_removed */
if (transport == BT_TRANSPORT_LE) {
- p_dev_rec->ble_hci_handle = HCI_INVALID_HANDLE;
- p_dev_rec->sec_flags &= ~(BTM_SEC_LE_AUTHENTICATED | BTM_SEC_LE_ENCRYPTED |
- BTM_SEC_ROLE_SWITCHED);
+ p_dev_rec->ble_hci_handle = BTM_SEC_INVALID_HANDLE;
+ p_dev_rec->sec_flags &= ~(BTM_SEC_LE_AUTHENTICATED | BTM_SEC_LE_ENCRYPTED);
p_dev_rec->enc_key_size = 0;
- if ((p_dev_rec->sec_flags & BTM_SEC_LE_LINK_KEY_KNOWN) == 0) {
- p_dev_rec->sec_flags &=
- ~(BTM_SEC_LE_LINK_KEY_AUTHED | BTM_SEC_LE_AUTHENTICATED);
- }
-
// This is for chips that don't support being in connected and advertising
// state at same time.
- if (!p_dev_rec->IsLocallyInitiated()) {
+ if (!p_dev_rec->is_originator) {
btm_ble_advertiser_notify_terminated_legacy(HCI_SUCCESS, handle);
}
} else {
- p_dev_rec->hci_handle = HCI_INVALID_HANDLE;
+ p_dev_rec->hci_handle = BTM_SEC_INVALID_HANDLE;
p_dev_rec->sec_flags &=
- ~(BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED | BTM_SEC_ROLE_SWITCHED |
- BTM_SEC_16_DIGIT_PIN_AUTHED);
+ ~(BTM_SEC_AUTHORIZED | BTM_SEC_AUTHENTICATED | BTM_SEC_ENCRYPTED |
+ BTM_SEC_ROLE_SWITCHED | BTM_SEC_16_DIGIT_PIN_AUTHED);
// Remove temporary key.
- if (p_dev_rec->bond_type == tBTM_SEC_DEV_REC::BOND_TYPE_TEMPORARY)
+ if (p_dev_rec->bond_type == BOND_TYPE_TEMPORARY)
p_dev_rec->sec_flags &= ~(BTM_SEC_LINK_KEY_KNOWN);
}
@@ -3781,9 +4361,10 @@ void btm_sec_disconnected(uint16_t handle, tHCI_REASON reason) {
return;
}
+ BTM_TRACE_EVENT("%s after update sec_flags=0x%x", __func__,
+ p_dev_rec->sec_flags);
+
if (p_dev_rec->sec_state == BTM_SEC_STATE_DISCONNECTING_BOTH) {
- LOG_DEBUG("Waiting for other transport to disconnect current:%s",
- bt_transport_text(transport).c_str());
p_dev_rec->sec_state = (transport == BT_TRANSPORT_LE)
? BTM_SEC_STATE_DISCONNECTING
: BTM_SEC_STATE_DISCONNECTING_BLE;
@@ -3792,16 +4373,17 @@ void btm_sec_disconnected(uint16_t handle, tHCI_REASON reason) {
p_dev_rec->sec_state = BTM_SEC_STATE_IDLE;
p_dev_rec->security_required = BTM_SEC_NONE;
- if (p_dev_rec->p_callback != nullptr) {
- tBTM_SEC_CALLBACK* p_callback = p_dev_rec->p_callback;
- /* when the peer device time out the authentication before
- we do, this call back must be reset here */
- p_dev_rec->p_callback = nullptr;
+ p_callback = p_dev_rec->p_callback;
+
+ /* if security is pending, send callback to clean up the security state */
+ if (p_callback) {
+ BTM_TRACE_DEBUG("%s: clearing callback. p_dev_rec=%p, p_callback=%p",
+ __func__, p_dev_rec, p_dev_rec->p_callback);
+ p_dev_rec->p_callback =
+ NULL; /* when the peer device time out the authentication before
+ we do, this call back must be reset here */
(*p_callback)(&p_dev_rec->bd_addr, transport, p_dev_rec->p_ref_data,
BTM_ERR_PROCESSING);
- LOG_DEBUG("Cleaned up pending security state device:%s transport:%s",
- PRIVATE_ADDRESS(p_dev_rec->bd_addr),
- bt_transport_text(transport).c_str());
}
}
@@ -3835,7 +4417,6 @@ void btm_sec_link_key_notification(const RawAddress& p_bda,
if (p_dev_rec->pin_code_length >= 16 ||
p_dev_rec->link_key_type == BTM_LKEY_TYPE_AUTH_COMB ||
p_dev_rec->link_key_type == BTM_LKEY_TYPE_AUTH_COMB_P_256) {
- p_dev_rec->sec_flags |= BTM_SEC_LINK_KEY_AUTHED;
p_dev_rec->sec_flags |= BTM_SEC_16_DIGIT_PIN_AUTHED;
}
@@ -3884,7 +4465,8 @@ void btm_sec_link_key_notification(const RawAddress& p_bda,
/* If it is for bonding nothing else will follow, so we need to start name
* resolution */
if (we_are_bonding) {
- SendRemoteNameRequest(p_bda);
+ btsnd_hcic_rmt_name_req(p_bda, HCI_PAGE_SCAN_REP_MODE_R1,
+ HCI_MANDATARY_PAGE_SCAN_MODE, 0);
}
BTM_TRACE_EVENT("rmt_io_caps:%d, sec_flags:x%x, dev_class[1]:x%02x",
@@ -3893,6 +4475,19 @@ void btm_sec_link_key_notification(const RawAddress& p_bda,
return;
}
+ /* If its not us who perform authentication, we should tell stackserver */
+ /* that some authentication has been completed */
+ /* This is required when different entities receive link notification and auth
+ * complete */
+ if (!(p_dev_rec->security_required & BTM_SEC_OUT_AUTHENTICATE)
+ /* for derived key, always send authentication callback for BR channel */
+ || ltk_derived_lk) {
+ if (btm_cb.api.p_auth_complete_callback)
+ (*btm_cb.api.p_auth_complete_callback)(
+ p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
+ HCI_SUCCESS);
+ }
+
/* We will save link key only if the user authorized it - BTE report link key in
* all cases */
#ifdef BRCM_NONE_BTE
@@ -3923,10 +4518,7 @@ void btm_sec_link_key_notification(const RawAddress& p_bda,
* Returns Pointer to the record or NULL
*
******************************************************************************/
-void btm_sec_link_key_request(uint8_t* p_event) {
- RawAddress bda;
-
- STREAM_TO_BDADDR(bda, p_event);
+void btm_sec_link_key_request(const RawAddress& bda) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_or_alloc_dev(bda);
VLOG(2) << __func__ << " bda: " << bda;
@@ -3969,7 +4561,7 @@ static void btm_sec_pairing_timeout(UNUSED_ATTR void* data) {
tBTM_AUTH_REQ auth_req = (btm_cb.devcb.loc_io_caps == BTM_IO_CAP_NONE)
? BTM_AUTH_AP_NO
: BTM_AUTH_AP_YES;
- BD_NAME name;
+ uint8_t name[2];
p_dev_rec = btm_find_dev(p_cb->pairing_bda);
@@ -3993,7 +4585,9 @@ static void btm_sec_pairing_timeout(UNUSED_ATTR void* data) {
(*btm_cb.api.p_auth_complete_callback)(p_cb->pairing_bda, NULL, name,
HCI_ERR_CONNECTION_TOUT);
} else
- NotifyBondingChange(*p_dev_rec, HCI_ERR_CONNECTION_TOUT);
+ (*btm_cb.api.p_auth_complete_callback)(
+ p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
+ HCI_ERR_CONNECTION_TOUT);
}
break;
@@ -4011,7 +4605,9 @@ static void btm_sec_pairing_timeout(UNUSED_ATTR void* data) {
break;
case BTM_PAIR_STATE_WAIT_LOCAL_IOCAPS:
- // TODO(optedoblivion): Inject OOB_DATA_PRESENT Flag
+ if (btm_cb.pairing_flags & BTM_PAIR_FLAGS_WE_STARTED_DD)
+ auth_req |= BTM_AUTH_DD_BOND;
+
btsnd_hcic_io_cap_req_reply(p_cb->pairing_bda, btm_cb.devcb.loc_io_caps,
BTM_OOB_NONE, auth_req);
btm_sec_change_pairing_state(BTM_PAIR_STATE_IDLE);
@@ -4047,9 +4643,10 @@ static void btm_sec_pairing_timeout(UNUSED_ATTR void* data) {
name[0] = 0;
(*btm_cb.api.p_auth_complete_callback)(p_cb->pairing_bda, NULL, name,
HCI_ERR_CONNECTION_TOUT);
- } else {
- NotifyBondingChange(*p_dev_rec, HCI_ERR_CONNECTION_TOUT);
- }
+ } else
+ (*btm_cb.api.p_auth_complete_callback)(
+ p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
+ HCI_ERR_CONNECTION_TOUT);
}
break;
@@ -4070,16 +4667,9 @@ static void btm_sec_pairing_timeout(UNUSED_ATTR void* data) {
* Returns Pointer to the record or NULL
*
******************************************************************************/
-void btm_sec_pin_code_request(uint8_t* p_event) {
+void btm_sec_pin_code_request(const RawAddress& p_bda) {
tBTM_SEC_DEV_REC* p_dev_rec;
tBTM_CB* p_cb = &btm_cb;
- RawAddress p_bda;
-
- STREAM_TO_BDADDR(p_bda, p_event);
-
- /* Tell L2CAP that there was a PIN code request, */
- /* it may need to stretch timeouts */
- l2c_pin_code_request(p_bda);
VLOG(2) << __func__ << " BDA: " << p_bda
<< " state: " << btm_pair_state_descr(btm_cb.pairing_state);
@@ -4113,6 +4703,8 @@ void btm_sec_pin_code_request(uint8_t* p_event) {
btm_cb.pairing_bda = p_bda;
btm_cb.pairing_flags = BTM_PAIR_FLAGS_PEER_STARTED_DD;
+ /* Make sure we reset the trusted mask to help against attacks */
+ BTM_SEC_CLR_TRUSTED_DEVICE(p_dev_rec->trusted_mask);
}
if (!p_cb->pairing_disabled && (p_cb->cfg.pin_type == HCI_PIN_TYPE_FIXED)) {
@@ -4147,19 +4739,19 @@ void btm_sec_pin_code_request(uint8_t* p_event) {
/* If pairing disabled OR (no PIN callback and not bonding) */
/* OR we could not allocate entry in the database reject pairing request */
- else if (p_cb->pairing_disabled ||
- (p_cb->api.p_pin_callback == NULL)
-
- /* OR Microsoft keyboard can for some reason try to establish
- * connection
- */
- /* the only thing we can do here is to shut it up. Normally we will
- be originator */
- /* for keyboard bonding */
- || (!p_dev_rec->IsLocallyInitiated() &&
- ((p_dev_rec->dev_class[1] & BTM_COD_MAJOR_CLASS_MASK) ==
- BTM_COD_MAJOR_PERIPHERAL) &&
- (p_dev_rec->dev_class[2] & BTM_COD_MINOR_KEYBOARD))) {
+ else if (
+ p_cb->pairing_disabled ||
+ (p_cb->api.p_pin_callback == NULL)
+
+ /* OR Microsoft keyboard can for some reason try to establish connection
+ */
+ /* the only thing we can do here is to shut it up. Normally we will be
+ originator */
+ /* for keyboard bonding */
+ || (!p_dev_rec->is_originator &&
+ ((p_dev_rec->dev_class[1] & BTM_COD_MAJOR_CLASS_MASK) ==
+ BTM_COD_MAJOR_PERIPHERAL) &&
+ (p_dev_rec->dev_class[2] & BTM_COD_MINOR_KEYBOARD))) {
BTM_TRACE_WARNING(
"btm_sec_pin_code_request(): Pairing disabled:%d; PIN callback:%x, Dev "
"Rec:%x!",
@@ -4187,8 +4779,10 @@ void btm_sec_pin_code_request(uint8_t* p_event) {
if (p_cb->api.p_pin_callback) {
(*p_cb->api.p_pin_callback)(
p_bda, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
- (p_dev_rec->required_security_flags_for_pairing &
- BTM_SEC_IN_MIN_16_DIGIT_PIN));
+ (p_dev_rec->p_cur_service == NULL)
+ ? false
+ : (p_dev_rec->p_cur_service->security_flags &
+ BTM_SEC_IN_MIN_16_DIGIT_PIN));
}
} else {
BTM_TRACE_EVENT("btm_sec_pin_code_request going for remote name");
@@ -4196,7 +4790,8 @@ void btm_sec_pin_code_request(uint8_t* p_event) {
/* We received PIN code request for the device with unknown name */
/* it is not user friendly just to ask for the PIN without name */
/* try to get name at first */
- SendRemoteNameRequest(p_dev_rec->bd_addr);
+ btsnd_hcic_rmt_name_req(p_dev_rec->bd_addr, HCI_PAGE_SCAN_REP_MODE_R1,
+ HCI_MANDATARY_PAGE_SCAN_MODE, 0);
}
}
@@ -4227,11 +4822,6 @@ void btm_sec_update_clock_offset(uint16_t handle, uint16_t clock_offset) {
p_inq_info->results.clock_offset = clock_offset | BTM_CLOCK_OFFSET_VALID;
}
-uint16_t BTM_GetClockOffset(const RawAddress& remote_bda) {
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(remote_bda);
- return (p_dev_rec) ? p_dev_rec->clock_offset : 0;
-}
-
/******************************************************************
* S T A T I C F U N C T I O N S
******************************************************************/
@@ -4252,31 +4842,18 @@ uint16_t BTM_GetClockOffset(const RawAddress& remote_bda) {
*
******************************************************************************/
tBTM_STATUS btm_sec_execute_procedure(tBTM_SEC_DEV_REC* p_dev_rec) {
- CHECK(p_dev_rec != nullptr);
- LOG_DEBUG(
- "security_required:0x%x security_flags:0x%x security_state:%s[%hhu]",
- p_dev_rec->security_required, p_dev_rec->sec_flags,
- security_state_text(static_cast<tSECURITY_STATE>(p_dev_rec->sec_state))
- .c_str(),
- p_dev_rec->sec_state);
-
- if (p_dev_rec->sec_state != BTM_SEC_STATE_IDLE) {
- LOG_DEBUG(
- "Security state is idle indicating remote name request is outstanding");
- return (BTM_CMD_STARTED);
- }
+ BTM_TRACE_EVENT(
+ "btm_sec_execute_procedure: Required:0x%x Flags:0x%x State:%d",
+ p_dev_rec->security_required, p_dev_rec->sec_flags, p_dev_rec->sec_state);
- if (!bluetooth::shim::is_gd_acl_enabled()) {
- // Load the SM4 values //
- HACK_acl_check_sm4(*p_dev_rec);
- }
+ /* There is a chance that we are getting name. Wait until done. */
+ if (p_dev_rec->sec_state != 0) return (BTM_CMD_STARTED);
/* If any security is required, get the name first */
if (!(p_dev_rec->sec_flags & BTM_SEC_NAME_KNOWN) &&
- (p_dev_rec->hci_handle != HCI_INVALID_HANDLE)) {
- LOG_DEBUG("Security Manager: Start get name");
+ (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE)) {
+ BTM_TRACE_EVENT("Security Manager: Start get name");
if (!btm_sec_start_get_name(p_dev_rec)) {
- LOG_WARN("Unable to start remote name request");
return (BTM_NO_RESOURCES);
}
return (BTM_CMD_STARTED);
@@ -4285,22 +4862,22 @@ tBTM_STATUS btm_sec_execute_procedure(tBTM_SEC_DEV_REC* p_dev_rec) {
/* If connection is not authenticated and authentication is required */
/* start authentication and return PENDING to the caller */
if ((((!(p_dev_rec->sec_flags & BTM_SEC_AUTHENTICATED)) &&
- ((p_dev_rec->IsLocallyInitiated() &&
+ ((p_dev_rec->is_originator &&
(p_dev_rec->security_required & BTM_SEC_OUT_AUTHENTICATE)) ||
- (!p_dev_rec->IsLocallyInitiated() &&
+ (!p_dev_rec->is_originator &&
(p_dev_rec->security_required & BTM_SEC_IN_AUTHENTICATE)))) ||
(!(p_dev_rec->sec_flags & BTM_SEC_16_DIGIT_PIN_AUTHED) &&
- (!p_dev_rec->IsLocallyInitiated() &&
+ (!p_dev_rec->is_originator &&
(p_dev_rec->security_required & BTM_SEC_IN_MIN_16_DIGIT_PIN)))) &&
- (p_dev_rec->hci_handle != HCI_INVALID_HANDLE)) {
- /*
- * We rely on BTM_SEC_16_DIGIT_PIN_AUTHED being set if MITM is in use,
- * as 16 DIGIT is only needed if MITM is not used. Unfortunately, the
- * BTM_SEC_AUTHENTICATED is used for both MITM and non-MITM
- * authenticated connections, hence we cannot distinguish here.
- */
+ (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE)) {
+/*
+ * We rely on BTM_SEC_16_DIGIT_PIN_AUTHED being set if MITM is in use,
+ * as 16 DIGIT is only needed if MITM is not used. Unfortunately, the
+ * BTM_SEC_AUTHENTICATED is used for both MITM and non-MITM
+ * authenticated connections, hence we cannot distinguish here.
+ */
- LOG_DEBUG("Security Manager: Start authentication");
+ BTM_TRACE_EVENT("Security Manager: Start authentication");
/*
* If we do have a link-key, but we end up here because we need an
@@ -4315,7 +4892,7 @@ tBTM_STATUS btm_sec_execute_procedure(tBTM_SEC_DEV_REC* p_dev_rec) {
*/
if ((p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_KNOWN) &&
(!(p_dev_rec->sec_flags & BTM_SEC_16_DIGIT_PIN_AUTHED) &&
- (!p_dev_rec->IsLocallyInitiated() &&
+ (!p_dev_rec->is_originator &&
(p_dev_rec->security_required & BTM_SEC_IN_MIN_16_DIGIT_PIN)))) {
p_dev_rec->sec_flags &=
~(BTM_SEC_LINK_KEY_KNOWN | BTM_SEC_LINK_KEY_AUTHED |
@@ -4324,25 +4901,21 @@ tBTM_STATUS btm_sec_execute_procedure(tBTM_SEC_DEV_REC* p_dev_rec) {
btm_sec_start_authentication(p_dev_rec);
return (BTM_CMD_STARTED);
- } else {
- LOG_DEBUG("Authentication not required");
}
/* If connection is not encrypted and encryption is required */
/* start encryption and return PENDING to the caller */
if (!(p_dev_rec->sec_flags & BTM_SEC_ENCRYPTED) &&
- ((p_dev_rec->IsLocallyInitiated() &&
+ ((p_dev_rec->is_originator &&
(p_dev_rec->security_required & BTM_SEC_OUT_ENCRYPT)) ||
- (!p_dev_rec->IsLocallyInitiated() &&
+ (!p_dev_rec->is_originator &&
(p_dev_rec->security_required & BTM_SEC_IN_ENCRYPT))) &&
- (p_dev_rec->hci_handle != HCI_INVALID_HANDLE)) {
+ (p_dev_rec->hci_handle != BTM_SEC_INVALID_HANDLE)) {
+
BTM_TRACE_EVENT("Security Manager: Start encryption");
- btsnd_hcic_set_conn_encrypt(p_dev_rec->hci_handle, true);
- p_dev_rec->sec_state = BTM_SEC_STATE_ENCRYPTING;
+ btm_sec_start_encryption(p_dev_rec);
return (BTM_CMD_STARTED);
- } else {
- LOG_DEBUG("Encryption not required");
}
if ((p_dev_rec->security_required & BTM_SEC_MODE4_LEVEL4) &&
@@ -4353,11 +4926,35 @@ tBTM_STATUS btm_sec_execute_procedure(tBTM_SEC_DEV_REC* p_dev_rec) {
return (BTM_FAILED_ON_SECURITY);
}
+ /* If connection is not authorized and authorization is required */
+ /* start authorization and return PENDING to the caller */
+ if (!(p_dev_rec->sec_flags & BTM_SEC_AUTHORIZED) &&
+ ((p_dev_rec->is_originator &&
+ (p_dev_rec->security_required & BTM_SEC_OUT_AUTHORIZE)) ||
+ (!p_dev_rec->is_originator &&
+ (p_dev_rec->security_required & BTM_SEC_IN_AUTHORIZE)))) {
+ BTM_TRACE_EVENT(
+ "service id:%d, is trusted:%d", p_dev_rec->p_cur_service->service_id,
+ (BTM_SEC_IS_SERVICE_TRUSTED(p_dev_rec->trusted_mask,
+ p_dev_rec->p_cur_service->service_id)));
+ if ((!btm_sec_are_all_trusted(p_dev_rec->trusted_mask)) &&
+ (p_dev_rec->p_cur_service->service_id < BTM_SEC_MAX_SERVICES) &&
+ (!BTM_SEC_IS_SERVICE_TRUSTED(p_dev_rec->trusted_mask,
+ p_dev_rec->p_cur_service->service_id))) {
+ BTM_TRACE_EVENT("Security Manager: Start authorization");
+ return (btm_sec_start_authorization(p_dev_rec));
+ }
+ }
+
/* All required security procedures already established */
p_dev_rec->security_required &=
- ~(BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_IN_AUTHENTICATE |
- BTM_SEC_OUT_ENCRYPT | BTM_SEC_IN_ENCRYPT);
+ ~(BTM_SEC_OUT_AUTHORIZE | BTM_SEC_IN_AUTHORIZE |
+ BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_IN_AUTHENTICATE |
+ BTM_SEC_OUT_ENCRYPT | BTM_SEC_IN_ENCRYPT | BTM_SEC_FORCE_MASTER |
+ BTM_SEC_ATTEMPT_MASTER | BTM_SEC_FORCE_SLAVE | BTM_SEC_ATTEMPT_SLAVE);
+ BTM_TRACE_EVENT("Security Manager: trusted:0x%04x%04x",
+ p_dev_rec->trusted_mask[1], p_dev_rec->trusted_mask[0]);
BTM_TRACE_EVENT("Security Manager: access granted");
return (BTM_SUCCESS);
@@ -4373,14 +4970,19 @@ tBTM_STATUS btm_sec_execute_procedure(tBTM_SEC_DEV_REC* p_dev_rec) {
*
******************************************************************************/
static bool btm_sec_start_get_name(tBTM_SEC_DEV_REC* p_dev_rec) {
- if (!BTM_IsDeviceUp()) return false;
+ uint8_t tempstate = p_dev_rec->sec_state;
p_dev_rec->sec_state = BTM_SEC_STATE_GETTING_NAME;
/* 0 and NULL are as timeout and callback params because they are not used in
* security get name case */
- SendRemoteNameRequest(p_dev_rec->bd_addr);
- return true;
+ if ((btm_initiate_rem_name(p_dev_rec->bd_addr, BTM_RMT_NAME_SEC, 0, NULL)) !=
+ BTM_CMD_STARTED) {
+ p_dev_rec->sec_state = tempstate;
+ return (false);
+ }
+
+ return (true);
}
/*******************************************************************************
@@ -4397,6 +4999,101 @@ static void btm_sec_start_authentication(tBTM_SEC_DEV_REC* p_dev_rec) {
/*******************************************************************************
*
+ * Function btm_sec_start_encryption
+ *
+ * Description This function is called to start encryption
+ *
+ ******************************************************************************/
+static void btm_sec_start_encryption(tBTM_SEC_DEV_REC* p_dev_rec) {
+ btsnd_hcic_set_conn_encrypt(p_dev_rec->hci_handle, true);
+ p_dev_rec->sec_state = BTM_SEC_STATE_ENCRYPTING;
+}
+
+/*******************************************************************************
+ *
+ * Function btm_sec_start_authorization
+ *
+ * Description This function is called to start authorization
+ *
+ * Returns true if started
+ *
+ ******************************************************************************/
+static uint8_t btm_sec_start_authorization(tBTM_SEC_DEV_REC* p_dev_rec) {
+ uint8_t result;
+ uint8_t* p_service_name = NULL;
+ uint8_t service_id;
+
+ if ((p_dev_rec->sec_flags & BTM_SEC_NAME_KNOWN) ||
+ (p_dev_rec->hci_handle == BTM_SEC_INVALID_HANDLE)) {
+ if (!btm_cb.api.p_authorize_callback) return (BTM_MODE_UNSUPPORTED);
+
+ if (p_dev_rec->p_cur_service) {
+#if BTM_SEC_SERVICE_NAME_LEN > 0
+ if (p_dev_rec->is_originator)
+ p_service_name = p_dev_rec->p_cur_service->orig_service_name;
+ else
+ p_service_name = p_dev_rec->p_cur_service->term_service_name;
+#endif
+ service_id = p_dev_rec->p_cur_service->service_id;
+ } else
+ service_id = 0;
+
+ /* Send authorization request if not already sent during this service
+ * connection */
+ if (p_dev_rec->last_author_service_id == BTM_SEC_NO_LAST_SERVICE_ID ||
+ p_dev_rec->last_author_service_id != service_id) {
+ p_dev_rec->sec_state = BTM_SEC_STATE_AUTHORIZING;
+ result = (*btm_cb.api.p_authorize_callback)(
+ p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
+ p_service_name, service_id, p_dev_rec->is_originator);
+ }
+
+ else /* Already authorized once for this L2CAP bringup */
+ {
+ BTM_TRACE_DEBUG(
+ "btm_sec_start_authorization: (Ignoring extra Authorization prompt "
+ "for service %d)",
+ service_id);
+ return (BTM_SUCCESS);
+ }
+
+ if (result == BTM_SUCCESS) {
+ p_dev_rec->sec_flags |= BTM_SEC_AUTHORIZED;
+
+ /* Save the currently authorized service in case we are asked again by
+ * another multiplexer layer */
+ if (!p_dev_rec->is_originator)
+ p_dev_rec->last_author_service_id = service_id;
+
+ p_dev_rec->sec_state = BTM_SEC_STATE_IDLE;
+ }
+ return (result);
+ }
+ btm_sec_start_get_name(p_dev_rec);
+ return (BTM_CMD_STARTED);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_sec_are_all_trusted
+ *
+ * Description This function is called check if all services are trusted
+ *
+ * Returns true if all are trusted, otherwise false
+ *
+ ******************************************************************************/
+bool btm_sec_are_all_trusted(uint32_t p_mask[]) {
+ uint32_t trusted_inx;
+ for (trusted_inx = 0; trusted_inx < BTM_SEC_SERVICE_ARRAY_SIZE;
+ trusted_inx++) {
+ if (p_mask[trusted_inx] != BTM_SEC_TRUST_ALL) return (false);
+ }
+
+ return (true);
+}
+
+/*******************************************************************************
+ *
* Function btm_sec_find_first_serv
*
* Description Look for the first record in the service database
@@ -4405,9 +5102,11 @@ static void btm_sec_start_authentication(tBTM_SEC_DEV_REC* p_dev_rec) {
* Returns Pointer to the record or NULL
*
******************************************************************************/
-tBTM_SEC_SERV_REC* btm_sec_find_first_serv(bool is_originator, uint16_t psm) {
+tBTM_SEC_SERV_REC* btm_sec_find_first_serv(CONNECTION_TYPE conn_type,
+ uint16_t psm) {
tBTM_SEC_SERV_REC* p_serv_rec = &btm_cb.sec_serv_rec[0];
int i;
+ bool is_originator = conn_type;
if (is_originator && btm_cb.p_out_serv && btm_cb.p_out_serv->psm == psm) {
/* If this is outgoing connection and the PSM matches p_out_serv,
@@ -4426,6 +5125,70 @@ tBTM_SEC_SERV_REC* btm_sec_find_first_serv(bool is_originator, uint16_t psm) {
/*******************************************************************************
*
+ * Function btm_sec_find_next_serv
+ *
+ * Description Look for the next record in the service database
+ * with specified PSM
+ *
+ * Returns Pointer to the record or NULL
+ *
+ ******************************************************************************/
+static tBTM_SEC_SERV_REC* btm_sec_find_next_serv(tBTM_SEC_SERV_REC* p_cur) {
+ tBTM_SEC_SERV_REC* p_serv_rec = &btm_cb.sec_serv_rec[0];
+ int i;
+
+ for (i = 0; i < BTM_SEC_MAX_SERVICE_RECORDS; i++, p_serv_rec++) {
+ if ((p_serv_rec->security_flags & BTM_SEC_IN_USE) &&
+ (p_serv_rec->psm == p_cur->psm)) {
+ if (p_cur != p_serv_rec) {
+ return (p_serv_rec);
+ }
+ }
+ }
+ return (NULL);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_sec_find_mx_serv
+ *
+ * Description Look for the record in the service database with specified
+ * PSM and multiplexor channel information
+ *
+ * Returns Pointer to the record or NULL
+ *
+ ******************************************************************************/
+static tBTM_SEC_SERV_REC* btm_sec_find_mx_serv(uint8_t is_originator,
+ uint16_t psm,
+ uint32_t mx_proto_id,
+ uint32_t mx_chan_id) {
+ tBTM_SEC_SERV_REC* p_out_serv = btm_cb.p_out_serv;
+ tBTM_SEC_SERV_REC* p_serv_rec = &btm_cb.sec_serv_rec[0];
+ int i;
+
+ BTM_TRACE_DEBUG("%s()", __func__);
+ if (is_originator && p_out_serv && p_out_serv->psm == psm &&
+ p_out_serv->mx_proto_id == mx_proto_id &&
+ p_out_serv->orig_mx_chan_id == mx_chan_id) {
+ /* If this is outgoing connection and the parameters match p_out_serv,
+ * use it as the current service */
+ return btm_cb.p_out_serv;
+ }
+
+ /* otherwise, the old way */
+ for (i = 0; i < BTM_SEC_MAX_SERVICE_RECORDS; i++, p_serv_rec++) {
+ if ((p_serv_rec->security_flags & BTM_SEC_IN_USE) &&
+ (p_serv_rec->psm == psm) && (p_serv_rec->mx_proto_id == mx_proto_id) &&
+ ((is_originator && (p_serv_rec->orig_mx_chan_id == mx_chan_id)) ||
+ (!is_originator && (p_serv_rec->term_mx_chan_id == mx_chan_id)))) {
+ return (p_serv_rec);
+ }
+ }
+ return (NULL);
+}
+
+/*******************************************************************************
+ *
* Function btm_sec_collision_timeout
*
* Description Encryption could not start because of the collision
@@ -4465,6 +5228,24 @@ static void btm_send_link_key_notif(tBTM_SEC_DEV_REC* p_dev_rec) {
/*******************************************************************************
*
+ * Function BTM_ReadTrustedMask
+ *
+ * Description Get trusted mask for the peer device
+ *
+ * Parameters: bd_addr - Address of the device
+ *
+ * Returns NULL, if the device record is not found.
+ * otherwise, the trusted mask
+ *
+ ******************************************************************************/
+uint32_t* BTM_ReadTrustedMask(const RawAddress& bd_addr) {
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
+ if (p_dev_rec != NULL) return (p_dev_rec->trusted_mask);
+ return NULL;
+}
+
+/*******************************************************************************
+ *
* Function btm_restore_mode
*
* Description This function returns the security mode to previous setting
@@ -4477,7 +5258,10 @@ static void btm_send_link_key_notif(tBTM_SEC_DEV_REC* p_dev_rec) {
static void btm_restore_mode(void) {
if (btm_cb.security_mode_changed) {
btm_cb.security_mode_changed = false;
- btsnd_hcic_write_auth_enable(false);
+ BTM_TRACE_DEBUG("%s() Auth enable -> %d", __func__,
+ (btm_cb.security_mode == BTM_SEC_MODE_LINK));
+ btsnd_hcic_write_auth_enable(
+ (uint8_t)(btm_cb.security_mode == BTM_SEC_MODE_LINK));
}
if (btm_cb.pin_type_changed) {
@@ -4522,14 +5306,11 @@ tBTM_SEC_DEV_REC* btm_sec_find_dev_by_sec_state(uint8_t state) {
static void btm_sec_change_pairing_state(tBTM_PAIRING_STATE new_state) {
tBTM_PAIRING_STATE old_state = btm_cb.pairing_state;
- LOG_DEBUG("Pairing state changed %s => %s pairing_flags:0x%x",
- btm_pair_state_descr(btm_cb.pairing_state),
- btm_pair_state_descr(new_state), btm_cb.pairing_flags);
+ BTM_TRACE_EVENT("%s() Old: %s", __func__,
+ btm_pair_state_descr(btm_cb.pairing_state));
+ BTM_TRACE_EVENT("%s() New: %s pairing_flags:0x%x", __func__,
+ btm_pair_state_descr(new_state), btm_cb.pairing_flags);
- BTM_LogHistory(
- kBtmLogTag, btm_cb.pairing_bda, "Pairing state changed",
- base::StringPrintf("%s => %s", btm_pair_state_descr(btm_cb.pairing_state),
- btm_pair_state_descr(new_state)));
btm_cb.pairing_state = new_state;
if (new_state == BTM_PAIR_STATE_IDLE) {
@@ -4602,37 +5383,28 @@ static const char* btm_pair_state_descr(tBTM_PAIRING_STATE state) {
* Parameters: void
*
******************************************************************************/
-void btm_sec_dev_rec_cback_event(tBTM_SEC_DEV_REC* p_dev_rec,
- tBTM_STATUS btm_status, bool is_le_transport) {
- ASSERT(p_dev_rec != nullptr);
- LOG_DEBUG("transport=%s, btm_status=%s", is_le_transport ? "le" : "classic",
- btm_status_text(btm_status).c_str());
-
+void btm_sec_dev_rec_cback_event(tBTM_SEC_DEV_REC* p_dev_rec, uint8_t res,
+ bool is_le_transport) {
tBTM_SEC_CALLBACK* p_callback = p_dev_rec->p_callback;
- p_dev_rec->p_callback = NULL;
- if (p_callback != nullptr) {
- if (is_le_transport) {
+
+ BTM_TRACE_DEBUG("%s: p_callback=%p, is_le_transport=%d, res=%d, p_dev_rec=%p",
+ __func__, p_dev_rec->p_callback, is_le_transport, res,
+ p_dev_rec);
+
+ if (p_dev_rec->p_callback) {
+ p_dev_rec->p_callback = NULL;
+
+ if (is_le_transport)
(*p_callback)(&p_dev_rec->ble.pseudo_addr, BT_TRANSPORT_LE,
- p_dev_rec->p_ref_data, btm_status);
- } else {
+ p_dev_rec->p_ref_data, res);
+ else
(*p_callback)(&p_dev_rec->bd_addr, BT_TRANSPORT_BR_EDR,
- p_dev_rec->p_ref_data, btm_status);
- }
+ p_dev_rec->p_ref_data, res);
}
btm_sec_check_pending_reqs();
}
-void btm_sec_cr_loc_oob_data_cback_event(const RawAddress& address,
- tSMP_LOC_OOB_DATA loc_oob_data) {
- tBTM_LE_EVT_DATA evt_data = {
- .local_oob_data = loc_oob_data,
- };
- if (btm_cb.api.p_le_callback) {
- (*btm_cb.api.p_le_callback)(BTM_LE_SC_LOC_OOB_EVT, address, &evt_data);
- }
-}
-
/*******************************************************************************
*
* Function btm_sec_queue_mx_request
@@ -4652,8 +5424,10 @@ static bool btm_sec_queue_mx_request(const RawAddress& bd_addr, uint16_t psm,
p_e->is_orig = is_orig;
p_e->p_callback = p_callback;
p_e->p_ref_data = p_ref_data;
+ p_e->mx_proto_id = mx_proto_id;
+ p_e->mx_chan_id = mx_chan_id;
p_e->transport = BT_TRANSPORT_BR_EDR;
- p_e->sec_act = BTM_BLE_SEC_NONE;
+ p_e->sec_act = 0;
p_e->bd_addr = bd_addr;
BTM_TRACE_EVENT(
@@ -4680,7 +5454,10 @@ static bool btm_sec_check_prefetch_pin(tBTM_SEC_DEV_REC* p_dev_rec) {
if (!btm_cb.security_mode_changed) {
btm_cb.security_mode_changed = true;
- btsnd_hcic_write_auth_enable(true);
+#ifdef APPL_AUTH_WRITE_EXCEPTION
+ if (!(APPL_AUTH_WRITE_EXCEPTION)(p_dev_rec->bd_addr))
+#endif
+ btsnd_hcic_write_auth_enable(true);
}
} else {
btm_sec_change_pairing_state(BTM_PAIR_STATE_WAIT_LOCAL_PIN);
@@ -4688,18 +5465,20 @@ static bool btm_sec_check_prefetch_pin(tBTM_SEC_DEV_REC* p_dev_rec) {
/* If we got a PIN, use that, else try to get one */
if (btm_cb.pin_code_len) {
BTM_PINCodeReply(p_dev_rec->bd_addr, BTM_SUCCESS, btm_cb.pin_code_len,
- btm_cb.pin_code);
+ btm_cb.pin_code, p_dev_rec->trusted_mask);
} else {
/* pin was not supplied - pre-fetch pin code now */
if (btm_cb.api.p_pin_callback &&
((btm_cb.pairing_flags & BTM_PAIR_FLAGS_PIN_REQD) == 0)) {
BTM_TRACE_DEBUG("%s() PIN code callback called", __func__);
- if (BTM_IsAclConnectionUp(p_dev_rec->bd_addr, BT_TRANSPORT_BR_EDR))
+ if (btm_bda_to_acl(p_dev_rec->bd_addr, BT_TRANSPORT_BR_EDR) == NULL)
btm_cb.pairing_flags |= BTM_PAIR_FLAGS_PIN_REQD;
(btm_cb.api.p_pin_callback)(
p_dev_rec->bd_addr, p_dev_rec->dev_class, p_dev_rec->sec_bd_name,
- (p_dev_rec->required_security_flags_for_pairing &
- BTM_SEC_IN_MIN_16_DIGIT_PIN));
+ (p_dev_rec->p_cur_service == NULL)
+ ? false
+ : (p_dev_rec->p_cur_service->security_flags &
+ BTM_SEC_IN_MIN_16_DIGIT_PIN));
}
}
@@ -4711,6 +5490,28 @@ static bool btm_sec_check_prefetch_pin(tBTM_SEC_DEV_REC* p_dev_rec) {
/*******************************************************************************
*
+ * Function btm_sec_auth_payload_tout
+ *
+ * Description Processes the HCI Autheniticated Payload Timeout Event
+ * indicating that a packet containing a valid MIC on the
+ * connection handle was not received within the programmed
+ * timeout value. (Spec Default is 30 secs, but can be
+ * changed via the BTM_SecSetAuthPayloadTimeout() function.
+ *
+ ******************************************************************************/
+void btm_sec_auth_payload_tout(uint8_t* p, uint16_t hci_evt_len) {
+ uint16_t handle;
+
+ STREAM_TO_UINT16(handle, p);
+ handle = HCID_GET_HANDLE(handle);
+
+ /* Will be exposed to upper layers in the future if/when determined necessary
+ */
+ BTM_TRACE_ERROR("%s on handle 0x%02x", __func__, handle);
+}
+
+/*******************************************************************************
+ *
* Function btm_sec_queue_encrypt_request
*
* Description encqueue encryption request when device has active security
@@ -4738,6 +5539,61 @@ static bool btm_sec_queue_encrypt_request(const RawAddress& bd_addr,
/*******************************************************************************
*
+ * Function btm_sec_set_peer_sec_caps
+ *
+ * Description This function is called to set sm4 and rmt_sec_caps fields
+ * based on the available peer device features.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void btm_sec_set_peer_sec_caps(tACL_CONN* p_acl_cb,
+ tBTM_SEC_DEV_REC* p_dev_rec) {
+ if ((btm_cb.security_mode == BTM_SEC_MODE_SP ||
+ btm_cb.security_mode == BTM_SEC_MODE_SP_DEBUG ||
+ btm_cb.security_mode == BTM_SEC_MODE_SC) &&
+ HCI_SSP_HOST_SUPPORTED(p_acl_cb->peer_lmp_feature_pages[1])) {
+ p_dev_rec->sm4 = BTM_SM4_TRUE;
+ p_dev_rec->remote_supports_secure_connections =
+ (HCI_SC_HOST_SUPPORTED(p_acl_cb->peer_lmp_feature_pages[1]));
+ } else {
+ p_dev_rec->sm4 = BTM_SM4_KNOWN;
+ p_dev_rec->remote_supports_secure_connections = false;
+ }
+
+ BTM_TRACE_API("%s: sm4: 0x%02x, rmt_support_for_secure_connections %d",
+ __func__, p_dev_rec->sm4,
+ p_dev_rec->remote_supports_secure_connections);
+
+ if (p_dev_rec->remote_features_needed) {
+ BTM_TRACE_EVENT(
+ "%s: Now device in SC Only mode, waiting for peer remote features!",
+ __func__);
+ btm_io_capabilities_req(p_dev_rec->bd_addr);
+ p_dev_rec->remote_features_needed = false;
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function btm_sec_is_serv_level0
+ *
+ * Description This function is called to check if the service
+ * corresponding to PSM is security mode 4 level 0 service.
+ *
+ * Returns true if the service is security mode 4 level 0 service
+ *
+ ******************************************************************************/
+static bool btm_sec_is_serv_level0(uint16_t psm) {
+ if (psm == BT_PSM_SDP) {
+ BTM_TRACE_DEBUG("%s: PSM: 0x%04x -> mode 4 level 0 service", __func__, psm);
+ return true;
+ }
+ return false;
+}
+
+/*******************************************************************************
+ *
* Function btm_sec_check_pending_enc_req
*
* Description This function is called to send pending encryption callback
@@ -4751,7 +5607,7 @@ static void btm_sec_check_pending_enc_req(tBTM_SEC_DEV_REC* p_dev_rec,
uint8_t encr_enable) {
if (fixed_queue_is_empty(btm_cb.sec_pending_q)) return;
- const tBTM_STATUS res = encr_enable ? BTM_SUCCESS : BTM_ERR_PROCESSING;
+ uint8_t res = encr_enable ? BTM_SUCCESS : BTM_ERR_PROCESSING;
list_t* list = fixed_queue_get_list(btm_cb.sec_pending_q);
for (const list_node_t* node = list_begin(list); node != list_end(list);) {
tBTM_SEC_QUEUE_ENTRY* p_e = (tBTM_SEC_QUEUE_ENTRY*)list_node(node);
@@ -4808,7 +5664,9 @@ void btm_sec_clear_ble_keys(tBTM_SEC_DEV_REC* p_dev_rec) {
p_dev_rec->ble.key_type = BTM_LE_KEY_NONE;
memset(&p_dev_rec->ble.keys, 0, sizeof(tBTM_SEC_BLE_KEYS));
+#if (BLE_PRIVACY_SPT == TRUE)
btm_ble_resolving_list_remove_dev(p_dev_rec);
+#endif
}
/*******************************************************************************
@@ -4829,9 +5687,27 @@ bool btm_sec_is_a_bonded_dev(const RawAddress& bda) {
(p_dev_rec->sec_flags & BTM_SEC_LINK_KEY_KNOWN))) {
is_bonded = true;
}
- LOG_DEBUG("Device record bonded check peer:%s is_bonded:%s",
- PRIVATE_ADDRESS(bda), logbool(is_bonded).c_str());
- return is_bonded;
+ BTM_TRACE_DEBUG("%s() is_bonded=%d", __func__, is_bonded);
+ return (is_bonded);
+}
+
+/*******************************************************************************
+ *
+ * Function btm_sec_is_le_capable_dev
+ *
+ * Description Is the specified device is dual mode or LE only device
+ *
+ * Returns true - dev is a dual mode
+ *
+ ******************************************************************************/
+bool btm_sec_is_le_capable_dev(const RawAddress& bda) {
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bda);
+ bool le_capable = false;
+
+ if (p_dev_rec &&
+ (p_dev_rec->device_type & BT_DEVICE_TYPE_BLE) == BT_DEVICE_TYPE_BLE)
+ le_capable = true;
+ return le_capable;
}
/*******************************************************************************
@@ -4869,72 +5745,15 @@ static bool btm_sec_use_smp_br_chnl(tBTM_SEC_DEV_REC* p_dev_rec) {
/*******************************************************************************
*
- * Function btm_sec_set_peer_sec_caps
+ * Function btm_sec_is_master
*
- * Description This function is called to set sm4 and rmt_sec_caps fields
- * based on the available peer device features.
+ * Description The function checks if the device is BR/EDR master after
+ * pairing is completed.
*
- * Returns void
+ * Returns true - if the device is master.
*
******************************************************************************/
-void btm_sec_set_peer_sec_caps(uint16_t hci_handle, bool ssp_supported,
- bool sc_supported,
- bool hci_role_switch_supported,
- bool br_edr_supported, bool le_supported) {
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev_by_handle(hci_handle);
- if (p_dev_rec == nullptr) return;
-
- p_dev_rec->remote_feature_received = true;
- p_dev_rec->remote_supports_hci_role_switch = hci_role_switch_supported;
-
- uint8_t req_pend = (p_dev_rec->sm4 & BTM_SM4_REQ_PEND);
-
- if (!(p_dev_rec->sec_flags & BTM_SEC_NAME_KNOWN) ||
- p_dev_rec->is_originator) {
- tBTM_STATUS btm_status = btm_sec_execute_procedure(p_dev_rec);
- if (btm_status != BTM_CMD_STARTED) {
- LOG_WARN("Security procedure not started! status:%s",
- btm_status_text(btm_status).c_str());
- btm_sec_dev_rec_cback_event(p_dev_rec, btm_status, false);
- }
- }
-
- /* Store the Peer Security Capabilites (in SM4 and rmt_sec_caps) */
- if ((btm_cb.security_mode == BTM_SEC_MODE_SP ||
- btm_cb.security_mode == BTM_SEC_MODE_SC) &&
- ssp_supported) {
- p_dev_rec->sm4 = BTM_SM4_TRUE;
- p_dev_rec->remote_supports_secure_connections = sc_supported;
- } else {
- p_dev_rec->sm4 = BTM_SM4_KNOWN;
- p_dev_rec->remote_supports_secure_connections = false;
- }
-
- if (p_dev_rec->remote_features_needed) {
- LOG_DEBUG("Now device in SC Only mode, waiting for peer remote features!");
- btm_io_capabilities_req(p_dev_rec->bd_addr);
- p_dev_rec->remote_features_needed = false;
- }
-
- if (req_pend) {
- /* Request for remaining Security Features (if any) */
- l2cu_resubmit_pending_sec_req(&p_dev_rec->bd_addr);
- }
-
- p_dev_rec->remote_supports_bredr = br_edr_supported;
- p_dev_rec->remote_supports_ble = le_supported;
-}
-
-// Return DEV_CLASS (uint8_t[3]) of bda. If record doesn't exist, create one.
-const uint8_t* btm_get_dev_class(const RawAddress& bda) {
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_or_alloc_dev(bda);
- return p_dev_rec->dev_class;
-}
-
-void BTM_update_version_info(const RawAddress& bd_addr,
- const remote_version_info& remote_version_info) {
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
- if (p_dev_rec == NULL) return;
-
- p_dev_rec->remote_version_info = remote_version_info;
+static bool btm_sec_is_master(tBTM_SEC_DEV_REC* p_dev_rec) {
+ tACL_CONN* p = btm_bda_to_acl(p_dev_rec->bd_addr, BT_TRANSPORT_BR_EDR);
+ return (p && (p->link_role == BTM_ROLE_MASTER));
}
diff --git a/stack/btm/btm_sec.h b/stack/btm/btm_sec.h
deleted file mode 100644
index 5f32f09fc..000000000
--- a/stack/btm/btm_sec.h
+++ /dev/null
@@ -1,800 +0,0 @@
-/******************************************************************************
- *
- * Copyright 1999-2012 Broadcom Corporation
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-/******************************************************************************
- *
- * This file contains functions for the Bluetooth Security Manager
- *
- ******************************************************************************/
-
-#pragma once
-#include <cstdint>
-#include "stack/btm/security_device_record.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/security_client_callbacks.h"
-#include "types/hci_role.h"
-
-#define BTM_SEC_MAX_COLLISION_DELAY (5000)
-
-/*******************************************************************************
- * L O C A L F U N C T I O N P R O T O T Y P E S *
- ******************************************************************************/
-tBTM_SEC_SERV_REC* btm_sec_find_first_serv(bool is_originator, uint16_t psm);
-
-tBTM_SEC_DEV_REC* btm_sec_find_dev_by_sec_state(uint8_t state);
-
-/*******************************************************************************
- *
- * Function BTM_SecRegister
- *
- * Description Application manager calls this function to register for
- * security services. There can be one and only one
- * application saving link keys. BTM allows only first
- * registration.
- *
- * Returns true if registered OK, else false
- *
- ******************************************************************************/
-bool BTM_SecRegister(const tBTM_APPL_INFO* p_cb_info);
-
-/*******************************************************************************
- *
- * Function BTM_SecAddRmtNameNotifyCallback
- *
- * Description Any profile can register to be notified when name of the
- * remote device is resolved.
- *
- * Returns true if registered OK, else false
- *
- ******************************************************************************/
-bool BTM_SecAddRmtNameNotifyCallback(tBTM_RMT_NAME_CALLBACK* p_callback);
-
-/*******************************************************************************
- *
- * Function BTM_SecDeleteRmtNameNotifyCallback
- *
- * Description Any profile can deregister notification when a new Link Key
- * is generated per connection.
- *
- * Returns true if OK, else false
- *
- ******************************************************************************/
-bool BTM_SecDeleteRmtNameNotifyCallback(tBTM_RMT_NAME_CALLBACK* p_callback);
-
-/*******************************************************************************
- *
- * Function BTM_GetSecurityFlags
- *
- * Description Get security flags for the device
- *
- * Returns bool true or false is device found
- *
- ******************************************************************************/
-bool BTM_GetSecurityFlags(const RawAddress& bd_addr, uint8_t* p_sec_flags);
-
-/*******************************************************************************
- *
- * Function BTM_GetSecurityFlagsByTransport
- *
- * Description Get security flags for the device on a particular transport
- *
- * Returns bool true or false is device found
- *
- ******************************************************************************/
-bool BTM_GetSecurityFlagsByTransport(const RawAddress& bd_addr,
- uint8_t* p_sec_flags,
- tBT_TRANSPORT transport);
-
-bool BTM_IsEncrypted(const RawAddress& bd_addr, tBT_TRANSPORT transport);
-bool BTM_IsLinkKeyAuthed(const RawAddress& bd_addr, tBT_TRANSPORT transport);
-bool BTM_IsLinkKeyKnown(const RawAddress& bd_addr, tBT_TRANSPORT transport);
-bool BTM_IsAuthenticated(const RawAddress& bd_addr, tBT_TRANSPORT transport);
-
-/*******************************************************************************
- *
- * Function BTM_SetPinType
- *
- * Description Set PIN type for the device.
- *
- * Returns void
- *
- ******************************************************************************/
-void BTM_SetPinType(uint8_t pin_type, PIN_CODE pin_code, uint8_t pin_code_len);
-
-/*******************************************************************************
- *
- * Function BTM_SetSecurityLevel
- *
- * Description Register service security level with Security Manager
- *
- * Parameters: is_originator - true if originating the connection
- * p_name - Name of the service relevant only if
- * authorization will show this name to user.
- * Ignored if BT_MAX_SERVICE_NAME_LEN is 0.
- * service_id - service ID for the service passed to
- * authorization callback
- * sec_level - bit mask of the security features
- * psm - L2CAP PSM
- * mx_proto_id - protocol ID of multiplexing proto below
- * mx_chan_id - channel ID of multiplexing proto below
- *
- * Returns true if registered OK, else false
- *
- ******************************************************************************/
-bool BTM_SetSecurityLevel(bool is_originator, const char* p_name,
- uint8_t service_id, uint16_t sec_level, uint16_t psm,
- uint32_t mx_proto_id, uint32_t mx_chan_id);
-
-/*******************************************************************************
- *
- * Function BTM_SecClrService
- *
- * Description Removes specified service record(s) from the security
- * database. All service records with the specified name are
- * removed. Typically used only by devices with limited RAM so
- * that it can reuse an old security service record.
- *
- * Note: Unpredictable results may occur if a service is
- * cleared that is still in use by an application/profile.
- *
- * Parameters Service ID - Id of the service to remove. '0' removes all
- * service records (except SDP).
- *
- * Returns Number of records that were freed.
- *
- ******************************************************************************/
-uint8_t BTM_SecClrService(uint8_t service_id);
-
-/*******************************************************************************
- *
- * Function BTM_SecClrServiceByPsm
- *
- * Description Removes specified service record from the security database.
- * All service records with the specified psm are removed.
- * Typically used by L2CAP to free up the service record used
- * by dynamic PSM clients when the channel is closed.
- * The given psm must be a virtual psm.
- *
- * Parameters Service ID - Id of the service to remove. '0' removes all
- * service records (except SDP).
- *
- * Returns Number of records that were freed.
- *
- ******************************************************************************/
-uint8_t BTM_SecClrServiceByPsm(uint16_t psm);
-
-/*******************************************************************************
- *
- * Function BTM_PINCodeReply
- *
- * Description This function is called after Security Manager submitted
- * PIN code request to the UI.
- *
- * Parameters: bd_addr - Address of the device for which PIN was
- * requested
- * res - result of the operation BTM_SUCCESS
- * if success
- * pin_len - length in bytes of the PIN Code
- * p_pin - pointer to array with the PIN Code
- *
- ******************************************************************************/
-void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res, uint8_t pin_len,
- uint8_t* p_pin);
-
-/*******************************************************************************
- *
- * Function btm_sec_bond_by_transport
- *
- * Description this is the bond function that will start either SSP or SMP.
- *
- * Parameters: bd_addr - Address of the device to bond
- * pin_len - length in bytes of the PIN Code
- * p_pin - pointer to array with the PIN Code
- *
- * Note: After 2.1 parameters are not used and preserved here not to change API
- ******************************************************************************/
-tBTM_STATUS btm_sec_bond_by_transport(const RawAddress& bd_addr,
- tBT_TRANSPORT transport, uint8_t pin_len,
- uint8_t* p_pin);
-
-/*******************************************************************************
- *
- * Function BTM_SecBond
- *
- * Description This function is called to perform bonding with peer device.
- * If the connection is already up, but not secure, pairing
- * is attempted. If already paired BTM_SUCCESS is returned.
- *
- * Parameters: bd_addr - Address of the device to bond
- * transport - doing SSP over BR/EDR or SMP over LE
- * pin_len - length in bytes of the PIN Code
- * p_pin - pointer to array with the PIN Code
- *
- * Note: After 2.1 parameters are not used and preserved here not to change API
- ******************************************************************************/
-tBTM_STATUS BTM_SecBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type,
- uint8_t pin_len, uint8_t* p_pin);
-
-/*******************************************************************************
- *
- * Function BTM_SecBondCancel
- *
- * Description This function is called to cancel ongoing bonding process
- * with peer device.
- *
- * Parameters: bd_addr - Address of the peer device
- * transport - false for BR/EDR link; true for LE link
- *
- ******************************************************************************/
-tBTM_STATUS BTM_SecBondCancel(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function BTM_SecGetDeviceLinkKeyType
- *
- * Description This function is called to obtain link key type for the
- * device.
- * it returns BTM_SUCCESS if link key is available, or
- * BTM_UNKNOWN_ADDR if Security Manager does not know about
- * the device or device record does not contain link key info
- *
- * Returns BTM_LKEY_TYPE_IGNORE if link key is unknown, link type
- * otherwise.
- *
- ******************************************************************************/
-tBTM_LINK_KEY_TYPE BTM_SecGetDeviceLinkKeyType(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function BTM_SetEncryption
- *
- * Description This function is called to ensure that connection is
- * encrypted. Should be called only on an open connection.
- * Typically only needed for connections that first want to
- * bring up unencrypted links, then later encrypt them.
- *
- * Parameters: bd_addr - Address of the peer device
- * transport - Link transport
- * p_callback - Pointer to callback function called if
- * this function returns PENDING after required
- * procedures are completed. Can be set to
- * NULL if status is not desired.
- * p_ref_data - pointer to any data the caller wishes to
- * receive in the callback function upon
- * completion. can be set to NULL if not used.
- * sec_act - LE security action, unused for BR/EDR
- *
- * Returns BTM_SUCCESS - already encrypted
- * BTM_PENDING - command will be returned in the callback
- * BTM_WRONG_MODE- connection not up.
- * BTM_BUSY - security procedures are currently active
- * BTM_MODE_UNSUPPORTED - if security manager not linked in.
- *
- ******************************************************************************/
-tBTM_STATUS BTM_SetEncryption(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback, void* p_ref_data,
- tBTM_BLE_SEC_ACT sec_act);
-
-bool BTM_SecIsSecurityPending(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function BTM_ConfirmReqReply
- *
- * Description This function is called to confirm the numeric value for
- * Simple Pairing in response to BTM_SP_CFM_REQ_EVT
- *
- * Parameters: res - result of the operation BTM_SUCCESS if
- * success
- * bd_addr - Address of the peer device
- *
- ******************************************************************************/
-void BTM_ConfirmReqReply(tBTM_STATUS res, const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function BTM_PasskeyReqReply
- *
- * Description This function is called to provide the passkey for
- * Simple Pairing in response to BTM_SP_KEY_REQ_EVT
- *
- * Parameters: res - result of the operation BTM_SUCCESS if success
- * bd_addr - Address of the peer device
- * passkey - numeric value in the range of
- * BTM_MIN_PASSKEY_VAL(0) -
- * BTM_MAX_PASSKEY_VAL(999999(0xF423F)).
- *
- ******************************************************************************/
-void BTM_PasskeyReqReply(tBTM_STATUS res, const RawAddress& bd_addr,
- uint32_t passkey);
-
-/*******************************************************************************
- *
- * Function BTM_ReadLocalOobData
- *
- * Description This function is called to read the local OOB data from
- * LM
- *
- ******************************************************************************/
-void BTM_ReadLocalOobData(void);
-
-/*******************************************************************************
- *
- * Function BTM_RemoteOobDataReply
- *
- * Description This function is called to provide the remote OOB data for
- * Simple Pairing in response to BTM_SP_RMT_OOB_EVT
- *
- * Parameters: bd_addr - Address of the peer device
- * c - simple pairing Hash C.
- * r - simple pairing Randomizer C.
- *
- ******************************************************************************/
-void BTM_RemoteOobDataReply(tBTM_STATUS res, const RawAddress& bd_addr,
- const Octet16& c, const Octet16& r);
-
-/*******************************************************************************
- *
- * Function BTM_BothEndsSupportSecureConnections
- *
- * Description This function is called to check if both the local device
- * and the peer device specified by bd_addr support BR/EDR
- * Secure Connections.
- *
- * Parameters: bd_addr - address of the peer
- *
- * Returns true if BR/EDR Secure Connections are supported by both
- * local and the remote device, else false.
- *
- ******************************************************************************/
-bool BTM_BothEndsSupportSecureConnections(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function BTM_PeerSupportsSecureConnections
- *
- * Description This function is called to check if the peer supports
- * BR/EDR Secure Connections.
- *
- * Parameters: bd_addr - address of the peer
- *
- * Returns true if BR/EDR Secure Connections are supported by the peer,
- * else false.
- *
- ******************************************************************************/
-bool BTM_PeerSupportsSecureConnections(const RawAddress& bd_addr);
-
-/*******************************************************************************
- *
- * Function btm_sec_l2cap_access_req
- *
- * Description This function is called by the L2CAP to grant permission to
- * establish L2CAP connection to or from the peer device.
- *
- * Parameters: bd_addr - Address of the peer device
- * psm - L2CAP PSM
- * is_originator - true if protocol above L2CAP originates
- * connection
- * p_callback - Pointer to callback function called if
- * this function returns PENDING after required
- * procedures are complete. MUST NOT BE NULL.
- *
- * Returns tBTM_STATUS
- *
- ******************************************************************************/
-tBTM_STATUS btm_sec_l2cap_access_req(const RawAddress& bd_addr, uint16_t psm,
- bool is_originator,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data);
-
-// Allow enforcing security by specific requirement (from shim layer).
-tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
- const RawAddress& bd_addr, uint16_t security_required, bool is_originator,
- tBTM_SEC_CALLBACK* p_callback, void* p_ref_data);
-
-/*******************************************************************************
- *
- * Function btm_sec_mx_access_request
- *
- * Description This function is called by all Multiplexing Protocols
- *during establishing connection to or from peer device to grant permission
- *to establish application connection.
- *
- * Parameters: bd_addr - Address of the peer device
- * psm - L2CAP PSM
- * is_originator - true if protocol above L2CAP originates
- * connection
- * mx_proto_id - protocol ID of the multiplexer
- * mx_chan_id - multiplexer channel to reach application
- * p_callback - Pointer to callback function called if
- * this function returns PENDING after
- *required procedures are completed p_ref_data - Pointer to any reference
- *data needed by the the callback function.
- *
- * Returns BTM_CMD_STARTED
- *
- ******************************************************************************/
-tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
- bool is_originator,
- uint16_t security_requirement,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data);
-
-/*******************************************************************************
- *
- * Function btm_sec_conn_req
- *
- * Description This function is when the peer device is requesting
- * connection
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_conn_req(const RawAddress& bda, uint8_t* dc);
-
-/*******************************************************************************
- *
- * Function btm_create_conn_cancel_complete
- *
- * Description This function is called when the command complete message
- * is received from the HCI for the create connection cancel
- * command.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_create_conn_cancel_complete(uint8_t* p);
-
-/*******************************************************************************
- *
- * Function btm_sec_dev_reset
- *
- * Description This function should be called after device reset
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_dev_reset(void);
-
-/*******************************************************************************
- *
- * Function btm_sec_abort_access_req
- *
- * Description This function is called by the L2CAP or RFCOMM to abort
- * the pending operation.
- *
- * Parameters: bd_addr - Address of the peer device
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_abort_access_req(const RawAddress& bd_addr);
-
-bool is_state_getting_name(void* data, void* context);
-
-/*******************************************************************************
- *
- * Function btm_sec_rmt_name_request_complete
- *
- * Description This function is called when remote name was obtained from
- * the peer device
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_rmt_name_request_complete(const RawAddress* p_bd_addr,
- uint8_t* p_bd_name, tHCI_STATUS status);
-
-/*******************************************************************************
- *
- * Function btm_sec_rmt_host_support_feat_evt
- *
- * Description This function is called when the
- * HCI_RMT_HOST_SUP_FEAT_NOTIFY_EVT is received
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_rmt_host_support_feat_evt(uint8_t* p);
-
-/*******************************************************************************
- *
- * Function btm_io_capabilities_req
- *
- * Description This function is called when LM request for the IO
- * capability of the local device and
- * if the OOB data is present for the device in the event
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_io_capabilities_req(const RawAddress& p);
-
-/*******************************************************************************
- *
- * Function btm_io_capabilities_rsp
- *
- * Description This function is called when the IO capability of the
- * specified device is received
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_io_capabilities_rsp(uint8_t* p);
-
-/*******************************************************************************
- *
- * Function btm_proc_sp_req_evt
- *
- * Description This function is called to process/report
- * HCI_USER_CONFIRMATION_REQUEST_EVT
- * or HCI_USER_PASSKEY_REQUEST_EVT
- * or HCI_USER_PASSKEY_NOTIFY_EVT
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_proc_sp_req_evt(tBTM_SP_EVT event, uint8_t* p);
-
-/*******************************************************************************
- *
- * Function btm_simple_pair_complete
- *
- * Description This function is called when simple pairing process is
- * complete
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_simple_pair_complete(uint8_t* p);
-
-/*******************************************************************************
- *
- * Function btm_rem_oob_req
- *
- * Description This function is called to process/report
- * HCI_REMOTE_OOB_DATA_REQUEST_EVT
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_rem_oob_req(uint8_t* p);
-
-/*******************************************************************************
- *
- * Function btm_read_local_oob_complete
- *
- * Description This function is called when read local oob data is
- * completed by the LM
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_read_local_oob_complete(uint8_t* p);
-
-/*******************************************************************************
- *
- * Function btm_sec_auth_complete
- *
- * Description This function is when authentication of the connection is
- * completed by the LM
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_auth_complete(uint16_t handle, tHCI_STATUS status);
-
-/*******************************************************************************
- *
- * Function btm_sec_encrypt_change
- *
- * Description This function is when encryption of the connection is
- * completed by the LM
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_encrypt_change(uint16_t handle, tHCI_STATUS status,
- uint8_t encr_enable);
-
-/*******************************************************************************
- *
- * Function btm_sec_connected
- *
- * Description This function is when a connection to the peer device is
- * established
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_connected(const RawAddress& bda, uint16_t handle,
- tHCI_STATUS status, uint8_t enc_mode,
- tHCI_ROLE assigned_role = HCI_ROLE_PERIPHERAL);
-
-/*******************************************************************************
- *
- * Function btm_sec_disconnect
- *
- * Description This function is called to disconnect HCI link
- *
- * Returns btm status
- *
- ******************************************************************************/
-tBTM_STATUS btm_sec_disconnect(uint16_t handle, tHCI_STATUS reason);
-
-/*******************************************************************************
- *
- * Function btm_sec_disconnected
- *
- * Description This function is when a connection to the peer device is
- * dropped
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_disconnected(uint16_t handle, tHCI_STATUS reason);
-
-/** This function is called when a new connection link key is generated */
-void btm_sec_link_key_notification(const RawAddress& p_bda,
- const Octet16& link_key, uint8_t key_type);
-
-/*******************************************************************************
- *
- * Function btm_sec_link_key_request
- *
- * Description This function is called when controller requests link key
- *
- * Returns Pointer to the record or NULL
- *
- ******************************************************************************/
-void btm_sec_link_key_request(uint8_t* p_event);
-
-/*******************************************************************************
- *
- * Function btm_sec_pin_code_request
- *
- * Description This function is called when controller requests PIN code
- *
- * Returns Pointer to the record or NULL
- *
- ******************************************************************************/
-void btm_sec_pin_code_request(uint8_t* p_event);
-
-/*******************************************************************************
- *
- * Function btm_sec_update_clock_offset
- *
- * Description This function is called to update clock offset
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_update_clock_offset(uint16_t handle, uint16_t clock_offset);
-
-/*******************************************************************************
- *
- * Function btm_sec_execute_procedure
- *
- * Description This function is called to start required security
- * procedure. There is a case when multiplexing protocol
- * calls this function on the originating side, connection to
- * the peer will not be established. This function in this
- * case performs only authorization.
- *
- * Returns BTM_SUCCESS - permission is granted
- * BTM_CMD_STARTED - in process
- * BTM_NO_RESOURCES - permission declined
- *
- ******************************************************************************/
-tBTM_STATUS btm_sec_execute_procedure(tBTM_SEC_DEV_REC* p_dev_rec);
-
-/*******************************************************************************
- *
- * Function btm_sec_find_first_serv
- *
- * Description Look for the first record in the service database
- * with specified PSM
- *
- * Returns Pointer to the record or NULL
- *
- ******************************************************************************/
-tBTM_SEC_SERV_REC* btm_sec_find_first_serv(bool is_originator, uint16_t psm);
-
-bool is_sec_state_equal(void* data, void* context);
-
-/*******************************************************************************
- *
- * Function btm_sec_find_dev_by_sec_state
- *
- * Description Look for the record in the device database for the device
- * which is being authenticated or encrypted
- *
- * Returns Pointer to the record or NULL
- *
- ******************************************************************************/
-tBTM_SEC_DEV_REC* btm_sec_find_dev_by_sec_state(uint8_t state);
-
-/*******************************************************************************
- *
- * Function btm_sec_dev_rec_cback_event
- *
- * Description This function calls the callback function with the given
- * result and clear the callback function.
- *
- * Parameters: void
- *
- ******************************************************************************/
-void btm_sec_dev_rec_cback_event(tBTM_SEC_DEV_REC* p_dev_rec, tBTM_STATUS res,
- bool is_le_transport);
-
-/*******************************************************************************
- *
- * Function btm_sec_clear_ble_keys
- *
- * Description This function is called to clear out the BLE keys.
- * Typically when devices are removed in BTM_SecDeleteDevice,
- * or when a new BT Link key is generated.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_clear_ble_keys(tBTM_SEC_DEV_REC* p_dev_rec);
-
-/*******************************************************************************
- *
- * Function btm_sec_is_a_bonded_dev
- *
- * Description Is the specified device is a bonded device
- *
- * Returns true - dev is bonded
- *
- ******************************************************************************/
-bool btm_sec_is_a_bonded_dev(const RawAddress& bda);
-
-/*******************************************************************************
- *
- * Function btm_sec_set_peer_sec_caps
- *
- * Description This function is called to set sm4 and rmt_sec_caps fields
- * based on the available peer device features.
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_set_peer_sec_caps(uint16_t hci_handle, bool ssp_supported,
- bool sc_supported,
- bool hci_role_switch_supported,
- bool br_edr_supported, bool le_supported);
-
-/*******************************************************************************
- *
- * Function btm_sec_cr_loc_oob_data_cback_event
- *
- * Description This function is called to pass the local oob up to caller
- *
- * Returns void
- *
- ******************************************************************************/
-void btm_sec_cr_loc_oob_data_cback_event(const RawAddress& address,
- tSMP_LOC_OOB_DATA loc_oob_data);
-
-// Return DEV_CLASS (uint8_t[3]) of bda. If record doesn't exist, create one.
-const uint8_t* btm_get_dev_class(const RawAddress& bda);
diff --git a/stack/btm/neighbor_inquiry.h b/stack/btm/neighbor_inquiry.h
deleted file mode 100644
index 8d1b0d547..000000000
--- a/stack/btm/neighbor_inquiry.h
+++ /dev/null
@@ -1,257 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include "osi/include/alarm.h"
-#include "stack/include/btm_api_types.h"
-#include "types/ble_address_with_type.h"
-#include "types/raw_address.h"
-
-/* Discoverable modes */
-enum : uint16_t {
- BTM_NON_DISCOVERABLE = 0,
- BTM_LIMITED_DISCOVERABLE = (1 << 0),
- BTM_GENERAL_DISCOVERABLE = (1 << 1),
- BTM_MAX_DISCOVERABLE = BTM_GENERAL_DISCOVERABLE,
- BTM_DISCOVERABLE_MASK = (BTM_LIMITED_DISCOVERABLE | BTM_GENERAL_DISCOVERABLE),
- /* high byte for BLE Discoverable modes */
- BTM_BLE_NON_DISCOVERABLE = 0x0000,
- BTM_BLE_LIMITED_DISCOVERABLE = 0x0100,
- BTM_BLE_GENERAL_DISCOVERABLE = 0x0200,
- BTM_BLE_MAX_DISCOVERABLE = BTM_BLE_GENERAL_DISCOVERABLE,
- BTM_BLE_DISCOVERABLE_MASK =
- (BTM_BLE_LIMITED_DISCOVERABLE | BTM_BLE_GENERAL_DISCOVERABLE),
-};
-
-/* Connectable modes */
-enum : uint16_t {
- BTM_NON_CONNECTABLE = 0,
- BTM_CONNECTABLE = (1 << 0),
- BTM_CONNECTABLE_MASK = (BTM_NON_CONNECTABLE | BTM_CONNECTABLE),
- /* high byte for BLE Connectable modes */
- BTM_BLE_NON_CONNECTABLE = BTM_NON_CONNECTABLE,
- BTM_BLE_CONNECTABLE = 0x0100,
- BTM_BLE_MAX_CONNECTABLE = BTM_BLE_CONNECTABLE,
- BTM_BLE_CONNECTABLE_MASK = (BTM_BLE_NON_CONNECTABLE | BTM_BLE_CONNECTABLE),
-};
-
-/* Inquiry modes
- * Note: These modes are associated with the inquiry active values (BTM_*ACTIVE)
- */
-enum : uint8_t {
- BTM_INQUIRY_NONE = 0,
- BTM_INQUIRY_INACTIVE = 0x0,
- BTM_GENERAL_INQUIRY = 0x01,
- /* SSP is active, so inquiry is disallowed (work around for FW bug) */
- BTM_SSP_INQUIRY_ACTIVE = 0x4,
- /* high nibble of inquiry mode for BLE inquiry mode */
- BTM_BLE_GENERAL_INQUIRY = 0x10,
- BTM_BR_INQUIRY_MASK = (BTM_GENERAL_INQUIRY),
- BTM_BLE_INQUIRY_MASK = (BTM_BLE_GENERAL_INQUIRY),
- BTM_BLE_INQUIRY_NONE = BTM_INQUIRY_NONE,
- BTM_GENERAL_INQUIRY_ACTIVE = BTM_GENERAL_INQUIRY,
- /* a general inquiry is in progress */
- BTM_LE_GENERAL_INQUIRY_ACTIVE = BTM_BLE_GENERAL_INQUIRY,
- /* BR/EDR inquiry activity mask */
- BTM_BR_INQ_ACTIVE_MASK = (BTM_GENERAL_INQUIRY_ACTIVE),
- /* LE scan activity mask */
- BTM_BLE_SCAN_ACTIVE_MASK = 0xF0,
- /* LE inquiry activity mask*/
- BTM_BLE_INQ_ACTIVE_MASK = (BTM_LE_GENERAL_INQUIRY_ACTIVE),
- /* inquiry activity mask */
- BTM_INQUIRY_ACTIVE_MASK = (BTM_BR_INQ_ACTIVE_MASK | BTM_BLE_INQ_ACTIVE_MASK),
-};
-
-/* Define scan types */
-enum : uint16_t {
- BTM_SCAN_TYPE_STANDARD = 0,
- BTM_SCAN_TYPE_INTERLACED = 1, /* 1.2 devices only */
-};
-
-/* Define inquiry results mode */
-enum : uint8_t {
- BTM_INQ_RESULT_STANDARD = 0,
- BTM_INQ_RESULT_WITH_RSSI = 1,
- BTM_INQ_RESULT_EXTENDED = 2,
- /* RSSI value not supplied (ignore it) */
- BTM_INQ_RES_IGNORE_RSSI = 0x7f,
-};
-
-/* These are the fields returned in each device's response to the inquiry. It
- * is returned in the results callback if registered.
- */
-typedef struct {
- uint16_t clock_offset;
- RawAddress remote_bd_addr;
- DEV_CLASS dev_class;
- uint8_t page_scan_rep_mode;
- uint8_t page_scan_per_mode;
- uint8_t page_scan_mode;
- int8_t rssi; /* Set to BTM_INQ_RES_IGNORE_RSSI if not valid */
- uint32_t eir_uuid[BTM_EIR_SERVICE_ARRAY_SIZE];
- bool eir_complete_list;
- tBT_DEVICE_TYPE device_type;
- uint8_t inq_result_type;
- tBLE_ADDR_TYPE ble_addr_type;
- uint16_t ble_evt_type;
- uint8_t ble_primary_phy;
- uint8_t ble_secondary_phy;
- uint8_t ble_advertising_sid;
- int8_t ble_tx_power;
- uint16_t ble_periodic_adv_int;
- uint8_t flag;
-} tBTM_INQ_RESULTS;
-
-/****************************************
- * Device Discovery Callback Functions
- ****************************************/
-/* Callback function for notifications when the BTM gets inquiry response.
- * First param is inquiry results database, second is pointer of EIR.
- */
-typedef void(tBTM_INQ_RESULTS_CB)(tBTM_INQ_RESULTS* p_inq_results,
- uint8_t* p_eir, uint16_t eir_len);
-
-typedef struct {
- uint32_t inq_count; /* Used for determining if a response has already been */
- /* received for the current inquiry operation. (We do not */
- /* want to flood the caller with multiple responses from */
- /* the same device. */
- RawAddress bd_addr;
-} tINQ_BDADDR;
-
-/* This is the inquiry response information held in its database by BTM, and
- * available to applications via BTM_InqDbRead, BTM_InqDbFirst, and
- * BTM_InqDbNext.
- */
-typedef struct {
- tBTM_INQ_RESULTS results;
-
- bool appl_knows_rem_name; /* set by application if it knows the remote name of
- the peer device.
- This is later used by application to determine if
- remote name request is
- required to be done. Having the flag here avoid
- duplicate store of inquiry results */
- uint16_t remote_name_len;
- tBTM_BD_NAME remote_name;
- uint8_t remote_name_state;
- uint8_t remote_name_type;
-
-} tBTM_INQ_INFO;
-
-typedef struct {
- uint64_t time_of_resp;
- uint32_t
- inq_count; /* "timestamps" the entry with a particular inquiry count */
- /* Used for determining if a response has already been */
- /* received for the current inquiry operation. (We do not */
- /* want to flood the caller with multiple responses from */
- /* the same device. */
- tBTM_INQ_INFO inq_info;
- bool in_use;
- bool scan_rsp;
-} tINQ_DB_ENT;
-
-typedef struct /* contains the parameters passed to the inquiry functions */
-{
- uint8_t mode; /* general or limited */
- uint8_t duration; /* duration of the inquiry (1.28 sec increments) */
-} tBTM_INQ_PARMS;
-
-/* Structure returned with inquiry complete callback */
-typedef struct {
- tBTM_STATUS status;
- uint8_t num_resp; /* Number of results from the current inquiry */
-} tBTM_INQUIRY_CMPL;
-
-typedef struct {
- tBTM_CMPL_CB* p_remname_cmpl_cb;
-
-#define BTM_EXT_RMT_NAME_TIMEOUT_MS (40 * 1000) /* 40 seconds */
-
- alarm_t* remote_name_timer;
-
- uint16_t discoverable_mode;
- uint16_t connectable_mode;
- uint16_t page_scan_window;
- uint16_t page_scan_period;
- uint16_t inq_scan_window;
- uint16_t inq_scan_period;
- uint16_t inq_scan_type;
- uint16_t page_scan_type; /* current page scan type */
-
- RawAddress remname_bda; /* Name of bd addr for active remote name request */
-#define BTM_RMT_NAME_EXT 0x1 /* Initiated through API */
- bool remname_active; /* State of a remote name request by external API */
-
- tBTM_CMPL_CB* p_inq_cmpl_cb;
- tBTM_INQ_RESULTS_CB* p_inq_results_cb;
- uint32_t inq_counter; /* Counter incremented each time an inquiry completes */
- /* Used for determining whether or not duplicate devices */
- /* have responded to the same inquiry */
- tINQ_BDADDR* p_bd_db; /* Pointer to memory that holds bdaddrs */
- uint16_t num_bd_entries; /* Number of entries in database */
- uint16_t max_bd_entries; /* Maximum number of entries that can be stored */
- tINQ_DB_ENT inq_db[BTM_INQ_DB_SIZE];
- tBTM_INQ_PARMS inqparms; /* Contains the parameters for the current inquiry */
- tBTM_INQUIRY_CMPL
- inq_cmpl_info; /* Status and number of responses from the last inquiry */
-
- uint16_t per_min_delay; /* Current periodic minimum delay */
- uint16_t per_max_delay; /* Current periodic maximum delay */
- /* inquiry that has been cancelled*/
- uint8_t inqfilt_type; /* Contains the inquiry filter type (BD ADDR, COD, or
- Clear) */
-
-#define BTM_INQ_INACTIVE_STATE 0
-#define BTM_INQ_ACTIVE_STATE \
- 3 /* Actual inquiry or periodic inquiry is in progress */
-
- uint8_t state; /* Current state that the inquiry process is in */
- uint8_t inq_active; /* Bit Mask indicating type of inquiry is active */
- bool no_inc_ssp; /* true, to stop inquiry on incoming SSP */
-
- void Init() {
- alarm_free(remote_name_timer);
- remote_name_timer = alarm_new("btm_inq.remote_name_timer");
- no_inc_ssp = BTM_NO_SSP_ON_INQUIRY;
- }
- void Free() { alarm_free(remote_name_timer); }
-
-} tBTM_INQUIRY_VAR_ST;
-
-/* Structure returned with remote name request */
-typedef struct {
- uint16_t status;
- RawAddress bd_addr;
- uint16_t length;
- BD_NAME remote_bd_name;
-} tBTM_REMOTE_DEV_NAME;
-
-typedef union /* contains the inquiry filter condition */
-{
- RawAddress bdaddr_cond;
- tBTM_COD_COND cod_cond;
-} tBTM_INQ_FILT_COND;
-
-#define BTM_INQ_RESULT_BR 0x01
-#define BTM_INQ_RESULT_BLE 0x02
-
-extern bool btm_inq_find_bdaddr(const RawAddress& p_bda);
-extern tINQ_DB_ENT* btm_inq_db_find(const RawAddress& p_bda);
diff --git a/stack/btm/security_device_record.h b/stack/btm/security_device_record.h
deleted file mode 100644
index 56d8108a0..000000000
--- a/stack/btm/security_device_record.h
+++ /dev/null
@@ -1,439 +0,0 @@
-/******************************************************************************
- *
- * Copyright 1999-2012 Broadcom Corporation
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#pragma once
-
-#include <base/strings/stringprintf.h>
-#include <string.h>
-#include <cstdint>
-#include <string>
-
-#include "gd/crypto_toolbox/crypto_toolbox.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/alarm.h"
-#include "stack/include/btm_api_types.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
-
-typedef char tBTM_LOC_BD_NAME[BTM_MAX_LOC_BD_NAME_LEN + 1];
-
-typedef struct {
- uint16_t min_conn_int;
- uint16_t max_conn_int;
- uint16_t peripheral_latency;
- uint16_t supervision_tout;
-
-} tBTM_LE_CONN_PRAMS;
-
-/* The MSB of the clock offset field indicates whether the offset is valid. */
-#define BTM_CLOCK_OFFSET_VALID 0x8000
-
-/*
- * Define structure for Security Service Record.
- * A record exists for each service registered with the Security Manager
- */
-#define BTM_SEC_OUT_FLAGS (BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT)
-#define BTM_SEC_IN_FLAGS (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT)
-
-#define BTM_SEC_OUT_LEVEL4_FLAGS \
- (BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT | BTM_SEC_OUT_MITM | \
- BTM_SEC_MODE4_LEVEL4)
-
-#define BTM_SEC_IN_LEVEL4_FLAGS \
- (BTM_SEC_IN_AUTHENTICATE | BTM_SEC_IN_ENCRYPT | BTM_SEC_IN_MITM | \
- BTM_SEC_MODE4_LEVEL4)
-typedef struct {
- uint32_t mx_proto_id; /* Service runs over this multiplexer protocol */
- uint32_t orig_mx_chan_id; /* Channel on the multiplexer protocol */
- uint32_t term_mx_chan_id; /* Channel on the multiplexer protocol */
- uint16_t psm; /* L2CAP PSM value */
- uint16_t security_flags; /* Bitmap of required security features */
- uint8_t service_id; /* Passed in authorization callback */
- uint8_t orig_service_name[BT_MAX_SERVICE_NAME_LEN + 1];
- uint8_t term_service_name[BT_MAX_SERVICE_NAME_LEN + 1];
-} tBTM_SEC_SERV_REC;
-
-/* LE Security information of device in Peripheral Role */
-typedef struct {
- Octet16 irk; /* peer diverified identity root */
- Octet16 pltk; /* peer long term key */
- Octet16 pcsrk; /* peer SRK peer device used to secured sign local data */
-
- Octet16 lltk; /* local long term key */
- Octet16 lcsrk; /* local SRK peer device used to secured sign local data */
-
- BT_OCTET8 rand; /* random vector for LTK generation */
- uint16_t ediv; /* LTK diversifier of this peripheral device */
- uint16_t div; /* local DIV to generate local LTK=d1(ER,DIV,0) and
- CSRK=d1(ER,DIV,1) */
- uint8_t sec_level; /* local pairing security level */
- uint8_t key_size; /* key size of the LTK delivered to peer device */
- uint8_t srk_sec_level; /* security property of peer SRK for this device */
- uint8_t local_csrk_sec_level; /* security property of local CSRK for this
- device */
-
- uint32_t counter; /* peer sign counter for verifying rcv signed cmd */
- uint32_t local_counter; /* local sign counter for sending signed write cmd*/
-} tBTM_SEC_BLE_KEYS;
-
-typedef struct {
- RawAddress pseudo_addr; /* LE pseudo address of the device if different from
- device address */
- tBLE_ADDR_TYPE ble_addr_type; /* LE device type: public or random address */
-
- tBLE_BD_ADDR identity_address_with_type;
-
-#define BTM_ACCEPTLIST_BIT 0x01
-#define BTM_RESOLVING_LIST_BIT 0x02
- uint8_t in_controller_list; /* in controller resolving list or not */
- uint8_t resolving_list_index;
- RawAddress cur_rand_addr; /* current random address */
-
- typedef enum : uint8_t {
- BTM_BLE_ADDR_PSEUDO = 0,
- BTM_BLE_ADDR_RRA = 1,
- BTM_BLE_ADDR_STATIC = 2,
- } tADDRESS_TYPE;
- tADDRESS_TYPE active_addr_type;
-
- tBTM_LE_KEY_TYPE key_type; /* bit mask of valid key types in record */
- tBTM_SEC_BLE_KEYS keys; /* LE device security info in peripheral rode */
-} tBTM_SEC_BLE;
-
-enum : uint16_t {
- BTM_SEC_AUTHENTICATED = 0x0002,
- BTM_SEC_ENCRYPTED = 0x0004,
- BTM_SEC_NAME_KNOWN = 0x0008,
- BTM_SEC_LINK_KEY_KNOWN = 0x0010,
- BTM_SEC_LINK_KEY_AUTHED = 0x0020,
- BTM_SEC_ROLE_SWITCHED = 0x0040, // UNUSED - only cleared
- BTM_SEC_IN_USE = 0x0080, // UNUSED - only set
- /* LE link security flag */
- /* LE link is encrypted after pairing with MITM */
- BTM_SEC_LE_AUTHENTICATED = 0x0200,
- /* LE link is encrypted */
- BTM_SEC_LE_ENCRYPTED = 0x0400,
- /* not used */
- BTM_SEC_LE_NAME_KNOWN = 0x0800, // UNUSED
- /* bonded with peer (peer LTK and/or SRK is saved) */
- BTM_SEC_LE_LINK_KEY_KNOWN = 0x1000,
- /* pairing is done with MITM */
- BTM_SEC_LE_LINK_KEY_AUTHED = 0x2000,
- /* pairing is done with 16 digit pin */
- BTM_SEC_16_DIGIT_PIN_AUTHED = 0x4000,
-};
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-typedef enum : uint8_t {
- BTM_SEC_STATE_IDLE = 0,
- BTM_SEC_STATE_AUTHENTICATING = 1,
- BTM_SEC_STATE_ENCRYPTING = 2,
- BTM_SEC_STATE_GETTING_NAME = 3,
- BTM_SEC_STATE_AUTHORIZING = 4,
- BTM_SEC_STATE_SWITCHING_ROLE = 5,
- /* disconnecting BR/EDR */
- BTM_SEC_STATE_DISCONNECTING = 6,
- /* delay to check for encryption to work around */
- /* controller problems */
- BTM_SEC_STATE_DELAY_FOR_ENC = 7,
- BTM_SEC_STATE_DISCONNECTING_BLE = 8,
- BTM_SEC_STATE_DISCONNECTING_BOTH = 9,
-} tSECURITY_STATE;
-
-static inline std::string security_state_text(const tSECURITY_STATE& state) {
- switch (state) {
- CASE_RETURN_TEXT(BTM_SEC_STATE_IDLE);
- CASE_RETURN_TEXT(BTM_SEC_STATE_AUTHENTICATING);
- CASE_RETURN_TEXT(BTM_SEC_STATE_ENCRYPTING);
- CASE_RETURN_TEXT(BTM_SEC_STATE_GETTING_NAME);
- CASE_RETURN_TEXT(BTM_SEC_STATE_AUTHORIZING);
- CASE_RETURN_TEXT(BTM_SEC_STATE_SWITCHING_ROLE);
- CASE_RETURN_TEXT(BTM_SEC_STATE_DISCONNECTING);
- CASE_RETURN_TEXT(BTM_SEC_STATE_DELAY_FOR_ENC);
- CASE_RETURN_TEXT(BTM_SEC_STATE_DISCONNECTING_BLE);
- CASE_RETURN_TEXT(BTM_SEC_STATE_DISCONNECTING_BOTH);
- default:
- return std::string("UNKNOWN[%hhu]", state);
- }
-}
-
-typedef enum : uint8_t {
- BTM_SM4_UNKNOWN = 0x00,
- BTM_SM4_KNOWN = 0x10,
- BTM_SM4_TRUE = 0x11,
- BTM_SM4_REQ_PEND = 0x08, /* set this bit when getting remote features */
- BTM_SM4_UPGRADE = 0x04, /* set this bit when upgrading link key */
- BTM_SM4_RETRY = 0x02, /* set this bit to retry on HCI_ERR_KEY_MISSING or \
- HCI_ERR_LMP_ERR_TRANS_COLLISION */
- BTM_SM4_DD_ACP =
- 0x20, /* set this bit to indicate peer initiated dedicated bonding */
- BTM_SM4_CONN_PEND = 0x40, /* set this bit to indicate accepting acl conn; to
- be cleared on \ btm_acl_created */
-} tBTM_SM4_BIT;
-
-inline std::string class_of_device_text(const DEV_CLASS& cod) {
- return base::StringPrintf("0x%02x%02x%02x", cod[2], cod[1], cod[0]);
-}
-
-/*
- * Define structure for Security Device Record.
- * A record exists for each device authenticated with this device
- */
-struct tBTM_SEC_DEV_REC {
- /* Peering bond type */
- typedef enum : uint8_t {
- BOND_TYPE_UNKNOWN = 0,
- BOND_TYPE_PERSISTENT = 1,
- BOND_TYPE_TEMPORARY = 2
- } tBTM_BOND_TYPE;
-
- uint32_t required_security_flags_for_pairing;
- tBTM_SEC_CALLBACK* p_callback;
- void* p_ref_data;
- uint32_t timestamp; /* Timestamp of the last connection */
- uint16_t hci_handle; /* Handle to connection when exists */
- uint16_t clock_offset; /* Latest known clock offset */
- RawAddress bd_addr; /* BD_ADDR of the device */
- DEV_CLASS dev_class; /* DEV_CLASS of the device */
- LinkKey link_key; /* Device link key */
-
- public:
- RawAddress RemoteAddress() const { return bd_addr; }
- uint16_t get_br_edr_hci_handle() const { return hci_handle; }
-
- private:
- friend bool BTM_SecAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
- BD_NAME bd_name, uint8_t* features,
- LinkKey* p_link_key, uint8_t key_type,
- uint8_t pin_length);
- friend void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res,
- uint8_t pin_len, uint8_t* p_pin);
- friend void btm_sec_auth_complete(uint16_t handle, tHCI_STATUS status);
- friend void btm_sec_connected(const RawAddress& bda, uint16_t handle,
- tHCI_STATUS status, uint8_t enc_mode,
- tHCI_ROLE);
- friend void btm_sec_encrypt_change(uint16_t handle, tHCI_STATUS status,
- uint8_t encr_enable);
- friend void btm_sec_link_key_notification(const RawAddress& p_bda,
- const Octet16& link_key,
- uint8_t key_type);
- friend tBTM_STATUS btm_sec_bond_by_transport(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
- uint8_t pin_len, uint8_t* p_pin);
- uint8_t pin_code_length; /* Length of the pin_code used for paring */
-
- public:
- uint16_t sec_flags; /* Current device security state */
- bool is_device_authenticated() const {
- return sec_flags & BTM_SEC_AUTHENTICATED;
- }
- void set_device_authenticated() { sec_flags |= BTM_SEC_AUTHENTICATED; }
- void reset_device_authenticated() { sec_flags &= ~BTM_SEC_AUTHENTICATED; }
-
- bool is_device_encrypted() const { return sec_flags & BTM_SEC_ENCRYPTED; }
- void set_device_encrypted() { sec_flags |= BTM_SEC_ENCRYPTED; }
- void reset_device_encrypted() { sec_flags &= ~BTM_SEC_ENCRYPTED; }
-
- bool is_name_known() const { return sec_flags & BTM_SEC_NAME_KNOWN; }
- void set_device_known() { sec_flags |= BTM_SEC_NAME_KNOWN; }
- void reset_device_known() { sec_flags &= ~BTM_SEC_NAME_KNOWN; }
-
- bool is_link_key_known() const { return sec_flags & BTM_SEC_LINK_KEY_KNOWN; }
- void set_link_key_known() { sec_flags |= BTM_SEC_LINK_KEY_KNOWN; }
- void reset_link_key_known() { sec_flags &= ~BTM_SEC_LINK_KEY_KNOWN; }
-
- bool is_link_key_authenticated() const {
- return sec_flags & BTM_SEC_LINK_KEY_AUTHED;
- }
- void set_link_key_authenticated() { sec_flags |= BTM_SEC_LINK_KEY_AUTHED; }
- void reset_link_key_authenticated() { sec_flags &= ~BTM_SEC_LINK_KEY_AUTHED; }
-
- bool is_le_device_authenticated() const {
- return sec_flags & BTM_SEC_LE_AUTHENTICATED;
- }
- void set_le_device_authenticated() { sec_flags |= BTM_SEC_LE_AUTHENTICATED; }
- void reset_le_device_authenticated() {
- sec_flags &= ~BTM_SEC_LE_AUTHENTICATED;
- }
-
- bool is_le_device_encrypted() const {
- return sec_flags & BTM_SEC_LE_ENCRYPTED;
- }
- void set_le_device_encrypted() { sec_flags |= BTM_SEC_LE_ENCRYPTED; }
- void reset_le_device_encrypted() { sec_flags &= ~BTM_SEC_LE_ENCRYPTED; }
-
- bool is_le_link_key_known() const {
- return sec_flags & BTM_SEC_LE_LINK_KEY_KNOWN;
- }
- void set_le_link_key_known() { sec_flags |= BTM_SEC_LE_LINK_KEY_KNOWN; }
- void reset_le_link_key_known() { sec_flags &= ~BTM_SEC_LE_LINK_KEY_KNOWN; }
-
- bool is_le_link_key_authenticated() const {
- return sec_flags & BTM_SEC_LE_LINK_KEY_AUTHED;
- }
- void set_le_link_key_authenticated() {
- sec_flags |= BTM_SEC_LE_LINK_KEY_AUTHED;
- }
- void reset_le_link_key_authenticated() {
- sec_flags &= ~BTM_SEC_LE_LINK_KEY_AUTHED;
- }
-
- bool is_le_link_16_digit_key_authenticated() const {
- return sec_flags & BTM_SEC_16_DIGIT_PIN_AUTHED;
- }
- void set_le_link_16_digit_key_authenticated() {
- sec_flags |= BTM_SEC_16_DIGIT_PIN_AUTHED;
- }
- void reset_le_link_16_digit_key_authenticated() {
- sec_flags &= ~BTM_SEC_16_DIGIT_PIN_AUTHED;
- }
-
- tBTM_BD_NAME sec_bd_name; /* User friendly name of the device. (may be
- truncated to save space in dev_rec table) */
-
- uint8_t sec_state; /* Operating state */
- bool is_security_state_idle() const {
- return sec_state == BTM_SEC_STATE_IDLE;
- }
- bool is_security_state_authenticating() const {
- return sec_state == BTM_SEC_STATE_AUTHENTICATING;
- }
- bool is_security_state_encrypting() const {
- return sec_state == BTM_SEC_STATE_ENCRYPTING;
- }
- bool is_security_state_getting_name() const {
- return sec_state == BTM_SEC_STATE_GETTING_NAME;
- }
- bool is_security_state_authorizing() const {
- return sec_state == BTM_SEC_STATE_AUTHORIZING;
- }
- bool is_security_state_switching_role() const {
- return sec_state == BTM_SEC_STATE_SWITCHING_ROLE;
- }
- bool is_security_state_disconnecting() const {
- return sec_state == BTM_SEC_STATE_DISCONNECTING;
- }
- bool is_security_state_wait_for_encryption() const {
- return sec_state == BTM_SEC_STATE_DELAY_FOR_ENC;
- }
- bool is_security_state_ble_disconnecting() const {
- return sec_state == BTM_SEC_STATE_DISCONNECTING_BLE;
- }
- bool is_security_state_br_edr_and_ble() const {
- return sec_state == BTM_SEC_STATE_DISCONNECTING_BOTH;
- }
-
- private:
- bool is_originator; /* true if device is originating connection */
- friend tBTM_STATUS BTM_SetEncryption(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data,
- tBTM_BLE_SEC_ACT sec_act);
- friend tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
- const RawAddress& bd_addr, uint16_t security_required, bool is_originator,
- tBTM_SEC_CALLBACK* p_callback, void* p_ref_data);
- friend tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
- bool is_originator,
- uint16_t security_required,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data);
-
- public:
- bool IsLocallyInitiated() const { return is_originator; }
-
- bool role_central; /* true if current mode is central */
- uint16_t security_required; /* Security required for connection */
- bool link_key_not_sent; /* link key notification has not been sent waiting for
- name */
- uint8_t link_key_type; /* Type of key used in pairing */
-
- uint8_t sm4; /* BTM_SM4_TRUE, if the peer supports SM4 */
- tBTM_IO_CAP rmt_io_caps; /* IO capability of the peer device */
- tBTM_AUTH_REQ rmt_auth_req; /* the auth_req flag as in the IO caps rsp evt */
-
- bool remote_supports_secure_connections;
- friend void btm_sec_set_peer_sec_caps(uint16_t hci_handle, bool ssp_supported,
- bool sc_supported,
- bool hci_role_switch_supported,
- bool br_edr_supported,
- bool le_supported);
-
- public:
- bool SupportsSecureConnections() const {
- return remote_supports_secure_connections;
- }
-
- bool remote_features_needed; /* set to true if the local device is in */
- /* "Secure Connections Only" mode and it receives */
- /* HCI_IO_CAPABILITY_REQUEST_EVT from the peer before */
- /* it knows peer's support for Secure Connections */
- bool remote_supports_hci_role_switch = false;
- bool remote_supports_bredr;
- bool remote_supports_ble;
- bool remote_feature_received = false;
-
- uint16_t ble_hci_handle; /* use in DUMO connection */
- uint16_t get_ble_hci_handle() const { return ble_hci_handle; }
-
- uint8_t enc_key_size; /* current link encryption key size */
- uint8_t get_encryption_key_size() const { return enc_key_size; }
-
- tBT_DEVICE_TYPE device_type;
- bool is_device_type_br_edr() const {
- return device_type == BT_DEVICE_TYPE_BREDR;
- }
- bool is_device_type_ble() const { return device_type == BT_DEVICE_TYPE_BLE; }
- bool is_device_type_dual_mode() const {
- return device_type == BT_DEVICE_TYPE_DUMO;
- }
-
- bool is_device_type_has_ble() const {
- return device_type & BT_DEVICE_TYPE_BLE;
- }
- bool new_encryption_key_is_p256; /* Set to true when the newly generated LK
- ** is generated from P-256.
- ** Link encrypted with such LK can be used
- ** for SM over BR/EDR.
- */
- tBTM_BOND_TYPE bond_type; /* peering bond type */
- bool is_bond_type_unknown() const { return bond_type == BOND_TYPE_UNKNOWN; }
- bool is_bond_type_persistent() const {
- return bond_type == BOND_TYPE_PERSISTENT;
- }
- bool is_bond_type_temporary() const {
- return bond_type == BOND_TYPE_TEMPORARY;
- }
-
- tBTM_SEC_BLE ble;
- tBTM_LE_CONN_PRAMS conn_params;
-
- tREMOTE_VERSION_INFO remote_version_info;
-
- std::string ToString() const {
- return base::StringPrintf(
- "%s %6s cod:%s remote_info:%-14s sm4:0x%02x SecureConn:%c name:\"%s\"",
- PRIVATE_ADDRESS(bd_addr), DeviceTypeText(device_type).c_str(),
- class_of_device_text(dev_class).c_str(),
- remote_version_info.ToString().c_str(), sm4,
- (remote_supports_secure_connections) ? 'T' : 'F', sec_bd_name);
- }
-};
diff --git a/stack/btu/btu_hcif.cc b/stack/btu/btu_hcif.cc
index a2d9ef8af..28897b91a 100644
--- a/stack/btu/btu_hcif.cc
+++ b/stack/btu/btu_hcif.cc
@@ -28,45 +28,49 @@
#define LOG_TAG "bt_btu_hcif"
#include <base/bind.h>
+#include <base/callback.h>
#include <base/location.h>
-#include <cstdint>
-
-#include "btif/include/btif_config.h"
+#include <base/logging.h>
+#include <base/threading/thread.h>
+#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
+#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
+#include <log/log.h>
+#include <statslog.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "bt_common.h"
+#include "bt_types.h"
+#include "bt_utils.h"
+#include "btif_config.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
#include "common/metrics.h"
#include "device/include/controller.h"
+#include "hci_evt_length.h"
+#include "hci_layer.h"
+#include "hcimsgs.h"
+#include "l2c_int.h"
#include "osi/include/log.h"
-#include "stack/include/acl_hci_link_interface.h"
-#include "stack/include/ble_acl_interface.h"
-#include "stack/include/ble_hci_link_interface.h"
-#include "stack/include/btm_iso_api.h"
-#include "stack/include/btu.h"
-#include "stack/include/dev_hci_link_interface.h"
-#include "stack/include/gatt_api.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hci_evt_length.h"
-#include "stack/include/hcidefs.h"
-#include "stack/include/inq_hci_link_interface.h"
-#include "stack/include/l2cap_hci_link_interface.h"
-#include "stack/include/sco_hci_link_interface.h"
-#include "stack/include/sec_hci_link_interface.h"
-#include "stack/include/stack_metrics_logging.h"
-#include "types/hci_role.h"
+#include "osi/include/osi.h"
using base::Location;
-using bluetooth::hci::IsoManager;
-bool l2c_link_hci_disc_comp(uint16_t handle,
- tHCI_REASON reason); // TODO remove
-bool BTM_BLE_IS_RESOLVE_BDA(const RawAddress& x); // TODO remove
-void BTA_sys_signal_hw_error(); // TODO remove
-void smp_cancel_start_encryption_attempt(); // TODO remove
-void acl_disconnect_from_handle(uint16_t handle,
- tHCI_STATUS reason); // TODO remove
+extern void btm_process_cancel_complete(uint8_t status, uint8_t mode);
+extern void btm_process_inq_results2(uint8_t* p, uint8_t inq_res_mode);
+extern void btm_ble_test_command_complete(uint8_t* p);
+extern void smp_cancel_start_encryption_attempt();
/******************************************************************************/
/* L O C A L F U N C T I O N P R O T O T Y P E S */
/******************************************************************************/
static void btu_hcif_inquiry_comp_evt(uint8_t* p);
+static void btu_hcif_inquiry_result_evt(uint8_t* p, uint8_t hci_evt_len);
+static void btu_hcif_inquiry_rssi_result_evt(uint8_t* p, uint8_t hci_evt_len);
+static void btu_hcif_extended_inquiry_result_evt(uint8_t* p,
+ uint8_t hci_evt_len);
static void btu_hcif_connection_comp_evt(uint8_t* p, uint8_t evt_len);
static void btu_hcif_connection_request_evt(uint8_t* p);
@@ -74,27 +78,64 @@ static void btu_hcif_disconnection_comp_evt(uint8_t* p);
static void btu_hcif_authentication_comp_evt(uint8_t* p);
static void btu_hcif_rmt_name_request_comp_evt(uint8_t* p, uint16_t evt_len);
static void btu_hcif_encryption_change_evt(uint8_t* p);
+static void btu_hcif_read_rmt_features_comp_evt(uint8_t* p);
static void btu_hcif_read_rmt_ext_features_comp_evt(uint8_t* p,
uint8_t evt_len);
+static void btu_hcif_read_rmt_version_comp_evt(uint8_t* p);
+static void btu_hcif_qos_setup_comp_evt(uint8_t* p);
static void btu_hcif_command_complete_evt(BT_HDR* response, void* context);
static void btu_hcif_command_status_evt(uint8_t status, BT_HDR* command,
void* context);
static void btu_hcif_hardware_error_evt(uint8_t* p);
+static void btu_hcif_flush_occured_evt(void);
static void btu_hcif_role_change_evt(uint8_t* p);
+static void btu_hcif_num_compl_data_pkts_evt(uint8_t* p, uint8_t evt_len);
static void btu_hcif_mode_change_evt(uint8_t* p);
+static void btu_hcif_pin_code_request_evt(uint8_t* p);
+static void btu_hcif_link_key_request_evt(uint8_t* p);
static void btu_hcif_link_key_notification_evt(uint8_t* p);
+static void btu_hcif_loopback_command_evt(void);
+static void btu_hcif_data_buf_overflow_evt(void);
+static void btu_hcif_max_slots_changed_evt(void);
static void btu_hcif_read_clock_off_comp_evt(uint8_t* p);
+static void btu_hcif_conn_pkt_type_change_evt(void);
+static void btu_hcif_qos_violation_evt(uint8_t* p);
+static void btu_hcif_page_scan_mode_change_evt(void);
+static void btu_hcif_page_scan_rep_mode_chng_evt(void);
static void btu_hcif_esco_connection_comp_evt(uint8_t* p);
static void btu_hcif_esco_connection_chg_evt(uint8_t* p);
/* Simple Pairing Events */
+static void btu_hcif_host_support_evt(uint8_t* p);
static void btu_hcif_io_cap_request_evt(uint8_t* p);
+static void btu_hcif_io_cap_response_evt(uint8_t* p);
+static void btu_hcif_user_conf_request_evt(uint8_t* p);
+static void btu_hcif_user_passkey_request_evt(uint8_t* p);
+static void btu_hcif_user_passkey_notif_evt(uint8_t* p);
+static void btu_hcif_keypress_notif_evt(uint8_t* p);
+static void btu_hcif_rem_oob_request_evt(uint8_t* p);
+
+static void btu_hcif_simple_pair_complete_evt(uint8_t* p);
+#if L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE
+static void btu_hcif_enhanced_flush_complete_evt(void);
+#endif
+
+#if (BTM_SSR_INCLUDED == TRUE)
+static void btu_hcif_ssr_evt(uint8_t* p, uint16_t evt_len);
+#endif /* BTM_SSR_INCLUDED == TRUE */
+static void btu_ble_ll_conn_complete_evt(uint8_t* p, uint16_t evt_len);
+static void btu_ble_read_remote_feat_evt(uint8_t* p);
static void btu_ble_ll_conn_param_upd_evt(uint8_t* p, uint16_t evt_len);
static void btu_ble_proc_ltk_req(uint8_t* p);
static void btu_hcif_encryption_key_refresh_cmpl_evt(uint8_t* p);
static void btu_ble_data_length_change_evt(uint8_t* p, uint16_t evt_len);
+#if (BLE_LLT_INCLUDED == TRUE)
static void btu_ble_rc_param_req_evt(uint8_t* p);
+#endif
+#if (BLE_PRIVACY_SPT == TRUE)
+static void btu_ble_proc_enhanced_conn_cmpl(uint8_t* p, uint16_t evt_len);
+#endif
/**
* Log HCI event metrics that are not handled in special functions
@@ -120,30 +161,26 @@ void btu_hcif_log_event_metrics(uint8_t evt_code, uint8_t* p_event) {
case HCI_KEYPRESS_NOTIFY_EVT:
case HCI_REMOTE_OOB_DATA_REQUEST_EVT:
STREAM_TO_BDADDR(bda, p_event);
- log_classic_pairing_event(bda, handle, cmd, evt_code, status, reason,
- value);
+ bluetooth::common::LogClassicPairingEvent(bda, handle, cmd, evt_code, status, reason, value);
break;
case HCI_SIMPLE_PAIRING_COMPLETE_EVT:
case HCI_RMT_NAME_REQUEST_COMP_EVT:
STREAM_TO_UINT8(status, p_event);
STREAM_TO_BDADDR(bda, p_event);
- log_classic_pairing_event(bda, handle, cmd, evt_code, status, reason,
- value);
+ bluetooth::common::LogClassicPairingEvent(bda, handle, cmd, evt_code, status, reason, value);
break;
case HCI_AUTHENTICATION_COMP_EVT:
STREAM_TO_UINT8(status, p_event);
STREAM_TO_UINT16(handle, p_event);
handle = HCID_GET_HANDLE(handle);
- log_classic_pairing_event(bda, handle, cmd, evt_code, status, reason,
- value);
+ bluetooth::common::LogClassicPairingEvent(bda, handle, cmd, evt_code, status, reason, value);
break;
case HCI_ENCRYPTION_CHANGE_EVT: {
uint8_t encryption_enabled;
STREAM_TO_UINT8(status, p_event);
STREAM_TO_UINT16(handle, p_event);
STREAM_TO_UINT8(encryption_enabled, p_event);
- log_classic_pairing_event(bda, handle, cmd, evt_code, status, reason,
- encryption_enabled);
+ bluetooth::common::LogClassicPairingEvent(bda, handle, cmd, evt_code, status, reason, encryption_enabled);
break;
}
case HCI_CONNECTION_COMP_EVT: {
@@ -153,7 +190,7 @@ void btu_hcif_log_event_metrics(uint8_t evt_code, uint8_t* p_event) {
STREAM_TO_BDADDR(bda, p_event);
STREAM_TO_UINT8(link_type, p_event);
handle = HCID_GET_HANDLE(handle);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
&bda, handle, android::bluetooth::DIRECTION_UNKNOWN, link_type, cmd,
evt_code, android::bluetooth::hci::BLE_EVT_UNKNOWN, status, reason);
@@ -176,7 +213,7 @@ void btu_hcif_log_event_metrics(uint8_t evt_code, uint8_t* p_event) {
std::stringstream ss;
// [N - native]::SDP::[DIP - Device ID Profile]
ss << "N:SDP::DIP::" << loghex(sdp_di_vendor_id_source);
- log_manufacturer_info(
+ bluetooth::common::LogManufacturerInfo(
bda, android::bluetooth::DeviceInfoSrcEnum::DEVICE_INFO_INTERNAL,
ss.str(), loghex(sdp_di_manufacturer_id), loghex(sdp_di_model_id),
loghex(sdp_di_hw_version), "");
@@ -202,7 +239,7 @@ void btu_hcif_log_event_metrics(uint8_t evt_code, uint8_t* p_event) {
STREAM_TO_BDADDR(bda, p_event);
STREAM_TO_DEVCLASS(dc, p_event);
STREAM_TO_UINT8(link_type, p_event);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
&bda, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_INCOMING, link_type, cmd, evt_code,
android::bluetooth::hci::BLE_EVT_UNKNOWN, status, reason);
@@ -213,7 +250,7 @@ void btu_hcif_log_event_metrics(uint8_t evt_code, uint8_t* p_event) {
STREAM_TO_UINT16(handle, p_event);
STREAM_TO_UINT8(reason, p_event);
handle = HCID_GET_HANDLE(handle);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
nullptr, handle, android::bluetooth::DIRECTION_UNKNOWN,
android::bluetooth::LINK_TYPE_UNKNOWN, cmd, evt_code,
android::bluetooth::hci::BLE_EVT_UNKNOWN, status, reason);
@@ -226,7 +263,7 @@ void btu_hcif_log_event_metrics(uint8_t evt_code, uint8_t* p_event) {
STREAM_TO_BDADDR(bda, p_event);
STREAM_TO_UINT8(link_type, p_event);
handle = HCID_GET_HANDLE(handle);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
&bda, handle, android::bluetooth::DIRECTION_UNKNOWN, link_type, cmd,
evt_code, android::bluetooth::hci::BLE_EVT_UNKNOWN, status, reason);
break;
@@ -235,7 +272,7 @@ void btu_hcif_log_event_metrics(uint8_t evt_code, uint8_t* p_event) {
STREAM_TO_UINT8(status, p_event);
STREAM_TO_UINT16(handle, p_event);
handle = HCID_GET_HANDLE(handle);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
nullptr, handle, android::bluetooth::DIRECTION_UNKNOWN,
android::bluetooth::LINK_TYPE_UNKNOWN, cmd, evt_code,
android::bluetooth::hci::BLE_EVT_UNKNOWN, status, reason);
@@ -275,13 +312,13 @@ void btu_hcif_process_event(UNUSED_ATTR uint8_t controller_id, BT_HDR* p_msg) {
btu_hcif_inquiry_comp_evt(p);
break;
case HCI_INQUIRY_RESULT_EVT:
- btm_process_inq_results(p, hci_evt_len, BTM_INQ_RESULT_STANDARD);
+ btu_hcif_inquiry_result_evt(p, hci_evt_len);
break;
case HCI_INQUIRY_RSSI_RESULT_EVT:
- btm_process_inq_results(p, hci_evt_len, BTM_INQ_RESULT_WITH_RSSI);
+ btu_hcif_inquiry_rssi_result_evt(p, hci_evt_len);
break;
case HCI_EXTENDED_INQUIRY_RESULT_EVT:
- btm_process_inq_results(p, hci_evt_len, BTM_INQ_RESULT_EXTENDED);
+ btu_hcif_extended_inquiry_result_evt(p, hci_evt_len);
break;
case HCI_CONNECTION_COMP_EVT:
btu_hcif_connection_comp_evt(p, hci_evt_len);
@@ -305,110 +342,155 @@ void btu_hcif_process_event(UNUSED_ATTR uint8_t controller_id, BT_HDR* p_msg) {
btu_hcif_encryption_key_refresh_cmpl_evt(p);
break;
case HCI_READ_RMT_FEATURES_COMP_EVT:
- btm_read_remote_features_complete_raw(p);
+ btu_hcif_read_rmt_features_comp_evt(p);
break;
case HCI_READ_RMT_EXT_FEATURES_COMP_EVT:
btu_hcif_read_rmt_ext_features_comp_evt(p, hci_evt_len);
break;
case HCI_READ_RMT_VERSION_COMP_EVT:
- btm_read_remote_version_complete_raw(p);
+ btu_hcif_read_rmt_version_comp_evt(p);
+ break;
+ case HCI_QOS_SETUP_COMP_EVT:
+ btu_hcif_qos_setup_comp_evt(p);
break;
case HCI_COMMAND_COMPLETE_EVT:
- LOG_ERROR(
- "%s should not have received a command complete event. "
- "Someone didn't go through the hci transmit_command function.",
- __func__);
+ LOG_ERROR(LOG_TAG,
+ "%s should not have received a command complete event. "
+ "Someone didn't go through the hci transmit_command function.",
+ __func__);
break;
case HCI_COMMAND_STATUS_EVT:
- LOG_ERROR(
- "%s should not have received a command status event. "
- "Someone didn't go through the hci transmit_command function.",
- __func__);
+ LOG_ERROR(LOG_TAG,
+ "%s should not have received a command status event. "
+ "Someone didn't go through the hci transmit_command function.",
+ __func__);
break;
case HCI_HARDWARE_ERROR_EVT:
btu_hcif_hardware_error_evt(p);
break;
+ case HCI_FLUSH_OCCURED_EVT:
+ btu_hcif_flush_occured_evt();
+ break;
case HCI_ROLE_CHANGE_EVT:
btu_hcif_role_change_evt(p);
break;
case HCI_NUM_COMPL_DATA_PKTS_EVT:
- acl_process_num_completed_pkts(p, hci_evt_len);
+ btu_hcif_num_compl_data_pkts_evt(p, hci_evt_len);
break;
case HCI_MODE_CHANGE_EVT:
btu_hcif_mode_change_evt(p);
break;
case HCI_PIN_CODE_REQUEST_EVT:
- btm_sec_pin_code_request(p);
+ btu_hcif_pin_code_request_evt(p);
break;
case HCI_LINK_KEY_REQUEST_EVT:
- btm_sec_link_key_request(p);
+ btu_hcif_link_key_request_evt(p);
break;
case HCI_LINK_KEY_NOTIFICATION_EVT:
btu_hcif_link_key_notification_evt(p);
break;
+ case HCI_LOOPBACK_COMMAND_EVT:
+ btu_hcif_loopback_command_evt();
+ break;
+ case HCI_DATA_BUF_OVERFLOW_EVT:
+ btu_hcif_data_buf_overflow_evt();
+ break;
+ case HCI_MAX_SLOTS_CHANGED_EVT:
+ btu_hcif_max_slots_changed_evt();
+ break;
case HCI_READ_CLOCK_OFF_COMP_EVT:
btu_hcif_read_clock_off_comp_evt(p);
break;
+ case HCI_CONN_PKT_TYPE_CHANGE_EVT:
+ btu_hcif_conn_pkt_type_change_evt();
+ break;
+ case HCI_QOS_VIOLATION_EVT:
+ btu_hcif_qos_violation_evt(p);
+ break;
+ case HCI_PAGE_SCAN_MODE_CHANGE_EVT:
+ btu_hcif_page_scan_mode_change_evt();
+ break;
+ case HCI_PAGE_SCAN_REP_MODE_CHNG_EVT:
+ btu_hcif_page_scan_rep_mode_chng_evt();
+ break;
case HCI_ESCO_CONNECTION_COMP_EVT:
btu_hcif_esco_connection_comp_evt(p);
break;
case HCI_ESCO_CONNECTION_CHANGED_EVT:
btu_hcif_esco_connection_chg_evt(p);
break;
+#if (BTM_SSR_INCLUDED == TRUE)
case HCI_SNIFF_SUB_RATE_EVT:
- btm_pm_proc_ssr_evt(p, hci_evt_len);
+ btu_hcif_ssr_evt(p, hci_evt_len);
break;
+#endif /* BTM_SSR_INCLUDED == TRUE */
case HCI_RMT_HOST_SUP_FEAT_NOTIFY_EVT:
- btm_sec_rmt_host_support_feat_evt(p);
+ btu_hcif_host_support_evt(p);
break;
case HCI_IO_CAPABILITY_REQUEST_EVT:
btu_hcif_io_cap_request_evt(p);
break;
case HCI_IO_CAPABILITY_RESPONSE_EVT:
- btm_io_capabilities_rsp(p);
+ btu_hcif_io_cap_response_evt(p);
break;
case HCI_USER_CONFIRMATION_REQUEST_EVT:
- btm_proc_sp_req_evt(BTM_SP_CFM_REQ_EVT, p);
+ btu_hcif_user_conf_request_evt(p);
break;
case HCI_USER_PASSKEY_REQUEST_EVT:
- btm_proc_sp_req_evt(BTM_SP_KEY_REQ_EVT, p);
+ btu_hcif_user_passkey_request_evt(p);
break;
case HCI_REMOTE_OOB_DATA_REQUEST_EVT:
- btm_rem_oob_req(p);
+ btu_hcif_rem_oob_request_evt(p);
break;
case HCI_SIMPLE_PAIRING_COMPLETE_EVT:
- btm_simple_pair_complete(p);
+ btu_hcif_simple_pair_complete_evt(p);
break;
case HCI_USER_PASSKEY_NOTIFY_EVT:
- btm_proc_sp_req_evt(BTM_SP_KEY_NOTIF_EVT, p);
+ btu_hcif_user_passkey_notif_evt(p);
+ break;
+ case HCI_KEYPRESS_NOTIFY_EVT:
+ btu_hcif_keypress_notif_evt(p);
+ break;
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
+ case HCI_ENHANCED_FLUSH_COMPLETE_EVT:
+ btu_hcif_enhanced_flush_complete_evt();
break;
+#endif
case HCI_BLE_EVENT: {
STREAM_TO_UINT8(ble_sub_code, p);
+ HCI_TRACE_EVENT("BLE HCI(id=%d) event = 0x%02x)", hci_evt_code,
+ ble_sub_code);
+
uint8_t ble_evt_len = hci_evt_len - 1;
switch (ble_sub_code) {
case HCI_BLE_ADV_PKT_RPT_EVT: /* result of inquiry */
+ HCI_TRACE_EVENT("HCI_BLE_ADV_PKT_RPT_EVT");
btm_ble_process_adv_pkt(ble_evt_len, p);
break;
case HCI_BLE_CONN_COMPLETE_EVT:
- btm_ble_conn_complete(p, hci_evt_len, false);
+ btu_ble_ll_conn_complete_evt(p, hci_evt_len);
break;
case HCI_BLE_LL_CONN_PARAM_UPD_EVT:
btu_ble_ll_conn_param_upd_evt(p, hci_evt_len);
break;
case HCI_BLE_READ_REMOTE_FEAT_CMPL_EVT:
- btm_ble_read_remote_features_complete(p);
+ btu_ble_read_remote_feat_evt(p);
break;
- case HCI_BLE_LTK_REQ_EVT: /* received only at peripheral device */
+ case HCI_BLE_LTK_REQ_EVT: /* received only at slave device */
btu_ble_proc_ltk_req(p);
break;
+#if (BLE_PRIVACY_SPT == TRUE)
case HCI_BLE_ENHANCED_CONN_COMPLETE_EVT:
- btm_ble_conn_complete(p, hci_evt_len, true);
+ btu_ble_proc_enhanced_conn_cmpl(p, hci_evt_len);
break;
+#endif
+#if (BLE_LLT_INCLUDED == TRUE)
case HCI_BLE_RC_PARAM_REQ_EVT:
btu_ble_rc_param_req_evt(p);
break;
+#endif
case HCI_BLE_DATA_LENGTH_CHANGE_EVT:
btu_ble_data_length_change_evt(p, hci_evt_len);
break;
@@ -424,32 +506,6 @@ void btu_hcif_process_event(UNUSED_ATTR uint8_t controller_id, BT_HDR* p_msg) {
case HCI_LE_ADVERTISING_SET_TERMINATED_EVT:
btm_le_on_advertising_set_terminated(p, hci_evt_len);
break;
-
- case HCI_BLE_REQ_PEER_SCA_CPL_EVT:
- btm_acl_process_sca_cmpl_pkt(ble_evt_len, p);
- break;
-
- case HCI_BLE_PERIODIC_ADV_SYNC_EST_EVT:
- btm_ble_process_periodic_adv_sync_est_evt(ble_evt_len, p);
- break;
-
- case HCI_BLE_PERIODIC_ADV_REPORT_EVT:
- btm_ble_process_periodic_adv_pkt(ble_evt_len, p);
- break;
-
- case HCI_BLE_PERIODIC_ADV_SYNC_LOST_EVT:
- btm_ble_process_periodic_adv_sync_lost_evt(ble_evt_len, p);
- break;
-
- case HCI_BLE_CIS_EST_EVT:
- case HCI_BLE_CREATE_BIG_CPL_EVT:
- case HCI_BLE_TERM_BIG_CPL_EVT:
- case HCI_BLE_CIS_REQ_EVT:
- case HCI_BLE_BIG_SYNC_EST_EVT:
- case HCI_BLE_BIG_SYNC_LOST_EVT:
- IsoManager::GetInstance()->HandleHciEvent(ble_sub_code, p,
- ble_evt_len);
- break;
}
break;
}
@@ -479,7 +535,7 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
case HCI_CREATE_CONNECTION:
case HCI_CREATE_CONNECTION_CANCEL:
STREAM_TO_BDADDR(bd_addr, p_cmd);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
&bd_addr, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_OUTGOING,
android::bluetooth::LINK_TYPE_ACL, opcode, hci_event, kUnknownBleEvt,
@@ -488,7 +544,7 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
case HCI_DISCONNECT:
STREAM_TO_UINT16(handle, p_cmd);
STREAM_TO_UINT8(reason, p_cmd);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
nullptr, handle, android::bluetooth::DIRECTION_UNKNOWN,
android::bluetooth::LINK_TYPE_UNKNOWN, opcode, hci_event,
kUnknownBleEvt, cmd_status, reason);
@@ -496,7 +552,7 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
case HCI_SETUP_ESCO_CONNECTION:
case HCI_ENH_SETUP_ESCO_CONNECTION:
STREAM_TO_UINT16(handle, p_cmd);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
nullptr, handle, android::bluetooth::DIRECTION_OUTGOING,
android::bluetooth::LINK_TYPE_UNKNOWN, opcode, hci_event,
kUnknownBleEvt, cmd_status, android::bluetooth::hci::STATUS_UNKNOWN);
@@ -505,7 +561,7 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
case HCI_ACCEPT_ESCO_CONNECTION:
case HCI_ENH_ACCEPT_ESCO_CONNECTION:
STREAM_TO_BDADDR(bd_addr, p_cmd);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
&bd_addr, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_INCOMING,
android::bluetooth::LINK_TYPE_UNKNOWN, opcode, hci_event,
@@ -515,7 +571,7 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
case HCI_REJECT_ESCO_CONNECTION:
STREAM_TO_BDADDR(bd_addr, p_cmd);
STREAM_TO_UINT8(reason, p_cmd);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
&bd_addr, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_INCOMING,
android::bluetooth::LINK_TYPE_UNKNOWN, opcode, hci_event,
@@ -535,6 +591,7 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
const RawAddress* bd_addr_p = nullptr;
if (initiator_filter_policy == 0x00) {
bd_addr_p = &bd_addr;
+#if (BLE_PRIVACY_SPT == TRUE)
if (peer_address_type == BLE_ADDR_PUBLIC_ID ||
peer_address_type == BLE_ADDR_RANDOM_ID) {
// if identity address is not matched, this address is invalid
@@ -543,13 +600,14 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
bd_addr_p = nullptr;
}
}
+#endif
}
if (initiator_filter_policy == 0x00 ||
(cmd_status != HCI_SUCCESS && !is_cmd_status)) {
- // Selectively log to avoid log spam due to acceptlist connections:
- // - When doing non-acceptlist connection
+ // Selectively log to avoid log spam due to whitelist connections:
+ // - When doing non-whitelist connection
// - When there is an error in command status
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
bd_addr_p, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_OUTGOING,
android::bluetooth::LINK_TYPE_ACL, opcode, hci_event,
@@ -569,15 +627,17 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
const RawAddress* bd_addr_p = nullptr;
if (initiator_filter_policy == 0x00) {
bd_addr_p = &bd_addr;
+#if (BLE_PRIVACY_SPT == TRUE)
// if identity address is not matched, this should be a static address
btm_identity_addr_to_random_pseudo(&bd_addr, &peer_addr_type, false);
+#endif
}
if (initiator_filter_policy == 0x00 ||
(cmd_status != HCI_SUCCESS && !is_cmd_status)) {
- // Selectively log to avoid log spam due to acceptlist connections:
- // - When doing non-acceptlist connection
+ // Selectively log to avoid log spam due to whitelist connections:
+ // - When doing non-whitelist connection
// - When there is an error in command status
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
bd_addr_p, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_OUTGOING,
android::bluetooth::LINK_TYPE_ACL, opcode, hci_event,
@@ -588,8 +648,8 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
}
case HCI_BLE_CREATE_CONN_CANCEL:
if (cmd_status != HCI_SUCCESS && !is_cmd_status) {
- // Only log errors to prevent log spam due to acceptlist connections
- log_link_layer_connection_event(
+ // Only log errors to prevent log spam due to whitelist connections
+ bluetooth::common::LogLinkLayerConnectionEvent(
nullptr, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_OUTGOING,
android::bluetooth::LINK_TYPE_ACL, opcode, hci_event,
@@ -597,15 +657,15 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
android::bluetooth::hci::STATUS_UNKNOWN);
}
break;
- case HCI_BLE_CLEAR_ACCEPTLIST:
- log_link_layer_connection_event(
+ case HCI_BLE_CLEAR_WHITE_LIST:
+ bluetooth::common::LogLinkLayerConnectionEvent(
nullptr, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_INCOMING,
android::bluetooth::LINK_TYPE_ACL, opcode, hci_event, kUnknownBleEvt,
cmd_status, android::bluetooth::hci::STATUS_UNKNOWN);
break;
- case HCI_BLE_ADD_ACCEPTLIST:
- case HCI_BLE_REMOVE_ACCEPTLIST: {
+ case HCI_BLE_ADD_WHITE_LIST:
+ case HCI_BLE_REMOVE_WHITE_LIST: {
uint8_t peer_addr_type;
STREAM_TO_UINT8(peer_addr_type, p_cmd);
STREAM_TO_BDADDR(bd_addr, p_cmd);
@@ -613,6 +673,7 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
// When peer_addr_type is 0xFF, bd_addr should be ignored per BT spec
if (peer_addr_type != BLE_ADDR_ANONYMOUS) {
bd_addr_p = &bd_addr;
+#if (BLE_PRIVACY_SPT == TRUE)
bool addr_is_rpa = peer_addr_type == BLE_ADDR_RANDOM &&
BTM_BLE_IS_RESOLVE_BDA(bd_addr);
// Only try to match identity address for pseudo if address is not RPA
@@ -620,8 +681,9 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
// if identity address is not matched, this should be a static address
btm_identity_addr_to_random_pseudo(&bd_addr, &peer_addr_type, false);
}
+#endif
}
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
bd_addr_p, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_INCOMING,
android::bluetooth::LINK_TYPE_ACL, opcode, hci_event, kUnknownBleEvt,
@@ -629,52 +691,44 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
break;
}
case HCI_READ_LOCAL_OOB_DATA:
- log_classic_pairing_event(RawAddress::kEmpty,
- bluetooth::common::kUnknownConnectionHandle,
- opcode, hci_event, cmd_status,
- android::bluetooth::hci::STATUS_UNKNOWN, 0);
+ bluetooth::common::LogClassicPairingEvent(RawAddress::kEmpty, bluetooth::common::kUnknownConnectionHandle, opcode,
+ hci_event, cmd_status, android::bluetooth::hci::STATUS_UNKNOWN, 0);
break;
case HCI_WRITE_SIMPLE_PAIRING_MODE: {
uint8_t simple_pairing_mode;
STREAM_TO_UINT8(simple_pairing_mode, p_cmd);
- log_classic_pairing_event(
- RawAddress::kEmpty, bluetooth::common::kUnknownConnectionHandle,
- opcode, hci_event, cmd_status,
- android::bluetooth::hci::STATUS_UNKNOWN, simple_pairing_mode);
+ bluetooth::common::LogClassicPairingEvent(RawAddress::kEmpty, bluetooth::common::kUnknownConnectionHandle, opcode,
+ hci_event, cmd_status, android::bluetooth::hci::STATUS_UNKNOWN,
+ simple_pairing_mode);
break;
}
case HCI_WRITE_SECURE_CONNS_SUPPORT: {
uint8_t secure_conn_host_support;
STREAM_TO_UINT8(secure_conn_host_support, p_cmd);
- log_classic_pairing_event(
- RawAddress::kEmpty, bluetooth::common::kUnknownConnectionHandle,
- opcode, hci_event, cmd_status,
- android::bluetooth::hci::STATUS_UNKNOWN, secure_conn_host_support);
+ bluetooth::common::LogClassicPairingEvent(RawAddress::kEmpty, bluetooth::common::kUnknownConnectionHandle, opcode,
+ hci_event, cmd_status, android::bluetooth::hci::STATUS_UNKNOWN,
+ secure_conn_host_support);
break;
}
case HCI_AUTHENTICATION_REQUESTED:
STREAM_TO_UINT16(handle, p_cmd);
- log_classic_pairing_event(RawAddress::kEmpty, handle, opcode, hci_event,
- cmd_status,
- android::bluetooth::hci::STATUS_UNKNOWN, 0);
+ bluetooth::common::LogClassicPairingEvent(RawAddress::kEmpty, handle, opcode, hci_event, cmd_status,
+ android::bluetooth::hci::STATUS_UNKNOWN, 0);
break;
case HCI_SET_CONN_ENCRYPTION: {
STREAM_TO_UINT16(handle, p_cmd);
uint8_t encryption_enable;
STREAM_TO_UINT8(encryption_enable, p_cmd);
- log_classic_pairing_event(
- RawAddress::kEmpty, handle, opcode, hci_event, cmd_status,
- android::bluetooth::hci::STATUS_UNKNOWN, encryption_enable);
+ bluetooth::common::LogClassicPairingEvent(RawAddress::kEmpty, handle, opcode, hci_event, cmd_status,
+ android::bluetooth::hci::STATUS_UNKNOWN, encryption_enable);
break;
}
case HCI_DELETE_STORED_LINK_KEY: {
uint8_t delete_all_flag;
STREAM_TO_BDADDR(bd_addr, p_cmd);
STREAM_TO_UINT8(delete_all_flag, p_cmd);
- log_classic_pairing_event(
- bd_addr, bluetooth::common::kUnknownConnectionHandle, opcode,
- hci_event, cmd_status, android::bluetooth::hci::STATUS_UNKNOWN,
- delete_all_flag);
+ bluetooth::common::LogClassicPairingEvent(bd_addr, bluetooth::common::kUnknownConnectionHandle, opcode, hci_event,
+ cmd_status, android::bluetooth::hci::STATUS_UNKNOWN, delete_all_flag);
break;
}
case HCI_RMT_NAME_REQUEST:
@@ -689,16 +743,14 @@ static void btu_hcif_log_command_metrics(uint16_t opcode, uint8_t* p_cmd,
case HCI_REM_OOB_DATA_REQ_REPLY:
case HCI_REM_OOB_DATA_REQ_NEG_REPLY:
STREAM_TO_BDADDR(bd_addr, p_cmd);
- log_classic_pairing_event(
- bd_addr, bluetooth::common::kUnknownConnectionHandle, opcode,
- hci_event, cmd_status, android::bluetooth::hci::STATUS_UNKNOWN, 0);
+ bluetooth::common::LogClassicPairingEvent(bd_addr, bluetooth::common::kUnknownConnectionHandle, opcode, hci_event,
+ cmd_status, android::bluetooth::hci::STATUS_UNKNOWN, 0);
break;
case HCI_IO_CAP_REQ_NEG_REPLY:
STREAM_TO_BDADDR(bd_addr, p_cmd);
STREAM_TO_UINT8(reason, p_cmd);
- log_classic_pairing_event(bd_addr,
- bluetooth::common::kUnknownConnectionHandle,
- opcode, hci_event, cmd_status, reason, 0);
+ bluetooth::common::LogClassicPairingEvent(bd_addr, bluetooth::common::kUnknownConnectionHandle, opcode, hci_event,
+ cmd_status, reason, 0);
break;
}
}
@@ -744,7 +796,7 @@ using hci_cmd_cb = base::OnceCallback<void(
struct cmd_with_cb_data {
hci_cmd_cb cb;
- base::Location posted_from;
+ Location posted_from;
};
void cmd_with_cb_data_init(cmd_with_cb_data* cb_wrapper) {
@@ -771,11 +823,11 @@ static void btu_hcif_log_command_complete_metrics(uint16_t opcode,
uint16_t hci_ble_event = android::bluetooth::hci::BLE_EVT_UNKNOWN;
RawAddress bd_addr = RawAddress::kEmpty;
switch (opcode) {
- case HCI_BLE_CLEAR_ACCEPTLIST:
- case HCI_BLE_ADD_ACCEPTLIST:
- case HCI_BLE_REMOVE_ACCEPTLIST: {
+ case HCI_BLE_CLEAR_WHITE_LIST:
+ case HCI_BLE_ADD_WHITE_LIST:
+ case HCI_BLE_REMOVE_WHITE_LIST: {
STREAM_TO_UINT8(status, p_return_params);
- log_link_layer_connection_event(
+ bluetooth::common::LogLinkLayerConnectionEvent(
nullptr, bluetooth::common::kUnknownConnectionHandle,
android::bluetooth::DIRECTION_INCOMING,
android::bluetooth::LINK_TYPE_ACL, opcode, hci_event, hci_ble_event,
@@ -787,9 +839,8 @@ static void btu_hcif_log_command_complete_metrics(uint16_t opcode,
case HCI_WRITE_SIMPLE_PAIRING_MODE:
case HCI_WRITE_SECURE_CONNS_SUPPORT:
STREAM_TO_UINT8(status, p_return_params);
- log_classic_pairing_event(RawAddress::kEmpty,
- bluetooth::common::kUnknownConnectionHandle,
- opcode, hci_event, status, reason, 0);
+ bluetooth::common::LogClassicPairingEvent(RawAddress::kEmpty, bluetooth::common::kUnknownConnectionHandle, opcode,
+ hci_event, status, reason, 0);
break;
case HCI_READ_ENCR_KEY_SIZE: {
uint16_t handle;
@@ -797,8 +848,8 @@ static void btu_hcif_log_command_complete_metrics(uint16_t opcode,
STREAM_TO_UINT8(status, p_return_params);
STREAM_TO_UINT16(handle, p_return_params);
STREAM_TO_UINT8(key_size, p_return_params);
- log_classic_pairing_event(RawAddress::kEmpty, handle, opcode, hci_event,
- status, reason, key_size);
+ bluetooth::common::LogClassicPairingEvent(RawAddress::kEmpty, handle, opcode, hci_event, status, reason,
+ key_size);
break;
}
case HCI_LINK_KEY_REQUEST_REPLY:
@@ -813,9 +864,8 @@ static void btu_hcif_log_command_complete_metrics(uint16_t opcode,
case HCI_REM_OOB_DATA_REQ_NEG_REPLY:
STREAM_TO_UINT8(status, p_return_params);
STREAM_TO_BDADDR(bd_addr, p_return_params);
- log_classic_pairing_event(bd_addr,
- bluetooth::common::kUnknownConnectionHandle,
- opcode, hci_event, status, reason, 0);
+ bluetooth::common::LogClassicPairingEvent(bd_addr, bluetooth::common::kUnknownConnectionHandle, opcode, hci_event,
+ status, reason, 0);
break;
}
}
@@ -890,9 +940,9 @@ static void btu_hcif_command_status_evt_with_cb(uint8_t status, BT_HDR* command,
/* This function is called to send commands to the Host Controller. |cb| is
* called when command status event is called with error code, or when the
* command complete event is received. */
-void btu_hcif_send_cmd_with_cb(const base::Location& posted_from,
- uint16_t opcode, uint8_t* params,
- uint8_t params_len, hci_cmd_cb cb) {
+void btu_hcif_send_cmd_with_cb(const Location& posted_from, uint16_t opcode,
+ uint8_t* params, uint8_t params_len,
+ hci_cmd_cb cb) {
BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
uint8_t* pp = (uint8_t*)(p + 1);
@@ -940,6 +990,49 @@ static void btu_hcif_inquiry_comp_evt(uint8_t* p) {
/*******************************************************************************
*
+ * Function btu_hcif_inquiry_result_evt
+ *
+ * Description Process event HCI_INQUIRY_RESULT_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_inquiry_result_evt(uint8_t* p, uint8_t hci_evt_len) {
+ /* Store results in the cache */
+ btm_process_inq_results(p, hci_evt_len, BTM_INQ_RESULT_STANDARD);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_inquiry_rssi_result_evt
+ *
+ * Description Process event HCI_INQUIRY_RSSI_RESULT_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_inquiry_rssi_result_evt(uint8_t* p, uint8_t hci_evt_len) {
+ /* Store results in the cache */
+ btm_process_inq_results(p, hci_evt_len, BTM_INQ_RESULT_WITH_RSSI);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_extended_inquiry_result_evt
+ *
+ * Description Process event HCI_EXTENDED_INQUIRY_RESULT_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_extended_inquiry_result_evt(uint8_t* p,
+ uint8_t hci_evt_len) {
+ /* Store results in the cache */
+ btm_process_inq_results(p, hci_evt_len, BTM_INQ_RESULT_EXTENDED);
+}
+
+/*******************************************************************************
+ *
* Function btu_hcif_connection_comp_evt
*
* Description Process event HCI_CONNECTION_COMP_EVT
@@ -977,13 +1070,14 @@ static void btu_hcif_connection_comp_evt(uint8_t* p, uint8_t evt_len) {
}
if (link_type == HCI_LINK_TYPE_ACL) {
- btm_acl_connected(bda, handle, static_cast<tHCI_STATUS>(status), enc_mode);
+ btm_sec_connected(bda, handle, status, enc_mode);
+
+ l2c_link_hci_conn_comp(status, handle, bda);
} else {
memset(&esco_data, 0, sizeof(tBTM_ESCO_DATA));
/* esco_data.link_type = HCI_LINK_TYPE_SCO; already zero */
esco_data.bd_addr = bda;
- btm_sco_connected(static_cast<tHCI_STATUS>(status), bda, handle,
- &esco_data);
+ btm_sco_connected(status, &bda, handle, &esco_data);
}
}
@@ -1005,8 +1099,10 @@ static void btu_hcif_connection_request_evt(uint8_t* p) {
STREAM_TO_DEVCLASS(dc, p);
STREAM_TO_UINT8(link_type, p);
+ /* Pass request to security manager to check connect filters before */
+ /* passing request to l2cap */
if (link_type == HCI_LINK_TYPE_ACL) {
- btm_acl_connection_request(bda, dc);
+ btm_sec_conn_req(bda, dc);
} else {
btm_sco_conn_req(bda, dc, link_type);
}
@@ -1032,8 +1128,18 @@ static void btu_hcif_disconnection_comp_evt(uint8_t* p) {
handle = HCID_GET_HANDLE(handle);
- btm_acl_disconnected(static_cast<tHCI_STATUS>(status), handle,
- static_cast<tHCI_STATUS>(reason));
+ if ((reason != HCI_ERR_CONN_CAUSE_LOCAL_HOST) &&
+ (reason != HCI_ERR_PEER_USER)) {
+ /* Uncommon disconnection reasons */
+ HCI_TRACE_DEBUG("%s: Got Disconn Complete Event: reason=%d, handle=%d",
+ __func__, reason, handle);
+ }
+
+ /* If L2CAP doesn't know about it, send it to SCO */
+ if (!l2c_link_hci_disc_comp(handle, reason)) btm_sco_removed(handle, reason);
+
+ /* Notify security manager */
+ btm_sec_disconnected(handle, reason);
}
/*******************************************************************************
@@ -1052,7 +1158,7 @@ static void btu_hcif_authentication_comp_evt(uint8_t* p) {
STREAM_TO_UINT8(status, p);
STREAM_TO_UINT16(handle, p);
- btm_sec_auth_complete(handle, static_cast<tHCI_STATUS>(status));
+ btm_sec_auth_complete(handle, status);
}
/*******************************************************************************
@@ -1075,8 +1181,7 @@ static void btu_hcif_rmt_name_request_comp_evt(uint8_t* p, uint16_t evt_len) {
btm_process_remote_name(&bd_addr, p, evt_len, status);
- btm_sec_rmt_name_request_complete(&bd_addr, p,
- static_cast<tHCI_STATUS>(status));
+ btm_sec_rmt_name_request_complete(&bd_addr, p, status);
}
constexpr uint8_t MIN_KEY_SIZE = 7;
@@ -1093,7 +1198,7 @@ static void read_encryption_key_size_complete_after_encryption_change(uint8_t st
if (status != HCI_SUCCESS) {
LOG(INFO) << __func__ << ": disconnecting, status: " << loghex(status);
- acl_disconnect_from_handle(handle, HCI_ERR_PEER_USER);
+ btsnd_hcic_disconnect(handle, HCI_ERR_PEER_USER);
return;
}
@@ -1102,15 +1207,13 @@ static void read_encryption_key_size_complete_after_encryption_change(uint8_t st
LOG(ERROR) << __func__ << " encryption key too short, disconnecting. handle: " << loghex(handle)
<< " key_size: " << +key_size;
- acl_disconnect_from_handle(handle, HCI_ERR_HOST_REJECT_SECURITY);
+ btsnd_hcic_disconnect(handle, HCI_ERR_HOST_REJECT_SECURITY);
return;
}
// good key size - succeed
- btm_acl_encrypt_change(handle, static_cast<tHCI_STATUS>(status),
- 1 /* enable */);
- btm_sec_encrypt_change(handle, static_cast<tHCI_STATUS>(status),
- 1 /* enable */);
+ btm_acl_encrypt_change(handle, status, 1 /* enable */);
+ btm_sec_encrypt_change(handle, status, 1 /* enable */);
}
/*******************************************************************************
*
@@ -1136,10 +1239,8 @@ static void btu_hcif_encryption_change_evt(uint8_t* p) {
return;
}
- btm_acl_encrypt_change(handle, static_cast<tHCI_STATUS>(status),
- encr_enable);
- btm_sec_encrypt_change(handle, static_cast<tHCI_STATUS>(status),
- encr_enable);
+ btm_acl_encrypt_change(handle, status, encr_enable);
+ btm_sec_encrypt_change(handle, status, encr_enable);
} else {
btsnd_hcic_read_encryption_key_size(handle, base::Bind(&read_encryption_key_size_complete_after_encryption_change));
}
@@ -1147,6 +1248,19 @@ static void btu_hcif_encryption_change_evt(uint8_t* p) {
/*******************************************************************************
*
+ * Function btu_hcif_read_rmt_features_comp_evt
+ *
+ * Description Process event HCI_READ_RMT_FEATURES_COMP_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_read_rmt_features_comp_evt(uint8_t* p) {
+ btm_read_remote_features_complete(p);
+}
+
+/*******************************************************************************
+ *
* Function btu_hcif_read_rmt_ext_features_comp_evt
*
* Description Process event HCI_READ_RMT_EXT_FEATURES_COMP_EVT
@@ -1163,7 +1277,7 @@ static void btu_hcif_read_rmt_ext_features_comp_evt(uint8_t* p,
STREAM_TO_UINT8(status, p_cur);
if (status == HCI_SUCCESS)
- btm_read_remote_ext_features_complete_raw(p, evt_len);
+ btm_read_remote_ext_features_complete(p, evt_len);
else {
STREAM_TO_UINT16(handle, p_cur);
btm_read_remote_ext_features_failed(status, handle);
@@ -1172,6 +1286,45 @@ static void btu_hcif_read_rmt_ext_features_comp_evt(uint8_t* p,
/*******************************************************************************
*
+ * Function btu_hcif_read_rmt_version_comp_evt
+ *
+ * Description Process event HCI_READ_RMT_VERSION_COMP_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_read_rmt_version_comp_evt(uint8_t* p) {
+ btm_read_remote_version_complete(p);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_qos_setup_comp_evt
+ *
+ * Description Process event HCI_QOS_SETUP_COMP_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_qos_setup_comp_evt(uint8_t* p) {
+ uint8_t status;
+ uint16_t handle;
+ FLOW_SPEC flow;
+
+ STREAM_TO_UINT8(status, p);
+ STREAM_TO_UINT16(handle, p);
+ STREAM_TO_UINT8(flow.qos_flags, p);
+ STREAM_TO_UINT8(flow.service_type, p);
+ STREAM_TO_UINT32(flow.token_rate, p);
+ STREAM_TO_UINT32(flow.peak_bandwidth, p);
+ STREAM_TO_UINT32(flow.latency, p);
+ STREAM_TO_UINT32(flow.delay_variation, p);
+
+ btm_qos_setup_complete(status, handle, &flow);
+}
+
+/*******************************************************************************
+ *
* Function btu_hcif_esco_connection_comp_evt
*
* Description Process event HCI_ESCO_CONNECTION_COMP_EVT
@@ -1199,7 +1352,7 @@ static void btu_hcif_esco_connection_comp_evt(uint8_t* p) {
handle = HCID_GET_HANDLE(handle);
data.bd_addr = bda;
- btm_sco_connected(static_cast<tHCI_STATUS>(status), bda, handle, &data);
+ btm_sco_connected(status, &bda, handle, &data);
}
/*******************************************************************************
@@ -1251,6 +1404,7 @@ static void btu_hcif_hdl_command_complete(uint16_t opcode, uint8_t* p,
btm_process_cancel_complete(HCI_SUCCESS, BTM_BR_INQUIRY_MASK);
break;
case HCI_SET_EVENT_FILTER:
+ btm_event_filter_complete(p);
break;
case HCI_DELETE_STORED_LINK_KEY:
@@ -1290,6 +1444,7 @@ static void btu_hcif_hdl_command_complete(uint16_t opcode, uint8_t* p,
break;
case HCI_READ_INQ_TX_POWER_LEVEL:
+ btm_read_inq_tx_power_complete(p);
break;
/* BLE Commands sComplete*/
@@ -1322,6 +1477,7 @@ static void btu_hcif_hdl_command_complete(uint16_t opcode, uint8_t* p,
btm_ble_test_command_complete(p);
break;
+#if (BLE_PRIVACY_SPT == TRUE)
case HCI_BLE_ADD_DEV_RESOLVING_LIST:
btm_ble_add_resolving_list_entry_complete(p, evt_len);
break;
@@ -1342,6 +1498,7 @@ static void btu_hcif_hdl_command_complete(uint16_t opcode, uint8_t* p,
case HCI_BLE_SET_ADDR_RESOLUTION_ENABLE:
case HCI_BLE_SET_RAND_PRIV_ADDR_TIMOUT:
break;
+#endif
default:
if ((opcode & HCI_GRP_VENDOR_SPECIFIC) == HCI_GRP_VENDOR_SPECIFIC)
btm_vsc_complete(p, opcode, evt_len, (tBTM_VSC_CMPL_CB*)p_cplt_cback);
@@ -1406,43 +1563,47 @@ static void btu_hcif_hdl_command_status(uint16_t opcode, uint8_t status,
btm_process_inq_complete(status, BTM_BR_INQUIRY_MASK);
}
break;
+ case HCI_QOS_SETUP:
+ if (status != HCI_SUCCESS) {
+ // Tell qos setup that we are done
+ btm_qos_setup_complete(status, 0, nullptr);
+ }
+ break;
case HCI_SWITCH_ROLE:
if (status != HCI_SUCCESS) {
// Tell BTM that the command failed
STREAM_TO_BDADDR(bd_addr, p_cmd);
- btm_acl_role_changed(static_cast<tHCI_STATUS>(status), bd_addr,
- HCI_ROLE_UNKNOWN);
+ btm_acl_role_changed(status, &bd_addr, BTM_ROLE_UNDEFINED);
+ l2c_link_role_changed(nullptr, BTM_ROLE_UNDEFINED,
+ HCI_ERR_COMMAND_DISALLOWED);
}
break;
case HCI_CREATE_CONNECTION:
if (status != HCI_SUCCESS) {
STREAM_TO_BDADDR(bd_addr, p_cmd);
- btm_acl_connected(bd_addr, HCI_INVALID_HANDLE,
- static_cast<tHCI_STATUS>(status), 0);
+ btm_sec_connected(bd_addr, HCI_INVALID_HANDLE, status, 0);
+ l2c_link_hci_conn_comp(status, HCI_INVALID_HANDLE, bd_addr);
}
break;
case HCI_AUTHENTICATION_REQUESTED:
if (status != HCI_SUCCESS) {
// Device refused to start authentication
// This is treated as an authentication failure
- btm_sec_auth_complete(HCI_INVALID_HANDLE,
- static_cast<tHCI_STATUS>(status));
+ btm_sec_auth_complete(BTM_INVALID_HCI_HANDLE, status);
}
break;
case HCI_SET_CONN_ENCRYPTION:
if (status != HCI_SUCCESS) {
// Device refused to start encryption
// This is treated as an encryption failure
- btm_sec_encrypt_change(HCI_INVALID_HANDLE,
- static_cast<tHCI_STATUS>(status), false);
+ btm_sec_encrypt_change(BTM_INVALID_HCI_HANDLE, status, false);
}
break;
case HCI_RMT_NAME_REQUEST:
if (status != HCI_SUCCESS) {
// Tell inquiry processing that we are done
btm_process_remote_name(nullptr, nullptr, 0, status);
- btm_sec_rmt_name_request_complete(nullptr, nullptr,
- static_cast<tHCI_STATUS>(status));
+ btm_sec_rmt_name_request_complete(nullptr, nullptr, status);
}
break;
case HCI_READ_RMT_EXT_FEATURES:
@@ -1458,6 +1619,8 @@ static void btu_hcif_hdl_command_status(uint16_t opcode, uint8_t status,
// Determine if initial connection failed or is a change of setup
if (btm_is_sco_active(handle)) {
btm_esco_proc_conn_chg(status, handle, 0, 0, 0, 0);
+ } else {
+ btm_sco_connected(status, nullptr, handle, nullptr);
}
}
break;
@@ -1466,7 +1629,7 @@ static void btu_hcif_hdl_command_status(uint16_t opcode, uint8_t status,
case HCI_BLE_CREATE_LL_CONN:
case HCI_LE_EXTENDED_CREATE_CONNECTION:
if (status != HCI_SUCCESS) {
- btm_ble_create_ll_conn_complete(static_cast<tHCI_STATUS>(status));
+ btm_ble_create_ll_conn_complete(status);
}
break;
case HCI_BLE_START_ENC:
@@ -1484,13 +1647,13 @@ static void btu_hcif_hdl_command_status(uint16_t opcode, uint8_t status,
if (status != HCI_SUCCESS) {
// Allow SCO initiation to continue if waiting for change mode event
STREAM_TO_UINT16(handle, p_cmd);
- btm_sco_chk_pend_unpark(static_cast<tHCI_STATUS>(status), handle);
+ btm_sco_chk_pend_unpark(status, handle);
}
FALLTHROUGH_INTENDED; /* FALLTHROUGH */
case HCI_HOLD_MODE:
case HCI_SNIFF_MODE:
case HCI_PARK_MODE:
- btm_pm_proc_cmd_status(static_cast<tHCI_STATUS>(status));
+ btm_pm_proc_cmd_status(status);
break;
default:
@@ -1544,15 +1707,30 @@ static void btu_hcif_hardware_error_evt(uint8_t* p) {
if (hci_is_root_inflammation_event_received()) {
// Ignore the hardware error event here as we have already received
// root inflammation event earlier.
- HCI_TRACE_ERROR("H/w error event after root inflammation event!");
+ HCI_TRACE_ERROR(LOG_TAG, "H/w error event after root inflammation event!");
return;
}
- BTA_sys_signal_hw_error();
+ /* If anyone wants device status notifications, give him one. */
+ btm_report_device_status(BTM_DEV_STATUS_DOWN);
+
+ /* Reset the controller */
+ if (BTM_IsDeviceUp()) BTM_DeviceReset(NULL);
}
/*******************************************************************************
*
+ * Function btu_hcif_flush_occured_evt
+ *
+ * Description Process event HCI_FLUSH_OCCURED_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_flush_occured_evt(void) {}
+
+/*******************************************************************************
+ *
* Function btu_hcif_role_change_evt
*
* Description Process event HCI_ROLE_CHANGE_EVT
@@ -1569,8 +1747,26 @@ static void btu_hcif_role_change_evt(uint8_t* p) {
STREAM_TO_BDADDR(bda, p);
STREAM_TO_UINT8(role, p);
- btm_rejectlist_role_change_device(bda, status);
- btm_acl_role_changed(to_hci_status_code(status), bda, to_hci_role(role));
+ btm_blacklist_role_change_device(bda, status);
+ l2c_link_role_changed(&bda, role, status);
+ btm_acl_role_changed(status, &bda, role);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_num_compl_data_pkts_evt
+ *
+ * Description Process event HCI_NUM_COMPL_DATA_PKTS_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_num_compl_data_pkts_evt(uint8_t* p, uint8_t evt_len) {
+ /* Process for L2CAP and SCO */
+ l2c_link_process_num_completed_pkts(p, evt_len);
+
+ /* Send on to SCO */
+ /*?? No SCO for now */
}
/*******************************************************************************
@@ -1593,9 +1789,8 @@ static void btu_hcif_mode_change_evt(uint8_t* p) {
STREAM_TO_UINT16(handle, p);
STREAM_TO_UINT8(current_mode, p);
STREAM_TO_UINT16(interval, p);
- btm_sco_chk_pend_unpark(static_cast<tHCI_STATUS>(status), handle);
- btm_pm_proc_mode_change(static_cast<tHCI_STATUS>(status), handle,
- static_cast<tHCI_MODE>(current_mode), interval);
+ btm_sco_chk_pend_unpark(status, handle);
+ btm_pm_proc_mode_change(status, handle, current_mode, interval);
#if (HID_DEV_INCLUDED == TRUE && HID_DEV_PM_INCLUDED == TRUE)
hidd_pm_proc_mode_change(status, current_mode, interval);
@@ -1604,6 +1799,58 @@ static void btu_hcif_mode_change_evt(uint8_t* p) {
/*******************************************************************************
*
+ * Function btu_hcif_ssr_evt
+ *
+ * Description Process event HCI_SNIFF_SUB_RATE_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+#if (BTM_SSR_INCLUDED == TRUE)
+static void btu_hcif_ssr_evt(uint8_t* p, uint16_t evt_len) {
+ btm_pm_proc_ssr_evt(p, evt_len);
+}
+#endif
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_pin_code_request_evt
+ *
+ * Description Process event HCI_PIN_CODE_REQUEST_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_pin_code_request_evt(uint8_t* p) {
+ RawAddress bda;
+
+ STREAM_TO_BDADDR(bda, p);
+
+ /* Tell L2CAP that there was a PIN code request, */
+ /* it may need to stretch timeouts */
+ l2c_pin_code_request(bda);
+
+ btm_sec_pin_code_request(bda);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_link_key_request_evt
+ *
+ * Description Process event HCI_LINK_KEY_REQUEST_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_link_key_request_evt(uint8_t* p) {
+ RawAddress bda;
+
+ STREAM_TO_BDADDR(bda, p);
+ btm_sec_link_key_request(bda);
+}
+
+/*******************************************************************************
+ *
* Function btu_hcif_link_key_notification_evt
*
* Description Process event HCI_LINK_KEY_NOTIFICATION_EVT
@@ -1625,6 +1872,39 @@ static void btu_hcif_link_key_notification_evt(uint8_t* p) {
/*******************************************************************************
*
+ * Function btu_hcif_loopback_command_evt
+ *
+ * Description Process event HCI_LOOPBACK_COMMAND_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_loopback_command_evt(void) {}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_data_buf_overflow_evt
+ *
+ * Description Process event HCI_DATA_BUF_OVERFLOW_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_data_buf_overflow_evt(void) {}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_max_slots_changed_evt
+ *
+ * Description Process event HCI_MAX_SLOTS_CHANGED_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_max_slots_changed_evt(void) {}
+
+/*******************************************************************************
+ *
* Function btu_hcif_read_clock_off_comp_evt
*
* Description Process event HCI_READ_CLOCK_OFF_COMP_EVT
@@ -1647,15 +1927,81 @@ static void btu_hcif_read_clock_off_comp_evt(uint8_t* p) {
handle = HCID_GET_HANDLE(handle);
+ btm_process_clk_off_comp_evt(handle, clock_offset);
btm_sec_update_clock_offset(handle, clock_offset);
}
+/*******************************************************************************
+ *
+ * Function btu_hcif_conn_pkt_type_change_evt
+ *
+ * Description Process event HCI_CONN_PKT_TYPE_CHANGE_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_conn_pkt_type_change_evt(void) {}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_qos_violation_evt
+ *
+ * Description Process event HCI_QOS_VIOLATION_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_qos_violation_evt(uint8_t* p) {
+ uint16_t handle;
+
+ STREAM_TO_UINT16(handle, p);
+
+ handle = HCID_GET_HANDLE(handle);
+
+ l2c_link_hci_qos_violation(handle);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_page_scan_mode_change_evt
+ *
+ * Description Process event HCI_PAGE_SCAN_MODE_CHANGE_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_page_scan_mode_change_evt(void) {}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_page_scan_rep_mode_chng_evt
+ *
+ * Description Process event HCI_PAGE_SCAN_REP_MODE_CHNG_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_page_scan_rep_mode_chng_evt(void) {}
+
/**********************************************
* Simple Pairing Events
**********************************************/
/*******************************************************************************
*
+ * Function btu_hcif_host_support_evt
+ *
+ * Description Process event HCI_RMT_HOST_SUP_FEAT_NOTIFY_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_host_support_evt(uint8_t* p) {
+ btm_sec_rmt_host_support_feat_evt(p);
+}
+
+/*******************************************************************************
+ *
* Function btu_hcif_io_cap_request_evt
*
* Description Process event HCI_IO_CAPABILITY_REQUEST_EVT
@@ -1669,6 +2015,109 @@ static void btu_hcif_io_cap_request_evt(uint8_t* p) {
btm_io_capabilities_req(bda);
}
+/*******************************************************************************
+ *
+ * Function btu_hcif_io_cap_response_evt
+ *
+ * Description Process event HCI_IO_CAPABILITY_RESPONSE_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_io_cap_response_evt(uint8_t* p) {
+ btm_io_capabilities_rsp(p);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_user_conf_request_evt
+ *
+ * Description Process event HCI_USER_CONFIRMATION_REQUEST_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_user_conf_request_evt(uint8_t* p) {
+ btm_proc_sp_req_evt(BTM_SP_CFM_REQ_EVT, p);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_user_passkey_request_evt
+ *
+ * Description Process event HCI_USER_PASSKEY_REQUEST_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_user_passkey_request_evt(uint8_t* p) {
+ btm_proc_sp_req_evt(BTM_SP_KEY_REQ_EVT, p);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_user_passkey_notif_evt
+ *
+ * Description Process event HCI_USER_PASSKEY_NOTIFY_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_user_passkey_notif_evt(uint8_t* p) {
+ btm_proc_sp_req_evt(BTM_SP_KEY_NOTIF_EVT, p);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_keypress_notif_evt
+ *
+ * Description Process event HCI_KEYPRESS_NOTIFY_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_keypress_notif_evt(uint8_t* p) {
+ btm_keypress_notif_evt(p);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_rem_oob_request_evt
+ *
+ * Description Process event HCI_REMOTE_OOB_DATA_REQUEST_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_rem_oob_request_evt(uint8_t* p) { btm_rem_oob_req(p); }
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_simple_pair_complete_evt
+ *
+ * Description Process event HCI_SIMPLE_PAIRING_COMPLETE_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void btu_hcif_simple_pair_complete_evt(uint8_t* p) {
+ btm_simple_pair_complete(p);
+}
+
+/*******************************************************************************
+ *
+ * Function btu_hcif_enhanced_flush_complete_evt
+ *
+ * Description Process event HCI_ENHANCED_FLUSH_COMPLETE_EVT
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
+static void btu_hcif_enhanced_flush_complete_evt(void) {
+ /* This is empty until an upper layer cares about returning event */
+}
+#endif
/**********************************************
* End of Simple Pairing Events
**********************************************/
@@ -1684,7 +2133,7 @@ static void read_encryption_key_size_complete_after_key_refresh(uint8_t status,
if (status != HCI_SUCCESS) {
LOG(INFO) << __func__ << ": disconnecting, status: " << loghex(status);
- acl_disconnect_from_handle(handle, HCI_ERR_PEER_USER);
+ btsnd_hcic_disconnect(handle, HCI_ERR_PEER_USER);
return;
}
@@ -1693,12 +2142,11 @@ static void read_encryption_key_size_complete_after_key_refresh(uint8_t status,
LOG(ERROR) << __func__ << " encryption key too short, disconnecting. handle: " << loghex(handle)
<< " key_size: " << +key_size;
- acl_disconnect_from_handle(handle, HCI_ERR_HOST_REJECT_SECURITY);
+ btsnd_hcic_disconnect(handle, HCI_ERR_HOST_REJECT_SECURITY);
return;
}
- btm_sec_encrypt_change(handle, static_cast<tHCI_STATUS>(status),
- 1 /* enc_enable */);
+ btm_sec_encrypt_change(handle, status, 1 /* enc_enable */);
}
static void btu_hcif_encryption_key_refresh_cmpl_evt(uint8_t* p) {
@@ -1709,8 +2157,7 @@ static void btu_hcif_encryption_key_refresh_cmpl_evt(uint8_t* p) {
STREAM_TO_UINT16(handle, p);
if (status != HCI_SUCCESS || BTM_IsBleConnection(handle)) {
- btm_sec_encrypt_change(handle, static_cast<tHCI_STATUS>(status),
- (status == HCI_SUCCESS) ? 1 : 0);
+ btm_sec_encrypt_change(handle, status, (status == HCI_SUCCESS) ? 1 : 0);
} else {
btsnd_hcic_read_encryption_key_size(handle, base::Bind(&read_encryption_key_size_complete_after_key_refresh));
}
@@ -1720,12 +2167,21 @@ static void btu_hcif_encryption_key_refresh_cmpl_evt(uint8_t* p) {
* BLE Events
**********************************************/
-extern void gatt_notify_conn_update(const RawAddress& remote, uint16_t interval,
+static void btu_ble_ll_conn_complete_evt(uint8_t* p, uint16_t evt_len) {
+ btm_ble_conn_complete(p, evt_len, false);
+}
+#if (BLE_PRIVACY_SPT == TRUE)
+static void btu_ble_proc_enhanced_conn_cmpl(uint8_t* p, uint16_t evt_len) {
+ btm_ble_conn_complete(p, evt_len, true);
+}
+#endif
+
+extern void gatt_notify_conn_update(uint16_t handle, uint16_t interval,
uint16_t latency, uint16_t timeout,
- tHCI_STATUS status);
+ uint8_t status);
static void btu_ble_ll_conn_param_upd_evt(uint8_t* p, uint16_t evt_len) {
- /* LE connection update has completed successfully as a central. */
+ /* LE connection update has completed successfully as a master. */
/* We can enable the update request if the result is a success. */
/* extract the HCI handle first */
uint8_t status;
@@ -1740,8 +2196,13 @@ static void btu_ble_ll_conn_param_upd_evt(uint8_t* p, uint16_t evt_len) {
STREAM_TO_UINT16(latency, p);
STREAM_TO_UINT16(timeout, p);
- acl_ble_update_event_received(static_cast<tHCI_STATUS>(status), handle,
- interval, latency, timeout);
+ l2cble_process_conn_update_evt(handle, status, interval, latency, timeout);
+
+ gatt_notify_conn_update(handle & 0x0FFF, interval, latency, timeout, status);
+}
+
+static void btu_ble_read_remote_feat_evt(uint8_t* p) {
+ btm_ble_read_remote_features_complete(p);
}
static void btu_ble_proc_ltk_req(uint8_t* p) {
@@ -1776,6 +2237,7 @@ static void btu_ble_data_length_change_evt(uint8_t* p, uint16_t evt_len) {
/**********************************************
* End of BLE Events Handler
**********************************************/
+#if (BLE_LLT_INCLUDED == TRUE)
static void btu_ble_rc_param_req_evt(uint8_t* p) {
uint16_t handle;
uint16_t int_min, int_max, latency, timeout;
@@ -1789,3 +2251,4 @@ static void btu_ble_rc_param_req_evt(uint8_t* p) {
l2cble_process_rc_param_request_evt(handle, int_min, int_max, latency,
timeout);
}
+#endif /* BLE_LLT_INCLUDED */
diff --git a/stack/btu/btu_init.cc b/stack/btu/btu_init.cc
new file mode 100644
index 000000000..e6e5a74ba
--- /dev/null
+++ b/stack/btu/btu_init.cc
@@ -0,0 +1,125 @@
+/******************************************************************************
+ *
+ * Copyright 2000-2012 Broadcom Corporation
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+
+#define LOG_TAG "bt_task"
+
+#include <base/logging.h>
+#include <pthread.h>
+#include <string.h>
+
+#include "bt_target.h"
+#include "btm_int.h"
+#include "btu.h"
+#include "common/message_loop_thread.h"
+#include "device/include/controller.h"
+#include "gatt_api.h"
+#include "gatt_int.h"
+#include "l2c_int.h"
+#include "osi/include/alarm.h"
+#include "osi/include/fixed_queue.h"
+#include "osi/include/log.h"
+#include "sdpint.h"
+#include "smp_int.h"
+
+using bluetooth::common::MessageLoopThread;
+
+MessageLoopThread bt_startup_thread("bt_startup_thread");
+
+void btu_task_start_up(void* context);
+void btu_task_shut_down(void* context);
+
+/*****************************************************************************
+ *
+ * Function btu_init_core
+ *
+ * Description Initialize control block memory for each core component.
+ *
+ *
+ * Returns void
+ *
+ *****************************************************************************/
+void btu_init_core() {
+ /* Initialize the mandatory core stack components */
+ btm_init();
+
+ l2c_init();
+
+ sdp_init();
+
+ gatt_init();
+
+ SMP_Init();
+
+ btm_ble_init();
+}
+
+/*****************************************************************************
+ *
+ * Function btu_free_core
+ *
+ * Description Releases control block memory for each core component.
+ *
+ *
+ * Returns void
+ *
+ *****************************************************************************/
+void btu_free_core() {
+ /* Free the mandatory core stack components */
+ gatt_free();
+
+ l2c_free();
+
+ sdp_free();
+
+ btm_free();
+}
+
+/*****************************************************************************
+ *
+ * Function BTU_StartUp
+ *
+ * Description Initializes the BTU control block.
+ *
+ * NOTE: Must be called before creating any tasks
+ * (RPC, BTU, HCIT, APPL, etc.)
+ *
+ * Returns void
+ *
+ *****************************************************************************/
+void BTU_StartUp() {
+ btu_trace_level = HCI_INITIAL_TRACE_LEVEL;
+ bt_startup_thread.StartUp();
+ if (!bt_startup_thread.EnableRealTimeScheduling()) {
+ LOG(ERROR) << __func__ << ": Unable to set real time scheduling policy for "
+ << bt_startup_thread;
+ BTU_ShutDown();
+ return;
+ }
+ if (!bt_startup_thread.DoInThread(FROM_HERE,
+ base::Bind(btu_task_start_up, nullptr))) {
+ LOG(ERROR) << __func__ << ": Unable to continue start-up on "
+ << bt_startup_thread;
+ BTU_ShutDown();
+ return;
+ }
+}
+
+void BTU_ShutDown() {
+ btu_task_shut_down(nullptr);
+ bt_startup_thread.ShutDown();
+}
diff --git a/stack/btu/btu_task.cc b/stack/btu/btu_task.cc
index 5e83e4d07..06d06d1b4 100644
--- a/stack/btu/btu_task.cc
+++ b/stack/btu/btu_task.cc
@@ -27,12 +27,11 @@
#include "btcore/include/module.h"
#include "bte.h"
#include "btif/include/btif_common.h"
-#include "btm_iso_api.h"
#include "common/message_loop_thread.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
-#include "stack/include/acl_hci_link_interface.h"
+#include "stack/btm/btm_int.h"
#include "stack/include/btu.h"
+#include "stack/l2cap/l2c_int.h"
#include <base/bind.h>
#include <base/logging.h>
@@ -40,26 +39,23 @@
#include <base/threading/thread.h>
using bluetooth::common::MessageLoopThread;
-using bluetooth::hci::IsoManager;
-
-void btm_route_sco_data(BT_HDR* p_msg);
/* Define BTU storage area */
uint8_t btu_trace_level = HCI_INITIAL_TRACE_LEVEL;
-static MessageLoopThread main_thread("bt_main_thread", true);
+static MessageLoopThread main_thread("bt_main_thread");
void btu_hci_msg_process(BT_HDR* p_msg) {
/* Determine the input message type. */
switch (p_msg->event & BT_EVT_MASK) {
case BT_EVT_TO_BTU_HCI_ACL:
- /* All Acl Data goes to ACL */
- acl_rcv_acl_data(p_msg);
+ /* All Acl Data goes to L2CAP */
+ l2c_rcv_acl_data(p_msg);
break;
case BT_EVT_TO_BTU_L2C_SEG_XMIT:
/* L2CAP segment transmit complete */
- acl_link_segments_xmitted(p_msg);
+ l2c_link_segments_xmitted(p_msg);
break;
case BT_EVT_TO_BTU_HCI_SCO:
@@ -76,7 +72,7 @@ void btu_hci_msg_process(BT_HDR* p_msg) {
break;
case BT_EVT_TO_BTU_HCI_ISO:
- IsoManager::GetInstance()->HandleIsoData(p_msg);
+ // TODO: implement handler
osi_free(p_msg);
break;
@@ -88,6 +84,10 @@ void btu_hci_msg_process(BT_HDR* p_msg) {
bluetooth::common::MessageLoopThread* get_main_thread() { return &main_thread; }
+base::MessageLoop* get_main_message_loop() {
+ return main_thread.message_loop();
+}
+
bt_status_t do_in_main_thread(const base::Location& from_here,
base::OnceClosure task) {
if (!main_thread.DoInThread(from_here, std::move(task))) {
@@ -100,22 +100,34 @@ bt_status_t do_in_main_thread(const base::Location& from_here,
bt_status_t do_in_main_thread_delayed(const base::Location& from_here,
base::OnceClosure task,
const base::TimeDelta& delay) {
- if (!main_thread.DoInThreadDelayed(from_here, std::move(task), delay)) {
+ if (!get_main_message_loop()->task_runner()->PostDelayedTask(
+ from_here, std::move(task), delay)) {
LOG(ERROR) << __func__ << ": failed from " << from_here.ToString();
return BT_STATUS_FAIL;
}
return BT_STATUS_SUCCESS;
}
-static void do_post_on_bt_main(BtMainClosure closure) { closure(); }
+void btu_task_start_up(UNUSED_ATTR void* context) {
+ LOG(INFO) << "Bluetooth chip preload is complete";
-void post_on_bt_main(BtMainClosure closure) {
- ASSERT(do_in_main_thread(
- FROM_HERE, base::Bind(do_post_on_bt_main, std::move(closure))) ==
- BT_STATUS_SUCCESS);
-}
+ /* Initialize the mandatory core stack control blocks
+ (BTU, BTM, L2CAP, and SDP)
+ */
+ btu_init_core();
+
+ /* Initialize any optional stack components */
+ BTE_InitStack();
+
+ bta_sys_init();
+
+ /* Initialise platform trace levels at this point as BTE_InitStack() and
+ * bta_sys_init()
+ * reset the control blocks and preset the trace level with
+ * XXX_INITIAL_TRACE_LEVEL
+ */
+ module_init(get_module(BTE_LOGMSG_MODULE));
-void main_thread_start_up() {
main_thread.StartUp();
if (!main_thread.IsRunning()) {
LOG(FATAL) << __func__ << ": unable to start btu message loop thread.";
@@ -123,6 +135,18 @@ void main_thread_start_up() {
if (!main_thread.EnableRealTimeScheduling()) {
LOG(FATAL) << __func__ << ": unable to enable real time scheduling";
}
+ if (do_in_jni_thread(FROM_HERE, base::Bind(btif_init_ok, 0, nullptr)) !=
+ BT_STATUS_SUCCESS) {
+ LOG(FATAL) << __func__ << ": unable to continue starting Bluetooth";
+ }
}
-void main_thread_shut_down() { main_thread.ShutDown(); }
+void btu_task_shut_down(UNUSED_ATTR void* context) {
+ // Shutdown message loop on task completed
+ main_thread.ShutDown();
+
+ module_clean_up(get_module(BTE_LOGMSG_MODULE));
+
+ bta_sys_free();
+ btu_free_core();
+}
diff --git a/stack/crypto_toolbox/crypto_toolbox.h b/stack/crypto_toolbox/crypto_toolbox.h
index 0796833ad..b445fa24e 100644
--- a/stack/crypto_toolbox/crypto_toolbox.h
+++ b/stack/crypto_toolbox/crypto_toolbox.h
@@ -15,7 +15,6 @@
*/
#pragma once
-#include <base/logging.h>
#include "stack/include/bt_types.h"
@@ -62,4 +61,4 @@ inline Octet16 aes_cmac(const Octet16& key, const Octet16& message) {
return aes_cmac(key, message.data(), message.size());
}
-} // namespace crypto_toolbox
+} // namespace crypto_toolbox \ No newline at end of file
diff --git a/stack/eatt/eatt.cc b/stack/eatt/eatt.cc
deleted file mode 100644
index b02331a8a..000000000
--- a/stack/eatt/eatt.cc
+++ /dev/null
@@ -1,207 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com. Represented by EHIMA -
- * www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "eatt_impl.h"
-#include "stack/l2cap/l2c_int.h"
-
-using bluetooth::eatt::eatt_impl;
-
-namespace bluetooth {
-namespace eatt {
-
-struct EattExtension::impl {
- impl() = default;
- ~impl() = default;
-
- void Start() {
- if (eatt_impl_) {
- LOG(ERROR) << "Eatt already started";
- return;
- };
-
- /* Register server for Eatt */
- memset(&reg_info_, 0, sizeof(reg_info_));
- reg_info_.pL2CA_CreditBasedConnectInd_Cb = eatt_connect_ind;
- reg_info_.pL2CA_CreditBasedConnectCfm_Cb = eatt_connect_cfm;
- reg_info_.pL2CA_CreditBasedReconfigCompleted_Cb = eatt_reconfig_completed;
- reg_info_.pL2CA_DisconnectInd_Cb = eatt_disconnect_ind;
- reg_info_.pL2CA_Error_Cb = eatt_error_cb;
- reg_info_.pL2CA_DataInd_Cb = eatt_data_ind;
-
- if (L2CA_RegisterLECoc(BT_PSM_EATT, reg_info_, BTM_SEC_NONE, {}) == 0) {
- LOG(ERROR) << __func__ << " cannot register EATT";
- } else {
- eatt_impl_ = std::make_unique<eatt_impl>();
- }
- }
-
- void Stop() {
- if (!eatt_impl_) {
- LOG(ERROR) << "Eatt not started";
- return;
- }
- eatt_impl_.reset(nullptr);
- L2CA_DeregisterLECoc(BT_PSM_EATT);
- }
-
- bool IsRunning() { return eatt_impl_ ? true : false; }
-
- static eatt_impl* GetImplInstance(void) {
- auto* instance = EattExtension::GetInstance();
- return instance->pimpl_->eatt_impl_.get();
- }
-
- static void eatt_connect_ind(const RawAddress& bda,
- std::vector<uint16_t>& lcids, uint16_t psm,
- uint16_t peer_mtu, uint8_t identifier) {
- auto p_eatt_impl = GetImplInstance();
- if (p_eatt_impl)
- p_eatt_impl->eatt_l2cap_connect_ind(bda, lcids, psm, peer_mtu,
- identifier);
- }
-
- static void eatt_connect_cfm(const RawAddress& bda, uint16_t lcid,
- uint16_t peer_mtu, uint16_t result) {
- auto p_eatt_impl = GetImplInstance();
- if (p_eatt_impl)
- p_eatt_impl->eatt_l2cap_connect_cfm(bda, lcid, peer_mtu, result);
- }
-
- static void eatt_reconfig_completed(const RawAddress& bda, uint16_t lcid,
- bool is_local_cfg,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- auto p_eatt_impl = GetImplInstance();
- if (p_eatt_impl)
- p_eatt_impl->eatt_l2cap_reconfig_completed(bda, lcid, is_local_cfg,
- p_cfg);
- }
-
- static void eatt_error_cb(uint16_t lcid, uint16_t reason) {
- auto p_eatt_impl = GetImplInstance();
- if (p_eatt_impl) p_eatt_impl->eatt_l2cap_error_cb(lcid, reason);
- }
-
- static void eatt_disconnect_ind(uint16_t lcid, bool please_confirm) {
- auto p_eatt_impl = GetImplInstance();
- if (p_eatt_impl)
- p_eatt_impl->eatt_l2cap_disconnect_ind(lcid, please_confirm);
- }
-
- static void eatt_data_ind(uint16_t lcid, BT_HDR* data_p) {
- auto p_eatt_impl = GetImplInstance();
- if (p_eatt_impl) p_eatt_impl->eatt_l2cap_data_ind(lcid, data_p);
- }
-
- std::unique_ptr<eatt_impl> eatt_impl_;
- tL2CAP_APPL_INFO reg_info_;
-};
-
-void EattExtension::AddFromStorage(const RawAddress& bd_addr) {
- eatt_impl* p_eatt_impl = EattExtension::impl::GetImplInstance();
- if (p_eatt_impl) p_eatt_impl->add_from_storage(bd_addr);
-}
-
-EattExtension::EattExtension() : pimpl_(std::make_unique<impl>()) {}
-
-bool EattExtension::IsEattSupportedByPeer(const RawAddress& bd_addr) {
- return pimpl_->eatt_impl_->is_eatt_supported_by_peer(bd_addr);
-}
-
-void EattExtension::Connect(const RawAddress& bd_addr) {
- pimpl_->eatt_impl_->connect(bd_addr);
-}
-
-void EattExtension::Disconnect(const RawAddress& bd_addr) {
- pimpl_->eatt_impl_->disconnect(bd_addr);
-}
-
-void EattExtension::Reconfigure(const RawAddress& bd_addr, uint16_t cid,
- uint16_t mtu) {
- pimpl_->eatt_impl_->reconfigure(bd_addr, cid, mtu);
-}
-void EattExtension::ReconfigureAll(const RawAddress& bd_addr, uint16_t mtu) {
- pimpl_->eatt_impl_->reconfigure_all(bd_addr, mtu);
-}
-
-EattChannel* EattExtension::FindEattChannelByCid(const RawAddress& bd_addr,
- uint16_t cid) {
- return pimpl_->eatt_impl_->find_eatt_channel_by_cid(bd_addr, cid);
-}
-
-EattChannel* EattExtension::FindEattChannelByTransId(const RawAddress& bd_addr,
- uint32_t trans_id) {
- return pimpl_->eatt_impl_->find_eatt_channel_by_transid(bd_addr, trans_id);
-}
-
-bool EattExtension::IsIndicationPending(const RawAddress& bd_addr,
- uint16_t indication_handle) {
- return pimpl_->eatt_impl_->is_indication_pending(bd_addr, indication_handle);
-}
-
-EattChannel* EattExtension::GetChannelAvailableForIndication(
- const RawAddress& bd_addr) {
- return pimpl_->eatt_impl_->get_channel_available_for_indication(bd_addr);
-}
-
-void EattExtension::FreeGattResources(const RawAddress& bd_addr) {
- pimpl_->eatt_impl_->free_gatt_resources(bd_addr);
-}
-
-bool EattExtension::IsOutstandingMsgInSendQueue(const RawAddress& bd_addr) {
- return pimpl_->eatt_impl_->is_outstanding_msg_in_send_queue(bd_addr);
-}
-
-EattChannel* EattExtension::GetChannelWithQueuedData(
- const RawAddress& bd_addr) {
- return pimpl_->eatt_impl_->get_channel_with_queued_data(bd_addr);
-}
-
-EattChannel* EattExtension::GetChannelAvailableForClientRequest(
- const RawAddress& bd_addr) {
- return pimpl_->eatt_impl_->get_channel_available_for_client_request(bd_addr);
-}
-
-/* Start stop GATT indication timer per CID */
-void EattExtension::StartIndicationConfirmationTimer(const RawAddress& bd_addr,
- uint16_t cid) {
- pimpl_->eatt_impl_->start_indication_confirm_timer(bd_addr, cid);
-}
-
-void EattExtension::StopIndicationConfirmationTimer(const RawAddress& bd_addr,
- uint16_t cid) {
- pimpl_->eatt_impl_->stop_indication_confirm_timer(bd_addr, cid);
-}
-
-/* Start stop application indication timeout */
-void EattExtension::StartAppIndicationTimer(const RawAddress& bd_addr,
- uint16_t cid) {
- pimpl_->eatt_impl_->start_app_indication_timer(bd_addr, cid);
-}
-
-void EattExtension::StopAppIndicationTimer(const RawAddress& bd_addr,
- uint16_t cid) {
- pimpl_->eatt_impl_->stop_app_indication_timer(bd_addr, cid);
-}
-
-void EattExtension::Start() { pimpl_->Start(); }
-
-void EattExtension::Stop() { pimpl_->Stop(); }
-
-EattExtension::~EattExtension() = default;
-
-} // namespace eatt
-} // namespace bluetooth
diff --git a/stack/eatt/eatt.h b/stack/eatt/eatt.h
deleted file mode 100644
index 0af2fe3de..000000000
--- a/stack/eatt/eatt.h
+++ /dev/null
@@ -1,284 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com. Represented by EHIMA -
- * www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <queue>
-
-#include "stack/gatt/gatt_int.h"
-
-#define EATT_MIN_MTU_MPS (64)
-#define EATT_DEFAULT_MTU (256)
-
-namespace bluetooth {
-namespace eatt {
-
-/* Enums */
-enum class EattChannelState : uint8_t {
- EATT_CHANNEL_PENDING = 0x00,
- EATT_CHANNEL_OPENED,
- EATT_CHANNEL_RECONFIGURING,
-};
-
-class EattChannel {
- public:
- /* Pointer to EattDevice */
- RawAddress bda_;
- uint16_t cid_;
- uint16_t tx_mtu_;
- uint16_t rx_mtu_;
- EattChannelState state_;
-
- /* Used to keep server commands */
- tGATT_SR_CMD server_outstanding_cmd_;
- /* Used to veryfy indication confirmation*/
- uint16_t indicate_handle_;
- /* local app confirm to indication timer */
- alarm_t* ind_ack_timer_;
- /* indication confirmation timer */
- alarm_t* ind_confirmation_timer_;
- /* GATT client command queue */
- std::queue<tGATT_CMD_Q> cl_cmd_q_;
-
- EattChannel(RawAddress& bda, uint16_t cid, uint16_t tx_mtu, uint16_t rx_mtu)
- : bda_(bda),
- cid_(cid),
- tx_mtu_(tx_mtu),
- rx_mtu_(rx_mtu),
- state_(EattChannelState::EATT_CHANNEL_PENDING),
- indicate_handle_(0),
- ind_ack_timer_(NULL),
- ind_confirmation_timer_(NULL) {}
-
- ~EattChannel() {
- if (ind_ack_timer_ != NULL) {
- alarm_free(ind_ack_timer_);
- }
-
- if (ind_confirmation_timer_ != NULL) {
- alarm_free(ind_confirmation_timer_);
- }
- }
-
- void EattChannelSetState(EattChannelState state) {
- if (state_ == EattChannelState::EATT_CHANNEL_PENDING) {
- if (state == EattChannelState::EATT_CHANNEL_OPENED) {
- cl_cmd_q_ = std::queue<tGATT_CMD_Q>();
- memset(&server_outstanding_cmd_, 0, sizeof(tGATT_SR_CMD));
- char name[64];
- sprintf(name, "eatt_ind_ack_timer_%s_cid_0x%04x",
- bda_.ToString().c_str(), cid_);
- ind_ack_timer_ = alarm_new(name);
-
- sprintf(name, "eatt_ind_conf_timer_%s_cid_0x%04x",
- bda_.ToString().c_str(), cid_);
- ind_confirmation_timer_ = alarm_new(name);
- }
- }
- state_ = state;
- }
- void EattChannelSetTxMTU(uint16_t tx_mtu) { this->tx_mtu_ = tx_mtu; }
-};
-
-/* Interface class */
-class EattExtension {
- public:
- EattExtension();
- virtual ~EattExtension();
-
- static EattExtension* GetInstance() {
- static EattExtension* instance = new EattExtension();
- return instance;
- }
-
- static void AddFromStorage(const RawAddress& bd_addr);
-
- /**
- * Checks if EATT is supported on peer device.
- *
- * @param bd_addr peer device address
- */
- virtual bool IsEattSupportedByPeer(const RawAddress& bd_addr);
-
- /**
- * Connect at maximum 5 EATT channels to peer device.
- *
- * @param bd_addr peer device address
- */
- virtual void Connect(const RawAddress& bd_addr);
-
- /**
- * Disconnect all EATT channels to peer device.
- *
- * @param bd_addr peer device address
- */
- virtual void Disconnect(const RawAddress& bd_addr);
-
- /**
- * Reconfigure EATT channel for give CID
- *
- * @param bd_addr peer device address
- * @param cid channel id
- * @param mtu new maximum transmit unit available of local device
- */
- virtual void Reconfigure(const RawAddress& bd_addr, uint16_t cid,
- uint16_t mtu);
-
- /**
- * Reconfigure all EATT channels to peer device.
- *
- * @param bd_addr peer device address
- * @param mtu new maximum transmit unit available of local device
- */
- virtual void ReconfigureAll(const RawAddress& bd_addr, uint16_t mtu);
-
- /* Below methods required by GATT implementation */
-
- /**
- * Find EATT channel by cid.
- *
- * @param bd_addr peer device address
- * @param cid channel id
- *
- * @return Eatt Channel instance.
- */
- virtual EattChannel* FindEattChannelByCid(const RawAddress& bd_addr,
- uint16_t cid);
-
- /**
- * Find EATT channel by transaction id.
- *
- * @param bd_addr peer device address
- * @param trans_id transaction id
- *
- * @return pointer to EATT channel.
- */
- virtual EattChannel* FindEattChannelByTransId(const RawAddress& bd_addr,
- uint32_t trans_id);
-
- /**
- * Check if EATT channel on given handle is waiting for a indication
- * confirmation
- *
- * @param bd_addr peer device address
- * @param indication_handle handle of the pending indication
- *
- * @return true if confirmation is pending false otherwise
- */
- virtual bool IsIndicationPending(const RawAddress& bd_addr,
- uint16_t indication_handle);
-
- /**
- * Get EATT channel available for indication.
- *
- * @param bd_addr peer device address
- *
- * @return pointer to EATT channel.
- */
- virtual EattChannel* GetChannelAvailableForIndication(
- const RawAddress& bd_addr);
-
- /**
- * Free Resources.
- *
- * (Maybe not needed)
- * @param bd_addr peer device address
- *
- */
- virtual void FreeGattResources(const RawAddress& bd_addr);
-
- /**
- * Check if there is any EATT channels having some msg in its send queue
- *
- * @param bd_addr peer device address
- *
- * @return true when there is at least one EATT channel ready to send
- */
- virtual bool IsOutstandingMsgInSendQueue(const RawAddress& bd_addr);
-
- /**
- * Get EATT channel ready to send.
- *
- * @param bd_addr peer device address
- *
- * @return pointer to EATT channel.
- */
- virtual EattChannel* GetChannelWithQueuedData(const RawAddress& bd_addr);
-
- /**
- * Get EATT channel available to send GATT request.
- *
- * @param bd_addr peer device address
- *
- * @return pointer to EATT channel.
- */
- virtual EattChannel* GetChannelAvailableForClientRequest(
- const RawAddress& bd_addr);
-
- /**
- * Start GATT indication timer per CID.
- *
- * @param bd_addr peer device address
- * @param cid channel id
- */
- virtual void StartIndicationConfirmationTimer(const RawAddress& bd_addr,
- uint16_t cid);
-
- /**
- * Stop GATT indication timer per CID.
- *
- * @param bd_addr peer device address
- * @param cid channel id
- */
- virtual void StopIndicationConfirmationTimer(const RawAddress& bd_addr,
- uint16_t cid);
-
- /**
- * Start application time for incoming indication on given CID
- *
- * @param bd_addr peer device address
- * @param cid channel id
- */
- virtual void StartAppIndicationTimer(const RawAddress& bd_addr, uint16_t cid);
-
- /**
- * Stop application time for incoming indication on given CID
- *
- * @param bd_addr peer device address
- * @param cid channel id
- */
- virtual void StopAppIndicationTimer(const RawAddress& bd_addr, uint16_t cid);
-
- /**
- * Starts the EattExtension module
- */
- void Start();
-
- /**
- * Stops the EattExtension module
- */
- void Stop();
-
- private:
- struct impl;
- std::unique_ptr<impl> pimpl_;
-
- DISALLOW_COPY_AND_ASSIGN(EattExtension);
-};
-
-} // namespace eatt
-} // namespace bluetooth \ No newline at end of file
diff --git a/stack/eatt/eatt_impl.h b/stack/eatt/eatt_impl.h
deleted file mode 100644
index b61454cdf..000000000
--- a/stack/eatt/eatt_impl.h
+++ /dev/null
@@ -1,672 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com. Represented by EHIMA -
- * www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <map>
-#include <queue>
-
-#include "acl_api.h"
-#include "base/bind_helpers.h"
-#include "bt_types.h"
-#include "device/include/controller.h"
-#include "eatt.h"
-#include "l2c_api.h"
-#include "osi/include/alarm.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/gatt/gatt_int.h"
-#include "stack/l2cap/l2c_int.h"
-
-namespace bluetooth {
-namespace eatt {
-
-#define BLE_GATT_SVR_SUP_FEAT_EATT_BITMASK 0x01
-
-class eatt_device {
- public:
- RawAddress bda_;
- uint16_t rx_mtu_;
- uint16_t rx_mps_;
-
- tGATT_TCB* eatt_tcb_;
-
- std::map<uint16_t, std::shared_ptr<EattChannel>> eatt_channels;
-
- eatt_device(const RawAddress& bd_addr, uint16_t mtu, uint16_t mps)
- : rx_mtu_(mtu), rx_mps_(mps), eatt_tcb_(nullptr) {
- bda_ = bd_addr;
- }
-};
-
-struct eatt_impl {
- std::vector<eatt_device> devices_;
- uint16_t psm_;
- uint16_t default_mtu_;
- uint16_t max_mps_;
- tL2CAP_APPL_INFO reg_info_;
-
- eatt_impl() {
- default_mtu_ = EATT_DEFAULT_MTU;
- max_mps_ = EATT_MIN_MTU_MPS;
- psm_ = BT_PSM_EATT;
- };
-
- ~eatt_impl() = default;
-
- eatt_device* find_device_by_cid(uint16_t lcid) {
- /* This works only because Android CIDs are unique across the ACL
- * connections */
- auto iter = find_if(devices_.begin(), devices_.end(),
- [&lcid](const eatt_device& ed) {
- auto it = ed.eatt_channels.find(lcid);
- return it != ed.eatt_channels.end();
- });
-
- return (iter == devices_.end()) ? nullptr : &(*iter);
- }
-
- EattChannel* find_channel_by_cid(uint16_t lcid) {
- eatt_device* eatt_dev = find_device_by_cid(lcid);
- if (!eatt_dev) return nullptr;
-
- auto it = eatt_dev->eatt_channels.find(lcid);
- return (it == eatt_dev->eatt_channels.end()) ? nullptr : it->second.get();
- }
-
- EattChannel* find_channel_by_cid(const RawAddress& bdaddr, uint16_t lcid) {
- eatt_device* eatt_dev = find_device_by_address(bdaddr);
- if (!eatt_dev) return nullptr;
-
- auto it = eatt_dev->eatt_channels.find(lcid);
- return (it == eatt_dev->eatt_channels.end()) ? nullptr : it->second.get();
- }
-
- void remove_channel_by_cid(eatt_device* eatt_dev, uint16_t lcid) {
- eatt_dev->eatt_channels.erase(lcid);
-
- if (eatt_dev->eatt_channels.size() == 0) eatt_dev->eatt_tcb_ = NULL;
- }
-
- void remove_channel_by_cid(uint16_t lcid) {
- eatt_device* eatt_dev = find_device_by_cid(lcid);
- if (!eatt_dev) return;
-
- remove_channel_by_cid(eatt_dev, lcid);
- }
-
- void eatt_l2cap_connect_ind(const RawAddress& bda,
- std::vector<uint16_t>& lcids, uint16_t psm,
- uint16_t peer_mtu, uint8_t identifier) {
- /* The assumption is that L2CAP layer already check parameters etc.
- * Get our capabilities and accept all the channels.
- */
- eatt_device* eatt_dev = this->find_device_by_address(bda);
- if (!eatt_dev) {
- LOG(ERROR) << __func__ << " unknown device: " << bda;
- L2CA_ConnectCreditBasedRsp(bda, identifier, lcids,
- L2CAP_CONN_NO_RESOURCES, NULL);
- return;
- }
-
- uint16_t max_mps = controller_get_interface()->get_acl_data_size_ble();
-
- tL2CAP_LE_CFG_INFO local_coc_cfg = {
- .mtu = eatt_dev->rx_mtu_,
- .mps = eatt_dev->rx_mps_ < max_mps ? eatt_dev->rx_mps_ : max_mps,
- .credits = L2CAP_LE_CREDIT_DEFAULT};
-
- if (!L2CA_ConnectCreditBasedRsp(bda, identifier, lcids, L2CAP_CONN_OK,
- &local_coc_cfg))
- return;
-
- if (!eatt_dev->eatt_tcb_) {
- eatt_dev->eatt_tcb_ =
- gatt_find_tcb_by_addr(eatt_dev->bda_, BT_TRANSPORT_LE);
- CHECK(eatt_dev->eatt_tcb_);
- }
-
- for (uint16_t cid : lcids) {
- EattChannel* channel = find_eatt_channel_by_cid(bda, cid);
- CHECK(!channel);
-
- auto chan = std::make_shared<EattChannel>(eatt_dev->bda_, cid, peer_mtu,
- eatt_dev->rx_mtu_);
- eatt_dev->eatt_channels.insert({cid, chan});
-
- chan->EattChannelSetState(EattChannelState::EATT_CHANNEL_OPENED);
- eatt_dev->eatt_tcb_->eatt++;
-
- LOG(INFO) << __func__ << " Channel connected CID " << loghex(cid);
- }
- }
-
- void eatt_l2cap_connect_cfm(const RawAddress& bda, uint16_t lcid,
- uint16_t peer_mtu, uint16_t result) {
- LOG(INFO) << __func__ << " bda: " << bda << " cid: " << +lcid
- << "peer mtu: " << +peer_mtu << " result " << +result;
-
- eatt_device* eatt_dev = find_device_by_address(bda);
- if (!eatt_dev) {
- LOG(ERROR) << __func__ << " unknown device";
- return;
- }
-
- EattChannel* channel = this->find_channel_by_cid(bda, lcid);
- if (!channel) {
- LOG(ERROR) << __func__ << " unknown cid: " << loghex(lcid);
- return;
- }
-
- if (result != L2CAP_CONN_OK) {
- LOG(ERROR) << __func__
- << " Could not connect CoC result: " << loghex(result);
- remove_channel_by_cid(eatt_dev, lcid);
- return;
- }
-
- channel->EattChannelSetState(EattChannelState::EATT_CHANNEL_OPENED);
- channel->EattChannelSetTxMTU(peer_mtu);
-
- CHECK(eatt_dev->eatt_tcb_);
- CHECK(eatt_dev->bda_ == channel->bda_);
- eatt_dev->eatt_tcb_->eatt++;
-
- LOG(INFO) << __func__ << " Channel connected CID " << loghex(lcid);
- }
-
- void eatt_l2cap_reconfig_completed(const RawAddress& bda, uint16_t lcid,
- bool is_local_cfg,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- LOG(INFO) << __func__ << "lcid: " << loghex(lcid)
- << " local cfg?: " << is_local_cfg;
-
- if (p_cfg->result != L2CAP_CFG_OK) {
- LOG(INFO) << __func__ << " reconfig failed lcid: " << loghex(lcid)
- << " result: " << loghex(p_cfg->result);
- return;
- }
-
- EattChannel* channel = find_channel_by_cid(bda, lcid);
- if (!channel) return;
-
- /* On this layer we don't care about mps as this is handled in L2CAP layer
- */
- if (is_local_cfg)
- channel->rx_mtu_ = p_cfg->mtu;
- else
- channel->tx_mtu_ = p_cfg->mtu;
-
- /* Go back to open state */
- channel->EattChannelSetState(EattChannelState::EATT_CHANNEL_OPENED);
- }
-
- void eatt_l2cap_error_cb(uint16_t lcid, uint16_t reason) {
- LOG(INFO) << __func__ << " cid: " << loghex(lcid) << " reason "
- << loghex(reason);
-
- /*TODO: provide address in the L2CAP callback */
-
- EattChannel* channel = find_channel_by_cid(lcid);
- if (!channel) {
- LOG(ERROR) << __func__ << "Unknown lcid";
- return;
- }
-
- eatt_device* eatt_dev = find_device_by_address(channel->bda_);
-
- switch (channel->state_) {
- case EattChannelState::EATT_CHANNEL_PENDING:
- LOG(ERROR) << "Connecting failed";
- remove_channel_by_cid(eatt_dev, lcid);
- break;
- case EattChannelState::EATT_CHANNEL_RECONFIGURING:
- /* Just go back to open state */
- LOG(ERROR) << "Reconfig failed";
- channel->EattChannelSetState(EattChannelState::EATT_CHANNEL_OPENED);
- break;
- default:
- LOG(ERROR) << __func__ << "Invalid state: "
- << static_cast<uint8_t>(channel->state_);
- break;
- }
- }
-
- void eatt_l2cap_disconnect_ind(uint16_t lcid, bool please_confirm) {
- LOG(INFO) << __func__ << " cid: " << loghex(lcid);
- eatt_device* eatt_dev = find_device_by_cid(lcid);
- if (!eatt_dev) {
- LOG(ERROR) << __func__ << " unknown cid: " << loghex(lcid);
- return;
- }
-
- eatt_dev->eatt_tcb_->eatt--;
- remove_channel_by_cid(eatt_dev, lcid);
- }
-
- void eatt_l2cap_data_ind(uint16_t lcid, BT_HDR* data_p) {
- LOG(INFO) << __func__ << " cid: " << loghex(lcid);
- eatt_device* eatt_dev = find_device_by_cid(lcid);
- if (!eatt_dev) {
- LOG(ERROR) << __func__ << " unknown cid: " << loghex(lcid);
- return;
- }
-
- EattChannel* channel = find_channel_by_cid(eatt_dev->bda_, lcid);
- if (!channel) {
- LOG(ERROR) << __func__ << "Received data on closed channel "
- << loghex(lcid);
- return;
- }
-
- gatt_data_process(*eatt_dev->eatt_tcb_, channel->cid_, data_p);
- osi_free(data_p);
- }
-
- bool is_eatt_supported_by_peer(const RawAddress& bd_addr) {
- return gatt_profile_get_eatt_support(bd_addr);
- }
-
- eatt_device* find_device_by_address(const RawAddress& bd_addr) {
- auto iter = find_if(
- devices_.begin(), devices_.end(),
- [&bd_addr](const eatt_device& ed) { return ed.bda_ == bd_addr; });
-
- return iter == devices_.end() ? nullptr : &(*iter);
- }
-
- eatt_device* add_eatt_device(const RawAddress& bd_addr) {
- devices_.push_back(eatt_device(bd_addr, default_mtu_, max_mps_));
- eatt_device* eatt_dev = &devices_.back();
- return eatt_dev;
- }
-
- void connect_eatt(eatt_device* eatt_dev) {
- /* Let us use maximum possible mps */
- if (eatt_dev->rx_mps_ == EATT_MIN_MTU_MPS)
- eatt_dev->rx_mps_ = controller_get_interface()->get_acl_data_size_ble();
-
- tL2CAP_LE_CFG_INFO local_coc_cfg = {
- .mtu = eatt_dev->rx_mtu_,
- .mps = eatt_dev->rx_mps_,
- .credits = L2CAP_LE_CREDIT_DEFAULT,
- };
-
- /* Warning! CIDs in Android are unique across the ACL connections */
- std::vector<uint16_t> connecting_cids =
- L2CA_ConnectCreditBasedReq(psm_, eatt_dev->bda_, &local_coc_cfg);
-
- if (connecting_cids.size() == 0) {
- LOG(ERROR) << "Unable to get cid";
- return;
- }
-
- LOG(INFO) << __func__
- << "Successfully sent CoC request, number of channel: "
- << +connecting_cids.size();
-
- for (uint16_t cid : connecting_cids) {
- LOG(INFO) << " \t cid: " << loghex(cid);
-
- auto chan = std::make_shared<EattChannel>(eatt_dev->bda_, cid, 0,
- eatt_dev->rx_mtu_);
- eatt_dev->eatt_channels.insert({cid, chan});
- }
-
- if (eatt_dev->eatt_tcb_) {
- LOG(INFO) << __func__ << " has tcb ? " << eatt_dev->eatt_tcb_;
- return;
- }
-
- eatt_dev->eatt_tcb_ =
- gatt_find_tcb_by_addr(eatt_dev->bda_, BT_TRANSPORT_LE);
- CHECK(eatt_dev->eatt_tcb_);
- }
-
- EattChannel* find_eatt_channel_by_cid(const RawAddress& bd_addr,
- uint16_t cid) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
-
- LOG(INFO) << __func__ << bd_addr << " " << +cid;
-
- if (!eatt_dev) return nullptr;
-
- auto iter = find_if(
- eatt_dev->eatt_channels.begin(), eatt_dev->eatt_channels.end(),
- [&cid](const std::pair<uint16_t, std::shared_ptr<EattChannel>>& el) {
- return el.first == cid;
- });
-
- return iter == eatt_dev->eatt_channels.end() ? nullptr : iter->second.get();
- }
-
- EattChannel* find_eatt_channel_by_transid(const RawAddress& bd_addr,
- uint32_t trans_id) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
- if (!eatt_dev) return nullptr;
-
- auto iter = find_if(
- eatt_dev->eatt_channels.begin(), eatt_dev->eatt_channels.end(),
- [&trans_id](
- const std::pair<uint16_t, std::shared_ptr<EattChannel>>& el) {
- return el.second->server_outstanding_cmd_.trans_id == trans_id;
- });
-
- return iter == eatt_dev->eatt_channels.end() ? nullptr : iter->second.get();
- }
-
- bool is_indication_pending(const RawAddress& bd_addr,
- uint16_t indication_handle) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
- if (!eatt_dev) return false;
-
- auto iter = find_if(
- eatt_dev->eatt_channels.begin(), eatt_dev->eatt_channels.end(),
- [&indication_handle](
- const std::pair<uint16_t, std::shared_ptr<EattChannel>>& el) {
- return el.second->indicate_handle_ == indication_handle;
- });
-
- return (iter != eatt_dev->eatt_channels.end());
- };
-
- EattChannel* get_channel_available_for_indication(const RawAddress& bd_addr) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
- auto iter = find_if(
- eatt_dev->eatt_channels.begin(), eatt_dev->eatt_channels.end(),
- [](const std::pair<uint16_t, std::shared_ptr<EattChannel>>& el) {
- return !GATT_HANDLE_IS_VALID(el.second->indicate_handle_);
- });
-
- return (iter == eatt_dev->eatt_channels.end()) ? nullptr
- : iter->second.get();
- };
-
- EattChannel* get_channel_available_for_client_request(
- const RawAddress& bd_addr) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
- if (!eatt_dev) return nullptr;
-
- auto iter = find_if(
- eatt_dev->eatt_channels.begin(), eatt_dev->eatt_channels.end(),
- [](const std::pair<uint16_t, std::shared_ptr<EattChannel>>& el) {
- return el.second->cl_cmd_q_.empty();
- });
-
- return (iter == eatt_dev->eatt_channels.end()) ? nullptr
- : iter->second.get();
- }
-
- void free_gatt_resources(const RawAddress& bd_addr) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
- if (!eatt_dev) return;
-
- auto iter = eatt_dev->eatt_channels.begin();
- while (iter != eatt_dev->eatt_channels.end()) {
- EattChannel* channel = iter->second.get();
-
- fixed_queue_free(channel->server_outstanding_cmd_.multi_rsp_q, NULL);
- channel->server_outstanding_cmd_.multi_rsp_q = NULL;
- }
- }
-
- bool is_outstanding_msg_in_send_queue(const RawAddress& bd_addr) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
- if (!eatt_dev) return false;
-
- auto iter = find_if(
- eatt_dev->eatt_channels.begin(), eatt_dev->eatt_channels.end(),
- [](const std::pair<uint16_t, std::shared_ptr<EattChannel>>& el) {
- return !el.second->cl_cmd_q_.empty();
- });
- return (iter != eatt_dev->eatt_channels.end());
- }
-
- EattChannel* get_channel_with_queued_data(const RawAddress& bd_addr) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
- if (!eatt_dev) return nullptr;
-
- auto iter = find_if(
- eatt_dev->eatt_channels.begin(), eatt_dev->eatt_channels.end(),
- [](const std::pair<uint16_t, std::shared_ptr<EattChannel>>& el) {
- return !el.second->cl_cmd_q_.empty();
- });
- return (iter == eatt_dev->eatt_channels.end()) ? nullptr
- : iter->second.get();
- }
-
- static void eatt_ind_ack_timeout(void* data) {
- EattChannel* channel = (EattChannel*)data;
- tGATT_TCB* p_tcb = gatt_find_tcb_by_addr(channel->bda_, BT_TRANSPORT_LE);
-
- LOG(WARNING) << __func__ << ": send ack now";
- attp_send_cl_confirmation_msg(*p_tcb, channel->cid_);
- }
-
- static void eatt_ind_confirmation_timeout(void* data) {
- EattChannel* channel = (EattChannel*)data;
- tGATT_TCB* p_tcb = gatt_find_tcb_by_addr(channel->bda_, BT_TRANSPORT_LE);
-
- LOG(WARNING) << __func__ << " disconnecting...";
- gatt_disconnect(p_tcb);
- }
-
- void start_indication_confirm_timer(const RawAddress& bd_addr, uint16_t cid) {
- EattChannel* channel = find_eatt_channel_by_cid(bd_addr, cid);
- if (!channel) {
- LOG(ERROR) << __func__ << "Unknown cid: " << loghex(cid) << " or device "
- << bd_addr;
- return;
- }
-
- alarm_set_on_mloop(channel->ind_confirmation_timer_,
- GATT_WAIT_FOR_RSP_TIMEOUT_MS,
- eatt_ind_confirmation_timeout, channel);
- }
-
- void stop_indication_confirm_timer(const RawAddress& bd_addr, uint16_t cid) {
- EattChannel* channel = find_eatt_channel_by_cid(bd_addr, cid);
- if (!channel) {
- LOG(ERROR) << __func__ << "Unknown cid: " << loghex(cid) << " or device "
- << bd_addr;
- return;
- }
-
- alarm_cancel(channel->ind_confirmation_timer_);
- }
-
- void start_app_indication_timer(const RawAddress& bd_addr, uint16_t cid) {
- EattChannel* channel = find_eatt_channel_by_cid(bd_addr, cid);
- if (!channel) {
- LOG(ERROR) << __func__ << "Unknown cid: " << loghex(cid) << " or device "
- << bd_addr;
- return;
- }
-
- alarm_set_on_mloop(channel->ind_ack_timer_, GATT_WAIT_FOR_RSP_TIMEOUT_MS,
- eatt_ind_ack_timeout, channel);
- }
-
- void stop_app_indication_timer(const RawAddress& bd_addr, uint16_t cid) {
- EattChannel* channel = find_eatt_channel_by_cid(bd_addr, cid);
- if (!channel) {
- LOG(ERROR) << __func__ << "Unknown cid: " << loghex(cid) << " or device "
- << bd_addr;
- return;
- }
-
- alarm_cancel(channel->ind_ack_timer_);
- }
-
- void reconfigure(const RawAddress& bd_addr, uint16_t cid, uint16_t new_mtu) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
- if (!eatt_dev) {
- LOG(ERROR) << __func__ << "Unknown device " << bd_addr;
- return;
- }
-
- EattChannel* channel = find_eatt_channel_by_cid(bd_addr, cid);
- if (!channel) {
- LOG(ERROR) << __func__ << "Unknown cid: " << loghex(cid) << " or device "
- << bd_addr;
- return;
- }
-
- if (new_mtu <= channel->rx_mtu_) {
- LOG(ERROR) << __func__ << "Invalid mtu: " << loghex(new_mtu);
- return;
- }
-
- std::vector<uint16_t> cids = {cid};
-
- tL2CAP_LE_CFG_INFO cfg = {.mps = eatt_dev->rx_mps_, .mtu = new_mtu};
-
- if (!L2CA_ReconfigCreditBasedConnsReq(eatt_dev->bda_, cids, &cfg))
- LOG(ERROR) << __func__ << "Could not start reconfig cid: " << loghex(cid)
- << " or device " << bd_addr;
- }
-
- void reconfigure_all(const RawAddress& bd_addr, uint16_t new_mtu) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
- if (!eatt_dev) {
- LOG(ERROR) << __func__ << "Unknown device " << bd_addr;
- return;
- }
-
- uint8_t num_of_channels = eatt_dev->eatt_channels.size();
- if (num_of_channels == 0) {
- LOG(ERROR) << __func__ << "No channels for device " << bd_addr;
- return;
- }
-
- std::vector<uint16_t> cids;
-
- auto iter = eatt_dev->eatt_channels.begin();
- while (iter != eatt_dev->eatt_channels.end()) {
- uint16_t cid = iter->first;
- cids.push_back(cid);
- iter++;
- }
-
- if (new_mtu <= EATT_MIN_MTU_MPS) {
- LOG(ERROR) << __func__ << "Invalid mtu: " << loghex(new_mtu);
- return;
- }
-
- tL2CAP_LE_CFG_INFO cfg = {.mps = eatt_dev->rx_mps_, .mtu = new_mtu};
-
- if (!L2CA_ReconfigCreditBasedConnsReq(eatt_dev->bda_, cids, &cfg))
- LOG(ERROR) << __func__ << "Could not start reconfig for device "
- << bd_addr;
- }
-
- void supported_features_cb(uint8_t role, const RawAddress& bd_addr,
- uint8_t features) {
- bool is_eatt_supported = features & BLE_GATT_SVR_SUP_FEAT_EATT_BITMASK;
-
- LOG(INFO) << __func__ << " " << bd_addr
- << " is_eatt_supported = " << int(is_eatt_supported);
- if (!is_eatt_supported) return;
-
- eatt_device* eatt_dev = add_eatt_device(bd_addr);
-
- if (role != HCI_ROLE_CENTRAL) {
- /* TODO For now do nothing, we could run a timer here and start EATT if
- * not started by central */
- LOG(INFO)
- << " EATT Should be connected by the central. Let's wait for it.";
- return;
- }
-
- connect_eatt(eatt_dev);
- }
-
- void disconnect_channel(uint16_t cid) { L2CA_DisconnectReq(cid); }
-
- void disconnect(const RawAddress& bd_addr) {
- LOG(INFO) << __func__ << " " << bd_addr;
-
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
- if (!eatt_dev) {
- LOG(WARNING) << __func__ << " no eatt device found";
- return;
- }
-
- if (!eatt_dev->eatt_tcb_) {
- LOG_ASSERT(eatt_dev->eatt_channels.size() == 0);
- LOG(WARNING) << __func__ << " no eatt channels found";
- return;
- }
-
- auto iter = eatt_dev->eatt_channels.begin();
- while (iter != eatt_dev->eatt_channels.end()) {
- uint16_t cid = iter->first;
- disconnect_channel(cid);
- /* When initiating disconnection, stack will not notify us that it is
- * done. We need to assume success
- */
- iter = eatt_dev->eatt_channels.erase(iter);
- }
- eatt_dev->eatt_tcb_->eatt = 0;
- eatt_dev->eatt_tcb_ = nullptr;
- }
-
- void connect(const RawAddress& bd_addr) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
-
- uint8_t role = L2CA_GetBleConnRole(bd_addr);
- if (role == HCI_ROLE_UNKNOWN) {
- LOG(ERROR) << __func__ << "Could not get device role" << bd_addr;
- return;
- }
-
- LOG(INFO) << __func__ << " device " << bd_addr << " role"
- << (role == HCI_ROLE_CENTRAL ? "central" : "peripheral");
-
- if (eatt_dev) {
- /* We are reconnecting device we know that support EATT.
- * Just connect CoC
- */
- LOG(INFO) << __func__ << " Known device, connect eCoC";
-
- if (role != HCI_ROLE_CENTRAL) {
- LOG(INFO)
- << " EATT Should be connected by the central. Let's wait for it.";
- return;
- }
-
- connect_eatt(eatt_dev);
- return;
- }
-
- /* For new device, first read GATT server supported features. */
- if (gatt_cl_read_sr_supp_feat_req(
- bd_addr, base::BindOnce(&eatt_impl::supported_features_cb,
- base::Unretained(this), role)) == false) {
- LOG(INFO) << __func__ << "Eatt is not supported. Checked for device "
- << bd_addr;
- }
- }
-
- void add_from_storage(const RawAddress& bd_addr) {
- eatt_device* eatt_dev = find_device_by_address(bd_addr);
-
- LOG(INFO) << __func__ << ", restoring: " << bd_addr;
-
- if (!eatt_dev) add_eatt_device(bd_addr);
- }
-};
-
-} // namespace eatt
-} // namespace bluetooth
diff --git a/stack/gap/gap_ble.cc b/stack/gap/gap_ble.cc
index f6b047c0d..e71238f36 100644
--- a/stack/gap/gap_ble.cc
+++ b/stack/gap/gap_ble.cc
@@ -24,9 +24,6 @@
#include <queue>
#include "gap_api.h"
#include "gatt_api.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "types/bt_transport.h"
using base::StringPrintf;
using bluetooth::Uuid;
@@ -56,21 +53,19 @@ typedef struct {
void server_attr_request_cback(uint16_t, uint32_t, tGATTS_REQ_TYPE,
tGATTS_DATA*);
void client_connect_cback(tGATT_IF, const RawAddress&, uint16_t, bool,
- tGATT_DISCONN_REASON, tBT_TRANSPORT);
+ tGATT_DISCONN_REASON, tGATT_TRANSPORT);
void client_cmpl_cback(uint16_t, tGATTC_OPTYPE, tGATT_STATUS,
tGATT_CL_COMPLETE*);
-tGATT_CBACK gap_cback = {
- .p_conn_cb = client_connect_cback,
- .p_cmpl_cb = client_cmpl_cback,
- .p_disc_res_cb = nullptr,
- .p_disc_cmpl_cb = nullptr,
- .p_req_cb = server_attr_request_cback,
- .p_enc_cmpl_cb = nullptr,
- .p_congestion_cb = nullptr,
- .p_phy_update_cb = nullptr,
- .p_conn_update_cb = nullptr,
-};
+tGATT_CBACK gap_cback = {client_connect_cback,
+ client_cmpl_cback,
+ NULL,
+ NULL,
+ server_attr_request_cback,
+ NULL,
+ NULL,
+ NULL,
+ NULL};
constexpr int GAP_CHAR_DEV_NAME_SIZE = BD_NAME_LEN;
constexpr int GAP_MAX_CHAR_NUM = 4;
@@ -185,7 +180,7 @@ tGATT_STATUS proc_read(tGATTS_REQ_TYPE, tGATT_READ_REQ* p_data,
}
/** GAP ATT server process a write request */
-tGATT_STATUS proc_write_req(tGATTS_REQ_TYPE, tGATT_WRITE_REQ* p_data) {
+uint8_t proc_write_req(tGATTS_REQ_TYPE, tGATT_WRITE_REQ* p_data) {
for (const auto& db_addr : gatt_attr)
if (p_data->handle == db_addr.handle) return GATT_WRITE_NOT_PERMIT;
@@ -195,7 +190,7 @@ tGATT_STATUS proc_write_req(tGATTS_REQ_TYPE, tGATT_WRITE_REQ* p_data) {
/** GAP ATT server attribute access request callback */
void server_attr_request_cback(uint16_t conn_id, uint32_t trans_id,
tGATTS_REQ_TYPE type, tGATTS_DATA* p_data) {
- tGATT_STATUS status = GATT_INVALID_PDU;
+ uint8_t status = GATT_INVALID_PDU;
bool ignore = false;
DVLOG(1) << StringPrintf("%s: recv type (0x%02x)", __func__, type);
@@ -291,22 +286,16 @@ void cl_op_cmpl(tGAP_CLCB& clcb, bool status, uint16_t len, uint8_t* p_name) {
/** Client connection callback */
void client_connect_cback(tGATT_IF, const RawAddress& bda, uint16_t conn_id,
bool connected, tGATT_DISCONN_REASON reason,
- tBT_TRANSPORT) {
+ tGATT_TRANSPORT) {
tGAP_CLCB* p_clcb = find_clcb_by_bd_addr(bda);
- if (p_clcb == NULL) {
- LOG_INFO("No active GAP service found for peer:%s callback:%s",
- PRIVATE_ADDRESS(bda), (connected) ? "Connected" : "Disconnected");
- return;
- }
+ if (p_clcb == NULL) return;
if (connected) {
- LOG_DEBUG("Connected GAP to remote device");
p_clcb->conn_id = conn_id;
p_clcb->connected = true;
/* start operation is pending */
send_cl_read_request(*p_clcb);
} else {
- LOG_WARN("Disconnected GAP from remote device");
p_clcb->connected = false;
cl_op_cmpl(*p_clcb, false, 0, NULL);
/* clean up clcb */
@@ -412,7 +401,7 @@ void gap_attr_db_init(void) {
Uuid app_uuid = Uuid::From128BitBE(tmp);
gatt_attr.fill({});
- gatt_if = GATT_Register(app_uuid, "Gap", &gap_cback, false);
+ gatt_if = GATT_Register(app_uuid, &gap_cback);
GATT_StartIf(gatt_if);
@@ -547,6 +536,21 @@ bool GAP_BleReadPeerDevName(const RawAddress& peer_bda,
/*******************************************************************************
*
+ * Function GAP_BleReadPeerAddressResolutionCap
+ *
+ * Description Start a process to read peer address resolution capability
+ *
+ * Returns true if request accepted
+ *
+ ******************************************************************************/
+bool GAP_BleReadPeerAddressResolutionCap(const RawAddress& peer_bda,
+ tGAP_BLE_CMPL_CBACK* p_cback) {
+ return accept_client_operation(peer_bda, GATT_UUID_GAP_CENTRAL_ADDR_RESOL,
+ p_cback);
+}
+
+/*******************************************************************************
+ *
* Function GAP_BleCancelReadPeerDevName
*
* Description Cancel reading a peripheral's device name.
diff --git a/stack/gap/gap_conn.cc b/stack/gap/gap_conn.cc
index 0f0026f71..1285bc5ec 100644
--- a/stack/gap/gap_conn.cc
+++ b/stack/gap/gap_conn.cc
@@ -19,13 +19,15 @@
#include <base/strings/stringprintf.h>
#include <string.h>
#include "bt_target.h"
+#include "bt_utils.h"
+#include "btm_int.h"
+#include "btu.h"
#include "device/include/controller.h"
#include "gap_api.h"
-#include "l2c_api.h"
+#include "l2c_int.h"
#include "l2cdefs.h"
#include "osi/include/fixed_queue.h"
#include "osi/include/mutex.h"
-#include "stack/btm/btm_sec.h"
using base::StringPrintf;
@@ -35,6 +37,7 @@ typedef struct {
#define GAP_CCB_STATE_LISTENING 1
#define GAP_CCB_STATE_CONN_SETUP 2
#define GAP_CCB_STATE_CFG_SETUP 3
+#define GAP_CCB_STATE_WAIT_SEC 4
#define GAP_CCB_STATE_CONNECTED 5
uint8_t con_state;
@@ -76,7 +79,7 @@ typedef struct {
namespace {
tGAP_CONN conn;
-} // namespace
+}
/******************************************************************************/
/* L O C A L F U N C T I O N P R O T O T Y P E S */
@@ -85,13 +88,15 @@ static void gap_connect_ind(const RawAddress& bd_addr, uint16_t l2cap_cid,
uint16_t psm, uint8_t l2cap_id);
static void gap_connect_cfm(uint16_t l2cap_cid, uint16_t result);
static void gap_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg);
-static void gap_config_cfm(uint16_t l2cap_cid, uint16_t result,
- tL2CAP_CFG_INFO* p_cfg);
+static void gap_config_cfm(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg);
static void gap_disconnect_ind(uint16_t l2cap_cid, bool ack_needed);
static void gap_data_ind(uint16_t l2cap_cid, BT_HDR* p_msg);
static void gap_congestion_ind(uint16_t lcid, bool is_congested);
static void gap_tx_complete_ind(uint16_t l2cap_cid, uint16_t sdu_sent);
-static void gap_on_l2cap_error(uint16_t l2cap_cid, uint16_t result);
+static void gap_credits_received_cb(uint16_t l2cap_cid,
+ uint16_t credits_received,
+ uint16_t credit_count);
+
static tGAP_CCB* gap_find_ccb_by_cid(uint16_t cid);
static tGAP_CCB* gap_find_ccb_by_handle(uint16_t handle);
static tGAP_CCB* gap_allocate_ccb(void);
@@ -112,13 +117,16 @@ void gap_conn_init(void) {
memset(&conn, 0, sizeof(tGAP_CONN));
conn.reg_info.pL2CA_ConnectInd_Cb = gap_connect_ind;
conn.reg_info.pL2CA_ConnectCfm_Cb = gap_connect_cfm;
+ conn.reg_info.pL2CA_ConnectPnd_Cb = NULL;
conn.reg_info.pL2CA_ConfigInd_Cb = gap_config_ind;
conn.reg_info.pL2CA_ConfigCfm_Cb = gap_config_cfm;
conn.reg_info.pL2CA_DisconnectInd_Cb = gap_disconnect_ind;
+ conn.reg_info.pL2CA_DisconnectCfm_Cb = NULL;
+ conn.reg_info.pL2CA_QoSViolationInd_Cb = NULL;
conn.reg_info.pL2CA_DataInd_Cb = gap_data_ind;
conn.reg_info.pL2CA_CongestionStatus_Cb = gap_congestion_ind;
conn.reg_info.pL2CA_TxComplete_Cb = gap_tx_complete_ind;
- conn.reg_info.pL2CA_Error_Cb = gap_on_l2cap_error;
+ conn.reg_info.pL2CA_CreditsReceived_Cb = gap_credits_received_cb;
}
/*******************************************************************************
@@ -161,7 +169,8 @@ uint16_t GAP_ConnOpen(const char* p_serv_name, uint8_t service_id,
bool is_server, const RawAddress* p_rem_bda, uint16_t psm,
uint16_t le_mps, tL2CAP_CFG_INFO* p_cfg,
tL2CAP_ERTM_INFO* ertm_info, uint16_t security,
- tGAP_CONN_CALLBACK* p_cb, tBT_TRANSPORT transport) {
+ uint8_t chan_mode_mask, tGAP_CONN_CALLBACK* p_cb,
+ tBT_TRANSPORT transport) {
tGAP_CCB* p_ccb;
uint16_t cid;
@@ -185,7 +194,6 @@ uint16_t GAP_ConnOpen(const char* p_serv_name, uint8_t service_id,
p_ccb->rem_dev_address = *p_rem_bda;
} else if (!is_server) {
/* remore addr is not specified and is not a server -> bad */
- gap_release_ccb(p_ccb);
return (GAP_INVALID_HANDLE);
}
@@ -229,6 +237,10 @@ uint16_t GAP_ConnOpen(const char* p_serv_name, uint8_t service_id,
if (p_ccb->cfg.fcr_present) {
if (ertm_info == NULL) {
p_ccb->ertm_info.preferred_mode = p_ccb->cfg.fcr.mode;
+ p_ccb->ertm_info.user_rx_buf_size = GAP_DATA_BUF_SIZE;
+ p_ccb->ertm_info.user_tx_buf_size = GAP_DATA_BUF_SIZE;
+ p_ccb->ertm_info.fcr_rx_buf_size = L2CAP_INVALID_ERM_BUF_SIZE;
+ p_ccb->ertm_info.fcr_tx_buf_size = L2CAP_INVALID_ERM_BUF_SIZE;
} else {
p_ccb->ertm_info = *ertm_info;
}
@@ -236,9 +248,8 @@ uint16_t GAP_ConnOpen(const char* p_serv_name, uint8_t service_id,
/* Register the PSM with L2CAP */
if (transport == BT_TRANSPORT_BR_EDR) {
- p_ccb->psm =
- L2CA_Register2(psm, conn.reg_info, false /* enable_snoop */,
- &p_ccb->ertm_info, L2CAP_SDU_LENGTH_MAX, 0, security);
+ p_ccb->psm = L2CA_Register(psm, &conn.reg_info, false /* enable_snoop */,
+ &p_ccb->ertm_info);
if (p_ccb->psm == 0) {
LOG(ERROR) << StringPrintf("%s: Failure registering PSM 0x%04x", __func__,
psm);
@@ -248,8 +259,7 @@ uint16_t GAP_ConnOpen(const char* p_serv_name, uint8_t service_id,
}
if (transport == BT_TRANSPORT_LE) {
- p_ccb->psm =
- L2CA_RegisterLECoc(psm, conn.reg_info, security, p_ccb->local_coc_cfg);
+ p_ccb->psm = L2CA_RegisterLECoc(psm, (tL2CAP_APPL_INFO*)&conn.reg_info);
if (p_ccb->psm == 0) {
LOG(ERROR) << StringPrintf("%s: Failure registering PSM 0x%04x", __func__,
psm);
@@ -258,6 +268,20 @@ uint16_t GAP_ConnOpen(const char* p_serv_name, uint8_t service_id,
}
}
+ /* Register with Security Manager for the specific security level */
+ if (!BTM_SetSecurityLevel((uint8_t)!is_server, p_serv_name, p_ccb->service_id,
+ security, p_ccb->psm, 0, 0)) {
+ LOG(ERROR) << "GAP_CONN - Security Error";
+ gap_release_ccb(p_ccb);
+ return (GAP_INVALID_HANDLE);
+ }
+
+ /* optional FCR channel modes */
+ if (ertm_info != NULL) {
+ p_ccb->ertm_info.allowed_modes =
+ (chan_mode_mask) ? chan_mode_mask : (uint8_t)L2CAP_FCR_CHAN_OPT_BASIC;
+ }
+
if (is_server) {
p_ccb->con_flags |=
GAP_CCB_FLAGS_SEC_DONE; /* assume btm/l2cap would handle it */
@@ -272,12 +296,13 @@ uint16_t GAP_ConnOpen(const char* p_serv_name, uint8_t service_id,
p_ccb->con_state = GAP_CCB_STATE_CONN_SETUP;
/* mark security done flag, when security is not required */
- if ((security & (BTM_SEC_OUT_AUTHENTICATE | BTM_SEC_OUT_ENCRYPT)) == 0)
+ if ((security & (BTM_SEC_OUT_AUTHORIZE | BTM_SEC_OUT_AUTHENTICATE |
+ BTM_SEC_OUT_ENCRYPT)) == 0)
p_ccb->con_flags |= GAP_CCB_FLAGS_SEC_DONE;
/* Check if L2CAP started the connection process */
if (p_rem_bda && (transport == BT_TRANSPORT_BR_EDR)) {
- cid = L2CA_ConnectReq2(p_ccb->psm, *p_rem_bda, security);
+ cid = L2CA_ErtmConnectReq(p_ccb->psm, *p_rem_bda, &p_ccb->ertm_info);
if (cid != 0) {
p_ccb->connection_id = cid;
return (p_ccb->gap_handle);
@@ -285,8 +310,7 @@ uint16_t GAP_ConnOpen(const char* p_serv_name, uint8_t service_id,
}
if (p_rem_bda && (transport == BT_TRANSPORT_LE)) {
- cid = L2CA_ConnectLECocReq(p_ccb->psm, *p_rem_bda, &p_ccb->local_coc_cfg,
- security);
+ cid = L2CA_ConnectLECocReq(p_ccb->psm, *p_rem_bda, &p_ccb->local_coc_cfg);
if (cid != 0) {
p_ccb->connection_id = cid;
return (p_ccb->gap_handle);
@@ -317,13 +341,8 @@ uint16_t GAP_ConnClose(uint16_t gap_handle) {
if (p_ccb) {
/* Check if we have a connection ID */
- if (p_ccb->con_state != GAP_CCB_STATE_LISTENING) {
- if (p_ccb->transport == BT_TRANSPORT_LE) {
- L2CA_DisconnectLECocReq(p_ccb->connection_id);
- } else {
- L2CA_DisconnectReq(p_ccb->connection_id);
- }
- }
+ if (p_ccb->con_state != GAP_CCB_STATE_LISTENING)
+ L2CA_DisconnectReq(p_ccb->connection_id);
gap_release_ccb(p_ccb);
@@ -427,6 +446,40 @@ int GAP_GetRxQueueCnt(uint16_t handle, uint32_t* p_rx_queue_count) {
return (rc);
}
+/*******************************************************************************
+ *
+ * Function GAP_ConnBTRead
+ *
+ * Description Bluetooth-aware applications will call this function after
+ * receiving GAP_EVT_RXDATA event.
+ *
+ * Parameters: handle - Handle of the connection returned in the Open
+ * pp_buf - pointer to address of buffer with data,
+ *
+ * Returns BT_PASS - data read
+ * GAP_ERR_BAD_HANDLE - invalid handle
+ * GAP_NO_DATA_AVAIL - no data available
+ *
+ ******************************************************************************/
+uint16_t GAP_ConnBTRead(uint16_t gap_handle, BT_HDR** pp_buf) {
+ tGAP_CCB* p_ccb = gap_find_ccb_by_handle(gap_handle);
+ BT_HDR* p_buf;
+
+ if (!p_ccb) return (GAP_ERR_BAD_HANDLE);
+
+ p_buf = (BT_HDR*)fixed_queue_try_dequeue(p_ccb->rx_queue);
+
+ if (p_buf) {
+ *pp_buf = p_buf;
+
+ p_ccb->rx_queue_size -= p_buf->len;
+ return (BT_PASS);
+ } else {
+ *pp_buf = NULL;
+ return (GAP_NO_DATA_AVAIL);
+ }
+}
+
/* Try to write the queued data to l2ca. Return true on success, or if queue is
* congested. False if error occured when writing. */
static bool gap_try_write_queued_data(tGAP_CCB* p_ccb) {
@@ -435,12 +488,7 @@ static bool gap_try_write_queued_data(tGAP_CCB* p_ccb) {
/* Send the buffer through L2CAP */
BT_HDR* p_buf;
while ((p_buf = (BT_HDR*)fixed_queue_try_dequeue(p_ccb->tx_queue)) != NULL) {
- uint8_t status;
- if (p_ccb->transport == BT_TRANSPORT_LE) {
- status = L2CA_LECocDataWrite(p_ccb->connection_id, p_buf);
- } else {
- status = L2CA_DataWrite(p_ccb->connection_id, p_buf);
- }
+ uint8_t status = L2CA_DataWrite(p_ccb->connection_id, p_buf);
if (status == L2CAP_DW_CONGESTED) {
p_ccb->is_congested = true;
@@ -497,6 +545,67 @@ uint16_t GAP_ConnWriteData(uint16_t gap_handle, BT_HDR* msg) {
/*******************************************************************************
*
+ * Function GAP_ConnReconfig
+ *
+ * Description Applications can call this function to reconfigure the
+ * connection.
+ *
+ * Parameters: handle - Handle of the connection
+ * p_cfg - Pointer to new configuration
+ *
+ * Returns BT_PASS - config process started
+ * GAP_ERR_BAD_HANDLE - invalid handle
+ *
+ ******************************************************************************/
+uint16_t GAP_ConnReconfig(uint16_t gap_handle, tL2CAP_CFG_INFO* p_cfg) {
+ tGAP_CCB* p_ccb = gap_find_ccb_by_handle(gap_handle);
+
+ if (!p_ccb) return (GAP_ERR_BAD_HANDLE);
+
+ p_ccb->cfg = *p_cfg;
+
+ if (p_ccb->con_state == GAP_CCB_STATE_CONNECTED)
+ L2CA_ConfigReq(p_ccb->connection_id, p_cfg);
+
+ return (BT_PASS);
+}
+
+/*******************************************************************************
+ *
+ * Function GAP_ConnSetIdleTimeout
+ *
+ * Description Higher layers call this function to set the idle timeout for
+ * a connection, or for all future connections. The "idle
+ * timeout" is the amount of time that a connection can remain
+ * up with no L2CAP channels on it. A timeout of zero means
+ * that the connection will be torn down immediately when the
+ * last channel is removed. A timeout of 0xFFFF means no
+ * timeout. Values are in seconds.
+ *
+ * Parameters: handle - Handle of the connection
+ * timeout - in secs
+ * 0 = immediate disconnect when last channel is
+ * removed
+ * 0xFFFF = no idle timeout
+ *
+ * Returns BT_PASS - config process started
+ * GAP_ERR_BAD_HANDLE - invalid handle
+ *
+ ******************************************************************************/
+uint16_t GAP_ConnSetIdleTimeout(uint16_t gap_handle, uint16_t timeout) {
+ tGAP_CCB* p_ccb;
+
+ p_ccb = gap_find_ccb_by_handle(gap_handle);
+ if (p_ccb == NULL) return (GAP_ERR_BAD_HANDLE);
+
+ if (L2CA_SetIdleTimeout(p_ccb->connection_id, timeout, false))
+ return (BT_PASS);
+ else
+ return (GAP_ERR_BAD_HANDLE);
+}
+
+/*******************************************************************************
+ *
* Function GAP_ConnGetRemoteAddr
*
* Description This function is called to get the remote BD address
@@ -584,6 +693,16 @@ void gap_tx_complete_ind(uint16_t l2cap_cid, uint16_t sdu_sent) {
}
}
+void gap_credits_received_cb(uint16_t l2cap_cid, uint16_t credits_received,
+ uint16_t credit_count) {
+ tGAP_CCB* p_ccb = gap_find_ccb_by_cid(l2cap_cid);
+ if (!p_ccb) return;
+
+ tGAP_CB_DATA data{.coc_credits = {.credits_received = credits_received,
+ .credit_count = credit_count}};
+ p_ccb->p_callback(p_ccb->gap_handle, GAP_EVT_LE_COC_CREDITS, &data);
+}
+
/*******************************************************************************
*
* Function gap_connect_ind
@@ -614,11 +733,7 @@ static void gap_connect_ind(const RawAddress& bd_addr, uint16_t l2cap_cid,
LOG(WARNING) << "*******";
/* Disconnect because it is an unexpected connection */
- if (p_ccb->transport == BT_TRANSPORT_LE) {
- L2CA_DisconnectLECocReq(l2cap_cid);
- } else {
- L2CA_DisconnectReq(l2cap_cid);
- }
+ L2CA_DisconnectReq(l2cap_cid);
return;
}
@@ -630,7 +745,15 @@ static void gap_connect_ind(const RawAddress& bd_addr, uint16_t l2cap_cid,
p_ccb->rem_dev_address = bd_addr;
p_ccb->connection_id = l2cap_cid;
+ /* Send response to the L2CAP layer. */
+ if (p_ccb->transport == BT_TRANSPORT_BR_EDR)
+ L2CA_ErtmConnectRsp(bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_OK,
+ L2CAP_CONN_OK, &p_ccb->ertm_info);
+
if (p_ccb->transport == BT_TRANSPORT_LE) {
+ L2CA_ConnectLECocRsp(bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_OK,
+ L2CAP_CONN_OK, &p_ccb->local_coc_cfg);
+
/* get the remote coc configuration */
L2CA_GetPeerLECocConfig(l2cap_cid, &p_ccb->peer_coc_cfg);
p_ccb->rem_mtu_size = p_ccb->peer_coc_cfg.mtu;
@@ -643,6 +766,10 @@ static void gap_connect_ind(const RawAddress& bd_addr, uint16_t l2cap_cid,
DVLOG(1) << StringPrintf("GAP_CONN - Rcvd L2CAP conn ind, CID: 0x%x",
p_ccb->connection_id);
+
+ /* Send a Configuration Request. */
+ if (p_ccb->transport == BT_TRANSPORT_BR_EDR)
+ L2CA_ConfigReq(l2cap_cid, &p_ccb->cfg);
}
/*******************************************************************************
@@ -675,21 +802,22 @@ static void gap_checks_con_flags(tGAP_CCB* p_ccb) {
* Returns void
*
******************************************************************************/
-static void gap_sec_check_complete(tGAP_CCB* p_ccb) {
- if (p_ccb->con_state == GAP_CCB_STATE_IDLE) return;
- p_ccb->con_flags |= GAP_CCB_FLAGS_SEC_DONE;
- gap_checks_con_flags(p_ccb);
-}
+static void gap_sec_check_complete(const RawAddress*, tBT_TRANSPORT,
+ void* p_ref_data, uint8_t res) {
+ tGAP_CCB* p_ccb = (tGAP_CCB*)p_ref_data;
-static void gap_on_l2cap_error(uint16_t l2cap_cid, uint16_t result) {
- tGAP_CCB* p_ccb = gap_find_ccb_by_cid(l2cap_cid);
- if (p_ccb == nullptr) return;
-
- /* Tell the user if there is a callback */
- if (p_ccb->p_callback)
- (*p_ccb->p_callback)(p_ccb->gap_handle, GAP_EVT_CONN_CLOSED, nullptr);
+ DVLOG(1) << StringPrintf(
+ "gap_sec_check_complete conn_state:%d, conn_flags:0x%x, status:%d",
+ p_ccb->con_state, p_ccb->con_flags, res);
+ if (p_ccb->con_state == GAP_CCB_STATE_IDLE) return;
- gap_release_ccb(p_ccb);
+ if (res == BTM_SUCCESS) {
+ p_ccb->con_flags |= GAP_CCB_FLAGS_SEC_DONE;
+ gap_checks_con_flags(p_ccb);
+ } else {
+ /* security failed - disconnect the channel */
+ L2CA_DisconnectReq(p_ccb->connection_id);
+ }
}
/*******************************************************************************
@@ -713,8 +841,8 @@ static void gap_connect_cfm(uint16_t l2cap_cid, uint16_t result) {
/* initiate security process, if needed */
if ((p_ccb->con_flags & GAP_CCB_FLAGS_SEC_DONE) == 0 &&
p_ccb->transport != BT_TRANSPORT_LE) {
- // Assume security check is done by L2cap
- gap_sec_check_complete(p_ccb);
+ btm_sec_mx_access_request(p_ccb->rem_dev_address, p_ccb->psm, true, 0, 0,
+ &gap_sec_check_complete, p_ccb);
}
/* If the connection response contains success status, then */
@@ -723,6 +851,9 @@ static void gap_connect_cfm(uint16_t l2cap_cid, uint16_t result) {
(p_ccb->con_state == GAP_CCB_STATE_CONN_SETUP)) {
if (p_ccb->transport == BT_TRANSPORT_BR_EDR) {
p_ccb->con_state = GAP_CCB_STATE_CFG_SETUP;
+
+ /* Send a Configuration Request. */
+ L2CA_ConfigReq(l2cap_cid, &p_ccb->cfg);
}
if (p_ccb->transport == BT_TRANSPORT_LE) {
@@ -736,6 +867,12 @@ static void gap_connect_cfm(uint16_t l2cap_cid, uint16_t result) {
p_ccb->con_flags |= GAP_CCB_FLAGS_SEC_DONE;
gap_checks_con_flags(p_ccb);
}
+ } else {
+ /* Tell the user if he has a callback */
+ if (p_ccb->p_callback)
+ (*p_ccb->p_callback)(p_ccb->gap_handle, GAP_EVT_CONN_CLOSED, nullptr);
+
+ gap_release_ccb(p_ccb);
}
}
@@ -760,7 +897,8 @@ static void gap_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
/* Remember the remote MTU size */
if (p_ccb->cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) {
- local_mtu_size = BT_DEFAULT_BUFFER_SIZE - sizeof(BT_HDR) - L2CAP_MIN_OFFSET;
+ local_mtu_size =
+ p_ccb->ertm_info.user_tx_buf_size - sizeof(BT_HDR) - L2CAP_MIN_OFFSET;
} else
local_mtu_size = L2CAP_MTU_SIZE;
@@ -768,6 +906,18 @@ static void gap_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
p_ccb->rem_mtu_size = local_mtu_size;
} else
p_ccb->rem_mtu_size = p_cfg->mtu;
+
+ /* For now, always accept configuration from the other side */
+ p_cfg->flush_to_present = false;
+ p_cfg->mtu_present = false;
+ p_cfg->result = L2CAP_CFG_OK;
+ p_cfg->fcs_present = false;
+
+ L2CA_ConfigRsp(l2cap_cid, p_cfg);
+
+ p_ccb->con_flags |= GAP_CCB_FLAGS_HIS_CFG_DONE;
+
+ gap_checks_con_flags(p_ccb);
}
/*******************************************************************************
@@ -780,19 +930,26 @@ static void gap_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
* Returns void
*
******************************************************************************/
-static void gap_config_cfm(uint16_t l2cap_cid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
- gap_config_ind(l2cap_cid, p_cfg);
-
+static void gap_config_cfm(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
tGAP_CCB* p_ccb;
/* Find CCB based on CID */
p_ccb = gap_find_ccb_by_cid(l2cap_cid);
if (p_ccb == NULL) return;
- p_ccb->con_flags |= GAP_CCB_FLAGS_MY_CFG_DONE;
- p_ccb->con_flags |= GAP_CCB_FLAGS_HIS_CFG_DONE;
- gap_checks_con_flags(p_ccb);
+ if (p_cfg->result == L2CAP_CFG_OK) {
+ p_ccb->con_flags |= GAP_CCB_FLAGS_MY_CFG_DONE;
+
+ if (p_ccb->cfg.fcr_present)
+ p_ccb->cfg.fcr.mode = p_cfg->fcr.mode;
+ else
+ p_ccb->cfg.fcr.mode = L2CAP_FCR_BASIC_MODE;
+
+ gap_checks_con_flags(p_ccb);
+ } else {
+ p_ccb->p_callback(p_ccb->gap_handle, GAP_EVT_CONN_CLOSED, nullptr);
+ gap_release_ccb(p_ccb);
+ }
}
/*******************************************************************************
@@ -814,6 +971,8 @@ static void gap_disconnect_ind(uint16_t l2cap_cid, bool ack_needed) {
p_ccb = gap_find_ccb_by_cid(l2cap_cid);
if (p_ccb == NULL) return;
+ if (ack_needed) L2CA_DisconnectRsp(l2cap_cid);
+
p_ccb->p_callback(p_ccb->gap_handle, GAP_EVT_CONN_CLOSED, nullptr);
gap_release_ccb(p_ccb);
}
@@ -994,7 +1153,7 @@ static void gap_release_ccb(tGAP_CCB* p_ccb) {
}
/* Free the security record for this PSM */
- BTM_SecClrServiceByPsm(p_ccb->psm);
+ BTM_SecClrService(p_ccb->service_id);
if (p_ccb->transport == BT_TRANSPORT_BR_EDR) L2CA_Deregister(p_ccb->psm);
if (p_ccb->transport == BT_TRANSPORT_LE) L2CA_DeregisterLECoc(p_ccb->psm);
}
diff --git a/stack/gatt/att_protocol.cc b/stack/gatt/att_protocol.cc
index 87da319d8..5d3d4a818 100644
--- a/stack/gatt/att_protocol.cc
+++ b/stack/gatt/att_protocol.cc
@@ -26,7 +26,6 @@
#include "gatt_int.h"
#include "l2c_api.h"
-#include "osi/include/log.h"
#define GATT_HDR_FIND_TYPE_VALUE_LEN 21
#define GATT_OP_CODE_SIZE 1
@@ -46,7 +45,7 @@ using bluetooth::Uuid;
* Returns None.
*
******************************************************************************/
-static BT_HDR* attp_build_mtu_cmd(uint8_t op_code, uint16_t rx_mtu) {
+BT_HDR* attp_build_mtu_cmd(uint8_t op_code, uint16_t rx_mtu) {
uint8_t* p;
BT_HDR* p_buf =
(BT_HDR*)osi_malloc(sizeof(BT_HDR) + GATT_HDR_SIZE + L2CAP_MIN_OFFSET);
@@ -69,7 +68,7 @@ static BT_HDR* attp_build_mtu_cmd(uint8_t op_code, uint16_t rx_mtu) {
* Returns None.
*
******************************************************************************/
-static BT_HDR* attp_build_exec_write_cmd(uint8_t op_code, uint8_t flag) {
+BT_HDR* attp_build_exec_write_cmd(uint8_t op_code, uint8_t flag) {
BT_HDR* p_buf = (BT_HDR*)osi_malloc(GATT_DATA_BUF_SIZE);
uint8_t* p;
@@ -98,8 +97,8 @@ static BT_HDR* attp_build_exec_write_cmd(uint8_t op_code, uint8_t flag) {
* Returns None.
*
******************************************************************************/
-static BT_HDR* attp_build_err_cmd(uint8_t cmd_code, uint16_t err_handle,
- uint8_t reason) {
+BT_HDR* attp_build_err_cmd(uint8_t cmd_code, uint16_t err_handle,
+ uint8_t reason) {
uint8_t* p;
BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR) + L2CAP_MIN_OFFSET + 5);
@@ -125,9 +124,8 @@ static BT_HDR* attp_build_err_cmd(uint8_t cmd_code, uint16_t err_handle,
* Returns None.
*
******************************************************************************/
-static BT_HDR* attp_build_browse_cmd(uint8_t op_code, uint16_t s_hdl,
- uint16_t e_hdl,
- const bluetooth::Uuid& uuid) {
+BT_HDR* attp_build_browse_cmd(uint8_t op_code, uint16_t s_hdl, uint16_t e_hdl,
+ const bluetooth::Uuid& uuid) {
const size_t payload_size =
(GATT_OP_CODE_SIZE) + (GATT_START_END_HANDLE_SIZE) + (Uuid::kNumBytes128);
BT_HDR* p_buf =
@@ -155,8 +153,8 @@ static BT_HDR* attp_build_browse_cmd(uint8_t op_code, uint16_t s_hdl,
* Returns pointer to the command buffer.
*
******************************************************************************/
-static BT_HDR* attp_build_read_by_type_value_cmd(
- uint16_t payload_size, tGATT_FIND_TYPE_VALUE* p_value_type) {
+BT_HDR* attp_build_read_by_type_value_cmd(uint16_t payload_size,
+ tGATT_FIND_TYPE_VALUE* p_value_type) {
uint8_t* p;
uint16_t len = p_value_type->value_len;
BT_HDR* p_buf =
@@ -190,9 +188,8 @@ static BT_HDR* attp_build_read_by_type_value_cmd(
* Returns None.
*
******************************************************************************/
-static BT_HDR* attp_build_read_multi_cmd(uint8_t op_code, uint16_t payload_size,
- uint16_t num_handle,
- uint16_t* p_handle) {
+BT_HDR* attp_build_read_multi_cmd(uint16_t payload_size, uint16_t num_handle,
+ uint16_t* p_handle) {
uint8_t *p, i = 0;
BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR) + num_handle * 2 + 1 +
L2CAP_MIN_OFFSET);
@@ -201,7 +198,7 @@ static BT_HDR* attp_build_read_multi_cmd(uint8_t op_code, uint16_t payload_size,
p_buf->offset = L2CAP_MIN_OFFSET;
p_buf->len = 1;
- UINT8_TO_STREAM(p, op_code);
+ UINT8_TO_STREAM(p, GATT_REQ_READ_MULTI);
for (i = 0; i < num_handle && p_buf->len + 2 <= payload_size; i++) {
UINT16_TO_STREAM(p, *(p_handle + i));
@@ -219,8 +216,8 @@ static BT_HDR* attp_build_read_multi_cmd(uint8_t op_code, uint16_t payload_size,
* Returns None.
*
******************************************************************************/
-static BT_HDR* attp_build_handle_cmd(uint8_t op_code, uint16_t handle,
- uint16_t offset) {
+BT_HDR* attp_build_handle_cmd(uint8_t op_code, uint16_t handle,
+ uint16_t offset) {
uint8_t* p;
BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR) + 5 + L2CAP_MIN_OFFSET);
@@ -250,7 +247,7 @@ static BT_HDR* attp_build_handle_cmd(uint8_t op_code, uint16_t handle,
* Returns None.
*
******************************************************************************/
-static BT_HDR* attp_build_opcode_cmd(uint8_t op_code) {
+BT_HDR* attp_build_opcode_cmd(uint8_t op_code) {
uint8_t* p;
BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR) + 1 + L2CAP_MIN_OFFSET);
@@ -272,9 +269,9 @@ static BT_HDR* attp_build_opcode_cmd(uint8_t op_code) {
* Returns None.
*
******************************************************************************/
-static BT_HDR* attp_build_value_cmd(uint16_t payload_size, uint8_t op_code,
- uint16_t handle, uint16_t offset,
- uint16_t len, uint8_t* p_data) {
+BT_HDR* attp_build_value_cmd(uint16_t payload_size, uint8_t op_code,
+ uint16_t handle, uint16_t offset, uint16_t len,
+ uint8_t* p_data) {
uint8_t *p, *pp, pair_len, *p_pair_len;
BT_HDR* p_buf =
(BT_HDR*)osi_malloc(sizeof(BT_HDR) + payload_size + L2CAP_MIN_OFFSET);
@@ -325,17 +322,13 @@ static BT_HDR* attp_build_value_cmd(uint16_t payload_size, uint8_t op_code,
* Description Send message to L2CAP.
*
******************************************************************************/
-tGATT_STATUS attp_send_msg_to_l2cap(tGATT_TCB& tcb, uint16_t lcid,
- BT_HDR* p_toL2CAP) {
+tGATT_STATUS attp_send_msg_to_l2cap(tGATT_TCB& tcb, BT_HDR* p_toL2CAP) {
uint16_t l2cap_ret;
- if (lcid == L2CAP_ATT_CID) {
- LOG_DEBUG("Sending ATT message on att fixed channel");
- l2cap_ret = L2CA_SendFixedChnlData(lcid, tcb.peer_bda, p_toL2CAP);
- } else {
- LOG_DEBUG("Sending ATT message on lcid:%hu", lcid);
- l2cap_ret = (uint16_t)L2CA_DataWrite(lcid, p_toL2CAP);
- }
+ if (tcb.att_lcid == L2CAP_ATT_CID)
+ l2cap_ret = L2CA_SendFixedChnlData(L2CAP_ATT_CID, tcb.peer_bda, p_toL2CAP);
+ else
+ l2cap_ret = (uint16_t)L2CA_DataWrite(tcb.att_lcid, p_toL2CAP);
if (l2cap_ret == L2CAP_DW_FAILED) {
LOG(ERROR) << __func__ << ": failed to write data to L2CAP";
@@ -401,15 +394,11 @@ BT_HDR* attp_build_sr_msg(tGATT_TCB& tcb, uint8_t op_code,
*
*
******************************************************************************/
-tGATT_STATUS attp_send_sr_msg(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_msg) {
- if (p_msg == NULL) {
- LOG_WARN("Unable to send empty message");
- return GATT_NO_RESOURCES;
- }
+tGATT_STATUS attp_send_sr_msg(tGATT_TCB& tcb, BT_HDR* p_msg) {
+ if (p_msg == NULL) return GATT_NO_RESOURCES;
- LOG_DEBUG("Sending server response or indication message to client");
p_msg->offset = L2CAP_MIN_OFFSET;
- return attp_send_msg_to_l2cap(tcb, cid, p_msg);
+ return attp_send_msg_to_l2cap(tcb, p_msg);
}
/*******************************************************************************
@@ -424,31 +413,26 @@ tGATT_STATUS attp_send_sr_msg(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_msg) {
* GATT_ERROR if command sending failure
*
******************************************************************************/
-static tGATT_STATUS attp_cl_send_cmd(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
- uint8_t cmd_code, BT_HDR* p_cmd) {
+tGATT_STATUS attp_cl_send_cmd(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
+ uint8_t cmd_code, BT_HDR* p_cmd) {
cmd_code &= ~GATT_AUTH_SIGN_MASK;
- if (gatt_tcb_is_cid_busy(tcb, p_clcb->cid) &&
- cmd_code != GATT_HANDLE_VALUE_CONF) {
+ if (!tcb.cl_cmd_q.empty() && cmd_code != GATT_HANDLE_VALUE_CONF) {
gatt_cmd_enq(tcb, p_clcb, true, cmd_code, p_cmd);
- LOG_DEBUG("Enqueued ATT command");
return GATT_CMD_STARTED;
}
- LOG_DEBUG(
- "Sending ATT command to l2cap cid:0x%04x eatt_channels:%u transport:%s",
- p_clcb->cid, tcb.eatt, bt_transport_text(tcb.transport).c_str());
- tGATT_STATUS att_ret = attp_send_msg_to_l2cap(tcb, p_clcb->cid, p_cmd);
+ /* no pending request or value confirmation */
+ tGATT_STATUS att_ret = attp_send_msg_to_l2cap(tcb, p_cmd);
if (att_ret != GATT_CONGESTED && att_ret != GATT_SUCCESS) {
- LOG_WARN("Unable to send ATT command to l2cap layer");
return GATT_INTERNAL_ERROR;
}
+ /* do not enq cmd if handle value confirmation or set request */
if (cmd_code == GATT_HANDLE_VALUE_CONF || cmd_code == GATT_CMD_WRITE) {
return att_ret;
}
- LOG_DEBUG("Starting ATT response timer");
gatt_start_rsp_timer(p_clcb);
gatt_cmd_enq(tcb, p_clcb, false, cmd_code, NULL);
return att_ret;
@@ -456,35 +440,6 @@ static tGATT_STATUS attp_cl_send_cmd(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
/*******************************************************************************
*
- * Function attp_send_cl_confirmation_msg
- *
- * Description This function sends the client confirmation
- * message to server.
- *
- * Parameter p_tcb: pointer to the connection control block.
- * cid: channel id
- *
- * Returns GATT_SUCCESS if successfully sent; otherwise error code.
- *
- *
- ******************************************************************************/
-tGATT_STATUS attp_send_cl_confirmation_msg(tGATT_TCB& tcb, uint16_t cid) {
- BT_HDR* p_cmd = NULL;
- p_cmd = attp_build_opcode_cmd(GATT_HANDLE_VALUE_CONF);
-
- if (p_cmd == NULL) return GATT_NO_RESOURCES;
-
- /* no pending request or value confirmation */
- tGATT_STATUS att_ret = attp_send_msg_to_l2cap(tcb, cid, p_cmd);
- if (att_ret != GATT_CONGESTED && att_ret != GATT_SUCCESS) {
- return GATT_INTERNAL_ERROR;
- }
-
- return att_ret;
-}
-
-/*******************************************************************************
- *
* Function attp_send_cl_msg
*
* Description This function sends the client request or confirmation
@@ -503,22 +458,9 @@ tGATT_STATUS attp_send_cl_msg(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
uint8_t op_code, tGATT_CL_MSG* p_msg) {
BT_HDR* p_cmd = NULL;
uint16_t offset = 0, handle;
-
- if (!p_clcb) {
- LOG_ERROR("Missing p_clcb");
- return GATT_ILLEGAL_PARAMETER;
- }
-
- uint16_t payload_size = gatt_tcb_get_payload_size_tx(tcb, p_clcb->cid);
-
switch (op_code) {
case GATT_REQ_MTU:
- if (p_msg->mtu > GATT_MAX_MTU_SIZE) {
- LOG_WARN(
- "GATT message MTU is larger than max GATT MTU size op_code:%hhu",
- op_code);
- return GATT_ILLEGAL_PARAMETER;
- }
+ if (p_msg->mtu > GATT_MAX_MTU_SIZE) return GATT_ILLEGAL_PARAMETER;
tcb.payload_size = p_msg->mtu;
p_cmd = attp_build_mtu_cmd(GATT_REQ_MTU, p_msg->mtu);
@@ -529,10 +471,8 @@ tGATT_STATUS attp_send_cl_msg(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
case GATT_REQ_READ_BY_GRP_TYPE:
if (!GATT_HANDLE_IS_VALID(p_msg->browse.s_handle) ||
!GATT_HANDLE_IS_VALID(p_msg->browse.e_handle) ||
- p_msg->browse.s_handle > p_msg->browse.e_handle) {
- LOG_WARN("GATT message has invalid handle op_code:%hhu", op_code);
+ p_msg->browse.s_handle > p_msg->browse.e_handle)
return GATT_ILLEGAL_PARAMETER;
- }
p_cmd = attp_build_browse_cmd(op_code, p_msg->browse.s_handle,
p_msg->browse.e_handle, p_msg->browse.uuid);
@@ -545,27 +485,26 @@ tGATT_STATUS attp_send_cl_msg(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
handle =
(op_code == GATT_REQ_READ) ? p_msg->handle : p_msg->read_blob.handle;
/* handle checking */
- if (!GATT_HANDLE_IS_VALID(handle)) {
- LOG_WARN("GATT message has invalid handle op_code:%hhu", op_code);
- return GATT_ILLEGAL_PARAMETER;
- }
+ if (!GATT_HANDLE_IS_VALID(handle)) return GATT_ILLEGAL_PARAMETER;
p_cmd = attp_build_handle_cmd(op_code, handle, offset);
break;
+ case GATT_HANDLE_VALUE_CONF:
+ p_cmd = attp_build_opcode_cmd(op_code);
+ break;
+
case GATT_REQ_PREPARE_WRITE:
offset = p_msg->attr_value.offset;
FALLTHROUGH_INTENDED; /* FALLTHROUGH */
case GATT_REQ_WRITE:
case GATT_CMD_WRITE:
case GATT_SIGN_CMD_WRITE:
- if (!GATT_HANDLE_IS_VALID(p_msg->attr_value.handle)) {
- LOG_WARN("GATT message has invalid handle op_code:%hhu", op_code);
+ if (!GATT_HANDLE_IS_VALID(p_msg->attr_value.handle))
return GATT_ILLEGAL_PARAMETER;
- }
p_cmd = attp_build_value_cmd(
- payload_size, op_code, p_msg->attr_value.handle, offset,
+ tcb.payload_size, op_code, p_msg->attr_value.handle, offset,
p_msg->attr_value.len, p_msg->attr_value.value);
break;
@@ -574,13 +513,12 @@ tGATT_STATUS attp_send_cl_msg(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
break;
case GATT_REQ_FIND_TYPE_VALUE:
- p_cmd = attp_build_read_by_type_value_cmd(payload_size,
+ p_cmd = attp_build_read_by_type_value_cmd(tcb.payload_size,
&p_msg->find_type_value);
break;
case GATT_REQ_READ_MULTI:
- case GATT_REQ_READ_MULTI_VAR:
- p_cmd = attp_build_read_multi_cmd(op_code, payload_size,
+ p_cmd = attp_build_read_multi_cmd(tcb.payload_size,
p_msg->read_multi.num_handles,
p_msg->read_multi.handles);
break;
@@ -589,13 +527,7 @@ tGATT_STATUS attp_send_cl_msg(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
break;
}
- if (p_cmd == NULL) {
- LOG_WARN(
- "Unable to build proper GATT message to send to peer device "
- "op_code:%hhu",
- op_code);
- return GATT_NO_RESOURCES;
- }
+ if (p_cmd == NULL) return GATT_NO_RESOURCES;
return attp_cl_send_cmd(tcb, p_clcb, op_code, p_cmd);
}
diff --git a/stack/gatt/connection_manager.cc b/stack/gatt/connection_manager.cc
index 2d71d635b..9454be0c4 100644
--- a/stack/gatt/connection_manager.cc
+++ b/stack/gatt/connection_manager.cc
@@ -27,11 +27,8 @@
#include <set>
#include "internal_include/bt_trace.h"
-#include "main/shim/shim.h"
#include "osi/include/alarm.h"
-#include "osi/include/log.h"
#include "stack/btm/btm_ble_bgconn.h"
-#include "stack/include/l2c_api.h"
#define DIRECT_CONNECT_TIMEOUT (30 * 1000) /* 30 seconds */
@@ -92,29 +89,25 @@ std::set<tAPP_ID> get_apps_connecting_to(const RawAddress& address) {
/** Add a device from the background connection list. Returns true if device
* added to the list, or already in list, false otherwise */
bool background_connect_add(uint8_t app_id, const RawAddress& address) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return L2CA_ConnectFixedChnl(L2CAP_ATT_CID, address);
- }
-
auto it = bgconn_dev.find(address);
- bool in_acceptlist = false;
+ bool in_white_list = false;
if (it != bgconn_dev.end()) {
- // device already in the acceptlist, just add interested app to the list
+ // device already in the whitelist, just add interested app to the list
if (it->second.doing_bg_conn.count(app_id)) {
LOG(INFO) << "App id=" << loghex(app_id)
<< "already doing background connection to " << address;
return true;
}
- // Already in acceptlist ?
+ // Already in white list ?
if (anyone_connecting(it)) {
- in_acceptlist = true;
+ in_white_list = true;
}
}
- if (!in_acceptlist) {
- // the device is not in the acceptlist
- if (!BTM_AcceptlistAdd(address)) return false;
+ if (!in_white_list) {
+ // the device is not in the whitelist
+ if (!BTM_WhiteListAdd(address)) return false;
}
// create endtry for address, and insert app_id.
@@ -128,7 +121,7 @@ bool remove_unconditional(const RawAddress& address) {
auto it = bgconn_dev.find(address);
if (it == bgconn_dev.end()) return false;
- BTM_AcceptlistRemove(address);
+ BTM_WhiteListRemove(address);
bgconn_dev.erase(it);
return true;
}
@@ -145,8 +138,8 @@ bool background_connect_remove(uint8_t app_id, const RawAddress& address) {
if (anyone_connecting(it)) return true;
- // no more apps interested - remove from acceptlist and delete record
- BTM_AcceptlistRemove(address);
+ // no more apps interested - remove from whitelist and delete record
+ BTM_WhiteListRemove(address);
bgconn_dev.erase(it);
return true;
}
@@ -166,14 +159,15 @@ void on_app_deregistered(uint8_t app_id) {
continue;
}
- BTM_AcceptlistRemove(it->first);
+ BTM_WhiteListRemove(it->first);
it = bgconn_dev.erase(it);
}
}
-static void remove_all_clients_with_pending_connections(
- const RawAddress& address) {
+void on_connection_complete(const RawAddress& address) {
+ VLOG(2) << __func__;
auto it = bgconn_dev.find(address);
+
while (it != bgconn_dev.end() && !it->second.doing_direct_conn.empty()) {
uint8_t app_id = it->second.doing_direct_conn.begin()->first;
direct_connect_remove(app_id, address);
@@ -181,17 +175,11 @@ static void remove_all_clients_with_pending_connections(
}
}
-void on_connection_complete(const RawAddress& address) {
- LOG_INFO("Le connection completed to device:%s", address.ToString().c_str());
-
- remove_all_clients_with_pending_connections(address);
-}
-
/** Reset bg device list. If called after controller reset, set |after_reset| to
- * true, as there is no need to wipe controller acceptlist in this case. */
+ * true, as there is no need to wipe controller white list in this case. */
void reset(bool after_reset) {
bgconn_dev.clear();
- if (!after_reset) BTM_AcceptlistClear();
+ if (!after_reset) BTM_WhiteListClear();
}
void wl_direct_connect_timeout_cb(uint8_t app_id, const RawAddress& address) {
@@ -205,12 +193,9 @@ void wl_direct_connect_timeout_cb(uint8_t app_id, const RawAddress& address) {
/** Add a device to the direcgt connection list. Returns true if device
* added to the list, false otherwise */
bool direct_connect_add(uint8_t app_id, const RawAddress& address) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return L2CA_ConnectFixedChnl(L2CAP_ATT_CID, address);
- }
-
- bool in_acceptlist = false;
auto it = bgconn_dev.find(address);
+ bool in_white_list = false;
+
if (it != bgconn_dev.end()) {
// app already trying to connect to this particular device
if (it->second.doing_direct_conn.count(app_id)) {
@@ -219,20 +204,17 @@ bool direct_connect_add(uint8_t app_id, const RawAddress& address) {
return false;
}
- // are we already in the acceptlist ?
+ // are we already in the white list ?
if (anyone_connecting(it)) {
- LOG_WARN("Background connection attempt already in progress app_id=%x",
- app_id);
- in_acceptlist = true;
+ in_white_list = true;
}
}
bool params_changed = BTM_SetLeConnectionModeToFast();
- if (!in_acceptlist) {
- if (!BTM_AcceptlistAdd(address)) {
- // if we can't add to acceptlist, turn parameters back to slow.
- LOG_WARN("Unable to add le device to acceptlist");
+ if (!in_white_list) {
+ if (!BTM_WhiteListAdd(address)) {
+ // if we can't add to white list, turn parameters back to slow.
if (params_changed) BTM_SetLeConnectionModeToSlow();
return false;
}
@@ -249,7 +231,7 @@ bool direct_connect_add(uint8_t app_id, const RawAddress& address) {
return true;
}
-static bool any_direct_connect_left() {
+bool any_direct_connect_left() {
for (const auto& tmp : bgconn_dev) {
if (!tmp.second.doing_direct_conn.empty()) return true;
}
@@ -257,17 +239,13 @@ static bool any_direct_connect_left() {
}
bool direct_connect_remove(uint8_t app_id, const RawAddress& address) {
+ VLOG(2) << __func__ << ": "
+ << "app_id: " << +app_id << ", address:" << address;
auto it = bgconn_dev.find(address);
- if (it == bgconn_dev.end()) {
- LOG_WARN("Unable to find background connection to remove");
- return false;
- }
+ if (it == bgconn_dev.end()) return false;
auto app_it = it->second.doing_direct_conn.find(app_id);
- if (app_it == it->second.doing_direct_conn.end()) {
- LOG_WARN("Unable to find direct connection to remove");
- return false;
- }
+ if (app_it == it->second.doing_direct_conn.end()) return false;
// this will free the alarm
it->second.doing_direct_conn.erase(app_it);
@@ -278,12 +256,10 @@ bool direct_connect_remove(uint8_t app_id, const RawAddress& address) {
BTM_SetLeConnectionModeToSlow();
}
- if (anyone_connecting(it)) {
- return true;
- }
+ if (anyone_connecting(it)) return true;
- // no more apps interested - remove from acceptlist
- BTM_AcceptlistRemove(address);
+ // no more apps interested - remove from whitelist
+ BTM_WhiteListRemove(address);
bgconn_dev.erase(it);
return true;
}
diff --git a/stack/gatt/connection_manager.h b/stack/gatt/connection_manager.h
index 4d8295e3c..4704c8fe0 100644
--- a/stack/gatt/connection_manager.h
+++ b/stack/gatt/connection_manager.h
@@ -24,7 +24,7 @@
/* connection_manager takes care of all the low-level details of LE connection
* initiation. It accept requests from multiple subsystems to connect to
- * devices, and multiplex them into acceptlist add/remove, and scan parameter
+ * devices, and multiplex them into whitelist add/remove, and scan parameter
* changes.
*
* There is no code for app_id generation. GATT clients use their GATT_IF, and
diff --git a/stack/gatt/gatt_api.cc b/stack/gatt/gatt_api.cc
index 188e38e89..5fe9a373a 100644
--- a/stack/gatt/gatt_api.cc
+++ b/stack/gatt/gatt_api.cc
@@ -23,19 +23,16 @@
******************************************************************************/
#include "bt_target.h"
-#include <string>
-
#include <base/strings/string_number_conversions.h>
#include <stdio.h>
+#include <string.h>
#include "bt_common.h"
+#include "btm_int.h"
#include "device/include/controller.h"
#include "gatt_api.h"
#include "gatt_int.h"
#include "l2c_api.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
#include "stack/gatt/connection_manager.h"
-#include "types/bt_transport.h"
using bluetooth::Uuid;
@@ -108,16 +105,12 @@ static uint16_t compute_service_size(btgatt_db_element_t* service, int count) {
if (el->type == BTGATT_DB_PRIMARY_SERVICE ||
el->type == BTGATT_DB_SECONDARY_SERVICE ||
el->type == BTGATT_DB_DESCRIPTOR ||
- el->type == BTGATT_DB_INCLUDED_SERVICE) {
+ el->type == BTGATT_DB_INCLUDED_SERVICE)
db_size += 1;
- } else if (el->type == BTGATT_DB_CHARACTERISTIC) {
+ else if (el->type == BTGATT_DB_CHARACTERISTIC)
db_size += 2;
-
- // if present, Characteristic Extended Properties takes one handle
- if (el->properties & GATT_CHAR_PROP_BIT_EXT_PROP) db_size++;
- } else {
+ else
LOG(ERROR) << __func__ << ": Unknown element type: " << el->type;
- }
return db_size;
}
@@ -141,17 +134,6 @@ static void gatt_update_last_srv_info() {
}
}
-/** Update database hash and client status */
-static void gatt_update_for_database_change() {
- gatt_cb.database_hash = gatts_calculate_database_hash(gatt_cb.srv_list_info);
-
- uint8_t i = 0;
- for (i = 0; i < GATT_MAX_PHY_CHANNEL; i++) {
- tGATT_TCB& tcb = gatt_cb.tcb[i];
- if (tcb.in_use) gatt_sr_update_cl_status(tcb, /* chg_aware= */ false);
- }
-}
-
/*******************************************************************************
*
* Function GATTS_AddService
@@ -167,8 +149,8 @@ static void gatt_update_for_database_change() {
* on error error status is returned.
*
******************************************************************************/
-tGATT_STATUS GATTS_AddService(tGATT_IF gatt_if, btgatt_db_element_t* service,
- int count) {
+uint16_t GATTS_AddService(tGATT_IF gatt_if, btgatt_db_element_t* service,
+ int count) {
uint16_t s_hdl = 0;
bool save_hdl = false;
tGATT_REG* p_reg = gatt_get_regcb(gatt_if);
@@ -254,12 +236,6 @@ tGATT_STATUS GATTS_AddService(tGATT_IF gatt_if, btgatt_db_element_t* service,
el->attribute_handle = gatts_add_characteristic(
list.svc_db, el->permissions, el->properties, uuid);
-
- // add characteristic extended properties descriptor if needed
- if (el->properties & GATT_CHAR_PROP_BIT_EXT_PROP) {
- gatts_add_char_ext_prop_descr(list.svc_db, el->extended_properties);
- }
-
} else if (el->type == BTGATT_DB_DESCRIPTOR) {
if (is_gatt_attr_type(uuid)) {
LOG(ERROR) << __func__
@@ -321,7 +297,6 @@ tGATT_STATUS GATTS_AddService(tGATT_IF gatt_if, btgatt_db_element_t* service,
<< ", e_hdl=" << loghex(elem.e_hdl) << ", type=" << loghex(elem.type)
<< ", sdp_hdl=" << loghex(elem.sdp_handle);
- gatt_update_for_database_change();
gatt_proc_srv_chg();
return GATT_SERVICE_STARTED;
@@ -372,13 +347,12 @@ bool GATTS_DeleteService(tGATT_IF gatt_if, Uuid* p_svc_uuid,
return false;
}
+ gatt_proc_srv_chg();
+
if (is_active_service(p_reg->app_uuid128, p_svc_uuid, svc_inst)) {
GATTS_StopService(it->asgn_range.s_handle);
}
- gatt_update_for_database_change();
- gatt_proc_srv_chg();
-
VLOG(1) << "released handles s_hdl=" << loghex(it->asgn_range.s_handle)
<< ", e_hdl=" << loghex(it->asgn_range.e_handle);
@@ -402,7 +376,7 @@ bool GATTS_DeleteService(tGATT_IF gatt_if, Uuid* p_svc_uuid,
*
******************************************************************************/
void GATTS_StopService(uint16_t service_handle) {
- LOG(INFO) << __func__ << ": service = " << loghex(service_handle);
+ LOG(INFO) << __func__ << ": " << loghex(service_handle);
auto it = gatt_sr_find_i_rcb_by_handle(service_handle);
if (it == gatt_cb.srv_list_info->end()) {
@@ -456,11 +430,7 @@ tGATT_STATUS GATTS_HandleValueIndication(uint16_t conn_id, uint16_t attr_handle,
memcpy(indication.value, p_val, val_len);
indication.auth_req = GATT_AUTH_REQ_NONE;
- uint16_t* indicate_handle_p = NULL;
- uint16_t cid;
-
- if (!gatt_tcb_get_cid_available_for_indication(p_tcb, p_reg->eatt_support,
- &indicate_handle_p, &cid)) {
+ if (GATT_HANDLE_IS_VALID(p_tcb->indicate_handle)) {
VLOG(1) << "Add a pending indication";
gatt_add_pending_ind(p_tcb, &indication);
return GATT_SUCCESS;
@@ -472,10 +442,10 @@ tGATT_STATUS GATTS_HandleValueIndication(uint16_t conn_id, uint16_t attr_handle,
attp_build_sr_msg(*p_tcb, GATT_HANDLE_VALUE_IND, &gatt_sr_msg);
if (!p_msg) return GATT_NO_RESOURCES;
- tGATT_STATUS cmd_status = attp_send_sr_msg(*p_tcb, cid, p_msg);
+ tGATT_STATUS cmd_status = attp_send_sr_msg(*p_tcb, p_msg);
if (cmd_status == GATT_SUCCESS || cmd_status == GATT_CONGESTED) {
- *indicate_handle_p = indication.handle;
- gatt_start_conf_timer(p_tcb, cid);
+ p_tcb->indicate_handle = indication.handle;
+ gatt_start_conf_timer(p_tcb);
}
return cmd_status;
}
@@ -515,7 +485,6 @@ tGATT_STATUS GATTS_HandleValueNotification(uint16_t conn_id,
return GATT_ILLEGAL_PARAMETER;
}
- memset(&notif, 0, sizeof(notif));
notif.handle = attr_handle;
notif.len = val_len;
memcpy(notif.value, p_val, val_len);
@@ -524,13 +493,10 @@ tGATT_STATUS GATTS_HandleValueNotification(uint16_t conn_id,
tGATT_STATUS cmd_sent;
tGATT_SR_MSG gatt_sr_msg;
gatt_sr_msg.attr_value = notif;
-
- uint16_t cid = gatt_tcb_get_att_cid(*p_tcb, p_reg->eatt_support);
-
BT_HDR* p_buf =
attp_build_sr_msg(*p_tcb, GATT_HANDLE_VALUE_NOTIF, &gatt_sr_msg);
if (p_buf != NULL) {
- cmd_sent = attp_send_sr_msg(*p_tcb, cid, p_buf);
+ cmd_sent = attp_send_sr_msg(*p_tcb, p_buf);
} else
cmd_sent = GATT_NO_RESOURCES;
return cmd_sent;
@@ -552,31 +518,30 @@ tGATT_STATUS GATTS_HandleValueNotification(uint16_t conn_id,
******************************************************************************/
tGATT_STATUS GATTS_SendRsp(uint16_t conn_id, uint32_t trans_id,
tGATT_STATUS status, tGATTS_RSP* p_msg) {
+ tGATT_STATUS cmd_sent = GATT_ILLEGAL_PARAMETER;
tGATT_IF gatt_if = GATT_GET_GATT_IF(conn_id);
uint8_t tcb_idx = GATT_GET_TCB_IDX(conn_id);
tGATT_REG* p_reg = gatt_get_regcb(gatt_if);
tGATT_TCB* p_tcb = gatt_get_tcb_by_idx(tcb_idx);
VLOG(1) << __func__ << ": conn_id=" << loghex(conn_id)
- << ", trans_id=" << loghex(trans_id)
- << ", status=" << loghex(static_cast<uint8_t>(status));
+ << ", trans_id=" << loghex(trans_id) << ", status=" << loghex(status);
if ((p_reg == NULL) || (p_tcb == NULL)) {
LOG(ERROR) << "Unknown conn_id=" << loghex(conn_id);
return (tGATT_STATUS)GATT_INVALID_CONN_ID;
}
- tGATT_SR_CMD* sr_res_p = gatt_sr_get_cmd_by_trans_id(p_tcb, trans_id);
-
- if (!sr_res_p) {
+ if (p_tcb->sr_cmd.trans_id != trans_id) {
LOG(ERROR) << "conn_id=" << loghex(conn_id)
- << " waiting for other op_code ";
+ << " waiting for op_code=" << loghex(p_tcb->sr_cmd.op_code);
return (GATT_WRONG_STATE);
}
-
/* Process App response */
- return gatt_sr_process_app_rsp(*p_tcb, gatt_if, trans_id, sr_res_p->op_code,
- status, p_msg, sr_res_p);
+ cmd_sent = gatt_sr_process_app_rsp(*p_tcb, gatt_if, trans_id,
+ p_tcb->sr_cmd.op_code, status, p_msg);
+
+ return cmd_sent;
}
/******************************************************************************/
@@ -607,13 +572,10 @@ tGATT_STATUS GATTC_ConfigureMTU(uint16_t conn_id, uint16_t mtu) {
tGATT_TCB* p_tcb = gatt_get_tcb_by_idx(tcb_idx);
tGATT_REG* p_reg = gatt_get_regcb(gatt_if);
+ VLOG(1) << __func__ << ": conn_id=" << loghex(conn_id) << ", mtu=" << +mtu;
+
if ((p_tcb == NULL) || (p_reg == NULL) || (mtu < GATT_DEF_BLE_MTU_SIZE) ||
(mtu > GATT_MAX_MTU_SIZE)) {
- LOG_WARN(
- "Unable to configure ATT mtu size illegal parameter conn_id:%hu "
- "mtu:%hu tcb:%s reg:%s",
- conn_id, mtu, (p_tcb == nullptr) ? "BAD" : "ok",
- (p_reg == nullptr) ? "BAD" : "ok");
return GATT_ILLEGAL_PARAMETER;
}
@@ -623,24 +585,17 @@ tGATT_STATUS GATTC_ConfigureMTU(uint16_t conn_id, uint16_t mtu) {
}
if (gatt_is_clcb_allocated(conn_id)) {
- LOG_WARN("Connection is already used conn_id:%hu", conn_id);
+ LOG(ERROR) << "GATT_BUSY conn_id = " << +conn_id;
return GATT_BUSY;
}
tGATT_CLCB* p_clcb = gatt_clcb_alloc(conn_id);
- if (!p_clcb) {
- LOG_WARN("Unable to allocate connection link control block");
- return GATT_NO_RESOURCES;
- }
+ if (!p_clcb) return GATT_NO_RESOURCES;
- /* For this request only ATT CID is valid */
- p_clcb->cid = L2CAP_ATT_CID;
p_clcb->p_tcb->payload_size = mtu;
p_clcb->operation = GATTC_OPTYPE_CONFIG;
tGATT_CL_MSG gatt_cl_msg;
gatt_cl_msg.mtu = mtu;
- LOG_DEBUG("Configuring ATT mtu size conn_id:%hu mtu:%hu", conn_id, mtu);
-
return attp_send_cl_msg(*p_clcb->p_tcb, p_clcb, GATT_REQ_MTU, &gatt_cl_msg);
}
@@ -674,14 +629,15 @@ tGATT_STATUS GATTC_Discover(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
return GATT_ILLEGAL_PARAMETER;
}
+ LOG(INFO) << __func__ << " conn_id=" << loghex(conn_id)
+ << ", disc_type=" << +disc_type
+ << ", s_handle=" << loghex(start_handle)
+ << ", e_handle=" << loghex(end_handle);
+
if (!GATT_HANDLE_IS_VALID(start_handle) ||
!GATT_HANDLE_IS_VALID(end_handle) ||
/* search by type does not have a valid UUID param */
(disc_type == GATT_DISC_SRVC_BY_UUID && uuid.IsEmpty())) {
- LOG(WARNING) << __func__ << " Illegal parameter conn_id=" << loghex(conn_id)
- << ", disc_type=" << +disc_type
- << ", s_handle=" << loghex(start_handle)
- << ", e_handle=" << loghex(end_handle);
return GATT_ILLEGAL_PARAMETER;
}
@@ -691,13 +647,7 @@ tGATT_STATUS GATTC_Discover(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
}
tGATT_CLCB* p_clcb = gatt_clcb_alloc(conn_id);
- if (!p_clcb) {
- LOG(WARNING) << __func__ << " No resources conn_id=" << loghex(conn_id)
- << ", disc_type=" << +disc_type
- << ", s_handle=" << loghex(start_handle)
- << ", e_handle=" << loghex(end_handle);
- return GATT_NO_RESOURCES;
- }
+ if (!p_clcb) return GATT_NO_RESOURCES;
p_clcb->operation = GATTC_OPTYPE_DISCOVERY;
p_clcb->op_subtype = disc_type;
@@ -705,11 +655,6 @@ tGATT_STATUS GATTC_Discover(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
p_clcb->e_handle = end_handle;
p_clcb->uuid = uuid;
- LOG(INFO) << __func__ << " conn_id=" << loghex(conn_id)
- << ", disc_type=" << +disc_type
- << ", s_handle=" << loghex(start_handle)
- << ", e_handle=" << loghex(end_handle);
-
gatt_act_discovery(p_clcb);
return GATT_SUCCESS;
}
@@ -763,8 +708,7 @@ tGATT_STATUS GATTC_Read(uint16_t conn_id, tGATT_READ_TYPE type,
p_clcb->op_subtype = type;
p_clcb->auth_req = p_read->by_handle.auth_req;
p_clcb->counter = 0;
- p_clcb->read_req_current_mtu =
- gatt_tcb_get_payload_size_tx(*p_tcb, p_clcb->cid);
+ p_clcb->read_req_current_mtu = p_tcb->payload_size;
switch (type) {
case GATT_READ_BY_TYPE:
@@ -906,14 +850,14 @@ tGATT_STATUS GATTC_ExecuteWrite(uint16_t conn_id, bool is_execute) {
* as response to a handle value notification from server.
*
* Parameters conn_id: connection identifier.
- * cid: channel id.
+ * handle: the handle of the attribute confirmation.
*
* Returns GATT_SUCCESS if command started successfully.
*
******************************************************************************/
-tGATT_STATUS GATTC_SendHandleValueConfirm(uint16_t conn_id, uint16_t cid) {
+tGATT_STATUS GATTC_SendHandleValueConfirm(uint16_t conn_id, uint16_t handle) {
VLOG(1) << __func__ << " conn_id=" << loghex(conn_id)
- << ", cid=" << loghex(cid);
+ << ", handle=" << loghex(handle);
tGATT_TCB* p_tcb = gatt_get_tcb_by_idx(GATT_GET_TCB_IDX(conn_id));
if (!p_tcb) {
@@ -927,13 +871,16 @@ tGATT_STATUS GATTC_SendHandleValueConfirm(uint16_t conn_id, uint16_t cid) {
return GATT_SUCCESS;
}
- gatt_stop_ind_ack_timer(p_tcb, cid);
+ alarm_cancel(p_tcb->ind_ack_timer);
VLOG(1) << "notif_count= " << p_tcb->ind_count;
/* send confirmation now */
- tGATT_STATUS ret = attp_send_cl_confirmation_msg(*p_tcb, cid);
-
+ tGATT_CL_MSG gatt_cl_msg;
+ gatt_cl_msg.handle = handle;
+ tGATT_STATUS ret =
+ attp_send_cl_msg(*p_tcb, nullptr, GATT_HANDLE_VALUE_CONF, &gatt_cl_msg);
+ p_tcb->ind_count = 0;
return ret;
}
@@ -962,11 +909,16 @@ void GATT_SetIdleTimeout(const RawAddress& bd_addr, uint16_t idle_tout,
tGATT_TCB* p_tcb = gatt_find_tcb_by_addr(bd_addr, transport);
if (p_tcb != NULL) {
- status = L2CA_SetLeGattTimeout(bd_addr, idle_tout);
+ if (p_tcb->att_lcid == L2CAP_ATT_CID) {
+ status = L2CA_SetFixedChannelTout(bd_addr, L2CAP_ATT_CID, idle_tout);
- if (idle_tout == GATT_LINK_IDLE_TIMEOUT_WHEN_NO_APP)
- L2CA_SetIdleTimeoutByBdAddr(
- p_tcb->peer_bda, GATT_LINK_IDLE_TIMEOUT_WHEN_NO_APP, BT_TRANSPORT_LE);
+ if (idle_tout == GATT_LINK_IDLE_TIMEOUT_WHEN_NO_APP)
+ L2CA_SetIdleTimeoutByBdAddr(p_tcb->peer_bda,
+ GATT_LINK_IDLE_TIMEOUT_WHEN_NO_APP,
+ BT_TRANSPORT_LE);
+ } else {
+ status = L2CA_SetIdleTimeout(p_tcb->att_lcid, idle_tout, false);
+ }
}
VLOG(1) << __func__ << " idle_tout=" << idle_tout << ", status=" << +status
@@ -982,23 +934,22 @@ void GATT_SetIdleTimeout(const RawAddress& bd_addr, uint16_t idle_tout,
*
* Parameter p_app_uuid128: Application UUID
* p_cb_info: callback functions.
- * eatt_support: indicate eatt support.
*
* Returns 0 for error, otherwise the index of the client registered
* with GATT
*
******************************************************************************/
-tGATT_IF GATT_Register(const Uuid& app_uuid128, std::string name,
- tGATT_CBACK* p_cb_info, bool eatt_support) {
+tGATT_IF GATT_Register(const Uuid& app_uuid128, tGATT_CBACK* p_cb_info) {
tGATT_REG* p_reg;
uint8_t i_gatt_if = 0;
tGATT_IF gatt_if = 0;
+ LOG(INFO) << __func__ << " " << app_uuid128;
+
for (i_gatt_if = 0, p_reg = gatt_cb.cl_rcb; i_gatt_if < GATT_MAX_APPS;
i_gatt_if++, p_reg++) {
if (p_reg->in_use && p_reg->app_uuid128 == app_uuid128) {
- LOG(ERROR) << __func__ << ": Application already registered "
- << app_uuid128;
+ LOG(ERROR) << "application already registered.";
return 0;
}
}
@@ -1006,23 +957,19 @@ tGATT_IF GATT_Register(const Uuid& app_uuid128, std::string name,
for (i_gatt_if = 0, p_reg = gatt_cb.cl_rcb; i_gatt_if < GATT_MAX_APPS;
i_gatt_if++, p_reg++) {
if (!p_reg->in_use) {
- *p_reg = {};
+ memset(p_reg, 0, sizeof(tGATT_REG));
i_gatt_if++; /* one based number */
p_reg->app_uuid128 = app_uuid128;
gatt_if = p_reg->gatt_if = (tGATT_IF)i_gatt_if;
p_reg->app_cb = *p_cb_info;
p_reg->in_use = true;
- p_reg->eatt_support = eatt_support;
- p_reg->name = name;
- LOG_INFO("Allocated name:%s uuid:%s gatt_if:%hhu eatt_support:%u",
- name.c_str(), app_uuid128.ToString().c_str(), gatt_if,
- eatt_support);
+
+ LOG(INFO) << "allocated gatt_if=" << +gatt_if;
return gatt_if;
}
}
- LOG(ERROR) << __func__
- << ": Unable to register GATT client, MAX client reached: "
+ LOG(ERROR) << "can't Register GATT client, MAX client reached: "
<< GATT_MAX_APPS;
return 0;
}
@@ -1039,14 +986,12 @@ tGATT_IF GATT_Register(const Uuid& app_uuid128, std::string name,
*
******************************************************************************/
void GATT_Deregister(tGATT_IF gatt_if) {
- LOG(INFO) << __func__ << " gatt_if=" << +gatt_if;
+ VLOG(1) << __func__ << " gatt_if=" << +gatt_if;
tGATT_REG* p_reg = gatt_get_regcb(gatt_if);
/* Index 0 is GAP and is never deregistered */
if ((gatt_if == 0) || (p_reg == NULL)) {
- LOG(ERROR) << __func__
- << ": Unable to deregister client with invalid gatt_if="
- << +gatt_if;
+ LOG(ERROR) << "invalid gatt_if=" << +gatt_if;
return;
}
@@ -1091,7 +1036,7 @@ void GATT_Deregister(tGATT_IF gatt_if) {
connection_manager::on_app_deregistered(gatt_if);
- *p_reg = {};
+ memset(p_reg, 0, sizeof(tGATT_REG));
}
/*******************************************************************************
@@ -1113,10 +1058,9 @@ void GATT_StartIf(tGATT_IF gatt_if) {
RawAddress bda;
uint8_t start_idx, found_idx;
uint16_t conn_id;
- tBT_TRANSPORT transport;
-
- LOG_DEBUG("Starting GATT interface gatt_if_:%hu", gatt_if);
+ tGATT_TRANSPORT transport;
+ VLOG(1) << __func__ << " gatt_if=" << +gatt_if;
p_reg = gatt_get_regcb(gatt_if);
if (p_reg != NULL) {
start_idx = 0;
@@ -1125,8 +1069,7 @@ void GATT_StartIf(tGATT_IF gatt_if) {
p_tcb = gatt_find_tcb_by_addr(bda, transport);
if (p_reg->app_cb.p_conn_cb && p_tcb) {
conn_id = GATT_CREATE_CONN_ID(p_tcb->tcb_idx, gatt_if);
- (*p_reg->app_cb.p_conn_cb)(gatt_if, bda, conn_id, true,
- GATT_CONN_UNKNOWN, transport);
+ (*p_reg->app_cb.p_conn_cb)(gatt_if, bda, conn_id, true, 0, transport);
}
start_idx = ++found_idx;
}
@@ -1159,46 +1102,36 @@ bool GATT_Connect(tGATT_IF gatt_if, const RawAddress& bd_addr, bool is_direct,
bool GATT_Connect(tGATT_IF gatt_if, const RawAddress& bd_addr, bool is_direct,
tBT_TRANSPORT transport, bool opportunistic,
uint8_t initiating_phys) {
+ LOG(INFO) << __func__ << "gatt_if=" << +gatt_if << ", address=" << bd_addr;
+
/* Make sure app is registered */
tGATT_REG* p_reg = gatt_get_regcb(gatt_if);
if (!p_reg) {
- LOG(ERROR) << __func__
- << ": Unable to find registered app gatt_if=" << +gatt_if;
+ LOG(ERROR) << "gatt_if = " << +gatt_if << " is not registered";
return false;
}
if (!is_direct && transport != BT_TRANSPORT_LE) {
- LOG(ERROR) << __func__
- << ": Unsupported transport for background connection gatt_if="
- << +gatt_if;
+ LOG(ERROR) << "Unsupported transport for background connection";
return false;
}
if (opportunistic) {
- LOG(INFO) << __func__
- << ": Registered for opportunistic connection gatt_if="
- << +gatt_if;
+ LOG(INFO) << __func__ << " opportunistic connection";
return true;
}
bool ret;
if (is_direct) {
- LOG_DEBUG("Starting direct connect gatt_if=%u address=%s", gatt_if,
- bd_addr.ToString().c_str());
ret = gatt_act_connect(p_reg, bd_addr, transport, initiating_phys);
} else {
- LOG_DEBUG("Starting background connect gatt_if=%u address=%s", gatt_if,
- bd_addr.ToString().c_str());
if (!BTM_BackgroundConnectAddressKnown(bd_addr)) {
// RPA can rotate, causing address to "expire" in the background
// connection list. RPA is allowed for direct connect, as such request
// times out after 30 seconds
- LOG(INFO) << __func__
- << ": Unable to add RPA to background connection gatt_if="
- << +gatt_if;
+ LOG(INFO) << "Can't add RPA to background connection.";
ret = true;
} else {
- LOG_DEBUG("Adding to acceptlist device:%s", PRIVATE_ADDRESS(bd_addr));
ret = connection_manager::background_connect_add(gatt_if, bd_addr);
}
}
diff --git a/stack/gatt/gatt_attr.cc b/stack/gatt/gatt_attr.cc
index 21058de5a..1acfd81c9 100644
--- a/stack/gatt/gatt_attr.cc
+++ b/stack/gatt/gatt_attr.cc
@@ -23,40 +23,26 @@
*
******************************************************************************/
-#include <map>
-
-#include "base/callback.h"
#include "bt_target.h"
#include "bt_utils.h"
-#include "btif/include/btif_storage.h"
-#include "eatt/eatt.h"
+
#include "gatt_api.h"
#include "gatt_int.h"
-#include "gd/common/init_flags.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
using base::StringPrintf;
using bluetooth::Uuid;
-#define BLE_GATT_SVR_SUP_FEAT_EATT_BITMASK 0x01
-
-#define BLE_GATT_CL_SUP_FEAT_CACHING_BITMASK 0x01
-#define BLE_GATT_CL_SUP_FEAT_EATT_BITMASK 0x02
-#define BLE_GATT_CL_SUP_FEAT_MULTI_NOTIF_BITMASK 0x04
-
-#define BLE_GATT_CL_ANDROID_SUP_FEAT \
- (BLE_GATT_CL_SUP_FEAT_EATT_BITMASK | BLE_GATT_CL_SUP_FEAT_MULTI_NOTIF_BITMASK)
+#define GATTP_MAX_NUM_INC_SVR 0
+#define GATTP_MAX_CHAR_NUM 2
+#define GATTP_MAX_ATTR_NUM (GATTP_MAX_CHAR_NUM * 2 + GATTP_MAX_NUM_INC_SVR + 1)
+#define GATTP_MAX_CHAR_VALUE_SIZE 50
-using gatt_sr_supported_feat_cb =
- base::OnceCallback<void(const RawAddress&, uint8_t)>;
-
-typedef struct {
- uint16_t op_uuid;
- gatt_sr_supported_feat_cb cb;
-} gatt_op_cb_data;
-
-static std::map<uint16_t, gatt_op_cb_data> OngoingOps;
+#ifndef GATTP_ATTR_DB_SIZE
+#define GATTP_ATTR_DB_SIZE \
+ GATT_DB_MEM_SIZE(GATTP_MAX_NUM_INC_SVR, GATTP_MAX_CHAR_NUM, \
+ GATTP_MAX_CHAR_VALUE_SIZE)
+#endif
static void gatt_request_cback(uint16_t conn_id, uint32_t trans_id,
uint8_t op_code, tGATTS_DATA* p_data);
@@ -68,30 +54,22 @@ static void gatt_disc_res_cback(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
tGATT_DISC_RES* p_data);
static void gatt_disc_cmpl_cback(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
tGATT_STATUS status);
-static void gatt_cl_op_cmpl_cback(uint16_t conn_id, tGATTC_OPTYPE op,
- tGATT_STATUS status,
- tGATT_CL_COMPLETE* p_data);
+static void gatt_cl_op_cmpl_cback(UNUSED_ATTR uint16_t conn_id,
+ UNUSED_ATTR tGATTC_OPTYPE op,
+ UNUSED_ATTR tGATT_STATUS status,
+ UNUSED_ATTR tGATT_CL_COMPLETE* p_data);
static void gatt_cl_start_config_ccc(tGATT_PROFILE_CLCB* p_clcb);
-static bool gatt_sr_is_robust_caching_enabled();
-
-static tGATT_STATUS gatt_sr_read_db_hash(uint16_t conn_id,
- tGATT_VALUE* p_value);
-static tGATT_STATUS gatt_sr_read_cl_supp_feat(uint16_t conn_id,
- tGATT_VALUE* p_value);
-static tGATT_STATUS gatt_sr_write_cl_supp_feat(uint16_t conn_id,
- tGATT_WRITE_REQ* p_data);
-
-static tGATT_CBACK gatt_profile_cback = {.p_conn_cb = gatt_connect_cback,
- .p_cmpl_cb = gatt_cl_op_cmpl_cback,
- .p_disc_res_cb = gatt_disc_res_cback,
- .p_disc_cmpl_cb = gatt_disc_cmpl_cback,
- .p_req_cb = gatt_request_cback,
- .p_enc_cmpl_cb = nullptr,
- .p_congestion_cb = nullptr,
- .p_phy_update_cb = nullptr,
- .p_conn_update_cb = nullptr};
+static tGATT_CBACK gatt_profile_cback = {gatt_connect_cback,
+ gatt_cl_op_cmpl_cback,
+ gatt_disc_res_cback,
+ gatt_disc_cmpl_cback,
+ gatt_request_cback,
+ NULL,
+ NULL,
+ NULL,
+ NULL};
/*******************************************************************************
*
@@ -204,74 +182,6 @@ void gatt_profile_clcb_dealloc(tGATT_PROFILE_CLCB* p_clcb) {
memset(p_clcb, 0, sizeof(tGATT_PROFILE_CLCB));
}
-/** GAP Attributes Database Request callback */
-tGATT_STATUS read_attr_value(uint16_t conn_id, uint16_t handle,
- tGATT_VALUE* p_value, bool is_long) {
- uint8_t* p = p_value->value;
-
- if (handle == gatt_cb.handle_sr_supported_feat) {
- /* GATT_UUID_SERVER_SUP_FEAT*/
- if (is_long) return GATT_NOT_LONG;
-
- UINT8_TO_STREAM(p, gatt_cb.gatt_svr_supported_feat_mask);
- p_value->len = sizeof(gatt_cb.gatt_svr_supported_feat_mask);
- return GATT_SUCCESS;
- }
-
- if (handle == gatt_cb.handle_cl_supported_feat) {
- /*GATT_UUID_CLIENT_SUP_FEAT */
- if (is_long) return GATT_NOT_LONG;
-
- return gatt_sr_read_cl_supp_feat(conn_id, p_value);
- }
-
- if (handle == gatt_cb.handle_of_database_hash) {
- /* GATT_UUID_DATABASE_HASH */
- if (is_long) return GATT_NOT_LONG;
-
- return gatt_sr_read_db_hash(conn_id, p_value);
- }
-
- if (handle == gatt_cb.handle_of_h_r) {
- /* GATT_UUID_GATT_SRV_CHGD */
- return GATT_READ_NOT_PERMIT;
- }
-
- return GATT_NOT_FOUND;
-}
-
-/** GAP Attributes Database Read/Read Blob Request process */
-tGATT_STATUS proc_read_req(uint16_t conn_id, tGATTS_REQ_TYPE,
- tGATT_READ_REQ* p_data, tGATTS_RSP* p_rsp) {
- if (p_data->is_long) p_rsp->attr_value.offset = p_data->offset;
-
- p_rsp->attr_value.handle = p_data->handle;
-
- return read_attr_value(conn_id, p_data->handle, &p_rsp->attr_value,
- p_data->is_long);
-}
-
-/** GAP ATT server process a write request */
-tGATT_STATUS proc_write_req(uint16_t conn_id, tGATTS_REQ_TYPE,
- tGATT_WRITE_REQ* p_data) {
- uint16_t handle = p_data->handle;
-
- /* GATT_UUID_SERVER_SUP_FEAT*/
- if (handle == gatt_cb.handle_sr_supported_feat) return GATT_WRITE_NOT_PERMIT;
-
- /* GATT_UUID_CLIENT_SUP_FEAT*/
- if (handle == gatt_cb.handle_cl_supported_feat)
- return gatt_sr_write_cl_supp_feat(conn_id, p_data);
-
- /* GATT_UUID_DATABASE_HASH */
- if (handle == gatt_cb.handle_of_database_hash) return GATT_WRITE_NOT_PERMIT;
-
- /* GATT_UUID_GATT_SRV_CHGD */
- if (handle == gatt_cb.handle_of_h_r) return GATT_WRITE_NOT_PERMIT;
-
- return GATT_NOT_FOUND;
-}
-
/*******************************************************************************
*
* Function gatt_request_cback
@@ -283,30 +193,32 @@ tGATT_STATUS proc_write_req(uint16_t conn_id, tGATTS_REQ_TYPE,
******************************************************************************/
static void gatt_request_cback(uint16_t conn_id, uint32_t trans_id,
tGATTS_REQ_TYPE type, tGATTS_DATA* p_data) {
- tGATT_STATUS status = GATT_INVALID_PDU;
+ uint8_t status = GATT_INVALID_PDU;
tGATTS_RSP rsp_msg;
- bool rsp_needed = true;
+ bool ignore = false;
memset(&rsp_msg, 0, sizeof(tGATTS_RSP));
switch (type) {
case GATTS_REQ_TYPE_READ_CHARACTERISTIC:
case GATTS_REQ_TYPE_READ_DESCRIPTOR:
- status = proc_read_req(conn_id, type, &p_data->read_req, &rsp_msg);
+ status = GATT_READ_NOT_PERMIT;
break;
case GATTS_REQ_TYPE_WRITE_CHARACTERISTIC:
case GATTS_REQ_TYPE_WRITE_DESCRIPTOR:
+ status = GATT_WRITE_NOT_PERMIT;
+ break;
+
case GATTS_REQ_TYPE_WRITE_EXEC:
case GATT_CMD_WRITE:
- if (!p_data->write_req.need_rsp) rsp_needed = false;
-
- status = proc_write_req(conn_id, type, &p_data->write_req);
+ ignore = true;
+ VLOG(1) << "Ignore GATT_REQ_EXEC_WRITE/WRITE_CMD";
break;
case GATTS_REQ_TYPE_MTU:
VLOG(1) << "Get MTU exchange new mtu size: " << +p_data->mtu;
- rsp_needed = false;
+ ignore = true;
break;
default:
@@ -314,7 +226,7 @@ static void gatt_request_cback(uint16_t conn_id, uint32_t trans_id,
break;
}
- if (rsp_needed) GATTS_SendRsp(conn_id, trans_id, status, &rsp_msg);
+ if (!ignore) GATTS_SendRsp(conn_id, trans_id, status, &rsp_msg);
}
/*******************************************************************************
@@ -331,14 +243,7 @@ static void gatt_connect_cback(UNUSED_ATTR tGATT_IF gatt_if,
bool connected, tGATT_DISCONN_REASON reason,
tBT_TRANSPORT transport) {
VLOG(1) << __func__ << ": from " << bda << " connected: " << connected
- << ", conn_id: " << loghex(conn_id);
-
- // if the device is not trusted, remove data when the link is disconnected
- if (!connected && !btm_sec_is_a_bonded_dev(bda)) {
- LOG(INFO) << __func__ << ": remove untrusted client status, bda=" << bda;
- btif_storage_remove_gatt_cl_supp_feat(bda);
- btif_storage_remove_gatt_cl_db_hash(bda);
- }
+ << ", conn_id: " << loghex(conn_id) << "reason: " << loghex(reason);
tGATT_PROFILE_CLCB* p_clcb =
gatt_profile_find_clcb_by_bd_addr(bda, transport);
@@ -372,16 +277,12 @@ void gatt_profile_db_init(void) {
tmp.fill(0x81);
/* Create a GATT profile service */
- gatt_cb.gatt_if = GATT_Register(Uuid::From128BitBE(tmp), "GattProfileDb",
- &gatt_profile_cback, false);
+ gatt_cb.gatt_if = GATT_Register(Uuid::From128BitBE(tmp), &gatt_profile_cback);
GATT_StartIf(gatt_cb.gatt_if);
Uuid service_uuid = Uuid::From16Bit(UUID_SERVCLASS_GATT_SERVER);
- Uuid srv_changed_char_uuid = Uuid::From16Bit(GATT_UUID_GATT_SRV_CHGD);
- Uuid svr_sup_feat_uuid = Uuid::From16Bit(GATT_UUID_SERVER_SUP_FEAT);
- Uuid cl_sup_feat_uuid = Uuid::From16Bit(GATT_UUID_CLIENT_SUP_FEAT);
- Uuid database_hash_uuid = Uuid::From16Bit(GATT_UUID_DATABASE_HASH);
+ Uuid char_uuid = Uuid::From16Bit(GATT_UUID_GATT_SRV_CHGD);
btgatt_db_element_t service[] = {
{
@@ -389,28 +290,10 @@ void gatt_profile_db_init(void) {
.type = BTGATT_DB_PRIMARY_SERVICE,
},
{
- .uuid = srv_changed_char_uuid,
+ .uuid = char_uuid,
.type = BTGATT_DB_CHARACTERISTIC,
.properties = GATT_CHAR_PROP_BIT_INDICATE,
.permissions = 0,
- },
- {
- .type = BTGATT_DB_CHARACTERISTIC,
- .uuid = svr_sup_feat_uuid,
- .properties = GATT_CHAR_PROP_BIT_READ,
- .permissions = GATT_PERM_READ,
- },
- {
- .type = BTGATT_DB_CHARACTERISTIC,
- .uuid = cl_sup_feat_uuid,
- .properties = GATT_CHAR_PROP_BIT_READ | GATT_CHAR_PROP_BIT_WRITE,
- .permissions = GATT_PERM_READ | GATT_PERM_WRITE,
- },
- {
- .uuid = database_hash_uuid,
- .type = BTGATT_DB_CHARACTERISTIC,
- .properties = GATT_CHAR_PROP_BIT_READ,
- .permissions = GATT_PERM_READ,
}};
GATTS_AddService(gatt_cb.gatt_if, service,
@@ -418,17 +301,8 @@ void gatt_profile_db_init(void) {
service_handle = service[0].attribute_handle;
gatt_cb.handle_of_h_r = service[1].attribute_handle;
- gatt_cb.handle_sr_supported_feat = service[2].attribute_handle;
- gatt_cb.handle_cl_supported_feat = service[3].attribute_handle;
- gatt_cb.handle_of_database_hash = service[4].attribute_handle;
- gatt_cb.gatt_svr_supported_feat_mask |= BLE_GATT_SVR_SUP_FEAT_EATT_BITMASK;
- gatt_cb.gatt_cl_supported_feat_mask |= BLE_GATT_CL_ANDROID_SUP_FEAT;
-
- if (gatt_sr_is_robust_caching_enabled())
- gatt_cb.gatt_cl_supported_feat_mask |= BLE_GATT_CL_SUP_FEAT_CACHING_BITMASK;
-
- VLOG(1) << __func__ << ": gatt_if=" << gatt_cb.gatt_if << " EATT supported";
+ VLOG(1) << __func__ << ": gatt_if=" << +gatt_cb.gatt_if;
}
/*******************************************************************************
@@ -463,12 +337,6 @@ static void gatt_disc_res_cback(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
p_clcb->ccc_result++;
}
break;
-
- case GATT_DISC_SRVC_ALL:
- case GATT_DISC_INC_SRVC:
- case GATT_DISC_MAX:
- LOG_ERROR("Illegal discovery item handled");
- break;
}
}
@@ -484,18 +352,12 @@ static void gatt_disc_res_cback(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
static void gatt_disc_cmpl_cback(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
tGATT_STATUS status) {
tGATT_PROFILE_CLCB* p_clcb = gatt_profile_find_clcb_by_conn_id(conn_id);
- if (p_clcb == NULL) {
- LOG_WARN("Unable to find gatt profile after discovery complete");
- return;
- }
- if (status != GATT_SUCCESS) {
- LOG_WARN("Gatt discovery completed with errors status:%u", status);
- return;
- }
- if (p_clcb->ccc_result == 0) {
- LOG_WARN("Gatt discovery completed but connection was idle id:%hu",
- conn_id);
+ if (p_clcb == NULL) return;
+
+ if (status != GATT_SUCCESS || p_clcb->ccc_result == 0) {
+ LOG(WARNING) << __func__
+ << ": Unable to register for service changed indication";
return;
}
@@ -504,49 +366,6 @@ static void gatt_disc_cmpl_cback(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
gatt_cl_start_config_ccc(p_clcb);
}
-static bool gatt_svc_read_cl_supp_feat_req(uint16_t conn_id,
- gatt_op_cb_data* cb) {
- tGATT_READ_PARAM param;
-
- memset(&param, 0, sizeof(tGATT_READ_PARAM));
-
- param.service.s_handle = 1;
- param.service.e_handle = 0xFFFF;
- param.service.auth_req = 0;
-
- param.service.uuid = bluetooth::Uuid::From16Bit(GATT_UUID_CLIENT_SUP_FEAT);
-
- tGATT_STATUS status = GATTC_Read(conn_id, GATT_READ_BY_TYPE, &param);
- if (status != GATT_SUCCESS) {
- LOG(ERROR) << __func__ << " Read failed. Status: "
- << loghex(static_cast<uint8_t>(status));
- return false;
- }
-
- cb->op_uuid = GATT_UUID_CLIENT_SUP_FEAT;
- return true;
-}
-
-static bool gatt_att_write_cl_supp_feat(uint16_t conn_id, uint16_t handle) {
- tGATT_VALUE attr;
-
- memset(&attr, 0, sizeof(tGATT_VALUE));
-
- attr.conn_id = conn_id;
- attr.handle = handle;
- attr.len = 1;
- attr.value[0] = gatt_cb.gatt_cl_supported_feat_mask;
-
- tGATT_STATUS status = GATTC_Write(conn_id, GATT_WRITE, &attr);
- if (status != GATT_SUCCESS) {
- LOG(ERROR) << __func__ << " Write failed. Status: "
- << loghex(static_cast<uint8_t>(status));
- return false;
- }
-
- return true;
-}
-
/*******************************************************************************
*
* Function gatt_cl_op_cmpl_cback
@@ -556,76 +375,10 @@ static bool gatt_att_write_cl_supp_feat(uint16_t conn_id, uint16_t handle) {
* Returns void
*
******************************************************************************/
-static void gatt_cl_op_cmpl_cback(uint16_t conn_id, tGATTC_OPTYPE op,
- tGATT_STATUS status,
- tGATT_CL_COMPLETE* p_data) {
- auto iter = OngoingOps.find(conn_id);
-
- VLOG(1) << __func__ << " opcode: " << loghex(static_cast<uint8_t>(op))
- << " status: " << status
- << " conn id: " << loghex(static_cast<uint8_t>(conn_id));
-
- if (op != GATTC_OPTYPE_READ) return;
-
- if (iter == OngoingOps.end()) {
- LOG(ERROR) << __func__ << " Unexpected read complete";
- return;
- }
-
- gatt_op_cb_data* operation_callback_data = &iter->second;
- uint16_t cl_op_uuid = operation_callback_data->op_uuid;
- operation_callback_data->op_uuid = 0;
-
- uint8_t* pp = p_data->att_value.value;
-
- VLOG(1) << __func__ << " cl_op_uuid " << loghex(cl_op_uuid);
-
- switch (cl_op_uuid) {
- case GATT_UUID_SERVER_SUP_FEAT: {
- uint8_t tcb_idx = GATT_GET_TCB_IDX(conn_id);
- tGATT_TCB& tcb = gatt_cb.tcb[tcb_idx];
-
- /* Check if EATT is supported */
- if (status == GATT_SUCCESS) {
- STREAM_TO_UINT8(tcb.sr_supp_feat, pp);
- btif_storage_set_gatt_sr_supp_feat(tcb.peer_bda, tcb.sr_supp_feat);
- }
-
- /* Notify user about the supported features */
- std::move(operation_callback_data->cb)
- .Run(tcb.peer_bda, tcb.sr_supp_feat);
-
- /* If server supports EATT lets try to find handle for the
- * client supported features characteristic, where we could write
- * our supported features as a client.
- */
- if (tcb.sr_supp_feat & BLE_GATT_SVR_SUP_FEAT_EATT_BITMASK) {
- /* If read succeed, return here */
- if (gatt_svc_read_cl_supp_feat_req(conn_id, operation_callback_data))
- return;
- }
-
- /* Could not read client supported charcteristic or eatt is not
- * supported. Erase callback data now.
- */
- OngoingOps.erase(iter);
- break;
- }
- case GATT_UUID_CLIENT_SUP_FEAT:
- /*We don't need callback data anymore */
- OngoingOps.erase(iter);
-
- if (status != GATT_SUCCESS) {
- LOG(INFO) << __func__
- << " Client supported features charcteristic not found";
- return;
- }
-
- /* Write our client supported features to the remote device */
- gatt_att_write_cl_supp_feat(conn_id, p_data->att_value.handle);
- break;
- }
-}
+static void gatt_cl_op_cmpl_cback(UNUSED_ATTR uint16_t conn_id,
+ UNUSED_ATTR tGATTC_OPTYPE op,
+ UNUSED_ATTR tGATT_STATUS status,
+ UNUSED_ATTR tGATT_CL_COMPLETE* p_data) {}
/*******************************************************************************
*
@@ -704,318 +457,3 @@ void GATT_ConfigServiceChangeCCC(const RawAddress& remote_bda, bool enable,
p_clcb->ccc_stage++;
gatt_cl_start_config_ccc(p_clcb);
}
-
-/*******************************************************************************
- *
- * Function gatt_cl_init_sr_status
- *
- * Description Restore status for trusted GATT Server device
- *
- * Returns none
- *
- ******************************************************************************/
-void gatt_cl_init_sr_status(tGATT_TCB& tcb) {
- tcb.sr_supp_feat = btif_storage_get_sr_supp_feat(tcb.peer_bda);
-
- if (tcb.sr_supp_feat & BLE_GATT_SVR_SUP_FEAT_EATT_BITMASK)
- bluetooth::eatt::EattExtension::AddFromStorage(tcb.peer_bda);
-}
-
-/*******************************************************************************
- *
- * Function gatt_cl_read_sr_supp_feat_req
- *
- * Description Read remote device supported GATT feature mask.
- *
- * Returns bool
- *
- ******************************************************************************/
-bool gatt_cl_read_sr_supp_feat_req(
- const RawAddress& peer_bda,
- base::OnceCallback<void(const RawAddress&, uint8_t)> cb) {
- tGATT_PROFILE_CLCB* p_clcb;
- tGATT_READ_PARAM param;
- uint16_t conn_id;
-
- if (!cb) return false;
-
- VLOG(1) << __func__ << " BDA: " << peer_bda
- << " read gatt supported features";
-
- GATT_GetConnIdIfConnected(gatt_cb.gatt_if, peer_bda, &conn_id,
- BT_TRANSPORT_LE);
- if (conn_id == GATT_INVALID_CONN_ID) return false;
-
- p_clcb = gatt_profile_find_clcb_by_conn_id(conn_id);
- if (!p_clcb) {
- p_clcb = gatt_profile_clcb_alloc(conn_id, peer_bda, BT_TRANSPORT_LE);
- }
-
- if (!p_clcb) {
- VLOG(1) << __func__ << " p_clcb is NULL " << loghex(conn_id);
- return false;
- }
-
- auto it = OngoingOps.find(conn_id);
- if (it != OngoingOps.end()) {
- LOG(ERROR) << __func__ << " There is ongoing operation for conn_id: "
- << loghex(conn_id);
- return false;
- }
-
- memset(&param, 0, sizeof(tGATT_READ_PARAM));
-
- param.service.s_handle = 1;
- param.service.e_handle = 0xFFFF;
- param.service.auth_req = 0;
-
- param.service.uuid = bluetooth::Uuid::From16Bit(GATT_UUID_SERVER_SUP_FEAT);
-
- if (GATTC_Read(conn_id, GATT_READ_BY_TYPE, &param) != GATT_SUCCESS) {
- LOG(ERROR) << __func__ << " Read GATT Support features GATT_Read Failed";
- return false;
- }
-
- gatt_op_cb_data cb_data;
- cb_data.cb = std::move(cb);
- cb_data.op_uuid = GATT_UUID_SERVER_SUP_FEAT;
- OngoingOps[conn_id] = std::move(cb_data);
-
- return true;
-}
-
-/*******************************************************************************
- *
- * Function gatt_profile_get_eatt_support
- *
- * Description Check if EATT is supported with remote device.
- *
- * Returns if EATT is supported.
- *
- ******************************************************************************/
-bool gatt_profile_get_eatt_support(const RawAddress& remote_bda) {
- uint16_t conn_id;
-
- VLOG(1) << __func__ << " BDA: " << remote_bda << " read GATT support";
-
- GATT_GetConnIdIfConnected(gatt_cb.gatt_if, remote_bda, &conn_id,
- BT_TRANSPORT_LE);
-
- /* This read is important only when connected */
- if (conn_id == GATT_INVALID_CONN_ID) return false;
-
- /* Get tcb info */
- uint8_t tcb_idx = GATT_GET_TCB_IDX(conn_id);
- tGATT_TCB& tcb = gatt_cb.tcb[tcb_idx];
- return tcb.sr_supp_feat & BLE_GATT_SVR_SUP_FEAT_EATT_BITMASK;
-}
-
-/*******************************************************************************
- *
- * Function gatt_sr_is_robust_caching_enabled
- *
- * Description Check if Robust Caching is enabled on server side.
- *
- * Returns true if enabled in gd flag, otherwise false
- *
- ******************************************************************************/
-static bool gatt_sr_is_robust_caching_enabled() {
- return bluetooth::common::init_flags::gatt_robust_caching_is_enabled();
-}
-
-/*******************************************************************************
- *
- * Function gatt_sr_is_cl_robust_caching_supported
- *
- * Description Check if Robust Caching is supported for the connection
- *
- * Returns true if enabled by client side, otherwise false
- *
- ******************************************************************************/
-static bool gatt_sr_is_cl_robust_caching_supported(tGATT_TCB& tcb) {
- // if robust caching is not enabled, should always return false
- if (!gatt_sr_is_robust_caching_enabled()) return false;
- return (tcb.cl_supp_feat & BLE_GATT_CL_SUP_FEAT_CACHING_BITMASK);
-}
-
-/*******************************************************************************
- *
- * Function gatt_sr_is_cl_change_aware
- *
- * Description Check if the connection is change-aware
- *
- * Returns true if change aware, otherwise false
- *
- ******************************************************************************/
-bool gatt_sr_is_cl_change_aware(tGATT_TCB& tcb) {
- // if robust caching is not supported, should always return true by default
- if (!gatt_sr_is_cl_robust_caching_supported(tcb)) return true;
- return tcb.is_robust_cache_change_aware;
-}
-
-/*******************************************************************************
- *
- * Function gatt_sr_init_cl_status
- *
- * Description Restore status for trusted device
- *
- * Returns none
- *
- ******************************************************************************/
-void gatt_sr_init_cl_status(tGATT_TCB& tcb) {
- tcb.cl_supp_feat = btif_storage_get_gatt_cl_supp_feat(tcb.peer_bda);
- // This is used to reset bit when robust caching is disabled
- if (!gatt_sr_is_robust_caching_enabled()) {
- tcb.cl_supp_feat &= ~BLE_GATT_CL_SUP_FEAT_CACHING_BITMASK;
- }
-
- if (gatt_sr_is_cl_robust_caching_supported(tcb)) {
- Octet16 stored_hash = btif_storage_get_gatt_cl_db_hash(tcb.peer_bda);
- tcb.is_robust_cache_change_aware = (stored_hash == gatt_cb.database_hash);
- } else {
- // set default value for untrusted device
- tcb.is_robust_cache_change_aware = true;
- }
-
- LOG(INFO) << __func__ << ": bda=" << tcb.peer_bda
- << ", cl_supp_feat=" << loghex(tcb.cl_supp_feat)
- << ", aware=" << tcb.is_robust_cache_change_aware;
-}
-
-/*******************************************************************************
- *
- * Function gatt_sr_update_cl_status
- *
- * Description Update change-aware status for the remote device
- *
- * Returns none
- *
- ******************************************************************************/
-void gatt_sr_update_cl_status(tGATT_TCB& tcb, bool chg_aware) {
- // if robust caching is not supported, do nothing
- if (!gatt_sr_is_cl_robust_caching_supported(tcb)) return;
-
- // only when client status is changed from change-unaware to change-aware, we
- // can then store database hash into btif_storage
- if (!tcb.is_robust_cache_change_aware && chg_aware) {
- btif_storage_set_gatt_cl_db_hash(tcb.peer_bda, gatt_cb.database_hash);
- }
-
- // only when the status is changed, print the log
- if (tcb.is_robust_cache_change_aware != chg_aware) {
- LOG(INFO) << __func__ << ": bda=" << tcb.peer_bda
- << ", chg_aware=" << chg_aware;
- }
-
- tcb.is_robust_cache_change_aware = chg_aware;
-}
-
-/* handle request for reading database hash */
-static tGATT_STATUS gatt_sr_read_db_hash(uint16_t conn_id,
- tGATT_VALUE* p_value) {
- LOG(INFO) << __func__ << ": conn_id=" << loghex(conn_id);
-
- uint8_t* p = p_value->value;
- Octet16& db_hash = gatt_cb.database_hash;
- ARRAY_TO_STREAM(p, db_hash.data(), (uint16_t)db_hash.size());
- p_value->len = (uint16_t)db_hash.size();
-
- // Every time when database hash is requested, reset flag.
- uint8_t tcb_idx = GATT_GET_TCB_IDX(conn_id);
- gatt_sr_update_cl_status(gatt_cb.tcb[tcb_idx], /* chg_aware= */ true);
- return GATT_SUCCESS;
-}
-
-/* handle request for reading client supported features */
-static tGATT_STATUS gatt_sr_read_cl_supp_feat(uint16_t conn_id,
- tGATT_VALUE* p_value) {
- // Get tcb info
- uint8_t tcb_idx = GATT_GET_TCB_IDX(conn_id);
- tGATT_TCB& tcb = gatt_cb.tcb[tcb_idx];
-
- uint8_t* p = p_value->value;
- UINT8_TO_STREAM(p, tcb.cl_supp_feat);
- p_value->len = 1;
-
- return GATT_SUCCESS;
-}
-
-/* handle request for writing client supported features */
-static tGATT_STATUS gatt_sr_write_cl_supp_feat(uint16_t conn_id,
- tGATT_WRITE_REQ* p_data) {
- std::list<uint8_t> tmp;
- uint16_t len = p_data->len;
- uint8_t value, *p = p_data->value;
- // Read all octets into list
- while (len > 0) {
- STREAM_TO_UINT8(value, p);
- tmp.push_back(value);
- len--;
- }
- // Remove trailing zero octets
- while (!tmp.empty()) {
- if (tmp.back() != 0x00) break;
- tmp.pop_back();
- }
-
- // Get tcb info
- uint8_t tcb_idx = GATT_GET_TCB_IDX(conn_id);
- tGATT_TCB& tcb = gatt_cb.tcb[tcb_idx];
-
- std::list<uint8_t> feature_list;
- feature_list.push_back(tcb.cl_supp_feat);
-
- // If input length is zero, return value_not_allowed
- if (tmp.empty()) {
- LOG(INFO) << __func__ << ": zero length, conn_id=" << loghex(conn_id)
- << ", bda=" << tcb.peer_bda;
- return GATT_VALUE_NOT_ALLOWED;
- }
- // if original length is longer than new one, it must be the bit reset case.
- if (feature_list.size() > tmp.size()) {
- LOG(INFO) << __func__ << ": shorter length, conn_id=" << loghex(conn_id)
- << ", bda=" << tcb.peer_bda;
- return GATT_VALUE_NOT_ALLOWED;
- }
- // new length is longer or equals to the original, need to check bits
- // one by one. Here we use bit-wise operation.
- // 1. Use XOR to locate the change bit, val_xor is the change bit mask
- // 2. Use AND for val_xor and *it_new to get val_and
- // 3. If val_and != val_xor, it means the change is from 1 to 0
- auto it_old = feature_list.cbegin();
- auto it_new = tmp.cbegin();
- for (; it_old != feature_list.cend(); it_old++, it_new++) {
- uint8_t val_xor = *it_old ^ *it_new;
- uint8_t val_and = val_xor & *it_new;
- if (val_and != val_xor) {
- LOG(INFO) << __func__
- << ": bit cannot be reset, conn_id=" << loghex(conn_id)
- << ", bda=" << tcb.peer_bda;
- return GATT_VALUE_NOT_ALLOWED;
- }
- }
-
- // get current robust caching status before setting new one
- bool curr_caching_state = gatt_sr_is_cl_robust_caching_supported(tcb);
-
- tcb.cl_supp_feat = tmp.front();
- if (!gatt_sr_is_robust_caching_enabled()) {
- // remove robust caching bit
- tcb.cl_supp_feat &= ~BLE_GATT_CL_SUP_FEAT_CACHING_BITMASK;
- LOG(INFO) << __func__
- << ": reset robust caching bit, conn_id=" << loghex(conn_id)
- << ", bda=" << tcb.peer_bda;
- }
- // TODO(hylo): save data as byte array
- btif_storage_set_gatt_cl_supp_feat(tcb.peer_bda, tcb.cl_supp_feat);
-
- // get new robust caching status after setting new one
- bool new_caching_state = gatt_sr_is_cl_robust_caching_supported(tcb);
- // only when the first time robust caching request, print the log
- if (!curr_caching_state && new_caching_state) {
- LOG(INFO) << __func__ << ": robust caching enabled by client"
- << ", conn_id=" << loghex(conn_id);
- }
-
- return GATT_SUCCESS;
-}
diff --git a/stack/gatt/gatt_auth.cc b/stack/gatt/gatt_auth.cc
index c27ba61da..ba44c713f 100644
--- a/stack/gatt/gatt_auth.cc
+++ b/stack/gatt/gatt_auth.cc
@@ -27,13 +27,10 @@
#include <string.h>
#include "bt_common.h"
+#include "btm_int.h"
#include "gatt_api.h"
#include "gatt_int.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_ble_int_types.h"
-#include "stack/btm/btm_int.h"
-#include "stack/btm/btm_sec.h"
using base::StringPrintf;
@@ -96,7 +93,7 @@ static bool gatt_sign_data(tGATT_CLCB* p_clcb) {
* Returns
*
******************************************************************************/
-void gatt_verify_signature(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_buf) {
+void gatt_verify_signature(tGATT_TCB& tcb, BT_HDR* p_buf) {
uint16_t cmd_len;
uint8_t op_code;
uint8_t *p, *p_orig = (uint8_t*)(p_buf + 1) + p_buf->offset;
@@ -118,7 +115,7 @@ void gatt_verify_signature(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_buf) {
}
STREAM_TO_UINT8(op_code, p_orig);
- gatt_server_handle_client_req(tcb, cid, op_code, (uint16_t)(p_buf->len - 1),
+ gatt_server_handle_client_req(tcb, op_code, (uint16_t)(p_buf->len - 1),
p_orig);
}
/*******************************************************************************
@@ -177,7 +174,12 @@ void gatt_enc_cmpl_cback(const RawAddress* bd_addr, tBT_TRANSPORT transport,
bool status = false;
if (result == BTM_SUCCESS) {
if (gatt_get_sec_act(p_tcb) == GATT_SEC_ENCRYPT_MITM) {
- status = BTM_IsLinkKeyAuthed(*bd_addr, transport);
+ uint8_t sec_flag = 0;
+ BTM_GetSecurityFlagsByTransport(*bd_addr, &sec_flag, transport);
+
+ if (sec_flag & BTM_SEC_FLAG_LKEY_AUTHED) {
+ status = true;
+ }
} else {
status = true;
}
@@ -268,27 +270,33 @@ tGATT_SEC_ACTION gatt_get_sec_act(tGATT_TCB* p_tcb) {
*/
tGATT_SEC_ACTION gatt_determine_sec_act(tGATT_CLCB* p_clcb) {
tGATT_SEC_ACTION act = GATT_SEC_OK;
+ uint8_t sec_flag;
tGATT_TCB* p_tcb = p_clcb->p_tcb;
tGATT_AUTH_REQ auth_req = p_clcb->auth_req;
bool is_link_encrypted = false;
bool is_link_key_known = false;
bool is_key_mitm = false;
uint8_t key_type;
- tBTM_BLE_SEC_REQ_ACT sec_act = BTM_BLE_SEC_REQ_ACT_NONE;
+ tBTM_BLE_SEC_REQ_ACT sec_act = BTM_LE_SEC_NONE;
if (auth_req == GATT_AUTH_REQ_NONE) return act;
+ BTM_GetSecurityFlagsByTransport(p_tcb->peer_bda, &sec_flag,
+ p_clcb->p_tcb->transport);
+
btm_ble_link_sec_check(p_tcb->peer_bda, auth_req, &sec_act);
/* if a encryption is pending, need to wait */
if (sec_act == BTM_BLE_SEC_REQ_ACT_DISCARD && auth_req != GATT_AUTH_REQ_NONE)
return GATT_SEC_ENC_PENDING;
- is_link_key_known =
- BTM_IsLinkKeyKnown(p_tcb->peer_bda, p_clcb->p_tcb->transport);
- is_link_encrypted =
- BTM_IsEncrypted(p_tcb->peer_bda, p_clcb->p_tcb->transport);
- is_key_mitm = BTM_IsLinkKeyAuthed(p_tcb->peer_bda, p_clcb->p_tcb->transport);
+ if (sec_flag & (BTM_SEC_FLAG_ENCRYPTED | BTM_SEC_FLAG_LKEY_KNOWN)) {
+ if (sec_flag & BTM_SEC_FLAG_ENCRYPTED) is_link_encrypted = true;
+
+ is_link_key_known = true;
+
+ if (sec_flag & BTM_SEC_FLAG_LKEY_AUTHED) is_key_mitm = true;
+ }
/* first check link key upgrade required or not */
switch (auth_req) {
@@ -346,16 +354,15 @@ tGATT_SEC_ACTION gatt_determine_sec_act(tGATT_CLCB* p_clcb) {
******************************************************************************/
tGATT_STATUS gatt_get_link_encrypt_status(tGATT_TCB& tcb) {
tGATT_STATUS encrypt_status = GATT_NOT_ENCRYPTED;
+ uint8_t sec_flag = 0;
- bool encrypted = BTM_IsEncrypted(tcb.peer_bda, tcb.transport);
- bool link_key_known = BTM_IsLinkKeyKnown(tcb.peer_bda, tcb.transport);
- bool link_key_authed = BTM_IsLinkKeyAuthed(tcb.peer_bda, tcb.transport);
+ BTM_GetSecurityFlagsByTransport(tcb.peer_bda, &sec_flag, tcb.transport);
- if (encrypted && link_key_known) {
+ if ((sec_flag & BTM_SEC_FLAG_ENCRYPTED) &&
+ (sec_flag & BTM_SEC_FLAG_LKEY_KNOWN)) {
encrypt_status = GATT_ENCRYPED_NO_MITM;
- if (link_key_authed) {
+ if (sec_flag & BTM_SEC_FLAG_LKEY_AUTHED)
encrypt_status = GATT_ENCRYPED_MITM;
- }
}
VLOG(1) << StringPrintf("gatt_get_link_encrypt_status status=0x%x",
diff --git a/stack/gatt/gatt_cl.cc b/stack/gatt/gatt_cl.cc
index 8c3567d7a..842cb6c3e 100644
--- a/stack/gatt/gatt_cl.cc
+++ b/stack/gatt/gatt_cl.cc
@@ -22,18 +22,15 @@
*
******************************************************************************/
-#define LOG_TAG "bluetooth"
+#include "bt_target.h"
#include <string.h>
-
#include "bt_common.h"
-#include "bt_target.h"
#include "bt_utils.h"
#include "gatt_int.h"
-#include "l2c_api.h"
-#include "osi/include/log.h"
+#include "l2c_int.h"
+#include "log/log.h"
#include "osi/include/osi.h"
-#include "stack/eatt/eatt.h"
#define GATT_WRITE_LONG_HDR_SIZE 5 /* 1 opcode + 2 handle + 2 offset */
#define GATT_READ_CHAR_VALUE_HDL (GATT_READ_CHAR_VALUE | 0x80)
@@ -48,8 +45,6 @@
using base::StringPrintf;
using bluetooth::Uuid;
-using bluetooth::eatt::EattExtension;
-using bluetooth::eatt::EattChannel;
/*******************************************************************************
* G L O B A L G A T T D A T A *
@@ -87,7 +82,7 @@ void gatt_act_discovery(tGATT_CLCB* p_clcb) {
uint8_t op_code = disc_type_to_att_opcode[p_clcb->op_subtype];
if (p_clcb->s_handle > p_clcb->e_handle || p_clcb->s_handle == 0) {
- LOG_DEBUG("Completed GATT discovery of all handle ranges");
+ /* end of handle range */
gatt_end_operation(p_clcb, GATT_SUCCESS, NULL);
return;
}
@@ -128,7 +123,6 @@ void gatt_act_discovery(tGATT_CLCB* p_clcb) {
tGATT_STATUS st = attp_send_cl_msg(*p_clcb->p_tcb, p_clcb, op_code, &cl_req);
if (st != GATT_SUCCESS && st != GATT_CMD_STARTED) {
- LOG_WARN("Unable to send ATT message");
gatt_end_operation(p_clcb, GATT_ERROR, NULL);
}
}
@@ -144,7 +138,7 @@ void gatt_act_discovery(tGATT_CLCB* p_clcb) {
******************************************************************************/
void gatt_act_read(tGATT_CLCB* p_clcb, uint16_t offset) {
tGATT_TCB& tcb = *p_clcb->p_tcb;
- tGATT_STATUS rt = GATT_INTERNAL_ERROR;
+ uint8_t rt = GATT_INTERNAL_ERROR;
tGATT_CL_MSG msg;
uint8_t op_code = 0;
@@ -219,15 +213,13 @@ void gatt_act_write(tGATT_CLCB* p_clcb, uint8_t sec_act) {
CHECK(p_clcb->p_attr_buf);
tGATT_VALUE& attr = *((tGATT_VALUE*)p_clcb->p_attr_buf);
- uint16_t payload_size = gatt_tcb_get_payload_size_tx(tcb, p_clcb->cid);
-
switch (p_clcb->op_subtype) {
case GATT_WRITE_NO_RSP: {
p_clcb->s_handle = attr.handle;
uint8_t op_code = (sec_act == GATT_SEC_SIGN_DATA) ? GATT_SIGN_CMD_WRITE
: GATT_CMD_WRITE;
- tGATT_STATUS rt = gatt_send_write_msg(tcb, p_clcb, op_code, attr.handle,
- attr.len, 0, attr.value);
+ uint8_t rt = gatt_send_write_msg(tcb, p_clcb, op_code, attr.handle,
+ attr.len, 0, attr.value);
if (rt != GATT_CMD_STARTED) {
if (rt != GATT_SUCCESS) {
LOG(ERROR) << StringPrintf(
@@ -239,11 +231,11 @@ void gatt_act_write(tGATT_CLCB* p_clcb, uint8_t sec_act) {
}
case GATT_WRITE: {
- if (attr.len <= (payload_size - GATT_HDR_SIZE)) {
+ if (attr.len <= (tcb.payload_size - GATT_HDR_SIZE)) {
p_clcb->s_handle = attr.handle;
- tGATT_STATUS rt = gatt_send_write_msg(
- tcb, p_clcb, GATT_REQ_WRITE, attr.handle, attr.len, 0, attr.value);
+ uint8_t rt = gatt_send_write_msg(tcb, p_clcb, GATT_REQ_WRITE,
+ attr.handle, attr.len, 0, attr.value);
if (rt != GATT_SUCCESS && rt != GATT_CMD_STARTED &&
rt != GATT_CONGESTED) {
if (rt != GATT_SUCCESS) {
@@ -281,7 +273,7 @@ void gatt_act_write(tGATT_CLCB* p_clcb, uint8_t sec_act) {
******************************************************************************/
void gatt_send_queue_write_cancel(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
tGATT_EXEC_FLAG flag) {
- tGATT_STATUS rt;
+ uint8_t rt;
VLOG(1) << __func__;
@@ -340,10 +332,9 @@ void gatt_send_prepare_write(tGATT_TCB& tcb, tGATT_CLCB* p_clcb) {
VLOG(1) << __func__ << StringPrintf(" type=0x%x", type);
uint16_t to_send = p_attr->len - p_attr->offset;
- uint16_t payload_size = gatt_tcb_get_payload_size_tx(tcb, p_clcb->cid);
- if (to_send > (payload_size -
+ if (to_send > (tcb.payload_size -
GATT_WRITE_LONG_HDR_SIZE)) /* 2 = uint16_t offset bytes */
- to_send = payload_size - GATT_WRITE_LONG_HDR_SIZE;
+ to_send = tcb.payload_size - GATT_WRITE_LONG_HDR_SIZE;
p_clcb->s_handle = p_attr->handle;
@@ -354,10 +345,10 @@ void gatt_send_prepare_write(tGATT_TCB& tcb, tGATT_CLCB* p_clcb) {
VLOG(1) << StringPrintf("offset =0x%x len=%d", offset, to_send);
- tGATT_STATUS rt = gatt_send_write_msg(
- tcb, p_clcb, GATT_REQ_PREPARE_WRITE, p_attr->handle, to_send, /* length */
- offset, /* used as offset */
- p_attr->value + p_attr->offset); /* data */
+ uint8_t rt = gatt_send_write_msg(tcb, p_clcb, GATT_REQ_PREPARE_WRITE,
+ p_attr->handle, to_send, /* length */
+ offset, /* used as offset */
+ p_attr->value + p_attr->offset); /* data */
/* remember the write long attribute length */
p_clcb->counter = to_send;
@@ -401,9 +392,8 @@ void gatt_process_find_type_value_rsp(UNUSED_ATTR tGATT_TCB& tcb,
len -= 4;
if (p_clcb->p_reg->app_cb.p_disc_res_cb)
- (*p_clcb->p_reg->app_cb.p_disc_res_cb)(
- p_clcb->conn_id, static_cast<tGATT_DISC_TYPE>(p_clcb->op_subtype),
- &result);
+ (*p_clcb->p_reg->app_cb.p_disc_res_cb)(p_clcb->conn_id,
+ p_clcb->op_subtype, &result);
}
/* last handle + 1 */
@@ -459,9 +449,8 @@ void gatt_process_read_info_rsp(UNUSED_ATTR tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
len -= (uuid_len + 2);
if (p_clcb->p_reg->app_cb.p_disc_res_cb)
- (*p_clcb->p_reg->app_cb.p_disc_res_cb)(
- p_clcb->conn_id, static_cast<tGATT_DISC_TYPE>(p_clcb->op_subtype),
- &result);
+ (*p_clcb->p_reg->app_cb.p_disc_res_cb)(p_clcb->conn_id,
+ p_clcb->op_subtype, &result);
}
p_clcb->s_handle = (result.handle == 0) ? 0 : (result.handle + 1);
@@ -517,8 +506,7 @@ void gatt_proc_disc_error_rsp(UNUSED_ATTR tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
void gatt_process_error_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
UNUSED_ATTR uint8_t op_code,
UNUSED_ATTR uint16_t len, uint8_t* p_data) {
- uint8_t opcode, *p = p_data;
- uint8_t reason;
+ uint8_t opcode, reason, *p = p_data;
uint16_t handle;
tGATT_VALUE* p_attr = (tGATT_VALUE*)p_clcb->p_attr_buf;
@@ -535,7 +523,7 @@ void gatt_process_error_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
// specification, then the Error Response shall still be considered to state
// that the given request cannot be performed for an unknown reason."
opcode = handle = 0;
- reason = static_cast<tGATT_STATUS>(0x7f);
+ reason = 0x7F;
} else {
STREAM_TO_UINT8(opcode, p);
STREAM_TO_UINT16(handle, p);
@@ -543,14 +531,13 @@ void gatt_process_error_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
}
if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY) {
- gatt_proc_disc_error_rsp(tcb, p_clcb, opcode, handle,
- static_cast<tGATT_STATUS>(reason));
+ gatt_proc_disc_error_rsp(tcb, p_clcb, opcode, handle, reason);
} else {
if ((p_clcb->operation == GATTC_OPTYPE_WRITE) &&
(p_clcb->op_subtype == GATT_WRITE) &&
(opcode == GATT_REQ_PREPARE_WRITE) && (p_attr) &&
(handle == p_attr->handle)) {
- p_clcb->status = static_cast<tGATT_STATUS>(reason);
+ p_clcb->status = reason;
gatt_send_queue_write_cancel(tcb, p_clcb, GATT_PREP_WRITE_CANCEL);
} else if ((p_clcb->operation == GATTC_OPTYPE_READ) &&
((p_clcb->op_subtype == GATT_READ_CHAR_VALUE_HDL) ||
@@ -560,7 +547,7 @@ void gatt_process_error_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
(reason == GATT_NOT_LONG)) {
gatt_end_operation(p_clcb, GATT_SUCCESS, (void*)p_clcb->p_attr_buf);
} else
- gatt_end_operation(p_clcb, static_cast<tGATT_STATUS>(reason), NULL);
+ gatt_end_operation(p_clcb, reason, NULL);
}
}
/*******************************************************************************
@@ -582,8 +569,8 @@ void gatt_process_prep_write_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
.conn_id = p_clcb->conn_id, .auth_req = GATT_AUTH_REQ_NONE,
};
- VLOG(1) << StringPrintf("value resp op_code = %s len = %d",
- gatt_dbg_op_name(op_code), len);
+ LOG(ERROR) << StringPrintf("value resp op_code = %s len = %d",
+ gatt_dbg_op_name(op_code), len);
if (len < GATT_PREP_WRITE_RSP_MIN_LEN) {
LOG(ERROR) << "illegal prepare write response length, discard";
@@ -609,7 +596,6 @@ void gatt_process_prep_write_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
gatt_end_operation(p_clcb, p_clcb->status, &value);
}
}
-
/*******************************************************************************
*
* Function gatt_process_notification
@@ -619,66 +605,41 @@ void gatt_process_prep_write_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
* Returns void
*
******************************************************************************/
-void gatt_process_notification(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
- uint16_t len, uint8_t* p_data) {
- tGATT_VALUE value = {};
+void gatt_process_notification(tGATT_TCB& tcb, uint8_t op_code, uint16_t len,
+ uint8_t* p_data) {
+ tGATT_VALUE value;
tGATT_REG* p_reg;
uint16_t conn_id;
- tGATT_STATUS encrypt_status = {};
+ tGATT_STATUS encrypt_status;
uint8_t* p = p_data;
uint8_t i;
- tGATTC_OPTYPE event = (op_code == GATT_HANDLE_VALUE_IND)
- ? GATTC_OPTYPE_INDICATION
- : GATTC_OPTYPE_NOTIFICATION;
+ uint8_t event = (op_code == GATT_HANDLE_VALUE_NOTIF)
+ ? GATTC_OPTYPE_NOTIFICATION
+ : GATTC_OPTYPE_INDICATION;
VLOG(1) << __func__;
- // Ensure our packet has enough data (2 bytes)
if (len < GATT_NOTIFICATION_MIN_LEN) {
LOG(ERROR) << "illegal notification PDU length, discard";
return;
}
- // Get 2 byte handle
+ memset(&value, 0, sizeof(value));
STREAM_TO_UINT16(value.handle, p);
+ value.len = len - 2;
+ if (value.len > GATT_MAX_ATTR_LEN) {
+ LOG(ERROR) << "value.len larger than GATT_MAX_ATTR_LEN, discard";
+ return;
+ }
+ memcpy(value.value, p, value.len);
- // Fail early if the GATT handle is not valid
if (!GATT_HANDLE_IS_VALID(value.handle)) {
/* illegal handle, send ack now */
if (op_code == GATT_HANDLE_VALUE_IND)
- attp_send_cl_confirmation_msg(tcb, cid);
+ attp_send_cl_msg(tcb, nullptr, GATT_HANDLE_VALUE_CONF, NULL);
return;
}
- // Calculate value length based on opcode
- if (op_code == GATT_HANDLE_MULTI_VALUE_NOTIF) {
- // Ensure our packet has enough data; MIN + 2 more bytes for len value
- if (len < GATT_NOTIFICATION_MIN_LEN + 2) {
- LOG(ERROR) << "illegal notification PDU length, discard";
- return;
- }
-
- // Allow multi value opcode to set value len from the packet
- STREAM_TO_UINT16(value.len, p);
-
- if (value.len > len - 4) {
- LOG(ERROR) << "value.len (" << value.len << ") greater than length ("
- << (len - 4);
- return;
- }
-
- } else {
- // For single value, just use the passed in len minus opcode length (2)
- value.len = len - 2;
- }
-
- // Verify the new calculated length
- if (value.len > GATT_MAX_ATTR_LEN) {
- LOG(ERROR) << "value.len larger than GATT_MAX_ATTR_LEN, discard";
- return;
- }
-
- // Handle indications differently
if (event == GATTC_OPTYPE_INDICATION) {
if (tcb.ind_count) {
/* this is an error case that receiving an indication but we
@@ -689,34 +650,32 @@ void gatt_process_notification(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
LOG(ERROR) << __func__ << " rcv Ind. but ind_count=" << tcb.ind_count
<< " (will reset ind_count)";
}
-
- // Zero out the ind_count
tcb.ind_count = 0;
+ }
- // Notify all registered clients with the handle value
- // notification/indication
- // Note: need to do the indication count and start timer first then do
- // callback
- for (i = 0, p_reg = gatt_cb.cl_rcb; i < GATT_MAX_APPS; i++, p_reg++) {
- if (p_reg->in_use && p_reg->app_cb.p_cmpl_cb) tcb.ind_count++;
- }
+ /* should notify all registered client with the handle value
+ notificaion/indication
+ Note: need to do the indication count and start timer first then do
+ callback
+ */
+
+ for (i = 0, p_reg = gatt_cb.cl_rcb; i < GATT_MAX_APPS; i++, p_reg++) {
+ if (p_reg->in_use && p_reg->app_cb.p_cmpl_cb &&
+ (event == GATTC_OPTYPE_INDICATION))
+ tcb.ind_count++;
+ }
+ if (event == GATTC_OPTYPE_INDICATION) {
/* start a timer for app confirmation */
- if (tcb.ind_count > 0) {
- gatt_start_ind_ack_timer(tcb, cid);
- } else { /* no app to indicate, or invalid handle */
- attp_send_cl_confirmation_msg(tcb, cid);
- }
+ if (tcb.ind_count > 0)
+ gatt_start_ind_ack_timer(tcb);
+ else /* no app to indicate, or invalid handle */
+ attp_send_cl_msg(tcb, nullptr, GATT_HANDLE_VALUE_CONF, NULL);
}
encrypt_status = gatt_get_link_encrypt_status(tcb);
-
- STREAM_TO_ARRAY(value.value, p, value.len);
-
tGATT_CL_COMPLETE gatt_cl_complete;
gatt_cl_complete.att_value = value;
- gatt_cl_complete.cid = cid;
-
for (i = 0, p_reg = gatt_cb.cl_rcb; i < GATT_MAX_APPS; i++, p_reg++) {
if (p_reg->in_use && p_reg->app_cb.p_cmpl_cb) {
conn_id = GATT_CREATE_CONN_ID(tcb.tcb_idx, p_reg->gatt_if);
@@ -724,43 +683,6 @@ void gatt_process_notification(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
&gatt_cl_complete);
}
}
-
- // If this is single value, then nothing is left to do
- if (op_code != GATT_HANDLE_MULTI_VALUE_NOTIF) return;
-
- // Need a signed type to check if the value is below 0
- // as uint16_t doesn't have negatives so the negatives register as a number
- // thus anything less than zero won't trigger the conditional and it is not
- // always 0
- // when done looping as value.len is arbitrary.
- int16_t rem_len = (int16_t)len - (4 /* octets */ + value.len);
-
- // Already streamed the first value and sent it, lets send the rest
- while (rem_len > 4 /* octets */) {
- // 2
- STREAM_TO_UINT16(value.handle, p);
- // + 2 = 4
- STREAM_TO_UINT16(value.len, p);
- // Accounting
- rem_len -= 4;
- // Make sure we don't read past the remaining data even if the length says
- // we can Also need to watch comparing the int16_t with the uint16_t
- value.len = std::min(rem_len, (int16_t)value.len);
- STREAM_TO_ARRAY(value.value, p, value.len);
- // Accounting
- rem_len -= value.len;
-
- gatt_cl_complete.att_value = value;
- gatt_cl_complete.cid = cid;
-
- for (i = 0, p_reg = gatt_cb.cl_rcb; i < GATT_MAX_APPS; i++, p_reg++) {
- if (p_reg->in_use && p_reg->app_cb.p_cmpl_cb) {
- conn_id = GATT_CREATE_CONN_ID(tcb.tcb_idx, p_reg->gatt_if);
- (*p_reg->app_cb.p_cmpl_cb)(conn_id, event, encrypt_status,
- &gatt_cl_complete);
- }
- }
- }
}
/*******************************************************************************
@@ -794,8 +716,8 @@ void gatt_process_read_by_type_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
}
STREAM_TO_UINT8(value_len, p);
- uint16_t payload_size = gatt_tcb_get_payload_size_rx(tcb, p_clcb->cid);
- if ((value_len > (payload_size - 2)) || (value_len > (len - 1))) {
+
+ if ((value_len > (tcb.payload_size - 2)) || (value_len > (len - 1))) {
/* this is an error case that server's response containing a value length
which is larger than MTU-2
or value_len > message total length -1 */
@@ -803,7 +725,7 @@ void gatt_process_read_by_type_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
<< StringPrintf(
": Discard response op_code=%d "
"vale_len=%d > (MTU-2=%d or msg_len-1=%d)",
- op_code, value_len, (payload_size - 2), (len - 1));
+ op_code, value_len, (tcb.payload_size - 2), (len - 1));
gatt_end_operation(p_clcb, GATT_ERROR, NULL);
return;
}
@@ -892,7 +814,7 @@ void gatt_process_read_by_type_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
p_clcb->op_subtype == GATT_READ_BY_TYPE) {
p_clcb->counter = len - 2;
p_clcb->s_handle = handle;
- if (p_clcb->counter == (payload_size - 4)) {
+ if (p_clcb->counter == (p_clcb->p_tcb->payload_size - 4)) {
p_clcb->op_subtype = GATT_READ_BY_HANDLE;
if (!p_clcb->p_attr_buf)
p_clcb->p_attr_buf = (uint8_t*)osi_malloc(GATT_MAX_ATTR_LEN);
@@ -954,9 +876,8 @@ void gatt_process_read_by_type_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
/* send callback if is discover procedure */
if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY &&
p_clcb->p_reg->app_cb.p_disc_res_cb)
- (*p_clcb->p_reg->app_cb.p_disc_res_cb)(
- p_clcb->conn_id, static_cast<tGATT_DISC_TYPE>(p_clcb->op_subtype),
- &result);
+ (*p_clcb->p_reg->app_cb.p_disc_res_cb)(p_clcb->conn_id,
+ p_clcb->op_subtype, &result);
}
p_clcb->s_handle = (handle == 0) ? 0 : (handle + 1);
@@ -986,8 +907,6 @@ void gatt_process_read_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
uint16_t offset = p_clcb->counter;
uint8_t* p = p_data;
- uint16_t payload_size = gatt_tcb_get_payload_size_rx(tcb, p_clcb->cid);
-
if (p_clcb->operation == GATTC_OPTYPE_READ) {
if (p_clcb->op_subtype != GATT_READ_BY_HANDLE) {
p_clcb->counter = len;
@@ -1008,12 +927,12 @@ void gatt_process_read_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
/* full packet for read or read blob rsp */
bool packet_is_full;
- if (payload_size == p_clcb->read_req_current_mtu) {
- packet_is_full = (len == (payload_size - 1));
+ if (tcb.payload_size == p_clcb->read_req_current_mtu) {
+ packet_is_full = (len == (tcb.payload_size - 1));
} else {
packet_is_full = (len == (p_clcb->read_req_current_mtu - 1) ||
- len == (payload_size - 1));
- p_clcb->read_req_current_mtu = payload_size;
+ len == (tcb.payload_size - 1));
+ p_clcb->read_req_current_mtu = tcb.payload_size;
}
/* send next request if needed */
@@ -1045,9 +964,9 @@ void gatt_process_read_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
p_clcb->read_uuid128.result.value.incl_service.service_type =
bluetooth::Uuid::From128BitLE(p);
if (p_clcb->p_reg->app_cb.p_disc_res_cb)
- (*p_clcb->p_reg->app_cb.p_disc_res_cb)(
- p_clcb->conn_id, static_cast<tGATT_DISC_TYPE>(p_clcb->op_subtype),
- &p_clcb->read_uuid128.result);
+ (*p_clcb->p_reg->app_cb.p_disc_res_cb)(p_clcb->conn_id,
+ p_clcb->op_subtype,
+ &p_clcb->read_uuid128.result);
gatt_act_discovery(p_clcb);
} else {
gatt_end_operation(p_clcb, GATT_INVALID_PDU, (void*)p);
@@ -1094,8 +1013,8 @@ void gatt_process_mtu_rsp(tGATT_TCB& tcb, tGATT_CLCB* p_clcb, uint16_t len,
tcb.payload_size = mtu;
}
- BTM_SetBleDataLength(tcb.peer_bda, tcb.payload_size);
-
+ l2cble_set_fixed_channel_tx_data_length(tcb.peer_bda, L2CAP_ATT_CID,
+ tcb.payload_size);
gatt_end_operation(p_clcb, status, NULL);
}
/*******************************************************************************
@@ -1119,29 +1038,14 @@ uint8_t gatt_cmd_to_rsp_code(uint8_t cmd_code) {
/** Find next command in queue and sent to server */
bool gatt_cl_send_next_cmd_inq(tGATT_TCB& tcb) {
- std::queue<tGATT_CMD_Q>* cl_cmd_q;
-
- while (!tcb.cl_cmd_q.empty() ||
- EattExtension::GetInstance()->IsOutstandingMsgInSendQueue(tcb.peer_bda)) {
- if (!tcb.cl_cmd_q.empty()) {
- cl_cmd_q = &tcb.cl_cmd_q;
- } else {
- EattChannel* channel =
- EattExtension::GetInstance()->GetChannelWithQueuedData(tcb.peer_bda);
- cl_cmd_q = &channel->cl_cmd_q_;
- }
-
- tGATT_CMD_Q& cmd = cl_cmd_q->front();
- if (!cmd.to_send || cmd.p_cmd == NULL) {
- return false;
- }
-
- tGATT_STATUS att_ret;
- att_ret = attp_send_msg_to_l2cap(tcb, cmd.cid, cmd.p_cmd);
+ while (!tcb.cl_cmd_q.empty()) {
+ tGATT_CMD_Q& cmd = tcb.cl_cmd_q.front();
+ if (!cmd.to_send || cmd.p_cmd == NULL) return false;
+ tGATT_STATUS att_ret = attp_send_msg_to_l2cap(tcb, cmd.p_cmd);
if (att_ret != GATT_SUCCESS && att_ret != GATT_CONGESTED) {
LOG(ERROR) << __func__ << ": L2CAP sent error";
- cl_cmd_q->pop();
+ tcb.cl_cmd_q.pop();
continue;
}
@@ -1151,7 +1055,7 @@ bool gatt_cl_send_next_cmd_inq(tGATT_TCB& tcb) {
if (cmd.op_code == GATT_CMD_WRITE || cmd.op_code == GATT_SIGN_CMD_WRITE) {
/* dequeue the request if is write command or sign write */
uint8_t rsp_code;
- tGATT_CLCB* p_clcb = gatt_cmd_dequeue(tcb, cmd.cid, &rsp_code);
+ tGATT_CLCB* p_clcb = gatt_cmd_dequeue(tcb, &rsp_code);
/* send command complete callback here */
gatt_end_operation(p_clcb, att_ret, NULL);
@@ -1170,28 +1074,22 @@ bool gatt_cl_send_next_cmd_inq(tGATT_TCB& tcb) {
}
/** This function is called to handle the server response to client */
-void gatt_client_handle_server_rsp(tGATT_TCB& tcb, uint16_t cid,
- uint8_t op_code, uint16_t len,
- uint8_t* p_data) {
- VLOG(1) << __func__ << " opcode: " << loghex(op_code);
-
- uint16_t payload_size = gatt_tcb_get_payload_size_rx(tcb, cid);
-
- if (op_code == GATT_HANDLE_VALUE_IND || op_code == GATT_HANDLE_VALUE_NOTIF ||
- op_code == GATT_HANDLE_MULTI_VALUE_NOTIF) {
- if (len >= payload_size) {
+void gatt_client_handle_server_rsp(tGATT_TCB& tcb, uint8_t op_code,
+ uint16_t len, uint8_t* p_data) {
+ if (op_code == GATT_HANDLE_VALUE_IND || op_code == GATT_HANDLE_VALUE_NOTIF) {
+ if (len >= tcb.payload_size) {
LOG(ERROR) << StringPrintf(
"%s: invalid indicate pkt size: %d, PDU size: %d", __func__, len + 1,
- payload_size);
+ tcb.payload_size);
return;
}
- gatt_process_notification(tcb, cid, op_code, len, p_data);
+ gatt_process_notification(tcb, op_code, len, p_data);
return;
}
uint8_t cmd_code = 0;
- tGATT_CLCB* p_clcb = gatt_cmd_dequeue(tcb, cid, &cmd_code);
+ tGATT_CLCB* p_clcb = gatt_cmd_dequeue(tcb, &cmd_code);
uint8_t rsp_code = gatt_cmd_to_rsp_code(cmd_code);
if (!p_clcb || (rsp_code != op_code && op_code != GATT_RSP_ERROR)) {
LOG(WARNING) << StringPrintf(
@@ -1206,16 +1104,16 @@ void gatt_client_handle_server_rsp(tGATT_TCB& tcb, uint16_t cid,
return;
}
- gatt_stop_rsp_timer(p_clcb);
+ alarm_cancel(p_clcb->gatt_rsp_timer_ent);
p_clcb->retry_count = 0;
/* the size of the message may not be bigger than the local max PDU size*/
/* The message has to be smaller than the agreed MTU, len does not count
* op_code */
- if (len >= payload_size) {
+ if (len >= tcb.payload_size) {
LOG(ERROR) << StringPrintf(
"%s: invalid response pkt size: %d, PDU size: %d", __func__, len + 1,
- payload_size);
+ tcb.payload_size);
gatt_end_operation(p_clcb, GATT_ERROR, NULL);
} else {
switch (op_code) {
@@ -1239,7 +1137,6 @@ void gatt_client_handle_server_rsp(tGATT_TCB& tcb, uint16_t cid,
case GATT_RSP_READ:
case GATT_RSP_READ_BLOB:
case GATT_RSP_READ_MULTI:
- case GATT_RSP_READ_MULTI_VAR:
gatt_process_read_rsp(tcb, p_clcb, op_code, len, p_data);
break;
diff --git a/stack/gatt/gatt_db.cc b/stack/gatt/gatt_db.cc
index f7d18e4a2..2d0c5b001 100644
--- a/stack/gatt/gatt_db.cc
+++ b/stack/gatt/gatt_db.cc
@@ -29,12 +29,10 @@
#include <stdio.h>
#include <string.h>
+#include "btm_int.h"
#include "gatt_int.h"
#include "l2c_api.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/acl_api.h"
using base::StringPrintf;
using bluetooth::Uuid;
@@ -45,8 +43,8 @@ using bluetooth::Uuid;
static tGATT_ATTR& allocate_attr_in_db(tGATT_SVC_DB& db, const Uuid& uuid,
tGATT_PERM perm);
static tGATT_STATUS gatts_send_app_read_request(
- tGATT_TCB& tcb, uint16_t cid, uint8_t op_code, uint16_t handle,
- uint16_t offset, uint32_t trans_id, bt_gatt_db_attribute_type_t gatt_type);
+ tGATT_TCB& tcb, uint8_t op_code, uint16_t handle, uint16_t offset,
+ uint32_t trans_id, bt_gatt_db_attribute_type_t gatt_type);
/**
* Initialize a memory space to be a service database.
@@ -66,7 +64,7 @@ void gatts_init_service_db(tGATT_SVC_DB& db, const Uuid& service_uuid,
Uuid uuid =
Uuid::From16Bit(is_pri ? GATT_UUID_PRI_SERVICE : GATT_UUID_SEC_SERVICE);
tGATT_ATTR& attr = allocate_attr_in_db(db, uuid, GATT_PERM_READ);
- attr.p_value.reset(new tGATT_ATTR_VALUE);
+ attr.p_value.reset((tGATT_ATTR_VALUE*)(new Uuid));
attr.p_value->uuid = service_uuid;
}
@@ -231,18 +229,7 @@ static tGATT_STATUS read_attr_value(tGATT_ATTR& attr16, uint16_t offset,
return GATT_SUCCESS;
}
- if (uuid16 == GATT_UUID_CHAR_EXT_PROP) {
- // sometimes this descriptor is added by users manually, we need to check if
- // the p_value is nullptr.
- uint16_t char_ext_prop =
- attr16.p_value ? attr16.p_value->char_ext_prop : 0x0000;
- *p_len = 2;
- UINT16_TO_STREAM(p, char_ext_prop);
- *p_data = p;
- return GATT_SUCCESS;
- }
-
- /* characteristic descriptor or characteristic value (again) */
+ /* characteristic description or characteristic value (again) */
return GATT_PENDING;
}
@@ -265,10 +252,10 @@ static tGATT_STATUS read_attr_value(tGATT_ATTR& attr16, uint16_t offset,
*
******************************************************************************/
tGATT_STATUS gatts_db_read_attr_value_by_type(
- tGATT_TCB& tcb, uint16_t cid, tGATT_SVC_DB* p_db, uint8_t op_code,
- BT_HDR* p_rsp, uint16_t s_handle, uint16_t e_handle, const Uuid& type,
- uint16_t* p_len, tGATT_SEC_FLAG sec_flag, uint8_t key_size,
- uint32_t trans_id, uint16_t* p_cur_handle) {
+ tGATT_TCB& tcb, tGATT_SVC_DB* p_db, uint8_t op_code, BT_HDR* p_rsp,
+ uint16_t s_handle, uint16_t e_handle, const Uuid& type, uint16_t* p_len,
+ tGATT_SEC_FLAG sec_flag, uint8_t key_size, uint32_t trans_id,
+ uint16_t* p_cur_handle) {
tGATT_STATUS status = GATT_NOT_FOUND;
uint16_t len = 0;
uint8_t* p = (uint8_t*)(p_rsp + 1) + p_rsp->len + L2CAP_MIN_OFFSET;
@@ -287,8 +274,8 @@ tGATT_STATUS gatts_db_read_attr_value_by_type(
&len, sec_flag, key_size);
if (status == GATT_PENDING) {
- status = gatts_send_app_read_request(tcb, cid, op_code, attr.handle,
- 0, trans_id, attr.gatt_type);
+ status = gatts_send_app_read_request(tcb, op_code, attr.handle, 0,
+ trans_id, attr.gatt_type);
/* one callback at a time */
break;
@@ -311,6 +298,21 @@ tGATT_STATUS gatts_db_read_attr_value_by_type(
}
}
+#if (BLE_DELAY_REQUEST_ENC == TRUE)
+ uint8_t flag = 0;
+ if (BTM_GetSecurityFlags(tcb.peer_bda, &flag)) {
+ if ((tcb.att_lcid == L2CAP_ATT_CID) && (status == GATT_PENDING) &&
+ (type.As16Bit() == GATT_UUID_GAP_DEVICE_NAME)) {
+ if ((flag & (BTM_SEC_LINK_KEY_KNOWN | BTM_SEC_FLAG_ENCRYPTED)) ==
+ BTM_SEC_LINK_KEY_KNOWN) {
+ tACL_CONN* p = btm_bda_to_acl(tcb.peer_bda, BT_TRANSPORT_LE);
+ if ((p != NULL) && (p->link_role == BTM_ROLE_MASTER))
+ btm_ble_set_encryption(tcb.peer_bda, BTM_BLE_SEC_ENCRYPT,
+ p->link_role);
+ }
+ }
+ }
+#endif
return status;
}
@@ -338,7 +340,7 @@ uint16_t gatts_add_included_service(tGATT_SVC_DB& db, uint16_t s_handle,
tGATT_ATTR& attr = allocate_attr_in_db(db, uuid, GATT_PERM_READ);
- attr.p_value.reset(new tGATT_ATTR_VALUE);
+ attr.p_value.reset((tGATT_ATTR_VALUE*)(new tGATT_INCL_SRVC));
attr.p_value->incl_handle.s_handle = s_handle;
attr.p_value->incl_handle.e_handle = e_handle;
attr.p_value->incl_handle.service_type = service;
@@ -356,7 +358,6 @@ uint16_t gatts_add_included_service(tGATT_SVC_DB& db, uint16_t s_handle,
* Parameter db: database.
* perm: permission (authentication and key size requirements)
* property: property of the characteristic.
- * extended_properties: characteristic extended properties.
* p_char: characteristic value information.
*
* Returns Status of te operation.
@@ -373,43 +374,15 @@ uint16_t gatts_add_characteristic(tGATT_SVC_DB& db, tGATT_PERM perm,
tGATT_ATTR& char_decl = allocate_attr_in_db(db, uuid, GATT_PERM_READ);
tGATT_ATTR& char_val = allocate_attr_in_db(db, char_uuid, perm);
- char_decl.p_value.reset(new tGATT_ATTR_VALUE);
+ char_decl.p_value.reset((tGATT_ATTR_VALUE*)(new tGATT_CHAR_DECL));
char_decl.p_value->char_decl.property = property;
char_decl.p_value->char_decl.char_val_handle = char_val.handle;
char_val.gatt_type = BTGATT_DB_CHARACTERISTIC;
-
return char_val.handle;
}
/*******************************************************************************
*
- * Function gatts_add_char_ext_prop_descr
- *
- * Description add a characteristics extended properties descriptor.
- *
- * Parameter db: database pointer.
- * extended_properties: characteristic descriptors values.
- *
- * Returns Status of the operation.
- *
- ******************************************************************************/
-uint16_t gatts_add_char_ext_prop_descr(
- tGATT_SVC_DB& db, uint16_t extended_properties) {
- Uuid descr_uuid = Uuid::From16Bit(GATT_UUID_CHAR_EXT_PROP);
-
- VLOG(1) << StringPrintf("gatts_add_char_ext_prop_descr uuid=%s",
- descr_uuid.ToString().c_str());
-
- tGATT_ATTR& char_dscptr = allocate_attr_in_db(db, descr_uuid, GATT_PERM_READ);
- char_dscptr.gatt_type = BTGATT_DB_DESCRIPTOR;
- char_dscptr.p_value.reset(new tGATT_ATTR_VALUE);
- char_dscptr.p_value->char_ext_prop = extended_properties;
-
- return char_dscptr.handle;
-}
-
-/*******************************************************************************
- *
* Function gatts_add_char_descr
*
* Description This function add a characteristics descriptor.
@@ -467,10 +440,9 @@ tGATT_ATTR* find_attr_by_handle(tGATT_SVC_DB* p_db, uint16_t handle) {
*
******************************************************************************/
tGATT_STATUS gatts_read_attr_value_by_handle(
- tGATT_TCB& tcb, uint16_t cid, tGATT_SVC_DB* p_db, uint8_t op_code,
- uint16_t handle, uint16_t offset, uint8_t* p_value, uint16_t* p_len,
- uint16_t mtu, tGATT_SEC_FLAG sec_flag, uint8_t key_size,
- uint32_t trans_id) {
+ tGATT_TCB& tcb, tGATT_SVC_DB* p_db, uint8_t op_code, uint16_t handle,
+ uint16_t offset, uint8_t* p_value, uint16_t* p_len, uint16_t mtu,
+ tGATT_SEC_FLAG sec_flag, uint8_t key_size, uint32_t trans_id) {
tGATT_ATTR* p_attr = find_attr_by_handle(p_db, handle);
if (!p_attr) return GATT_NOT_FOUND;
@@ -480,8 +452,8 @@ tGATT_STATUS gatts_read_attr_value_by_handle(
mtu, p_len, sec_flag, key_size);
if (status == GATT_PENDING) {
- status = gatts_send_app_read_request(tcb, cid, op_code, p_attr->handle,
- offset, trans_id, p_attr->gatt_type);
+ status = gatts_send_app_read_request(tcb, op_code, p_attr->handle, offset,
+ trans_id, p_attr->gatt_type);
}
return status;
}
@@ -704,14 +676,14 @@ static tGATT_ATTR& allocate_attr_in_db(tGATT_SVC_DB& db, const Uuid& uuid,
*
******************************************************************************/
static tGATT_STATUS gatts_send_app_read_request(
- tGATT_TCB& tcb, uint16_t cid, uint8_t op_code, uint16_t handle,
- uint16_t offset, uint32_t trans_id, bt_gatt_db_attribute_type_t gatt_type) {
+ tGATT_TCB& tcb, uint8_t op_code, uint16_t handle, uint16_t offset,
+ uint32_t trans_id, bt_gatt_db_attribute_type_t gatt_type) {
tGATT_SRV_LIST_ELEM& el = *gatt_sr_find_i_rcb_by_handle(handle);
uint16_t conn_id = GATT_CREATE_CONN_ID(tcb.tcb_idx, el.gatt_if);
if (trans_id == 0) {
- trans_id = gatt_sr_enqueue_cmd(tcb, cid, op_code, handle);
- gatt_sr_update_cback_cnt(tcb, cid, el.gatt_if, true, true);
+ trans_id = gatt_sr_enqueue_cmd(tcb, op_code, handle);
+ gatt_sr_update_cback_cnt(tcb, el.gatt_if, true, true);
}
if (trans_id != 0) {
diff --git a/stack/gatt/gatt_int.h b/stack/gatt/gatt_int.h
index b7278bf1b..e072a47d8 100644
--- a/stack/gatt/gatt_int.h
+++ b/stack/gatt/gatt_int.h
@@ -26,7 +26,6 @@
#include "gatt_api.h"
#include "osi/include/fixed_queue.h"
-#include <base/bind.h>
#include <base/strings/stringprintf.h>
#include <string.h>
#include <list>
@@ -41,38 +40,34 @@
#define GATT_TRANS_ID_MAX 0x0fffffff /* 4 MSB is reserved */
/* security action for GATT write and read request */
-typedef enum : uint8_t {
- GATT_SEC_NONE = 0,
- GATT_SEC_OK = 1,
- GATT_SEC_SIGN_DATA = 2, /* compute the signature for the write cmd */
- GATT_SEC_ENCRYPT = 3, /* encrypt the link with current key */
- GATT_SEC_ENCRYPT_NO_MITM = 4, /* unauthenticated encryption or better */
- GATT_SEC_ENCRYPT_MITM = 5, /* authenticated encryption */
- GATT_SEC_ENC_PENDING = 6, /* wait for link encryption pending */
-} tGATT_SEC_ACTION;
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string gatt_security_action_text(const tGATT_SEC_ACTION& action) {
- switch (action) {
- CASE_RETURN_TEXT(GATT_SEC_NONE);
- CASE_RETURN_TEXT(GATT_SEC_OK);
- CASE_RETURN_TEXT(GATT_SEC_SIGN_DATA);
- CASE_RETURN_TEXT(GATT_SEC_ENCRYPT);
- CASE_RETURN_TEXT(GATT_SEC_ENCRYPT_NO_MITM);
- CASE_RETURN_TEXT(GATT_SEC_ENCRYPT_MITM);
- CASE_RETURN_TEXT(GATT_SEC_ENC_PENDING);
- default:
- return std::string("UNKNOWN[%hhu]", action);
- }
-}
-
-#undef CASE_RETURN_TEXT
+#define GATT_SEC_NONE 0
+#define GATT_SEC_OK 1
+#define GATT_SEC_SIGN_DATA 2 /* compute the signature for the write cmd */
+#define GATT_SEC_ENCRYPT 3 /* encrypt the link with current key */
+#define GATT_SEC_ENCRYPT_NO_MITM 4 /* unauthenticated encryption or better */
+#define GATT_SEC_ENCRYPT_MITM 5 /* authenticated encryption */
+#define GATT_SEC_ENC_PENDING 6 /* wait for link encryption pending */
+typedef uint8_t tGATT_SEC_ACTION;
+
+#define GATT_ATTR_OP_SPT_MTU (0x00000001 << 0)
+#define GATT_ATTR_OP_SPT_FIND_INFO (0x00000001 << 1)
+#define GATT_ATTR_OP_SPT_FIND_BY_TYPE (0x00000001 << 2)
+#define GATT_ATTR_OP_SPT_READ_BY_TYPE (0x00000001 << 3)
+#define GATT_ATTR_OP_SPT_READ (0x00000001 << 4)
+#define GATT_ATTR_OP_SPT_MULT_READ (0x00000001 << 5)
+#define GATT_ATTR_OP_SPT_READ_BLOB (0x00000001 << 6)
+#define GATT_ATTR_OP_SPT_READ_BY_GRP_TYPE (0x00000001 << 7)
+#define GATT_ATTR_OP_SPT_WRITE (0x00000001 << 8)
+#define GATT_ATTR_OP_SPT_WRITE_CMD (0x00000001 << 9)
+#define GATT_ATTR_OP_SPT_PREP_WRITE (0x00000001 << 10)
+#define GATT_ATTR_OP_SPT_EXE_WRITE (0x00000001 << 11)
+#define GATT_ATTR_OP_SPT_HDL_VALUE_CONF (0x00000001 << 12)
+#define GATT_ATTR_OP_SP_SIGN_WRITE (0x00000001 << 13)
#define GATT_INDEX_INVALID 0xff
+#define GATT_PENDING_REQ_NONE 0
+
#define GATT_WRITE_CMD_MASK 0xc0 /*0x1100-0000*/
#define GATT_AUTH_SIGN_MASK 0x80 /*0x1000-0000*/
#define GATT_AUTH_SIGN_LEN 12
@@ -84,6 +79,16 @@ inline std::string gatt_security_action_text(const tGATT_SEC_ACTION& action) {
#define GATT_WAIT_FOR_DISC_RSP_TIMEOUT_MS (5 * 1000)
#define GATT_REQ_RETRY_LIMIT 2
+/* characteristic descriptor type */
+#define GATT_DESCR_EXT_DSCPTOR 1 /* Characteristic Extended Properties */
+#define GATT_DESCR_USER_DSCPTOR 2 /* Characteristic User Description */
+#define GATT_DESCR_CLT_CONFIG 3 /* Client Characteristic Configuration */
+#define GATT_DESCR_SVR_CONFIG 4 /* Server Characteristic Configuration */
+#define GATT_DESCR_PRES_FORMAT 5 /* Characteristic Presentation Format */
+#define GATT_DESCR_AGGR_FORMAT 6 /* Characteristic Aggregate Format */
+#define GATT_DESCR_VALID_RANGE 7 /* Characteristic Valid Range */
+#define GATT_DESCR_UNKNOWN 0xff
+
#define GATT_SEC_FLAG_LKEY_UNAUTHED BTM_SEC_FLAG_LKEY_KNOWN
#define GATT_SEC_FLAG_LKEY_AUTHED BTM_SEC_FLAG_LKEY_AUTHED
#define GATT_SEC_FLAG_ENCRYPTED BTM_SEC_FLAG_ENCRYPTED
@@ -94,9 +99,6 @@ typedef uint8_t tGATT_SEC_FLAG;
#define GATT_INFO_TYPE_PAIR_16 0x01
#define GATT_INFO_TYPE_PAIR_128 0x02
-constexpr bool kGattConnected = true;
-constexpr bool kGattDisconnected = !kGattConnected;
-
/* GATT client FIND_TYPE_VALUE_Request data */
typedef struct {
bluetooth::Uuid uuid; /* type of attribute to be found */
@@ -153,7 +155,6 @@ typedef union {
bluetooth::Uuid uuid; /* service declaration */
tGATT_CHAR_DECL char_decl; /* characteristic declaration */
tGATT_INCL_SRVC incl_handle; /* included service */
- uint16_t char_ext_prop; /* Characteristic Extended Properties */
} tGATT_ATTR_VALUE;
/* Attribute UUID type
@@ -188,12 +189,10 @@ typedef struct {
typedef struct {
bluetooth::Uuid app_uuid128;
- tGATT_CBACK app_cb{};
- tGATT_IF gatt_if{0}; /* one based */
- bool in_use{false};
- uint8_t listening{0}; /* if adv for all has been enabled */
- bool eatt_support{false};
- std::string name;
+ tGATT_CBACK app_cb;
+ tGATT_IF gatt_if; /* one based */
+ bool in_use;
+ uint8_t listening; /* if adv for all has been enabled */
} tGATT_REG;
struct tGATT_CLCB;
@@ -204,7 +203,6 @@ typedef struct {
tGATT_CLCB* p_clcb;
uint8_t op_code;
bool to_send;
- uint16_t cid;
} tGATT_CMD_Q;
#if GATT_MAX_SR_PROFILES <= 8
@@ -225,33 +223,15 @@ typedef struct {
uint8_t op_code;
uint8_t status;
uint8_t cback_cnt[GATT_MAX_APPS];
- uint16_t cid;
} tGATT_SR_CMD;
-typedef enum : uint8_t {
- GATT_CH_CLOSE = 0,
- GATT_CH_CLOSING = 1,
- GATT_CH_CONN = 2,
- GATT_CH_CFG = 3,
- GATT_CH_OPEN = 4,
-} tGATT_CH_STATE;
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string gatt_channel_state_text(const tGATT_CH_STATE& state) {
- switch (state) {
- CASE_RETURN_TEXT(GATT_CH_CLOSE);
- CASE_RETURN_TEXT(GATT_CH_CLOSING);
- CASE_RETURN_TEXT(GATT_CH_CONN);
- CASE_RETURN_TEXT(GATT_CH_CFG);
- CASE_RETURN_TEXT(GATT_CH_OPEN);
- default:
- return std::string("UNKNOWN[%hhu]", state);
- }
-}
-#undef CASE_RETURN_TEXT
+#define GATT_CH_CLOSE 0
+#define GATT_CH_CLOSING 1
+#define GATT_CH_CONN 2
+#define GATT_CH_CFG 3
+#define GATT_CH_OPEN 4
+
+typedef uint8_t tGATT_CH_STATE;
#define GATT_GATT_START_HANDLE 1
#define GATT_GAP_START_HANDLE 20
@@ -290,13 +270,11 @@ typedef struct {
tBT_TRANSPORT transport;
uint32_t trans_id;
- /* Indicates number of available eatt channels */
- uint8_t eatt;
-
uint16_t att_lcid; /* L2CAP channel ID for ATT */
uint16_t payload_size;
tGATT_CH_STATE ch_state;
+ uint8_t ch_flags;
std::unordered_set<uint8_t> app_hold_link;
@@ -314,14 +292,6 @@ typedef struct {
std::queue<tGATT_CMD_Q> cl_cmd_q;
alarm_t* ind_ack_timer; /* local app confirm to indication timer */
- // TODO(hylo): support byte array data
- /* Client supported feature*/
- uint8_t cl_supp_feat;
- /* Server supported features */
- uint8_t sr_supp_feat;
- /* Use for server. if false, should handle database out of sync. */
- bool is_robust_cache_change_aware;
-
bool in_use;
uint8_t tcb_idx;
} tGATT_TCB;
@@ -345,9 +315,9 @@ struct tGATT_CLCB {
uint16_t counter; /* used as offset, attribute length, num of prepare write */
uint16_t start_offset;
tGATT_AUTH_REQ auth_req; /* authentication requirement */
- tGATTC_OPTYPE operation; /* one logic channel can have one operation active */
+ uint8_t operation; /* one logic channel can have one operation active */
uint8_t op_subtype; /* operation subtype */
- tGATT_STATUS status; /* operation status */
+ uint8_t status; /* operation status */
bool first_read_blob_after_read;
tGATT_READ_INC_UUID128 read_uuid128;
bool in_use;
@@ -355,7 +325,6 @@ struct tGATT_CLCB {
uint8_t retry_count;
uint16_t read_req_current_mtu; /* This is the MTU value that the read was
initiated with */
- uint16_t cid;
};
typedef struct {
@@ -398,6 +367,7 @@ typedef struct {
fixed_queue_t* srv_chg_clt_q; /* service change clients queue */
tGATT_REG cl_rcb[GATT_MAX_APPS];
tGATT_CLCB clcb[GATT_CL_MAX_LCB]; /* connection link control block*/
+ uint16_t def_mtu_size;
#if (GATT_CONFORMANCE_TESTING == TRUE)
bool enable_err_rsp;
@@ -409,19 +379,6 @@ typedef struct {
tGATT_PROFILE_CLCB profile_clcb[GATT_MAX_APPS];
uint16_t
handle_of_h_r; /* Handle of the handles reused characteristic value */
- uint16_t handle_cl_supported_feat;
- uint16_t handle_sr_supported_feat;
- uint8_t
- gatt_svr_supported_feat_mask; /* Local supported features as a server */
-
- /* Supported features as a client. To be written to remote device.
- * Note this is NOT a value of the characteristic with handle
- * handle_cl_support_feat, as that one should be written by remote device.
- */
- uint8_t gatt_cl_supported_feat_mask;
-
- uint16_t handle_of_database_hash;
- Octet16 database_hash;
tGATT_APPL_INFO cb_info;
@@ -445,7 +402,7 @@ extern bool gatt_act_connect(tGATT_REG* p_reg, const RawAddress& bd_addr,
extern bool gatt_connect(const RawAddress& rem_bda, tGATT_TCB* p_tcb,
tBT_TRANSPORT transport, uint8_t initiating_phys,
tGATT_IF gatt_if);
-extern void gatt_data_process(tGATT_TCB& p_tcb, uint16_t cid, BT_HDR* p_buf);
+extern void gatt_data_process(tGATT_TCB& p_tcb, BT_HDR* p_buf);
extern void gatt_update_app_use_link_flag(tGATT_IF gatt_if, tGATT_TCB* p_tcb,
bool is_add, bool check_acl_link);
@@ -461,26 +418,13 @@ extern void gatt_add_a_bonded_dev_for_srv_chg(const RawAddress& bda);
/* from gatt_attr.cc */
extern uint16_t gatt_profile_find_conn_id_by_bd_addr(const RawAddress& bda);
-extern bool gatt_profile_get_eatt_support(const RawAddress& remote_bda);
-extern void gatt_cl_init_sr_status(tGATT_TCB& tcb);
-extern bool gatt_cl_read_sr_supp_feat_req(
- const RawAddress& peer_bda,
- base::OnceCallback<void(const RawAddress&, uint8_t)> cb);
-
-extern bool gatt_sr_is_cl_change_aware(tGATT_TCB& tcb);
-extern void gatt_sr_init_cl_status(tGATT_TCB& tcb);
-extern void gatt_sr_update_cl_status(tGATT_TCB& tcb, bool chg_unaware);
-
/* Functions provided by att_protocol.cc */
-extern tGATT_STATUS attp_send_cl_confirmation_msg(tGATT_TCB& tcb, uint16_t cid);
extern tGATT_STATUS attp_send_cl_msg(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
uint8_t op_code, tGATT_CL_MSG* p_msg);
extern BT_HDR* attp_build_sr_msg(tGATT_TCB& tcb, uint8_t op_code,
tGATT_SR_MSG* p_msg);
-extern tGATT_STATUS attp_send_sr_msg(tGATT_TCB& tcb, uint16_t cid,
- BT_HDR* p_msg);
-extern tGATT_STATUS attp_send_msg_to_l2cap(tGATT_TCB& tcb, uint16_t cid,
- BT_HDR* p_toL2CAP);
+extern tGATT_STATUS attp_send_sr_msg(tGATT_TCB& tcb, BT_HDR* p_msg);
+extern tGATT_STATUS attp_send_msg_to_l2cap(tGATT_TCB& tcb, BT_HDR* p_toL2CAP);
/* utility functions */
extern uint8_t* gatt_dbg_op_name(uint8_t op_code);
@@ -495,17 +439,14 @@ extern void gatt_sr_get_sec_info(const RawAddress& rem_bda,
tBT_TRANSPORT transport, uint8_t* p_sec_flag,
uint8_t* p_key_size);
extern void gatt_start_rsp_timer(tGATT_CLCB* p_clcb);
-extern void gatt_stop_rsp_timer(tGATT_CLCB* p_clcb);
-extern void gatt_start_conf_timer(tGATT_TCB* p_tcb, uint16_t cid);
-extern void gatt_stop_conf_timer(tGATT_TCB& tcb, uint16_t cid);
+extern void gatt_start_conf_timer(tGATT_TCB* p_tcb);
extern void gatt_rsp_timeout(void* data);
extern void gatt_indication_confirmation_timeout(void* data);
extern void gatt_ind_ack_timeout(void* data);
-extern void gatt_start_ind_ack_timer(tGATT_TCB& tcb, uint16_t cid);
-extern void gatt_stop_ind_ack_timer(tGATT_TCB* p_tcb, uint16_t cid);
-extern tGATT_STATUS gatt_send_error_rsp(tGATT_TCB& tcb, uint16_t cid,
- uint8_t err_code, uint8_t op_code,
- uint16_t handle, bool deq);
+extern void gatt_start_ind_ack_timer(tGATT_TCB& tcb);
+extern tGATT_STATUS gatt_send_error_rsp(tGATT_TCB& tcb, uint8_t err_code,
+ uint8_t op_code, uint16_t handle,
+ bool deq);
extern bool gatt_is_srv_chg_ind_pending(tGATT_TCB* p_tcb);
extern tGATTS_SRV_CHG* gatt_is_bda_in_the_srv_chg_clt_list(
@@ -537,48 +478,30 @@ extern std::list<tGATT_SRV_LIST_ELEM>::iterator gatt_sr_find_i_rcb_by_handle(
extern tGATT_STATUS gatt_sr_process_app_rsp(tGATT_TCB& tcb, tGATT_IF gatt_if,
uint32_t trans_id, uint8_t op_code,
tGATT_STATUS status,
- tGATTS_RSP* p_msg,
- tGATT_SR_CMD* sr_res_p);
-extern void gatt_server_handle_client_req(tGATT_TCB& p_tcb, uint16_t cid,
- uint8_t op_code, uint16_t len,
- uint8_t* p_data);
+ tGATTS_RSP* p_msg);
+extern void gatt_server_handle_client_req(tGATT_TCB& p_tcb, uint8_t op_code,
+ uint16_t len, uint8_t* p_data);
extern void gatt_sr_send_req_callback(uint16_t conn_id, uint32_t trans_id,
uint8_t op_code, tGATTS_DATA* p_req_data);
-extern uint32_t gatt_sr_enqueue_cmd(tGATT_TCB& tcb, uint16_t cid,
- uint8_t op_code, uint16_t handle);
+extern uint32_t gatt_sr_enqueue_cmd(tGATT_TCB& tcb, uint8_t op_code,
+ uint16_t handle);
extern bool gatt_cancel_open(tGATT_IF gatt_if, const RawAddress& bda);
-extern void gatt_notify_phy_updated(tGATT_STATUS status, uint16_t handle,
+extern void gatt_notify_phy_updated(uint8_t status, uint16_t handle,
uint8_t tx_phy, uint8_t rx_phy);
/* */
-extern bool gatt_tcb_is_cid_busy(tGATT_TCB& tcb, uint16_t cid);
-
extern tGATT_REG* gatt_get_regcb(tGATT_IF gatt_if);
extern bool gatt_is_clcb_allocated(uint16_t conn_id);
extern tGATT_CLCB* gatt_clcb_alloc(uint16_t conn_id);
-
-extern bool gatt_tcb_get_cid_available_for_indication(
- tGATT_TCB* p_tcb, bool eatt_support, uint16_t** indicate_handle_p,
- uint16_t* cid_p);
-extern bool gatt_tcb_find_indicate_handle(tGATT_TCB& tcb, uint16_t cid,
- uint16_t* indicated_handle_p);
-extern uint16_t gatt_tcb_get_att_cid(tGATT_TCB& tcb, bool eatt_support);
-extern uint16_t gatt_tcb_get_payload_size_tx(tGATT_TCB& tcb, uint16_t cid);
-extern uint16_t gatt_tcb_get_payload_size_rx(tGATT_TCB& tcb, uint16_t cid);
extern void gatt_clcb_dealloc(tGATT_CLCB* p_clcb);
extern void gatt_sr_copy_prep_cnt_to_cback_cnt(tGATT_TCB& p_tcb);
extern bool gatt_sr_is_cback_cnt_zero(tGATT_TCB& p_tcb);
extern bool gatt_sr_is_prep_cnt_zero(tGATT_TCB& p_tcb);
-extern void gatt_sr_reset_cback_cnt(tGATT_TCB& p_tcb, uint16_t cid);
+extern void gatt_sr_reset_cback_cnt(tGATT_TCB& p_tcb);
extern void gatt_sr_reset_prep_cnt(tGATT_TCB& tcb);
-extern tGATT_SR_CMD* gatt_sr_get_cmd_by_trans_id(tGATT_TCB* p_tcb,
- uint32_t trans_id);
-extern tGATT_SR_CMD* gatt_sr_get_cmd_by_cid(tGATT_TCB& tcb, uint16_t cid);
-extern tGATT_READ_MULTI* gatt_sr_get_read_multi(tGATT_TCB& tcb, uint16_t cid);
-extern void gatt_sr_update_cback_cnt(tGATT_TCB& p_tcb, uint16_t cid,
- tGATT_IF gatt_if, bool is_inc,
- bool is_reset_first);
+extern void gatt_sr_update_cback_cnt(tGATT_TCB& p_tcb, tGATT_IF gatt_if,
+ bool is_inc, bool is_reset_first);
extern void gatt_sr_update_prep_cnt(tGATT_TCB& tcb, tGATT_IF gatt_if,
bool is_inc, bool is_reset_first);
@@ -593,13 +516,12 @@ extern bool gatt_send_ble_burst_data(const RawAddress& remote_bda,
BT_HDR* p_buf);
/* GATT client functions */
-extern void gatt_dequeue_sr_cmd(tGATT_TCB& tcb, uint16_t cid);
-extern tGATT_STATUS gatt_send_write_msg(tGATT_TCB& p_tcb, tGATT_CLCB* p_clcb,
- uint8_t op_code, uint16_t handle,
- uint16_t len, uint16_t offset,
- uint8_t* p_data);
-extern void gatt_cleanup_upon_disc(const RawAddress& bda,
- tGATT_DISCONN_REASON reason,
+extern void gatt_dequeue_sr_cmd(tGATT_TCB& tcb);
+extern uint8_t gatt_send_write_msg(tGATT_TCB& p_tcb, tGATT_CLCB* p_clcb,
+ uint8_t op_code, uint16_t handle,
+ uint16_t len, uint16_t offset,
+ uint8_t* p_data);
+extern void gatt_cleanup_upon_disc(const RawAddress& bda, uint16_t reason,
tBT_TRANSPORT transport);
extern void gatt_end_operation(tGATT_CLCB* p_clcb, tGATT_STATUS status,
void* p_data);
@@ -607,19 +529,17 @@ extern void gatt_end_operation(tGATT_CLCB* p_clcb, tGATT_STATUS status,
extern void gatt_act_discovery(tGATT_CLCB* p_clcb);
extern void gatt_act_read(tGATT_CLCB* p_clcb, uint16_t offset);
extern void gatt_act_write(tGATT_CLCB* p_clcb, uint8_t sec_act);
-extern tGATT_CLCB* gatt_cmd_dequeue(tGATT_TCB& tcb, uint16_t cid,
- uint8_t* p_opcode);
+extern tGATT_CLCB* gatt_cmd_dequeue(tGATT_TCB& tcb, uint8_t* p_opcode);
extern void gatt_cmd_enq(tGATT_TCB& tcb, tGATT_CLCB* p_clcb, bool to_send,
uint8_t op_code, BT_HDR* p_buf);
-extern void gatt_client_handle_server_rsp(tGATT_TCB& tcb, uint16_t cid,
- uint8_t op_code, uint16_t len,
- uint8_t* p_data);
+extern void gatt_client_handle_server_rsp(tGATT_TCB& tcb, uint8_t op_code,
+ uint16_t len, uint8_t* p_data);
extern void gatt_send_queue_write_cancel(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
tGATT_EXEC_FLAG flag);
/* gatt_auth.cc */
extern bool gatt_security_check_start(tGATT_CLCB* p_clcb);
-extern void gatt_verify_signature(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_buf);
+extern void gatt_verify_signature(tGATT_TCB& tcb, BT_HDR* p_buf);
extern tGATT_STATUS gatt_get_link_encrypt_status(tGATT_TCB& tcb);
extern tGATT_SEC_ACTION gatt_get_sec_act(tGATT_TCB* p_tcb);
extern void gatt_set_sec_act(tGATT_TCB* p_tcb, tGATT_SEC_ACTION sec_act);
@@ -634,19 +554,17 @@ extern uint16_t gatts_add_included_service(tGATT_SVC_DB& db, uint16_t s_handle,
extern uint16_t gatts_add_characteristic(tGATT_SVC_DB& db, tGATT_PERM perm,
tGATT_CHAR_PROP property,
const bluetooth::Uuid& char_uuid);
-extern uint16_t gatts_add_char_ext_prop_descr(tGATT_SVC_DB& db,
- uint16_t extended_properties);
extern uint16_t gatts_add_char_descr(tGATT_SVC_DB& db, tGATT_PERM perm,
const bluetooth::Uuid& dscp_uuid);
extern tGATT_STATUS gatts_db_read_attr_value_by_type(
- tGATT_TCB& tcb, uint16_t cid, tGATT_SVC_DB* p_db, uint8_t op_code,
- BT_HDR* p_rsp, uint16_t s_handle, uint16_t e_handle,
- const bluetooth::Uuid& type, uint16_t* p_len, tGATT_SEC_FLAG sec_flag,
- uint8_t key_size, uint32_t trans_id, uint16_t* p_cur_handle);
+ tGATT_TCB& tcb, tGATT_SVC_DB* p_db, uint8_t op_code, BT_HDR* p_rsp,
+ uint16_t s_handle, uint16_t e_handle, const bluetooth::Uuid& type,
+ uint16_t* p_len, tGATT_SEC_FLAG sec_flag, uint8_t key_size,
+ uint32_t trans_id, uint16_t* p_cur_handle);
extern tGATT_STATUS gatts_read_attr_value_by_handle(
- tGATT_TCB& tcb, uint16_t cid, tGATT_SVC_DB* p_db, uint8_t op_code,
- uint16_t handle, uint16_t offset, uint8_t* p_value, uint16_t* p_len,
- uint16_t mtu, tGATT_SEC_FLAG sec_flag, uint8_t key_size, uint32_t trans_id);
+ tGATT_TCB& tcb, tGATT_SVC_DB* p_db, uint8_t op_code, uint16_t handle,
+ uint16_t offset, uint8_t* p_value, uint16_t* p_len, uint16_t mtu,
+ tGATT_SEC_FLAG sec_flag, uint8_t key_size, uint32_t trans_id);
extern tGATT_STATUS gatts_write_attr_perm_check(
tGATT_SVC_DB* p_db, uint8_t op_code, uint16_t handle, uint16_t offset,
uint8_t* p_data, uint16_t len, tGATT_SEC_FLAG sec_flag, uint8_t key_size);
@@ -656,8 +574,4 @@ extern tGATT_STATUS gatts_read_attr_perm_check(tGATT_SVC_DB* p_db, bool is_long,
uint8_t key_size);
extern bluetooth::Uuid* gatts_get_service_uuid(tGATT_SVC_DB* p_db);
-/* gatt_sr_hash.cc */
-extern Octet16 gatts_calculate_database_hash(
- std::list<tGATT_SRV_LIST_ELEM>* lst_ptr);
-
#endif
diff --git a/stack/gatt/gatt_main.cc b/stack/gatt/gatt_main.cc
index 164a86ff1..e0a7b6bb8 100644
--- a/stack/gatt/gatt_main.cc
+++ b/stack/gatt/gatt_main.cc
@@ -26,20 +26,24 @@
#include "bt_common.h"
#include "bt_utils.h"
-#include "btif/include/btif_storage.h"
+#include "btif_storage.h"
+#include "btm_ble_int.h"
+#include "btm_int.h"
#include "connection_manager.h"
#include "device/include/interop.h"
+#include "gatt_int.h"
#include "l2c_api.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/eatt/eatt.h"
-#include "stack/gatt/gatt_int.h"
-#include "stack/include/l2cap_acl_interface.h"
using base::StringPrintf;
-using bluetooth::eatt::EattExtension;
+
+/* Configuration flags. */
+#define GATT_L2C_CFG_IND_DONE (1 << 0)
+#define GATT_L2C_CFG_CFM_DONE (1 << 1)
+
+/* minimum GATT MTU size over BR/EDR link
+ */
+#define GATT_MIN_BR_MTU_SIZE 48
/******************************************************************************/
/* L O C A L F U N C T I O N P R O T O T Y P E S */
@@ -57,30 +61,28 @@ static void gatt_l2cif_connect_ind_cback(const RawAddress& bd_addr,
static void gatt_l2cif_connect_cfm_cback(uint16_t l2cap_cid, uint16_t result);
static void gatt_l2cif_config_ind_cback(uint16_t l2cap_cid,
tL2CAP_CFG_INFO* p_cfg);
-static void gatt_l2cif_config_cfm_cback(uint16_t lcid, uint16_t result,
+static void gatt_l2cif_config_cfm_cback(uint16_t l2cap_cid,
tL2CAP_CFG_INFO* p_cfg);
static void gatt_l2cif_disconnect_ind_cback(uint16_t l2cap_cid,
bool ack_needed);
-static void gatt_l2cif_disconnect(uint16_t l2cap_cid);
+static void gatt_l2cif_disconnect_cfm_cback(uint16_t l2cap_cid,
+ uint16_t result);
static void gatt_l2cif_data_ind_cback(uint16_t l2cap_cid, BT_HDR* p_msg);
static void gatt_send_conn_cback(tGATT_TCB* p_tcb);
static void gatt_l2cif_congest_cback(uint16_t cid, bool congested);
-static void gatt_on_l2cap_error(uint16_t lcid, uint16_t result);
-
-static const tL2CAP_APPL_INFO dyn_info = {
- gatt_l2cif_connect_ind_cback,
- gatt_l2cif_connect_cfm_cback,
- gatt_l2cif_config_ind_cback,
- gatt_l2cif_config_cfm_cback,
- gatt_l2cif_disconnect_ind_cback,
- gatt_l2cif_data_ind_cback,
- gatt_l2cif_congest_cback,
- NULL,
- gatt_on_l2cap_error,
- NULL,
- NULL,
- NULL
-};
+
+static const tL2CAP_APPL_INFO dyn_info = {gatt_l2cif_connect_ind_cback,
+ gatt_l2cif_connect_cfm_cback,
+ NULL,
+ gatt_l2cif_config_ind_cback,
+ gatt_l2cif_config_cfm_cback,
+ gatt_l2cif_disconnect_ind_cback,
+ gatt_l2cif_disconnect_cfm_cback,
+ NULL,
+ gatt_l2cif_data_ind_cback,
+ gatt_l2cif_congest_cback,
+ NULL,
+ NULL /* tL2CA_CREDITS_RECEIVED_CB */};
tGATT_CB gatt_cb;
@@ -103,9 +105,17 @@ void gatt_init(void) {
connection_manager::reset(true);
memset(&fixed_reg, 0, sizeof(tL2CAP_FIXED_CHNL_REG));
+ gatt_cb.def_mtu_size = GATT_DEF_BLE_MTU_SIZE;
gatt_cb.sign_op_queue = fixed_queue_new(SIZE_MAX);
gatt_cb.srv_chg_clt_q = fixed_queue_new(SIZE_MAX);
/* First, register fixed L2CAP channel for ATT over BLE */
+ fixed_reg.fixed_chnl_opts.mode = L2CAP_FCR_BASIC_MODE;
+ fixed_reg.fixed_chnl_opts.max_transmit = 0xFF;
+ fixed_reg.fixed_chnl_opts.rtrans_tout = 2000;
+ fixed_reg.fixed_chnl_opts.mon_tout = 12000;
+ fixed_reg.fixed_chnl_opts.mps = 670;
+ fixed_reg.fixed_chnl_opts.tx_win_sz = 1;
+
fixed_reg.pL2CA_FixedConn_Cb = gatt_le_connect_cback;
fixed_reg.pL2CA_FixedData_Cb = gatt_le_data_ind;
fixed_reg.pL2CA_FixedCong_Cb = gatt_le_cong_cback; /* congestion callback */
@@ -114,11 +124,16 @@ void gatt_init(void) {
L2CA_RegisterFixedChannel(L2CAP_ATT_CID, &fixed_reg);
/* Now, register with L2CAP for ATT PSM over BR/EDR */
- if (!L2CA_Register2(BT_PSM_ATT, dyn_info, false /* enable_snoop */, nullptr,
- GATT_MAX_MTU_SIZE, 0, BTM_SEC_NONE)) {
+ if (!L2CA_Register(BT_PSM_ATT, (tL2CAP_APPL_INFO*)&dyn_info,
+ false /* enable_snoop */, nullptr)) {
LOG(ERROR) << "ATT Dynamic Registration failed";
}
+ BTM_SetSecurityLevel(true, "", BTM_SEC_SERVICE_ATT, BTM_SEC_NONE, BT_PSM_ATT,
+ 0, 0);
+ BTM_SetSecurityLevel(false, "", BTM_SEC_SERVICE_ATT, BTM_SEC_NONE, BT_PSM_ATT,
+ 0, 0);
+
gatt_cb.hdl_cfg.gatt_start_hdl = GATT_GATT_START_HANDLE;
gatt_cb.hdl_cfg.gap_start_hdl = GATT_GAP_START_HANDLE;
gatt_cb.hdl_cfg.app_start_hdl = GATT_APP_START_HANDLE;
@@ -126,8 +141,6 @@ void gatt_init(void) {
gatt_cb.hdl_list_info = new std::list<tGATT_HDL_LIST_ELEM>();
gatt_cb.srv_list_info = new std::list<tGATT_SRV_LIST_ELEM>();
gatt_profile_db_init();
-
- EattExtension::GetInstance()->Start();
}
/*******************************************************************************
@@ -161,39 +174,12 @@ void gatt_free(void) {
fixed_queue_free(gatt_cb.tcb[i].sr_cmd.multi_rsp_q, NULL);
gatt_cb.tcb[i].sr_cmd.multi_rsp_q = NULL;
-
- if (gatt_cb.tcb[i].eatt)
- EattExtension::GetInstance()->FreeGattResources(gatt_cb.tcb[i].peer_bda);
}
gatt_cb.hdl_list_info->clear();
- delete gatt_cb.hdl_list_info;
gatt_cb.hdl_list_info = nullptr;
gatt_cb.srv_list_info->clear();
- delete gatt_cb.srv_list_info;
gatt_cb.srv_list_info = nullptr;
-
- EattExtension::GetInstance()->Stop();
-}
-
-void gatt_find_in_device_record(const RawAddress& bd_addr,
- tBLE_BD_ADDR* address_with_type) {
- const tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
- if (p_dev_rec == nullptr) {
- return;
- }
-
- if (p_dev_rec->device_type & BT_DEVICE_TYPE_BLE) {
- if (p_dev_rec->ble.identity_address_with_type.bda.IsEmpty()) {
- *address_with_type = {.type = p_dev_rec->ble.ble_addr_type,
- .bda = bd_addr};
- return;
- }
- *address_with_type = p_dev_rec->ble.identity_address_with_type;
- return;
- }
- *address_with_type = {.type = BLE_ADDR_PUBLIC, .bda = bd_addr};
- return;
}
/*******************************************************************************
@@ -215,7 +201,7 @@ bool gatt_connect(const RawAddress& rem_bda, tGATT_TCB* p_tcb,
gatt_set_ch_state(p_tcb, GATT_CH_CONN);
if (transport != BT_TRANSPORT_LE) {
- p_tcb->att_lcid = L2CA_ConnectReq2(BT_PSM_ATT, rem_bda, BTM_SEC_NONE);
+ p_tcb->att_lcid = L2CA_ConnectReq(BT_PSM_ATT, rem_bda);
return p_tcb->att_lcid != 0;
}
@@ -226,7 +212,7 @@ bool gatt_connect(const RawAddress& rem_bda, tGATT_TCB* p_tcb,
}
p_tcb->att_lcid = L2CAP_ATT_CID;
- return acl_create_le_connection_with_id(gatt_if, rem_bda);
+ return connection_manager::direct_connect_add(gatt_if, rem_bda);
}
/*******************************************************************************
@@ -252,25 +238,25 @@ bool gatt_disconnect(tGATT_TCB* p_tcb) {
return true;
}
+ bool ret = true;
if (p_tcb->att_lcid == L2CAP_ATT_CID) {
if (ch_state == GATT_CH_OPEN) {
- L2CA_RemoveFixedChnl(L2CAP_ATT_CID, p_tcb->peer_bda);
- gatt_set_ch_state(p_tcb, GATT_CH_CLOSING);
+ /* only LCB exist between remote device and local */
+ ret = L2CA_RemoveFixedChnl(L2CAP_ATT_CID, p_tcb->peer_bda);
} else {
- connection_manager::direct_connect_remove(CONN_MGR_ID_L2CAP,
- p_tcb->peer_bda);
- gatt_cleanup_upon_disc(p_tcb->peer_bda, GATT_CONN_TERMINATE_LOCAL_HOST,
- p_tcb->transport);
+ L2CA_CancelBleConnectReq(p_tcb->peer_bda);
+ gatt_cleanup_upon_disc(p_tcb->peer_bda, HCI_ERR_CONN_CAUSE_LOCAL_HOST, p_tcb->transport);
+ return true;
}
+ gatt_set_ch_state(p_tcb, GATT_CH_CLOSING);
} else {
- if ((ch_state == GATT_CH_OPEN) || (ch_state == GATT_CH_CFG)) {
- gatt_l2cif_disconnect(p_tcb->att_lcid);
- } else {
+ if ((ch_state == GATT_CH_OPEN) || (ch_state == GATT_CH_CFG))
+ ret = L2CA_DisconnectReq(p_tcb->att_lcid);
+ else
VLOG(1) << __func__ << " gatt_disconnect channel not opened";
- }
}
- return true;
+ return ret;
}
/*******************************************************************************
@@ -349,10 +335,6 @@ void gatt_update_app_use_link_flag(tGATT_IF gatt_if, tGATT_TCB* p_tcb,
if (p_tcb->app_hold_link.empty()) {
// acl link is connected but no application needs to use the link
if (p_tcb->att_lcid == L2CAP_ATT_CID && is_valid_handle) {
-
- /* Drop EATT before closing ATT */
- EattExtension::GetInstance()->Disconnect(p_tcb->peer_bda);
-
/* for fixed channel, set the timeout value to
GATT_LINK_IDLE_TIMEOUT_WHEN_NO_APP seconds */
VLOG(1) << " start link idle timer = "
@@ -420,10 +402,8 @@ static void gatt_le_connect_cback(uint16_t chan, const RawAddress& bd_addr,
bool check_srv_chg = false;
tGATTS_SRV_CHG* p_srv_chg_clt = NULL;
- if (transport == BT_TRANSPORT_BR_EDR) {
- LOG_WARN("Ignoring fixed channel connect/disconnect on br_edr for GATT");
- return;
- }
+ /* ignore all fixed channel connect/disconnect on BR/EDR link for GATT */
+ if (transport == BT_TRANSPORT_BR_EDR) return;
VLOG(1) << "GATT ATT protocol channel with BDA: " << bd_addr << " is "
<< ((connected) ? "connected" : "disconnected");
@@ -437,8 +417,8 @@ static void gatt_le_connect_cback(uint16_t chan, const RawAddress& bd_addr,
}
if (!connected) {
- gatt_cleanup_upon_disc(bd_addr, static_cast<tGATT_DISCONN_REASON>(reason),
- transport);
+ gatt_cleanup_upon_disc(bd_addr, reason, transport);
+ VLOG(1) << "ATT disconnected";
return;
}
@@ -474,8 +454,6 @@ static void gatt_le_connect_cback(uint16_t chan, const RawAddress& bd_addr,
gatt_chk_srv_chg(p_srv_chg_clt);
}
}
-
- EattExtension::GetInstance()->Connect(bd_addr);
}
/** This function is called to process the congestion callback from lcb */
@@ -499,11 +477,11 @@ static void gatt_channel_congestion(tGATT_TCB* p_tcb, bool congested) {
}
}
-void gatt_notify_phy_updated(tGATT_STATUS status, uint16_t handle,
- uint8_t tx_phy, uint8_t rx_phy) {
+void gatt_notify_phy_updated(uint8_t status, uint16_t handle, uint8_t tx_phy,
+ uint8_t rx_phy) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev_by_handle(handle);
if (!p_dev_rec) {
- LOG_WARN("No Device Found!");
+ BTM_TRACE_WARNING("%s: No Device Found!", __func__);
return;
}
@@ -521,11 +499,14 @@ void gatt_notify_phy_updated(tGATT_STATUS status, uint16_t handle,
}
}
-void gatt_notify_conn_update(const RawAddress& remote, uint16_t interval,
+void gatt_notify_conn_update(uint16_t handle, uint16_t interval,
uint16_t latency, uint16_t timeout,
- tHCI_STATUS status) {
- tGATT_TCB* p_tcb = gatt_find_tcb_by_addr(remote, BT_TRANSPORT_LE);
+ uint8_t status) {
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev_by_handle(handle);
+ if (!p_dev_rec) return;
+ tGATT_TCB* p_tcb =
+ gatt_find_tcb_by_addr(p_dev_rec->ble.pseudo_addr, BT_TRANSPORT_LE);
if (!p_tcb) return;
for (int i = 0; i < GATT_MAX_APPS; i++) {
@@ -533,8 +514,7 @@ void gatt_notify_conn_update(const RawAddress& remote, uint16_t interval,
if (p_reg->in_use && p_reg->app_cb.p_conn_update_cb) {
uint16_t conn_id = GATT_CREATE_CONN_ID(p_tcb->tcb_idx, p_reg->gatt_if);
(*p_reg->app_cb.p_conn_update_cb)(p_reg->gatt_if, conn_id, interval,
- latency, timeout,
- static_cast<tGATT_STATUS>(status));
+ latency, timeout, status);
}
}
}
@@ -575,7 +555,7 @@ static void gatt_le_data_ind(uint16_t chan, const RawAddress& bd_addr,
LOG(WARNING) << "ATT - Ignored L2CAP data while in state: "
<< +gatt_get_ch_state(p_tcb);
} else
- gatt_data_process(*p_tcb, L2CAP_ATT_CID, p_buf);
+ gatt_data_process(*p_tcb, p_buf);
}
osi_free(p_buf);
@@ -614,30 +594,28 @@ static void gatt_l2cif_connect_ind_cback(const RawAddress& bd_addr,
result = L2CAP_CONN_NO_RESOURCES;
}
- /* If we reject the connection, send DisconnectReq */
- if (result != L2CAP_CONN_OK) {
- L2CA_DisconnectReq(lcid);
- return;
- }
+ /* Send L2CAP connect rsp */
+ L2CA_ConnectRsp(bd_addr, id, lcid, result, 0);
+
+ /* if result ok, proceed with connection */
+ if (result != L2CAP_CONN_OK) return;
/* transition to configuration state */
gatt_set_ch_state(p_tcb, GATT_CH_CFG);
-}
-static void gatt_on_l2cap_error(uint16_t lcid, uint16_t result) {
- tGATT_TCB* p_tcb = gatt_find_tcb_by_cid(lcid);
- if (p_tcb == nullptr) return;
- if (gatt_get_ch_state(p_tcb) == GATT_CH_CONN) {
- gatt_cleanup_upon_disc(p_tcb->peer_bda, GATT_CONN_L2C_FAILURE,
- BT_TRANSPORT_BR_EDR);
- } else {
- gatt_l2cif_disconnect(lcid);
- }
+ /* Send L2CAP config req */
+ tL2CAP_CFG_INFO cfg;
+ memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ cfg.mtu_present = true;
+ cfg.mtu = GATT_MAX_MTU_SIZE;
+
+ L2CA_ConfigReq(lcid, &cfg);
}
/** This is the L2CAP connect confirm callback function */
static void gatt_l2cif_connect_cfm_cback(uint16_t lcid, uint16_t result) {
tGATT_TCB* p_tcb;
+ tL2CAP_CFG_INFO cfg;
/* look up clcb for this channel */
p_tcb = gatt_find_tcb_by_cid(lcid);
@@ -647,17 +625,35 @@ static void gatt_l2cif_connect_cfm_cback(uint16_t lcid, uint16_t result) {
<< StringPrintf(" result: %d ch_state: %d, lcid:0x%x", result,
gatt_get_ch_state(p_tcb), p_tcb->att_lcid);
- if (gatt_get_ch_state(p_tcb) == GATT_CH_CONN && result == L2CAP_CONN_OK) {
- gatt_set_ch_state(p_tcb, GATT_CH_CFG);
- } else {
- gatt_on_l2cap_error(lcid, result);
+ /* if in correct state */
+ if (gatt_get_ch_state(p_tcb) == GATT_CH_CONN) {
+ /* if result successful */
+ if (result == L2CAP_CONN_OK) {
+ /* set channel state */
+ gatt_set_ch_state(p_tcb, GATT_CH_CFG);
+
+ /* Send L2CAP config req */
+ memset(&cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ cfg.mtu_present = true;
+ cfg.mtu = GATT_MAX_MTU_SIZE;
+ L2CA_ConfigReq(lcid, &cfg);
+ }
+ /* else initiating connection failure */
+ else {
+ gatt_cleanup_upon_disc(p_tcb->peer_bda, result, GATT_TRANSPORT_BR_EDR);
+ }
+ } else /* wrong state, disconnect it */
+ {
+ if (result == L2CAP_CONN_OK) {
+ /* just in case the peer also accepts our connection - Send L2CAP
+ * disconnect req */
+ L2CA_DisconnectReq(lcid);
+ }
}
}
/** This is the L2CAP config confirm callback function */
-void gatt_l2cif_config_cfm_cback(uint16_t lcid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
- gatt_l2cif_config_ind_cback(lcid, p_cfg);
+void gatt_l2cif_config_cfm_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
/* look up clcb for this channel */
tGATT_TCB* p_tcb = gatt_find_tcb_by_cid(lcid);
@@ -666,6 +662,19 @@ void gatt_l2cif_config_cfm_cback(uint16_t lcid, uint16_t initiator,
/* if in incorrect state */
if (gatt_get_ch_state(p_tcb) != GATT_CH_CFG) return;
+ /* if result not successful */
+ if (p_cfg->result != L2CAP_CFG_OK) {
+ /* Send L2CAP disconnect req */
+ L2CA_DisconnectReq(lcid);
+ return;
+ }
+
+ /* update flags */
+ p_tcb->ch_flags |= GATT_L2C_CFG_CFM_DONE;
+
+ /* if configuration not complete */
+ if (!(p_tcb->ch_flags & GATT_L2C_CFG_IND_DONE)) return;
+
gatt_set_ch_state(p_tcb, GATT_CH_OPEN);
tGATTS_SRV_CHG* p_srv_chg_clt =
@@ -683,15 +692,43 @@ void gatt_l2cif_config_cfm_cback(uint16_t lcid, uint16_t initiator,
/** This is the L2CAP config indication callback function */
void gatt_l2cif_config_ind_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
+ tGATTS_SRV_CHG* p_srv_chg_clt = NULL;
/* look up clcb for this channel */
tGATT_TCB* p_tcb = gatt_find_tcb_by_cid(lcid);
if (!p_tcb) return;
/* GATT uses the smaller of our MTU and peer's MTU */
- if (p_cfg->mtu_present && p_cfg->mtu < L2CAP_DEFAULT_MTU)
+ if (p_cfg->mtu_present &&
+ (p_cfg->mtu >= GATT_MIN_BR_MTU_SIZE && p_cfg->mtu < L2CAP_DEFAULT_MTU))
p_tcb->payload_size = p_cfg->mtu;
else
p_tcb->payload_size = L2CAP_DEFAULT_MTU;
+
+ /* send L2CAP configure response */
+ memset(p_cfg, 0, sizeof(tL2CAP_CFG_INFO));
+ p_cfg->result = L2CAP_CFG_OK;
+ L2CA_ConfigRsp(lcid, p_cfg);
+
+ /* if not first config ind */
+ if ((p_tcb->ch_flags & GATT_L2C_CFG_IND_DONE)) return;
+
+ /* update flags */
+ p_tcb->ch_flags |= GATT_L2C_CFG_IND_DONE;
+
+ /* if configuration not complete */
+ if ((p_tcb->ch_flags & GATT_L2C_CFG_CFM_DONE) == 0) return;
+
+ gatt_set_ch_state(p_tcb, GATT_CH_OPEN);
+ p_srv_chg_clt = gatt_is_bda_in_the_srv_chg_clt_list(p_tcb->peer_bda);
+ if (p_srv_chg_clt != NULL) {
+ gatt_chk_srv_chg(p_srv_chg_clt);
+ } else {
+ if (btm_sec_is_a_bonded_dev(p_tcb->peer_bda))
+ gatt_add_a_bonded_dev_for_srv_chg(p_tcb->peer_bda);
+ }
+
+ /* send callback */
+ gatt_send_conn_cback(p_tcb);
}
/** This is the L2CAP disconnect indication callback function */
@@ -701,17 +738,27 @@ void gatt_l2cif_disconnect_ind_cback(uint16_t lcid, bool ack_needed) {
tGATT_TCB* p_tcb = gatt_find_tcb_by_cid(lcid);
if (!p_tcb) return;
+ if (ack_needed) {
+ /* send L2CAP disconnect response */
+ L2CA_DisconnectRsp(lcid);
+ }
+
if (gatt_is_bda_in_the_srv_chg_clt_list(p_tcb->peer_bda) == NULL) {
if (btm_sec_is_a_bonded_dev(p_tcb->peer_bda))
gatt_add_a_bonded_dev_for_srv_chg(p_tcb->peer_bda);
}
+ /* if ACL link is still up, no reason is logged, l2cap is disconnect from
+ * peer */
+ uint16_t reason = L2CA_GetDisconnectReason(p_tcb->peer_bda, p_tcb->transport);
+ if (reason == 0) reason = GATT_CONN_TERMINATE_PEER_USER;
+
/* send disconnect callback */
- gatt_cleanup_upon_disc(p_tcb->peer_bda, GATT_CONN_TERMINATE_PEER_USER,
- BT_TRANSPORT_BR_EDR);
+ gatt_cleanup_upon_disc(p_tcb->peer_bda, reason, GATT_TRANSPORT_BR_EDR);
}
-static void gatt_l2cif_disconnect(uint16_t lcid) {
- L2CA_DisconnectReq(lcid);
+/** This is the L2CAP disconnect confirm callback function */
+static void gatt_l2cif_disconnect_cfm_cback(uint16_t lcid,
+ UNUSED_ATTR uint16_t result) {
/* look up clcb for this channel */
tGATT_TCB* p_tcb = gatt_find_tcb_by_cid(lcid);
@@ -723,8 +770,13 @@ static void gatt_l2cif_disconnect(uint16_t lcid) {
gatt_add_a_bonded_dev_for_srv_chg(p_tcb->peer_bda);
}
- gatt_cleanup_upon_disc(p_tcb->peer_bda, GATT_CONN_TERMINATE_LOCAL_HOST,
- BT_TRANSPORT_BR_EDR);
+ /* send disconnect callback */
+ /* if ACL link is still up, no reason is logged, l2cap is disconnect from
+ * peer */
+ uint16_t reason = L2CA_GetDisconnectReason(p_tcb->peer_bda, p_tcb->transport);
+ if (reason == 0) reason = GATT_CONN_TERMINATE_LOCAL_HOST;
+
+ gatt_cleanup_upon_disc(p_tcb->peer_bda, reason, GATT_TRANSPORT_BR_EDR);
}
/** This is the L2CAP data indication callback function */
@@ -733,7 +785,7 @@ static void gatt_l2cif_data_ind_cback(uint16_t lcid, BT_HDR* p_buf) {
tGATT_TCB* p_tcb = gatt_find_tcb_by_cid(lcid);
if (p_tcb && gatt_get_ch_state(p_tcb) == GATT_CH_OPEN) {
/* process the data */
- gatt_data_process(*p_tcb, lcid, p_buf);
+ gatt_data_process(*p_tcb, p_buf);
}
osi_free(p_buf);
@@ -766,9 +818,8 @@ static void gatt_send_conn_cback(tGATT_TCB* p_tcb) {
if (p_reg->app_cb.p_conn_cb) {
conn_id = GATT_CREATE_CONN_ID(p_tcb->tcb_idx, p_reg->gatt_if);
- (*p_reg->app_cb.p_conn_cb)(p_reg->gatt_if, p_tcb->peer_bda, conn_id,
- kGattConnected, GATT_CONN_OK,
- p_tcb->transport);
+ (*p_reg->app_cb.p_conn_cb)(p_reg->gatt_if, p_tcb->peer_bda, conn_id, true,
+ 0, p_tcb->transport);
}
}
@@ -799,7 +850,7 @@ static void gatt_send_conn_cback(tGATT_TCB* p_tcb) {
* Returns void
*
******************************************************************************/
-void gatt_data_process(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_buf) {
+void gatt_data_process(tGATT_TCB& tcb, BT_HDR* p_buf) {
uint8_t* p = (uint8_t*)(p_buf + 1) + p_buf->offset;
uint8_t op_code, pseudo_op_code;
@@ -819,18 +870,18 @@ void gatt_data_process(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_buf) {
*/
LOG(ERROR) << __func__
<< ": ATT - Rcvd L2CAP data, unknown cmd: " << loghex(op_code);
- gatt_send_error_rsp(tcb, cid, GATT_REQ_NOT_SUPPORTED, op_code, 0, false);
+ gatt_send_error_rsp(tcb, GATT_REQ_NOT_SUPPORTED, op_code, 0, false);
return;
}
if (op_code == GATT_SIGN_CMD_WRITE) {
- gatt_verify_signature(tcb, cid, p_buf);
+ gatt_verify_signature(tcb, p_buf);
} else {
/* message from client */
if ((op_code % 2) == 0)
- gatt_server_handle_client_req(tcb, cid, op_code, msg_len, p);
+ gatt_server_handle_client_req(tcb, op_code, msg_len, p);
else
- gatt_client_handle_server_rsp(tcb, cid, op_code, msg_len, p);
+ gatt_client_handle_server_rsp(tcb, op_code, msg_len, p);
}
}
@@ -960,7 +1011,7 @@ void gatt_set_ch_state(tGATT_TCB* p_tcb, tGATT_CH_STATE ch_state) {
if (!p_tcb) return;
VLOG(1) << __func__ << ": old=" << +p_tcb->ch_state
- << " new=" << loghex(static_cast<uint8_t>(ch_state));
+ << " new=" << loghex(ch_state);
p_tcb->ch_state = ch_state;
}
diff --git a/stack/gatt/gatt_sr.cc b/stack/gatt/gatt_sr.cc
index c0aedfafa..4b4b5da6f 100644
--- a/stack/gatt/gatt_sr.cc
+++ b/stack/gatt/gatt_sr.cc
@@ -21,22 +21,21 @@
* this file contains the GATT server functions
*
******************************************************************************/
+
#include "bt_target.h"
+#include "bt_utils.h"
#include "osi/include/osi.h"
+#include <log/log.h>
#include <string.h>
#include "gatt_int.h"
#include "l2c_api.h"
-#include "osi/include/log.h"
-#include "stack/eatt/eatt.h"
-#include "stack/l2cap/l2c_int.h"
+#include "l2c_int.h"
#define GATT_MTU_REQ_MIN_LEN 2
using base::StringPrintf;
using bluetooth::Uuid;
-using bluetooth::eatt::EattExtension;
-using bluetooth::eatt::EattChannel;
/*******************************************************************************
*
@@ -48,22 +47,10 @@ using bluetooth::eatt::EattChannel;
* Returns void
*
******************************************************************************/
-uint32_t gatt_sr_enqueue_cmd(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
- uint16_t handle) {
- tGATT_SR_CMD* p_cmd;
-
- if (cid == tcb.att_lcid) {
- p_cmd = &tcb.sr_cmd;
- } else {
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
- p_cmd = &channel->server_outstanding_cmd_;
- }
-
+uint32_t gatt_sr_enqueue_cmd(tGATT_TCB& tcb, uint8_t op_code, uint16_t handle) {
+ tGATT_SR_CMD* p_cmd = &tcb.sr_cmd;
uint32_t trans_id = 0;
- p_cmd->cid = cid;
-
if ((p_cmd->op_code == 0) ||
(op_code == GATT_HANDLE_VALUE_CONF)) /* no pending request */
{
@@ -92,14 +79,7 @@ uint32_t gatt_sr_enqueue_cmd(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
* Returns true if empty, false if there is pending command.
*
******************************************************************************/
-bool gatt_sr_cmd_empty(tGATT_TCB& tcb, uint16_t cid) {
- if (cid == tcb.att_lcid) return (tcb.sr_cmd.op_code == 0);
-
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
-
- return (channel->server_outstanding_cmd_.op_code == 0);
-}
+bool gatt_sr_cmd_empty(tGATT_TCB& tcb) { return (tcb.sr_cmd.op_code == 0); }
/*******************************************************************************
*
@@ -110,114 +90,17 @@ bool gatt_sr_cmd_empty(tGATT_TCB& tcb, uint16_t cid) {
* Returns void
*
******************************************************************************/
-void gatt_dequeue_sr_cmd(tGATT_TCB& tcb, uint16_t cid) {
- tGATT_SR_CMD* p_cmd;
-
- if (cid == tcb.att_lcid) {
- p_cmd = &tcb.sr_cmd;
- } else {
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
-
- p_cmd = &channel->server_outstanding_cmd_;
- }
-
+void gatt_dequeue_sr_cmd(tGATT_TCB& tcb) {
/* Double check in case any buffers are queued */
- VLOG(1) << "gatt_dequeue_sr_cmd cid: " << loghex(cid);
- if (p_cmd->p_rsp_msg)
- LOG(ERROR) << "free tcb.sr_cmd.p_rsp_msg = "
- << p_cmd->p_rsp_msg;
- osi_free_and_reset((void**)&p_cmd->p_rsp_msg);
-
- while (!fixed_queue_is_empty(p_cmd->multi_rsp_q))
- osi_free(fixed_queue_try_dequeue(p_cmd->multi_rsp_q));
- fixed_queue_free(p_cmd->multi_rsp_q, NULL);
- memset(p_cmd, 0, sizeof(tGATT_SR_CMD));
-}
-
-static void build_read_multi_rsp(tGATT_SR_CMD* p_cmd, uint16_t mtu) {
- uint16_t ii, total_len, len;
- uint8_t* p;
- bool is_overflow = false;
-
- len = sizeof(BT_HDR) + L2CAP_MIN_OFFSET + mtu;
- BT_HDR* p_buf = (BT_HDR*)osi_calloc(len);
- p_buf->offset = L2CAP_MIN_OFFSET;
- p = (uint8_t*)(p_buf + 1) + p_buf->offset;
-
- /* First byte in the response is the opcode */
- if (p_cmd->multi_req.variable_len)
- *p++ = GATT_RSP_READ_MULTI_VAR;
- else
- *p++ = GATT_RSP_READ_MULTI;
-
- p_buf->len = 1;
-
- /* Now walk through the buffers putting the data into the response in order
- */
- list_t* list = NULL;
- const list_node_t* node = NULL;
- if (!fixed_queue_is_empty(p_cmd->multi_rsp_q))
- list = fixed_queue_get_list(p_cmd->multi_rsp_q);
- for (ii = 0; ii < p_cmd->multi_req.num_handles; ii++) {
- tGATTS_RSP* p_rsp = NULL;
-
- if (list != NULL) {
- if (ii == 0)
- node = list_begin(list);
- else
- node = list_next(node);
- if (node != list_end(list)) p_rsp = (tGATTS_RSP*)list_node(node);
- }
-
- if (p_rsp != NULL) {
- total_len = (p_buf->len + p_rsp->attr_value.len);
-
- if (total_len > mtu) {
- /* just send the partial response for the overflow case */
- len = p_rsp->attr_value.len - (total_len - mtu);
- is_overflow = true;
- VLOG(1) << StringPrintf(
- "multi read overflow available len=%d val_len=%d", len,
- p_rsp->attr_value.len);
- } else {
- len = p_rsp->attr_value.len;
- }
-
- if (p_cmd->multi_req.variable_len) {
- UINT16_TO_STREAM(p, len);
- p_buf->len += 2;
- }
-
- if (p_rsp->attr_value.handle == p_cmd->multi_req.handles[ii]) {
- memcpy(p, p_rsp->attr_value.value, len);
- if (!is_overflow) p += len;
- p_buf->len += len;
- } else {
- p_cmd->status = GATT_NOT_FOUND;
- break;
- }
-
- if (is_overflow) break;
-
- } else {
- p_cmd->status = GATT_NOT_FOUND;
- break;
- }
-
- } /* loop through all handles*/
-
- /* Sanity check on the buffer length */
- if (p_buf->len == 0) {
- LOG(ERROR) << __func__ << " nothing found!!";
- p_cmd->status = GATT_NOT_FOUND;
- osi_free(p_buf);
- VLOG(1) << __func__ << "osi_free(p_buf)";
- } else if (p_cmd->p_rsp_msg != NULL) {
- osi_free(p_buf);
- } else {
- p_cmd->p_rsp_msg = p_buf;
- }
+ VLOG(1) << "gatt_dequeue_sr_cmd";
+ if (tcb.sr_cmd.p_rsp_msg)
+ LOG(ERROR) << "free tcb.sr_cmd.p_rsp_msg = " << tcb.sr_cmd.p_rsp_msg;
+ osi_free_and_reset((void**)&tcb.sr_cmd.p_rsp_msg);
+
+ while (!fixed_queue_is_empty(tcb.sr_cmd.multi_rsp_q))
+ osi_free(fixed_queue_try_dequeue(tcb.sr_cmd.multi_rsp_q));
+ fixed_queue_free(tcb.sr_cmd.multi_rsp_q, NULL);
+ memset(&tcb.sr_cmd, 0, sizeof(tGATT_SR_CMD));
}
/*******************************************************************************
@@ -231,6 +114,10 @@ static void build_read_multi_rsp(tGATT_SR_CMD* p_cmd, uint16_t mtu) {
******************************************************************************/
static bool process_read_multi_rsp(tGATT_SR_CMD* p_cmd, tGATT_STATUS status,
tGATTS_RSP* p_msg, uint16_t mtu) {
+ uint16_t ii, total_len, len;
+ uint8_t* p;
+ bool is_overflow = false;
+
VLOG(1) << StringPrintf("%s status=%d mtu=%d", __func__, status, mtu);
if (p_cmd->multi_rsp_q == NULL)
@@ -244,12 +131,80 @@ static bool process_read_multi_rsp(tGATT_SR_CMD* p_cmd, tGATT_STATUS status,
p_cmd->status = status;
if (status == GATT_SUCCESS) {
VLOG(1) << "Multi read count=" << fixed_queue_length(p_cmd->multi_rsp_q)
- << " num_hdls=" << p_cmd->multi_req.num_handles
- << " variable=" << p_cmd->multi_req.variable_len;
+ << " num_hdls=" << p_cmd->multi_req.num_handles;
/* Wait till we get all the responses */
if (fixed_queue_length(p_cmd->multi_rsp_q) ==
p_cmd->multi_req.num_handles) {
- build_read_multi_rsp(p_cmd, mtu);
+ len = sizeof(BT_HDR) + L2CAP_MIN_OFFSET + mtu;
+ p_buf = (BT_HDR*)osi_calloc(len);
+ p_buf->offset = L2CAP_MIN_OFFSET;
+ p = (uint8_t*)(p_buf + 1) + p_buf->offset;
+
+ /* First byte in the response is the opcode */
+ *p++ = GATT_RSP_READ_MULTI;
+ p_buf->len = 1;
+
+ /* Now walk through the buffers puting the data into the response in order
+ */
+ list_t* list = NULL;
+ const list_node_t* node = NULL;
+ if (!fixed_queue_is_empty(p_cmd->multi_rsp_q))
+ list = fixed_queue_get_list(p_cmd->multi_rsp_q);
+ for (ii = 0; ii < p_cmd->multi_req.num_handles; ii++) {
+ tGATTS_RSP* p_rsp = NULL;
+
+ if (list != NULL) {
+ if (ii == 0)
+ node = list_begin(list);
+ else
+ node = list_next(node);
+ if (node != list_end(list)) p_rsp = (tGATTS_RSP*)list_node(node);
+ }
+
+ if (p_rsp != NULL) {
+ total_len = (p_buf->len + p_rsp->attr_value.len);
+
+ if (total_len > mtu) {
+ /* just send the partial response for the overflow case */
+ len = p_rsp->attr_value.len - (total_len - mtu);
+ is_overflow = true;
+ VLOG(1) << StringPrintf(
+ "multi read overflow available len=%d val_len=%d", len,
+ p_rsp->attr_value.len);
+ } else {
+ len = p_rsp->attr_value.len;
+ }
+
+ if (p_rsp->attr_value.handle == p_cmd->multi_req.handles[ii]) {
+ memcpy(p, p_rsp->attr_value.value, len);
+ if (!is_overflow) p += len;
+ p_buf->len += len;
+ } else {
+ p_cmd->status = GATT_NOT_FOUND;
+ break;
+ }
+
+ if (is_overflow) break;
+
+ } else {
+ p_cmd->status = GATT_NOT_FOUND;
+ break;
+ }
+
+ } /* loop through all handles*/
+
+ /* Sanity check on the buffer length */
+ if (p_buf->len == 0) {
+ LOG(ERROR) << __func__ << " nothing found!!";
+ p_cmd->status = GATT_NOT_FOUND;
+ osi_free(p_buf);
+ VLOG(1) << __func__ << "osi_free(p_buf)";
+ } else if (p_cmd->p_rsp_msg != NULL) {
+ osi_free(p_buf);
+ } else {
+ p_cmd->p_rsp_msg = p_buf;
+ }
+
return (true);
}
} else /* any handle read exception occurs, return error */
@@ -274,48 +229,45 @@ static bool process_read_multi_rsp(tGATT_SR_CMD* p_cmd, tGATT_STATUS status,
tGATT_STATUS gatt_sr_process_app_rsp(tGATT_TCB& tcb, tGATT_IF gatt_if,
UNUSED_ATTR uint32_t trans_id,
uint8_t op_code, tGATT_STATUS status,
- tGATTS_RSP* p_msg,
- tGATT_SR_CMD* sr_res_p) {
+ tGATTS_RSP* p_msg) {
tGATT_STATUS ret_code = GATT_SUCCESS;
- uint16_t payload_size = gatt_tcb_get_payload_size_rx(tcb, sr_res_p->cid);
VLOG(1) << __func__ << " gatt_if=" << +gatt_if;
- gatt_sr_update_cback_cnt(tcb, sr_res_p->cid, gatt_if, false, false);
+ gatt_sr_update_cback_cnt(tcb, gatt_if, false, false);
- if ((op_code == GATT_REQ_READ_MULTI) ||
- (op_code == GATT_REQ_READ_MULTI_VAR)) {
+ if (op_code == GATT_REQ_READ_MULTI) {
/* If no error and still waiting, just return */
- if (!process_read_multi_rsp(sr_res_p, status, p_msg, payload_size))
+ if (!process_read_multi_rsp(&tcb.sr_cmd, status, p_msg, tcb.payload_size))
return (GATT_SUCCESS);
} else {
if (op_code == GATT_REQ_PREPARE_WRITE && status == GATT_SUCCESS)
gatt_sr_update_prep_cnt(tcb, gatt_if, true, false);
if (op_code == GATT_REQ_EXEC_WRITE && status != GATT_SUCCESS)
- gatt_sr_reset_cback_cnt(tcb, sr_res_p->cid);
+ gatt_sr_reset_cback_cnt(tcb);
- sr_res_p->status = status;
+ tcb.sr_cmd.status = status;
if (gatt_sr_is_cback_cnt_zero(tcb) && status == GATT_SUCCESS) {
- if (sr_res_p->p_rsp_msg == NULL) {
- sr_res_p->p_rsp_msg = attp_build_sr_msg(tcb, (uint8_t)(op_code + 1),
- (tGATT_SR_MSG*)p_msg);
+ if (tcb.sr_cmd.p_rsp_msg == NULL) {
+ tcb.sr_cmd.p_rsp_msg = attp_build_sr_msg(tcb, (uint8_t)(op_code + 1),
+ (tGATT_SR_MSG*)p_msg);
} else {
LOG(ERROR) << "Exception!!! already has respond message";
}
}
}
if (gatt_sr_is_cback_cnt_zero(tcb)) {
- if ((sr_res_p->status == GATT_SUCCESS) && (sr_res_p->p_rsp_msg)) {
- ret_code = attp_send_sr_msg(tcb, sr_res_p->cid, sr_res_p->p_rsp_msg);
- sr_res_p->p_rsp_msg = NULL;
+ if ((tcb.sr_cmd.status == GATT_SUCCESS) && (tcb.sr_cmd.p_rsp_msg)) {
+ ret_code = attp_send_sr_msg(tcb, tcb.sr_cmd.p_rsp_msg);
+ tcb.sr_cmd.p_rsp_msg = NULL;
} else {
- ret_code = gatt_send_error_rsp(tcb, sr_res_p->cid, status, op_code,
- sr_res_p->handle, false);
+ ret_code =
+ gatt_send_error_rsp(tcb, status, op_code, tcb.sr_cmd.handle, false);
}
- gatt_dequeue_sr_cmd(tcb, sr_res_p->cid);
+ gatt_dequeue_sr_cmd(tcb);
}
VLOG(1) << __func__ << " ret_code=" << +ret_code;
@@ -333,8 +285,8 @@ tGATT_STATUS gatt_sr_process_app_rsp(tGATT_TCB& tcb, tGATT_IF gatt_if,
* Returns void
*
******************************************************************************/
-void gatt_process_exec_write_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
- uint16_t len, uint8_t* p_data) {
+void gatt_process_exec_write_req(tGATT_TCB& tcb, uint8_t op_code, uint16_t len,
+ uint8_t* p_data) {
uint8_t *p = p_data, flag, i = 0;
uint32_t trans_id = 0;
tGATT_IF gatt_if;
@@ -346,7 +298,7 @@ void gatt_process_exec_write_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
<< "Conformance tst: forced err rspv for Execute Write: error status="
<< +gatt_cb.err_status;
- gatt_send_error_rsp(tcb, cid, gatt_cb.err_status, gatt_cb.req_op_code,
+ gatt_send_error_rsp(tcb, gatt_cb.err_status, gatt_cb.req_op_code,
gatt_cb.handle, false);
return;
@@ -356,8 +308,7 @@ void gatt_process_exec_write_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
if (len < sizeof(flag)) {
android_errorWriteLog(0x534e4554, "73172115");
LOG(ERROR) << __func__ << "invalid length";
- gatt_send_error_rsp(tcb, cid, GATT_INVALID_PDU, GATT_REQ_EXEC_WRITE, 0,
- false);
+ gatt_send_error_rsp(tcb, GATT_INVALID_PDU, GATT_REQ_EXEC_WRITE, 0, false);
return;
}
@@ -368,7 +319,7 @@ void gatt_process_exec_write_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
/* no prep write is queued */
if (!gatt_sr_is_prep_cnt_zero(tcb)) {
- trans_id = gatt_sr_enqueue_cmd(tcb, cid, op_code, 0);
+ trans_id = gatt_sr_enqueue_cmd(tcb, op_code, 0);
gatt_sr_copy_prep_cnt_to_cback_cnt(tcb);
for (i = 0; i < GATT_MAX_APPS; i++) {
@@ -385,7 +336,7 @@ void gatt_process_exec_write_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
} else /* nothing needs to be executed , send response now */
{
LOG(ERROR) << "gatt_process_exec_write_req: no prepare write pending";
- gatt_send_error_rsp(tcb, cid, GATT_ERROR, GATT_REQ_EXEC_WRITE, 0, false);
+ gatt_send_error_rsp(tcb, GATT_ERROR, GATT_REQ_EXEC_WRITE, 0, false);
}
}
@@ -399,8 +350,8 @@ void gatt_process_exec_write_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
* Returns void
*
******************************************************************************/
-void gatt_process_read_multi_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
- uint16_t len, uint8_t* p_data) {
+void gatt_process_read_multi_req(tGATT_TCB& tcb, uint8_t op_code, uint16_t len,
+ uint8_t* p_data) {
uint32_t trans_id;
uint16_t handle = 0, ll = len;
uint8_t* p = p_data;
@@ -408,10 +359,8 @@ void gatt_process_read_multi_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
uint8_t sec_flag, key_size;
VLOG(1) << __func__;
+ tcb.sr_cmd.multi_req.num_handles = 0;
- tGATT_READ_MULTI* multi_req = gatt_sr_get_read_multi(tcb, cid);
- multi_req->num_handles = 0;
- multi_req->variable_len = (op_code == GATT_REQ_READ_MULTI_VAR);
gatt_sr_get_sec_info(tcb.peer_bda, tcb.transport, &sec_flag, &key_size);
#if (GATT_CONFORMANCE_TESTING == TRUE)
@@ -421,19 +370,20 @@ void gatt_process_read_multi_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
STREAM_TO_UINT16(handle, p);
- gatt_send_error_rsp(tcb, cid, gatt_cb.err_status, gatt_cb.req_op_code,
- handle, false);
+ gatt_send_error_rsp(tcb, gatt_cb.err_status, gatt_cb.req_op_code, handle,
+ false);
return;
}
#endif
- while (ll >= 2 && multi_req->num_handles < GATT_MAX_READ_MULTI_HANDLES) {
+ while (ll >= 2 &&
+ tcb.sr_cmd.multi_req.num_handles < GATT_MAX_READ_MULTI_HANDLES) {
STREAM_TO_UINT16(handle, p);
auto it = gatt_sr_find_i_rcb_by_handle(handle);
if (it != gatt_cb.srv_list_info->end()) {
- multi_req->handles[multi_req->num_handles++] = handle;
+ tcb.sr_cmd.multi_req.handles[tcb.sr_cmd.multi_req.num_handles++] = handle;
/* check read permission */
err = gatts_read_attr_perm_check(it->p_db, false, handle, sec_flag,
@@ -454,30 +404,28 @@ void gatt_process_read_multi_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
LOG(ERROR) << "max attribute handle reached in ReadMultiple Request.";
}
- if (multi_req->num_handles == 0) err = GATT_INVALID_HANDLE;
+ if (tcb.sr_cmd.multi_req.num_handles == 0) err = GATT_INVALID_HANDLE;
if (err == GATT_SUCCESS) {
- trans_id = gatt_sr_enqueue_cmd(tcb, cid, op_code, multi_req->handles[0]);
+ trans_id =
+ gatt_sr_enqueue_cmd(tcb, op_code, tcb.sr_cmd.multi_req.handles[0]);
if (trans_id != 0) {
- tGATT_SR_CMD* sr_cmd_p = gatt_sr_get_cmd_by_cid(tcb, cid);
-
- gatt_sr_reset_cback_cnt(tcb,
- cid); /* read multiple use multi_rsp_q's count*/
+ gatt_sr_reset_cback_cnt(tcb); /* read multiple use multi_rsp_q's count*/
- for (ll = 0; ll < multi_req->num_handles; ll++) {
+ for (ll = 0; ll < tcb.sr_cmd.multi_req.num_handles; ll++) {
tGATTS_RSP* p_msg = (tGATTS_RSP*)osi_calloc(sizeof(tGATTS_RSP));
- handle = multi_req->handles[ll];
+ handle = tcb.sr_cmd.multi_req.handles[ll];
auto it = gatt_sr_find_i_rcb_by_handle(handle);
p_msg->attr_value.handle = handle;
err = gatts_read_attr_value_by_handle(
- tcb, cid, it->p_db, op_code, handle, 0, p_msg->attr_value.value,
+ tcb, it->p_db, op_code, handle, 0, p_msg->attr_value.value,
&p_msg->attr_value.len, GATT_MAX_ATTR_LEN, sec_flag, key_size,
trans_id);
if (err == GATT_SUCCESS) {
gatt_sr_process_app_rsp(tcb, it->gatt_if, trans_id, op_code,
- GATT_SUCCESS, p_msg, sr_cmd_p);
+ GATT_SUCCESS, p_msg);
}
/* either not using or done using the buffer, release it now */
osi_free(p_msg);
@@ -489,7 +437,7 @@ void gatt_process_read_multi_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
/* in theroy BUSY is not possible(should already been checked), protected
* check */
if (err != GATT_SUCCESS && err != GATT_PENDING && err != GATT_BUSY)
- gatt_send_error_rsp(tcb, cid, err, op_code, handle, false);
+ gatt_send_error_rsp(tcb, err, op_code, handle, false);
}
/*******************************************************************************
@@ -503,16 +451,13 @@ void gatt_process_read_multi_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
*
******************************************************************************/
static tGATT_STATUS gatt_build_primary_service_rsp(
- BT_HDR* p_msg, tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
- uint16_t s_hdl, uint16_t e_hdl, UNUSED_ATTR uint8_t* p_data,
- const Uuid& value) {
+ BT_HDR* p_msg, tGATT_TCB& tcb, uint8_t op_code, uint16_t s_hdl,
+ uint16_t e_hdl, UNUSED_ATTR uint8_t* p_data, const Uuid& value) {
tGATT_STATUS status = GATT_NOT_FOUND;
uint8_t handle_len = 4;
uint8_t* p = (uint8_t*)(p_msg + 1) + L2CAP_MIN_OFFSET;
- uint16_t payload_size = gatt_tcb_get_payload_size_tx(tcb, cid);
-
for (tGATT_SRV_LIST_ELEM& el : *gatt_cb.srv_list_info) {
if (el.s_hdl < s_hdl || el.s_hdl > e_hdl ||
el.type != GATT_UUID_PRI_SERVICE) {
@@ -537,7 +482,7 @@ static tGATT_STATUS gatt_build_primary_service_rsp(
}
}
- if (p_msg->len + p_msg->offset > payload_size ||
+ if (p_msg->len + p_msg->offset > tcb.payload_size ||
handle_len != p_msg->offset) {
break;
}
@@ -669,30 +614,28 @@ static tGATT_STATUS gatts_validate_packet_format(uint8_t op_code, uint16_t& len,
* Returns void
*
******************************************************************************/
-void gatts_process_primary_service_req(tGATT_TCB& tcb, uint16_t cid,
- uint8_t op_code, uint16_t len,
- uint8_t* p_data) {
+void gatts_process_primary_service_req(tGATT_TCB& tcb, uint8_t op_code,
+ uint16_t len, uint8_t* p_data) {
uint16_t s_hdl = 0, e_hdl = 0;
Uuid uuid = Uuid::kEmpty;
uint8_t reason =
gatts_validate_packet_format(op_code, len, p_data, &uuid, s_hdl, e_hdl);
if (reason != GATT_SUCCESS) {
- gatt_send_error_rsp(tcb, cid, reason, op_code, s_hdl, false);
+ gatt_send_error_rsp(tcb, reason, op_code, s_hdl, false);
return;
}
if (uuid != Uuid::From16Bit(GATT_UUID_PRI_SERVICE)) {
if (op_code == GATT_REQ_READ_BY_GRP_TYPE) {
- gatt_send_error_rsp(tcb, cid, GATT_UNSUPPORT_GRP_TYPE, op_code, s_hdl,
- false);
+ gatt_send_error_rsp(tcb, GATT_UNSUPPORT_GRP_TYPE, op_code, s_hdl, false);
VLOG(1) << StringPrintf("unexpected ReadByGrpType Group: %s",
uuid.ToString().c_str());
return;
}
// we do not support ReadByTypeValue with any non-primamry_service type
- gatt_send_error_rsp(tcb, cid, GATT_NOT_FOUND, op_code, s_hdl, false);
+ gatt_send_error_rsp(tcb, GATT_NOT_FOUND, op_code, s_hdl, false);
VLOG(1) << StringPrintf("unexpected ReadByTypeValue type: %s",
uuid.ToString().c_str());
return;
@@ -702,24 +645,22 @@ void gatts_process_primary_service_req(tGATT_TCB& tcb, uint16_t cid,
Uuid value = Uuid::kEmpty;
if (op_code == GATT_REQ_FIND_TYPE_VALUE) {
if (!gatt_parse_uuid_from_cmd(&value, len, &p_data)) {
- gatt_send_error_rsp(tcb, cid, GATT_INVALID_PDU, op_code, s_hdl, false);
+ gatt_send_error_rsp(tcb, GATT_INVALID_PDU, op_code, s_hdl, false);
}
}
- uint16_t payload_size = gatt_tcb_get_payload_size_tx(tcb, cid);
-
uint16_t msg_len =
- (uint16_t)(sizeof(BT_HDR) + payload_size + L2CAP_MIN_OFFSET);
+ (uint16_t)(sizeof(BT_HDR) + tcb.payload_size + L2CAP_MIN_OFFSET);
BT_HDR* p_msg = (BT_HDR*)osi_calloc(msg_len);
- reason = gatt_build_primary_service_rsp(p_msg, tcb, cid, op_code, s_hdl,
- e_hdl, p_data, value);
+ reason = gatt_build_primary_service_rsp(p_msg, tcb, op_code, s_hdl, e_hdl,
+ p_data, value);
if (reason != GATT_SUCCESS) {
osi_free(p_msg);
- gatt_send_error_rsp(tcb, cid, reason, op_code, s_hdl, false);
+ gatt_send_error_rsp(tcb, reason, op_code, s_hdl, false);
return;
}
- attp_send_sr_msg(tcb, cid, p_msg);
+ attp_send_sr_msg(tcb, p_msg);
}
/*******************************************************************************
@@ -732,19 +673,17 @@ void gatts_process_primary_service_req(tGATT_TCB& tcb, uint16_t cid,
* Returns void
*
******************************************************************************/
-static void gatts_process_find_info(tGATT_TCB& tcb, uint16_t cid,
- uint8_t op_code, uint16_t len,
- uint8_t* p_data) {
+static void gatts_process_find_info(tGATT_TCB& tcb, uint8_t op_code,
+ uint16_t len, uint8_t* p_data) {
uint16_t s_hdl = 0, e_hdl = 0;
uint8_t reason = read_handles(len, p_data, s_hdl, e_hdl);
if (reason != GATT_SUCCESS) {
- gatt_send_error_rsp(tcb, cid, reason, op_code, s_hdl, false);
+ gatt_send_error_rsp(tcb, reason, op_code, s_hdl, false);
return;
}
- uint16_t payload_size = gatt_tcb_get_payload_size_tx(tcb, cid);
uint16_t buf_len =
- (uint16_t)(sizeof(BT_HDR) + payload_size + L2CAP_MIN_OFFSET);
+ (uint16_t)(sizeof(BT_HDR) + tcb.payload_size + L2CAP_MIN_OFFSET);
BT_HDR* p_msg = (BT_HDR*)osi_calloc(buf_len);
reason = GATT_NOT_FOUND;
@@ -753,7 +692,7 @@ static void gatts_process_find_info(tGATT_TCB& tcb, uint16_t cid,
*p++ = op_code + 1;
p_msg->len = 2;
- buf_len = payload_size - 2;
+ buf_len = tcb.payload_size - 2;
for (tGATT_SRV_LIST_ELEM& el : *gatt_cb.srv_list_info) {
if (el.s_hdl <= e_hdl && el.e_hdl >= s_hdl) {
@@ -771,9 +710,9 @@ static void gatts_process_find_info(tGATT_TCB& tcb, uint16_t cid,
if (reason != GATT_SUCCESS) {
osi_free(p_msg);
- gatt_send_error_rsp(tcb, cid, reason, op_code, s_hdl, false);
+ gatt_send_error_rsp(tcb, reason, op_code, s_hdl, false);
} else
- attp_send_sr_msg(tcb, cid, p_msg);
+ attp_send_sr_msg(tcb, p_msg);
}
/*******************************************************************************
@@ -786,18 +725,17 @@ static void gatts_process_find_info(tGATT_TCB& tcb, uint16_t cid,
* Returns void
*
******************************************************************************/
-static void gatts_process_mtu_req(tGATT_TCB& tcb, uint16_t cid, uint16_t len,
+static void gatts_process_mtu_req(tGATT_TCB& tcb, uint16_t len,
uint8_t* p_data) {
/* BR/EDR conenction, send error response */
- if (cid != L2CAP_ATT_CID) {
- gatt_send_error_rsp(tcb, cid, GATT_REQ_NOT_SUPPORTED, GATT_REQ_MTU, 0,
- false);
+ if (tcb.att_lcid != L2CAP_ATT_CID) {
+ gatt_send_error_rsp(tcb, GATT_REQ_NOT_SUPPORTED, GATT_REQ_MTU, 0, false);
return;
}
if (len < GATT_MTU_REQ_MIN_LEN) {
LOG(ERROR) << "invalid MTU request PDU received.";
- gatt_send_error_rsp(tcb, cid, GATT_INVALID_PDU, GATT_REQ_MTU, 0, false);
+ gatt_send_error_rsp(tcb, GATT_INVALID_PDU, GATT_REQ_MTU, 0, false);
return;
}
@@ -814,12 +752,13 @@ static void gatts_process_mtu_req(tGATT_TCB& tcb, uint16_t cid, uint16_t len,
LOG(INFO) << "MTU request PDU with MTU size " << +tcb.payload_size;
- BTM_SetBleDataLength(tcb.peer_bda, tcb.payload_size);
+ l2cble_set_fixed_channel_tx_data_length(tcb.peer_bda, L2CAP_ATT_CID,
+ tcb.payload_size);
tGATT_SR_MSG gatt_sr_msg;
gatt_sr_msg.mtu = tcb.payload_size;
BT_HDR* p_buf = attp_build_sr_msg(tcb, GATT_RSP_MTU, &gatt_sr_msg);
- attp_send_sr_msg(tcb, cid, p_buf);
+ attp_send_sr_msg(tcb, p_buf);
tGATTS_DATA gatts_data;
gatts_data.mtu = tcb.payload_size;
@@ -849,9 +788,8 @@ static void gatts_process_mtu_req(tGATT_TCB& tcb, uint16_t cid, uint16_t len,
* Returns void
*
******************************************************************************/
-void gatts_process_read_by_type_req(tGATT_TCB& tcb, uint16_t cid,
- uint8_t op_code, uint16_t len,
- uint8_t* p_data) {
+void gatts_process_read_by_type_req(tGATT_TCB& tcb, uint8_t op_code,
+ uint16_t len, uint8_t* p_data) {
Uuid uuid = Uuid::kEmpty;
uint16_t s_hdl = 0, e_hdl = 0, err_hdl = 0;
tGATT_STATUS reason =
@@ -862,28 +800,26 @@ void gatts_process_read_by_type_req(tGATT_TCB& tcb, uint16_t cid,
VLOG(1) << "Conformance tst: forced err rsp for ReadByType: error status="
<< +gatt_cb.err_status;
- gatt_send_error_rsp(tcb, cid, gatt_cb.err_status, gatt_cb.req_op_code,
- s_hdl, false);
+ gatt_send_error_rsp(tcb, gatt_cb.err_status, gatt_cb.req_op_code, s_hdl,
+ false);
return;
}
#endif
if (reason != GATT_SUCCESS) {
- gatt_send_error_rsp(tcb, cid, reason, op_code, s_hdl, false);
+ gatt_send_error_rsp(tcb, reason, op_code, s_hdl, false);
return;
}
- uint16_t payload_size = gatt_tcb_get_payload_size_tx(tcb, cid);
-
- size_t msg_len = sizeof(BT_HDR) + payload_size + L2CAP_MIN_OFFSET;
+ size_t msg_len = sizeof(BT_HDR) + tcb.payload_size + L2CAP_MIN_OFFSET;
BT_HDR* p_msg = (BT_HDR*)osi_calloc(msg_len);
uint8_t* p = (uint8_t*)(p_msg + 1) + L2CAP_MIN_OFFSET;
*p++ = op_code + 1;
/* reserve length byte */
p_msg->len = 2;
- uint16_t buf_len = payload_size - 2;
+ uint16_t buf_len = tcb.payload_size - 2;
reason = GATT_NOT_FOUND;
for (tGATT_SRV_LIST_ELEM& el : *gatt_cb.srv_list_info) {
@@ -892,8 +828,8 @@ void gatts_process_read_by_type_req(tGATT_TCB& tcb, uint16_t cid,
gatt_sr_get_sec_info(tcb.peer_bda, tcb.transport, &sec_flag, &key_size);
tGATT_STATUS ret = gatts_db_read_attr_value_by_type(
- tcb, cid, el.p_db, op_code, p_msg, s_hdl, e_hdl, uuid, &buf_len,
- sec_flag, key_size, 0, &err_hdl);
+ tcb, el.p_db, op_code, p_msg, s_hdl, e_hdl, uuid, &buf_len, sec_flag,
+ key_size, 0, &err_hdl);
if (ret != GATT_NOT_FOUND) {
reason = ret;
if (ret == GATT_NO_RESOURCES) reason = GATT_SUCCESS;
@@ -914,21 +850,20 @@ void gatts_process_read_by_type_req(tGATT_TCB& tcb, uint16_t cid,
/* in theroy BUSY is not possible(should already been checked), protected
* check */
if (reason != GATT_PENDING && reason != GATT_BUSY)
- gatt_send_error_rsp(tcb, cid, reason, op_code, s_hdl, false);
+ gatt_send_error_rsp(tcb, reason, op_code, s_hdl, false);
return;
}
- attp_send_sr_msg(tcb, cid, p_msg);
+ attp_send_sr_msg(tcb, p_msg);
}
/**
* This function is called to process the write request from client.
*/
-static void gatts_process_write_req(tGATT_TCB& tcb, uint16_t cid,
- tGATT_SRV_LIST_ELEM& el, uint16_t handle,
- uint8_t op_code, uint16_t len,
- uint8_t* p_data,
+static void gatts_process_write_req(tGATT_TCB& tcb, tGATT_SRV_LIST_ELEM& el,
+ uint16_t handle, uint8_t op_code,
+ uint16_t len, uint8_t* p_data,
bt_gatt_db_attribute_type_t gatt_type) {
tGATTS_DATA sr_data;
uint32_t trans_id;
@@ -944,7 +879,7 @@ static void gatts_process_write_req(tGATT_TCB& tcb, uint16_t cid,
LOG(ERROR) << __func__
<< ": Prepare write request was invalid - missing offset, "
"sending error response";
- gatt_send_error_rsp(tcb, cid, GATT_INVALID_PDU, op_code, handle, false);
+ gatt_send_error_rsp(tcb, GATT_INVALID_PDU, op_code, handle, false);
return;
}
sr_data.write_req.is_prep = true;
@@ -977,7 +912,7 @@ static void gatts_process_write_req(tGATT_TCB& tcb, uint16_t cid,
sec_flag, key_size);
if (status == GATT_SUCCESS) {
- trans_id = gatt_sr_enqueue_cmd(tcb, cid, op_code, handle);
+ trans_id = gatt_sr_enqueue_cmd(tcb, op_code, handle);
if (trans_id != 0) {
conn_id = GATT_CREATE_CONN_ID(tcb.tcb_idx, el.gatt_if);
@@ -1007,7 +942,7 @@ static void gatts_process_write_req(tGATT_TCB& tcb, uint16_t cid,
* check */
if (status != GATT_PENDING && status != GATT_BUSY &&
(op_code == GATT_REQ_PREPARE_WRITE || op_code == GATT_REQ_WRITE)) {
- gatt_send_error_rsp(tcb, cid, status, op_code, handle, false);
+ gatt_send_error_rsp(tcb, status, op_code, handle, false);
}
return;
}
@@ -1015,13 +950,10 @@ static void gatts_process_write_req(tGATT_TCB& tcb, uint16_t cid,
/**
* This function is called to process the read request from client.
*/
-static void gatts_process_read_req(tGATT_TCB& tcb, uint16_t cid,
- tGATT_SRV_LIST_ELEM& el, uint8_t op_code,
- uint16_t handle, uint16_t len,
- uint8_t* p_data) {
- uint16_t payload_size = gatt_tcb_get_payload_size_tx(tcb, cid);
-
- size_t buf_len = sizeof(BT_HDR) + payload_size + L2CAP_MIN_OFFSET;
+static void gatts_process_read_req(tGATT_TCB& tcb, tGATT_SRV_LIST_ELEM& el,
+ uint8_t op_code, uint16_t handle,
+ uint16_t len, uint8_t* p_data) {
+ size_t buf_len = sizeof(BT_HDR) + tcb.payload_size + L2CAP_MIN_OFFSET;
uint16_t offset = 0;
if (op_code == GATT_REQ_READ_BLOB && len < sizeof(uint16_t)) {
@@ -1029,7 +961,7 @@ static void gatts_process_read_req(tGATT_TCB& tcb, uint16_t cid,
LOG(ERROR) << __func__ << ": packet length=" << len
<< " too short. min=" << sizeof(uint16_t);
android_errorWriteWithInfoLog(0x534e4554, "73172115", -1, NULL, 0);
- gatt_send_error_rsp(tcb, cid, GATT_INVALID_PDU, op_code, 0, false);
+ gatt_send_error_rsp(tcb, GATT_INVALID_PDU, op_code, 0, false);
return;
}
@@ -1040,15 +972,15 @@ static void gatts_process_read_req(tGATT_TCB& tcb, uint16_t cid,
uint8_t* p = (uint8_t*)(p_msg + 1) + L2CAP_MIN_OFFSET;
*p++ = op_code + 1;
p_msg->len = 1;
- buf_len = payload_size - 1;
+ buf_len = tcb.payload_size - 1;
uint8_t sec_flag, key_size;
gatt_sr_get_sec_info(tcb.peer_bda, tcb.transport, &sec_flag, &key_size);
uint16_t value_len = 0;
tGATT_STATUS reason = gatts_read_attr_value_by_handle(
- tcb, cid, el.p_db, op_code, handle, offset, p, &value_len,
- (uint16_t)buf_len, sec_flag, key_size, 0);
+ tcb, el.p_db, op_code, handle, offset, p, &value_len, (uint16_t)buf_len,
+ sec_flag, key_size, 0);
p_msg->len += value_len;
if (reason != GATT_SUCCESS) {
@@ -1057,12 +989,12 @@ static void gatts_process_read_req(tGATT_TCB& tcb, uint16_t cid,
/* in theory BUSY is not possible(should already been checked), protected
* check */
if (reason != GATT_PENDING && reason != GATT_BUSY)
- gatt_send_error_rsp(tcb, cid, reason, op_code, handle, false);
+ gatt_send_error_rsp(tcb, reason, op_code, handle, false);
return;
}
- attp_send_sr_msg(tcb, cid, p_msg);
+ attp_send_sr_msg(tcb, p_msg);
}
/*******************************************************************************
@@ -1075,8 +1007,8 @@ static void gatts_process_read_req(tGATT_TCB& tcb, uint16_t cid,
* Returns void
*
******************************************************************************/
-void gatts_process_attribute_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
- uint16_t len, uint8_t* p_data) {
+void gatts_process_attribute_req(tGATT_TCB& tcb, uint8_t op_code, uint16_t len,
+ uint8_t* p_data) {
uint16_t handle = 0;
uint8_t* p = p_data;
tGATT_STATUS status = GATT_INVALID_HANDLE;
@@ -1095,8 +1027,8 @@ void gatts_process_attribute_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
VLOG(1) << "Conformance tst: forced err rsp: error status="
<< +gatt_cb.err_status;
- gatt_send_error_rsp(tcb, cid, gatt_cb.err_status, cid, gatt_cb.req_op_code,
- handle, false);
+ gatt_send_error_rsp(tcb, gatt_cb.err_status, gatt_cb.req_op_code, handle,
+ false);
return;
}
@@ -1110,14 +1042,14 @@ void gatts_process_attribute_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
switch (op_code) {
case GATT_REQ_READ: /* read char/char descriptor value */
case GATT_REQ_READ_BLOB:
- gatts_process_read_req(tcb, cid, el, op_code, handle, len, p);
+ gatts_process_read_req(tcb, el, op_code, handle, len, p);
break;
case GATT_REQ_WRITE: /* write char/char descriptor value */
case GATT_CMD_WRITE:
case GATT_SIGN_CMD_WRITE:
case GATT_REQ_PREPARE_WRITE:
- gatts_process_write_req(tcb, cid, el, handle, op_code, len, p,
+ gatts_process_write_req(tcb, el, handle, op_code, len, p,
attr.gatt_type);
break;
default:
@@ -1134,7 +1066,7 @@ void gatts_process_attribute_req(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
if (status != GATT_SUCCESS && op_code != GATT_CMD_WRITE &&
op_code != GATT_SIGN_CMD_WRITE)
- gatt_send_error_rsp(tcb, cid, status, op_code, handle, false);
+ gatt_send_error_rsp(tcb, status, op_code, handle, false);
}
/*******************************************************************************
@@ -1205,9 +1137,6 @@ static bool gatts_proc_ind_ack(tGATT_TCB& tcb, uint16_t ack_handle) {
/* there is no need to inform the application since srv chg is handled
* internally by GATT */
continue_processing = false;
-
- // After receiving ack of svc_chg_ind, reset client status
- gatt_sr_update_cl_status(tcb, /* chg_aware= */ true);
}
gatts_chk_pending_ind(tcb);
@@ -1224,16 +1153,16 @@ static bool gatts_proc_ind_ack(tGATT_TCB& tcb, uint16_t ack_handle) {
* Returns void
*
******************************************************************************/
-void gatts_process_value_conf(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code) {
- uint16_t handle;
+void gatts_process_value_conf(tGATT_TCB& tcb, uint8_t op_code) {
+ uint16_t handle = tcb.indicate_handle;
- if (!gatt_tcb_find_indicate_handle(tcb, cid, &handle)) {
+ alarm_cancel(tcb.conf_timer);
+ if (!GATT_HANDLE_IS_VALID(handle)) {
LOG(ERROR) << "unexpected handle value confirmation";
return;
}
- gatt_stop_conf_timer(tcb, cid);
-
+ tcb.indicate_handle = 0;
bool continue_processing = gatts_proc_ind_ack(tcb, handle);
if (continue_processing) {
@@ -1241,7 +1170,7 @@ void gatts_process_value_conf(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code) {
gatts_data.handle = handle;
for (auto& el : *gatt_cb.srv_list_info) {
if (el.s_hdl <= handle && el.e_hdl >= handle) {
- uint32_t trans_id = gatt_sr_enqueue_cmd(tcb, cid, op_code, handle);
+ uint32_t trans_id = gatt_sr_enqueue_cmd(tcb, op_code, handle);
uint16_t conn_id = GATT_CREATE_CONN_ID(tcb.tcb_idx, el.gatt_if);
gatt_sr_send_req_callback(conn_id, trans_id, GATTS_REQ_TYPE_CONF,
&gatts_data);
@@ -1250,119 +1179,39 @@ void gatts_process_value_conf(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code) {
}
}
-static bool gatts_process_db_out_of_sync(tGATT_TCB& tcb, uint16_t cid,
- uint8_t op_code, uint16_t len,
- uint8_t* p_data) {
- if (gatt_sr_is_cl_change_aware(tcb)) return false;
-
- // default value
- bool should_ignore = true;
- bool should_rsp = true;
-
- switch (op_code) {
- case GATT_REQ_READ_BY_TYPE: {
- // Check if read database hash by UUID
- Uuid uuid = Uuid::kEmpty;
- uint16_t s_hdl = 0, e_hdl = 0;
- uint16_t db_hash_handle = gatt_cb.handle_of_database_hash;
- tGATT_STATUS reason = gatts_validate_packet_format(op_code, len, p_data,
- &uuid, s_hdl, e_hdl);
- if (reason == GATT_SUCCESS &&
- (s_hdl <= db_hash_handle && db_hash_handle <= e_hdl) &&
- (uuid == Uuid::From16Bit(GATT_UUID_DATABASE_HASH)))
- should_ignore = false;
-
- } break;
- case GATT_REQ_READ: {
- // Check if read database hash by handle
- uint16_t handle = 0;
- uint8_t* p = p_data;
- tGATT_STATUS status = GATT_SUCCESS;
-
- if (len < 2) {
- status = GATT_INVALID_PDU;
- } else {
- STREAM_TO_UINT16(handle, p);
- len -= 2;
- }
-
- if (status == GATT_SUCCESS && handle == gatt_cb.handle_of_database_hash)
- should_ignore = false;
-
- } break;
- case GATT_REQ_READ_BY_GRP_TYPE: /* discover primary services */
- case GATT_REQ_FIND_TYPE_VALUE: /* discover service by UUID */
- case GATT_REQ_FIND_INFO: /* discover char descrptor */
- case GATT_REQ_READ_BLOB: /* read long char */
- case GATT_REQ_READ_MULTI: /* read multi char*/
- case GATT_REQ_WRITE: /* write char/char descriptor value */
- case GATT_REQ_PREPARE_WRITE: /* write long char */
- // Use default value
- break;
- case GATT_CMD_WRITE: /* cmd */
- case GATT_SIGN_CMD_WRITE: /* sign cmd */
- should_rsp = false;
- break;
- case GATT_REQ_MTU: /* configure mtu */
- case GATT_REQ_EXEC_WRITE: /* execute write */
- case GATT_HANDLE_VALUE_CONF: /* confirm for indication */
- default:
- should_ignore = false;
- }
-
- if (should_ignore) {
- if (should_rsp) {
- gatt_send_error_rsp(tcb, cid, GATT_DATABASE_OUT_OF_SYNC, op_code, 0x0000,
- false);
- }
- LOG(INFO) << __func__ << ": database out of sync, device=" << tcb.peer_bda
- << ", op_code=" << loghex((uint16_t)op_code)
- << ", should_rsp=" << should_rsp;
- gatt_sr_update_cl_status(tcb, /* chg_aware= */ should_rsp);
- }
-
- return should_ignore;
-}
-
/** This function is called to handle the client requests to server */
-void gatt_server_handle_client_req(tGATT_TCB& tcb, uint16_t cid,
- uint8_t op_code, uint16_t len,
- uint8_t* p_data) {
+void gatt_server_handle_client_req(tGATT_TCB& tcb, uint8_t op_code,
+ uint16_t len, uint8_t* p_data) {
/* there is pending command, discard this one */
- if (!gatt_sr_cmd_empty(tcb, cid) && op_code != GATT_HANDLE_VALUE_CONF) return;
+ if (!gatt_sr_cmd_empty(tcb) && op_code != GATT_HANDLE_VALUE_CONF) return;
/* the size of the message may not be bigger than the local max PDU size*/
/* The message has to be smaller than the agreed MTU, len does not include op
* code */
-
- uint16_t payload_size = gatt_tcb_get_payload_size_rx(tcb, cid);
- if (len >= payload_size) {
+ if (len >= tcb.payload_size) {
LOG(ERROR) << StringPrintf("server receive invalid PDU size:%d pdu size:%d",
- len + 1, payload_size);
+ len + 1, tcb.payload_size);
/* for invalid request expecting response, send it now */
if (op_code != GATT_CMD_WRITE && op_code != GATT_SIGN_CMD_WRITE &&
op_code != GATT_HANDLE_VALUE_CONF) {
- gatt_send_error_rsp(tcb, cid, GATT_INVALID_PDU, op_code, 0, false);
+ gatt_send_error_rsp(tcb, GATT_INVALID_PDU, op_code, 0, false);
}
/* otherwise, ignore the pkt */
} else {
- // handle database out of sync
- if (gatts_process_db_out_of_sync(tcb, cid, op_code, len, p_data)) return;
-
switch (op_code) {
case GATT_REQ_READ_BY_GRP_TYPE: /* discover primary services */
case GATT_REQ_FIND_TYPE_VALUE: /* discover service by UUID */
- gatts_process_primary_service_req(tcb, cid, op_code, len, p_data);
+ gatts_process_primary_service_req(tcb, op_code, len, p_data);
break;
case GATT_REQ_FIND_INFO: /* discover char descrptor */
- gatts_process_find_info(tcb, cid, op_code, len, p_data);
+ gatts_process_find_info(tcb, op_code, len, p_data);
break;
case GATT_REQ_READ_BY_TYPE: /* read characteristic value, char descriptor
value */
/* discover characteristic, discover char by UUID */
- gatts_process_read_by_type_req(tcb, cid, op_code, len, p_data);
+ gatts_process_read_by_type_req(tcb, op_code, len, p_data);
break;
case GATT_REQ_READ: /* read char/char descriptor value */
@@ -1371,24 +1220,23 @@ void gatt_server_handle_client_req(tGATT_TCB& tcb, uint16_t cid,
case GATT_CMD_WRITE:
case GATT_SIGN_CMD_WRITE:
case GATT_REQ_PREPARE_WRITE:
- gatts_process_attribute_req(tcb, cid, op_code, len, p_data);
+ gatts_process_attribute_req(tcb, op_code, len, p_data);
break;
case GATT_HANDLE_VALUE_CONF:
- gatts_process_value_conf(tcb, cid, op_code);
+ gatts_process_value_conf(tcb, op_code);
break;
case GATT_REQ_MTU:
- gatts_process_mtu_req(tcb, cid, len, p_data);
+ gatts_process_mtu_req(tcb, len, p_data);
break;
case GATT_REQ_EXEC_WRITE:
- gatt_process_exec_write_req(tcb, cid, op_code, len, p_data);
+ gatt_process_exec_write_req(tcb, op_code, len, p_data);
break;
case GATT_REQ_READ_MULTI:
- case GATT_REQ_READ_MULTI_VAR:
- gatt_process_read_multi_req(tcb, cid, op_code, len, p_data);
+ gatt_process_read_multi_req(tcb, op_code, len, p_data);
break;
default:
diff --git a/stack/gatt/gatt_sr_hash.cc b/stack/gatt/gatt_sr_hash.cc
deleted file mode 100644
index c664d1435..000000000
--- a/stack/gatt/gatt_sr_hash.cc
+++ /dev/null
@@ -1,128 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#include <base/strings/string_number_conversions.h>
-#include <list>
-
-#include "gatt_int.h"
-#include "stack/crypto_toolbox/crypto_toolbox.h"
-
-using bluetooth::Uuid;
-
-static size_t calculate_database_info_size(std::list<tGATT_SRV_LIST_ELEM>* lst_ptr) {
- size_t len = 0;
- auto srv_it = lst_ptr->begin();
- for (; srv_it != lst_ptr->end(); srv_it++) {
- auto attr_list = &srv_it->p_db->attr_list;
- auto attr_it = attr_list->begin();
- for (; attr_it != attr_list->end(); attr_it++) {
- if (attr_it->uuid == Uuid::From16Bit(GATT_UUID_PRI_SERVICE) ||
- attr_it->uuid == Uuid::From16Bit(GATT_UUID_SEC_SERVICE)) {
- // Service declaration (Handle + Type + Value)
- len += 4 + gatt_build_uuid_to_stream_len(attr_it->p_value->uuid);
- } else if (attr_it->uuid == Uuid::From16Bit(GATT_UUID_INCLUDE_SERVICE)){
- // Included service declaration (Handle + Type + Value)
- len += 8 + gatt_build_uuid_to_stream_len(attr_it->p_value->incl_handle.service_type);
- } else if (attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_DECLARE)) {
- // Characteristic declaration (Handle + Type + Value)
- len += 7 + gatt_build_uuid_to_stream_len((++attr_it)->uuid);
- } else if (attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_DESCRIPTION) ||
- attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_CLIENT_CONFIG) ||
- attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_SRVR_CONFIG) ||
- attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_PRESENT_FORMAT) ||
- attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_AGG_FORMAT)) {
- // Descriptor (Handle + Type)
- len += 4;
- } else if (attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_EXT_PROP)) {
- // Descriptor for ext property (Handle + Type + Value)
- len += 6;
- }
- }
- }
- return len;
-}
-
-static void fill_database_info(std::list<tGATT_SRV_LIST_ELEM>* lst_ptr, uint8_t* p_data) {
- auto srv_it = lst_ptr->begin();
- for (; srv_it != lst_ptr->end(); srv_it++) {
- auto attr_list = &srv_it->p_db->attr_list;
- auto attr_it = attr_list->begin();
- for (; attr_it != attr_list->end(); attr_it++) {
- if (attr_it->uuid == Uuid::From16Bit(GATT_UUID_PRI_SERVICE) ||
- attr_it->uuid == Uuid::From16Bit(GATT_UUID_SEC_SERVICE)) {
- // Service declaration
- UINT16_TO_STREAM(p_data, attr_it->handle);
-
- if (srv_it->is_primary) {
- UINT16_TO_STREAM(p_data, GATT_UUID_PRI_SERVICE);
- } else {
- UINT16_TO_STREAM(p_data, GATT_UUID_SEC_SERVICE);
- }
-
- gatt_build_uuid_to_stream(&p_data, attr_it->p_value->uuid);
- } else if (attr_it->uuid == Uuid::From16Bit(GATT_UUID_INCLUDE_SERVICE)){
- // Included service declaration
- UINT16_TO_STREAM(p_data, attr_it->handle);
- UINT16_TO_STREAM(p_data, GATT_UUID_INCLUDE_SERVICE);
- UINT16_TO_STREAM(p_data, attr_it->p_value->incl_handle.s_handle);
- UINT16_TO_STREAM(p_data, attr_it->p_value->incl_handle.e_handle);
-
- gatt_build_uuid_to_stream(&p_data, attr_it->p_value->incl_handle.service_type);
- } else if (attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_DECLARE)) {
- // Characteristic declaration
- UINT16_TO_STREAM(p_data, attr_it->handle);
- UINT16_TO_STREAM(p_data, GATT_UUID_CHAR_DECLARE);
- UINT8_TO_STREAM(p_data, attr_it->p_value->char_decl.property);
- UINT16_TO_STREAM(p_data, attr_it->p_value->char_decl.char_val_handle);
-
- // Increment 1 to fetch characteristic uuid from value declaration attribute
- gatt_build_uuid_to_stream(&p_data, (++attr_it)->uuid);
- } else if (attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_DESCRIPTION) ||
- attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_CLIENT_CONFIG) ||
- attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_SRVR_CONFIG) ||
- attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_PRESENT_FORMAT) ||
- attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_AGG_FORMAT)) {
- // Descriptor
- UINT16_TO_STREAM(p_data, attr_it->handle);
- UINT16_TO_STREAM(p_data, attr_it->uuid.As16Bit());
- } else if (attr_it->uuid == Uuid::From16Bit(GATT_UUID_CHAR_EXT_PROP)) {
- // Descriptor
- UINT16_TO_STREAM(p_data, attr_it->handle);
- UINT16_TO_STREAM(p_data, attr_it->uuid.As16Bit());
- UINT16_TO_STREAM(p_data, attr_it->p_value
- ? attr_it->p_value->char_ext_prop
- : 0x0000);
- }
- }
- }
-}
-
-Octet16 gatts_calculate_database_hash(std::list<tGATT_SRV_LIST_ELEM>* lst_ptr) {
- int len = calculate_database_info_size(lst_ptr);
-
- std::vector<uint8_t> serialized(len);
- fill_database_info(lst_ptr, serialized.data());
-
- std::reverse(serialized.begin(), serialized.end());
- Octet16 db_hash = crypto_toolbox::aes_cmac(Octet16{0}, serialized.data(),
- serialized.size());
- LOG(INFO) << __func__ << ": hash="
- << base::HexEncode(db_hash.data(), db_hash.size());
-
- return db_hash;
-}
diff --git a/stack/gatt/gatt_utils.cc b/stack/gatt/gatt_utils.cc
index 146dee207..2bd424000 100644
--- a/stack/gatt/gatt_utils.cc
+++ b/stack/gatt/gatt_utils.cc
@@ -21,28 +21,25 @@
* this file contains GATT utility functions
*
******************************************************************************/
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-
-#include "bt_target.h" // Must be first to define build configuration
-
-#include "main/shim/shim.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/eatt/eatt.h"
+#include "bt_target.h"
+#include "bt_utils.h"
+#include "osi/include/osi.h"
+
+#include <string.h>
+#include "bt_common.h"
+#include "stdio.h"
+
+#include "btm_int.h"
+#include "connection_manager.h"
+#include "gatt_api.h"
+#include "gatt_int.h"
+#include "gattdefs.h"
+#include "l2cdefs.h"
+#include "sdp_api.h"
#include "stack/gatt/connection_manager.h"
-#include "stack/gatt/gatt_int.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/l2cdefs.h"
-#include "stack/include/sdp_api.h"
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
-
-uint8_t btm_ble_read_sec_key_size(const RawAddress& bd_addr);
using base::StringPrintf;
using bluetooth::Uuid;
-using bluetooth::eatt::EattExtension;
-using bluetooth::eatt::EattChannel;
/* check if [x, y] and [a, b] have overlapping range */
#define GATT_VALIDATE_HANDLE_RANGE(x, y, a, b) ((y) >= (a) && (x) <= (b))
@@ -286,10 +283,6 @@ bool gatt_is_srv_chg_ind_pending(tGATT_TCB* p_tcb) {
if (p_tcb->indicate_handle == gatt_cb.handle_of_h_r) return true;
- if (p_tcb->eatt && EattExtension::GetInstance()->IsIndicationPending(
- p_tcb->peer_bda, gatt_cb.handle_of_h_r))
- return true;
-
if (fixed_queue_is_empty(p_tcb->pending_ind_q)) return false;
list_t* list = fixed_queue_get_list(p_tcb->pending_ind_q);
@@ -444,10 +437,6 @@ tGATT_TCB* gatt_allocate_tcb_by_bdaddr(const RawAddress& bda,
p_tcb->tcb_idx = i;
p_tcb->transport = transport;
p_tcb->peer_bda = bda;
- p_tcb->eatt = 0;
- gatt_sr_init_cl_status(*p_tcb);
- gatt_cl_init_sr_status(*p_tcb);
-
return p_tcb;
}
@@ -547,19 +536,6 @@ void gatt_start_rsp_timer(tGATT_CLCB* p_clcb) {
/*******************************************************************************
*
- * Function gatt_stop_rsp_timer
- *
- * Description Stops a GATT response timer.
- *
- * Returns void
- *
- ******************************************************************************/
-void gatt_stop_rsp_timer(tGATT_CLCB* p_clcb) {
- alarm_cancel(p_clcb->gatt_rsp_timer_ent);
-}
-
-/*******************************************************************************
- *
* Function gatt_start_conf_timer
*
* Description Start a wait_for_confirmation timer.
@@ -567,30 +543,9 @@ void gatt_stop_rsp_timer(tGATT_CLCB* p_clcb) {
* Returns void
*
******************************************************************************/
-void gatt_start_conf_timer(tGATT_TCB* p_tcb, uint16_t cid) {
- /* start notification cache timer */
- if (p_tcb->eatt && cid != L2CAP_ATT_CID)
- EattExtension::GetInstance()->StartIndicationConfirmationTimer(p_tcb->peer_bda, cid);
- else
- alarm_set_on_mloop(p_tcb->conf_timer, GATT_WAIT_FOR_RSP_TIMEOUT_MS,
- gatt_indication_confirmation_timeout, p_tcb);
-}
-
-/*******************************************************************************
- *
- * Function gatt_stop_conf_timer
- *
- * Description Start a wait_for_confirmation timer.
- *
- * Returns void
- *
- ******************************************************************************/
-void gatt_stop_conf_timer(tGATT_TCB& tcb, uint16_t cid) {
- /* start notification cache timer */
- if (tcb.eatt && cid != L2CAP_ATT_CID)
- EattExtension::GetInstance()->StopIndicationConfirmationTimer(tcb.peer_bda, cid);
- else
- alarm_cancel(tcb.conf_timer);
+void gatt_start_conf_timer(tGATT_TCB* p_tcb) {
+ alarm_set_on_mloop(p_tcb->conf_timer, GATT_WAIT_FOR_RSP_TIMEOUT_MS,
+ gatt_indication_confirmation_timeout, p_tcb);
}
/*******************************************************************************
@@ -602,35 +557,14 @@ void gatt_stop_conf_timer(tGATT_TCB& tcb, uint16_t cid) {
* Returns void
*
******************************************************************************/
-void gatt_start_ind_ack_timer(tGATT_TCB& tcb, uint16_t cid) {
+void gatt_start_ind_ack_timer(tGATT_TCB& tcb) {
/* start notification cache timer */
- if (tcb.eatt && cid != L2CAP_ATT_CID)
- EattExtension::GetInstance()->StartAppIndicationTimer(tcb.peer_bda, cid);
- else
- alarm_set_on_mloop(tcb.ind_ack_timer, GATT_WAIT_FOR_RSP_TIMEOUT_MS,
- gatt_ind_ack_timeout, &tcb);
+ alarm_set_on_mloop(tcb.ind_ack_timer, GATT_WAIT_FOR_RSP_TIMEOUT_MS,
+ gatt_ind_ack_timeout, &tcb);
}
/*******************************************************************************
*
- * Function gatt_stop_ind_ack_timer
- *
- * Description stop the application ack timer
- *
- * Returns void
- *
- ******************************************************************************/
-void gatt_stop_ind_ack_timer(tGATT_TCB* p_tcb, uint16_t cid) {
- /* start notification cache timer */
- if (p_tcb->eatt && cid != L2CAP_ATT_CID) {
- EattExtension::GetInstance()->StopAppIndicationTimer(p_tcb->peer_bda, cid);
- } else {
- alarm_cancel(p_tcb->ind_ack_timer);
- p_tcb->ind_count = 0;
- }
-}
-/*******************************************************************************
- *
* Function gatt_rsp_timeout
*
* Description Called when GATT wait for ATT command response timer expires
@@ -650,7 +584,7 @@ void gatt_rsp_timeout(void* data) {
p_clcb->retry_count < GATT_REQ_RETRY_LIMIT) {
uint8_t rsp_code;
LOG(WARNING) << __func__ << " retry discovery primary service";
- if (p_clcb != gatt_cmd_dequeue(*p_clcb->p_tcb, p_clcb->cid, &rsp_code)) {
+ if (p_clcb != gatt_cmd_dequeue(*p_clcb->p_tcb, &rsp_code)) {
LOG(ERROR) << __func__ << " command queue out of sync, disconnect";
} else {
p_clcb->retry_count++;
@@ -710,16 +644,13 @@ void gatt_indication_confirmation_timeout(void* data) {
* Returns void
*
******************************************************************************/
-void gatt_ind_ack_timeout(void* data) {
+void gatt_ind_ack_timeout(void* data) {
tGATT_TCB* p_tcb = (tGATT_TCB*)data;
CHECK(p_tcb);
LOG(WARNING) << __func__ << ": send ack now";
p_tcb->ind_count = 0;
- /*TODO: For now ATT used only, but we need to have timeout per CID
- * and use it here corretly.
- */
- attp_send_cl_confirmation_msg(*p_tcb, L2CAP_ATT_CID);
+ attp_send_cl_msg(*p_tcb, nullptr, GATT_HANDLE_VALUE_CONF, NULL);
}
/*******************************************************************************
*
@@ -800,7 +731,7 @@ void gatt_sr_send_req_callback(uint16_t conn_id, uint32_t trans_id,
* Returns void
*
******************************************************************************/
-tGATT_STATUS gatt_send_error_rsp(tGATT_TCB& tcb, uint16_t cid, uint8_t err_code,
+tGATT_STATUS gatt_send_error_rsp(tGATT_TCB& tcb, uint8_t err_code,
uint8_t op_code, uint16_t handle, bool deq) {
tGATT_STATUS status;
BT_HDR* p_buf;
@@ -812,12 +743,11 @@ tGATT_STATUS gatt_send_error_rsp(tGATT_TCB& tcb, uint16_t cid, uint8_t err_code,
p_buf = attp_build_sr_msg(tcb, GATT_RSP_ERROR, &msg);
if (p_buf != NULL) {
- status = attp_send_sr_msg(tcb, cid, p_buf);
+ status = attp_send_sr_msg(tcb, p_buf);
} else
status = GATT_INSUF_RESOURCE;
- if (deq)
- gatt_dequeue_sr_cmd(tcb, cid);
+ if (deq) gatt_dequeue_sr_cmd(tcb);
return status;
}
@@ -946,47 +876,20 @@ tGATT_REG* gatt_get_regcb(tGATT_IF gatt_if) {
bool gatt_is_clcb_allocated(uint16_t conn_id) {
uint8_t i = 0;
- uint8_t num_of_allocated = 0;
- tGATT_IF gatt_if = GATT_GET_GATT_IF(conn_id);
- uint8_t tcb_idx = GATT_GET_TCB_IDX(conn_id);
- tGATT_TCB* p_tcb = gatt_get_tcb_by_idx(tcb_idx);
- tGATT_REG* p_reg = gatt_get_regcb(gatt_if);
- int possible_plcb = 1;
-
- if (p_reg->eatt_support) possible_plcb += p_tcb->eatt;
+ bool is_allocated = false;
- /* With eatt number of active clcbs can me up to 1 + number of eatt channels
- */
for (i = 0; i < GATT_CL_MAX_LCB; i++) {
if (gatt_cb.clcb[i].in_use && (gatt_cb.clcb[i].conn_id == conn_id)) {
- if (++num_of_allocated == possible_plcb) return true;
+ is_allocated = true;
+ break;
}
}
- return false;
+ return is_allocated;
}
/*******************************************************************************
*
- * Function gatt_tcb_is_cid_busy
- *
- * Description The function check if channel with given cid is busy
- *
- * Returns True when busy
- *
- ******************************************************************************/
-
-bool gatt_tcb_is_cid_busy(tGATT_TCB& tcb, uint16_t cid) {
- if (cid == tcb.att_lcid) return !tcb.cl_cmd_q.empty();
-
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
- if (!channel) return false;
-
- return !channel->cl_cmd_q_.empty();
-}
-/*******************************************************************************
- *
* Function gatt_clcb_alloc
*
* Description The function allocates a GATT connection link control block
@@ -1011,10 +914,6 @@ tGATT_CLCB* gatt_clcb_alloc(uint16_t conn_id) {
p_clcb->conn_id = conn_id;
p_clcb->p_reg = p_reg;
p_clcb->p_tcb = p_tcb;
-
- /* Use eatt only when clients wants that */
- p_clcb->cid = gatt_tcb_get_att_cid(*p_tcb, p_reg->eatt_support);
-
break;
}
}
@@ -1024,127 +923,6 @@ tGATT_CLCB* gatt_clcb_alloc(uint16_t conn_id) {
/*******************************************************************************
*
- * Function gatt_tcb_get_cid_available_for_indication
- *
- * Description This function checks if indication can be send
- *
- * Returns true when stack is busy with waiting on indication
- * confirmation, false otherwise
- *
- ******************************************************************************/
-bool gatt_tcb_get_cid_available_for_indication(tGATT_TCB* p_tcb,
- bool eatt_support,
- uint16_t** indicated_handle_p,
- uint16_t* cid_p) {
- if (p_tcb->eatt && eatt_support) {
- EattChannel* channel =
- EattExtension::GetInstance()->GetChannelAvailableForIndication(p_tcb->peer_bda);
- if (channel) {
- *indicated_handle_p = &channel->indicate_handle_;
- *cid_p = channel->cid_;
- return true;
- }
- }
-
- if (!GATT_HANDLE_IS_VALID(p_tcb->indicate_handle)) {
- *indicated_handle_p = &p_tcb->indicate_handle;
- *cid_p = p_tcb->att_lcid;
- return true;
- }
-
- return false;
-}
-
-/*******************************************************************************
- *
- * Function gatt_tcb_find_indicate_handle
- *
- * Description This function checks if indication can be send
- *
- * Returns true when indication handle found, false otherwise
- *
- ******************************************************************************/
-bool gatt_tcb_find_indicate_handle(tGATT_TCB& tcb, uint16_t cid,
- uint16_t* indicated_handle_p) {
- if (cid == tcb.att_lcid) {
- *indicated_handle_p = tcb.indicate_handle;
- tcb.indicate_handle = 0;
- return true;
- }
-
- if (tcb.eatt) {
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
- if (channel) {
- *indicated_handle_p = channel->indicate_handle_;
- channel->indicate_handle_ = 0;
- return true;
- }
- }
-
- return false;
-}
-
-/*******************************************************************************
- *
- * Function gatt_tcb_get_att_cid
- *
- * Description This function gets cid for the GATT operation
- *
- * Returns Available CID
- *
- ******************************************************************************/
-
-uint16_t gatt_tcb_get_att_cid(tGATT_TCB& tcb, bool eatt_support) {
- if (eatt_support && tcb.eatt) {
- EattChannel* channel =
- EattExtension::GetInstance()->GetChannelAvailableForClientRequest(tcb.peer_bda);
- if (channel) {
- return channel->cid_;
- }
- }
- return tcb.att_lcid;
-}
-
-/*******************************************************************************
- *
- * Function gatt_tcb_get_payload_size_tx
- *
- * Description This function gets payload size for the GATT operation
- *
- * Returns Payload size for sending data
- *
- ******************************************************************************/
-uint16_t gatt_tcb_get_payload_size_tx(tGATT_TCB& tcb, uint16_t cid) {
- if (!tcb.eatt || (cid == tcb.att_lcid)) return tcb.payload_size;
-
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
-
- return channel->tx_mtu_;
-}
-
-/*******************************************************************************
- *
- * Function gatt_tcb_get_payload_size_rx
- *
- * Description This function gets payload size for the GATT operation
- *
- * Returns Payload size for receiving data
- *
- ******************************************************************************/
-
-uint16_t gatt_tcb_get_payload_size_rx(tGATT_TCB& tcb, uint16_t cid) {
- if (!tcb.eatt || (cid == tcb.att_lcid)) return tcb.payload_size;
-
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
-
- return channel->rx_mtu_;
-}
-
-/*******************************************************************************
- *
* Function gatt_clcb_dealloc
*
* Description The function de-allocates a GATT connection link control
@@ -1175,10 +953,7 @@ tGATT_TCB* gatt_find_tcb_by_cid(uint16_t lcid) {
tGATT_TCB* p_tcb = NULL;
for (xx = 0; xx < GATT_MAX_PHY_CHANNEL; xx++) {
- if (gatt_cb.tcb[xx].in_use &&
- ((gatt_cb.tcb[xx].att_lcid == lcid) ||
- ((EattExtension::GetInstance()->FindEattChannelByCid(gatt_cb.tcb[xx].peer_bda,
- lcid) != nullptr)))) {
+ if (gatt_cb.tcb[xx].in_use && gatt_cb.tcb[xx].att_lcid == lcid) {
p_tcb = &gatt_cb.tcb[xx];
break;
}
@@ -1212,18 +987,6 @@ void gatt_sr_copy_prep_cnt_to_cback_cnt(tGATT_TCB& tcb) {
}
}
-/* Get outstanding server command pointer by the transaction id */
-tGATT_SR_CMD* gatt_sr_get_cmd_by_trans_id(tGATT_TCB* p_tcb, uint32_t trans_id) {
- if (p_tcb->sr_cmd.trans_id == trans_id) return &p_tcb->sr_cmd;
-
- if (!p_tcb->eatt) return nullptr;
-
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByTransId(p_tcb->peer_bda, trans_id);
- if (!channel) return nullptr;
-
- return &channel->server_outstanding_cmd_;
-}
/*******************************************************************************
*
* Function gatt_sr_is_cback_cnt_zero
@@ -1269,15 +1032,9 @@ bool gatt_sr_is_prep_cnt_zero(tGATT_TCB& tcb) {
* Returns None
*
******************************************************************************/
-void gatt_sr_reset_cback_cnt(tGATT_TCB& tcb, uint16_t cid) {
+void gatt_sr_reset_cback_cnt(tGATT_TCB& tcb) {
for (uint8_t i = 0; i < GATT_MAX_APPS; i++) {
- if (cid == tcb.att_lcid) {
- tcb.sr_cmd.cback_cnt[i] = 0;
- } else {
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
- channel->server_outstanding_cmd_.cback_cnt[i] = 0;
- }
+ tcb.sr_cmd.cback_cnt[i] = 0;
}
}
@@ -1296,38 +1053,6 @@ void gatt_sr_reset_prep_cnt(tGATT_TCB& tcb) {
}
}
-/* Get pointer to server command on given cid */
-tGATT_SR_CMD* gatt_sr_get_cmd_by_cid(tGATT_TCB& tcb, uint16_t cid) {
- tGATT_SR_CMD* sr_cmd_p;
-
- LOG(INFO) << __func__ << " cid: " << int(cid) << " tcb cid " << tcb.att_lcid;
- if (cid == tcb.att_lcid) {
- sr_cmd_p = &tcb.sr_cmd;
- } else {
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
- sr_cmd_p = &channel->server_outstanding_cmd_;
- }
-
- return sr_cmd_p;
-}
-
-/* Get pointer to the context of outstanding multi request */
-tGATT_READ_MULTI* gatt_sr_get_read_multi(tGATT_TCB& tcb, uint16_t cid) {
- tGATT_READ_MULTI* read_multi_p;
-
- LOG(INFO) << __func__ << " cid: " << int(cid) << " tcb cid " << tcb.att_lcid;
- if (cid == tcb.att_lcid) {
- read_multi_p = &tcb.sr_cmd.multi_req;
- } else {
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
- read_multi_p = &channel->server_outstanding_cmd_.multi_req;
- }
-
- return read_multi_p;
-}
-
/*******************************************************************************
*
* Function gatt_sr_update_cback_cnt
@@ -1337,27 +1062,18 @@ tGATT_READ_MULTI* gatt_sr_get_read_multi(tGATT_TCB& tcb, uint16_t cid) {
* Returns None
*
******************************************************************************/
-void gatt_sr_update_cback_cnt(tGATT_TCB& tcb, uint16_t cid, tGATT_IF gatt_if,
- bool is_inc, bool is_reset_first) {
+void gatt_sr_update_cback_cnt(tGATT_TCB& tcb, tGATT_IF gatt_if, bool is_inc,
+ bool is_reset_first) {
uint8_t idx = ((uint8_t)gatt_if) - 1;
- tGATT_SR_CMD* sr_cmd_p;
-
- if (cid == tcb.att_lcid) {
- sr_cmd_p = &tcb.sr_cmd;
- } else {
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
- sr_cmd_p = &channel->server_outstanding_cmd_;
- }
if (is_reset_first) {
- gatt_sr_reset_cback_cnt(tcb, cid);
+ gatt_sr_reset_cback_cnt(tcb);
}
if (is_inc) {
- sr_cmd_p->cback_cnt[idx]++;
+ tcb.sr_cmd.cback_cnt[idx]++;
} else {
- if (sr_cmd_p->cback_cnt[idx]) {
- sr_cmd_p->cback_cnt[idx]--;
+ if (tcb.sr_cmd.cback_cnt[idx]) {
+ tcb.sr_cmd.cback_cnt[idx]--;
}
}
}
@@ -1417,46 +1133,31 @@ void gatt_cmd_enq(tGATT_TCB& tcb, tGATT_CLCB* p_clcb, bool to_send,
cmd.op_code = op_code;
cmd.p_cmd = p_buf;
cmd.p_clcb = p_clcb;
- cmd.cid = p_clcb->cid;
- if (p_clcb->cid == tcb.att_lcid) {
- tcb.cl_cmd_q.push(cmd);
- } else {
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cmd.cid);
- CHECK(channel);
- channel->cl_cmd_q_.push(cmd);
+ if (!to_send) {
+ // TODO: WTF why do we clear the queue here ?!
+ tcb.cl_cmd_q = std::queue<tGATT_CMD_Q>();
}
+
+ tcb.cl_cmd_q.push(cmd);
}
/** dequeue the command in the client CCB command queue */
-tGATT_CLCB* gatt_cmd_dequeue(tGATT_TCB& tcb, uint16_t cid, uint8_t* p_op_code) {
- std::queue<tGATT_CMD_Q>* cl_cmd_q_p;
+tGATT_CLCB* gatt_cmd_dequeue(tGATT_TCB& tcb, uint8_t* p_op_code) {
+ if (tcb.cl_cmd_q.empty()) return nullptr;
- if (cid == tcb.att_lcid) {
- cl_cmd_q_p = &tcb.cl_cmd_q;
- } else {
- EattChannel* channel =
- EattExtension::GetInstance()->FindEattChannelByCid(tcb.peer_bda, cid);
- CHECK(channel);
- cl_cmd_q_p = &channel->cl_cmd_q_;
- }
-
- if (cl_cmd_q_p->empty()) return nullptr;
-
- tGATT_CMD_Q cmd = cl_cmd_q_p->front();
+ tGATT_CMD_Q cmd = tcb.cl_cmd_q.front();
tGATT_CLCB* p_clcb = cmd.p_clcb;
*p_op_code = cmd.op_code;
- p_clcb->cid = cid;
- cl_cmd_q_p->pop();
+ tcb.cl_cmd_q.pop();
return p_clcb;
}
/** Send out the ATT message for write */
-tGATT_STATUS gatt_send_write_msg(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
- uint8_t op_code, uint16_t handle, uint16_t len,
- uint16_t offset, uint8_t* p_data) {
+uint8_t gatt_send_write_msg(tGATT_TCB& tcb, tGATT_CLCB* p_clcb, uint8_t op_code,
+ uint16_t handle, uint16_t len, uint16_t offset,
+ uint8_t* p_data) {
tGATT_CL_MSG msg;
msg.attr_value.handle = handle;
msg.attr_value.len = len;
@@ -1481,8 +1182,7 @@ void gatt_end_operation(tGATT_CLCB* p_clcb, tGATT_STATUS status, void* p_data) {
tGATT_CL_COMPLETE cb_data;
tGATT_CMPL_CBACK* p_cmpl_cb =
(p_clcb->p_reg) ? p_clcb->p_reg->app_cb.p_cmpl_cb : NULL;
- tGATTC_OPTYPE op = p_clcb->operation;
- tGATT_DISC_TYPE disc_type = GATT_DISC_MAX;
+ uint8_t op = p_clcb->operation, disc_type = GATT_DISC_MAX;
tGATT_DISC_CMPL_CB* p_disc_cmpl_cb =
(p_clcb->p_reg) ? p_clcb->p_reg->app_cb.p_disc_cmpl_cb : NULL;
uint16_t conn_id;
@@ -1518,7 +1218,7 @@ void gatt_end_operation(tGATT_CLCB* p_clcb, tGATT_STATUS status, void* p_data) {
cb_data.mtu = p_clcb->p_tcb->payload_size;
if (p_clcb->operation == GATTC_OPTYPE_DISCOVERY) {
- disc_type = static_cast<tGATT_DISC_TYPE>(p_clcb->op_subtype);
+ disc_type = p_clcb->op_subtype;
}
}
@@ -1526,7 +1226,7 @@ void gatt_end_operation(tGATT_CLCB* p_clcb, tGATT_STATUS status, void* p_data) {
operation = p_clcb->operation;
conn_id = p_clcb->conn_id;
- gatt_stop_rsp_timer(p_clcb);
+ alarm_cancel(p_clcb->gatt_rsp_timer_ent);
gatt_clcb_dealloc(p_clcb);
@@ -1542,7 +1242,7 @@ void gatt_end_operation(tGATT_CLCB* p_clcb, tGATT_STATUS status, void* p_data) {
}
/** This function cleans up the control blocks when L2CAP channel disconnect */
-void gatt_cleanup_upon_disc(const RawAddress& bda, tGATT_DISCONN_REASON reason,
+void gatt_cleanup_upon_disc(const RawAddress& bda, uint16_t reason,
tBT_TRANSPORT transport) {
VLOG(1) << __func__;
@@ -1554,7 +1254,7 @@ void gatt_cleanup_upon_disc(const RawAddress& bda, tGATT_DISCONN_REASON reason,
tGATT_CLCB* p_clcb = &gatt_cb.clcb[i];
if (!p_clcb->in_use || p_clcb->p_tcb != p_tcb) continue;
- gatt_stop_rsp_timer(p_clcb);
+ alarm_cancel(p_clcb->gatt_rsp_timer_ent);
VLOG(1) << "found p_clcb conn_id=" << +p_clcb->conn_id;
if (p_clcb->operation == GATTC_OPTYPE_NONE) {
gatt_clcb_dealloc(p_clcb);
@@ -1576,8 +1276,10 @@ void gatt_cleanup_upon_disc(const RawAddress& bda, tGATT_DISCONN_REASON reason,
tGATT_REG* p_reg = &gatt_cb.cl_rcb[i];
if (p_reg->in_use && p_reg->app_cb.p_conn_cb) {
uint16_t conn_id = GATT_CREATE_CONN_ID(p_tcb->tcb_idx, p_reg->gatt_if);
- (*p_reg->app_cb.p_conn_cb)(p_reg->gatt_if, bda, conn_id,
- kGattDisconnected, reason, transport);
+ VLOG(1) << StringPrintf("found p_reg tcb_idx=%d gatt_if=%d conn_id=0x%x",
+ p_tcb->tcb_idx, p_reg->gatt_if, conn_id);
+ (*p_reg->app_cb.p_conn_cb)(p_reg->gatt_if, bda, conn_id, false, reason,
+ transport);
}
}
@@ -1614,8 +1316,5 @@ uint8_t* gatt_dbg_op_name(uint8_t op_code) {
bool gatt_auto_connect_dev_remove(tGATT_IF gatt_if, const RawAddress& bd_addr) {
tGATT_TCB* p_tcb = gatt_find_tcb_by_addr(bd_addr, BT_TRANSPORT_LE);
if (p_tcb) gatt_update_app_use_link_flag(gatt_if, p_tcb, false, false);
- if (bluetooth::shim::is_gd_acl_enabled()) {
- acl_add_to_ignore_auto_connect_after_disconnect(bd_addr);
- }
return connection_manager::background_connect_remove(gatt_if, bd_addr);
}
diff --git a/stack/hcic/hciblecmds.cc b/stack/hcic/hciblecmds.cc
index bc18dd62d..001532dc2 100644
--- a/stack/hcic/hciblecmds.cc
+++ b/stack/hcic/hciblecmds.cc
@@ -29,83 +29,10 @@
#include "hcidefs.h"
#include "hcimsgs.h"
-#include <bitset>
-
#include <base/bind.h>
#include <stddef.h>
#include <string.h>
-/*******************************************************************************
- * BLE Commands
- * Note: "local_controller_id" is for transport, not counted in HCI
- * message size
- ******************************************************************************/
-#define HCIC_BLE_RAND_DI_SIZE 8
-#define HCIC_BLE_IRK_SIZE 16
-
-#define HCIC_PARAM_SIZE_SET_USED_FEAT_CMD 8
-#define HCIC_PARAM_SIZE_WRITE_RANDOM_ADDR_CMD 6
-#define HCIC_PARAM_SIZE_BLE_WRITE_ADV_PARAMS 15
-#define HCIC_PARAM_SIZE_BLE_WRITE_SCAN_RSP 31
-#define HCIC_PARAM_SIZE_WRITE_ADV_ENABLE 1
-#define HCIC_PARAM_SIZE_BLE_WRITE_SCAN_PARAM 7
-#define HCIC_PARAM_SIZE_BLE_WRITE_SCAN_ENABLE 2
-#define HCIC_PARAM_SIZE_BLE_CREATE_LL_CONN 25
-#define HCIC_PARAM_SIZE_BLE_CREATE_CONN_CANCEL 0
-#define HCIC_PARAM_SIZE_CLEAR_ACCEPTLIST 0
-#define HCIC_PARAM_SIZE_ADD_ACCEPTLIST 7
-#define HCIC_PARAM_SIZE_REMOVE_ACCEPTLIST 7
-#define HCIC_PARAM_SIZE_BLE_UPD_LL_CONN_PARAMS 14
-#define HCIC_PARAM_SIZE_SET_HOST_CHNL_CLASS 5
-#define HCIC_PARAM_SIZE_READ_CHNL_MAP 2
-#define HCIC_PARAM_SIZE_BLE_READ_REMOTE_FEAT 2
-#define HCIC_PARAM_SIZE_BLE_ENCRYPT 32
-#define HCIC_PARAM_SIZE_WRITE_LE_HOST_SUPPORTED 2
-
-#define HCIC_BLE_RAND_DI_SIZE 8
-#define HCIC_BLE_ENCRYPT_KEY_SIZE 16
-#define HCIC_PARAM_SIZE_BLE_START_ENC \
- (4 + HCIC_BLE_RAND_DI_SIZE + HCIC_BLE_ENCRYPT_KEY_SIZE)
-#define HCIC_PARAM_SIZE_LTK_REQ_REPLY (2 + HCIC_BLE_ENCRYPT_KEY_SIZE)
-#define HCIC_PARAM_SIZE_LTK_REQ_NEG_REPLY 2
-#define HCIC_BLE_CHNL_MAP_SIZE 5
-#define HCIC_PARAM_SIZE_BLE_WRITE_ADV_DATA 31
-
-#define HCIC_PARAM_SIZE_BLE_ADD_DEV_RESOLVING_LIST (7 + HCIC_BLE_IRK_SIZE * 2)
-#define HCIC_PARAM_SIZE_BLE_RM_DEV_RESOLVING_LIST 7
-#define HCIC_PARAM_SIZE_BLE_SET_PRIVACY_MODE 8
-#define HCIC_PARAM_SIZE_BLE_CLEAR_RESOLVING_LIST 0
-#define HCIC_PARAM_SIZE_BLE_READ_RESOLVING_LIST_SIZE 0
-#define HCIC_PARAM_SIZE_BLE_READ_RESOLVABLE_ADDR_PEER 7
-#define HCIC_PARAM_SIZE_BLE_READ_RESOLVABLE_ADDR_LOCAL 7
-#define HCIC_PARAM_SIZE_BLE_SET_ADDR_RESOLUTION_ENABLE 1
-#define HCIC_PARAM_SIZE_BLE_SET_RAND_PRIV_ADDR_TIMOUT 2
-
-#define HCIC_PARAM_SIZE_BLE_READ_PHY 2
-#define HCIC_PARAM_SIZE_BLE_SET_DEFAULT_PHY 3
-#define HCIC_PARAM_SIZE_BLE_SET_PHY 7
-#define HCIC_PARAM_SIZE_BLE_ENH_RX_TEST 3
-#define HCIC_PARAM_SIZE_BLE_ENH_TX_TEST 4
-
-#define HCIC_PARAM_SIZE_BLE_SET_DATA_LENGTH 6
-#define HCIC_PARAM_SIZE_BLE_WRITE_EXTENDED_SCAN_PARAM 11
-
-#define HCIC_PARAM_SIZE_BLE_RC_PARAM_REQ_REPLY 14
-#define HCIC_PARAM_SIZE_BLE_RC_PARAM_REQ_NEG_REPLY 3
-
-#define HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_CREATE_SYNC 14
-#define HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_CREATE_SYNC_CANCEL 0
-#define HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_TERMINATE_SYNC 2
-#define HCIC_PARAM_SIZE_ADD_DEVICE_TO_PERIODIC_ADVERTISER_LIST 8
-#define HCIC_PARAM_SIZE_REMOVE_DEVICE_FROM_PERIODIC_ADVERTISER_LIST 8
-#define HCIC_PARAM_SIZE_CLEAR_PERIODIC_ADVERTISER_LIST 0
-#define HCIC_PARAM_SIZE_READ_PERIODIC_ADVERTISER_LIST_SIZE 0
-#define HCIC_PARAM_SIZE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE 3
-#define HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_SYNC_TRANSFER 6
-#define HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER 5
-#define HCIC_PARAM_SIZE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMS 8
-#define HCIC_PARAM_SIZE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMS 8
-
void btsnd_hcic_ble_set_local_used_feat(uint8_t feat_set[8]) {
BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
uint8_t* pp = (uint8_t*)(p + 1);
@@ -317,36 +244,36 @@ void btsnd_hcic_ble_create_conn_cancel(void) {
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
-void btsnd_hcic_ble_clear_acceptlist(
+void btsnd_hcic_ble_clear_white_list(
base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_BLE_CLEAR_ACCEPTLIST, nullptr, 0,
+ btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_BLE_CLEAR_WHITE_LIST, nullptr, 0,
std::move(cb));
}
-void btsnd_hcic_ble_add_acceptlist(
+void btsnd_hcic_ble_add_white_list(
uint8_t addr_type, const RawAddress& bda,
base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t param[HCIC_PARAM_SIZE_ADD_ACCEPTLIST];
+ uint8_t param[HCIC_PARAM_SIZE_ADD_WHITE_LIST];
uint8_t* pp = param;
UINT8_TO_STREAM(pp, addr_type);
BDADDR_TO_STREAM(pp, bda);
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_BLE_ADD_ACCEPTLIST, param,
- HCIC_PARAM_SIZE_ADD_ACCEPTLIST, std::move(cb));
+ btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_BLE_ADD_WHITE_LIST, param,
+ HCIC_PARAM_SIZE_ADD_WHITE_LIST, std::move(cb));
}
-void btsnd_hcic_ble_remove_from_acceptlist(
+void btsnd_hcic_ble_remove_from_white_list(
uint8_t addr_type, const RawAddress& bda,
base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t param[HCIC_PARAM_SIZE_REMOVE_ACCEPTLIST];
+ uint8_t param[HCIC_PARAM_SIZE_REMOVE_WHITE_LIST];
uint8_t* pp = param;
UINT8_TO_STREAM(pp, addr_type);
BDADDR_TO_STREAM(pp, bda);
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_BLE_REMOVE_ACCEPTLIST, param,
- HCIC_PARAM_SIZE_REMOVE_ACCEPTLIST, std::move(cb));
+ btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_BLE_REMOVE_WHITE_LIST, param,
+ HCIC_PARAM_SIZE_REMOVE_WHITE_LIST, std::move(cb));
}
void btsnd_hcic_ble_upd_ll_conn_params(uint16_t handle, uint16_t conn_int_min,
@@ -440,11 +367,11 @@ void btsnd_hcic_ble_encrypt(uint8_t* key, uint8_t key_len, uint8_t* plain_text,
memset(pp, 0, HCIC_PARAM_SIZE_BLE_ENCRYPT);
- if (key_len > HCIC_BLE_ENCRYPT_KEY_SIZE) key_len = HCIC_BLE_ENCRYPT_KEY_SIZE;
- if (pt_len > HCIC_BLE_ENCRYPT_KEY_SIZE) pt_len = HCIC_BLE_ENCRYPT_KEY_SIZE;
+ if (key_len > HCIC_BLE_ENCRYT_KEY_SIZE) key_len = HCIC_BLE_ENCRYT_KEY_SIZE;
+ if (pt_len > HCIC_BLE_ENCRYT_KEY_SIZE) pt_len = HCIC_BLE_ENCRYT_KEY_SIZE;
ARRAY_TO_STREAM(pp, key, key_len);
- pp += (HCIC_BLE_ENCRYPT_KEY_SIZE - key_len);
+ pp += (HCIC_BLE_ENCRYT_KEY_SIZE - key_len);
ARRAY_TO_STREAM(pp, plain_text, pt_len);
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
@@ -477,7 +404,7 @@ void btsnd_hcic_ble_start_enc(uint16_t handle,
UINT16_TO_STREAM(pp, handle);
ARRAY_TO_STREAM(pp, rand, HCIC_BLE_RAND_DI_SIZE);
UINT16_TO_STREAM(pp, ediv);
- ARRAY_TO_STREAM(pp, ltk.data(), HCIC_BLE_ENCRYPT_KEY_SIZE);
+ ARRAY_TO_STREAM(pp, ltk.data(), HCIC_BLE_ENCRYT_KEY_SIZE);
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
@@ -493,7 +420,7 @@ void btsnd_hcic_ble_ltk_req_reply(uint16_t handle, const Octet16& ltk) {
UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_LTK_REQ_REPLY);
UINT16_TO_STREAM(pp, handle);
- ARRAY_TO_STREAM(pp, ltk.data(), HCIC_BLE_ENCRYPT_KEY_SIZE);
+ ARRAY_TO_STREAM(pp, ltk.data(), HCIC_BLE_ENCRYT_KEY_SIZE);
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
@@ -572,6 +499,8 @@ void btsnd_hcic_ble_read_host_supported(void) {
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
+#if (BLE_LLT_INCLUDED == TRUE)
+
void btsnd_hcic_ble_rc_param_req_reply(uint16_t handle, uint16_t conn_int_min,
uint16_t conn_int_max,
uint16_t conn_latency,
@@ -613,6 +542,7 @@ void btsnd_hcic_ble_rc_param_req_neg_reply(uint16_t handle, uint8_t reason) {
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
+#endif
void btsnd_hcic_ble_add_device_resolving_list(uint8_t addr_type_peer,
const RawAddress& bda_peer,
@@ -628,8 +558,8 @@ void btsnd_hcic_ble_add_device_resolving_list(uint8_t addr_type_peer,
UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_BLE_ADD_DEV_RESOLVING_LIST);
UINT8_TO_STREAM(pp, addr_type_peer);
BDADDR_TO_STREAM(pp, bda_peer);
- ARRAY_TO_STREAM(pp, irk_peer.data(), HCIC_BLE_ENCRYPT_KEY_SIZE);
- ARRAY_TO_STREAM(pp, irk_local.data(), HCIC_BLE_ENCRYPT_KEY_SIZE);
+ ARRAY_TO_STREAM(pp, irk_peer.data(), HCIC_BLE_ENCRYT_KEY_SIZE);
+ ARRAY_TO_STREAM(pp, irk_local.data(), HCIC_BLE_ENCRYT_KEY_SIZE);
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
@@ -889,437 +819,3 @@ void btsnd_hcic_ble_ext_create_conn(uint8_t init_filter_policy,
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
-
-void btsnd_hcic_read_iso_tx_sync(
- uint16_t iso_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- const int params_len = 2;
- uint8_t param[params_len];
- uint8_t* pp = param;
-
- UINT16_TO_STREAM(pp, iso_handle);
-
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_LE_READ_ISO_TX_SYNC, param,
- params_len, std::move(cb));
-}
-
-void btsnd_hcic_set_cig_params(
- uint8_t cig_id, uint32_t sdu_itv_mtos, uint32_t sdu_itv_stom, uint8_t sca,
- uint8_t packing, uint8_t framing, uint16_t max_trans_lat_stom,
- uint16_t max_trans_lat_mtos, uint8_t cis_cnt, const EXT_CIS_CFG* cis_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- const int params_len = 15 + cis_cnt * 9;
- uint8_t param[params_len];
- uint8_t* pp = param;
-
- UINT8_TO_STREAM(pp, cig_id);
- UINT24_TO_STREAM(pp, sdu_itv_mtos);
- UINT24_TO_STREAM(pp, sdu_itv_stom);
- UINT8_TO_STREAM(pp, sca);
- UINT8_TO_STREAM(pp, packing);
- UINT8_TO_STREAM(pp, framing);
- UINT16_TO_STREAM(pp, max_trans_lat_mtos);
- UINT16_TO_STREAM(pp, max_trans_lat_stom);
- UINT8_TO_STREAM(pp, cis_cnt);
-
- for (int i = 0; i < cis_cnt; i++) {
- UINT8_TO_STREAM(pp, cis_cfg[i].cis_id);
- UINT16_TO_STREAM(pp, cis_cfg[i].max_sdu_size_mtos);
- UINT16_TO_STREAM(pp, cis_cfg[i].max_sdu_size_stom);
- UINT8_TO_STREAM(pp, cis_cfg[i].phy_mtos);
- UINT8_TO_STREAM(pp, cis_cfg[i].phy_stom);
- UINT8_TO_STREAM(pp, cis_cfg[i].rtn_mtos);
- UINT8_TO_STREAM(pp, cis_cfg[i].rtn_stom);
- }
-
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_LE_SET_CIG_PARAMS, param, params_len,
- std::move(cb));
-}
-
-void btsnd_hcic_create_cis(uint8_t num_cis, const EXT_CIS_CREATE_CFG* cis_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- const int params_len = 1 + num_cis * 4;
- uint8_t param[params_len];
- uint8_t* pp = param;
-
- UINT8_TO_STREAM(pp, num_cis);
-
- for (int i = 0; i < num_cis; i++) {
- UINT16_TO_STREAM(pp, cis_cfg[i].cis_conn_handle);
- UINT16_TO_STREAM(pp, cis_cfg[i].acl_conn_handle);
- }
-
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_LE_CREATE_CIS, param, params_len,
- std::move(cb));
-}
-
-void btsnd_hcic_remove_cig(uint8_t cig_id,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- const int params_len = 1;
- uint8_t param[params_len];
- uint8_t* pp = param;
-
- UINT8_TO_STREAM(pp, cig_id);
-
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_LE_REMOVE_CIG, param, params_len,
- std::move(cb));
-}
-
-void btsnd_hcic_accept_cis_req(uint16_t conn_handle) {
- BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
- uint8_t* pp = (uint8_t*)(p + 1);
-
- const int param_len = 2;
- p->len = HCIC_PREAMBLE_SIZE + param_len;
- p->offset = 0;
-
- UINT16_TO_STREAM(pp, HCI_LE_ACCEPT_CIS_REQ);
- UINT8_TO_STREAM(pp, param_len);
-
- UINT16_TO_STREAM(pp, conn_handle);
-
- btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
-}
-
-void btsnd_hcic_rej_cis_req(uint16_t conn_handle, uint8_t reason,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- const int params_len = 3;
- uint8_t param[params_len];
- uint8_t* pp = param;
-
- UINT16_TO_STREAM(pp, conn_handle);
- UINT8_TO_STREAM(pp, reason);
-
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_LE_REJ_CIS_REQ, param, params_len,
- std::move(cb));
-}
-
-void btsnd_hcic_req_peer_sca(uint16_t conn_handle) {
- BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
- uint8_t* pp = (uint8_t*)(p + 1);
-
- const int param_len = 2;
- p->len = HCIC_PREAMBLE_SIZE + param_len;
- p->offset = 0;
-
- UINT16_TO_STREAM(pp, HCI_LE_REQ_PEER_SCA);
- UINT8_TO_STREAM(pp, param_len);
- UINT16_TO_STREAM(pp, conn_handle);
-
- btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
-}
-
-void btsnd_hcic_create_big(uint8_t big_handle, uint8_t adv_handle,
- uint8_t num_bis, uint32_t sdu_itv,
- uint16_t max_sdu_size, uint16_t transport_latency,
- uint8_t rtn, uint8_t phy, uint8_t packing,
- uint8_t framing, uint8_t enc,
- std::array<uint8_t, 16> bcst_code) {
- BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
- uint8_t* pp = (uint8_t*)(p + 1);
-
- const int param_len = 31;
- p->len = HCIC_PREAMBLE_SIZE + param_len;
- p->offset = 0;
-
- UINT16_TO_STREAM(pp, HCI_LE_CREATE_BIG);
- UINT8_TO_STREAM(pp, param_len);
-
- UINT8_TO_STREAM(pp, big_handle);
- UINT8_TO_STREAM(pp, adv_handle);
- UINT8_TO_STREAM(pp, num_bis);
- UINT24_TO_STREAM(pp, sdu_itv);
- UINT16_TO_STREAM(pp, max_sdu_size);
- UINT16_TO_STREAM(pp, transport_latency);
- UINT8_TO_STREAM(pp, rtn);
- UINT8_TO_STREAM(pp, phy);
- UINT8_TO_STREAM(pp, packing);
- UINT8_TO_STREAM(pp, framing);
- UINT8_TO_STREAM(pp, enc);
-
- uint8_t* buf_ptr = bcst_code.data();
- ARRAY_TO_STREAM(pp, buf_ptr, 16);
-
- btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
-}
-
-void btsnd_hcic_term_big(uint8_t big_handle, uint8_t reason) {
- BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
- uint8_t* pp = (uint8_t*)(p + 1);
-
- const int param_len = 2;
- p->len = HCIC_PREAMBLE_SIZE + param_len;
- p->offset = 0;
-
- UINT16_TO_STREAM(pp, HCI_LE_TERM_BIG);
- UINT8_TO_STREAM(pp, param_len);
-
- UINT8_TO_STREAM(pp, big_handle);
- UINT8_TO_STREAM(pp, reason);
-
- btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
-}
-
-void btsnd_hcic_big_create_sync(uint8_t big_handle, uint16_t sync_handle,
- uint8_t enc, std::array<uint8_t, 16> bcst_code,
- uint8_t mse, uint16_t big_sync_timeout,
- std::vector<uint8_t> bis) {
- BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
- uint8_t* pp = (uint8_t*)(p + 1);
- uint8_t num_bis = bis.size();
-
- const int param_len = 24 + num_bis;
- p->len = HCIC_PREAMBLE_SIZE + param_len;
- p->offset = 0;
-
- UINT16_TO_STREAM(pp, HCI_LE_BIG_CREATE_SYNC);
- UINT8_TO_STREAM(pp, param_len);
-
- UINT8_TO_STREAM(pp, big_handle);
- UINT16_TO_STREAM(pp, sync_handle);
- UINT8_TO_STREAM(pp, enc);
-
- uint8_t* buf_ptr = bcst_code.data();
- ARRAY_TO_STREAM(pp, buf_ptr, 16);
-
- UINT8_TO_STREAM(pp, mse);
- UINT16_TO_STREAM(pp, big_sync_timeout);
- UINT8_TO_STREAM(pp, num_bis);
-
- for (int i = 0; i < num_bis; i++) {
- UINT8_TO_STREAM(pp, bis[i]);
- }
-
- btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
-}
-
-void btsnd_hcic_big_term_sync(uint8_t big_handle,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- const int params_len = 1;
- uint8_t param[params_len];
- uint8_t* pp = param;
-
- UINT8_TO_STREAM(pp, big_handle);
-
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_LE_BIG_TERM_SYNC, param, params_len,
- std::move(cb));
-}
-
-void btsnd_hcic_setup_iso_data_path(
- uint16_t iso_handle, uint8_t data_path_dir, uint8_t data_path_id,
- uint8_t codec_id_format, uint16_t codec_id_company,
- uint16_t codec_id_vendor, uint32_t controller_delay,
- std::vector<uint8_t> codec_conf,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- const int params_len = 13 + codec_conf.size();
- uint8_t param[params_len];
- uint8_t* pp = param;
-
- UINT16_TO_STREAM(pp, iso_handle);
- UINT8_TO_STREAM(pp, data_path_dir);
- UINT8_TO_STREAM(pp, data_path_id);
- UINT8_TO_STREAM(pp, codec_id_format);
- UINT16_TO_STREAM(pp, codec_id_company);
- UINT16_TO_STREAM(pp, codec_id_vendor);
- UINT24_TO_STREAM(pp, controller_delay);
- UINT8_TO_STREAM(pp, codec_conf.size());
- ARRAY_TO_STREAM(pp, codec_conf.data(), static_cast<int>(codec_conf.size()));
-
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_LE_SETUP_ISO_DATA_PATH, param,
- params_len, std::move(cb));
-}
-
-void btsnd_hcic_remove_iso_data_path(
- uint16_t iso_handle, uint8_t data_path_dir,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- const int params_len = 3;
- uint8_t param[params_len];
- uint8_t* pp = param;
-
- UINT16_TO_STREAM(pp, iso_handle);
- UINT8_TO_STREAM(pp, data_path_dir);
-
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_LE_REMOVE_ISO_DATA_PATH, param,
- params_len, std::move(cb));
-}
-
-void btsnd_hcic_read_iso_link_quality(
- uint16_t iso_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- const int params_len = 2;
- uint8_t param[params_len];
- uint8_t* pp = param;
-
- UINT16_TO_STREAM(pp, iso_handle);
-
- btu_hcif_send_cmd_with_cb(FROM_HERE, HCI_LE_READ_ISO_LINK_QUALITY, param,
- params_len, std::move(cb));
-}
-
-void btsnd_hcic_ble_periodic_advertising_create_sync(
- uint8_t options, uint8_t adv_sid, uint8_t adv_addr_type,
- const RawAddress& adv_addr, uint16_t skip_num, uint16_t sync_timeout,
- uint8_t sync_cte_type) {
- BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
- uint8_t* pp = (uint8_t*)(p + 1);
-
- p->len =
- HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_CREATE_SYNC;
- p->offset = 0;
-
- UINT16_TO_STREAM(pp, HCI_BLE_PERIODIC_ADVERTISING_CREATE_SYNC);
- UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_CREATE_SYNC);
- UINT8_TO_STREAM(pp, options);
- UINT8_TO_STREAM(pp, adv_sid);
- UINT8_TO_STREAM(pp, adv_addr_type);
- BDADDR_TO_STREAM(pp, adv_addr);
- UINT16_TO_STREAM(pp, skip_num);
- UINT16_TO_STREAM(pp, sync_timeout);
- UINT8_TO_STREAM(pp, sync_cte_type);
-
- btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
-}
-
-void btsnd_hcic_ble_periodic_advertising_create_sync_cancel(
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- btu_hcif_send_cmd_with_cb(
- FROM_HERE, HCI_BLE_PERIODIC_ADVERTISING_CREATE_SYNC_CANCEL, nullptr,
- HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_CREATE_SYNC_CANCEL, std::move(cb));
-}
-
-void btsnd_hcic_ble_periodic_advertising_terminate_sync(
- uint16_t sync_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t param[HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_TERMINATE_SYNC];
- uint8_t* pp = param;
-
- UINT16_TO_STREAM(pp, sync_handle);
-
- btu_hcif_send_cmd_with_cb(
- FROM_HERE, HCI_BLE_PERIODIC_ADVERTISING_TERMINATE_SYNC, param,
- HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_TERMINATE_SYNC, std::move(cb));
-}
-
-void btsnd_hci_ble_add_device_to_periodic_advertiser_list(
- uint8_t adv_addr_type, const RawAddress& adv_addr, uint8_t adv_sid,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t param[HCIC_PARAM_SIZE_ADD_DEVICE_TO_PERIODIC_ADVERTISER_LIST];
- uint8_t* pp = param;
-
- UINT8_TO_STREAM(pp, adv_addr_type);
- BDADDR_TO_STREAM(pp, adv_addr);
- UINT8_TO_STREAM(pp, adv_sid);
-
- btu_hcif_send_cmd_with_cb(
- FROM_HERE, HCI_BLE_ADD_DEVICE_TO_PERIODIC_ADVERTISER_LIST, param,
- HCIC_PARAM_SIZE_ADD_DEVICE_TO_PERIODIC_ADVERTISER_LIST, std::move(cb));
-}
-
-void btsnd_hci_ble_remove_device_from_periodic_advertiser_list(
- uint8_t adv_addr_type, const RawAddress& adv_addr, uint8_t adv_sid,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t param[HCIC_PARAM_SIZE_REMOVE_DEVICE_FROM_PERIODIC_ADVERTISER_LIST];
- uint8_t* pp = param;
-
- UINT8_TO_STREAM(pp, adv_addr_type);
- BDADDR_TO_STREAM(pp, adv_addr);
- UINT8_TO_STREAM(pp, adv_sid);
-
- btu_hcif_send_cmd_with_cb(
- FROM_HERE, HCI_BLE_REMOVE_DEVICE_FROM_PERIODIC_ADVERTISER_LIST, param,
- HCIC_PARAM_SIZE_REMOVE_DEVICE_FROM_PERIODIC_ADVERTISER_LIST,
- std::move(cb));
-}
-
-void btsnd_hci_ble_clear_periodic_advertiser_list(
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- btu_hcif_send_cmd_with_cb(
- FROM_HERE, HCI_BLE_CLEAR_PERIODIC_ADVERTISER_LIST, nullptr,
- HCIC_PARAM_SIZE_CLEAR_PERIODIC_ADVERTISER_LIST, std::move(cb));
-}
-
-void btsnd_hci_ble_read_periodic_advertiser_list_size(
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- btu_hcif_send_cmd_with_cb(
- FROM_HERE, HCI_BLE_READ_PERIODIC_ADVERTISER_LIST_SIZE, nullptr,
- HCIC_PARAM_SIZE_READ_PERIODIC_ADVERTISER_LIST_SIZE, std::move(cb));
-}
-
-void btsnd_hcic_ble_set_periodic_advertising_receive_enable(
- uint16_t sync_handle, bool enable,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t param[HCIC_PARAM_SIZE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE];
- uint8_t* pp = param;
-
- UINT16_TO_STREAM(pp, sync_handle);
- UINT8_TO_STREAM(pp, (enable ? 0x01 : 0x00));
-
- btu_hcif_send_cmd_with_cb(
- FROM_HERE, HCI_LE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE, param,
- HCIC_PARAM_SIZE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE, std::move(cb));
-}
-
-void btsnd_hcic_ble_periodic_advertising_sync_transfer(
- uint16_t conn_handle, uint16_t service_data, uint16_t sync_handle,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t param[HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_SYNC_TRANSFER];
- uint8_t* pp = param;
-
- UINT16_TO_STREAM(pp, conn_handle);
- UINT16_TO_STREAM(pp, service_data);
- UINT16_TO_STREAM(pp, sync_handle);
-
- btu_hcif_send_cmd_with_cb(
- FROM_HERE, HCI_LE_PERIODIC_ADVERTISING_SYNC_TRANSFER, param,
- HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_SYNC_TRANSFER, std::move(cb));
-}
-
-void btsnd_hcic_ble_periodic_advertising_set_info_transfer(
- uint16_t conn_handle, uint16_t service_data, uint8_t adv_handle,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t param[HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER];
- uint8_t* pp = param;
-
- UINT16_TO_STREAM(pp, conn_handle);
- UINT16_TO_STREAM(pp, service_data);
- UINT8_TO_STREAM(pp, adv_handle);
-
- btu_hcif_send_cmd_with_cb(
- FROM_HERE, HCI_LE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER, param,
- HCIC_PARAM_SIZE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER, std::move(cb));
-}
-
-void btsnd_hcic_ble_set_periodic_advertising_sync_transfer_params(
- uint16_t conn_handle, uint8_t mode, uint16_t skip, uint16_t sync_timeout,
- uint8_t cte_type, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t param[HCIC_PARAM_SIZE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMS];
- uint8_t* pp = param;
-
- UINT16_TO_STREAM(pp, conn_handle);
- UINT8_TO_STREAM(pp, mode);
- UINT16_TO_STREAM(pp, skip);
- UINT16_TO_STREAM(pp, sync_timeout);
- UINT8_TO_STREAM(pp, cte_type);
-
- btu_hcif_send_cmd_with_cb(
- FROM_HERE, HCI_LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAM, param,
- HCIC_PARAM_SIZE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMS,
- std::move(cb));
-}
-
-void btsnd_hcic_ble_set_default_periodic_advertising_sync_transfer_params(
- uint16_t conn_handle, uint8_t mode, uint16_t skip, uint16_t sync_timeout,
- uint8_t cte_type, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t param
- [HCIC_PARAM_SIZE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMS];
- uint8_t* pp = param;
-
- UINT16_TO_STREAM(pp, conn_handle);
- UINT8_TO_STREAM(pp, mode);
- UINT16_TO_STREAM(pp, skip);
- UINT16_TO_STREAM(pp, sync_timeout);
- UINT8_TO_STREAM(pp, cte_type);
-
- btu_hcif_send_cmd_with_cb(
- FROM_HERE, HCI_LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAM,
- param,
- HCIC_PARAM_SIZE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAMS,
- std::move(cb));
-}
diff --git a/stack/hcic/hcicmds.cc b/stack/hcic/hcicmds.cc
index 395a4503f..23a8648b0 100644
--- a/stack/hcic/hcicmds.cc
+++ b/stack/hcic/hcicmds.cc
@@ -32,458 +32,10 @@
#include <stddef.h>
#include <string.h>
-#include "stack/include/acl_hci_link_interface.h"
+#include "btm_int.h" /* Included for UIPC_* macro definitions */
-#include "bt_target.h"
-#include "bt_types.h"
-#include "device/include/esco_parameters.h"
-#include "hcidefs.h"
-
-#include <base/callback_forward.h>
-
-void bte_main_hci_send(BT_HDR* p_msg, uint16_t event);
-
-/* Message by message.... */
-
-#define HCIC_PARAM_SIZE_INQUIRY 5
-
-#define HCIC_INQ_INQ_LAP_OFF 0
-#define HCIC_INQ_DUR_OFF 3
-#define HCIC_INQ_RSP_CNT_OFF 4
-/* Inquiry */
-
-/* Inquiry Cancel */
-#define HCIC_PARAM_SIZE_INQ_CANCEL 0
-
-/* Periodic Inquiry Mode */
-#define HCIC_PARAM_SIZE_PER_INQ_MODE 9
-
-#define HCI_PER_INQ_MAX_INTRVL_OFF 0
-#define HCI_PER_INQ_MIN_INTRVL_OFF 2
-#define HCI_PER_INQ_INQ_LAP_OFF 4
-#define HCI_PER_INQ_DURATION_OFF 7
-#define HCI_PER_INQ_RSP_CNT_OFF 8
-/* Periodic Inquiry Mode */
-
-/* Exit Periodic Inquiry Mode */
-#define HCIC_PARAM_SIZE_EXIT_PER_INQ 0
-
-/* Create Connection */
-#define HCIC_PARAM_SIZE_CREATE_CONN 13
-
-#define HCIC_CR_CONN_BD_ADDR_OFF 0
-#define HCIC_CR_CONN_PKT_TYPES_OFF 6
-#define HCIC_CR_CONN_REP_MODE_OFF 8
-#define HCIC_CR_CONN_PAGE_SCAN_MODE_OFF 9
-#define HCIC_CR_CONN_CLK_OFF_OFF 10
-#define HCIC_CR_CONN_ALLOW_SWITCH_OFF 12
-/* Create Connection */
-
-/* Disconnect */
-#define HCIC_PARAM_SIZE_DISCONNECT 3
-
-#define HCI_DISC_HANDLE_OFF 0
-#define HCI_DISC_REASON_OFF 2
-/* Disconnect */
-
-/* Add SCO Connection */
-#define HCIC_PARAM_SIZE_ADD_SCO_CONN 4
-
-#define HCI_ADD_SCO_HANDLE_OFF 0
-#define HCI_ADD_SCO_PACKET_TYPES_OFF 2
-/* Add SCO Connection */
-
-/* Create Connection Cancel */
-#define HCIC_PARAM_SIZE_CREATE_CONN_CANCEL 6
-
-#define HCIC_CR_CONN_CANCEL_BD_ADDR_OFF 0
-/* Create Connection Cancel */
-
-/* Accept Connection Request */
-#define HCIC_PARAM_SIZE_ACCEPT_CONN 7
-
-#define HCI_ACC_CONN_BD_ADDR_OFF 0
-#define HCI_ACC_CONN_ROLE_OFF 6
-/* Accept Connection Request */
-
-/* Reject Connection Request */
-#define HCIC_PARAM_SIZE_REJECT_CONN 7
-
-#define HCI_REJ_CONN_BD_ADDR_OFF 0
-#define HCI_REJ_CONN_REASON_OFF 6
-/* Reject Connection Request */
-
-/* Link Key Request Reply */
-#define HCIC_PARAM_SIZE_LINK_KEY_REQ_REPLY 22
-
-#define HCI_LINK_KEY_REPLY_BD_ADDR_OFF 0
-#define HCI_LINK_KEY_REPLY_LINK_KEY_OFF 6
-/* Link Key Request Reply */
-
-/* Link Key Request Neg Reply */
-#define HCIC_PARAM_SIZE_LINK_KEY_NEG_REPLY 6
-
-#define HCI_LINK_KEY_NEG_REP_BD_ADR_OFF 0
-/* Link Key Request Neg Reply */
-
-/* PIN Code Request Reply */
-#define HCIC_PARAM_SIZE_PIN_CODE_REQ_REPLY 23
-
-#define HCI_PIN_CODE_REPLY_BD_ADDR_OFF 0
-#define HCI_PIN_CODE_REPLY_PIN_LEN_OFF 6
-#define HCI_PIN_CODE_REPLY_PIN_CODE_OFF 7
-/* PIN Code Request Reply */
-
-/* Link Key Request Neg Reply */
-#define HCIC_PARAM_SIZE_PIN_CODE_NEG_REPLY 6
-
-#define HCI_PIN_CODE_NEG_REP_BD_ADR_OFF 0
-/* Link Key Request Neg Reply */
-
-/* Change Connection Type */
-#define HCIC_PARAM_SIZE_CHANGE_CONN_TYPE 4
-
-#define HCI_CHNG_PKT_TYPE_HANDLE_OFF 0
-#define HCI_CHNG_PKT_TYPE_PKT_TYPE_OFF 2
-/* Change Connection Type */
-
-#define HCIC_PARAM_SIZE_CMD_HANDLE 2
-
-#define HCI_CMD_HANDLE_HANDLE_OFF 0
-
-/* Set Connection Encryption */
-#define HCIC_PARAM_SIZE_SET_CONN_ENCRYPT 3
-
-#define HCI_SET_ENCRYPT_HANDLE_OFF 0
-#define HCI_SET_ENCRYPT_ENABLE_OFF 2
-/* Set Connection Encryption */
-
-/* Remote Name Request */
-#define HCIC_PARAM_SIZE_RMT_NAME_REQ 10
-
-#define HCI_RMT_NAME_BD_ADDR_OFF 0
-#define HCI_RMT_NAME_REP_MODE_OFF 6
-#define HCI_RMT_NAME_PAGE_SCAN_MODE_OFF 7
-#define HCI_RMT_NAME_CLK_OFF_OFF 8
-/* Remote Name Request */
-
-/* Remote Name Request Cancel */
-#define HCIC_PARAM_SIZE_RMT_NAME_REQ_CANCEL 6
-
-#define HCI_RMT_NAME_CANCEL_BD_ADDR_OFF 0
-/* Remote Name Request Cancel */
-
-/* Remote Extended Features */
-#define HCIC_PARAM_SIZE_RMT_EXT_FEATURES 3
-
-#define HCI_RMT_EXT_FEATURES_HANDLE_OFF 0
-#define HCI_RMT_EXT_FEATURES_PAGE_NUM_OFF 2
-/* Remote Extended Features */
-
-#define HCIC_PARAM_SIZE_SETUP_ESCO 17
-
-#define HCI_SETUP_ESCO_HANDLE_OFF 0
-#define HCI_SETUP_ESCO_TX_BW_OFF 2
-#define HCI_SETUP_ESCO_RX_BW_OFF 6
-#define HCI_SETUP_ESCO_MAX_LAT_OFF 10
-#define HCI_SETUP_ESCO_VOICE_OFF 12
-#define HCI_SETUP_ESCO_RETRAN_EFF_OFF 14
-#define HCI_SETUP_ESCO_PKT_TYPES_OFF 15
-
-#define HCIC_PARAM_SIZE_ACCEPT_ESCO 21
-
-#define HCI_ACCEPT_ESCO_BDADDR_OFF 0
-#define HCI_ACCEPT_ESCO_TX_BW_OFF 6
-#define HCI_ACCEPT_ESCO_RX_BW_OFF 10
-#define HCI_ACCEPT_ESCO_MAX_LAT_OFF 14
-#define HCI_ACCEPT_ESCO_VOICE_OFF 16
-#define HCI_ACCEPT_ESCO_RETRAN_EFF_OFF 18
-#define HCI_ACCEPT_ESCO_PKT_TYPES_OFF 19
-
-#define HCIC_PARAM_SIZE_REJECT_ESCO 7
-
-#define HCI_REJECT_ESCO_BDADDR_OFF 0
-#define HCI_REJECT_ESCO_REASON_OFF 6
-
-/* Hold Mode */
-#define HCIC_PARAM_SIZE_HOLD_MODE 6
-
-#define HCI_HOLD_MODE_HANDLE_OFF 0
-#define HCI_HOLD_MODE_MAX_PER_OFF 2
-#define HCI_HOLD_MODE_MIN_PER_OFF 4
-/* Hold Mode */
-
-/* Sniff Mode */
-#define HCIC_PARAM_SIZE_SNIFF_MODE 10
-
-#define HCI_SNIFF_MODE_HANDLE_OFF 0
-#define HCI_SNIFF_MODE_MAX_PER_OFF 2
-#define HCI_SNIFF_MODE_MIN_PER_OFF 4
-#define HCI_SNIFF_MODE_ATTEMPT_OFF 6
-#define HCI_SNIFF_MODE_TIMEOUT_OFF 8
-/* Sniff Mode */
-
-/* Park Mode */
-#define HCIC_PARAM_SIZE_PARK_MODE 6
-
-#define HCI_PARK_MODE_HANDLE_OFF 0
-#define HCI_PARK_MODE_MAX_PER_OFF 2
-#define HCI_PARK_MODE_MIN_PER_OFF 4
-/* Park Mode */
-
-/* QoS Setup */
-#define HCIC_PARAM_SIZE_QOS_SETUP 20
-
-#define HCI_QOS_HANDLE_OFF 0
-#define HCI_QOS_FLAGS_OFF 2
-#define HCI_QOS_SERVICE_TYPE_OFF 3
-#define HCI_QOS_TOKEN_RATE_OFF 4
-#define HCI_QOS_PEAK_BANDWIDTH_OFF 8
-#define HCI_QOS_LATENCY_OFF 12
-#define HCI_QOS_DELAY_VAR_OFF 16
-/* QoS Setup */
-
-#define HCIC_PARAM_SIZE_SWITCH_ROLE 7
-
-#define HCI_SWITCH_BD_ADDR_OFF 0
-#define HCI_SWITCH_ROLE_OFF 6
-/* Switch Role Request */
-
-/* Write Policy Settings */
-#define HCIC_PARAM_SIZE_WRITE_POLICY_SET 4
-
-#define HCI_WRITE_POLICY_HANDLE_OFF 0
-#define HCI_WRITE_POLICY_SETTINGS_OFF 2
-/* Write Policy Settings */
-
-/* Write Default Policy Settings */
-#define HCIC_PARAM_SIZE_WRITE_DEF_POLICY_SET 2
-
-#define HCI_WRITE_DEF_POLICY_SETTINGS_OFF 0
-/* Write Default Policy Settings */
-
-#define HCIC_PARAM_SIZE_SNIFF_SUB_RATE 8
-
-#define HCI_SNIFF_SUB_RATE_HANDLE_OFF 0
-#define HCI_SNIFF_SUB_RATE_MAX_LAT_OFF 2
-#define HCI_SNIFF_SUB_RATE_MIN_REM_LAT_OFF 4
-#define HCI_SNIFF_SUB_RATE_MIN_LOC_LAT_OFF 6
-/* Sniff Subrating */
-
-/* Extended Inquiry Response */
-#define HCIC_PARAM_SIZE_EXT_INQ_RESP 241
-
-#define HCIC_EXT_INQ_RESP_FEC_OFF 0
-#define HCIC_EXT_INQ_RESP_RESPONSE 1
-/* IO Capabilities Response */
-#define HCIC_PARAM_SIZE_IO_CAP_RESP 9
-
-#define HCI_IO_CAP_BD_ADDR_OFF 0
-#define HCI_IO_CAPABILITY_OFF 6
-#define HCI_IO_CAP_OOB_DATA_OFF 7
-#define HCI_IO_CAP_AUTH_REQ_OFF 8
-
-/* IO Capabilities Req Neg Reply */
-#define HCIC_PARAM_SIZE_IO_CAP_NEG_REPLY 7
-
-#define HCI_IO_CAP_NR_BD_ADDR_OFF 0
-#define HCI_IO_CAP_NR_ERR_CODE 6
-
-/* Read Local OOB Data */
-#define HCIC_PARAM_SIZE_R_LOCAL_OOB 0
-
-#define HCIC_PARAM_SIZE_UCONF_REPLY 6
-
-#define HCI_USER_CONF_BD_ADDR_OFF 0
-
-#define HCIC_PARAM_SIZE_U_PKEY_REPLY 10
-
-#define HCI_USER_PASSKEY_BD_ADDR_OFF 0
-#define HCI_USER_PASSKEY_VALUE_OFF 6
-
-#define HCIC_PARAM_SIZE_U_PKEY_NEG_REPLY 6
-
-#define HCI_USER_PASSKEY_NEG_BD_ADDR_OFF 0
-
-/* Remote OOB Data Request Reply */
-#define HCIC_PARAM_SIZE_REM_OOB_REPLY 38
-
-#define HCI_REM_OOB_DATA_BD_ADDR_OFF 0
-#define HCI_REM_OOB_DATA_C_OFF 6
-#define HCI_REM_OOB_DATA_R_OFF 22
-
-/* Remote OOB Data Request Negative Reply */
-#define HCIC_PARAM_SIZE_REM_OOB_NEG_REPLY 6
-
-#define HCI_REM_OOB_DATA_NEG_BD_ADDR_OFF 0
-
-/* Read Tx Power Level */
-#define HCIC_PARAM_SIZE_R_TX_POWER 0
-
-/* Read Default Erroneous Data Reporting */
-#define HCIC_PARAM_SIZE_R_ERR_DATA_RPT 0
-
-#define HCIC_PARAM_SIZE_ENHANCED_FLUSH 3
-
-#define HCIC_PARAM_SIZE_SEND_KEYPRESS_NOTIF 7
-
-#define HCI_SEND_KEYPRESS_NOTIF_BD_ADDR_OFF 0
-#define HCI_SEND_KEYPRESS_NOTIF_NOTIF_OFF 6
-
-/**** end of Simple Pairing Commands ****/
-
-#define HCIC_PARAM_SIZE_SET_EVT_FILTER 9
-
-#define HCI_FILT_COND_FILT_TYPE_OFF 0
-#define HCI_FILT_COND_COND_TYPE_OFF 1
-#define HCI_FILT_COND_FILT_OFF 2
-/* Set Event Filter */
-
-/* Delete Stored Key */
-#define HCIC_PARAM_SIZE_DELETE_STORED_KEY 7
-
-#define HCI_DELETE_KEY_BD_ADDR_OFF 0
-#define HCI_DELETE_KEY_ALL_FLAG_OFF 6
-/* Delete Stored Key */
-
-/* Change Local Name */
-#define HCIC_PARAM_SIZE_CHANGE_NAME BD_NAME_LEN
-
-#define HCI_CHANGE_NAME_NAME_OFF 0
-/* Change Local Name */
-
-#define HCIC_PARAM_SIZE_READ_CMD 0
-
-#define HCIC_PARAM_SIZE_WRITE_PARAM1 1
-
-#define HCIC_WRITE_PARAM1_PARAM_OFF 0
-
-#define HCIC_PARAM_SIZE_WRITE_PARAM2 2
-
-#define HCIC_WRITE_PARAM2_PARAM_OFF 0
-
-#define HCIC_PARAM_SIZE_WRITE_PARAM3 3
-
-#define HCIC_WRITE_PARAM3_PARAM_OFF 0
-
-#define HCIC_PARAM_SIZE_SET_AFH_CHANNELS 10
-
-#define HCIC_PARAM_SIZE_ENH_SET_ESCO_CONN 59
-#define HCIC_PARAM_SIZE_ENH_ACC_ESCO_CONN 63
-
-#define HCIC_PARAM_SIZE_WRITE_PAGESCAN_CFG 4
-
-#define HCI_SCAN_CFG_INTERVAL_OFF 0
-#define HCI_SCAN_CFG_WINDOW_OFF 2
-/* Write Page Scan Activity */
-
-/* Write Inquiry Scan Activity */
-#define HCIC_PARAM_SIZE_WRITE_INQSCAN_CFG 4
-
-#define HCI_SCAN_CFG_INTERVAL_OFF 0
-#define HCI_SCAN_CFG_WINDOW_OFF 2
-/* Write Inquiry Scan Activity */
-
-/* Host Controller to Host flow control */
-#define HCI_HOST_FLOW_CTRL_OFF 0
-#define HCI_HOST_FLOW_CTRL_ACL_ON 1
-#define HCI_HOST_FLOW_CTRL_SCO_ON 2
-#define HCI_HOST_FLOW_CTRL_BOTH_ON 3
-
-#define HCIC_PARAM_SIZE_WRITE_AUTOMATIC_FLUSH_TIMEOUT 4
-
-#define HCI_FLUSH_TOUT_HANDLE_OFF 0
-#define HCI_FLUSH_TOUT_TOUT_OFF 2
-
-#define HCIC_PARAM_SIZE_READ_TX_POWER 3
-
-#define HCI_READ_TX_POWER_HANDLE_OFF 0
-#define HCI_READ_TX_POWER_TYPE_OFF 2
-
-/* Read transmit power level parameter */
-#define HCI_READ_CURRENT 0x00
-#define HCI_READ_MAXIMUM 0x01
-
-#define HCIC_PARAM_SIZE_NUM_PKTS_DONE_SIZE sizeof(btmsg_hcic_num_pkts_done_t)
-
-#define MAX_DATA_HANDLES 10
-
-#define HCI_PKTS_DONE_NUM_HANDLES_OFF 0
-#define HCI_PKTS_DONE_HANDLE_OFF 1
-#define HCI_PKTS_DONE_NUM_PKTS_OFF 3
-
-#define HCIC_PARAM_SIZE_WRITE_LINK_SUPER_TOUT 4
-
-#define HCI_LINK_SUPER_TOUT_HANDLE_OFF 0
-#define HCI_LINK_SUPER_TOUT_TOUT_OFF 2
-/* Write Link Supervision Timeout */
-
-#define MAX_IAC_LAPS 0x40
-
-#define HCI_WRITE_IAC_LAP_NUM_OFF 0
-#define HCI_WRITE_IAC_LAP_LAP_OFF 1
-/* Write Current IAC LAP */
-
-/*******************************************************************************
- * BLE Commands
- * Note: "local_controller_id" is for transport, not counted in HCI
- * message size
- ******************************************************************************/
-#define HCIC_BLE_RAND_DI_SIZE 8
-#define HCIC_BLE_IRK_SIZE 16
-
-#define HCIC_PARAM_SIZE_SET_USED_FEAT_CMD 8
-#define HCIC_PARAM_SIZE_WRITE_RANDOM_ADDR_CMD 6
-#define HCIC_PARAM_SIZE_BLE_WRITE_ADV_PARAMS 15
-#define HCIC_PARAM_SIZE_BLE_WRITE_SCAN_RSP 31
-#define HCIC_PARAM_SIZE_WRITE_ADV_ENABLE 1
-#define HCIC_PARAM_SIZE_BLE_WRITE_SCAN_PARAM 7
-#define HCIC_PARAM_SIZE_BLE_WRITE_SCAN_ENABLE 2
-#define HCIC_PARAM_SIZE_BLE_CREATE_LL_CONN 25
-#define HCIC_PARAM_SIZE_BLE_CREATE_CONN_CANCEL 0
-#define HCIC_PARAM_SIZE_CLEAR_ACCEPTLIST 0
-#define HCIC_PARAM_SIZE_ADD_ACCEPTLIST 7
-#define HCIC_PARAM_SIZE_REMOVE_ACCEPTLIST 7
-#define HCIC_PARAM_SIZE_BLE_UPD_LL_CONN_PARAMS 14
-#define HCIC_PARAM_SIZE_SET_HOST_CHNL_CLASS 5
-#define HCIC_PARAM_SIZE_READ_CHNL_MAP 2
-#define HCIC_PARAM_SIZE_BLE_READ_REMOTE_FEAT 2
-#define HCIC_PARAM_SIZE_BLE_ENCRYPT 32
-#define HCIC_PARAM_SIZE_WRITE_LE_HOST_SUPPORTED 2
-
-#define HCIC_BLE_RAND_DI_SIZE 8
-#define HCIC_BLE_ENCRYPT_KEY_SIZE 16
-#define HCIC_PARAM_SIZE_BLE_START_ENC \
- (4 + HCIC_BLE_RAND_DI_SIZE + HCIC_BLE_ENCRYPT_KEY_SIZE)
-#define HCIC_PARAM_SIZE_LTK_REQ_REPLY (2 + HCIC_BLE_ENCRYPT_KEY_SIZE)
-#define HCIC_PARAM_SIZE_LTK_REQ_NEG_REPLY 2
-#define HCIC_BLE_CHNL_MAP_SIZE 5
-#define HCIC_PARAM_SIZE_BLE_WRITE_ADV_DATA 31
-
-#define HCIC_PARAM_SIZE_BLE_ADD_DEV_RESOLVING_LIST (7 + HCIC_BLE_IRK_SIZE * 2)
-#define HCIC_PARAM_SIZE_BLE_RM_DEV_RESOLVING_LIST 7
-#define HCIC_PARAM_SIZE_BLE_SET_PRIVACY_MODE 8
-#define HCIC_PARAM_SIZE_BLE_CLEAR_RESOLVING_LIST 0
-#define HCIC_PARAM_SIZE_BLE_READ_RESOLVING_LIST_SIZE 0
-#define HCIC_PARAM_SIZE_BLE_READ_RESOLVABLE_ADDR_PEER 7
-#define HCIC_PARAM_SIZE_BLE_READ_RESOLVABLE_ADDR_LOCAL 7
-#define HCIC_PARAM_SIZE_BLE_SET_ADDR_RESOLUTION_ENABLE 1
-#define HCIC_PARAM_SIZE_BLE_SET_RAND_PRIV_ADDR_TIMOUT 2
-
-#define HCIC_PARAM_SIZE_BLE_READ_PHY 2
-#define HCIC_PARAM_SIZE_BLE_SET_DEFAULT_PHY 3
-#define HCIC_PARAM_SIZE_BLE_SET_PHY 7
-#define HCIC_PARAM_SIZE_BLE_ENH_RX_TEST 3
-#define HCIC_PARAM_SIZE_BLE_ENH_TX_TEST 4
-
-#define HCIC_PARAM_SIZE_BLE_SET_DATA_LENGTH 6
-#define HCIC_PARAM_SIZE_BLE_WRITE_EXTENDED_SCAN_PARAM 11
-
-#define HCIC_PARAM_SIZE_BLE_RC_PARAM_REQ_REPLY 14
-#define HCIC_PARAM_SIZE_BLE_RC_PARAM_REQ_NEG_REPLY 3
-
-static void btsnd_hcic_inquiry(const LAP inq_lap, uint8_t duration,
- uint8_t response_cnt) {
+void btsnd_hcic_inquiry(const LAP inq_lap, uint8_t duration,
+ uint8_t response_cnt) {
BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
uint8_t* pp = (uint8_t*)(p + 1);
@@ -500,7 +52,7 @@ static void btsnd_hcic_inquiry(const LAP inq_lap, uint8_t duration,
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
-static void btsnd_hcic_inq_cancel(void) {
+void btsnd_hcic_inq_cancel(void) {
BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
uint8_t* pp = (uint8_t*)(p + 1);
@@ -551,21 +103,31 @@ void btsnd_hcic_create_conn(const RawAddress& dest, uint16_t packet_types,
BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
uint8_t* pp = (uint8_t*)(p + 1);
+#ifndef BT_10A
p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_CREATE_CONN;
+#else
+ p->len = HCIC_PREAMBLE_SIZE + HCIC_PARAM_SIZE_CREATE_CONN - 1;
+#endif
p->offset = 0;
UINT16_TO_STREAM(pp, HCI_CREATE_CONNECTION);
+#ifndef BT_10A
UINT8_TO_STREAM(pp, HCIC_PARAM_SIZE_CREATE_CONN);
+#else
+ UINT8_TO_STREAM(pp, (HCIC_PARAM_SIZE_CREATE_CONN - 1));
+#endif
BDADDR_TO_STREAM(pp, dest);
UINT16_TO_STREAM(pp, packet_types);
UINT8_TO_STREAM(pp, page_scan_rep_mode);
UINT8_TO_STREAM(pp, page_scan_mode);
UINT16_TO_STREAM(pp, clock_offset);
+#if !defined(BT_10A)
UINT8_TO_STREAM(pp, allow_switch);
+#endif
btm_acl_paging(p, dest);
}
-static void btsnd_hcic_disconnect(uint16_t handle, uint8_t reason) {
+void btsnd_hcic_disconnect(uint16_t handle, uint8_t reason) {
BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
uint8_t* pp = (uint8_t*)(p + 1);
@@ -1045,7 +607,7 @@ void btsnd_hcic_qos_setup(uint16_t handle, uint8_t flags, uint8_t service_type,
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
-static void btsnd_hcic_switch_role(const RawAddress& bd_addr, uint8_t role) {
+void btsnd_hcic_switch_role(const RawAddress& bd_addr, uint8_t role) {
BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
uint8_t* pp = (uint8_t*)(p + 1);
@@ -1393,6 +955,8 @@ void btsnd_hcic_write_cur_iac_lap(uint8_t num_cur_iac, LAP* const iac_lap) {
/******************************************
* Lisbon Features
******************************************/
+#if (BTM_SSR_INCLUDED == TRUE)
+
void btsnd_hcic_sniff_sub_rate(uint16_t handle, uint16_t max_lat,
uint16_t min_remote_lat,
uint16_t min_local_lat) {
@@ -1412,6 +976,7 @@ void btsnd_hcic_sniff_sub_rate(uint16_t handle, uint16_t max_lat,
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
+#endif /* BTM_SSR_INCLUDED */
/**** Extended Inquiry Response Commands ****/
void btsnd_hcic_write_ext_inquiry_response(void* buffer, uint8_t fec_req) {
@@ -1693,6 +1258,7 @@ void btsnd_hcic_send_keypress_notif(const RawAddress& bd_addr, uint8_t notif) {
/**** end of Simple Pairing Commands ****/
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
void btsnd_hcic_enhanced_flush(uint16_t handle, uint8_t packet_type) {
BT_HDR* p = (BT_HDR*)osi_malloc(HCI_CMD_BUF_SIZE);
uint8_t* pp = (uint8_t*)(p + 1);
@@ -1707,6 +1273,7 @@ void btsnd_hcic_enhanced_flush(uint16_t handle, uint8_t packet_type) {
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
+#endif
/*************************
* End of Lisbon Commands
@@ -1877,178 +1444,3 @@ void btsnd_hcic_vendor_spec_cmd(void* buffer, uint16_t opcode, uint8_t len,
btu_hcif_send_cmd(LOCAL_BR_EDR_CONTROLLER_ID, p);
}
-
-bluetooth::legacy::hci::Interface interface_ = {
- // LINK_CONTROL
- .StartInquiry = btsnd_hcic_inquiry, // OCF 0x0401
- .InquiryCancel = btsnd_hcic_inq_cancel, // OCF 0x0402
- .StartPeriodicInquiryMode = btsnd_hcic_per_inq_mode, // OCF 0x0403
- .ExitPeriodicInquiryMode = btsnd_hcic_exit_per_inq, // OCF 0x0404
- .CreateConnection = btsnd_hcic_create_conn, // OCF 0x0405
- .Disconnect = btsnd_hcic_disconnect, // OCF 0x0406
- // UNUSED OCF 0x0407 btsnd_hcic_add_SCO_conn
- .CreateConnectionCancel = btsnd_hcic_create_conn_cancel, // OCF 0x0408
- .AcceptConnectionRequest = btsnd_hcic_accept_conn, // OCF 0x0409
- .RejectConnectionRequest = btsnd_hcic_reject_conn, // OCF 0x040A
- .LinkKeyRequestReply = btsnd_hcic_link_key_req_reply, // OCF 0x040B
- .LinkKeyRequestNegativeReply =
- btsnd_hcic_link_key_neg_reply, // OCF 0x040C,
- .PinCodeRequestReply = btsnd_hcic_pin_code_req_reply, // OCF 0x040D,
- .PinCodeRequestNegativeReply =
- btsnd_hcic_pin_code_neg_reply, // OCF 0x040E,
- .ChangeConnectionPacketType = btsnd_hcic_change_conn_type, // OCF 0x040F,
- // UNUSED OCF 0x0410
- .AuthenticationRequested = btsnd_hcic_auth_request, // OCF 0x0411,
- // UNUSED OCF 0x0412
- .SetConnectionEncryption = btsnd_hcic_set_conn_encrypt, // OCF 0x0413,
- // UNUSED OCF 0x0414
- .ChangeConnectionLinkKey = nullptr, // OCF 0x0415,
- // UNUSED OCF 0x0416
- .CentralLinkKey = nullptr, // OCF 0x0417,
- // UNUSED OCF 0x0418
- .RemoteNameRequest = btsnd_hcic_rmt_name_req, // OCF 0x0419,
- .RemoteNameRequestCancel = btsnd_hcic_rmt_name_req_cancel, // OCF 0x041A,
- .ReadRemoteSupportedFeatures = btsnd_hcic_rmt_features_req, // OCF 0x041B,
- .ReadRemoteExtendedFeatures = btsnd_hcic_rmt_ext_features, // OCF 0x041C,
- .ReadRemoteVersionInformation = btsnd_hcic_rmt_ver_req, // OCF 0x041D,
- // UNUSED OCF 0x041E
- .ReadClockOffset = btsnd_hcic_read_rmt_clk_offset, // OCF 0x041F,
- .ReadLmpHandle = btsnd_hcic_read_lmp_handle, // OCF 0x0420,
- // UNUSED OCF 0x0420 - 0x0427
- .SetupSynchronousConnection = btsnd_hcic_setup_esco_conn, // OCF 0x0428,
- .AcceptSynchronousConnection = btsnd_hcic_accept_esco_conn, // OCF 0x0429,
- .RejectSynchronousConnection = btsnd_hcic_reject_esco_conn, // OCF 0x042A,
- .IoCapabilityRequestReply = btsnd_hcic_io_cap_req_reply, // OCF 0x042B,
- .UserConfirmationRequestReply = btsnd_hcic_user_conf_reply, // OCF 0x042C,
- .UserConfirmationRequestNegativeReply =
- btsnd_hcic_user_conf_reply, // OCF 0x042D,
- .UserPasskeyRequestReply = btsnd_hcic_user_passkey_reply, // OCF 0x042E,
- .UserPasskeyRequestNegativeReply =
- btsnd_hcic_user_passkey_neg_reply, // OCF 0x042F,
- .RemoteOobDataRequestReply = btsnd_hcic_rem_oob_reply, // OCF 0x0430,
- // UNUSED OCF 0x0431 - 0x0432
- .RemoteOobDataRequestNegativeReply =
- btsnd_hcic_rem_oob_neg_reply, // OCF 0x0433,
- .IoCapabilityRequestNegativeReply =
- btsnd_hcic_io_cap_req_neg_reply, // OCF 0x0434,
- // UNUSED OCF 0x0435 - 0x043C
- .EnhancedSetupSynchronousConnection =
- btsnd_hcic_enhanced_set_up_synchronous_connection, // OCF 0x043D,
- .EnhancedAcceptSynchronousConnection =
- btsnd_hcic_enhanced_accept_synchronous_connection, // OCF 0x043E,
- // UNUSED OCF 0x043F - 0x0444
- .RemoteOobExtendedDataRequestReply = nullptr, // OCF 0x0445,
-
- // LINK_POLICY
- .HoldMode = btsnd_hcic_hold_mode, // OCF 0x0801,
- // UNUSED OCF 0x0802
- .SniffMode = btsnd_hcic_sniff_mode, // OCF 0x0803,
- .ExitSniffMode = btsnd_hcic_exit_sniff_mode, // OCF 0x0804,
- // UNUSED OCF 0x0805 - 0x0806
- .QosSetup = btsnd_hcic_qos_setup, // OCF 0x0807,
- // UNUSED OCF 0x0808
- .RoleDiscovery = nullptr, // OCF 0x0809,
- // UNUSED OCF 0x080A
- .StartRoleSwitch = btsnd_hcic_switch_role, // OCF 0x080B,
- .ReadLinkPolicySettings = nullptr, // OCF 0x080C,
- .WriteLinkPolicySettings = btsnd_hcic_write_policy_set, // OCF 0x080D,
- .ReadDefaultLinkPolicySettings = nullptr, // OCF 0x080E,
- .WriteDefaultLinkPolicySettings =
- btsnd_hcic_write_def_policy_set, // OCF 0x080F,
- .FlowSpecification = nullptr, // OCF 0x0810,
- .SniffSubrating = btsnd_hcic_sniff_sub_rate, // OCF 0x0811,
-
- // CONTROLLER_AND_BASEBAND
- .SetEventMask = nullptr, // OCF 0x0C01,
- // UNUSED OCF 0x0C02
- .Reset = nullptr, // OCF 0x0C03,
- // UNUSED OCF 0x0C04
- .SetEventFilter = btsnd_hcic_set_event_filter, // OCF 0x0C05,
- // UNUSED OCF 0x0C06 = 0x0C07
- .Flush = nullptr, // OCF 0x0C08,
- .ReadPinType = nullptr, // OCF 0x0C09,
- .WritePinType = btsnd_hcic_write_pin_type, // OCF 0x0C0A,
- .CreateNewUnitKey = nullptr, // OCF 0x0C0B,
- // UNUSED OCF 0x0C0C
- .ReadStoredLinkKey = nullptr, // OCF 0x0C0D,
- // UNUSED OCF 0x0C0E - 0x0C10
- .WriteStoredLinkKey = nullptr, // OCF 0x0C11,
- .DeleteStoredLinkKey = btsnd_hcic_delete_stored_key, // OCF 0x0C12,
- .WriteLocalName = btsnd_hcic_change_name, // OCF 0x0C13,
- .ReadLocalName = btsnd_hcic_read_name, // OCF 0x0C14,
- .ReadConnectionAcceptTimeout = nullptr, // OCF 0x0C15,
- .WriteConnectionAcceptTimeout = btsnd_hcic_write_page_tout, // OCF 0x0C16,
- .ReadPageTimeout = nullptr, // OCF 0x0C17,
- .WritePageTimeout = nullptr, // OCF 0x0C18,
- .ReadScanEnable = nullptr, // OCF 0x0C19,
- .WriteScanEnable = btsnd_hcic_write_scan_enable, // OCF 0x0C1A,
- .ReadPageScanActivity = nullptr, // OCF 0x0C1B,
- .WritePageScanActivity = btsnd_hcic_write_pagescan_cfg, // OCF 0x0C1C,
- .ReadInquiryScanActivity = nullptr, // OCF 0x0C1D,
- .WriteInquiryScanActivity = btsnd_hcic_write_inqscan_cfg, // OCF 0x0C1E,
- .ReadAuthenticationEnable = nullptr, // OCF 0x0C1F,
- // UNUSED OCF 0x0C20 - 0x0C22
- .ReadClassOfDevice = nullptr, // OCF 0x0C23,
- .WriteClassOfDevice = btsnd_hcic_write_dev_class, // OCF 0x0C24,
- .ReadVoiceSetting = nullptr, // OCF 0x0C25,
- .WriteVoiceSetting = btsnd_hcic_write_voice_settings, // OCF 0x0C26,
- .ReadAutomaticFlushTimeout =
- btsnd_hcic_read_automatic_flush_timeout, // OCF 0x0C27,
- .WriteAutomaticFlushTimeout =
- btsnd_hcic_write_auto_flush_tout, // OCF 0x0C28,
- .ReadNumBroadcastRetransmits = nullptr, // OCF 0x0C29,
- .WriteNumBroadcastRetransmits = nullptr, // OCF 0x0C2A,
- .ReadHoldModeActivity = nullptr, // OCF 0x0C2B,
- .WriteHoldModeActivity = nullptr, // OCF 0x0C2C,
- .ReadTransmitPowerLevel = btsnd_hcic_read_tx_power, // OCF 0x0C2D,
- .ReadSynchronousFlowControlEnable = nullptr, // OCF 0x0C2E,
- .WriteSynchronousFlowControlEnable = nullptr, // OCF 0x0C2F,
- // UNUSED OCF 0x0C30
- .SetControllerToHostFlowControl = nullptr, // OCF 0x0C31,
- // UNUSED OCF 0x0C32
- .HostBufferSize = nullptr, // OCF 0x0C33,
- // UNUSED OCF 0x0C34
- .HostNumCompletedPackets = nullptr, // OCF 0x0C35,
- .ReadLinkSupervisionTimeout =
- btsnd_hcic_write_link_super_tout, // OCF 0x0C36,
- .WriteLinkSupervisionTimeout = nullptr, // OCF 0x0C37,
- .ReadNumberOfSupportedIac = nullptr, // OCF 0x0C38,
- .ReadCurrentIacLap = nullptr, // OCF 0x0C39,
- .WriteCurrentIacLap = btsnd_hcic_write_cur_iac_lap, // OCF 0x0C3A,
- .SetAfhHostChannelClassification = nullptr, // OCF 0x0C3F,
- .ReadInquiryScanType = nullptr, // OCF 0x0C42,
- .WriteInquiryScanType = btsnd_hcic_write_inqscan_type, // OCF 0x0C43,
- .ReadInquiryMode = nullptr, // OCF 0x0C44,
- .WriteInquiryMode = btsnd_hcic_write_inquiry_mode, // OCF 0x0C45,
- .ReadPageScanType = nullptr, // OCF 0x0C46,
- .WritePageScanType = btsnd_hcic_write_pagescan_type, // OCF 0x0C47,
- .ReadAfhChannelAssessmentMode = nullptr, // OCF 0x0C48,
- .WriteAfhChannelAssessmentMode = nullptr, // OCF 0x0C49,
- .ReadExtendedInquiryResponse = nullptr, // OCF 0x0C51,
- .WriteExtendedInquiryResponse =
- btsnd_hcic_write_ext_inquiry_response, // OCF 0x0C52,
- .RefreshEncryptionKey = nullptr, // OCF 0x0C53,
- .ReadSimplePairingMode = nullptr, // OCF 0x0C55,
- .WriteSimplePairingMode = nullptr, // OCF 0x0C56,
- .ReadLocalOobData = btsnd_hcic_read_local_oob_data, // OCF 0x0C57,
- .ReadInquiryResponseTransmitPowerLevel = nullptr, // OCF 0x0C58,
- .WriteInquiryTransmitPowerLevel = nullptr, // OCF 0x0C59,
- .EnhancedFlush = btsnd_hcic_enhanced_flush, // OCF 0x0C5F,
- .SendKeypressNotification = btsnd_hcic_send_keypress_notif, // OCF 0x0C60,
-
- // STATUS_PARAMETERS
- .ReadFailedContactCounter =
- btsnd_hcic_read_failed_contact_counter, // OCF 0x1401,
- .ResetFailedContactCounter = nullptr, // OCF 0x1402,
- .ReadLinkQuality = btsnd_hcic_get_link_quality, // OCF 0x1403,
- // UNUSED OCF 0x1404
- .ReadRssi = btsnd_hcic_read_rssi, // OCF 0x1405,
- .ReadAfhChannelMap = nullptr, // OCF 0x1406,
- .ReadClock = nullptr, // OCF 0x1407,
- .ReadEncryptionKeySize = nullptr, // OCF 0x1408,
-};
-
-const bluetooth::legacy::hci::Interface&
-bluetooth::legacy::hci::GetInterface() {
- return interface_;
-}
diff --git a/stack/hid/hid_conn.h b/stack/hid/hid_conn.h
index e92d4914f..46a2850f8 100644
--- a/stack/hid/hid_conn.h
+++ b/stack/hid/hid_conn.h
@@ -27,46 +27,31 @@
#include "osi/include/alarm.h"
-typedef enum : uint8_t {
- HID_CONN_STATE_UNUSED = 0,
- HID_CONN_STATE_CONNECTING_CTRL = 1,
- HID_CONN_STATE_CONNECTING_INTR = 2,
- HID_CONN_STATE_CONFIG = 3,
- HID_CONN_STATE_CONNECTED = 4,
- HID_CONN_STATE_DISCONNECTING = 5,
- HID_CONN_STATE_SECURITY = 6,
-} tHID_CONN_STATE;
-
/* Define the HID Connection Block
*/
typedef struct hid_conn {
- tHID_CONN_STATE conn_state;
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
+#define HID_CONN_STATE_UNUSED (0)
+#define HID_CONN_STATE_CONNECTING_CTRL (1)
+#define HID_CONN_STATE_CONNECTING_INTR (2)
+#define HID_CONN_STATE_CONFIG (3)
+#define HID_CONN_STATE_CONNECTED (4)
+#define HID_CONN_STATE_DISCONNECTING (5)
+#define HID_CONN_STATE_SECURITY (6)
- static inline std::string state_text(const tHID_CONN_STATE& state) {
- switch (state) {
- CASE_RETURN_TEXT(HID_CONN_STATE_UNUSED);
- CASE_RETURN_TEXT(HID_CONN_STATE_CONNECTING_CTRL);
- CASE_RETURN_TEXT(HID_CONN_STATE_CONNECTING_INTR);
- CASE_RETURN_TEXT(HID_CONN_STATE_CONFIG);
- CASE_RETURN_TEXT(HID_CONN_STATE_CONNECTED);
- CASE_RETURN_TEXT(HID_CONN_STATE_DISCONNECTING);
- CASE_RETURN_TEXT(HID_CONN_STATE_SECURITY);
- default:
- return std::string("UNKNOWN[%hhu]", state);
- }
- }
-#undef CASE_RETURN_TEXT
+ uint8_t conn_state;
#define HID_CONN_FLAGS_IS_ORIG (0x01)
+#define HID_CONN_FLAGS_HIS_CTRL_CFG_DONE (0x02)
+#define HID_CONN_FLAGS_MY_CTRL_CFG_DONE (0x04)
+#define HID_CONN_FLAGS_HIS_INTR_CFG_DONE (0x08)
+#define HID_CONN_FLAGS_MY_INTR_CFG_DONE (0x10)
+#define HID_CONN_FLAGS_ALL_CONFIGURED (0x1E) /* All the config done */
#define HID_CONN_FLAGS_CONGESTED (0x20)
#define HID_CONN_FLAGS_INACTIVE (0x40)
uint8_t conn_flags;
+ uint8_t ctrl_id;
uint16_t ctrl_cid;
uint16_t intr_cid;
uint16_t rem_mtu_size;
@@ -78,5 +63,6 @@ typedef struct hid_conn {
#define HID_NOSEC_CHN 2
#define HIDD_SEC_CHN 3
+#define HIDD_NOSEC_CHN 4
#endif
diff --git a/stack/hid/hidd_api.cc b/stack/hid/hidd_api.cc
index fe919baf9..cd40c2cc0 100644
--- a/stack/hid/hidd_api.cc
+++ b/stack/hid/hidd_api.cc
@@ -33,7 +33,6 @@
#include "hidd_api.h"
#include "hidd_int.h"
#include "hiddefs.h"
-#include "stack/btm/btm_sec.h"
tHID_DEV_CTB hd_cb;
@@ -126,6 +125,50 @@ tHID_STATUS HID_DevDeregister(void) {
return (HID_SUCCESS);
}
+tHID_STATUS HID_DevSetSecurityLevel(uint8_t sec_lvl) {
+ HIDD_TRACE_API("%s", __func__);
+
+ if (!BTM_SetSecurityLevel(FALSE, "", BTM_SEC_SERVICE_HIDD_SEC_CTRL, sec_lvl,
+ HID_PSM_CONTROL, BTM_SEC_PROTO_HID, HIDD_SEC_CHN)) {
+ HIDD_TRACE_ERROR("Security Registration 1 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ if (!BTM_SetSecurityLevel(TRUE, "", BTM_SEC_SERVICE_HIDD_SEC_CTRL, sec_lvl,
+ HID_PSM_CONTROL, BTM_SEC_PROTO_HID, HIDD_SEC_CHN)) {
+ HIDD_TRACE_ERROR("Security Registration 2 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ if (!BTM_SetSecurityLevel(FALSE, "", BTM_SEC_SERVICE_HIDD_NOSEC_CTRL,
+ BTM_SEC_NONE, HID_PSM_CONTROL, BTM_SEC_PROTO_HID,
+ HIDD_NOSEC_CHN)) {
+ HIDD_TRACE_ERROR("Security Registration 3 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ if (!BTM_SetSecurityLevel(TRUE, "", BTM_SEC_SERVICE_HIDD_NOSEC_CTRL,
+ BTM_SEC_NONE, HID_PSM_CONTROL, BTM_SEC_PROTO_HID,
+ HIDD_NOSEC_CHN)) {
+ HIDD_TRACE_ERROR("Security Registration 4 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ if (!BTM_SetSecurityLevel(TRUE, "", BTM_SEC_SERVICE_HIDD_INTR, BTM_SEC_NONE,
+ HID_PSM_INTERRUPT, BTM_SEC_PROTO_HID, 0)) {
+ HIDD_TRACE_ERROR("Security Registration 5 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ if (!BTM_SetSecurityLevel(FALSE, "", BTM_SEC_SERVICE_HIDD_INTR, BTM_SEC_NONE,
+ HID_PSM_INTERRUPT, BTM_SEC_PROTO_HID, 0)) {
+ HIDD_TRACE_ERROR("Security Registration 6 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ return (HID_SUCCESS);
+}
+
/*******************************************************************************
*
* Function HID_DevAddRecord
diff --git a/stack/hid/hidd_conn.cc b/stack/hid/hidd_conn.cc
index da6b46ddb..a239f7399 100644
--- a/stack/hid/hidd_conn.cc
+++ b/stack/hid/hidd_conn.cc
@@ -23,34 +23,50 @@
*
******************************************************************************/
-#include <cstdint>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
-#include "bta/include/bta_api.h"
-#include "btif/include/btif_hd.h"
-#include "osi/include/allocator.h"
-#include "stack/hid/hidd_int.h"
-#include "stack/include/bt_types.h"
-#include "types/raw_address.h"
+#include "bt_types.h"
+
+#include "l2c_api.h"
+#include "l2cdefs.h"
+
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
+
+#include "hiddefs.h"
+
+#include "bt_utils.h"
+#include "hidd_api.h"
+#include "hidd_int.h"
+
+#include "osi/include/osi.h"
static void hidd_l2cif_connect_ind(const RawAddress& bd_addr, uint16_t cid,
uint16_t psm, uint8_t id);
static void hidd_l2cif_connect_cfm(uint16_t cid, uint16_t result);
static void hidd_l2cif_config_ind(uint16_t cid, tL2CAP_CFG_INFO* p_cfg);
-static void hidd_l2cif_config_cfm(uint16_t cid, uint16_t result,
- tL2CAP_CFG_INFO* p_cfg);
+static void hidd_l2cif_config_cfm(uint16_t cid, tL2CAP_CFG_INFO* p_cfg);
static void hidd_l2cif_disconnect_ind(uint16_t cid, bool ack_needed);
-static void hidd_l2cif_disconnect(uint16_t cid);
+static void hidd_l2cif_disconnect_cfm(uint16_t cid, uint16_t result);
static void hidd_l2cif_data_ind(uint16_t cid, BT_HDR* p_msg);
static void hidd_l2cif_cong_ind(uint16_t cid, bool congested);
-static void hidd_on_l2cap_error(uint16_t lcid, uint16_t result);
+
static const tL2CAP_APPL_INFO dev_reg_info = {
- hidd_l2cif_connect_ind, hidd_l2cif_connect_cfm,
- hidd_l2cif_config_ind, hidd_l2cif_config_cfm,
- hidd_l2cif_disconnect_ind, hidd_l2cif_data_ind,
- hidd_l2cif_cong_ind, NULL,
- hidd_on_l2cap_error, NULL,
- NULL, NULL
-};
+ hidd_l2cif_connect_ind,
+ hidd_l2cif_connect_cfm,
+ NULL,
+ hidd_l2cif_config_ind,
+ hidd_l2cif_config_cfm,
+ hidd_l2cif_disconnect_ind,
+ hidd_l2cif_disconnect_cfm,
+ NULL,
+ hidd_l2cif_data_ind,
+ hidd_l2cif_cong_ind,
+ NULL,
+ NULL /* tL2CA_CREDITS_RECEIVED_CB */};
/*******************************************************************************
*
@@ -62,9 +78,13 @@ static const tL2CAP_APPL_INFO dev_reg_info = {
*
******************************************************************************/
static void hidd_check_config_done() {
- tHID_CONN* p_hcon = &hd_cb.device.conn;
+ tHID_CONN* p_hcon;
- if (p_hcon->conn_state == HID_CONN_STATE_CONFIG) {
+ p_hcon = &hd_cb.device.conn;
+
+ if (((p_hcon->conn_flags & HID_CONN_FLAGS_ALL_CONFIGURED) ==
+ HID_CONN_FLAGS_ALL_CONFIGURED) &&
+ (p_hcon->conn_state == HID_CONN_STATE_CONFIG)) {
p_hcon->conn_state = HID_CONN_STATE_CONNECTED;
hd_cb.device.state = HIDD_DEV_CONNECTED;
@@ -81,6 +101,73 @@ static void hidd_check_config_done() {
/*******************************************************************************
*
+ * Function hidh_sec_check_complete_term
+ *
+ * Description HID security check complete callback function.
+ *
+ * Returns Send L2CA_ConnectRsp OK if secutiry check succeed; otherwise
+ * send security block L2C connection response.
+ *
+ ******************************************************************************/
+static void hidd_sec_check_complete(UNUSED_ATTR const RawAddress* bd_addr,
+ UNUSED_ATTR tBT_TRANSPORT transport,
+ void* p_ref_data, uint8_t res) {
+ tHID_DEV_DEV_CTB* p_dev = (tHID_DEV_DEV_CTB*)p_ref_data;
+
+ if (res == BTM_SUCCESS && p_dev->conn.conn_state == HID_CONN_STATE_SECURITY) {
+ p_dev->conn.disc_reason = HID_SUCCESS;
+ p_dev->conn.conn_state = HID_CONN_STATE_CONNECTING_INTR;
+
+ L2CA_ConnectRsp(p_dev->addr, p_dev->conn.ctrl_id, p_dev->conn.ctrl_cid,
+ L2CAP_CONN_OK, L2CAP_CONN_OK);
+ L2CA_ConfigReq(p_dev->conn.ctrl_cid, &hd_cb.l2cap_cfg);
+ } else if (res != BTM_SUCCESS) {
+ HIDD_TRACE_WARNING("%s: connection rejected by security", __func__);
+
+ p_dev->conn.disc_reason = HID_ERR_AUTH_FAILED;
+ p_dev->conn.conn_state = HID_CONN_STATE_UNUSED;
+ L2CA_ConnectRsp(p_dev->addr, p_dev->conn.ctrl_id, p_dev->conn.ctrl_cid,
+ L2CAP_CONN_SECURITY_BLOCK, L2CAP_CONN_OK);
+ return;
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function hidd_sec_check_complete_orig
+ *
+ * Description HID security check complete callback function (device
+*originated)
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void hidd_sec_check_complete_orig(UNUSED_ATTR const RawAddress* bd_addr,
+ UNUSED_ATTR tBT_TRANSPORT transport,
+ void* p_ref_data, uint8_t res) {
+ tHID_DEV_DEV_CTB* p_dev = (tHID_DEV_DEV_CTB*)p_ref_data;
+
+ if (p_dev->conn.conn_state != HID_CONN_STATE_SECURITY) {
+ HIDD_TRACE_WARNING("%s: invalid state (%02x)", __func__,
+ p_dev->conn.conn_state);
+ return;
+ }
+
+ if (res == BTM_SUCCESS) {
+ HIDD_TRACE_EVENT("%s: security ok", __func__);
+ p_dev->conn.disc_reason = HID_SUCCESS;
+
+ p_dev->conn.conn_state = HID_CONN_STATE_CONFIG;
+ L2CA_ConfigReq(p_dev->conn.ctrl_cid, &hd_cb.l2cap_cfg);
+ } else {
+ HIDD_TRACE_WARNING("%s: security check failed (%02x)", __func__, res);
+ p_dev->conn.disc_reason = HID_ERR_AUTH_FAILED;
+ hidd_conn_disconnect();
+ }
+}
+
+/*******************************************************************************
+ *
* Function hidd_l2cif_connect_ind
*
* Description Handles incoming L2CAP connection (we act as server)
@@ -90,22 +177,22 @@ static void hidd_check_config_done() {
******************************************************************************/
static void hidd_l2cif_connect_ind(const RawAddress& bd_addr, uint16_t cid,
uint16_t psm, uint8_t id) {
+ tHID_CONN* p_hcon;
tHID_DEV_DEV_CTB* p_dev;
bool accept = TRUE; // accept by default
- HIDD_TRACE_EVENT("%s: psm=%04x cid=%04x", __func__, psm, cid);
+ HIDD_TRACE_EVENT("%s: psm=%04x cid=%04x id=%02x", __func__, psm, cid, id);
p_dev = &hd_cb.device;
if (!hd_cb.allow_incoming) {
HIDD_TRACE_WARNING("%s: incoming connections not allowed, rejecting",
__func__);
- L2CA_DisconnectReq(cid);
-
+ L2CA_ConnectRsp(bd_addr, id, cid, L2CAP_CONN_NO_RESOURCES, 0);
return;
}
- tHID_CONN* p_hcon = &hd_cb.device.conn;
+ p_hcon = &hd_cb.device.conn;
switch (psm) {
case HID_PSM_INTERRUPT:
@@ -139,7 +226,7 @@ static void hidd_l2cif_connect_ind(const RawAddress& bd_addr, uint16_t cid,
}
if (!accept) {
- L2CA_DisconnectReq(cid);
+ L2CA_ConnectRsp(bd_addr, id, cid, L2CAP_CONN_NO_RESOURCES, 0);
return;
}
@@ -153,25 +240,26 @@ static void hidd_l2cif_connect_ind(const RawAddress& bd_addr, uint16_t cid,
p_hcon->conn_flags = 0;
p_hcon->ctrl_cid = cid;
- p_hcon->disc_reason = HID_SUCCESS;
- p_hcon->conn_state = HID_CONN_STATE_CONNECTING_INTR;
+ p_hcon->ctrl_id = id;
+ p_hcon->disc_reason = HID_L2CAP_CONN_FAIL;
+
+ p_hcon->conn_state = HID_CONN_STATE_SECURITY;
+ if (btm_sec_mx_access_request(p_dev->addr, HID_PSM_CONTROL, FALSE,
+ BTM_SEC_PROTO_HID, HIDD_NOSEC_CHN,
+ &hidd_sec_check_complete,
+ p_dev) == BTM_CMD_STARTED) {
+ L2CA_ConnectRsp(bd_addr, id, cid, L2CAP_CONN_PENDING, L2CAP_CONN_OK);
+ }
+
return;
}
// for INTR we go directly to config state
p_hcon->conn_state = HID_CONN_STATE_CONFIG;
p_hcon->intr_cid = cid;
-}
-
-static void hidd_on_l2cap_error(uint16_t lcid, uint16_t result) {
- HIDD_TRACE_WARNING("%s: connection of config failed, now disconnect",
- __func__);
- hidd_conn_disconnect();
-
- // NOTE that the client doesn't care about error code
- hd_cb.callback(hd_cb.device.addr, HID_DHOST_EVT_CLOSE,
- HID_L2CAP_CONN_FAIL | (uint32_t)result, NULL);
+ L2CA_ConnectRsp(bd_addr, id, cid, L2CAP_CONN_OK, L2CAP_CONN_OK);
+ L2CA_ConfigReq(cid, &hd_cb.l2cap_intr_cfg);
}
/*******************************************************************************
@@ -184,6 +272,7 @@ static void hidd_on_l2cap_error(uint16_t lcid, uint16_t result) {
*
******************************************************************************/
static void hidd_l2cif_connect_cfm(uint16_t cid, uint16_t result) {
+ tHID_DEV_DEV_CTB* p_dev = &hd_cb.device;
tHID_CONN* p_hcon = &hd_cb.device.conn;
HIDD_TRACE_EVENT("%s: cid=%04x result=%d", __func__, cid, result);
@@ -203,16 +292,32 @@ static void hidd_l2cif_connect_cfm(uint16_t cid, uint16_t result) {
}
if (result != L2CAP_CONN_OK) {
- LOG(ERROR) << __func__ << ": invoked with non OK status";
+ HIDD_TRACE_WARNING("%s: connection failed, now disconnect", __func__);
+
+ if (cid == p_hcon->ctrl_cid)
+ p_hcon->ctrl_cid = 0;
+ else
+ p_hcon->intr_cid = 0;
+
+ hidd_conn_disconnect();
+
+ hd_cb.callback(hd_cb.device.addr, HID_DHOST_EVT_CLOSE,
+ HID_L2CAP_CONN_FAIL | (uint32_t)result, NULL);
return;
}
/* CTRL connect conf */
if (cid == p_hcon->ctrl_cid) {
- p_hcon->disc_reason = HID_SUCCESS;
- p_hcon->conn_state = HID_CONN_STATE_CONFIG;
+ p_hcon->conn_state = HID_CONN_STATE_SECURITY;
+ p_hcon->disc_reason =
+ HID_L2CAP_CONN_FAIL; /* in case disconnected before sec completed */
+
+ btm_sec_mx_access_request(p_dev->addr, HID_PSM_CONTROL, TRUE,
+ BTM_SEC_PROTO_HID, HIDD_SEC_CHN,
+ &hidd_sec_check_complete_orig, p_dev);
} else {
p_hcon->conn_state = HID_CONN_STATE_CONFIG;
+ L2CA_ConfigReq(cid, &hd_cb.l2cap_intr_cfg);
}
return;
@@ -228,9 +333,11 @@ static void hidd_l2cif_connect_cfm(uint16_t cid, uint16_t result) {
*
******************************************************************************/
static void hidd_l2cif_config_ind(uint16_t cid, tL2CAP_CFG_INFO* p_cfg) {
+ tHID_CONN* p_hcon;
+
HIDD_TRACE_EVENT("%s: cid=%04x", __func__, cid);
- tHID_CONN* p_hcon = &hd_cb.device.conn;
+ p_hcon = &hd_cb.device.conn;
if (p_hcon->ctrl_cid != cid && p_hcon->intr_cid != cid) {
HIDD_TRACE_WARNING("%s: unknown cid", __func__);
@@ -241,6 +348,45 @@ static void hidd_l2cif_config_ind(uint16_t cid, tL2CAP_CFG_INFO* p_cfg) {
p_hcon->rem_mtu_size = HID_DEV_MTU_SIZE;
else
p_hcon->rem_mtu_size = p_cfg->mtu;
+
+ // accept without changes
+ p_cfg->flush_to_present = FALSE;
+ p_cfg->mtu_present = FALSE;
+ p_cfg->result = L2CAP_CFG_OK;
+
+ if (cid == p_hcon->intr_cid && hd_cb.use_in_qos && !p_cfg->qos_present) {
+ p_cfg->qos_present = TRUE;
+ memcpy(&p_cfg->qos, &hd_cb.in_qos, sizeof(FLOW_SPEC));
+ }
+
+ L2CA_ConfigRsp(cid, p_cfg);
+
+ // update flags
+ if (cid == p_hcon->ctrl_cid) {
+ p_hcon->conn_flags |= HID_CONN_FLAGS_HIS_CTRL_CFG_DONE;
+
+ if ((p_hcon->conn_flags & HID_CONN_FLAGS_IS_ORIG) &&
+ (p_hcon->conn_flags & HID_CONN_FLAGS_MY_CTRL_CFG_DONE)) {
+ p_hcon->disc_reason = HID_L2CAP_CONN_FAIL;
+ if ((p_hcon->intr_cid =
+ L2CA_ConnectReq(HID_PSM_INTERRUPT, hd_cb.device.addr)) == 0) {
+ hidd_conn_disconnect();
+ p_hcon->conn_state = HID_CONN_STATE_UNUSED;
+
+ HIDD_TRACE_WARNING("%s: could not start L2CAP connection for INTR",
+ __func__);
+ hd_cb.callback(hd_cb.device.addr, HID_DHOST_EVT_CLOSE,
+ HID_ERR_L2CAP_FAILED, NULL);
+ return;
+ } else {
+ p_hcon->conn_state = HID_CONN_STATE_CONNECTING_INTR;
+ }
+ }
+ } else {
+ p_hcon->conn_flags |= HID_CONN_FLAGS_HIS_INTR_CFG_DONE;
+ }
+
+ hidd_check_config_done();
}
/*******************************************************************************
@@ -252,27 +398,61 @@ static void hidd_l2cif_config_ind(uint16_t cid, tL2CAP_CFG_INFO* p_cfg) {
* Returns void
*
******************************************************************************/
-static void hidd_l2cif_config_cfm(uint16_t cid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
- hidd_l2cif_config_ind(cid, p_cfg);
+static void hidd_l2cif_config_cfm(uint16_t cid, tL2CAP_CFG_INFO* p_cfg) {
+ tHID_CONN* p_hcon;
+ uint32_t reason;
+ HIDD_TRACE_EVENT("%s: cid=%04x pcfg->result=%d", __func__, cid,
+ p_cfg->result);
- HIDD_TRACE_EVENT("%s: cid=%04x", __func__, cid);
-
- tHID_CONN* p_hcon = &hd_cb.device.conn;
+ p_hcon = &hd_cb.device.conn;
if (p_hcon->ctrl_cid != cid && p_hcon->intr_cid != cid) {
HIDD_TRACE_WARNING("%s: unknown cid", __func__);
return;
}
+ if (p_hcon->intr_cid == cid &&
+ p_cfg->result == L2CAP_CFG_UNACCEPTABLE_PARAMS && p_cfg->qos_present) {
+ tL2CAP_CFG_INFO new_qos;
+
+ // QoS parameters not accepted for intr, try again with host proposal
+
+ memcpy(&new_qos, &hd_cb.l2cap_intr_cfg, sizeof(new_qos));
+ memcpy(&new_qos.qos, &p_cfg->qos, sizeof(FLOW_SPEC));
+ new_qos.qos_present = TRUE;
+
+ HIDD_TRACE_WARNING("%s: config failed, retry", __func__);
+
+ L2CA_ConfigReq(cid, &new_qos);
+ return;
+ } else if (p_hcon->intr_cid == cid &&
+ p_cfg->result == L2CAP_CFG_UNKNOWN_OPTIONS) {
+ // QoS not understood by remote device, try configuring without QoS
+
+ HIDD_TRACE_WARNING("%s: config failed, retry without QoS", __func__);
+
+ L2CA_ConfigReq(cid, &hd_cb.l2cap_cfg);
+ return;
+ } else if (p_cfg->result != L2CAP_CFG_OK) {
+ HIDD_TRACE_WARNING("%s: config failed, disconnecting", __func__);
+
+ hidd_conn_disconnect();
+ reason = HID_L2CAP_CFG_FAIL | (uint32_t)p_cfg->result;
+
+ hd_cb.callback(hd_cb.device.addr, HID_DHOST_EVT_CLOSE, reason, NULL);
+ return;
+ }
+
// update flags
if (cid == p_hcon->ctrl_cid) {
- if (p_hcon->conn_flags & HID_CONN_FLAGS_IS_ORIG) {
+ p_hcon->conn_flags |= HID_CONN_FLAGS_MY_CTRL_CFG_DONE;
+
+ if ((p_hcon->conn_flags & HID_CONN_FLAGS_IS_ORIG) &&
+ (p_hcon->conn_flags & HID_CONN_FLAGS_HIS_CTRL_CFG_DONE)) {
p_hcon->disc_reason = HID_L2CAP_CONN_FAIL;
if ((p_hcon->intr_cid =
- L2CA_ConnectReq2(HID_PSM_INTERRUPT, hd_cb.device.addr,
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT)) == 0) {
+ L2CA_ConnectReq(HID_PSM_INTERRUPT, hd_cb.device.addr)) == 0) {
hidd_conn_disconnect();
p_hcon->conn_state = HID_CONN_STATE_UNUSED;
@@ -285,6 +465,8 @@ static void hidd_l2cif_config_cfm(uint16_t cid, uint16_t initiator,
p_hcon->conn_state = HID_CONN_STATE_CONNECTING_INTR;
}
}
+ } else {
+ p_hcon->conn_flags |= HID_CONN_FLAGS_MY_INTR_CFG_DONE;
}
hidd_check_config_done();
@@ -300,10 +482,11 @@ static void hidd_l2cif_config_cfm(uint16_t cid, uint16_t initiator,
*
******************************************************************************/
static void hidd_l2cif_disconnect_ind(uint16_t cid, bool ack_needed) {
+ tHID_CONN* p_hcon;
HIDD_TRACE_EVENT("%s: cid=%04x ack_needed=%d", __func__, cid, ack_needed);
- tHID_CONN* p_hcon = &hd_cb.device.conn;
+ p_hcon = &hd_cb.device.conn;
if (p_hcon->conn_state == HID_CONN_STATE_UNUSED ||
(p_hcon->ctrl_cid != cid && p_hcon->intr_cid != cid)) {
@@ -311,6 +494,8 @@ static void hidd_l2cif_disconnect_ind(uint16_t cid, bool ack_needed) {
return;
}
+ if (ack_needed) L2CA_DisconnectRsp(cid);
+
p_hcon->conn_state = HID_CONN_STATE_DISCONNECTING;
if (cid == p_hcon->ctrl_cid)
@@ -335,13 +520,21 @@ static void hidd_l2cif_disconnect_ind(uint16_t cid, bool ack_needed) {
}
}
-static void hidd_l2cif_disconnect(uint16_t cid) {
- L2CA_DisconnectReq(cid);
-
+/*******************************************************************************
+ *
+ * Function hidd_l2cif_disconnect_cfm
+ *
+ * Description Handles L2CAP disconection response
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void hidd_l2cif_disconnect_cfm(uint16_t cid, uint16_t result) {
+ tHID_CONN* p_hcon;
- HIDD_TRACE_EVENT("%s: cid=%04x", __func__, cid);
+ HIDD_TRACE_EVENT("%s: cid=%04x result=%d", __func__, cid, result);
- tHID_CONN* p_hcon = &hd_cb.device.conn;
+ p_hcon = &hd_cb.device.conn;
if (p_hcon->conn_state == HID_CONN_STATE_UNUSED ||
(p_hcon->ctrl_cid != cid && p_hcon->intr_cid != cid)) {
@@ -385,10 +578,11 @@ static void hidd_l2cif_disconnect(uint16_t cid) {
*
******************************************************************************/
static void hidd_l2cif_cong_ind(uint16_t cid, bool congested) {
+ tHID_CONN* p_hcon;
HIDD_TRACE_EVENT("%s: cid=%04x congested=%d", __func__, cid, congested);
- tHID_CONN* p_hcon = &hd_cb.device.conn;
+ p_hcon = &hd_cb.device.conn;
if (p_hcon->conn_state == HID_CONN_STATE_UNUSED ||
(p_hcon->ctrl_cid != cid && p_hcon->intr_cid != cid)) {
@@ -413,6 +607,7 @@ static void hidd_l2cif_cong_ind(uint16_t cid, bool congested) {
*
******************************************************************************/
static void hidd_l2cif_data_ind(uint16_t cid, BT_HDR* p_msg) {
+ tHID_CONN* p_hcon;
uint8_t* p_data = (uint8_t*)(p_msg + 1) + p_msg->offset;
uint8_t msg_type, param;
bool err = FALSE;
@@ -425,7 +620,7 @@ static void hidd_l2cif_data_ind(uint16_t cid, BT_HDR* p_msg) {
return;
}
- tHID_CONN* p_hcon = &hd_cb.device.conn;
+ p_hcon = &hd_cb.device.conn;
if (p_hcon->conn_state == HID_CONN_STATE_UNUSED ||
(p_hcon->ctrl_cid != cid && p_hcon->intr_cid != cid)) {
@@ -558,20 +753,23 @@ tHID_STATUS hidd_conn_reg(void) {
hd_cb.l2cap_cfg.mtu_present = TRUE;
hd_cb.l2cap_cfg.mtu = HID_DEV_MTU_SIZE;
+ hd_cb.l2cap_cfg.flush_to_present = TRUE;
+ hd_cb.l2cap_cfg.flush_to = HID_DEV_FLUSH_TO;
+
memset(&hd_cb.l2cap_intr_cfg, 0, sizeof(tL2CAP_CFG_INFO));
hd_cb.l2cap_intr_cfg.mtu_present = TRUE;
hd_cb.l2cap_intr_cfg.mtu = HID_DEV_MTU_SIZE;
+ hd_cb.l2cap_intr_cfg.flush_to_present = TRUE;
+ hd_cb.l2cap_intr_cfg.flush_to = HID_DEV_FLUSH_TO;
- if (!L2CA_Register2(HID_PSM_CONTROL, dev_reg_info, false /* enable_snoop */,
- nullptr, HID_DEV_MTU_SIZE, 0,
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT)) {
+ if (!L2CA_Register(HID_PSM_CONTROL, (tL2CAP_APPL_INFO*)&dev_reg_info,
+ false /* enable_snoop */, nullptr)) {
HIDD_TRACE_ERROR("HID Control (device) registration failed");
return (HID_ERR_L2CAP_FAILED);
}
- if (!L2CA_Register2(HID_PSM_INTERRUPT, dev_reg_info, false /* enable_snoop */,
- nullptr, HID_DEV_MTU_SIZE, 0,
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT)) {
+ if (!L2CA_Register(HID_PSM_INTERRUPT, (tL2CAP_APPL_INFO*)&dev_reg_info,
+ false /* enable_snoop */, nullptr)) {
L2CA_Deregister(HID_PSM_CONTROL);
HIDD_TRACE_ERROR("HID Interrupt (device) registration failed");
return (HID_ERR_L2CAP_FAILED);
@@ -626,10 +824,11 @@ tHID_STATUS hidd_conn_initiate(void) {
p_dev->conn.conn_flags = HID_CONN_FLAGS_IS_ORIG;
+ BTM_SetOutService(p_dev->addr, BTM_SEC_SERVICE_HIDD_SEC_CTRL, HIDD_SEC_CHN);
+
/* Check if L2CAP started the connection process */
- if ((p_dev->conn.ctrl_cid =
- L2CA_ConnectReq2(HID_PSM_CONTROL, p_dev->addr,
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT)) == 0) {
+ if ((p_dev->conn.ctrl_cid = L2CA_ConnectReq(HID_PSM_CONTROL, p_dev->addr)) ==
+ 0) {
HIDD_TRACE_WARNING("%s: could not start L2CAP connection", __func__);
hd_cb.callback(hd_cb.device.addr, HID_DHOST_EVT_CLOSE, HID_ERR_L2CAP_FAILED,
NULL);
@@ -650,6 +849,7 @@ tHID_STATUS hidd_conn_initiate(void) {
*
******************************************************************************/
tHID_STATUS hidd_conn_disconnect(void) {
+ tHID_CONN* p_hcon;
HIDD_TRACE_API("%s", __func__);
@@ -659,7 +859,7 @@ tHID_STATUS hidd_conn_disconnect(void) {
hd_cb.pending_data = NULL;
}
- tHID_CONN* p_hcon = &hd_cb.device.conn;
+ p_hcon = &hd_cb.device.conn;
if ((p_hcon->ctrl_cid != 0) || (p_hcon->intr_cid != 0)) {
p_hcon->conn_state = HID_CONN_STATE_DISCONNECTING;
@@ -669,9 +869,9 @@ tHID_STATUS hidd_conn_disconnect(void) {
L2CA_SetIdleTimeoutByBdAddr(hd_cb.device.addr, 0, BT_TRANSPORT_BR_EDR);
if (p_hcon->intr_cid) {
- hidd_l2cif_disconnect(p_hcon->intr_cid);
+ L2CA_DisconnectReq(p_hcon->intr_cid);
} else if (p_hcon->ctrl_cid) {
- hidd_l2cif_disconnect(p_hcon->ctrl_cid);
+ L2CA_DisconnectReq(p_hcon->ctrl_cid);
}
} else {
HIDD_TRACE_WARNING("%s: already disconnected", __func__);
@@ -693,6 +893,7 @@ tHID_STATUS hidd_conn_disconnect(void) {
tHID_STATUS hidd_conn_send_data(uint8_t channel, uint8_t msg_type,
uint8_t param, uint8_t data, uint16_t len,
uint8_t* p_data) {
+ tHID_CONN* p_hcon;
BT_HDR* p_buf;
uint8_t* p_out;
uint16_t cid;
@@ -701,7 +902,7 @@ tHID_STATUS hidd_conn_send_data(uint8_t channel, uint8_t msg_type,
HIDD_TRACE_VERBOSE("%s: channel(%d), msg_type(%d), len(%d)", __func__,
channel, msg_type, len);
- tHID_CONN* p_hcon = &hd_cb.device.conn;
+ p_hcon = &hd_cb.device.conn;
if (p_hcon->conn_flags & HID_CONN_FLAGS_CONGESTED) {
return HID_ERR_CONGESTED;
diff --git a/stack/hid/hidd_int.h b/stack/hid/hidd_int.h
index 400b76923..0981dcc13 100644
--- a/stack/hid/hidd_int.h
+++ b/stack/hid/hidd_int.h
@@ -26,12 +26,9 @@
#ifndef HIDD_INT_H
#define HIDD_INT_H
-#include <cstdint>
-
-#include "stack/hid/hid_conn.h"
-#include "stack/include/hidd_api.h"
-#include "stack/include/l2c_api.h" // tL2CAP_CFG_INFO && FLOW_SPEC
-#include "types/raw_address.h"
+#include "hid_conn.h"
+#include "hidd_api.h"
+#include "l2c_api.h"
enum { HIDD_DEV_NO_CONN, HIDD_DEV_CONNECTED };
diff --git a/stack/hid/hidh_api.cc b/stack/hid/hidh_api.cc
index 49ee92831..de62385e7 100644
--- a/stack/hid/hidh_api.cc
+++ b/stack/hid/hidh_api.cc
@@ -29,18 +29,17 @@
#include "bt_common.h"
#include "bt_types.h"
#include "btm_api.h"
+#include "btm_int.h"
#include "btu.h"
#include "hiddefs.h"
#include "hidh_api.h"
#include "hidh_int.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_sec.h"
using bluetooth::Uuid;
tHID_HOST_CTB hh_cb;
-static void hidh_search_callback(tSDP_RESULT sdp_result);
+static void hidh_search_callback(uint16_t sdp_result);
/*******************************************************************************
*
@@ -88,7 +87,7 @@ void hidh_get_str_attr(tSDP_DISC_REC* p_rec, uint16_t attr_id, uint16_t max_len,
str[0] = '\0';
}
-static void hidh_search_callback(tSDP_RESULT sdp_result) {
+static void hidh_search_callback(uint16_t sdp_result) {
tSDP_DISCOVERY_DB* p_db = hh_cb.p_sdp_db;
tSDP_DISC_REC* p_rec;
tSDP_DISC_ATTR *p_attr, *p_subattr1, *p_subattr2, *p_repdesc;
@@ -461,3 +460,96 @@ tHID_STATUS HID_HostCloseDev(uint8_t dev_handle) {
hh_cb.devices[dev_handle].conn_tries = HID_HOST_MAX_CONN_RETRY + 1;
return hidh_conn_disconnect(dev_handle);
}
+
+tHID_STATUS HID_HostSetSecurityLevel(const char serv_name[], uint8_t sec_lvl) {
+ if (!BTM_SetSecurityLevel(false, serv_name, BTM_SEC_SERVICE_HIDH_SEC_CTRL,
+ sec_lvl, HID_PSM_CONTROL, BTM_SEC_PROTO_HID,
+ HID_SEC_CHN)) {
+ HIDH_TRACE_ERROR("Security Registration 1 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ if (!BTM_SetSecurityLevel(true, serv_name, BTM_SEC_SERVICE_HIDH_SEC_CTRL,
+ sec_lvl, HID_PSM_CONTROL, BTM_SEC_PROTO_HID,
+ HID_SEC_CHN)) {
+ HIDH_TRACE_ERROR("Security Registration 2 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ if (!BTM_SetSecurityLevel(false, serv_name, BTM_SEC_SERVICE_HIDH_NOSEC_CTRL,
+ BTM_SEC_NONE, HID_PSM_CONTROL, BTM_SEC_PROTO_HID,
+ HID_NOSEC_CHN)) {
+ HIDH_TRACE_ERROR("Security Registration 3 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ if (!BTM_SetSecurityLevel(true, serv_name, BTM_SEC_SERVICE_HIDH_NOSEC_CTRL,
+ BTM_SEC_NONE, HID_PSM_CONTROL, BTM_SEC_PROTO_HID,
+ HID_NOSEC_CHN)) {
+ HIDH_TRACE_ERROR("Security Registration 4 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ if (!BTM_SetSecurityLevel(true, serv_name, BTM_SEC_SERVICE_HIDH_INTR,
+ BTM_SEC_NONE, HID_PSM_INTERRUPT, BTM_SEC_PROTO_HID,
+ 0)) {
+ HIDH_TRACE_ERROR("Security Registration 5 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ if (!BTM_SetSecurityLevel(false, serv_name, BTM_SEC_SERVICE_HIDH_INTR,
+ BTM_SEC_NONE, HID_PSM_INTERRUPT, BTM_SEC_PROTO_HID,
+ 0)) {
+ HIDH_TRACE_ERROR("Security Registration 6 failed");
+ return (HID_ERR_NO_RESOURCES);
+ }
+
+ return (HID_SUCCESS);
+}
+
+/******************************************************************************
+ *
+ * Function hid_known_hid_device
+ *
+ * Description check if this device is of type HID Device
+ *
+ * Returns true if device is HID Device else false
+ *
+ ******************************************************************************/
+bool hid_known_hid_device(const RawAddress& bd_addr) {
+ uint8_t i;
+ tBTM_INQ_INFO* p_inq_info = BTM_InqDbRead(bd_addr);
+
+ if (!hh_cb.reg_flag) return false;
+
+ /* First check for class of device , if Inq DB has information about this
+ * device*/
+ if (p_inq_info != NULL) {
+ /* Check if remote major device class is of type BTM_COD_MAJOR_PERIPHERAL */
+ if ((p_inq_info->results.dev_class[1] & BTM_COD_MAJOR_CLASS_MASK) ==
+ BTM_COD_MAJOR_PERIPHERAL) {
+ HIDH_TRACE_DEBUG(
+ "hid_known_hid_device:dev found in InqDB & COD matches HID dev");
+ return true;
+ }
+ } else {
+ /* Look for this device in security device DB */
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(bd_addr);
+ if ((p_dev_rec != NULL) &&
+ ((p_dev_rec->dev_class[1] & BTM_COD_MAJOR_CLASS_MASK) ==
+ BTM_COD_MAJOR_PERIPHERAL)) {
+ HIDH_TRACE_DEBUG(
+ "hid_known_hid_device:dev found in SecDevDB & COD matches HID dev");
+ return true;
+ }
+ }
+
+ /* Find an entry for this device in hh_cb.devices array */
+ for (i = 0; i < HID_HOST_MAX_DEVICES; i++) {
+ if ((hh_cb.devices[i].in_use) && bd_addr == hh_cb.devices[i].addr)
+ return true;
+ }
+ /* Check if this device is marked as HID Device in IOP Dev */
+ HIDH_TRACE_DEBUG("hid_known_hid_device:remote is not HID device");
+ return false;
+}
diff --git a/stack/hid/hidh_conn.cc b/stack/hid/hidh_conn.cc
index 87ded1c07..944d8595d 100644
--- a/stack/hid/hidh_conn.cc
+++ b/stack/hid/hidh_conn.cc
@@ -22,7 +22,8 @@
*
******************************************************************************/
-#include <base/strings/stringprintf.h>
+#include <stdio.h>
+#include <stdlib.h>
#include <string.h>
#include "bt_common.h"
@@ -31,22 +32,18 @@
#include "l2c_api.h"
#include "l2cdefs.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
+
#include "hiddefs.h"
+#include "bt_utils.h"
#include "hidh_api.h"
#include "hidh_int.h"
-#include "bta/include/bta_api.h"
-#include "osi/include/log.h"
+#include "log/log.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/btm_api.h" // BTM_LogHistory
-
-namespace {
-constexpr char kBtmLogTag[] = "HIDH";
-constexpr uint8_t kHID_HOST_MAX_DEVICES = HID_HOST_MAX_DEVICES;
-}
static uint8_t find_conn_by_cid(uint16_t cid);
static void hidh_conn_retry(uint8_t dhandle);
@@ -59,29 +56,25 @@ static void hidh_l2cif_connect_ind(const RawAddress& bd_addr,
uint8_t l2cap_id);
static void hidh_l2cif_connect_cfm(uint16_t l2cap_cid, uint16_t result);
static void hidh_l2cif_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg);
-static void hidh_l2cif_config_cfm(uint16_t l2cap_cid, uint16_t result,
- tL2CAP_CFG_INFO* p_cfg);
+static void hidh_l2cif_config_cfm(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg);
static void hidh_l2cif_disconnect_ind(uint16_t l2cap_cid, bool ack_needed);
static void hidh_l2cif_data_ind(uint16_t l2cap_cid, BT_HDR* p_msg);
-static void hidh_l2cif_disconnect(uint16_t l2cap_cid);
+static void hidh_l2cif_disconnect_cfm(uint16_t l2cap_cid, uint16_t result);
static void hidh_l2cif_cong_ind(uint16_t l2cap_cid, bool congested);
-static void hidh_on_l2cap_error(uint16_t l2cap_cid, uint16_t result);
static const tL2CAP_APPL_INFO hst_reg_info = {
- .pL2CA_ConnectInd_Cb = hidh_l2cif_connect_ind,
- .pL2CA_ConnectCfm_Cb = hidh_l2cif_connect_cfm,
- .pL2CA_ConfigInd_Cb = hidh_l2cif_config_ind,
- .pL2CA_ConfigCfm_Cb = hidh_l2cif_config_cfm,
- .pL2CA_DisconnectInd_Cb = hidh_l2cif_disconnect_ind,
- .pL2CA_DataInd_Cb = hidh_l2cif_data_ind,
- .pL2CA_CongestionStatus_Cb = hidh_l2cif_cong_ind,
- .pL2CA_TxComplete_Cb = nullptr,
- .pL2CA_Error_Cb = hidh_on_l2cap_error,
- .pL2CA_CreditBasedConnectInd_Cb = nullptr,
- .pL2CA_CreditBasedConnectCfm_Cb = nullptr,
- .pL2CA_CreditBasedReconfigCompleted_Cb = nullptr,
-};
-static void hidh_try_repage(uint8_t dhandle);
+ hidh_l2cif_connect_ind,
+ hidh_l2cif_connect_cfm,
+ NULL,
+ hidh_l2cif_config_ind,
+ hidh_l2cif_config_cfm,
+ hidh_l2cif_disconnect_ind,
+ hidh_l2cif_disconnect_cfm,
+ NULL,
+ hidh_l2cif_data_ind,
+ hidh_l2cif_cong_ind,
+ NULL, /* tL2CA_TX_COMPLETE_CB */
+ NULL /* tL2CA_CREDITS_RECEIVED_CB */};
/*******************************************************************************
*
@@ -100,23 +93,23 @@ tHID_STATUS hidh_conn_reg(void) {
hh_cb.l2cap_cfg.mtu_present = true;
hh_cb.l2cap_cfg.mtu = HID_HOST_MTU;
+ hh_cb.l2cap_cfg.flush_to_present = true;
+ hh_cb.l2cap_cfg.flush_to = HID_HOST_FLUSH_TO;
/* Now, register with L2CAP */
- if (!L2CA_Register2(HID_PSM_CONTROL, hst_reg_info, false /* enable_snoop */,
- nullptr, HID_HOST_MTU, 0,
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT)) {
+ if (!L2CA_Register(HID_PSM_CONTROL, (tL2CAP_APPL_INFO*)&hst_reg_info,
+ false /* enable_snoop */, nullptr)) {
HIDH_TRACE_ERROR("HID-Host Control Registration failed");
return (HID_ERR_L2CAP_FAILED);
}
- if (!L2CA_Register2(HID_PSM_INTERRUPT, hst_reg_info, false /* enable_snoop */,
- nullptr, HID_HOST_MTU, 0,
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT)) {
+ if (!L2CA_Register(HID_PSM_INTERRUPT, (tL2CAP_APPL_INFO*)&hst_reg_info,
+ false /* enable_snoop */, nullptr)) {
L2CA_Deregister(HID_PSM_CONTROL);
HIDH_TRACE_ERROR("HID-Host Interrupt Registration failed");
return (HID_ERR_L2CAP_FAILED);
}
- for (xx = 0; xx < kHID_HOST_MAX_DEVICES; xx++) {
+ for (xx = 0; xx < HID_HOST_MAX_DEVICES; xx++) {
hh_cb.devices[xx].in_use = false;
hh_cb.devices[xx].conn.conn_state = HID_CONN_STATE_UNUSED;
}
@@ -136,6 +129,8 @@ tHID_STATUS hidh_conn_reg(void) {
tHID_STATUS hidh_conn_disconnect(uint8_t dhandle) {
tHID_CONN* p_hcon = &hh_cb.devices[dhandle].conn;
+ HIDH_TRACE_EVENT("HID-Host disconnect");
+
if ((p_hcon->ctrl_cid != 0) || (p_hcon->intr_cid != 0)) {
p_hcon->conn_state = HID_CONN_STATE_DISCONNECTING;
@@ -145,16 +140,54 @@ tHID_STATUS hidh_conn_disconnect(uint8_t dhandle) {
BT_TRANSPORT_BR_EDR);
/* Disconnect both interrupt and control channels */
if (p_hcon->intr_cid)
- hidh_l2cif_disconnect(p_hcon->intr_cid);
+ L2CA_DisconnectReq(p_hcon->intr_cid);
else if (p_hcon->ctrl_cid)
- hidh_l2cif_disconnect(p_hcon->ctrl_cid);
-
- BTM_LogHistory(kBtmLogTag, hh_cb.devices[dhandle].addr, "Disconnecting",
- "local initiated");
+ L2CA_DisconnectReq(p_hcon->ctrl_cid);
} else {
p_hcon->conn_state = HID_CONN_STATE_UNUSED;
}
- return HID_SUCCESS;
+
+ return (HID_SUCCESS);
+}
+
+/*******************************************************************************
+ *
+ * Function hidh_sec_check_complete_term
+ *
+ * Description HID security check complete callback function.
+ *
+ * Returns Send L2CA_ConnectRsp OK if secutiry check succeed; otherwise
+ * send security block L2C connection response.
+ *
+ ******************************************************************************/
+void hidh_sec_check_complete_term(UNUSED_ATTR const RawAddress* bd_addr,
+ UNUSED_ATTR tBT_TRANSPORT transport,
+ void* p_ref_data, uint8_t res) {
+ tHID_HOST_DEV_CTB* p_dev = (tHID_HOST_DEV_CTB*)p_ref_data;
+
+ if (res == BTM_SUCCESS && p_dev->conn.conn_state == HID_CONN_STATE_SECURITY) {
+ p_dev->conn.disc_reason = HID_SUCCESS; /* Authentication passed. Reset
+ disc_reason (from
+ HID_ERR_AUTH_FAILED) */
+
+ p_dev->conn.conn_state = HID_CONN_STATE_CONNECTING_INTR;
+
+ /* Send response to the L2CAP layer. */
+ L2CA_ConnectRsp(p_dev->addr, p_dev->conn.ctrl_id, p_dev->conn.ctrl_cid,
+ L2CAP_CONN_OK, L2CAP_CONN_OK);
+
+ /* Send a Configuration Request. */
+ L2CA_ConfigReq(p_dev->conn.ctrl_cid, &hh_cb.l2cap_cfg);
+
+ }
+ /* security check fail */
+ else if (res != BTM_SUCCESS) {
+ p_dev->conn.disc_reason =
+ HID_ERR_AUTH_FAILED; /* Save reason for disconnecting */
+ p_dev->conn.conn_state = HID_CONN_STATE_UNUSED;
+ L2CA_ConnectRsp(p_dev->addr, p_dev->conn.ctrl_id, p_dev->conn.ctrl_cid,
+ L2CAP_CONN_SECURITY_BLOCK, L2CAP_CONN_OK);
+ }
}
/*******************************************************************************
@@ -171,25 +204,22 @@ tHID_STATUS hidh_conn_disconnect(uint8_t dhandle) {
static void hidh_l2cif_connect_ind(const RawAddress& bd_addr,
uint16_t l2cap_cid, uint16_t psm,
uint8_t l2cap_id) {
+ tHID_CONN* p_hcon;
bool bAccept = true;
- uint8_t i = kHID_HOST_MAX_DEVICES;
+ uint8_t i = HID_HOST_MAX_DEVICES;
+ tHID_HOST_DEV_CTB* p_dev;
HIDH_TRACE_EVENT("HID-Host Rcvd L2CAP conn ind, PSM: 0x%04x CID 0x%x", psm,
l2cap_cid);
/* always add incoming connection device into HID database by default */
if (HID_HostAddDev(bd_addr, HID_SEC_REQUIRED, &i) != HID_SUCCESS) {
- L2CA_DisconnectReq(l2cap_cid);
+ L2CA_ConnectRsp(bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_SECURITY_BLOCK, 0);
return;
}
- tHID_CONN* p_hcon = &hh_cb.devices[i].conn;
-
- BTM_LogHistory(
- kBtmLogTag, hh_cb.devices[i].addr, "Connect request",
- base::StringPrintf("%s state:%s",
- (psm == HID_PSM_CONTROL) ? "control" : "interrupt",
- hid_conn::state_text(p_hcon->conn_state).c_str()));
+ p_hcon = &hh_cb.devices[i].conn;
+ p_dev = &hh_cb.devices[i];
/* Check we are in the correct state for this */
if (psm == HID_PSM_INTERRUPT) {
@@ -218,19 +248,28 @@ static void hidh_l2cif_connect_ind(const RawAddress& bd_addr,
}
if (!bAccept) {
- L2CA_DisconnectReq(l2cap_cid);
+ L2CA_ConnectRsp(bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_NO_RESOURCES, 0);
return;
}
if (psm == HID_PSM_CONTROL) {
p_hcon->conn_flags = 0;
p_hcon->ctrl_cid = l2cap_cid;
- p_hcon->disc_reason = HID_SUCCESS; /* Authentication passed. Reset
- disc_reason (from
- HID_ERR_AUTH_FAILED) */
- p_hcon->conn_state = HID_CONN_STATE_CONNECTING_INTR;
- BTM_LogHistory(kBtmLogTag, hh_cb.devices[i].addr, "Connecting",
- "waiting for interrupt channel");
+ p_hcon->ctrl_id = l2cap_id;
+ p_hcon->disc_reason = HID_L2CAP_CONN_FAIL; /* In case disconnection occurs
+ before security is completed,
+ then set CLOSE_EVT reason code
+ to 'connection failure' */
+
+ p_hcon->conn_state = HID_CONN_STATE_SECURITY;
+ if (btm_sec_mx_access_request(
+ p_dev->addr, HID_PSM_CONTROL, false, BTM_SEC_PROTO_HID,
+ (p_dev->attr_mask & HID_SEC_REQUIRED) ? HID_SEC_CHN : HID_NOSEC_CHN,
+ &hidh_sec_check_complete_term, p_dev) == BTM_CMD_STARTED) {
+ L2CA_ConnectRsp(bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_PENDING,
+ L2CAP_CONN_OK);
+ }
+
return;
}
@@ -238,12 +277,18 @@ static void hidh_l2cif_connect_ind(const RawAddress& bd_addr,
p_hcon->conn_state = HID_CONN_STATE_CONFIG;
p_hcon->intr_cid = l2cap_cid;
+ /* Send response to the L2CAP layer. */
+ L2CA_ConnectRsp(bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_OK, L2CAP_CONN_OK);
+
+ /* Send a Configuration Request. */
+ L2CA_ConfigReq(l2cap_cid, &hh_cb.l2cap_cfg);
+
HIDH_TRACE_EVENT(
"HID-Host Rcvd L2CAP conn ind, sent config req, PSM: 0x%04x CID 0x%x",
psm, l2cap_cid);
}
-static void hidh_process_repage_timer_timeout(void* data) {
+void hidh_process_repage_timer_timeout(void* data) {
uint8_t dhandle = PTR_TO_UINT(data);
hidh_try_repage(dhandle);
}
@@ -257,7 +302,7 @@ static void hidh_process_repage_timer_timeout(void* data) {
* Returns void
*
******************************************************************************/
-static void hidh_try_repage(uint8_t dhandle) {
+void hidh_try_repage(uint8_t dhandle) {
tHID_HOST_DEV_CTB* device;
hidh_conn_initiate(dhandle);
@@ -269,34 +314,51 @@ static void hidh_try_repage(uint8_t dhandle) {
device->conn_tries, NULL);
}
-static void hidh_on_l2cap_error(uint16_t l2cap_cid, uint16_t result) {
- auto dhandle = find_conn_by_cid(l2cap_cid);
- if (dhandle == kHID_HOST_MAX_DEVICES) {
- LOG_WARN("Received error for unknown device cid:0x%04x reason:%s",
- l2cap_cid,
- hci_reason_code_text(to_hci_reason_code(result)).c_str());
- return;
- }
+/*******************************************************************************
+ *
+ * Function hidh_sec_check_complete_orig
+ *
+ * Description This function checks to see if security procedures are being
+ * carried out or not..
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void hidh_sec_check_complete_orig(UNUSED_ATTR const RawAddress* bd_addr,
+ UNUSED_ATTR tBT_TRANSPORT transport,
+ void* p_ref_data, uint8_t res) {
+ tHID_HOST_DEV_CTB* p_dev = (tHID_HOST_DEV_CTB*)p_ref_data;
+ uint8_t dhandle;
+
+ // TODO(armansito): This kind of math to determine a device handle is way
+ // too dirty and unnecessary. Why can't |p_dev| store it's handle?
+ dhandle = (PTR_TO_UINT(p_dev) - PTR_TO_UINT(&(hh_cb.devices[0]))) /
+ sizeof(tHID_HOST_DEV_CTB);
+ if (res == BTM_SUCCESS && p_dev->conn.conn_state == HID_CONN_STATE_SECURITY) {
+ HIDH_TRACE_EVENT("HID-Host Originator security pass.");
+ p_dev->conn.disc_reason = HID_SUCCESS; /* Authentication passed. Reset
+ disc_reason (from
+ HID_ERR_AUTH_FAILED) */
- hidh_conn_disconnect(dhandle);
+ /* Transition to the next appropriate state, configuration */
+ p_dev->conn.conn_state = HID_CONN_STATE_CONFIG;
+ L2CA_ConfigReq(p_dev->conn.ctrl_cid, &hh_cb.l2cap_cfg);
+ HIDH_TRACE_EVENT("HID-Host Got Control conn cnf, sent cfg req, CID: 0x%x",
+ p_dev->conn.ctrl_cid);
+ }
- if (result != L2CAP_CFG_FAILED_NO_REASON) {
+ if (res != BTM_SUCCESS && p_dev->conn.conn_state == HID_CONN_STATE_SECURITY) {
#if (HID_HOST_MAX_CONN_RETRY > 0)
- if ((hh_cb.devices[dhandle].conn_tries <= HID_HOST_MAX_CONN_RETRY) &&
- (result == HCI_ERR_CONNECTION_TOUT || result == HCI_ERR_UNSPECIFIED ||
- result == HCI_ERR_PAGE_TIMEOUT)) {
- hidh_conn_retry(dhandle);
- } else
-#endif
- {
- uint32_t reason = HID_L2CAP_CONN_FAIL | (uint32_t)result;
- hh_cb.callback(dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE,
- reason, NULL);
+ if (res == BTM_DEVICE_TIMEOUT) {
+ if (p_dev->conn_tries <= HID_HOST_MAX_CONN_RETRY) {
+ hidh_conn_retry(dhandle);
+ return;
+ }
}
- } else {
- uint32_t reason = HID_L2CAP_CFG_FAIL | (uint32_t)result;
- hh_cb.callback(dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE,
- reason, NULL);
+#endif
+ p_dev->conn.disc_reason =
+ HID_ERR_AUTH_FAILED; /* Save reason for disconnecting */
+ hidh_conn_disconnect(dhandle);
}
}
@@ -314,12 +376,13 @@ static void hidh_on_l2cap_error(uint16_t l2cap_cid, uint16_t result) {
static void hidh_l2cif_connect_cfm(uint16_t l2cap_cid, uint16_t result) {
uint8_t dhandle;
tHID_CONN* p_hcon = NULL;
+ uint32_t reason;
tHID_HOST_DEV_CTB* p_dev = NULL;
/* Find CCB based on CID, and verify we are in a state to accept this message
*/
dhandle = find_conn_by_cid(l2cap_cid);
- if (dhandle < kHID_HOST_MAX_DEVICES) {
+ if (dhandle < HID_HOST_MAX_DEVICES) {
p_dev = &hh_cb.devices[dhandle];
p_hcon = &hh_cb.devices[dhandle].conn;
}
@@ -336,27 +399,48 @@ static void hidh_l2cif_connect_cfm(uint16_t l2cap_cid, uint16_t result) {
}
if (result != L2CAP_CONN_OK) {
- // TODO: We need to provide the real HCI status if we want to retry.
- LOG(ERROR) << __func__ << ": invoked with non OK status";
+ if (l2cap_cid == p_hcon->ctrl_cid)
+ p_hcon->ctrl_cid = 0;
+ else
+ p_hcon->intr_cid = 0;
+
+ hidh_conn_disconnect(dhandle);
+
+#if (HID_HOST_MAX_CONN_RETRY > 0)
+ if ((hh_cb.devices[dhandle].conn_tries <= HID_HOST_MAX_CONN_RETRY) &&
+ (result == HCI_ERR_CONNECTION_TOUT || result == HCI_ERR_UNSPECIFIED ||
+ result == HCI_ERR_PAGE_TIMEOUT)) {
+ hidh_conn_retry(dhandle);
+ } else
+#endif
+ {
+ reason = HID_L2CAP_CONN_FAIL | (uint32_t)result;
+ hh_cb.callback(dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE,
+ reason, NULL);
+ }
return;
}
/* receive Control Channel connect confirmation */
if (l2cap_cid == p_hcon->ctrl_cid) {
/* check security requirement */
- p_hcon->disc_reason = HID_SUCCESS; /* Authentication passed. Reset
- disc_reason (from
- HID_ERR_AUTH_FAILED) */
-
- /* Transition to the next appropriate state, configuration */
- p_hcon->conn_state = HID_CONN_STATE_CONFIG;
+ p_hcon->conn_state = HID_CONN_STATE_SECURITY;
+ p_hcon->disc_reason = HID_L2CAP_CONN_FAIL; /* In case disconnection occurs
+ before security is completed,
+ then set CLOSE_EVT reason code
+ to "connection failure" */
+
+ btm_sec_mx_access_request(
+ p_dev->addr, HID_PSM_CONTROL, true, BTM_SEC_PROTO_HID,
+ (p_dev->attr_mask & HID_SEC_REQUIRED) ? HID_SEC_CHN : HID_NOSEC_CHN,
+ &hidh_sec_check_complete_orig, p_dev);
} else {
p_hcon->conn_state = HID_CONN_STATE_CONFIG;
+ /* Send a Configuration Request. */
+ L2CA_ConfigReq(l2cap_cid, &hh_cb.l2cap_cfg);
+ HIDH_TRACE_EVENT("HID-Host got Interrupt conn cnf, sent cfg req, CID: 0x%x",
+ l2cap_cid);
}
- BTM_LogHistory(
- kBtmLogTag, hh_cb.devices[dhandle].addr, "Configuring",
- base::StringPrintf("control:0x%04x interrupt:0x%04x state:%s",
- p_hcon->ctrl_cid, p_hcon->intr_cid,
- hid_conn::state_text(p_hcon->conn_state).c_str()));
+
return;
}
@@ -373,10 +457,11 @@ static void hidh_l2cif_connect_cfm(uint16_t l2cap_cid, uint16_t result) {
static void hidh_l2cif_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
uint8_t dhandle;
tHID_CONN* p_hcon = NULL;
+ uint32_t reason;
/* Find CCB based on CID */
dhandle = find_conn_by_cid(l2cap_cid);
- if (dhandle < kHID_HOST_MAX_DEVICES) {
+ if (dhandle < HID_HOST_MAX_DEVICES) {
p_hcon = &hh_cb.devices[dhandle].conn;
}
@@ -393,6 +478,55 @@ static void hidh_l2cif_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
p_hcon->rem_mtu_size = HID_HOST_MTU;
else
p_hcon->rem_mtu_size = p_cfg->mtu;
+
+ /* For now, always accept configuration from the other side */
+ p_cfg->flush_to_present = false;
+ p_cfg->mtu_present = false;
+ p_cfg->result = L2CAP_CFG_OK;
+
+ L2CA_ConfigRsp(l2cap_cid, p_cfg);
+
+ if (l2cap_cid == p_hcon->ctrl_cid) {
+ p_hcon->conn_flags |= HID_CONN_FLAGS_HIS_CTRL_CFG_DONE;
+ if ((p_hcon->conn_flags & HID_CONN_FLAGS_IS_ORIG) &&
+ (p_hcon->conn_flags & HID_CONN_FLAGS_MY_CTRL_CFG_DONE)) {
+ /* Connect interrupt channel */
+ p_hcon->disc_reason = HID_L2CAP_CONN_FAIL; /* Reset initial reason for
+ CLOSE_EVT: Connection
+ Attempt was made but failed
+ */
+ p_hcon->intr_cid =
+ L2CA_ConnectReq(HID_PSM_INTERRUPT, hh_cb.devices[dhandle].addr);
+ if (p_hcon->intr_cid == 0) {
+ HIDH_TRACE_WARNING("HID-Host INTR Originate failed");
+ reason = HID_L2CAP_REQ_FAIL;
+ p_hcon->conn_state = HID_CONN_STATE_UNUSED;
+ hidh_conn_disconnect(dhandle);
+ hh_cb.callback(dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE,
+ reason, NULL);
+ return;
+ } else {
+ /* Transition to the next appropriate state, waiting for connection
+ * confirm on interrupt channel. */
+ p_hcon->conn_state = HID_CONN_STATE_CONNECTING_INTR;
+ }
+ }
+ } else
+ p_hcon->conn_flags |= HID_CONN_FLAGS_HIS_INTR_CFG_DONE;
+
+ /* If all configuration is complete, change state and tell management we are
+ * up */
+ if (((p_hcon->conn_flags & HID_CONN_FLAGS_ALL_CONFIGURED) ==
+ HID_CONN_FLAGS_ALL_CONFIGURED) &&
+ (p_hcon->conn_state == HID_CONN_STATE_CONFIG)) {
+ p_hcon->conn_state = HID_CONN_STATE_CONNECTED;
+ /* Reset disconnect reason to success, as connection successful */
+ p_hcon->disc_reason = HID_SUCCESS;
+
+ hh_cb.devices[dhandle].state = HID_DEV_CONNECTED;
+ hh_cb.callback(dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_OPEN, 0,
+ NULL);
+ }
}
/*******************************************************************************
@@ -405,19 +539,17 @@ static void hidh_l2cif_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
* Returns void
*
******************************************************************************/
-static void hidh_l2cif_config_cfm(uint16_t l2cap_cid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
- hidh_l2cif_config_ind(l2cap_cid, p_cfg);
-
+static void hidh_l2cif_config_cfm(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
uint8_t dhandle;
tHID_CONN* p_hcon = NULL;
uint32_t reason;
- HIDH_TRACE_EVENT("HID-Host Rcvd cfg cfm, CID: 0x%x", l2cap_cid);
+ HIDH_TRACE_EVENT("HID-Host Rcvd cfg cfm, CID: 0x%x Result: %d", l2cap_cid,
+ p_cfg->result);
/* Find CCB based on CID */
dhandle = find_conn_by_cid(l2cap_cid);
- if (dhandle < kHID_HOST_MAX_DEVICES) p_hcon = &hh_cb.devices[dhandle].conn;
+ if (dhandle < HID_HOST_MAX_DEVICES) p_hcon = &hh_cb.devices[dhandle].conn;
if (p_hcon == NULL) {
HIDH_TRACE_WARNING("HID-Host Rcvd L2CAP cfg ind, unknown CID: 0x%x",
@@ -425,21 +557,30 @@ static void hidh_l2cif_config_cfm(uint16_t l2cap_cid, uint16_t initiator,
return;
}
+ /* If configuration failed, disconnect the channel(s) */
+ if (p_cfg->result != L2CAP_CFG_OK) {
+ hidh_conn_disconnect(dhandle);
+ reason = HID_L2CAP_CFG_FAIL | (uint32_t)p_cfg->result;
+ hh_cb.callback(dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE,
+ reason, NULL);
+ return;
+ }
+
if (l2cap_cid == p_hcon->ctrl_cid) {
- if (p_hcon->conn_flags & HID_CONN_FLAGS_IS_ORIG) {
+ p_hcon->conn_flags |= HID_CONN_FLAGS_MY_CTRL_CFG_DONE;
+ if ((p_hcon->conn_flags & HID_CONN_FLAGS_IS_ORIG) &&
+ (p_hcon->conn_flags & HID_CONN_FLAGS_HIS_CTRL_CFG_DONE)) {
/* Connect interrupt channel */
p_hcon->disc_reason = HID_L2CAP_CONN_FAIL; /* Reset initial reason for
CLOSE_EVT: Connection
Attempt was made but failed
*/
p_hcon->intr_cid =
- L2CA_ConnectReq2(HID_PSM_INTERRUPT, hh_cb.devices[dhandle].addr,
- BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT);
+ L2CA_ConnectReq(HID_PSM_INTERRUPT, hh_cb.devices[dhandle].addr);
if (p_hcon->intr_cid == 0) {
HIDH_TRACE_WARNING("HID-Host INTR Originate failed");
reason = HID_L2CAP_REQ_FAIL;
p_hcon->conn_state = HID_CONN_STATE_UNUSED;
- BTM_LogHistory(kBtmLogTag, hh_cb.devices[dhandle].addr, "Failed");
hidh_conn_disconnect(dhandle);
hh_cb.callback(dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE,
reason, NULL);
@@ -448,15 +589,16 @@ static void hidh_l2cif_config_cfm(uint16_t l2cap_cid, uint16_t initiator,
/* Transition to the next appropriate state, waiting for connection
* confirm on interrupt channel. */
p_hcon->conn_state = HID_CONN_STATE_CONNECTING_INTR;
- BTM_LogHistory(kBtmLogTag, hh_cb.devices[dhandle].addr, "Connecting",
- "interrupt channel");
}
}
- }
+ } else
+ p_hcon->conn_flags |= HID_CONN_FLAGS_MY_INTR_CFG_DONE;
/* If all configuration is complete, change state and tell management we are
* up */
- if (p_hcon->conn_state == HID_CONN_STATE_CONFIG) {
+ if (((p_hcon->conn_flags & HID_CONN_FLAGS_ALL_CONFIGURED) ==
+ HID_CONN_FLAGS_ALL_CONFIGURED) &&
+ (p_hcon->conn_state == HID_CONN_STATE_CONFIG)) {
p_hcon->conn_state = HID_CONN_STATE_CONNECTED;
/* Reset disconnect reason to success, as connection successful */
p_hcon->disc_reason = HID_SUCCESS;
@@ -464,11 +606,6 @@ static void hidh_l2cif_config_cfm(uint16_t l2cap_cid, uint16_t initiator,
hh_cb.devices[dhandle].state = HID_DEV_CONNECTED;
hh_cb.callback(dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_OPEN, 0,
NULL);
- BTM_LogHistory(
- kBtmLogTag, hh_cb.devices[dhandle].addr, "Connected",
- base::StringPrintf("control:0x%04x interrupt:0x%04x state:%s",
- p_hcon->ctrl_cid, p_hcon->intr_cid,
- hid_conn::state_text(p_hcon->conn_state).c_str()));
}
}
@@ -485,12 +622,12 @@ static void hidh_l2cif_config_cfm(uint16_t l2cap_cid, uint16_t initiator,
static void hidh_l2cif_disconnect_ind(uint16_t l2cap_cid, bool ack_needed) {
uint8_t dhandle;
tHID_CONN* p_hcon = NULL;
- tHCI_REASON disc_res = HCI_SUCCESS;
+ uint16_t disc_res = HCI_SUCCESS;
uint16_t hid_close_evt_reason;
/* Find CCB based on CID */
dhandle = find_conn_by_cid(l2cap_cid);
- if (dhandle < kHID_HOST_MAX_DEVICES) p_hcon = &hh_cb.devices[dhandle].conn;
+ if (dhandle < HID_HOST_MAX_DEVICES) p_hcon = &hh_cb.devices[dhandle].conn;
if (p_hcon == NULL) {
HIDH_TRACE_WARNING("HID-Host Rcvd L2CAP disc, unknown CID: 0x%x",
@@ -498,14 +635,11 @@ static void hidh_l2cif_disconnect_ind(uint16_t l2cap_cid, bool ack_needed) {
return;
}
+ if (ack_needed) L2CA_DisconnectRsp(l2cap_cid);
+
HIDH_TRACE_EVENT("HID-Host Rcvd L2CAP disc, CID: 0x%x", l2cap_cid);
p_hcon->conn_state = HID_CONN_STATE_DISCONNECTING;
- BTM_LogHistory(
- kBtmLogTag, hh_cb.devices[dhandle].addr, "Disconnecting",
- base::StringPrintf("%s channel", (l2cap_cid == p_hcon->ctrl_cid)
- ? "control"
- : "interrupt"));
if (l2cap_cid == p_hcon->ctrl_cid)
p_hcon->ctrl_cid = 0;
@@ -555,32 +689,45 @@ static void hidh_l2cif_disconnect_ind(uint16_t l2cap_cid, bool ack_needed) {
}
}
-static void hidh_l2cif_disconnect(uint16_t l2cap_cid) {
- L2CA_DisconnectReq(l2cap_cid);
+/*******************************************************************************
+ *
+ * Function hidh_l2cif_disconnect_cfm
+ *
+ * Description This function handles a disconnect confirm event from L2CAP.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void hidh_l2cif_disconnect_cfm(uint16_t l2cap_cid,
+ UNUSED_ATTR uint16_t result) {
+ uint8_t dhandle;
+ tHID_CONN* p_hcon = NULL;
/* Find CCB based on CID */
- const uint8_t dhandle = find_conn_by_cid(l2cap_cid);
- if (dhandle == kHID_HOST_MAX_DEVICES) {
- LOG_WARN("HID-Host Rcvd L2CAP disc cfm, unknown CID: 0x%x", l2cap_cid);
+ dhandle = find_conn_by_cid(l2cap_cid);
+ if (dhandle < HID_HOST_MAX_DEVICES) p_hcon = &hh_cb.devices[dhandle].conn;
+
+ if (p_hcon == NULL) {
+ HIDH_TRACE_WARNING("HID-Host Rcvd L2CAP disc cfm, unknown CID: 0x%x",
+ l2cap_cid);
return;
}
- tHID_CONN* p_hcon = &hh_cb.devices[dhandle].conn;
- if (l2cap_cid == p_hcon->ctrl_cid) {
+ HIDH_TRACE_EVENT("HID-Host Rcvd L2CAP disc cfm, CID: 0x%x", l2cap_cid);
+
+ if (l2cap_cid == p_hcon->ctrl_cid)
p_hcon->ctrl_cid = 0;
- } else {
+ else {
p_hcon->intr_cid = 0;
if (p_hcon->ctrl_cid) {
HIDH_TRACE_EVENT("HID-Host Initiating L2CAP Ctrl disconnection");
L2CA_DisconnectReq(p_hcon->ctrl_cid);
- p_hcon->ctrl_cid = 0;
}
}
if ((p_hcon->ctrl_cid == 0) && (p_hcon->intr_cid == 0)) {
hh_cb.devices[dhandle].state = HID_DEV_NO_CONN;
p_hcon->conn_state = HID_CONN_STATE_UNUSED;
- BTM_LogHistory(kBtmLogTag, hh_cb.devices[dhandle].addr, "Disconnected");
hh_cb.callback(dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE,
p_hcon->disc_reason, NULL);
}
@@ -601,7 +748,7 @@ static void hidh_l2cif_cong_ind(uint16_t l2cap_cid, bool congested) {
/* Find CCB based on CID */
dhandle = find_conn_by_cid(l2cap_cid);
- if (dhandle < kHID_HOST_MAX_DEVICES) p_hcon = &hh_cb.devices[dhandle].conn;
+ if (dhandle < HID_HOST_MAX_DEVICES) p_hcon = &hh_cb.devices[dhandle].conn;
if (p_hcon == NULL) {
HIDH_TRACE_WARNING(
@@ -646,7 +793,7 @@ static void hidh_l2cif_data_ind(uint16_t l2cap_cid, BT_HDR* p_msg) {
/* Find CCB based on CID */
dhandle = find_conn_by_cid(l2cap_cid);
- if (dhandle < kHID_HOST_MAX_DEVICES) p_hcon = &hh_cb.devices[dhandle].conn;
+ if (dhandle < HID_HOST_MAX_DEVICES) p_hcon = &hh_cb.devices[dhandle].conn;
if (p_hcon == NULL) {
HIDH_TRACE_WARNING("HID-Host Rcvd L2CAP data, unknown CID: 0x%x",
@@ -848,6 +995,9 @@ tHID_STATUS hidh_conn_snd_data(uint8_t dhandle, uint8_t trans_type,
*
******************************************************************************/
tHID_STATUS hidh_conn_initiate(uint8_t dhandle) {
+ uint8_t service_id = BTM_SEC_SERVICE_HIDH_NOSEC_CTRL;
+ uint32_t mx_chan_id = HID_NOSEC_CHN;
+
tHID_HOST_DEV_CTB* p_dev = &hh_cb.devices[dhandle];
if (p_dev->conn.conn_state != HID_CONN_STATE_UNUSED)
@@ -862,9 +1012,14 @@ tHID_STATUS hidh_conn_initiate(uint8_t dhandle) {
/* We are the originator of this connection */
p_dev->conn.conn_flags = HID_CONN_FLAGS_IS_ORIG;
+ if (p_dev->attr_mask & HID_SEC_REQUIRED) {
+ service_id = BTM_SEC_SERVICE_HIDH_SEC_CTRL;
+ mx_chan_id = HID_SEC_CHN;
+ }
+ BTM_SetOutService(p_dev->addr, service_id, mx_chan_id);
+
/* Check if L2CAP started the connection process */
- p_dev->conn.ctrl_cid = L2CA_ConnectReq2(
- HID_PSM_CONTROL, p_dev->addr, BTA_SEC_AUTHENTICATE | BTA_SEC_ENCRYPT);
+ p_dev->conn.ctrl_cid = L2CA_ConnectReq(HID_PSM_CONTROL, p_dev->addr);
if (p_dev->conn.ctrl_cid == 0) {
HIDH_TRACE_WARNING("HID-Host Originate failed");
hh_cb.callback(dhandle, hh_cb.devices[dhandle].addr, HID_HDEV_EVT_CLOSE,
@@ -873,8 +1028,6 @@ tHID_STATUS hidh_conn_initiate(uint8_t dhandle) {
/* Transition to the next appropriate state, waiting for connection confirm
* on control channel. */
p_dev->conn.conn_state = HID_CONN_STATE_CONNECTING_CTRL;
- BTM_LogHistory(kBtmLogTag, hh_cb.devices[dhandle].addr, "Connecting",
- "control channel");
}
return (HID_SUCCESS);
@@ -884,16 +1037,15 @@ tHID_STATUS hidh_conn_initiate(uint8_t dhandle) {
*
* Function find_conn_by_cid
*
- * Description This function finds a connection control block based on CID.
+ * Description This function finds a connection control block based on CID
*
- * Returns index of control block, or kHID_HOST_MAX_DEVICES if not
- * found.
+ * Returns address of control block, or NULL if not found
*
******************************************************************************/
static uint8_t find_conn_by_cid(uint16_t cid) {
uint8_t xx;
- for (xx = 0; xx < kHID_HOST_MAX_DEVICES; xx++) {
+ for (xx = 0; xx < HID_HOST_MAX_DEVICES; xx++) {
if ((hh_cb.devices[xx].in_use) &&
(hh_cb.devices[xx].conn.conn_state != HID_CONN_STATE_UNUSED) &&
((hh_cb.devices[xx].conn.ctrl_cid == cid) ||
diff --git a/stack/hid/hidh_int.h b/stack/hid/hidh_int.h
index fe9a3c861..8fa8ec8cb 100644
--- a/stack/hid/hidh_int.h
+++ b/stack/hid/hidh_int.h
@@ -25,12 +25,9 @@
#ifndef HIDH_INT_H
#define HIDH_INT_H
-#include <cstdint>
-
-#include "stack/hid/hid_conn.h"
-#include "stack/include/hidh_api.h"
-#include "stack/include/l2c_api.h" // tL2CAP_CFG_INFO
-#include "types/raw_address.h"
+#include "hid_conn.h"
+#include "hidh_api.h"
+#include "l2c_api.h"
enum { HID_DEV_NO_CONN, HID_DEV_CONNECTED };
@@ -41,6 +38,7 @@ typedef struct per_device_ctb {
reconn_initiate;
0x04- sdp_disable; */
uint8_t state; /* Device state if in HOST-KNOWN mode */
+ uint8_t conn_substate;
uint8_t conn_tries; /* Remembers the number of connection attempts while
CONNECTING */
@@ -69,6 +67,8 @@ extern tHID_STATUS hidh_conn_reg(void);
extern void hidh_conn_dereg(void);
extern tHID_STATUS hidh_conn_disconnect(uint8_t dhandle);
extern tHID_STATUS hidh_conn_initiate(uint8_t dhandle);
+extern void hidh_process_repage_timer_timeout(void* data);
+extern void hidh_try_repage(uint8_t dhandle);
/******************************************************************************
* Main Control Block
diff --git a/stack/include/a2dp_aac_encoder.h b/stack/include/a2dp_aac_encoder.h
index 5e909d8b4..143a5774a 100644
--- a/stack/include/a2dp_aac_encoder.h
+++ b/stack/include/a2dp_aac_encoder.h
@@ -21,29 +21,8 @@
#ifndef A2DP_AAC_ENCODER_H
#define A2DP_AAC_ENCODER_H
-#include "a2dp_aac_constants.h"
#include "a2dp_codec_api.h"
-// Is used in btav_a2dp_codec_config_t.codec_specific_1 when codec is AAC
-enum class AacEncoderBitrateMode : int64_t {
- // Variable bitrate mode unsupported when used in a codec report, and upper
- // layer can use this value as system default (keep current settings)
- AACENC_BR_MODE_CBR = A2DP_AAC_VARIABLE_BIT_RATE_DISABLED,
- // Constant bitrate mode when Variable bitrate mode is supported. This can
- // also be used to disable Variable bitrate mode by upper layer
- AACENC_BR_MODE_VBR_C = (A2DP_AAC_VARIABLE_BIT_RATE_ENABLED | 0x00),
- // Variable bitrate mode (very low bitrate for software encoding).
- AACENC_BR_MODE_VBR_1 = (A2DP_AAC_VARIABLE_BIT_RATE_ENABLED | 0x01),
- // Variable bitrate mode (low bitrate for software encoding).
- AACENC_BR_MODE_VBR_2 = (A2DP_AAC_VARIABLE_BIT_RATE_ENABLED | 0x02),
- // Variable bitrate mode (medium bitrate for software encoding).
- AACENC_BR_MODE_VBR_3 = (A2DP_AAC_VARIABLE_BIT_RATE_ENABLED | 0x03),
- // Variable bitrate mode (high bitrate for software encoding).
- AACENC_BR_MODE_VBR_4 = (A2DP_AAC_VARIABLE_BIT_RATE_ENABLED | 0x04),
- // Variable bitrate mode (very high bitrate for software encoding).
- AACENC_BR_MODE_VBR_5 = (A2DP_AAC_VARIABLE_BIT_RATE_ENABLED | 0x05),
-};
-
// Loads the A2DP AAC encoder.
// Return true on success, otherwise false.
bool A2DP_LoadEncoderAac(void);
diff --git a/stack/include/a2dp_sbc_constants.h b/stack/include/a2dp_sbc_constants.h
index 7426688f6..87b9eb981 100644
--- a/stack/include/a2dp_sbc_constants.h
+++ b/stack/include/a2dp_sbc_constants.h
@@ -61,7 +61,6 @@
#define A2DP_SBC_IE_MIN_BITPOOL 2
#define A2DP_SBC_IE_MAX_BITPOOL 250
-#define A2DP_SBC_BITPOOL_MIDDLE_QUALITY 35
/* for media payload header */
#define A2DP_SBC_HDR_F_MSK 0x80
diff --git a/stack/include/acl_api.h b/stack/include/acl_api.h
deleted file mode 100644
index b4829d860..000000000
--- a/stack/include/acl_api.h
+++ /dev/null
@@ -1,316 +0,0 @@
-/* Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/acl_api_types.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_status.h"
-#include "stack/include/hci_error_code.h"
-#include "types/raw_address.h"
-
-// Note: From stack/include/btm_api.h
-
-/*****************************************************************************
- * ACL CHANNEL MANAGEMENT FUNCTIONS
- ****************************************************************************/
-bool BTM_is_sniff_allowed_for(const RawAddress& peer_addr);
-
-void BTM_unblock_sniff_mode_for(const RawAddress& peer_addr);
-void BTM_block_sniff_mode_for(const RawAddress& peer_addr);
-void BTM_unblock_role_switch_for(const RawAddress& peer_addr);
-void BTM_block_role_switch_for(const RawAddress& peer_addr);
-
-void BTM_default_unblock_role_switch();
-void BTM_default_block_role_switch();
-
-void BTM_acl_after_controller_started(const controller_t* controller);
-
-/*******************************************************************************
- *
- * Function BTM_SetLinkSuperTout
- *
- * Description Create and send HCI "Write Link Supervision Timeout" command
- *
- * Returns BTM_CMD_STARTED if successfully initiated, otherwise error
- *
- ******************************************************************************/
-tBTM_STATUS BTM_SetLinkSuperTout(const RawAddress& remote_bda,
- uint16_t timeout);
-/*******************************************************************************
- *
- * Function BTM_GetLinkSuperTout
- *
- * Description Read the link supervision timeout value of the connection
- *
- * Returns status of the operation
- *
- ******************************************************************************/
-tBTM_STATUS BTM_GetLinkSuperTout(const RawAddress& remote_bda,
- uint16_t* p_timeout);
-
-/*******************************************************************************
- *
- * Function BTM_IsAclConnectionUp
- *
- * Description This function is called to check if an ACL connection exists
- * to a specific remote BD Address. The second version ensures
- * the hci handle is valid (Unsure if needed)
- *
- * Returns true if connection is up, else false.
- *
- ******************************************************************************/
-bool BTM_IsAclConnectionUp(const RawAddress& remote_bda,
- tBT_TRANSPORT transport);
-
-bool BTM_IsAclConnectionUpAndHandleValid(const RawAddress& remote_bda,
- tBT_TRANSPORT transport);
-
-bool BTM_IsAclConnectionUpFromHandle(uint16_t hci_handle);
-
-/*******************************************************************************
- *
- * Function BTM_GetRole
- *
- * Description This function is called to get the role of the local device
- * for the ACL connection with the specified remote device
- *
- * Returns BTM_SUCCESS if connection exists.
- * BTM_UNKNOWN_ADDR if no active link with bd addr specified
- *
- ******************************************************************************/
-tBTM_STATUS BTM_GetRole(const RawAddress& remote_bd_addr, tHCI_ROLE* p_role);
-
-/*******************************************************************************
- *
- * Function BTM_SwitchRoleToCentral
- *
- * Description This function is called to switch role between central and
- * peripheral. If role is already set it will do nothing.
- *
- * Returns BTM_SUCCESS if already in specified role.
- * BTM_CMD_STARTED if command issued to controller.
- * BTM_NO_RESOURCES if memory couldn't be allocated to issue
- * the command
- * BTM_UNKNOWN_ADDR if no active link with bd addr specified
- * BTM_MODE_UNSUPPORTED if the local device does not support
- * role switching
- *
- ******************************************************************************/
-tBTM_STATUS BTM_SwitchRoleToCentral(const RawAddress& remote_bd_addr);
-
-/*******************************************************************************
- *
- * Function BTM_ReadRSSI
- *
- * Description This function is called to read the link policy settings.
- * The address of link policy results are returned in the
- * callback. (tBTM_RSSI_RESULT)
- *
- * Returns BTM_CMD_STARTED if command issued to controller.
- * BTM_NO_RESOURCES if memory couldn't be allocated to issue
- * the command
- * BTM_UNKNOWN_ADDR if no active link with bd addr specified
- * BTM_BUSY if command is already in progress
- *
- ******************************************************************************/
-tBTM_STATUS BTM_ReadRSSI(const RawAddress& remote_bda, tBTM_CMPL_CB* p_cb);
-
-/*******************************************************************************
- *
- * Function BTM_ReadFailedContactCounter
- *
- * Description This function is called to read the failed contact counter.
- * The result is returned in the callback.
- * (tBTM_FAILED_CONTACT_COUNTER_RESULT)
- *
- * Returns BTM_CMD_STARTED if command issued to controller.
- * BTM_NO_RESOURCES if memory couldn't be allocated to issue
- * the command
- * BTM_UNKNOWN_ADDR if no active link with bd addr specified
- * BTM_BUSY if command is already in progress
- *
- ******************************************************************************/
-tBTM_STATUS BTM_ReadFailedContactCounter(const RawAddress& remote_bda,
- tBTM_CMPL_CB* p_cb);
-
-/*******************************************************************************
- *
- * Function BTM_ReadTxPower
- *
- * Description This function is called to read the current connection
- * TX power of the connection. The TX power level results
- * are returned in the callback.
- * (tBTM_RSSI_RESULT)
- *
- * Returns BTM_CMD_STARTED if command issued to controller.
- * BTM_NO_RESOURCES if memory couldn't be allocated to issue
- * the command
- * BTM_UNKNOWN_ADDR if no active link with bd addr specified
- * BTM_BUSY if command is already in progress
- *
- ******************************************************************************/
-tBTM_STATUS BTM_ReadTxPower(const RawAddress& remote_bda,
- tBT_TRANSPORT transport, tBTM_CMPL_CB* p_cb);
-
-/*******************************************************************************
- *
- * Function BTM_GetNumAclLinks
- *
- * Description This function is called to count the number of
- * ACL links that are active.
- *
- * Returns uint16_t Number of active ACL links
- *
- ******************************************************************************/
-uint16_t BTM_GetNumAclLinks(void);
-
-void btm_set_packet_types_from_address(const RawAddress& bda,
- uint16_t pkt_types);
-
-#define BLE_RESOLVE_ADDR_MASK 0xc0
-#define BLE_RESOLVE_ADDR_MSB 0x40
-
-bool BTM_BLE_IS_RESOLVE_BDA(const RawAddress& x);
-
-bool acl_refresh_remote_address(const RawAddress& identity_address,
- tBLE_ADDR_TYPE identity_address_type,
- const RawAddress& remote_bda, uint8_t rra_type,
- const RawAddress& rpa);
-
-void btm_establish_continue_from_address(const RawAddress& remote_bda,
- tBT_TRANSPORT transport);
-
-bool acl_peer_supports_ble_connection_parameters_request(
- const RawAddress& remote_bda);
-
-bool sco_peer_supports_esco_2m_phy(const RawAddress& remote_bda);
-bool sco_peer_supports_esco_3m_phy(const RawAddress& remote_bda);
-
-bool acl_peer_supports_ble_packet_extension(uint16_t hci_handle);
-bool acl_peer_supports_ble_2m_phy(uint16_t hci_handle);
-bool acl_peer_supports_ble_coded_phy(uint16_t hci_handle);
-
-bool acl_is_switch_role_idle(const RawAddress& bd_addr,
- tBT_TRANSPORT transport);
-
-bool acl_peer_supports_ble_packet_extension(uint16_t hci_handle);
-
-/*******************************************************************************
- *
- * Function BTM_ReadConnectionAddr
- *
- * Description Read the local device random address.
- *
- * Returns void
- *
- ******************************************************************************/
-void BTM_ReadConnectionAddr(const RawAddress& remote_bda,
- RawAddress& local_conn_addr,
- tBLE_ADDR_TYPE* p_addr_type);
-
-/*******************************************************************************
- *
- * Function BTM_IsBleConnection
- *
- * Description This function is called to check if the connection handle
- * for an LE link
- *
- * Returns true if connection is LE link, otherwise false.
- *
- ******************************************************************************/
-bool BTM_IsBleConnection(uint16_t hci_handle);
-
-const RawAddress acl_address_from_handle(uint16_t hci_handle);
-
-void btm_ble_refresh_local_resolvable_private_addr(
- const RawAddress& pseudo_addr, const RawAddress& local_rpa);
-
-void btm_cont_rswitch_from_handle(uint16_t hci_handle);
-
-uint8_t acl_link_role_from_handle(uint16_t handle);
-
-void acl_set_disconnect_reason(tHCI_STATUS acl_disc_reason);
-
-bool acl_is_role_switch_allowed();
-
-uint16_t acl_get_supported_packet_types();
-
-bool acl_set_peer_le_features_from_handle(uint16_t hci_handle,
- const uint8_t* p);
-
-tBTM_STATUS btm_read_power_mode_state(const RawAddress& remote_bda,
- tBTM_PM_STATE* pmState);
-
-void btm_acl_notif_conn_collision(const RawAddress& bda);
-
-void btm_acl_update_conn_addr(uint16_t conn_handle, const RawAddress& address);
-
-/*******************************************************************************
- *
- * Function BTM_ReadPowerMode
- *
- * Description This returns the current mode for a specific
- * ACL connection.
- *
- * Input Param remote_bda - device address of desired ACL connection
- *
- * Output Param p_mode - address where the current mode is copied into.
- * BTM_ACL_MODE_NORMAL
- * BTM_ACL_MODE_HOLD
- * BTM_ACL_MODE_SNIFF
- * BTM_ACL_MODE_PARK
- * (valid only if return code is BTM_SUCCESS)
- *
- * Returns true if successful, false otherwise.
- *
- ******************************************************************************/
-bool BTM_ReadPowerMode(const RawAddress& remote_bda, tBTM_PM_MODE* p_mode);
-
-void btm_acl_created(const RawAddress& bda, uint16_t hci_handle,
- tHCI_ROLE link_role, tBT_TRANSPORT transport);
-
-void btm_acl_removed(uint16_t handle);
-
-void acl_disconnect_from_handle(uint16_t handle, tHCI_STATUS reason);
-void acl_disconnect_after_role_switch(uint16_t conn_handle, tHCI_STATUS reason);
-
-bool acl_peer_supports_sniff_subrating(const RawAddress& remote_bda);
-
-void btm_acl_set_paging(bool value);
-
-void btm_process_cancel_complete(uint8_t status, uint8_t mode);
-
-uint8_t btm_handle_to_acl_index(uint16_t hci_handle);
-
-tHCI_REASON btm_get_acl_disc_reason_code(void);
-
-extern tBTM_STATUS btm_remove_acl(const RawAddress& bd_addr,
- tBT_TRANSPORT transport);
-
-void btm_acl_device_down(void);
-void btm_acl_update_inquiry_status(uint8_t status);
-
-void ACL_RegisterClient(struct acl_client_callback_s* callbacks);
-void ACL_UnregisterClient(struct acl_client_callback_s* callbacks);
-bool ACL_SupportTransparentSynchronousData(const RawAddress& bd_addr);
-
-void acl_add_to_ignore_auto_connect_after_disconnect(const RawAddress& bd_addr);
-bool acl_check_and_clear_ignore_auto_connect_after_disconnect(
- const RawAddress& bd_addr);
-void acl_clear_all_ignore_auto_connect_after_disconnect();
diff --git a/stack/include/acl_api_types.h b/stack/include/acl_api_types.h
deleted file mode 100644
index 860f10049..000000000
--- a/stack/include/acl_api_types.h
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_status.h"
-#include "types/raw_address.h"
-
-// Note: From include/btm_api_types.h
-
-/*****************************************************************************
- * ACL CHANNEL MANAGEMENT
- ****************************************************************************/
-/******************
- * ACL Constants
- ******************/
-/***************
- * ACL Types
- ***************/
-
-/* Structure returned with read RSSI event (in tBTM_CMPL_CB callback function)
- * in response to BTM_ReadRSSI call.
- */
-typedef struct {
- tBTM_STATUS status;
- uint8_t hci_status;
- RawAddress rem_bda;
- int8_t rssi;
-} tBTM_RSSI_RESULT;
-
-/* Structure returned with read failed contact counter event
- * (in tBTM_CMPL_CB callback function) in response to
- * BTM_ReadFailedContactCounter call.
- */
-typedef struct {
- tBTM_STATUS status;
- uint8_t hci_status;
- RawAddress rem_bda;
- uint16_t failed_contact_counter;
-} tBTM_FAILED_CONTACT_COUNTER_RESULT;
-
-/* Structure returned with read automatic flush timeout event
- * (in tBTM_CMPL_CB callback function) in response to
- * BTM_ReadAutomaticFlushTimeout call.
- */
-typedef struct {
- tBTM_STATUS status;
- uint8_t hci_status;
- RawAddress rem_bda;
- uint16_t automatic_flush_timeout;
-} tBTM_AUTOMATIC_FLUSH_TIMEOUT_RESULT;
-
-/* Structure returned with read current TX power event (in tBTM_CMPL_CB callback
- * function) in response to BTM_ReadTxPower call.
- */
-typedef struct {
- tBTM_STATUS status;
- uint8_t hci_status;
- RawAddress rem_bda;
- int8_t tx_power;
-} tBTM_TX_POWER_RESULT;
-
-/* Structure returned with read link quality event (in tBTM_CMPL_CB callback
- * function) in response to BTM_ReadLinkQuality call.
- */
-typedef struct {
- tBTM_STATUS status;
- uint8_t hci_status;
- RawAddress rem_bda;
- uint8_t link_quality;
-} tBTM_LINK_QUALITY_RESULT;
-
-#define BTM_INQUIRY_STARTED 1
-#define BTM_INQUIRY_CANCELLED 2
-#define BTM_INQUIRY_COMPLETE 3
diff --git a/stack/include/acl_client_callbacks.h b/stack/include/acl_client_callbacks.h
deleted file mode 100644
index 158ba2286..000000000
--- a/stack/include/acl_client_callbacks.h
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcidefs.h"
-#include "types/bt_transport.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
-
-struct acl_client_callback_s {
- virtual void on_acl_link_down(const RawAddress bd_addr,
- tBT_TRANSPORT transport) = 0;
- virtual void on_acl_link_up(const RawAddress bd_addr,
- tBT_TRANSPORT transport) = 0;
- virtual void on_acl_remote_features_complete(const RawAddress bd_addr) = 0;
- virtual void on_acl_role_change(const RawAddress bd_addr, hci_role_t new_role,
- tHCI_STATUS hci_status) = 0;
-
- virtual ~acl_client_callback_s() = default;
-};
diff --git a/stack/include/acl_hci_link_interface.h b/stack/include/acl_hci_link_interface.h
deleted file mode 100644
index ffeec79ce..000000000
--- a/stack/include/acl_hci_link_interface.h
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include "stack/include/bt_types.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcidefs.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
-
-// This header contains functions for HCIF-Acl Management to invoke
-//
-void btm_acl_connection_request(const RawAddress& bda, uint8_t* dc);
-void btm_acl_connected(const RawAddress& bda, uint16_t handle,
- tHCI_STATUS status, uint8_t enc_mode);
-void on_acl_br_edr_connected(const RawAddress& bda, uint16_t handle,
- uint8_t enc_mode);
-void on_acl_br_edr_failed(const RawAddress& bda, tHCI_STATUS status);
-void btm_acl_disconnected(tHCI_STATUS status, uint16_t handle,
- tHCI_STATUS reason);
-void btm_acl_encrypt_change(uint16_t handle, uint8_t status,
- uint8_t encr_enable);
-void btm_acl_paging(BT_HDR* p, const RawAddress& dest);
-void btm_acl_resubmit_page(void);
-void btm_acl_role_changed(tHCI_STATUS hci_status, const RawAddress& bd_addr,
- tHCI_ROLE new_role);
-void btm_rejectlist_role_change_device(const RawAddress& bd_addr,
- uint8_t hci_status);
-void btm_pm_proc_cmd_status(tHCI_STATUS status);
-void btm_pm_proc_mode_change(tHCI_STATUS hci_status, uint16_t hci_handle,
- tHCI_MODE mode, uint16_t interval);
-void btm_pm_proc_ssr_evt(uint8_t* p, uint16_t evt_len);
-void btm_read_automatic_flush_timeout_complete(uint8_t* p);
-void btm_read_failed_contact_counter_complete(uint8_t* p);
-void btm_read_link_quality_complete(uint8_t* p);
-void btm_read_remote_ext_features_complete_raw(uint8_t* p, uint8_t evt_len);
-void btm_read_remote_ext_features_complete(uint16_t handle, uint8_t page_num,
- uint8_t max_page, uint8_t* features);
-void btm_read_remote_ext_features_failed(uint8_t status, uint16_t handle);
-void btm_read_remote_features_complete_raw(uint8_t* p);
-void btm_read_remote_features_complete(uint16_t handle, uint8_t* features);
-void btm_read_remote_version_complete_raw(uint8_t* p);
-void btm_read_remote_version_complete(tHCI_STATUS status, uint16_t handle,
- uint8_t lmp_version,
- uint16_t manufacturer,
- uint16_t lmp_subversion);
-void btm_read_rssi_complete(uint8_t* p);
-void btm_read_tx_power_complete(uint8_t* p, bool is_ble);
-
-void acl_rcv_acl_data(BT_HDR* p_msg);
-void acl_link_segments_xmitted(BT_HDR* p_msg);
-void acl_process_num_completed_pkts(uint8_t* p, uint8_t evt_len);
-void acl_packets_completed(uint16_t handle, uint16_t num_packets);
-void acl_process_supported_features(uint16_t handle, uint64_t features);
-void acl_process_extended_features(uint16_t handle, uint8_t current_page_number,
- uint8_t max_page_number, uint64_t features);
-void btm_pm_on_mode_change(tHCI_STATUS status, uint16_t handle,
- tHCI_MODE current_mode, uint16_t interval);
-void btm_pm_on_sniff_subrating(tHCI_STATUS status, uint16_t handle,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout);
diff --git a/stack/include/avct_api.h b/stack/include/avct_api.h
index 8cc0bba37..21a880aed 100644
--- a/stack/include/avct_api.h
+++ b/stack/include/avct_api.h
@@ -136,7 +136,7 @@ typedef struct {
* Returns void
*
******************************************************************************/
-extern void AVCT_Register();
+extern void AVCT_Register(uint16_t mtu, uint16_t mtu_br, uint8_t sec_mask);
/*******************************************************************************
*
diff --git a/stack/include/avdt_api.h b/stack/include/avdt_api.h
index 085eca1b0..09e7f7cb8 100644
--- a/stack/include/avdt_api.h
+++ b/stack/include/avdt_api.h
@@ -25,13 +25,8 @@
#ifndef AVDT_API_H
#define AVDT_API_H
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <string>
-
#include "bt_target.h"
#include "bt_types.h"
-#include "osi/include/log.h"
/*****************************************************************************
* Constants
@@ -44,38 +39,12 @@
#define AVDT_CODEC_SIZE 20
/* API function return value result codes. */
-typedef enum : uint16_t {
- AVDT_SUCCESS = 0, /* Function successful */
- AVDT_BAD_PARAMS = 1, /* Invalid parameters */
- AVDT_NO_RESOURCES = 2, /* Not enough resources */
- AVDT_BAD_HANDLE = 3, /* Bad handle */
- AVDT_BUSY = 4, /* A procedure is already in progress */
- AVDT_WRITE_FAIL = 5, /* Write failed */
-} tAVDT_RESULT;
-
-inline tAVDT_RESULT ToAvdtResult(uint16_t result) {
- ASSERT_LOG(result <= AVDT_WRITE_FAIL, "Unable to convert illegal result:%hu",
- result);
- return static_cast<tAVDT_RESULT>(result);
-}
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string avdt_result_text(const tAVDT_RESULT& result) {
- switch (result) {
- CASE_RETURN_TEXT(AVDT_SUCCESS);
- CASE_RETURN_TEXT(AVDT_BAD_PARAMS);
- CASE_RETURN_TEXT(AVDT_NO_RESOURCES);
- CASE_RETURN_TEXT(AVDT_BAD_HANDLE);
- CASE_RETURN_TEXT(AVDT_BUSY);
- CASE_RETURN_TEXT(AVDT_WRITE_FAIL);
- default:
- return base::StringPrintf("UNKNOWN[%hu]", result);
- }
-}
-#undef CASE_RETURN_TEXT
+#define AVDT_SUCCESS 0 /* Function successful */
+#define AVDT_BAD_PARAMS 1 /* Invalid parameters */
+#define AVDT_NO_RESOURCES 2 /* Not enough resources */
+#define AVDT_BAD_HANDLE 3 /* Bad handle */
+#define AVDT_BUSY 4 /* A procedure is already in progress */
+#define AVDT_WRITE_FAIL 5 /* Write failed */
/* The index to access the codec type in codec_info[]. */
#define AVDT_CODEC_TYPE_INDEX 2
@@ -109,16 +78,6 @@ inline std::string avdt_result_text(const tAVDT_RESULT& result) {
#define AVDT_TSEP_SRC 0 /* Source SEP */
#define AVDT_TSEP_SNK 1 /* Sink SEP */
#define AVDT_TSEP_INVALID 3 /* Invalid SEP */
-inline const std::string peer_stream_endpoint_text(int type) {
- switch (type) {
- case AVDT_TSEP_SRC:
- return std::string("Source");
- case AVDT_TSEP_SNK:
- return std::string("Sink");
- default:
- return std::string("Invalid");
- }
-}
/* initiator/acceptor role for adaption */
#define AVDT_INT 0 /* initiator */
@@ -318,6 +277,7 @@ class AvdtpRcb {
ret_tout(0),
sig_tout(0),
idle_tout(0),
+ sec_mask(0),
scb_index(0) {}
AvdtpRcb& operator=(const AvdtpRcb&) = default;
@@ -326,6 +286,7 @@ class AvdtpRcb {
ret_tout = 0;
sig_tout = 0;
idle_tout = 0;
+ sec_mask = 0;
scb_index = 0;
}
@@ -333,6 +294,7 @@ class AvdtpRcb {
uint8_t ret_tout; /* AVDTP signaling retransmission timeout */
uint8_t sig_tout; /* AVDTP signaling message timeout */
uint8_t idle_tout; /* AVDTP idle signaling channel timeout */
+ uint8_t sec_mask; /* Security mask for BTM_SetSecurityLevel() */
uint8_t scb_index; /* The Stream Control Block index */
};
@@ -508,6 +470,7 @@ class AvdtpStreamConfig {
p_sink_data_cback(nullptr),
p_report_cback(nullptr),
mtu(0),
+ flush_to(0),
tsep(0),
media_type(0),
nsc_mask(0) {}
@@ -519,6 +482,7 @@ class AvdtpStreamConfig {
p_sink_data_cback = nullptr;
p_report_cback = nullptr;
mtu = 0;
+ flush_to = 0;
tsep = 0;
media_type = 0;
nsc_mask = 0;
@@ -530,6 +494,7 @@ class AvdtpStreamConfig {
tAVDT_SINK_DATA_CBACK* p_sink_data_cback; // Sink data callback function
tAVDT_REPORT_CBACK* p_report_cback; // Report callback function
uint16_t mtu; // The L2CAP MTU of the transport channel
+ uint16_t flush_to; // The L2CAP flush timeout of the transport channel
uint8_t tsep; // SEP type
uint8_t media_type; // Media type: AVDT_MEDIA_TYPE_*
uint16_t nsc_mask; // Nonsupported protocol command messages
@@ -796,6 +761,21 @@ extern uint16_t AVDT_ReconfigReq(uint8_t handle, AvdtpSepConfig* p_cfg);
/*******************************************************************************
*
+ * Function AVDT_ReconfigRsp
+ *
+ * Description Respond to a reconfigure request from the peer device.
+ * This function must be called if the application receives
+ * an AVDT_RECONFIG_IND_EVT through its control callback.
+ *
+ *
+ * Returns AVDT_SUCCESS if successful, otherwise error.
+ *
+ ******************************************************************************/
+extern uint16_t AVDT_ReconfigRsp(uint8_t handle, uint8_t label,
+ uint8_t error_code, uint8_t category);
+
+/*******************************************************************************
+ *
* Function AVDT_SecurityReq
*
* Description Send a security request to the peer device. When the
@@ -830,6 +810,42 @@ extern uint16_t AVDT_SecurityRsp(uint8_t handle, uint8_t label,
/*******************************************************************************
*
+ * Function AVDT_WriteReq
+ *
+ * Description Send a media packet to the peer device. The stream must
+ * be started before this function is called. Also, this
+ * function can only be called if the stream is a SRC.
+ *
+ * When AVDTP has sent the media packet and is ready for the
+ * next packet, an AVDT_WRITE_CFM_EVT is sent to the
+ * application via the control callback. The application must
+ * wait for the AVDT_WRITE_CFM_EVT before it makes the next
+ * call to AVDT_WriteReq(). If the applications calls
+ * AVDT_WriteReq() before it receives the event the packet
+ * will not be sent. The application may make its first call
+ * to AVDT_WriteReq() after it receives an AVDT_START_CFM_EVT
+ * or AVDT_START_IND_EVT.
+ *
+ * The application passes the packet using the BT_HDR
+ * structure.
+ * This structure is described in section 2.1. The offset
+ * field must be equal to or greater than AVDT_MEDIA_OFFSET.
+ * This allows enough space in the buffer for the L2CAP and
+ * AVDTP headers.
+ *
+ * The memory pointed to by p_pkt must be a GKI buffer
+ * allocated by the application. This buffer will be freed
+ * by the protocol stack; the application must not free
+ * this buffer.
+ *
+ *
+ * Returns AVDT_SUCCESS if successful, otherwise error.
+ *
+ ******************************************************************************/
+extern uint16_t AVDT_WriteReq(uint8_t handle, BT_HDR* p_pkt,
+ uint32_t time_stamp, uint8_t m_pt);
+/*******************************************************************************
+ *
* Function AVDT_WriteReqOpt
*
* Description Send a media packet to the peer device. The stream must
@@ -884,7 +900,7 @@ extern uint16_t AVDT_WriteReqOpt(uint8_t handle, BT_HDR* p_pkt,
*
******************************************************************************/
extern uint16_t AVDT_ConnectReq(const RawAddress& bd_addr,
- uint8_t channel_index,
+ uint8_t channel_index, uint8_t sec_mask,
tAVDT_CTRL_CBACK* p_cback);
/*******************************************************************************
@@ -913,6 +929,33 @@ extern uint16_t AVDT_DisconnectReq(const RawAddress& bd_addr,
******************************************************************************/
extern uint16_t AVDT_GetL2CapChannel(uint8_t handle);
+/*******************************************************************************
+ *
+ * Function AVDT_GetSignalChannel
+ *
+ * Description Get the L2CAP CID used by the signal channel of the given
+ * handle.
+ *
+ * Returns CID if successful, otherwise 0.
+ *
+ ******************************************************************************/
+extern uint16_t AVDT_GetSignalChannel(uint8_t handle,
+ const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
+ * Function AVDT_SendReport
+ *
+ * Description
+ *
+ *
+ *
+ * Returns
+ *
+ ******************************************************************************/
+extern uint16_t AVDT_SendReport(uint8_t handle, AVDT_REPORT_TYPE type,
+ tAVDT_REPORT_DATA* p_data);
+
/******************************************************************************
*
* Function AVDT_SetTraceLevel
diff --git a/stack/include/avrc_api.h b/stack/include/avrc_api.h
index 7796ae0b6..77c37dec1 100644
--- a/stack/include/avrc_api.h
+++ b/stack/include/avrc_api.h
@@ -109,31 +109,6 @@
* response from the peer */
#define AVRC_CMD_TIMEOUT_EVT 8
-/* Configurable avrcp version key and constant values */
-#ifndef AVRC_VERSION_PROPERTY
-#define AVRC_VERSION_PROPERTY "persist.bluetooth.avrcpversion"
-#endif
-
-#ifndef AVRC_1_6_STRING
-#define AVRC_1_6_STRING "avrcp16"
-#endif
-
-#ifndef AVRC_1_5_STRING
-#define AVRC_1_5_STRING "avrcp15"
-#endif
-
-#ifndef AVRC_1_4_STRING
-#define AVRC_1_4_STRING "avrcp14"
-#endif
-
-#ifndef AVRC_1_3_STRING
-#define AVRC_1_3_STRING "avrcp13"
-#endif
-
-#ifndef AVRC_DEFAULT_VERSION
-#define AVRC_DEFAULT_VERSION AVRC_1_4_STRING
-#endif
-
/* Supported categories */
#define AVRC_SUPF_CT_CAT1 0x0001 /* Category 1 */
#define AVRC_SUPF_CT_CAT2 0x0002 /* Category 2 */
@@ -224,17 +199,6 @@ typedef struct {
/******************************************************************************
*
- * Function ARVC_GetProfileVersion
- *
- * Description Get the user assigned AVRCP profile version
- *
- * Returns The AVRCP profile version
- *
- *****************************************************************************/
-extern uint16_t AVRC_GetProfileVersion();
-
-/******************************************************************************
- *
* Function AVRC_AddRecord
*
* Description This function is called to build an AVRCP SDP record.
@@ -258,13 +222,6 @@ extern uint16_t AVRC_GetProfileVersion();
*
* sdp_handle: SDP handle returned by SDP_CreateRecord().
*
- * browse_supported: browse support info.
- *
- * profile_version: profile version of avrcp record.
- *
- * cover_art_psm: The PSM of a cover art service, if
- * supported. Use 0 Otherwise. Ignored on controller
- *
* Output Parameters:
* None.
*
@@ -277,23 +234,7 @@ extern uint16_t AVRC_AddRecord(uint16_t service_uuid,
const char* p_service_name,
const char* p_provider_name, uint16_t categories,
uint32_t sdp_handle, bool browse_supported,
- uint16_t profile_version,
- uint16_t cover_art_psm);
-
-/*******************************************************************************
- *
- * Function AVRC_RemoveRecord
- *
- * Description This function is called to remove an AVRCP SDP record.
- *
- * Input Parameters:
- * sdp_handle: Handle you used with AVRC_AddRecord
- *
- * Returns AVRC_SUCCESS if successful.
- * AVRC_FAIL otherwise
- *
- *******************************************************************************/
-extern uint16_t AVRC_RemoveRecord(uint32_t sdp_handle);
+ uint16_t profile_version);
/******************************************************************************
*
diff --git a/stack/include/avrc_defs.h b/stack/include/avrc_defs.h
index 16ff60881..29d3e3983 100644
--- a/stack/include/avrc_defs.h
+++ b/stack/include/avrc_defs.h
@@ -202,49 +202,47 @@
#define AVRC_PKT_END 3
#define AVRC_PKT_TYPE_MASK 3
-typedef enum : uint8_t {
- /* Define the PDUs carried in the vendor dependant data
- */
- AVRC_PDU_GET_CAPABILITIES = 0x10,
- AVRC_PDU_LIST_PLAYER_APP_ATTR = 0x11,
- AVRC_PDU_LIST_PLAYER_APP_VALUES = 0x12,
- AVRC_PDU_GET_CUR_PLAYER_APP_VALUE = 0x13,
- AVRC_PDU_SET_PLAYER_APP_VALUE = 0x14,
- AVRC_PDU_GET_PLAYER_APP_ATTR_TEXT = 0x15,
- AVRC_PDU_GET_PLAYER_APP_VALUE_TEXT = 0x16,
- AVRC_PDU_INFORM_DISPLAY_CHARSET = 0x17,
- AVRC_PDU_INFORM_BATTERY_STAT_OF_CT = 0x18,
- AVRC_PDU_GET_ELEMENT_ATTR = 0x20,
- AVRC_PDU_GET_PLAY_STATUS = 0x30,
- AVRC_PDU_REGISTER_NOTIFICATION = 0x31,
- AVRC_PDU_REQUEST_CONTINUATION_RSP = 0x40,
- AVRC_PDU_ABORT_CONTINUATION_RSP = 0x41,
- /* added in 1.4 */
- AVRC_PDU_SET_ABSOLUTE_VOLUME = 0x50,
- AVRC_PDU_SET_ADDRESSED_PLAYER = 0x60,
- AVRC_PDU_SET_BROWSED_PLAYER = 0x70,
- AVRC_PDU_GET_FOLDER_ITEMS = 0x71,
- AVRC_PDU_CHANGE_PATH = 0x72,
- AVRC_PDU_GET_ITEM_ATTRIBUTES = 0x73,
- AVRC_PDU_PLAY_ITEM = 0x74,
- /* Added in post 1.5 */
- AVRC_PDU_GET_TOTAL_NUM_OF_ITEMS = 0x75,
- AVRC_PDU_SEARCH = 0x80,
- AVRC_PDU_ADD_TO_NOW_PLAYING = 0x90,
- AVRC_PDU_GENERAL_REJECT = 0xA0,
- /* Define the vendor unique id carried in the pass through data
- */
- AVRC_PDU_NEXT_GROUP = 0x00,
- AVRC_PDU_PREV_GROUP = 0x01,
- AVRC_PDU_INVALID = 0xff,
-} tAVRC_PDU;
-
+/* Define the PDUs carried in the vendor dependant data
+*/
+#define AVRC_PDU_GET_CAPABILITIES 0x10
+#define AVRC_PDU_LIST_PLAYER_APP_ATTR 0x11
+#define AVRC_PDU_LIST_PLAYER_APP_VALUES 0x12
+#define AVRC_PDU_GET_CUR_PLAYER_APP_VALUE 0x13
+#define AVRC_PDU_SET_PLAYER_APP_VALUE 0x14
+#define AVRC_PDU_GET_PLAYER_APP_ATTR_TEXT 0x15
+#define AVRC_PDU_GET_PLAYER_APP_VALUE_TEXT 0x16
+#define AVRC_PDU_INFORM_DISPLAY_CHARSET 0x17
+#define AVRC_PDU_INFORM_BATTERY_STAT_OF_CT 0x18
+#define AVRC_PDU_GET_ELEMENT_ATTR 0x20
+#define AVRC_PDU_GET_PLAY_STATUS 0x30
+#define AVRC_PDU_REGISTER_NOTIFICATION 0x31
+#define AVRC_PDU_REQUEST_CONTINUATION_RSP 0x40
+#define AVRC_PDU_ABORT_CONTINUATION_RSP 0x41
+/* added in 1.4 */
+#define AVRC_PDU_SET_ABSOLUTE_VOLUME 0x50
+#define AVRC_PDU_SET_ADDRESSED_PLAYER 0x60
+#define AVRC_PDU_SET_BROWSED_PLAYER 0x70
+#define AVRC_PDU_GET_FOLDER_ITEMS 0x71
+#define AVRC_PDU_CHANGE_PATH 0x72
+#define AVRC_PDU_GET_ITEM_ATTRIBUTES 0x73
+#define AVRC_PDU_PLAY_ITEM 0x74
+/* Added in post 1.5 */
+#define AVRC_PDU_GET_TOTAL_NUM_OF_ITEMS 0x75
+#define AVRC_PDU_SEARCH 0x80
+#define AVRC_PDU_ADD_TO_NOW_PLAYING 0x90
+#define AVRC_PDU_GENERAL_REJECT 0xA0
+
+/* Define the vendor unique id carried in the pass through data
+*/
+#define AVRC_PDU_NEXT_GROUP 0x00
+#define AVRC_PDU_PREV_GROUP 0x01
/* The only pass through vendor unique commands defined by AVRC are the group
* navigation commands.
* The len for vendor unique data is 5
*/
#define AVRC_PASS_THRU_GROUP_LEN 5
+#define AVRC_PDU_INVALID 0xff
/* 6.15.3 error status code for general reject */
/* Invalid command, sent if TG received a PDU that it did not understand. */
#define AVRC_STS_BAD_CMD 0x00
diff --git a/stack/include/ble_acl_interface.h b/stack/include/ble_acl_interface.h
deleted file mode 100644
index 2359b307c..000000000
--- a/stack/include/ble_acl_interface.h
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "stack/include/bt_types.h"
-#include "stack/include/hci_error_code.h"
-
-void acl_ble_connection_complete(const tBLE_BD_ADDR& address_with_type,
- uint16_t handle, tHCI_ROLE role, bool match,
- uint16_t conn_interval, uint16_t conn_latency,
- uint16_t conn_timeout);
-void acl_ble_enhanced_connection_complete(
- const tBLE_BD_ADDR& address_with_type, uint16_t handle, tHCI_ROLE role,
- bool match, uint16_t conn_interval, uint16_t conn_latency,
- uint16_t conn_timeout, const RawAddress& local_rpa,
- const RawAddress& peer_rpa, uint8_t peer_addr_type);
-void acl_ble_enhanced_connection_complete_from_shim(
- const tBLE_BD_ADDR& address_with_type, uint16_t handle, tHCI_ROLE role,
- uint16_t conn_interval, uint16_t conn_latency, uint16_t conn_timeout,
- const RawAddress& local_rpa, const RawAddress& peer_rpa,
- uint8_t peer_addr_type);
-void acl_ble_connection_fail(const tBLE_BD_ADDR& address_with_type,
- uint16_t handle, bool enhanced,
- tHCI_STATUS status);
-void acl_ble_update_event_received(tHCI_STATUS status, uint16_t handle,
- uint16_t interval, uint16_t latency,
- uint16_t timeout);
diff --git a/stack/include/ble_hci_link_interface.h b/stack/include/ble_hci_link_interface.h
deleted file mode 100644
index fd4b462c1..000000000
--- a/stack/include/ble_hci_link_interface.h
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include "bt_common.h"
-
-// This header contains functions for HCI-ble to invoke
-void btm_ble_conn_complete(uint8_t* p, UNUSED_ATTR uint16_t evt_len,
- bool enhanced);
-void btm_ble_process_adv_pkt(uint8_t len, uint8_t* p);
-void btm_ble_process_ext_adv_pkt(uint8_t len, uint8_t* p);
-void btm_ble_process_phy_update_pkt(uint8_t len, uint8_t* p);
-void btm_ble_read_remote_features_complete(uint8_t* p);
-void btm_le_on_advertising_set_terminated(uint8_t* p, uint16_t length);
-extern void btm_ble_write_adv_enable_complete(uint8_t* p);
-extern void btm_ble_create_ll_conn_complete(tHCI_STATUS status);
-extern void btm_ble_ltk_request(uint16_t handle, uint8_t rand[8],
- uint16_t ediv);
-extern void btm_ble_test_command_complete(uint8_t* p);
-extern void btm_ble_rand_enc_complete(uint8_t* p, uint16_t op_code,
- tBTM_RAND_ENC_CB* p_enc_cplt_cback);
-extern bool btm_identity_addr_to_random_pseudo(RawAddress* bd_addr,
- uint8_t* p_addr_type,
- bool refresh);
-extern bool btm_identity_addr_to_random_pseudo_from_address_with_type(
- tBLE_BD_ADDR* address_with_type, bool refresh);
-extern void btm_ble_read_resolving_list_entry_complete(uint8_t* p,
- uint16_t evt_len);
-extern void btm_ble_create_conn_cancel_complete(uint8_t* p);
-extern void btm_ble_remove_resolving_list_entry_complete(uint8_t* p,
- uint16_t evt_len);
-extern void btm_ble_add_resolving_list_entry_complete(uint8_t* p,
- uint16_t evt_len);
-extern void btm_ble_clear_resolving_list_complete(uint8_t* p, uint16_t evt_len);
-extern void btm_ble_process_periodic_adv_pkt(uint8_t len, uint8_t* p);
-extern void btm_ble_process_periodic_adv_sync_est_evt(uint8_t len, uint8_t* p);
-extern void btm_ble_process_periodic_adv_sync_lost_evt(uint8_t len, uint8_t* p);
diff --git a/stack/include/bnep_api.h b/stack/include/bnep_api.h
index a956d0cbe..03b72e4c4 100644
--- a/stack/include/bnep_api.h
+++ b/stack/include/bnep_api.h
@@ -176,6 +176,26 @@ typedef struct {
} tBNEP_REGISTER;
+/* This is the structure used by profile to get the status of BNEP */
+typedef struct {
+#define BNEP_STATUS_FAILE 0
+#define BNEP_STATUS_CONNECTED 1
+ uint8_t con_status;
+
+ uint16_t l2cap_cid;
+ RawAddress rem_bda;
+ uint16_t rem_mtu_size;
+ uint16_t xmit_q_depth;
+
+ uint16_t sent_num_filters;
+ uint16_t sent_mcast_filters;
+ uint16_t rcvd_num_filters;
+ uint16_t rcvd_mcast_filters;
+ bluetooth::Uuid src_uuid;
+ bluetooth::Uuid dst_uuid;
+
+} tBNEP_STATUS;
+
/*****************************************************************************
* External Function Declarations
****************************************************************************/
@@ -229,7 +249,7 @@ extern void BNEP_Deregister(void);
extern tBNEP_RESULT BNEP_Connect(const RawAddress& p_rem_bda,
const bluetooth::Uuid& src_uuid,
const bluetooth::Uuid& dst_uuid,
- uint16_t* p_handle, uint32_t mx_chan_id);
+ uint16_t* p_handle);
/*******************************************************************************
*
@@ -396,4 +416,20 @@ extern uint8_t BNEP_SetTraceLevel(uint8_t new_level);
******************************************************************************/
extern void BNEP_Init(void);
+/*******************************************************************************
+ *
+ * Function BNEP_GetStatus
+ *
+ * Description This function gets the status information for BNEP
+ * connection
+ *
+ * Returns BNEP_SUCCESS - if the status is available
+ * BNEP_NO_RESOURCES - if no structure is passed for
+ * output
+ * BNEP_WRONG_HANDLE - if the handle is invalid
+ * BNEP_WRONG_STATE - if not in connected state
+ *
+ ******************************************************************************/
+extern tBNEP_RESULT BNEP_GetStatus(uint16_t handle, tBNEP_STATUS* p_status);
+
#endif
diff --git a/stack/include/bt_types.h b/stack/include/bt_types.h
index 609181177..e4d8fcc6e 100644
--- a/stack/include/bt_types.h
+++ b/stack/include/bt_types.h
@@ -21,9 +21,22 @@
#include <stdbool.h>
#include <stdint.h>
-#ifdef __cplusplus
-#include <string>
-#endif // __cplusplus
+
+#ifndef FALSE
+#define FALSE false
+#endif
+
+#ifndef TRUE
+#define TRUE true
+#endif
+
+#ifdef __arm
+#define PACKED __packed
+#define INLINE __inline
+#else
+#define PACKED
+#define INLINE
+#endif
/* READ WELL !!
*
@@ -39,8 +52,19 @@
#define BT_SUB_EVT_MASK 0x00FF
/* To Bluetooth Upper Layers */
/************************************/
+/* L2CAP event */
+#define BT_EVT_TO_BTU_L2C_EVT 0x0900
/* HCI Event */
#define BT_EVT_TO_BTU_HCI_EVT 0x1000
+/* event from BR/EDR controller */
+#define BT_EVT_TO_BTU_HCI_BR_EDR_EVT (0x0000 | BT_EVT_TO_BTU_HCI_EVT)
+/* event from local AMP 1 controller */
+#define BT_EVT_TO_BTU_HCI_AMP1_EVT (0x0001 | BT_EVT_TO_BTU_HCI_EVT)
+/* event from local AMP 2 controller */
+#define BT_EVT_TO_BTU_HCI_AMP2_EVT (0x0002 | BT_EVT_TO_BTU_HCI_EVT)
+/* event from local AMP 3 controller */
+#define BT_EVT_TO_BTU_HCI_AMP3_EVT (0x0003 | BT_EVT_TO_BTU_HCI_EVT)
+
/* ACL Data from HCI */
#define BT_EVT_TO_BTU_HCI_ACL 0x1100
/* SCO Data from HCI */
@@ -48,6 +72,8 @@
/* HCI Transport Error */
#define BT_EVT_TO_BTU_HCIT_ERR 0x1300
+/* Serial Port Event */
+#define BT_EVT_TO_BTU_SP_EVT 0x1400
/* Serial Port Data */
#define BT_EVT_TO_BTU_SP_DATA 0x1500
@@ -60,6 +86,14 @@
/* L2CAP segment(s) transmitted */
#define BT_EVT_TO_BTU_L2C_SEG_XMIT 0x1900
+/* BlueStackTester event: incoming message from target */
+#define BT_EVT_PROXY_INCOMING_MSG 0x1A00
+
+/* Insight BTSIM event */
+#define BT_EVT_BTSIM 0x1B00
+/* Insight Script Engine event */
+#define BT_EVT_BTISE 0x1C00
+
/* To LM */
/************************************/
/* HCI Command */
@@ -68,19 +102,119 @@
#define BT_EVT_TO_LM_HCI_ACL 0x2100
/* HCI SCO Data */
#define BT_EVT_TO_LM_HCI_SCO 0x2200
+/* HCI Transport Error */
+#define BT_EVT_TO_LM_HCIT_ERR 0x2300
+/* LC event */
+#define BT_EVT_TO_LM_LC_EVT 0x2400
+/* LC Received LMP command frame */
+#define BT_EVT_TO_LM_LC_LMP 0x2500
+/* LC Received ACL data */
+#define BT_EVT_TO_LM_LC_ACL 0x2600
+/* LC Received SCO data (not used) */
+#define BT_EVT_TO_LM_LC_SCO 0x2700
+/* LMP data transmit complete */
+#define BT_EVT_TO_LM_LC_ACL_TX 0x2800
+/* LMP Command transmit complete */
+#define BT_EVT_TO_LM_LC_LMPC_TX 0x2900
+/* Data to be locally loopbacked */
+#define BT_EVT_TO_LM_LOCAL_ACL_LB 0x2a00
+/* HCI ACL Data ack (not used) */
+#define BT_EVT_TO_LM_HCI_ACL_ACK 0x2b00
+/* LM Diagnostics commands */
+#define BT_EVT_TO_LM_DIAG 0x2c00
/* HCI ISO Data */
#define BT_EVT_TO_LM_HCI_ISO 0x2d00
+#define BT_EVT_TO_BTM_CMDS 0x2f00
+#define BT_EVT_TO_BTM_PM_MDCHG_EVT (0x0001 | BT_EVT_TO_BTM_CMDS)
+
+#define BT_EVT_TO_TCS_CMDS 0x3000
+
+#define BT_EVT_TO_CTP_CMDS 0x3300
+
+/* ftp events */
+#define BT_EVT_TO_FTP_SRVR_CMDS 0x3600
+#define BT_EVT_TO_FTP_CLNT_CMDS 0x3700
+
+/* SIM Access Profile events */
+#define BT_EVT_TO_BTU_SAP 0x3800
+
+/* opp events */
+#define BT_EVT_TO_OPP_SRVR_CMDS 0x3900
+#define BT_EVT_TO_OPP_CLNT_CMDS 0x3a00
+
+/* for NFC */
+/************************************/
+/* NCI Command, Notification or Data*/
+#define BT_EVT_TO_NFC_NCI 0x4000
+/* Initialization message */
+#define BT_EVT_TO_NFC_INIT 0x4100
+/* Low power */
+#define BT_EVT_TO_NCI_LP 0x4200
+/* Error notification to NFC Task */
+#define BT_EVT_TO_NFC_ERR 0x4300
+
+/* events to NFCC simulation (NCI packets) */
+#define BT_EVT_TO_NFCCSIM_NCI 0x4a00
+
+/* HCISU Events */
+
#define BT_EVT_HCISU 0x5000
+#define BT_EVT_TO_HCISU_RECONFIG_EVT (0x0001 | BT_EVT_HCISU)
+#define BT_EVT_TO_HCISU_UPDATE_BAUDRATE_EVT (0x0002 | BT_EVT_HCISU)
+#define BT_EVT_TO_HCISU_LP_ENABLE_EVT (0x0003 | BT_EVT_HCISU)
+#define BT_EVT_TO_HCISU_LP_DISABLE_EVT (0x0004 | BT_EVT_HCISU)
+#define BT_EVT_TO_HCISU_LP_APP_SLEEPING_EVT (0x0005 | BT_EVT_HCISU)
+#define BT_EVT_TO_HCISU_LP_ALLOW_BT_SLEEP_EVT (0x0006 | BT_EVT_HCISU)
+#define BT_EVT_TO_HCISU_LP_WAKEUP_HOST_EVT (0x0007 | BT_EVT_HCISU)
+#define BT_EVT_TO_HCISU_LP_RCV_H4IBSS_EVT (0x0008 | BT_EVT_HCISU)
+#define BT_EVT_TO_HCISU_H5_RESET_EVT (0x0009 | BT_EVT_HCISU)
+#define BT_EVT_HCISU_START_QUICK_TIMER (0x000a | BT_EVT_HCISU)
+
+#define BT_EVT_DATA_TO_AMP_1 0x5100
+#define BT_EVT_DATA_TO_AMP_15 0x5f00
+
+/* HSP Events */
+
+#define BT_EVT_BTU_HSP2 0x6000
+
+#define BT_EVT_TO_BTU_HSP2_EVT (0x0001 | BT_EVT_BTU_HSP2)
+
+/* BPP Events */
+#define BT_EVT_TO_BPP_PR_CMDS 0x6100 /* Printer Events */
+#define BT_EVT_TO_BPP_SND_CMDS 0x6200 /* BPP Sender Events */
+
+/* BIP Events */
+#define BT_EVT_TO_BIP_CMDS 0x6300
+
+/* HCRP Events */
+
+#define BT_EVT_BTU_HCRP 0x7000
+
+#define BT_EVT_TO_BTU_HCRP_EVT (0x0001 | BT_EVT_BTU_HCRP)
+#define BT_EVT_TO_BTU_HCRPM_EVT (0x0002 | BT_EVT_BTU_HCRP)
+
+#define BT_EVT_BTU_HFP 0x8000
+#define BT_EVT_TO_BTU_HFP_EVT (0x0001 | BT_EVT_BTU_HFP)
+
+#define BT_EVT_BTU_IPC_EVT 0x9000
+#define BT_EVT_BTU_IPC_LOGMSG_EVT (0x0000 | BT_EVT_BTU_IPC_EVT)
+#define BT_EVT_BTU_IPC_ACL_EVT (0x0001 | BT_EVT_BTU_IPC_EVT)
+#define BT_EVT_BTU_IPC_BTU_EVT (0x0002 | BT_EVT_BTU_IPC_EVT)
+#define BT_EVT_BTU_IPC_L2C_EVT (0x0003 | BT_EVT_BTU_IPC_EVT)
+#define BT_EVT_BTU_IPC_L2C_MSG_EVT (0x0004 | BT_EVT_BTU_IPC_EVT)
+#define BT_EVT_BTU_IPC_BTM_EVT (0x0005 | BT_EVT_BTU_IPC_EVT)
+#define BT_EVT_BTU_IPC_AVDT_EVT (0x0006 | BT_EVT_BTU_IPC_EVT)
+#define BT_EVT_BTU_IPC_SLIP_EVT (0x0007 | BT_EVT_BTU_IPC_EVT)
+#define BT_EVT_BTU_IPC_MGMT_EVT (0x0008 | BT_EVT_BTU_IPC_EVT)
+#define BT_EVT_BTU_IPC_BTTRC_EVT (0x0009 | BT_EVT_BTU_IPC_EVT)
+#define BT_EVT_BTU_IPC_BURST_EVT (0x000A | BT_EVT_BTU_IPC_EVT)
+
/* BTIF Events */
#define BT_EVT_BTIF 0xA000
#define BT_EVT_CONTEXT_SWITCH_EVT (0x0001 | BT_EVT_BTIF)
-/* ISO Layer specific */
-#define BT_ISO_HDR_CONTAINS_TS (0x0001)
-#define BT_ISO_HDR_OFFSET_POINTS_DATA (0x0002)
-
/* Define the header of each buffer used in the Bluetooth stack.
*/
typedef struct {
@@ -91,52 +225,35 @@ typedef struct {
uint8_t data[];
} BT_HDR;
-typedef struct {
- uint16_t event;
- uint16_t len;
- uint16_t offset;
- uint16_t layer_specific;
- // Note: Removal of flexible array member with no specified size.
- // This struct may be embedded in any position within other structs
- // and will not trigger various flexible member compilation issues.
-} BT_HDR_RIGID;
-
-#ifdef __cplusplus
-template <typename T>
-T* ToPacketData(BT_HDR* bt_hdr, size_t offset = 0) {
- return reinterpret_cast<T*>(bt_hdr->data + bt_hdr->offset + offset);
-}
-template <typename T>
-const T* ToPacketData(const BT_HDR* bt_hdr, size_t offset = 0) {
- return reinterpret_cast<const T*>(bt_hdr->data + bt_hdr->offset + offset);
-}
-#endif // __cplusplus
-
#define BT_HDR_SIZE (sizeof(BT_HDR))
-enum {
- BT_PSM_SDP = 0x0001,
- BT_PSM_RFCOMM = 0x0003,
- BT_PSM_TCS = 0x0005,
- BT_PSM_CTP = 0x0007,
- BT_PSM_BNEP = 0x000F,
- BT_PSM_HIDC = 0x0011,
- HID_PSM_CONTROL = 0x0011,
- BT_PSM_HIDI = 0x0013,
- HID_PSM_INTERRUPT = 0x0013,
- BT_PSM_UPNP = 0x0015,
- BT_PSM_AVCTP = 0x0017,
- BT_PSM_AVDTP = 0x0019,
- BT_PSM_AVCTP_13 = 0x001B, /* Advanced Control - Browsing */
- BT_PSM_UDI_CP =
- 0x001D, /* Unrestricted Digital Information Profile C-Plane */
- BT_PSM_ATT = 0x001F, /* Attribute Protocol */
- BT_PSM_EATT = 0x0027,
- /* We will not allocate a PSM in the reserved range to 3rd party apps
- */
- BRCM_RESERVED_PSM_START = 0x5AE1,
- BRCM_RESERVED_PSM_END = 0x5AFF,
-};
+#define BT_PSM_SDP 0x0001
+#define BT_PSM_RFCOMM 0x0003
+#define BT_PSM_TCS 0x0005
+#define BT_PSM_CTP 0x0007
+#define BT_PSM_BNEP 0x000F
+#define BT_PSM_HIDC 0x0011
+#define BT_PSM_HIDI 0x0013
+#define BT_PSM_UPNP 0x0015
+#define BT_PSM_AVCTP 0x0017
+#define BT_PSM_AVDTP 0x0019
+#define BT_PSM_AVCTP_13 0x001B /* Advanced Control - Browsing */
+#define BT_PSM_UDI_CP \
+ 0x001D /* Unrestricted Digital Information Profile C-Plane */
+#define BT_PSM_ATT 0x001F /* Attribute Protocol */
+
+/* These macros extract the HCI opcodes from a buffer
+ */
+#define HCI_GET_CMD_HDR_OPCODE(p) \
+ (uint16_t)((*((uint8_t*)((p) + 1) + (p)->offset) + \
+ (*((uint8_t*)((p) + 1) + (p)->offset + 1) << 8)))
+#define HCI_GET_CMD_HDR_PARAM_LEN(p) \
+ (uint8_t)(*((uint8_t*)((p) + 1) + (p)->offset + 2))
+
+#define HCI_GET_EVT_HDR_OPCODE(p) \
+ (uint8_t)(*((uint8_t*)((p) + 1) + (p)->offset))
+#define HCI_GET_EVT_HDR_PARAM_LEN(p) \
+ (uint8_t)(*((uint8_t*)((p) + 1) + (p)->offset + 1))
/*******************************************************************************
* Macros to get and put bytes to and from a stream (Little Endian format).
@@ -301,10 +418,6 @@ enum {
do { \
(p) += 2; \
} while (0)
-#define STREAM_SKIP_UINT32(p) \
- do { \
- (p) += 4; \
- } while (0)
/*******************************************************************************
* Macros to get and put bytes to and from a field (Little Endian format).
@@ -445,9 +558,18 @@ inline void STREAM_TO_BDADDR(RawAddress& a, uint8_t*& p) {
#endif
+#define AMP_KEY_TYPE_GAMP 0
+#define AMP_KEY_TYPE_WIFI 1
+#define AMP_KEY_TYPE_UWB 2
+typedef uint8_t tAMP_KEY_TYPE;
+
#define BT_OCTET8_LEN 8
typedef uint8_t BT_OCTET8[BT_OCTET8_LEN]; /* octet array: size 16 */
+#define AMP_LINK_KEY_LEN 32
+typedef uint8_t
+ AMP_LINK_KEY[AMP_LINK_KEY_LEN]; /* Dedicated AMP and GAMP Link Keys */
+
/* Some C files include this header file */
#ifdef __cplusplus
@@ -469,37 +591,27 @@ inline bool is_sample_ltk(const Octet16& ltk) { return ltk == SAMPLE_LTK; }
#define PIN_CODE_LEN 16
typedef uint8_t PIN_CODE[PIN_CODE_LEN]; /* Pin Code (upto 128 bits) MSB is 0 */
+typedef uint8_t* PIN_CODE_PTR; /* Pointer to Pin Code */
#define BT_OCTET32_LEN 32
typedef uint8_t BT_OCTET32[BT_OCTET32_LEN]; /* octet array: size 32 */
#define DEV_CLASS_LEN 3
typedef uint8_t DEV_CLASS[DEV_CLASS_LEN]; /* Device class */
+typedef uint8_t* DEV_CLASS_PTR; /* Pointer to Device class */
#define EXT_INQ_RESP_LEN 3
typedef uint8_t EXT_INQ_RESP[EXT_INQ_RESP_LEN]; /* Extended Inquiry Response */
+typedef uint8_t* EXT_INQ_RESP_PTR; /* Pointer to Extended Inquiry Response */
#define BD_NAME_LEN 248
typedef uint8_t BD_NAME[BD_NAME_LEN + 1]; /* Device name */
+typedef uint8_t* BD_NAME_PTR; /* Pointer to Device name */
#define BD_FEATURES_LEN 8
typedef uint8_t
BD_FEATURES[BD_FEATURES_LEN]; /* LMP features supported by device */
-#ifdef __cplusplus
-// Bit order [0]:0-7 [1]:8-15 ... [7]:56-63
-inline std::string bd_features_text(const BD_FEATURES& features) {
- uint8_t len = BD_FEATURES_LEN;
- char buf[255];
- char* pbuf = buf;
- const uint8_t* b = features;
- while (len--) {
- pbuf += sprintf(pbuf, "0x%02x ", *b++);
- }
- return std::string(buf);
-}
-#endif // __cplusplus
-
#define BT_EVENT_MASK_LEN 8
typedef uint8_t BT_EVENT_MASK[BT_EVENT_MASK_LEN]; /* Event Mask */
@@ -507,9 +619,54 @@ typedef uint8_t BT_EVENT_MASK[BT_EVENT_MASK_LEN]; /* Event Mask */
typedef uint8_t LAP[LAP_LEN]; /* IAC as passed to Inquiry (LAP) */
typedef uint8_t INQ_LAP[LAP_LEN]; /* IAC as passed to Inquiry (LAP) */
+#define RAND_NUM_LEN 16
+typedef uint8_t RAND_NUM[RAND_NUM_LEN];
+
+#define ACO_LEN 12
+typedef uint8_t ACO[ACO_LEN]; /* Authenticated ciphering offset */
+
#define COF_LEN 12
typedef uint8_t COF[COF_LEN]; /* ciphering offset number */
+typedef struct {
+ uint8_t qos_flags; /* TBD */
+ uint8_t service_type; /* see below */
+ uint32_t token_rate; /* bytes/second */
+ uint32_t token_bucket_size; /* bytes */
+ uint32_t peak_bandwidth; /* bytes/second */
+ uint32_t latency; /* microseconds */
+ uint32_t delay_variation; /* microseconds */
+} FLOW_SPEC;
+
+/* Values for service_type */
+#define SVC_TYPE_NO_TRAFFIC 0
+#define SVC_TYPE_BEST_EFFORT 1
+#define SVC_TYPE_GUARANTEED 2
+
+/* Service class of the CoD */
+#define SERV_CLASS_NETWORKING (1 << 1)
+#define SERV_CLASS_RENDERING (1 << 2)
+#define SERV_CLASS_CAPTURING (1 << 3)
+#define SERV_CLASS_OBJECT_TRANSFER (1 << 4)
+#define SERV_CLASS_OBJECT_AUDIO (1 << 5)
+#define SERV_CLASS_OBJECT_TELEPHONY (1 << 6)
+#define SERV_CLASS_OBJECT_INFORMATION (1 << 7)
+
+/* Second byte */
+#define SERV_CLASS_LIMITED_DISC_MODE (0x20)
+
+/* Field size definitions. Note that byte lengths are rounded up. */
+#define ACCESS_CODE_BIT_LEN 72
+#define ACCESS_CODE_BYTE_LEN 9
+#define SHORTENED_ACCESS_CODE_BIT_LEN 68
+
+typedef uint8_t ACCESS_CODE[ACCESS_CODE_BYTE_LEN];
+
+#define SYNTH_TX 1 /* want synth code to TRANSMIT at this freq */
+#define SYNTH_RX 2 /* want synth code to RECEIVE at this freq */
+
+#define SYNC_REPS 1 /* repeats of sync word transmitted to start of burst */
+
#define BT_1SEC_TIMEOUT_MS (1 * 1000) /* 1 second */
#define BT_EIR_FLAGS_TYPE 0x01
@@ -532,27 +689,258 @@ typedef uint8_t COF[COF_LEN]; /* ciphering offset number */
#define BT_EIR_SERVICE_DATA_128BITS_UUID_TYPE 0x21
#define BT_EIR_MANUFACTURER_SPECIFIC_TYPE 0xFF
-/* Device Types
+#define BT_OOB_COD_SIZE 3
+#define BT_OOB_HASH_C_SIZE 16
+#define BT_OOB_RAND_R_SIZE 16
+
+/* Broadcom proprietary UUIDs and reserved PSMs
+ *
+ * The lowest 4 bytes byte of the UUID or GUID depend on the feature. Typically,
+ * the value of those bytes will be the PSM or SCN.
+ */
+#define BRCM_PROPRIETARY_UUID_BASE \
+ 0xDA, 0x23, 0x41, 0x02, 0xA3, 0xBB, 0xC1, 0x71, 0xBA, 0x09, 0x6f, 0x21
+#define BRCM_PROPRIETARY_GUID_BASE \
+ 0xda23, 0x4102, 0xa3, 0xbb, 0xc1, 0x71, 0xba, 0x09, 0x6f, 0x21
+
+/* We will not allocate a PSM in the reserved range to 3rd party apps
+ */
+#define BRCM_RESERVED_PSM_START 0x5AE1
+#define BRCM_RESERVED_PSM_END 0x5AFF
+
+#define BRCM_UTILITY_SERVICE_PSM 0x5AE1
+#define BRCM_MATCHER_PSM 0x5AE3
+
+/* Connection statistics
*/
-enum {
- BT_DEVICE_TYPE_BREDR = (1 << 0),
- BT_DEVICE_TYPE_BLE = (1 << 1),
- BT_DEVICE_TYPE_DUMO = BT_DEVICE_TYPE_BREDR | BT_DEVICE_TYPE_BLE,
+
+/* Structure to hold connection stats */
+#ifndef BT_CONN_STATS_DEFINED
+#define BT_CONN_STATS_DEFINED
+
+/* These bits are used in the bIsConnected field */
+#define BT_CONNECTED_USING_BREDR 1
+#define BT_CONNECTED_USING_AMP 2
+
+typedef struct {
+ uint32_t is_connected;
+ int32_t rssi;
+ uint32_t bytes_sent;
+ uint32_t bytes_rcvd;
+ uint32_t duration;
+} tBT_CONN_STATS;
+
+#endif
+
+/*****************************************************************************
+ * Low Energy definitions
+ *
+ * Address types
+ */
+#define BLE_ADDR_PUBLIC 0x00
+#define BLE_ADDR_RANDOM 0x01
+#define BLE_ADDR_PUBLIC_ID 0x02
+#define BLE_ADDR_RANDOM_ID 0x03
+#define BLE_ADDR_ANONYMOUS 0xFF
+typedef uint8_t tBLE_ADDR_TYPE;
+#define BLE_ADDR_TYPE_MASK (BLE_ADDR_RANDOM | BLE_ADDR_PUBLIC)
+
+#define BT_TRANSPORT_INVALID 0
+#define BT_TRANSPORT_BR_EDR 1
+#define BT_TRANSPORT_LE 2
+typedef uint8_t tBT_TRANSPORT;
+
+#define PHY_LE_1M_MASK 1
+#define PHY_LE_2M_MASK 2
+#define PHY_LE_CODED_MASK 4
+
+#define BLE_ADDR_IS_STATIC(x) (((x)[0] & 0xC0) == 0xC0)
+
+#ifdef __cplusplus
+struct tBLE_BD_ADDR {
+ tBLE_ADDR_TYPE type;
+ RawAddress bda;
};
+#endif
+
+/* Device Types
+ */
+#define BT_DEVICE_TYPE_BREDR 0x01
+#define BT_DEVICE_TYPE_BLE 0x02
+#define BT_DEVICE_TYPE_DUMO 0x03
typedef uint8_t tBT_DEVICE_TYPE;
-#ifdef __cplusplus
-inline std::string DeviceTypeText(tBT_DEVICE_TYPE type) {
- switch (type) {
- case BT_DEVICE_TYPE_BREDR:
- return std::string("BR_EDR");
- case BT_DEVICE_TYPE_BLE:
- return std::string("BLE");
- case BT_DEVICE_TYPE_DUMO:
- return std::string("DUAL");
- default:
- return std::string("Unknown");
- }
-}
-#endif // __cplusplus
+/*****************************************************************************/
+
+/* Define trace levels */
+#define BT_TRACE_LEVEL_NONE 0 /* No trace messages to be generated */
+#define BT_TRACE_LEVEL_ERROR 1 /* Error condition trace messages */
+#define BT_TRACE_LEVEL_WARNING 2 /* Warning condition trace messages */
+#define BT_TRACE_LEVEL_API 3 /* API traces */
+#define BT_TRACE_LEVEL_EVENT 4 /* Debug messages for events */
+#define BT_TRACE_LEVEL_DEBUG 5 /* Full debug messages */
+#define BT_TRACE_LEVEL_VERBOSE 6 /* Verbose debug messages */
+
+#define MAX_TRACE_LEVEL 6
+
+/* Define New Trace Type Definition */
+/* TRACE_CTRL_TYPE 0x^^000000*/
+#define TRACE_CTRL_MASK 0xff000000
+#define TRACE_GET_CTRL(x) ((((uint32_t)(x)) & TRACE_CTRL_MASK) >> 24)
+
+#define TRACE_CTRL_GENERAL 0x00000000
+#define TRACE_CTRL_STR_RESOURCE 0x01000000
+#define TRACE_CTRL_SEQ_FLOW 0x02000000
+#define TRACE_CTRL_MAX_NUM 3
+
+/* LAYER SPECIFIC 0x00^^0000*/
+#define TRACE_LAYER_MASK 0x00ff0000
+#define TRACE_GET_LAYER(x) ((((uint32_t)(x)) & TRACE_LAYER_MASK) >> 16)
+
+#define TRACE_LAYER_NONE 0x00000000
+#define TRACE_LAYER_USB 0x00010000
+#define TRACE_LAYER_SERIAL 0x00020000
+#define TRACE_LAYER_SOCKET 0x00030000
+#define TRACE_LAYER_RS232 0x00040000
+#define TRACE_LAYER_TRANS_MAX_NUM 5
+#define TRACE_LAYER_TRANS_ALL 0x007f0000
+#define TRACE_LAYER_LC 0x00050000
+#define TRACE_LAYER_LM 0x00060000
+#define TRACE_LAYER_HCI 0x00070000
+#define TRACE_LAYER_L2CAP 0x00080000
+#define TRACE_LAYER_RFCOMM 0x00090000
+#define TRACE_LAYER_SDP 0x000a0000
+#define TRACE_LAYER_TCS 0x000b0000
+#define TRACE_LAYER_OBEX 0x000c0000
+#define TRACE_LAYER_BTM 0x000d0000
+#define TRACE_LAYER_ICP 0x00110000
+#define TRACE_LAYER_HSP2 0x00120000
+#define TRACE_LAYER_SPP 0x00130000
+#define TRACE_LAYER_CTP 0x00140000
+#define TRACE_LAYER_BPP 0x00150000
+#define TRACE_LAYER_HCRP 0x00160000
+#define TRACE_LAYER_FTP 0x00170000
+#define TRACE_LAYER_OPP 0x00180000
+#define TRACE_LAYER_BTU 0x00190000
+#define TRACE_LAYER_GKI 0x001a0000 /* OBSOLETED */
+#define TRACE_LAYER_BNEP 0x001b0000
+#define TRACE_LAYER_PAN 0x001c0000
+#define TRACE_LAYER_HFP 0x001d0000
+#define TRACE_LAYER_HID 0x001e0000
+#define TRACE_LAYER_BIP 0x001f0000
+#define TRACE_LAYER_AVP 0x00200000
+#define TRACE_LAYER_A2DP 0x00210000
+#define TRACE_LAYER_SAP 0x00220000
+#define TRACE_LAYER_AMP 0x00230000
+#define TRACE_LAYER_MCA 0x00240000 /* OBSOLETED */
+#define TRACE_LAYER_ATT 0x00250000
+#define TRACE_LAYER_SMP 0x00260000
+#define TRACE_LAYER_NFC 0x00270000
+#define TRACE_LAYER_NCI 0x00280000
+#define TRACE_LAYER_LLCP 0x00290000
+#define TRACE_LAYER_NDEF 0x002a0000
+#define TRACE_LAYER_RW 0x002b0000
+#define TRACE_LAYER_CE 0x002c0000
+#define TRACE_LAYER_P2P 0x002d0000
+#define TRACE_LAYER_SNEP 0x002e0000
+#define TRACE_LAYER_CHO 0x002f0000
+#define TRACE_LAYER_NFA 0x00300000
+
+#define TRACE_LAYER_MAX_NUM 0x0031
+
+/* TRACE_ORIGINATOR 0x0000^^00*/
+#define TRACE_ORG_MASK 0x0000ff00
+#define TRACE_GET_ORG(x) ((((uint32_t)(x)) & TRACE_ORG_MASK) >> 8)
+
+#define TRACE_ORG_STACK 0x00000000
+#define TRACE_ORG_HCI_TRANS 0x00000100
+#define TRACE_ORG_PROTO_DISP 0x00000200
+#define TRACE_ORG_RPC 0x00000300
+#define TRACE_ORG_GKI 0x00000400 /* OBSOLETED */
+#define TRACE_ORG_APPL 0x00000500
+#define TRACE_ORG_SCR_WRAPPER 0x00000600
+#define TRACE_ORG_SCR_ENGINE 0x00000700
+#define TRACE_ORG_USER_SCR 0x00000800
+#define TRACE_ORG_TESTER 0x00000900
+#define TRACE_ORG_MAX_NUM 10 /* 32-bit mask; must be < 32 */
+#define TRACE_LITE_ORG_MAX_NUM 6
+#define TRACE_ORG_ALL 0x03ff
+#define TRACE_ORG_RPC_TRANS 0x04
+
+#define TRACE_ORG_REG 0x00000909
+#define TRACE_ORG_REG_SUCCESS 0x0000090a
+
+/* TRACE_TYPE 0x000000^^*/
+#define TRACE_TYPE_MASK 0x000000ff
+#define TRACE_GET_TYPE(x) (((uint32_t)(x)) & TRACE_TYPE_MASK)
+
+#define TRACE_TYPE_ERROR 0x00000000
+#define TRACE_TYPE_WARNING 0x00000001
+#define TRACE_TYPE_API 0x00000002
+#define TRACE_TYPE_EVENT 0x00000003
+#define TRACE_TYPE_DEBUG 0x00000004
+#define TRACE_TYPE_STACK_ONLY_MAX TRACE_TYPE_DEBUG
+#define TRACE_TYPE_TX 0x00000005
+#define TRACE_TYPE_RX 0x00000006
+#define TRACE_TYPE_DEBUG_ASSERT 0x00000007
+#define TRACE_TYPE_GENERIC 0x00000008
+#define TRACE_TYPE_REG 0x00000009
+#define TRACE_TYPE_REG_SUCCESS 0x0000000a
+#define TRACE_TYPE_CMD_TX 0x0000000b
+#define TRACE_TYPE_EVT_TX 0x0000000c
+#define TRACE_TYPE_ACL_TX 0x0000000d
+#define TRACE_TYPE_CMD_RX 0x0000000e
+#define TRACE_TYPE_EVT_RX 0x0000000f
+#define TRACE_TYPE_ACL_RX 0x00000010
+#define TRACE_TYPE_TARGET_TRACE 0x00000011
+#define TRACE_TYPE_SCO_TX 0x00000012
+#define TRACE_TYPE_SCO_RX 0x00000013
+
+#define TRACE_TYPE_MAX_NUM 20
+#define TRACE_TYPE_ALL 0xffff
+
+/* Define color for script type */
+#define SCR_COLOR_DEFAULT 0
+#define SCR_COLOR_TYPE_COMMENT 1
+#define SCR_COLOR_TYPE_COMMAND 2
+#define SCR_COLOR_TYPE_EVENT 3
+#define SCR_COLOR_TYPE_SELECT 4
+
+/* Define protocol trace flag values */
+#define SCR_PROTO_TRACE_HCI_SUMMARY 0x00000001
+#define SCR_PROTO_TRACE_HCI_DATA 0x00000002
+#define SCR_PROTO_TRACE_L2CAP 0x00000004
+#define SCR_PROTO_TRACE_RFCOMM 0x00000008
+#define SCR_PROTO_TRACE_SDP 0x00000010
+#define SCR_PROTO_TRACE_TCS 0x00000020
+#define SCR_PROTO_TRACE_OBEX 0x00000040
+#define SCR_PROTO_TRACE_OAPP 0x00000080 /* OBEX Application Profile */
+#define SCR_PROTO_TRACE_AMP 0x00000100
+#define SCR_PROTO_TRACE_BNEP 0x00000200
+#define SCR_PROTO_TRACE_AVP 0x00000400
+#define SCR_PROTO_TRACE_MCA 0x00000800
+#define SCR_PROTO_TRACE_ATT 0x00001000
+#define SCR_PROTO_TRACE_SMP 0x00002000
+#define SCR_PROTO_TRACE_NCI 0x00004000
+#define SCR_PROTO_TRACE_LLCP 0x00008000
+#define SCR_PROTO_TRACE_NDEF 0x00010000
+#define SCR_PROTO_TRACE_RW 0x00020000
+#define SCR_PROTO_TRACE_CE 0x00040000
+#define SCR_PROTO_TRACE_SNEP 0x00080000
+#define SCR_PROTO_TRACE_CHO 0x00100000
+#define SCR_PROTO_TRACE_ALL 0x001fffff
+#define SCR_PROTO_TRACE_HCI_LOGGING_VSE \
+ 0x0800 /* Brcm vs event for logmsg and protocol traces */
+
+#define MAX_SCRIPT_TYPE 5
+
+#define TCS_PSM_INTERCOM 5
+#define TCS_PSM_CORDLESS 7
+#define BT_PSM_BNEP 0x000F
+/* Define PSMs HID uses */
+#define HID_PSM_CONTROL 0x0011
+#define HID_PSM_INTERRUPT 0x0013
+
+/* Define a function for logging */
+typedef void(BT_LOG_FUNC)(int trace_type, const char* fmt_str, ...);
#endif
diff --git a/stack/include/btm_api.h b/stack/include/btm_api.h
index eaac9c904..d0abee2a1 100644
--- a/stack/include/btm_api.h
+++ b/stack/include/btm_api.h
@@ -1,4 +1,5 @@
-/*
+/******************************************************************************
+ *
* Copyright 1999-2012 Broadcom Corporation
*
* Licensed under the Apache License, Version 2.0 (the "License");
@@ -24,18 +25,14 @@
#ifndef BTM_API_H
#define BTM_API_H
-#include <cstdint>
+#include "bt_target.h"
+#include "device/include/esco_parameters.h"
+#include "hcidefs.h"
+#include "sdp_api.h"
-#include "stack/btm/neighbor_inquiry.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/btm_status.h"
-#include "stack/include/sco_client_callbacks.h"
-#include "stack/include/sdp_api.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
+#include "smp_api.h"
-void btm_init();
-void btm_free();
+#include "btm_api_types.h"
/*****************************************************************************
* DEVICE CONTROL and COMMON
@@ -49,7 +46,18 @@ void btm_free();
* DEVICE CONTROL and COMMON FUNCTIONS
****************************************************************************/
-void BTM_reset_complete();
+/*******************************************************************************
+ *
+ * Function BTM_DeviceReset
+ *
+ * Description This function is called to reset the controller. The
+ * Callback function if provided is called when startup of the
+ * device has completed.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_DeviceReset(tBTM_CMPL_CB* p_cb);
/*******************************************************************************
*
@@ -60,7 +68,7 @@ void BTM_reset_complete();
* Returns true if device is up, else false
*
******************************************************************************/
-bool BTM_IsDeviceUp(void);
+extern bool BTM_IsDeviceUp(void);
/*******************************************************************************
*
@@ -71,7 +79,7 @@ bool BTM_IsDeviceUp(void);
* Returns BTM_CMD_STARTED if successful, otherwise an error
*
******************************************************************************/
-tBTM_STATUS BTM_SetLocalDeviceName(char* p_name);
+extern tBTM_STATUS BTM_SetLocalDeviceName(char* p_name);
/*******************************************************************************
*
@@ -82,7 +90,7 @@ tBTM_STATUS BTM_SetLocalDeviceName(char* p_name);
* Returns BTM_SUCCESS if successful, otherwise an error
*
******************************************************************************/
-tBTM_STATUS BTM_SetDeviceClass(DEV_CLASS dev_class);
+extern tBTM_STATUS BTM_SetDeviceClass(DEV_CLASS dev_class);
/*******************************************************************************
*
@@ -97,7 +105,7 @@ tBTM_STATUS BTM_SetDeviceClass(DEV_CLASS dev_class);
* is returned and p_name is set to NULL
*
******************************************************************************/
-tBTM_STATUS BTM_ReadLocalDeviceName(char** p_name);
+extern tBTM_STATUS BTM_ReadLocalDeviceName(char** p_name);
/*******************************************************************************
*
@@ -109,7 +117,7 @@ tBTM_STATUS BTM_ReadLocalDeviceName(char** p_name);
* Returns BTM_CMD_STARTED if successful, otherwise an error
*
******************************************************************************/
-tBTM_STATUS BTM_ReadLocalDeviceNameFromController(
+extern tBTM_STATUS BTM_ReadLocalDeviceNameFromController(
tBTM_CMPL_CB* p_rln_cmpl_cback);
/*******************************************************************************
@@ -121,7 +129,32 @@ tBTM_STATUS BTM_ReadLocalDeviceNameFromController(
* Returns pointer to the device class
*
******************************************************************************/
-uint8_t* BTM_ReadDeviceClass(void);
+extern uint8_t* BTM_ReadDeviceClass(void);
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadLocalFeatures
+ *
+ * Description This function is called to read the local features
+ *
+ * Returns pointer to the local features string
+ *
+ ******************************************************************************/
+extern uint8_t* BTM_ReadLocalFeatures(void);
+
+/*******************************************************************************
+ *
+ * Function BTM_RegisterForDeviceStatusNotif
+ *
+ * Description This function is called to register for device status
+ * change notifications.
+ *
+ * Returns pointer to previous caller's callback function or NULL if
+ * first registration.
+ *
+ ******************************************************************************/
+extern tBTM_DEV_STATUS_CB* BTM_RegisterForDeviceStatusNotif(
+ tBTM_DEV_STATUS_CB* p_cb);
/*******************************************************************************
*
@@ -138,7 +171,8 @@ uint8_t* BTM_ReadDeviceClass(void);
* registered.
*
******************************************************************************/
-tBTM_STATUS BTM_RegisterForVSEvents(tBTM_VS_EVT_CB* p_cb, bool is_register);
+extern tBTM_STATUS BTM_RegisterForVSEvents(tBTM_VS_EVT_CB* p_cb,
+ bool is_register);
/*******************************************************************************
*
@@ -147,8 +181,9 @@ tBTM_STATUS BTM_RegisterForVSEvents(tBTM_VS_EVT_CB* p_cb, bool is_register);
* Description Send a vendor specific HCI command to the controller.
*
******************************************************************************/
-void BTM_VendorSpecificCommand(uint16_t opcode, uint8_t param_len,
- uint8_t* p_param_buf, tBTM_VSC_CMPL_CB* p_cb);
+extern void BTM_VendorSpecificCommand(uint16_t opcode, uint8_t param_len,
+ uint8_t* p_param_buf,
+ tBTM_VSC_CMPL_CB* p_cb);
/*******************************************************************************
*
@@ -160,7 +195,7 @@ void BTM_VendorSpecificCommand(uint16_t opcode, uint8_t param_len,
* Returns Allocated SCN number or 0 if none.
*
******************************************************************************/
-uint8_t BTM_AllocateSCN(void);
+extern uint8_t BTM_AllocateSCN(void);
/*******************************************************************************
*
@@ -171,7 +206,7 @@ uint8_t BTM_AllocateSCN(void);
* Returns Returns true if server channel was available
*
******************************************************************************/
-bool BTM_TryAllocateSCN(uint8_t scn);
+extern bool BTM_TryAllocateSCN(uint8_t scn);
/*******************************************************************************
*
@@ -182,7 +217,7 @@ bool BTM_TryAllocateSCN(uint8_t scn);
* Returns true if successful, false if SCN is not in use or invalid
*
******************************************************************************/
-bool BTM_FreeSCN(uint8_t scn);
+extern bool BTM_FreeSCN(uint8_t scn);
/*******************************************************************************
*
@@ -194,7 +229,7 @@ bool BTM_FreeSCN(uint8_t scn);
* Returns The new or current trace level
*
******************************************************************************/
-uint8_t BTM_SetTraceLevel(uint8_t new_level);
+extern uint8_t BTM_SetTraceLevel(uint8_t new_level);
/*******************************************************************************
*
@@ -203,7 +238,7 @@ uint8_t BTM_SetTraceLevel(uint8_t new_level);
* Description Send HCI Wite Page Timeout.
*
******************************************************************************/
-void BTM_WritePageTimeout(uint16_t timeout);
+extern void BTM_WritePageTimeout(uint16_t timeout);
/*******************************************************************************
*
@@ -213,7 +248,7 @@ void BTM_WritePageTimeout(uint16_t timeout);
* See hcidefs.h for settings bitmask values.
*
******************************************************************************/
-void BTM_WriteVoiceSettings(uint16_t settings);
+extern void BTM_WriteVoiceSettings(uint16_t settings);
/*******************************************************************************
*
@@ -230,7 +265,7 @@ void BTM_WriteVoiceSettings(uint16_t settings);
*
*
******************************************************************************/
-tBTM_STATUS BTM_EnableTestMode(void);
+extern tBTM_STATUS BTM_EnableTestMode(void);
/*******************************************************************************
* DEVICE DISCOVERY FUNCTIONS - Inquiry, Remote Name, Discovery, Class of Device
@@ -252,7 +287,25 @@ tBTM_STATUS BTM_EnableTestMode(void);
* BTM_WRONG_MODE if the device is not up.
*
******************************************************************************/
-tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode);
+extern tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode, uint16_t window,
+ uint16_t interval);
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadDiscoverability
+ *
+ * Description This function is called to read the current discoverability
+ * mode of the device.
+ *
+ * Output Params: p_window - current inquiry scan duration
+ * p_interval - current inquiry scan interval
+ *
+ * Returns BTM_NON_DISCOVERABLE, BTM_LIMITED_DISCOVERABLE, or
+ * BTM_GENERAL_DISCOVERABLE
+ *
+ ******************************************************************************/
+extern uint16_t BTM_ReadDiscoverability(uint16_t* p_window,
+ uint16_t* p_interval);
/*******************************************************************************
*
@@ -264,6 +317,8 @@ tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode);
* mode - GENERAL or LIMITED inquiry
* duration - length in 1.28 sec intervals (If '0', the
* inquiry is CANCELLED)
+ * max_resps - maximum amount of devices to search for
+ * before ending the inquiry
* filter_cond_type - BTM_CLR_INQUIRY_FILTER,
* BTM_FILTER_COND_DEVICE_CLASS, or
* BTM_FILTER_COND_BD_ADDR
@@ -288,8 +343,9 @@ tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode);
* BTM_WRONG_MODE if the device is not up.
*
******************************************************************************/
-tBTM_STATUS BTM_StartInquiry(tBTM_INQ_RESULTS_CB* p_results_cb,
- tBTM_CMPL_CB* p_cmpl_cb);
+extern tBTM_STATUS BTM_StartInquiry(tBTM_INQ_PARMS* p_inqparms,
+ tBTM_INQ_RESULTS_CB* p_results_cb,
+ tBTM_CMPL_CB* p_cmpl_cb);
/*******************************************************************************
*
@@ -298,10 +354,12 @@ tBTM_STATUS BTM_StartInquiry(tBTM_INQ_RESULTS_CB* p_results_cb,
* Description Return a bit mask of the current inquiry state
*
* Returns BTM_INQUIRY_INACTIVE if inactive (0)
+ * BTM_LIMITED_INQUIRY_ACTIVE if a limted inquiry is active
* BTM_GENERAL_INQUIRY_ACTIVE if a general inquiry is active
+ * BTM_PERIODIC_INQUIRY_ACTIVE if a periodic inquiry is active
*
******************************************************************************/
-uint16_t BTM_IsInquiryActive(void);
+extern uint16_t BTM_IsInquiryActive(void);
/*******************************************************************************
*
@@ -309,8 +367,26 @@ uint16_t BTM_IsInquiryActive(void);
*
* Description This function cancels an inquiry if active
*
+ * Returns BTM_SUCCESS if successful
+ * BTM_NO_RESOURCES if could not allocate a message buffer
+ * BTM_WRONG_MODE if the device is not up.
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_CancelInquiry(void);
+
+/*******************************************************************************
+ *
+ * Function BTM_CancelPeriodicInquiry
+ *
+ * Description This function cancels a periodic inquiry
+ *
+ * Returns
+ * BTM_NO_RESOURCES if could not allocate a message buffer
+ * BTM_SUCCESS - if cancelling the periodic inquiry
+ * BTM_WRONG_MODE if the device is not up.
+ *
******************************************************************************/
-void BTM_CancelInquiry(void);
+extern tBTM_STATUS BTM_CancelPeriodicInquiry(void);
/*******************************************************************************
*
@@ -326,7 +402,23 @@ void BTM_CancelInquiry(void);
* BTM_WRONG_MODE if the device is not up.
*
******************************************************************************/
-tBTM_STATUS BTM_SetConnectability(uint16_t page_mode);
+extern tBTM_STATUS BTM_SetConnectability(uint16_t page_mode, uint16_t window,
+ uint16_t interval);
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadConnectability
+ *
+ * Description This function is called to read the current discoverability
+ * mode of the device.
+ * Output Params p_window - current page scan duration
+ * p_interval - current time between page scans
+ *
+ * Returns BTM_NON_CONNECTABLE or BTM_CONNECTABLE
+ *
+ ******************************************************************************/
+extern uint16_t BTM_ReadConnectability(uint16_t* p_window,
+ uint16_t* p_interval);
/*******************************************************************************
*
@@ -344,11 +436,40 @@ tBTM_STATUS BTM_SetConnectability(uint16_t page_mode);
* BTM_WRONG_MODE if the device is not up.
*
******************************************************************************/
-tBTM_STATUS BTM_SetInquiryMode(uint8_t mode);
+extern tBTM_STATUS BTM_SetInquiryMode(uint8_t mode);
-void BTM_EnableInterlacedInquiryScan();
+/*******************************************************************************
+ *
+ * Function BTM_SetInquiryScanType
+ *
+ * Description This function is called to set the iquiry scan-type to
+ * standard or interlaced.
+ *
+ * Input Params: BTM_SCAN_TYPE_STANDARD or BTM_SCAN_TYPE_INTERLACED
+ *
+ * Returns BTM_SUCCESS if successful
+ * BTM_MODE_UNSUPPORTED if not a 1.2 device
+ * BTM_WRONG_MODE if the device is not up.
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_SetInquiryScanType(uint16_t scan_type);
-void BTM_EnableInterlacedPageScan();
+/*******************************************************************************
+ *
+ * Function BTM_SetPageScanType
+ *
+ * Description This function is called to set the page scan-type to
+ * standard or interlaced.
+ *
+ * Input Params: BTM_SCAN_TYPE_STANDARD or BTM_SCAN_TYPE_INTERLACED
+ *
+ * Returns BTM_SUCCESS if successful
+ * BTM_MODE_UNSUPPORTED if not a 1.2 device
+ * BTM_WRONG_MODE if the device is not up.
+ *
+ ******************************************************************************/
+
+extern tBTM_STATUS BTM_SetPageScanType(uint16_t scan_type);
/*******************************************************************************
*
@@ -374,9 +495,9 @@ void BTM_EnableInterlacedPageScan();
* BTM_WRONG_MODE if the device is not up.
*
******************************************************************************/
-tBTM_STATUS BTM_ReadRemoteDeviceName(const RawAddress& remote_bda,
- tBTM_CMPL_CB* p_cb,
- tBT_TRANSPORT transport);
+extern tBTM_STATUS BTM_ReadRemoteDeviceName(const RawAddress& remote_bda,
+ tBTM_CMPL_CB* p_cb,
+ tBT_TRANSPORT transport);
/*******************************************************************************
*
@@ -395,7 +516,7 @@ tBTM_STATUS BTM_ReadRemoteDeviceName(const RawAddress& remote_bda,
* BTM_WRONG_MODE if there is no active remote name request.
*
******************************************************************************/
-tBTM_STATUS BTM_CancelRemoteDeviceName(void);
+extern tBTM_STATUS BTM_CancelRemoteDeviceName(void);
/*******************************************************************************
*
@@ -403,11 +524,13 @@ tBTM_STATUS BTM_CancelRemoteDeviceName(void);
*
* Description This function is called to read a remote device's version
*
- * Returns true if data valid, false otherwise
+ * Returns BTM_SUCCESS if successful, otherwise an error
*
******************************************************************************/
-bool BTM_ReadRemoteVersion(const RawAddress& addr, uint8_t* lmp_version,
- uint16_t* manufacturer, uint16_t* lmp_sub_version);
+extern tBTM_STATUS BTM_ReadRemoteVersion(const RawAddress& addr,
+ uint8_t* lmp_version,
+ uint16_t* manufacturer,
+ uint16_t* lmp_sub_version);
/*******************************************************************************
*
@@ -416,12 +539,13 @@ bool BTM_ReadRemoteVersion(const RawAddress& addr, uint8_t* lmp_version,
* Description This function is called to read a remote device's
* supported features mask (features mask located at page 0)
*
+ * Note: The size of device features mask page is
+ * BTM_FEATURE_BYTES_PER_PAGE bytes.
+ *
* Returns pointer to the remote supported features mask
- * The size of device features mask page is
- * HCI_FEATURE_BYTES_PER_PAGE bytes.
*
******************************************************************************/
-uint8_t* BTM_ReadRemoteFeatures(const RawAddress& addr);
+extern uint8_t* BTM_ReadRemoteFeatures(const RawAddress& addr);
/*******************************************************************************
*
@@ -435,7 +559,7 @@ uint8_t* BTM_ReadRemoteFeatures(const RawAddress& addr);
* Returns pointer to entry, or NULL if not found
*
******************************************************************************/
-tBTM_INQ_INFO* BTM_InqDbRead(const RawAddress& p_bda);
+extern tBTM_INQ_INFO* BTM_InqDbRead(const RawAddress& p_bda);
/*******************************************************************************
*
@@ -449,7 +573,7 @@ tBTM_INQ_INFO* BTM_InqDbRead(const RawAddress& p_bda);
* Returns pointer to first in-use entry, or NULL if DB is empty
*
******************************************************************************/
-tBTM_INQ_INFO* BTM_InqDbFirst(void);
+extern tBTM_INQ_INFO* BTM_InqDbFirst(void);
/*******************************************************************************
*
@@ -462,7 +586,7 @@ tBTM_INQ_INFO* BTM_InqDbFirst(void);
* Returns pointer to next in-use entry, or NULL if no more found.
*
******************************************************************************/
-tBTM_INQ_INFO* BTM_InqDbNext(tBTM_INQ_INFO* p_cur);
+extern tBTM_INQ_INFO* BTM_InqDbNext(tBTM_INQ_INFO* p_cur);
/*******************************************************************************
*
@@ -478,7 +602,216 @@ tBTM_INQ_INFO* BTM_InqDbNext(tBTM_INQ_INFO* p_cur);
* is active, otherwise BTM_SUCCESS
*
******************************************************************************/
-tBTM_STATUS BTM_ClearInqDb(const RawAddress* p_bda);
+extern tBTM_STATUS BTM_ClearInqDb(const RawAddress* p_bda);
+
+/*****************************************************************************
+ * ACL CHANNEL MANAGEMENT FUNCTIONS
+ ****************************************************************************/
+/*******************************************************************************
+ *
+ * Function BTM_SetLinkPolicy
+ *
+ * Description Create and send HCI "Write Policy Set" command
+ *
+ * Returns BTM_CMD_STARTED if successfully initiated, otherwise error
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_SetLinkPolicy(const RawAddress& remote_bda,
+ uint16_t* settings);
+
+/*******************************************************************************
+ *
+ * Function BTM_SetDefaultLinkPolicy
+ *
+ * Description Set the default value for HCI "Write Policy Set" command
+ * to use when an ACL link is created.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_SetDefaultLinkPolicy(uint16_t settings);
+
+/*******************************************************************************
+ *
+ * Function BTM_SetDefaultLinkSuperTout
+ *
+ * Description Set the default value for HCI "Write Link Supervision
+ * Timeout" command to use when an ACL link is created.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_SetDefaultLinkSuperTout(uint16_t timeout);
+
+/*******************************************************************************
+ *
+ * Function BTM_SetLinkSuperTout
+ *
+ * Description Create and send HCI "Write Link Supervision Timeout" command
+ *
+ * Returns BTM_CMD_STARTED if successfully initiated, otherwise error
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_SetLinkSuperTout(const RawAddress& remote_bda,
+ uint16_t timeout);
+/*******************************************************************************
+ *
+ * Function BTM_GetLinkSuperTout
+ *
+ * Description Read the link supervision timeout value of the connection
+ *
+ * Returns status of the operation
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_GetLinkSuperTout(const RawAddress& remote_bda,
+ uint16_t* p_timeout);
+
+/*******************************************************************************
+ *
+ * Function BTM_IsAclConnectionUp
+ *
+ * Description This function is called to check if an ACL connection exists
+ * to a specific remote BD Address.
+ *
+ * Returns true if connection is up, else false.
+ *
+ ******************************************************************************/
+extern bool BTM_IsAclConnectionUp(const RawAddress& remote_bda,
+ tBT_TRANSPORT transport);
+
+/*******************************************************************************
+ *
+ * Function BTM_GetRole
+ *
+ * Description This function is called to get the role of the local device
+ * for the ACL connection with the specified remote device
+ *
+ * Returns BTM_SUCCESS if connection exists.
+ * BTM_UNKNOWN_ADDR if no active link with bd addr specified
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_GetRole(const RawAddress& remote_bd_addr,
+ uint8_t* p_role);
+
+/*******************************************************************************
+ *
+ * Function BTM_SwitchRole
+ *
+ * Description This function is called to switch role between master and
+ * slave. If role is already set it will do nothing. If the
+ * command was initiated, the callback function is called upon
+ * completion.
+ *
+ * Returns BTM_SUCCESS if already in specified role.
+ * BTM_CMD_STARTED if command issued to controller.
+ * BTM_NO_RESOURCES if memory couldn't be allocated to issue
+ * the command
+ * BTM_UNKNOWN_ADDR if no active link with bd addr specified
+ * BTM_MODE_UNSUPPORTED if the local device does not support
+ * role switching
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_SwitchRole(const RawAddress& remote_bd_addr,
+ uint8_t new_role, tBTM_CMPL_CB* p_cb);
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadRSSI
+ *
+ * Description This function is called to read the link policy settings.
+ * The address of link policy results are returned in the
+ * callback. (tBTM_RSSI_RESULT)
+ *
+ * Returns BTM_CMD_STARTED if command issued to controller.
+ * BTM_NO_RESOURCES if memory couldn't be allocated to issue
+ * the command
+ * BTM_UNKNOWN_ADDR if no active link with bd addr specified
+ * BTM_BUSY if command is already in progress
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_ReadRSSI(const RawAddress& remote_bda,
+ tBTM_CMPL_CB* p_cb);
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadFailedContactCounter
+ *
+ * Description This function is called to read the failed contact counter.
+ * The result is returned in the callback.
+ * (tBTM_FAILED_CONTACT_COUNTER_RESULT)
+ *
+ * Returns BTM_CMD_STARTED if command issued to controller.
+ * BTM_NO_RESOURCES if memory couldn't be allocated to issue
+ * the command
+ * BTM_UNKNOWN_ADDR if no active link with bd addr specified
+ * BTM_BUSY if command is already in progress
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_ReadFailedContactCounter(const RawAddress& remote_bda,
+ tBTM_CMPL_CB* p_cb);
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadAutomaticFlushTimeout
+ *
+ * Description This function is called to read the automatic flush timeout.
+ * The result is returned in the callback.
+ * (tBTM_AUTOMATIC_FLUSH_TIMEOUT_RESULT)
+ *
+ * Returns BTM_CMD_STARTED if command issued to controller.
+ * BTM_NO_RESOURCES if memory couldn't be allocated to issue
+ * the command
+ * BTM_UNKNOWN_ADDR if no active link with bd addr specified
+ * BTM_BUSY if command is already in progress
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_ReadAutomaticFlushTimeout(const RawAddress& remote_bda,
+ tBTM_CMPL_CB* p_cb);
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadTxPower
+ *
+ * Description This function is called to read the current connection
+ * TX power of the connection. The TX power level results
+ * are returned in the callback.
+ * (tBTM_RSSI_RESULT)
+ *
+ * Returns BTM_CMD_STARTED if command issued to controller.
+ * BTM_NO_RESOURCES if memory couldn't be allocated to issue
+ * the command
+ * BTM_UNKNOWN_ADDR if no active link with bd addr specified
+ * BTM_BUSY if command is already in progress
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_ReadTxPower(const RawAddress& remote_bda,
+ tBT_TRANSPORT transport, tBTM_CMPL_CB* p_cb);
+
+/*******************************************************************************
+ *
+ * Function BTM_RegBusyLevelNotif
+ *
+ * Description This function is called to register a callback to receive
+ * busy level change events.
+ *
+ * Returns BTM_SUCCESS if successfully registered, otherwise error
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_RegBusyLevelNotif(tBTM_BL_CHANGE_CB* p_cb,
+ uint8_t* p_level,
+ tBTM_BL_EVENT_MASK evt_mask);
+
+/*******************************************************************************
+ *
+ * Function BTM_GetNumAclLinks
+ *
+ * Description This function is called to count the number of
+ * ACL links that are active.
+ *
+ * Returns uint16_t Number of active ACL links
+ *
+ ******************************************************************************/
+extern uint16_t BTM_GetNumAclLinks(void);
/*****************************************************************************
* (e)SCO CHANNEL MANAGEMENT FUNCTIONS
@@ -500,9 +833,10 @@ tBTM_STATUS BTM_ClearInqDb(const RawAddress* p_bda);
* with the sco index used for the connection.
*
******************************************************************************/
-tBTM_STATUS BTM_CreateSco(const RawAddress* remote_bda, bool is_orig,
- uint16_t pkt_types, uint16_t* p_sco_inx,
- tBTM_SCO_CB* p_conn_cb, tBTM_SCO_CB* p_disc_cb);
+extern tBTM_STATUS BTM_CreateSco(const RawAddress* remote_bda, bool is_orig,
+ uint16_t pkt_types, uint16_t* p_sco_inx,
+ tBTM_SCO_CB* p_conn_cb,
+ tBTM_SCO_CB* p_disc_cb);
/*******************************************************************************
*
@@ -513,8 +847,7 @@ tBTM_STATUS BTM_CreateSco(const RawAddress* remote_bda, bool is_orig,
* Returns BTM_CMD_STARTED if successfully initiated, otherwise error
*
******************************************************************************/
-tBTM_STATUS BTM_RemoveSco(uint16_t sco_inx);
-void BTM_RemoveSco(const RawAddress& bda);
+extern tBTM_STATUS BTM_RemoveSco(uint16_t sco_inx);
/*******************************************************************************
*
@@ -526,7 +859,7 @@ void BTM_RemoveSco(const RawAddress& bda);
* Returns pointer to BD address or NULL if not known
*
******************************************************************************/
-const RawAddress* BTM_ReadScoBdAddr(uint16_t sco_inx);
+extern const RawAddress* BTM_ReadScoBdAddr(uint16_t sco_inx);
/*******************************************************************************
*
@@ -541,7 +874,7 @@ const RawAddress* BTM_ReadScoBdAddr(uint16_t sco_inx);
* BTM_BUSY if there are one or more active (e)SCO links.
*
******************************************************************************/
-tBTM_STATUS BTM_SetEScoMode(enh_esco_params_t* p_parms);
+extern tBTM_STATUS BTM_SetEScoMode(enh_esco_params_t* p_parms);
/*******************************************************************************
*
@@ -556,7 +889,8 @@ tBTM_STATUS BTM_SetEScoMode(enh_esco_params_t* p_parms);
* BTM_ILLEGAL_VALUE if there is an illegal sco_inx
*
******************************************************************************/
-tBTM_STATUS BTM_RegForEScoEvts(uint16_t sco_inx, tBTM_ESCO_CBACK* p_esco_cback);
+extern tBTM_STATUS BTM_RegForEScoEvts(uint16_t sco_inx,
+ tBTM_ESCO_CBACK* p_esco_cback);
/*******************************************************************************
*
@@ -577,8 +911,8 @@ tBTM_STATUS BTM_RegForEScoEvts(uint16_t sco_inx, tBTM_ESCO_CBACK* p_esco_cback);
* 1.2 specification.
*
******************************************************************************/
-tBTM_STATUS BTM_ChangeEScoLinkParms(uint16_t sco_inx,
- tBTM_CHG_ESCO_PARAMS* p_parms);
+extern tBTM_STATUS BTM_ChangeEScoLinkParms(uint16_t sco_inx,
+ tBTM_CHG_ESCO_PARAMS* p_parms);
/*******************************************************************************
*
@@ -598,8 +932,8 @@ tBTM_STATUS BTM_ChangeEScoLinkParms(uint16_t sco_inx,
* Returns void
*
******************************************************************************/
-void BTM_EScoConnRsp(uint16_t sco_inx, uint8_t hci_status,
- enh_esco_params_t* p_parms);
+extern void BTM_EScoConnRsp(uint16_t sco_inx, uint8_t hci_status,
+ enh_esco_params_t* p_parms);
/*******************************************************************************
*
@@ -610,11 +944,165 @@ void BTM_EScoConnRsp(uint16_t sco_inx, uint8_t hci_status,
* Returns uint8_t
*
******************************************************************************/
-uint8_t BTM_GetNumScoLinks(void);
+extern uint8_t BTM_GetNumScoLinks(void);
/*****************************************************************************
* SECURITY MANAGEMENT FUNCTIONS
****************************************************************************/
+/*******************************************************************************
+ *
+ * Function BTM_SecRegister
+ *
+ * Description Application manager calls this function to register for
+ * security services. There can be one and only one
+ * application saving link keys. BTM allows only first
+ * registration.
+ *
+ * Returns true if registered OK, else false
+ *
+ ******************************************************************************/
+extern bool BTM_SecRegister(const tBTM_APPL_INFO* p_cb_info);
+
+/*******************************************************************************
+ *
+ * Function BTM_SecAddRmtNameNotifyCallback
+ *
+ * Description Profiles can register to be notified when name of the
+ * remote device is resolved (up to
+ * BTM_SEC_MAX_RMT_NAME_CALLBACKS).
+ *
+ * Returns true if registered OK, else false
+ *
+ ******************************************************************************/
+extern bool BTM_SecAddRmtNameNotifyCallback(tBTM_RMT_NAME_CALLBACK* p_callback);
+
+/*******************************************************************************
+ *
+ * Function BTM_SecDeleteRmtNameNotifyCallback
+ *
+ * Description A profile can deregister notification when a new Link Key
+ * is generated per connection.
+ *
+ * Returns true if OK, else false
+ *
+ ******************************************************************************/
+extern bool BTM_SecDeleteRmtNameNotifyCallback(
+ tBTM_RMT_NAME_CALLBACK* p_callback);
+
+/*******************************************************************************
+ *
+ * Function BTM_GetSecurityFlags
+ *
+ * Description Get security flags for the device
+ *
+ * Returns bool true or false is device found
+ *
+ ******************************************************************************/
+extern bool BTM_GetSecurityFlags(const RawAddress& bd_addr,
+ uint8_t* p_sec_flags);
+
+/*******************************************************************************
+ *
+ * Function BTM_GetSecurityFlagsByTransport
+ *
+ * Description Get security flags for the device on a particular transport
+ *
+ * Parameters bd_addr: BD address of remote device
+ * p_sec_flags : Out parameter to be filled with security
+ * flags for the connection
+ * transport : Physical transport of the connection
+ * (BR/EDR or LE)
+ *
+ * Returns bool true or false is device found
+ *
+ ******************************************************************************/
+extern bool BTM_GetSecurityFlagsByTransport(const RawAddress& bd_addr,
+ uint8_t* p_sec_flags,
+ tBT_TRANSPORT transport);
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadTrustedMask
+ *
+ * Description Get trusted mask for the device
+ *
+ * Returns NULL, if the device record is not found.
+ * otherwise, the trusted mask
+ *
+ ******************************************************************************/
+extern uint32_t* BTM_ReadTrustedMask(const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
+ * Function BTM_SetPinType
+ *
+ * Description Set PIN type for the device.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_SetPinType(uint8_t pin_type, PIN_CODE pin_code,
+ uint8_t pin_code_len);
+
+/*******************************************************************************
+ *
+ * Function BTM_SetPairableMode
+ *
+ * Description Enable or disable pairing
+ *
+ * Parameters allow_pairing - (true or false) whether or not the device
+ * allows pairing.
+ * connect_only_paired - (true or false) whether or not to
+ * only allow paired devices to connect.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_SetPairableMode(bool allow_pairing, bool connect_only_paired);
+
+/*******************************************************************************
+ *
+ * Function BTM_SetSecurityLevel
+ *
+ * Description Register service security level with Security Manager. Each
+ * service must register its requirements regardless of the
+ * security level that is used. This API is called once for
+ * originators and again for acceptors of connections.
+ *
+ * Returns true if registered OK, else false
+ *
+ ******************************************************************************/
+extern bool BTM_SetSecurityLevel(bool is_originator, const char* p_name,
+ uint8_t service_id, uint16_t sec_level,
+ uint16_t psm, uint32_t mx_proto_id,
+ uint32_t mx_chan_id);
+
+/*******************************************************************************
+ *
+ * Function BTM_SetOutService
+ *
+ * Description This function is called to set the service for
+ * outgoing connection.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_SetOutService(const RawAddress& bd_addr, uint8_t service_id,
+ uint32_t mx_chan_id);
+
+/*******************************************************************************
+ *
+ * Function BTM_SecClrService
+ *
+ * Description Removes specified service record(s) from the security
+ * database. All service records with the specified name are
+ * removed. Typically used only by devices with limited RAM
+ * so that it can reuse an old security service record.
+ *
+ * Returns Number of records that were freed.
+ *
+ ******************************************************************************/
+extern uint8_t BTM_SecClrService(uint8_t service_id);
/*******************************************************************************
*
@@ -629,9 +1117,11 @@ uint8_t BTM_GetNumScoLinks(void);
* Returns true if added OK, else false
*
******************************************************************************/
-bool BTM_SecAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
- BD_NAME bd_name, uint8_t* features, LinkKey* link_key,
- uint8_t key_type, uint8_t pin_length);
+extern bool BTM_SecAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
+ BD_NAME bd_name, uint8_t* features,
+ uint32_t trusted_mask[], LinkKey* link_key,
+ uint8_t key_type, tBTM_IO_CAP io_cap,
+ uint8_t pin_length);
/** Free resources associated with the device associated with |bd_addr| address.
*
@@ -643,7 +1133,7 @@ bool BTM_SecAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
*
* Returns true if removed OK, false if not found or ACL link is active.
*/
-bool BTM_SecDeleteDevice(const RawAddress& bd_addr);
+extern bool BTM_SecDeleteDevice(const RawAddress& bd_addr);
/*******************************************************************************
*
@@ -653,36 +1143,239 @@ bool BTM_SecDeleteDevice(const RawAddress& bd_addr);
* remove device.
*
******************************************************************************/
-void BTM_SecClearSecurityFlags(const RawAddress& bd_addr);
+extern void BTM_SecClearSecurityFlags(const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
+ * Function BTM_SecGetDeviceLinkKeyType
+ *
+ * Description This function is called to obtain link key type for the
+ * device.
+ * it returns BTM_SUCCESS if link key is available, or
+ * BTM_UNKNOWN_ADDR if Security Manager does not know about
+ * the device or device record does not contain link key info
+ *
+ * Returns BTM_LKEY_TYPE_IGNORE if link key is unknown, link type
+ * otherwise.
+ *
+ ******************************************************************************/
+extern tBTM_LINK_KEY_TYPE BTM_SecGetDeviceLinkKeyType(
+ const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
+ * Function BTM_PINCodeReply
+ *
+ * Description This function is called after Security Manager submitted
+ * PIN code request to the UI.
+ *
+ * Parameters: bd_addr - Address of the device for which PIN was
+ * requested
+ * res - result of the operation BTM_SUCCESS if
+ * success
+ * pin_len - length in bytes of the PIN Code
+ * p_pin - pointer to array with the PIN Code
+ * trusted_mask - bitwise OR of trusted services
+ * (array of uint32_t)
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res,
+ uint8_t pin_len, uint8_t* p_pin,
+ uint32_t trusted_mask[]);
+
+/*******************************************************************************
+ *
+ * Function BTM_SecBond
+ *
+ * Description Perform bonding by designated transport
+ *
+ * Parameters: bd_addr - Address of the device to bond
+ * addr_type - address type for LE transport
+ * pin_len - length in bytes of the PIN Code
+ * p_pin - pointer to array with the PIN Code
+ * trusted_mask - bitwise OR of trusted services
+ * (array of uint32_t)
+ * transport : Physical transport to use for bonding
+ * (BR/EDR or LE)
+ *
+ * Returns BTM_CMD_STARTED if successfully initiated, otherwise error
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_SecBond(const RawAddress& bd_addr,
+ tBLE_ADDR_TYPE addr_type,
+ tBT_TRANSPORT transport, uint8_t pin_len,
+ uint8_t* p_pin, uint32_t trusted_mask[]);
+
+/*******************************************************************************
+ *
+ * Function BTM_SecBondCancel
+ *
+ * Description This function is called to cancel ongoing bonding process
+ * with peer device.
+ *
+ * Returns BTM_CMD_STARTED if successfully initiated, otherwise error
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_SecBondCancel(const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
+ * Function BTM_SetEncryption
+ *
+ * Description This function is called to ensure that connection is
+ * encrypted. Should be called only on an open connection.
+ * Typically only needed for connections that first want to
+ * bring up unencrypted links, then later encrypt them.
+ *
+ * Parameters: bd_addr - Address of the peer device
+ * transport - Link transport
+ * p_callback - Pointer to callback function called if
+ * this function returns PENDING after required
+ * procedures are completed. Can be set to
+ * NULL if status is not desired.
+ * p_ref_data - pointer to any data the caller wishes to
+ * receive in the callback function upon
+ * completion.
+ * can be set to NULL if not used.
+ * sec_act - LE security action, unused for BR/EDR
+ *
+ * Returns BTM_SUCCESS - already encrypted
+ * BTM_PENDING - command will be returned in the callback
+ * BTM_WRONG_MODE- connection not up.
+ * BTM_BUSY - security procedures are currently active
+ * BTM_MODE_UNSUPPORTED - if security manager not linked in.
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_SetEncryption(const RawAddress& bd_addr,
+ tBT_TRANSPORT transport,
+ tBTM_SEC_CBACK* p_callback,
+ void* p_ref_data,
+ tBTM_BLE_SEC_ACT sec_act);
+
+/*******************************************************************************
+ *
+ * Function BTM_ConfirmReqReply
+ *
+ * Description This function is called to confirm the numeric value for
+ * Simple Pairing in response to BTM_SP_CFM_REQ_EVT
+ *
+ * Parameters: res - result of the operation BTM_SUCCESS if
+ * success
+ * bd_addr - Address of the peer device
+ *
+ ******************************************************************************/
+extern void BTM_ConfirmReqReply(tBTM_STATUS res, const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
+ * Function BTM_PasskeyReqReply
+ *
+ * Description This function is called to provide the passkey for
+ * Simple Pairing in response to BTM_SP_KEY_REQ_EVT
+ *
+ * Parameters: res - result of the operation BTM_SUCCESS if
+ * success
+ * bd_addr - Address of the peer device
+ * passkey - numeric value in the range of
+ * 0 - 999999(0xF423F).
+ *
+ ******************************************************************************/
+extern void BTM_PasskeyReqReply(tBTM_STATUS res, const RawAddress& bd_addr,
+ uint32_t passkey);
/*******************************************************************************
*
- * Function btm_sec_is_a_bonded_dev
+ * Function BTM_SendKeypressNotif
*
- * Description Is the specified device is a bonded device
+ * Description This function is used during the passkey entry model
+ * by a device with KeyboardOnly IO capabilities
+ * (very likely to be a HID Device).
+ * It is called by a HID Device to inform the remote device
+ * when a key has been entered or erased.
*
- * Returns true - dev is bonded
+ * Parameters: bd_addr - Address of the peer device
+ * type - notification type
*
******************************************************************************/
-extern bool btm_sec_is_a_bonded_dev(const RawAddress& bda);
+extern void BTM_SendKeypressNotif(const RawAddress& bd_addr,
+ tBTM_SP_KEY_TYPE type);
/*******************************************************************************
*
- * Function BTM_GetPeerDeviceTypeFromFeatures
+ * Function BTM_IoCapRsp
*
- * Description This function is called to retrieve the peer device type
- * by referencing the remote features.
+ * Description This function is called in response to BTM_SP_IO_REQ_EVT
+ * When the event data io_req.oob_data is set to
+ * BTM_OOB_UNKNOWN by the tBTM_SP_CALLBACK implementation, this
+ * function is called to provide the actual response
+ *
+ * Parameters: bd_addr - Address of the peer device
+ * io_cap - The IO capability of local device.
+ * oob - BTM_OOB_NONE or BTM_OOB_PRESENT.
+ * auth_req- MITM protection required or not.
+ *
+ ******************************************************************************/
+extern void BTM_IoCapRsp(const RawAddress& bd_addr, tBTM_IO_CAP io_cap,
+ tBTM_OOB_DATA oob, tBTM_AUTH_REQ auth_req);
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadLocalOobData
+ *
+ * Description This function is called to read the local OOB data from
+ * LM
+ *
+ ******************************************************************************/
+extern void BTM_ReadLocalOobData(void);
+
+/*******************************************************************************
+ *
+ * Function BTM_RemoteOobDataReply
+ *
+ * Description This function is called to provide the remote OOB data for
+ * Simple Pairing in response to BTM_SP_RMT_OOB_EVT
+ *
+ * Parameters: bd_addr - Address of the peer device
+ * c - simple pairing Hash C.
+ * r - simple pairing Randomizer C.
+ *
+ ******************************************************************************/
+extern void BTM_RemoteOobDataReply(tBTM_STATUS res, const RawAddress& bd_addr,
+ const Octet16& c, const Octet16& r);
+
+/*******************************************************************************
+ *
+ * Function BTM_BothEndsSupportSecureConnections
+ *
+ * Description This function is called to check if both the local device
+ * and the peer device specified by bd_addr support BR/EDR
+ * Secure Connections.
*
* Parameters: bd_addr - address of the peer
*
- * Returns BT_DEVICE_TYPE_DUMO if both BR/EDR and BLE transports are
- * supported by the peer,
- * BT_DEVICE_TYPE_BREDR if only BR/EDR transport is supported,
- * BT_DEVICE_TYPE_BLE if only BLE transport is supported.
+ * Returns true if BR/EDR Secure Connections are supported by both
+ * local and the remote device.
+ * else false.
*
******************************************************************************/
-extern tBT_DEVICE_TYPE BTM_GetPeerDeviceTypeFromFeatures(
- const RawAddress& bd_addr);
+extern bool BTM_BothEndsSupportSecureConnections(const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
+ * Function BTM_PeerSupportsSecureConnections
+ *
+ * Description This function is called to check if the peer supports
+ * BR/EDR Secure Connections.
+ *
+ * Parameters: bd_addr - address of the peer
+ *
+ * Returns true if BR/EDR Secure Connections are supported by the peer,
+ * else false.
+ *
+ ******************************************************************************/
+extern bool BTM_PeerSupportsSecureConnections(const RawAddress& bd_addr);
/*******************************************************************************
*
@@ -694,7 +1387,7 @@ extern tBT_DEVICE_TYPE BTM_GetPeerDeviceTypeFromFeatures(
* Returns Pointer to the name or NULL
*
******************************************************************************/
-char* BTM_SecReadDevName(const RawAddress& bd_addr);
+extern char* BTM_SecReadDevName(const RawAddress& bd_addr);
/*****************************************************************************
* POWER MANAGEMENT FUNCTIONS
@@ -710,14 +1403,8 @@ char* BTM_SecReadDevName(const RawAddress& bd_addr);
* BTM_ILLEGAL_VALUE
*
******************************************************************************/
-tBTM_STATUS BTM_PmRegister(uint8_t mask, uint8_t* p_pm_id,
- tBTM_PM_STATUS_CBACK* p_cb);
-
-// Notified by ACL that a new link is connected
-void BTM_PM_OnConnected(uint16_t handle, const RawAddress& remote_bda);
-
-// Notified by ACL that a link is disconnected
-void BTM_PM_OnDisconnected(uint16_t handle);
+extern tBTM_STATUS BTM_PmRegister(uint8_t mask, uint8_t* p_pm_id,
+ tBTM_PM_STATUS_CBACK* p_cb);
/*******************************************************************************
*
@@ -730,9 +1417,31 @@ void BTM_PM_OnDisconnected(uint16_t handle);
* BTM_UNKNOWN_ADDR if bd addr is not active or bad
*
******************************************************************************/
-tBTM_STATUS BTM_SetPowerMode(uint8_t pm_id, const RawAddress& remote_bda,
- const tBTM_PM_PWR_MD* p_mode);
-bool BTM_SetLinkPolicyActiveMode(const RawAddress& remote_bda);
+extern tBTM_STATUS BTM_SetPowerMode(uint8_t pm_id, const RawAddress& remote_bda,
+ const tBTM_PM_PWR_MD* p_mode);
+
+/*******************************************************************************
+ *
+ * Function BTM_ReadPowerMode
+ *
+ * Description This returns the current mode for a specific
+ * ACL connection.
+ *
+ * Input Param remote_bda - device address of desired ACL connection
+ *
+ * Output Param p_mode - address where the current mode is copied into.
+ * BTM_ACL_MODE_NORMAL
+ * BTM_ACL_MODE_HOLD
+ * BTM_ACL_MODE_SNIFF
+ * BTM_ACL_MODE_PARK
+ * (valid only if return code is BTM_SUCCESS)
+ *
+ * Returns BTM_SUCCESS if successful,
+ * BTM_UNKNOWN_ADDR if bd addr is not active or bad
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_ReadPowerMode(const RawAddress& remote_bda,
+ tBTM_PM_MODE* p_mode);
/*******************************************************************************
*
@@ -752,8 +1461,9 @@ bool BTM_SetLinkPolicyActiveMode(const RawAddress& remote_bda);
* BTM_CMD_STORED if the command is stored
*
******************************************************************************/
-tBTM_STATUS BTM_SetSsrParams(const RawAddress& remote_bda, uint16_t max_lat,
- uint16_t min_rmt_to, uint16_t min_loc_to);
+extern tBTM_STATUS BTM_SetSsrParams(const RawAddress& remote_bda,
+ uint16_t max_lat, uint16_t min_rmt_to,
+ uint16_t min_loc_to);
/*******************************************************************************
*
@@ -765,43 +1475,8 @@ tBTM_STATUS BTM_SetSsrParams(const RawAddress& remote_bda, uint16_t max_lat,
* Returns the handle of the connection, or 0xFFFF if none.
*
******************************************************************************/
-uint16_t BTM_GetHCIConnHandle(const RawAddress& remote_bda,
- tBT_TRANSPORT transport);
-
-/*******************************************************************************
- *
- * Function BTM_IsPhy2mSupported
- *
- * Description This function is called to check PHY 2M support
- * from peer device
- * Returns True when PHY 2M supported false otherwise
- *
- ******************************************************************************/
-bool BTM_IsPhy2mSupported(const RawAddress& remote_bda, tBT_TRANSPORT transport);
-
-/*******************************************************************************
- *
- * Function BTM_RequestPeerSCA
- *
- * Description This function is called to request sleep clock accuracy
- * from peer device
- *
- ******************************************************************************/
-extern void BTM_RequestPeerSCA(const RawAddress& remote_bda,
- tBT_TRANSPORT transport);
-
-/*******************************************************************************
- *
- * Function BTM_GetPeerSCA
- *
- * Description This function is called to get peer sleep clock accuracy
- *
- * Returns SCA or 0xFF if SCA was never previously requested, request
- * is not supported by peer device or ACL does not exist
- *
- ******************************************************************************/
-extern uint8_t BTM_GetPeerSCA(const RawAddress& remote_bda,
- tBT_TRANSPORT transport);
+extern uint16_t BTM_GetHCIConnHandle(const RawAddress& remote_bda,
+ tBT_TRANSPORT transport);
/*******************************************************************************
*
@@ -816,8 +1491,8 @@ extern uint8_t BTM_GetPeerSCA(const RawAddress& remote_bda,
* the results
*
******************************************************************************/
-tBTM_STATUS BTM_DeleteStoredLinkKey(const RawAddress* bd_addr,
- tBTM_CMPL_CB* p_cb);
+extern tBTM_STATUS BTM_DeleteStoredLinkKey(const RawAddress* bd_addr,
+ tBTM_CMPL_CB* p_cb);
/*******************************************************************************
*
@@ -832,7 +1507,7 @@ tBTM_STATUS BTM_DeleteStoredLinkKey(const RawAddress* bd_addr,
* BTM_MODE_UNSUPPORTED - if local device cannot support it
*
******************************************************************************/
-tBTM_STATUS BTM_WriteEIR(BT_HDR* p_buff);
+extern tBTM_STATUS BTM_WriteEIR(BT_HDR* p_buff);
/*******************************************************************************
*
@@ -847,7 +1522,7 @@ tBTM_STATUS BTM_WriteEIR(BT_HDR* p_buff);
* false - if not found
*
******************************************************************************/
-bool BTM_HasEirService(const uint32_t* p_eir_uuid, uint16_t uuid16);
+extern bool BTM_HasEirService(const uint32_t* p_eir_uuid, uint16_t uuid16);
/*******************************************************************************
*
@@ -863,8 +1538,8 @@ bool BTM_HasEirService(const uint32_t* p_eir_uuid, uint16_t uuid16);
* BTM_EIR_UNKNOWN - if not found and it is not complete list
*
******************************************************************************/
-tBTM_EIR_SEARCH_RESULT BTM_HasInquiryEirService(tBTM_INQ_RESULTS* p_results,
- uint16_t uuid16);
+extern tBTM_EIR_SEARCH_RESULT BTM_HasInquiryEirService(
+ tBTM_INQ_RESULTS* p_results, uint16_t uuid16);
/*******************************************************************************
*
@@ -879,7 +1554,7 @@ tBTM_EIR_SEARCH_RESULT BTM_HasInquiryEirService(tBTM_INQ_RESULTS* p_results,
* Returns None
*
******************************************************************************/
-void BTM_AddEirService(uint32_t* p_eir_uuid, uint16_t uuid16);
+extern void BTM_AddEirService(uint32_t* p_eir_uuid, uint16_t uuid16);
/*******************************************************************************
*
@@ -894,7 +1569,7 @@ void BTM_AddEirService(uint32_t* p_eir_uuid, uint16_t uuid16);
* Returns None
*
******************************************************************************/
-void BTM_RemoveEirService(uint32_t* p_eir_uuid, uint16_t uuid16);
+extern void BTM_RemoveEirService(uint32_t* p_eir_uuid, uint16_t uuid16);
/*******************************************************************************
*
@@ -912,9 +1587,9 @@ void BTM_RemoveEirService(uint32_t* p_eir_uuid, uint16_t uuid16);
* BTM_EIR_COMPLETE_16BITS_UUID_TYPE, otherwise
*
******************************************************************************/
-uint8_t BTM_GetEirSupportedServices(uint32_t* p_eir_uuid, uint8_t** p,
- uint8_t max_num_uuid16,
- uint8_t* p_num_uuid16);
+extern uint8_t BTM_GetEirSupportedServices(uint32_t* p_eir_uuid, uint8_t** p,
+ uint8_t max_num_uuid16,
+ uint8_t* p_num_uuid16);
/*******************************************************************************
*
@@ -939,9 +1614,9 @@ uint8_t BTM_GetEirSupportedServices(uint32_t* p_eir_uuid, uint8_t** p,
* BTM_EIR_MORE_128BITS_UUID_TYPE
*
******************************************************************************/
-uint8_t BTM_GetEirUuidList(uint8_t* p_eir, size_t eir_len, uint8_t uuid_size,
- uint8_t* p_num_uuid, uint8_t* p_uuid_list,
- uint8_t max_num_uuid);
+extern uint8_t BTM_GetEirUuidList(uint8_t* p_eir, size_t eir_len,
+ uint8_t uuid_size, uint8_t* p_num_uuid,
+ uint8_t* p_uuid_list, uint8_t max_num_uuid);
/*******************************************************************************
*
@@ -953,32 +1628,6 @@ uint8_t BTM_GetEirUuidList(uint8_t* p_eir, size_t eir_len, uint8_t uuid_size,
* BTM_CONTRL_IDLE)
*
******************************************************************************/
-tBTM_CONTRL_STATE BTM_PM_ReadControllerState(void);
-
-/**
- * Send remote name request, either to legacy HCI, or to GD shim Name module
- */
-void SendRemoteNameRequest(const RawAddress& raw_address);
-
-bool BTM_IsScoActiveByBdaddr(const RawAddress& remote_bda);
-
-uint16_t BTM_GetClockOffset(const RawAddress& remote_bda);
-
-/* Read maximum data packet that can be sent over current connection */
-uint16_t BTM_GetMaxPacketSize(const RawAddress& addr);
-
-extern tBTM_STATUS BTM_BT_Quality_Report_VSE_Register(
- bool is_register, tBTM_BT_QUALITY_REPORT_RECEIVER* p_bqr_report_receiver);
-
-void BTM_LogHistory(const std::string& tag, const RawAddress& addr,
- const std::string& msg);
-void BTM_LogHistory(const std::string& tag, const RawAddress& addr,
- const std::string& msg, const std::string& extra);
-void BTM_LogHistory(const std::string& tag, const tBLE_BD_ADDR& addr,
- const std::string& msg);
-void BTM_LogHistory(const std::string& tag, const tBLE_BD_ADDR& addr,
- const std::string& msg, const std::string& extra);
-
-uint8_t btm_ble_read_sec_key_size(const RawAddress& bd_addr);
+extern tBTM_CONTRL_STATE BTM_PM_ReadControllerState(void);
#endif /* BTM_API_H */
diff --git a/stack/include/btm_api_types.h b/stack/include/btm_api_types.h
index 8146fc08e..05f12f0c2 100644..100755
--- a/stack/include/btm_api_types.h
+++ b/stack/include/btm_api_types.h
@@ -19,21 +19,63 @@
#ifndef BTM_API_TYPES_H
#define BTM_API_TYPES_H
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <string>
-
+#include "bt_target.h"
#include "device/include/esco_parameters.h"
-#include "internal_include/bt_target.h"
-#include "stack/include/btm_status.h"
-#include "stack/include/hcidefs.h"
-#include "stack/include/smp_api_types.h"
-#include "types/ble_address_with_type.h"
-#include "types/bt_transport.h"
+#include "hcidefs.h"
+#include "smp_api_types.h"
+
+/* Maximum number of bytes allowed for vendor specific command parameters */
+#define BTM_MAX_VENDOR_SPECIFIC_LEN HCI_COMMAND_SIZE
+
+/* BTM application return status codes */
+enum {
+ BTM_SUCCESS = 0, /* 0 Command succeeded */
+ BTM_CMD_STARTED, /* 1 Command started OK. */
+ BTM_BUSY, /* 2 Device busy with another command */
+ BTM_NO_RESOURCES, /* 3 No resources to issue command */
+ BTM_MODE_UNSUPPORTED, /* 4 Request for 1 or more unsupported modes */
+ BTM_ILLEGAL_VALUE, /* 5 Illegal parameter value */
+ BTM_WRONG_MODE, /* 6 Device in wrong mode for request */
+ BTM_UNKNOWN_ADDR, /* 7 Unknown remote BD address */
+ BTM_DEVICE_TIMEOUT, /* 8 Device timeout */
+ BTM_BAD_VALUE_RET, /* 9 A bad value was received from HCI */
+ BTM_ERR_PROCESSING, /* 10 Generic error */
+ BTM_NOT_AUTHORIZED, /* 11 Authorization failed */
+ BTM_DEV_RESET, /* 12 Device has been reset */
+ BTM_CMD_STORED, /* 13 request is stored in control block */
+ BTM_ILLEGAL_ACTION, /* 14 state machine gets illegal command */
+ BTM_DELAY_CHECK, /* 15 delay the check on encryption */
+ BTM_SCO_BAD_LENGTH, /* 16 Bad SCO over HCI data length */
+ BTM_SUCCESS_NO_SECURITY, /* 17 security passed, no security set */
+ BTM_FAILED_ON_SECURITY, /* 18 security failed */
+ BTM_REPEATED_ATTEMPTS, /* 19 repeated attempts for LE security requests */
+ BTM_MODE4_LEVEL4_NOT_SUPPORTED, /* 20 Secure Connections Only Mode can't be
+ supported */
+ BTM_DEV_BLACKLISTED /* 21 The device is Blacklisted */
+};
+
+typedef uint8_t tBTM_STATUS;
+
+/*************************
+ * Device Control Types
+ *************************/
+#define BTM_DEVICE_ROLE_BR 0x01
+#define BTM_DEVICE_ROLE_DUAL 0x02
+#define BTM_MAX_DEVICE_ROLE BTM_DEVICE_ROLE_DUAL
+typedef uint8_t tBTM_DEVICE_ROLE;
/* Device name of peer (may be truncated to save space in BTM database) */
typedef uint8_t tBTM_BD_NAME[BTM_MAX_REM_BD_NAME_LEN + 1];
+/* Structure returned with local version information */
+typedef struct {
+ uint8_t hci_version;
+ uint16_t hci_revision;
+ uint8_t lmp_version;
+ uint16_t manufacturer;
+ uint16_t lmp_subversion;
+} tBTM_VERSION_INFO;
+
/* Structure returned with Vendor Specific Command complete callback */
typedef struct {
uint16_t opcode;
@@ -41,9 +83,22 @@ typedef struct {
uint8_t* p_param_buf;
} tBTM_VSC_CMPL;
+#define BTM_VSC_CMPL_DATA_SIZE \
+ (BTM_MAX_VENDOR_SPECIFIC_LEN + sizeof(tBTM_VSC_CMPL))
/**************************************************
* Device Control and General Callback Functions
**************************************************/
+/* Callback function for when device status changes. Appl must poll for
+ * what the new state is (BTM_IsDeviceUp). The event occurs whenever the stack
+ * has detected that the controller status has changed. This asynchronous event
+ * is enabled/disabled by calling BTM_RegisterForDeviceStatusNotif().
+*/
+enum { BTM_DEV_STATUS_UP, BTM_DEV_STATUS_DOWN, BTM_DEV_STATUS_CMD_TOUT };
+
+typedef uint8_t tBTM_DEV_STATUS;
+
+typedef void(tBTM_DEV_STATUS_CB)(tBTM_DEV_STATUS status);
+
/* Callback function for when a vendor specific event occurs. The length and
* array of returned parameter bytes are included. This asynchronous event
* is enabled/disabled by calling BTM_RegisterForVSEvents().
@@ -62,46 +117,223 @@ typedef void(tBTM_CMPL_CB)(void* p1);
*/
typedef void(tBTM_VSC_CMPL_CB)(tBTM_VSC_CMPL* p1);
+/* Callback for apps to check connection and inquiry filters.
+ * Parameters are the BD Address of remote and the Dev Class of remote. If the
+ * app returns none zero, the connection or inquiry result will be dropped.
+*/
+typedef uint8_t(tBTM_FILTER_CB)(const RawAddress& bd_addr, DEV_CLASS dc);
+
/*****************************************************************************
* DEVICE DISCOVERY - Inquiry, Remote Name, Discovery, Class of Device
****************************************************************************/
/*******************************
* Device Discovery Constants
*******************************/
+/* Discoverable modes */
+#define BTM_NON_DISCOVERABLE 0
+#define BTM_LIMITED_DISCOVERABLE 1
+#define BTM_GENERAL_DISCOVERABLE 2
+#define BTM_DISCOVERABLE_MASK \
+ (BTM_LIMITED_DISCOVERABLE | BTM_GENERAL_DISCOVERABLE)
+#define BTM_MAX_DISCOVERABLE BTM_GENERAL_DISCOVERABLE
+/* high byte for BLE Discoverable modes */
+#define BTM_BLE_NON_DISCOVERABLE 0x0000
+#define BTM_BLE_LIMITED_DISCOVERABLE 0x0100
+#define BTM_BLE_GENERAL_DISCOVERABLE 0x0200
+#define BTM_BLE_MAX_DISCOVERABLE BTM_BLE_GENERAL_DISCOVERABLE
+#define BTM_BLE_DISCOVERABLE_MASK \
+ (BTM_BLE_NON_DISCOVERABLE | BTM_BLE_LIMITED_DISCOVERABLE | \
+ BTM_BLE_GENERAL_DISCOVERABLE)
+
+/* Connectable modes */
+#define BTM_NON_CONNECTABLE 0
+#define BTM_CONNECTABLE 1
+#define BTM_CONNECTABLE_MASK (BTM_NON_CONNECTABLE | BTM_CONNECTABLE)
+/* high byte for BLE Connectable modes */
+#define BTM_BLE_NON_CONNECTABLE 0x0000
+#define BTM_BLE_CONNECTABLE 0x0100
+#define BTM_BLE_MAX_CONNECTABLE BTM_BLE_CONNECTABLE
+#define BTM_BLE_CONNECTABLE_MASK (BTM_BLE_NON_CONNECTABLE | BTM_BLE_CONNECTABLE)
+
+/* Inquiry modes
+ * Note: These modes are associated with the inquiry active values (BTM_*ACTIVE)
+ */
+#define BTM_INQUIRY_NONE 0
+#define BTM_GENERAL_INQUIRY 0x01
+#define BTM_LIMITED_INQUIRY 0x02
+#define BTM_BR_INQUIRY_MASK (BTM_GENERAL_INQUIRY | BTM_LIMITED_INQUIRY)
+
+/* high byte of inquiry mode for BLE inquiry mode */
+#define BTM_BLE_INQUIRY_NONE 0x00
+#define BTM_BLE_GENERAL_INQUIRY 0x10
+#define BTM_BLE_LIMITED_INQUIRY 0x20
+#define BTM_BLE_INQUIRY_MASK (BTM_BLE_GENERAL_INQUIRY | BTM_BLE_LIMITED_INQUIRY)
+
+/* BTM_IsInquiryActive return values (Bit Mask)
+ * Note: These bit masks are associated with the inquiry modes (BTM_*_INQUIRY)
+ */
+/* no inquiry in progress */
+#define BTM_INQUIRY_INACTIVE 0x0
+/* a general inquiry is in progress */
+#define BTM_GENERAL_INQUIRY_ACTIVE BTM_GENERAL_INQUIRY
+/* a limited inquiry is in progress */
+#define BTM_LIMITED_INQUIRY_ACTIVE BTM_LIMITED_INQUIRY
+/* a periodic inquiry is active */
+#define BTM_PERIODIC_INQUIRY_ACTIVE 0x8
+/* SSP is active, so inquiry is disallowed (work around for FW bug) */
+#define BTM_SSP_INQUIRY_ACTIVE 0x4
+/* a general inquiry is in progress */
+#define BTM_LE_GENERAL_INQUIRY_ACTIVE BTM_BLE_GENERAL_INQUIRY
+/* a limited inquiry is in progress */
+#define BTM_LE_LIMITED_INQUIRY_ACTIVE BTM_BLE_LIMITED_INQUIRY
+
+/* inquiry activity mask */
+/* BR/EDR inquiry activity mask */
+#define BTM_BR_INQ_ACTIVE_MASK \
+ (BTM_GENERAL_INQUIRY_ACTIVE | BTM_LIMITED_INQUIRY_ACTIVE | \
+ BTM_PERIODIC_INQUIRY_ACTIVE)
+/* LE scan activity mask */
+#define BTM_BLE_SCAN_ACTIVE_MASK 0xF0
+/* LE inquiry activity mask*/
+#define BTM_BLE_INQ_ACTIVE_MASK \
+ (BTM_LE_GENERAL_INQUIRY_ACTIVE | BTM_LE_LIMITED_INQUIRY_ACTIVE)
+/* inquiry activity mask */
+#define BTM_INQUIRY_ACTIVE_MASK \
+ (BTM_BR_INQ_ACTIVE_MASK | BTM_BLE_INQ_ACTIVE_MASK)
+
+/* Define scan types */
+#define BTM_SCAN_TYPE_STANDARD 0
+#define BTM_SCAN_TYPE_INTERLACED 1 /* 1.2 devices only */
+
+/* Define inquiry results mode */
+#define BTM_INQ_RESULT_STANDARD 0
+#define BTM_INQ_RESULT_WITH_RSSI 1
+#define BTM_INQ_RESULT_EXTENDED 2
+/* RSSI value not supplied (ignore it) */
+#define BTM_INQ_RES_IGNORE_RSSI 0x7f
+
+/* Inquiry Filter Condition types (see tBTM_INQ_PARMS) */
+/* Inquiry Filtering is turned off */
+#define BTM_CLR_INQUIRY_FILTER 0
+/* Filter on device class */
+#define BTM_FILTER_COND_DEVICE_CLASS HCI_FILTER_COND_DEVICE_CLASS
+/* Filter on device addr */
+#define BTM_FILTER_COND_BD_ADDR HCI_FILTER_COND_BD_ADDR
+
+/* State of the remote name retrieval during inquiry operations.
+ * Used in the tBTM_INQ_INFO structure, and returned in the
+ * BTM_InqDbRead, BTM_InqDbFirst, and BTM_InqDbNext functions.
+ * The name field is valid when the state returned is
+ * BTM_INQ_RMT_NAME_DONE */
+#define BTM_INQ_RMT_NAME_EMPTY 0
+#define BTM_INQ_RMT_NAME_PENDING 1
+#define BTM_INQ_RMT_NAME_DONE 2
+#define BTM_INQ_RMT_NAME_FAILED 3
+
+/*********************************
+ *** Class of Device constants ***
+ *********************************/
+#define BTM_FORMAT_TYPE_1 0x00
+
/****************************
* minor device class field
****************************/
/* 0x00 is used as unclassified for all minor device classes */
#define BTM_COD_MINOR_UNCLASSIFIED 0x00
+
+/* minor device class field for Computer Major Class */
+/* #define BTM_COD_MINOR_UNCLASSIFIED 0x00 */
+#define BTM_COD_MINOR_DESKTOP_WORKSTATION 0x04
+#define BTM_COD_MINOR_SERVER_COMPUTER 0x08
+#define BTM_COD_MINOR_LAPTOP 0x0C
+#define BTM_COD_MINOR_HANDHELD_PC_PDA 0x10 /* clam shell */
+#define BTM_COD_MINOR_PALM_SIZE_PC_PDA 0x14
+#define BTM_COD_MINOR_WEARABLE_COMPUTER 0x18 /* watch sized */
+
+/* minor device class field for Phone Major Class */
+/* #define BTM_COD_MINOR_UNCLASSIFIED 0x00 */
+#define BTM_COD_MINOR_CELLULAR 0x04
+#define BTM_COD_MINOR_CORDLESS 0x08
+#define BTM_COD_MINOR_SMART_PHONE 0x0C
+/* wired modem or voice gatway */
+#define BTM_COD_MINOR_WIRED_MDM_V_GTWY 0x10
+#define BTM_COD_MINOR_ISDN_ACCESS 0x14
+
+/* minor device class field for LAN Access Point Major Class */
+/* Load Factor Field bit 5-7 */
+#define BTM_COD_MINOR_FULLY_AVAILABLE 0x00
+#define BTM_COD_MINOR_1_17_UTILIZED 0x20
+#define BTM_COD_MINOR_17_33_UTILIZED 0x40
+#define BTM_COD_MINOR_33_50_UTILIZED 0x60
+#define BTM_COD_MINOR_50_67_UTILIZED 0x80
+#define BTM_COD_MINOR_67_83_UTILIZED 0xA0
+#define BTM_COD_MINOR_83_99_UTILIZED 0xC0
+#define BTM_COD_MINOR_NO_SERVICE_AVAILABLE 0xE0
+/* sub-Field bit 2-4 */
+/* #define BTM_COD_MINOR_UNCLASSIFIED 0x00 */
+
+/* minor device class field for Audio/Video Major Class */
+/* #define BTM_COD_MINOR_UNCLASSIFIED 0x00 */
+#define BTM_COD_MINOR_CONFM_HEADSET 0x04
#define BTM_COD_MINOR_CONFM_HANDSFREE 0x08
+#define BTM_COD_MINOR_MICROPHONE 0x10
+#define BTM_COD_MINOR_LOUDSPEAKER 0x14
+#define BTM_COD_MINOR_HEADPHONES 0x18
+#define BTM_COD_MINOR_PORTABLE_AUDIO 0x1C
#define BTM_COD_MINOR_CAR_AUDIO 0x20
#define BTM_COD_MINOR_SET_TOP_BOX 0x24
+#define BTM_COD_MINOR_HIFI_AUDIO 0x28
+#define BTM_COD_MINOR_VCR 0x2C
+#define BTM_COD_MINOR_VIDEO_CAMERA 0x30
+#define BTM_COD_MINOR_CAMCORDER 0x34
+#define BTM_COD_MINOR_VIDEO_MONITOR 0x38
+#define BTM_COD_MINOR_VIDDISP_LDSPKR 0x3C
+#define BTM_COD_MINOR_VIDEO_CONFERENCING 0x40
+#define BTM_COD_MINOR_GAMING_TOY 0x48
/* minor device class field for Peripheral Major Class */
/* Bits 6-7 independently specify mouse, keyboard, or combo mouse/keyboard */
#define BTM_COD_MINOR_KEYBOARD 0x40
#define BTM_COD_MINOR_POINTING 0x80
+#define BTM_COD_MINOR_COMBO 0xC0
/* Bits 2-5 OR'd with selection from bits 6-7 */
/* #define BTM_COD_MINOR_UNCLASSIFIED 0x00 */
#define BTM_COD_MINOR_JOYSTICK 0x04
#define BTM_COD_MINOR_GAMEPAD 0x08
#define BTM_COD_MINOR_REMOTE_CONTROL 0x0C
+#define BTM_COD_MINOR_SENSING_DEVICE 0x10
#define BTM_COD_MINOR_DIGITIZING_TABLET 0x14
#define BTM_COD_MINOR_CARD_READER 0x18 /* e.g. SIM card reader */
#define BTM_COD_MINOR_DIGITAL_PAN 0x1C
+#define BTM_COD_MINOR_HAND_SCANNER 0x20
+#define BTM_COD_MINOR_HAND_GESTURAL_INPUT 0x24
/* minor device class field for Imaging Major Class */
/* Bits 5-7 independently specify display, camera, scanner, or printer */
#define BTM_COD_MINOR_DISPLAY 0x10
+#define BTM_COD_MINOR_CAMERA 0x20
+#define BTM_COD_MINOR_SCANNER 0x40
+#define BTM_COD_MINOR_PRINTER 0x80
/* Bits 2-3 Reserved */
/* #define BTM_COD_MINOR_UNCLASSIFIED 0x00 */
/* minor device class field for Wearable Major Class */
/* Bits 2-7 meaningful */
#define BTM_COD_MINOR_WRIST_WATCH 0x04
+#define BTM_COD_MINOR_PAGER 0x08
+#define BTM_COD_MINOR_JACKET 0x0C
+#define BTM_COD_MINOR_HELMET 0x10
#define BTM_COD_MINOR_GLASSES 0x14
+/* minor device class field for Toy Major Class */
+/* Bits 2-7 meaningful */
+#define BTM_COD_MINOR_ROBOT 0x04
+#define BTM_COD_MINOR_VEHICLE 0x08
+#define BTM_COD_MINOR_DOLL_ACTION_FIGURE 0x0C
+#define BTM_COD_MINOR_CONTROLLER 0x10
+#define BTM_COD_MINOR_GAME 0x14
+
/* minor device class field for Health Major Class */
/* Bits 2-7 meaningful */
#define BTM_COD_MINOR_BLOOD_MONITOR 0x04
@@ -110,17 +342,26 @@ typedef void(tBTM_VSC_CMPL_CB)(tBTM_VSC_CMPL* p1);
#define BTM_COD_MINOR_GLUCOSE_METER 0x10
#define BTM_COD_MINOR_PULSE_OXIMETER 0x14
#define BTM_COD_MINOR_HEART_PULSE_MONITOR 0x18
+#define BTM_COD_MINOR_HEALTH_DATA_DISPLAY 0x1C
#define BTM_COD_MINOR_STEP_COUNTER 0x20
+#define BTM_COD_MINOR_BODY_COM_ANALYZER 0x24
+#define BTM_COD_MINOR_PEAK_FLOW_MONITOR 0x28
+#define BTM_COD_MINOR_MEDICATION_MONITOR 0x2C
+#define BTM_COD_MINOR_KNEE_PROSTHESIS 0x30
+#define BTM_COD_MINOR_ANKLE_PROSTHESIS 0x34
/***************************
* major device class field
***************************/
+#define BTM_COD_MAJOR_MISCELLANEOUS 0x00
#define BTM_COD_MAJOR_COMPUTER 0x01
#define BTM_COD_MAJOR_PHONE 0x02
+#define BTM_COD_MAJOR_LAN_ACCESS_PT 0x03
#define BTM_COD_MAJOR_AUDIO 0x04
#define BTM_COD_MAJOR_PERIPHERAL 0x05
#define BTM_COD_MAJOR_IMAGING 0x06
#define BTM_COD_MAJOR_WEARABLE 0x07
+#define BTM_COD_MAJOR_TOY 0x08
#define BTM_COD_MAJOR_HEALTH 0x09
#define BTM_COD_MAJOR_UNCLASSIFIED 0x1F
@@ -138,6 +379,8 @@ typedef void(tBTM_VSC_CMPL_CB)(tBTM_VSC_CMPL* p1);
#define BTM_COD_SERVICE_INFORMATION 0x8000
/* class of device field macros */
+#define BTM_COD_FORMAT_TYPE(u8, pd) \
+ { (u8) = (pd)[2] & 0x03; }
#define BTM_COD_MINOR_CLASS(u8, pd) \
{ (u8) = (pd)[2] & 0xFC; }
#define BTM_COD_MAJOR_CLASS(u8, pd) \
@@ -158,6 +401,7 @@ typedef void(tBTM_VSC_CMPL_CB)(tBTM_VSC_CMPL* p1);
}
/* the COD masks */
+#define BTM_COD_FORMAT_TYPE_MASK 0x03
#define BTM_COD_MINOR_CLASS_MASK 0xFC
#define BTM_COD_MAJOR_CLASS_MASK 0x1F
#define BTM_COD_SERVICE_CLASS_LO_B 0x00E0
@@ -269,14 +513,33 @@ typedef uint8_t tBTM_EIR_SEARCH_RESULT;
#define BTM_EIR_COMPLETE_LOCAL_NAME_TYPE HCI_EIR_COMPLETE_LOCAL_NAME_TYPE
/* 0x0A */
#define BTM_EIR_TX_POWER_LEVEL_TYPE HCI_EIR_TX_POWER_LEVEL_TYPE
-
-typedef enum : uint8_t {
- BTM_BLE_SEC_NONE = 0,
- /* encrypt the link using current key */
- BTM_BLE_SEC_ENCRYPT = 1,
- BTM_BLE_SEC_ENCRYPT_NO_MITM = 2,
- BTM_BLE_SEC_ENCRYPT_MITM = 3,
-} tBTM_BLE_SEC_ACT;
+/* 0xFF */
+#define BTM_EIR_MANUFACTURER_SPECIFIC_TYPE HCI_EIR_MANUFACTURER_SPECIFIC_TYPE
+
+/* the following EIR tags are defined to OOB, not regular EIR data */
+/* 6 bytes */
+#define BTM_EIR_OOB_BD_ADDR_TYPE HCI_EIR_OOB_BD_ADDR_TYPE
+/* 3 bytes */
+#define BTM_EIR_OOB_COD_TYPE HCI_EIR_OOB_COD_TYPE
+/* 16 bytes */
+#define BTM_EIR_OOB_SSP_HASH_C_TYPE HCI_EIR_OOB_SSP_HASH_C_TYPE
+/* 16 bytes */
+#define BTM_EIR_OOB_SSP_RAND_R_TYPE HCI_EIR_OOB_SSP_RAND_R_TYPE
+
+/* include 2 bytes length & 6 bytes bd_addr */
+#define BTM_OOB_MANDATORY_SIZE 8
+#define BTM_OOB_DATA_LEN_SIZE 2
+#define BTM_OOB_BD_ADDR_SIZE 6
+#define BTM_OOB_COD_SIZE BT_OOB_COD_SIZE
+#define BTM_OOB_HASH_C_SIZE BT_OOB_HASH_C_SIZE
+#define BTM_OOB_RAND_R_SIZE BT_OOB_RAND_R_SIZE
+
+#define BTM_BLE_SEC_NONE 0
+/* encrypt the link using current key */
+#define BTM_BLE_SEC_ENCRYPT 1
+#define BTM_BLE_SEC_ENCRYPT_NO_MITM 2
+#define BTM_BLE_SEC_ENCRYPT_MITM 3
+typedef uint8_t tBTM_BLE_SEC_ACT;
/*******************************************************************************
* BTM Services MACROS handle array of uint32_t bits for more than 32 services
@@ -318,6 +581,26 @@ typedef struct /* contains the two device class condition fields */
DEV_CLASS dev_class_mask;
} tBTM_COD_COND;
+typedef union /* contains the inquiry filter condition */
+{
+ RawAddress bdaddr_cond;
+ tBTM_COD_COND cod_cond;
+} tBTM_INQ_FILT_COND;
+
+typedef struct /* contains the parameters passed to the inquiry functions */
+{
+ uint8_t mode; /* general or limited */
+ uint8_t duration; /* duration of the inquiry (1.28 sec increments) */
+ uint8_t max_resps; /* maximum number of responses to return */
+ bool report_dup; /* report duplicated inquiry response with higher RSSI value
+ */
+ uint8_t filter_cond_type; /* new devices, BD ADDR, COD, or No filtering */
+ tBTM_INQ_FILT_COND filter_cond; /* filter value based on filter cond type */
+} tBTM_INQ_PARMS;
+
+#define BTM_INQ_RESULT_BR 0x01
+#define BTM_INQ_RESULT_BLE 0x02
+
constexpr uint8_t BLE_EVT_CONNECTABLE_BIT = 0;
constexpr uint8_t BLE_EVT_SCANNABLE_BIT = 1;
constexpr uint8_t BLE_EVT_DIRECTED_BIT = 2;
@@ -332,20 +615,292 @@ constexpr uint8_t PHY_LE_CODED = 0x04;
constexpr uint8_t NO_ADI_PRESENT = 0xFF;
constexpr uint8_t TX_POWER_NOT_PRESENT = 0x7F;
+/* These are the fields returned in each device's response to the inquiry. It
+ * is returned in the results callback if registered.
+*/
+typedef struct {
+ uint16_t clock_offset;
+ RawAddress remote_bd_addr;
+ DEV_CLASS dev_class;
+ uint8_t page_scan_rep_mode;
+ uint8_t page_scan_per_mode;
+ uint8_t page_scan_mode;
+ int8_t rssi; /* Set to BTM_INQ_RES_IGNORE_RSSI if not valid */
+ uint32_t eir_uuid[BTM_EIR_SERVICE_ARRAY_SIZE];
+ bool eir_complete_list;
+ tBT_DEVICE_TYPE device_type;
+ uint8_t inq_result_type;
+ uint8_t ble_addr_type;
+ uint16_t ble_evt_type;
+ uint8_t ble_primary_phy;
+ uint8_t ble_secondary_phy;
+ uint8_t ble_advertising_sid;
+ int8_t ble_tx_power;
+ uint16_t ble_periodic_adv_int;
+ uint8_t flag;
+} tBTM_INQ_RESULTS;
+
+/* This is the inquiry response information held in its database by BTM, and
+ * available to applications via BTM_InqDbRead, BTM_InqDbFirst, and
+ * BTM_InqDbNext.
+*/
+typedef struct {
+ tBTM_INQ_RESULTS results;
+
+ bool appl_knows_rem_name; /* set by application if it knows the remote name of
+ the peer device.
+ This is later used by application to determine if
+ remote name request is
+ required to be done. Having the flag here avoid
+ duplicate store of inquiry results */
+ uint16_t remote_name_len;
+ tBTM_BD_NAME remote_name;
+ uint8_t remote_name_state;
+ uint8_t remote_name_type;
+
+} tBTM_INQ_INFO;
+
+/* Structure returned with inquiry complete callback */
+typedef struct {
+ tBTM_STATUS status;
+ uint8_t num_resp; /* Number of results from the current inquiry */
+} tBTM_INQUIRY_CMPL;
+
+/* Structure returned with remote name request */
+typedef struct {
+ uint16_t status;
+ RawAddress bd_addr;
+ uint16_t length;
+ BD_NAME remote_bd_name;
+} tBTM_REMOTE_DEV_NAME;
+
typedef struct {
uint8_t pcm_intf_rate; /* PCM interface rate: 0: 128kbps, 1: 256 kbps;
2:512 bps; 3: 1024kbps; 4: 2048kbps */
uint8_t frame_type; /* frame type: 0: short; 1: long */
- uint8_t sync_mode; /* sync mode: 0: peripheral; 1: central */
- uint8_t clock_mode; /* clock mode: 0: peripheral; 1: central */
+ uint8_t sync_mode; /* sync mode: 0: slave; 1: master */
+ uint8_t clock_mode; /* clock mode: 0: slave; 1: master */
} tBTM_SCO_PCM_PARAM;
+/****************************************
+ * Device Discovery Callback Functions
+ ****************************************/
+/* Callback function for asynchronous notifications when the BTM inquiry DB
+ * changes. First param is inquiry database, second is if added to or removed
+ * from the inquiry database.
+*/
+typedef void(tBTM_INQ_DB_CHANGE_CB)(void* p1, bool is_new);
+
+/* Callback function for notifications when the BTM gets inquiry response.
+ * First param is inquiry results database, second is pointer of EIR.
+*/
+typedef void(tBTM_INQ_RESULTS_CB)(tBTM_INQ_RESULTS* p_inq_results,
+ uint8_t* p_eir, uint16_t eir_len);
+
/*****************************************************************************
* ACL CHANNEL MANAGEMENT
****************************************************************************/
-// NOTE: Moved to stack/include/acl_api_types.h
+/******************
+ * ACL Constants
+ ******************/
+
+/* ACL modes */
+#define BTM_ACL_MODE_NORMAL HCI_MODE_ACTIVE
+#define BTM_ACL_MODE_HOLD HCI_MODE_HOLD
+#define BTM_ACL_MODE_SNIFF HCI_MODE_SNIFF
+#define BTM_ACL_MODE_PARK HCI_MODE_PARK
+
+/* Returned with structure in role switch callback (tBTM_ROLE_SWITCH_CMPL) */
+#define BTM_ROLE_MASTER HCI_ROLE_MASTER
+#define BTM_ROLE_SLAVE HCI_ROLE_SLAVE
+#define BTM_ROLE_UNDEFINED 0xff /* undefined value (error status) */
+
+/* ACL Packet Types */
+#define BTM_ACL_PKT_TYPES_MASK_DM1 HCI_PKT_TYPES_MASK_DM1
+#define BTM_ACL_PKT_TYPES_MASK_DH1 HCI_PKT_TYPES_MASK_DH1
+#define BTM_ACL_PKT_TYPES_MASK_DM3 HCI_PKT_TYPES_MASK_DM3
+#define BTM_ACL_PKT_TYPES_MASK_DH3 HCI_PKT_TYPES_MASK_DH3
+#define BTM_ACL_PKT_TYPES_MASK_DM5 HCI_PKT_TYPES_MASK_DM5
+#define BTM_ACL_PKT_TYPES_MASK_DH5 HCI_PKT_TYPES_MASK_DH5
+#define BTM_ACL_PKT_TYPES_MASK_NO_2_DH1 HCI_PKT_TYPES_MASK_NO_2_DH1
+#define BTM_ACL_PKT_TYPES_MASK_NO_3_DH1 HCI_PKT_TYPES_MASK_NO_3_DH1
+#define BTM_ACL_PKT_TYPES_MASK_NO_2_DH3 HCI_PKT_TYPES_MASK_NO_2_DH3
+#define BTM_ACL_PKT_TYPES_MASK_NO_3_DH3 HCI_PKT_TYPES_MASK_NO_3_DH3
+#define BTM_ACL_PKT_TYPES_MASK_NO_2_DH5 HCI_PKT_TYPES_MASK_NO_2_DH5
+#define BTM_ACL_PKT_TYPES_MASK_NO_3_DH5 HCI_PKT_TYPES_MASK_NO_3_DH5
+
+/***************
+ * ACL Types
+ ***************/
+/* Structure returned with Role Switch information (in tBTM_CMPL_CB callback
+ * function) in response to BTM_SwitchRole call.
+*/
+typedef struct {
+ uint8_t hci_status; /* HCI status returned with the event */
+ uint8_t role; /* BTM_ROLE_MASTER or BTM_ROLE_SLAVE */
+ RawAddress remote_bd_addr; /* Remote BD addr involved with the switch */
+} tBTM_ROLE_SWITCH_CMPL;
+
+/* Structure returned with QoS information (in tBTM_CMPL_CB callback function)
+ * in response to BTM_SetQoS call.
+*/
+typedef struct {
+ FLOW_SPEC flow;
+ uint16_t handle;
+ uint8_t status;
+} tBTM_QOS_SETUP_CMPL;
+
+/* Structure returned with read RSSI event (in tBTM_CMPL_CB callback function)
+ * in response to BTM_ReadRSSI call.
+*/
+typedef struct {
+ tBTM_STATUS status;
+ uint8_t hci_status;
+ int8_t rssi;
+ RawAddress rem_bda;
+} tBTM_RSSI_RESULT;
+
+/* Structure returned with read failed contact counter event
+ * (in tBTM_CMPL_CB callback function) in response to
+ * BTM_ReadFailedContactCounter call.
+ */
+typedef struct {
+ tBTM_STATUS status;
+ uint8_t hci_status;
+ uint16_t failed_contact_counter;
+ RawAddress rem_bda;
+} tBTM_FAILED_CONTACT_COUNTER_RESULT;
+
+/* Structure returned with read automatic flush timeout event
+ * (in tBTM_CMPL_CB callback function) in response to
+ * BTM_ReadAutomaticFlushTimeout call.
+ */
+typedef struct {
+ tBTM_STATUS status;
+ uint8_t hci_status;
+ uint16_t automatic_flush_timeout;
+ RawAddress rem_bda;
+} tBTM_AUTOMATIC_FLUSH_TIMEOUT_RESULT;
+
+/* Structure returned with read current TX power event (in tBTM_CMPL_CB callback
+ * function) in response to BTM_ReadTxPower call.
+*/
+typedef struct {
+ tBTM_STATUS status;
+ uint8_t hci_status;
+ int8_t tx_power;
+ RawAddress rem_bda;
+} tBTM_TX_POWER_RESULT;
+
+/* Structure returned with read link quality event (in tBTM_CMPL_CB callback
+ * function) in response to BTM_ReadLinkQuality call.
+*/
+typedef struct {
+ tBTM_STATUS status;
+ uint8_t hci_status;
+ uint8_t link_quality;
+ RawAddress rem_bda;
+} tBTM_LINK_QUALITY_RESULT;
+
+/* Structure returned with read inq tx power quality event (in tBTM_CMPL_CB
+ * callback function) in response to BTM_ReadInquiryRspTxPower call.
+*/
+typedef struct {
+ tBTM_STATUS status;
+ uint8_t hci_status;
+ int8_t tx_power;
+} tBTM_INQ_TXPWR_RESULT;
+
+enum {
+ BTM_BL_CONN_EVT,
+ BTM_BL_DISCN_EVT,
+ BTM_BL_UPDATE_EVT,
+ BTM_BL_ROLE_CHG_EVT,
+ BTM_BL_COLLISION_EVT
+};
+typedef uint8_t tBTM_BL_EVENT;
+typedef uint16_t tBTM_BL_EVENT_MASK;
+
+#define BTM_BL_CONN_MASK 0x0001
+#define BTM_BL_DISCN_MASK 0x0002
+#define BTM_BL_UPDATE_MASK 0x0004
+#define BTM_BL_ROLE_CHG_MASK 0x0008
+
+/* Device features mask definitions */
+#define BTM_FEATURE_BYTES_PER_PAGE HCI_FEATURE_BYTES_PER_PAGE
+#define BTM_EXT_FEATURES_PAGE_MAX HCI_EXT_FEATURES_PAGE_MAX
+
+/* the data type associated with BTM_BL_CONN_EVT */
+typedef struct {
+ tBTM_BL_EVENT event; /* The event reported. */
+ const RawAddress* p_bda; /* The address of the newly connected device */
+ DEV_CLASS_PTR p_dc; /* The device class */
+ BD_NAME_PTR p_bdn; /* The device name */
+ uint8_t* p_features; /* pointer to the remote device's features page[0]
+ (supported features page) */
+ uint16_t handle; /* connection handle */
+ tBT_TRANSPORT transport; /* link is LE or not */
+} tBTM_BL_CONN_DATA;
+
+/* the data type associated with BTM_BL_DISCN_EVT */
+typedef struct {
+ tBTM_BL_EVENT event; /* The event reported. */
+ const RawAddress* p_bda; /* The address of the disconnected device */
+ uint16_t handle; /* disconnected connection handle */
+ tBT_TRANSPORT transport; /* link is LE link or not */
+} tBTM_BL_DISCN_DATA;
+
+/* Busy-Level shall have the inquiry_paging mask set when
+ * inquiry/paging is in progress, Else the number of ACL links */
+#define BTM_BL_INQUIRY_PAGING_MASK 0x10
+#define BTM_BL_INQUIRY_STARTED (BTM_BL_INQUIRY_PAGING_MASK | 0x1)
+#define BTM_BL_INQUIRY_CANCELLED (BTM_BL_INQUIRY_PAGING_MASK | 0x2)
+#define BTM_BL_INQUIRY_COMPLETE (BTM_BL_INQUIRY_PAGING_MASK | 0x3)
+#define BTM_BL_PAGING_STARTED (BTM_BL_INQUIRY_PAGING_MASK | 0x4)
+#define BTM_BL_PAGING_COMPLETE (BTM_BL_INQUIRY_PAGING_MASK | 0x5)
+/* the data type associated with BTM_BL_UPDATE_EVT */
+typedef struct {
+ tBTM_BL_EVENT event; /* The event reported. */
+ uint8_t busy_level; /* when paging or inquiring, level is 10.
+ * Otherwise, the number of ACL links. */
+ uint8_t busy_level_flags; /* Notifies actual inquiry/page activities */
+} tBTM_BL_UPDATE_DATA;
+
+/* the data type associated with BTM_BL_ROLE_CHG_EVT */
+typedef struct {
+ tBTM_BL_EVENT event; /* The event reported. */
+ const RawAddress* p_bda; /* The address of the peer connected device */
+ uint8_t new_role;
+ uint8_t hci_status; /* HCI status returned with the event */
+} tBTM_BL_ROLE_CHG_DATA;
+
+typedef union {
+ tBTM_BL_EVENT event; /* The event reported. */
+ tBTM_BL_CONN_DATA conn; /* The data associated with BTM_BL_CONN_EVT */
+ tBTM_BL_DISCN_DATA discn; /* The data associated with BTM_BL_DISCN_EVT */
+ tBTM_BL_UPDATE_DATA update; /* The data associated with BTM_BL_UPDATE_EVT */
+ tBTM_BL_ROLE_CHG_DATA
+ role_chg; /*The data associated with BTM_BL_ROLE_CHG_EVT */
+} tBTM_BL_EVENT_DATA;
+
+/* Callback function for notifications when the BTM busy level
+ * changes.
+*/
+typedef void(tBTM_BL_CHANGE_CB)(tBTM_BL_EVENT_DATA* p_data);
+
+/***************************
+ * ACL Callback Functions
+ ***************************/
+/* Callback function for notifications when the BTM ACL connection DB
+ * changes. First param is BD address, second is if added or removed.
+ * Registered through BTM_AclRegisterForChanges call.
+*/
+typedef void(tBTM_ACL_DB_CHANGE_CB)(const RawAddress& p_bda, DEV_CLASS p_dc,
+ BD_NAME p_bdn, uint8_t* features,
+ bool is_new, uint16_t handle,
+ tBT_TRANSPORT transport);
/*****************************************************************************
* SCO CHANNEL MANAGEMENT
****************************************************************************/
@@ -355,16 +910,25 @@ typedef struct {
/* Define an invalid SCO index and an invalid HCI handle */
#define BTM_INVALID_SCO_INDEX 0xFFFF
+#define BTM_INVALID_HCI_HANDLE 0xFFFF
/* Define an invalid SCO disconnect reason */
#define BTM_INVALID_SCO_DISC_REASON 0xFFFF
+/* Define first active SCO index */
+#define BTM_FIRST_ACTIVE_SCO_INDEX BTM_MAX_SCO_LINKS
+
#define BTM_SCO_LINK_ONLY_MASK \
(ESCO_PKT_TYPES_MASK_HV1 | ESCO_PKT_TYPES_MASK_HV2 | ESCO_PKT_TYPES_MASK_HV3)
#define BTM_ESCO_LINK_ONLY_MASK \
(ESCO_PKT_TYPES_MASK_EV3 | ESCO_PKT_TYPES_MASK_EV4 | ESCO_PKT_TYPES_MASK_EV5)
+#define BTM_SCO_LINK_ALL_PKT_MASK \
+ (BTM_SCO_LINK_ONLY_MASK | BTM_ESCO_LINK_ONLY_MASK)
+
+#define BTM_VALID_SCO_ALL_PKT_TYPE HCI_VALID_SCO_ALL_PKT_TYPE
+
/***************
* SCO Types
***************/
@@ -395,12 +959,20 @@ typedef uint16_t tBTM_SCO_CODEC_TYPE;
/*******************
* SCO Data Status
*******************/
+enum {
+ BTM_SCO_DATA_CORRECT,
+ BTM_SCO_DATA_PAR_ERR,
+ BTM_SCO_DATA_NONE,
+ BTM_SCO_DATA_PAR_LOST
+};
typedef uint8_t tBTM_SCO_DATA_FLAG;
/***************************
* SCO Callback Functions
***************************/
typedef void(tBTM_SCO_CB)(uint16_t sco_inx);
+typedef void(tBTM_SCO_DATA_CB)(uint16_t sco_inx, BT_HDR* p_data,
+ tBTM_SCO_DATA_FLAG status);
/***************
* eSCO Types
@@ -420,7 +992,7 @@ typedef struct {
} tBTM_CHG_ESCO_PARAMS;
/* Returned by BTM_ReadEScoLinkParms() */
-struct tBTM_ESCO_DATA {
+typedef struct {
uint16_t rx_pkt_len;
uint16_t tx_pkt_len;
RawAddress bd_addr;
@@ -428,7 +1000,7 @@ struct tBTM_ESCO_DATA {
uint8_t tx_interval;
uint8_t retrans_window;
uint8_t air_mode;
-};
+} tBTM_ESCO_DATA;
typedef struct {
uint16_t sco_inx;
@@ -464,66 +1036,68 @@ typedef void(tBTM_ESCO_CBACK)(tBTM_ESCO_EVT event, tBTM_ESCO_EVT_DATA* p_data);
* Security Manager Constants
*******************************/
-typedef enum : uint8_t {
- BTM_SEC_MODE_SERVICE = 2,
- BTM_SEC_MODE_SP = 4,
- BTM_SEC_MODE_SC = 6,
-} tSECURITY_MODE;
-
-inline std::string security_mode_text(const tSECURITY_MODE& security_mode) {
- switch (security_mode) {
- case BTM_SEC_MODE_SERVICE:
- return std::string("service");
- case BTM_SEC_MODE_SP:
- return std::string("simple pairing");
- case BTM_SEC_MODE_SC:
- return std::string("secure connections only");
- default:
- return std::string("UNKNOWN[%hhu]", security_mode);
- }
-}
-
-enum : uint16_t {
- /* Nothing required */
- BTM_SEC_NONE = 0x0000,
- /* Inbound call requires authentication */
- BTM_SEC_IN_AUTHENTICATE = 0x0002,
- /* Inbound call requires encryption */
- BTM_SEC_IN_ENCRYPT = 0x0004,
- /* Outbound call requires authentication */
- BTM_SEC_OUT_AUTHENTICATE = 0x0010,
- /* Outbound call requires encryption */
- BTM_SEC_OUT_ENCRYPT = 0x0020,
- /* Secure Connections Only Mode */
- BTM_SEC_MODE4_LEVEL4 = 0x0040,
- /* Need to switch connection to be central */
- BTM_SEC_FORCE_CENTRAL = 0x0100,
- /* Need to switch connection to be central */
- BTM_SEC_ATTEMPT_CENTRAL = 0x0200,
- /* Need to switch connection to be peripheral */
- BTM_SEC_FORCE_PERIPHERAL = 0x0400,
- /* Try to switch connection to be peripheral */
- BTM_SEC_ATTEMPT_PERIPHERAL = 0x0800,
- /* inbound Do man in the middle protection */
- BTM_SEC_IN_MITM = 0x1000,
- /* outbound Do man in the middle protection */
- BTM_SEC_OUT_MITM = 0x2000,
- /* enforce a minimum of 16 digit for sec mode 2 */
- BTM_SEC_IN_MIN_16_DIGIT_PIN = 0x4000,
-};
+/* Security Mode (BTM_SetSecurityMode) */
+#define BTM_SEC_MODE_UNDEFINED 0
+#define BTM_SEC_MODE_NONE 1
+#define BTM_SEC_MODE_SERVICE 2
+#define BTM_SEC_MODE_LINK 3
+#define BTM_SEC_MODE_SP 4
+#define BTM_SEC_MODE_SP_DEBUG 5
+#define BTM_SEC_MODE_SC 6
+
+/* Security Service Levels [bit mask] (BTM_SetSecurityLevel)
+ * Encryption should not be used without authentication
+*/
+/* Nothing required */
+#define BTM_SEC_NONE 0x0000
+/* Inbound call requires authorization */
+#define BTM_SEC_IN_AUTHORIZE 0x0001
+/* Inbound call requires authentication */
+#define BTM_SEC_IN_AUTHENTICATE 0x0002
+/* Inbound call requires encryption */
+#define BTM_SEC_IN_ENCRYPT 0x0004
+/* Outbound call requires authorization */
+#define BTM_SEC_OUT_AUTHORIZE 0x0008
+/* Outbound call requires authentication */
+#define BTM_SEC_OUT_AUTHENTICATE 0x0010
+/* Outbound call requires encryption */
+#define BTM_SEC_OUT_ENCRYPT 0x0020
+/* Secure Connections Only Mode */
+#define BTM_SEC_MODE4_LEVEL4 0x0040
+/* Need to switch connection to be master */
+#define BTM_SEC_FORCE_MASTER 0x0100
+/* Try to switch connection to be master */
+#define BTM_SEC_ATTEMPT_MASTER 0x0200
+/* Need to switch connection to be master */
+#define BTM_SEC_FORCE_SLAVE 0x0400
+/* Try to switch connection to be slave */
+#define BTM_SEC_ATTEMPT_SLAVE 0x0800
+/* inbound Do man in the middle protection */
+#define BTM_SEC_IN_MITM 0x1000
+/* outbound Do man in the middle protection */
+#define BTM_SEC_OUT_MITM 0x2000
+/* enforce a minimum of 16 digit for sec mode 2 */
+#define BTM_SEC_IN_MIN_16_DIGIT_PIN 0x4000
/* Security Flags [bit mask] (BTM_GetSecurityFlags)
*/
+#define BTM_SEC_FLAG_AUTHORIZED 0x01
#define BTM_SEC_FLAG_AUTHENTICATED 0x02
#define BTM_SEC_FLAG_ENCRYPTED 0x04
#define BTM_SEC_FLAG_LKEY_KNOWN 0x10
#define BTM_SEC_FLAG_LKEY_AUTHED 0x20
+/* PIN types */
+#define BTM_PIN_TYPE_VARIABLE HCI_PIN_TYPE_VARIABLE
+#define BTM_PIN_TYPE_FIXED HCI_PIN_TYPE_FIXED
+
/* Link Key types used to generate the new link key.
* returned in link key notification callback function
*/
#define BTM_LKEY_TYPE_COMBINATION HCI_LKEY_TYPE_COMBINATION
+#define BTM_LKEY_TYPE_LOCAL_UNIT HCI_LKEY_TYPE_LOCAL_UNIT
#define BTM_LKEY_TYPE_REMOTE_UNIT HCI_LKEY_TYPE_REMOTE_UNIT
+#define BTM_LKEY_TYPE_DEBUG_COMB HCI_LKEY_TYPE_DEBUG_COMB
#define BTM_LKEY_TYPE_UNAUTH_COMB HCI_LKEY_TYPE_UNAUTH_COMB
#define BTM_LKEY_TYPE_AUTH_COMB HCI_LKEY_TYPE_AUTH_COMB
#define BTM_LKEY_TYPE_CHANGED_COMB HCI_LKEY_TYPE_CHANGED_COMB
@@ -545,16 +1119,75 @@ typedef uint8_t tBTM_LINK_KEY_TYPE;
#define BTM_SEC_PROTO_HID 6 /* HID */
#define BTM_SEC_PROTO_AVDT 7
+/* Determine the number of uint32_t's necessary for security services */
+#define BTM_SEC_ARRAY_BITS 32 /* Number of bits in each array element */
+#define BTM_SEC_SERVICE_ARRAY_SIZE \
+ (((uint32_t)BTM_SEC_MAX_SERVICES / BTM_SEC_ARRAY_BITS) + \
+ (((uint32_t)BTM_SEC_MAX_SERVICES % BTM_SEC_ARRAY_BITS) ? 1 : 0))
+
+/* Security service definitions (BTM_SetSecurityLevel)
+ * Used for Authorization APIs
+*/
+#define BTM_SEC_SERVICE_SDP_SERVER 0
+#define BTM_SEC_SERVICE_SERIAL_PORT 1
+#define BTM_SEC_SERVICE_LAN_ACCESS 2
+#define BTM_SEC_SERVICE_DUN 3
+#define BTM_SEC_SERVICE_IRMC_SYNC 4
+#define BTM_SEC_SERVICE_IRMC_SYNC_CMD 5
+#define BTM_SEC_SERVICE_OBEX 6
+#define BTM_SEC_SERVICE_OBEX_FTP 7
#define BTM_SEC_SERVICE_HEADSET 8
+#define BTM_SEC_SERVICE_CORDLESS 9
+#define BTM_SEC_SERVICE_INTERCOM 10
+#define BTM_SEC_SERVICE_FAX 11
#define BTM_SEC_SERVICE_HEADSET_AG 12
+#define BTM_SEC_SERVICE_PNP_INFO 13
+#define BTM_SEC_SERVICE_GEN_NET 14
+#define BTM_SEC_SERVICE_GEN_FILE 15
+#define BTM_SEC_SERVICE_GEN_AUDIO 16
+#define BTM_SEC_SERVICE_GEN_TEL 17
+#define BTM_SEC_SERVICE_CTP_DATA 18
+#define BTM_SEC_SERVICE_HCRP_CTRL 19
+#define BTM_SEC_SERVICE_HCRP_DATA 20
+#define BTM_SEC_SERVICE_HCRP_NOTIF 21
+#define BTM_SEC_SERVICE_BPP_JOB 22
+#define BTM_SEC_SERVICE_BPP_STATUS 23
+#define BTM_SEC_SERVICE_BPP_REF 24
+#define BTM_SEC_SERVICE_BNEP_PANU 25
+#define BTM_SEC_SERVICE_BNEP_GN 26
+#define BTM_SEC_SERVICE_BNEP_NAP 27
+#define BTM_SEC_SERVICE_HF_HANDSFREE 28
#define BTM_SEC_SERVICE_AG_HANDSFREE 29
+#define BTM_SEC_SERVICE_TE_PHONE_ACCESS 30
+#define BTM_SEC_SERVICE_ME_PHONE_ACCESS 31
+
+#define BTM_SEC_SERVICE_HIDH_SEC_CTRL 32
+#define BTM_SEC_SERVICE_HIDH_NOSEC_CTRL 33
+#define BTM_SEC_SERVICE_HIDH_INTR 34
+#define BTM_SEC_SERVICE_BIP 35
+#define BTM_SEC_SERVICE_BIP_REF 36
+#define BTM_SEC_SERVICE_AVDTP 37
+#define BTM_SEC_SERVICE_AVDTP_NOSEC 38
+#define BTM_SEC_SERVICE_AVCTP 39
+#define BTM_SEC_SERVICE_SAP 40
+#define BTM_SEC_SERVICE_PBAP 41
#define BTM_SEC_SERVICE_RFC_MUX 42
+#define BTM_SEC_SERVICE_AVCTP_BROWSE 43
+#define BTM_SEC_SERVICE_MAP 44
+#define BTM_SEC_SERVICE_MAP_NOTIF 45
+#define BTM_SEC_SERVICE_MCAP_CTRL 46
+#define BTM_SEC_SERVICE_MCAP_DATA 47
+#define BTM_SEC_SERVICE_HDP_SNK 48
+#define BTM_SEC_SERVICE_HDP_SRC 49
+#define BTM_SEC_SERVICE_ATT 50
+#define BTM_SEC_SERVICE_HIDD_SEC_CTRL 51
+#define BTM_SEC_SERVICE_HIDD_NOSEC_CTRL 52
+#define BTM_SEC_SERVICE_HIDD_INTR 53
#define BTM_SEC_SERVICE_HEARING_AID_LEFT 54
#define BTM_SEC_SERVICE_HEARING_AID_RIGHT 55
-#define BTM_SEC_SERVICE_EATT 56
/* Update these as services are added */
-#define BTM_SEC_SERVICE_FIRST_EMPTY 57
+#define BTM_SEC_SERVICE_FIRST_EMPTY 56
#ifndef BTM_SEC_MAX_SERVICES
#define BTM_SEC_MAX_SERVICES 75
@@ -564,6 +1197,95 @@ typedef uint8_t tBTM_LINK_KEY_TYPE;
* Security Services MACROS handle array of uint32_t bits for more than 32
* trusted services
******************************************************************************/
+/* MACRO to set the security service bit mask in a bit stream */
+#define BTM_SEC_SET_SERVICE(p, service) \
+ (((uint32_t*)(p))[(((uint32_t)(service)) / BTM_SEC_ARRAY_BITS)] |= \
+ ((uint32_t)1 << (((uint32_t)(service)) % BTM_SEC_ARRAY_BITS)))
+
+/* MACRO to clear the security service bit mask in a bit stream */
+#define BTM_SEC_CLR_SERVICE(p, service) \
+ (((uint32_t*)(p))[(((uint32_t)(service)) / BTM_SEC_ARRAY_BITS)] &= \
+ ~((uint32_t)1 << (((uint32_t)(service)) % BTM_SEC_ARRAY_BITS)))
+
+/* MACRO to check the security service bit mask in a bit stream (Returns true or
+ * false) */
+#define BTM_SEC_IS_SERVICE_TRUSTED(p, service) \
+ (((((uint32_t*)(p))[(((uint32_t)(service)) / BTM_SEC_ARRAY_BITS)]) & \
+ (uint32_t)(((uint32_t)1 << (((uint32_t)(service)) % BTM_SEC_ARRAY_BITS)))) \
+ ? true \
+ : false)
+
+/* MACRO to copy two trusted device bitmask */
+#define BTM_SEC_COPY_TRUSTED_DEVICE(p_src, p_dst) \
+ { \
+ uint32_t trst; \
+ for (trst = 0; trst < BTM_SEC_SERVICE_ARRAY_SIZE; trst++) \
+ ((uint32_t*)(p_dst))[trst] = ((uint32_t*)(p_src))[trst]; \
+ }
+
+/* MACRO to clear two trusted device bitmask */
+#define BTM_SEC_CLR_TRUSTED_DEVICE(p_dst) \
+ { \
+ uint32_t trst; \
+ for (trst = 0; trst < BTM_SEC_SERVICE_ARRAY_SIZE; trst++) \
+ ((uint32_t*)(p_dst))[trst] = 0; \
+ }
+
+#define BTM_SEC_TRUST_ALL 0xFFFFFFFF /* for each array element */
+
+/****************************************
+ * Security Manager Callback Functions
+ ****************************************/
+/* Authorize device for service. Parameters are
+ * BD Address of remote
+ * Device Class of remote
+ * BD Name of remote
+ * Service name
+ * Service Id (NULL - unknown service or unused
+ * [BTM_SEC_SERVICE_NAME_LEN set to 0])
+ * Is originator of the connection
+ * Result of the operation
+*/
+typedef uint8_t(tBTM_AUTHORIZE_CALLBACK)(
+ const RawAddress& bd_addr, DEV_CLASS dev_class, tBTM_BD_NAME bd_name,
+ uint8_t* service_name, uint8_t service_id, bool is_originator);
+
+/* Get PIN for the connection. Parameters are
+ * BD Address of remote
+ * Device Class of remote
+ * BD Name of remote
+ * Flag indicating the minimum pin code length to be 16 digits
+*/
+typedef uint8_t(tBTM_PIN_CALLBACK)(const RawAddress& bd_addr,
+ DEV_CLASS dev_class, tBTM_BD_NAME bd_name,
+ bool min_16_digit);
+
+/* New Link Key for the connection. Parameters are
+ * BD Address of remote
+ * Link Key
+ * Key Type: Combination, Local Unit, or Remote Unit
+*/
+typedef uint8_t(tBTM_LINK_KEY_CALLBACK)(const RawAddress& bd_addr,
+ DEV_CLASS dev_class,
+ tBTM_BD_NAME bd_name,
+ const LinkKey& key, uint8_t key_type);
+
+/* Remote Name Resolved. Parameters are
+ * BD Address of remote
+ * BD Name of remote
+*/
+typedef void(tBTM_RMT_NAME_CALLBACK)(const RawAddress& bd_addr, DEV_CLASS dc,
+ tBTM_BD_NAME bd_name);
+
+/* Authentication complete for the connection. Parameters are
+ * BD Address of remote
+ * Device Class of remote
+ * BD Name of remote
+ *
+*/
+typedef uint8_t(tBTM_AUTH_COMPLETE_CALLBACK)(const RawAddress& bd_addr,
+ DEV_CLASS dev_class,
+ tBTM_BD_NAME bd_name, int result);
enum {
BTM_SP_IO_REQ_EVT, /* received IO_CAPABILITY_REQUEST event */
@@ -571,70 +1293,50 @@ enum {
BTM_SP_CFM_REQ_EVT, /* received USER_CONFIRMATION_REQUEST event */
BTM_SP_KEY_NOTIF_EVT, /* received USER_PASSKEY_NOTIFY event */
BTM_SP_KEY_REQ_EVT, /* received USER_PASSKEY_REQUEST event */
+ BTM_SP_KEYPRESS_EVT, /* received KEYPRESS_NOTIFY event */
BTM_SP_LOC_OOB_EVT, /* received result for READ_LOCAL_OOB_DATA command */
BTM_SP_RMT_OOB_EVT, /* received REMOTE_OOB_DATA_REQUEST event */
+ BTM_SP_COMPLT_EVT, /* received SIMPLE_PAIRING_COMPLETE event */
+ BTM_SP_UPGRADE_EVT /* check if the application wants to upgrade the link key
+ */
};
typedef uint8_t tBTM_SP_EVT;
-enum : uint8_t {
- BTM_IO_CAP_OUT = 0, /* DisplayOnly */
- BTM_IO_CAP_IO = 1, /* DisplayYesNo */
- BTM_IO_CAP_IN = 2, /* KeyboardOnly */
- BTM_IO_CAP_NONE = 3, /* NoInputNoOutput */
- BTM_IO_CAP_KBDISP = 4, /* Keyboard display */
- BTM_IO_CAP_MAX = 5,
- BTM_IO_CAP_UNKNOWN = 0xFF /* Unknown value */
-};
-typedef uint8_t tBTM_IO_CAP;
+#define BTM_IO_CAP_OUT 0 /* DisplayOnly */
+#define BTM_IO_CAP_IO 1 /* DisplayYesNo */
+#define BTM_IO_CAP_IN 2 /* KeyboardOnly */
+#define BTM_IO_CAP_NONE 3 /* NoInputNoOutput */
+#define BTM_IO_CAP_KBDISP 4 /* Keyboard display */
+#define BTM_IO_CAP_MAX 5
+#define BTM_IO_CAP_UNKNOWN 0xFF /* Unknown value */
-inline std::string io_capabilities_text(const tBTM_IO_CAP& io_caps) {
- switch (io_caps) {
- case BTM_IO_CAP_OUT:
- return std::string("Display only");
- case BTM_IO_CAP_IO:
- return std::string("Display yes-no");
- case BTM_IO_CAP_IN:
- return std::string("Keyboard Only");
- case BTM_IO_CAP_NONE:
- return std::string("No input or output");
- case BTM_IO_CAP_KBDISP:
- return std::string("Keyboard-Display");
- default:
- return base::StringPrintf("UNKNOWN[%hhu]", io_caps);
- }
-}
+typedef uint8_t tBTM_IO_CAP;
#define BTM_MAX_PASSKEY_VAL (999999)
-
-typedef enum : uint8_t {
- /* MITM Protection Not Required - Single Profile/non-bonding Numeric
- * comparison with automatic accept allowed */
- // NO_BONDING
- BTM_AUTH_SP_NO = 0,
- /* MITM Protection Required - Single Profile/non-bonding. Use IO Capabilities
- * to determine authentication procedure */
- // NO_BONDING_MITM_PROTECTION
- BTM_AUTH_SP_YES = 1,
- /* MITM Protection Not Required - All Profiles/dedicated bonding Numeric
- * comparison with automatic accept allowed */
- // DEDICATED_BONDING
- BTM_AUTH_AP_NO = 2,
- /* MITM Protection Required - All Profiles/dedicated bonding Use IO
- * Capabilities to determine authentication procedure */
- // DEDICATED_BONDING_MITM_PROTECTION
- BTM_AUTH_AP_YES = 3,
- /* MITM Protection Not Required - Single Profiles/general bonding Numeric
- * comparison with automatic accept allowed */
- // GENERAL_BONDING
- BTM_AUTH_SPGB_NO = 4,
- /* MITM Protection Required - Single Profiles/general bonding Use IO
- * Capabilities to determine authentication procedure */
- // GENERAL_BONDING_MITM_PROTECTION
- BTM_AUTH_SPGB_YES = 5,
-} tBTM_AUTH;
+#define BTM_MIN_PASSKEY_VAL (0)
+
+/* MITM Protection Not Required - Single Profile/non-bonding Numeric comparison
+ * with automatic accept allowed */
+#define BTM_AUTH_SP_NO 0
+/* MITM Protection Required - Single Profile/non-bonding. Use IO Capabilities to
+ * determine authentication procedure */
+#define BTM_AUTH_SP_YES 1
+/* MITM Protection Not Required - All Profiles/dedicated bonding Numeric
+ * comparison with automatic accept allowed */
+#define BTM_AUTH_AP_NO 2
+/* MITM Protection Required - All Profiles/dedicated bonding Use IO Capabilities
+ * to determine authentication procedure */
+#define BTM_AUTH_AP_YES 3
+/* MITM Protection Not Required - Single Profiles/general bonding Numeric
+ * comparison with automatic accept allowed */
+#define BTM_AUTH_SPGB_NO 4
+/* MITM Protection Required - Single Profiles/general bonding Use IO
+ * Capabilities to determine authentication procedure */
+#define BTM_AUTH_SPGB_YES 5
/* this bit is ORed with BTM_AUTH_SP_* when IO exchange for dedicated bonding */
#define BTM_AUTH_DD_BOND 2
+#define BTM_AUTH_GB_BIT 4 /* the genernal bonding bit */
#define BTM_AUTH_BONDS 6 /* the general/dedicated bonding bits */
#define BTM_AUTH_YN_BIT 1 /* this is the Yes or No bit */
@@ -644,14 +1346,7 @@ typedef enum : uint8_t {
typedef uint8_t tBTM_AUTH_REQ;
-enum {
- BTM_OOB_NONE,
- BTM_OOB_PRESENT_192,
- BTM_OOB_PRESENT_256,
- BTM_OOB_PRESENT_192_AND_256,
- BTM_OOB_UNKNOWN
-};
-
+enum { BTM_OOB_NONE, BTM_OOB_PRESENT, BTM_OOB_UNKNOWN };
typedef uint8_t tBTM_OOB_DATA;
/* data type for BTM_SP_IO_REQ_EVT */
@@ -701,6 +1396,22 @@ typedef struct {
uint32_t passkey; /* passkey */
} tBTM_SP_KEY_NOTIF;
+enum {
+ BTM_SP_KEY_STARTED, /* 0 - passkey entry started */
+ BTM_SP_KEY_ENTERED, /* 1 - passkey digit entered */
+ BTM_SP_KEY_ERASED, /* 2 - passkey digit erased */
+ BTM_SP_KEY_CLEARED, /* 3 - passkey cleared */
+ BTM_SP_KEY_COMPLT, /* 4 - passkey entry completed */
+ BTM_SP_KEY_OUT_OF_RANGE /* 5 - out of range */
+};
+typedef uint8_t tBTM_SP_KEY_TYPE;
+
+/* data type for BTM_SP_KEYPRESS_EVT */
+typedef struct {
+ RawAddress bd_addr; /* peer address */
+ tBTM_SP_KEY_TYPE notif_type;
+} tBTM_SP_KEYPRESS;
+
/* data type for BTM_SP_LOC_OOB_EVT */
typedef struct {
tBTM_STATUS status; /* */
@@ -715,21 +1426,37 @@ typedef struct {
tBTM_BD_NAME bd_name; /* peer device name */
} tBTM_SP_RMT_OOB;
+/* data type for BTM_SP_COMPLT_EVT */
+typedef struct {
+ RawAddress bd_addr; /* peer address */
+ DEV_CLASS dev_class; /* peer CoD */
+ tBTM_BD_NAME bd_name; /* peer device name */
+ tBTM_STATUS status; /* status of the simple pairing process */
+} tBTM_SP_COMPLT;
+
+/* data type for BTM_SP_UPGRADE_EVT */
+typedef struct {
+ RawAddress bd_addr; /* peer address */
+ bool upgrade; /* true, to upgrade the link key */
+} tBTM_SP_UPGRADE;
+
typedef union {
tBTM_SP_IO_REQ io_req; /* BTM_SP_IO_REQ_EVT */
tBTM_SP_IO_RSP io_rsp; /* BTM_SP_IO_RSP_EVT */
tBTM_SP_CFM_REQ cfm_req; /* BTM_SP_CFM_REQ_EVT */
tBTM_SP_KEY_NOTIF key_notif; /* BTM_SP_KEY_NOTIF_EVT */
tBTM_SP_KEY_REQ key_req; /* BTM_SP_KEY_REQ_EVT */
+ tBTM_SP_KEYPRESS key_press; /* BTM_SP_KEYPRESS_EVT */
tBTM_SP_LOC_OOB loc_oob; /* BTM_SP_LOC_OOB_EVT */
tBTM_SP_RMT_OOB rmt_oob; /* BTM_SP_RMT_OOB_EVT */
+ tBTM_SP_COMPLT complt; /* BTM_SP_COMPLT_EVT */
+ tBTM_SP_UPGRADE upgrade; /* BTM_SP_UPGRADE_EVT */
} tBTM_SP_EVT_DATA;
/* Simple Pairing Events. Called by the stack when Simple Pairing related
* events occur.
*/
-typedef tBTM_STATUS(tBTM_SP_CALLBACK)(tBTM_SP_EVT event,
- tBTM_SP_EVT_DATA* p_data);
+typedef uint8_t(tBTM_SP_CALLBACK)(tBTM_SP_EVT event, tBTM_SP_EVT_DATA* p_data);
typedef void(tBTM_MKEY_CALLBACK)(const RawAddress& bd_addr, uint8_t status,
uint8_t key_flag);
@@ -741,10 +1468,8 @@ typedef void(tBTM_MKEY_CALLBACK)(const RawAddress& bd_addr, uint8_t status,
* optional data passed in by BTM_SetEncryption
* tBTM_STATUS - result of the operation
*/
-typedef void(tBTM_SEC_CALLBACK)(const RawAddress* bd_addr,
- tBT_TRANSPORT trasnport, void* p_ref_data,
- tBTM_STATUS result);
-typedef tBTM_SEC_CALLBACK tBTM_SEC_CALLBACK;
+typedef void(tBTM_SEC_CBACK)(const RawAddress* bd_addr, tBT_TRANSPORT trasnport,
+ void* p_ref_data, tBTM_STATUS result);
/* Bond Cancel complete. Parameters are
* Result of the cancel operation
@@ -772,30 +1497,31 @@ typedef void(tBTM_BOND_CANCEL_CMPL_CALLBACK)(tBTM_STATUS result);
#define BTM_LE_SC_OOB_REQ_EVT SMP_SC_OOB_REQ_EVT
/* SC OOB local data set is created (as result of SMP_CrLocScOobData(...)) */
#define BTM_LE_SC_LOC_OOB_EVT SMP_SC_LOC_OOB_DATA_UP_EVT
+/* SMP over BR keys request event */
+#define BTM_LE_BR_KEYS_REQ_EVT SMP_BR_KEYS_REQ_EVT
/* SMP complete event */
#define BTM_LE_COMPLT_EVT SMP_COMPLT_EVT
-#define BTM_LE_LAST_FROM_SMP SMP_BR_KEYS_REQ_EVT
+#define BTM_LE_LAST_FROM_SMP BTM_LE_BR_KEYS_REQ_EVT
/* KEY update event */
#define BTM_LE_KEY_EVT (BTM_LE_LAST_FROM_SMP + 1)
#define BTM_LE_CONSENT_REQ_EVT SMP_CONSENT_REQ_EVT
typedef uint8_t tBTM_LE_EVT;
-enum : uint8_t {
- BTM_LE_KEY_NONE = 0,
- BTM_LE_KEY_PENC = SMP_SEC_KEY_TYPE_ENC,
- /* identity key of the peer device */
- BTM_LE_KEY_PID = SMP_SEC_KEY_TYPE_ID,
- /* peer SRK */
- BTM_LE_KEY_PCSRK = SMP_SEC_KEY_TYPE_CSRK,
- BTM_LE_KEY_PLK = SMP_SEC_KEY_TYPE_LK,
- BTM_LE_KEY_LLK = (SMP_SEC_KEY_TYPE_LK << 4),
- /* master role security information:div */
- BTM_LE_KEY_LENC = (SMP_SEC_KEY_TYPE_ENC << 4),
- /* master device ID key */
- BTM_LE_KEY_LID = (SMP_SEC_KEY_TYPE_ID << 4),
- /* local CSRK has been deliver to peer */
- BTM_LE_KEY_LCSRK = (SMP_SEC_KEY_TYPE_CSRK << 4),
-};
+#define BTM_LE_KEY_NONE 0
+/* encryption information of peer device */
+#define BTM_LE_KEY_PENC SMP_SEC_KEY_TYPE_ENC
+/* identity key of the peer device */
+#define BTM_LE_KEY_PID SMP_SEC_KEY_TYPE_ID
+/* peer SRK */
+#define BTM_LE_KEY_PCSRK SMP_SEC_KEY_TYPE_CSRK
+#define BTM_LE_KEY_PLK SMP_SEC_KEY_TYPE_LK
+#define BTM_LE_KEY_LLK (SMP_SEC_KEY_TYPE_LK << 4)
+/* master role security information:div */
+#define BTM_LE_KEY_LENC (SMP_SEC_KEY_TYPE_ENC << 4)
+/* master device ID key */
+#define BTM_LE_KEY_LID (SMP_SEC_KEY_TYPE_ID << 4)
+/* local CSRK has been deliver to peer */
+#define BTM_LE_KEY_LCSRK (SMP_SEC_KEY_TYPE_CSRK << 4)
typedef uint8_t tBTM_LE_KEY_TYPE;
#define BTM_LE_AUTH_REQ_NO_BOND SMP_AUTH_NO_BOND /* 0 */
@@ -839,6 +1565,117 @@ typedef struct {
bool smp_over_br;
} tBTM_LE_COMPLT;
+/* BLE encryption keys */
+typedef struct {
+ Octet16 ltk;
+ BT_OCTET8 rand;
+ uint16_t ediv;
+ uint8_t sec_level;
+ uint8_t key_size;
+} tBTM_LE_PENC_KEYS;
+
+/* BLE CSRK keys */
+typedef struct {
+ uint32_t counter;
+ Octet16 csrk;
+ uint8_t sec_level;
+} tBTM_LE_PCSRK_KEYS;
+
+/* BLE Encryption reproduction keys */
+typedef struct {
+ Octet16 ltk;
+ uint16_t div;
+ uint8_t key_size;
+ uint8_t sec_level;
+} tBTM_LE_LENC_KEYS;
+
+/* BLE SRK keys */
+typedef struct {
+ uint32_t counter;
+ uint16_t div;
+ uint8_t sec_level;
+ Octet16 csrk;
+} tBTM_LE_LCSRK_KEYS;
+
+typedef struct {
+ Octet16 irk;
+ tBLE_ADDR_TYPE identity_addr_type;
+ RawAddress identity_addr;
+} tBTM_LE_PID_KEYS;
+
+typedef union {
+ tBTM_LE_PENC_KEYS penc_key; /* received peer encryption key */
+ tBTM_LE_PCSRK_KEYS pcsrk_key; /* received peer device SRK */
+ tBTM_LE_PID_KEYS pid_key; /* peer device ID key */
+ tBTM_LE_LENC_KEYS lenc_key; /* local encryption reproduction keys
+ * LTK = = d1(ER,DIV,0) */
+ tBTM_LE_LCSRK_KEYS lcsrk_key; /* local device CSRK = d1(ER,DIV,1)*/
+} tBTM_LE_KEY_VALUE;
+
+typedef struct {
+ tBTM_LE_KEY_TYPE key_type;
+ tBTM_LE_KEY_VALUE* p_key_value;
+} tBTM_LE_KEY;
+
+typedef union {
+ tBTM_LE_IO_REQ io_req; /* BTM_LE_IO_REQ_EVT */
+ uint32_t key_notif; /* BTM_LE_KEY_NOTIF_EVT */
+ /* BTM_LE_NC_REQ_EVT */
+ /* no callback data for
+ * BTM_LE_KEY_REQ_EVT
+ * and BTM_LE_OOB_REQ_EVT */
+ tBTM_LE_COMPLT complt; /* BTM_LE_COMPLT_EVT */
+ tSMP_OOB_DATA_TYPE req_oob_type;
+ tBTM_LE_KEY key;
+} tBTM_LE_EVT_DATA;
+
+/* Simple Pairing Events. Called by the stack when Simple Pairing related
+ * events occur.
+*/
+typedef uint8_t(tBTM_LE_CALLBACK)(tBTM_LE_EVT event, const RawAddress& bda,
+ tBTM_LE_EVT_DATA* p_data);
+
+#define BTM_BLE_KEY_TYPE_ID 1
+#define BTM_BLE_KEY_TYPE_ER 2
+#define BTM_BLE_KEY_TYPE_COUNTER 3 // tobe obsolete
+
+typedef struct {
+ Octet16 ir;
+ Octet16 irk;
+ Octet16 dhk;
+
+} tBTM_BLE_LOCAL_ID_KEYS;
+
+typedef union {
+ tBTM_BLE_LOCAL_ID_KEYS id_keys;
+ Octet16 er;
+} tBTM_BLE_LOCAL_KEYS;
+
+/* New LE identity key for local device.
+*/
+typedef void(tBTM_LE_KEY_CALLBACK)(uint8_t key_type,
+ tBTM_BLE_LOCAL_KEYS* p_key);
+
+/***************************
+ * Security Manager Types
+ ***************************/
+/* Structure that applications use to register with BTM_SecRegister */
+typedef struct {
+ tBTM_AUTHORIZE_CALLBACK* p_authorize_callback;
+ tBTM_PIN_CALLBACK* p_pin_callback;
+ tBTM_LINK_KEY_CALLBACK* p_link_key_callback;
+ tBTM_AUTH_COMPLETE_CALLBACK* p_auth_complete_callback;
+ tBTM_BOND_CANCEL_CMPL_CALLBACK* p_bond_cancel_cmpl_callback;
+ tBTM_SP_CALLBACK* p_sp_callback;
+ tBTM_LE_CALLBACK* p_le_callback;
+ tBTM_LE_KEY_CALLBACK* p_le_key_callback;
+} tBTM_APPL_INFO;
+
+/* Callback function for when a link supervision timeout event occurs.
+ * This asynchronous event is enabled/disabled by calling BTM_RegForLstoEvt().
+*/
+typedef void(tBTM_LSTO_CBACK)(const RawAddress& remote_bda, uint16_t timeout);
+
/*****************************************************************************
* POWER MANAGEMENT
****************************************************************************/
@@ -846,97 +1683,46 @@ typedef struct {
* Power Manager Constants
****************************/
/* BTM Power manager status codes */
-enum : uint8_t {
- BTM_PM_STS_ACTIVE = HCI_MODE_ACTIVE, // 0x00
- BTM_PM_STS_HOLD = HCI_MODE_HOLD, // 0x01
- BTM_PM_STS_SNIFF = HCI_MODE_SNIFF, // 0x02
- BTM_PM_STS_PARK = HCI_MODE_PARK, // 0x03
+enum {
+ BTM_PM_STS_ACTIVE = HCI_MODE_ACTIVE,
+ BTM_PM_STS_HOLD = HCI_MODE_HOLD,
+ BTM_PM_STS_SNIFF = HCI_MODE_SNIFF,
+ BTM_PM_STS_PARK = HCI_MODE_PARK,
BTM_PM_STS_SSR, /* report the SSR parameters in HCI_SNIFF_SUB_RATE_EVT */
BTM_PM_STS_PENDING, /* when waiting for status from controller */
BTM_PM_STS_ERROR /* when HCI command status returns error */
};
typedef uint8_t tBTM_PM_STATUS;
-inline std::string power_mode_status_text(tBTM_PM_STATUS status) {
- switch (status) {
- case BTM_PM_STS_ACTIVE:
- return std::string("active");
- case BTM_PM_STS_HOLD:
- return std::string("hold");
- case BTM_PM_STS_SNIFF:
- return std::string("sniff");
- case BTM_PM_STS_PARK:
- return std::string("park");
- case BTM_PM_STS_SSR:
- return std::string("sniff_subrating");
- case BTM_PM_STS_PENDING:
- return std::string("pending");
- case BTM_PM_STS_ERROR:
- return std::string("error");
- default:
- return std::string("UNKNOWN");
- }
-}
-
/* BTM Power manager modes */
-enum : uint8_t {
- BTM_PM_MD_ACTIVE = HCI_MODE_ACTIVE, // 0x00
- BTM_PM_MD_HOLD = HCI_MODE_HOLD, // 0x01
- BTM_PM_MD_SNIFF = HCI_MODE_SNIFF, // 0x02
- BTM_PM_MD_PARK = HCI_MODE_PARK, // 0x03
- BTM_PM_MD_FORCE = 0x10, /* OR this to force ACL link to a certain mode */
- BTM_PM_MD_UNKNOWN = 0xEF,
+enum {
+ BTM_PM_MD_ACTIVE = BTM_PM_STS_ACTIVE,
+ BTM_PM_MD_HOLD = BTM_PM_STS_HOLD,
+ BTM_PM_MD_SNIFF = BTM_PM_STS_SNIFF,
+ BTM_PM_MD_PARK = BTM_PM_STS_PARK,
+ BTM_PM_MD_FORCE = 0x10 /* OR this to force ACL link to a certain mode */
};
typedef uint8_t tBTM_PM_MODE;
-#define HCI_TO_BTM_POWER_MODE(mode) (static_cast<tBTM_PM_MODE>(mode))
-
-inline bool is_legal_power_mode(tBTM_PM_MODE mode) {
- switch (mode & ~BTM_PM_MD_FORCE) {
- case BTM_PM_MD_ACTIVE:
- case BTM_PM_MD_HOLD:
- case BTM_PM_MD_SNIFF:
- case BTM_PM_MD_PARK:
- return true;
- default:
- return false;
- }
-}
-
-inline std::string power_mode_text(tBTM_PM_MODE mode) {
- std::string s = base::StringPrintf((mode & BTM_PM_MD_FORCE) ? "" : "forced:");
- switch (mode & ~BTM_PM_MD_FORCE) {
- case BTM_PM_MD_ACTIVE:
- return s + std::string("active");
- case BTM_PM_MD_HOLD:
- return s + std::string("hold");
- case BTM_PM_MD_SNIFF:
- return s + std::string("sniff");
- case BTM_PM_MD_PARK:
- return s + std::string("park");
- default:
- return s + std::string("UNKNOWN");
- }
-}
#define BTM_PM_SET_ONLY_ID 0x80
/* Operation codes */
-typedef enum : uint8_t {
- /* The module wants to set the desired power mode */
- BTM_PM_REG_SET = (1u << 0),
- /* The module does not want to involve with PM anymore */
- BTM_PM_DEREG = (1u << 2),
-} tBTM_PM_REGISTER;
+/* The module wants to set the desired power mode */
+#define BTM_PM_REG_SET 1
+/* The module wants to receive mode change event */
+#define BTM_PM_REG_NOTIF 2
+/* The module does not want to involve with PM anymore */
+#define BTM_PM_DEREG 4
/************************
* Power Manager Types
************************/
typedef struct {
- uint16_t max = 0;
- uint16_t min = 0;
- uint16_t attempt = 0;
- uint16_t timeout = 0;
- tBTM_PM_MODE mode = BTM_PM_MD_ACTIVE; // 0
+ uint16_t max;
+ uint16_t min;
+ uint16_t attempt;
+ uint16_t timeout;
+ tBTM_PM_MODE mode;
} tBTM_PM_PWR_MD;
/*************************************
@@ -944,7 +1730,7 @@ typedef struct {
*************************************/
typedef void(tBTM_PM_STATUS_CBACK)(const RawAddress& p_bda,
tBTM_PM_STATUS status, uint16_t value,
- tHCI_STATUS hci_status);
+ uint8_t hci_status);
/************************
* Stored Linkkey Types
@@ -967,20 +1753,4 @@ typedef struct {
typedef uint8_t tBTM_CONTRL_STATE;
-// Bluetooth Quality Report - Report receiver
-typedef void(tBTM_BT_QUALITY_REPORT_RECEIVER)(uint8_t len, uint8_t* p_stream);
-
-struct tREMOTE_VERSION_INFO {
- uint8_t lmp_version{0};
- uint16_t lmp_subversion{0};
- uint16_t manufacturer{0};
- bool valid{false};
- std::string ToString() const {
- return (valid) ? base::StringPrintf("%02hhu-%05hu-%05hu", lmp_version,
- lmp_subversion, manufacturer)
- : std::string("UNKNOWN");
- }
-};
-using remote_version_info = tREMOTE_VERSION_INFO;
-
#endif // BTM_API_TYPES_H
diff --git a/stack/include/btm_ble_api.h b/stack/include/btm_ble_api.h
index 4dd4f1b08..5bf325a4d 100644
--- a/stack/include/btm_ble_api.h
+++ b/stack/include/btm_ble_api.h
@@ -32,11 +32,6 @@
#include "btm_api.h"
#include "btm_ble_api_types.h"
#include "osi/include/alarm.h"
-#include "stack/btm/neighbor_inquiry.h"
-#include "types/bt_transport.h"
-
-void btm_ble_init();
-void btm_ble_free();
/*****************************************************************************
* EXTERNAL FUNCTION DECLARATIONS
@@ -50,11 +45,14 @@ void btm_ble_free();
* for a LE device stored in the NVRAM.
*
* Parameters: bd_addr - BD address of the peer
+ * bd_name - Name of the peer device. NULL if unknown.
* dev_type - Remote device's device type.
* addr_type - LE device address type.
*
+ * Returns true if added OK, else false
+ *
******************************************************************************/
-extern void BTM_SecAddBleDevice(const RawAddress& bd_addr,
+extern bool BTM_SecAddBleDevice(const RawAddress& bd_addr, BD_NAME bd_name,
tBT_DEVICE_TYPE dev_type,
tBLE_ADDR_TYPE addr_type);
@@ -70,11 +68,26 @@ extern void BTM_SecAddBleDevice(const RawAddress& bd_addr,
* p_le_key - LE key values.
* key_type - LE SMP key type.
*
+ * Returns true if added OK, else false
+ *
******************************************************************************/
-extern void BTM_SecAddBleKey(const RawAddress& bd_addr,
+extern bool BTM_SecAddBleKey(const RawAddress& bd_addr,
tBTM_LE_KEY_VALUE* p_le_key,
tBTM_LE_KEY_TYPE key_type);
+/*******************************************************************************
+ *
+ * Function BTM_BleObtainVendorCapabilities
+ *
+ * Description This function is called to obatin vendor capabilties
+ *
+ * Parameters p_cmn_vsc_cb - Returns the vednor capabilities
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_BleObtainVendorCapabilities(tBTM_BLE_VSC_CB* p_cmn_vsc_cb);
+
/**
* This function is called to set scan parameters. |cb| is called with operation
* status
@@ -95,21 +108,6 @@ extern void BTM_BleSetScanParams(uint32_t scan_interval, uint32_t scan_window,
*
******************************************************************************/
extern void BTM_BleGetVendorCapabilities(tBTM_BLE_VSC_CB* p_cmn_vsc_cb);
-
-/*******************************************************************************
- *
- * Function BTM_BleGetDynamicAudioBuffer
- *
- * Description This function reads dynamic audio buffer
- *
- * Parameters p_dynamic_audio_buffer_cb : Dynamic Audio Buffer structure
- *
- * Returns void
- *
- ******************************************************************************/
-extern void BTM_BleGetDynamicAudioBuffer(
- tBTM_BT_DYNAMIC_AUDIO_BUFFER_CB* p_dynamic_audio_buffer_cb);
-
/*******************************************************************************
*
* Function BTM_BleSetStorageConfig
@@ -154,6 +152,20 @@ extern void BTM_BleTrackAdvertiser(tBTM_BLE_TRACK_ADV_CBACK* p_track_cback,
/*******************************************************************************
*
+ * Function BTM_BleWriteScanRsp
+ *
+ * Description This function is called to write LE scan response.
+ *
+ * Parameters: p_scan_rsp: scan response.
+ *
+ * Returns status
+ *
+ ******************************************************************************/
+extern void BTM_BleWriteScanRsp(uint8_t* data, uint8_t length,
+ tBTM_BLE_ADV_DATA_CMPL_CBACK* p_adv_data_cback);
+
+/*******************************************************************************
+ *
* Function BTM_BleObserve
*
* Description This procedure keep the device listening for advertising
@@ -296,6 +308,19 @@ extern bool BTM_BleVerifySignature(const RawAddress& bd_addr, uint8_t* p_orig,
/*******************************************************************************
*
+ * Function BTM_ReadConnectionAddr
+ *
+ * Description Read the local device random address.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_ReadConnectionAddr(const RawAddress& remote_bda,
+ RawAddress& local_conn_addr,
+ tBLE_ADDR_TYPE* p_addr_type);
+
+/*******************************************************************************
+ *
* Function BTM_IsBleConnection
*
* Description This function is called to check if the connection handle
@@ -349,7 +374,7 @@ extern void BTM_BleLoadLocalKeys(uint8_t key_type, tBTM_BLE_LOCAL_KEYS* p_key);
* Parameters: bd_addr - BD address of the peripheral
* min_conn_int - minimum preferred connection interval
* max_conn_int - maximum preferred connection interval
- * peripheral_latency - preferred peripheral latency
+ * slave_latency - preferred slave latency
* supervision_tout - preferred supervision timeout
*
* Returns void
@@ -358,11 +383,26 @@ extern void BTM_BleLoadLocalKeys(uint8_t key_type, tBTM_BLE_LOCAL_KEYS* p_key);
extern void BTM_BleSetPrefConnParams(const RawAddress& bd_addr,
uint16_t min_conn_int,
uint16_t max_conn_int,
- uint16_t peripheral_latency,
+ uint16_t slave_latency,
uint16_t supervision_tout);
/******************************************************************************
*
+ * Function BTM_BleSetConnScanParams
+ *
+ * Description Set scan parameters used in BLE connection request
+ *
+ * Parameters: scan_interval - scan interval
+ * scan_window - scan window
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_BleSetConnScanParams(uint32_t scan_interval,
+ uint32_t scan_window);
+
+/******************************************************************************
+ *
* Function BTM_BleReadControllerFeatures
*
* Description Reads BLE specific controller features
@@ -461,6 +501,20 @@ extern bool BTM_BleLocalPrivacyEnabled(void);
/*******************************************************************************
*
+ * Function BTM_BleEnableMixedPrivacyMode
+ *
+ * Description This function is called to enabled Mixed mode if privacy 1.2
+ * is applicable in controller.
+ *
+ * Parameters mixed_on: mixed mode to be used or not.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_BleEnableMixedPrivacyMode(bool mixed_on);
+
+/*******************************************************************************
+ *
* Function BTM_BleMaxMultiAdvInstanceCount
*
* Description Returns the maximum number of multi adv instances supported
@@ -473,6 +527,54 @@ extern uint8_t BTM_BleMaxMultiAdvInstanceCount();
/*******************************************************************************
*
+ * Function BTM_BleSetConnectableMode
+ *
+ * Description This function is called to set BLE connectable mode for a
+ * peripheral device.
+ *
+ * Parameters connectable_mode: directed connectable mode, or
+ * non-directed. It can be
+ * BTM_BLE_CONNECT_EVT,
+ * BTM_BLE_CONNECT_DIR_EVT or
+ * BTM_BLE_CONNECT_LO_DUTY_DIR_EVT
+ *
+ * Returns BTM_ILLEGAL_VALUE if controller does not support BLE.
+ * BTM_SUCCESS is status set successfully; otherwise failure.
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_BleSetConnectableMode(
+ tBTM_BLE_CONN_MODE connectable_mode);
+
+/*******************************************************************************
+ *
+ * Function BTM_BleTurnOnPrivacyOnRemote
+ *
+ * Description This function is called to enable or disable the privacy on
+ * the remote device.
+ *
+ * Parameters bd_addr: remote device address.
+ * privacy_on: true to enable it; false to disable it.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern void BTM_BleTurnOnPrivacyOnRemote(const RawAddress& bd_addr,
+ bool privacy_on);
+
+/*******************************************************************************
+ *
+ * Function BTM_BleUpdateAdvFilterPolicy
+ *
+ * Description This function update the filter policy of advertiser.
+ *
+ * Parameter adv_policy: advertising filter policy
+ *
+ * Return void
+ ******************************************************************************/
+extern void BTM_BleUpdateAdvFilterPolicy(tBTM_BLE_AFP adv_policy);
+
+/*******************************************************************************
+ *
* Function BTM_BleReceiverTest
*
* Description This function is called to start the LE Receiver test
@@ -524,6 +626,59 @@ extern bool BTM_UseLeLink(const RawAddress& bd_addr);
/*******************************************************************************
*
+ * Function BTM_BleStackEnable
+ *
+ * Description Enable/Disable BLE functionality on stack regardless of
+ * controller capability.
+ *
+ * Parameters: enable: true to enable, false to disable.
+ *
+ * Returns true if added OK, else false
+ *
+ ******************************************************************************/
+extern tBTM_STATUS BTM_BleStackEnable(bool enable);
+
+/*******************************************************************************
+ *
+ * Function BTM_GetLeSecurityState
+ *
+ * Description This function is called to get security mode 1 flags and
+ * encryption key size for LE peer.
+ *
+ * Returns bool true if LE device is found, false otherwise.
+ *
+ ******************************************************************************/
+extern bool BTM_GetLeSecurityState(const RawAddress& bd_addr,
+ uint8_t* p_le_dev_sec_flags,
+ uint8_t* p_le_key_size);
+
+/*******************************************************************************
+ *
+ * Function BTM_BleSecurityProcedureIsRunning
+ *
+ * Description This function indicates if LE security procedure is
+ * currently running with the peer.
+ *
+ * Returns bool true if security procedure is running, false otherwise.
+ *
+ ******************************************************************************/
+extern bool BTM_BleSecurityProcedureIsRunning(const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
+ * Function BTM_BleGetSupportedKeySize
+ *
+ * Description This function gets the maximum encryption key size in bytes
+ * the local device can suport.
+ * record.
+ *
+ * Returns the key size or 0 if the size can't be retrieved.
+ *
+ ******************************************************************************/
+extern uint8_t BTM_BleGetSupportedKeySize(const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
* Function BTM_BleAdvFilterParamSetup
*
* Description This function is called to setup the adv data payload filter
@@ -598,30 +753,30 @@ extern void BTM_BleReadPhy(
/*******************************************************************************
*
- * Function BTM_BleSetPhy
+ * Function BTM_BleSetDefaultPhy
*
- * Description To set PHY preferences for specified LE connection
+ * Description To set preferred PHY for ensuing LE connections
*
*
* Returns BTM_SUCCESS if success; otherwise failed.
*
******************************************************************************/
-extern void BTM_BleSetPhy(const RawAddress& bd_addr, uint8_t tx_phys,
- uint8_t rx_phys, uint16_t phy_options);
-
-extern void btm_ble_multi_adv_cleanup(void);
+extern tBTM_STATUS BTM_BleSetDefaultPhy(uint8_t all_phys, uint8_t tx_phys,
+ uint8_t rx_phys);
/*******************************************************************************
*
- * Function btm_ble_get_acl_remote_addr
+ * Function BTM_BleSetPhy
+ *
+ * Description To set PHY preferences for specified LE connection
*
- * Description This function reads the active remote address used for the
- * connection.
*
- * Returns success return true, otherwise false.
+ * Returns BTM_SUCCESS if success; otherwise failed.
*
******************************************************************************/
-bool btm_ble_get_acl_remote_addr(uint16_t hci_handle, RawAddress& conn_addr,
- tBLE_ADDR_TYPE* p_addr_type);
+extern void BTM_BleSetPhy(const RawAddress& bd_addr, uint8_t tx_phys,
+ uint8_t rx_phys, uint16_t phy_options);
+
+extern void btm_ble_multi_adv_cleanup(void);
#endif
diff --git a/stack/include/btm_ble_api_types.h b/stack/include/btm_ble_api_types.h
index fe5a7fb8c..6c59a758c 100644
--- a/stack/include/btm_ble_api_types.h
+++ b/stack/include/btm_ble_api_types.h
@@ -21,38 +21,32 @@
#include <base/callback_forward.h>
#include <hardware/bt_common_types.h>
-#include <cstdint>
#include <vector>
-#include "stack/include/btm_api_types.h"
-#include "stack/include/btm_status.h"
-#include "stack/include/hci_error_code.h"
-#include "types/ble_address_with_type.h"
-
#define CHNL_MAP_LEN 5
typedef uint8_t tBTM_BLE_CHNL_MAP[CHNL_MAP_LEN];
-enum : uint8_t {
- /* 0x00-0x04 only used for set advertising parameter command */
- BTM_BLE_CONNECT_EVT = 0x00,
- /* Connectable directed advertising */
- BTM_BLE_CONNECT_DIR_EVT = 0x01,
- /* Scannable undirected advertising */
- BTM_BLE_DISCOVER_EVT = 0x02,
- /* Non connectable undirected advertising */
- BTM_BLE_NON_CONNECT_EVT = 0x03,
- /* Connectable low duty cycle directed advertising */
- BTM_BLE_CONNECT_LO_DUTY_DIR_EVT = 0x04,
-};
-
+/* 0x00-0x04 only used for set advertising parameter command */
+#define BTM_BLE_CONNECT_EVT 0x00
+/* Connectable directed advertising */
+#define BTM_BLE_CONNECT_DIR_EVT 0x01
+/* Scannable undirected advertising */
+#define BTM_BLE_DISCOVER_EVT 0x02
+/* Non connectable undirected advertising */
+#define BTM_BLE_NON_CONNECT_EVT 0x03
+/* Connectable low duty cycle directed advertising */
+#define BTM_BLE_CONNECT_LO_DUTY_DIR_EVT 0x04
/* 0x00 - 0x04 can be received on adv event type */
-typedef enum : uint8_t {
- BTM_BLE_ADV_IND_EVT = 0x00,
- BTM_BLE_ADV_DIRECT_IND_EVT = 0x01,
- BTM_BLE_ADV_SCAN_IND_EVT = 0x02,
- BTM_BLE_ADV_NONCONN_IND_EVT = 0x03,
- BTM_BLE_SCAN_RSP_EVT = 0x04,
-} tBTM_BLE_EVT;
+#define BTM_BLE_ADV_IND_EVT 0x00
+#define BTM_BLE_ADV_DIRECT_IND_EVT 0x01
+#define BTM_BLE_ADV_SCAN_IND_EVT 0x02
+#define BTM_BLE_ADV_NONCONN_IND_EVT 0x03
+#define BTM_BLE_SCAN_RSP_EVT 0x04
+
+#define BTM_BLE_UNKNOWN_EVT 0xff
+
+typedef uint8_t tBTM_BLE_EVT;
+typedef uint8_t tBTM_BLE_CONN_MODE;
typedef uint32_t tBTM_BLE_REF_VALUE;
@@ -97,6 +91,15 @@ typedef uint8_t tBTM_BLE_AFP;
/* 0: accept adv packet from all, directed adv pkt not directed */
/* to local device is ignored */
#define SP_ADV_ALL 0x00
+/* 1: accept adv packet from device in white list, directed adv */
+/* packet not directed to local device is ignored */
+#define SP_ADV_WL 0x01
+/* 2: accept adv packet from all, directed adv pkt */
+/* not directed to me is ignored except direct adv with RPA */
+#define SP_ADV_ALL_RPA_DIR_ADV 0x02
+/* 3: accept adv packet from device in white list, directed */
+/* adv pkt not directed to me is ignored except direct adv with RPA */
+#define SP_ADV_WL_RPA_DIR_ADV 0x03
typedef uint8_t tBTM_BLE_SFP;
@@ -104,14 +107,20 @@ typedef uint8_t tBTM_BLE_SFP;
#define BTM_BLE_DEFAULT_SFP SP_ADV_ALL
#endif
+/* adv parameter boundary values */
+#define BTM_BLE_ADV_INT_MIN 0x0020
+#define BTM_BLE_ADV_INT_MAX 0x4000
+
/* Full scan boundary values */
#define BTM_BLE_ADV_SCAN_FULL_MIN 0x00
#define BTM_BLE_ADV_SCAN_FULL_MAX 0x64
/* Partial scan boundary values */
+#define BTM_BLE_ADV_SCAN_TRUNC_MIN BTM_BLE_ADV_SCAN_FULL_MIN
#define BTM_BLE_ADV_SCAN_TRUNC_MAX BTM_BLE_ADV_SCAN_FULL_MAX
/* Threshold values */
+#define BTM_BLE_ADV_SCAN_THR_MIN BTM_BLE_ADV_SCAN_FULL_MIN
#define BTM_BLE_ADV_SCAN_THR_MAX BTM_BLE_ADV_SCAN_FULL_MAX
/* connection parameter boundary values */
@@ -161,22 +170,18 @@ typedef uint8_t tBTM_BLE_SFP;
/* default connection interval min */
#ifndef BTM_BLE_CONN_INT_MIN_DEF
/* recommended min: 30ms = 24 * 1.25 */
-#ifndef BTM_BLE_CONN_INT_MIN_DEF
#define BTM_BLE_CONN_INT_MIN_DEF 24
#endif
-#endif
/* default connectino interval max */
#ifndef BTM_BLE_CONN_INT_MAX_DEF
/* recommended max: 50 ms = 56 * 1.25 */
-#ifndef BTM_BLE_CONN_INT_MAX_DEF
#define BTM_BLE_CONN_INT_MAX_DEF 40
#endif
-#endif
-/* default peripheral latency */
-#ifndef BTM_BLE_CONN_PERIPHERAL_LATENCY_DEF
-#define BTM_BLE_CONN_PERIPHERAL_LATENCY_DEF 0 /* 0 */
+/* default slave latency */
+#ifndef BTM_BLE_CONN_SLAVE_LATENCY_DEF
+#define BTM_BLE_CONN_SLAVE_LATENCY_DEF 0 /* 0 */
#endif
/* default supervision timeout */
@@ -278,6 +283,14 @@ typedef struct {
*/
typedef void(tBTM_RAND_ENC_CB)(tBTM_RAND_ENC* p1);
+#define BTM_BLE_FILTER_TARGET_SCANNER 0x01
+#define BTM_BLE_FILTER_TARGET_ADVR 0x00
+
+#define BTM_BLE_POLICY_BLACK_ALL 0x00 /* relevant to both */
+#define BTM_BLE_POLICY_ALLOW_SCAN 0x01 /* relevant to advertiser */
+#define BTM_BLE_POLICY_ALLOW_CONN 0x02 /* relevant to advertiser */
+#define BTM_BLE_POLICY_WHITE_ALL 0x03 /* relevant to both */
+
/* ADV data flag bit definition used for BTM_BLE_AD_TYPE_FLAG */
#define BTM_BLE_LIMIT_DISC_FLAG (0x01 << 0)
#define BTM_BLE_GEN_DISC_FLAG (0x01 << 1)
@@ -285,6 +298,10 @@ typedef void(tBTM_RAND_ENC_CB)(tBTM_RAND_ENC* p1);
/* 4.1 spec adv flag for simultaneous BR/EDR+LE connection support */
#define BTM_BLE_DMT_CONTROLLER_SPT (0x01 << 3)
#define BTM_BLE_DMT_HOST_SPT (0x01 << 4)
+#define BTM_BLE_NON_LIMIT_DISC_FLAG (0x00) /* lowest bit unset */
+#define BTM_BLE_ADV_FLAG_MASK \
+ (BTM_BLE_LIMIT_DISC_FLAG | BTM_BLE_BREDR_NOT_SPT | BTM_BLE_GEN_DISC_FLAG)
+#define BTM_BLE_LIMIT_DISC_MASK (BTM_BLE_LIMIT_DISC_FLAG)
// TODO(jpawlowski): this should be removed with code that depend on it.
#define BTM_BLE_AD_BIT_FLAGS (0x00000001 << 1)
@@ -293,8 +310,18 @@ typedef void(tBTM_RAND_ENC_CB)(tBTM_RAND_ENC* p1);
#define BTM_BLE_AD_TYPE_16SRV_CMPL \
HCI_EIR_COMPLETE_16BITS_UUID_TYPE /* 0x03 \
*/
+#define BTM_BLE_AD_TYPE_NAME_SHORT \
+ HCI_EIR_SHORTENED_LOCAL_NAME_TYPE /* 0x08 \
+ */
+#define BTM_BLE_AD_TYPE_NAME_CMPL HCI_EIR_COMPLETE_LOCAL_NAME_TYPE /* 0x09 */
+
#define BTM_BLE_AD_TYPE_APPEARANCE 0x19
+/* Security settings used with L2CAP LE COC */
+#define BTM_SEC_LE_LINK_ENCRYPTED 0x01
+#define BTM_SEC_LE_LINK_PAIRED_WITHOUT_MITM 0x02
+#define BTM_SEC_LE_LINK_PAIRED_WITH_MITM 0x04
+
/* Min/max Preferred number of payload octets that the local Controller
should include in a single Link Layer Data Channel PDU. */
#define BTM_BLE_DATA_SIZE_MAX 0x00fb
@@ -302,6 +329,7 @@ typedef void(tBTM_RAND_ENC_CB)(tBTM_RAND_ENC* p1);
/* Preferred maximum number of microseconds that the local Controller
should use to transmit a single Link Layer Data Channel PDU. */
+#define BTM_BLE_DATA_TX_TIME_MIN 0x0148
#define BTM_BLE_DATA_TX_TIME_MAX_LEGACY 0x0848
#define BTM_BLE_DATA_TX_TIME_MAX 0x4290
@@ -319,21 +347,8 @@ typedef struct {
uint16_t total_trackable_advertisers;
uint8_t extended_scan_support;
uint8_t debug_logging_supported;
- uint8_t le_address_generation_offloading_support;
- uint32_t a2dp_source_offload_capability_mask;
- uint8_t quality_report_support;
- uint32_t dynamic_audio_buffer_support;
} tBTM_BLE_VSC_CB;
-/* Stored the default/maximum/minimum buffer time for dynamic audio buffer.
- * For A2DP offload usage, the unit is millisecond.
- * For A2DP legacy usage, the unit is buffer queue size*/
-typedef struct {
- uint16_t default_buffer_time;
- uint16_t maximum_buffer_time;
- uint16_t minimum_buffer_time;
-} tBTM_BT_DYNAMIC_AUDIO_BUFFER_CB;
-
typedef void(tBTM_BLE_ADV_DATA_CMPL_CBACK)(tBTM_STATUS status);
#ifndef BTM_BLE_MULTI_ADV_MAX
@@ -346,7 +361,7 @@ typedef uint8_t tGATT_IF;
typedef void(tBTM_BLE_SCAN_THRESHOLD_CBACK)(tBTM_BLE_REF_VALUE ref_value);
using tBTM_BLE_SCAN_REP_CBACK =
- base::Callback<void(tBTM_STATUS /* status */, uint8_t /* report_format */,
+ base::Callback<void(uint8_t /* status */, uint8_t /* report_format */,
uint8_t /* num_reports */, std::vector<uint8_t>)>;
#ifndef BTM_BLE_BATCH_SCAN_MAX
@@ -413,9 +428,12 @@ typedef uint8_t tBTM_BLE_PF_LOGIC_TYPE;
#define BTM_BLE_PF_ENABLE 1
#define BTM_BLE_PF_CONFIG 2
+typedef uint8_t tBTM_BLE_PF_ACTION;
typedef uint8_t tBTM_BLE_PF_FILT_INDEX;
+typedef uint8_t tBTM_BLE_PF_AVBL_SPACE;
+
enum {
BTM_BLE_SCAN_COND_ADD,
BTM_BLE_SCAN_COND_DELETE,
@@ -425,15 +443,18 @@ typedef uint8_t tBTM_BLE_SCAN_COND_OP;
/* BLE adv payload filtering config complete callback */
using tBTM_BLE_PF_CFG_CBACK = base::Callback<void(
- uint8_t /* avbl_space */, uint8_t /* action */, uint8_t /* btm_status */)>;
+ uint8_t /* avbl_space */, uint8_t /* action */, uint8_t /* status */)>;
/* BLE adv payload filtering status setup complete callback */
using tBTM_BLE_PF_STATUS_CBACK =
- base::Callback<void(uint8_t /*action*/, uint8_t /* btm_status */)>;
+ base::Callback<void(uint8_t /*action*/, tBTM_STATUS /* status */)>;
/* BLE adv payload filtering param setup complete callback */
using tBTM_BLE_PF_PARAM_CB = base::Callback<void(
- uint8_t /* avbl_space */, uint8_t /* action */, uint8_t /* btm_status */)>;
+ uint8_t /* avbl_space */, uint8_t /* action */, uint8_t /* status */)>;
+
+/* per device filter + one generic filter indexed by 0 */
+#define BTM_BLE_MAX_FILTER_COUNTER (BTM_BLE_MAX_ADDR_FILTER + 1)
#ifndef BTM_CS_IRK_LIST_MAX
#define BTM_CS_IRK_LIST_MAX 0x20
@@ -464,6 +485,11 @@ typedef struct {
#define BTM_BLE_META_PF_SRVC_DATA 0x07
#define BTM_BLE_META_PF_ALL 0x08
+typedef uint8_t BTM_BLE_ADV_STATE;
+typedef uint8_t BTM_BLE_ADV_INFO_PRESENT;
+typedef uint8_t BTM_BLE_RSSI_VALUE;
+typedef uint16_t BTM_BLE_ADV_INFO_TIMESTAMP;
+
#define ADV_INFO_PRESENT 0x00
#define NO_ADV_INFO_PRESENT 0x01
@@ -472,11 +498,19 @@ typedef btgatt_track_adv_info_t tBTM_BLE_TRACK_ADV_DATA;
typedef void(tBTM_BLE_TRACK_ADV_CBACK)(
tBTM_BLE_TRACK_ADV_DATA* p_track_adv_data);
+typedef uint8_t tBTM_BLE_TRACK_ADV_EVT;
+
typedef struct {
tBTM_BLE_REF_VALUE ref_value;
tBTM_BLE_TRACK_ADV_CBACK* p_track_cback;
} tBTM_BLE_ADV_TRACK_CB;
+enum { BTM_BLE_TRACK_ADV_ADD, BTM_BLE_TRACK_ADV_REMOVE };
+
+typedef uint8_t tBTM_BLE_TRACK_ADV_ACTION;
+
+typedef uint8_t tBTM_BLE_BATCH_SCAN_EVT;
+
typedef uint32_t tBTM_BLE_TX_TIME_MS;
typedef uint32_t tBTM_BLE_RX_TIME_MS;
typedef uint32_t tBTM_BLE_IDLE_TIME_MS;
@@ -486,104 +520,15 @@ typedef void(tBTM_BLE_ENERGY_INFO_CBACK)(tBTM_BLE_TX_TIME_MS tx_time,
tBTM_BLE_RX_TIME_MS rx_time,
tBTM_BLE_IDLE_TIME_MS idle_time,
tBTM_BLE_ENERGY_USED energy_used,
- tHCI_STATUS status);
+ tBTM_STATUS status);
typedef struct {
tBTM_BLE_ENERGY_INFO_CBACK* p_ener_cback;
} tBTM_BLE_ENERGY_INFO_CB;
-typedef void(tBTM_BLE_CTRL_FEATURES_CBACK)(tHCI_STATUS status);
-
-/* BLE encryption keys */
-typedef struct {
- Octet16 ltk;
- BT_OCTET8 rand;
- uint16_t ediv;
- uint8_t sec_level;
- uint8_t key_size;
-} tBTM_LE_PENC_KEYS;
-
-/* BLE CSRK keys */
-typedef struct {
- uint32_t counter;
- Octet16 csrk;
- uint8_t sec_level;
-} tBTM_LE_PCSRK_KEYS;
-
-/* BLE Encryption reproduction keys */
-typedef struct {
- Octet16 ltk;
- uint16_t div;
- uint8_t key_size;
- uint8_t sec_level;
-} tBTM_LE_LENC_KEYS;
-
-/* BLE SRK keys */
-typedef struct {
- uint32_t counter;
- uint16_t div;
- uint8_t sec_level;
- Octet16 csrk;
-} tBTM_LE_LCSRK_KEYS;
-
-typedef struct {
- Octet16 irk;
- tBLE_ADDR_TYPE identity_addr_type;
- RawAddress identity_addr;
-} tBTM_LE_PID_KEYS;
-
-typedef union {
- tBTM_LE_PENC_KEYS penc_key; /* received peer encryption key */
- tBTM_LE_PCSRK_KEYS pcsrk_key; /* received peer device SRK */
- tBTM_LE_PID_KEYS pid_key; /* peer device ID key */
- tBTM_LE_LENC_KEYS lenc_key; /* local encryption reproduction keys
- * LTK = = d1(ER,DIV,0) */
- tBTM_LE_LCSRK_KEYS lcsrk_key; /* local device CSRK = d1(ER,DIV,1)*/
-} tBTM_LE_KEY_VALUE;
-
-typedef struct {
- tBTM_LE_KEY_TYPE key_type;
- tBTM_LE_KEY_VALUE* p_key_value;
-} tBTM_LE_KEY;
-
-typedef union {
- tBTM_LE_IO_REQ io_req; /* BTM_LE_IO_REQ_EVT */
- uint32_t key_notif; /* BTM_LE_KEY_NOTIF_EVT */
- /* BTM_LE_NC_REQ_EVT */
- /* no callback data for
- * BTM_LE_KEY_REQ_EVT
- * and BTM_LE_OOB_REQ_EVT */
- tBTM_LE_COMPLT complt; /* BTM_LE_COMPLT_EVT */
- tSMP_OOB_DATA_TYPE req_oob_type;
- tBTM_LE_KEY key;
- tSMP_LOC_OOB_DATA local_oob_data;
-} tBTM_LE_EVT_DATA;
-
-/* Simple Pairing Events. Called by the stack when Simple Pairing related
- * events occur.
- */
-typedef uint8_t(tBTM_LE_CALLBACK)(tBTM_LE_EVT event, const RawAddress& bda,
- tBTM_LE_EVT_DATA* p_data);
-
-#define BTM_BLE_KEY_TYPE_ID 1
-#define BTM_BLE_KEY_TYPE_ER 2
-#define BTM_BLE_KEY_TYPE_COUNTER 3 // tobe obsolete
-
-typedef struct {
- Octet16 ir;
- Octet16 irk;
- Octet16 dhk;
-
-} tBTM_BLE_LOCAL_ID_KEYS;
-
-typedef union {
- tBTM_BLE_LOCAL_ID_KEYS id_keys;
- Octet16 er;
-} tBTM_BLE_LOCAL_KEYS;
+typedef void(tBTM_BLE_CTRL_FEATURES_CBACK)(tBTM_STATUS status);
-/* New LE identity key for local device.
- */
-typedef void(tBTM_LE_KEY_CALLBACK)(uint8_t key_type,
- tBTM_BLE_LOCAL_KEYS* p_key);
+typedef void (*tBLE_SCAN_PARAM_SETUP_CBACK)(tGATT_IF client_if,
+ tBTM_STATUS status);
#endif // BTM_BLE_API_TYPES_H
diff --git a/stack/include/btm_client_interface.h b/stack/include/btm_client_interface.h
deleted file mode 100644
index 373d1c3d5..000000000
--- a/stack/include/btm_client_interface.h
+++ /dev/null
@@ -1,228 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include "stack/btm/neighbor_inquiry.h"
-#include "stack/include/acl_client_callbacks.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/btm_ble_api_types.h"
-#include "stack/include/btm_status.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcidefs.h"
-#include "stack/include/security_client_callbacks.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
-
-struct btm_client_interface_s {
- struct {
- tBTM_STATUS (*BTM_PmRegister)(uint8_t mask, uint8_t* p_pm_id,
- tBTM_PM_STATUS_CBACK* p_cback);
- uint16_t (*BTM_GetHCIConnHandle)(const RawAddress& bd_addr,
- tBT_TRANSPORT transport);
- void (*BTM_VendorSpecificCommand)(uint16_t opcode, uint8_t param_len,
- uint8_t* p_param_buf,
- tBTM_VSC_CMPL_CB* p_cb);
- void (*ACL_RegisterClient)(struct acl_client_callback_s* callbacks);
- void (*ACL_UnregisterClient)(struct acl_client_callback_s* callbacks);
- void (*btm_init)();
- void (*btm_free)();
- void (*btm_ble_init)();
- void (*btm_ble_free)();
- void (*BTM_reset_complete)();
- } lifecycle;
-
- struct {
- // Server channel number
- uint8_t (*BTM_AllocateSCN)(void);
- bool (*BTM_TryAllocateSCN)(uint8_t scn);
- bool (*BTM_FreeSCN)(uint8_t scn);
- } scn;
-
- // Neighbor
- struct {
- void (*BTM_CancelInquiry)();
- tBTM_INQ_INFO* (*BTM_InqDbNext)(tBTM_INQ_INFO* p_cur);
- tBTM_STATUS (*BTM_ClearInqDb)(const RawAddress* p_bda);
- tBTM_STATUS (*BTM_SetDiscoverability)(uint16_t inq_mode);
- tBTM_STATUS (*BTM_SetConnectability)(uint16_t page_mode);
- tBTM_STATUS (*BTM_StartInquiry)(tBTM_INQ_RESULTS_CB* p_results_cb,
- tBTM_CMPL_CB* p_cmpl_cb);
- uint16_t (*BTM_IsInquiryActive)(void);
- tBTM_STATUS (*BTM_SetInquiryMode)(uint8_t mode);
- void (*BTM_EnableInterlacedInquiryScan)();
- void (*BTM_EnableInterlacedPageScan)();
- } neighbor;
-
- // Acl peer and lifecycle
- struct {
- struct {
- bool (*SupportTransparentSynchronousData)(const RawAddress& bd_addr);
- } features;
-
- bool (*BTM_IsAclConnectionUp)(const RawAddress& bd_addr,
- tBT_TRANSPORT transport);
- bool (*BTM_ReadConnectedTransportAddress)(RawAddress* bd_addr,
- tBT_TRANSPORT transport);
- tBTM_STATUS (*BTM_CancelRemoteDeviceName)(void);
- tBTM_STATUS (*BTM_ReadRemoteDeviceName)(const RawAddress& bd_addr,
- tBTM_CMPL_CB* p_cb,
- tBT_TRANSPORT transport);
- uint8_t* (*BTM_ReadRemoteFeatures)(const RawAddress&);
- void (*BTM_ReadDevInfo)(const RawAddress& bd_addr,
- tBT_DEVICE_TYPE* p_dev_type,
- tBLE_ADDR_TYPE* p_addr_type);
- uint16_t (*BTM_GetMaxPacketSize)(const RawAddress& bd_addr);
- bool (*BTM_ReadRemoteVersion)(const RawAddress& addr, uint8_t* lmp_version,
- uint16_t* manufacturer,
- uint16_t* lmp_sub_version);
- } peer;
-
- struct {
- tBTM_STATUS (*BTM_GetRole)(const RawAddress& remote_bd_addr,
- tHCI_ROLE* p_role);
- tBTM_STATUS (*BTM_SetPowerMode)(uint8_t pm_id, const RawAddress& bd_addr,
- const tBTM_PM_PWR_MD* p_mode);
- tBTM_STATUS (*BTM_SetSsrParams)(const RawAddress& bd_addr, uint16_t max_lat,
- uint16_t min_rmt_to, uint16_t min_loc_to);
- tBTM_STATUS (*BTM_SwitchRoleToCentral)(const RawAddress& remote_bd_addr);
- void (*BTM_block_role_switch_for)(const RawAddress& peer_addr);
- void (*BTM_block_sniff_mode_for)(const RawAddress& peer_addr);
- void (*BTM_default_unblock_role_switch)();
- void (*BTM_unblock_role_switch_for)(const RawAddress& peer_addr);
- void (*BTM_unblock_sniff_mode_for)(const RawAddress& peer_addr);
- void (*BTM_WritePageTimeout)(uint16_t timeout);
- } link_policy;
-
- struct {
- tBTM_STATUS (*BTM_GetLinkSuperTout)(const RawAddress& bd_addr,
- uint16_t* p_timeout);
- tBTM_STATUS (*BTM_ReadRSSI)(const RawAddress& bd_addr, tBTM_CMPL_CB* p_cb);
- } link_controller;
-
- struct {
- bool (*BTM_SecAddDevice)(const RawAddress& bd_addr, DEV_CLASS dev_class,
- BD_NAME bd_name, uint8_t* features,
- LinkKey* link_key, uint8_t key_type,
- uint8_t pin_length);
- bool (*BTM_SecAddRmtNameNotifyCallback)(tBTM_RMT_NAME_CALLBACK* p_callback);
- bool (*BTM_SecDeleteDevice)(const RawAddress& bd_addr);
- bool (*BTM_SecDeleteRmtNameNotifyCallbac)(
- tBTM_RMT_NAME_CALLBACK* p_callback);
- bool (*BTM_SecRegister)(const tBTM_APPL_INFO* p_cb_info);
- char* (*BTM_SecReadDevName)(const RawAddress& bd_addr);
- tBTM_STATUS (*BTM_SecBond)(const RawAddress& bd_addr,
- tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type,
- uint8_t pin_len, uint8_t* p_pin);
- tBTM_STATUS (*BTM_SecBondCancel)(const RawAddress& bd_addr);
- void (*BTM_SecAddBleKey)(const RawAddress& bd_addr,
- tBTM_LE_KEY_VALUE* p_le_key,
- tBTM_LE_KEY_TYPE key_type);
- void (*BTM_SecAddBleDevice)(const RawAddress& bd_addr,
- tBT_DEVICE_TYPE dev_type,
- tBLE_ADDR_TYPE addr_type);
- void (*BTM_SecClearSecurityFlags)(const RawAddress& bd_addr);
- uint8_t (*BTM_SecClrService)(uint8_t service_id);
- uint8_t (*BTM_SecClrServiceByPsm)(uint16_t psm);
- void (*BTM_RemoteOobDataReply)(tBTM_STATUS res, const RawAddress& bd_addr,
- const Octet16& c, const Octet16& r);
- void (*BTM_PINCodeReply)(const RawAddress& bd_addr, uint8_t res,
- uint8_t pin_len, uint8_t* p_pin);
- void (*BTM_ConfirmReqReply)(tBTM_STATUS res, const RawAddress& bd_addr);
- bool (*BTM_SecDeleteRmtNameNotifyCallback)(
- tBTM_RMT_NAME_CALLBACK* p_callback);
- tBTM_STATUS (*BTM_SetEncryption)(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data,
- tBTM_BLE_SEC_ACT sec_act);
- bool (*BTM_IsEncrypted)(const RawAddress& bd_addr, tBT_TRANSPORT transport);
- bool (*BTM_SecIsSecurityPending)(const RawAddress& bd_addr);
- bool (*BTM_IsLinkKeyKnown)(const RawAddress& bd_addr,
- tBT_TRANSPORT transport);
- } security;
-
- struct {
- tBTM_STATUS (*BTM_BleGetEnergyInfo)(tBTM_BLE_ENERGY_INFO_CBACK* callback);
- tBTM_STATUS (*BTM_BleObserve)(bool start, uint8_t duration,
- tBTM_INQ_RESULTS_CB* p_results_cb,
- tBTM_CMPL_CB* p_cmpl_cb);
- tBTM_STATUS (*BTM_SetBleDataLength)(const RawAddress& bd_addr,
- uint16_t tx_pdu_length);
- void (*BTM_BleConfirmReply)(const RawAddress& bd_addr, uint8_t res);
- void (*BTM_BleLoadLocalKeys)(uint8_t key_type, tBTM_BLE_LOCAL_KEYS* p_key);
- void (*BTM_BlePasskeyReply)(const RawAddress& bd_addr, uint8_t res,
- uint32_t passkey);
- void (*BTM_BleReadControllerFeatures)(
- tBTM_BLE_CTRL_FEATURES_CBACK* p_vsc_cback);
- void (*BTM_BleSetConnScanParams)(uint32_t scan_interval,
- uint32_t scan_window);
- void (*BTM_BleSetPhy)(const RawAddress& bd_addr, uint8_t tx_phys,
- uint8_t rx_phys, uint16_t phy_options);
- void (*BTM_BleSetPrefConnParams)(const RawAddress& bd_addr,
- uint16_t min_conn_int,
- uint16_t max_conn_int,
- uint16_t peripheral_latency,
- uint16_t supervision_tout);
- bool (*BTM_UseLeLink)(const RawAddress& bd_addr);
- } ble;
-
- struct {
- tBTM_STATUS (*BTM_CreateSco)(const RawAddress* bd_addr, bool is_orig,
- uint16_t pkt_types, uint16_t* p_sco_inx,
- tBTM_SCO_CB* p_conn_cb,
- tBTM_SCO_CB* p_disc_cb);
- tBTM_STATUS (*BTM_RegForEScoEvts)(uint16_t sco_inx,
- tBTM_ESCO_CBACK* p_esco_cback);
- tBTM_STATUS (*BTM_RemoveSco)(uint16_t sco_inx);
- void (*BTM_WriteVoiceSettings)(uint16_t settings);
- void (*BTM_EScoConnRsp)(uint16_t sco_inx, uint8_t hci_status,
- enh_esco_params_t* p_parms);
- uint8_t (*BTM_GetNumScoLinks)();
- tBTM_STATUS (*BTM_SetEScoMode)(enh_esco_params_t* p_parms);
- } sco;
-
- struct {
- tBTM_STATUS (*BTM_ReadLocalDeviceNameFromController)(
- tBTM_CMPL_CB* p_rln_cmpl_cback);
- tBTM_STATUS (*BTM_SetLocalDeviceName)(char* p_name);
- tBTM_STATUS (*BTM_SetDeviceClass)(DEV_CLASS dev_class);
- bool (*BTM_IsDeviceUp)();
- uint8_t* (*BTM_ReadDeviceClass)();
- } local;
-
- struct {
- tBTM_STATUS (*BTM_WriteEIR)(BT_HDR* p_buff);
- uint8_t (*BTM_GetEirSupportedServices)(uint32_t* p_eir_uuid, uint8_t** p,
- uint8_t max_num_uuid16,
- uint8_t* p_num_uuid16);
- uint8_t (*BTM_GetEirUuidList)(uint8_t* p_eir, size_t eir_len,
- uint8_t uuid_size, uint8_t* p_num_uuid,
- uint8_t* p_uuid_list, uint8_t max_num_uuid);
- void (*BTM_RemoveEirService)(uint32_t* p_eir_uuid, uint16_t uuid16);
- } eir;
-
- struct {
- tBTM_INQ_INFO* (*BTM_InqDbRead)(const RawAddress& p_bda);
- tBTM_INQ_INFO* (*BTM_InqDbFirst)();
- tBTM_INQ_INFO* (*BTM_InqDbNext)(tBTM_INQ_INFO* p_cur);
- tBTM_STATUS (*BTM_ClearInqDb)(const RawAddress* p_bda);
- } db;
-};
-
-struct btm_client_interface_s& get_btm_client_interface();
diff --git a/stack/include/btm_iso_api.h b/stack/include/btm_iso_api.h
deleted file mode 100644
index dc3e91dd3..000000000
--- a/stack/include/btm_iso_api.h
+++ /dev/null
@@ -1,239 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <memory>
-#include <string>
-#include <vector>
-
-#include "btm_iso_api_types.h"
-
-namespace bluetooth {
-namespace hci {
-namespace iso_manager {
-struct CigCallbacks {
- virtual ~CigCallbacks() = default;
- virtual void OnSetupIsoDataPath(uint8_t status, uint16_t conn_handle,
- uint8_t cig_id) = 0;
- virtual void OnRemoveIsoDataPath(uint8_t status, uint16_t conn_handle,
- uint8_t cig_id) = 0;
- virtual void OnIsoLinkQualityRead(
- uint8_t conn_handle, uint8_t cig_id, uint32_t txUnackedPackets,
- uint32_t txFlushedPackets, uint32_t txLastSubeventPackets,
- uint32_t retransmittedPackets, uint32_t crcErrorPackets,
- uint32_t rxUnreceivedPackets, uint32_t duplicatePackets) = 0;
-
- virtual void OnCisEvent(uint8_t event, void* data) = 0;
- virtual void OnCigEvent(uint8_t event, void* data) = 0;
-};
-
-struct BigCallbacks {
- virtual ~BigCallbacks() = default;
- virtual void OnSetupIsoDataPath(uint8_t status, uint16_t conn_handle,
- uint8_t big_id) = 0;
- virtual void OnRemoveIsoDataPath(uint8_t status, uint16_t conn_handle,
- uint8_t big_id) = 0;
-
- virtual void OnBigEvent(uint8_t event, void* data) = 0;
-};
-} // namespace iso_manager
-
-class IsoManager {
- public:
- IsoManager();
- virtual ~IsoManager();
-
- static IsoManager* GetInstance() {
- static IsoManager* instance = new IsoManager();
- return instance;
- }
-
- /**
- * Set CIG and CIS related callbacks
- *
- * <p> Shall be set by the Le Audio Unicaster implementation
- *
- * @param callbacks CigCallbacks implementation
- */
- virtual void RegisterCigCallbacks(iso_manager::CigCallbacks* callbacks) const;
-
- /**
- * Set BIG related callbacks
- *
- * <p> Shall be set by the Le Audio Broadcaster implementation
- *
- * @param callbacks BigCallbacks implementation
- */
- virtual void RegisterBigCallbacks(iso_manager::BigCallbacks* callbacks) const;
-
- /**
- * Creates connected isochronous group (CIG) according to given params.
- *
- * @param cig_id connected isochronous group id
- * @param cig_params CIG parameters
- */
- virtual void CreateCig(uint8_t cig_id,
- struct iso_manager::cig_create_params cig_params);
-
- /**
- * Reconfigures connected isochronous group (CIG) according to given params.
- *
- * @param cig_id connected isochronous group id
- * @param cig_params CIG parameters
- */
- virtual void ReconfigureCig(uint8_t cig_id,
- struct iso_manager::cig_create_params cig_params);
-
- /**
- * Initiates removing of connected isochronous group (CIG).
- *
- * @param cig_id connected isochronous group id
- */
- virtual void RemoveCig(uint8_t cig_id);
-
- /**
- * Initiates creation of connected isochronous stream (CIS).
- *
- * @param conn_params A set of cis and acl connection handles
- */
- virtual void EstablishCis(
- struct iso_manager::cis_establish_params conn_params);
-
- /**
- * Initiates disconnection of connected isochronous stream (CIS).
- *
- * @param conn_handle CIS connection handle
- * @param reason HCI reason for disconnection
- */
- virtual void DisconnectCis(uint16_t conn_handle, uint8_t reason);
-
- /**
- * Initiates creation of isochronous data path for connected isochronous
- * stream.
- *
- * @param conn_handle handle of BIS or CIS connection
- * @param path_params iso data path parameters
- */
- virtual void SetupIsoDataPath(
- uint16_t conn_handle,
- struct iso_manager::iso_data_path_params path_params);
-
- /**
- * Initiates removal of isochronous data path for connected isochronous
- * stream.
- *
- * @param conn_handle handle of BIS or CIS connection
- * @param data_path_dir iso data path direction
- */
- virtual void RemoveIsoDataPath(uint16_t conn_handle, uint8_t data_path_dir);
-
- /**
- * Reads the ISO link quality. OnIsoLinkQualityRead callback is invoked only
- * if read is successful.
- *
- * @param conn_handle handle of ISO connection
- */
- virtual void ReadIsoLinkQuality(uint16_t conn_handle);
-
- /**
- * Sends iso data to the controller
- *
- * @param conn_handle handle of BIS or CIS connection
- * @param data data buffer. The ownership of data is not being transferred.
- * @param data_len data buffer length
- */
- virtual void SendIsoData(uint16_t conn_handle, const uint8_t* data,
- uint16_t data_len);
-
- /**
- * Creates the Broadcast Isochronous Group
- *
- * @param big_id host assigned BIG identifier
- * @param big_params BIG parameters
- */
- virtual void CreateBig(uint8_t big_id,
- struct iso_manager::big_create_params big_params);
-
- /**
- * Terminates the Broadcast Isochronous Group
- *
- * @param big_id host assigned BIG identifier
- * @param reason termination reason data
- */
- virtual void TerminateBig(uint8_t big_id, uint8_t reason);
-
- /* Below are defined handlers called by the legacy code in btu_hcif.cc */
-
- /**
- * Handles Iso Data packets from the controller
- *
- * @param p_msg raw data packet. The ownership of p_msg is not being
- * transferred.
- */
- virtual void HandleIsoData(void* p_msg);
-
- /**
- * Handles disconnect HCI event
- *
- * <p> This callback can be called with handles other than ISO connection
- * handles.
- *
- * @param conn_handle connection handle
- * @param reason HCI reason for disconnection
- */
- virtual void HandleDisconnect(uint16_t conn_handle, uint8_t reason);
-
- /**
- * Handles HCI event for the number of completed packets
- *
- * @param p raw packet buffer for the event. The ownership of p is not being
- * transferred.
- * @param evt_len event packet buffer length
- */
- virtual void HandleNumComplDataPkts(uint8_t* p, uint8_t evt_len);
-
- /**
- * Handle CIS and BIG related HCI events
- *
- * @param sub_code ble subcode for the HCI event
- * @param params raw packet buffer for the event. The ownership of params is
- * not being transferred
- * @param length event packet buffer length
- */
- virtual void HandleHciEvent(uint8_t sub_code, uint8_t* params,
- uint16_t length);
-
- /**
- * Starts the IsoManager module
- */
- void Start();
-
- /**
- * Stops the IsoManager module
- */
- void Stop();
-
- private:
- struct impl;
- std::unique_ptr<impl> pimpl_;
-
- DISALLOW_COPY_AND_ASSIGN(IsoManager);
-};
-
-} // namespace hci
-} // namespace bluetooth
diff --git a/stack/include/btm_iso_api_types.h b/stack/include/btm_iso_api_types.h
deleted file mode 100644
index 2009dd332..000000000
--- a/stack/include/btm_iso_api_types.h
+++ /dev/null
@@ -1,159 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "bt_types.h"
-#include "hcimsgs.h"
-
-namespace bluetooth {
-namespace hci {
-namespace iso_manager {
-
-constexpr uint8_t kIsoDataPathDirectionIn = 0x00;
-constexpr uint8_t kIsoDataPathDirectionOut = 0x01;
-
-constexpr uint8_t kIsoDataPathHci = 0x00;
-constexpr uint8_t kIsoDataPathDisabled = 0xFF;
-
-constexpr uint8_t kIsoSca251To500Ppm = 0x00;
-constexpr uint8_t kIsoSca151To250Ppm = 0x01;
-constexpr uint8_t kIsoSca101To150Ppm = 0x02;
-constexpr uint8_t kIsoSca76To100Ppm = 0x03;
-constexpr uint8_t kIsoSca51To75Ppm = 0x04;
-constexpr uint8_t kIsoSca31To50Ppm = 0x05;
-constexpr uint8_t kIsoSca21To30Ppm = 0x06;
-constexpr uint8_t kIsoSca0To20Ppm = 0x07;
-
-constexpr uint8_t kIsoEventCisDataAvailable = 0x00;
-constexpr uint8_t kIsoEventCisEstablishCmpl = 0x01;
-constexpr uint8_t kIsoEventCisDisconnected = 0x02;
-
-constexpr uint8_t kIsoEventCigOnCreateCmpl = 0x00;
-constexpr uint8_t kIsoEventCigOnReconfigureCmpl = 0x01;
-constexpr uint8_t kIsoEventCigOnRemoveCmpl = 0x02;
-
-constexpr uint8_t kIsoEventBigOnCreateCmpl = 0x00;
-constexpr uint8_t kIsoEventBigOnTerminateCmpl = 0x01;
-
-struct cig_create_params {
- uint32_t sdu_itv_mtos;
- uint32_t sdu_itv_stom;
- uint8_t sca;
- uint8_t packing;
- uint8_t framing;
- uint16_t max_trans_lat_stom;
- uint16_t max_trans_lat_mtos;
- std::vector<EXT_CIS_CFG> cis_cfgs;
-};
-
-struct cig_remove_cmpl_evt {
- uint8_t status;
- uint8_t cig_id;
-};
-
-struct cig_create_cmpl_evt {
- uint8_t status;
- uint8_t cig_id;
- std::vector<uint16_t> conn_handles;
-};
-
-struct cis_data_evt {
- uint8_t cig_id;
- uint16_t cis_conn_hdl;
- uint32_t ts;
- uint16_t evt_lost;
- BT_HDR* p_msg;
-};
-
-struct cis_establish_params {
- std::vector<EXT_CIS_CREATE_CFG> conn_pairs;
-};
-
-struct cis_establish_cmpl_evt {
- uint8_t status;
- uint8_t cig_id;
- uint16_t cis_conn_hdl;
- uint32_t cig_sync_delay;
- uint32_t cis_sync_delay;
- uint32_t trans_lat_mtos;
- uint32_t trans_lat_stom;
- uint8_t phy_mtos;
- uint8_t phy_stom;
- uint8_t nse;
- uint8_t bn_mtos;
- uint8_t bn_stom;
- uint8_t ft_mtos;
- uint8_t ft_stom;
- uint16_t max_pdu_mtos;
- uint16_t max_pdu_stom;
- uint16_t iso_itv;
-};
-
-struct cis_disconnected_evt {
- uint8_t reason;
- uint8_t cig_id;
- uint16_t cis_conn_hdl;
-};
-
-struct big_create_params {
- uint8_t adv_handle;
- uint8_t num_bis;
- uint32_t sdu_itv;
- uint16_t max_sdu_size;
- uint16_t max_transport_latency;
- uint8_t rtn;
- uint8_t phy;
- uint8_t packing;
- uint8_t framing;
- uint8_t enc;
- std::array<uint8_t, 16> enc_code;
-};
-
-struct big_create_cmpl_evt {
- uint8_t status;
- uint8_t big_id;
- uint32_t big_sync_delay;
- uint32_t transport_latency_big;
- uint8_t phy;
- uint8_t nse;
- uint8_t bn;
- uint8_t pto;
- uint8_t irc;
- uint16_t max_pdu;
- uint16_t iso_interval;
- std::vector<uint16_t> conn_handles;
-};
-
-struct big_terminate_cmpl_evt {
- uint8_t big_id;
- uint8_t reason;
-};
-
-struct iso_data_path_params {
- uint8_t data_path_dir;
- uint8_t data_path_id;
- uint8_t codec_id_format;
- uint16_t codec_id_company;
- uint16_t codec_id_vendor;
- uint32_t controller_delay;
- std::vector<uint8_t> codec_conf;
-};
-
-} // namespace iso_manager
-} // namespace hci
-} // namespace bluetooth
diff --git a/stack/include/btm_log_history.h b/stack/include/btm_log_history.h
deleted file mode 100644
index e9f1e0bb1..000000000
--- a/stack/include/btm_log_history.h
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <string>
-
-#include "types/ble_address_with_type.h"
-#include "types/raw_address.h"
-
-void BTM_LogHistory(const std::string& tag, const RawAddress& addr,
- const std::string& msg);
-void BTM_LogHistory(const std::string& tag, const RawAddress& addr,
- const std::string& msg, const std::string& extra);
-void BTM_LogHistory(const std::string& tag, const tBLE_BD_ADDR& addr,
- const std::string& msg);
-void BTM_LogHistory(const std::string& tag, const tBLE_BD_ADDR& addr,
- const std::string& msg, const std::string& extra);
diff --git a/stack/include/btm_status.h b/stack/include/btm_status.h
deleted file mode 100644
index 9d5057147..000000000
--- a/stack/include/btm_status.h
+++ /dev/null
@@ -1,94 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-
-/* BTM application return status codes */
-enum : uint8_t {
- BTM_SUCCESS = 0, /* 0 Command succeeded */
- BTM_CMD_STARTED, /* 1 Command started OK. */
- BTM_BUSY, /* 2 Device busy with another command */
- BTM_NO_RESOURCES, /* 3 No resources to issue command */
- BTM_MODE_UNSUPPORTED, /* 4 Request for 1 or more unsupported modes */
- BTM_ILLEGAL_VALUE, /* 5 Illegal parameter value */
- BTM_WRONG_MODE, /* 6 Device in wrong mode for request */
- BTM_UNKNOWN_ADDR, /* 7 Unknown remote BD address */
- BTM_DEVICE_TIMEOUT, /* 8 Device timeout */
- BTM_BAD_VALUE_RET, /* 9 A bad value was received from HCI */
- BTM_ERR_PROCESSING, /* 10 Generic error */
- BTM_NOT_AUTHORIZED, /* 11 Authorization failed */
- BTM_DEV_RESET, /* 12 Device has been reset */
- BTM_CMD_STORED, /* 13 request is stored in control block */
- BTM_ILLEGAL_ACTION, /* 14 state machine gets illegal command */
- BTM_DELAY_CHECK, /* 15 delay the check on encryption */
- BTM_SCO_BAD_LENGTH, /* 16 Bad SCO over HCI data length */
- BTM_SUCCESS_NO_SECURITY, /* 17 security passed, no security set */
- BTM_FAILED_ON_SECURITY, /* 18 security failed */
- BTM_REPEATED_ATTEMPTS, /* 19 repeated attempts for LE security requests */
- BTM_MODE4_LEVEL4_NOT_SUPPORTED, /* 20 Secure Connections Only Mode can't be
- supported */
- BTM_DEV_RESTRICT_LISTED, /* 21 The device is restrict listed */
- BTM_MAX_STATUS_VALUE = BTM_DEV_RESTRICT_LISTED,
- BTM_UNDEFINED = 0xFF,
-};
-typedef uint8_t tBTM_STATUS;
-
-inline uint8_t btm_status_value(const tBTM_STATUS& status) {
- return static_cast<uint8_t>(status);
-}
-
-inline tBTM_STATUS to_btm_status(const uint8_t& value) {
- if (value > BTM_MAX_STATUS_VALUE) return BTM_UNDEFINED;
- return static_cast<tBTM_STATUS>(value);
-}
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string btm_status_text(const tBTM_STATUS& status) {
- switch (status) {
- CASE_RETURN_TEXT(BTM_SUCCESS);
- CASE_RETURN_TEXT(BTM_CMD_STARTED);
- CASE_RETURN_TEXT(BTM_BUSY);
- CASE_RETURN_TEXT(BTM_NO_RESOURCES);
- CASE_RETURN_TEXT(BTM_MODE_UNSUPPORTED);
- CASE_RETURN_TEXT(BTM_ILLEGAL_VALUE);
- CASE_RETURN_TEXT(BTM_WRONG_MODE);
- CASE_RETURN_TEXT(BTM_UNKNOWN_ADDR);
- CASE_RETURN_TEXT(BTM_DEVICE_TIMEOUT);
- CASE_RETURN_TEXT(BTM_BAD_VALUE_RET);
- CASE_RETURN_TEXT(BTM_ERR_PROCESSING);
- CASE_RETURN_TEXT(BTM_NOT_AUTHORIZED);
- CASE_RETURN_TEXT(BTM_DEV_RESET);
- CASE_RETURN_TEXT(BTM_CMD_STORED);
- CASE_RETURN_TEXT(BTM_ILLEGAL_ACTION);
- CASE_RETURN_TEXT(BTM_DELAY_CHECK);
- CASE_RETURN_TEXT(BTM_SCO_BAD_LENGTH);
- CASE_RETURN_TEXT(BTM_SUCCESS_NO_SECURITY);
- CASE_RETURN_TEXT(BTM_FAILED_ON_SECURITY);
- CASE_RETURN_TEXT(BTM_REPEATED_ATTEMPTS);
- CASE_RETURN_TEXT(BTM_MODE4_LEVEL4_NOT_SUPPORTED);
- CASE_RETURN_TEXT(BTM_DEV_RESTRICT_LISTED);
- default:
- return std::string("UNKNOWN[%hhu]", status);
- }
-}
-
-#undef CASE_RETURN_TEXT
diff --git a/stack/include/btu.h b/stack/include/btu.h
index f5a5c8a8d..03fe2a196 100644
--- a/stack/include/btu.h
+++ b/stack/include/btu.h
@@ -49,17 +49,24 @@ void btu_hcif_send_cmd_with_cb(const base::Location& posted_from,
uint8_t params_len,
base::OnceCallback<void(uint8_t*, uint16_t)> cb);
+/* Functions provided by btu_init.cc
+ ***********************************
+*/
+void btu_init_core(void);
+void btu_free_core(void);
+
/* Functions provided by btu_task.cc
***********************************
*/
bluetooth::common::MessageLoopThread* get_main_thread();
+base::MessageLoop* get_main_message_loop();
bt_status_t do_in_main_thread(const base::Location& from_here,
base::OnceClosure task);
bt_status_t do_in_main_thread_delayed(const base::Location& from_here,
base::OnceClosure task,
const base::TimeDelta& delay);
-using BtMainClosure = std::function<void()>;
-void post_on_bt_main(BtMainClosure closure);
+void BTU_StartUp(void);
+void BTU_ShutDown(void);
#endif
diff --git a/stack/include/dev_hci_link_interface.h b/stack/include/dev_hci_link_interface.h
deleted file mode 100644
index 4ac6fbb23..000000000
--- a/stack/include/dev_hci_link_interface.h
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include <cstdint>
-
-#include "types/raw_address.h"
-
-extern void btm_delete_stored_link_key_complete(uint8_t* p);
-extern void btm_vendor_specific_evt(uint8_t* p, uint8_t evt_len);
-extern void btm_vsc_complete(uint8_t* p, uint16_t cc_opcode, uint16_t evt_len,
- tBTM_VSC_CMPL_CB* p_vsc_cplt_cback);
-extern void btm_read_local_name_complete(uint8_t* p, uint16_t evt_len);
diff --git a/stack/include/gap_api.h b/stack/include/gap_api.h
index f3b57f7b0..9293378f2 100644
--- a/stack/include/gap_api.h
+++ b/stack/include/gap_api.h
@@ -22,31 +22,74 @@
#include "btm_api.h"
#include "l2c_api.h"
#include "profiles_api.h"
-#include "types/bt_transport.h"
/*****************************************************************************
* Constants
****************************************************************************/
/*** GAP Error and Status Codes ***/
+/* Unsupported call */
+#define GAP_UNSUPPORTED (GAP_ERR_GRP + 0x01)
+/* End of inquiry database marker */
+#define GAP_EOINQDB (GAP_ERR_GRP + 0x02)
+/* The requested function was busy */
+#define GAP_ERR_BUSY (GAP_ERR_GRP + 0x03)
+/* No control blocks available */
+#define GAP_ERR_NO_CTRL_BLK (GAP_ERR_GRP + 0x04)
+/* Error occurred while initiating the command */
+#define GAP_ERR_STARTING_CMD (GAP_ERR_GRP + 0x05)
+/* No Inquiry DB record for BD_ADDR */
+#define GAP_NO_BDADDR_REC (GAP_ERR_GRP + 0x06)
+/* An illegal mode parameter was detected */
+#define GAP_ERR_ILL_MODE (GAP_ERR_GRP + 0x07)
+/* An illegal time parameter was detected */
+#define GAP_ERR_ILL_INQ_TIME (GAP_ERR_GRP + 0x08)
/* An illegal parameter was detected */
#define GAP_ERR_ILL_PARM (GAP_ERR_GRP + 0x09)
+/* Error starting the remote device name request */
+#define GAP_ERR_REM_NAME (GAP_ERR_GRP + 0x0a)
+/* The GAP command was started (result pending) */
+#define GAP_CMD_INITIATED (GAP_ERR_GRP + 0x0b)
+/* The device was not up; the request was not executed */
+#define GAP_DEVICE_NOT_UP (GAP_ERR_GRP + 0x0c)
+/* The bd addr passed in was not found or invalid */
+#define GAP_BAD_BD_ADDR (GAP_ERR_GRP + 0x0d)
/* Bad GAP handle */
#define GAP_ERR_BAD_HANDLE (GAP_ERR_GRP + 0x0e)
+/* Buffer offset invalid */
+#define GAP_ERR_BUF_OFFSET (GAP_ERR_GRP + 0x0f)
/* Connection is in invalid state */
#define GAP_ERR_BAD_STATE (GAP_ERR_GRP + 0x10)
/* No data available */
#define GAP_NO_DATA_AVAIL (GAP_ERR_GRP + 0x11)
+/* BT stack is congested */
+#define GAP_ERR_CONGESTED (GAP_ERR_GRP + 0x12)
+/* Security failed */
+#define GAP_ERR_SECURITY (GAP_ERR_GRP + 0x13)
+
+/* General error processing BTM request */
+#define GAP_ERR_PROCESSING (GAP_ERR_GRP + 0x14)
+/* Timeout occurred while processing cmd */
+#define GAP_ERR_TIMEOUT (GAP_ERR_GRP + 0x15)
#define GAP_EVT_CONN_OPENED 0x0100
#define GAP_EVT_CONN_CLOSED 0x0101
#define GAP_EVT_CONN_DATA_AVAIL 0x0102
#define GAP_EVT_CONN_CONGESTED 0x0103
#define GAP_EVT_CONN_UNCONGESTED 0x0104
#define GAP_EVT_TX_EMPTY 0x0105
+#define GAP_EVT_LE_COC_CREDITS 0x0106
+/* Values for 'chan_mode_mask' field */
+/* GAP_ConnOpen() - optional channels to negotiate */
+#define GAP_FCR_CHAN_OPT_BASIC L2CAP_FCR_CHAN_OPT_BASIC
+#define GAP_FCR_CHAN_OPT_ERTM L2CAP_FCR_CHAN_OPT_ERTM
+#define GAP_FCR_CHAN_OPT_STREAM L2CAP_FCR_CHAN_OPT_STREAM
/*** used in connection variables and functions ***/
#define GAP_INVALID_HANDLE 0xFFFF
+/* This is used to change the criteria for AMP */
+#define GAP_PROTOCOL_ID (UUID_PROTOCOL_UDP)
+
#ifndef GAP_PREFER_CONN_INT_MAX
#define GAP_PREFER_CONN_INT_MAX BTM_BLE_CONN_INT_MIN
#endif
@@ -64,6 +107,7 @@
#endif
struct tGAP_COC_CREDITS {
+ uint16_t gap_handle;
uint16_t credits_received;
uint16_t credit_count;
};
@@ -81,6 +125,19 @@ union tGAP_CB_DATA {
typedef void(tGAP_CONN_CALLBACK)(uint16_t gap_handle, uint16_t event,
tGAP_CB_DATA* data);
+/*
+ * Define the callback function prototypes. Parameters are specific
+ * to each event and are described below
+*/
+typedef void(tGAP_CALLBACK)(uint16_t event, void* p_data);
+
+/* Definition of the GAP_FindAddrByName results structure */
+typedef struct {
+ uint16_t status;
+ RawAddress bd_addr;
+ tBTM_BD_NAME devname;
+} tGAP_FINDADDR_RESULTS;
+
typedef struct {
uint16_t int_min;
uint16_t int_max;
@@ -121,7 +178,8 @@ extern uint16_t GAP_ConnOpen(const char* p_serv_name, uint8_t service_id,
uint16_t psm, uint16_t le_mps,
tL2CAP_CFG_INFO* p_cfg,
tL2CAP_ERTM_INFO* ertm_info, uint16_t security,
- tGAP_CONN_CALLBACK* p_cb, tBT_TRANSPORT transport);
+ uint8_t chan_mode_mask, tGAP_CONN_CALLBACK* p_cb,
+ tBT_TRANSPORT transport);
/*******************************************************************************
*
@@ -166,6 +224,21 @@ extern int GAP_GetRxQueueCnt(uint16_t handle, uint32_t* p_rx_queue_count);
/*******************************************************************************
*
+ * Function GAP_ConnBTRead
+ *
+ * Description GKI buffer aware applications will call this function after
+ * receiving an GAP_EVT_RXDATA event to process the incoming
+ * data buffer.
+ *
+ * Returns BT_PASS - data read
+ * GAP_ERR_BAD_HANDLE - invalid handle
+ * GAP_NO_DATA_AVAIL - no data available
+ *
+ ******************************************************************************/
+extern uint16_t GAP_ConnBTRead(uint16_t gap_handle, BT_HDR** pp_buf);
+
+/*******************************************************************************
+ *
* Function GAP_ConnWriteData
*
* Description GKI buffer unaware application will call this function
@@ -182,6 +255,37 @@ extern uint16_t GAP_ConnWriteData(uint16_t gap_handle, BT_HDR* msg);
/*******************************************************************************
*
+ * Function GAP_ConnReconfig
+ *
+ * Description Applications can call this function to reconfigure the
+ * connection.
+ *
+ * Returns BT_PASS - config process started
+ * GAP_ERR_BAD_HANDLE - invalid handle
+ *
+ ******************************************************************************/
+extern uint16_t GAP_ConnReconfig(uint16_t gap_handle, tL2CAP_CFG_INFO* p_cfg);
+
+/*******************************************************************************
+ *
+ * Function GAP_ConnSetIdleTimeout
+ *
+ * Description Higher layers call this function to set the idle timeout for
+ * a connection, or for all future connections. The "idle
+ * timeout" is the amount of time that a connection can remain
+ * up with no L2CAP channels on it. A timeout of zero means
+ * that the connection will be torn down immediately when the
+ * last channel is removed. A timeout of 0xFFFF means no
+ * timeout. Values are in seconds.
+ *
+ * Returns BT_PASS - config process started
+ * GAP_ERR_BAD_HANDLE - invalid handle
+ *
+ ******************************************************************************/
+extern uint16_t GAP_ConnSetIdleTimeout(uint16_t gap_handle, uint16_t timeout);
+
+/*******************************************************************************
+ *
* Function GAP_ConnGetRemoteAddr
*
* Description This function is called to get the remote BD address
@@ -271,6 +375,18 @@ extern bool GAP_BleReadPeerDevName(const RawAddress& peer_bda,
/*******************************************************************************
*
+ * Function GAP_BleReadPeerAddressResolutionCap
+ *
+ * Description Start a process to read peer address resolution capability
+ *
+ * Returns true if request accepted
+ *
+ ******************************************************************************/
+extern bool GAP_BleReadPeerAddressResolutionCap(const RawAddress& peer_bda,
+ tGAP_BLE_CMPL_CBACK* p_cback);
+
+/*******************************************************************************
+ *
* Function GAP_BleCancelReadPeerDevName
*
* Description Cancel reading a peripheral's device name.
diff --git a/stack/include/gatt_api.h b/stack/include/gatt_api.h
index c6c9890b6..069a17984 100644
--- a/stack/include/gatt_api.h
+++ b/stack/include/gatt_api.h
@@ -18,219 +18,116 @@
#ifndef GATT_API_H
#define GATT_API_H
-#include <base/strings/stringprintf.h>
-#include <string>
-
#include "bt_target.h"
#include "btm_ble_api.h"
#include "gattdefs.h"
-#include "types/bt_transport.h"
/*****************************************************************************
* Constants
****************************************************************************/
/* Success code and error codes */
-typedef enum GattStatus : uint8_t {
- GATT_SUCCESS = 0x00,
- GATT_INVALID_HANDLE = 0x01,
- GATT_READ_NOT_PERMIT = 0x02,
- GATT_WRITE_NOT_PERMIT = 0x03,
- GATT_INVALID_PDU = 0x04,
- GATT_INSUF_AUTHENTICATION = 0x05,
- GATT_REQ_NOT_SUPPORTED = 0x06,
- GATT_INVALID_OFFSET = 0x07,
- GATT_INSUF_AUTHORIZATION = 0x08,
- GATT_PREPARE_Q_FULL = 0x09,
- GATT_NOT_FOUND = 0x0a,
- GATT_NOT_LONG = 0x0b,
- GATT_INSUF_KEY_SIZE = 0x0c,
- GATT_INVALID_ATTR_LEN = 0x0d,
- GATT_ERR_UNLIKELY = 0x0e,
- GATT_INSUF_ENCRYPTION = 0x0f,
- GATT_UNSUPPORT_GRP_TYPE = 0x10,
- GATT_INSUF_RESOURCE = 0x11,
- GATT_DATABASE_OUT_OF_SYNC = 0x12,
- GATT_VALUE_NOT_ALLOWED = 0x13,
- GATT_ILLEGAL_PARAMETER = 0x87,
- GATT_TOO_SHORT = 0x7f,
- GATT_NO_RESOURCES = 0x80,
- GATT_INTERNAL_ERROR = 0x81,
- GATT_WRONG_STATE = 0x82,
- GATT_DB_FULL = 0x83,
- GATT_BUSY = 0x84,
- GATT_ERROR = 0x85,
- GATT_CMD_STARTED = 0x86,
- GATT_PENDING = 0x88,
- GATT_AUTH_FAIL = 0x89,
- GATT_MORE = 0x8a,
- GATT_INVALID_CFG = 0x8b,
- GATT_SERVICE_STARTED = 0x8c,
- GATT_ENCRYPED_MITM = GATT_SUCCESS,
- GATT_ENCRYPED_NO_MITM = 0x8d,
- GATT_NOT_ENCRYPTED = 0x8e,
- GATT_CONGESTED = 0x8f,
- GATT_DUP_REG = 0x90, /* 0x90 */
- GATT_ALREADY_OPEN = 0x91, /* 0x91 */
- GATT_CANCEL = 0x92, /* 0x92 */
- /* = 0xE0 ~ 0xFC reserved for future use */
-
- /* Client Characteristic Configuration Descriptor Improperly Configured */
- GATT_CCC_CFG_ERR = 0xFD,
- /* Procedure Already in progress */
- GATT_PRC_IN_PROGRESS = 0xFE,
- /* Attribute value out of range */
- GATT_OUT_OF_RANGE = 0xFF,
-} tGATT_STATUS;
-
-typedef enum : uint8_t {
- GATT_RSP_ERROR = 0x01,
- GATT_REQ_MTU = 0x02,
- GATT_RSP_MTU = 0x03,
- GATT_REQ_FIND_INFO = 0x04,
- GATT_RSP_FIND_INFO = 0x05,
- GATT_REQ_FIND_TYPE_VALUE = 0x06,
- GATT_RSP_FIND_TYPE_VALUE = 0x07,
- GATT_REQ_READ_BY_TYPE = 0x08,
- GATT_RSP_READ_BY_TYPE = 0x09,
- GATT_REQ_READ = 0x0A,
- GATT_RSP_READ = 0x0B,
- GATT_REQ_READ_BLOB = 0x0C,
- GATT_RSP_READ_BLOB = 0x0D,
- GATT_REQ_READ_MULTI = 0x0E,
- GATT_RSP_READ_MULTI = 0x0F,
- GATT_REQ_READ_BY_GRP_TYPE = 0x10,
- GATT_RSP_READ_BY_GRP_TYPE = 0x11,
- /* 0001-0010 (write)*/
- GATT_REQ_WRITE = 0x12,
- GATT_RSP_WRITE = 0x13,
- /* changed in V4.0 01001-0010(write cmd)*/
- GATT_CMD_WRITE = 0x52,
- GATT_REQ_PREPARE_WRITE = 0x16,
- GATT_RSP_PREPARE_WRITE = 0x17,
- GATT_REQ_EXEC_WRITE = 0x18,
- GATT_RSP_EXEC_WRITE = 0x19,
- GATT_HANDLE_VALUE_NOTIF = 0x1B,
- GATT_HANDLE_VALUE_IND = 0x1D,
- GATT_HANDLE_VALUE_CONF = 0x1E,
-
- GATT_REQ_READ_MULTI_VAR = 0x20,
- GATT_RSP_READ_MULTI_VAR = 0x21,
- GATT_HANDLE_MULTI_VALUE_NOTIF = 0x23,
-
- /* changed in V4.0 1101-0010 (signed write) see write cmd above*/
- GATT_SIGN_CMD_WRITE = 0xD2,
- /* 0x1E = 30 + 1 = 31*/
- GATT_OP_CODE_MAX = (GATT_HANDLE_MULTI_VALUE_NOTIF + 1),
-} tGATT_OP_CODE;
-
-inline std::string gatt_op_code_text(const tGATT_OP_CODE& op_code) {
- switch (op_code) {
- case GATT_RSP_ERROR:
- return std::string("GATT_RSP_ERROR");
- case GATT_REQ_MTU:
- return std::string("GATT_REQ_MTU");
- case GATT_RSP_MTU:
- return std::string("GATT_RSP_MTU");
- case GATT_REQ_FIND_INFO:
- return std::string("GATT_REQ_FIND_INFO");
- case GATT_RSP_FIND_INFO:
- return std::string("GATT_RSP_FIND_INFO");
- case GATT_REQ_FIND_TYPE_VALUE:
- return std::string("GATT_REQ_FIND_TYPE_VALUE");
- case GATT_RSP_FIND_TYPE_VALUE:
- return std::string("GATT_RSP_FIND_TYPE_VALUE");
- case GATT_REQ_READ_BY_TYPE:
- return std::string("GATT_REQ_READ_BY_TYPE");
- case GATT_RSP_READ_BY_TYPE:
- return std::string("GATT_RSP_READ_BY_TYPE");
- case GATT_REQ_READ:
- return std::string("GATT_REQ_READ");
- case GATT_RSP_READ:
- return std::string("GATT_RSP_READ");
- case GATT_REQ_READ_BLOB:
- return std::string("GATT_REQ_READ_BLOB");
- case GATT_RSP_READ_BLOB:
- return std::string("GATT_RSP_READ_BLOB");
- case GATT_REQ_READ_MULTI:
- return std::string("GATT_REQ_READ_MULTI");
- case GATT_RSP_READ_MULTI:
- return std::string("GATT_RSP_READ_MULTI");
- case GATT_REQ_READ_BY_GRP_TYPE:
- return std::string("GATT_REQ_READ_BY_GRP_TYPE");
- case GATT_RSP_READ_BY_GRP_TYPE:
- return std::string("GATT_RSP_READ_BY_GRP_TYPE");
- case GATT_REQ_WRITE:
- return std::string("GATT_REQ_WRITE");
- case GATT_RSP_WRITE:
- return std::string("GATT_RSP_WRITE");
- case GATT_CMD_WRITE:
- return std::string("GATT_CMD_WRITE");
- case GATT_REQ_PREPARE_WRITE:
- return std::string("GATT_REQ_PREPARE_WRITE");
- case GATT_RSP_PREPARE_WRITE:
- return std::string("GATT_RSP_PREPARE_WRITE");
- case GATT_REQ_EXEC_WRITE:
- return std::string("GATT_REQ_EXEC_WRITE");
- case GATT_RSP_EXEC_WRITE:
- return std::string("GATT_RSP_EXEC_WRITE");
- case GATT_HANDLE_VALUE_NOTIF:
- return std::string("GATT_HANDLE_VALUE_NOTIF");
- case GATT_HANDLE_VALUE_IND:
- return std::string("GATT_HANDLE_VALUE_IND");
- case GATT_HANDLE_VALUE_CONF:
- return std::string("GATT_HANDLE_VALUE_CONF");
- case GATT_REQ_READ_MULTI_VAR:
- return std::string("GATT_REQ_READ_MULTI_VAR");
- case GATT_RSP_READ_MULTI_VAR:
- return std::string("GATT_RSP_READ_MULTI_VAR");
- case GATT_HANDLE_MULTI_VALUE_NOTIF:
- return std::string("GATT_HANDLE_MULTI_VALUE_NOTIF");
- case GATT_SIGN_CMD_WRITE:
- return std::string("GATT_SIGN_CMD_WRITE");
- case GATT_OP_CODE_MAX:
- return std::string("GATT_OP_CODE_MAX");
- };
-}
+#define GATT_SUCCESS 0x00
+#define GATT_INVALID_HANDLE 0x01
+#define GATT_READ_NOT_PERMIT 0x02
+#define GATT_WRITE_NOT_PERMIT 0x03
+#define GATT_INVALID_PDU 0x04
+#define GATT_INSUF_AUTHENTICATION 0x05
+#define GATT_REQ_NOT_SUPPORTED 0x06
+#define GATT_INVALID_OFFSET 0x07
+#define GATT_INSUF_AUTHORIZATION 0x08
+#define GATT_PREPARE_Q_FULL 0x09
+#define GATT_NOT_FOUND 0x0a
+#define GATT_NOT_LONG 0x0b
+#define GATT_INSUF_KEY_SIZE 0x0c
+#define GATT_INVALID_ATTR_LEN 0x0d
+#define GATT_ERR_UNLIKELY 0x0e
+#define GATT_INSUF_ENCRYPTION 0x0f
+#define GATT_UNSUPPORT_GRP_TYPE 0x10
+#define GATT_INSUF_RESOURCE 0x11
+
+#define GATT_ILLEGAL_PARAMETER 0x87
+#define GATT_NO_RESOURCES 0x80
+#define GATT_INTERNAL_ERROR 0x81
+#define GATT_WRONG_STATE 0x82
+#define GATT_DB_FULL 0x83
+#define GATT_BUSY 0x84
+#define GATT_ERROR 0x85
+#define GATT_CMD_STARTED 0x86
+#define GATT_PENDING 0x88
+#define GATT_AUTH_FAIL 0x89
+#define GATT_MORE 0x8a
+#define GATT_INVALID_CFG 0x8b
+#define GATT_SERVICE_STARTED 0x8c
+#define GATT_ENCRYPED_MITM GATT_SUCCESS
+#define GATT_ENCRYPED_NO_MITM 0x8d
+#define GATT_NOT_ENCRYPTED 0x8e
+#define GATT_CONGESTED 0x8f
+
+#define GATT_DUP_REG 0x90 /* 0x90 */
+#define GATT_ALREADY_OPEN 0x91 /* 0x91 */
+#define GATT_CANCEL 0x92 /* 0x92 */
+/* 0xE0 ~ 0xFC reserved for future use */
+
+/* Client Characteristic Configuration Descriptor Improperly Configured */
+#define GATT_CCC_CFG_ERR 0xFD
+/* Procedure Already in progress */
+#define GATT_PRC_IN_PROGRESS 0xFE
+/* Attribute value out of range */
+#define GATT_OUT_OF_RANGE 0xFF
+typedef uint8_t tGATT_STATUS;
+
+#define GATT_RSP_ERROR 0x01
+#define GATT_REQ_MTU 0x02
+#define GATT_RSP_MTU 0x03
+#define GATT_REQ_FIND_INFO 0x04
+#define GATT_RSP_FIND_INFO 0x05
+#define GATT_REQ_FIND_TYPE_VALUE 0x06
+#define GATT_RSP_FIND_TYPE_VALUE 0x07
+#define GATT_REQ_READ_BY_TYPE 0x08
+#define GATT_RSP_READ_BY_TYPE 0x09
+#define GATT_REQ_READ 0x0A
+#define GATT_RSP_READ 0x0B
+#define GATT_REQ_READ_BLOB 0x0C
+#define GATT_RSP_READ_BLOB 0x0D
+#define GATT_REQ_READ_MULTI 0x0E
+#define GATT_RSP_READ_MULTI 0x0F
+#define GATT_REQ_READ_BY_GRP_TYPE 0x10
+#define GATT_RSP_READ_BY_GRP_TYPE 0x11
+/* 0001-0010 (write)*/
+#define GATT_REQ_WRITE 0x12
+#define GATT_RSP_WRITE 0x13
+/* changed in V4.0 01001-0010(write cmd)*/
+#define GATT_CMD_WRITE 0x52
+#define GATT_REQ_PREPARE_WRITE 0x16
+#define GATT_RSP_PREPARE_WRITE 0x17
+#define GATT_REQ_EXEC_WRITE 0x18
+#define GATT_RSP_EXEC_WRITE 0x19
+#define GATT_HANDLE_VALUE_NOTIF 0x1B
+#define GATT_HANDLE_VALUE_IND 0x1D
+#define GATT_HANDLE_VALUE_CONF 0x1E
+/* changed in V4.0 1101-0010 (signed write) see write cmd above*/
+#define GATT_SIGN_CMD_WRITE 0xD2
+/* 0x1E = 30 + 1 = 31*/
+#define GATT_OP_CODE_MAX (GATT_HANDLE_VALUE_CONF + 1)
#define GATT_HANDLE_IS_VALID(x) ((x) != 0)
-typedef enum : uint16_t {
- GATT_CONN_OK = 0,
- GATT_CONN_UNKNOWN = 0,
- /* general L2cap failure */
- GATT_CONN_L2C_FAILURE = 1,
- /* 0x08 connection timeout */
- GATT_CONN_TIMEOUT = HCI_ERR_CONNECTION_TOUT,
- /* 0x13 connection terminate by peer user */
- GATT_CONN_TERMINATE_PEER_USER = HCI_ERR_PEER_USER,
- /* 0x16 connectionterminated by local host */
- GATT_CONN_TERMINATE_LOCAL_HOST = HCI_ERR_CONN_CAUSE_LOCAL_HOST,
- /* 0x22 connection fail for LMP response tout */
- GATT_CONN_LMP_TIMEOUT = HCI_ERR_LMP_RESPONSE_TIMEOUT,
-
- BTA_GATT_CONN_NONE = 0x0101, /* 0x0101 no connection to cancel */
-
-} tGATT_DISCONN_REASON;
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string gatt_disconnection_reason_text(
- const tGATT_DISCONN_REASON& reason) {
- switch (reason) {
- CASE_RETURN_TEXT(GATT_CONN_OK);
- CASE_RETURN_TEXT(GATT_CONN_L2C_FAILURE);
- CASE_RETURN_TEXT(GATT_CONN_TIMEOUT);
- CASE_RETURN_TEXT(GATT_CONN_TERMINATE_PEER_USER);
- CASE_RETURN_TEXT(GATT_CONN_TERMINATE_LOCAL_HOST);
- CASE_RETURN_TEXT(GATT_CONN_LMP_TIMEOUT);
- CASE_RETURN_TEXT(BTA_GATT_CONN_NONE);
- default:
- return std::string("UNKNOWN[%hu]", reason);
- }
-}
-#undef CASE_RETURN_TEXT
+#define GATT_CONN_UNKNOWN 0
+/* general L2cap failure */
+#define GATT_CONN_L2C_FAILURE 1
+/* 0x08 connection timeout */
+#define GATT_CONN_TIMEOUT HCI_ERR_CONNECTION_TOUT
+/* 0x13 connection terminate by peer user */
+#define GATT_CONN_TERMINATE_PEER_USER HCI_ERR_PEER_USER
+/* 0x16 connectionterminated by local host */
+#define GATT_CONN_TERMINATE_LOCAL_HOST HCI_ERR_CONN_CAUSE_LOCAL_HOST
+/* 0x03E connection fail to establish */
+#define GATT_CONN_FAIL_ESTABLISH HCI_ERR_CONN_FAILED_ESTABLISHMENT
+/* 0x22 connection fail for LMP response tout */
+#define GATT_CONN_LMP_TIMEOUT HCI_ERR_LMP_RESPONSE_TIMEOUT
+/* 0x0100 L2CAP connection cancelled */
+#define GATT_CONN_CANCEL L2CAP_CONN_CANCEL
+typedef uint16_t tGATT_DISCONN_REASON;
/* MAX GATT MTU size
*/
@@ -442,6 +339,12 @@ typedef union {
} tGATTS_RSP;
+/* Transports for the primary service */
+#define GATT_TRANSPORT_LE BT_TRANSPORT_LE
+#define GATT_TRANSPORT_BR_EDR BT_TRANSPORT_BR_EDR
+#define GATT_TRANSPORT_LE_BR_EDR (BT_TRANSPORT_LE | BT_TRANSPORT_BR_EDR)
+typedef uint8_t tGATT_TRANSPORT;
+
#define GATT_PREP_WRITE_CANCEL 0x00
#define GATT_PREP_WRITE_EXEC 0x01
typedef uint8_t tGATT_EXEC_FLAG;
@@ -496,7 +399,7 @@ typedef uint8_t tGATTS_REQ_TYPE;
/* Client Used Data Structure
*/
/* definition of different discovery types */
-typedef enum : uint8_t {
+enum {
GATT_DISC_SRVC_ALL = 1, /* discover all services */
GATT_DISC_SRVC_BY_UUID, /* discover service of a special type */
GATT_DISC_INC_SRVC, /* discover the included service within a service */
@@ -504,7 +407,8 @@ typedef enum : uint8_t {
requirement */
GATT_DISC_CHAR_DSCPT, /* discover characteristic descriptors of a character */
GATT_DISC_MAX /* maximnun discover type */
-} tGATT_DISC_TYPE;
+};
+typedef uint8_t tGATT_DISC_TYPE;
/* GATT read type enumeration
*/
@@ -535,7 +439,6 @@ typedef struct {
tGATT_AUTH_REQ auth_req;
uint16_t num_handles; /* number of handles to read */
uint16_t handles[GATT_MAX_READ_MULTI_HANDLES]; /* handles list to be read */
- bool variable_len;
} tGATT_READ_MULTI;
/* Read By Handle Request (GATT_READ_BY_HANDLE) data */
@@ -571,21 +474,19 @@ typedef union {
tGATT_VALUE att_value;
uint16_t mtu;
uint16_t handle;
- uint16_t cid;
} tGATT_CL_COMPLETE;
/* GATT client operation type, used in client callback function
*/
-typedef enum : uint8_t {
- GATTC_OPTYPE_NONE = 0,
- GATTC_OPTYPE_DISCOVERY = 1,
- GATTC_OPTYPE_READ = 2,
- GATTC_OPTYPE_WRITE = 3,
- GATTC_OPTYPE_EXE_WRITE = 4,
- GATTC_OPTYPE_CONFIG = 5,
- GATTC_OPTYPE_NOTIFICATION = 6,
- GATTC_OPTYPE_INDICATION = 7,
-} tGATTC_OPTYPE;
+#define GATTC_OPTYPE_NONE 0
+#define GATTC_OPTYPE_DISCOVERY 1
+#define GATTC_OPTYPE_READ 2
+#define GATTC_OPTYPE_WRITE 3
+#define GATTC_OPTYPE_EXE_WRITE 4
+#define GATTC_OPTYPE_CONFIG 5
+#define GATTC_OPTYPE_NOTIFICATION 6
+#define GATTC_OPTYPE_INDICATION 7
+typedef uint8_t tGATTC_OPTYPE;
/* characteristic declaration
*/
@@ -672,27 +573,27 @@ typedef void(tGATT_ENC_CMPL_CB)(tGATT_IF gatt_if, const RawAddress& bda);
/* Define a callback function when phy is updated. */
typedef void(tGATT_PHY_UPDATE_CB)(tGATT_IF gatt_if, uint16_t conn_id,
uint8_t tx_phy, uint8_t rx_phy,
- tGATT_STATUS status);
+ uint8_t status);
/* Define a callback function when connection parameters are updated */
typedef void(tGATT_CONN_UPDATE_CB)(tGATT_IF gatt_if, uint16_t conn_id,
uint16_t interval, uint16_t latency,
- uint16_t timeout, tGATT_STATUS status);
+ uint16_t timeout, uint8_t status);
/* Define the structure that applications use to register with
* GATT. This structure includes callback functions. All functions
* MUST be provided.
*/
typedef struct {
- tGATT_CONN_CBACK* p_conn_cb{nullptr};
- tGATT_CMPL_CBACK* p_cmpl_cb{nullptr};
- tGATT_DISC_RES_CB* p_disc_res_cb{nullptr};
- tGATT_DISC_CMPL_CB* p_disc_cmpl_cb{nullptr};
- tGATT_REQ_CBACK* p_req_cb{nullptr};
- tGATT_ENC_CMPL_CB* p_enc_cmpl_cb{nullptr};
- tGATT_CONGESTION_CBACK* p_congestion_cb{nullptr};
- tGATT_PHY_UPDATE_CB* p_phy_update_cb{nullptr};
- tGATT_CONN_UPDATE_CB* p_conn_update_cb{nullptr};
+ tGATT_CONN_CBACK* p_conn_cb;
+ tGATT_CMPL_CBACK* p_cmpl_cb;
+ tGATT_DISC_RES_CB* p_disc_res_cb;
+ tGATT_DISC_CMPL_CB* p_disc_cmpl_cb;
+ tGATT_REQ_CBACK* p_req_cb;
+ tGATT_ENC_CMPL_CB* p_enc_cmpl_cb;
+ tGATT_CONGESTION_CBACK* p_congestion_cb;
+ tGATT_PHY_UPDATE_CB* p_phy_update_cb;
+ tGATT_CONN_UPDATE_CB* p_conn_update_cb;
} tGATT_CBACK;
/***************** Start Handle Management Definitions *********************/
@@ -797,8 +698,8 @@ extern bool GATTS_NVRegister(tGATT_APPL_INFO* p_cb_info);
* on error error status is returned.
*
******************************************************************************/
-extern tGATT_STATUS GATTS_AddService(tGATT_IF gatt_if,
- btgatt_db_element_t* service, int count);
+extern uint16_t GATTS_AddService(tGATT_IF gatt_if, btgatt_db_element_t* service,
+ int count);
/*******************************************************************************
*
@@ -1010,7 +911,7 @@ extern tGATT_STATUS GATTC_SendHandleValueConfirm(uint16_t conn_id,
*
******************************************************************************/
extern void GATT_SetIdleTimeout(const RawAddress& bd_addr, uint16_t idle_tout,
- tBT_TRANSPORT transport);
+ tGATT_TRANSPORT transport);
/*******************************************************************************
*
@@ -1021,15 +922,13 @@ extern void GATT_SetIdleTimeout(const RawAddress& bd_addr, uint16_t idle_tout,
*
* Parameter p_app_uuid128: Application UUID
* p_cb_info: callback functions.
- * eatt_support: set support for eatt
*
* Returns 0 for error, otherwise the index of the client registered
* with GATT
*
******************************************************************************/
extern tGATT_IF GATT_Register(const bluetooth::Uuid& p_app_uuid128,
- const std::string name, tGATT_CBACK* p_cb_info,
- bool eatt_support);
+ tGATT_CBACK* p_cb_info);
/*******************************************************************************
*
@@ -1184,7 +1083,7 @@ extern void gatt_free(void);
extern void gatt_notify_enc_cmpl(const RawAddress& bd_addr);
/** Reset bg device list. If called after controller reset, set |after_reset| to
- * true, as there is no need to wipe controller acceptlist in this case. */
+ * true, as there is no need to wipe controller white list in this case. */
extern void gatt_reset_bgdev_list(bool after_reset);
#endif /* GATT_API_H */
diff --git a/stack/include/gattdefs.h b/stack/include/gattdefs.h
index a483d6a44..186542cf5 100644
--- a/stack/include/gattdefs.h
+++ b/stack/include/gattdefs.h
@@ -131,11 +131,4 @@
#define GATT_UUID_SCAN_INT_WINDOW 0x2A4F
#define GATT_UUID_SCAN_REFRESH 0x2A31
-/* GATT Service characteristics */
-#define GATT_UUID_SERVER_SUP_FEAT 0x2B3A
-#define GATT_UUID_CLIENT_SUP_FEAT 0x2B29
-
-/* Database Hash characteristic */
-#define GATT_UUID_DATABASE_HASH 0x2B2A
-
#endif
diff --git a/stack/include/hci_error_code.h b/stack/include/hci_error_code.h
deleted file mode 100644
index fcb93e8f5..000000000
--- a/stack/include/hci_error_code.h
+++ /dev/null
@@ -1,177 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <base/strings/stringprintf.h>
-#include <string>
-
-/*
- * Definitions for HCI Error Codes that are passed in the events
- */
-typedef enum : uint8_t {
- HCI_SUCCESS = 0x00,
- HCI_ERR_ILLEGAL_COMMAND = 0x01,
- HCI_ERR_NO_CONNECTION = 0x02,
- HCI_ERR_HW_FAILURE = 0x03,
- HCI_ERR_PAGE_TIMEOUT = 0x04,
- HCI_ERR_AUTH_FAILURE = 0x05,
- HCI_ERR_KEY_MISSING = 0x06,
- HCI_ERR_MEMORY_FULL = 0x07,
- HCI_ERR_CONNECTION_TOUT = 0x08,
- HCI_ERR_MAX_NUM_OF_CONNECTIONS = 0x09,
- HCI_ERR_MAX_NUM_OF_SCOS = 0x0A,
- HCI_ERR_CONNECTION_EXISTS = 0x0B,
- HCI_ERR_COMMAND_DISALLOWED = 0x0C,
- HCI_ERR_HOST_REJECT_RESOURCES = 0x0D,
- HCI_ERR_HOST_REJECT_SECURITY = 0x0E,
- HCI_ERR_HOST_REJECT_DEVICE = 0x0F,
- HCI_ERR_HOST_TIMEOUT = 0x10, // stack/btm/btm_ble_gap,
- HCI_ERR_ILLEGAL_PARAMETER_FMT = 0x12,
- HCI_ERR_PEER_USER = 0x13,
- HCI_ERR_CONN_CAUSE_LOCAL_HOST = 0x16,
- HCI_ERR_REPEATED_ATTEMPTS = 0x17,
- HCI_ERR_PAIRING_NOT_ALLOWED = 0x18,
- HCI_ERR_UNSUPPORTED_REM_FEATURE = 0x1A, // stack/btm/btm_ble_gap
- HCI_ERR_UNSPECIFIED = 0x1F,
- HCI_ERR_LMP_RESPONSE_TIMEOUT = 0x22, // GATT_CONN_LMP_TIMEOUT
- HCI_ERR_LMP_ERR_TRANS_COLLISION = 0x23, // TODO remove
- HCI_ERR_ENCRY_MODE_NOT_ACCEPTABLE = 0x25,
- HCI_ERR_UNIT_KEY_USED = 0x26,
- HCI_ERR_PAIRING_WITH_UNIT_KEY_NOT_SUPPORTED = 0x29,
- HCI_ERR_DIFF_TRANSACTION_COLLISION = 0x2A, // stack/btm/btm_sec
- HCI_ERR_INSUFFCIENT_SECURITY = 0x2F, // btif/btu
- HCI_ERR_ROLE_SWITCH_PENDING = 0x32, // stack/btm/btm_sco
- HCI_ERR_ROLE_SWITCH_FAILED = 0x35,
- HCI_ERR_HOST_BUSY_PAIRING = 0x38, // stack/btm/btm_sec
- HCI_ERR_UNACCEPT_CONN_INTERVAL = 0x3B, // stack/l2cap/l2c_ble
- HCI_ERR_ADVERTISING_TIMEOUT = 0x3C, // stack/btm/btm_ble
- HCI_ERR_CONN_FAILED_ESTABLISHMENT = 0x3E, // GATT_CONN_FAIL_ESTABLISH
- HCI_ERR_LIMIT_REACHED = 0x43, // stack/btm/btm_ble_multi_adv.cc
-
- _HCI_ERR_MAX_ERR = 0x43,
- HCI_ERR_UNDEFINED = 0xff,
-} tHCI_ERROR_CODE;
-
-#define HCI_ERR_MAX_ERR _HCI_ERR_MAX_ERR // HACK for now for SMP
-
-inline std::string hci_error_code_text(const tHCI_ERROR_CODE& error_code) {
- switch (error_code) {
- case HCI_SUCCESS:
- return std::string("Success");
- case HCI_ERR_ILLEGAL_COMMAND:
- return std::string("Illegal Command");
- case HCI_ERR_NO_CONNECTION:
- return std::string("Unknown Connection");
- case HCI_ERR_HW_FAILURE:
- return std::string("Hardware Failure");
- case HCI_ERR_PAGE_TIMEOUT:
- return std::string("Page Timeout");
- case HCI_ERR_AUTH_FAILURE:
- return std::string("Authentication Failure");
- case HCI_ERR_KEY_MISSING:
- return std::string("Pin or Key Missing");
- case HCI_ERR_MEMORY_FULL:
- return std::string("Memory Capacity Exceeded");
- case HCI_ERR_CONNECTION_TOUT:
- return std::string("Connection Timeout");
- case HCI_ERR_MAX_NUM_OF_CONNECTIONS:
- return std::string("Connection Limit Exceeded");
- case HCI_ERR_MAX_NUM_OF_SCOS:
- return std::string("Synchronous Connection Limit Exceeded");
- case HCI_ERR_CONNECTION_EXISTS:
- return std::string("Connection Already Exists");
- case HCI_ERR_COMMAND_DISALLOWED:
- return std::string("Command Disallowed");
- case HCI_ERR_HOST_REJECT_RESOURCES:
- return std::string("Connection Rejected Limited Resources");
- case HCI_ERR_HOST_REJECT_SECURITY:
- return std::string("Connection Rejected Security Reasons");
- case HCI_ERR_HOST_REJECT_DEVICE:
- return std::string("Connection Rejected Unacceptable BdAddr");
- case HCI_ERR_HOST_TIMEOUT:
- return std::string("Connection Accept Timeout");
- case HCI_ERR_ILLEGAL_PARAMETER_FMT:
- return std::string("Unsupported Feature or Parameter Value");
- case HCI_ERR_PEER_USER:
- return std::string("Remote Terminated Connection");
- case HCI_ERR_CONN_CAUSE_LOCAL_HOST:
- return std::string("Local Terminated Connection");
- case HCI_ERR_REPEATED_ATTEMPTS:
- return std::string("Repeated Attempts");
- case HCI_ERR_PAIRING_NOT_ALLOWED:
- return std::string("Pairing not Allowed");
- case HCI_ERR_UNSUPPORTED_REM_FEATURE:
- return std::string("Unsupported Remote or Lmp Feature");
- case HCI_ERR_UNSPECIFIED:
- return std::string("Unspecified Error");
- case HCI_ERR_LMP_RESPONSE_TIMEOUT:
- return std::string("Gatt Connection Lmp Timeout");
- case HCI_ERR_LMP_ERR_TRANS_COLLISION:
- return std::string("Link Layer Collision");
- case HCI_ERR_ENCRY_MODE_NOT_ACCEPTABLE:
- return std::string("Encryption Mode not Acceptable");
- case HCI_ERR_UNIT_KEY_USED:
- return std::string("Unit Key Used");
- case HCI_ERR_PAIRING_WITH_UNIT_KEY_NOT_SUPPORTED:
- return std::string("Pairing with Unit Key Unsupported");
- case HCI_ERR_DIFF_TRANSACTION_COLLISION:
- return std::string("Diff Transaction Collision");
- case HCI_ERR_INSUFFCIENT_SECURITY:
- return std::string("Insufficient Security");
- case HCI_ERR_ROLE_SWITCH_PENDING:
- return std::string("Role Switch Pending");
- case HCI_ERR_HOST_BUSY_PAIRING:
- return std::string("Host Busy Pairing");
- case HCI_ERR_UNACCEPT_CONN_INTERVAL:
- return std::string("Unacceptable Connection Interval");
- case HCI_ERR_ADVERTISING_TIMEOUT:
- return std::string("Advertising Timeout");
- case HCI_ERR_CONN_FAILED_ESTABLISHMENT:
- return std::string("Connection Failed Establishment");
- case HCI_ERR_LIMIT_REACHED:
- return std::string("Limit Reached");
- default:
- return base::StringPrintf("Unknown Error[%02hx]", error_code);
- }
-}
-
-// Context equivalence
-using tHCI_STATUS = tHCI_ERROR_CODE;
-inline std::string hci_status_code_text(const tHCI_STATUS& status_code) {
- return hci_error_code_text(status_code);
-}
-
-using tHCI_REASON = tHCI_ERROR_CODE;
-inline std::string hci_reason_code_text(const tHCI_REASON& reason_code) {
- return hci_error_code_text(reason_code);
-}
-
-// Conversion from raw packet value
-inline tHCI_ERROR_CODE to_hci_error_code(const uint8_t& error_code) {
- if (error_code > _HCI_ERR_MAX_ERR) return HCI_ERR_UNDEFINED;
- return static_cast<tHCI_ERROR_CODE>(error_code);
-}
-
-inline tHCI_STATUS to_hci_status_code(const uint8_t& status_code) {
- if (status_code > _HCI_ERR_MAX_ERR) return HCI_ERR_UNDEFINED;
- return static_cast<tHCI_STATUS>(status_code);
-}
-
-inline tHCI_REASON to_hci_reason_code(const uint8_t& reason_code) {
- if (reason_code > _HCI_ERR_MAX_ERR) return HCI_ERR_UNDEFINED;
- return static_cast<tHCI_REASON>(reason_code);
-}
diff --git a/stack/include/hci_evt_length.h b/stack/include/hci_evt_length.h
index 046816b01..ea8dfdff1 100644
--- a/stack/include/hci_evt_length.h
+++ b/stack/include/hci_evt_length.h
@@ -28,7 +28,7 @@ static const uint8_t hci_event_parameters_minimum_length[] = {
255, // 0x07 - HCI_Remote_Name_Request_Complete Event
4, // 0x08 - HCI_Encryption_Change Event
3, // 0x09 - HCI_Change_Connection_Link_Key_Complete Event
- 4, // 0x0A - HCI_Central_Link_Key_Complete Event
+ 4, // 0x0A - HCI_Master_Link_Key_Complete Event
11, // 0x0B - HCI_Read_Remote_Supported_Features_Complete Event
8, // 0x0C - HCI_Read_Remote_Version_Information_Complete Event
21, // 0x0D - HCI_QoS_Setup_Complete Event
@@ -99,13 +99,12 @@ static const uint8_t hci_event_parameters_minimum_length[] = {
9, // 0x4E - HCI_Triggered_Clock_Capture Event
1, // 0x4F - HCI_Synchronization_Train_Complete Event
29, // 0x50 - HCI_Synchronization_Train_Received Event
- 18, // 0x51 - HCI_Connectionless_Peripheral_Broadcast_Receive Event
+ 18, // 0x51 - HCI_Connectionless_Slave_Broadcast_Receive Event
// (Data_Length = 0)
- 7, // 0x52 - HCI_Connectionless_Peripheral_Broadcast_Timeout Event
+ 7, // 0x52 - HCI_Connectionless_Slave_Broadcast_Timeout Event
7, // 0x53 - HCI_Truncated_Page_Complete Event
- 0, // 0x54 - HCI_Peripheral_Page_Response_Timeout Event
- 10, // 0x55 - HCI_Connectionless_Peripheral_Broadcast_Channel_Map_Change
- // Event
+ 0, // 0x54 - HCI_Slave_Page_Response_Timeout Event
+ 10, // 0x55 - HCI_Connectionless_Slave_Broadcast_Channel_Map_Change Event
4, // 0x56 - HCI_Inquiry_Response_Notification Event
2, // 0x57 - HCI_Authenticated_Payload_Timeout_Expired Event
8, // 0x58 - HCI_SAM_Status_Change Event
diff --git a/stack/include/hcidefs.h b/stack/include/hcidefs.h
index c6a468b30..088f2b36a 100644
--- a/stack/include/hcidefs.h
+++ b/stack/include/hcidefs.h
@@ -19,8 +19,6 @@
#ifndef HCIDEFS_H
#define HCIDEFS_H
-#include "stack/include/hci_error_code.h"
-
#define HCI_PROTO_VERSION 0x01 /* Version for BT spec 1.1 */
#define HCI_PROTO_VERSION_1_2 0x02 /* Version for BT spec 1.2 */
#define HCI_PROTO_VERSION_2_0 0x03 /* Version for BT spec 2.0 */
@@ -44,6 +42,10 @@
#define HCI_GRP_VENDOR_SPECIFIC (0x3F << 10) /* 0xFC00 */
+/* Group occupies high 6 bits of the HCI command rest is opcode itself */
+#define HCI_OGF(p) (uint8_t)((0xFC00 & (p)) >> 10)
+#define HCI_OCF(p) (0x3FF & (p))
+
/*
* Definitions for Link Control Commands
*/
@@ -69,7 +71,7 @@
#define HCI_AUTHENTICATION_REQUESTED (0x0011 | HCI_GRP_LINK_CONTROL_CMDS)
#define HCI_SET_CONN_ENCRYPTION (0x0013 | HCI_GRP_LINK_CONTROL_CMDS)
#define HCI_CHANGE_CONN_LINK_KEY (0x0015 | HCI_GRP_LINK_CONTROL_CMDS)
-#define HCI_CENTRAL_LINK_KEY (0x0017 | HCI_GRP_LINK_CONTROL_CMDS)
+#define HCI_MASTER_LINK_KEY (0x0017 | HCI_GRP_LINK_CONTROL_CMDS)
#define HCI_RMT_NAME_REQUEST (0x0019 | HCI_GRP_LINK_CONTROL_CMDS)
#define HCI_RMT_NAME_REQUEST_CANCEL (0x001A | HCI_GRP_LINK_CONTROL_CMDS)
#define HCI_READ_RMT_FEATURES (0x001B | HCI_GRP_LINK_CONTROL_CMDS)
@@ -139,6 +141,7 @@
#define HCI_FLUSH (0x0008 | HCI_GRP_HOST_CONT_BASEBAND_CMDS)
#define HCI_READ_PIN_TYPE (0x0009 | HCI_GRP_HOST_CONT_BASEBAND_CMDS)
#define HCI_WRITE_PIN_TYPE (0x000A | HCI_GRP_HOST_CONT_BASEBAND_CMDS)
+#define HCI_CREATE_NEW_UNIT_KEY (0x000B | HCI_GRP_HOST_CONT_BASEBAND_CMDS)
#define HCI_GET_MWS_TRANS_LAYER_CFG (0x000C | HCI_GRP_HOST_CONT_BASEBAND_CMDS)
#define HCI_READ_STORED_LINK_KEY (0x000D | HCI_GRP_HOST_CONT_BASEBAND_CMDS)
#define HCI_WRITE_STORED_LINK_KEY (0x0011 | HCI_GRP_HOST_CONT_BASEBAND_CMDS)
@@ -321,10 +324,10 @@
#define HCI_BLE_WRITE_SCAN_ENABLE (0x000C | HCI_GRP_BLE_CMDS)
#define HCI_BLE_CREATE_LL_CONN (0x000D | HCI_GRP_BLE_CMDS)
#define HCI_BLE_CREATE_CONN_CANCEL (0x000E | HCI_GRP_BLE_CMDS)
-#define HCI_BLE_READ_ACCEPTLIST_SIZE (0x000F | HCI_GRP_BLE_CMDS)
-#define HCI_BLE_CLEAR_ACCEPTLIST (0x0010 | HCI_GRP_BLE_CMDS)
-#define HCI_BLE_ADD_ACCEPTLIST (0x0011 | HCI_GRP_BLE_CMDS)
-#define HCI_BLE_REMOVE_ACCEPTLIST (0x0012 | HCI_GRP_BLE_CMDS)
+#define HCI_BLE_READ_WHITE_LIST_SIZE (0x000F | HCI_GRP_BLE_CMDS)
+#define HCI_BLE_CLEAR_WHITE_LIST (0x0010 | HCI_GRP_BLE_CMDS)
+#define HCI_BLE_ADD_WHITE_LIST (0x0011 | HCI_GRP_BLE_CMDS)
+#define HCI_BLE_REMOVE_WHITE_LIST (0x0012 | HCI_GRP_BLE_CMDS)
#define HCI_BLE_UPD_LL_CONN_PARAMS (0x0013 | HCI_GRP_BLE_CMDS)
#define HCI_BLE_SET_HOST_CHNL_CLASS (0x0014 | HCI_GRP_BLE_CMDS)
#define HCI_BLE_READ_CHNL_MAP (0x0015 | HCI_GRP_BLE_CMDS)
@@ -382,51 +385,19 @@
(0x0045 | HCI_GRP_BLE_CMDS)
#define HCI_BLE_PERIODIC_ADVERTISING_TERMINATE_SYNC \
(0x0046 | HCI_GRP_BLE_CMDS)
-#define HCI_BLE_ADD_DEVICE_TO_PERIODIC_ADVERTISER_LIST \
+#define HCI_BLE_ADD_DEVICE_TO_PERIODIC_ADVERTISING_LIST \
(0x0047 | HCI_GRP_BLE_CMDS)
-#define HCI_BLE_REMOVE_DEVICE_FROM_PERIODIC_ADVERTISER_LIST \
+#define HCI_BLE_RM_DEVICE_FROM_PERIODIC_ADVERTISING_LIST \
(0x0048 | HCI_GRP_BLE_CMDS)
-#define HCI_BLE_CLEAR_PERIODIC_ADVERTISER_LIST (0x0049 | HCI_GRP_BLE_CMDS)
-#define HCI_BLE_READ_PERIODIC_ADVERTISER_LIST_SIZE (0x004A | HCI_GRP_BLE_CMDS)
+#define HCI_BLE_CLEAR_PERIODIC_ADVERTISING_LIST (0x0049 | HCI_GRP_BLE_CMDS)
+#define HCI_BLE_READ_PERIODIC_ADVERTISING_LIST_SIZE (0x004A | HCI_GRP_BLE_CMDS)
#define HCI_BLE_READ_TRANSMIT_POWER (0x004B | HCI_GRP_BLE_CMDS)
#define HCI_BLE_READ_RF_COMPENS_POWER (0x004C | HCI_GRP_BLE_CMDS)
#define HCI_BLE_WRITE_RF_COMPENS_POWER (0x004D | HCI_GRP_BLE_CMDS)
#define HCI_BLE_SET_PRIVACY_MODE (0x004E | HCI_GRP_BLE_CMDS)
-#define HCI_LE_SET_PERIODIC_ADVERTISING_RECEIVE_ENABLE \
- (0x0059 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_PERIODIC_ADVERTISING_SYNC_TRANSFER (0x005A | HCI_GRP_BLE_CMDS)
-#define HCI_LE_PERIODIC_ADVERTISING_SET_INFO_TRANSFER \
- (0x005B | HCI_GRP_BLE_CMDS)
-#define HCI_LE_SET_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAM \
- (0x005C | HCI_GRP_BLE_CMDS)
-#define HCI_LE_SET_DEFAULT_PERIODIC_ADVERTISING_SYNC_TRANSFER_PARAM \
- (0x005D | HCI_GRP_BLE_CMDS)
-#define HCI_BLE_READ_BUFFER_SIZE_V2 (0x0060 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_SET_HOST_FEATURE (0x0074 | HCI_GRP_BLE_CMDS)
/* LE Get Vendor Capabilities Command opcode */
#define HCI_BLE_VENDOR_CAP (0x0153 | HCI_GRP_VENDOR_SPECIFIC)
-#define HCI_LE_READ_ISO_TX_SYNC (0x0061 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_SET_CIG_PARAMS (0x0062 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_SET_CIG_PARAMS_TEST (0x0063 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_CREATE_CIS (0x0064 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_REMOVE_CIG (0x0065 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_ACCEPT_CIS_REQ (0x0066 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_REJ_CIS_REQ (0x0067 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_CREATE_BIG (0x0068 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_CREATE_BIG_TEST (0x0069 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_TERM_BIG (0x006A | HCI_GRP_BLE_CMDS)
-#define HCI_LE_BIG_CREATE_SYNC (0x006B | HCI_GRP_BLE_CMDS)
-#define HCI_LE_BIG_TERM_SYNC (0x006C | HCI_GRP_BLE_CMDS)
-#define HCI_LE_REQ_PEER_SCA (0x006D | HCI_GRP_BLE_CMDS)
-#define HCI_LE_SETUP_ISO_DATA_PATH (0x006E | HCI_GRP_BLE_CMDS)
-#define HCI_LE_REMOVE_ISO_DATA_PATH (0x006F | HCI_GRP_BLE_CMDS)
-#define HCI_LE_ISO_TRANSMIT_TEST (0x0070 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_ISO_RECEIVE_TEST (0x0071 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_ISO_READ_TEST_CNTRS (0x0072 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_ISO_TEST_END (0x0073 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_SET_HOST_FEATURE (0x0074 | HCI_GRP_BLE_CMDS)
-#define HCI_LE_READ_ISO_LINK_QUALITY (0x0075 | HCI_GRP_BLE_CMDS)
/* Multi adv opcode */
#define HCI_BLE_MULTI_ADV (0x0154 | HCI_GRP_VENDOR_SPECIFIC)
@@ -437,9 +408,15 @@
/* ADV filter opcode */
#define HCI_BLE_ADV_FILTER (0x0157 | HCI_GRP_VENDOR_SPECIFIC)
+/* Tracking opcode */
+#define HCI_BLE_TRACK_ADV (0x0158 | HCI_GRP_VENDOR_SPECIFIC)
+
/* Energy info opcode */
#define HCI_BLE_ENERGY_INFO (0x0159 | HCI_GRP_VENDOR_SPECIFIC)
+/* Extended BLE Scan parameters opcode */
+#define HCI_BLE_EXTENDED_SCAN_PARAMS (0x015A | HCI_GRP_VENDOR_SPECIFIC)
+
/* Controller debug info opcode */
#define HCI_CONTROLLER_DEBUG_INFO (0x015B | HCI_GRP_VENDOR_SPECIFIC)
@@ -449,11 +426,6 @@
/* Bluetooth Quality Report opcode */
#define HCI_CONTROLLER_BQR (0x015E | HCI_GRP_VENDOR_SPECIFIC)
-/* Bluetooth Dynamic Audio Buffer opcode */
-#define HCI_CONTROLLER_DAB (0x015F | HCI_GRP_VENDOR_SPECIFIC)
-#define HCI_CONTROLLER_DAB_GET_BUFFER_TIME 0x01
-#define HCI_CONTROLLER_DAB_SET_BUFFER_TIME 0x02
-
/* subcode for multi adv feature */
#define BTM_BLE_MULTI_ADV_SET_PARAM 0x01
#define BTM_BLE_MULTI_ADV_WRITE_ADV_DATA 0x02
@@ -483,6 +455,20 @@
/* Bluetooth Quality Report sub event */
#define HCI_VSE_SUBCODE_BQR_SUB_EVT 0x58
+/* LE supported states definition */
+#define HCI_LE_ADV_STATE 0x00000001
+#define HCI_LE_SCAN_STATE 0x00000002
+#define HCI_LE_INIT_STATE 0x00000004
+#define HCI_LE_CONN_SL_STATE 0x00000008
+#define HCI_LE_ADV_SCAN_STATE 0x00000010
+#define HCI_LE_ADV_INIT_STATE 0x00000020
+#define HCI_LE_ADV_MA_STATE 0x00000040
+#define HCI_LE_ADV_SL_STATE 0x00000080
+#define HCI_LE_SCAN_INIT_STATE 0x00000100
+#define HCI_LE_SCAN_MA_STATE 0x00000200
+#define HCI_LE_SCAN_SL_STATE 0x00000400
+#define HCI_LE_INIT_MA_STATE 0x00000800
+
/* LE Supported States */
constexpr uint8_t HCI_LE_STATES_NON_CONN_ADV_BIT = 0;
constexpr uint8_t HCI_LE_STATES_SCAN_ADV_BIT = 1;
@@ -491,7 +477,7 @@ constexpr uint8_t HCI_LE_STATES_HI_DUTY_DIR_ADV_BIT = 3;
constexpr uint8_t HCI_LE_STATES_PASS_SCAN_BIT = 4;
constexpr uint8_t HCI_LE_STATES_ACTIVE_SCAN_BIT = 5;
constexpr uint8_t HCI_LE_STATES_INIT_BIT = 6;
-constexpr uint8_t HCI_LE_STATES_PERIPHERAL_BIT = 7;
+constexpr uint8_t HCI_LE_STATES_SLAVE_BIT = 7;
constexpr uint8_t HCI_LE_STATES_NON_CONN_ADV_PASS_SCAN_BIT = 8;
constexpr uint8_t HCI_LE_STATES_SCAN_ADV_PASS_SCAN_BIT = 9;
constexpr uint8_t HCI_LE_STATES_CONN_ADV_PASS_SCAN_BIT = 10;
@@ -502,30 +488,30 @@ constexpr uint8_t HCI_LE_STATES_CONN_ADV_ACTIVE_SCAN_BIT = 14;
constexpr uint8_t HCI_LE_STATES_HI_DUTY_DIR_ADV_ACTIVE_SCAN_BIT = 15;
constexpr uint8_t HCI_LE_STATES_NON_CONN_INIT_BIT = 16;
constexpr uint8_t HCI_LE_STATES_SCAN_ADV_INIT_BIT = 17;
-constexpr uint8_t HCI_LE_STATES_NON_CONN_ADV_CENTRAL_BIT = 18;
-constexpr uint8_t HCI_LE_STATES_SCAN_ADV_CENTRAL_BIT = 19;
-constexpr uint8_t HCI_LE_STATES_NON_CONN_ADV_PERIPHERAL_BIT = 20;
-constexpr uint8_t HCI_LE_STATES_SCAN_ADV_PERIPHERAL_BIT = 21;
+constexpr uint8_t HCI_LE_STATES_NON_CONN_ADV_MASTER_BIT = 18;
+constexpr uint8_t HCI_LE_STATES_SCAN_ADV_MASTER_BIT = 19;
+constexpr uint8_t HCI_LE_STATES_NON_CONN_ADV_SLAVE_BIT = 20;
+constexpr uint8_t HCI_LE_STATES_SCAN_ADV_SLAVE_BIT = 21;
constexpr uint8_t HCI_LE_STATES_PASS_SCAN_INIT_BIT = 22;
constexpr uint8_t HCI_LE_STATES_ACTIVE_SCAN_INIT_BIT = 23;
-constexpr uint8_t HCI_LE_STATES_PASS_SCAN_CENTRAL_BIT = 24;
-constexpr uint8_t HCI_LE_STATES_ACTIVE_SCAN_CENTRAL_BIT = 25;
-constexpr uint8_t HCI_LE_STATES_PASS_SCAN_PERIPHERAL_BIT = 26;
-constexpr uint8_t HCI_LE_STATES_ACTIVE_SCAN_PERIPHERAL_BIT = 27;
-constexpr uint8_t HCI_LE_STATES_INIT_CENTRAL_BIT = 28;
+constexpr uint8_t HCI_LE_STATES_PASS_SCAN_MASTER_BIT = 24;
+constexpr uint8_t HCI_LE_STATES_ACTIVE_SCAN_MASTER_BIT = 25;
+constexpr uint8_t HCI_LE_STATES_PASS_SCAN_SLAVE_BIT = 26;
+constexpr uint8_t HCI_LE_STATES_ACTIVE_SCAN_SLAVE_BIT = 27;
+constexpr uint8_t HCI_LE_STATES_INIT_MASTER_BIT = 28;
constexpr uint8_t HCI_LE_STATES_LOW_DUTY_DIR_ADV_BIT = 29;
constexpr uint8_t HCI_LE_STATES_LO_DUTY_DIR_ADV_PASS_SCAN_BIT = 30;
constexpr uint8_t HCI_LE_STATES_LO_DUTY_DIR_ADV_ACTIVE_SCAN_BIT = 31;
constexpr uint8_t HCI_LE_STATES_CONN_ADV_INIT_BIT = 32;
constexpr uint8_t HCI_LE_STATES_HI_DUTY_DIR_ADV_INIT_BIT = 33;
constexpr uint8_t HCI_LE_STATES_LO_DUTY_DIR_ADV_INIT_BIT = 34;
-constexpr uint8_t HCI_LE_STATES_CONN_ADV_CENTRAL_BIT = 35;
-constexpr uint8_t HCI_LE_STATES_HI_DUTY_DIR_ADV_CENTRAL_BIT = 36;
-constexpr uint8_t HCI_LE_STATES_LO_DUTY_DIR_ADV_CENTRAL_BIT = 37;
-constexpr uint8_t HCI_LE_STATES_CONN_ADV_PERIPHERAL_BIT = 38;
-constexpr uint8_t HCI_LE_STATES_HI_DUTY_DIR_ADV_PERIPHERAL_BIT = 39;
-constexpr uint8_t HCI_LE_STATES_LO_DUTY_DIR_ADV_PERIPHERAL_BIT = 40;
-constexpr uint8_t HCI_LE_STATES_INIT_CENTRAL_PERIPHERAL_BIT = 41;
+constexpr uint8_t HCI_LE_STATES_CONN_ADV_MASTER_BIT = 35;
+constexpr uint8_t HCI_LE_STATES_HI_DUTY_DIR_ADV_MASTER_BIT = 36;
+constexpr uint8_t HCI_LE_STATES_LO_DUTY_DIR_ADV_MASTER_BIT = 37;
+constexpr uint8_t HCI_LE_STATES_CONN_ADV_SLAVE_BIT = 38;
+constexpr uint8_t HCI_LE_STATES_HI_DUTY_DIR_ADV_SLAVE_BIT = 39;
+constexpr uint8_t HCI_LE_STATES_LO_DUTY_DIR_ADV_SLAVE_BIT = 40;
+constexpr uint8_t HCI_LE_STATES_INIT_MASTER_SLAVE_BIT = 41;
/*
* Definitions for HCI Events
@@ -539,7 +525,7 @@ constexpr uint8_t HCI_LE_STATES_INIT_CENTRAL_PERIPHERAL_BIT = 41;
#define HCI_RMT_NAME_REQUEST_COMP_EVT 0x07
#define HCI_ENCRYPTION_CHANGE_EVT 0x08
#define HCI_CHANGE_CONN_LINK_KEY_EVT 0x09
-#define HCI_CENTRAL_LINK_KEY_COMP_EVT 0x0A
+#define HCI_MASTER_LINK_KEY_COMP_EVT 0x0A
#define HCI_READ_RMT_FEATURES_COMP_EVT 0x0B
#define HCI_READ_RMT_VERSION_COMP_EVT 0x0C
#define HCI_QOS_SETUP_COMP_EVT 0x0D
@@ -582,6 +568,20 @@ constexpr uint8_t HCI_LE_STATES_INIT_CENTRAL_PERIPHERAL_BIT = 41;
#define HCI_KEYPRESS_NOTIFY_EVT 0x3C
#define HCI_RMT_HOST_SUP_FEAT_NOTIFY_EVT 0x3D
+/*#define HCI_GENERIC_AMP_LINK_KEY_NOTIF_EVT 0x3E Removed from spec */
+#define HCI_PHYSICAL_LINK_COMP_EVT 0x40
+#define HCI_CHANNEL_SELECTED_EVT 0x41
+#define HCI_DISC_PHYSICAL_LINK_COMP_EVT 0x42
+#define HCI_PHY_LINK_LOSS_EARLY_WARNING_EVT 0x43
+#define HCI_PHY_LINK_RECOVERY_EVT 0x44
+#define HCI_LOGICAL_LINK_COMP_EVT 0x45
+#define HCI_DISC_LOGICAL_LINK_COMP_EVT 0x46
+#define HCI_FLOW_SPEC_MODIFY_COMP_EVT 0x47
+#define HCI_NUM_COMPL_DATA_BLOCKS_EVT 0x48
+#define HCI_SHORT_RANGE_MODE_COMPLETE_EVT 0x4C
+#define HCI_AMP_STATUS_CHANGE_EVT 0x4D
+#define HCI_SET_TRIGGERED_CLOCK_CAPTURE_EVT 0x4E
+
/* ULP HCI Event */
#define HCI_BLE_EVENT 0x3e
/* ULP Event sub code */
@@ -602,19 +602,100 @@ constexpr uint8_t HCI_LE_STATES_INIT_CENTRAL_PERIPHERAL_BIT = 41;
#define HCI_BLE_SCAN_TIMEOUT_EVT 0x11
#define HCI_LE_ADVERTISING_SET_TERMINATED_EVT 0x12
#define HCI_BLE_SCAN_REQ_RX_EVT 0x13
-#define HCI_BLE_CIS_EST_EVT 0x19
-#define HCI_BLE_CIS_REQ_EVT 0x1a
-#define HCI_BLE_CREATE_BIG_CPL_EVT 0x1b
-#define HCI_BLE_TERM_BIG_CPL_EVT 0x1c
-#define HCI_BLE_BIG_SYNC_EST_EVT 0x1d
-#define HCI_BLE_BIG_SYNC_LOST_EVT 0x1e
-#define HCI_BLE_REQ_PEER_SCA_CPL_EVT 0x1f
+
+/* Definitions for LE Channel Map */
+#define HCI_BLE_CHNL_MAP_SIZE 5
#define HCI_VENDOR_SPECIFIC_EVT 0xFF /* Vendor specific events */
+#define HCI_NAP_TRACE_EVT \
+ 0xFF /* was define 0xFE, 0xFD, change to 0xFF \
+ because conflict w/ TCI_EVT and per \
+ specification compliant */
+
+/*
+ * Defentions for HCI Error Codes that are past in the events
+*/
+#define HCI_SUCCESS 0x00
+#define HCI_PENDING 0x00
+#define HCI_ERR_ILLEGAL_COMMAND 0x01
+#define HCI_ERR_NO_CONNECTION 0x02
+#define HCI_ERR_HW_FAILURE 0x03
+#define HCI_ERR_PAGE_TIMEOUT 0x04
+#define HCI_ERR_AUTH_FAILURE 0x05
+#define HCI_ERR_KEY_MISSING 0x06
+#define HCI_ERR_MEMORY_FULL 0x07
+#define HCI_ERR_CONNECTION_TOUT 0x08
+#define HCI_ERR_MAX_NUM_OF_CONNECTIONS 0x09
+#define HCI_ERR_MAX_NUM_OF_SCOS 0x0A
+#define HCI_ERR_CONNECTION_EXISTS 0x0B
+#define HCI_ERR_COMMAND_DISALLOWED 0x0C
+#define HCI_ERR_HOST_REJECT_RESOURCES 0x0D
+#define HCI_ERR_HOST_REJECT_SECURITY 0x0E
+#define HCI_ERR_HOST_REJECT_DEVICE 0x0F
+#define HCI_ERR_HOST_TIMEOUT 0x10
+#define HCI_ERR_UNSUPPORTED_VALUE 0x11
+#define HCI_ERR_ILLEGAL_PARAMETER_FMT 0x12
+#define HCI_ERR_PEER_USER 0x13
+#define HCI_ERR_PEER_LOW_RESOURCES 0x14
+#define HCI_ERR_PEER_POWER_OFF 0x15
+#define HCI_ERR_CONN_CAUSE_LOCAL_HOST 0x16
+#define HCI_ERR_REPEATED_ATTEMPTS 0x17
+#define HCI_ERR_PAIRING_NOT_ALLOWED 0x18
+#define HCI_ERR_UNKNOWN_LMP_PDU 0x19
+#define HCI_ERR_UNSUPPORTED_REM_FEATURE 0x1A
+#define HCI_ERR_SCO_OFFSET_REJECTED 0x1B
+#define HCI_ERR_SCO_INTERVAL_REJECTED 0x1C
+#define HCI_ERR_SCO_AIR_MODE 0x1D
+#define HCI_ERR_INVALID_LMP_PARAM 0x1E
+#define HCI_ERR_UNSPECIFIED 0x1F
+#define HCI_ERR_UNSUPPORTED_LMP_FEATURE 0x20
+#define HCI_ERR_ROLE_CHANGE_NOT_ALLOWED 0x21
+#define HCI_ERR_LMP_RESPONSE_TIMEOUT 0x22
+#define HCI_ERR_LMP_ERR_TRANS_COLLISION 0x23
+#define HCI_ERR_LMP_PDU_NOT_ALLOWED 0x24
+#define HCI_ERR_ENCRY_MODE_NOT_ACCEPTABLE 0x25
+#define HCI_ERR_UNIT_KEY_USED 0x26
+#define HCI_ERR_QOS_NOT_SUPPORTED 0x27
+#define HCI_ERR_INSTANT_PASSED 0x28
+#define HCI_ERR_PAIRING_WITH_UNIT_KEY_NOT_SUPPORTED 0x29
+#define HCI_ERR_DIFF_TRANSACTION_COLLISION 0x2A
+#define HCI_ERR_UNDEFINED_0x2B 0x2B
+#define HCI_ERR_QOS_UNACCEPTABLE_PARAM 0x2C
+#define HCI_ERR_QOS_REJECTED 0x2D
+#define HCI_ERR_CHAN_CLASSIF_NOT_SUPPORTED 0x2E
+#define HCI_ERR_INSUFFCIENT_SECURITY 0x2F
+#define HCI_ERR_PARAM_OUT_OF_RANGE 0x30
+#define HCI_ERR_UNDEFINED_0x31 0x31
+#define HCI_ERR_ROLE_SWITCH_PENDING 0x32
+#define HCI_ERR_UNDEFINED_0x33 0x33
+#define HCI_ERR_RESERVED_SLOT_VIOLATION 0x34
+#define HCI_ERR_ROLE_SWITCH_FAILED 0x35
+#define HCI_ERR_INQ_RSP_DATA_TOO_LARGE 0x36
+#define HCI_ERR_SIMPLE_PAIRING_NOT_SUPPORTED 0x37
+#define HCI_ERR_HOST_BUSY_PAIRING 0x38
+#define HCI_ERR_REJ_NO_SUITABLE_CHANNEL 0x39
+#define HCI_ERR_CONTROLLER_BUSY 0x3A
+#define HCI_ERR_UNACCEPT_CONN_INTERVAL 0x3B
+#define HCI_ERR_ADVERTISING_TIMEOUT 0x3C
+#define HCI_ERR_CONN_TOUT_DUE_TO_MIC_FAILURE 0x3D
+#define HCI_ERR_CONN_FAILED_ESTABLISHMENT 0x3E
+#define HCI_ERR_LIMIT_REACHED 0x43
+#define HCI_ERR_MAC_CONNECTION_FAILED 0x3F
+
+/* ConnectionLess Broadcast errors */
+#define HCI_ERR_LT_ADDR_ALREADY_IN_USE 0x40
+#define HCI_ERR_LT_ADDR_NOT_ALLOCATED 0x41
+#define HCI_ERR_CLB_NOT_ENABLED 0x42
+#define HCI_ERR_CLB_DATA_TOO_BIG 0x43
+
+#define HCI_ERR_MAX_ERR 0x43
+
+#define HCI_HINT_TO_RECREATE_AMP_PHYS_LINK 0xFF
/*
* Definitions for HCI enable event
*/
+#define HCI_INQUIRY_COMPLETE_EV(p) (*((uint32_t*)(p)) & 0x00000001)
#define HCI_INQUIRY_RESULT_EV(p) (*((uint32_t*)(p)) & 0x00000002)
#define HCI_CONNECTION_COMPLETE_EV(p) (*((uint32_t*)(p)) & 0x00000004)
#define HCI_CONNECTION_REQUEST_EV(p) (*((uint32_t*)(p)) & 0x00000008)
@@ -623,7 +704,7 @@ constexpr uint8_t HCI_LE_STATES_INIT_CENTRAL_PERIPHERAL_BIT = 41;
#define HCI_RMT_NAME_REQUEST_COMPL_EV(p) (*((uint32_t*)(p)) & 0x00000040)
#define HCI_CHANGE_CONN_ENCRPT_ENABLE_EV(p) (*((uint32_t*)(p)) & 0x00000080)
#define HCI_CHANGE_CONN_LINK_KEY_EV(p) (*((uint32_t*)(p)) & 0x00000100)
-#define HCI_CENTRAL_LINK_KEY_COMPLETE_EV(p) (*((uint32_t*)(p)) & 0x00000200)
+#define HCI_MASTER_LINK_KEY_COMPLETE_EV(p) (*((uint32_t*)(p)) & 0x00000200)
#define HCI_READ_RMT_FEATURES_COMPL_EV(p) (*((uint32_t*)(p)) & 0x00000400)
#define HCI_READ_RMT_VERSION_COMPL_EV(p) (*((uint32_t*)(p)) & 0x00000800)
#define HCI_QOS_SETUP_COMPLETE_EV(p) (*((uint32_t*)(p)) & 0x00001000)
@@ -647,7 +728,17 @@ constexpr uint8_t HCI_LE_STATES_INIT_CENTRAL_PERIPHERAL_BIT = 41;
#define HCI_PAGE_SCAN_MODE_CHANGED_EV(p) (*((uint32_t*)(p)) & 0x40000000)
#define HCI_PAGE_SCAN_REP_MODE_CHNG_EV(p) (*((uint32_t*)(p)) & 0x80000000)
+/* the default event mask for 2.1+EDR (Lisbon) does not include Lisbon events */
+#define HCI_DEFAULT_EVENT_MASK_0 0xFFFFFFFF
+#define HCI_DEFAULT_EVENT_MASK_1 0x00001FFF
+
/* the event mask for 2.0 + EDR and later (includes Lisbon events) */
+#define HCI_LISBON_EVENT_MASK_0 0xFFFFFFFF
+#define HCI_LISBON_EVENT_MASK_1 0x1DBFFFFF
+#define HCI_LISBON_EVENT_MASK \
+ { 0x0D, 0xBF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }
+#define HCI_LISBON_EVENT_MASK_EXT \
+ { 0x1D, 0xBF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }
#define HCI_DUMO_EVENT_MASK_EXT \
{ 0x3D, 0xBF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF, 0xFF }
/* 0x00001FFF FFFFFFFF Default - no Lisbon events
@@ -671,26 +762,99 @@ constexpr uint8_t HCI_LE_STATES_INIT_CENTRAL_PERIPHERAL_BIT = 41;
0x20000000 00000000 LE Meta Event
*/
+/* the event mask for AMP controllers */
+#define HCI_AMP_EVENT_MASK_3_0 "\x00\x00\x00\x00\x00\x00\x3F\xFF"
+
+/* 0x0000000000000000 No events specified (default)
+ 0x0000000000000001 Physical Link Complete Event
+ 0x0000000000000002 Channel Selected Event
+ 0x0000000000000004 Disconnection Physical Link Event
+ 0x0000000000000008 Physical Link Loss Early Warning Event
+ 0x0000000000000010 Physical Link Recovery Event
+ 0x0000000000000020 Logical Link Complete Event
+ 0x0000000000000040 Disconnection Logical Link Complete Event
+ 0x0000000000000080 Flow Spec Modify Complete Event
+ 0x0000000000000100 Number of Completed Data Blocks Event
+ 0x0000000000000200 AMP Start Test Event
+ 0x0000000000000400 AMP Test End Event
+ 0x0000000000000800 AMP Receiver Report Event
+ 0x0000000000001000 Short Range Mode Change Complete Event
+ 0x0000000000002000 AMP Status Change Event
+*/
+
+/* the event mask page 2 (CLB + CSA4) for BR/EDR controller */
+#define HCI_PAGE_2_EVENT_MASK "\x00\x00\x00\x00\x00\x7F\xC0\x00"
+/* 0x0000000000004000 Triggered Clock Capture Event
+ 0x0000000000008000 Sync Train Complete Event
+ 0x0000000000010000 Sync Train Received Event
+ 0x0000000000020000 Connectionless Broadcast Receive Event
+ 0x0000000000040000 Connectionless Broadcast Timeout Event
+ 0x0000000000080000 Truncated Page Complete Event
+ 0x0000000000100000 Salve Page Response Timeout Event
+ 0x0000000000200000 Connectionless Broadcast Channel Map Change Event
+ 0x0000000000400000 Inquiry Response Notification Event
+*/
+
/*
* Definitions for packet type masks (BT1.2 and BT2.0 definitions)
*/
-typedef enum : uint16_t {
- HCI_PKT_TYPES_MASK_NO_2_DH1 = 0x0002,
- HCI_PKT_TYPES_MASK_NO_3_DH1 = 0x0004,
- HCI_PKT_TYPES_MASK_DM1 = 0x0008,
- HCI_PKT_TYPES_MASK_DH1 = 0x0010,
- HCI_PKT_TYPES_MASK_HV1 = 0x0020,
- HCI_PKT_TYPES_MASK_HV2 = 0x0040,
- HCI_PKT_TYPES_MASK_HV3 = 0x0080,
- HCI_PKT_TYPES_MASK_NO_2_DH3 = 0x0100,
- HCI_PKT_TYPES_MASK_NO_3_DH3 = 0x0200,
- HCI_PKT_TYPES_MASK_DM3 = 0x0400,
- HCI_PKT_TYPES_MASK_DH3 = 0x0800,
- HCI_PKT_TYPES_MASK_NO_2_DH5 = 0x1000,
- HCI_PKT_TYPES_MASK_NO_3_DH5 = 0x2000,
- HCI_PKT_TYPES_MASK_DM5 = 0x4000,
- HCI_PKT_TYPES_MASK_DH5 = 0x8000,
-} tHCI_PKT_TYPE_BITMASK;
+#define HCI_PKT_TYPES_MASK_NO_2_DH1 0x0002
+#define HCI_PKT_TYPES_MASK_NO_3_DH1 0x0004
+#define HCI_PKT_TYPES_MASK_DM1 0x0008
+#define HCI_PKT_TYPES_MASK_DH1 0x0010
+#define HCI_PKT_TYPES_MASK_HV1 0x0020
+#define HCI_PKT_TYPES_MASK_HV2 0x0040
+#define HCI_PKT_TYPES_MASK_HV3 0x0080
+#define HCI_PKT_TYPES_MASK_NO_2_DH3 0x0100
+#define HCI_PKT_TYPES_MASK_NO_3_DH3 0x0200
+#define HCI_PKT_TYPES_MASK_DM3 0x0400
+#define HCI_PKT_TYPES_MASK_DH3 0x0800
+#define HCI_PKT_TYPES_MASK_NO_2_DH5 0x1000
+#define HCI_PKT_TYPES_MASK_NO_3_DH5 0x2000
+#define HCI_PKT_TYPES_MASK_DM5 0x4000
+#define HCI_PKT_TYPES_MASK_DH5 0x8000
+
+/* Packet type should be one of valid but at least one should be specified */
+#define HCI_VALID_SCO_PKT_TYPE(t) \
+ (((((t) & \
+ ~(HCI_PKT_TYPES_MASK_HV1 | HCI_PKT_TYPES_MASK_HV2 | \
+ HCI_PKT_TYPES_MASK_HV3)) == 0)) && \
+ ((t) != 0))
+
+/* Packet type should not be invalid and at least one should be specified */
+#define HCI_VALID_ACL_PKT_TYPE(t) \
+ (((((t) & \
+ ~(HCI_PKT_TYPES_MASK_DM1 | HCI_PKT_TYPES_MASK_DH1 | \
+ HCI_PKT_TYPES_MASK_DM3 | HCI_PKT_TYPES_MASK_DH3 | \
+ HCI_PKT_TYPES_MASK_DM5 | HCI_PKT_TYPES_MASK_DH5 | \
+ HCI_PKT_TYPES_MASK_NO_2_DH1 | HCI_PKT_TYPES_MASK_NO_3_DH1 | \
+ HCI_PKT_TYPES_MASK_NO_2_DH3 | HCI_PKT_TYPES_MASK_NO_3_DH3 | \
+ HCI_PKT_TYPES_MASK_NO_2_DH5 | HCI_PKT_TYPES_MASK_NO_3_DH5)) == 0)) && \
+ (((t) & (HCI_PKT_TYPES_MASK_DM1 | HCI_PKT_TYPES_MASK_DH1 | \
+ HCI_PKT_TYPES_MASK_DM3 | HCI_PKT_TYPES_MASK_DH3 | \
+ HCI_PKT_TYPES_MASK_DM5 | HCI_PKT_TYPES_MASK_DH5)) != 0))
+
+/* Packet type should be one of valid but at least one should be specified for
+ * 1.2 */
+#define HCI_VALID_ESCO_PKT_TYPE(t) \
+ (((((t) & \
+ ~(HCI_ESCO_PKT_TYPES_MASK_EV3 | HCI_ESCO_PKT_TYPES_MASK_EV4 | \
+ HCI_ESCO_PKT_TYPES_MASK_EV5)) == 0)) && \
+ ((t) != 0)) /* Packet type should be one of valid but at least one should \
+ be specified */
+
+#define HCI_VALID_ESCO_SCOPKT_TYPE(t) \
+ (((((t) & \
+ ~(ESCO_PKT_TYPES_MASK_HV1 | HCI_ESCO_PKT_TYPES_MASK_HV2 | \
+ HCI_ESCO_PKT_TYPES_MASK_HV3)) == 0)) && \
+ ((t) != 0))
+
+#define HCI_VALID_SCO_ALL_PKT_TYPE(t) \
+ (((((t) & \
+ ~(ESCO_PKT_TYPES_MASK_HV1 | HCI_ESCO_PKT_TYPES_MASK_HV2 | \
+ HCI_ESCO_PKT_TYPES_MASK_HV3 | HCI_ESCO_PKT_TYPES_MASK_EV3 | \
+ HCI_ESCO_PKT_TYPES_MASK_EV4 | HCI_ESCO_PKT_TYPES_MASK_EV5)) == 0)) && \
+ ((t) != 0))
/*
* Define parameters to allow role switch during create connection
@@ -698,39 +862,93 @@ typedef enum : uint16_t {
#define HCI_CR_CONN_NOT_ALLOW_SWITCH 0x00
#define HCI_CR_CONN_ALLOW_SWITCH 0x01
+/*
+ * Hold Mode command destination
+*/
+#define HOLD_MODE_DEST_LOCAL_DEVICE 0x00
+#define HOLD_MODE_DEST_RMT_DEVICE 0x01
+
+/*
+ * Definitions for different HCI parameters
+*/
+#define HCI_PER_INQ_MIN_MAX_PERIOD 0x0003
+#define HCI_PER_INQ_MAX_MAX_PERIOD 0xFFFF
+#define HCI_PER_INQ_MIN_MIN_PERIOD 0x0002
+#define HCI_PER_INQ_MAX_MIN_PERIOD 0xFFFE
+
+#define HCI_MAX_INQUIRY_LENGTH 0x30
+
+#define HCI_MIN_INQ_LAP 0x9E8B00
+#define HCI_MAX_INQ_LAP 0x9E8B3F
+
+/* HCI role defenitions */
+#define HCI_ROLE_MASTER 0x00
+#define HCI_ROLE_SLAVE 0x01
+#define HCI_ROLE_UNKNOWN 0xff
+
/* HCI mode defenitions */
-typedef enum : uint8_t {
- HCI_MODE_ACTIVE = 0x00,
- HCI_MODE_HOLD = 0x01,
- HCI_MODE_SNIFF = 0x02,
- HCI_MODE_PARK = 0x03,
-} tHCI_MODE;
-
-inline std::string hci_mode_text(const tHCI_MODE& mode) {
- switch (mode) {
- case HCI_MODE_ACTIVE:
- return std::string("active");
- case HCI_MODE_HOLD:
- return std::string("hold");
- case HCI_MODE_SNIFF:
- return std::string("sniff");
- case HCI_MODE_PARK:
- return std::string("park");
- default:
- return std::string("UNKNOWN");
- }
-}
+#define HCI_MODE_ACTIVE 0x00
+#define HCI_MODE_HOLD 0x01
+#define HCI_MODE_SNIFF 0x02
+#define HCI_MODE_PARK 0x03
+
+/* HCI Flow Control Mode defenitions */
+#define HCI_PACKET_BASED_FC_MODE 0x00
+#define HCI_BLOCK_BASED_FC_MODE 0x01
+
+/* Define Packet types as requested by the Host */
+#define HCI_ACL_PKT_TYPE_NONE 0x0000
+#define HCI_ACL_PKT_TYPE_DM1 0x0008
+#define HCI_ACL_PKT_TYPE_DH1 0x0010
+#define HCI_ACL_PKT_TYPE_AUX1 0x0200
+#define HCI_ACL_PKT_TYPE_DM3 0x0400
+#define HCI_ACL_PKT_TYPE_DH3 0x0800
+#define HCI_ACL_PKT_TYPE_DM5 0x4000
+#define HCI_ACL_PKT_TYPE_DH5 0x8000
+
+/* Define key type in the Master Link Key command */
+#define HCI_USE_SEMI_PERMANENT_KEY 0x00
+#define HCI_USE_TEMPORARY_KEY 0x01
/* Page scan period modes */
+#define HCI_PAGE_SCAN_REP_MODE_R0 0x00
#define HCI_PAGE_SCAN_REP_MODE_R1 0x01
+#define HCI_PAGE_SCAN_REP_MODE_R2 0x02
+
+/* Define limits for page scan repetition modes */
+#define HCI_PAGE_SCAN_R1_LIMIT 0x0800
+#define HCI_PAGE_SCAN_R2_LIMIT 0x1000
+
+/* Page scan period modes */
+#define HCI_PAGE_SCAN_PER_MODE_P0 0x00
+#define HCI_PAGE_SCAN_PER_MODE_P1 0x01
+#define HCI_PAGE_SCAN_PER_MODE_P2 0x02
/* Page scan modes */
#define HCI_MANDATARY_PAGE_SCAN_MODE 0x00
+#define HCI_OPTIONAL_PAGE_SCAN_MODE1 0x01
+#define HCI_OPTIONAL_PAGE_SCAN_MODE2 0x02
+#define HCI_OPTIONAL_PAGE_SCAN_MODE3 0x03
/* Page and inquiry scan types */
#define HCI_SCAN_TYPE_STANDARD 0x00
+#define HCI_SCAN_TYPE_INTERLACED 0x01 /* 1.2 devices or later */
#define HCI_DEF_SCAN_TYPE HCI_SCAN_TYPE_STANDARD
+/* Definitions for quality of service service types */
+#define HCI_SERVICE_NO_TRAFFIC 0x00
+#define HCI_SERVICE_BEST_EFFORT 0x01
+#define HCI_SERVICE_GUARANTEED 0x02
+
+#define HCI_QOS_LATENCY_DO_NOT_CARE 0xFFFFFFFF
+#define HCI_QOS_DELAY_DO_NOT_CARE 0xFFFFFFFF
+
+/* Definitions for Flow Specification */
+#define HCI_FLOW_SPEC_LATENCY_DO_NOT_CARE 0xFFFFFFFF
+
+/* Definitions for AFH Channel Map */
+#define HCI_AFH_CHANNEL_MAP_LEN 10
+
/* Definitions for Extended Inquiry Response */
#define HCI_EXT_INQ_RESPONSE_LEN 240
#define HCI_EIR_FLAGS_TYPE BT_EIR_FLAGS_TYPE
@@ -757,59 +975,125 @@ inline std::string hci_mode_text(const tHCI_MODE& mode) {
#define HCI_EIR_OOB_SSP_RAND_R_TYPE BT_EIR_OOB_SSP_RAND_R_TYPE
/* Definitions for Write Simple Pairing Mode */
+#define HCI_SP_MODE_UNDEFINED 0x00
#define HCI_SP_MODE_ENABLED 0x01
+/* Definitions for Write Simple Pairing Debug Mode */
+#define HCI_SPD_MODE_DISABLED 0x00
+#define HCI_SPD_MODE_ENABLED 0x01
+
/* Definitions for Write Secure Connections Host Support */
+#define HCI_SC_MODE_DISABLED 0x00
#define HCI_SC_MODE_ENABLED 0x01
+/* Definitions for IO Capability Response/Command */
+#define HCI_IO_CAP_DISPLAY_ONLY 0x00
+#define HCI_IO_CAP_DISPLAY_YESNO 0x01
+#define HCI_IO_CAP_KEYBOARD_ONLY 0x02
+#define HCI_IO_CAP_NO_IO 0x03
+
+#define HCI_OOB_AUTH_DATA_NOT_PRESENT 0x00
+#define HCI_OOB_REM_AUTH_DATA_PRESENT 0x01
+
+#define HCI_MITM_PROTECT_NOT_REQUIRED 0x00
+#define HCI_MITM_PROTECT_REQUIRED 0x01
+
+/* Policy settings status */
+#define HCI_DISABLE_ALL_LM_MODES 0x0000
+#define HCI_ENABLE_MASTER_SLAVE_SWITCH 0x0001
+#define HCI_ENABLE_HOLD_MODE 0x0002
+#define HCI_ENABLE_SNIFF_MODE 0x0004
+#define HCI_ENABLE_PARK_MODE 0x0008
+
+/* By default allow switch, because host can not allow that */
+/* that until he created the connection */
+#define HCI_DEFAULT_POLICY_SETTINGS HCI_DISABLE_ALL_LM_MODES
+
/* Filters that are sent in set filter command */
+#define HCI_FILTER_TYPE_CLEAR_ALL 0x00
+#define HCI_FILTER_INQUIRY_RESULT 0x01
#define HCI_FILTER_CONNECTION_SETUP 0x02
#define HCI_FILTER_COND_NEW_DEVICE 0x00
#define HCI_FILTER_COND_DEVICE_CLASS 0x01
#define HCI_FILTER_COND_BD_ADDR 0x02
+#define HCI_DO_NOT_AUTO_ACCEPT_CONNECT 1
/* role switch disabled */
#define HCI_DO_AUTO_ACCEPT_CONNECT 2
+/* role switch enabled (1.1 errata 1115) */
+#define HCI_DO_AUTO_ACCEPT_CONNECT_RS 3
+
+/* Auto accept flags */
+#define HCI_AUTO_ACCEPT_OFF 0x00
+#define HCI_AUTO_ACCEPT_ACL_CONNECTIONS 0x01
+#define HCI_AUTO_ACCEPT_SCO_CONNECTIONS 0x02
/* PIN type */
+#define HCI_PIN_TYPE_VARIABLE 0
#define HCI_PIN_TYPE_FIXED 1
+/* Loopback Modes */
+#define HCI_LOOPBACK_MODE_DISABLED 0
+#define HCI_LOOPBACK_MODE_LOCAL 1
+#define HCI_LOOPBACK_MODE_REMOTE 2
+
+#define SLOTS_PER_10MS 16 /* 0.625 ms slots in a 10 ms tick */
+
+/* Maximum connection accept timeout in 0.625msec */
+#define HCI_MAX_CONN_ACCEPT_TOUT 0xB540 /* 29 sec */
+#define HCI_DEF_CONN_ACCEPT_TOUT 0x1F40 /* 5 sec */
+
+/* Page timeout is used in LC only and LC is counting down slots not using OS */
+#define HCI_DEFAULT_PAGE_TOUT 0x2000 /* 5.12 sec (in slots) */
+
/* Scan enable flags */
+#define HCI_NO_SCAN_ENABLED 0x00
#define HCI_INQUIRY_SCAN_ENABLED 0x01
#define HCI_PAGE_SCAN_ENABLED 0x02
/* Pagescan timer definitions in 0.625 ms */
+#define HCI_MIN_PAGESCAN_INTERVAL 0x12 /* 11.25 ms */
+#define HCI_MAX_PAGESCAN_INTERVAL 0x1000 /* 2.56 sec */
#define HCI_DEF_PAGESCAN_INTERVAL 0x0800 /* 1.28 sec */
/* Parameter for pagescan window is passed to LC and is kept in slots */
+#define HCI_MIN_PAGESCAN_WINDOW 0x11 /* 10.625 ms */
+#define HCI_MAX_PAGESCAN_WINDOW 0x1000 /* 2.56 sec */
#define HCI_DEF_PAGESCAN_WINDOW 0x12 /* 11.25 ms */
/* Inquiryscan timer definitions in 0.625 ms */
+#define HCI_MIN_INQUIRYSCAN_INTERVAL 0x12 /* 11.25 ms */
+#define HCI_MAX_INQUIRYSCAN_INTERVAL 0x1000 /* 2.56 sec */
#define HCI_DEF_INQUIRYSCAN_INTERVAL 0x1000 /* 2.56 sec */
/* Parameter for inquiryscan window is passed to LC and is kept in slots */
+#define HCI_MIN_INQUIRYSCAN_WINDOW 0x11 /* 10.625 ms */
+#define HCI_MAX_INQUIRYSCAN_WINDOW 0x1000 /* 2.56 sec */
#define HCI_DEF_INQUIRYSCAN_WINDOW 0x12 /* 11.25 ms */
/* Encryption modes */
-typedef enum : uint8_t {
- HCI_ENCRYPT_MODE_DISABLED = 0x00,
- HCI_ENCRYPT_MODE_ON = 0x01,
- HCI_ENCRYPT_MODE_ON_BR_EDR_AES_CCM = 0x02,
-} tHCI_ENCRYPT_MODE;
+#define HCI_ENCRYPT_MODE_DISABLED 0x00
+#define HCI_ENCRYPT_MODE_POINT_TO_POINT 0x01
+#define HCI_ENCRYPT_MODE_ALL 0x02
/* Voice settings */
#define HCI_INP_CODING_LINEAR 0x0000 /* 0000000000 */
#define HCI_INP_CODING_U_LAW 0x0100 /* 0100000000 */
#define HCI_INP_CODING_A_LAW 0x0200 /* 1000000000 */
+#define HCI_INP_CODING_MASK 0x0300 /* 1100000000 */
+#define HCI_INP_DATA_FMT_1S_COMPLEMENT 0x0000 /* 0000000000 */
#define HCI_INP_DATA_FMT_2S_COMPLEMENT 0x0040 /* 0001000000 */
#define HCI_INP_DATA_FMT_SIGN_MAGNITUDE 0x0080 /* 0010000000 */
#define HCI_INP_DATA_FMT_UNSIGNED 0x00c0 /* 0011000000 */
+#define HCI_INP_DATA_FMT_MASK 0x00c0 /* 0011000000 */
#define HCI_INP_SAMPLE_SIZE_8BIT 0x0000 /* 0000000000 */
#define HCI_INP_SAMPLE_SIZE_16BIT 0x0020 /* 0000100000 */
+#define HCI_INP_SAMPLE_SIZE_MASK 0x0020 /* 0000100000 */
+#define HCI_INP_LINEAR_PCM_BIT_POS_MASK 0x001c /* 0000011100 */
#define HCI_INP_LINEAR_PCM_BIT_POS_OFFS 2
#define HCI_AIR_CODING_FORMAT_CVSD 0x0000 /* 0000000000 */
@@ -823,14 +1107,40 @@ typedef enum : uint8_t {
(HCI_INP_CODING_LINEAR | HCI_INP_DATA_FMT_2S_COMPLEMENT | \
HCI_INP_SAMPLE_SIZE_16BIT | HCI_AIR_CODING_FORMAT_CVSD)
+#define HCI_CVSD_SUPPORTED(x) \
+ (((x)&HCI_AIR_CODING_FORMAT_MASK) == HCI_AIR_CODING_FORMAT_CVSD)
+#define HCI_U_LAW_SUPPORTED(x) \
+ (((x)&HCI_AIR_CODING_FORMAT_MASK) == HCI_AIR_CODING_FORMAT_U_LAW)
+#define HCI_A_LAW_SUPPORTED(x) \
+ (((x)&HCI_AIR_CODING_FORMAT_MASK) == HCI_AIR_CODING_FORMAT_A_LAW)
+#define HCI_TRANSPNT_SUPPORTED(x) \
+ (((x)&HCI_AIR_CODING_FORMAT_MASK) == HCI_AIR_CODING_FORMAT_TRANSPNT)
+
/* Retransmit timer definitions in 0.625 */
#define HCI_MAX_AUTOMATIC_FLUSH_TIMEOUT 0x07FF
+#define HCI_DEFAULT_AUTOMATIC_FLUSH_TIMEOUT 0 /* No auto flush */
+
+/* Broadcast retransmitions */
+#define HCI_DEFAULT_NUM_BCAST_RETRAN 1
+
+/* Define broadcast data types as passed in the hci data packet */
+#define HCI_DATA_POINT_TO_POINT 0x00
+#define HCI_DATA_ACTIVE_BCAST 0x01
+#define HCI_DATA_PICONET_BCAST 0x02
+
+/* Hold mode activity */
+#define HCI_MAINTAIN_CUR_POWER_STATE 0x00
+#define HCI_SUSPEND_PAGE_SCAN 0x01
+#define HCI_SUSPEND_INQUIRY_SCAN 0x02
+#define HCI_SUSPEND_PERIODIC_INQUIRIES 0x04
/* Default Link Supervision timeoout */
#define HCI_DEFAULT_INACT_TOUT 0x7D00 /* BR/EDR (20 seconds) */
+#define HCI_DEFAULT_AMP_INACT_TOUT 0x3E80 /* AMP (10 seconds) */
/* Read transmit power level parameter */
#define HCI_READ_CURRENT 0x00
+#define HCI_READ_MAXIMUM 0x01
/* Link types for connection complete event */
#define HCI_LINK_TYPE_SCO 0x00
@@ -839,6 +1149,7 @@ typedef enum : uint8_t {
/* Link Key Notification Event (Key Type) definitions */
#define HCI_LKEY_TYPE_COMBINATION 0x00
+#define HCI_LKEY_TYPE_LOCAL_UNIT 0x01
#define HCI_LKEY_TYPE_REMOTE_UNIT 0x02
#define HCI_LKEY_TYPE_DEBUG_COMB 0x03
#define HCI_LKEY_TYPE_UNAUTH_COMB 0x04
@@ -847,9 +1158,21 @@ typedef enum : uint8_t {
#define HCI_LKEY_TYPE_UNAUTH_COMB_P_256 0x07
#define HCI_LKEY_TYPE_AUTH_COMB_P_256 0x08
+/* Internal definitions - not used over HCI */
+#define HCI_LKEY_TYPE_AMP_WIFI 0x80
+#define HCI_LKEY_TYPE_AMP_UWB 0x81
+#define HCI_LKEY_TYPE_UNKNOWN 0xff
+
+/* Read Local Version HCI Version return values (Command Complete Event) */
+#define HCI_VERSION_1_0B 0x00
+#define HCI_VERSION_1_1 0x01
+
/* Define an invalid value for a handle */
#define HCI_INVALID_HANDLE 0xFFFF
+/* Define max ammount of data in the HCI command */
+#define HCI_COMMAND_SIZE 255
+
/* Define the preamble length for all HCI Commands.
* This is 2-bytes for opcode and 1 byte for length
*/
@@ -860,44 +1183,39 @@ typedef enum : uint8_t {
*/
#define HCIE_PREAMBLE_SIZE 2
#define HCI_SCO_PREAMBLE_SIZE 3
-
-// Packet boundary flags
-constexpr uint8_t kFIRST_NON_AUTOMATICALLY_FLUSHABLE = 0x0;
-constexpr uint8_t kCONTINUING_FRAGMENT = 0x1;
-constexpr uint8_t kHCI_FIRST_AUTOMATICALLY_FLUSHABLE = 0x2;
-
-struct HciDataPreambleBits {
- uint16_t handle : 12;
- uint16_t boundary : 2;
- uint16_t broadcast : 1;
- uint16_t unused15 : 1;
- uint16_t length;
-};
-struct HciDataPreambleRaw {
- uint16_t word0;
- uint16_t word1;
-};
-union HciDataPreamble {
- HciDataPreambleBits bits;
- HciDataPreambleRaw raw;
- void Serialize(uint8_t* data) {
- *data++ = ((raw.word0) & 0xff);
- *data++ = (((raw.word0) >> 8) & 0xff);
- *data++ = ((raw.word1) & 0xff);
- *data++ = (((raw.word1 >> 8)) & 0xff);
- }
- bool IsFlushable() const {
- return bits.boundary == kHCI_FIRST_AUTOMATICALLY_FLUSHABLE;
- }
- void SetFlushable() { bits.boundary = kHCI_FIRST_AUTOMATICALLY_FLUSHABLE; }
-};
-#define HCI_DATA_PREAMBLE_SIZE sizeof(HciDataPreamble)
-static_assert(HCI_DATA_PREAMBLE_SIZE == 4);
-static_assert(sizeof(HciDataPreambleRaw) == sizeof(HciDataPreambleBits));
+#define HCI_DATA_PREAMBLE_SIZE 4
/* local Bluetooth controller id for AMP HCI */
#define LOCAL_BR_EDR_CONTROLLER_ID 0
+/* controller id types for AMP HCI */
+#define HCI_CONTROLLER_TYPE_BR_EDR 0
+#define HCI_CONTROLLER_TYPE_802_11 1
+#define HCI_CONTROLLER_TYPE_ECMA 2
+#define HCI_MAX_CONTROLLER_TYPES 3
+
+/* ConnectionLess Broadcast */
+#define HCI_CLB_DISABLE 0x00
+#define HCI_CLB_ENABLE 0x01
+
+/* ConnectionLess Broadcast Data fragment */
+#define HCI_CLB_FRAGMENT_CONT 0x00
+#define HCI_CLB_FRAGMENT_START 0x01
+#define HCI_CLB_FRAGMENT_END 0x02
+#define HCI_CLB_FRAGMENT_SINGLE 0x03
+
+/* AMP Controller Status codes
+*/
+#define HCI_AMP_CTRLR_PHYSICALLY_DOWN 0
+#define HCI_AMP_CTRLR_USABLE_BY_BT 1
+#define HCI_AMP_CTRLR_UNUSABLE_FOR_BT 2
+#define HCI_AMP_CTRLR_LOW_CAP_FOR_BT 3
+#define HCI_AMP_CTRLR_MED_CAP_FOR_BT 4
+#define HCI_AMP_CTRLR_HIGH_CAP_FOR_BT 5
+#define HCI_AMP_CTRLR_FULL_CAP_FOR_BT 6
+
+#define HCI_MAX_AMP_STATUS_TYPES 7
+
/* Define the extended flow specification fields used by AMP */
typedef struct {
uint8_t id;
@@ -908,18 +1226,78 @@ typedef struct {
uint32_t flush_timeout;
} tHCI_EXT_FLOW_SPEC;
+/* HCI message type definitions (for H4 messages) */
+#define HCIT_TYPE_COMMAND 1
+#define HCIT_TYPE_ACL_DATA 2
+#define HCIT_TYPE_SCO_DATA 3
+#define HCIT_TYPE_EVENT 4
+#define HCIT_TYPE_LM_DIAG 7
+#define HCIT_TYPE_NFC 16
+
+#define HCIT_LM_DIAG_LENGTH 63
+
/* Parameter information for HCI_BRCM_SET_ACL_PRIORITY */
#define HCI_BRCM_ACL_PRIORITY_PARAM_SIZE 3
#define HCI_BRCM_ACL_PRIORITY_LOW 0x00
#define HCI_BRCM_ACL_PRIORITY_HIGH 0xFF
#define HCI_BRCM_SET_ACL_PRIORITY (0x0057 | HCI_GRP_VENDOR_SPECIFIC)
+/* Define values for LMP Test Control parameters
+ * Test Scenario, Hopping Mode, Power Control Mode
+*/
+#define LMP_TESTCTL_TESTSC_PAUSE 0
+#define LMP_TESTCTL_TESTSC_TXTEST_0 1
+#define LMP_TESTCTL_TESTSC_TXTEST_1 2
+#define LMP_TESTCTL_TESTSC_TXTEST_1010 3
+#define LMP_TESTCTL_TESTSC_PSRND_BITSEQ 4
+#define LMP_TESTCTL_TESTSC_CLOSEDLB_ACL 5
+#define LMP_TESTCTL_TESTSC_CLOSEDLB_SCO 6
+#define LMP_TESTCTL_TESTSC_ACL_NOWHIT 7
+#define LMP_TESTCTL_TESTSC_SCO_NOWHIT 8
+#define LMP_TESTCTL_TESTSC_TXTEST_11110000 9
+#define LMP_TESTCTL_TESTSC_EXITTESTMODE 255
+
+#define LMP_TESTCTL_HOPMOD_RXTX1FREQ 0
+#define LMP_TESTCTL_HOPMOD_HOP_EURUSA 1
+#define LMP_TESTCTL_HOPMOD_HOP_JAPAN 2
+#define LMP_TESTCTL_HOPMOD_HOP_FRANCE 3
+#define LMP_TESTCTL_HOPMOD_HOP_SPAIN 4
+#define LMP_TESTCTL_HOPMOD_REDUCED_HOP 5
+
+#define LMP_TESTCTL_POWCTL_FIXEDTX_OP 0
+#define LMP_TESTCTL_POWCTL_ADAPTIVE 1
+
#define LMP_COMPID_GOOGLE 0xE0
// TODO(zachoverflow): remove this once broadcom specific hacks are removed
#define LMP_COMPID_BROADCOM 15
/*
+ * Define the packet types in the packet header, and a couple extra
+*/
+#define PKT_TYPE_NULL 0x00
+#define PKT_TYPE_POLL 0x01
+#define PKT_TYPE_FHS 0x02
+#define PKT_TYPE_DM1 0x03
+
+#define PKT_TYPE_DH1 0x04
+#define PKT_TYPE_HV1 0x05
+#define PKT_TYPE_HV2 0x06
+#define PKT_TYPE_HV3 0x07
+#define PKT_TYPE_DV 0x08
+#define PKT_TYPE_AUX1 0x09
+
+#define PKT_TYPE_DM3 0x0a
+#define PKT_TYPE_DH3 0x0b
+
+#define PKT_TYPE_DM5 0x0e
+#define PKT_TYPE_DH5 0x0f
+
+#define PKT_TYPE_ID 0x10 /* Internally used packet types */
+#define PKT_TYPE_BAD 0x11
+#define PKT_TYPE_NONE 0x12
+
+/*
* Define packet size
*/
#define HCI_DM1_PACKET_SIZE 17
@@ -947,6 +1325,9 @@ typedef struct {
#define HCI_EXT_FEATURES_SUCCESS_EVT_LEN 13
+#define HCI_FEATURES_KNOWN(x) \
+ (((x)[0] | (x)[1] | (x)[2] | (x)[3] | (x)[4] | (x)[5] | (x)[6] | (x)[7]) != 0)
+
/* LMP features encoding - page 0 */
#define HCI_3_SLOT_PACKETS_SUPPORTED(x) ((x)[0] & 0x01)
#define HCI_5_SLOT_PACKETS_SUPPORTED(x) ((x)[0] & 0x02)
@@ -985,14 +1366,14 @@ typedef struct {
#define HCI_ESCO_EV4_SUPPORTED(x) ((x)[4] & 0x01)
#define HCI_ESCO_EV5_SUPPORTED(x) ((x)[4] & 0x02)
#define HCI_LMP_ABSENCE_MASKS_SUPPORTED(x) ((x)[4] & 0x04)
-#define HCI_LMP_AFH_CAP_PERIPHERAL_SUPPORTED(x) ((x)[4] & 0x08)
-#define HCI_LMP_AFH_CLASS_PERIPHERAL_SUPPORTED(x) ((x)[4] & 0x10)
+#define HCI_LMP_AFH_CAP_SLAVE_SUPPORTED(x) ((x)[4] & 0x08)
+#define HCI_LMP_AFH_CLASS_SLAVE_SUPPORTED(x) ((x)[4] & 0x10)
#define HCI_BREDR_NOT_SPT_SUPPORTED(x) ((x)[4] & 0x20)
#define HCI_LE_SPT_SUPPORTED(x) ((x)[4] & 0x40)
#define HCI_3_SLOT_EDR_ACL_SUPPORTED(x) ((x)[4] & 0x80)
#define HCI_5_SLOT_EDR_ACL_SUPPORTED(x) ((x)[5] & 0x01)
-#define HCI_SNIFF_SUB_RATE_SUPPORTED(x) (static_cast<bool>((x)[5] & 0x02))
+#define HCI_SNIFF_SUB_RATE_SUPPORTED(x) ((x)[5] & 0x02)
#define HCI_ATOMIC_ENCRYPT_SUPPORTED(x) ((x)[5] & 0x04)
#define HCI_LMP_AFH_CAP_MASTR_SUPPORTED(x) ((x)[5] & 0x08)
#define HCI_LMP_AFH_CLASS_MASTR_SUPPORTED(x) ((x)[5] & 0x10)
@@ -1021,10 +1402,10 @@ typedef struct {
#define HCI_SC_HOST_SUPPORTED(x) ((x)[0] & 0x08)
/* LMP features encoding - page 2 */
-#define HCI_CSB_CENTRAL_SUPPORTED(x) ((x)[0] & 0x01)
-#define HCI_CSB_PERIPHERAL_SUPPORTED(x) ((x)[0] & 0x02)
-#define HCI_SYNC_TRAIN_CENTRAL_SUPPORTED(x) ((x)[0] & 0x04)
-#define HCI_SYNC_SCAN_PERIPHERAL_SUPPORTED(x) ((x)[0] & 0x08)
+#define HCI_CSB_MASTER_SUPPORTED(x) ((x)[0] & 0x01)
+#define HCI_CSB_SLAVE_SUPPORTED(x) ((x)[0] & 0x02)
+#define HCI_SYNC_TRAIN_MASTER_SUPPORTED(x) ((x)[0] & 0x04)
+#define HCI_SYNC_SCAN_SLAVE_SUPPORTED(x) ((x)[0] & 0x08)
#define HCI_INQ_RESP_NOTIF_SUPPORTED(x) ((x)[0] & 0x10)
#define HCI_SC_CTRLR_SUPPORTED(x) ((x)[1] & 0x01)
@@ -1034,7 +1415,7 @@ typedef struct {
#define HCI_LE_ENCRYPTION_SUPPORTED(x) ((x)[0] & 0x01)
#define HCI_LE_CONN_PARAM_REQ_SUPPORTED(x) ((x)[0] & 0x02)
#define HCI_LE_EXT_REJ_IND_SUPPORTED(x) ((x)[0] & 0x04)
-#define HCI_LE_PERIPHERAL_INIT_FEAT_EXC_SUPPORTED(x) ((x)[0] & 0x08)
+#define HCI_LE_SLAVE_INIT_FEAT_EXC_SUPPORTED(x) ((x)[0] & 0x08)
#define HCI_LE_DATA_LEN_EXT_SUPPORTED(x) ((x)[0] & 0x20)
#define HCI_LE_ENHANCED_PRIVACY_SUPPORTED(x) ((x)[0] & 0x40)
#define HCI_LE_EXT_SCAN_FILTER_POLICY_SUPPORTED(x) ((x)[0] & 0x80)
@@ -1043,12 +1424,6 @@ typedef struct {
#define HCI_LE_CODED_PHY_SUPPORTED(x) ((x)[1] & 0x08)
#define HCI_LE_EXTENDED_ADVERTISING_SUPPORTED(x) ((x)[1] & 0x10)
#define HCI_LE_PERIODIC_ADVERTISING_SUPPORTED(x) ((x)[1] & 0x20)
-#define HCI_LE_PERIODIC_ADVERTISING_SYNC_TRANSFER_SENDER(x) ((x)[3] & 0x01)
-#define HCI_LE_PERIODIC_ADVERTISING_SYNC_TRANSFER_RECIPIENT(x) ((x)[3] & 0x02)
-#define HCI_LE_CIS_CENTRAL(x) ((x)[3] & 0x10)
-#define HCI_LE_CIS_PERIPHERAL(x) ((x)[3] & 0x20)
-#define HCI_LE_ISO_BROADCASTER(x) ((x)[3] & 0x40)
-#define HCI_LE_SYNCHRONIZED_RECEIVER(x) ((x)[3] & 0x80)
/* Supported Commands*/
#define HCI_NUM_SUPP_COMMANDS_BYTES 64
@@ -1073,7 +1448,7 @@ typedef struct {
#define HCI_SET_CONN_ENCRYPTION_SUPPORTED(x) ((x)[2] & 0x01)
#define HCI_CHANGE_CONN_LINK_KEY_SUPPORTED(x) ((x)[2] & 0x02)
-#define HCI_CENTRAL_LINK_KEY_SUPPORTED(x) ((x)[2] & 0x04)
+#define HCI_MASTER_LINK_KEY_SUPPORTED(x) ((x)[2] & 0x04)
#define HCI_REMOTE_NAME_REQUEST_SUPPORTED(x) ((x)[2] & 0x08)
#define HCI_CANCEL_REMOTE_NAME_REQUEST_SUPPORTED(x) ((x)[2] & 0x10)
#define HCI_READ_REMOTE_SUPP_FEATURES_SUPPORTED(x) ((x)[2] & 0x20)
@@ -1105,6 +1480,7 @@ typedef struct {
#define HCI_FLUSH_SUPPORTED(x) ((x)[6] & 0x02)
#define HCI_READ_PIN_TYPE_SUPPORTED(x) ((x)[6] & 0x04)
#define HCI_WRITE_PIN_TYPE_SUPPORTED(x) ((x)[6] & 0x08)
+#define HCI_CREATE_NEW_UNIT_KEY_SUPPORTED(x) ((x)[6] & 0x10)
#define HCI_READ_STORED_LINK_KEY_SUPPORTED(x) ((x)[6] & 0x20)
#define HCI_WRITE_STORED_LINK_KEY_SUPPORTED(x) ((x)[6] & 0x40)
#define HCI_DELETE_STORED_LINK_KEY_SUPPORTED(x) ((x)[6] & 0x80)
@@ -1260,13 +1636,13 @@ typedef struct {
#define HCI_TRUNCATED_PAGE_SUPPORTED(x) ((x)[30] & 0x40)
#define HCI_TRUNCATED_PAGE_CANCEL_SUPPORTED(x) ((x)[30] & 0x80)
-#define HCI_SET_CONLESS_PERIPHERAL_BRCST_SUPPORTED(x) ((x)[31] & 0x01)
-#define HCI_SET_CONLESS_PERIPHERAL_BRCST_RECEIVE_SUPPORTED(x) ((x)[31] & 0x02)
+#define HCI_SET_CONLESS_SLAVE_BRCST_SUPPORTED(x) ((x)[31] & 0x01)
+#define HCI_SET_CONLESS_SLAVE_BRCST_RECEIVE_SUPPORTED(x) ((x)[31] & 0x02)
#define HCI_START_SYNC_TRAIN_SUPPORTED(x) ((x)[31] & 0x04)
#define HCI_RECEIVE_SYNC_TRAIN_SUPPORTED(x) ((x)[31] & 0x08)
#define HCI_SET_RESERVED_LT_ADDR_SUPPORTED(x) ((x)[31] & 0x10)
#define HCI_DELETE_RESERVED_LT_ADDR_SUPPORTED(x) ((x)[31] & 0x20)
-#define HCI_SET_CONLESS_PERIPHERAL_BRCST_DATA_SUPPORTED(x) ((x)[31] & 0x40)
+#define HCI_SET_CONLESS_SLAVE_BRCST_DATA_SUPPORTED(x) ((x)[31] & 0x40)
#define HCI_READ_SYNC_TRAIN_PARAM_SUPPORTED(x) ((x)[31] & 0x80)
#define HCI_WRITE_SYNC_TRAIN_PARAM_SUPPORTED(x) ((x)[32] & 0x01)
@@ -1290,6 +1666,4 @@ typedef struct {
#define HCI_LE_SET_PRIVACY_MODE_SUPPORTED(x) ((x)[39] & 0x04)
-#define HCI_LE_SET_HOST_FEATURE_SUPPORTED(x) ((x)[44] & 0x02)
-
#endif
diff --git a/stack/include/hcimsgs.h b/stack/include/hcimsgs.h
index 8502c8c01..285ae419b 100644
--- a/stack/include/hcimsgs.h
+++ b/stack/include/hcimsgs.h
@@ -30,19 +30,39 @@ void bte_main_hci_send(BT_HDR* p_msg, uint16_t event);
/* Message by message.... */
+extern void btsnd_hcic_inquiry(const LAP inq_lap, uint8_t duration,
+ uint8_t response_cnt);
+
+#define HCIC_PARAM_SIZE_INQUIRY 5
+
+#define HCIC_INQ_INQ_LAP_OFF 0
+#define HCIC_INQ_DUR_OFF 3
+#define HCIC_INQ_RSP_CNT_OFF 4
/* Inquiry */
+
/* Inquiry Cancel */
+extern void btsnd_hcic_inq_cancel(void);
+
+#define HCIC_PARAM_SIZE_INQ_CANCEL 0
/* Periodic Inquiry Mode */
extern void btsnd_hcic_per_inq_mode(uint16_t max_period, uint16_t min_period,
const LAP inq_lap, uint8_t duration,
uint8_t response_cnt);
+#define HCIC_PARAM_SIZE_PER_INQ_MODE 9
+
+#define HCI_PER_INQ_MAX_INTRVL_OFF 0
+#define HCI_PER_INQ_MIN_INTRVL_OFF 2
+#define HCI_PER_INQ_INQ_LAP_OFF 4
+#define HCI_PER_INQ_DURATION_OFF 7
+#define HCI_PER_INQ_RSP_CNT_OFF 8
/* Periodic Inquiry Mode */
/* Exit Periodic Inquiry Mode */
extern void btsnd_hcic_exit_per_inq(void);
+#define HCIC_PARAM_SIZE_EXIT_PER_INQ 0
/* Create Connection */
extern void btsnd_hcic_create_conn(const RawAddress& dest,
uint16_t packet_types,
@@ -50,217 +70,76 @@ extern void btsnd_hcic_create_conn(const RawAddress& dest,
uint8_t page_scan_mode,
uint16_t clock_offset, uint8_t allow_switch);
+#define HCIC_PARAM_SIZE_CREATE_CONN 13
+
+#define HCIC_CR_CONN_BD_ADDR_OFF 0
+#define HCIC_CR_CONN_PKT_TYPES_OFF 6
+#define HCIC_CR_CONN_REP_MODE_OFF 8
+#define HCIC_CR_CONN_PAGE_SCAN_MODE_OFF 9
+#define HCIC_CR_CONN_CLK_OFF_OFF 10
+#define HCIC_CR_CONN_ALLOW_SWITCH_OFF 12
/* Create Connection */
/* Disconnect */
-namespace bluetooth {
-namespace legacy {
-namespace hci {
-struct Interface {
- // LINK_CONTROL 0x04xx
- void (*StartInquiry)(const LAP inq_lap, uint8_t duration,
- uint8_t response_cnt);
- void (*InquiryCancel)();
- void (*StartPeriodicInquiryMode)(uint16_t max_period, uint16_t min_period,
- const LAP inq_lap, uint8_t duration,
- uint8_t response_cnt);
- void (*ExitPeriodicInquiryMode)();
- void (*CreateConnection)(const RawAddress& dest, uint16_t packet_types,
- uint8_t page_scan_rep_mode, uint8_t page_scan_mode,
- uint16_t clock_offset, uint8_t allow_switch);
- void (*Disconnect)(uint16_t handle, uint8_t reason);
- // UNUSED 0x0407 btsnd_hcic_add_SCO_conn
- void (*CreateConnectionCancel)(const RawAddress& dest);
- void (*AcceptConnectionRequest)(const RawAddress& dest, uint8_t role);
- void (*RejectConnectionRequest)(const RawAddress& dest, uint8_t reason);
- void (*LinkKeyRequestReply)(const RawAddress& bd_addr,
- const LinkKey& link_key);
- void (*LinkKeyRequestNegativeReply)(const RawAddress& bd_addr);
- void (*PinCodeRequestReply)(const RawAddress& bd_addr, uint8_t pin_code_len,
- PIN_CODE pin_code);
- void (*PinCodeRequestNegativeReply)(const RawAddress& bd_addr);
- void (*ChangeConnectionPacketType)(uint16_t handle, uint16_t packet_types);
- void (*AuthenticationRequested)(uint16_t handle);
- void (*SetConnectionEncryption)(uint16_t handle, bool enable);
- void (*ChangeConnectionLinkKey)(); // 0x0415,
- // UNUSED 0x0416
- void (*CentralLinkKey)(); // 0x0417,
- void (*RemoteNameRequest)(const RawAddress& bd_addr,
- uint8_t page_scan_rep_mode, uint8_t page_scan_mode,
- uint16_t clock_offset);
- void (*RemoteNameRequestCancel)(const RawAddress& bd_addr);
- void (*ReadRemoteSupportedFeatures)(uint16_t handle);
- void (*ReadRemoteExtendedFeatures)(uint16_t handle, uint8_t page_num);
- void (*ReadRemoteVersionInformation)(uint16_t handle);
- void (*ReadClockOffset)(uint16_t handle);
- void (*ReadLmpHandle)(uint16_t handle);
- void (*SetupSynchronousConnection)(uint16_t handle,
- uint32_t transmit_bandwidth,
- uint32_t receive_bandwidth,
- uint16_t max_latency, uint16_t voice,
- uint8_t retrans_effort,
- uint16_t packet_types);
- void (*AcceptSynchronousConnection)(
- const RawAddress& bd_addr, uint32_t transmit_bandwidth,
- uint32_t receive_bandwidth, uint16_t max_latency, uint16_t content_fmt,
- uint8_t retrans_effort, uint16_t packet_types);
- void (*RejectSynchronousConnection)(const RawAddress& bd_addr,
- uint8_t reason);
- void (*IoCapabilityRequestReply)(const RawAddress& bd_addr,
- uint8_t capability, uint8_t oob_present,
- uint8_t auth_req);
- void (*UserConfirmationRequestReply)(const RawAddress& bd_addr, bool is_yes);
- void (*UserConfirmationRequestNegativeReply)(const RawAddress& bd_addr,
- bool is_yes);
- void (*UserPasskeyRequestReply)(const RawAddress& bd_addr, uint32_t value);
- void (*UserPasskeyRequestNegativeReply)(const RawAddress& bd_addr);
- void (*RemoteOobDataRequestReply)(const RawAddress& bd_addr, const Octet16& c,
- const Octet16& r);
- void (*RemoteOobDataRequestNegativeReply)(const RawAddress& bd_addr);
- void (*IoCapabilityRequestNegativeReply)(const RawAddress& bd_addr,
- uint8_t err_code);
- void (*EnhancedSetupSynchronousConnection)(uint16_t conn_handle,
- enh_esco_params_t* p_params);
- void (*EnhancedAcceptSynchronousConnection)(const RawAddress& bd_addr,
- enh_esco_params_t* p_params);
- void (*RemoteOobExtendedDataRequestReply)();
-
- // LINK_POLICY 0x08xx
- void (*HoldMode)(uint16_t handle, uint16_t max_hold_period,
- uint16_t min_hold_period);
- void (*SniffMode)(uint16_t handle, uint16_t max_sniff_period,
- uint16_t min_sniff_period, uint16_t sniff_attempt,
- uint16_t sniff_timeout);
- void (*ExitSniffMode)(uint16_t handle);
- void (*QosSetup)(uint16_t handle, uint8_t flags, uint8_t service_type,
- uint32_t token_rate, uint32_t peak, uint32_t latency,
- uint32_t delay_var);
- // UNUSED 0x0808
- void (*RoleDiscovery)();
- void (*StartRoleSwitch)(const RawAddress& bd_addr, uint8_t role);
- void (*ReadLinkPolicySettings)();
- void (*WriteLinkPolicySettings)(uint16_t handle, uint16_t settings);
- void (*ReadDefaultLinkPolicySettings)();
- void (*WriteDefaultLinkPolicySettings)(uint16_t settings);
- void (*FlowSpecification)();
- void (*SniffSubrating)(uint16_t handle, uint16_t max_lat,
- uint16_t min_remote_lat, uint16_t min_local_lat);
-
- // CONTROLLER_AND_BASEBAND 0x0Cxx
- void (*SetEventMask)();
- void (*Reset)();
- void (*SetEventFilter)(uint8_t filt_type, uint8_t filt_cond_type,
- uint8_t* filt_cond, uint8_t filt_cond_len);
- void (*Flush)();
- void (*ReadPinType)();
- void (*WritePinType)(uint8_t type);
- void (*CreateNewUnitKey)();
- void (*ReadStoredLinkKey)();
- void (*WriteStoredLinkKey)();
- void (*DeleteStoredLinkKey)(const RawAddress& bd_addr, bool delete_all_flag);
- void (*WriteLocalName)(BD_NAME name);
- void (*ReadLocalName)();
- void (*ReadConnectionAcceptTimeout)();
- void (*WriteConnectionAcceptTimeout)(uint16_t timeout);
- void (*ReadPageTimeout)();
- void (*WritePageTimeout)();
- void (*ReadScanEnable)();
- void (*WriteScanEnable)(uint8_t flag);
- void (*ReadPageScanActivity)();
- void (*WritePageScanActivity)(uint16_t interval, uint16_t window);
- void (*ReadInquiryScanActivity)();
- void (*WriteInquiryScanActivity)(uint16_t interval, uint16_t window);
- void (*ReadAuthenticationEnable)();
- void (*WriteAuthenticationEnable)(uint8_t flag);
- void (*ReadClassOfDevice)();
- void (*WriteClassOfDevice)(DEV_CLASS dev_class);
- void (*ReadVoiceSetting)();
- void (*WriteVoiceSetting)(uint16_t flags);
- void (*ReadAutomaticFlushTimeout)(uint16_t handle);
- void (*WriteAutomaticFlushTimeout)(uint16_t handle, uint16_t tout);
- void (*ReadNumBroadcastRetransmits)();
- void (*WriteNumBroadcastRetransmits)();
- void (*ReadHoldModeActivity)();
- void (*WriteHoldModeActivity)();
- void (*ReadTransmitPowerLevel)(uint16_t handle, uint8_t type);
- void (*ReadSynchronousFlowControlEnable)();
- void (*WriteSynchronousFlowControlEnable)();
- void (*SetControllerToHostFlowControl)();
- void (*HostBufferSize)();
- void (*HostNumCompletedPackets)();
- void (*ReadLinkSupervisionTimeout)(uint8_t local_controller_id,
- uint16_t handle, uint16_t timeout);
- void (*WriteLinkSupervisionTimeout)();
- void (*ReadNumberOfSupportedIac)();
- void (*ReadCurrentIacLap)();
- void (*WriteCurrentIacLap)(uint8_t num_cur_iac, LAP* const iac_lap);
- void (*SetAfhHostChannelClassification)();
- void (*ReadInquiryScanType)();
- void (*WriteInquiryScanType)(uint8_t type);
- void (*ReadInquiryMode)(); // 0x0C44,
- void (*WriteInquiryMode)(uint8_t mode);
- void (*ReadPageScanType)(); // 0x0C46,
- void (*WritePageScanType)(uint8_t type);
- void (*ReadAfhChannelAssessmentMode)();
- void (*WriteAfhChannelAssessmentMode)();
- void (*ReadExtendedInquiryResponse)();
- void (*WriteExtendedInquiryResponse)(void* buffer, uint8_t fec_req);
- void (*RefreshEncryptionKey)();
- void (*ReadSimplePairingMode)();
- void (*WriteSimplePairingMode)();
- void (*ReadLocalOobData)();
- void (*ReadInquiryResponseTransmitPowerLevel)();
- void (*WriteInquiryTransmitPowerLevel)();
- void (*EnhancedFlush)(uint16_t handle, uint8_t packet_type);
- void (*SendKeypressNotification)(const RawAddress& bd_addr, uint8_t notif);
-
- // STATUS_PARAMETER 0x14xxS
- void (*ReadFailedContactCounter)(uint16_t handle);
- void (*ResetFailedContactCounter)();
- void (*ReadLinkQuality)(uint16_t handle);
- // UNUSED 0x1404
- void (*ReadRssi)(uint16_t handle);
- void (*ReadAfhChannelMap)();
- void (*ReadClock)();
- void (*ReadEncryptionKeySize)();
-};
+extern void btsnd_hcic_disconnect(uint16_t handle, uint8_t reason);
-const Interface& GetInterface();
-} // namespace hci
-} // namespace legacy
-} // namespace bluetooth
+#define HCIC_PARAM_SIZE_DISCONNECT 3
+#define HCI_DISC_HANDLE_OFF 0
+#define HCI_DISC_REASON_OFF 2
/* Disconnect */
/* Add SCO Connection */
extern void btsnd_hcic_add_SCO_conn(uint16_t handle, uint16_t packet_types);
+#define HCIC_PARAM_SIZE_ADD_SCO_CONN 4
+
+#define HCI_ADD_SCO_HANDLE_OFF 0
+#define HCI_ADD_SCO_PACKET_TYPES_OFF 2
/* Add SCO Connection */
/* Create Connection Cancel */
extern void btsnd_hcic_create_conn_cancel(const RawAddress& dest);
+#define HCIC_PARAM_SIZE_CREATE_CONN_CANCEL 6
+
+#define HCIC_CR_CONN_CANCEL_BD_ADDR_OFF 0
/* Create Connection Cancel */
/* Accept Connection Request */
extern void btsnd_hcic_accept_conn(const RawAddress& bd_addr, uint8_t role);
+#define HCIC_PARAM_SIZE_ACCEPT_CONN 7
+
+#define HCI_ACC_CONN_BD_ADDR_OFF 0
+#define HCI_ACC_CONN_ROLE_OFF 6
/* Accept Connection Request */
/* Reject Connection Request */
extern void btsnd_hcic_reject_conn(const RawAddress& bd_addr, uint8_t reason);
+#define HCIC_PARAM_SIZE_REJECT_CONN 7
+
+#define HCI_REJ_CONN_BD_ADDR_OFF 0
+#define HCI_REJ_CONN_REASON_OFF 6
/* Reject Connection Request */
/* Link Key Request Reply */
extern void btsnd_hcic_link_key_req_reply(const RawAddress& bd_addr,
const LinkKey& link_key);
+#define HCIC_PARAM_SIZE_LINK_KEY_REQ_REPLY 22
+
+#define HCI_LINK_KEY_REPLY_BD_ADDR_OFF 0
+#define HCI_LINK_KEY_REPLY_LINK_KEY_OFF 6
/* Link Key Request Reply */
/* Link Key Request Neg Reply */
extern void btsnd_hcic_link_key_neg_reply(const RawAddress& bd_addr);
+#define HCIC_PARAM_SIZE_LINK_KEY_NEG_REPLY 6
+
+#define HCI_LINK_KEY_NEG_REP_BD_ADR_OFF 0
/* Link Key Request Neg Reply */
/* PIN Code Request Reply */
@@ -268,23 +147,43 @@ extern void btsnd_hcic_pin_code_req_reply(const RawAddress& bd_addr,
uint8_t pin_code_len,
PIN_CODE pin_code);
+#define HCIC_PARAM_SIZE_PIN_CODE_REQ_REPLY 23
+
+#define HCI_PIN_CODE_REPLY_BD_ADDR_OFF 0
+#define HCI_PIN_CODE_REPLY_PIN_LEN_OFF 6
+#define HCI_PIN_CODE_REPLY_PIN_CODE_OFF 7
/* PIN Code Request Reply */
/* Link Key Request Neg Reply */
extern void btsnd_hcic_pin_code_neg_reply(const RawAddress& bd_addr);
+#define HCIC_PARAM_SIZE_PIN_CODE_NEG_REPLY 6
+
+#define HCI_PIN_CODE_NEG_REP_BD_ADR_OFF 0
/* Link Key Request Neg Reply */
/* Change Connection Type */
extern void btsnd_hcic_change_conn_type(uint16_t handle, uint16_t packet_types);
+#define HCIC_PARAM_SIZE_CHANGE_CONN_TYPE 4
+
+#define HCI_CHNG_PKT_TYPE_HANDLE_OFF 0
+#define HCI_CHNG_PKT_TYPE_PKT_TYPE_OFF 2
/* Change Connection Type */
+#define HCIC_PARAM_SIZE_CMD_HANDLE 2
+
+#define HCI_CMD_HANDLE_HANDLE_OFF 0
+
extern void btsnd_hcic_auth_request(
uint16_t handle); /* Authentication Request */
/* Set Connection Encryption */
extern void btsnd_hcic_set_conn_encrypt(uint16_t handle, bool enable);
+#define HCIC_PARAM_SIZE_SET_CONN_ENCRYPT 3
+
+#define HCI_SET_ENCRYPT_HANDLE_OFF 0
+#define HCI_SET_ENCRYPT_ENABLE_OFF 2
/* Set Connection Encryption */
/* Remote Name Request */
@@ -292,10 +191,21 @@ extern void btsnd_hcic_rmt_name_req(const RawAddress& bd_addr,
uint8_t page_scan_rep_mode,
uint8_t page_scan_mode,
uint16_t clock_offset);
+
+#define HCIC_PARAM_SIZE_RMT_NAME_REQ 10
+
+#define HCI_RMT_NAME_BD_ADDR_OFF 0
+#define HCI_RMT_NAME_REP_MODE_OFF 6
+#define HCI_RMT_NAME_PAGE_SCAN_MODE_OFF 7
+#define HCI_RMT_NAME_CLK_OFF_OFF 8
/* Remote Name Request */
/* Remote Name Request Cancel */
extern void btsnd_hcic_rmt_name_req_cancel(const RawAddress& bd_addr);
+
+#define HCIC_PARAM_SIZE_RMT_NAME_REQ_CANCEL 6
+
+#define HCI_RMT_NAME_CANCEL_BD_ADDR_OFF 0
/* Remote Name Request Cancel */
extern void btsnd_hcic_rmt_features_req(
@@ -303,6 +213,11 @@ extern void btsnd_hcic_rmt_features_req(
/* Remote Extended Features */
extern void btsnd_hcic_rmt_ext_features(uint16_t handle, uint8_t page_num);
+
+#define HCIC_PARAM_SIZE_RMT_EXT_FEATURES 3
+
+#define HCI_RMT_EXT_FEATURES_HANDLE_OFF 0
+#define HCI_RMT_EXT_FEATURES_PAGE_NUM_OFF 2
/* Remote Extended Features */
extern void btsnd_hcic_rmt_ver_req(
@@ -316,17 +231,46 @@ extern void btsnd_hcic_setup_esco_conn(uint16_t handle,
uint16_t max_latency, uint16_t voice,
uint8_t retrans_effort,
uint16_t packet_types);
+#define HCIC_PARAM_SIZE_SETUP_ESCO 17
+
+#define HCI_SETUP_ESCO_HANDLE_OFF 0
+#define HCI_SETUP_ESCO_TX_BW_OFF 2
+#define HCI_SETUP_ESCO_RX_BW_OFF 6
+#define HCI_SETUP_ESCO_MAX_LAT_OFF 10
+#define HCI_SETUP_ESCO_VOICE_OFF 12
+#define HCI_SETUP_ESCO_RETRAN_EFF_OFF 14
+#define HCI_SETUP_ESCO_PKT_TYPES_OFF 15
+
extern void btsnd_hcic_accept_esco_conn(
const RawAddress& bd_addr, uint32_t transmit_bandwidth,
uint32_t receive_bandwidth, uint16_t max_latency, uint16_t content_fmt,
uint8_t retrans_effort, uint16_t packet_types);
+#define HCIC_PARAM_SIZE_ACCEPT_ESCO 21
+
+#define HCI_ACCEPT_ESCO_BDADDR_OFF 0
+#define HCI_ACCEPT_ESCO_TX_BW_OFF 6
+#define HCI_ACCEPT_ESCO_RX_BW_OFF 10
+#define HCI_ACCEPT_ESCO_MAX_LAT_OFF 14
+#define HCI_ACCEPT_ESCO_VOICE_OFF 16
+#define HCI_ACCEPT_ESCO_RETRAN_EFF_OFF 18
+#define HCI_ACCEPT_ESCO_PKT_TYPES_OFF 19
extern void btsnd_hcic_reject_esco_conn(const RawAddress& bd_addr,
uint8_t reason);
+#define HCIC_PARAM_SIZE_REJECT_ESCO 7
+
+#define HCI_REJECT_ESCO_BDADDR_OFF 0
+#define HCI_REJECT_ESCO_REASON_OFF 6
+
/* Hold Mode */
extern void btsnd_hcic_hold_mode(uint16_t handle, uint16_t max_hold_period,
uint16_t min_hold_period);
+#define HCIC_PARAM_SIZE_HOLD_MODE 6
+
+#define HCI_HOLD_MODE_HANDLE_OFF 0
+#define HCI_HOLD_MODE_MAX_PER_OFF 2
+#define HCI_HOLD_MODE_MIN_PER_OFF 4
/* Hold Mode */
/* Sniff Mode */
@@ -334,6 +278,14 @@ extern void btsnd_hcic_sniff_mode(uint16_t handle, uint16_t max_sniff_period,
uint16_t min_sniff_period,
uint16_t sniff_attempt,
uint16_t sniff_timeout);
+
+#define HCIC_PARAM_SIZE_SNIFF_MODE 10
+
+#define HCI_SNIFF_MODE_HANDLE_OFF 0
+#define HCI_SNIFF_MODE_MAX_PER_OFF 2
+#define HCI_SNIFF_MODE_MIN_PER_OFF 4
+#define HCI_SNIFF_MODE_ATTEMPT_OFF 6
+#define HCI_SNIFF_MODE_TIMEOUT_OFF 8
/* Sniff Mode */
extern void btsnd_hcic_exit_sniff_mode(uint16_t handle); /* Exit Sniff Mode */
@@ -341,6 +293,12 @@ extern void btsnd_hcic_exit_sniff_mode(uint16_t handle); /* Exit Sniff Mode */
/* Park Mode */
extern void btsnd_hcic_park_mode(uint16_t handle, uint16_t beacon_max_interval,
uint16_t beacon_min_interval);
+
+#define HCIC_PARAM_SIZE_PARK_MODE 6
+
+#define HCI_PARK_MODE_HANDLE_OFF 0
+#define HCI_PARK_MODE_MAX_PER_OFF 2
+#define HCI_PARK_MODE_MIN_PER_OFF 4
/* Park Mode */
extern void btsnd_hcic_exit_park_mode(uint16_t handle); /* Exit Park Mode */
@@ -350,86 +308,215 @@ extern void btsnd_hcic_qos_setup(uint16_t handle, uint8_t flags,
uint8_t service_type, uint32_t token_rate,
uint32_t peak, uint32_t latency,
uint32_t delay_var);
+
+#define HCIC_PARAM_SIZE_QOS_SETUP 20
+
+#define HCI_QOS_HANDLE_OFF 0
+#define HCI_QOS_FLAGS_OFF 2
+#define HCI_QOS_SERVICE_TYPE_OFF 3
+#define HCI_QOS_TOKEN_RATE_OFF 4
+#define HCI_QOS_PEAK_BANDWIDTH_OFF 8
+#define HCI_QOS_LATENCY_OFF 12
+#define HCI_QOS_DELAY_VAR_OFF 16
/* QoS Setup */
/* Switch Role Request */
+extern void btsnd_hcic_switch_role(const RawAddress& bd_addr, uint8_t role);
+
+#define HCIC_PARAM_SIZE_SWITCH_ROLE 7
+
+#define HCI_SWITCH_BD_ADDR_OFF 0
+#define HCI_SWITCH_ROLE_OFF 6
+/* Switch Role Request */
/* Write Policy Settings */
extern void btsnd_hcic_write_policy_set(uint16_t handle, uint16_t settings);
+
+#define HCIC_PARAM_SIZE_WRITE_POLICY_SET 4
+
+#define HCI_WRITE_POLICY_HANDLE_OFF 0
+#define HCI_WRITE_POLICY_SETTINGS_OFF 2
/* Write Policy Settings */
/* Write Default Policy Settings */
extern void btsnd_hcic_write_def_policy_set(uint16_t settings);
+
+#define HCIC_PARAM_SIZE_WRITE_DEF_POLICY_SET 2
+
+#define HCI_WRITE_DEF_POLICY_SETTINGS_OFF 0
/* Write Default Policy Settings */
/******************************************
* Lisbon Features
******************************************/
+#if (BTM_SSR_INCLUDED == TRUE)
/* Sniff Subrating */
extern void btsnd_hcic_sniff_sub_rate(uint16_t handle, uint16_t max_lat,
uint16_t min_remote_lat,
uint16_t min_local_lat);
+
+#define HCIC_PARAM_SIZE_SNIFF_SUB_RATE 8
+
+#define HCI_SNIFF_SUB_RATE_HANDLE_OFF 0
+#define HCI_SNIFF_SUB_RATE_MAX_LAT_OFF 2
+#define HCI_SNIFF_SUB_RATE_MIN_REM_LAT_OFF 4
+#define HCI_SNIFF_SUB_RATE_MIN_LOC_LAT_OFF 6
/* Sniff Subrating */
+#else /* BTM_SSR_INCLUDED == FALSE */
+
+#define btsnd_hcic_sniff_sub_rate(handle, max_lat, min_remote_lat, \
+ min_local_lat) \
+ false
+
+#endif /* BTM_SSR_INCLUDED */
+
/* Extended Inquiry Response */
extern void btsnd_hcic_write_ext_inquiry_response(void* buffer,
uint8_t fec_req);
+
+#define HCIC_PARAM_SIZE_EXT_INQ_RESP 241
+
+#define HCIC_EXT_INQ_RESP_FEC_OFF 0
+#define HCIC_EXT_INQ_RESP_RESPONSE 1
/* IO Capabilities Response */
extern void btsnd_hcic_io_cap_req_reply(const RawAddress& bd_addr,
uint8_t capability, uint8_t oob_present,
uint8_t auth_req);
+
+#define HCIC_PARAM_SIZE_IO_CAP_RESP 9
+
+#define HCI_IO_CAP_BD_ADDR_OFF 0
+#define HCI_IO_CAPABILITY_OFF 6
+#define HCI_IO_CAP_OOB_DATA_OFF 7
+#define HCI_IO_CAP_AUTH_REQ_OFF 8
+
/* IO Capabilities Req Neg Reply */
extern void btsnd_hcic_io_cap_req_neg_reply(const RawAddress& bd_addr,
uint8_t err_code);
+
+#define HCIC_PARAM_SIZE_IO_CAP_NEG_REPLY 7
+
+#define HCI_IO_CAP_NR_BD_ADDR_OFF 0
+#define HCI_IO_CAP_NR_ERR_CODE 6
+
/* Read Local OOB Data */
extern void btsnd_hcic_read_local_oob_data(void);
+#define HCIC_PARAM_SIZE_R_LOCAL_OOB 0
+
extern void btsnd_hcic_user_conf_reply(const RawAddress& bd_addr, bool is_yes);
+#define HCIC_PARAM_SIZE_UCONF_REPLY 6
+
+#define HCI_USER_CONF_BD_ADDR_OFF 0
+
extern void btsnd_hcic_user_passkey_reply(const RawAddress& bd_addr,
uint32_t value);
+#define HCIC_PARAM_SIZE_U_PKEY_REPLY 10
+
+#define HCI_USER_PASSKEY_BD_ADDR_OFF 0
+#define HCI_USER_PASSKEY_VALUE_OFF 6
+
extern void btsnd_hcic_user_passkey_neg_reply(const RawAddress& bd_addr);
+#define HCIC_PARAM_SIZE_U_PKEY_NEG_REPLY 6
+
+#define HCI_USER_PASSKEY_NEG_BD_ADDR_OFF 0
+
/* Remote OOB Data Request Reply */
extern void btsnd_hcic_rem_oob_reply(const RawAddress& bd_addr,
const Octet16& c, const Octet16& r);
+#define HCIC_PARAM_SIZE_REM_OOB_REPLY 38
+
+#define HCI_REM_OOB_DATA_BD_ADDR_OFF 0
+#define HCI_REM_OOB_DATA_C_OFF 6
+#define HCI_REM_OOB_DATA_R_OFF 22
+
/* Remote OOB Data Request Negative Reply */
extern void btsnd_hcic_rem_oob_neg_reply(const RawAddress& bd_addr);
+#define HCIC_PARAM_SIZE_REM_OOB_NEG_REPLY 6
+
+#define HCI_REM_OOB_DATA_NEG_BD_ADDR_OFF 0
+
/* Read Tx Power Level */
extern void btsnd_hcic_read_inq_tx_power(void);
+#define HCIC_PARAM_SIZE_R_TX_POWER 0
+
/* Read Default Erroneous Data Reporting */
extern void btsnd_hcic_read_default_erroneous_data_rpt(void);
+#define HCIC_PARAM_SIZE_R_ERR_DATA_RPT 0
+
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
extern void btsnd_hcic_enhanced_flush(uint16_t handle, uint8_t packet_type);
+#define HCIC_PARAM_SIZE_ENHANCED_FLUSH 3
+#endif
+
extern void btsnd_hcic_send_keypress_notif(const RawAddress& bd_addr,
uint8_t notif);
+
+#define HCIC_PARAM_SIZE_SEND_KEYPRESS_NOTIF 7
+
+#define HCI_SEND_KEYPRESS_NOTIF_BD_ADDR_OFF 0
+#define HCI_SEND_KEYPRESS_NOTIF_NOTIF_OFF 6
+
/**** end of Simple Pairing Commands ****/
+/* Store Current Settings */
+#define MAX_FILT_COND (sizeof(BD_ADDR) + 1)
+
extern void btsnd_hcic_set_event_filter(uint8_t filt_type,
uint8_t filt_cond_type,
uint8_t* filt_cond,
uint8_t filt_cond_len);
+
+#define HCIC_PARAM_SIZE_SET_EVT_FILTER 9
+
+#define HCI_FILT_COND_FILT_TYPE_OFF 0
+#define HCI_FILT_COND_COND_TYPE_OFF 1
+#define HCI_FILT_COND_FILT_OFF 2
/* Set Event Filter */
/* Delete Stored Key */
extern void btsnd_hcic_delete_stored_key(const RawAddress& bd_addr,
bool delete_all_flag);
+
+#define HCIC_PARAM_SIZE_DELETE_STORED_KEY 7
+
+#define HCI_DELETE_KEY_BD_ADDR_OFF 0
+#define HCI_DELETE_KEY_ALL_FLAG_OFF 6
/* Delete Stored Key */
/* Change Local Name */
extern void btsnd_hcic_change_name(BD_NAME name);
+#define HCIC_PARAM_SIZE_CHANGE_NAME BD_NAME_LEN
+
+#define HCI_CHANGE_NAME_NAME_OFF 0
+/* Change Local Name */
+
#define HCIC_PARAM_SIZE_READ_CMD 0
#define HCIC_PARAM_SIZE_WRITE_PARAM1 1
+#define HCIC_WRITE_PARAM1_PARAM_OFF 0
+
+#define HCIC_PARAM_SIZE_WRITE_PARAM2 2
+
+#define HCIC_WRITE_PARAM2_PARAM_OFF 0
+
#define HCIC_PARAM_SIZE_WRITE_PARAM3 3
+#define HCIC_WRITE_PARAM3_PARAM_OFF 0
+
+#define HCIC_PARAM_SIZE_SET_AFH_CHANNELS 10
+
extern void btsnd_hcic_write_pin_type(uint8_t type); /* Write PIN Type */
extern void btsnd_hcic_write_auto_accept(uint8_t flag); /* Write Auto Accept */
extern void btsnd_hcic_read_name(void); /* Read Local Name */
@@ -438,10 +525,23 @@ extern void btsnd_hcic_write_page_tout(
extern void btsnd_hcic_write_scan_enable(uint8_t flag); /* Write Scan Enable */
extern void btsnd_hcic_write_pagescan_cfg(
uint16_t interval, uint16_t window); /* Write Page Scan Activity */
+
+#define HCIC_PARAM_SIZE_ENH_SET_ESCO_CONN 59
+#define HCIC_PARAM_SIZE_ENH_ACC_ESCO_CONN 63
+
+#define HCIC_PARAM_SIZE_WRITE_PAGESCAN_CFG 4
+
+#define HCI_SCAN_CFG_INTERVAL_OFF 0
+#define HCI_SCAN_CFG_WINDOW_OFF 2
/* Write Page Scan Activity */
/* Write Inquiry Scan Activity */
extern void btsnd_hcic_write_inqscan_cfg(uint16_t interval, uint16_t window);
+
+#define HCIC_PARAM_SIZE_WRITE_INQSCAN_CFG 4
+
+#define HCI_SCAN_CFG_INTERVAL_OFF 0
+#define HCI_SCAN_CFG_WINDOW_OFF 2
/* Write Inquiry Scan Activity */
extern void btsnd_hcic_write_auth_enable(
@@ -451,24 +551,61 @@ extern void btsnd_hcic_write_dev_class(
extern void btsnd_hcic_write_voice_settings(
uint16_t flags); /* Write Voice Settings */
+/* Host Controller to Host flow control */
+#define HCI_HOST_FLOW_CTRL_OFF 0
+#define HCI_HOST_FLOW_CTRL_ACL_ON 1
+#define HCI_HOST_FLOW_CTRL_SCO_ON 2
+#define HCI_HOST_FLOW_CTRL_BOTH_ON 3
+
extern void btsnd_hcic_write_auto_flush_tout(
uint16_t handle, uint16_t timeout); /* Write Retransmit Timout */
+#define HCIC_PARAM_SIZE_WRITE_AUTOMATIC_FLUSH_TIMEOUT 4
+
+#define HCI_FLUSH_TOUT_HANDLE_OFF 0
+#define HCI_FLUSH_TOUT_TOUT_OFF 2
+
extern void btsnd_hcic_read_tx_power(uint16_t handle,
uint8_t type); /* Read Tx Power */
+#define HCIC_PARAM_SIZE_READ_TX_POWER 3
+
+#define HCI_READ_TX_POWER_HANDLE_OFF 0
+#define HCI_READ_TX_POWER_TYPE_OFF 2
+
/* Read transmit power level parameter */
+#define HCI_READ_CURRENT 0x00
+#define HCI_READ_MAXIMUM 0x01
+
extern void btsnd_hcic_host_num_xmitted_pkts(
uint8_t num_handles, uint16_t* handle,
uint16_t* num_pkts); /* Set Host Buffer Size */
+#define HCIC_PARAM_SIZE_NUM_PKTS_DONE_SIZE sizeof(btmsg_hcic_num_pkts_done_t)
+
+#define MAX_DATA_HANDLES 10
+
+#define HCI_PKTS_DONE_NUM_HANDLES_OFF 0
+#define HCI_PKTS_DONE_HANDLE_OFF 1
+#define HCI_PKTS_DONE_NUM_PKTS_OFF 3
+
/* Write Link Supervision Timeout */
extern void btsnd_hcic_write_link_super_tout(uint8_t local_controller_id,
uint16_t handle, uint16_t timeout);
+
+#define HCIC_PARAM_SIZE_WRITE_LINK_SUPER_TOUT 4
+
+#define HCI_LINK_SUPER_TOUT_HANDLE_OFF 0
+#define HCI_LINK_SUPER_TOUT_TOUT_OFF 2
/* Write Link Supervision Timeout */
extern void btsnd_hcic_write_cur_iac_lap(
uint8_t num_cur_iac, LAP* const iac_lap); /* Write Current IAC LAP */
+
+#define MAX_IAC_LAPS 0x40
+
+#define HCI_WRITE_IAC_LAP_NUM_OFF 0
+#define HCI_WRITE_IAC_LAP_LAP_OFF 1
/* Write Current IAC LAP */
extern void btsnd_hcic_get_link_quality(uint16_t handle); /* Get Link Quality */
@@ -507,6 +644,19 @@ extern void btsnd_hcic_enhanced_accept_synchronous_connection(
#define HCID_GET_EVENT(u16) \
(uint8_t)(((u16) >> HCI_DATA_EVENT_OFFSET) & HCI_DATA_EVENT_MASK)
+#define HCI_DATA_BCAST_MASK 3
+#define HCI_DATA_BCAST_OFFSET 10
+#define HCID_GET_BCAST(u16) \
+ (uint8_t)(((u16) >> HCI_DATA_BCAST_OFFSET) & HCI_DATA_BCAST_MASK)
+
+#define HCID_GET_ACL_LEN(p) \
+ (uint16_t)((*((uint8_t*)((p) + 1) + (p)->offset + 2) + \
+ (*((uint8_t*)((p) + 1) + (p)->offset + 3) << 8)))
+
+#define HCID_HEADER_SIZE 4
+
+#define HCID_GET_SCO_LEN(p) (*((uint8_t*)((p) + 1) + (p)->offset + 2))
+
extern void btsnd_hcic_vendor_spec_cmd(void* buffer, uint16_t opcode,
uint8_t len, uint8_t* p_data,
void* p_cmd_cplt_cback);
@@ -517,10 +667,54 @@ extern void btsnd_hcic_vendor_spec_cmd(void* buffer, uint16_t opcode,
* message size
******************************************************************************/
#define HCIC_BLE_RAND_DI_SIZE 8
+#define HCIC_BLE_IRK_SIZE 16
+
+#define HCIC_PARAM_SIZE_SET_USED_FEAT_CMD 8
+#define HCIC_PARAM_SIZE_WRITE_RANDOM_ADDR_CMD 6
+#define HCIC_PARAM_SIZE_BLE_WRITE_ADV_PARAMS 15
+#define HCIC_PARAM_SIZE_BLE_WRITE_SCAN_RSP 31
+#define HCIC_PARAM_SIZE_WRITE_ADV_ENABLE 1
+#define HCIC_PARAM_SIZE_BLE_WRITE_SCAN_PARAM 7
+#define HCIC_PARAM_SIZE_BLE_WRITE_SCAN_ENABLE 2
+#define HCIC_PARAM_SIZE_BLE_CREATE_LL_CONN 25
+#define HCIC_PARAM_SIZE_BLE_CREATE_CONN_CANCEL 0
+#define HCIC_PARAM_SIZE_CLEAR_WHITE_LIST 0
+#define HCIC_PARAM_SIZE_ADD_WHITE_LIST 7
+#define HCIC_PARAM_SIZE_REMOVE_WHITE_LIST 7
+#define HCIC_PARAM_SIZE_BLE_UPD_LL_CONN_PARAMS 14
+#define HCIC_PARAM_SIZE_SET_HOST_CHNL_CLASS 5
+#define HCIC_PARAM_SIZE_READ_CHNL_MAP 2
+#define HCIC_PARAM_SIZE_BLE_READ_REMOTE_FEAT 2
+#define HCIC_PARAM_SIZE_BLE_ENCRYPT 32
+#define HCIC_PARAM_SIZE_WRITE_LE_HOST_SUPPORTED 2
+#define HCIC_BLE_RAND_DI_SIZE 8
+#define HCIC_BLE_ENCRYT_KEY_SIZE 16
+#define HCIC_PARAM_SIZE_BLE_START_ENC \
+ (4 + HCIC_BLE_RAND_DI_SIZE + HCIC_BLE_ENCRYT_KEY_SIZE)
+#define HCIC_PARAM_SIZE_LTK_REQ_REPLY (2 + HCIC_BLE_ENCRYT_KEY_SIZE)
+#define HCIC_PARAM_SIZE_LTK_REQ_NEG_REPLY 2
#define HCIC_BLE_CHNL_MAP_SIZE 5
+#define HCIC_PARAM_SIZE_BLE_WRITE_ADV_DATA 31
+
+#define HCIC_PARAM_SIZE_BLE_ADD_DEV_RESOLVING_LIST (7 + HCIC_BLE_IRK_SIZE * 2)
+#define HCIC_PARAM_SIZE_BLE_RM_DEV_RESOLVING_LIST 7
+#define HCIC_PARAM_SIZE_BLE_SET_PRIVACY_MODE 8
+#define HCIC_PARAM_SIZE_BLE_CLEAR_RESOLVING_LIST 0
+#define HCIC_PARAM_SIZE_BLE_READ_RESOLVING_LIST_SIZE 0
+#define HCIC_PARAM_SIZE_BLE_READ_RESOLVABLE_ADDR_PEER 7
+#define HCIC_PARAM_SIZE_BLE_READ_RESOLVABLE_ADDR_LOCAL 7
+#define HCIC_PARAM_SIZE_BLE_SET_ADDR_RESOLUTION_ENABLE 1
+#define HCIC_PARAM_SIZE_BLE_SET_RAND_PRIV_ADDR_TIMOUT 2
+
#define HCIC_PARAM_SIZE_BLE_READ_PHY 2
+#define HCIC_PARAM_SIZE_BLE_SET_DEFAULT_PHY 3
#define HCIC_PARAM_SIZE_BLE_SET_PHY 7
+#define HCIC_PARAM_SIZE_BLE_ENH_RX_TEST 3
+#define HCIC_PARAM_SIZE_BLE_ENH_TX_TEST 4
+
+#define HCIC_PARAM_SIZE_BLE_SET_DATA_LENGTH 6
+#define HCIC_PARAM_SIZE_BLE_WRITE_EXTENDED_SCAN_PARAM 11
/* ULP HCI command */
extern void btsnd_hcic_ble_set_evt_mask(BT_EVENT_MASK event_mask);
@@ -562,16 +756,16 @@ extern void btsnd_hcic_ble_create_ll_conn(
extern void btsnd_hcic_ble_create_conn_cancel(void);
-extern void btsnd_hcic_ble_read_acceptlist_size(void);
+extern void btsnd_hcic_ble_read_white_list_size(void);
-extern void btsnd_hcic_ble_clear_acceptlist(
+extern void btsnd_hcic_ble_clear_white_list(
base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-extern void btsnd_hcic_ble_add_acceptlist(
+extern void btsnd_hcic_ble_add_white_list(
uint8_t addr_type, const RawAddress& bda,
base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-extern void btsnd_hcic_ble_remove_from_acceptlist(
+extern void btsnd_hcic_ble_remove_from_white_list(
uint8_t addr_type, const RawAddress& bda,
base::OnceCallback<void(uint8_t*, uint16_t)> cb);
@@ -615,14 +809,20 @@ extern void btsnd_hcic_ble_transmitter_test(uint8_t tx_freq,
uint8_t payload);
extern void btsnd_hcic_ble_test_end(void);
+#if (BLE_LLT_INCLUDED == TRUE)
+
+#define HCIC_PARAM_SIZE_BLE_RC_PARAM_REQ_REPLY 14
extern void btsnd_hcic_ble_rc_param_req_reply(
uint16_t handle, uint16_t conn_int_min, uint16_t conn_int_max,
uint16_t conn_latency, uint16_t conn_timeout, uint16_t min_ce_len,
uint16_t max_ce_len);
+#define HCIC_PARAM_SIZE_BLE_RC_PARAM_REQ_NEG_REPLY 3
extern void btsnd_hcic_ble_rc_param_req_neg_reply(uint16_t handle,
uint8_t reason);
+#endif /* BLE_LLT_INCLUDED */
+
extern void btsnd_hcic_ble_set_data_length(uint16_t conn_handle,
uint16_t tx_octets,
uint16_t tx_time);
@@ -690,136 +890,6 @@ extern void btsnd_hcic_read_authenticated_payload_tout(uint16_t handle);
extern void btsnd_hcic_write_authenticated_payload_tout(uint16_t handle,
uint16_t timeout);
-extern void btsnd_hcic_read_iso_tx_sync(
- uint16_t iso_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-struct EXT_CIS_CFG {
- uint8_t cis_id;
- uint16_t max_sdu_size_mtos;
- uint16_t max_sdu_size_stom;
- uint8_t phy_mtos;
- uint8_t phy_stom;
- uint8_t rtn_mtos;
- uint8_t rtn_stom;
-};
-
-extern void btsnd_hcic_set_cig_params(
- uint8_t cig_id, uint32_t sdu_itv_mtos, uint32_t sdu_itv_stom, uint8_t sca,
- uint8_t packing, uint8_t framing, uint16_t max_trans_lat_stom,
- uint16_t max_trans_lat_mtos, uint8_t cis_cnt, const EXT_CIS_CFG* cis_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-struct EXT_CIS_TEST_CFG {
- uint8_t cis_id;
- uint8_t nse;
- uint16_t max_sdu_size_mtos;
- uint16_t max_sdu_size_stom;
- uint8_t max_pdu_mtos;
- uint8_t max_pdu_stom;
- uint8_t phy_mtos;
- uint8_t phy_stom;
- uint8_t bn_mtos;
- uint8_t bn_stom;
-};
-
-struct EXT_CIS_CREATE_CFG {
- uint16_t cis_conn_handle;
- uint16_t acl_conn_handle;
-};
-
-extern void btsnd_hcic_create_cis(
- uint8_t num_cis, const EXT_CIS_CREATE_CFG* cis_create_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_remove_cig(
- uint8_t cig_id, base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_accept_cis_req(uint16_t conn_handle);
-
-extern void btsnd_hcic_rej_cis_req(
- uint16_t conn_handle, uint8_t reason,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_req_peer_sca(uint16_t conn_handle);
-
-extern void btsnd_hcic_create_big(uint8_t big_handle, uint8_t adv_handle,
- uint8_t num_bis, uint32_t sdu_itv,
- uint16_t max_sdu_size, uint16_t max_trans_lat,
- uint8_t rtn, uint8_t phy, uint8_t packing,
- uint8_t framing, uint8_t enc,
- std::array<uint8_t, 16> bcst_code);
-
-extern void btsnd_hcic_term_big(uint8_t big_handle, uint8_t reason);
-
-extern void btsnd_hcic_big_create_sync(uint8_t big_handle, uint16_t sync_handle,
- uint8_t enc,
- std::array<uint8_t, 16> bcst_code,
- uint8_t mse, uint16_t big_sync_timeout,
- std::vector<uint8_t> bis);
-
-extern void btsnd_hcic_big_term_sync(
- uint8_t big_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_setup_iso_data_path(
- uint16_t iso_handle, uint8_t data_path_dir, uint8_t data_path_id,
- uint8_t codec_id_format, uint16_t codec_id_company,
- uint16_t codec_id_vendor, uint32_t controller_delay,
- std::vector<uint8_t> codec_conf,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_remove_iso_data_path(
- uint16_t iso_handle, uint8_t data_path_dir,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_read_iso_link_quality(
- uint16_t iso_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_ble_periodic_advertising_create_sync(
- uint8_t options, uint8_t adv_sid, uint8_t adv_addr_type,
- const RawAddress& adv_addr, uint16_t skip_num, uint16_t sync_timeout,
- uint8_t sync_cte_type);
-
-extern void btsnd_hcic_ble_periodic_advertising_create_sync_cancel(
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_ble_periodic_advertising_terminate_sync(
- uint16_t sync_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hci_ble_add_device_to_periodic_advertiser_list(
- uint8_t adv_addr_type, const RawAddress& adv_addr, uint8_t adv_sid,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hci_ble_remove_device_from_periodic_advertiser_list(
- uint8_t adv_addr_type, const RawAddress& adv_addr, uint8_t adv_sid,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hci_ble_clear_periodic_advertiser_list(
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hci_ble_read_periodic_advertiser_list_size(
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_ble_set_periodic_advertising_receive_enable(
- uint16_t sync_handle, bool enable,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_ble_periodic_advertising_sync_transfer(
- uint16_t conn_handle, uint16_t service_data, uint16_t sync_handle,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_ble_periodic_advertising_set_info_transfer(
- uint16_t conn_handle, uint16_t service_data, uint8_t adv_handle,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void btsnd_hcic_ble_set_periodic_advertising_sync_transfer_params(
- uint16_t conn_handle, uint8_t mode, uint16_t skip, uint16_t sync_timeout,
- uint8_t cte_type, base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
-extern void
-btsnd_hcic_ble_set_default_periodic_advertising_sync_transfer_params(
- uint16_t conn_handle, uint8_t mode, uint16_t skip, uint16_t sync_timeout,
- uint8_t cte_type, base::OnceCallback<void(uint8_t*, uint16_t)> cb);
-
#define HCIC_PARAM_SIZE_WRITE_AUTHENT_PAYLOAD_TOUT 4
#define HCI__WRITE_AUTHENT_PAYLOAD_TOUT_HANDLE_OFF 0
diff --git a/stack/include/hidd_api.h b/stack/include/hidd_api.h
index 90a8bc1a0..145c0f1ee 100644
--- a/stack/include/hidd_api.h
+++ b/stack/include/hidd_api.h
@@ -92,6 +92,17 @@ extern tHID_STATUS HID_DevDeregister(void);
/*******************************************************************************
*
+ * Function HID_DevSetSecurityLevel
+ *
+ * Description Sets security level for HID device connections
+ *
+ * Returns tHID_STATUS
+ *
+ ******************************************************************************/
+extern tHID_STATUS HID_DevSetSecurityLevel(uint8_t sec_lvl);
+
+/*******************************************************************************
+ *
* Function HID_DevAddRecord
*
* Description Creates SDP record for HID device
diff --git a/stack/include/hiddefs.h b/stack/include/hiddefs.h
index 6657bda39..df01e7d5d 100644
--- a/stack/include/hiddefs.h
+++ b/stack/include/hiddefs.h
@@ -25,14 +25,12 @@
#ifndef HIDDEFS_H
#define HIDDEFS_H
-#include <string>
-
#include "sdp_api.h"
/*
* tHID_STATUS: HID result codes, returned by HID and device and host functions.
*/
-typedef enum : uint8_t {
- HID_SUCCESS = 0,
+enum {
+ HID_SUCCESS,
HID_ERR_NOT_REGISTERED,
HID_ERR_ALREADY_REGISTERED,
HID_ERR_NO_RESOURCES,
@@ -53,38 +51,9 @@ typedef enum : uint8_t {
HID_ERR_GATT,
HID_ERR_INVALID = 0xFF
-} tHID_STATUS;
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string hid_status_text(const tHID_STATUS& status) {
- switch (status) {
- CASE_RETURN_TEXT(HID_SUCCESS);
- CASE_RETURN_TEXT(HID_ERR_NOT_REGISTERED);
- CASE_RETURN_TEXT(HID_ERR_ALREADY_REGISTERED);
- CASE_RETURN_TEXT(HID_ERR_NO_RESOURCES);
- CASE_RETURN_TEXT(HID_ERR_NO_CONNECTION);
- CASE_RETURN_TEXT(HID_ERR_INVALID_PARAM);
- CASE_RETURN_TEXT(HID_ERR_UNSUPPORTED);
- CASE_RETURN_TEXT(HID_ERR_UNKNOWN_COMMAND);
- CASE_RETURN_TEXT(HID_ERR_CONGESTED);
- CASE_RETURN_TEXT(HID_ERR_CONN_IN_PROCESS);
- CASE_RETURN_TEXT(HID_ERR_ALREADY_CONN);
- CASE_RETURN_TEXT(HID_ERR_DISCONNECTING);
- CASE_RETURN_TEXT(HID_ERR_SET_CONNABLE_FAIL);
- CASE_RETURN_TEXT(HID_ERR_HOST_UNKNOWN);
- CASE_RETURN_TEXT(HID_ERR_L2CAP_FAILED);
- CASE_RETURN_TEXT(HID_ERR_AUTH_FAILED);
- CASE_RETURN_TEXT(HID_ERR_SDP_BUSY);
- CASE_RETURN_TEXT(HID_ERR_GATT);
- CASE_RETURN_TEXT(HID_ERR_INVALID);
- default:
- return std::string("UNKNOWN[%hhu]", status);
- }
-}
-#undef CASE_RETURN_TEXT
+};
+
+typedef uint8_t tHID_STATUS;
#define HID_L2CAP_CONN_FAIL \
(0x0100) /* Connection Attempt was made but failed */
diff --git a/stack/include/hidh_api.h b/stack/include/hidh_api.h
index 71a053382..37b520588 100644
--- a/stack/include/hidh_api.h
+++ b/stack/include/hidh_api.h
@@ -25,6 +25,11 @@
* Constants
****************************************************************************/
+enum {
+ HID_SDP_NO_SERV_UUID = (SDP_ILLEGAL_PARAMETER + 1),
+ HID_SDP_MANDATORY_MISSING
+};
+
/* Attributes mask values to be used in HID_HostAddDev API */
#define HID_VIRTUAL_CABLE 0x0001
#define HID_NORMALLY_CONNECTABLE 0x0002
@@ -191,6 +196,28 @@ extern tHID_STATUS HID_HostCloseDev(uint8_t dev_handle);
extern void HID_HostInit(void);
/*******************************************************************************
+ * Function HID_HostSetSecurityLevel
+ *
+ * Description This function sets the security level for the devices which
+ * are marked by application as requiring security
+ *
+ * Returns tHID_STATUS
+ ******************************************************************************/
+extern tHID_STATUS HID_HostSetSecurityLevel(const char serv_name[],
+ uint8_t sec_lvl);
+
+/*******************************************************************************
+ *
+ * Function hid_known_hid_device
+ *
+ * Description This function checks if this device is of type HID Device
+ *
+ * Returns true if device exists else false
+ *
+ ******************************************************************************/
+bool hid_known_hid_device(const RawAddress& bd_addr);
+
+/*******************************************************************************
*
* Function HID_HostSetTraceLevel
*
diff --git a/stack/include/inq_hci_link_interface.h b/stack/include/inq_hci_link_interface.h
deleted file mode 100644
index 2d7fd08a9..000000000
--- a/stack/include/inq_hci_link_interface.h
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include <cstdint>
-
-#include "types/raw_address.h"
-
-extern void btm_process_remote_name(const RawAddress* bda, BD_NAME name,
- uint16_t evt_len, uint8_t hci_status);
-
-extern void btm_process_inq_results(uint8_t* p, uint8_t hci_evt_len,
- uint8_t inq_res_mode);
-
-extern void btm_process_inq_complete(uint8_t status, uint8_t mode);
-extern void btm_process_cancel_complete(uint8_t status, uint8_t mode);
-
-extern void btm_acl_process_sca_cmpl_pkt(uint8_t len, uint8_t* data);
-extern tINQ_DB_ENT* btm_inq_db_new(const RawAddress& p_bda);
diff --git a/stack/include/l2c_api.h b/stack/include/l2c_api.h
index 9de3b9bb9..4b2d8f434 100644
--- a/stack/include/l2c_api.h
+++ b/stack/include/l2c_api.h
@@ -24,14 +24,11 @@
#ifndef L2C_API_H
#define L2C_API_H
-#include <vector>
#include <stdbool.h>
#include "bt_target.h"
#include "hcidefs.h"
#include "l2cdefs.h"
-#include "types/bt_transport.h"
-#include "types/hci_role.h"
/*****************************************************************************
* Constants
@@ -48,25 +45,32 @@
#define L2CAP_FCS_LENGTH 2
+/* ping result codes */
+#define L2CAP_PING_RESULT_OK 0 /* Ping reply received OK */
+#define L2CAP_PING_RESULT_NO_LINK 1 /* Link could not be setup */
+#define L2CAP_PING_RESULT_NO_RESP 2 /* Remote L2CAP did not reply */
+
/* result code for L2CA_DataWrite() */
#define L2CAP_DW_FAILED false
#define L2CAP_DW_SUCCESS true
#define L2CAP_DW_CONGESTED 2
/* Values for priority parameter to L2CA_SetAclPriority */
-typedef enum : uint8_t {
- L2CAP_PRIORITY_NORMAL = 0,
- L2CAP_PRIORITY_HIGH = 1,
-} tL2CAP_PRIORITY;
+#define L2CAP_PRIORITY_NORMAL 0
+#define L2CAP_PRIORITY_HIGH 1
/* Values for priority parameter to L2CA_SetTxPriority */
#define L2CAP_CHNL_PRIORITY_HIGH 0
+#define L2CAP_CHNL_PRIORITY_MEDIUM 1
#define L2CAP_CHNL_PRIORITY_LOW 2
typedef uint8_t tL2CAP_CHNL_PRIORITY;
/* Values for Tx/Rx data rate parameter to L2CA_SetChnlDataRate */
+#define L2CAP_CHNL_DATA_RATE_HIGH 3
+#define L2CAP_CHNL_DATA_RATE_MEDIUM 2
#define L2CAP_CHNL_DATA_RATE_LOW 1
+#define L2CAP_CHNL_DATA_RATE_NO_TRAFFIC 0
typedef uint8_t tL2CAP_CHNL_DATA_RATE;
@@ -81,13 +85,21 @@ typedef uint8_t tL2CAP_CHNL_DATA_RATE;
#define L2CAP_FLUSH_CHANS_ALL 0xffff
#define L2CAP_FLUSH_CHANS_GET 0x0000
+/* set this bit to allow switch at create conn */
+#define L2CAP_ROLE_ALLOW_SWITCH 0x80
+/* set this bit to disallow switch at create conn */
+#define L2CAP_ROLE_DISALLOW_SWITCH 0x40
+#define L2CAP_ROLE_CHECK_SWITCH 0xC0
+
/* Values for 'allowed_modes' field passed in structure tL2CAP_ERTM_INFO
*/
#define L2CAP_FCR_CHAN_OPT_BASIC (1 << L2CAP_FCR_BASIC_MODE)
#define L2CAP_FCR_CHAN_OPT_ERTM (1 << L2CAP_FCR_ERTM_MODE)
+#define L2CAP_FCR_CHAN_OPT_STREAM (1 << L2CAP_FCR_STREAM_MODE)
-#define L2CAP_FCR_CHAN_OPT_ALL_MASK \
- (L2CAP_FCR_CHAN_OPT_BASIC | L2CAP_FCR_CHAN_OPT_ERTM)
+#define L2CAP_FCR_CHAN_OPT_ALL_MASK \
+ (L2CAP_FCR_CHAN_OPT_BASIC | L2CAP_FCR_CHAN_OPT_ERTM | \
+ L2CAP_FCR_CHAN_OPT_STREAM)
/* Validity check for PSM. PSM values must be odd. Also, all PSM values must
* be assigned such that the least significant bit of the most sigificant
@@ -104,6 +116,7 @@ typedef uint8_t tL2CAP_CHNL_DATA_RATE;
typedef struct {
#define L2CAP_FCR_BASIC_MODE 0x00
#define L2CAP_FCR_ERTM_MODE 0x03
+#define L2CAP_FCR_STREAM_MODE 0x04
#define L2CAP_FCR_LE_COC_MODE 0x05
uint8_t mode;
@@ -115,30 +128,6 @@ typedef struct {
uint16_t mps;
} tL2CAP_FCR_OPTS;
-/* default options for ERTM mode */
-constexpr tL2CAP_FCR_OPTS kDefaultErtmOptions = {
- L2CAP_FCR_ERTM_MODE,
- 10, /* Tx window size */
- 20, /* Maximum transmissions before disconnecting */
- 2000, /* Retransmission timeout (2 secs) */
- 12000, /* Monitor timeout (12 secs) */
- 1010 /* MPS segment size */
-};
-
-typedef struct {
- uint8_t qos_flags; /* TBD */
- uint8_t service_type; /* see below */
- uint32_t token_rate; /* bytes/second */
- uint32_t token_bucket_size; /* bytes */
- uint32_t peak_bandwidth; /* bytes/second */
- uint32_t latency; /* microseconds */
- uint32_t delay_variation; /* microseconds */
-} FLOW_SPEC;
-
-/* Values for service_type */
-#define SVC_TYPE_BEST_EFFORT 1
-#define SVC_TYPE_GUARANTEED 2
-
/* Define a structure to hold the configuration parameters. Since the
* parameters are optional, for each parameter there is a boolean to
* use to signify its presence or absence.
@@ -160,32 +149,24 @@ typedef struct {
uint16_t flags; /* bit 0: 0-no continuation, 1-continuation */
} tL2CAP_CFG_INFO;
-/* LE credit based L2CAP connection parameters */
-constexpr uint16_t L2CAP_LE_MIN_MTU = 23; // Minimum SDU size
-constexpr uint16_t L2CAP_LE_MIN_MPS = 23;
-constexpr uint16_t L2CAP_LE_MAX_MPS = 65533;
-constexpr uint16_t L2CAP_LE_CREDIT_MAX = 65535;
-
-// This is initial amout of credits we send, and amount to which we increase
-// credits once they fall below threshold
-constexpr uint16_t L2CAP_LE_CREDIT_DEFAULT = 0xffff;
-
-// If credit count on remote fall below this value, we send back credits to
-// reach default value.
-constexpr uint16_t L2CAP_LE_CREDIT_THRESHOLD = 0x0040;
-
-static_assert(L2CAP_LE_CREDIT_THRESHOLD < L2CAP_LE_CREDIT_DEFAULT,
- "Threshold must be smaller than default credits");
-
/* Define a structure to hold the configuration parameter for LE L2CAP
* connection oriented channels.
*/
-struct tL2CAP_LE_CFG_INFO {
- uint16_t result; /* Only used in confirm messages */
- uint16_t mtu = 100;
- uint16_t mps = 100;
- uint16_t credits = L2CAP_LE_CREDIT_DEFAULT;
-};
+typedef struct {
+ uint16_t mtu;
+ uint16_t mps;
+ uint16_t credits;
+} tL2CAP_LE_CFG_INFO;
+
+/* L2CAP channel configured field bitmap */
+#define L2CAP_CH_CFG_MASK_MTU 0x0001
+#define L2CAP_CH_CFG_MASK_QOS 0x0002
+#define L2CAP_CH_CFG_MASK_FLUSH_TO 0x0004
+#define L2CAP_CH_CFG_MASK_FCR 0x0008
+#define L2CAP_CH_CFG_MASK_FCS 0x0010
+#define L2CAP_CH_CFG_MASK_EXT_FLOW_SPEC 0x0020
+
+typedef uint16_t tL2CAP_CH_CFG_BITS;
/*********************************
* Callback Functions Prototypes
@@ -202,26 +183,26 @@ typedef void(tL2CA_CONNECT_IND_CB)(const RawAddress&, uint16_t, uint16_t,
/* Connection confirmation callback prototype. Parameters are
* Local CID
- * Result - 0 = connected
- * If there is an error, tL2CA_ERROR_CB is invoked
+ * Result - 0 = connected, non-zero means failure reason
*/
typedef void(tL2CA_CONNECT_CFM_CB)(uint16_t, uint16_t);
+/* Connection pending callback prototype. Parameters are
+ * Local CID
+ */
+typedef void(tL2CA_CONNECT_PND_CB)(uint16_t);
+
/* Configuration indication callback prototype. Parameters are
* Local CID assigned to the connection
* Pointer to configuration info
*/
typedef void(tL2CA_CONFIG_IND_CB)(uint16_t, tL2CAP_CFG_INFO*);
-constexpr uint16_t L2CAP_INITIATOR_LOCAL = 1;
-constexpr uint16_t L2CAP_INITIATOR_REMOTE = 0;
/* Configuration confirm callback prototype. Parameters are
* Local CID assigned to the connection
- * Initiator (1 for local, 0 for remote)
- * Initial config from remote
- * If there is an error, tL2CA_ERROR_CB is invoked
+ * Pointer to configuration info
*/
-typedef void(tL2CA_CONFIG_CFM_CB)(uint16_t, uint16_t, tL2CAP_CFG_INFO*);
+typedef void(tL2CA_CONFIG_CFM_CB)(uint16_t, tL2CAP_CFG_INFO*);
/* Disconnect indication callback prototype. Parameters are
* Local CID
@@ -233,8 +214,30 @@ typedef void(tL2CA_DISCONNECT_IND_CB)(uint16_t, bool);
* Local CID
* Result
*/
+typedef void(tL2CA_DISCONNECT_CFM_CB)(uint16_t, uint16_t);
+
+/* QOS Violation indication callback prototype. Parameters are
+ * BD Address of violating device
+ */
+typedef void(tL2CA_QOS_VIOLATION_IND_CB)(const RawAddress&);
+
+/* Data received indication callback prototype. Parameters are
+ * Local CID
+ * Address of buffer
+ */
typedef void(tL2CA_DATA_IND_CB)(uint16_t, BT_HDR*);
+/* Echo response callback prototype. Note that this is not included in the
+ * registration information, but is passed to L2CAP as part of the API to
+ * actually send an echo request. Parameters are
+ * Result
+ */
+typedef void(tL2CA_ECHO_RSP_CB)(uint16_t);
+
+/* Callback function prototype to pass broadcom specific echo response */
+/* to the upper layer */
+typedef void(tL2CA_ECHO_DATA_CB)(const RawAddress&, uint16_t, uint8_t*);
+
/* Congestion status callback protype. This callback is optional. If
* an application tries to send data when the transmit queue is full,
* the data will anyways be dropped. The parameter is:
@@ -243,6 +246,15 @@ typedef void(tL2CA_DATA_IND_CB)(uint16_t, BT_HDR*);
*/
typedef void(tL2CA_CONGESTION_STATUS_CB)(uint16_t, bool);
+/* Callback prototype for number of packets completed events.
+ * This callback notifies the application when Number of Completed Packets
+ * event has been received.
+ * This callback is originally designed for 3DG devices.
+ * The parameter is:
+ * peer BD_ADDR
+ */
+typedef void(tL2CA_NOCP_CB)(const RawAddress&);
+
/* Transmit complete callback protype. This callback is optional. If
* set, L2CAP will call it when packets are sent or flushed. If the
* count is 0xFFFF, it means all packets are sent for that CID (eRTM
@@ -252,47 +264,14 @@ typedef void(tL2CA_CONGESTION_STATUS_CB)(uint16_t, bool);
*/
typedef void(tL2CA_TX_COMPLETE_CB)(uint16_t, uint16_t);
-/*
- * Notify the user when the remote send error result on ConnectRsp or ConfigRsp
- * The parameters are:
- * Local CID
- * Error type (L2CAP_CONN_OTHER_ERROR for ConnectRsp,
- * L2CAP_CFG_FAILED_NO_REASON for ConfigRsp)
- */
-typedef void(tL2CA_ERROR_CB)(uint16_t, uint16_t);
-
-/* Create credit based connection request callback prototype. Parameters are
- * BD Address of remote
- * Vector of allocated local cids to accept
- * PSM
- * Peer MTU
- * Identifier that the remote sent
- */
-typedef void(tL2CA_CREDIT_BASED_CONNECT_IND_CB)(const RawAddress& bdaddr,
- std::vector<uint16_t>& lcids,
- uint16_t psm, uint16_t peer_mtu,
- uint8_t identifier);
-
-/* Credit based connection confirmation callback prototype. Parameters are
- * BD Address of remote
- * Connected Local CIDs
- * Peer MTU
- * Result - 0 = connected, non-zero means CID is not connected
+/* Callback for receiving credits from the remote device.
+ * |credit_received| parameter represents number of credits received in "LE Flow
+ * Control Credit" packet from the remote. |credit_count| parameter represents
+ * the total available credits, including |credit_received|.
*/
-typedef void(tL2CA_CREDIT_BASED_CONNECT_CFM_CB)(const RawAddress& bdaddr,
- uint16_t lcid,
- uint16_t peer_mtu,
- uint16_t result);
-
-/* Credit based reconfiguration confirm callback prototype. Parameters are
- * BD Address of remote
- * Local CID assigned to the connection
- * Flag indicating if this is local or peer configuration
- * Pointer to configuration info
- */
-typedef void(tL2CA_CREDIT_BASED_RECONFIG_COMPLETED_CB)(
- const RawAddress& bdaddr, uint16_t lcid, bool is_local_cfg,
- tL2CAP_LE_CFG_INFO* p_cfg);
+typedef void(tL2CA_CREDITS_RECEIVED_CB)(uint16_t local_cid,
+ uint16_t credits_received,
+ uint16_t credit_count);
/* Define the structure that applications use to register with
* L2CAP. This structure includes callback functions. All functions
@@ -302,17 +281,16 @@ typedef void(tL2CA_CREDIT_BASED_RECONFIG_COMPLETED_CB)(
typedef struct {
tL2CA_CONNECT_IND_CB* pL2CA_ConnectInd_Cb;
tL2CA_CONNECT_CFM_CB* pL2CA_ConnectCfm_Cb;
+ tL2CA_CONNECT_PND_CB* pL2CA_ConnectPnd_Cb;
tL2CA_CONFIG_IND_CB* pL2CA_ConfigInd_Cb;
tL2CA_CONFIG_CFM_CB* pL2CA_ConfigCfm_Cb;
tL2CA_DISCONNECT_IND_CB* pL2CA_DisconnectInd_Cb;
+ tL2CA_DISCONNECT_CFM_CB* pL2CA_DisconnectCfm_Cb;
+ tL2CA_QOS_VIOLATION_IND_CB* pL2CA_QoSViolationInd_Cb;
tL2CA_DATA_IND_CB* pL2CA_DataInd_Cb;
tL2CA_CONGESTION_STATUS_CB* pL2CA_CongestionStatus_Cb;
tL2CA_TX_COMPLETE_CB* pL2CA_TxComplete_Cb;
- tL2CA_ERROR_CB* pL2CA_Error_Cb;
- tL2CA_CREDIT_BASED_CONNECT_IND_CB* pL2CA_CreditBasedConnectInd_Cb;
- tL2CA_CREDIT_BASED_CONNECT_CFM_CB* pL2CA_CreditBasedConnectCfm_Cb;
- tL2CA_CREDIT_BASED_RECONFIG_COMPLETED_CB*
- pL2CA_CreditBasedReconfigCompleted_Cb;
+ tL2CA_CREDITS_RECEIVED_CB* pL2CA_CreditsReceived_Cb;
} tL2CAP_APPL_INFO;
/* Define the structure that applications use to create or accept
@@ -320,24 +298,18 @@ typedef struct {
*/
typedef struct {
uint8_t preferred_mode;
-} tL2CAP_ERTM_INFO;
+ uint8_t allowed_modes;
+ uint16_t user_rx_buf_size;
+ uint16_t user_tx_buf_size;
+ uint16_t fcr_rx_buf_size;
+ uint16_t fcr_tx_buf_size;
-/**
- * Stack management declarations
- */
-void l2c_init();
-void l2c_free();
+} tL2CAP_ERTM_INFO;
/*****************************************************************************
* External Function Declarations
****************************************************************************/
-// Also does security for you
-uint16_t L2CA_Register2(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level);
-
/*******************************************************************************
*
* Function L2CA_Register
@@ -352,10 +324,8 @@ uint16_t L2CA_Register2(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
* BTM_SetSecurityLevel().
*
******************************************************************************/
-extern uint16_t L2CA_Register(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level);
+extern uint16_t L2CA_Register(uint16_t psm, tL2CAP_APPL_INFO* p_cb_info,
+ bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info);
/*******************************************************************************
*
@@ -371,6 +341,18 @@ extern void L2CA_Deregister(uint16_t psm);
/*******************************************************************************
*
+ * Function L2CA_AllocatePSM
+ *
+ * Description Other layers call this function to find an unused PSM for
+ * L2CAP services.
+ *
+ * Returns PSM to use.
+ *
+ ******************************************************************************/
+extern uint16_t L2CA_AllocatePSM(void);
+
+/*******************************************************************************
+ *
* Function L2CA_AllocateLePSM
*
* Description Other layers call this function to find an unused LE PSM for
@@ -392,8 +374,6 @@ extern uint16_t L2CA_AllocateLePSM(void);
******************************************************************************/
extern void L2CA_FreeLePSM(uint16_t psm);
-extern uint16_t L2CA_ConnectReq2(uint16_t psm, const RawAddress& p_bd_addr,
- uint16_t sec_level);
/*******************************************************************************
*
* Function L2CA_ConnectReq
@@ -411,6 +391,36 @@ extern uint16_t L2CA_ConnectReq(uint16_t psm, const RawAddress& p_bd_addr);
/*******************************************************************************
*
+ * Function L2CA_ConnectRsp
+ *
+ * Description Higher layers call this function to accept an incoming
+ * L2CAP connection, for which they had gotten an connect
+ * indication callback.
+ *
+ * Returns true for success, false for failure
+ *
+ ******************************************************************************/
+extern bool L2CA_ConnectRsp(const RawAddress& p_bd_addr, uint8_t id,
+ uint16_t lcid, uint16_t result, uint16_t status);
+
+/*******************************************************************************
+ *
+ * Function L2CA_ErtmConnectReq
+ *
+ * Description Higher layers call this function to create an L2CAP
+ * connection that needs to use Enhanced Retransmission Mode.
+ * Note that the connection is not established at this time,
+ * but connection establishment gets started. The callback
+ * will be invoked when connection establishes or fails.
+ *
+ * Returns the CID of the connection, or 0 if it failed to start
+ *
+ ******************************************************************************/
+extern uint16_t L2CA_ErtmConnectReq(uint16_t psm, const RawAddress& p_bd_addr,
+ tL2CAP_ERTM_INFO* p_ertm_info);
+
+/*******************************************************************************
+ *
* Function L2CA_RegisterLECoc
*
* Description Other layers call this function to register for L2CAP
@@ -423,9 +433,7 @@ extern uint16_t L2CA_ConnectReq(uint16_t psm, const RawAddress& p_bd_addr);
* and BTM_SetSecurityLevel().
*
******************************************************************************/
-extern uint16_t L2CA_RegisterLECoc(uint16_t psm,
- const tL2CAP_APPL_INFO& p_cb_info,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg);
+extern uint16_t L2CA_RegisterLECoc(uint16_t psm, tL2CAP_APPL_INFO* p_cb_info);
/*******************************************************************************
*
@@ -452,8 +460,22 @@ extern void L2CA_DeregisterLECoc(uint16_t psm);
*
******************************************************************************/
extern uint16_t L2CA_ConnectLECocReq(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg,
- uint16_t sec_level);
+ tL2CAP_LE_CFG_INFO* p_cfg);
+
+/*******************************************************************************
+ *
+ * Function L2CA_ConnectLECocRsp
+ *
+ * Description Higher layers call this function to accept an incoming
+ * L2CAP LE COC connection, for which they had gotten a connect
+ * indication callback.
+ *
+ * Returns true for success, false for failure
+ *
+ ******************************************************************************/
+extern bool L2CA_ConnectLECocRsp(const RawAddress& p_bd_addr, uint8_t id,
+ uint16_t lcid, uint16_t result,
+ uint16_t status, tL2CAP_LE_CFG_INFO* p_cfg);
/*******************************************************************************
*
@@ -469,49 +491,43 @@ extern bool L2CA_GetPeerLECocConfig(uint16_t lcid,
/*******************************************************************************
*
- * Function L2CA_ReconfigCreditBasedConnsReq
+ * Function L2CA_ErtmConnectRsp
*
- * Description Start reconfigure procedure on Connection Oriented Channel.
+ * Description Higher layers call this function to accept an incoming
+ * L2CAP connection, for which they had gotten an connect
+ * indication callback, and for which the higher layer wants
+ * to use Enhanced Retransmission Mode.
*
- * Return value: true if peer is connected
+ * Returns true for success, false for failure
*
******************************************************************************/
-
-extern bool L2CA_ReconfigCreditBasedConnsReq(const RawAddress& bd_addr,
- std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg);
+extern bool L2CA_ErtmConnectRsp(const RawAddress& p_bd_addr, uint8_t id,
+ uint16_t lcid, uint16_t result, uint16_t status,
+ tL2CAP_ERTM_INFO* p_ertm_info);
/*******************************************************************************
*
- * Function L2CA_ConnectCreditBasedReq
+ * Function L2CA_ConfigReq
*
- * Description With this function L2CAP will initiate setup of up to 5 credit
- * based connections for given psm using provided configuration.
- * L2CAP will notify user on the connection result, by calling
- * pL2CA_CreditBasedConnectCfm_Cb for each cid with a result.
+ * Description Higher layers call this function to send configuration.
*
- * Return value: vector of allocated local cids for the connection
+ * Returns true if configuration sent, else false
*
******************************************************************************/
-
-extern std::vector<uint16_t> L2CA_ConnectCreditBasedReq(
- uint16_t psm, const RawAddress& p_bd_addr, tL2CAP_LE_CFG_INFO* p_cfg);
+extern bool L2CA_ConfigReq(uint16_t cid, tL2CAP_CFG_INFO* p_cfg);
/*******************************************************************************
*
- * Function L2CA_ConnectCreditBasedRsp
+ * Function L2CA_ConfigRsp
*
- * Description Response for the pL2CA_CreditBasedConnectInd_Cb which is the
- * indication for peer requesting credit based connection.
+ * Description Higher layers call this function to send a configuration
+ * response.
*
- * Return value: true if peer is connected
+ * Returns true if configuration response sent, else false
*
******************************************************************************/
+extern bool L2CA_ConfigRsp(uint16_t cid, tL2CAP_CFG_INFO* p_cfg);
-extern bool L2CA_ConnectCreditBasedRsp(const RawAddress& p_bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids,
- uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg);
/*******************************************************************************
*
* Function L2CA_DisconnectReq
@@ -523,7 +539,17 @@ extern bool L2CA_ConnectCreditBasedRsp(const RawAddress& p_bd_addr, uint8_t id,
******************************************************************************/
extern bool L2CA_DisconnectReq(uint16_t cid);
-extern bool L2CA_DisconnectLECocReq(uint16_t cid);
+/*******************************************************************************
+ *
+ * Function L2CA_DisconnectRsp
+ *
+ * Description Higher layers call this function to acknowledge the
+ * disconnection of a channel.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+extern bool L2CA_DisconnectRsp(uint16_t cid);
/*******************************************************************************
*
@@ -539,13 +565,29 @@ extern bool L2CA_DisconnectLECocReq(uint16_t cid);
******************************************************************************/
extern uint8_t L2CA_DataWrite(uint16_t cid, BT_HDR* p_data);
-extern uint8_t L2CA_LECocDataWrite(uint16_t cid, BT_HDR* p_data);
-
// Given a local channel identifier, |lcid|, this function returns the bound
-// remote channel identifier, |rcid|. If
+// remote channel identifier, |rcid|, and the ACL link handle, |handle|. If
// |lcid| is not known or is invalid, this function returns false and does not
-// modify the value pointed at by |rcid|. |rcid| may be NULL.
-bool L2CA_GetRemoteCid(uint16_t lcid, uint16_t* rcid);
+// modify the values pointed at by |rcid| and |handle|. |rcid| and |handle| may
+// be NULL.
+bool L2CA_GetIdentifiers(uint16_t lcid, uint16_t* rcid, uint16_t* handle);
+
+/*******************************************************************************
+ *
+ * Function L2CA_SetIdleTimeout
+ *
+ * Description Higher layers call this function to set the idle timeout for
+ * a connection, or for all future connections. The "idle
+ * timeout" is the amount of time that a connection can remain
+ * up with no L2CAP channels on it. A timeout of zero means
+ * that the connection will be torn down immediately when the
+ * last channel is removed. A timeout of 0xFFFF means no
+ * timeout. Values are in seconds.
+ *
+ * Returns true if command succeeded, false if failed
+ *
+ ******************************************************************************/
+extern bool L2CA_SetIdleTimeout(uint16_t cid, uint16_t timeout, bool is_global);
/*******************************************************************************
*
@@ -584,6 +626,25 @@ extern uint8_t L2CA_SetTraceLevel(uint8_t trace_level);
/*******************************************************************************
*
+ * Function L2CA_SetDesireRole
+ *
+ * Description This function sets the desire role for L2CAP.
+ * If the new role is L2CAP_ROLE_ALLOW_SWITCH, allow switch on
+ * HciCreateConnection.
+ * If the new role is L2CAP_ROLE_DISALLOW_SWITCH, do not allow
+ * switch on HciCreateConnection.
+ *
+ * If the new role is a valid role (HCI_ROLE_MASTER or
+ * HCI_ROLE_SLAVE), the desire role is set to the new value.
+ * Otherwise, it is not changed.
+ *
+ * Returns the new (current) role
+ *
+ ******************************************************************************/
+extern uint8_t L2CA_SetDesireRole(uint8_t new_role);
+
+/*******************************************************************************
+ *
* Function L2CA_FlushChannel
*
* Description This function flushes none, some or all buffers queued up
@@ -609,8 +670,7 @@ extern uint16_t L2CA_FlushChannel(uint16_t lcid, uint16_t num_to_flush);
* Returns true if a valid channel, else false
*
******************************************************************************/
-extern bool L2CA_SetAclPriority(const RawAddress& bd_addr,
- tL2CAP_PRIORITY priority);
+extern bool L2CA_SetAclPriority(const RawAddress& bd_addr, uint8_t priority);
/*******************************************************************************
*
@@ -625,6 +685,33 @@ extern bool L2CA_SetTxPriority(uint16_t cid, tL2CAP_CHNL_PRIORITY priority);
/*******************************************************************************
*
+ * Function L2CA_SetFlushTimeout
+ *
+ * Description This function set the automatic flush time out in Baseband
+ * for ACL-U packets.
+ * BdAddr : the remote BD address of ACL link. If it is
+ * BT_DB_ANY then the flush time out will be applied
+ * to all ACL link.
+ * FlushTimeout: flush time out in ms
+ * 0x0000 : No automatic flush
+ * L2CAP_NO_RETRANSMISSION : No retransmission
+ * 0x0002 - 0xFFFE : flush time out, if
+ * (flush_tout * 8) + 3 / 5) <=
+ * HCI_MAX_AUTOMATIC_FLUSH_TIMEOUT
+ * (in 625us slot).
+ * Otherwise, return false.
+ * L2CAP_NO_AUTOMATIC_FLUSH : No automatic flush
+ *
+ * Returns true if command succeeded, false if failed
+ *
+ * NOTE This flush timeout applies to all logical channels active on
+ * the ACL link.
+ ******************************************************************************/
+extern bool L2CA_SetFlushTimeout(const RawAddress& bd_addr,
+ uint16_t flush_tout);
+
+/*******************************************************************************
+ *
* Function L2CA_SetChnlFlushability
*
* Description Higher layers call this function to set a channels
@@ -687,10 +774,14 @@ typedef struct {
tL2CA_FIXED_CHNL_CB* pL2CA_FixedConn_Cb;
tL2CA_FIXED_DATA_CB* pL2CA_FixedData_Cb;
tL2CA_FIXED_CONGESTION_STATUS_CB* pL2CA_FixedCong_Cb;
+ tL2CAP_FCR_OPTS fixed_chnl_opts;
uint16_t default_idle_tout;
+ tL2CA_TX_COMPLETE_CB*
+ pL2CA_FixedTxComplete_Cb; /* fixed channel tx complete callback */
} tL2CAP_FIXED_CHNL_REG;
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
/*******************************************************************************
*
* Function L2CA_RegisterFixedChannel
@@ -720,6 +811,8 @@ extern bool L2CA_RegisterFixedChannel(uint16_t fixed_cid,
******************************************************************************/
extern bool L2CA_ConnectFixedChnl(uint16_t fixed_cid,
const RawAddress& bd_addr);
+extern bool L2CA_ConnectFixedChnl(uint16_t fixed_cid, const RawAddress& bd_addr,
+ uint8_t initiating_phys);
/*******************************************************************************
*
@@ -756,7 +849,7 @@ extern bool L2CA_RemoveFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda);
/*******************************************************************************
*
- * Function L2CA_SetLeGattTimeout
+ * Function L2CA_SetFixedChannelTout
*
* Description Higher layers call this function to set the idle timeout for
* a fixed channel. The "idle timeout" is the amount of time
@@ -771,9 +864,38 @@ extern bool L2CA_RemoveFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda);
* Returns true if command succeeded, false if failed
*
******************************************************************************/
-extern bool L2CA_SetLeGattTimeout(const RawAddress& rem_bda,
- uint16_t idle_tout);
+extern bool L2CA_SetFixedChannelTout(const RawAddress& rem_bda,
+ uint16_t fixed_cid, uint16_t idle_tout);
+
+#endif /* (L2CAP_NUM_FIXED_CHNLS > 0) */
+/*******************************************************************************
+ *
+ * Function L2CA_CancelBleConnectReq
+ *
+ * Description Cancel a pending connection attempt to a BLE device.
+ *
+ * Parameters: BD Address of remote
+ *
+ * Return value: true if connection was cancelled
+ *
+ ******************************************************************************/
+extern bool L2CA_CancelBleConnectReq(const RawAddress& rem_bda);
+
+/*******************************************************************************
+ *
+ * Function L2CA_UpdateBleConnParams
+ *
+ * Description Update BLE connection parameters.
+ *
+ * Parameters: BD Address of remote
+ *
+ * Return value: true if update started
+ *
+ ******************************************************************************/
+extern bool L2CA_UpdateBleConnParams(const RawAddress& rem_bdRa,
+ uint16_t min_int, uint16_t max_int,
+ uint16_t latency, uint16_t timeout);
extern bool L2CA_UpdateBleConnParams(const RawAddress& rem_bda,
uint16_t min_int, uint16_t max_int,
uint16_t latency, uint16_t timeout,
@@ -803,16 +925,24 @@ extern bool L2CA_EnableUpdateBleConnParams(const RawAddress& rem_bda,
* Returns link role.
*
******************************************************************************/
-extern tHCI_ROLE L2CA_GetBleConnRole(const RawAddress& bd_addr);
+extern uint8_t L2CA_GetBleConnRole(const RawAddress& bd_addr);
+
+/*******************************************************************************
+ *
+ * Function L2CA_GetDisconnectReason
+ *
+ * Description This function returns the disconnect reason code.
+ *
+ * Parameters: BD Address of remote
+ * Physical transport for the L2CAP connection (BR/EDR or LE)
+ *
+ * Returns disconnect reason
+ *
+ ******************************************************************************/
+extern uint16_t L2CA_GetDisconnectReason(const RawAddress& remote_bda,
+ tBT_TRANSPORT transport);
extern void L2CA_AdjustConnectionIntervals(uint16_t* min_interval,
uint16_t* max_interval,
uint16_t floor_interval);
-
-/**
- * Check whether an ACL or LE link to the remote device is established
- */
-extern bool L2CA_IsLinkEstablished(const RawAddress& bd_addr,
- tBT_TRANSPORT transport);
-
#endif /* L2C_API_H */
diff --git a/stack/include/l2cap_acl_interface.h b/stack/include/l2cap_acl_interface.h
deleted file mode 100644
index 79aa103ba..000000000
--- a/stack/include/l2cap_acl_interface.h
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include "bt_common.h"
-#include "types/raw_address.h"
-
-// This header contains functions for L2cap-ACL to invoke
-//
-void acl_accept_connection_request(const RawAddress& bd_addr, uint8_t role);
-void acl_create_classic_connection(const RawAddress& bd_addr,
- bool there_are_high_priority_channels,
- bool is_bonding);
-bool acl_create_le_connection(const RawAddress& bd_addr);
-bool acl_create_le_connection_with_id(uint8_t id, const RawAddress& bd_addr);
-void acl_reject_connection_request(const RawAddress& bd_addr, uint8_t reason);
-void acl_send_data_packet_br_edr(const RawAddress& bd_addr, BT_HDR* p_buf);
-void acl_send_data_packet_ble(const RawAddress& bd_addr, BT_HDR* p_buf);
-void acl_write_automatic_flush_timeout(const RawAddress& bd_addr,
- uint16_t flush_timeout);
-
-// ACL data received from HCI-ACL
-extern void l2c_rcv_acl_data(BT_HDR* p_msg);
-
-// Segments is sent to HCI-ACL
-extern void l2c_link_segments_xmitted(BT_HDR* p_msg);
-
-extern void l2c_link_hci_conn_req(const RawAddress& bd_addr);
-
-extern void l2cu_resubmit_pending_sec_req(const RawAddress* p_bda);
-
-extern void l2c_link_process_num_completed_pkts(uint8_t* p, uint8_t evt_len);
-
-extern void l2c_packets_completed(uint16_t handle, uint16_t num_sent);
diff --git a/stack/include/l2cap_controller_interface.h b/stack/include/l2cap_controller_interface.h
deleted file mode 100644
index a88aa4253..000000000
--- a/stack/include/l2cap_controller_interface.h
+++ /dev/null
@@ -1,30 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include "bt_common.h"
-
-// This header contains functions for Controller Module to invoke
-
-extern void l2cu_set_non_flushable_pbf(bool is_supported);
-
-extern void l2c_link_init();
-
-extern void l2c_link_processs_ble_num_bufs(uint16_t num_lm_acl_bufs);
-
-extern void l2cu_device_reset(void);
diff --git a/stack/include/l2cap_hci_link_interface.h b/stack/include/l2cap_hci_link_interface.h
deleted file mode 100644
index db4eceee7..000000000
--- a/stack/include/l2cap_hci_link_interface.h
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include "bt_common.h"
-#include "stack/include/hci_error_code.h"
-
-// This header contains functions for HCI-LinkManagement to invoke
-
-extern bool l2c_link_hci_disc_comp(uint16_t handle, tHCI_REASON reason);
-
-extern void l2c_link_role_changed(const RawAddress* bd_addr, uint8_t new_role,
- uint8_t hci_status);
-
-extern bool l2cble_conn_comp(uint16_t handle, uint8_t role,
- const RawAddress& bda, tBLE_ADDR_TYPE type,
- uint16_t conn_interval, uint16_t conn_latency,
- uint16_t conn_timeout);
-
-extern bool l2cble_conn_comp_from_address_with_type(
- uint16_t handle, uint8_t role, const tBLE_BD_ADDR& address_with_type,
- uint16_t conn_interval, uint16_t conn_latency, uint16_t conn_timeout);
-
-extern void l2cble_process_conn_update_evt(uint16_t handle, uint8_t status,
- uint16_t interval, uint16_t latency,
- uint16_t timeout);
-
-extern void l2cble_process_data_length_change_event(uint16_t handle,
- uint16_t tx_data_len,
- uint16_t rx_data_len);
-
-// Notify to L2cap layer that ACL data or remote version is received
-extern void l2cble_notify_le_connection(const RawAddress& bda);
-
-void l2cble_use_preferred_conn_params(const RawAddress& bda);
-
-extern void l2cble_process_rc_param_request_evt(uint16_t handle,
- uint16_t int_min,
- uint16_t int_max,
- uint16_t latency,
- uint16_t timeout);
-
-// Invoked when HCI mode is changed to HCI_MODE_ACTIVE or HCI_MODE_SNIFF
-extern void l2c_OnHciModeChangeSendPendingPackets(RawAddress remote);
-
-// Invoked when HCI indicates to L2cap to check Security requirement
-extern void l2cu_resubmit_pending_sec_req(const RawAddress* p_bda);
diff --git a/stack/include/l2cap_security_interface.h b/stack/include/l2cap_security_interface.h
deleted file mode 100644
index 11059df5d..000000000
--- a/stack/include/l2cap_security_interface.h
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include "bt_common.h"
-
-// This header contains functions for Security Module to invoke
-
-extern void l2cu_update_lcb_4_bonding(const RawAddress& p_bd_addr,
- bool is_bonding);
-
-extern bool l2cu_start_post_bond_timer(uint16_t handle);
-
-extern void l2c_pin_code_request(const RawAddress& bd_addr);
-
-extern void l2cu_resubmit_pending_sec_req(const RawAddress* p_bda);
-
-// Establish ACL link to remote device for Security Manager/Pairing.
-// Returns BTM_CMD_STARTED if already connecting, BTM_NO_RESOURCES if can't
-// allocate lcb, BTM_SUCCESS if initiated the connection
-tBTM_STATUS l2cu_ConnectAclForSecurity(const RawAddress& bd_addr);
-
-extern void l2cble_update_sec_act(const RawAddress& bd_addr, uint16_t sec_act);
diff --git a/stack/include/l2cdefs.h b/stack/include/l2cdefs.h
index 38d16d9f3..2d4d6dbae 100644
--- a/stack/include/l2cdefs.h
+++ b/stack/include/l2cdefs.h
@@ -33,17 +33,16 @@
#define L2CAP_CMD_INFO_REQ 0x0A
#define L2CAP_CMD_INFO_RSP 0x0B
#define L2CAP_CMD_AMP_CONN_REQ 0x0C
+#define L2CAP_CMD_AMP_CONN_RSP 0x0D
#define L2CAP_CMD_AMP_MOVE_REQ 0x0E
+#define L2CAP_CMD_AMP_MOVE_RSP 0x0F
+#define L2CAP_CMD_AMP_MOVE_CFM 0x10
+#define L2CAP_CMD_AMP_MOVE_CFM_RSP 0x11
#define L2CAP_CMD_BLE_UPDATE_REQ 0x12
#define L2CAP_CMD_BLE_UPDATE_RSP 0x13
#define L2CAP_CMD_BLE_CREDIT_BASED_CONN_REQ 0x14
#define L2CAP_CMD_BLE_CREDIT_BASED_CONN_RES 0x15
#define L2CAP_CMD_BLE_FLOW_CTRL_CREDIT 0x16
-/* Enhanced CoC */
-#define L2CAP_CMD_CREDIT_BASED_CONN_REQ 0x17
-#define L2CAP_CMD_CREDIT_BASED_CONN_RES 0x18
-#define L2CAP_CMD_CREDIT_BASED_RECONFIG_REQ 0x19
-#define L2CAP_CMD_CREDIT_BASED_RECONFIG_RES 0x1A
/* Define some packet and header lengths
*/
@@ -69,8 +68,23 @@
#define L2CAP_ECHO_REQ_LEN 0
/* Data is optional */
#define L2CAP_ECHO_RSP_LEN 0
+/* Info type */
+#define L2CAP_INFO_REQ_LEN 2
/* Info type, result (data is optional) */
#define L2CAP_INFO_RSP_LEN 4
+/* Additional connectionless packet overhead */
+#define L2CAP_UCD_OVERHEAD 2
+
+/* PSM, CID, and remote controller ID */
+#define L2CAP_AMP_CONN_REQ_LEN 5
+/* CID and remote controller ID */
+#define L2CAP_AMP_MOVE_REQ_LEN 3
+/* CID and result */
+#define L2CAP_AMP_MOVE_RSP_LEN 4
+/* CID and result */
+#define L2CAP_AMP_MOVE_CFM_LEN 4
+/* CID */
+#define L2CAP_AMP_MOVE_CFM_RSP_LEN 2
/* Min and max interval, latency, tout */
#define L2CAP_CMD_BLE_UPD_REQ_LEN 8
@@ -84,89 +98,62 @@
/* CID, Credit */
#define L2CAP_CMD_BLE_FLOW_CTRL_CREDIT_LEN 4
-/* LE PSM, MTU, MPS, Initial Credits, SCIDS[] */
-#define L2CAP_CMD_CREDIT_BASED_CONN_REQ_MIN_LEN 8
-/* MTU, MPS, Initial Credits, Result, DCIDS[] */
-#define L2CAP_CMD_CREDIT_BASED_CONN_RES_MIN_LEN 8
-
-/* MTU, MPS, DCIDS[] */
-#define L2CAP_CMD_CREDIT_BASED_RECONFIG_REQ_MIN_LEN 4
-/* Result */
-#define L2CAP_CMD_CREDIT_BASED_RECONFIG_RES_LEN 2
-
/* Define the packet boundary flags
*/
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
+#define L2CAP_PKT_START_FLUSHABLE 2
#define L2CAP_PKT_START_NON_FLUSHABLE 0
+#endif
+#define L2CAP_COMPLETE_AMP_PKT 3 /* complete L2CAP packet on AMP HCI */
#define L2CAP_PKT_START 2
#define L2CAP_PKT_CONTINUE 1
+#define L2CAP_MASK_FLAG 0x0FFF
#define L2CAP_PKT_TYPE_SHIFT 12
+#define L2CAP_PKT_TYPE_MASK 3
/* Define the L2CAP connection result codes
*/
-typedef enum : uint16_t {
- L2CAP_CONN_OK = 0,
- L2CAP_CONN_PENDING = 1,
- L2CAP_CONN_NO_PSM = 2,
- L2CAP_CONN_SECURITY_BLOCK = 3,
- L2CAP_CONN_NO_RESOURCES = 4,
- L2CAP_CONN_OTHER_ERROR = 5,
- L2CAP_CONN_TIMEOUT = 0xEEEE,
- /* Add a couple of our own for internal use */
- L2CAP_CONN_NO_LINK = 255,
- L2CAP_CONN_CANCEL = 256, /* L2CAP connection cancelled */
-} tL2CAP_CONN;
+#define L2CAP_CONN_OK 0
+#define L2CAP_CONN_PENDING 1
+#define L2CAP_CONN_NO_PSM 2
+#define L2CAP_CONN_SECURITY_BLOCK 3
+#define L2CAP_CONN_NO_RESOURCES 4
+#define L2CAP_CONN_BAD_CTLR_ID 5 /* AMP related */
+#define L2CAP_CONN_TIMEOUT 0xEEEE
+#define L2CAP_CONN_AMP_FAILED 254
+/* Add a couple of our own for internal use */
+#define L2CAP_CONN_NO_LINK 255
+#define L2CAP_CONN_CANCEL 256 /* L2CAP connection cancelled */
/* Define the LE L2CAP Connection Response Result codes
*/
-typedef enum : uint8_t {
- L2CAP_LE_RESULT_CONN_OK = 0,
- L2CAP_LE_RESULT_NO_PSM = 2,
- L2CAP_LE_RESULT_NO_RESOURCES = 4,
- L2CAP_LE_RESULT_INSUFFICIENT_AUTHENTICATION = 5,
- L2CAP_LE_RESULT_INSUFFICIENT_AUTHORIZATION = 6,
- L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP_KEY_SIZE = 7,
- L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP = 8,
- /* We don't like peer device response */
- L2CAP_LE_RESULT_INVALID_SOURCE_CID = 9,
- L2CAP_LE_RESULT_SOURCE_CID_ALREADY_ALLOCATED = 0x0A,
- L2CAP_LE_RESULT_UNACCEPTABLE_PARAMETERS = 0x0B,
- L2CAP_LE_RESULT_INVALID_PARAMETERS = 0x0C
-} tL2CAP_LE_RESULT_CODE;
-
-inline std::string l2cap_le_result_code_text(
- const tL2CAP_LE_RESULT_CODE& code) {
- switch (code) {
- case L2CAP_LE_RESULT_CONN_OK:
- return std::string("le connection success");
- case L2CAP_LE_RESULT_NO_PSM:
- return std::string("le no psm service");
- case L2CAP_LE_RESULT_NO_RESOURCES:
- return std::string("le no resources");
- case L2CAP_LE_RESULT_INSUFFICIENT_AUTHENTICATION:
- return std::string("le authentication failed");
- case L2CAP_LE_RESULT_INSUFFICIENT_AUTHORIZATION:
- return std::string("le authorization failed");
- case L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP_KEY_SIZE:
- return std::string("le encryption key size failed");
- case L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP:
- return std::string("le encryption failed");
- case L2CAP_LE_RESULT_INVALID_SOURCE_CID:
- return std::string("le invalid source channel identifier");
- case L2CAP_LE_RESULT_SOURCE_CID_ALREADY_ALLOCATED:
- return std::string("le source channel identifier busy");
- case L2CAP_LE_RESULT_UNACCEPTABLE_PARAMETERS:
- return std::string("le unacceptable parameters");
- case L2CAP_LE_RESULT_INVALID_PARAMETERS:
- return std::string("invalid parameters");
- }
-}
-
-/* Credit based reconfig results code */
-#define L2CAP_RECONFIG_SUCCEED 0
-#define L2CAP_RECONFIG_REDUCTION_MTU_NO_ALLOWED 1
-#define L2CAP_RECONFIG_REDUCTION_MPS_NO_ALLOWED 2
-#define L2CAP_RECONFIG_INVALID_DCID 3
-#define L2CAP_RECONFIG_UNACCAPTED_PARAM 4
+#define L2CAP_LE_RESULT_CONN_OK 0
+#define L2CAP_LE_RESULT_NO_PSM 2
+#define L2CAP_LE_RESULT_NO_RESOURCES 4
+#define L2CAP_LE_RESULT_INSUFFICIENT_AUTHENTICATION 5
+#define L2CAP_LE_RESULT_INSUFFICIENT_AUTHORIZATION 6
+#define L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP_KEY_SIZE 7
+#define L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP 8
+/* We don't like peer device response */
+#define L2CAP_LE_RESULT_INVALID_SOURCE_CID 9
+#define L2CAP_LE_RESULT_SOURCE_CID_ALREADY_ALLOCATED 0x0A
+
+typedef uint8_t tL2CAP_LE_RESULT_CODE;
+
+/* Define L2CAP Move Channel Response result codes
+*/
+#define L2CAP_MOVE_OK 0
+#define L2CAP_MOVE_PENDING 1
+#define L2CAP_MOVE_CTRL_ID_NOT_SUPPORT 2
+#define L2CAP_MOVE_SAME_CTRLR_ID 3
+#define L2CAP_MOVE_CONFIG_NOT_SUPPORTED 4
+#define L2CAP_MOVE_CHAN_COLLISION 5
+#define L2CAP_MOVE_NOT_ALLOWED 6
+
+/* Define L2CAP Move Channel Confirmation result codes
+*/
+#define L2CAP_MOVE_CFM_OK 0
+#define L2CAP_MOVE_CFM_REFUSED 1
/* Define the L2CAP command reject reason codes
*/
@@ -176,16 +163,16 @@ inline std::string l2cap_le_result_code_text(
/* L2CAP Predefined CIDs
*/
-enum : uint16_t {
- L2CAP_SIGNALLING_CID = 1,
- L2CAP_CONNECTIONLESS_CID = 2,
- L2CAP_AMP_CID = 3,
- L2CAP_ATT_CID = 4,
- L2CAP_BLE_SIGNALLING_CID = 5,
- L2CAP_SMP_CID = 6,
- L2CAP_SMP_BR_CID = 7,
- L2CAP_BASE_APPL_CID = 0x0040,
-};
+#define L2CAP_SIGNALLING_CID 1
+#define L2CAP_CONNECTIONLESS_CID 2
+#define L2CAP_AMP_CID 3
+#define L2CAP_ATT_CID 4
+#define L2CAP_BLE_SIGNALLING_CID 5
+#define L2CAP_SMP_CID 6
+#define L2CAP_SMP_BR_CID 7
+#define L2CAP_AMP_TEST_CID 0x003F
+#define L2CAP_BASE_APPL_CID 0x0040
+#define L2CAP_BLE_CONN_MAX_CID 0x007F
/* Fixed Channels mask bits */
@@ -195,6 +182,9 @@ enum : uint16_t {
/* Connectionless reception */
#define L2CAP_FIXED_CHNL_CNCTLESS_BIT (1 << L2CAP_CONNECTIONLESS_CID)
+/* AMP Manager supported */
+#define L2CAP_FIXED_CHNL_AMP_BIT (1 << L2CAP_AMP_CID)
+
/* Attribute protocol supported */
#define L2CAP_FIXED_CHNL_ATT_BIT (1 << L2CAP_ATT_CID)
@@ -214,10 +204,7 @@ enum : uint16_t {
#define L2CAP_CFG_FAILED_NO_REASON 2
#define L2CAP_CFG_UNKNOWN_OPTIONS 3
#define L2CAP_CFG_PENDING 4
-
-static_assert(L2CAP_CONN_OTHER_ERROR != L2CAP_CFG_FAILED_NO_REASON,
- "Different error code should be provided for Connect error and "
- "Config error");
+#define L2CAP_CFG_FLOW_SPEC_REJECTED 5
/* Define the L2CAP configuration option types
*/
@@ -227,6 +214,7 @@ static_assert(L2CAP_CONN_OTHER_ERROR != L2CAP_CFG_FAILED_NO_REASON,
#define L2CAP_CFG_TYPE_FCR 0x04
#define L2CAP_CFG_TYPE_FCS 0x05
#define L2CAP_CFG_TYPE_EXT_FLOW 0x06
+#define L2CAP_CFG_TYPE_EXT_WIN_SIZE 0x07
#define L2CAP_CFG_MTU_OPTION_LEN 2 /* MTU option length */
#define L2CAP_CFG_FLUSH_OPTION_LEN 2 /* Flush option len */
@@ -234,6 +222,7 @@ static_assert(L2CAP_CONN_OTHER_ERROR != L2CAP_CFG_FAILED_NO_REASON,
#define L2CAP_CFG_FCR_OPTION_LEN 9 /* FCR option length */
#define L2CAP_CFG_FCS_OPTION_LEN 1 /* FCR option length */
#define L2CAP_CFG_EXT_FLOW_OPTION_LEN 16 /* Extended Flow Spec */
+#define L2CAP_CFG_EXT_WIN_SIZE_LEN 2 /* Ext window size length */
#define L2CAP_CFG_OPTION_OVERHEAD 2 /* Type and length */
/* Configuration Cmd/Rsp Flags mask
@@ -249,14 +238,17 @@ static_assert(L2CAP_CONN_OTHER_ERROR != L2CAP_CFG_FAILED_NO_REASON,
/* Default values for configuration
*/
#define L2CAP_NO_AUTOMATIC_FLUSH 0xFFFF
+#define L2CAP_NO_RETRANSMISSION 0x0001
#define L2CAP_DEFAULT_MTU (672)
+#define L2CAP_DEFAULT_FLUSH_TO L2CAP_NO_AUTOMATIC_FLUSH
#define L2CAP_DEFAULT_SERV_TYPE 1
#define L2CAP_DEFAULT_TOKEN_RATE 0
#define L2CAP_DEFAULT_BUCKET_SIZE 0
#define L2CAP_DEFAULT_PEAK_BANDWIDTH 0
#define L2CAP_DEFAULT_LATENCY 0xFFFFFFFF
#define L2CAP_DEFAULT_DELAY 0xFFFFFFFF
+#define L2CAP_DEFAULT_FCS L2CAP_CFG_FCS_USE
/* Define the L2CAP disconnect result codes
*/
@@ -285,6 +277,11 @@ static_assert(L2CAP_CONN_OTHER_ERROR != L2CAP_CFG_FAILED_NO_REASON,
/* Extended features mask bits
*/
+/* Retransmission Mode (Not Supported) */
+#define L2CAP_EXTFEA_RTRANS 0x00000001
+/* Flow Control Mode (Not Supported) */
+#define L2CAP_EXTFEA_FC 0x00000002
+#define L2CAP_EXTFEA_QOS 0x00000004
/* Enhanced retransmission mode */
#define L2CAP_EXTFEA_ENH_RETRANS 0x00000008
/* Streaming Mode */
@@ -336,6 +333,11 @@ static_assert(L2CAP_CONN_OTHER_ERROR != L2CAP_CFG_FAILED_NO_REASON,
#define L2CAP_SDU_LENGTH_MAX (8080 + 26 - (L2CAP_MIN_OFFSET + 6))
constexpr uint16_t L2CAP_SDU_LENGTH_LE_MAX = 0xffff;
+/* Part of L2CAP_MIN_OFFSET that is not part of L2CAP
+*/
+#define L2CAP_OFFSET_WO_L2HDR \
+ (L2CAP_MIN_OFFSET - (L2CAP_PKT_OVERHEAD + L2CAP_FCR_OVERHEAD))
+
/* SAR bits in the control word
*/
/* Control word to begin with for unsegmented PDU*/
diff --git a/stack/include/ldacBT_bco_for_fluoride.h b/stack/include/ldacBT_bco_for_fluoride.h
index ff5286933..9666a7c9d 100644
--- a/stack/include/ldacBT_bco_for_fluoride.h
+++ b/stack/include/ldacBT_bco_for_fluoride.h
@@ -27,7 +27,7 @@ extern "C" {
#endif /* LDAC_BCO_API */
/* This file contains the definitions, declarations and macros for an
- * implimentation of LDAC buffer control operation.
+ * implementation of LDAC buffer control operation.
*/
#define LDAC_BCO_ERR_NONE 0
diff --git a/stack/include/pan_api.h b/stack/include/pan_api.h
index 55895a4b0..0f9bab1cd 100644
--- a/stack/include/pan_api.h
+++ b/stack/include/pan_api.h
@@ -45,6 +45,7 @@
/* Bit map for PAN roles */
#define PAN_ROLE_CLIENT 0x01 /* PANU role */
+#define PAN_ROLE_GN_SERVER 0x02 /* GN role */
#define PAN_ROLE_NAP_SERVER 0x04 /* NAP role */
/* Bitmap to indicate the usage of the Data */
@@ -239,6 +240,7 @@ extern void PAN_Deregister(void);
*
* Parameters: role - is bit map of roles to be active
* PAN_ROLE_CLIENT is for PANU role
+ * PAN_ROLE_GN_SERVER is for GN role
* PAN_ROLE_NAP_SERVER is for NAP role
* sec_mask - Security mask for different roles
* It is array of uint8_t. The bytes
@@ -246,6 +248,7 @@ extern void PAN_Deregister(void);
* GN and NAP in order
*
* p_user_name - Service name for PANU role
+ * p_gn_name - Service name for GN role
* p_nap_name - Service name for NAP role
* Can be NULL if user wants it to be default
*
@@ -253,7 +256,8 @@ extern void PAN_Deregister(void);
* PAN_FAILURE - if the role is not valid
*
******************************************************************************/
-extern tPAN_RESULT PAN_SetRole(uint8_t role, const char* p_user_name,
+extern tPAN_RESULT PAN_SetRole(uint8_t role, uint8_t* sec_mask,
+ const char* p_user_name, const char* p_gn_name,
const char* p_nap_name);
/*******************************************************************************
@@ -267,6 +271,7 @@ extern tPAN_RESULT PAN_SetRole(uint8_t role, const char* p_user_name,
* src_role - Role of the local device for the connection
* dst_role - Role of the remote device for the connection
* PAN_ROLE_CLIENT is for PANU role
+ * PAN_ROLE_GN_SERVER is for GN role
* PAN_ROLE_NAP_SERVER is for NAP role
* *handle - Pointer for returning Handle to the connection
*
diff --git a/stack/include/port_api.h b/stack/include/port_api.h
index e331a3d19..daea3d484 100644
--- a/stack/include/port_api.h
+++ b/stack/include/port_api.h
@@ -181,15 +181,6 @@ typedef void(tPORT_CALLBACK)(uint32_t code, uint16_t port_handle);
* (scn * 2 + 1) dlci.
*
******************************************************************************/
-extern int RFCOMM_CreateConnectionWithSecurity(uint16_t uuid, uint8_t scn,
- bool is_server, uint16_t mtu,
- const RawAddress& bd_addr,
- uint16_t* p_handle,
- tPORT_CALLBACK* p_mgmt_cb,
- uint16_t sec_mask);
-
-extern void RFCOMM_ClearSecurityRecord(uint32_t scn);
-
extern int RFCOMM_CreateConnection(uint16_t uuid, uint8_t scn, bool is_server,
uint16_t mtu, const RawAddress& bd_addr,
uint16_t* p_handle,
diff --git a/stack/include/sco_client_callbacks.h b/stack/include/sco_client_callbacks.h
deleted file mode 100644
index 52482eb95..000000000
--- a/stack/include/sco_client_callbacks.h
+++ /dev/null
@@ -1,25 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "stack/include/btm_api_types.h"
-
-struct sco_client_callback_s {
- tBTM_SCO_CB on_connected;
- tBTM_SCO_CB on_disconnected;
- tBTM_ESCO_CBACK on_sco_event;
-};
diff --git a/stack/include/sco_hci_link_interface.h b/stack/include/sco_hci_link_interface.h
deleted file mode 100644
index 9054c4025..000000000
--- a/stack/include/sco_hci_link_interface.h
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include "stack/include/hci_error_code.h"
-#include "types/class_of_device.h"
-#include "types/raw_address.h"
-
-struct tBTM_ESCO_DATA;
-
-extern void btm_esco_proc_conn_chg(uint8_t status, uint16_t handle,
- uint8_t tx_interval, uint8_t retrans_window,
- uint16_t rx_pkt_len, uint16_t tx_pkt_len);
-extern bool btm_is_sco_active(uint16_t handle);
-extern void btm_sco_chk_pend_unpark(tHCI_STATUS hci_status,
- uint16_t hci_handle);
-extern void btm_sco_conn_req(const RawAddress& bda, const DEV_CLASS& dev_class,
- uint8_t link_type);
-extern void btm_sco_connected(tHCI_STATUS hci_status, const RawAddress& bda,
- uint16_t hci_handle, tBTM_ESCO_DATA* p_esco_data);
-extern bool btm_sco_removed(uint16_t hci_handle, tHCI_REASON reason);
-
-void btm_sco_on_disconnected(uint16_t hci_handle, tHCI_REASON reason);
-void btm_sco_on_esco_connect_request(const RawAddress&,
- const bluetooth::types::ClassOfDevice&);
-void btm_sco_on_sco_connect_request(const RawAddress&,
- const bluetooth::types::ClassOfDevice&);
diff --git a/stack/include/sdp_api.h b/stack/include/sdp_api.h
index 3758eae88..3bc1a3022 100644
--- a/stack/include/sdp_api.h
+++ b/stack/include/sdp_api.h
@@ -26,66 +26,31 @@
****************************************************************************/
/* Success code and error codes */
-typedef enum : uint16_t {
- SDP_SUCCESS = 0x0000,
- SDP_INVALID_VERSION = 0x0001,
- SDP_INVALID_SERV_REC_HDL = 0x0002,
- SDP_INVALID_REQ_SYNTAX = 0x0003,
- SDP_INVALID_PDU_SIZE = 0x0004,
- SDP_INVALID_CONT_STATE = 0x0005,
- SDP_NO_RESOURCES = 0x0006,
- SDP_DI_REG_FAILED = 0x0007,
- SDP_DI_DISC_FAILED = 0x0008,
- SDP_NO_DI_RECORD_FOUND = 0x0009,
- SDP_ERR_ATTR_NOT_PRESENT = 0x000A,
- SDP_ILLEGAL_PARAMETER = 0x000B,
-
- HID_SDP_NO_SERV_UUID = (SDP_ILLEGAL_PARAMETER + 1),
- HID_SDP_MANDATORY_MISSING,
-
- SDP_NO_RECS_MATCH = 0xFFF0,
- SDP_CONN_FAILED = 0xFFF1,
- SDP_CFG_FAILED = 0xFFF2,
- SDP_GENERIC_ERROR = 0xFFF3,
- SDP_DB_FULL = 0xFFF4,
- SDP_CANCEL = 0xFFF8,
-} tSDP_STATUS;
-using tSDP_RESULT = tSDP_STATUS;
-using tSDP_REASON = tSDP_STATUS;
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-static inline std::string sdp_status_text(const tSDP_STATUS& status) {
- switch (status) {
- CASE_RETURN_TEXT(SDP_SUCCESS);
- CASE_RETURN_TEXT(SDP_INVALID_VERSION);
- CASE_RETURN_TEXT(SDP_INVALID_SERV_REC_HDL);
- CASE_RETURN_TEXT(SDP_INVALID_REQ_SYNTAX);
- CASE_RETURN_TEXT(SDP_INVALID_PDU_SIZE);
- CASE_RETURN_TEXT(SDP_INVALID_CONT_STATE);
- CASE_RETURN_TEXT(SDP_NO_RESOURCES);
- CASE_RETURN_TEXT(SDP_DI_REG_FAILED);
- CASE_RETURN_TEXT(SDP_DI_DISC_FAILED);
- CASE_RETURN_TEXT(SDP_NO_DI_RECORD_FOUND);
- CASE_RETURN_TEXT(SDP_ERR_ATTR_NOT_PRESENT);
- CASE_RETURN_TEXT(SDP_ILLEGAL_PARAMETER);
-
- CASE_RETURN_TEXT(HID_SDP_NO_SERV_UUID);
- CASE_RETURN_TEXT(HID_SDP_MANDATORY_MISSING);
-
- CASE_RETURN_TEXT(SDP_NO_RECS_MATCH);
- CASE_RETURN_TEXT(SDP_CONN_FAILED);
- CASE_RETURN_TEXT(SDP_CFG_FAILED);
- CASE_RETURN_TEXT(SDP_GENERIC_ERROR);
- CASE_RETURN_TEXT(SDP_DB_FULL);
- CASE_RETURN_TEXT(SDP_CANCEL);
- default:
- return std::string("UNKNOWN[%hhu]", status);
- }
-}
-#undef CASE_RETURN_TEXT
+#define SDP_SUCCESS 0x0000
+#define SDP_INVALID_VERSION 0x0001
+#define SDP_INVALID_SERV_REC_HDL 0x0002
+#define SDP_INVALID_REQ_SYNTAX 0x0003
+#define SDP_INVALID_PDU_SIZE 0x0004
+#define SDP_INVALID_CONT_STATE 0x0005
+#define SDP_NO_RESOURCES 0x0006
+#define SDP_DI_REG_FAILED 0x0007
+#define SDP_DI_DISC_FAILED 0x0008
+#define SDP_NO_DI_RECORD_FOUND 0x0009
+#define SDP_ERR_ATTR_NOT_PRESENT 0x000A
+#define SDP_ILLEGAL_PARAMETER 0x000B
+
+#define SDP_NO_RECS_MATCH 0xFFF0
+#define SDP_CONN_FAILED 0xFFF1
+#define SDP_CFG_FAILED 0xFFF2
+#define SDP_GENERIC_ERROR 0xFFF3
+#define SDP_DB_FULL 0xFFF4
+#define SDP_INVALID_PDU 0xFFF5
+#define SDP_SECURITY_ERR 0xFFF6
+#define SDP_CONN_REJECTED 0xFFF7
+#define SDP_CANCEL 0xFFF8
+
+/* Define the PSM that SDP uses */
+#define SDP_PSM 0x0001
/* Masks for attr_value field of tSDP_DISC_ATTR */
#define SDP_DISC_ATTR_LEN_MASK 0x0FFF
@@ -100,8 +65,8 @@ static inline std::string sdp_status_text(const tSDP_STATUS& status) {
****************************************************************************/
/* Define a callback function for when discovery is complete. */
-typedef void(tSDP_DISC_CMPL_CB)(tSDP_RESULT result);
-typedef void(tSDP_DISC_CMPL_CB2)(tSDP_RESULT result, void* user_data);
+typedef void(tSDP_DISC_CMPL_CB)(uint16_t result);
+typedef void(tSDP_DISC_CMPL_CB2)(uint16_t result, void* user_data);
typedef struct {
RawAddress peer_addr;
@@ -569,9 +534,9 @@ uint16_t SDP_SetLocalDiRecord(tSDP_DI_RECORD* device_info, uint32_t* p_handle);
* Returns SDP_SUCCESS if query started successfully, else error
*
******************************************************************************/
-tSDP_STATUS SDP_DiDiscover(const RawAddress& remote_device,
- tSDP_DISCOVERY_DB* p_db, uint32_t len,
- tSDP_DISC_CMPL_CB* p_cb);
+uint16_t SDP_DiDiscover(const RawAddress& remote_device,
+ tSDP_DISCOVERY_DB* p_db, uint32_t len,
+ tSDP_DISC_CMPL_CB* p_cb);
/*******************************************************************************
*
diff --git a/stack/include/sdpdefs.h b/stack/include/sdpdefs.h
index 277510a92..4e4b7b90f 100644
--- a/stack/include/sdpdefs.h
+++ b/stack/include/sdpdefs.h
@@ -29,13 +29,17 @@
*/
#define ATTR_ID_SERVICE_RECORD_HDL 0x0000
#define ATTR_ID_SERVICE_CLASS_ID_LIST 0x0001
+#define ATTR_ID_SERVICE_RECORD_STATE 0x0002
#define ATTR_ID_SERVICE_ID 0x0003
#define ATTR_ID_PROTOCOL_DESC_LIST 0x0004
#define ATTR_ID_BROWSE_GROUP_LIST 0x0005
#define ATTR_ID_LANGUAGE_BASE_ATTR_ID_LIST 0x0006
+#define ATTR_ID_SERVICE_INFO_TIME_TO_LIVE 0x0007
+#define ATTR_ID_SERVICE_AVAILABILITY 0x0008
#define ATTR_ID_BT_PROFILE_DESC_LIST 0x0009
#define ATTR_ID_DOCUMENTATION_URL 0x000A
#define ATTR_ID_CLIENT_EXE_URL 0x000B
+#define ATTR_ID_ICON_URL 0x000C
#define ATTR_ID_ADDITION_PROTO_DESC_LISTS 0x000D
#define LANGUAGE_BASE_ID 0x0100
@@ -53,26 +57,72 @@
#define ATTR_ID_VENDOR_ID_SOURCE 0x0205
#define BLUETOOTH_DI_SPECIFICATION 0x0103 /* 1.3 */
+#define DI_VENDOR_ID_DEFAULT 0xFFFF
#define DI_VENDOR_ID_SOURCE_BTSIG 0x0001
#define DI_VENDOR_ID_SOURCE_USBIF 0x0002
+#define ATTR_ID_IP_SUBNET 0x0200 /* PAN Profile (***) */
+#define ATTR_ID_VERSION_NUMBER_LIST 0x0200
#define ATTR_ID_GOEP_L2CAP_PSM 0x0200
+#define ATTR_ID_GROUP_ID 0x0200
+#define ATTR_ID_SERVICE_DATABASE_STATE 0x0201
+#define ATTR_ID_SERVICE_VERSION 0x0300
+#define ATTR_ID_HCRP_1284ID 0x0300
+#define ATTR_ID_SUPPORTED_DATA_STORES 0x0301
#define ATTR_ID_NETWORK 0x0301
+#define ATTR_ID_EXTERNAL_NETWORK 0x0301
#define ATTR_ID_FAX_CLASS_1_SUPPORT 0x0302
#define ATTR_ID_REMOTE_AUDIO_VOLUME_CONTROL 0x0302
+#define ATTR_ID_DEVICE_NAME 0x0302
#define ATTR_ID_SUPPORTED_FORMATS_LIST 0x0303
+#define ATTR_ID_FAX_CLASS_2_0_SUPPORT 0x0303
+#define ATTR_ID_FAX_CLASS_2_SUPPORT 0x0304
+#define ATTR_ID_FRIENDLY_NAME 0x0304
+#define ATTR_ID_AUDIO_FEEDBACK_SUPPORT 0x0305
+#define ATTR_ID_NETWORK_ADDRESS 0x0306
+#define ATTR_ID_DEVICE_LOCATION 0x0306
+#define ATTR_ID_WAP_GATEWAY 0x0307
+#define ATTR_ID_HOME_PAGE_URL 0x0308
+#define ATTR_ID_WAP_STACK_TYPE 0x0309
+#define ATTR_ID_IMG_SUPPORTED_CAPABILITIES 0x0310 /* Imaging Profile */
#define ATTR_ID_SUPPORTED_FEATURES 0x0311 /* HFP, BIP */
+#define ATTR_ID_IMG_SUPPORTED_FUNCTIONS 0x0312 /* Imaging Profile */
+#define ATTR_ID_IMG_TOT_DATA_CAPABILITY 0x0313 /* Imaging Profile */
#define ATTR_ID_SUPPORTED_REPOSITORIES 0x0314 /* Phone book access Profile */
#define ATTR_ID_MAS_INSTANCE_ID 0x0315 /* MAP profile */
#define ATTR_ID_SUPPORTED_MSG_TYPE 0x0316 /* MAP profile */
#define ATTR_ID_MAP_SUPPORTED_FEATURES 0x0317 /* MAP profile */
#define ATTR_ID_PBAP_SUPPORTED_FEATURES 0x0317 /* PBAP profile */
+/* These values are for the BPP profile */
+#define ATTR_ID_DOCUMENT_FORMATS_SUPPORTED 0x0350
+#define ATTR_ID_CHARACTER_REPERTOIRES_SUPPORTED 0x0352
+#define ATTR_ID_XHTML_IMAGE_FORMATS_SUPPORTED 0x0354
+#define ATTR_ID_COLOR_SUPPORTED 0x0356
+#define ATTR_ID_1284ID 0x0358
+#define ATTR_ID_PRINTER_NAME 0x035A
+#define ATTR_ID_PRINTER_LOCATION 0x035C
+#define ATTR_ID_DUPLEX_SUPPORTED 0x035E
+#define ATTR_ID_MEDIA_TYPES_SUPPORTED 0x0360
+#define ATTR_ID_MAX_MEDIA_WIDTH 0x0362
+#define ATTR_ID_MAX_MEDIA_LENGTH 0x0364
+#define ATTR_ID_ENHANCED_LAYOUT_SUPPORTED 0x0366
+#define ATTR_ID_RUI_FORMATS_SUPPORTED 0x0368
+#define ATTR_ID_RUI_REF_PRINTING_SUPPORTED 0x0370 /* Boolean */
+#define ATTR_ID_RUI_DIRECT_PRINTING_SUPPORTED 0x0372 /* Boolean */
+#define ATTR_ID_REF_PRINTING_TOP_URL 0x0374
+#define ATTR_ID_DIRECT_PRINTING_TOP_URL 0x0376
+#define ATTR_ID_PRINTER_ADMIN_RUI_TOP_URL 0x0378
+#define ATTR_ID_BPP_DEVICE_NAME 0x037A
+
/* These values are for the PAN profile */
#define ATTR_ID_SECURITY_DESCRIPTION 0x030A
#define ATTR_ID_NET_ACCESS_TYPE 0x030B
#define ATTR_ID_MAX_NET_ACCESS_RATE 0x030C
+#define ATTR_ID_IPV4_SUBNET 0x030D
+#define ATTR_ID_IPV6_SUBNET 0x030E
+#define ATTR_ID_PAN_SECURITY 0x0400
/* These values are for HID profile */
#define ATTR_ID_HID_DEVICE_RELNUM 0x0200
@@ -95,12 +145,29 @@
/* Define common 16-bit protocol UUIDs
*/
+#define UUID_PROTOCOL_SDP 0x0001
+#define UUID_PROTOCOL_UDP 0x0002
#define UUID_PROTOCOL_RFCOMM 0x0003
+#define UUID_PROTOCOL_TCP 0x0004
+#define UUID_PROTOCOL_TCS_BIN 0x0005
+#define UUID_PROTOCOL_TCS_AT 0x0006
#define UUID_PROTOCOL_OBEX 0x0008
+#define UUID_PROTOCOL_IP 0x0009
+#define UUID_PROTOCOL_FTP 0x000A
+#define UUID_PROTOCOL_HTTP 0x000C
+#define UUID_PROTOCOL_WSP 0x000E
#define UUID_PROTOCOL_BNEP 0x000F
+#define UUID_PROTOCOL_UPNP 0x0010
#define UUID_PROTOCOL_HIDP 0x0011
+#define UUID_PROTOCOL_HCRP_CTRL 0x0012
+#define UUID_PROTOCOL_HCRP_DATA 0x0014
+#define UUID_PROTOCOL_HCRP_NOTIF 0x0016
#define UUID_PROTOCOL_AVCTP 0x0017
#define UUID_PROTOCOL_AVDTP 0x0019
+#define UUID_PROTOCOL_CMTP 0x001B
+#define UUID_PROTOCOL_UDI 0x001D
+#define UUID_PROTOCOL_MCAP_CTRL 0x001E
+#define UUID_PROTOCOL_MCAP_DATA 0x001F
#define UUID_PROTOCOL_L2CAP 0x0100
#define UUID_PROTOCOL_ATT 0x0007
@@ -192,15 +259,37 @@
#define UUID_SERVCLASS_GAP_SERVER 0x1800
#define UUID_SERVCLASS_GATT_SERVER 0x1801
+#define UUID_SERVCLASS_IMMEDIATE_ALERT 0x1802 /* immediate alert */
+#define UUID_SERVCLASS_LINKLOSS 0x1803 /* Link Loss Alert */
+#define UUID_SERVCLASS_TX_POWER 0x1804 /* TX power */
+#define UUID_SERVCLASS_CURRENT_TIME 0x1805 /* Link Loss Alert */
+#define UUID_SERVCLASS_DST_CHG 0x1806 /* DST Time change */
+#define UUID_SERVCLASS_REF_TIME_UPD 0x1807 /* reference time update */
+#define UUID_SERVCLASS_THERMOMETER 0x1809 /* Thermometer UUID */
#define UUID_SERVCLASS_DEVICE_INFO 0x180A /* device info service */
+#define UUID_SERVCLASS_NWA 0x180B /* Network availability */
+#define UUID_SERVCLASS_HEART_RATE 0x180D /* Heart Rate service */
+#define UUID_SERVCLASS_PHALERT 0x180E /* phone alert service */
+#define UUID_SERVCLASS_BATTERY 0x180F /* battery service */
+#define UUID_SERVCLASS_BPM 0x1810 /* blood pressure service */
+#define UUID_SERVCLASS_ALERT_NOTIFICATION 0x1811
#define UUID_SERVCLASS_LE_HID 0x1812 /* HID over LE */
#define UUID_SERVCLASS_SCAN_PARAM 0x1813 /* Scan Parameter service */
+#define UUID_SERVCLASS_GLUCOSE 0x1808 /* Glucose Meter Service */
+#define UUID_SERVCLASS_RSC 0x1814 /* RUNNERS SPEED AND CADENCE SERVICE */
+#define UUID_SERVCLASS_CSC 0x1816 /* Cycling SPEED AND CADENCE SERVICE */
+
+#define UUID_SERVCLASS_TEST_SERVER 0x9000 /* Test Group UUID */
#define UUID_CODEC_CVSD 0x0001 /* CVSD */
#define UUID_CODEC_MSBC 0x0002 /* mSBC */
+#define UUID_HF_IND_ENHANCED_DRIVER_SAFETY 0x0001 /* Enhanced Safety */
+#define UUID_HF_IND_BATTERY_LEVEL_STATUS 0x0002 /* Battery Status */
+
/* Define all the 'Descriptor Type' values.
*/
+#define NULL_DESC_TYPE 0
#define UINT_DESC_TYPE 1
#define TWO_COMP_INT_DESC_TYPE 2
#define UUID_DESC_TYPE 3
@@ -227,6 +316,17 @@
/* Constants used for display purposes only. These define overlapping attribute
* values */
+#define ATTR_ID_VERS_OR_GRP_OR_DRELNUM_OR_IPSUB_OR_SPECID 0x0200
+#define ATTR_ID_VEND_ID_OR_SERVICE_DB_STATE_OR_PARSE_VER 0x0201
+#define ATTR_ID_PROD_ID_OR_HID_DEV_SUBCLASS 0x0202
+#define ATTR_ID_PROD_VER_OR_HID_COUNTRY_CODE 0x0203
+#define ATTR_ID_PRIMARY_REC_OR_HID_VIRTUAL_CABLE 0x0204
+#define ATTR_ID_DI_VENDOR_ID_SOURCE_OR_HID_INIT_RECONNECT 0x0205
+#define ATTR_ID_SERV_VERS_OR_1284ID 0x0300
#define ATTR_ID_DATA_STORES_OR_NETWORK 0x0301
+#define ATTR_ID_FAX_1_OR_AUD_VOL_OR_DEV_NAME 0x0302
+#define ATTR_ID_FORMATS_OR_FAX_2_0 0x0303
+#define ATTR_ID_FAX_CLASS_2_OR_FRIENDLY_NAME 0x0304
+#define ATTR_ID_NETADDRESS_OR_DEVLOCATION 0x0306
#endif
diff --git a/stack/include/sec_hci_link_interface.h b/stack/include/sec_hci_link_interface.h
deleted file mode 100644
index f57c01266..000000000
--- a/stack/include/sec_hci_link_interface.h
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_api_types.h"
-#include "types/raw_address.h"
-
-// This header contains functions for HCIF-Security Management to invoke
-//
-
-void btm_create_conn_cancel_complete(uint8_t* p);
-void btm_create_conn_cancel_complete(uint8_t* p);
-void btm_io_capabilities_req(const RawAddress& p);
-void btm_io_capabilities_rsp(uint8_t* p);
-void btm_proc_sp_req_evt(tBTM_SP_EVT event, uint8_t* p);
-void btm_read_inq_tx_power_complete(uint8_t* p);
-void btm_read_local_oob_complete(uint8_t* p);
-void btm_rem_oob_req(uint8_t* p);
-void btm_sec_auth_complete(uint16_t handle, tHCI_STATUS status);
-void btm_sec_disconnected(uint16_t handle, tHCI_STATUS reason);
-void btm_sec_encrypt_change(uint16_t handle, tHCI_STATUS status,
- uint8_t encr_enable);
-void btm_sec_link_key_notification(const RawAddress& p_bda,
- const Octet16& link_key, uint8_t key_type);
-void btm_sec_link_key_request(uint8_t* p_event);
-void btm_sec_pin_code_request(uint8_t* p_event);
-void btm_sec_rmt_host_support_feat_evt(uint8_t* p);
-void btm_sec_rmt_name_request_complete(const RawAddress* bd_addr,
- uint8_t* bd_name, tHCI_STATUS status);
-void btm_sec_update_clock_offset(uint16_t handle, uint16_t clock_offset);
-void btm_simple_pair_complete(uint8_t* p);
diff --git a/stack/include/security_client_callbacks.h b/stack/include/security_client_callbacks.h
deleted file mode 100644
index 04c5d2aac..000000000
--- a/stack/include/security_client_callbacks.h
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "stack/include/btm_api_types.h"
-#include "stack/include/btm_ble_api_types.h"
-#include "stack/include/hci_error_code.h"
-
-/****************************************
- * Security Manager Callback Functions
- ****************************************/
-/* Authorize device for service. Parameters are
- * Service Id (NULL - unknown service or unused
- * [BTM_SEC_SERVICE_NAME_LEN set to 0])
- */
-typedef uint8_t(tBTM_AUTHORIZE_CALLBACK)(uint8_t service_id);
-
-/* Get PIN for the connection. Parameters are
- * BD Address of remote
- * Device Class of remote
- * BD Name of remote
- * Flag indicating the minimum pin code length to be 16 digits
- */
-typedef uint8_t(tBTM_PIN_CALLBACK)(const RawAddress& bd_addr,
- DEV_CLASS dev_class, tBTM_BD_NAME bd_name,
- bool min_16_digit);
-
-/* New Link Key for the connection. Parameters are
- * BD Address of remote
- * Link Key
- * Key Type: Combination, Local Unit, or Remote Unit
- */
-typedef uint8_t(tBTM_LINK_KEY_CALLBACK)(const RawAddress& bd_addr,
- DEV_CLASS dev_class,
- tBTM_BD_NAME bd_name,
- const LinkKey& key, uint8_t key_type);
-
-/* Remote Name Resolved. Parameters are
- * BD Address of remote
- * BD Name of remote
- */
-typedef void(tBTM_RMT_NAME_CALLBACK)(const RawAddress& bd_addr, DEV_CLASS dc,
- tBTM_BD_NAME bd_name);
-
-/* Authentication complete for the connection. Parameters are
- * BD Address of remote
- * Device Class of remote
- * BD Name of remote
- *
- */
-typedef void(tBTM_AUTH_COMPLETE_CALLBACK)(const RawAddress& bd_addr,
- DEV_CLASS dev_class,
- tBTM_BD_NAME bd_name,
- tHCI_REASON reason);
-
-struct tBTM_APPL_INFO {
- tBTM_PIN_CALLBACK* p_pin_callback{nullptr};
- tBTM_LINK_KEY_CALLBACK* p_link_key_callback{nullptr};
- tBTM_AUTH_COMPLETE_CALLBACK* p_auth_complete_callback{nullptr};
- tBTM_BOND_CANCEL_CMPL_CALLBACK* p_bond_cancel_cmpl_callback{nullptr};
- tBTM_SP_CALLBACK* p_sp_callback{nullptr};
- tBTM_LE_CALLBACK* p_le_callback{nullptr};
- tBTM_LE_KEY_CALLBACK* p_le_key_callback{nullptr};
-};
diff --git a/stack/include/smp_api.h b/stack/include/smp_api.h
index 9787bd856..8a66aaeb9 100644
--- a/stack/include/smp_api.h
+++ b/stack/include/smp_api.h
@@ -26,7 +26,6 @@
#include "bt_target.h"
#include "smp_api_types.h"
-#include "types/bt_transport.h"
/*****************************************************************************
* External Function Declarations
@@ -115,7 +114,7 @@ extern bool SMP_PairCancel(const RawAddress& bd_addr);
* Returns None
*
******************************************************************************/
-extern void SMP_SecurityGrant(const RawAddress& bd_addr, tSMP_STATUS res);
+extern void SMP_SecurityGrant(const RawAddress& bd_addr, uint8_t res);
/*******************************************************************************
*
@@ -177,28 +176,37 @@ extern void SMP_SecureConnectionOobDataReply(uint8_t* p_data);
/*******************************************************************************
*
- * Function SMP_CrLocScOobData
+ * Function SMP_KeypressNotification
*
- * Description This function is called to generate a public key to be
- * passed to a remote device via an Out of Band transport
+ * Description Notify SM about Keypress Notification.
+ *
+ * Parameters: bd_addr - Address of the device to send keypress
+ * notification to
+ * value - keypress notification parameter value
*
******************************************************************************/
-extern void SMP_CrLocScOobData();
+extern void SMP_KeypressNotification(const RawAddress& bd_addr, uint8_t value);
/*******************************************************************************
*
- * Function SMP_ClearLocScOobData
+ * Function SMP_CreateLocalSecureConnectionsOobData
+ *
+ * Description This function is called to start creation of local SC OOB
+ * data set (tSMP_LOC_OOB_DATA).
*
- * Description This function is called to clear out the OOB stored locally.
+ * Parameters: bd_addr - Address of the device to send OOB data block
+ * to.
*
+ * Returns Boolean - true: creation of local SC OOB data set started.
******************************************************************************/
-extern void SMP_ClearLocScOobData();
+extern bool SMP_CreateLocalSecureConnectionsOobData(
+ tBLE_BD_ADDR* addr_to_send_to);
// Called when LTK request is received from controller.
extern bool smp_proc_ltk_request(const RawAddress& bda);
-// Called when link is encrypted and notified to peripheral device.
-// Proceed to send LTK, DIV and ER to central if bonding the devices.
+// Called when link is encrypted and notified to slave device.
+// Proceed to send LTK, DIV and ER to master if bonding the devices.
extern void smp_link_encrypted(const RawAddress& bda, uint8_t encr_enable);
#endif /* SMP_API_H */
diff --git a/stack/include/smp_api_types.h b/stack/include/smp_api_types.h
index c144973d3..96e7d9efd 100644
--- a/stack/include/smp_api_types.h
+++ b/stack/include/smp_api_types.h
@@ -19,121 +19,93 @@
#ifndef SMP_API_TYPES_H
#define SMP_API_TYPES_H
-#include "bt_target.h" // Must be first to define build configuration
+#include "bt_target.h"
-#include "stack/include/btm_status.h"
-#include "types/ble_address_with_type.h"
+#define SMP_PIN_CODE_LEN_MAX PIN_CODE_LEN
+#define SMP_PIN_CODE_LEN_MIN 6
/* SMP command code */
-typedef enum : uint8_t {
- SMP_OPCODE_PAIRING_REQ = 0x01,
- SMP_OPCODE_PAIRING_RSP = 0x02,
- SMP_OPCODE_CONFIRM = 0x03,
- SMP_OPCODE_RAND = 0x04,
- SMP_OPCODE_PAIRING_FAILED = 0x05,
- SMP_OPCODE_ENCRYPT_INFO = 0x06,
- SMP_OPCODE_CENTRAL_ID = 0x07,
- SMP_OPCODE_IDENTITY_INFO = 0x08,
- SMP_OPCODE_ID_ADDR = 0x09,
- SMP_OPCODE_SIGN_INFO = 0x0A,
- SMP_OPCODE_SEC_REQ = 0x0B,
- SMP_OPCODE_PAIR_PUBLIC_KEY = 0x0C,
- SMP_OPCODE_PAIR_DHKEY_CHECK = 0x0D,
- SMP_OPCODE_PAIR_KEYPR_NOTIF = 0x0E,
- SMP_OPCODE_MAX = SMP_OPCODE_PAIR_KEYPR_NOTIF,
- SMP_OPCODE_MIN = SMP_OPCODE_PAIRING_REQ,
- // NOTE: For some reason this is outside the MAX/MIN values
- SMP_OPCODE_PAIR_COMMITM = 0x0F,
-} tSMP_OPCODE;
-
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string smp_opcode_text(const tSMP_OPCODE& opcode) {
- switch (opcode) {
- CASE_RETURN_TEXT(SMP_OPCODE_PAIRING_REQ);
- CASE_RETURN_TEXT(SMP_OPCODE_PAIRING_RSP);
- CASE_RETURN_TEXT(SMP_OPCODE_CONFIRM);
- CASE_RETURN_TEXT(SMP_OPCODE_RAND);
- CASE_RETURN_TEXT(SMP_OPCODE_PAIRING_FAILED);
- CASE_RETURN_TEXT(SMP_OPCODE_ENCRYPT_INFO);
- CASE_RETURN_TEXT(SMP_OPCODE_CENTRAL_ID);
- CASE_RETURN_TEXT(SMP_OPCODE_IDENTITY_INFO);
- CASE_RETURN_TEXT(SMP_OPCODE_ID_ADDR);
- CASE_RETURN_TEXT(SMP_OPCODE_SIGN_INFO);
- CASE_RETURN_TEXT(SMP_OPCODE_SEC_REQ);
- CASE_RETURN_TEXT(SMP_OPCODE_PAIR_PUBLIC_KEY);
- CASE_RETURN_TEXT(SMP_OPCODE_PAIR_DHKEY_CHECK);
- CASE_RETURN_TEXT(SMP_OPCODE_PAIR_KEYPR_NOTIF);
- CASE_RETURN_TEXT(SMP_OPCODE_PAIR_COMMITM);
- default:
- return std::string("UNKNOWN:%hhu", opcode);
- }
-}
-#undef CASE_RETURN_TEXT
+#define SMP_OPCODE_PAIRING_REQ 0x01
+#define SMP_OPCODE_PAIRING_RSP 0x02
+#define SMP_OPCODE_CONFIRM 0x03
+#define SMP_OPCODE_RAND 0x04
+#define SMP_OPCODE_PAIRING_FAILED 0x05
+#define SMP_OPCODE_ENCRYPT_INFO 0x06
+#define SMP_OPCODE_MASTER_ID 0x07
+#define SMP_OPCODE_IDENTITY_INFO 0x08
+#define SMP_OPCODE_ID_ADDR 0x09
+#define SMP_OPCODE_SIGN_INFO 0x0A
+#define SMP_OPCODE_SEC_REQ 0x0B
+#define SMP_OPCODE_PAIR_PUBLIC_KEY 0x0C
+#define SMP_OPCODE_PAIR_DHKEY_CHECK 0x0D
+#define SMP_OPCODE_PAIR_KEYPR_NOTIF 0x0E
+#define SMP_OPCODE_MAX SMP_OPCODE_PAIR_KEYPR_NOTIF
+#define SMP_OPCODE_MIN SMP_OPCODE_PAIRING_REQ
+#define SMP_OPCODE_PAIR_COMMITM 0x0F
/* SMP event type */
-typedef enum : uint8_t {
- SMP_EVT_NONE = 0, /* Default no event */
- SMP_IO_CAP_REQ_EVT = 1, /* IO capability request event */
- SMP_SEC_REQUEST_EVT = 2, /* SMP pairing request */
- SMP_PASSKEY_NOTIF_EVT = 3, /* passkey notification event */
- SMP_PASSKEY_REQ_EVT = 4, /* passkey request event */
- SMP_OOB_REQ_EVT = 5, /* OOB request event */
- SMP_NC_REQ_EVT = 6, /* Numeric Comparison request event */
- SMP_COMPLT_EVT = 7, /* SMP complete event */
- SMP_PEER_KEYPR_NOT_EVT = 8, /* Peer keypress notification */
-
- /* SC OOB request event (both local and peer OOB data can be expected in
- * response) */
- SMP_SC_OOB_REQ_EVT = 9,
- /* SC OOB local data set is created (as result of SMP_CrLocScOobData(...)) */
- SMP_SC_LOC_OOB_DATA_UP_EVT = 10,
- SMP_UNUSED11 = 11,
- SMP_BR_KEYS_REQ_EVT = 12, /* SMP over BR keys request event */
- SMP_UNUSED13 = 13,
- SMP_CONSENT_REQ_EVT = 14, /* Consent request event */
-} tSMP_EVT;
+#define SMP_IO_CAP_REQ_EVT 1 /* IO capability request event */
+#define SMP_SEC_REQUEST_EVT 2 /* SMP pairing request */
+#define SMP_PASSKEY_NOTIF_EVT 3 /* passkey notification event */
+#define SMP_PASSKEY_REQ_EVT 4 /* passkey request event */
+#define SMP_OOB_REQ_EVT 5 /* OOB request event */
+#define SMP_NC_REQ_EVT 6 /* Numeric Comparison request event */
+#define SMP_COMPLT_EVT 7 /* SMP complete event */
+#define SMP_PEER_KEYPR_NOT_EVT 8 /* Peer keypress notification */
+
+/* SC OOB request event (both local and peer OOB data can be expected in
+ * response) */
+#define SMP_SC_OOB_REQ_EVT 9
+/* SC OOB local data set is created (as result of SMP_CrLocScOobData(...)) */
+#define SMP_SC_LOC_OOB_DATA_UP_EVT 10
+#define SMP_BR_KEYS_REQ_EVT 12 /* SMP over BR keys request event */
+#define SMP_CONSENT_REQ_EVT 14 /* Consent request event */
+typedef uint8_t tSMP_EVT;
/* pairing failure reason code */
-typedef enum : uint8_t {
- SMP_SUCCESS = 0,
- SMP_PASSKEY_ENTRY_FAIL = 0x01,
- SMP_OOB_FAIL = 0x02,
- SMP_PAIR_AUTH_FAIL = 0x03,
- SMP_CONFIRM_VALUE_ERR = 0x04,
- SMP_PAIR_NOT_SUPPORT = 0x05,
- SMP_ENC_KEY_SIZE = 0x06,
- SMP_INVALID_CMD = 0x07,
- SMP_PAIR_FAIL_UNKNOWN = 0x08,
- SMP_REPEATED_ATTEMPTS = 0x09,
- SMP_INVALID_PARAMETERS = 0x0A,
- SMP_DHKEY_CHK_FAIL = 0x0B,
- SMP_NUMERIC_COMPAR_FAIL = 0x0C,
- SMP_BR_PARING_IN_PROGR = 0x0D,
- SMP_XTRANS_DERIVE_NOT_ALLOW = 0x0E,
- SMP_MAX_FAIL_RSN_PER_SPEC = SMP_XTRANS_DERIVE_NOT_ALLOW,
-
- /* self defined error code */
- SMP_PAIR_INTERNAL_ERR = (SMP_MAX_FAIL_RSN_PER_SPEC + 0x01), /* 0x0F */
-
- /* Unknown IO capability, unable to decide association model */
- SMP_UNKNOWN_IO_CAP = (SMP_MAX_FAIL_RSN_PER_SPEC + 0x02), /* 0x10 */
-
- SMP_BUSY = (SMP_MAX_FAIL_RSN_PER_SPEC + 0x05), /* 0x13 */
- SMP_ENC_FAIL = (SMP_MAX_FAIL_RSN_PER_SPEC + 0x06), /* 0x14 */
- SMP_STARTED = (SMP_MAX_FAIL_RSN_PER_SPEC + 0x07), /* 0x15 */
- SMP_RSP_TIMEOUT = (SMP_MAX_FAIL_RSN_PER_SPEC + 0x08), /* 0x16 */
-
- /* Unspecified failure reason */
- SMP_FAIL = (SMP_MAX_FAIL_RSN_PER_SPEC + 0x0A), /* 0x18 */
-
- SMP_CONN_TOUT = (SMP_MAX_FAIL_RSN_PER_SPEC + 0x0B), /* 0x19 */
-} tSMP_STATUS;
+#define SMP_PASSKEY_ENTRY_FAIL 0x01
+#define SMP_OOB_FAIL 0x02
+#define SMP_PAIR_AUTH_FAIL 0x03
+#define SMP_CONFIRM_VALUE_ERR 0x04
+#define SMP_PAIR_NOT_SUPPORT 0x05
+#define SMP_ENC_KEY_SIZE 0x06
+#define SMP_INVALID_CMD 0x07
+#define SMP_PAIR_FAIL_UNKNOWN 0x08
+#define SMP_REPEATED_ATTEMPTS 0x09
+#define SMP_INVALID_PARAMETERS 0x0A
+#define SMP_DHKEY_CHK_FAIL 0x0B
+#define SMP_NUMERIC_COMPAR_FAIL 0x0C
+#define SMP_BR_PARING_IN_PROGR 0x0D
+#define SMP_XTRANS_DERIVE_NOT_ALLOW 0x0E
+#define SMP_MAX_FAIL_RSN_PER_SPEC SMP_XTRANS_DERIVE_NOT_ALLOW
+
+/* self defined error code */
+#define SMP_PAIR_INTERNAL_ERR (SMP_MAX_FAIL_RSN_PER_SPEC + 0x01) /* 0x0F */
+
+/* Unknown IO capability, unable to decide association model */
+#define SMP_UNKNOWN_IO_CAP (SMP_MAX_FAIL_RSN_PER_SPEC + 0x02) /* 0x10 */
+
+#define SMP_INIT_FAIL (SMP_MAX_FAIL_RSN_PER_SPEC + 0x03) /* 0x11 */
+#define SMP_CONFIRM_FAIL (SMP_MAX_FAIL_RSN_PER_SPEC + 0x04) /* 0x12 */
+#define SMP_BUSY (SMP_MAX_FAIL_RSN_PER_SPEC + 0x05) /* 0x13 */
+#define SMP_ENC_FAIL (SMP_MAX_FAIL_RSN_PER_SPEC + 0x06) /* 0x14 */
+#define SMP_STARTED (SMP_MAX_FAIL_RSN_PER_SPEC + 0x07) /* 0x15 */
+#define SMP_RSP_TIMEOUT (SMP_MAX_FAIL_RSN_PER_SPEC + 0x08) /* 0x16 */
+#define SMP_DIV_NOT_AVAIL (SMP_MAX_FAIL_RSN_PER_SPEC + 0x09) /* 0x17 */
+
+/* Unspecified failure reason */
+#define SMP_FAIL (SMP_MAX_FAIL_RSN_PER_SPEC + 0x0A) /* 0x18 */
+
+#define SMP_CONN_TOUT (SMP_MAX_FAIL_RSN_PER_SPEC + 0x0B) /* 0x19 */
+#define SMP_SUCCESS 0
+
+typedef uint8_t tSMP_STATUS;
/* Device IO capability */
+#define SMP_IO_CAP_OUT BTM_IO_CAP_OUT /* DisplayOnly */
#define SMP_IO_CAP_IO BTM_IO_CAP_IO /* DisplayYesNo */
+#define SMP_IO_CAP_IN BTM_IO_CAP_IN /* KeyboardOnly */
+#define SMP_IO_CAP_NONE BTM_IO_CAP_NONE /* NoInputNoOutput */
#define SMP_IO_CAP_KBDISP BTM_IO_CAP_KBDISP /* Keyboard Display */
#define SMP_IO_CAP_MAX BTM_IO_CAP_MAX
typedef uint8_t tSMP_IO_CAP;
@@ -146,30 +118,50 @@ typedef uint8_t tSMP_OOB_FLAG;
enum { SMP_OOB_INVALID_TYPE, SMP_OOB_PEER, SMP_OOB_LOCAL, SMP_OOB_BOTH };
typedef uint8_t tSMP_OOB_DATA_TYPE;
-enum : uint8_t {
- SMP_AUTH_NO_BOND = 0x00,
- /* no MITM, No Bonding, encryption only */
- SMP_AUTH_NB_ENC_ONLY = 0x00, //(SMP_AUTH_MASK | BTM_AUTH_SP_NO)
- SMP_AUTH_BOND = (1u << 0),
- SMP_AUTH_UNUSED = (1u << 1),
- /* SMP Authentication requirement */
- SMP_AUTH_YN_BIT = (1u << 2),
- SMP_SC_SUPPORT_BIT = (1u << 3),
- SMP_KP_SUPPORT_BIT = (1u << 4),
- SMP_H7_SUPPORT_BIT = (1u << 5),
-};
+#define SMP_AUTH_NO_BOND 0x00
+#define SMP_AUTH_BOND 0x01
+
+/* SMP Authentication requirement */
+#define SMP_AUTH_YN_BIT (1 << 2)
+#define SMP_SC_SUPPORT_BIT (1 << 3)
+#define SMP_KP_SUPPORT_BIT (1 << 4)
+#define SMP_H7_SUPPORT_BIT (1 << 5)
#define SMP_AUTH_MASK \
(SMP_AUTH_BOND | SMP_AUTH_YN_BIT | SMP_SC_SUPPORT_BIT | SMP_KP_SUPPORT_BIT | \
SMP_H7_SUPPORT_BIT)
+/* no MITM, No Bonding, encryption only */
+#define SMP_AUTH_NB_ENC_ONLY 0x00 //(SMP_AUTH_MASK | BTM_AUTH_SP_NO)
+
+/* MITM, No Bonding, Use IO Capability to determine authentication procedure */
+#define SMP_AUTH_NB_IOCAP (SMP_AUTH_NO_BOND | SMP_AUTH_YN_BIT)
+
+/* No MITM, General Bonding, Encryption only */
+#define SMP_AUTH_GB_ENC_ONLY SMP_AUTH_BOND
+
+/* MITM, General Bonding, Use IO Capability to determine authentication
+ * procedure */
+#define SMP_AUTH_GB_IOCAP (SMP_AUTH_BOND | SMP_AUTH_YN_BIT)
+
/* Secure Connections, no MITM, no Bonding */
#define SMP_AUTH_SC_ENC_ONLY (SMP_H7_SUPPORT_BIT | SMP_SC_SUPPORT_BIT)
+/* Secure Connections, no MITM, Bonding */
+#define SMP_AUTH_SC_GB (SMP_H7_SUPPORT_BIT | SMP_SC_SUPPORT_BIT | SMP_AUTH_BOND)
+
+/* Secure Connections, MITM, no Bonding */
+#define SMP_AUTH_SC_MITM_NB \
+ (SMP_H7_SUPPORT_BIT | SMP_SC_SUPPORT_BIT | SMP_AUTH_YN_BIT | SMP_AUTH_NO_BOND)
+
/* Secure Connections, MITM, Bonding */
#define SMP_AUTH_SC_MITM_GB \
(SMP_H7_SUPPORT_BIT | SMP_SC_SUPPORT_BIT | SMP_AUTH_YN_BIT | SMP_AUTH_BOND)
+/* All AuthReq RFU bits are set to 1 - NOTE: reserved bit in Bonding_Flags is
+ * not set */
+#define SMP_AUTH_ALL_RFU_SET 0xF8
+
typedef uint8_t tSMP_AUTH_REQ;
#define SMP_SEC_NONE 0
@@ -184,7 +176,7 @@ typedef uint8_t tSMP_SEC_LEVEL;
/* SMP key types */
#define SMP_SEC_KEY_TYPE_ENC (1 << 0) /* encryption key */
#define SMP_SEC_KEY_TYPE_ID (1 << 1) /* identity key */
-#define SMP_SEC_KEY_TYPE_CSRK (1 << 2) /* peripheral CSRK */
+#define SMP_SEC_KEY_TYPE_CSRK (1 << 2) /* slave CSRK */
#define SMP_SEC_KEY_TYPE_LK (1 << 3) /* BR/EDR link key */
typedef uint8_t tSMP_KEYS;
@@ -196,6 +188,11 @@ typedef uint8_t tSMP_KEYS;
(SMP_SEC_KEY_TYPE_ENC | SMP_SEC_KEY_TYPE_ID | SMP_SEC_KEY_TYPE_CSRK | \
SMP_SEC_KEY_TYPE_LK)
+#define SMP_SC_KEY_STARTED 0 /* passkey entry started */
+#define SMP_SC_KEY_ENTERED 1 /* passkey digit entered */
+#define SMP_SC_KEY_ERASED 2 /* passkey digit erased */
+#define SMP_SC_KEY_CLEARED 3 /* passkey cleared */
+#define SMP_SC_KEY_COMPLT 4 /* passkey entry completed */
#define SMP_SC_KEY_OUT_OF_RANGE 5 /* out of range */
typedef uint8_t tSMP_SC_KEY_TYPE;
@@ -266,7 +263,12 @@ typedef struct {
/* Security Manager events - Called by the stack when Security Manager related
* events occur.*/
-typedef tBTM_STATUS(tSMP_CALLBACK)(tSMP_EVT event, const RawAddress& bd_addr,
- tSMP_EVT_DATA* p_data);
+typedef uint8_t(tSMP_CALLBACK)(tSMP_EVT event, const RawAddress& bd_addr,
+ tSMP_EVT_DATA* p_data);
+
+/* callback function for CMAC algorithm
+*/
+typedef void(tCMAC_CMPL_CBACK)(uint8_t* p_mac, uint16_t tlen,
+ uint32_t sign_counter);
#endif // SMP_API_TYPES_H
diff --git a/stack/include/srvc_api.h b/stack/include/srvc_api.h
index dad6909bb..ad01237fd 100644
--- a/stack/include/srvc_api.h
+++ b/stack/include/srvc_api.h
@@ -22,7 +22,6 @@
#include "bt_target.h"
#include "gatt_api.h"
#include "gattdefs.h"
-#include "types/bt_transport.h"
#define DIS_SUCCESS GATT_SUCCESS
#define DIS_ILLEGAL_PARAM GATT_ILLEGAL_PARAMETER
@@ -44,6 +43,8 @@ typedef uint8_t tDIS_STATUS;
#define DIS_ATTR_PNP_ID_BIT 0x0100
typedef uint16_t tDIS_ATTR_MASK;
+#define DIS_ATTR_ALL_MASK 0xffff
+
typedef tDIS_ATTR_MASK tDIS_ATTR_BIT;
typedef struct {
@@ -101,7 +102,7 @@ typedef uint8_t tBA_LEVEL_DESCR;
typedef struct {
bool is_pri;
tBA_LEVEL_DESCR ba_level_descr;
- tBT_TRANSPORT transport;
+ tGATT_TRANSPORT transport;
tBA_CBACK* p_cback;
} tBA_REG_INFO;
diff --git a/stack/include/stack_metrics_logging.h b/stack/include/stack_metrics_logging.h
deleted file mode 100644
index 20c28530f..000000000
--- a/stack/include/stack_metrics_logging.h
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
-
-#include "types/raw_address.h"
-
-void log_classic_pairing_event(const RawAddress& address, uint16_t handle,
- uint32_t hci_cmd, uint16_t hci_event,
- uint16_t cmd_status, uint16_t reason_code,
- int64_t event_value);
-
-void log_link_layer_connection_event(
- const RawAddress* address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction, uint16_t link_type,
- uint32_t hci_cmd, uint16_t hci_event, uint16_t hci_ble_event,
- uint16_t cmd_status, uint16_t reason_code);
-
-void log_smp_pairing_event(const RawAddress& address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason);
-
-void log_sdp_attribute(const RawAddress& address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value);
-
-void log_manufacturer_info(const RawAddress& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer,
- const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version); \ No newline at end of file
diff --git a/stack/l2cap/l2c_api.cc b/stack/l2cap/l2c_api.cc
index c8f2659ef..38b0ee868 100644
--- a/stack/l2cap/l2c_api.cc
+++ b/stack/l2cap/l2c_api.cc
@@ -26,38 +26,26 @@
#include <base/logging.h>
#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <string>
-
-#include "btm_sec.h"
-#include "device/include/controller.h" // TODO Remove
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "bt_common.h"
+#include "bt_types.h"
+#include "btm_api.h"
+#include "btu.h"
+#include "device/include/controller.h"
+#include "hcidefs.h"
+#include "hcimsgs.h"
+#include "l2c_int.h"
+#include "l2cdefs.h"
#include "main/shim/l2c_api.h"
#include "main/shim/shim.h"
+#include "osi/include/allocator.h"
#include "osi/include/log.h"
-#include "stack/include/l2c_api.h"
-#include "stack/l2cap/l2c_int.h"
-
-void btsnd_hcic_enhanced_flush(uint16_t handle,
- uint8_t packet_type); // TODO Remove
using base::StringPrintf;
-tBT_TRANSPORT l2c_get_transport_from_fixed_cid(uint16_t fixed_cid) {
- if (fixed_cid >= L2CAP_ATT_CID && fixed_cid <= L2CAP_SMP_CID)
- return BT_TRANSPORT_LE;
- return BT_TRANSPORT_BR_EDR;
-}
-
-uint16_t L2CA_Register2(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level) {
- auto ret = L2CA_Register(psm, p_cb_info, enable_snoop, p_ertm_info, my_mtu,
- required_remote_mtu, sec_level);
- BTM_SetSecurityLevel(false, "", 0, sec_level, psm, 0, 0);
- return ret;
-}
-
/*******************************************************************************
*
* Function L2CA_Register
@@ -72,52 +60,45 @@ uint16_t L2CA_Register2(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
* L2CA_ErtmConnectReq() and L2CA_Deregister()
*
******************************************************************************/
-uint16_t L2CA_Register(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+uint16_t L2CA_Register(uint16_t psm, tL2CAP_APPL_INFO* p_cb_info,
+ bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_Register(psm, p_cb_info, enable_snoop,
- p_ertm_info, my_mtu,
- required_remote_mtu, sec_level);
+ p_ertm_info);
}
- const bool config_cfm_cb = (p_cb_info.pL2CA_ConfigCfm_Cb != nullptr);
- const bool config_ind_cb = (p_cb_info.pL2CA_ConfigInd_Cb != nullptr);
- const bool data_ind_cb = (p_cb_info.pL2CA_DataInd_Cb != nullptr);
- const bool disconnect_ind_cb = (p_cb_info.pL2CA_DisconnectInd_Cb != nullptr);
-
tL2C_RCB* p_rcb;
uint16_t vpsm = psm;
+ L2CAP_TRACE_API("L2CAP - L2CA_Register() called for PSM: 0x%04x", psm);
+
/* Verify that the required callback info has been filled in
** Note: Connection callbacks are required but not checked
** for here because it is possible to be only a client
** or only a server.
*/
- if (!config_cfm_cb || !data_ind_cb || !disconnect_ind_cb) {
- LOG_ERROR(
- "L2CAP - no cb registering PSM: 0x%04x cfg_cfm:%u cfg_ind:%u"
- " data_ind:%u discon_int:%u",
- psm, config_cfm_cb, config_ind_cb, data_ind_cb, disconnect_ind_cb);
+ if ((!p_cb_info->pL2CA_ConfigCfm_Cb) || (!p_cb_info->pL2CA_ConfigInd_Cb) ||
+ (!p_cb_info->pL2CA_DataInd_Cb) || (!p_cb_info->pL2CA_DisconnectInd_Cb)) {
+ L2CAP_TRACE_ERROR("L2CAP - no cb registering PSM: 0x%04x", psm);
return (0);
}
/* Verify PSM is valid */
if (L2C_INVALID_PSM(psm)) {
- LOG_ERROR("L2CAP - invalid PSM value, PSM: 0x%04x", psm);
+ L2CAP_TRACE_ERROR("L2CAP - invalid PSM value, PSM: 0x%04x", psm);
return (0);
}
/* Check if this is a registration for an outgoing-only connection to */
/* a dynamic PSM. If so, allocate a "virtual" PSM for the app to use. */
- if ((psm >= 0x1001) && (p_cb_info.pL2CA_ConnectInd_Cb == NULL)) {
+ if ((psm >= 0x1001) && (p_cb_info->pL2CA_ConnectInd_Cb == NULL)) {
for (vpsm = 0x1002; vpsm < 0x8000; vpsm += 2) {
p_rcb = l2cu_find_rcb_by_psm(vpsm);
if (p_rcb == NULL) break;
}
- LOG_DEBUG("L2CAP - Real PSM: 0x%04x Virtual PSM: 0x%04x", psm, vpsm);
+ L2CAP_TRACE_API("L2CA_Register - Real PSM: 0x%04x Virtual PSM: 0x%04x",
+ psm, vpsm);
}
/* If registration block already there, just overwrite it */
@@ -125,22 +106,15 @@ uint16_t L2CA_Register(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
if (p_rcb == NULL) {
p_rcb = l2cu_allocate_rcb(vpsm);
if (p_rcb == NULL) {
- LOG_WARN("L2CAP - no RCB available, PSM: 0x%04x vPSM: 0x%04x", psm,
- vpsm);
+ L2CAP_TRACE_WARNING("L2CAP - no RCB available, PSM: 0x%04x vPSM: 0x%04x",
+ psm, vpsm);
return (0);
}
}
- LOG_INFO("L2CAP Registered service classic PSM: 0x%04x", psm);
p_rcb->log_packets = enable_snoop;
- p_rcb->api = p_cb_info;
+ p_rcb->api = *p_cb_info;
p_rcb->real_psm = psm;
- p_rcb->ertm_info = p_ertm_info == nullptr
- ? tL2CAP_ERTM_INFO{L2CAP_FCR_BASIC_MODE}
- : *p_ertm_info;
- p_rcb->my_mtu = my_mtu;
- p_rcb->required_remote_mtu =
- std::max<uint16_t>(required_remote_mtu, L2CAP_MIN_MTU);
return (vpsm);
}
@@ -156,7 +130,7 @@ uint16_t L2CA_Register(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
*
******************************************************************************/
void L2CA_Deregister(uint16_t psm) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_Deregister(psm);
}
@@ -197,6 +171,46 @@ void L2CA_Deregister(uint16_t psm) {
/*******************************************************************************
*
+ * Function L2CA_AllocatePSM
+ *
+ * Description Other layers call this function to find an unused PSM for
+ * L2CAP services.
+ *
+ * Returns PSM to use.
+ *
+ ******************************************************************************/
+uint16_t L2CA_AllocatePSM(void) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_AllocatePSM();
+ }
+
+ bool done = false;
+ uint16_t psm = l2cb.dyn_psm;
+
+ L2CAP_TRACE_API("L2CA_AllocatePSM");
+ while (!done) {
+ psm += 2;
+ if (psm > 0xfeff) {
+ psm = 0x1001;
+ } else if (psm & 0x0100) {
+ /* the upper byte must be even */
+ psm += 0x0100;
+ }
+
+ /* if psm is in range of reserved BRCM Aware features */
+ if ((BRCM_RESERVED_PSM_START <= psm) && (psm <= BRCM_RESERVED_PSM_END))
+ continue;
+
+ /* make sure the newlly allocated psm is not used right now */
+ if ((l2cu_find_rcb_by_psm(psm)) == NULL) done = true;
+ }
+ l2cb.dyn_psm = psm;
+
+ return (psm);
+}
+
+/*******************************************************************************
+ *
* Function L2CA_AllocateLePSM
*
* Description To find an unused LE PSM for L2CAP services.
@@ -205,7 +219,7 @@ void L2CA_Deregister(uint16_t psm) {
*
******************************************************************************/
uint16_t L2CA_AllocateLePSM(void) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_AllocateLePSM();
}
@@ -255,7 +269,7 @@ uint16_t L2CA_AllocateLePSM(void) {
*
******************************************************************************/
void L2CA_FreeLePSM(uint16_t psm) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_FreeLePSM(psm);
}
@@ -272,32 +286,54 @@ void L2CA_FreeLePSM(uint16_t psm) {
l2cb.le_dyn_psm_assigned[psm - LE_DYNAMIC_PSM_START] = false;
}
-uint16_t L2CA_ConnectReq2(uint16_t psm, const RawAddress& p_bd_addr,
- uint16_t sec_level) {
- BTM_SetSecurityLevel(true, "", 0, sec_level, psm, 0, 0);
- return L2CA_ConnectReq(psm, p_bd_addr);
-}
-
/*******************************************************************************
*
* Function L2CA_ConnectReq
*
* Description Higher layers call this function to create an L2CAP
- * connection.
- * Note that the connection is not established at this time,
- * but connection establishment gets started. The callback
- * will be invoked when connection establishes or fails.
+ * connection. Note that the connection is not established at
+ * this time, but connection establishment gets started. The
+ * callback function will be invoked when connection
+ * establishes or fails.
*
* Returns the CID of the connection, or 0 if it failed to start
*
******************************************************************************/
uint16_t L2CA_ConnectReq(uint16_t psm, const RawAddress& p_bd_addr) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_ConnectReq(psm, p_bd_addr);
}
+ return L2CA_ErtmConnectReq(psm, p_bd_addr, nullptr);
+}
+
+/*******************************************************************************
+ *
+ * Function L2CA_ErtmConnectReq
+ *
+ * Description Higher layers call this function to create an L2CAP
+ * connection. Note that the connection is not established at
+ * this time, but connection establishment gets started. The
+ * callback function will be invoked when connection
+ * establishes or fails.
+ *
+ * Parameters: PSM: L2CAP PSM for the connection
+ * BD address of the peer
+ * Enhaced retransmission mode configurations
+
+ * Returns the CID of the connection, or 0 if it failed to start
+ *
+ ******************************************************************************/
+uint16_t L2CA_ErtmConnectReq(uint16_t psm, const RawAddress& p_bd_addr,
+ tL2CAP_ERTM_INFO* p_ertm_info) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_ErtmConnectReq(psm, p_bd_addr, p_ertm_info);
+ }
+
VLOG(1) << __func__ << "BDA " << p_bd_addr
- << StringPrintf(" PSM: 0x%04x", psm);
+ << StringPrintf(" PSM: 0x%04x allowed:0x%x preferred:%d", psm,
+ (p_ertm_info) ? p_ertm_info->allowed_modes : 0,
+ (p_ertm_info) ? p_ertm_info->preferred_mode : 0);
/* Fail if we have not established communications with the controller */
if (!BTM_IsDeviceUp()) {
@@ -318,13 +354,12 @@ uint16_t L2CA_ConnectReq(uint16_t psm, const RawAddress& p_bd_addr) {
/* No link. Get an LCB and start link establishment */
p_lcb = l2cu_allocate_lcb(p_bd_addr, false, BT_TRANSPORT_BR_EDR);
/* currently use BR/EDR for ERTM mode l2cap connection */
- if (p_lcb == nullptr) {
+ if ((p_lcb == nullptr) || (!l2cu_create_conn_br_edr(p_lcb))) {
LOG(WARNING) << __func__
<< ": connection not started for PSM=" << loghex(psm)
<< ", p_lcb=" << p_lcb;
return 0;
}
- l2cu_create_conn_br_edr(p_lcb);
}
/* Allocate a channel control block */
@@ -337,7 +372,26 @@ uint16_t L2CA_ConnectReq(uint16_t psm, const RawAddress& p_bd_addr) {
/* Save registration info */
p_ccb->p_rcb = p_rcb;
- p_ccb->connection_initiator = L2CAP_INITIATOR_LOCAL;
+ if (p_ertm_info) {
+ p_ccb->ertm_info = *p_ertm_info;
+
+ /* Replace default indicators with the actual default pool */
+ if (p_ccb->ertm_info.fcr_rx_buf_size == L2CAP_INVALID_ERM_BUF_SIZE)
+ p_ccb->ertm_info.fcr_rx_buf_size = L2CAP_FCR_RX_BUF_SIZE;
+
+ if (p_ccb->ertm_info.fcr_tx_buf_size == L2CAP_INVALID_ERM_BUF_SIZE)
+ p_ccb->ertm_info.fcr_tx_buf_size = L2CAP_FCR_TX_BUF_SIZE;
+
+ if (p_ccb->ertm_info.user_rx_buf_size == L2CAP_INVALID_ERM_BUF_SIZE)
+ p_ccb->ertm_info.user_rx_buf_size = L2CAP_USER_RX_BUF_SIZE;
+
+ if (p_ccb->ertm_info.user_tx_buf_size == L2CAP_INVALID_ERM_BUF_SIZE)
+ p_ccb->ertm_info.user_tx_buf_size = L2CAP_USER_TX_BUF_SIZE;
+
+ p_ccb->max_rx_mtu =
+ p_ertm_info->user_rx_buf_size -
+ (L2CAP_MIN_OFFSET + L2CAP_SDU_LEN_OFFSET + L2CAP_FCS_LEN);
+ }
/* If link is up, start the L2CAP connection */
if (p_lcb->link_state == LST_CONNECTED) {
@@ -376,31 +430,26 @@ uint16_t L2CA_ConnectReq(uint16_t psm, const RawAddress& p_bd_addr) {
* and L2CA_DeregisterLECoc()
*
******************************************************************************/
-uint16_t L2CA_RegisterLECoc(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_RegisterLECoc(psm, p_cb_info, sec_level, cfg);
+uint16_t L2CA_RegisterLECoc(uint16_t psm, tL2CAP_APPL_INFO* p_cb_info) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_RegisterLECoc(psm, p_cb_info);
}
- if (p_cb_info.pL2CA_ConnectInd_Cb != nullptr || psm < LE_DYNAMIC_PSM_START) {
- // If we register LE COC for outgoing connection only, don't register with
- // BTM_Sec, because it's handled by L2CA_ConnectLECocReq.
- BTM_SetSecurityLevel(false, "", 0, sec_level, psm, 0, 0);
- }
+ L2CAP_TRACE_API("%s called for LE PSM: 0x%04x", __func__, psm);
/* Verify that the required callback info has been filled in
** Note: Connection callbacks are required but not checked
** for here because it is possible to be only a client
** or only a server.
*/
- if ((!p_cb_info.pL2CA_DataInd_Cb) || (!p_cb_info.pL2CA_DisconnectInd_Cb)) {
- LOG_ERROR("No cb registering BLE PSM: 0x%04x", psm);
+ if ((!p_cb_info->pL2CA_DataInd_Cb) || (!p_cb_info->pL2CA_DisconnectInd_Cb)) {
+ L2CAP_TRACE_ERROR("%s No cb registering BLE PSM: 0x%04x", __func__, psm);
return 0;
}
/* Verify PSM is valid */
if (!L2C_IS_VALID_LE_PSM(psm)) {
- LOG_ERROR("Invalid BLE PSM value, PSM: 0x%04x", psm);
+ L2CAP_TRACE_ERROR("%s Invalid BLE PSM value, PSM: 0x%04x", __func__, psm);
return 0;
}
@@ -410,31 +459,31 @@ uint16_t L2CA_RegisterLECoc(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
/* Check if this is a registration for an outgoing-only connection to */
/* a dynamic PSM. If so, allocate a "virtual" PSM for the app to use. */
if ((psm >= LE_DYNAMIC_PSM_START) &&
- (p_cb_info.pL2CA_ConnectInd_Cb == NULL)) {
+ (p_cb_info->pL2CA_ConnectInd_Cb == NULL)) {
vpsm = L2CA_AllocateLePSM();
if (vpsm == 0) {
- LOG_ERROR("Out of free BLE PSM");
+ L2CAP_TRACE_ERROR("%s: Out of free BLE PSM", __func__);
return 0;
}
- LOG_DEBUG("Real PSM: 0x%04x Virtual PSM: 0x%04x", psm, vpsm);
+ L2CAP_TRACE_API("%s Real PSM: 0x%04x Virtual PSM: 0x%04x", __func__, psm,
+ vpsm);
}
/* If registration block already there, just overwrite it */
p_rcb = l2cu_find_ble_rcb_by_psm(vpsm);
if (p_rcb == NULL) {
- LOG_DEBUG("Allocate rcp for Virtual PSM: 0x%04x", vpsm);
+ L2CAP_TRACE_API("%s Allocate rcp for Virtual PSM: 0x%04x", __func__, vpsm);
p_rcb = l2cu_allocate_ble_rcb(vpsm);
if (p_rcb == NULL) {
- LOG_WARN("No BLE RCB available, PSM: 0x%04x vPSM: 0x%04x", psm, vpsm);
+ L2CAP_TRACE_WARNING("%s No BLE RCB available, PSM: 0x%04x vPSM: 0x%04x",
+ __func__, psm, vpsm);
return 0;
}
}
- LOG_INFO("Registered service LE COC PSM: 0x%04x", psm);
- p_rcb->api = p_cb_info;
+ p_rcb->api = *p_cb_info;
p_rcb->real_psm = psm;
- p_rcb->coc_cfg = cfg;
return vpsm;
}
@@ -450,7 +499,7 @@ uint16_t L2CA_RegisterLECoc(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
*
******************************************************************************/
void L2CA_DeregisterLECoc(uint16_t psm) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_DeregisterLECoc(psm);
}
@@ -499,13 +548,11 @@ void L2CA_DeregisterLECoc(uint16_t psm) {
*
******************************************************************************/
uint16_t L2CA_ConnectLECocReq(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg, uint16_t sec_level) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ tL2CAP_LE_CFG_INFO* p_cfg) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_ConnectLECocReq(psm, p_bd_addr, p_cfg);
}
- BTM_SetSecurityLevel(true, "", 0, sec_level, psm, 0, 0);
-
VLOG(1) << __func__ << " BDA: " << p_bd_addr
<< StringPrintf(" PSM: 0x%04x", psm);
@@ -546,11 +593,9 @@ uint16_t L2CA_ConnectLECocReq(uint16_t psm, const RawAddress& p_bd_addr,
/* Save registration info */
p_ccb->p_rcb = p_rcb;
- p_ccb->connection_initiator = L2CAP_INITIATOR_LOCAL;
-
/* Save the configuration */
if (p_cfg) {
- p_ccb->local_conn_cfg = *p_cfg;
+ memcpy(&p_ccb->local_conn_cfg, p_cfg, sizeof(tL2CAP_LE_CFG_INFO));
p_ccb->remote_credit_count = p_cfg->credits;
}
@@ -584,6 +629,69 @@ uint16_t L2CA_ConnectLECocReq(uint16_t psm, const RawAddress& p_bd_addr,
/*******************************************************************************
*
+ * Function L2CA_ConnectLECocRsp
+ *
+ * Description Higher layers call this function to accept an incoming
+ * L2CAP COC connection, for which they had gotten an connect
+ * indication callback.
+ *
+ * Returns true for success, false for failure
+ *
+ ******************************************************************************/
+bool L2CA_ConnectLECocRsp(const RawAddress& p_bd_addr, uint8_t id,
+ uint16_t lcid, uint16_t result, uint16_t status,
+ tL2CAP_LE_CFG_INFO* p_cfg) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_ConnectLECocRsp(p_bd_addr, id, lcid, result,
+ status, p_cfg);
+ }
+
+ VLOG(1) << __func__ << " BDA: " << p_bd_addr
+ << StringPrintf(" CID: 0x%04x Result: %d Status: %d", lcid, result,
+ status);
+
+ /* First, find the link control block */
+ tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(p_bd_addr, BT_TRANSPORT_LE);
+ if (p_lcb == NULL) {
+ /* No link. Get an LCB and start link establishment */
+ L2CAP_TRACE_WARNING("%s no LCB", __func__);
+ return false;
+ }
+
+ /* Now, find the channel control block */
+ tL2C_CCB* p_ccb = l2cu_find_ccb_by_cid(p_lcb, lcid);
+ if (p_ccb == NULL) {
+ L2CAP_TRACE_WARNING("%s no CCB", __func__);
+ return false;
+ }
+
+ /* The IDs must match */
+ if (p_ccb->remote_id != id) {
+ L2CAP_TRACE_WARNING("%s bad id. Expected: %d Got: %d", __func__,
+ p_ccb->remote_id, id);
+ return false;
+ }
+
+ if (p_cfg) {
+ memcpy(&p_ccb->local_conn_cfg, p_cfg, sizeof(tL2CAP_LE_CFG_INFO));
+ p_ccb->remote_credit_count = p_cfg->credits;
+ }
+
+ if (result == L2CAP_CONN_OK)
+ l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONNECT_RSP, NULL);
+ else {
+ tL2C_CONN_INFO conn_info;
+ conn_info.bd_addr = p_bd_addr;
+ conn_info.l2cap_result = result;
+ conn_info.l2cap_status = status;
+ l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONNECT_RSP_NEG, &conn_info);
+ }
+
+ return true;
+}
+
+/*******************************************************************************
+ *
* Function L2CA_GetPeerLECocConfig
*
* Description Get a peers configuration for LE Connection Oriented
@@ -596,7 +704,7 @@ uint16_t L2CA_ConnectLECocReq(uint16_t psm, const RawAddress& p_bd_addr,
*
******************************************************************************/
bool L2CA_GetPeerLECocConfig(uint16_t lcid, tL2CAP_LE_CFG_INFO* peer_cfg) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_GetPeerLECocConfig(lcid, peer_cfg);
}
@@ -616,257 +724,210 @@ bool L2CA_GetPeerLECocConfig(uint16_t lcid, tL2CAP_LE_CFG_INFO* peer_cfg) {
/*******************************************************************************
*
- * Function L2CA_ConnectCreditBasedRsp
+ * Function L2CA_ConnectRsp
+ *
+ * Description Higher layers call this function to accept an incoming
+ * L2CAP connection, for which they had gotten an connect
+ * indication callback.
+ *
+ * Returns true for success, false for failure
+ *
+ ******************************************************************************/
+bool L2CA_ConnectRsp(const RawAddress& p_bd_addr, uint8_t id, uint16_t lcid,
+ uint16_t result, uint16_t status) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_ConnectRsp(p_bd_addr, id, lcid, result,
+ status);
+ }
+
+ return L2CA_ErtmConnectRsp(p_bd_addr, id, lcid, result, status, NULL);
+}
+
+/*******************************************************************************
*
- * Description Response for the pL2CA_CreditBasedConnectInd_Cb which is the
- * indication for peer requesting credit based connection.
+ * Function L2CA_ErtmConnectRsp
*
- * Parameters: BD address of the peer
- * Identifier of the transaction
- * Vector of accepted lcids by upper layer
- * L2CAP result
- * Local channel configuration
+ * Description Higher layers call this function to accept an incoming
+ * L2CAP connection, for which they had gotten an connect
+ * indication callback.
*
* Returns true for success, false for failure
*
******************************************************************************/
-bool L2CA_ConnectCreditBasedRsp(const RawAddress& p_bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids,
- uint16_t result, tL2CAP_LE_CFG_INFO* p_cfg) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_ConnectCreditBasedRsp(
- p_bd_addr, id, accepted_lcids, result, p_cfg);
+bool L2CA_ErtmConnectRsp(const RawAddress& p_bd_addr, uint8_t id, uint16_t lcid,
+ uint16_t result, uint16_t status,
+ tL2CAP_ERTM_INFO* p_ertm_info) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_ErtmConnectRsp(p_bd_addr, id, lcid, result,
+ status, p_ertm_info);
}
+ tL2C_LCB* p_lcb;
+ tL2C_CCB* p_ccb;
+
VLOG(1) << __func__ << " BDA: " << p_bd_addr
- << StringPrintf(" num of cids: %d Result: %d",
- int(accepted_lcids.size()), +result);
+ << StringPrintf(" CID:0x%04x Result:%d Status:%d", lcid, result,
+ status);
/* First, find the link control block */
- tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(p_bd_addr, BT_TRANSPORT_LE);
+ p_lcb = l2cu_find_lcb_by_bd_addr(p_bd_addr, BT_TRANSPORT_BR_EDR);
if (p_lcb == NULL) {
/* No link. Get an LCB and start link establishment */
- L2CAP_TRACE_WARNING("%s no LCB", __func__);
- return false;
+ L2CAP_TRACE_WARNING("L2CAP - no LCB for L2CA_conn_rsp");
+ return (false);
}
- /* Now, find the channel control block. We kept lead cid.
- */
- tL2C_CCB* p_ccb = l2cu_find_ccb_by_cid(p_lcb, p_lcb->pending_lead_cid);
-
- for (uint16_t cid : accepted_lcids) {
- tL2C_CCB* temp_p_ccb = l2cu_find_ccb_by_cid(p_lcb, cid);
- if (temp_p_ccb == NULL) {
- L2CAP_TRACE_WARNING("%s no CCB", __func__);
- return false;
- }
-
- if (p_cfg) {
- temp_p_ccb->local_conn_cfg = *p_cfg;
- temp_p_ccb->remote_credit_count = p_cfg->credits;
- }
+ /* Now, find the channel control block */
+ p_ccb = l2cu_find_ccb_by_cid(p_lcb, lcid);
+ if (p_ccb == NULL) {
+ L2CAP_TRACE_WARNING("L2CAP - no CCB for L2CA_conn_rsp");
+ return (false);
}
/* The IDs must match */
if (p_ccb->remote_id != id) {
- L2CAP_TRACE_WARNING("%s bad id. Expected: %d Got: %d", __func__,
+ L2CAP_TRACE_WARNING("L2CAP - bad id in L2CA_conn_rsp. Exp: %d Got: %d",
p_ccb->remote_id, id);
- return false;
+ return (false);
}
- tL2C_CONN_INFO conn_info;
- conn_info.lcids = accepted_lcids;
- conn_info.bd_addr = p_bd_addr;
- conn_info.l2cap_result = result;
+ if (p_ertm_info) {
+ p_ccb->ertm_info = *p_ertm_info;
+
+ /* Replace default indicators with the actual default pool */
+ if (p_ccb->ertm_info.fcr_rx_buf_size == L2CAP_INVALID_ERM_BUF_SIZE)
+ p_ccb->ertm_info.fcr_rx_buf_size = L2CAP_FCR_RX_BUF_SIZE;
+
+ if (p_ccb->ertm_info.fcr_tx_buf_size == L2CAP_INVALID_ERM_BUF_SIZE)
+ p_ccb->ertm_info.fcr_tx_buf_size = L2CAP_FCR_TX_BUF_SIZE;
+
+ if (p_ccb->ertm_info.user_rx_buf_size == L2CAP_INVALID_ERM_BUF_SIZE)
+ p_ccb->ertm_info.user_rx_buf_size = L2CAP_USER_RX_BUF_SIZE;
+
+ if (p_ccb->ertm_info.user_tx_buf_size == L2CAP_INVALID_ERM_BUF_SIZE)
+ p_ccb->ertm_info.user_tx_buf_size = L2CAP_USER_TX_BUF_SIZE;
- if (accepted_lcids.size() > 0) {
- l2c_csm_execute(p_ccb, L2CEVT_L2CA_CREDIT_BASED_CONNECT_RSP, &conn_info);
+ p_ccb->max_rx_mtu =
+ p_ertm_info->user_rx_buf_size -
+ (L2CAP_MIN_OFFSET + L2CAP_SDU_LEN_OFFSET + L2CAP_FCS_LEN);
+ }
+
+ if (result == L2CAP_CONN_OK) {
+ l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONNECT_RSP, NULL);
} else {
- l2c_csm_execute(p_ccb, L2CEVT_L2CA_CREDIT_BASED_CONNECT_RSP_NEG,
- &conn_info);
+ tL2C_CONN_INFO conn_info;
+
+ conn_info.l2cap_result = result;
+ conn_info.l2cap_status = status;
+
+ if (result == L2CAP_CONN_PENDING)
+ l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONNECT_RSP, &conn_info);
+ else
+ l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONNECT_RSP_NEG, &conn_info);
}
- return true;
+ return (true);
}
+
/*******************************************************************************
*
- * Function L2CA_ConnectCreditBasedReq
+ * Function L2CA_ConfigReq
*
- * Description Initiate Create Credit Based connections.
+ * Description Higher layers call this function to send configuration.
*
- * Parameters: PSM for the L2CAP channel
- * BD address of the peer
- * Local channel configuration
+ * Note: The FCR options of p_cfg are not used.
*
- * Return value: Vector of allocated local cids.
+ * Returns true if configuration sent, else false
*
******************************************************************************/
-
-std::vector<uint16_t> L2CA_ConnectCreditBasedReq(uint16_t psm,
- const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_ConnectCreditBasedReq(psm, p_bd_addr, p_cfg);
- }
-
- VLOG(1) << __func__ << " BDA: " << p_bd_addr
- << StringPrintf(" PSM: 0x%04x", psm);
-
- std::vector<uint16_t> allocated_cids;
-
- /* Fail if we have not established communications with the controller */
- if (!BTM_IsDeviceUp()) {
- L2CAP_TRACE_WARNING("%s BTU not ready", __func__);
- return allocated_cids;
- }
-
- if (!p_cfg) {
- L2CAP_TRACE_WARNING("%s p_cfg is NULL", __func__);
- return allocated_cids;
+bool L2CA_ConfigReq(uint16_t cid, tL2CAP_CFG_INFO* p_cfg) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_ConfigReq(cid, p_cfg);
}
- /* Fail if the PSM is not registered */
- tL2C_RCB* p_rcb = l2cu_find_ble_rcb_by_psm(psm);
- if (p_rcb == NULL) {
- L2CAP_TRACE_WARNING("%s No BLE RCB, PSM: 0x%04x", __func__, psm);
- return allocated_cids;
- }
+ tL2C_CCB* p_ccb;
- /* First, see if we already have a le link to the remote */
- tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(p_bd_addr, BT_TRANSPORT_LE);
- if (p_lcb == NULL) {
- L2CAP_TRACE_WARNING("%s No link available", __func__);
- return allocated_cids;
- }
+ L2CAP_TRACE_API(
+ "L2CA_ConfigReq() CID 0x%04x: fcr_present:%d (mode %d) mtu_present:%d "
+ "(%d)",
+ cid, p_cfg->fcr_present, p_cfg->fcr.mode, p_cfg->mtu_present, p_cfg->mtu);
- if (p_lcb->link_state != LST_CONNECTED) {
- L2CAP_TRACE_WARNING("%s incorrect link state: %d", __func__,
- p_lcb->link_state);
- return allocated_cids;
+ /* Find the channel control block. We don't know the link it is on. */
+ p_ccb = l2cu_find_ccb_by_cid(NULL, cid);
+ if (p_ccb == NULL) {
+ L2CAP_TRACE_WARNING("L2CAP - no CCB for L2CA_cfg_req, CID: %d", cid);
+ return (false);
}
- L2CAP_TRACE_DEBUG("%s LE Link is up", __func__);
+ /* We need to have at least one mode type common with the peer */
+ if (!l2c_fcr_adj_our_req_options(p_ccb, p_cfg)) return (false);
- tL2C_CCB* p_ccb_primary;
+ /* Don't adjust FCR options if not used */
+ if ((!p_cfg->fcr_present) || (p_cfg->fcr.mode == L2CAP_FCR_BASIC_MODE)) {
+ /* FCR and FCS options are not used in basic mode */
+ p_cfg->fcs_present = false;
+ p_cfg->ext_flow_spec_present = false;
- for (int i = 0; i < 5; i++) {
- /* Allocate a channel control block */
- tL2C_CCB* p_ccb = l2cu_allocate_ccb(p_lcb, 0);
- if (p_ccb == NULL) {
- if (i == 0) {
- L2CAP_TRACE_WARNING("%s no CCB, PSM: 0x%04x", __func__, psm);
- return allocated_cids;
- } else {
- break;
- }
+ if ((p_cfg->mtu_present) && (p_cfg->mtu > L2CAP_MTU_SIZE)) {
+ L2CAP_TRACE_WARNING("L2CAP - adjust MTU: %u too large", p_cfg->mtu);
+ p_cfg->mtu = L2CAP_MTU_SIZE;
}
-
- p_ccb->ecoc = true;
- p_ccb->local_conn_cfg = *p_cfg;
- p_ccb->remote_credit_count = p_cfg->credits;
- /* Save registration info */
- p_ccb->p_rcb = p_rcb;
- if (i == 0) {
- p_ccb_primary = p_ccb;
- } else {
- /* Only primary channel we keep in closed state, as in that
- * context we will run state machine where security is checked etc.
- * Others we can directly put into waiting for connect
- * response, so those are not confused by system as incomming connections
- */
- p_ccb->chnl_state = CST_W4_L2CAP_CONNECT_RSP;
- }
-
- allocated_cids.push_back(p_ccb->local_cid);
}
- for (int i = 0; i < (int)(allocated_cids.size()); i++)
- p_lcb->pending_ecoc_connection_cids[i] = allocated_cids[i];
+ /* Save the adjusted configuration in case it needs to be used for
+ * renegotiation */
+ p_ccb->our_cfg = *p_cfg;
- p_lcb->pending_ecoc_conn_cnt = (uint16_t)(allocated_cids.size());
- l2c_csm_execute(p_ccb_primary, L2CEVT_L2CA_CREDIT_BASED_CONNECT_REQ, NULL);
+ l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONFIG_REQ, p_cfg);
- L2CAP_TRACE_API("%s(psm: 0x%04x) returned CID: 0x%04x", __func__, psm,
- p_ccb_primary->local_cid);
-
- return allocated_cids;
+ return (true);
}
/*******************************************************************************
*
- * Function L2CA_ReconfigCreditBasedConnsReq
+ * Function L2CA_ConfigRsp
*
- * Description Start reconfigure procedure on Connection Oriented Channel.
+ * Description Higher layers call this function to send a configuration
+ * response.
*
- * Parameters: Vector of channels for which configuration should be changed
- * New local channel configuration
- *
- * Return value: true if peer is connected
+ * Returns true if configuration response sent, else false
*
******************************************************************************/
-
-bool L2CA_ReconfigCreditBasedConnsReq(const RawAddress& bda,
- std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_ReconfigCreditBasedConnsReq(bda, lcids, p_cfg);
+bool L2CA_ConfigRsp(uint16_t cid, tL2CAP_CFG_INFO* p_cfg) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_ConfigRsp(cid, p_cfg);
}
tL2C_CCB* p_ccb;
- L2CAP_TRACE_API("L2CA_ReconfigCreditBasedConnsReq() ");
+ L2CAP_TRACE_API(
+ "L2CA_ConfigRsp() CID: 0x%04x Result: %d MTU present:%d Flush TO:%d "
+ "FCR:%d FCS:%d",
+ cid, p_cfg->result, p_cfg->mtu_present, p_cfg->flush_to_present,
+ p_cfg->fcr_present, p_cfg->fcs_present);
- if (lcids.empty()) {
- L2CAP_TRACE_WARNING("L2CAP - no lcids given to %s", __func__);
+ /* Find the channel control block. We don't know the link it is on. */
+ p_ccb = l2cu_find_ccb_by_cid(NULL, cid);
+ if (p_ccb == NULL) {
+ L2CAP_TRACE_WARNING("L2CAP - no CCB for L2CA_cfg_rsp, CID: %d", cid);
return (false);
}
- for (uint16_t cid : lcids) {
- p_ccb = l2cu_find_ccb_by_cid(NULL, cid);
+ if ((p_cfg->result == L2CAP_CFG_OK) || (p_cfg->result == L2CAP_CFG_PENDING))
+ l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONFIG_RSP, p_cfg);
+ else {
+ p_cfg->fcr_present =
+ false; /* FCR options already negotiated before this point */
- if (!p_ccb) {
- L2CAP_TRACE_WARNING("L2CAP - no CCB for L2CA_cfg_req, CID: %d", cid);
- return (false);
- }
+ /* Clear out any cached options that are being returned as an error
+ * (excluding FCR) */
+ if (p_cfg->mtu_present) p_ccb->peer_cfg.mtu_present = false;
+ if (p_cfg->flush_to_present) p_ccb->peer_cfg.flush_to_present = false;
+ if (p_cfg->qos_present) p_ccb->peer_cfg.qos_present = false;
- if ((p_ccb->local_conn_cfg.mtu > p_cfg->mtu) ||
- (p_ccb->local_conn_cfg.mps > p_cfg->mps)) {
- L2CAP_TRACE_WARNING("L2CAP - MPS or MTU reduction, CID: %d", cid);
- return (false);
- }
+ l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONFIG_RSP_NEG, p_cfg);
}
- if (p_cfg->mtu > L2CAP_MTU_SIZE) {
- L2CAP_TRACE_WARNING("L2CAP - adjust MTU: %u too large", p_cfg->mtu);
- p_cfg->mtu = L2CAP_MTU_SIZE;
- }
-
- /* Mark all the p_ccbs which going to be reconfigured */
- for (uint16_t cid : lcids) {
- L2CAP_TRACE_API(" cid: %d", cid);
- p_ccb = l2cu_find_ccb_by_cid(NULL, cid);
- if (!p_ccb) {
- LOG(ERROR) << __func__ << "Missing cid? " << int(cid);
- return (false);
- }
- p_ccb->reconfig_started = true;
- }
-
- tL2C_LCB* p_lcb = p_ccb->p_lcb;
-
- /* Hack warning - the whole reconfig we are doing in the context of the first
- * p_ccb. In the p_lcp we store configuration and cid in which context we are
- * doing reconfiguration.
- */
- for (p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb; p_ccb = p_ccb->p_next_ccb)
- if ((p_ccb->in_use) && (p_ccb->ecoc) && (p_ccb->reconfig_started)) {
- p_ccb->p_lcb->pending_ecoc_reconfig_cfg = *p_cfg;
- p_ccb->p_lcb->pending_ecoc_reconfig_cnt = lcids.size();
- break;
- }
-
- l2c_csm_execute(p_ccb, L2CEVT_L2CA_CREDIT_BASED_RECONFIG_REQ, p_cfg);
-
return (true);
}
@@ -880,48 +941,122 @@ bool L2CA_ReconfigCreditBasedConnsReq(const RawAddress& bda,
*
******************************************************************************/
bool L2CA_DisconnectReq(uint16_t cid) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_DisconnectReq(cid);
}
tL2C_CCB* p_ccb;
+ L2CAP_TRACE_API("L2CA_DisconnectReq() CID: 0x%04x", cid);
+
/* Find the channel control block. We don't know the link it is on. */
p_ccb = l2cu_find_ccb_by_cid(NULL, cid);
if (p_ccb == NULL) {
- LOG_WARN("L2CAP - no CCB for L2CA_disc_req, CID: %d", cid);
+ L2CAP_TRACE_WARNING("L2CAP - no CCB for L2CA_disc_req, CID: %d", cid);
return (false);
}
- LOG_DEBUG("L2CAP Local disconnect request CID: 0x%04x", cid);
-
l2c_csm_execute(p_ccb, L2CEVT_L2CA_DISCONNECT_REQ, NULL);
return (true);
}
-bool L2CA_DisconnectLECocReq(uint16_t cid) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_DisconnectLECocReq(cid);
+/*******************************************************************************
+ *
+ * Function L2CA_DisconnectRsp
+ *
+ * Description Higher layers call this function to acknowledge the
+ * disconnection of a channel.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+bool L2CA_DisconnectRsp(uint16_t cid) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_DisconnectRsp(cid);
+ }
+
+ tL2C_CCB* p_ccb;
+
+ L2CAP_TRACE_API("L2CA_DisconnectRsp() CID: 0x%04x", cid);
+
+ /* Find the channel control block. We don't know the link it is on. */
+ p_ccb = l2cu_find_ccb_by_cid(NULL, cid);
+ if (p_ccb == NULL) {
+ L2CAP_TRACE_WARNING("L2CAP - no CCB for L2CA_disc_rsp, CID: %d", cid);
+ return (false);
}
- return L2CA_DisconnectReq(cid);
+
+ l2c_csm_execute(p_ccb, L2CEVT_L2CA_DISCONNECT_RSP, NULL);
+
+ return (true);
}
-bool L2CA_GetRemoteCid(uint16_t lcid, uint16_t* rcid) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_GetRemoteCid(lcid, rcid);
+bool L2CA_GetIdentifiers(uint16_t lcid, uint16_t* rcid, uint16_t* handle) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_GetIdentifiers(lcid, rcid, handle);
}
tL2C_CCB* control_block = l2cu_find_ccb_by_cid(NULL, lcid);
if (!control_block) return false;
if (rcid) *rcid = control_block->remote_cid;
+ if (handle) *handle = control_block->p_lcb->handle;
return true;
}
/*******************************************************************************
*
+ * Function L2CA_SetIdleTimeout
+ *
+ * Description Higher layers call this function to set the idle timeout for
+ * a connection, or for all future connections. The "idle
+ * timeout" is the amount of time that a connection can remain
+ * up with no L2CAP channels on it. A timeout of zero means
+ * that the connection will be torn down immediately when the
+ * last channel is removed. A timeout of 0xFFFF means no
+ * timeout. Values are in seconds.
+ *
+ * Returns true if command succeeded, false if failed
+ *
+ * NOTE This timeout takes effect after at least 1 channel has been
+ * established and removed. L2CAP maintains its own timer from
+ * whan a connection is established till the first channel is
+ * set up.
+ ******************************************************************************/
+bool L2CA_SetIdleTimeout(uint16_t cid, uint16_t timeout, bool is_global) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_SetIdleTimeout(cid, timeout, is_global);
+ }
+
+ tL2C_CCB* p_ccb;
+ tL2C_LCB* p_lcb;
+
+ if (is_global) {
+ l2cb.idle_timeout = timeout;
+ } else {
+ /* Find the channel control block. We don't know the link it is on. */
+ p_ccb = l2cu_find_ccb_by_cid(NULL, cid);
+ if (p_ccb == NULL) {
+ L2CAP_TRACE_WARNING("L2CAP - no CCB for L2CA_SetIdleTimeout, CID: %d",
+ cid);
+ return (false);
+ }
+
+ p_lcb = p_ccb->p_lcb;
+
+ if ((p_lcb) && (p_lcb->in_use) && (p_lcb->link_state == LST_CONNECTED))
+ p_lcb->idle_timeout = timeout;
+ else
+ return (false);
+ }
+
+ return (true);
+}
+
+/*******************************************************************************
+ *
* Function L2CA_SetIdleTimeoutByBdAddr
*
* Description Higher layers call this function to set the idle timeout for
@@ -941,7 +1076,7 @@ bool L2CA_GetRemoteCid(uint16_t lcid, uint16_t* rcid) {
******************************************************************************/
bool L2CA_SetIdleTimeoutByBdAddr(const RawAddress& bd_addr, uint16_t timeout,
tBT_TRANSPORT transport) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_SetIdleTimeoutByBdAddr(bd_addr, timeout,
transport);
}
@@ -990,6 +1125,47 @@ uint8_t L2CA_SetTraceLevel(uint8_t new_level) {
/*******************************************************************************
*
+ * Function L2CA_SetDesireRole
+ *
+ * Description This function sets the desire role for L2CAP.
+ * If the new role is L2CAP_ROLE_ALLOW_SWITCH, allow switch on
+ * HciCreateConnection.
+ * If the new role is L2CAP_ROLE_DISALLOW_SWITCH, do not allow
+ * switch on HciCreateConnection.
+ *
+ * If the new role is a valid role (HCI_ROLE_MASTER or
+ * HCI_ROLE_SLAVE), the desire role is set to the new value.
+ * Otherwise, it is not changed.
+ *
+ * Returns the new (current) role
+ *
+ ******************************************************************************/
+uint8_t L2CA_SetDesireRole(uint8_t new_role) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_SetDesireRole(new_role);
+ }
+
+ L2CAP_TRACE_API("L2CA_SetDesireRole() new:x%x, disallow_switch:%d", new_role,
+ l2cb.disallow_switch);
+
+ if (L2CAP_ROLE_CHECK_SWITCH != (L2CAP_ROLE_CHECK_SWITCH & new_role)) {
+ /* do not process the allow_switch when both bits are set */
+ if (new_role & L2CAP_ROLE_ALLOW_SWITCH) {
+ l2cb.disallow_switch = false;
+ }
+ if (new_role & L2CAP_ROLE_DISALLOW_SWITCH) {
+ l2cb.disallow_switch = true;
+ }
+ }
+
+ if (new_role == HCI_ROLE_MASTER || new_role == HCI_ROLE_SLAVE)
+ l2cb.desire_role = new_role;
+
+ return (l2cb.desire_role);
+}
+
+/*******************************************************************************
+ *
* Function L2CA_SetAclPriority
*
* Description Sets the transmission priority for a channel.
@@ -999,8 +1175,8 @@ uint8_t L2CA_SetTraceLevel(uint8_t new_level) {
* Returns true if a valid channel, else false
*
******************************************************************************/
-bool L2CA_SetAclPriority(const RawAddress& bd_addr, tL2CAP_PRIORITY priority) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+bool L2CA_SetAclPriority(const RawAddress& bd_addr, uint8_t priority) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_SetAclPriority(bd_addr, priority);
}
@@ -1019,7 +1195,7 @@ bool L2CA_SetAclPriority(const RawAddress& bd_addr, tL2CAP_PRIORITY priority) {
*
******************************************************************************/
bool L2CA_SetTxPriority(uint16_t cid, tL2CAP_CHNL_PRIORITY priority) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_SetTxPriority(cid, priority);
}
@@ -1044,6 +1220,105 @@ bool L2CA_SetTxPriority(uint16_t cid, tL2CAP_CHNL_PRIORITY priority) {
/*******************************************************************************
*
+ * Function L2CA_SetFlushTimeout
+ *
+ * Description This function set the automatic flush time out in Baseband
+ * for ACL-U packets.
+ * BdAddr : the remote BD address of ACL link. If it is
+ * BT_DB_ANY then the flush time out will be applied to
+ * all ACL links.
+ * FlushTimeout: flush time out in ms
+ * 0x0000 : No automatic flush
+ * L2CAP_NO_RETRANSMISSION : No retransmission
+ * 0x0002 - 0xFFFE : flush time out, if
+ * (flush_tout * 8) + 3 / 5) <=
+ * HCI_MAX_AUTOMATIC_FLUSH_TIMEOUT
+ * (in 625us slot).
+ * Otherwise, return false.
+ * L2CAP_NO_AUTOMATIC_FLUSH : No automatic flush
+ *
+ * Returns true if command succeeded, false if failed
+ *
+ * NOTE This flush timeout applies to all logical channels active on
+ * the ACL link.
+ ******************************************************************************/
+bool L2CA_SetFlushTimeout(const RawAddress& bd_addr, uint16_t flush_tout) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_SetFlushTimeout(bd_addr, flush_tout);
+ }
+
+ tL2C_LCB* p_lcb;
+ uint16_t hci_flush_to;
+ uint32_t temp;
+
+ /* no automatic flush (infinite timeout) */
+ if (flush_tout == 0x0000) {
+ hci_flush_to = flush_tout;
+ flush_tout = L2CAP_NO_AUTOMATIC_FLUSH;
+ }
+ /* no retransmission */
+ else if (flush_tout == L2CAP_NO_RETRANSMISSION) {
+ /* not mandatory range for controller */
+ /* Packet is flushed before getting any ACK/NACK */
+ /* To do this, flush timeout should be 1 baseband slot */
+ hci_flush_to = flush_tout;
+ }
+ /* no automatic flush (infinite timeout) */
+ else if (flush_tout == L2CAP_NO_AUTOMATIC_FLUSH) {
+ hci_flush_to = 0x0000;
+ } else {
+ /* convert L2CAP flush_to to 0.625 ms units, with round */
+ temp = (((uint32_t)flush_tout * 8) + 3) / 5;
+
+ /* if L2CAP flush_to within range of HCI, set HCI flush timeout */
+ if (temp > HCI_MAX_AUTOMATIC_FLUSH_TIMEOUT) {
+ L2CAP_TRACE_WARNING(
+ "WARNING L2CA_SetFlushTimeout timeout(0x%x) is out of range",
+ flush_tout);
+ return false;
+ } else {
+ hci_flush_to = (uint16_t)temp;
+ }
+ }
+
+ if (RawAddress::kAny != bd_addr) {
+ p_lcb = l2cu_find_lcb_by_bd_addr(bd_addr, BT_TRANSPORT_BR_EDR);
+
+ if ((p_lcb) && (p_lcb->in_use) && (p_lcb->link_state == LST_CONNECTED)) {
+ if (p_lcb->link_flush_tout != flush_tout) {
+ p_lcb->link_flush_tout = flush_tout;
+
+ VLOG(1) << __func__ << " BDA: " << bd_addr << " " << flush_tout << "ms";
+
+ btsnd_hcic_write_auto_flush_tout(p_lcb->handle, hci_flush_to);
+ }
+ } else {
+ LOG(WARNING) << __func__ << " No lcb for bd_addr " << bd_addr;
+ return (false);
+ }
+ } else {
+ int xx;
+ p_lcb = &l2cb.lcb_pool[0];
+
+ for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p_lcb++) {
+ if ((p_lcb->in_use) && (p_lcb->link_state == LST_CONNECTED)) {
+ if (p_lcb->link_flush_tout != flush_tout) {
+ p_lcb->link_flush_tout = flush_tout;
+
+ VLOG(1) << __func__ << " BDA: " << p_lcb->remote_bd_addr << " "
+ << flush_tout << "ms";
+
+ btsnd_hcic_write_auto_flush_tout(p_lcb->handle, hci_flush_to);
+ }
+ }
+ }
+ }
+
+ return (true);
+}
+
+/*******************************************************************************
+ *
* Function L2CA_GetPeerFeatures
*
* Description Get a peers features and fixed channel map
@@ -1056,7 +1331,7 @@ bool L2CA_SetTxPriority(uint16_t cid, tL2CAP_CHNL_PRIORITY priority) {
******************************************************************************/
bool L2CA_GetPeerFeatures(const RawAddress& bd_addr, uint32_t* p_ext_feat,
uint8_t* p_chnl_mask) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_GetPeerFeatures(bd_addr, p_ext_feat,
p_chnl_mask);
}
@@ -1081,6 +1356,7 @@ bool L2CA_GetPeerFeatures(const RawAddress& bd_addr, uint32_t* p_ext_feat,
return true;
}
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
/*******************************************************************************
*
* Function L2CA_RegisterFixedChannel
@@ -1093,43 +1369,22 @@ bool L2CA_GetPeerFeatures(const RawAddress& bd_addr, uint32_t* p_ext_feat,
* Return value: -
*
******************************************************************************/
-static std::string fixed_channel_text(const uint16_t& fixed_cid) {
- switch (fixed_cid) {
- case L2CAP_SIGNALLING_CID:
- return std::string("br_edr signalling");
- case L2CAP_CONNECTIONLESS_CID:
- return std::string("connectionless");
- case L2CAP_AMP_CID:
- return std::string("amp");
- case L2CAP_ATT_CID:
- return std::string("att");
- case L2CAP_BLE_SIGNALLING_CID:
- return std::string("ble signalling");
- case L2CAP_SMP_CID:
- return std::string("smp");
- case L2CAP_SMP_BR_CID:
- return std::string("br_edr smp");
- default:
- return std::string("unknown");
- }
-}
-
bool L2CA_RegisterFixedChannel(uint16_t fixed_cid,
tL2CAP_FIXED_CHNL_REG* p_freg) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_RegisterFixedChannel(fixed_cid, p_freg);
}
if ((fixed_cid < L2CAP_FIRST_FIXED_CHNL) ||
(fixed_cid > L2CAP_LAST_FIXED_CHNL)) {
- LOG_ERROR("Invalid fixed CID: 0x%04x", fixed_cid);
- return false;
+ L2CAP_TRACE_ERROR("L2CA_RegisterFixedChannel() Invalid CID: 0x%04x",
+ fixed_cid);
+
+ return (false);
}
l2cb.fixed_reg[fixed_cid - L2CAP_FIRST_FIXED_CHNL] = *p_freg;
- LOG_DEBUG("Registered fixed channel:%s",
- fixed_channel_text(fixed_cid).c_str());
- return true;
+ return (true);
}
/*******************************************************************************
@@ -1145,27 +1400,39 @@ bool L2CA_RegisterFixedChannel(uint16_t fixed_cid,
*
******************************************************************************/
bool L2CA_ConnectFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_ConnectFixedChnl(fixed_cid, rem_bda);
}
+ uint8_t phy = controller_get_interface()->get_le_all_initiating_phys();
+ return L2CA_ConnectFixedChnl(fixed_cid, rem_bda, phy);
+}
+
+bool L2CA_ConnectFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda,
+ uint8_t initiating_phys) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_ConnectFixedChnl(fixed_cid, rem_bda,
+ initiating_phys);
+ }
+
tL2C_LCB* p_lcb;
tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
- LOG_DEBUG(" fixed_cid:0x%04x", fixed_cid);
+ VLOG(1) << __func__ << " BDA: " << rem_bda
+ << StringPrintf("CID: 0x%04x ", fixed_cid);
// Check CID is valid and registered
if ((fixed_cid < L2CAP_FIRST_FIXED_CHNL) ||
(fixed_cid > L2CAP_LAST_FIXED_CHNL) ||
(l2cb.fixed_reg[fixed_cid - L2CAP_FIRST_FIXED_CHNL].pL2CA_FixedData_Cb ==
NULL)) {
- LOG_ERROR("Invalid fixed_cid:0x%04x", fixed_cid);
+ L2CAP_TRACE_ERROR("%s() Invalid CID: 0x%04x", __func__, fixed_cid);
return (false);
}
// Fail if BT is not yet up
if (!BTM_IsDeviceUp()) {
- LOG_WARN("Bt controller is not ready fixed_cid:0x%04x", fixed_cid);
+ L2CAP_TRACE_WARNING("%s(0x%04x) - BTU not ready", __func__, fixed_cid);
return (false);
}
@@ -1187,22 +1454,23 @@ bool L2CA_ConnectFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda) {
// Check for supported channel
if (!(peer_channel_mask & (1 << fixed_cid))) {
- LOG_INFO("Peer device does not support fixed_cid:0x%04x", fixed_cid);
+ VLOG(2) << __func__ << " BDA " << rem_bda
+ << StringPrintf(" CID:0x%04x not supported", fixed_cid);
return false;
}
// Get a CCB and link the lcb to it
- if (!l2cu_initialize_fixed_ccb(p_lcb, fixed_cid)) {
- LOG_WARN("Unable to allocate fixed channel resource fixed_cid:0x%04x",
- fixed_cid);
+ if (!l2cu_initialize_fixed_ccb(
+ p_lcb, fixed_cid,
+ &l2cb.fixed_reg[fixed_cid - L2CAP_FIRST_FIXED_CHNL]
+ .fixed_chnl_opts)) {
+ L2CAP_TRACE_WARNING("%s(0x%04x) - LCB but no CCB", __func__, fixed_cid);
return false;
}
// racing with disconnecting, queue the connection request
if (p_lcb->link_state == LST_DISCONNECTING) {
- LOG_DEBUG(
- "Link is disconnecting so deferring connection fixed_cid:0x%04x",
- fixed_cid);
+ L2CAP_TRACE_DEBUG("$s() - link disconnecting: RETRY LATER", __func__);
/* Save ccb so it can be started after disconnect is finished */
p_lcb->p_pending_ccb =
p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL];
@@ -1217,31 +1485,30 @@ bool L2CA_ConnectFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda) {
// No link. Get an LCB and start link establishment
p_lcb = l2cu_allocate_lcb(rem_bda, false, transport);
if (p_lcb == NULL) {
- LOG_WARN("Unable to allocate link resource for connection fixed_cid:0x%04x",
- fixed_cid);
+ L2CAP_TRACE_WARNING("%s(0x%04x) - no LCB", __func__, fixed_cid);
return false;
}
// Get a CCB and link the lcb to it
- if (!l2cu_initialize_fixed_ccb(p_lcb, fixed_cid)) {
- LOG_WARN("Unable to allocate fixed channel resource fixed_cid:0x%04x",
- fixed_cid);
+ if (!l2cu_initialize_fixed_ccb(
+ p_lcb, fixed_cid, &l2cb.fixed_reg[fixed_cid - L2CAP_FIRST_FIXED_CHNL]
+ .fixed_chnl_opts)) {
+ p_lcb->disc_reason = L2CAP_CONN_NO_RESOURCES;
+ L2CAP_TRACE_WARNING("%s(0x%04x) - no CCB", __func__, fixed_cid);
l2cu_release_lcb(p_lcb);
return false;
}
- if (transport == BT_TRANSPORT_LE) {
- bool ret = l2cu_create_conn_le(p_lcb);
- if (!ret) {
- LOG_WARN("Unable to create fixed channel le connection fixed_cid:0x%04x",
- fixed_cid);
- l2cu_release_lcb(p_lcb);
- return false;
- }
- } else {
- l2cu_create_conn_br_edr(p_lcb);
+ bool ret = ((transport == BT_TRANSPORT_LE)
+ ? l2cu_create_conn_le(p_lcb, initiating_phys)
+ : l2cu_create_conn_br_edr(p_lcb));
+
+ if (!ret) {
+ L2CAP_TRACE_WARNING("%s() - create connection failed", __func__);
+ l2cu_release_lcb(p_lcb);
}
- return true;
+
+ return ret;
}
/*******************************************************************************
@@ -1260,35 +1527,43 @@ bool L2CA_ConnectFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda) {
******************************************************************************/
uint16_t L2CA_SendFixedChnlData(uint16_t fixed_cid, const RawAddress& rem_bda,
BT_HDR* p_buf) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_SendFixedChnlData(fixed_cid, rem_bda, p_buf);
}
tL2C_LCB* p_lcb;
tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
+ VLOG(2) << __func__ << " BDA: " << rem_bda
+ << StringPrintf(" CID: 0x%04x", fixed_cid);
+
if (fixed_cid >= L2CAP_ATT_CID && fixed_cid <= L2CAP_SMP_CID)
transport = BT_TRANSPORT_LE;
+ // Check CID is valid and registered
if ((fixed_cid < L2CAP_FIRST_FIXED_CHNL) ||
(fixed_cid > L2CAP_LAST_FIXED_CHNL) ||
(l2cb.fixed_reg[fixed_cid - L2CAP_FIRST_FIXED_CHNL].pL2CA_FixedData_Cb ==
NULL)) {
- LOG_WARN("No service registered or invalid CID: 0x%04x", fixed_cid);
+ L2CAP_TRACE_ERROR("L2CA_SendFixedChnlData() Invalid CID: 0x%04x",
+ fixed_cid);
osi_free(p_buf);
return (L2CAP_DW_FAILED);
}
+ // Fail if BT is not yet up
if (!BTM_IsDeviceUp()) {
- LOG_WARN("Controller is not ready CID: 0x%04x", fixed_cid);
+ L2CAP_TRACE_WARNING("L2CA_SendFixedChnlData(0x%04x) - BTU not ready",
+ fixed_cid);
osi_free(p_buf);
return (L2CAP_DW_FAILED);
}
+ // We need to have a link up
p_lcb = l2cu_find_lcb_by_bd_addr(rem_bda, transport);
if (p_lcb == NULL || p_lcb->link_state == LST_DISCONNECTING) {
/* if link is disconnecting, also report data sending failure */
- LOG_WARN("Link is disconnecting or does not exist CID: 0x%04x", fixed_cid);
+ L2CAP_TRACE_WARNING("L2CA_SendFixedChnlData(0x%04x) - no LCB", fixed_cid);
osi_free(p_buf);
return (L2CAP_DW_FAILED);
}
@@ -1302,7 +1577,9 @@ uint16_t L2CA_SendFixedChnlData(uint16_t fixed_cid, const RawAddress& rem_bda,
peer_channel_mask = p_lcb->peer_chnl_mask[0];
if ((peer_channel_mask & (1 << fixed_cid)) == 0) {
- LOG_WARN("Peer does not support fixed channel CID: 0x%04x", fixed_cid);
+ L2CAP_TRACE_WARNING(
+ "L2CA_SendFixedChnlData() - peer does not support fixed chnl: 0x%04x",
+ fixed_cid);
osi_free(p_buf);
return (L2CAP_DW_FAILED);
}
@@ -1311,31 +1588,34 @@ uint16_t L2CA_SendFixedChnlData(uint16_t fixed_cid, const RawAddress& rem_bda,
p_buf->layer_specific = L2CAP_FLUSHABLE_CH_BASED;
if (!p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL]) {
- if (!l2cu_initialize_fixed_ccb(p_lcb, fixed_cid)) {
- LOG_WARN("No channel control block found for CID: 0x%4x", fixed_cid);
+ if (!l2cu_initialize_fixed_ccb(
+ p_lcb, fixed_cid,
+ &l2cb.fixed_reg[fixed_cid - L2CAP_FIRST_FIXED_CHNL]
+ .fixed_chnl_opts)) {
+ L2CAP_TRACE_WARNING("L2CA_SendFixedChnlData() - no CCB for chnl: 0x%4x",
+ fixed_cid);
osi_free(p_buf);
return (L2CAP_DW_FAILED);
}
}
+ // If already congested, do not accept any more packets
if (p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL]->cong_sent) {
- LOG_WARN(
- "Unable to send data due to congestion CID: 0x%04x xmit_hold_q.count: "
- "%zu buff_quota: %u",
- fixed_cid,
- fixed_queue_length(
- p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL]
- ->xmit_hold_q),
+ L2CAP_TRACE_ERROR(
+ "L2CAP - CID: 0x%04x cannot send, already congested \
+ xmit_hold_q.count: %u buff_quota: %u",
+ fixed_cid, fixed_queue_length(
+ p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL]
+ ->xmit_hold_q),
p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL]->buff_quota);
osi_free(p_buf);
return (L2CAP_DW_FAILED);
}
- LOG_DEBUG("Enqueued data for CID: 0x%04x len:%hu", fixed_cid, p_buf->len);
l2c_enqueue_peer_data(p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL],
p_buf);
- l2c_link_check_send_pkts(p_lcb, 0, NULL);
+ l2c_link_check_send_pkts(p_lcb, NULL, NULL);
// If there is no dynamic CCB on the link, restart the idle timer each time
// something is sent
@@ -1344,10 +1624,8 @@ uint16_t L2CA_SendFixedChnlData(uint16_t fixed_cid, const RawAddress& rem_bda,
l2cu_no_dynamic_ccbs(p_lcb);
}
- if (p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL]->cong_sent) {
- LOG_DEBUG("Link congested for CID: 0x%04x", fixed_cid);
+ if (p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL]->cong_sent)
return (L2CAP_DW_CONGESTED);
- }
return (L2CAP_DW_SUCCESS);
}
@@ -1366,7 +1644,7 @@ uint16_t L2CA_SendFixedChnlData(uint16_t fixed_cid, const RawAddress& rem_bda,
*
******************************************************************************/
bool L2CA_RemoveFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_RemoveFixedChnl(fixed_cid, rem_bda);
}
@@ -1404,7 +1682,7 @@ bool L2CA_RemoveFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda) {
p_ccb = p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL];
p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL] = NULL;
- p_lcb->SetDisconnectReason(HCI_ERR_CONN_CAUSE_LOCAL_HOST);
+ p_lcb->disc_reason = HCI_ERR_CONN_CAUSE_LOCAL_HOST;
// Retain the link for a few more seconds after SMP pairing is done, since
// the Android platform always does service discovery after pairing is
@@ -1422,7 +1700,7 @@ bool L2CA_RemoveFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda) {
/*******************************************************************************
*
- * Function L2CA_SetLeGattTimeout
+ * Function L2CA_SetFixedChannelTout
*
* Description Higher layers call this function to set the idle timeout for
* a fixed channel. The "idle timeout" is the amount of time
@@ -1435,24 +1713,30 @@ bool L2CA_RemoveFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda) {
* Returns true if command succeeded, false if failed
*
******************************************************************************/
-bool L2CA_SetLeGattTimeout(const RawAddress& rem_bda, uint16_t idle_tout) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_SetLeGattTimeout(rem_bda, idle_tout);
+bool L2CA_SetFixedChannelTout(const RawAddress& rem_bda, uint16_t fixed_cid,
+ uint16_t idle_tout) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
+ return bluetooth::shim::L2CA_SetFixedChannelTout(rem_bda, fixed_cid,
+ idle_tout);
}
- constexpr uint16_t kAttCid = 4;
+ tL2C_LCB* p_lcb;
+ tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
+
+ if (fixed_cid >= L2CAP_ATT_CID && fixed_cid <= L2CAP_SMP_CID)
+ transport = BT_TRANSPORT_LE;
/* Is a fixed channel connected to the remote BDA ?*/
- tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(rem_bda, BT_TRANSPORT_LE);
+ p_lcb = l2cu_find_lcb_by_bd_addr(rem_bda, transport);
if (((p_lcb) == NULL) ||
- (!p_lcb->p_fixed_ccbs[kAttCid - L2CAP_FIRST_FIXED_CHNL])) {
+ (!p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL])) {
LOG(WARNING) << __func__ << " BDA: " << rem_bda
- << StringPrintf(" CID: 0x%04x not connected", kAttCid);
+ << StringPrintf(" CID: 0x%04x not connected", fixed_cid);
return (false);
}
- p_lcb->p_fixed_ccbs[kAttCid - L2CAP_FIRST_FIXED_CHNL]->fixed_chnl_idle_tout =
- idle_tout;
+ p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL]
+ ->fixed_chnl_idle_tout = idle_tout;
if (p_lcb->in_use && p_lcb->link_state == LST_CONNECTED &&
!p_lcb->ccb_queue.p_first_ccb) {
@@ -1464,6 +1748,8 @@ bool L2CA_SetLeGattTimeout(const RawAddress& rem_bda, uint16_t idle_tout) {
return true;
}
+#endif /* #if (L2CAP_NUM_FIXED_CHNLS > 0) */
+
/*******************************************************************************
*
* Function L2CA_DataWrite
@@ -1477,7 +1763,7 @@ bool L2CA_SetLeGattTimeout(const RawAddress& rem_bda, uint16_t idle_tout) {
*
******************************************************************************/
uint8_t L2CA_DataWrite(uint16_t cid, BT_HDR* p_data) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_DataWrite(cid, p_data);
}
@@ -1485,14 +1771,6 @@ uint8_t L2CA_DataWrite(uint16_t cid, BT_HDR* p_data) {
return l2c_data_write(cid, p_data, L2CAP_FLUSHABLE_CH_BASED);
}
-uint8_t L2CA_LECocDataWrite(uint16_t cid, BT_HDR* p_data) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_LECocDataWrite(cid, p_data);
- }
-
- return L2CA_DataWrite(cid, p_data);
-}
-
/*******************************************************************************
*
* Function L2CA_SetChnlFlushability
@@ -1504,10 +1782,11 @@ uint8_t L2CA_LECocDataWrite(uint16_t cid, BT_HDR* p_data) {
*
******************************************************************************/
bool L2CA_SetChnlFlushability(uint16_t cid, bool is_flushable) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_SetChnlFlushability(cid, is_flushable);
}
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
tL2C_CCB* p_ccb;
/* Find the channel control block. We don't know the link it is on. */
@@ -1523,6 +1802,8 @@ bool L2CA_SetChnlFlushability(uint16_t cid, bool is_flushable) {
L2CAP_TRACE_API("L2CA_SetChnlFlushability() CID: 0x%04x is_flushable: %d",
cid, is_flushable);
+#endif
+
return (true);
}
@@ -1541,7 +1822,7 @@ bool L2CA_SetChnlFlushability(uint16_t cid, bool is_flushable) {
*
******************************************************************************/
uint16_t L2CA_FlushChannel(uint16_t lcid, uint16_t num_to_flush) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
+ if (bluetooth::shim::is_gd_shim_enabled()) {
return bluetooth::shim::L2CA_FlushChannel(lcid, num_to_flush);
}
@@ -1570,16 +1851,21 @@ uint16_t L2CA_FlushChannel(uint16_t lcid, uint16_t num_to_flush) {
/* Cannot flush eRTM buffers once they have a sequence number */
if (p_ccb->peer_cfg.fcr.mode != L2CAP_FCR_ERTM_MODE) {
- const controller_t* controller = controller_get_interface();
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
if (num_to_flush != L2CAP_FLUSH_CHANS_GET) {
/* If the controller supports enhanced flush, flush the data queued at the
* controller */
- if (controller->supports_non_flushable_pb() &&
+ if ((HCI_NON_FLUSHABLE_PB_SUPPORTED(BTM_ReadLocalFeatures())) &&
(BTM_GetNumScoLinks() == 0)) {
- /* The only packet type defined - 0 - Automatically-Flushable Only */
- btsnd_hcic_enhanced_flush(p_lcb->Handle(), 0);
+ if (!l2cb.is_flush_active) {
+ l2cb.is_flush_active = true;
+
+ /* The only packet type defined - 0 - Automatically-Flushable Only */
+ btsnd_hcic_enhanced_flush(p_lcb->handle, 0);
+ }
}
}
+#endif
// Iterate though list and flush the amount requested from
// the transmit data queue that satisfy the layer and event conditions.
@@ -1605,7 +1891,7 @@ uint16_t L2CA_FlushChannel(uint16_t lcid, uint16_t num_to_flush) {
num_flushed2++;
}
- /* If app needs to track all packets, call it */
+ /* If app needs to track all packets, call him */
if ((p_ccb->p_rcb) && (p_ccb->p_rcb->api.pL2CA_TxComplete_Cb) &&
(num_flushed2))
(*p_ccb->p_rcb->api.pL2CA_TxComplete_Cb)(p_ccb->local_cid, num_flushed2);
@@ -1629,12 +1915,3 @@ uint16_t L2CA_FlushChannel(uint16_t lcid, uint16_t num_to_flush) {
return (num_left);
}
-
-bool L2CA_IsLinkEstablished(const RawAddress& bd_addr,
- tBT_TRANSPORT transport) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_IsLinkEstablished(bd_addr, transport);
- }
-
- return l2cu_find_lcb_by_bd_addr(bd_addr, transport) != nullptr;
-}
diff --git a/stack/l2cap/l2c_ble.cc b/stack/l2cap/l2c_ble.cc
index b826dc19c..bd1a5039d 100644
--- a/stack/l2cap/l2c_ble.cc
+++ b/stack/l2cap/l2c_ble.cc
@@ -22,40 +22,62 @@
*
******************************************************************************/
-#define LOG_TAG "l2c_ble"
-
#include <base/logging.h>
#include <base/strings/stringprintf.h>
-
+#include <string.h>
#include "bt_target.h"
+#include "bt_utils.h"
#include "bta_hearing_aid_api.h"
+#include "btm_int.h"
+#include "btu.h"
#include "device/include/controller.h"
#include "hcimsgs.h"
#include "l2c_api.h"
#include "l2c_int.h"
#include "l2cdefs.h"
-#include "main/shim/l2c_api.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
+#include "log/log.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/acl_api.h"
+#include "stack/gatt/connection_manager.h"
#include "stack_config.h"
-tL2CAP_LE_RESULT_CODE btm_ble_start_sec_check(const RawAddress& bd_addr,
- uint16_t psm, bool is_originator,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data);
-
-extern tBTM_CB btm_cb;
-
using base::StringPrintf;
static void l2cble_start_conn_update(tL2C_LCB* p_lcb);
-extern void gatt_notify_conn_update(const RawAddress& remote, uint16_t interval,
- uint16_t latency, uint16_t timeout,
- tHCI_STATUS status);
+
+/*******************************************************************************
+ *
+ * Function L2CA_CancelBleConnectReq
+ *
+ * Description Cancel a pending connection attempt to a BLE device.
+ *
+ * Parameters: BD Address of remote
+ *
+ * Return value: true if connection was cancelled
+ *
+ ******************************************************************************/
+bool L2CA_CancelBleConnectReq(const RawAddress& rem_bda) {
+ tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(rem_bda, BT_TRANSPORT_LE);
+
+ tACL_CONN* p_acl = btm_bda_to_acl(rem_bda, BT_TRANSPORT_LE);
+ if (p_acl) {
+ if (p_lcb != NULL && p_lcb->link_state == LST_CONNECTING) {
+ L2CAP_TRACE_WARNING("%s - disconnecting the LE link", __func__);
+ L2CA_RemoveFixedChnl(L2CAP_ATT_CID, rem_bda);
+ return (true);
+ }
+ }
+
+ connection_manager::direct_connect_remove(CONN_MGR_ID_L2CAP, rem_bda);
+
+ /* Do not remove lcb if an LE link is already up as a peripheral */
+ if (p_lcb != NULL &&
+ !(p_lcb->link_role == HCI_ROLE_SLAVE &&
+ btm_bda_to_acl(rem_bda, BT_TRANSPORT_LE) != NULL)) {
+ p_lcb->disc_reason = L2CAP_CONN_CANCEL;
+ l2cu_release_lcb(p_lcb);
+ }
+ return (true);
+}
/*******************************************************************************
*
@@ -72,19 +94,14 @@ bool L2CA_UpdateBleConnParams(const RawAddress& rem_bda, uint16_t min_int,
uint16_t max_int, uint16_t latency,
uint16_t timeout, uint16_t min_ce_len,
uint16_t max_ce_len) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- bluetooth::shim::L2CA_LeConnectionUpdate(rem_bda, min_int, max_int, latency,
- timeout, min_ce_len, max_ce_len);
- return true;
- }
-
tL2C_LCB* p_lcb;
+ tACL_CONN* p_acl_cb = btm_bda_to_acl(rem_bda, BT_TRANSPORT_LE);
/* See if we have a link control block for the remote device */
p_lcb = l2cu_find_lcb_by_bd_addr(rem_bda, BT_TRANSPORT_LE);
- /* If we do not have one, create one and accept the connection. */
- if (!p_lcb || !BTM_IsAclConnectionUp(rem_bda, BT_TRANSPORT_LE)) {
+ /* If we don't have one, create one and accept the connection. */
+ if (!p_lcb || !p_acl_cb) {
LOG(WARNING) << __func__ << " - unknown BD_ADDR " << rem_bda;
return (false);
}
@@ -111,6 +128,13 @@ bool L2CA_UpdateBleConnParams(const RawAddress& rem_bda, uint16_t min_int,
return (true);
}
+bool L2CA_UpdateBleConnParams(const RawAddress& rem_bda, uint16_t min_int,
+ uint16_t max_int, uint16_t latency,
+ uint16_t timeout) {
+ return L2CA_UpdateBleConnParams(rem_bda, min_int, max_int, latency, timeout,
+ 0, 0);
+}
+
/*******************************************************************************
*
* Function L2CA_EnableUpdateBleConnParams
@@ -123,10 +147,6 @@ bool L2CA_UpdateBleConnParams(const RawAddress& rem_bda, uint16_t min_int,
*
******************************************************************************/
bool L2CA_EnableUpdateBleConnParams(const RawAddress& rem_bda, bool enable) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_EnableUpdateBleConnParams(rem_bda, enable);
- }
-
if (stack_config_get_interface()->get_pts_conn_updates_disabled())
return false;
@@ -146,7 +166,7 @@ bool L2CA_EnableUpdateBleConnParams(const RawAddress& rem_bda, bool enable) {
if (p_lcb->transport != BT_TRANSPORT_LE) {
LOG(WARNING) << __func__ << " - BD_ADDR " << rem_bda
- << " not LE, link role " << p_lcb->LinkRole();
+ << " not LE, link role " << p_lcb->link_role;
return false;
}
@@ -160,16 +180,45 @@ bool L2CA_EnableUpdateBleConnParams(const RawAddress& rem_bda, bool enable) {
return (true);
}
-hci_role_t L2CA_GetBleConnRole(const RawAddress& bd_addr) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return bluetooth::shim::L2CA_GetBleConnRole(bd_addr);
- }
+/*******************************************************************************
+ *
+ * Function L2CA_GetBleConnRole
+ *
+ * Description This function returns the connection role.
+ *
+ * Returns link role.
+ *
+ ******************************************************************************/
+uint8_t L2CA_GetBleConnRole(const RawAddress& bd_addr) {
+ uint8_t role = HCI_ROLE_UNKNOWN;
- tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(bd_addr, BT_TRANSPORT_LE);
- if (p_lcb == nullptr) {
- return HCI_ROLE_UNKNOWN;
- }
- return p_lcb->LinkRole();
+ tL2C_LCB* p_lcb;
+
+ p_lcb = l2cu_find_lcb_by_bd_addr(bd_addr, BT_TRANSPORT_LE);
+ if (p_lcb != NULL) role = p_lcb->link_role;
+
+ return role;
+}
+/*******************************************************************************
+ *
+ * Function L2CA_GetDisconnectReason
+ *
+ * Description This function returns the disconnect reason code.
+ *
+ * Returns disconnect reason
+ *
+ ******************************************************************************/
+uint16_t L2CA_GetDisconnectReason(const RawAddress& remote_bda,
+ tBT_TRANSPORT transport) {
+ tL2C_LCB* p_lcb;
+ uint16_t reason = 0;
+
+ p_lcb = l2cu_find_lcb_by_bd_addr(remote_bda, transport);
+ if (p_lcb != NULL) reason = p_lcb->disc_reason;
+
+ L2CAP_TRACE_DEBUG("L2CA_GetDisconnectReason=%d ", reason);
+
+ return reason;
}
/*******************************************************************************
@@ -183,101 +232,104 @@ hci_role_t L2CA_GetBleConnRole(const RawAddress& bd_addr) {
******************************************************************************/
void l2cble_notify_le_connection(const RawAddress& bda) {
tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(bda, BT_TRANSPORT_LE);
- if (p_lcb == nullptr) {
- LOG_WARN("Received notification for le connection but no lcb found");
- return;
- }
+ tACL_CONN* p_acl = btm_bda_to_acl(bda, BT_TRANSPORT_LE);
+ tL2C_CCB* p_ccb;
- if (BTM_IsAclConnectionUp(bda, BT_TRANSPORT_LE) &&
- p_lcb->link_state != LST_CONNECTED) {
+ if (p_lcb != NULL && p_acl != NULL && p_lcb->link_state != LST_CONNECTED) {
/* update link status */
- // TODO Move this back into acl layer
- btm_establish_continue_from_address(bda, BT_TRANSPORT_LE);
+ btm_establish_continue(p_acl);
/* update l2cap link status and send callback */
p_lcb->link_state = LST_CONNECTED;
l2cu_process_fixed_chnl_resp(p_lcb);
}
- /* For all channels, send the event through their FSMs */
- for (tL2C_CCB* p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb;
- p_ccb = p_ccb->p_next_ccb) {
- if (p_ccb->chnl_state == CST_CLOSED)
- l2c_csm_execute(p_ccb, L2CEVT_LP_CONNECT_CFM, NULL);
+ if (p_lcb != NULL) {
+ /* For all channels, send the event through their FSMs */
+ for (p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb;
+ p_ccb = p_ccb->p_next_ccb) {
+ if (p_ccb->chnl_state == CST_CLOSED)
+ l2c_csm_execute(p_ccb, L2CEVT_LP_CONNECT_CFM, NULL);
+ }
}
}
/** This function is called when an HCI Connection Complete event is received.
*/
-bool l2cble_conn_comp(uint16_t handle, uint8_t role, const RawAddress& bda,
+void l2cble_conn_comp(uint16_t handle, uint8_t role, const RawAddress& bda,
tBLE_ADDR_TYPE type, uint16_t conn_interval,
uint16_t conn_latency, uint16_t conn_timeout) {
- // role == HCI_ROLE_CENTRAL => scanner completed connection
- // role == HCI_ROLE_PERIPHERAL => advertiser completed connection
+ btm_ble_update_link_topology_mask(role, true);
+
+ // role == HCI_ROLE_MASTER => scanner completed connection
+ // role == HCI_ROLE_SLAVE => advertiser completed connection
+
+ L2CAP_TRACE_DEBUG(
+ "%s: HANDLE=%d addr_type=%d conn_interval=%d "
+ "slave_latency=%d supervision_tout=%d",
+ __func__, handle, type, conn_interval, conn_latency, conn_timeout);
/* See if we have a link control block for the remote device */
tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(bda, BT_TRANSPORT_LE);
- /* If we do not have one, create one. this is auto connection complete. */
+ /* If we don't have one, create one. this is auto connection complete. */
if (!p_lcb) {
p_lcb = l2cu_allocate_lcb(bda, false, BT_TRANSPORT_LE);
if (!p_lcb) {
- LOG_ERROR("Unable to allocate link resource for le acl connection");
- return false;
+ btm_sec_disconnect(handle, HCI_ERR_NO_CONNECTION);
+ LOG(ERROR) << __func__ << "failed to allocate LCB";
+ return;
} else {
- if (!l2cu_initialize_fixed_ccb(p_lcb, L2CAP_ATT_CID)) {
- LOG_ERROR("Unable to allocate channel resource for le acl connection");
- return false;
+ if (!l2cu_initialize_fixed_ccb(
+ p_lcb, L2CAP_ATT_CID,
+ &l2cb.fixed_reg[L2CAP_ATT_CID - L2CAP_FIRST_FIXED_CHNL]
+ .fixed_chnl_opts)) {
+ btm_sec_disconnect(handle, HCI_ERR_NO_CONNECTION);
+ LOG(WARNING) << __func__ << "LCB but no CCB";
+ return;
}
}
- } else if (role == HCI_ROLE_CENTRAL && p_lcb->link_state != LST_CONNECTING) {
- LOG_ERROR(
- "Received le acl connection as role central but not in connecting "
- "state");
- return false;
+ } else if (role == HCI_ROLE_MASTER && p_lcb->link_state != LST_CONNECTING) {
+ LOG(ERROR) << "L2CAP got BLE scanner conn_comp in bad state: "
+ << +p_lcb->link_state;
+ return;
}
- if (role == HCI_ROLE_CENTRAL) alarm_cancel(p_lcb->l2c_lcb_timer);
+ if (role == HCI_ROLE_MASTER) alarm_cancel(p_lcb->l2c_lcb_timer);
/* Save the handle */
- l2cu_set_lcb_handle(*p_lcb, handle);
+ p_lcb->handle = handle;
- /* Connected OK. Change state to connected, we were scanning so we are central
+ /* Connected OK. Change state to connected, we were scanning so we are master
*/
- if (role == HCI_ROLE_CENTRAL) {
- p_lcb->SetLinkRoleAsCentral();
- } else {
- p_lcb->SetLinkRoleAsPeripheral();
- }
-
+ p_lcb->link_role = role;
p_lcb->transport = BT_TRANSPORT_LE;
- /* update link parameter, set peripheral link as non-spec default upon link up
- */
+ /* update link parameter, set slave link as non-spec default upon link up */
p_lcb->min_interval = p_lcb->max_interval = conn_interval;
p_lcb->timeout = conn_timeout;
p_lcb->latency = conn_latency;
p_lcb->conn_update_mask = L2C_BLE_NOT_DEFAULT_PARAM;
+ /* Tell BTM Acl management about the link */
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_or_alloc_dev(bda);
+ btm_acl_created(bda, NULL, p_dev_rec->sec_bd_name, handle, p_lcb->link_role,
+ BT_TRANSPORT_LE);
+
p_lcb->peer_chnl_mask[0] = L2CAP_FIXED_CHNL_ATT_BIT |
L2CAP_FIXED_CHNL_BLE_SIG_BIT |
L2CAP_FIXED_CHNL_SMP_BIT;
- if (role == HCI_ROLE_PERIPHERAL) {
- if (!controller_get_interface()
- ->supports_ble_peripheral_initiated_feature_exchange()) {
+#if (BLE_PRIVACY_SPT == TRUE)
+ btm_ble_disable_resolving_list(BTM_BLE_RL_INIT, true);
+#endif
+
+ if (role == HCI_ROLE_SLAVE) {
+ if (!HCI_LE_SLAVE_INIT_FEAT_EXC_SUPPORTED(
+ controller_get_interface()->get_features_ble()->as_array)) {
p_lcb->link_state = LST_CONNECTED;
l2cu_process_fixed_chnl_resp(p_lcb);
}
}
- return true;
-}
-
-bool l2cble_conn_comp_from_address_with_type(
- uint16_t handle, uint8_t role, const tBLE_BD_ADDR& address_with_type,
- uint16_t conn_interval, uint16_t conn_latency, uint16_t conn_timeout) {
- return l2cble_conn_comp(handle, role, address_with_type.bda,
- address_with_type.type, conn_interval, conn_latency,
- conn_timeout);
}
/*******************************************************************************
@@ -293,8 +345,9 @@ bool l2cble_conn_comp_from_address_with_type(
*
******************************************************************************/
static void l2cble_start_conn_update(tL2C_LCB* p_lcb) {
- uint16_t min_conn_int, max_conn_int, peripheral_latency, supervision_tout;
- if (!BTM_IsAclConnectionUp(p_lcb->remote_bd_addr, BT_TRANSPORT_LE)) {
+ uint16_t min_conn_int, max_conn_int, slave_latency, supervision_tout;
+ tACL_CONN* p_acl_cb = btm_bda_to_acl(p_lcb->remote_bd_addr, BT_TRANSPORT_LE);
+ if (!p_acl_cb) {
LOG(ERROR) << "No known connection ACL for " << p_lcb->remote_bd_addr;
return;
}
@@ -313,29 +366,30 @@ static void l2cble_start_conn_update(tL2C_LCB* p_lcb) {
if (p_lcb->conn_update_mask & L2C_BLE_NOT_DEFAULT_PARAM &&
/* current connection interval is greater than default min */
p_lcb->min_interval > BTM_BLE_CONN_INT_MIN) {
- /* use 7.5 ms as fast connection parameter, 0 peripheral latency */
+ /* use 7.5 ms as fast connection parameter, 0 slave latency */
min_conn_int = max_conn_int = BTM_BLE_CONN_INT_MIN;
L2CA_AdjustConnectionIntervals(&min_conn_int, &max_conn_int,
BTM_BLE_CONN_INT_MIN);
- peripheral_latency = BTM_BLE_CONN_PERIPHERAL_LATENCY_DEF;
+ slave_latency = BTM_BLE_CONN_SLAVE_LATENCY_DEF;
supervision_tout = BTM_BLE_CONN_TIMEOUT_DEF;
- /* if both side 4.1, or we are central device, send HCI command */
- if (p_lcb->IsLinkRoleCentral()
- || (controller_get_interface()
- ->supports_ble_connection_parameter_request() &&
- acl_peer_supports_ble_connection_parameters_request(
- p_lcb->remote_bd_addr))
- ) {
- btsnd_hcic_ble_upd_ll_conn_params(p_lcb->Handle(), min_conn_int,
- max_conn_int, peripheral_latency,
+ /* if both side 4.1, or we are master device, send HCI command */
+ if (p_lcb->link_role == HCI_ROLE_MASTER
+#if (BLE_LLT_INCLUDED == TRUE)
+ || (HCI_LE_CONN_PARAM_REQ_SUPPORTED(
+ controller_get_interface()->get_features_ble()->as_array) &&
+ HCI_LE_CONN_PARAM_REQ_SUPPORTED(p_acl_cb->peer_le_features))
+#endif
+ ) {
+ btsnd_hcic_ble_upd_ll_conn_params(p_lcb->handle, min_conn_int,
+ max_conn_int, slave_latency,
supervision_tout, 0, 0);
p_lcb->conn_update_mask |= L2C_BLE_UPDATE_PENDING;
} else {
l2cu_send_peer_ble_par_req(p_lcb, min_conn_int, max_conn_int,
- peripheral_latency, supervision_tout);
+ slave_latency, supervision_tout);
}
p_lcb->conn_update_mask &= ~L2C_BLE_NOT_DEFAULT_PARAM;
p_lcb->conn_update_mask |= L2C_BLE_NEW_CONN_PARAM;
@@ -343,14 +397,15 @@ static void l2cble_start_conn_update(tL2C_LCB* p_lcb) {
} else {
/* application allows to do update, if we were delaying one do it now */
if (p_lcb->conn_update_mask & L2C_BLE_NEW_CONN_PARAM) {
- /* if both side 4.1, or we are central device, send HCI command */
- if (p_lcb->IsLinkRoleCentral()
- || (controller_get_interface()
- ->supports_ble_connection_parameter_request() &&
- acl_peer_supports_ble_connection_parameters_request(
- p_lcb->remote_bd_addr))
- ) {
- btsnd_hcic_ble_upd_ll_conn_params(p_lcb->Handle(), p_lcb->min_interval,
+ /* if both side 4.1, or we are master device, send HCI command */
+ if (p_lcb->link_role == HCI_ROLE_MASTER
+#if (BLE_LLT_INCLUDED == TRUE)
+ || (HCI_LE_CONN_PARAM_REQ_SUPPORTED(
+ controller_get_interface()->get_features_ble()->as_array) &&
+ HCI_LE_CONN_PARAM_REQ_SUPPORTED(p_acl_cb->peer_le_features))
+#endif
+ ) {
+ btsnd_hcic_ble_upd_ll_conn_params(p_lcb->handle, p_lcb->min_interval,
p_lcb->max_interval, p_lcb->latency,
p_lcb->timeout, p_lcb->min_ce_len,
p_lcb->max_ce_len);
@@ -421,8 +476,6 @@ void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
tL2C_CCB *p_ccb = NULL, *temp_p_ccb = NULL;
tL2C_RCB* p_rcb;
uint16_t credit;
- uint8_t num_of_channels;
-
p_pkt_end = p + pkt_len;
if (p + 4 > p_pkt_end) {
@@ -466,8 +519,8 @@ void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
STREAM_TO_UINT16(max_interval, p); /* 0x0006 - 0x0C80 */
STREAM_TO_UINT16(latency, p); /* 0x0000 - 0x03E8 */
STREAM_TO_UINT16(timeout, p); /* 0x000A - 0x0C80 */
- /* If we are a central, the peripheral wants to update the parameters */
- if (p_lcb->IsLinkRoleCentral()) {
+ /* If we are a master, the slave wants to update the parameters */
+ if (p_lcb->link_role == HCI_ROLE_MASTER) {
L2CA_AdjustConnectionIntervals(&min_interval, &max_interval,
BTM_BLE_CONN_INT_MIN_LIMIT);
@@ -502,343 +555,6 @@ void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
p += 2;
break;
- case L2CAP_CMD_CREDIT_BASED_CONN_REQ: {
- if (p + 10 > p_pkt_end) {
- LOG(ERROR) << "invalid L2CAP_CMD_CREDIT_BASED_CONN_REQ len";
- return;
- }
-
- STREAM_TO_UINT16(con_info.psm, p);
- STREAM_TO_UINT16(mtu, p);
- STREAM_TO_UINT16(mps, p);
- STREAM_TO_UINT16(initial_credit, p);
-
- /* Check how many channels remote side wants. */
- num_of_channels = (p_pkt_end - p) / sizeof(uint16_t);
-
- LOG_DEBUG(
- "Recv L2CAP_CMD_CREDIT_BASED_CONN_REQ with "
- "mtu = %d, "
- "mps = %d, "
- "initial credit = %d"
- "num_of_channels = %d",
- mtu, mps, initial_credit, num_of_channels);
-
- if (p_lcb->pending_ecoc_conn_cnt > 0) {
- LOG_WARN("L2CAP - L2CAP_CMD_CREDIT_BASED_CONN_REQ collision:");
- l2cu_reject_credit_based_conn_req(p_lcb, id, num_of_channels,
- L2CAP_LE_RESULT_NO_RESOURCES);
- return;
- }
-
- p_lcb->pending_ecoc_conn_cnt = num_of_channels;
-
- /* Check PSM Support */
- p_rcb = l2cu_find_ble_rcb_by_psm(con_info.psm);
- if (p_rcb == NULL) {
- LOG_WARN("L2CAP - rcvd conn req for unknown PSM: 0x%04x", con_info.psm);
- l2cu_reject_credit_based_conn_req(p_lcb, id, num_of_channels,
- L2CAP_LE_RESULT_NO_PSM);
- return;
- }
-
- if (!p_rcb->api.pL2CA_CreditBasedConnectInd_Cb) {
- LOG_WARN("L2CAP - rcvd conn req for outgoing-only connection PSM: %d",
- con_info.psm);
- l2cu_reject_credit_based_conn_req(p_lcb, id, num_of_channels,
- L2CAP_CONN_NO_PSM);
- return;
- }
-
- /* validate the parameters */
- if (mtu < L2CAP_CREDIT_BASED_MIN_MTU ||
- mps < L2CAP_CREDIT_BASED_MIN_MPS || mps > L2CAP_LE_MAX_MPS) {
- LOG_ERROR("L2CAP don't like the params");
- l2cu_reject_credit_based_conn_req(p_lcb, id, num_of_channels,
- L2CAP_LE_RESULT_INVALID_PARAMETERS);
- return;
- }
-
- bool lead_cid_set = false;
-
- for (int i = 0; i < num_of_channels; i++) {
- STREAM_TO_UINT16(rcid, p);
- temp_p_ccb = l2cu_find_ccb_by_remote_cid(p_lcb, rcid);
- if (temp_p_ccb) {
- LOG_WARN("L2CAP - rcvd conn req for duplicated cid: 0x%04x", rcid);
- p_lcb->pending_ecoc_connection_cids[i] = 0;
- p_lcb->pending_l2cap_result =
- L2CAP_LE_RESULT_SOURCE_CID_ALREADY_ALLOCATED;
- } else {
- /* Allocate a ccb for this.*/
- temp_p_ccb = l2cu_allocate_ccb(p_lcb, 0);
- if (temp_p_ccb == NULL) {
- LOG_ERROR("L2CAP - unable to allocate CCB");
- p_lcb->pending_ecoc_connection_cids[i] = 0;
- p_lcb->pending_l2cap_result = L2CAP_LE_RESULT_NO_RESOURCES;
- continue;
- }
-
- temp_p_ccb->ecoc = true;
- temp_p_ccb->remote_id = id;
- temp_p_ccb->p_rcb = p_rcb;
- temp_p_ccb->remote_cid = rcid;
-
- temp_p_ccb->peer_conn_cfg.mtu = mtu;
- temp_p_ccb->peer_conn_cfg.mps = mps;
- temp_p_ccb->peer_conn_cfg.credits = initial_credit;
-
- temp_p_ccb->tx_mps = mps;
- temp_p_ccb->ble_sdu = NULL;
- temp_p_ccb->ble_sdu_length = 0;
- temp_p_ccb->is_first_seg = true;
- temp_p_ccb->peer_cfg.fcr.mode = L2CAP_FCR_LE_COC_MODE;
-
- /* This list will be used to prepare response */
- p_lcb->pending_ecoc_connection_cids[i] = temp_p_ccb->local_cid;
-
- /*This is going to be our lead p_ccb for state machine */
- if (!lead_cid_set) {
- p_ccb = temp_p_ccb;
- p_ccb->local_conn_cfg.mtu = L2CAP_SDU_LENGTH_LE_MAX;
- p_ccb->local_conn_cfg.mps =
- controller_get_interface()->get_acl_data_size_ble();
- p_lcb->pending_lead_cid = p_ccb->local_cid;
- lead_cid_set = true;
- }
- }
- }
-
- if (!lead_cid_set) {
- LOG_ERROR("L2CAP - unable to allocate CCB");
- l2cu_reject_credit_based_conn_req(p_lcb, id, num_of_channels,
- p_lcb->pending_l2cap_result);
- return;
- }
-
- LOG_DEBUG("L2CAP - processing peer credit based connect request");
- l2c_csm_execute(p_ccb, L2CEVT_L2CAP_CREDIT_BASED_CONNECT_REQ, NULL);
- break;
- }
- case L2CAP_CMD_CREDIT_BASED_CONN_RES:
- if (p + 2 > p_pkt_end) {
- LOG(ERROR) << "invalid L2CAP_CMD_CREDIT_BASED_CONN_RES len";
- return;
- }
-
- L2CAP_TRACE_DEBUG("Recv L2CAP_CMD_CREDIT_BASED_CONN_RES");
- /* For all channels, see whose identifier matches this id */
- for (temp_p_ccb = p_lcb->ccb_queue.p_first_ccb; temp_p_ccb;
- temp_p_ccb = temp_p_ccb->p_next_ccb) {
- if (temp_p_ccb->local_id == id) {
- p_ccb = temp_p_ccb;
- break;
- }
- }
-
- if (!p_ccb) {
- L2CAP_TRACE_DEBUG(" Cannot find matching connection req");
- con_info.l2cap_result = L2CAP_LE_RESULT_INVALID_SOURCE_CID;
- l2c_csm_execute(p_ccb, L2CEVT_L2CAP_CONNECT_RSP_NEG, &con_info);
- return;
- }
-
- STREAM_TO_UINT16(mtu, p);
- STREAM_TO_UINT16(mps, p);
- STREAM_TO_UINT16(initial_credit, p);
- STREAM_TO_UINT16(con_info.l2cap_result, p);
-
- /* When one of these result is sent back that means,
- * all the channels has been rejected
- */
- if (con_info.l2cap_result == L2CAP_LE_RESULT_NO_PSM ||
- con_info.l2cap_result ==
- L2CAP_LE_RESULT_INSUFFICIENT_AUTHENTICATION ||
- con_info.l2cap_result == L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP ||
- con_info.l2cap_result == L2CAP_LE_RESULT_INSUFFICIENT_AUTHORIZATION ||
- con_info.l2cap_result == L2CAP_LE_RESULT_UNACCEPTABLE_PARAMETERS ||
- con_info.l2cap_result == L2CAP_LE_RESULT_INVALID_PARAMETERS) {
- l2c_csm_execute(p_ccb, L2CEVT_L2CAP_CREDIT_BASED_CONNECT_RSP_NEG,
- &con_info);
- return;
- }
-
- /* validate the parameters */
- if (mtu < L2CAP_CREDIT_BASED_MIN_MTU ||
- mps < L2CAP_CREDIT_BASED_MIN_MPS || mps > L2CAP_LE_MAX_MPS) {
- L2CAP_TRACE_ERROR("L2CAP - invalid params");
- con_info.l2cap_result = L2CAP_LE_RESULT_INVALID_PARAMETERS;
- l2c_csm_execute(p_ccb, L2CEVT_L2CAP_CREDIT_BASED_CONNECT_RSP_NEG,
- &con_info);
- break;
- }
-
- /* At least some of the channels has been created and parameters are
- * good*/
- num_of_channels = (p_pkt_end - p) / sizeof(uint16_t);
- if (num_of_channels != p_lcb->pending_ecoc_conn_cnt) {
- L2CAP_TRACE_ERROR(
- "Incorrect response."
- "expected num of channels = %d",
- "received num of channels = %d", num_of_channels,
- p_lcb->pending_ecoc_conn_cnt);
- return;
- }
-
- L2CAP_TRACE_DEBUG(
- "mtu = %d, "
- "mps = %d, "
- "initial_credit = %d, "
- "con_info.l2cap_result = %d"
- "num_of_channels = %d",
- mtu, mps, initial_credit, con_info.l2cap_result, num_of_channels);
-
- con_info.peer_mtu = mtu;
-
- for (int i = 0; i < p_lcb->pending_ecoc_conn_cnt; i++) {
- uint16_t cid = p_lcb->pending_ecoc_connection_cids[i];
- temp_p_ccb = l2cu_find_ccb_by_cid(p_lcb, cid);
- STREAM_TO_UINT16(temp_p_ccb->remote_cid, p);
-
- L2CAP_TRACE_DEBUG(
- "local cid = %d "
- "remote cid = %d",
- cid, temp_p_ccb->remote_cid);
-
- /* Check if peer accepted channel, if not release the one not
- * created
- */
- if (temp_p_ccb->remote_cid == 0) {
- l2c_csm_execute(temp_p_ccb, L2CEVT_L2CAP_CREDIT_BASED_CONNECT_RSP_NEG,
- &con_info);
- } else {
- temp_p_ccb->tx_mps = mps;
- temp_p_ccb->ble_sdu = NULL;
- temp_p_ccb->ble_sdu_length = 0;
- temp_p_ccb->is_first_seg = true;
- temp_p_ccb->peer_cfg.fcr.mode = L2CAP_FCR_LE_COC_MODE;
- temp_p_ccb->peer_conn_cfg.mtu = mtu;
- temp_p_ccb->peer_conn_cfg.mps = mps;
- temp_p_ccb->peer_conn_cfg.credits = initial_credit;
-
- l2c_csm_execute(temp_p_ccb, L2CEVT_L2CAP_CREDIT_BASED_CONNECT_RSP,
- &con_info);
- }
- }
-
- p_lcb->pending_ecoc_conn_cnt = 0;
- memset(p_lcb->pending_ecoc_connection_cids, 0,
- L2CAP_CREDIT_BASED_MAX_CIDS);
-
- break;
- case L2CAP_CMD_CREDIT_BASED_RECONFIG_REQ: {
- if (p + 6 > p_pkt_end) {
- l2cu_send_ble_reconfig_rsp(p_lcb, id, L2CAP_RECONFIG_UNACCAPTED_PARAM);
- return;
- }
-
- STREAM_TO_UINT16(mtu, p);
- STREAM_TO_UINT16(mps, p);
-
- /* validate the parameters */
- if (mtu < L2CAP_CREDIT_BASED_MIN_MTU ||
- mps < L2CAP_CREDIT_BASED_MIN_MPS || mps > L2CAP_LE_MAX_MPS) {
- L2CAP_TRACE_ERROR("L2CAP - invalid params");
- l2cu_send_ble_reconfig_rsp(p_lcb, id, L2CAP_RECONFIG_UNACCAPTED_PARAM);
- return;
- }
-
- /* Check how many channels remote side wants to reconfigure */
- num_of_channels = (p_pkt_end - p) / sizeof(uint16_t);
-
- L2CAP_TRACE_DEBUG(
- "Recv L2CAP_CMD_CREDIT_BASED_RECONFIG_REQ with "
- "mtu = %d, "
- "mps = %d, "
- "num_of_channels = %d",
- mtu, mps, num_of_channels);
-
- uint8_t* p_tmp = p;
- for (int i = 0; i < num_of_channels; i++) {
- STREAM_TO_UINT16(rcid, p_tmp);
- p_ccb = l2cu_find_ccb_by_remote_cid(p_lcb, rcid);
- if (!p_ccb) {
- L2CAP_TRACE_WARNING(
- "L2CAP - rcvd config req for non existing cid: 0x%04x", rcid);
- l2cu_send_ble_reconfig_rsp(p_lcb, id, L2CAP_RECONFIG_INVALID_DCID);
- return;
- }
-
- if (p_ccb->peer_conn_cfg.mtu > mtu) {
- L2CAP_TRACE_WARNING(
- "L2CAP - rcvd config req mtu reduction new mtu < mtu (%d < %d)",
- mtu, p_ccb->peer_conn_cfg.mtu);
- l2cu_send_ble_reconfig_rsp(p_lcb, id,
- L2CAP_RECONFIG_REDUCTION_MTU_NO_ALLOWED);
- return;
- }
-
- if (p_ccb->peer_conn_cfg.mps > mps) {
- L2CAP_TRACE_WARNING(
- "L2CAP - rcvd config req mps reduction new mps < mps (%d < %d)",
- mtu, p_ccb->peer_conn_cfg.mtu);
- l2cu_send_ble_reconfig_rsp(p_lcb, id,
- L2CAP_RECONFIG_REDUCTION_MPS_NO_ALLOWED);
- return;
- }
- }
-
- for (int i = 0; i < num_of_channels; i++) {
- STREAM_TO_UINT16(rcid, p);
-
- /* Store new values */
- p_ccb = l2cu_find_ccb_by_remote_cid(p_lcb, rcid);
- p_ccb->peer_conn_cfg.mtu = mtu;
- p_ccb->peer_conn_cfg.mps = mps;
- p_ccb->tx_mps = mps;
-
- tL2CAP_LE_CFG_INFO le_cfg;
- le_cfg.mps = mps;
- le_cfg.mtu = mtu;
-
- l2c_csm_execute(p_ccb, L2CEVT_L2CAP_CREDIT_BASED_RECONFIG_REQ, &le_cfg);
- }
-
- l2cu_send_ble_reconfig_rsp(p_lcb, id, L2CAP_RECONFIG_SUCCEED);
-
- break;
- }
-
- case L2CAP_CMD_CREDIT_BASED_RECONFIG_RES: {
- uint16_t result;
- STREAM_TO_UINT16(result, p);
-
- L2CAP_TRACE_DEBUG(
- "Recv L2CAP_CMD_CREDIT_BASED_RECONFIG_RES for "
- "result = 0x%04x",
- result);
-
- p_lcb->pending_ecoc_reconfig_cfg.result = result;
-
- /* All channels which are in reconfiguration state are marked with
- * reconfig_started flag. Find it and send response
- */
- for (temp_p_ccb = p_lcb->ccb_queue.p_first_ccb; temp_p_ccb;
- temp_p_ccb = temp_p_ccb->p_next_ccb) {
- if ((temp_p_ccb->in_use) && (temp_p_ccb->reconfig_started)) {
- l2c_csm_execute(temp_p_ccb, L2CEVT_L2CAP_CREDIT_BASED_RECONFIG_RSP,
- &p_lcb->pending_ecoc_reconfig_cfg);
-
- temp_p_ccb->reconfig_started = false;
- if (result == L2CAP_CFG_OK) {
- temp_p_ccb->local_conn_cfg = p_lcb->pending_ecoc_reconfig_cfg;
- }
- }
- }
-
- break;
- }
-
case L2CAP_CMD_BLE_CREDIT_BASED_CONN_REQ:
if (p + 10 > p_pkt_end) {
android_errorWriteLog(0x534e4554, "80261585");
@@ -863,7 +579,7 @@ void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
if (p_ccb) {
L2CAP_TRACE_WARNING("L2CAP - rcvd conn req for duplicated cid: 0x%04x",
rcid);
- l2cu_reject_ble_coc_connection(
+ l2cu_reject_ble_connection(
p_lcb, id, L2CAP_LE_RESULT_SOURCE_CID_ALREADY_ALLOCATED);
break;
}
@@ -872,14 +588,14 @@ void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
if (p_rcb == NULL) {
L2CAP_TRACE_WARNING("L2CAP - rcvd conn req for unknown PSM: 0x%04x",
con_info.psm);
- l2cu_reject_ble_coc_connection(p_lcb, id, L2CAP_LE_RESULT_NO_PSM);
+ l2cu_reject_ble_connection(p_lcb, id, L2CAP_LE_RESULT_NO_PSM);
break;
} else {
if (!p_rcb->api.pL2CA_ConnectInd_Cb) {
L2CAP_TRACE_WARNING(
"L2CAP - rcvd conn req for outgoing-only connection PSM: %d",
con_info.psm);
- l2cu_reject_ble_coc_connection(p_lcb, id, L2CAP_CONN_NO_PSM);
+ l2cu_reject_ble_connection(p_lcb, id, L2CAP_CONN_NO_PSM);
break;
}
}
@@ -888,15 +604,15 @@ void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
p_ccb = l2cu_allocate_ccb(p_lcb, 0);
if (p_ccb == NULL) {
L2CAP_TRACE_ERROR("L2CAP - unable to allocate CCB");
- l2cu_reject_ble_connection(p_ccb, id, L2CAP_CONN_NO_RESOURCES);
+ l2cu_reject_ble_connection(p_lcb, id, L2CAP_CONN_NO_RESOURCES);
break;
}
/* validate the parameters */
if (mtu < L2CAP_LE_MIN_MTU || mps < L2CAP_LE_MIN_MPS ||
mps > L2CAP_LE_MAX_MPS) {
- L2CAP_TRACE_ERROR("L2CAP do not like the params");
- l2cu_reject_ble_connection(p_ccb, id, L2CAP_CONN_NO_RESOURCES);
+ L2CAP_TRACE_ERROR("L2CAP don't like the params");
+ l2cu_reject_ble_connection(p_lcb, id, L2CAP_CONN_NO_RESOURCES);
break;
}
@@ -904,11 +620,6 @@ void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
p_ccb->p_rcb = p_rcb;
p_ccb->remote_cid = rcid;
- p_ccb->local_conn_cfg.mtu = L2CAP_SDU_LENGTH_LE_MAX;
- p_ccb->local_conn_cfg.mps =
- controller_get_interface()->get_acl_data_size_ble();
- p_ccb->local_conn_cfg.credits = L2CAP_LE_CREDIT_DEFAULT,
-
p_ccb->peer_conn_cfg.mtu = mtu;
p_ccb->peer_conn_cfg.mps = mps;
p_ccb->peer_conn_cfg.credits = initial_credit;
@@ -919,8 +630,6 @@ void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
p_ccb->is_first_seg = true;
p_ccb->peer_cfg.fcr.mode = L2CAP_FCR_LE_COC_MODE;
- p_ccb->connection_initiator = L2CAP_INITIATOR_REMOTE;
-
l2c_csm_execute(p_ccb, L2CEVT_L2CAP_CONNECT_REQ, &con_info);
break;
@@ -963,7 +672,7 @@ void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
if (p_ccb->peer_conn_cfg.mtu < L2CAP_LE_MIN_MTU ||
p_ccb->peer_conn_cfg.mps < L2CAP_LE_MIN_MPS ||
p_ccb->peer_conn_cfg.mps > L2CAP_LE_MAX_MPS) {
- L2CAP_TRACE_ERROR("L2CAP do not like the params");
+ L2CAP_TRACE_ERROR("L2CAP don't like the params");
con_info.l2cap_result = L2CAP_LE_RESULT_NO_RESOURCES;
l2c_csm_execute(p_ccb, L2CEVT_L2CAP_CONNECT_RSP_NEG, &con_info);
break;
@@ -1051,9 +760,9 @@ void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
/** This function is to initate a direct connection. Returns true if connection
* initiated, false otherwise. */
bool l2cble_create_conn(tL2C_LCB* p_lcb) {
- if (!acl_create_le_connection(p_lcb->remote_bd_addr)) {
- return false;
- }
+ bool ret = connection_manager::direct_connect_add(CONN_MGR_ID_L2CAP,
+ p_lcb->remote_bd_addr);
+ if (!ret) return ret;
p_lcb->link_state = LST_CONNECTING;
@@ -1076,17 +785,12 @@ bool l2cble_create_conn(tL2C_LCB* p_lcb) {
*
******************************************************************************/
void l2c_link_processs_ble_num_bufs(uint16_t num_lm_ble_bufs) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return;
- }
-
if (num_lm_ble_bufs == 0) {
num_lm_ble_bufs = L2C_DEF_NUM_BLE_BUF_SHARED;
l2cb.num_lm_acl_bufs -= L2C_DEF_NUM_BLE_BUF_SHARED;
}
- l2cb.num_lm_ble_bufs = num_lm_ble_bufs;
- l2cb.controller_le_xmit_window = num_lm_ble_bufs;
+ l2cb.num_lm_ble_bufs = l2cb.controller_le_xmit_window = num_lm_ble_bufs;
}
/*******************************************************************************
@@ -1175,8 +879,8 @@ void l2c_ble_link_adjust_allocation(void) {
} else {
/* Safety check in case we switched to round-robin with something
* outstanding */
- /* if sent_not_acked is added into round_robin_unacked then do not add
- * it again */
+ /* if sent_not_acked is added into round_robin_unacked then don't add it
+ * again */
/* l2cap keeps updating sent_not_acked for exiting from round robin */
if ((p_lcb->link_xmit_quota > 0) && (qq == 0))
l2cb.ble_round_robin_unacked += p_lcb->sent_not_acked;
@@ -1209,6 +913,7 @@ void l2c_ble_link_adjust_allocation(void) {
}
}
+#if (BLE_LLT_INCLUDED == TRUE)
/*******************************************************************************
*
* Function l2cble_process_rc_param_request_evt
@@ -1244,6 +949,7 @@ void l2cble_process_rc_param_request_evt(uint16_t handle, uint16_t int_min,
L2CAP_TRACE_WARNING("No link to update connection parameter")
}
}
+#endif
/*******************************************************************************
*
@@ -1302,6 +1008,41 @@ void l2cble_process_data_length_change_event(uint16_t handle,
/*******************************************************************************
*
+ * Function l2cble_set_fixed_channel_tx_data_length
+ *
+ * Description This function update max fixed channel tx data length if
+ * applicable
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void l2cble_set_fixed_channel_tx_data_length(const RawAddress& remote_bda,
+ uint16_t fix_cid,
+ uint16_t tx_mtu) {
+ tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(remote_bda, BT_TRANSPORT_LE);
+ uint16_t cid = fix_cid - L2CAP_FIRST_FIXED_CHNL;
+
+ L2CAP_TRACE_DEBUG("%s TX MTU = %d", __func__, tx_mtu);
+
+ if (!controller_get_interface()->supports_ble_packet_extension()) {
+ L2CAP_TRACE_WARNING("%s, request not supported", __func__);
+ return;
+ }
+
+ /* See if we have a link control block for the connection */
+ if (p_lcb == NULL) return;
+
+ if (p_lcb->p_fixed_ccbs[cid] != NULL) {
+ if (tx_mtu > BTM_BLE_DATA_SIZE_MAX) tx_mtu = BTM_BLE_DATA_SIZE_MAX;
+
+ p_lcb->p_fixed_ccbs[cid]->tx_data_len = tx_mtu;
+ }
+
+ l2cble_update_data_length(p_lcb);
+}
+
+/*******************************************************************************
+ *
* Function l2cble_credit_based_conn_req
*
* Description This function sends LE Credit Based Connection Request for
@@ -1318,11 +1059,7 @@ void l2cble_credit_based_conn_req(tL2C_CCB* p_ccb) {
return;
}
- if (p_ccb->ecoc) {
- l2cu_send_peer_credit_based_conn_req(p_ccb);
- } else {
- l2cu_send_peer_ble_credit_based_conn_req(p_ccb);
- }
+ l2cu_send_peer_ble_credit_based_conn_req(p_ccb);
return;
}
@@ -1404,10 +1141,11 @@ void l2cble_send_peer_disc_req(tL2C_CCB* p_ccb) {
*
******************************************************************************/
void l2cble_sec_comp(const RawAddress* bda, tBT_TRANSPORT transport,
- void* p_ref_data, tBTM_STATUS status) {
+ void* p_ref_data, uint8_t status) {
const RawAddress& p_bda = *bda;
tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(p_bda, BT_TRANSPORT_LE);
tL2CAP_SEC_DATA* p_buf = NULL;
+ uint8_t sec_flag;
uint8_t sec_act;
if (!p_lcb) {
@@ -1432,7 +1170,8 @@ void l2cble_sec_comp(const RawAddress* bda, tBT_TRANSPORT transport,
(*(p_buf->p_callback))(p_bda, BT_TRANSPORT_LE, p_buf->p_ref_data, status);
} else {
if (sec_act == BTM_SEC_ENCRYPT_MITM) {
- if (BTM_IsLinkKeyAuthed(p_bda, transport))
+ BTM_GetSecurityFlagsByTransport(p_bda, &sec_flag, transport);
+ if (sec_flag & BTM_SEC_FLAG_LKEY_AUTHED)
(*(p_buf->p_callback))(p_bda, BT_TRANSPORT_LE, p_buf->p_ref_data,
status);
else {
@@ -1482,18 +1221,19 @@ tL2CAP_LE_RESULT_CODE l2ble_sec_access_req(const RawAddress& bd_addr,
uint16_t psm, bool is_originator,
tL2CAP_SEC_CBACK* p_callback,
void* p_ref_data) {
+ L2CAP_TRACE_DEBUG("%s", __func__);
tL2CAP_LE_RESULT_CODE result;
tL2C_LCB* p_lcb = NULL;
if (!p_callback) {
- LOG_ERROR("No callback function");
+ L2CAP_TRACE_ERROR("%s No callback function", __func__);
return L2CAP_LE_RESULT_NO_RESOURCES;
}
p_lcb = l2cu_find_lcb_by_bd_addr(bd_addr, BT_TRANSPORT_LE);
if (!p_lcb) {
- LOG_ERROR("Security check for unknown device");
+ L2CAP_TRACE_ERROR("%s Security check for unknown device", __func__);
p_callback(bd_addr, BT_TRANSPORT_LE, p_ref_data, BTM_UNKNOWN_ADDR);
return L2CAP_LE_RESULT_NO_RESOURCES;
}
@@ -1501,7 +1241,6 @@ tL2CAP_LE_RESULT_CODE l2ble_sec_access_req(const RawAddress& bd_addr,
tL2CAP_SEC_DATA* p_buf =
(tL2CAP_SEC_DATA*)osi_malloc((uint16_t)sizeof(tL2CAP_SEC_DATA));
if (!p_buf) {
- LOG_ERROR("No resources for connection");
p_callback(bd_addr, BT_TRANSPORT_LE, p_ref_data, BTM_NO_RESOURCES);
return L2CAP_LE_RESULT_NO_RESOURCES;
}
@@ -1550,42 +1289,3 @@ void L2CA_AdjustConnectionIntervals(uint16_t* min_interval,
*max_interval = phone_min_interval;
}
}
-
-void l2cble_use_preferred_conn_params(const RawAddress& bda) {
- tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(bda, BT_TRANSPORT_LE);
- tBTM_SEC_DEV_REC* p_dev_rec = btm_find_or_alloc_dev(bda);
-
- /* If there are any preferred connection parameters, set them now */
- if ((p_lcb != NULL) && (p_dev_rec != NULL) &&
- (p_dev_rec->conn_params.min_conn_int >= BTM_BLE_CONN_INT_MIN) &&
- (p_dev_rec->conn_params.min_conn_int <= BTM_BLE_CONN_INT_MAX) &&
- (p_dev_rec->conn_params.max_conn_int >= BTM_BLE_CONN_INT_MIN) &&
- (p_dev_rec->conn_params.max_conn_int <= BTM_BLE_CONN_INT_MAX) &&
- (p_dev_rec->conn_params.peripheral_latency <= BTM_BLE_CONN_LATENCY_MAX) &&
- (p_dev_rec->conn_params.supervision_tout >= BTM_BLE_CONN_SUP_TOUT_MIN) &&
- (p_dev_rec->conn_params.supervision_tout <= BTM_BLE_CONN_SUP_TOUT_MAX) &&
- ((p_lcb->min_interval < p_dev_rec->conn_params.min_conn_int &&
- p_dev_rec->conn_params.min_conn_int != BTM_BLE_CONN_PARAM_UNDEF) ||
- (p_lcb->min_interval > p_dev_rec->conn_params.max_conn_int) ||
- (p_lcb->latency > p_dev_rec->conn_params.peripheral_latency) ||
- (p_lcb->timeout > p_dev_rec->conn_params.supervision_tout))) {
- BTM_TRACE_DEBUG(
- "%s: HANDLE=%d min_conn_int=%d max_conn_int=%d peripheral_latency=%d "
- "supervision_tout=%d",
- __func__, p_lcb->Handle(), p_dev_rec->conn_params.min_conn_int,
- p_dev_rec->conn_params.max_conn_int,
- p_dev_rec->conn_params.peripheral_latency,
- p_dev_rec->conn_params.supervision_tout);
-
- p_lcb->min_interval = p_dev_rec->conn_params.min_conn_int;
- p_lcb->max_interval = p_dev_rec->conn_params.max_conn_int;
- p_lcb->timeout = p_dev_rec->conn_params.supervision_tout;
- p_lcb->latency = p_dev_rec->conn_params.peripheral_latency;
-
- btsnd_hcic_ble_upd_ll_conn_params(
- p_lcb->Handle(), p_dev_rec->conn_params.min_conn_int,
- p_dev_rec->conn_params.max_conn_int,
- p_dev_rec->conn_params.peripheral_latency,
- p_dev_rec->conn_params.supervision_tout, 0, 0);
- }
-}
diff --git a/stack/l2cap/l2c_csm.cc b/stack/l2cap/l2c_csm.cc
index 07d1d92aa..06ef7e868 100644
--- a/stack/l2cap/l2c_csm.cc
+++ b/stack/l2cap/l2c_csm.cc
@@ -21,84 +21,41 @@
* This file contains the L2CAP channel state machine
*
******************************************************************************/
-#define LOG_TAG "l2c_csm"
-#include <string>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
#include "bt_common.h"
#include "bt_target.h"
+#include "btm_int.h"
+#include "btu.h"
#include "common/time_util.h"
#include "hcidefs.h"
+#include "hcimsgs.h"
#include "l2c_int.h"
#include "l2cdefs.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/acl_api.h"
/******************************************************************************/
/* L O C A L F U N C T I O N P R O T O T Y P E S */
/******************************************************************************/
-static void l2c_csm_closed(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data);
-static void l2c_csm_orig_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_closed(tL2C_CCB* p_ccb, uint16_t event, void* p_data);
+static void l2c_csm_orig_w4_sec_comp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data);
-static void l2c_csm_term_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_term_w4_sec_comp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data);
-static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data);
-static void l2c_csm_w4_l2ca_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_w4_l2ca_connect_rsp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data);
-static void l2c_csm_config(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data);
-static void l2c_csm_open(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data);
-static void l2c_csm_w4_l2cap_disconnect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_config(tL2C_CCB* p_ccb, uint16_t event, void* p_data);
+static void l2c_csm_open(tL2C_CCB* p_ccb, uint16_t event, void* p_data);
+static void l2c_csm_w4_l2cap_disconnect_rsp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data);
-static void l2c_csm_w4_l2ca_disconnect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_w4_l2ca_disconnect_rsp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data);
-static const char* l2c_csm_get_event_name(tL2CEVT event);
-
-// Send a connect response with result OK and adjust the state machine
-static void l2c_csm_send_connect_rsp(tL2C_CCB* p_ccb) {
- l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONNECT_RSP, NULL);
-}
-
-// Send a config request and adjust the state machine
-static void l2c_csm_send_config_req(tL2C_CCB* p_ccb) {
- tL2CAP_CFG_INFO config{};
- config.mtu_present = true;
- config.mtu = p_ccb->p_rcb->my_mtu;
- p_ccb->max_rx_mtu = config.mtu;
- if (p_ccb->p_rcb->ertm_info.preferred_mode != L2CAP_FCR_BASIC_MODE) {
- config.fcr_present = true;
- config.fcr = kDefaultErtmOptions;
- }
- p_ccb->our_cfg = config;
- l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONFIG_REQ, &config);
-}
-
-// Send a config response with result OK and adjust the state machine
-static void l2c_csm_send_config_rsp_ok(tL2C_CCB* p_ccb) {
- tL2CAP_CFG_INFO config{};
- config.result = L2CAP_CFG_OK;
- l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONFIG_RSP, &config);
-}
-
-static void l2c_csm_send_disconnect_rsp(tL2C_CCB* p_ccb) {
- l2c_csm_execute(p_ccb, L2CEVT_L2CA_DISCONNECT_RSP, NULL);
-}
-
-static void l2c_csm_indicate_connection_open(tL2C_CCB* p_ccb) {
- if (p_ccb->connection_initiator == L2CAP_INITIATOR_LOCAL) {
- (*p_ccb->p_rcb->api.pL2CA_ConnectCfm_Cb)(p_ccb->local_cid, L2CAP_CONN_OK);
- } else {
- (*p_ccb->p_rcb->api.pL2CA_ConnectInd_Cb)(
- p_ccb->p_lcb->remote_bd_addr, p_ccb->local_cid, p_ccb->p_rcb->psm,
- p_ccb->remote_id);
- }
- if (p_ccb->chnl_state == CST_OPEN && !p_ccb->p_lcb->is_transport_ble()) {
- (*p_ccb->p_rcb->api.pL2CA_ConfigCfm_Cb)(
- p_ccb->local_cid, p_ccb->connection_initiator, &p_ccb->peer_cfg);
- }
-}
+static const char* l2c_csm_get_event_name(uint16_t event);
/*******************************************************************************
*
@@ -109,16 +66,13 @@ static void l2c_csm_indicate_connection_open(tL2C_CCB* p_ccb) {
* Returns void
*
******************************************************************************/
-void l2c_csm_execute(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
+void l2c_csm_execute(tL2C_CCB* p_ccb, uint16_t event, void* p_data) {
if (!l2cu_is_ccb_active(p_ccb)) {
- LOG_WARN("CCB not in use, event (%d) cannot be processed", event);
+ L2CAP_TRACE_WARNING("%s CCB not in use, event (%d) cannot be processed",
+ __func__, event);
return;
}
- LOG_DEBUG("Entry chnl_state=%s [%d], event=%s [%d]",
- channel_state_text(p_ccb->chnl_state).c_str(), p_ccb->chnl_state,
- l2c_csm_get_event_name(event), event);
-
switch (p_ccb->chnl_state) {
case CST_CLOSED:
l2c_csm_closed(p_ccb, event, p_data);
@@ -157,7 +111,7 @@ void l2c_csm_execute(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
break;
default:
- LOG_ERROR("Unhandled state %d, event %d", p_ccb->chnl_state, event);
+ L2CAP_TRACE_DEBUG("Unhandled event! event = %d", event);
break;
}
}
@@ -173,26 +127,29 @@ void l2c_csm_execute(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
* Returns void
*
******************************************************************************/
-static void l2c_csm_closed(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
+static void l2c_csm_closed(tL2C_CCB* p_ccb, uint16_t event, void* p_data) {
tL2C_CONN_INFO* p_ci = (tL2C_CONN_INFO*)p_data;
uint16_t local_cid = p_ccb->local_cid;
tL2CA_DISCONNECT_IND_CB* disconnect_ind;
+ tL2CA_CONNECT_CFM_CB* connect_cfm;
if (p_ccb->p_rcb == NULL) {
- LOG_ERROR("LCID: 0x%04x st: CLOSED evt: %s p_rcb == NULL",
- p_ccb->local_cid, l2c_csm_get_event_name(event));
+ L2CAP_TRACE_ERROR("L2CAP - LCID: 0x%04x st: CLOSED evt: %s p_rcb == NULL",
+ p_ccb->local_cid, l2c_csm_get_event_name(event));
return;
}
disconnect_ind = p_ccb->p_rcb->api.pL2CA_DisconnectInd_Cb;
+ connect_cfm = p_ccb->p_rcb->api.pL2CA_ConnectCfm_Cb;
- LOG_DEBUG("LCID: 0x%04x st: CLOSED evt: %s", p_ccb->local_cid,
- l2c_csm_get_event_name(event));
+ L2CAP_TRACE_EVENT("L2CAP - LCID: 0x%04x st: CLOSED evt: %s",
+ p_ccb->local_cid, l2c_csm_get_event_name(event));
switch (event) {
case L2CEVT_LP_DISCONNECT_IND: /* Link was disconnected */
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
+ p_ccb->local_cid);
l2cu_release_ccb(p_ccb);
(*disconnect_ind)(local_cid, false);
break;
@@ -205,35 +162,43 @@ static void l2c_csm_closed(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
} else {
p_ccb->chnl_state = CST_ORIG_W4_SEC_COMP;
btm_sec_l2cap_access_req(p_ccb->p_lcb->remote_bd_addr,
- p_ccb->p_rcb->psm, true, &l2c_link_sec_comp,
- p_ccb);
+ p_ccb->p_rcb->psm, p_ccb->p_lcb->handle, true,
+ &l2c_link_sec_comp, p_ccb);
}
break;
case L2CEVT_LP_CONNECT_CFM_NEG: /* Link failed */
- if (p_ci->status == HCI_ERR_CONNECTION_EXISTS) {
- btm_acl_notif_conn_collision(p_ccb->p_lcb->remote_bd_addr);
- } else {
+ /* Disconnect unless ACL collision and upper layer wants to handle it */
+ if (p_ci->status != HCI_ERR_CONNECTION_EXISTS ||
+ !btm_acl_notif_conn_collision(p_ccb->p_lcb->remote_bd_addr)) {
+ L2CAP_TRACE_API(
+ "L2CAP - Calling ConnectCfm_Cb(), CID: 0x%04x Status: %d",
+ p_ccb->local_cid, p_ci->status);
l2cu_release_ccb(p_ccb);
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(local_cid, L2CAP_CONN_OTHER_ERROR);
+ (*connect_cfm)(local_cid, p_ci->status);
}
break;
- case L2CEVT_L2CA_CREDIT_BASED_CONNECT_REQ: /* API connect request */
- case L2CEVT_L2CA_CONNECT_REQ:
+ case L2CEVT_L2CA_CONNECT_REQ: /* API connect request */
if (p_ccb->p_lcb->transport == BT_TRANSPORT_LE) {
p_ccb->chnl_state = CST_ORIG_W4_SEC_COMP;
l2ble_sec_access_req(p_ccb->p_lcb->remote_bd_addr, p_ccb->p_rcb->psm,
true, &l2c_link_sec_comp2, p_ccb);
} else {
- if (!BTM_SetLinkPolicyActiveMode(p_ccb->p_lcb->remote_bd_addr)) {
- LOG_WARN("Unable to set link policy active");
- }
+ /* Cancel sniff mode if needed */
+ tBTM_PM_PWR_MD settings;
+ memset((void*)&settings, 0, sizeof(settings));
+ settings.mode = BTM_PM_MD_ACTIVE;
+
+ BTM_SetPowerMode(BTM_PM_SET_ONLY_ID, p_ccb->p_lcb->remote_bd_addr,
+ &settings);
+
/* If sec access does not result in started SEC_COM or COMP_NEG are
* already processed */
- if (btm_sec_l2cap_access_req(
- p_ccb->p_lcb->remote_bd_addr, p_ccb->p_rcb->psm, true,
- &l2c_link_sec_comp, p_ccb) == BTM_CMD_STARTED) {
+ if (btm_sec_l2cap_access_req(p_ccb->p_lcb->remote_bd_addr,
+ p_ccb->p_rcb->psm, p_ccb->p_lcb->handle,
+ true, &l2c_link_sec_comp,
+ p_ccb) == BTM_CMD_STARTED) {
p_ccb->chnl_state = CST_ORIG_W4_SEC_COMP;
}
}
@@ -248,8 +213,8 @@ static void l2c_csm_closed(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
/* Need to have at least one compatible channel to continue */
if (!l2c_fcr_chk_chan_modes(p_ccb)) {
l2cu_release_ccb(p_ccb);
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(local_cid,
- L2CAP_CONN_OTHER_ERROR);
+ (*p_ccb->p_rcb->api.pL2CA_ConnectCfm_Cb)(local_cid,
+ L2CAP_CONN_NO_LINK);
} else {
l2cu_send_peer_connect_req(p_ccb);
alarm_set_on_mloop(p_ccb->l2c_ccb_timer,
@@ -260,12 +225,14 @@ static void l2c_csm_closed(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
break;
case L2CEVT_SEC_COMP_NEG: /* something is really bad with security */
+ L2CAP_TRACE_API(
+ "L2CAP - Calling ConnectCfm_Cb(), CID: 0x%04x Status: %d",
+ p_ccb->local_cid, L2CAP_CONN_TIMEOUT);
l2cu_release_ccb(p_ccb);
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(local_cid, L2CAP_CONN_OTHER_ERROR);
+ (*connect_cfm)(local_cid, L2CAP_CONN_SECURITY_BLOCK);
break;
- case L2CEVT_L2CAP_CREDIT_BASED_CONNECT_REQ: /* Peer connect request */
- case L2CEVT_L2CAP_CONNECT_REQ:
+ case L2CEVT_L2CAP_CONNECT_REQ: /* Peer connect request */
/* stop link timer to avoid race condition between A2MP, Security, and
* L2CAP */
alarm_cancel(p_ccb->p_lcb->l2c_lcb_timer);
@@ -277,43 +244,43 @@ static void l2c_csm_closed(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
&l2c_link_sec_comp2, p_ccb);
switch (result) {
- case L2CAP_LE_RESULT_INSUFFICIENT_AUTHORIZATION:
- case L2CAP_LE_RESULT_UNACCEPTABLE_PARAMETERS:
- case L2CAP_LE_RESULT_INVALID_PARAMETERS:
case L2CAP_LE_RESULT_INSUFFICIENT_AUTHENTICATION:
case L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP_KEY_SIZE:
case L2CAP_LE_RESULT_INSUFFICIENT_ENCRYP:
- l2cu_reject_ble_connection(p_ccb, p_ccb->remote_id, result);
+ l2cu_reject_ble_connection(p_ccb->p_lcb, p_ccb->remote_id, result);
l2cu_release_ccb(p_ccb);
break;
- case L2CAP_LE_RESULT_CONN_OK:
- case L2CAP_LE_RESULT_NO_PSM:
- case L2CAP_LE_RESULT_NO_RESOURCES:
- case L2CAP_LE_RESULT_INVALID_SOURCE_CID:
- case L2CAP_LE_RESULT_SOURCE_CID_ALREADY_ALLOCATED:
- break;
+ // TODO: Handle the other return codes
}
} else {
- if (!BTM_SetLinkPolicyActiveMode(p_ccb->p_lcb->remote_bd_addr)) {
- LOG_WARN("Unable to set link policy active");
+ /* Cancel sniff mode if needed */
+ {
+ tBTM_PM_PWR_MD settings;
+ memset((void*)&settings, 0, sizeof(settings));
+ settings.mode = BTM_PM_MD_ACTIVE;
+
+ BTM_SetPowerMode(BTM_PM_SET_ONLY_ID, p_ccb->p_lcb->remote_bd_addr,
+ &settings);
}
+
p_ccb->chnl_state = CST_TERM_W4_SEC_COMP;
- auto status = btm_sec_l2cap_access_req(p_ccb->p_lcb->remote_bd_addr,
- p_ccb->p_rcb->psm, false,
- &l2c_link_sec_comp, p_ccb);
- if (status == BTM_CMD_STARTED) {
- // started the security process, tell the peer to set a longer timer
+ if (btm_sec_l2cap_access_req(p_ccb->p_lcb->remote_bd_addr,
+ p_ccb->p_rcb->psm, p_ccb->p_lcb->handle,
+ false, &l2c_link_sec_comp,
+ p_ccb) == BTM_CMD_STARTED) {
+ /* started the security process, tell the peer to set a longer timer
+ */
l2cu_send_peer_connect_rsp(p_ccb, L2CAP_CONN_PENDING, 0);
- } else {
- LOG_INFO("Check security for psm 0x%04x, status %d",
- p_ccb->p_rcb->psm, status);
}
}
break;
case L2CEVT_TIMEOUT:
+ L2CAP_TRACE_API(
+ "L2CAP - Calling ConnectCfm_Cb(), CID: 0x%04x Status: %d",
+ p_ccb->local_cid, L2CAP_CONN_TIMEOUT);
l2cu_release_ccb(p_ccb);
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(local_cid, L2CAP_CONN_OTHER_ERROR);
+ (*connect_cfm)(local_cid, L2CAP_CONN_TIMEOUT);
break;
case L2CEVT_L2CAP_DATA: /* Peer data packet rcvd */
@@ -324,13 +291,7 @@ static void l2c_csm_closed(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
case L2CEVT_L2CA_DISCONNECT_REQ: /* Upper wants to disconnect */
l2cu_release_ccb(p_ccb);
break;
-
- default:
- LOG_ERROR("Handling unexpected event:%s", l2c_csm_get_event_name(event));
}
- LOG_DEBUG("Exit chnl_state=%s [%d], event=%s [%d]",
- channel_state_text(p_ccb->chnl_state).c_str(), p_ccb->chnl_state,
- l2c_csm_get_event_name(event), event);
}
/*******************************************************************************
@@ -343,22 +304,24 @@ static void l2c_csm_closed(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
* Returns void
*
******************************************************************************/
-static void l2c_csm_orig_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_orig_w4_sec_comp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data) {
tL2CA_DISCONNECT_IND_CB* disconnect_ind =
p_ccb->p_rcb->api.pL2CA_DisconnectInd_Cb;
+ tL2CA_CONNECT_CFM_CB* connect_cfm = p_ccb->p_rcb->api.pL2CA_ConnectCfm_Cb;
uint16_t local_cid = p_ccb->local_cid;
- LOG_DEBUG("%s - LCID: 0x%04x st: ORIG_W4_SEC_COMP evt: %s",
- ((p_ccb->p_lcb) && (p_ccb->p_lcb->transport == BT_TRANSPORT_LE))
- ? "LE "
- : "",
- p_ccb->local_cid, l2c_csm_get_event_name(event));
+ L2CAP_TRACE_EVENT(
+ "%s: %sL2CAP - LCID: 0x%04x st: ORIG_W4_SEC_COMP evt: %s", __func__,
+ ((p_ccb->p_lcb) && (p_ccb->p_lcb->transport == BT_TRANSPORT_LE)) ? "LE "
+ : "",
+ p_ccb->local_cid, l2c_csm_get_event_name(event));
switch (event) {
case L2CEVT_LP_DISCONNECT_IND: /* Link was disconnected */
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
+ p_ccb->local_cid);
l2cu_release_ccb(p_ccb);
(*disconnect_ind)(local_cid, false);
break;
@@ -370,8 +333,8 @@ static void l2c_csm_orig_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
false, &l2c_link_sec_comp2, p_ccb);
} else {
btm_sec_l2cap_access_req(p_ccb->p_lcb->remote_bd_addr,
- p_ccb->p_rcb->psm, true, &l2c_link_sec_comp,
- p_ccb);
+ p_ccb->p_rcb->psm, p_ccb->p_lcb->handle, true,
+ &l2c_link_sec_comp, p_ccb);
}
break;
@@ -388,8 +351,7 @@ static void l2c_csm_orig_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
/* Need to have at least one compatible channel to continue */
if (!l2c_fcr_chk_chan_modes(p_ccb)) {
l2cu_release_ccb(p_ccb);
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(local_cid,
- L2CAP_CONN_OTHER_ERROR);
+ (*connect_cfm)(local_cid, L2CAP_CONN_NO_LINK);
} else {
alarm_set_on_mloop(p_ccb->l2c_ccb_timer,
L2CAP_CHNL_CONNECT_TIMEOUT_MS,
@@ -401,6 +363,10 @@ static void l2c_csm_orig_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
break;
case L2CEVT_SEC_COMP_NEG:
+ L2CAP_TRACE_API(
+ "L2CAP - Calling ConnectCfm_Cb(), CID: 0x%04x Status: %d",
+ p_ccb->local_cid, HCI_ERR_AUTH_FAILURE);
+
/* If last channel immediately disconnect the ACL for better security.
Also prevents a race condition between BTM and L2CAP */
if ((p_ccb == p_ccb->p_lcb->ccb_queue.p_first_ccb) &&
@@ -409,7 +375,7 @@ static void l2c_csm_orig_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
}
l2cu_release_ccb(p_ccb);
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(local_cid, L2CAP_CONN_OTHER_ERROR);
+ (*connect_cfm)(local_cid, HCI_ERR_AUTH_FAILURE);
break;
case L2CEVT_L2CA_DATA_WRITE: /* Upper layer data to send */
@@ -423,13 +389,7 @@ static void l2c_csm_orig_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
l2cu_release_ccb(p_ccb);
break;
-
- default:
- LOG_ERROR("Handling unexpected event:%s", l2c_csm_get_event_name(event));
}
- LOG_DEBUG("Exit chnl_state=%s [%d], event=%s [%d]",
- channel_state_text(p_ccb->chnl_state).c_str(), p_ccb->chnl_state,
- l2c_csm_get_event_name(event), event);
}
/*******************************************************************************
@@ -442,10 +402,10 @@ static void l2c_csm_orig_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
* Returns void
*
******************************************************************************/
-static void l2c_csm_term_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_term_w4_sec_comp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data) {
- LOG_DEBUG("LCID: 0x%04x st: TERM_W4_SEC_COMP evt: %s", p_ccb->local_cid,
- l2c_csm_get_event_name(event));
+ L2CAP_TRACE_EVENT("L2CAP - LCID: 0x%04x st: TERM_W4_SEC_COMP evt: %s",
+ p_ccb->local_cid, l2c_csm_get_event_name(event));
switch (event) {
case L2CEVT_LP_DISCONNECT_IND: /* Link was disconnected */
@@ -461,38 +421,15 @@ static void l2c_csm_term_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
/* Wait for the info resp in next state before sending connect ind (if
* needed) */
if (!p_ccb->p_lcb->w4_info_rsp) {
- LOG_DEBUG("Not waiting for info response, sending connect response");
/* Don't need to get info from peer or already retrieved so continue */
alarm_set_on_mloop(p_ccb->l2c_ccb_timer, L2CAP_CHNL_CONNECT_TIMEOUT_MS,
l2c_ccb_timer_timeout, p_ccb);
+ L2CAP_TRACE_API("L2CAP - Calling Connect_Ind_Cb(), CID: 0x%04x",
+ p_ccb->local_cid);
- if (p_ccb->p_lcb->transport != BT_TRANSPORT_LE) {
- LOG_DEBUG("Not LE connection, sending configure request");
- l2c_csm_send_connect_rsp(p_ccb);
- l2c_csm_send_config_req(p_ccb);
- } else {
- if (p_ccb->ecoc) {
- /* Handle Credit Based Connection */
- LOG_DEBUG("Calling CreditBasedConnect_Ind_Cb(), num of cids: %d",
- p_ccb->p_lcb->pending_ecoc_conn_cnt);
-
- std::vector<uint16_t> pending_cids;
- for (int i = 0; i < p_ccb->p_lcb->pending_ecoc_conn_cnt; i++) {
- uint16_t cid = p_ccb->p_lcb->pending_ecoc_connection_cids[i];
- if (cid != 0) pending_cids.push_back(cid);
- }
-
- (*p_ccb->p_rcb->api.pL2CA_CreditBasedConnectInd_Cb)(
- p_ccb->p_lcb->remote_bd_addr, pending_cids, p_ccb->p_rcb->psm,
- p_ccb->peer_cfg.mtu, p_ccb->remote_id);
- } else {
- /* Handle BLE CoC */
- LOG_DEBUG("Calling Connect_Ind_Cb(), CID: 0x%04x",
- p_ccb->local_cid);
- l2c_csm_send_connect_rsp(p_ccb);
- l2c_csm_indicate_connection_open(p_ccb);
- }
- }
+ (*p_ccb->p_rcb->api.pL2CA_ConnectInd_Cb)(
+ p_ccb->p_lcb->remote_bd_addr, p_ccb->local_cid, p_ccb->p_rcb->psm,
+ p_ccb->remote_id);
} else {
/*
** L2CAP Connect Response will be sent out by 3 sec timer expiration
@@ -504,7 +441,6 @@ static void l2c_csm_term_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
*/
/* Waiting for the info resp, tell the peer to set a longer timer */
- LOG_DEBUG("Waiting for info response, sending connect pending");
l2cu_send_peer_connect_rsp(p_ccb, L2CAP_CONN_PENDING, 0);
}
break;
@@ -519,7 +455,7 @@ static void l2c_csm_term_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
} else {
if (p_ccb->p_lcb->transport == BT_TRANSPORT_LE)
l2cu_reject_ble_connection(
- p_ccb, p_ccb->remote_id,
+ p_ccb->p_lcb, p_ccb->remote_id,
L2CAP_LE_RESULT_INSUFFICIENT_AUTHENTICATION);
else
l2cu_send_peer_connect_rsp(p_ccb, L2CAP_CONN_SECURITY_BLOCK, 0);
@@ -548,20 +484,15 @@ static void l2c_csm_term_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
case L2CEVT_TIMEOUT:
/* SM4 related. */
- acl_disconnect_from_handle(p_ccb->p_lcb->Handle(), HCI_ERR_AUTH_FAILURE);
+ btsnd_hcic_disconnect(p_ccb->p_lcb->handle, HCI_ERR_AUTH_FAILURE);
break;
case L2CEVT_SEC_RE_SEND_CMD: /* BTM has enough info to proceed */
btm_sec_l2cap_access_req(p_ccb->p_lcb->remote_bd_addr, p_ccb->p_rcb->psm,
- false, &l2c_link_sec_comp, p_ccb);
+ p_ccb->p_lcb->handle, false, &l2c_link_sec_comp,
+ p_ccb);
break;
-
- default:
- LOG_ERROR("Handling unexpected event:%s", l2c_csm_get_event_name(event));
}
- LOG_DEBUG("Exit chnl_state=%s [%d], event=%s [%d]",
- channel_state_text(p_ccb->chnl_state).c_str(), p_ccb->chnl_state,
- l2c_csm_get_event_name(event), event);
}
/*******************************************************************************
@@ -574,18 +505,16 @@ static void l2c_csm_term_w4_sec_comp(tL2C_CCB* p_ccb, tL2CEVT event,
* Returns void
*
******************************************************************************/
-static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data) {
tL2C_CONN_INFO* p_ci = (tL2C_CONN_INFO*)p_data;
tL2CA_DISCONNECT_IND_CB* disconnect_ind =
p_ccb->p_rcb->api.pL2CA_DisconnectInd_Cb;
- tL2CA_CREDIT_BASED_CONNECT_CFM_CB* credit_based_connect_cfm =
- p_ccb->p_rcb->api.pL2CA_CreditBasedConnectCfm_Cb;
+ tL2CA_CONNECT_CFM_CB* connect_cfm = p_ccb->p_rcb->api.pL2CA_ConnectCfm_Cb;
uint16_t local_cid = p_ccb->local_cid;
- tL2C_LCB* p_lcb = p_ccb->p_lcb;
- LOG_DEBUG("LCID: 0x%04x st: W4_L2CAP_CON_RSP evt: %s", p_ccb->local_cid,
- l2c_csm_get_event_name(event));
+ L2CAP_TRACE_EVENT("L2CAP - LCID: 0x%04x st: W4_L2CAP_CON_RSP evt: %s",
+ p_ccb->local_cid, l2c_csm_get_event_name(event));
switch (event) {
case L2CEVT_LP_DISCONNECT_IND: /* Link was disconnected */
@@ -596,8 +525,9 @@ static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
p_ccb->chnl_state = CST_CLOSED;
if ((p_ccb->flags & CCB_FLAG_NO_RETRY) || !p_data ||
(*((uint8_t*)p_data) != HCI_ERR_PEER_USER)) {
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
+ p_ccb->local_cid);
l2cu_release_ccb(p_ccb);
(*disconnect_ind)(local_cid, false);
}
@@ -610,19 +540,15 @@ static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
/* Connection is completed */
alarm_cancel(p_ccb->l2c_ccb_timer);
p_ccb->chnl_state = CST_OPEN;
- l2c_csm_indicate_connection_open(p_ccb);
- p_ccb->local_conn_cfg = p_ccb->p_rcb->coc_cfg;
- p_ccb->remote_credit_count = p_ccb->p_rcb->coc_cfg.credits;
- l2c_csm_execute(p_ccb, L2CEVT_L2CA_CONNECT_RSP, NULL);
} else {
p_ccb->chnl_state = CST_CONFIG;
alarm_set_on_mloop(p_ccb->l2c_ccb_timer, L2CAP_CHNL_CFG_TIMEOUT_MS,
l2c_ccb_timer_timeout, p_ccb);
}
- LOG_DEBUG("Calling Connect_Cfm_Cb(), CID: 0x%04x, Success",
- p_ccb->local_cid);
+ L2CAP_TRACE_API("L2CAP - Calling Connect_Cfm_Cb(), CID: 0x%04x, Success",
+ p_ccb->local_cid);
- l2c_csm_send_config_req(p_ccb);
+ (*p_ccb->p_rcb->api.pL2CA_ConnectCfm_Cb)(local_cid, L2CAP_CONN_OK);
break;
case L2CEVT_L2CAP_CONNECT_RSP_PND: /* Got peer connect pending */
@@ -630,28 +556,11 @@ static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
alarm_set_on_mloop(p_ccb->l2c_ccb_timer,
L2CAP_CHNL_CONNECT_EXT_TIMEOUT_MS,
l2c_ccb_timer_timeout, p_ccb);
- break;
-
- case L2CEVT_L2CAP_CREDIT_BASED_CONNECT_RSP:
- alarm_cancel(p_ccb->l2c_ccb_timer);
- p_ccb->chnl_state = CST_OPEN;
- LOG_DEBUG(
- "Calling credit_based_connect_cfm(),"
- "cid %d, result 0x%04x",
- p_ccb->local_cid, L2CAP_CONN_OK);
-
- (*credit_based_connect_cfm)(p_lcb->remote_bd_addr, p_ccb->local_cid,
- p_ci->peer_mtu, L2CAP_CONN_OK);
- break;
-
- case L2CEVT_L2CAP_CREDIT_BASED_CONNECT_RSP_NEG:
- LOG_DEBUG(
- "Calling pL2CA_Error_Cb(),"
- "cid %d, result 0x%04x",
- local_cid, p_ci->l2cap_result);
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(local_cid, p_ci->l2cap_result);
-
- l2cu_release_ccb(p_ccb);
+ if (p_ccb->p_rcb->api.pL2CA_ConnectPnd_Cb) {
+ L2CAP_TRACE_API("L2CAP - Calling Connect_Pnd_Cb(), CID: 0x%04x",
+ p_ccb->local_cid);
+ (*p_ccb->p_rcb->api.pL2CA_ConnectPnd_Cb)(p_ccb->local_cid);
+ }
break;
case L2CEVT_L2CAP_CONNECT_RSP_NEG: /* Peer rejected connection */
@@ -659,30 +568,14 @@ static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
<< loghex(p_ccb->local_cid)
<< ", reason=" << loghex(p_ci->l2cap_result);
l2cu_release_ccb(p_ccb);
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(local_cid, L2CAP_CONN_OTHER_ERROR);
+ (*connect_cfm)(local_cid, p_ci->l2cap_result);
break;
case L2CEVT_TIMEOUT:
- LOG(WARNING) << __func__ << ": L2CAP connection timeout";
-
- if (p_ccb->ecoc) {
- for (int i = 0; i < p_lcb->pending_ecoc_conn_cnt; i++) {
- uint16_t cid = p_lcb->pending_ecoc_connection_cids[i];
- tL2C_CCB* temp_p_ccb = l2cu_find_ccb_by_cid(p_lcb, cid);
- LOG(WARNING) << __func__ << ": lcid= " << loghex(cid);
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(p_ccb->local_cid,
- L2CAP_CONN_TIMEOUT);
- l2cu_release_ccb(temp_p_ccb);
- }
- p_lcb->pending_ecoc_conn_cnt = 0;
- memset(p_lcb->pending_ecoc_connection_cids, 0,
- L2CAP_CREDIT_BASED_MAX_CIDS);
-
- } else {
- LOG(WARNING) << __func__ << ": lcid= " << loghex(p_ccb->local_cid);
- l2cu_release_ccb(p_ccb);
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(local_cid, L2CAP_CONN_OTHER_ERROR);
- }
+ LOG(WARNING) << __func__ << ": L2CAP connection timeout, lcid="
+ << loghex(p_ccb->local_cid);
+ l2cu_release_ccb(p_ccb);
+ (*connect_cfm)(local_cid, L2CAP_CONN_TIMEOUT);
break;
case L2CEVT_L2CA_DISCONNECT_REQ: /* Upper wants to disconnect */
@@ -694,7 +587,14 @@ static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
L2CAP_CHNL_DISCONNECT_TIMEOUT_MS,
l2c_ccb_timer_timeout, p_ccb);
} else {
+ tL2CA_DISCONNECT_CFM_CB* disconnect_cfm =
+ p_ccb->p_rcb->api.pL2CA_DisconnectCfm_Cb;
l2cu_release_ccb(p_ccb);
+ if (disconnect_cfm) {
+ L2CAP_TRACE_API("%s: L2CAP - Calling DisconnectCfm_Cb(), CID: 0x%04x",
+ __func__, local_cid);
+ (*disconnect_cfm)(local_cid, L2CAP_CONN_NO_LINK);
+ }
}
break;
@@ -707,7 +607,7 @@ static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
/* Need to have at least one compatible channel to continue */
if (!l2c_fcr_chk_chan_modes(p_ccb)) {
l2cu_release_ccb(p_ccb);
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(local_cid, L2CAP_CONN_OTHER_ERROR);
+ (*connect_cfm)(local_cid, L2CAP_CONN_NO_LINK);
} else {
/* We have feature info, so now send peer connect request */
alarm_set_on_mloop(p_ccb->l2c_ccb_timer, L2CAP_CHNL_CONNECT_TIMEOUT_MS,
@@ -715,13 +615,7 @@ static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
l2cu_send_peer_connect_req(p_ccb); /* Start Connection */
}
break;
-
- default:
- LOG_ERROR("Handling unexpected event:%s", l2c_csm_get_event_name(event));
}
- LOG_DEBUG("Exit chnl_state=%s [%d], event=%s [%d]",
- channel_state_text(p_ccb->chnl_state).c_str(), p_ccb->chnl_state,
- l2c_csm_get_event_name(event), event);
}
/*******************************************************************************
@@ -734,49 +628,25 @@ static void l2c_csm_w4_l2cap_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
* Returns void
*
******************************************************************************/
-static void l2c_csm_w4_l2ca_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_w4_l2ca_connect_rsp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data) {
tL2C_CONN_INFO* p_ci;
tL2CA_DISCONNECT_IND_CB* disconnect_ind =
p_ccb->p_rcb->api.pL2CA_DisconnectInd_Cb;
uint16_t local_cid = p_ccb->local_cid;
- LOG_DEBUG("LCID: 0x%04x st: W4_L2CA_CON_RSP evt: %s", p_ccb->local_cid,
- l2c_csm_get_event_name(event));
+ L2CAP_TRACE_EVENT("L2CAP - LCID: 0x%04x st: W4_L2CA_CON_RSP evt: %s",
+ p_ccb->local_cid, l2c_csm_get_event_name(event));
switch (event) {
case L2CEVT_LP_DISCONNECT_IND: /* Link was disconnected */
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
+ p_ccb->local_cid);
l2cu_release_ccb(p_ccb);
(*disconnect_ind)(local_cid, false);
break;
- case L2CEVT_L2CA_CREDIT_BASED_CONNECT_RSP:
- p_ci = (tL2C_CONN_INFO*)p_data;
- if (p_ccb->p_lcb && p_ccb->p_lcb->transport != BT_TRANSPORT_LE) {
- LOG_WARN("LE link doesn't exist");
- return;
- }
- l2cu_send_peer_credit_based_conn_res(p_ccb, p_ci->lcids,
- p_ci->l2cap_result);
- alarm_cancel(p_ccb->l2c_ccb_timer);
-
- for (int i = 0; i < p_ccb->p_lcb->pending_ecoc_conn_cnt; i++) {
- uint16_t cid = p_ccb->p_lcb->pending_ecoc_connection_cids[i];
- tL2C_CCB* temp_p_ccb = l2cu_find_ccb_by_cid(p_ccb->p_lcb, cid);
- auto it = std::find(p_ci->lcids.begin(), p_ci->lcids.end(), cid);
- if (it != p_ci->lcids.end()) {
- temp_p_ccb->chnl_state = CST_OPEN;
- } else {
- l2cu_release_ccb(temp_p_ccb);
- }
- }
- p_ccb->p_lcb->pending_ecoc_conn_cnt = 0;
- memset(p_ccb->p_lcb->pending_ecoc_connection_cids, 0,
- L2CAP_CREDIT_BASED_MAX_CIDS);
-
- break;
case L2CEVT_L2CA_CONNECT_RSP:
p_ci = (tL2C_CONN_INFO*)p_data;
if (p_ccb->p_lcb->transport == BT_TRANSPORT_LE) {
@@ -792,15 +662,12 @@ static void l2c_csm_w4_l2ca_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
} else {
/* Result should be OK or PENDING */
if ((!p_ci) || (p_ci->l2cap_result == L2CAP_CONN_OK)) {
- LOG_DEBUG("Sending connection ok for BR_EDR");
l2cu_send_peer_connect_rsp(p_ccb, L2CAP_CONN_OK, 0);
p_ccb->chnl_state = CST_CONFIG;
alarm_set_on_mloop(p_ccb->l2c_ccb_timer, L2CAP_CHNL_CFG_TIMEOUT_MS,
l2c_ccb_timer_timeout, p_ccb);
} else {
/* If pending, stay in same state and start extended timer */
- LOG_DEBUG("Sending connection result %d and status %d",
- p_ci->l2cap_result, p_ci->l2cap_status);
l2cu_send_peer_connect_rsp(p_ccb, p_ci->l2cap_result,
p_ci->l2cap_status);
alarm_set_on_mloop(p_ccb->l2c_ccb_timer,
@@ -810,24 +677,6 @@ static void l2c_csm_w4_l2ca_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
}
break;
- case L2CEVT_L2CA_CREDIT_BASED_CONNECT_RSP_NEG:
- p_ci = (tL2C_CONN_INFO*)p_data;
- if (p_ccb->p_lcb && p_ccb->p_lcb->transport == BT_TRANSPORT_LE) {
- l2cu_send_peer_credit_based_conn_res(p_ccb, p_ci->lcids,
- p_ci->l2cap_result);
- }
- alarm_cancel(p_ccb->l2c_ccb_timer);
- for (int i = 0; i < p_ccb->p_lcb->pending_ecoc_conn_cnt; i++) {
- uint16_t cid = p_ccb->p_lcb->pending_ecoc_connection_cids[i];
- tL2C_CCB* temp_p_ccb = l2cu_find_ccb_by_cid(p_ccb->p_lcb, cid);
- l2cu_release_ccb(temp_p_ccb);
- }
-
- p_ccb->p_lcb->pending_ecoc_conn_cnt = 0;
- memset(p_ccb->p_lcb->pending_ecoc_connection_cids, 0,
- L2CAP_CREDIT_BASED_MAX_CIDS);
-
- break;
case L2CEVT_L2CA_CONNECT_RSP_NEG:
p_ci = (tL2C_CONN_INFO*)p_data;
if (p_ccb->p_lcb->transport == BT_TRANSPORT_LE)
@@ -840,8 +689,9 @@ static void l2c_csm_w4_l2ca_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
case L2CEVT_TIMEOUT:
l2cu_send_peer_connect_rsp(p_ccb, L2CAP_CONN_NO_PSM, 0);
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
+ p_ccb->local_cid);
l2cu_release_ccb(p_ccb);
(*disconnect_ind)(local_cid, false);
break;
@@ -862,17 +712,14 @@ static void l2c_csm_w4_l2ca_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
/* We have feature info, so now give the upper layer connect IND */
alarm_set_on_mloop(p_ccb->l2c_ccb_timer, L2CAP_CHNL_CONNECT_TIMEOUT_MS,
l2c_ccb_timer_timeout, p_ccb);
- LOG_DEBUG("Calling Connect_Ind_Cb(), CID: 0x%04x", p_ccb->local_cid);
+ L2CAP_TRACE_API("L2CAP - Calling Connect_Ind_Cb(), CID: 0x%04x",
+ p_ccb->local_cid);
- l2c_csm_send_connect_rsp(p_ccb);
- l2c_csm_send_config_req(p_ccb);
+ (*p_ccb->p_rcb->api.pL2CA_ConnectInd_Cb)(
+ p_ccb->p_lcb->remote_bd_addr, p_ccb->local_cid, p_ccb->p_rcb->psm,
+ p_ccb->remote_id);
break;
- default:
- LOG_ERROR("Handling unexpected event:%s", l2c_csm_get_event_name(event));
}
- LOG_DEBUG("Exit chnl_state=%s [%d], event=%s [%d]",
- channel_state_text(p_ccb->chnl_state).c_str(), p_ccb->chnl_state,
- l2c_csm_get_event_name(event), event);
}
/*******************************************************************************
@@ -885,131 +732,104 @@ static void l2c_csm_w4_l2ca_connect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
* Returns void
*
******************************************************************************/
-static void l2c_csm_config(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
+static void l2c_csm_config(tL2C_CCB* p_ccb, uint16_t event, void* p_data) {
tL2CAP_CFG_INFO* p_cfg = (tL2CAP_CFG_INFO*)p_data;
tL2CA_DISCONNECT_IND_CB* disconnect_ind =
p_ccb->p_rcb->api.pL2CA_DisconnectInd_Cb;
uint16_t local_cid = p_ccb->local_cid;
uint8_t cfg_result;
- tL2C_LCB* p_lcb = p_ccb->p_lcb;
- tL2C_CCB* temp_p_ccb;
- tL2CAP_LE_CFG_INFO* p_le_cfg = (tL2CAP_LE_CFG_INFO*)p_data;
- LOG_DEBUG("LCID: 0x%04x st: CONFIG evt: %s", p_ccb->local_cid,
- l2c_csm_get_event_name(event));
+ L2CAP_TRACE_EVENT("L2CAP - LCID: 0x%04x st: CONFIG evt: %s",
+ p_ccb->local_cid, l2c_csm_get_event_name(event));
switch (event) {
case L2CEVT_LP_DISCONNECT_IND: /* Link was disconnected */
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
+ p_ccb->local_cid);
l2cu_release_ccb(p_ccb);
(*disconnect_ind)(local_cid, false);
break;
- case L2CEVT_L2CAP_CREDIT_BASED_RECONFIG_REQ:
- /* For ecoc reconfig is handled below in l2c_ble. In case of success
- * let us notify upper layer about the reconfig
- */
- LOG_DEBUG("Calling LeReconfigCompleted_Cb(), CID: 0x%04x",
- p_ccb->local_cid);
-
- (*p_ccb->p_rcb->api.pL2CA_CreditBasedReconfigCompleted_Cb)(
- p_lcb->remote_bd_addr, p_ccb->local_cid, false, p_le_cfg);
- break;
case L2CEVT_L2CAP_CONFIG_REQ: /* Peer config request */
+
cfg_result = l2cu_process_peer_cfg_req(p_ccb, p_cfg);
if (cfg_result == L2CAP_PEER_CFG_OK) {
- LOG_DEBUG("Calling Config_Req_Cb(), CID: 0x%04x, C-bit %d",
- p_ccb->local_cid, (p_cfg->flags & L2CAP_CFG_FLAGS_MASK_CONT));
- l2c_csm_send_config_rsp_ok(p_ccb);
- if (p_ccb->config_done & OB_CFG_DONE) {
- if (p_ccb->remote_config_rsp_result == L2CAP_CFG_OK) {
- l2c_csm_indicate_connection_open(p_ccb);
- } else {
- if (p_ccb->connection_initiator == L2CAP_INITIATOR_LOCAL) {
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(p_ccb->local_cid,
- L2CAP_CFG_FAILED_NO_REASON);
- }
- }
- }
+ L2CAP_TRACE_EVENT(
+ "L2CAP - Calling Config_Req_Cb(), CID: 0x%04x, C-bit %d",
+ p_ccb->local_cid, (p_cfg->flags & L2CAP_CFG_FLAGS_MASK_CONT));
+ (*p_ccb->p_rcb->api.pL2CA_ConfigInd_Cb)(p_ccb->local_cid, p_cfg);
} else if (cfg_result == L2CAP_PEER_CFG_DISCONNECT) {
/* Disconnect if channels are incompatible */
- LOG_DEBUG("incompatible configurations disconnect");
+ L2CAP_TRACE_EVENT("L2CAP - incompatible configurations disconnect");
l2cu_disconnect_chnl(p_ccb);
- } else /* Return error to peer so it can renegotiate if possible */
+ } else /* Return error to peer so he can renegotiate if possible */
{
- LOG_DEBUG("incompatible configurations trying reconfig");
+ L2CAP_TRACE_EVENT(
+ "L2CAP - incompatible configurations trying reconfig");
l2cu_send_peer_config_rsp(p_ccb, p_cfg);
}
break;
- case L2CEVT_L2CAP_CREDIT_BASED_RECONFIG_RSP:
- p_ccb->config_done |= OB_CFG_DONE;
- p_ccb->config_done |= RECONFIG_FLAG;
- p_ccb->chnl_state = CST_OPEN;
- alarm_cancel(p_ccb->l2c_ccb_timer);
-
- LOG_DEBUG("Calling Config_Rsp_Cb(), CID: 0x%04x", p_ccb->local_cid);
-
- p_ccb->p_rcb->api.pL2CA_CreditBasedReconfigCompleted_Cb(
- p_lcb->remote_bd_addr, p_ccb->local_cid, true, p_le_cfg);
-
- break;
case L2CEVT_L2CAP_CONFIG_RSP: /* Peer config response */
l2cu_process_peer_cfg_rsp(p_ccb, p_cfg);
- /* TBD: When config options grow beyong minimum MTU (48 bytes)
- * logic needs to be added to handle responses with
- * continuation bit set in flags field.
- * 1. Send additional config request out until C-bit is cleared in
- * response
- */
- p_ccb->config_done |= OB_CFG_DONE;
-
- if (p_ccb->config_done & IB_CFG_DONE) {
- /* Verify two sides are in compatible modes before continuing */
- if (p_ccb->our_cfg.fcr.mode != p_ccb->peer_cfg.fcr.mode) {
- l2cu_send_peer_disc_req(p_ccb);
- LOG_WARN(
- "Calling Disconnect_Ind_Cb(Incompatible CFG), CID: "
- "0x%04x No Conf Needed",
- p_ccb->local_cid);
- l2cu_release_ccb(p_ccb);
- (*disconnect_ind)(local_cid, false);
- break;
- }
-
- p_ccb->config_done |= RECONFIG_FLAG;
- p_ccb->chnl_state = CST_OPEN;
- l2c_link_adjust_chnl_allocation();
- alarm_cancel(p_ccb->l2c_ccb_timer);
+ if (p_cfg->result != L2CAP_CFG_PENDING) {
+ /* TBD: When config options grow beyong minimum MTU (48 bytes)
+ * logic needs to be added to handle responses with
+ * continuation bit set in flags field.
+ * 1. Send additional config request out until C-bit is cleared in
+ * response
+ */
+ p_ccb->config_done |= OB_CFG_DONE;
+
+ if (p_ccb->config_done & IB_CFG_DONE) {
+ /* Verify two sides are in compatible modes before continuing */
+ if (p_ccb->our_cfg.fcr.mode != p_ccb->peer_cfg.fcr.mode) {
+ l2cu_send_peer_disc_req(p_ccb);
+ L2CAP_TRACE_WARNING(
+ "L2CAP - Calling Disconnect_Ind_Cb(Incompatible CFG), CID: "
+ "0x%04x No Conf Needed",
+ p_ccb->local_cid);
+ l2cu_release_ccb(p_ccb);
+ (*disconnect_ind)(local_cid, false);
+ break;
+ }
- /* If using eRTM and waiting for an ACK, restart the ACK timer */
- if (p_ccb->fcrb.wait_ack) l2c_fcr_start_timer(p_ccb);
+ p_ccb->config_done |= RECONFIG_FLAG;
+ p_ccb->chnl_state = CST_OPEN;
+ l2c_link_adjust_chnl_allocation();
+ alarm_cancel(p_ccb->l2c_ccb_timer);
- /*
- ** check p_ccb->our_cfg.fcr.mon_tout and
- *p_ccb->our_cfg.fcr.rtrans_tout
- ** we may set them to zero when sending config request during
- *renegotiation
- */
- if ((p_ccb->our_cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) &&
- ((p_ccb->our_cfg.fcr.mon_tout == 0) ||
- (p_ccb->our_cfg.fcr.rtrans_tout))) {
- l2c_fcr_adj_monitor_retran_timeout(p_ccb);
- }
+ /* If using eRTM and waiting for an ACK, restart the ACK timer */
+ if (p_ccb->fcrb.wait_ack) l2c_fcr_start_timer(p_ccb);
+
+ /*
+ ** check p_ccb->our_cfg.fcr.mon_tout and
+ *p_ccb->our_cfg.fcr.rtrans_tout
+ ** we may set them to zero when sending config request during
+ *renegotiation
+ */
+ if ((p_ccb->our_cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) &&
+ ((p_ccb->our_cfg.fcr.mon_tout == 0) ||
+ (p_ccb->our_cfg.fcr.rtrans_tout))) {
+ l2c_fcr_adj_monitor_retran_timeout(p_ccb);
+ }
- /* See if we can forward anything on the hold queue */
- if (!fixed_queue_is_empty(p_ccb->xmit_hold_q)) {
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, NULL);
+#if (L2CAP_ERTM_STATS == TRUE)
+ p_ccb->fcrb.connect_tick_count =
+ bluetooth::common::time_get_os_boottime_ms();
+#endif
+ /* See if we can forward anything on the hold queue */
+ if (!fixed_queue_is_empty(p_ccb->xmit_hold_q)) {
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, NULL);
+ }
}
}
- LOG_DEBUG("Calling Config_Rsp_Cb(), CID: 0x%04x", p_ccb->local_cid);
- p_ccb->remote_config_rsp_result = p_cfg->result;
- if (p_ccb->config_done & IB_CFG_DONE) {
- l2c_csm_indicate_connection_open(p_ccb);
- }
+ L2CAP_TRACE_API("L2CAP - Calling Config_Rsp_Cb(), CID: 0x%04x",
+ p_ccb->local_cid);
+ (*p_ccb->p_rcb->api.pL2CA_ConfigCfm_Cb)(p_ccb->local_cid, p_cfg);
break;
case L2CEVT_L2CAP_CONFIG_RSP_NEG: /* Peer config error rsp */
@@ -1018,12 +838,10 @@ static void l2c_csm_config(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
/* If failure was channel mode try to renegotiate */
if (!l2c_fcr_renegotiate_chan(p_ccb, p_cfg)) {
- LOG_DEBUG("Calling Config_Rsp_Cb(), CID: 0x%04x, Failure: %d",
- p_ccb->local_cid, p_cfg->result);
- if (p_ccb->connection_initiator == L2CAP_INITIATOR_LOCAL) {
- (*p_ccb->p_rcb->api.pL2CA_Error_Cb)(p_ccb->local_cid,
- L2CAP_CFG_FAILED_NO_REASON);
- }
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Config_Rsp_Cb(), CID: 0x%04x, Failure: %d",
+ p_ccb->local_cid, p_cfg->result);
+ (*p_ccb->p_rcb->api.pL2CA_ConfigCfm_Cb)(p_ccb->local_cid, p_cfg);
}
break;
@@ -1031,17 +849,12 @@ static void l2c_csm_config(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
alarm_set_on_mloop(p_ccb->l2c_ccb_timer, L2CAP_CHNL_DISCONNECT_TIMEOUT_MS,
l2c_ccb_timer_timeout, p_ccb);
p_ccb->chnl_state = CST_W4_L2CA_DISCONNECT_RSP;
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x Conf Needed",
+ p_ccb->local_cid);
(*p_ccb->p_rcb->api.pL2CA_DisconnectInd_Cb)(p_ccb->local_cid, true);
- l2c_csm_send_disconnect_rsp(p_ccb);
break;
- case L2CEVT_L2CA_CREDIT_BASED_RECONFIG_REQ:
- l2cu_send_credit_based_reconfig_req(p_ccb, (tL2CAP_LE_CFG_INFO*)p_data);
- alarm_set_on_mloop(p_ccb->l2c_ccb_timer, L2CAP_CHNL_CFG_TIMEOUT_MS,
- l2c_ccb_timer_timeout, p_ccb);
- break;
case L2CEVT_L2CA_CONFIG_REQ: /* Upper layer config req */
l2cu_process_our_cfg_req(p_ccb, p_cfg);
l2cu_send_peer_config_req(p_ccb, p_cfg);
@@ -1052,14 +865,28 @@ static void l2c_csm_config(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
case L2CEVT_L2CA_CONFIG_RSP: /* Upper layer config rsp */
l2cu_process_our_cfg_rsp(p_ccb, p_cfg);
+ /* Not finished if continuation flag is set */
+ if ((p_cfg->flags & L2CAP_CFG_FLAGS_MASK_CONT) ||
+ (p_cfg->result == L2CAP_CFG_PENDING)) {
+ /* Send intermediate response; remain in cfg state */
+ l2cu_send_peer_config_rsp(p_ccb, p_cfg);
+ break;
+ }
+
+ /* Local config done; clear cached configuration in case reconfig takes
+ * place later */
+ p_ccb->peer_cfg.mtu_present = false;
+ p_ccb->peer_cfg.flush_to_present = false;
+ p_ccb->peer_cfg.qos_present = false;
+
p_ccb->config_done |= IB_CFG_DONE;
if (p_ccb->config_done & OB_CFG_DONE) {
/* Verify two sides are in compatible modes before continuing */
if (p_ccb->our_cfg.fcr.mode != p_ccb->peer_cfg.fcr.mode) {
l2cu_send_peer_disc_req(p_ccb);
- LOG_WARN(
- "Calling Disconnect_Ind_Cb(Incompatible CFG), CID: "
+ L2CAP_TRACE_WARNING(
+ "L2CAP - Calling Disconnect_Ind_Cb(Incompatible CFG), CID: "
"0x%04x No Conf Needed",
p_ccb->local_cid);
l2cu_release_ccb(p_ccb);
@@ -1078,13 +905,24 @@ static void l2c_csm_config(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
/* If using eRTM and waiting for an ACK, restart the ACK timer */
if (p_ccb->fcrb.wait_ack) l2c_fcr_start_timer(p_ccb);
+#if (L2CAP_ERTM_STATS == TRUE)
+ p_ccb->fcrb.connect_tick_count =
+ bluetooth::common::time_get_os_boottime_ms();
+#endif
+
/* See if we can forward anything on the hold queue */
if ((p_ccb->chnl_state == CST_OPEN) &&
(!fixed_queue_is_empty(p_ccb->xmit_hold_q))) {
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, NULL);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, NULL);
}
break;
+ case L2CEVT_L2CA_CONFIG_RSP_NEG: /* Upper layer config reject */
+ l2cu_send_peer_config_rsp(p_ccb, p_cfg);
+ alarm_set_on_mloop(p_ccb->l2c_ccb_timer, L2CAP_CHNL_CFG_TIMEOUT_MS,
+ l2c_ccb_timer_timeout, p_ccb);
+ break;
+
case L2CEVT_L2CA_DISCONNECT_REQ: /* Upper wants to disconnect */
l2cu_send_peer_disc_req(p_ccb);
p_ccb->chnl_state = CST_W4_L2CAP_DISCONNECT_RSP;
@@ -1093,24 +931,24 @@ static void l2c_csm_config(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
break;
case L2CEVT_L2CAP_DATA: /* Peer data packet rcvd */
- LOG_DEBUG("Calling DataInd_Cb(), CID: 0x%04x", p_ccb->local_cid);
+ L2CAP_TRACE_API("L2CAP - Calling DataInd_Cb(), CID: 0x%04x",
+ p_ccb->local_cid);
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
if (p_ccb->local_cid >= L2CAP_FIRST_FIXED_CHNL &&
p_ccb->local_cid <= L2CAP_LAST_FIXED_CHNL) {
if (p_ccb->local_cid < L2CAP_BASE_APPL_CID) {
if (l2cb.fixed_reg[p_ccb->local_cid - L2CAP_FIRST_FIXED_CHNL]
- .pL2CA_FixedData_Cb != nullptr) {
- p_ccb->metrics.rx(static_cast<BT_HDR*>(p_data)->len);
+ .pL2CA_FixedData_Cb)
(*l2cb.fixed_reg[p_ccb->local_cid - L2CAP_FIRST_FIXED_CHNL]
.pL2CA_FixedData_Cb)(p_ccb->local_cid,
p_ccb->p_lcb->remote_bd_addr,
(BT_HDR*)p_data);
- } else {
- if (p_data != nullptr) osi_free_and_reset(&p_data);
- }
+ else
+ osi_free(p_data);
break;
}
}
- if (p_data) p_ccb->metrics.rx(static_cast<BT_HDR*>(p_data)->len);
+#endif
(*p_ccb->p_rcb->api.pL2CA_DataInd_Cb)(p_ccb->local_cid, (BT_HDR*)p_data);
break;
@@ -1122,33 +960,14 @@ static void l2c_csm_config(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
break;
case L2CEVT_TIMEOUT:
- if (p_ccb->ecoc) {
- for (temp_p_ccb = p_lcb->ccb_queue.p_first_ccb; temp_p_ccb;
- temp_p_ccb = temp_p_ccb->p_next_ccb) {
- if ((temp_p_ccb->in_use) && (temp_p_ccb->reconfig_started)) {
- (*temp_p_ccb->p_rcb->api.pL2CA_DisconnectInd_Cb)(
- temp_p_ccb->local_cid, false);
- l2cu_release_ccb(temp_p_ccb);
- }
- }
-
- acl_disconnect_from_handle(p_ccb->p_lcb->Handle(),
- HCI_ERR_CONN_CAUSE_LOCAL_HOST);
- return;
- }
-
l2cu_send_peer_disc_req(p_ccb);
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
+ p_ccb->local_cid);
l2cu_release_ccb(p_ccb);
(*disconnect_ind)(local_cid, false);
break;
- default:
- LOG_ERROR("Handling unexpected event:%s", l2c_csm_get_event_name(event));
}
- LOG_DEBUG("Exit chnl_state=%s [%d], event=%s [%d]",
- channel_state_text(p_ccb->chnl_state).c_str(), p_ccb->chnl_state,
- l2c_csm_get_event_name(event), event);
}
/*******************************************************************************
@@ -1161,36 +980,32 @@ static void l2c_csm_config(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
* Returns void
*
******************************************************************************/
-static void l2c_csm_open(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
+static void l2c_csm_open(tL2C_CCB* p_ccb, uint16_t event, void* p_data) {
uint16_t local_cid = p_ccb->local_cid;
tL2CAP_CFG_INFO* p_cfg;
tL2C_CHNL_STATE tempstate;
uint8_t tempcfgdone;
uint8_t cfg_result;
- uint16_t credit = 0;
- tL2CAP_LE_CFG_INFO* p_le_cfg = (tL2CAP_LE_CFG_INFO*)p_data;
+ uint16_t* credit;
- LOG_DEBUG("LCID: 0x%04x st: OPEN evt: %s", p_ccb->local_cid,
- l2c_csm_get_event_name(event));
+ L2CAP_TRACE_EVENT("L2CAP - LCID: 0x%04x st: OPEN evt: %s", p_ccb->local_cid,
+ l2c_csm_get_event_name(event));
switch (event) {
case L2CEVT_LP_DISCONNECT_IND: /* Link was disconnected */
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
+ p_ccb->local_cid);
l2cu_release_ccb(p_ccb);
if (p_ccb->p_rcb)
(*p_ccb->p_rcb->api.pL2CA_DisconnectInd_Cb)(local_cid, false);
break;
- case L2CEVT_L2CAP_CREDIT_BASED_RECONFIG_REQ:
- /* For ecoc reconfig is handled below in l2c_ble. In case of success
- * let us notify upper layer about the reconfig
- */
- LOG_DEBUG("Calling LeReconfigCompleted_Cb(), CID: 0x%04x",
- p_ccb->local_cid);
-
- (*p_ccb->p_rcb->api.pL2CA_CreditBasedReconfigCompleted_Cb)(
- p_ccb->p_lcb->remote_bd_addr, p_ccb->local_cid, false, p_le_cfg);
+ case L2CEVT_LP_QOS_VIOLATION_IND: /* QOS violation */
+ /* Tell upper layer. If service guaranteed, then clear the channel */
+ if (p_ccb->p_rcb->api.pL2CA_QoSViolationInd_Cb)
+ (*p_ccb->p_rcb->api.pL2CA_QoSViolationInd_Cb)(
+ p_ccb->p_lcb->remote_bd_addr);
break;
case L2CEVT_L2CAP_CONFIG_REQ: /* Peer config request */
@@ -1199,10 +1014,6 @@ static void l2c_csm_open(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
tempstate = p_ccb->chnl_state;
tempcfgdone = p_ccb->config_done;
p_ccb->chnl_state = CST_CONFIG;
- // clear cached configuration in case reconfig takes place later
- p_ccb->peer_cfg.mtu_present = false;
- p_ccb->peer_cfg.flush_to_present = false;
- p_ccb->peer_cfg.qos_present = false;
p_ccb->config_done &= ~IB_CFG_DONE;
alarm_set_on_mloop(p_ccb->l2c_ccb_timer, L2CAP_CHNL_CFG_TIMEOUT_MS,
@@ -1211,7 +1022,6 @@ static void l2c_csm_open(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
cfg_result = l2cu_process_peer_cfg_req(p_ccb, p_cfg);
if (cfg_result == L2CAP_PEER_CFG_OK) {
(*p_ccb->p_rcb->api.pL2CA_ConfigInd_Cb)(p_ccb->local_cid, p_cfg);
- l2c_csm_send_config_rsp_ok(p_ccb);
}
/* Error in config parameters: reset state and config flag */
@@ -1232,33 +1042,40 @@ static void l2c_csm_open(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
case L2CEVT_L2CAP_DISCONNECT_REQ: /* Peer disconnected request */
if (p_ccb->p_lcb->transport != BT_TRANSPORT_LE) {
- if (!BTM_SetLinkPolicyActiveMode(p_ccb->p_lcb->remote_bd_addr)) {
- LOG_WARN("Unable to set link policy active");
+ /* Make sure we are not in sniff mode */
+ {
+ tBTM_PM_PWR_MD settings;
+ memset((void*)&settings, 0, sizeof(settings));
+ settings.mode = BTM_PM_MD_ACTIVE;
+ BTM_SetPowerMode(BTM_PM_SET_ONLY_ID, p_ccb->p_lcb->remote_bd_addr,
+ &settings);
}
}
p_ccb->chnl_state = CST_W4_L2CA_DISCONNECT_RSP;
alarm_set_on_mloop(p_ccb->l2c_ccb_timer, L2CAP_CHNL_DISCONNECT_TIMEOUT_MS,
l2c_ccb_timer_timeout, p_ccb);
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x Conf Needed",
+ p_ccb->local_cid);
(*p_ccb->p_rcb->api.pL2CA_DisconnectInd_Cb)(p_ccb->local_cid, true);
- l2c_csm_send_disconnect_rsp(p_ccb);
break;
case L2CEVT_L2CAP_DATA: /* Peer data packet rcvd */
- if ((p_ccb->p_rcb) && (p_ccb->p_rcb->api.pL2CA_DataInd_Cb)) {
- p_ccb->metrics.rx(static_cast<BT_HDR*>(p_data)->len);
+ if ((p_ccb->p_rcb) && (p_ccb->p_rcb->api.pL2CA_DataInd_Cb))
(*p_ccb->p_rcb->api.pL2CA_DataInd_Cb)(p_ccb->local_cid,
(BT_HDR*)p_data);
- }
break;
case L2CEVT_L2CA_DISCONNECT_REQ: /* Upper wants to disconnect */
if (p_ccb->p_lcb->transport != BT_TRANSPORT_LE) {
/* Make sure we are not in sniff mode */
- if (!BTM_SetLinkPolicyActiveMode(p_ccb->p_lcb->remote_bd_addr)) {
- LOG_WARN("Unable to set link policy active");
+ {
+ tBTM_PM_PWR_MD settings;
+ memset((void*)&settings, 0, sizeof(settings));
+ settings.mode = BTM_PM_MD_ACTIVE;
+ BTM_SetPowerMode(BTM_PM_SET_ONLY_ID, p_ccb->p_lcb->remote_bd_addr,
+ &settings);
}
}
@@ -1274,25 +1091,18 @@ static void l2c_csm_open(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
case L2CEVT_L2CA_DATA_WRITE: /* Upper layer data to send */
l2c_enqueue_peer_data(p_ccb, (BT_HDR*)p_data);
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, NULL);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, NULL);
break;
- case L2CEVT_L2CA_CREDIT_BASED_RECONFIG_REQ:
+ case L2CEVT_L2CA_CONFIG_REQ: /* Upper layer config req */
p_ccb->chnl_state = CST_CONFIG;
- p_ccb->config_done &= ~OB_CFG_DONE;
-
- l2cu_send_credit_based_reconfig_req(p_ccb, (tL2CAP_LE_CFG_INFO*)p_data);
-
+ p_ccb->config_done &= ~CFG_DONE_MASK;
+ l2cu_process_our_cfg_req(p_ccb, (tL2CAP_CFG_INFO*)p_data);
+ l2cu_send_peer_config_req(p_ccb, (tL2CAP_CFG_INFO*)p_data);
alarm_set_on_mloop(p_ccb->l2c_ccb_timer, L2CAP_CHNL_CFG_TIMEOUT_MS,
l2c_ccb_timer_timeout, p_ccb);
break;
- case L2CEVT_L2CA_CONFIG_REQ: /* Upper layer config req */
- LOG_ERROR(
- "Dropping L2CAP re-config request because there is no usage and "
- "should not be invoked");
- break;
-
case L2CEVT_TIMEOUT:
/* Process the monitor/retransmission time-outs in flow control/retrans
* mode */
@@ -1305,30 +1115,31 @@ static void l2c_csm_open(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
break;
case L2CEVT_L2CA_SEND_FLOW_CONTROL_CREDIT:
- LOG_DEBUG("Sending credit");
- credit = *(uint16_t*)p_data;
- l2cble_send_flow_control_credit(p_ccb, credit);
+ L2CAP_TRACE_DEBUG("%s Sending credit", __func__);
+ credit = (uint16_t*)p_data;
+ l2cble_send_flow_control_credit(p_ccb, *credit);
break;
case L2CEVT_L2CAP_RECV_FLOW_CONTROL_CREDIT:
- credit = *(uint16_t*)p_data;
- LOG_DEBUG("Credits received %d", credit);
- if ((p_ccb->peer_conn_cfg.credits + credit) > L2CAP_LE_CREDIT_MAX) {
+ credit = (uint16_t*)p_data;
+ L2CAP_TRACE_DEBUG("%s Credits received %d", __func__, *credit);
+ if ((p_ccb->peer_conn_cfg.credits + *credit) > L2CAP_LE_CREDIT_MAX) {
/* we have received credits more than max coc credits,
* so disconnecting the Le Coc Channel
*/
l2cble_send_peer_disc_req(p_ccb);
} else {
- p_ccb->peer_conn_cfg.credits += credit;
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, NULL);
+ p_ccb->peer_conn_cfg.credits += *credit;
+
+ tL2CA_CREDITS_RECEIVED_CB* cr_cb =
+ p_ccb->p_rcb->api.pL2CA_CreditsReceived_Cb;
+ if (p_ccb->p_lcb->transport == BT_TRANSPORT_LE && (cr_cb)) {
+ (*cr_cb)(p_ccb->local_cid, *credit, p_ccb->peer_conn_cfg.credits);
+ }
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, NULL);
}
break;
- default:
- LOG_ERROR("Handling unexpected event:%s", l2c_csm_get_event_name(event));
}
- LOG_DEBUG("Exit chnl_state=%s [%d], event=%s [%d]",
- channel_state_text(p_ccb->chnl_state).c_str(), p_ccb->chnl_state,
- l2c_csm_get_event_name(event), event);
}
/*******************************************************************************
@@ -1341,37 +1152,51 @@ static void l2c_csm_open(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data) {
* Returns void
*
******************************************************************************/
-static void l2c_csm_w4_l2cap_disconnect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_w4_l2cap_disconnect_rsp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data) {
- LOG_DEBUG("LCID: 0x%04x st: W4_L2CAP_DISC_RSP evt: %s", p_ccb->local_cid,
- l2c_csm_get_event_name(event));
+ tL2CA_DISCONNECT_CFM_CB* disconnect_cfm =
+ p_ccb->p_rcb->api.pL2CA_DisconnectCfm_Cb;
+ uint16_t local_cid = p_ccb->local_cid;
+
+ L2CAP_TRACE_EVENT("L2CAP - LCID: 0x%04x st: W4_L2CAP_DISC_RSP evt: %s",
+ p_ccb->local_cid, l2c_csm_get_event_name(event));
switch (event) {
case L2CEVT_L2CAP_DISCONNECT_RSP: /* Peer disconnect response */
l2cu_release_ccb(p_ccb);
+ if (disconnect_cfm) {
+ L2CAP_TRACE_API("L2CAP - Calling DisconnectCfm_Cb(), CID: 0x%04x",
+ local_cid);
+ (*disconnect_cfm)(local_cid, L2CAP_DISC_OK);
+ }
break;
case L2CEVT_L2CAP_DISCONNECT_REQ: /* Peer disconnect request */
l2cu_send_peer_disc_rsp(p_ccb->p_lcb, p_ccb->remote_id, p_ccb->local_cid,
p_ccb->remote_cid);
l2cu_release_ccb(p_ccb);
+ if (disconnect_cfm) {
+ L2CAP_TRACE_API("L2CAP - Calling DisconnectCfm_Cb(), CID: 0x%04x",
+ local_cid);
+ (*disconnect_cfm)(local_cid, L2CAP_DISC_OK);
+ }
break;
case L2CEVT_LP_DISCONNECT_IND: /* Link was disconnected */
case L2CEVT_TIMEOUT: /* Timeout */
l2cu_release_ccb(p_ccb);
+ if (disconnect_cfm) {
+ L2CAP_TRACE_API("L2CAP - Calling DisconnectCfm_Cb(), CID: 0x%04x",
+ local_cid);
+ (*disconnect_cfm)(local_cid, L2CAP_DISC_TIMEOUT);
+ }
break;
case L2CEVT_L2CAP_DATA: /* Peer data packet rcvd */
case L2CEVT_L2CA_DATA_WRITE: /* Upper layer data to send */
osi_free(p_data);
break;
- default:
- LOG_ERROR("Handling unexpected event:%s", l2c_csm_get_event_name(event));
}
- LOG_DEBUG("Exit chnl_state=%s [%d], event=%s [%d]",
- channel_state_text(p_ccb->chnl_state).c_str(), p_ccb->chnl_state,
- l2c_csm_get_event_name(event), event);
}
/*******************************************************************************
@@ -1384,19 +1209,20 @@ static void l2c_csm_w4_l2cap_disconnect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
* Returns void
*
******************************************************************************/
-static void l2c_csm_w4_l2ca_disconnect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
+static void l2c_csm_w4_l2ca_disconnect_rsp(tL2C_CCB* p_ccb, uint16_t event,
void* p_data) {
tL2CA_DISCONNECT_IND_CB* disconnect_ind =
p_ccb->p_rcb->api.pL2CA_DisconnectInd_Cb;
uint16_t local_cid = p_ccb->local_cid;
- LOG_DEBUG("LCID: 0x%04x st: W4_L2CA_DISC_RSP evt: %s", p_ccb->local_cid,
- l2c_csm_get_event_name(event));
+ L2CAP_TRACE_EVENT("L2CAP - LCID: 0x%04x st: W4_L2CA_DISC_RSP evt: %s",
+ p_ccb->local_cid, l2c_csm_get_event_name(event));
switch (event) {
case L2CEVT_LP_DISCONNECT_IND: /* Link was disconnected */
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
+ p_ccb->local_cid);
l2cu_release_ccb(p_ccb);
(*disconnect_ind)(local_cid, false);
break;
@@ -1404,8 +1230,9 @@ static void l2c_csm_w4_l2ca_disconnect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
case L2CEVT_TIMEOUT:
l2cu_send_peer_disc_rsp(p_ccb->p_lcb, p_ccb->remote_id, p_ccb->local_cid,
p_ccb->remote_cid);
- LOG_DEBUG("Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
- p_ccb->local_cid);
+ L2CAP_TRACE_API(
+ "L2CAP - Calling Disconnect_Ind_Cb(), CID: 0x%04x No Conf Needed",
+ p_ccb->local_cid);
l2cu_release_ccb(p_ccb);
(*disconnect_ind)(local_cid, false);
break;
@@ -1421,12 +1248,7 @@ static void l2c_csm_w4_l2ca_disconnect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
case L2CEVT_L2CA_DATA_WRITE: /* Upper layer data to send */
osi_free(p_data);
break;
- default:
- LOG_ERROR("Handling unexpected event:%s", l2c_csm_get_event_name(event));
}
- LOG_DEBUG("Exit chnl_state=%s [%d], event=%s [%d]",
- channel_state_text(p_ccb->chnl_state).c_str(), p_ccb->chnl_state,
- l2c_csm_get_event_name(event), event);
}
/*******************************************************************************
@@ -1440,7 +1262,7 @@ static void l2c_csm_w4_l2ca_disconnect_rsp(tL2C_CCB* p_ccb, tL2CEVT event,
* Returns pointer to the name
*
******************************************************************************/
-static const char* l2c_csm_get_event_name(tL2CEVT event) {
+static const char* l2c_csm_get_event_name(uint16_t event) {
switch (event) {
case L2CEVT_LP_CONNECT_CFM: /* Lower layer connect confirm */
return ("LOWER_LAYER_CONNECT_CFM");
@@ -1450,6 +1272,12 @@ static const char* l2c_csm_get_event_name(tL2CEVT event) {
return ("LOWER_LAYER_CONNECT_IND");
case L2CEVT_LP_DISCONNECT_IND: /* Lower layer disconnect indication */
return ("LOWER_LAYER_DISCONNECT_IND");
+ case L2CEVT_LP_QOS_CFM: /* Lower layer QOS confirmation */
+ return ("LOWER_LAYER_QOS_CFM");
+ case L2CEVT_LP_QOS_CFM_NEG: /* Lower layer QOS confirmation (failed)*/
+ return ("LOWER_LAYER_QOS_CFM_NEG");
+ case L2CEVT_LP_QOS_VIOLATION_IND: /* Lower layer QOS violation indication */
+ return ("LOWER_LAYER_QOS_VIOLATION_IND");
case L2CEVT_SEC_COMP: /* Security cleared successfully */
return ("SECURITY_COMPLETE");
@@ -1487,6 +1315,8 @@ static const char* l2c_csm_get_event_name(tL2CEVT event) {
return ("UPPER_LAYER_CONFIG_REQ");
case L2CEVT_L2CA_CONFIG_RSP: /* Upper layer config response */
return ("UPPER_LAYER_CONFIG_RSP");
+ case L2CEVT_L2CA_CONFIG_RSP_NEG: /* Upper layer config response (failed) */
+ return ("UPPER_LAYER_CONFIG_RSP_NEG");
case L2CEVT_L2CA_DISCONNECT_REQ: /* Upper layer disconnect request */
return ("UPPER_LAYER_DISCONNECT_REQ");
case L2CEVT_L2CA_DISCONNECT_RSP: /* Upper layer disconnect response */
@@ -1504,34 +1334,11 @@ static const char* l2c_csm_get_event_name(tL2CEVT event) {
case L2CEVT_ACK_TIMEOUT:
return ("L2CEVT_ACK_TIMEOUT");
case L2CEVT_L2CA_SEND_FLOW_CONTROL_CREDIT: /* Upper layer send credit packet
- */
+ */
return ("SEND_FLOW_CONTROL_CREDIT");
- case L2CEVT_L2CA_CREDIT_BASED_CONNECT_REQ: /* Upper layer credit based
- connect request */
- return ("SEND_CREDIT_BASED_CONNECT_REQ");
- case L2CEVT_L2CA_CREDIT_BASED_CONNECT_RSP: /* Upper layer credit based
- connect response */
- return ("SEND_CREDIT_BASED_CONNECT_RSP");
- case L2CEVT_L2CA_CREDIT_BASED_RECONFIG_REQ: /* Upper layer credit based
- reconfig request */
- return ("SEND_CREDIT_BASED_RECONFIG_REQ");
case L2CEVT_L2CAP_RECV_FLOW_CONTROL_CREDIT: /* Peer send credit packet */
return ("RECV_FLOW_CONTROL_CREDIT");
- case L2CEVT_L2CAP_CREDIT_BASED_CONNECT_REQ: /* Peer send credit based
- connect request */
- return ("RECV_CREDIT_BASED_CONNECT_REQ");
- case L2CEVT_L2CAP_CREDIT_BASED_CONNECT_RSP: /* Peer send credit based
- connect response */
- return ("RECV_CREDIT_BASED_CONNECT_RSP");
- case L2CEVT_L2CAP_CREDIT_BASED_CONNECT_RSP_NEG: /* Peer send reject credit
- based connect response */
- return ("RECV_CREDIT_BASED_CONNECT_RSP_NEG");
- case L2CEVT_L2CAP_CREDIT_BASED_RECONFIG_REQ: /* Peer send credit based
- reconfig request */
- return ("RECV_CREDIT_BASED_RECONFIG_REQ");
- case L2CEVT_L2CAP_CREDIT_BASED_RECONFIG_RSP: /* Peer send credit based
- reconfig response */
- return ("RECV_CREDIT_BASED_RECONFIG_RSP");
+
default:
return ("???? UNKNOWN EVENT");
}
@@ -1548,10 +1355,6 @@ static const char* l2c_csm_get_event_name(tL2CEVT event) {
*
******************************************************************************/
void l2c_enqueue_peer_data(tL2C_CCB* p_ccb, BT_HDR* p_buf) {
- CHECK(p_ccb != nullptr);
-
- p_ccb->metrics.tx(p_buf->len);
-
uint8_t* p;
if (p_ccb->peer_cfg.fcr.mode != L2CAP_FCR_BASIC_MODE) {
@@ -1573,22 +1376,24 @@ void l2c_enqueue_peer_data(tL2C_CCB* p_ccb, BT_HDR* p_buf) {
}
if (p_ccb->xmit_hold_q == NULL) {
- LOG_ERROR(
- "empty queue: p_ccb = %p p_ccb->in_use = %d p_ccb->chnl_state = %d "
+ L2CAP_TRACE_ERROR(
+ "%s: empty queue: p_ccb = %p p_ccb->in_use = %d p_ccb->chnl_state = %d "
"p_ccb->local_cid = %u p_ccb->remote_cid = %u",
- p_ccb, p_ccb->in_use, p_ccb->chnl_state, p_ccb->local_cid,
+ __func__, p_ccb, p_ccb->in_use, p_ccb->chnl_state, p_ccb->local_cid,
p_ccb->remote_cid);
}
fixed_queue_enqueue(p_ccb->xmit_hold_q, p_buf);
l2cu_check_channel_congestion(p_ccb);
+#if (L2CAP_ROUND_ROBIN_CHANNEL_SERVICE == TRUE)
/* if new packet is higher priority than serving ccb and it is not overrun */
if ((p_ccb->p_lcb->rr_pri > p_ccb->ccb_priority) &&
(p_ccb->p_lcb->rr_serv[p_ccb->ccb_priority].quota > 0)) {
/* send out higher priority packet */
p_ccb->p_lcb->rr_pri = p_ccb->ccb_priority;
}
+#endif
/* if we are doing a round robin scheduling, set the flag */
if (p_ccb->p_lcb->link_xmit_quota == 0) l2cb.check_round_robin = true;
diff --git a/stack/l2cap/l2c_fcr.cc b/stack/l2cap/l2c_fcr.cc
index 4e6095c95..3cb7c205d 100644
--- a/stack/l2cap/l2c_fcr.cc
+++ b/stack/l2cap/l2c_fcr.cc
@@ -24,6 +24,7 @@
******************************************************************************/
#include <base/logging.h>
+#include <log/log.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
@@ -37,8 +38,6 @@
#include "l2c_int.h"
#include "l2cdefs.h"
-#include "osi/include/log.h"
-
/* Flag passed to retransmit_i_frames() when all packets should be retransmitted
*/
#define L2C_FCR_RETX_ALL_PKTS 0xFF
@@ -93,9 +92,14 @@ static void process_i_frame(tL2C_CCB* p_ccb, BT_HDR* p_buf, uint16_t ctrl_word,
static bool retransmit_i_frames(tL2C_CCB* p_ccb, uint8_t tx_seq);
static void prepare_I_frame(tL2C_CCB* p_ccb, BT_HDR* p_buf,
bool is_retransmission);
+static void process_stream_frame(tL2C_CCB* p_ccb, BT_HDR* p_buf);
static bool do_sar_reassembly(tL2C_CCB* p_ccb, BT_HDR* p_buf,
uint16_t ctrl_word);
+#if (L2CAP_ERTM_STATS == TRUE)
+static void l2c_fcr_collect_ack_delay(tL2C_CCB* p_ccb, uint8_t num_bufs_acked);
+#endif
+
/*******************************************************************************
*
* Function l2c_fcr_updcrc
@@ -223,6 +227,104 @@ void l2c_fcr_cleanup(tL2C_CCB* p_ccb) {
fixed_queue_free(p_fcrb->retrans_q, osi_free);
p_fcrb->retrans_q = NULL;
+#if (L2CAP_ERTM_STATS == TRUE)
+ if ((p_ccb->local_cid >= L2CAP_BASE_APPL_CID) &&
+ (p_ccb->peer_cfg.fcr.mode == L2CAP_FCR_ERTM_MODE)) {
+ uint64_t dur = bluetooth::common::time_get_os_boottime_ms() -
+ p_ccb->fcrb.connect_tick_count;
+ size_t p_str_size = 120;
+ char* p_str = (char*)osi_malloc(p_str_size);
+ uint16_t i;
+ uint32_t throughput_avg, ack_delay_avg, ack_q_count_avg;
+
+ BT_TRACE(TRACE_CTRL_GENERAL | TRACE_LAYER_GKI | TRACE_ORG_GKI,
+ TRACE_TYPE_GENERIC,
+ "--- L2CAP ERTM Stats for CID: 0x%04x Duration: %08ums",
+ p_ccb->local_cid, dur);
+ BT_TRACE(TRACE_CTRL_GENERAL | TRACE_LAYER_GKI | TRACE_ORG_GKI,
+ TRACE_TYPE_GENERIC,
+ "Retransmissions:%08u Times Flow Controlled:%08u Retrans "
+ "Touts:%08u Ack Touts:%08u",
+ p_ccb->fcrb.pkts_retransmitted, p_ccb->fcrb.xmit_window_closed,
+ p_ccb->fcrb.retrans_touts, p_ccb->fcrb.xmit_ack_touts);
+ BT_TRACE(TRACE_CTRL_GENERAL | TRACE_LAYER_GKI | TRACE_ORG_GKI,
+ TRACE_TYPE_GENERIC,
+ "Times there is less than 2 packets in controller when flow "
+ "controlled:%08u",
+ p_ccb->fcrb.controller_idle);
+ BT_TRACE(TRACE_CTRL_GENERAL | TRACE_LAYER_GKI | TRACE_ORG_GKI,
+ TRACE_TYPE_GENERIC,
+ "max_held_acks:%08u, in_cfg.fcr.tx_win_sz:%08u",
+ p_ccb->fcrb.max_held_acks, p_ccb->peer_cfg.fcr.tx_win_sz);
+
+ snprintf(
+ p_str, p_str_size,
+ "Sent Pkts:%08u Bytes:%10u(%06u/sec) RR:%08u REJ:%08u RNR:%08u "
+ "SREJ:%08u",
+ p_ccb->fcrb.ertm_pkt_counts[0], p_ccb->fcrb.ertm_byte_counts[0],
+ (dur >= 10 ? (p_ccb->fcrb.ertm_byte_counts[0] * 100) / (dur / 10) : 0),
+ p_ccb->fcrb.s_frames_sent[0], p_ccb->fcrb.s_frames_sent[1],
+ p_ccb->fcrb.s_frames_sent[2], p_ccb->fcrb.s_frames_sent[3]);
+
+ BT_TRACE(TRACE_CTRL_GENERAL | TRACE_LAYER_GKI | TRACE_ORG_GKI,
+ TRACE_TYPE_GENERIC, "%s", p_str);
+
+ snprintf(
+ p_str, p_str_size,
+ "Rcvd Pkts:%08u Bytes:%10u(%06u/sec) RR:%08u REJ:%08u RNR:%08u "
+ "SREJ:%08u",
+ p_ccb->fcrb.ertm_pkt_counts[1], p_ccb->fcrb.ertm_byte_counts[1],
+ (dur >= 10 ? (p_ccb->fcrb.ertm_byte_counts[1] * 100) / (dur / 10) : 0),
+ p_ccb->fcrb.s_frames_rcvd[0], p_ccb->fcrb.s_frames_rcvd[1],
+ p_ccb->fcrb.s_frames_rcvd[2], p_ccb->fcrb.s_frames_rcvd[3]);
+
+ BT_TRACE(TRACE_CTRL_GENERAL | TRACE_LAYER_GKI | TRACE_ORG_GKI,
+ TRACE_TYPE_GENERIC, "%s", p_str);
+
+ throughput_avg = 0;
+ ack_delay_avg = 0;
+ ack_q_count_avg = 0;
+
+ for (i = 0; i < L2CAP_ERTM_STATS_NUM_AVG; i++) {
+ if (i == p_ccb->fcrb.ack_delay_avg_index) {
+ BT_TRACE(TRACE_CTRL_GENERAL | TRACE_LAYER_GKI | TRACE_ORG_GKI,
+ TRACE_TYPE_GENERIC, "[%02u] collecting data ...", i);
+ continue;
+ }
+
+ snprintf(p_str, p_str_size,
+ "[%02u] throughput: %5u, ack_delay avg:%3u, min:%3u, max:%3u, "
+ "ack_q_count avg:%3u, min:%3u, max:%3u",
+ i, p_ccb->fcrb.throughput[i], p_ccb->fcrb.ack_delay_avg[i],
+ p_ccb->fcrb.ack_delay_min[i], p_ccb->fcrb.ack_delay_max[i],
+ p_ccb->fcrb.ack_q_count_avg[i], p_ccb->fcrb.ack_q_count_min[i],
+ p_ccb->fcrb.ack_q_count_max[i]);
+
+ BT_TRACE(TRACE_CTRL_GENERAL | TRACE_LAYER_GKI | TRACE_ORG_GKI,
+ TRACE_TYPE_GENERIC, "%s", p_str);
+
+ throughput_avg += p_ccb->fcrb.throughput[i];
+ ack_delay_avg += p_ccb->fcrb.ack_delay_avg[i];
+ ack_q_count_avg += p_ccb->fcrb.ack_q_count_avg[i];
+ }
+
+ throughput_avg /= (L2CAP_ERTM_STATS_NUM_AVG - 1);
+ ack_delay_avg /= (L2CAP_ERTM_STATS_NUM_AVG - 1);
+ ack_q_count_avg /= (L2CAP_ERTM_STATS_NUM_AVG - 1);
+
+ BT_TRACE(TRACE_CTRL_GENERAL | TRACE_LAYER_GKI | TRACE_ORG_GKI,
+ TRACE_TYPE_GENERIC,
+ "throughput_avg: %8u (kbytes/sec), ack_delay_avg: %8u ms, "
+ "ack_q_count_avg: %8u",
+ throughput_avg, ack_delay_avg, ack_q_count_avg);
+
+ osi_free(p_str);
+
+ BT_TRACE(TRACE_CTRL_GENERAL | TRACE_LAYER_GKI | TRACE_ORG_GKI,
+ TRACE_TYPE_GENERIC, "---");
+ }
+#endif
+
memset(p_fcrb, 0, sizeof(tL2C_FCRB));
}
@@ -244,6 +346,13 @@ BT_HDR* l2c_fcr_clone_buf(BT_HDR* p_buf, uint16_t new_offset,
* the FCS (Frame Check Sequence) at the end of the buffer.
*/
uint16_t buf_size = no_of_bytes + sizeof(BT_HDR) + new_offset + L2CAP_FCS_LEN;
+#if (L2CAP_ERTM_STATS == TRUE)
+ /*
+ * NOTE: If L2CAP_ERTM_STATS is enabled, we need 4 extra octets at the
+ * end for a timestamp at the end of an I-frame.
+ */
+ buf_size += sizeof(uint32_t);
+#endif
BT_HDR* p_buf2 = (BT_HDR*)osi_malloc(buf_size);
p_buf2->offset = new_offset;
@@ -270,6 +379,15 @@ bool l2c_fcr_is_flow_controlled(tL2C_CCB* p_ccb) {
if ((p_ccb->fcrb.remote_busy) ||
(fixed_queue_length(p_ccb->fcrb.waiting_for_ack_q) >=
p_ccb->peer_cfg.fcr.tx_win_sz)) {
+#if (L2CAP_ERTM_STATS == TRUE)
+ if (!fixed_queue_is_empty(p_ccb->xmit_hold_q)) {
+ p_ccb->fcrb.xmit_window_closed++;
+
+ if ((p_ccb->p_lcb->sent_not_acked < 2) &&
+ (l2cb.controller_xmit_window > 0))
+ p_ccb->fcrb.controller_idle++;
+ }
+#endif
return (true);
}
}
@@ -331,23 +449,25 @@ static void prepare_I_frame(tL2C_CCB* p_ccb, BT_HDR* p_buf,
UINT16_TO_STREAM(p, ctrl_word);
/* Compute the FCS and add to the end of the buffer if not bypassed */
- /* length field in l2cap header has to include FCS length */
- p = ((uint8_t*)(p_buf + 1)) + p_buf->offset;
- UINT16_TO_STREAM(p, p_buf->len + L2CAP_FCS_LEN - L2CAP_PKT_OVERHEAD);
+ if (p_ccb->bypass_fcs != L2CAP_BYPASS_FCS) {
+ /* length field in l2cap header has to include FCS length */
+ p = ((uint8_t*)(p_buf + 1)) + p_buf->offset;
+ UINT16_TO_STREAM(p, p_buf->len + L2CAP_FCS_LEN - L2CAP_PKT_OVERHEAD);
- /* Calculate the FCS */
- fcs = l2c_fcr_tx_get_fcs(p_buf);
+ /* Calculate the FCS */
+ fcs = l2c_fcr_tx_get_fcs(p_buf);
- /* Point to the end of the buffer and put the FCS there */
- /*
- * NOTE: Here we assume the allocated buffer is large enough
- * to include extra L2CAP_FCS_LEN octets at the end.
- */
- p = ((uint8_t*)(p_buf + 1)) + p_buf->offset + p_buf->len;
+ /* Point to the end of the buffer and put the FCS there */
+ /*
+ * NOTE: Here we assume the allocated buffer is large enough
+ * to include extra L2CAP_FCS_LEN octets at the end.
+ */
+ p = ((uint8_t*)(p_buf + 1)) + p_buf->offset + p_buf->len;
- UINT16_TO_STREAM(p, fcs);
+ UINT16_TO_STREAM(p, fcs);
- p_buf->len += L2CAP_FCS_LEN;
+ p_buf->len += L2CAP_FCS_LEN;
+ }
if (is_retransmission) {
L2CAP_TRACE_EVENT(
@@ -392,6 +512,10 @@ void l2c_fcr_send_S_frame(tL2C_CCB* p_ccb, uint16_t function_code,
if ((!p_ccb->in_use) || (p_ccb->chnl_state != CST_OPEN)) return;
+#if (L2CAP_ERTM_STATS == TRUE)
+ p_ccb->fcrb.s_frames_sent[function_code]++;
+#endif
+
if (pf_bit == L2CAP_FCR_P_BIT) {
p_ccb->fcrb.wait_ack = true;
@@ -417,10 +541,16 @@ void l2c_fcr_send_S_frame(tL2C_CCB* p_ccb, uint16_t function_code,
UINT16_TO_STREAM(p, ctrl_word);
/* Compute the FCS and add to the end of the buffer if not bypassed */
- fcs = l2c_fcr_tx_get_fcs(p_buf);
+ if (p_ccb->bypass_fcs != L2CAP_BYPASS_FCS) {
+ fcs = l2c_fcr_tx_get_fcs(p_buf);
- UINT16_TO_STREAM(p, fcs);
- p_buf->len += L2CAP_FCS_LEN;
+ UINT16_TO_STREAM(p, fcs);
+ p_buf->len += L2CAP_FCS_LEN;
+ } else {
+ /* rewrite the length without FCS length */
+ p -= 6;
+ UINT16_TO_STREAM(p, L2CAP_FCR_OVERHEAD);
+ }
/* Now, the HCI transport header */
p_buf->layer_specific = L2CAP_NON_FLUSHABLE_PKT;
@@ -449,7 +579,7 @@ void l2c_fcr_send_S_frame(tL2C_CCB* p_ccb, uint16_t function_code,
L2CAP_TRACE_EVENT(" Buf Len: %u", p_buf->len);
}
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, p_buf);
p_ccb->fcrb.last_ack_sent = p_ccb->fcrb.next_seq_expected;
@@ -476,7 +606,9 @@ void l2c_fcr_proc_pdu(tL2C_CCB* p_ccb, BT_HDR* p_buf) {
uint16_t ctrl_word;
/* Check the length */
- min_pdu_len = (uint16_t)(L2CAP_FCS_LEN + L2CAP_FCR_OVERHEAD);
+ min_pdu_len = (p_ccb->bypass_fcs == L2CAP_BYPASS_FCS)
+ ? (uint16_t)L2CAP_FCR_OVERHEAD
+ : (uint16_t)(L2CAP_FCS_LEN + L2CAP_FCR_OVERHEAD);
if (p_buf->len < min_pdu_len) {
L2CAP_TRACE_WARNING("Rx L2CAP PDU: CID: 0x%04x Len too short: %u",
@@ -485,6 +617,11 @@ void l2c_fcr_proc_pdu(tL2C_CCB* p_ccb, BT_HDR* p_buf) {
return;
}
+ if (p_ccb->peer_cfg.fcr.mode == L2CAP_FCR_STREAM_MODE) {
+ process_stream_frame(p_ccb, p_buf);
+ return;
+ }
+
/* Get the control word */
p = ((uint8_t*)(p_buf + 1)) + p_buf->offset;
STREAM_TO_UINT16(ctrl_word, p);
@@ -530,16 +667,19 @@ void l2c_fcr_proc_pdu(tL2C_CCB* p_ccb, BT_HDR* p_buf) {
fixed_queue_length(p_ccb->fcrb.waiting_for_ack_q), p_ccb->fcrb.num_tries);
/* Verify FCS if using */
- p = ((uint8_t*)(p_buf + 1)) + p_buf->offset + p_buf->len - L2CAP_FCS_LEN;
+ if (p_ccb->bypass_fcs != L2CAP_BYPASS_FCS) {
+ p = ((uint8_t*)(p_buf + 1)) + p_buf->offset + p_buf->len - L2CAP_FCS_LEN;
- /* Extract and drop the FCS from the packet */
- STREAM_TO_UINT16(fcs, p);
- p_buf->len -= L2CAP_FCS_LEN;
+ /* Extract and drop the FCS from the packet */
+ STREAM_TO_UINT16(fcs, p);
+ p_buf->len -= L2CAP_FCS_LEN;
- if (l2c_fcr_rx_get_fcs(p_buf) != fcs) {
- L2CAP_TRACE_WARNING("Rx L2CAP PDU: CID: 0x%04x BAD FCS", p_ccb->local_cid);
- osi_free(p_buf);
- return;
+ if (l2c_fcr_rx_get_fcs(p_buf) != fcs) {
+ L2CAP_TRACE_WARNING("Rx L2CAP PDU: CID: 0x%04x BAD FCS",
+ p_ccb->local_cid);
+ osi_free(p_buf);
+ return;
+ }
}
/* Get the control word */
@@ -558,6 +698,8 @@ void l2c_fcr_proc_pdu(tL2C_CCB* p_ccb, BT_HDR* p_buf) {
(ctrl_word & L2CAP_FCR_S_FRAME_BIT)) {
if (p_ccb->fcrb.srej_sent)
l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_SREJ, L2CAP_FCR_F_BIT);
+ else if (p_ccb->fcrb.local_busy)
+ l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RNR, L2CAP_FCR_F_BIT);
else
l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RR, L2CAP_FCR_F_BIT);
@@ -567,8 +709,8 @@ void l2c_fcr_proc_pdu(tL2C_CCB* p_ccb, BT_HDR* p_buf) {
* saw */
/* that if the other side sends us a poll when we are waiting for a
* final, */
- /* then it speeds up recovery significantly if we poll it back soon
- * after its poll. */
+ /* then it speeds up recovery significantly if we poll him back soon
+ * after his poll. */
alarm_set_on_mloop(p_ccb->fcrb.mon_retrans_timer, BT_1SEC_TIMEOUT_MS,
l2c_ccb_timer_timeout, p_ccb);
}
@@ -608,7 +750,7 @@ void l2c_fcr_proc_pdu(tL2C_CCB* p_ccb, BT_HDR* p_buf) {
/* If we have some buffers held while doing SREJ, and SREJ has cleared,
* process them now */
- if ((!p_ccb->fcrb.srej_sent) &&
+ if ((!p_ccb->fcrb.local_busy) && (!p_ccb->fcrb.srej_sent) &&
(!fixed_queue_is_empty(p_ccb->fcrb.srej_rcv_hold_q))) {
fixed_queue_t* temp_q = p_ccb->fcrb.srej_rcv_hold_q;
p_ccb->fcrb.srej_rcv_hold_q = fixed_queue_new(SIZE_MAX);
@@ -644,15 +786,17 @@ void l2c_fcr_proc_pdu(tL2C_CCB* p_ccb, BT_HDR* p_buf) {
fixed_queue_free(temp_q, NULL);
/* Now, if needed, send one RR for the whole held queue */
- if ((!p_ccb->fcrb.rej_sent) && (!p_ccb->fcrb.srej_sent) &&
+ if ((!p_ccb->fcrb.local_busy) && (!p_ccb->fcrb.rej_sent) &&
+ (!p_ccb->fcrb.srej_sent) &&
(p_ccb->fcrb.next_seq_expected != p_ccb->fcrb.last_ack_sent))
l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RR, 0);
else {
L2CAP_TRACE_DEBUG(
"l2c_fcr_proc_pdu() not sending RR CID: 0x%04x local_busy:%d "
"rej_sent:%d srej_sent:%d Expected_Seq:%u Last_Ack:%u",
- p_ccb->local_cid, 0, p_ccb->fcrb.rej_sent, p_ccb->fcrb.srej_sent,
- p_ccb->fcrb.next_seq_expected, p_ccb->fcrb.last_ack_sent);
+ p_ccb->local_cid, p_ccb->fcrb.local_busy, p_ccb->fcrb.rej_sent,
+ p_ccb->fcrb.srej_sent, p_ccb->fcrb.next_seq_expected,
+ p_ccb->fcrb.last_ack_sent);
}
}
@@ -660,7 +804,7 @@ void l2c_fcr_proc_pdu(tL2C_CCB* p_ccb, BT_HDR* p_buf) {
if ((!fixed_queue_is_empty(p_ccb->fcrb.retrans_q) ||
!fixed_queue_is_empty(p_ccb->xmit_hold_q)) &&
(!p_ccb->fcrb.wait_ack) && (!l2c_fcr_is_flow_controlled(p_ccb))) {
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, NULL);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, NULL);
}
}
@@ -782,12 +926,19 @@ void l2c_fcr_proc_tout(tL2C_CCB* p_ccb) {
p_ccb->local_cid, p_ccb->fcrb.num_tries, p_ccb->peer_cfg.fcr.max_transmit,
p_ccb->fcrb.wait_ack, fixed_queue_length(p_ccb->fcrb.waiting_for_ack_q));
+#if (L2CAP_ERTM_STATS == TRUE)
+ p_ccb->fcrb.retrans_touts++;
+#endif
+
if ((p_ccb->peer_cfg.fcr.max_transmit != 0) &&
(++p_ccb->fcrb.num_tries > p_ccb->peer_cfg.fcr.max_transmit)) {
l2cu_disconnect_chnl(p_ccb);
} else {
if (!p_ccb->fcrb.srej_sent && !p_ccb->fcrb.rej_sent) {
- l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RR, L2CAP_FCR_P_BIT);
+ if (p_ccb->fcrb.local_busy)
+ l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RNR, L2CAP_FCR_P_BIT);
+ else
+ l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RR, L2CAP_FCR_P_BIT);
}
}
}
@@ -810,7 +961,13 @@ void l2c_fcr_proc_ack_tout(tL2C_CCB* p_ccb) {
if ((p_ccb->chnl_state == CST_OPEN) && (!p_ccb->fcrb.wait_ack) &&
(p_ccb->fcrb.last_ack_sent != p_ccb->fcrb.next_seq_expected)) {
- l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RR, 0);
+#if (L2CAP_ERTM_STATS == TRUE)
+ p_ccb->fcrb.xmit_ack_touts++;
+#endif
+ if (p_ccb->fcrb.local_busy)
+ l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RNR, 0);
+ else
+ l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RR, 0);
}
}
@@ -870,6 +1027,10 @@ static bool process_reqseq(tL2C_CCB* p_ccb, uint16_t ctrl_word) {
p_fcrb->num_tries = 0;
full_sdus_xmitted = 0;
+#if (L2CAP_ERTM_STATS == TRUE)
+ l2c_fcr_collect_ack_delay(p_ccb, num_bufs_acked);
+#endif
+
for (xx = 0; xx < num_bufs_acked; xx++) {
BT_HDR* p_tmp =
(BT_HDR*)fixed_queue_try_dequeue(p_fcrb->waiting_for_ack_q);
@@ -931,6 +1092,10 @@ static void process_s_frame(tL2C_CCB* p_ccb, BT_HDR* p_buf,
L2CAP_TRACE_DEBUG("process_s_frame ctrl_word 0x%04x fcrb_remote_busy:%d",
ctrl_word, p_fcrb->remote_busy);
+#if (L2CAP_ERTM_STATS == TRUE)
+ p_ccb->fcrb.s_frames_rcvd[s_frame_type]++;
+#endif
+
if (ctrl_word & L2CAP_FCR_P_BIT) {
p_fcrb->rej_sent = false; /* After checkpoint, we can send anoher REJ */
p_fcrb->send_f_rsp = true; /* Set a flag in case an I-frame is pending */
@@ -969,6 +1134,8 @@ static void process_s_frame(tL2C_CCB* p_ccb, BT_HDR* p_buf,
if (p_fcrb->send_f_rsp) {
if (p_fcrb->srej_sent)
l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_SREJ, L2CAP_FCR_F_BIT);
+ else if (p_fcrb->local_busy)
+ l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RNR, L2CAP_FCR_F_BIT);
else
l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RR, L2CAP_FCR_F_BIT);
@@ -1007,9 +1174,23 @@ static void process_i_frame(tL2C_CCB* p_ccb, BT_HDR* p_buf, uint16_t ctrl_word,
}
}
+#if (L2CAP_ERTM_STATS == TRUE)
+ p_ccb->fcrb.ertm_pkt_counts[1]++;
+ p_ccb->fcrb.ertm_byte_counts[1] += p_buf->len;
+#endif
+
/* Extract the sequence number */
tx_seq = (ctrl_word & L2CAP_FCR_TX_SEQ_BITS) >> L2CAP_FCR_TX_SEQ_BITS_SHIFT;
+ /* If we have flow controlled the peer, ignore any bad I-frames from him */
+ if ((tx_seq != p_fcrb->next_seq_expected) && (p_fcrb->local_busy)) {
+ L2CAP_TRACE_WARNING("Dropping bad I-Frame since we flowed off, tx_seq:%u",
+ tx_seq);
+ l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RNR, 0);
+ osi_free(p_buf);
+ return;
+ }
+
/* Check if tx-sequence is the expected one */
if (tx_seq != p_fcrb->next_seq_expected) {
num_lost = (tx_seq - p_fcrb->next_seq_expected) & L2CAP_FCR_SEQ_MODULO;
@@ -1041,6 +1222,24 @@ static void process_i_frame(tL2C_CCB* p_ccb, BT_HDR* p_buf, uint16_t ctrl_word,
if ((tx_seq == next_srej) &&
(fixed_queue_length(p_fcrb->srej_rcv_hold_q) <
p_ccb->our_cfg.fcr.tx_win_sz)) {
+ /* If user gave us a pool for held rx buffers, use that */
+ /* TODO: Could that happen? Get rid of this code. */
+ if (p_ccb->ertm_info.fcr_rx_buf_size != L2CAP_FCR_RX_BUF_SIZE) {
+ BT_HDR* p_buf2;
+
+ /* Adjust offset and len so that control word is copied */
+ p_buf->offset -= L2CAP_FCR_OVERHEAD;
+ p_buf->len += L2CAP_FCR_OVERHEAD;
+
+ p_buf2 = l2c_fcr_clone_buf(p_buf, p_buf->offset, p_buf->len);
+
+ if (p_buf2) {
+ osi_free(p_buf);
+ p_buf = p_buf2;
+ }
+ p_buf->offset += L2CAP_FCR_OVERHEAD;
+ p_buf->len -= L2CAP_FCR_OVERHEAD;
+ }
L2CAP_TRACE_DEBUG(
"process_i_frame() Lost: %u tx_seq:%u ExpTxSeq %u Rej: %u "
"SRej1",
@@ -1120,7 +1319,8 @@ static void process_i_frame(tL2C_CCB* p_ccb, BT_HDR* p_buf, uint16_t ctrl_word,
num_to_ack = (p_fcrb->next_seq_expected - p_fcrb->last_ack_sent) &
L2CAP_FCR_SEQ_MODULO;
- if (num_to_ack < p_ccb->fcrb.max_held_acks) delay_ack = true;
+ if ((num_to_ack < p_ccb->fcrb.max_held_acks) && (!p_fcrb->local_busy))
+ delay_ack = true;
/* We should neve never ack frame if we are not in OPEN state */
if ((num_to_ack != 0) && p_ccb->in_use && (p_ccb->chnl_state == CST_OPEN)) {
@@ -1135,13 +1335,100 @@ static void process_i_frame(tL2C_CCB* p_ccb, BT_HDR* p_buf, uint16_t ctrl_word,
} else if ((fixed_queue_is_empty(p_ccb->xmit_hold_q) ||
l2c_fcr_is_flow_controlled(p_ccb)) &&
fixed_queue_is_empty(p_ccb->fcrb.srej_rcv_hold_q)) {
- l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RR, 0);
+ if (p_fcrb->local_busy)
+ l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RNR, 0);
+ else
+ l2c_fcr_send_S_frame(p_ccb, L2CAP_FCR_SUP_RR, 0);
}
}
}
/*******************************************************************************
*
+ * Function process_stream_frame
+ *
+ * Description This function processes frames in streaming mode
+ *
+ * Returns -
+ *
+ ******************************************************************************/
+static void process_stream_frame(tL2C_CCB* p_ccb, BT_HDR* p_buf) {
+ CHECK(p_ccb != NULL);
+ CHECK(p_buf != NULL);
+
+ uint16_t ctrl_word;
+ uint16_t fcs;
+ uint8_t* p;
+ uint8_t tx_seq;
+
+ /* Verify FCS if using */
+ if (p_ccb->bypass_fcs != L2CAP_BYPASS_FCS) {
+ p = ((uint8_t*)(p_buf + 1)) + p_buf->offset + p_buf->len - L2CAP_FCS_LEN;
+
+ /* Extract and drop the FCS from the packet */
+ STREAM_TO_UINT16(fcs, p);
+ p_buf->len -= L2CAP_FCS_LEN;
+
+ if (l2c_fcr_rx_get_fcs(p_buf) != fcs) {
+ L2CAP_TRACE_WARNING("Rx L2CAP PDU: CID: 0x%04x BAD FCS",
+ p_ccb->local_cid);
+ osi_free(p_buf);
+ return;
+ }
+ }
+
+ /* Get the control word */
+ p = ((uint8_t*)(p_buf + 1)) + p_buf->offset;
+
+ STREAM_TO_UINT16(ctrl_word, p);
+
+ p_buf->len -= L2CAP_FCR_OVERHEAD;
+ p_buf->offset += L2CAP_FCR_OVERHEAD;
+
+ /* Make sure it is an I-frame */
+ if (ctrl_word & L2CAP_FCR_S_FRAME_BIT) {
+ L2CAP_TRACE_WARNING(
+ "Rx L2CAP PDU: CID: 0x%04x BAD S-frame in streaming mode ctrl_word: "
+ "0x%04x",
+ p_ccb->local_cid, ctrl_word);
+ osi_free(p_buf);
+ return;
+ }
+
+ L2CAP_TRACE_EVENT(
+ "L2CAP eRTM Rx I-frame: cid: 0x%04x Len: %u SAR: %-12s TxSeq: %u "
+ "ReqSeq: %u F: %u",
+ p_ccb->local_cid, p_buf->len,
+ SAR_types[(ctrl_word & L2CAP_FCR_SAR_BITS) >> L2CAP_FCR_SAR_BITS_SHIFT],
+ (ctrl_word & L2CAP_FCR_TX_SEQ_BITS) >> L2CAP_FCR_TX_SEQ_BITS_SHIFT,
+ (ctrl_word & L2CAP_FCR_REQ_SEQ_BITS) >> L2CAP_FCR_REQ_SEQ_BITS_SHIFT,
+ (ctrl_word & L2CAP_FCR_F_BIT) >> L2CAP_FCR_F_BIT_SHIFT);
+
+ /* Extract the sequence number */
+ tx_seq = (ctrl_word & L2CAP_FCR_TX_SEQ_BITS) >> L2CAP_FCR_TX_SEQ_BITS_SHIFT;
+
+ /* Check if tx-sequence is the expected one */
+ if (tx_seq != p_ccb->fcrb.next_seq_expected) {
+ L2CAP_TRACE_WARNING(
+ "Rx L2CAP PDU: CID: 0x%04x Lost frames Exp: %u Got: %u p_rx_sdu: "
+ "0x%08x",
+ p_ccb->local_cid, p_ccb->fcrb.next_seq_expected, tx_seq,
+ p_ccb->fcrb.p_rx_sdu);
+
+ /* Lost one or more packets, so flush the SAR queue */
+ osi_free_and_reset((void**)&p_ccb->fcrb.p_rx_sdu);
+ }
+
+ p_ccb->fcrb.next_seq_expected = (tx_seq + 1) & L2CAP_FCR_SEQ_MODULO;
+
+ if (!do_sar_reassembly(p_ccb, p_buf, ctrl_word)) {
+ /* Some sort of SAR error, so flush the SAR queue */
+ osi_free_and_reset((void**)&p_ccb->fcrb.p_rx_sdu);
+ }
+}
+
+/*******************************************************************************
+ *
* Function do_sar_reassembly
*
* Description Process SAR bits and re-assemble frame
@@ -1194,7 +1481,7 @@ static bool do_sar_reassembly(tL2C_CCB* p_ccb, BT_HDR* p_buf,
if (p_fcrb->rx_sdu_len > p_ccb->max_rx_mtu) {
L2CAP_TRACE_WARNING("SAR - SDU len: %u larger than MTU: %u",
- p_fcrb->rx_sdu_len, p_ccb->max_rx_mtu);
+ p_fcrb->rx_sdu_len, p_fcrb->rx_sdu_len);
packet_ok = false;
} else {
p_fcrb->p_rx_sdu = (BT_HDR*)osi_malloc(
@@ -1237,6 +1524,7 @@ static bool do_sar_reassembly(tL2C_CCB* p_ccb, BT_HDR* p_buf,
if (!packet_ok) {
osi_free(p_buf);
} else if (p_buf != NULL) {
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
if (p_ccb->local_cid < L2CAP_BASE_APPL_CID &&
(p_ccb->local_cid >= L2CAP_FIRST_FIXED_CHNL &&
p_ccb->local_cid <= L2CAP_LAST_FIXED_CHNL)) {
@@ -1246,6 +1534,7 @@ static bool do_sar_reassembly(tL2C_CCB* p_ccb, BT_HDR* p_buf,
.pL2CA_FixedData_Cb)(p_ccb->local_cid,
p_ccb->p_lcb->remote_bd_addr, p_buf);
} else
+#endif
l2c_csm_execute(p_ccb, L2CEVT_L2CAP_DATA, p_buf);
}
@@ -1357,7 +1646,7 @@ static bool retransmit_i_frames(tL2C_CCB* p_ccb, uint8_t tx_seq) {
}
}
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, NULL);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, NULL);
if (fixed_queue_length(p_ccb->fcrb.waiting_for_ack_q)) {
p_ccb->fcrb.num_tries++;
@@ -1398,6 +1687,11 @@ BT_HDR* l2c_fcr_get_next_xmit_sdu_seg(tL2C_CCB* p_ccb,
p_buf->event = p_ccb->local_cid;
+#if (L2CAP_ERTM_STATS == TRUE)
+ p_ccb->fcrb.pkts_retransmitted++;
+ p_ccb->fcrb.ertm_pkt_counts[0]++;
+ p_ccb->fcrb.ertm_byte_counts[0] += (p_buf->len - 8);
+#endif
return (p_buf);
}
@@ -1497,19 +1791,34 @@ BT_HDR* l2c_fcr_get_next_xmit_sdu_seg(tL2C_CCB* p_ccb,
p_ccb->local_cid, p_xmit->len);
/* We will not save the FCS in case we reconfigure and change options */
- p_xmit->len -= L2CAP_FCS_LEN;
+ if (p_ccb->bypass_fcs != L2CAP_BYPASS_FCS) p_xmit->len -= L2CAP_FCS_LEN;
/* Pretend we sent it and it got lost */
fixed_queue_enqueue(p_ccb->fcrb.waiting_for_ack_q, p_xmit);
return (NULL);
} else {
+#if (L2CAP_ERTM_STATS == TRUE)
+ /* set timestamp at the end of tx I-frame to get acking delay */
+ /*
+ * NOTE: Here we assume the allocate buffer is large enough
+ * to include extra 4 octets at the end.
+ */
+ p = ((uint8_t*)(p_wack + 1)) + p_wack->offset + p_wack->len;
+ // Have to cast to uint32_t which wraps in 49.7 days
+ UINT32_TO_STREAM(p, static_cast<uint32_t>(
+ bluetooth::common::time_get_os_boottime_ms()));
+#endif
/* We will not save the FCS in case we reconfigure and change options */
- p_wack->len -= L2CAP_FCS_LEN;
+ if (p_ccb->bypass_fcs != L2CAP_BYPASS_FCS) p_wack->len -= L2CAP_FCS_LEN;
p_wack->layer_specific = p_xmit->layer_specific;
fixed_queue_enqueue(p_ccb->fcrb.waiting_for_ack_q, p_wack);
}
+#if (L2CAP_ERTM_STATS == TRUE)
+ p_ccb->fcrb.ertm_pkt_counts[0]++;
+ p_ccb->fcrb.ertm_byte_counts[0] += (p_xmit->len - 8);
+#endif
}
return (p_xmit);
@@ -1596,14 +1905,141 @@ uint8_t l2c_fcr_chk_chan_modes(tL2C_CCB* p_ccb) {
CHECK(p_ccb != NULL);
/* Remove nonbasic options that the peer does not support */
- if (!(p_ccb->p_lcb->peer_ext_fea & L2CAP_EXTFEA_ENH_RETRANS) &&
- p_ccb->p_rcb->ertm_info.preferred_mode == L2CAP_FCR_ERTM_MODE) {
+ if (!(p_ccb->p_lcb->peer_ext_fea & L2CAP_EXTFEA_ENH_RETRANS))
+ p_ccb->ertm_info.allowed_modes &= ~L2CAP_FCR_CHAN_OPT_ERTM;
+
+ if (!(p_ccb->p_lcb->peer_ext_fea & L2CAP_EXTFEA_STREAM_MODE))
+ p_ccb->ertm_info.allowed_modes &= ~L2CAP_FCR_CHAN_OPT_STREAM;
+
+ /* At least one type needs to be set (Basic, ERTM, STM) to continue */
+ if (!p_ccb->ertm_info.allowed_modes) {
L2CAP_TRACE_WARNING(
"L2CAP - Peer does not support our desired channel types");
- p_ccb->p_rcb->ertm_info.preferred_mode = 0;
- return false;
}
- return true;
+
+ return (p_ccb->ertm_info.allowed_modes);
+}
+
+/*******************************************************************************
+ *
+ * Function l2c_fcr_adj_our_req_options
+ *
+ * Description Validates and sets up the FCR options passed in from
+ * L2CA_ConfigReq based on remote device's features.
+ *
+ * Returns true if no errors, Otherwise false
+ *
+ ******************************************************************************/
+bool l2c_fcr_adj_our_req_options(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
+ CHECK(p_ccb != NULL);
+ CHECK(p_cfg != NULL);
+
+ tL2CAP_FCR_OPTS* p_fcr = &p_cfg->fcr;
+
+ if (p_fcr->mode != p_ccb->ertm_info.preferred_mode) {
+ L2CAP_TRACE_WARNING(
+ "l2c_fcr_adj_our_req_options - preferred_mode (%d), does not match "
+ "mode (%d)",
+ p_ccb->ertm_info.preferred_mode, p_fcr->mode);
+
+ /* The preferred mode is passed in through tL2CAP_ERTM_INFO, so override
+ * this one */
+ p_fcr->mode = p_ccb->ertm_info.preferred_mode;
+ }
+
+ /* If upper layer did not request eRTM mode, BASIC must be used */
+ if (p_ccb->ertm_info.allowed_modes == L2CAP_FCR_CHAN_OPT_BASIC) {
+ if (p_cfg->fcr_present && p_fcr->mode != L2CAP_FCR_BASIC_MODE) {
+ L2CAP_TRACE_WARNING(
+ "l2c_fcr_adj_our_req_options (mode %d): ERROR: No FCR options set "
+ "using BASIC mode",
+ p_fcr->mode);
+ }
+ p_fcr->mode = L2CAP_FCR_BASIC_MODE;
+ }
+
+ /* Process the FCR options if initial channel bring-up (not a reconfig
+ *request)
+ ** Determine initial channel mode to try based on our options and remote's
+ *features
+ */
+ if (p_cfg->fcr_present && !(p_ccb->config_done & RECONFIG_FLAG)) {
+ /* We need to have at least one mode type common with the peer */
+ if (!l2c_fcr_chk_chan_modes(p_ccb)) {
+ /* Two channels have incompatible supported types */
+ l2cu_disconnect_chnl(p_ccb);
+ return (false);
+ }
+
+ /* Basic is the only common channel mode between the two devices */
+ else if (p_ccb->ertm_info.allowed_modes == L2CAP_FCR_CHAN_OPT_BASIC) {
+ /* We only want to try Basic, so bypass sending the FCR options entirely
+ */
+ p_cfg->fcr_present = false;
+ p_cfg->fcs_present = false; /* Illegal to use FCS option in basic mode */
+ p_cfg->ext_flow_spec_present =
+ false; /* Illegal to use extended flow spec in basic mode */
+ }
+
+ /* We have at least one non-basic mode available
+ * Override mode from available mode options based on preference, if needed
+ */
+ else {
+ /* If peer does not support STREAMING, try ERTM */
+ if (p_fcr->mode == L2CAP_FCR_STREAM_MODE &&
+ !(p_ccb->ertm_info.allowed_modes & L2CAP_FCR_CHAN_OPT_STREAM)) {
+ L2CAP_TRACE_DEBUG(
+ "L2C CFG: mode is STREAM, but peer does not support; Try ERTM");
+ p_fcr->mode = L2CAP_FCR_ERTM_MODE;
+ }
+
+ /* If peer does not support ERTM, try BASIC (will support this if made it
+ * here in the code) */
+ if (p_fcr->mode == L2CAP_FCR_ERTM_MODE &&
+ !(p_ccb->ertm_info.allowed_modes & L2CAP_FCR_CHAN_OPT_ERTM)) {
+ L2CAP_TRACE_DEBUG(
+ "L2C CFG: mode is ERTM, but peer does not support; Try BASIC");
+ p_fcr->mode = L2CAP_FCR_BASIC_MODE;
+ }
+ }
+
+ if (p_fcr->mode != L2CAP_FCR_BASIC_MODE) {
+ /* MTU must be smaller than buffer size */
+ if ((p_cfg->mtu_present) && (p_cfg->mtu > p_ccb->max_rx_mtu)) {
+ L2CAP_TRACE_WARNING("L2CAP - MTU: %u larger than buf size: %u",
+ p_cfg->mtu, p_ccb->max_rx_mtu);
+ return (false);
+ }
+
+ /* application want to use the default MPS */
+ if (p_fcr->mps == L2CAP_DEFAULT_ERM_MPS) {
+ p_fcr->mps = L2CAP_MPS_OVER_BR_EDR;
+ }
+ /* MPS must be less than MTU */
+ else if (p_fcr->mps > p_ccb->max_rx_mtu) {
+ L2CAP_TRACE_WARNING("L2CAP - MPS %u invalid MTU: %u", p_fcr->mps,
+ p_ccb->max_rx_mtu);
+ return (false);
+ }
+
+ /* We always initially read into the HCI buffer pool, so make sure it fits
+ */
+ if (p_fcr->mps > (L2CAP_MTU_SIZE - L2CAP_MAX_HEADER_FCS))
+ p_fcr->mps = L2CAP_MTU_SIZE - L2CAP_MAX_HEADER_FCS;
+ } else {
+ p_cfg->fcs_present = false; /* Illegal to use FCS option in basic mode */
+ p_cfg->ext_flow_spec_present =
+ false; /* Illegal to use extended flow spec in basic mode */
+ }
+
+ p_ccb->our_cfg.fcr = *p_fcr;
+ } else /* Not sure how to send a reconfiguration(??) should fcr be included?
+ */
+ {
+ p_ccb->our_cfg.fcr_present = false;
+ }
+
+ return (true);
}
/*******************************************************************************
@@ -1720,9 +2156,25 @@ bool l2c_fcr_renegotiate_chan(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
/* Try another supported mode if available based on our last attempted
* channel */
switch (p_ccb->our_cfg.fcr.mode) {
+ /* Our Streaming mode request was unnacceptable; try ERTM or Basic */
+ case L2CAP_FCR_STREAM_MODE:
+ /* Peer wants ERTM and we support it */
+ if ((peer_mode == L2CAP_FCR_ERTM_MODE) &&
+ (p_ccb->ertm_info.allowed_modes & L2CAP_FCR_CHAN_OPT_ERTM)) {
+ L2CAP_TRACE_DEBUG("%s(Trying ERTM)", __func__);
+ p_ccb->our_cfg.fcr.mode = L2CAP_FCR_ERTM_MODE;
+ can_renegotiate = true;
+ } else if (p_ccb->ertm_info.allowed_modes &
+ L2CAP_FCR_CHAN_OPT_BASIC) {
+ /* We can try basic for any other peer mode if we support it */
+ L2CAP_TRACE_DEBUG("%s(Trying Basic)", __func__);
+ can_renegotiate = true;
+ p_ccb->our_cfg.fcr.mode = L2CAP_FCR_BASIC_MODE;
+ }
+ break;
case L2CAP_FCR_ERTM_MODE:
/* We can try basic for any other peer mode if we support it */
- if (p_ccb->p_rcb->ertm_info.preferred_mode & L2CAP_FCR_BASIC_MODE) {
+ if (p_ccb->ertm_info.allowed_modes & L2CAP_FCR_CHAN_OPT_BASIC) {
L2CAP_TRACE_DEBUG("%s(Trying Basic)", __func__);
can_renegotiate = true;
p_ccb->our_cfg.fcr.mode = L2CAP_FCR_BASIC_MODE;
@@ -1790,19 +2242,19 @@ uint8_t l2c_fcr_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
L2CAP_TRACE_EVENT(
"l2c_fcr_process_peer_cfg_req() CFG fcr_present:%d fcr.mode:%d CCB FCR "
- "mode:%d preferred: %u",
+ "mode:%d preferred: %u allowed:%u",
p_cfg->fcr_present, p_cfg->fcr.mode, p_ccb->our_cfg.fcr.mode,
- p_ccb->p_rcb->ertm_info.preferred_mode);
+ p_ccb->ertm_info.preferred_mode, p_ccb->ertm_info.allowed_modes);
/* If Peer wants basic, we are done (accept it or disconnect) */
if (p_cfg->fcr.mode == L2CAP_FCR_BASIC_MODE) {
/* If we do not allow basic, disconnect */
- if (p_ccb->p_rcb->ertm_info.preferred_mode != L2CAP_FCR_BASIC_MODE)
+ if (!(p_ccb->ertm_info.allowed_modes & L2CAP_FCR_CHAN_OPT_BASIC))
fcr_ok = L2CAP_PEER_CFG_DISCONNECT;
}
/* Need to negotiate if our modes are not the same */
- else if (p_cfg->fcr.mode != p_ccb->p_rcb->ertm_info.preferred_mode) {
+ else if (p_cfg->fcr.mode != p_ccb->ertm_info.preferred_mode) {
/* If peer wants a mode that we don't support then retry our mode (ex.
*rtx/flc), OR
** If we want ERTM and they wanted streaming retry our mode.
@@ -1810,7 +2262,7 @@ uint8_t l2c_fcr_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
** from their EXF mask.
*/
if ((((1 << p_cfg->fcr.mode) & L2CAP_FCR_CHAN_OPT_ALL_MASK) == 0) ||
- (p_ccb->p_rcb->ertm_info.preferred_mode == L2CAP_FCR_ERTM_MODE)) {
+ (p_ccb->ertm_info.preferred_mode == L2CAP_FCR_ERTM_MODE)) {
p_cfg->fcr.mode = p_ccb->our_cfg.fcr.mode;
p_cfg->fcr.tx_win_sz = p_ccb->our_cfg.fcr.tx_win_sz;
p_cfg->fcr.max_transmit = p_ccb->our_cfg.fcr.max_transmit;
@@ -1818,7 +2270,7 @@ uint8_t l2c_fcr_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
}
/* If we wanted basic, then try to renegotiate it */
- else if (p_ccb->p_rcb->ertm_info.preferred_mode == L2CAP_FCR_BASIC_MODE) {
+ else if (p_ccb->ertm_info.preferred_mode == L2CAP_FCR_BASIC_MODE) {
p_cfg->fcr.mode = L2CAP_FCR_BASIC_MODE;
p_cfg->fcr.max_transmit = p_cfg->fcr.tx_win_sz = 0;
p_cfg->fcr.rtrans_tout = p_cfg->fcr.mon_tout = p_cfg->fcr.mps = 0;
@@ -1826,6 +2278,15 @@ uint8_t l2c_fcr_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
p_ccb->our_cfg.fcr.mps = 0;
fcr_ok = L2CAP_PEER_CFG_UNACCEPTABLE;
}
+
+ /* Only other valid case is if they want ERTM and we wanted STM which should
+ be
+ accepted if we support it; otherwise the channel should be disconnected
+ */
+ else if ((p_cfg->fcr.mode != L2CAP_FCR_ERTM_MODE) ||
+ !(p_ccb->ertm_info.allowed_modes & L2CAP_FCR_CHAN_OPT_ERTM)) {
+ fcr_ok = L2CAP_PEER_CFG_DISCONNECT;
+ }
}
/* Configuration for FCR channels so make any adjustments and fwd to upper
@@ -1839,9 +2300,12 @@ uint8_t l2c_fcr_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
/* Peer desires to bypass FCS check, and streaming or ERTM mode */
if (p_cfg->fcs_present) {
p_ccb->peer_cfg.fcs = p_cfg->fcs;
+ p_ccb->peer_cfg_bits |= L2CAP_CH_CFG_MASK_FCS;
+ if (p_cfg->fcs == L2CAP_CFG_FCS_BYPASS)
+ p_ccb->bypass_fcs |= L2CAP_CFG_FCS_PEER;
}
- max_retrans_size = BT_DEFAULT_BUFFER_SIZE - sizeof(BT_HDR) -
+ max_retrans_size = p_ccb->ertm_info.fcr_tx_buf_size - sizeof(BT_HDR) -
L2CAP_MIN_OFFSET - L2CAP_SDU_LEN_OFFSET -
L2CAP_FCS_LEN;
@@ -1860,7 +2324,8 @@ uint8_t l2c_fcr_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
p_ccb->out_cfg_fcr_present = true;
}
- if (p_cfg->fcr.mode == L2CAP_FCR_ERTM_MODE) {
+ if (p_cfg->fcr.mode == L2CAP_FCR_ERTM_MODE ||
+ p_cfg->fcr.mode == L2CAP_FCR_STREAM_MODE) {
/* Always respond with FCR ERTM parameters */
p_ccb->out_cfg_fcr_present = true;
}
@@ -1869,6 +2334,7 @@ uint8_t l2c_fcr_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
/* Everything ok, so save the peer's adjusted fcr options */
p_ccb->peer_cfg.fcr = p_cfg->fcr;
+ if (p_cfg->fcr_present) p_ccb->peer_cfg_bits |= L2CAP_CH_CFG_MASK_FCR;
} else if (fcr_ok == L2CAP_PEER_CFG_UNACCEPTABLE) {
/* Allow peer only one retry for mode */
if (p_ccb->peer_cfg_already_rejected)
@@ -1879,3 +2345,118 @@ uint8_t l2c_fcr_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
return (fcr_ok);
}
+
+#if (L2CAP_ERTM_STATS == TRUE)
+/*******************************************************************************
+ *
+ * Function l2c_fcr_collect_ack_delay
+ *
+ * Description collect throughput, delay, queue size of waiting ack
+ *
+ * Parameters
+ * tL2C_CCB
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void l2c_fcr_collect_ack_delay(tL2C_CCB* p_ccb, uint8_t num_bufs_acked) {
+ uint32_t index;
+ BT_HDR* p_buf;
+ uint8_t* p;
+ uint32_t timestamp, delay;
+ uint8_t xx;
+ uint8_t str[120];
+
+ index = p_ccb->fcrb.ack_delay_avg_index;
+
+ /* update sum, max and min of waiting for ack queue size */
+ p_ccb->fcrb.ack_q_count_avg[index] +=
+ fixed_queue_length(p_ccb->fcrb.waiting_for_ack_q);
+
+ if (fixed_queue_length(p_ccb->fcrb.waiting_for_ack_q) >
+ p_ccb->fcrb.ack_q_count_max[index])
+ p_ccb->fcrb.ack_q_count_max[index] =
+ fixed_queue_length(p_ccb->fcrb.waiting_for_ack_q);
+
+ if (fixed_queue_length(p_ccb->fcrb.waiting_for_ack_q) <
+ p_ccb->fcrb.ack_q_count_min[index])
+ p_ccb->fcrb.ack_q_count_min[index] =
+ fixed_queue_length(p_ccb->fcrb.waiting_for_ack_q);
+
+ /* update sum, max and min of round trip delay of acking */
+ list_t* list = NULL;
+ if (!fixed_queue_is_empty(p_ccb->fcrb.waiting_for_ack_q))
+ list = fixed_queue_get_list(p_ccb->fcrb.waiting_for_ack_q);
+ if (list != NULL) {
+ for (const list_node_t *node = list_begin(list), xx = 0;
+ (node != list_end(list)) && (xx < num_bufs_acked);
+ node = list_next(node), xx++) {
+ p_buf = list_node(node);
+ /* adding up length of acked I-frames to get throughput */
+ p_ccb->fcrb.throughput[index] += p_buf->len - 8;
+
+ if (xx == num_bufs_acked - 1) {
+ /* get timestamp from tx I-frame that receiver is acking */
+ p = ((uint8_t*)(p_buf + 1)) + p_buf->offset + p_buf->len;
+ if (p_ccb->bypass_fcs != L2CAP_BYPASS_FCS) {
+ p += L2CAP_FCS_LEN;
+ }
+
+ STREAM_TO_UINT32(timestamp, p);
+ delay = static_cast<uint32_t>(
+ bluetooth::common::time_get_os_boottime_ms()) -
+ timestamp;
+
+ p_ccb->fcrb.ack_delay_avg[index] += delay;
+ if (delay > p_ccb->fcrb.ack_delay_max[index])
+ p_ccb->fcrb.ack_delay_max[index] = delay;
+ if (delay < p_ccb->fcrb.ack_delay_min[index])
+ p_ccb->fcrb.ack_delay_min[index] = delay;
+ }
+ }
+ }
+
+ p_ccb->fcrb.ack_delay_avg_count++;
+
+ /* calculate average and initialize next avg, min and max */
+ if (p_ccb->fcrb.ack_delay_avg_count > L2CAP_ERTM_STATS_AVG_NUM_SAMPLES) {
+ p_ccb->fcrb.ack_delay_avg_count = 0;
+
+ p_ccb->fcrb.ack_q_count_avg[index] /= L2CAP_ERTM_STATS_AVG_NUM_SAMPLES;
+ p_ccb->fcrb.ack_delay_avg[index] /= L2CAP_ERTM_STATS_AVG_NUM_SAMPLES;
+
+ /* calculate throughput */
+ timestamp = bluetooth::common::time_get_os_boottime_ms();
+ if (timestamp - p_ccb->fcrb.throughput_start > 0)
+ p_ccb->fcrb.throughput[index] /=
+ (timestamp - p_ccb->fcrb.throughput_start);
+
+ p_ccb->fcrb.throughput_start = timestamp;
+
+ snprintf(
+ str, sizeof(str),
+ "[%02u] throughput: %5u, ack_delay avg:%3u, min:%3u, max:%3u, "
+ "ack_q_count avg:%3u, min:%3u, max:%3u",
+ index, p_ccb->fcrb.throughput[index], p_ccb->fcrb.ack_delay_avg[index],
+ p_ccb->fcrb.ack_delay_min[index], p_ccb->fcrb.ack_delay_max[index],
+ p_ccb->fcrb.ack_q_count_avg[index], p_ccb->fcrb.ack_q_count_min[index],
+ p_ccb->fcrb.ack_q_count_max[index]);
+
+ BT_TRACE(TRACE_CTRL_GENERAL | TRACE_LAYER_GKI | TRACE_ORG_GKI,
+ TRACE_TYPE_GENERIC, "%s", str);
+
+ index = (index + 1) % L2CAP_ERTM_STATS_NUM_AVG;
+ p_ccb->fcrb.ack_delay_avg_index = index;
+
+ p_ccb->fcrb.ack_q_count_max[index] = 0;
+ p_ccb->fcrb.ack_q_count_min[index] = 0xFFFFFFFF;
+ p_ccb->fcrb.ack_q_count_avg[index] = 0;
+
+ p_ccb->fcrb.ack_delay_max[index] = 0;
+ p_ccb->fcrb.ack_delay_min[index] = 0xFFFFFFFF;
+ p_ccb->fcrb.ack_delay_avg[index] = 0;
+
+ p_ccb->fcrb.throughput[index] = 0;
+ }
+}
+#endif
diff --git a/stack/l2cap/l2c_int.h b/stack/l2cap/l2c_int.h
index b16678ba6..e58efaf16 100644
--- a/stack/l2cap/l2c_int.h
+++ b/stack/l2cap/l2c_int.h
@@ -25,27 +25,35 @@
#define L2C_INT_H
#include <stdbool.h>
-#include <string>
#include "bt_common.h"
#include "btm_api.h"
#include "btm_ble_api.h"
#include "l2c_api.h"
-#include "l2cap_acl_interface.h"
-#include "l2cap_controller_interface.h"
-#include "l2cap_hci_link_interface.h"
-#include "l2cap_security_interface.h"
#include "l2cdefs.h"
#include "osi/include/alarm.h"
#include "osi/include/fixed_queue.h"
#include "osi/include/list.h"
-#include "stack/include/hci_error_code.h"
-#include "types/hci_role.h"
#define L2CAP_MIN_MTU 48 /* Minimum acceptable MTU is 48 bytes */
-constexpr uint16_t L2CAP_CREDIT_BASED_MIN_MTU = 64;
-constexpr uint16_t L2CAP_CREDIT_BASED_MIN_MPS = 64;
+/* LE credit based L2CAP connection parameters */
+constexpr uint16_t L2CAP_LE_MIN_MTU = 23; // Minimum SDU size
+constexpr uint16_t L2CAP_LE_MIN_MPS = 23;
+constexpr uint16_t L2CAP_LE_MAX_MPS = 65533;
+constexpr uint16_t L2CAP_LE_CREDIT_MAX = 65535;
+
+// This is initial amout of credits we send, and amount to which we increase
+// credits once they fall below threshold
+constexpr uint16_t L2CAP_LE_CREDIT_DEFAULT = 0xffff;
+
+// If credit count on remote fall below this value, we send back credits to
+// reach default value.
+constexpr uint16_t L2CAP_LE_CREDIT_THRESHOLD = 0x0040;
+
+static_assert(L2CAP_LE_CREDIT_THRESHOLD < L2CAP_LE_CREDIT_DEFAULT,
+ "Threshold must be smaller then default credits");
+
#define L2CAP_NO_IDLE_TIMEOUT 0xFFFF
/*
@@ -54,6 +62,7 @@ constexpr uint16_t L2CAP_CREDIT_BASED_MIN_MPS = 64;
#define L2CAP_LINK_ROLE_SWITCH_TIMEOUT_MS (10 * 1000) /* 10 seconds */
#define L2CAP_LINK_CONNECT_TIMEOUT_MS (60 * 1000) /* 30 seconds */
#define L2CAP_LINK_CONNECT_EXT_TIMEOUT_MS (120 * 1000) /* 120 seconds */
+#define L2CAP_ECHO_RSP_TIMEOUT_MS (30 * 1000) /* 30 seconds */
#define L2CAP_LINK_FLOW_CONTROL_TIMEOUT_MS (2 * 1000) /* 2 seconds */
#define L2CAP_LINK_DISCONNECT_TIMEOUT_MS (30 * 1000) /* 30 seconds */
#define L2CAP_CHNL_CONNECT_TIMEOUT_MS (60 * 1000) /* 60 seconds */
@@ -81,27 +90,6 @@ typedef enum {
CST_W4_L2CA_DISCONNECT_RSP /* Waiting for upper layer disc rsp */
} tL2C_CHNL_STATE;
-#define CASE_RETURN_TEXT(code) \
- case code: \
- return #code
-
-inline std::string channel_state_text(const tL2C_CHNL_STATE& state) {
- switch (state) {
- CASE_RETURN_TEXT(CST_CLOSED);
- CASE_RETURN_TEXT(CST_ORIG_W4_SEC_COMP);
- CASE_RETURN_TEXT(CST_TERM_W4_SEC_COMP);
- CASE_RETURN_TEXT(CST_W4_L2CAP_CONNECT_RSP);
- CASE_RETURN_TEXT(CST_W4_L2CA_CONNECT_RSP);
- CASE_RETURN_TEXT(CST_CONFIG);
- CASE_RETURN_TEXT(CST_OPEN);
- CASE_RETURN_TEXT(CST_W4_L2CAP_DISCONNECT_RSP);
- CASE_RETURN_TEXT(CST_W4_L2CA_DISCONNECT_RSP);
- default:
- return std::string("UNKNOWN[%hhu]", state);
- }
-}
-#undef CASE_RETURN_TEXT
-
/* Define the possible L2CAP link states
*/
typedef enum {
@@ -113,99 +101,73 @@ typedef enum {
LST_DISCONNECTING
} tL2C_LINK_STATE;
-inline std::string link_state_text(const tL2C_LINK_STATE& state) {
- switch (state) {
- case LST_DISCONNECTED:
- return std::string("LST_DISCONNECTED");
- case LST_CONNECT_HOLDING:
- return std::string("LST_CONNECT_HOLDING");
- case LST_CONNECTING_WAIT_SWITCH:
- return std::string("LST_CONNECTING_WAIT_SWITCH");
- case LST_CONNECTING:
- return std::string("LST_CONNECTING");
- case LST_CONNECTED:
- return std::string("LST_CONNECTED");
- case LST_DISCONNECTING:
- return std::string("LST_DISCONNECTING");
- default:
- return std::string("UNKNOWN");
- }
-}
-
/* Define input events to the L2CAP link and channel state machines. The names
* of the events may seem a bit strange, but they are taken from
* the Bluetooth specification.
*/
-typedef enum : uint16_t {
- /* Lower layer */
- L2CEVT_LP_CONNECT_CFM = 0, /* connect confirm */
- L2CEVT_LP_CONNECT_CFM_NEG = 1, /* connect confirm (failed) */
- L2CEVT_LP_CONNECT_IND = 2, /* connect indication */
- L2CEVT_LP_DISCONNECT_IND = 3, /* disconnect indication */
-
- /* Security */
- L2CEVT_SEC_COMP = 7, /* cleared successfully */
- L2CEVT_SEC_COMP_NEG = 8, /* procedure failed */
-
- /* Peer connection */
- L2CEVT_L2CAP_CONNECT_REQ = 10, /* request */
- L2CEVT_L2CAP_CONNECT_RSP = 11, /* response */
- L2CEVT_L2CAP_CONNECT_RSP_PND = 12, /* response pending */
- L2CEVT_L2CAP_CONNECT_RSP_NEG = 13, /* response (failed) */
-
- /* Peer configuration */
- L2CEVT_L2CAP_CONFIG_REQ = 14, /* request */
- L2CEVT_L2CAP_CONFIG_RSP = 15, /* response */
- L2CEVT_L2CAP_CONFIG_RSP_NEG = 16, /* response (failed) */
-
- L2CEVT_L2CAP_DISCONNECT_REQ = 17, /* Peer disconnect request */
- L2CEVT_L2CAP_DISCONNECT_RSP = 18, /* Peer disconnect response */
- L2CEVT_L2CAP_INFO_RSP = 19, /* Peer information response */
- L2CEVT_L2CAP_DATA = 20, /* Peer data */
-
- /* Upper layer */
- L2CEVT_L2CA_CONNECT_REQ = 21, /* connect request */
- L2CEVT_L2CA_CONNECT_RSP = 22, /* connect response */
- L2CEVT_L2CA_CONNECT_RSP_NEG = 23, /* connect response (failed)*/
- L2CEVT_L2CA_CONFIG_REQ = 24, /* config request */
- L2CEVT_L2CA_CONFIG_RSP = 25, /* config response */
- L2CEVT_L2CA_DISCONNECT_REQ = 27, /* disconnect request */
- L2CEVT_L2CA_DISCONNECT_RSP = 28, /* disconnect response */
- L2CEVT_L2CA_DATA_READ = 29, /* data read */
- L2CEVT_L2CA_DATA_WRITE = 30, /* data write */
-
- L2CEVT_TIMEOUT = 32, /* Timeout */
- L2CEVT_SEC_RE_SEND_CMD = 33, /* btm_sec has enough info to proceed */
-
- L2CEVT_ACK_TIMEOUT = 34, /* RR delay timeout */
-
- L2CEVT_L2CA_SEND_FLOW_CONTROL_CREDIT = 35, /* Upper layer credit packet \
- */
- /* Peer credit based connection */
- L2CEVT_L2CAP_RECV_FLOW_CONTROL_CREDIT = 36, /* credit packet */
- L2CEVT_L2CAP_CREDIT_BASED_CONNECT_REQ =
- 37, /* credit based connection request */
- L2CEVT_L2CAP_CREDIT_BASED_CONNECT_RSP =
- 38, /* accepted credit based connection */
- L2CEVT_L2CAP_CREDIT_BASED_CONNECT_RSP_NEG =
- 39, /* rejected credit based connection */
- L2CEVT_L2CAP_CREDIT_BASED_RECONFIG_REQ =
- 40, /* credit based reconfig request*/
- L2CEVT_L2CAP_CREDIT_BASED_RECONFIG_RSP =
- 41, /* credit based reconfig response */
-
- /* Upper layer credit based connection */
- L2CEVT_L2CA_CREDIT_BASED_CONNECT_REQ = 42, /* connect request */
- L2CEVT_L2CA_CREDIT_BASED_CONNECT_RSP = 43, /* connect response */
- L2CEVT_L2CA_CREDIT_BASED_CONNECT_RSP_NEG = 44, /* connect response (failed)*/
- L2CEVT_L2CA_CREDIT_BASED_RECONFIG_REQ = 45, /* reconfig request */
-} tL2CEVT;
+/* Lower layer */
+#define L2CEVT_LP_CONNECT_CFM 0 /* connect confirm */
+#define L2CEVT_LP_CONNECT_CFM_NEG 1 /* connect confirm (failed) */
+#define L2CEVT_LP_CONNECT_IND 2 /* connect indication */
+#define L2CEVT_LP_DISCONNECT_IND 3 /* disconnect indication */
+#define L2CEVT_LP_QOS_CFM 4 /* QOS confirmation */
+#define L2CEVT_LP_QOS_CFM_NEG 5 /* QOS confirmation (failed)*/
+#define L2CEVT_LP_QOS_VIOLATION_IND 6 /* QOS violation indication */
+
+/* Security */
+#define L2CEVT_SEC_COMP 7 /* cleared successfully */
+#define L2CEVT_SEC_COMP_NEG 8 /* procedure failed */
+
+/* Peer connection */
+#define L2CEVT_L2CAP_CONNECT_REQ 10 /* request */
+#define L2CEVT_L2CAP_CONNECT_RSP 11 /* response */
+#define L2CEVT_L2CAP_CONNECT_RSP_PND 12 /* response pending */
+#define L2CEVT_L2CAP_CONNECT_RSP_NEG 13 /* response (failed) */
+
+/* Peer configuration */
+#define L2CEVT_L2CAP_CONFIG_REQ 14 /* request */
+#define L2CEVT_L2CAP_CONFIG_RSP 15 /* response */
+#define L2CEVT_L2CAP_CONFIG_RSP_NEG 16 /* response (failed) */
+
+#define L2CEVT_L2CAP_DISCONNECT_REQ 17 /* Peer disconnect request */
+#define L2CEVT_L2CAP_DISCONNECT_RSP 18 /* Peer disconnect response */
+#define L2CEVT_L2CAP_INFO_RSP 19 /* Peer information response */
+#define L2CEVT_L2CAP_DATA 20 /* Peer data */
+
+/* Upper layer */
+#define L2CEVT_L2CA_CONNECT_REQ 21 /* connect request */
+#define L2CEVT_L2CA_CONNECT_RSP 22 /* connect response */
+#define L2CEVT_L2CA_CONNECT_RSP_NEG 23 /* connect response (failed)*/
+#define L2CEVT_L2CA_CONFIG_REQ 24 /* config request */
+#define L2CEVT_L2CA_CONFIG_RSP 25 /* config response */
+#define L2CEVT_L2CA_CONFIG_RSP_NEG 26 /* config response (failed) */
+#define L2CEVT_L2CA_DISCONNECT_REQ 27 /* disconnect request */
+#define L2CEVT_L2CA_DISCONNECT_RSP 28 /* disconnect response */
+#define L2CEVT_L2CA_DATA_READ 29 /* data read */
+#define L2CEVT_L2CA_DATA_WRITE 30 /* data write */
+#define L2CEVT_L2CA_FLUSH_REQ 31 /* flush */
+
+#define L2CEVT_TIMEOUT 32 /* Timeout */
+#define L2CEVT_SEC_RE_SEND_CMD 33 /* btm_sec has enough info to proceed */
+
+#define L2CEVT_ACK_TIMEOUT 34 /* RR delay timeout */
+
+#define L2CEVT_L2CA_SEND_FLOW_CONTROL_CREDIT \
+ 35 /* Upper layer credit packet \
+ */
+#define L2CEVT_L2CAP_RECV_FLOW_CONTROL_CREDIT 36 /* Peer credit packet */
/* Constants for LE Dynamic PSM values */
#define LE_DYNAMIC_PSM_START 0x0080
#define LE_DYNAMIC_PSM_END 0x00FF
#define LE_DYNAMIC_PSM_RANGE (LE_DYNAMIC_PSM_END - LE_DYNAMIC_PSM_START + 1)
+/* Bitmask to skip over Broadcom feature reserved (ID) to avoid sending two
+ successive ID values, '0' id only or both */
+#define L2CAP_ADJ_BRCM_ID 0x1
+#define L2CAP_ADJ_ZERO_ID 0x2
+#define L2CAP_ADJ_ID 0x3
+
/* Return values for l2cu_process_peer_cfg_req() */
#define L2CAP_PEER_CFG_UNACCEPTABLE 0
#define L2CAP_PEER_CFG_OK 1
@@ -230,6 +192,7 @@ typedef struct {
uint8_t max_held_acks; /* Max acks we can hold before sending */
bool remote_busy; /* true if peer has flowed us off */
+ bool local_busy; /* true if we have flowed off the peer */
bool rej_sent; /* Reject was sent */
bool srej_sent; /* Selective Reject was sent */
@@ -248,6 +211,32 @@ typedef struct {
alarm_t* ack_timer; /* Timer delaying RR */
alarm_t* mon_retrans_timer; /* Timer Monitor or Retransmission */
+#if (L2CAP_ERTM_STATS == TRUE)
+ uint64_t connect_tick_count; /* Time channel was established */
+ uint32_t ertm_pkt_counts[2]; /* Packets sent and received */
+ uint32_t ertm_byte_counts[2]; /* Bytes sent and received */
+ uint32_t s_frames_sent[4]; /* S-frames sent (RR, REJ, RNR, SREJ) */
+ uint32_t s_frames_rcvd[4]; /* S-frames rcvd (RR, REJ, RNR, SREJ) */
+ uint32_t xmit_window_closed; /* # of times the xmit window was closed */
+ uint32_t controller_idle; /* # of times less than 2 packets in controller */
+ /* when the xmit window was closed */
+ uint32_t pkts_retransmitted; /* # of packets that were retransmitted */
+ uint32_t retrans_touts; /* # of retransmission timouts */
+ uint32_t xmit_ack_touts; /* # of xmit ack timouts */
+
+#define L2CAP_ERTM_STATS_NUM_AVG 10
+#define L2CAP_ERTM_STATS_AVG_NUM_SAMPLES 100
+ uint32_t ack_delay_avg_count;
+ uint32_t ack_delay_avg_index;
+ uint32_t throughput_start;
+ uint32_t throughput[L2CAP_ERTM_STATS_NUM_AVG];
+ uint32_t ack_delay_avg[L2CAP_ERTM_STATS_NUM_AVG];
+ uint32_t ack_delay_min[L2CAP_ERTM_STATS_NUM_AVG];
+ uint32_t ack_delay_max[L2CAP_ERTM_STATS_NUM_AVG];
+ uint32_t ack_q_count_avg[L2CAP_ERTM_STATS_NUM_AVG];
+ uint32_t ack_q_count_min[L2CAP_ERTM_STATS_NUM_AVG];
+ uint32_t ack_q_count_max[L2CAP_ERTM_STATS_NUM_AVG];
+#endif
} tL2C_FCRB;
typedef struct {
@@ -257,10 +246,6 @@ typedef struct {
uint16_t real_psm; /* This may be a dummy RCB for an o/b connection but */
/* this is the real PSM that we need to connect to */
tL2CAP_APPL_INFO api;
- tL2CAP_ERTM_INFO ertm_info;
- tL2CAP_LE_CFG_INFO coc_cfg;
- uint16_t my_mtu;
- uint16_t required_remote_mtu;
} tL2C_RCB;
#ifndef L2CAP_CBB_DEFAULT_DATA_RATE_BUFF_QUOTA
@@ -305,13 +290,14 @@ typedef struct t_l2c_ccb {
alarm_t* l2c_ccb_timer; /* CCB Timer Entry */
tL2C_RCB* p_rcb; /* Registration CB for this Channel */
+ bool should_free_rcb; /* True if RCB was allocated on the heap */
#define IB_CFG_DONE 0x01
#define OB_CFG_DONE 0x02
#define RECONFIG_FLAG 0x04 /* True after initial configuration */
+#define CFG_DONE_MASK (IB_CFG_DONE | OB_CFG_DONE)
uint8_t config_done; /* Configuration flag word */
- uint16_t remote_config_rsp_result; /* The config rsp result from remote */
uint8_t local_id; /* Transaction ID for local trans */
uint8_t remote_id; /* Transaction ID for local */
@@ -319,9 +305,8 @@ typedef struct t_l2c_ccb {
#define CCB_FLAG_SENT_PENDING 0x02 /* already sent pending response */
uint8_t flags;
- bool connection_initiator; /* true if we sent ConnectReq */
-
tL2CAP_CFG_INFO our_cfg; /* Our saved configuration options */
+ tL2CAP_CH_CFG_BITS peer_cfg_bits; /* Store what peer wants to configure */
tL2CAP_CFG_INFO peer_cfg; /* Peer's saved configuration options */
fixed_queue_t* xmit_hold_q; /* Transmit data hold queue */
@@ -342,40 +327,23 @@ typedef struct t_l2c_ccb {
bool out_cfg_fcr_present; /* true if cfg response shoulkd include fcr options
*/
+#define L2CAP_CFG_FCS_OUR 0x01 /* Our desired config FCS option */
+#define L2CAP_CFG_FCS_PEER 0x02 /* Peer's desired config FCS option */
+#define L2CAP_BYPASS_FCS (L2CAP_CFG_FCS_OUR | L2CAP_CFG_FCS_PEER)
+ uint8_t bypass_fcs;
+
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
bool is_flushable; /* true if channel is flushable */
+#endif
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
uint16_t fixed_chnl_idle_tout; /* Idle timeout to use for the fixed channel */
+#endif
uint16_t tx_data_len;
/* Number of LE frames that the remote can send to us (credit count in
* remote). Valid only for LE CoC */
uint16_t remote_credit_count;
-
- /* used to indicate that ECOC is used */
- bool ecoc{false};
- bool reconfig_started;
-
- struct {
- struct {
- unsigned bytes{0};
- unsigned packets{0};
- void operator()(unsigned bytes) {
- this->bytes += bytes;
- this->packets++;
- }
- } rx, tx;
- struct {
- struct {
- unsigned bytes{0};
- unsigned packets{0};
- void operator()(unsigned bytes) {
- this->bytes += bytes;
- this->packets++;
- }
- } rx, tx;
- } dropped;
- } metrics;
-
} tL2C_CCB;
/***********************************************************************
@@ -386,6 +354,8 @@ typedef struct {
tL2C_CCB* p_last_ccb; /* The last channel in this queue */
} tL2C_CCB_Q;
+#if (L2CAP_ROUND_ROBIN_CHANNEL_SERVICE == TRUE)
+
/* Round-Robin service for the same priority channels */
#define L2CAP_NUM_CHNL_PRIORITY \
3 /* Total number of priority group (high, medium, low)*/
@@ -394,8 +364,6 @@ typedef struct {
#define L2CAP_GET_PRIORITY_QUOTA(pri) \
((L2CAP_NUM_CHNL_PRIORITY - (pri)) * L2CAP_CHNL_PRIORITY_WEIGHT)
-#define L2CAP_CREDIT_BASED_MAX_CIDS 5
-
/* CCBs within the same LCB are served in round robin with priority It will make
* sure that low priority channel (for example, HF signaling on RFCOMM) can be
* sent to the headset even if higher priority channel (for example, AV media
@@ -409,16 +377,7 @@ typedef struct {
uint8_t quota; /* burst transmission quota */
} tL2C_RR_SERV;
-typedef enum : uint8_t {
- /* disable update connection parameters */
- L2C_BLE_CONN_UPDATE_DISABLE = (1u << 0),
- /* new connection parameter to be set */
- L2C_BLE_NEW_CONN_PARAM = (1u << 1),
- /* waiting for connection update finished */
- L2C_BLE_UPDATE_PENDING = (1u << 2),
- /* not using default connection parameters */
- L2C_BLE_NOT_DEFAULT_PARAM = (1u << 3),
-} tCONN_UPDATE_MASK;
+#endif /* (L2CAP_ROUND_ROBIN_CHANNEL_SERVICE == TRUE) */
/* Define a link control block. There is one link control block between
* this device and any other device (i.e. BD ADDR).
@@ -428,14 +387,7 @@ typedef struct t_l2c_linkcb {
tL2C_LINK_STATE link_state;
alarm_t* l2c_lcb_timer; /* Timer entry for timeout evt */
- private:
- uint16_t handle_; /* The handle used with LM */
- friend void l2cu_set_lcb_handle(struct t_l2c_linkcb& p_lcb, uint16_t handle);
- void SetHandle(uint16_t handle) { handle_ = handle; }
-
- public:
- uint16_t Handle() const { return handle_; }
- void InvalidateHandle() { handle_ = HCI_INVALID_HANDLE; }
+ uint16_t handle; /* The handle used with LM */
tL2C_CCB_Q ccb_queue; /* Queue of CCBs on this LCB */
@@ -443,79 +395,52 @@ typedef struct t_l2c_linkcb {
alarm_t* info_resp_timer; /* Timer entry for info resp timeout evt */
RawAddress remote_bd_addr; /* The BD address of the remote */
- private:
- tHCI_ROLE link_role_{HCI_ROLE_CENTRAL}; /* Central or peripheral */
- public:
- tHCI_ROLE LinkRole() const { return link_role_; }
- bool IsLinkRoleCentral() const { return link_role_ == HCI_ROLE_CENTRAL; }
- bool IsLinkRolePeripheral() const {
- return link_role_ == HCI_ROLE_PERIPHERAL;
- }
- void SetLinkRoleAsCentral() { link_role_ = HCI_ROLE_CENTRAL; }
- void SetLinkRoleAsPeripheral() { link_role_ = HCI_ROLE_PERIPHERAL; }
-
- uint8_t signal_id; /* Signalling channel id */
+ uint8_t link_role; /* Master or slave */
+ uint8_t id;
uint8_t cur_echo_id; /* Current id value for echo request */
+ tL2CA_ECHO_RSP_CB* p_echo_rsp_cb; /* Echo response callback */
uint16_t idle_timeout; /* Idle timeout */
- private:
- bool is_bonding_{false}; /* True - link active only for bonding */
- public:
- bool IsBonding() const { return is_bonding_; }
- void SetBonding() { is_bonding_ = true; }
- void ResetBonding() { is_bonding_ = false; }
+ bool is_bonding; /* True - link active only for bonding */
- uint16_t link_xmit_quota; /* Num outstanding pkts allowed */
- bool is_round_robin_scheduling() const { return link_xmit_quota == 0; }
+ uint16_t link_flush_tout; /* Flush timeout used */
+ uint16_t link_xmit_quota; /* Num outstanding pkts allowed */
uint16_t sent_not_acked; /* Num packets sent but not acked */
- void update_outstanding_packets(uint16_t packets_acked) {
- if (sent_not_acked > packets_acked)
- sent_not_acked -= packets_acked;
- else
- sent_not_acked = 0;
- }
bool partial_segment_being_sent; /* Set true when a partial segment */
/* is being sent. */
bool w4_info_rsp; /* true when info request is active */
+ uint8_t info_rx_bits; /* set 1 if received info type */
uint32_t peer_ext_fea; /* Peer's extended features mask */
list_t* link_xmit_data_q; /* Link transmit data buffer queue */
uint8_t peer_chnl_mask[L2CAP_FIXED_CHNL_ARRAY_SIZE];
- tL2CAP_PRIORITY acl_priority;
- bool is_normal_priority() const {
- return acl_priority == L2CAP_PRIORITY_NORMAL;
- }
- bool is_high_priority() const { return acl_priority == L2CAP_PRIORITY_HIGH; }
- bool set_priority(tL2CAP_PRIORITY priority) {
- if (acl_priority != priority) {
- acl_priority = priority;
- return true;
- }
- return false;
- }
+ BT_HDR* p_hcit_rcv_acl; /* Current HCIT ACL buf being rcvd */
+ uint16_t idle_timeout_sv; /* Save current Idle timeout */
+ uint8_t acl_priority; /* L2C_PRIORITY_NORMAL or L2C_PRIORITY_HIGH */
+ tL2CA_NOCP_CB* p_nocp_cb; /* Num Cmpl pkts callback */
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
tL2C_CCB* p_fixed_ccbs[L2CAP_NUM_FIXED_CHNLS];
-
- private:
- tHCI_REASON disc_reason_{HCI_ERR_UNDEFINED};
-
- public:
- tHCI_REASON DisconnectReason() const { return disc_reason_; }
- void SetDisconnectReason(tHCI_REASON disc_reason) {
- disc_reason_ = disc_reason;
- }
+ uint16_t disc_reason;
+#endif
tBT_TRANSPORT transport;
- bool is_transport_br_edr() const { return transport == BT_TRANSPORT_BR_EDR; }
- bool is_transport_ble() const { return transport == BT_TRANSPORT_LE; }
-
+ uint8_t initiating_phys; // LE PHY used for connection initiation
+ tBLE_ADDR_TYPE ble_addr_type;
uint16_t tx_data_len; /* tx data length used in data length extension */
fixed_queue_t* le_sec_pending_q; /* LE coc channels waiting for security check
completion */
uint8_t sec_act;
-
+#define L2C_BLE_CONN_UPDATE_DISABLE \
+ 0x1 /* disable update connection parameters */
+#define L2C_BLE_NEW_CONN_PARAM 0x2 /* new connection parameter to be set */
+#define L2C_BLE_UPDATE_PENDING \
+ 0x4 /* waiting for connection update finished \
+ */
+#define L2C_BLE_NOT_DEFAULT_PARAM \
+ 0x8 /* not using default connection parameters */
uint8_t conn_update_mask;
uint16_t min_interval; /* parameters as requested by peripheral */
@@ -525,33 +450,13 @@ typedef struct t_l2c_linkcb {
uint16_t min_ce_len;
uint16_t max_ce_len;
+#if (L2CAP_ROUND_ROBIN_CHANNEL_SERVICE == TRUE)
/* each priority group is limited burst transmission */
/* round robin service for the same priority channels */
tL2C_RR_SERV rr_serv[L2CAP_NUM_CHNL_PRIORITY];
uint8_t rr_pri; /* current serving priority group */
+#endif
- /* Pending ECOC reconfiguration data */
- tL2CAP_LE_CFG_INFO pending_ecoc_reconfig_cfg;
- uint8_t pending_ecoc_reconfig_cnt;
-
- /* This is to keep list of local cids use in the
- * credit based connection response.
- */
- uint16_t pending_ecoc_connection_cids[L2CAP_CREDIT_BASED_MAX_CIDS];
- uint8_t pending_ecoc_conn_cnt;
-
- uint16_t pending_lead_cid;
- uint16_t pending_l2cap_result;
-
- unsigned number_of_active_dynamic_channels() const {
- unsigned cnt = 0;
- const tL2C_CCB* cur = ccb_queue.p_first_ccb;
- while (cur != nullptr) {
- cnt++;
- cur = cur->p_next_ccb;
- }
- return cnt;
- }
} tL2C_LCB;
/* Define the L2CAP control structure
@@ -562,16 +467,6 @@ typedef struct {
uint16_t round_robin_quota; /* Round-robin link quota */
uint16_t round_robin_unacked; /* Round-robin unacked */
- bool is_classic_round_robin_quota_available() const {
- return round_robin_unacked < round_robin_quota;
- }
- void update_outstanding_classic_packets(uint16_t num_packets_acked) {
- if (round_robin_unacked > num_packets_acked)
- round_robin_unacked -= num_packets_acked;
- else
- round_robin_unacked = 0;
- }
-
bool check_round_robin; /* Do a round robin check */
bool is_cong_cback_context;
@@ -583,6 +478,8 @@ typedef struct {
tL2C_CCB* p_free_ccb_first; /* Pointer to first free CCB */
tL2C_CCB* p_free_ccb_last; /* Pointer to last free CCB */
+ uint8_t
+ desire_role; /* desire to be master/slave when accepting a connection */
bool disallow_switch; /* false, to allow switch at create conn */
uint16_t num_lm_acl_bufs; /* # of ACL buffers on controller */
uint16_t idle_timeout; /* Idle timeout */
@@ -591,18 +488,23 @@ typedef struct {
alarm_t* receive_hold_timer; /* Timer entry for rcv hold */
tL2C_LCB* p_cur_hcit_lcb; /* Current HCI Transport buffer */
- uint16_t num_used_lcbs; /* Number of active link control blocks */
+ uint16_t num_links_active; /* Number of links active */
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
uint16_t non_flushable_pbf; /* L2CAP_PKT_START_NON_FLUSHABLE if controller
supports */
/* Otherwise, L2CAP_PKT_START */
+ bool is_flush_active; /* true if an HCI_Enhanced_Flush has been sent */
+#endif
#if (L2CAP_CONFORMANCE_TESTING == TRUE)
uint32_t test_info_resp; /* Conformance testing needs a dynamic response */
#endif
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
tL2CAP_FIXED_CHNL_REG
fixed_reg[L2CAP_NUM_FIXED_CHNLS]; /* Reg info for fixed channels */
+#endif
uint16_t num_ble_links_active; /* Number of LE links active */
uint16_t controller_le_xmit_window; /* Total ACL window for all links */
@@ -610,19 +512,18 @@ typedef struct {
uint16_t num_lm_ble_bufs; /* # of ACL buffers on controller */
uint16_t ble_round_robin_quota; /* Round-robin link quota */
uint16_t ble_round_robin_unacked; /* Round-robin unacked */
- bool is_ble_round_robin_quota_available() const {
- return ble_round_robin_unacked < ble_round_robin_quota;
- }
- void update_outstanding_le_packets(uint16_t num_packets_acked) {
- if (ble_round_robin_unacked > num_packets_acked)
- ble_round_robin_unacked -= num_packets_acked;
- else
- ble_round_robin_unacked = 0;
- }
-
bool ble_check_round_robin; /* Do a round robin check */
tL2C_RCB ble_rcb_pool[BLE_MAX_L2CAP_CLIENTS]; /* Registration info pool */
+ tL2CA_ECHO_DATA_CB* p_echo_data_cb; /* Echo data callback */
+
+#if (L2CAP_HIGH_PRI_CHAN_QUOTA_IS_CONFIGURABLE == TRUE)
+ uint16_t high_pri_min_xmit_quota; /* Minimum number of ACL credit for high
+ priority link */
+#endif /* (L2CAP_HIGH_PRI_CHAN_QUOTA_IS_CONFIGURABLE == TRUE) */
+
+ uint16_t dyn_psm;
+
uint16_t le_dyn_psm; /* Next LE dynamic PSM value to try to assign */
bool le_dyn_psm_assigned[LE_DYNAMIC_PSM_RANGE]; /* Table of assigned LE PSM */
@@ -639,19 +540,29 @@ typedef struct {
uint16_t l2cap_result; /* L2CAP result */
uint16_t l2cap_status; /* L2CAP status */
uint16_t remote_cid; /* Remote CID */
- std::vector<uint16_t> lcids; /* Used when credit based is used*/
- uint16_t peer_mtu; /* Peer MTU */
} tL2C_CONN_INFO;
typedef void(tL2C_FCR_MGMT_EVT_HDLR)(uint8_t, tL2C_CCB*);
+/* Necessary info for postponed TX completion callback
+*/
+typedef struct {
+ uint16_t local_cid;
+ uint16_t num_sdu;
+ tL2CA_TX_COMPLETE_CB* cb;
+} tL2C_TX_COMPLETE_CB_INFO;
+
/* The offset in a buffer that L2CAP will use when building commands.
*/
#define L2CAP_SEND_CMD_OFFSET 0
/* Number of ACL buffers to use for high priority channel
*/
+#if (L2CAP_HIGH_PRI_CHAN_QUOTA_IS_CONFIGURABLE == FALSE)
#define L2CAP_HIGH_PRI_MIN_XMIT_QUOTA_A (L2CAP_HIGH_PRI_MIN_XMIT_QUOTA)
+#else
+#define L2CAP_HIGH_PRI_MIN_XMIT_QUOTA_A (l2cb.high_pri_min_xmit_quota)
+#endif
/* L2CAP global data
***********************************
@@ -661,23 +572,33 @@ extern tL2C_CB l2cb;
/* Functions provided by l2c_main.cc
***********************************
*/
+void l2c_init(void);
+void l2c_free(void);
extern void l2c_receive_hold_timer_timeout(void* data);
extern void l2c_ccb_timer_timeout(void* data);
extern void l2c_lcb_timer_timeout(void* data);
extern void l2c_fcrb_ack_timer_timeout(void* data);
extern uint8_t l2c_data_write(uint16_t cid, BT_HDR* p_data, uint16_t flag);
+extern void l2c_rcv_acl_data(BT_HDR* p_msg);
extern void l2c_process_held_packets(bool timed_out);
+/* Functions provided by l2c_utils.cc
+ ***********************************
+*/
+extern bool l2cu_can_allocate_lcb(void);
extern tL2C_LCB* l2cu_allocate_lcb(const RawAddress& p_bd_addr, bool is_bonding,
tBT_TRANSPORT transport);
+extern bool l2cu_start_post_bond_timer(uint16_t handle);
extern void l2cu_release_lcb(tL2C_LCB* p_lcb);
extern tL2C_LCB* l2cu_find_lcb_by_bd_addr(const RawAddress& p_bd_addr,
tBT_TRANSPORT transport);
extern tL2C_LCB* l2cu_find_lcb_by_handle(uint16_t handle);
+extern void l2cu_update_lcb_4_bonding(const RawAddress& p_bd_addr,
+ bool is_bonding);
-extern bool l2cu_set_acl_priority(const RawAddress& bd_addr,
- tL2CAP_PRIORITY priority,
+extern uint8_t l2cu_get_conn_role(tL2C_LCB* p_this_lcb);
+extern bool l2cu_set_acl_priority(const RawAddress& bd_addr, uint8_t priority,
bool reset_after_rs);
extern void l2cu_enqueue_ccb(tL2C_CCB* p_ccb);
@@ -689,6 +610,7 @@ extern void l2cu_release_ccb(tL2C_CCB* p_ccb);
extern tL2C_CCB* l2cu_find_ccb_by_cid(tL2C_LCB* p_lcb, uint16_t local_cid);
extern tL2C_CCB* l2cu_find_ccb_by_remote_cid(tL2C_LCB* p_lcb,
uint16_t remote_cid);
+extern void l2cu_adj_id(tL2C_LCB* p_lcb, uint8_t adj_mask);
extern bool l2c_is_cmd_rejected(uint8_t cmd_code, uint8_t id, tL2C_LCB* p_lcb);
extern void l2cu_send_peer_cmd_reject(tL2C_LCB* p_lcb, uint16_t reason,
@@ -703,6 +625,8 @@ extern void l2cu_send_peer_config_rej(tL2C_CCB* p_ccb, uint8_t* p_data,
extern void l2cu_send_peer_disc_req(tL2C_CCB* p_ccb);
extern void l2cu_send_peer_disc_rsp(tL2C_LCB* p_lcb, uint8_t remote_id,
uint16_t local_cid, uint16_t remote_cid);
+extern void l2cu_send_peer_echo_req(tL2C_LCB* p_lcb, uint8_t* p_data,
+ uint16_t data_len);
extern void l2cu_send_peer_echo_rsp(tL2C_LCB* p_lcb, uint8_t id,
uint8_t* p_data, uint16_t data_len);
extern void l2cu_send_peer_info_rsp(tL2C_LCB* p_lcb, uint8_t id,
@@ -714,36 +638,28 @@ extern void l2cu_set_acl_hci_header(BT_HDR* p_buf, tL2C_CCB* p_ccb);
extern void l2cu_check_channel_congestion(tL2C_CCB* p_ccb);
extern void l2cu_disconnect_chnl(tL2C_CCB* p_ccb);
+extern void l2cu_tx_complete(tL2C_TX_COMPLETE_CB_INFO* p_cbi);
+
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
+extern void l2cu_set_non_flushable_pbf(bool);
+#endif
+
extern void l2cu_send_peer_ble_par_req(tL2C_LCB* p_lcb, uint16_t min_int,
uint16_t max_int, uint16_t latency,
uint16_t timeout);
extern void l2cu_send_peer_ble_par_rsp(tL2C_LCB* p_lcb, uint16_t reason,
uint8_t rem_id);
-extern void l2cu_reject_ble_connection(tL2C_CCB* p_ccb, uint8_t rem_id,
+extern void l2cu_reject_ble_connection(tL2C_LCB* p_lcb, uint8_t rem_id,
uint16_t result);
-extern void l2cu_reject_credit_based_conn_req(tL2C_LCB* p_lcb, uint8_t rem_id,
- uint8_t num_of_channels,
- uint16_t result);
-extern void l2cu_reject_ble_coc_connection(tL2C_LCB* p_lcb, uint8_t rem_id,
- uint16_t result);
extern void l2cu_send_peer_ble_credit_based_conn_res(tL2C_CCB* p_ccb,
uint16_t result);
-extern void l2cu_send_peer_credit_based_conn_res(
- tL2C_CCB* p_ccb, std::vector<uint16_t>& accepted_lcids, uint16_t result);
-
extern void l2cu_send_peer_ble_credit_based_conn_req(tL2C_CCB* p_ccb);
-extern void l2cu_send_peer_credit_based_conn_req(tL2C_CCB* p_ccb);
-
-extern void l2cu_send_ble_reconfig_rsp(tL2C_LCB* p_lcb, uint8_t rem_id,
- uint16_t result);
-extern void l2cu_send_credit_based_reconfig_req(tL2C_CCB* p_ccb,
- tL2CAP_LE_CFG_INFO* p_data);
-
extern void l2cu_send_peer_ble_flow_control_credit(tL2C_CCB* p_ccb,
uint16_t credit_value);
extern void l2cu_send_peer_ble_credit_based_disconn_req(tL2C_CCB* p_ccb);
-extern bool l2cu_initialize_fixed_ccb(tL2C_LCB* p_lcb, uint16_t fixed_cid);
+extern bool l2cu_initialize_fixed_ccb(tL2C_LCB* p_lcb, uint16_t fixed_cid,
+ tL2CAP_FCR_OPTS* p_fcr);
extern void l2cu_no_dynamic_ccbs(tL2C_LCB* p_lcb);
extern void l2cu_process_fixed_chnl_resp(tL2C_LCB* p_lcb);
extern bool l2cu_is_ccb_active(tL2C_CCB* p_ccb);
@@ -751,6 +667,11 @@ extern bool l2cu_is_ccb_active(tL2C_CCB* p_ccb);
/* Functions provided for Broadcom Aware
***************************************
*/
+extern bool l2cu_check_feature_req(tL2C_LCB* p_lcb, uint8_t id, uint8_t* p_data,
+ uint16_t data_len);
+extern void l2cu_check_feature_rsp(tL2C_LCB* p_lcb, uint8_t id, uint8_t* p_data,
+ uint16_t data_len);
+extern void l2cu_send_feature_req(tL2C_CCB* p_ccb);
extern tL2C_RCB* l2cu_allocate_rcb(uint16_t psm);
extern tL2C_RCB* l2cu_find_rcb_by_psm(uint16_t psm);
@@ -765,29 +686,57 @@ extern void l2cu_process_peer_cfg_rsp(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg);
extern void l2cu_process_our_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg);
extern void l2cu_process_our_cfg_rsp(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg);
+extern void l2cu_device_reset(void);
extern tL2C_LCB* l2cu_find_lcb_by_state(tL2C_LINK_STATE state);
extern bool l2cu_lcb_disconnecting(void);
-extern void l2cu_create_conn_br_edr(tL2C_LCB* p_lcb);
+extern bool l2cu_create_conn_br_edr(tL2C_LCB* p_lcb);
extern bool l2cu_create_conn_le(tL2C_LCB* p_lcb);
-extern void l2cu_create_conn_after_switch(tL2C_LCB* p_lcb);
+extern bool l2cu_create_conn_le(tL2C_LCB* p_lcb, uint8_t initiating_phys);
+extern bool l2cu_create_conn_after_switch(tL2C_LCB* p_lcb);
+extern BT_HDR* l2cu_get_next_buffer_to_send(tL2C_LCB* p_lcb,
+ tL2C_TX_COMPLETE_CB_INFO* p_cbi);
+extern void l2cu_resubmit_pending_sec_req(const RawAddress* p_bda);
+extern void l2cu_initialize_amp_ccb(tL2C_LCB* p_lcb);
extern void l2cu_adjust_out_mps(tL2C_CCB* p_ccb);
/* Functions provided by l2c_link.cc
***********************************
*/
+extern bool l2c_link_hci_conn_req(const RawAddress& bd_addr);
+extern bool l2c_link_hci_conn_comp(uint8_t status, uint16_t handle,
+ const RawAddress& p_bda);
+extern bool l2c_link_hci_disc_comp(uint16_t handle, uint8_t reason);
+extern bool l2c_link_hci_qos_violation(uint16_t handle);
extern void l2c_link_timeout(tL2C_LCB* p_lcb);
extern void l2c_info_resp_timer_timeout(void* data);
-extern void l2c_link_check_send_pkts(tL2C_LCB* p_lcb, uint16_t local_cid,
+extern void l2c_link_check_send_pkts(tL2C_LCB* p_lcb, tL2C_CCB* p_ccb,
BT_HDR* p_buf);
extern void l2c_link_adjust_allocation(void);
-
+extern void l2c_link_process_num_completed_pkts(uint8_t* p, uint8_t evt_len);
+extern void l2c_link_process_num_completed_blocks(uint8_t controller_id,
+ uint8_t* p, uint16_t evt_len);
+extern void l2c_link_processs_num_bufs(uint16_t num_lm_acl_bufs);
+extern uint8_t l2c_link_pkts_rcvd(uint16_t* num_pkts, uint16_t* handles);
+extern void l2c_link_role_changed(const RawAddress* bd_addr, uint8_t new_role,
+ uint8_t hci_status);
extern void l2c_link_sec_comp(const RawAddress* p_bda, tBT_TRANSPORT trasnport,
- void* p_ref_data, tBTM_STATUS status);
+ void* p_ref_data, uint8_t status);
extern void l2c_link_sec_comp2(const RawAddress& p_bda, tBT_TRANSPORT trasnport,
- void* p_ref_data, tBTM_STATUS status);
+ void* p_ref_data, uint8_t status);
+extern void l2c_link_segments_xmitted(BT_HDR* p_msg);
+extern void l2c_pin_code_request(const RawAddress& bd_addr);
extern void l2c_link_adjust_chnl_allocation(void);
+extern void l2c_link_processs_ble_num_bufs(uint16_t num_lm_acl_bufs);
+
+#if (L2CAP_WAKE_PARKED_LINK == TRUE)
+extern bool l2c_link_check_power_mode(tL2C_LCB* p_lcb);
+#define L2C_LINK_CHECK_POWER_MODE(x) l2c_link_check_power_mode((x))
+#else // L2CAP_WAKE_PARKED_LINK
+#define L2C_LINK_CHECK_POWER_MODE(x) (false)
+#endif // L2CAP_WAKE_PARKED_LINK
+
#if (L2CAP_CONFORMANCE_TESTING == TRUE)
/* Used only for conformance testing */
extern void l2cu_set_info_rsp_mask(uint32_t mask);
@@ -796,7 +745,7 @@ extern void l2cu_set_info_rsp_mask(uint32_t mask);
/* Functions provided by l2c_csm.cc
***********************************
*/
-extern void l2c_csm_execute(tL2C_CCB* p_ccb, tL2CEVT event, void* p_data);
+extern void l2c_csm_execute(tL2C_CCB* p_ccb, uint16_t event, void* p_data);
extern void l2c_enqueue_peer_data(tL2C_CCB* p_ccb, BT_HDR* p_buf);
@@ -821,7 +770,8 @@ extern BT_HDR* l2c_lcc_get_next_xmit_sdu_seg(tL2C_CCB* p_ccb,
/* Configuration negotiation */
extern uint8_t l2c_fcr_chk_chan_modes(tL2C_CCB* p_ccb);
-
+extern bool l2c_fcr_adj_our_req_options(tL2C_CCB* p_ccb,
+ tL2CAP_CFG_INFO* p_cfg);
extern void l2c_fcr_adj_our_rsp_options(tL2C_CCB* p_ccb,
tL2CAP_CFG_INFO* p_peer_cfg);
extern bool l2c_fcr_renegotiate_chan(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg);
@@ -836,7 +786,15 @@ extern void l2c_fcr_stop_timer(tL2C_CCB* p_ccb);
extern bool l2cble_create_conn(tL2C_LCB* p_lcb);
extern void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p,
uint16_t pkt_len);
+extern void l2cble_conn_comp(uint16_t handle, uint8_t role,
+ const RawAddress& bda, tBLE_ADDR_TYPE type,
+ uint16_t conn_interval, uint16_t conn_latency,
+ uint16_t conn_timeout);
+extern void l2cble_notify_le_connection(const RawAddress& bda);
extern void l2c_ble_link_adjust_allocation(void);
+extern void l2cble_process_conn_update_evt(uint16_t handle, uint8_t status,
+ uint16_t interval, uint16_t latency,
+ uint16_t timeout);
extern void l2cble_credit_based_conn_req(tL2C_CCB* p_ccb);
extern void l2cble_credit_based_conn_res(tL2C_CCB* p_ccb, uint16_t result);
@@ -849,7 +807,20 @@ extern tL2CAP_LE_RESULT_CODE l2ble_sec_access_req(const RawAddress& bd_addr,
tL2CAP_SEC_CBACK* p_callback,
void* p_ref_data);
+#if (BLE_LLT_INCLUDED == TRUE)
+extern void l2cble_process_rc_param_request_evt(uint16_t handle,
+ uint16_t int_min,
+ uint16_t int_max,
+ uint16_t latency,
+ uint16_t timeout);
+#endif
+
extern void l2cble_update_data_length(tL2C_LCB* p_lcb);
+extern void l2cble_set_fixed_channel_tx_data_length(
+ const RawAddress& remote_bda, uint16_t fix_cid, uint16_t tx_mtu);
+extern void l2cble_process_data_length_change_event(uint16_t handle,
+ uint16_t tx_data_len,
+ uint16_t rx_data_len);
extern void l2cu_process_fixed_disc_cback(tL2C_LCB* p_lcb);
diff --git a/stack/l2cap/l2c_link.cc b/stack/l2cap/l2c_link.cc
index 70adbb661..f15e12319 100644
--- a/stack/l2cap/l2c_link.cc
+++ b/stack/l2cap/l2c_link.cc
@@ -23,38 +23,28 @@
* are managed.
*
******************************************************************************/
-#define LOG_TAG "l2c_link"
-
-#include <cstdint>
+#include <base/logging.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+
+#include "bt_common.h"
+#include "bt_types.h"
+#include "bt_utils.h"
+#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
#include "device/include/controller.h"
-#include "main/shim/l2c_api.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
+#include "hcimsgs.h"
+#include "l2c_api.h"
+#include "l2c_int.h"
+#include "l2cdefs.h"
+#include "log/log.h"
#include "osi/include/osi.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcimsgs.h"
-#include "stack/l2cap/l2c_int.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
-
-extern tBTM_CB btm_cb;
-
-bool BTM_ReadPowerMode(const RawAddress& remote_bda, tBTM_PM_MODE* p_mode);
-bool btm_dev_support_role_switch(const RawAddress& bd_addr);
-tBTM_STATUS btm_sec_disconnect(uint16_t handle, tHCI_STATUS reason);
-void btm_acl_created(const RawAddress& bda, uint16_t hci_handle,
- uint8_t link_role, tBT_TRANSPORT transport);
-void btm_acl_removed(uint16_t handle);
-void btm_acl_set_paging(bool value);
-void btm_ble_decrement_link_topology_mask(uint8_t link_role);
-void btm_sco_acl_removed(const RawAddress* bda);
-
-static void l2c_link_send_to_lower(tL2C_LCB* p_lcb, BT_HDR* p_buf);
-static BT_HDR* l2cu_get_next_buffer_to_send(tL2C_LCB* p_lcb);
+
+static bool l2c_link_send_to_lower(tL2C_LCB* p_lcb, BT_HDR* p_buf,
+ tL2C_TX_COMPLETE_CB_INFO* p_cbi);
/*******************************************************************************
*
@@ -63,8 +53,10 @@ static BT_HDR* l2cu_get_next_buffer_to_send(tL2C_LCB* p_lcb);
* Description This function is called when an HCI Connection Request
* event is received.
*
+ * Returns true, if accept conn
+ *
******************************************************************************/
-void l2c_link_hci_conn_req(const RawAddress& bd_addr) {
+bool l2c_link_hci_conn_req(const RawAddress& bd_addr) {
tL2C_LCB* p_lcb;
tL2C_LCB* p_lcb_cur;
int xx;
@@ -78,71 +70,88 @@ void l2c_link_hci_conn_req(const RawAddress& bd_addr) {
p_lcb = l2cu_allocate_lcb(bd_addr, false, BT_TRANSPORT_BR_EDR);
if (!p_lcb) {
btsnd_hcic_reject_conn(bd_addr, HCI_ERR_HOST_REJECT_RESOURCES);
- LOG_ERROR("L2CAP failed to allocate LCB");
- return;
+ L2CAP_TRACE_ERROR("L2CAP failed to allocate LCB");
+ return false;
}
no_links = true;
- /* If we already have connection, accept as a central */
+ /* If we already have connection, accept as a master */
for (xx = 0, p_lcb_cur = &l2cb.lcb_pool[0]; xx < MAX_L2CAP_LINKS;
xx++, p_lcb_cur++) {
if (p_lcb_cur == p_lcb) continue;
if (p_lcb_cur->in_use) {
no_links = false;
- p_lcb->SetLinkRoleAsCentral();
+ p_lcb->link_role = HCI_ROLE_MASTER;
break;
}
}
if (no_links) {
- if (!btm_dev_support_role_switch(bd_addr))
- p_lcb->SetLinkRoleAsPeripheral();
+ if (!btm_dev_support_switch(bd_addr))
+ p_lcb->link_role = HCI_ROLE_SLAVE;
else
- p_lcb->SetLinkRoleAsCentral();
+ p_lcb->link_role = l2cu_get_conn_role(p_lcb);
}
/* Tell the other side we accept the connection */
- acl_accept_connection_request(bd_addr, p_lcb->LinkRole());
+ btsnd_hcic_accept_conn(bd_addr, p_lcb->link_role);
p_lcb->link_state = LST_CONNECTING;
/* Start a timer waiting for connect complete */
alarm_set_on_mloop(p_lcb->l2c_lcb_timer, L2CAP_LINK_CONNECT_TIMEOUT_MS,
l2c_lcb_timer_timeout, p_lcb);
- return;
+ return (true);
}
- /* We already had a link control block. Check what state it is in
+ /* We already had a link control block to the guy. Check what state it is in
*/
if ((p_lcb->link_state == LST_CONNECTING) ||
(p_lcb->link_state == LST_CONNECT_HOLDING)) {
- if (!btm_dev_support_role_switch(bd_addr))
- p_lcb->SetLinkRoleAsPeripheral();
+ /* Connection collision. Accept the connection anyways. */
+
+ if (!btm_dev_support_switch(bd_addr))
+ p_lcb->link_role = HCI_ROLE_SLAVE;
else
- p_lcb->SetLinkRoleAsCentral();
+ p_lcb->link_role = l2cu_get_conn_role(p_lcb);
- acl_accept_connection_request(bd_addr, p_lcb->LinkRole());
+ btsnd_hcic_accept_conn(bd_addr, p_lcb->link_role);
p_lcb->link_state = LST_CONNECTING;
+ return (true);
} else if (p_lcb->link_state == LST_DISCONNECTING) {
- acl_reject_connection_request(bd_addr, HCI_ERR_HOST_REJECT_DEVICE);
+ /* In disconnecting state, reject the connection. */
+ btsnd_hcic_reject_conn(bd_addr, HCI_ERR_HOST_REJECT_DEVICE);
} else {
- LOG_ERROR("L2CAP got conn_req while connected (state:%d). Reject it",
- p_lcb->link_state);
- acl_reject_connection_request(bd_addr, HCI_ERR_CONNECTION_EXISTS);
+ L2CAP_TRACE_ERROR(
+ "L2CAP got conn_req while connected (state:%d). Reject it",
+ p_lcb->link_state);
+ /* Reject the connection with ACL Connection Already exist reason */
+ btsnd_hcic_reject_conn(bd_addr, HCI_ERR_CONNECTION_EXISTS);
}
+ return (false);
}
-void l2c_link_hci_conn_comp(tHCI_STATUS status, uint16_t handle,
+/*******************************************************************************
+ *
+ * Function l2c_link_hci_conn_comp
+ *
+ * Description This function is called when an HCI Connection Complete
+ * event is received.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+bool l2c_link_hci_conn_comp(uint8_t status, uint16_t handle,
const RawAddress& p_bda) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return;
- }
tL2C_CONN_INFO ci;
tL2C_LCB* p_lcb;
tL2C_CCB* p_ccb;
+ tBTM_SEC_DEV_REC* p_dev_info = NULL;
+
+ btm_acl_update_busy_level(BTM_BLI_PAGE_DONE_EVT);
/* Save the parameters */
ci.status = status;
@@ -153,35 +162,31 @@ void l2c_link_hci_conn_comp(tHCI_STATUS status, uint16_t handle,
/* If we don't have one, allocate one */
if (p_lcb == nullptr) {
+ L2CAP_TRACE_WARNING("No available link control block, try allocate one");
p_lcb = l2cu_allocate_lcb(ci.bd_addr, false, BT_TRANSPORT_BR_EDR);
if (p_lcb == nullptr) {
- LOG_WARN("Failed to allocate an LCB");
- return;
+ L2CAP_TRACE_WARNING("%s: Failed to allocate an LCB", __func__);
+ return (false);
}
- LOG_DEBUG("Allocated l2cap control block for new connection state:%s",
- link_state_text(p_lcb->link_state).c_str());
p_lcb->link_state = LST_CONNECTING;
}
if ((p_lcb->link_state == LST_CONNECTED) &&
(status == HCI_ERR_CONNECTION_EXISTS)) {
- LOG_WARN("Connection already exists handle:0x%04x", handle);
- return;
+ L2CAP_TRACE_WARNING("%s: An ACL connection already exists. Handle:%d",
+ __func__, handle);
+ return (true);
} else if (p_lcb->link_state != LST_CONNECTING) {
- LOG_ERROR(
- "Link received unexpected connection complete state:%s status:%s "
- "handle:0x%04x",
- link_state_text(p_lcb->link_state).c_str(),
- hci_error_code_text(status).c_str(), p_lcb->Handle());
- if (status != HCI_SUCCESS) {
- LOG_ERROR("Disconnecting...");
- l2c_link_hci_disc_comp(p_lcb->Handle(), status);
- }
- return;
+ L2CAP_TRACE_ERROR("L2CAP got conn_comp in bad state: %d status: 0x%d",
+ p_lcb->link_state, status);
+
+ if (status != HCI_SUCCESS) l2c_link_hci_disc_comp(p_lcb->handle, status);
+
+ return (false);
}
/* Save the handle */
- l2cu_set_lcb_handle(*p_lcb, handle);
+ p_lcb->handle = handle;
if (ci.status == HCI_SUCCESS) {
/* Connected OK. Change state to connected */
@@ -190,9 +195,21 @@ void l2c_link_hci_conn_comp(tHCI_STATUS status, uint16_t handle,
/* Get the peer information if the l2cap flow-control/rtrans is supported */
l2cu_send_peer_info_req(p_lcb, L2CAP_EXTENDED_FEATURES_INFO_TYPE);
- if (p_lcb->IsBonding()) {
- LOG_DEBUG("Link is dedicated bonding handle:0x%04x", p_lcb->Handle());
- if (l2cu_start_post_bond_timer(handle)) return;
+ /* Tell BTM Acl management about the link */
+ p_dev_info = btm_find_dev(p_bda);
+ if (p_dev_info != NULL)
+ btm_acl_created(ci.bd_addr, p_dev_info->dev_class,
+ p_dev_info->sec_bd_name, handle, p_lcb->link_role,
+ BT_TRANSPORT_BR_EDR);
+ else
+ btm_acl_created(ci.bd_addr, NULL, NULL, handle, p_lcb->link_role,
+ BT_TRANSPORT_BR_EDR);
+
+ BTM_SetLinkSuperTout(ci.bd_addr, btm_cb.btm_def_link_super_tout);
+
+ /* If dedicated bonding do not process any further */
+ if (p_lcb->is_bonding) {
+ if (l2cu_start_post_bond_timer(handle)) return (true);
}
/* Update the timeouts in the hold queue */
@@ -206,7 +223,11 @@ void l2c_link_hci_conn_comp(tHCI_STATUS status, uint16_t handle,
l2c_csm_execute(p_ccb, L2CEVT_LP_CONNECT_CFM, &ci);
}
- if (!p_lcb->ccb_queue.p_first_ccb) {
+ if (p_lcb->p_echo_rsp_cb) {
+ l2cu_send_peer_echo_req(p_lcb, NULL, 0);
+ alarm_set_on_mloop(p_lcb->l2c_lcb_timer, L2CAP_ECHO_RSP_TIMEOUT_MS,
+ l2c_lcb_timer_timeout, p_lcb);
+ } else if (!p_lcb->ccb_queue.p_first_ccb) {
uint64_t timeout_ms = L2CAP_LINK_STARTUP_TOUT * 1000;
alarm_set_on_mloop(p_lcb->l2c_lcb_timer, timeout_ms,
l2c_lcb_timer_timeout, p_lcb);
@@ -216,10 +237,8 @@ void l2c_link_hci_conn_comp(tHCI_STATUS status, uint16_t handle,
/* If there's an lcb disconnecting set this one to holding */
else if ((ci.status == HCI_ERR_MAX_NUM_OF_CONNECTIONS) &&
l2cu_lcb_disconnecting()) {
- LOG_WARN("Delaying connection as reached max number of links:%u",
- HCI_ERR_MAX_NUM_OF_CONNECTIONS);
p_lcb->link_state = LST_CONNECT_HOLDING;
- p_lcb->InvalidateHandle();
+ p_lcb->handle = HCI_INVALID_HANDLE;
} else {
/* Just in case app decides to try again in the callback context */
p_lcb->link_state = LST_DISCONNECTING;
@@ -234,9 +253,7 @@ void l2c_link_hci_conn_comp(tHCI_STATUS status, uint16_t handle,
p_ccb = pn;
}
- LOG_INFO("Disconnecting link handle:0x%04x status:%s", p_lcb->Handle(),
- hci_error_code_text(status).c_str());
- p_lcb->SetDisconnectReason(status);
+ p_lcb->disc_reason = status;
/* Release the LCB */
if (p_lcb->ccb_queue.p_first_ccb == NULL)
l2cu_release_lcb(p_lcb);
@@ -251,6 +268,7 @@ void l2c_link_hci_conn_comp(tHCI_STATUS status, uint16_t handle,
}
}
}
+ return (true);
}
/*******************************************************************************
@@ -265,25 +283,23 @@ void l2c_link_hci_conn_comp(tHCI_STATUS status, uint16_t handle,
******************************************************************************/
void l2c_link_sec_comp(const RawAddress* p_bda,
UNUSED_ATTR tBT_TRANSPORT transport, void* p_ref_data,
- tBTM_STATUS status) {
+ uint8_t status) {
l2c_link_sec_comp2(*p_bda, transport, p_ref_data, status);
}
void l2c_link_sec_comp2(const RawAddress& p_bda,
UNUSED_ATTR tBT_TRANSPORT transport, void* p_ref_data,
- tBTM_STATUS status) {
+ uint8_t status) {
tL2C_CONN_INFO ci;
tL2C_LCB* p_lcb;
tL2C_CCB* p_ccb;
tL2C_CCB* p_next_ccb;
+ uint8_t event;
- LOG_DEBUG("btm_status=%s, BD_ADDR=%s, transport=%s",
- btm_status_text(status).c_str(), PRIVATE_ADDRESS(p_bda),
- bt_transport_text(transport).c_str());
+ L2CAP_TRACE_DEBUG("%s: status=%d, p_ref_data=%p, BD_ADDR=%s", __func__,
+ status, p_ref_data, p_bda.ToString().c_str());
- if (status == BTM_SUCCESS_NO_SECURITY) {
- status = BTM_SUCCESS;
- }
+ if (status == BTM_SUCCESS_NO_SECURITY) status = BTM_SUCCESS;
/* Save the parameters */
ci.status = status;
@@ -293,7 +309,7 @@ void l2c_link_sec_comp2(const RawAddress& p_bda,
/* If we don't have one, this is an error */
if (!p_lcb) {
- LOG_WARN("L2CAP got sec_comp for unknown BD_ADDR");
+ L2CAP_TRACE_WARNING("L2CAP got sec_comp for unknown BD_ADDR");
return;
}
@@ -304,7 +320,7 @@ void l2c_link_sec_comp2(const RawAddress& p_bda,
if (p_ccb == p_ref_data) {
switch (status) {
case BTM_SUCCESS:
- l2c_csm_execute(p_ccb, L2CEVT_SEC_COMP, &ci);
+ event = L2CEVT_SEC_COMP;
break;
case BTM_DELAY_CHECK:
@@ -316,9 +332,9 @@ void l2c_link_sec_comp2(const RawAddress& p_bda,
return;
default:
- l2c_csm_execute(p_ccb, L2CEVT_SEC_COMP_NEG, &ci);
- break;
+ event = L2CEVT_SEC_COMP_NEG;
}
+ l2c_csm_execute(p_ccb, event, &ci);
break;
}
}
@@ -334,28 +350,33 @@ void l2c_link_sec_comp2(const RawAddress& p_bda,
* Returns true if the link is known about, else false
*
******************************************************************************/
-bool l2c_link_hci_disc_comp(uint16_t handle, tHCI_REASON reason) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return false;
- }
-
- tL2C_LCB* p_lcb = l2cu_find_lcb_by_handle(handle);
+bool l2c_link_hci_disc_comp(uint16_t handle, uint8_t reason) {
+ tL2C_LCB* p_lcb;
tL2C_CCB* p_ccb;
bool status = true;
bool lcb_is_free = true;
+ tBT_TRANSPORT transport = BT_TRANSPORT_BR_EDR;
+
+ /* See if we have a link control block for the connection */
+ p_lcb = l2cu_find_lcb_by_handle(handle);
/* If we don't have one, maybe an SCO link. Send to MM */
if (!p_lcb) {
status = false;
} else {
- p_lcb->SetDisconnectReason(reason);
+ /* There can be a case when we rejected PIN code authentication */
+ /* otherwise save a new reason */
+ if (btm_cb.acl_disc_reason != HCI_ERR_HOST_REJECT_SECURITY)
+ btm_cb.acl_disc_reason = reason;
+
+ p_lcb->disc_reason = btm_cb.acl_disc_reason;
/* Just in case app decides to try again in the callback context */
p_lcb->link_state = LST_DISCONNECTING;
/* Check for BLE and handle that differently */
if (p_lcb->transport == BT_TRANSPORT_LE)
- btm_ble_decrement_link_topology_mask(p_lcb->LinkRole());
+ btm_ble_update_link_topology_mask(p_lcb->link_role, false);
/* Link is disconnected. For all channels, send the event through */
/* their FSMs. The CCBs should remove themselves from the LCB */
for (p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb;) {
@@ -383,7 +404,8 @@ bool l2c_link_hci_disc_comp(uint16_t handle, tHCI_REASON reason) {
disconnecting
*/
if (p_lcb->ccb_queue.p_first_ccb != NULL || p_lcb->p_pending_ccb) {
- LOG_DEBUG("l2c_link_hci_disc_comp: Restarting pending ACL request");
+ L2CAP_TRACE_DEBUG(
+ "l2c_link_hci_disc_comp: Restarting pending ACL request");
/* Release any held buffers */
while (!list_is_empty(p_lcb->link_xmit_data_q)) {
BT_HDR* p_buf =
@@ -391,11 +413,13 @@ bool l2c_link_hci_disc_comp(uint16_t handle, tHCI_REASON reason) {
list_remove(p_lcb->link_xmit_data_q, p_buf);
osi_free(p_buf);
}
+ transport = p_lcb->transport;
/* for LE link, always drop and re-open to ensure to get LE remote feature
*/
if (p_lcb->transport == BT_TRANSPORT_LE) {
- btm_acl_removed(handle);
+ btm_acl_removed(p_lcb->remote_bd_addr, p_lcb->transport);
} else {
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
/* If we are going to re-use the LCB without dropping it, release all
fixed channels
here */
@@ -405,17 +429,17 @@ bool l2c_link_hci_disc_comp(uint16_t handle, tHCI_REASON reason) {
p_lcb->p_fixed_ccbs[xx] != p_lcb->p_pending_ccb) {
(*l2cb.fixed_reg[xx].pL2CA_FixedConn_Cb)(
xx + L2CAP_FIRST_FIXED_CHNL, p_lcb->remote_bd_addr, false,
- p_lcb->DisconnectReason(), p_lcb->transport);
+ p_lcb->disc_reason, p_lcb->transport);
if (p_lcb->p_fixed_ccbs[xx] == NULL) {
- LOG_ERROR(
- "unexpected p_fixed_ccbs[%d] is NULL remote_bd_addr = %s "
+ L2CAP_TRACE_ERROR(
+ "%s: unexpected p_fixed_ccbs[%d] is NULL remote_bd_addr = %s "
"p_lcb = %p in_use = %d link_state = %d handle = %d "
"link_role = %d is_bonding = %d disc_reason = %d transport = "
"%d",
- xx, p_lcb->remote_bd_addr.ToString().c_str(), p_lcb,
- p_lcb->in_use, p_lcb->link_state, p_lcb->Handle(),
- p_lcb->LinkRole(), p_lcb->IsBonding(),
- p_lcb->DisconnectReason(), p_lcb->transport);
+ __func__, xx, p_lcb->remote_bd_addr.ToString().c_str(), p_lcb,
+ p_lcb->in_use, p_lcb->link_state, p_lcb->handle,
+ p_lcb->link_role, p_lcb->is_bonding, p_lcb->disc_reason,
+ p_lcb->transport);
}
CHECK(p_lcb->p_fixed_ccbs[xx] != NULL);
l2cu_release_ccb(p_lcb->p_fixed_ccbs[xx]);
@@ -423,13 +447,14 @@ bool l2c_link_hci_disc_comp(uint16_t handle, tHCI_REASON reason) {
p_lcb->p_fixed_ccbs[xx] = NULL;
}
}
+#endif
}
if (p_lcb->transport == BT_TRANSPORT_LE) {
if (l2cu_create_conn_le(p_lcb))
lcb_is_free = false; /* still using this lcb */
} else {
- l2cu_create_conn_br_edr(p_lcb);
- lcb_is_free = false; /* still using this lcb */
+ if (l2cu_create_conn_br_edr(p_lcb))
+ lcb_is_free = false; /* still using this lcb */
}
}
@@ -451,6 +476,35 @@ bool l2c_link_hci_disc_comp(uint16_t handle, tHCI_REASON reason) {
/*******************************************************************************
*
+ * Function l2c_link_hci_qos_violation
+ *
+ * Description This function is called when an HCI QOS Violation
+ * event is received.
+ *
+ * Returns true if the link is known about, else false
+ *
+ ******************************************************************************/
+bool l2c_link_hci_qos_violation(uint16_t handle) {
+ tL2C_LCB* p_lcb;
+ tL2C_CCB* p_ccb;
+
+ /* See if we have a link control block for the connection */
+ p_lcb = l2cu_find_lcb_by_handle(handle);
+
+ /* If we don't have one, maybe an SCO link. */
+ if (!p_lcb) return (false);
+
+ /* For all channels, tell the upper layer about it */
+ for (p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb; p_ccb = p_ccb->p_next_ccb) {
+ if (p_ccb->p_rcb->api.pL2CA_QoSViolationInd_Cb)
+ l2c_csm_execute(p_ccb, L2CEVT_LP_QOS_VIOLATION_IND, NULL);
+ }
+
+ return (true);
+}
+
+/*******************************************************************************
+ *
* Function l2c_link_timeout
*
* Description This function is called when a link timer expires
@@ -462,9 +516,9 @@ void l2c_link_timeout(tL2C_LCB* p_lcb) {
tL2C_CCB* p_ccb;
tBTM_STATUS rc;
- LOG_DEBUG("L2CAP - l2c_link_timeout() link state:%s is_bonding:%s",
- link_state_text(p_lcb->link_state).c_str(),
- logbool(p_lcb->IsBonding()).c_str());
+ L2CAP_TRACE_EVENT(
+ "L2CAP - l2c_link_timeout() link state %d first CCB %p is_bonding:%d",
+ p_lcb->link_state, p_lcb->ccb_queue.p_first_ccb, p_lcb->is_bonding);
/* If link was connecting or disconnecting, clear all channels and drop the
* LCB */
@@ -490,13 +544,34 @@ void l2c_link_timeout(tL2C_LCB* p_lcb) {
/* If link is connected, check for inactivity timeout */
if (p_lcb->link_state == LST_CONNECTED) {
+ /* Check for ping outstanding */
+ if (p_lcb->p_echo_rsp_cb) {
+ tL2CA_ECHO_RSP_CB* p_cb = p_lcb->p_echo_rsp_cb;
+
+ /* Zero out the callback in case app immediately calls us again */
+ p_lcb->p_echo_rsp_cb = NULL;
+
+ (*p_cb)(L2CAP_PING_RESULT_NO_RESP);
+
+ L2CAP_TRACE_WARNING("L2CAP - ping timeout");
+
+ /* For all channels, send a disconnect indication event through */
+ /* their FSMs. The CCBs should remove themselves from the LCB */
+ for (p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb;) {
+ tL2C_CCB* pn = p_ccb->p_next_ccb;
+
+ l2c_csm_execute(p_ccb, L2CEVT_LP_DISCONNECT_IND, NULL);
+
+ p_ccb = pn;
+ }
+ }
+
/* If no channels in use, drop the link. */
if (!p_lcb->ccb_queue.p_first_ccb) {
uint64_t timeout_ms;
bool start_timeout = true;
- LOG_WARN("TODO: Remove this callback into bcm_sec_disconnect");
- rc = btm_sec_disconnect(p_lcb->Handle(), HCI_ERR_PEER_USER);
+ rc = btm_sec_disconnect(p_lcb->handle, HCI_ERR_PEER_USER);
if (rc == BTM_CMD_STORED) {
/* Security Manager will take care of disconnecting, state will be
@@ -514,8 +589,8 @@ void l2c_link_timeout(tL2C_LCB* p_lcb) {
} else if (rc == BTM_BUSY) {
/* BTM is still executing security process. Let lcb stay as connected */
start_timeout = false;
- } else if (p_lcb->IsBonding()) {
- acl_disconnect_from_handle(p_lcb->Handle(), HCI_ERR_PEER_USER);
+ } else if (p_lcb->is_bonding) {
+ btsnd_hcic_disconnect(p_lcb->handle, HCI_ERR_PEER_USER);
l2cu_process_fixed_disc_cback(p_lcb);
p_lcb->link_state = LST_DISCONNECTING;
timeout_ms = L2CAP_LINK_DISCONNECT_TIMEOUT_MS;
@@ -530,7 +605,7 @@ void l2c_link_timeout(tL2C_LCB* p_lcb) {
}
} else {
/* Check in case we were flow controlled */
- l2c_link_check_send_pkts(p_lcb, 0, NULL);
+ l2c_link_check_send_pkts(p_lcb, NULL, NULL);
}
}
}
@@ -610,7 +685,7 @@ void l2c_link_adjust_allocation(void) {
(l2cb.num_lm_ble_bufs == L2C_DEF_NUM_BLE_BUF_SHARED) ? true : false;
/* If no links active, reset buffer quotas and controller buffers */
- if (l2cb.num_used_lcbs == 0) {
+ if (l2cb.num_links_active == 0) {
l2cb.controller_xmit_window = l2cb.num_lm_acl_bufs;
l2cb.round_robin_quota = l2cb.round_robin_unacked = 0;
return;
@@ -659,7 +734,7 @@ void l2c_link_adjust_allocation(void) {
qq = qq_remainder = 1;
}
- LOG_DEBUG(
+ L2CAP_TRACE_EVENT(
"l2c_link_adjust_allocation num_hipri: %u num_lowpri: %u low_quota: "
"%u round_robin_quota: %u qq: %u",
num_hipri_links, num_lowpri_links, low_quota, l2cb.round_robin_quota, qq);
@@ -686,12 +761,12 @@ void l2c_link_adjust_allocation(void) {
}
}
- LOG_DEBUG(
+ L2CAP_TRACE_EVENT(
"l2c_link_adjust_allocation LCB %d Priority: %d XmitQuota: %d", yy,
p_lcb->acl_priority, p_lcb->link_xmit_quota);
- LOG_DEBUG(" SentNotAcked: %d RRUnacked: %d",
- p_lcb->sent_not_acked, l2cb.round_robin_unacked);
+ L2CAP_TRACE_EVENT(" SentNotAcked: %d RRUnacked: %d",
+ p_lcb->sent_not_acked, l2cb.round_robin_unacked);
/* There is a special case where we have readjusted the link quotas and */
/* this link may have sent anything but some other link sent packets so */
@@ -722,15 +797,19 @@ void l2c_link_adjust_allocation(void) {
*
******************************************************************************/
void l2c_link_adjust_chnl_allocation(void) {
+ uint8_t xx;
+
+ L2CAP_TRACE_DEBUG("%s", __func__);
+
/* assign buffer quota to each channel based on its data rate requirement */
- for (uint8_t xx = 0; xx < MAX_L2CAP_CHANNELS; xx++) {
+ for (xx = 0; xx < MAX_L2CAP_CHANNELS; xx++) {
tL2C_CCB* p_ccb = l2cb.ccb_pool + xx;
if (!p_ccb->in_use) continue;
tL2CAP_CHNL_DATA_RATE data_rate = p_ccb->tx_data_rate + p_ccb->rx_data_rate;
p_ccb->buff_quota = L2CAP_CBB_DEFAULT_DATA_RATE_BUFF_QUOTA * data_rate;
- LOG_DEBUG(
+ L2CAP_TRACE_EVENT(
"CID:0x%04x FCR Mode:%u Priority:%u TxDataRate:%u RxDataRate:%u "
"Quota:%u",
p_ccb->local_cid, p_ccb->peer_cfg.fcr.mode, p_ccb->ccb_priority,
@@ -741,41 +820,63 @@ void l2c_link_adjust_chnl_allocation(void) {
}
}
-void l2c_link_init() {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- // GD L2cap gets this info through GD ACL
- return;
- }
+/*******************************************************************************
+ *
+ * Function l2c_link_processs_num_bufs
+ *
+ * Description This function is called when a "controller buffer size"
+ * event is first received from the controller. It updates
+ * the L2CAP values.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void l2c_link_processs_num_bufs(uint16_t num_lm_acl_bufs) {
+ l2cb.num_lm_acl_bufs = l2cb.controller_xmit_window = num_lm_acl_bufs;
+}
- const controller_t* controller = controller_get_interface();
+/*******************************************************************************
+ *
+ * Function l2c_link_pkts_rcvd
+ *
+ * Description This function is called from the HCI transport when it is
+ * time to send a "Host ready for packets" command. This is
+ * only when host to controller flow control is used. It fills
+ * in the arrays of numbers of packets and handles.
+ *
+ * Returns count of number of entries filled in
+ *
+ ******************************************************************************/
+uint8_t l2c_link_pkts_rcvd(UNUSED_ATTR uint16_t* num_pkts,
+ UNUSED_ATTR uint16_t* handles) {
+ uint8_t num_found = 0;
- l2cb.num_lm_acl_bufs = controller->get_acl_buffer_count_classic();
- l2cb.controller_xmit_window = controller->get_acl_buffer_count_classic();
+ return (num_found);
}
/*******************************************************************************
*
* Function l2c_link_role_changed
*
- * Description This function is called whan a link's central/peripheral
- *role change event is received. It simply updates the link control block.
+ * Description This function is called whan a link's master/slave role
+ * change event is received. It simply updates the link control
+ * block.
*
* Returns void
*
******************************************************************************/
void l2c_link_role_changed(const RawAddress* bd_addr, uint8_t new_role,
uint8_t hci_status) {
+ tL2C_LCB* p_lcb;
+ int xx;
+
/* Make sure not called from HCI Command Status (bd_addr and new_role are
* invalid) */
- if (bd_addr != nullptr) {
+ if (bd_addr) {
/* If here came form hci role change event */
- tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(*bd_addr, BT_TRANSPORT_BR_EDR);
+ p_lcb = l2cu_find_lcb_by_bd_addr(*bd_addr, BT_TRANSPORT_BR_EDR);
if (p_lcb) {
- if (new_role == HCI_ROLE_CENTRAL) {
- p_lcb->SetLinkRoleAsCentral();
- } else {
- p_lcb->SetLinkRoleAsPeripheral();
- }
+ p_lcb->link_role = new_role;
/* Reset high priority link if needed */
if (hci_status == HCI_SUCCESS)
@@ -784,8 +885,7 @@ void l2c_link_role_changed(const RawAddress* bd_addr, uint8_t new_role,
}
/* Check if any LCB was waiting for switch to be completed */
- tL2C_LCB* p_lcb = &l2cb.lcb_pool[0];
- for (uint8_t xx = 0; xx < MAX_L2CAP_LINKS; xx++, p_lcb++) {
+ for (xx = 0, p_lcb = &l2cb.lcb_pool[0]; xx < MAX_L2CAP_LINKS; xx++, p_lcb++) {
if ((p_lcb->in_use) && (p_lcb->link_state == LST_CONNECTING_WAIT_SWITCH)) {
l2cu_create_conn_after_switch(p_lcb);
}
@@ -814,6 +914,7 @@ void l2c_pin_code_request(const RawAddress& bd_addr) {
}
}
+#if (L2CAP_WAKE_PARKED_LINK == TRUE)
/*******************************************************************************
*
* Function l2c_link_check_power_mode
@@ -824,37 +925,39 @@ void l2c_pin_code_request(const RawAddress& bd_addr) {
* false if nothing to send or not in park mode
*
******************************************************************************/
-static bool l2c_link_check_power_mode(tL2C_LCB* p_lcb) {
+bool l2c_link_check_power_mode(tL2C_LCB* p_lcb) {
+ tBTM_PM_MODE mode;
+ tL2C_CCB* p_ccb;
bool need_to_active = false;
/*
* We only switch park to active only if we have unsent packets
*/
if (list_is_empty(p_lcb->link_xmit_data_q)) {
- for (tL2C_CCB* p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb;
+ for (p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb;
p_ccb = p_ccb->p_next_ccb) {
if (!fixed_queue_is_empty(p_ccb->xmit_hold_q)) {
need_to_active = true;
break;
}
}
- } else {
+ } else
need_to_active = true;
- }
/* if we have packets to send */
- if (need_to_active && !p_lcb->is_transport_ble()) {
+ if (need_to_active) {
/* check power mode */
- tBTM_PM_MODE mode;
- if (BTM_ReadPowerMode(p_lcb->remote_bd_addr, &mode)) {
+ if (BTM_ReadPowerMode(p_lcb->remote_bd_addr, &mode) == BTM_SUCCESS) {
if (mode == BTM_PM_STS_PENDING) {
- LOG_DEBUG("LCB(0x%x) is in PM pending state", p_lcb->Handle());
+ L2CAP_TRACE_DEBUG("LCB(0x%x) is in PM pending state", p_lcb->handle);
+
return true;
}
}
}
return false;
}
+#endif /* L2CAP_WAKE_PARKED_LINK == TRUE) */
/*******************************************************************************
*
@@ -867,16 +970,17 @@ static bool l2c_link_check_power_mode(tL2C_LCB* p_lcb) {
* Returns void
*
******************************************************************************/
-void l2c_link_check_send_pkts(tL2C_LCB* p_lcb, uint16_t local_cid,
- BT_HDR* p_buf) {
+void l2c_link_check_send_pkts(tL2C_LCB* p_lcb, tL2C_CCB* p_ccb, BT_HDR* p_buf) {
+ int xx;
bool single_write = false;
/* Save the channel ID for faster counting */
if (p_buf) {
- p_buf->event = local_cid;
- if (local_cid != 0) {
+ if (p_ccb != NULL) {
+ p_buf->event = p_ccb->local_cid;
single_write = true;
- }
+ } else
+ p_buf->event = 0;
p_buf->layer_specific = 0;
list_append(p_lcb->link_xmit_data_q, p_buf);
@@ -890,27 +994,22 @@ void l2c_link_check_send_pkts(tL2C_LCB* p_lcb, uint16_t local_cid,
}
/* If this is called from uncongested callback context break recursive
- *calling.
- ** This LCB will be served when receiving number of completed packet event.
- */
- if (l2cb.is_cong_cback_context) {
- LOG_INFO("skipping, is_cong_cback_context=true");
- return;
- }
+ *calling.
+ ** This LCB will be served when receiving number of completed packet event.
+ */
+ if (l2cb.is_cong_cback_context) return;
/* If we are in a scenario where there are not enough buffers for each link to
** have at least 1, then do a round-robin for all the LCBs
*/
if ((p_lcb == NULL) || (p_lcb->link_xmit_quota == 0)) {
- LOG_DEBUG("Round robin");
- if (p_lcb == NULL) {
+ if (p_lcb == NULL)
p_lcb = l2cb.lcb_pool;
- } else if (!single_write) {
+ else if (!single_write)
p_lcb++;
- }
/* Loop through, starting at the next */
- for (int xx = 0; xx < MAX_L2CAP_LINKS; xx++, p_lcb++) {
+ for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p_lcb++) {
/* Check for wraparound */
if (p_lcb == &l2cb.lcb_pool[MAX_L2CAP_LINKS]) p_lcb = &l2cb.lcb_pool[0];
@@ -920,36 +1019,29 @@ void l2c_link_check_send_pkts(tL2C_LCB* p_lcb, uint16_t local_cid,
(p_lcb->transport == BT_TRANSPORT_BR_EDR)) ||
(p_lcb->transport == BT_TRANSPORT_LE &&
(l2cb.ble_round_robin_unacked >= l2cb.ble_round_robin_quota ||
- l2cb.controller_le_xmit_window == 0))) {
- LOG_DEBUG("Skipping lcb %d due to controller window full", xx);
+ l2cb.controller_le_xmit_window == 0)))
continue;
- }
if ((!p_lcb->in_use) || (p_lcb->partial_segment_being_sent) ||
(p_lcb->link_state != LST_CONNECTED) ||
- (p_lcb->link_xmit_quota != 0) || (l2c_link_check_power_mode(p_lcb))) {
- LOG_DEBUG("Skipping lcb %d due to quota", xx);
+ (p_lcb->link_xmit_quota != 0) || (L2C_LINK_CHECK_POWER_MODE(p_lcb)))
continue;
- }
/* See if we can send anything from the Link Queue */
if (!list_is_empty(p_lcb->link_xmit_data_q)) {
- LOG_DEBUG("Sending to lower layer");
p_buf = (BT_HDR*)list_front(p_lcb->link_xmit_data_q);
list_remove(p_lcb->link_xmit_data_q, p_buf);
- l2c_link_send_to_lower(p_lcb, p_buf);
+ l2c_link_send_to_lower(p_lcb, p_buf, NULL);
} else if (single_write) {
/* If only doing one write, break out */
- LOG_DEBUG("single_write is true, skipping");
break;
}
/* If nothing on the link queue, check the channel queue */
else {
- LOG_DEBUG("Check next buffer");
- p_buf = l2cu_get_next_buffer_to_send(p_lcb);
+ tL2C_TX_COMPLETE_CB_INFO cbi;
+ p_buf = l2cu_get_next_buffer_to_send(p_lcb, &cbi);
if (p_buf != NULL) {
- LOG_DEBUG("Sending next buffer");
- l2c_link_send_to_lower(p_lcb, p_buf);
+ l2c_link_send_to_lower(p_lcb, p_buf, &cbi);
}
}
}
@@ -969,16 +1061,8 @@ void l2c_link_check_send_pkts(tL2C_LCB* p_lcb, uint16_t local_cid,
/* If a partial segment is being sent, can't send anything else */
if ((p_lcb->partial_segment_being_sent) ||
(p_lcb->link_state != LST_CONNECTED) ||
- (l2c_link_check_power_mode(p_lcb))) {
- LOG_INFO("A partial segment is being sent, cannot send anything else");
+ (L2C_LINK_CHECK_POWER_MODE(p_lcb)))
return;
- }
- LOG_DEBUG(
- "Direct send, transport=%d, xmit_window=%d, le_xmit_window=%d, "
- "sent_not_acked=%d, link_xmit_quota=%d",
- p_lcb->transport, l2cb.controller_xmit_window,
- l2cb.controller_le_xmit_window, p_lcb->sent_not_acked,
- p_lcb->link_xmit_quota);
/* See if we can send anything from the link queue */
while (((l2cb.controller_xmit_window != 0 &&
@@ -986,31 +1070,25 @@ void l2c_link_check_send_pkts(tL2C_LCB* p_lcb, uint16_t local_cid,
(l2cb.controller_le_xmit_window != 0 &&
(p_lcb->transport == BT_TRANSPORT_LE))) &&
(p_lcb->sent_not_acked < p_lcb->link_xmit_quota)) {
- if (list_is_empty(p_lcb->link_xmit_data_q)) {
- LOG_DEBUG("No transmit data, skipping");
- break;
- }
- LOG_DEBUG("Sending to lower layer");
+ if (list_is_empty(p_lcb->link_xmit_data_q)) break;
+
p_buf = (BT_HDR*)list_front(p_lcb->link_xmit_data_q);
list_remove(p_lcb->link_xmit_data_q, p_buf);
- l2c_link_send_to_lower(p_lcb, p_buf);
+ if (!l2c_link_send_to_lower(p_lcb, p_buf, NULL)) break;
}
if (!single_write) {
/* See if we can send anything for any channel */
- LOG_DEBUG("Trying to send other data when single_write is false");
while (((l2cb.controller_xmit_window != 0 &&
(p_lcb->transport == BT_TRANSPORT_BR_EDR)) ||
(l2cb.controller_le_xmit_window != 0 &&
(p_lcb->transport == BT_TRANSPORT_LE))) &&
(p_lcb->sent_not_acked < p_lcb->link_xmit_quota)) {
- p_buf = l2cu_get_next_buffer_to_send(p_lcb);
- if (p_buf == NULL) {
- LOG_DEBUG("No next buffer, skipping");
- break;
- }
- LOG_DEBUG("Sending to lower layer");
- l2c_link_send_to_lower(p_lcb, p_buf);
+ tL2C_TX_COMPLETE_CB_INFO cbi;
+ p_buf = l2cu_get_next_buffer_to_send(p_lcb, &cbi);
+ if (p_buf == NULL) break;
+
+ if (!l2c_link_send_to_lower(p_lcb, p_buf, &cbi)) break;
}
}
@@ -1026,44 +1104,53 @@ void l2c_link_check_send_pkts(tL2C_LCB* p_lcb, uint16_t local_cid,
}
}
-void l2c_OnHciModeChangeSendPendingPackets(RawAddress remote) {
- tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(remote, BT_TRANSPORT_BR_EDR);
- if (p_lcb != NULL) {
- /* There might be any pending packets due to SNIFF or PENDING state */
- /* Trigger L2C to start transmission of the pending packets. */
- BTM_TRACE_DEBUG(
- "btm mode change to active; check l2c_link for outgoing packets");
- l2c_link_check_send_pkts(p_lcb, 0, NULL);
- }
-}
-
/*******************************************************************************
*
* Function l2c_link_send_to_lower
*
* Description This function queues the buffer for HCI transmission
*
+ * Returns true for success, false for fail
+ *
******************************************************************************/
-static void l2c_link_send_to_lower_br_edr(tL2C_LCB* p_lcb, BT_HDR* p_buf) {
- const uint16_t acl_packet_size_classic =
- controller_get_interface()->get_acl_packet_size_classic();
- const uint16_t link_xmit_quota = p_lcb->link_xmit_quota;
- const bool is_bdr_and_fits_in_buffer =
- bluetooth::shim::is_gd_acl_enabled()
- ? true
- : (p_buf->len <= acl_packet_size_classic);
-
- if (is_bdr_and_fits_in_buffer) {
- if (link_xmit_quota == 0) {
- l2cb.round_robin_unacked++;
+static bool l2c_link_send_to_lower(tL2C_LCB* p_lcb, BT_HDR* p_buf,
+ tL2C_TX_COMPLETE_CB_INFO* p_cbi) {
+ uint16_t num_segs;
+ uint16_t xmit_window, acl_data_size;
+ const controller_t* controller = controller_get_interface();
+
+ if ((p_buf->len <= controller->get_acl_packet_size_classic() &&
+ (p_lcb->transport == BT_TRANSPORT_BR_EDR)) ||
+ ((p_lcb->transport == BT_TRANSPORT_LE) &&
+ (p_buf->len <= controller->get_acl_packet_size_ble()))) {
+ if (p_lcb->link_xmit_quota == 0) {
+ if (p_lcb->transport == BT_TRANSPORT_LE)
+ l2cb.ble_round_robin_unacked++;
+ else
+ l2cb.round_robin_unacked++;
}
p_lcb->sent_not_acked++;
p_buf->layer_specific = 0;
- l2cb.controller_xmit_window--;
+
+ if (p_lcb->transport == BT_TRANSPORT_LE) {
+ l2cb.controller_le_xmit_window--;
+ bte_main_hci_send(
+ p_buf, (uint16_t)(BT_EVT_TO_LM_HCI_ACL | LOCAL_BLE_CONTROLLER_ID));
+ } else {
+ l2cb.controller_xmit_window--;
+ bte_main_hci_send(p_buf, BT_EVT_TO_LM_HCI_ACL);
+ }
} else {
- uint16_t num_segs =
- (p_buf->len - HCI_DATA_PREAMBLE_SIZE + acl_packet_size_classic - 1) /
- acl_packet_size_classic;
+ if (p_lcb->transport == BT_TRANSPORT_LE) {
+ acl_data_size = controller->get_acl_data_size_ble();
+ xmit_window = l2cb.controller_le_xmit_window;
+
+ } else {
+ acl_data_size = controller->get_acl_data_size_classic();
+ xmit_window = l2cb.controller_xmit_window;
+ }
+ num_segs = (p_buf->len - HCI_DATA_PREAMBLE_SIZE + acl_data_size - 1) /
+ acl_data_size;
/* If doing round-robin, then only 1 segment each time */
if (p_lcb->link_xmit_quota == 0) {
@@ -1071,8 +1158,8 @@ static void l2c_link_send_to_lower_br_edr(tL2C_LCB* p_lcb, BT_HDR* p_buf) {
p_lcb->partial_segment_being_sent = true;
} else {
/* Multi-segment packet. Make sure it can fit */
- if (num_segs > l2cb.controller_xmit_window) {
- num_segs = l2cb.controller_xmit_window;
+ if (num_segs > xmit_window) {
+ num_segs = xmit_window;
p_lcb->partial_segment_being_sent = true;
}
@@ -1082,71 +1169,44 @@ static void l2c_link_send_to_lower_br_edr(tL2C_LCB* p_lcb, BT_HDR* p_buf) {
}
}
- p_lcb->sent_not_acked += num_segs;
p_buf->layer_specific = num_segs;
- l2cb.controller_xmit_window -= num_segs;
- if (p_lcb->link_xmit_quota == 0) l2cb.round_robin_unacked += num_segs;
- }
- acl_send_data_packet_br_edr(p_lcb->remote_bd_addr, p_buf);
- LOG_DEBUG("TotalWin=%d,Hndl=0x%x,Quota=%d,Unack=%d,RRQuota=%d,RRUnack=%d",
- l2cb.controller_xmit_window, p_lcb->Handle(),
- p_lcb->link_xmit_quota, p_lcb->sent_not_acked,
- l2cb.round_robin_quota, l2cb.round_robin_unacked);
-}
-
-static void l2c_link_send_to_lower_ble(tL2C_LCB* p_lcb, BT_HDR* p_buf) {
- const uint16_t acl_packet_size_ble =
- controller_get_interface()->get_acl_packet_size_ble();
- const uint16_t link_xmit_quota = p_lcb->link_xmit_quota;
- const bool is_ble_and_fits_in_buffer = (p_buf->len <= acl_packet_size_ble);
-
- if (is_ble_and_fits_in_buffer) {
- if (link_xmit_quota == 0) {
- l2cb.ble_round_robin_unacked++;
- }
- p_lcb->sent_not_acked++;
- p_buf->layer_specific = 0;
- l2cb.controller_le_xmit_window--;
- } else {
- uint16_t num_segs =
- (p_buf->len - HCI_DATA_PREAMBLE_SIZE + acl_packet_size_ble - 1) /
- acl_packet_size_ble;
-
- /* If doing round-robin, then only 1 segment each time */
- if (p_lcb->link_xmit_quota == 0) {
- num_segs = 1;
- p_lcb->partial_segment_being_sent = true;
+ if (p_lcb->transport == BT_TRANSPORT_LE) {
+ l2cb.controller_le_xmit_window -= num_segs;
+ if (p_lcb->link_xmit_quota == 0) l2cb.ble_round_robin_unacked += num_segs;
} else {
- /* Multi-segment packet. Make sure it can fit */
- if (num_segs > l2cb.controller_le_xmit_window) {
- num_segs = l2cb.controller_le_xmit_window;
- p_lcb->partial_segment_being_sent = true;
- }
+ l2cb.controller_xmit_window -= num_segs;
- if (num_segs > (p_lcb->link_xmit_quota - p_lcb->sent_not_acked)) {
- num_segs = (p_lcb->link_xmit_quota - p_lcb->sent_not_acked);
- p_lcb->partial_segment_being_sent = true;
- }
+ if (p_lcb->link_xmit_quota == 0) l2cb.round_robin_unacked += num_segs;
}
p_lcb->sent_not_acked += num_segs;
- p_buf->layer_specific = num_segs;
- l2cb.controller_le_xmit_window -= num_segs;
- if (p_lcb->link_xmit_quota == 0) l2cb.ble_round_robin_unacked += num_segs;
+ if (p_lcb->transport == BT_TRANSPORT_LE) {
+ bte_main_hci_send(
+ p_buf, (uint16_t)(BT_EVT_TO_LM_HCI_ACL | LOCAL_BLE_CONTROLLER_ID));
+ } else {
+ bte_main_hci_send(p_buf, BT_EVT_TO_LM_HCI_ACL);
+ }
}
- acl_send_data_packet_ble(p_lcb->remote_bd_addr, p_buf);
- LOG_DEBUG("TotalWin=%d,Hndl=0x%x,Quota=%d,Unack=%d,RRQuota=%d,RRUnack=%d",
- l2cb.controller_le_xmit_window, p_lcb->Handle(),
- p_lcb->link_xmit_quota, p_lcb->sent_not_acked,
- l2cb.ble_round_robin_quota, l2cb.ble_round_robin_unacked);
-}
-static void l2c_link_send_to_lower(tL2C_LCB* p_lcb, BT_HDR* p_buf) {
- if (p_lcb->transport == BT_TRANSPORT_BR_EDR) {
- l2c_link_send_to_lower_br_edr(p_lcb, p_buf);
+#if (L2CAP_HCI_FLOW_CONTROL_DEBUG == TRUE)
+ if (p_lcb->transport == BT_TRANSPORT_LE) {
+ L2CAP_TRACE_DEBUG(
+ "TotalWin=%d,Hndl=0x%x,Quota=%d,Unack=%d,RRQuota=%d,RRUnack=%d",
+ l2cb.controller_le_xmit_window, p_lcb->handle, p_lcb->link_xmit_quota,
+ p_lcb->sent_not_acked, l2cb.ble_round_robin_quota,
+ l2cb.ble_round_robin_unacked);
} else {
- l2c_link_send_to_lower_ble(p_lcb, p_buf);
+ L2CAP_TRACE_DEBUG(
+ "TotalWin=%d,Hndl=0x%x,Quota=%d,Unack=%d,RRQuota=%d,RRUnack=%d",
+ l2cb.controller_xmit_window, p_lcb->handle, p_lcb->link_xmit_quota,
+ p_lcb->sent_not_acked, l2cb.round_robin_quota,
+ l2cb.round_robin_unacked);
}
+#endif
+
+ if (p_cbi) l2cu_tx_complete(p_cbi);
+
+ return true;
}
/*******************************************************************************
@@ -1161,9 +1221,6 @@ static void l2c_link_send_to_lower(tL2C_LCB* p_lcb, BT_HDR* p_buf) {
*
******************************************************************************/
void l2c_link_process_num_completed_pkts(uint8_t* p, uint8_t evt_len) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return;
- }
uint8_t num_handles, xx;
uint16_t handle;
uint16_t num_sent;
@@ -1182,12 +1239,17 @@ void l2c_link_process_num_completed_pkts(uint8_t* p, uint8_t evt_len) {
for (xx = 0; xx < num_handles; xx++) {
STREAM_TO_UINT16(handle, p);
- /* Extract the handle */
- handle = HCID_GET_HANDLE(handle);
STREAM_TO_UINT16(num_sent, p);
p_lcb = l2cu_find_lcb_by_handle(handle);
+ /* Callback for number of completed packet event */
+ /* Originally designed for [3DSG] */
+ if ((p_lcb != NULL) && (p_lcb->p_nocp_cb)) {
+ L2CAP_TRACE_DEBUG("L2CAP - calling NoCP callback");
+ (*p_lcb->p_nocp_cb)(p_lcb->remote_bd_addr);
+ }
+
if (p_lcb) {
if (p_lcb && (p_lcb->transport == BT_TRANSPORT_LE))
l2cb.controller_le_xmit_window += num_sent;
@@ -1218,85 +1280,43 @@ void l2c_link_process_num_completed_pkts(uint8_t* p, uint8_t evt_len) {
else
p_lcb->sent_not_acked = 0;
- l2c_link_check_send_pkts(p_lcb, 0, NULL);
+ l2c_link_check_send_pkts(p_lcb, NULL, NULL);
/* If we were doing round-robin for low priority links, check 'em */
if ((p_lcb->acl_priority == L2CAP_PRIORITY_HIGH) &&
(l2cb.check_round_robin) &&
(l2cb.round_robin_unacked < l2cb.round_robin_quota)) {
- l2c_link_check_send_pkts(NULL, 0, NULL);
+ l2c_link_check_send_pkts(NULL, NULL, NULL);
}
if ((p_lcb->transport == BT_TRANSPORT_LE) &&
(p_lcb->acl_priority == L2CAP_PRIORITY_HIGH) &&
((l2cb.ble_check_round_robin) &&
(l2cb.ble_round_robin_unacked < l2cb.ble_round_robin_quota))) {
- l2c_link_check_send_pkts(NULL, 0, NULL);
+ l2c_link_check_send_pkts(NULL, NULL, NULL);
}
}
+#if (L2CAP_HCI_FLOW_CONTROL_DEBUG == TRUE)
if (p_lcb) {
if (p_lcb->transport == BT_TRANSPORT_LE) {
- LOG_DEBUG("TotalWin=%d,LinkUnack(0x%x)=%d,RRCheck=%d,RRUnack=%d",
- l2cb.controller_le_xmit_window, p_lcb->Handle(),
- p_lcb->sent_not_acked, l2cb.ble_check_round_robin,
- l2cb.ble_round_robin_unacked);
+ L2CAP_TRACE_DEBUG(
+ "TotalWin=%d,LinkUnack(0x%x)=%d,RRCheck=%d,RRUnack=%d",
+ l2cb.controller_le_xmit_window, p_lcb->handle,
+ p_lcb->sent_not_acked, l2cb.ble_check_round_robin,
+ l2cb.ble_round_robin_unacked);
} else {
- LOG_DEBUG("TotalWin=%d,LinkUnack(0x%x)=%d,RRCheck=%d,RRUnack=%d",
- l2cb.controller_xmit_window, p_lcb->Handle(),
- p_lcb->sent_not_acked, l2cb.check_round_robin,
- l2cb.round_robin_unacked);
+ L2CAP_TRACE_DEBUG(
+ "TotalWin=%d,LinkUnack(0x%x)=%d,RRCheck=%d,RRUnack=%d",
+ l2cb.controller_xmit_window, p_lcb->handle, p_lcb->sent_not_acked,
+ l2cb.check_round_robin, l2cb.round_robin_unacked);
}
} else {
- LOG_DEBUG("TotalWin=%d LE_Win: %d, Handle=0x%x, RRCheck=%d, RRUnack=%d",
- l2cb.controller_xmit_window, l2cb.controller_le_xmit_window,
- handle, l2cb.ble_check_round_robin,
- l2cb.ble_round_robin_unacked);
- }
- }
-}
-
-void l2c_packets_completed(uint16_t handle, uint16_t num_sent) {
- tL2C_LCB* p_lcb = l2cu_find_lcb_by_handle(handle);
- if (p_lcb == nullptr) {
- LOG_WARN("Received l2c packets completed for unknown ACL");
- return;
- }
- p_lcb->update_outstanding_packets(num_sent);
-
- switch (p_lcb->transport) {
- case BT_TRANSPORT_BR_EDR:
- l2cb.controller_xmit_window += num_sent;
- if (p_lcb->is_round_robin_scheduling())
- l2cb.update_outstanding_classic_packets(num_sent);
- break;
- case BT_TRANSPORT_LE:
- l2cb.controller_le_xmit_window += num_sent;
- if (p_lcb->is_round_robin_scheduling())
- l2cb.update_outstanding_le_packets(num_sent);
- break;
- default:
- LOG_ERROR("Unknown transport received:%u", p_lcb->transport);
- return;
- }
-
- l2c_link_check_send_pkts(p_lcb, 0, NULL);
-
- if (p_lcb->is_high_priority()) {
- switch (p_lcb->transport) {
- case BT_TRANSPORT_LE:
- if (l2cb.ble_check_round_robin &&
- l2cb.is_ble_round_robin_quota_available())
- l2c_link_check_send_pkts(NULL, 0, NULL);
- break;
- case BT_TRANSPORT_BR_EDR:
- if (l2cb.check_round_robin &&
- l2cb.is_classic_round_robin_quota_available()) {
- l2c_link_check_send_pkts(NULL, 0, NULL);
- }
- break;
- default:
- break;
+ L2CAP_TRACE_DEBUG(
+ "TotalWin=%d LE_Win: %d, Handle=0x%x, RRCheck=%d, RRUnack=%d",
+ l2cb.controller_xmit_window, l2cb.controller_le_xmit_window, handle,
+ l2cb.ble_check_round_robin, l2cb.ble_round_robin_unacked);
}
+#endif
}
}
@@ -1312,261 +1332,30 @@ void l2c_packets_completed(uint16_t handle, uint16_t num_sent) {
******************************************************************************/
void l2c_link_segments_xmitted(BT_HDR* p_msg) {
uint8_t* p = (uint8_t*)(p_msg + 1) + p_msg->offset;
+ uint16_t handle;
+ tL2C_LCB* p_lcb;
/* Extract the handle */
- uint16_t handle{HCI_INVALID_HANDLE};
STREAM_TO_UINT16(handle, p);
handle = HCID_GET_HANDLE(handle);
/* Find the LCB based on the handle */
- tL2C_LCB* p_lcb = l2cu_find_lcb_by_handle(handle);
- if (p_lcb == nullptr) {
- LOG_WARN("Received segment complete for unknown connection handle:%d",
- handle);
+ p_lcb = l2cu_find_lcb_by_handle(handle);
+ if (p_lcb == NULL) {
+ L2CAP_TRACE_WARNING("L2CAP - rcvd segment complete, unknown handle: %d",
+ handle);
osi_free(p_msg);
return;
}
- if (p_lcb->link_state != LST_CONNECTED) {
- LOG_INFO("Received segment complete for unconnected connection handle:%d:",
- handle);
- osi_free(p_msg);
- return;
- }
-
- /* Enqueue the buffer to the head of the transmit queue, and see */
- /* if we can transmit anything more. */
- list_prepend(p_lcb->link_xmit_data_q, p_msg);
-
- p_lcb->partial_segment_being_sent = false;
-
- l2c_link_check_send_pkts(p_lcb, 0, NULL);
-}
-
-tBTM_STATUS l2cu_ConnectAclForSecurity(const RawAddress& bd_addr) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- bluetooth::shim::L2CA_ConnectForSecurity(bd_addr);
- return BTM_SUCCESS;
- }
-
- tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(bd_addr, BT_TRANSPORT_BR_EDR);
- if (p_lcb && (p_lcb->link_state == LST_CONNECTED ||
- p_lcb->link_state == LST_CONNECTING)) {
- LOG_WARN("Connection already exists");
- return BTM_CMD_STARTED;
- }
-
- /* Make sure an L2cap link control block is available */
- if (!p_lcb &&
- (p_lcb = l2cu_allocate_lcb(bd_addr, true, BT_TRANSPORT_BR_EDR)) == NULL) {
- LOG_WARN("failed allocate LCB for %s", bd_addr.ToString().c_str());
- return BTM_NO_RESOURCES;
- }
-
- l2cu_create_conn_br_edr(p_lcb);
- btm_acl_set_paging(true);
- return BTM_SUCCESS;
-}
-
-void l2cble_update_sec_act(const RawAddress& bd_addr, uint16_t sec_act) {
- tL2C_LCB* lcb = l2cu_find_lcb_by_bd_addr(bd_addr, BT_TRANSPORT_LE);
- lcb->sec_act = sec_act;
-}
-
-/******************************************************************************
- *
- * Function l2cu_get_next_channel_in_rr
- *
- * Description get the next channel to send on a link. It also adjusts the
- * CCB queue to do a basic priority and round-robin scheduling.
- *
- * Returns pointer to CCB or NULL
- *
- ******************************************************************************/
-tL2C_CCB* l2cu_get_next_channel_in_rr(tL2C_LCB* p_lcb) {
- tL2C_CCB* p_serve_ccb = NULL;
- tL2C_CCB* p_ccb;
-
- int i, j;
-
- /* scan all of priority until finding a channel to serve */
- for (i = 0; (i < L2CAP_NUM_CHNL_PRIORITY) && (!p_serve_ccb); i++) {
- /* scan all channel within serving priority group until finding a channel to
- * serve */
- for (j = 0; (j < p_lcb->rr_serv[p_lcb->rr_pri].num_ccb) && (!p_serve_ccb);
- j++) {
- /* scaning from next serving channel */
- p_ccb = p_lcb->rr_serv[p_lcb->rr_pri].p_serve_ccb;
-
- if (!p_ccb) {
- LOG_ERROR("p_serve_ccb is NULL, rr_pri=%d", p_lcb->rr_pri);
- return NULL;
- }
-
- LOG_DEBUG("RR scan pri=%d, lcid=0x%04x, q_cout=%zu", p_ccb->ccb_priority,
- p_ccb->local_cid, fixed_queue_length(p_ccb->xmit_hold_q));
-
- /* store the next serving channel */
- /* this channel is the last channel of its priority group */
- if ((p_ccb->p_next_ccb == NULL) ||
- (p_ccb->p_next_ccb->ccb_priority != p_ccb->ccb_priority)) {
- /* next serving channel is set to the first channel in the group */
- p_lcb->rr_serv[p_lcb->rr_pri].p_serve_ccb =
- p_lcb->rr_serv[p_lcb->rr_pri].p_first_ccb;
- } else {
- /* next serving channel is set to the next channel in the group */
- p_lcb->rr_serv[p_lcb->rr_pri].p_serve_ccb = p_ccb->p_next_ccb;
- }
-
- if (p_ccb->chnl_state != CST_OPEN) continue;
-
- if (p_ccb->p_lcb->transport == BT_TRANSPORT_LE) {
- LOG_DEBUG("Connection oriented channel");
- if (fixed_queue_is_empty(p_ccb->xmit_hold_q)) continue;
-
- } else {
- /* eL2CAP option in use */
- if (p_ccb->peer_cfg.fcr.mode != L2CAP_FCR_BASIC_MODE) {
- if (p_ccb->fcrb.wait_ack || p_ccb->fcrb.remote_busy) continue;
-
- if (fixed_queue_is_empty(p_ccb->fcrb.retrans_q)) {
- if (fixed_queue_is_empty(p_ccb->xmit_hold_q)) continue;
-
- /* If in eRTM mode, check for window closure */
- if ((p_ccb->peer_cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) &&
- (l2c_fcr_is_flow_controlled(p_ccb)))
- continue;
- }
- } else {
- if (fixed_queue_is_empty(p_ccb->xmit_hold_q)) continue;
- }
- }
-
- /* found a channel to serve */
- p_serve_ccb = p_ccb;
- /* decrease quota of its priority group */
- p_lcb->rr_serv[p_lcb->rr_pri].quota--;
- }
-
- /* if there is no more quota of the priority group or no channel to have
- * data to send */
- if ((p_lcb->rr_serv[p_lcb->rr_pri].quota == 0) || (!p_serve_ccb)) {
- /* serve next priority group */
- p_lcb->rr_pri = (p_lcb->rr_pri + 1) % L2CAP_NUM_CHNL_PRIORITY;
- /* initialize its quota */
- p_lcb->rr_serv[p_lcb->rr_pri].quota =
- L2CAP_GET_PRIORITY_QUOTA(p_lcb->rr_pri);
- }
- }
-
- if (p_serve_ccb) {
- LOG_DEBUG("RR service pri=%d, quota=%d, lcid=0x%04x",
- p_serve_ccb->ccb_priority,
- p_lcb->rr_serv[p_serve_ccb->ccb_priority].quota,
- p_serve_ccb->local_cid);
- }
-
- return p_serve_ccb;
-}
-
-/******************************************************************************
- *
- * Function l2cu_get_next_buffer_to_send
- *
- * Description get the next buffer to send on a link. It also adjusts the
- * CCB queue to do a basic priority and round-robin scheduling.
- *
- * Returns pointer to buffer or NULL
- *
- ******************************************************************************/
-BT_HDR* l2cu_get_next_buffer_to_send(tL2C_LCB* p_lcb) {
- tL2C_CCB* p_ccb;
- BT_HDR* p_buf;
-
- /* Highest priority are fixed channels */
- int xx;
-
- for (xx = 0; xx < L2CAP_NUM_FIXED_CHNLS; xx++) {
- p_ccb = p_lcb->p_fixed_ccbs[xx];
- if (p_ccb == NULL) continue;
-
- /* eL2CAP option in use */
- if (p_ccb->peer_cfg.fcr.mode != L2CAP_FCR_BASIC_MODE) {
- if (p_ccb->fcrb.wait_ack || p_ccb->fcrb.remote_busy) continue;
-
- /* No more checks needed if sending from the reatransmit queue */
- if (fixed_queue_is_empty(p_ccb->fcrb.retrans_q)) {
- if (fixed_queue_is_empty(p_ccb->xmit_hold_q)) continue;
-
- /* If in eRTM mode, check for window closure */
- if ((p_ccb->peer_cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) &&
- (l2c_fcr_is_flow_controlled(p_ccb)))
- continue;
- }
-
- p_buf = l2c_fcr_get_next_xmit_sdu_seg(p_ccb, 0);
- if (p_buf != NULL) {
- l2cu_check_channel_congestion(p_ccb);
- l2cu_set_acl_hci_header(p_buf, p_ccb);
- return (p_buf);
- }
- } else {
- if (!fixed_queue_is_empty(p_ccb->xmit_hold_q)) {
- p_buf = (BT_HDR*)fixed_queue_try_dequeue(p_ccb->xmit_hold_q);
- if (NULL == p_buf) {
- LOG_ERROR("No data to be sent");
- return (NULL);
- }
-
- l2cu_check_channel_congestion(p_ccb);
- l2cu_set_acl_hci_header(p_buf, p_ccb);
- return (p_buf);
- }
- }
- }
-
- /* get next serving channel in round-robin */
- p_ccb = l2cu_get_next_channel_in_rr(p_lcb);
-
- /* Return if no buffer */
- if (p_ccb == NULL) return (NULL);
-
- if (p_ccb->p_lcb->transport == BT_TRANSPORT_LE) {
- /* Check credits */
- if (p_ccb->peer_conn_cfg.credits == 0) {
- LOG_DEBUG("No credits to send packets");
- return NULL;
- }
-
- bool last_piece_of_sdu = false;
- p_buf = l2c_lcc_get_next_xmit_sdu_seg(p_ccb, &last_piece_of_sdu);
- p_ccb->peer_conn_cfg.credits--;
-
- if (last_piece_of_sdu) {
- // TODO: send callback up the stack. Investigate setting p_cbi->cb to
- // notify after controller ack send.
- }
-
- } else {
- if (p_ccb->peer_cfg.fcr.mode != L2CAP_FCR_BASIC_MODE) {
- p_buf = l2c_fcr_get_next_xmit_sdu_seg(p_ccb, 0);
- if (p_buf == NULL) return (NULL);
- } else {
- p_buf = (BT_HDR*)fixed_queue_try_dequeue(p_ccb->xmit_hold_q);
- if (NULL == p_buf) {
- LOG_ERROR("#2: No data to be sent");
- return (NULL);
- }
- }
- }
-
- if (p_ccb->p_rcb && p_ccb->p_rcb->api.pL2CA_TxComplete_Cb &&
- (p_ccb->peer_cfg.fcr.mode != L2CAP_FCR_ERTM_MODE))
- (*p_ccb->p_rcb->api.pL2CA_TxComplete_Cb)(p_ccb->local_cid, 1);
-
- l2cu_check_channel_congestion(p_ccb);
+ if (p_lcb->link_state == LST_CONNECTED) {
+ /* Enqueue the buffer to the head of the transmit queue, and see */
+ /* if we can transmit anything more. */
+ list_prepend(p_lcb->link_xmit_data_q, p_msg);
- l2cu_set_acl_hci_header(p_buf, p_ccb);
+ p_lcb->partial_segment_being_sent = false;
- return (p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, NULL);
+ } else
+ osi_free(p_msg);
}
diff --git a/stack/l2cap/l2c_main.cc b/stack/l2cap/l2c_main.cc
index 003c8fbea..2e533bc17 100644
--- a/stack/l2cap/l2c_main.cc
+++ b/stack/l2cap/l2c_main.cc
@@ -24,16 +24,19 @@
#define LOG_TAG "bt_l2c_main"
+#include <stdio.h>
+#include <stdlib.h>
#include <string.h>
#include "bt_common.h"
#include "bt_target.h"
+#include "btu.h"
+#include "device/include/controller.h"
#include "hci/include/btsnoop.h"
#include "hcimsgs.h"
#include "l2c_api.h"
#include "l2c_int.h"
#include "l2cdefs.h"
-#include "main/shim/shim.h"
#include "osi/include/log.h"
#include "osi/include/osi.h"
@@ -103,8 +106,8 @@ void l2c_rcv_acl_data(BT_HDR* p_msg) {
if ((p_msg->layer_specific != 0) || (rcv_cid != L2CAP_SIGNALLING_CID) ||
(cmd_code != L2CAP_CMD_INFO_REQ && cmd_code != L2CAP_CMD_CONN_REQ)) {
- bool qcom_debug_log = (handle == 3804 && ((rcv_cid & 0xff) == 0xff) &&
- p_msg->layer_specific == 0);
+ bool qcom_debug_log =
+ (handle == 3804 && cmd_code == 10 && p_msg->layer_specific == 0);
if (!qcom_debug_log) {
L2CAP_TRACE_ERROR(
@@ -185,6 +188,7 @@ void l2c_rcv_acl_data(BT_HDR* p_msg) {
return;
}
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
if ((rcv_cid >= L2CAP_FIRST_FIXED_CHNL) &&
(rcv_cid <= L2CAP_LAST_FIXED_CHNL) &&
(l2cb.fixed_reg[rcv_cid - L2CAP_FIRST_FIXED_CHNL].pL2CA_FixedData_Cb !=
@@ -192,14 +196,16 @@ void l2c_rcv_acl_data(BT_HDR* p_msg) {
/* only process fixed channel data when link is open or wait for data
* indication */
if (!p_lcb || p_lcb->link_state == LST_DISCONNECTING ||
- !l2cu_initialize_fixed_ccb(p_lcb, rcv_cid)) {
+ !l2cu_initialize_fixed_ccb(
+ p_lcb, rcv_cid,
+ &l2cb.fixed_reg[rcv_cid - L2CAP_FIRST_FIXED_CHNL]
+ .fixed_chnl_opts)) {
osi_free(p_msg);
return;
}
/* If no CCB for this channel, allocate one */
p_ccb = p_lcb->p_fixed_ccbs[rcv_cid - L2CAP_FIRST_FIXED_CHNL];
- p_ccb->metrics.rx(p_msg->len);
if (p_ccb->peer_cfg.fcr.mode != L2CAP_FCR_BASIC_MODE)
l2c_fcr_proc_pdu(p_ccb, p_msg);
@@ -208,6 +214,7 @@ void l2c_rcv_acl_data(BT_HDR* p_msg) {
rcv_cid, p_lcb->remote_bd_addr, p_msg);
return;
}
+#endif
if (!p_ccb) {
osi_free(p_msg);
@@ -257,10 +264,7 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
/* if l2cap command received in CID 1 on top of an LE link, ignore this
* command */
- if (p_lcb->transport == BT_TRANSPORT_LE) {
- LOG_INFO("Dropping data on CID 1 for LE link");
- return;
- }
+ if (p_lcb->transport == BT_TRANSPORT_LE) return;
/* Reject the packet if it exceeds the default Signalling Channel MTU */
bool pkt_size_rej = false;
@@ -270,8 +274,7 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
* will be ignored. Here we simply mark the bad packet and decide which cmd
* ID to reject later */
pkt_size_rej = true;
- LOG_WARN("Signaling pkt_len=%d exceeds MTU size %d", pkt_len,
- L2CAP_DEFAULT_MTU);
+ L2CAP_TRACE_ERROR("L2CAP SIG MTU pkt_len=%d Exceeded 672", pkt_len);
}
uint8_t* p_next_cmd = p;
@@ -293,8 +296,7 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
STREAM_TO_UINT16(cmd_len, p);
if (cmd_len > BT_SMALL_BUFFER_SIZE) {
- LOG_WARN("Command size %u exceeds limit %d", cmd_len,
- BT_SMALL_BUFFER_SIZE);
+ L2CAP_TRACE_WARNING("L2CAP - Invalid MTU Size");
l2cu_send_peer_cmd_reject(p_lcb, L2CAP_CMD_REJ_MTU_EXCEEDED, id, 0, 0);
return;
}
@@ -302,62 +304,51 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
/* Check command length does not exceed packet length */
p_next_cmd = p + cmd_len;
if (p_next_cmd > p_pkt_end) {
- LOG_WARN("cmd_len > pkt_len, pkt_len=%d, cmd_len=%d, code=%d", pkt_len,
- cmd_len, cmd_code);
+ L2CAP_TRACE_WARNING("Command len bad pkt_len: %d cmd_len: %d code: %d",
+ pkt_len, cmd_len, cmd_code);
break;
}
- LOG_DEBUG("cmd_code: %d, id:%d, cmd_len:%d", cmd_code, id, cmd_len);
+ L2CAP_TRACE_DEBUG("cmd_code: %d, id:%d, cmd_len:%d", cmd_code, id, cmd_len);
/* Bad L2CAP packet length, look for cmd to reject */
if (pkt_size_rej) {
/* If command found rejected it and we're done, otherwise keep looking */
- if (l2c_is_cmd_rejected(cmd_code, id, p_lcb)) {
- LOG_WARN("Rejected command %d due to bad packet length", cmd_code);
+ if (l2c_is_cmd_rejected(cmd_code, id, p_lcb))
return;
- } else {
- LOG_WARN("No need to reject command %d for bad packet len", cmd_code);
+ else
continue; /* Look for next cmd/response in current packet */
- }
}
switch (cmd_code) {
case L2CAP_CMD_REJECT:
uint16_t rej_reason;
- if (p + 2 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_REJECT");
- return;
- }
+ if (p + 2 > p_next_cmd) return;
STREAM_TO_UINT16(rej_reason, p);
if (rej_reason == L2CAP_CMD_REJ_MTU_EXCEEDED) {
uint16_t rej_mtu;
- if (p + 2 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_REJ_MTU_EXCEEDED");
- return;
- }
+ if (p + 2 > p_next_cmd) return;
STREAM_TO_UINT16(rej_mtu, p);
/* What to do with the MTU reject ? We have negotiated an MTU. For now
* we will ignore it and let a higher protocol timeout take care of it
*/
- LOG_WARN("MTU rej Handle: %d MTU: %d", p_lcb->Handle(), rej_mtu);
+ L2CAP_TRACE_WARNING("L2CAP - MTU rej Handle: %d MTU: %d",
+ p_lcb->handle, rej_mtu);
}
if (rej_reason == L2CAP_CMD_REJ_INVALID_CID) {
uint16_t lcid, rcid;
- if (p + 4 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_REJ_INVALID_CID");
- return;
- }
+ if (p + 4 > p_next_cmd) return;
STREAM_TO_UINT16(rcid, p);
STREAM_TO_UINT16(lcid, p);
- LOG_WARN("Rejected due to invalid CID, LCID: 0x%04x RCID: 0x%04x",
- lcid, rcid);
+ L2CAP_TRACE_WARNING(
+ "L2CAP - rej with CID invalid, LCID: 0x%04x RCID: 0x%04x", lcid,
+ rcid);
/* Remote CID invalid. Treat as a disconnect */
tL2C_CCB* p_ccb = l2cu_find_ccb_by_cid(p_lcb, lcid);
if ((p_ccb != NULL) && (p_ccb->remote_cid == rcid)) {
/* Fake link disconnect - no reply is generated */
- LOG_WARN("Remote CID is invalid, treat as disconnected");
l2c_csm_execute(p_ccb, L2CEVT_LP_DISCONNECT_IND, NULL);
}
}
@@ -382,42 +373,40 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
case L2CAP_CMD_CONN_REQ: {
uint16_t rcid;
- if (p + 4 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_CONN_REQ");
- return;
- }
+ if (p + 4 > p_next_cmd) return;
STREAM_TO_UINT16(con_info.psm, p);
STREAM_TO_UINT16(rcid, p);
tL2C_RCB* p_rcb = l2cu_find_rcb_by_psm(con_info.psm);
if (!p_rcb) {
- LOG_WARN("Rcvd conn req for unknown PSM: %d", con_info.psm);
+ L2CAP_TRACE_WARNING("L2CAP - rcvd conn req for unknown PSM: %d",
+ con_info.psm);
l2cu_reject_connection(p_lcb, rcid, id, L2CAP_CONN_NO_PSM);
break;
} else {
if (!p_rcb->api.pL2CA_ConnectInd_Cb) {
- LOG_WARN("Rcvd conn req for outgoing-only connection PSM: %d",
- con_info.psm);
+ L2CAP_TRACE_WARNING(
+ "L2CAP - rcvd conn req for outgoing-only connection PSM: %d",
+ con_info.psm);
l2cu_reject_connection(p_lcb, rcid, id, L2CAP_CONN_NO_PSM);
break;
}
}
tL2C_CCB* p_ccb = l2cu_allocate_ccb(p_lcb, 0);
- if (p_ccb == nullptr) {
- LOG_ERROR("Unable to allocate CCB");
+ if (!p_ccb) {
+ L2CAP_TRACE_ERROR("L2CAP - unable to allocate CCB");
l2cu_reject_connection(p_lcb, rcid, id, L2CAP_CONN_NO_RESOURCES);
break;
}
p_ccb->remote_id = id;
p_ccb->p_rcb = p_rcb;
p_ccb->remote_cid = rcid;
- p_ccb->connection_initiator = L2CAP_INITIATOR_REMOTE;
if (p_rcb->psm == BT_PSM_RFCOMM) {
btsnoop_get_interface()->add_rfc_l2c_channel(
- p_lcb->Handle(), p_ccb->local_cid, p_ccb->remote_cid);
+ p_lcb->handle, p_ccb->local_cid, p_ccb->remote_cid);
} else if (p_rcb->log_packets) {
- btsnoop_get_interface()->allowlist_l2c_channel(
- p_lcb->Handle(), p_ccb->local_cid, p_ccb->remote_cid);
+ btsnoop_get_interface()->whitelist_l2c_channel(
+ p_lcb->handle, p_ccb->local_cid, p_ccb->remote_cid);
}
l2c_csm_execute(p_ccb, L2CEVT_L2CAP_CONNECT_REQ, &con_info);
@@ -426,10 +415,7 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
case L2CAP_CMD_CONN_RSP: {
uint16_t lcid;
- if (p + 8 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_CONN_REQ");
- return;
- }
+ if (p + 8 > p_next_cmd) return;
STREAM_TO_UINT16(con_info.remote_cid, p);
STREAM_TO_UINT16(lcid, p);
STREAM_TO_UINT16(con_info.l2cap_result, p);
@@ -437,12 +423,13 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
tL2C_CCB* p_ccb = l2cu_find_ccb_by_cid(p_lcb, lcid);
if (!p_ccb) {
- LOG_WARN("no CCB for conn rsp, LCID: %d RCID: %d", lcid,
- con_info.remote_cid);
+ L2CAP_TRACE_WARNING("L2CAP - no CCB for conn rsp, LCID: %d RCID: %d",
+ lcid, con_info.remote_cid);
break;
}
if (p_ccb->local_id != id) {
- LOG_WARN("con rsp - bad ID. Exp: %d Got: %d", p_ccb->local_id, id);
+ L2CAP_TRACE_WARNING("L2CAP - con rsp - bad ID. Exp: %d Got: %d",
+ p_ccb->local_id, id);
break;
}
@@ -456,10 +443,10 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
tL2C_RCB* p_rcb = p_ccb->p_rcb;
if (p_rcb->psm == BT_PSM_RFCOMM) {
btsnoop_get_interface()->add_rfc_l2c_channel(
- p_lcb->Handle(), p_ccb->local_cid, p_ccb->remote_cid);
+ p_lcb->handle, p_ccb->local_cid, p_ccb->remote_cid);
} else if (p_rcb->log_packets) {
- btsnoop_get_interface()->allowlist_l2c_channel(
- p_lcb->Handle(), p_ccb->local_cid, p_ccb->remote_cid);
+ btsnoop_get_interface()->whitelist_l2c_channel(
+ p_lcb->handle, p_ccb->local_cid, p_ccb->remote_cid);
}
break;
@@ -471,10 +458,7 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
uint16_t cfg_rej_len = 0;
uint16_t lcid;
- if (p + 4 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_CONFIG_REQ");
- return;
- }
+ if (p + 4 > p_next_cmd) return;
STREAM_TO_UINT16(lcid, p);
STREAM_TO_UINT16(cfg_info.flags, p);
@@ -486,10 +470,7 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
while (p < p_cfg_end) {
uint8_t cfg_code, cfg_len;
- if (p + 2 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_CONFIG_REQ sub_event");
- return;
- }
+ if (p + 2 > p_next_cmd) return;
STREAM_TO_UINT8(cfg_code, p);
STREAM_TO_UINT8(cfg_len, p);
@@ -627,10 +608,7 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
case L2CAP_CMD_CONFIG_RSP: {
uint8_t* p_cfg_end = p + cmd_len;
uint16_t lcid;
- if (p + 6 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_CONFIG_RSP");
- return;
- }
+ if (p + 6 > p_next_cmd) return;
STREAM_TO_UINT16(lcid, p);
STREAM_TO_UINT16(cfg_info.flags, p);
STREAM_TO_UINT16(cfg_info.result, p);
@@ -641,38 +619,26 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
while (p < p_cfg_end) {
uint8_t cfg_code, cfg_len;
- if (p + 2 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_CONFIG_RSP sub_event");
- return;
- }
+ if (p + 2 > p_next_cmd) return;
STREAM_TO_UINT8(cfg_code, p);
STREAM_TO_UINT8(cfg_len, p);
switch (cfg_code & 0x7F) {
case L2CAP_CFG_TYPE_MTU:
cfg_info.mtu_present = true;
- if (p + 2 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CFG_TYPE_MTU");
- return;
- }
+ if (p + 2 > p_next_cmd) return;
STREAM_TO_UINT16(cfg_info.mtu, p);
break;
case L2CAP_CFG_TYPE_FLUSH_TOUT:
cfg_info.flush_to_present = true;
- if (p + 2 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CFG_TYPE_FLUSH_TOUT");
- return;
- }
+ if (p + 2 > p_next_cmd) return;
STREAM_TO_UINT16(cfg_info.flush_to, p);
break;
case L2CAP_CFG_TYPE_QOS:
cfg_info.qos_present = true;
- if (p + 2 + 5 * 4 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CFG_TYPE_QOS");
- return;
- }
+ if (p + 2 + 5 * 4 > p_next_cmd) return;
STREAM_TO_UINT8(cfg_info.qos.qos_flags, p);
STREAM_TO_UINT8(cfg_info.qos.service_type, p);
STREAM_TO_UINT32(cfg_info.qos.token_rate, p);
@@ -684,10 +650,7 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
case L2CAP_CFG_TYPE_FCR:
cfg_info.fcr_present = true;
- if (p + 3 + 3 * 2 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CFG_TYPE_FCR");
- return;
- }
+ if (p + 3 + 3 * 2 > p_next_cmd) return;
STREAM_TO_UINT8(cfg_info.fcr.mode, p);
STREAM_TO_UINT8(cfg_info.fcr.tx_win_sz, p);
STREAM_TO_UINT8(cfg_info.fcr.max_transmit, p);
@@ -698,19 +661,13 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
case L2CAP_CFG_TYPE_FCS:
cfg_info.fcs_present = true;
- if (p + 1 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CFG_TYPE_FCS");
- return;
- }
+ if (p + 1 > p_next_cmd) return;
STREAM_TO_UINT8(cfg_info.fcs, p);
break;
case L2CAP_CFG_TYPE_EXT_FLOW:
cfg_info.ext_flow_spec_present = true;
- if (p + 2 + 2 + 3 * 4 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CFG_TYPE_EXT_FLOW");
- return;
- }
+ if (p + 2 + 2 + 3 * 4 > p_next_cmd) return;
STREAM_TO_UINT8(cfg_info.ext_flow_spec.id, p);
STREAM_TO_UINT8(cfg_info.ext_flow_spec.stype, p);
STREAM_TO_UINT16(cfg_info.ext_flow_spec.max_sdu_size, p);
@@ -724,26 +681,25 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
tL2C_CCB* p_ccb = l2cu_find_ccb_by_cid(p_lcb, lcid);
if (p_ccb) {
if (p_ccb->local_id != id) {
- LOG_WARN("cfg rsp - bad ID. Exp: %d Got: %d", p_ccb->local_id, id);
+ L2CAP_TRACE_WARNING("L2CAP - cfg rsp - bad ID. Exp: %d Got: %d",
+ p_ccb->local_id, id);
break;
}
- if (cfg_info.result == L2CAP_CFG_OK) {
+ if ((cfg_info.result == L2CAP_CFG_OK) ||
+ (cfg_info.result == L2CAP_CFG_PENDING))
l2c_csm_execute(p_ccb, L2CEVT_L2CAP_CONFIG_RSP, &cfg_info);
- } else {
+ else
l2c_csm_execute(p_ccb, L2CEVT_L2CAP_CONFIG_RSP_NEG, &cfg_info);
- }
} else {
- LOG_WARN("Rcvd cfg rsp for unknown CID: 0x%04x", lcid);
+ L2CAP_TRACE_WARNING("L2CAP - rcvd cfg rsp for unknown CID: 0x%04x",
+ lcid);
}
break;
}
case L2CAP_CMD_DISC_REQ: {
uint16_t lcid, rcid;
- if (p + 4 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_DISC_REQ");
- return;
- }
+ if (p + 4 > p_next_cmd) return;
STREAM_TO_UINT16(lcid, p);
STREAM_TO_UINT16(rcid, p);
@@ -761,10 +717,7 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
case L2CAP_CMD_DISC_RSP: {
uint16_t lcid, rcid;
- if (p + 4 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_DISC_RSP");
- return;
- }
+ if (p + 4 > p_next_cmd) return;
STREAM_TO_UINT16(rcid, p);
STREAM_TO_UINT16(lcid, p);
@@ -781,12 +734,20 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
l2cu_send_peer_echo_rsp(p_lcb, id, p, cmd_len);
break;
+ case L2CAP_CMD_ECHO_RSP:
+ if (p_lcb->p_echo_rsp_cb) {
+ tL2CA_ECHO_RSP_CB* p_cb = p_lcb->p_echo_rsp_cb;
+
+ /* Zero out the callback in case app immediately calls us again */
+ p_lcb->p_echo_rsp_cb = NULL;
+
+ (*p_cb)(L2CAP_PING_RESULT_OK);
+ }
+ break;
+
case L2CAP_CMD_INFO_REQ: {
uint16_t info_type;
- if (p + 2 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_INFO_REQ");
- return;
- }
+ if (p + 2 > p_next_cmd) return;
STREAM_TO_UINT16(info_type, p);
l2cu_send_peer_info_rsp(p_lcb, id, info_type);
break;
@@ -800,29 +761,28 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
}
uint16_t info_type, result;
- if (p + 4 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_INFO_RSP");
- return;
- }
+ if (p + 4 > p_next_cmd) return;
STREAM_TO_UINT16(info_type, p);
STREAM_TO_UINT16(result, p);
+ p_lcb->info_rx_bits |= (1 << info_type);
+
if ((info_type == L2CAP_EXTENDED_FEATURES_INFO_TYPE) &&
(result == L2CAP_INFO_RESP_RESULT_SUCCESS)) {
- if (p + 4 > p_next_cmd) {
- LOG_WARN("Not enough data for L2CAP_CMD_INFO_RSP sub_event");
- return;
- }
+ if (p + 4 > p_next_cmd) return;
STREAM_TO_UINT32(p_lcb->peer_ext_fea, p);
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
if (p_lcb->peer_ext_fea & L2CAP_EXTFEA_FIXED_CHNLS) {
l2cu_send_peer_info_req(p_lcb, L2CAP_FIXED_CHANNELS_INFO_TYPE);
break;
} else {
l2cu_process_fixed_chnl_resp(p_lcb);
}
+#endif
}
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
if (info_type == L2CAP_FIXED_CHANNELS_INFO_TYPE) {
if (result == L2CAP_INFO_RESP_RESULT_SUCCESS) {
if (p + L2CAP_FIXED_CHNL_ARRAY_SIZE > p_next_cmd) {
@@ -834,19 +794,18 @@ static void process_l2cap_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
l2cu_process_fixed_chnl_resp(p_lcb);
}
- {
- tL2C_CONN_INFO ci;
- ci.status = HCI_SUCCESS;
- ci.bd_addr = p_lcb->remote_bd_addr;
- for (tL2C_CCB* p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb;
- p_ccb = p_ccb->p_next_ccb) {
- l2c_csm_execute(p_ccb, L2CEVT_L2CAP_INFO_RSP, &ci);
- }
+#endif
+ tL2C_CONN_INFO ci;
+ ci.status = HCI_SUCCESS;
+ ci.bd_addr = p_lcb->remote_bd_addr;
+ for (tL2C_CCB* p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb;
+ p_ccb = p_ccb->p_next_ccb) {
+ l2c_csm_execute(p_ccb, L2CEVT_L2CAP_INFO_RSP, &ci);
}
break;
default:
- LOG_WARN("Bad cmd code: %d", cmd_code);
+ L2CAP_TRACE_WARNING("L2CAP - bad cmd code: %d", cmd_code);
l2cu_send_peer_cmd_reject(p_lcb, L2CAP_CMD_REJ_NOT_UNDERSTOOD, id, 0,
0);
return;
@@ -905,14 +864,11 @@ void l2c_process_held_packets(bool timed_out) {
*
******************************************************************************/
void l2c_init(void) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- // L2CAP init should be handled by GD stack manager
- return;
- }
-
int16_t xx;
memset(&l2cb, 0, sizeof(tL2C_CB));
+ /* the psm is increased by 2 before being used */
+ l2cb.dyn_psm = 0xFFF;
/* the LE PSM is increased by 1 before being used */
l2cb.le_dyn_psm = LE_DYNAMIC_PSM_START - 1;
@@ -922,12 +878,20 @@ void l2c_init(void) {
l2cb.ccb_pool[xx].p_next_ccb = &l2cb.ccb_pool[xx + 1];
}
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
/* it will be set to L2CAP_PKT_START_NON_FLUSHABLE if controller supports */
l2cb.non_flushable_pbf = L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT;
+#endif
l2cb.p_free_ccb_first = &l2cb.ccb_pool[0];
l2cb.p_free_ccb_last = &l2cb.ccb_pool[MAX_L2CAP_CHANNELS - 1];
+#ifdef L2CAP_DESIRED_LINK_ROLE
+ l2cb.desire_role = L2CAP_DESIRED_LINK_ROLE;
+#else
+ l2cb.desire_role = HCI_ROLE_SLAVE;
+#endif
+
/* Set the default idle timeout */
l2cb.idle_timeout = L2CAP_LINK_INACTIVITY_TOUT;
@@ -942,7 +906,10 @@ void l2c_init(void) {
l2cb.test_info_resp = L2CAP_EXTFEA_SUPPORTED_MASK;
#endif
- /* Number of ACL buffers to use for high priority channel */
+/* Number of ACL buffers to use for high priority channel */
+#if (L2CAP_HIGH_PRI_CHAN_QUOTA_IS_CONFIGURABLE == TRUE)
+ l2cb.high_pri_min_xmit_quota = L2CAP_HIGH_PRI_MIN_XMIT_QUOTA;
+#endif
l2cb.l2c_ble_fixed_chnls_mask = L2CAP_FIXED_CHNL_ATT_BIT |
L2CAP_FIXED_CHNL_BLE_SIG_BIT |
@@ -955,11 +922,6 @@ void l2c_init(void) {
}
void l2c_free(void) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- // L2CAP cleanup should be handled by GD stack manager
- return;
- }
-
list_free(l2cb.rcv_pending_q);
l2cb.rcv_pending_q = NULL;
}
@@ -1000,6 +962,7 @@ void l2c_lcb_timer_timeout(void* data) {
*
******************************************************************************/
uint8_t l2c_data_write(uint16_t cid, BT_HDR* p_data, uint16_t flags) {
+
/* Find the channel control block. We don't know the link it is on. */
tL2C_CCB* p_ccb = l2cu_find_ccb_by_cid(NULL, cid);
if (!p_ccb) {
@@ -1008,7 +971,9 @@ uint8_t l2c_data_write(uint16_t cid, BT_HDR* p_data, uint16_t flags) {
return (L2CAP_DW_FAILED);
}
- /* Sending message bigger than mtu size of peer is a violation of protocol */
+#ifndef TESTER
+ /* Tester may send any amount of data. otherwise sending message bigger than
+ * mtu size of peer is a violation of protocol */
uint16_t mtu;
if (p_ccb->p_lcb->transport == BT_TRANSPORT_LE)
@@ -1024,6 +989,7 @@ uint8_t l2c_data_write(uint16_t cid, BT_HDR* p_data, uint16_t flags) {
osi_free(p_data);
return (L2CAP_DW_FAILED);
}
+#endif
/* channel based, packet based flushable or non-flushable */
p_data->layer_specific = flags;
diff --git a/stack/l2cap/l2c_utils.cc b/stack/l2cap/l2c_utils.cc
index 72c5326fa..da30f2b8a 100644
--- a/stack/l2cap/l2c_utils.cc
+++ b/stack/l2cap/l2c_utils.cc
@@ -21,28 +21,40 @@
* This file contains L2CAP utility functions
*
******************************************************************************/
-#define LOG_TAG "l2c_utils"
#include <stdio.h>
+#include <stdlib.h>
#include <string.h>
#include "bt_common.h"
#include "bt_types.h"
+#include "bt_utils.h"
#include "btm_api.h"
+#include "btm_int.h"
+#include "btu.h"
#include "device/include/controller.h"
#include "hci/include/btsnoop.h"
#include "hcidefs.h"
+#include "hcimsgs.h"
#include "l2c_int.h"
#include "l2cdefs.h"
-#include "main/shim/l2c_api.h"
-#include "main/shim/shim.h"
#include "osi/include/allocator.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/hci_error_code.h"
-tL2C_CCB* l2cu_get_next_channel_in_rr(tL2C_LCB* p_lcb); // TODO Move
+/*******************************************************************************
+ *
+ * Function l2cu_can_allocate_lcb
+ *
+ * Description Look for an unused LCB
+ *
+ * Returns true if there is space for one more lcb
+ *
+ ******************************************************************************/
+bool l2cu_can_allocate_lcb(void) {
+ for (int i = 0; i < MAX_L2CAP_LINKS; i++) {
+ if (!l2cb.lcb_pool[i].in_use) return true;
+ }
+ return false;
+}
/*******************************************************************************
*
@@ -68,16 +80,13 @@ tL2C_LCB* l2cu_allocate_lcb(const RawAddress& p_bd_addr, bool is_bonding,
p_lcb->in_use = true;
p_lcb->link_state = LST_DISCONNECTED;
- p_lcb->InvalidateHandle();
+ p_lcb->handle = HCI_INVALID_HANDLE;
+ p_lcb->link_flush_tout = 0xFFFF;
p_lcb->l2c_lcb_timer = alarm_new("l2c_lcb.l2c_lcb_timer");
p_lcb->info_resp_timer = alarm_new("l2c_lcb.info_resp_timer");
p_lcb->idle_timeout = l2cb.idle_timeout;
- p_lcb->signal_id = 1; /* spec does not allow '0' */
- if (is_bonding) {
- p_lcb->SetBonding();
- } else {
- p_lcb->ResetBonding();
- }
+ p_lcb->id = 1; /* spec does not allow '0' */
+ p_lcb->is_bonding = is_bonding;
p_lcb->transport = transport;
p_lcb->tx_data_len =
controller_get_interface()->get_ble_default_data_packet_length();
@@ -87,7 +96,7 @@ tL2C_LCB* l2cu_allocate_lcb(const RawAddress& p_bd_addr, bool is_bonding,
l2cb.num_ble_links_active++;
l2c_ble_link_adjust_allocation();
} else {
- l2cb.num_used_lcbs++;
+ l2cb.num_links_active++;
l2c_link_adjust_allocation();
}
p_lcb->link_xmit_data_q = list_new(NULL);
@@ -99,14 +108,6 @@ tL2C_LCB* l2cu_allocate_lcb(const RawAddress& p_bd_addr, bool is_bonding,
return (NULL);
}
-void l2cu_set_lcb_handle(struct t_l2c_linkcb& p_lcb, uint16_t handle) {
- if (p_lcb.Handle() != HCI_INVALID_HANDLE) {
- LOG_WARN("Should not replace active handle:%hu with new handle:%hu",
- p_lcb.Handle(), handle);
- }
- p_lcb.SetHandle(handle);
-}
-
/*******************************************************************************
*
* Function l2cu_update_lcb_4_bonding
@@ -118,21 +119,12 @@ void l2cu_set_lcb_handle(struct t_l2c_linkcb& p_lcb, uint16_t handle) {
*
******************************************************************************/
void l2cu_update_lcb_4_bonding(const RawAddress& p_bd_addr, bool is_bonding) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- bluetooth::shim::L2CA_SetBondingState(p_bd_addr, is_bonding);
- return;
- }
-
tL2C_LCB* p_lcb = l2cu_find_lcb_by_bd_addr(p_bd_addr, BT_TRANSPORT_BR_EDR);
if (p_lcb) {
VLOG(1) << __func__ << " BDA: " << p_bd_addr
<< " is_bonding: " << is_bonding;
- if (is_bonding) {
- p_lcb->SetBonding();
- } else {
- p_lcb->ResetBonding();
- }
+ p_lcb->is_bonding = is_bonding;
}
}
@@ -150,7 +142,7 @@ void l2cu_release_lcb(tL2C_LCB* p_lcb) {
tL2C_CCB* p_ccb;
p_lcb->in_use = false;
- p_lcb->ResetBonding();
+ p_lcb->is_bonding = false;
/* Stop and free timers */
alarm_free(p_lcb->l2c_lcb_timer);
@@ -158,8 +150,11 @@ void l2cu_release_lcb(tL2C_LCB* p_lcb) {
alarm_free(p_lcb->info_resp_timer);
p_lcb->info_resp_timer = NULL;
+ /* Release any unfinished L2CAP packet on this link */
+ osi_free_and_reset((void**)&p_lcb->p_hcit_rcv_acl);
+
if (p_lcb->transport == BT_TRANSPORT_BR_EDR) /* Release all SCO links */
- BTM_RemoveSco(p_lcb->remote_bd_addr);
+ btm_remove_sco_links(p_lcb->remote_bd_addr);
if (p_lcb->sent_not_acked > 0) {
if (p_lcb->transport == BT_TRANSPORT_LE) {
@@ -175,7 +170,9 @@ void l2cu_release_lcb(tL2C_LCB* p_lcb) {
}
}
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
l2cu_process_fixed_disc_cback(p_lcb);
+#endif
/* Ensure no CCBs left on this LCB */
for (p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb;
@@ -186,7 +183,7 @@ void l2cu_release_lcb(tL2C_LCB* p_lcb) {
/* Tell BTM Acl management the link was removed */
if ((p_lcb->link_state == LST_CONNECTED) ||
(p_lcb->link_state == LST_DISCONNECTING))
- btm_acl_removed(p_lcb->Handle());
+ btm_acl_removed(p_lcb->remote_bd_addr, p_lcb->transport);
/* Release any held buffers */
if (p_lcb->link_xmit_data_q) {
@@ -205,11 +202,21 @@ void l2cu_release_lcb(tL2C_LCB* p_lcb) {
l2c_ble_link_adjust_allocation();
} else {
- if (l2cb.num_used_lcbs >= 1) l2cb.num_used_lcbs--;
+ if (l2cb.num_links_active >= 1) l2cb.num_links_active--;
l2c_link_adjust_allocation();
}
+ /* Check for ping outstanding */
+ if (p_lcb->p_echo_rsp_cb) {
+ tL2CA_ECHO_RSP_CB* p_cb = p_lcb->p_echo_rsp_cb;
+
+ /* Zero out the callback in case app immediately calls us again */
+ p_lcb->p_echo_rsp_cb = NULL;
+
+ (*p_cb)(L2CAP_PING_RESULT_NO_LINK);
+ }
+
/* Check and release all the LE COC connections waiting for security */
if (p_lcb->le_sec_pending_q) {
while (!fixed_queue_is_empty(p_lcb->le_sec_pending_q)) {
@@ -253,6 +260,20 @@ tL2C_LCB* l2cu_find_lcb_by_bd_addr(const RawAddress& p_bd_addr,
/*******************************************************************************
*
+ * Function l2cu_get_conn_role
+ *
+ * Description Determine the desired role (master or slave) of a link.
+ * If already got a slave link, this one must be a master. If
+ * already got at least 1 link where we are the master, make
+ * this also a master.
+ *
+ * Returns HCI_ROLE_MASTER or HCI_ROLE_SLAVE
+ *
+ ******************************************************************************/
+uint8_t l2cu_get_conn_role(tL2C_LCB* p_this_lcb) { return l2cb.desire_role; }
+
+/*******************************************************************************
+ *
* Function l2c_is_cmd_rejected
*
* Description Checks if cmd_code is command or response
@@ -264,7 +285,7 @@ tL2C_LCB* l2cu_find_lcb_by_bd_addr(const RawAddress& p_bd_addr,
* false if response code. (command not rejected)
*
******************************************************************************/
-bool l2c_is_cmd_rejected(uint8_t cmd_code, uint8_t signal_id, tL2C_LCB* p_lcb) {
+bool l2c_is_cmd_rejected(uint8_t cmd_code, uint8_t id, tL2C_LCB* p_lcb) {
switch (cmd_code) {
case L2CAP_CMD_CONN_REQ:
case L2CAP_CMD_CONFIG_REQ:
@@ -274,7 +295,7 @@ bool l2c_is_cmd_rejected(uint8_t cmd_code, uint8_t signal_id, tL2C_LCB* p_lcb) {
case L2CAP_CMD_AMP_CONN_REQ:
case L2CAP_CMD_AMP_MOVE_REQ:
case L2CAP_CMD_BLE_UPDATE_REQ:
- l2cu_send_peer_cmd_reject(p_lcb, L2CAP_CMD_REJ_MTU_EXCEEDED, signal_id,
+ l2cu_send_peer_cmd_reject(p_lcb, L2CAP_CMD_REJ_MTU_EXCEEDED, id,
L2CAP_DEFAULT_MTU, 0);
L2CAP_TRACE_WARNING("Dumping first Command (%d)", cmd_code);
return true;
@@ -294,7 +315,7 @@ bool l2c_is_cmd_rejected(uint8_t cmd_code, uint8_t signal_id, tL2C_LCB* p_lcb) {
*
******************************************************************************/
BT_HDR* l2cu_build_header(tL2C_LCB* p_lcb, uint16_t len, uint8_t cmd,
- uint8_t signal_id) {
+ uint8_t id) {
BT_HDR* p_buf = (BT_HDR*)osi_malloc(L2CAP_CMD_BUF_SIZE);
uint8_t* p;
@@ -305,10 +326,15 @@ BT_HDR* l2cu_build_header(tL2C_LCB* p_lcb, uint16_t len, uint8_t cmd,
/* Put in HCI header - handle + pkt boundary */
if (p_lcb->transport == BT_TRANSPORT_LE) {
- UINT16_TO_STREAM(p, (p_lcb->Handle() | (L2CAP_PKT_START_NON_FLUSHABLE
- << L2CAP_PKT_TYPE_SHIFT)));
+ UINT16_TO_STREAM(p, (p_lcb->handle | (L2CAP_PKT_START_NON_FLUSHABLE
+ << L2CAP_PKT_TYPE_SHIFT)));
} else {
- UINT16_TO_STREAM(p, p_lcb->Handle() | l2cb.non_flushable_pbf);
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
+ UINT16_TO_STREAM(p, p_lcb->handle | l2cb.non_flushable_pbf);
+#else
+ UINT16_TO_STREAM(
+ p, (p_lcb->handle | (L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT)));
+#endif
}
UINT16_TO_STREAM(p, len + L2CAP_PKT_OVERHEAD + L2CAP_CMD_OVERHEAD);
@@ -322,7 +348,7 @@ BT_HDR* l2cu_build_header(tL2C_LCB* p_lcb, uint16_t len, uint8_t cmd,
/* Put in L2CAP command header */
UINT8_TO_STREAM(p, cmd);
- UINT8_TO_STREAM(p, signal_id);
+ UINT8_TO_STREAM(p, id);
UINT16_TO_STREAM(p, len);
return (p_buf);
@@ -338,9 +364,9 @@ BT_HDR* l2cu_build_header(tL2C_LCB* p_lcb, uint16_t len, uint8_t cmd,
* Returns void
*
******************************************************************************/
-void l2cu_adj_id(tL2C_LCB* p_lcb) {
- if (p_lcb->signal_id == 0) {
- p_lcb->signal_id++;
+void l2cu_adj_id(tL2C_LCB* p_lcb, uint8_t adj_mask) {
+ if ((adj_mask & L2CAP_ADJ_ZERO_ID) && !p_lcb->id) {
+ p_lcb->id++;
}
}
@@ -384,7 +410,7 @@ void l2cu_send_peer_cmd_reject(tL2C_LCB* p_lcb, uint16_t reason, uint8_t rem_id,
if (param_len >= 4) UINT16_TO_STREAM(p, p2);
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -402,10 +428,10 @@ void l2cu_send_peer_connect_req(tL2C_CCB* p_ccb) {
uint8_t* p;
/* Create an identifier for this packet */
- p_ccb->p_lcb->signal_id++;
- l2cu_adj_id(p_ccb->p_lcb);
+ p_ccb->p_lcb->id++;
+ l2cu_adj_id(p_ccb->p_lcb, L2CAP_ADJ_ID);
- p_ccb->local_id = p_ccb->p_lcb->signal_id;
+ p_ccb->local_id = p_ccb->p_lcb->id;
p_buf = l2cu_build_header(p_ccb->p_lcb, L2CAP_CONN_REQ_LEN,
L2CAP_CMD_CONN_REQ, p_ccb->local_id);
@@ -420,7 +446,7 @@ void l2cu_send_peer_connect_req(tL2C_CCB* p_ccb) {
UINT16_TO_STREAM(p, p_ccb->p_rcb->real_psm);
UINT16_TO_STREAM(p, p_ccb->local_cid);
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -435,32 +461,33 @@ void l2cu_send_peer_connect_req(tL2C_CCB* p_ccb) {
******************************************************************************/
void l2cu_send_peer_connect_rsp(tL2C_CCB* p_ccb, uint16_t result,
uint16_t status) {
+ BT_HDR* p_buf;
+ uint8_t* p;
+
if (result == L2CAP_CONN_PENDING) {
/* if we already sent pending response */
- if (p_ccb->flags & CCB_FLAG_SENT_PENDING) {
- LOG_DEBUG("Already sent connection pending, not sending again");
+ if (p_ccb->flags & CCB_FLAG_SENT_PENDING)
return;
- } else {
+ else
p_ccb->flags |= CCB_FLAG_SENT_PENDING;
- }
}
- BT_HDR* p_buf = l2cu_build_header(p_ccb->p_lcb, L2CAP_CONN_RSP_LEN,
- L2CAP_CMD_CONN_RSP, p_ccb->remote_id);
- if (p_buf == nullptr) {
- LOG_WARN("no buffer for conn_rsp");
+ p_buf = l2cu_build_header(p_ccb->p_lcb, L2CAP_CONN_RSP_LEN,
+ L2CAP_CMD_CONN_RSP, p_ccb->remote_id);
+ if (p_buf == NULL) {
+ L2CAP_TRACE_WARNING("L2CAP - no buffer for conn_rsp");
return;
}
- uint8_t* p = (uint8_t*)(p_buf + 1) + L2CAP_SEND_CMD_OFFSET +
- HCI_DATA_PREAMBLE_SIZE + L2CAP_PKT_OVERHEAD + L2CAP_CMD_OVERHEAD;
+ p = (uint8_t*)(p_buf + 1) + L2CAP_SEND_CMD_OFFSET + HCI_DATA_PREAMBLE_SIZE +
+ L2CAP_PKT_OVERHEAD + L2CAP_CMD_OVERHEAD;
UINT16_TO_STREAM(p, p_ccb->local_cid);
UINT16_TO_STREAM(p, p_ccb->remote_cid);
UINT16_TO_STREAM(p, result);
UINT16_TO_STREAM(p, status);
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -494,60 +521,7 @@ void l2cu_reject_connection(tL2C_LCB* p_lcb, uint16_t remote_cid,
UINT16_TO_STREAM(p, result);
UINT16_TO_STREAM(p, 0); /* Status of 0 */
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
-}
-
-/*******************************************************************************
- *
- * Function l2cu_send_credit_based_reconfig_req
- *
- * Description Build and send an L2CAP "recoonfiguration request" message
- * to the peer.
- *
- * Returns void
- *
- ******************************************************************************/
-void l2cu_send_credit_based_reconfig_req(tL2C_CCB* p_ccb,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- BT_HDR* p_buf;
- uint16_t cmd_len;
- uint8_t* p;
- tL2C_LCB* p_lcb = p_ccb->p_lcb;
- tL2C_CCB* p_ccb_temp;
-
- cmd_len = L2CAP_CMD_CREDIT_BASED_RECONFIG_REQ_MIN_LEN +
- sizeof(uint16_t) * p_lcb->pending_ecoc_reconfig_cnt;
-
- /* Create an identifier for this packet */
- p_lcb->signal_id++;
- l2cu_adj_id(p_lcb);
-
- p_ccb->local_id = p_lcb->signal_id;
-
- p_buf = l2cu_build_header(p_lcb, cmd_len, L2CAP_CMD_CREDIT_BASED_RECONFIG_REQ,
- p_lcb->signal_id);
- if (p_buf == NULL) {
- L2CAP_TRACE_WARNING("l2cu_send_reconfig_req - no buffer");
- return;
- }
-
- p = (uint8_t*)(p_buf + 1) + L2CAP_SEND_CMD_OFFSET + HCI_DATA_PREAMBLE_SIZE +
- L2CAP_PKT_OVERHEAD + L2CAP_CMD_OVERHEAD;
-
- L2CAP_TRACE_DEBUG("l2cu_send_reconfig_req number of cids: %d mtu:%d mps:%d",
- p_lcb->pending_ecoc_reconfig_cnt, p_cfg->mtu, p_cfg->mps);
-
- UINT16_TO_STREAM(p, p_cfg->mtu);
- UINT16_TO_STREAM(p, p_cfg->mps);
-
- for (p_ccb_temp = p_lcb->ccb_queue.p_first_ccb; p_ccb_temp;
- p_ccb_temp = p_ccb_temp->p_next_ccb) {
- if ((p_ccb_temp->in_use) && (p_ccb_temp->ecoc) &&
- (p_ccb_temp->reconfig_started))
- UINT16_TO_STREAM(p, p_ccb_temp->local_cid);
- }
-
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -566,10 +540,10 @@ void l2cu_send_peer_config_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
uint8_t* p;
/* Create an identifier for this packet */
- p_ccb->p_lcb->signal_id++;
- l2cu_adj_id(p_ccb->p_lcb);
+ p_ccb->p_lcb->id++;
+ l2cu_adj_id(p_ccb->p_lcb, L2CAP_ADJ_ID);
- p_ccb->local_id = p_ccb->p_lcb->signal_id;
+ p_ccb->local_id = p_ccb->p_lcb->id;
if (p_cfg->mtu_present)
cfg_len += L2CAP_CFG_MTU_OPTION_LEN + L2CAP_CFG_OPTION_OVERHEAD;
@@ -648,7 +622,7 @@ void l2cu_send_peer_config_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
UINT32_TO_STREAM(p, p_cfg->ext_flow_spec.flush_timeout);
}
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -738,7 +712,7 @@ void l2cu_send_peer_config_rsp(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
UINT32_TO_STREAM(p, p_cfg->ext_flow_spec.flush_timeout);
}
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -773,16 +747,16 @@ void l2cu_send_peer_config_rej(tL2C_CCB* p_ccb, uint8_t* p_data,
p_buf->offset = L2CAP_SEND_CMD_OFFSET;
p = (uint8_t*)(p_buf + 1) + L2CAP_SEND_CMD_OFFSET;
- const controller_t* controller = controller_get_interface();
-
/* Put in HCI header - handle + pkt boundary */
- if (controller->supports_non_flushable_pb()) {
- UINT16_TO_STREAM(p, (p_ccb->p_lcb->Handle() | (L2CAP_PKT_START_NON_FLUSHABLE
- << L2CAP_PKT_TYPE_SHIFT)));
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
+ if (HCI_NON_FLUSHABLE_PB_SUPPORTED(BTM_ReadLocalFeatures())) {
+ UINT16_TO_STREAM(p, (p_ccb->p_lcb->handle | (L2CAP_PKT_START_NON_FLUSHABLE
+ << L2CAP_PKT_TYPE_SHIFT)));
} else
+#endif
{
- UINT16_TO_STREAM(p, (p_ccb->p_lcb->Handle() |
- (L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT)));
+ UINT16_TO_STREAM(
+ p, (p_ccb->p_lcb->handle | (L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT)));
}
/* Remember the HCI header length position, and save space for it */
@@ -855,7 +829,7 @@ void l2cu_send_peer_config_rej(tL2C_CCB* p_ccb, uint8_t* p_data,
L2CAP_TRACE_DEBUG("L2CAP - cfg_rej pkt hci_len=%d, l2cap_len=%d", len,
(L2CAP_CMD_OVERHEAD + L2CAP_CONFIG_RSP_LEN + rej_len));
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -878,10 +852,10 @@ void l2cu_send_peer_disc_req(tL2C_CCB* p_ccb) {
}
/* Create an identifier for this packet */
- p_ccb->p_lcb->signal_id++;
- l2cu_adj_id(p_ccb->p_lcb);
+ p_ccb->p_lcb->id++;
+ l2cu_adj_id(p_ccb->p_lcb, L2CAP_ADJ_ID);
- p_ccb->local_id = p_ccb->p_lcb->signal_id;
+ p_ccb->local_id = p_ccb->p_lcb->id;
p_buf = l2cu_build_header(p_ccb->p_lcb, L2CAP_DISC_REQ_LEN,
L2CAP_CMD_DISC_REQ, p_ccb->local_id);
@@ -903,11 +877,11 @@ void l2cu_send_peer_disc_req(tL2C_CCB* p_ccb) {
while ((p_buf2 = (BT_HDR*)fixed_queue_try_dequeue(p_ccb->xmit_hold_q)) !=
NULL) {
l2cu_set_acl_hci_header(p_buf2, p_ccb);
- l2c_link_check_send_pkts(p_ccb->p_lcb, p_ccb->local_cid, p_buf2);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, p_ccb, p_buf2);
}
}
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -942,7 +916,43 @@ void l2cu_send_peer_disc_rsp(tL2C_LCB* p_lcb, uint8_t remote_id,
UINT16_TO_STREAM(p, local_cid);
UINT16_TO_STREAM(p, remote_cid);
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
+}
+
+/*******************************************************************************
+ *
+ * Function l2cu_send_peer_echo_req
+ *
+ * Description Build and send an L2CAP "echo request" message
+ * to the peer. Note that we do not currently allow
+ * data in the echo request.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+void l2cu_send_peer_echo_req(tL2C_LCB* p_lcb, uint8_t* p_data,
+ uint16_t data_len) {
+ BT_HDR* p_buf;
+ uint8_t* p;
+
+ p_lcb->id++;
+ l2cu_adj_id(p_lcb, L2CAP_ADJ_ZERO_ID); /* check for wrap to '0' */
+
+ p_buf = l2cu_build_header(p_lcb, (uint16_t)(L2CAP_ECHO_REQ_LEN + data_len),
+ L2CAP_CMD_ECHO_REQ, p_lcb->id);
+ if (p_buf == NULL) {
+ L2CAP_TRACE_WARNING("L2CAP - no buffer for echo_req");
+ return;
+ }
+
+ p = (uint8_t*)(p_buf + 1) + L2CAP_SEND_CMD_OFFSET + HCI_DATA_PREAMBLE_SIZE +
+ L2CAP_PKT_OVERHEAD + L2CAP_CMD_OVERHEAD;
+
+ if (data_len) {
+ ARRAY_TO_STREAM(p, p_data, data_len);
+ }
+
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -955,20 +965,19 @@ void l2cu_send_peer_disc_rsp(tL2C_LCB* p_lcb, uint8_t remote_id,
* Returns void
*
******************************************************************************/
-void l2cu_send_peer_echo_rsp(tL2C_LCB* p_lcb, uint8_t signal_id,
- uint8_t* p_data, uint16_t data_len) {
+void l2cu_send_peer_echo_rsp(tL2C_LCB* p_lcb, uint8_t id, uint8_t* p_data,
+ uint16_t data_len) {
BT_HDR* p_buf;
uint8_t* p;
uint16_t maxlen;
/* Filter out duplicate IDs or if available buffers are low (intruder
* checking) */
- if (!signal_id || signal_id == p_lcb->cur_echo_id) {
+ if (!id || id == p_lcb->cur_echo_id) {
/* Dump this request since it is illegal */
- L2CAP_TRACE_WARNING("L2CAP ignoring duplicate echo request (%d)",
- signal_id);
+ L2CAP_TRACE_WARNING("L2CAP ignoring duplicate echo request (%d)", id);
return;
} else
- p_lcb->cur_echo_id = signal_id;
+ p_lcb->cur_echo_id = id;
uint16_t acl_data_size =
controller_get_interface()->get_acl_data_size_classic();
@@ -985,7 +994,7 @@ void l2cu_send_peer_echo_rsp(tL2C_LCB* p_lcb, uint8_t signal_id,
if (data_len > maxlen) data_len = 0;
p_buf = l2cu_build_header(p_lcb, (uint16_t)(L2CAP_ECHO_RSP_LEN + data_len),
- L2CAP_CMD_ECHO_RSP, signal_id);
+ L2CAP_CMD_ECHO_RSP, id);
if (p_buf == NULL) {
L2CAP_TRACE_WARNING("L2CAP - no buffer for echo_rsp");
return;
@@ -998,7 +1007,7 @@ void l2cu_send_peer_echo_rsp(tL2C_LCB* p_lcb, uint8_t signal_id,
ARRAY_TO_STREAM(p, p_data, data_len);
}
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -1014,11 +1023,11 @@ void l2cu_send_peer_info_req(tL2C_LCB* p_lcb, uint16_t info_type) {
BT_HDR* p_buf;
uint8_t* p;
- /* Create an identifier for this packet */
- p_lcb->signal_id++;
- l2cu_adj_id(p_lcb);
+ /* check for wrap and/or BRCM ID */
+ p_lcb->id++;
+ l2cu_adj_id(p_lcb, L2CAP_ADJ_ID);
- p_buf = l2cu_build_header(p_lcb, 2, L2CAP_CMD_INFO_REQ, p_lcb->signal_id);
+ p_buf = l2cu_build_header(p_lcb, 2, L2CAP_CMD_INFO_REQ, p_lcb->id);
if (p_buf == NULL) {
L2CAP_TRACE_WARNING("L2CAP - no buffer for info_req");
return;
@@ -1035,7 +1044,7 @@ void l2cu_send_peer_info_req(tL2C_LCB* p_lcb, uint16_t info_type) {
alarm_set_on_mloop(p_lcb->info_resp_timer, L2CAP_WAIT_INFO_RSP_TIMEOUT_MS,
l2c_info_resp_timer_timeout, p_lcb);
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -1107,8 +1116,12 @@ void l2cu_send_peer_info_rsp(tL2C_LCB* p_lcb, uint8_t remote_id,
#if (L2CAP_CONFORMANCE_TESTING == TRUE)
UINT32_TO_STREAM(p, l2cb.test_info_resp);
#else
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
UINT32_TO_STREAM(p,
L2CAP_EXTFEA_SUPPORTED_MASK | L2CAP_EXTFEA_FIXED_CHNLS);
+#else
+ UINT32_TO_STREAM(p, L2CAP_EXTFEA_SUPPORTED_MASK);
+#endif
#endif
}
} else if (info_type == L2CAP_FIXED_CHANNELS_INFO_TYPE) {
@@ -1120,6 +1133,7 @@ void l2cu_send_peer_info_rsp(tL2C_LCB* p_lcb, uint8_t remote_id,
if (L2CAP_EXTFEA_SUPPORTED_MASK & L2CAP_EXTFEA_UCD_RECEPTION)
p[0] |= L2CAP_FIXED_CHNL_CNCTLESS_BIT;
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
{
int xx;
@@ -1134,6 +1148,7 @@ void l2cu_send_peer_info_rsp(tL2C_LCB* p_lcb, uint8_t remote_id,
1 << ((xx + L2CAP_FIRST_FIXED_CHNL) % 8);
}
}
+#endif
} else if (info_type == L2CAP_CONNLESS_MTU_INFO_TYPE) {
UINT16_TO_STREAM(p, L2CAP_INFO_RESP_RESULT_SUCCESS);
UINT16_TO_STREAM(p, L2CAP_MTU_SIZE);
@@ -1142,7 +1157,7 @@ void l2cu_send_peer_info_rsp(tL2C_LCB* p_lcb, uint8_t remote_id,
p, L2CAP_INFO_RESP_RESULT_NOT_SUPPORTED); /* 'not supported' */
}
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/******************************************************************************
@@ -1209,6 +1224,7 @@ void l2cu_enqueue_ccb(tL2C_CCB* p_ccb) {
}
}
+#if (L2CAP_ROUND_ROBIN_CHANNEL_SERVICE == TRUE)
/* Adding CCB into round robin service table of its LCB */
if (p_ccb->p_lcb != NULL) {
/* if this is the first channel in this priority group */
@@ -1224,6 +1240,7 @@ void l2cu_enqueue_ccb(tL2C_CCB* p_ccb) {
/* increase number of channels in this group */
p_ccb->p_lcb->rr_serv[p_ccb->ccb_priority].num_ccb++;
}
+#endif
}
/******************************************************************************
@@ -1253,6 +1270,7 @@ void l2cu_dequeue_ccb(tL2C_CCB* p_ccb) {
return;
}
+#if (L2CAP_ROUND_ROBIN_CHANNEL_SERVICE == TRUE)
/* Removing CCB from round robin service table of its LCB */
if (p_ccb->p_lcb != NULL) {
/* decrease number of channels in this priority group */
@@ -1276,6 +1294,7 @@ void l2cu_dequeue_ccb(tL2C_CCB* p_ccb) {
}
}
}
+#endif
if (p_ccb == p_q->p_first_ccb) {
/* We are removing the first in a queue */
@@ -1319,6 +1338,7 @@ void l2cu_change_pri_ccb(tL2C_CCB* p_ccb, tL2CAP_CHNL_PRIORITY priority) {
p_ccb->ccb_priority = priority;
l2cu_enqueue_ccb(p_ccb);
}
+#if (L2CAP_ROUND_ROBIN_CHANNEL_SERVICE == TRUE)
else {
/* If CCB is the only guy on the queue, no need to re-enqueue */
/* update only round robin service data */
@@ -1334,6 +1354,7 @@ void l2cu_change_pri_ccb(tL2C_CCB* p_ccb, tL2CAP_CHNL_PRIORITY priority) {
L2CAP_GET_PRIORITY_QUOTA(p_ccb->ccb_priority);
p_ccb->p_lcb->rr_serv[p_ccb->ccb_priority].num_ccb = 1;
}
+#endif
}
}
@@ -1349,44 +1370,46 @@ void l2cu_change_pri_ccb(tL2C_CCB* p_ccb, tL2CAP_CHNL_PRIORITY priority) {
*
******************************************************************************/
tL2C_CCB* l2cu_allocate_ccb(tL2C_LCB* p_lcb, uint16_t cid) {
- LOG_DEBUG("cid 0x%04x", cid);
- if (!l2cb.p_free_ccb_first) {
- LOG_ERROR("First free ccb is null for cid 0x%04x", cid);
- return nullptr;
- }
tL2C_CCB* p_ccb;
+ tL2C_CCB* p_prev;
+
+ L2CAP_TRACE_DEBUG("l2cu_allocate_ccb: cid 0x%04x", cid);
+
+ if (!l2cb.p_free_ccb_first) return (NULL);
+
/* If a CID was passed in, use that, else take the first free one */
if (cid == 0) {
p_ccb = l2cb.p_free_ccb_first;
l2cb.p_free_ccb_first = p_ccb->p_next_ccb;
} else {
- tL2C_CCB* p_prev = nullptr;
+ p_prev = NULL;
p_ccb = &l2cb.ccb_pool[cid - L2CAP_BASE_APPL_CID];
- if (p_ccb == l2cb.p_free_ccb_first) {
+ if (p_ccb == l2cb.p_free_ccb_first)
l2cb.p_free_ccb_first = p_ccb->p_next_ccb;
- } else {
- for (p_prev = l2cb.p_free_ccb_first; p_prev != nullptr;
+ else {
+ for (p_prev = l2cb.p_free_ccb_first; p_prev != NULL;
p_prev = p_prev->p_next_ccb) {
if (p_prev->p_next_ccb == p_ccb) {
p_prev->p_next_ccb = p_ccb->p_next_ccb;
- if (p_ccb == l2cb.p_free_ccb_last) {
- l2cb.p_free_ccb_last = p_prev;
- }
+ if (p_ccb == l2cb.p_free_ccb_last) l2cb.p_free_ccb_last = p_prev;
break;
}
}
- if (p_prev == nullptr) {
- LOG_ERROR("Could not find CCB for CID 0x%04x in the free list", cid);
- return nullptr;
+ if (p_prev == NULL) {
+ L2CAP_TRACE_ERROR(
+ "l2cu_allocate_ccb: could not find CCB for CID 0x%04x in the free "
+ "list",
+ cid);
+ return NULL;
}
}
}
- p_ccb->p_next_ccb = p_ccb->p_prev_ccb = nullptr;
+ p_ccb->p_next_ccb = p_ccb->p_prev_ccb = NULL;
p_ccb->in_use = true;
@@ -1394,19 +1417,23 @@ tL2C_CCB* l2cu_allocate_ccb(tL2C_LCB* p_lcb, uint16_t cid) {
p_ccb->local_cid = L2CAP_BASE_APPL_CID + (uint16_t)(p_ccb - l2cb.ccb_pool);
p_ccb->p_lcb = p_lcb;
- p_ccb->p_rcb = nullptr;
+ p_ccb->p_rcb = NULL;
+ p_ccb->should_free_rcb = false;
/* Set priority then insert ccb into LCB queue (if we have an LCB) */
p_ccb->ccb_priority = L2CAP_CHNL_PRIORITY_LOW;
if (p_lcb) l2cu_enqueue_ccb(p_ccb);
+ /* clear what peer wants to configure */
+ p_ccb->peer_cfg_bits = 0;
+
/* Put in default values for configuration */
memset(&p_ccb->our_cfg, 0, sizeof(tL2CAP_CFG_INFO));
memset(&p_ccb->peer_cfg, 0, sizeof(tL2CAP_CFG_INFO));
/* Put in default values for local/peer configurations */
- p_ccb->our_cfg.flush_to = p_ccb->peer_cfg.flush_to = L2CAP_NO_AUTOMATIC_FLUSH;
+ p_ccb->our_cfg.flush_to = p_ccb->peer_cfg.flush_to = L2CAP_DEFAULT_FLUSH_TO;
p_ccb->our_cfg.mtu = p_ccb->peer_cfg.mtu = L2CAP_DEFAULT_MTU;
p_ccb->our_cfg.qos.service_type = p_ccb->peer_cfg.qos.service_type =
L2CAP_DEFAULT_SERV_TYPE;
@@ -1421,6 +1448,8 @@ tL2C_CCB* l2cu_allocate_ccb(tL2C_LCB* p_lcb, uint16_t cid) {
p_ccb->our_cfg.qos.delay_variation = p_ccb->peer_cfg.qos.delay_variation =
L2CAP_DEFAULT_DELAY;
+ p_ccb->bypass_fcs = 0;
+ memset(&p_ccb->ertm_info, 0, sizeof(tL2CAP_ERTM_INFO));
p_ccb->peer_cfg_already_rejected = false;
p_ccb->fcr_cfg_tries = L2CAP_MAX_FCR_CFG_TRIES;
@@ -1434,9 +1463,16 @@ tL2C_CCB* l2cu_allocate_ccb(tL2C_LCB* p_lcb, uint16_t cid) {
alarm_free(p_ccb->fcrb.mon_retrans_timer);
p_ccb->fcrb.mon_retrans_timer = alarm_new("l2c_fcrb.mon_retrans_timer");
- p_ccb->max_rx_mtu = BT_DEFAULT_BUFFER_SIZE -
- (L2CAP_MIN_OFFSET + L2CAP_SDU_LEN_OFFSET + L2CAP_FCS_LEN);
- p_ccb->tx_mps = BT_DEFAULT_BUFFER_SIZE - 32;
+ p_ccb->ertm_info.preferred_mode =
+ L2CAP_FCR_BASIC_MODE; /* Default mode for channel is basic mode */
+ p_ccb->ertm_info.allowed_modes =
+ L2CAP_FCR_CHAN_OPT_BASIC; /* Default mode for channel is basic mode */
+ p_ccb->ertm_info.fcr_rx_buf_size = L2CAP_FCR_RX_BUF_SIZE;
+ p_ccb->ertm_info.fcr_tx_buf_size = L2CAP_FCR_TX_BUF_SIZE;
+ p_ccb->ertm_info.user_rx_buf_size = L2CAP_USER_RX_BUF_SIZE;
+ p_ccb->ertm_info.user_tx_buf_size = L2CAP_USER_TX_BUF_SIZE;
+ p_ccb->max_rx_mtu = L2CAP_MTU_SIZE;
+ p_ccb->tx_mps = L2CAP_FCR_TX_BUF_SIZE - 32;
p_ccb->xmit_hold_q = fixed_queue_new(SIZE_MAX);
p_ccb->fcrb.srej_rcv_hold_q = fixed_queue_new(SIZE_MAX);
@@ -1447,10 +1483,11 @@ tL2C_CCB* l2cu_allocate_ccb(tL2C_LCB* p_lcb, uint16_t cid) {
p_ccb->buff_quota = 2; /* This gets set after config */
/* If CCB was reserved Config_Done can already have some value */
- if (cid == 0) {
+ if (cid == 0)
p_ccb->config_done = 0;
- } else {
- LOG_DEBUG("cid 0x%04x config_done:0x%x", cid, p_ccb->config_done);
+ else {
+ L2CAP_TRACE_DEBUG("l2cu_allocate_ccb: cid 0x%04x config_done:0x%x", cid,
+ p_ccb->config_done);
}
p_ccb->chnl_state = CST_CLOSED;
@@ -1458,15 +1495,16 @@ tL2C_CCB* l2cu_allocate_ccb(tL2C_LCB* p_lcb, uint16_t cid) {
p_ccb->tx_data_rate = L2CAP_CHNL_DATA_RATE_LOW;
p_ccb->rx_data_rate = L2CAP_CHNL_DATA_RATE_LOW;
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
p_ccb->is_flushable = false;
- p_ccb->ecoc = false;
+#endif
alarm_free(p_ccb->l2c_ccb_timer);
p_ccb->l2c_ccb_timer = alarm_new("l2c.l2c_ccb_timer");
l2c_link_adjust_chnl_allocation();
- return p_ccb;
+ return (p_ccb);
}
/*******************************************************************************
@@ -1483,15 +1521,11 @@ tL2C_CCB* l2cu_allocate_ccb(tL2C_LCB* p_lcb, uint16_t cid) {
*
******************************************************************************/
bool l2cu_start_post_bond_timer(uint16_t handle) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return true;
- }
-
tL2C_LCB* p_lcb = l2cu_find_lcb_by_handle(handle);
if (!p_lcb) return (true);
- p_lcb->ResetBonding();
+ p_lcb->is_bonding = false;
/* Only start timer if no control blocks allocated */
if (p_lcb->ccb_queue.p_first_ccb != NULL) return (false);
@@ -1503,7 +1537,7 @@ bool l2cu_start_post_bond_timer(uint16_t handle) {
uint64_t timeout_ms = L2CAP_BONDING_TIMEOUT * 1000;
if (p_lcb->idle_timeout == 0) {
- acl_disconnect_from_handle(p_lcb->Handle(), HCI_ERR_PEER_USER);
+ btsnd_hcic_disconnect(p_lcb->handle, HCI_ERR_PEER_USER);
p_lcb->link_state = LST_DISCONNECTING;
timeout_ms = L2CAP_LINK_DISCONNECT_TIMEOUT_MS;
}
@@ -1536,13 +1570,21 @@ void l2cu_release_ccb(tL2C_CCB* p_ccb) {
/* If already released, could be race condition */
if (!p_ccb->in_use) return;
- btsnoop_get_interface()->clear_l2cap_allowlist(
- p_lcb->Handle(), p_ccb->local_cid, p_ccb->remote_cid);
+ btsnoop_get_interface()->clear_l2cap_whitelist(
+ p_lcb->handle, p_ccb->local_cid, p_ccb->remote_cid);
if (p_rcb && (p_rcb->psm != p_rcb->real_psm)) {
- BTM_SecClrServiceByPsm(p_rcb->psm);
+ btm_sec_clr_service_by_psm(p_rcb->psm);
}
+ if (p_ccb->should_free_rcb) {
+ osi_free(p_rcb);
+ p_ccb->p_rcb = NULL;
+ p_ccb->should_free_rcb = false;
+ }
+
+ btm_sec_clr_temp_auth_service(p_lcb->remote_bd_addr);
+
/* Free the timer */
alarm_free(p_ccb->l2c_ccb_timer);
p_ccb->l2c_ccb_timer = NULL;
@@ -1809,19 +1851,14 @@ uint8_t l2cu_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
bool flush_to_ok = true;
bool fcr_ok = true;
uint8_t fcr_status;
- uint16_t required_remote_mtu =
- std::max<uint16_t>(L2CAP_MIN_MTU, p_ccb->p_rcb->required_remote_mtu);
/* Ignore FCR parameters for basic mode */
if (!p_cfg->fcr_present) p_cfg->fcr.mode = L2CAP_FCR_BASIC_MODE;
- if (!p_cfg->mtu_present && required_remote_mtu > L2CAP_DEFAULT_MTU) {
- // We reject if we have a MTU requirement higher than default MTU
- p_cfg->mtu = required_remote_mtu;
- mtu_ok = false;
- } else if (p_cfg->mtu_present) {
+ /* Save the MTU that our peer can receive */
+ if (p_cfg->mtu_present) {
/* Make sure MTU is at least the minimum */
- if (p_cfg->mtu >= required_remote_mtu) {
+ if (p_cfg->mtu >= L2CAP_MIN_MTU) {
/* In basic mode, limit the MTU to our buffer size */
if ((!p_cfg->fcr_present) && (p_cfg->mtu > L2CAP_MTU_SIZE))
p_cfg->mtu = L2CAP_MTU_SIZE;
@@ -1829,14 +1866,15 @@ uint8_t l2cu_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
/* Save the accepted value in case of renegotiation */
p_ccb->peer_cfg.mtu = p_cfg->mtu;
p_ccb->peer_cfg.mtu_present = true;
+ p_ccb->peer_cfg_bits |= L2CAP_CH_CFG_MASK_MTU;
} else /* Illegal MTU value */
{
- p_cfg->mtu = required_remote_mtu;
+ p_cfg->mtu = L2CAP_MIN_MTU;
mtu_ok = false;
}
}
/* Reload mtu from a previously accepted config request */
- else if (p_ccb->peer_cfg.mtu_present && !(p_ccb->config_done & IB_CFG_DONE)) {
+ else if (p_ccb->peer_cfg.mtu_present) {
p_cfg->mtu_present = true;
p_cfg->mtu = p_ccb->peer_cfg.mtu;
}
@@ -1850,11 +1888,11 @@ uint8_t l2cu_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
{
p_ccb->peer_cfg.flush_to_present = true;
p_ccb->peer_cfg.flush_to = p_cfg->flush_to;
+ p_ccb->peer_cfg_bits |= L2CAP_CH_CFG_MASK_FLUSH_TO;
}
}
/* Reload flush_to from a previously accepted config request */
- else if (p_ccb->peer_cfg.flush_to_present &&
- !(p_ccb->config_done & IB_CFG_DONE)) {
+ else if (p_ccb->peer_cfg.flush_to_present) {
p_cfg->flush_to_present = true;
p_cfg->flush_to = p_ccb->peer_cfg.flush_to;
}
@@ -1867,6 +1905,7 @@ uint8_t l2cu_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
if (p_cfg->qos.service_type <= SVC_TYPE_GUARANTEED) {
p_ccb->peer_cfg.qos = p_cfg->qos;
p_ccb->peer_cfg.qos_present = true;
+ p_ccb->peer_cfg_bits |= L2CAP_CH_CFG_MASK_QOS;
} else /* Illegal service type value */
{
p_cfg->qos.service_type = SVC_TYPE_BEST_EFFORT;
@@ -1874,7 +1913,7 @@ uint8_t l2cu_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
}
}
/* Reload QOS from a previously accepted config request */
- else if (p_ccb->peer_cfg.qos_present && !(p_ccb->config_done & IB_CFG_DONE)) {
+ else if (p_ccb->peer_cfg.qos_present) {
p_cfg->qos_present = true;
p_cfg->qos = p_ccb->peer_cfg.qos;
}
@@ -1957,6 +1996,9 @@ void l2cu_process_peer_cfg_rsp(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
*
******************************************************************************/
void l2cu_process_our_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
+ tL2C_LCB* p_lcb;
+ uint16_t hci_flush_to;
+
/* Save the QOS settings we are using for transmit */
if (p_cfg->qos_present) {
p_ccb->our_cfg.qos_present = true;
@@ -1974,21 +2016,54 @@ void l2cu_process_our_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
/* timer value in config response shall be greater than
* received processing time */
p_cfg->fcr.mon_tout = p_cfg->fcr.rtrans_tout = 0;
+
+ if (p_cfg->fcr.mode == L2CAP_FCR_STREAM_MODE)
+ p_cfg->fcr.max_transmit = p_cfg->fcr.tx_win_sz = 0;
}
/* Set the threshold to send acks (may be updated in the cfg response) */
p_ccb->fcrb.max_held_acks = p_cfg->fcr.tx_win_sz / 3;
/* Include FCS option only if peer can handle it */
- if ((p_ccb->p_lcb->peer_ext_fea & L2CAP_EXTFEA_NO_CRC) == 0) {
+ if (p_ccb->p_lcb->peer_ext_fea & L2CAP_EXTFEA_NO_CRC) {
+ /* FCS check can be bypassed if peer also desires to bypass */
+ if (p_cfg->fcs_present && p_cfg->fcs == L2CAP_CFG_FCS_BYPASS)
+ p_ccb->bypass_fcs |= L2CAP_CFG_FCS_OUR;
+ } else
p_cfg->fcs_present = false;
- }
} else {
p_cfg->fcr.mode = L2CAP_FCR_BASIC_MODE;
}
p_ccb->our_cfg.fcr.mode = p_cfg->fcr.mode;
p_ccb->our_cfg.fcr_present = p_cfg->fcr_present;
+
+ /* Check the flush timeout. If it is lower than the current one used */
+ /* then we need to adjust the flush timeout sent to the controller */
+ if (p_cfg->flush_to_present) {
+ if ((p_cfg->flush_to == 0) ||
+ (p_cfg->flush_to == L2CAP_NO_AUTOMATIC_FLUSH)) {
+ /* don't send invalid flush timeout */
+ /* SPEC: The sender of the Request shall specify its flush timeout value
+ */
+ /* if it differs from the default value of 0xFFFF */
+ p_cfg->flush_to_present = false;
+ } else {
+ p_ccb->our_cfg.flush_to = p_cfg->flush_to;
+ p_lcb = p_ccb->p_lcb;
+
+ if (p_cfg->flush_to < p_lcb->link_flush_tout) {
+ p_lcb->link_flush_tout = p_cfg->flush_to;
+
+ /* If the timeout is within range of HCI, set the flush timeout */
+ if (p_cfg->flush_to <= ((HCI_MAX_AUTOMATIC_FLUSH_TIMEOUT * 5) / 8)) {
+ /* Convert flush timeout to 0.625 ms units, with round */
+ hci_flush_to = ((p_cfg->flush_to * 8) + 3) / 5;
+ btsnd_hcic_write_auto_flush_tout(p_lcb->handle, hci_flush_to);
+ }
+ }
+ }
+ }
}
/*******************************************************************************
@@ -2024,70 +2099,86 @@ void l2cu_process_our_cfg_rsp(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
*
******************************************************************************/
void l2cu_device_reset(void) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return;
- }
-
int xx;
tL2C_LCB* p_lcb = &l2cb.lcb_pool[0];
for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p_lcb++) {
- if ((p_lcb->in_use) && (p_lcb->Handle() != HCI_INVALID_HANDLE)) {
- l2c_link_hci_disc_comp(p_lcb->Handle(), HCI_ERR_UNDEFINED);
+ if ((p_lcb->in_use) && (p_lcb->handle != HCI_INVALID_HANDLE)) {
+ l2c_link_hci_disc_comp(p_lcb->handle, (uint8_t)-1);
}
}
}
+bool l2cu_create_conn_le(tL2C_LCB* p_lcb) {
+ uint8_t phy = controller_get_interface()->get_le_all_initiating_phys();
+ return l2cu_create_conn_le(p_lcb, phy);
+}
+
/* This function initiates an acl connection to a LE device.
* Returns true if request started successfully, false otherwise. */
-bool l2cu_create_conn_le(tL2C_LCB* p_lcb) {
+bool l2cu_create_conn_le(tL2C_LCB* p_lcb, uint8_t initiating_phys) {
+ tBT_DEVICE_TYPE dev_type;
+ tBLE_ADDR_TYPE addr_type;
+
+ BTM_ReadDevInfo(p_lcb->remote_bd_addr, &dev_type, &addr_type);
+
if (!controller_get_interface()->supports_ble()) return false;
+
+ p_lcb->ble_addr_type = addr_type;
p_lcb->transport = BT_TRANSPORT_LE;
+ p_lcb->initiating_phys = initiating_phys;
+
return (l2cble_create_conn(p_lcb));
}
-/* This function initiates an acl connection to a Classic device via HCI. */
-void l2cu_create_conn_br_edr(tL2C_LCB* p_lcb) {
- const bool controller_supports_role_switch =
- controller_get_interface()->supports_role_switch();
-
- /* While creating a new classic connection, check check all the other
- * active connections where we are not SCO nor central.
- * If our controller supports role switching, try switching
- * roles back to CENTRAL on those connections.
- */
+/* This function initiates an acl connection to a Classic device via HCI.
+ * Returns true on success, false otherwise. */
+bool l2cu_create_conn_br_edr(tL2C_LCB* p_lcb) {
+ int xx;
tL2C_LCB* p_lcb_cur = &l2cb.lcb_pool[0];
- for (uint8_t xx = 0; xx < MAX_L2CAP_LINKS; xx++, p_lcb_cur++) {
+ bool is_sco_active;
+
+ /* If there is a connection where we perform as a slave, try to switch roles
+ for this connection */
+ for (xx = 0, p_lcb_cur = &l2cb.lcb_pool[0]; xx < MAX_L2CAP_LINKS;
+ xx++, p_lcb_cur++) {
if (p_lcb_cur == p_lcb) continue;
- if (!p_lcb_cur->in_use) continue;
- if (BTM_IsScoActiveByBdaddr(p_lcb_cur->remote_bd_addr)) {
- L2CAP_TRACE_DEBUG(
- "%s Central peripheral switch not allowed when SCO active", __func__);
- continue;
- }
- if (p_lcb->IsLinkRoleCentral()) continue;
- /* The LMP_switch_req shall be sent only if the ACL logical transport
- is in active mode, when encryption is disabled, and all synchronous
- logical transports on the same physical link are disabled." */
-
- /*4_1_TODO check if btm_cb.devcb.local_features to be used instead */
- if (controller_supports_role_switch) {
- /* mark this lcb waiting for switch to be completed and
- start switch on the other one */
- p_lcb->link_state = LST_CONNECTING_WAIT_SWITCH;
- p_lcb->SetLinkRoleAsCentral();
-
- if (BTM_SwitchRoleToCentral(p_lcb_cur->remote_bd_addr) ==
- BTM_CMD_STARTED) {
- alarm_set_on_mloop(p_lcb->l2c_lcb_timer,
- L2CAP_LINK_ROLE_SWITCH_TIMEOUT_MS,
- l2c_lcb_timer_timeout, p_lcb);
- return;
+
+ if ((p_lcb_cur->in_use) && (p_lcb_cur->link_role == HCI_ROLE_SLAVE)) {
+ /* The LMP_switch_req shall be sent only if the ACL logical transport
+ is in active mode, when encryption is disabled, and all synchronous
+ logical transports on the same physical link are disabled." */
+
+ /* Check if there is any SCO Active on this BD Address */
+ is_sco_active = btm_is_sco_active_by_bdaddr(p_lcb_cur->remote_bd_addr);
+
+ L2CAP_TRACE_API(
+ "l2cu_create_conn - btm_is_sco_active_by_bdaddr() is_sco_active = %s",
+ (is_sco_active) ? "true" : "false");
+
+ if (is_sco_active)
+ continue; /* No Master Slave switch not allowed when SCO Active */
+ /*4_1_TODO check if btm_cb.devcb.local_features to be used instead */
+ if (HCI_SWITCH_SUPPORTED(BTM_ReadLocalFeatures())) {
+ /* mark this lcb waiting for switch to be completed and
+ start switch on the other one */
+ p_lcb->link_state = LST_CONNECTING_WAIT_SWITCH;
+ p_lcb->link_role = HCI_ROLE_MASTER;
+
+ if (BTM_SwitchRole(p_lcb_cur->remote_bd_addr, HCI_ROLE_MASTER, NULL) ==
+ BTM_CMD_STARTED) {
+ alarm_set_on_mloop(p_lcb->l2c_lcb_timer,
+ L2CAP_LINK_ROLE_SWITCH_TIMEOUT_MS,
+ l2c_lcb_timer_timeout, p_lcb);
+ return (true);
+ }
}
}
}
+
p_lcb->link_state = LST_CONNECTING;
- l2cu_create_conn_after_switch(p_lcb);
+
+ return (l2cu_create_conn_after_switch(p_lcb));
}
/*******************************************************************************
@@ -2116,20 +2207,68 @@ uint8_t l2cu_get_num_hi_priority(void) {
*
* Function l2cu_create_conn_after_switch
*
- * Description This continues a connection creation possibly after
- * a role switch.
+ * Description This function initiates an acl connection via HCI
+ * If switch required to create connection it is already done.
+ *
+ * Returns true if successful, false if get buffer fails.
*
******************************************************************************/
-void l2cu_create_conn_after_switch(tL2C_LCB* p_lcb) {
- const bool there_are_high_priority_channels =
- (l2cu_get_num_hi_priority() > 0);
- acl_create_classic_connection(p_lcb->remote_bd_addr,
- there_are_high_priority_channels,
- p_lcb->IsBonding());
+bool l2cu_create_conn_after_switch(tL2C_LCB* p_lcb) {
+ uint8_t allow_switch = HCI_CR_CONN_ALLOW_SWITCH;
+ tBTM_INQ_INFO* p_inq_info;
+ uint8_t page_scan_rep_mode;
+ uint8_t page_scan_mode;
+ uint16_t clock_offset;
+ uint8_t* p_features;
+ uint16_t num_acl = BTM_GetNumAclLinks();
+ tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(p_lcb->remote_bd_addr);
+ uint8_t no_hi_prio_chs = l2cu_get_num_hi_priority();
+
+ p_features = BTM_ReadLocalFeatures();
+
+ L2CAP_TRACE_DEBUG(
+ "l2cu_create_conn_after_switch :%d num_acl:%d no_hi: %d is_bonding:%d",
+ l2cb.disallow_switch, num_acl, no_hi_prio_chs, p_lcb->is_bonding);
+ /* FW team says that we can participant in 4 piconets
+ * typically 3 piconet + 1 for scanning.
+ * We can enhance the code to count the number of piconets later. */
+ if (((!l2cb.disallow_switch && (num_acl < 3)) ||
+ (p_lcb->is_bonding && (no_hi_prio_chs == 0))) &&
+ HCI_SWITCH_SUPPORTED(p_features))
+ allow_switch = HCI_CR_CONN_ALLOW_SWITCH;
+ else
+ allow_switch = HCI_CR_CONN_NOT_ALLOW_SWITCH;
+
+ p_lcb->link_state = LST_CONNECTING;
+
+ /* Check with the BT manager if details about remote device are known */
+ p_inq_info = BTM_InqDbRead(p_lcb->remote_bd_addr);
+ if ((p_inq_info != NULL) &&
+ (p_inq_info->results.inq_result_type & BTM_INQ_RESULT_BR)) {
+ page_scan_rep_mode = p_inq_info->results.page_scan_rep_mode;
+ page_scan_mode = p_inq_info->results.page_scan_mode;
+ clock_offset = (uint16_t)(p_inq_info->results.clock_offset);
+ } else {
+ /* No info known. Use default settings */
+ page_scan_rep_mode = HCI_PAGE_SCAN_REP_MODE_R1;
+ page_scan_mode = HCI_MANDATARY_PAGE_SCAN_MODE;
+
+ clock_offset = (p_dev_rec) ? p_dev_rec->clock_offset : 0;
+ }
+
+ btsnd_hcic_create_conn(
+ p_lcb->remote_bd_addr, (HCI_PKT_TYPES_MASK_DM1 | HCI_PKT_TYPES_MASK_DH1 |
+ HCI_PKT_TYPES_MASK_DM3 | HCI_PKT_TYPES_MASK_DH3 |
+ HCI_PKT_TYPES_MASK_DM5 | HCI_PKT_TYPES_MASK_DH5),
+ page_scan_rep_mode, page_scan_mode, clock_offset, allow_switch);
+
+ btm_acl_update_busy_level(BTM_BLI_PAGE_EVT);
alarm_set_on_mloop(p_lcb->l2c_lcb_timer, L2CAP_LINK_CONNECT_TIMEOUT_MS,
l2c_lcb_timer_timeout, p_lcb);
+
+ return (true);
}
/*******************************************************************************
@@ -2212,7 +2351,7 @@ bool l2cu_lcb_disconnecting(void) {
*
******************************************************************************/
-bool l2cu_set_acl_priority(const RawAddress& bd_addr, tL2CAP_PRIORITY priority,
+bool l2cu_set_acl_priority(const RawAddress& bd_addr, uint8_t priority,
bool reset_after_rs) {
tL2C_LCB* p_lcb;
uint8_t* pp;
@@ -2228,19 +2367,17 @@ bool l2cu_set_acl_priority(const RawAddress& bd_addr, tL2CAP_PRIORITY priority,
return (false);
}
- if (controller_get_interface()->get_bt_version()->manufacturer ==
- LMP_COMPID_BROADCOM) {
+ if (BTM_IS_BRCM_CONTROLLER()) {
/* Called from above L2CAP through API; send VSC if changed */
if ((!reset_after_rs && (priority != p_lcb->acl_priority)) ||
- /* Called because of a central/peripheral role switch; if high resend
- VSC */
+ /* Called because of a master/slave role switch; if high resend VSC */
(reset_after_rs && p_lcb->acl_priority == L2CAP_PRIORITY_HIGH)) {
pp = command;
vs_param = (priority == L2CAP_PRIORITY_HIGH) ? HCI_BRCM_ACL_PRIORITY_HIGH
: HCI_BRCM_ACL_PRIORITY_LOW;
- UINT16_TO_STREAM(pp, p_lcb->Handle());
+ UINT16_TO_STREAM(pp, p_lcb->handle);
UINT8_TO_STREAM(pp, vs_param);
BTM_VendorSpecificCommand(HCI_BRCM_SET_ACL_PRIORITY,
@@ -2257,6 +2394,7 @@ bool l2cu_set_acl_priority(const RawAddress& bd_addr, tL2CAP_PRIORITY priority,
return (true);
}
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
/******************************************************************************
*
* Function l2cu_set_non_flushable_pbf
@@ -2267,16 +2405,13 @@ bool l2cu_set_acl_priority(const RawAddress& bd_addr, tL2CAP_PRIORITY priority,
*
******************************************************************************/
void l2cu_set_non_flushable_pbf(bool is_supported) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- return;
- }
-
if (is_supported)
l2cb.non_flushable_pbf =
(L2CAP_PKT_START_NON_FLUSHABLE << L2CAP_PKT_TYPE_SHIFT);
else
l2cb.non_flushable_pbf = (L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT);
}
+#endif
/*******************************************************************************
*
@@ -2289,11 +2424,6 @@ void l2cu_set_non_flushable_pbf(bool is_supported) {
*
******************************************************************************/
void l2cu_resubmit_pending_sec_req(const RawAddress* p_bda) {
- if (bluetooth::shim::is_gd_l2cap_enabled()) {
- // GD L2cap will enforce security when condition changed
- return;
- }
-
tL2C_LCB* p_lcb;
tL2C_CCB* p_ccb;
tL2C_CCB* p_next_ccb;
@@ -2357,7 +2487,7 @@ void l2cu_adjust_out_mps(tL2C_CCB* p_ccb) {
uint16_t packet_size;
/* on the tx side MTU is selected based on packet size of the controller */
- packet_size = BTM_GetMaxPacketSize(p_ccb->p_lcb->remote_bd_addr);
+ packet_size = btm_get_max_packet_size(p_ccb->p_lcb->remote_bd_addr);
if (packet_size <= (L2CAP_PKT_OVERHEAD + L2CAP_FCR_OVERHEAD +
L2CAP_SDU_LEN_OVERHEAD + L2CAP_FCS_LEN)) {
@@ -2402,7 +2532,9 @@ void l2cu_adjust_out_mps(tL2C_CCB* p_ccb) {
* Returns true or false
*
******************************************************************************/
-bool l2cu_initialize_fixed_ccb(tL2C_LCB* p_lcb, uint16_t fixed_cid) {
+bool l2cu_initialize_fixed_ccb(tL2C_LCB* p_lcb, uint16_t fixed_cid,
+ tL2CAP_FCR_OPTS* p_fcr) {
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
tL2C_CCB* p_ccb;
/* If we already have a CCB, then simply return */
@@ -2426,6 +2558,18 @@ bool l2cu_initialize_fixed_ccb(tL2C_LCB* p_lcb, uint16_t fixed_cid) {
p_ccb->is_flushable = false;
+ if (p_fcr) {
+ /* Set the FCR parameters. For now, we will use default pools */
+ p_ccb->our_cfg.fcr = p_ccb->peer_cfg.fcr = *p_fcr;
+
+ p_ccb->ertm_info.fcr_rx_buf_size = L2CAP_FCR_RX_BUF_SIZE;
+ p_ccb->ertm_info.fcr_tx_buf_size = L2CAP_FCR_TX_BUF_SIZE;
+ p_ccb->ertm_info.user_rx_buf_size = L2CAP_USER_RX_BUF_SIZE;
+ p_ccb->ertm_info.user_tx_buf_size = L2CAP_USER_TX_BUF_SIZE;
+
+ p_ccb->fcrb.max_held_acks = p_fcr->tx_win_sz / 3;
+ }
+
/* Link ccb to lcb and lcb to ccb */
p_lcb->p_fixed_ccbs[fixed_cid - L2CAP_FIRST_FIXED_CHNL] = p_ccb;
p_ccb->p_lcb = p_lcb;
@@ -2436,6 +2580,7 @@ bool l2cu_initialize_fixed_ccb(tL2C_LCB* p_lcb, uint16_t fixed_cid) {
/* Set the default idle timeout value to use */
p_ccb->fixed_chnl_idle_tout =
l2cb.fixed_reg[fixed_cid - L2CAP_FIRST_FIXED_CHNL].default_idle_tout;
+#endif
return (true);
}
@@ -2456,6 +2601,7 @@ void l2cu_no_dynamic_ccbs(tL2C_LCB* p_lcb) {
uint64_t timeout_ms = p_lcb->idle_timeout * 1000;
bool start_timeout = true;
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
int xx;
for (xx = 0; xx < L2CAP_NUM_FIXED_CHNLS; xx++) {
@@ -2470,15 +2616,16 @@ void l2cu_no_dynamic_ccbs(tL2C_LCB* p_lcb) {
timeout_ms = p_lcb->p_fixed_ccbs[xx]->fixed_chnl_idle_tout * 1000;
}
}
+#endif
/* If the link is pairing, do not mess with the timeouts */
- if (p_lcb->IsBonding()) return;
+ if (p_lcb->is_bonding) return;
if (timeout_ms == 0) {
L2CAP_TRACE_DEBUG(
"l2cu_no_dynamic_ccbs() IDLE timer 0, disconnecting link");
- rc = btm_sec_disconnect(p_lcb->Handle(), HCI_ERR_PEER_USER);
+ rc = btm_sec_disconnect(p_lcb->handle, HCI_ERR_PEER_USER);
if (rc == BTM_CMD_STARTED) {
l2cu_process_fixed_disc_cback(p_lcb);
p_lcb->link_state = LST_DISCONNECTING;
@@ -2489,8 +2636,8 @@ void l2cu_no_dynamic_ccbs(tL2C_LCB* p_lcb) {
* done) */
p_lcb->link_state = LST_DISCONNECTING;
start_timeout = false;
- } else if (p_lcb->IsBonding()) {
- acl_disconnect_from_handle(p_lcb->Handle(), HCI_ERR_PEER_USER);
+ } else if (p_lcb->is_bonding) {
+ btsnd_hcic_disconnect(p_lcb->handle, HCI_ERR_PEER_USER);
l2cu_process_fixed_disc_cback(p_lcb);
p_lcb->link_state = LST_DISCONNECTING;
timeout_ms = L2CAP_LINK_DISCONNECT_TIMEOUT_MS;
@@ -2509,6 +2656,7 @@ void l2cu_no_dynamic_ccbs(tL2C_LCB* p_lcb) {
}
}
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
/*******************************************************************************
*
* Function l2cu_process_fixed_chnl_resp
@@ -2551,7 +2699,7 @@ void l2cu_process_fixed_chnl_resp(tL2C_LCB* p_lcb) {
channel_id, p_lcb->remote_bd_addr, true, 0, p_lcb->transport);
} else {
(*l2cb.fixed_reg[xx].pL2CA_FixedConn_Cb)(
- channel_id, p_lcb->remote_bd_addr, false, p_lcb->DisconnectReason(),
+ channel_id, p_lcb->remote_bd_addr, false, p_lcb->disc_reason,
p_lcb->transport);
if (p_lcb->p_fixed_ccbs[xx]) {
@@ -2561,6 +2709,7 @@ void l2cu_process_fixed_chnl_resp(tL2C_LCB* p_lcb) {
}
}
}
+#endif
/*******************************************************************************
*
@@ -2573,6 +2722,7 @@ void l2cu_process_fixed_chnl_resp(tL2C_LCB* p_lcb) {
*
******************************************************************************/
void l2cu_process_fixed_disc_cback(tL2C_LCB* p_lcb) {
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
/* Select peer channels mask to use depending on transport */
uint8_t peer_channel_mask = p_lcb->peer_chnl_mask[0];
@@ -2589,14 +2739,15 @@ void l2cu_process_fixed_disc_cback(tL2C_LCB* p_lcb) {
l2cu_release_ccb(p_l2c_chnl_ctrl_block);
(*l2cb.fixed_reg[xx].pL2CA_FixedConn_Cb)(
xx + L2CAP_FIRST_FIXED_CHNL, p_lcb->remote_bd_addr, false,
- p_lcb->DisconnectReason(), p_lcb->transport);
+ p_lcb->disc_reason, p_lcb->transport);
}
} else if ((peer_channel_mask & (1 << (xx + L2CAP_FIRST_FIXED_CHNL))) &&
(l2cb.fixed_reg[xx].pL2CA_FixedConn_Cb != NULL))
(*l2cb.fixed_reg[xx].pL2CA_FixedConn_Cb)(
xx + L2CAP_FIRST_FIXED_CHNL, p_lcb->remote_bd_addr, false,
- p_lcb->DisconnectReason(), p_lcb->transport);
+ p_lcb->disc_reason, p_lcb->transport);
}
+#endif
}
/*******************************************************************************
@@ -2616,11 +2767,11 @@ void l2cu_send_peer_ble_par_req(tL2C_LCB* p_lcb, uint16_t min_int,
uint8_t* p;
/* Create an identifier for this packet */
- p_lcb->signal_id++;
- l2cu_adj_id(p_lcb);
+ p_lcb->id++;
+ l2cu_adj_id(p_lcb, L2CAP_ADJ_ID);
p_buf = l2cu_build_header(p_lcb, L2CAP_CMD_BLE_UPD_REQ_LEN,
- L2CAP_CMD_BLE_UPDATE_REQ, p_lcb->signal_id);
+ L2CAP_CMD_BLE_UPDATE_REQ, p_lcb->id);
if (p_buf == NULL) {
L2CAP_TRACE_WARNING("l2cu_send_peer_ble_par_req - no buffer");
return;
@@ -2634,7 +2785,7 @@ void l2cu_send_peer_ble_par_req(tL2C_LCB* p_lcb, uint16_t min_int,
UINT16_TO_STREAM(p, latency);
UINT16_TO_STREAM(p, timeout);
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -2664,7 +2815,7 @@ void l2cu_send_peer_ble_par_rsp(tL2C_LCB* p_lcb, uint16_t reason,
UINT16_TO_STREAM(p, reason);
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -2689,14 +2840,13 @@ void l2cu_send_peer_ble_credit_based_conn_req(tL2C_CCB* p_ccb) {
p_lcb = p_ccb->p_lcb;
/* Create an identifier for this packet */
- p_ccb->p_lcb->signal_id++;
- l2cu_adj_id(p_ccb->p_lcb);
+ p_ccb->p_lcb->id++;
+ l2cu_adj_id(p_ccb->p_lcb, L2CAP_ADJ_ID);
- p_ccb->local_id = p_ccb->p_lcb->signal_id;
+ p_ccb->local_id = p_ccb->p_lcb->id;
- p_buf =
- l2cu_build_header(p_lcb, L2CAP_CMD_BLE_CREDIT_BASED_CONN_REQ_LEN,
- L2CAP_CMD_BLE_CREDIT_BASED_CONN_REQ, p_lcb->signal_id);
+ p_buf = l2cu_build_header(p_lcb, L2CAP_CMD_BLE_CREDIT_BASED_CONN_REQ_LEN,
+ L2CAP_CMD_BLE_CREDIT_BASED_CONN_REQ, p_lcb->id);
if (p_buf == NULL) {
L2CAP_TRACE_WARNING("l2cu_send_peer_ble_credit_based_conn_req - no buffer");
return;
@@ -2720,75 +2870,12 @@ void l2cu_send_peer_ble_credit_based_conn_req(tL2C_CCB* p_ccb) {
UINT16_TO_STREAM(p, mps);
UINT16_TO_STREAM(p, initial_credit);
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/*******************************************************************************
*
- * Function l2cu_send_peer_credit_based_conn_req
- *
- * Description Build and send a BLE packet to establish enhanced connection
- * oriented L2CAP channel.
- *
- * Returns void
- *
- ******************************************************************************/
-void l2cu_send_peer_credit_based_conn_req(tL2C_CCB* p_ccb) {
- BT_HDR* p_buf;
- uint8_t* p;
- tL2C_LCB* p_lcb = NULL;
- uint16_t mtu;
- uint16_t mps;
- uint16_t initial_credit;
-
- if (!p_ccb) return;
-
- p_lcb = p_ccb->p_lcb;
-
- /* Create an identifier for this packet */
- p_ccb->p_lcb->signal_id++;
- l2cu_adj_id(p_ccb->p_lcb);
-
- p_ccb->local_id = p_lcb->signal_id;
-
- p_buf = l2cu_build_header(p_lcb,
- L2CAP_CMD_CREDIT_BASED_CONN_REQ_MIN_LEN +
- 2 * p_lcb->pending_ecoc_conn_cnt,
- L2CAP_CMD_CREDIT_BASED_CONN_REQ, p_ccb->local_id);
- if (p_buf == NULL) {
- L2CAP_TRACE_WARNING("%s - no buffer", __func__);
- return;
- }
-
- p = (uint8_t*)(p_buf + 1) + L2CAP_SEND_CMD_OFFSET + HCI_DATA_PREAMBLE_SIZE +
- L2CAP_PKT_OVERHEAD + L2CAP_CMD_OVERHEAD;
-
- mtu = p_ccb->local_conn_cfg.mtu;
- mps = p_ccb->local_conn_cfg.mps;
- initial_credit = p_ccb->local_conn_cfg.credits;
-
- L2CAP_TRACE_DEBUG(
- "%s PSM:0x%04x mtu:%d mps:%d initial_credit:%d, cids_cnt %d", __func__,
- p_ccb->p_rcb->real_psm, mtu, mps, initial_credit,
- p_lcb->pending_ecoc_conn_cnt);
-
- UINT16_TO_STREAM(p, p_ccb->p_rcb->real_psm);
- UINT16_TO_STREAM(p, mtu);
- UINT16_TO_STREAM(p, mps);
- UINT16_TO_STREAM(p, initial_credit);
-
- for (int i = 0; i < p_lcb->pending_ecoc_conn_cnt; i++) {
- uint16_t cid = p_lcb->pending_ecoc_connection_cids[i];
- L2CAP_TRACE_DEBUG("\n\t cid: ", cid);
- UINT16_TO_STREAM(p, cid);
- }
-
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
-}
-
-/*******************************************************************************
- *
- * Function l2cu_reject_ble_coc_connection
+ * Function l2cu_reject_ble_connection
*
* Description Build and send an L2CAP "Credit based connection res"
* message to the peer. This function is called for non-success
@@ -2797,15 +2884,15 @@ void l2cu_send_peer_credit_based_conn_req(tL2C_CCB* p_ccb) {
* Returns void
*
******************************************************************************/
-void l2cu_reject_ble_coc_connection(tL2C_LCB* p_lcb, uint8_t rem_id,
- uint16_t result) {
+void l2cu_reject_ble_connection(tL2C_LCB* p_lcb, uint8_t rem_id,
+ uint16_t result) {
BT_HDR* p_buf;
uint8_t* p;
p_buf = l2cu_build_header(p_lcb, L2CAP_CMD_BLE_CREDIT_BASED_CONN_RES_LEN,
L2CAP_CMD_BLE_CREDIT_BASED_CONN_RES, rem_id);
if (p_buf == NULL) {
- L2CAP_TRACE_WARNING("l2cu_reject_ble_coc_connection - no buffer");
+ L2CAP_TRACE_WARNING("l2cu_reject_ble_connection - no buffer");
return;
}
@@ -2818,168 +2905,7 @@ void l2cu_reject_ble_coc_connection(tL2C_LCB* p_lcb, uint8_t rem_id,
UINT16_TO_STREAM(p, 0); /* initial credit */
UINT16_TO_STREAM(p, result);
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
-}
-
-/*******************************************************************************
- *
- * Function l2cu_reject_credit_based_connection_req
- *
- * Description Build and send an L2CAP "credit based connection
- *res" message to the peer. This function is called for non-success cases.
- *
- * Returns void
- *
- ******************************************************************************/
-void l2cu_reject_credit_based_conn_req(tL2C_LCB* p_lcb, uint8_t rem_id,
- uint8_t num_of_channels,
- uint16_t result) {
- BT_HDR* p_buf;
- uint8_t* p;
- uint8_t rsp_len = L2CAP_CMD_CREDIT_BASED_CONN_RES_MIN_LEN +
- sizeof(uint16_t) * num_of_channels;
-
- p_buf = l2cu_build_header(p_lcb, rsp_len, L2CAP_CMD_CREDIT_BASED_CONN_RES,
- rem_id);
- if (p_buf == NULL) {
- L2CAP_TRACE_WARNING("l2cu_reject_credit_based_conn_req - no buffer");
- return;
- }
-
- p = (uint8_t*)(p_buf + 1) + L2CAP_SEND_CMD_OFFSET + HCI_DATA_PREAMBLE_SIZE +
- L2CAP_PKT_OVERHEAD + L2CAP_CMD_OVERHEAD;
-
- memset(p, 0, rsp_len);
- UINT16_TO_STREAM(p, L2CAP_CREDIT_BASED_MIN_MTU); /* dummy MTU to satisy PTS */
- UINT16_TO_STREAM(p, L2CAP_CREDIT_BASED_MIN_MPS); /* dummy MPS to satisy PTS*/
- UINT16_TO_STREAM(p, 1); /* dummy initial credit to satisy PTS */
- UINT16_TO_STREAM(p, result);
-
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
-}
-
-/*******************************************************************************
- *
- * Function l2cu_send_peer_credit_based_conn_res
- *
- * Description Build and send an L2CAP "Credit based connection res"
- * message to the peer. This function is called in case of
- * success.
- *
- * Returns void
- *
- ******************************************************************************/
-void l2cu_send_peer_credit_based_conn_res(tL2C_CCB* p_ccb,
- std::vector<uint16_t>& accepted_cids,
- uint16_t result) {
- BT_HDR* p_buf;
- uint8_t* p;
-
- L2CAP_TRACE_DEBUG("%s", __func__);
- uint8_t rsp_len = L2CAP_CMD_CREDIT_BASED_CONN_RES_MIN_LEN +
- p_ccb->p_lcb->pending_ecoc_conn_cnt * sizeof(uint16_t);
-
- p_buf = l2cu_build_header(p_ccb->p_lcb, rsp_len,
- L2CAP_CMD_CREDIT_BASED_CONN_RES, p_ccb->remote_id);
- if (p_buf == NULL) {
- L2CAP_TRACE_WARNING("%s - no buffer", __func__);
- return;
- }
-
- p = (uint8_t*)(p_buf + 1) + L2CAP_SEND_CMD_OFFSET + HCI_DATA_PREAMBLE_SIZE +
- L2CAP_PKT_OVERHEAD + L2CAP_CMD_OVERHEAD;
-
- memset(p, 0, rsp_len);
- UINT16_TO_STREAM(p, p_ccb->local_conn_cfg.mtu); /* MTU */
- UINT16_TO_STREAM(p, p_ccb->local_conn_cfg.mps); /* MPS */
- UINT16_TO_STREAM(p, p_ccb->local_conn_cfg.credits); /* initial credit */
-
- if (result == L2CAP_CONN_OK) {
- /* In case of success, we need to check if stack
- * did not have previous result stored e.g. when there was no
- * resources for allocation all the requrested channels,
- * before user indication.
- */
- result = p_ccb->p_lcb->pending_l2cap_result;
- }
-
- UINT16_TO_STREAM(p, result);
-
- /* We need to keep order from the request.
- * if this vector contais 0 it means channel has been rejected by
- * the stack.
- * If there is valid cid, we need to verify if it is accepted by upper layer.
- */
- for (int i = 0; i < p_ccb->p_lcb->pending_ecoc_conn_cnt; i++) {
- uint16_t cid = p_ccb->p_lcb->pending_ecoc_connection_cids[i];
- if (cid == 0) {
- UINT16_TO_STREAM(p, 0);
- continue;
- }
- auto it = std::find(accepted_cids.begin(), accepted_cids.end(), cid);
- if (it != accepted_cids.end()) {
- UINT16_TO_STREAM(p, cid);
- } else {
- UINT16_TO_STREAM(p, 0);
- }
- }
-
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, p_buf);
-}
-
-/*******************************************************************************
- *
- * Function l2cu_reject_ble_connection
- *
- * Description Build and send an L2CAP "Credit based connection res"
- * message to the peer. This function is called for non-success
- * cases.
- *
- * Returns void
- *
- ******************************************************************************/
-void l2cu_reject_ble_connection(tL2C_CCB* p_ccb, uint8_t rem_id,
- uint16_t result) {
- if (p_ccb->ecoc)
- l2cu_reject_credit_based_conn_req(
- p_ccb->p_lcb, rem_id, p_ccb->p_lcb->pending_ecoc_reconfig_cnt, result);
- else
- l2cu_reject_ble_coc_connection(p_ccb->p_lcb, rem_id, result);
-}
-
-/*******************************************************************************
- *
- * Function l2cu_send_ble_reconfig_rsp
- *
- * Description Build and send an L2CAP "Credit based reconfig res"
- * message to the peer. This function is called for non-success
- * cases.
- *
- * Returns void
- *
- ******************************************************************************/
-
-void l2cu_send_ble_reconfig_rsp(tL2C_LCB* p_lcb, uint8_t rem_id,
- uint16_t result) {
- BT_HDR* p_buf;
- uint8_t* p;
-
- L2CAP_TRACE_DEBUG("l2cu_send_ble_reconfig_rsp result 0x04%x", result);
-
- p_buf = l2cu_build_header(p_lcb, L2CAP_CMD_CREDIT_BASED_RECONFIG_RES_LEN,
- L2CAP_CMD_CREDIT_BASED_RECONFIG_RES, rem_id);
- if (p_buf == NULL) {
- L2CAP_TRACE_WARNING("l2cu_send_peer_ble_credit_based_conn_res - no buffer");
- return;
- }
-
- p = (uint8_t*)(p_buf + 1) + L2CAP_SEND_CMD_OFFSET + HCI_DATA_PREAMBLE_SIZE +
- L2CAP_PKT_OVERHEAD + L2CAP_CMD_OVERHEAD;
-
- memset(p, 0, L2CAP_CMD_CREDIT_BASED_RECONFIG_RES_LEN);
- UINT16_TO_STREAM(p, result);
-
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -3016,7 +2942,7 @@ void l2cu_send_peer_ble_credit_based_conn_res(tL2C_CCB* p_ccb,
UINT16_TO_STREAM(p, p_ccb->local_conn_cfg.credits); /* initial credit */
UINT16_TO_STREAM(p, result);
- l2c_link_check_send_pkts(p_ccb->p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_ccb->p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -3039,13 +2965,13 @@ void l2cu_send_peer_ble_flow_control_credit(tL2C_CCB* p_ccb,
p_lcb = p_ccb->p_lcb;
/* Create an identifier for this packet */
- p_ccb->p_lcb->signal_id++;
- l2cu_adj_id(p_ccb->p_lcb);
+ p_ccb->p_lcb->id++;
+ l2cu_adj_id(p_ccb->p_lcb, L2CAP_ADJ_ID);
- p_ccb->local_id = p_ccb->p_lcb->signal_id;
+ p_ccb->local_id = p_ccb->p_lcb->id;
p_buf = l2cu_build_header(p_lcb, L2CAP_CMD_BLE_FLOW_CTRL_CREDIT_LEN,
- L2CAP_CMD_BLE_FLOW_CTRL_CREDIT, p_lcb->signal_id);
+ L2CAP_CMD_BLE_FLOW_CTRL_CREDIT, p_lcb->id);
if (p_buf == NULL) {
L2CAP_TRACE_WARNING("l2cu_send_peer_ble_credit_based_conn_req - no buffer");
return;
@@ -3057,7 +2983,7 @@ void l2cu_send_peer_ble_flow_control_credit(tL2C_CCB* p_ccb,
UINT16_TO_STREAM(p, p_ccb->local_cid);
UINT16_TO_STREAM(p, credit_value);
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -3080,12 +3006,12 @@ void l2cu_send_peer_ble_credit_based_disconn_req(tL2C_CCB* p_ccb) {
p_lcb = p_ccb->p_lcb;
/* Create an identifier for this packet */
- p_ccb->p_lcb->signal_id++;
- l2cu_adj_id(p_ccb->p_lcb);
+ p_ccb->p_lcb->id++;
+ l2cu_adj_id(p_ccb->p_lcb, L2CAP_ADJ_ID);
- p_ccb->local_id = p_ccb->p_lcb->signal_id;
+ p_ccb->local_id = p_ccb->p_lcb->id;
p_buf = l2cu_build_header(p_lcb, L2CAP_DISC_REQ_LEN, L2CAP_CMD_DISC_REQ,
- p_lcb->signal_id);
+ p_lcb->id);
if (p_buf == NULL) {
L2CAP_TRACE_WARNING(
"l2cu_send_peer_ble_credit_based_disconn_req - no buffer");
@@ -3098,7 +3024,7 @@ void l2cu_send_peer_ble_credit_based_disconn_req(tL2C_CCB* p_ccb) {
UINT16_TO_STREAM(p, p_ccb->remote_cid);
UINT16_TO_STREAM(p, p_ccb->local_cid);
- l2c_link_check_send_pkts(p_lcb, 0, p_buf);
+ l2c_link_check_send_pkts(p_lcb, NULL, p_buf);
}
/*******************************************************************************
@@ -3120,7 +3046,7 @@ tL2C_LCB* l2cu_find_lcb_by_handle(uint16_t handle) {
tL2C_LCB* p_lcb = &l2cb.lcb_pool[0];
for (xx = 0; xx < MAX_L2CAP_LINKS; xx++, p_lcb++) {
- if ((p_lcb->in_use) && (p_lcb->Handle() == handle)) {
+ if ((p_lcb->in_use) && (p_lcb->handle == handle)) {
return (p_lcb);
}
}
@@ -3162,6 +3088,264 @@ tL2C_CCB* l2cu_find_ccb_by_cid(tL2C_LCB* p_lcb, uint16_t local_cid) {
return (p_ccb);
}
+#if (L2CAP_ROUND_ROBIN_CHANNEL_SERVICE == TRUE)
+
+/******************************************************************************
+ *
+ * Function l2cu_get_next_channel_in_rr
+ *
+ * Description get the next channel to send on a link. It also adjusts the
+ * CCB queue to do a basic priority and round-robin scheduling.
+ *
+ * Returns pointer to CCB or NULL
+ *
+ ******************************************************************************/
+static tL2C_CCB* l2cu_get_next_channel_in_rr(tL2C_LCB* p_lcb) {
+ tL2C_CCB* p_serve_ccb = NULL;
+ tL2C_CCB* p_ccb;
+
+ int i, j;
+
+ /* scan all of priority until finding a channel to serve */
+ for (i = 0; (i < L2CAP_NUM_CHNL_PRIORITY) && (!p_serve_ccb); i++) {
+ /* scan all channel within serving priority group until finding a channel to
+ * serve */
+ for (j = 0; (j < p_lcb->rr_serv[p_lcb->rr_pri].num_ccb) && (!p_serve_ccb);
+ j++) {
+ /* scaning from next serving channel */
+ p_ccb = p_lcb->rr_serv[p_lcb->rr_pri].p_serve_ccb;
+
+ if (!p_ccb) {
+ L2CAP_TRACE_ERROR("p_serve_ccb is NULL, rr_pri=%d", p_lcb->rr_pri);
+ return NULL;
+ }
+
+ L2CAP_TRACE_DEBUG("RR scan pri=%d, lcid=0x%04x, q_cout=%d",
+ p_ccb->ccb_priority, p_ccb->local_cid,
+ fixed_queue_length(p_ccb->xmit_hold_q));
+
+ /* store the next serving channel */
+ /* this channel is the last channel of its priority group */
+ if ((p_ccb->p_next_ccb == NULL) ||
+ (p_ccb->p_next_ccb->ccb_priority != p_ccb->ccb_priority)) {
+ /* next serving channel is set to the first channel in the group */
+ p_lcb->rr_serv[p_lcb->rr_pri].p_serve_ccb =
+ p_lcb->rr_serv[p_lcb->rr_pri].p_first_ccb;
+ } else {
+ /* next serving channel is set to the next channel in the group */
+ p_lcb->rr_serv[p_lcb->rr_pri].p_serve_ccb = p_ccb->p_next_ccb;
+ }
+
+ if (p_ccb->chnl_state != CST_OPEN) continue;
+
+ if (p_ccb->p_lcb->transport == BT_TRANSPORT_LE) {
+ L2CAP_TRACE_DEBUG("%s : Connection oriented channel", __func__);
+ if (fixed_queue_is_empty(p_ccb->xmit_hold_q)) continue;
+
+ } else {
+ /* eL2CAP option in use */
+ if (p_ccb->peer_cfg.fcr.mode != L2CAP_FCR_BASIC_MODE) {
+ if (p_ccb->fcrb.wait_ack || p_ccb->fcrb.remote_busy) continue;
+
+ if (fixed_queue_is_empty(p_ccb->fcrb.retrans_q)) {
+ if (fixed_queue_is_empty(p_ccb->xmit_hold_q)) continue;
+
+ /* If in eRTM mode, check for window closure */
+ if ((p_ccb->peer_cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) &&
+ (l2c_fcr_is_flow_controlled(p_ccb)))
+ continue;
+ }
+ } else {
+ if (fixed_queue_is_empty(p_ccb->xmit_hold_q)) continue;
+ }
+ }
+
+ /* found a channel to serve */
+ p_serve_ccb = p_ccb;
+ /* decrease quota of its priority group */
+ p_lcb->rr_serv[p_lcb->rr_pri].quota--;
+ }
+
+ /* if there is no more quota of the priority group or no channel to have
+ * data to send */
+ if ((p_lcb->rr_serv[p_lcb->rr_pri].quota == 0) || (!p_serve_ccb)) {
+ /* serve next priority group */
+ p_lcb->rr_pri = (p_lcb->rr_pri + 1) % L2CAP_NUM_CHNL_PRIORITY;
+ /* initialize its quota */
+ p_lcb->rr_serv[p_lcb->rr_pri].quota =
+ L2CAP_GET_PRIORITY_QUOTA(p_lcb->rr_pri);
+ }
+ }
+
+ if (p_serve_ccb) {
+ L2CAP_TRACE_DEBUG("RR service pri=%d, quota=%d, lcid=0x%04x",
+ p_serve_ccb->ccb_priority,
+ p_lcb->rr_serv[p_serve_ccb->ccb_priority].quota,
+ p_serve_ccb->local_cid);
+ }
+
+ return p_serve_ccb;
+}
+
+#else /* (L2CAP_ROUND_ROBIN_CHANNEL_SERVICE == TRUE) */
+
+/******************************************************************************
+ *
+ * Function l2cu_get_next_channel
+ *
+ * Description get the next channel to send on a link bassed on priority
+ * scheduling.
+ *
+ * Returns pointer to CCB or NULL
+ *
+ ******************************************************************************/
+static tL2C_CCB* l2cu_get_next_channel(tL2C_LCB* p_lcb) {
+ tL2C_CCB* p_ccb;
+
+ /* Get the first CCB with data to send.
+ */
+ for (p_ccb = p_lcb->ccb_queue.p_first_ccb; p_ccb; p_ccb = p_ccb->p_next_ccb) {
+ if (p_ccb->chnl_state != CST_OPEN) continue;
+
+ if (p_ccb->fcrb.wait_ack || p_ccb->fcrb.remote_busy) continue;
+
+ if (!fixed_queue_is_empty(p_ccb->fcrb.retrans_q)) return p_ccb;
+
+ if (fixed_queue_is_empty(p_ccb->xmit_hold_q)) continue;
+
+ /* If in eRTM mode, check for window closure */
+ if ((p_ccb->peer_cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) &&
+ (l2c_fcr_is_flow_controlled(p_ccb)))
+ continue;
+
+ /* If here, we found someone */
+ return p_ccb;
+ }
+
+ return NULL;
+}
+#endif /* (L2CAP_ROUND_ROBIN_CHANNEL_SERVICE == TRUE) */
+
+void l2cu_tx_complete(tL2C_TX_COMPLETE_CB_INFO* p_cbi) {
+ if (p_cbi->cb != NULL) p_cbi->cb(p_cbi->local_cid, p_cbi->num_sdu);
+}
+
+/******************************************************************************
+ *
+ * Function l2cu_get_next_buffer_to_send
+ *
+ * Description get the next buffer to send on a link. It also adjusts the
+ * CCB queue to do a basic priority and round-robin scheduling.
+ *
+ * Returns pointer to buffer or NULL
+ *
+ ******************************************************************************/
+BT_HDR* l2cu_get_next_buffer_to_send(tL2C_LCB* p_lcb,
+ tL2C_TX_COMPLETE_CB_INFO* p_cbi) {
+ tL2C_CCB* p_ccb;
+ BT_HDR* p_buf;
+
+/* Highest priority are fixed channels */
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
+ int xx;
+
+ p_cbi->cb = NULL;
+
+ for (xx = 0; xx < L2CAP_NUM_FIXED_CHNLS; xx++) {
+ p_ccb = p_lcb->p_fixed_ccbs[xx];
+ if (p_ccb == NULL) continue;
+
+ /* eL2CAP option in use */
+ if (p_ccb->peer_cfg.fcr.mode != L2CAP_FCR_BASIC_MODE) {
+ if (p_ccb->fcrb.wait_ack || p_ccb->fcrb.remote_busy) continue;
+
+ /* No more checks needed if sending from the reatransmit queue */
+ if (fixed_queue_is_empty(p_ccb->fcrb.retrans_q)) {
+ if (fixed_queue_is_empty(p_ccb->xmit_hold_q)) continue;
+
+ /* If in eRTM mode, check for window closure */
+ if ((p_ccb->peer_cfg.fcr.mode == L2CAP_FCR_ERTM_MODE) &&
+ (l2c_fcr_is_flow_controlled(p_ccb)))
+ continue;
+ }
+
+ p_buf = l2c_fcr_get_next_xmit_sdu_seg(p_ccb, 0);
+ if (p_buf != NULL) {
+ l2cu_check_channel_congestion(p_ccb);
+ l2cu_set_acl_hci_header(p_buf, p_ccb);
+ return (p_buf);
+ }
+ } else {
+ if (!fixed_queue_is_empty(p_ccb->xmit_hold_q)) {
+ p_buf = (BT_HDR*)fixed_queue_try_dequeue(p_ccb->xmit_hold_q);
+ if (NULL == p_buf) {
+ L2CAP_TRACE_ERROR("%s: No data to be sent", __func__);
+ return (NULL);
+ }
+
+ /* Prepare callback info for TX completion */
+ p_cbi->cb = l2cb.fixed_reg[xx].pL2CA_FixedTxComplete_Cb;
+ p_cbi->local_cid = p_ccb->local_cid;
+ p_cbi->num_sdu = 1;
+
+ l2cu_check_channel_congestion(p_ccb);
+ l2cu_set_acl_hci_header(p_buf, p_ccb);
+ return (p_buf);
+ }
+ }
+ }
+#endif
+
+#if (L2CAP_ROUND_ROBIN_CHANNEL_SERVICE == TRUE)
+ /* get next serving channel in round-robin */
+ p_ccb = l2cu_get_next_channel_in_rr(p_lcb);
+#else
+ p_ccb = l2cu_get_next_channel(p_lcb);
+#endif
+
+ /* Return if no buffer */
+ if (p_ccb == NULL) return (NULL);
+
+ if (p_ccb->p_lcb->transport == BT_TRANSPORT_LE) {
+ /* Check credits */
+ if (p_ccb->peer_conn_cfg.credits == 0) {
+ L2CAP_TRACE_DEBUG("%s No credits to send packets", __func__);
+ return NULL;
+ }
+
+ bool last_piece_of_sdu = false;
+ p_buf = l2c_lcc_get_next_xmit_sdu_seg(p_ccb, &last_piece_of_sdu);
+ p_ccb->peer_conn_cfg.credits--;
+
+ if (last_piece_of_sdu) {
+ // TODO: send callback up the stack. Investigate setting p_cbi->cb to
+ // notify after controller ack send.
+ }
+
+ } else {
+ if (p_ccb->peer_cfg.fcr.mode != L2CAP_FCR_BASIC_MODE) {
+ p_buf = l2c_fcr_get_next_xmit_sdu_seg(p_ccb, 0);
+ if (p_buf == NULL) return (NULL);
+ } else {
+ p_buf = (BT_HDR*)fixed_queue_try_dequeue(p_ccb->xmit_hold_q);
+ if (NULL == p_buf) {
+ L2CAP_TRACE_ERROR("l2cu_get_buffer_to_send() #2: No data to be sent");
+ return (NULL);
+ }
+ }
+ }
+
+ if (p_ccb->p_rcb && p_ccb->p_rcb->api.pL2CA_TxComplete_Cb &&
+ (p_ccb->peer_cfg.fcr.mode != L2CAP_FCR_ERTM_MODE))
+ (*p_ccb->p_rcb->api.pL2CA_TxComplete_Cb)(p_ccb->local_cid, 1);
+
+ l2cu_check_channel_congestion(p_ccb);
+
+ l2cu_set_acl_hci_header(p_buf, p_ccb);
+
+ return (p_buf);
+}
+
/******************************************************************************
*
* Function l2cu_set_acl_hci_header
@@ -3179,8 +3363,8 @@ void l2cu_set_acl_hci_header(BT_HDR* p_buf, tL2C_CCB* p_ccb) {
p = (uint8_t*)(p_buf + 1) + p_buf->offset - HCI_DATA_PREAMBLE_SIZE;
if (p_ccb->p_lcb->transport == BT_TRANSPORT_LE) {
- UINT16_TO_STREAM(p, p_ccb->p_lcb->Handle() | (L2CAP_PKT_START_NON_FLUSHABLE
- << L2CAP_PKT_TYPE_SHIFT));
+ UINT16_TO_STREAM(p, p_ccb->p_lcb->handle | (L2CAP_PKT_START_NON_FLUSHABLE
+ << L2CAP_PKT_TYPE_SHIFT));
uint16_t acl_data_size =
controller_get_interface()->get_acl_data_size_ble();
@@ -3191,14 +3375,21 @@ void l2cu_set_acl_hci_header(BT_HDR* p_buf, tL2C_CCB* p_ccb) {
UINT16_TO_STREAM(p, p_buf->len);
}
} else {
- if (((p_buf->layer_specific & L2CAP_FLUSHABLE_MASK) ==
- L2CAP_FLUSHABLE_CH_BASED) &&
- (p_ccb->is_flushable)) {
- UINT16_TO_STREAM(p, p_ccb->p_lcb->Handle() |
- (L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT));
+#if (L2CAP_NON_FLUSHABLE_PB_INCLUDED == TRUE)
+ if ((((p_buf->layer_specific & L2CAP_FLUSHABLE_MASK) ==
+ L2CAP_FLUSHABLE_CH_BASED) &&
+ (p_ccb->is_flushable)) ||
+ ((p_buf->layer_specific & L2CAP_FLUSHABLE_MASK) ==
+ L2CAP_FLUSHABLE_PKT)) {
+ UINT16_TO_STREAM(
+ p, p_ccb->p_lcb->handle | (L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT));
} else {
- UINT16_TO_STREAM(p, p_ccb->p_lcb->Handle() | l2cb.non_flushable_pbf);
+ UINT16_TO_STREAM(p, p_ccb->p_lcb->handle | l2cb.non_flushable_pbf);
}
+#else
+ UINT16_TO_STREAM(
+ p, p_ccb->p_lcb->handle | (L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT));
+#endif
uint16_t acl_data_size =
controller_get_interface()->get_acl_data_size_classic();
@@ -3231,6 +3422,7 @@ static void send_congestion_status_to_all_clients(tL2C_CCB* p_ccb,
if (status == false) l2cb.is_cong_cback_context = false;
}
+#if (L2CAP_NUM_FIXED_CHNLS > 0)
else {
for (uint8_t xx = 0; xx < L2CAP_NUM_FIXED_CHNLS; xx++) {
if (p_ccb->p_lcb->p_fixed_ccbs[xx] == p_ccb) {
@@ -3241,6 +3433,7 @@ static void send_congestion_status_to_all_clients(tL2C_CCB* p_ccb,
}
}
}
+#endif
}
/* check if any change in congestion status */
diff --git a/stack/metrics/stack_metrics_logging.cc b/stack/metrics/stack_metrics_logging.cc
deleted file mode 100644
index 49c77395c..000000000
--- a/stack/metrics/stack_metrics_logging.cc
+++ /dev/null
@@ -1,97 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
-
-#include "common/metrics.h"
-#include "main/shim/metrics_api.h"
-#include "main/shim/shim.h"
-#include "stack/include/stack_metrics_logging.h"
-#include "types/raw_address.h"
-
-void log_classic_pairing_event(const RawAddress& address, uint16_t handle,
- uint32_t hci_cmd, uint16_t hci_event,
- uint16_t cmd_status, uint16_t reason_code,
- int64_t event_value) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricClassicPairingEvent(address, handle, hci_cmd,
- hci_event, cmd_status,
- reason_code, event_value);
- } else {
- bluetooth::common::LogClassicPairingEvent(address, handle, hci_cmd,
- hci_event, cmd_status,
- reason_code, event_value);
- }
-}
-
-void log_link_layer_connection_event(
- const RawAddress* address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction, uint16_t link_type,
- uint32_t hci_cmd, uint16_t hci_event, uint16_t hci_ble_event,
- uint16_t cmd_status, uint16_t reason_code) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricLinkLayerConnectionEvent(
- address, connection_handle, direction, link_type, hci_cmd, hci_event,
- hci_ble_event, cmd_status, reason_code);
- } else {
- bluetooth::common::LogLinkLayerConnectionEvent(
- address, connection_handle, direction, link_type, hci_cmd, hci_event,
- hci_ble_event, cmd_status, reason_code);
- }
-}
-
-void log_smp_pairing_event(const RawAddress& address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricSmpPairingEvent(address, smp_cmd, direction,
- smp_fail_reason);
- } else {
- bluetooth::common::LogSmpPairingEvent(address, smp_cmd, direction,
- smp_fail_reason);
- }
-}
-
-void log_sdp_attribute(const RawAddress& address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricSdpAttribute(address, protocol_uuid, attribute_id,
- attribute_size, attribute_value);
- } else {
- bluetooth::common::LogSdpAttribute(address, protocol_uuid, attribute_id,
- attribute_size, attribute_value);
- }
-}
-
-void log_manufacturer_info(const RawAddress& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer,
- const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version) {
- if (bluetooth::shim::is_any_gd_enabled()) {
- bluetooth::shim::LogMetricManufacturerInfo(
- address, source_type, source_name, manufacturer, model,
- hardware_version, software_version);
- } else {
- bluetooth::common::LogManufacturerInfo(address, source_type, source_name,
- manufacturer, model,
- hardware_version, software_version);
- }
-} \ No newline at end of file
diff --git a/stack/pan/pan_api.cc b/stack/pan/pan_api.cc
index 902138027..ea7791b46 100644
--- a/stack/pan/pan_api.cc
+++ b/stack/pan/pan_api.cc
@@ -36,7 +36,6 @@
#include "pan_int.h"
#include "sdp_api.h"
#include "sdpdefs.h"
-#include "stack/btm/btm_sec.h"
using bluetooth::Uuid;
@@ -55,6 +54,9 @@ using bluetooth::Uuid;
*
******************************************************************************/
void PAN_Register(tPAN_REGISTER* p_register) {
+ BTM_SetDiscoverability(BTM_GENERAL_DISCOVERABLE, 0, 0);
+ BTM_SetConnectability(BTM_CONNECTABLE, 0, 0);
+
pan_register_with_bnep();
if (!p_register) return;
@@ -93,7 +95,7 @@ void PAN_Deregister(void) {
pan_cb.pan_pfilt_ind_cb = NULL;
pan_cb.pan_mfilt_ind_cb = NULL;
- PAN_SetRole(PAN_ROLE_INACTIVE, NULL, NULL);
+ PAN_SetRole(PAN_ROLE_INACTIVE, NULL, NULL, NULL, NULL);
BNEP_Deregister();
return;
@@ -109,8 +111,14 @@ void PAN_Deregister(void) {
*
* Parameters: role - is bit map of roles to be active
* PAN_ROLE_CLIENT is for PANU role
+ * PAN_ROLE_GN_SERVER is for GN role
* PAN_ROLE_NAP_SERVER is for NAP role
+ * sec_mask - Security mask for different roles
+ * It is array of uint8_t. The bytes
+ * represent the security for roles PANU,
+ * GN and NAP in order
* p_user_name - Service name for PANU role
+ * p_gn_name - Service name for GN role
* p_nap_name - Service name for NAP role
* Can be NULL if user wants the default
*
@@ -118,19 +126,17 @@ void PAN_Deregister(void) {
* PAN_FAILURE - if the role is not valid
*
******************************************************************************/
-tPAN_RESULT PAN_SetRole(uint8_t role, const char* p_user_name,
+tPAN_RESULT PAN_SetRole(uint8_t role, uint8_t* sec_mask,
+ const char* p_user_name, const char* p_gn_name,
const char* p_nap_name) {
- /* Check if it is a shutdown request */
- if (role == PAN_ROLE_INACTIVE) {
- pan_close_all_connections();
- pan_cb.role = role;
- return PAN_SUCCESS;
- }
-
const char* p_desc;
+ uint8_t security[3] = {PAN_PANU_SECURITY_LEVEL, PAN_GN_SECURITY_LEVEL,
+ PAN_NAP_SECURITY_LEVEL};
+ uint8_t* p_sec;
/* If the role is not a valid combination reject it */
- if ((!(role & (PAN_ROLE_CLIENT | PAN_ROLE_NAP_SERVER))) &&
+ if ((!(role &
+ (PAN_ROLE_CLIENT | PAN_ROLE_GN_SERVER | PAN_ROLE_NAP_SERVER))) &&
role != PAN_ROLE_INACTIVE) {
PAN_TRACE_ERROR("PAN role %d is invalid", role);
return PAN_FAILURE;
@@ -142,6 +148,11 @@ tPAN_RESULT PAN_SetRole(uint8_t role, const char* p_user_name,
return PAN_SUCCESS;
}
+ if (!sec_mask)
+ p_sec = security;
+ else
+ p_sec = sec_mask;
+
/* Register all the roles with SDP */
PAN_TRACE_API("PAN_SetRole() called with role 0x%x", role);
#if (PAN_SUPPORTS_ROLE_NAP == TRUE)
@@ -157,7 +168,7 @@ tPAN_RESULT PAN_SetRole(uint8_t role, const char* p_user_name,
SDP_DeleteRecord(pan_cb.pan_nap_sdp_handle);
pan_cb.pan_nap_sdp_handle =
- pan_register_with_sdp(UUID_SERVCLASS_NAP, p_nap_name, p_desc);
+ pan_register_with_sdp(UUID_SERVCLASS_NAP, p_sec[2], p_nap_name, p_desc);
bta_sys_add_uuid(UUID_SERVCLASS_NAP);
}
/* If the NAP role is already active and now being cleared delete the record
@@ -171,6 +182,32 @@ tPAN_RESULT PAN_SetRole(uint8_t role, const char* p_user_name,
}
#endif
+#if (PAN_SUPPORTS_ROLE_GN == TRUE)
+ if (role & PAN_ROLE_GN_SERVER) {
+ /* Check the service name */
+ if ((p_gn_name == NULL) || (*p_gn_name == 0))
+ p_gn_name = PAN_GN_DEFAULT_SERVICE_NAME;
+
+ /* Registering for GN service with SDP */
+ p_desc = PAN_GN_DEFAULT_DESCRIPTION;
+
+ if (pan_cb.pan_gn_sdp_handle != 0)
+ SDP_DeleteRecord(pan_cb.pan_gn_sdp_handle);
+
+ pan_cb.pan_gn_sdp_handle =
+ pan_register_with_sdp(UUID_SERVCLASS_GN, p_sec[1], p_gn_name, p_desc);
+ bta_sys_add_uuid(UUID_SERVCLASS_GN);
+ }
+ /* If the GN role is already active and now being cleared delete the record */
+ else if (pan_cb.role & PAN_ROLE_GN_SERVER) {
+ if (pan_cb.pan_gn_sdp_handle != 0) {
+ SDP_DeleteRecord(pan_cb.pan_gn_sdp_handle);
+ pan_cb.pan_gn_sdp_handle = 0;
+ bta_sys_remove_uuid(UUID_SERVCLASS_GN);
+ }
+ }
+#endif
+
#if (PAN_SUPPORTS_ROLE_PANU == TRUE)
if (role & PAN_ROLE_CLIENT) {
/* Check the service name */
@@ -182,8 +219,8 @@ tPAN_RESULT PAN_SetRole(uint8_t role, const char* p_user_name,
if (pan_cb.pan_user_sdp_handle != 0)
SDP_DeleteRecord(pan_cb.pan_user_sdp_handle);
- pan_cb.pan_user_sdp_handle =
- pan_register_with_sdp(UUID_SERVCLASS_PANU, p_user_name, p_desc);
+ pan_cb.pan_user_sdp_handle = pan_register_with_sdp(
+ UUID_SERVCLASS_PANU, p_sec[0], p_user_name, p_desc);
bta_sys_add_uuid(UUID_SERVCLASS_PANU);
}
/* If the PANU role is already active and now being cleared delete the record
@@ -197,6 +234,9 @@ tPAN_RESULT PAN_SetRole(uint8_t role, const char* p_user_name,
}
#endif
+ /* Check if it is a shutdown request */
+ if (role == PAN_ROLE_INACTIVE) pan_close_all_connections();
+
pan_cb.role = role;
PAN_TRACE_EVENT("PAN role set to: %d", role);
return PAN_SUCCESS;
@@ -213,6 +253,7 @@ tPAN_RESULT PAN_SetRole(uint8_t role, const char* p_user_name,
* src_role - Role of the local device for the connection
* dst_role - Role of the remote device for the connection
* PAN_ROLE_CLIENT is for PANU role
+ * PAN_ROLE_GN_SERVER is for GN role
* PAN_ROLE_NAP_SERVER is for NAP role
* *handle - Pointer for returning Handle to the connection
*
@@ -242,8 +283,10 @@ tPAN_RESULT PAN_Connect(const RawAddress& rem_bda, uint8_t src_role,
}
/* Validate the parameters before proceeding */
- if ((src_role != PAN_ROLE_CLIENT && src_role != PAN_ROLE_NAP_SERVER) ||
- (dst_role != PAN_ROLE_CLIENT && dst_role != PAN_ROLE_NAP_SERVER)) {
+ if ((src_role != PAN_ROLE_CLIENT && src_role != PAN_ROLE_GN_SERVER &&
+ src_role != PAN_ROLE_NAP_SERVER) ||
+ (dst_role != PAN_ROLE_CLIENT && dst_role != PAN_ROLE_GN_SERVER &&
+ dst_role != PAN_ROLE_NAP_SERVER)) {
PAN_TRACE_ERROR("Either source %d or destination role %d is invalid",
src_role, dst_role);
return PAN_FAILURE;
@@ -270,6 +313,8 @@ tPAN_RESULT PAN_Connect(const RawAddress& rem_bda, uint8_t src_role,
src_uuid = UUID_SERVCLASS_PANU;
if (dst_role == PAN_ROLE_CLIENT) {
dst_uuid = UUID_SERVCLASS_PANU;
+ } else if (dst_role == PAN_ROLE_GN_SERVER) {
+ dst_uuid = UUID_SERVCLASS_GN;
} else {
dst_uuid = UUID_SERVCLASS_NAP;
}
@@ -283,7 +328,11 @@ tPAN_RESULT PAN_Connect(const RawAddress& rem_bda, uint8_t src_role,
}
dst_uuid = UUID_SERVCLASS_PANU;
- src_uuid = UUID_SERVCLASS_NAP;
+ if (src_role == PAN_ROLE_GN_SERVER) {
+ src_uuid = UUID_SERVCLASS_GN;
+ } else {
+ src_uuid = UUID_SERVCLASS_NAP;
+ }
mx_chan_id = src_uuid;
}
/* The role combination is not valid */
@@ -300,6 +349,7 @@ tPAN_RESULT PAN_Connect(const RawAddress& rem_bda, uint8_t src_role,
PAN_TRACE_ERROR("PAN Connection failed because of no resources");
return PAN_NO_RESOURCES;
}
+ BTM_SetOutService(rem_bda, BTM_SEC_SERVICE_BNEP_PANU, mx_chan_id);
VLOG(0) << __func__ << " for BD Addr: " << rem_bda;
if (pcb->con_state == PAN_STATE_IDLE) {
@@ -317,9 +367,8 @@ tPAN_RESULT PAN_Connect(const RawAddress& rem_bda, uint8_t src_role,
pcb->src_uuid = src_uuid;
pcb->dst_uuid = dst_uuid;
- tBNEP_RESULT ret =
- BNEP_Connect(rem_bda, Uuid::From16Bit(src_uuid),
- Uuid::From16Bit(dst_uuid), &(pcb->handle), mx_chan_id);
+ tBNEP_RESULT ret = BNEP_Connect(rem_bda, Uuid::From16Bit(src_uuid),
+ Uuid::From16Bit(dst_uuid), &(pcb->handle));
if (ret != BNEP_SUCCESS) {
pan_release_pcb(pcb);
return ret;
diff --git a/stack/pan/pan_int.h b/stack/pan/pan_int.h
index 85581d836..1f7662859 100644
--- a/stack/pan/pan_int.h
+++ b/stack/pan/pan_int.h
@@ -33,6 +33,10 @@
*/
#define PAN_ROLE_INACTIVE 0
+/* Protocols supported by the host internal stack, are registered with SDP */
+#define PAN_PROTOCOL_IP 0x0800
+#define PAN_PROTOCOL_ARP 0x0806
+
#define PAN_PROFILE_VERSION 0x0100 /* Version 1.00 */
/* Define the PAN Connection Control Block
@@ -99,6 +103,9 @@ extern void pan_conn_ind_cb(uint16_t handle, const RawAddress& p_bda,
bool is_role_change);
extern void pan_connect_state_cb(uint16_t handle, const RawAddress& rem_bda,
tBNEP_RESULT result, bool is_role_change);
+extern void pan_data_ind_cb(uint16_t handle, const RawAddress& src,
+ const RawAddress& dst, uint16_t protocol,
+ uint8_t* p_data, uint16_t len, bool fw_ext_present);
extern void pan_data_buf_ind_cb(uint16_t handle, const RawAddress& src,
const RawAddress& dst, uint16_t protocol,
BT_HDR* p_buf, bool ext);
@@ -109,8 +116,8 @@ void pan_proto_filt_ind_cb(uint16_t handle, bool indication,
void pan_mcast_filt_ind_cb(uint16_t handle, bool indication,
tBNEP_RESULT result, uint16_t num_filters,
uint8_t* p_filters);
-extern uint32_t pan_register_with_sdp(uint16_t uuid, const char* p_name,
- const char* p_desc);
+extern uint32_t pan_register_with_sdp(uint16_t uuid, uint8_t sec_mask,
+ const char* p_name, const char* p_desc);
extern tPAN_CONN* pan_allocate_pcb(const RawAddress& p_bda, uint16_t handle);
extern tPAN_CONN* pan_get_pcb_by_handle(uint16_t handle);
extern tPAN_CONN* pan_get_pcb_by_addr(const RawAddress& p_bda);
diff --git a/stack/pan/pan_main.cc b/stack/pan/pan_main.cc
index e4301e366..21bd1c972 100644
--- a/stack/pan/pan_main.cc
+++ b/stack/pan/pan_main.cc
@@ -184,6 +184,8 @@ void pan_conn_ind_cb(uint16_t handle, const RawAddress& p_bda,
/* Requested destination role is */
if (local_uuid16 == UUID_SERVCLASS_PANU)
req_role = PAN_ROLE_CLIENT;
+ else if (local_uuid16 == UUID_SERVCLASS_GN)
+ req_role = PAN_ROLE_GN_SERVER;
else
req_role = PAN_ROLE_NAP_SERVER;
@@ -331,11 +333,15 @@ void pan_connect_state_cb(uint16_t handle,
/* Requested destination role is */
if (pcb->src_uuid == UUID_SERVCLASS_PANU)
pan_cb.active_role = PAN_ROLE_CLIENT;
+ else if (pcb->src_uuid == UUID_SERVCLASS_GN)
+ pan_cb.active_role = PAN_ROLE_GN_SERVER;
else
pan_cb.active_role = PAN_ROLE_NAP_SERVER;
if (pcb->dst_uuid == UUID_SERVCLASS_PANU)
peer_role = PAN_ROLE_CLIENT;
+ else if (pcb->dst_uuid == UUID_SERVCLASS_GN)
+ peer_role = PAN_ROLE_GN_SERVER;
else
peer_role = PAN_ROLE_NAP_SERVER;
@@ -355,6 +361,100 @@ void pan_connect_state_cb(uint16_t handle,
/*******************************************************************************
*
+ * Function pan_data_ind_cb
+ *
+ * Description This function is registered with BNEP as data indication
+ * callback. BNEP will call this when the peer sends any data
+ * on this connection
+ *
+ * Parameters: handle - handle for the connection
+ * src - source BD Addr
+ * dst - destination BD Addr
+ * protocol - Network protocol of the Eth packet
+ * p_data - pointer to the data
+ * len - length of the data
+ * fw_ext_present - to indicate whether the data contains any
+ * extension headers before the payload
+ *
+ * Returns none
+ *
+ ******************************************************************************/
+void pan_data_ind_cb(uint16_t handle, const RawAddress& src,
+ const RawAddress& dst, uint16_t protocol, uint8_t* p_data,
+ uint16_t len, bool ext) {
+ tPAN_CONN* pcb;
+ uint16_t i;
+ bool forward;
+
+ /*
+ ** Check the connection status
+ ** If the destination address is MAC broadcast send on all links
+ ** except on the one received
+ ** If the destination uuid is for NAP send to host system also
+ ** If the destination address is one of the devices connected
+ ** send the packet to over that link
+ ** If the destination address is unknown and destination uuid is NAP
+ ** send it to the host system
+ */
+
+ PAN_TRACE_EVENT("pan_data_ind_cb - for handle %d", handle);
+ pcb = pan_get_pcb_by_handle(handle);
+ if (!pcb) {
+ PAN_TRACE_ERROR("PAN Data indication for wrong handle %d", handle);
+ return;
+ }
+
+ if (pcb->con_state != PAN_STATE_CONNECTED) {
+ PAN_TRACE_ERROR("PAN Data indication in wrong state %d for handle %d",
+ pcb->con_state, handle);
+ return;
+ }
+
+ /* Check if it is broadcast packet */
+ if (dst.address[0] & 0x01) {
+ PAN_TRACE_DEBUG("PAN received broadcast packet on handle %d, src uuid 0x%x",
+ handle, pcb->src_uuid);
+ for (i = 0; i < MAX_PAN_CONNS; i++) {
+ if (pan_cb.pcb[i].con_state == PAN_STATE_CONNECTED &&
+ pan_cb.pcb[i].handle != handle &&
+ pcb->src_uuid == pan_cb.pcb[i].src_uuid) {
+ BNEP_Write(pan_cb.pcb[i].handle, dst, p_data, len, protocol, &src, ext);
+ }
+ }
+
+ if (pan_cb.pan_data_ind_cb)
+ (*pan_cb.pan_data_ind_cb)(pcb->handle, src, dst, protocol, p_data, len,
+ ext, true);
+
+ return;
+ }
+
+ /* Check if it is for any other PAN connection */
+ for (i = 0; i < MAX_PAN_CONNS; i++) {
+ if (pan_cb.pcb[i].con_state == PAN_STATE_CONNECTED &&
+ pcb->src_uuid == pan_cb.pcb[i].src_uuid) {
+ if (pan_cb.pcb[i].rem_bda == dst) {
+ BNEP_Write(pan_cb.pcb[i].handle, dst, p_data, len, protocol, &src, ext);
+ return;
+ }
+ }
+ }
+
+ if (pcb->src_uuid == UUID_SERVCLASS_NAP)
+ forward = true;
+ else
+ forward = false;
+
+ /* Send it over the LAN or give it to host software */
+ if (pan_cb.pan_data_ind_cb)
+ (*pan_cb.pan_data_ind_cb)(pcb->handle, src, dst, protocol, p_data, len, ext,
+ forward);
+
+ return;
+}
+
+/*******************************************************************************
+ *
* Function pan_data_buf_ind_cb
*
* Description This function is registered with BNEP as data buffer
diff --git a/stack/pan/pan_utils.cc b/stack/pan/pan_utils.cc
index f2edcc843..fa76200ad 100644
--- a/stack/pan/pan_utils.cc
+++ b/stack/pan/pan_utils.cc
@@ -35,7 +35,6 @@
#include "pan_int.h"
#include "sdp_api.h"
#include "sdpdefs.h"
-#include "stack/btm/btm_sec.h"
static const uint8_t pan_proto_elem_data[] = {
0x35, 0x18, /* data element sequence of length 0x18 bytes */
@@ -62,8 +61,8 @@ static const uint8_t pan_proto_elem_data[] = {
* Returns
*
******************************************************************************/
-uint32_t pan_register_with_sdp(uint16_t uuid, const char* p_name,
- const char* p_desc) {
+uint32_t pan_register_with_sdp(uint16_t uuid, uint8_t sec_mask,
+ const char* p_name, const char* p_desc) {
uint32_t sdp_handle;
uint16_t browse_list = UUID_SERVCLASS_PUBLIC_BROWSE_GROUP;
uint16_t security = 0;
@@ -101,8 +100,7 @@ uint32_t pan_register_with_sdp(uint16_t uuid, const char* p_name,
(uint8_t)(strlen(p_desc) + 1), (uint8_t*)p_desc);
/* Security description */
- // Only NAP and PANU has service level security; GN has no security
- if (uuid == UUID_SERVCLASS_NAP || uuid == UUID_SERVCLASS_PANU) {
+ if (sec_mask) {
UINT16_TO_BE_FIELD(&security, 0x0001);
}
SDP_AddAttribute(sdp_handle, ATTR_ID_SECURITY_DESCRIPTION, UINT_DESC_TYPE, 2,
@@ -125,6 +123,40 @@ uint32_t pan_register_with_sdp(uint16_t uuid, const char* p_name,
UINT32_TO_BE_STREAM(p, NetAccessRate);
SDP_AddAttribute(sdp_handle, ATTR_ID_MAX_NET_ACCESS_RATE, UINT_DESC_TYPE, 4,
array);
+
+ /* Register with Security Manager for the specific security level */
+ if ((!BTM_SetSecurityLevel(true, p_name, BTM_SEC_SERVICE_BNEP_NAP, sec_mask,
+ BT_PSM_BNEP, BTM_SEC_PROTO_BNEP,
+ UUID_SERVCLASS_NAP)) ||
+ (!BTM_SetSecurityLevel(false, p_name, BTM_SEC_SERVICE_BNEP_NAP,
+ sec_mask, BT_PSM_BNEP, BTM_SEC_PROTO_BNEP,
+ UUID_SERVCLASS_NAP))) {
+ PAN_TRACE_ERROR("PAN Security Registration failed for PANU");
+ }
+ }
+#endif
+#if (PAN_SUPPORTS_ROLE_GN == TRUE)
+ if (uuid == UUID_SERVCLASS_GN) {
+ if ((!BTM_SetSecurityLevel(true, p_name, BTM_SEC_SERVICE_BNEP_GN, sec_mask,
+ BT_PSM_BNEP, BTM_SEC_PROTO_BNEP,
+ UUID_SERVCLASS_GN)) ||
+ (!BTM_SetSecurityLevel(false, p_name, BTM_SEC_SERVICE_BNEP_GN, sec_mask,
+ BT_PSM_BNEP, BTM_SEC_PROTO_BNEP,
+ UUID_SERVCLASS_GN))) {
+ PAN_TRACE_ERROR("PAN Security Registration failed for GN");
+ }
+ }
+#endif
+#if (PAN_SUPPORTS_ROLE_PANU == TRUE)
+ if (uuid == UUID_SERVCLASS_PANU) {
+ if ((!BTM_SetSecurityLevel(true, p_name, BTM_SEC_SERVICE_BNEP_PANU,
+ sec_mask, BT_PSM_BNEP, BTM_SEC_PROTO_BNEP,
+ UUID_SERVCLASS_PANU)) ||
+ (!BTM_SetSecurityLevel(false, p_name, BTM_SEC_SERVICE_BNEP_PANU,
+ sec_mask, BT_PSM_BNEP, BTM_SEC_PROTO_BNEP,
+ UUID_SERVCLASS_PANU))) {
+ PAN_TRACE_ERROR("PAN Security Registration failed for PANU");
+ }
}
#endif
diff --git a/stack/rfcomm/port_api.cc b/stack/rfcomm/port_api.cc
index a0b9c9c11..f2b9583c8 100644
--- a/stack/rfcomm/port_api.cc
+++ b/stack/rfcomm/port_api.cc
@@ -38,10 +38,8 @@
#include "rfcdefs.h"
#include "sdp_api.h"
-#include "stack/include/btm_api_types.h"
-
#define error(fmt, ...) \
- LOG_ERROR("## ERROR : %s: " fmt "##", __func__, ##__VA_ARGS__)
+ LOG_ERROR(LOG_TAG, "## ERROR : %s: " fmt "##", __func__, ##__VA_ARGS__)
/* Mapping from PORT_* result codes to human readable strings. */
static const char* result_code_strings[] = {"Success",
@@ -72,22 +70,6 @@ static const char* result_code_strings[] = {"Success",
"Invalid SCN",
"Unknown result code"};
-int RFCOMM_CreateConnectionWithSecurity(uint16_t uuid, uint8_t scn,
- bool is_server, uint16_t mtu,
- const RawAddress& bd_addr,
- uint16_t* p_handle,
- tPORT_CALLBACK* p_mgmt_cb,
- uint16_t sec_mask) {
- rfcomm_security_records[scn] = sec_mask;
-
- return RFCOMM_CreateConnection(uuid, scn, is_server, mtu, bd_addr, p_handle,
- p_mgmt_cb);
-}
-
-extern void RFCOMM_ClearSecurityRecord(uint32_t scn) {
- rfcomm_security_records.erase(scn);
-}
-
/*******************************************************************************
*
* Function RFCOMM_CreateConnection
@@ -1109,8 +1091,6 @@ int PORT_WriteData(uint16_t handle, const char* p_data, uint16_t max_len,
******************************************************************************/
void RFCOMM_Init(void) {
memset(&rfc_cb, 0, sizeof(tRFC_CB)); /* Init RFCOMM control block */
- rfcomm_security_records = {};
- rfc_lcid_mcb = {};
rfc_cb.rfc.last_mux = MAX_BD_CONNECTIONS;
diff --git a/stack/rfcomm/port_int.h b/stack/rfcomm/port_int.h
index d8f462f23..01eb95f47 100644
--- a/stack/rfcomm/port_int.h
+++ b/stack/rfcomm/port_int.h
@@ -27,7 +27,6 @@
#include "bt_common.h"
#include "bt_target.h"
-#include "l2c_api.h"
#include "osi/include/alarm.h"
#include "osi/include/fixed_queue.h"
#include "port_api.h"
@@ -78,16 +77,17 @@ typedef struct {
* RFCOMM multiplexer Control Block
*/
typedef struct {
- alarm_t* mcb_timer = nullptr; /* MCB timer */
- fixed_queue_t* cmd_q = nullptr; /* Queue for command messages on this mux */
+ alarm_t* mcb_timer; /* MCB timer */
+ fixed_queue_t* cmd_q; /* Queue for command messages on this mux */
uint8_t port_handles[RFCOMM_MAX_DLCI + 1]; /* Array for quick access to */
/* port handles based on dlci */
- RawAddress bd_addr =
- RawAddress::kEmpty; /* BD ADDR of the peer if initiator */
+ RawAddress bd_addr; /* BD ADDR of the peer if initiator */
uint16_t lcid; /* Local cid used for this channel */
uint16_t peer_l2cap_mtu; /* Max frame that can be sent to peer L2CAP */
uint8_t state; /* Current multiplexer channel state */
uint8_t is_initiator; /* true if this side sends SABME (dlci=0) */
+ bool local_cfg_sent;
+ bool peer_cfg_rcvd;
bool restart_required; /* true if has to restart channel after disc */
bool peer_ready; /* True if other side can accept frames */
uint8_t flow; /* flow control mechanism for this mux */
@@ -95,10 +95,8 @@ typedef struct {
bool is_disc_initiator; /* true if initiated disc of port */
uint16_t
pending_lcid; /* store LCID for incoming connection while connecting */
- bool pending_configure_complete; /* true if confiquration of the pending
- connection was completed*/
- tL2CAP_CFG_INFO pending_cfg_info = {}; /* store configure info for incoming
- connection while connecting */
+ uint8_t
+ pending_id; /* store l2cap ID for incoming connection while connecting */
} tRFC_MCB;
/*
diff --git a/stack/rfcomm/port_rfc.cc b/stack/rfcomm/port_rfc.cc
index 53cbdba48..3228f6442 100644
--- a/stack/rfcomm/port_rfc.cc
+++ b/stack/rfcomm/port_rfc.cc
@@ -32,6 +32,7 @@
#include "bt_target.h"
#include "bt_utils.h"
#include "btm_api.h"
+#include "btm_int.h"
#include "port_api.h"
#include "port_int.h"
#include "rfc_int.h"
@@ -819,7 +820,7 @@ void PORT_DataInd(tRFC_MCB* p_mcb, uint8_t dlci, BT_HDR* p_buf) {
/* perform flow control procedures if necessary */
port_flow_control_peer(p_port, false, 0);
- /* If user indicated flow control can not deliver any notifications to them */
+ /* If user indicated flow control can not deliver any notifications to him */
if (p_port->rx.user_fc) {
if (events & PORT_EV_RXFLAG) {
p_port->rx_flag_ev_pending = true;
diff --git a/stack/rfcomm/port_utils.cc b/stack/rfcomm/port_utils.cc
index c53113490..77983757f 100644
--- a/stack/rfcomm/port_utils.cc
+++ b/stack/rfcomm/port_utils.cc
@@ -35,7 +35,6 @@
#include "port_int.h"
#include "rfc_int.h"
#include "rfcdefs.h"
-#include "stack/include/btm_client_interface.h"
static const tPORT_STATE default_port_pars = {
PORT_BAUD_RATE_9600,
@@ -144,8 +143,7 @@ void port_select_mtu(tPORT* p_port) {
/* Will select MTU only if application did not setup something */
if (p_port->mtu == 0) {
/* find packet size which connection supports */
- packet_size =
- get_btm_client_interface().peer.BTM_GetMaxPacketSize(p_port->bd_addr);
+ packet_size = btm_get_max_packet_size(p_port->bd_addr);
if (packet_size == 0) {
/* something is very wrong */
LOG(WARNING) << __func__ << ": bad packet size 0 for" << p_port->bd_addr;
diff --git a/stack/rfcomm/rfc_int.h b/stack/rfcomm/rfc_int.h
index e9aabfdce..22aab6640 100644
--- a/stack/rfcomm/rfc_int.h
+++ b/stack/rfcomm/rfc_int.h
@@ -27,15 +27,16 @@
#include "l2c_api.h"
#include "port_int.h"
-#include "stack/include/btm_status.h"
-
-#include <unordered_map>
/*
* Define RFCOMM result codes
*/
#define RFCOMM_SUCCESS 0
#define RFCOMM_ERROR 1
+#define RFCOMM_LOW_RESOURCES 2
+#define RFCOMM_TRY_LATER 3
+
+#define RFCOMM_USER_ERR 111
#define RFCOMM_SECURITY_ERR 112
/*
@@ -61,6 +62,8 @@ extern void RFCOMM_ParameterNegotiationResponse(tRFC_MCB* p_mcb, uint8_t dlci,
uint16_t mtu, uint8_t cl,
uint8_t k);
+extern void RFCOMM_TestReq(uint8_t* p_data, uint16_t len);
+
extern void RFCOMM_FlowReq(tRFC_MCB* p_mcb, uint8_t dlci, bool state);
extern void RFCOMM_PortParameterNegotiationRequest(tRFC_MCB* p_mcb,
@@ -144,40 +147,17 @@ typedef struct {
/*
* Define states and events for the RFC multiplexer state machine
*/
-typedef enum : uint16_t {
- RFC_MX_STATE_IDLE = 0,
- RFC_MX_STATE_WAIT_CONN_CNF = 1,
- RFC_MX_STATE_CONFIGURE = 2,
- RFC_MX_STATE_SABME_WAIT_UA = 3,
- RFC_MX_STATE_WAIT_SABME = 4,
- RFC_MX_STATE_CONNECTED = 5,
- RFC_MX_STATE_DISC_WAIT_UA = 6,
-} tRFC_MX_STATE;
-
-inline std::string rfcomm_mx_state_text(tRFC_MX_STATE state) {
- switch (state) {
- case RFC_MX_STATE_IDLE:
- return std::string("idle");
- case RFC_MX_STATE_WAIT_CONN_CNF:
- return std::string("wait_config");
- case RFC_MX_STATE_CONFIGURE:
- return std::string("configure");
- case RFC_MX_STATE_SABME_WAIT_UA:
- return std::string("sabme_wait_ua");
- case RFC_MX_STATE_WAIT_SABME:
- return std::string("wait_sabme");
- case RFC_MX_STATE_CONNECTED:
- return std::string("connected");
- case RFC_MX_STATE_DISC_WAIT_UA:
- return std::string("disconnect_wait_ua");
- default:
- return std::string("UNKNOWN");
- }
-}
+#define RFC_MX_STATE_IDLE 0
+#define RFC_MX_STATE_WAIT_CONN_CNF 1
+#define RFC_MX_STATE_CONFIGURE 2
+#define RFC_MX_STATE_SABME_WAIT_UA 3
+#define RFC_MX_STATE_WAIT_SABME 4
+#define RFC_MX_STATE_CONNECTED 5
+#define RFC_MX_STATE_DISC_WAIT_UA 6
/*
* Define port states
- */
+*/
#define RFC_STATE_CLOSED 0
#define RFC_STATE_SABME_WAIT_UA 1
#define RFC_STATE_ORIG_WAIT_SEC_CHECK 2
@@ -207,6 +187,12 @@ inline std::string rfcomm_mx_state_text(tRFC_MX_STATE state) {
#define RFC_MX_EVENT_CONF_IND 12
#define RFC_MX_EVENT_QOS_VIOLATION_IND 13
#define RFC_MX_EVENT_DISC_IND 14
+#define RFC_MX_EVENT_TEST_CMD 15
+#define RFC_MX_EVENT_TEST_RSP 16
+#define RFC_MX_EVENT_FCON_CMD 17
+#define RFC_MX_EVENT_FCOFF_CMD 18
+#define RFC_MX_EVENT_NSC 19
+#define RFC_MX_EVENT_NSC_RSP 20
/*
* Port events
@@ -236,6 +222,8 @@ typedef struct {
MX_FRAME rx_frame;
tL2CAP_APPL_INFO reg_info; /* L2CAP Registration info */
+ /* MCB based on the L2CAP's lcid */
+ tRFC_MCB* p_rfc_lcid_mcb[MAX_L2CAP_CHANNELS];
bool peer_rx_disabled; /* If true peer sent FCOFF */
uint8_t last_mux; /* Last mux allocated */
uint8_t last_port_index; // Index of last port allocated in rfc_cb.port
@@ -250,17 +238,20 @@ typedef struct {
extern tRFC_CB rfc_cb;
-extern std::unordered_map<uint32_t /* scn */, uint16_t /* sec_mask */>
- rfcomm_security_records;
-
-/* MCB based on the L2CAP's lcid */
-extern std::unordered_map<uint16_t /* cid */, tRFC_MCB*> rfc_lcid_mcb;
-
/* Timer running on the multiplexor channel while no DLCI connection is open */
#define RFC_MCB_INIT_INACT_TIMER 60 /* in seconds */
/* Timer running on the multiplexor channel after last DLCI is released */
-#define RFC_MCB_RELEASE_INACT_TIMER 20 /* in seconds */
+#define RFC_MCB_RELEASE_INACT_TIMER 2 /* in seconds */
+
+/*
+ * Define RFCOMM frame processing errors
+*/
+#define RFCOMM_ERR_BAD_SABME 1
+#define RFCOMM_ERR_BAD_UA 2
+#define RFCOMM_ERR_BAD_DM 3
+#define RFCOMM_ERR_BAD_DISC 4
+#define RFCOMM_ERR_BAD_UIH 5
#ifdef RFCOMM_PRECALC_FCS
@@ -303,8 +294,6 @@ extern void rfc_process_fcon(tRFC_MCB* p_rfc_mcb, bool is_command);
extern void rfc_process_fcoff(tRFC_MCB* p_rfc_mcb, bool is_command);
extern void rfc_process_l2cap_congestion(tRFC_MCB* p_mcb, bool is_congested);
-void rfc_on_l2cap_error(uint16_t lcid, uint16_t result);
-
/*
* Functions provided by the rfc_utils.cc
*/
@@ -316,6 +305,7 @@ extern void rfc_timer_stop(tRFC_MCB* p_rfc_mcb);
extern void rfc_port_timer_start(tPORT* p_port, uint16_t tout);
extern void rfc_port_timer_stop(tPORT* p_port);
+bool rfc_check_uih_fcs(uint8_t dlci, uint8_t received_fcs);
bool rfc_check_fcs(uint16_t len, uint8_t* p, uint8_t received_fcs);
tRFC_MCB* rfc_find_lcid_mcb(uint16_t lcid);
extern void rfc_save_lcid_mcb(tRFC_MCB* p_rfc_mcb, uint16_t lcid);
@@ -323,7 +313,7 @@ extern void rfc_check_mcb_active(tRFC_MCB* p_mcb);
extern void rfc_port_closed(tPORT* p_port);
extern void rfc_sec_check_complete(const RawAddress* bd_addr,
tBT_TRANSPORT transport, void* p_ref_data,
- tBTM_STATUS res);
+ uint8_t res);
extern void rfc_inc_credit(tPORT* p_port, uint8_t credit);
extern void rfc_dec_credit(tPORT* p_port);
extern void rfc_check_send_cmd(tRFC_MCB* p_mcb, BT_HDR* p_buf);
@@ -374,6 +364,8 @@ extern void PORT_ParNegInd(tRFC_MCB* p_mcb, uint8_t dlci, uint16_t mtu,
extern void PORT_ParNegCnf(tRFC_MCB* p_mcb, uint8_t dlci, uint16_t mtu,
uint8_t cl, uint8_t k);
+extern void PORT_TestCnf(tRFC_MCB* p_mcb, uint8_t* p_data, uint16_t len);
+
extern void PORT_FlowInd(tRFC_MCB* p_mcb, uint8_t dlci, bool fc);
extern void PORT_PortNegInd(tRFC_MCB* p_mcb, uint8_t dlci, tPORT_STATE* p_pars,
diff --git a/stack/rfcomm/rfc_l2cap_if.cc b/stack/rfcomm/rfc_l2cap_if.cc
index 46e12bb11..34e0cebc0 100644
--- a/stack/rfcomm/rfc_l2cap_if.cc
+++ b/stack/rfcomm/rfc_l2cap_if.cc
@@ -45,9 +45,9 @@ static void RFCOMM_ConnectInd(const RawAddress& bd_addr, uint16_t lcid,
uint16_t psm, uint8_t id);
static void RFCOMM_ConnectCnf(uint16_t lcid, uint16_t err);
static void RFCOMM_ConfigInd(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg);
-static void RFCOMM_ConfigCnf(uint16_t lcid, uint16_t result,
- tL2CAP_CFG_INFO* p_cfg);
+static void RFCOMM_ConfigCnf(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg);
static void RFCOMM_DisconnectInd(uint16_t lcid, bool is_clear);
+static void RFCOMM_QoSViolationInd(UNUSED_ATTR const RawAddress& bd_addr);
static void RFCOMM_BufDataInd(uint16_t lcid, BT_HDR* p_buf);
static void RFCOMM_CongestionStatusInd(uint16_t lcid, bool is_congested);
@@ -64,16 +64,17 @@ void rfcomm_l2cap_if_init(void) {
p_l2c->pL2CA_ConnectInd_Cb = RFCOMM_ConnectInd;
p_l2c->pL2CA_ConnectCfm_Cb = RFCOMM_ConnectCnf;
+ p_l2c->pL2CA_ConnectPnd_Cb = NULL;
p_l2c->pL2CA_ConfigInd_Cb = RFCOMM_ConfigInd;
p_l2c->pL2CA_ConfigCfm_Cb = RFCOMM_ConfigCnf;
p_l2c->pL2CA_DisconnectInd_Cb = RFCOMM_DisconnectInd;
+ p_l2c->pL2CA_DisconnectCfm_Cb = NULL;
+ p_l2c->pL2CA_QoSViolationInd_Cb = RFCOMM_QoSViolationInd;
p_l2c->pL2CA_DataInd_Cb = RFCOMM_BufDataInd;
p_l2c->pL2CA_CongestionStatus_Cb = RFCOMM_CongestionStatusInd;
p_l2c->pL2CA_TxComplete_Cb = NULL;
- p_l2c->pL2CA_Error_Cb = rfc_on_l2cap_error;
- L2CA_Register(BT_PSM_RFCOMM, rfc_cb.rfc.reg_info, true /* enable_snoop */,
- nullptr, L2CAP_MTU_SIZE, 0, 0);
+ L2CA_Register(BT_PSM_RFCOMM, p_l2c, true /* enable_snoop */, nullptr);
}
/*******************************************************************************
@@ -93,6 +94,7 @@ void RFCOMM_ConnectInd(const RawAddress& bd_addr, uint16_t lcid,
/* if this is collision case */
if ((p_mcb->is_initiator) && (p_mcb->state == RFC_MX_STATE_WAIT_CONN_CNF)) {
p_mcb->pending_lcid = lcid;
+ p_mcb->pending_id = id;
/* wait random timeout (2 - 12) to resolve collision */
/* if peer gives up then local device rejects incoming connection and
@@ -119,7 +121,7 @@ void RFCOMM_ConnectInd(const RawAddress& bd_addr, uint16_t lcid,
}
if (p_mcb == nullptr) {
- L2CA_DisconnectReq(lcid);
+ L2CA_ConnectRsp(bd_addr, id, lcid, L2CAP_CONN_NO_RESOURCES, 0);
return;
}
p_mcb->lcid = lcid;
@@ -148,14 +150,42 @@ void RFCOMM_ConnectCnf(uint16_t lcid, uint16_t result) {
/* if peer rejects our connect request but peer's connect request is pending
*/
if (result != L2CAP_CONN_OK) {
+ RFCOMM_TRACE_DEBUG(
+ "RFCOMM_ConnectCnf retry as acceptor on pending LCID(0x%x)",
+ p_mcb->pending_lcid);
+
+ /* remove mcb from mapping table */
+ rfc_save_lcid_mcb(NULL, p_mcb->lcid);
+
+ p_mcb->lcid = p_mcb->pending_lcid;
+ p_mcb->is_initiator = false;
+ p_mcb->state = RFC_MX_STATE_IDLE;
+
+ /* store mcb into mapping table */
+ rfc_save_lcid_mcb(p_mcb, p_mcb->lcid);
+
+ /* update direction bit */
+ for (int i = 0; i < RFCOMM_MAX_DLCI; i += 2) {
+ uint8_t handle = p_mcb->port_handles[i];
+ if (handle != 0) {
+ p_mcb->port_handles[i] = 0;
+ p_mcb->port_handles[i + 1] = handle;
+ rfc_cb.port.port[handle - 1].dlci += 1;
+ RFCOMM_TRACE_DEBUG("RFCOMM MX, port_handle=%d, DLCI[%d->%d]", handle,
+ i, rfc_cb.port.port[handle - 1].dlci);
+ }
+ }
+
+ rfc_mx_sm_execute(p_mcb, RFC_MX_EVENT_CONN_IND, &(p_mcb->pending_id));
return;
} else {
RFCOMM_TRACE_DEBUG("RFCOMM_ConnectCnf peer gave up pending LCID(0x%x)",
p_mcb->pending_lcid);
- /* Peer gave up its connection request, make sure cleaning up L2CAP
+ /* Peer gave up his connection request, make sure cleaning up L2CAP
* channel */
- L2CA_DisconnectReq(p_mcb->pending_lcid);
+ L2CA_ConnectRsp(p_mcb->bd_addr, p_mcb->pending_id, p_mcb->pending_lcid,
+ L2CAP_CONN_NO_RESOURCES, 0);
p_mcb->pending_lcid = 0;
}
@@ -181,14 +211,6 @@ void RFCOMM_ConfigInd(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
if (!p_mcb) {
RFCOMM_TRACE_ERROR("RFCOMM_ConfigInd LCID:0x%x", lcid);
- for (auto& [cid, mcb] : rfc_lcid_mcb) {
- if (mcb != nullptr && mcb->pending_lcid == lcid) {
- tL2CAP_CFG_INFO l2cap_cfg_info(*p_cfg);
- mcb->pending_configure_complete = true;
- mcb->pending_cfg_info = l2cap_cfg_info;
- return;
- }
- }
return;
}
@@ -204,22 +226,30 @@ void RFCOMM_ConfigInd(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
* event to the FSM.
*
******************************************************************************/
-void RFCOMM_ConfigCnf(uint16_t lcid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
- RFCOMM_ConfigInd(lcid, p_cfg);
-
+void RFCOMM_ConfigCnf(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
tRFC_MCB* p_mcb = rfc_find_lcid_mcb(lcid);
if (!p_mcb) {
RFCOMM_TRACE_ERROR("RFCOMM_ConfigCnf no MCB LCID:0x%x", lcid);
return;
}
- uintptr_t result_as_ptr = L2CAP_CFG_OK;
- rfc_mx_sm_execute(p_mcb, RFC_MX_EVENT_CONF_CNF, (void*)result_as_ptr);
+
+ rfc_mx_sm_execute(p_mcb, RFC_MX_EVENT_CONF_CNF, (void*)p_cfg);
}
/*******************************************************************************
*
+ * Function RFCOMM_QoSViolationInd
+ *
+ * Description This is a callback function called by L2CAP when
+ * L2CA_QoSViolationIndInd received. Dispatch event to the
+ * FSM.
+ *
+ ******************************************************************************/
+void RFCOMM_QoSViolationInd(UNUSED_ATTR const RawAddress& bd_addr) {}
+
+/*******************************************************************************
+ *
* Function RFCOMM_DisconnectInd
*
* Description This is a callback function called by L2CAP when
@@ -230,6 +260,9 @@ void RFCOMM_DisconnectInd(uint16_t lcid, bool is_conf_needed) {
VLOG(1) << __func__ << ": lcid=" << loghex(lcid)
<< ", is_conf_needed=" << is_conf_needed;
tRFC_MCB* p_mcb = rfc_find_lcid_mcb(lcid);
+ if (is_conf_needed) {
+ L2CA_DisconnectRsp(lcid);
+ }
if (!p_mcb) {
LOG(WARNING) << __func__ << ": no mcb for lcid " << loghex(lcid);
return;
@@ -365,15 +398,20 @@ void RFCOMM_CongestionStatusInd(uint16_t lcid, bool is_congested) {
*
******************************************************************************/
tRFC_MCB* rfc_find_lcid_mcb(uint16_t lcid) {
- tRFC_MCB* p_mcb = rfc_lcid_mcb[lcid];
- if (p_mcb != nullptr) {
- if (p_mcb->lcid != lcid) {
- LOG(WARNING) << __func__ << "LCID reused lcid=:" << loghex(lcid)
- << ", current_lcid=" << loghex(p_mcb->lcid);
- return nullptr;
+ if (lcid - L2CAP_BASE_APPL_CID >= MAX_L2CAP_CHANNELS) {
+ RFCOMM_TRACE_ERROR("rfc_find_lcid_mcb LCID:0x%x", lcid);
+ return nullptr;
+ } else {
+ tRFC_MCB* p_mcb = rfc_cb.rfc.p_rfc_lcid_mcb[lcid - L2CAP_BASE_APPL_CID];
+ if (p_mcb != nullptr) {
+ if (p_mcb->lcid != lcid) {
+ LOG(WARNING) << __func__ << "LCID reused lcid=:" << loghex(lcid)
+ << ", current_lcid=" << loghex(p_mcb->lcid);
+ return nullptr;
+ }
}
+ return p_mcb;
}
- return p_mcb;
}
/*******************************************************************************
@@ -384,6 +422,14 @@ tRFC_MCB* rfc_find_lcid_mcb(uint16_t lcid) {
*
******************************************************************************/
void rfc_save_lcid_mcb(tRFC_MCB* p_mcb, uint16_t lcid) {
- auto mcb_index = static_cast<size_t>(lcid);
- rfc_lcid_mcb[mcb_index] = p_mcb;
+ if (lcid < L2CAP_BASE_APPL_CID) {
+ LOG(ERROR) << __func__ << ": LCID " << lcid << " is too small";
+ return;
+ }
+ auto mcb_index = static_cast<size_t>(lcid - L2CAP_BASE_APPL_CID);
+ if (mcb_index >= MAX_L2CAP_CHANNELS) {
+ LOG(ERROR) << __func__ << ": LCID " << lcid << " is too large";
+ return;
+ }
+ rfc_cb.rfc.p_rfc_lcid_mcb[mcb_index] = p_mcb;
}
diff --git a/stack/rfcomm/rfc_mx_fsm.cc b/stack/rfcomm/rfc_mx_fsm.cc
index 96302f2cb..d1da01e9b 100644
--- a/stack/rfcomm/rfc_mx_fsm.cc
+++ b/stack/rfcomm/rfc_mx_fsm.cc
@@ -28,8 +28,6 @@
#include "bt_utils.h"
#include "l2c_api.h"
#include "l2cdefs.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
#include "port_api.h"
#include "port_int.h"
@@ -58,7 +56,7 @@ static void rfc_mx_sm_state_disc_wait_ua(tRFC_MCB* p_mcb, uint16_t event,
static void rfc_mx_send_config_req(tRFC_MCB* p_mcb);
static void rfc_mx_conf_ind(tRFC_MCB* p_mcb, tL2CAP_CFG_INFO* p_cfg);
-static void rfc_mx_conf_cnf(tRFC_MCB* p_mcb, uint16_t result);
+static void rfc_mx_conf_cnf(tRFC_MCB* p_mcb, tL2CAP_CFG_INFO* p_cfg);
/*******************************************************************************
*
@@ -72,12 +70,8 @@ static void rfc_mx_conf_cnf(tRFC_MCB* p_mcb, uint16_t result);
******************************************************************************/
void rfc_mx_sm_execute(tRFC_MCB* p_mcb, uint16_t event, void* p_data) {
CHECK(p_mcb != nullptr) << __func__ << ": NULL mcb for event " << event;
-
- LOG_INFO(
- "RFCOMM peer:%s event:%d state:%s", PRIVATE_ADDRESS(p_mcb->bd_addr),
- event,
- rfcomm_mx_state_text(static_cast<tRFC_MX_STATE>(p_mcb->state)).c_str());
-
+ VLOG(1) << __func__ << ": bd_addr=" << p_mcb->bd_addr
+ << ", state=" << std::to_string(p_mcb->state) << ", event=" << event;
switch (p_mcb->state) {
case RFC_MX_STATE_IDLE:
rfc_mx_sm_state_idle(p_mcb, event, p_data);
@@ -144,9 +138,18 @@ void rfc_mx_sm_state_idle(tRFC_MCB* p_mcb, uint16_t event, void* p_data) {
return;
}
+ case RFC_MX_EVENT_START_RSP:
+ case RFC_MX_EVENT_CONN_CNF:
+ case RFC_MX_EVENT_CONF_IND:
+ case RFC_MX_EVENT_CONF_CNF:
+ RFCOMM_TRACE_ERROR("Mx error state %d event %d", p_mcb->state, event);
+ return;
+
case RFC_MX_EVENT_CONN_IND:
rfc_timer_start(p_mcb, RFCOMM_CONN_TIMEOUT);
+ L2CA_ConnectRsp(p_mcb->bd_addr, *((uint8_t*)p_data), p_mcb->lcid,
+ L2CAP_CONN_OK, 0);
rfc_mx_send_config_req(p_mcb);
@@ -167,10 +170,6 @@ void rfc_mx_sm_state_idle(tRFC_MCB* p_mcb, uint16_t event, void* p_data) {
case RFC_EVENT_UIH:
rfc_send_dm(p_mcb, RFCOMM_MX_DLCI, false);
return;
-
- default:
- RFCOMM_TRACE_ERROR("Mx error state %d event %d", p_mcb->state, event);
- return;
}
RFCOMM_TRACE_EVENT("RFCOMM MX ignored - evt:%d in state:%d", event,
p_mcb->state);
@@ -249,7 +248,7 @@ void rfc_mx_sm_state_wait_conn_cnf(tRFC_MCB* p_mcb, uint16_t event,
}
}
- rfc_mx_sm_execute(p_mcb, RFC_MX_EVENT_CONN_IND, nullptr);
+ rfc_mx_sm_execute(p_mcb, RFC_MX_EVENT_CONN_IND, &(p_mcb->pending_id));
} else {
PORT_CloseInd(p_mcb);
}
@@ -283,7 +282,7 @@ void rfc_mx_sm_state_configure(tRFC_MCB* p_mcb, uint16_t event, void* p_data) {
return;
case RFC_MX_EVENT_CONF_CNF:
- rfc_mx_conf_cnf(p_mcb, (uintptr_t)p_data);
+ rfc_mx_conf_cnf(p_mcb, (tL2CAP_CFG_INFO*)p_data);
return;
case RFC_MX_EVENT_DISC_IND:
@@ -511,6 +510,8 @@ void rfc_mx_sm_state_disc_wait_ua(tRFC_MCB* p_mcb, uint16_t event,
p_mcb->is_initiator = true;
p_mcb->restart_required = false;
+ p_mcb->local_cfg_sent = false;
+ p_mcb->peer_cfg_rcvd = false;
p_mcb->state = RFC_MX_STATE_WAIT_CONN_CNF;
return;
@@ -555,81 +556,51 @@ void rfc_mx_sm_state_disc_wait_ua(tRFC_MCB* p_mcb, uint16_t event,
*
******************************************************************************/
static void rfc_mx_send_config_req(tRFC_MCB* p_mcb) {
- // Not needed. L2CAP sends config req for us
+ RFCOMM_TRACE_EVENT("rfc_mx_send_config_req");
+ tL2CAP_CFG_INFO cfg = {};
+ cfg.mtu_present = true;
+ cfg.mtu = L2CAP_MTU_SIZE;
+
+ /* Defaults set by memset
+ cfg.flush_to_present = false;
+ cfg.qos_present = false;
+ cfg.fcr_present = false;
+ cfg.fcr.mode = L2CAP_FCR_BASIC_MODE;
+ cfg.fcs_present = false;
+ cfg.fcs = N/A when fcs_present is false;
+ */
+ L2CA_ConfigReq(p_mcb->lcid, &cfg);
}
-void rfc_on_l2cap_error(uint16_t lcid, uint16_t result) {
- tRFC_MCB* p_mcb = rfc_find_lcid_mcb(lcid);
- if (p_mcb == nullptr) return;
-
- if (result == L2CAP_CONN_OTHER_ERROR) {
- /* if peer rejects our connect request but peer's connect request is pending
- */
- if (p_mcb->pending_lcid) {
- RFCOMM_TRACE_DEBUG(
- "RFCOMM_ConnectCnf retry as acceptor on pending LCID(0x%x)",
- p_mcb->pending_lcid);
-
- /* remove mcb from mapping table */
- rfc_save_lcid_mcb(NULL, p_mcb->lcid);
-
- p_mcb->lcid = p_mcb->pending_lcid;
- p_mcb->is_initiator = false;
- p_mcb->state = RFC_MX_STATE_IDLE;
-
- /* store mcb into mapping table */
- rfc_save_lcid_mcb(p_mcb, p_mcb->lcid);
-
- /* update direction bit */
- for (int i = 0; i < RFCOMM_MAX_DLCI; i += 2) {
- uint8_t handle = p_mcb->port_handles[i];
- if (handle != 0) {
- p_mcb->port_handles[i] = 0;
- p_mcb->port_handles[i + 1] = handle;
- rfc_cb.port.port[handle - 1].dlci += 1;
- RFCOMM_TRACE_DEBUG("RFCOMM MX, port_handle=%d, DLCI[%d->%d]", handle,
- i, rfc_cb.port.port[handle - 1].dlci);
- }
- }
- rfc_mx_sm_execute(p_mcb, RFC_MX_EVENT_CONN_IND, nullptr);
- if (p_mcb->pending_configure_complete) {
- LOG_INFO("Configuration of the pending connection was completed");
- p_mcb->pending_configure_complete = false;
- uintptr_t result_as_ptr = L2CAP_CFG_OK;
- rfc_mx_sm_execute(p_mcb, RFC_MX_EVENT_CONF_IND,
- &p_mcb->pending_cfg_info);
- rfc_mx_sm_execute(p_mcb, RFC_MX_EVENT_CONF_CNF, (void*)result_as_ptr);
- }
- return;
- }
+/*******************************************************************************
+ *
+ * Function rfc_mx_conf_cnf
+ *
+ * Description This function handles L2CA_ConfigCnf message from the
+ * L2CAP. If result is not success tell upper layer that
+ * start has not been accepted. If initiator send SABME
+ * on DLCI 0. T1 is still running.
+ *
+ ******************************************************************************/
+static void rfc_mx_conf_cnf(tRFC_MCB* p_mcb, tL2CAP_CFG_INFO* p_cfg) {
+ RFCOMM_TRACE_EVENT("rfc_mx_conf_cnf p_cfg:%08x result:%d ", p_cfg,
+ (p_cfg) ? p_cfg->result : 0);
- p_mcb->lcid = lcid;
- rfc_mx_sm_execute(p_mcb, RFC_MX_EVENT_CONN_CNF, &result);
- } else if (result == L2CAP_CFG_FAILED_NO_REASON) {
+ if (p_cfg->result != L2CAP_CFG_OK) {
LOG(ERROR) << __func__ << ": failed to configure L2CAP for "
<< p_mcb->bd_addr;
if (p_mcb->is_initiator) {
LOG(ERROR) << __func__ << ": disconnect L2CAP due to config failure for "
<< p_mcb->bd_addr;
- PORT_StartCnf(p_mcb, result);
+ PORT_StartCnf(p_mcb, p_cfg->result);
L2CA_DisconnectReq(p_mcb->lcid);
}
rfc_release_multiplexer_channel(p_mcb);
+ return;
}
-}
-/*******************************************************************************
- *
- * Function rfc_mx_conf_cnf
- *
- * Description This function handles L2CA_ConfigCnf message from the
- * L2CAP. If result is not success tell upper layer that
- * start has not been accepted. If initiator send SABME
- * on DLCI 0. T1 is still running.
- *
- ******************************************************************************/
-static void rfc_mx_conf_cnf(tRFC_MCB* p_mcb, uint16_t result) {
- if (p_mcb->state == RFC_MX_STATE_CONFIGURE) {
+ p_mcb->local_cfg_sent = true;
+ if ((p_mcb->state == RFC_MX_STATE_CONFIGURE) && p_mcb->peer_cfg_rcvd) {
if (p_mcb->is_initiator) {
p_mcb->state = RFC_MX_STATE_SABME_WAIT_UA;
rfc_send_sabme(p_mcb, RFCOMM_MX_DLCI);
@@ -660,4 +631,27 @@ static void rfc_mx_conf_ind(tRFC_MCB* p_mcb, tL2CAP_CFG_INFO* p_cfg) {
} else {
p_mcb->peer_l2cap_mtu = L2CAP_DEFAULT_MTU - RFCOMM_MIN_OFFSET - 1;
}
+
+ p_cfg->mtu_present = false;
+ p_cfg->flush_to_present = false;
+ p_cfg->qos_present = false;
+
+ p_cfg->result = L2CAP_CFG_OK;
+
+ L2CA_ConfigRsp(p_mcb->lcid, p_cfg);
+
+ p_mcb->peer_cfg_rcvd = true;
+ if ((p_mcb->state == RFC_MX_STATE_CONFIGURE) && p_mcb->local_cfg_sent) {
+ if (p_mcb->is_initiator) {
+ p_mcb->state = RFC_MX_STATE_SABME_WAIT_UA;
+ rfc_send_sabme(p_mcb, RFCOMM_MX_DLCI);
+ rfc_timer_start(p_mcb, RFC_T1_TIMEOUT);
+ } else {
+ p_mcb->state = RFC_MX_STATE_WAIT_SABME;
+ rfc_timer_start(
+ p_mcb, RFCOMM_CONN_TIMEOUT); /* - increased from T2=20 to CONN=120
+ to allow the user more than 10 sec to type in the
+ pin which can be e.g. 16 digits */
+ }
+ }
}
diff --git a/stack/rfcomm/rfc_port_fsm.cc b/stack/rfcomm/rfc_port_fsm.cc
index b62f785df..1b82ddf57 100644
--- a/stack/rfcomm/rfc_port_fsm.cc
+++ b/stack/rfcomm/rfc_port_fsm.cc
@@ -27,6 +27,7 @@
#include "bt_target.h"
#include "bt_utils.h"
#include "btm_api.h"
+#include "btm_int.h"
#include "osi/include/osi.h"
#include "port_api.h"
#include "port_int.h"
@@ -35,9 +36,8 @@
#include <set>
#include "hci/include/btsnoop.h"
-#include "stack/btm/btm_sec.h"
-static const std::set<uint16_t> uuid_logging_acceptlist = {
+static const std::set<uint16_t> uuid_logging_whitelist = {
UUID_SERVCLASS_HEADSET_AUDIO_GATEWAY,
UUID_SERVCLASS_AG_HANDSFREE,
};
@@ -116,18 +116,12 @@ void rfc_port_sm_execute(tPORT* p_port, uint16_t event, void* p_data) {
*
******************************************************************************/
void rfc_port_sm_state_closed(tPORT* p_port, uint16_t event, void* p_data) {
- uint32_t scn = (uint32_t)(p_port->dlci / 2);
switch (event) {
case RFC_EVENT_OPEN:
p_port->rfc.state = RFC_STATE_ORIG_WAIT_SEC_CHECK;
- if (rfcomm_security_records.count(scn) == 0) {
- rfc_sec_check_complete(nullptr, BT_TRANSPORT_BR_EDR, p_port,
- BTM_NO_RESOURCES);
- return;
- }
- btm_sec_mx_access_request(p_port->rfc.p_mcb->bd_addr, true,
- rfcomm_security_records[scn],
- &rfc_sec_check_complete, p_port);
+ btm_sec_mx_access_request(
+ p_port->rfc.p_mcb->bd_addr, BT_PSM_RFCOMM, true, BTM_SEC_PROTO_RFCOMM,
+ (uint32_t)(p_port->dlci / 2), &rfc_sec_check_complete, p_port);
return;
case RFC_EVENT_CLOSE:
@@ -147,13 +141,9 @@ void rfc_port_sm_state_closed(tPORT* p_port, uint16_t event, void* p_data) {
/* Open will be continued after security checks are passed */
p_port->rfc.state = RFC_STATE_TERM_WAIT_SEC_CHECK;
- if (rfcomm_security_records.count(scn) == 0) {
- rfc_sec_check_complete(nullptr, BT_TRANSPORT_BR_EDR, p_port,
- BTM_NO_RESOURCES);
- return;
- }
- btm_sec_mx_access_request(p_port->rfc.p_mcb->bd_addr, true,
- rfcomm_security_records[scn],
+ btm_sec_mx_access_request(p_port->rfc.p_mcb->bd_addr, BT_PSM_RFCOMM,
+ false, BTM_SEC_PROTO_RFCOMM,
+ (uint32_t)(p_port->dlci / 2),
&rfc_sec_check_complete, p_port);
return;
@@ -225,9 +215,9 @@ void rfc_port_sm_sabme_wait_ua(tPORT* p_port, uint16_t event, void* p_data) {
rfc_port_timer_stop(p_port);
p_port->rfc.state = RFC_STATE_OPENED;
- if (uuid_logging_acceptlist.find(p_port->uuid) !=
- uuid_logging_acceptlist.end()) {
- btsnoop_get_interface()->allowlist_rfc_dlci(p_port->rfc.p_mcb->lcid,
+ if (uuid_logging_whitelist.find(p_port->uuid) !=
+ uuid_logging_whitelist.end()) {
+ btsnoop_get_interface()->whitelist_rfc_dlci(p_port->rfc.p_mcb->lcid,
p_port->dlci);
}
@@ -343,9 +333,9 @@ void rfc_port_sm_term_wait_sec_check(tPORT* p_port, uint16_t event,
rfc_send_ua(p_port->rfc.p_mcb, p_port->dlci);
p_port->rfc.state = RFC_STATE_OPENED;
- if (uuid_logging_acceptlist.find(p_port->uuid) !=
- uuid_logging_acceptlist.end()) {
- btsnoop_get_interface()->allowlist_rfc_dlci(p_port->rfc.p_mcb->lcid,
+ if (uuid_logging_whitelist.find(p_port->uuid) !=
+ uuid_logging_whitelist.end()) {
+ btsnoop_get_interface()->whitelist_rfc_dlci(p_port->rfc.p_mcb->lcid,
p_port->dlci);
}
}
@@ -667,7 +657,7 @@ void rfc_process_rpn(tRFC_MCB* p_mcb, bool is_command, bool is_request,
return;
}
- /* If we sent a request for port parameters to the peer it is replying with */
+ /* If we sent a request for port parameters to the peer he is replying with */
/* mask 0. */
rfc_port_timer_stop(p_port);
diff --git a/stack/rfcomm/rfc_port_if.cc b/stack/rfcomm/rfc_port_if.cc
index 0b454b4a8..097d7745f 100644
--- a/stack/rfcomm/rfc_port_if.cc
+++ b/stack/rfcomm/rfc_port_if.cc
@@ -35,8 +35,6 @@
#include "rfcdefs.h"
tRFC_CB rfc_cb;
-std::unordered_map<uint32_t, uint16_t> rfcomm_security_records;
-std::unordered_map<uint16_t /* sci */, tRFC_MCB*> rfc_lcid_mcb;
/*******************************************************************************
*
diff --git a/stack/rfcomm/rfc_ts_frames.cc b/stack/rfcomm/rfc_ts_frames.cc
index ac7d49d6f..7bc98a274 100644
--- a/stack/rfcomm/rfc_ts_frames.cc
+++ b/stack/rfcomm/rfc_ts_frames.cc
@@ -26,13 +26,12 @@
#include "bt_common.h"
#include "bt_target.h"
#include "l2c_api.h"
+#include "log/log.h"
#include "port_api.h"
#include "port_int.h"
#include "rfc_int.h"
#include "rfcdefs.h"
-#include "osi/include/log.h"
-
/*******************************************************************************
*
* Function rfc_send_sabme
diff --git a/stack/rfcomm/rfc_utils.cc b/stack/rfcomm/rfc_utils.cc
index 544f665e2..3dee8a1ad 100644
--- a/stack/rfcomm/rfc_utils.cc
+++ b/stack/rfcomm/rfc_utils.cc
@@ -27,6 +27,7 @@
#include "bt_utils.h"
#include "btm_api.h"
+#include "btm_int.h"
#include "btu.h"
#include "osi/include/osi.h"
#include "port_api.h"
@@ -322,7 +323,7 @@ void rfcomm_mcb_timer_timeout(void* data) {
******************************************************************************/
void rfc_sec_check_complete(UNUSED_ATTR const RawAddress* bd_addr,
UNUSED_ATTR tBT_TRANSPORT transport,
- void* p_ref_data, tBTM_STATUS res) {
+ void* p_ref_data, uint8_t res) {
tPORT* p_port = (tPORT*)p_ref_data;
/* Verify that PORT is still waiting for Security to complete */
diff --git a/stack/sdp/sdp_api.cc b/stack/sdp/sdp_api.cc
index 2d7ec6bad..34ac349d1 100644
--- a/stack/sdp/sdp_api.cc
+++ b/stack/sdp/sdp_api.cc
@@ -726,10 +726,10 @@ bool SDP_FindProfileVersionInRec(tSDP_DISC_REC* p_rec, uint16_t profile_uuid,
* Returns SDP_SUCCESS if query started successfully, else error
*
******************************************************************************/
-tSDP_STATUS SDP_DiDiscover(const RawAddress& remote_device,
- tSDP_DISCOVERY_DB* p_db, uint32_t len,
- tSDP_DISC_CMPL_CB* p_cb) {
- tSDP_STATUS result = SDP_DI_DISC_FAILED;
+uint16_t SDP_DiDiscover(const RawAddress& remote_device,
+ tSDP_DISCOVERY_DB* p_db, uint32_t len,
+ tSDP_DISC_CMPL_CB* p_cb) {
+ uint16_t result = SDP_DI_DISC_FAILED;
uint16_t num_uuids = 1;
uint16_t di_uuid = UUID_SERVCLASS_PNP_INFORMATION;
@@ -901,6 +901,7 @@ uint16_t SDP_GetDiRecord(uint8_t get_record_index,
******************************************************************************/
uint16_t SDP_SetLocalDiRecord(tSDP_DI_RECORD* p_device_info,
uint32_t* p_handle) {
+#if (SDP_SERVER_ENABLED == TRUE)
uint16_t result = SDP_SUCCESS;
uint32_t handle;
uint16_t di_uuid = UUID_SERVCLASS_PNP_INFORMATION;
@@ -1025,6 +1026,9 @@ uint16_t SDP_SetLocalDiRecord(tSDP_DI_RECORD* p_device_info,
sdp_cb.server_db.di_primary_handle = handle;
return result;
+#else /* SDP_SERVER_ENABLED is FALSE */
+ return SDP_DI_REG_FAILED;
+#endif /* if SDP_SERVER_ENABLED */
}
/*******************************************************************************
diff --git a/stack/sdp/sdp_db.cc b/stack/sdp/sdp_db.cc
index 2b258d25c..2cc04b039 100644
--- a/stack/sdp/sdp_db.cc
+++ b/stack/sdp/sdp_db.cc
@@ -32,6 +32,7 @@
#include "sdp_api.h"
#include "sdpint.h"
+#if (SDP_SERVER_ENABLED == TRUE)
/******************************************************************************/
/* L O C A L F U N C T I O N P R O T O T Y P E S */
/******************************************************************************/
@@ -231,6 +232,8 @@ static int sdp_compose_proto_list(uint8_t* p, uint16_t num_elem,
return (p - p_head);
}
+#endif /* SDP_SERVER_ENABLED == TRUE */
+
/*******************************************************************************
*
* Function SDP_CreateRecord
@@ -244,6 +247,7 @@ static int sdp_compose_proto_list(uint8_t* p, uint16_t num_elem,
*
******************************************************************************/
uint32_t SDP_CreateRecord(void) {
+#if (SDP_SERVER_ENABLED == TRUE)
uint32_t handle;
uint8_t buf[4];
tSDP_DB* p_db = &sdp_cb.server_db;
@@ -272,6 +276,7 @@ uint32_t SDP_CreateRecord(void) {
} else
SDP_TRACE_ERROR("SDP_CreateRecord fail, exceed maximum records:%d",
SDP_MAX_RECORDS);
+#endif
return (0);
}
@@ -289,6 +294,7 @@ uint32_t SDP_CreateRecord(void) {
*
******************************************************************************/
bool SDP_DeleteRecord(uint32_t handle) {
+#if (SDP_SERVER_ENABLED == TRUE)
uint16_t xx, yy, zz;
tSDP_RECORD* p_rec = &sdp_cb.server_db.record[0];
@@ -327,6 +333,7 @@ bool SDP_DeleteRecord(uint32_t handle) {
}
}
}
+#endif
return (false);
}
@@ -346,6 +353,7 @@ bool SDP_DeleteRecord(uint32_t handle) {
******************************************************************************/
bool SDP_AddAttribute(uint32_t handle, uint16_t attr_id, uint8_t attr_type,
uint32_t attr_len, uint8_t* p_val) {
+#if (SDP_SERVER_ENABLED == TRUE)
uint16_t xx, yy, zz;
tSDP_RECORD* p_rec = &sdp_cb.server_db.record[0];
@@ -372,22 +380,11 @@ bool SDP_AddAttribute(uint32_t handle, uint16_t attr_id, uint8_t attr_type,
"SDP_AddAttribute: handle:%X, id:%04X, type:%d, len:%d, p_val:%p, "
"*p_val:%d",
handle, attr_id, attr_type, attr_len, p_val, *p_val);
- } else if ((attr_type == TEXT_STR_DESC_TYPE) ||
- (attr_type == URL_DESC_TYPE)) {
- if (p_val[attr_len - 1] == '\0') {
- SDP_TRACE_DEBUG(
- "SDP_AddAttribute: handle:%X, id:%04X, type:%d, len:%d, p_val:%p, "
- "*p_val:%s",
- handle, attr_id, attr_type, attr_len, p_val, (char*)p_val);
- } else {
- SDP_TRACE_DEBUG(
- "SDP_AddAttribute: handle:%X, id:%04X, type:%d, len:%d, p_val:%p",
- handle, attr_id, attr_type, attr_len, p_val);
- }
} else {
SDP_TRACE_DEBUG(
- "SDP_AddAttribute: handle:%X, id:%04X, type:%d, len:%d, p_val:%p",
- handle, attr_id, attr_type, attr_len, p_val);
+ "SDP_AddAttribute: handle:%X, id:%04X, type:%d, len:%d, p_val:%p, "
+ "*p_val:%s",
+ handle, attr_id, attr_type, attr_len, p_val, p_val);
}
}
@@ -454,6 +451,7 @@ bool SDP_AddAttribute(uint32_t handle, uint16_t attr_id, uint8_t attr_type,
return (true);
}
}
+#endif
return (false);
}
@@ -473,6 +471,7 @@ bool SDP_AddAttribute(uint32_t handle, uint16_t attr_id, uint8_t attr_type,
******************************************************************************/
bool SDP_AddSequence(uint32_t handle, uint16_t attr_id, uint16_t num_elem,
uint8_t type[], uint8_t len[], uint8_t* p_val[]) {
+#if (SDP_SERVER_ENABLED == TRUE)
uint16_t xx;
uint8_t* p;
uint8_t* p_head;
@@ -527,6 +526,9 @@ bool SDP_AddSequence(uint32_t handle, uint16_t attr_id, uint16_t num_elem,
(uint32_t)(p - p_buff), p_buff);
osi_free(p_buff);
return result;
+#else /* SDP_SERVER_ENABLED == FALSE */
+ return (false);
+#endif
}
/*******************************************************************************
@@ -543,6 +545,7 @@ bool SDP_AddSequence(uint32_t handle, uint16_t attr_id, uint16_t num_elem,
******************************************************************************/
bool SDP_AddUuidSequence(uint32_t handle, uint16_t attr_id, uint16_t num_uuids,
uint16_t* p_uuids) {
+#if (SDP_SERVER_ENABLED == TRUE)
uint16_t xx;
uint8_t* p;
int32_t max_len = SDP_MAX_ATTR_LEN - 3;
@@ -568,6 +571,9 @@ bool SDP_AddUuidSequence(uint32_t handle, uint16_t attr_id, uint16_t num_uuids,
(uint32_t)(p - p_buff), p_buff);
osi_free(p_buff);
return result;
+#else /* SDP_SERVER_ENABLED == FALSE */
+ return (false);
+#endif
}
/*******************************************************************************
@@ -584,6 +590,7 @@ bool SDP_AddUuidSequence(uint32_t handle, uint16_t attr_id, uint16_t num_uuids,
******************************************************************************/
bool SDP_AddProtocolList(uint32_t handle, uint16_t num_elem,
tSDP_PROTOCOL_ELEM* p_elem_list) {
+#if (SDP_SERVER_ENABLED == TRUE)
int offset;
bool result;
uint8_t* p_buff =
@@ -594,6 +601,9 @@ bool SDP_AddProtocolList(uint32_t handle, uint16_t num_elem,
DATA_ELE_SEQ_DESC_TYPE, (uint32_t)offset, p_buff);
osi_free(p_buff);
return result;
+#else /* SDP_SERVER_ENABLED == FALSE */
+ return (false);
+#endif
}
/*******************************************************************************
@@ -610,6 +620,7 @@ bool SDP_AddProtocolList(uint32_t handle, uint16_t num_elem,
******************************************************************************/
bool SDP_AddAdditionProtoLists(uint32_t handle, uint16_t num_elem,
tSDP_PROTO_LIST_ELEM* p_proto_list) {
+#if (SDP_SERVER_ENABLED == TRUE)
uint16_t xx;
uint8_t* p;
uint8_t* p_len;
@@ -636,6 +647,10 @@ bool SDP_AddAdditionProtoLists(uint32_t handle, uint16_t num_elem,
DATA_ELE_SEQ_DESC_TYPE, (uint32_t)(p - p_buff), p_buff);
osi_free(p_buff);
return result;
+
+#else /* SDP_SERVER_ENABLED == FALSE */
+ return (false);
+#endif
}
/*******************************************************************************
@@ -652,6 +667,7 @@ bool SDP_AddAdditionProtoLists(uint32_t handle, uint16_t num_elem,
******************************************************************************/
bool SDP_AddProfileDescriptorList(uint32_t handle, uint16_t profile_uuid,
uint16_t version) {
+#if (SDP_SERVER_ENABLED == TRUE)
uint8_t* p;
bool result;
uint8_t* p_buff = (uint8_t*)osi_malloc(sizeof(uint8_t) * SDP_MAX_ATTR_LEN);
@@ -676,6 +692,10 @@ bool SDP_AddProfileDescriptorList(uint32_t handle, uint16_t profile_uuid,
DATA_ELE_SEQ_DESC_TYPE, (uint32_t)(p - p_buff), p_buff);
osi_free(p_buff);
return result;
+
+#else /* SDP_SERVER_ENABLED == FALSE */
+ return (false);
+#endif
}
/*******************************************************************************
@@ -692,6 +712,7 @@ bool SDP_AddProfileDescriptorList(uint32_t handle, uint16_t profile_uuid,
******************************************************************************/
bool SDP_AddLanguageBaseAttrIDList(uint32_t handle, uint16_t lang,
uint16_t char_enc, uint16_t base_id) {
+#if (SDP_SERVER_ENABLED == TRUE)
uint8_t* p;
bool result;
uint8_t* p_buff = (uint8_t*)osi_malloc(sizeof(uint8_t) * SDP_MAX_ATTR_LEN);
@@ -714,6 +735,9 @@ bool SDP_AddLanguageBaseAttrIDList(uint32_t handle, uint16_t lang,
DATA_ELE_SEQ_DESC_TYPE, (uint32_t)(p - p_buff), p_buff);
osi_free(p_buff);
return result;
+#else /* SDP_SERVER_ENABLED == FALSE */
+ return (false);
+#endif
}
/*******************************************************************************
@@ -730,6 +754,7 @@ bool SDP_AddLanguageBaseAttrIDList(uint32_t handle, uint16_t lang,
******************************************************************************/
bool SDP_AddServiceClassIdList(uint32_t handle, uint16_t num_services,
uint16_t* p_service_uuids) {
+#if (SDP_SERVER_ENABLED == TRUE)
uint16_t xx;
uint8_t* p;
bool result;
@@ -748,6 +773,9 @@ bool SDP_AddServiceClassIdList(uint32_t handle, uint16_t num_services,
DATA_ELE_SEQ_DESC_TYPE, (uint32_t)(p - p_buff), p_buff);
osi_free(p_buff);
return result;
+#else /* SDP_SERVER_ENABLED == FALSE */
+ return (false);
+#endif
}
/*******************************************************************************
@@ -762,18 +790,19 @@ bool SDP_AddServiceClassIdList(uint32_t handle, uint16_t num_services,
*
******************************************************************************/
bool SDP_DeleteAttribute(uint32_t handle, uint16_t attr_id) {
+#if (SDP_SERVER_ENABLED == TRUE)
tSDP_RECORD* p_rec = &sdp_cb.server_db.record[0];
uint8_t* pad_ptr;
uint32_t len; /* Number of bytes in the entry */
/* Find the record in the database */
- for (uint16_t record_index = 0; record_index < sdp_cb.server_db.num_records; record_index++, p_rec++) {
+ for (uint16_t xx = 0; xx < sdp_cb.server_db.num_records; xx++, p_rec++) {
if (p_rec->record_handle == handle) {
tSDP_ATTRIBUTE* p_attr = &p_rec->attribute[0];
SDP_TRACE_API("Deleting attr_id 0x%04x for handle 0x%x", attr_id, handle);
/* Found it. Now, find the attribute */
- for (uint16_t attribute_index = 0; attribute_index < p_rec->num_attributes; attribute_index++, p_attr++) {
+ for (uint16_t yy = 0; yy < p_rec->num_attributes; yy++, p_attr++) {
if (p_attr->id == attr_id) {
pad_ptr = p_attr->value_ptr;
len = p_attr->len;
@@ -788,15 +817,15 @@ bool SDP_DeleteAttribute(uint32_t handle, uint16_t attr_id) {
/* Found it. Shift everything up one */
p_rec->num_attributes--;
- for (uint16_t zz = attribute_index; zz < p_rec->num_attributes; zz++, p_attr++) {
+ for (uint16_t zz = xx; zz < p_rec->num_attributes; zz++, p_attr++) {
*p_attr = *(p_attr + 1);
}
/* adjust attribute values if needed */
if (len) {
- uint16_t last_attribute_to_adjust =
+ xx =
(p_rec->free_pad_ptr - ((pad_ptr + len) - &p_rec->attr_pad[0]));
- for (uint16_t zz = 0; zz < last_attribute_to_adjust; zz++, pad_ptr++) {
+ for (uint16_t zz = 0; zz < xx; zz++, pad_ptr++) {
*pad_ptr = *(pad_ptr + len);
}
p_rec->free_pad_ptr -= len;
@@ -806,6 +835,7 @@ bool SDP_DeleteAttribute(uint32_t handle, uint16_t attr_id) {
}
}
}
+#endif
/* If here, not found */
return (false);
}
diff --git a/stack/sdp/sdp_discovery.cc b/stack/sdp/sdp_discovery.cc
index e6075407e..bdc15bd1c 100644
--- a/stack/sdp/sdp_discovery.cc
+++ b/stack/sdp/sdp_discovery.cc
@@ -22,8 +22,6 @@
*
******************************************************************************/
-#define LOG_TAG "sdp_discovery"
-
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
@@ -35,7 +33,7 @@
#include "hcidefs.h"
#include "hcimsgs.h"
#include "l2cdefs.h"
-#include "osi/include/log.h"
+#include "log/log.h"
#include "sdp_api.h"
#include "sdpint.h"
@@ -137,8 +135,13 @@ static void sdp_snd_service_search_req(tCONN_CB* p_ccb, uint8_t cont_len,
p += 2;
/* Build the UID sequence. */
+#if (SDP_BROWSE_PLUS == TRUE)
+ p = sdpu_build_uuid_seq(p, 1,
+ &p_ccb->p_db->uuid_filters[p_ccb->cur_uuid_idx]);
+#else
p = sdpu_build_uuid_seq(p, p_ccb->p_db->num_uuid_filters,
p_ccb->p_db->uuid_filters);
+#endif
/* Set max service record count */
UINT16_TO_BE_STREAM(p, sdp_cb.max_recs_per_search);
@@ -586,8 +589,13 @@ static void process_service_search_attr_rsp(tCONN_CB* p_ccb, uint8_t* p_reply,
p += 2;
/* Build the UID sequence. */
+#if (SDP_BROWSE_PLUS == TRUE)
+ p = sdpu_build_uuid_seq(p, 1,
+ &p_ccb->p_db->uuid_filters[p_ccb->cur_uuid_idx]);
+#else
p = sdpu_build_uuid_seq(p, p_ccb->p_db->num_uuid_filters,
p_ccb->p_db->uuid_filters);
+#endif
/* Max attribute byte count */
UINT16_TO_BE_STREAM(p, sdp_cb.max_attr_list_size);
@@ -631,8 +639,9 @@ static void process_service_search_attr_rsp(tCONN_CB* p_ccb, uint8_t* p_reply,
/*******************************************************************/
#if (SDP_RAW_DATA_INCLUDED == TRUE)
+ SDP_TRACE_WARNING("process_service_search_attr_rsp");
if (!sdp_copy_raw_data(p_ccb, true)) {
- LOG_ERROR("sdp_copy_raw_data failed");
+ SDP_TRACE_ERROR("sdp_copy_raw_data failed");
sdp_disconnect(p_ccb, SDP_ILLEGAL_PARAMETER);
return;
}
@@ -644,12 +653,12 @@ static void process_service_search_attr_rsp(tCONN_CB* p_ccb, uint8_t* p_reply,
type = *p++;
if ((type >> 3) != DATA_ELE_SEQ_DESC_TYPE) {
- LOG_WARN("Wrong element in attr_rsp type:0x%02x", type);
+ SDP_TRACE_WARNING("SDP - Wrong type: 0x%02x in attr_rsp", type);
return;
}
p = sdpu_get_len_from_type(p, p + p_ccb->list_len, type, &seq_len);
if (p == NULL || (p + seq_len) > (p + p_ccb->list_len)) {
- LOG_WARN("Illegal search attribute length");
+ SDP_TRACE_WARNING("%s: bad length", __func__);
sdp_disconnect(p_ccb, SDP_ILLEGAL_PARAMETER);
return;
}
@@ -893,7 +902,7 @@ static uint8_t* add_attr(uint8_t* p, uint8_t* p_end, tSDP_DISCOVERY_DB* p_db,
}
break;
case 16:
- /* See if we can compress the UUID down to 16 or 32bit UUIDs */
+ /* See if we can compress his UUID down to 16 or 32bit UUIDs */
if (sdpu_is_base_uuid(p)) {
if ((p[0] == 0) && (p[1] == 0)) {
p_attr->attr_len_type =
diff --git a/stack/sdp/sdp_main.cc b/stack/sdp/sdp_main.cc
index b2b048671..93a4f0639 100644
--- a/stack/sdp/sdp_main.cc
+++ b/stack/sdp/sdp_main.cc
@@ -32,9 +32,10 @@
#include "l2cdefs.h"
#include "osi/include/osi.h"
+#include "btm_api.h"
+
#include "sdp_api.h"
#include "sdpint.h"
-#include "stack/btm/btm_sec.h"
/******************************************************************************/
/* G L O B A L S D P D A T A */
@@ -47,13 +48,12 @@ tSDP_CB sdp_cb;
static void sdp_connect_ind(const RawAddress& bd_addr, uint16_t l2cap_cid,
UNUSED_ATTR uint16_t psm, uint8_t l2cap_id);
static void sdp_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg);
-static void sdp_config_cfm(uint16_t l2cap_cid, uint16_t result,
- tL2CAP_CFG_INFO* p_cfg);
+static void sdp_config_cfm(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg);
static void sdp_disconnect_ind(uint16_t l2cap_cid, bool ack_needed);
static void sdp_data_ind(uint16_t l2cap_cid, BT_HDR* p_msg);
static void sdp_connect_cfm(uint16_t l2cap_cid, uint16_t result);
-static void sdp_on_l2cap_error(uint16_t l2cap_cid, uint16_t result);
+static void sdp_disconnect_cfm(uint16_t l2cap_cid, uint16_t result);
/*******************************************************************************
*
@@ -72,26 +72,52 @@ void sdp_init(void) {
sdp_cb.ccb[i].sdp_conn_timer = alarm_new("sdp.sdp_conn_timer");
}
- /* Initialize the L2CAP configuration. We only care about MTU */
+ /* Initialize the L2CAP configuration. We only care about MTU and flush */
sdp_cb.l2cap_my_cfg.mtu_present = true;
sdp_cb.l2cap_my_cfg.mtu = SDP_MTU_SIZE;
+ sdp_cb.l2cap_my_cfg.flush_to_present = true;
+ sdp_cb.l2cap_my_cfg.flush_to = SDP_FLUSH_TO;
sdp_cb.max_attr_list_size = SDP_MTU_SIZE - 16;
sdp_cb.max_recs_per_search = SDP_MAX_DISC_SERVER_RECS;
- sdp_cb.trace_level = BT_TRACE_LEVEL_WARNING;
+#if (SDP_SERVER_ENABLED == TRUE)
+ /* Register with Security Manager for the specific security level */
+ if (!BTM_SetSecurityLevel(false, SDP_SERVICE_NAME, BTM_SEC_SERVICE_SDP_SERVER,
+ BTM_SEC_NONE, SDP_PSM, 0, 0)) {
+ SDP_TRACE_ERROR("Security Registration Server failed");
+ return;
+ }
+#endif
+
+ /* Register with Security Manager for the specific security level */
+ if (!BTM_SetSecurityLevel(true, SDP_SERVICE_NAME, BTM_SEC_SERVICE_SDP_SERVER,
+ BTM_SEC_NONE, SDP_PSM, 0, 0)) {
+ SDP_TRACE_ERROR("Security Registration for Client failed");
+ return;
+ }
+
+#if defined(SDP_INITIAL_TRACE_LEVEL)
+ sdp_cb.trace_level = SDP_INITIAL_TRACE_LEVEL;
+#else
+ sdp_cb.trace_level = BT_TRACE_LEVEL_NONE; /* No traces */
+#endif
sdp_cb.reg_info.pL2CA_ConnectInd_Cb = sdp_connect_ind;
sdp_cb.reg_info.pL2CA_ConnectCfm_Cb = sdp_connect_cfm;
+ sdp_cb.reg_info.pL2CA_ConnectPnd_Cb = NULL;
sdp_cb.reg_info.pL2CA_ConfigInd_Cb = sdp_config_ind;
sdp_cb.reg_info.pL2CA_ConfigCfm_Cb = sdp_config_cfm;
sdp_cb.reg_info.pL2CA_DisconnectInd_Cb = sdp_disconnect_ind;
+ sdp_cb.reg_info.pL2CA_DisconnectCfm_Cb = sdp_disconnect_cfm;
+ sdp_cb.reg_info.pL2CA_QoSViolationInd_Cb = NULL;
sdp_cb.reg_info.pL2CA_DataInd_Cb = sdp_data_ind;
- sdp_cb.reg_info.pL2CA_Error_Cb = sdp_on_l2cap_error;
+ sdp_cb.reg_info.pL2CA_CongestionStatus_Cb = NULL;
+ sdp_cb.reg_info.pL2CA_TxComplete_Cb = NULL;
/* Now, register with L2CAP */
- if (!L2CA_Register2(BT_PSM_SDP, sdp_cb.reg_info, true /* enable_snoop */,
- nullptr, SDP_MTU_SIZE, 0, BTM_SEC_NONE)) {
+ if (!L2CA_Register(SDP_PSM, &sdp_cb.reg_info, true /* enable_snoop */,
+ nullptr)) {
SDP_TRACE_ERROR("SDP Registration failed");
}
}
@@ -116,7 +142,11 @@ void sdp_free(void) {
******************************************************************************/
static void sdp_connect_ind(const RawAddress& bd_addr, uint16_t l2cap_cid,
UNUSED_ATTR uint16_t psm, uint8_t l2cap_id) {
- tCONN_CB* p_ccb = sdpu_allocate_ccb();
+#if (SDP_SERVER_ENABLED == TRUE)
+ tCONN_CB* p_ccb;
+
+ /* Allocate a new CCB. Return if none available. */
+ p_ccb = sdpu_allocate_ccb();
if (p_ccb == NULL) return;
/* Transition to the next appropriate state, waiting for config setup. */
@@ -125,12 +155,35 @@ static void sdp_connect_ind(const RawAddress& bd_addr, uint16_t l2cap_cid,
/* Save the BD Address and Channel ID. */
p_ccb->device_address = bd_addr;
p_ccb->connection_id = l2cap_cid;
-}
-static void sdp_on_l2cap_error(uint16_t l2cap_cid, uint16_t result) {
- tCONN_CB* p_ccb = sdpu_find_ccb_by_cid(l2cap_cid);
- if (p_ccb == nullptr) return;
- sdp_disconnect(p_ccb, SDP_CFG_FAILED);
+ /* Send response to the L2CAP layer. */
+ L2CA_ConnectRsp(bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_OK, L2CAP_CONN_OK);
+ {
+ tL2CAP_CFG_INFO cfg = sdp_cb.l2cap_my_cfg;
+
+ if (cfg.fcr_present) {
+ SDP_TRACE_DEBUG(
+ "sdp_connect_ind: mode %u, txwinsz %u, max_trans %u, rtrans_tout "
+ "%u, mon_tout %u, mps %u",
+ cfg.fcr.mode, cfg.fcr.tx_win_sz, cfg.fcr.max_transmit,
+ cfg.fcr.rtrans_tout, cfg.fcr.mon_tout, cfg.fcr.mps);
+ }
+
+ if ((!L2CA_ConfigReq(l2cap_cid, &cfg)) && cfg.fcr_present &&
+ cfg.fcr.mode != L2CAP_FCR_BASIC_MODE) {
+ /* FCR not desired; try again in basic mode */
+ cfg.fcr.mode = L2CAP_FCR_BASIC_MODE;
+ cfg.fcr_present = false;
+ L2CA_ConfigReq(l2cap_cid, &cfg);
+ }
+ }
+
+ SDP_TRACE_EVENT("SDP - Rcvd L2CAP conn ind, sent config req, CID 0x%x",
+ p_ccb->connection_id);
+#else /* No server */
+ /* Reject the connection */
+ L2CA_ConnectRsp(bd_addr, l2cap_id, l2cap_cid, L2CAP_CONN_NO_PSM, 0);
+#endif
}
/*******************************************************************************
@@ -146,6 +199,7 @@ static void sdp_on_l2cap_error(uint16_t l2cap_cid, uint16_t result) {
******************************************************************************/
static void sdp_connect_cfm(uint16_t l2cap_cid, uint16_t result) {
tCONN_CB* p_ccb;
+ tL2CAP_CFG_INFO cfg;
/* Find CCB based on CID */
p_ccb = sdpu_find_ccb_by_cid(l2cap_cid);
@@ -158,8 +212,50 @@ static void sdp_connect_cfm(uint16_t l2cap_cid, uint16_t result) {
/* Transition to the next state and startup the timer. */
if ((result == L2CAP_CONN_OK) && (p_ccb->con_state == SDP_STATE_CONN_SETUP)) {
p_ccb->con_state = SDP_STATE_CFG_SETUP;
+
+ cfg = sdp_cb.l2cap_my_cfg;
+
+ if (cfg.fcr_present) {
+ SDP_TRACE_DEBUG(
+ "sdp_connect_cfm: mode %u, txwinsz %u, max_trans %u, rtrans_tout "
+ "%u, mon_tout %u, mps %u",
+ cfg.fcr.mode, cfg.fcr.tx_win_sz, cfg.fcr.max_transmit,
+ cfg.fcr.rtrans_tout, cfg.fcr.mon_tout, cfg.fcr.mps);
+ }
+
+ if ((!L2CA_ConfigReq(l2cap_cid, &cfg)) && cfg.fcr_present &&
+ cfg.fcr.mode != L2CAP_FCR_BASIC_MODE) {
+ /* FCR not desired; try again in basic mode */
+ cfg.fcr_present = false;
+ cfg.fcr.mode = L2CAP_FCR_BASIC_MODE;
+ L2CA_ConfigReq(l2cap_cid, &cfg);
+ }
+
+ SDP_TRACE_EVENT("SDP - got conn cnf, sent cfg req, CID: 0x%x",
+ p_ccb->connection_id);
} else {
- LOG(ERROR) << __func__ << ": invoked with non OK status";
+ SDP_TRACE_WARNING("SDP - Rcvd conn cnf with error: 0x%x CID 0x%x", result,
+ p_ccb->connection_id);
+
+ /* Tell the user if he has a callback */
+ if (p_ccb->p_cb || p_ccb->p_cb2) {
+ uint16_t err = -1;
+ if ((result == HCI_ERR_HOST_REJECT_SECURITY) ||
+ (result == HCI_ERR_AUTH_FAILURE) ||
+ (result == HCI_ERR_PAIRING_NOT_ALLOWED) ||
+ (result == HCI_ERR_PAIRING_WITH_UNIT_KEY_NOT_SUPPORTED) ||
+ (result == HCI_ERR_KEY_MISSING))
+ err = SDP_SECURITY_ERR;
+ else if (result == HCI_ERR_HOST_REJECT_DEVICE)
+ err = SDP_CONN_REJECTED;
+ else
+ err = SDP_CONN_FAILED;
+ if (p_ccb->p_cb)
+ (*p_ccb->p_cb)(err);
+ else if (p_ccb->p_cb2)
+ (*p_ccb->p_cb2)(err, p_ccb->user_data);
+ }
+ sdpu_release_ccb(p_ccb);
}
}
@@ -195,7 +291,63 @@ static void sdp_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
p_ccb->rem_mtu_size = p_cfg->mtu;
}
+ /* For now, always accept configuration from the other side */
+ p_cfg->flush_to_present = false;
+ p_cfg->mtu_present = false;
+ p_cfg->result = L2CAP_CFG_OK;
+
+ /* Check peer config request against our rfcomm configuration */
+ if (p_cfg->fcr_present) {
+ /* Reject the window size if it is bigger than we want it to be */
+ if (p_cfg->fcr.mode != L2CAP_FCR_BASIC_MODE) {
+ if (sdp_cb.l2cap_my_cfg.fcr.mode != L2CAP_FCR_BASIC_MODE &&
+ p_cfg->fcr.tx_win_sz > sdp_cb.l2cap_my_cfg.fcr.tx_win_sz) {
+ p_cfg->fcr.tx_win_sz = sdp_cb.l2cap_my_cfg.fcr.tx_win_sz;
+ p_cfg->result = L2CAP_CFG_UNACCEPTABLE_PARAMS;
+ SDP_TRACE_DEBUG(
+ "sdp_config_ind(CONFIG) -> Please try again with SMALLER TX "
+ "WINDOW");
+ }
+
+ /* Reject if locally we want basic and they don't */
+ if (sdp_cb.l2cap_my_cfg.fcr.mode == L2CAP_FCR_BASIC_MODE) {
+ /* Ask for a new setup */
+ p_cfg->fcr.mode = L2CAP_FCR_BASIC_MODE;
+ p_cfg->result = L2CAP_CFG_UNACCEPTABLE_PARAMS;
+ SDP_TRACE_DEBUG(
+ "sdp_config_ind(CONFIG) -> Please try again with BASIC mode");
+ }
+ /* Remain in configure state and give the peer our desired configuration
+ */
+ if (p_cfg->result != L2CAP_CFG_OK) {
+ SDP_TRACE_WARNING(
+ "SDP - Rcvd cfg ind, Unacceptable Parameters sent cfg cfm, CID: "
+ "0x%x",
+ l2cap_cid);
+ L2CA_ConfigRsp(l2cap_cid, p_cfg);
+ return;
+ }
+ } else /* We agree with peer's request */
+ p_cfg->fcr_present = false;
+ }
+
+ L2CA_ConfigRsp(l2cap_cid, p_cfg);
+
SDP_TRACE_EVENT("SDP - Rcvd cfg ind, sent cfg cfm, CID: 0x%x", l2cap_cid);
+
+ p_ccb->con_flags |= SDP_FLAGS_HIS_CFG_DONE;
+
+ if (p_ccb->con_flags & SDP_FLAGS_MY_CFG_DONE) {
+ p_ccb->con_state = SDP_STATE_CONNECTED;
+
+ if (p_ccb->con_flags & SDP_FLAGS_IS_ORIG) {
+ sdp_disc_connected(p_ccb);
+ } else {
+ /* Start inactivity timer */
+ alarm_set_on_mloop(p_ccb->sdp_conn_timer, SDP_INACT_TIMEOUT_MS,
+ sdp_conn_timer_timeout, p_ccb);
+ }
+ }
}
/*******************************************************************************
@@ -208,13 +360,11 @@ static void sdp_config_ind(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
* Returns void
*
******************************************************************************/
-static void sdp_config_cfm(uint16_t l2cap_cid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
- sdp_config_ind(l2cap_cid, p_cfg);
-
+static void sdp_config_cfm(uint16_t l2cap_cid, tL2CAP_CFG_INFO* p_cfg) {
tCONN_CB* p_ccb;
- SDP_TRACE_EVENT("SDP - Rcvd cfg cfm, CID: 0x%x", l2cap_cid);
+ SDP_TRACE_EVENT("SDP - Rcvd cfg cfm, CID: 0x%x Result: %d", l2cap_cid,
+ p_cfg->result);
/* Find CCB based on CID */
p_ccb = sdpu_find_ccb_by_cid(l2cap_cid);
@@ -224,14 +374,32 @@ static void sdp_config_cfm(uint16_t l2cap_cid, uint16_t initiator,
}
/* For now, always accept configuration from the other side */
- p_ccb->con_state = SDP_STATE_CONNECTED;
-
- if (p_ccb->con_flags & SDP_FLAGS_IS_ORIG) {
- sdp_disc_connected(p_ccb);
+ if (p_cfg->result == L2CAP_CFG_OK) {
+ p_ccb->con_flags |= SDP_FLAGS_MY_CFG_DONE;
+
+ if (p_ccb->con_flags & SDP_FLAGS_HIS_CFG_DONE) {
+ p_ccb->con_state = SDP_STATE_CONNECTED;
+
+ if (p_ccb->con_flags & SDP_FLAGS_IS_ORIG) {
+ sdp_disc_connected(p_ccb);
+ } else {
+ /* Start inactivity timer */
+ alarm_set_on_mloop(p_ccb->sdp_conn_timer, SDP_INACT_TIMEOUT_MS,
+ sdp_conn_timer_timeout, p_ccb);
+ }
+ }
} else {
- /* Start inactivity timer */
- alarm_set_on_mloop(p_ccb->sdp_conn_timer, SDP_INACT_TIMEOUT_MS,
- sdp_conn_timer_timeout, p_ccb);
+ /* If peer has rejected FCR and suggested basic then try basic */
+ if (p_cfg->fcr_present) {
+ tL2CAP_CFG_INFO cfg = sdp_cb.l2cap_my_cfg;
+ cfg.fcr_present = false;
+ L2CA_ConfigReq(l2cap_cid, &cfg);
+
+ /* Remain in configure state */
+ return;
+ }
+
+ sdp_disconnect(p_ccb, SDP_CFG_FAILED);
}
}
@@ -255,16 +423,18 @@ static void sdp_disconnect_ind(uint16_t l2cap_cid, bool ack_needed) {
return;
}
+ if (ack_needed) L2CA_DisconnectRsp(l2cap_cid);
+
SDP_TRACE_EVENT("SDP - Rcvd L2CAP disc, CID: 0x%x", l2cap_cid);
- /* Tell the user if there is a callback */
+ /* Tell the user if he has a callback */
if (p_ccb->p_cb)
- (*p_ccb->p_cb)(((p_ccb->con_state == SDP_STATE_CONNECTED)
- ? SDP_SUCCESS
- : SDP_CONN_FAILED));
+ (*p_ccb->p_cb)((uint16_t)((p_ccb->con_state == SDP_STATE_CONNECTED)
+ ? SDP_SUCCESS
+ : SDP_CONN_FAILED));
else if (p_ccb->p_cb2)
(*p_ccb->p_cb2)(
- ((p_ccb->con_state == SDP_STATE_CONNECTED) ? SDP_SUCCESS
- : SDP_CONN_FAILED),
+ (uint16_t)((p_ccb->con_state == SDP_STATE_CONNECTED) ? SDP_SUCCESS
+ : SDP_CONN_FAILED),
p_ccb->user_data);
sdpu_release_ccb(p_ccb);
@@ -343,7 +513,7 @@ tCONN_CB* sdp_conn_originate(const RawAddress& p_bd_addr) {
*/
p_ccb->con_state = SDP_STATE_CONN_SETUP;
- cid = L2CA_ConnectReq2(BT_PSM_SDP, p_bd_addr, BTM_SEC_NONE);
+ cid = L2CA_ConnectReq(SDP_PSM, p_bd_addr);
/* Check if L2CAP started the connection process */
if (cid == 0) {
@@ -365,7 +535,46 @@ tCONN_CB* sdp_conn_originate(const RawAddress& p_bd_addr) {
* Returns void
*
******************************************************************************/
-void sdp_disconnect(tCONN_CB* p_ccb, tSDP_REASON reason) {
+void sdp_disconnect(tCONN_CB* p_ccb, uint16_t reason) {
+#if (SDP_BROWSE_PLUS == TRUE)
+
+ /* If we are browsing for multiple UUIDs ... */
+ if ((p_ccb->con_state == SDP_STATE_CONNECTED) &&
+ (p_ccb->con_flags & SDP_FLAGS_IS_ORIG) &&
+ ((reason == SDP_SUCCESS) || (reason == SDP_NO_RECS_MATCH))) {
+ /* If the browse found something, do no more searching */
+ if ((p_ccb->cur_uuid_idx == 0) && (p_ccb->p_db->p_first_rec))
+ p_ccb->cur_uuid_idx = p_ccb->p_db->num_uuid_filters;
+
+ while (++p_ccb->cur_uuid_idx < p_ccb->p_db->num_uuid_filters) {
+ /* Check we have not already found the UUID (maybe through browse) */
+ if ((p_ccb->p_db->uuid_filters[p_ccb->cur_uuid_idx].len == 2) &&
+ (SDP_FindServiceInDb(
+ p_ccb->p_db,
+ p_ccb->p_db->uuid_filters[p_ccb->cur_uuid_idx].uu.uuid16, NULL)))
+ continue;
+
+ if ((p_ccb->p_db->uuid_filters[p_ccb->cur_uuid_idx].len > 2) &&
+ (SDP_FindServiceUUIDInDb(
+ p_ccb->p_db, &p_ccb->p_db->uuid_filters[p_ccb->cur_uuid_idx],
+ NULL)))
+ continue;
+
+ p_ccb->cur_handle = 0;
+
+ SDP_TRACE_EVENT("SDP - looking for for more, CID: 0x%x",
+ p_ccb->connection_id);
+
+ sdp_disc_connected(p_ccb);
+ return;
+ }
+ }
+
+ if ((reason == SDP_NO_RECS_MATCH) && (p_ccb->p_db->p_first_rec))
+ reason = SDP_SUCCESS;
+
+#endif
+
SDP_TRACE_EVENT("SDP - disconnect CID: 0x%x", p_ccb->connection_id);
/* Check if we have a connection ID */
@@ -374,15 +583,52 @@ void sdp_disconnect(tCONN_CB* p_ccb, tSDP_REASON reason) {
p_ccb->disconnect_reason = reason;
}
- /* Tell the user if there is a callback */
+ /* If at setup state, we may not get callback ind from L2CAP */
+ /* Call user callback immediately */
+ if (p_ccb->con_state == SDP_STATE_CONN_SETUP) {
+ /* Tell the user if he has a callback */
+ if (p_ccb->p_cb)
+ (*p_ccb->p_cb)(reason);
+ else if (p_ccb->p_cb2)
+ (*p_ccb->p_cb2)(reason, p_ccb->user_data);
+
+ sdpu_release_ccb(p_ccb);
+ }
+}
+
+/*******************************************************************************
+ *
+ * Function sdp_disconnect_cfm
+ *
+ * Description This function handles a disconnect confirm event from L2CAP.
+ *
+ * Returns void
+ *
+ ******************************************************************************/
+static void sdp_disconnect_cfm(uint16_t l2cap_cid,
+ UNUSED_ATTR uint16_t result) {
+ tCONN_CB* p_ccb;
+
+ /* Find CCB based on CID */
+ p_ccb = sdpu_find_ccb_by_cid(l2cap_cid);
+ if (p_ccb == NULL) {
+ SDP_TRACE_WARNING("SDP - Rcvd L2CAP disc cfm, unknown CID: 0x%x",
+ l2cap_cid);
+ return;
+ }
+
+ SDP_TRACE_EVENT("SDP - Rcvd L2CAP disc cfm, CID: 0x%x", l2cap_cid);
+
+ /* Tell the user if he has a callback */
if (p_ccb->p_cb)
- (*p_ccb->p_cb)(reason);
+ (*p_ccb->p_cb)(p_ccb->disconnect_reason);
else if (p_ccb->p_cb2)
- (*p_ccb->p_cb2)(reason, p_ccb->user_data);
+ (*p_ccb->p_cb2)(p_ccb->disconnect_reason, p_ccb->user_data);
sdpu_release_ccb(p_ccb);
}
+
/*******************************************************************************
*
* Function sdp_conn_timer_timeout
@@ -400,7 +646,7 @@ void sdp_conn_timer_timeout(void* data) {
p_ccb->connection_id);
L2CA_DisconnectReq(p_ccb->connection_id);
- /* Tell the user if there is a callback */
+ /* Tell the user if he has a callback */
if (p_ccb->p_cb)
(*p_ccb->p_cb)(SDP_CONN_FAILED);
else if (p_ccb->p_cb2)
diff --git a/stack/sdp/sdp_server.cc b/stack/sdp/sdp_server.cc
index 1814ba551..50bcfebb3 100644
--- a/stack/sdp/sdp_server.cc
+++ b/stack/sdp/sdp_server.cc
@@ -23,18 +23,18 @@
*
******************************************************************************/
+#include <log/log.h>
#include <string.h>
#include "bt_common.h"
#include "bt_types.h"
-#include "avrc_defs.h"
-#include "device/include/interop.h"
-#include "osi/include/log.h"
#include "osi/include/osi.h"
#include "sdp_api.h"
#include "sdpint.h"
+#if (SDP_SERVER_ENABLED == TRUE)
+
/* Maximum number of bytes to reserve out of SDP MTU for response data */
#define SDP_MAX_SERVICE_RSPHDR_LEN 12
#define SDP_MAX_SERVATTR_RSPHDR_LEN 10
@@ -552,7 +552,6 @@ static void process_service_search_attr_req(tCONN_CB* p_ccb, uint16_t trans_num,
tSDP_RECORD* p_rec;
tSDP_ATTR_SEQ attr_seq, attr_seq_sav;
tSDP_ATTRIBUTE* p_attr;
- tSDP_ATTRIBUTE attr_sav;
bool maxxed_out = false, is_cont = false;
uint8_t* p_seq_start;
uint16_t seq_len, attr_len;
@@ -651,19 +650,6 @@ static void process_service_search_attr_req(tCONN_CB* p_ccb, uint16_t trans_num,
attr_seq.attr_entry[xx].end);
if (p_attr) {
- // Check if the attribute contain AVRCP profile description list
- uint16_t avrcp_version = sdpu_is_avrcp_profile_description_list(p_attr);
- if (avrcp_version > AVRC_REV_1_4 &&
- interop_match_addr(INTEROP_AVRCP_1_4_ONLY,
- &(p_ccb->device_address))) {
- SDP_TRACE_DEBUG(
- "%s, device=%s is only accept AVRCP 1.4, reply AVRCP 1.4 "
- "instead.",
- __func__, p_ccb->device_address.ToString().c_str());
- memcpy(&attr_sav, p_attr, sizeof(tSDP_ATTRIBUTE));
- attr_sav.value_ptr[attr_sav.len - 1] = 0x04;
- p_attr = &attr_sav;
- }
/* Check if attribute fits. Assume 3-byte value type/length */
rem_len = max_list_len - (int16_t)(p_rsp - &p_ccb->rsp_list[0]);
@@ -843,3 +829,5 @@ static void process_service_search_attr_req(tCONN_CB* p_ccb, uint16_t trans_num,
/* Send the buffer through L2CAP */
L2CA_DataWrite(p_ccb->connection_id, p_buf);
}
+
+#endif /* SDP_SERVER_ENABLED == TRUE */
diff --git a/stack/sdp/sdp_utils.cc b/stack/sdp/sdp_utils.cc
index 3fbafb21f..f66a8fd39 100644
--- a/stack/sdp/sdp_utils.cc
+++ b/stack/sdp/sdp_utils.cc
@@ -31,11 +31,10 @@
#include "bt_types.h"
#include "btif_config.h"
-#include "avrc_defs.h"
#include "sdp_api.h"
#include "sdpint.h"
-#include "stack/include/stack_metrics_logging.h"
+#include "common/metrics.h"
using bluetooth::Uuid;
static const uint8_t sdp_base_uuid[] = {0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
@@ -166,15 +165,16 @@ void sdpu_log_attribute_metrics(const RawAddress& bda,
}
// Log the existence of a profile role
// This can be different from Bluetooth Profile Descriptor List
- log_sdp_attribute(bda, service_uuid, 0, 0, nullptr);
+ bluetooth::common::LogSdpAttribute(bda, service_uuid, 0, 0, nullptr);
// Log profile version from Bluetooth Profile Descriptor List
auto uuid_version_array = sdpu_find_profile_version(p_rec);
for (const auto& uuid_version_pair : uuid_version_array) {
uint16_t profile_uuid = uuid_version_pair.first;
uint16_t version = uuid_version_pair.second;
auto version_array = to_little_endian_array(version);
- log_sdp_attribute(bda, profile_uuid, ATTR_ID_BT_PROFILE_DESC_LIST,
- version_array.size(), version_array.data());
+ bluetooth::common::LogSdpAttribute(
+ bda, profile_uuid, ATTR_ID_BT_PROFILE_DESC_LIST, version_array.size(),
+ version_array.data());
}
// Log protocol version from Protocol Descriptor List
uint16_t protocol_uuid = 0;
@@ -200,8 +200,9 @@ void sdpu_log_attribute_metrics(const RawAddress& bda,
if (protocol_elements.num_params >= 1) {
uint16_t version = protocol_elements.params[0];
auto version_array = to_little_endian_array(version);
- log_sdp_attribute(bda, protocol_uuid, ATTR_ID_PROTOCOL_DESC_LIST,
- version_array.size(), version_array.data());
+ bluetooth::common::LogSdpAttribute(
+ bda, protocol_uuid, ATTR_ID_PROTOCOL_DESC_LIST,
+ version_array.size(), version_array.data());
}
}
}
@@ -221,8 +222,9 @@ void sdpu_log_attribute_metrics(const RawAddress& bda,
}
uint16_t supported_features = p_attr->attr_value.v.u16;
auto version_array = to_little_endian_array(supported_features);
- log_sdp_attribute(bda, service_uuid, ATTR_ID_SUPPORTED_FEATURES,
- version_array.size(), version_array.data());
+ bluetooth::common::LogSdpAttribute(
+ bda, service_uuid, ATTR_ID_SUPPORTED_FEATURES, version_array.size(),
+ version_array.data());
break;
}
case UUID_SERVCLASS_MESSAGE_NOTIFICATION:
@@ -234,8 +236,9 @@ void sdpu_log_attribute_metrics(const RawAddress& bda,
}
uint32_t map_supported_features = p_attr->attr_value.v.u32;
auto features_array = to_little_endian_array(map_supported_features);
- log_sdp_attribute(bda, service_uuid, ATTR_ID_MAP_SUPPORTED_FEATURES,
- features_array.size(), features_array.data());
+ bluetooth::common::LogSdpAttribute(
+ bda, service_uuid, ATTR_ID_MAP_SUPPORTED_FEATURES,
+ features_array.size(), features_array.data());
break;
}
case UUID_SERVCLASS_PBAP_PCE:
@@ -247,8 +250,9 @@ void sdpu_log_attribute_metrics(const RawAddress& bda,
}
uint32_t pbap_supported_features = p_attr->attr_value.v.u32;
auto features_array = to_little_endian_array(pbap_supported_features);
- log_sdp_attribute(bda, service_uuid, ATTR_ID_PBAP_SUPPORTED_FEATURES,
- features_array.size(), features_array.data());
+ bluetooth::common::LogSdpAttribute(
+ bda, service_uuid, ATTR_ID_PBAP_SUPPORTED_FEATURES,
+ features_array.size(), features_array.data());
break;
}
}
@@ -261,13 +265,13 @@ void sdpu_log_attribute_metrics(const RawAddress& bda,
tSDP_DI_GET_RECORD di_record = {};
if (SDP_GetDiRecord(1, &di_record, p_db) == SDP_SUCCESS) {
auto version_array = to_little_endian_array(di_record.spec_id);
- log_sdp_attribute(bda, UUID_SERVCLASS_PNP_INFORMATION,
- ATTR_ID_SPECIFICATION_ID, version_array.size(),
- version_array.data());
+ bluetooth::common::LogSdpAttribute(
+ bda, UUID_SERVCLASS_PNP_INFORMATION, ATTR_ID_SPECIFICATION_ID,
+ version_array.size(), version_array.data());
std::stringstream ss;
// [N - native]::SDP::[DIP - Device ID Profile]
ss << "N:SDP::DIP::" << loghex(di_record.rec.vendor_id_source);
- log_manufacturer_info(
+ bluetooth::common::LogManufacturerInfo(
bda, android::bluetooth::DeviceInfoSrcEnum::DEVICE_INFO_INTERNAL,
ss.str(), loghex(di_record.rec.vendor), loghex(di_record.rec.product),
loghex(di_record.rec.version), "");
@@ -1151,41 +1155,3 @@ uint8_t* sdpu_build_partial_attrib_entry(uint8_t* p_out, tSDP_ATTRIBUTE* p_attr,
osi_free(p_attr_buff);
return p_out;
}
-/*******************************************************************************
- *
- * Function sdpu_is_avrcp_profile_description_list
- *
- * Description This function is to check if attirbute contain AVRCP profile
- * description list
- *
- * p_attr: attibute to be check
- *
- * Returns AVRCP profile version if matched, else 0
- *
- ******************************************************************************/
-uint16_t sdpu_is_avrcp_profile_description_list(tSDP_ATTRIBUTE* p_attr) {
- if (p_attr->id != ATTR_ID_BT_PROFILE_DESC_LIST || p_attr->len != 8) {
- return 0;
- }
-
- uint8_t* p_uuid = p_attr->value_ptr + 3;
- // Check if AVRCP profile UUID
- if (p_uuid[0] != 0x11 || p_uuid[1] != 0xe) {
- return 0;
- }
- uint8_t p_version = *(p_uuid + 4);
- switch (p_version) {
- case 0x0:
- return AVRC_REV_1_0;
- case 0x3:
- return AVRC_REV_1_3;
- case 0x4:
- return AVRC_REV_1_4;
- case 0x5:
- return AVRC_REV_1_5;
- case 0x6:
- return AVRC_REV_1_6;
- default:
- return 0;
- }
-}
diff --git a/stack/sdp/sdpint.h b/stack/sdp/sdpint.h
index 770bf7fed..af9ccb824 100644
--- a/stack/sdp/sdpint.h
+++ b/stack/sdp/sdpint.h
@@ -106,6 +106,7 @@ typedef struct {
tSDP_RECORD record[SDP_MAX_RECORDS];
} tSDP_DB;
+#if (SDP_SERVER_ENABLED == TRUE)
/* Continuation information for the SDP server response */
typedef struct {
uint16_t next_attr_index; /* attr index for next continuation response */
@@ -118,6 +119,7 @@ typedef struct {
uint16_t attr_offset; /* offset within the attr to keep trak of partial
attributes in the responses */
} tSDP_CONT_INFO;
+#endif /* SDP_SERVER_ENABLED == TRUE */
/* Define the SDP Connection Control Block */
typedef struct {
@@ -150,6 +152,9 @@ typedef struct {
uint16_t cur_handle; /* Current handle being processed */
uint16_t transaction_id;
uint16_t disconnect_reason; /* Disconnect reason */
+#if (SDP_BROWSE_PLUS == TRUE)
+ uint16_t cur_uuid_idx;
+#endif
#define SDP_DISC_WAIT_CONN 0
#define SDP_DISC_WAIT_HANDLES 1
@@ -160,9 +165,11 @@ typedef struct {
uint8_t disc_state;
uint8_t is_attr_search;
+#if (SDP_SERVER_ENABLED == TRUE)
uint16_t cont_offset; /* Continuation state data in the server response */
tSDP_CONT_INFO cont_info; /* structure to hold continuation information for
the server response */
+#endif /* SDP_SERVER_ENABLED == TRUE */
} tCONN_CB;
@@ -170,7 +177,9 @@ typedef struct {
typedef struct {
tL2CAP_CFG_INFO l2cap_my_cfg; /* My L2CAP config */
tCONN_CB ccb[SDP_MAX_CONNECTIONS];
+#if (SDP_SERVER_ENABLED == TRUE)
tSDP_DB server_db;
+#endif
tL2CAP_APPL_INFO reg_info; /* L2CAP Registration info */
uint16_t max_attr_list_size; /* Max attribute list size to use */
uint16_t max_recs_per_search; /* Max records we want per seaarch */
@@ -183,7 +192,7 @@ extern tSDP_CB sdp_cb;
/* Functions provided by sdp_main.cc */
extern void sdp_init(void);
extern void sdp_free(void);
-extern void sdp_disconnect(tCONN_CB* p_ccb, tSDP_REASON reason);
+extern void sdp_disconnect(tCONN_CB* p_ccb, uint16_t reason);
extern void sdp_conn_timer_timeout(void* data);
@@ -226,7 +235,6 @@ extern uint16_t sdpu_get_attrib_entry_len(tSDP_ATTRIBUTE* p_attr);
extern uint8_t* sdpu_build_partial_attrib_entry(uint8_t* p_out,
tSDP_ATTRIBUTE* p_attr,
uint16_t len, uint16_t* offset);
-extern uint16_t sdpu_is_avrcp_profile_description_list(tSDP_ATTRIBUTE* p_attr);
/* Functions provided by sdp_db.cc
*/
@@ -239,7 +247,11 @@ extern tSDP_ATTRIBUTE* sdp_db_find_attr_in_rec(tSDP_RECORD* p_rec,
/* Functions provided by sdp_server.cc
*/
+#if (SDP_SERVER_ENABLED == TRUE)
extern void sdp_server_handle_client_req(tCONN_CB* p_ccb, BT_HDR* p_msg);
+#else
+#define sdp_server_handle_client_req(p_ccb, p_msg)
+#endif
/* Functions provided by sdp_discovery.cc
*/
diff --git a/stack/smp/smp_act.cc b/stack/smp/smp_act.cc
index 3afae8b18..03d73f781 100644
--- a/stack/smp/smp_act.cc
+++ b/stack/smp/smp_act.cc
@@ -16,26 +16,19 @@
*
******************************************************************************/
-#define LOG_TAG "smp_act"
-
+#include <cutils/log.h>
+#include <log/log.h>
#include <string.h>
#include "btif_api.h"
#include "btif_common.h"
#include "btif_storage.h"
#include "device/include/interop.h"
#include "internal_include/bt_target.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/acl_api.h"
+#include "stack/btm/btm_int.h"
#include "stack/include/l2c_api.h"
-#include "stack/include/smp_api_types.h"
#include "stack/smp/p_256_ecc_pp.h"
#include "stack/smp/smp_int.h"
-#include "types/raw_address.h"
-
-extern tBTM_CB btm_cb;
+#include "utils/include/bt_utils.h"
#define SMP_KEY_DIST_TYPE_MAX 4
@@ -46,8 +39,19 @@ const tSMP_ACT smp_distribute_act[] = {
smp_set_derive_link_key /* SMP_SEC_KEY_TYPE_LK - '1' bit index */
};
+static bool lmp_version_below(const RawAddress& bda, uint8_t version) {
+ tACL_CONN* acl = btm_bda_to_acl(bda, BT_TRANSPORT_LE);
+ if (acl == NULL || acl->lmp_version == 0) {
+ SMP_TRACE_WARNING("%s cannot retrieve LMP version...", __func__);
+ return false;
+ }
+ SMP_TRACE_WARNING("%s LMP version %d < %d", __func__, acl->lmp_version,
+ version);
+ return acl->lmp_version < version;
+}
+
static bool pts_test_send_authentication_complete_failure(tSMP_CB* p_cb) {
- tSMP_STATUS reason = p_cb->cert_failure;
+ uint8_t reason = p_cb->cert_failure;
if (reason == SMP_PAIR_AUTH_FAIL || reason == SMP_PAIR_FAIL_UNKNOWN ||
reason == SMP_PAIR_NOT_SUPPORT || reason == SMP_PASSKEY_ENTRY_FAIL ||
reason == SMP_REPEATED_ATTEMPTS) {
@@ -75,7 +79,7 @@ static void smp_update_key_mask(tSMP_CB* p_cb, uint8_t key_type, bool recv) {
** being exchanged with the peer */
p_cb->local_i_key &= ~key_type;
p_cb->local_r_key &= ~key_type;
- } else if (p_cb->role == HCI_ROLE_PERIPHERAL) {
+ } else if (p_cb->role == HCI_ROLE_SLAVE) {
if (recv)
p_cb->local_i_key &= ~key_type;
else
@@ -98,8 +102,8 @@ static void smp_update_key_mask(tSMP_CB* p_cb, uint8_t key_type, bool recv) {
******************************************************************************/
void smp_send_app_cback(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
tSMP_EVT_DATA cb_data;
- tBTM_STATUS callback_rc;
- uint8_t remote_lmp_version = 0;
+ tSMP_STATUS callback_rc;
+ SMP_TRACE_DEBUG("%s p_cb->cb_evt=%d", __func__, p_cb->cb_evt);
if (p_cb->p_callback && p_cb->cb_evt != 0) {
switch (p_cb->cb_evt) {
case SMP_IO_CAP_REQ_EVT:
@@ -109,7 +113,7 @@ void smp_send_app_cback(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
cb_data.io_req.max_key_size = SMP_MAX_ENC_KEY_SIZE;
cb_data.io_req.init_keys = p_cb->local_i_key;
cb_data.io_req.resp_keys = p_cb->local_r_key;
- LOG_DEBUG("Notify app io_cap = %hhu", cb_data.io_req.io_cap);
+ SMP_TRACE_WARNING("io_cap = %d", cb_data.io_req.io_cap);
break;
case SMP_NC_REQ_EVT:
@@ -132,14 +136,16 @@ void smp_send_app_cback(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
break;
default:
- LOG_ERROR("Unexpected event:%hhu", p_cb->cb_evt);
break;
}
callback_rc =
(*p_cb->p_callback)(p_cb->cb_evt, p_cb->pairing_bda, &cb_data);
- if (callback_rc == BTM_SUCCESS) {
+ SMP_TRACE_DEBUG("%s: callback_rc=%d p_cb->cb_evt=%d", __func__,
+ callback_rc, p_cb->cb_evt);
+
+ if (callback_rc == SMP_SUCCESS) {
switch (p_cb->cb_evt) {
case SMP_IO_CAP_REQ_EVT:
p_cb->loc_auth_req = cb_data.io_req.auth_req;
@@ -150,14 +156,14 @@ void smp_send_app_cback(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
p_cb->local_r_key = cb_data.io_req.resp_keys;
if (!(p_cb->loc_auth_req & SMP_AUTH_BOND)) {
- LOG_INFO("Non bonding: No keys will be exchanged");
+ SMP_TRACE_WARNING("Non bonding: No keys will be exchanged");
p_cb->local_i_key = 0;
p_cb->local_r_key = 0;
}
- LOG_DEBUG(
- "Remote request IO capabilities precondition auth_req: 0x%02x,"
- " io_cap: %d loc_oob_flag: %d loc_enc_size: %d, "
+ SMP_TRACE_WARNING(
+ "rcvd auth_req: 0x%02x, io_cap: %d "
+ "loc_oob_flag: %d loc_enc_size: %d, "
"local_i_key: 0x%02x, local_r_key: 0x%02x",
p_cb->loc_auth_req, p_cb->local_io_capability, p_cb->loc_oob_flag,
p_cb->loc_enc_size, p_cb->local_i_key, p_cb->local_r_key);
@@ -169,34 +175,23 @@ void smp_send_app_cback(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
p_cb->loc_auth_req |= SMP_SC_SUPPORT_BIT;
}
- if (!BTM_ReadRemoteVersion(p_cb->pairing_bda, &remote_lmp_version,
- nullptr, nullptr)) {
- LOG_WARN(
- "SMP Unable to determine remote security authentication "
- "remote_lmp_version:%hu",
- remote_lmp_version);
+ if (!p_cb->secure_connections_only_mode_required &&
+ (!(p_cb->loc_auth_req & SMP_SC_SUPPORT_BIT) ||
+ lmp_version_below(p_cb->pairing_bda, HCI_PROTO_VERSION_4_2) ||
+ interop_match_addr(INTEROP_DISABLE_LE_SECURE_CONNECTIONS,
+ (const RawAddress*)&p_cb->pairing_bda))) {
+ p_cb->loc_auth_req &= ~SMP_SC_SUPPORT_BIT;
+ p_cb->loc_auth_req &= ~SMP_KP_SUPPORT_BIT;
+ p_cb->local_i_key &= ~SMP_SEC_KEY_TYPE_LK;
+ p_cb->local_r_key &= ~SMP_SEC_KEY_TYPE_LK;
}
- if (!bluetooth::shim::is_gd_acl_enabled()) {
- if (!p_cb->secure_connections_only_mode_required &&
- (!(p_cb->loc_auth_req & SMP_SC_SUPPORT_BIT) ||
- remote_lmp_version < HCI_PROTO_VERSION_4_2 ||
- interop_match_addr(INTEROP_DISABLE_LE_SECURE_CONNECTIONS,
- (const RawAddress*)&p_cb->pairing_bda))) {
- p_cb->loc_auth_req &= ~SMP_SC_SUPPORT_BIT;
- p_cb->loc_auth_req &= ~SMP_KP_SUPPORT_BIT;
- p_cb->local_i_key &= ~SMP_SEC_KEY_TYPE_LK;
- p_cb->local_r_key &= ~SMP_SEC_KEY_TYPE_LK;
- }
-
- if (remote_lmp_version < HCI_PROTO_VERSION_5_0) {
- p_cb->loc_auth_req &= ~SMP_H7_SUPPORT_BIT;
- }
+ if (lmp_version_below(p_cb->pairing_bda, HCI_PROTO_VERSION_5_0)) {
+ p_cb->loc_auth_req &= ~SMP_H7_SUPPORT_BIT;
}
- LOG_DEBUG(
- "Remote request IO capabilities postcondition auth_req: 0x%02x,"
- " local_i_key: 0x%02x, local_r_key: 0x%02x",
+ SMP_TRACE_WARNING(
+ "set auth_req: 0x%02x, local_i_key: 0x%02x, local_r_key: 0x%02x",
p_cb->loc_auth_req, p_cb->local_i_key, p_cb->local_r_key);
smp_sm_event(p_cb, SMP_IO_RSP_EVT, NULL);
@@ -211,7 +206,7 @@ void smp_send_app_cback(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
p_cb->local_i_key &= ~SMP_SEC_KEY_TYPE_LK;
p_cb->local_r_key &= ~SMP_SEC_KEY_TYPE_LK;
- LOG_DEBUG(
+ SMP_TRACE_WARNING(
"for SMP over BR max_key_size: 0x%02x, local_i_key: 0x%02x, "
"local_r_key: 0x%02x, p_cb->loc_auth_req: 0x%02x",
p_cb->loc_enc_size, p_cb->local_i_key, p_cb->local_r_key,
@@ -219,13 +214,6 @@ void smp_send_app_cback(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
smp_br_state_machine_event(p_cb, SMP_BR_KEYS_RSP_EVT, NULL);
break;
-
- // Expected, but nothing to do
- case SMP_SC_LOC_OOB_DATA_UP_EVT:
- break;
-
- default:
- LOG_ERROR("Unexpected event: %hhu", p_cb->cb_evt);
}
}
}
@@ -234,6 +222,8 @@ void smp_send_app_cback(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
p_cb->discard_sec_req = false;
smp_sm_event(p_cb, SMP_DISCARD_SEC_REQ_EVT, NULL);
}
+
+ SMP_TRACE_DEBUG("%s: return", __func__);
}
/*******************************************************************************
@@ -262,7 +252,7 @@ void smp_send_pair_req(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
tBTM_SEC_DEV_REC* p_dev_rec = btm_find_dev(p_cb->pairing_bda);
SMP_TRACE_DEBUG("%s", __func__);
- /* erase all keys when central sends pairing req*/
+ /* erase all keys when master sends pairing req*/
if (p_dev_rec) btm_sec_clear_ble_keys(p_dev_rec);
/* do not manipulate the key, let app decide,
leave out to BTM to mandate key distribution for bonding case */
@@ -298,7 +288,7 @@ void smp_send_confirm(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
/*******************************************************************************
* Function smp_send_init
- * Description process pairing initializer to peripheral device
+ * Description process pairing initializer to slave device
******************************************************************************/
void smp_send_init(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
SMP_TRACE_DEBUG("%s", __func__);
@@ -361,9 +351,9 @@ void smp_send_enc_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
smp_update_key_mask(p_cb, SMP_SEC_KEY_TYPE_ENC, false);
smp_send_cmd(SMP_OPCODE_ENCRYPT_INFO, p_cb);
- smp_send_cmd(SMP_OPCODE_CENTRAL_ID, p_cb);
+ smp_send_cmd(SMP_OPCODE_MASTER_ID, p_cb);
- /* save the DIV and key size information when acting as peripheral device */
+ /* save the DIV and key size information when acting as slave device */
le_key.lenc_key.ltk = p_cb->ltk;
le_key.lenc_key.div = p_cb->div;
le_key.lenc_key.key_size = p_cb->loc_enc_size;
@@ -394,6 +384,7 @@ void smp_send_id_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
(p_cb->loc_auth_req & SMP_AUTH_BOND))
btm_sec_save_le_key(p_cb->pairing_bda, BTM_LE_KEY_LID, &le_key, true);
+ SMP_TRACE_WARNING("%s", __func__);
smp_key_distribution_by_transport(p_cb, NULL);
}
@@ -437,7 +428,7 @@ void smp_proc_sec_req(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
SMP_TRACE_DEBUG("%s: auth_req=0x%x", __func__, auth_req);
- p_cb->cb_evt = SMP_EVT_NONE;
+ p_cb->cb_evt = 0;
btm_ble_link_sec_check(p_cb->pairing_bda, auth_req, &sec_req_act);
@@ -524,8 +515,8 @@ void smp_proc_pair_cmd(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
SMP_TRACE_DEBUG("%s: pairing_bda=%s", __func__,
p_cb->pairing_bda.ToString().c_str());
- /* erase all keys if it is peripheral proc pairing req */
- if (p_dev_rec && (p_cb->role == HCI_ROLE_PERIPHERAL))
+ /* erase all keys if it is slave proc pairing req */
+ if (p_dev_rec && (p_cb->role == HCI_ROLE_SLAVE))
btm_sec_clear_ble_keys(p_dev_rec);
p_cb->flags |= SMP_PAIR_FLAG_ENC_AFTER_PAIR;
@@ -555,16 +546,16 @@ void smp_proc_pair_cmd(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
// PTS Testing failure modes
if (pts_test_send_authentication_complete_failure(p_cb)) return;
- if (p_cb->role == HCI_ROLE_PERIPHERAL) {
+ if (p_cb->role == HCI_ROLE_SLAVE) {
if (!(p_cb->flags & SMP_PAIR_FLAGS_WE_STARTED_DD)) {
- /* peer (central) started pairing sending Pairing Request */
+ /* peer (master) started pairing sending Pairing Request */
p_cb->local_i_key = p_cb->peer_i_key;
p_cb->local_r_key = p_cb->peer_r_key;
p_cb->cb_evt = SMP_SEC_REQUEST_EVT;
} else /* update local i/r key according to pairing request */
{
- /* pairing started with this side (peripheral) sending Security Request */
+ /* pairing started with this side (slave) sending Security Request */
p_cb->local_i_key &= p_cb->peer_i_key;
p_cb->local_r_key &= p_cb->peer_r_key;
p_cb->selected_association_model = smp_select_association_model(p_cb);
@@ -574,8 +565,7 @@ void smp_proc_pair_cmd(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
(p_cb->selected_association_model ==
SMP_MODEL_SEC_CONN_JUSTWORKS))) {
SMP_TRACE_ERROR(
- "%s: pairing failed - peripheral requires secure connection only "
- "mode",
+ "%s: pairing failed - slave requires secure connection only mode",
__func__);
tSMP_INT_DATA smp_int_data;
smp_int_data.status = SMP_PAIR_AUTH_FAIL;
@@ -589,7 +579,7 @@ void smp_proc_pair_cmd(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
smp_send_pair_rsp(p_cb, NULL);
}
}
- } else /* Central receives pairing response */
+ } else /* Master receives pairing response */
{
p_cb->selected_association_model = smp_select_association_model(p_cb);
@@ -597,8 +587,8 @@ void smp_proc_pair_cmd(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
(!(p_cb->le_secure_connections_mode_is_used) ||
(p_cb->selected_association_model == SMP_MODEL_SEC_CONN_JUSTWORKS))) {
SMP_TRACE_ERROR(
- "Central requires secure connection only mode "
- "but it can't be provided -> Central fails pairing");
+ "Master requires secure connection only mode "
+ "but it can't be provided -> Master fails pairing");
tSMP_INT_DATA smp_int_data;
smp_int_data.status = SMP_PAIR_AUTH_FAIL;
smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &smp_int_data);
@@ -787,7 +777,7 @@ void smp_process_keypress_notification(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
if (p != NULL) {
STREAM_TO_UINT8(p_cb->peer_keypress_notification, p);
} else {
- p_cb->peer_keypress_notification = SMP_SC_KEY_OUT_OF_RANGE;
+ p_cb->peer_keypress_notification = BTM_SP_KEY_OUT_OF_RANGE;
}
p_cb->cb_evt = SMP_PEER_KEYPR_NOT_EVT;
}
@@ -803,16 +793,15 @@ void smp_br_process_pairing_command(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
SMP_TRACE_DEBUG("%s", __func__);
/* rejecting BR pairing request over non-SC BR link */
- if (!p_dev_rec->new_encryption_key_is_p256 &&
- p_cb->role == HCI_ROLE_PERIPHERAL) {
+ if (!p_dev_rec->new_encryption_key_is_p256 && p_cb->role == HCI_ROLE_SLAVE) {
tSMP_INT_DATA smp_int_data;
smp_int_data.status = SMP_XTRANS_DERIVE_NOT_ALLOW;
smp_br_state_machine_event(p_cb, SMP_BR_AUTH_CMPL_EVT, &smp_int_data);
return;
}
- /* erase all keys if it is peripheral proc pairing req*/
- if (p_dev_rec && (p_cb->role == HCI_ROLE_PERIPHERAL))
+ /* erase all keys if it is slave proc pairing req*/
+ if (p_dev_rec && (p_cb->role == HCI_ROLE_SLAVE))
btm_sec_clear_ble_keys(p_dev_rec);
p_cb->flags |= SMP_PAIR_FLAG_ENC_AFTER_PAIR;
@@ -839,20 +828,19 @@ void smp_br_process_pairing_command(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
return;
}
- /* peer (central) started pairing sending Pairing Request */
- /* or being central device always use received i/r key as keys to distribute
- */
+ /* peer (master) started pairing sending Pairing Request */
+ /* or being master device always use received i/r key as keys to distribute */
p_cb->local_i_key = p_cb->peer_i_key;
p_cb->local_r_key = p_cb->peer_r_key;
- if (p_cb->role == HCI_ROLE_PERIPHERAL) {
+ if (p_cb->role == HCI_ROLE_SLAVE) {
p_dev_rec->new_encryption_key_is_p256 = false;
/* shortcut to skip Security Grant step */
p_cb->cb_evt = SMP_BR_KEYS_REQ_EVT;
} else {
- /* Central receives pairing response */
+ /* Master receives pairing response */
SMP_TRACE_DEBUG(
- "%s central rcvs valid PAIRING RESPONSE."
+ "%s master rcvs valid PAIRING RESPONSE."
" Supposed to move to key distribution phase. ",
__func__);
}
@@ -891,8 +879,8 @@ void smp_br_check_authorization_request(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
p_cb->local_r_key &= ~SMP_SEC_KEY_TYPE_LK;
/* In LE SC mode only IRK, IAI, CSRK are exchanged with the peer.
- ** Set local_r_key on central to expect only these keys. */
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ ** Set local_r_key on master to expect only these keys. */
+ if (p_cb->role == HCI_ROLE_MASTER) {
p_cb->local_r_key &= (SMP_SEC_KEY_TYPE_ID | SMP_SEC_KEY_TYPE_CSRK);
}
@@ -912,8 +900,8 @@ void smp_br_check_authorization_request(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
(p_cb->local_i_key || p_cb->local_r_key)) {
smp_br_state_machine_event(p_cb, SMP_BR_BOND_REQ_EVT, NULL);
- /* if no peer key is expected, start central key distribution */
- if (p_cb->role == HCI_ROLE_CENTRAL && p_cb->local_r_key == 0)
+ /* if no peer key is expected, start master key distribution */
+ if (p_cb->role == HCI_ROLE_MASTER && p_cb->local_r_key == 0)
smp_key_distribution_by_transport(p_cb, NULL);
} else {
tSMP_INT_DATA smp_int_data;
@@ -928,11 +916,11 @@ void smp_br_check_authorization_request(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
* used.
******************************************************************************/
void smp_br_select_next_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- SMP_TRACE_DEBUG("%s role=%d (0-central) r_keys=0x%x i_keys=0x%x", __func__,
+ SMP_TRACE_DEBUG("%s role=%d (0-master) r_keys=0x%x i_keys=0x%x", __func__,
p_cb->role, p_cb->local_r_key, p_cb->local_i_key);
- if (p_cb->role == HCI_ROLE_PERIPHERAL ||
- (!p_cb->local_r_key && p_cb->role == HCI_ROLE_CENTRAL)) {
+ if (p_cb->role == HCI_ROLE_SLAVE ||
+ (!p_cb->local_r_key && p_cb->role == HCI_ROLE_MASTER)) {
smp_key_pick_key(p_cb, p_data);
}
@@ -969,8 +957,8 @@ void smp_proc_enc_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
smp_key_distribution(p_cb, NULL);
}
-/** process central ID from peripheral device */
-void smp_proc_central_id(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
+/** process master ID from slave device */
+void smp_proc_master_id(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
uint8_t* p = p_data->p_data;
tBTM_LE_KEY_VALUE le_key;
@@ -1095,10 +1083,10 @@ void smp_proc_compare(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
if (p_cb->peer_enc_size < p_cb->loc_enc_size)
p_cb->loc_enc_size = p_cb->peer_enc_size;
- if (p_cb->role == HCI_ROLE_PERIPHERAL)
+ if (p_cb->role == HCI_ROLE_SLAVE)
smp_sm_event(p_cb, SMP_RAND_EVT, NULL);
else {
- /* central device always use received i/r key as keys to distribute */
+ /* master device always use received i/r key as keys to distribute */
p_cb->local_i_key = p_cb->peer_i_key;
p_cb->local_r_key = p_cb->peer_r_key;
@@ -1200,9 +1188,9 @@ void smp_check_auth_req(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
}
/* In LE SC mode only IRK, IAI, CSRK are exchanged with the peer.
- ** Set local_r_key on central to expect only these keys.
+ ** Set local_r_key on master to expect only these keys.
*/
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ if (p_cb->role == HCI_ROLE_MASTER) {
p_cb->local_r_key &= (SMP_SEC_KEY_TYPE_ID | SMP_SEC_KEY_TYPE_CSRK);
}
} else {
@@ -1230,9 +1218,8 @@ void smp_check_auth_req(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
if (p_cb->flags & SMP_PAIR_FLAG_ENC_AFTER_PAIR)
smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &smp_int_data);
/* if enc failed for old security information */
- /* if central device, clean up and abck to idle; peripheral device do
- * nothing */
- else if (p_cb->role == HCI_ROLE_CENTRAL) {
+ /* if master device, clean up and abck to idle; slave device do nothing */
+ else if (p_cb->role == HCI_ROLE_MASTER) {
smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &smp_int_data);
}
}
@@ -1243,8 +1230,8 @@ void smp_check_auth_req(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
* Description Pick a key distribution function based on the key mask.
******************************************************************************/
void smp_key_pick_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- uint8_t key_to_dist = (p_cb->role == HCI_ROLE_PERIPHERAL) ? p_cb->local_r_key
- : p_cb->local_i_key;
+ uint8_t key_to_dist =
+ (p_cb->role == HCI_ROLE_SLAVE) ? p_cb->local_r_key : p_cb->local_i_key;
uint8_t i = 0;
SMP_TRACE_DEBUG("%s key_to_dist=0x%x", __func__, key_to_dist);
@@ -1264,11 +1251,11 @@ void smp_key_pick_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
* Description start key distribution if required.
******************************************************************************/
void smp_key_distribution(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- SMP_TRACE_DEBUG("%s role=%d (0-central) r_keys=0x%x i_keys=0x%x", __func__,
+ SMP_TRACE_DEBUG("%s role=%d (0-master) r_keys=0x%x i_keys=0x%x", __func__,
p_cb->role, p_cb->local_r_key, p_cb->local_i_key);
- if (p_cb->role == HCI_ROLE_PERIPHERAL ||
- (!p_cb->local_r_key && p_cb->role == HCI_ROLE_CENTRAL)) {
+ if (p_cb->role == HCI_ROLE_SLAVE ||
+ (!p_cb->local_r_key && p_cb->role == HCI_ROLE_MASTER)) {
smp_key_pick_key(p_cb, p_data);
}
@@ -1294,7 +1281,7 @@ void smp_key_distribution(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
/*
* Instead of declaring authorization complete immediately,
* delay the event from being sent by SMP_DELAYED_AUTH_TIMEOUT_MS.
- * This allows the peripheral to send over Pairing Failed if the
+ * This allows the slave to send over Pairing Failed if the
* last key is rejected. During this waiting window, the
* state should remain in SMP_STATE_BOND_PENDING.
*/
@@ -1318,7 +1305,7 @@ void smp_key_distribution(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
*
******************************************************************************/
void smp_decide_association_model(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- tSMP_EVENT int_evt = SMP_NOP_EVT;
+ uint8_t int_evt = 0;
tSMP_INT_DATA smp_int_data;
SMP_TRACE_DEBUG("%s Association Model = %d", __func__,
@@ -1326,7 +1313,7 @@ void smp_decide_association_model(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
switch (p_cb->selected_association_model) {
case SMP_MODEL_ENCRYPTION_ONLY: /* TK = 0, go calculate Confirm */
- if (p_cb->role == HCI_ROLE_CENTRAL &&
+ if (p_cb->role == HCI_ROLE_MASTER &&
((p_cb->peer_auth_req & SMP_AUTH_YN_BIT) != 0) &&
((p_cb->loc_auth_req & SMP_AUTH_YN_BIT) == 0)) {
SMP_TRACE_ERROR(
@@ -1414,39 +1401,33 @@ void smp_decide_association_model(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
/*******************************************************************************
* Function smp_process_io_response
- * Description process IO response for a peripheral device.
+ * Description process IO response for a slave device.
******************************************************************************/
void smp_process_io_response(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
SMP_TRACE_DEBUG("%s", __func__);
if (p_cb->flags & SMP_PAIR_FLAGS_WE_STARTED_DD) {
- /* pairing started by local (peripheral) Security Request */
+ /* pairing started by local (slave) Security Request */
smp_set_state(SMP_STATE_SEC_REQ_PENDING);
smp_send_cmd(SMP_OPCODE_SEC_REQ, p_cb);
} else /* plan to send pairing respond */
{
- /* pairing started by peer (central) Pairing Request */
+ /* pairing started by peer (master) Pairing Request */
p_cb->selected_association_model = smp_select_association_model(p_cb);
if (p_cb->secure_connections_only_mode_required &&
(!(p_cb->le_secure_connections_mode_is_used) ||
(p_cb->selected_association_model == SMP_MODEL_SEC_CONN_JUSTWORKS))) {
SMP_TRACE_ERROR(
- "Peripheral requires secure connection only mode "
- "but it can't be provided -> Peripheral fails pairing");
+ "Slave requires secure connection only mode "
+ "but it can't be provided -> Slave fails pairing");
tSMP_INT_DATA smp_int_data;
smp_int_data.status = SMP_PAIR_AUTH_FAIL;
smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &smp_int_data);
return;
}
- // If we are doing SMP_MODEL_SEC_CONN_OOB we don't need to request OOB data
- // locally if loc_oob_flag == 0x00 b/c there is no OOB data to give. In the
- // event the loc_oob_flag is another value, we should request the OOB data
- // locally. Which seems to cause it to make a TK REQUEST which is used for
- // the legacy flow which requires both sides to have OOB data.
- if (p_cb->selected_association_model == SMP_MODEL_SEC_CONN_OOB &&
- p_cb->loc_oob_flag != 0x00) {
+ if (p_cb->selected_association_model == SMP_MODEL_SEC_CONN_OOB) {
if (smp_request_oob_data(p_cb)) return;
}
@@ -1458,12 +1439,11 @@ void smp_process_io_response(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
}
/*******************************************************************************
- * Function smp_br_process_peripheral_keys_response
- * Description process application keys response for a peripheral device
+ * Function smp_br_process_slave_keys_response
+ * Description process application keys response for a slave device
* (BR/EDR transport).
******************************************************************************/
-void smp_br_process_peripheral_keys_response(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data) {
+void smp_br_process_slave_keys_response(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
smp_br_send_pair_response(p_cb, NULL);
}
@@ -1523,8 +1503,7 @@ void smp_idle_terminate(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
* saved.
* Actions:
* - invokes DHKey computation;
- * - on peripheral side invokes sending local public key to the
- *peer.
+ * - on slave side invokes sending local public key to the peer.
* - invokes SC phase 1 process.
******************************************************************************/
void smp_both_have_public_keys(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
@@ -1533,8 +1512,8 @@ void smp_both_have_public_keys(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
/* invokes DHKey computation */
smp_compute_dhkey(p_cb);
- /* on peripheral side invokes sending local public key to the peer */
- if (p_cb->role == HCI_ROLE_PERIPHERAL) smp_send_pair_public_key(p_cb, NULL);
+ /* on slave side invokes sending local public key to the peer */
+ if (p_cb->role == HCI_ROLE_SLAVE) smp_send_pair_public_key(p_cb, NULL);
smp_sm_event(p_cb, SMP_SC_DHKEY_CMPLT_EVT, NULL);
}
@@ -1598,20 +1577,20 @@ void smp_process_local_nonce(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
switch (p_cb->selected_association_model) {
case SMP_MODEL_SEC_CONN_JUSTWORKS:
case SMP_MODEL_SEC_CONN_NUM_COMP:
- if (p_cb->role == HCI_ROLE_PERIPHERAL) {
- /* peripheral calculates and sends local commitment */
+ if (p_cb->role == HCI_ROLE_SLAVE) {
+ /* slave calculates and sends local commitment */
smp_calculate_local_commitment(p_cb);
smp_send_commitment(p_cb, NULL);
- /* peripheral has to wait for peer nonce */
+ /* slave has to wait for peer nonce */
smp_set_state(SMP_STATE_WAIT_NONCE);
- } else /* i.e. central */
+ } else /* i.e. master */
{
if (p_cb->flags & SMP_PAIR_FLAG_HAVE_PEER_COMM) {
- /* peripheral commitment is already received, send local nonce, wait
- * for remote nonce*/
+ /* slave commitment is already received, send local nonce, wait for
+ * remote nonce*/
SMP_TRACE_DEBUG(
- "central in assoc mode = %d "
- "already rcvd peripheral commitment - race condition",
+ "master in assoc mode = %d "
+ "already rcvd slave commitment - race condition",
p_cb->selected_association_model);
p_cb->flags &= ~SMP_PAIR_FLAG_HAVE_PEER_COMM;
smp_send_rand(p_cb, NULL);
@@ -1623,19 +1602,19 @@ void smp_process_local_nonce(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
case SMP_MODEL_SEC_CONN_PASSKEY_DISP:
smp_calculate_local_commitment(p_cb);
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ if (p_cb->role == HCI_ROLE_MASTER) {
smp_send_commitment(p_cb, NULL);
- } else /* peripheral */
+ } else /* slave */
{
if (p_cb->flags & SMP_PAIR_FLAG_HAVE_PEER_COMM) {
- /* central commitment is already received */
+ /* master commitment is already received */
smp_send_commitment(p_cb, NULL);
smp_set_state(SMP_STATE_WAIT_NONCE);
}
}
break;
case SMP_MODEL_SEC_CONN_OOB:
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ if (p_cb->role == HCI_ROLE_MASTER) {
smp_send_rand(p_cb, NULL);
}
@@ -1671,7 +1650,7 @@ void smp_process_peer_nonce(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
// PTS Testing failure modes (for LT)
if ((p_cb->cert_failure == SMP_NUMERIC_COMPAR_FAIL) &&
(p_cb->selected_association_model == SMP_MODEL_SEC_CONN_JUSTWORKS) &&
- (p_cb->role == HCI_ROLE_PERIPHERAL)) {
+ (p_cb->role == HCI_ROLE_SLAVE)) {
SMP_TRACE_ERROR("%s failure case = %d", __func__, p_cb->cert_failure);
tSMP_INT_DATA smp_int_data;
smp_int_data.status = SMP_NUMERIC_COMPAR_FAIL;
@@ -1683,8 +1662,8 @@ void smp_process_peer_nonce(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
switch (p_cb->selected_association_model) {
case SMP_MODEL_SEC_CONN_JUSTWORKS:
case SMP_MODEL_SEC_CONN_NUM_COMP:
- /* in these models only central receives commitment */
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ /* in these models only master receives commitment */
+ if (p_cb->role == HCI_ROLE_MASTER) {
if (!smp_check_commitment(p_cb)) {
tSMP_INT_DATA smp_int_data;
smp_int_data.status = SMP_CONFIRM_VALUE_ERR;
@@ -1693,7 +1672,7 @@ void smp_process_peer_nonce(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
break;
}
} else {
- /* peripheral sends local nonce */
+ /* slave sends local nonce */
smp_send_rand(p_cb, NULL);
}
@@ -1727,7 +1706,7 @@ void smp_process_peer_nonce(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
break;
}
- if (p_cb->role == HCI_ROLE_PERIPHERAL) {
+ if (p_cb->role == HCI_ROLE_SLAVE) {
smp_send_rand(p_cb, NULL);
}
@@ -1741,7 +1720,7 @@ void smp_process_peer_nonce(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
smp_sm_event(p_cb, SMP_SC_PHASE1_CMPLT_EVT, NULL);
break;
case SMP_MODEL_SEC_CONN_OOB:
- if (p_cb->role == HCI_ROLE_PERIPHERAL) {
+ if (p_cb->role == HCI_ROLE_SLAVE) {
smp_send_rand(p_cb, NULL);
}
@@ -1781,10 +1760,10 @@ void smp_match_dhkey_checks(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
if (p_cb->peer_enc_size < p_cb->loc_enc_size)
p_cb->loc_enc_size = p_cb->peer_enc_size;
- if (p_cb->role == HCI_ROLE_PERIPHERAL) {
+ if (p_cb->role == HCI_ROLE_SLAVE) {
smp_sm_event(p_cb, SMP_PAIR_DHKEY_CHCK_EVT, NULL);
} else {
- /* central device always use received i/r key as keys to distribute */
+ /* master device always use received i/r key as keys to distribute */
p_cb->local_i_key = p_cb->peer_i_key;
p_cb->local_r_key = p_cb->peer_r_key;
smp_sm_event(p_cb, SMP_ENC_REQ_EVT, NULL);
@@ -1809,8 +1788,8 @@ void smp_move_to_secure_connections_phase2(tSMP_CB* p_cb,
* Description generates event if dhkey check from the peer is already
* received.
*
- * Note It is supposed to be used on peripheral to prevent race
- *condition. It is supposed to be called after peripheral dhkey check is
+ * Note It is supposed to be used on slave to prevent race condition.
+ * It is supposed to be called after slave dhkey check is
* calculated.
******************************************************************************/
void smp_phase_2_dhkey_checks_are_present(tSMP_CB* p_cb,
@@ -1824,9 +1803,9 @@ void smp_phase_2_dhkey_checks_are_present(tSMP_CB* p_cb,
/*******************************************************************************
* Function smp_wait_for_both_public_keys
* Description generates SMP_BOTH_PUBL_KEYS_RCVD_EVT event when both local and
- * central public keys are available.
+ * master public keys are available.
*
- * Note on the peripheral it is used to prevent race condition.
+ * Note on the slave it is used to prevent race condition.
*
******************************************************************************/
void smp_wait_for_both_public_keys(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
@@ -1834,7 +1813,7 @@ void smp_wait_for_both_public_keys(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
if ((p_cb->flags & SMP_PAIR_FLAG_HAVE_PEER_PUBL_KEY) &&
(p_cb->flags & SMP_PAIR_FLAG_HAVE_LOCAL_PUBL_KEY)) {
- if ((p_cb->role == HCI_ROLE_PERIPHERAL) &&
+ if ((p_cb->role == HCI_ROLE_SLAVE) &&
((p_cb->req_oob_type == SMP_OOB_LOCAL) ||
(p_cb->req_oob_type == SMP_OOB_BOTH))) {
smp_set_state(SMP_STATE_PUBLIC_KEY_EXCH);
@@ -1937,21 +1916,32 @@ void smp_set_local_oob_random_commitment(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
p_cb->sc_oob_data.loc_oob_data.publ_key_used.x,
p_cb->sc_oob_data.loc_oob_data.randomizer, 0);
- p_cb->sc_oob_data.loc_oob_data.present = true;
+#if (SMP_DEBUG == TRUE)
+ uint8_t* p_print = NULL;
+ SMP_TRACE_DEBUG("local SC OOB data set:");
+ p_print = (uint8_t*)&p_cb->sc_oob_data.loc_oob_data.addr_sent_to;
+ smp_debug_print_nbyte_little_endian(p_print, "addr_sent_to",
+ sizeof(tBLE_BD_ADDR));
+ p_print = (uint8_t*)&p_cb->sc_oob_data.loc_oob_data.private_key_used;
+ smp_debug_print_nbyte_little_endian(p_print, "private_key_used",
+ BT_OCTET32_LEN);
+ p_print = (uint8_t*)&p_cb->sc_oob_data.loc_oob_data.publ_key_used.x;
+ smp_debug_print_nbyte_little_endian(p_print, "publ_key_used.x",
+ BT_OCTET32_LEN);
+ p_print = (uint8_t*)&p_cb->sc_oob_data.loc_oob_data.publ_key_used.y;
+ smp_debug_print_nbyte_little_endian(p_print, "publ_key_used.y",
+ BT_OCTET32_LEN);
+ p_print = (uint8_t*)&p_cb->sc_oob_data.loc_oob_data.randomizer;
+ smp_debug_print_nbyte_little_endian(p_print, "randomizer", OCTET16_LEN);
+ p_print = (uint8_t*)&p_cb->sc_oob_data.loc_oob_data.commitment;
+ smp_debug_print_nbyte_little_endian(p_print, "commitment", OCTET16_LEN);
+ SMP_TRACE_DEBUG("");
+#endif
/* pass created OOB data up */
p_cb->cb_evt = SMP_SC_LOC_OOB_DATA_UP_EVT;
smp_send_app_cback(p_cb, NULL);
- // Store the data for later use when we are paired with
- // Event though the doc above says to pass up for safe keeping it never gets
- // kept safe. Additionally, when we need the data to make a decision we
- // wouldn't have it. This will save the sc_oob_data in the smp_keys.cc such
- // that when we receive a request to create new keys we check to see if the
- // sc_oob_data exists and utilize the keys that are stored there otherwise the
- // connector will fail commitment check and dhkey exchange.
- smp_save_local_oob_data(p_cb);
-
smp_cb_cleanup(p_cb);
}
@@ -1960,8 +1950,8 @@ void smp_set_local_oob_random_commitment(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
* Function smp_link_encrypted
*
* Description This function is called when link is encrypted and notified
- * to the peripheral device. Proceed to to send LTK, DIV and ER
- *to central if bonding the devices.
+ * to the slave device. Proceed to to send LTK, DIV and ER to
+ * master if bonding the devices.
*
*
* Returns void
@@ -1980,11 +1970,8 @@ void smp_link_encrypted(const RawAddress& bda, uint8_t encr_enable) {
btm_ble_update_sec_key_size(bda, p_cb->loc_enc_size);
}
- tSMP_INT_DATA smp_int_data = {
- // TODO This is not a tSMP_STATUS
- .status = static_cast<tSMP_STATUS>(encr_enable),
- };
-
+ tSMP_INT_DATA smp_int_data;
+ smp_int_data.status = encr_enable;
smp_sm_event(&smp_cb, SMP_ENCRYPTED_EVT, &smp_int_data);
}
}
diff --git a/stack/smp/smp_api.cc b/stack/smp/smp_api.cc
index 164971dfc..f2c7ed816 100644
--- a/stack/smp/smp_api.cc
+++ b/stack/smp/smp_api.cc
@@ -29,16 +29,14 @@
#include "bt_utils.h"
#include "stack_config.h"
-#include "gd/os/log.h"
-#include "gd/os/rand.h"
+#include "btm_int.h"
#include "hcimsgs.h"
-#include "l2c_api.h"
+#include "l2c_int.h"
#include "l2cdefs.h"
-#include "main/shim/shim.h"
#include "smp_api.h"
#include "smp_int.h"
-#include "stack/btm/btm_dev.h"
+#include "btu.h"
#include "p_256_ecc_pp.h"
/*******************************************************************************
@@ -51,11 +49,6 @@
*
******************************************************************************/
void SMP_Init(void) {
- if (bluetooth::shim::is_gd_shim_enabled()) {
- LOG(INFO) << "Skipping legacy SMP_Init because GD is enabled";
- return;
- }
-
memset(&smp_cb, 0, sizeof(tSMP_CB));
smp_cb.smp_rsp_timer_ent = alarm_new("smp.smp_rsp_timer_ent");
smp_cb.delayed_auth_timer_ent = alarm_new("smp.delayed_auth_timer_ent");
@@ -72,8 +65,8 @@ void SMP_Init(void) {
p_256_init_curve();
/* Initialize failure case for certification */
- smp_cb.cert_failure = static_cast<tSMP_STATUS>(
- stack_config_get_interface()->get_pts_smp_failure_case());
+ smp_cb.cert_failure =
+ stack_config_get_interface()->get_pts_smp_failure_case();
if (smp_cb.cert_failure)
SMP_TRACE_ERROR("%s PTS FAILURE MODE IN EFFECT (CASE %d)", __func__,
smp_cb.cert_failure);
@@ -99,7 +92,7 @@ void SMP_Init(void) {
* Returns The new or current trace level
*
******************************************************************************/
-uint8_t SMP_SetTraceLevel(uint8_t new_level) {
+extern uint8_t SMP_SetTraceLevel(uint8_t new_level) {
if (new_level != 0xFF) smp_cb.trace_level = new_level;
return (smp_cb.trace_level);
@@ -115,9 +108,6 @@ uint8_t SMP_SetTraceLevel(uint8_t new_level) {
*
******************************************************************************/
bool SMP_Register(tSMP_CALLBACK* p_cback) {
- LOG_ASSERT(!bluetooth::shim::is_gd_shim_enabled())
- << "Legacy SMP API should not be invoked when GD Security is used";
-
SMP_TRACE_EVENT("SMP_Register state=%d", smp_cb.state);
if (smp_cb.p_callback != NULL) {
@@ -141,8 +131,6 @@ bool SMP_Register(tSMP_CALLBACK* p_cback) {
*
******************************************************************************/
tSMP_STATUS SMP_Pair(const RawAddress& bd_addr) {
- LOG_ASSERT(!bluetooth::shim::is_gd_shim_enabled())
- << "Legacy SMP API should not be invoked when GD Security is used";
tSMP_CB* p_cb = &smp_cb;
SMP_TRACE_EVENT("%s: state=%d br_state=%d flag=0x%x, bd_addr=%s", __func__,
@@ -160,7 +148,6 @@ tSMP_STATUS SMP_Pair(const RawAddress& bd_addr) {
if (!L2CA_ConnectFixedChnl(L2CAP_SMP_CID, bd_addr)) {
tSMP_INT_DATA smp_int_data;
smp_int_data.status = SMP_PAIR_INTERNAL_ERR;
- p_cb->status = SMP_PAIR_INTERNAL_ERR;
SMP_TRACE_ERROR("%s: L2C connect fixed channel failed.", __func__);
smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &smp_int_data);
return SMP_PAIR_INTERNAL_ERR;
@@ -184,9 +171,6 @@ tSMP_STATUS SMP_Pair(const RawAddress& bd_addr) {
*
******************************************************************************/
tSMP_STATUS SMP_BR_PairWith(const RawAddress& bd_addr) {
- LOG_ASSERT(!bluetooth::shim::is_gd_shim_enabled())
- << "Legacy SMP API should not be invoked when GD Security is used";
-
tSMP_CB* p_cb = &smp_cb;
SMP_TRACE_EVENT("%s: state=%d br_state=%d flag=0x%x, bd_addr=%s", __func__,
@@ -199,7 +183,7 @@ tSMP_STATUS SMP_BR_PairWith(const RawAddress& bd_addr) {
return SMP_BUSY;
}
- p_cb->role = HCI_ROLE_CENTRAL;
+ p_cb->role = HCI_ROLE_MASTER;
p_cb->flags = SMP_PAIR_FLAGS_WE_STARTED_DD;
p_cb->smp_over_br = true;
p_cb->pairing_bda = bd_addr;
@@ -208,7 +192,6 @@ tSMP_STATUS SMP_BR_PairWith(const RawAddress& bd_addr) {
SMP_TRACE_ERROR("%s: L2C connect fixed channel failed.", __func__);
tSMP_INT_DATA smp_int_data;
smp_int_data.status = SMP_PAIR_INTERNAL_ERR;
- p_cb->status = SMP_PAIR_INTERNAL_ERR;
smp_br_state_machine_event(p_cb, SMP_BR_AUTH_CMPL_EVT, &smp_int_data);
return SMP_PAIR_INTERNAL_ERR;
}
@@ -228,9 +211,6 @@ tSMP_STATUS SMP_BR_PairWith(const RawAddress& bd_addr) {
*
******************************************************************************/
bool SMP_PairCancel(const RawAddress& bd_addr) {
- LOG_ASSERT(!bluetooth::shim::is_gd_shim_enabled())
- << "Legacy SMP API should not be invoked when GD Security is used";
-
tSMP_CB* p_cb = &smp_cb;
uint8_t err_code = SMP_PAIR_FAIL_UNKNOWN;
@@ -239,7 +219,7 @@ bool SMP_PairCancel(const RawAddress& bd_addr) {
p_cb->cert_failure == SMP_NUMERIC_COMPAR_FAIL)
err_code = p_cb->cert_failure;
- SMP_TRACE_EVENT("SMP_CancelPair state=%d flag=0x%x ", p_cb->state,
+ BTM_TRACE_EVENT("SMP_CancelPair state=%d flag=0x%x ", p_cb->state,
p_cb->flags);
if (p_cb->state != SMP_STATE_IDLE && p_cb->pairing_bda == bd_addr) {
p_cb->is_pair_cancel = true;
@@ -266,10 +246,7 @@ bool SMP_PairCancel(const RawAddress& bd_addr) {
* Returns None
*
******************************************************************************/
-void SMP_SecurityGrant(const RawAddress& bd_addr, tSMP_STATUS res) {
- LOG_ASSERT(!bluetooth::shim::is_gd_shim_enabled())
- << "Legacy SMP API should not be invoked when GD Security is used";
-
+void SMP_SecurityGrant(const RawAddress& bd_addr, uint8_t res) {
SMP_TRACE_EVENT("SMP_SecurityGrant ");
// If just showing consent dialog, send response
@@ -318,7 +295,7 @@ void SMP_SecurityGrant(const RawAddress& bd_addr, tSMP_STATUS res) {
/* clear the SMP_SEC_REQUEST_EVT event after get grant */
/* avoid generating duplicate pair request */
- smp_cb.cb_evt = SMP_EVT_NONE;
+ smp_cb.cb_evt = 0;
tSMP_INT_DATA smp_int_data;
smp_int_data.status = res;
smp_br_state_machine_event(&smp_cb, SMP_BR_API_SEC_GRANT_EVT,
@@ -331,7 +308,7 @@ void SMP_SecurityGrant(const RawAddress& bd_addr, tSMP_STATUS res) {
return;
/* clear the SMP_SEC_REQUEST_EVT event after get grant */
/* avoid generate duplicate pair request */
- smp_cb.cb_evt = SMP_EVT_NONE;
+ smp_cb.cb_evt = 0;
tSMP_INT_DATA smp_int_data;
smp_int_data.status = res;
smp_sm_event(&smp_cb, SMP_API_SEC_GRANT_EVT, &smp_int_data);
@@ -354,9 +331,6 @@ void SMP_SecurityGrant(const RawAddress& bd_addr, tSMP_STATUS res) {
******************************************************************************/
void SMP_PasskeyReply(const RawAddress& bd_addr, uint8_t res,
uint32_t passkey) {
- LOG_ASSERT(!bluetooth::shim::is_gd_shim_enabled())
- << "Legacy SMP API should not be invoked when GD Security is used";
-
tSMP_CB* p_cb = &smp_cb;
SMP_TRACE_EVENT("SMP_PasskeyReply: Key: %d Result:%d", passkey, res);
@@ -411,9 +385,6 @@ void SMP_PasskeyReply(const RawAddress& bd_addr, uint8_t res,
*
******************************************************************************/
void SMP_ConfirmReply(const RawAddress& bd_addr, uint8_t res) {
- LOG_ASSERT(!bluetooth::shim::is_gd_shim_enabled())
- << "Legacy SMP API should not be invoked when GD Security is used";
-
tSMP_CB* p_cb = &smp_cb;
SMP_TRACE_EVENT("%s: Result:%d", __func__, res);
@@ -459,9 +430,6 @@ void SMP_ConfirmReply(const RawAddress& bd_addr, uint8_t res) {
******************************************************************************/
void SMP_OobDataReply(const RawAddress& bd_addr, tSMP_STATUS res, uint8_t len,
uint8_t* p_data) {
- LOG_ASSERT(!bluetooth::shim::is_gd_shim_enabled())
- << "Legacy SMP API should not be invoked when GD Security is used";
-
tSMP_CB* p_cb = &smp_cb;
tSMP_KEY key;
@@ -554,22 +522,83 @@ void SMP_SecureConnectionOobDataReply(uint8_t* p_data) {
/*******************************************************************************
*
- * Function SMP_CrLocScOobData
+ * Function SMP_KeypressNotification
+ *
+ * Description This function is called to notify Security Manager about
+ * Keypress Notification.
*
- * Description This function is called to generate a public key to be
- * passed to a remote device via Out of Band transport.
+ * Parameters: bd_addr Address of the device to send keypress
+ * notification to
+ * value Keypress notification parameter value
*
******************************************************************************/
-void SMP_CrLocScOobData() {
+void SMP_KeypressNotification(const RawAddress& bd_addr, uint8_t value) {
+ tSMP_CB* p_cb = &smp_cb;
+
+ SMP_TRACE_EVENT("%s: Value: %d", __func__, value);
+
+ if (bd_addr != p_cb->pairing_bda) {
+ SMP_TRACE_ERROR("%s() - Wrong BD Addr", __func__);
+ return;
+ }
+
+ if (btm_find_dev(bd_addr) == NULL) {
+ SMP_TRACE_ERROR("%s() - no dev CB", __func__);
+ return;
+ }
+
+ /* Keypress Notification is used by a device with KeyboardOnly IO capabilities
+ * during the passkey entry protocol */
+ if (p_cb->local_io_capability != SMP_IO_CAP_IN) {
+ SMP_TRACE_ERROR("%s() - wrong local IO capabilities %d", __func__,
+ p_cb->local_io_capability);
+ return;
+ }
+
+ if (p_cb->selected_association_model != SMP_MODEL_SEC_CONN_PASSKEY_ENT) {
+ SMP_TRACE_ERROR("%s() - wrong protocol %d", __func__,
+ p_cb->selected_association_model);
+ return;
+ }
+
tSMP_INT_DATA smp_int_data;
- smp_sm_event(&smp_cb, SMP_CR_LOC_SC_OOB_DATA_EVT, &smp_int_data);
+ smp_int_data.status = value;
+ smp_sm_event(p_cb, SMP_KEYPRESS_NOTIFICATION_EVENT, &smp_int_data);
}
/*******************************************************************************
*
- * Function SMP_ClearLocScOobData
+ * Function SMP_CreateLocalSecureConnectionsOobData
+ *
+ * Description This function is called to start creation of local SC OOB
+ * data set (tSMP_LOC_OOB_DATA).
*
- * Description This function is called to clear out the OOB stored locally.
+ * Parameters: bd_addr - Address of the device to send OOB data block to
*
+ * Returns Boolean - true: creation of local SC OOB data set started.
******************************************************************************/
-void SMP_ClearLocScOobData() { smp_clear_local_oob_data(); }
+bool SMP_CreateLocalSecureConnectionsOobData(tBLE_BD_ADDR* addr_to_send_to) {
+ tSMP_CB* p_cb = &smp_cb;
+
+ if (addr_to_send_to == NULL) {
+ SMP_TRACE_ERROR("%s addr_to_send_to is not provided", __func__);
+ return false;
+ }
+
+ VLOG(2) << __func__ << " addr type:" << +addr_to_send_to->type
+ << ", BDA:" << addr_to_send_to->bda << ", state:" << p_cb->state
+ << ", br_state: " << p_cb->br_state;
+
+ if ((p_cb->state != SMP_STATE_IDLE) || (p_cb->smp_over_br)) {
+ SMP_TRACE_WARNING(
+ "%s creation of local OOB data set "
+ "starts only in IDLE state",
+ __func__);
+ return false;
+ }
+
+ p_cb->sc_oob_data.loc_oob_data.addr_sent_to = *addr_to_send_to;
+ smp_sm_event(p_cb, SMP_CR_LOC_SC_OOB_DATA_EVT, NULL);
+
+ return true;
+}
diff --git a/stack/smp/smp_br_main.cc b/stack/smp/smp_br_main.cc
index b311d9d25..b06055fb5 100644
--- a/stack/smp/smp_br_main.cc
+++ b/stack/smp/smp_br_main.cc
@@ -19,10 +19,8 @@
#include "bt_target.h"
#include <string.h>
-
-#include "osi/include/log.h"
+#include "log/log.h"
#include "smp_int.h"
-#include "types/hci_role.h"
const char* const smp_br_state_name[SMP_BR_STATE_MAX + 1] = {
"SMP_BR_STATE_IDLE", "SMP_BR_STATE_WAIT_APP_RSP",
@@ -33,7 +31,7 @@ const char* const smp_br_event_name[SMP_BR_MAX_EVT] = {
"BR_PAIRING_REQ_EVT", "BR_PAIRING_RSP_EVT",
"BR_CONFIRM_EVT", "BR_RAND_EVT",
"BR_PAIRING_FAILED_EVT", "BR_ENCRPTION_INFO_EVT",
- "BR_CENTRAL_ID_EVT", "BR_ID_INFO_EVT",
+ "BR_MASTER_ID_EVT", "BR_ID_INFO_EVT",
"BR_ID_ADDR_EVT", "BR_SIGN_INFO_EVT",
"BR_SECURITY_REQ_EVT", "BR_PAIR_PUBLIC_KEY_EVT",
"BR_PAIR_DHKEY_CHCK_EVT", "BR_PAIR_KEYPR_NOTIF_EVT",
@@ -75,23 +73,23 @@ enum {
};
static const tSMP_ACT smp_br_sm_action[] = {
- smp_send_pair_req, /* SMP_SEND_PAIR_REQ */
- smp_br_send_pair_response, /* SMP_BR_SEND_PAIR_RSP */
- smp_send_pair_fail, /* SMP_SEND_PAIR_FAIL */
- smp_send_id_info, /* SMP_SEND_ID_INFO */
- smp_br_process_pairing_command, /* SMP_BR_PROC_PAIR_CMD */
- smp_proc_pair_fail, /* SMP_PROC_PAIR_FAIL */
- smp_proc_id_info, /* SMP_PROC_ID_INFO */
- smp_proc_id_addr, /* SMP_PROC_ID_ADDR */
- smp_proc_srk_info, /* SMP_PROC_SRK_INFO */
- smp_br_process_security_grant, /* SMP_BR_PROC_SEC_GRANT */
- smp_br_process_peripheral_keys_response, /* SMP_BR_PROC_SL_KEYS_RSP */
- smp_br_select_next_key, /* SMP_BR_KEY_DISTRIBUTION */
- smp_br_pairing_complete, /* SMP_BR_PAIRING_COMPLETE */
- smp_send_app_cback, /* SMP_SEND_APP_CBACK */
- smp_br_check_authorization_request, /* SMP_BR_CHECK_AUTH_REQ */
- smp_pair_terminate, /* SMP_PAIR_TERMINATE */
- smp_idle_terminate /* SMP_IDLE_TERMINATE */
+ smp_send_pair_req, /* SMP_SEND_PAIR_REQ */
+ smp_br_send_pair_response, /* SMP_BR_SEND_PAIR_RSP */
+ smp_send_pair_fail, /* SMP_SEND_PAIR_FAIL */
+ smp_send_id_info, /* SMP_SEND_ID_INFO */
+ smp_br_process_pairing_command, /* SMP_BR_PROC_PAIR_CMD */
+ smp_proc_pair_fail, /* SMP_PROC_PAIR_FAIL */
+ smp_proc_id_info, /* SMP_PROC_ID_INFO */
+ smp_proc_id_addr, /* SMP_PROC_ID_ADDR */
+ smp_proc_srk_info, /* SMP_PROC_SRK_INFO */
+ smp_br_process_security_grant, /* SMP_BR_PROC_SEC_GRANT */
+ smp_br_process_slave_keys_response, /* SMP_BR_PROC_SL_KEYS_RSP */
+ smp_br_select_next_key, /* SMP_BR_KEY_DISTRIBUTION */
+ smp_br_pairing_complete, /* SMP_BR_PAIRING_COMPLETE */
+ smp_send_app_cback, /* SMP_SEND_APP_CBACK */
+ smp_br_check_authorization_request, /* SMP_BR_CHECK_AUTH_REQ */
+ smp_pair_terminate, /* SMP_PAIR_TERMINATE */
+ smp_idle_terminate /* SMP_IDLE_TERMINATE */
};
static const uint8_t smp_br_all_table[][SMP_BR_SM_NUM_COLS] = {
@@ -103,8 +101,8 @@ static const uint8_t smp_br_all_table[][SMP_BR_SM_NUM_COLS] = {
/* BR_L2CAP_DISCONN */
{SMP_PAIR_TERMINATE, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_IDLE}};
-/************ SMP Central FSM State/Event Indirection Table **************/
-static const uint8_t smp_br_central_entry_map[][SMP_BR_STATE_MAX] = {
+/************ SMP Master FSM State/Event Indirection Table **************/
+static const uint8_t smp_br_master_entry_map[][SMP_BR_STATE_MAX] = {
/* br_state name: Idle WaitApp Pair Bond
Rsp ReqRsp Pend */
/* BR_PAIRING_REQ */ {0, 0, 0, 0},
@@ -113,7 +111,7 @@ static const uint8_t smp_br_central_entry_map[][SMP_BR_STATE_MAX] = {
/* BR_RAND */ {0, 0, 0, 0},
/* BR_PAIRING_FAILED */ {0, 0x81, 0x81, 0},
/* BR_ENCRPTION_INFO */ {0, 0, 0, 0},
- /* BR_CENTRAL_ID */ {0, 0, 0, 0},
+ /* BR_MASTER_ID */ {0, 0, 0, 0},
/* BR_ID_INFO */ {0, 0, 0, 1},
/* BR_ID_ADDR */ {0, 0, 0, 2},
/* BR_SIGN_INFO */ {0, 0, 0, 3},
@@ -133,7 +131,7 @@ static const uint8_t smp_br_central_entry_map[][SMP_BR_STATE_MAX] = {
/* BR_BOND_REQ */ {0, 0, 2, 0},
/* BR_DISCARD_SEC_REQ */ {0, 0, 0, 0}};
-static const uint8_t smp_br_central_idle_table[][SMP_BR_SM_NUM_COLS] = {
+static const uint8_t smp_br_master_idle_table[][SMP_BR_SM_NUM_COLS] = {
/* Event Action Next State */
/* BR_L2CAP_CONN */
{SMP_SEND_APP_CBACK, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_WAIT_APP_RSP},
@@ -141,13 +139,13 @@ static const uint8_t smp_br_central_idle_table[][SMP_BR_SM_NUM_COLS] = {
{SMP_IDLE_TERMINATE, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_IDLE}};
static const uint8_t
- smp_br_central_wait_appln_response_table[][SMP_BR_SM_NUM_COLS] = {
+ smp_br_master_wait_appln_response_table[][SMP_BR_SM_NUM_COLS] = {
/* Event Action Next State */
/* BR_KEYS_RSP */
{SMP_SEND_PAIR_REQ, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_PAIR_REQ_RSP}};
static const uint8_t
- smp_br_central_pair_request_response_table[][SMP_BR_SM_NUM_COLS] = {
+ smp_br_master_pair_request_response_table[][SMP_BR_SM_NUM_COLS] = {
/* Event Action Next State */
/* BR_PAIRING_RSP */
{SMP_BR_PROC_PAIR_CMD, SMP_BR_CHECK_AUTH_REQ,
@@ -155,7 +153,7 @@ static const uint8_t
/* BR_BOND_REQ */
{SMP_BR_SM_NO_ACTION, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_BOND_PENDING}};
-static const uint8_t smp_br_central_bond_pending_table[][SMP_BR_SM_NUM_COLS] = {
+static const uint8_t smp_br_master_bond_pending_table[][SMP_BR_SM_NUM_COLS] = {
/* Event Action Next State */
/* BR_ID_INFO */
{SMP_PROC_ID_INFO, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_BOND_PENDING},
@@ -164,7 +162,7 @@ static const uint8_t smp_br_central_bond_pending_table[][SMP_BR_SM_NUM_COLS] = {
/* BR_SIGN_INFO */
{SMP_PROC_SRK_INFO, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_BOND_PENDING}};
-static const uint8_t smp_br_peripheral_entry_map[][SMP_BR_STATE_MAX] = {
+static const uint8_t smp_br_slave_entry_map[][SMP_BR_STATE_MAX] = {
/* br_state name: Idle WaitApp Pair Bond
Rsp ReqRsp Pend */
/* BR_PAIRING_REQ */ {1, 0, 0, 0},
@@ -173,7 +171,7 @@ static const uint8_t smp_br_peripheral_entry_map[][SMP_BR_STATE_MAX] = {
/* BR_RAND */ {0, 0, 0, 0},
/* BR_PAIRING_FAILED */ {0, 0x81, 0x81, 0x81},
/* BR_ENCRPTION_INFO */ {0, 0, 0, 0},
- /* BR_CENTRAL_ID */ {0, 0, 0, 0},
+ /* BR_MASTER_ID */ {0, 0, 0, 0},
/* BR_ID_INFO */ {0, 0, 0, 1},
/* BR_ID_ADDR */ {0, 0, 0, 2},
/* BR_SIGN_INFO */ {0, 0, 0, 3},
@@ -193,13 +191,13 @@ static const uint8_t smp_br_peripheral_entry_map[][SMP_BR_STATE_MAX] = {
/* BR_BOND_REQ */ {0, 3, 0, 0},
/* BR_DISCARD_SEC_REQ */ {0, 0, 0, 0}};
-static const uint8_t smp_br_peripheral_idle_table[][SMP_BR_SM_NUM_COLS] = {
+static const uint8_t smp_br_slave_idle_table[][SMP_BR_SM_NUM_COLS] = {
/* Event Action Next State */
/* BR_PAIRING_REQ */
{SMP_BR_PROC_PAIR_CMD, SMP_SEND_APP_CBACK, SMP_BR_STATE_WAIT_APP_RSP}};
static const uint8_t
- smp_br_peripheral_wait_appln_response_table[][SMP_BR_SM_NUM_COLS] = {
+ smp_br_slave_wait_appln_response_table[][SMP_BR_SM_NUM_COLS] = {
/* Event Action Next State */
/* BR_API_SEC_GRANT */
{SMP_BR_PROC_SEC_GRANT, SMP_SEND_APP_CBACK, SMP_BR_STATE_WAIT_APP_RSP},
@@ -210,35 +208,34 @@ static const uint8_t
{SMP_BR_KEY_DISTRIBUTION, SMP_BR_SM_NO_ACTION,
SMP_BR_STATE_BOND_PENDING}};
-static const uint8_t
- smp_br_peripheral_bond_pending_table[][SMP_BR_SM_NUM_COLS] = {
- /* Event Action Next State */
- /* BR_ID_INFO */
- {SMP_PROC_ID_INFO, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_BOND_PENDING},
- /* BR_ID_ADDR */
- {SMP_PROC_ID_ADDR, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_BOND_PENDING},
- /* BR_SIGN_INFO */
- {SMP_PROC_SRK_INFO, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_BOND_PENDING}};
+static const uint8_t smp_br_slave_bond_pending_table[][SMP_BR_SM_NUM_COLS] = {
+ /* Event Action Next State */
+ /* BR_ID_INFO */
+ {SMP_PROC_ID_INFO, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_BOND_PENDING},
+ /* BR_ID_ADDR */
+ {SMP_PROC_ID_ADDR, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_BOND_PENDING},
+ /* BR_SIGN_INFO */
+ {SMP_PROC_SRK_INFO, SMP_BR_SM_NO_ACTION, SMP_BR_STATE_BOND_PENDING}};
static const tSMP_BR_SM_TBL smp_br_state_table[][2] = {
/* SMP_BR_STATE_IDLE */
- {smp_br_central_idle_table, smp_br_peripheral_idle_table},
+ {smp_br_master_idle_table, smp_br_slave_idle_table},
/* SMP_BR_STATE_WAIT_APP_RSP */
- {smp_br_central_wait_appln_response_table,
- smp_br_peripheral_wait_appln_response_table},
+ {smp_br_master_wait_appln_response_table,
+ smp_br_slave_wait_appln_response_table},
/* SMP_BR_STATE_PAIR_REQ_RSP */
- {smp_br_central_pair_request_response_table, NULL},
+ {smp_br_master_pair_request_response_table, NULL},
/* SMP_BR_STATE_BOND_PENDING */
- {smp_br_central_bond_pending_table, smp_br_peripheral_bond_pending_table},
+ {smp_br_master_bond_pending_table, smp_br_slave_bond_pending_table},
};
typedef const uint8_t (*tSMP_BR_ENTRY_TBL)[SMP_BR_STATE_MAX];
-static const tSMP_BR_ENTRY_TBL smp_br_entry_table[] = {
- smp_br_central_entry_map, smp_br_peripheral_entry_map};
+static const tSMP_BR_ENTRY_TBL smp_br_entry_table[] = {smp_br_master_entry_map,
+ smp_br_slave_entry_map};
#define SMP_BR_ALL_TABLE_MASK 0x80
@@ -306,6 +303,7 @@ void smp_br_state_machine_event(tSMP_CB* p_cb, tSMP_BR_EVENT event,
tSMP_BR_STATE curr_state = p_cb->br_state;
tSMP_BR_SM_TBL state_table;
uint8_t action, entry;
+ tSMP_BR_ENTRY_TBL entry_table = smp_br_entry_table[p_cb->role];
SMP_TRACE_EVENT("main %s", __func__);
if (curr_state >= SMP_BR_STATE_MAX) {
@@ -313,19 +311,16 @@ void smp_br_state_machine_event(tSMP_CB* p_cb, tSMP_BR_EVENT event,
return;
}
- if (p_cb->role > HCI_ROLE_PERIPHERAL) {
+ if (p_cb->role > HCI_ROLE_SLAVE) {
SMP_TRACE_ERROR("%s: invalid role %d", __func__, p_cb->role);
android_errorWriteLog(0x534e4554, "80145946");
return;
}
- tSMP_BR_ENTRY_TBL entry_table = smp_br_entry_table[p_cb->role];
-
- SMP_TRACE_DEBUG(
- "SMP Role: %s State: [%s (%d)], Event: [%s (%d)]",
- (p_cb->role == HCI_ROLE_PERIPHERAL) ? "Peripheral" : "Central",
- smp_get_br_state_name(p_cb->br_state), p_cb->br_state,
- smp_get_br_event_name(event), event);
+ SMP_TRACE_DEBUG("SMP Role: %s State: [%s (%d)], Event: [%s (%d)]",
+ (p_cb->role == HCI_ROLE_SLAVE) ? "Slave" : "Master",
+ smp_get_br_state_name(p_cb->br_state), p_cb->br_state,
+ smp_get_br_event_name(event), event);
/* look up the state table for the current state */
/* lookup entry / w event & curr_state */
diff --git a/stack/smp/smp_int.h b/stack/smp/smp_int.h
index 54fdfdffa..72fdf55a9 100644
--- a/stack/smp/smp_int.h
+++ b/stack/smp/smp_int.h
@@ -30,22 +30,21 @@
#include "smp_api.h"
#include "stack/crypto_toolbox/crypto_toolbox.h"
-typedef enum : uint8_t {
- /* Legacy mode */
- SMP_MODEL_ENCRYPTION_ONLY = 0, /* Just Works model */
- SMP_MODEL_PASSKEY = 1, /* Passkey Entry model, input the key */
- SMP_MODEL_OOB = 2, /* OOB model */
- SMP_MODEL_KEY_NOTIF = 3, /* Passkey Entry model, display the key */
- /* Secure connections mode */
- SMP_MODEL_SEC_CONN_JUSTWORKS = 4, /* Just Works model */
- SMP_MODEL_SEC_CONN_NUM_COMP = 5, /* Numeric Comparison model */
- SMP_MODEL_SEC_CONN_PASSKEY_ENT = 6, /* Passkey Entry model, */
- /* this side inputs the key */
- SMP_MODEL_SEC_CONN_PASSKEY_DISP = 7, /* Passkey Entry model, */
- /* this side displays the key */
- SMP_MODEL_SEC_CONN_OOB = 8, /* Secure Connections mode, OOB model */
- SMP_MODEL_OUT_OF_RANGE = 9,
-} tSMP_ASSO_MODEL;
+/* Legacy mode */
+#define SMP_MODEL_ENCRYPTION_ONLY 0 /* Just Works model */
+#define SMP_MODEL_PASSKEY 1 /* Passkey Entry model, input the key */
+#define SMP_MODEL_OOB 2 /* OOB model */
+#define SMP_MODEL_KEY_NOTIF 3 /* Passkey Entry model, display the key */
+/* Secure connections mode */
+#define SMP_MODEL_SEC_CONN_JUSTWORKS 4 /* Just Works model */
+#define SMP_MODEL_SEC_CONN_NUM_COMP 5 /* Numeric Comparison model */
+#define SMP_MODEL_SEC_CONN_PASSKEY_ENT 6 /* Passkey Entry model, */
+ /* this side inputs the key */
+#define SMP_MODEL_SEC_CONN_PASSKEY_DISP 7 /* Passkey Entry model, */
+ /* this side displays the key */
+#define SMP_MODEL_SEC_CONN_OOB 8 /* Secure Connections mode, OOB model */
+#define SMP_MODEL_OUT_OF_RANGE 9
+typedef uint8_t tSMP_ASSO_MODEL;
#ifndef SMP_MAX_CONN
#define SMP_MAX_CONN 2
@@ -57,88 +56,83 @@ typedef enum : uint8_t {
#define SMP_OPCODE_INIT 0x04
/* SMP events */
-typedef enum : uint8_t {
- SMP_NOP_EVT = 0,
- SMP_CONFIRM_EVT = SMP_OPCODE_CONFIRM, // 0x03
- SMP_RAND_EVT = SMP_OPCODE_RAND, // 0x04
-
- SMP_PAIR_COMMITM_EVT = SMP_OPCODE_PAIR_COMMITM, // 0x0f
- SMP_SELF_DEF_EVT = (SMP_PAIR_COMMITM_EVT + 1), // 0x10
- SMP_KEY_READY_EVT = (SMP_SELF_DEF_EVT), // 0x04
- SMP_ENCRYPTED_EVT = (SMP_SELF_DEF_EVT + 1), // 0x05
- SMP_L2CAP_CONN_EVT = (SMP_SELF_DEF_EVT + 2), // 0x06
- SMP_L2CAP_DISCONN_EVT = (SMP_SELF_DEF_EVT + 3), // 0x07
- SMP_IO_RSP_EVT = (SMP_SELF_DEF_EVT + 4), // 0x08
- SMP_API_SEC_GRANT_EVT = (SMP_SELF_DEF_EVT + 5), // 0x09
- SMP_TK_REQ_EVT = (SMP_SELF_DEF_EVT + 6), // 0x0a
- SMP_AUTH_CMPL_EVT = (SMP_SELF_DEF_EVT + 7), // 0x0b
- SMP_ENC_REQ_EVT = (SMP_SELF_DEF_EVT + 8), // 0x0c
- SMP_BOND_REQ_EVT = (SMP_SELF_DEF_EVT + 9), // 0x0d
- SMP_DISCARD_SEC_REQ_EVT = (SMP_SELF_DEF_EVT + 10), // 0x0e
-
- SMP_BR_PAIR_KEYPR_NOTIF_EVT = SMP_OPCODE_PAIR_KEYPR_NOTIF,
- /* not over BR/EDR */ // 0x0e
- SMP_BR_SELF_DEF_EVT = SMP_BR_PAIR_KEYPR_NOTIF_EVT, // 0x0e
- SMP_BR_KEY_READY_EVT = (SMP_BR_SELF_DEF_EVT + 1), // 0x0f
- SMP_BR_ENCRYPTED_EVT = (SMP_BR_SELF_DEF_EVT + 2), // 0x10
- SMP_BR_L2CAP_CONN_EVT = (SMP_BR_SELF_DEF_EVT + 3), // 0x11
- SMP_BR_L2CAP_DISCONN_EVT = (SMP_BR_SELF_DEF_EVT + 4), // 0x12
- SMP_BR_KEYS_RSP_EVT = (SMP_BR_SELF_DEF_EVT + 5), // 0x13
- SMP_BR_API_SEC_GRANT_EVT = (SMP_BR_SELF_DEF_EVT + 6), // 0x14
- SMP_BR_TK_REQ_EVT = (SMP_BR_SELF_DEF_EVT + 7), // 0x15
- SMP_BR_AUTH_CMPL_EVT = (SMP_BR_SELF_DEF_EVT + 8), // 0x16
- SMP_BR_ENC_REQ_EVT = (SMP_BR_SELF_DEF_EVT + 9), // 0x17
- SMP_BR_BOND_REQ_EVT = (SMP_BR_SELF_DEF_EVT + 10), // 0x18
- SMP_BR_DISCARD_SEC_REQ_EVT = (SMP_BR_SELF_DEF_EVT + 11), // 0x19
- SMP_BR_MAX_EVT = (SMP_BR_SELF_DEF_EVT + 12), // 0x1a
-
- SMP_PAIR_DHKEY_CHCK_EVT = SMP_OPCODE_PAIR_DHKEY_CHECK, // 0x0d
-
- /* request to start public key exchange */
- SMP_PUBL_KEY_EXCH_REQ_EVT = (SMP_SELF_DEF_EVT + 11), // 0x1b
-
- /* local public key created */
- SMP_LOC_PUBL_KEY_CRTD_EVT = (SMP_SELF_DEF_EVT + 12), // 0x1c
-
- /* both local and peer public keys are saved in cb */
- SMP_BOTH_PUBL_KEYS_RCVD_EVT = (SMP_SELF_DEF_EVT + 13), // 0x1d
-
- /* DHKey computation is completed, time to start SC phase1 */
- SMP_SC_DHKEY_CMPLT_EVT = (SMP_SELF_DEF_EVT + 14), // 0x1d
-
- /* new local nonce is generated and saved in p_cb->rand */
- SMP_HAVE_LOC_NONCE_EVT = (SMP_SELF_DEF_EVT + 15), // 0x1f
-
- /* time to start SC phase2 */
- SMP_SC_PHASE1_CMPLT_EVT = (SMP_SELF_DEF_EVT + 16), // 0x20
-
- /* request to calculate number for user check. Used only in the numeric
- * compare protocol */
- SMP_SC_CALC_NC_EVT = (SMP_SELF_DEF_EVT + 17), // 0x21
-
- /* Request to display the number for user check to the user.*/
- /* Used only in the numeric compare protocol */
- SMP_SC_DSPL_NC_EVT = (SMP_SELF_DEF_EVT + 18), // 0x22
-
- /* user confirms 'OK' numeric comparison request */
- SMP_SC_NC_OK_EVT = (SMP_SELF_DEF_EVT + 19), // 0x23
-
- /* both local and peer DHKey Checks are already present - it is used on
- * peripheral to prevent a race condition */
- SMP_SC_2_DHCK_CHKS_PRES_EVT = (SMP_SELF_DEF_EVT + 20), // 0x24
-
- /* same meaning as SMP_KEY_READY_EVT to separate between SC and legacy actions
- */
- SMP_SC_KEY_READY_EVT = (SMP_SELF_DEF_EVT + 21), // 0x25
- SMP_KEYPRESS_NOTIFICATION_EVENT = (SMP_SELF_DEF_EVT + 22), // 0x26
-
- /* SC OOB data from some repository is provided */
- SMP_SC_OOB_DATA_EVT = (SMP_SELF_DEF_EVT + 23), // 0x27
-
- SMP_CR_LOC_SC_OOB_DATA_EVT = (SMP_SELF_DEF_EVT + 24), // 0x28
- SMP_MAX_EVT = SMP_CR_LOC_SC_OOB_DATA_EVT, // 0x28
-} tSMP_EVENT;
-typedef tSMP_EVENT tSMP_BR_EVENT;
+#define SMP_PAIRING_REQ_EVT SMP_OPCODE_PAIRING_REQ
+#define SMP_PAIRING_RSP_EVT SMP_OPCODE_PAIRING_RSP
+#define SMP_CONFIRM_EVT SMP_OPCODE_CONFIRM
+#define SMP_RAND_EVT SMP_OPCODE_RAND
+#define SMP_PAIRING_FAILED_EVT SMP_OPCODE_PAIRING_FAILED
+#define SMP_ENCRPTION_INFO_EVT SMP_OPCODE_ENCRYPT_INFO
+#define SMP_MASTER_ID_EVT SMP_OPCODE_MASTER_ID
+#define SMP_ID_INFO_EVT SMP_OPCODE_IDENTITY_INFO
+#define SMP_ID_ADDR_EVT SMP_OPCODE_ID_ADDR
+#define SMP_SIGN_INFO_EVT SMP_OPCODE_SIGN_INFO
+#define SMP_SECURITY_REQ_EVT SMP_OPCODE_SEC_REQ
+
+#define SMP_PAIR_PUBLIC_KEY_EVT SMP_OPCODE_PAIR_PUBLIC_KEY
+#define SMP_PAIR_KEYPRESS_NOTIFICATION_EVT SMP_OPCODE_PAIR_KEYPR_NOTIF
+
+#define SMP_PAIR_COMMITM_EVT SMP_OPCODE_PAIR_COMMITM
+
+#define SMP_SELF_DEF_EVT (SMP_PAIR_COMMITM_EVT + 1)
+#define SMP_KEY_READY_EVT (SMP_SELF_DEF_EVT)
+#define SMP_ENCRYPTED_EVT (SMP_SELF_DEF_EVT + 1)
+#define SMP_L2CAP_CONN_EVT (SMP_SELF_DEF_EVT + 2)
+#define SMP_L2CAP_DISCONN_EVT (SMP_SELF_DEF_EVT + 3)
+#define SMP_IO_RSP_EVT (SMP_SELF_DEF_EVT + 4)
+#define SMP_API_SEC_GRANT_EVT (SMP_SELF_DEF_EVT + 5)
+#define SMP_TK_REQ_EVT (SMP_SELF_DEF_EVT + 6)
+#define SMP_AUTH_CMPL_EVT (SMP_SELF_DEF_EVT + 7)
+#define SMP_ENC_REQ_EVT (SMP_SELF_DEF_EVT + 8)
+#define SMP_BOND_REQ_EVT (SMP_SELF_DEF_EVT + 9)
+#define SMP_DISCARD_SEC_REQ_EVT (SMP_SELF_DEF_EVT + 10)
+
+#define SMP_PAIR_DHKEY_CHCK_EVT SMP_OPCODE_PAIR_DHKEY_CHECK
+
+/* request to start public key exchange */
+#define SMP_PUBL_KEY_EXCH_REQ_EVT (SMP_SELF_DEF_EVT + 11)
+
+/* local public key created */
+#define SMP_LOC_PUBL_KEY_CRTD_EVT (SMP_SELF_DEF_EVT + 12)
+
+/* both local and peer public keys are saved in cb */
+#define SMP_BOTH_PUBL_KEYS_RCVD_EVT (SMP_SELF_DEF_EVT + 13)
+
+/* DHKey computation is completed, time to start SC phase1 */
+#define SMP_SC_DHKEY_CMPLT_EVT (SMP_SELF_DEF_EVT + 14)
+
+/* new local nonce is generated and saved in p_cb->rand */
+#define SMP_HAVE_LOC_NONCE_EVT (SMP_SELF_DEF_EVT + 15)
+
+/* time to start SC phase2 */
+#define SMP_SC_PHASE1_CMPLT_EVT (SMP_SELF_DEF_EVT + 16)
+
+/* request to calculate number for user check. Used only in the numeric compare
+ * protocol */
+#define SMP_SC_CALC_NC_EVT (SMP_SELF_DEF_EVT + 17)
+
+/* Request to display the number for user check to the user.*/
+/* Used only in the numeric compare protocol */
+#define SMP_SC_DSPL_NC_EVT (SMP_SELF_DEF_EVT + 18)
+
+/* user confirms 'OK' numeric comparison request */
+#define SMP_SC_NC_OK_EVT (SMP_SELF_DEF_EVT + 19)
+
+/* both local and peer DHKey Checks are already present - it is used on slave to
+ * prevent a race condition */
+#define SMP_SC_2_DHCK_CHKS_PRES_EVT (SMP_SELF_DEF_EVT + 20)
+
+/* same meaning as SMP_KEY_READY_EVT to separate between SC and legacy actions
+ */
+#define SMP_SC_KEY_READY_EVT (SMP_SELF_DEF_EVT + 21)
+#define SMP_KEYPRESS_NOTIFICATION_EVENT (SMP_SELF_DEF_EVT + 22)
+
+/* SC OOB data from some repository is provided */
+#define SMP_SC_OOB_DATA_EVT (SMP_SELF_DEF_EVT + 23)
+
+#define SMP_CR_LOC_SC_OOB_DATA_EVT (SMP_SELF_DEF_EVT + 24)
+#define SMP_MAX_EVT SMP_CR_LOC_SC_OOB_DATA_EVT
+
+typedef uint8_t tSMP_EVENT;
/* Assumption it's only using the low 8 bits, if bigger than that, need to
* expand it to 16 bits */
@@ -167,6 +161,41 @@ enum {
};
typedef uint8_t tSMP_STATE;
+/* SMP over BR/EDR events */
+#define SMP_BR_PAIRING_REQ_EVT SMP_OPCODE_PAIRING_REQ
+#define SMP_BR_PAIRING_RSP_EVT SMP_OPCODE_PAIRING_RSP
+#define SMP_BR_CONFIRM_EVT SMP_OPCODE_CONFIRM /* not over BR/EDR */
+#define SMP_BR_RAND_EVT SMP_OPCODE_RAND /* not over BR/EDR */
+#define SMP_BR_PAIRING_FAILED_EVT SMP_OPCODE_PAIRING_FAILED
+#define SMP_BR_ENCRPTION_INFO_EVT \
+ SMP_OPCODE_ENCRYPT_INFO /* not over BR/EDR \
+ */
+#define SMP_BR_MASTER_ID_EVT SMP_OPCODE_MASTER_ID /* not over BR/EDR */
+#define SMP_BR_ID_INFO_EVT SMP_OPCODE_IDENTITY_INFO
+#define SMP_BR_ID_ADDR_EVT SMP_OPCODE_ID_ADDR
+#define SMP_BR_SIGN_INFO_EVT SMP_OPCODE_SIGN_INFO
+#define SMP_BR_SECURITY_REQ_EVT SMP_OPCODE_SEC_REQ /* not over BR/EDR */
+#define SMP_BR_PAIR_PUBLIC_KEY_EVT \
+ SMP_OPCODE_PAIR_PUBLIC_KEY /* not over BR/EDR */
+#define SMP_BR_PAIR_DHKEY_CHCK_EVT \
+ SMP_OPCODE_PAIR_DHKEY_CHECK /* not over BR/EDR */
+#define SMP_BR_PAIR_KEYPR_NOTIF_EVT \
+ SMP_OPCODE_PAIR_KEYPR_NOTIF /* not over BR/EDR */
+#define SMP_BR_SELF_DEF_EVT SMP_BR_PAIR_KEYPR_NOTIF_EVT
+#define SMP_BR_KEY_READY_EVT (SMP_BR_SELF_DEF_EVT + 1)
+#define SMP_BR_ENCRYPTED_EVT (SMP_BR_SELF_DEF_EVT + 2)
+#define SMP_BR_L2CAP_CONN_EVT (SMP_BR_SELF_DEF_EVT + 3)
+#define SMP_BR_L2CAP_DISCONN_EVT (SMP_BR_SELF_DEF_EVT + 4)
+#define SMP_BR_KEYS_RSP_EVT (SMP_BR_SELF_DEF_EVT + 5)
+#define SMP_BR_API_SEC_GRANT_EVT (SMP_BR_SELF_DEF_EVT + 6)
+#define SMP_BR_TK_REQ_EVT (SMP_BR_SELF_DEF_EVT + 7)
+#define SMP_BR_AUTH_CMPL_EVT (SMP_BR_SELF_DEF_EVT + 8)
+#define SMP_BR_ENC_REQ_EVT (SMP_BR_SELF_DEF_EVT + 9)
+#define SMP_BR_BOND_REQ_EVT (SMP_BR_SELF_DEF_EVT + 10)
+#define SMP_BR_DISCARD_SEC_REQ_EVT (SMP_BR_SELF_DEF_EVT + 11)
+#define SMP_BR_MAX_EVT (SMP_BR_SELF_DEF_EVT + 12)
+typedef uint8_t tSMP_BR_EVENT;
+
/* SMP over BR/EDR pairing states */
enum {
SMP_BR_STATE_IDLE = SMP_STATE_IDLE,
@@ -193,7 +222,8 @@ typedef struct {
typedef union {
uint8_t* p_data; /* uint8_t type data pointer */
tSMP_KEY key;
- tSMP_STATUS status;
+ uint8_t status;
+ uint16_t reason;
uint32_t passkey;
tSMP_OOB_DATA_TYPE req_oob_type;
} tSMP_INT_DATA;
@@ -204,13 +234,13 @@ typedef union {
#define SMP_PAIR_FLAGS_CMD_CONFIRM (1 << SMP_OPCODE_CONFIRM) /* 1 << 3 */
#define SMP_PAIR_FLAG_ENC_AFTER_PAIR (1 << 4)
#define SMP_PAIR_FLAG_HAVE_PEER_DHK_CHK \
- (1 << 5) /* used on peripheral to resolve race condition */
+ (1 << 5) /* used on slave to resolve race condition */
#define SMP_PAIR_FLAG_HAVE_PEER_PUBL_KEY \
- (1 << 6) /* used on peripheral to resolve race condition */
+ (1 << 6) /* used on slave to resolve race condition */
#define SMP_PAIR_FLAG_HAVE_PEER_COMM \
(1 << 7) /* used to resolve race condition */
#define SMP_PAIR_FLAG_HAVE_LOCAL_PUBL_KEY \
- (1 << 8) /* used on peripheral to resolve race condition */
+ (1 << 8) /* used on slave to resolve race condition */
/* check if authentication requirement need MITM protection */
#define SMP_NO_MITM_REQUIRED(x) (((x)&SMP_AUTH_YN_BIT) == 0)
@@ -234,10 +264,10 @@ typedef struct {
bool smp_over_br;
tSMP_BR_STATE br_state; /* if SMP over BR/ERD has priority over SMP */
uint8_t failure;
- tSMP_STATUS status;
+ uint8_t status;
uint8_t role;
uint16_t flags;
- tSMP_EVT cb_evt;
+ uint8_t cb_evt;
tSMP_SEC_LEVEL sec_level;
bool connect_initialized;
Octet16 confirm;
@@ -288,7 +318,7 @@ typedef struct {
Octet16 csrk; /* storage for local CSRK */
uint16_t ediv;
BT_OCTET8 enc_rand;
- tBLE_ADDR_TYPE addr_type;
+ uint8_t addr_type;
RawAddress local_bda;
bool is_pair_cancel;
bool discard_sec_req;
@@ -296,7 +326,7 @@ typedef struct {
uint8_t rcvd_cmd_len;
uint16_t total_tx_unacked;
bool wait_for_authorization_complete;
- tSMP_STATUS cert_failure; /*failure case for certification */
+ uint8_t cert_failure; /*failure case for certification */
alarm_t* delayed_auth_timer_ent;
} tSMP_CB;
@@ -337,7 +367,7 @@ extern void smp_proc_rand(tSMP_CB* p_cb, tSMP_INT_DATA* p_data);
extern void smp_process_pairing_public_key(tSMP_CB* p_cb,
tSMP_INT_DATA* p_data);
extern void smp_proc_enc_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data);
-extern void smp_proc_central_id(tSMP_CB* p_cb, tSMP_INT_DATA* p_data);
+extern void smp_proc_master_id(tSMP_CB* p_cb, tSMP_INT_DATA* p_data);
extern void smp_proc_id_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data);
extern void smp_proc_id_addr(tSMP_CB* p_cb, tSMP_INT_DATA* p_data);
extern void smp_proc_sec_grant(tSMP_CB* p_cb, tSMP_INT_DATA* p_data);
@@ -394,8 +424,8 @@ extern void smp_derive_link_key_from_long_term_key(tSMP_CB* p_cb,
extern void smp_br_process_pairing_command(tSMP_CB* p_cb,
tSMP_INT_DATA* p_data);
extern void smp_br_process_security_grant(tSMP_CB* p_cb, tSMP_INT_DATA* p_data);
-extern void smp_br_process_peripheral_keys_response(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data);
+extern void smp_br_process_slave_keys_response(tSMP_CB* p_cb,
+ tSMP_INT_DATA* p_data);
extern void smp_br_send_pair_response(tSMP_CB* p_cb, tSMP_INT_DATA* p_data);
extern void smp_br_check_authorization_request(tSMP_CB* p_cb,
tSMP_INT_DATA* p_data);
@@ -424,6 +454,7 @@ extern bool smp_command_has_invalid_length(tSMP_CB* p_cb);
extern bool smp_command_has_invalid_parameters(tSMP_CB* p_cb);
extern void smp_reject_unexpected_pairing_command(const RawAddress& bd_addr);
extern tSMP_ASSO_MODEL smp_select_association_model(tSMP_CB* p_cb);
+extern void smp_reverse_array(uint8_t* arr, uint8_t len);
extern uint8_t smp_calculate_random_input(uint8_t* random, uint8_t round);
extern void smp_collect_local_io_capabilities(uint8_t* iocap, tSMP_CB* p_cb);
extern void smp_collect_peer_io_capabilities(uint8_t* iocap, tSMP_CB* p_cb);
@@ -458,12 +489,20 @@ extern void smp_start_nonce_generation(tSMP_CB* p_cb);
extern bool smp_calculate_link_key_from_long_term_key(tSMP_CB* p_cb);
extern bool smp_calculate_long_term_key_from_link_key(tSMP_CB* p_cb);
+#if (SMP_DEBUG == TRUE)
+extern void smp_debug_print_nbyte_little_endian(uint8_t* p,
+ const char* key_name,
+ uint8_t len);
+
+inline void smp_debug_print_nbyte_little_endian(const Octet16& p,
+ const char* key_name,
+ uint8_t len) {
+ smp_debug_print_nbyte_little_endian(const_cast<uint8_t*>(p.data()), key_name,
+ len);
+}
+#endif
+
extern void print128(const Octet16& x, const uint8_t* key_name);
extern void smp_xor_128(Octet16* a, const Octet16& b);
-/* Save the p_cb->sc_oob_data.loc_oob_data for later, since the p_cb gets
- * cleaned up */
-extern void smp_save_local_oob_data(tSMP_CB* p_cb);
-extern void smp_clear_local_oob_data();
-
#endif /* SMP_INT_H */
diff --git a/stack/smp/smp_keys.cc b/stack/smp/smp_keys.cc
index 5614499fb..a372ba46a 100644
--- a/stack/smp/smp_keys.cc
+++ b/stack/smp/smp_keys.cc
@@ -23,25 +23,24 @@
******************************************************************************/
#include "bt_target.h"
+#if (SMP_DEBUG == TRUE)
+#include <stdio.h>
+#endif
#include <base/bind.h>
#include <string.h>
#include "bt_utils.h"
#include "btm_ble_api.h"
#include "btm_ble_int.h"
+#include "btm_int.h"
#include "device/include/controller.h"
#include "hcimsgs.h"
#include "osi/include/osi.h"
#include "p_256_ecc_pp.h"
#include "smp_int.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_sec.h"
#include "stack/crypto_toolbox/crypto_toolbox.h"
-#include "stack/include/acl_api.h"
#include <algorithm>
-extern tBTM_CB btm_cb; // TODO Remove
-
using base::Bind;
using crypto_toolbox::aes_128;
@@ -55,23 +54,27 @@ static void smp_process_private_key(tSMP_CB* p_cb);
#define SMP_PASSKEY_MASK 0xfff00000
-// If there is data saved here, then use its info instead
-// This needs to be cleared on a successfult pairing using the oob data
-static tSMP_LOC_OOB_DATA saved_local_oob_data = {};
-
-void smp_save_local_oob_data(tSMP_CB* p_cb) {
- saved_local_oob_data = p_cb->sc_oob_data.loc_oob_data;
-}
-
-void smp_clear_local_oob_data() { saved_local_oob_data = {}; }
-
-static bool is_empty(tSMP_LOC_OOB_DATA* data) {
- tSMP_LOC_OOB_DATA empty_data = {};
- return memcmp(data, &empty_data, sizeof(tSMP_LOC_OOB_DATA)) == 0;
-}
-
void smp_debug_print_nbyte_little_endian(uint8_t* p, const char* key_name,
uint8_t len) {
+#if (SMP_DEBUG == TRUE)
+ int ind;
+ int col_count = 32;
+ int row_count;
+ uint8_t p_buf[512];
+
+ SMP_TRACE_DEBUG("%s(LSB ~ MSB):", key_name);
+ memset(p_buf, 0, sizeof(p_buf));
+ row_count = len % col_count ? len / col_count + 1 : len / col_count;
+
+ ind = 0;
+ for (int row = 0; row < row_count; row++) {
+ for (int column = 0, x = 0; (ind < len) && (column < col_count);
+ column++, ind++) {
+ x += snprintf((char*)&p_buf[x], sizeof(p_buf) - x, "%02x ", p[ind]);
+ }
+ SMP_TRACE_DEBUG(" [%03d]: %s", row * col_count, p_buf);
+ }
+#endif
}
inline void smp_debug_print_nbyte_little_endian(const Octet16& p,
@@ -83,6 +86,25 @@ inline void smp_debug_print_nbyte_little_endian(const Octet16& p,
void smp_debug_print_nbyte_big_endian(uint8_t* p, const char* key_name,
uint8_t len) {
+#if (SMP_DEBUG == TRUE)
+ uint8_t p_buf[512];
+
+ SMP_TRACE_DEBUG("%s(MSB ~ LSB):", key_name);
+ memset(p_buf, 0, sizeof(p_buf));
+
+ int ind = 0;
+ int ncols = 32; /* num entries in one line */
+ int nrows; /* num lines */
+
+ nrows = len % ncols ? len / ncols + 1 : len / ncols;
+ for (int row = 0; row < nrows; row++) {
+ for (int col = 0, x = 0; (ind < len) && (col < ncols); col++, ind++) {
+ x += snprintf((char*)&p_buf[len - x - 1], sizeof(p_buf) - (len - x - 1),
+ "%02x ", p[ind]);
+ }
+ SMP_TRACE_DEBUG("[%03d]: %s", row * ncols, p_buf);
+ }
+#endif
}
/** This function is called to process a passkey. */
@@ -255,7 +277,7 @@ Octet16 smp_gen_p1_4_confirm(tSMP_CB* p_cb,
SMP_TRACE_DEBUG("%s", __func__);
Octet16 p1;
uint8_t* p = p1.data();
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ if (p_cb->role == HCI_ROLE_MASTER) {
/* iat': initiator's (local) address type */
UINT8_TO_STREAM(p, p_cb->addr_type);
/* rat': responder's (remote) address type */
@@ -291,7 +313,7 @@ Octet16 smp_gen_p2_4_confirm(tSMP_CB* p_cb, const RawAddress& remote_bda) {
uint8_t* p = p2.data();
/* 32-bit Padding */
memset(p, 0, OCTET16_LEN);
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ if (p_cb->role == HCI_ROLE_MASTER) {
/* ra : Responder's (remote) address */
BDADDR_TO_STREAM(p, remote_bda);
/* ia : Initiator's (local) address */
@@ -319,7 +341,7 @@ tSMP_STATUS smp_calculate_comfirm(tSMP_CB* p_cb, const Octet16& rand,
Octet16* output) {
SMP_TRACE_DEBUG("%s", __func__);
RawAddress remote_bda;
- tBLE_ADDR_TYPE remote_bd_addr_type = BLE_ADDR_PUBLIC;
+ tBLE_ADDR_TYPE remote_bd_addr_type = 0;
/* get remote connection specific bluetooth address */
if (!BTM_ReadRemoteConnectionAddr(p_cb->pairing_bda, remote_bda,
&remote_bd_addr_type)) {
@@ -449,6 +471,9 @@ static void smp_process_stk(tSMP_CB* p_cb, Octet16* p) {
tSMP_KEY key;
SMP_TRACE_DEBUG("smp_process_stk ");
+#if (SMP_DEBUG == TRUE)
+ SMP_TRACE_ERROR("STK Generated");
+#endif
smp_mask_enc_key(p_cb->loc_enc_size, p);
key.key_type = SMP_KEY_TYPE_STK;
@@ -561,7 +586,7 @@ Octet16 smp_calculate_legacy_short_term_key(tSMP_CB* p_cb) {
SMP_TRACE_DEBUG("%s", __func__);
Octet16 text{0};
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ if (p_cb->role == HCI_ROLE_MASTER) {
memcpy(text.data(), p_cb->rand.data(), BT_OCTET8_LEN);
memcpy(text.data() + BT_OCTET8_LEN, p_cb->rrand.data(), BT_OCTET8_LEN);
} else {
@@ -588,28 +613,6 @@ Octet16 smp_calculate_legacy_short_term_key(tSMP_CB* p_cb) {
void smp_create_private_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
SMP_TRACE_DEBUG("%s", __func__);
- // Only use the stored OOB data if we are in an oob association model
- if (p_cb->selected_association_model == SMP_MODEL_SEC_CONN_OOB) {
- LOG_WARN("OOB Association Model");
- // Make sure our data isn't empty, otherwise we generate new and eventually
- // pairing will fail Not much we can do about it at this point, just have to
- // generate new data The data will be cleared after the advertiser times
- // out, so if the advertiser times out we want the pairing to fail anyway.
- if (!is_empty(&saved_local_oob_data)) {
- LOG_WARN("Found OOB data, loading keys");
- for (int i = 0; i < BT_OCTET32_LEN; i++) {
- p_cb->private_key[i] = saved_local_oob_data.private_key_used[i];
- p_cb->loc_publ_key.x[i] = saved_local_oob_data.publ_key_used.x[i];
- p_cb->loc_publ_key.y[i] = saved_local_oob_data.publ_key_used.y[i];
- }
- p_cb->sc_oob_data.loc_oob_data = saved_local_oob_data;
- p_cb->local_random = saved_local_oob_data.randomizer;
- smp_process_private_key(p_cb);
- return;
- }
- LOG_WARN("OOB Association Model with no saved data present");
- }
-
btsnd_hcic_ble_rand(Bind(
[](tSMP_CB* p_cb, BT_OCTET8 rand) {
memcpy((void*)p_cb->private_key, rand, BT_OCTET8_LEN);
@@ -651,18 +654,19 @@ void smp_create_private_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
*
******************************************************************************/
void smp_use_oob_private_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- LOG_INFO("req_oob_type: %d, role: %d", p_cb->req_oob_type, p_cb->role);
+ SMP_TRACE_DEBUG("%s req_oob_type: %d, role: %d", __func__, p_cb->req_oob_type,
+ p_cb->role);
switch (p_cb->req_oob_type) {
case SMP_OOB_BOTH:
case SMP_OOB_LOCAL:
- LOG_INFO("restore secret key");
+ SMP_TRACE_DEBUG("%s restore secret key", __func__)
memcpy(p_cb->private_key, p_cb->sc_oob_data.loc_oob_data.private_key_used,
BT_OCTET32_LEN);
smp_process_private_key(p_cb);
break;
default:
- LOG_INFO("create secret key anew");
+ SMP_TRACE_DEBUG("%s create secret key anew", __func__);
smp_set_state(SMP_STATE_PAIR_REQ_RSP);
smp_decide_association_model(p_cb, NULL);
break;
@@ -748,9 +752,9 @@ void smp_calculate_local_commitment(tSMP_CB* p_cb) {
switch (p_cb->selected_association_model) {
case SMP_MODEL_SEC_CONN_JUSTWORKS:
case SMP_MODEL_SEC_CONN_NUM_COMP:
- if (p_cb->role == HCI_ROLE_CENTRAL)
+ if (p_cb->role == HCI_ROLE_MASTER)
SMP_TRACE_WARNING(
- "local commitment calc on central is not expected "
+ "local commitment calc on master is not expected "
"for Just Works/Numeric Comparison models");
p_cb->commitment = crypto_toolbox::f4(
p_cb->loc_publ_key.x, p_cb->peer_publ_key.x, p_cb->rand, 0);
@@ -787,9 +791,9 @@ Octet16 smp_calculate_peer_commitment(tSMP_CB* p_cb) {
switch (p_cb->selected_association_model) {
case SMP_MODEL_SEC_CONN_JUSTWORKS:
case SMP_MODEL_SEC_CONN_NUM_COMP:
- if (p_cb->role == HCI_ROLE_PERIPHERAL)
+ if (p_cb->role == HCI_ROLE_SLAVE)
SMP_TRACE_WARNING(
- "peer commitment calc on peripheral is not expected "
+ "peer commitment calc on slave is not expected "
"for Just Works/Numeric Comparison models");
output = crypto_toolbox::f4(p_cb->peer_publ_key.x, p_cb->loc_publ_key.x,
p_cb->rrand, 0);
@@ -828,7 +832,7 @@ void smp_calculate_numeric_comparison_display_number(tSMP_CB* p_cb,
tSMP_INT_DATA* p_data) {
SMP_TRACE_DEBUG("%s", __func__);
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ if (p_cb->role == HCI_ROLE_MASTER) {
p_cb->number_to_display = crypto_toolbox::g2(
p_cb->loc_publ_key.x, p_cb->peer_publ_key.x, p_cb->rand, p_cb->rrand);
} else {
@@ -908,6 +912,10 @@ void smp_calculate_peer_dhkey_check(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
p_cb->local_random, iocap, b, a);
SMP_TRACE_EVENT("peer DHKey check calculation is completed");
+#if (SMP_DEBUG == TRUE)
+ smp_debug_print_nbyte_little_endian(param_buf, "peer DHKey check",
+ OCTET16_LEN);
+#endif
key.key_type = SMP_KEY_TYPE_PEER_DHK_CHCK;
key.p_data = param_buf.data();
tSMP_INT_DATA smp_int_data;
diff --git a/stack/smp/smp_l2c.cc b/stack/smp/smp_l2c.cc
index 6c286b133..2daeb2171 100644
--- a/stack/smp/smp_l2c.cc
+++ b/stack/smp/smp_l2c.cc
@@ -22,19 +22,18 @@
*
******************************************************************************/
-#define LOG_TAG "bluetooth"
-
+#include <cutils/log.h>
#include "bt_target.h"
#include <string.h>
#include "btm_ble_api.h"
#include "common/metrics.h"
#include "l2c_api.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
+
#include "smp_int.h"
+static void smp_tx_complete_callback(uint16_t cid, uint16_t num_pkt);
+
static void smp_connect_callback(uint16_t channel, const RawAddress& bd_addr,
bool connected, uint16_t reason,
tBT_TRANSPORT transport);
@@ -58,9 +57,16 @@ static void smp_br_data_received(uint16_t channel, const RawAddress& bd_addr,
void smp_l2cap_if_init(void) {
tL2CAP_FIXED_CHNL_REG fixed_reg;
SMP_TRACE_EVENT("SMDBG l2c %s", __func__);
+ fixed_reg.fixed_chnl_opts.mode = L2CAP_FCR_BASIC_MODE;
+ fixed_reg.fixed_chnl_opts.max_transmit = 0;
+ fixed_reg.fixed_chnl_opts.rtrans_tout = 0;
+ fixed_reg.fixed_chnl_opts.mon_tout = 0;
+ fixed_reg.fixed_chnl_opts.mps = 0;
+ fixed_reg.fixed_chnl_opts.tx_win_sz = 0;
fixed_reg.pL2CA_FixedConn_Cb = smp_connect_callback;
fixed_reg.pL2CA_FixedData_Cb = smp_data_received;
+ fixed_reg.pL2CA_FixedTxComplete_Cb = smp_tx_complete_callback;
fixed_reg.pL2CA_FixedCong_Cb =
NULL; /* do not handle congestion on this channel */
@@ -84,36 +90,21 @@ void smp_l2cap_if_init(void) {
* connected (conn = true)/disconnected (conn = false).
*
******************************************************************************/
-static void smp_connect_callback(UNUSED_ATTR uint16_t channel,
- const RawAddress& bd_addr, bool connected,
- UNUSED_ATTR uint16_t reason,
+static void smp_connect_callback(uint16_t channel, const RawAddress& bd_addr,
+ bool connected, uint16_t reason,
tBT_TRANSPORT transport) {
tSMP_CB* p_cb = &smp_cb;
tSMP_INT_DATA int_data;
- if (bd_addr.IsEmpty()) {
- LOG_WARN("Received unexpected callback for empty address");
- return;
- }
-
- if (transport == BT_TRANSPORT_BR_EDR) {
- LOG_WARN("Received unexpected callback on classic channel peer:%s",
- PRIVATE_ADDRESS(bd_addr));
- return;
- }
+ SMP_TRACE_EVENT("%s: SMDBG l2c: bd_addr=%s, p_cb->pairing_bda=%s", __func__,
+ bd_addr.ToString().c_str(),
+ p_cb->pairing_bda.ToString().c_str());
- if (connected) {
- LOG_DEBUG("SMP Received connect callback bd_addr:%s transport:%s",
- PRIVATE_ADDRESS(bd_addr), bt_transport_text(transport).c_str());
- } else {
- LOG_DEBUG("SMP Received disconnect callback bd_addr:%s transport:%s",
- PRIVATE_ADDRESS(bd_addr), bt_transport_text(transport).c_str());
- }
+ if (transport == BT_TRANSPORT_BR_EDR || bd_addr.IsEmpty()) return;
if (bd_addr == p_cb->pairing_bda) {
- LOG_DEBUG("Received callback for device in pairing process:%s state:%s",
- PRIVATE_ADDRESS(bd_addr),
- (connected) ? "connected" : "disconnected");
+ VLOG(2) << __func__ << " for pairing BDA: " << bd_addr
+ << " Event: " << ((connected) ? "connected" : "disconnected");
if (connected) {
if (!p_cb->connect_initialized) {
@@ -128,6 +119,7 @@ static void smp_connect_callback(UNUSED_ATTR uint16_t channel,
smp_sm_event(p_cb, SMP_L2CAP_CONN_EVT, NULL);
}
} else {
+ int_data.reason = reason;
/* Disconnected while doing security */
smp_sm_event(p_cb, SMP_L2CAP_DISCONN_EVT, &int_data);
}
@@ -209,7 +201,7 @@ static void smp_data_received(uint16_t channel, const RawAddress& bd_addr,
p_cb->rcvd_cmd_len = (uint8_t)p_buf->len;
tSMP_INT_DATA smp_int_data;
smp_int_data.p_data = p;
- smp_sm_event(p_cb, static_cast<tSMP_EVENT>(cmd), &smp_int_data);
+ smp_sm_event(p_cb, cmd, &smp_int_data);
}
osi_free(p_buf);
@@ -217,6 +209,32 @@ static void smp_data_received(uint16_t channel, const RawAddress& bd_addr,
/*******************************************************************************
*
+ * Function smp_tx_complete_callback
+ *
+ * Description SMP channel tx complete callback
+ *
+ ******************************************************************************/
+static void smp_tx_complete_callback(uint16_t cid, uint16_t num_pkt) {
+ tSMP_CB* p_cb = &smp_cb;
+
+ if (p_cb->total_tx_unacked >= num_pkt)
+ p_cb->total_tx_unacked -= num_pkt;
+ else
+ SMP_TRACE_ERROR("Unexpected %s: num_pkt = %d", __func__, num_pkt);
+
+ if (p_cb->total_tx_unacked == 0 && p_cb->wait_for_authorization_complete) {
+ tSMP_INT_DATA smp_int_data;
+ smp_int_data.status = SMP_SUCCESS;
+ if (cid == L2CAP_SMP_CID) {
+ smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &smp_int_data);
+ } else {
+ smp_br_state_machine_event(p_cb, SMP_BR_AUTH_CMPL_EVT, &smp_int_data);
+ }
+ }
+}
+
+/*******************************************************************************
+ *
* Function smp_br_connect_callback
*
* Description This callback function is called by L2CAP to indicate that
@@ -254,6 +272,7 @@ static void smp_br_connect_callback(uint16_t channel, const RawAddress& bd_addr,
smp_br_state_machine_event(p_cb, SMP_BR_L2CAP_CONN_EVT, NULL);
}
} else {
+ int_data.reason = reason;
/* Disconnected while doing security */
smp_br_state_machine_event(p_cb, SMP_BR_L2CAP_DISCONN_EVT, &int_data);
}
@@ -297,7 +316,7 @@ static void smp_br_data_received(uint16_t channel, const RawAddress& bd_addr,
if (SMP_OPCODE_PAIRING_REQ == cmd) {
if ((p_cb->state == SMP_STATE_IDLE) &&
(p_cb->br_state == SMP_BR_STATE_IDLE)) {
- p_cb->role = HCI_ROLE_PERIPHERAL;
+ p_cb->role = HCI_ROLE_SLAVE;
p_cb->smp_over_br = true;
p_cb->pairing_bda = bd_addr;
} else if (bd_addr != p_cb->pairing_bda) {
@@ -319,8 +338,7 @@ static void smp_br_data_received(uint16_t channel, const RawAddress& bd_addr,
p_cb->rcvd_cmd_len = (uint8_t)p_buf->len;
tSMP_INT_DATA smp_int_data;
smp_int_data.p_data = p;
- smp_br_state_machine_event(p_cb, static_cast<tSMP_EVENT>(cmd),
- &smp_int_data);
+ smp_br_state_machine_event(p_cb, cmd, &smp_int_data);
}
osi_free(p_buf);
diff --git a/stack/smp/smp_main.cc b/stack/smp/smp_main.cc
index ed5d94c81..89ecb4fb9 100644
--- a/stack/smp/smp_main.cc
+++ b/stack/smp/smp_main.cc
@@ -16,15 +16,12 @@
*
******************************************************************************/
-#define LOG_TAG "bluetooth"
-
#include "bt_target.h"
+#include <log/log.h>
#include <string.h>
#include "smp_int.h"
-#include "osi/include/log.h"
-
const char* const smp_state_name[] = {
"SMP_STATE_IDLE",
"SMP_STATE_WAIT_APP_RSP",
@@ -51,7 +48,7 @@ const char* const smp_event_name[] = {"PAIRING_REQ_EVT",
"RAND_EVT",
"PAIRING_FAILED_EVT",
"ENC_INFO_EVT",
- "CENTRAL_ID_EVT",
+ "MASTER_ID_EVT",
"ID_INFO_EVT",
"ID_ADDR_EVT",
"SIGN_INFO_EVT",
@@ -112,7 +109,7 @@ enum {
SMP_PROC_CONFIRM,
SMP_PROC_RAND,
SMP_PROC_ENC_INFO,
- SMP_PROC_CENTRAL_ID,
+ SMP_PROC_MASTER_ID,
SMP_PROC_ID_INFO,
SMP_PROC_ID_ADDR,
SMP_PROC_SRK_INFO,
@@ -176,7 +173,7 @@ static const tSMP_ACT smp_sm_action[] = {
smp_proc_confirm,
smp_proc_rand,
smp_proc_enc_info,
- smp_proc_central_id,
+ smp_proc_master_id,
smp_proc_id_info,
smp_proc_id_addr,
smp_proc_srk_info,
@@ -223,8 +220,8 @@ static const tSMP_ACT smp_sm_action[] = {
smp_set_local_oob_random_commitment,
smp_idle_terminate};
-/************ SMP Central FSM State/Event Indirection Table **************/
-static const uint8_t smp_central_entry_map[][SMP_STATE_MAX] = {
+/************ SMP Master FSM State/Event Indirection Table **************/
+static const uint8_t smp_master_entry_map[][SMP_STATE_MAX] = {
/* state name: */
/* Idle, WaitApp Rsp, SecReq Pend, Pair ReqRsp, Wait Cfm, Confirm, Rand,
PublKey Exch, SCPhs1 Strt, Wait Cmtm, Wait Nonce, SCPhs2 Strt, Wait
@@ -242,7 +239,7 @@ static const uint8_t smp_central_entry_map[][SMP_STATE_MAX] = {
0x81, 0, 0x81, 0},
/* ENC_INFO */
{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0},
- /* CENTRAL_ID */
+ /* MASTER_ID */
{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 0},
/* ID_INFO */
{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 2, 0},
@@ -323,7 +320,7 @@ static const uint8_t smp_all_table[][SMP_SM_NUM_COLS] = {
/* L2C_DISC */
{SMP_PAIR_TERMINATE, SMP_SM_NO_ACTION, SMP_STATE_IDLE}};
-static const uint8_t smp_central_idle_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_idle_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* L2C_CONN */
{SMP_SEND_APP_CBACK, SMP_SM_NO_ACTION, SMP_STATE_WAIT_APP_RSP},
@@ -339,8 +336,8 @@ static const uint8_t smp_central_idle_table[][SMP_SM_NUM_COLS] = {
};
-static const uint8_t
- smp_central_wait_for_app_response_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_wait_for_app_response_table[][SMP_SM_NUM_COLS] =
+ {
/* Event Action Next State */
/* SEC_GRANT */
{SMP_PROC_SEC_GRANT, SMP_SEND_APP_CBACK, SMP_STATE_WAIT_APP_RSP},
@@ -373,8 +370,8 @@ static const uint8_t
/* SC_OOB_DATA */
{SMP_USE_OOB_PRIVATE_KEY, SMP_SM_NO_ACTION, SMP_STATE_PUBLIC_KEY_EXCH}};
-static const uint8_t
- smp_central_pair_request_response_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_pair_request_response_table[][SMP_SM_NUM_COLS] =
+ {
/* Event Action Next State */
/* PAIR_RSP */
{SMP_PROC_PAIR_CMD, SMP_SM_NO_ACTION, SMP_STATE_PAIR_REQ_RSP},
@@ -387,18 +384,18 @@ static const uint8_t
/* PUBL_KEY_EXCH_REQ */,
{SMP_CREATE_PRIVATE_KEY, SMP_SM_NO_ACTION, SMP_STATE_PUBLIC_KEY_EXCH}};
-static const uint8_t smp_central_wait_for_confirm_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_wait_for_confirm_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* KEY_READY*/
/* CONFIRM ready */
{SMP_SEND_CONFIRM, SMP_SM_NO_ACTION, SMP_STATE_CONFIRM}};
-static const uint8_t smp_central_confirm_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_confirm_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* CONFIRM */
{SMP_PROC_CONFIRM, SMP_SEND_RAND, SMP_STATE_RAND}};
-static const uint8_t smp_central_rand_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_rand_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* RAND */
{SMP_PROC_RAND, SMP_GENERATE_COMPARE, SMP_STATE_RAND},
@@ -407,44 +404,40 @@ static const uint8_t smp_central_rand_table[][SMP_SM_NUM_COLS] = {
/* ENC_REQ */
{SMP_GENERATE_STK, SMP_SM_NO_ACTION, SMP_STATE_ENCRYPTION_PENDING}};
-static const uint8_t smp_central_public_key_exchange_table[][SMP_SM_NUM_COLS] =
- {
- /* Event Action Next State */
- /* LOC_PUBL_KEY_CRTD */
- {SMP_SEND_PAIR_PUBLIC_KEY, SMP_SM_NO_ACTION, SMP_STATE_PUBLIC_KEY_EXCH},
- /* PAIR_PUBLIC_KEY */
- {SMP_PROCESS_PAIR_PUBLIC_KEY, SMP_SM_NO_ACTION,
- SMP_STATE_PUBLIC_KEY_EXCH},
- /* BOTH_PUBL_KEYS_RCVD */
- {SMP_HAVE_BOTH_PUBLIC_KEYS, SMP_SM_NO_ACTION,
- SMP_STATE_SEC_CONN_PHS1_START},
+static const uint8_t smp_master_public_key_exchange_table[][SMP_SM_NUM_COLS] = {
+ /* Event Action Next State */
+ /* LOC_PUBL_KEY_CRTD */
+ {SMP_SEND_PAIR_PUBLIC_KEY, SMP_SM_NO_ACTION, SMP_STATE_PUBLIC_KEY_EXCH},
+ /* PAIR_PUBLIC_KEY */
+ {SMP_PROCESS_PAIR_PUBLIC_KEY, SMP_SM_NO_ACTION, SMP_STATE_PUBLIC_KEY_EXCH},
+ /* BOTH_PUBL_KEYS_RCVD */
+ {SMP_HAVE_BOTH_PUBLIC_KEYS, SMP_SM_NO_ACTION,
+ SMP_STATE_SEC_CONN_PHS1_START},
};
-static const uint8_t smp_central_sec_conn_phs1_start_table[][SMP_SM_NUM_COLS] =
- {
- /* Event Action Next State */
- /* SC_DHKEY_CMPLT */
- {SMP_START_SEC_CONN_PHASE1, SMP_SM_NO_ACTION,
- SMP_STATE_SEC_CONN_PHS1_START},
- /* HAVE_LOC_NONCE */
- {SMP_PROCESS_LOCAL_NONCE, SMP_SM_NO_ACTION, SMP_STATE_WAIT_COMMITMENT},
- /* TK_REQ */
- {SMP_SEND_APP_CBACK, SMP_SM_NO_ACTION, SMP_STATE_WAIT_APP_RSP},
- /* SMP_MODEL_SEC_CONN_PASSKEY_DISP model, passkey is sent up to
- display,*/
- /* It's time to start commitment calculation */
- /* KEY_READY */
- {SMP_START_PASSKEY_VERIFICATION, SMP_SM_NO_ACTION,
- SMP_STATE_SEC_CONN_PHS1_START},
- /* PAIR_KEYPR_NOTIF */
- {SMP_PROCESS_KEYPRESS_NOTIFICATION, SMP_SEND_APP_CBACK,
- SMP_STATE_SEC_CONN_PHS1_START},
- /* PAIR_COMMITM */
- {SMP_PROCESS_PAIRING_COMMITMENT, SMP_SM_NO_ACTION,
- SMP_STATE_SEC_CONN_PHS1_START},
+static const uint8_t smp_master_sec_conn_phs1_start_table[][SMP_SM_NUM_COLS] = {
+ /* Event Action Next State */
+ /* SC_DHKEY_CMPLT */
+ {SMP_START_SEC_CONN_PHASE1, SMP_SM_NO_ACTION,
+ SMP_STATE_SEC_CONN_PHS1_START},
+ /* HAVE_LOC_NONCE */
+ {SMP_PROCESS_LOCAL_NONCE, SMP_SM_NO_ACTION, SMP_STATE_WAIT_COMMITMENT},
+ /* TK_REQ */
+ {SMP_SEND_APP_CBACK, SMP_SM_NO_ACTION, SMP_STATE_WAIT_APP_RSP},
+ /* SMP_MODEL_SEC_CONN_PASSKEY_DISP model, passkey is sent up to display,*/
+ /* It's time to start commitment calculation */
+ /* KEY_READY */
+ {SMP_START_PASSKEY_VERIFICATION, SMP_SM_NO_ACTION,
+ SMP_STATE_SEC_CONN_PHS1_START},
+ /* PAIR_KEYPR_NOTIF */
+ {SMP_PROCESS_KEYPRESS_NOTIFICATION, SMP_SEND_APP_CBACK,
+ SMP_STATE_SEC_CONN_PHS1_START},
+ /* PAIR_COMMITM */
+ {SMP_PROCESS_PAIRING_COMMITMENT, SMP_SM_NO_ACTION,
+ SMP_STATE_SEC_CONN_PHS1_START},
};
-static const uint8_t smp_central_wait_commitment_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_wait_commitment_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* PAIR_COMMITM */
{SMP_PROCESS_PAIRING_COMMITMENT, SMP_SEND_RAND, SMP_STATE_WAIT_NONCE},
@@ -453,7 +446,7 @@ static const uint8_t smp_central_wait_commitment_table[][SMP_SM_NUM_COLS] = {
SMP_STATE_WAIT_COMMITMENT},
};
-static const uint8_t smp_central_wait_nonce_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_wait_nonce_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* peer nonce is received */
/* RAND */
@@ -467,22 +460,21 @@ static const uint8_t smp_central_wait_nonce_table[][SMP_SM_NUM_COLS] = {
{SMP_SEND_APP_CBACK, SMP_SM_NO_ACTION, SMP_STATE_WAIT_APP_RSP},
};
-static const uint8_t smp_central_sec_conn_phs2_start_table[][SMP_SM_NUM_COLS] =
- {
- /* Event Action Next State */
- /* SC_PHASE1_CMPLT */
- {SMP_CALCULATE_LOCAL_DHKEY_CHECK, SMP_SEND_DHKEY_CHECK,
- SMP_STATE_WAIT_DHK_CHECK},
+static const uint8_t smp_master_sec_conn_phs2_start_table[][SMP_SM_NUM_COLS] = {
+ /* Event Action Next State */
+ /* SC_PHASE1_CMPLT */
+ {SMP_CALCULATE_LOCAL_DHKEY_CHECK, SMP_SEND_DHKEY_CHECK,
+ SMP_STATE_WAIT_DHK_CHECK},
};
-static const uint8_t smp_central_wait_dhk_check_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_wait_dhk_check_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* PAIR_DHKEY_CHCK */
{SMP_PROCESS_DHKEY_CHECK, SMP_CALCULATE_PEER_DHKEY_CHECK,
SMP_STATE_DHK_CHECK},
};
-static const uint8_t smp_central_dhk_check_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_dhk_check_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* locally calculated peer dhkey check is ready -> compare it withs DHKey
* Check
@@ -497,7 +489,7 @@ static const uint8_t smp_central_dhk_check_table[][SMP_SM_NUM_COLS] = {
{SMP_GENERATE_STK, SMP_SM_NO_ACTION, SMP_STATE_ENCRYPTION_PENDING},
};
-static const uint8_t smp_central_enc_pending_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_enc_pending_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* STK ready */
/* KEY_READY */
@@ -506,7 +498,7 @@ static const uint8_t smp_central_enc_pending_table[][SMP_SM_NUM_COLS] = {
{SMP_CHECK_AUTH_REQ, SMP_SM_NO_ACTION, SMP_STATE_ENCRYPTION_PENDING},
/* BOND_REQ */
{SMP_KEY_DISTRIBUTE, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING}};
-static const uint8_t smp_central_bond_pending_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_master_bond_pending_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* ENC_INFO */
{SMP_PROC_ENC_INFO, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING},
@@ -514,8 +506,8 @@ static const uint8_t smp_central_bond_pending_table[][SMP_SM_NUM_COLS] = {
{SMP_PROC_ID_INFO, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING},
/* SIGN_INFO */
{SMP_PROC_SRK_INFO, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING},
- /* CENTRAL_ID */
- {SMP_PROC_CENTRAL_ID, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING},
+ /* MASTER_ID */
+ {SMP_PROC_MASTER_ID, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING},
/* ID_ADDR */
{SMP_PROC_ID_ADDR, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING},
/* KEY_READY */
@@ -523,7 +515,7 @@ static const uint8_t smp_central_bond_pending_table[][SMP_SM_NUM_COLS] = {
{SMP_SEND_ENC_INFO, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING}};
static const uint8_t
- smp_central_create_local_sec_conn_oob_data[][SMP_SM_NUM_COLS] = {
+ smp_master_create_local_sec_conn_oob_data[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* LOC_PUBL_KEY_CRTD */
{SMP_SET_LOCAL_OOB_KEYS, SMP_SM_NO_ACTION,
@@ -531,8 +523,8 @@ static const uint8_t
/* HAVE_LOC_NONCE */
{SMP_SET_LOCAL_OOB_RAND_COMMITMENT, SMP_SM_NO_ACTION, SMP_STATE_IDLE}};
-/************ SMP Peripheral FSM State/Event Indirection Table **************/
-static const uint8_t smp_peripheral_entry_map[][SMP_STATE_MAX] = {
+/************ SMP Slave FSM State/Event Indirection Table **************/
+static const uint8_t smp_slave_entry_map[][SMP_STATE_MAX] = {
/* state name: */
/* Idle, WaitApp Rsp, SecReq Pend, Pair ReqRsp, Wait Cfm, Confirm, Rand,
PublKey Exch, SCPhs1 Strt, Wait Cmtm, Wait Nonce, SCPhs2 Strt, Wait
@@ -550,7 +542,7 @@ static const uint8_t smp_peripheral_entry_map[][SMP_STATE_MAX] = {
0x81, 0x81, 0, 0},
/* ENC_INFO */
{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 3, 0},
- /* CENTRAL_ID */
+ /* MASTER_ID */
{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, 0},
/* ID_INFO */
{0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 4, 0},
@@ -622,7 +614,7 @@ static const uint8_t smp_peripheral_entry_map[][SMP_STATE_MAX] = {
{3, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0},
};
-static const uint8_t smp_peripheral_idle_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_idle_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* L2C_CONN */
{SMP_SEND_APP_CBACK, SMP_SM_NO_ACTION, SMP_STATE_WAIT_APP_RSP},
@@ -632,8 +624,8 @@ static const uint8_t smp_peripheral_idle_table[][SMP_SM_NUM_COLS] = {
{SMP_CREATE_PRIVATE_KEY, SMP_SM_NO_ACTION,
SMP_STATE_CREATE_LOCAL_SEC_CONN_OOB_DATA}};
-static const uint8_t
- smp_peripheral_wait_for_app_response_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_wait_for_app_response_table[][SMP_SM_NUM_COLS] =
+ {
/* Event Action Next State */
/* IO_RSP */
{SMP_PROC_IO_RSP, SMP_SM_NO_ACTION, SMP_STATE_PAIR_REQ_RSP},
@@ -645,7 +637,7 @@ static const uint8_t
{SMP_PROC_SL_KEY, SMP_SM_NO_ACTION, SMP_STATE_WAIT_APP_RSP},
/* CONFIRM */
{SMP_PROC_CONFIRM, SMP_SM_NO_ACTION, SMP_STATE_CONFIRM},
- /* DHKey Check from central is received before phase 1 is completed -
+ /* DHKey Check from master is received before phase 1 is completed -
race */
/* PAIR_DHKEY_CHCK */
{SMP_PROCESS_DHKEY_CHECK, SMP_SM_NO_ACTION, SMP_STATE_WAIT_APP_RSP},
@@ -670,7 +662,7 @@ static const uint8_t
{SMP_SEND_PAIR_RSP, SMP_SM_NO_ACTION, SMP_STATE_PAIR_REQ_RSP},
};
-static const uint8_t smp_peripheral_sec_request_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_sec_request_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* PAIR_REQ */
{SMP_PROC_PAIR_CMD, SMP_SM_NO_ACTION, SMP_STATE_PAIR_REQ_RSP},
@@ -678,8 +670,8 @@ static const uint8_t smp_peripheral_sec_request_table[][SMP_SM_NUM_COLS] = {
{SMP_ENC_CMPL, SMP_SM_NO_ACTION, SMP_STATE_PAIR_REQ_RSP},
};
-static const uint8_t
- smp_peripheral_pair_request_response_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_pair_request_response_table[][SMP_SM_NUM_COLS] =
+ {
/* Event Action Next State */
/* CONFIRM */
{SMP_PROC_CONFIRM, SMP_SM_NO_ACTION, SMP_STATE_CONFIRM},
@@ -695,14 +687,14 @@ static const uint8_t
{SMP_PROCESS_PAIR_PUBLIC_KEY, SMP_SM_NO_ACTION, SMP_STATE_PAIR_REQ_RSP},
};
-static const uint8_t smp_peripheral_wait_confirm_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_wait_confirm_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* CONFIRM */
{SMP_PROC_CONFIRM, SMP_SEND_CONFIRM, SMP_STATE_CONFIRM},
/* KEY_READY*/
{SMP_PROC_SL_KEY, SMP_SM_NO_ACTION, SMP_STATE_WAIT_CONFIRM}};
-static const uint8_t smp_peripheral_confirm_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_confirm_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* RAND */
{SMP_PROC_RAND, SMP_GENERATE_COMPARE, SMP_STATE_RAND},
@@ -711,14 +703,14 @@ static const uint8_t smp_peripheral_confirm_table[][SMP_SM_NUM_COLS] = {
/* KEY_READY*/
{SMP_PROC_SL_KEY, SMP_SM_NO_ACTION, SMP_STATE_CONFIRM}};
-static const uint8_t smp_peripheral_rand_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_rand_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* KEY_READY */
{SMP_PROC_COMPARE, SMP_SM_NO_ACTION, SMP_STATE_RAND}, /* compare match */
/* RAND */
{SMP_SEND_RAND, SMP_SM_NO_ACTION, SMP_STATE_ENCRYPTION_PENDING}};
-static const uint8_t smp_peripheral_public_key_exch_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_public_key_exch_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* LOC_PUBL_KEY_CRTD */
{SMP_WAIT_FOR_BOTH_PUBLIC_KEYS, SMP_SM_NO_ACTION,
@@ -730,32 +722,31 @@ static const uint8_t smp_peripheral_public_key_exch_table[][SMP_SM_NUM_COLS] = {
SMP_STATE_SEC_CONN_PHS1_START},
};
-static const uint8_t
- smp_peripheral_sec_conn_phs1_start_table[][SMP_SM_NUM_COLS] = {
- /* Event Action Next State */
- /* SC_DHKEY_CMPLT */
- {SMP_START_SEC_CONN_PHASE1, SMP_SM_NO_ACTION,
- SMP_STATE_SEC_CONN_PHS1_START},
- /* HAVE_LOC_NONCE */
- {SMP_PROCESS_LOCAL_NONCE, SMP_SM_NO_ACTION, SMP_STATE_WAIT_COMMITMENT},
- /* TK_REQ */
- {SMP_SEND_APP_CBACK, SMP_SM_NO_ACTION, SMP_STATE_WAIT_APP_RSP},
- /* SMP_MODEL_SEC_CONN_PASSKEY_DISP model, passkey is sent up to display,
- * it's
- * time to start */
- /* commitment calculation */
- /* KEY_READY */
- {SMP_START_PASSKEY_VERIFICATION, SMP_SM_NO_ACTION,
- SMP_STATE_SEC_CONN_PHS1_START},
- /* PAIR_KEYPR_NOTIF */
- {SMP_PROCESS_KEYPRESS_NOTIFICATION, SMP_SEND_APP_CBACK,
- SMP_STATE_SEC_CONN_PHS1_START},
- /*COMMIT*/
- {SMP_PROCESS_PAIRING_COMMITMENT, SMP_SM_NO_ACTION,
- SMP_STATE_SEC_CONN_PHS1_START},
+static const uint8_t smp_slave_sec_conn_phs1_start_table[][SMP_SM_NUM_COLS] = {
+ /* Event Action Next State */
+ /* SC_DHKEY_CMPLT */
+ {SMP_START_SEC_CONN_PHASE1, SMP_SM_NO_ACTION,
+ SMP_STATE_SEC_CONN_PHS1_START},
+ /* HAVE_LOC_NONCE */
+ {SMP_PROCESS_LOCAL_NONCE, SMP_SM_NO_ACTION, SMP_STATE_WAIT_COMMITMENT},
+ /* TK_REQ */
+ {SMP_SEND_APP_CBACK, SMP_SM_NO_ACTION, SMP_STATE_WAIT_APP_RSP},
+ /* SMP_MODEL_SEC_CONN_PASSKEY_DISP model, passkey is sent up to display,
+ * it's
+ * time to start */
+ /* commitment calculation */
+ /* KEY_READY */
+ {SMP_START_PASSKEY_VERIFICATION, SMP_SM_NO_ACTION,
+ SMP_STATE_SEC_CONN_PHS1_START},
+ /* PAIR_KEYPR_NOTIF */
+ {SMP_PROCESS_KEYPRESS_NOTIFICATION, SMP_SEND_APP_CBACK,
+ SMP_STATE_SEC_CONN_PHS1_START},
+ /*COMMIT*/
+ {SMP_PROCESS_PAIRING_COMMITMENT, SMP_SM_NO_ACTION,
+ SMP_STATE_SEC_CONN_PHS1_START},
};
-static const uint8_t smp_peripheral_wait_commitment_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_wait_commitment_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* PAIR_COMMITM */
{SMP_PROCESS_PAIRING_COMMITMENT, SMP_SEND_COMMITMENT, SMP_STATE_WAIT_NONCE},
@@ -764,7 +755,7 @@ static const uint8_t smp_peripheral_wait_commitment_table[][SMP_SM_NUM_COLS] = {
SMP_STATE_WAIT_COMMITMENT},
};
-static const uint8_t smp_peripheral_wait_nonce_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_wait_nonce_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* peer nonce is received */
/* RAND */
@@ -778,31 +769,28 @@ static const uint8_t smp_peripheral_wait_nonce_table[][SMP_SM_NUM_COLS] = {
{SMP_SEND_APP_CBACK, SMP_SM_NO_ACTION, SMP_STATE_WAIT_APP_RSP},
};
-static const uint8_t
- smp_peripheral_sec_conn_phs2_start_table[][SMP_SM_NUM_COLS] = {
- /* Event Action Next State */
- /* SC_PHASE1_CMPLT */
- {SMP_CALCULATE_LOCAL_DHKEY_CHECK, SMP_PH2_DHKEY_CHECKS_ARE_PRESENT,
- SMP_STATE_WAIT_DHK_CHECK},
- /* DHKey Check from central is received before peripheral DHKey
- * calculation is completed - race */
- /* PAIR_DHKEY_CHCK */
- {SMP_PROCESS_DHKEY_CHECK, SMP_SM_NO_ACTION,
- SMP_STATE_SEC_CONN_PHS2_START},
+static const uint8_t smp_slave_sec_conn_phs2_start_table[][SMP_SM_NUM_COLS] = {
+ /* Event Action Next State */
+ /* SC_PHASE1_CMPLT */
+ {SMP_CALCULATE_LOCAL_DHKEY_CHECK, SMP_PH2_DHKEY_CHECKS_ARE_PRESENT,
+ SMP_STATE_WAIT_DHK_CHECK},
+ /* DHKey Check from master is received before slave DHKey calculation is
+ * completed - race */
+ /* PAIR_DHKEY_CHCK */
+ {SMP_PROCESS_DHKEY_CHECK, SMP_SM_NO_ACTION, SMP_STATE_SEC_CONN_PHS2_START},
};
-static const uint8_t smp_peripheral_wait_dhk_check_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_wait_dhk_check_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* PAIR_DHKEY_CHCK */
{SMP_PROCESS_DHKEY_CHECK, SMP_CALCULATE_PEER_DHKEY_CHECK,
SMP_STATE_DHK_CHECK},
- /* DHKey Check from central was received before peripheral came to this
- state */
+ /* DHKey Check from master was received before slave came to this state */
/* SC_2_DHCK_CHKS_PRES */
{SMP_CALCULATE_PEER_DHKEY_CHECK, SMP_SM_NO_ACTION, SMP_STATE_DHK_CHECK},
};
-static const uint8_t smp_peripheral_dhk_check_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_dhk_check_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* locally calculated peer dhkey check is ready -> compare it withs DHKey
@@ -812,7 +800,7 @@ static const uint8_t smp_peripheral_dhk_check_table[][SMP_SM_NUM_COLS] = {
/* SC_KEY_READY */
{SMP_MATCH_DHKEY_CHECKS, SMP_SM_NO_ACTION, SMP_STATE_DHK_CHECK},
- /* dhkey checks match -> send local dhkey check to central, go to wait for
+ /* dhkey checks match -> send local dhkey check to master, go to wait for
* HCI LE
*/
/* Long Term Key Request Event */
@@ -820,7 +808,7 @@ static const uint8_t smp_peripheral_dhk_check_table[][SMP_SM_NUM_COLS] = {
{SMP_SEND_DHKEY_CHECK, SMP_SM_NO_ACTION, SMP_STATE_ENCRYPTION_PENDING},
};
-static const uint8_t smp_peripheral_enc_pending_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_enc_pending_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* ENC_REQ */
{SMP_GENERATE_STK, SMP_SM_NO_ACTION, SMP_STATE_ENCRYPTION_PENDING},
@@ -832,7 +820,7 @@ static const uint8_t smp_peripheral_enc_pending_table[][SMP_SM_NUM_COLS] = {
{SMP_CHECK_AUTH_REQ, SMP_SM_NO_ACTION, SMP_STATE_ENCRYPTION_PENDING},
/* BOND_REQ */
{SMP_KEY_DISTRIBUTE, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING}};
-static const uint8_t smp_peripheral_bond_pending_table[][SMP_SM_NUM_COLS] = {
+static const uint8_t smp_slave_bond_pending_table[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* LTK ready */
@@ -846,15 +834,15 @@ static const uint8_t smp_peripheral_bond_pending_table[][SMP_SM_NUM_COLS] = {
{SMP_PROC_ENC_INFO, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING},
/* ID_INFO */
{SMP_PROC_ID_INFO, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING},
- /* CENTRAL_ID*/
- {SMP_PROC_CENTRAL_ID, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING},
+ /* MASTER_ID*/
+ {SMP_PROC_MASTER_ID, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING},
/* ID_ADDR */
{SMP_PROC_ID_ADDR, SMP_SM_NO_ACTION, SMP_STATE_BOND_PENDING}
};
static const uint8_t
- smp_peripheral_create_local_sec_conn_oob_data[][SMP_SM_NUM_COLS] = {
+ smp_slave_create_local_sec_conn_oob_data[][SMP_SM_NUM_COLS] = {
/* Event Action Next State */
/* LOC_PUBL_KEY_CRTD */
{SMP_SET_LOCAL_OOB_KEYS, SMP_SM_NO_ACTION,
@@ -864,65 +852,62 @@ static const uint8_t
static const tSMP_SM_TBL smp_state_table[][2] = {
/* SMP_STATE_IDLE */
- {smp_central_idle_table, smp_peripheral_idle_table},
+ {smp_master_idle_table, smp_slave_idle_table},
/* SMP_STATE_WAIT_APP_RSP */
- {smp_central_wait_for_app_response_table,
- smp_peripheral_wait_for_app_response_table},
+ {smp_master_wait_for_app_response_table,
+ smp_slave_wait_for_app_response_table},
/* SMP_STATE_SEC_REQ_PENDING */
- {NULL, smp_peripheral_sec_request_table},
+ {NULL, smp_slave_sec_request_table},
/* SMP_STATE_PAIR_REQ_RSP */
- {smp_central_pair_request_response_table,
- smp_peripheral_pair_request_response_table},
+ {smp_master_pair_request_response_table,
+ smp_slave_pair_request_response_table},
/* SMP_STATE_WAIT_CONFIRM */
- {smp_central_wait_for_confirm_table, smp_peripheral_wait_confirm_table},
+ {smp_master_wait_for_confirm_table, smp_slave_wait_confirm_table},
/* SMP_STATE_CONFIRM */
- {smp_central_confirm_table, smp_peripheral_confirm_table},
+ {smp_master_confirm_table, smp_slave_confirm_table},
/* SMP_STATE_RAND */
- {smp_central_rand_table, smp_peripheral_rand_table},
+ {smp_master_rand_table, smp_slave_rand_table},
/* SMP_STATE_PUBLIC_KEY_EXCH */
- {smp_central_public_key_exchange_table,
- smp_peripheral_public_key_exch_table},
+ {smp_master_public_key_exchange_table, smp_slave_public_key_exch_table},
/* SMP_STATE_SEC_CONN_PHS1_START */
- {smp_central_sec_conn_phs1_start_table,
- smp_peripheral_sec_conn_phs1_start_table},
+ {smp_master_sec_conn_phs1_start_table, smp_slave_sec_conn_phs1_start_table},
/* SMP_STATE_WAIT_COMMITMENT */
- {smp_central_wait_commitment_table, smp_peripheral_wait_commitment_table},
+ {smp_master_wait_commitment_table, smp_slave_wait_commitment_table},
/* SMP_STATE_WAIT_NONCE */
- {smp_central_wait_nonce_table, smp_peripheral_wait_nonce_table},
+ {smp_master_wait_nonce_table, smp_slave_wait_nonce_table},
/* SMP_STATE_SEC_CONN_PHS2_START */
- {smp_central_sec_conn_phs2_start_table,
- smp_peripheral_sec_conn_phs2_start_table},
+ {smp_master_sec_conn_phs2_start_table, smp_slave_sec_conn_phs2_start_table},
/* SMP_STATE_WAIT_DHK_CHECK */
- {smp_central_wait_dhk_check_table, smp_peripheral_wait_dhk_check_table},
+ {smp_master_wait_dhk_check_table, smp_slave_wait_dhk_check_table},
/* SMP_STATE_DHK_CHECK */
- {smp_central_dhk_check_table, smp_peripheral_dhk_check_table},
+ {smp_master_dhk_check_table, smp_slave_dhk_check_table},
/* SMP_STATE_ENCRYPTION_PENDING */
- {smp_central_enc_pending_table, smp_peripheral_enc_pending_table},
+ {smp_master_enc_pending_table, smp_slave_enc_pending_table},
/* SMP_STATE_BOND_PENDING */
- {smp_central_bond_pending_table, smp_peripheral_bond_pending_table},
+ {smp_master_bond_pending_table, smp_slave_bond_pending_table},
/* SMP_STATE_CREATE_LOCAL_SEC_CONN_OOB_DATA */
- {smp_central_create_local_sec_conn_oob_data,
- smp_peripheral_create_local_sec_conn_oob_data}};
+ {smp_master_create_local_sec_conn_oob_data,
+ smp_slave_create_local_sec_conn_oob_data}};
typedef const uint8_t (*tSMP_ENTRY_TBL)[SMP_STATE_MAX];
-static const tSMP_ENTRY_TBL smp_entry_table[] = {smp_central_entry_map,
- smp_peripheral_entry_map};
+static const tSMP_ENTRY_TBL smp_entry_table[] = {smp_master_entry_map,
+ smp_slave_entry_map};
tSMP_CB smp_cb;
@@ -984,7 +969,7 @@ void smp_sm_event(tSMP_CB* p_cb, tSMP_EVENT event, tSMP_INT_DATA* p_data) {
}
SMP_TRACE_DEBUG("SMP Role: %s State: [%s (%d)], Event: [%s (%d)]",
- (p_cb->role == 0x01) ? "Peripheral" : "Central",
+ (p_cb->role == 0x01) ? "Slave" : "Master",
smp_get_state_name(p_cb->state), p_cb->state,
smp_get_event_name(event), event);
diff --git a/stack/smp/smp_utils.cc b/stack/smp/smp_utils.cc
index 54d4aeba4..b5da5ba7d 100644
--- a/stack/smp/smp_utils.cc
+++ b/stack/smp/smp_utils.cc
@@ -28,22 +28,21 @@
#include "bt_types.h"
#include "bt_utils.h"
#include "btm_ble_api.h"
+#include "btm_int.h"
+#include "common/metrics.h"
#include "device/include/controller.h"
#include "hcidefs.h"
#include "l2c_api.h"
-#include "osi/include/log.h"
+#include "l2c_int.h"
#include "osi/include/osi.h"
#include "smp_int.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/stack_metrics_logging.h"
#define SMP_PAIRING_REQ_SIZE 7
#define SMP_CONFIRM_CMD_SIZE (OCTET16_LEN + 1)
#define SMP_RAND_CMD_SIZE (OCTET16_LEN + 1)
#define SMP_INIT_CMD_SIZE (OCTET16_LEN + 1)
#define SMP_ENC_INFO_SIZE (OCTET16_LEN + 1)
-#define SMP_CENTRAL_ID_SIZE (BT_OCTET8_LEN + 2 + 1)
+#define SMP_MASTER_ID_SIZE (BT_OCTET8_LEN + 2 + 1)
#define SMP_ID_INFO_SIZE (OCTET16_LEN + 1)
#define SMP_ID_ADDR_SIZE (BD_ADDR_LEN + 1 + 1)
#define SMP_SIGN_INFO_SIZE (OCTET16_LEN + 1)
@@ -65,7 +64,7 @@ static const uint8_t smp_cmd_size_per_spec[] = {
SMP_RAND_CMD_SIZE, /* 0x04: pairing random */
SMP_PAIR_FAIL_SIZE, /* 0x05: pairing failed */
SMP_ENC_INFO_SIZE, /* 0x06: encryption information */
- SMP_CENTRAL_ID_SIZE, /* 0x07: central identification */
+ SMP_MASTER_ID_SIZE, /* 0x07: master identification */
SMP_ID_INFO_SIZE, /* 0x08: identity information */
SMP_ID_ADDR_SIZE, /* 0x09: identity address information */
SMP_SIGN_INFO_SIZE, /* 0x0A: signing information */
@@ -92,7 +91,7 @@ static const tSMP_CMD_LEN_VALID smp_cmd_len_is_valid[] = {
smp_command_has_valid_fixed_length, /* 0x04: pairing random */
smp_command_has_valid_fixed_length, /* 0x05: pairing failed */
smp_command_has_valid_fixed_length, /* 0x06: encryption information */
- smp_command_has_valid_fixed_length, /* 0x07: central identification */
+ smp_command_has_valid_fixed_length, /* 0x07: master identification */
smp_command_has_valid_fixed_length, /* 0x08: identity information */
smp_command_has_valid_fixed_length, /* 0x09: identity address information */
smp_command_has_valid_fixed_length, /* 0x0A: signing information */
@@ -119,7 +118,7 @@ static const tSMP_CMD_PARAM_RANGES_VALID smp_cmd_param_ranges_are_valid[] = {
smp_parameter_unconditionally_valid, /* 0x04: pairing random */
smp_parameter_unconditionally_valid, /* 0x05: pairing failed */
smp_parameter_unconditionally_valid, /* 0x06: encryption information */
- smp_parameter_unconditionally_valid, /* 0x07: central identification */
+ smp_parameter_unconditionally_valid, /* 0x07: master identification */
smp_parameter_unconditionally_valid, /* 0x08: identity information */
smp_parameter_unconditionally_valid, /* 0x09: identity address
information */
@@ -149,8 +148,8 @@ static BT_HDR* smp_build_security_request(UNUSED_ATTR uint8_t cmd_code,
tSMP_CB* p_cb);
static BT_HDR* smp_build_signing_info_cmd(UNUSED_ATTR uint8_t cmd_code,
tSMP_CB* p_cb);
-static BT_HDR* smp_build_central_id_cmd(UNUSED_ATTR uint8_t cmd_code,
- tSMP_CB* p_cb);
+static BT_HDR* smp_build_master_id_cmd(UNUSED_ATTR uint8_t cmd_code,
+ tSMP_CB* p_cb);
static BT_HDR* smp_build_id_addr_cmd(UNUSED_ATTR uint8_t cmd_code,
tSMP_CB* p_cb);
static BT_HDR* smp_build_pair_public_key_cmd(UNUSED_ATTR uint8_t cmd_code,
@@ -163,14 +162,13 @@ static BT_HDR* smp_build_pairing_keypress_notification_cmd(
UNUSED_ATTR uint8_t cmd_code, tSMP_CB* p_cb);
static const tSMP_CMD_ACT smp_cmd_build_act[] = {
- NULL,
- smp_build_pairing_cmd, /* 0x01: pairing request */
+ NULL, smp_build_pairing_cmd, /* 0x01: pairing request */
smp_build_pairing_cmd, /* 0x02: pairing response */
smp_build_confirm_cmd, /* 0x03: pairing confirm */
smp_build_rand_cmd, /* 0x04: pairing random */
smp_build_pairing_fail, /* 0x05: pairing failure */
smp_build_encrypt_info_cmd, /* 0x06: encryption information */
- smp_build_central_id_cmd, /* 0x07: central identification */
+ smp_build_master_id_cmd, /* 0x07: master identification */
smp_build_identity_info_cmd, /* 0x08: identity information */
smp_build_id_addr_cmd, /* 0x09: identity address information */
smp_build_signing_info_cmd, /* 0x0A: signing information */
@@ -182,8 +180,8 @@ static const tSMP_CMD_ACT smp_cmd_build_act[] = {
smp_build_pairing_commitment_cmd /* 0x0F: pairing commitment */
};
-static const tSMP_ASSO_MODEL
- smp_association_table[2][SMP_IO_CAP_MAX][SMP_IO_CAP_MAX] = {
+static const uint8_t smp_association_table[2][SMP_IO_CAP_MAX][SMP_IO_CAP_MAX] =
+ {
/* display only */ /* Display Yes/No */ /* keyboard only */
/* No Input/Output */ /* keyboard display */
@@ -233,7 +231,7 @@ static const tSMP_ASSO_MODEL
{SMP_MODEL_PASSKEY, SMP_MODEL_PASSKEY, SMP_MODEL_KEY_NOTIF,
SMP_MODEL_ENCRYPTION_ONLY, SMP_MODEL_PASSKEY}}};
-static const tSMP_ASSO_MODEL
+static const uint8_t
smp_association_table_sc[2][SMP_IO_CAP_MAX][SMP_IO_CAP_MAX] = {
/* display only */ /* Display Yes/No */ /* keyboard only */
/* No InputOutput */ /* keyboard display */
@@ -322,7 +320,8 @@ void smp_log_metrics(const RawAddress& bd_addr, bool is_outgoing,
android::bluetooth::DirectionEnum direction =
is_outgoing ? android::bluetooth::DirectionEnum::DIRECTION_OUTGOING
: android::bluetooth::DirectionEnum::DIRECTION_INCOMING;
- log_smp_pairing_event(bd_addr, cmd, direction, failure_reason);
+ bluetooth::common::LogSmpPairingEvent(bd_addr, cmd, direction,
+ failure_reason);
}
/*******************************************************************************
@@ -341,28 +340,18 @@ bool smp_send_msg_to_L2CAP(const RawAddress& rem_bda, BT_HDR* p_toL2CAP) {
}
SMP_TRACE_EVENT("%s", __func__);
+ smp_cb.total_tx_unacked += 1;
smp_log_metrics(rem_bda, true /* outgoing */,
p_toL2CAP->data + p_toL2CAP->offset, p_toL2CAP->len);
l2cap_ret = L2CA_SendFixedChnlData(fixed_cid, rem_bda, p_toL2CAP);
if (l2cap_ret == L2CAP_DW_FAILED) {
+ smp_cb.total_tx_unacked -= 1;
SMP_TRACE_ERROR("SMP failed to pass msg to L2CAP");
return false;
- } else {
- tSMP_CB* p_cb = &smp_cb;
-
- if (p_cb->wait_for_authorization_complete) {
- tSMP_INT_DATA smp_int_data;
- smp_int_data.status = SMP_SUCCESS;
- if (fixed_cid == L2CAP_SMP_CID) {
- smp_sm_event(p_cb, SMP_AUTH_CMPL_EVT, &smp_int_data);
- } else {
- smp_br_state_machine_event(p_cb, SMP_BR_AUTH_CMPL_EVT, &smp_int_data);
- }
- }
+ } else
return true;
- }
}
/*******************************************************************************
@@ -376,9 +365,8 @@ bool smp_send_cmd(uint8_t cmd_code, tSMP_CB* p_cb) {
BT_HDR* p_buf;
bool sent = false;
- LOG_DEBUG("Sending SMP command:%s[0x%x] pairing_bda=%s",
- smp_opcode_text(static_cast<tSMP_OPCODE>(cmd_code)).c_str(),
- cmd_code, PRIVATE_ADDRESS(p_cb->pairing_bda));
+ SMP_TRACE_EVENT("%s: on l2cap cmd_code=0x%x, pairing_bda=%s", __func__,
+ cmd_code, p_cb->pairing_bda.ToString().c_str());
if (cmd_code <= (SMP_OPCODE_MAX + 1 /* for SMP_OPCODE_PAIR_COMMITM */) &&
smp_cmd_build_act[cmd_code] != NULL) {
@@ -557,26 +545,26 @@ static BT_HDR* smp_build_encrypt_info_cmd(UNUSED_ATTR uint8_t cmd_code,
/*******************************************************************************
*
- * Function smp_build_central_id_cmd
+ * Function smp_build_master_id_cmd
*
* Description Build security information command.
*
******************************************************************************/
-static BT_HDR* smp_build_central_id_cmd(UNUSED_ATTR uint8_t cmd_code,
- tSMP_CB* p_cb) {
+static BT_HDR* smp_build_master_id_cmd(UNUSED_ATTR uint8_t cmd_code,
+ tSMP_CB* p_cb) {
uint8_t* p;
- BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR) + SMP_CENTRAL_ID_SIZE +
+ BT_HDR* p_buf = (BT_HDR*)osi_malloc(sizeof(BT_HDR) + SMP_MASTER_ID_SIZE +
L2CAP_MIN_OFFSET);
SMP_TRACE_EVENT("%s", __func__);
p = (uint8_t*)(p_buf + 1) + L2CAP_MIN_OFFSET;
- UINT8_TO_STREAM(p, SMP_OPCODE_CENTRAL_ID);
+ UINT8_TO_STREAM(p, SMP_OPCODE_MASTER_ID);
UINT16_TO_STREAM(p, p_cb->ediv);
ARRAY_TO_STREAM(p, p_cb->enc_rand, BT_OCTET8_LEN);
p_buf->offset = L2CAP_MIN_OFFSET;
- p_buf->len = SMP_CENTRAL_ID_SIZE;
+ p_buf->len = SMP_MASTER_ID_SIZE;
return p_buf;
}
@@ -943,20 +931,21 @@ void smp_proc_pairing_cmpl(tSMP_CB* p_cb) {
tSMP_EVT_DATA evt_data = {0};
tSMP_CALLBACK* p_callback = p_cb->p_callback;
+ SMP_TRACE_DEBUG("%s: pairing_bda=%s", __func__,
+ p_cb->pairing_bda.ToString().c_str());
+
evt_data.cmplt.reason = p_cb->status;
evt_data.cmplt.smp_over_br = p_cb->smp_over_br;
- LOG_DEBUG(
- "Pairing process has completed to remote:%s reason:0x%0x sec_level=0x%0x",
- PRIVATE_ADDRESS(p_cb->pairing_bda), evt_data.cmplt.reason,
- evt_data.cmplt.sec_level);
-
if (p_cb->status == SMP_SUCCESS) evt_data.cmplt.sec_level = p_cb->sec_level;
evt_data.cmplt.is_pair_cancel = false;
if (p_cb->is_pair_cancel) evt_data.cmplt.is_pair_cancel = true;
+ SMP_TRACE_DEBUG("send SMP_COMPLT_EVT reason=0x%0x sec_level=0x%0x",
+ evt_data.cmplt.reason, evt_data.cmplt.sec_level);
+
RawAddress pairing_bda = p_cb->pairing_bda;
smp_reset_control_value(p_cb);
@@ -1125,11 +1114,11 @@ bool smp_pairing_request_response_parameters_are_valid(tSMP_CB* p_cb) {
*
******************************************************************************/
bool smp_pairing_keypress_notification_is_valid(tSMP_CB* p_cb) {
- tSMP_SC_KEY_TYPE keypress_notification = p_cb->peer_keypress_notification;
+ tBTM_SP_KEY_TYPE keypress_notification = p_cb->peer_keypress_notification;
SMP_TRACE_DEBUG("%s for cmd code 0x%02x", __func__, p_cb->rcvd_cmd_code);
- if (keypress_notification >= SMP_SC_KEY_OUT_OF_RANGE) {
+ if (keypress_notification >= BTM_SP_KEY_OUT_OF_RANGE) {
SMP_TRACE_WARNING(
"Rcvd from the peer cmd 0x%02x with Pairing Keypress "
"Notification value (0x%02x) out of range).",
@@ -1268,7 +1257,7 @@ tSMP_ASSO_MODEL smp_select_legacy_association_model(tSMP_CB* p_cb) {
/* otherwise use IO capability to select association model */
if (p_cb->peer_io_caps < SMP_IO_CAP_MAX &&
p_cb->local_io_capability < SMP_IO_CAP_MAX) {
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ if (p_cb->role == HCI_ROLE_MASTER) {
model = smp_association_table[p_cb->role][p_cb->peer_io_caps]
[p_cb->local_io_capability];
} else {
@@ -1306,7 +1295,7 @@ tSMP_ASSO_MODEL smp_select_association_model_secure_connections(tSMP_CB* p_cb) {
/* otherwise use IO capability to select association model */
if (p_cb->peer_io_caps < SMP_IO_CAP_MAX &&
p_cb->local_io_capability < SMP_IO_CAP_MAX) {
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ if (p_cb->role == HCI_ROLE_MASTER) {
model = smp_association_table_sc[p_cb->role][p_cb->peer_io_caps]
[p_cb->local_io_capability];
} else {
@@ -1319,6 +1308,24 @@ tSMP_ASSO_MODEL smp_select_association_model_secure_connections(tSMP_CB* p_cb) {
}
/*******************************************************************************
+ * Function smp_reverse_array
+ *
+ * Description This function reverses array bytes
+ *
+ ******************************************************************************/
+void smp_reverse_array(uint8_t* arr, uint8_t len) {
+ uint8_t i = 0, tmp;
+
+ SMP_TRACE_DEBUG("smp_reverse_array");
+
+ for (i = 0; i < len / 2; i++) {
+ tmp = arr[i];
+ arr[i] = arr[len - 1 - i];
+ arr[len - 1 - i] = tmp;
+ }
+}
+
+/*******************************************************************************
* Function smp_calculate_random_input
*
* Description This function returns random input value to be used in
@@ -1386,7 +1393,7 @@ void smp_collect_peer_io_capabilities(uint8_t* iocap, tSMP_CB* p_cb) {
*
******************************************************************************/
void smp_collect_local_ble_address(uint8_t* le_addr, tSMP_CB* p_cb) {
- tBLE_ADDR_TYPE addr_type = BLE_ADDR_PUBLIC;
+ tBLE_ADDR_TYPE addr_type = 0;
RawAddress bda;
uint8_t* p = le_addr;
@@ -1408,7 +1415,7 @@ void smp_collect_local_ble_address(uint8_t* le_addr, tSMP_CB* p_cb) {
*
******************************************************************************/
void smp_collect_peer_ble_address(uint8_t* le_addr, tSMP_CB* p_cb) {
- tBLE_ADDR_TYPE addr_type = BLE_ADDR_PUBLIC;
+ tBLE_ADDR_TYPE addr_type = 0;
RawAddress bda;
uint8_t* p = le_addr;
@@ -1493,7 +1500,7 @@ void smp_calculate_f5_mackey_and_long_term_key(tSMP_CB* p_cb) {
SMP_TRACE_DEBUG("%s", __func__);
- if (p_cb->role == HCI_ROLE_CENTRAL) {
+ if (p_cb->role == HCI_ROLE_MASTER) {
smp_collect_local_ble_address(a, p_cb);
smp_collect_peer_ble_address(b, p_cb);
na = p_cb->rand;
diff --git a/stack/srvc/srvc_dis.cc b/stack/srvc/srvc_dis.cc
index fd453a93c..3ca2e3383 100644
--- a/stack/srvc/srvc_dis.cc
+++ b/stack/srvc/srvc_dis.cc
@@ -197,7 +197,7 @@ static void dis_gatt_c_read_dis_value_cmpl(uint16_t conn_id) {
srvc_eng_release_channel(conn_id);
if (dis_cb.p_read_dis_cback && p_clcb) {
- LOG_INFO("%s conn_id:%d attr_mask = 0x%04x", __func__, conn_id,
+ LOG_INFO(LOG_TAG, "%s conn_id:%d attr_mask = 0x%04x", __func__, conn_id,
p_clcb->dis_value.attr_mask);
(*dis_cb.p_read_dis_cback)(p_clcb->bda, &p_clcb->dis_value);
diff --git a/stack/srvc/srvc_eng.cc b/stack/srvc/srvc_eng.cc
index add145e98..564a2eac1 100644
--- a/stack/srvc/srvc_eng.cc
+++ b/stack/srvc/srvc_eng.cc
@@ -244,7 +244,7 @@ uint8_t srvc_eng_process_write_req(uint8_t clcb_idx, tGATT_WRITE_REQ* p_data,
static void srvc_eng_s_request_cback(uint16_t conn_id, uint32_t trans_id,
tGATTS_REQ_TYPE type,
tGATTS_DATA* p_data) {
- tGATT_STATUS status = GATT_INVALID_PDU;
+ uint8_t status = GATT_INVALID_PDU;
tGATTS_RSP rsp_msg;
uint8_t act = SRVC_ACT_IGNORE;
uint8_t clcb_idx = srvc_eng_find_clcb_idx_by_conn_id(conn_id);
@@ -329,7 +329,8 @@ static void srvc_eng_connect_cback(UNUSED_ATTR tGATT_IF gatt_if,
bool connected, tGATT_DISCONN_REASON reason,
UNUSED_ATTR tBT_TRANSPORT transport) {
VLOG(1) << __func__ << ": from " << bda
- << StringPrintf(" connected:%d conn_id=%d", connected, conn_id);
+ << StringPrintf(" connected:%d conn_id=%d reason = 0x%04x", connected,
+ conn_id, reason);
if (connected) {
if (srvc_eng_clcb_alloc(conn_id, bda) == NULL) {
@@ -401,8 +402,7 @@ tGATT_STATUS srvc_eng_init(void) {
/* Create a GATT profile service */
bluetooth::Uuid app_uuid =
bluetooth::Uuid::From16Bit(UUID_SERVCLASS_DEVICE_INFO);
- srvc_eng_cb.gatt_if =
- GATT_Register(app_uuid, "GattServiceEngine", &srvc_gatt_cback, false);
+ srvc_eng_cb.gatt_if = GATT_Register(app_uuid, &srvc_gatt_cback);
GATT_StartIf(srvc_eng_cb.gatt_if);
VLOG(1) << "Srvc_Init: gatt_if=" << +srvc_eng_cb.gatt_if;
diff --git a/stack/test/ble_advertiser_test.cc b/stack/test/ble_advertiser_test.cc
index adf6e45ef..98142ddc0 100644
--- a/stack/test/ble_advertiser_test.cc
+++ b/stack/test/ble_advertiser_test.cc
@@ -26,7 +26,6 @@
using ::testing::Args;
using ::testing::Contains;
-using ::testing::DoAll;
using ::testing::ElementsAreArray;
using ::testing::Exactly;
using ::testing::Field;
@@ -45,6 +44,9 @@ const int num_adv_instances = 16;
* whole stack. They will be removed, or changed into mocks one by one in the
* future, as the refactoring progresses */
bool BTM_BleLocalPrivacyEnabled() { return true; }
+uint16_t BTM_ReadDiscoverability(uint16_t* p_window, uint16_t* p_interval) {
+ return true;
+}
void btm_acl_update_conn_addr(uint16_t conn_handle, const RawAddress& address) {
}
void btm_gen_resolvable_private_addr(
@@ -1111,4 +1113,4 @@ TEST_F(BleAdvertisingManagerTest, test_recompute_timeout) {
testRecomputeTimeout1();
testRecomputeTimeout2();
testRecomputeTimeout3();
-}
+} \ No newline at end of file
diff --git a/stack/test/btm/peer_packet_types_test.cc b/stack/test/btm/peer_packet_types_test.cc
deleted file mode 100644
index 905a6ea54..000000000
--- a/stack/test/btm/peer_packet_types_test.cc
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- *
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-#include <map>
-
-#include "stack/acl/peer_packet_types.h"
-#include "stack/include/bt_types.h"
-
-namespace {
-
-using testing::_;
-using testing::DoAll;
-using testing::NotNull;
-using testing::Pointee;
-using testing::Return;
-using testing::SaveArg;
-using testing::SaveArgPointee;
-using testing::StrEq;
-using testing::StrictMock;
-using testing::Test;
-
-class PeerPacketTest : public Test {
- public:
- protected:
- void SetUp() override {}
- void TearDown() override {}
-};
-
-TEST_F(PeerPacketTest, all_ones) {
- const BD_FEATURES bd_features = {0xff, 0xff, 0xff, 0xff,
- 0xff, 0xff, 0xff, 0xff};
- PeerPacketTypes peer_packet_types(bd_features);
- ASSERT_EQ(peer_packet_types.acl.supported, 0xcc00);
- ASSERT_EQ(peer_packet_types.acl.unsupported, 0x0);
-}
-
-TEST_F(PeerPacketTest, 3SLOT_DH3_DM3) {
- const BD_FEATURES bd_features = {0x01, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00};
- PeerPacketTypes peer_packet_types(bd_features);
- ASSERT_EQ(peer_packet_types.acl.supported, 0x0c00);
- ASSERT_EQ(peer_packet_types.acl.unsupported, 0x3306);
-}
-
-TEST_F(PeerPacketTest, 5SLOT_DH5_DM5) {
- const BD_FEATURES bd_features = {0x02, 0x00, 0x00, 0x00,
- 0x00, 0x00, 0x00, 0x00};
- PeerPacketTypes peer_packet_types(bd_features);
- ASSERT_EQ(peer_packet_types.acl.supported, 0xc000);
- ASSERT_EQ(peer_packet_types.acl.unsupported, 0x3306);
-}
-
-TEST_F(PeerPacketTest, 2Mb_support) {
- const BD_FEATURES bd_features = {0x00, 0x00, 0x00, 0x02,
- 0x00, 0x00, 0x00, 0x00};
- PeerPacketTypes peer_packet_types(bd_features);
- ASSERT_EQ(peer_packet_types.acl.supported, 0x0000);
- ASSERT_EQ(peer_packet_types.acl.unsupported, 0x3304);
-}
-
-TEST_F(PeerPacketTest, 3Mb_support) {
- const BD_FEATURES bd_features = {0x00, 0x00, 0x00, 0x04,
- 0x00, 0x00, 0x00, 0x00};
- PeerPacketTypes peer_packet_types(bd_features);
- ASSERT_EQ(peer_packet_types.acl.supported, 0x0000);
- ASSERT_EQ(peer_packet_types.acl.unsupported, 0x3302);
-}
-
-} // namespace
diff --git a/stack/test/btm/stack_btm_test.cc b/stack/test/btm/stack_btm_test.cc
deleted file mode 100644
index f2880c676..000000000
--- a/stack/test/btm/stack_btm_test.cc
+++ /dev/null
@@ -1,185 +0,0 @@
-/*
- *
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- */
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-#include <map>
-
-#include "btif/include/btif_hh.h"
-#include "hci/include/hci_layer.h"
-#include "hci/include/hci_packet_factory.h"
-#include "hci/include/packet_fragmenter.h"
-#include "internal_include/stack_config.h"
-#include "osi/include/osi.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/acl_hci_link_interface.h"
-#include "stack/include/btm_client_interface.h"
-#include "stack/l2cap/l2c_int.h"
-#include "test/mock/mock_hcic_hcicmds.h"
-#include "types/raw_address.h"
-
-namespace mock = test::mock::hcic_hcicmds;
-
-extern tBTM_CB btm_cb;
-
-uint8_t appl_trace_level = BT_TRACE_LEVEL_VERBOSE;
-btif_hh_cb_t btif_hh_cb;
-tL2C_CB l2cb;
-
-const hci_packet_factory_t* hci_packet_factory_get_interface() {
- return nullptr;
-}
-const hci_t* hci_layer_get_interface() { return nullptr; }
-
-void LogMsg(uint32_t trace_set_mask, const char* fmt_str, ...) {}
-
-const std::string kSmpOptions("mock smp options");
-
-bool get_trace_config_enabled(void) { return false; }
-bool get_pts_avrcp_test(void) { return false; }
-bool get_pts_secure_only_mode(void) { return false; }
-bool get_pts_conn_updates_disabled(void) { return false; }
-bool get_pts_crosskey_sdp_disable(void) { return false; }
-const std::string* get_pts_smp_options(void) { return &kSmpOptions; }
-int get_pts_smp_failure_case(void) { return 123; }
-config_t* get_all(void) { return nullptr; }
-const packet_fragmenter_t* packet_fragmenter_get_interface() { return nullptr; }
-
-stack_config_t mock_stack_config{
- .get_trace_config_enabled = get_trace_config_enabled,
- .get_pts_avrcp_test = get_pts_avrcp_test,
- .get_pts_secure_only_mode = get_pts_secure_only_mode,
- .get_pts_conn_updates_disabled = get_pts_conn_updates_disabled,
- .get_pts_crosskey_sdp_disable = get_pts_crosskey_sdp_disable,
- .get_pts_smp_options = get_pts_smp_options,
- .get_pts_smp_failure_case = get_pts_smp_failure_case,
- .get_all = get_all,
-};
-const stack_config_t* stack_config_get_interface(void) {
- return &mock_stack_config;
-}
-
-std::map<std::string, int> mock_function_count_map;
-
-extern bool MOCK_bluetooth_shim_is_gd_acl_enabled_;
-
-namespace {
-
-using testing::_;
-using testing::DoAll;
-using testing::NotNull;
-using testing::Pointee;
-using testing::Return;
-using testing::SaveArg;
-using testing::SaveArgPointee;
-using testing::StrEq;
-using testing::StrictMock;
-using testing::Test;
-
-class StackBtmTest : public Test {
- public:
- protected:
- void SetUp() override { mock_function_count_map.clear(); }
- void TearDown() override {}
-};
-
-TEST_F(StackBtmTest, GlobalLifecycle) {
- get_btm_client_interface().lifecycle.btm_init();
- get_btm_client_interface().lifecycle.btm_free();
-}
-
-TEST_F(StackBtmTest, DynamicLifecycle) {
- auto* btm = new tBTM_CB();
- delete btm;
-}
-
-TEST_F(StackBtmTest, InformClientOnConnectionSuccess) {
- MOCK_bluetooth_shim_is_gd_acl_enabled_ = true;
-
- get_btm_client_interface().lifecycle.btm_init();
-
- RawAddress bda({0x11, 0x22, 0x33, 0x44, 0x55, 0x66});
-
- btm_acl_connected(bda, 2, HCI_SUCCESS, false);
- ASSERT_EQ(static_cast<size_t>(1),
- mock_function_count_map.count("BTA_dm_acl_up"));
-
- get_btm_client_interface().lifecycle.btm_free();
-}
-
-TEST_F(StackBtmTest, NoInformClientOnConnectionFail) {
- MOCK_bluetooth_shim_is_gd_acl_enabled_ = true;
-
- get_btm_client_interface().lifecycle.btm_init();
-
- RawAddress bda({0x11, 0x22, 0x33, 0x44, 0x55, 0x66});
-
- btm_acl_connected(bda, 2, HCI_ERR_NO_CONNECTION, false);
- ASSERT_EQ(static_cast<size_t>(0),
- mock_function_count_map.count("BTA_dm_acl_up"));
-
- get_btm_client_interface().lifecycle.btm_free();
-}
-
-TEST_F(StackBtmTest, default_packet_type) {
- get_btm_client_interface().lifecycle.btm_init();
-
- btm_cb.acl_cb_.SetDefaultPacketTypeMask(0x4321);
- ASSERT_EQ(0x4321, btm_cb.acl_cb_.DefaultPacketTypes());
-
- get_btm_client_interface().lifecycle.btm_free();
-}
-
-TEST_F(StackBtmTest, change_packet_type) {
- int cnt = 0;
- get_btm_client_interface().lifecycle.btm_init();
-
- btm_cb.acl_cb_.SetDefaultPacketTypeMask(0xffff);
- ASSERT_EQ(0xffff, btm_cb.acl_cb_.DefaultPacketTypes());
-
- // Create connection
- RawAddress bda({0x11, 0x22, 0x33, 0x44, 0x55, 0x66});
- btm_acl_created(bda, 0x123, HCI_ROLE_CENTRAL, BT_TRANSPORT_BR_EDR);
-
- uint64_t features = 0xffffffffffffffff;
- acl_process_supported_features(0x123, features);
-
- mock::btsnd_hcic_change_conn_type = {};
- uint16_t pkt_types = 0x55aa;
- btm_set_packet_types_from_address(bda, pkt_types);
- ASSERT_EQ(++cnt, mock_function_count_map["btsnd_hcic_change_conn_type"]);
- ASSERT_EQ(0x123, mock::btsnd_hcic_change_conn_type.handle);
- ASSERT_EQ(0x4400, mock::btsnd_hcic_change_conn_type.packet_types);
-
- mock::btsnd_hcic_change_conn_type = {};
- btm_set_packet_types_from_address(bda, 0xffff);
- ASSERT_EQ(++cnt, mock_function_count_map["btsnd_hcic_change_conn_type"]);
- ASSERT_EQ(0x123, mock::btsnd_hcic_change_conn_type.handle);
- ASSERT_EQ(0xcc00, mock::btsnd_hcic_change_conn_type.packet_types);
-
- mock::btsnd_hcic_change_conn_type = {};
- btm_set_packet_types_from_address(bda, 0x0);
- // NOTE: The call should not be executed with no bits set
- ASSERT_EQ(0x0, mock::btsnd_hcic_change_conn_type.handle);
- ASSERT_EQ(0x0, mock::btsnd_hcic_change_conn_type.packet_types);
-
- get_btm_client_interface().lifecycle.btm_free();
-}
-
-} // namespace
diff --git a/stack/test/btm_iso_test.cc b/stack/test/btm_iso_test.cc
deleted file mode 100644
index 2444ea1d3..000000000
--- a/stack/test/btm_iso_test.cc
+++ /dev/null
@@ -1,2314 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include "btm_iso_api.h"
-#include "device/include/controller.h"
-#include "main/shim/shim.h"
-#include "mock_controller.h"
-#include "mock_hcic_layer.h"
-
-using bluetooth::hci::IsoManager;
-using testing::_;
-using testing::AnyNumber;
-using testing::AtLeast;
-using testing::Eq;
-using testing::Matcher;
-using testing::Return;
-using testing::SaveArg;
-using testing::StrictMock;
-using testing::Test;
-
-// Iso Manager currently works on top of the legacy HCI layer
-bool bluetooth::shim::is_gd_shim_enabled() { return false; }
-
-namespace bte {
-class BteInterface {
- public:
- virtual void HciSend(BT_HDR* p_msg, uint16_t event) = 0;
- virtual ~BteInterface() = default;
-};
-
-class MockBteInterface : public BteInterface {
- public:
- MOCK_METHOD((void), HciSend, (BT_HDR * p_msg, uint16_t event), (override));
-};
-
-static MockBteInterface* bte_interface = nullptr;
-static void SetMockBteInterface(MockBteInterface* interface) {
- bte_interface = interface;
-}
-} // namespace bte
-
-void bte_main_hci_send(BT_HDR* p_msg, uint16_t event) {
- bte::bte_interface->HciSend(p_msg, event);
- osi_free(p_msg);
-}
-
-namespace {
-class MockCigCallbacks : public bluetooth::hci::iso_manager::CigCallbacks {
- public:
- MockCigCallbacks() = default;
- ~MockCigCallbacks() override = default;
-
- MOCK_METHOD((void), OnSetupIsoDataPath,
- (uint8_t status, uint16_t conn_handle, uint8_t cig_id),
- (override));
- MOCK_METHOD((void), OnRemoveIsoDataPath,
- (uint8_t status, uint16_t conn_handle, uint8_t cig_id),
- (override));
- MOCK_METHOD((void), OnIsoLinkQualityRead,
- (uint8_t conn_handle, uint8_t cig_id, uint32_t txUnackedPackets,
- uint32_t txFlushedPackets, uint32_t txLastSubeventPackets,
- uint32_t retransmittedPackets, uint32_t crcErrorPackets,
- uint32_t rxUnreceivedPackets, uint32_t duplicatePackets),
- (override));
-
- MOCK_METHOD((void), OnCisEvent, (uint8_t event, void* data), (override));
- MOCK_METHOD((void), OnCigEvent, (uint8_t event, void* data), (override));
-
- private:
- DISALLOW_COPY_AND_ASSIGN(MockCigCallbacks);
-};
-
-class MockBigCallbacks : public bluetooth::hci::iso_manager::BigCallbacks {
- public:
- MockBigCallbacks() = default;
- ~MockBigCallbacks() override = default;
-
- MOCK_METHOD((void), OnSetupIsoDataPath,
- (uint8_t status, uint16_t conn_handle, uint8_t big_id),
- (override));
- MOCK_METHOD((void), OnRemoveIsoDataPath,
- (uint8_t status, uint16_t conn_handle, uint8_t big_id),
- (override));
-
- MOCK_METHOD((void), OnBigEvent, (uint8_t event, void* data), (override));
-
- private:
- DISALLOW_COPY_AND_ASSIGN(MockBigCallbacks);
-};
-} // namespace
-
-class IsoManagerTest : public Test {
- protected:
- void SetUp() override {
- bte::SetMockBteInterface(&bte_interface_);
- hcic::SetMockHcicInterface(&hcic_interface_);
- controller::SetMockControllerInterface(&controller_interface_);
-
- big_callbacks_.reset(new MockBigCallbacks());
- cig_callbacks_.reset(new MockCigCallbacks());
-
- EXPECT_CALL(controller_interface_, GetIsoBufferCount())
- .Times(AtLeast(1))
- .WillRepeatedly(Return(6));
- EXPECT_CALL(controller_interface_, GetIsoDataSize())
- .Times(AtLeast(1))
- .WillRepeatedly(Return(1024));
-
- InitIsoManager();
- }
-
- void TearDown() override {
- CleanupIsoManager();
-
- big_callbacks_.reset();
- cig_callbacks_.reset();
-
- bte::SetMockBteInterface(nullptr);
- hcic::SetMockHcicInterface(nullptr);
- controller::SetMockControllerInterface(nullptr);
- }
-
- virtual void InitIsoManager() {
- manager_instance_ = IsoManager::GetInstance();
- manager_instance_->Start();
- manager_instance_->RegisterCigCallbacks(cig_callbacks_.get());
- manager_instance_->RegisterBigCallbacks(big_callbacks_.get());
-
- // Default mock SetCigParams action
- volatile_test_cig_create_cmpl_evt_ = kDefaultCigParamsEvt;
- ON_CALL(hcic_interface_, SetCigParams)
- .WillByDefault([this](auto cig_id, auto,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t hci_mock_rsp_buffer
- [3 + sizeof(uint16_t) * this->volatile_test_cig_create_cmpl_evt_
- .conn_handles.size()];
- uint8_t* p = hci_mock_rsp_buffer;
-
- UINT8_TO_STREAM(p, this->volatile_test_cig_create_cmpl_evt_.status);
- UINT8_TO_STREAM(p, cig_id);
- UINT8_TO_STREAM(
- p, this->volatile_test_cig_create_cmpl_evt_.conn_handles.size());
- for (auto handle :
- this->volatile_test_cig_create_cmpl_evt_.conn_handles) {
- UINT16_TO_STREAM(p, handle);
- }
-
- std::move(cb).Run(
- hci_mock_rsp_buffer,
- 3 + sizeof(uint16_t) * this->volatile_test_cig_create_cmpl_evt_
- .conn_handles.size());
- return 0;
- });
-
- // Default mock CreateCis action
- ON_CALL(hcic_interface_, CreateCis)
- .WillByDefault([](uint8_t num_cis, const EXT_CIS_CREATE_CFG* cis_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- for (const EXT_CIS_CREATE_CFG* cis = cis_cfg; num_cis != 0;
- num_cis--, cis++) {
- std::vector<uint8_t> buf(28);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, HCI_SUCCESS);
- UINT16_TO_STREAM(p, cis->cis_conn_handle);
- UINT24_TO_STREAM(p, 0xEA); // CIG sync delay
- UINT24_TO_STREAM(p, 0xEB); // CIS sync delay
- UINT24_TO_STREAM(p, 0xEC); // transport latency mtos
- UINT24_TO_STREAM(p, 0xED); // transport latency stom
- UINT8_TO_STREAM(p, 0x01); // phy mtos
- UINT8_TO_STREAM(p, 0x02); // phy stom
- UINT8_TO_STREAM(p, 0x01); // nse
- UINT8_TO_STREAM(p, 0x02); // bn mtos
- UINT8_TO_STREAM(p, 0x03); // bn stom
- UINT8_TO_STREAM(p, 0x04); // ft mtos
- UINT8_TO_STREAM(p, 0x05); // ft stom
- UINT16_TO_STREAM(p, 0x00FA); // Max PDU mtos
- UINT16_TO_STREAM(p, 0x00FB); // Max PDU stom
- UINT16_TO_STREAM(p, 0x0C60); // ISO interval
-
- IsoManager::GetInstance()->HandleHciEvent(HCI_BLE_CIS_EST_EVT,
- buf.data(), buf.size());
- }
- });
-
- // Default mock disconnect action
- ON_CALL(hcic_interface_, Disconnect)
- .WillByDefault([](uint16_t handle, uint8_t reason) {
- IsoManager::GetInstance()->HandleDisconnect(handle, reason);
- });
-
- // Default mock CreateBig HCI action
- volatile_test_big_params_evt_ = kDefaultBigParamsEvt;
- ON_CALL(hcic_interface_, CreateBig)
- .WillByDefault(
- [this](auto big_handle,
- bluetooth::hci::iso_manager::big_create_params big_params) {
- std::vector<uint8_t> buf(big_params.num_bis * sizeof(uint16_t) +
- 18);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, HCI_SUCCESS);
- UINT8_TO_STREAM(p, big_handle);
-
- ASSERT_TRUE(big_params.num_bis <=
- volatile_test_big_params_evt_.conn_handles.size());
-
- UINT24_TO_STREAM(p, volatile_test_big_params_evt_.big_sync_delay);
- UINT24_TO_STREAM(
- p, volatile_test_big_params_evt_.transport_latency_big);
- UINT8_TO_STREAM(p, big_params.phy);
- UINT8_TO_STREAM(p, volatile_test_big_params_evt_.nse);
- UINT8_TO_STREAM(p, volatile_test_big_params_evt_.bn);
- UINT8_TO_STREAM(p, volatile_test_big_params_evt_.pto);
- UINT8_TO_STREAM(p, volatile_test_big_params_evt_.irc);
- UINT16_TO_STREAM(p, volatile_test_big_params_evt_.max_pdu);
- UINT16_TO_STREAM(p, volatile_test_big_params_evt_.iso_interval);
-
- UINT8_TO_STREAM(p, big_params.num_bis);
- for (auto i = 0; i < big_params.num_bis; ++i) {
- UINT16_TO_STREAM(p,
- volatile_test_big_params_evt_.conn_handles[i]);
- }
-
- IsoManager::GetInstance()->HandleHciEvent(
- HCI_BLE_CREATE_BIG_CPL_EVT, buf.data(), buf.size());
- });
-
- // Default mock TerminateBig HCI action
- ON_CALL(hcic_interface_, TerminateBig)
- .WillByDefault([](auto big_handle, uint8_t reason) {
- std::vector<uint8_t> buf(2);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, big_handle);
- UINT8_TO_STREAM(p, reason);
-
- IsoManager::GetInstance()->HandleHciEvent(HCI_BLE_TERM_BIG_CPL_EVT,
- buf.data(), buf.size());
- });
-
- // Default mock SetupIsoDataPath HCI action
- ON_CALL(hcic_interface_, SetupIsoDataPath)
- .WillByDefault(
- [](uint16_t iso_handle, uint8_t /* data_path_dir */,
- uint8_t /* data_path_id */, uint8_t /* codec_id_format */,
- uint16_t /* codec_id_company */, uint16_t /* codec_id_vendor */,
- uint32_t /* controller_delay */,
- std::vector<uint8_t> /* codec_conf */,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::vector<uint8_t> buf(3);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, HCI_SUCCESS);
- UINT16_TO_STREAM(p, iso_handle);
-
- std::move(cb).Run(buf.data(), buf.size());
- });
-
- // Default mock RemoveIsoDataPath HCI action
- ON_CALL(hcic_interface_, RemoveIsoDataPath)
- .WillByDefault([](uint16_t iso_handle, uint8_t data_path_dir,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::vector<uint8_t> buf(3);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, HCI_SUCCESS);
- UINT16_TO_STREAM(p, iso_handle);
-
- std::move(cb).Run(buf.data(), buf.size());
- });
- }
-
- virtual void CleanupIsoManager() {
- manager_instance_->Stop();
- manager_instance_ = nullptr;
- }
-
- static const bluetooth::hci::iso_manager::big_create_params kDefaultBigParams;
- static const bluetooth::hci::iso_manager::cig_create_params kDefaultCigParams;
- static const bluetooth::hci::iso_manager::cig_create_params
- kDefaultCigParams2;
- static const bluetooth::hci::iso_manager::cig_create_cmpl_evt
- kDefaultCigParamsEvt;
- static const bluetooth::hci::iso_manager::big_create_cmpl_evt
- kDefaultBigParamsEvt;
- static const bluetooth::hci::iso_manager::iso_data_path_params
- kDefaultIsoDataPathParams;
-
- bluetooth::hci::iso_manager::cig_create_cmpl_evt
- volatile_test_cig_create_cmpl_evt_;
- bluetooth::hci::iso_manager::big_create_cmpl_evt
- volatile_test_big_params_evt_;
-
- IsoManager* manager_instance_;
- bte::MockBteInterface bte_interface_;
- hcic::MockHcicInterface hcic_interface_;
- controller::MockControllerInterface controller_interface_;
-
- std::unique_ptr<MockBigCallbacks> big_callbacks_;
- std::unique_ptr<MockCigCallbacks> cig_callbacks_;
-};
-
-const bluetooth::hci::iso_manager::cig_create_cmpl_evt
- IsoManagerTest::kDefaultCigParamsEvt = {
- .cig_id = 128,
- .status = 0x00,
- .conn_handles = std::vector<uint16_t>({0x0EFF, 0x00FF}),
-};
-
-const bluetooth::hci::iso_manager::big_create_cmpl_evt
- IsoManagerTest::kDefaultBigParamsEvt = {
- .status = 0x00,
- .big_id = 0,
- .big_sync_delay = 0x0080de,
- .transport_latency_big = 0x00cefe,
- .phy = 0x02,
- .nse = 4,
- .bn = 1,
- .pto = 0,
- .irc = 4,
- .max_pdu = 108,
- .iso_interval = 6,
- .conn_handles = std::vector<uint16_t>({0x0EFE, 0x0E00}),
-};
-
-const bluetooth::hci::iso_manager::iso_data_path_params
- IsoManagerTest::kDefaultIsoDataPathParams = {
- .data_path_dir = bluetooth::hci::iso_manager::kIsoDataPathDirectionOut,
- .data_path_id = bluetooth::hci::iso_manager::kIsoDataPathHci,
- .codec_id_format = 0x06,
- .codec_id_company = 0,
- .codec_id_vendor = 0,
- .controller_delay = 0,
- .codec_conf = {0x02, 0x01, 0x02},
-};
-
-const bluetooth::hci::iso_manager::big_create_params
- IsoManagerTest::kDefaultBigParams = {
- .adv_handle = 0x00,
- .num_bis = 2,
- .sdu_itv = 0x002710,
- .max_sdu_size = 108,
- .max_transport_latency = 0x3c,
- .rtn = 3,
- .phy = 0x02,
- .packing = 0x00,
- .framing = 0x00,
- .enc = 0,
- .enc_code = std::array<uint8_t, 16>({0}),
-};
-
-const bluetooth::hci::iso_manager::cig_create_params
- IsoManagerTest::kDefaultCigParams = {
- .sdu_itv_mtos = 0x00002710,
- .sdu_itv_stom = 0x00002711,
- .sca = bluetooth::hci::iso_manager::kIsoSca0To20Ppm,
- .packing = 0x00,
- .framing = 0x01,
- .max_trans_lat_stom = 0x000A,
- .max_trans_lat_mtos = 0x0009,
- .cis_cfgs =
- {
- // CIS #1
- {
- .cis_id = 1,
- .max_sdu_size_mtos = 0x0028,
- .max_sdu_size_stom = 0x0027,
- .phy_mtos = 0x04,
- .phy_stom = 0x03,
- .rtn_mtos = 0x02,
- .rtn_stom = 0x01,
- },
- // CIS #2
- {
- .cis_id = 2,
- .max_sdu_size_mtos = 0x0029,
- .max_sdu_size_stom = 0x002A,
- .phy_mtos = 0x09,
- .phy_stom = 0x08,
- .rtn_mtos = 0x07,
- .rtn_stom = 0x06,
- },
- },
-};
-
-const bluetooth::hci::iso_manager::cig_create_params
- IsoManagerTest::kDefaultCigParams2 = {
- .sdu_itv_mtos = 0x00002709,
- .sdu_itv_stom = 0x00002700,
- .sca = bluetooth::hci::iso_manager::kIsoSca0To20Ppm,
- .packing = 0x01,
- .framing = 0x00,
- .max_trans_lat_stom = 0x000B,
- .max_trans_lat_mtos = 0x0006,
- .cis_cfgs =
- {
- // CIS #1
- {
- .cis_id = 1,
- .max_sdu_size_mtos = 0x0022,
- .max_sdu_size_stom = 0x0022,
- .phy_mtos = 0x01,
- .phy_stom = 0x02,
- .rtn_mtos = 0x02,
- .rtn_stom = 0x01,
- },
- // CIS #2
- {
- .cis_id = 2,
- .max_sdu_size_mtos = 0x002A,
- .max_sdu_size_stom = 0x002B,
- .phy_mtos = 0x06,
- .phy_stom = 0x06,
- .rtn_mtos = 0x07,
- .rtn_stom = 0x07,
- },
- },
-};
-
-class IsoManagerDeathTest : public IsoManagerTest {};
-
-class IsoManagerDeathTestNoInit : public IsoManagerTest {
- protected:
- void InitIsoManager() override { /* DO NOTHING */
- }
-
- void CleanupIsoManager() override { /* DO NOTHING */
- }
-};
-
-class IsoManagerDeathTestNoCleanup : public IsoManagerTest {
- protected:
- void CleanupIsoManager() override { /* DO NOTHING */
- }
-};
-
-bool operator==(const EXT_CIS_CFG& x, const EXT_CIS_CFG& y) {
- return ((x.cis_id == y.cis_id) &&
- (x.max_sdu_size_mtos == y.max_sdu_size_mtos) &&
- (x.max_sdu_size_stom == y.max_sdu_size_stom) &&
- (x.phy_mtos == y.phy_mtos) && (x.phy_stom == y.phy_stom) &&
- (x.rtn_mtos == y.rtn_mtos) && (x.rtn_stom == y.rtn_stom));
-}
-
-bool operator==(
- const struct bluetooth::hci::iso_manager::cig_create_params& x,
- const struct bluetooth::hci::iso_manager::cig_create_params& y) {
- return ((x.sdu_itv_mtos == y.sdu_itv_mtos) &&
- (x.sdu_itv_stom == y.sdu_itv_stom) && (x.sca == y.sca) &&
- (x.packing == y.packing) && (x.framing == y.framing) &&
- (x.max_trans_lat_stom == y.max_trans_lat_stom) &&
- (x.max_trans_lat_mtos == y.max_trans_lat_mtos) &&
- std::is_permutation(x.cis_cfgs.begin(), x.cis_cfgs.end(),
- y.cis_cfgs.begin()));
-}
-
-bool operator==(
- const struct bluetooth::hci::iso_manager::big_create_params& x,
- const struct bluetooth::hci::iso_manager::big_create_params& y) {
- return ((x.adv_handle == y.adv_handle) && (x.num_bis == y.num_bis) &&
- (x.sdu_itv == y.sdu_itv) && (x.max_sdu_size == y.max_sdu_size) &&
- (x.max_transport_latency == y.max_transport_latency) &&
- (x.rtn == y.rtn) && (x.phy == y.phy) && (x.packing == y.packing) &&
- (x.framing == y.framing) && (x.enc == y.enc) &&
- (x.enc_code == y.enc_code));
-}
-
-namespace iso_matchers {
-MATCHER_P(Eq, value, "") { return (arg == value); }
-MATCHER_P2(EqPointedArray, value, len, "") {
- return (!std::memcmp(arg, value, len));
-}
-} // namespace iso_matchers
-
-TEST_F(IsoManagerTest, SingletonAccess) {
- auto* iso_mgr = IsoManager::GetInstance();
- ASSERT_EQ(manager_instance_, iso_mgr);
-}
-
-TEST_F(IsoManagerTest, RegisterCallbacks) {
- auto* iso_mgr = IsoManager::GetInstance();
- ASSERT_EQ(manager_instance_, iso_mgr);
-
- iso_mgr->RegisterBigCallbacks(new MockBigCallbacks());
- iso_mgr->RegisterCigCallbacks(new MockCigCallbacks());
-}
-
-TEST_F(IsoManagerDeathTestNoInit, RegisterNullBigCallbacks) {
- IsoManager::GetInstance()->Start();
-
- ASSERT_EXIT(IsoManager::GetInstance()->RegisterBigCallbacks(nullptr),
- ::testing::KilledBySignal(SIGABRT), "Invalid BIG callbacks");
-
- // Manual cleanup as IsoManagerDeathTest has no 'generic' cleanup
- IsoManager::GetInstance()->Stop();
-}
-
-TEST_F(IsoManagerDeathTestNoInit, RegisterNullCigCallbacks) {
- IsoManager::GetInstance()->Start();
-
- ASSERT_EXIT(IsoManager::GetInstance()->RegisterCigCallbacks(nullptr),
- ::testing::KilledBySignal(SIGABRT), "Invalid CIG callbacks");
-
- // Manual cleanup as IsoManagerDeathTest has no 'generic' cleanup
- IsoManager::GetInstance()->Stop();
-}
-
-// Verify hci layer being called by the Iso Manager
-TEST_F(IsoManagerTest, CreateCigHciCall) {
- for (uint8_t i = 220; i != 60; ++i) {
- EXPECT_CALL(hcic_interface_,
- SetCigParams(i, iso_matchers::Eq(kDefaultCigParams), _))
- .Times(1)
- .RetiresOnSaturation();
- IsoManager::GetInstance()->CreateCig(i, kDefaultCigParams);
- }
-}
-
-// Check handling create cig request twice with the same CIG id
-TEST_F(IsoManagerDeathTest, CreateSameCigTwice) {
- bluetooth::hci::iso_manager::cig_create_cmpl_evt evt;
- evt.status = 0x01;
- EXPECT_CALL(
- *cig_callbacks_,
- OnCigEvent(bluetooth::hci::iso_manager::kIsoEventCigOnCreateCmpl, _))
- .WillOnce([&evt](uint8_t type, void* data) {
- evt = *static_cast<bluetooth::hci::iso_manager::cig_create_cmpl_evt*>(
- data);
- return 0;
- });
-
- volatile_test_cig_create_cmpl_evt_.cig_id = 127;
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
- ASSERT_EQ(evt.status, HCI_SUCCESS);
-
- // Second call with the same CIG ID should fail
- ASSERT_EXIT(IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams),
- ::testing::KilledBySignal(SIGABRT), "already exists");
-}
-
-// Check for handling invalid length response from the faulty controller
-TEST_F(IsoManagerDeathTest, CreateCigCallbackInvalidRspPacket) {
- uint8_t hci_mock_rsp_buffer[] = {0x00, 0x00};
- ON_CALL(hcic_interface_, SetCigParams)
- .WillByDefault(
- [&hci_mock_rsp_buffer](
- auto, auto, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::move(cb).Run(hci_mock_rsp_buffer, sizeof(hci_mock_rsp_buffer));
- return 0;
- });
-
- ASSERT_EXIT(IsoManager::GetInstance()->CreateCig(128, kDefaultCigParams),
- ::testing::KilledBySignal(SIGABRT), "Invalid packet length");
-}
-
-// Check for handling invalid length response from the faulty controller
-TEST_F(IsoManagerDeathTest, CreateCigCallbackInvalidRspPacket2) {
- uint8_t hci_mock_rsp_buffer[] = {0x00, 0x00, 0x02, 0x01, 0x00};
- ON_CALL(hcic_interface_, SetCigParams)
- .WillByDefault(
- [&hci_mock_rsp_buffer](
- auto, auto, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::move(cb).Run(hci_mock_rsp_buffer, sizeof(hci_mock_rsp_buffer));
- return 0;
- });
-
- ASSERT_EXIT(IsoManager::GetInstance()->CreateCig(128, kDefaultCigParams),
- ::testing::KilledBySignal(SIGABRT), "Invalid CIS count");
-}
-
-// Check if IsoManager properly handles error responses from HCI layer
-TEST_F(IsoManagerTest, CreateCigCallbackInvalidStatus) {
- uint8_t rsp_cig_id = 128;
- uint8_t rsp_status = 0x01;
- uint8_t rsp_cis_cnt = 3;
- uint8_t hci_mock_rsp_buffer[] = {rsp_status, rsp_cig_id, rsp_cis_cnt};
-
- ON_CALL(hcic_interface_, SetCigParams)
- .WillByDefault(
- [&hci_mock_rsp_buffer](
- auto, auto, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::move(cb).Run(hci_mock_rsp_buffer, sizeof(hci_mock_rsp_buffer));
- return 0;
- });
-
- bluetooth::hci::iso_manager::cig_create_cmpl_evt evt;
- EXPECT_CALL(
- *cig_callbacks_,
- OnCigEvent(bluetooth::hci::iso_manager::kIsoEventCigOnCreateCmpl, _))
- .WillOnce([&evt](uint8_t type, void* data) {
- evt = *static_cast<bluetooth::hci::iso_manager::cig_create_cmpl_evt*>(
- data);
- return 0;
- });
-
- IsoManager::GetInstance()->CreateCig(rsp_cig_id, kDefaultCigParams);
- ASSERT_EQ(evt.cig_id, rsp_cig_id);
- ASSERT_EQ(evt.status, rsp_status);
- ASSERT_TRUE(evt.conn_handles.empty());
-}
-
-// Check valid callback response
-TEST_F(IsoManagerTest, CreateCigCallbackValid) {
- bluetooth::hci::iso_manager::cig_create_cmpl_evt evt;
- EXPECT_CALL(
- *cig_callbacks_,
- OnCigEvent(bluetooth::hci::iso_manager::kIsoEventCigOnCreateCmpl, _))
- .WillOnce([&evt](uint8_t type, void* data) {
- evt = *static_cast<bluetooth::hci::iso_manager::cig_create_cmpl_evt*>(
- data);
- return 0;
- });
-
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
- ASSERT_EQ(evt.cig_id, volatile_test_cig_create_cmpl_evt_.cig_id);
- ASSERT_EQ(evt.status, volatile_test_cig_create_cmpl_evt_.status);
- ASSERT_EQ(evt.conn_handles.size(), 2u);
- ASSERT_TRUE(
- std::is_permutation(evt.conn_handles.begin(), evt.conn_handles.end(),
- std::vector<uint16_t>({0x0EFF, 0x00FF}).begin()));
-}
-
-// Check if CIG reconfigure triggers HCI layer call
-TEST_F(IsoManagerTest, ReconfigureCigHciCall) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- EXPECT_CALL(hcic_interface_,
- SetCigParams(volatile_test_cig_create_cmpl_evt_.cig_id,
- iso_matchers::Eq(kDefaultCigParams), _))
- .Times(1);
- IsoManager::GetInstance()->ReconfigureCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-}
-
-// Verify handlidng invalid call - reconfiguring invalid CIG
-TEST_F(IsoManagerDeathTest, ReconfigureCigWithNoSuchCig) {
- ASSERT_EXIT(IsoManager::GetInstance()->ReconfigureCig(128, kDefaultCigParams),
- ::testing::KilledBySignal(SIGABRT), "No such cig");
-}
-
-TEST_F(IsoManagerDeathTest, ReconfigureCigInvalidRspPacket) {
- uint8_t hci_mock_rsp_buffer[] = {0x00, 0x00};
-
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- ON_CALL(hcic_interface_, SetCigParams)
- .WillByDefault(
- [&hci_mock_rsp_buffer](
- auto, auto, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::move(cb).Run(hci_mock_rsp_buffer, sizeof(hci_mock_rsp_buffer));
- return 0;
- });
- ASSERT_EXIT(IsoManager::GetInstance()->ReconfigureCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams),
- ::testing::KilledBySignal(SIGABRT), "Invalid packet length");
-}
-
-TEST_F(IsoManagerDeathTest, ReconfigureCigInvalidRspPacket2) {
- uint8_t hci_mock_rsp_buffer[] = {0x00, 0x00, 0x02, 0x01, 0x00};
-
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- ON_CALL(hcic_interface_, SetCigParams)
- .WillByDefault(
- [&hci_mock_rsp_buffer](
- auto, auto, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::move(cb).Run(hci_mock_rsp_buffer, sizeof(hci_mock_rsp_buffer));
- return 0;
- });
- ASSERT_EXIT(
- IsoManager::GetInstance()->ReconfigureCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams2),
- ::testing::KilledBySignal(SIGABRT), "Invalid CIS count");
-}
-
-TEST_F(IsoManagerTest, ReconfigureCigInvalidStatus) {
- uint8_t rsp_cig_id = 128;
- uint8_t rsp_status = 0x01;
- uint8_t rsp_cis_cnt = 3;
- uint8_t hci_mock_rsp_buffer[] = {rsp_status, rsp_cig_id, rsp_cis_cnt};
-
- IsoManager::GetInstance()->CreateCig(rsp_cig_id, kDefaultCigParams);
-
- // Set-up the invalid response
- ON_CALL(hcic_interface_, SetCigParams)
- .WillByDefault(
- [&hci_mock_rsp_buffer](
- auto, auto, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::move(cb).Run(hci_mock_rsp_buffer, sizeof(hci_mock_rsp_buffer));
- return 0;
- });
-
- bluetooth::hci::iso_manager::cig_create_cmpl_evt evt;
- EXPECT_CALL(
- *cig_callbacks_,
- OnCigEvent(bluetooth::hci::iso_manager::kIsoEventCigOnReconfigureCmpl, _))
- .WillOnce([&evt](uint8_t type, void* data) {
- evt = *static_cast<bluetooth::hci::iso_manager::cig_create_cmpl_evt*>(
- data);
- return 0;
- });
- IsoManager::GetInstance()->ReconfigureCig(rsp_cig_id, kDefaultCigParams2);
-
- ASSERT_EQ(evt.cig_id, rsp_cig_id);
- ASSERT_EQ(evt.status, rsp_status);
- ASSERT_TRUE(evt.conn_handles.empty());
-}
-
-TEST_F(IsoManagerTest, ReconfigureCigValid) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- bluetooth::hci::iso_manager::cig_create_cmpl_evt evt;
- EXPECT_CALL(
- *cig_callbacks_,
- OnCigEvent(bluetooth::hci::iso_manager::kIsoEventCigOnReconfigureCmpl, _))
- .WillOnce([&evt](uint8_t type, void* data) {
- evt = *static_cast<bluetooth::hci::iso_manager::cig_create_cmpl_evt*>(
- data);
- return 0;
- });
-
- // Verify valid reconfiguration request
- IsoManager::GetInstance()->ReconfigureCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams2);
- ASSERT_EQ(evt.cig_id, volatile_test_cig_create_cmpl_evt_.cig_id);
- ASSERT_EQ(evt.status, volatile_test_cig_create_cmpl_evt_.status);
- ASSERT_TRUE(std::is_permutation(
- evt.conn_handles.begin(), evt.conn_handles.end(),
- volatile_test_cig_create_cmpl_evt_.conn_handles.begin()));
-}
-
-TEST_F(IsoManagerTest, RemoveCigHciCall) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- EXPECT_CALL(hcic_interface_,
- RemoveCig(volatile_test_cig_create_cmpl_evt_.cig_id, _))
- .Times(1);
- IsoManager::GetInstance()->RemoveCig(
- volatile_test_cig_create_cmpl_evt_.cig_id);
-}
-
-TEST_F(IsoManagerDeathTest, RemoveCigWithNoSuchCig) {
- ASSERT_EXIT(IsoManager::GetInstance()->RemoveCig(
- volatile_test_cig_create_cmpl_evt_.cig_id),
- ::testing::KilledBySignal(SIGABRT), "No such cig");
-}
-
-TEST_F(IsoManagerDeathTest, RemoveSameCigTwice) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- ON_CALL(hcic_interface_, RemoveCig)
- .WillByDefault(
- [this](auto, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t hci_mock_rsp_buffer[2];
- uint8_t* p = hci_mock_rsp_buffer;
-
- UINT8_TO_STREAM(p, HCI_SUCCESS);
- UINT8_TO_STREAM(p, this->volatile_test_cig_create_cmpl_evt_.cig_id);
-
- std::move(cb).Run(hci_mock_rsp_buffer, sizeof(hci_mock_rsp_buffer));
- return 0;
- });
-
- IsoManager::GetInstance()->RemoveCig(
- volatile_test_cig_create_cmpl_evt_.cig_id);
-
- ASSERT_EXIT(IsoManager::GetInstance()->RemoveCig(
- volatile_test_cig_create_cmpl_evt_.cig_id),
- ::testing::KilledBySignal(SIGABRT), "No such cig");
-}
-
-TEST_F(IsoManagerDeathTest, RemoveCigInvalidRspPacket) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- ON_CALL(hcic_interface_, RemoveCig)
- .WillByDefault([](auto, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- uint8_t hci_mock_rsp_buffer[] = {0x00}; // status byte only
-
- std::move(cb).Run(hci_mock_rsp_buffer, sizeof(hci_mock_rsp_buffer));
- return 0;
- });
- ASSERT_EXIT(IsoManager::GetInstance()->RemoveCig(
- volatile_test_cig_create_cmpl_evt_.cig_id),
- ::testing::KilledBySignal(SIGABRT), "Invalid packet length");
-}
-
-TEST_F(IsoManagerTest, RemoveCigInvalidStatus) {
- uint8_t rsp_status = 0x02;
- uint8_t hci_mock_rsp_buffer[] = {rsp_status,
- volatile_test_cig_create_cmpl_evt_.cig_id};
-
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- ON_CALL(hcic_interface_, RemoveCig)
- .WillByDefault(
- [&hci_mock_rsp_buffer](
- auto, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::move(cb).Run(hci_mock_rsp_buffer, sizeof(hci_mock_rsp_buffer));
- return 0;
- });
-
- bluetooth::hci::iso_manager::cig_remove_cmpl_evt evt;
- ON_CALL(*cig_callbacks_,
- OnCigEvent(bluetooth::hci::iso_manager::kIsoEventCigOnRemoveCmpl, _))
- .WillByDefault([&evt](uint8_t type, void* data) {
- evt = *static_cast<bluetooth::hci::iso_manager::cig_remove_cmpl_evt*>(
- data);
- return 0;
- });
-
- IsoManager::GetInstance()->RemoveCig(
- volatile_test_cig_create_cmpl_evt_.cig_id);
- ASSERT_EQ(evt.cig_id, volatile_test_cig_create_cmpl_evt_.cig_id);
- ASSERT_EQ(evt.status, rsp_status);
-}
-
-TEST_F(IsoManagerTest, RemoveCigValid) {
- uint8_t hci_mock_rsp_buffer[] = {HCI_SUCCESS,
- volatile_test_cig_create_cmpl_evt_.cig_id};
-
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- ON_CALL(hcic_interface_, RemoveCig)
- .WillByDefault(
- [&hci_mock_rsp_buffer](
- auto, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::move(cb).Run(hci_mock_rsp_buffer, sizeof(hci_mock_rsp_buffer));
- return 0;
- });
-
- bluetooth::hci::iso_manager::cig_remove_cmpl_evt evt;
- EXPECT_CALL(
- *cig_callbacks_,
- OnCigEvent(bluetooth::hci::iso_manager::kIsoEventCigOnRemoveCmpl, _))
- .WillOnce([&evt](uint8_t type, void* data) {
- evt = *static_cast<bluetooth::hci::iso_manager::cig_remove_cmpl_evt*>(
- data);
- return 0;
- });
-
- IsoManager::GetInstance()->RemoveCig(
- volatile_test_cig_create_cmpl_evt_.cig_id);
- ASSERT_EQ(evt.cig_id, volatile_test_cig_create_cmpl_evt_.cig_id);
- ASSERT_EQ(evt.status, HCI_SUCCESS);
-}
-
-TEST_F(IsoManagerTest, EstablishCisHciCall) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
-
- EXPECT_CALL(hcic_interface_,
- CreateCis(2,
- iso_matchers::EqPointedArray(
- params.conn_pairs.data(),
- params.conn_pairs.size() *
- sizeof(params.conn_pairs.data()[0])),
- _))
- .Times(1);
- IsoManager::GetInstance()->EstablishCis(params);
-}
-
-TEST_F(IsoManagerDeathTest, EstablishCisWithNoSuchCis) {
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
-
- ASSERT_EXIT(
- IsoManager::GetInstance()->IsoManager::GetInstance()->EstablishCis(
- params),
- ::testing::KilledBySignal(SIGABRT), "No such cis");
-}
-
-TEST_F(IsoManagerDeathTest, ConnectSameCisTwice) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- ASSERT_EXIT(
- IsoManager::GetInstance()->IsoManager::GetInstance()->EstablishCis(
- params),
- ::testing::KilledBySignal(SIGABRT), "Already connected");
-}
-
-TEST_F(IsoManagerDeathTest, EstablishCisInvalidResponsePacket) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- ON_CALL(hcic_interface_, CreateCis)
- .WillByDefault([this](uint8_t num_cis, const EXT_CIS_CREATE_CFG* cis_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- std::vector<uint8_t> buf(27);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, HCI_SUCCESS);
- UINT16_TO_STREAM(p, handle);
- UINT24_TO_STREAM(p, 0xEA); // CIG sync delay
- UINT24_TO_STREAM(p, 0xEB); // CIS sync delay
- UINT24_TO_STREAM(p, 0xEC); // transport latency mtos
- UINT24_TO_STREAM(p, 0xED); // transport latency stom
- UINT8_TO_STREAM(p, 0x01); // phy mtos
- UINT8_TO_STREAM(p, 0x02); // phy stom
- UINT8_TO_STREAM(p, 0x01); // nse
- UINT8_TO_STREAM(p, 0x02); // bn mtos
- UINT8_TO_STREAM(p, 0x03); // bn stom
- UINT8_TO_STREAM(p, 0x04); // ft mtos
- UINT8_TO_STREAM(p, 0x05); // ft stom
- UINT16_TO_STREAM(p, 0x00FA); // Max PDU mtos
- UINT16_TO_STREAM(p, 0x00FB); // Max PDU stom
-
- IsoManager::GetInstance()->HandleHciEvent(HCI_BLE_CIS_EST_EVT,
- buf.data(), buf.size());
- }
- });
-
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
-
- ASSERT_EXIT(
- IsoManager::GetInstance()->IsoManager::GetInstance()->EstablishCis(
- params),
- ::testing::KilledBySignal(SIGABRT), "Invalid packet length");
-}
-
-TEST_F(IsoManagerTest, EstablishCisInvalidCommandStatus) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
- uint16_t invalid_status = 0x0001;
-
- ON_CALL(hcic_interface_, CreateCis)
- .WillByDefault([invalid_status](
- uint8_t num_cis, const EXT_CIS_CREATE_CFG* cis_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::move(cb).Run((uint8_t*)&invalid_status, sizeof(invalid_status));
- return 0;
- });
-
- EXPECT_CALL(
- *cig_callbacks_,
- OnCisEvent(bluetooth::hci::iso_manager::kIsoEventCisEstablishCmpl, _))
- .Times(kDefaultCigParams.cis_cfgs.size())
- .WillRepeatedly([this, invalid_status](uint8_t type, void* data) {
- bluetooth::hci::iso_manager::cis_establish_cmpl_evt* evt =
- static_cast<bluetooth::hci::iso_manager::cis_establish_cmpl_evt*>(
- data);
-
- ASSERT_EQ(evt->status, invalid_status);
- ASSERT_TRUE(
- std::find(volatile_test_cig_create_cmpl_evt_.conn_handles.begin(),
- volatile_test_cig_create_cmpl_evt_.conn_handles.end(),
- evt->cis_conn_hdl) !=
- volatile_test_cig_create_cmpl_evt_.conn_handles.end());
- });
-
- // Establish all CISes
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-}
-
-TEST_F(IsoManagerTest, EstablishCisInvalidStatus) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
- uint8_t invalid_status = 0x01;
-
- ON_CALL(hcic_interface_, CreateCis)
- .WillByDefault([this, invalid_status](
- uint8_t num_cis, const EXT_CIS_CREATE_CFG* cis_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- std::vector<uint8_t> buf(28);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, invalid_status);
- UINT16_TO_STREAM(p, handle);
- UINT24_TO_STREAM(p, 0xEA); // CIG sync delay
- UINT24_TO_STREAM(p, 0xEB); // CIS sync delay
- UINT24_TO_STREAM(p, 0xEC); // transport latency mtos
- UINT24_TO_STREAM(p, 0xED); // transport latency stom
- UINT8_TO_STREAM(p, 0x01); // phy mtos
- UINT8_TO_STREAM(p, 0x02); // phy stom
- UINT8_TO_STREAM(p, 0x01); // nse
- UINT8_TO_STREAM(p, 0x02); // bn mtos
- UINT8_TO_STREAM(p, 0x03); // bn stom
- UINT8_TO_STREAM(p, 0x04); // ft mtos
- UINT8_TO_STREAM(p, 0x05); // ft stom
- UINT16_TO_STREAM(p, 0x00FA); // Max PDU mtos
- UINT16_TO_STREAM(p, 0x00FB); // Max PDU stom
- UINT16_TO_STREAM(p, 0x0C60); // ISO interval
-
- IsoManager::GetInstance()->HandleHciEvent(HCI_BLE_CIS_EST_EVT,
- buf.data(), buf.size());
- }
- });
-
- EXPECT_CALL(
- *cig_callbacks_,
- OnCisEvent(bluetooth::hci::iso_manager::kIsoEventCisEstablishCmpl, _))
- .Times(kDefaultCigParams.cis_cfgs.size())
- .WillRepeatedly([this, invalid_status](uint8_t type, void* data) {
- bluetooth::hci::iso_manager::cis_establish_cmpl_evt* evt =
- static_cast<bluetooth::hci::iso_manager::cis_establish_cmpl_evt*>(
- data);
-
- ASSERT_EQ(evt->status, invalid_status);
- ASSERT_TRUE(
- std::find(volatile_test_cig_create_cmpl_evt_.conn_handles.begin(),
- volatile_test_cig_create_cmpl_evt_.conn_handles.end(),
- evt->cis_conn_hdl) !=
- volatile_test_cig_create_cmpl_evt_.conn_handles.end());
- });
-
- // Establish all CISes before setting up their data paths
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-}
-
-TEST_F(IsoManagerTest, EstablishCisValid) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- EXPECT_CALL(
- *cig_callbacks_,
- OnCisEvent(bluetooth::hci::iso_manager::kIsoEventCisEstablishCmpl, _))
- .Times(kDefaultCigParams.cis_cfgs.size())
- .WillRepeatedly([this](uint8_t type, void* data) {
- bluetooth::hci::iso_manager::cis_establish_cmpl_evt* evt =
- static_cast<bluetooth::hci::iso_manager::cis_establish_cmpl_evt*>(
- data);
-
- ASSERT_EQ(evt->status, HCI_SUCCESS);
- ASSERT_TRUE(
- std::find(volatile_test_cig_create_cmpl_evt_.conn_handles.begin(),
- volatile_test_cig_create_cmpl_evt_.conn_handles.end(),
- evt->cis_conn_hdl) !=
- volatile_test_cig_create_cmpl_evt_.conn_handles.end());
- });
-
- // Establish all CISes before setting up their data paths
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-}
-
-TEST_F(IsoManagerTest, ReconnectCisValid) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- // Establish all CISes before setting up their data paths
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- // trigger HCI disconnection event
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- IsoManager::GetInstance()->HandleDisconnect(handle, 0x16);
- }
-
- EXPECT_CALL(
- *cig_callbacks_,
- OnCisEvent(bluetooth::hci::iso_manager::kIsoEventCisEstablishCmpl, _))
- .Times(kDefaultCigParams.cis_cfgs.size())
- .WillRepeatedly([this](uint8_t type, void* data) {
- bluetooth::hci::iso_manager::cis_establish_cmpl_evt* evt =
- static_cast<bluetooth::hci::iso_manager::cis_establish_cmpl_evt*>(
- data);
-
- ASSERT_EQ(evt->status, HCI_SUCCESS);
- ASSERT_TRUE(
- std::find(volatile_test_cig_create_cmpl_evt_.conn_handles.begin(),
- volatile_test_cig_create_cmpl_evt_.conn_handles.end(),
- evt->cis_conn_hdl) !=
- volatile_test_cig_create_cmpl_evt_.conn_handles.end());
- });
- IsoManager::GetInstance()->EstablishCis(params);
-}
-
-TEST_F(IsoManagerTest, DisconnectCisHciCall) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- // Establish all CISes before setting up their data paths
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- EXPECT_CALL(hcic_interface_, Disconnect(handle, 0x16))
- .Times(1)
- .RetiresOnSaturation();
- IsoManager::GetInstance()->IsoManager::GetInstance()->DisconnectCis(handle,
- 0x16);
- }
-}
-
-TEST_F(IsoManagerDeathTest, DisconnectCisWithNoSuchCis) {
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- ASSERT_EXIT(
- IsoManager::GetInstance()->IsoManager::GetInstance()->DisconnectCis(
- handle, 0x16),
- ::testing::KilledBySignal(SIGABRT), "No such cis");
- }
-}
-
-TEST_F(IsoManagerDeathTest, DisconnectSameCisTwice) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- // Establish all CISes before setting up their data paths
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- IsoManager::GetInstance()->IsoManager::GetInstance()->DisconnectCis(handle,
- 0x16);
- }
-
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- ASSERT_EXIT(
- IsoManager::GetInstance()->IsoManager::GetInstance()->DisconnectCis(
- handle, 0x16),
- ::testing::KilledBySignal(SIGABRT), "Not connected");
- }
-}
-
-TEST_F(IsoManagerTest, DisconnectCisValid) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- // Establish all CISes before setting up their data paths
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- uint8_t disconnect_reason = 0x16;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- EXPECT_CALL(*cig_callbacks_, OnCisEvent)
- .WillOnce([this, handle, disconnect_reason](uint8_t event_code,
- void* data) {
- ASSERT_EQ(event_code,
- bluetooth::hci::iso_manager::kIsoEventCisDisconnected);
- auto* event =
- static_cast<bluetooth::hci::iso_manager::cis_disconnected_evt*>(
- data);
- ASSERT_EQ(event->reason, disconnect_reason);
- ASSERT_EQ(event->cig_id, volatile_test_cig_create_cmpl_evt_.cig_id);
- ASSERT_EQ(event->cis_conn_hdl, handle);
- })
- .RetiresOnSaturation();
- IsoManager::GetInstance()->IsoManager::GetInstance()->DisconnectCis(
- handle, disconnect_reason);
- }
-}
-
-// Check if we properly ignore not ISO related disconnect events
-TEST_F(IsoManagerDeathTest, DisconnectCisInvalidResponse) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- // Make the HCI layer send invalid handles in disconnect event
- ON_CALL(hcic_interface_, Disconnect)
- .WillByDefault([](uint16_t handle, uint8_t reason) {
- IsoManager::GetInstance()->HandleDisconnect(handle + 1, reason);
- });
-
- // We don't expect any calls as these are not ISO handles
- ON_CALL(*cig_callbacks_,
- OnCisEvent(bluetooth::hci::iso_manager::kIsoEventCisDisconnected, _))
- .WillByDefault([](uint8_t event_code, void* data) { FAIL(); });
-
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- IsoManager::GetInstance()->IsoManager::GetInstance()->DisconnectCis(handle,
- 0x16);
- }
-}
-
-TEST_F(IsoManagerTest, CreateBigHciCall) {
- for (uint8_t i = 220; i != 60; ++i) {
- EXPECT_CALL(hcic_interface_,
- CreateBig(i, iso_matchers::Eq(kDefaultBigParams)))
- .Times(1)
- .RetiresOnSaturation();
- IsoManager::GetInstance()->CreateBig(i, kDefaultBigParams);
- }
-}
-
-TEST_F(IsoManagerTest, CreateBigValid) {
- bluetooth::hci::iso_manager::big_create_cmpl_evt evt;
- evt.status = 0x01;
- EXPECT_CALL(
- *big_callbacks_,
- OnBigEvent(bluetooth::hci::iso_manager::kIsoEventBigOnCreateCmpl, _))
- .WillOnce([&evt](uint8_t type, void* data) {
- evt = *static_cast<bluetooth::hci::iso_manager::big_create_cmpl_evt*>(
- data);
- return 0;
- });
-
- IsoManager::GetInstance()->CreateBig(0x01, kDefaultBigParams);
- ASSERT_EQ(evt.status, HCI_SUCCESS);
-}
-
-TEST_F(IsoManagerDeathTest, CreateBigInvalidResponsePacket) {
- ON_CALL(hcic_interface_, CreateBig)
- .WillByDefault(
- [](auto big_handle,
- bluetooth::hci::iso_manager::big_create_params big_params) {
- std::vector<uint8_t> buf(18);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, 0x00);
- UINT8_TO_STREAM(p, big_handle);
-
- UINT24_TO_STREAM(p, 0x0080de); // big_sync_delay
- UINT24_TO_STREAM(p, 0x00cefe); // transport_latency_big
- UINT8_TO_STREAM(p, big_params.phy); // phy
- UINT8_TO_STREAM(p, 4); // nse
- UINT8_TO_STREAM(p, 1); // bn
- UINT8_TO_STREAM(p, 0); // pto
- UINT8_TO_STREAM(p, 4); // irc
- UINT16_TO_STREAM(p, 108); // max_pdu
- UINT16_TO_STREAM(p, 6); // iso_interval
- UINT8_TO_STREAM(p, 0); // num BISes
-
- IsoManager::GetInstance()->HandleHciEvent(
- HCI_BLE_CREATE_BIG_CPL_EVT, buf.data(), buf.size());
- });
-
- ASSERT_EXIT(IsoManager::GetInstance()->CreateBig(0x01, kDefaultBigParams),
- ::testing::KilledBySignal(SIGABRT), "Invalid bis count");
-}
-
-TEST_F(IsoManagerDeathTest, CreateBigInvalidResponsePacket2) {
- ON_CALL(hcic_interface_, CreateBig)
- .WillByDefault(
- [](auto big_handle,
- bluetooth::hci::iso_manager::big_create_params big_params) {
- std::vector<uint8_t> buf(18);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, 0x00);
- UINT8_TO_STREAM(p, big_handle);
-
- UINT24_TO_STREAM(p, 0x0080de); // big_sync_delay
- UINT24_TO_STREAM(p, 0x00cefe); // transport_latency_big
- UINT8_TO_STREAM(p, big_params.phy); // phy
- UINT8_TO_STREAM(p, 4); // nse
- UINT8_TO_STREAM(p, 1); // bn
- UINT8_TO_STREAM(p, 0); // pto
- UINT8_TO_STREAM(p, 4); // irc
- UINT16_TO_STREAM(p, 108); // max_pdu
- UINT16_TO_STREAM(p, 6); // iso_interval
- UINT8_TO_STREAM(p, big_params.num_bis);
-
- IsoManager::GetInstance()->HandleHciEvent(
- HCI_BLE_CREATE_BIG_CPL_EVT, buf.data(), buf.size());
- });
-
- ASSERT_EXIT(IsoManager::GetInstance()->CreateBig(0x01, kDefaultBigParams),
- ::testing::KilledBySignal(SIGABRT), "Invalid packet length");
-}
-
-TEST_F(IsoManagerTest, CreateBigInvalidStatus) {
- bluetooth::hci::iso_manager::big_create_cmpl_evt evt;
- evt.status = 0x00;
- EXPECT_CALL(
- *big_callbacks_,
- OnBigEvent(bluetooth::hci::iso_manager::kIsoEventBigOnCreateCmpl, _))
- .WillOnce([&evt](uint8_t type, void* data) {
- evt = *static_cast<bluetooth::hci::iso_manager::big_create_cmpl_evt*>(
- data);
- return 0;
- });
-
- ON_CALL(hcic_interface_, CreateBig)
- .WillByDefault(
- [](auto big_handle,
- bluetooth::hci::iso_manager::big_create_params big_params) {
- std::vector<uint8_t> buf(big_params.num_bis * sizeof(uint16_t) +
- 18);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, 0x01);
- UINT8_TO_STREAM(p, big_handle);
-
- UINT24_TO_STREAM(p, 0x0080de); // big_sync_delay
- UINT24_TO_STREAM(p, 0x00cefe); // transport_latency_big
- UINT8_TO_STREAM(p, big_params.phy); // phy
- UINT8_TO_STREAM(p, 4); // nse
- UINT8_TO_STREAM(p, 1); // bn
- UINT8_TO_STREAM(p, 0); // pto
- UINT8_TO_STREAM(p, 4); // irc
- UINT16_TO_STREAM(p, 108); // max_pdu
- UINT16_TO_STREAM(p, 6); // iso_interval
-
- UINT8_TO_STREAM(p, big_params.num_bis);
- static uint8_t conn_hdl = 0x01;
- for (auto i = 0; i < big_params.num_bis; ++i) {
- UINT16_TO_STREAM(p, conn_hdl++);
- }
-
- IsoManager::GetInstance()->HandleHciEvent(
- HCI_BLE_CREATE_BIG_CPL_EVT, buf.data(), buf.size());
- });
-
- IsoManager::GetInstance()->CreateBig(0x01, kDefaultBigParams);
- ASSERT_EQ(evt.status, 0x01);
- ASSERT_EQ(evt.big_id, 0x01);
- ASSERT_EQ(evt.conn_handles.size(), kDefaultBigParams.num_bis);
-}
-
-TEST_F(IsoManagerDeathTest, CreateSameBigTwice) {
- bluetooth::hci::iso_manager::big_create_cmpl_evt evt;
- evt.status = 0x01;
- EXPECT_CALL(
- *big_callbacks_,
- OnBigEvent(bluetooth::hci::iso_manager::kIsoEventBigOnCreateCmpl, _))
- .WillOnce([&evt](uint8_t type, void* data) {
- evt = *static_cast<bluetooth::hci::iso_manager::big_create_cmpl_evt*>(
- data);
- return 0;
- });
-
- IsoManager::GetInstance()->CreateBig(0x01, kDefaultBigParams);
- ASSERT_EQ(evt.status, HCI_SUCCESS);
- ASSERT_EQ(evt.big_id, 0x01);
- ASSERT_EQ(evt.conn_handles.size(), kDefaultBigParams.num_bis);
-}
-
-TEST_F(IsoManagerTest, TerminateBigHciCall) {
- const uint8_t big_id = 0x22;
- const uint8_t reason = 0x16; // Terminated by local host
-
- IsoManager::GetInstance()->CreateBig(big_id, kDefaultBigParams);
- EXPECT_CALL(hcic_interface_, TerminateBig(big_id, reason)).Times(1);
- IsoManager::GetInstance()->TerminateBig(big_id, reason);
-}
-
-TEST_F(IsoManagerDeathTest, TerminateSameBigTwice) {
- const uint8_t big_id = 0x22;
- const uint8_t reason = 0x16; // Terminated by local host
-
- IsoManager::GetInstance()->CreateBig(big_id, kDefaultBigParams);
- EXPECT_CALL(
- *big_callbacks_,
- OnBigEvent(bluetooth::hci::iso_manager::kIsoEventBigOnTerminateCmpl, _));
-
- IsoManager::GetInstance()->TerminateBig(big_id, reason);
- ASSERT_EXIT(IsoManager::GetInstance()->TerminateBig(big_id, reason),
- ::testing::KilledBySignal(SIGABRT), "No such big");
-}
-
-TEST_F(IsoManagerDeathTest, TerminateBigNoSuchBig) {
- const uint8_t big_id = 0x01;
- const uint8_t reason = 0x16; // Terminated by local host
-
- EXPECT_CALL(
- *big_callbacks_,
- OnBigEvent(bluetooth::hci::iso_manager::kIsoEventBigOnCreateCmpl, _));
- IsoManager::GetInstance()->CreateBig(big_id, kDefaultBigParams);
-
- ASSERT_EXIT(IsoManager::GetInstance()->TerminateBig(big_id + 1, reason),
- ::testing::KilledBySignal(SIGABRT), "No such big");
-}
-
-TEST_F(IsoManagerDeathTest, TerminateBigInvalidResponsePacket) {
- ON_CALL(hcic_interface_, TerminateBig)
- .WillByDefault([](auto big_handle, uint8_t reason) {
- std::vector<uint8_t> buf(1);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, reason);
-
- IsoManager::GetInstance()->HandleHciEvent(HCI_BLE_TERM_BIG_CPL_EVT,
- buf.data(), buf.size());
- });
-
- const uint8_t big_id = 0x22;
- const uint8_t reason = 0x16; // Terminated by local host
-
- IsoManager::GetInstance()->CreateBig(big_id, kDefaultBigParams);
- ASSERT_EXIT(IsoManager::GetInstance()->TerminateBig(big_id, reason),
- ::testing::KilledBySignal(SIGABRT), "Invalid packet length");
-}
-
-TEST_F(IsoManagerDeathTest, TerminateBigInvalidResponsePacket2) {
- const uint8_t big_id = 0x22;
- const uint8_t reason = 0x16; // Terminated by local host
-
- ON_CALL(hcic_interface_, TerminateBig)
- .WillByDefault([](auto big_handle, uint8_t reason) {
- std::vector<uint8_t> buf(3);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, reason);
-
- IsoManager::GetInstance()->HandleHciEvent(HCI_BLE_TERM_BIG_CPL_EVT,
- buf.data(), buf.size());
- });
-
- IsoManager::GetInstance()->CreateBig(big_id, kDefaultBigParams);
- ASSERT_EXIT(IsoManager::GetInstance()->TerminateBig(big_id, reason),
- ::testing::KilledBySignal(SIGABRT), "Invalid packet length");
-}
-
-TEST_F(IsoManagerTest, TerminateBigInvalidResponseBigId) {
- const uint8_t big_id = 0x22;
- const uint8_t reason = 0x16; // Terminated by local host
-
- ON_CALL(hcic_interface_, TerminateBig)
- .WillByDefault([](auto big_handle, uint8_t reason) {
- std::vector<uint8_t> buf(2);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, reason);
- UINT8_TO_STREAM(p, big_handle + 1);
-
- IsoManager::GetInstance()->HandleHciEvent(HCI_BLE_TERM_BIG_CPL_EVT,
- buf.data(), buf.size());
- });
-
- IsoManager::GetInstance()->CreateBig(big_id, kDefaultBigParams);
- ASSERT_EXIT(IsoManager::GetInstance()->TerminateBig(big_id, reason),
- ::testing::KilledBySignal(SIGABRT), "No such big");
-}
-
-TEST_F(IsoManagerTest, TerminateBigValid) {
- const uint8_t big_id = 0x22;
- const uint8_t reason = 0x16; // Terminated by local host
- bluetooth::hci::iso_manager::big_terminate_cmpl_evt evt;
-
- IsoManager::GetInstance()->CreateBig(big_id, kDefaultBigParams);
-
- EXPECT_CALL(
- *big_callbacks_,
- OnBigEvent(bluetooth::hci::iso_manager::kIsoEventBigOnTerminateCmpl, _))
- .WillOnce([&evt](uint8_t type, void* data) {
- evt =
- *static_cast<bluetooth::hci::iso_manager::big_terminate_cmpl_evt*>(
- data);
- return 0;
- });
-
- IsoManager::GetInstance()->TerminateBig(big_id, reason);
- ASSERT_EQ(evt.big_id, big_id);
- ASSERT_EQ(evt.reason, reason);
-}
-
-TEST_F(IsoManagerTest, SetupIsoDataPathValid) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
- IsoManager::GetInstance()->CreateBig(volatile_test_big_params_evt_.big_id,
- kDefaultBigParams);
-
- // Establish all CISes before setting up their data paths
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- bluetooth::hci::iso_manager::iso_data_path_params path_params =
- kDefaultIsoDataPathParams;
-
- // Setup data paths for all CISes
- path_params.data_path_dir =
- bluetooth::hci::iso_manager::kIsoDataPathDirectionIn;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- EXPECT_CALL(*cig_callbacks_,
- OnSetupIsoDataPath(HCI_SUCCESS, handle,
- volatile_test_cig_create_cmpl_evt_.cig_id))
- .Times(1)
- .RetiresOnSaturation();
-
- path_params.data_path_dir =
- (bluetooth::hci::iso_manager::kIsoDataPathDirectionIn + handle) % 2;
-
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
- }
-
- // Setup data paths for all BISes
- path_params.data_path_dir =
- bluetooth::hci::iso_manager::kIsoDataPathDirectionOut;
- for (auto& handle : volatile_test_big_params_evt_.conn_handles) {
- std::cerr << "setting up BIS data path on conn_hdl: " << int{handle};
- EXPECT_CALL(*big_callbacks_,
- OnSetupIsoDataPath(HCI_SUCCESS, handle,
- volatile_test_big_params_evt_.big_id))
- .Times(1)
- .RetiresOnSaturation();
-
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
- }
-}
-
-TEST_F(IsoManagerTest, SetupIsoDataPathTwice) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- // Establish CISes
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- // Setup data paths for all CISes twice
- bluetooth::hci::iso_manager::iso_data_path_params path_params =
- kDefaultIsoDataPathParams;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
- // Should be possible to reconfigure
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
- }
-
- IsoManager::GetInstance()->CreateBig(volatile_test_big_params_evt_.big_id,
- kDefaultBigParams);
- // Setup data paths for all BISes twice
- for (auto& handle : volatile_test_big_params_evt_.conn_handles) {
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
- // Should be possible to reconfigure
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
- }
-}
-
-TEST_F(IsoManagerTest, SetupIsoDataPathInvalidStatus) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
- IsoManager::GetInstance()->CreateBig(volatile_test_big_params_evt_.big_id,
- kDefaultBigParams);
-
- // Establish all CISes before setting up their data paths
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- bluetooth::hci::iso_manager::iso_data_path_params path_params =
- kDefaultIsoDataPathParams;
-
- uint8_t setup_datapath_rsp_status = HCI_SUCCESS;
- ON_CALL(hcic_interface_, SetupIsoDataPath)
- .WillByDefault([&setup_datapath_rsp_status](
- uint16_t iso_handle, uint8_t, uint8_t, uint8_t,
- uint16_t, uint16_t, uint32_t, std::vector<uint8_t>,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::vector<uint8_t> buf(3);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, setup_datapath_rsp_status);
- UINT16_TO_STREAM(p, iso_handle);
-
- std::move(cb).Run(buf.data(), buf.size());
- });
-
- // Try to setup data paths for all CISes
- path_params.data_path_dir =
- bluetooth::hci::iso_manager::kIsoDataPathDirectionIn;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- // Mock the response with status != HCI_SUCCESS
- EXPECT_CALL(*cig_callbacks_,
- OnSetupIsoDataPath(0x11, handle,
- volatile_test_cig_create_cmpl_evt_.cig_id))
- .Times(1)
- .RetiresOnSaturation();
- setup_datapath_rsp_status = 0x11;
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
-
- // It should be possible to retry on the same handle after the first
- // failure
- EXPECT_CALL(*cig_callbacks_,
- OnSetupIsoDataPath(HCI_SUCCESS, handle,
- volatile_test_cig_create_cmpl_evt_.cig_id))
- .Times(1)
- .RetiresOnSaturation();
- setup_datapath_rsp_status = HCI_SUCCESS;
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
- }
-
- // Try to setup data paths for all BISes
- path_params.data_path_dir =
- bluetooth::hci::iso_manager::kIsoDataPathDirectionOut;
- for (auto& handle : volatile_test_big_params_evt_.conn_handles) {
- EXPECT_CALL(
- *big_callbacks_,
- OnSetupIsoDataPath(0x11, handle, volatile_test_big_params_evt_.big_id))
- .Times(1)
- .RetiresOnSaturation();
- setup_datapath_rsp_status = 0x11;
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
-
- EXPECT_CALL(*big_callbacks_,
- OnSetupIsoDataPath(HCI_SUCCESS, handle,
- volatile_test_big_params_evt_.big_id))
- .Times(1)
- .RetiresOnSaturation();
- setup_datapath_rsp_status = HCI_SUCCESS;
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
- }
-}
-
-TEST_F(IsoManagerTest, RemoveIsoDataPathValid) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
- IsoManager::GetInstance()->CreateBig(volatile_test_big_params_evt_.big_id,
- kDefaultBigParams);
-
- // Establish all CISes before setting up their data paths
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- bluetooth::hci::iso_manager::iso_data_path_params path_params =
- kDefaultIsoDataPathParams;
-
- // Setup and remove data paths for all CISes
- path_params.data_path_dir =
- bluetooth::hci::iso_manager::kIsoDataPathDirectionIn;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
-
- EXPECT_CALL(*cig_callbacks_,
- OnRemoveIsoDataPath(HCI_SUCCESS, handle,
- volatile_test_cig_create_cmpl_evt_.cig_id))
- .Times(1)
- .RetiresOnSaturation();
- IsoManager::GetInstance()->RemoveIsoDataPath(handle,
- path_params.data_path_dir);
- }
-
- // Setup and remove data paths for all BISes
- path_params.data_path_dir =
- bluetooth::hci::iso_manager::kIsoDataPathDirectionOut;
- for (auto& handle : volatile_test_big_params_evt_.conn_handles) {
- std::cerr << "setting up BIS data path on conn_hdl: " << int{handle};
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
-
- EXPECT_CALL(*big_callbacks_,
- OnRemoveIsoDataPath(HCI_SUCCESS, handle,
- volatile_test_big_params_evt_.big_id))
- .Times(1)
- .RetiresOnSaturation();
- IsoManager::GetInstance()->RemoveIsoDataPath(handle,
- path_params.data_path_dir);
- }
-}
-
-TEST_F(IsoManagerDeathTest, RemoveIsoDataPathNoSuchPath) {
- // Check on CIS
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
- uint16_t iso_handle = volatile_test_cig_create_cmpl_evt_.conn_handles[0];
- ASSERT_EXIT(
- IsoManager::GetInstance()->RemoveIsoDataPath(
- iso_handle, bluetooth::hci::iso_manager::kIsoDataPathDirectionOut),
- ::testing::KilledBySignal(SIGABRT), "path not set");
-
- IsoManager::GetInstance()->EstablishCis({.conn_pairs = {{iso_handle, 1}}});
- ASSERT_EXIT(
- IsoManager::GetInstance()->RemoveIsoDataPath(
- iso_handle, bluetooth::hci::iso_manager::kIsoDataPathDirectionOut),
- ::testing::KilledBySignal(SIGABRT), "path not set");
-
- // Check on BIS
- iso_handle = volatile_test_big_params_evt_.conn_handles[0];
- IsoManager::GetInstance()->CreateBig(volatile_test_big_params_evt_.big_id,
- kDefaultBigParams);
- ASSERT_EXIT(
- IsoManager::GetInstance()->RemoveIsoDataPath(
- iso_handle, bluetooth::hci::iso_manager::kIsoDataPathDirectionOut),
- ::testing::KilledBySignal(SIGABRT), "path not set");
-}
-
-TEST_F(IsoManagerDeathTest, RemoveIsoDataPathTwice) {
- // Check on CIS
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
- uint16_t iso_handle = volatile_test_cig_create_cmpl_evt_.conn_handles[0];
- IsoManager::GetInstance()->EstablishCis({.conn_pairs = {{iso_handle, 1}}});
- IsoManager::GetInstance()->SetupIsoDataPath(iso_handle,
- kDefaultIsoDataPathParams);
- IsoManager::GetInstance()->RemoveIsoDataPath(
- iso_handle, kDefaultIsoDataPathParams.data_path_dir);
- ASSERT_EXIT(
- IsoManager::GetInstance()->RemoveIsoDataPath(
- iso_handle, bluetooth::hci::iso_manager::kIsoDataPathDirectionOut),
- ::testing::KilledBySignal(SIGABRT), "path not set");
-
- // Check on BIS
- iso_handle = volatile_test_big_params_evt_.conn_handles[0];
- IsoManager::GetInstance()->CreateBig(volatile_test_big_params_evt_.big_id,
- kDefaultBigParams);
- IsoManager::GetInstance()->SetupIsoDataPath(iso_handle,
- kDefaultIsoDataPathParams);
- IsoManager::GetInstance()->RemoveIsoDataPath(
- iso_handle, kDefaultIsoDataPathParams.data_path_dir);
- ASSERT_EXIT(
- IsoManager::GetInstance()->RemoveIsoDataPath(
- iso_handle, bluetooth::hci::iso_manager::kIsoDataPathDirectionOut),
- ::testing::KilledBySignal(SIGABRT), "path not set");
-}
-
-// Check if HCI status other than HCI_SUCCESS is being propagated to the caller
-TEST_F(IsoManagerTest, RemoveIsoDataPathInvalidStatus) {
- // Mock invalid status response
- uint8_t remove_datapath_rsp_status = 0x12;
- ON_CALL(hcic_interface_, RemoveIsoDataPath)
- .WillByDefault([&remove_datapath_rsp_status](
- uint16_t iso_handle, uint8_t data_path_dir,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- std::vector<uint8_t> buf(3);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, remove_datapath_rsp_status);
- UINT16_TO_STREAM(p, iso_handle);
-
- std::move(cb).Run(buf.data(), buf.size());
- });
-
- // Check on CIS
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
- uint16_t iso_handle = volatile_test_cig_create_cmpl_evt_.conn_handles[0];
- IsoManager::GetInstance()->EstablishCis({.conn_pairs = {{iso_handle, 1}}});
- IsoManager::GetInstance()->SetupIsoDataPath(iso_handle,
- kDefaultIsoDataPathParams);
-
- EXPECT_CALL(*cig_callbacks_,
- OnRemoveIsoDataPath(remove_datapath_rsp_status, iso_handle,
- volatile_test_cig_create_cmpl_evt_.cig_id))
- .Times(1);
- IsoManager::GetInstance()->RemoveIsoDataPath(
- iso_handle, kDefaultIsoDataPathParams.data_path_dir);
-
- // Check on BIS
- iso_handle = volatile_test_big_params_evt_.conn_handles[0];
- IsoManager::GetInstance()->CreateBig(volatile_test_big_params_evt_.big_id,
- kDefaultBigParams);
- IsoManager::GetInstance()->SetupIsoDataPath(iso_handle,
- kDefaultIsoDataPathParams);
-
- EXPECT_CALL(*big_callbacks_,
- OnRemoveIsoDataPath(remove_datapath_rsp_status, iso_handle,
- volatile_test_big_params_evt_.big_id))
- .Times(1);
- IsoManager::GetInstance()->RemoveIsoDataPath(
- iso_handle, kDefaultIsoDataPathParams.data_path_dir);
-}
-
-TEST_F(IsoManagerTest, SendIsoDataCigValid) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- bluetooth::hci::iso_manager::iso_data_path_params path_params =
- kDefaultIsoDataPathParams;
- path_params.data_path_dir =
- bluetooth::hci::iso_manager::kIsoDataPathDirectionOut;
- IsoManager::GetInstance()->SetupIsoDataPath(handle, path_params);
-
- for (uint8_t num_pkts = 2; num_pkts != 0; num_pkts--) {
- constexpr uint8_t data_len = 108;
-
- EXPECT_CALL(bte_interface_, HciSend)
- .WillOnce([handle, data_len](BT_HDR* p_msg, uint16_t event) {
- uint8_t* p = p_msg->data;
- uint16_t msg_handle;
- uint16_t iso_load_len;
-
- ASSERT_TRUE((event & MSG_STACK_TO_HC_HCI_ISO) != 0);
- ASSERT_NE(p_msg, nullptr);
- ASSERT_EQ(p_msg->len, data_len + ((p_msg->layer_specific &
- BT_ISO_HDR_CONTAINS_TS)
- ? 12
- : 8));
-
- // Verify packet internals
- STREAM_TO_UINT16(msg_handle, p);
- ASSERT_EQ(msg_handle, handle);
-
- STREAM_TO_UINT16(iso_load_len, p);
- ASSERT_EQ(
- iso_load_len,
- data_len +
- ((p_msg->layer_specific & BT_ISO_HDR_CONTAINS_TS) ? 8 : 4));
-
- if (p_msg->layer_specific & BT_ISO_HDR_CONTAINS_TS) {
- STREAM_SKIP_UINT16(p); // skip ts LSB halfword
- STREAM_SKIP_UINT16(p); // skip ts MSB halfword
- }
- STREAM_SKIP_UINT16(p); // skip seq_nb
-
- uint16_t msg_data_len;
- STREAM_TO_UINT16(msg_data_len, p);
- ASSERT_EQ(msg_data_len, data_len);
- })
- .RetiresOnSaturation();
-
- std::vector<uint8_t> data_vec(data_len, 0);
- IsoManager::GetInstance()->SendIsoData(handle, data_vec.data(),
- data_vec.size());
- }
- }
-}
-
-TEST_F(IsoManagerTest, SendIsoDataBigValid) {
- IsoManager::GetInstance()->CreateBig(volatile_test_big_params_evt_.big_id,
- kDefaultBigParams);
-
- for (auto& handle : volatile_test_big_params_evt_.conn_handles) {
- IsoManager::GetInstance()->SetupIsoDataPath(handle,
- kDefaultIsoDataPathParams);
- for (uint8_t num_pkts = 2; num_pkts != 0; num_pkts--) {
- constexpr uint8_t data_len = 108;
-
- EXPECT_CALL(bte_interface_, HciSend)
- .WillOnce([handle, data_len](BT_HDR* p_msg, uint16_t event) {
- uint8_t* p = p_msg->data;
- uint16_t msg_handle;
- uint16_t iso_load_len;
-
- ASSERT_TRUE((event & MSG_STACK_TO_HC_HCI_ISO) != 0);
- ASSERT_NE(p_msg, nullptr);
- ASSERT_EQ(p_msg->len, data_len + ((p_msg->layer_specific &
- BT_ISO_HDR_CONTAINS_TS)
- ? 12
- : 8));
-
- // Verify packet internals
- STREAM_TO_UINT16(msg_handle, p);
- ASSERT_EQ(msg_handle, handle);
-
- STREAM_TO_UINT16(iso_load_len, p);
- ASSERT_EQ(
- iso_load_len,
- data_len +
- ((p_msg->layer_specific & BT_ISO_HDR_CONTAINS_TS) ? 8 : 4));
-
- uint16_t msg_data_len;
- uint16_t msg_dummy;
- if (p_msg->layer_specific & BT_ISO_HDR_CONTAINS_TS) {
- STREAM_TO_UINT16(msg_dummy, p); // skip ts LSB halfword
- STREAM_TO_UINT16(msg_dummy, p); // skip ts MSB halfword
- }
- STREAM_TO_UINT16(msg_dummy, p); // skip seq_nb
-
- STREAM_TO_UINT16(msg_data_len, p);
- ASSERT_EQ(msg_data_len, data_len);
- })
- .RetiresOnSaturation();
-
- std::vector<uint8_t> data_vec(data_len, 0);
- IsoManager::GetInstance()->SendIsoData(handle, data_vec.data(),
- data_vec.size());
- }
- }
-}
-
-TEST_F(IsoManagerTest, SendIsoDataNoCredits) {
- uint8_t num_buffers = controller_interface_.GetIsoBufferCount();
- std::vector<uint8_t> data_vec(108, 0);
-
- // Check on CIG
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- IsoManager::GetInstance()->SetupIsoDataPath(
- volatile_test_cig_create_cmpl_evt_.conn_handles[0],
- kDefaultIsoDataPathParams);
-
- /* Try sending twice as much data as we can ignoring the credit limits and
- * expect the redundant packets to be ignored and not propagated down to the
- * HCI.
- */
- EXPECT_CALL(bte_interface_, HciSend).Times(num_buffers).RetiresOnSaturation();
- for (uint8_t i = 0; i < (2 * num_buffers); i++) {
- IsoManager::GetInstance()->SendIsoData(
- volatile_test_cig_create_cmpl_evt_.conn_handles[0], data_vec.data(),
- data_vec.size());
- }
-
- // Return all credits for this one handle
- uint8_t mock_rsp[5];
- uint8_t* p = mock_rsp;
- UINT8_TO_STREAM(p, 1);
- UINT16_TO_STREAM(p, volatile_test_cig_create_cmpl_evt_.conn_handles[0]);
- UINT16_TO_STREAM(p, num_buffers);
- IsoManager::GetInstance()->HandleNumComplDataPkts(mock_rsp, sizeof(mock_rsp));
-
- // Check on BIG
- IsoManager::GetInstance()->CreateBig(volatile_test_big_params_evt_.big_id,
- kDefaultBigParams);
- IsoManager::GetInstance()->SetupIsoDataPath(
- volatile_test_big_params_evt_.conn_handles[0], kDefaultIsoDataPathParams);
-
- /* Try sending twice as much data as we can ignoring the credit limits and
- * expect the redundant packets to be ignored and not propagated down to the
- * HCI.
- */
- EXPECT_CALL(bte_interface_, HciSend).Times(num_buffers);
- for (uint8_t i = 0; i < (2 * num_buffers); i++) {
- IsoManager::GetInstance()->SendIsoData(
- volatile_test_big_params_evt_.conn_handles[0], data_vec.data(),
- data_vec.size());
- }
-}
-
-TEST_F(IsoManagerTest, SendIsoDataCreditsReturned) {
- uint8_t num_buffers = controller_interface_.GetIsoBufferCount();
- std::vector<uint8_t> data_vec(108, 0);
-
- // Check on CIG
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- IsoManager::GetInstance()->SetupIsoDataPath(
- volatile_test_cig_create_cmpl_evt_.conn_handles[0],
- kDefaultIsoDataPathParams);
-
- /* Try sending twice as much data as we can, ignoring the credits limit and
- * expect the redundant packets to be ignored and not propagated down to the
- * HCI.
- */
- EXPECT_CALL(bte_interface_, HciSend).Times(num_buffers).RetiresOnSaturation();
- for (uint8_t i = 0; i < (2 * num_buffers); i++) {
- IsoManager::GetInstance()->SendIsoData(
- volatile_test_cig_create_cmpl_evt_.conn_handles[0], data_vec.data(),
- data_vec.size());
- }
-
- // Return all credits for this one handle
- uint8_t mock_rsp[5];
- uint8_t* p = mock_rsp;
- UINT8_TO_STREAM(p, 1);
- UINT16_TO_STREAM(p, volatile_test_cig_create_cmpl_evt_.conn_handles[0]);
- UINT16_TO_STREAM(p, num_buffers);
- IsoManager::GetInstance()->HandleNumComplDataPkts(mock_rsp, sizeof(mock_rsp));
-
- // Expect some more events go down the HCI
- EXPECT_CALL(bte_interface_, HciSend).Times(num_buffers).RetiresOnSaturation();
- for (uint8_t i = 0; i < (2 * num_buffers); i++) {
- IsoManager::GetInstance()->SendIsoData(
- volatile_test_cig_create_cmpl_evt_.conn_handles[0], data_vec.data(),
- data_vec.size());
- }
-
- // Return all credits for this one handle
- p = mock_rsp;
- UINT8_TO_STREAM(p, 1);
- UINT16_TO_STREAM(p, volatile_test_cig_create_cmpl_evt_.conn_handles[0]);
- UINT16_TO_STREAM(p, num_buffers);
- IsoManager::GetInstance()->HandleNumComplDataPkts(mock_rsp, sizeof(mock_rsp));
-
- // Check on BIG
- IsoManager::GetInstance()->CreateBig(volatile_test_big_params_evt_.big_id,
- kDefaultBigParams);
- IsoManager::GetInstance()->SetupIsoDataPath(
- volatile_test_big_params_evt_.conn_handles[0], kDefaultIsoDataPathParams);
-
- /* Try sending twice as much data as we can, ignoring the credits limit and
- * expect the redundant packets to be ignored and not propagated down to the
- * HCI.
- */
- EXPECT_CALL(bte_interface_, HciSend).Times(num_buffers).RetiresOnSaturation();
- for (uint8_t i = 0; i < (2 * num_buffers); i++) {
- IsoManager::GetInstance()->SendIsoData(
- volatile_test_big_params_evt_.conn_handles[0], data_vec.data(),
- data_vec.size());
- }
-
- // Return all credits for this one handle
- p = mock_rsp;
- UINT8_TO_STREAM(p, 1);
- UINT16_TO_STREAM(p, volatile_test_big_params_evt_.conn_handles[0]);
- UINT16_TO_STREAM(p, num_buffers);
- IsoManager::GetInstance()->HandleNumComplDataPkts(mock_rsp, sizeof(mock_rsp));
-
- // Expect some more events go down the HCI
- EXPECT_CALL(bte_interface_, HciSend).Times(num_buffers).RetiresOnSaturation();
- for (uint8_t i = 0; i < (2 * num_buffers); i++) {
- IsoManager::GetInstance()->SendIsoData(
- volatile_test_big_params_evt_.conn_handles[0], data_vec.data(),
- data_vec.size());
- }
-}
-
-TEST_F(IsoManagerDeathTest, SendIsoDataWithNoDataPath) {
- std::vector<uint8_t> data_vec(108, 0);
-
- // Check on CIG
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- bluetooth::hci::iso_manager::cis_establish_params params;
- for (auto& conn_handle : volatile_test_cig_create_cmpl_evt_.conn_handles) {
- params.conn_pairs.push_back({conn_handle, 1});
- }
- IsoManager::GetInstance()->EstablishCis(params);
-
- EXPECT_CALL(bte_interface_, HciSend).Times(0);
- ASSERT_EXIT(IsoManager::GetInstance()->SendIsoData(
- volatile_test_cig_create_cmpl_evt_.conn_handles[0],
- data_vec.data(), data_vec.size()),
- ::testing::KilledBySignal(SIGABRT), "Data path not set");
-
- // Check on BIG
- IsoManager::GetInstance()->CreateBig(volatile_test_big_params_evt_.big_id,
- kDefaultBigParams);
-
- EXPECT_CALL(bte_interface_, HciSend).Times(0);
- ASSERT_EXIT(IsoManager::GetInstance()->SendIsoData(
- volatile_test_big_params_evt_.conn_handles[0],
- data_vec.data(), data_vec.size()),
- ::testing::KilledBySignal(SIGABRT), "Data path not set");
-}
-
-TEST_F(IsoManagerDeathTest, SendIsoDataWithNoCigBigHandle) {
- std::vector<uint8_t> data_vec(108, 0);
- ASSERT_EXIT(IsoManager::GetInstance()->SendIsoData(134, data_vec.data(),
- data_vec.size()),
- ::testing::KilledBySignal(SIGABRT), "No such iso");
-}
-
-TEST_F(IsoManagerDeathTest, SendIsoDataWithNoCigConnected) {
- std::vector<uint8_t> data_vec(108, 0);
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- auto handle = volatile_test_cig_create_cmpl_evt_.conn_handles[0];
- ASSERT_EXIT(IsoManager::GetInstance()->SendIsoData(handle, data_vec.data(),
- data_vec.size()),
- ::testing::KilledBySignal(SIGABRT), "CIS not established");
-}
-
-TEST_F(IsoManagerTest, HandleDisconnectNoSuchHandle) {
- // Don't expect any callbacks when connection handle is not for ISO.
- EXPECT_CALL(*cig_callbacks_, OnCigEvent).Times(0);
- EXPECT_CALL(*cig_callbacks_, OnCisEvent).Times(0);
- EXPECT_CALL(*big_callbacks_, OnBigEvent).Times(0);
-
- IsoManager::GetInstance()->HandleDisconnect(123, 16);
-}
-
-TEST_F(IsoManagerTest, HandleDisconnectValidCig) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- auto handle = volatile_test_cig_create_cmpl_evt_.conn_handles[0];
- IsoManager::GetInstance()->EstablishCis({{{handle, 1}}});
-
- EXPECT_CALL(*big_callbacks_, OnBigEvent).Times(0);
- EXPECT_CALL(*cig_callbacks_, OnCigEvent).Times(0);
- EXPECT_CALL(*cig_callbacks_, OnCisEvent).Times(0);
-
- // Expect disconnect event exactly once
- EXPECT_CALL(*cig_callbacks_, OnCisEvent)
- .WillOnce([this, handle](uint8_t event_code, void* data) {
- ASSERT_EQ(event_code,
- bluetooth::hci::iso_manager::kIsoEventCisDisconnected);
- auto* event =
- static_cast<bluetooth::hci::iso_manager::cis_disconnected_evt*>(
- data);
- ASSERT_EQ(event->reason, 16);
- ASSERT_EQ(event->cig_id, volatile_test_cig_create_cmpl_evt_.cig_id);
- ASSERT_EQ(event->cis_conn_hdl, handle);
- });
-
- IsoManager::GetInstance()->HandleDisconnect(handle, 16);
-}
-
-TEST_F(IsoManagerTest, HandleDisconnectDisconnectedCig) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- auto handle = volatile_test_cig_create_cmpl_evt_.conn_handles[0];
- IsoManager::GetInstance()->EstablishCis({{{handle, 1}}});
-
- EXPECT_CALL(*big_callbacks_, OnBigEvent).Times(0);
- EXPECT_CALL(*cig_callbacks_, OnCigEvent).Times(0);
- EXPECT_CALL(*cig_callbacks_, OnCisEvent).Times(0);
-
- // Expect disconnect event exactly once
- EXPECT_CALL(
- *cig_callbacks_,
- OnCisEvent(bluetooth::hci::iso_manager::kIsoEventCisDisconnected, _))
- .Times(1)
- .RetiresOnSaturation();
- IsoManager::GetInstance()->HandleDisconnect(handle, 16);
-
- // This one was once connected - expect no events
- IsoManager::GetInstance()->HandleDisconnect(handle, 16);
-
- // This one was never connected - expect no events
- handle = volatile_test_cig_create_cmpl_evt_.conn_handles[1];
- IsoManager::GetInstance()->HandleDisconnect(handle, 16);
-}
-
-TEST_F(IsoManagerTest, HandleIsoData) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- auto handle = volatile_test_cig_create_cmpl_evt_.conn_handles[0];
- IsoManager::GetInstance()->EstablishCis({{{handle, 1}}});
-
- EXPECT_CALL(
- *cig_callbacks_,
- OnCisEvent(bluetooth::hci::iso_manager::kIsoEventCisDataAvailable, _))
- .Times(1);
-
- std::vector<uint8_t> dummy_msg(18);
- uint8_t* p = dummy_msg.data();
- UINT16_TO_STREAM(p, BT_EVT_TO_BTU_HCI_ISO);
- UINT16_TO_STREAM(p, 10); // .len
- UINT16_TO_STREAM(p, 0); // .offset
- UINT16_TO_STREAM(p, 0); // .layer_specific
- UINT16_TO_STREAM(p, handle);
- IsoManager::GetInstance()->HandleIsoData(dummy_msg.data());
-}
-
-/* This test case simulates HCI thread scheduling events on the main thread,
- * without knowing the we are already shutting down the stack and Iso Manager
- * is already stopped.
- */
-TEST_F(IsoManagerDeathTestNoCleanup, HandleLateArivingEventHandleIsoData) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- auto handle = volatile_test_cig_create_cmpl_evt_.conn_handles[0];
- IsoManager::GetInstance()->EstablishCis({{{handle, 1}}});
-
- // Stop iso manager before trying to call the HCI callbacks
- IsoManager::GetInstance()->Stop();
-
- EXPECT_CALL(
- *cig_callbacks_,
- OnCisEvent(bluetooth::hci::iso_manager::kIsoEventCisDataAvailable, _))
- .Times(0);
-
- // Expect no assert on this call - should be gracefully ignored
- std::vector<uint8_t> dummy_msg(18);
- uint8_t* p = dummy_msg.data();
- UINT16_TO_STREAM(p, BT_EVT_TO_BTU_HCI_ISO);
- UINT16_TO_STREAM(p, 10); // .len
- UINT16_TO_STREAM(p, 0); // .offset
- UINT16_TO_STREAM(p, 0); // .layer_specific
- UINT16_TO_STREAM(p, handle);
- IsoManager::GetInstance()->HandleIsoData(dummy_msg.data());
-}
-
-/* This test case simulates HCI thread scheduling events on the main thread,
- * without knowing the we are already shutting down the stack and Iso Manager
- * is already stopped.
- */
-TEST_F(IsoManagerDeathTestNoCleanup, HandleLateArivingEventHandleDisconnect) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- auto handle = volatile_test_cig_create_cmpl_evt_.conn_handles[0];
- IsoManager::GetInstance()->EstablishCis({{{handle, 1}}});
-
- // Stop iso manager before trying to call the HCI callbacks
- IsoManager::GetInstance()->Stop();
-
- // Expect no event when callback is being called on a stopped iso manager
- EXPECT_CALL(*cig_callbacks_, OnCisEvent).Times(0);
- // Expect no assert on this call - should be gracefully ignored
- IsoManager::GetInstance()->HandleDisconnect(handle, 16);
-}
-
-/* This test case simulates HCI thread scheduling events on the main thread,
- * without knowing the we are already shutting down the stack and Iso Manager
- * is already stopped.
- */
-TEST_F(IsoManagerDeathTestNoCleanup,
- HandleLateArivingEventHandleNumComplDataPkts) {
- uint8_t num_buffers = controller_interface_.GetIsoBufferCount();
-
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- auto handle = volatile_test_cig_create_cmpl_evt_.conn_handles[0];
- IsoManager::GetInstance()->EstablishCis({{{handle, 1}}});
-
- // Stop iso manager before trying to call the HCI callbacks
- IsoManager::GetInstance()->Stop();
-
- // Expect no assert on this call - should be gracefully ignored
- uint8_t mock_rsp[5];
- uint8_t* p = mock_rsp;
- UINT8_TO_STREAM(p, 1);
- UINT16_TO_STREAM(p, handle);
- UINT16_TO_STREAM(p, num_buffers);
- IsoManager::GetInstance()->HandleNumComplDataPkts(mock_rsp, sizeof(mock_rsp));
-}
-
-/* This test case simulates HCI thread scheduling events on the main thread,
- * without knowing the we are already shutting down the stack and Iso Manager
- * is already stopped.
- */
-TEST_F(IsoManagerDeathTestNoCleanup, HandleLateArivingEventHandleHciEvent) {
- const uint8_t big_id = 0x22;
-
- IsoManager::GetInstance()->CreateBig(big_id, kDefaultBigParams);
-
- // Stop iso manager before trying to call the HCI callbacks
- IsoManager::GetInstance()->Stop();
- EXPECT_CALL(
- *big_callbacks_,
- OnBigEvent(bluetooth::hci::iso_manager::kIsoEventBigOnTerminateCmpl, _))
- .Times(0);
-
- // Expect no assert on this call - should be gracefully ignored
- std::vector<uint8_t> buf(2);
- uint8_t* p = buf.data();
- UINT8_TO_STREAM(p, big_id);
- UINT8_TO_STREAM(p, 16); // Terminated by local host
- IsoManager::GetInstance()->HandleHciEvent(HCI_BLE_TERM_BIG_CPL_EVT,
- buf.data(), buf.size());
-}
-
-TEST_F(IsoManagerTest, HandleIsoDataSameSeqNb) {
- IsoManager::GetInstance()->CreateCig(
- volatile_test_cig_create_cmpl_evt_.cig_id, kDefaultCigParams);
-
- auto handle = volatile_test_cig_create_cmpl_evt_.conn_handles[0];
- IsoManager::GetInstance()->EstablishCis({{{handle, 1}}});
-
- EXPECT_CALL(
- *cig_callbacks_,
- OnCisEvent(bluetooth::hci::iso_manager::kIsoEventCisDataAvailable, _))
- .Times(2);
-
- std::vector<uint8_t> dummy_msg(18);
- uint8_t* p = dummy_msg.data();
- UINT16_TO_STREAM(p, BT_EVT_TO_BTU_HCI_ISO);
- UINT16_TO_STREAM(p, 10); // .len
- UINT16_TO_STREAM(p, 0); // .offset
- UINT16_TO_STREAM(p, 0); // .layer_specific
- UINT16_TO_STREAM(p, handle);
-
- IsoManager::GetInstance()->HandleIsoData(dummy_msg.data());
- IsoManager::GetInstance()->HandleIsoData(dummy_msg.data());
-}
diff --git a/stack/test/common/mock_acl.cc b/stack/test/common/mock_acl.cc
deleted file mode 100644
index ed0095f4e..000000000
--- a/stack/test/common/mock_acl.cc
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:14
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#define LOG_TAG "bt_shim"
-#include "gd/common/init_flags.h"
-#include "main/shim/entry.h"
-#include "main/shim/shim.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void acl_add_to_ignore_auto_connect_after_disconnect(
- const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-
-bool acl_check_and_clear_ignore_auto_connect_after_disconnect(
- const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-
-void acl_clear_all_ignore_auto_connect_after_disconnect() {
- mock_function_count_map[__func__]++;
-}
diff --git a/stack/test/common/mock_bta_dm_act.cc b/stack/test/common/mock_bta_dm_act.cc
deleted file mode 100644
index b7b39dbac..000000000
--- a/stack/test/common/mock_bta_dm_act.cc
+++ /dev/null
@@ -1,123 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:53
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "bta/dm/bta_dm_int.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void BTA_dm_acl_down(const RawAddress bd_addr, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void BTA_dm_acl_up(const RawAddress bd_addr, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void BTA_dm_notify_remote_features_complete(const RawAddress bd_addr) {
- mock_function_count_map[__func__]++;
-}
-
-void BTA_dm_on_hw_off() { mock_function_count_map[__func__]++; }
-void BTA_dm_on_hw_on() { mock_function_count_map[__func__]++; }
-void BTA_dm_report_role_change(const RawAddress bd_addr, tHCI_ROLE new_role,
- tHCI_STATUS hci_status) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_add_device(std::unique_ptr<tBTA_DM_API_ADD_DEVICE> msg) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_bond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_bond_cancel(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_ci_rmt_oob_act(std::unique_ptr<tBTA_DM_CI_RMT_OOB> msg) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_close_acl(const RawAddress& bd_addr, bool remove_dev,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_confirm(const RawAddress& bd_addr, bool accept) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_deinit_cb(void) { mock_function_count_map[__func__]++; }
-void bta_dm_disable() { mock_function_count_map[__func__]++; }
-void bta_dm_disc_result(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_disc_rmt_name(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_discover(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_free_sdp_db() { mock_function_count_map[__func__]++; }
-void bta_dm_init_cb(void) { mock_function_count_map[__func__]++; }
-void bta_dm_inq_cmpl(uint8_t num) { mock_function_count_map[__func__]++; }
-void bta_dm_pin_reply(std::unique_ptr<tBTA_DM_API_PIN_REPLY> msg) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_process_remove_device(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_queue_disc(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_queue_search(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_remove_device(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_rmt_name(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_search_cancel() { mock_function_count_map[__func__]++; }
-void bta_dm_search_cancel_cmpl() { mock_function_count_map[__func__]++; }
-void bta_dm_search_cancel_notify() { mock_function_count_map[__func__]++; }
-void bta_dm_execute_queued_request() { mock_function_count_map[__func__]++; }
-bool bta_dm_is_search_request_queued() {
- mock_function_count_map[__func__]++;
- return false;
-}
-void bta_dm_search_clear_queue() { mock_function_count_map[__func__]++; }
-void bta_dm_search_cmpl() { mock_function_count_map[__func__]++; }
-void bta_dm_search_result(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_search_start(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_set_dev_name(const std::vector<uint8_t>& name) {
- mock_function_count_map[__func__]++;
-}
diff --git a/stack/test/common/mock_bta_sys_conn.cc b/stack/test/common/mock_bta_sys_conn.cc
deleted file mode 100644
index cc5147b1c..000000000
--- a/stack/test/common/mock_bta_sys_conn.cc
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:17
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <stddef.h>
-#include "bt_common.h"
-#include "bta/include/bta_api.h"
-#include "bta/include/utl.h"
-#include "bta/sys/bta_sys.h"
-#include "bta/sys/bta_sys_int.h"
-#include "osi/include/osi.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void bta_sys_app_close(uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_app_open(uint8_t id, uint8_t app_id, const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_busy(uint8_t id, uint8_t app_id, const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_collision_register(uint8_t bta_id, tBTA_SYS_CONN_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_conn_close(uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_conn_open(uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_idle(uint8_t id, uint8_t app_id, const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_notify_collision(const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_notify_role_chg(const RawAddress& peer_addr, uint8_t new_role,
- tHCI_STATUS hci_status) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_pm_register(tBTA_SYS_CONN_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_rm_register(tBTA_SYS_CONN_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_role_chg_register(tBTA_SYS_CONN_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_sco_close(uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_sco_open(uint8_t id, uint8_t app_id, const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_sco_register(tBTA_SYS_CONN_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_sco_unuse(uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_sco_use(UNUSED_ATTR uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
diff --git a/stack/test/common/mock_btif_dm.cc b/stack/test/common/mock_btif_dm.cc
deleted file mode 100644
index d783ceada..000000000
--- a/stack/test/common/mock_btif_dm.cc
+++ /dev/null
@@ -1,163 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:51
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "bta/include/bta_api.h"
-#include "include/hardware/bluetooth.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
-
-struct uid_set_t;
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool btif_dm_pairing_is_busy() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool check_cod(const RawAddress* remote_bdaddr, uint32_t cod) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool check_cod_hid(const RawAddress* remote_bdaddr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool check_sdp_bl(const RawAddress* remote_bdaddr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bt_status_t btif_dm_get_adapter_property(bt_property_t* prop) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_in_execute_service_request(tBTA_SERVICE_ID service_id,
- bool b_enable) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-uint16_t btif_dm_get_connection_state(const RawAddress* bd_addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void BTIF_dm_disable() { mock_function_count_map[__func__]++; }
-void BTIF_dm_enable() { mock_function_count_map[__func__]++; }
-void BTIF_dm_on_hw_error() { mock_function_count_map[__func__]++; }
-void BTIF_dm_report_inquiry_status_change(uint8_t status) {
- mock_function_count_map[__func__]++;
-}
-void bte_dm_evt(tBTA_DM_SEC_EVT event, tBTA_DM_SEC* p_data) {
- mock_function_count_map[__func__]++;
-}
-void btif_ble_receiver_test(uint8_t rx_freq) {
- mock_function_count_map[__func__]++;
-}
-void btif_ble_test_end() { mock_function_count_map[__func__]++; }
-void btif_ble_transmitter_test(uint8_t tx_freq, uint8_t test_data_len,
- uint8_t packet_payload) {
- mock_function_count_map[__func__]++;
-}
-void btif_debug_bond_event_dump(int fd) { mock_function_count_map[__func__]++; }
-void btif_dm_ble_sec_req_evt(tBTA_DM_BLE_SEC_REQ* p_ble_req, bool is_consent) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_cancel_bond(const RawAddress bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_cancel_discovery(void) { mock_function_count_map[__func__]++; }
-void btif_dm_cleanup(void) { mock_function_count_map[__func__]++; }
-void btif_dm_create_bond(const RawAddress bd_addr, int transport) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_create_bond_out_of_band(const RawAddress bd_addr, int transport,
- const bt_oob_data_t p192_data,
- const bt_oob_data_t p256_data) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_enable_service(tBTA_SERVICE_ID service_id, bool enable) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_get_ble_local_keys(tBTA_DM_BLE_LOCAL_KEY_MASK* p_key_mask,
- Octet16* p_er,
- tBTA_BLE_LOCAL_ID_KEYS* p_id_keys) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_get_remote_services(RawAddress remote_addr, const int transport) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_hh_open_failed(RawAddress* bdaddr) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_init(uid_set_t* set) { mock_function_count_map[__func__]++; }
-void btif_dm_load_ble_local_keys(void) { mock_function_count_map[__func__]++; }
-void btif_dm_on_disable() { mock_function_count_map[__func__]++; }
-void btif_dm_pin_reply(const RawAddress bd_addr, uint8_t accept,
- uint8_t pin_len, bt_pin_code_t pin_code) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_proc_io_req(tBTM_AUTH_REQ* p_auth_req, bool is_orig) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_proc_io_rsp(UNUSED_ATTR const RawAddress& bd_addr,
- tBTM_IO_CAP io_cap, UNUSED_ATTR tBTM_OOB_DATA oob_data,
- tBTM_AUTH_REQ auth_req) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_read_energy_info() { mock_function_count_map[__func__]++; }
-void btif_dm_remove_ble_bonding_keys(void) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_remove_bond(const RawAddress bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_save_ble_bonding_keys(RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_set_oob_for_io_req(tBTM_OOB_DATA* p_has_oob_data) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_set_oob_for_le_io_req(const RawAddress& bd_addr,
- tBTM_OOB_DATA* p_has_oob_data,
- tBTM_LE_AUTH_REQ* p_auth_req) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_ssp_reply(const RawAddress bd_addr, bt_ssp_variant_t variant,
- uint8_t accept) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_start_discovery(void) { mock_function_count_map[__func__]++; }
-void btif_dm_update_ble_remote_properties(const RawAddress& bd_addr,
- BD_NAME bd_name,
- tBT_DEVICE_TYPE dev_type) {
- mock_function_count_map[__func__]++;
-}
-
-void btif_dm_proc_loc_oob(tBT_TRANSPORT transport, bool is_valid,
- const Octet16& c, const Octet16& r) {
- mock_function_count_map[__func__]++;
-}
diff --git a/stack/test/common/mock_btm_api_layer.cc b/stack/test/common/mock_btm_api_layer.cc
deleted file mode 100644
index 0b5c76fc8..000000000
--- a/stack/test/common/mock_btm_api_layer.cc
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.dk.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "mock_btm_api_layer.h"
-
-static bluetooth::manager::MockBtmApiInterface* btm_api_interface = nullptr;
-
-void bluetooth::manager::SetMockBtmApiInterface(
- MockBtmApiInterface* mock_btm_api_interface) {
- btm_api_interface = mock_btm_api_interface;
-}
-
-bool BTM_SetSecurityLevel(bool is_originator, const char* p_name,
- uint8_t service_id, uint16_t sec_level, uint16_t psm,
- uint32_t mx_proto_id, uint32_t mx_chan_id) {
- return btm_api_interface->SetSecurityLevel(is_originator, p_name, service_id,
- sec_level, psm, mx_proto_id,
- mx_chan_id);
-}
diff --git a/stack/test/common/mock_btm_api_layer.h b/stack/test/common/mock_btm_api_layer.h
deleted file mode 100644
index 0d7ee14c5..000000000
--- a/stack/test/common/mock_btm_api_layer.h
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.dk.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <gmock/gmock.h>
-
-#include "btm_api.h"
-
-namespace bluetooth {
-namespace manager {
-
-class BtmApiInterface {
- public:
- virtual bool SetSecurityLevel(bool is_originator, const char* p_name,
- uint8_t service_id, uint16_t sec_level,
- uint16_t psm, uint32_t mx_proto_id,
- uint32_t mx_chan_id) = 0;
- virtual uint8_t acl_link_role(const RawAddress& remote_bd_addr,
- tBT_TRANSPORT transport) = 0;
- virtual ~BtmApiInterface() = default;
-};
-
-class MockBtmApiInterface : public BtmApiInterface {
- public:
- MOCK_METHOD7(SetSecurityLevel,
- bool(bool is_originator, const char* p_name, uint8_t service_id,
- uint16_t sec_level, uint16_t psm, uint32_t mx_proto_id,
- uint32_t mx_chan_id));
- MOCK_METHOD2(acl_link_role, uint8_t(const RawAddress& remote_bd_addr,
- tBT_TRANSPORT transport));
-};
-
-/**
- * Set the {@link MockBtmApiInterface} for testing
- *
- * @param mock_btm_api_interface pointer to mock btm interface, could be null
- */
-void SetMockBtmApiInterface(MockBtmApiInterface* mock_btm_interface);
-
-} // namespace manager
-} // namespace bluetooth \ No newline at end of file
diff --git a/stack/test/common/mock_btm_layer.cc b/stack/test/common/mock_btm_layer.cc
index 7c3ae2ea0..1405c5544 100644
--- a/stack/test/common/mock_btm_layer.cc
+++ b/stack/test/common/mock_btm_layer.cc
@@ -17,8 +17,6 @@
******************************************************************************/
#include "mock_btm_layer.h"
-#include "stack/include/btm_client_interface.h"
-#include "stack/include/rfcdefs.h"
static bluetooth::manager::MockBtmSecurityInternalInterface*
btm_security_internal_interface = nullptr;
@@ -32,32 +30,16 @@ void btm_sec_abort_access_req(const RawAddress& bd_addr) {
btm_security_internal_interface->AbortAccessRequest(bd_addr);
}
-tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
- bool is_originator, uint16_t requirement,
+tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr, uint16_t psm,
+ bool is_originator, uint32_t mx_proto_id,
+ uint32_t mx_chan_id,
tBTM_SEC_CALLBACK* p_callback,
void* p_ref_data) {
return btm_security_internal_interface->MultiplexingProtocolAccessRequest(
- bd_addr, BT_PSM_RFCOMM, is_originator, BTM_SEC_PROTO_RFCOMM, 0,
- p_callback, p_ref_data);
+ bd_addr, psm, is_originator, mx_proto_id, mx_chan_id, p_callback,
+ p_ref_data);
}
-bool BTM_SetSecurityLevel(bool is_originator, const char* p_name,
- uint8_t service_id, uint16_t sec_level, uint16_t psm,
- uint32_t mx_proto_id, uint32_t mx_chan_id) {
- return true;
-}
-
-uint16_t BTM_GetMaxPacketSize(const RawAddress& addr) {
+uint16_t btm_get_max_packet_size(const RawAddress& addr) {
return RFCOMM_DEFAULT_MTU;
-}
-
-struct btm_client_interface_s btm_client_interface = {
- .peer =
- {
- .BTM_GetMaxPacketSize = BTM_GetMaxPacketSize,
- },
-};
-
-struct btm_client_interface_s& get_btm_client_interface() {
- return btm_client_interface;
-}
+} \ No newline at end of file
diff --git a/stack/test/common/mock_btm_layer.h b/stack/test/common/mock_btm_layer.h
index e8c3b457d..45f32d1dc 100644
--- a/stack/test/common/mock_btm_layer.h
+++ b/stack/test/common/mock_btm_layer.h
@@ -20,9 +20,6 @@
#include <gmock/gmock.h>
#include "btm_int.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/btm_status.h"
-#include "types/raw_address.h"
namespace bluetooth {
namespace manager {
@@ -57,4 +54,4 @@ void SetMockSecurityInternalInterface(
MockBtmSecurityInternalInterface* mock_btm_security_internal_interface);
} // namespace manager
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/stack/test/common/mock_btsnoop_module.cc b/stack/test/common/mock_btsnoop_module.cc
index 5bc656125..7a5c5ae88 100644
--- a/stack/test/common/mock_btsnoop_module.cc
+++ b/stack/test/common/mock_btsnoop_module.cc
@@ -21,22 +21,22 @@
static void capture(const BT_HDR*, bool) { /* do nothing */
}
-static void allowlist_l2c_channel(uint16_t, uint16_t,
+static void whitelist_l2c_channel(uint16_t, uint16_t,
uint16_t) { /* do nothing */
}
-static void allowlist_rfc_dlci(uint16_t, uint8_t) { /* do nothing */
+static void whitelist_rfc_dlci(uint16_t, uint8_t) { /* do nothing */
}
static void add_rfc_l2c_channel(uint16_t, uint16_t, uint16_t) { /* do nothing */
}
-static void clear_l2cap_allowlist(uint16_t, uint16_t,
+static void clear_l2cap_whitelist(uint16_t, uint16_t,
uint16_t) { /* do nothing */
}
-static const btsnoop_t fake_snoop = {capture, allowlist_l2c_channel,
- allowlist_rfc_dlci, add_rfc_l2c_channel,
- clear_l2cap_allowlist};
+static const btsnoop_t fake_snoop = {capture, whitelist_l2c_channel,
+ whitelist_rfc_dlci, add_rfc_l2c_channel,
+ clear_l2cap_whitelist};
const btsnoop_t* btsnoop_get_interface() { return &fake_snoop; }
diff --git a/stack/test/common/mock_btu_layer.cc b/stack/test/common/mock_btu_layer.cc
index cc9ef53c7..6d7abe943 100644
--- a/stack/test/common/mock_btu_layer.cc
+++ b/stack/test/common/mock_btu_layer.cc
@@ -16,6 +16,6 @@
*
******************************************************************************/
-#include "common/message_loop_thread.h"
+#include <base/message_loop/message_loop.h>
-bluetooth::common::MessageLoopThread* get_main_thread() { return nullptr; }
+base::MessageLoop* get_main_message_loop() { return nullptr; } \ No newline at end of file
diff --git a/stack/test/common/mock_controller.cc b/stack/test/common/mock_controller.cc
deleted file mode 100644
index 5083425ab..000000000
--- a/stack/test/common/mock_controller.cc
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "mock_controller.h"
-
-#include "device/include/controller.h"
-
-static controller::MockControllerInterface* controller_interface = nullptr;
-
-void controller::SetMockControllerInterface(
- MockControllerInterface* interface) {
- controller_interface = interface;
-}
-
-uint16_t get_iso_data_size(void) {
- return controller_interface->GetIsoDataSize();
-}
-
-uint8_t get_iso_buffer_count(void) {
- return controller_interface->GetIsoBufferCount();
-}
-uint16_t get_acl_data_size_ble(void) {
- return controller_interface->GetAclDataSizeBle();
-}
-
-const controller_t* controller_get_interface() {
- static controller_t* controller_instance = new controller_t();
-
- controller_instance->get_iso_data_size = &get_iso_data_size;
- controller_instance->get_iso_buffer_count = &get_iso_buffer_count;
- controller_instance->get_acl_data_size_ble = &get_acl_data_size_ble;
-
- return controller_instance;
-}
diff --git a/stack/test/common/mock_controller.h b/stack/test/common/mock_controller.h
deleted file mode 100644
index 137ca2bcb..000000000
--- a/stack/test/common/mock_controller.h
+++ /dev/null
@@ -1,43 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <base/callback.h>
-#include <gmock/gmock.h>
-
-#include "hcimsgs.h"
-
-namespace controller {
-class ControllerInterface {
- public:
- virtual uint8_t GetIsoBufferCount(void) = 0;
- virtual uint16_t GetIsoDataSize(void) = 0;
- virtual uint16_t GetAclDataSizeBle(void) = 0;
-
- virtual ~ControllerInterface() = default;
-};
-
-class MockControllerInterface : public ControllerInterface {
- public:
- MOCK_METHOD((uint8_t), GetIsoBufferCount, (), (override));
- MOCK_METHOD((uint16_t), GetIsoDataSize, (), (override));
- MOCK_METHOD((uint16_t), GetAclDataSizeBle, (), (override));
-};
-
-void SetMockControllerInterface(
- MockControllerInterface* mock_controller_interface);
-} // namespace controller
diff --git a/stack/test/common/mock_eatt.cc b/stack/test/common/mock_eatt.cc
deleted file mode 100644
index c0cfc2413..000000000
--- a/stack/test/common/mock_eatt.cc
+++ /dev/null
@@ -1,143 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com. Represented by EHIMA -
- * www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "mock_eatt.h"
-
-MockEattExtension* mock_pimpl_;
-MockEattExtension* MockEattExtension::GetInstance() {
- bluetooth::eatt::EattExtension::GetInstance();
- return mock_pimpl_;
-}
-
-namespace bluetooth {
-namespace eatt {
-
-struct EattExtension::impl : public MockEattExtension {
- impl() = default;
- ~impl() = default;
- bool IsRunning() { return mock_pimpl_ ? true : false; }
-};
-
-void EattExtension::AddFromStorage(const RawAddress& bd_addr) {}
-
-EattExtension::EattExtension() : pimpl_(std::make_unique<impl>()) {}
-
-bool EattExtension::IsEattSupportedByPeer(const RawAddress& bd_addr) {
- return pimpl_->IsEattSupportedByPeer(bd_addr);
-}
-
-void EattExtension::Connect(const RawAddress& bd_addr) {
- pimpl_->Connect(bd_addr);
-}
-
-void EattExtension::Disconnect(const RawAddress& bd_addr) {
- pimpl_->Disconnect(bd_addr);
-}
-
-void EattExtension::Reconfigure(const RawAddress& bd_addr, uint16_t cid,
- uint16_t mtu) {
- pimpl_->Reconfigure(bd_addr, cid, mtu);
-}
-void EattExtension::ReconfigureAll(const RawAddress& bd_addr, uint16_t mtu) {
- pimpl_->ReconfigureAll(bd_addr, mtu);
-}
-
-EattChannel* EattExtension::FindEattChannelByCid(const RawAddress& bd_addr,
- uint16_t cid) {
- return pimpl_->FindEattChannelByCid(bd_addr, cid);
-}
-
-EattChannel* EattExtension::FindEattChannelByTransId(const RawAddress& bd_addr,
- uint32_t trans_id) {
- return pimpl_->FindEattChannelByTransId(bd_addr, trans_id);
-}
-
-bool EattExtension::IsIndicationPending(const RawAddress& bd_addr,
- uint16_t indication_handle) {
- return pimpl_->IsIndicationPending(bd_addr, indication_handle);
-}
-
-EattChannel* EattExtension::GetChannelAvailableForIndication(
- const RawAddress& bd_addr) {
- return pimpl_->GetChannelAvailableForIndication(bd_addr);
-}
-
-void EattExtension::FreeGattResources(const RawAddress& bd_addr) {
- pimpl_->FreeGattResources(bd_addr);
-}
-
-bool EattExtension::IsOutstandingMsgInSendQueue(const RawAddress& bd_addr) {
- return pimpl_->IsOutstandingMsgInSendQueue(bd_addr);
-}
-
-EattChannel* EattExtension::GetChannelWithQueuedData(
- const RawAddress& bd_addr) {
- return pimpl_->GetChannelWithQueuedData(bd_addr);
-}
-
-EattChannel* EattExtension::GetChannelAvailableForClientRequest(
- const RawAddress& bd_addr) {
- return pimpl_->GetChannelAvailableForClientRequest(bd_addr);
-}
-
-/* Start stop GATT indication timer per CID */
-void EattExtension::StartIndicationConfirmationTimer(const RawAddress& bd_addr,
- uint16_t cid) {
- pimpl_->StartIndicationConfirmationTimer(bd_addr, cid);
-}
-
-void EattExtension::StopIndicationConfirmationTimer(const RawAddress& bd_addr,
- uint16_t cid) {
- pimpl_->StopIndicationConfirmationTimer(bd_addr, cid);
-}
-
-/* Start stop application indication timeout */
-void EattExtension::StartAppIndicationTimer(const RawAddress& bd_addr,
- uint16_t cid) {
- pimpl_->StartAppIndicationTimer(bd_addr, cid);
-}
-
-void EattExtension::StopAppIndicationTimer(const RawAddress& bd_addr,
- uint16_t cid) {
- pimpl_->StopAppIndicationTimer(bd_addr, cid);
-}
-
-void EattExtension::Start() {
- // It is needed here as IsoManager which is a singleton creates it, but in
- // this mock we want to destroy and recreate the mock on each test case.
- if (!pimpl_) {
- pimpl_ = std::make_unique<impl>();
- }
-
- mock_pimpl_ = pimpl_.get();
- pimpl_->Start();
-}
-
-void EattExtension::Stop() {
- // It is needed here as IsoManager which is a singleton creates it, but in
- // this mock we want to destroy and recreate the mock on each test case.
- if (pimpl_) {
- pimpl_->Stop();
- pimpl_.reset();
- }
-
- mock_pimpl_ = nullptr;
-}
-
-EattExtension::~EattExtension() = default;
-} // namespace eatt
-} // namespace bluetooth
diff --git a/stack/test/common/mock_eatt.h b/stack/test/common/mock_eatt.h
deleted file mode 100644
index 9875c7bb4..000000000
--- a/stack/test/common/mock_eatt.h
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <gmock/gmock.h>
-
-#include "stack/eatt/eatt.h"
-
-using bluetooth::eatt::EattChannel;
-using bluetooth::eatt::EattExtension;
-
-class MockEattExtension : public EattExtension {
- public:
- MockEattExtension() = default;
- ~MockEattExtension() override = default;
-
- static MockEattExtension* GetInstance();
-
- MOCK_METHOD((void), Connect, (const RawAddress& bd_addr));
- MOCK_METHOD((void), Disconnect, (const RawAddress& bd_addr));
- MOCK_METHOD((void), Reconfigure,
- (const RawAddress& bd_addr, uint16_t cid, uint16_t mtu));
- MOCK_METHOD((void), ReconfigureAll,
- (const RawAddress& bd_addr, uint16_t mtu));
-
- MOCK_METHOD((bool), IsEattSupportedByPeer, (const RawAddress& bd_addr));
- MOCK_METHOD((EattChannel*), FindEattChannelByCid,
- (const RawAddress& bd_addr, uint16_t cid));
- MOCK_METHOD((EattChannel*), FindEattChannelByTransId,
- (const RawAddress& bd_addr, uint32_t trans_id));
- MOCK_METHOD((bool), IsIndicationPending,
- (const RawAddress& bd_addr, uint16_t indication_handle));
- MOCK_METHOD((EattChannel*), GetChannelAvailableForIndication,
- (const RawAddress& bd_addr));
- MOCK_METHOD((void), FreeGattResources, (const RawAddress& bd_addr));
- MOCK_METHOD((bool), IsOutstandingMsgInSendQueue, (const RawAddress& bd_addr));
- MOCK_METHOD((EattChannel*), GetChannelWithQueuedData,
- (const RawAddress& bd_addr));
- MOCK_METHOD((EattChannel*), GetChannelAvailableForClientRequest,
- (const RawAddress& bd_addr));
- MOCK_METHOD((void), StartIndicationConfirmationTimer,
- (const RawAddress& bd_addr, uint16_t cid));
- MOCK_METHOD((void), StopIndicationConfirmationTimer,
- (const RawAddress& bd_addr, uint16_t cid));
-
- MOCK_METHOD((void), StartAppIndicationTimer,
- (const RawAddress& bd_addr, uint16_t cid));
- MOCK_METHOD((void), StopAppIndicationTimer,
- (const RawAddress& bd_addr, uint16_t cid));
-
- MOCK_METHOD((void), Start, ());
- MOCK_METHOD((void), Stop, ());
-
- private:
- DISALLOW_COPY_AND_ASSIGN(MockEattExtension);
-};
diff --git a/stack/test/common/mock_gap_gap_ble.cc b/stack/test/common/mock_gap_gap_ble.cc
deleted file mode 100644
index 4c48167c5..000000000
--- a/stack/test/common/mock_gap_gap_ble.cc
+++ /dev/null
@@ -1,50 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:6
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "stack/include/gap_api.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool GAP_BleCancelReadPeerDevName(const RawAddress& peer_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool GAP_BleReadPeerDevName(const RawAddress& peer_bda,
- tGAP_BLE_CMPL_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool GAP_BleReadPeerPrefConnParams(const RawAddress& peer_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-void GAP_BleAttrDBUpdate(uint16_t attr_uuid, tGAP_BLE_ATTR_VALUE* p_value) {
- mock_function_count_map[__func__]++;
-}
-void gap_attr_db_init(void) { mock_function_count_map[__func__]++; }
diff --git a/stack/test/common/mock_gatt_connection_manager.cc b/stack/test/common/mock_gatt_connection_manager.cc
deleted file mode 100644
index 9ce6b8584..000000000
--- a/stack/test/common/mock_gatt_connection_manager.cc
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:4
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/callback.h>
-#include <base/location.h>
-#include <base/logging.h>
-#include <map>
-#include <memory>
-#include <set>
-#include "internal_include/bt_trace.h"
-#include "main/shim/shim.h"
-#include "osi/include/alarm.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_ble_bgconn.h"
-#include "stack/gatt/connection_manager.h"
-#include "stack/include/l2c_api.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool connection_manager::direct_connect_add(uint8_t app_id,
- const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool connection_manager::direct_connect_remove(uint8_t app_id,
- const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return false;
-}
-void connection_manager::on_connection_complete(const RawAddress& address) {
- mock_function_count_map[__func__]++;
-}
-void connection_manager::reset(bool) { mock_function_count_map[__func__]++; }
diff --git a/stack/test/common/mock_gatt_layer.cc b/stack/test/common/mock_gatt_layer.cc
deleted file mode 100644
index a94106695..000000000
--- a/stack/test/common/mock_gatt_layer.cc
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "mock_gatt_layer.h"
-
-static bluetooth::gatt::MockGattInterface* gatt_interface = nullptr;
-
-void bluetooth::gatt::SetMockGattInterface(
- MockGattInterface* mock_gatt_interface) {
- gatt_interface = mock_gatt_interface;
-}
-
-bool gatt_profile_get_eatt_support(const RawAddress& peer_bda) {
- return gatt_interface->GetEattSupport(peer_bda);
-}
-
-void gatt_cl_init_sr_status(tGATT_TCB& tcb) {
- return gatt_interface->ClientInitServerStatus(tcb);
-}
-
-bool gatt_cl_read_sr_supp_feat_req(
- const RawAddress& peer_bda,
- base::OnceCallback<void(const RawAddress&, uint8_t)> cb) {
- return gatt_interface->ClientReadSupportedFeatures(peer_bda, std::move(cb));
-}
diff --git a/stack/test/common/mock_gatt_layer.h b/stack/test/common/mock_gatt_layer.h
deleted file mode 100644
index df071ed03..000000000
--- a/stack/test/common/mock_gatt_layer.h
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <gmock/gmock.h>
-
-#include "base/bind_helpers.h"
-#include "stack/gatt/gatt_int.h"
-
-namespace bluetooth {
-namespace gatt {
-
-class GattInterface {
- public:
- virtual void ClientInitServerStatus(tGATT_TCB& tcb) = 0;
- virtual bool ClientReadSupportedFeatures(
- const RawAddress& peer_bda,
- base::OnceCallback<void(const RawAddress&, uint8_t)> cb) = 0;
- virtual bool GetEattSupport(const RawAddress& peer_bda) = 0;
- virtual ~GattInterface() = default;
-};
-
-class MockGattInterface : public GattInterface {
- public:
- MOCK_METHOD1(ClientInitServerStatus, void(tGATT_TCB& tcb));
- MOCK_METHOD2(ClientReadSupportedFeatures,
- bool(const RawAddress& peer_bda,
- base::OnceCallback<void(const RawAddress&, uint8_t)> cb));
- MOCK_METHOD1(GetEattSupport, bool(const RawAddress& peer_bda));
-};
-
-/**
- * Set the {@link MockGattInterface} for testing
- *
- * @param mock_gatt_interface pointer to mock gatt interface, could be null
- */
-void SetMockGattInterface(MockGattInterface* mock_gatt_interface);
-
-} // namespace gatt
-} // namespace bluetooth
diff --git a/stack/test/common/mock_gatt_main.cc b/stack/test/common/mock_gatt_main.cc
deleted file mode 100644
index 9eb4336fd..000000000
--- a/stack/test/common/mock_gatt_main.cc
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:23
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "bt_common.h"
-#include "bt_target.h"
-#include "btm_ble_int.h"
-#include "device/include/interop.h"
-#include "l2c_api.h"
-#include "osi/include/osi.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/gatt/gatt_int.h"
-#include "stack/include/l2cap_acl_interface.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool gatt_act_connect(tGATT_REG* p_reg, const RawAddress& bd_addr,
- tBT_TRANSPORT transport, int8_t initiating_phys) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool gatt_connect(const RawAddress& rem_bda, tGATT_TCB* p_tcb,
- tBT_TRANSPORT transport, uint8_t initiating_phys,
- tGATT_IF gatt_if) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool gatt_disconnect(tGATT_TCB* p_tcb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool gatt_update_app_hold_link_status(tGATT_IF gatt_if, tGATT_TCB* p_tcb,
- bool is_add) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tGATT_CH_STATE gatt_get_ch_state(tGATT_TCB* p_tcb) {
- mock_function_count_map[__func__]++;
- return GATT_CH_CLOSE;
-}
-void gatt_add_a_bonded_dev_for_srv_chg(const RawAddress& bda) {
- mock_function_count_map[__func__]++;
-}
-void gatt_chk_srv_chg(tGATTS_SRV_CHG* p_srv_chg_clt) {
- mock_function_count_map[__func__]++;
-}
-void gatt_data_process(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
-}
-void gatt_find_in_device_record(const RawAddress& bd_addr,
- tBLE_BD_ADDR* address_with_type) {
- mock_function_count_map[__func__]++;
-}
-void gatt_free(void) { mock_function_count_map[__func__]++; }
-void gatt_init(void) { mock_function_count_map[__func__]++; }
-void gatt_init_srv_chg(void) { mock_function_count_map[__func__]++; }
-void gatt_l2cif_config_cfm_cback(uint16_t lcid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
-}
-void gatt_l2cif_config_ind_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
-}
-void gatt_l2cif_disconnect_ind_cback(uint16_t lcid, bool ack_needed) {
- mock_function_count_map[__func__]++;
-}
-void gatt_notify_conn_update(const RawAddress&, uint16_t interval,
- uint16_t latency, uint16_t timeout,
- tHCI_STATUS status) {
- mock_function_count_map[__func__]++;
-}
-void gatt_notify_phy_updated(tGATT_STATUS status, uint16_t handle,
- uint8_t tx_phy, uint8_t rx_phy) {
- mock_function_count_map[__func__]++;
-}
-void gatt_proc_srv_chg(void) { mock_function_count_map[__func__]++; }
-void gatt_send_srv_chg_ind(const RawAddress& peer_bda) {
- mock_function_count_map[__func__]++;
-}
-void gatt_set_ch_state(tGATT_TCB* p_tcb, tGATT_CH_STATE ch_state) {
- mock_function_count_map[__func__]++;
-}
-void gatt_update_app_use_link_flag(tGATT_IF gatt_if, tGATT_TCB* p_tcb,
- bool is_add, bool check_acl_link) {
- mock_function_count_map[__func__]++;
-}
diff --git a/stack/test/common/mock_hci_packet_parser.cc b/stack/test/common/mock_hci_packet_parser.cc
deleted file mode 100644
index 8d5d1652a..000000000
--- a/stack/test/common/mock_hci_packet_parser.cc
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "hci/include/hci_packet_parser.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-const hci_packet_parser_t* hci_packet_parser_get_interface() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const hci_packet_parser_t* hci_packet_parser_get_test_interface(
- allocator_t* buffer_allocator_interface) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
diff --git a/stack/test/common/mock_hcic_layer.cc b/stack/test/common/mock_hcic_layer.cc
deleted file mode 100644
index e9f4d13a7..000000000
--- a/stack/test/common/mock_hcic_layer.cc
+++ /dev/null
@@ -1,114 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "mock_hcic_layer.h"
-
-static hcic::MockHcicInterface* hcic_interface = nullptr;
-
-void hcic::SetMockHcicInterface(MockHcicInterface* interface) {
- hcic_interface = interface;
-}
-
-void btsnd_hcic_set_cig_params(
- uint8_t cig_id, uint32_t sdu_itv_mtos, uint32_t sdu_itv_stom, uint8_t sca,
- uint8_t packing, uint8_t framing, uint16_t max_trans_lat_stom,
- uint16_t max_trans_lat_mtos, uint8_t cis_cnt, const EXT_CIS_CFG* cis_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- struct bluetooth::hci::iso_manager::cig_create_params cig_params = {
- .sdu_itv_mtos = sdu_itv_mtos,
- .sdu_itv_stom = sdu_itv_stom,
- .sca = sca,
- .packing = packing,
- .framing = framing,
- .max_trans_lat_stom = max_trans_lat_stom,
- .max_trans_lat_mtos = max_trans_lat_mtos,
- .cis_cfgs = std::vector(cis_cfg, cis_cfg + cis_cnt),
- };
- hcic_interface->SetCigParams(cig_id, std::move(cig_params), std::move(cb));
-}
-
-void btsnd_hcic_remove_cig(uint8_t cig_id,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- hcic_interface->RemoveCig(cig_id, std::move(cb));
-}
-
-void btsnd_hcic_create_cis(uint8_t num_cis, const EXT_CIS_CREATE_CFG* cis_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- hcic_interface->CreateCis(num_cis, cis_cfg, std::move(cb));
-}
-
-static void btsnd_hcic_disconnect(uint16_t handle, uint8_t reason) {
- hcic_interface->Disconnect(handle, reason);
-}
-
-void btsnd_hcic_setup_iso_data_path(
- uint16_t iso_handle, uint8_t data_path_dir, uint8_t data_path_id,
- uint8_t codec_id_format, uint16_t codec_id_company,
- uint16_t codec_id_vendor, uint32_t controller_delay,
- std::vector<uint8_t> codec_conf,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- hcic_interface->SetupIsoDataPath(iso_handle, data_path_dir, data_path_id,
- codec_id_format, codec_id_company,
- codec_id_vendor, controller_delay,
- std::move(codec_conf), std::move(cb));
-}
-
-void btsnd_hcic_remove_iso_data_path(
- uint16_t iso_handle, uint8_t data_path_dir,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- hcic_interface->RemoveIsoDataPath(iso_handle, data_path_dir, std::move(cb));
-}
-
-void btsnd_hcic_read_iso_link_quality(
- uint16_t iso_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- hcic_interface->ReadIsoLinkQuality(iso_handle, std::move(cb));
-}
-
-void btsnd_hcic_create_big(uint8_t big_handle, uint8_t adv_handle,
- uint8_t num_bis, uint32_t sdu_itv,
- uint16_t max_sdu_size, uint16_t transport_latency,
- uint8_t rtn, uint8_t phy, uint8_t packing,
- uint8_t framing, uint8_t enc,
- std::array<uint8_t, 16> bcst_code) {
- struct bluetooth::hci::iso_manager::big_create_params big_params = {
- .adv_handle = adv_handle,
- .num_bis = num_bis,
- .sdu_itv = sdu_itv,
- .max_sdu_size = max_sdu_size,
- .max_transport_latency = transport_latency,
- .rtn = rtn,
- .phy = phy,
- .packing = packing,
- .framing = framing,
- .enc = enc,
- .enc_code = std::move(bcst_code),
- };
- hcic_interface->CreateBig(big_handle, std::move(big_params));
-}
-
-void btsnd_hcic_term_big(uint8_t big_handle, uint8_t reason) {
- hcic_interface->TerminateBig(big_handle, reason);
-}
-
-bluetooth::legacy::hci::Interface interface_ = {
- .Disconnect = btsnd_hcic_disconnect,
-};
-
-const bluetooth::legacy::hci::Interface&
-bluetooth::legacy::hci::GetInterface() {
- return interface_;
-}
diff --git a/stack/test/common/mock_hcic_layer.h b/stack/test/common/mock_hcic_layer.h
deleted file mode 100644
index c7ad5eca6..000000000
--- a/stack/test/common/mock_hcic_layer.h
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.com.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <base/callback.h>
-#include <gmock/gmock.h>
-
-#include <array>
-
-#include "btm_iso_api_types.h"
-#include "hcimsgs.h"
-
-namespace hcic {
-class HcicInterface {
- public:
- // iso_manager::cig_create_params is a workaround for the 10 params function
- // limitation that gmock sets
- virtual void SetCigParams(
- uint8_t cig_id,
- struct bluetooth::hci::iso_manager::cig_create_params cig_params,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) = 0;
-
- virtual void RemoveCig(uint8_t cig_id,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) = 0;
-
- virtual void CreateCis(uint8_t num_cis,
- const EXT_CIS_CREATE_CFG* cis_create_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) = 0;
-
- virtual void Disconnect(uint16_t handle, uint8_t reason) = 0;
-
- virtual void SetupIsoDataPath(
- uint16_t iso_handle, uint8_t data_path_dir, uint8_t data_path_id,
- uint8_t codec_id_format, uint16_t codec_id_company,
- uint16_t codec_id_vendor, uint32_t controller_delay,
- std::vector<uint8_t> codec_conf,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) = 0;
-
- virtual void RemoveIsoDataPath(
- uint16_t iso_handle, uint8_t data_path_dir,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) = 0;
-
- virtual void ReadIsoLinkQuality(
- uint16_t iso_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb) = 0;
-
- // iso_manager::big_create_params is a workaround for the 10 params function
- // limitation that gmock sets
- virtual void CreateBig(
- uint8_t big_handle,
- struct bluetooth::hci::iso_manager::big_create_params big_params) = 0;
-
- virtual void TerminateBig(uint8_t big_handle, uint8_t reason) = 0;
-
- virtual ~HcicInterface() = default;
-};
-
-class MockHcicInterface : public HcicInterface {
- public:
- MOCK_METHOD((void), SetCigParams,
- (uint8_t cig_id,
- struct bluetooth::hci::iso_manager::cig_create_params cig_params,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb),
- (override));
-
- MOCK_METHOD((void), RemoveCig,
- (uint8_t cig_id, base::OnceCallback<void(uint8_t*, uint16_t)> cb),
- (override));
-
- MOCK_METHOD((void), CreateCis,
- (uint8_t num_cis, const EXT_CIS_CREATE_CFG* cis_create_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb),
- (override));
-
- MOCK_METHOD((void), Disconnect, (uint16_t handle, uint8_t reason),
- (override));
-
- MOCK_METHOD((void), SetupIsoDataPath,
- (uint16_t iso_handle, uint8_t data_path_dir, uint8_t data_path_id,
- uint8_t codec_id_format, uint16_t codec_id_company,
- uint16_t codec_id_vendor, uint32_t controller_delay,
- std::vector<uint8_t> codec_conf,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb),
- (override));
-
- MOCK_METHOD((void), RemoveIsoDataPath,
- (uint16_t iso_handle, uint8_t data_path_dir,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb),
- (override));
-
- MOCK_METHOD((void), ReadIsoLinkQuality,
- (uint16_t iso_handle,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb),
- (override));
-
- MOCK_METHOD(
- (void), CreateBig,
- (uint8_t big_handle,
- struct bluetooth::hci::iso_manager::big_create_params big_params),
- (override));
-
- MOCK_METHOD((void), TerminateBig, (uint8_t big_handle, uint8_t reason),
- (override));
-};
-
-void SetMockHcicInterface(MockHcicInterface* mock_hcic_interface);
-
-} // namespace hcic
diff --git a/stack/test/common/mock_l2cap_layer.cc b/stack/test/common/mock_l2cap_layer.cc
index 4fd77b26e..605eb4937 100644
--- a/stack/test/common/mock_l2cap_layer.cc
+++ b/stack/test/common/mock_l2cap_layer.cc
@@ -24,11 +24,10 @@ void bluetooth::l2cap::SetMockInterface(
l2cap_interface = mock_l2cap_interface;
}
-uint16_t L2CA_Register(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level) {
- VLOG(1) << __func__ << ": psm=" << psm << ", enable_snoop=" << enable_snoop;
+uint16_t L2CA_Register(uint16_t psm, tL2CAP_APPL_INFO* p_cb_info,
+ bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info) {
+ VLOG(1) << __func__ << ": psm=" << psm << ", p_cb_info=" << p_cb_info
+ << ", enable_snoop=" << enable_snoop;
return l2cap_interface->Register(psm, p_cb_info, enable_snoop, p_ertm_info);
}
@@ -60,34 +59,3 @@ bool L2CA_ConfigRsp(uint16_t cid, tL2CAP_CFG_INFO* p_cfg) {
uint8_t L2CA_DataWrite(uint16_t cid, BT_HDR* p_data) {
return l2cap_interface->DataWrite(cid, p_data);
}
-
-uint16_t L2CA_RegisterLECoc(uint16_t psm, const tL2CAP_APPL_INFO& cb_info,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg) {
- return l2cap_interface->RegisterLECoc(psm, cb_info, sec_level);
-}
-
-void L2CA_DeregisterLECoc(uint16_t psm) {
- return l2cap_interface->DeregisterLECoc(psm);
-}
-
-tHCI_ROLE L2CA_GetBleConnRole(const RawAddress& bd_addr) {
- return to_hci_role(l2cap_interface->GetBleConnRole(bd_addr));
-}
-
-std::vector<uint16_t> L2CA_ConnectCreditBasedReq(uint16_t psm,
- const RawAddress& bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- return l2cap_interface->ConnectCreditBasedReq(psm, bd_addr, p_cfg);
-}
-
-bool L2CA_ConnectCreditBasedRsp(const RawAddress& bd_addr, uint8_t id,
- std::vector<uint16_t> &lcids,
- uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- return l2cap_interface->ConnectCreditBasedRsp(bd_addr, id, lcids, result, p_cfg);
-}
-
-bool L2CA_ReconfigCreditBasedConnsReq(const RawAddress& bd_addr, std::vector<uint16_t> &lcids,
- tL2CAP_LE_CFG_INFO* peer_cfg) {
- return l2cap_interface->ReconfigCreditBasedConnsReq(bd_addr, lcids, peer_cfg);
-}
diff --git a/stack/test/common/mock_l2cap_layer.h b/stack/test/common/mock_l2cap_layer.h
index 15ffcae00..732d4150e 100644
--- a/stack/test/common/mock_l2cap_layer.h
+++ b/stack/test/common/mock_l2cap_layer.h
@@ -26,7 +26,7 @@ namespace l2cap {
class L2capInterface {
public:
- virtual uint16_t Register(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
+ virtual uint16_t Register(uint16_t psm, tL2CAP_APPL_INFO* p_cb_info,
bool enable_snoop,
tL2CAP_ERTM_INFO* p_ertm_info) = 0;
virtual uint16_t ConnectRequest(uint16_t psm, const RawAddress& bd_addr) = 0;
@@ -38,24 +38,13 @@ class L2capInterface {
virtual bool ConfigRequest(uint16_t cid, tL2CAP_CFG_INFO* p_cfg) = 0;
virtual bool ConfigResponse(uint16_t cid, tL2CAP_CFG_INFO* p_cfg) = 0;
virtual uint8_t DataWrite(uint16_t cid, BT_HDR* p_data) = 0;
- virtual uint16_t RegisterLECoc(uint16_t psm, const tL2CAP_APPL_INFO &cb_info, uint16_t sec_level) = 0;
- virtual void DeregisterLECoc(uint16_t psm) = 0;
- virtual bool ConnectCreditBasedRsp(const RawAddress& bd_addr, uint8_t id,
- std::vector<uint16_t> &lcids,
- uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg) = 0;
- virtual std::vector<uint16_t> ConnectCreditBasedReq(uint16_t psm,
- const RawAddress& bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) = 0;
- virtual bool ReconfigCreditBasedConnsReq(const RawAddress& bd_addr, std::vector<uint16_t> &lcids,
- tL2CAP_LE_CFG_INFO* peer_cfg) = 0;
virtual ~L2capInterface() = default;
};
class MockL2capInterface : public L2capInterface {
public:
MOCK_METHOD4(Register,
- uint16_t(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
+ uint16_t(uint16_t psm, tL2CAP_APPL_INFO* p_cb_info,
bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info));
MOCK_METHOD2(ConnectRequest,
uint16_t(uint16_t psm, const RawAddress& bd_addr));
@@ -67,21 +56,6 @@ class MockL2capInterface : public L2capInterface {
MOCK_METHOD2(ConfigRequest, bool(uint16_t cid, tL2CAP_CFG_INFO* p_cfg));
MOCK_METHOD2(ConfigResponse, bool(uint16_t cid, tL2CAP_CFG_INFO* p_cfg));
MOCK_METHOD2(DataWrite, uint8_t(uint16_t cid, BT_HDR* p_data));
- MOCK_METHOD3(RegisterLECoc,
- uint16_t(uint16_t psm, const tL2CAP_APPL_INFO &cb_info, uint16_t sec_level));
- MOCK_METHOD1(DeregisterLECoc, void(uint16_t psm));
- MOCK_METHOD1(GetBleConnRole, uint8_t(const RawAddress& bd_addr));
- MOCK_METHOD5(ConnectCreditBasedRsp,
- bool(const RawAddress& p_bd_addr, uint8_t id,
- std::vector<uint16_t> &lcids,
- uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg));
- MOCK_METHOD3(ConnectCreditBasedReq,
- std::vector<uint16_t> (uint16_t psm,
- const RawAddress& bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg));
- MOCK_METHOD3(ReconfigCreditBasedConnsReq,
- bool(const RawAddress& p_bd_addr, std::vector<uint16_t> &lcids, tL2CAP_LE_CFG_INFO* peer_cfg));
};
/**
diff --git a/stack/test/common/mock_main_bte_main.cc b/stack/test/common/mock_main_bte_main.cc
deleted file mode 100644
index 581782ef2..000000000
--- a/stack/test/common/mock_main_bte_main.cc
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <hardware/bluetooth.h>
-#include "bt_common.h"
-#include "btcore/include/module.h"
-#include "bte.h"
-#include "btif/include/btif_config.h"
-#include "btu.h"
-#include "device/include/interop.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void bte_main_hci_send(BT_HDR* p_msg, uint16_t event) {
- mock_function_count_map[__func__]++;
-}
-void bte_main_init(void) { mock_function_count_map[__func__]++; }
-void post_to_main_message_loop(const base::Location& from_here, BT_HDR* p_msg) {
- mock_function_count_map[__func__]++;
-}
diff --git a/stack/test/common/mock_main_shim.cc b/stack/test/common/mock_main_shim.cc
deleted file mode 100644
index b8a7b19a7..000000000
--- a/stack/test/common/mock_main_shim.cc
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:14
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#define LOG_TAG "bt_shim"
-#include "gd/common/init_flags.h"
-#include "main/shim/entry.h"
-#include "main/shim/shim.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-extern bool MOCK_bluetooth_shim_is_gd_acl_enabled_;
-
-bool bluetooth::shim::is_any_gd_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_acl_enabled() {
- mock_function_count_map[__func__]++;
- return MOCK_bluetooth_shim_is_gd_acl_enabled_;
-}
-bool bluetooth::shim::is_gd_advertising_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_scanning_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_controller_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_hci_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_l2cap_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_security_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_shim_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_stack_started_up() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_link_policy_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-future_t* GeneralShutDown() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-future_t* IdleModuleStartUp() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-future_t* ShimModuleStartUp() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
diff --git a/stack/test/common/mock_main_shim_btm_api.cc b/stack/test/common/mock_main_shim_btm_api.cc
deleted file mode 100644
index 623135c35..000000000
--- a/stack/test/common/mock_main_shim_btm_api.cc
+++ /dev/null
@@ -1,465 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:85
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/callback.h>
-#include <mutex>
-#include "common/metric_id_allocator.h"
-#include "common/time_util.h"
-#include "device/include/controller.h"
-#include "main/shim/btm_api.h"
-#include "main/shim/controller.h"
-#include "main/shim/link_policy.h"
-#include "main/shim/shim.h"
-#include "stack/btm/btm_int_types.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-Octet16 octet16;
-
-bool bluetooth::shim::BTM_BleDataSignature(const RawAddress& bd_addr,
- uint8_t* p_text, uint16_t len,
- BLE_SIGNATURE signature) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_BleLocalPrivacyEnabled(void) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_BleSecurityProcedureIsRunning(
- const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_BleVerifySignature(const RawAddress& bd_addr,
- uint8_t* p_orig, uint16_t len,
- uint32_t counter,
- uint8_t* p_comp) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_GetLeSecurityState(const RawAddress& bd_addr,
- uint8_t* p_le_dev_sec_flags,
- uint8_t* p_le_key_size) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_HasEirService(const uint32_t* p_eir_uuid,
- uint16_t uuid16) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_ReadConnectedTransportAddress(
- RawAddress* remote_bda, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_ReadRemoteConnectionAddr(
- const RawAddress& pseudo_addr, RawAddress& conn_addr,
- tBLE_ADDR_TYPE* p_addr_type) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_SecAddDevice(const RawAddress& bd_addr,
- DEV_CLASS dev_class, BD_NAME bd_name,
- uint8_t* features, LinkKey* link_key,
- uint8_t key_type, uint8_t pin_length) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_SecAddRmtNameNotifyCallback(
- tBTM_RMT_NAME_CALLBACK* p_callback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_SecDeleteDevice(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_SecDeleteRmtNameNotifyCallback(
- tBTM_RMT_NAME_CALLBACK* p_callback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_SecRegister(const tBTM_APPL_INFO* bta_callbacks) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_UseLeLink(const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
- return false;
-}
-char* bluetooth::shim::BTM_SecReadDevName(const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const Octet16& bluetooth::shim::BTM_GetDeviceEncRoot() {
- mock_function_count_map[__func__]++;
- return octet16;
-}
-const Octet16& bluetooth::shim::BTM_GetDeviceDHK() {
- mock_function_count_map[__func__]++;
- return octet16;
-}
-const Octet16& bluetooth::shim::BTM_GetDeviceIDRoot() {
- mock_function_count_map[__func__]++;
- return octet16;
-}
-tBTM_EIR_SEARCH_RESULT bluetooth::shim::BTM_HasInquiryEirService(
- tBTM_INQ_RESULTS* p_results, uint16_t uuid16) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTM_INQ_INFO* bluetooth::shim::BTM_InqDbFirst(void) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_INQ_INFO* bluetooth::shim::BTM_InqDbNext(tBTM_INQ_INFO* p_cur) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_INQ_INFO* bluetooth::shim::BTM_InqDbRead(const RawAddress& p_bda) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_STATUS bluetooth::shim::BTM_BleObserve(bool start, uint8_t duration_sec,
- tBTM_INQ_RESULTS_CB* p_results_cb,
- tBTM_CMPL_CB* p_cmpl_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_CancelRemoteDeviceName(void) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_ClearInqDb(const RawAddress* p_bda) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_ReadRemoteDeviceName(
- const RawAddress& raw_address, tBTM_CMPL_CB* callback,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SecBond(const RawAddress& bd_addr,
- tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport,
- int device_type) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SecBondCancel(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetConnectability(uint16_t page_mode,
- uint16_t window,
- uint16_t interval) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetDeviceClass(DEV_CLASS dev_class) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetDiscoverability(uint16_t discoverable_mode,
- uint16_t window,
- uint16_t interval) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetEncryption(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data,
- tBTM_BLE_SEC_ACT sec_act) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetInquiryMode(uint8_t inquiry_mode) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_StartInquiry(tBTM_INQ_RESULTS_CB* p_results_cb,
- tBTM_CMPL_CB* p_cmpl_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_WriteEIR(BT_HDR* p_buff) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::btm_sec_mx_access_request(
- const RawAddress& bd_addr, bool is_originator,
- uint16_t security_requirement, tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-uint16_t bluetooth::shim::BTM_GetHCIConnHandle(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t bluetooth::shim::BTM_IsInquiryActive(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t bluetooth::shim::BTM_BleGetSupportedKeySize(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t bluetooth::shim::BTM_BleMaxMultiAdvInstanceCount() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t bluetooth::shim::BTM_GetEirSupportedServices(uint32_t* p_eir_uuid,
- uint8_t** p,
- uint8_t max_num_uuid16,
- uint8_t* p_num_uuid16) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t bluetooth::shim::BTM_GetEirUuidList(uint8_t* p_eir, size_t eir_len,
- uint8_t uuid_size,
- uint8_t* p_num_uuid,
- uint8_t* p_uuid_list,
- uint8_t max_num_uuid) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void bluetooth::shim::BTM_AddEirService(uint32_t* p_eir_uuid, uint16_t uuid16) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleAdvFilterParamSetup(
- int action, tBTM_BLE_PF_FILT_INDEX filt_index,
- std::unique_ptr<btgatt_filt_param_setup_t> p_filt_params,
- tBTM_BLE_PF_PARAM_CB cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleEnableDisableFilterFeature(
- uint8_t enable, tBTM_BLE_PF_STATUS_CBACK p_stat_cback) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleLoadLocalKeys(uint8_t key_type,
- tBTM_BLE_LOCAL_KEYS* p_key) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleOobDataReply(const RawAddress& bd_addr,
- uint8_t res, uint8_t len,
- uint8_t* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleReadPhy(
- const RawAddress& bd_addr,
- base::Callback<void(uint8_t tx_phy, uint8_t rx_phy, uint8_t status)> cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleReceiverTest(uint8_t rx_freq,
- tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleSecureConnectionOobDataReply(
- const RawAddress& bd_addr, uint8_t* p_c, uint8_t* p_r) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleSetConnScanParams(uint32_t scan_interval,
- uint32_t scan_window) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleSetPhy(const RawAddress& bd_addr, uint8_t tx_phys,
- uint8_t rx_phys, uint16_t phy_options) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleSetPrefConnParams(const RawAddress& bd_addr,
- uint16_t min_conn_int,
- uint16_t max_conn_int,
- uint16_t peripheral_latency,
- uint16_t supervision_tout) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleTestEnd(tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleTransmitterTest(uint8_t tx_freq,
- uint8_t test_data_len,
- uint8_t packet_payload,
- tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleUpdateAdvFilterPolicy(tBTM_BLE_AFP adv_policy) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_CancelInquiry(void) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_ConfirmReqReply(tBTM_STATUS res,
- const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_EnableInterlacedInquiryScan() {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_EnableInterlacedPageScan() {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_addr_filter(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index,
- tBLE_BD_ADDR addr,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_clear(tBTM_BLE_PF_FILT_INDEX filt_index,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_local_name(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index,
- std::vector<uint8_t> name,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_manu_data(
- tBTM_BLE_SCAN_COND_OP action, tBTM_BLE_PF_FILT_INDEX filt_index,
- uint16_t company_id, uint16_t company_id_mask, std::vector<uint8_t> data,
- std::vector<uint8_t> data_mask, tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_set(tBTM_BLE_PF_FILT_INDEX filt_index,
- std::vector<ApcfCommand> commands,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_srvc_data(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_srvc_data_pattern(
- tBTM_BLE_SCAN_COND_OP action, tBTM_BLE_PF_FILT_INDEX filt_index,
- std::vector<uint8_t> data, std::vector<uint8_t> data_mask,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_uuid_filter(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index,
- tBTM_BLE_PF_COND_TYPE filter_type,
- const bluetooth::Uuid& uuid,
- tBTM_BLE_PF_LOGIC_TYPE cond_logic,
- const bluetooth::Uuid& uuid_mask,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res,
- uint8_t pin_len, uint8_t* p_pin) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_ReadConnectionAddr(const RawAddress& remote_bda,
- RawAddress& local_conn_addr,
- tBLE_ADDR_TYPE* p_addr_type) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_ReadDevInfo(const RawAddress& remote_bda,
- tBT_DEVICE_TYPE* p_dev_type,
- tBLE_ADDR_TYPE* p_addr_type) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_RemoteOobDataReply(tBTM_STATUS res,
- const RawAddress& bd_addr,
- const Octet16& c,
- const Octet16& r) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_RemoveEirService(uint32_t* p_eir_uuid,
- uint16_t uuid16) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_SecAddBleDevice(const RawAddress& bd_addr,
- tBT_DEVICE_TYPE dev_type,
- tBLE_ADDR_TYPE addr_type) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_SecAddBleKey(const RawAddress& bd_addr,
- tBTM_LE_KEY_VALUE* p_le_key,
- tBTM_LE_KEY_TYPE key_type) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_SecClearSecurityFlags(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_SecurityGrant(const RawAddress& bd_addr,
- uint8_t res) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::SendRemoteNameRequest(const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
-}
-void btm_api_process_extended_inquiry_result(RawAddress raw_address,
- uint8_t page_scan_rep_mode,
- DEV_CLASS device_class,
- uint16_t clock_offset, int8_t rssi,
- const uint8_t* eir_data,
- size_t eir_len) {
- mock_function_count_map[__func__]++;
-}
-void btm_api_process_inquiry_result(const RawAddress& raw_address,
- uint8_t page_scan_rep_mode,
- DEV_CLASS device_class,
- uint16_t clock_offset) {
- mock_function_count_map[__func__]++;
-}
-void btm_api_process_inquiry_result_with_rssi(RawAddress raw_address,
- uint8_t page_scan_rep_mode,
- DEV_CLASS device_class,
- uint16_t clock_offset,
- int8_t rssi) {
- mock_function_count_map[__func__]++;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetPowerMode(uint16_t, tBTM_PM_PWR_MD const&) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-void bluetooth::shim::btm_pm_on_mode_change(tHCI_STATUS status, uint16_t handle,
- tHCI_MODE current_mode,
- uint16_t interval) {
- mock_function_count_map[__func__]++;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetSsrParams(uint16_t, uint16_t max_lat,
- uint16_t min_rmt_to,
- uint16_t min_loc_to) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-void bluetooth::shim::btm_pm_on_sniff_subrating(
- tHCI_STATUS status, uint16_t handle, uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- UNUSED_ATTR uint16_t minimum_remote_timeout,
- UNUSED_ATTR uint16_t minimum_local_timeout) {
- mock_function_count_map[__func__]++;
-}
diff --git a/stack/test/common/mock_main_shim_controller.cc b/stack/test/common/mock_main_shim_controller.cc
deleted file mode 100644
index 8e4c9f5c2..000000000
--- a/stack/test/common/mock_main_shim_controller.cc
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:5
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "main/shim/controller.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-const controller_t* bluetooth::shim::controller_get_interface() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
diff --git a/stack/test/common/mock_main_shim_l2c_api.cc b/stack/test/common/mock_main_shim_l2c_api.cc
deleted file mode 100644
index 64c4aeb0e..000000000
--- a/stack/test/common/mock_main_shim_l2c_api.cc
+++ /dev/null
@@ -1,230 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:54
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "main/shim/l2c_api.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool bluetooth::shim::L2CA_RegisterFixedChannel(uint16_t cid,
- tL2CAP_FIXED_CHNL_REG* p_freg) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_ConnectCreditBasedRsp(
- const RawAddress& bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids, uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_ConnectFixedChnl(uint16_t cid,
- const RawAddress& rem_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-
-bool bluetooth::shim::L2CA_DisconnectLECocReq(uint16_t cid) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_DisconnectReq(uint16_t cid) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_GetPeerFeatures(const RawAddress& bd_addr,
- uint32_t* p_ext_feat,
- uint8_t* p_chnl_mask) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_GetPeerLECocConfig(uint16_t cid,
- tL2CAP_LE_CFG_INFO* peer_cfg) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_GetRemoteCid(uint16_t lcid, uint16_t* rcid) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_IsLinkEstablished(const RawAddress& bd_addr,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-uint16_t bluetooth::shim::L2CA_GetLeHandle(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-bool bluetooth::shim::L2CA_IsLeLink(uint16_t) {
- mock_function_count_map[__func__]++;
- return false;
-}
-void bluetooth::shim::L2CA_ReadConnectionAddr(const RawAddress& pseudo_addr,
- RawAddress& conn_addr,
- uint8_t* p_addr_type) {
- mock_function_count_map[__func__]++;
-}
-bool bluetooth::shim::L2CA_ReadRemoteConnectionAddr(
- const RawAddress& pseudo_addr, RawAddress& conn_addr,
- uint8_t* p_addr_type) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_ReconfigCreditBasedConnsReq(
- const RawAddress& bd_addr, std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_RemoveFixedChnl(uint16_t cid,
- const RawAddress& rem_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_SetAclPriority(const RawAddress& bd_addr,
- tL2CAP_PRIORITY priority) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_SetChnlFlushability(uint16_t cid,
- bool is_flushable) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_SetLeGattTimeout(const RawAddress& rem_bda,
- uint16_t idle_tout) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_SetIdleTimeoutByBdAddr(const RawAddress& bd_addr,
- uint16_t timeout,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::L2CA_SetTxPriority(uint16_t cid,
- tL2CAP_CHNL_PRIORITY priority) {
- mock_function_count_map[__func__]++;
- return false;
-}
-uint16_t bluetooth::shim::L2CA_AllocateLePSM(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t bluetooth::shim::L2CA_ConnectLECocReq(uint16_t psm,
- const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t bluetooth::shim::L2CA_ConnectReq(uint16_t psm,
- const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t bluetooth::shim::L2CA_FlushChannel(uint16_t lcid,
- uint16_t num_to_flush) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t bluetooth::shim::L2CA_Register(
- uint16_t client_psm, const tL2CAP_APPL_INFO& callbacks, bool enable_snoop,
- tL2CAP_ERTM_INFO* p_ertm_info, uint16_t my_mtu,
- uint16_t required_remote_mtu, uint16_t sec_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t bluetooth::shim::L2CA_SendFixedChnlData(uint16_t cid,
- const RawAddress& rem_bda,
- BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t find_classic_cid_token_by_psm_address(uint16_t psm,
- RawAddress remote) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t find_le_cid_token_by_psm_address(uint16_t psm, RawAddress remote) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t bluetooth::shim::L2CA_DataWrite(uint16_t cid, BT_HDR* p_data) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t bluetooth::shim::L2CA_LECocDataWrite(uint16_t cid, BT_HDR* p_data) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void bluetooth::shim::L2CA_ConnectForSecurity(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::L2CA_Deregister(uint16_t client_psm) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::L2CA_DeregisterLECoc(uint16_t psm) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::L2CA_FreeLePSM(uint16_t psm) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::L2CA_SetBondingState(const RawAddress& bd_addr,
- bool is_bonding) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::L2CA_SwitchRoleToCentral(const RawAddress& addr) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::L2CA_UseLegacySecurityModule() {
- mock_function_count_map[__func__]++;
-}
-void remove_classic_cid_token_entry(uint16_t cid_token) {
- mock_function_count_map[__func__]++;
-}
-void remove_le_cid_token_entry(uint16_t cid_token) {
- mock_function_count_map[__func__]++;
-}
-bool bluetooth::shim::L2CA_ReadRemoteVersion(const RawAddress& addr,
- uint8_t* lmp_version,
- uint16_t* manufacturer,
- uint16_t* lmp_sub_version) {
- mock_function_count_map[__func__]++;
- return false;
-}
-uint8_t* bluetooth::shim::L2CA_ReadRemoteFeatures(const RawAddress& remote) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void bluetooth::shim::L2CA_DisconnectLink(const RawAddress& remote) {
- mock_function_count_map[__func__]++;
-}
-uint16_t bluetooth::shim::L2CA_GetNumLinks() {
- mock_function_count_map[__func__]++;
- return 0;
-}
diff --git a/stack/test/common/mock_main_shim_link_policy.cc b/stack/test/common/mock_main_shim_link_policy.cc
deleted file mode 100644
index a9f337e38..000000000
--- a/stack/test/common/mock_main_shim_link_policy.cc
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:14
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#define LOG_TAG "bt_shim"
-
-#include "main/shim/link_policy.h"
-#include "stack/include/btm_api_types.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool bluetooth::shim::UnregisterLinkPolicyClient(tBTM_PM_STATUS_CBACK* p_cb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::RegisterLinkPolicyClient(tBTM_PM_STATUS_CBACK* p_cb) {
- mock_function_count_map[__func__]++;
- return false;
-}
diff --git a/stack/test/common/mock_smp_smp_act.cc b/stack/test/common/mock_smp_smp_act.cc
deleted file mode 100644
index b3e2390f1..000000000
--- a/stack/test/common/mock_smp_smp_act.cc
+++ /dev/null
@@ -1,252 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:73
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "stack/smp/smp_int.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool smp_proc_ltk_request(const RawAddress& bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-void smp_both_have_public_keys(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_br_check_authorization_request(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_br_pairing_complete(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_br_process_link_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_br_process_pairing_command(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_br_process_peripheral_keys_response(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_br_process_security_grant(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_br_select_next_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_br_send_pair_response(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_cancel_start_encryption_attempt() {
- mock_function_count_map[__func__]++;
-}
-void smp_check_auth_req(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_decide_association_model(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_derive_link_key_from_long_term_key(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_enc_cmpl(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_idle_terminate(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_key_distribution(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_key_distribution_by_transport(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_key_pick_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_link_encrypted(const RawAddress& bda, uint8_t encr_enable) {
- mock_function_count_map[__func__]++;
-}
-void smp_match_dhkey_checks(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_move_to_secure_connections_phase2(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_pair_terminate(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_pairing_cmpl(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_phase_2_dhkey_checks_are_present(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_central_id(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_compare(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_confirm(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_discard(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_enc_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_id_addr(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_id_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_init(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_pair_cmd(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_pair_fail(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_rand(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_sec_grant(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_sec_req(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_sl_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_proc_srk_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_process_dhkey_check(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_process_io_response(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_process_keypress_notification(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_process_local_nonce(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_process_pairing_commitment(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_process_pairing_public_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_process_peer_nonce(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_process_secure_connection_long_term_key(void) {
- mock_function_count_map[__func__]++;
-}
-void smp_process_secure_connection_oob_data(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_app_cback(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_commitment(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_confirm(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_csrk_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_dhkey_check(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_enc_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_id_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_init(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_keypress_notification(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_ltk_reply(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_pair_fail(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_pair_public_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_pair_req(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_pair_rsp(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_send_rand(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_set_derive_link_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_set_local_oob_keys(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_set_local_oob_random_commitment(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_start_enc(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_start_passkey_verification(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_start_secure_connection_phase1(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void smp_wait_for_both_public_keys(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
diff --git a/stack/test/common/mock_smp_smp_api.cc b/stack/test/common/mock_smp_smp_api.cc
deleted file mode 100644
index 1fd8fe69c..000000000
--- a/stack/test/common/mock_smp_smp_api.cc
+++ /dev/null
@@ -1,88 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:11
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "bt_target.h"
-#include "hcimsgs.h"
-#include "main/shim/shim.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/include/l2c_api.h"
-#include "stack/include/l2cdefs.h"
-#include "stack/include/smp_api.h"
-#include "stack/smp/smp_int.h"
-#include "stack_config.h"
-#include "utils/include/bt_utils.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool SMP_PairCancel(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SMP_Register(tSMP_CALLBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tSMP_STATUS SMP_BR_PairWith(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return SMP_SUCCESS;
-}
-tSMP_STATUS SMP_Pair(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return SMP_SUCCESS;
-}
-uint8_t SMP_SetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void SMP_ConfirmReply(const RawAddress& bd_addr, uint8_t res) {
- mock_function_count_map[__func__]++;
-}
-void SMP_Init(void) { mock_function_count_map[__func__]++; }
-void SMP_OobDataReply(const RawAddress& bd_addr, tSMP_STATUS res, uint8_t len,
- uint8_t* p_data) {
- mock_function_count_map[__func__]++;
-}
-void SMP_PasskeyReply(const RawAddress& bd_addr, uint8_t res,
- uint32_t passkey) {
- mock_function_count_map[__func__]++;
-}
-void SMP_SecureConnectionOobDataReply(uint8_t* p_data) {
- mock_function_count_map[__func__]++;
-}
-void SMP_SecurityGrant(const RawAddress& bd_addr, tSMP_STATUS res) {
- mock_function_count_map[__func__]++;
-}
-
-void SMP_CrLocScOobData(
- base::OnceCallback<void(tBT_TRANSPORT, bool,
- const std::array<unsigned char, 16>&,
- const std::array<unsigned char, 16>&)>
- callback) {
- mock_function_count_map[__func__]++;
-}
diff --git a/stack/test/common/mock_stack_avdt_msg.cc b/stack/test/common/mock_stack_avdt_msg.cc
deleted file mode 100644
index a4eebf684..000000000
--- a/stack/test/common/mock_stack_avdt_msg.cc
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <map>
-#include <string>
-#include <vector>
-#include "stack/avdt/avdt_int.h"
-
-extern std::map<std::string, int> mock_function_count_map;
-
-/*
- * TODO: This way of mocking is primitive.
- * Need to consider more sophisticated existing methods.
- */
-
-static std::vector<uint8_t> _rsp_sig_ids{};
-
-void avdt_msg_send_rsp(AvdtpCcb* p_ccb, uint8_t sig_id, tAVDT_MSG* p_params) {
- mock_function_count_map[__func__]++;
- _rsp_sig_ids.push_back(sig_id);
-}
-
-size_t mock_avdt_msg_send_rsp_get_count(void) {
- return _rsp_sig_ids.size();
-}
-
-void mock_avdt_msg_send_rsp_clear_history(void) {
- _rsp_sig_ids.clear();
-}
-
-uint8_t mock_avdt_msg_send_rsp_get_sig_id_at(size_t nth) {
- return _rsp_sig_ids[nth];
-}
-
-void avdt_msg_ind(AvdtpCcb* p_ccb, BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
-}
-
-void avdt_msg_send_rej(AvdtpCcb* p_ccb, uint8_t sig_id, tAVDT_MSG* p_params) {
- mock_function_count_map[__func__]++;
-}
-
-static std::vector<uint8_t> _cmd_sig_ids{};
-
-void avdt_msg_send_cmd(AvdtpCcb* p_ccb, void* p_scb, uint8_t sig_id,
- tAVDT_MSG* p_params) {
- mock_function_count_map[__func__]++;
- _cmd_sig_ids.push_back(sig_id);
-}
-
-size_t mock_avdt_msg_send_cmd_get_count(void) {
- return _cmd_sig_ids.size();
-}
-
-void mock_avdt_msg_send_cmd_clear_history(void) {
- _cmd_sig_ids.clear();
-}
-
-uint8_t mock_avdt_msg_send_cmd_get_sig_id_at(size_t nth) {
- return _cmd_sig_ids[nth];
-}
-
-bool avdt_msg_send(AvdtpCcb* p_ccb, BT_HDR* p_msg) {
- mock_function_count_map[__func__]++;
- return true;
-}
-
-const uint8_t avdt_msg_rej_2_evt[AVDT_CCB_NUM_ACTIONS] = { }; \ No newline at end of file
diff --git a/stack/test/common/mock_stack_avdt_msg.h b/stack/test/common/mock_stack_avdt_msg.h
deleted file mode 100644
index 038ee79e6..000000000
--- a/stack/test/common/mock_stack_avdt_msg.h
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-/**
- * Get how many responses sent
- *
- * @return the count of responses.
- */
-size_t mock_avdt_msg_send_rsp_get_count(void);
-
-/**
- * Clear all the history of the sent responses.
- */
-void mock_avdt_msg_send_rsp_clear_history(void);
-
-/**
- * Get the nth (zero based) response's sig id
- *
- * @param nth response recorded since last time clear history
- * @return the sig id of the response
- *
- * @note undefined behavior if nth >= total count
- */
-uint8_t mock_avdt_msg_send_rsp_get_sig_id_at(size_t nth);
-
-/**
- * Get how many commands sent
- *
- * @return the count of commands.
- */
-size_t mock_avdt_msg_send_cmd_get_count(void);
-
-/**
- * Clear all the history of the sent commands.
- */
-void mock_avdt_msg_send_cmd_clear_history(void);
-
-/**
- * Get the nth (zero based) commands's sig id
- *
- * @param nth command recorded since last time clear history
- * @return the sig id of the command
- *
- * @note undefined behavior if nth >= total count
- */
-uint8_t mock_avdt_msg_send_cmd_get_sig_id_at(size_t nth); \ No newline at end of file
diff --git a/stack/test/common/mock_stack_l2cap_link.cc b/stack/test/common/mock_stack_l2cap_link.cc
deleted file mode 100644
index 8840d1d7b..000000000
--- a/stack/test/common/mock_stack_l2cap_link.cc
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-#define UNUSED_ATTR
-
-#include <cstdint>
-#include "stack/l2cap/l2c_int.h"
-BT_HDR* l2cu_get_next_buffer_to_send(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-bool l2c_link_hci_disc_comp(uint16_t handle, tHCI_REASON reason) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tBTM_STATUS l2cu_ConnectAclForSecurity(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tL2C_CCB* l2cu_get_next_channel_in_rr(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void l2c_OnHciModeChangeSendPendingPackets(RawAddress remote) {
- mock_function_count_map[__func__]++;
-}
-void l2c_info_resp_timer_timeout(void* data) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_adjust_allocation(void) { mock_function_count_map[__func__]++; }
-void l2c_link_adjust_chnl_allocation(void) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_check_send_pkts(tL2C_LCB* p_lcb, uint16_t local_cid,
- BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_hci_conn_comp(tHCI_STATUS status, uint16_t handle,
- const RawAddress& p_bda) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_hci_conn_req(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_init() { mock_function_count_map[__func__]++; }
-void l2c_link_process_num_completed_pkts(uint8_t* p, uint8_t evt_len) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_role_changed(const RawAddress* bd_addr, uint8_t new_role,
- uint8_t hci_status) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_sec_comp(const RawAddress* p_bda,
- UNUSED_ATTR tBT_TRANSPORT transport, void* p_ref_data,
- uint8_t status) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_sec_comp2(const RawAddress& p_bda,
- UNUSED_ATTR tBT_TRANSPORT transport, void* p_ref_data,
- uint8_t status) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_segments_xmitted(BT_HDR* p_msg) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_timeout(tL2C_LCB* p_lcb) { mock_function_count_map[__func__]++; }
-void l2c_packets_completed(uint16_t handle, uint16_t num_sent) {
- mock_function_count_map[__func__]++;
-}
-void l2c_pin_code_request(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void l2cble_update_sec_act(const RawAddress& bd_addr, uint16_t sec_act) {
- mock_function_count_map[__func__]++;
-}
diff --git a/stack/test/eatt/eatt_test.cc b/stack/test/eatt/eatt_test.cc
deleted file mode 100644
index 2a4191d08..000000000
--- a/stack/test/eatt/eatt_test.cc
+++ /dev/null
@@ -1,443 +0,0 @@
-/*
- * Copyright 2020 HIMSA II K/S - www.himsa.dk.
- * Represented by EHIMA - www.ehima.com
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-
-#include <vector>
-
-#include "base/bind_helpers.h"
-#include "btm_api.h"
-#include "l2c_api.h"
-#include "mock_btif_storage.h"
-#include "mock_btm_api_layer.h"
-#include "mock_controller.h"
-#include "mock_eatt.h"
-#include "mock_gatt_layer.h"
-#include "mock_l2cap_layer.h"
-
-using testing::_;
-using testing::DoAll;
-using testing::MockFunction;
-using testing::NiceMock;
-using testing::NotNull;
-using testing::Return;
-using testing::SaveArg;
-using testing::SaveArgPointee;
-using testing::StrictMock;
-
-using bluetooth::eatt::EattChannel;
-using bluetooth::eatt::EattChannelState;
-
-#define BLE_GATT_SVR_SUP_FEAT_EATT_BITMASK 0x01
-
-/* Needed for testing context */
-static tGATT_TCB test_tcb;
-void btif_storage_add_eatt_supported(const RawAddress& addr) { return; }
-void gatt_data_process(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_buf) { return; }
-tGATT_TCB* gatt_find_tcb_by_addr(const RawAddress& bda,
- tBT_TRANSPORT transport) {
- LOG(INFO) << __func__;
- return &test_tcb;
-}
-
-namespace {
-const RawAddress test_address({0x11, 0x11, 0x11, 0x11, 0x11, 0x11});
-
-class EattTest : public testing::Test {
- protected:
- void ConnectDeviceEattSupported(int num_of_accepted_connections) {
- ON_CALL(gatt_interface_, ClientReadSupportedFeatures)
- .WillByDefault(
- [](const RawAddress& addr,
- base::OnceCallback<void(const RawAddress&, uint8_t)> cb) {
- std::move(cb).Run(addr, BLE_GATT_SVR_SUP_FEAT_EATT_BITMASK);
- return true;
- });
- ON_CALL(gatt_interface_, GetEattSupport)
- .WillByDefault([](const RawAddress& addr) { return true; });
-
- std::vector<uint16_t> test_local_cids{61, 62, 63, 64, 65};
- EXPECT_CALL(l2cap_interface_,
- ConnectCreditBasedReq(BT_PSM_EATT, test_address, _))
- .WillOnce(Return(test_local_cids));
-
- eatt_instance_->Connect(test_address);
-
- int i = 0;
- for (uint16_t cid : test_local_cids) {
- EattChannel* channel =
- eatt_instance_->FindEattChannelByCid(test_address, cid);
- ASSERT_TRUE(channel != nullptr);
- ASSERT_TRUE(channel->state_ == EattChannelState::EATT_CHANNEL_PENDING);
-
- if (i < num_of_accepted_connections) {
- l2cap_app_info_.pL2CA_CreditBasedConnectCfm_Cb(
- test_address, cid, EATT_MIN_MTU_MPS, L2CAP_CONN_OK);
- connected_cids_.push_back(cid);
-
- ASSERT_TRUE(channel->state_ == EattChannelState::EATT_CHANNEL_OPENED);
- } else {
- l2cap_app_info_.pL2CA_Error_Cb(cid, L2CAP_CONN_NO_RESOURCES);
-
- EattChannel* channel =
- eatt_instance_->FindEattChannelByCid(test_address, cid);
- ASSERT_TRUE(channel == nullptr);
- }
- i++;
- }
-
- ASSERT_TRUE(test_tcb.eatt == num_of_accepted_connections);
- }
-
- void DisconnectEattByPeer(void) {
- for (uint16_t cid : connected_cids_)
- l2cap_app_info_.pL2CA_DisconnectInd_Cb(cid, true);
- ASSERT_TRUE(test_tcb.eatt == 0);
- }
-
- void DisconnectEattDevice(std::vector<uint16_t> cids) {
- EXPECT_CALL(l2cap_interface_, DisconnectRequest(_)).Times(cids.size());
- eatt_instance_->Disconnect(test_address);
-
- ASSERT_TRUE(test_tcb.eatt == 0);
- }
-
- void SetUp() override {
- bluetooth::l2cap::SetMockInterface(&l2cap_interface_);
- bluetooth::manager::SetMockBtmApiInterface(&btm_api_interface_);
- bluetooth::manager::SetMockBtifStorageInterface(&btif_storage_interface_);
- bluetooth::gatt::SetMockGattInterface(&gatt_interface_);
- controller::SetMockControllerInterface(&controller_interface);
-
- EXPECT_CALL(l2cap_interface_, RegisterLECoc(BT_PSM_EATT, _, _))
- .WillOnce(DoAll(SaveArg<1>(&l2cap_app_info_), Return(BT_PSM_EATT)));
-
- ON_CALL(btif_storage_interface_, LoadBondedEatt).WillByDefault([]() {
- return;
- });
-
- hci_role_ = HCI_ROLE_CENTRAL;
-
- ON_CALL(l2cap_interface_, GetBleConnRole(_))
- .WillByDefault(DoAll(Return(hci_role_)));
-
- ON_CALL(controller_interface, GetAclDataSizeBle())
- .WillByDefault(Return(128));
-
- eatt_instance_ = EattExtension::GetInstance();
- eatt_instance_->Start();
-
- Test::SetUp();
- }
-
- void TearDown() override {
- EXPECT_CALL(l2cap_interface_, DeregisterLECoc(BT_PSM_EATT)).Times(1);
-
- eatt_instance_->Stop();
- eatt_instance_ = nullptr;
- hci_role_ = 0;
- connected_cids_.clear();
-
- bluetooth::gatt::SetMockGattInterface(nullptr);
- bluetooth::l2cap::SetMockInterface(nullptr);
- bluetooth::manager::SetMockBtifStorageInterface(nullptr);
- bluetooth::manager::SetMockBtmApiInterface(nullptr);
- controller::SetMockControllerInterface(nullptr);
-
- Test::TearDown();
- }
-
- bluetooth::manager::MockBtifStorageInterface btif_storage_interface_;
- bluetooth::manager::MockBtmApiInterface btm_api_interface_;
- bluetooth::l2cap::MockL2capInterface l2cap_interface_;
- bluetooth::gatt::MockGattInterface gatt_interface_;
- controller::MockControllerInterface controller_interface;
-
- tL2CAP_APPL_INFO l2cap_app_info_;
- EattExtension* eatt_instance_;
- std::vector<uint16_t> connected_cids_;
- uint8_t hci_role_ = HCI_ROLE_CENTRAL;
-};
-
-TEST_F(EattTest, ConnectSucceed) {
- ConnectDeviceEattSupported(1);
- DisconnectEattDevice(connected_cids_);
-}
-
-TEST_F(EattTest, IncomingEattConnectionByUnknownDevice) {
- std::vector<uint16_t> incoming_cids{71, 72, 73, 74, 75};
-
- EXPECT_CALL(l2cap_interface_,
- ConnectCreditBasedRsp(test_address, 1, incoming_cids,
- L2CAP_CONN_NO_RESOURCES, _))
- .WillOnce(Return(true));
-
- l2cap_app_info_.pL2CA_CreditBasedConnectInd_Cb(
- test_address, incoming_cids, BT_PSM_EATT, EATT_MIN_MTU_MPS, 1);
-}
-
-TEST_F(EattTest, IncomingEattConnectionByKnownDevice) {
- hci_role_ = HCI_ROLE_PERIPHERAL;
- ON_CALL(gatt_interface_, ClientReadSupportedFeatures)
- .WillByDefault(
- [](const RawAddress& addr,
- base::OnceCallback<void(const RawAddress&, uint8_t)> cb) {
- std::move(cb).Run(addr, BLE_GATT_SVR_SUP_FEAT_EATT_BITMASK);
- return true;
- });
- ON_CALL(gatt_interface_, GetEattSupport)
- .WillByDefault([](const RawAddress& addr) { return true; });
-
- eatt_instance_->Connect(test_address);
- std::vector<uint16_t> incoming_cids{71, 72, 73, 74, 75};
-
- EXPECT_CALL(
- l2cap_interface_,
- ConnectCreditBasedRsp(test_address, 1, incoming_cids, L2CAP_CONN_OK, _))
- .WillOnce(Return(true));
-
- l2cap_app_info_.pL2CA_CreditBasedConnectInd_Cb(
- test_address, incoming_cids, BT_PSM_EATT, EATT_MIN_MTU_MPS, 1);
-
- DisconnectEattDevice(incoming_cids);
-
- hci_role_ = HCI_ROLE_CENTRAL;
-}
-
-TEST_F(EattTest, ReconnectInitiatedByRemoteSucceed) {
- ConnectDeviceEattSupported(1);
- DisconnectEattDevice(connected_cids_);
- std::vector<uint16_t> incoming_cids{71, 72, 73, 74, 75};
-
- EXPECT_CALL(
- l2cap_interface_,
- ConnectCreditBasedRsp(test_address, 1, incoming_cids, L2CAP_CONN_OK, _))
- .WillOnce(Return(true));
-
- l2cap_app_info_.pL2CA_CreditBasedConnectInd_Cb(
- test_address, incoming_cids, BT_PSM_EATT, EATT_MIN_MTU_MPS, 1);
-
- DisconnectEattDevice(incoming_cids);
-}
-
-TEST_F(EattTest, ConnectSucceedMultipleChannels) {
- ConnectDeviceEattSupported(5);
- DisconnectEattDevice(connected_cids_);
-}
-
-TEST_F(EattTest, ConnectFailedEattNotSupported) {
- ON_CALL(gatt_interface_, ClientReadSupportedFeatures)
- .WillByDefault(
- [](const RawAddress& addr,
- base::OnceCallback<void(const RawAddress&, uint8_t)> cb) {
- std::move(cb).Run(addr, 0);
- return true;
- });
- ON_CALL(gatt_interface_, GetEattSupport)
- .WillByDefault([](const RawAddress& addr) { return false; });
-
- EXPECT_CALL(l2cap_interface_,
- ConnectCreditBasedReq(BT_PSM_EATT, test_address, _))
- .Times(0);
- eatt_instance_->Connect(test_address);
- ASSERT_TRUE(eatt_instance_->IsEattSupportedByPeer(test_address) == false);
-}
-
-TEST_F(EattTest, ConnectFailedSlaveOnTheLink) {
- EXPECT_CALL(l2cap_interface_,
- ConnectCreditBasedReq(BT_PSM_EATT, test_address, _))
- .Times(0);
-
- hci_role_ = HCI_ROLE_PERIPHERAL;
- eatt_instance_->Connect(test_address);
-
- /* Back to default btm role */
- hci_role_ = HCI_ROLE_CENTRAL;
-}
-
-TEST_F(EattTest, DisonnectByPeerSucceed) {
- ConnectDeviceEattSupported(2);
-
- uint16_t cid = connected_cids_[0];
- EattChannel* channel =
- eatt_instance_->FindEattChannelByCid(test_address, cid);
- ASSERT_TRUE(channel->state_ == EattChannelState::EATT_CHANNEL_OPENED);
-
- DisconnectEattByPeer();
-
- channel = eatt_instance_->FindEattChannelByCid(test_address, cid);
- ASSERT_TRUE(channel == nullptr);
-}
-
-TEST_F(EattTest, ReconfigAllSucceed) {
- ConnectDeviceEattSupported(3);
-
- std::vector<uint16_t> cids;
- EXPECT_CALL(l2cap_interface_, ReconfigCreditBasedConnsReq(_, _, _))
- .WillOnce(DoAll(SaveArg<1>(&cids), Return(true)));
-
- uint16_t new_mtu = 300;
- eatt_instance_->ReconfigureAll(test_address, new_mtu);
-
- ASSERT_TRUE(cids.size() == connected_cids_.size());
-
- tL2CAP_LE_CFG_INFO cfg = {.result = L2CAP_CFG_OK, .mtu = new_mtu};
-
- for (uint16_t cid : cids) {
- l2cap_app_info_.pL2CA_CreditBasedReconfigCompleted_Cb(test_address, cid,
- true, &cfg);
-
- EattChannel* channel =
- eatt_instance_->FindEattChannelByCid(test_address, cid);
- ASSERT_TRUE(channel->state_ == EattChannelState::EATT_CHANNEL_OPENED);
- ASSERT_TRUE(channel->rx_mtu_ == new_mtu);
- }
-
- DisconnectEattDevice(connected_cids_);
-}
-
-TEST_F(EattTest, ReconfigAllFailed) {
- ConnectDeviceEattSupported(4);
-
- std::vector<uint16_t> cids;
- EXPECT_CALL(l2cap_interface_, ReconfigCreditBasedConnsReq(_, _, _))
- .WillOnce(DoAll(SaveArg<1>(&cids), Return(true)));
-
- uint16_t new_mtu = 300;
- eatt_instance_->ReconfigureAll(test_address, new_mtu);
-
- ASSERT_TRUE(cids.size() == connected_cids_.size());
-
- tL2CAP_LE_CFG_INFO cfg = {.result = L2CAP_CFG_FAILED_NO_REASON,
- .mtu = new_mtu};
-
- for (uint16_t cid : cids) {
- l2cap_app_info_.pL2CA_CreditBasedReconfigCompleted_Cb(test_address, cid,
- true, &cfg);
-
- EattChannel* channel =
- eatt_instance_->FindEattChannelByCid(test_address, cid);
- ASSERT_TRUE(channel->state_ == EattChannelState::EATT_CHANNEL_OPENED);
- ASSERT_TRUE(channel->rx_mtu_ != new_mtu);
- }
-
- DisconnectEattDevice(connected_cids_);
-}
-
-TEST_F(EattTest, ReconfigSingleSucceed) {
- ConnectDeviceEattSupported(2);
-
- std::vector<uint16_t> cids;
- EXPECT_CALL(l2cap_interface_, ReconfigCreditBasedConnsReq(_, _, _))
- .WillOnce(DoAll(SaveArg<1>(&cids), Return(true)));
-
- uint16_t new_mtu = 300;
- eatt_instance_->Reconfigure(test_address, connected_cids_[1], new_mtu);
-
- ASSERT_TRUE(cids.size() == 1);
-
- tL2CAP_LE_CFG_INFO cfg = {.result = L2CAP_CFG_OK, .mtu = new_mtu};
-
- auto it = std::find(connected_cids_.begin(), connected_cids_.end(), cids[0]);
- ASSERT_TRUE(it != connected_cids_.end());
-
- l2cap_app_info_.pL2CA_CreditBasedReconfigCompleted_Cb(test_address, cids[0],
- true, &cfg);
- EattChannel* channel =
- eatt_instance_->FindEattChannelByCid(test_address, cids[0]);
- ASSERT_TRUE(channel->state_ == EattChannelState::EATT_CHANNEL_OPENED);
- ASSERT_TRUE(channel->rx_mtu_ == new_mtu);
-
- DisconnectEattDevice(connected_cids_);
-}
-
-TEST_F(EattTest, ReconfigSingleFailed) {
- ConnectDeviceEattSupported(2);
-
- std::vector<uint16_t> cids;
- EXPECT_CALL(l2cap_interface_, ReconfigCreditBasedConnsReq(_, _, _))
- .WillOnce(DoAll(SaveArg<1>(&cids), Return(true)));
-
- uint16_t new_mtu = 300;
- eatt_instance_->ReconfigureAll(test_address, new_mtu);
-
- ASSERT_TRUE(cids.size() == connected_cids_.size());
-
- tL2CAP_LE_CFG_INFO cfg = {.result = L2CAP_CFG_FAILED_NO_REASON,
- .mtu = new_mtu};
-
- auto it = std::find(connected_cids_.begin(), connected_cids_.end(), cids[0]);
- ASSERT_TRUE(it != connected_cids_.end());
-
- l2cap_app_info_.pL2CA_CreditBasedReconfigCompleted_Cb(test_address, cids[0],
- true, &cfg);
- EattChannel* channel =
- eatt_instance_->FindEattChannelByCid(test_address, cids[0]);
- ASSERT_TRUE(channel->state_ == EattChannelState::EATT_CHANNEL_OPENED);
- ASSERT_TRUE(channel->rx_mtu_ != new_mtu);
-
- DisconnectEattDevice(connected_cids_);
-}
-
-TEST_F(EattTest, ReconfigPeerSucceed) {
- ConnectDeviceEattSupported(3);
-
- uint16_t new_mtu = 300;
- tL2CAP_LE_CFG_INFO cfg = {.result = L2CAP_CFG_OK, .mtu = new_mtu};
-
- for (uint16_t cid : connected_cids_) {
- l2cap_app_info_.pL2CA_CreditBasedReconfigCompleted_Cb(test_address, cid,
- false, &cfg);
-
- EattChannel* channel =
- eatt_instance_->FindEattChannelByCid(test_address, cid);
- ASSERT_TRUE(channel->state_ == EattChannelState::EATT_CHANNEL_OPENED);
- ASSERT_TRUE(channel->tx_mtu_ == new_mtu);
- }
-
- DisconnectEattDevice(connected_cids_);
-}
-
-TEST_F(EattTest, ReconfigPeerFailed) {
- ConnectDeviceEattSupported(2);
-
- uint16_t new_mtu = 300;
- tL2CAP_LE_CFG_INFO cfg = {.result = L2CAP_CFG_FAILED_NO_REASON,
- .mtu = new_mtu};
-
- for (uint16_t cid : connected_cids_) {
- l2cap_app_info_.pL2CA_CreditBasedReconfigCompleted_Cb(test_address, cid,
- false, &cfg);
-
- EattChannel* channel =
- eatt_instance_->FindEattChannelByCid(test_address, cid);
- ASSERT_TRUE(channel->state_ == EattChannelState::EATT_CHANNEL_OPENED);
- ASSERT_TRUE(channel->tx_mtu_ != new_mtu);
- }
-
- DisconnectEattDevice(connected_cids_);
-}
-
-TEST_F(EattTest, DoubleDisconnect) {
- ConnectDeviceEattSupported(1);
- DisconnectEattDevice(connected_cids_);
-
- /* Force second disconnect */
- eatt_instance_->Disconnect(test_address);
-}
-} // namespace
diff --git a/stack/test/fuzzers/Android.bp b/stack/test/fuzzers/Android.bp
deleted file mode 100644
index c26720982..000000000
--- a/stack/test/fuzzers/Android.bp
+++ /dev/null
@@ -1,62 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_defaults {
- name: "libbt-stack_fuzz_defaults",
- defaults: ["fluoride_defaults"],
- include_dirs: [
- "system/bt/",
- "system/bt/include/",
- "system/bt/types/",
- "system/bt/internal_include/",
- "system/bt/stack/include",
- "system/bt/stack/test",
- ],
- static_libs: [
- "libbt-stack",
- "libbte",
- "libFraunhoferAAC",
- "libbt-audio-hal-interface",
- "libbtcore",
- "libbt-bta",
- "libbt-stack",
- "libbt-common",
- "libbt-sbc-decoder",
- "libbt-sbc-encoder",
- "libbt-utils",
- "libbtif",
- "libbt-hci",
- "libbtdevice",
- "libg722codec",
- "libosi",
- "libudrv-uipc",
- "libbt-protos-lite",
- "libbluetooth_gd",
- ],
- shared_libs: [
- "libbinder",
- "libbase",
- "libcutils",
- "liblog",
- "android.hardware.bluetooth@1.0",
- "android.hardware.bluetooth@1.1",
- "android.hardware.bluetooth.a2dp@1.0",
- "android.hardware.bluetooth.audio@2.0",
- "android.hardware.bluetooth.audio@2.1",
- "android.system.suspend.control-V1-ndk",
- "libaaudio",
- "libbinder_ndk",
- "libfmq",
- "libhidlbase",
- "libprocessgroup",
- "libprotobuf-cpp-lite",
- "libutils",
- "libcrypto",
- ],
-}
diff --git a/stack/test/fuzzers/a2dp/Android.bp b/stack/test/fuzzers/a2dp/Android.bp
deleted file mode 100644
index b39a8022a..000000000
--- a/stack/test/fuzzers/a2dp/Android.bp
+++ /dev/null
@@ -1,16 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "a2dp_fuzz",
- defaults: ["libbt-stack_fuzz_defaults"],
- srcs: [
- "fuzz_a2dp.cc",
- ],
-}
diff --git a/stack/test/fuzzers/a2dp/a2dpFuzzFunctions.h b/stack/test/fuzzers/a2dp/a2dpFuzzFunctions.h
deleted file mode 100644
index 819ee9a78..000000000
--- a/stack/test/fuzzers/a2dp/a2dpFuzzFunctions.h
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BT_STACK_FUZZ_A2DP_FUNCTIONS_H_
-#define BT_STACK_FUZZ_A2DP_FUNCTIONS_H_
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <vector>
-#include "a2dp_api.h"
-#include "osi/include/allocator.h"
-#include "raw_address.h"
-#include "stack/a2dp/a2dp_int.h"
-
-#include "fuzzers/a2dp/a2dpFuzzHelpers.h"
-#include "fuzzers/common/commonFuzzHelpers.h"
-#include "fuzzers/sdp/sdpFuzzFunctions.h"
-
-#define MAX_STR_LEN 4096
-
-/* This is a vector of lambda functions the fuzzer will pull from.
- * This is done so new functions can be added to the fuzzer easily
- * without requiring modifications to the main fuzzer file. This also
- * allows multiple fuzzers to include this file, if functionality is needed.
- */
-std::vector<std::function<void(FuzzedDataProvider*)>> a2dp_operations = {
- // Init
- [](FuzzedDataProvider*) -> void {
- // Re-init zeros out memory containing some pointers.
- // Free the db first to prevent memleaks
- if (a2dp_cb.find.p_db) {
- osi_free(a2dp_cb.find.p_db);
- }
-
- // Attempt re-initializations mid-run.
- A2DP_Init();
- },
-
- // A2DP_AddRecord
- [](FuzzedDataProvider* fdp) -> void {
- std::vector<char> p_service_name =
- fdp->ConsumeBytesWithTerminator<char>(MAX_STR_LEN);
- std::vector<char> p_provider_name =
- fdp->ConsumeBytesWithTerminator<char>(MAX_STR_LEN);
- A2DP_AddRecord(fdp->ConsumeIntegral<uint16_t>(), p_service_name.data(),
- p_provider_name.data(), fdp->ConsumeIntegral<uint16_t>(),
- // This should be a val returned by SDP_CreateRecord
- getArbitraryVectorElement(fdp, sdp_record_handles, true));
- },
-
- // A2DP_FindService
- [](FuzzedDataProvider* fdp) -> void {
- tA2DP_SDP_DB_PARAMS p_db = generateDBParams(fdp);
- const RawAddress bd_addr = generateRawAddress(fdp);
- A2DP_FindService(fdp->ConsumeIntegral<uint16_t>(), bd_addr, &p_db,
- a2dp_find_callback);
- },
-
- // A2DP_GetAvdtpVersion
- [](FuzzedDataProvider*) -> void { A2DP_GetAvdtpVersion(); },
-
- // A2DP_SetTraceLevel
- [](FuzzedDataProvider* fdp) -> void {
- // Expected val is [0-5], 0xff but other values are supported so fuzz all
- A2DP_SetTraceLevel(fdp->ConsumeIntegral<uint8_t>());
- },
-
- // A2DP_BitsSet
- [](FuzzedDataProvider* fdp) -> void {
- A2DP_BitsSet(fdp->ConsumeIntegral<uint64_t>());
- },
-
- // SDP Calls
- [](FuzzedDataProvider* fdp) -> void {
- callArbitraryFunction(fdp, sdp_operations);
- }};
-
-#endif // BT_STACK_FUZZ_A2DP_FUNCTIONS_H_
diff --git a/stack/test/fuzzers/a2dp/a2dpFuzzHelpers.h b/stack/test/fuzzers/a2dp/a2dpFuzzHelpers.h
deleted file mode 100644
index 428bf351a..000000000
--- a/stack/test/fuzzers/a2dp/a2dpFuzzHelpers.h
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BT_STACK_FUZZ_A2DP_HELPERS_H_
-#define BT_STACK_FUZZ_A2DP_HELPERS_H_
-
-// NOTE: This file should not be included directly.
-// It is included by the corresponding "...Functions.h" file.
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <vector>
-#include "bt_target.h"
-#include "bt_trace.h"
-#include "fuzzers/sdp/sdpFuzzHelpers.h"
-#include "osi/include/allocator.h"
-#include "stack/a2dp/a2dp_int.h"
-
-#define MAX_DB_SIZE 4096
-
-tA2DP_SDP_DB_PARAMS generateDBParams(FuzzedDataProvider* fdp) {
- std::vector<uint16_t> attr_list = generateArbitraryAttrList(fdp);
-
- tA2DP_SDP_DB_PARAMS db_params;
- db_params.db_len = fdp->ConsumeIntegralInRange<uint32_t>(0, MAX_DB_SIZE);
- db_params.num_attr = attr_list.size();
- db_params.p_attrs = attr_list.empty() ? nullptr : attr_list.data();
-
- return db_params;
-}
-
-// Define our empty callback function
-void a2dp_find_callback(bool found, tA2DP_Service* p_service,
- const RawAddress& peer_address) {
- // Free the RawAddress we created in the generate function
- delete &peer_address;
-}
-
-// Function to clean up and clear our allocated objects
-void cleanupA2dpFuzz() {
- // Delete our a2dp_cb database if it exists
- if (a2dp_cb.find.p_db) {
- osi_free(a2dp_cb.find.p_db);
- }
- // This function resets the a2dp_cb global to defaults
- A2DP_Init();
-
- // SDP needs to perform cleanup as well.
- cleanupSdpFuzz();
-}
-
-#endif // BT_STACK_FUZZ_A2DP_HELPERS_H_
diff --git a/stack/test/fuzzers/a2dp/codec/Android.bp b/stack/test/fuzzers/a2dp/codec/Android.bp
deleted file mode 100644
index 12691a3c9..000000000
--- a/stack/test/fuzzers/a2dp/codec/Android.bp
+++ /dev/null
@@ -1,41 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_defaults {
- name: "libbt-stack_fuzz_codec_defaults",
- defaults: ["libbt-stack_fuzz_defaults"],
- include_dirs: [
- "system/bt/bta/include/", // For tBT_A2DP_OFFLOAD
- "system/bt/bta/sys/", // For tBT_A2DP_OFFLOAD
- ],
-}
-
-cc_fuzz {
- name: "a2dp_codec_fuzz",
- defaults: ["libbt-stack_fuzz_codec_defaults"],
- srcs: [
- "fuzz_a2dp_codec.cc",
- ],
-}
-
-cc_fuzz {
- name: "a2dp_codec_info_fuzz",
- defaults: ["libbt-stack_fuzz_codec_defaults"],
- srcs: [
- "fuzz_a2dp_codec_info.cc",
- ],
-}
-
-cc_fuzz {
- name: "a2dp_codec_cfg_fuzz",
- defaults: ["libbt-stack_fuzz_codec_defaults"],
- srcs: [
- "fuzz_a2dp_codec_config.cc",
- ],
-}
diff --git a/stack/test/fuzzers/a2dp/codec/a2dpCodecConfigFuzzFunctions.h b/stack/test/fuzzers/a2dp/codec/a2dpCodecConfigFuzzFunctions.h
deleted file mode 100644
index cc15a834c..000000000
--- a/stack/test/fuzzers/a2dp/codec/a2dpCodecConfigFuzzFunctions.h
+++ /dev/null
@@ -1,227 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BT_STACK_FUZZ_A2DP_CODECCONFIG_FUNCTIONS_H_
-#define BT_STACK_FUZZ_A2DP_CODECCONFIG_FUNCTIONS_H_
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <vector>
-#include "a2dp_codec_api.h"
-#include "fuzzers/a2dp/codec/a2dpCodecHelperFunctions.h"
-#include "fuzzers/a2dp/codec/a2dpCodecInfoFuzzFunctions.h"
-#include "fuzzers/common/commonFuzzHelpers.h"
-
-#include "fuzzers/a2dp/codec/a2dpCodecConfigFuzzHelpers.h"
-
-/* This is a vector of lambda functions the fuzzer will pull from.
- * This is done so new functions can be added to the fuzzer easily
- * without requiring modifications to the main fuzzer file. This also
- * allows multiple fuzzers to include this file, if functionality is needed.
- */
-std::vector<std::function<void(FuzzedDataProvider*)>>
- a2dp_codec_config_operations = {
- // createCodec
- [](FuzzedDataProvider* fdp) -> void {
- // Generate our arguments
- btav_a2dp_codec_index_t codec_index = getArbitraryBtavCodecIndex(fdp);
- btav_a2dp_codec_priority_t codec_priority =
- getArbitraryBtavCodecPriority(fdp);
- // Create our new codec
- std::shared_ptr<A2dpCodecConfig> codec_config(
- A2dpCodecConfig::createCodec(codec_index, codec_priority));
- // Push it to our vector
- if (codec_config) {
- a2dp_codec_config_vect.push_back(codec_config);
- }
- },
-
- // A2dpCodecConfig Destructor
- [](FuzzedDataProvider* fdp) -> void {
- if (a2dp_codec_config_vect.empty()) {
- return;
- }
- // Get random vector index
- size_t index = fdp->ConsumeIntegralInRange<size_t>(
- 0, a2dp_codec_config_vect.size() - 1);
- // Remove from vector
- a2dp_codec_config_vect.erase(a2dp_codec_config_vect.begin() + index);
- },
-
- // codecIndex
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- codec_config->codecIndex();
- },
-
- // name
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- codec_config->name();
- },
-
- // codecPriority
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- codec_config->codecPriority();
- },
-
- // getCodecSpecificConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- tBT_A2DP_OFFLOAD a2dp_offload = generateArbitrarytA2dpOffload(fdp);
- codec_config->getCodecSpecificConfig(&a2dp_offload);
- },
-
- // getTrackBitRate
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- codec_config->getTrackBitRate();
- },
-
- // copyOutOtaCodecConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- uint8_t* codec_info =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, true);
- codec_config->copyOutOtaCodecConfig(codec_info);
- },
-
- // getCodecConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- codec_config->getCodecConfig();
- },
-
- // getCodecCapability
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- codec_config->getCodecCapability();
- },
-
- // getCodecLocalCapability
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- codec_config->getCodecLocalCapability();
- },
-
- // getCodecSelectableCapability
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- codec_config->getCodecSelectableCapability();
- },
-
- // getCodecUserConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- codec_config->getCodecUserConfig();
- },
-
- // getCodecAudioConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- codec_config->getCodecAudioConfig();
- },
-
- // getAudioBitsPerSample
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- codec_config->getAudioBitsPerSample();
- },
-
- // getAudioBitsPerSample
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecConfig> codec_config(
- getArbitraryVectorElement(fdp, a2dp_codec_config_vect, false));
- if (codec_config == nullptr) {
- return;
- }
-
- const btav_a2dp_codec_config_t btav_codec_config =
- getArbitraryBtavCodecConfig(fdp);
- codec_config->isCodecConfigEmpty(btav_codec_config);
- },
-
- // Dependency calling: CodecInfo
- [](FuzzedDataProvider* fdp) -> void {
- callArbitraryCodecInfoFunction(fdp, a2dp_codec_info_operations);
- }};
-
-#endif // BT_STACK_FUZZ_A2DP_CODECCONFIG_FUNCTIONS_H_
diff --git a/stack/test/fuzzers/a2dp/codec/a2dpCodecConfigFuzzHelpers.h b/stack/test/fuzzers/a2dp/codec/a2dpCodecConfigFuzzHelpers.h
deleted file mode 100644
index 66c3fb790..000000000
--- a/stack/test/fuzzers/a2dp/codec/a2dpCodecConfigFuzzHelpers.h
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BT_STACK_FUZZ_A2DP_CODECCONFIG_HELPERS_H_
-#define BT_STACK_FUZZ_A2DP_CODECCONFIG_HELPERS_H_
-
-// NOTE: This file should not be included directly.
-// It is included by the corresponding "...Functions.h" file.
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <vector>
-#include "a2dp_codec_api.h"
-#include "fuzzers/a2dp/codec/a2dpCodecInfoFuzzHelpers.h"
-
-// Keep a vector of our initialized codec_config objects
-// It will be up to the caller to free this array at the end of a fuzz loop
-std::vector<std::shared_ptr<A2dpCodecConfig>> a2dp_codec_config_vect;
-
-// Function to clean up and clear our allocated objects
-void cleanupA2dpCodecConfigFuzz() {
- a2dp_codec_config_vect.clear();
-
- // Cleanup dependencies
- cleanupA2dpCodecInfoFuzz();
-}
-
-#endif // BT_STACK_FUZZ_A2DP_CODECCONFIG_HELPERS_H_
diff --git a/stack/test/fuzzers/a2dp/codec/a2dpCodecFuzzFunctions.h b/stack/test/fuzzers/a2dp/codec/a2dpCodecFuzzFunctions.h
deleted file mode 100644
index 8cacd336f..000000000
--- a/stack/test/fuzzers/a2dp/codec/a2dpCodecFuzzFunctions.h
+++ /dev/null
@@ -1,341 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BT_STACK_FUZZ_A2DP_CODEC_FUNCTIONS_H_
-#define BT_STACK_FUZZ_A2DP_CODEC_FUNCTIONS_H_
-
-#include <fcntl.h> // For fd
-#include <fuzzer/FuzzedDataProvider.h>
-#include <sys/stat.h> // For fd
-#include <vector>
-#include "a2dp_codec_api.h"
-#include "fuzzers/a2dp/codec/a2dpCodecHelperFunctions.h"
-#include "fuzzers/a2dp/codec/a2dpCodecInfoFuzzFunctions.h"
-#include "fuzzers/common/commonFuzzHelpers.h"
-
-#include "fuzzers/a2dp/codec/a2dpCodecFuzzHelpers.h"
-
-#define MAX_NUM_PROPERTIES 128
-#define A2DP_MAX_INIT_RUNS 16
-
-/* This is a vector of lambda functions the fuzzer will pull from.
- * This is done so new functions can be added to the fuzzer easily
- * without requiring modifications to the main fuzzer file. This also
- * allows multiple fuzzers to include this file, if functionality is needed.
- */
-std::vector<std::function<void(FuzzedDataProvider*)>> a2dp_codec_operations = {
- // A2dpCodecs Constructor
- [](FuzzedDataProvider* fdp) -> void {
- // Build out a vector of codec objects
- std::vector<btav_a2dp_codec_config_t> codec_priorities;
- size_t num_priorities =
- fdp->ConsumeIntegralInRange<size_t>(0, MAX_NUM_PROPERTIES);
- for (size_t i = 0; i < num_priorities; i++) {
- codec_priorities.push_back(getArbitraryBtavCodecConfig(fdp));
- }
- // Construct a const ref so we can pass to constructor
- const std::vector<btav_a2dp_codec_config_t>& codec_priorities_const =
- codec_priorities;
- std::shared_ptr<A2dpCodecs> codecs(
- new A2dpCodecs(codec_priorities_const));
- if (codecs) {
- a2dp_codecs_vect.push_back(codecs);
- }
- },
-
- // A2dpCodecs Destructor
- [](FuzzedDataProvider* fdp) -> void {
- if (a2dp_codecs_vect.empty()) {
- return;
- }
- // Get random vector index
- size_t index =
- fdp->ConsumeIntegralInRange<size_t>(0, a2dp_codecs_vect.size() - 1);
- // Remove from vector
- a2dp_codecs_vect.erase(a2dp_codecs_vect.begin() + index);
- },
-
- // init
- [](FuzzedDataProvider* fdp) -> void {
- // Limit the number of times we can call this function per iteration
- // (This is to prevent slow-units)
- if (a2dp_init_runs <= A2DP_MAX_INIT_RUNS) {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs) {
- a2dp_init_runs++;
- codecs->init();
- }
- }
- },
-
- // findSourceCodecConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- uint8_t* p_codec_info =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
-
- if (codecs && p_codec_info) {
- codecs->findSourceCodecConfig(p_codec_info);
- }
- },
-
- // findSinkCodecConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- uint8_t* p_codec_info =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
-
- if (codecs && p_codec_info) {
- codecs->findSinkCodecConfig(p_codec_info);
- }
- },
-
- // isSupportedCodec
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs) {
- codecs->isSupportedCodec(getArbitraryBtavCodecIndex(fdp));
- }
- },
-
- // getCurrentCodecConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs) {
- codecs->getCurrentCodecConfig();
- }
- },
-
- // orderedSourceCodecs
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs) {
- codecs->orderedSourceCodecs();
- }
- },
-
- // orderedSinkCodecs
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs) {
- codecs->orderedSinkCodecs();
- }
- },
-
- // setCodecConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs == nullptr) {
- return;
- }
-
- const uint8_t* peer_codec_info =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
- if (peer_codec_info == nullptr) {
- return;
- }
-
- // Codec_config is actually some buffer
- std::unique_ptr<uint8_t, void (*)(void*)> p_result_codec_config(
- reinterpret_cast<uint8_t*>(calloc(500, sizeof(uint8_t))), free);
- if (p_result_codec_config) {
- codecs->setCodecConfig(peer_codec_info, fdp->ConsumeBool(),
- p_result_codec_config.get(), fdp->ConsumeBool());
- }
- },
-
- // setSinkCodecConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs == nullptr) {
- return;
- }
-
- const uint8_t* peer_codec_info =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
- if (peer_codec_info == nullptr) {
- return;
- }
-
- // Codec_config is actually some buffer
- std::unique_ptr<uint8_t, void (*)(void*)> p_result_codec_config(
- reinterpret_cast<uint8_t*>(calloc(500, sizeof(uint8_t))), free);
- if (p_result_codec_config) {
- codecs->setSinkCodecConfig(peer_codec_info, fdp->ConsumeBool(),
- p_result_codec_config.get(),
- fdp->ConsumeBool());
- }
- },
-
- // setCodecUserConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs == nullptr) {
- return;
- }
-
- const btav_a2dp_codec_config_t codec_user_config =
- getArbitraryBtavCodecConfig(fdp);
- const tA2DP_ENCODER_INIT_PEER_PARAMS p_peer_params =
- getArbitraryA2dpEncoderInitPeerParams(fdp);
- const uint8_t* p_peer_sink_capabilities =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
- if (p_peer_sink_capabilities == nullptr) {
- return;
- }
-
- // Craft our result variables (And possibly pass nullptrs)
- btav_a2dp_codec_config_t result_codec_config;
- bool restart_input, restart_output, config_updated;
- uint8_t* p_result_codec_config =
- reinterpret_cast<uint8_t*>(&result_codec_config);
- codecs->setCodecUserConfig(codec_user_config, &p_peer_params,
- p_peer_sink_capabilities,
- p_result_codec_config, &restart_input,
- &restart_output, &config_updated);
- },
-
- // setCodecAudioConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs == nullptr) {
- return;
- }
-
- const btav_a2dp_codec_config_t codec_audio_config =
- getArbitraryBtavCodecConfig(fdp);
- const tA2DP_ENCODER_INIT_PEER_PARAMS p_peer_params =
- getArbitraryA2dpEncoderInitPeerParams(fdp);
- const uint8_t* p_peer_sink_capabilities =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
- if (p_peer_sink_capabilities == nullptr) {
- return;
- }
- btav_a2dp_codec_config_t result_codec_config;
- uint8_t* p_result_codec_config =
- reinterpret_cast<uint8_t*>(&result_codec_config);
- bool p_restart_output, p_config_updated;
- codecs->setCodecAudioConfig(
- codec_audio_config, &p_peer_params, p_peer_sink_capabilities,
- p_result_codec_config, &p_restart_output, &p_config_updated);
- },
-
- // setCodecOtaConfig
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs == nullptr) {
- return;
- }
-
- const uint8_t* p_ota_codec_config =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
- if (p_ota_codec_config == nullptr) {
- return;
- }
-
- const tA2DP_ENCODER_INIT_PEER_PARAMS p_peer_params =
- getArbitraryA2dpEncoderInitPeerParams(fdp);
- btav_a2dp_codec_config_t result_codec_config;
- uint8_t* p_result_codec_config =
- reinterpret_cast<uint8_t*>(&result_codec_config);
- bool p_restart_input, p_restart_output, p_config_updated;
- codecs->setCodecOtaConfig(p_ota_codec_config, &p_peer_params,
- p_result_codec_config, &p_restart_input,
- &p_restart_output, &p_config_updated);
- },
-
- // setPeerSinkCodecCapabilities
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs == nullptr) {
- return;
- }
-
- const uint8_t* p_peer_codec_capabilities =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
- if (p_peer_codec_capabilities == nullptr) {
- return;
- }
- codecs->setPeerSinkCodecCapabilities(p_peer_codec_capabilities);
- },
-
- // setPeerSourceCodecCapabilities
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs == nullptr) {
- return;
- }
-
- const uint8_t* p_peer_codec_capabilities =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
- if (p_peer_codec_capabilities == nullptr) {
- return;
- }
- codecs->setPeerSourceCodecCapabilities(p_peer_codec_capabilities);
- },
-
- // getCodecConfigAndCapabilities
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs == nullptr) {
- return;
- }
-
- // Return objects
- std::vector<btav_a2dp_codec_config_t> codecs_local_capabilities;
- std::vector<btav_a2dp_codec_config_t> codecs_selectable_capabilities;
- btav_a2dp_codec_config_t codec_config;
- codecs->getCodecConfigAndCapabilities(&codec_config,
- &codecs_local_capabilities,
- &codecs_selectable_capabilities);
- },
-
- // debug_codec_dump
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<A2dpCodecs> codecs =
- getArbitraryVectorElement(fdp, a2dp_codecs_vect, false);
- if (codecs == nullptr) {
- return;
- }
-
- // Dump this to /dev/null
- int fd = open("/dev/null", O_WRONLY);
- codecs->debug_codec_dump(fd);
- close(fd);
- },
-
- // Since we're dependent on having valid codec_info objects,
- // have a change to call fuzz functions for that
- [](FuzzedDataProvider* fdp) -> void {
- callArbitraryCodecInfoFunction(fdp, a2dp_codec_info_operations);
- }};
-
-#endif // BT_STACK_FUZZ_A2DP_CODEC_FUNCTIONS_H_
diff --git a/stack/test/fuzzers/a2dp/codec/a2dpCodecFuzzHelpers.h b/stack/test/fuzzers/a2dp/codec/a2dpCodecFuzzHelpers.h
deleted file mode 100644
index 18c2be0cd..000000000
--- a/stack/test/fuzzers/a2dp/codec/a2dpCodecFuzzHelpers.h
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BT_STACK_FUZZ_A2DP_CODEC_HELPERS_H_
-#define BT_STACK_FUZZ_A2DP_CODEC_HELPERS_H_
-
-// NOTE: This file should not be included directly.
-// It is included by the corresponding "...Functions.h" file.
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <vector>
-#include "a2dp_codec_api.h"
-#include "fuzzers/a2dp/codec/a2dpCodecInfoFuzzHelpers.h"
-
-// Keep a vector of any allocated A2dpCodecs objects.
-// It will be up to the caller to free this array at the end of a fuzz loop
-std::vector<std::shared_ptr<A2dpCodecs>> a2dp_codecs_vect;
-
-uint16_t a2dp_init_runs = 0;
-
-// Function to clean up and clear our allocated objects
-void cleanupA2dpCodecFuzz() {
- // Clean up our vector
- a2dp_codecs_vect.clear();
-
- // Reset the number of times we've called init
- a2dp_init_runs = 0;
-
- // Clean up dependencies
- cleanupA2dpCodecInfoFuzz();
-}
-
-#endif // BT_STACK_FUZZ_A2DP_CODEC_HELPERS_H_
diff --git a/stack/test/fuzzers/a2dp/codec/a2dpCodecHelperFunctions.h b/stack/test/fuzzers/a2dp/codec/a2dpCodecHelperFunctions.h
deleted file mode 100644
index 5b3848abd..000000000
--- a/stack/test/fuzzers/a2dp/codec/a2dpCodecHelperFunctions.h
+++ /dev/null
@@ -1,171 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef A2DP_CODEC_HELPERFUNCTIONS_H_
-#define A2DP_CODEC_HELPERFUNCTIONS_H_
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <vector>
-
-// =============================================================================
-static const std::vector<const btav_a2dp_codec_index_t> CODEC_INDEX_ENUM_VALS =
- {BTAV_A2DP_CODEC_INDEX_SOURCE_MIN,
- BTAV_A2DP_CODEC_INDEX_SOURCE_SBC,
- BTAV_A2DP_CODEC_INDEX_SOURCE_AAC,
- BTAV_A2DP_CODEC_INDEX_SOURCE_APTX,
- BTAV_A2DP_CODEC_INDEX_SOURCE_APTX_HD,
- BTAV_A2DP_CODEC_INDEX_SOURCE_LDAC,
- BTAV_A2DP_CODEC_INDEX_SOURCE_MAX,
- BTAV_A2DP_CODEC_INDEX_SINK_MIN,
- BTAV_A2DP_CODEC_INDEX_SINK_SBC,
- BTAV_A2DP_CODEC_INDEX_SINK_AAC,
- BTAV_A2DP_CODEC_INDEX_SINK_LDAC,
- BTAV_A2DP_CODEC_INDEX_SINK_MAX,
- BTAV_A2DP_CODEC_INDEX_MIN,
- BTAV_A2DP_CODEC_INDEX_MAX};
-
-static const std::vector<const btav_a2dp_codec_priority_t>
- CODEC_PRIORITY_ENUM_VALS = {BTAV_A2DP_CODEC_PRIORITY_DISABLED,
- BTAV_A2DP_CODEC_PRIORITY_DEFAULT,
- BTAV_A2DP_CODEC_PRIORITY_HIGHEST};
-
-static const std::vector<const btav_a2dp_codec_sample_rate_t>
- CODEC_SAMPLERATE_ENUM_VALS = {
- BTAV_A2DP_CODEC_SAMPLE_RATE_NONE, BTAV_A2DP_CODEC_SAMPLE_RATE_44100,
- BTAV_A2DP_CODEC_SAMPLE_RATE_48000, BTAV_A2DP_CODEC_SAMPLE_RATE_88200,
- BTAV_A2DP_CODEC_SAMPLE_RATE_96000, BTAV_A2DP_CODEC_SAMPLE_RATE_176400,
- BTAV_A2DP_CODEC_SAMPLE_RATE_192000, BTAV_A2DP_CODEC_SAMPLE_RATE_16000,
- BTAV_A2DP_CODEC_SAMPLE_RATE_24000};
-
-static const std::vector<const btav_a2dp_codec_bits_per_sample_t>
- CODEC_BPS_ENUM_VALS = {BTAV_A2DP_CODEC_BITS_PER_SAMPLE_NONE,
- BTAV_A2DP_CODEC_BITS_PER_SAMPLE_16,
- BTAV_A2DP_CODEC_BITS_PER_SAMPLE_24,
- BTAV_A2DP_CODEC_BITS_PER_SAMPLE_32};
-
-static const std::vector<const btav_a2dp_codec_channel_mode_t>
- CODEC_CHANNELMODE_ENUM_VALS = {BTAV_A2DP_CODEC_CHANNEL_MODE_NONE,
- BTAV_A2DP_CODEC_CHANNEL_MODE_MONO,
- BTAV_A2DP_CODEC_CHANNEL_MODE_STEREO};
-
-// Construct a btav_a2dp_codec_index_t object
-btav_a2dp_codec_index_t getArbitraryBtavCodecIndex(FuzzedDataProvider* fdp) {
- return CODEC_INDEX_ENUM_VALS.at(
- fdp->ConsumeIntegralInRange<size_t>(0, CODEC_INDEX_ENUM_VALS.size() - 1));
-}
-
-// Construct a btav_a2dp_codec_priority_t object
-btav_a2dp_codec_priority_t getArbitraryBtavCodecPriority(
- FuzzedDataProvider* fdp) {
- return CODEC_PRIORITY_ENUM_VALS.at(fdp->ConsumeIntegralInRange<size_t>(
- 0, CODEC_PRIORITY_ENUM_VALS.size() - 1));
-}
-// Construct a btav_a2dp_codec_sample_rate_t object
-btav_a2dp_codec_sample_rate_t getArbitraryBtavCodecSampleRate(
- FuzzedDataProvider* fdp) {
- return CODEC_SAMPLERATE_ENUM_VALS.at(fdp->ConsumeIntegralInRange<size_t>(
- 0, CODEC_SAMPLERATE_ENUM_VALS.size() - 1));
-}
-// Construct a btav_a2dp_codec_bits_per_sample_t object
-btav_a2dp_codec_bits_per_sample_t getArbitraryBtavCodecBitsPerSample(
- FuzzedDataProvider* fdp) {
- return CODEC_BPS_ENUM_VALS.at(
- fdp->ConsumeIntegralInRange<size_t>(0, CODEC_BPS_ENUM_VALS.size() - 1));
-}
-// Construct a btav_a2dp_codec_channel_mode_t object
-btav_a2dp_codec_channel_mode_t getArbitraryBtavCodecChannelMode(
- FuzzedDataProvider* fdp) {
- return CODEC_CHANNELMODE_ENUM_VALS.at(fdp->ConsumeIntegralInRange<size_t>(
- 0, CODEC_CHANNELMODE_ENUM_VALS.size() - 1));
-}
-// Construct a btav_a2dp_codec_config_t object
-btav_a2dp_codec_config_t getArbitraryBtavCodecConfig(FuzzedDataProvider* fdp) {
- btav_a2dp_codec_config_t config;
-
- config.codec_type = getArbitraryBtavCodecIndex(fdp);
- config.codec_priority = getArbitraryBtavCodecPriority(fdp);
- config.sample_rate = getArbitraryBtavCodecSampleRate(fdp);
- config.bits_per_sample = getArbitraryBtavCodecBitsPerSample(fdp);
- config.channel_mode = getArbitraryBtavCodecChannelMode(fdp);
- config.codec_specific_1 = fdp->ConsumeIntegral<int64_t>();
- config.codec_specific_2 = fdp->ConsumeIntegral<int64_t>();
- config.codec_specific_3 = fdp->ConsumeIntegral<int64_t>();
- config.codec_specific_4 = fdp->ConsumeIntegral<int64_t>();
-
- return config;
-}
-// =============================================================================
-tA2DP_ENCODER_INIT_PEER_PARAMS getArbitraryA2dpEncoderInitPeerParams(
- FuzzedDataProvider* fdp) {
- tA2DP_ENCODER_INIT_PEER_PARAMS params;
-
- params.is_peer_edr = fdp->ConsumeBool();
- params.peer_supports_3mbps = fdp->ConsumeBool();
- params.peer_mtu = fdp->ConsumeIntegral<uint16_t>();
-
- return params;
-}
-// =============================================================================
-#include "bt_types.h"
-#define MAX_BTHDR_SIZE 1024
-std::shared_ptr<BT_HDR> getArbitraryBtHdr(FuzzedDataProvider* fdp) {
- // Build a data buffer
- size_t buf_size = fdp->ConsumeIntegralInRange<size_t>(0, MAX_BTHDR_SIZE);
- std::vector<uint8_t> bytes = fdp->ConsumeBytes<uint8_t>(buf_size);
-
- if (bytes.empty()) {
- return nullptr;
- }
-
- uint16_t hdr_size = bytes.size() + sizeof(BT_HDR);
- std::shared_ptr<BT_HDR> bt_hdr(
- reinterpret_cast<BT_HDR*>(calloc(hdr_size, sizeof(uint8_t))), free);
-
- bt_hdr->event = fdp->ConsumeIntegral<uint16_t>();
- bt_hdr->len = bytes.size();
- bt_hdr->offset =
- fdp->ConsumeIntegralInRange<uint16_t>(0, hdr_size - sizeof(BT_HDR));
- bt_hdr->layer_specific = fdp->ConsumeIntegral<uint16_t>();
- std::copy(bytes.begin(), bytes.end(), bt_hdr->data);
-
- return bt_hdr;
-}
-// =============================================================================
-#include "bta/av/bta_av_int.h"
-tBT_A2DP_OFFLOAD generateArbitrarytA2dpOffload(FuzzedDataProvider* fdp) {
- tBT_A2DP_OFFLOAD retval;
-
- retval.codec_type = fdp->ConsumeIntegral<uint32_t>();
- retval.max_latency = fdp->ConsumeIntegral<uint16_t>();
- std::vector<uint8_t> scms_t_enable = fdp->ConsumeBytes<uint8_t>(2);
- memcpy(&retval.scms_t_enable[0], scms_t_enable.data(), scms_t_enable.size());
- retval.sample_rate = fdp->ConsumeIntegral<uint32_t>();
- retval.bits_per_sample = fdp->ConsumeIntegral<uint8_t>();
- retval.ch_mode = fdp->ConsumeIntegral<uint8_t>();
- retval.encoded_audio_bitrate = fdp->ConsumeIntegral<uint32_t>();
- retval.acl_hdl = fdp->ConsumeIntegral<uint16_t>();
- retval.l2c_rcid = fdp->ConsumeIntegral<uint16_t>();
- retval.mtu = fdp->ConsumeIntegral<uint16_t>();
-
- std::vector<uint8_t> codec_info_bytes = fdp->ConsumeBytes<uint8_t>(32);
- memcpy(&retval.codec_info[0], codec_info_bytes.data(),
- codec_info_bytes.size());
-
- return retval;
-}
-// =============================================================================
-
-#endif // A2DP_CODEC_HELPERFUNCTIONS_H_
diff --git a/stack/test/fuzzers/a2dp/codec/a2dpCodecInfoFuzzFunctions.h b/stack/test/fuzzers/a2dp/codec/a2dpCodecInfoFuzzFunctions.h
deleted file mode 100644
index 187b474d7..000000000
--- a/stack/test/fuzzers/a2dp/codec/a2dpCodecInfoFuzzFunctions.h
+++ /dev/null
@@ -1,215 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BT_STACK_FUZZ_A2DP_CODECINFO_FUNCTIONS_H_
-#define BT_STACK_FUZZ_A2DP_CODECINFO_FUNCTIONS_H_
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <vector>
-#include "a2dp_codec_api.h"
-#include "bt_types.h"
-#include "fuzzers/a2dp/codec/a2dpCodecHelperFunctions.h"
-#include "fuzzers/common/commonFuzzHelpers.h"
-
-#include "fuzzers/a2dp/codec/a2dpCodecInfoFuzzHelpers.h"
-
-#define MAX_PACKET_SIZE 2048
-
-/* This is a vector of lambda functions the fuzzer will pull from.
- * This is done so new functions can be added to the fuzzer easily
- * without requiring modifications to the main fuzzer file. This also
- * allows multiple fuzzers to include this file, if functionality is needed.
- */
-std::vector<std::function<void(FuzzedDataProvider*, uint8_t*)>>
- a2dp_codec_info_operations = {
- // A2DP_InitDefaultCodec
- [](FuzzedDataProvider* fdp, uint8_t*) -> void {
- // Allocate space for a new codec & add it to our tracking vector
- uint8_t* codec_info = new uint8_t[AVDT_CODEC_SIZE];
- a2dp_codec_info_vect.push_back(codec_info);
-
- A2DP_InitDefaultCodec(codec_info);
- },
-
- // Delete a codec_info object
- [](FuzzedDataProvider* fdp, uint8_t*) -> void {
- if (a2dp_codec_info_vect.empty()) {
- return;
- }
- // Get random vector index
- size_t index = fdp->ConsumeIntegralInRange<size_t>(
- 0, a2dp_codec_info_vect.size() - 1);
- // delete codec
- delete a2dp_codec_info_vect.at(index);
- // Remove from vector
- a2dp_codec_info_vect.erase(a2dp_codec_info_vect.begin() + index);
- },
-
- // A2DP_GetCodecType
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_GetCodecType(codec_info);
- },
-
- // A2DP_IsSourceCodecValid
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_IsSourceCodecValid(codec_info);
- },
-
- // A2DP_IsSinkCodecValid
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_IsSinkCodecValid(codec_info);
- },
-
- // A2DP_IsPeerSourceCodecValid
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_IsPeerSourceCodecValid(codec_info);
- },
-
- // A2DP_IsPeerSinkCodecValid
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_IsPeerSinkCodecValid(codec_info);
- },
-
- // A2DP_IsSinkCodecSupported
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_IsSinkCodecSupported(codec_info);
- },
-
- // A2DP_IsPeerSourceCodecSupported
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_IsPeerSourceCodecSupported(codec_info);
- },
-
- // A2DP_UsesRtpHeader
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_UsesRtpHeader(fdp->ConsumeBool(), codec_info);
- },
-
- // A2DP_GetMediaType
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_GetMediaType(codec_info);
- },
-
- // A2DP_CodecName
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_CodecName(codec_info);
- },
-
- // A2DP_CodecTypeEquals
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- uint8_t* codec_info_2 =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
- if (codec_info_2) {
- A2DP_CodecTypeEquals(codec_info, codec_info_2);
- }
- },
-
- // A2DP_CodecEquals
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- uint8_t* codec_info_2 =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
- if (codec_info_2) {
- A2DP_CodecEquals(codec_info, codec_info_2);
- }
- },
-
- // A2DP_GetTrackSampleRate
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_GetTrackSampleRate(codec_info);
- },
-
- // A2DP_GetTrackBitsPerSample
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_GetTrackBitsPerSample(codec_info);
- },
-
- // A2DP_GetTrackChannelCount
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_GetTrackChannelCount(codec_info);
- },
-
- // A2DP_GetSinkTrackChannelType
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_GetSinkTrackChannelType(codec_info);
- },
-
- // A2DP_GetPacketTimestamp
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- uint32_t timestamp_retval;
- size_t packet_size =
- fdp->ConsumeIntegralInRange<size_t>(0, MAX_PACKET_SIZE);
- std::vector<uint8_t> bytes = fdp->ConsumeBytes<uint8_t>(packet_size);
- // Timestamp will fail if p_data is < 4 bytes, due to a cast & deref
- // to a uint32_t*
- if (bytes.size() < 4) {
- return;
- }
- const uint8_t* p_data = bytes.data();
-
- A2DP_GetPacketTimestamp(codec_info, p_data, &timestamp_retval);
- },
-
- // A2DP_BuildCodecHeader
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- std::shared_ptr<BT_HDR> p_buf = getArbitraryBtHdr(fdp);
- if (p_buf) {
- uint16_t frames_per_packet = fdp->ConsumeIntegral<uint16_t>();
- A2DP_BuildCodecHeader(codec_info, p_buf.get(), frames_per_packet);
- }
- },
-
- // A2DP_GetEncoderInterface
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_GetEncoderInterface(codec_info);
- },
-
- // A2DP_GetDecoderInterface
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_GetDecoderInterface(codec_info);
- },
-
- // A2DP_AdjustCodec
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_AdjustCodec(codec_info);
- },
-
- // A2DP_SourceCodecIndex
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_SourceCodecIndex(codec_info);
- },
-
- // A2DP_SinkCodecIndex
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_SinkCodecIndex(codec_info);
- },
-
- // A2DP_CodecIndexStr
- [](FuzzedDataProvider* fdp, uint8_t*) -> void {
- A2DP_CodecIndexStr(getArbitraryBtavCodecIndex(fdp));
- },
-
- // A2DP_InitCodecConfig
- [](FuzzedDataProvider* fdp, uint8_t*) -> void {
- AvdtpSepConfig cfg_retval;
- A2DP_InitCodecConfig(getArbitraryBtavCodecIndex(fdp), &cfg_retval);
- },
-
- // A2DP_CodecInfoString
- [](FuzzedDataProvider* fdp, uint8_t* codec_info) -> void {
- A2DP_CodecInfoString(codec_info);
- }};
-
-#endif // BT_STACK_FUZZ_A2DP_CODECINFO_FUNCTIONS_H_
diff --git a/stack/test/fuzzers/a2dp/codec/a2dpCodecInfoFuzzHelpers.h b/stack/test/fuzzers/a2dp/codec/a2dpCodecInfoFuzzHelpers.h
deleted file mode 100644
index fc1e2c2c8..000000000
--- a/stack/test/fuzzers/a2dp/codec/a2dpCodecInfoFuzzHelpers.h
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BT_STACK_FUZZ_A2DP_CODECINFO_HELPERS_H_
-#define BT_STACK_FUZZ_A2DP_CODECINFO_HELPERS_H_
-
-// NOTE: This file should not be included directly.
-// It is included by the corresponding "...Functions.h" file.
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <vector>
-#include "a2dp_codec_api.h"
-#include "bt_types.h"
-
-// Keep a vector of any allocated codec_info objects.
-// It will be up to the caller to free this array at the end of a fuzz loop
-std::vector<uint8_t*> a2dp_codec_info_vect;
-
-// Calls a function from the ops_vector
-void callArbitraryCodecInfoFunction(
- FuzzedDataProvider* fdp,
- std::vector<std::function<void(FuzzedDataProvider*, uint8_t*)>>
- ops_vector) {
- // Choose which function we'll be calling
- uint8_t function_id =
- fdp->ConsumeIntegralInRange<uint8_t>(0, ops_vector.size() - 1);
-
- // Get a info object
- uint8_t* codec_info =
- getArbitraryVectorElement(fdp, a2dp_codec_info_vect, false);
-
- // Most functions require a valid codec_info
- if (codec_info || function_id == 0 || function_id == 25 ||
- function_id == 26) {
- // Call the function we've chosen
- ops_vector[function_id](fdp, codec_info);
- }
-}
-
-// Function to clean up and clear our allocated objects
-void cleanupA2dpCodecInfoFuzz() {
- for (auto it : a2dp_codec_info_vect) {
- if (it != nullptr) {
- delete it;
- }
- }
- a2dp_codec_info_vect.clear();
-}
-
-#endif // BT_STACK_FUZZ_A2DP_CODECINFO_HELPERS_H_
diff --git a/stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec.cc b/stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec.cc
deleted file mode 100644
index 9dd201345..000000000
--- a/stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec.cc
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "fuzzers/a2dp/codec/a2dpCodecFuzzFunctions.h"
-#include "fuzzers/common/commonFuzzHelpers.h"
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Call some functions
- while (dataProvider.remaining_bytes() > 0) {
- callArbitraryFunction(&dataProvider, a2dp_codec_operations);
- }
-
- // Cleanup our state
- cleanupA2dpCodecFuzz();
-
- return 0;
-}
diff --git a/stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec_config.cc b/stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec_config.cc
deleted file mode 100644
index 97cac26c7..000000000
--- a/stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec_config.cc
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "fuzzers/a2dp/codec/a2dpCodecConfigFuzzFunctions.h"
-#include "fuzzers/common/commonFuzzHelpers.h"
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Call some functions
- while (dataProvider.remaining_bytes() > 0) {
- callArbitraryFunction(&dataProvider, a2dp_codec_config_operations);
- }
-
- // Cleanup our state
- cleanupA2dpCodecConfigFuzz();
-
- return 0;
-}
diff --git a/stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec_info.cc b/stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec_info.cc
deleted file mode 100644
index 93eacc8da..000000000
--- a/stack/test/fuzzers/a2dp/codec/fuzz_a2dp_codec_info.cc
+++ /dev/null
@@ -1,34 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "fuzzers/a2dp/codec/a2dpCodecInfoFuzzFunctions.h"
-#include "fuzzers/common/commonFuzzHelpers.h"
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Call some functions
- while (dataProvider.remaining_bytes() > 0) {
- callArbitraryCodecInfoFunction(&dataProvider, a2dp_codec_info_operations);
- }
-
- // Cleanup our state
- cleanupA2dpCodecInfoFuzz();
-
- return 0;
-}
diff --git a/stack/test/fuzzers/a2dp/fuzz_a2dp.cc b/stack/test/fuzzers/a2dp/fuzz_a2dp.cc
deleted file mode 100644
index 34ef7d31c..000000000
--- a/stack/test/fuzzers/a2dp/fuzz_a2dp.cc
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "a2dp_api.h"
-#include "fuzzers/a2dp/a2dpFuzzFunctions.h"
-#include "fuzzers/common/commonFuzzHelpers.h"
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* Data, size_t Size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(Data, Size);
-
- // Call SDP setup as we'll be using that object as well
- setupSdpFuzz();
-
- // Call some functions
- while (dataProvider.remaining_bytes() > 0) {
- callArbitraryFunction(&dataProvider, a2dp_operations);
- }
-
- // Cleanup
- cleanupA2dpFuzz();
-
- return 0;
-}
diff --git a/stack/test/fuzzers/common/commonFuzzHelpers.h b/stack/test/fuzzers/common/commonFuzzHelpers.h
deleted file mode 100644
index b138c5fac..000000000
--- a/stack/test/fuzzers/common/commonFuzzHelpers.h
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef BT_STACK_FUZZ_COMMON_HELPERS_H_
-#define BT_STACK_FUZZ_COMMON_HELPERS_H_
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <cstring> // For memcpy
-#include <vector>
-#include "raw_address.h"
-#include "sdp_api.h"
-
-// Calls a function from the ops_vector
-void callArbitraryFunction(
- FuzzedDataProvider* fdp,
- std::vector<std::function<void(FuzzedDataProvider*)>> ops_vector) {
- // Choose which function we'll be calling
- uint8_t function_id =
- fdp->ConsumeIntegralInRange<uint8_t>(0, ops_vector.size() - 1);
-
- // Call the function we've chosen
- ops_vector[function_id](fdp);
-}
-
-template <class T>
-T getArbitraryVectorElement(FuzzedDataProvider* fdp, std::vector<T> vect,
- bool allow_null) {
- // If we're allowing null, give it a 50:50 shot at returning a zero element
- // (Or if the vector's empty)
- if (vect.empty() || (allow_null && fdp->ConsumeBool())) {
- return static_cast<T>(0);
- }
-
- // Otherwise, return an element from our vector
- return vect.at(fdp->ConsumeIntegralInRange<size_t>(0, vect.size() - 1));
-}
-
-RawAddress generateRawAddress(FuzzedDataProvider* fdp) {
- RawAddress retval;
-
- // Zero address
- for (int i = 0; i < 6; i++) {
- retval.address[i] = 0;
- }
-
- // Read as much as we can from the buffer and copy it in
- std::vector<uint8_t> bytes = fdp->ConsumeBytes<uint8_t>(retval.kLength);
- memcpy(retval.address, bytes.data(), bytes.size());
-
- return retval;
-}
-
-bluetooth::Uuid generateArbitraryUuid(FuzzedDataProvider* fdp) {
- std::vector<uint8_t> bytes_vect =
- fdp->ConsumeBytes<uint8_t>(bluetooth::Uuid::kNumBytes128);
- // We need it to be the correct size regardless of if fdp ran out of bytes
- while (bytes_vect.size() < bluetooth::Uuid::kNumBytes128) {
- bytes_vect.push_back('\0');
- }
-
- return bluetooth::Uuid::From128BitBE(bytes_vect.data());
-}
-
-#endif // BT_STACK_FUZZ_COMMON_HELPERS_H_
diff --git a/stack/test/fuzzers/sdp/Android.bp b/stack/test/fuzzers/sdp/Android.bp
deleted file mode 100644
index 79b5c393a..000000000
--- a/stack/test/fuzzers/sdp/Android.bp
+++ /dev/null
@@ -1,16 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-cc_fuzz {
- name: "sdp_fuzz",
- defaults: ["libbt-stack_fuzz_defaults"],
- srcs: [
- "fuzz_sdp.cc",
- ],
-}
diff --git a/stack/test/fuzzers/sdp/fuzz_sdp.cc b/stack/test/fuzzers/sdp/fuzz_sdp.cc
deleted file mode 100644
index 20e773de7..000000000
--- a/stack/test/fuzzers/sdp/fuzz_sdp.cc
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include "fuzzers/common/commonFuzzHelpers.h"
-#include "fuzzers/sdp/sdpFuzzFunctions.h"
-
-extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
- // Init our wrapper
- FuzzedDataProvider dataProvider(data, size);
-
- setupSdpFuzz();
-
- // Call some functions
- while (dataProvider.remaining_bytes() > 0) {
- callArbitraryFunction(&dataProvider, sdp_operations);
- }
-
- // Cleanup our state
- cleanupSdpFuzz();
-
- return 0;
-}
diff --git a/stack/test/fuzzers/sdp/sdpFuzzFunctions.h b/stack/test/fuzzers/sdp/sdpFuzzFunctions.h
deleted file mode 100644
index e39312342..000000000
--- a/stack/test/fuzzers/sdp/sdpFuzzFunctions.h
+++ /dev/null
@@ -1,331 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef FUZZER_SDP_FUNCTIONS_H_
-#define FUZZER_SDP_FUNCTIONS_H_
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <vector>
-#include "fuzzers/common/commonFuzzHelpers.h"
-#include "fuzzers/sdp/sdpFuzzHelpers.h"
-#include "sdp_api.h"
-
-#define SDP_MAX_DB_LEN 1024 * 1024 // 1 MB
-#define MAX_NUM_DBS 64
-
-/* This is a vector of lambda functions the fuzzer will pull from.
- * This is done so new functions can be added to the fuzzer easily
- * without requiring modifications to the main fuzzer file. This also
- * allows multiple fuzzers to include this file, if functionality is needed.
- */
-static const std::vector<std::function<void(FuzzedDataProvider*)>>
- sdp_operations = {
- // SDP_InitDiscoveryDb
- [](FuzzedDataProvider* fdp) -> void {
- if (sdp_db_vect.size() >= MAX_NUM_DBS) {
- return;
- }
-
- // build out uuid_list
- std::vector<bluetooth::Uuid> uuid_list;
- uint8_t num_uuids = fdp->ConsumeIntegral<uint8_t>();
- for (uint8_t i = 0; i < num_uuids; i++) {
- uuid_list.push_back(generateArbitraryUuid(fdp));
- }
-
- // build out attr_list
- std::vector<uint16_t> attr_list = generateArbitraryAttrList(fdp);
-
- uint32_t db_size =
- fdp->ConsumeIntegralInRange<uint32_t>(0, SDP_MAX_DB_LEN);
- std::shared_ptr<tSDP_DISCOVERY_DB> p_db(
- reinterpret_cast<tSDP_DISCOVERY_DB*>(malloc(db_size)), free);
- if (p_db) {
- bool success = SDP_InitDiscoveryDb(
- p_db.get(), db_size, uuid_list.size(), uuid_list.data(),
- attr_list.size(),
- reinterpret_cast<uint16_t*>(attr_list.data()));
- if (success) {
- sdp_db_vect.push_back(p_db);
- }
- }
- },
-
- // SDP_CancelServiceSearch
- [](FuzzedDataProvider* fdp) -> void {
- SDP_CancelServiceSearch(
- getArbitraryVectorElement(fdp, sdp_db_vect, true).get());
- },
-
- // SDP_ServiceSearchRequest
- [](FuzzedDataProvider* fdp) -> void {
- const RawAddress bd_addr = generateRawAddress(fdp);
- tSDP_DISCOVERY_DB* db =
- getArbitraryVectorElement(fdp, sdp_db_vect, false).get();
- if (db) {
- SDP_ServiceSearchRequest(bd_addr, db, &sdp_disc_cmpl_cb);
- }
- },
-
- // SDP_ServiceSearchAttributeRequest
- [](FuzzedDataProvider* fdp) -> void {
- const RawAddress bd_addr = generateRawAddress(fdp);
- tSDP_DISCOVERY_DB* db =
- getArbitraryVectorElement(fdp, sdp_db_vect, false).get();
- if (db) {
- SDP_ServiceSearchAttributeRequest(bd_addr, db, &sdp_disc_cmpl_cb);
- }
- },
-
- // SDP_ServiceSearchAttributeRequest2
- [](FuzzedDataProvider* fdp) -> void {
- const RawAddress bd_addr = generateRawAddress(fdp);
- std::vector<uint8_t> user_data = fdp->ConsumeBytes<uint8_t>(
- fdp->ConsumeIntegralInRange<size_t>(0, 1024));
- tSDP_DISCOVERY_DB* db =
- getArbitraryVectorElement(fdp, sdp_db_vect, false).get();
-
- if (db) {
- SDP_ServiceSearchAttributeRequest2(bd_addr, db, &sdp_disc_cmpl_cb2,
- user_data.data());
- }
- },
-
- // SDP_FindAttributeInRec
- [](FuzzedDataProvider* fdp) -> void {
- tSDP_DISC_REC* p_rec =
- generateArbitrarySdpDiscRecord(fdp, false).get();
- SDP_FindAttributeInRec(p_rec, fdp->ConsumeIntegral<uint16_t>());
- },
-
- // SDP_FindServiceInDb
- [](FuzzedDataProvider* fdp) -> void {
- SDP_FindServiceInDb(
- getArbitraryVectorElement(fdp, sdp_db_vect, true).get(),
- fdp->ConsumeIntegral<uint16_t>(),
- generateArbitrarySdpDiscRecord(fdp, true).get());
- },
-
- // SDP_FindServiceUUIDInDb
- [](FuzzedDataProvider* fdp) -> void {
- const bluetooth::Uuid uuid = generateArbitraryUuid(fdp);
- SDP_FindServiceUUIDInDb(
- getArbitraryVectorElement(fdp, sdp_db_vect, true).get(), uuid,
- generateArbitrarySdpDiscRecord(fdp, true).get());
- },
-
- // SDP_FindServiceUUIDInRec_128bit
- [](FuzzedDataProvider* fdp) -> void {
- bluetooth::Uuid uuid = generateArbitraryUuid(fdp);
- tSDP_DISC_REC* p_rec =
- generateArbitrarySdpDiscRecord(fdp, false).get();
- SDP_FindServiceUUIDInRec_128bit(p_rec, &uuid);
- },
-
- // SDP_FindServiceInDb_128bit
- [](FuzzedDataProvider* fdp) -> void {
- SDP_FindServiceInDb_128bit(
- getArbitraryVectorElement(fdp, sdp_db_vect, true).get(),
- generateArbitrarySdpDiscRecord(fdp, true).get());
- },
-
- // SDP_FindProtocolListElemInRec
- [](FuzzedDataProvider* fdp) -> void {
- tSDP_PROTOCOL_ELEM elem = generateArbitrarySdpProtocolElements(fdp);
- tSDP_DISC_REC* p_rec =
- generateArbitrarySdpDiscRecord(fdp, false).get();
- SDP_FindProtocolListElemInRec(p_rec, fdp->ConsumeIntegral<uint16_t>(),
- &elem);
- },
-
- // SDP_FindProfileVersionInRec
- [](FuzzedDataProvider* fdp) -> void {
- uint16_t p_version;
- tSDP_DISC_REC* p_rec =
- generateArbitrarySdpDiscRecord(fdp, false).get();
-
- SDP_FindProfileVersionInRec(p_rec, fdp->ConsumeIntegral<uint16_t>(),
- &p_version);
- },
-
- // SDP_CreateRecord
- [](FuzzedDataProvider* fdp) -> void {
- uint32_t handle = SDP_CreateRecord();
- if (handle) {
- sdp_record_handles.push_back(handle);
- }
- },
-
- // SDP_DeleteRecord
- [](FuzzedDataProvider* fdp) -> void {
- SDP_DeleteRecord(
- getArbitraryVectorElement(fdp, sdp_record_handles, true));
- },
-
- // SDP_AddAttribute
- [](FuzzedDataProvider* fdp) -> void {
- std::vector<uint8_t> val = fdp->ConsumeBytes<uint8_t>(
- fdp->ConsumeIntegralInRange<size_t>(1, 1024));
- if (val.size() > 0) {
- SDP_AddAttribute(
- getArbitraryVectorElement(fdp, sdp_record_handles, true),
- fdp->ConsumeIntegral<uint16_t>(),
- fdp->ConsumeIntegral<uint8_t>(), val.size(), val.data());
- }
- },
-
- // SDP_AddSequence
- [](FuzzedDataProvider* fdp) -> void {
- SDP_Sequence_Helper seq = generateArbitrarySdpElemSequence(fdp);
-
- SDP_AddSequence(
- getArbitraryVectorElement(fdp, sdp_record_handles, true),
- fdp->ConsumeIntegral<uint16_t>(), seq.num_elem, seq.type.get(),
- seq.len.get(), seq.p_val.get());
- },
-
- // SDP_AddUuidSequence
- [](FuzzedDataProvider* fdp) -> void {
- uint16_t num_uuids = fdp->ConsumeIntegralInRange<uint16_t>(1, 64);
- uint16_t* uuids = new uint16_t[num_uuids];
- for (uint16_t i = 0; i < num_uuids; i++) {
- uuids[i] = fdp->ConsumeIntegral<uint16_t>();
- }
-
- SDP_AddUuidSequence(
- getArbitraryVectorElement(fdp, sdp_record_handles, true),
- fdp->ConsumeIntegral<uint16_t>(), num_uuids, uuids);
- delete[] uuids;
- },
-
- // SDP_AddProtocolList
- [](FuzzedDataProvider* fdp) -> void {
- std::shared_ptr<tSDP_PROTO_LIST_ELEM> p_proto_list =
- generateArbitrarySdpProtocolElementList(fdp);
- if (p_proto_list) {
- SDP_AddProtocolList(
- getArbitraryVectorElement(fdp, sdp_record_handles, true),
- p_proto_list.get()->num_elems, p_proto_list.get()->list_elem);
- }
- },
-
- // SDP_AddAdditionProtoLists
- [](FuzzedDataProvider* fdp) -> void {
- uint16_t arr_size;
- tSDP_PROTO_LIST_ELEM** p_proto_list =
- generateArbitrarySdpProtocolElementListArray(fdp, &arr_size);
- if (p_proto_list) {
- if (p_proto_list[0]) {
- SDP_AddAdditionProtoLists(
- getArbitraryVectorElement(fdp, sdp_record_handles, true),
- arr_size, p_proto_list[0]);
- for (uint16_t i = 0; i < arr_size; i++) {
- delete p_proto_list[i];
- }
- }
- free(p_proto_list);
- }
- },
-
- // SDP_AddProfileDescriptorList
- [](FuzzedDataProvider* fdp) -> void {
- SDP_AddProfileDescriptorList(
- getArbitraryVectorElement(fdp, sdp_record_handles, true),
- fdp->ConsumeIntegral<uint16_t>(),
- fdp->ConsumeIntegral<uint16_t>());
- },
-
- // SDP_AddLanguageBaseAttrIDList
- [](FuzzedDataProvider* fdp) -> void {
- SDP_AddLanguageBaseAttrIDList(
- getArbitraryVectorElement(fdp, sdp_record_handles, true),
- fdp->ConsumeIntegral<uint16_t>(),
- fdp->ConsumeIntegral<uint16_t>(),
- fdp->ConsumeIntegral<uint16_t>());
- },
-
- // SDP_AddServiceClassIdList
- [](FuzzedDataProvider* fdp) -> void {
- uint16_t num_services = fdp->ConsumeIntegralInRange<uint16_t>(0, 64);
- uint16_t* service_uuids = new uint16_t[num_services];
- for (uint16_t i = 0; i < num_services; i++) {
- service_uuids[i] = fdp->ConsumeIntegral<uint16_t>();
- }
-
- SDP_AddServiceClassIdList(
- getArbitraryVectorElement(fdp, sdp_record_handles, true),
- num_services, service_uuids);
-
- delete[] service_uuids;
- },
-
- // SDP_DeleteAttribute
- [](FuzzedDataProvider* fdp) -> void {
- SDP_DeleteAttribute(
- getArbitraryVectorElement(fdp, sdp_record_handles, true),
- fdp->ConsumeIntegral<uint16_t>());
- },
-
- // SDP_SetLocalDiRecord
- [](FuzzedDataProvider* fdp) -> void {
- uint32_t handle; // Output var
- tSDP_DI_RECORD device_info = generateArbitrarySdpDiRecord(fdp);
- SDP_SetLocalDiRecord(&device_info, &handle);
- },
-
- // SDP_DiDiscover
- [](FuzzedDataProvider* fdp) -> void {
- const RawAddress remote_device = generateRawAddress(fdp);
-
- // Create a new buffer for the discoveryDB init call
- uint32_t db_size =
- fdp->ConsumeIntegralInRange<uint32_t>(0, SDP_MAX_DB_LEN);
- std::shared_ptr<tSDP_DISCOVERY_DB> p_db(
- reinterpret_cast<tSDP_DISCOVERY_DB*>(malloc(db_size)), free);
- if (p_db) {
- SDP_DiDiscover(remote_device, p_db.get(), db_size,
- &sdp_disc_cmpl_cb);
- }
- },
-
- // SDP_GetNumDiRecords
- [](FuzzedDataProvider* fdp) -> void {
- SDP_GetNumDiRecords(
- getArbitraryVectorElement(fdp, sdp_db_vect, true).get());
- },
-
- // SDP_GetDiRecord
- [](FuzzedDataProvider* fdp) -> void {
- tSDP_DI_GET_RECORD device_info; // Output var
- SDP_GetDiRecord(
- fdp->ConsumeIntegral<uint8_t>(), &device_info,
- getArbitraryVectorElement(fdp, sdp_db_vect, true).get());
- },
-
- // SDP_SetTraceLevel
- [](FuzzedDataProvider* fdp) -> void {
- SDP_SetTraceLevel(fdp->ConsumeIntegral<uint8_t>());
- },
-
- // SDP_FindServiceUUIDInRec
- [](FuzzedDataProvider* fdp) -> void {
- tSDP_DISC_REC* p_rec =
- generateArbitrarySdpDiscRecord(fdp, false).get();
- bluetooth::Uuid uuid; // Output var
- SDP_FindServiceUUIDInRec(p_rec, &uuid);
- }};
-
-#endif // FUZZER_SDP_FUNCTIONS_H_
diff --git a/stack/test/fuzzers/sdp/sdpFuzzHelpers.h b/stack/test/fuzzers/sdp/sdpFuzzHelpers.h
deleted file mode 100644
index bae17854c..000000000
--- a/stack/test/fuzzers/sdp/sdpFuzzHelpers.h
+++ /dev/null
@@ -1,273 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#ifndef FUZZER_SDP_HELPERS_H_
-#define FUZZER_SDP_HELPERS_H_
-
-// NOTE: This file should not be included directly.
-// It is included by the corresponding "...Functions.h" file.
-
-#include <fuzzer/FuzzedDataProvider.h>
-#include <algorithm>
-#include <vector>
-#include "fuzzers/common/commonFuzzHelpers.h"
-#include "osi/include/alarm.h"
-#include "stack/sdp/sdpint.h"
-
-#define SDP_MAX_NUM_ELEMS 128
-#define SDP_MAX_ELEM_LEN 1024
-#define SDP_MAX_ATTRS 1024
-
-struct SDP_Sequence_Helper {
- uint8_t num_elem;
- std::shared_ptr<uint8_t> type;
- std::shared_ptr<uint8_t> len;
- std::shared_ptr<uint8_t*> p_val;
- std::vector<std::shared_ptr<uint8_t>> p_val_buffers;
-};
-
-// Keep a vector of our initialized db objects
-// It will be up to the caller to free this array at the end of a fuzz loop
-std::vector<std::shared_ptr<tSDP_DISCOVERY_DB>> sdp_db_vect;
-std::vector<uint32_t> sdp_record_handles;
-std::vector<SDP_Sequence_Helper> sdp_sequence_vect;
-std::vector<std::shared_ptr<tSDP_DISC_REC>> sdp_disc_rec_vect;
-std::vector<std::shared_ptr<tSDP_DISC_ATTR>> sdp_disc_attr_vect;
-std::vector<std::shared_ptr<tSDP_PROTO_LIST_ELEM>> sdp_protolist_elem_vect;
-
-std::shared_ptr<tSDP_DISC_ATTR> generateArbitrarySdpDiscAttr(
- FuzzedDataProvider*, bool);
-
-static bool initialized = false;
-void setupSdpFuzz() {
- if (!initialized) {
- sdp_init();
- initialized = true;
- }
-}
-
-// Function to clean up and clear any allocated objects
-void cleanupSdpFuzz() {
- // Delete sdp_sequence_vect, sdp_disc_rec_vect, sdp_disc_attr_vect
- sdp_sequence_vect.clear();
-
- sdp_disc_rec_vect.clear();
-
- // Delete attributes & protolist elements
- sdp_disc_attr_vect.clear();
- sdp_protolist_elem_vect.clear();
-
- // Delete all records
- SDP_DeleteRecord(0);
- sdp_record_handles.clear();
-
- // Delete Databases
- sdp_db_vect.clear();
-
- // Set SDP Trace level back to default
- SDP_SetTraceLevel(0);
-}
-
-std::vector<uint16_t> generateArbitraryAttrList(FuzzedDataProvider* fdp) {
- // build out attr_list
- uint16_t num_attrs = fdp->ConsumeIntegralInRange<uint16_t>(0, SDP_MAX_ATTRS);
-
- std::vector<uint16_t> attr_list;
- for (uint16_t i = 0; i < num_attrs; i++) {
- attr_list.push_back(fdp->ConsumeIntegral<uint16_t>());
- }
-
- return attr_list;
-}
-
-tSDP_DISC_ATVAL generateArbitrarySdpDiscAttrVal(FuzzedDataProvider* fdp) {
- tSDP_DISC_ATVAL new_attrval;
-
- new_attrval.v.u8 = fdp->ConsumeIntegral<uint8_t>();
- new_attrval.v.u16 = fdp->ConsumeIntegral<uint16_t>();
- new_attrval.v.u32 = fdp->ConsumeIntegral<uint32_t>();
- for (int i = 0; i < 4; i++) {
- new_attrval.v.array[i] = fdp->ConsumeIntegral<uint8_t>();
- }
- new_attrval.v.p_sub_attr = generateArbitrarySdpDiscAttr(fdp, true).get();
-
- return new_attrval;
-}
-
-std::shared_ptr<tSDP_DISC_ATTR> generateArbitrarySdpDiscAttr(
- FuzzedDataProvider* fdp, bool allow_null) {
- // Give it a chance to return a nullptr
- if (allow_null && !fdp->ConsumeBool()) {
- return nullptr;
- }
-
- std::shared_ptr<tSDP_DISC_ATTR> new_attr(new tSDP_DISC_ATTR);
- sdp_disc_attr_vect.push_back(new_attr);
-
- new_attr->p_next_attr = generateArbitrarySdpDiscAttr(fdp, true).get();
- new_attr->attr_id = fdp->ConsumeIntegral<uint16_t>();
- new_attr->attr_len_type =
- fdp->ConsumeBool() ? 16 : fdp->ConsumeIntegral<uint16_t>();
- new_attr->attr_value = generateArbitrarySdpDiscAttrVal(fdp);
-
- return new_attr;
-}
-
-std::shared_ptr<tSDP_DISC_REC> generateArbitrarySdpDiscRecord(
- FuzzedDataProvider* fdp, bool allow_null) {
- // Give it a chance to return a nullptr
- if (allow_null && !fdp->ConsumeBool()) {
- return nullptr;
- }
-
- std::shared_ptr<tSDP_DISC_REC> new_rec(new tSDP_DISC_REC);
- sdp_disc_rec_vect.push_back(new_rec);
-
- new_rec->p_first_attr = generateArbitrarySdpDiscAttr(fdp, true).get();
- new_rec->p_next_rec = generateArbitrarySdpDiscRecord(fdp, true).get();
- new_rec->time_read = fdp->ConsumeIntegral<uint32_t>();
- new_rec->remote_bd_addr = generateRawAddress(fdp);
-
- return new_rec;
-}
-
-tSDP_PROTOCOL_ELEM generateArbitrarySdpProtocolElements(
- FuzzedDataProvider* fdp) {
- tSDP_PROTOCOL_ELEM p_elem;
-
- // Set our protocol element values
- p_elem.protocol_uuid = fdp->ConsumeIntegral<uint16_t>();
- p_elem.num_params =
- fdp->ConsumeIntegralInRange<uint16_t>(0, SDP_MAX_PROTOCOL_PARAMS);
- uint16_t num_loops = std::min(
- p_elem.num_params, static_cast<unsigned short>(SDP_MAX_PROTOCOL_PARAMS));
- // Regardless of number set above, fill out the entire allocated array
- for (uint16_t i = 0; i < num_loops; i++) {
- p_elem.params[i] = fdp->ConsumeIntegral<uint16_t>();
- }
-
- return p_elem;
-}
-
-std::shared_ptr<tSDP_PROTO_LIST_ELEM> generateArbitrarySdpProtocolElementList(
- FuzzedDataProvider* fdp) {
- std::shared_ptr<tSDP_PROTO_LIST_ELEM> p_elem_list(new tSDP_PROTO_LIST_ELEM);
- sdp_protolist_elem_vect.push_back(p_elem_list);
-
- // Populate our element list
- p_elem_list->num_elems =
- fdp->ConsumeIntegralInRange<uint16_t>(0, SDP_MAX_LIST_ELEMS);
- uint16_t num_loops = std::min(
- p_elem_list->num_elems, static_cast<unsigned short>(SDP_MAX_LIST_ELEMS));
- for (uint16_t i = 0; i < num_loops; i++) {
- p_elem_list->list_elem[i] = generateArbitrarySdpProtocolElements(fdp);
- }
-
- return p_elem_list;
-}
-
-tSDP_PROTO_LIST_ELEM** generateArbitrarySdpProtocolElementListArray(
- FuzzedDataProvider* fdp, uint16_t* array_size) {
- *array_size = fdp->ConsumeIntegralInRange<uint16_t>(0, SDP_MAX_ATTR_LEN);
- if (*array_size == 0) {
- return nullptr;
- }
- tSDP_PROTO_LIST_ELEM** p_list_array = static_cast<tSDP_PROTO_LIST_ELEM**>(
- calloc(*array_size, sizeof(tSDP_PROTO_LIST_ELEM*)));
- if (p_list_array == nullptr) {
- return nullptr;
- }
-
- tSDP_PROTO_LIST_ELEM* p = p_list_array[0];
- for (uint16_t i = 0; i < *array_size; i++, p++) {
- p = generateArbitrarySdpProtocolElementList(fdp).get();
- }
-
- return p_list_array;
-}
-
-tSDP_DI_RECORD generateArbitrarySdpDiRecord(FuzzedDataProvider* fdp) {
- tSDP_DI_RECORD record;
-
- record.vendor = fdp->ConsumeIntegral<uint16_t>();
- record.vendor_id_source = fdp->ConsumeIntegral<uint16_t>();
- record.product = fdp->ConsumeIntegral<uint16_t>();
- record.version = fdp->ConsumeIntegral<uint16_t>();
- record.primary_record = fdp->ConsumeBool();
- size_t num_executable_urls =
- fdp->ConsumeIntegralInRange<size_t>(0, SDP_MAX_ATTR_LEN);
- for (size_t i = 0; i < num_executable_urls; i++) {
- record.client_executable_url[i] = fdp->ConsumeIntegral<char>();
- }
- size_t num_descriptions =
- fdp->ConsumeIntegralInRange<size_t>(0, SDP_MAX_ATTR_LEN);
- for (size_t i = 0; i < num_descriptions; i++) {
- record.service_description[i] = fdp->ConsumeIntegral<char>();
- }
- size_t num_documentation_urls =
- fdp->ConsumeIntegralInRange<size_t>(0, SDP_MAX_ATTR_LEN);
- for (size_t i = 0; i < num_documentation_urls; i++) {
- record.documentation_url[i] = fdp->ConsumeIntegral<char>();
- }
-
- return record;
-}
-
-tSDP_DI_GET_RECORD generateArbitrarySdpDiGetRecord(FuzzedDataProvider* fdp) {
- tSDP_DI_GET_RECORD get_record;
- get_record.spec_id = fdp->ConsumeIntegral<uint16_t>();
- get_record.rec = generateArbitrarySdpDiRecord(fdp);
-
- return get_record;
-}
-
-SDP_Sequence_Helper generateArbitrarySdpElemSequence(FuzzedDataProvider* fdp) {
- SDP_Sequence_Helper ret;
-
- // Get the number of our elements
- ret.num_elem = fdp->ConsumeIntegralInRange<uint16_t>(1, SDP_MAX_NUM_ELEMS);
- ret.type.reset(new uint8_t[ret.num_elem]);
- ret.len.reset(new uint8_t[ret.num_elem]);
- ret.p_val.reset(new uint8_t*[ret.num_elem]);
- for (uint16_t i = 0; i < ret.num_elem; i++) {
- (ret.type.get())[i] = fdp->ConsumeIntegral<uint8_t>();
- if ((ret.len.get())[i] == 0) {
- (ret.p_val.get())[i] = nullptr;
- (ret.len.get())[i] = 0;
- } else {
- uint8_t buf_size = fdp->ConsumeIntegral<uint8_t>();
- // Link the size to the size of the buffer we're creating
- (ret.len.get())[i] = buf_size;
- std::shared_ptr<uint8_t> p_val_sp(
- reinterpret_cast<uint8_t*>(calloc(buf_size, sizeof(uint8_t))), free);
- ret.p_val_buffers.push_back(p_val_sp);
- (ret.p_val.get())[i] = p_val_sp.get();
- std::vector<uint8_t> bytes = fdp->ConsumeBytes<uint8_t>(buf_size);
- memcpy((ret.p_val.get())[i], bytes.data(), bytes.size());
- }
- }
-
- // Push this struct to our array so we can delete later
- sdp_sequence_vect.push_back(ret);
-
- return ret;
-}
-
-// Define our callback functions we'll be using within our functions
-void sdp_disc_cmpl_cb(tSDP_STATUS result) {}
-void sdp_disc_cmpl_cb2(tSDP_STATUS result, void* user_data) {}
-
-#endif // FUZZER_SDP_HELPERS_H_
diff --git a/stack/test/gatt/gatt_sr_test.cc b/stack/test/gatt/gatt_sr_test.cc
index 95a091a01..a5fe4cd40 100644
--- a/stack/test/gatt/gatt_sr_test.cc
+++ b/stack/test/gatt/gatt_sr_test.cc
@@ -20,7 +20,6 @@
#include <cstdint>
#include "osi/test/AllocationTestHarness.h"
-#include "stack/test/common/mock_eatt.h"
#include "stack/gatt/gatt_int.h"
#undef LOG_TAG
#include "stack/gatt/gatt_sr.cc"
@@ -28,9 +27,6 @@
#define MAX_UINT16 ((uint16_t)0xffff)
-bool MOCK_bluetooth_shim_is_gd_acl_enabled_ = true;
-std::map<std::string, int> mock_function_count_map;
-
tGATT_CB gatt_cb;
namespace {
@@ -68,21 +64,11 @@ BT_HDR* attp_build_sr_msg(tGATT_TCB& tcb, uint8_t op_code,
test_state_.attp_build_sr_msg.op_code_ = op_code;
return nullptr;
}
-tGATT_STATUS attp_send_cl_confirmation_msg(tGATT_TCB& tcb, uint16_t cid) {
- return GATT_SUCCESS;
-}
tGATT_STATUS attp_send_cl_msg(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
uint8_t op_code, tGATT_CL_MSG* p_msg) {
- return GATT_SUCCESS;
-}
-tGATT_STATUS attp_send_sr_msg(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_msg) {
- return GATT_SUCCESS;
-}
-
-tBTM_STATUS BTM_SetBleDataLength(const RawAddress& bd_addr, uint16_t length) {
- return BTM_SUCCESS;
+ return 0;
}
-
+tGATT_STATUS attp_send_sr_msg(tGATT_TCB& tcb, BT_HDR* p_msg) { return 0; }
uint8_t btm_ble_read_sec_key_size(const RawAddress& bd_addr) { return 0; }
bool BTM_GetSecurityFlagsByTransport(const RawAddress& bd_addr,
uint8_t* p_sec_flags,
@@ -91,13 +77,13 @@ bool BTM_GetSecurityFlagsByTransport(const RawAddress& bd_addr,
}
void gatt_act_discovery(tGATT_CLCB* p_clcb) {}
bool gatt_disconnect(tGATT_TCB* p_tcb) { return false; }
-tGATT_CH_STATE gatt_get_ch_state(tGATT_TCB* p_tcb) { return GATT_CH_CLOSE; }
+tGATT_CH_STATE gatt_get_ch_state(tGATT_TCB* p_tcb) { return 0; }
tGATT_STATUS gatts_db_read_attr_value_by_type(
- tGATT_TCB& tcb, uint16_t cid, tGATT_SVC_DB* p_db, uint8_t op_code,
- BT_HDR* p_rsp, uint16_t s_handle, uint16_t e_handle, const Uuid& type,
- uint16_t* p_len, tGATT_SEC_FLAG sec_flag, uint8_t key_size,
- uint32_t trans_id, uint16_t* p_cur_handle) {
- return GATT_SUCCESS;
+ tGATT_TCB& tcb, tGATT_SVC_DB* p_db, uint8_t op_code, BT_HDR* p_rsp,
+ uint16_t s_handle, uint16_t e_handle, const Uuid& type, uint16_t* p_len,
+ tGATT_SEC_FLAG sec_flag, uint8_t key_size, uint32_t trans_id,
+ uint16_t* p_cur_handle) {
+ return 0;
}
void gatt_set_ch_state(tGATT_TCB* p_tcb, tGATT_CH_STATE ch_state) {}
Uuid* gatts_get_service_uuid(tGATT_SVC_DB* p_db) { return nullptr; }
@@ -112,10 +98,9 @@ tGATT_STATUS gatts_read_attr_perm_check(tGATT_SVC_DB* p_db, bool is_long,
return GATT_SUCCESS;
}
tGATT_STATUS gatts_read_attr_value_by_handle(
- tGATT_TCB& tcb, uint16_t cid, tGATT_SVC_DB* p_db, uint8_t op_code,
- uint16_t handle, uint16_t offset, uint8_t* p_value, uint16_t* p_len,
- uint16_t mtu, tGATT_SEC_FLAG sec_flag, uint8_t key_size,
- uint32_t trans_id) {
+ tGATT_TCB& tcb, tGATT_SVC_DB* p_db, uint8_t op_code, uint16_t handle,
+ uint16_t offset, uint8_t* p_value, uint16_t* p_len, uint16_t mtu,
+ tGATT_SEC_FLAG sec_flag, uint8_t key_size, uint32_t trans_id) {
return GATT_SUCCESS;
}
tGATT_STATUS gatts_write_attr_perm_check(tGATT_SVC_DB* p_db, uint8_t op_code,
@@ -128,13 +113,10 @@ tGATT_STATUS gatts_write_attr_perm_check(tGATT_SVC_DB* p_db, uint8_t op_code,
}
void gatt_update_app_use_link_flag(tGATT_IF gatt_if, tGATT_TCB* p_tcb,
bool is_add, bool check_acl_link) {}
-bluetooth::common::MessageLoopThread* get_main_thread() { return nullptr; }
+base::MessageLoop* get_main_message_loop() { return nullptr; }
void l2cble_set_fixed_channel_tx_data_length(const RawAddress& remote_bda,
uint16_t fix_cid,
uint16_t tx_mtu) {}
-void L2CA_SetLeFixedChannelTxDataLength(const RawAddress& remote_bda,
- uint16_t fix_cid,
- uint16_t tx_mtu) {}
bool SDP_AddAttribute(uint32_t handle, uint16_t attr_id, uint8_t attr_type,
uint32_t attr_len, uint8_t* p_val) {
return false;
@@ -161,12 +143,6 @@ void ApplicationRequestCallback(uint16_t conn_id, uint32_t trans_id,
test_state_.application_request_callback.data_ = *p_data;
}
-bool gatt_sr_is_cl_change_aware(tGATT_TCB& tcb) { return false; }
-void gatt_sr_init_cl_status(tGATT_TCB& p_tcb) {}
-void gatt_sr_update_cl_status(tGATT_TCB& p_tcb, bool chg_aware) {
- p_tcb.is_robust_cache_change_aware = chg_aware;
-}
-
/**
* Test class to test selected functionality in stack/gatt/gatt_sr.cc
*/
@@ -185,7 +161,6 @@ class GattSrTest : public AllocationTestHarness {
memset(&el_, 0, sizeof(el_));
tcb_.trans_id = 0x12345677;
- tcb_.att_lcid = L2CAP_ATT_CID;
el_.gatt_if = 1;
gatt_cb.cl_rcb[el_.gatt_if - 1].in_use = true;
gatt_cb.cl_rcb[el_.gatt_if - 1].app_cb.p_req_cb =
@@ -200,53 +175,29 @@ class GattSrTest : public AllocationTestHarness {
tGATT_SRV_LIST_ELEM el_;
};
-/* Server Robust Caching Test */
-class GattSrRobustCachingTest : public AllocationTestHarness {
- protected:
- void SetUp() override {
- AllocationTestHarness::SetUp();
- memset(&tcb_, 0, sizeof(tcb_));
-
- default_length_ = 2;
- memset(default_data_, 0, sizeof(default_data_));
-
- gatt_cb.handle_of_database_hash = 0x0010;
- }
-
- void TearDown() override { AllocationTestHarness::TearDown(); }
-
- tGATT_TCB tcb_;
- uint16_t default_length_;
- uint8_t default_data_[2];
-};
-
TEST_F(GattSrTest, gatts_process_write_req_request_prepare_write_no_data) {
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle,
- GATT_REQ_PREPARE_WRITE, 0, nullptr,
- kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_REQ_PREPARE_WRITE, 0,
+ nullptr, kGattCharacteristicType);
}
TEST_F(GattSrTest,
gatts_process_write_req_request_prepare_write_max_len_no_data) {
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle,
- GATT_REQ_PREPARE_WRITE, MAX_UINT16, nullptr,
- kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_REQ_PREPARE_WRITE,
+ MAX_UINT16, nullptr, kGattCharacteristicType);
}
TEST_F(GattSrTest,
gatts_process_write_req_request_prepare_write_zero_len_max_data) {
uint8_t max_mem[MAX_UINT16];
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle,
- GATT_REQ_PREPARE_WRITE, 0, max_mem,
- kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_REQ_PREPARE_WRITE, 0,
+ max_mem, kGattCharacteristicType);
}
TEST_F(GattSrTest, gatts_process_write_req_request_prepare_write_typical) {
uint8_t p_data[2] = {0x34, 0x12};
uint16_t length = static_cast<uint16_t>(sizeof(p_data) / sizeof(p_data[0]));
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle,
- GATT_REQ_PREPARE_WRITE, length, p_data,
- kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_REQ_PREPARE_WRITE, length,
+ p_data, kGattCharacteristicType);
CHECK(test_state_.gatts_write_attr_perm_check.access_count_ == 1);
CHECK(test_state_.application_request_callback.conn_id_ == el_.gatt_if);
@@ -261,23 +212,20 @@ TEST_F(GattSrTest, gatts_process_write_req_request_prepare_write_typical) {
}
TEST_F(GattSrTest, gatts_process_write_req_signed_command_write_no_data) {
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle,
- GATT_SIGN_CMD_WRITE, 0, nullptr,
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_SIGN_CMD_WRITE, 0, nullptr,
kGattCharacteristicType);
}
TEST_F(GattSrTest,
gatts_process_write_req_signed_command_write_max_len_no_data) {
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle,
- GATT_SIGN_CMD_WRITE, MAX_UINT16, nullptr,
- kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_SIGN_CMD_WRITE, MAX_UINT16,
+ nullptr, kGattCharacteristicType);
}
TEST_F(GattSrTest,
gatts_process_write_req_signed_command_write_zero_len_max_data) {
uint8_t max_mem[MAX_UINT16];
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle,
- GATT_SIGN_CMD_WRITE, 0, max_mem,
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_SIGN_CMD_WRITE, 0, max_mem,
kGattCharacteristicType);
}
@@ -287,9 +235,8 @@ TEST_F(GattSrTest, gatts_process_write_req_signed_command_write_typical) {
0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88,
0x99, 0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff, 0x01};
uint16_t length = static_cast<uint16_t>(sizeof(p_data) / sizeof(p_data[0]));
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle,
- GATT_SIGN_CMD_WRITE, length, p_data,
- kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_SIGN_CMD_WRITE, length,
+ p_data, kGattCharacteristicType);
CHECK(test_state_.gatts_write_attr_perm_check.access_count_ == 1);
CHECK(test_state_.application_request_callback.conn_id_ == el_.gatt_if);
@@ -304,27 +251,27 @@ TEST_F(GattSrTest, gatts_process_write_req_signed_command_write_typical) {
}
TEST_F(GattSrTest, gatts_process_write_req_command_write_no_data) {
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle, GATT_CMD_WRITE, 0,
- nullptr, kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_CMD_WRITE, 0, nullptr,
+ kGattCharacteristicType);
}
TEST_F(GattSrTest, gatts_process_write_req_command_write_max_len_no_data) {
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle, GATT_CMD_WRITE,
- MAX_UINT16, nullptr, kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_CMD_WRITE, MAX_UINT16,
+ nullptr, kGattCharacteristicType);
}
TEST_F(GattSrTest, gatts_process_write_req_command_write_zero_len_max_data) {
uint8_t max_mem[MAX_UINT16];
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle, GATT_CMD_WRITE, 0,
- max_mem, kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_CMD_WRITE, 0, max_mem,
+ kGattCharacteristicType);
}
TEST_F(GattSrTest, gatts_process_write_req_command_write_typical) {
uint8_t p_data[16] = {0x11, 0x22, 0x33, 0x44, 0x55, 0x66, 0x77, 0x88,
0x99, 0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff, 0x01};
uint16_t length = static_cast<uint16_t>(sizeof(p_data) / sizeof(p_data[0]));
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle, GATT_CMD_WRITE,
- length, p_data, kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_CMD_WRITE, length, p_data,
+ kGattCharacteristicType);
CHECK(test_state_.gatts_write_attr_perm_check.access_count_ == 1);
CHECK(test_state_.application_request_callback.conn_id_ == el_.gatt_if);
@@ -338,19 +285,19 @@ TEST_F(GattSrTest, gatts_process_write_req_command_write_typical) {
}
TEST_F(GattSrTest, gatts_process_write_req_request_write_no_data) {
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle, GATT_REQ_WRITE, 0,
- nullptr, kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_REQ_WRITE, 0, nullptr,
+ kGattCharacteristicType);
}
TEST_F(GattSrTest, gatts_process_write_req_request_write_max_len_no_data) {
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle, GATT_REQ_WRITE,
- MAX_UINT16, nullptr, kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_REQ_WRITE, MAX_UINT16,
+ nullptr, kGattCharacteristicType);
}
TEST_F(GattSrTest, gatts_process_write_req_request_write_zero_len_max_data) {
uint8_t max_mem[MAX_UINT16];
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle, GATT_REQ_WRITE, 0,
- max_mem, kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_REQ_WRITE, 0, max_mem,
+ kGattCharacteristicType);
}
TEST_F(GattSrTest, gatts_process_write_req_request_write_typical) {
@@ -358,8 +305,8 @@ TEST_F(GattSrTest, gatts_process_write_req_request_write_typical) {
0x99, 0xaa, 0xbb, 0xcc, 0xdd, 0xee, 0xff, 0x01};
uint16_t length = static_cast<uint16_t>(sizeof(p_data) / sizeof(p_data[0]));
- gatts_process_write_req(tcb_, L2CAP_ATT_CID, el_, kHandle, GATT_REQ_WRITE,
- length, p_data, kGattCharacteristicType);
+ gatts_process_write_req(tcb_, el_, kHandle, GATT_REQ_WRITE, length, p_data,
+ kGattCharacteristicType);
CHECK(test_state_.gatts_write_attr_perm_check.access_count_ == 1);
CHECK(test_state_.application_request_callback.conn_id_ == el_.gatt_if);
@@ -371,231 +318,3 @@ TEST_F(GattSrTest, gatts_process_write_req_request_write_typical) {
false);
CHECK(test_state_.application_request_callback.data_.write_req.len == length);
}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_read_by_grp_type) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_READ_BY_GRP_TYPE, default_length_,
- default_data_);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_find_type_value) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_FIND_TYPE_VALUE, default_length_,
- default_data_);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_find_info) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_FIND_INFO, default_length_, default_data_);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_read_by_type_parse_failed) {
- // INVALID_PDU
- uint16_t len = 4;
- uint8_t p_data[4] = {0x00, 0x02, 0x14, 0x02};
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_READ_BY_TYPE, len, p_data);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_read_by_type_db_hash_uuid) {
- // ATT_READ_BY_TYPE_REQ(0x0001, 0x0010, 0x2B2A)
- uint16_t len = 6;
- uint8_t p_data[6] = {0x01, 0x00, 0x10, 0x00, 0x2A, 0x2B};
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_READ_BY_TYPE, len, p_data);
-
- ASSERT_FALSE(should_ignore);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_read_by_type_wrong_range) {
- // ATT_READ_BY_TYPE_REQ(0x0200, 0x0214, 0x2803)
- uint16_t len = 6;
- uint8_t p_data[6] = {0x00, 0x02, 0x14, 0x02, 0x2A, 0x28};
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_READ_BY_TYPE, len, p_data);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_read_by_type_other_uuid) {
- // ATT_READ_BY_TYPE_REQ(0x0200, 0x0214, 0x2803)
- uint16_t len = 6;
- uint8_t p_data[6] = {0x00, 0x02, 0x14, 0x02, 0x03, 0x28};
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_READ_BY_TYPE, len, p_data);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_read_parse_failed) {
- // INVALID_PDU
- uint8_t p_data[1] = {0x02};
- uint16_t len = 1;
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(tcb_, L2CAP_ATT_CID,
- GATT_REQ_READ, len, p_data);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_read_db_hash_handle) {
- // ATT_READ_REQ(0x0010)
- uint8_t p_data[2] = {0x10, 0x00};
- uint16_t len = 2;
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(tcb_, L2CAP_ATT_CID,
- GATT_REQ_READ, len, p_data);
-
- ASSERT_FALSE(should_ignore);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_read_other_handle) {
- // ATT_READ_REQ(0x0002)
- uint8_t p_data[2] = {0x02, 0x00};
- uint16_t len = 2;
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(tcb_, L2CAP_ATT_CID,
- GATT_REQ_READ, len, p_data);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_read_blob) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_READ_BLOB, default_length_, default_data_);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_read_multi) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_READ_MULTI, default_length_, default_data_);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_write) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_WRITE, default_length_, default_data_);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_cmd_write) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_CMD_WRITE, default_length_, default_data_);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_FALSE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_sign_cmd_write) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_SIGN_CMD_WRITE, default_length_, default_data_);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_FALSE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_prepare_write) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore =
- gatts_process_db_out_of_sync(tcb_, L2CAP_ATT_CID, GATT_REQ_PREPARE_WRITE,
- default_length_, default_data_);
-
- ASSERT_TRUE(should_ignore);
- ASSERT_TRUE(tcb_.is_robust_cache_change_aware);
-}
-
-TEST_F(GattSrRobustCachingTest, gatts_process_db_out_of_sync_for_gatt_req_mtu) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_MTU, default_length_, default_data_);
-
- ASSERT_FALSE(should_ignore);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_req_exec_write) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore = gatts_process_db_out_of_sync(
- tcb_, L2CAP_ATT_CID, GATT_REQ_EXEC_WRITE, default_length_, default_data_);
-
- ASSERT_FALSE(should_ignore);
-}
-
-TEST_F(GattSrRobustCachingTest,
- gatts_process_db_out_of_sync_for_gatt_handle_value_conf) {
- tcb_.is_robust_cache_change_aware = false;
-
- bool should_ignore =
- gatts_process_db_out_of_sync(tcb_, L2CAP_ATT_CID, GATT_HANDLE_VALUE_CONF,
- default_length_, default_data_);
-
- ASSERT_FALSE(should_ignore);
-}
diff --git a/stack/test/gatt/mock_gatt_utils_ref.cc b/stack/test/gatt/mock_gatt_utils_ref.cc
deleted file mode 100644
index 6829aaf2a..000000000
--- a/stack/test/gatt/mock_gatt_utils_ref.cc
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "stack/gatt/gatt_int.h"
-#include "utils/include/bt_utils.h"
-
-/** stack/btm/btm_ble.cc*/
-uint8_t btm_ble_read_sec_key_size(const RawAddress& bd_addr) { return 0; }
-bool BTM_GetSecurityFlagsByTransport(const RawAddress& bd_addr,
- uint8_t* p_sec_flags,
- tBT_TRANSPORT transport) {
- return false;
-}
-
-/** stack/btu/btu_task.cc, indirect reference, gatt_utils.cc -> libosi */
-bluetooth::common::MessageLoopThread* get_main_thread() { return nullptr; }
-
-/** stack/gatt/connection_manager.cc */
-namespace connection_manager {
-bool background_connect_remove(uint8_t app_id, const RawAddress& address) {
- return false;
-}
-bool direct_connect_remove(uint8_t app_id, const RawAddress& address) {
- return false;
-}
-} // namespace connection_manager
-
-/** stack/gatt/att_protocol.cc */
-BT_HDR* attp_build_sr_msg(tGATT_TCB& tcb, uint8_t op_code,
- tGATT_SR_MSG* p_msg) {
- return nullptr;
-}
-tGATT_STATUS attp_send_cl_confirmation_msg(tGATT_TCB& tcb, uint16_t cid) {
- return GATT_SUCCESS;
-}
-tGATT_STATUS attp_send_cl_msg(tGATT_TCB& tcb, tGATT_CLCB* p_clcb,
- uint8_t op_code, tGATT_CL_MSG* p_msg) {
- return GATT_SUCCESS;
-}
-tGATT_STATUS attp_send_sr_msg(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_msg) {
- return GATT_SUCCESS;
-}
-
-/** stack/gatt/gatt_attr.cc */
-void gatt_sr_init_cl_status(tGATT_TCB& tcb) {}
-
-/** stack/gatt/gatt_cl.cc */
-void gatt_act_discovery(tGATT_CLCB* p_clcb) {}
-
-/** stack/gatt/gatt_main.cc */
-void gatt_update_app_use_link_flag(tGATT_IF gatt_if, tGATT_TCB* p_tcb,
- bool is_add, bool check_acl_link) {}
-void gatts_proc_srv_chg_ind_ack(tGATT_TCB) {}
-bool gatt_disconnect(tGATT_TCB* p_tcb) { return false; }
-tGATT_CH_STATE gatt_get_ch_state(tGATT_TCB* p_tcb) { return GATT_CH_CLOSE; }
-void gatt_set_ch_state(tGATT_TCB* p_tcb, tGATT_CH_STATE ch_state) {}
-
-/** stack/gatt/gatt_sr.cc */
-uint32_t gatt_sr_enqueue_cmd(tGATT_TCB& tcb, uint16_t cid, uint8_t op_code,
- uint16_t handle) { return 0x0000; }
-void gatt_dequeue_sr_cmd(tGATT_TCB& tcb, uint16_t cid) {}
-
-
-/** stack/l2cap/l2c_ble.cc */
-void l2cble_set_fixed_channel_tx_data_length(const RawAddress& remote_bda,
- uint16_t fix_cid,
- uint16_t tx_mtu) {}
-void L2CA_SetLeFixedChannelTxDataLength(const RawAddress& remote_bda,
- uint16_t fix_cid,
- uint16_t tx_mtu) {}
-/** stack/sdp/sdp_db.cc */
-bool SDP_AddAttribute(uint32_t handle, uint16_t attr_id, uint8_t attr_type,
- uint32_t attr_len, uint8_t* p_val) {
- return false;
-}
-bool SDP_AddProtocolList(uint32_t handle, uint16_t num_elem,
- tSDP_PROTOCOL_ELEM* p_elem_list) {
- return false;
-}
-bool SDP_AddServiceClassIdList(uint32_t handle, uint16_t num_services,
- uint16_t* p_service_uuids) {
- return false;
-}
-bool SDP_AddUuidSequence(uint32_t handle, uint16_t attr_id, uint16_t num_uuids,
- uint16_t* p_uuids) {
- return false;
-}
-uint32_t SDP_CreateRecord(void) { return 0; }
-
diff --git a/stack/test/gatt/stack_gatt_test.cc b/stack/test/gatt/stack_gatt_test.cc
deleted file mode 100644
index 4c58ea86f..000000000
--- a/stack/test/gatt/stack_gatt_test.cc
+++ /dev/null
@@ -1,141 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gtest/gtest.h>
-#include <string.h>
-
-#include <cstdint>
-#include <map>
-#include <memory>
-#include <string>
-
-#include "common/message_loop_thread.h"
-#include "common/strings.h"
-#include "stack/gatt/gatt_int.h"
-#include "stack/include/gatt_api.h"
-
-std::map<std::string, int> mock_function_count_map;
-
-void LogMsg(uint32_t trace_set_mask, const char* fmt_str, ...) {}
-
-bluetooth::common::MessageLoopThread* get_main_thread() { return nullptr; }
-
-class StackGattTest : public ::testing::Test {};
-
-namespace {
-
-// Actual size of structure without compiler padding
-size_t actual_sizeof_tGATT_REG() {
- return sizeof(bluetooth::Uuid) + sizeof(tGATT_CBACK) + sizeof(tGATT_IF) +
- sizeof(bool) + sizeof(uint8_t) + sizeof(bool);
-}
-
-void tGATT_DISC_RES_CB(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
- tGATT_DISC_RES* p_data) {}
-void tGATT_DISC_CMPL_CB(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
- tGATT_STATUS status) {}
-void tGATT_CMPL_CBACK(uint16_t conn_id, tGATTC_OPTYPE op, tGATT_STATUS status,
- tGATT_CL_COMPLETE* p_data) {}
-void tGATT_CONN_CBACK(tGATT_IF gatt_if, const RawAddress& bda, uint16_t conn_id,
- bool connected, tGATT_DISCONN_REASON reason,
- tBT_TRANSPORT transport) {}
-void tGATT_REQ_CBACK(uint16_t conn_id, uint32_t trans_id, tGATTS_REQ_TYPE type,
- tGATTS_DATA* p_data) {}
-void tGATT_CONGESTION_CBACK(uint16_t conn_id, bool congested) {}
-void tGATT_ENC_CMPL_CB(tGATT_IF gatt_if, const RawAddress& bda) {}
-void tGATT_PHY_UPDATE_CB(tGATT_IF gatt_if, uint16_t conn_id, uint8_t tx_phy,
- uint8_t rx_phy, tGATT_STATUS status) {}
-void tGATT_CONN_UPDATE_CB(tGATT_IF gatt_if, uint16_t conn_id, uint16_t interval,
- uint16_t latency, uint16_t timeout,
- tGATT_STATUS status) {}
-
-tGATT_CBACK gatt_callbacks = {
- .p_conn_cb = tGATT_CONN_CBACK,
- .p_cmpl_cb = tGATT_CMPL_CBACK,
- .p_disc_res_cb = tGATT_DISC_RES_CB,
- .p_disc_cmpl_cb = tGATT_DISC_CMPL_CB,
- .p_req_cb = tGATT_REQ_CBACK,
- .p_enc_cmpl_cb = tGATT_ENC_CMPL_CB,
- .p_congestion_cb = tGATT_CONGESTION_CBACK,
- .p_phy_update_cb = tGATT_PHY_UPDATE_CB,
- .p_conn_update_cb = tGATT_CONN_UPDATE_CB,
-};
-
-} // namespace
-
-TEST_F(StackGattTest, lifecycle_tGATT_REG) {
- {
- std::unique_ptr<tGATT_REG> reg0 = std::make_unique<tGATT_REG>();
- std::unique_ptr<tGATT_REG> reg1 = std::make_unique<tGATT_REG>();
- memset(reg0.get(), 0xff, sizeof(tGATT_REG));
- memset(reg1.get(), 0xff, sizeof(tGATT_REG));
- ASSERT_EQ(0, memcmp(reg0.get(), reg1.get(), sizeof(tGATT_REG)));
-
- memset(reg0.get(), 0x0, sizeof(tGATT_REG));
- memset(reg1.get(), 0x0, sizeof(tGATT_REG));
- ASSERT_EQ(0, memcmp(reg0.get(), reg1.get(), sizeof(tGATT_REG)));
- }
-
- {
- std::unique_ptr<tGATT_REG> reg0 = std::make_unique<tGATT_REG>();
- memset(reg0.get(), 0xff, sizeof(tGATT_REG));
-
- tGATT_REG reg1;
- memset(&reg1, 0xff, sizeof(tGATT_REG));
-
- // Clear the structures
- memset(reg0.get(), 0, sizeof(tGATT_REG));
- // Restore the complex structure after memset
- memset(&reg1.name, 0, sizeof(std::string));
- reg1 = {};
- ASSERT_EQ(0, memcmp(reg0.get(), &reg1, actual_sizeof_tGATT_REG()));
- }
-
- {
- tGATT_REG* reg0 = new tGATT_REG();
- tGATT_REG* reg1 = new tGATT_REG();
- memset(reg0, 0, sizeof(tGATT_REG));
- *reg1 = {};
- reg0->in_use = true;
- ASSERT_NE(0, memcmp(reg0, reg1, sizeof(tGATT_REG)));
- delete reg1;
- delete reg0;
- }
-}
-
-TEST_F(StackGattTest, gatt_init_free) {
- gatt_init();
- gatt_free();
-}
-
-TEST_F(StackGattTest, GATT_Register_Deregister) {
- gatt_init();
-
- // Gatt db profile always takes the first slot
- tGATT_IF apps[GATT_MAX_APPS - 1];
-
- for (int i = 0; i < GATT_MAX_APPS - 1; i++) {
- std::string name = bluetooth::common::StringFormat("name%02d", i);
- apps[i] = GATT_Register(bluetooth::Uuid::GetRandom(), name, &gatt_callbacks,
- false);
- }
-
- for (int i = 0; i < GATT_MAX_APPS - 1; i++) {
- GATT_Deregister(apps[i]);
- }
-
- gatt_free();
-}
diff --git a/stack/test/gatt_connection_manager_test.cc b/stack/test/gatt_connection_manager_test.cc
index b5d28647e..0997aa89a 100644
--- a/stack/test/gatt_connection_manager_test.cc
+++ b/stack/test/gatt_connection_manager_test.cc
@@ -10,7 +10,6 @@
#include "osi/test/alarm_mock.h"
using testing::_;
-using testing::DoAll;
using testing::Mock;
using testing::Return;
using testing::SaveArg;
@@ -18,19 +17,19 @@ using testing::SaveArg;
using connection_manager::tAPP_ID;
namespace {
-// convenience mock, for verifying acceptlist operations on lower layer are
+// convinience mock, for verifying whitelist operaitons on lower layer are
// actually scheduled
-class AcceptlistMock {
+class WhiteListMock {
public:
- MOCK_METHOD1(AcceptlistAdd, bool(const RawAddress&));
- MOCK_METHOD1(AcceptlistRemove, void(const RawAddress&));
- MOCK_METHOD0(AcceptlistClear, void());
+ MOCK_METHOD1(WhiteListAdd, bool(const RawAddress&));
+ MOCK_METHOD1(WhiteListRemove, void(const RawAddress&));
+ MOCK_METHOD0(WhiteListClear, void());
MOCK_METHOD0(SetLeConnectionModeToFast, bool());
MOCK_METHOD0(SetLeConnectionModeToSlow, void());
MOCK_METHOD2(OnConnectionTimedOut, void(uint8_t, const RawAddress&));
};
-std::unique_ptr<AcceptlistMock> localAcceptlistMock;
+std::unique_ptr<WhiteListMock> localWhiteListMock;
} // namespace
RawAddress address1{{0x01, 0x01, 0x01, 0x01, 0x01, 0x01}};
@@ -42,83 +41,73 @@ constexpr tAPP_ID CLIENT3 = 3;
constexpr tAPP_ID CLIENT10 = 10;
// Implementation of btm_ble_bgconn.h API for test.
-bool BTM_AcceptlistAdd(const RawAddress& address) {
- return localAcceptlistMock->AcceptlistAdd(address);
+bool BTM_WhiteListAdd(const RawAddress& address) {
+ return localWhiteListMock->WhiteListAdd(address);
}
-void BTM_AcceptlistRemove(const RawAddress& address) {
- return localAcceptlistMock->AcceptlistRemove(address);
+void BTM_WhiteListRemove(const RawAddress& address) {
+ return localWhiteListMock->WhiteListRemove(address);
}
-void BTM_AcceptlistClear() { return localAcceptlistMock->AcceptlistClear(); }
+void BTM_WhiteListClear() { return localWhiteListMock->WhiteListClear(); }
bool BTM_SetLeConnectionModeToFast() {
- return localAcceptlistMock->SetLeConnectionModeToFast();
+ return localWhiteListMock->SetLeConnectionModeToFast();
}
void BTM_SetLeConnectionModeToSlow() {
- localAcceptlistMock->SetLeConnectionModeToSlow();
-}
-
-namespace bluetooth {
-namespace shim {
-bool is_gd_l2cap_enabled() { return false; }
-} // namespace shim
-} // namespace bluetooth
-
-bool L2CA_ConnectFixedChnl(uint16_t fixed_cid, const RawAddress& bd_addr) {
- return false;
+ localWhiteListMock->SetLeConnectionModeToSlow();
}
namespace connection_manager {
class BleConnectionManager : public testing::Test {
void SetUp() override {
- localAcceptlistMock = std::make_unique<AcceptlistMock>();
+ localWhiteListMock = std::make_unique<WhiteListMock>();
}
void TearDown() override {
connection_manager::reset(true);
AlarmMock::Reset();
- localAcceptlistMock.reset();
+ localWhiteListMock.reset();
}
};
void on_connection_timed_out(uint8_t app_id, const RawAddress& address) {
- localAcceptlistMock->OnConnectionTimedOut(app_id, address);
+ localWhiteListMock->OnConnectionTimedOut(app_id, address);
}
-/** Verify that app can add a device to acceptlist, it is returned as interested
+/** Verify that app can add a device to white list, it is returned as interested
* app, and then can remove the device later. */
TEST_F(BleConnectionManager, test_background_connection_add_remove) {
- EXPECT_CALL(*localAcceptlistMock, AcceptlistAdd(address1))
+ EXPECT_CALL(*localWhiteListMock, WhiteListAdd(address1))
.WillOnce(Return(true));
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(_)).Times(0);
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(_)).Times(0);
EXPECT_TRUE(background_connect_add(CLIENT1, address1));
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
std::set<tAPP_ID> apps = get_apps_connecting_to(address1);
EXPECT_EQ(apps.size(), 1UL);
EXPECT_EQ(apps.count(CLIENT1), 1UL);
- EXPECT_CALL(*localAcceptlistMock, AcceptlistAdd(_)).Times(0);
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(address1)).Times(1);
+ EXPECT_CALL(*localWhiteListMock, WhiteListAdd(_)).Times(0);
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(address1)).Times(1);
EXPECT_TRUE(background_connect_remove(CLIENT1, address1));
EXPECT_EQ(get_apps_connecting_to(address1).size(), 0UL);
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
}
/** Verify that multiple clients adding same device multiple times, result in
* device being added to whtie list only once, also, that device is removed only
* after last client removes it. */
TEST_F(BleConnectionManager, test_background_connection_multiple_clients) {
- EXPECT_CALL(*localAcceptlistMock, AcceptlistAdd(address1))
+ EXPECT_CALL(*localWhiteListMock, WhiteListAdd(address1))
.WillOnce(Return(true));
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(_)).Times(0);
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(_)).Times(0);
EXPECT_TRUE(background_connect_add(CLIENT1, address1));
EXPECT_TRUE(background_connect_add(CLIENT1, address1));
EXPECT_TRUE(background_connect_add(CLIENT2, address1));
@@ -126,9 +115,9 @@ TEST_F(BleConnectionManager, test_background_connection_multiple_clients) {
EXPECT_EQ(get_apps_connecting_to(address1).size(), 3UL);
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
- EXPECT_CALL(*localAcceptlistMock, AcceptlistAdd(_)).Times(0);
+ EXPECT_CALL(*localWhiteListMock, WhiteListAdd(_)).Times(0);
// removing from nonexisting client, should fail
EXPECT_FALSE(background_connect_remove(CLIENT10, address1));
@@ -138,22 +127,22 @@ TEST_F(BleConnectionManager, test_background_connection_multiple_clients) {
EXPECT_FALSE(background_connect_remove(CLIENT1, address1));
EXPECT_TRUE(background_connect_remove(CLIENT2, address1));
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(address1)).Times(1);
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(address1)).Times(1);
EXPECT_TRUE(background_connect_remove(CLIENT3, address1));
EXPECT_EQ(get_apps_connecting_to(address1).size(), 0UL);
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
}
/** Verify adding/removing device to direct connection. */
TEST_F(BleConnectionManager, test_direct_connection_client) {
- // Direct connect attempt: use faster scan parameters, add to acceptlist,
+ // Direct connect attempt: use faster scan parameters, add to white list,
// start 30 timeout
- EXPECT_CALL(*localAcceptlistMock, SetLeConnectionModeToFast()).Times(1);
- EXPECT_CALL(*localAcceptlistMock, AcceptlistAdd(address1))
+ EXPECT_CALL(*localWhiteListMock, SetLeConnectionModeToFast()).Times(1);
+ EXPECT_CALL(*localWhiteListMock, WhiteListAdd(address1))
.WillOnce(Return(true));
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(_)).Times(0);
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(_)).Times(0);
EXPECT_CALL(*AlarmMock::Get(), AlarmNew(_)).Times(1);
EXPECT_CALL(*AlarmMock::Get(), AlarmSetOnMloop(_, _, _, _)).Times(1);
EXPECT_TRUE(direct_connect_add(CLIENT1, address1));
@@ -164,25 +153,25 @@ TEST_F(BleConnectionManager, test_direct_connection_client) {
// Client that don't do direct connection should fail attempt to stop it
EXPECT_FALSE(direct_connect_remove(CLIENT2, address1));
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
- EXPECT_CALL(*localAcceptlistMock, SetLeConnectionModeToSlow()).Times(1);
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(_)).Times(1);
+ EXPECT_CALL(*localWhiteListMock, SetLeConnectionModeToSlow()).Times(1);
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(_)).Times(1);
EXPECT_CALL(*AlarmMock::Get(), AlarmFree(_)).Times(1);
// Removal should lower the connection parameters, and free the alarm.
- // Even though we call AcceptlistRemove, it won't be executed over HCI until
- // acceptlist is in use, i.e. next connection attempt
+ // Even though we call WhiteListRemove, it won't be executed over HCI until
+ // whitelist is in use, i.e. next connection attempt
EXPECT_TRUE(direct_connect_remove(CLIENT1, address1));
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
}
-/** Verify direct connection timeout does remove device from acceptlist, and
+/** Verify direct connection timeout does remove device from white list, and
* lower the connection scan parameters */
TEST_F(BleConnectionManager, test_direct_connect_timeout) {
- EXPECT_CALL(*localAcceptlistMock, SetLeConnectionModeToFast()).Times(1);
- EXPECT_CALL(*localAcceptlistMock, AcceptlistAdd(address1))
+ EXPECT_CALL(*localWhiteListMock, SetLeConnectionModeToFast()).Times(1);
+ EXPECT_CALL(*localWhiteListMock, WhiteListAdd(address1))
.WillOnce(Return(true));
EXPECT_CALL(*AlarmMock::Get(), AlarmNew(_)).Times(1);
alarm_callback_t alarm_callback = nullptr;
@@ -195,24 +184,23 @@ TEST_F(BleConnectionManager, test_direct_connect_timeout) {
// Start direct connect attempt...
EXPECT_TRUE(direct_connect_add(CLIENT1, address1));
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
- EXPECT_CALL(*localAcceptlistMock, SetLeConnectionModeToSlow()).Times(1);
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(_)).Times(1);
- EXPECT_CALL(*localAcceptlistMock, OnConnectionTimedOut(CLIENT1, address1))
- .Times(1);
+ EXPECT_CALL(*localWhiteListMock, SetLeConnectionModeToSlow()).Times(1);
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(_)).Times(1);
+ EXPECT_CALL(*localWhiteListMock, OnConnectionTimedOut(CLIENT1, address1)).Times(1);
EXPECT_CALL(*AlarmMock::Get(), AlarmFree(_)).Times(1);
// simulate timeout seconds passed, alarm executing
alarm_callback(alarm_data);
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
}
/** Verify that we properly handle successfull direct connection */
TEST_F(BleConnectionManager, test_direct_connection_success) {
- EXPECT_CALL(*localAcceptlistMock, SetLeConnectionModeToFast()).Times(1);
- EXPECT_CALL(*localAcceptlistMock, AcceptlistAdd(address1))
+ EXPECT_CALL(*localWhiteListMock, SetLeConnectionModeToFast()).Times(1);
+ EXPECT_CALL(*localWhiteListMock, WhiteListAdd(address1))
.WillOnce(Return(true));
EXPECT_CALL(*AlarmMock::Get(), AlarmNew(_)).Times(1);
EXPECT_CALL(*AlarmMock::Get(), AlarmSetOnMloop(_, _, _, _)).Times(1);
@@ -220,10 +208,10 @@ TEST_F(BleConnectionManager, test_direct_connection_success) {
// Start direct connect attempt...
EXPECT_TRUE(direct_connect_add(CLIENT1, address1));
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
- EXPECT_CALL(*localAcceptlistMock, SetLeConnectionModeToSlow()).Times(1);
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(address1)).Times(1);
+ EXPECT_CALL(*localWhiteListMock, SetLeConnectionModeToSlow()).Times(1);
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(address1)).Times(1);
EXPECT_CALL(*AlarmMock::Get(), AlarmFree(_)).Times(1);
// simulate event from lower layers - connections was established
// successfully.
@@ -235,52 +223,52 @@ TEST_F(BleConnectionManager, test_app_unregister) {
/* Test scenario:
* - Client 1 connecting to address1 and address2.
* - Client 2 connecting to address2
- * - unregistration of Client1 should trigger address1 removal from acceptlist
+ * - unregistration of Client1 should trigger address1 removal from white list
* - unregistration of Client2 should trigger address2 removal
*/
- EXPECT_CALL(*localAcceptlistMock, AcceptlistAdd(address1))
+ EXPECT_CALL(*localWhiteListMock, WhiteListAdd(address1))
.WillOnce(Return(true));
- EXPECT_CALL(*localAcceptlistMock, AcceptlistAdd(address2))
+ EXPECT_CALL(*localWhiteListMock, WhiteListAdd(address2))
.WillOnce(Return(true));
EXPECT_TRUE(direct_connect_add(CLIENT1, address1));
EXPECT_TRUE(background_connect_add(CLIENT1, address2));
EXPECT_TRUE(direct_connect_add(CLIENT2, address2));
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(address1)).Times(1);
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(address1)).Times(1);
on_app_deregistered(CLIENT1);
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(address2)).Times(1);
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(address2)).Times(1);
on_app_deregistered(CLIENT2);
}
/** Verify adding device to both direct connection and background connection. */
TEST_F(BleConnectionManager, test_direct_and_background_connect) {
- EXPECT_CALL(*localAcceptlistMock, SetLeConnectionModeToFast()).Times(1);
- EXPECT_CALL(*localAcceptlistMock, AcceptlistAdd(address1))
+ EXPECT_CALL(*localWhiteListMock, SetLeConnectionModeToFast()).Times(1);
+ EXPECT_CALL(*localWhiteListMock, WhiteListAdd(address1))
.WillOnce(Return(true));
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(_)).Times(0);
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(_)).Times(0);
EXPECT_CALL(*AlarmMock::Get(), AlarmNew(_)).Times(1);
EXPECT_CALL(*AlarmMock::Get(), AlarmSetOnMloop(_, _, _, _)).Times(1);
// add device as both direct and background connection
EXPECT_TRUE(direct_connect_add(CLIENT1, address1));
EXPECT_TRUE(background_connect_add(CLIENT1, address1));
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
- EXPECT_CALL(*localAcceptlistMock, SetLeConnectionModeToSlow()).Times(1);
+ EXPECT_CALL(*localWhiteListMock, SetLeConnectionModeToSlow()).Times(1);
EXPECT_CALL(*AlarmMock::Get(), AlarmFree(_)).Times(1);
- // not removing from acceptlist yet, as the background connection is still
+ // not removing from white list yet, as the background connection is still
// pending.
EXPECT_TRUE(direct_connect_remove(CLIENT1, address1));
- // remove from acceptlist, because no more interest in device.
- EXPECT_CALL(*localAcceptlistMock, AcceptlistRemove(_)).Times(1);
+ // remove from white list, because no more interest in device.
+ EXPECT_CALL(*localWhiteListMock, WhiteListRemove(_)).Times(1);
EXPECT_TRUE(background_connect_remove(CLIENT1, address1));
- Mock::VerifyAndClearExpectations(localAcceptlistMock.get());
+ Mock::VerifyAndClearExpectations(localWhiteListMock.get());
}
} // namespace connection_manager
diff --git a/stack/test/hci/stack_hci_test.cc b/stack/test/hci/stack_hci_test.cc
deleted file mode 100644
index 8ef98a3df..000000000
--- a/stack/test/hci/stack_hci_test.cc
+++ /dev/null
@@ -1,133 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-#include <cstring>
-#include <map>
-
-#include "osi/include/log.h"
-#include "stack/include/hcidefs.h"
-#include "stack/include/l2cdefs.h"
-#include "test/mock/mock_hcic_hcicmds.h"
-
-std::map<std::string, int> mock_function_count_map;
-
-namespace mock = test::mock::hcic_hcicmds;
-
-namespace {
-
-using testing::_;
-using testing::DoAll;
-using testing::NotNull;
-using testing::Pointee;
-using testing::Return;
-using testing::SaveArg;
-using testing::SaveArgPointee;
-using testing::StrEq;
-using testing::StrictMock;
-using testing::Test;
-
-class StackHciTest : public Test {
- public:
- protected:
- void SetUp() override { mock_function_count_map.clear(); }
- void TearDown() override {}
-};
-
-TEST_F(StackHciTest, hci_preamble) {
- {
- HciDataPreamble preamble;
-
- ASSERT_EQ(sizeof(preamble), HCI_DATA_PREAMBLE_SIZE);
-
- preamble.bits.handle = 0xfff;
- preamble.bits.boundary = 0x3;
- preamble.bits.broadcast = 0x1;
- preamble.bits.unused15 = 0x0;
- preamble.bits.length = 0xffff;
-
- ASSERT_EQ(0x7fff, preamble.raw.word0);
- ASSERT_EQ(0xffff, preamble.raw.word1);
-
- const uint8_t exp[] = {0xff, 0x7f, 0xff, 0xff};
- uint8_t act[sizeof(preamble)];
- preamble.Serialize(act);
- ASSERT_EQ(0, std::memcmp(exp, act, sizeof(preamble)));
- }
-
- {
- HciDataPreamble preamble;
- preamble.raw.word0 =
- 0x123 | (L2CAP_PKT_START_NON_FLUSHABLE << L2CAP_PKT_TYPE_SHIFT);
- preamble.raw.word1 = 0x4567;
-
- ASSERT_EQ(sizeof(preamble), HCI_DATA_PREAMBLE_SIZE);
-
- ASSERT_EQ(0x0123, preamble.raw.word0);
- ASSERT_EQ(0x4567, preamble.raw.word1);
-
- const uint8_t exp[] = {0x23, 0x01, 0x67, 0x45};
- uint8_t act[sizeof(preamble)];
- preamble.Serialize(act);
- ASSERT_EQ(0, std::memcmp(exp, act, sizeof(preamble)));
- }
- {
- HciDataPreamble preamble;
- preamble.raw.word0 = 0x123 | (L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT);
- preamble.raw.word1 = 0x4567;
-
- ASSERT_EQ(sizeof(preamble), HCI_DATA_PREAMBLE_SIZE);
-
- ASSERT_EQ(0x2123, preamble.raw.word0);
- ASSERT_EQ(0x4567, preamble.raw.word1);
-
- const uint8_t exp[] = {0x23, 0x21, 0x67, 0x45};
- uint8_t act[sizeof(preamble)];
- preamble.Serialize(act);
- ASSERT_EQ(0, std::memcmp(exp, act, sizeof(preamble)));
- }
-
- {
- HciDataPreamble preamble;
- preamble.raw.word0 = 0x0 | (L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT);
- preamble.raw.word1 = 0x0;
-
- ASSERT_EQ(sizeof(preamble), HCI_DATA_PREAMBLE_SIZE);
-
- ASSERT_EQ(0x2000, preamble.raw.word0);
- ASSERT_EQ(0x0000, preamble.raw.word1);
-
- const uint8_t exp[] = {0x00, 0x20, 0x00, 0x00};
- uint8_t act[sizeof(preamble)];
- preamble.Serialize(act);
- ASSERT_EQ(0, std::memcmp(exp, act, sizeof(preamble)));
- }
-
- {
- HciDataPreamble preamble;
- preamble.raw.word0 = 0x0 | (L2CAP_PKT_START << L2CAP_PKT_TYPE_SHIFT);
- preamble.raw.word1 = 0x0;
-
- ASSERT_TRUE(preamble.IsFlushable());
-
- preamble.raw.word0 =
- 0x0 | (L2CAP_PKT_START << L2CAP_PKT_START_NON_FLUSHABLE);
- ASSERT_TRUE(!preamble.IsFlushable());
- }
-}
-
-} // namespace
diff --git a/stack/test/hid/stack_hid_test.cc b/stack/test/hid/stack_hid_test.cc
deleted file mode 100644
index 3a955d348..000000000
--- a/stack/test/hid/stack_hid_test.cc
+++ /dev/null
@@ -1,77 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <gmock/gmock.h>
-#include <gtest/gtest.h>
-#include <cstring>
-#include <map>
-
-#include "common/message_loop_thread.h"
-#include "osi/include/log.h"
-#include "stack/hid/hidh_int.h"
-#include "stack/include/hci_error_code.h"
-#include "test/mock/mock_stack_l2cap_api.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
-
-std::map<std::string, int> mock_function_count_map;
-
-bluetooth::common::MessageLoopThread* get_main_thread() { return nullptr; }
-tHCI_REASON btm_get_acl_disc_reason_code(void) { return HCI_SUCCESS; }
-
-bool BTM_IsAclConnectionUp(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- return true;
-}
-namespace {
-
-using testing::_;
-using testing::DoAll;
-using testing::NotNull;
-using testing::Pointee;
-using testing::Return;
-using testing::SaveArg;
-using testing::SaveArgPointee;
-using testing::StrEq;
-using testing::StrictMock;
-using testing::Test;
-
-class StackHidTest : public Test {
- public:
- protected:
- void SetUp() override { mock_function_count_map.clear(); }
- void TearDown() override {}
-};
-
-TEST_F(StackHidTest, disconnect_bad_cid) {
- tL2CAP_APPL_INFO l2cap_callbacks;
-
- test::mock::stack_l2cap_api::L2CA_Register2.body =
- [&l2cap_callbacks](uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level) {
- l2cap_callbacks = p_cb_info;
- return psm;
- };
-
- tHID_STATUS status = hidh_conn_reg();
- ASSERT_EQ(HID_SUCCESS, status);
-
- l2cap_callbacks.pL2CA_Error_Cb(123, 456);
-}
-
-} // namespace
diff --git a/stack/test/rfcomm/stack_rfcomm_test.cc b/stack/test/rfcomm/stack_rfcomm_test.cc
index b20bc8ba4..d0d1c6e4e 100644
--- a/stack/test/rfcomm/stack_rfcomm_test.cc
+++ b/stack/test/rfcomm/stack_rfcomm_test.cc
@@ -26,6 +26,7 @@
#include "osi/include/osi.h"
#include "port_api.h"
+#include "btm_int.h"
#include "rfc_int.h"
#include "mock_btm_layer.h"
@@ -159,7 +160,7 @@ class StackRfcommTest : public Test {
VLOG(1) << "Step 2";
// MTU configuration is done
cfg_req.mtu_present = false;
- l2cap_appl_info_.pL2CA_ConfigCfm_Cb(lcid, L2CAP_CFG_OK, {});
+ l2cap_appl_info_.pL2CA_ConfigCfm_Cb(lcid, &cfg_req);
VLOG(1) << "Step 3";
// Remote device also ask to configure MTU size
@@ -300,7 +301,7 @@ class StackRfcommTest : public Test {
VLOG(1) << "Step 2";
// Remote device confirms our configuration request
cfg_req.mtu_present = false;
- l2cap_appl_info_.pL2CA_ConfigCfm_Cb(lcid, L2CAP_CFG_OK, {});
+ l2cap_appl_info_.pL2CA_ConfigCfm_Cb(lcid, &cfg_req);
VLOG(1) << "Step 3";
// Remote device also asks to configure MTU
@@ -453,7 +454,8 @@ class StackRfcommTest : public Test {
bluetooth::l2cap::SetMockInterface(&l2cap_interface_);
rfcomm_callback = &rfcomm_callback_;
EXPECT_CALL(l2cap_interface_, Register(BT_PSM_RFCOMM, _, _, _))
- .WillOnce(Return(BT_PSM_RFCOMM));
+ .WillOnce(
+ DoAll(SaveArgPointee<1>(&l2cap_appl_info_), Return(BT_PSM_RFCOMM)));
RFCOMM_Init();
rfc_cb.trace_level = BT_TRACE_LEVEL_DEBUG;
}
@@ -781,7 +783,8 @@ TEST_F(StackRfcommTest, TestConnectionCollision) {
VLOG(1) << "Step 6";
// Remote device accepted our MTU size
- l2cap_appl_info_.pL2CA_ConfigCfm_Cb(new_lcid, L2CAP_CFG_OK, {});
+ tL2CAP_CFG_INFO peer_cfg_rsp = {.mtu_present = true, .mtu = L2CAP_MTU_SIZE};
+ l2cap_appl_info_.pL2CA_ConfigCfm_Cb(new_lcid, &peer_cfg_rsp);
// L2CAP collision and connection setup done
diff --git a/stack/test/stack_a2dp_test.cc b/stack/test/stack_a2dp_test.cc
index 2c1e38739..fecb3cada 100644
--- a/stack/test/stack_a2dp_test.cc
+++ b/stack/test/stack_a2dp_test.cc
@@ -41,9 +41,9 @@ const uint8_t codec_info_sbc[AVDT_CODEC_SIZE] = {
// Allocation Method: A2DP_SBC_IE_ALLOC_MD_L
2, // MinimumBitpool Value: A2DP_SBC_IE_MIN_BITPOOL
53, // Maximum Bitpool Value: A2DP_SBC_MAX_BITPOOL
- 7, // Fake
- 8, // Fake
- 9 // Fake
+ 7, // Dummy
+ 8, // Dummy
+ 9 // Dummy
};
const uint8_t codec_info_sbc_capability[AVDT_CODEC_SIZE] = {
@@ -61,9 +61,9 @@ const uint8_t codec_info_sbc_capability[AVDT_CODEC_SIZE] = {
0x01, // Allocation Method: A2DP_SBC_IE_ALLOC_MD_L
2, // MinimumBitpool Value: A2DP_SBC_IE_MIN_BITPOOL
53, // Maximum Bitpool Value: A2DP_SBC_MAX_BITPOOL
- 7, // Fake
- 8, // Fake
- 9 // Fake
+ 7, // Dummy
+ 8, // Dummy
+ 9 // Dummy
};
const uint8_t codec_info_sbc_sink_capability[AVDT_CODEC_SIZE] = {
@@ -86,9 +86,9 @@ const uint8_t codec_info_sbc_sink_capability[AVDT_CODEC_SIZE] = {
// A2DP_SBC_IE_ALLOC_MD_L
2, // MinimumBitpool Value: A2DP_SBC_IE_MIN_BITPOOL
53, // Maximum Bitpool Value: A2DP_SBC_MAX_BITPOOL
- 7, // Fake
- 8, // Fake
- 9 // Fake
+ 7, // Dummy
+ 8, // Dummy
+ 9 // Dummy
};
const uint8_t codec_info_aac[AVDT_CODEC_SIZE] = {
@@ -103,26 +103,9 @@ const uint8_t codec_info_aac[AVDT_CODEC_SIZE] = {
// Bit Rate: 320000 = 0x4e200
0xe2, // Bit Rate: 320000 = 0x4e200
0x00, // Bit Rate: 320000 = 0x4e200
- 7, // Unused
- 8, // Unused
- 9 // Unused
-};
-
-const uint8_t codec_info_aac_vbr[AVDT_CODEC_SIZE] = {
- 8, // Length (A2DP_AAC_INFO_LEN)
- 0, // Media Type: AVDT_MEDIA_TYPE_AUDIO
- 2, // Media Codec Type: A2DP_MEDIA_CT_AAC
- 0x80, // Object Type: A2DP_AAC_OBJECT_TYPE_MPEG2_LC
- 0x01, // Sampling Frequency: A2DP_AAC_SAMPLING_FREQ_44100
- 0x04, // Channels: A2DP_AAC_CHANNEL_MODE_STEREO
- 0x80 | 0x4, // Variable Bit Rate:
- // A2DP_AAC_VARIABLE_BIT_RATE_ENABLED
- // Bit Rate: 320000 = 0x4e200
- 0xe2, // Bit Rate: 320000 = 0x4e200
- 0x00, // Bit Rate: 320000 = 0x4e200
- 7, // Unused
- 8, // Unused
- 9 // Unused
+ 7, // Dummy
+ 8, // Dummy
+ 9 // Dummy
};
const uint8_t codec_info_aac_capability[AVDT_CODEC_SIZE] = {
@@ -138,27 +121,9 @@ const uint8_t codec_info_aac_capability[AVDT_CODEC_SIZE] = {
// Bit Rate: 320000 = 0x4e200
0xe2, // Bit Rate: 320000 = 0x4e200
0x00, // Bit Rate: 320000 = 0x4e200
- 7, // Unused
- 8, // Unused
- 9 // Unused
-};
-
-const uint8_t codec_info_aac_vbr_capability[AVDT_CODEC_SIZE] = {
- 8, // Length (A2DP_AAC_INFO_LEN)
- 0, // Media Type: AVDT_MEDIA_TYPE_AUDIO
- 2, // Media Codec Type: A2DP_MEDIA_CT_AAC
- 0x80, // Object Type: A2DP_AAC_OBJECT_TYPE_MPEG2_LC
- 0x01, // Sampling Frequency: A2DP_AAC_SAMPLING_FREQ_44100
- // TODO: AAC 48.0kHz sampling rate should be added back - see b/62301376
- 0x04, // Channels: A2DP_AAC_CHANNEL_MODE_STEREO
- 0x80 | 0x4, // Variable Bit Rate:
- // A2DP_AAC_VARIABLE_BIT_RATE_ENABLED
- // Bit Rate: 320000 = 0x4e200
- 0xe2, // Bit Rate: 320000 = 0x4e200
- 0x00, // Bit Rate: 320000 = 0x4e200
- 7, // Unused
- 8, // Unused
- 9 // Unused
+ 7, // Dummy
+ 8, // Dummy
+ 9 // Dummy
};
const uint8_t codec_info_aac_sink_capability[AVDT_CODEC_SIZE] = {
@@ -182,9 +147,9 @@ const uint8_t codec_info_aac_sink_capability[AVDT_CODEC_SIZE] = {
// Bit Rate: 320000 = 0x4e200
0xe2, // Bit Rate: 320000 = 0x4e200
0x00, // Bit Rate: 320000 = 0x4e200
- 7, // Fake
- 8, // Fake
- 9 // Fake
+ 7, // Dummy
+ 8, // Dummy
+ 9 // Dummy
};
const uint8_t codec_info_non_a2dp[AVDT_CODEC_SIZE] = {
@@ -193,16 +158,16 @@ const uint8_t codec_info_non_a2dp[AVDT_CODEC_SIZE] = {
0xFF, // Media Codec Type: A2DP_MEDIA_CT_NON_A2DP
3, 4, 0, 0, // Vendor ID: LSB first, upper two octets should be 0
7, 8, // Codec ID: LSB first
- 9 // Fake
+ 9 // Dummy
};
-const uint8_t codec_info_non_a2dp_fake[AVDT_CODEC_SIZE] = {
+const uint8_t codec_info_non_a2dp_dummy[AVDT_CODEC_SIZE] = {
8, // Length
0, // Media Type: AVDT_MEDIA_TYPE_AUDIO
0xFF, // Media Codec Type: A2DP_MEDIA_CT_NON_A2DP
3, 4, 0, 0, // Vendor ID: LSB first, upper two octets should be 0
7, 8, // Codec ID: LSB first
- 10 // Unused
+ 10 // Dummy
};
static const char* APTX_ENCODER_LIB_NAME = "libaptX_encoder.so";
@@ -352,10 +317,6 @@ TEST_F(StackA2dpTest, test_a2dp_is_codec_valid_sbc) {
}
TEST_F(StackA2dpTest, test_a2dp_is_codec_valid_aac) {
- ASSERT_TRUE(A2DP_IsSourceCodecValid(codec_info_aac_vbr));
- ASSERT_TRUE(A2DP_IsSourceCodecValid(codec_info_aac_vbr_capability));
- ASSERT_TRUE(A2DP_IsPeerSourceCodecValid(codec_info_aac_vbr));
- ASSERT_TRUE(A2DP_IsPeerSourceCodecValid(codec_info_aac_vbr_capability));
EXPECT_TRUE(A2DP_IsSourceCodecValid(codec_info_aac));
EXPECT_TRUE(A2DP_IsSourceCodecValid(codec_info_aac_capability));
EXPECT_TRUE(A2DP_IsPeerSourceCodecValid(codec_info_aac));
@@ -449,7 +410,7 @@ TEST_F(StackA2dpTest, test_a2dp_get_media_type) {
EXPECT_EQ(A2DP_GetMediaType(codec_info_aac), AVDT_MEDIA_TYPE_AUDIO);
EXPECT_EQ(A2DP_GetMediaType(codec_info_non_a2dp), AVDT_MEDIA_TYPE_AUDIO);
- // Prepare fake codec info for video and for multimedia
+ // Prepare dummy codec info for video and for multimedia
memset(codec_info_test, 0, sizeof(codec_info_test));
codec_info_test[0] = sizeof(codec_info_test);
codec_info_test[1] = 0x01 << 4;
@@ -495,7 +456,7 @@ TEST_F(StackA2dpTest, test_a2dp_codec_type_equals) {
EXPECT_TRUE(
A2DP_CodecTypeEquals(codec_info_aac, codec_info_aac_sink_capability));
EXPECT_TRUE(
- A2DP_CodecTypeEquals(codec_info_non_a2dp, codec_info_non_a2dp_fake));
+ A2DP_CodecTypeEquals(codec_info_non_a2dp, codec_info_non_a2dp_dummy));
EXPECT_FALSE(A2DP_CodecTypeEquals(codec_info_sbc, codec_info_non_a2dp));
EXPECT_FALSE(A2DP_CodecTypeEquals(codec_info_aac, codec_info_non_a2dp));
EXPECT_FALSE(A2DP_CodecTypeEquals(codec_info_sbc, codec_info_aac));
@@ -544,14 +505,14 @@ TEST_F(StackA2dpTest, test_a2dp_codec_equals) {
codec_info_aac_test[8] = codec_info_aac[8] + 1;
EXPECT_FALSE(A2DP_CodecEquals(codec_info_aac, codec_info_aac_test));
- // Test two SBC codecs that are identical, but with different fake
+ // Test two SBC codecs that are identical, but with different dummy
// trailer data.
memset(codec_info_sbc_test, 0xAB, sizeof(codec_info_sbc_test));
memcpy(codec_info_sbc_test, codec_info_sbc, sizeof(codec_info_sbc));
codec_info_sbc_test[7] = codec_info_sbc[7] + 1;
EXPECT_TRUE(A2DP_CodecEquals(codec_info_sbc, codec_info_sbc_test));
- // Test two AAC codecs that are identical, but with different fake
+ // Test two AAC codecs that are identical, but with different dummy
// trailer data.
memset(codec_info_aac_test, 0xAB, sizeof(codec_info_aac_test));
memcpy(codec_info_aac_test, codec_info_aac, sizeof(codec_info_aac));
@@ -831,22 +792,12 @@ TEST_F(StackA2dpTest, test_a2dp_init_codec_config) {
// Test for AAC Source
//
memset(&avdt_cfg, 0, sizeof(avdt_cfg));
- ASSERT_TRUE(
+ EXPECT_TRUE(
A2DP_InitCodecConfig(BTAV_A2DP_CODEC_INDEX_SOURCE_AAC, &avdt_cfg));
- // Check the vbr mode status.
- bool aac_vbr_mode_enabled =
- avdt_cfg.codec_info[6] & A2DP_AAC_VARIABLE_BIT_RATE_MASK;
// Compare the result codec with the local test codec info
- if (aac_vbr_mode_enabled) {
- for (size_t i = 0; i < codec_info_aac_vbr_capability[0] + 1; i++) {
- ASSERT_EQ(avdt_cfg.codec_info[i], codec_info_aac_vbr_capability[i]);
- }
- } else {
- for (size_t i = 0; i < codec_info_aac_capability[0] + 1; i++) {
- ASSERT_EQ(avdt_cfg.codec_info[i], codec_info_aac_capability[i]);
- }
+ for (size_t i = 0; i < codec_info_aac_capability[0] + 1; i++) {
+ EXPECT_EQ(avdt_cfg.codec_info[i], codec_info_aac_capability[i]);
}
-
// Test for content protection
#if (BTA_AV_CO_CP_SCMS_T == TRUE)
EXPECT_EQ(avdt_cfg.protect_info[0], AVDT_CP_LOSC);
@@ -902,6 +853,23 @@ TEST_F(A2dpCodecConfigTest, setCodecConfig) {
}
EXPECT_EQ(codec_config->getAudioBitsPerSample(), 16);
+ // Create the codec capability - AAC
+ memset(codec_info_result, 0, sizeof(codec_info_result));
+ peer_codec_index = A2DP_SourceCodecIndex(codec_info_aac_sink_capability);
+ EXPECT_NE(peer_codec_index, BTAV_A2DP_CODEC_INDEX_MAX);
+ codec_config =
+ a2dp_codecs->findSourceCodecConfig(codec_info_aac_sink_capability);
+ EXPECT_NE(codec_config, nullptr);
+ EXPECT_TRUE(a2dp_codecs->setCodecConfig(
+ codec_info_aac_sink_capability, true /* is_capability */,
+ codec_info_result, true /* select_current_codec */));
+ EXPECT_EQ(a2dp_codecs->getCurrentCodecConfig(), codec_config);
+ // Compare the result codec with the local test codec info
+ for (size_t i = 0; i < codec_info_aac[0] + 1; i++) {
+ EXPECT_EQ(codec_info_result[i], codec_info_aac[i]);
+ }
+ EXPECT_EQ(codec_config->getAudioBitsPerSample(), 16);
+
// Create the codec config - SBC
memset(codec_info_result, 0, sizeof(codec_info_result));
peer_codec_index = A2DP_SourceCodecIndex(codec_info_sbc);
@@ -1005,59 +973,6 @@ TEST_F(A2dpCodecConfigTest, setCodecConfig) {
EXPECT_FALSE(a2dp_codecs->setCodecConfig(
codec_info_sbc_test1, true /* is_capability */, codec_info_result,
true /* select_current_codec */));
-
- AvdtpSepConfig avdt_cfg;
- memset(&avdt_cfg, 0, sizeof(avdt_cfg));
- ASSERT_TRUE(
- A2DP_InitCodecConfig(BTAV_A2DP_CODEC_INDEX_SOURCE_AAC, &avdt_cfg));
- bool aac_vbr_mode_enabled =
- avdt_cfg.codec_info[6] & A2DP_AAC_VARIABLE_BIT_RATE_MASK;
-
- // Create the codec capability - AAC
- memset(codec_info_result, 0, sizeof(codec_info_result));
- peer_codec_index = A2DP_SourceCodecIndex(codec_info_aac_sink_capability);
- ASSERT_NE(peer_codec_index, BTAV_A2DP_CODEC_INDEX_MAX);
- codec_config =
- a2dp_codecs->findSourceCodecConfig(codec_info_aac_sink_capability);
- ASSERT_NE(codec_config, nullptr);
- ASSERT_TRUE(a2dp_codecs->setCodecConfig(
- codec_info_aac_sink_capability, true /* is_capability */,
- codec_info_result, true /* select_current_codec */));
- ASSERT_EQ(a2dp_codecs->getCurrentCodecConfig(), codec_config);
- // Compare the result codec with the local test codec info
- if (aac_vbr_mode_enabled) {
- for (size_t i = 0; i < codec_info_aac_vbr[0] + 1; i++) {
- ASSERT_EQ(codec_info_result[i], codec_info_aac_vbr[i]);
- }
- } else {
- for (size_t i = 0; i < codec_info_aac[0] + 1; i++) {
- ASSERT_EQ(codec_info_result[i], codec_info_aac[i]);
- }
- }
- ASSERT_EQ(codec_config->getAudioBitsPerSample(), 16);
-
- // Create the codec config - AAC with vbr
- memset(codec_info_result, 0, sizeof(codec_info_result));
- peer_codec_index = A2DP_SourceCodecIndex(codec_info_aac_vbr);
- ASSERT_NE(peer_codec_index, BTAV_A2DP_CODEC_INDEX_MAX);
- codec_config = a2dp_codecs->findSourceCodecConfig(codec_info_aac_vbr);
- ASSERT_NE(codec_config, nullptr);
- ASSERT_TRUE(a2dp_codecs->setCodecConfig(
- codec_info_aac_vbr, false /* is_capability */, codec_info_result,
- true /* select_current_codec */));
- ASSERT_EQ(a2dp_codecs->getCurrentCodecConfig(), codec_config);
- // Compare the result codec with the local test codec info
- if (aac_vbr_mode_enabled) {
- for (size_t i = 0; i < codec_info_aac[0] + 1; i++) {
- ASSERT_EQ(codec_info_result[i], codec_info_aac_vbr[i]);
- }
- } else {
- for (size_t i = 0; i < codec_info_aac[0] + 1; i++) {
- ASSERT_EQ(codec_info_result[i], codec_info_aac[i]);
- }
- }
- ASSERT_TRUE(codec_config->useRtpHeaderMarkerBit());
-
delete a2dp_codecs;
}
diff --git a/stack/test/stack_avdtp_test.cc b/stack/test/stack_avdtp_test.cc
deleted file mode 100644
index e6621bef8..000000000
--- a/stack/test/stack_avdtp_test.cc
+++ /dev/null
@@ -1,182 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-//#include <dlfcn.h>
-#include <gtest/gtest.h>
-
-#include "stack/include/avdt_api.h"
-#include "stack/avdt/avdt_int.h"
-#include "stack/test/common/mock_stack_avdt_msg.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Global trace level referred in the code under test
-uint8_t appl_trace_level = BT_TRACE_LEVEL_VERBOSE;
-
-void LogMsg(uint32_t trace_set_mask, const char* fmt_str, ...) { }
-
-// All mock requires this symbol to count calling times
-std::map<std::string, int> mock_function_count_map;
-
-class StackAvdtpTest : public ::testing::Test {
- protected:
- StackAvdtpTest() = default;
-
- virtual ~StackAvdtpTest() = default;
- protected:
- static AvdtpRcb _reg;
- static uint8_t _expected_stream_event;
-
- uint8_t scb_handle_;
-
- protected:
- static void _avdtcallback(UNUSED_ATTR uint8_t handle, const RawAddress& bd_addr,
- uint8_t event, tAVDT_CTRL* p_data, uint8_t scb_index) {
- mock_function_count_map[__func__]++;
- }
-
- static void _streamcallback(uint8_t handle, const RawAddress& bd_addr,
- uint8_t event, tAVDT_CTRL* p_data,
- uint8_t scb_index) {
- mock_function_count_map[__func__]++;
- ASSERT_EQ(event, _expected_stream_event);
- };
-
- static void SetUpTestCase() {
- _reg.ctrl_mtu = 672;
- _reg.ret_tout = 4;
- _reg.sig_tout = 4;
- _reg.idle_tout = 10;
- _reg.scb_index = 0;
- AVDT_Register(&_reg, _avdtcallback);
- }
-
- static void TearDownTestCase() {
- AVDT_Deregister();
- }
-
- void SetUp() override {
- uint8_t peer_id = 1;
- scb_handle_ = 0;
- _expected_stream_event = 0;
- AvdtpStreamConfig avdtp_stream_config;
- avdtp_stream_config.cfg.psc_mask = AVDT_PSC_DELAY_RPT;
- avdtp_stream_config.tsep = AVDT_TSEP_SNK;
- avdtp_stream_config.p_avdt_ctrl_cback = _streamcallback;
- mock_function_count_map["_streamcallback"] = 0;
-
- ASSERT_EQ(AVDT_CreateStream(peer_id, &scb_handle_, avdtp_stream_config), AVDT_SUCCESS);
- }
-
- void TearDown() override {
- ASSERT_EQ(AVDT_RemoveStream(scb_handle_), AVDT_SUCCESS);
- }
-
- void StreamCallBackExpect(uint8_t event) {
- _expected_stream_event = event;
- }
-};
-
-AvdtpRcb StackAvdtpTest::_reg{};
-uint8_t StackAvdtpTest::_expected_stream_event = 0;
-
-TEST_F(StackAvdtpTest, test_delay_report_as_accept) {
- // Get SCB ready to send response
- auto pscb = avdt_scb_by_hdl(scb_handle_);
- pscb->in_use = true;
-
- // Send SetConfig response
- uint8_t label = 0;
- uint8_t err_code = 0;
- uint8_t category = 0;
-
- mock_avdt_msg_send_cmd_clear_history();
- mock_avdt_msg_send_rsp_clear_history();
- mock_function_count_map["avdt_msg_send_rsp"] = 0;
- mock_function_count_map["avdt_msg_send_cmd"] = 0;
- ASSERT_EQ(AVDT_ConfigRsp(scb_handle_, label, err_code, category), AVDT_SUCCESS);
-
- // Config response sent
- ASSERT_EQ(mock_function_count_map["avdt_msg_send_rsp"], 1);
- ASSERT_EQ(mock_avdt_msg_send_rsp_get_sig_id_at(0), AVDT_SIG_SETCONFIG);
-
- // Delay report command sent
- ASSERT_EQ(mock_function_count_map["avdt_msg_send_cmd"], 1);
- ASSERT_EQ(mock_avdt_msg_send_cmd_get_sig_id_at(0), AVDT_SIG_DELAY_RPT);
-
- // Delay report confirmed
- tAVDT_SCB_EVT data;
- ASSERT_EQ(mock_function_count_map["_streamcallback"], 0);
- StreamCallBackExpect(AVDT_DELAY_REPORT_CFM_EVT);
- avdt_scb_hdl_delay_rpt_rsp(pscb, &data);
- ASSERT_EQ(mock_function_count_map["_streamcallback"], 1);
-}
-
-TEST_F(StackAvdtpTest, test_no_delay_report_if_not_sink) {
- // Get SCB ready to send response
- auto pscb = avdt_scb_by_hdl(scb_handle_);
- pscb->in_use = true;
-
- // Change the scb to SRC
- pscb->stream_config.tsep = AVDT_TSEP_SRC;
-
- // Send SetConfig response
- uint8_t label = 0;
- uint8_t err_code = 0;
- uint8_t category = 0;
- mock_function_count_map["avdt_msg_send_rsp"] = 0;
- mock_function_count_map["avdt_msg_send_cmd"] = 0;
- ASSERT_EQ(AVDT_ConfigRsp(scb_handle_, label, err_code, category), AVDT_SUCCESS);
- ASSERT_EQ(mock_function_count_map["avdt_msg_send_rsp"], 1); // Config response sent
- ASSERT_EQ(mock_function_count_map["avdt_msg_send_cmd"], 0); // Delay report command not sent
-}
-
-TEST_F(StackAvdtpTest, test_no_delay_report_if_not_enabled) {
- // Get SCB ready to send response
- auto pscb = avdt_scb_by_hdl(scb_handle_);
- pscb->in_use = true;
-
- // Disable the scb's delay report mask
- pscb->stream_config.cfg.psc_mask &= ~AVDT_PSC_DELAY_RPT;
-
- // Send SetConfig response
- uint8_t label = 0;
- uint8_t err_code = 0;
- uint8_t category = 0;
- mock_function_count_map["avdt_msg_send_rsp"] = 0;
- mock_function_count_map["avdt_msg_send_cmd"] = 0;
- ASSERT_EQ(AVDT_ConfigRsp(scb_handle_, label, err_code, category), AVDT_SUCCESS);
- ASSERT_EQ(mock_function_count_map["avdt_msg_send_rsp"], 1); // Config response sent
- ASSERT_EQ(mock_function_count_map["avdt_msg_send_cmd"], 0); // Delay report command not sent
-}
-
-TEST_F(StackAvdtpTest, test_delay_report_as_init) {
- auto pscb = avdt_scb_by_hdl(scb_handle_);
-
- tAVDT_SCB_EVT data;
-
- mock_function_count_map["avdt_msg_send_cmd"] = 0;
-
- // Delay report -> Open command
- mock_avdt_msg_send_cmd_clear_history();
- avdt_scb_event(pscb, AVDT_SCB_MSG_SETCONFIG_RSP_EVT, &data);
- ASSERT_EQ(mock_function_count_map["avdt_msg_send_cmd"], 2);
- ASSERT_EQ(mock_avdt_msg_send_cmd_get_sig_id_at(0), AVDT_SIG_DELAY_RPT);
- ASSERT_EQ(mock_avdt_msg_send_cmd_get_sig_id_at(1), AVDT_SIG_OPEN);
-}
-
diff --git a/stack/test/stack_btu_test.cc b/stack/test/stack_btu_test.cc
index 86011d0dd..250264699 100644
--- a/stack/test/stack_btu_test.cc
+++ b/stack/test/stack_btu_test.cc
@@ -1,30 +1,127 @@
-/*
- * Copyright 2021 The Android Open Source Project
+/******************************************************************************
*
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
+ * Copyright 2017 The Android Open Source Project
*
- * http://www.apache.org/licenses/LICENSE-2.0
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at:
*
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ *
+ ******************************************************************************/
+#include <base/bind.h>
+#include <base/logging.h>
+#include <base/threading/thread.h>
+#include <gmock/gmock.h>
#include <gtest/gtest.h>
-#include <cstdint>
-#include <map>
-#include <string>
+#include <semaphore.h>
+#include <time.h>
+#include <unistd.h>
+#include "btcore/include/module.h"
+#include "common/message_loop_thread.h"
+#include "osi/include/alarm.h"
+#include "osi/include/fixed_queue.h"
#include "stack/include/btu.h"
-std::map<std::string, int> mock_function_count_map;
+class TimeoutHelper {
+ public:
+ TimeoutHelper() { sem_init(&sem, 0, 0); }
+
+ ~TimeoutHelper() { sem_destroy(&sem); }
+
+ void wait(int seconds, base::Closure callback) {
+ struct timespec timeout;
+ clock_gettime(CLOCK_REALTIME, &timeout);
+ timeout.tv_sec += seconds;
+
+ int semvalue;
+ sem_getvalue(&sem, &semvalue);
+
+ // Call the callback if timeout occured
+ if (sem_timedwait(&sem, &timeout) == -1 && !callback.is_null()) {
+ callback.Run();
+ }
+ }
+
+ void notify() { sem_post(&sem); }
+
+ private:
+ sem_t sem;
+};
+
+TimeoutHelper helper;
+
+// External function definitions
+void btu_task_start_up(void* context);
+void btu_task_shut_down(void* context);
+
+/* Below are methods and variables that must be implemented if we don't want to
+ * compile the whole stack. They will be removed, or changed into mocks one by
+ * one in the future, as the refactoring progresses */
+bt_status_t do_in_jni_thread(const base::Location& from_here,
+ base::OnceClosure task) {
+ helper.notify();
+ return BT_STATUS_SUCCESS;
+}
+
+void btu_init_core(){};
+void btif_init_ok(unsigned short, char*){};
+void BTE_InitStack(){};
+void bta_sys_init(){};
+void bta_sys_free(){};
+void btu_free_core(){};
+const module_t* get_module(const char*) { return nullptr; };
+bool module_init(module_t const*) { return true; };
+void module_clean_up(module_t const*){};
+
+bluetooth::common::MessageLoopThread bt_startup_thread("test alarm thread");
+
+class BtuMessageLoopTest : public testing::Test {
+ public:
+ MOCK_METHOD0(TestCallback, void(void));
+ base::MessageLoop* message_loop;
+
+ void SetUp() override {
+ // Initialize alarms to prevent btu_task_shut_down from crashing
+ alarm_new("test alarm");
+ bt_startup_thread.StartUp();
+ // btu_task_start_up calls btif_transfer_context to let the stack know
+ // start up is finished
+ btu_task_start_up(nullptr);
+ helper.wait(5, base::Bind(&BtuMessageLoopTest::Fail, base::Unretained(this),
+ "BTU startup timed out"));
+ }
+
+ void TearDown() override {
+ btu_task_shut_down(nullptr);
+ alarm_cleanup();
+ bt_startup_thread.ShutDown();
+ }
+
+ void Fail(std::string message) { FAIL() << message; }
+};
+
+TEST_F(BtuMessageLoopTest, send_message) {
+ message_loop = get_main_message_loop();
+ EXPECT_FALSE(message_loop == nullptr);
-void LogMsg(uint32_t trace_set_mask, const char* fmt_str, ...) {}
+ EXPECT_CALL(*this, TestCallback()).Times(1);
+ message_loop->task_runner()->PostTask(
+ FROM_HERE,
+ base::Bind(&BtuMessageLoopTest::TestCallback, base::Unretained(this)));
-class StackBtuTest : public ::testing::Test {};
+ message_loop->task_runner()->PostTask(
+ FROM_HERE, base::Bind(&TimeoutHelper::notify, base::Unretained(&helper)));
-TEST_F(StackBtuTest, post_on_main) {}
+ // Prevent the test from ending before the message loop posts the function
+ helper.wait(5, base::Bind(&BtuMessageLoopTest::Fail, base::Unretained(this),
+ "Timed out waiting for callback"));
+}
diff --git a/stack/test/stack_gatt_sr_hash_test.cc b/stack/test/stack_gatt_sr_hash_test.cc
deleted file mode 100644
index ffaf59dbf..000000000
--- a/stack/test/stack_gatt_sr_hash_test.cc
+++ /dev/null
@@ -1,89 +0,0 @@
-/******************************************************************************
- *
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at:
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- *
- ******************************************************************************/
-
-#include <gtest/gtest.h>
-
-#include "stack/test/common/mock_eatt.h"
-#include "crypto_toolbox/crypto_toolbox.h"
-#include "stack/gatt/gatt_int.h"
-
-using bluetooth::Uuid;
-
-tGATT_CB gatt_cb;
-
-std::map<std::string, int> mock_function_count_map;
-bool MOCK_bluetooth_shim_is_gd_acl_enabled_ = false;
-
-static void add_item_to_list(std::list<tGATT_SRV_LIST_ELEM>& srv_list_info,
- tGATT_SVC_DB* db, bool is_primary) {
- srv_list_info.emplace_back();
- tGATT_SRV_LIST_ELEM& elem = srv_list_info.back();
- elem.p_db = db;
- elem.is_primary = is_primary;
-}
-
-// BT Spec 5.2, Vol 3, Part G, Appendix B
-TEST(GattDatabaseTest, matchExampleInBtSpecV52) {
- tGATT_SVC_DB local_db[4];
- for (int i=0; i<4; i++) local_db[i] = tGATT_SVC_DB();
- std::list<tGATT_SRV_LIST_ELEM> srv_list_info;
-
- // 0x1800
- add_item_to_list(srv_list_info, &local_db[0], true);
- gatts_init_service_db(local_db[0], Uuid::From16Bit(0x1800), true, 0x0001, 5);
- gatts_add_characteristic(local_db[0],
- GATT_PERM_READ | GATT_PERM_WRITE,
- GATT_CHAR_PROP_BIT_READ | GATT_CHAR_PROP_BIT_WRITE,
- Uuid::From16Bit(0x2A00));
- gatts_add_characteristic(local_db[0], GATT_PERM_READ, GATT_CHAR_PROP_BIT_READ,
- Uuid::From16Bit(0x2A01));
- // 0x1801
- add_item_to_list(srv_list_info, &local_db[1], true);
- gatts_init_service_db(local_db[1], Uuid::From16Bit(0x1801), true, 0x0006, 8);
- gatts_add_characteristic(local_db[1], 0, GATT_CHAR_PROP_BIT_INDICATE,
- Uuid::From16Bit(0x2A05));
- gatts_add_char_descr(local_db[1], GATT_CHAR_PROP_BIT_READ, Uuid::From16Bit(0x2902));
- gatts_add_characteristic(local_db[1],
- GATT_PERM_READ | GATT_PERM_WRITE,
- GATT_CHAR_PROP_BIT_READ | GATT_CHAR_PROP_BIT_WRITE,
- Uuid::From16Bit(0x2B29));
- gatts_add_characteristic(local_db[1], GATT_PERM_READ, GATT_CHAR_PROP_BIT_READ,
- Uuid::From16Bit(0x2B2A));
- // 0x1808
- add_item_to_list(srv_list_info, &local_db[2], true);
- gatts_init_service_db(local_db[2], Uuid::From16Bit(0x1808), true, 0x000E, 6);
- gatts_add_included_service(local_db[2], 0x0014, 0x0016, Uuid::From16Bit(0x180F));
- gatts_add_characteristic(local_db[2], GATT_PERM_READ,
- GATT_CHAR_PROP_BIT_READ | GATT_CHAR_PROP_BIT_INDICATE | GATT_CHAR_PROP_BIT_EXT_PROP,
- Uuid::From16Bit(0x2A18));
- gatts_add_char_descr(local_db[2], 0x0000, Uuid::From16Bit(0x2902));
- gatts_add_char_ext_prop_descr(local_db[2], 0x0000);
- // 0x180F
- add_item_to_list(srv_list_info, &local_db[3], false);
- gatts_init_service_db(local_db[3], Uuid::From16Bit(0x180F), false, 0x0014, 3);
- gatts_add_characteristic(local_db[3], GATT_PERM_READ, GATT_CHAR_PROP_BIT_READ,
- Uuid::From16Bit(0x2A19));
-
- Octet16 expected_hash{0xF1, 0xCA, 0x2D, 0x48, 0xEC, 0xF5, 0x8B, 0xAC,
- 0x8A, 0x88, 0x30, 0xBB, 0xB9, 0xFB, 0xA9, 0x90};
- std::reverse(expected_hash.begin(), expected_hash.end());
-
- Octet16 result_hash = gatts_calculate_database_hash(&srv_list_info);
-
- ASSERT_EQ(result_hash, expected_hash);
-}
diff --git a/stack/test/stack_smp_test.cc b/stack/test/stack_smp_test.cc
index 639d24a90..d83430c36 100644
--- a/stack/test/stack_smp_test.cc
+++ b/stack/test/stack_smp_test.cc
@@ -25,13 +25,12 @@
#include "stack/include/smp_api.h"
#include "stack/smp/p_256_ecc_pp.h"
#include "stack/smp/smp_int.h"
-#include "types/hci_role.h"
/*
* This test verifies various key distribution methods in SMP works using the
* following parameter set:
*
- * When testing target as Central (Initiator is local, Responder is remote)
+ * When testing target as Master (Initiator is local, Responder is remote)
*
* Initiator's Pairing Request: 0x070710000001(01)
* Responder's Pairing Response: 0x050008000003(02)
@@ -148,8 +147,8 @@ class SmpCalculateConfirmTest : public Test {
p_cb_.peer_enc_size = 0x08;
p_cb_.peer_i_key = 0x00;
p_cb_.peer_r_key = 0x05;
- // Set role to central
- p_cb_.role = HCI_ROLE_CENTRAL;
+ // Set role to master
+ p_cb_.role = HCI_ROLE_MASTER;
std::reverse(rand_.begin(), rand_.end());
}
void TearDown() override {}
@@ -158,7 +157,7 @@ class SmpCalculateConfirmTest : public Test {
};
// Test smp_gen_p2_4_confirm function implementation
-TEST_F(SmpCalculateConfirmTest, test_smp_gen_p2_4_confirm_as_central) {
+TEST_F(SmpCalculateConfirmTest, test_smp_gen_p2_4_confirm_as_master) {
RawAddress remote_bda;
tBLE_ADDR_TYPE remote_bd_addr_type = 0;
BTM_ReadRemoteConnectionAddr(p_cb_.pairing_bda, remote_bda,
@@ -173,7 +172,7 @@ TEST_F(SmpCalculateConfirmTest, test_smp_gen_p2_4_confirm_as_central) {
}
// Test smp_gen_p1_4_confirm and aes_128 function implementation
-TEST_F(SmpCalculateConfirmTest, test_aes_128_as_central) {
+TEST_F(SmpCalculateConfirmTest, test_aes_128_as_master) {
RawAddress remote_bda;
tBLE_ADDR_TYPE remote_bd_addr_type = 0;
BTM_ReadRemoteConnectionAddr(p_cb_.pairing_bda, remote_bda,
@@ -199,7 +198,7 @@ TEST_F(SmpCalculateConfirmTest, test_aes_128_as_central) {
}
// Test smp_calculate_comfirm function implementation
-TEST_F(SmpCalculateConfirmTest, test_smp_calculate_comfirm_as_central) {
+TEST_F(SmpCalculateConfirmTest, test_smp_calculate_comfirm_as_master) {
Octet16 output;
tSMP_STATUS status = smp_calculate_comfirm(&p_cb_, rand_, &output);
EXPECT_EQ(status, SMP_SUCCESS);
diff --git a/test/Android.bp b/test/Android.bp
index a89951af6..8cf611e10 100644
--- a/test/Android.bp
+++ b/test/Android.bp
@@ -1,223 +1,4 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
subdirs = [
"rootcanal",
"suite",
]
-
-filegroup {
- name: "TestMockBta",
- srcs: [
- "mock/mock_bta_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockMainShim",
- srcs: [
- "mock/mock_main_shim*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockCommon",
- srcs: [
- "mock/mock_common_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockStackA2dp",
- srcs: [
- "mock/mock_stack_a2dp_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockStackL2cap",
- srcs: [
- "mock/mock_stack_l2cap_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockStack",
- srcs: [
- "mock/mock_stack_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockHci",
- srcs: [
- "mock/mock_hci_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockFrameworks",
- srcs: [
- "mock/mock_frameworks_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockBtcore",
- srcs: [
- "mock/mock_btcore_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockSystemLibfmq",
- srcs: [
- "mock/mock_system_libfmq_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockUdrv",
- srcs: [
- "mock/mock_udrv_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockAndroidHardware",
- srcs: [
- "mock/mock_android_hardware_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockDevice",
- srcs: [
- "mock/mock_device_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockLegacyHciCommands",
- srcs: [
- "mock/mock_hcic_*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockMainShimEntry",
- srcs: [
- "mock/mock_main_shim_entry.cc",
- ],
-}
-
-filegroup {
- name: "TestMockMainShimFlags",
- srcs: [
- "mock/mock_main_shim.cc",
- ],
-}
-
-filegroup {
- name: "TestMockBtif",
- srcs: [
- "mock/mock_btif*.cc",
- ],
-}
-
-filegroup {
- name: "TestStackL2cap",
- srcs: [
- "mock/mock_stack_l2cap_*.cc",
- ],
-}
-
-filegroup {
- name: "TestStackSdp",
- srcs: [
- "mock/mock_stack_sdp*.cc",
- ],
-}
-
-filegroup {
- name: "TestStackBtm",
- srcs: [
- "mock/mock_stack_btm*.cc",
- ],
-}
-
-filegroup {
- name: "TestStubLegacyTrace",
- srcs: [
- "stub/legacy_trace.cc",
- ],
-}
-
-filegroup {
- name: "TestStubOsi",
- srcs: [
- "stub/osi.cc",
- ],
-}
-
-filegroup {
- name: "TestMockStackAcl",
- srcs: [
- "mock/mock_stack_acl*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockStackSmp",
- srcs: [
- "mock/mock_stack_smp*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockStackMetrics",
- srcs: [
- "mock/mock_stack_metrics*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockStackGap",
- srcs: [
- "mock/mock_stack_gap*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockStackGatt",
- srcs: [
- "mock/mock_stack_gatt*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockStackBtu",
- srcs: [
- "mock/mock_stack_btu*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockMainBte",
- srcs: [
- "mock/mock_main_bte*.cc",
- ],
-}
-
-filegroup {
- name: "TestMockStackCryptotoolbox",
- srcs: [
- "mock/mock_stack_crypto_toolbox*.cc",
- ],
-}
diff --git a/test/common/main_handler.cc b/test/common/main_handler.cc
deleted file mode 100644
index a6137fdfb..000000000
--- a/test/common/main_handler.cc
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <base/bind.h>
-#include <base/callback_forward.h>
-#include <base/location.h>
-#include <base/time/time.h>
-#include <functional>
-
-#include "common/message_loop_thread.h"
-#include "include/hardware/bluetooth.h"
-#include "osi/include/log.h"
-
-using bluetooth::common::MessageLoopThread;
-using BtMainClosure = std::function<void()>;
-
-namespace {
-
-MessageLoopThread main_thread("bt_fake_main_thread", true);
-void do_post_on_bt_main(BtMainClosure closure) { closure(); }
-
-} // namespace
-
-bt_status_t do_in_main_thread(const base::Location& from_here,
- base::OnceClosure task) {
- ASSERT_LOG(main_thread.DoInThread(from_here, std::move(task)),
- "Unable to run on main thread");
- return BT_STATUS_SUCCESS;
-}
-
-bt_status_t do_in_main_thread_delayed(const base::Location& from_here,
- base::OnceClosure task,
- const base::TimeDelta& delay) {
- ASSERT_LOG(!main_thread.DoInThreadDelayed(from_here, std::move(task), delay),
- "Unable to run on main thread delayed");
- return BT_STATUS_SUCCESS;
-}
-
-void post_on_bt_main(BtMainClosure closure) {
- ASSERT(do_in_main_thread(FROM_HERE,
- base::Bind(do_post_on_bt_main, std::move(closure))));
-}
-
-void main_thread_start_up() {
- main_thread.StartUp();
- ASSERT_LOG(main_thread.IsRunning(),
- "Unable to start message loop on main thread");
-}
-
-void main_thread_shut_down() { main_thread.ShutDown(); }
diff --git a/test/common/main_handler.h b/test/common/main_handler.h
deleted file mode 100644
index c4e50696b..000000000
--- a/test/common/main_handler.h
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <base/callback_forward.h>
-#include <base/location.h>
-#include <base/time/time.h>
-#include <functional>
-
-#include "common/message_loop_thread.h"
-
-using bluetooth::common::MessageLoopThread;
-using BtMainClosure = std::function<void()>;
-
-bt_status_t do_in_main_thread(const base::Location& from_here,
- base::OnceClosure task);
-bt_status_t do_in_main_thread_delayed(const base::Location& from_here,
- base::OnceClosure task,
- const base::TimeDelta& delay);
-void post_on_bt_main(BtMainClosure closure);
-void main_thread_start_up();
-void main_thread_shut_down();
diff --git a/test/gen_coverage.py b/test/gen_coverage.py
index 187a90a15..c7b6c335f 100755
--- a/test/gen_coverage.py
+++ b/test/gen_coverage.py
@@ -70,7 +70,8 @@ COVERAGE_TESTS = [
],
},
{
- "test_name": "test-vendor_test_host",
+ "test_name":
+ "test-vendor_test_host",
"covered_files": [
"system/bt/vendor_libs/test_vendor_lib/include",
"system/bt/vendor_libs/test_vendor_lib/src",
@@ -153,8 +154,9 @@ def write_root_html_rows(f, tests):
json_results = generate_coverage_json(test)
test_totals = json_results['data'][0]['totals']
- f.write("<tr class='light-row'><td><pre><a href=\'" + os.path.join(test_name, "index.html") + "\'>" +
- test_name + "</a></pre></td>")
+ f.write("<tr class='light-row'><td><pre><a href=\'" +
+ os.path.join(test_name, "index.html") + "\'>" + test_name +
+ "</a></pre></td>")
for field_name in ['functions', 'instantiations', 'lines', 'regions']:
field = test_totals[field_name]
totals[field_name]['covered'] += field['covered']
@@ -178,7 +180,8 @@ def write_root_html_tail(f):
def generate_root_html(tests):
# Copy the css file from one of the coverage reports.
- source_file = os.path.join(os.path.join(WORKING_DIR, tests[0]['test_name']), "style.css")
+ source_file = os.path.join(
+ os.path.join(WORKING_DIR, tests[0]['test_name']), "style.css")
dest_file = os.path.join(WORKING_DIR, "style.css")
shutil.copy2(source_file, dest_file)
@@ -193,23 +196,28 @@ def get_profraw_for_test(test_name):
test_root = get_native_test_root_or_die()
test_cmd = os.path.join(os.path.join(test_root, test_name), test_name)
if not os.path.isfile(test_cmd):
- logging.error('The test ' + test_name + ' does not exist, please compile first')
+ logging.error('The test ' + test_name +
+ ' does not exist, please compile first')
sys.exit(1)
profraw_file_name = test_name + ".profraw"
- profraw_path = os.path.join(WORKING_DIR, os.path.join(test_name, profraw_file_name))
+ profraw_path = os.path.join(WORKING_DIR,
+ os.path.join(test_name, profraw_file_name))
llvm_env_var = "LLVM_PROFILE_FILE=\"" + profraw_path + "\""
test_cmd = llvm_env_var + " " + test_cmd
logging.info('Generating profraw data for ' + test_name)
logging.debug('cmd: ' + test_cmd)
if subprocess.call(test_cmd, shell=True) != 0:
- logging.error('Test ' + test_name + ' failed. Please fix the test before generating coverage.')
+ logging.error(
+ 'Test ' + test_name +
+ ' failed. Please fix the test before generating coverage.')
sys.exit(1)
if not os.path.isfile(profraw_path):
logging.error(
- 'Generating the profraw file failed. Did you remember to add the proper compiler flags to your build?')
+ 'Generating the profraw file failed. Did you remember to add the proper compiler flags to your build?'
+ )
sys.exit(1)
return profraw_file_name
@@ -241,14 +249,16 @@ def generate_coverage_html(test):
test_profdata_file = os.path.join(test_working_dir, test_name + ".profdata")
cmd = [
- os.path.join(get_android_root_or_die(), LLVM_COV), "show", "-format=html", "-summary-only",
- "-show-line-counts-or-regions", "-show-instantiation-summary", "-instr-profile=" + test_profdata_file,
- "-path-equivalence=\"" + COVERAGE_ROOT + "\",\"" + get_android_root_or_die() + "\"",
- "-output-dir=" + test_working_dir
+ os.path.join(get_android_root_or_die(), LLVM_COV), "show",
+ "-format=html", "-summary-only", "-show-line-counts-or-regions",
+ "-show-instantiation-summary", "-instr-profile=" + test_profdata_file,
+ "-path-equivalence=\"" + COVERAGE_ROOT + "\",\"" +
+ get_android_root_or_die() + "\"", "-output-dir=" + test_working_dir
]
# We have to have one object file not as an argument otherwise we can't specify source files.
- test_cmd = os.path.join(os.path.join(get_native_test_root_or_die(), test_name), test_name)
+ test_cmd = os.path.join(
+ os.path.join(get_native_test_root_or_die(), test_name), test_name)
cmd.append(test_cmd)
# Filter out the specific files we want coverage for
@@ -276,10 +286,12 @@ def generate_coverage_json(test):
"-summary-only",
"-show-region-summary",
"-instr-profile=" + test_profdata_file,
- "-path-equivalence=\"" + COVERAGE_ROOT + "\",\"" + get_android_root_or_die() + "\"",
+ "-path-equivalence=\"" + COVERAGE_ROOT + "\",\"" +
+ get_android_root_or_die() + "\"",
]
- test_cmd = os.path.join(os.path.join(get_native_test_root_or_die(), test_name), test_name)
+ test_cmd = os.path.join(
+ os.path.join(get_native_test_root_or_die(), test_name), test_name)
cmd.append(test_cmd)
# Filter out the specific files we want coverage for
@@ -313,7 +325,8 @@ def list_tests():
def main():
- parser = argparse.ArgumentParser(description='Generate code coverage for enabled tests.')
+ parser = argparse.ArgumentParser(
+ description='Generate code coverage for enabled tests.')
parser.add_argument(
'-l',
'--list-tests',
@@ -355,11 +368,22 @@ def main():
action='store_true',
help='Write out summary results to json file in test directory.')
- logging.basicConfig(stream=sys.stderr, level=logging.DEBUG, format='%(levelname)s %(message)s')
- logging.addLevelName(logging.DEBUG, "[\033[1;34m%s\033[0m]" % logging.getLevelName(logging.DEBUG))
- logging.addLevelName(logging.INFO, "[\033[1;34m%s\033[0m]" % logging.getLevelName(logging.INFO))
- logging.addLevelName(logging.WARNING, "[\033[1;31m%s\033[0m]" % logging.getLevelName(logging.WARNING))
- logging.addLevelName(logging.ERROR, "[\033[1;31m%s\033[0m]" % logging.getLevelName(logging.ERROR))
+ logging.basicConfig(
+ stream=sys.stderr,
+ level=logging.DEBUG,
+ format='%(levelname)s %(message)s')
+ logging.addLevelName(
+ logging.DEBUG,
+ "[\033[1;34m%s\033[0m]" % logging.getLevelName(logging.DEBUG))
+ logging.addLevelName(
+ logging.INFO,
+ "[\033[1;34m%s\033[0m]" % logging.getLevelName(logging.INFO))
+ logging.addLevelName(
+ logging.WARNING,
+ "[\033[1;31m%s\033[0m]" % logging.getLevelName(logging.WARNING))
+ logging.addLevelName(
+ logging.ERROR,
+ "[\033[1;31m%s\033[0m]" % logging.getLevelName(logging.ERROR))
args = parser.parse_args()
logging.debug("Args: " + str(args))
@@ -389,7 +413,8 @@ def main():
# Error if a test was specified but doesn't exist.
if len(args.tests) != 0:
for test_name in args.tests:
- logging.error('\"' + test_name + '\" was not found in the list of available tests.')
+ logging.error('\"' + test_name +
+ '\" was not found in the list of available tests.')
sys.exit(1)
# Generate the info for the tests
diff --git a/test/headless/Android.bp b/test/headless/Android.bp
index 0aff030e7..fbfb2f46c 100644
--- a/test/headless/Android.bp
+++ b/test/headless/Android.bp
@@ -1,23 +1,12 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_test {
name: "bt_headless",
test_suites: ["device-tests"],
defaults: ["fluoride_defaults"],
srcs: [
- "connect/connect.cc",
"get_options.cc",
"headless.cc",
"main.cc",
"pairing/pairing.cc",
- "dumpsys/dumpsys.cc",
"sdp/sdp.cc",
"sdp/sdp_db.cc",
"nop/nop.cc",
@@ -26,7 +15,6 @@ cc_test {
],
include_dirs: [
"system/bt",
- "system/bt/gd",
"system/bt/stack/include",
],
whole_static_libs: [
@@ -46,25 +34,19 @@ cc_test {
"libbtdevice",
"libbte",
"libbtif",
- "libflatbuffers-cpp",
"libg722codec",
"libosi",
"libprotobuf-cpp-lite",
"libudrv-uipc",
"libz",
- "libbluetooth_rust_interop",
],
shared_libs: [
"android.hardware.bluetooth.a2dp@1.0",
"android.hardware.bluetooth.audio@2.0",
- "android.hardware.bluetooth.audio@2.1",
"android.hardware.bluetooth@1.0",
"android.hardware.bluetooth@1.1",
- "android.system.suspend.control-V1-ndk",
- "android.system.suspend@1.0",
"libaaudio",
"libbase",
- "libbinder_ndk",
"libcrypto",
"libcutils", // property_get_bool
"libfmq",
@@ -76,7 +58,4 @@ cc_test {
"libutils",
],
ldflags: ["-rdynamic"],
- sanitize: {
- cfi: false,
- },
}
diff --git a/test/headless/README.md b/test/headless/README.md
deleted file mode 100644
index 13b7f9236..000000000
--- a/test/headless/README.md
+++ /dev/null
@@ -1,24 +0,0 @@
-##
-## bluetooth headless
-##
-## A device-side executable that consists of a binary executable
-## driving the Android libbluetooth libraries.
-##
-
-Requirements:
- 1. Android installation,
- 2. Root access to adb connected Android device.
-
-Build: Source, lunch and build as typical Android target for selected device and architecture.
- cd $ANDROID_BUILD_TOP
- . build/envsetup.sh && lunch <target>
- make bt_headless
-
-Install: Push the binary to an executable area on target device.
- adb push out/target/product/<device..arch>/bt_headless/bt_headless /data/data/.
-
-Prepare: Ensure the system is queisced to prevent resource conflicts from the bluetooth process.
- adb shell stop
-
-Run: Script or directly execute the target file.
- adb shell /data/data/bt_headless --flags=INIT_logging_debug_enabled_for_all=true,INIT_gd_acl=true nop
diff --git a/test/headless/connect/connect.cc b/test/headless/connect/connect.cc
deleted file mode 100644
index a867e5e57..000000000
--- a/test/headless/connect/connect.cc
+++ /dev/null
@@ -1,134 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "bt_headless_mode"
-
-#include <inttypes.h>
-#include <chrono>
-#include <cstdint>
-#include <cstdio>
-#include <future>
-#include <map>
-#include <string>
-
-#include "base/logging.h" // LOG() stdout and android log
-#include "btif/include/stack_manager.h"
-#include "osi/include/log.h" // android log only
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/l2cap_acl_interface.h"
-#include "test/headless/connect/connect.h"
-#include "test/headless/get_options.h"
-#include "test/headless/headless.h"
-#include "test/headless/interface.h"
-#include "types/raw_address.h"
-
-const stack_manager_t* stack_manager_get_interface();
-extern bt_interface_t bluetoothInterface;
-
-void power_mode_callback(const RawAddress& p_bda, tBTM_PM_STATUS status,
- uint16_t value, tHCI_STATUS hci_status) {
- fprintf(stdout, "Got callback\n");
-};
-
-std::promise<acl_state_changed_params_t> acl_state_changed_promise;
-
-void callback_interface(interface_data_t data) {
- if (data.name == "acl_state_changed") {
- LOG(INFO) << "Received acl state changed";
- acl_state_changed_params_t p{
- .status = BT_STATUS_SUCCESS,
- .remote_bd_addr = nullptr,
- .state = BT_ACL_STATE_CONNECTED,
- };
- acl_state_changed_promise.set_value(p);
- return;
- }
- LOG(ERROR) << "Received unexpected interface callback";
-}
-
-namespace {
-
-int do_connect(unsigned int num_loops, const RawAddress& bd_addr,
- std::list<std::string> options) {
- int disconnect_wait_time{0};
-
- if (options.size() != 0) {
- std::string opt = options.front();
- options.pop_front();
- auto v = bluetooth::test::headless::GetOpt::Split(opt);
- if (v.size() == 2) {
- if (v[0] == "wait") disconnect_wait_time = std::stoi(v[1]);
- }
- }
- ASSERT_LOG(disconnect_wait_time >= 0, "Time cannot go backwards");
-
- headless_add_callback("acl_state_changed", callback_interface);
-
- acl_state_changed_promise = std::promise<acl_state_changed_params_t>();
- auto future = acl_state_changed_promise.get_future();
-
- fprintf(stdout, "Creating connection to:%s\n", bd_addr.ToString().c_str());
- LOG(INFO) << "Creating classic connection to " << bd_addr.ToString();
- acl_create_classic_connection(bd_addr, false, false);
-
- acl_state_changed_params_t result = future.get();
- fprintf(stdout, "Connected created to:%s result:%s[%u]\n",
- bd_addr.ToString().c_str(), bt_status_text(result.status).c_str(),
- result.status);
- acl_state_changed_promise = std::promise<acl_state_changed_params_t>();
- future = acl_state_changed_promise.get_future();
-
- uint64_t connect = std::chrono::duration_cast<std::chrono::milliseconds>(
- std::chrono::system_clock::now().time_since_epoch())
- .count();
-
- fprintf(stdout, "Just crushing stack\n");
- LOG(INFO) << "Just crushing stack";
- stack_manager_get_interface()->clean_up_stack();
-
- if (disconnect_wait_time == 0) {
- fprintf(stdout, "Waiting to disconnect from supervision timeout\n");
- result = future.get();
- uint64_t disconnect =
- std::chrono::duration_cast<std::chrono::milliseconds>(
- std::chrono::system_clock::now().time_since_epoch())
- .count();
-
- fprintf(stdout, "Disconnected after:%" PRId64 "ms from:%s result:%s[%u]\n",
- disconnect - connect, bd_addr.ToString().c_str(),
- bt_status_text(result.status).c_str(), result.status);
-
- headless_remove_callback("acl_state_changed", callback_interface);
- } else {
- fprintf(stdout, "Waiting %d seconds to just shutdown\n",
- disconnect_wait_time);
- sleep(disconnect_wait_time);
- bluetoothInterface.dump(1, nullptr);
- bluetoothInterface.cleanup();
- }
- return 0;
-}
-
-} // namespace
-
-int bluetooth::test::headless::Connect::Run() {
- return RunOnHeadlessStack<int>([this]() {
- return do_connect(options_.loop_, options_.device_.front(),
- options_.non_options_);
- });
-}
diff --git a/test/headless/connect/connect.h b/test/headless/connect/connect.h
deleted file mode 100644
index b7eeadd87..000000000
--- a/test/headless/connect/connect.h
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "test/headless/get_options.h"
-#include "test/headless/headless.h"
-
-namespace bluetooth {
-namespace test {
-namespace headless {
-
-class Connect : public HeadlessTest<int> {
- public:
- Connect(const bluetooth::test::headless::GetOpt& options)
- : HeadlessTest<int>(options) {}
- int Run() override;
-};
-
-} // namespace headless
-} // namespace test
-} // namespace bluetooth
diff --git a/test/headless/dumpsys/dumpsys.cc b/test/headless/dumpsys/dumpsys.cc
deleted file mode 100644
index baeeb3278..000000000
--- a/test/headless/dumpsys/dumpsys.cc
+++ /dev/null
@@ -1,39 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "bt_headless_sdp"
-
-#include <future>
-
-#include "base/logging.h" // LOG() stdout and android log
-#include "osi/include/log.h" // android log only
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/hci_error_code.h"
-#include "test/headless/dumpsys/dumpsys.h"
-#include "test/headless/get_options.h"
-#include "test/headless/headless.h"
-#include "types/raw_address.h"
-
-extern bt_interface_t bluetoothInterface;
-
-int bluetooth::test::headless::Dumpsys::Run() {
- return RunOnHeadlessStack<int>([this]() {
- fprintf(stdout, "Dumpsys loop:%lu \n", loop_);
- bluetoothInterface.dump(1, nullptr);
- return 0;
- });
-}
diff --git a/test/headless/dumpsys/dumpsys.h b/test/headless/dumpsys/dumpsys.h
deleted file mode 100644
index eb93aeb7e..000000000
--- a/test/headless/dumpsys/dumpsys.h
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include "test/headless/get_options.h"
-#include "test/headless/headless.h"
-
-namespace bluetooth {
-namespace test {
-namespace headless {
-
-class Dumpsys : public HeadlessTest<int> {
- public:
- Dumpsys(const bluetooth::test::headless::GetOpt& options)
- : HeadlessTest<int>(options) {}
- int Run() override;
-};
-
-} // namespace headless
-} // namespace test
-} // namespace bluetooth
diff --git a/test/headless/get_options.cc b/test/headless/get_options.cc
index 56ca1f939..f8d85760f 100644
--- a/test/headless/get_options.cc
+++ b/test/headless/get_options.cc
@@ -22,42 +22,28 @@
#include <unistd.h>
#include <list>
#include <string>
-#include "gd/os/log.h"
namespace {
+constexpr struct option long_options[] = {
+ {"device", required_argument, 0, 0}, {"loop", required_argument, 0, 0},
+ {"uuid", required_argument, 0, 0}, {"msleep", required_argument, 0, 0},
+ {"stderr", no_argument, 0, 0}, {0, 0, 0, 0}};
+
enum OptionType {
kOptionDevice = 0,
kOptionLoop = 1,
kOptionUuid = 2,
kOptionMsleep = 3,
kOptionStdErr = 4,
- kOptionFlags = 5,
- kOptionClear = 6,
};
-constexpr struct option long_options[] = {
- {"device", required_argument, 0, 0}, // kOptionDevice
- {"loop", required_argument, 0, 0}, // kOptionLoop/
- {"uuid", required_argument, 0, 0}, // kOptionUuid
- {"msleep", required_argument, 0, 0}, // kOptionMsleep
- {"stderr", no_argument, 0, 0}, // kOptionStdErr
- {"flags", required_argument, 0, 0}, // kOptionFlags
- {"clear", no_argument, 0, 0}, // kOptionDevice
- {0, 0, 0, 0}};
-
-const char* kShortArgs = "cd:l:u:";
-
} // namespace
void bluetooth::test::headless::GetOpt::Usage() const {
fprintf(stdout, "%s: Usage:\n", name_);
- fprintf(stdout, "%s -c Clear logcat logs\n", name_);
fprintf(stdout,
"%s --device=<device,> Comma separated list of remote devices\n",
name_);
- fprintf(stdout,
- "%s --flags=<flags,> Comma separated list of gd init flags\n",
- name_);
fprintf(stdout, "%s --uuid=<uuid,> Comma separated list of uuids\n",
name_);
fprintf(stdout, "%s --loop=<loop> Number of loops\n", name_);
@@ -82,17 +68,6 @@ void bluetooth::test::headless::GetOpt::ParseValue(
if (pp != p) string_list.push_back(std::string(pp));
}
-std::vector<std::string> bluetooth::test::headless::GetOpt::Split(
- std::string s) {
- std::stringstream ss(s);
- std::vector<std::string> values;
- std::string item;
- while (std::getline(ss, item, '=')) {
- values.push_back(item);
- }
- return values;
-}
-
void bluetooth::test::headless::GetOpt::ProcessOption(int option_index,
char* optarg) {
std::list<std::string> string_list;
@@ -128,16 +103,6 @@ void bluetooth::test::headless::GetOpt::ProcessOption(int option_index,
case kOptionStdErr:
close_stderr_ = false;
break;
- case kOptionFlags:
- if (!optarg) return;
- ParseValue(optarg, string_list);
- for (auto& flag : string_list) {
- init_flags_.push_back(flag);
- }
- break;
- case kOptionClear:
- clear_logcat_ = true;
- break;
default:
fflush(nullptr);
valid_ = false;
@@ -146,28 +111,11 @@ void bluetooth::test::headless::GetOpt::ProcessOption(int option_index,
}
}
-void bluetooth::test::headless::GetOpt::ParseStackInitFlags() {
- if (init_flags_.size() == 0) return;
-
- ASSERT(stack_init_flags_ == nullptr);
-
- unsigned idx = 0;
- stack_init_flags_ = (const char**)calloc(sizeof(char*), init_flags_.size());
- for (const std::string& flag : init_flags_)
- stack_init_flags_[idx++] = flag.c_str();
- stack_init_flags_[idx] = nullptr;
-}
-
-const char** bluetooth::test::headless::GetOpt::StackInitFlags() const {
- return stack_init_flags_;
-}
-
bluetooth::test::headless::GetOpt::GetOpt(int argc, char** argv)
: name_(argv[0]) {
while (1) {
int option_index = 0;
- int c =
- getopt_long_only(argc, argv, kShortArgs, long_options, &option_index);
+ int c = getopt_long_only(argc, argv, "d:l:u:", long_options, &option_index);
if (c == -1) break;
switch (c) {
@@ -186,10 +134,6 @@ bluetooth::test::headless::GetOpt::GetOpt(int argc, char** argv)
while (optind < argc) {
non_options_.push_back(argv[optind++]);
}
-
- ParseStackInitFlags();
-
fflush(nullptr);
}
-bluetooth::test::headless::GetOpt::~GetOpt() { free(stack_init_flags_); }
diff --git a/test/headless/get_options.h b/test/headless/get_options.h
index 321ac82bb..04a502564 100644
--- a/test/headless/get_options.h
+++ b/test/headless/get_options.h
@@ -18,7 +18,6 @@
#include <cstddef>
#include <list>
-#include <string>
#include "types/bluetooth/uuid.h"
#include "types/raw_address.h"
@@ -29,7 +28,7 @@ namespace headless {
class GetOpt {
public:
GetOpt(int argc, char** arv);
- virtual ~GetOpt();
+ virtual ~GetOpt() = default;
virtual void Usage() const;
virtual bool IsValid() const { return valid_; };
@@ -40,27 +39,19 @@ class GetOpt {
return test;
}
- const char** StackInitFlags() const;
-
std::list<RawAddress> device_;
- std::list<std::string> init_flags_;
std::list<bluetooth::Uuid> uuid_;
unsigned long loop_{1};
unsigned long msec_{0};
bool close_stderr_{true};
- bool clear_logcat_{false};
mutable std::list<std::string> non_options_;
- static std::vector<std::string> Split(std::string);
-
private:
void ParseValue(char* optarg, std::list<std::string>& my_list);
void ProcessOption(int option_index, char* optarg);
- void ParseStackInitFlags();
const char* name_{nullptr};
- const char** stack_init_flags_{nullptr};
bool valid_{true};
};
diff --git a/test/headless/headless.cc b/test/headless/headless.cc
index a3b54410a..9083e9c42 100644
--- a/test/headless/headless.cc
+++ b/test/headless/headless.cc
@@ -17,44 +17,17 @@
#define LOG_TAG "bt_headless"
#include <dlfcn.h> // dlopen
-#include <algorithm>
-#include <iostream>
-#include <map>
#include "base/logging.h" // LOG() stdout and android log
#include "include/hardware/bluetooth.h"
#include "osi/include/log.h" // android log only
#include "test/headless/get_options.h"
#include "test/headless/headless.h"
-#include "test/headless/interface.h"
extern bt_interface_t bluetoothInterface;
using namespace bluetooth::test::headless;
-std::map<const std::string, std::list<callback_function_t>>
- interface_api_callback_map_;
-
-void headless_add_callback(const std::string interface_name,
- callback_function_t function) {
- if (interface_api_callback_map_.find(interface_name) ==
- interface_api_callback_map_.end()) {
- interface_api_callback_map_.emplace(interface_name,
- std::list<callback_function_t>());
- }
- interface_api_callback_map_[interface_name].push_back(function);
-}
-
-void headless_remove_callback(const std::string interface_name,
- callback_function_t function) {
- if (interface_api_callback_map_.find(interface_name) ==
- interface_api_callback_map_.end()) {
- ASSERT_LOG(false, "No callbacks registered for interface:%s",
- interface_name.c_str());
- }
- interface_api_callback_map_[interface_name].remove(function);
-}
-
namespace {
std::mutex adapter_state_mutex_;
std::condition_variable adapter_state_cv_;
@@ -67,79 +40,59 @@ void adapter_state_changed(bt_state_t state) {
}
void adapter_properties(bt_status_t status, int num_properties,
bt_property_t* properties) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
}
void remote_device_properties(bt_status_t status, RawAddress* bd_addr,
int num_properties, bt_property_t* properties) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
}
void device_found(int num_properties, bt_property_t* properties) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
}
void discovery_state_changed(bt_discovery_state_t state) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
}
/** Bluetooth Legacy PinKey Request callback */
void pin_request(RawAddress* remote_bd_addr, bt_bdname_t* bd_name, uint32_t cod,
bool min_16_digit) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
}
void ssp_request(RawAddress* remote_bd_addr, bt_bdname_t* bd_name, uint32_t cod,
bt_ssp_variant_t pairing_variant, uint32_t pass_key) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
}
/** Bluetooth Bond state changed callback */
/* Invoked in response to create_bond, cancel_bond or remove_bond */
void bond_state_changed(bt_status_t status, RawAddress* remote_bd_addr,
bt_bond_state_t state) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
}
/** Bluetooth ACL connection state changed callback */
void acl_state_changed(bt_status_t status, RawAddress* remote_bd_addr,
- bt_acl_state_t state, bt_hci_error_code_t hci_reason) {
- auto callback_list = interface_api_callback_map_.at(__func__);
- for (auto callback : callback_list) {
- interface_data_t params{
- .name = __func__,
- .params.acl_state_changed.status = status,
- .params.acl_state_changed.remote_bd_addr = remote_bd_addr,
- .params.acl_state_changed.state = state,
- .params.acl_state_changed.hci_reason = hci_reason,
- };
- (callback)(params);
- }
- LOG_INFO("%s status:%s device:%s state:%s", __func__,
- bt_status_text(status).c_str(), remote_bd_addr->ToString().c_str(),
- (state) ? "disconnected" : "connected");
-}
-
-/** Bluetooth Link Quality Report callback */
-void link_quality_report(uint64_t timestamp, int report_id, int rssi, int snr,
- int retransmission_count, int packets_not_receive_count,
- int negative_acknowledgement_count) {
- LOG_INFO("%s", __func__);
-}
-
-void thread_event(bt_cb_thread_evt evt) { LOG_INFO("%s", __func__); }
+ bt_acl_state_t state) {
+ LOG_INFO(LOG_TAG, "%s", __func__);
+}
+
+void thread_event(bt_cb_thread_evt evt) { LOG_INFO(LOG_TAG, "%s", __func__); }
void dut_mode_recv(uint16_t opcode, uint8_t* buf, uint8_t len) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
}
void le_test_mode(bt_status_t status, uint16_t num_packets) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
}
void energy_info(bt_activity_energy_info* energy_info,
bt_uid_traffic_t* uid_data) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
}
bt_callbacks_t bt_callbacks{
@@ -158,23 +111,22 @@ bt_callbacks_t bt_callbacks{
.dut_mode_recv_cb = dut_mode_recv,
.le_test_mode_cb = le_test_mode,
.energy_info_cb = energy_info,
- .link_quality_report_cb = link_quality_report,
};
// HAL HARDWARE CALLBACKS
// OS CALLOUTS
bool set_wake_alarm_co(uint64_t delay_millis, bool should_wake, alarm_cb cb,
void* data) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
return true;
}
int acquire_wake_lock_co(const char* lock_name) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
return 1;
}
int release_wake_lock_co(const char* lock_name) {
- LOG_INFO("%s", __func__);
+ LOG_INFO(LOG_TAG, "%s", __func__);
return 0;
}
@@ -189,14 +141,7 @@ bt_os_callouts_t bt_os_callouts{
void HeadlessStack::SetUp() {
LOG(INFO) << __func__ << " Entry";
- const bool start_restricted = false;
- const bool is_common_criteria_mode = false;
- const int config_compare_result = 0;
- const bool is_atv = false;
- int status = bluetoothInterface.init(
- &bt_callbacks, start_restricted, is_common_criteria_mode,
- config_compare_result, StackInitFlags(), is_atv);
-
+ int status = bluetoothInterface.init(&bt_callbacks, false, false, 0, false);
(status == BT_STATUS_SUCCESS)
? LOG(INFO) << __func__ << " Initialized bluetooth callbacks"
: LOG(FATAL) << "Failed to initialize Bluetooth stack";
@@ -207,15 +152,15 @@ void HeadlessStack::SetUp() {
: LOG(ERROR) << "Failed to set up Bluetooth OS callouts";
bluetoothInterface.enable();
- LOG_INFO("%s HeadlessStack stack has enabled", __func__);
+ LOG_INFO(LOG_TAG, "%s HeadlessStack stack has enabled", __func__);
std::unique_lock<std::mutex> lck(adapter_state_mutex_);
while (bt_state_ != BT_STATE_ON) adapter_state_cv_.wait(lck);
- LOG_INFO("%s HeadlessStack stack is operational", __func__);
+ LOG_INFO(LOG_TAG, "%s HeadlessStack stack is operational", __func__);
}
void HeadlessStack::TearDown() {
- LOG_INFO("Stack has disabled");
+ LOG_INFO(LOG_TAG, "Stack has disabled");
int status = bluetoothInterface.disable();
LOG(INFO) << __func__ << " Interface has been disabled status:" << status;
@@ -225,5 +170,5 @@ void HeadlessStack::TearDown() {
std::unique_lock<std::mutex> lck(adapter_state_mutex_);
while (bt_state_ != BT_STATE_OFF) adapter_state_cv_.wait(lck);
- LOG_INFO("%s HeadlessStack stack has exited", __func__);
+ LOG_INFO(LOG_TAG, "%s HeadlessStack stack has exited", __func__);
}
diff --git a/test/headless/headless.h b/test/headless/headless.h
index 1931b7096..551f60f04 100644
--- a/test/headless/headless.h
+++ b/test/headless/headless.h
@@ -21,11 +21,8 @@
#include <unistd.h>
#include "base/logging.h" // LOG() stdout and android log
-#include "include/hardware/bluetooth.h"
#include "test/headless/get_options.h"
-extern bt_interface_t bluetoothInterface;
-
namespace bluetooth {
namespace test {
namespace headless {
@@ -35,33 +32,22 @@ namespace {
template <typename T>
using ExecutionUnit = std::function<T()>;
-constexpr char kHeadlessInitialSentinel[] =
- " INITIAL HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS "
- "HEADLESS";
constexpr char kHeadlessStartSentinel[] =
" START HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS "
"HEADLESS";
constexpr char kHeadlessStopSentinel[] =
" STOP HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS "
"HEADLESS";
-constexpr char kHeadlessFinalSentinel[] =
- " FINAL HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS HEADLESS "
- "HEADLESS";
} // namespace
class HeadlessStack {
protected:
- HeadlessStack(const char** stack_init_flags)
- : stack_init_flags_(stack_init_flags) {}
+ HeadlessStack() = default;
virtual ~HeadlessStack() = default;
void SetUp();
void TearDown();
- const char** StackInitFlags() const { return stack_init_flags_; }
-
- private:
- const char** stack_init_flags_;
};
class HeadlessRun : public HeadlessStack {
@@ -70,11 +56,10 @@ class HeadlessRun : public HeadlessStack {
unsigned long loop_{0};
HeadlessRun(const bluetooth::test::headless::GetOpt& options)
- : HeadlessStack(options.StackInitFlags()), options_(options) {}
+ : options_(options) {}
template <typename T>
T RunOnHeadlessStack(ExecutionUnit<T> func) {
- LOG(INFO) << kHeadlessInitialSentinel;
SetUp();
LOG(INFO) << kHeadlessStartSentinel;
@@ -98,7 +83,6 @@ class HeadlessRun : public HeadlessStack {
LOG(INFO) << kHeadlessStopSentinel;
TearDown();
- LOG(INFO) << kHeadlessFinalSentinel;
return rc;
}
virtual ~HeadlessRun() = default;
diff --git a/test/headless/interface.h b/test/headless/interface.h
deleted file mode 100644
index d79016a7f..000000000
--- a/test/headless/interface.h
+++ /dev/null
@@ -1,36 +0,0 @@
-
-
-#pragma once
-
-#include <list>
-#include <map>
-#include <string>
-
-#include "include/hardware/bluetooth.h"
-
-using acl_state_changed_params_t = struct {
- bt_status_t status;
- RawAddress* remote_bd_addr;
- bt_acl_state_t state;
- bt_hci_error_code_t hci_reason;
-};
-
-using callback_params_t = union {
- acl_state_changed_params_t acl_state_changed;
-};
-
-using interface_data_t = struct {
- std::string name;
- callback_params_t params;
-};
-
-using callback_function_t = void (*)(interface_data_t);
-using interface_callback_t = struct {
- std::string name;
- callback_function_t function;
-};
-
-void headless_add_callback(const std::string interface_name,
- callback_function_t function);
-void headless_remove_callback(const std::string interface_name,
- callback_function_t function);
diff --git a/test/headless/main.cc b/test/headless/main.cc
index 19dd0b652..487e96c49 100644
--- a/test/headless/main.cc
+++ b/test/headless/main.cc
@@ -16,16 +16,10 @@
#define LOG_TAG "bt_headless"
-#include <iostream>
#include <unordered_map>
-#include <sys/wait.h>
-#include <unistd.h>
-
#include "base/logging.h" // LOG() stdout and android log
#include "osi/include/log.h" // android log only
-#include "test/headless/connect/connect.h"
-#include "test/headless/dumpsys/dumpsys.h"
#include "test/headless/get_options.h"
#include "test/headless/headless.h"
#include "test/headless/nop/nop.h"
@@ -37,35 +31,11 @@ using namespace bluetooth::test::headless;
namespace {
-void clear_logcat() {
- int pid;
- if ((pid = fork())) {
- // parent process
- int status;
- waitpid(pid, &status, 0); // wait for the child to exit
- ASSERT_LOG(WIFEXITED(status), "Unable to clear logcat");
- } else {
- // child process
- const char exec[] = "/system/bin/logcat";
- const char arg0[] = "-c";
-
- execl(exec, exec, arg0, NULL);
-
- ASSERT_LOG(false, "Should not return from exec process");
- }
-}
-
class Main : public HeadlessTest<int> {
public:
Main(const bluetooth::test::headless::GetOpt& options)
: HeadlessTest<int>(options) {
test_nodes_.emplace(
- "dumpsys",
- std::make_unique<bluetooth::test::headless::Dumpsys>(options));
- test_nodes_.emplace(
- "connect",
- std::make_unique<bluetooth::test::headless::Connect>(options));
- test_nodes_.emplace(
"nop", std::make_unique<bluetooth::test::headless::Nop>(options));
test_nodes_.emplace(
"pairing",
@@ -80,11 +50,6 @@ class Main : public HeadlessTest<int> {
if (options_.close_stderr_) {
fclose(stderr);
}
-
- if (options_.clear_logcat_) {
- clear_logcat();
- }
-
return HeadlessTest<int>::Run();
}
};
diff --git a/test/headless/pairing/pairing.cc b/test/headless/pairing/pairing.cc
index ed5c490d2..7785ea4c1 100644
--- a/test/headless/pairing/pairing.cc
+++ b/test/headless/pairing/pairing.cc
@@ -41,7 +41,14 @@ int bluetooth::test::headless::Pairing::Run() {
RawAddress raw_address = options_.device_.front();
return RunOnHeadlessStack<int>([raw_address]() {
- btif_dm_create_bond(raw_address, BT_TRANSPORT_BR_EDR);
- return BT_STATUS_SUCCESS;
+ bt_status_t status = btif_dm_create_bond(&raw_address, BT_TRANSPORT_BR_EDR);
+ switch (status) {
+ case BT_STATUS_SUCCESS:
+ break;
+ default:
+ fprintf(stdout, "Failed to create bond status:%d", status);
+ break;
+ }
+ return status;
});
}
diff --git a/test/headless/sdp/sdp.cc b/test/headless/sdp/sdp.cc
index ea7efe43a..9e20340ea 100644
--- a/test/headless/sdp/sdp.cc
+++ b/test/headless/sdp/sdp.cc
@@ -29,8 +29,7 @@
using namespace bluetooth::test::headless;
-static void bta_jv_start_discovery_callback(tSDP_STATUS result,
- void* user_data) {
+static void bta_jv_start_discovery_callback(uint16_t result, void* user_data) {
auto promise = static_cast<std::promise<uint16_t>*>(user_data);
promise->set_value(result);
}
diff --git a/test/mock/mock_a2dp_api.cc b/test/mock/mock_a2dp_api.cc
deleted file mode 100644
index 5ca56717a..000000000
--- a/test/mock/mock_a2dp_api.cc
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:9
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "a2dp_api.h"
-#include "a2dp_int.h"
-#include "avdt_api.h"
-#include "bt_common.h"
-#include "bt_target.h"
-#include "osi/include/log.h"
-#include "sdpdefs.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tA2DP_STATUS A2DP_AddRecord(uint16_t service_uuid, char* p_service_name,
- char* p_provider_name, uint16_t features,
- uint32_t sdp_handle) {
- mock_function_count_map[__func__]++;
- return A2DP_SUCCESS;
-}
-tA2DP_STATUS A2DP_FindService(uint16_t service_uuid, const RawAddress& bd_addr,
- tA2DP_SDP_DB_PARAMS* p_db,
- tA2DP_FIND_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return A2DP_SUCCESS;
-}
-uint16_t A2DP_GetAvdtpVersion() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t A2DP_BitsSet(uint64_t num) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t A2DP_SetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void A2DP_Init(void) { mock_function_count_map[__func__]++; }
-void a2dp_set_avdt_sdp_ver(uint16_t avdt_sdp_ver) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_a2dp_codec_config.cc b/test/mock/mock_a2dp_codec_config.cc
deleted file mode 100644
index 8d0132826..000000000
--- a/test/mock/mock_a2dp_codec_config.cc
+++ /dev/null
@@ -1,351 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:67
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <inttypes.h>
-#include "a2dp_aac.h"
-#include "a2dp_codec_api.h"
-#include "a2dp_sbc.h"
-#include "a2dp_vendor.h"
-#include "bta/av/bta_av_int.h"
-#include "osi/include/log.h"
-#include "osi/include/properties.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-A2dpCodecConfig* A2dpCodecConfig::createCodec(
- btav_a2dp_codec_index_t codec_index,
- btav_a2dp_codec_priority_t codec_priority) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-A2dpCodecConfig* A2dpCodecs::findSinkCodecConfig(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-A2dpCodecConfig* A2dpCodecs::findSourceCodecConfig(
- const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-A2dpCodecConfig::A2dpCodecConfig(btav_a2dp_codec_index_t codec_index,
- const std::string& name,
- btav_a2dp_codec_priority_t codec_priority)
- : codec_index_(codec_index),
- name_(name),
- default_codec_priority_(codec_priority) {
- mock_function_count_map[__func__]++;
-}
-A2dpCodecConfig::~A2dpCodecConfig() { mock_function_count_map[__func__]++; }
-A2dpCodecs::A2dpCodecs(
- const std::vector<btav_a2dp_codec_config_t>& codec_priorities)
- : current_codec_config_(nullptr) {
- mock_function_count_map[__func__]++;
-}
-A2dpCodecs::~A2dpCodecs() { mock_function_count_map[__func__]++; }
-bool A2DP_AdjustCodec(uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_BuildCodecHeader(const uint8_t* p_codec_info, BT_HDR* p_buf,
- uint16_t frames_per_packet) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_CodecEquals(const uint8_t* p_codec_info_a,
- const uint8_t* p_codec_info_b) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_CodecTypeEquals(const uint8_t* p_codec_info_a,
- const uint8_t* p_codec_info_b) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_GetPacketTimestamp(const uint8_t* p_codec_info, const uint8_t* p_data,
- uint32_t* p_timestamp) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_InitCodecConfig(btav_a2dp_codec_index_t codec_index,
- AvdtpSepConfig* p_cfg) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsPeerSinkCodecValid(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsPeerSourceCodecSupported(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsPeerSourceCodecValid(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsSinkCodecSupported(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsSinkCodecValid(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsSourceCodecValid(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_UsesRtpHeader(bool content_protection_enabled,
- const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::codecConfigIsValid(
- const btav_a2dp_codec_config_t& codec_config) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::copyOutOtaCodecConfig(uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::getCodecSpecificConfig(tBT_A2DP_OFFLOAD* p_a2dp_offload) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::isCodecConfigEmpty(
- const btav_a2dp_codec_config_t& codec_config) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::isValid() const {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::setCodecUserConfig(
- const btav_a2dp_codec_config_t& codec_user_config,
- const btav_a2dp_codec_config_t& codec_audio_config,
- const tA2DP_ENCODER_INIT_PEER_PARAMS* p_peer_params,
- const uint8_t* p_peer_codec_info, bool is_capability,
- uint8_t* p_result_codec_config, bool* p_restart_input,
- bool* p_restart_output, bool* p_config_updated) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::getCodecConfigAndCapabilities(
- btav_a2dp_codec_config_t* p_codec_config,
- std::vector<btav_a2dp_codec_config_t>* p_codecs_local_capabilities,
- std::vector<btav_a2dp_codec_config_t>* p_codecs_selectable_capabilities) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::init() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::isSupportedCodec(btav_a2dp_codec_index_t codec_index) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setCodecAudioConfig(
- const btav_a2dp_codec_config_t& codec_audio_config,
- const tA2DP_ENCODER_INIT_PEER_PARAMS* p_peer_params,
- const uint8_t* p_peer_sink_capabilities, uint8_t* p_result_codec_config,
- bool* p_restart_output, bool* p_config_updated) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setCodecConfig(const uint8_t* p_peer_codec_info,
- bool is_capability,
- uint8_t* p_result_codec_config,
- bool select_current_codec) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setCodecOtaConfig(
- const uint8_t* p_ota_codec_config,
- const tA2DP_ENCODER_INIT_PEER_PARAMS* p_peer_params,
- uint8_t* p_result_codec_config, bool* p_restart_input,
- bool* p_restart_output, bool* p_config_updated) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setCodecUserConfig(
- const btav_a2dp_codec_config_t& codec_user_config,
- const tA2DP_ENCODER_INIT_PEER_PARAMS* p_peer_params,
- const uint8_t* p_peer_sink_capabilities, uint8_t* p_result_codec_config,
- bool* p_restart_input, bool* p_restart_output, bool* p_config_updated) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setPeerSinkCodecCapabilities(
- const uint8_t* p_peer_codec_capabilities) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setPeerSourceCodecCapabilities(
- const uint8_t* p_peer_codec_capabilities) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setSinkCodecConfig(const uint8_t* p_peer_codec_info,
- bool is_capability,
- uint8_t* p_result_codec_config,
- bool select_current_codec) {
- mock_function_count_map[__func__]++;
- return false;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecAudioConfig() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecCapability() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecConfig() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecLocalCapability() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecSelectableCapability() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecUserConfig() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_index_t A2DP_SinkCodecIndex(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return BTAV_A2DP_CODEC_INDEX_MAX;
-}
-btav_a2dp_codec_index_t A2DP_SourceCodecIndex(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return BTAV_A2DP_CODEC_INDEX_MAX;
-}
-const char* A2DP_CodecIndexStr(btav_a2dp_codec_index_t codec_index) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const char* A2DP_CodecName(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const tA2DP_DECODER_INTERFACE* A2DP_GetDecoderInterface(
- const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const tA2DP_ENCODER_INTERFACE* A2DP_GetEncoderInterface(
- const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-int A2DP_GetSinkTrackChannelType(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int A2DP_GetTrackBitsPerSample(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int A2DP_GetTrackChannelCount(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int A2DP_GetTrackSampleRate(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int A2dpCodecConfig::getTrackBitRate() const {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::string A2DP_CodecInfoString(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::string A2dpCodecConfig::codecBitsPerSample2Str(
- btav_a2dp_codec_bits_per_sample_t codec_bits_per_sample) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::string A2dpCodecConfig::codecChannelMode2Str(
- btav_a2dp_codec_channel_mode_t codec_channel_mode) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::string A2dpCodecConfig::codecConfig2Str(
- const btav_a2dp_codec_config_t& codec_config) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::string A2dpCodecConfig::codecSampleRate2Str(
- btav_a2dp_codec_sample_rate_t codec_sample_rate) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tA2DP_CODEC_TYPE A2DP_GetCodecType(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t A2DP_GetMediaType(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t A2dpCodecConfig::getAudioBitsPerSample() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void A2DP_InitDefaultCodec(uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
-}
-void A2dpCodecConfig::debug_codec_dump(int fd) {
- mock_function_count_map[__func__]++;
-}
-void A2dpCodecConfig::setCodecPriority(
- btav_a2dp_codec_priority_t codec_priority) {
- mock_function_count_map[__func__]++;
-}
-void A2dpCodecConfig::setDefaultCodecPriority() {
- mock_function_count_map[__func__]++;
-}
-void A2dpCodecs::debug_codec_dump(int fd) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_activity_attribution.cc b/test/mock/mock_activity_attribution.cc
deleted file mode 100644
index 68797968d..000000000
--- a/test/mock/mock_activity_attribution.cc
+++ /dev/null
@@ -1,35 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "gd/module.h"
-
-#include "btif/include/btif_activity_attribution.h"
-#include "main/shim/activity_attribution.h"
-#include "main/shim/shim.h"
-
-ActivityAttributionInterface*
-bluetooth::activity_attribution::get_activity_attribution_instance() {
- return nullptr;
-}
-
-ActivityAttributionInterface*
-bluetooth::shim::get_activity_attribution_instance() {
- return nullptr;
-}
-
-const bluetooth::ModuleFactory
- bluetooth::activity_attribution::ActivityAttribution::Factory =
- bluetooth::ModuleFactory([]() { return nullptr; });
diff --git a/test/mock/mock_android_hardware_audio.cc b/test/mock/mock_android_hardware_audio.cc
deleted file mode 100644
index 01910deee..000000000
--- a/test/mock/mock_android_hardware_audio.cc
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <cstdint>
-
-#include <android/hardware/bluetooth/a2dp/1.0/IBluetoothAudioHost.h>
-
-namespace android {
-namespace hardware {
-namespace bluetooth {
-
-namespace a2dp {
-namespace V1_0 {
-class BluetoothAudioHost : public IBluetoothAudioHost {
- ::android::hardware::Return<void> setHALInstrumentation() { return Void(); }
- ::android::hardware::Return<bool> linkToDeath(
- android::sp<android::hardware::hidl_death_recipient> const&, uint64_t) {
- return false;
- }
- ::android::hardware::Return<void> ping() { return Void(); }
- ::android::hardware::Return<void> getDebugInfo(
- std::__1::function<void(android::hidl::base::V1_0::DebugInfo const&)>) {
- return Void();
- }
- ::android::hardware::Return<void> notifySyspropsChanged() { return Void(); }
- ::android::hardware::Return<bool> unlinkToDeath(
- android::sp<android::hardware::hidl_death_recipient> const&) {
- return false;
- }
-};
-
-} // namespace V1_0
-} // namespace a2dp
-
-namespace audio {
-
-namespace V2_0 {
-
-class AudioConfiguration {
- AudioConfiguration() {}
-};
-
-} // namespace V2_0
-
-} // namespace audio
-} // namespace bluetooth
-} // namespace hardware
-} // namespace android
diff --git a/test/mock/mock_bta_ag_api.cc b/test/mock/mock_bta_ag_api.cc
deleted file mode 100644
index bc716b71a..000000000
--- a/test/mock/mock_bta_ag_api.cc
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:14
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/location.h>
-#include <cstdint>
-#include <cstring>
-#include <vector>
-#include "bta/ag/bta_ag_int.h"
-#include "bta/include/bta_ag_api.h"
-#include "stack/include/btu.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tBTA_STATUS BTA_AgEnable(tBTA_AG_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return BTA_SUCCESS;
-}
-void BTA_AgAudioClose(uint16_t handle) { mock_function_count_map[__func__]++; }
-void BTA_AgAudioOpen(uint16_t handle) { mock_function_count_map[__func__]++; }
-void BTA_AgClose(uint16_t handle) { mock_function_count_map[__func__]++; }
-void BTA_AgDeregister(uint16_t handle) { mock_function_count_map[__func__]++; }
-void BTA_AgDisable() { mock_function_count_map[__func__]++; }
-void BTA_AgOpen(uint16_t handle, const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AgRegister(tBTA_SERVICE_MASK services, tBTA_AG_FEAT features,
- const std::vector<std::string>& service_names,
- uint8_t app_id) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AgResult(uint16_t handle, tBTA_AG_RES result,
- const tBTA_AG_RES_DATA& data) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AgSetActiveDevice(const RawAddress& active_device_addr) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AgSetCodec(uint16_t handle, tBTA_AG_PEER_CODEC codec) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AgSetScoAllowed(bool value) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_bta_ar.cc b/test/mock/mock_bta_ar.cc
deleted file mode 100644
index 1b9932c36..000000000
--- a/test/mock/mock_bta_ar.cc
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:8
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "bta/ar/bta_ar_int.h"
-#include "bta/sys/bta_sys.h"
-#include "stack/include/avct_api.h"
-#include "stack/include/avrc_api.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void bta_ar_avdt_conn(tBTA_SYS_ID sys_id, const RawAddress& bd_addr,
- uint8_t scb_index) {
- mock_function_count_map[__func__]++;
-}
-void bta_ar_dereg_avct() { mock_function_count_map[__func__]++; }
-void bta_ar_dereg_avdt() { mock_function_count_map[__func__]++; }
-void bta_ar_dereg_avrc(uint16_t service_uuid) {
- mock_function_count_map[__func__]++;
-}
-void bta_ar_init(void) { mock_function_count_map[__func__]++; }
-void bta_ar_reg_avct() { mock_function_count_map[__func__]++; }
-void bta_ar_reg_avdt(AvdtpRcb* p_reg, tAVDT_CTRL_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_ar_reg_avrc(uint16_t service_uuid, const char* service_name,
- const char* provider_name, uint16_t categories,
- bool browse_supported, uint16_t profile_version) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_av_api.cc b/test/mock/mock_bta_av_api.cc
deleted file mode 100644
index 33f03b221..000000000
--- a/test/mock/mock_bta_av_api.cc
+++ /dev/null
@@ -1,105 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:23
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "bt_target.h"
-#include "bta/av/bta_av_int.h"
-#include "osi/include/allocator.h"
-#include "osi/include/compat.h"
-#include "osi/include/log.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void BTA_AvEnable(tBTA_AV_FEAT features, tBTA_AV_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvClose(tBTA_AV_HNDL handle) { mock_function_count_map[__func__]++; }
-void BTA_AvCloseRc(uint8_t rc_handle) { mock_function_count_map[__func__]++; }
-void BTA_AvDeregister(tBTA_AV_HNDL hndl) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvDisable(void) { mock_function_count_map[__func__]++; }
-void BTA_AvDisconnect(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvMetaCmd(uint8_t rc_handle, uint8_t label, tBTA_AV_CMD cmd_code,
- BT_HDR* p_pkt) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvMetaRsp(uint8_t rc_handle, uint8_t label, tBTA_AV_CODE rsp_code,
- BT_HDR* p_pkt) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvOffloadStart(tBTA_AV_HNDL hndl) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvOffloadStartRsp(tBTA_AV_HNDL hndl, tBTA_AV_STATUS status) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvOpen(const RawAddress& bd_addr, tBTA_AV_HNDL handle, bool use_rc,
- uint16_t uuid) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvOpenRc(tBTA_AV_HNDL handle) { mock_function_count_map[__func__]++; }
-void BTA_AvProtectReq(tBTA_AV_HNDL hndl, uint8_t* p_data, uint16_t len) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvProtectRsp(tBTA_AV_HNDL hndl, uint8_t error_code, uint8_t* p_data,
- uint16_t len) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvReconfig(tBTA_AV_HNDL hndl, bool suspend, uint8_t sep_info_idx,
- uint8_t* p_codec_info, uint8_t num_protect,
- const uint8_t* p_protect_info) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvRegister(tBTA_AV_CHNL chnl, const char* p_service_name,
- uint8_t app_id, tBTA_AV_SINK_DATA_CBACK* p_sink_data_cback,
- uint16_t service_uuid) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvRemoteCmd(uint8_t rc_handle, uint8_t label, tBTA_AV_RC rc_id,
- tBTA_AV_STATE key_state) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvRemoteVendorUniqueCmd(uint8_t rc_handle, uint8_t label,
- tBTA_AV_STATE key_state, uint8_t* p_msg,
- uint8_t buf_len) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvStart(tBTA_AV_HNDL handle) { mock_function_count_map[__func__]++; }
-void BTA_AvStop(tBTA_AV_HNDL handle, bool suspend) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvVendorCmd(uint8_t rc_handle, uint8_t label, tBTA_AV_CODE cmd_code,
- uint8_t* p_data, uint16_t len) {
- mock_function_count_map[__func__]++;
-}
-void BTA_AvVendorRsp(uint8_t rc_handle, uint8_t label, tBTA_AV_CODE rsp_code,
- uint8_t* p_data, uint16_t len, uint32_t company_id) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_av_ci.cc b/test/mock/mock_bta_av_ci.cc
deleted file mode 100644
index 2c8022479..000000000
--- a/test/mock/mock_bta_av_ci.cc
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "bta/av/bta_av_int.h"
-#include "osi/include/allocator.h"
-#include "osi/include/log.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void bta_av_ci_setconfig(tBTA_AV_HNDL bta_av_handle, uint8_t err_code,
- uint8_t category, uint8_t num_seid, uint8_t* p_seid,
- bool recfg_needed, uint8_t avdt_handle) {
- mock_function_count_map[__func__]++;
-}
-void bta_av_ci_src_data_ready(tBTA_AV_CHNL chnl) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_av_main.cc b/test/mock/mock_bta_av_main.cc
deleted file mode 100644
index d23be35e5..000000000
--- a/test/mock/mock_bta_av_main.cc
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:21
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "bt_target.h"
-#include "bta/av/bta_av_int.h"
-#include "bta/include/bta_ar_api.h"
-#include "bta/include/utl.h"
-#include "btif/avrcp/avrcp_service.h"
-#include "btif/include/btif_av_co.h"
-#include "btif/include/btif_config.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "osi/include/properties.h"
-#include "stack/include/acl_api.h"
-#include "types/hci_role.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool bta_av_chk_start(tBTA_AV_SCB* p_scb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bta_av_hdl_event(BT_HDR* p_msg) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bta_av_link_role_ok(tBTA_AV_SCB* p_scb, uint8_t bits) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bta_av_switch_if_needed(tBTA_AV_SCB* p_scb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-const char* bta_av_evt_code(uint16_t evt_code) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-int BTA_AvObtainPeerChannelIndex(const RawAddress& peer_address) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_AV_SCB* bta_av_addr_to_scb(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTA_AV_SCB* bta_av_hndl_to_scb(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void bta_av_api_deregister(tBTA_AV_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_av_conn_cback(UNUSED_ATTR uint8_t handle, const RawAddress& bd_addr,
- uint8_t event, tAVDT_CTRL* p_data, uint8_t scb_index) {
- mock_function_count_map[__func__]++;
-}
-void bta_av_dup_audio_buf(tBTA_AV_SCB* p_scb, BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
-}
-void bta_av_free_scb(tBTA_AV_SCB* p_scb) {
- mock_function_count_map[__func__]++;
-}
-void bta_av_restore_switch(void) { mock_function_count_map[__func__]++; }
-void bta_av_sm_execute(tBTA_AV_CB* p_cb, uint16_t event, tBTA_AV_DATA* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_debug_av_dump(int fd) { mock_function_count_map[__func__]++; }
-void tBTA_AV_SCB::OnConnected(const RawAddress& peer_address) {
- mock_function_count_map[__func__]++;
-}
-void tBTA_AV_SCB::OnDisconnected() { mock_function_count_map[__func__]++; }
-void tBTA_AV_SCB::SetAvdtpVersion(uint16_t avdtp_version) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_dm_act.cc b/test/mock/mock_bta_dm_act.cc
deleted file mode 100644
index 171613d5f..000000000
--- a/test/mock/mock_bta_dm_act.cc
+++ /dev/null
@@ -1,164 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:57
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "bta/dm/bta_dm_int.h"
-#include "bta/gatt/bta_gattc_int.h"
-#include "bta/include/bta_dm_ci.h"
-#include "btif/include/btif_dm.h"
-#include "btif/include/btif_storage.h"
-#include "btif/include/stack_manager.h"
-#include "device/include/controller.h"
-#include "device/include/interop.h"
-#include "main/shim/acl_api.h"
-#include "main/shim/btm_api.h"
-#include "main/shim/dumpsys.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/btm/neighbor_inquiry.h"
-#include "stack/gatt/connection_manager.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_client_interface.h"
-#include "stack/include/btu.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void bta_dm_enable(tBTA_DM_SEC_CBACK* p_sec_cback) {
- mock_function_count_map[__func__]++;
-}
-void BTA_dm_acl_down(const RawAddress bd_addr, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void BTA_dm_acl_up(const RawAddress bd_addr, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void BTA_dm_notify_remote_features_complete(const RawAddress bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void BTA_dm_on_hw_off() { mock_function_count_map[__func__]++; }
-void BTA_dm_on_hw_on() { mock_function_count_map[__func__]++; }
-void BTA_dm_report_role_change(const RawAddress bd_addr, tHCI_ROLE new_role,
- tHCI_STATUS hci_status) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_acl_up(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_add_device(std::unique_ptr<tBTA_DM_API_ADD_DEVICE> msg) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_bond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_bond_cancel(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_ci_rmt_oob_act(std::unique_ptr<tBTA_DM_CI_RMT_OOB> msg) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_close_acl(const RawAddress& bd_addr, bool remove_dev,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_confirm(const RawAddress& bd_addr, bool accept) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_deinit_cb(void) { mock_function_count_map[__func__]++; }
-void bta_dm_disable() { mock_function_count_map[__func__]++; }
-void bta_dm_disc_result(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_disc_rmt_name(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_discover(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_free_sdp_db() { mock_function_count_map[__func__]++; }
-void bta_dm_init_cb(void) { mock_function_count_map[__func__]++; }
-void bta_dm_inq_cmpl(uint8_t num) { mock_function_count_map[__func__]++; }
-void bta_dm_pin_reply(std::unique_ptr<tBTA_DM_API_PIN_REPLY> msg) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_process_remove_device(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_queue_disc(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_queue_search(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_remove_device(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_rm_cback(tBTA_SYS_CONN_STATUS status, uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_rmt_name(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_sdp_result(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_search_cancel() { mock_function_count_map[__func__]++; }
-void bta_dm_search_cancel_cmpl() { mock_function_count_map[__func__]++; }
-void bta_dm_search_cancel_notify() { mock_function_count_map[__func__]++; }
-void bta_dm_execute_queued_request() { mock_function_count_map[__func__]++; }
-bool bta_dm_is_search_request_queued() {
- mock_function_count_map[__func__]++;
- return false;
-}
-void bta_dm_search_clear_queue() { mock_function_count_map[__func__]++; }
-void bta_dm_search_cmpl() { mock_function_count_map[__func__]++; }
-void bta_dm_search_result(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_search_start(tBTA_DM_MSG* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bta_dm_set_dev_name(const std::vector<uint8_t>& name) {
- mock_function_count_map[__func__]++;
-}
-bool BTA_DmSetVisibility(bt_scan_mode_t mode) {
- mock_function_count_map[__func__]++;
- return false;
-}
-void handle_remote_features_complete(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-bool bta_dm_check_if_only_hd_connected(const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
diff --git a/test/mock/mock_bta_dm_api.cc b/test/mock/mock_bta_dm_api.cc
deleted file mode 100644
index 5fd4e8024..000000000
--- a/test/mock/mock_bta_dm_api.cc
+++ /dev/null
@@ -1,145 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:33
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <vector>
-#include "bt_target.h"
-#include "bta/dm/bta_dm_int.h"
-#include "osi/include/allocator.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btu.h"
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void BTA_dm_init() { mock_function_count_map[__func__]++; }
-bool BTA_DmGetConnectionState(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tBTA_STATUS BTA_DmRemoveDevice(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return BTA_SUCCESS;
-}
-tBTA_STATUS BTA_DmSetLocalDiRecord(tSDP_DI_RECORD* p_device_info,
- uint32_t* p_handle) {
- mock_function_count_map[__func__]++;
- return BTA_SUCCESS;
-}
-void BTA_AddEirUuid(uint16_t uuid16) { mock_function_count_map[__func__]++; }
-void BTA_DmAddBleDevice(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_DEVICE_TYPE dev_type) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmAddBleKey(const RawAddress& bd_addr, tBTA_LE_KEY_VALUE* p_le_key,
- tBTM_LE_KEY_TYPE key_type) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
- const LinkKey& link_key, uint8_t key_type,
- uint8_t pin_length) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmBleConfigLocalPrivacy(bool privacy_enable) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmBleConfirmReply(const RawAddress& bd_addr, bool accept) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmBleGetEnergyInfo(tBTA_BLE_ENERGY_INFO_CBACK* p_cmpl_cback) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmBlePasskeyReply(const RawAddress& bd_addr, bool accept,
- uint32_t passkey) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmBleRequestMaxTxDataLength(const RawAddress& remote_device) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmBleSecurityGrant(const RawAddress& bd_addr,
- tBTA_DM_BLE_SEC_GRANT res) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmBleUpdateConnectionParams(const RawAddress& bd_addr,
- uint16_t min_int, uint16_t max_int,
- uint16_t latency, uint16_t timeout,
- uint16_t min_ce_len, uint16_t max_ce_len) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmBondCancel(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmCloseACL(const RawAddress& bd_addr, bool remove_dev,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmConfirm(const RawAddress& bd_addr, bool accept) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmDiscover(const RawAddress& bd_addr, tBTA_DM_SEARCH_CBACK* p_cback,
- tBT_TRANSPORT transport, bool is_bonding_or_sd) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmLocalOob(void) { mock_function_count_map[__func__]++; }
-void BTA_DmPinReply(const RawAddress& bd_addr, bool accept, uint8_t pin_len,
- uint8_t* p_pin) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmSearch(tBTA_DM_SEARCH_CBACK* p_cback, bool is_bonding_or_sdp) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmSearchCancel(void) { mock_function_count_map[__func__]++; }
-void BTA_DmSetBlePrefConnParams(const RawAddress& bd_addr,
- uint16_t min_conn_int, uint16_t max_conn_int,
- uint16_t peripheral_latency,
- uint16_t supervision_tout) {
- mock_function_count_map[__func__]++;
-}
-void BTA_DmSetDeviceName(char* p_name) { mock_function_count_map[__func__]++; }
-void BTA_DmSetEncryption(const RawAddress& bd_addr, tBT_TRANSPORT transport,
- tBTA_DM_ENCRYPT_CBACK* p_callback,
- tBTM_BLE_SEC_ACT sec_act) {
- mock_function_count_map[__func__]++;
-}
-void BTA_EnableTestMode(void) { mock_function_count_map[__func__]++; }
-void BTA_GetEirService(uint8_t* p_eir, size_t eir_len,
- tBTA_SERVICE_MASK* p_services) {
- mock_function_count_map[__func__]++;
-}
-void BTA_RemoveEirUuid(uint16_t uuid16) { mock_function_count_map[__func__]++; }
-void BTA_DmBleObserve(bool start, uint8_t duration,
- tBTA_DM_SEARCH_CBACK* p_results_cb) {
- mock_function_count_map[__func__]++;
-}
-void BTA_VendorInit(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_bta_gattc_api.cc b/test/mock/mock_bta_gattc_api.cc
deleted file mode 100644
index 767e60531..000000000
--- a/test/mock/mock_bta_gattc_api.cc
+++ /dev/null
@@ -1,167 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:30
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <ios>
-#include <list>
-#include <memory>
-#include <vector>
-#include "bt_target.h"
-#include "bta/gatt/bta_gattc_int.h"
-#include "device/include/controller.h"
-#include "stack/include/btu.h"
-#include "types/bluetooth/uuid.h"
-#include "types/bt_transport.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void BTA_GATTC_Disable(void) { mock_function_count_map[__func__]++; }
-const gatt::Characteristic* BTA_GATTC_GetCharacteristic(uint16_t conn_id,
- uint16_t handle) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const gatt::Characteristic* BTA_GATTC_GetOwningCharacteristic(uint16_t conn_id,
- uint16_t handle) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const gatt::Descriptor* BTA_GATTC_GetDescriptor(uint16_t conn_id,
- uint16_t handle) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const gatt::Service* BTA_GATTC_GetOwningService(uint16_t conn_id,
- uint16_t handle) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const std::list<gatt::Service>* BTA_GATTC_GetServices(uint16_t conn_id) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tGATT_STATUS BTA_GATTC_DeregisterForNotifications(tGATT_IF client_if,
- const RawAddress& bda,
- uint16_t handle) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS BTA_GATTC_RegisterForNotifications(tGATT_IF client_if,
- const RawAddress& bda,
- uint16_t handle) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-void BTA_GATTC_AppDeregister(tGATT_IF client_if) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_AppRegister(tBTA_GATTC_CBACK* p_client_cb,
- BtaAppRegisterCallback cb, bool eatt_support) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_CancelOpen(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_Close(uint16_t conn_id) { mock_function_count_map[__func__]++; }
-void BTA_GATTC_ConfigureMTU(uint16_t conn_id, uint16_t mtu) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_ConfigureMTU(uint16_t conn_id, uint16_t mtu,
- GATT_CONFIGURE_MTU_OP_CB callback, void* cb_data) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_DiscoverServiceByUuid(uint16_t conn_id,
- const bluetooth::Uuid& srvc_uuid) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_ExecuteWrite(uint16_t conn_id, bool is_execute) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_GetGattDb(uint16_t conn_id, uint16_t start_handle,
- uint16_t end_handle, btgatt_db_element_t** db,
- int* count) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_Open(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct, bool opportunistic) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_Open(tGATT_IF client_if, const RawAddress& remote_bda,
- bool is_direct, tBT_TRANSPORT transport, bool opportunistic,
- uint8_t initiating_phys) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_PrepareWrite(uint16_t conn_id, uint16_t handle, uint16_t offset,
- std::vector<uint8_t> value, tGATT_AUTH_REQ auth_req,
- GATT_WRITE_OP_CB callback, void* cb_data) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_ReadCharDescr(uint16_t conn_id, uint16_t handle,
- tGATT_AUTH_REQ auth_req, GATT_READ_OP_CB callback,
- void* cb_data) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_ReadCharacteristic(uint16_t conn_id, uint16_t handle,
- tGATT_AUTH_REQ auth_req,
- GATT_READ_OP_CB callback, void* cb_data) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_ReadMultiple(uint16_t conn_id, tBTA_GATTC_MULTI* p_read_multi,
- tGATT_AUTH_REQ auth_req) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_ReadUsingCharUuid(uint16_t conn_id, const bluetooth::Uuid& uuid,
- uint16_t s_handle, uint16_t e_handle,
- tGATT_AUTH_REQ auth_req,
- GATT_READ_OP_CB callback, void* cb_data) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_Refresh(const RawAddress& remote_bda) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_SendIndConfirm(uint16_t conn_id, uint16_t cid) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_ServiceSearchRequest(uint16_t conn_id,
- const bluetooth::Uuid* p_srvc_uuid) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_WriteCharDescr(uint16_t conn_id, uint16_t handle,
- std::vector<uint8_t> value,
- tGATT_AUTH_REQ auth_req,
- GATT_WRITE_OP_CB callback, void* cb_data) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTC_WriteCharValue(uint16_t conn_id, uint16_t handle,
- tGATT_WRITE_TYPE write_type,
- std::vector<uint8_t> value,
- tGATT_AUTH_REQ auth_req,
- GATT_WRITE_OP_CB callback, void* cb_data) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_gatts_api.cc b/test/mock/mock_bta_gatts_api.cc
deleted file mode 100644
index 10329133d..000000000
--- a/test/mock/mock_bta_gatts_api.cc
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:13
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/location.h>
-#include <cstdint>
-#include <memory>
-#include <vector>
-#include "bt_target.h"
-#include "bta/gatt/bta_gatts_int.h"
-#include "osi/include/allocator.h"
-#include "stack/include/btu.h"
-#include "types/bluetooth/uuid.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void BTA_GATTS_Disable(void) { mock_function_count_map[__func__]++; }
-void BTA_GATTS_AppDeregister(tGATT_IF server_if) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTS_AppRegister(const bluetooth::Uuid& app_uuid,
- tBTA_GATTS_CBACK* p_cback, bool eatt_support) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTS_CancelOpen(tGATT_IF server_if, const RawAddress& remote_bda,
- bool is_direct) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTS_Close(uint16_t conn_id) { mock_function_count_map[__func__]++; }
-void BTA_GATTS_AddService(tGATT_IF server_if,
- std::vector<btgatt_db_element_t> service,
- BTA_GATTS_AddServiceCb cb) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTS_DeleteService(uint16_t service_id) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTS_HandleValueIndication(uint16_t conn_id, uint16_t attr_id,
- std::vector<uint8_t> value,
- bool need_confirm) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTS_Open(tGATT_IF server_if, const RawAddress& remote_bda,
- bool is_direct, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTS_SendRsp(uint16_t conn_id, uint32_t trans_id, tGATT_STATUS status,
- tGATTS_RSP* p_msg) {
- mock_function_count_map[__func__]++;
-}
-void BTA_GATTS_StopService(uint16_t service_id) {
- mock_function_count_map[__func__]++;
-}
-void bta_gatts_add_service_impl(tGATT_IF server_if,
- std::vector<btgatt_db_element_t> service,
- BTA_GATTS_AddServiceCb cb) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_hd_api.cc b/test/mock/mock_bta_hd_api.cc
deleted file mode 100644
index a8022450c..000000000
--- a/test/mock/mock_bta_hd_api.cc
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:12
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "bt_target.h"
-#include "bta/hd/bta_hd_int.h"
-#include "osi/include/allocator.h"
-#include "osi/include/compat.h"
-#include "osi/include/log.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void BTA_HdEnable(tBTA_HD_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HdAddDevice(const RawAddress& addr) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HdConnect(const RawAddress& addr) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HdDisable(void) { mock_function_count_map[__func__]++; }
-void BTA_HdDisconnect(void) { mock_function_count_map[__func__]++; }
-void BTA_HdRegisterApp(tBTA_HD_APP_INFO* p_app_info, tBTA_HD_QOS_INFO* p_in_qos,
- tBTA_HD_QOS_INFO* p_out_qos) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HdRemoveDevice(const RawAddress& addr) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HdReportError(uint8_t error) { mock_function_count_map[__func__]++; }
-void BTA_HdSendReport(tBTA_HD_REPORT* p_report) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HdUnregisterApp(void) { mock_function_count_map[__func__]++; }
-void BTA_HdVirtualCableUnplug(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_bta_hearing_aid.cc b/test/mock/mock_bta_hearing_aid.cc
deleted file mode 100644
index 865a78454..000000000
--- a/test/mock/mock_bta_hearing_aid.cc
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:8
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/callback.h>
-#include <base/strings/string_number_conversions.h>
-#include <cstdint>
-#include <vector>
-#include "bta/include/bta_gatt_api.h"
-#include "bta/include/bta_gatt_queue.h"
-#include "bta/include/bta_hearing_aid_api.h"
-#include "device/include/controller.h"
-#include "embdrv/g722/g722_enc_dec.h"
-#include "osi/include/log.h"
-#include "osi/include/properties.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/acl_api_types.h"
-#include "stack/include/gap_api.h"
-#include "stack/include/l2c_api.h"
-#include "types/bluetooth/uuid.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-int HearingAid::GetDeviceCount() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void HearingAid::AddFromStorage(const HearingDevice& dev_info,
- uint16_t is_acceptlisted) {
- mock_function_count_map[__func__]++;
-}
-void HearingAid::DebugDump(int fd) { mock_function_count_map[__func__]++; }
-HearingAid* HearingAid::Get() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-bool HearingAid::IsHearingAidRunning() {
- mock_function_count_map[__func__]++;
- return false;
-}
-void HearingAid::CleanUp() { mock_function_count_map[__func__]++; }
-void HearingAid::Initialize(
- bluetooth::hearing_aid::HearingAidCallbacks* callbacks,
- base::Closure initCb) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_hf_client_api.cc b/test/mock/mock_bta_hf_client_api.cc
deleted file mode 100644
index cd036c9da..000000000
--- a/test/mock/mock_bta_hf_client_api.cc
+++ /dev/null
@@ -1,62 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:8
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "bt_trace.h"
-#include "bta/hf_client/bta_hf_client_int.h"
-#include "bta/include/bta_hf_client_api.h"
-#include "bta/sys/bta_sys.h"
-#include "osi/include/allocator.h"
-#include "osi/include/compat.h"
-#include "stack/include/bt_types.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tBTA_STATUS BTA_HfClientEnable(tBTA_HF_CLIENT_CBACK* p_cback,
- tBTA_HF_CLIENT_FEAT features,
- const char* p_service_name) {
- mock_function_count_map[__func__]++;
- return BTA_SUCCESS;
-}
-void BTA_HfClientAudioClose(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HfClientAudioOpen(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HfClientClose(uint16_t handle) { mock_function_count_map[__func__]++; }
-void BTA_HfClientDisable(void) { mock_function_count_map[__func__]++; }
-void BTA_HfClientDumpStatistics(int fd) { mock_function_count_map[__func__]++; }
-void BTA_HfClientOpen(const RawAddress& bd_addr, uint16_t* p_handle) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HfClientSendAT(uint16_t handle, tBTA_HF_CLIENT_AT_CMD_TYPE at,
- uint32_t val1, uint32_t val2, const char* str) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_hh_api.cc b/test/mock/mock_bta_hh_api.cc
deleted file mode 100644
index 2547b07f5..000000000
--- a/test/mock/mock_bta_hh_api.cc
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:16
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "bt_target.h"
-#include "bta/hh/bta_hh_int.h"
-#include "bta/sys/bta_sys.h"
-#include "osi/include/allocator.h"
-#include "osi/include/osi.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void BTA_HhEnable(tBTA_HH_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HhAddDev(const RawAddress& bda, tBTA_HH_ATTR_MASK attr_mask,
- uint8_t sub_class, uint8_t app_id,
- tBTA_HH_DEV_DSCP_INFO dscp_info) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HhClose(uint8_t dev_handle) { mock_function_count_map[__func__]++; }
-void BTA_HhDisable(void) { mock_function_count_map[__func__]++; }
-void BTA_HhGetDscpInfo(uint8_t dev_handle) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HhGetIdle(uint8_t dev_handle) { mock_function_count_map[__func__]++; }
-void BTA_HhGetProtoMode(uint8_t dev_handle) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HhGetReport(uint8_t dev_handle, tBTA_HH_RPT_TYPE r_type,
- uint8_t rpt_id, uint16_t buf_size) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HhOpen(const RawAddress& dev_bda) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HhRemoveDev(uint8_t dev_handle) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HhSendCtrl(uint8_t dev_handle, tBTA_HH_TRANS_CTRL_TYPE c_type) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HhSendData(uint8_t dev_handle, UNUSED_ATTR const RawAddress& dev_bda,
- BT_HDR* p_data) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HhSetIdle(uint8_t dev_handle, uint16_t idle_rate) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HhSetProtoMode(uint8_t dev_handle, tBTA_HH_PROTO_MODE p_type) {
- mock_function_count_map[__func__]++;
-}
-void BTA_HhSetReport(uint8_t dev_handle, tBTA_HH_RPT_TYPE r_type,
- BT_HDR* p_data) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_jv_api.cc b/test/mock/mock_bta_jv_api.cc
deleted file mode 100644
index b0f7f339c..000000000
--- a/test/mock/mock_bta_jv_api.cc
+++ /dev/null
@@ -1,146 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:22
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/location.h>
-#include <base/logging.h>
-#include <cstdint>
-#include <memory>
-#include "bt_target.h"
-#include "bta/jv/bta_jv_int.h"
-#include "stack/include/btu.h"
-#include "stack/include/gap_api.h"
-#include "types/bluetooth/uuid.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tBTA_JV_STATUS BTA_JvCreateRecordByUser(uint32_t rfcomm_slot_id) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvDeleteRecord(uint32_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvEnable(tBTA_JV_DM_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvFreeChannel(uint16_t channel, int conn_type) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvL2capClose(uint32_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvL2capRead(uint32_t handle, uint32_t req_id,
- uint8_t* p_data, uint16_t len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvL2capReady(uint32_t handle, uint32_t* p_data_size) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvL2capStopServer(uint16_t local_psm,
- uint32_t l2cap_socket_id) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvL2capWrite(uint32_t handle, uint32_t req_id, BT_HDR* msg,
- uint32_t user_id) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvRfcommClose(uint32_t handle, uint32_t rfcomm_slot_id) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvRfcommConnect(tBTA_SEC sec_mask, tBTA_JV_ROLE role,
- uint8_t remote_scn,
- const RawAddress& peer_bd_addr,
- tBTA_JV_RFCOMM_CBACK* p_cback,
- uint32_t rfcomm_slot_id) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvRfcommStartServer(tBTA_SEC sec_mask, tBTA_JV_ROLE role,
- uint8_t local_scn, uint8_t max_session,
- tBTA_JV_RFCOMM_CBACK* p_cback,
- uint32_t rfcomm_slot_id) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvRfcommStopServer(uint32_t handle,
- uint32_t rfcomm_slot_id) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvRfcommWrite(uint32_t handle, uint32_t req_id) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvSetPmProfile(uint32_t handle, tBTA_JV_PM_ID app_id,
- tBTA_JV_CONN_STATE init_st) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_JV_STATUS BTA_JvStartDiscovery(const RawAddress& bd_addr,
- uint16_t num_uuid,
- const bluetooth::Uuid* p_uuid_list,
- uint32_t rfcomm_slot_id) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t BTA_JvRfcommGetPortHdl(uint32_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void BTA_JvDisable(void) { mock_function_count_map[__func__]++; }
-void BTA_JvGetChannelId(int conn_type, uint32_t id, int32_t channel) {
- mock_function_count_map[__func__]++;
-}
-void BTA_JvL2capConnect(int conn_type, tBTA_SEC sec_mask, tBTA_JV_ROLE role,
- std::unique_ptr<tL2CAP_ERTM_INFO> ertm_info,
- uint16_t remote_psm, uint16_t rx_mtu,
- std::unique_ptr<tL2CAP_CFG_INFO> cfg,
- const RawAddress& peer_bd_addr,
- tBTA_JV_L2CAP_CBACK* p_cback,
- uint32_t l2cap_socket_id) {
- mock_function_count_map[__func__]++;
-}
-void BTA_JvL2capStartServer(int conn_type, tBTA_SEC sec_mask, tBTA_JV_ROLE role,
- std::unique_ptr<tL2CAP_ERTM_INFO> ertm_info,
- uint16_t local_psm, uint16_t rx_mtu,
- std::unique_ptr<tL2CAP_CFG_INFO> cfg,
- tBTA_JV_L2CAP_CBACK* p_cback,
- uint32_t l2cap_socket_id) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_pan_api.cc b/test/mock/mock_bta_pan_api.cc
deleted file mode 100644
index adc1462c3..000000000
--- a/test/mock/mock_bta_pan_api.cc
+++ /dev/null
@@ -1,48 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:10
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "bt_target.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-#include "bta/pan/bta_pan_int.h"
-
-void BTA_PanClose(uint16_t handle) { mock_function_count_map[__func__]++; }
-void BTA_PanDisable(void) { mock_function_count_map[__func__]++; }
-void BTA_PanEnable(tBTA_PAN_CBACK p_cback) {
- mock_function_count_map[__func__]++;
-}
-void BTA_PanOpen(const RawAddress& bd_addr, tBTA_PAN_ROLE local_role,
- tBTA_PAN_ROLE peer_role) {
- mock_function_count_map[__func__]++;
-}
-void BTA_PanSetRole(tBTA_PAN_ROLE role, tBTA_PAN_ROLE_INFO* p_user_info,
- tBTA_PAN_ROLE_INFO* p_nap_info) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_pan_ci.cc b/test/mock/mock_bta_pan_ci.cc
deleted file mode 100644
index ffd2dc56e..000000000
--- a/test/mock/mock_bta_pan_ci.cc
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:8
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "bt_target.h"
-#include "bta/pan/bta_pan_int.h"
-#include "osi/include/allocator.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-BT_HDR* bta_pan_ci_readbuf(uint16_t handle, RawAddress& src, RawAddress& dst,
- uint16_t* p_protocol, bool* p_ext, bool* p_forward) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void bta_pan_ci_rx_ready(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void bta_pan_ci_rx_write(uint16_t handle, const RawAddress& dst,
- const RawAddress& src, uint16_t protocol,
- uint8_t* p_data, uint16_t len, bool ext) {
- mock_function_count_map[__func__]++;
-}
-void bta_pan_ci_rx_writebuf(uint16_t handle, const RawAddress& dst,
- const RawAddress& src, uint16_t protocol,
- BT_HDR* p_buf, bool ext) {
- mock_function_count_map[__func__]++;
-}
-void bta_pan_ci_set_mfilters(uint16_t handle, uint16_t num_mcast_filters,
- uint8_t* p_start_array, uint8_t* p_end_array) {
- mock_function_count_map[__func__]++;
-}
-void bta_pan_ci_set_pfilters(uint16_t handle, uint16_t num_filters,
- uint16_t* p_start_array, uint16_t* p_end_array) {
- mock_function_count_map[__func__]++;
-}
-void bta_pan_ci_tx_flow(uint16_t handle, bool enable) {
- mock_function_count_map[__func__]++;
-}
-void bta_pan_ci_tx_ready(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_sdp_api.cc b/test/mock/mock_bta_sdp_api.cc
deleted file mode 100644
index 87244d31d..000000000
--- a/test/mock/mock_bta_sdp_api.cc
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:4
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/location.h>
-#include "bt_target.h"
-#include "bta/include/bta_sdp_api.h"
-#include "bta/sdp/bta_sdp_int.h"
-#include "stack/include/btu.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tBTA_SDP_STATUS BTA_SdpCreateRecordByUser(void* user_data) {
- mock_function_count_map[__func__]++;
- return BTA_SDP_SUCCESS;
-}
-tBTA_SDP_STATUS BTA_SdpEnable(tBTA_SDP_DM_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return BTA_SDP_SUCCESS;
-}
-tBTA_SDP_STATUS BTA_SdpRemoveRecordByUser(void* user_data) {
- mock_function_count_map[__func__]++;
- return BTA_SDP_SUCCESS;
-}
-tBTA_SDP_STATUS BTA_SdpSearch(const RawAddress& bd_addr,
- const bluetooth::Uuid& uuid) {
- mock_function_count_map[__func__]++;
- return BTA_SDP_SUCCESS;
-}
diff --git a/test/mock/mock_bta_sys_conn.cc b/test/mock/mock_bta_sys_conn.cc
deleted file mode 100644
index fa334a8bc..000000000
--- a/test/mock/mock_bta_sys_conn.cc
+++ /dev/null
@@ -1,122 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:19
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "bt_target.h"
-#include "bta/sys/bta_sys.h"
-#include "bta/sys/bta_sys_int.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "stack/include/btm_api.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void bta_sys_app_close(uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_app_open(uint8_t id, uint8_t app_id, const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_busy(uint8_t id, uint8_t app_id, const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_chg_ssr_config(uint8_t id, uint8_t app_id, uint16_t max_latency,
- uint16_t min_tout) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_collision_register(uint8_t bta_id, tBTA_SYS_CONN_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_conn_close(uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_conn_open(uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_idle(uint8_t id, uint8_t app_id, const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_notify_collision(const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_notify_role_chg(const RawAddress& peer_addr, tHCI_ROLE new_role,
- tHCI_STATUS hci_status) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_pm_register(tBTA_SYS_CONN_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_rm_register(tBTA_SYS_CONN_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_role_chg_register(tBTA_SYS_CONN_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_sco_close(uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_sco_open(uint8_t id, uint8_t app_id, const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_sco_register(tBTA_SYS_CONN_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_sco_unuse(uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_sco_use(UNUSED_ATTR uint8_t id, uint8_t app_id,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_ssr_cfg_register(tBTA_SYS_SSR_CFG_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_eir_register(tBTA_SYS_EIR_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_cust_eir_register(tBTA_SYS_CUST_EIR_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_add_uuid(uint16_t uuid16) { mock_function_count_map[__func__]++; }
-void bta_sys_remove_uuid(uint16_t uuid16) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_add_cust_uuid(const tBTA_CUSTOM_UUID& curr) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_remove_cust_uuid(const tBTA_CUSTOM_UUID& curr) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_sys_main.cc b/test/mock/mock_bta_sys_main.cc
deleted file mode 100644
index 98713490b..000000000
--- a/test/mock/mock_bta_sys_main.cc
+++ /dev/null
@@ -1,64 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:10
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <cstring>
-#include "bt_target.h"
-#include "bta/sys/bta_sys.h"
-#include "bta/sys/bta_sys_int.h"
-#include "include/hardware/bluetooth.h"
-#include "osi/include/alarm.h"
-#include "osi/include/allocator.h"
-#include "osi/include/log.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btu.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool bta_sys_is_register(uint8_t id) {
- mock_function_count_map[__func__]++;
- return false;
-}
-void BTA_sys_signal_hw_error() { mock_function_count_map[__func__]++; }
-void bta_set_forward_hw_failures(bool value) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_deregister(uint8_t id) { mock_function_count_map[__func__]++; }
-void bta_sys_disable() { mock_function_count_map[__func__]++; }
-void bta_sys_init(void) { mock_function_count_map[__func__]++; }
-void bta_sys_register(uint8_t id, const tBTA_SYS_REG* p_reg) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_sendmsg(void* p_msg) { mock_function_count_map[__func__]++; }
-void bta_sys_sendmsg_delayed(void* p_msg, const base::TimeDelta& delay) {
- mock_function_count_map[__func__]++;
-}
-void bta_sys_start_timer(alarm_t* alarm, uint64_t interval_ms, uint16_t event,
- uint16_t layer_specific) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_sys_utl.cc b/test/mock/mock_bta_sys_utl.cc
deleted file mode 100644
index ee6dac205..000000000
--- a/test/mock/mock_bta_sys_utl.cc
+++ /dev/null
@@ -1,63 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:7
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "bt_target.h"
-#include "bta/include/utl.h"
-#include "stack/include/btm_api.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool utl_isdialchar(const char d) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool utl_isdialstr(const char* p_s) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool utl_isintstr(const char* p_s) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool utl_set_device_class(tBTA_UTL_COD* p_cod, uint8_t cmd) {
- mock_function_count_map[__func__]++;
- return false;
-}
-int utl_strucmp(const char* p_s, const char* p_t) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int16_t utl_str2int(const char* p_s) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t utl_itoa(uint16_t i, char* p_s) {
- mock_function_count_map[__func__]++;
- return 0;
-}
diff --git a/test/mock/mock_bta_vc.cc b/test/mock/mock_bta_vc.cc
deleted file mode 100644
index 4a702739f..000000000
--- a/test/mock/mock_bta_vc.cc
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:7
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/bind_helpers.h>
-#include <base/logging.h>
-#include <base/strings/string_number_conversions.h>
-#include <hardware/bt_vc.h>
-#include <string>
-#include <vector>
-#include "bta/include/bta_gatt_api.h"
-#include "bta/include/bta_gatt_queue.h"
-#include "bta/include/bta_vc_api.h"
-#include "btif/include/btif_storage.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void VolumeControl::AddFromStorage(const RawAddress& address,
- bool auto_connect) {
- mock_function_count_map[__func__]++;
-}
-void VolumeControl::CleanUp() { mock_function_count_map[__func__]++; }
-void VolumeControl::DebugDump(int fd) { mock_function_count_map[__func__]++; }
-VolumeControl* VolumeControl::Get(void) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-bool VolumeControl::IsVolumeControlRunning() {
- mock_function_count_map[__func__]++;
- return false;
-}
-void VolumeControl::Initialize(
- bluetooth::vc::VolumeControlCallbacks* callbacks) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_bta_vc_device.cc b/test/mock/mock_bta_vc_device.cc
deleted file mode 100644
index c2457cc91..000000000
--- a/test/mock/mock_bta_vc_device.cc
+++ /dev/null
@@ -1,92 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:12
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <map>
-#include <vector>
-#include "bta/vc/devices.h"
-#include "stack/btm/btm_sec.h"
-
-using namespace bluetooth::vc::internal;
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool VolumeControlDevice::EnableEncryption(tBTM_SEC_CALLBACK* callback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool VolumeControlDevice::EnqueueInitialRequests(
- tGATT_IF gatt_if, GATT_READ_OP_CB chrc_read_cb,
- GATT_WRITE_OP_CB cccd_write_cb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool VolumeControlDevice::IsEncryptionEnabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool VolumeControlDevice::UpdateHandles(void) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool VolumeControlDevice::VerifyReady(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool VolumeControlDevice::set_volume_control_service_handles(
- const gatt::Service& service) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool VolumeControlDevice::subscribe_for_notifications(tGATT_IF gatt_if,
- uint16_t handle,
- uint16_t ccc_handle,
- GATT_WRITE_OP_CB cb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-uint16_t VolumeControlDevice::find_ccc_handle(uint16_t chrc_handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void VolumeControlDevice::ControlPointOperation(uint8_t opcode,
- const std::vector<uint8_t>* arg,
- GATT_WRITE_OP_CB cb,
- void* cb_data) {
- mock_function_count_map[__func__]++;
-}
-void VolumeControlDevice::Disconnect(tGATT_IF gatt_if) {
- mock_function_count_map[__func__]++;
-}
-void VolumeControlDevice::EnqueueRemainingRequests(
- tGATT_IF gatt_if, GATT_READ_OP_CB chrc_read_cb,
- GATT_WRITE_OP_CB cccd_write_cb) {
- mock_function_count_map[__func__]++;
-}
-void VolumeControlDevice::ResetHandles(void) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_btcore_module.cc b/test/mock/mock_btcore_module.cc
deleted file mode 100644
index c83cb9deb..000000000
--- a/test/mock/mock_btcore_module.cc
+++ /dev/null
@@ -1,61 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:8
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <dlfcn.h>
-#include <string.h>
-#include <mutex>
-#include <unordered_map>
-#include "btcore/include/module.h"
-#include "common/message_loop_thread.h"
-#include "osi/include/allocator.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool module_init(const module_t* module) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool module_start_up(const module_t* module) {
- mock_function_count_map[__func__]++;
- return false;
-}
-const module_t* get_module(const char* name) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void module_management_start(void) { mock_function_count_map[__func__]++; }
-void module_clean_up(const module_t* module) {
- mock_function_count_map[__func__]++;
-}
-void module_management_stop(void) { mock_function_count_map[__func__]++; }
-void module_shut_down(const module_t* module) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_btif_bqr.cc b/test/mock/mock_btif_bqr.cc
deleted file mode 100644
index 078b11647..000000000
--- a/test/mock/mock_btif_bqr.cc
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:51
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-namespace bluetooth {
-namespace bqr {
-
-void DumpLmpLlMessage(uint8_t length, uint8_t* p_event) {
- mock_function_count_map[__func__]++;
-}
-
-void DumpBtScheduling(uint8_t length, uint8_t* p_event) {
- mock_function_count_map[__func__]++;
-}
-
-} // namespace bqr
-} // namespace bluetooth
diff --git a/test/mock/mock_btif_co_bta_dm_co.cc b/test/mock/mock_btif_co_bta_dm_co.cc
deleted file mode 100644
index e244296c5..000000000
--- a/test/mock/mock_btif_co_bta_dm_co.cc
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- */
-
-#include <cstdint>
-
-#include "bta/include/bta_api.h"
-#include "bta/sys/bta_sys.h"
-#include "internal_include/bte_appl.h"
-#include "osi/include/osi.h" // UNUSED_ATTR
-#include "stack/include/btm_api_types.h"
-
-tBTE_APPL_CFG bte_appl_cfg = {
- BTA_LE_AUTH_REQ_SC_MITM_BOND, // Authentication requirements
- BTM_IO_CAP_UNKNOWN, BTM_BLE_INITIATOR_KEY_SIZE, BTM_BLE_RESPONDER_KEY_SIZE,
- BTM_BLE_MAX_KEY_SIZE};
-
-bool bta_dm_co_get_compress_memory(UNUSED_ATTR tBTA_SYS_ID id,
- UNUSED_ATTR uint8_t** memory_p,
- UNUSED_ATTR uint32_t* memory_size) {
- return true;
-}
diff --git a/test/mock/mock_btif_co_bta_hh_co.cc b/test/mock/mock_btif_co_bta_hh_co.cc
deleted file mode 100644
index 83782555b..000000000
--- a/test/mock/mock_btif_co_bta_hh_co.cc
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:12
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "bta/include/bta_hh_api.h"
-#include "bta/include/bta_hh_co.h"
-#include "btif/include/btif_hh.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-int bta_hh_co_write(int fd, uint8_t* rpt, uint16_t len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_HH_RPT_CACHE_ENTRY* bta_hh_le_co_cache_load(const RawAddress& remote_bda,
- uint8_t* p_num_rpt,
- UNUSED_ATTR uint8_t app_id) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void bta_hh_co_close(uint8_t dev_handle, uint8_t app_id) {
- mock_function_count_map[__func__]++;
-}
-void bta_hh_co_data(uint8_t dev_handle, uint8_t* p_rpt, uint16_t len,
- tBTA_HH_PROTO_MODE mode, uint8_t sub_class,
- uint8_t ctry_code, UNUSED_ATTR const RawAddress& peer_addr,
- uint8_t app_id) {
- mock_function_count_map[__func__]++;
-}
-void bta_hh_co_destroy(int fd) { mock_function_count_map[__func__]++; }
-void bta_hh_co_get_rpt_rsp(uint8_t dev_handle, uint8_t status, uint8_t* p_rpt,
- uint16_t len) {
- mock_function_count_map[__func__]++;
-}
-void bta_hh_co_open(uint8_t dev_handle, uint8_t sub_class,
- tBTA_HH_ATTR_MASK attr_mask, uint8_t app_id) {
- mock_function_count_map[__func__]++;
-}
-void bta_hh_co_send_hid_info(btif_hh_device_t* p_dev, const char* dev_name,
- uint16_t vendor_id, uint16_t product_id,
- uint16_t version, uint8_t ctry_code, int dscp_len,
- uint8_t* p_dscp) {
- mock_function_count_map[__func__]++;
-}
-void bta_hh_co_set_rpt_rsp(uint8_t dev_handle, uint8_t status) {
- mock_function_count_map[__func__]++;
-}
-void bta_hh_le_co_reset_rpt_cache(const RawAddress& remote_bda,
- UNUSED_ATTR uint8_t app_id) {
- mock_function_count_map[__func__]++;
-}
-void bta_hh_le_co_rpt_info(const RawAddress& remote_bda,
- tBTA_HH_RPT_CACHE_ENTRY* p_entry,
- UNUSED_ATTR uint8_t app_id) {
- mock_function_count_map[__func__]++;
-}
-void uhid_set_non_blocking(int fd) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_btif_config.cc b/test/mock/mock_btif_config.cc
deleted file mode 100644
index 512a01f1d..000000000
--- a/test/mock/mock_btif_config.cc
+++ /dev/null
@@ -1,162 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:18
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_btif_config.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace btif_config {
-
-// Function state capture and return values, if needed
-struct btif_get_device_type btif_get_device_type;
-struct btif_get_address_type btif_get_address_type;
-struct btif_config_exist btif_config_exist;
-struct btif_config_get_int btif_config_get_int;
-struct btif_config_set_int btif_config_set_int;
-struct btif_config_get_uint64 btif_config_get_uint64;
-struct btif_config_set_uint64 btif_config_set_uint64;
-struct btif_config_get_str btif_config_get_str;
-struct btif_config_set_str btif_config_set_str;
-struct btif_config_get_bin btif_config_get_bin;
-struct btif_config_get_bin_length btif_config_get_bin_length;
-struct btif_config_set_bin btif_config_set_bin;
-struct btif_config_get_paired_devices btif_config_get_paired_devices;
-struct btif_config_remove btif_config_remove;
-struct btif_config_save btif_config_save;
-struct btif_config_flush btif_config_flush;
-struct btif_config_clear btif_config_clear;
-struct btif_debug_config_dump btif_debug_config_dump;
-
-} // namespace btif_config
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-bool btif_get_device_type(const RawAddress& bda, int* p_device_type) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_get_device_type(bda, p_device_type);
-}
-bool btif_get_address_type(const RawAddress& bda, tBLE_ADDR_TYPE* p_addr_type) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_get_address_type(bda, p_addr_type);
-}
-bool btif_config_exist(const std::string& section, const std::string& key) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_exist(section, key);
-}
-bool btif_config_get_int(const std::string& section, const std::string& key,
- int* value) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_get_int(section, key, value);
-}
-bool btif_config_set_int(const std::string& section, const std::string& key,
- int value) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_set_int(section, key, value);
-}
-bool btif_config_get_uint64(const std::string& section, const std::string& key,
- uint64_t* value) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_get_uint64(section, key, value);
-}
-bool btif_config_set_uint64(const std::string& section, const std::string& key,
- uint64_t value) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_set_uint64(section, key, value);
-}
-bool btif_config_get_str(const std::string& section, const std::string& key,
- char* value, int* size_bytes) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_get_str(section, key, value,
- size_bytes);
-}
-bool btif_config_set_str(const std::string& section, const std::string& key,
- const std::string& value) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_set_str(section, key, value);
-}
-bool btif_config_get_bin(const std::string& section, const std::string& key,
- uint8_t* value, size_t* length) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_get_bin(section, key, value,
- length);
-}
-size_t btif_config_get_bin_length(const std::string& section,
- const std::string& key) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_get_bin_length(section, key);
-}
-bool btif_config_set_bin(const std::string& section, const std::string& key,
- const uint8_t* value, size_t length) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_set_bin(section, key, value,
- length);
-}
-std::vector<RawAddress> btif_config_get_paired_devices() {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_get_paired_devices();
-}
-bool btif_config_remove(const std::string& section, const std::string& key) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_remove(section, key);
-}
-void btif_config_save(void) {
- mock_function_count_map[__func__]++;
- test::mock::btif_config::btif_config_save();
-}
-void btif_config_flush(void) {
- mock_function_count_map[__func__]++;
- test::mock::btif_config::btif_config_flush();
-}
-bool btif_config_clear(void) {
- mock_function_count_map[__func__]++;
- return test::mock::btif_config::btif_config_clear();
-}
-void btif_debug_config_dump(int fd) {
- mock_function_count_map[__func__]++;
- test::mock::btif_config::btif_debug_config_dump(fd);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_btif_config.h b/test/mock/mock_btif_config.h
deleted file mode 100644
index 642385504..000000000
--- a/test/mock/mock_btif_config.h
+++ /dev/null
@@ -1,265 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:18
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-#include "btif/include/btif_config.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace btif_config {
-
-// Shared state between mocked functions and tests
-// Name: btif_get_device_type
-// Params: const RawAddress& bda, int* p_device_type
-// Returns: bool
-struct btif_get_device_type {
- std::function<bool(const RawAddress& bda, int* p_device_type)> body{
- [](const RawAddress& bda, int* p_device_type) { return false; }};
- bool operator()(const RawAddress& bda, int* p_device_type) {
- return body(bda, p_device_type);
- };
-};
-extern struct btif_get_device_type btif_get_device_type;
-// Name: btif_get_address_type
-// Params: const RawAddress& bda, tBLE_ADDR_TYPE* p_addr_type
-// Returns: bool
-struct btif_get_address_type {
- std::function<bool(const RawAddress& bda, tBLE_ADDR_TYPE* p_addr_type)> body{
- [](const RawAddress& bda, tBLE_ADDR_TYPE* p_addr_type) { return false; }};
- bool operator()(const RawAddress& bda, tBLE_ADDR_TYPE* p_addr_type) {
- return body(bda, p_addr_type);
- };
-};
-extern struct btif_get_address_type btif_get_address_type;
-// Name: btif_config_exist
-// Params: const std::string& section, const std::string& key
-// Returns: bool
-struct btif_config_exist {
- std::function<bool(const std::string& section, const std::string& key)> body{
- [](const std::string& section, const std::string& key) { return false; }};
- bool operator()(const std::string& section, const std::string& key) {
- return body(section, key);
- };
-};
-extern struct btif_config_exist btif_config_exist;
-// Name: btif_config_get_int
-// Params: const std::string& section, const std::string& key, int* value
-// Returns: bool
-struct btif_config_get_int {
- std::function<bool(const std::string& section, const std::string& key,
- int* value)>
- body{[](const std::string& section, const std::string& key, int* value) {
- return false;
- }};
- bool operator()(const std::string& section, const std::string& key,
- int* value) {
- return body(section, key, value);
- };
-};
-extern struct btif_config_get_int btif_config_get_int;
-// Name: btif_config_set_int
-// Params: const std::string& section, const std::string& key, int value
-// Returns: bool
-struct btif_config_set_int {
- std::function<bool(const std::string& section, const std::string& key,
- int value)>
- body{[](const std::string& section, const std::string& key, int value) {
- return false;
- }};
- bool operator()(const std::string& section, const std::string& key,
- int value) {
- return body(section, key, value);
- };
-};
-extern struct btif_config_set_int btif_config_set_int;
-// Name: btif_config_get_uint64
-// Params: const std::string& section, const std::string& key, uint64_t* value
-// Returns: bool
-struct btif_config_get_uint64 {
- std::function<bool(const std::string& section, const std::string& key,
- uint64_t* value)>
- body{[](const std::string& section, const std::string& key,
- uint64_t* value) { return false; }};
- bool operator()(const std::string& section, const std::string& key,
- uint64_t* value) {
- return body(section, key, value);
- };
-};
-extern struct btif_config_get_uint64 btif_config_get_uint64;
-// Name: btif_config_set_uint64
-// Params: const std::string& section, const std::string& key, uint64_t value
-// Returns: bool
-struct btif_config_set_uint64 {
- std::function<bool(const std::string& section, const std::string& key,
- uint64_t value)>
- body{[](const std::string& section, const std::string& key,
- uint64_t value) { return false; }};
- bool operator()(const std::string& section, const std::string& key,
- uint64_t value) {
- return body(section, key, value);
- };
-};
-extern struct btif_config_set_uint64 btif_config_set_uint64;
-// Name: btif_config_get_str
-// Params: const std::string& section, const std::string& key, char* value, int*
-// size_bytes Returns: bool
-struct btif_config_get_str {
- std::function<bool(const std::string& section, const std::string& key,
- char* value, int* size_bytes)>
- body{[](const std::string& section, const std::string& key, char* value,
- int* size_bytes) { return false; }};
- bool operator()(const std::string& section, const std::string& key,
- char* value, int* size_bytes) {
- return body(section, key, value, size_bytes);
- };
-};
-extern struct btif_config_get_str btif_config_get_str;
-// Name: btif_config_set_str
-// Params: const std::string& section, const std::string& key, const
-// std::string& value Returns: bool
-struct btif_config_set_str {
- std::function<bool(const std::string& section, const std::string& key,
- const std::string& value)>
- body{[](const std::string& section, const std::string& key,
- const std::string& value) { return false; }};
- bool operator()(const std::string& section, const std::string& key,
- const std::string& value) {
- return body(section, key, value);
- };
-};
-extern struct btif_config_set_str btif_config_set_str;
-// Name: btif_config_get_bin
-// Params: const std::string& section, const std::string& key, uint8_t* value,
-// size_t* length Returns: bool
-struct btif_config_get_bin {
- std::function<bool(const std::string& section, const std::string& key,
- uint8_t* value, size_t* length)>
- body{[](const std::string& section, const std::string& key,
- uint8_t* value, size_t* length) { return false; }};
- bool operator()(const std::string& section, const std::string& key,
- uint8_t* value, size_t* length) {
- return body(section, key, value, length);
- };
-};
-extern struct btif_config_get_bin btif_config_get_bin;
-// Name: btif_config_get_bin_length
-// Params: const std::string& section, const std::string& key
-// Returns: size_t
-struct btif_config_get_bin_length {
- std::function<size_t(const std::string& section, const std::string& key)>
- body{
- [](const std::string& section, const std::string& key) { return 0; }};
- size_t operator()(const std::string& section, const std::string& key) {
- return body(section, key);
- };
-};
-extern struct btif_config_get_bin_length btif_config_get_bin_length;
-// Name: btif_config_set_bin
-// Params: const std::string& section, const std::string& key, const uint8_t*
-// value, size_t length Returns: bool
-struct btif_config_set_bin {
- std::function<bool(const std::string& section, const std::string& key,
- const uint8_t* value, size_t length)>
- body{[](const std::string& section, const std::string& key,
- const uint8_t* value, size_t length) { return false; }};
- bool operator()(const std::string& section, const std::string& key,
- const uint8_t* value, size_t length) {
- return body(section, key, value, length);
- };
-};
-extern struct btif_config_set_bin btif_config_set_bin;
-// Name: btif_config_get_paired_devices
-// Params:
-// Returns: std::vector<RawAddress>
-struct btif_config_get_paired_devices {
- std::vector<RawAddress> raw_addresses;
- std::function<std::vector<RawAddress>()> body{
- [this]() { return raw_addresses; }};
- std::vector<RawAddress> operator()() { return body(); };
-};
-extern struct btif_config_get_paired_devices btif_config_get_paired_devices;
-// Name: btif_config_remove
-// Params: const std::string& section, const std::string& key
-// Returns: bool
-struct btif_config_remove {
- std::function<bool(const std::string& section, const std::string& key)> body{
- [](const std::string& section, const std::string& key) { return false; }};
- bool operator()(const std::string& section, const std::string& key) {
- return body(section, key);
- };
-};
-extern struct btif_config_remove btif_config_remove;
-// Name: btif_config_save
-// Params: void
-// Returns: void
-struct btif_config_save {
- std::function<void(void)> body{[](void) {}};
- void operator()(void) { body(); };
-};
-extern struct btif_config_save btif_config_save;
-// Name: btif_config_flush
-// Params: void
-// Returns: void
-struct btif_config_flush {
- std::function<void(void)> body{[](void) {}};
- void operator()(void) { body(); };
-};
-extern struct btif_config_flush btif_config_flush;
-// Name: btif_config_clear
-// Params: void
-// Returns: bool
-struct btif_config_clear {
- std::function<bool(void)> body{[](void) { return false; }};
- bool operator()(void) { return body(); };
-};
-extern struct btif_config_clear btif_config_clear;
-// Name: btif_debug_config_dump
-// Params: int fd
-// Returns: void
-struct btif_debug_config_dump {
- std::function<void(int fd)> body{[](int fd) {}};
- void operator()(int fd) { body(fd); };
-};
-extern struct btif_debug_config_dump btif_debug_config_dump;
-
-} // namespace btif_config
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_btif_core.cc b/test/mock/mock_btif_core.cc
deleted file mode 100644
index 7d484727c..000000000
--- a/test/mock/mock_btif_core.cc
+++ /dev/null
@@ -1,150 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:27
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/at_exit.h>
-#include <base/bind.h>
-#include <base/threading/platform_thread.h>
-#include <signal.h>
-#include <sys/types.h>
-#include <cstdint>
-#include "bt_target.h"
-#include "btif/include/btif_av.h"
-#include "btif/include/btif_common.h"
-#include "btif/include/btif_config.h"
-#include "btif/include/btif_dm.h"
-#include "btif/include/btif_pan.h"
-#include "btif/include/btif_profile_queue.h"
-#include "btif/include/btif_sock.h"
-#include "btif/include/btif_storage.h"
-#include "btif/include/stack_manager.h"
-#include "common/message_loop_thread.h"
-#include "device/include/controller.h"
-#include "osi/include/future.h"
-#include "osi/include/log.h"
-#include "osi/include/properties.h"
-#include "stack/include/a2dp_api.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_ble_api.h"
-#include "types/bluetooth/uuid.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool btif_is_dut_mode() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool is_on_jni_thread() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bt_property_t* property_deep_copy(const bt_property_t* prop) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-bt_status_t btif_cleanup_bluetooth() {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_init_bluetooth() {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_set_dynamic_audio_buffer_size(int codec, int size) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_transfer_context(tBTIF_CBACK* p_cback, uint16_t event,
- char* p_params, int param_len,
- tBTIF_COPY_CBACK* p_copy_cback) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t do_in_jni_thread(base::OnceClosure task) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t do_in_jni_thread(const base::Location& from_here,
- base::OnceClosure task) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-btbase::AbstractMessageLoop* get_jni_message_loop() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-int btif_is_enabled(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTA_SERVICE_MASK btif_get_enabled_services_mask(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void DynamicAudiobufferSizeCompleteCallback(tBTM_VSC_CMPL* p_vsc_cmpl_params) {
- mock_function_count_map[__func__]++;
-}
-void btif_adapter_properties_evt(bt_status_t status, uint32_t num_props,
- bt_property_t* p_props) {
- mock_function_count_map[__func__]++;
-}
-void btif_disable_service(tBTA_SERVICE_ID service_id) {
- mock_function_count_map[__func__]++;
-}
-void btif_dut_mode_configure(uint8_t enable) {
- mock_function_count_map[__func__]++;
-}
-void btif_dut_mode_send(uint16_t opcode, uint8_t* buf, uint8_t len) {
- mock_function_count_map[__func__]++;
-}
-void btif_enable_bluetooth_evt() { mock_function_count_map[__func__]++; }
-void btif_enable_service(tBTA_SERVICE_ID service_id) {
- mock_function_count_map[__func__]++;
-}
-void btif_get_adapter_properties(void) { mock_function_count_map[__func__]++; }
-void btif_get_adapter_property(bt_property_type_t type) {
- mock_function_count_map[__func__]++;
-}
-void btif_get_remote_device_properties(RawAddress remote_addr) {
- mock_function_count_map[__func__]++;
-}
-void btif_get_remote_device_property(RawAddress remote_addr,
- bt_property_type_t type) {
- mock_function_count_map[__func__]++;
-}
-void btif_init_ok() { mock_function_count_map[__func__]++; }
-void btif_remote_properties_evt(bt_status_t status, RawAddress* remote_addr,
- uint32_t num_props, bt_property_t* p_props) {
- mock_function_count_map[__func__]++;
-}
-void btif_set_adapter_property(bt_property_t* property) {
- mock_function_count_map[__func__]++;
-}
-void btif_set_remote_device_property(RawAddress* remote_addr,
- bt_property_t* property) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_btif_debug_conn.cc b/test/mock/mock_btif_debug_conn.cc
deleted file mode 100644
index d2627606c..000000000
--- a/test/mock/mock_btif_debug_conn.cc
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "btif/include/btif_debug_conn.h"
-#include "stack/include/gatt_api.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void btif_debug_conn_dump(int fd) { mock_function_count_map[__func__]++; }
-void btif_debug_conn_state(const RawAddress& bda,
- const btif_debug_conn_state_t state,
- const tGATT_DISCONN_REASON disconnect_reason) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_btif_dm.cc b/test/mock/mock_btif_dm.cc
deleted file mode 100644
index f65fba00f..000000000
--- a/test/mock/mock_btif_dm.cc
+++ /dev/null
@@ -1,175 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:51
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "bta/include/bta_api.h"
-#include "include/hardware/bluetooth.h"
-#include "internal_include/bte_appl.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
-
-struct uid_set_t;
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool btif_dm_pairing_is_busy() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool check_cod(const RawAddress* remote_bdaddr, uint32_t cod) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool check_cod_hid(const RawAddress* remote_bdaddr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool check_sdp_bl(const RawAddress* remote_bdaddr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bt_status_t btif_dm_get_adapter_property(bt_property_t* prop) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_in_execute_service_request(tBTA_SERVICE_ID service_id,
- bool b_enable) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-uint16_t btif_dm_get_connection_state(const RawAddress* bd_addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void BTIF_dm_disable() { mock_function_count_map[__func__]++; }
-void BTIF_dm_enable() { mock_function_count_map[__func__]++; }
-void BTIF_dm_on_hw_error() { mock_function_count_map[__func__]++; }
-void BTIF_dm_report_inquiry_status_change(uint8_t status) {
- mock_function_count_map[__func__]++;
-}
-void bte_dm_evt(tBTA_DM_SEC_EVT event, tBTA_DM_SEC* p_data) {
- mock_function_count_map[__func__]++;
-}
-void btif_ble_receiver_test(uint8_t rx_freq) {
- mock_function_count_map[__func__]++;
-}
-void btif_ble_test_end() { mock_function_count_map[__func__]++; }
-void btif_ble_transmitter_test(uint8_t tx_freq, uint8_t test_data_len,
- uint8_t packet_payload) {
- mock_function_count_map[__func__]++;
-}
-void btif_debug_bond_event_dump(int fd) { mock_function_count_map[__func__]++; }
-void btif_dm_ble_sec_req_evt(tBTA_DM_BLE_SEC_REQ* p_ble_req, bool is_consent) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_cancel_bond(const RawAddress bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_cancel_discovery(void) { mock_function_count_map[__func__]++; }
-void btif_dm_cleanup(void) { mock_function_count_map[__func__]++; }
-void btif_dm_create_bond(const RawAddress bd_addr, int transport) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_create_bond_out_of_band(const RawAddress bd_addr, int transport,
- const bt_oob_data_t p192_data,
- const bt_oob_data_t p256_data) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_enable_service(tBTA_SERVICE_ID service_id, bool enable) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_get_ble_local_keys(tBTA_DM_BLE_LOCAL_KEY_MASK* p_key_mask,
- Octet16* p_er,
- tBTA_BLE_LOCAL_ID_KEYS* p_id_keys) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_get_remote_services(RawAddress remote_addr, const int transport) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_hh_open_failed(RawAddress* bdaddr) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_init(uid_set_t* set) { mock_function_count_map[__func__]++; }
-void btif_dm_load_ble_local_keys(void) { mock_function_count_map[__func__]++; }
-void btif_dm_on_disable() { mock_function_count_map[__func__]++; }
-void btif_dm_pin_reply(const RawAddress bd_addr, uint8_t accept,
- uint8_t pin_len, bt_pin_code_t pin_code) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_proc_io_req(tBTM_AUTH_REQ* p_auth_req, bool is_orig) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_proc_io_rsp(UNUSED_ATTR const RawAddress& bd_addr,
- tBTM_IO_CAP io_cap, UNUSED_ATTR tBTM_OOB_DATA oob_data,
- tBTM_AUTH_REQ auth_req) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_read_energy_info() { mock_function_count_map[__func__]++; }
-void btif_dm_remove_ble_bonding_keys(void) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_remove_bond(const RawAddress bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_save_ble_bonding_keys(RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_set_oob_for_io_req(tBTM_OOB_DATA* p_has_oob_data) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_set_oob_for_le_io_req(const RawAddress& bd_addr,
- tBTM_OOB_DATA* p_has_oob_data,
- tBTM_LE_AUTH_REQ* p_auth_req) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_ssp_reply(const RawAddress bd_addr, bt_ssp_variant_t variant,
- uint8_t accept) {
- mock_function_count_map[__func__]++;
-}
-void btif_dm_start_discovery(void) { mock_function_count_map[__func__]++; }
-void btif_dm_update_ble_remote_properties(const RawAddress& bd_addr,
- BD_NAME bd_name,
- tBT_DEVICE_TYPE dev_type) {
- mock_function_count_map[__func__]++;
-}
-
-bool btif_dm_get_smp_config(tBTE_APPL_CFG* p_cfg) {
- mock_function_count_map[__func__]++;
- return true;
-}
-
-bool btif_dm_proc_rmt_oob(const RawAddress& bd_addr, Octet16* p_c,
- Octet16* p_r) {
- mock_function_count_map[__func__]++;
- return false;
-}
-
-void btif_dm_proc_loc_oob(tBT_TRANSPORT transport, bool is_valid,
- const Octet16& c, const Octet16& r) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_btif_stack_manager.cc b/test/mock/mock_btif_stack_manager.cc
deleted file mode 100644
index bc07077c6..000000000
--- a/test/mock/mock_btif_stack_manager.cc
+++ /dev/null
@@ -1,25 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- */
-
-#include "osi/include/future.h"
-
-static future_t* hack_future;
-
-future_t* stack_manager_get_hack_future() { return hack_future; }
diff --git a/test/mock/mock_btif_storage.cc b/test/mock/mock_btif_storage.cc
deleted file mode 100644
index 4a700dbd1..000000000
--- a/test/mock/mock_btif_storage.cc
+++ /dev/null
@@ -1,224 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:44
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "bta/include/bta_hearing_aid_api.h"
-#include "stack/include/bt_types.h"
-#include "types/ble_address_with_type.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-Octet16 btif_storage_get_gatt_cl_db_hash(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- Octet16 octet;
- return octet;
-}
-bool btif_has_ble_keys(const std::string& bdstr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btif_storage_get_hearing_aid_prop(
- const RawAddress& address, uint8_t* capabilities, uint64_t* hi_sync_id,
- uint16_t* render_delay, uint16_t* preparation_delay, uint16_t* codecs) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btif_storage_get_stored_remote_name(const RawAddress& bd_addr,
- char* name) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btif_storage_is_restricted_device(const RawAddress* remote_bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bt_status_t btif_storage_add_ble_bonding_key(RawAddress* remote_bd_addr,
- const uint8_t* key,
- uint8_t key_type,
- uint8_t key_length) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_add_ble_local_key(const Octet16& key,
- uint8_t key_type) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_add_bonded_device(RawAddress* remote_bd_addr,
- LinkKey link_key, uint8_t key_type,
- uint8_t pin_length) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_add_hid_device_info(
- RawAddress* remote_bd_addr, uint16_t attr_mask, uint8_t sub_class,
- uint8_t app_id, uint16_t vendor_id, uint16_t product_id, uint16_t version,
- uint8_t ctry_code, uint16_t ssr_max_latency, uint16_t ssr_min_tout,
- uint16_t dl_len, uint8_t* dsc_list) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_add_remote_device(const RawAddress* remote_bd_addr,
- uint32_t num_properties,
- bt_property_t* properties) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_get_adapter_property(bt_property_t* property) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_get_ble_bonding_key(const RawAddress& remote_bd_addr,
- uint8_t key_type,
- uint8_t* key_value,
- int key_length) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_get_ble_local_key(uint8_t key_type,
- Octet16* key_value) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_get_remote_addr_type(const RawAddress* remote_bd_addr,
- tBLE_ADDR_TYPE* addr_type) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_get_remote_device_property(
- const RawAddress* remote_bd_addr, bt_property_t* property) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_load_bonded_devices(void) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_load_bonded_hid_info(void) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_load_hidd(void) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_remove_ble_bonding_keys(
- const RawAddress* remote_bd_addr) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_remove_ble_local_keys(void) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_remove_bonded_device(
- const RawAddress* remote_bd_addr) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_remove_hid_info(const RawAddress& remote_bd_addr) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_remove_hidd(RawAddress* remote_bd_addr) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_set_adapter_property(bt_property_t* property) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_set_hidd(const RawAddress& remote_bd_addr) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_set_remote_addr_type(const RawAddress* remote_bd_addr,
- tBLE_ADDR_TYPE addr_type) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t btif_storage_set_remote_device_property(
- const RawAddress* remote_bd_addr, bt_property_t* property) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-void btif_storage_add_hearing_aid(const HearingDevice& dev_info) {
- mock_function_count_map[__func__]++;
-}
-int btif_storage_get_num_bonded_devices(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-size_t btif_split_uuids_string(const char* str, bluetooth::Uuid* p_uuid,
- size_t max_uuids) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t btif_storage_get_gatt_cl_supp_feat(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t btif_storage_get_local_io_caps() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t btif_storage_get_local_io_caps_ble() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void btif_storage_load_bonded_hearing_aids() {
- mock_function_count_map[__func__]++;
-}
-void btif_storage_remove_gatt_cl_db_hash(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btif_storage_remove_gatt_cl_supp_feat(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btif_storage_remove_hearing_aid(const RawAddress& address) {
- mock_function_count_map[__func__]++;
-}
-void btif_storage_set_gatt_cl_db_hash(const RawAddress& bd_addr, Octet16 hash) {
- mock_function_count_map[__func__]++;
-}
-void btif_storage_set_gatt_cl_supp_feat(const RawAddress& bd_addr,
- uint8_t feat) {
- mock_function_count_map[__func__]++;
-}
-void btif_storage_set_hearing_aid_acceptlist(const RawAddress& address,
- bool add_to_acceptlist) {
- mock_function_count_map[__func__]++;
-}
-void btif_storage_set_gatt_sr_supp_feat(const RawAddress& addr, uint8_t feat) {
- mock_function_count_map[__func__]++;
-}
-uint8_t btif_storage_get_sr_supp_feat(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
diff --git a/test/mock/mock_common_address_obfuscator.cc b/test/mock/mock_common_address_obfuscator.cc
deleted file mode 100644
index 77ff20e0f..000000000
--- a/test/mock/mock_common_address_obfuscator.cc
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:4
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <openssl/hmac.h>
-#include <algorithm>
-#include "bt_trace.h"
-#include "common/address_obfuscator.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace bluetooth {
-namespace common {
-
-bool AddressObfuscator::IsInitialized() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool AddressObfuscator::IsSaltValid(const Octet32& salt_256bit) {
- mock_function_count_map[__func__]++;
- return false;
-}
-std::string AddressObfuscator::Obfuscate(const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void AddressObfuscator::Initialize(const Octet32& salt_256bit) {
- mock_function_count_map[__func__]++;
- salt_256bit_ = salt_256bit;
-}
-
-} // namespace common
-} // namespace bluetooth
diff --git a/test/mock/mock_common_message_loop_thread.cc b/test/mock/mock_common_message_loop_thread.cc
deleted file mode 100644
index 7562a1d2c..000000000
--- a/test/mock/mock_common_message_loop_thread.cc
+++ /dev/null
@@ -1,250 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "common/message_loop_thread.h"
-
-#include <sys/syscall.h>
-#include <unistd.h>
-#include <thread>
-
-#include <base/strings/stringprintf.h>
-
-#include "gd/common/init_flags.h"
-#include "osi/include/log.h"
-
-namespace bluetooth {
-
-namespace common {
-
-static constexpr int kRealTimeFifoSchedulingPriority = 1;
-
-MessageLoopThread::MessageLoopThread(const std::string& thread_name)
- : MessageLoopThread(thread_name, false) {}
-
-MessageLoopThread::MessageLoopThread(const std::string& thread_name,
- bool is_main)
- : thread_name_(thread_name),
- message_loop_(nullptr),
- run_loop_(nullptr),
- thread_(nullptr),
- thread_id_(-1),
- linux_tid_(-1),
- weak_ptr_factory_(this),
- shutting_down_(false),
- is_main_(is_main),
- rust_thread_(nullptr) {}
-
-MessageLoopThread::~MessageLoopThread() { ShutDown(); }
-
-void MessageLoopThread::StartUp() {
- if (is_main_ && init_flags::gd_rust_is_enabled()) {
- rust_thread_ = new ::rust::Box<shim::rust::MessageLoopThread>(
- shim::rust::main_message_loop_thread_create());
- auto rust_id =
- bluetooth::shim::rust::main_message_loop_thread_start(**rust_thread_);
- thread_id_ = rust_id;
- linux_tid_ = rust_id;
- return;
- }
-
- std::promise<void> start_up_promise;
- std::future<void> start_up_future = start_up_promise.get_future();
- {
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- if (thread_ != nullptr) {
- LOG(WARNING) << __func__ << ": thread " << *this << " is already started";
-
- return;
- }
- thread_ = new std::thread(&MessageLoopThread::RunThread, this,
- std::move(start_up_promise));
- }
- start_up_future.wait();
-}
-
-bool MessageLoopThread::DoInThread(const base::Location& from_here,
- base::OnceClosure task) {
- return DoInThreadDelayed(from_here, std::move(task), base::TimeDelta());
-}
-
-bool MessageLoopThread::DoInThreadDelayed(const base::Location& from_here,
- base::OnceClosure task,
- const base::TimeDelta& delay) {
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- if (is_main_ && init_flags::gd_rust_is_enabled()) {
- if (rust_thread_ == nullptr) {
- LOG(ERROR) << __func__ << ": rust thread is null for thread " << *this
- << ", from " << from_here.ToString();
- return false;
- }
-
- shim::rust::main_message_loop_thread_do_delayed(
- **rust_thread_,
- std::make_unique<shim::rust::OnceClosure>(std::move(task)),
- delay.InMilliseconds());
- return true;
- }
-
- if (message_loop_ == nullptr) {
- LOG(ERROR) << __func__ << ": message loop is null for thread " << *this
- << ", from " << from_here.ToString();
- return false;
- }
- if (!message_loop_->task_runner()->PostDelayedTask(from_here, std::move(task),
- delay)) {
- LOG(ERROR) << __func__
- << ": failed to post task to message loop for thread " << *this
- << ", from " << from_here.ToString();
- return false;
- }
- return true;
-}
-
-void MessageLoopThread::ShutDown() {
- {
- if (is_main_ && init_flags::gd_rust_is_enabled()) {
- delete rust_thread_;
- thread_id_ = -1;
- linux_tid_ = -1;
- return;
- }
-
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- if (thread_ == nullptr) {
- LOG(INFO) << __func__ << ": thread " << *this << " is already stopped";
- return;
- }
- if (message_loop_ == nullptr) {
- LOG(INFO) << __func__ << ": message_loop_ is null. Already stopping";
- return;
- }
- if (shutting_down_) {
- LOG(INFO) << __func__ << ": waiting for thread to join";
- return;
- }
- shutting_down_ = true;
- CHECK_NE(thread_id_, base::PlatformThread::CurrentId())
- << __func__ << " should not be called on the thread itself. "
- << "Otherwise, deadlock may happen.";
- if (!message_loop_->task_runner()->PostTask(
- FROM_HERE, run_loop_->QuitWhenIdleClosure())) {
- LOG(FATAL) << __func__
- << ": failed to post task to message loop for thread "
- << *this;
- }
- }
- thread_->join();
- {
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- delete thread_;
- thread_ = nullptr;
- shutting_down_ = false;
- }
-}
-
-base::PlatformThreadId MessageLoopThread::GetThreadId() const {
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- return thread_id_;
-}
-
-std::string MessageLoopThread::GetName() const { return thread_name_; }
-
-std::string MessageLoopThread::ToString() const {
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- return base::StringPrintf("%s(%d)", thread_name_.c_str(), thread_id_);
-}
-
-bool MessageLoopThread::IsRunning() const {
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- return thread_id_ != -1;
-}
-
-// Non API method, should not be protected by API mutex
-void MessageLoopThread::RunThread(MessageLoopThread* thread,
- std::promise<void> start_up_promise) {
- thread->Run(std::move(start_up_promise));
-}
-
-btbase::AbstractMessageLoop* MessageLoopThread::message_loop() const {
- ASSERT_LOG(!is_main_,
- "you are not allowed to get the main thread's message loop");
-
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- return message_loop_;
-}
-
-bool MessageLoopThread::EnableRealTimeScheduling() {
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
-
- if (!IsRunning()) {
- LOG(ERROR) << __func__ << ": thread " << *this << " is not running";
- return false;
- }
-
- struct sched_param rt_params = {.sched_priority =
- kRealTimeFifoSchedulingPriority};
- int rc = sched_setscheduler(linux_tid_, SCHED_FIFO, &rt_params);
- if (rc != 0) {
- LOG(ERROR) << __func__ << ": unable to set SCHED_FIFO priority "
- << kRealTimeFifoSchedulingPriority << " for linux_tid "
- << std::to_string(linux_tid_) << ", thread " << *this
- << ", error: " << strerror(errno);
- return false;
- }
- return true;
-}
-
-base::WeakPtr<MessageLoopThread> MessageLoopThread::GetWeakPtr() {
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- return weak_ptr_factory_.GetWeakPtr();
-}
-
-void MessageLoopThread::Run(std::promise<void> start_up_promise) {
- {
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- if (is_main_ && init_flags::gd_rust_is_enabled()) {
- return;
- }
-
- LOG(INFO) << __func__ << ": message loop starting for thread "
- << thread_name_;
- base::PlatformThread::SetName(thread_name_);
- message_loop_ = new btbase::AbstractMessageLoop();
- run_loop_ = new base::RunLoop();
- thread_id_ = base::PlatformThread::CurrentId();
- linux_tid_ = static_cast<pid_t>(syscall(SYS_gettid));
- start_up_promise.set_value();
- }
-
- // Blocking until ShutDown() is called
- run_loop_->Run();
-
- {
- std::lock_guard<std::recursive_mutex> api_lock(api_mutex_);
- thread_id_ = -1;
- linux_tid_ = -1;
- delete message_loop_;
- message_loop_ = nullptr;
- delete run_loop_;
- run_loop_ = nullptr;
- LOG(INFO) << __func__ << ": message loop finished for thread "
- << thread_name_;
- }
-}
-
-} // namespace common
-
-} // namespace bluetooth
diff --git a/test/mock/mock_common_metric_id_allocator.cc b/test/mock/mock_common_metric_id_allocator.cc
deleted file mode 100644
index c374db1f4..000000000
--- a/test/mock/mock_common_metric_id_allocator.cc
+++ /dev/null
@@ -1,104 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:11
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <functional>
-#include <mutex>
-#include <thread>
-#include "common/metric_id_allocator.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace {
-
-const size_t paired_device_cache_capacity{10};
-const std::string paired_device_cache_log_tag("Mock");
-} // namespace
-
-namespace bluetooth {
-namespace common {
-
-const int MetricIdAllocator::kMinId = 0;
-
-MetricIdAllocator::MetricIdAllocator()
- : paired_device_cache_(paired_device_cache_capacity,
- paired_device_cache_log_tag),
- temporary_device_cache_(paired_device_cache_capacity,
- paired_device_cache_log_tag) {
- next_id_ = 0;
- initialized_ = true;
-}
-
-class MockMetricIdAllocator : public MetricIdAllocator {
- public:
- MockMetricIdAllocator() {}
-};
-
-MockMetricIdAllocator metric_id_allocator;
-
-MetricIdAllocator& MetricIdAllocator::GetInstance() {
- mock_function_count_map[__func__]++;
- return metric_id_allocator;
-}
-MetricIdAllocator::~MetricIdAllocator() {}
-bool MetricIdAllocator::Close() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool MetricIdAllocator::Init(
- const std::unordered_map<RawAddress, int>& paired_device_map,
- Callback save_id_callback, Callback forget_device_callback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool MetricIdAllocator::IsEmpty() const {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool MetricIdAllocator::IsValidId(const int id) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool MetricIdAllocator::SaveDevice(const RawAddress& mac_address) {
- mock_function_count_map[__func__]++;
- return false;
-}
-int MetricIdAllocator::AllocateId(const RawAddress& mac_address) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void MetricIdAllocator::ForgetDevice(const RawAddress& mac_address) {
- mock_function_count_map[__func__]++;
-}
-void MetricIdAllocator::ForgetDevicePostprocess(const RawAddress& mac_address,
- const int id) {
- mock_function_count_map[__func__]++;
-}
-
-} // namespace common
-} // namespace bluetooth
diff --git a/test/mock/mock_common_metrics.cc b/test/mock/mock_common_metrics.cc
deleted file mode 100644
index 01612fb8b..000000000
--- a/test/mock/mock_common_metrics.cc
+++ /dev/null
@@ -1,207 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:36
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "common/metrics.h"
-
-#if 0
-#include <base/base64.h>
-#include <base/logging.h>
-#include <include/hardware/bt_av.h>
-#include <statslog.h>
-#include <unistd.h>
-#include <algorithm>
-#include <array>
-#include <cerrno>
-#include <chrono>
-#include <cstdint>
-#include <cstring>
-#include <memory>
-#include <mutex>
-#include "address_obfuscator.h"
-#include "bluetooth/metrics/bluetooth.pb.h"
-#include "leaky_bonded_queue.h"
-#include "metric_id_allocator.h"
-#include "osi/include/osi.h"
-#include "stack/include/btm_api_types.h"
-#include "time_util.h"
-#endif
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace bluetooth {
-namespace common {
-
-void A2dpSessionMetrics::Update(const A2dpSessionMetrics& metrics) {
- mock_function_count_map[__func__]++;
-}
-
-struct BluetoothMetricsLogger::impl {
- int mock{123};
-};
-
-BluetoothMetricsLogger::BluetoothMetricsLogger() {}
-void BluetoothMetricsLogger::Build() { mock_function_count_map[__func__]++; }
-void BluetoothMetricsLogger::CutoffSession() {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::LogA2dpSession(
- const A2dpSessionMetrics& a2dp_session_metrics) {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::LogBluetoothSessionDeviceInfo(
- uint32_t device_class, device_type_t device_type) {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::LogBluetoothSessionEnd(
- disconnect_reason_t disconnect_reason, uint64_t timestamp_ms) {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::LogBluetoothSessionStart(
- connection_tech_t connection_tech_type, uint64_t timestamp_ms) {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::LogHeadsetProfileRfcConnection(
- tBTA_SERVICE_ID service_id) {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::LogPairEvent(uint32_t disconnect_reason,
- uint64_t timestamp_ms,
- uint32_t device_class,
- device_type_t device_type) {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::LogScanEvent(bool start,
- const std::string& initator,
- scan_tech_t type, uint32_t results,
- uint64_t timestamp_ms) {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::LogWakeEvent(wake_event_type_t type,
- const std::string& requestor,
- const std::string& name,
- uint64_t timestamp_ms) {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::Reset() { mock_function_count_map[__func__]++; }
-void BluetoothMetricsLogger::ResetLog() { mock_function_count_map[__func__]++; }
-void BluetoothMetricsLogger::ResetSession() {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::WriteBase64(int fd) {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::WriteBase64String(std::string* serialized) {
- mock_function_count_map[__func__]++;
-}
-void BluetoothMetricsLogger::WriteString(std::string* serialized) {
- mock_function_count_map[__func__]++;
-}
-void LogA2dpAudioOverrunEvent(const RawAddress& address,
- uint64_t encoding_interval_millis,
- int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes) {
- mock_function_count_map[__func__]++;
-}
-void LogA2dpAudioUnderrunEvent(const RawAddress& address,
- uint64_t encoding_interval_millis,
- int num_missing_pcm_bytes) {
- mock_function_count_map[__func__]++;
-}
-void LogA2dpPlaybackEvent(const RawAddress& address, int playback_state,
- int audio_coding_mode) {
- mock_function_count_map[__func__]++;
-}
-void LogBluetoothHalCrashReason(const RawAddress& address, uint32_t error_code,
- uint32_t vendor_error_code) {
- mock_function_count_map[__func__]++;
-}
-void LogClassicPairingEvent(const RawAddress& address, uint16_t handle,
- uint32_t hci_cmd, uint16_t hci_event,
- uint16_t cmd_status, uint16_t reason_code,
- int64_t event_value) {
- mock_function_count_map[__func__]++;
-}
-void LogHciTimeoutEvent(uint32_t hci_cmd) {
- mock_function_count_map[__func__]++;
-}
-void LogLinkLayerConnectionEvent(const RawAddress* address,
- uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction,
- uint16_t link_type, uint32_t hci_cmd,
- uint16_t hci_event, uint16_t hci_ble_event,
- uint16_t cmd_status, uint16_t reason_code) {
- mock_function_count_map[__func__]++;
-}
-void LogManufacturerInfo(const RawAddress& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer,
- const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version) {
- mock_function_count_map[__func__]++;
-}
-void LogReadFailedContactCounterResult(const RawAddress& address,
- uint16_t handle, uint32_t cmd_status,
- int32_t failed_contact_counter) {
- mock_function_count_map[__func__]++;
-}
-void LogReadRssiResult(const RawAddress& address, uint16_t handle,
- uint32_t cmd_status, int8_t rssi) {
- mock_function_count_map[__func__]++;
-}
-void LogReadTxPowerLevelResult(const RawAddress& address, uint16_t handle,
- uint32_t cmd_status,
- int32_t transmit_power_level) {
- mock_function_count_map[__func__]++;
-}
-void LogRemoteVersionInfo(uint16_t handle, uint8_t status, uint8_t version,
- uint16_t manufacturer_name, uint16_t subversion) {
- mock_function_count_map[__func__]++;
-}
-void LogSdpAttribute(const RawAddress& address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value) {
- mock_function_count_map[__func__]++;
-}
-void LogSmpPairingEvent(const RawAddress& address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason) {
- mock_function_count_map[__func__]++;
-}
-void LogSocketConnectionState(
- const RawAddress& address, int port, int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes, int64_t rx_bytes, int uid, int server_port,
- android::bluetooth::SocketRoleEnum socket_role) {
- mock_function_count_map[__func__]++;
-}
-
-} // namespace common
-} // namespace bluetooth
diff --git a/test/mock/mock_common_repeating_timer.cc b/test/mock/mock_common_repeating_timer.cc
deleted file mode 100644
index f92e31626..000000000
--- a/test/mock/mock_common_repeating_timer.cc
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:8
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "common/message_loop_thread.h"
-#include "common/repeating_timer.h"
-#include "common/time_util.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-using namespace bluetooth::common;
-
-RepeatingTimer::~RepeatingTimer() { mock_function_count_map[__func__]++; }
-bool RepeatingTimer::IsScheduled() const {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool RepeatingTimer::SchedulePeriodic(
- const base::WeakPtr<MessageLoopThread>& thread,
- const base::Location& from_here, base::Closure task,
- base::TimeDelta period) {
- mock_function_count_map[__func__]++;
- return false;
-}
-void RepeatingTimer::Cancel() {
- mock_function_count_map[__func__]++;
- expected_time_next_task_us_ = 0;
-}
-void RepeatingTimer::CancelAndWait() { mock_function_count_map[__func__]++; }
-void RepeatingTimer::CancelClosure(std::promise<void> promise) {
- mock_function_count_map[__func__]++;
-}
-void RepeatingTimer::CancelHelper(std::promise<void> promise) {
- mock_function_count_map[__func__]++;
-}
-void RepeatingTimer::RunTask() { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_common_stop_watch_legacy.cc b/test/mock/mock_common_stop_watch_legacy.cc
deleted file mode 100644
index 534c537ac..000000000
--- a/test/mock/mock_common_stop_watch_legacy.cc
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:4
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <iomanip>
-#include <sstream>
-#include <utility>
-#include "common/stop_watch_legacy.h"
-#include "osi/include/log.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace bluetooth {
-namespace common {
-
-StopWatchLegacy::StopWatchLegacy(std::string text)
- : text_(std::move(text)),
- timestamp_(std::chrono::system_clock::now()),
- start_timestamp_(std::chrono::high_resolution_clock::now()) {
- mock_function_count_map[__func__]++;
-}
-StopWatchLegacy::~StopWatchLegacy() { mock_function_count_map[__func__]++; }
-void StopWatchLegacy::DumpStopWatchLog() {
- mock_function_count_map[__func__]++;
-}
-void StopWatchLegacy::RecordLog(StopWatchLog log) {
- mock_function_count_map[__func__]++;
-}
-
-} // namespace common
-} // namespace bluetooth
diff --git a/test/mock/mock_common_time_util.cc b/test/mock/mock_common_time_util.cc
deleted file mode 100644
index e29368e8b..000000000
--- a/test/mock/mock_common_time_util.cc
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <sys/time.h>
-#include <time.h>
-#include "common/time_util.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace bluetooth {
-namespace common {
-
-uint64_t time_get_os_boottime_ms() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint64_t time_get_os_boottime_us() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint64_t time_gettimeofday_us() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-
-} // namespace common
-} // namespace bluetooth
diff --git a/test/mock/mock_device_controller.cc b/test/mock/mock_device_controller.cc
deleted file mode 100644
index 1d087b5bc..000000000
--- a/test/mock/mock_device_controller.cc
+++ /dev/null
@@ -1,460 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:1
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include "bt_types.h"
-#include "main/shim/controller.h"
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_device_controller.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-namespace test {
-namespace mock {
-namespace device_controller {
-
-RawAddress address;
-bt_version_t bt_version = {
- .hci_version = 0,
- .hci_revision = 0,
- .lmp_version = 0,
- .manufacturer = 0,
- .lmp_subversion = 0,
-};
-
-uint8_t supported_commands[HCI_SUPPORTED_COMMANDS_ARRAY_SIZE]{0};
-bt_device_features_t features_classic[MAX_FEATURES_CLASSIC_PAGE_COUNT] = {{
- .as_array{0},
-}};
-uint8_t last_features_classic_page_index{0};
-
-uint16_t acl_data_size_classic{0};
-uint16_t acl_data_size_ble{0};
-uint16_t iso_data_size{0};
-
-uint16_t acl_buffer_count_classic{0};
-uint8_t acl_buffer_count_ble{0};
-uint8_t iso_buffer_count{0};
-
-uint8_t ble_acceptlist_size{0};
-uint8_t ble_resolving_list_max_size{0};
-uint8_t ble_supported_states[BLE_SUPPORTED_STATES_SIZE]{0};
-bt_device_features_t features_ble{0};
-uint16_t ble_suggested_default_data_length{0};
-uint16_t ble_supported_max_tx_octets{0};
-uint16_t ble_supported_max_tx_time{0};
-uint16_t ble_supported_max_rx_octets{0};
-uint16_t ble_supported_max_rx_time{0};
-
-uint16_t ble_maxium_advertising_data_length{0};
-uint8_t ble_number_of_supported_advertising_sets{0};
-uint8_t ble_periodic_advertiser_list_size{0};
-uint8_t local_supported_codecs[MAX_LOCAL_SUPPORTED_CODECS_SIZE]{0};
-uint8_t number_of_local_supported_codecs{0};
-
-bool readable{false};
-bool ble_supported{false};
-bool iso_supported{false};
-bool simple_pairing_supported{false};
-bool secure_connections_supported{false};
-
-bool get_is_ready(void) { return readable; }
-
-const RawAddress* get_address(void) { return &address; }
-
-const bt_version_t* get_bt_version(void) { return &bt_version; }
-
-uint8_t* get_local_supported_codecs(uint8_t* number_of_codecs) {
- if (number_of_local_supported_codecs) {
- *number_of_codecs = number_of_local_supported_codecs;
- return local_supported_codecs;
- }
- return NULL;
-}
-
-const uint8_t* get_ble_supported_states(void) { return ble_supported_states; }
-
-bool supports_simple_pairing(void) { return simple_pairing_supported; }
-
-bool supports_secure_connections(void) { return secure_connections_supported; }
-
-bool supports_simultaneous_le_bredr(void) {
- return HCI_SIMUL_LE_BREDR_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_reading_remote_extended_features(void) {
- return HCI_READ_REMOTE_EXT_FEATURES_SUPPORTED(supported_commands);
-}
-
-bool supports_interlaced_inquiry_scan(void) {
- return HCI_LMP_INTERLACED_INQ_SCAN_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_rssi_with_inquiry_results(void) {
- return HCI_LMP_INQ_RSSI_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_extended_inquiry_response(void) {
- return HCI_EXT_INQ_RSP_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_central_peripheral_role_switch(void) {
- return HCI_SWITCH_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_enhanced_setup_synchronous_connection(void) {
- return HCI_ENH_SETUP_SYNCH_CONN_SUPPORTED(supported_commands);
-}
-
-bool supports_enhanced_accept_synchronous_connection(void) {
- return HCI_ENH_ACCEPT_SYNCH_CONN_SUPPORTED(supported_commands);
-}
-
-bool supports_3_slot_packets(void) {
- return HCI_3_SLOT_PACKETS_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_5_slot_packets(void) {
- return HCI_5_SLOT_PACKETS_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_classic_2m_phy(void) {
- return HCI_EDR_ACL_2MPS_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_classic_3m_phy(void) {
- return HCI_EDR_ACL_3MPS_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_3_slot_edr_packets(void) {
- return HCI_3_SLOT_EDR_ACL_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_5_slot_edr_packets(void) {
- return HCI_5_SLOT_EDR_ACL_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_sco(void) {
- return HCI_SCO_LINK_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_hv2_packets(void) {
- return HCI_HV2_PACKETS_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_hv3_packets(void) {
- return HCI_HV3_PACKETS_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_ev3_packets(void) {
- return HCI_ESCO_EV3_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_ev4_packets(void) {
- return HCI_ESCO_EV4_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_ev5_packets(void) {
- return HCI_ESCO_EV5_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_esco_2m_phy(void) {
- return HCI_EDR_ESCO_2MPS_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_esco_3m_phy(void) {
- return HCI_EDR_ESCO_3MPS_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_3_slot_esco_edr_packets(void) {
- return HCI_3_SLOT_EDR_ESCO_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_role_switch(void) {
- return HCI_SWITCH_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_hold_mode(void) {
- return HCI_HOLD_MODE_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_sniff_mode(void) {
- return HCI_SNIFF_MODE_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_park_mode(void) {
- return HCI_PARK_MODE_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_non_flushable_pb(void) {
- return HCI_NON_FLUSHABLE_PB_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_sniff_subrating(void) {
- return HCI_SNIFF_SUB_RATE_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_encryption_pause(void) {
- return HCI_ATOMIC_ENCRYPT_SUPPORTED(features_classic[0].as_array);
-}
-
-bool supports_ble(void) { return ble_supported; }
-
-bool supports_ble_privacy(void) {
- return HCI_LE_ENHANCED_PRIVACY_SUPPORTED(features_ble.as_array);
-}
-
-bool supports_ble_set_privacy_mode() {
- return HCI_LE_ENHANCED_PRIVACY_SUPPORTED(features_ble.as_array) &&
- HCI_LE_SET_PRIVACY_MODE_SUPPORTED(supported_commands);
-}
-
-bool supports_ble_packet_extension(void) {
- return HCI_LE_DATA_LEN_EXT_SUPPORTED(features_ble.as_array);
-}
-
-bool supports_ble_connection_parameters_request(void) {
- return HCI_LE_CONN_PARAM_REQ_SUPPORTED(features_ble.as_array);
-}
-
-bool supports_ble_2m_phy(void) {
- return HCI_LE_2M_PHY_SUPPORTED(features_ble.as_array);
-}
-
-bool supports_ble_coded_phy(void) {
- return HCI_LE_CODED_PHY_SUPPORTED(features_ble.as_array);
-}
-
-bool supports_ble_extended_advertising(void) {
- return HCI_LE_EXTENDED_ADVERTISING_SUPPORTED(features_ble.as_array);
-}
-
-bool supports_ble_periodic_advertising(void) {
- return HCI_LE_PERIODIC_ADVERTISING_SUPPORTED(features_ble.as_array);
-}
-
-bool supports_ble_peripheral_initiated_feature_exchange(void) {
- return HCI_LE_PERIPHERAL_INIT_FEAT_EXC_SUPPORTED(features_ble.as_array);
-}
-
-bool supports_ble_connection_parameter_request(void) {
- return HCI_LE_CONN_PARAM_REQ_SUPPORTED(features_ble.as_array);
-}
-
-bool supports_ble_periodic_advertising_sync_transfer_sender(void) {
- return HCI_LE_PERIODIC_ADVERTISING_SYNC_TRANSFER_SENDER(
- features_ble.as_array);
-}
-
-bool supports_ble_periodic_advertising_sync_transfer_recipient(void) {
- return HCI_LE_PERIODIC_ADVERTISING_SYNC_TRANSFER_RECIPIENT(
- features_ble.as_array);
-}
-
-bool supports_ble_connected_isochronous_stream_central(void) {
- return HCI_LE_CIS_CENTRAL(features_ble.as_array);
-}
-
-bool supports_ble_connected_isochronous_stream_peripheral(void) {
- return HCI_LE_CIS_PERIPHERAL(features_ble.as_array);
-}
-
-bool supports_ble_isochronous_broadcaster(void) {
- return HCI_LE_ISO_BROADCASTER(features_ble.as_array);
-}
-
-bool supports_ble_synchronized_receiver(void) {
- return HCI_LE_SYNCHRONIZED_RECEIVER(features_ble.as_array);
-}
-
-uint16_t get_acl_data_size_classic(void) { return acl_data_size_classic; }
-
-uint16_t get_acl_data_size_ble(void) { return acl_data_size_ble; }
-
-uint16_t get_iso_data_size(void) { return iso_data_size; }
-
-uint16_t get_acl_packet_size_classic(void) {
- return acl_data_size_classic + HCI_DATA_PREAMBLE_SIZE;
-}
-
-uint16_t get_acl_packet_size_ble(void) {
- return acl_data_size_ble + HCI_DATA_PREAMBLE_SIZE;
-}
-
-uint16_t get_iso_packet_size(void) {
- return iso_data_size + HCI_DATA_PREAMBLE_SIZE;
-}
-
-uint16_t get_ble_suggested_default_data_length(void) {
- return ble_suggested_default_data_length;
-}
-
-uint16_t get_ble_maximum_tx_data_length(void) {
- return ble_supported_max_tx_octets;
-}
-
-uint16_t get_ble_maximum_tx_time(void) { return ble_supported_max_tx_time; }
-
-uint16_t get_ble_maxium_advertising_data_length(void) {
- return ble_maxium_advertising_data_length;
-}
-
-uint8_t get_ble_number_of_supported_advertising_sets(void) {
- return ble_number_of_supported_advertising_sets;
-}
-
-uint8_t get_ble_periodic_advertiser_list_size(void) {
- return ble_periodic_advertiser_list_size;
-}
-
-uint16_t get_acl_buffer_count_classic(void) { return acl_buffer_count_classic; }
-
-uint8_t get_acl_buffer_count_ble(void) { return acl_buffer_count_ble; }
-
-uint8_t get_iso_buffer_count(void) { return iso_buffer_count; }
-
-uint8_t get_ble_acceptlist_size(void) { return ble_acceptlist_size; }
-
-uint8_t get_ble_resolving_list_max_size(void) {
- return ble_resolving_list_max_size;
-}
-
-void set_ble_resolving_list_max_size(int resolving_list_max_size) {
- ble_resolving_list_max_size = resolving_list_max_size;
-}
-
-uint8_t get_le_all_initiating_phys() {
- uint8_t phy = PHY_LE_1M;
- return phy;
-}
-
-const controller_t interface = {
- get_is_ready,
-
- get_address,
- get_bt_version,
-
- get_ble_supported_states,
-
- supports_simple_pairing,
- supports_secure_connections,
- supports_simultaneous_le_bredr,
- supports_reading_remote_extended_features,
- supports_interlaced_inquiry_scan,
- supports_rssi_with_inquiry_results,
- supports_extended_inquiry_response,
- supports_central_peripheral_role_switch,
- supports_enhanced_setup_synchronous_connection,
- supports_enhanced_accept_synchronous_connection,
- supports_3_slot_packets,
- supports_5_slot_packets,
- supports_classic_2m_phy,
- supports_classic_3m_phy,
- supports_3_slot_edr_packets,
- supports_5_slot_edr_packets,
- supports_sco,
- supports_hv2_packets,
- supports_hv3_packets,
- supports_ev3_packets,
- supports_ev4_packets,
- supports_ev5_packets,
- supports_esco_2m_phy,
- supports_esco_3m_phy,
- supports_3_slot_esco_edr_packets,
- supports_role_switch,
- supports_hold_mode,
- supports_sniff_mode,
- supports_park_mode,
- supports_non_flushable_pb,
- supports_sniff_subrating,
- supports_encryption_pause,
-
- supports_ble,
- supports_ble_packet_extension,
- supports_ble_connection_parameters_request,
- supports_ble_privacy,
- supports_ble_set_privacy_mode,
- supports_ble_2m_phy,
- supports_ble_coded_phy,
- supports_ble_extended_advertising,
- supports_ble_periodic_advertising,
- supports_ble_peripheral_initiated_feature_exchange,
- supports_ble_connection_parameter_request,
- supports_ble_periodic_advertising_sync_transfer_sender,
- supports_ble_periodic_advertising_sync_transfer_recipient,
- supports_ble_connected_isochronous_stream_central,
- supports_ble_connected_isochronous_stream_peripheral,
- supports_ble_isochronous_broadcaster,
- supports_ble_synchronized_receiver,
-
- get_acl_data_size_classic,
- get_acl_data_size_ble,
- get_iso_data_size,
-
- get_acl_packet_size_classic,
- get_acl_packet_size_ble,
- get_iso_packet_size,
-
- get_ble_suggested_default_data_length,
- get_ble_maximum_tx_data_length,
- get_ble_maximum_tx_time,
- get_ble_maxium_advertising_data_length,
- get_ble_number_of_supported_advertising_sets,
- get_ble_periodic_advertiser_list_size,
-
- get_acl_buffer_count_classic,
- get_acl_buffer_count_ble,
- get_iso_buffer_count,
-
- get_ble_acceptlist_size,
-
- get_ble_resolving_list_max_size,
- set_ble_resolving_list_max_size,
- get_local_supported_codecs,
- get_le_all_initiating_phys};
-
-} // namespace device_controller
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-const controller_t* controller_get_interface() {
- return &test::mock::device_controller::interface;
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_device_controller.h b/test/mock/mock_device_controller.h
deleted file mode 100644
index 3417910e5..000000000
--- a/test/mock/mock_device_controller.h
+++ /dev/null
@@ -1,101 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:1
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include <base/logging.h>
-#include "bt_types.h"
-#include "btcore/include/event_mask.h"
-#include "btcore/include/module.h"
-#include "btcore/include/version.h"
-#include "device/include/controller.h"
-#include "hcimsgs.h"
-#include "main/shim/controller.h"
-#include "main/shim/shim.h"
-#include "osi/include/future.h"
-#include "osi/include/properties.h"
-#include "stack/include/btm_ble_api.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace device_controller {
-
-constexpr size_t HCI_SUPPORTED_COMMANDS_ARRAY_SIZE = 64;
-constexpr size_t MAX_FEATURES_CLASSIC_PAGE_COUNT = 3;
-constexpr size_t BLE_SUPPORTED_STATES_SIZE = 8;
-constexpr size_t MAX_LOCAL_SUPPORTED_CODECS_SIZE = 8;
-
-// Shared state between mocked functions and tests
-extern uint8_t supported_commands[HCI_SUPPORTED_COMMANDS_ARRAY_SIZE];
-extern bt_device_features_t features_classic[MAX_FEATURES_CLASSIC_PAGE_COUNT];
-extern uint8_t last_features_classic_page_index;
-
-extern uint16_t acl_data_size_classic;
-extern uint16_t acl_data_size_ble;
-extern uint16_t iso_data_size;
-
-extern uint16_t acl_buffer_count_classic;
-extern uint8_t acl_buffer_count_ble;
-extern uint8_t iso_buffer_count;
-
-extern uint8_t ble_acceptlist_size;
-extern uint8_t ble_resolving_list_max_size;
-extern uint8_t ble_supported_states[BLE_SUPPORTED_STATES_SIZE];
-extern bt_device_features_t features_ble;
-extern uint16_t ble_suggested_default_data_length;
-extern uint16_t ble_supported_max_tx_octets;
-extern uint16_t ble_supported_max_tx_time;
-extern uint16_t ble_supported_max_rx_octets;
-extern uint16_t ble_supported_max_rx_time;
-
-extern uint16_t ble_maxium_advertising_data_length;
-extern uint8_t ble_number_of_supported_advertising_sets;
-extern uint8_t ble_periodic_advertiser_list_size;
-extern uint8_t local_supported_codecs[MAX_LOCAL_SUPPORTED_CODECS_SIZE];
-extern uint8_t number_of_local_supported_codecs;
-
-extern bool readable;
-extern bool ble_supported;
-extern bool iso_supported;
-extern bool simple_pairing_supported;
-extern bool secure_connections_supported;
-
-} // namespace device_controller
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_device_interop.cc b/test/mock/mock_device_interop.cc
deleted file mode 100644
index 7afb53a0d..000000000
--- a/test/mock/mock_device_interop.cc
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:6
- */
-
-#include <cstddef>
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "device/include/interop.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool interop_match_addr(const interop_feature_t feature,
- const RawAddress* addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool interop_match_name(const interop_feature_t feature, const char* name) {
- mock_function_count_map[__func__]++;
- return false;
-}
-void interop_database_add(uint16_t feature, const RawAddress* addr,
- size_t length) {
- mock_function_count_map[__func__]++;
-}
-void interop_database_clear() { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_frameworks_libaudio.cc b/test/mock/mock_frameworks_libaudio.cc
deleted file mode 100644
index e4f55d419..000000000
--- a/test/mock/mock_frameworks_libaudio.cc
+++ /dev/null
@@ -1,305 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:60
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#undef __INTRODUCED_IN
-#define __INTRODUCED_IN(x)
-
-#include <aaudio/AAudio.h>
-#include <aaudio/AAudioTesting.h>
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-aaudio_allowed_capture_policy_t AAudioStream_getAllowedCapturePolicy(
- AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_content_type_t AAudioStream_getContentType(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_direction_t AAudioStream_getDirection(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_format_t AAudioStream_getFormat(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_input_preset_t AAudioStream_getInputPreset(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_performance_mode_t AAudioStream_getPerformanceMode(
- AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_policy_t AAudio_getMMapPolicy() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStreamBuilder_delete(AAudioStreamBuilder* builder) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStreamBuilder_openStream(AAudioStreamBuilder* builder,
- AAudioStream** streamPtr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStream_close(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStream_getTimestamp(AAudioStream* stream,
- clockid_t clockid,
- int64_t* framePosition,
- int64_t* timeNanoseconds) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStream_read(AAudioStream* stream, void* buffer,
- int32_t numFrames,
- int64_t timeoutNanoseconds) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStream_release(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStream_requestFlush(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStream_requestPause(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStream_requestStart(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStream_requestStop(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStream_setBufferSizeInFrames(AAudioStream* stream,
- int32_t requestedFrames) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStream_waitForStateChange(
- AAudioStream* stream, aaudio_stream_state_t inputState,
- aaudio_stream_state_t* nextState, int64_t timeoutNanoseconds) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudioStream_write(AAudioStream* stream, const void* buffer,
- int32_t numFrames,
- int64_t timeoutNanoseconds) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudio_createStreamBuilder(AAudioStreamBuilder** builder) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_result_t AAudio_setMMapPolicy(aaudio_policy_t policy) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_sharing_mode_t AAudioStream_getSharingMode(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_stream_state_t AAudioStream_getState(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-aaudio_usage_t AAudioStream_getUsage(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-bool AAudioStream_isMMapUsed(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool AAudioStream_isPrivacySensitive(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return false;
-}
-const char* AAudio_convertResultToText(aaudio_result_t returnCode) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const char* AAudio_convertStreamStateToText(aaudio_stream_state_t state) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-int32_t AAudioStream_getBufferCapacityInFrames(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int32_t AAudioStream_getBufferSizeInFrames(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int32_t AAudioStream_getChannelCount(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int32_t AAudioStream_getDeviceId(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int32_t AAudioStream_getFramesPerBurst(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int32_t AAudioStream_getFramesPerDataCallback(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int32_t AAudioStream_getSampleRate(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int32_t AAudioStream_getSamplesPerFrame(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int32_t AAudioStream_getSessionId(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int32_t AAudioStream_getXRunCount(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int64_t AAudioStream_getFramesRead(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int64_t AAudioStream_getFramesWritten(AAudioStream* stream) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void AAudioStreamBuilder_setAllowedCapturePolicy(
- AAudioStreamBuilder* builder, aaudio_allowed_capture_policy_t policy) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setBufferCapacityInFrames(AAudioStreamBuilder* builder,
- int32_t frames) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setChannelCount(AAudioStreamBuilder* builder,
- int32_t channelCount) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setContentType(AAudioStreamBuilder* builder,
- aaudio_content_type_t contentType) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setDataCallback(AAudioStreamBuilder* builder,
- AAudioStream_dataCallback callback,
- void* userData) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setDeviceId(AAudioStreamBuilder* builder,
- int32_t deviceId) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setDirection(AAudioStreamBuilder* builder,
- aaudio_direction_t direction) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setErrorCallback(AAudioStreamBuilder* builder,
- AAudioStream_errorCallback callback,
- void* userData) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setFormat(AAudioStreamBuilder* builder,
- aaudio_format_t format) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setFramesPerDataCallback(AAudioStreamBuilder* builder,
- int32_t frames) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setInputPreset(AAudioStreamBuilder* builder,
- aaudio_input_preset_t inputPreset) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setPerformanceMode(AAudioStreamBuilder* builder,
- aaudio_performance_mode_t mode) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setPrivacySensitive(AAudioStreamBuilder* builder,
- bool privacySensitive) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setSampleRate(AAudioStreamBuilder* builder,
- int32_t sampleRate) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setSamplesPerFrame(AAudioStreamBuilder* builder,
- int32_t samplesPerFrame) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setSessionId(AAudioStreamBuilder* builder,
- aaudio_session_id_t sessionId) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setSharingMode(AAudioStreamBuilder* builder,
- aaudio_sharing_mode_t sharingMode) {
- mock_function_count_map[__func__]++;
- return;
-}
-void AAudioStreamBuilder_setUsage(AAudioStreamBuilder* builder,
- aaudio_usage_t usage) {
- mock_function_count_map[__func__]++;
- return;
-}
diff --git a/test/mock/mock_hci_btsnoop_mem.cc b/test/mock/mock_hci_btsnoop_mem.cc
deleted file mode 100644
index 039a6124a..000000000
--- a/test/mock/mock_hci_btsnoop_mem.cc
+++ /dev/null
@@ -1,43 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include "gd/common/init_flags.h"
-#include "hci/include/btsnoop_mem.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void activity_attribution_set_callback(activity_attribution_cb cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnoop_mem_capture(const BT_HDR* packet, uint64_t timestamp_us) {
- mock_function_count_map[__func__]++;
-}
-void btsnoop_mem_set_callback(btsnoop_data_cb cb) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_hci_layer.cc b/test/mock/mock_hci_layer.cc
deleted file mode 100644
index 771998cac..000000000
--- a/test/mock/mock_hci_layer.cc
+++ /dev/null
@@ -1,126 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:13
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_hci_layer.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-typedef struct {
-} waiting_command_t;
-
-namespace test {
-namespace mock {
-namespace hci_layer {
-
-// Function state capture and return values, if needed
-struct initialization_complete initialization_complete;
-struct hci_event_received hci_event_received;
-struct acl_event_received acl_event_received;
-struct sco_data_received sco_data_received;
-struct iso_data_received iso_data_received;
-struct hal_service_died hal_service_died;
-struct process_command_credits process_command_credits;
-struct hci_is_root_inflammation_event_received
- hci_is_root_inflammation_event_received;
-struct handle_root_inflammation_event handle_root_inflammation_event;
-struct hci_layer_cleanup_interface hci_layer_cleanup_interface;
-struct hci_layer_get_interface hci_layer_get_interface;
-struct hci_layer_get_test_interface hci_layer_get_test_interface;
-
-} // namespace hci_layer
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-void initialization_complete() {
- mock_function_count_map[__func__]++;
- test::mock::hci_layer::initialization_complete();
-}
-void hci_event_received(const base::Location& from_here, BT_HDR* packet) {
- mock_function_count_map[__func__]++;
- test::mock::hci_layer::hci_event_received(from_here, packet);
-}
-void acl_event_received(BT_HDR* packet) {
- mock_function_count_map[__func__]++;
- test::mock::hci_layer::acl_event_received(packet);
-}
-void sco_data_received(BT_HDR* packet) {
- mock_function_count_map[__func__]++;
- test::mock::hci_layer::sco_data_received(packet);
-}
-void iso_data_received(BT_HDR* packet) {
- mock_function_count_map[__func__]++;
- test::mock::hci_layer::iso_data_received(packet);
-}
-void hal_service_died() {
- mock_function_count_map[__func__]++;
- test::mock::hci_layer::hal_service_died();
-}
-void process_command_credits(int credits) {
- mock_function_count_map[__func__]++;
- test::mock::hci_layer::process_command_credits(credits);
-}
-bool hci_is_root_inflammation_event_received() {
- mock_function_count_map[__func__]++;
- return test::mock::hci_layer::hci_is_root_inflammation_event_received();
-}
-void handle_root_inflammation_event() {
- mock_function_count_map[__func__]++;
- test::mock::hci_layer::handle_root_inflammation_event();
-}
-void hci_layer_cleanup_interface() {
- mock_function_count_map[__func__]++;
- test::mock::hci_layer::hci_layer_cleanup_interface();
-}
-const hci_t* hci_layer_get_interface() {
- mock_function_count_map[__func__]++;
- return test::mock::hci_layer::hci_layer_get_interface();
-}
-const hci_t* hci_layer_get_test_interface(
- const allocator_t* buffer_allocator_interface,
- const btsnoop_t* btsnoop_interface,
- const packet_fragmenter_t* packet_fragmenter_interface) {
- mock_function_count_map[__func__]++;
- return test::mock::hci_layer::hci_layer_get_test_interface(
- buffer_allocator_interface, btsnoop_interface,
- packet_fragmenter_interface);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_hci_layer.h b/test/mock/mock_hci_layer.h
deleted file mode 100644
index 80e30ef6d..000000000
--- a/test/mock/mock_hci_layer.h
+++ /dev/null
@@ -1,169 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:13
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-#include "hci/include/hci_layer.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace hci_layer {
-
-// Shared state between mocked functions and tests
-// Name: initialization_complete
-// Params:
-// Returns: void
-struct initialization_complete {
- std::function<void()> body{[]() {}};
- void operator()() { body(); };
-};
-extern struct initialization_complete initialization_complete;
-// Name: hci_event_received
-// Params: const base::Location& from_here, BT_HDR* packet
-// Returns: void
-struct hci_event_received {
- std::function<void(const base::Location& from_here, BT_HDR* packet)> body{
- [](const base::Location& from_here, BT_HDR* packet) {}};
- void operator()(const base::Location& from_here, BT_HDR* packet) {
- body(from_here, packet);
- };
-};
-extern struct hci_event_received hci_event_received;
-// Name: acl_event_received
-// Params: BT_HDR* packet
-// Returns: void
-struct acl_event_received {
- std::function<void(BT_HDR* packet)> body{[](BT_HDR* packet) {}};
- void operator()(BT_HDR* packet) { body(packet); };
-};
-extern struct acl_event_received acl_event_received;
-// Name: sco_data_received
-// Params: BT_HDR* packet
-// Returns: void
-struct sco_data_received {
- std::function<void(BT_HDR* packet)> body{[](BT_HDR* packet) {}};
- void operator()(BT_HDR* packet) { body(packet); };
-};
-extern struct sco_data_received sco_data_received;
-// Name: iso_data_received
-// Params: BT_HDR* packet
-// Returns: void
-struct iso_data_received {
- std::function<void(BT_HDR* packet)> body{[](BT_HDR* packet) {}};
- void operator()(BT_HDR* packet) { body(packet); };
-};
-extern struct iso_data_received iso_data_received;
-// Name: hal_service_died
-// Params:
-// Returns: void
-struct hal_service_died {
- std::function<void()> body{[]() {}};
- void operator()() { body(); };
-};
-extern struct hal_service_died hal_service_died;
-// Name: process_command_credits
-// Params: int credits
-// Returns: void
-struct process_command_credits {
- std::function<void(int credits)> body{[](int credits) {}};
- void operator()(int credits) { body(credits); };
-};
-extern struct process_command_credits process_command_credits;
-// Name: hci_is_root_inflammation_event_received
-// Params:
-// Returns: bool
-struct hci_is_root_inflammation_event_received {
- std::function<bool()> body{[]() { return false; }};
- bool operator()() { return body(); };
-};
-extern struct hci_is_root_inflammation_event_received
- hci_is_root_inflammation_event_received;
-// Name: handle_root_inflammation_event
-// Params:
-// Returns: void
-struct handle_root_inflammation_event {
- std::function<void()> body{[]() {}};
- void operator()() { body(); };
-};
-extern struct handle_root_inflammation_event handle_root_inflammation_event;
-// Name: hci_layer_cleanup_interface
-// Params:
-// Returns: void
-struct hci_layer_cleanup_interface {
- std::function<void()> body{[]() {}};
- void operator()() { body(); };
-};
-extern struct hci_layer_cleanup_interface hci_layer_cleanup_interface;
-// Name: hci_layer_get_interface
-// Params:
-// Returns: const hci_t*
-struct hci_layer_get_interface {
- hci_t* hci;
- std::function<const hci_t*()> body{[this]() { return hci; }};
- const hci_t* operator()() { return body(); };
-};
-extern struct hci_layer_get_interface hci_layer_get_interface;
-// Name: hci_layer_get_test_interface
-// Params: const allocator_t* buffer_allocator_interface, const btsnoop_t*
-// btsnoop_interface, const packet_fragmenter_t* packet_fragmenter_interface
-// Returns: const hci_t*
-struct hci_layer_get_test_interface {
- std::function<const hci_t*(
- const allocator_t* buffer_allocator_interface,
- const btsnoop_t* btsnoop_interface,
- const packet_fragmenter_t* packet_fragmenter_interface)>
- body{[](const allocator_t* buffer_allocator_interface,
- const btsnoop_t* btsnoop_interface,
- const packet_fragmenter_t* packet_fragmenter_interface) {
- return nullptr;
- }};
- const hci_t* operator()(
- const allocator_t* buffer_allocator_interface,
- const btsnoop_t* btsnoop_interface,
- const packet_fragmenter_t* packet_fragmenter_interface) {
- return body(buffer_allocator_interface, btsnoop_interface,
- packet_fragmenter_interface);
- };
-};
-extern struct hci_layer_get_test_interface hci_layer_get_test_interface;
-
-} // namespace hci_layer
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_hci_packet_factory.cc b/test/mock/mock_hci_packet_factory.cc
deleted file mode 100644
index a80f17c8a..000000000
--- a/test/mock/mock_hci_packet_factory.cc
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "hci/include/hci_packet_factory.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-const hci_packet_factory_t* hci_packet_factory_get_interface() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
diff --git a/test/mock/mock_hci_packet_parser.cc b/test/mock/mock_hci_packet_parser.cc
deleted file mode 100644
index d25725e43..000000000
--- a/test/mock/mock_hci_packet_parser.cc
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "hci/include/hci_packet_parser.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-const hci_packet_parser_t* hci_packet_parser_get_interface() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const hci_packet_parser_t* hci_packet_parser_get_test_interface(
- allocator_t* buffer_allocator_interface) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
diff --git a/test/mock/mock_hcic_hciblecmds.cc b/test/mock/mock_hcic_hciblecmds.cc
deleted file mode 100644
index 487f239d2..000000000
--- a/test/mock/mock_hcic_hciblecmds.cc
+++ /dev/null
@@ -1,327 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-#define UNUSED_ATTR
-
-#include <base/bind.h>
-#include <stddef.h>
-#include <string.h>
-#include "bt_common.h"
-#include "bt_target.h"
-#include "btu.h"
-#include "hcidefs.h"
-#include "hcimsgs.h"
-void btsnd_hci_ble_add_device_to_periodic_advertiser_list(
- uint8_t adv_addr_type, const RawAddress& adv_addr, uint8_t adv_sid,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hci_ble_clear_periodic_advertiser_list(
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hci_ble_read_periodic_advertiser_list_size(
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hci_ble_remove_device_from_periodic_advertiser_list(
- uint8_t adv_addr_type, const RawAddress& adv_addr, uint8_t adv_sid,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_accept_cis_req(uint16_t conn_handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_big_create_sync(uint8_t big_handle, uint16_t sync_handle,
- uint8_t enc, std::array<uint8_t, 16> bcst_code,
- uint8_t mse, uint16_t big_sync_timeout,
- std::vector<uint8_t> bis) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_big_term_sync(uint8_t big_handle,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_add_acceptlist(
- uint8_t addr_type, const RawAddress& bda,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_add_device_resolving_list(uint8_t addr_type_peer,
- const RawAddress& bda_peer,
- const Octet16& irk_peer,
- const Octet16& irk_local) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_clear_acceptlist(
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_clear_resolving_list(void) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_create_conn_cancel(void) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_create_ll_conn(
- uint16_t scan_int, uint16_t scan_win, uint8_t init_filter_policy,
- uint8_t addr_type_peer, const RawAddress& bda_peer, uint8_t addr_type_own,
- uint16_t conn_int_min, uint16_t conn_int_max, uint16_t conn_latency,
- uint16_t conn_timeout, uint16_t min_ce_len, uint16_t max_ce_len) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_encrypt(uint8_t* key, uint8_t key_len, uint8_t* plain_text,
- uint8_t pt_len, void* p_cmd_cplt_cback) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_enh_rx_test(uint8_t rx_chan, uint8_t phy,
- uint8_t mod_index) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_enh_tx_test(uint8_t tx_chan, uint8_t data_len,
- uint8_t payload, uint8_t phy) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_ext_create_conn(uint8_t init_filter_policy,
- uint8_t addr_type_own,
- uint8_t addr_type_peer,
- const RawAddress& bda_peer,
- uint8_t initiating_phys,
- EXT_CONN_PHY_CFG* phy_cfg) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_ltk_req_neg_reply(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_ltk_req_reply(uint16_t handle, const Octet16& ltk) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_periodic_advertising_create_sync(
- uint8_t options, uint8_t adv_sid, uint8_t adv_addr_type,
- const RawAddress& adv_addr, uint16_t skip_num, uint16_t sync_timeout,
- uint8_t sync_cte_type) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_periodic_advertising_create_sync_cancel(
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_periodic_advertising_set_info_transfer(
- uint16_t conn_handle, uint16_t service_data, uint8_t adv_handle,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_periodic_advertising_sync_transfer(
- uint16_t conn_handle, uint16_t service_data, uint16_t sync_handle,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_periodic_advertising_terminate_sync(
- uint16_t sync_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_rand(base::Callback<void(BT_OCTET8)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_read_adv_chnl_tx_power(void) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_read_chnl_map(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_read_host_supported(void) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_read_remote_feat(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_read_resolvable_addr_local(uint8_t addr_type_peer,
- const RawAddress& bda_peer) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_read_resolvable_addr_peer(uint8_t addr_type_peer,
- const RawAddress& bda_peer) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_receiver_test(uint8_t rx_freq) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_remove_from_acceptlist(
- uint8_t addr_type, const RawAddress& bda,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_rm_device_resolving_list(uint8_t addr_type_peer,
- const RawAddress& bda_peer) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_addr_resolution_enable(uint8_t addr_resolution_enable) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_adv_data(uint8_t data_len, uint8_t* p_data) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_adv_enable(uint8_t adv_enable) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_data_length(uint16_t conn_handle, uint16_t tx_octets,
- uint16_t tx_time) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_default_periodic_advertising_sync_transfer_params(
- uint16_t conn_handle, uint8_t mode, uint16_t skip, uint16_t sync_timeout,
- uint8_t cte_type, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_extended_scan_enable(uint8_t enable,
- uint8_t filter_duplicates,
- uint16_t duration,
- uint16_t period) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_extended_scan_params(uint8_t own_address_type,
- uint8_t scanning_filter_policy,
- uint8_t scanning_phys,
- scanning_phy_cfg* phy_cfg) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_host_chnl_class(
- uint8_t chnl_map[HCIC_BLE_CHNL_MAP_SIZE]) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_local_used_feat(uint8_t feat_set[8]) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_periodic_advertising_receive_enable(
- uint16_t sync_handle, bool enable,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_periodic_advertising_sync_transfer_params(
- uint16_t conn_handle, uint8_t mode, uint16_t skip, uint16_t sync_timeout,
- uint8_t cte_type, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_privacy_mode(uint8_t addr_type_peer,
- const RawAddress& bda_peer,
- uint8_t privacy_type) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_rand_priv_addr_timeout(uint16_t rpa_timout) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_random_addr(const RawAddress& random_bda) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_scan_enable(uint8_t scan_enable, uint8_t duplicate) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_scan_params(uint8_t scan_type, uint16_t scan_int,
- uint16_t scan_win, uint8_t addr_type_own,
- uint8_t scan_filter_policy) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_set_scan_rsp_data(uint8_t data_len, uint8_t* p_scan_rsp) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_start_enc(uint16_t handle,
- uint8_t rand[HCIC_BLE_RAND_DI_SIZE],
- uint16_t ediv, const Octet16& ltk) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_test_end(void) { mock_function_count_map[__func__]++; }
-void btsnd_hcic_ble_transmitter_test(uint8_t tx_freq, uint8_t test_data_len,
- uint8_t payload) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_upd_ll_conn_params(uint16_t handle, uint16_t conn_int_min,
- uint16_t conn_int_max,
- uint16_t conn_latency,
- uint16_t conn_timeout,
- uint16_t min_ce_len,
- uint16_t max_ce_len) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_ble_write_adv_params(uint16_t adv_int_min, uint16_t adv_int_max,
- uint8_t adv_type, uint8_t addr_type_own,
- uint8_t addr_type_dir,
- const RawAddress& direct_bda,
- uint8_t channel_map,
- uint8_t adv_filter_policy) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_create_big(uint8_t big_handle, uint8_t adv_handle,
- uint8_t num_bis, uint32_t sdu_itv,
- uint16_t max_sdu_size, uint16_t transport_latency,
- uint8_t rtn, uint8_t phy, uint8_t packing,
- uint8_t framing, uint8_t enc,
- std::array<uint8_t, 16> bcst_code) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_create_cis(uint8_t num_cis, const EXT_CIS_CREATE_CFG* cis_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_read_iso_tx_sync(
- uint16_t iso_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_rej_cis_req(uint16_t conn_handle, uint8_t reason,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_remove_cig(uint8_t cig_id,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_remove_iso_data_path(
- uint16_t iso_handle, uint8_t data_path_dir,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_read_iso_link_quality(
- uint16_t iso_handle, base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_req_peer_sca(uint16_t conn_handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_set_cig_params(
- uint8_t cig_id, uint32_t sdu_itv_mtos, uint32_t sdu_itv_stom, uint8_t sca,
- uint8_t packing, uint8_t framing, uint16_t max_trans_lat_stom,
- uint16_t max_trans_lat_mtos, uint8_t cis_cnt, const EXT_CIS_CFG* cis_cfg,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_setup_iso_data_path(
- uint16_t iso_handle, uint8_t data_path_dir, uint8_t data_path_id,
- uint8_t codec_id_format, uint16_t codec_id_company,
- uint16_t codec_id_vendor, uint32_t controller_delay,
- std::vector<uint8_t> codec_conf,
- base::OnceCallback<void(uint8_t*, uint16_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_term_big(uint8_t big_handle, uint8_t reason) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_hcic_hcicmds.cc b/test/mock/mock_hcic_hcicmds.cc
deleted file mode 100644
index 1b3f9d9f5..000000000
--- a/test/mock/mock_hcic_hcicmds.cc
+++ /dev/null
@@ -1,325 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:77
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-#define UNUSED_ATTR
-
-#include <stddef.h>
-#include "types/raw_address.h"
-
-#include "bt_common.h"
-#include "bt_target.h"
-#include "btu.h"
-#include "hcidefs.h"
-#include "hcimsgs.h"
-#include "stack/include/acl_hci_link_interface.h"
-
-namespace test {
-namespace mock {
-namespace hcic_hcicmds {
-
-struct btsnd_hcic_change_conn_type {
- uint16_t handle{0};
- uint16_t packet_types{0};
-} btsnd_hcic_change_conn_type;
-
-} // namespace hcic_hcicmds
-} // namespace mock
-} // namespace test
-
-namespace mock = test::mock::hcic_hcicmds;
-
-// Global by definition
-void btsnd_hcic_accept_conn(const RawAddress& dest, uint8_t role) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_accept_esco_conn(const RawAddress& bd_addr,
- uint32_t transmit_bandwidth,
- uint32_t receive_bandwidth,
- uint16_t max_latency, uint16_t content_fmt,
- uint8_t retrans_effort,
- uint16_t packet_types) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_add_SCO_conn(uint16_t handle, uint16_t packet_types) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_auth_request(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_change_conn_type(uint16_t handle, uint16_t packet_types) {
- mock::btsnd_hcic_change_conn_type.handle = handle;
- mock::btsnd_hcic_change_conn_type.packet_types = packet_types;
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_change_name(BD_NAME name) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_create_conn(const RawAddress& dest, uint16_t packet_types,
- uint8_t page_scan_rep_mode, uint8_t page_scan_mode,
- uint16_t clock_offset, uint8_t allow_switch) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_create_conn_cancel(const RawAddress& dest) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_delete_stored_key(const RawAddress& bd_addr,
- bool delete_all_flag) {
- mock_function_count_map[__func__]++;
-}
-static void btsnd_hcic_disconnect(uint16_t handle, uint8_t reason) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_enable_test_mode(void) { mock_function_count_map[__func__]++; }
-void btsnd_hcic_enhanced_accept_synchronous_connection(
- const RawAddress& bd_addr, enh_esco_params_t* p_params) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_enhanced_flush(uint16_t handle, uint8_t packet_type) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_enhanced_set_up_synchronous_connection(
- uint16_t conn_handle, enh_esco_params_t* p_params) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_exit_park_mode(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_exit_per_inq(void) { mock_function_count_map[__func__]++; }
-void btsnd_hcic_exit_sniff_mode(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_get_link_quality(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_hold_mode(uint16_t handle, uint16_t max_hold_period,
- uint16_t min_hold_period) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_host_num_xmitted_pkts(uint8_t num_handles, uint16_t* handle,
- uint16_t* num_pkts) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_inq_cancel(void) { mock_function_count_map[__func__]++; }
-void btsnd_hcic_inquiry(const LAP inq_lap, uint8_t duration,
- uint8_t response_cnt) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_io_cap_req_neg_reply(const RawAddress& bd_addr,
- uint8_t err_code) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_io_cap_req_reply(const RawAddress& bd_addr, uint8_t capability,
- uint8_t oob_present, uint8_t auth_req) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_link_key_neg_reply(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_link_key_req_reply(const RawAddress& bd_addr,
- const LinkKey& link_key) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_park_mode(uint16_t handle, uint16_t beacon_max_interval,
- uint16_t beacon_min_interval) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_per_inq_mode(uint16_t max_period, uint16_t min_period,
- const LAP inq_lap, uint8_t duration,
- uint8_t response_cnt) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_pin_code_neg_reply(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_pin_code_req_reply(const RawAddress& bd_addr,
- uint8_t pin_code_len, PIN_CODE pin_code) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_qos_setup(uint16_t handle, uint8_t flags, uint8_t service_type,
- uint32_t token_rate, uint32_t peak, uint32_t latency,
- uint32_t delay_var) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_read_automatic_flush_timeout(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_read_encryption_key_size(uint16_t handle, ReadEncKeySizeCb cb) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_read_failed_contact_counter(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_read_inq_tx_power(void) { mock_function_count_map[__func__]++; }
-void btsnd_hcic_read_lmp_handle(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_read_local_oob_data(void) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_read_name(void) { mock_function_count_map[__func__]++; }
-void btsnd_hcic_read_rmt_clk_offset(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_read_rssi(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_read_tx_power(uint16_t handle, uint8_t type) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_reject_conn(const RawAddress& dest, uint8_t reason) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_reject_esco_conn(const RawAddress& bd_addr, uint8_t reason) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_rem_oob_neg_reply(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_rem_oob_reply(const RawAddress& bd_addr, const Octet16& c,
- const Octet16& r) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_rmt_ext_features(uint16_t handle, uint8_t page_num) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_rmt_features_req(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_rmt_name_req(const RawAddress& bd_addr,
- uint8_t page_scan_rep_mode, uint8_t page_scan_mode,
- uint16_t clock_offset) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_rmt_name_req_cancel(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_rmt_ver_req(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_send_keypress_notif(const RawAddress& bd_addr, uint8_t notif) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_set_conn_encrypt(uint16_t handle, bool enable) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_set_event_filter(uint8_t filt_type, uint8_t filt_cond_type,
- uint8_t* filt_cond, uint8_t filt_cond_len) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_setup_esco_conn(uint16_t handle, uint32_t transmit_bandwidth,
- uint32_t receive_bandwidth,
- uint16_t max_latency, uint16_t voice,
- uint8_t retrans_effort, uint16_t packet_types) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_sniff_mode(uint16_t handle, uint16_t max_sniff_period,
- uint16_t min_sniff_period, uint16_t sniff_attempt,
- uint16_t sniff_timeout) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_sniff_sub_rate(uint16_t handle, uint16_t max_lat,
- uint16_t min_remote_lat,
- uint16_t min_local_lat) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_switch_role(const RawAddress& bd_addr, uint8_t role) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_user_conf_reply(const RawAddress& bd_addr, bool is_yes) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_user_passkey_neg_reply(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_user_passkey_reply(const RawAddress& bd_addr, uint32_t value) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_vendor_spec_cmd(void* buffer, uint16_t opcode, uint8_t len,
- uint8_t* p_data, void* p_cmd_cplt_cback) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_auth_enable(uint8_t flag) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_auto_flush_tout(uint16_t handle, uint16_t tout) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_cur_iac_lap(uint8_t num_cur_iac, LAP* const iac_lap) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_def_policy_set(uint16_t settings) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_dev_class(DEV_CLASS dev_class) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_ext_inquiry_response(void* buffer, uint8_t fec_req) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_inqscan_cfg(uint16_t interval, uint16_t window) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_inqscan_type(uint8_t type) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_inquiry_mode(uint8_t mode) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_link_super_tout(uint8_t local_controller_id,
- uint16_t handle, uint16_t timeout) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_page_tout(uint16_t timeout) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_pagescan_cfg(uint16_t interval, uint16_t window) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_pagescan_type(uint8_t type) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_pin_type(uint8_t type) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_policy_set(uint16_t handle, uint16_t settings) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_scan_enable(uint8_t flag) {
- mock_function_count_map[__func__]++;
-}
-void btsnd_hcic_write_voice_settings(uint16_t flags) {
- mock_function_count_map[__func__]++;
-}
-
-bluetooth::legacy::hci::Interface interface_ = {
- .Disconnect = btsnd_hcic_disconnect,
- .StartRoleSwitch = btsnd_hcic_switch_role,
- .ChangeConnectionPacketType = btsnd_hcic_change_conn_type,
-};
-
-const bluetooth::legacy::hci::Interface&
-bluetooth::legacy::hci::GetInterface() {
- return interface_;
-}
diff --git a/test/mock/mock_hcic_hcicmds.h b/test/mock/mock_hcic_hcicmds.h
deleted file mode 100644
index 980189bf4..000000000
--- a/test/mock/mock_hcic_hcicmds.h
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:1
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace hcic_hcicmds {
-
-struct btsnd_hcic_change_conn_type {
- uint16_t handle;
- uint16_t packet_types;
-};
-extern struct btsnd_hcic_change_conn_type btsnd_hcic_change_conn_type;
-
-} // namespace hcic_hcicmds
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_main_bte.cc b/test/mock/mock_main_bte.cc
deleted file mode 100644
index c0734f557..000000000
--- a/test/mock/mock_main_bte.cc
+++ /dev/null
@@ -1,68 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_main_bte.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace main_bte {
-
-// Function state capture and return values, if needed
-struct post_to_main_message_loop post_to_main_message_loop;
-struct bte_main_init bte_main_init;
-struct bte_main_hci_send bte_main_hci_send;
-
-} // namespace main_bte
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-void post_to_main_message_loop(const base::Location& from_here, BT_HDR* p_msg) {
- mock_function_count_map[__func__]++;
- test::mock::main_bte::post_to_main_message_loop(from_here, p_msg);
-}
-void bte_main_init(void) {
- mock_function_count_map[__func__]++;
- test::mock::main_bte::bte_main_init();
-}
-void bte_main_hci_send(BT_HDR* p_msg, uint16_t event) {
- mock_function_count_map[__func__]++;
- test::mock::main_bte::bte_main_hci_send(p_msg, event);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_main_bte.h b/test/mock/mock_main_bte.h
deleted file mode 100644
index 3ef95e153..000000000
--- a/test/mock/mock_main_bte.h
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include <base/logging.h>
-#include <hardware/bluetooth.h>
-#include "bt_common.h"
-#include "btcore/include/module.h"
-#include "bte.h"
-#include "btif/include/btif_config.h"
-#include "btu.h"
-#include "device/include/interop.h"
-#include "hci/include/btsnoop.h"
-#include "hci/include/hci_layer.h"
-#include "main/shim/hci_layer.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "stack_config.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace main_bte {
-
-// Shared state between mocked functions and tests
-// Name: post_to_main_message_loop
-// Params: const base::Location& from_here, BT_HDR* p_msg
-// Returns: void
-struct post_to_main_message_loop {
- std::function<void(const base::Location& from_here, BT_HDR* p_msg)> body{
- [](const base::Location& from_here, BT_HDR* p_msg) {}};
- void operator()(const base::Location& from_here, BT_HDR* p_msg) {
- body(from_here, p_msg);
- };
-};
-extern struct post_to_main_message_loop post_to_main_message_loop;
-// Name: bte_main_init
-// Params: void
-// Returns: void
-struct bte_main_init {
- std::function<void(void)> body{[](void) {}};
- void operator()(void) { body(); };
-};
-extern struct bte_main_init bte_main_init;
-// Name: bte_main_hci_send
-// Params: BT_HDR* p_msg, uint16_t event
-// Returns: void
-struct bte_main_hci_send {
- std::function<void(BT_HDR* p_msg, uint16_t event)> body{
- [](BT_HDR* p_msg, uint16_t event) {}};
- void operator()(BT_HDR* p_msg, uint16_t event) { body(p_msg, event); };
-};
-extern struct bte_main_hci_send bte_main_hci_send;
-
-} // namespace main_bte
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_main_shim.cc b/test/mock/mock_main_shim.cc
deleted file mode 100644
index a5226ba59..000000000
--- a/test/mock/mock_main_shim.cc
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:14
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#define LOG_TAG "bt_shim"
-#include "gd/common/init_flags.h"
-#include "main/shim/entry.h"
-#include "main/shim/shim.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool MOCK_bluetooth_shim_is_gd_acl_enabled_{false};
-
-bool bluetooth::shim::is_any_gd_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_acl_enabled() {
- mock_function_count_map[__func__]++;
- return MOCK_bluetooth_shim_is_gd_acl_enabled_;
-}
-bool bluetooth::shim::is_gd_advertising_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_scanning_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_controller_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_hci_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_l2cap_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_security_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_shim_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_stack_started_up() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::is_gd_link_policy_enabled() {
- mock_function_count_map[__func__]++;
- return false;
-}
-future_t* GeneralShutDown() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-future_t* IdleModuleStartUp() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-future_t* ShimModuleStartUp() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
diff --git a/test/mock/mock_main_shim_BtifConfigInterface.cc b/test/mock/mock_main_shim_BtifConfigInterface.cc
deleted file mode 100644
index 1981aef8b..000000000
--- a/test/mock/mock_main_shim_BtifConfigInterface.cc
+++ /dev/null
@@ -1,90 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <string>
-
-#include "main/shim/config.h"
-
-bool bluetooth::shim::BtifConfigInterface::HasSection(
- const std::string& section) {
- return false;
-}
-bool bluetooth::shim::BtifConfigInterface::HasProperty(
- const std::string& section, const std::string& property) {
- return false;
-}
-bool bluetooth::shim::BtifConfigInterface::GetInt(const std::string& section,
- const std::string& key,
- int* value) {
- return false;
-}
-bool bluetooth::shim::BtifConfigInterface::SetInt(const std::string& section,
- const std::string& key,
- int value) {
- return false;
-}
-bool bluetooth::shim::BtifConfigInterface::GetUint64(const std::string& section,
- const std::string& key,
- uint64_t* value) {
- return false;
-}
-bool bluetooth::shim::BtifConfigInterface::SetUint64(const std::string& section,
- const std::string& key,
- uint64_t value) {
- return false;
-}
-bool bluetooth::shim::BtifConfigInterface::GetStr(const std::string& section,
- const std::string& key,
- char* value,
- int* size_bytes) {
- return false;
-}
-std::optional<std::string> bluetooth::shim::BtifConfigInterface::GetStr(
- const std::string& section, const std::string& key) {
- return std::string();
-}
-bool bluetooth::shim::BtifConfigInterface::SetStr(const std::string& section,
- const std::string& key,
- const std::string& value) {
- return false;
-}
-bool bluetooth::shim::BtifConfigInterface::GetBin(const std::string& section,
- const std::string& key,
- uint8_t* value,
- size_t* length) {
- return false;
-}
-size_t bluetooth::shim::BtifConfigInterface::GetBinLength(
- const std::string& section, const std::string& key) {
- return 0;
-}
-bool bluetooth::shim::BtifConfigInterface::SetBin(const std::string& section,
- const std::string& key,
- const uint8_t* value,
- size_t length) {
- return false;
-}
-bool bluetooth::shim::BtifConfigInterface::RemoveProperty(
- const std::string& section, const std::string& key) {
- return false;
-}
-std::vector<std::string>
-bluetooth::shim::BtifConfigInterface::GetPersistentDevices() {
- return std::vector<std::string>();
-}
-void bluetooth::shim::BtifConfigInterface::Save(){};
-void bluetooth::shim::BtifConfigInterface::Flush(){};
-void bluetooth::shim::BtifConfigInterface::Clear(){};
diff --git a/test/mock/mock_main_shim_acl.cc b/test/mock/mock_main_shim_acl.cc
deleted file mode 100644
index ae7c9e5a2..000000000
--- a/test/mock/mock_main_shim_acl.cc
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:7
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "main/shim/acl_api.h"
-#include "types/ble_address_with_type.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void bluetooth::shim::ACL_Shutdown() { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_main_shim_acl_api.cc b/test/mock/mock_main_shim_acl_api.cc
deleted file mode 100644
index 3073c0731..000000000
--- a/test/mock/mock_main_shim_acl_api.cc
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:5
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstddef>
-#include <cstdint>
-#include "main/shim/acl_api.h"
-#include "types/ble_address_with_type.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void bluetooth::shim::ACL_CreateClassicConnection(
- const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::ACL_CancelClassicConnection(
- const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
-}
-bool bluetooth::shim::ACL_AcceptLeConnectionFrom(
- const tBLE_BD_ADDR& legacy_address_with_type, bool is_direct) {
- mock_function_count_map[__func__]++;
- return true;
-}
-void bluetooth::shim::ACL_IgnoreLeConnectionFrom(
- const tBLE_BD_ADDR& legacy_address_with_type) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::ACL_ConfigureLePrivacy(bool is_le_privacy_enabled) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::ACL_WriteData(uint16_t handle, BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::ACL_Disconnect(uint16_t handle, bool is_classic,
- tHCI_STATUS reason) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::ACL_IgnoreAllLeConnections() {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::ACL_ReadConnectionAddress(const RawAddress& pseudo_addr,
- RawAddress& conn_addr,
- uint8_t* p_addr_type) {
- mock_function_count_map[__func__]++;
-} \ No newline at end of file
diff --git a/test/mock/mock_main_shim_activity_attribution.cc b/test/mock/mock_main_shim_activity_attribution.cc
deleted file mode 100644
index 8dc746b2b..000000000
--- a/test/mock/mock_main_shim_activity_attribution.cc
+++ /dev/null
@@ -1,42 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "btif/include/btif_common.h"
-#include "main/shim/activity_attribution.h"
-#include "main/shim/entry.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-ActivityAttributionInterface*
-bluetooth::shim::get_activity_attribution_instance() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void bluetooth::shim::init_activity_attribution() {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_main_shim_btm_api.cc b/test/mock/mock_main_shim_btm_api.cc
deleted file mode 100644
index 0f241d9e9..000000000
--- a/test/mock/mock_main_shim_btm_api.cc
+++ /dev/null
@@ -1,439 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:85
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/callback.h>
-#include "main/shim/btm_api.h"
-#include "stack/include/btm_ble_api_types.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-Octet16 octet16;
-
-bool bluetooth::shim::BTM_BleDataSignature(const RawAddress& bd_addr,
- uint8_t* p_text, uint16_t len,
- BLE_SIGNATURE signature) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_BleLocalPrivacyEnabled(void) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_BleSecurityProcedureIsRunning(
- const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_BleVerifySignature(const RawAddress& bd_addr,
- uint8_t* p_orig, uint16_t len,
- uint32_t counter,
- uint8_t* p_comp) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_GetLeSecurityState(const RawAddress& bd_addr,
- uint8_t* p_le_dev_sec_flags,
- uint8_t* p_le_key_size) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_HasEirService(const uint32_t* p_eir_uuid,
- uint16_t uuid16) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_ReadConnectedTransportAddress(
- RawAddress* remote_bda, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_ReadRemoteConnectionAddr(
- const RawAddress& pseudo_addr, RawAddress& conn_addr,
- tBLE_ADDR_TYPE* p_addr_type) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_SecAddDevice(const RawAddress& bd_addr,
- DEV_CLASS dev_class, BD_NAME bd_name,
- uint8_t* features, LinkKey* link_key,
- uint8_t key_type, uint8_t pin_length) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_SecAddRmtNameNotifyCallback(
- tBTM_RMT_NAME_CALLBACK* p_callback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_SecDeleteDevice(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_SecDeleteRmtNameNotifyCallback(
- tBTM_RMT_NAME_CALLBACK* p_callback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_SecRegister(const tBTM_APPL_INFO* bta_callbacks) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool bluetooth::shim::BTM_UseLeLink(const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
- return false;
-}
-char* bluetooth::shim::BTM_SecReadDevName(const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const Octet16& bluetooth::shim::BTM_GetDeviceEncRoot() {
- mock_function_count_map[__func__]++;
- return octet16;
-}
-const Octet16& bluetooth::shim::BTM_GetDeviceDHK() {
- mock_function_count_map[__func__]++;
- return octet16;
-}
-const Octet16& bluetooth::shim::BTM_GetDeviceIDRoot() {
- mock_function_count_map[__func__]++;
- return octet16;
-}
-tBTM_EIR_SEARCH_RESULT bluetooth::shim::BTM_HasInquiryEirService(
- tBTM_INQ_RESULTS* p_results, uint16_t uuid16) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTM_INQ_INFO* bluetooth::shim::BTM_InqDbFirst(void) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_INQ_INFO* bluetooth::shim::BTM_InqDbNext(tBTM_INQ_INFO* p_cur) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_INQ_INFO* bluetooth::shim::BTM_InqDbRead(const RawAddress& p_bda) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_STATUS bluetooth::shim::BTM_BleObserve(bool start, uint8_t duration_sec,
- tBTM_INQ_RESULTS_CB* p_results_cb,
- tBTM_CMPL_CB* p_cmpl_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_CancelRemoteDeviceName(void) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_ClearInqDb(const RawAddress* p_bda) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_ReadRemoteDeviceName(
- const RawAddress& raw_address, tBTM_CMPL_CB* callback,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SecBond(const RawAddress& bd_addr,
- tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport,
- int device_type) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SecBondCancel(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetConnectability(uint16_t page_mode,
- uint16_t window,
- uint16_t interval) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetDeviceClass(DEV_CLASS dev_class) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetDiscoverability(uint16_t discoverable_mode,
- uint16_t window,
- uint16_t interval) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetEncryption(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data,
- tBTM_BLE_SEC_ACT sec_act) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_SetInquiryMode(uint8_t inquiry_mode) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_StartInquiry(tBTM_INQ_RESULTS_CB* p_results_cb,
- tBTM_CMPL_CB* p_cmpl_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::BTM_WriteEIR(BT_HDR* p_buff) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS bluetooth::shim::btm_sec_mx_access_request(
- const RawAddress& bd_addr, bool is_originator,
- uint16_t security_requirement, tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-uint16_t bluetooth::shim::BTM_GetHCIConnHandle(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t bluetooth::shim::BTM_IsInquiryActive(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t bluetooth::shim::BTM_BleGetSupportedKeySize(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t bluetooth::shim::BTM_BleMaxMultiAdvInstanceCount() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t bluetooth::shim::BTM_GetEirSupportedServices(uint32_t* p_eir_uuid,
- uint8_t** p,
- uint8_t max_num_uuid16,
- uint8_t* p_num_uuid16) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t bluetooth::shim::BTM_GetEirUuidList(uint8_t* p_eir, size_t eir_len,
- uint8_t uuid_size,
- uint8_t* p_num_uuid,
- uint8_t* p_uuid_list,
- uint8_t max_num_uuid) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void bluetooth::shim::BTM_AddEirService(uint32_t* p_eir_uuid, uint16_t uuid16) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleAdvFilterParamSetup(
- int action, tBTM_BLE_PF_FILT_INDEX filt_index,
- std::unique_ptr<btgatt_filt_param_setup_t> p_filt_params,
- tBTM_BLE_PF_PARAM_CB cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleEnableDisableFilterFeature(
- uint8_t enable, tBTM_BLE_PF_STATUS_CBACK p_stat_cback) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleLoadLocalKeys(uint8_t key_type,
- tBTM_BLE_LOCAL_KEYS* p_key) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleOobDataReply(const RawAddress& bd_addr,
- uint8_t res, uint8_t len,
- uint8_t* p_data) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleReadPhy(
- const RawAddress& bd_addr,
- base::Callback<void(uint8_t tx_phy, uint8_t rx_phy, uint8_t status)> cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleReceiverTest(uint8_t rx_freq,
- tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleSecureConnectionOobDataReply(
- const RawAddress& bd_addr, uint8_t* p_c, uint8_t* p_r) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleSetConnScanParams(uint32_t scan_interval,
- uint32_t scan_window) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleSetPhy(const RawAddress& bd_addr, uint8_t tx_phys,
- uint8_t rx_phys, uint16_t phy_options) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleSetPrefConnParams(const RawAddress& bd_addr,
- uint16_t min_conn_int,
- uint16_t max_conn_int,
- uint16_t peripheral_latency,
- uint16_t supervision_tout) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleTestEnd(tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleTransmitterTest(uint8_t tx_freq,
- uint8_t test_data_len,
- uint8_t packet_payload,
- tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_BleUpdateAdvFilterPolicy(tBTM_BLE_AFP adv_policy) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_CancelInquiry(void) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_ConfirmReqReply(tBTM_STATUS res,
- const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_EnableInterlacedInquiryScan() {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_EnableInterlacedPageScan() {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_addr_filter(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index,
- tBLE_BD_ADDR addr,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_clear(tBTM_BLE_PF_FILT_INDEX filt_index,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_local_name(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index,
- std::vector<uint8_t> name,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_manu_data(
- tBTM_BLE_SCAN_COND_OP action, tBTM_BLE_PF_FILT_INDEX filt_index,
- uint16_t company_id, uint16_t company_id_mask, std::vector<uint8_t> data,
- std::vector<uint8_t> data_mask, tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_set(tBTM_BLE_PF_FILT_INDEX filt_index,
- std::vector<ApcfCommand> commands,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_srvc_data(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_srvc_data_pattern(
- tBTM_BLE_SCAN_COND_OP action, tBTM_BLE_PF_FILT_INDEX filt_index,
- std::vector<uint8_t> data, std::vector<uint8_t> data_mask,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_LE_PF_uuid_filter(tBTM_BLE_SCAN_COND_OP action,
- tBTM_BLE_PF_FILT_INDEX filt_index,
- tBTM_BLE_PF_COND_TYPE filter_type,
- const bluetooth::Uuid& uuid,
- tBTM_BLE_PF_LOGIC_TYPE cond_logic,
- const bluetooth::Uuid& uuid_mask,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res,
- uint8_t pin_len, uint8_t* p_pin) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_ReadConnectionAddr(const RawAddress& remote_bda,
- RawAddress& local_conn_addr,
- tBLE_ADDR_TYPE* p_addr_type) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_ReadDevInfo(const RawAddress& remote_bda,
- tBT_DEVICE_TYPE* p_dev_type,
- tBLE_ADDR_TYPE* p_addr_type) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_RemoteOobDataReply(tBTM_STATUS res,
- const RawAddress& bd_addr,
- const Octet16& c,
- const Octet16& r) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_RemoveEirService(uint32_t* p_eir_uuid,
- uint16_t uuid16) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_SecAddBleDevice(const RawAddress& bd_addr,
- tBT_DEVICE_TYPE dev_type,
- tBLE_ADDR_TYPE addr_type) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_SecAddBleKey(const RawAddress& bd_addr,
- tBTM_LE_KEY_VALUE* p_le_key,
- tBTM_LE_KEY_TYPE key_type) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_SecClearSecurityFlags(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::BTM_SecurityGrant(const RawAddress& bd_addr,
- uint8_t res) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::SendRemoteNameRequest(const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
-}
-void btm_api_process_extended_inquiry_result(RawAddress raw_address,
- uint8_t page_scan_rep_mode,
- DEV_CLASS device_class,
- uint16_t clock_offset, int8_t rssi,
- const uint8_t* eir_data,
- size_t eir_len) {
- mock_function_count_map[__func__]++;
-}
-void btm_api_process_inquiry_result(const RawAddress& raw_address,
- uint8_t page_scan_rep_mode,
- DEV_CLASS device_class,
- uint16_t clock_offset) {
- mock_function_count_map[__func__]++;
-}
-void btm_api_process_inquiry_result_with_rssi(RawAddress raw_address,
- uint8_t page_scan_rep_mode,
- DEV_CLASS device_class,
- uint16_t clock_offset,
- int8_t rssi) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_main_shim_controller.cc b/test/mock/mock_main_shim_controller.cc
deleted file mode 100644
index d3ff4b801..000000000
--- a/test/mock/mock_main_shim_controller.cc
+++ /dev/null
@@ -1,37 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:9
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "device/include/controller.h"
-#include "main/shim/controller.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-const controller_t* bluetooth::shim::controller_get_interface() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
diff --git a/test/mock/mock_main_shim_dumpsys.cc b/test/mock/mock_main_shim_dumpsys.cc
deleted file mode 100644
index d6c1d851f..000000000
--- a/test/mock/mock_main_shim_dumpsys.cc
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:4
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "main/shim/dumpsys.h"
-#include "main/shim/entry.h"
-#include "main/shim/shim.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void bluetooth::shim::RegisterDumpsysFunction(const void* token,
- DumpsysFunction func) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::Dump(int fd, const char** args) {
- mock_function_count_map[__func__]++;
-}
-void bluetooth::shim::UnregisterDumpsysFunction(const void* token) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_main_shim_entry.cc b/test/mock/mock_main_shim_entry.cc
deleted file mode 100644
index 13cd5f305..000000000
--- a/test/mock/mock_main_shim_entry.cc
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-// #include "gd/btaa/activity_attribution.h"
-#include "gd/module.h"
-
-#include "gd/hci/acl_manager_mock.h"
-#include "gd/hci/controller_mock.h"
-#include "gd/hci/hci_layer.h"
-#include "gd/hci/le_advertising_manager.h"
-#include "gd/hci/le_scanning_manager.h"
-#include "gd/neighbor/connectability.h"
-#include "gd/neighbor/discoverability.h"
-#include "gd/neighbor/inquiry.h"
-#include "gd/neighbor/inquiry_mock.h"
-#include "gd/neighbor/name.h"
-#include "gd/neighbor/page.h"
-#include "gd/os/handler.h"
-#include "gd/security/security_module.h"
-#include "gd/shim/dumpsys.h"
-#include "gd/storage/storage_module.h"
-#include "main/shim/entry.h"
-#include "main/shim/stack.h"
-
-namespace bluetooth {
-namespace hci {
-namespace testing {
-
-MockAclManager* mock_acl_manager_{nullptr};
-MockController* mock_controller_{nullptr};
-os::Handler* mock_gd_shim_handler_{nullptr};
-
-} // namespace testing
-} // namespace hci
-
-namespace shim {
-
-Dumpsys* GetDumpsys() { return nullptr; }
-activity_attribution::ActivityAttribution* GetActivityAttribution() {
- return nullptr;
-}
-hci::AclManager* GetAclManager() { return hci::testing::mock_acl_manager_; }
-hci::Controller* GetController() { return hci::testing::mock_controller_; }
-hci::HciLayer* GetHciLayer() { return nullptr; }
-hci::LeAdvertisingManager* GetAdvertising() { return nullptr; }
-hci::LeScanningManager* GetScanning() { return nullptr; }
-hci::VendorSpecificEventManager* GetVendorSpecificEventManager() {
- return nullptr;
-}
-l2cap::classic::L2capClassicModule* GetL2capClassicModule() { return nullptr; }
-l2cap::le::L2capLeModule* GetL2capLeModule() { return nullptr; }
-neighbor::ConnectabilityModule* GetConnectability() { return nullptr; }
-neighbor::DiscoverabilityModule* GetDiscoverability() { return nullptr; }
-neighbor::InquiryModule* GetInquiry() { return nullptr; }
-neighbor::NameModule* GetName() { return nullptr; }
-neighbor::PageModule* GetPage() { return nullptr; }
-os::Handler* GetGdShimHandler() { return hci::testing::mock_gd_shim_handler_; }
-security::SecurityModule* GetSecurityModule() { return nullptr; }
-storage::StorageModule* GetStorage() { return nullptr; }
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/test/mock/mock_main_shim_entry.h b/test/mock/mock_main_shim_entry.h
deleted file mode 100644
index 4f6aa70cb..000000000
--- a/test/mock/mock_main_shim_entry.h
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-namespace bluetooth {
-namespace hci {
-namespace testing {
-
-extern MockAclManager* mock_acl_manager_;
-extern MockController* mock_controller_;
-
-} // namespace testing
-} // namespace hci
-} // namespace bluetooth
diff --git a/test/mock/mock_main_shim_l2cap_api.cc b/test/mock/mock_main_shim_l2cap_api.cc
deleted file mode 100644
index d934cac7e..000000000
--- a/test/mock/mock_main_shim_l2cap_api.cc
+++ /dev/null
@@ -1,343 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:45
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_main_shim_l2cap_api.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace main_shim_l2cap_api {
-
-// Function state capture and return values, if needed
-struct L2CA_ReadRemoteVersion L2CA_ReadRemoteVersion;
-struct L2CA_ReadRemoteFeatures L2CA_ReadRemoteFeatures;
-struct L2CA_UseLegacySecurityModule L2CA_UseLegacySecurityModule;
-struct L2CA_Register L2CA_Register;
-struct L2CA_Deregister L2CA_Deregister;
-struct L2CA_ConnectReq L2CA_ConnectReq;
-struct L2CA_DisconnectReq L2CA_DisconnectReq;
-struct L2CA_DataWrite L2CA_DataWrite;
-struct L2CA_ReconfigCreditBasedConnsReq L2CA_ReconfigCreditBasedConnsReq;
-struct L2CA_ConnectCreditBasedReq L2CA_ConnectCreditBasedReq;
-struct L2CA_ConnectCreditBasedRsp L2CA_ConnectCreditBasedRsp;
-struct L2CA_SetIdleTimeoutByBdAddr L2CA_SetIdleTimeoutByBdAddr;
-struct L2CA_SetAclPriority L2CA_SetAclPriority;
-struct L2CA_SetAclPriority2 L2CA_SetAclPriority2;
-struct L2CA_GetPeerFeatures L2CA_GetPeerFeatures;
-struct L2CA_RegisterFixedChannel L2CA_RegisterFixedChannel;
-struct L2CA_ConnectFixedChnl L2CA_ConnectFixedChnl;
-struct L2CA_SendFixedChnlData L2CA_SendFixedChnlData;
-struct L2CA_RemoveFixedChnl L2CA_RemoveFixedChnl;
-struct L2CA_GetLeHandle L2CA_GetLeHandle;
-struct L2CA_LeConnectionUpdate L2CA_LeConnectionUpdate;
-struct L2CA_EnableUpdateBleConnParams L2CA_EnableUpdateBleConnParams;
-struct L2CA_GetRemoteCid L2CA_GetRemoteCid;
-struct L2CA_SetTxPriority L2CA_SetTxPriority;
-struct L2CA_SetLeGattTimeout L2CA_SetLeGattTimeout;
-struct L2CA_SetChnlFlushability L2CA_SetChnlFlushability;
-struct L2CA_FlushChannel L2CA_FlushChannel;
-struct L2CA_IsLinkEstablished L2CA_IsLinkEstablished;
-struct L2CA_IsLeLink L2CA_IsLeLink;
-struct L2CA_ReadConnectionAddr L2CA_ReadConnectionAddr;
-struct L2CA_ReadRemoteConnectionAddr L2CA_ReadRemoteConnectionAddr;
-struct L2CA_GetBleConnRole L2CA_GetBleConnRole;
-struct L2CA_ConnectForSecurity L2CA_ConnectForSecurity;
-struct L2CA_SetBondingState L2CA_SetBondingState;
-struct L2CA_DisconnectLink L2CA_DisconnectLink;
-struct L2CA_GetNumLinks L2CA_GetNumLinks;
-struct L2CA_AllocateLePSM L2CA_AllocateLePSM;
-struct L2CA_FreeLePSM L2CA_FreeLePSM;
-struct L2CA_RegisterLECoc L2CA_RegisterLECoc;
-struct L2CA_DeregisterLECoc L2CA_DeregisterLECoc;
-struct L2CA_ConnectLECocReq L2CA_ConnectLECocReq;
-struct L2CA_GetPeerLECocConfig L2CA_GetPeerLECocConfig;
-struct L2CA_DisconnectLECocReq L2CA_DisconnectLECocReq;
-struct L2CA_LECocDataWrite L2CA_LECocDataWrite;
-struct L2CA_SwitchRoleToCentral L2CA_SwitchRoleToCentral;
-
-} // namespace main_shim_l2cap_api
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-bool bluetooth::shim::L2CA_ReadRemoteVersion(const RawAddress& addr,
- uint8_t* lmp_version,
- uint16_t* manufacturer,
- uint16_t* lmp_sub_version) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_ReadRemoteVersion(
- addr, lmp_version, manufacturer, lmp_sub_version);
-}
-uint8_t* bluetooth::shim::L2CA_ReadRemoteFeatures(const RawAddress& addr) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_ReadRemoteFeatures(addr);
-}
-void bluetooth::shim::L2CA_UseLegacySecurityModule() {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_l2cap_api::L2CA_UseLegacySecurityModule();
-}
-uint16_t bluetooth::shim::L2CA_Register(
- uint16_t client_psm, const tL2CAP_APPL_INFO& callbacks, bool enable_snoop,
- tL2CAP_ERTM_INFO* p_ertm_info, uint16_t my_mtu,
- uint16_t required_remote_mtu, uint16_t sec_level) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_Register(
- client_psm, callbacks, enable_snoop, p_ertm_info, my_mtu,
- required_remote_mtu, sec_level);
-}
-void bluetooth::shim::L2CA_Deregister(uint16_t psm) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_l2cap_api::L2CA_Deregister(psm);
-}
-uint16_t bluetooth::shim::L2CA_ConnectReq(uint16_t psm,
- const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_ConnectReq(psm, raw_address);
-}
-bool bluetooth::shim::L2CA_DisconnectReq(uint16_t cid) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_DisconnectReq(cid);
-}
-uint8_t bluetooth::shim::L2CA_DataWrite(uint16_t cid, BT_HDR* p_data) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_DataWrite(cid, p_data);
-}
-bool bluetooth::shim::L2CA_ReconfigCreditBasedConnsReq(
- const RawAddress& bd_addr, std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_ReconfigCreditBasedConnsReq(
- bd_addr, lcids, p_cfg);
-}
-std::vector<uint16_t> bluetooth::shim::L2CA_ConnectCreditBasedReq(
- uint16_t psm, const RawAddress& p_bd_addr, tL2CAP_LE_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_ConnectCreditBasedReq(
- psm, p_bd_addr, p_cfg);
-}
-bool bluetooth::shim::L2CA_ConnectCreditBasedRsp(
- const RawAddress& bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids, uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_ConnectCreditBasedRsp(
- bd_addr, id, accepted_lcids, result, p_cfg);
-}
-bool bluetooth::shim::L2CA_SetIdleTimeoutByBdAddr(const RawAddress& bd_addr,
- uint16_t timeout,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_SetIdleTimeoutByBdAddr(
- bd_addr, timeout, transport);
-}
-bool bluetooth::shim::L2CA_SetAclPriority(uint16_t handle, bool high_priority) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_SetAclPriority(handle,
- high_priority);
-}
-bool bluetooth::shim::L2CA_SetAclPriority(const RawAddress& bd_addr,
- tL2CAP_PRIORITY priority) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_SetAclPriority2(bd_addr,
- priority);
-}
-bool bluetooth::shim::L2CA_GetPeerFeatures(const RawAddress& bd_addr,
- uint32_t* p_ext_feat,
- uint8_t* p_chnl_mask) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_GetPeerFeatures(
- bd_addr, p_ext_feat, p_chnl_mask);
-}
-bool bluetooth::shim::L2CA_RegisterFixedChannel(uint16_t cid,
- tL2CAP_FIXED_CHNL_REG* p_freg) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_RegisterFixedChannel(cid,
- p_freg);
-}
-bool bluetooth::shim::L2CA_ConnectFixedChnl(uint16_t cid,
- const RawAddress& rem_bda) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_ConnectFixedChnl(cid, rem_bda);
-}
-uint16_t bluetooth::shim::L2CA_SendFixedChnlData(uint16_t cid,
- const RawAddress& rem_bda,
- BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_SendFixedChnlData(cid, rem_bda,
- p_buf);
-}
-bool bluetooth::shim::L2CA_RemoveFixedChnl(uint16_t cid,
- const RawAddress& rem_bda) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_RemoveFixedChnl(cid, rem_bda);
-}
-uint16_t bluetooth::shim::L2CA_GetLeHandle(const RawAddress& rem_bda) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_GetLeHandle(rem_bda);
-}
-void bluetooth::shim::L2CA_LeConnectionUpdate(
- const RawAddress& rem_bda, uint16_t min_int, uint16_t max_int,
- uint16_t latency, uint16_t timeout, uint16_t min_ce_len,
- uint16_t max_ce_len) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_l2cap_api::L2CA_LeConnectionUpdate(
- rem_bda, min_int, max_int, latency, timeout, min_ce_len, max_ce_len);
-}
-bool bluetooth::shim::L2CA_EnableUpdateBleConnParams(const RawAddress& rem_bda,
- bool enable) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_EnableUpdateBleConnParams(
- rem_bda, enable);
-}
-bool bluetooth::shim::L2CA_GetRemoteCid(uint16_t lcid, uint16_t* rcid) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_GetRemoteCid(lcid, rcid);
-}
-bool bluetooth::shim::L2CA_SetTxPriority(uint16_t cid,
- tL2CAP_CHNL_PRIORITY priority) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_SetTxPriority(cid, priority);
-}
-bool bluetooth::shim::L2CA_SetLeGattTimeout(const RawAddress& rem_bda,
- uint16_t idle_tout) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_SetLeGattTimeout(rem_bda,
- idle_tout);
-}
-bool bluetooth::shim::L2CA_SetChnlFlushability(uint16_t cid,
- bool is_flushable) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_SetChnlFlushability(
- cid, is_flushable);
-}
-uint16_t bluetooth::shim::L2CA_FlushChannel(uint16_t lcid,
- uint16_t num_to_flush) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_FlushChannel(lcid, num_to_flush);
-}
-bool bluetooth::shim::L2CA_IsLinkEstablished(const RawAddress& bd_addr,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_IsLinkEstablished(bd_addr,
- transport);
-}
-bool bluetooth::shim::L2CA_IsLeLink(uint16_t acl_handle) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_IsLeLink(acl_handle);
-}
-void bluetooth::shim::L2CA_ReadConnectionAddr(const RawAddress& pseudo_addr,
- RawAddress& conn_addr,
- uint8_t* p_addr_type) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_l2cap_api::L2CA_ReadConnectionAddr(
- pseudo_addr, conn_addr, p_addr_type);
-}
-bool bluetooth::shim::L2CA_ReadRemoteConnectionAddr(
- const RawAddress& pseudo_addr, RawAddress& conn_addr,
- uint8_t* p_addr_type) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_ReadRemoteConnectionAddr(
- pseudo_addr, conn_addr, p_addr_type);
-}
-hci_role_t bluetooth::shim::L2CA_GetBleConnRole(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_GetBleConnRole(bd_addr);
-}
-void bluetooth::shim::L2CA_ConnectForSecurity(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_l2cap_api::L2CA_ConnectForSecurity(bd_addr);
-}
-void bluetooth::shim::L2CA_SetBondingState(const RawAddress& bd_addr,
- bool is_bonding) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_l2cap_api::L2CA_SetBondingState(bd_addr, is_bonding);
-}
-void bluetooth::shim::L2CA_DisconnectLink(const RawAddress& remote) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_l2cap_api::L2CA_DisconnectLink(remote);
-}
-uint16_t bluetooth::shim::L2CA_GetNumLinks() {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_GetNumLinks();
-}
-uint16_t bluetooth::shim::L2CA_AllocateLePSM() {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_AllocateLePSM();
-}
-void bluetooth::shim::L2CA_FreeLePSM(uint16_t psm) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_l2cap_api::L2CA_FreeLePSM(psm);
-}
-uint16_t bluetooth::shim::L2CA_RegisterLECoc(uint16_t psm,
- const tL2CAP_APPL_INFO& callbacks,
- uint16_t sec_level,
- tL2CAP_LE_CFG_INFO cfg) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_RegisterLECoc(psm, callbacks,
- sec_level, cfg);
-}
-void bluetooth::shim::L2CA_DeregisterLECoc(uint16_t psm) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_l2cap_api::L2CA_DeregisterLECoc(psm);
-}
-uint16_t bluetooth::shim::L2CA_ConnectLECocReq(uint16_t psm,
- const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_ConnectLECocReq(psm, p_bd_addr,
- p_cfg);
-}
-bool bluetooth::shim::L2CA_GetPeerLECocConfig(uint16_t cid,
- tL2CAP_LE_CFG_INFO* peer_cfg) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_GetPeerLECocConfig(cid,
- peer_cfg);
-}
-bool bluetooth::shim::L2CA_DisconnectLECocReq(uint16_t cid) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_DisconnectLECocReq(cid);
-}
-uint8_t bluetooth::shim::L2CA_LECocDataWrite(uint16_t cid, BT_HDR* p_data) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_l2cap_api::L2CA_LECocDataWrite(cid, p_data);
-}
-void bluetooth::shim::L2CA_SwitchRoleToCentral(const RawAddress& addr) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_l2cap_api::L2CA_SwitchRoleToCentral(addr);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_main_shim_l2cap_api.h b/test/mock/mock_main_shim_l2cap_api.h
deleted file mode 100644
index 778ddbc10..000000000
--- a/test/mock/mock_main_shim_l2cap_api.h
+++ /dev/null
@@ -1,590 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:45
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include "gd/module.h"
-
-#include <future>
-#include <unordered_map>
-#include <unordered_set>
-#include "bta/include/bta_dm_acl.h"
-#include "gd/l2cap/classic/l2cap_classic_module.h"
-#include "gd/l2cap/le/l2cap_le_module.h"
-#include "gd/os/log.h"
-#include "gd/os/queue.h"
-#include "main/shim/acl_api.h"
-#include "main/shim/btm.h"
-#include "main/shim/entry.h"
-#include "main/shim/helpers.h"
-#include "main/shim/l2c_api.h"
-#include "main/shim/stack.h"
-#include "osi/include/allocator.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/acl_hci_link_interface.h"
-#include "stack/include/ble_acl_interface.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btu.h"
-#include "stack/include/gatt_api.h"
-#include "stack/include/sco_hci_link_interface.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace main_shim_l2cap_api {
-
-// Shared state between mocked functions and tests
-// Name: L2CA_ReadRemoteVersion
-// Params: const RawAddress& addr, uint8_t* lmp_version, uint16_t* manufacturer,
-// uint16_t* lmp_sub_version Returns: bool
-struct L2CA_ReadRemoteVersion {
- std::function<bool(const RawAddress& addr, uint8_t* lmp_version,
- uint16_t* manufacturer, uint16_t* lmp_sub_version)>
- body{[](const RawAddress& addr, uint8_t* lmp_version,
- uint16_t* manufacturer,
- uint16_t* lmp_sub_version) { return false; }};
- bool operator()(const RawAddress& addr, uint8_t* lmp_version,
- uint16_t* manufacturer, uint16_t* lmp_sub_version) {
- return body(addr, lmp_version, manufacturer, lmp_sub_version);
- };
-};
-extern struct L2CA_ReadRemoteVersion L2CA_ReadRemoteVersion;
-// Name: L2CA_ReadRemoteFeatures
-// Params: const RawAddress& addr
-// Returns: uint8_t*
-struct L2CA_ReadRemoteFeatures {
- std::function<uint8_t*(const RawAddress& addr)> body{
- [](const RawAddress& addr) { return nullptr; }};
- uint8_t* operator()(const RawAddress& addr) { return body(addr); };
-};
-extern struct L2CA_ReadRemoteFeatures L2CA_ReadRemoteFeatures;
-// Name: L2CA_UseLegacySecurityModule
-// Params:
-// Returns: void
-struct L2CA_UseLegacySecurityModule {
- std::function<void()> body{[]() {}};
- void operator()() { body(); };
-};
-extern struct L2CA_UseLegacySecurityModule L2CA_UseLegacySecurityModule;
-// Name: L2CA_Register
-// Params: uint16_t client_psm, const tL2CAP_APPL_INFO& callbacks, bool
-// enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info, uint16_t my_mtu, uint16_t
-// required_remote_mtu, uint16_t sec_level Returns: uint16_t
-struct L2CA_Register {
- std::function<uint16_t(uint16_t client_psm, const tL2CAP_APPL_INFO& callbacks,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level)>
- body{[](uint16_t client_psm, const tL2CAP_APPL_INFO& callbacks,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info, uint16_t my_mtu,
- uint16_t required_remote_mtu, uint16_t sec_level) { return 0; }};
- uint16_t operator()(uint16_t client_psm, const tL2CAP_APPL_INFO& callbacks,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level) {
- return body(client_psm, callbacks, enable_snoop, p_ertm_info, my_mtu,
- required_remote_mtu, sec_level);
- };
-};
-extern struct L2CA_Register L2CA_Register;
-// Name: L2CA_Deregister
-// Params: uint16_t psm
-// Returns: void
-struct L2CA_Deregister {
- std::function<void(uint16_t psm)> body{[](uint16_t psm) {}};
- void operator()(uint16_t psm) { body(psm); };
-};
-extern struct L2CA_Deregister L2CA_Deregister;
-// Name: L2CA_ConnectReq
-// Params: uint16_t psm, const RawAddress& raw_address
-// Returns: uint16_t
-struct L2CA_ConnectReq {
- std::function<uint16_t(uint16_t psm, const RawAddress& raw_address)> body{
- [](uint16_t psm, const RawAddress& raw_address) { return 0; }};
- uint16_t operator()(uint16_t psm, const RawAddress& raw_address) {
- return body(psm, raw_address);
- };
-};
-extern struct L2CA_ConnectReq L2CA_ConnectReq;
-// Name: L2CA_DisconnectReq
-// Params: uint16_t cid
-// Returns: bool
-struct L2CA_DisconnectReq {
- std::function<bool(uint16_t cid)> body{[](uint16_t cid) { return false; }};
- bool operator()(uint16_t cid) { return body(cid); };
-};
-extern struct L2CA_DisconnectReq L2CA_DisconnectReq;
-// Name: L2CA_DataWrite
-// Params: uint16_t cid, BT_HDR* p_data
-// Returns: uint8_t
-struct L2CA_DataWrite {
- std::function<uint8_t(uint16_t cid, BT_HDR* p_data)> body{
- [](uint16_t cid, BT_HDR* p_data) { return 0; }};
- uint8_t operator()(uint16_t cid, BT_HDR* p_data) {
- return body(cid, p_data);
- };
-};
-extern struct L2CA_DataWrite L2CA_DataWrite;
-// Name: L2CA_ReconfigCreditBasedConnsReq
-// Params: const RawAddress& bd_addr, std::vector<uint16_t>& lcids,
-// tL2CAP_LE_CFG_INFO* p_cfg Returns: bool
-struct L2CA_ReconfigCreditBasedConnsReq {
- std::function<bool(const RawAddress& bd_addr, std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg)>
- body{[](const RawAddress& bd_addr, std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg) { return false; }};
- bool operator()(const RawAddress& bd_addr, std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- return body(bd_addr, lcids, p_cfg);
- };
-};
-extern struct L2CA_ReconfigCreditBasedConnsReq L2CA_ReconfigCreditBasedConnsReq;
-// Name: L2CA_ConnectCreditBasedReq
-// Params: uint16_t psm, const RawAddress& p_bd_addr, tL2CAP_LE_CFG_INFO* p_cfg
-// Returns: std::vector<uint16_t>
-struct L2CA_ConnectCreditBasedReq {
- std::vector<uint16_t> cids;
- std::function<std::vector<uint16_t>(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg)>
- body{[this](uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) { return cids; }};
- std::vector<uint16_t> operator()(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- return body(psm, p_bd_addr, p_cfg);
- };
-};
-extern struct L2CA_ConnectCreditBasedReq L2CA_ConnectCreditBasedReq;
-// Name: L2CA_ConnectCreditBasedRsp
-// Params: const RawAddress& bd_addr, uint8_t id, std::vector<uint16_t>&
-// accepted_lcids, uint16_t result, tL2CAP_LE_CFG_INFO* p_cfg Returns: bool
-struct L2CA_ConnectCreditBasedRsp {
- std::function<bool(const RawAddress& bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids, uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg)>
- body{[](const RawAddress& bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids, uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg) { return false; }};
- bool operator()(const RawAddress& bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids, uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- return body(bd_addr, id, accepted_lcids, result, p_cfg);
- };
-};
-extern struct L2CA_ConnectCreditBasedRsp L2CA_ConnectCreditBasedRsp;
-// Name: L2CA_SetIdleTimeoutByBdAddr
-// Params: const RawAddress& bd_addr, uint16_t timeout, tBT_TRANSPORT transport
-// Returns: bool
-struct L2CA_SetIdleTimeoutByBdAddr {
- std::function<bool(const RawAddress& bd_addr, uint16_t timeout,
- tBT_TRANSPORT transport)>
- body{[](const RawAddress& bd_addr, uint16_t timeout,
- tBT_TRANSPORT transport) { return false; }};
- bool operator()(const RawAddress& bd_addr, uint16_t timeout,
- tBT_TRANSPORT transport) {
- return body(bd_addr, timeout, transport);
- };
-};
-extern struct L2CA_SetIdleTimeoutByBdAddr L2CA_SetIdleTimeoutByBdAddr;
-// Name: L2CA_SetAclPriority
-// Params: uint16_t handle, bool high_priority
-// Returns: bool
-struct L2CA_SetAclPriority {
- std::function<bool(uint16_t handle, bool high_priority)> body{
- [](uint16_t handle, bool high_priority) { return false; }};
- bool operator()(uint16_t handle, bool high_priority) {
- return body(handle, high_priority);
- };
-};
-extern struct L2CA_SetAclPriority L2CA_SetAclPriority;
-// Name: L2CA_SetAclPriority
-// Params: const RawAddress& bd_addr, tL2CAP_PRIORITY priority
-// Returns: bool
-struct L2CA_SetAclPriority2 {
- std::function<bool(const RawAddress& bd_addr, tL2CAP_PRIORITY priority)> body{
- [](const RawAddress& bd_addr, tL2CAP_PRIORITY priority) {
- return false;
- }};
- bool operator()(const RawAddress& bd_addr, tL2CAP_PRIORITY priority) {
- return body(bd_addr, priority);
- };
-};
-extern struct L2CA_SetAclPriority2 L2CA_SetAclPriority2;
-// Name: L2CA_GetPeerFeatures
-// Params: const RawAddress& bd_addr, uint32_t* p_ext_feat, uint8_t* p_chnl_mask
-// Returns: bool
-struct L2CA_GetPeerFeatures {
- std::function<bool(const RawAddress& bd_addr, uint32_t* p_ext_feat,
- uint8_t* p_chnl_mask)>
- body{[](const RawAddress& bd_addr, uint32_t* p_ext_feat,
- uint8_t* p_chnl_mask) { return false; }};
- bool operator()(const RawAddress& bd_addr, uint32_t* p_ext_feat,
- uint8_t* p_chnl_mask) {
- return body(bd_addr, p_ext_feat, p_chnl_mask);
- };
-};
-extern struct L2CA_GetPeerFeatures L2CA_GetPeerFeatures;
-// Name: L2CA_RegisterFixedChannel
-// Params: uint16_t cid, tL2CAP_FIXED_CHNL_REG* p_freg
-// Returns: bool
-struct L2CA_RegisterFixedChannel {
- std::function<bool(uint16_t cid, tL2CAP_FIXED_CHNL_REG* p_freg)> body{
- [](uint16_t cid, tL2CAP_FIXED_CHNL_REG* p_freg) { return false; }};
- bool operator()(uint16_t cid, tL2CAP_FIXED_CHNL_REG* p_freg) {
- return body(cid, p_freg);
- };
-};
-extern struct L2CA_RegisterFixedChannel L2CA_RegisterFixedChannel;
-// Name: L2CA_ConnectFixedChnl
-// Params: uint16_t cid, const RawAddress& rem_bda
-// Returns: bool
-struct L2CA_ConnectFixedChnl {
- std::function<bool(uint16_t cid, const RawAddress& rem_bda)> body{
- [](uint16_t cid, const RawAddress& rem_bda) { return false; }};
- bool operator()(uint16_t cid, const RawAddress& rem_bda) {
- return body(cid, rem_bda);
- };
-};
-extern struct L2CA_ConnectFixedChnl L2CA_ConnectFixedChnl;
-// Name: L2CA_SendFixedChnlData
-// Params: uint16_t cid, const RawAddress& rem_bda, BT_HDR* p_buf
-// Returns: uint16_t
-struct L2CA_SendFixedChnlData {
- std::function<uint16_t(uint16_t cid, const RawAddress& rem_bda,
- BT_HDR* p_buf)>
- body{[](uint16_t cid, const RawAddress& rem_bda, BT_HDR* p_buf) {
- return 0;
- }};
- uint16_t operator()(uint16_t cid, const RawAddress& rem_bda, BT_HDR* p_buf) {
- return body(cid, rem_bda, p_buf);
- };
-};
-extern struct L2CA_SendFixedChnlData L2CA_SendFixedChnlData;
-// Name: L2CA_RemoveFixedChnl
-// Params: uint16_t cid, const RawAddress& rem_bda
-// Returns: bool
-struct L2CA_RemoveFixedChnl {
- std::function<bool(uint16_t cid, const RawAddress& rem_bda)> body{
- [](uint16_t cid, const RawAddress& rem_bda) { return false; }};
- bool operator()(uint16_t cid, const RawAddress& rem_bda) {
- return body(cid, rem_bda);
- };
-};
-extern struct L2CA_RemoveFixedChnl L2CA_RemoveFixedChnl;
-// Name: L2CA_GetLeHandle
-// Params: const RawAddress& rem_bda
-// Returns: uint16_t
-struct L2CA_GetLeHandle {
- std::function<uint16_t(const RawAddress& rem_bda)> body{
- [](const RawAddress& rem_bda) { return 0; }};
- uint16_t operator()(const RawAddress& rem_bda) { return body(rem_bda); };
-};
-extern struct L2CA_GetLeHandle L2CA_GetLeHandle;
-// Name: L2CA_LeConnectionUpdate
-// Params: const RawAddress& rem_bda, uint16_t min_int, uint16_t max_int,
-// uint16_t latency, uint16_t timeout, uint16_t min_ce_len, uint16_t max_ce_len
-// Returns: void
-struct L2CA_LeConnectionUpdate {
- std::function<void(const RawAddress& rem_bda, uint16_t min_int,
- uint16_t max_int, uint16_t latency, uint16_t timeout,
- uint16_t min_ce_len, uint16_t max_ce_len)>
- body{[](const RawAddress& rem_bda, uint16_t min_int, uint16_t max_int,
- uint16_t latency, uint16_t timeout, uint16_t min_ce_len,
- uint16_t max_ce_len) {}};
- void operator()(const RawAddress& rem_bda, uint16_t min_int, uint16_t max_int,
- uint16_t latency, uint16_t timeout, uint16_t min_ce_len,
- uint16_t max_ce_len) {
- body(rem_bda, min_int, max_int, latency, timeout, min_ce_len, max_ce_len);
- };
-};
-extern struct L2CA_LeConnectionUpdate L2CA_LeConnectionUpdate;
-// Name: L2CA_EnableUpdateBleConnParams
-// Params: const RawAddress& rem_bda, bool enable
-// Returns: bool
-struct L2CA_EnableUpdateBleConnParams {
- std::function<bool(const RawAddress& rem_bda, bool enable)> body{
- [](const RawAddress& rem_bda, bool enable) { return false; }};
- bool operator()(const RawAddress& rem_bda, bool enable) {
- return body(rem_bda, enable);
- };
-};
-extern struct L2CA_EnableUpdateBleConnParams L2CA_EnableUpdateBleConnParams;
-// Name: L2CA_GetRemoteCid
-// Params: uint16_t lcid, uint16_t* rcid
-// Returns: bool
-struct L2CA_GetRemoteCid {
- std::function<bool(uint16_t lcid, uint16_t* rcid)> body{
- [](uint16_t lcid, uint16_t* rcid) { return false; }};
- bool operator()(uint16_t lcid, uint16_t* rcid) { return body(lcid, rcid); };
-};
-extern struct L2CA_GetRemoteCid L2CA_GetRemoteCid;
-// Name: L2CA_SetTxPriority
-// Params: uint16_t cid, tL2CAP_CHNL_PRIORITY priority
-// Returns: bool
-struct L2CA_SetTxPriority {
- std::function<bool(uint16_t cid, tL2CAP_CHNL_PRIORITY priority)> body{
- [](uint16_t cid, tL2CAP_CHNL_PRIORITY priority) { return false; }};
- bool operator()(uint16_t cid, tL2CAP_CHNL_PRIORITY priority) {
- return body(cid, priority);
- };
-};
-extern struct L2CA_SetTxPriority L2CA_SetTxPriority;
-// Name: L2CA_SetLeGattTimeout
-// Params: const RawAddress& rem_bda, uint16_t idle_tout
-// Returns: bool
-struct L2CA_SetLeGattTimeout {
- std::function<bool(const RawAddress& rem_bda, uint16_t idle_tout)> body{
- [](const RawAddress& rem_bda, uint16_t idle_tout) { return false; }};
- bool operator()(const RawAddress& rem_bda, uint16_t idle_tout) {
- return body(rem_bda, idle_tout);
- };
-};
-extern struct L2CA_SetLeGattTimeout L2CA_SetLeGattTimeout;
-// Name: L2CA_SetChnlFlushability
-// Params: uint16_t cid, bool is_flushable
-// Returns: bool
-struct L2CA_SetChnlFlushability {
- std::function<bool(uint16_t cid, bool is_flushable)> body{
- [](uint16_t cid, bool is_flushable) { return false; }};
- bool operator()(uint16_t cid, bool is_flushable) {
- return body(cid, is_flushable);
- };
-};
-extern struct L2CA_SetChnlFlushability L2CA_SetChnlFlushability;
-// Name: L2CA_FlushChannel
-// Params: uint16_t lcid, uint16_t num_to_flush
-// Returns: uint16_t
-struct L2CA_FlushChannel {
- std::function<uint16_t(uint16_t lcid, uint16_t num_to_flush)> body{
- [](uint16_t lcid, uint16_t num_to_flush) { return 0; }};
- uint16_t operator()(uint16_t lcid, uint16_t num_to_flush) {
- return body(lcid, num_to_flush);
- };
-};
-extern struct L2CA_FlushChannel L2CA_FlushChannel;
-// Name: L2CA_IsLinkEstablished
-// Params: const RawAddress& bd_addr, tBT_TRANSPORT transport
-// Returns: bool
-struct L2CA_IsLinkEstablished {
- std::function<bool(const RawAddress& bd_addr, tBT_TRANSPORT transport)> body{
- [](const RawAddress& bd_addr, tBT_TRANSPORT transport) { return false; }};
- bool operator()(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- return body(bd_addr, transport);
- };
-};
-extern struct L2CA_IsLinkEstablished L2CA_IsLinkEstablished;
-// Name: L2CA_IsLeLink
-// Params: uint16_t acl_handle
-// Returns: bool
-struct L2CA_IsLeLink {
- std::function<bool(uint16_t acl_handle)> body{
- [](uint16_t acl_handle) { return false; }};
- bool operator()(uint16_t acl_handle) { return body(acl_handle); };
-};
-extern struct L2CA_IsLeLink L2CA_IsLeLink;
-// Name: L2CA_ReadConnectionAddr
-// Params: const RawAddress& pseudo_addr, RawAddress& conn_addr, uint8_t*
-// p_addr_type Returns: void
-struct L2CA_ReadConnectionAddr {
- std::function<void(const RawAddress& pseudo_addr, RawAddress& conn_addr,
- uint8_t* p_addr_type)>
- body{[](const RawAddress& pseudo_addr, RawAddress& conn_addr,
- uint8_t* p_addr_type) {}};
- void operator()(const RawAddress& pseudo_addr, RawAddress& conn_addr,
- uint8_t* p_addr_type) {
- body(pseudo_addr, conn_addr, p_addr_type);
- };
-};
-extern struct L2CA_ReadConnectionAddr L2CA_ReadConnectionAddr;
-// Name: L2CA_ReadRemoteConnectionAddr
-// Params: const RawAddress& pseudo_addr, RawAddress& conn_addr, uint8_t*
-// p_addr_type Returns: bool
-struct L2CA_ReadRemoteConnectionAddr {
- std::function<bool(const RawAddress& pseudo_addr, RawAddress& conn_addr,
- uint8_t* p_addr_type)>
- body{[](const RawAddress& pseudo_addr, RawAddress& conn_addr,
- uint8_t* p_addr_type) { return false; }};
- bool operator()(const RawAddress& pseudo_addr, RawAddress& conn_addr,
- uint8_t* p_addr_type) {
- return body(pseudo_addr, conn_addr, p_addr_type);
- };
-};
-extern struct L2CA_ReadRemoteConnectionAddr L2CA_ReadRemoteConnectionAddr;
-// Name: L2CA_GetBleConnRole
-// Params: const RawAddress& bd_addr
-// Returns: hci_role_t
-struct L2CA_GetBleConnRole {
- std::function<hci_role_t(const RawAddress& bd_addr)> body{
- [](const RawAddress& bd_addr) { return HCI_ROLE_CENTRAL; }};
- hci_role_t operator()(const RawAddress& bd_addr) { return body(bd_addr); };
-};
-extern struct L2CA_GetBleConnRole L2CA_GetBleConnRole;
-// Name: L2CA_ConnectForSecurity
-// Params: const RawAddress& bd_addr
-// Returns: void
-struct L2CA_ConnectForSecurity {
- std::function<void(const RawAddress& bd_addr)> body{
- [](const RawAddress& bd_addr) {}};
- void operator()(const RawAddress& bd_addr) { body(bd_addr); };
-};
-extern struct L2CA_ConnectForSecurity L2CA_ConnectForSecurity;
-// Name: L2CA_SetBondingState
-// Params: const RawAddress& bd_addr, bool is_bonding
-// Returns: void
-struct L2CA_SetBondingState {
- std::function<void(const RawAddress& bd_addr, bool is_bonding)> body{
- [](const RawAddress& bd_addr, bool is_bonding) {}};
- void operator()(const RawAddress& bd_addr, bool is_bonding) {
- body(bd_addr, is_bonding);
- };
-};
-extern struct L2CA_SetBondingState L2CA_SetBondingState;
-// Name: L2CA_DisconnectLink
-// Params: const RawAddress& remote
-// Returns: void
-struct L2CA_DisconnectLink {
- std::function<void(const RawAddress& remote)> body{
- [](const RawAddress& remote) {}};
- void operator()(const RawAddress& remote) { body(remote); };
-};
-extern struct L2CA_DisconnectLink L2CA_DisconnectLink;
-// Name: L2CA_GetNumLinks
-// Params:
-// Returns: uint16_t
-struct L2CA_GetNumLinks {
- std::function<uint16_t()> body{[]() { return 0; }};
- uint16_t operator()() { return body(); };
-};
-extern struct L2CA_GetNumLinks L2CA_GetNumLinks;
-// Name: L2CA_AllocateLePSM
-// Params:
-// Returns: uint16_t
-struct L2CA_AllocateLePSM {
- std::function<uint16_t()> body{[]() { return 0; }};
- uint16_t operator()() { return body(); };
-};
-extern struct L2CA_AllocateLePSM L2CA_AllocateLePSM;
-// Name: L2CA_FreeLePSM
-// Params: uint16_t psm
-// Returns: void
-struct L2CA_FreeLePSM {
- std::function<void(uint16_t psm)> body{[](uint16_t psm) {}};
- void operator()(uint16_t psm) { body(psm); };
-};
-extern struct L2CA_FreeLePSM L2CA_FreeLePSM;
-// Name: L2CA_RegisterLECoc
-// Params: uint16_t psm, const tL2CAP_APPL_INFO& callbacks, uint16_t sec_level,
-// tL2CAP_LE_CFG_INFO cfg Returns: uint16_t
-struct L2CA_RegisterLECoc {
- std::function<uint16_t(uint16_t psm, const tL2CAP_APPL_INFO& callbacks,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg)>
- body{[](uint16_t psm, const tL2CAP_APPL_INFO& callbacks,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg) { return 0; }};
- uint16_t operator()(uint16_t psm, const tL2CAP_APPL_INFO& callbacks,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg) {
- return body(psm, callbacks, sec_level, cfg);
- };
-};
-extern struct L2CA_RegisterLECoc L2CA_RegisterLECoc;
-// Name: L2CA_DeregisterLECoc
-// Params: uint16_t psm
-// Returns: void
-struct L2CA_DeregisterLECoc {
- std::function<void(uint16_t psm)> body{[](uint16_t psm) {}};
- void operator()(uint16_t psm) { body(psm); };
-};
-extern struct L2CA_DeregisterLECoc L2CA_DeregisterLECoc;
-// Name: L2CA_ConnectLECocReq
-// Params: uint16_t psm, const RawAddress& p_bd_addr, tL2CAP_LE_CFG_INFO* p_cfg
-// Returns: uint16_t
-struct L2CA_ConnectLECocReq {
- std::function<uint16_t(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg)>
- body{[](uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) { return 0; }};
- uint16_t operator()(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- return body(psm, p_bd_addr, p_cfg);
- };
-};
-extern struct L2CA_ConnectLECocReq L2CA_ConnectLECocReq;
-// Name: L2CA_GetPeerLECocConfig
-// Params: uint16_t cid, tL2CAP_LE_CFG_INFO* peer_cfg
-// Returns: bool
-struct L2CA_GetPeerLECocConfig {
- std::function<bool(uint16_t cid, tL2CAP_LE_CFG_INFO* peer_cfg)> body{
- [](uint16_t cid, tL2CAP_LE_CFG_INFO* peer_cfg) { return false; }};
- bool operator()(uint16_t cid, tL2CAP_LE_CFG_INFO* peer_cfg) {
- return body(cid, peer_cfg);
- };
-};
-extern struct L2CA_GetPeerLECocConfig L2CA_GetPeerLECocConfig;
-// Name: L2CA_DisconnectLECocReq
-// Params: uint16_t cid
-// Returns: bool
-struct L2CA_DisconnectLECocReq {
- std::function<bool(uint16_t cid)> body{[](uint16_t cid) { return false; }};
- bool operator()(uint16_t cid) { return body(cid); };
-};
-extern struct L2CA_DisconnectLECocReq L2CA_DisconnectLECocReq;
-// Name: L2CA_LECocDataWrite
-// Params: uint16_t cid, BT_HDR* p_data
-// Returns: uint8_t
-struct L2CA_LECocDataWrite {
- std::function<uint8_t(uint16_t cid, BT_HDR* p_data)> body{
- [](uint16_t cid, BT_HDR* p_data) { return 0; }};
- uint8_t operator()(uint16_t cid, BT_HDR* p_data) {
- return body(cid, p_data);
- };
-};
-extern struct L2CA_LECocDataWrite L2CA_LECocDataWrite;
-// Name: L2CA_SwitchRoleToCentral
-// Params: const RawAddress& addr
-// Returns: void
-struct L2CA_SwitchRoleToCentral {
- std::function<void(const RawAddress& addr)> body{
- [](const RawAddress& addr) {}};
- void operator()(const RawAddress& addr) { body(addr); };
-};
-extern struct L2CA_SwitchRoleToCentral L2CA_SwitchRoleToCentral;
-
-} // namespace main_shim_l2cap_api
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_main_shim_le_advertising_manager.cc b/test/mock/mock_main_shim_le_advertising_manager.cc
deleted file mode 100644
index 21b2ceec9..000000000
--- a/test/mock/mock_main_shim_le_advertising_manager.cc
+++ /dev/null
@@ -1,45 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "btif/include/btif_common.h"
-#include "gd/common/init_flags.h"
-#include "include/hardware/ble_advertiser.h"
-#include "main/shim/le_advertising_manager.h"
-#include "stack/include/ble_advertiser.h"
-
-#include <vector>
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-BleAdvertiserInterface* bluetooth::shim::get_ble_advertiser_instance() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void bluetooth::shim::init_advertising_manager() {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_main_shim_le_scanning_manager.cc b/test/mock/mock_main_shim_le_scanning_manager.cc
deleted file mode 100644
index 2649ea37a..000000000
--- a/test/mock/mock_main_shim_le_scanning_manager.cc
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "include/hardware/ble_scanner.h"
-#include "main/shim/le_scanning_manager.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-BleScannerInterface* bluetooth::shim::get_ble_scanner_instance() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void bluetooth::shim::init_scanning_manager() {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_main_shim_link_policy.cc b/test/mock/mock_main_shim_link_policy.cc
deleted file mode 100644
index 06b4bbb1b..000000000
--- a/test/mock/mock_main_shim_link_policy.cc
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:10
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_main_shim_link_policy.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace main_shim_link_policy {
-
-// Function state capture and return values, if needed
-struct set_active_mode set_active_mode;
-struct set_hold_mode set_hold_mode;
-struct set_sniff_mode set_sniff_mode;
-struct controller_supports_link_policy_mode
- controller_supports_link_policy_mode;
-struct RegisterLinkPolicyClient RegisterLinkPolicyClient;
-struct UnregisterLinkPolicyClient UnregisterLinkPolicyClient;
-struct BTM_SetPowerMode BTM_SetPowerMode;
-struct btm_pm_on_mode_change btm_pm_on_mode_change;
-struct BTM_SetSsrParams BTM_SetSsrParams;
-struct btm_pm_on_sniff_subrating btm_pm_on_sniff_subrating;
-
-} // namespace main_shim_link_policy
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-tBTM_STATUS set_active_mode(tACL_CONN& p_acl) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_link_policy::set_active_mode(p_acl);
-}
-tBTM_STATUS set_hold_mode(tACL_CONN& p_acl, uint16_t max, uint16_t min) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_link_policy::set_hold_mode(p_acl, max, min);
-}
-tBTM_STATUS set_sniff_mode(tACL_CONN& p_acl, uint16_t max_interval,
- uint16_t min_interval, uint16_t attempt,
- uint16_t timeout) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_link_policy::set_sniff_mode(
- p_acl, max_interval, min_interval, attempt, timeout);
-}
-bool controller_supports_link_policy_mode(const tBTM_PM_MODE& mode,
- bool interop_check) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_link_policy::
- controller_supports_link_policy_mode(mode, interop_check);
-}
-bool bluetooth::shim::RegisterLinkPolicyClient(tBTM_PM_STATUS_CBACK* p_cb) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_link_policy::RegisterLinkPolicyClient(p_cb);
-}
-bool bluetooth::shim::UnregisterLinkPolicyClient(tBTM_PM_STATUS_CBACK* p_cb) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_link_policy::UnregisterLinkPolicyClient(p_cb);
-}
-tBTM_STATUS bluetooth::shim::BTM_SetPowerMode(uint16_t handle,
- const tBTM_PM_PWR_MD& new_mode) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_link_policy::BTM_SetPowerMode(handle, new_mode);
-}
-void bluetooth::shim::btm_pm_on_mode_change(tHCI_STATUS status, uint16_t handle,
- tHCI_MODE hci_mode,
- uint16_t interval) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_link_policy::btm_pm_on_mode_change(status, handle,
- hci_mode, interval);
-}
-tBTM_STATUS bluetooth::shim::BTM_SetSsrParams(uint16_t handle, uint16_t max_lat,
- uint16_t min_rmt_to,
- uint16_t min_loc_to) {
- mock_function_count_map[__func__]++;
- return test::mock::main_shim_link_policy::BTM_SetSsrParams(
- handle, max_lat, min_rmt_to, min_loc_to);
-}
-void bluetooth::shim::btm_pm_on_sniff_subrating(
- tHCI_STATUS status, uint16_t handle, uint16_t maximum_transmit_latency,
- UNUSED_ATTR uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout, uint16_t minimum_local_timeout) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_link_policy::btm_pm_on_sniff_subrating(
- status, handle, maximum_transmit_latency, maximum_receive_latency,
- minimum_remote_timeout, minimum_local_timeout);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_main_shim_link_policy.h b/test/mock/mock_main_shim_link_policy.h
deleted file mode 100644
index fe0f4cf4f..000000000
--- a/test/mock/mock_main_shim_link_policy.h
+++ /dev/null
@@ -1,201 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:10
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include <base/bind.h>
-#include <base/location.h>
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <memory>
-#include "device/include/interop.h"
-#include "gd/module.h"
-#include "hci/controller.h"
-#include "main/shim/controller.h"
-#include "main/shim/dumpsys.h"
-#include "main/shim/link_policy.h"
-#include "main/shim/stack.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/btm_ble_api_types.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcidefs.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace main_shim_link_policy {
-
-// Shared state between mocked functions and tests
-// Name: set_active_mode
-// Params: tACL_CONN& p_acl
-// Returns: tBTM_STATUS
-struct set_active_mode {
- std::function<tBTM_STATUS(tACL_CONN& p_acl)> body{
- [](tACL_CONN& p_acl) { return 0; }};
- tBTM_STATUS operator()(tACL_CONN& p_acl) { return body(p_acl); };
-};
-extern struct set_active_mode set_active_mode;
-// Name: set_hold_mode
-// Params: tACL_CONN& p_acl, uint16_t max, uint16_t min
-// Returns: tBTM_STATUS
-struct set_hold_mode {
- std::function<tBTM_STATUS(tACL_CONN& p_acl, uint16_t max, uint16_t min)> body{
- [](tACL_CONN& p_acl, uint16_t max, uint16_t min) { return 0; }};
- tBTM_STATUS operator()(tACL_CONN& p_acl, uint16_t max, uint16_t min) {
- return body(p_acl, max, min);
- };
-};
-extern struct set_hold_mode set_hold_mode;
-// Name: set_sniff_mode
-// Params: tACL_CONN& p_acl, uint16_t max_interval, uint16_t min_interval,
-// uint16_t attempt, uint16_t timeout Returns: tBTM_STATUS
-struct set_sniff_mode {
- std::function<tBTM_STATUS(tACL_CONN& p_acl, uint16_t max_interval,
- uint16_t min_interval, uint16_t attempt,
- uint16_t timeout)>
- body{[](tACL_CONN& p_acl, uint16_t max_interval, uint16_t min_interval,
- uint16_t attempt, uint16_t timeout) { return 0; }};
- tBTM_STATUS operator()(tACL_CONN& p_acl, uint16_t max_interval,
- uint16_t min_interval, uint16_t attempt,
- uint16_t timeout) {
- return body(p_acl, max_interval, min_interval, attempt, timeout);
- };
-};
-extern struct set_sniff_mode set_sniff_mode;
-// Name: controller_supports_link_policy_mode
-// Params: const tBTM_PM_MODE& mode, bool interop_check
-// Returns: bool
-struct controller_supports_link_policy_mode {
- std::function<bool(const tBTM_PM_MODE& mode, bool interop_check)> body{
- [](const tBTM_PM_MODE& mode, bool interop_check) { return false; }};
- bool operator()(const tBTM_PM_MODE& mode, bool interop_check) {
- return body(mode, interop_check);
- };
-};
-extern struct controller_supports_link_policy_mode
- controller_supports_link_policy_mode;
-// Name: bluetooth::shim::RegisterLinkPolicyClient
-// Params: tBTM_PM_STATUS_CBACK* p_cb
-// Returns: bool
-struct RegisterLinkPolicyClient {
- std::function<bool(tBTM_PM_STATUS_CBACK* p_cb)> body{
- [](tBTM_PM_STATUS_CBACK* p_cb) { return false; }};
- bool operator()(tBTM_PM_STATUS_CBACK* p_cb) { return body(p_cb); };
-};
-extern struct RegisterLinkPolicyClient RegisterLinkPolicyClient;
-// Name: bluetooth::shim::UnregisterLinkPolicyClient
-// Params: tBTM_PM_STATUS_CBACK* p_cb
-// Returns: bool
-struct UnregisterLinkPolicyClient {
- std::function<bool(tBTM_PM_STATUS_CBACK* p_cb)> body{
- [](tBTM_PM_STATUS_CBACK* p_cb) { return false; }};
- bool operator()(tBTM_PM_STATUS_CBACK* p_cb) { return body(p_cb); };
-};
-extern struct UnregisterLinkPolicyClient UnregisterLinkPolicyClient;
-// Name: bluetooth::shim::BTM_SetPowerMode
-// Params: uint16_t handle, const tBTM_PM_PWR_MD& new_mode
-// Returns: tBTM_STATUS
-struct BTM_SetPowerMode {
- std::function<tBTM_STATUS(uint16_t handle, const tBTM_PM_PWR_MD& new_mode)>
- body{[](uint16_t handle, const tBTM_PM_PWR_MD& new_mode) { return 0; }};
- tBTM_STATUS operator()(uint16_t handle, const tBTM_PM_PWR_MD& new_mode) {
- return body(handle, new_mode);
- };
-};
-extern struct BTM_SetPowerMode BTM_SetPowerMode;
-// Name: bluetooth::shim::btm_pm_on_mode_change
-// Params: tHCI_STATUS status, uint16_t handle, tHCI_MODE hci_mode, uint16_t
-// interval Returns: void
-struct btm_pm_on_mode_change {
- std::function<void(tHCI_STATUS status, uint16_t handle, tHCI_MODE hci_mode,
- uint16_t interval)>
- body{[](tHCI_STATUS status, uint16_t handle, tHCI_MODE hci_mode,
- uint16_t interval) {}};
- void operator()(tHCI_STATUS status, uint16_t handle, tHCI_MODE hci_mode,
- uint16_t interval) {
- body(status, handle, hci_mode, interval);
- };
-};
-extern struct btm_pm_on_mode_change btm_pm_on_mode_change;
-// Name: bluetooth::shim::BTM_SetSsrParams
-// Params: uint16_t handle, uint16_t max_lat, uint16_t min_rmt_to, uint16_t
-// min_loc_to Returns: tBTM_STATUS
-struct BTM_SetSsrParams {
- std::function<tBTM_STATUS(uint16_t handle, uint16_t max_lat,
- uint16_t min_rmt_to, uint16_t min_loc_to)>
- body{[](uint16_t handle, uint16_t max_lat, uint16_t min_rmt_to,
- uint16_t min_loc_to) { return 0; }};
- tBTM_STATUS operator()(uint16_t handle, uint16_t max_lat, uint16_t min_rmt_to,
- uint16_t min_loc_to) {
- return body(handle, max_lat, min_rmt_to, min_loc_to);
- };
-};
-extern struct BTM_SetSsrParams BTM_SetSsrParams;
-// Name: bluetooth::shim::btm_pm_on_sniff_subrating
-// Params: tHCI_STATUS status, uint16_t handle, uint16_t
-// maximum_transmit_latency, UNUSED_ATTR uint16_t maximum_receive_latency,
-// uint16_t minimum_remote_timeout, uint16_t minimum_local_timeout Returns: void
-struct btm_pm_on_sniff_subrating {
- std::function<void(
- tHCI_STATUS status, uint16_t handle, uint16_t maximum_transmit_latency,
- UNUSED_ATTR uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout, uint16_t minimum_local_timeout)>
- body{[](tHCI_STATUS status, uint16_t handle,
- uint16_t maximum_transmit_latency,
- UNUSED_ATTR uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) {}};
- void operator()(tHCI_STATUS status, uint16_t handle,
- uint16_t maximum_transmit_latency,
- UNUSED_ATTR uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) {
- body(status, handle, maximum_transmit_latency, maximum_receive_latency,
- minimum_remote_timeout, minimum_local_timeout);
- };
-};
-extern struct btm_pm_on_sniff_subrating btm_pm_on_sniff_subrating;
-
-} // namespace main_shim_link_policy
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_main_shim_metric_id_api.cc b/test/mock/mock_main_shim_metric_id_api.cc
deleted file mode 100644
index 4c5e3f499..000000000
--- a/test/mock/mock_main_shim_metric_id_api.cc
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:7
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "gd/common/metric_id_manager.h"
-#include "main/shim/metric_id_api.h"
-#include "main/shim/shim.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace bluetooth {
-namespace shim {
-
-bool InitMetricIdAllocator(
- const std::unordered_map<RawAddress, int>& paired_device_map,
- CallbackLegacy save_id_callback, CallbackLegacy forget_device_callback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool CloseMetricIdAllocator() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool IsEmptyMetricIdAllocator() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool IsValidIdFromMetricIdAllocator(const int id) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SaveDeviceOnMetricIdAllocator(const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
- return false;
-}
-int AllocateIdFromMetricIdAllocator(const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void ForgetDeviceFromMetricIdAllocator(const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
-}
-
-} // namespace shim
-} // namespace bluetooth
diff --git a/test/mock/mock_main_shim_metrics_api.cc b/test/mock/mock_main_shim_metrics_api.cc
deleted file mode 100644
index 76c5e3c0d..000000000
--- a/test/mock/mock_main_shim_metrics_api.cc
+++ /dev/null
@@ -1,180 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:12
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include "gd/hci/address.h"
-#include "gd/os/metrics.h"
-#include "main/shim/helpers.h"
-#include "main/shim/metrics_api.h"
-#include "types/raw_address.h"
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_main_shim_metrics_api.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace main_shim_metrics_api {
-
-// Function state capture and return values, if needed
-struct LogMetricLinkLayerConnectionEvent LogMetricLinkLayerConnectionEvent;
-struct LogMetricA2dpAudioUnderrunEvent LogMetricA2dpAudioUnderrunEvent;
-struct LogMetricA2dpAudioOverrunEvent LogMetricA2dpAudioOverrunEvent;
-struct LogMetricA2dpPlaybackEvent LogMetricA2dpPlaybackEvent;
-struct LogMetricReadRssiResult LogMetricReadRssiResult;
-struct LogMetricReadFailedContactCounterResult
- LogMetricReadFailedContactCounterResult;
-struct LogMetricReadTxPowerLevelResult LogMetricReadTxPowerLevelResult;
-struct LogMetricSmpPairingEvent LogMetricSmpPairingEvent;
-struct LogMetricClassicPairingEvent LogMetricClassicPairingEvent;
-struct LogMetricSdpAttribute LogMetricSdpAttribute;
-struct LogMetricSocketConnectionState LogMetricSocketConnectionState;
-struct LogMetricManufacturerInfo LogMetricManufacturerInfo;
-
-} // namespace main_shim_metrics_api
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-void bluetooth::shim::LogMetricLinkLayerConnectionEvent(
- const RawAddress* raw_address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction, uint16_t link_type,
- uint32_t hci_cmd, uint16_t hci_event, uint16_t hci_ble_event,
- uint16_t cmd_status, uint16_t reason_code) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricLinkLayerConnectionEvent(
- raw_address, connection_handle, direction, link_type, hci_cmd, hci_event,
- hci_ble_event, cmd_status, reason_code);
-}
-void bluetooth::shim::LogMetricA2dpAudioUnderrunEvent(
- const RawAddress& raw_address, uint64_t encoding_interval_millis,
- int num_missing_pcm_bytes) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricA2dpAudioUnderrunEvent(
- raw_address, encoding_interval_millis, num_missing_pcm_bytes);
-}
-void bluetooth::shim::LogMetricA2dpAudioOverrunEvent(
- const RawAddress& raw_address, uint64_t encoding_interval_millis,
- int num_dropped_buffers, int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricA2dpAudioOverrunEvent(
- raw_address, encoding_interval_millis, num_dropped_buffers,
- num_dropped_encoded_frames, num_dropped_encoded_bytes);
-}
-void bluetooth::shim::LogMetricA2dpPlaybackEvent(const RawAddress& raw_address,
- int playback_state,
- int audio_coding_mode) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricA2dpPlaybackEvent(
- raw_address, playback_state, audio_coding_mode);
-}
-void bluetooth::shim::LogMetricReadRssiResult(const RawAddress& raw_address,
- uint16_t handle,
- uint32_t cmd_status,
- int8_t rssi) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricReadRssiResult(
- raw_address, handle, cmd_status, rssi);
-}
-void bluetooth::shim::LogMetricReadFailedContactCounterResult(
- const RawAddress& raw_address, uint16_t handle, uint32_t cmd_status,
- int32_t failed_contact_counter) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricReadFailedContactCounterResult(
- raw_address, handle, cmd_status, failed_contact_counter);
-}
-void bluetooth::shim::LogMetricReadTxPowerLevelResult(
- const RawAddress& raw_address, uint16_t handle, uint32_t cmd_status,
- int32_t transmit_power_level) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricReadTxPowerLevelResult(
- raw_address, handle, cmd_status, transmit_power_level);
-}
-void bluetooth::shim::LogMetricSmpPairingEvent(
- const RawAddress& raw_address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction, uint8_t smp_fail_reason) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricSmpPairingEvent(
- raw_address, smp_cmd, direction, smp_fail_reason);
-}
-void bluetooth::shim::LogMetricClassicPairingEvent(
- const RawAddress& raw_address, uint16_t handle, uint32_t hci_cmd,
- uint16_t hci_event, uint16_t cmd_status, uint16_t reason_code,
- int64_t event_value) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricClassicPairingEvent(
- raw_address, handle, hci_cmd, hci_event, cmd_status, reason_code,
- event_value);
-}
-void bluetooth::shim::LogMetricSdpAttribute(const RawAddress& raw_address,
- uint16_t protocol_uuid,
- uint16_t attribute_id,
- size_t attribute_size,
- const char* attribute_value) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricSdpAttribute(
- raw_address, protocol_uuid, attribute_id, attribute_size,
- attribute_value);
-}
-void bluetooth::shim::LogMetricSocketConnectionState(
- const RawAddress& raw_address, int port, int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes, int64_t rx_bytes, int uid, int server_port,
- android::bluetooth::SocketRoleEnum socket_role) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricSocketConnectionState(
- raw_address, port, type, connection_state, tx_bytes, rx_bytes, uid,
- server_port, socket_role);
-}
-void bluetooth::shim::LogMetricManufacturerInfo(
- const RawAddress& raw_address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name, const std::string& manufacturer,
- const std::string& model, const std::string& hardware_version,
- const std::string& software_version) {
- mock_function_count_map[__func__]++;
- test::mock::main_shim_metrics_api::LogMetricManufacturerInfo(
- raw_address, source_type, source_name, manufacturer, model,
- hardware_version, software_version);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_main_shim_metrics_api.h b/test/mock/mock_main_shim_metrics_api.h
deleted file mode 100644
index aba10a800..000000000
--- a/test/mock/mock_main_shim_metrics_api.h
+++ /dev/null
@@ -1,287 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:12
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include "gd/hci/address.h"
-#include "gd/os/metrics.h"
-#include "main/shim/helpers.h"
-#include "main/shim/metrics_api.h"
-#include "types/raw_address.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace main_shim_metrics_api {
-
-// Shared state between mocked functions and tests
-// Name: LogMetricLinkLayerConnectionEvent
-// Params: const RawAddress* raw_address, uint32_t connection_handle,
-// android::bluetooth::DirectionEnum direction, uint16_t link_type, uint32_t
-// hci_cmd, uint16_t hci_event, uint16_t hci_ble_event, uint16_t cmd_status,
-// uint16_t reason_code Returns: void
-struct LogMetricLinkLayerConnectionEvent {
- std::function<void(const RawAddress* raw_address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction,
- uint16_t link_type, uint32_t hci_cmd, uint16_t hci_event,
- uint16_t hci_ble_event, uint16_t cmd_status,
- uint16_t reason_code)>
- body{[](const RawAddress* raw_address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction, uint16_t link_type,
- uint32_t hci_cmd, uint16_t hci_event, uint16_t hci_ble_event,
- uint16_t cmd_status, uint16_t reason_code) {}};
- void operator()(const RawAddress* raw_address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction,
- uint16_t link_type, uint32_t hci_cmd, uint16_t hci_event,
- uint16_t hci_ble_event, uint16_t cmd_status,
- uint16_t reason_code) {
- body(raw_address, connection_handle, direction, link_type, hci_cmd,
- hci_event, hci_ble_event, cmd_status, reason_code);
- };
-};
-extern struct LogMetricLinkLayerConnectionEvent
- LogMetricLinkLayerConnectionEvent;
-// Name: LogMetricA2dpAudioUnderrunEvent
-// Params: const RawAddress& raw_address, uint64_t encoding_interval_millis, int
-// num_missing_pcm_bytes Returns: void
-struct LogMetricA2dpAudioUnderrunEvent {
- std::function<void(const RawAddress& raw_address,
- uint64_t encoding_interval_millis,
- int num_missing_pcm_bytes)>
- body{[](const RawAddress& raw_address, uint64_t encoding_interval_millis,
- int num_missing_pcm_bytes) {}};
- void operator()(const RawAddress& raw_address,
- uint64_t encoding_interval_millis,
- int num_missing_pcm_bytes) {
- body(raw_address, encoding_interval_millis, num_missing_pcm_bytes);
- };
-};
-extern struct LogMetricA2dpAudioUnderrunEvent LogMetricA2dpAudioUnderrunEvent;
-// Name: LogMetricA2dpAudioOverrunEvent
-// Params: const RawAddress& raw_address, uint64_t encoding_interval_millis, int
-// num_dropped_buffers, int num_dropped_encoded_frames, int
-// num_dropped_encoded_bytes Returns: void
-struct LogMetricA2dpAudioOverrunEvent {
- std::function<void(const RawAddress& raw_address,
- uint64_t encoding_interval_millis, int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes)>
- body{[](const RawAddress& raw_address, uint64_t encoding_interval_millis,
- int num_dropped_buffers, int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes) {}};
- void operator()(const RawAddress& raw_address,
- uint64_t encoding_interval_millis, int num_dropped_buffers,
- int num_dropped_encoded_frames,
- int num_dropped_encoded_bytes) {
- body(raw_address, encoding_interval_millis, num_dropped_buffers,
- num_dropped_encoded_frames, num_dropped_encoded_bytes);
- };
-};
-extern struct LogMetricA2dpAudioOverrunEvent LogMetricA2dpAudioOverrunEvent;
-// Name: LogMetricA2dpPlaybackEvent
-// Params: const RawAddress& raw_address, int playback_state, int
-// audio_coding_mode Returns: void
-struct LogMetricA2dpPlaybackEvent {
- std::function<void(const RawAddress& raw_address, int playback_state,
- int audio_coding_mode)>
- body{[](const RawAddress& raw_address, int playback_state,
- int audio_coding_mode) {}};
- void operator()(const RawAddress& raw_address, int playback_state,
- int audio_coding_mode) {
- body(raw_address, playback_state, audio_coding_mode);
- };
-};
-extern struct LogMetricA2dpPlaybackEvent LogMetricA2dpPlaybackEvent;
-// Name: LogMetricReadRssiResult
-// Params: const RawAddress& raw_address, uint16_t handle, uint32_t cmd_status,
-// int8_t rssi Returns: void
-struct LogMetricReadRssiResult {
- std::function<void(const RawAddress& raw_address, uint16_t handle,
- uint32_t cmd_status, int8_t rssi)>
- body{[](const RawAddress& raw_address, uint16_t handle,
- uint32_t cmd_status, int8_t rssi) {}};
- void operator()(const RawAddress& raw_address, uint16_t handle,
- uint32_t cmd_status, int8_t rssi) {
- body(raw_address, handle, cmd_status, rssi);
- };
-};
-extern struct LogMetricReadRssiResult LogMetricReadRssiResult;
-// Name: LogMetricReadFailedContactCounterResult
-// Params: const RawAddress& raw_address, uint16_t handle, uint32_t cmd_status,
-// int32_t failed_contact_counter Returns: void
-struct LogMetricReadFailedContactCounterResult {
- std::function<void(const RawAddress& raw_address, uint16_t handle,
- uint32_t cmd_status, int32_t failed_contact_counter)>
- body{[](const RawAddress& raw_address, uint16_t handle,
- uint32_t cmd_status, int32_t failed_contact_counter) {}};
- void operator()(const RawAddress& raw_address, uint16_t handle,
- uint32_t cmd_status, int32_t failed_contact_counter) {
- body(raw_address, handle, cmd_status, failed_contact_counter);
- };
-};
-extern struct LogMetricReadFailedContactCounterResult
- LogMetricReadFailedContactCounterResult;
-// Name: LogMetricReadTxPowerLevelResult
-// Params: const RawAddress& raw_address, uint16_t handle, uint32_t cmd_status,
-// int32_t transmit_power_level Returns: void
-struct LogMetricReadTxPowerLevelResult {
- std::function<void(const RawAddress& raw_address, uint16_t handle,
- uint32_t cmd_status, int32_t transmit_power_level)>
- body{[](const RawAddress& raw_address, uint16_t handle,
- uint32_t cmd_status, int32_t transmit_power_level) {}};
- void operator()(const RawAddress& raw_address, uint16_t handle,
- uint32_t cmd_status, int32_t transmit_power_level) {
- body(raw_address, handle, cmd_status, transmit_power_level);
- };
-};
-extern struct LogMetricReadTxPowerLevelResult LogMetricReadTxPowerLevelResult;
-// Name: LogMetricSmpPairingEvent
-// Params: const RawAddress& raw_address, uint8_t smp_cmd,
-// android::bluetooth::DirectionEnum direction, uint8_t smp_fail_reason Returns:
-// void
-struct LogMetricSmpPairingEvent {
- std::function<void(const RawAddress& raw_address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason)>
- body{[](const RawAddress& raw_address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason) {}};
- void operator()(const RawAddress& raw_address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason) {
- body(raw_address, smp_cmd, direction, smp_fail_reason);
- };
-};
-extern struct LogMetricSmpPairingEvent LogMetricSmpPairingEvent;
-// Name: LogMetricClassicPairingEvent
-// Params: const RawAddress& raw_address, uint16_t handle, uint32_t hci_cmd,
-// uint16_t hci_event, uint16_t cmd_status, uint16_t reason_code, int64_t
-// event_value Returns: void
-struct LogMetricClassicPairingEvent {
- std::function<void(const RawAddress& raw_address, uint16_t handle,
- uint32_t hci_cmd, uint16_t hci_event, uint16_t cmd_status,
- uint16_t reason_code, int64_t event_value)>
- body{[](const RawAddress& raw_address, uint16_t handle, uint32_t hci_cmd,
- uint16_t hci_event, uint16_t cmd_status, uint16_t reason_code,
- int64_t event_value) {}};
- void operator()(const RawAddress& raw_address, uint16_t handle,
- uint32_t hci_cmd, uint16_t hci_event, uint16_t cmd_status,
- uint16_t reason_code, int64_t event_value) {
- body(raw_address, handle, hci_cmd, hci_event, cmd_status, reason_code,
- event_value);
- };
-};
-extern struct LogMetricClassicPairingEvent LogMetricClassicPairingEvent;
-// Name: LogMetricSdpAttribute
-// Params: const RawAddress& raw_address, uint16_t protocol_uuid, uint16_t
-// attribute_id, size_t attribute_size, const char* attribute_value Returns:
-// void
-struct LogMetricSdpAttribute {
- std::function<void(const RawAddress& raw_address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value)>
- body{[](const RawAddress& raw_address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value) {}};
- void operator()(const RawAddress& raw_address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value) {
- body(raw_address, protocol_uuid, attribute_id, attribute_size,
- attribute_value);
- };
-};
-extern struct LogMetricSdpAttribute LogMetricSdpAttribute;
-// Name: LogMetricSocketConnectionState
-// Params: const RawAddress& raw_address, int port, int type,
-// android::bluetooth::SocketConnectionstateEnum connection_state, int64_t
-// tx_bytes, int64_t rx_bytes, int uid, int server_port,
-// android::bluetooth::SocketRoleEnum socket_role Returns: void
-struct LogMetricSocketConnectionState {
- std::function<void(
- const RawAddress& raw_address, int port, int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes, int64_t rx_bytes, int uid, int server_port,
- android::bluetooth::SocketRoleEnum socket_role)>
- body{[](const RawAddress& raw_address, int port, int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes, int64_t rx_bytes, int uid, int server_port,
- android::bluetooth::SocketRoleEnum socket_role) {}};
- void operator()(
- const RawAddress& raw_address, int port, int type,
- android::bluetooth::SocketConnectionstateEnum connection_state,
- int64_t tx_bytes, int64_t rx_bytes, int uid, int server_port,
- android::bluetooth::SocketRoleEnum socket_role) {
- body(raw_address, port, type, connection_state, tx_bytes, rx_bytes, uid,
- server_port, socket_role);
- };
-};
-extern struct LogMetricSocketConnectionState LogMetricSocketConnectionState;
-// Name: LogMetricManufacturerInfo
-// Params: const RawAddress& raw_address, android::bluetooth::DeviceInfoSrcEnum
-// source_type, const std::string& source_name, const std::string& manufacturer,
-// const std::string& model, const std::string& hardware_version, const
-// std::string& software_version Returns: void
-struct LogMetricManufacturerInfo {
- std::function<void(const RawAddress& raw_address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer, const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version)>
- body{[](const RawAddress& raw_address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name, const std::string& manufacturer,
- const std::string& model, const std::string& hardware_version,
- const std::string& software_version) {}};
- void operator()(const RawAddress& raw_address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer, const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version) {
- body(raw_address, source_type, source_name, manufacturer, model,
- hardware_version, software_version);
- };
-};
-extern struct LogMetricManufacturerInfo LogMetricManufacturerInfo;
-
-} // namespace main_shim_metrics_api
-} // namespace mock
-} // namespace test
-
-// END mockcify generation \ No newline at end of file
diff --git a/test/mock/mock_stack_a2dp_api.cc b/test/mock/mock_stack_a2dp_api.cc
deleted file mode 100644
index db59f9f0f..000000000
--- a/test/mock/mock_stack_a2dp_api.cc
+++ /dev/null
@@ -1,67 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:9
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "a2dp_api.h"
-#include "avdt_api.h"
-#include "bt_common.h"
-#include "bt_target.h"
-#include "osi/include/log.h"
-#include "sdpdefs.h"
-#include "stack/a2dp/a2dp_int.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tA2DP_STATUS A2DP_AddRecord(uint16_t service_uuid, char* p_service_name,
- char* p_provider_name, uint16_t features,
- uint32_t sdp_handle) {
- mock_function_count_map[__func__]++;
- return A2DP_SUCCESS;
-}
-tA2DP_STATUS A2DP_FindService(uint16_t service_uuid, const RawAddress& bd_addr,
- tA2DP_SDP_DB_PARAMS* p_db,
- tA2DP_FIND_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return A2DP_SUCCESS;
-}
-uint16_t A2DP_GetAvdtpVersion() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t A2DP_BitsSet(uint64_t num) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t A2DP_SetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void A2DP_Init(void) { mock_function_count_map[__func__]++; }
-void a2dp_set_avdt_sdp_ver(uint16_t avdt_sdp_ver) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_a2dp_codec_config.cc b/test/mock/mock_stack_a2dp_codec_config.cc
deleted file mode 100644
index 8d0132826..000000000
--- a/test/mock/mock_stack_a2dp_codec_config.cc
+++ /dev/null
@@ -1,351 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:67
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <inttypes.h>
-#include "a2dp_aac.h"
-#include "a2dp_codec_api.h"
-#include "a2dp_sbc.h"
-#include "a2dp_vendor.h"
-#include "bta/av/bta_av_int.h"
-#include "osi/include/log.h"
-#include "osi/include/properties.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-A2dpCodecConfig* A2dpCodecConfig::createCodec(
- btav_a2dp_codec_index_t codec_index,
- btav_a2dp_codec_priority_t codec_priority) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-A2dpCodecConfig* A2dpCodecs::findSinkCodecConfig(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-A2dpCodecConfig* A2dpCodecs::findSourceCodecConfig(
- const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-A2dpCodecConfig::A2dpCodecConfig(btav_a2dp_codec_index_t codec_index,
- const std::string& name,
- btav_a2dp_codec_priority_t codec_priority)
- : codec_index_(codec_index),
- name_(name),
- default_codec_priority_(codec_priority) {
- mock_function_count_map[__func__]++;
-}
-A2dpCodecConfig::~A2dpCodecConfig() { mock_function_count_map[__func__]++; }
-A2dpCodecs::A2dpCodecs(
- const std::vector<btav_a2dp_codec_config_t>& codec_priorities)
- : current_codec_config_(nullptr) {
- mock_function_count_map[__func__]++;
-}
-A2dpCodecs::~A2dpCodecs() { mock_function_count_map[__func__]++; }
-bool A2DP_AdjustCodec(uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_BuildCodecHeader(const uint8_t* p_codec_info, BT_HDR* p_buf,
- uint16_t frames_per_packet) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_CodecEquals(const uint8_t* p_codec_info_a,
- const uint8_t* p_codec_info_b) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_CodecTypeEquals(const uint8_t* p_codec_info_a,
- const uint8_t* p_codec_info_b) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_GetPacketTimestamp(const uint8_t* p_codec_info, const uint8_t* p_data,
- uint32_t* p_timestamp) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_InitCodecConfig(btav_a2dp_codec_index_t codec_index,
- AvdtpSepConfig* p_cfg) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsPeerSinkCodecValid(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsPeerSourceCodecSupported(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsPeerSourceCodecValid(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsSinkCodecSupported(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsSinkCodecValid(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_IsSourceCodecValid(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2DP_UsesRtpHeader(bool content_protection_enabled,
- const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::codecConfigIsValid(
- const btav_a2dp_codec_config_t& codec_config) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::copyOutOtaCodecConfig(uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::getCodecSpecificConfig(tBT_A2DP_OFFLOAD* p_a2dp_offload) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::isCodecConfigEmpty(
- const btav_a2dp_codec_config_t& codec_config) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::isValid() const {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecConfig::setCodecUserConfig(
- const btav_a2dp_codec_config_t& codec_user_config,
- const btav_a2dp_codec_config_t& codec_audio_config,
- const tA2DP_ENCODER_INIT_PEER_PARAMS* p_peer_params,
- const uint8_t* p_peer_codec_info, bool is_capability,
- uint8_t* p_result_codec_config, bool* p_restart_input,
- bool* p_restart_output, bool* p_config_updated) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::getCodecConfigAndCapabilities(
- btav_a2dp_codec_config_t* p_codec_config,
- std::vector<btav_a2dp_codec_config_t>* p_codecs_local_capabilities,
- std::vector<btav_a2dp_codec_config_t>* p_codecs_selectable_capabilities) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::init() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::isSupportedCodec(btav_a2dp_codec_index_t codec_index) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setCodecAudioConfig(
- const btav_a2dp_codec_config_t& codec_audio_config,
- const tA2DP_ENCODER_INIT_PEER_PARAMS* p_peer_params,
- const uint8_t* p_peer_sink_capabilities, uint8_t* p_result_codec_config,
- bool* p_restart_output, bool* p_config_updated) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setCodecConfig(const uint8_t* p_peer_codec_info,
- bool is_capability,
- uint8_t* p_result_codec_config,
- bool select_current_codec) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setCodecOtaConfig(
- const uint8_t* p_ota_codec_config,
- const tA2DP_ENCODER_INIT_PEER_PARAMS* p_peer_params,
- uint8_t* p_result_codec_config, bool* p_restart_input,
- bool* p_restart_output, bool* p_config_updated) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setCodecUserConfig(
- const btav_a2dp_codec_config_t& codec_user_config,
- const tA2DP_ENCODER_INIT_PEER_PARAMS* p_peer_params,
- const uint8_t* p_peer_sink_capabilities, uint8_t* p_result_codec_config,
- bool* p_restart_input, bool* p_restart_output, bool* p_config_updated) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setPeerSinkCodecCapabilities(
- const uint8_t* p_peer_codec_capabilities) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setPeerSourceCodecCapabilities(
- const uint8_t* p_peer_codec_capabilities) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool A2dpCodecs::setSinkCodecConfig(const uint8_t* p_peer_codec_info,
- bool is_capability,
- uint8_t* p_result_codec_config,
- bool select_current_codec) {
- mock_function_count_map[__func__]++;
- return false;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecAudioConfig() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecCapability() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecConfig() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecLocalCapability() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecSelectableCapability() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_config_t A2dpCodecConfig::getCodecUserConfig() {
- mock_function_count_map[__func__]++;
- btav_a2dp_codec_config_t config;
- return config;
-}
-btav_a2dp_codec_index_t A2DP_SinkCodecIndex(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return BTAV_A2DP_CODEC_INDEX_MAX;
-}
-btav_a2dp_codec_index_t A2DP_SourceCodecIndex(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return BTAV_A2DP_CODEC_INDEX_MAX;
-}
-const char* A2DP_CodecIndexStr(btav_a2dp_codec_index_t codec_index) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const char* A2DP_CodecName(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const tA2DP_DECODER_INTERFACE* A2DP_GetDecoderInterface(
- const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const tA2DP_ENCODER_INTERFACE* A2DP_GetEncoderInterface(
- const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-int A2DP_GetSinkTrackChannelType(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int A2DP_GetTrackBitsPerSample(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int A2DP_GetTrackChannelCount(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int A2DP_GetTrackSampleRate(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int A2dpCodecConfig::getTrackBitRate() const {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::string A2DP_CodecInfoString(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::string A2dpCodecConfig::codecBitsPerSample2Str(
- btav_a2dp_codec_bits_per_sample_t codec_bits_per_sample) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::string A2dpCodecConfig::codecChannelMode2Str(
- btav_a2dp_codec_channel_mode_t codec_channel_mode) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::string A2dpCodecConfig::codecConfig2Str(
- const btav_a2dp_codec_config_t& codec_config) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::string A2dpCodecConfig::codecSampleRate2Str(
- btav_a2dp_codec_sample_rate_t codec_sample_rate) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tA2DP_CODEC_TYPE A2DP_GetCodecType(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t A2DP_GetMediaType(const uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t A2dpCodecConfig::getAudioBitsPerSample() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void A2DP_InitDefaultCodec(uint8_t* p_codec_info) {
- mock_function_count_map[__func__]++;
-}
-void A2dpCodecConfig::debug_codec_dump(int fd) {
- mock_function_count_map[__func__]++;
-}
-void A2dpCodecConfig::setCodecPriority(
- btav_a2dp_codec_priority_t codec_priority) {
- mock_function_count_map[__func__]++;
-}
-void A2dpCodecConfig::setDefaultCodecPriority() {
- mock_function_count_map[__func__]++;
-}
-void A2dpCodecs::debug_codec_dump(int fd) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_acl.cc b/test/mock/mock_stack_acl.cc
deleted file mode 100644
index ad69ce427..000000000
--- a/test/mock/mock_stack_acl.cc
+++ /dev/null
@@ -1,456 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:127
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "stack/acl/acl.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/hci_error_code.h"
-#include "types/bt_transport.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool IsEprAvailable(const tACL_CONN& p_acl) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool ACL_SupportTransparentSynchronousData(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_BLE_IS_RESOLVE_BDA(const RawAddress& x) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_IsAclConnectionUp(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_IsAclConnectionUpAndHandleValid(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_IsAclConnectionUpFromHandle(uint16_t hci_handle) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_IsBleConnection(uint16_t hci_handle) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_IsPhy2mSupported(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_ReadRemoteConnectionAddr(const RawAddress& pseudo_addr,
- RawAddress& conn_addr,
- tBLE_ADDR_TYPE* p_addr_type) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_ReadRemoteVersion(const RawAddress& addr, uint8_t* lmp_version,
- uint16_t* manufacturer, uint16_t* lmp_sub_version) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool acl_create_le_connection(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool acl_create_le_connection_with_id(uint8_t id, const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool acl_is_role_switch_allowed() {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool acl_is_switch_role_idle(const RawAddress& bd_addr,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool acl_peer_supports_ble_2m_phy(uint16_t hci_handle) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool acl_peer_supports_ble_coded_phy(uint16_t hci_handle) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool acl_peer_supports_ble_connection_parameters_request(
- const RawAddress& remote_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool acl_peer_supports_ble_packet_extension(uint16_t hci_handle) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool acl_peer_supports_sniff_subrating(const RawAddress& remote_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool acl_refresh_remote_address(const RawAddress& identity_address,
- tBLE_ADDR_TYPE identity_address_type,
- const RawAddress& bda, tBLE_ADDR_TYPE rra_type,
- const RawAddress& rpa) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool acl_set_peer_le_features_from_handle(uint16_t hci_handle,
- const uint8_t* p) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool sco_peer_supports_esco_2m_phy(const RawAddress& remote_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool sco_peer_supports_esco_3m_phy(const RawAddress& remote_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-const RawAddress acl_address_from_handle(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return RawAddress::kEmpty;
-}
-void acl_send_data_packet_br_edr([[maybe_unused]] const RawAddress& bd_addr,
- BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
-}
-void acl_create_classic_connection(const RawAddress& bd_addr,
- bool there_are_high_priority_channels,
- bool is_bonding) {
- mock_function_count_map[__func__]++;
-}
-tACL_CONN* acl_get_connection_from_address(const RawAddress& bd_addr,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tACL_CONN* acl_get_connection_from_handle(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_STATUS BTM_GetLinkSuperTout(const RawAddress& remote_bda,
- uint16_t* p_timeout) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_GetRole(const RawAddress& remote_bd_addr, tHCI_ROLE* p_role) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_ReadFailedContactCounter(const RawAddress& remote_bda,
- tBTM_CMPL_CB* p_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_ReadRSSI(const RawAddress& remote_bda, tBTM_CMPL_CB* p_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_ReadTxPower(const RawAddress& remote_bda,
- tBT_TRANSPORT transport, tBTM_CMPL_CB* p_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SetLinkSuperTout(const RawAddress& remote_bda,
- uint16_t timeout) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SwitchRoleToCentral(const RawAddress& remote_bd_addr) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_remove_acl(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-uint16_t BTM_GetHCIConnHandle(const RawAddress& remote_bda,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t BTM_GetMaxPacketSize(const RawAddress& addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t mock_stack_acl_num_links = 0;
-uint16_t BTM_GetNumAclLinks(void) {
- mock_function_count_map[__func__]++;
- return mock_stack_acl_num_links;
-}
-uint16_t acl_get_supported_packet_types() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tHCI_REASON btm_get_acl_disc_reason_code(void) {
- mock_function_count_map[__func__]++;
- return HCI_SUCCESS;
-}
-uint8_t BTM_GetPeerSCA(const RawAddress& remote_bda, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t BTM_SetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t acl_link_role_from_handle(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t btm_handle_to_acl_index(uint16_t hci_handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t* BTM_ReadRemoteFeatures(const RawAddress& addr) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void ACL_RegisterClient(struct acl_client_callback_s* callbacks) {
- mock_function_count_map[__func__]++;
-}
-void ACL_UnregisterClient(struct acl_client_callback_s* callbacks) {
- mock_function_count_map[__func__]++;
-}
-void BTM_ReadConnectionAddr(const RawAddress& remote_bda,
- RawAddress& local_conn_addr,
- tBLE_ADDR_TYPE* p_addr_type) {
- mock_function_count_map[__func__]++;
-}
-void BTM_RequestPeerSCA(const RawAddress& remote_bda, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void BTM_acl_after_controller_started(const controller_t* controller) {
- mock_function_count_map[__func__]++;
-}
-void BTM_block_role_switch_for(const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void BTM_block_sniff_mode_for(const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void BTM_default_block_role_switch() { mock_function_count_map[__func__]++; }
-void BTM_default_unblock_role_switch() { mock_function_count_map[__func__]++; }
-void BTM_unblock_role_switch_for(const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void BTM_unblock_sniff_mode_for(const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
-}
-void acl_accept_connection_request(const RawAddress& bd_addr, uint8_t role) {
- mock_function_count_map[__func__]++;
-}
-void acl_disconnect_after_role_switch(uint16_t conn_handle,
- tHCI_STATUS reason) {
- mock_function_count_map[__func__]++;
-}
-void acl_disconnect_from_handle(uint16_t handle, tHCI_STATUS reason) {
- mock_function_count_map[__func__]++;
-}
-void acl_link_segments_xmitted(BT_HDR* p_msg) {
- mock_function_count_map[__func__]++;
-}
-void acl_packets_completed(uint16_t handle, uint16_t credits) {
- mock_function_count_map[__func__]++;
-}
-void acl_process_supported_features(uint16_t handle, uint64_t features) {
- mock_function_count_map[__func__]++;
-}
-void acl_process_extended_features(uint16_t handle, uint8_t current_page_number,
- uint8_t max_page_number, uint64_t features) {
- mock_function_count_map[__func__]++;
-}
-void acl_process_num_completed_pkts(uint8_t* p, uint8_t evt_len) {
- mock_function_count_map[__func__]++;
-}
-void acl_rcv_acl_data(BT_HDR* p_msg) { mock_function_count_map[__func__]++; }
-void acl_reject_connection_request(const RawAddress& bd_addr, uint8_t reason) {
- mock_function_count_map[__func__]++;
-}
-void acl_send_data_packet_ble(const RawAddress& bd_addr, BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
-}
-void acl_set_disconnect_reason(tHCI_STATUS acl_disc_reason) {
- mock_function_count_map[__func__]++;
-}
-void acl_write_automatic_flush_timeout(const RawAddress& bd_addr,
- uint16_t flush_timeout_in_ticks) {
- mock_function_count_map[__func__]++;
-}
-void btm_acl_connected(const RawAddress& bda, uint16_t handle,
- tHCI_STATUS status, uint8_t enc_mode) {
- mock_function_count_map[__func__]++;
-}
-void btm_acl_connection_request(const RawAddress& bda, uint8_t* dc) {
- mock_function_count_map[__func__]++;
-}
-void btm_acl_created(const RawAddress& bda, uint16_t hci_handle,
- tHCI_ROLE link_role, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void btm_acl_device_down(void) { mock_function_count_map[__func__]++; }
-void btm_acl_disconnected(tHCI_STATUS status, uint16_t handle,
- tHCI_REASON reason) {
- mock_function_count_map[__func__]++;
-}
-void btm_acl_encrypt_change(uint16_t handle, uint8_t status,
- uint8_t encr_enable) {
- mock_function_count_map[__func__]++;
-}
-void btm_acl_notif_conn_collision(const RawAddress& bda) {
- mock_function_count_map[__func__]++;
-}
-void btm_acl_paging(BT_HDR* p, const RawAddress& bda) {
- mock_function_count_map[__func__]++;
-}
-void btm_acl_process_sca_cmpl_pkt(uint8_t len, uint8_t* data) {
- mock_function_count_map[__func__]++;
-}
-void btm_acl_removed(uint16_t handle) { mock_function_count_map[__func__]++; }
-void btm_acl_reset_paging(void) { mock_function_count_map[__func__]++; }
-void btm_acl_resubmit_page(void) { mock_function_count_map[__func__]++; }
-void btm_acl_role_changed(tHCI_STATUS hci_status, const RawAddress& bd_addr,
- tHCI_ROLE new_role) {
- mock_function_count_map[__func__]++;
-}
-void btm_acl_set_paging(bool value) { mock_function_count_map[__func__]++; }
-void btm_acl_update_conn_addr(uint16_t handle, const RawAddress& address) {
- mock_function_count_map[__func__]++;
-}
-void btm_acl_update_inquiry_status(uint8_t status) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_refresh_local_resolvable_private_addr(
- const RawAddress& pseudo_addr, const RawAddress& local_rpa) {
- mock_function_count_map[__func__]++;
-}
-void btm_cont_rswitch_from_handle(uint16_t hci_handle) {
- mock_function_count_map[__func__]++;
-}
-void btm_establish_continue_from_address(const RawAddress& bda,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void btm_process_remote_ext_features(tACL_CONN* p_acl_cb,
- uint8_t max_page_number) {
- mock_function_count_map[__func__]++;
-}
-void btm_process_remote_version_complete(uint8_t status, uint16_t handle,
- uint8_t lmp_version,
- uint16_t manufacturer,
- uint16_t lmp_subversion) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_automatic_flush_timeout_complete(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_failed_contact_counter_complete(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_failed_contact_counter_timeout(UNUSED_ATTR void* data) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_link_quality_complete(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_link_quality_timeout(UNUSED_ATTR void* data) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_remote_ext_features(uint16_t handle, uint8_t page_number) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_remote_ext_features_complete(uint16_t handle, uint8_t page_num,
- uint8_t max_page,
- uint8_t* features) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_remote_ext_features_complete_raw(uint8_t* p, uint8_t evt_len) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_remote_ext_features_failed(uint8_t status, uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_remote_features_complete(uint16_t handle, uint8_t* features) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_remote_features_complete_raw(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_remote_version_complete(tHCI_STATUS status, uint16_t handle,
- uint8_t lmp_version,
- uint16_t manufacturer,
- uint16_t lmp_subversion) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_remote_version_complete_raw(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_rssi_complete(uint8_t* p) { mock_function_count_map[__func__]++; }
-void btm_read_rssi_timeout(UNUSED_ATTR void* data) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_tx_power_complete(uint8_t* p, bool is_ble) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_tx_power_timeout(UNUSED_ATTR void* data) {
- mock_function_count_map[__func__]++;
-}
-void btm_rejectlist_role_change_device(const RawAddress& bd_addr,
- uint8_t hci_status) {
- mock_function_count_map[__func__]++;
-}
-void btm_set_link_policy(tACL_CONN* conn, tLINK_POLICY policy) {
- mock_function_count_map[__func__]++;
-}
-void btm_set_packet_types_from_address(const RawAddress& bd_addr,
- uint16_t pkt_types) {
- mock_function_count_map[__func__]++;
-}
-void hci_btm_set_link_supervision_timeout(tACL_CONN& link, uint16_t timeout) {
- mock_function_count_map[__func__]++;
-}
-void on_acl_br_edr_connected(const RawAddress& bda, uint16_t handle,
- uint8_t enc_mode) {
- mock_function_count_map[__func__]++;
-}
-void on_acl_br_edr_failed(const RawAddress& bda, tHCI_STATUS status) {
- mock_function_count_map[__func__]++;
-}
-void acl_add_to_ignore_auto_connect_after_disconnect(
- const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_acl_ble.cc b/test/mock/mock_stack_acl_ble.cc
deleted file mode 100644
index 45345cc26..000000000
--- a/test/mock/mock_stack_acl_ble.cc
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:6
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "osi/include/log.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/gatt/connection_manager.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/hcidefs.h"
-#include "stack/include/l2cap_hci_link_interface.h"
-#include "types/ble_address_with_type.h"
-#include "types/hci_role.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void acl_ble_connection_complete(const tBLE_BD_ADDR& address_with_type,
- uint16_t handle, tHCI_ROLE role, bool match,
- uint16_t conn_interval, uint16_t conn_latency,
- uint16_t conn_timeout) {
- mock_function_count_map[__func__]++;
-}
-void acl_ble_connection_fail(const tBLE_BD_ADDR& address_with_type,
- uint16_t handle, bool enhanced,
- tHCI_STATUS status) {
- mock_function_count_map[__func__]++;
-}
-void acl_ble_enhanced_connection_complete(
- const tBLE_BD_ADDR& address_with_type, uint16_t handle, tHCI_ROLE role,
- bool match, uint16_t conn_interval, uint16_t conn_latency,
- uint16_t conn_timeout, const RawAddress& local_rpa,
- const RawAddress& peer_rpa, uint8_t peer_addr_type) {
- mock_function_count_map[__func__]++;
-}
-void acl_ble_enhanced_connection_complete_from_shim(
- const tBLE_BD_ADDR& address_with_type, uint16_t handle, tHCI_ROLE role,
- uint16_t conn_interval, uint16_t conn_latency, uint16_t conn_timeout,
- const RawAddress& local_rpa, const RawAddress& peer_rpa,
- uint8_t peer_addr_type) {
- mock_function_count_map[__func__]++;
-}
-void gatt_notify_conn_update(const RawAddress& remote, uint16_t interval,
- uint16_t latency, uint16_t timeout,
- tHCI_STATUS status);
-void acl_ble_update_event_received(tHCI_STATUS status, uint16_t handle,
- uint16_t interval, uint16_t latency,
- uint16_t timeout) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_acl_btm_ble_connection_establishment.cc b/test/mock/mock_stack_acl_btm_ble_connection_establishment.cc
deleted file mode 100644
index 465a3fe13..000000000
--- a/test/mock/mock_stack_acl_btm_ble_connection_establishment.cc
+++ /dev/null
@@ -1,103 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:6
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_stack_acl_btm_ble_connection_establishment.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace stack_acl_btm_ble_connection_establishment {
-
-// Function state capture and return values, if needed
-struct btm_send_hci_create_connection btm_send_hci_create_connection;
-struct btm_ble_create_ll_conn_complete btm_ble_create_ll_conn_complete;
-struct maybe_resolve_address maybe_resolve_address;
-struct btm_ble_conn_complete btm_ble_conn_complete;
-struct btm_ble_create_conn_cancel btm_ble_create_conn_cancel;
-struct btm_ble_create_conn_cancel_complete btm_ble_create_conn_cancel_complete;
-
-} // namespace stack_acl_btm_ble_connection_establishment
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-void btm_send_hci_create_connection(
- uint16_t scan_int, uint16_t scan_win, uint8_t init_filter_policy,
- uint8_t addr_type_peer, const RawAddress& bda_peer, uint8_t addr_type_own,
- uint16_t conn_int_min, uint16_t conn_int_max, uint16_t conn_latency,
- uint16_t conn_timeout, uint16_t min_ce_len, uint16_t max_ce_len,
- uint8_t initiating_phys) {
- mock_function_count_map[__func__]++;
- test::mock::stack_acl_btm_ble_connection_establishment::
- btm_send_hci_create_connection(
- scan_int, scan_win, init_filter_policy, addr_type_peer, bda_peer,
- addr_type_own, conn_int_min, conn_int_max, conn_latency, conn_timeout,
- min_ce_len, max_ce_len, initiating_phys);
-}
-void btm_ble_create_ll_conn_complete(tHCI_STATUS status) {
- mock_function_count_map[__func__]++;
- test::mock::stack_acl_btm_ble_connection_establishment::
- btm_ble_create_ll_conn_complete(status);
-}
-bool maybe_resolve_address(RawAddress* bda, tBLE_ADDR_TYPE* bda_type) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_acl_btm_ble_connection_establishment::
- maybe_resolve_address(bda, bda_type);
-}
-void btm_ble_conn_complete(uint8_t* p, uint16_t evt_len, bool enhanced) {
- mock_function_count_map[__func__]++;
- test::mock::stack_acl_btm_ble_connection_establishment::btm_ble_conn_complete(
- p, evt_len, enhanced);
-}
-void btm_ble_create_conn_cancel() {
- mock_function_count_map[__func__]++;
- test::mock::stack_acl_btm_ble_connection_establishment::
- btm_ble_create_conn_cancel();
-}
-void btm_ble_create_conn_cancel_complete(uint8_t* p) {
- mock_function_count_map[__func__]++;
- test::mock::stack_acl_btm_ble_connection_establishment::
- btm_ble_create_conn_cancel_complete(p);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_acl_btm_ble_connection_establishment.h b/test/mock/mock_stack_acl_btm_ble_connection_establishment.h
deleted file mode 100644
index c546d030e..000000000
--- a/test/mock/mock_stack_acl_btm_ble_connection_establishment.h
+++ /dev/null
@@ -1,135 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:6
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-#include "stack/include/hci_error_code.h"
-#include "types/ble_address_with_type.h"
-#include "types/raw_address.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace stack_acl_btm_ble_connection_establishment {
-
-// Shared state between mocked functions and tests
-// Name: btm_send_hci_create_connection
-// Params: uint16_t scan_int, uint16_t scan_win, uint8_t init_filter_policy,
-// uint8_t addr_type_peer, const RawAddress& bda_peer, uint8_t addr_type_own,
-// uint16_t conn_int_min, uint16_t conn_int_max, uint16_t conn_latency, uint16_t
-// conn_timeout, uint16_t min_ce_len, uint16_t max_ce_len, uint8_t
-// initiating_phys Returns: void
-struct btm_send_hci_create_connection {
- std::function<void(
- uint16_t scan_int, uint16_t scan_win, uint8_t init_filter_policy,
- uint8_t addr_type_peer, const RawAddress& bda_peer, uint8_t addr_type_own,
- uint16_t conn_int_min, uint16_t conn_int_max, uint16_t conn_latency,
- uint16_t conn_timeout, uint16_t min_ce_len, uint16_t max_ce_len,
- uint8_t initiating_phys)>
- body{[](uint16_t scan_int, uint16_t scan_win, uint8_t init_filter_policy,
- uint8_t addr_type_peer, const RawAddress& bda_peer,
- uint8_t addr_type_own, uint16_t conn_int_min,
- uint16_t conn_int_max, uint16_t conn_latency,
- uint16_t conn_timeout, uint16_t min_ce_len, uint16_t max_ce_len,
- uint8_t initiating_phys) {}};
- void operator()(uint16_t scan_int, uint16_t scan_win,
- uint8_t init_filter_policy, uint8_t addr_type_peer,
- const RawAddress& bda_peer, uint8_t addr_type_own,
- uint16_t conn_int_min, uint16_t conn_int_max,
- uint16_t conn_latency, uint16_t conn_timeout,
- uint16_t min_ce_len, uint16_t max_ce_len,
- uint8_t initiating_phys) {
- body(scan_int, scan_win, init_filter_policy, addr_type_peer, bda_peer,
- addr_type_own, conn_int_min, conn_int_max, conn_latency, conn_timeout,
- min_ce_len, max_ce_len, initiating_phys);
- };
-};
-extern struct btm_send_hci_create_connection btm_send_hci_create_connection;
-// Name: btm_ble_create_ll_conn_complete
-// Params: tHCI_STATUS status
-// Returns: void
-struct btm_ble_create_ll_conn_complete {
- std::function<void(tHCI_STATUS status)> body{[](tHCI_STATUS status) {}};
- void operator()(tHCI_STATUS status) { body(status); };
-};
-extern struct btm_ble_create_ll_conn_complete btm_ble_create_ll_conn_complete;
-// Name: maybe_resolve_address
-// Params: RawAddress* bda, tBLE_ADDR_TYPE* bda_type
-// Returns: bool
-struct maybe_resolve_address {
- std::function<bool(RawAddress* bda, tBLE_ADDR_TYPE* bda_type)> body{
- [](RawAddress* bda, tBLE_ADDR_TYPE* bda_type) { return false; }};
- bool operator()(RawAddress* bda, tBLE_ADDR_TYPE* bda_type) {
- return body(bda, bda_type);
- };
-};
-extern struct maybe_resolve_address maybe_resolve_address;
-// Name: btm_ble_conn_complete
-// Params: uint8_t* p, uint16_t evt_len, bool enhanced
-// Returns: void
-struct btm_ble_conn_complete {
- std::function<void(uint8_t* p, uint16_t evt_len, bool enhanced)> body{
- [](uint8_t* p, uint16_t evt_len, bool enhanced) {}};
- void operator()(uint8_t* p, uint16_t evt_len, bool enhanced) {
- body(p, evt_len, enhanced);
- };
-};
-extern struct btm_ble_conn_complete btm_ble_conn_complete;
-// Name: btm_ble_create_conn_cancel
-// Params:
-// Returns: void
-struct btm_ble_create_conn_cancel {
- std::function<void()> body{[]() {}};
- void operator()() { body(); };
-};
-extern struct btm_ble_create_conn_cancel btm_ble_create_conn_cancel;
-// Name: btm_ble_create_conn_cancel_complete
-// Params: uint8_t* p
-// Returns: void
-struct btm_ble_create_conn_cancel_complete {
- std::function<void(uint8_t* p)> body{[](uint8_t* p) {}};
- void operator()(uint8_t* p) { body(p); };
-};
-extern struct btm_ble_create_conn_cancel_complete
- btm_ble_create_conn_cancel_complete;
-
-} // namespace stack_acl_btm_ble_connection_establishment
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_acl_btm_pm.cc b/test/mock/mock_stack_acl_btm_pm.cc
deleted file mode 100644
index 2461c3773..000000000
--- a/test/mock/mock_stack_acl_btm_pm.cc
+++ /dev/null
@@ -1,105 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:17
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <unordered_map>
-#include "bt_target.h"
-#include "device/include/controller.h"
-#include "device/include/interop.h"
-#include "main/shim/dumpsys.h"
-#include "main/shim/link_policy.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/btm_status.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool BTM_ReadPowerMode(const RawAddress& remote_bda, tBTM_PM_MODE* p_mode) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_SetLinkPolicyActiveMode(const RawAddress& remote_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tBTM_CONTRL_STATE BTM_PM_ReadControllerState(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTM_STATUS BTM_PmRegister(uint8_t mask, uint8_t* p_pm_id,
- tBTM_PM_STATUS_CBACK* p_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SetPowerMode(uint8_t pm_id, const RawAddress& remote_bda,
- const tBTM_PM_PWR_MD* p_mode) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SetSsrParams(const RawAddress& remote_bda, uint16_t max_lat,
- uint16_t min_rmt_to, uint16_t min_loc_to) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-void BTM_PM_OnConnected(uint16_t handle, const RawAddress& remote_bda) {
- mock_function_count_map[__func__]++;
-}
-void BTM_PM_OnDisconnected(uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void btm_pm_on_mode_change(tHCI_STATUS status, uint16_t handle,
- tHCI_MODE current_mode, uint16_t interval) {
- mock_function_count_map[__func__]++;
-}
-void btm_pm_on_sniff_subrating(tHCI_STATUS status, uint16_t handle,
- uint16_t maximum_transmit_latency,
- uint16_t maximum_receive_latency,
- uint16_t minimum_remote_timeout,
- uint16_t minimum_local_timeout) {
- mock_function_count_map[__func__]++;
-}
-void btm_pm_proc_cmd_status(tHCI_STATUS status) {
- mock_function_count_map[__func__]++;
-}
-void btm_pm_proc_mode_change(tHCI_STATUS hci_status, uint16_t hci_handle,
- tHCI_MODE hci_mode, uint16_t interval) {
- mock_function_count_map[__func__]++;
-}
-void btm_pm_proc_ssr_evt(uint8_t* p, UNUSED_ATTR uint16_t evt_len) {
- mock_function_count_map[__func__]++;
-}
-void btm_pm_reset(void) { mock_function_count_map[__func__]++; }
-void process_ssr_event(tHCI_STATUS status, uint16_t handle,
- UNUSED_ATTR uint16_t max_tx_lat, uint16_t max_rx_lat) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_avct_api.cc b/test/mock/mock_stack_avct_api.cc
deleted file mode 100644
index 85adf06a5..000000000
--- a/test/mock/mock_stack_avct_api.cc
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:9
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "avct_api.h"
-#include "bt_common.h"
-#include "bt_target.h"
-#include "bt_types.h"
-#include "bta/include/bta_api.h"
-#include "btm_api.h"
-#include "l2c_api.h"
-#include "l2cdefs.h"
-#include "osi/include/osi.h"
-#include "stack/avct/avct_int.h"
-#include "stack/btm/btm_sec.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-uint16_t AVCT_CreateBrowse(uint8_t handle, uint8_t role) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVCT_CreateConn(uint8_t* p_handle, tAVCT_CC* p_cc,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVCT_GetBrowseMtu(uint8_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVCT_GetPeerMtu(uint8_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVCT_MsgReq(uint8_t handle, uint8_t label, uint8_t cr, BT_HDR* p_msg) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVCT_RemoveBrowse(uint8_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVCT_RemoveConn(uint8_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void AVCT_Deregister(void) { mock_function_count_map[__func__]++; }
-void AVCT_Register() { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_avdt_api.cc b/test/mock/mock_stack_avdt_api.cc
deleted file mode 100644
index a75860146..000000000
--- a/test/mock/mock_stack_avdt_api.cc
+++ /dev/null
@@ -1,147 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:26
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "avdt_api.h"
-#include "avdtc_api.h"
-#include "bt_target.h"
-#include "bt_types.h"
-#include "bta/include/bta_api.h"
-#include "btm_api.h"
-#include "btu.h"
-#include "l2c_api.h"
-#include "main/shim/dumpsys.h"
-#include "osi/include/log.h"
-#include "stack/avdt/avdt_int.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/a2dp_codec_api.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-uint16_t AVDT_CloseReq(uint8_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_ConfigRsp(uint8_t handle, uint8_t label, uint8_t error_code,
- uint8_t category) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_ConnectReq(const RawAddress& bd_addr, uint8_t channel_index,
- tAVDT_CTRL_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_CreateStream(uint8_t peer_id, uint8_t* p_handle,
- const AvdtpStreamConfig& avdtp_stream_config) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_DelayReport(uint8_t handle, uint8_t seid, uint16_t delay) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_DisconnectReq(const RawAddress& bd_addr,
- tAVDT_CTRL_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_DiscoverReq(const RawAddress& bd_addr, uint8_t channel_index,
- tAVDT_SEP_INFO* p_sep_info, uint8_t max_seps,
- tAVDT_CTRL_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_GetCapReq(const RawAddress& bd_addr, uint8_t channel_index,
- uint8_t seid, AvdtpSepConfig* p_cfg,
- tAVDT_CTRL_CBACK* p_cback, bool get_all_cap) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_GetL2CapChannel(uint8_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_OpenReq(uint8_t handle, const RawAddress& bd_addr,
- uint8_t channel_index, uint8_t seid,
- AvdtpSepConfig* p_cfg) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_ReconfigReq(uint8_t handle, AvdtpSepConfig* p_cfg) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_RemoveStream(uint8_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_SecurityReq(uint8_t handle, uint8_t* p_data, uint16_t len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_SecurityRsp(uint8_t handle, uint8_t label, uint8_t error_code,
- uint8_t* p_data, uint16_t len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_StartReq(uint8_t* p_handles, uint8_t num_handles) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_SuspendReq(uint8_t* p_handles, uint8_t num_handles) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVDT_WriteReqOpt(uint8_t handle, BT_HDR* p_pkt, uint32_t time_stamp,
- uint8_t m_pt, tAVDT_DATA_OPT_MASK opt) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t AVDT_SetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void AVDT_AbortReq(uint8_t handle) { mock_function_count_map[__func__]++; }
-void AVDT_Deregister(void) { mock_function_count_map[__func__]++; }
-void AVDT_Register(AvdtpRcb* p_reg, tAVDT_CTRL_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
-}
-void avdt_ccb_idle_ccb_timer_timeout(void* data) {
- mock_function_count_map[__func__]++;
-}
-void avdt_ccb_ret_ccb_timer_timeout(void* data) {
- mock_function_count_map[__func__]++;
-}
-void avdt_ccb_rsp_ccb_timer_timeout(void* data) {
- mock_function_count_map[__func__]++;
-}
-void avdt_scb_transport_channel_timer_timeout(void* data) {
- mock_function_count_map[__func__]++;
-}
-void stack_debug_avdtp_api_dump(int fd) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_avrc_api.cc b/test/mock/mock_stack_avrc_api.cc
deleted file mode 100644
index 8214af36c..000000000
--- a/test/mock/mock_stack_avrc_api.cc
+++ /dev/null
@@ -1,83 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:14
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <string.h>
-#include "bt_common.h"
-#include "osi/include/fixed_queue.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "osi/include/properties.h"
-#include "stack/avrc/avrc_int.h"
-#include "stack/include/avrc_api.h"
-#include "stack/include/btu.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-uint16_t AVRC_Close(uint8_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVRC_CloseBrowse(uint8_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVRC_GetProfileVersion() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVRC_MsgReq(uint8_t handle, uint8_t label, uint8_t ctype,
- BT_HDR* p_pkt) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVRC_Open(uint8_t* p_handle, tAVRC_CONN_CB* p_ccb,
- const RawAddress& peer_addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVRC_OpenBrowse(uint8_t handle, uint8_t conn_role) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVRC_PassCmd(uint8_t handle, uint8_t label, tAVRC_MSG_PASS* p_msg) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVRC_PassRsp(uint8_t handle, uint8_t label, tAVRC_MSG_PASS* p_msg) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void avrc_flush_cmd_q(uint8_t handle) { mock_function_count_map[__func__]++; }
-void avrc_process_timeout(void* data) { mock_function_count_map[__func__]++; }
-void avrc_send_next_vendor_cmd(uint8_t handle) {
- mock_function_count_map[__func__]++;
-}
-void avrc_start_cmd_timer(uint8_t handle, uint8_t label, uint8_t msg_mask) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_avrc_bld_ct.cc b/test/mock/mock_stack_avrc_bld_ct.cc
deleted file mode 100644
index 011fe60e8..000000000
--- a/test/mock/mock_stack_avrc_bld_ct.cc
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "avrc_api.h"
-#include "avrc_defs.h"
-#include "bt_common.h"
-#include "stack/avrc/avrc_int.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tAVRC_STS AVRC_BldCommand(tAVRC_COMMAND* p_cmd, BT_HDR** pp_pkt) {
- mock_function_count_map[__func__]++;
- return 0;
-}
diff --git a/test/mock/mock_stack_avrc_bld_tg.cc b/test/mock/mock_stack_avrc_bld_tg.cc
deleted file mode 100644
index 2189915a7..000000000
--- a/test/mock/mock_stack_avrc_bld_tg.cc
+++ /dev/null
@@ -1,47 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <string.h>
-#include "avrc_api.h"
-#include "avrc_defs.h"
-#include "bt_common.h"
-#include "osi/include/osi.h"
-#include "stack/avrc/avrc_int.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tAVRC_STS AVRC_BldResponse(uint8_t handle, tAVRC_RESPONSE* p_rsp,
- BT_HDR** pp_pkt) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tAVRC_STS avrc_bld_group_navigation_rsp(uint16_t navi_id, BT_HDR* p_pkt) {
- mock_function_count_map[__func__]++;
- return 0;
-}
diff --git a/test/mock/mock_stack_avrc_pars.ct.cc b/test/mock/mock_stack_avrc_pars.ct.cc
deleted file mode 100644
index b4f88e7c6..000000000
--- a/test/mock/mock_stack_avrc_pars.ct.cc
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:4
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "avrc_api.h"
-#include "avrc_defs.h"
-#include "bt_common.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "stack/avrc/avrc_int.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tAVRC_STS AVRC_Ctrl_ParsResponse(tAVRC_MSG* p_msg, tAVRC_RESPONSE* p_result,
- uint8_t* p_buf, uint16_t* buf_len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tAVRC_STS AVRC_ParsResponse(tAVRC_MSG* p_msg, tAVRC_RESPONSE* p_result,
- UNUSED_ATTR uint8_t* p_buf,
- UNUSED_ATTR uint16_t buf_len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tAVRC_STS avrc_parse_notification_rsp(uint8_t* p_stream, uint16_t len,
- tAVRC_REG_NOTIF_RSP* p_rsp) {
- mock_function_count_map[__func__]++;
- return 0;
-}
diff --git a/test/mock/mock_stack_avrc_pars_tg.cc b/test/mock/mock_stack_avrc_pars_tg.cc
deleted file mode 100644
index 9033d5900..000000000
--- a/test/mock/mock_stack_avrc_pars_tg.cc
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:4
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "avrc_api.h"
-#include "avrc_defs.h"
-#include "bt_common.h"
-#include "osi/include/log.h"
-#include "stack/avrc/avrc_int.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tAVRC_STS AVRC_Ctrl_ParsCommand(tAVRC_MSG* p_msg, tAVRC_COMMAND* p_result) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tAVRC_STS AVRC_ParsCommand(tAVRC_MSG* p_msg, tAVRC_COMMAND* p_result,
- uint8_t* p_buf, uint16_t buf_len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
diff --git a/test/mock/mock_stack_avrc_sdp.cc b/test/mock/mock_stack_avrc_sdp.cc
deleted file mode 100644
index 52209bb64..000000000
--- a/test/mock/mock_stack_avrc_sdp.cc
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:7
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-
-#include "bt_common.h"
-#include "stack/avrc/avrc_int.h"
-#include "stack/include/avrc_api.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-uint16_t AVRC_AddRecord(uint16_t service_uuid, const char* p_service_name,
- const char* p_provider_name, uint16_t categories,
- uint32_t sdp_handle, bool browse_supported,
- uint16_t profile_version, uint16_t cover_art_psm) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVRC_FindService(uint16_t service_uuid, const RawAddress& bd_addr,
- tAVRC_SDP_DB_PARAMS* p_db,
- const tAVRC_FIND_CBACK& find_cback) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t AVRC_RemoveRecord(uint32_t sdp_handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t AVRC_SetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void AVRC_Init(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_bnep_api.cc b/test/mock/mock_stack_bnep_api.cc
deleted file mode 100644
index 0743317ac..000000000
--- a/test/mock/mock_stack_bnep_api.cc
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:11
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "bta/include/bta_api.h"
-#include "stack/bnep/bnep_int.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/bnep_api.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-using namespace bluetooth;
-
-tBNEP_RESULT BNEP_Connect(const RawAddress& p_rem_bda, const Uuid& src_uuid,
- const Uuid& dst_uuid, uint16_t* p_handle,
- uint32_t mx_chan_id) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBNEP_RESULT BNEP_ConnectResp(uint16_t handle, tBNEP_RESULT resp) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBNEP_RESULT BNEP_Disconnect(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBNEP_RESULT BNEP_Register(tBNEP_REGISTER* p_reg_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBNEP_RESULT BNEP_SetMulticastFilters(uint16_t handle, uint16_t num_filters,
- uint8_t* p_start_array,
- uint8_t* p_end_array) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBNEP_RESULT BNEP_SetProtocolFilters(uint16_t handle, uint16_t num_filters,
- uint16_t* p_start_array,
- uint16_t* p_end_array) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBNEP_RESULT BNEP_Write(uint16_t handle, const RawAddress& p_dest_addr,
- uint8_t* p_data, uint16_t len, uint16_t protocol,
- const RawAddress* p_src_addr, bool fw_ext_present) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBNEP_RESULT BNEP_WriteBuf(uint16_t handle, const RawAddress& p_dest_addr,
- BT_HDR* p_buf, uint16_t protocol,
- const RawAddress* p_src_addr, bool fw_ext_present) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t BNEP_SetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void BNEP_Deregister(void) { mock_function_count_map[__func__]++; }
-void BNEP_Init(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_btm.cc b/test/mock/mock_stack_btm.cc
deleted file mode 100644
index d1a8b6b4c..000000000
--- a/test/mock/mock_stack_btm.cc
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- */
-
-#include "stack/include/btm_ble_api_types.h"
-#include "stack/include/btm_client_interface.h"
-#include "types/raw_address.h"
-
-tBTM_STATUS BTM_BleGetEnergyInfo(tBTM_BLE_ENERGY_INFO_CBACK* p_ener_cback) {
- return BTM_SUCCESS;
-}
-void BTM_BleReadControllerFeatures(tBTM_BLE_CTRL_FEATURES_CBACK* p_vsc_cback) {}
-bool BTM_is_sniff_allowed_for(const RawAddress& peer_addr) { return false; }
-uint8_t BTM_GetAcceptlistSize() { return 0; }
-
-struct btm_client_interface_s btm_client_interface = {};
-
-struct btm_client_interface_s& get_btm_client_interface() {
- return btm_client_interface;
-}
diff --git a/test/mock/mock_stack_btm_ble.cc b/test/mock/mock_stack_btm_ble.cc
deleted file mode 100644
index 835b1d230..000000000
--- a/test/mock/mock_stack_btm_ble.cc
+++ /dev/null
@@ -1,256 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:50
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "device/include/controller.h"
-#include "main/shim/btm_api.h"
-#include "main/shim/l2c_api.h"
-#include "main/shim/shim.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/btm/security_device_record.h"
-#include "stack/crypto_toolbox/crypto_toolbox.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_api.h"
-#include "stack/include/btu.h"
-#include "stack/include/gatt_api.h"
-#include "stack/include/l2cap_security_interface.h"
-#include "stack/include/l2cdefs.h"
-#include "stack/include/smp_api.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool BTM_BleDataSignature(const RawAddress& bd_addr, uint8_t* p_text,
- uint16_t len, BLE_SIGNATURE signature) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_BleVerifySignature(const RawAddress& bd_addr, uint8_t* p_orig,
- uint16_t len, uint32_t counter, uint8_t* p_comp) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_ReadConnectedTransportAddress(RawAddress* remote_bda,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_UseLeLink(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_ble_get_acl_remote_addr(uint16_t hci_handle, RawAddress& conn_addr,
- tBLE_ADDR_TYPE* p_addr_type) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_ble_get_enc_key_type(const RawAddress& bd_addr, uint8_t* p_key_types) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_get_local_div(const RawAddress& bd_addr, uint16_t* p_div) {
- mock_function_count_map[__func__]++;
- return false;
-}
-static Octet16 octet16;
-
-const Octet16& BTM_GetDeviceDHK() {
- mock_function_count_map[__func__]++;
- return octet16;
-}
-const Octet16& BTM_GetDeviceEncRoot() {
- mock_function_count_map[__func__]++;
- return octet16;
-}
-const Octet16& BTM_GetDeviceIDRoot() {
- mock_function_count_map[__func__]++;
- return octet16;
-}
-tBTM_SEC_ACTION btm_ble_determine_security_act(bool is_originator,
- const RawAddress& bdaddr,
- uint16_t security_required) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTM_STATUS BTM_SetBleDataLength(const RawAddress& bd_addr,
- uint16_t tx_pdu_length) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTM_STATUS btm_ble_set_encryption(const RawAddress& bd_addr,
- tBTM_BLE_SEC_ACT sec_act,
- uint8_t link_role) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTM_STATUS btm_ble_start_encrypt(const RawAddress& bda, bool use_stk,
- Octet16* p_stk) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTM_STATUS btm_proc_smp_cback(tSMP_EVT event, const RawAddress& bd_addr,
- tSMP_EVT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tL2CAP_LE_RESULT_CODE btm_ble_start_sec_check(const RawAddress& bd_addr,
- uint16_t psm, bool is_originator,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data) {
- mock_function_count_map[__func__]++;
- return L2CAP_LE_RESULT_CONN_OK;
-}
-uint8_t btm_ble_br_keys_req(tBTM_SEC_DEV_REC* p_dev_rec,
- tBTM_LE_IO_REQ* p_data) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t btm_ble_io_capabilities_req(tBTM_SEC_DEV_REC* p_dev_rec,
- tBTM_LE_IO_REQ* p_data) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t btm_ble_read_sec_key_size(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void BTM_BleConfirmReply(const RawAddress& bd_addr, uint8_t res) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleLoadLocalKeys(uint8_t key_type, tBTM_BLE_LOCAL_KEYS* p_key) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleOobDataReply(const RawAddress& bd_addr, uint8_t res, uint8_t len,
- uint8_t* p_data) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BlePasskeyReply(const RawAddress& bd_addr, uint8_t res,
- uint32_t passkey) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleReadPhy(
- const RawAddress& bd_addr,
- base::Callback<void(uint8_t tx_phy, uint8_t rx_phy, uint8_t status)> cb) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleReceiverTest(uint8_t rx_freq, tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleSecureConnectionOobDataReply(const RawAddress& bd_addr,
- uint8_t* p_c, uint8_t* p_r) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleSetPhy(const RawAddress& bd_addr, uint8_t tx_phys, uint8_t rx_phys,
- uint16_t phy_options) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleSetPrefConnParams(const RawAddress& bd_addr, uint16_t min_conn_int,
- uint16_t max_conn_int,
- uint16_t peripheral_latency,
- uint16_t supervision_tout) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleTestEnd(tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleTransmitterTest(uint8_t tx_freq, uint8_t test_data_len,
- uint8_t packet_payload,
- tBTM_CMPL_CB* p_cmd_cmpl_cback) {
- mock_function_count_map[__func__]++;
-}
-void BTM_ReadDevInfo(const RawAddress& remote_bda, tBT_DEVICE_TYPE* p_dev_type,
- tBLE_ADDR_TYPE* p_addr_type) {
- mock_function_count_map[__func__]++;
-}
-void BTM_SecAddBleDevice(const RawAddress& bd_addr, tBT_DEVICE_TYPE dev_type,
- tBLE_ADDR_TYPE addr_type) {
- mock_function_count_map[__func__]++;
-}
-void BTM_SecAddBleKey(const RawAddress& bd_addr, tBTM_LE_KEY_VALUE* p_le_key,
- tBTM_LE_KEY_TYPE key_type) {
- mock_function_count_map[__func__]++;
-}
-void BTM_SecurityGrant(const RawAddress& bd_addr, uint8_t res) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_connected(const RawAddress& bda, uint16_t handle, uint8_t enc_mode,
- uint8_t role, tBLE_ADDR_TYPE addr_type,
- bool addr_matched) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_connected_from_address_with_type(
- const tBLE_BD_ADDR& address_with_type, uint16_t handle, uint8_t enc_mode,
- uint8_t role, bool addr_matched) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_increment_sign_ctr(const RawAddress& bd_addr, bool is_local) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_link_encrypted(const RawAddress& bd_addr, uint8_t encr_enable) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_link_sec_check(const RawAddress& bd_addr,
- tBTM_LE_AUTH_REQ auth_req,
- tBTM_BLE_SEC_REQ_ACT* p_sec_req_act) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_ltk_request(uint16_t handle, uint8_t rand[8], uint16_t ediv) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_ltk_request_reply(const RawAddress& bda, bool use_stk,
- const Octet16& stk) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_rand_enc_complete(uint8_t* p, uint16_t op_code,
- tBTM_RAND_ENC_CB* p_enc_cplt_cback) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_set_random_address(const RawAddress& random_bda) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_test_command_complete(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_update_sec_key_size(const RawAddress& bd_addr,
- uint8_t enc_key_size) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_save_le_key(const RawAddress& bd_addr, tBTM_LE_KEY_TYPE key_type,
- tBTM_LE_KEY_VALUE* p_keys, bool pass_to_application) {
- mock_function_count_map[__func__]++;
-}
-void doNothing(uint8_t* data, uint16_t len) {
- mock_function_count_map[__func__]++;
-}
-void read_phy_cb(
- base::Callback<void(uint8_t tx_phy, uint8_t rx_phy, uint8_t status)> cb,
- uint8_t* data, uint16_t len) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_btm_ble_addr.cc b/test/mock/mock_stack_btm_ble_addr.cc
deleted file mode 100644
index 7db849800..000000000
--- a/test/mock/mock_stack_btm_ble_addr.cc
+++ /dev/null
@@ -1,128 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:10
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_stack_btm_ble_addr.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace stack_btm_ble_addr {
-
-// Function state capture and return values, if needed
-struct btm_gen_resolve_paddr_low btm_gen_resolve_paddr_low;
-struct btm_gen_resolvable_private_addr btm_gen_resolvable_private_addr;
-struct btm_get_next_private_addrress_interval_ms
- btm_get_next_private_addrress_interval_ms;
-struct btm_ble_init_pseudo_addr btm_ble_init_pseudo_addr;
-struct btm_ble_addr_resolvable btm_ble_addr_resolvable;
-struct btm_ble_resolve_random_addr btm_ble_resolve_random_addr;
-struct btm_identity_addr_to_random_pseudo btm_identity_addr_to_random_pseudo;
-struct btm_identity_addr_to_random_pseudo_from_address_with_type
- btm_identity_addr_to_random_pseudo_from_address_with_type;
-struct btm_random_pseudo_to_identity_addr btm_random_pseudo_to_identity_addr;
-struct btm_ble_refresh_peer_resolvable_private_addr
- btm_ble_refresh_peer_resolvable_private_addr;
-
-} // namespace stack_btm_ble_addr
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-void btm_gen_resolve_paddr_low(const RawAddress& address) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_addr::btm_gen_resolve_paddr_low(address);
-}
-void btm_gen_resolvable_private_addr(
- base::Callback<void(const RawAddress&)> cb) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_addr::btm_gen_resolvable_private_addr(cb);
-}
-uint64_t btm_get_next_private_addrress_interval_ms() {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_addr::
- btm_get_next_private_addrress_interval_ms();
-}
-bool btm_ble_init_pseudo_addr(tBTM_SEC_DEV_REC* p_dev_rec,
- const RawAddress& new_pseudo_addr) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_addr::btm_ble_init_pseudo_addr(
- p_dev_rec, new_pseudo_addr);
-}
-bool btm_ble_addr_resolvable(const RawAddress& rpa,
- tBTM_SEC_DEV_REC* p_dev_rec) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_addr::btm_ble_addr_resolvable(rpa,
- p_dev_rec);
-}
-tBTM_SEC_DEV_REC* btm_ble_resolve_random_addr(const RawAddress& random_bda) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_addr::btm_ble_resolve_random_addr(
- random_bda);
-}
-bool btm_identity_addr_to_random_pseudo(RawAddress* bd_addr,
- uint8_t* p_addr_type, bool refresh) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_addr::btm_identity_addr_to_random_pseudo(
- bd_addr, p_addr_type, refresh);
-}
-bool btm_identity_addr_to_random_pseudo_from_address_with_type(
- tBLE_BD_ADDR* address_with_type, bool refresh) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_addr::
- btm_identity_addr_to_random_pseudo_from_address_with_type(
- address_with_type, refresh);
-}
-bool btm_random_pseudo_to_identity_addr(RawAddress* random_pseudo,
- uint8_t* p_identity_addr_type) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_addr::btm_random_pseudo_to_identity_addr(
- random_pseudo, p_identity_addr_type);
-}
-void btm_ble_refresh_peer_resolvable_private_addr(
- const RawAddress& pseudo_bda, const RawAddress& rpa,
- tBTM_SEC_BLE::tADDRESS_TYPE rra_type) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_addr::btm_ble_refresh_peer_resolvable_private_addr(
- pseudo_bda, rpa, rra_type);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_btm_ble_addr.h b/test/mock/mock_stack_btm_ble_addr.h
deleted file mode 100644
index a3236fb1b..000000000
--- a/test/mock/mock_stack_btm_ble_addr.h
+++ /dev/null
@@ -1,177 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:10
- *
- * mockcify.pl ver 0.2
- */
-
-#include <base/callback.h> // RepeatingCallback
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-//
-#include "stack/btm/security_device_record.h"
-#include "types/ble_address_with_type.h"
-#include "types/raw_address.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace stack_btm_ble_addr {
-
-// Shared state between mocked functions and tests
-// Name: btm_gen_resolve_paddr_low
-// Params: const RawAddress& address
-// Returns: void
-struct btm_gen_resolve_paddr_low {
- std::function<void(const RawAddress& address)> body{
- [](const RawAddress& address) {}};
- void operator()(const RawAddress& address) { body(address); };
-};
-extern struct btm_gen_resolve_paddr_low btm_gen_resolve_paddr_low;
-// Name: btm_gen_resolvable_private_addr
-// Params: base::Callback<void(const RawAddress&)> cb
-// Returns: void
-struct btm_gen_resolvable_private_addr {
- std::function<void(base::Callback<void(const RawAddress&)> cb)> body{
- [](base::Callback<void(const RawAddress&)> cb) {}};
- void operator()(base::Callback<void(const RawAddress&)> cb) { body(cb); };
-};
-extern struct btm_gen_resolvable_private_addr btm_gen_resolvable_private_addr;
-// Name: btm_get_next_private_addrress_interval_ms
-// Params:
-// Returns: uint64_t
-struct btm_get_next_private_addrress_interval_ms {
- std::function<uint64_t()> body{[]() { return 0; }};
- uint64_t operator()() { return body(); };
-};
-extern struct btm_get_next_private_addrress_interval_ms
- btm_get_next_private_addrress_interval_ms;
-// Name: btm_ble_init_pseudo_addr
-// Params: tBTM_SEC_DEV_REC* p_dev_rec, const RawAddress& new_pseudo_addr
-// Returns: bool
-struct btm_ble_init_pseudo_addr {
- std::function<bool(tBTM_SEC_DEV_REC* p_dev_rec,
- const RawAddress& new_pseudo_addr)>
- body{[](tBTM_SEC_DEV_REC* p_dev_rec, const RawAddress& new_pseudo_addr) {
- return false;
- }};
- bool operator()(tBTM_SEC_DEV_REC* p_dev_rec,
- const RawAddress& new_pseudo_addr) {
- return body(p_dev_rec, new_pseudo_addr);
- };
-};
-extern struct btm_ble_init_pseudo_addr btm_ble_init_pseudo_addr;
-// Name: btm_ble_addr_resolvable
-// Params: const RawAddress& rpa, tBTM_SEC_DEV_REC* p_dev_rec
-// Returns: bool
-struct btm_ble_addr_resolvable {
- std::function<bool(const RawAddress& rpa, tBTM_SEC_DEV_REC* p_dev_rec)> body{
- [](const RawAddress& rpa, tBTM_SEC_DEV_REC* p_dev_rec) { return false; }};
- bool operator()(const RawAddress& rpa, tBTM_SEC_DEV_REC* p_dev_rec) {
- return body(rpa, p_dev_rec);
- };
-};
-extern struct btm_ble_addr_resolvable btm_ble_addr_resolvable;
-// Name: btm_ble_resolve_random_addr
-// Params: const RawAddress& random_bda
-// Returns: tBTM_SEC_DEV_REC*
-struct btm_ble_resolve_random_addr {
- std::function<tBTM_SEC_DEV_REC*(const RawAddress& random_bda)> body{
- [](const RawAddress& random_bda) { return nullptr; }};
- tBTM_SEC_DEV_REC* operator()(const RawAddress& random_bda) {
- return body(random_bda);
- };
-};
-extern struct btm_ble_resolve_random_addr btm_ble_resolve_random_addr;
-// Name: btm_identity_addr_to_random_pseudo
-// Params: RawAddress* bd_addr, uint8_t* p_addr_type, bool refresh
-// Returns: bool
-struct btm_identity_addr_to_random_pseudo {
- std::function<bool(RawAddress* bd_addr, uint8_t* p_addr_type, bool refresh)>
- body{[](RawAddress* bd_addr, uint8_t* p_addr_type, bool refresh) {
- return false;
- }};
- bool operator()(RawAddress* bd_addr, uint8_t* p_addr_type, bool refresh) {
- return body(bd_addr, p_addr_type, refresh);
- };
-};
-extern struct btm_identity_addr_to_random_pseudo
- btm_identity_addr_to_random_pseudo;
-// Name: btm_identity_addr_to_random_pseudo_from_address_with_type
-// Params: tBLE_BD_ADDR* address_with_type, bool refresh
-// Returns: bool
-struct btm_identity_addr_to_random_pseudo_from_address_with_type {
- std::function<bool(tBLE_BD_ADDR* address_with_type, bool refresh)> body{
- [](tBLE_BD_ADDR* address_with_type, bool refresh) { return false; }};
- bool operator()(tBLE_BD_ADDR* address_with_type, bool refresh) {
- return body(address_with_type, refresh);
- };
-};
-extern struct btm_identity_addr_to_random_pseudo_from_address_with_type
- btm_identity_addr_to_random_pseudo_from_address_with_type;
-// Name: btm_random_pseudo_to_identity_addr
-// Params: RawAddress* random_pseudo, uint8_t* p_identity_addr_type
-// Returns: bool
-struct btm_random_pseudo_to_identity_addr {
- std::function<bool(RawAddress* random_pseudo, uint8_t* p_identity_addr_type)>
- body{[](RawAddress* random_pseudo, uint8_t* p_identity_addr_type) {
- return false;
- }};
- bool operator()(RawAddress* random_pseudo, uint8_t* p_identity_addr_type) {
- return body(random_pseudo, p_identity_addr_type);
- };
-};
-extern struct btm_random_pseudo_to_identity_addr
- btm_random_pseudo_to_identity_addr;
-// Name: btm_ble_refresh_peer_resolvable_private_addr
-// Params: const RawAddress& pseudo_bda, const RawAddress& rpa,
-// tBTM_SEC_BLE::tADDRESS_TYPE rra_type Returns: void
-struct btm_ble_refresh_peer_resolvable_private_addr {
- std::function<void(const RawAddress& pseudo_bda, const RawAddress& rpa,
- tBTM_SEC_BLE::tADDRESS_TYPE rra_type)>
- body{[](const RawAddress& pseudo_bda, const RawAddress& rpa,
- tBTM_SEC_BLE::tADDRESS_TYPE rra_type) {}};
- void operator()(const RawAddress& pseudo_bda, const RawAddress& rpa,
- tBTM_SEC_BLE::tADDRESS_TYPE rra_type) {
- body(pseudo_bda, rpa, rra_type);
- };
-};
-extern struct btm_ble_refresh_peer_resolvable_private_addr
- btm_ble_refresh_peer_resolvable_private_addr;
-
-} // namespace stack_btm_ble_addr
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_btm_ble_adv_filter.cc b/test/mock/mock_stack_btm_ble_adv_filter.cc
deleted file mode 100644
index b36a894e9..000000000
--- a/test/mock/mock_stack_btm_ble_adv_filter.cc
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:6
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/bind_helpers.h>
-#include <string.h>
-#include <algorithm>
-#include <vector>
-#include "bt_target.h"
-#include "bt_types.h"
-#include "btm_ble_api.h"
-#include "btu.h"
-#include "device/include/controller.h"
-#include "hcidefs.h"
-#include "hcimsgs.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_int_types.h"
-#include "utils/include/bt_utils.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void BTM_BleAdvFilterParamSetup(
- int action, tBTM_BLE_PF_FILT_INDEX filt_index,
- std::unique_ptr<btgatt_filt_param_setup_t> p_filt_params,
- tBTM_BLE_PF_PARAM_CB cb) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleEnableDisableFilterFeature(uint8_t enable,
- tBTM_BLE_PF_STATUS_CBACK p_stat_cback) {
- mock_function_count_map[__func__]++;
-}
-void BTM_LE_PF_clear(tBTM_BLE_PF_FILT_INDEX filt_index,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void BTM_LE_PF_set(tBTM_BLE_PF_FILT_INDEX filt_index,
- std::vector<ApcfCommand> commands,
- tBTM_BLE_PF_CFG_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_adv_filter_init(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_btm_ble_advertiser_hci_interface.cc b/test/mock/mock_stack_btm_ble_advertiser_hci_interface.cc
deleted file mode 100644
index 777410b98..000000000
--- a/test/mock/mock_stack_btm_ble_advertiser_hci_interface.cc
+++ /dev/null
@@ -1,75 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:5
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_stack_btm_ble_advertiser_hci_interface.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace stack_btm_ble_advertiser_hci_interface {
-
-// Function state capture and return values, if needed
-struct btm_le_on_advertising_set_terminated
- btm_le_on_advertising_set_terminated;
-struct btm_ble_advertiser_notify_terminated_legacy
- btm_ble_advertiser_notify_terminated_legacy;
-
-} // namespace stack_btm_ble_advertiser_hci_interface
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-void btm_le_on_advertising_set_terminated(uint8_t* p, uint16_t length) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_advertiser_hci_interface::
- btm_le_on_advertising_set_terminated(p, length);
-}
-void btm_ble_advertiser_notify_terminated_legacy(uint8_t status,
- uint16_t connection_handle) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_advertiser_hci_interface::
- btm_ble_advertiser_notify_terminated_legacy(status, connection_handle);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_btm_ble_advertiser_hci_interface.h b/test/mock/mock_stack_btm_ble_advertiser_hci_interface.h
deleted file mode 100644
index 05fef71bf..000000000
--- a/test/mock/mock_stack_btm_ble_advertiser_hci_interface.h
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:5
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include "stack/btm/ble_advertiser_hci_interface.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace stack_btm_ble_advertiser_hci_interface {
-
-// Shared state between mocked functions and tests
-// Name: btm_le_on_advertising_set_terminated
-// Params: uint8_t* p, uint16_t length
-// Returns: void
-struct btm_le_on_advertising_set_terminated {
- std::function<void(uint8_t* p, uint16_t length)> body{
- [](uint8_t* p, uint16_t length) {}};
- void operator()(uint8_t* p, uint16_t length) { body(p, length); };
-};
-extern struct btm_le_on_advertising_set_terminated
- btm_le_on_advertising_set_terminated;
-// Name: btm_ble_advertiser_notify_terminated_legacy
-// Params: uint8_t status, uint16_t connection_handle
-// Returns: void
-struct btm_ble_advertiser_notify_terminated_legacy {
- std::function<void(uint8_t status, uint16_t connection_handle)> body{
- [](uint8_t status, uint16_t connection_handle) {}};
- void operator()(uint8_t status, uint16_t connection_handle) {
- body(status, connection_handle);
- };
-};
-extern struct btm_ble_advertiser_notify_terminated_legacy
- btm_ble_advertiser_notify_terminated_legacy;
-
-} // namespace stack_btm_ble_advertiser_hci_interface
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_btm_ble_batchscan.cc b/test/mock/mock_stack_btm_ble_batchscan.cc
deleted file mode 100644
index 3f5a8803b..000000000
--- a/test/mock/mock_stack_btm_ble_batchscan.cc
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:7
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <stddef.h>
-#include <stdio.h>
-#include <string.h>
-#include <vector>
-#include "bt_target.h"
-#include "bt_types.h"
-#include "btm_ble_api.h"
-#include "btu.h"
-#include "device/include/controller.h"
-#include "hcimsgs.h"
-#include "stack/btm/btm_int_types.h"
-#include "utils/include/bt_utils.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void BTM_BleDisableBatchScan(base::Callback<void(uint8_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleEnableBatchScan(tBTM_BLE_BATCH_SCAN_MODE scan_mode,
- uint32_t scan_interval, uint32_t scan_window,
- tBLE_ADDR_TYPE addr_type,
- tBTM_BLE_DISCARD_RULE discard_rule,
- base::Callback<void(uint8_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleReadScanReports(tBTM_BLE_BATCH_SCAN_MODE scan_mode,
- tBTM_BLE_SCAN_REP_CBACK cb) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleSetStorageConfig(uint8_t batch_scan_full_max,
- uint8_t batch_scan_trunc_max,
- uint8_t batch_scan_notify_threshold,
- base::Callback<void(uint8_t)> cb,
- tBTM_BLE_SCAN_THRESHOLD_CBACK* p_thres_cback,
- tBTM_BLE_REF_VALUE ref_value) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleTrackAdvertiser(tBTM_BLE_TRACK_ADV_CBACK* p_track_cback,
- tBTM_BLE_REF_VALUE ref_value) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_batchscan_init(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_btm_ble_bgconn.cc b/test/mock/mock_stack_btm_ble_bgconn.cc
deleted file mode 100644
index 0772b2b09..000000000
--- a/test/mock/mock_stack_btm_ble_bgconn.cc
+++ /dev/null
@@ -1,116 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:11
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_stack_btm_ble_bgconn.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-struct BackgroundConnection {};
-struct BgConnHash {};
-
-namespace test {
-namespace mock {
-namespace stack_btm_ble_bgconn {
-
-// Function state capture and return values, if needed
-struct convert_to_address_with_type convert_to_address_with_type;
-struct btm_update_scanner_filter_policy btm_update_scanner_filter_policy;
-struct btm_ble_bgconn_cancel_if_disconnected
- btm_ble_bgconn_cancel_if_disconnected;
-struct btm_ble_suspend_bg_conn btm_ble_suspend_bg_conn;
-struct btm_ble_resume_bg_conn btm_ble_resume_bg_conn;
-struct BTM_BackgroundConnectAddressKnown BTM_BackgroundConnectAddressKnown;
-struct BTM_SetLeConnectionModeToFast BTM_SetLeConnectionModeToFast;
-struct BTM_SetLeConnectionModeToSlow BTM_SetLeConnectionModeToSlow;
-struct BTM_AcceptlistAdd BTM_AcceptlistAdd;
-struct BTM_AcceptlistRemove BTM_AcceptlistRemove;
-struct BTM_AcceptlistClear BTM_AcceptlistClear;
-
-} // namespace stack_btm_ble_bgconn
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-const tBLE_BD_ADDR convert_to_address_with_type(
- const RawAddress& bd_addr, const tBTM_SEC_DEV_REC* p_dev_rec) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_bgconn::convert_to_address_with_type(
- bd_addr, p_dev_rec);
-}
-void btm_update_scanner_filter_policy(tBTM_BLE_SFP scan_policy) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_bgconn::btm_update_scanner_filter_policy(
- scan_policy);
-}
-void btm_ble_bgconn_cancel_if_disconnected(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_bgconn::btm_ble_bgconn_cancel_if_disconnected(
- bd_addr);
-}
-bool btm_ble_suspend_bg_conn(void) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_bgconn::btm_ble_suspend_bg_conn();
-}
-bool btm_ble_resume_bg_conn(void) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_bgconn::btm_ble_resume_bg_conn();
-}
-bool BTM_BackgroundConnectAddressKnown(const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_bgconn::BTM_BackgroundConnectAddressKnown(
- address);
-}
-bool BTM_SetLeConnectionModeToFast() {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_bgconn::BTM_SetLeConnectionModeToFast();
-}
-void BTM_SetLeConnectionModeToSlow() {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_bgconn::BTM_SetLeConnectionModeToSlow();
-}
-bool BTM_AcceptlistAdd(const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_bgconn::BTM_AcceptlistAdd(address);
-}
-void BTM_AcceptlistRemove(const RawAddress& address) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_bgconn::BTM_AcceptlistRemove(address);
-}
-void BTM_AcceptlistClear() {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_bgconn::BTM_AcceptlistClear();
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_btm_ble_bgconn.h b/test/mock/mock_stack_btm_ble_bgconn.h
deleted file mode 100644
index 41914ba6b..000000000
--- a/test/mock/mock_stack_btm_ble_bgconn.h
+++ /dev/null
@@ -1,167 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:11
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include <base/bind.h>
-#include <cstdint>
-#include <unordered_map>
-#include "device/include/controller.h"
-#include "main/shim/acl_api.h"
-#include "main/shim/shim.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/btm/security_device_record.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/hcimsgs.h"
-#include "types/raw_address.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace stack_btm_ble_bgconn {
-
-// Shared state between mocked functions and tests
-// Name: convert_to_address_with_type
-// Params: const RawAddress& bd_addr, const tBTM_SEC_DEV_REC* p_dev_rec
-// Returns: const tBLE_BD_ADDR
-struct convert_to_address_with_type {
- tBLE_BD_ADDR ble_bd_addr;
- std::function<const tBLE_BD_ADDR(const RawAddress& bd_addr,
- const tBTM_SEC_DEV_REC* p_dev_rec)>
- body{[this](const RawAddress& bd_addr,
- const tBTM_SEC_DEV_REC* p_dev_rec) { return ble_bd_addr; }};
- const tBLE_BD_ADDR operator()(const RawAddress& bd_addr,
- const tBTM_SEC_DEV_REC* p_dev_rec) {
- return body(bd_addr, p_dev_rec);
- };
-};
-extern struct convert_to_address_with_type convert_to_address_with_type;
-// Name: btm_update_scanner_filter_policy
-// Params: tBTM_BLE_SFP scan_policy
-// Returns: void
-struct btm_update_scanner_filter_policy {
- std::function<void(tBTM_BLE_SFP scan_policy)> body{
- [](tBTM_BLE_SFP scan_policy) {}};
- void operator()(tBTM_BLE_SFP scan_policy) { body(scan_policy); };
-};
-extern struct btm_update_scanner_filter_policy btm_update_scanner_filter_policy;
-// Name: btm_ble_bgconn_cancel_if_disconnected
-// Params: const RawAddress& bd_addr
-// Returns: void
-struct btm_ble_bgconn_cancel_if_disconnected {
- std::function<void(const RawAddress& bd_addr)> body{
- [](const RawAddress& bd_addr) {}};
- void operator()(const RawAddress& bd_addr) { body(bd_addr); };
-};
-extern struct btm_ble_bgconn_cancel_if_disconnected
- btm_ble_bgconn_cancel_if_disconnected;
-// Name: btm_ble_suspend_bg_conn
-// Params: void
-// Returns: bool
-struct btm_ble_suspend_bg_conn {
- std::function<bool(void)> body{[](void) { return false; }};
- bool operator()(void) { return body(); };
-};
-extern struct btm_ble_suspend_bg_conn btm_ble_suspend_bg_conn;
-// Name: btm_ble_resume_bg_conn
-// Params: void
-// Returns: bool
-struct btm_ble_resume_bg_conn {
- std::function<bool(void)> body{[](void) { return false; }};
- bool operator()(void) { return body(); };
-};
-extern struct btm_ble_resume_bg_conn btm_ble_resume_bg_conn;
-// Name: BTM_BackgroundConnectAddressKnown
-// Params: const RawAddress& address
-// Returns: bool
-struct BTM_BackgroundConnectAddressKnown {
- std::function<bool(const RawAddress& address)> body{
- [](const RawAddress& address) { return false; }};
- bool operator()(const RawAddress& address) { return body(address); };
-};
-extern struct BTM_BackgroundConnectAddressKnown
- BTM_BackgroundConnectAddressKnown;
-// Name: BTM_SetLeConnectionModeToFast
-// Params:
-// Returns: bool
-struct BTM_SetLeConnectionModeToFast {
- std::function<bool()> body{[]() { return false; }};
- bool operator()() { return body(); };
-};
-extern struct BTM_SetLeConnectionModeToFast BTM_SetLeConnectionModeToFast;
-// Name: BTM_SetLeConnectionModeToSlow
-// Params:
-// Returns: void
-struct BTM_SetLeConnectionModeToSlow {
- std::function<void()> body{[]() {}};
- void operator()() { body(); };
-};
-extern struct BTM_SetLeConnectionModeToSlow BTM_SetLeConnectionModeToSlow;
-// Name: BTM_AcceptlistAdd
-// Params: const RawAddress& address
-// Returns: bool
-struct BTM_AcceptlistAdd {
- std::function<bool(const RawAddress& address)> body{
- [](const RawAddress& address) { return false; }};
- bool operator()(const RawAddress& address) { return body(address); };
-};
-extern struct BTM_AcceptlistAdd BTM_AcceptlistAdd;
-// Name: BTM_AcceptlistRemove
-// Params: const RawAddress& address
-// Returns: void
-struct BTM_AcceptlistRemove {
- std::function<void(const RawAddress& address)> body{
- [](const RawAddress& address) {}};
- void operator()(const RawAddress& address) { body(address); };
-};
-extern struct BTM_AcceptlistRemove BTM_AcceptlistRemove;
-// Name: BTM_AcceptlistClear
-// Params:
-// Returns: void
-struct BTM_AcceptlistClear {
- std::function<void()> body{[]() {}};
- void operator()() { body(); };
-};
-extern struct BTM_AcceptlistClear BTM_AcceptlistClear;
-
-} // namespace stack_btm_ble_bgconn
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_btm_ble_gap.cc b/test/mock/mock_stack_btm_ble_gap.cc
deleted file mode 100644
index 582a2dc40..000000000
--- a/test/mock/mock_stack_btm_ble_gap.cc
+++ /dev/null
@@ -1,213 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:47
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/strings/string_number_conversions.h>
-#include <cstdint>
-#include <list>
-#include <memory>
-#include <vector>
-#include "common/time_util.h"
-#include "device/include/controller.h"
-#include "main/shim/acl_api.h"
-#include "main/shim/btm_api.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_ble_int_types.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/gatt/gatt_int.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/advertise_data_parser.h"
-#include "stack/include/bt_types.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/include/gap_api.h"
-#include "stack/include/hci_error_code.h"
-#include "stack/include/hcimsgs.h"
-#include "stack/include/inq_hci_link_interface.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool BTM_BleConfigPrivacy(bool privacy_mode) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_BleLocalPrivacyEnabled(void) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_ble_cancel_remote_name(const RawAddress& remote_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_ble_clear_topology_mask(tBTM_BLE_STATE_MASK request_state_mask) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_ble_set_topology_mask(tBTM_BLE_STATE_MASK request_state_mask) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_ble_topology_check(tBTM_BLE_STATE_MASK request_state_mask) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tBTM_STATUS BTM_BleObserve(bool start, uint8_t duration,
- tBTM_INQ_RESULTS_CB* p_results_cb,
- tBTM_CMPL_CB* p_cmpl_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_ble_read_remote_name(const RawAddress& remote_bda,
- tBTM_CMPL_CB* p_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_ble_set_connectability(uint16_t combined_mode) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_ble_set_discoverability(uint16_t combined_mode) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_ble_start_adv(void) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_ble_start_inquiry(uint8_t duration) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_ble_stop_adv(void) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-uint16_t BTM_BleReadConnectability() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t BTM_BleReadDiscoverability() {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t BTM_BleMaxMultiAdvInstanceCount(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void BTM_BleGetDynamicAudioBuffer(
- tBTM_BT_DYNAMIC_AUDIO_BUFFER_CB p_dynamic_audio_buffer_cb[]) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleGetVendorCapabilities(tBTM_BLE_VSC_CB* p_cmn_vsc_cb) {
- mock_function_count_map[__func__]++;
-}
-void BTM_BleSetScanParams(uint32_t scan_interval, uint32_t scan_window,
- tBLE_SCAN_MODE scan_mode,
- base::Callback<void(uint8_t)> cb) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_decrement_link_topology_mask(uint8_t link_role) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_dir_adv_tout(void) { mock_function_count_map[__func__]++; }
-void btm_ble_free() { mock_function_count_map[__func__]++; }
-void btm_ble_increment_link_topology_mask(uint8_t link_role) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_init(void) { mock_function_count_map[__func__]++; }
-void btm_ble_process_adv_addr(RawAddress& bda, uint8_t* addr_type) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_process_adv_pkt(uint8_t data_len, uint8_t* data) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_process_adv_pkt_cont(uint16_t evt_type, uint8_t addr_type,
- const RawAddress& bda, uint8_t primary_phy,
- uint8_t secondary_phy,
- uint8_t advertising_sid, int8_t tx_power,
- int8_t rssi, uint16_t periodic_adv_int,
- uint8_t data_len, uint8_t* data) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_process_adv_pkt_cont_for_inquiry(
- uint16_t evt_type, uint8_t addr_type, const RawAddress& bda,
- uint8_t primary_phy, uint8_t secondary_phy, uint8_t advertising_sid,
- int8_t tx_power, int8_t rssi, uint16_t periodic_adv_int,
- std::vector<uint8_t> advertising_data) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_process_ext_adv_pkt(uint8_t data_len, uint8_t* data) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_process_phy_update_pkt(uint8_t len, uint8_t* data) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_read_remote_features_complete(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_read_remote_name_cmpl(bool status, const RawAddress& bda,
- uint16_t length, char* p_name) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_set_adv_flag(uint16_t connect_mode, uint16_t disc_mode) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_start_scan() { mock_function_count_map[__func__]++; }
-void btm_ble_stop_inquiry(void) { mock_function_count_map[__func__]++; }
-void btm_ble_stop_scan(void) { mock_function_count_map[__func__]++; }
-void btm_ble_update_dmt_flag_bits(uint8_t* adv_flag_value,
- const uint16_t connect_mode,
- const uint16_t disc_mode) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_update_inq_result(tINQ_DB_ENT* p_i, uint8_t addr_type,
- const RawAddress& bda, uint16_t evt_type,
- uint8_t primary_phy, uint8_t secondary_phy,
- uint8_t advertising_sid, int8_t tx_power,
- int8_t rssi, uint16_t periodic_adv_int,
- std::vector<uint8_t> const& data) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_update_mode_operation(uint8_t link_role, const RawAddress* bd_addr,
- tHCI_STATUS status) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_write_adv_enable_complete(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_clear_all_pending_le_entry(void) {
- mock_function_count_map[__func__]++;
-}
-void btm_send_hci_set_scan_params(uint8_t scan_type, uint16_t scan_int,
- uint16_t scan_win, uint8_t addr_type_own,
- uint8_t scan_filter_policy) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_btm_ble_multi_adv.cc b/test/mock/mock_stack_btm_ble_multi_adv.cc
deleted file mode 100644
index aa8c54fb7..000000000
--- a/test/mock/mock_stack_btm_ble_multi_adv.cc
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:11
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/bind_helpers.h>
-#include <base/location.h>
-#include <base/logging.h>
-#include <base/memory/weak_ptr.h>
-#include <base/strings/string_number_conversions.h>
-#include <base/time/time.h>
-#include <string.h>
-#include <queue>
-#include <vector>
-#include "ble_advertiser.h"
-#include "bt_target.h"
-#include "device/include/controller.h"
-#include "osi/include/alarm.h"
-#include "stack/btm/ble_advertiser_hci_interface.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_int_types.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void BleAdvertisingManager::CleanUp() { mock_function_count_map[__func__]++; }
-void btm_ble_adv_init() { mock_function_count_map[__func__]++; }
-base::WeakPtr<BleAdvertisingManager> BleAdvertisingManager::Get() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-bool BleAdvertisingManager::IsInitialized() {
- mock_function_count_map[__func__]++;
- return false;
-}
-void test_timeout_cb(uint8_t status) { mock_function_count_map[__func__]++; }
-void BleAdvertisingManager::Initialize(BleAdvertiserHciInterface* interface) {
- mock_function_count_map[__func__]++;
-}
-void btm_ble_multi_adv_cleanup(void) { mock_function_count_map[__func__]++; }
-void testRecomputeTimeout1() { mock_function_count_map[__func__]++; }
-void testRecomputeTimeout2() { mock_function_count_map[__func__]++; }
-void testRecomputeTimeout3() { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_btm_ble_privacy.cc b/test/mock/mock_stack_btm_ble_privacy.cc
deleted file mode 100644
index 2482a0e77..000000000
--- a/test/mock/mock_stack_btm_ble_privacy.cc
+++ /dev/null
@@ -1,140 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:13
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_stack_btm_ble_privacy.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace stack_btm_ble_privacy {
-
-// Function state capture and return values, if needed
-struct btm_ble_clear_resolving_list_complete
- btm_ble_clear_resolving_list_complete;
-struct btm_ble_add_resolving_list_entry_complete
- btm_ble_add_resolving_list_entry_complete;
-struct btm_ble_remove_resolving_list_entry_complete
- btm_ble_remove_resolving_list_entry_complete;
-struct btm_ble_read_resolving_list_entry_complete
- btm_ble_read_resolving_list_entry_complete;
-struct btm_ble_remove_resolving_list_entry btm_ble_remove_resolving_list_entry;
-struct btm_ble_clear_resolving_list btm_ble_clear_resolving_list;
-struct btm_ble_read_resolving_list_entry btm_ble_read_resolving_list_entry;
-struct btm_ble_disable_resolving_list btm_ble_disable_resolving_list;
-struct btm_ble_resolving_list_load_dev btm_ble_resolving_list_load_dev;
-struct btm_ble_resolving_list_remove_dev btm_ble_resolving_list_remove_dev;
-struct btm_ble_enable_resolving_list btm_ble_enable_resolving_list;
-struct btm_ble_enable_resolving_list_for_platform
- btm_ble_enable_resolving_list_for_platform;
-struct btm_ble_resolving_list_init btm_ble_resolving_list_init;
-
-} // namespace stack_btm_ble_privacy
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-void btm_ble_clear_resolving_list_complete(uint8_t* p, uint16_t evt_len) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_privacy::btm_ble_clear_resolving_list_complete(
- p, evt_len);
-}
-void btm_ble_add_resolving_list_entry_complete(uint8_t* p, uint16_t evt_len) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_privacy::btm_ble_add_resolving_list_entry_complete(
- p, evt_len);
-}
-void btm_ble_remove_resolving_list_entry_complete(uint8_t* p,
- uint16_t evt_len) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_privacy::
- btm_ble_remove_resolving_list_entry_complete(p, evt_len);
-}
-void btm_ble_read_resolving_list_entry_complete(uint8_t* p, uint16_t evt_len) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_privacy::btm_ble_read_resolving_list_entry_complete(
- p, evt_len);
-}
-tBTM_STATUS btm_ble_remove_resolving_list_entry(tBTM_SEC_DEV_REC* p_dev_rec) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_privacy::btm_ble_remove_resolving_list_entry(
- p_dev_rec);
-}
-void btm_ble_clear_resolving_list(void) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_privacy::btm_ble_clear_resolving_list();
-}
-bool btm_ble_read_resolving_list_entry(tBTM_SEC_DEV_REC* p_dev_rec) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_privacy::btm_ble_read_resolving_list_entry(
- p_dev_rec);
-}
-bool btm_ble_disable_resolving_list(uint8_t rl_mask, bool to_resume) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_privacy::btm_ble_disable_resolving_list(
- rl_mask, to_resume);
-}
-bool btm_ble_resolving_list_load_dev(tBTM_SEC_DEV_REC* p_dev_rec) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_btm_ble_privacy::btm_ble_resolving_list_load_dev(
- p_dev_rec);
-}
-void btm_ble_resolving_list_remove_dev(tBTM_SEC_DEV_REC* p_dev_rec) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_privacy::btm_ble_resolving_list_remove_dev(
- p_dev_rec);
-}
-void btm_ble_enable_resolving_list(uint8_t rl_mask) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_privacy::btm_ble_enable_resolving_list(rl_mask);
-}
-void btm_ble_enable_resolving_list_for_platform(uint8_t rl_mask) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_privacy::btm_ble_enable_resolving_list_for_platform(
- rl_mask);
-}
-void btm_ble_resolving_list_init(uint8_t max_irk_list_sz) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_privacy::btm_ble_resolving_list_init(
- max_irk_list_sz);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_btm_ble_privacy.h b/test/mock/mock_stack_btm_ble_privacy.h
deleted file mode 100644
index 18dbb3d3a..000000000
--- a/test/mock/mock_stack_btm_ble_privacy.h
+++ /dev/null
@@ -1,180 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:13
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include "stack/btm/security_device_record.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace stack_btm_ble_privacy {
-
-// Shared state between mocked functions and tests
-// Name: btm_ble_clear_resolving_list_complete
-// Params: uint8_t* p, uint16_t evt_len
-// Returns: void
-struct btm_ble_clear_resolving_list_complete {
- std::function<void(uint8_t* p, uint16_t evt_len)> body{
- [](uint8_t* p, uint16_t evt_len) {}};
- void operator()(uint8_t* p, uint16_t evt_len) { body(p, evt_len); };
-};
-extern struct btm_ble_clear_resolving_list_complete
- btm_ble_clear_resolving_list_complete;
-// Name: btm_ble_add_resolving_list_entry_complete
-// Params: uint8_t* p, uint16_t evt_len
-// Returns: void
-struct btm_ble_add_resolving_list_entry_complete {
- std::function<void(uint8_t* p, uint16_t evt_len)> body{
- [](uint8_t* p, uint16_t evt_len) {}};
- void operator()(uint8_t* p, uint16_t evt_len) { body(p, evt_len); };
-};
-extern struct btm_ble_add_resolving_list_entry_complete
- btm_ble_add_resolving_list_entry_complete;
-// Name: btm_ble_remove_resolving_list_entry_complete
-// Params: uint8_t* p, uint16_t evt_len
-// Returns: void
-struct btm_ble_remove_resolving_list_entry_complete {
- std::function<void(uint8_t* p, uint16_t evt_len)> body{
- [](uint8_t* p, uint16_t evt_len) {}};
- void operator()(uint8_t* p, uint16_t evt_len) { body(p, evt_len); };
-};
-extern struct btm_ble_remove_resolving_list_entry_complete
- btm_ble_remove_resolving_list_entry_complete;
-// Name: btm_ble_read_resolving_list_entry_complete
-// Params: uint8_t* p, uint16_t evt_len
-// Returns: void
-struct btm_ble_read_resolving_list_entry_complete {
- std::function<void(uint8_t* p, uint16_t evt_len)> body{
- [](uint8_t* p, uint16_t evt_len) {}};
- void operator()(uint8_t* p, uint16_t evt_len) { body(p, evt_len); };
-};
-extern struct btm_ble_read_resolving_list_entry_complete
- btm_ble_read_resolving_list_entry_complete;
-// Name: btm_ble_remove_resolving_list_entry
-// Params: tBTM_SEC_DEV_REC* p_dev_rec
-// Returns: tBTM_STATUS
-struct btm_ble_remove_resolving_list_entry {
- std::function<tBTM_STATUS(tBTM_SEC_DEV_REC* p_dev_rec)> body{
- [](tBTM_SEC_DEV_REC* p_dev_rec) { return 0; }};
- tBTM_STATUS operator()(tBTM_SEC_DEV_REC* p_dev_rec) {
- return body(p_dev_rec);
- };
-};
-extern struct btm_ble_remove_resolving_list_entry
- btm_ble_remove_resolving_list_entry;
-// Name: btm_ble_clear_resolving_list
-// Params: void
-// Returns: void
-struct btm_ble_clear_resolving_list {
- std::function<void(void)> body{[](void) {}};
- void operator()(void) { body(); };
-};
-extern struct btm_ble_clear_resolving_list btm_ble_clear_resolving_list;
-// Name: btm_ble_read_resolving_list_entry
-// Params: tBTM_SEC_DEV_REC* p_dev_rec
-// Returns: bool
-struct btm_ble_read_resolving_list_entry {
- std::function<bool(tBTM_SEC_DEV_REC* p_dev_rec)> body{
- [](tBTM_SEC_DEV_REC* p_dev_rec) { return false; }};
- bool operator()(tBTM_SEC_DEV_REC* p_dev_rec) { return body(p_dev_rec); };
-};
-extern struct btm_ble_read_resolving_list_entry
- btm_ble_read_resolving_list_entry;
-// Name: btm_ble_disable_resolving_list
-// Params: uint8_t rl_mask, bool to_resume
-// Returns: bool
-struct btm_ble_disable_resolving_list {
- std::function<bool(uint8_t rl_mask, bool to_resume)> body{
- [](uint8_t rl_mask, bool to_resume) { return false; }};
- bool operator()(uint8_t rl_mask, bool to_resume) {
- return body(rl_mask, to_resume);
- };
-};
-extern struct btm_ble_disable_resolving_list btm_ble_disable_resolving_list;
-// Name: btm_ble_resolving_list_load_dev
-// Params: tBTM_SEC_DEV_REC* p_dev_rec
-// Returns: bool
-struct btm_ble_resolving_list_load_dev {
- std::function<bool(tBTM_SEC_DEV_REC* p_dev_rec)> body{
- [](tBTM_SEC_DEV_REC* p_dev_rec) { return false; }};
- bool operator()(tBTM_SEC_DEV_REC* p_dev_rec) { return body(p_dev_rec); };
-};
-extern struct btm_ble_resolving_list_load_dev btm_ble_resolving_list_load_dev;
-// Name: btm_ble_resolving_list_remove_dev
-// Params: tBTM_SEC_DEV_REC* p_dev_rec
-// Returns: void
-struct btm_ble_resolving_list_remove_dev {
- std::function<void(tBTM_SEC_DEV_REC* p_dev_rec)> body{
- [](tBTM_SEC_DEV_REC* p_dev_rec) {}};
- void operator()(tBTM_SEC_DEV_REC* p_dev_rec) { body(p_dev_rec); };
-};
-extern struct btm_ble_resolving_list_remove_dev
- btm_ble_resolving_list_remove_dev;
-// Name: btm_ble_enable_resolving_list
-// Params: uint8_t rl_mask
-// Returns: void
-struct btm_ble_enable_resolving_list {
- std::function<void(uint8_t rl_mask)> body{[](uint8_t rl_mask) {}};
- void operator()(uint8_t rl_mask) { body(rl_mask); };
-};
-extern struct btm_ble_enable_resolving_list btm_ble_enable_resolving_list;
-// Name: btm_ble_enable_resolving_list_for_platform
-// Params: uint8_t rl_mask
-// Returns: void
-struct btm_ble_enable_resolving_list_for_platform {
- std::function<void(uint8_t rl_mask)> body{[](uint8_t rl_mask) {}};
- void operator()(uint8_t rl_mask) { body(rl_mask); };
-};
-extern struct btm_ble_enable_resolving_list_for_platform
- btm_ble_enable_resolving_list_for_platform;
-// Name: btm_ble_resolving_list_init
-// Params: uint8_t max_irk_list_sz
-// Returns: void
-struct btm_ble_resolving_list_init {
- std::function<void(uint8_t max_irk_list_sz)> body{
- [](uint8_t max_irk_list_sz) {}};
- void operator()(uint8_t max_irk_list_sz) { body(max_irk_list_sz); };
-};
-extern struct btm_ble_resolving_list_init btm_ble_resolving_list_init;
-
-} // namespace stack_btm_ble_privacy
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_btm_ble_scanner_hci_interface.cc b/test/mock/mock_stack_btm_ble_scanner_hci_interface.cc
deleted file mode 100644
index 8a69f1f2b..000000000
--- a/test/mock/mock_stack_btm_ble_scanner_hci_interface.cc
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:6
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_stack_btm_ble_scanner_hci_interface.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace stack_btm_ble_scanner_hci_interface {
-
-// Function state capture and return values, if needed
-struct btm_ble_process_periodic_adv_sync_est_evt
- btm_ble_process_periodic_adv_sync_est_evt;
-struct btm_ble_process_periodic_adv_pkt btm_ble_process_periodic_adv_pkt;
-struct btm_ble_process_periodic_adv_sync_lost_evt
- btm_ble_process_periodic_adv_sync_lost_evt;
-
-} // namespace stack_btm_ble_scanner_hci_interface
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-void btm_ble_process_periodic_adv_sync_est_evt(uint8_t data_len,
- uint8_t* data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_scanner_hci_interface::
- btm_ble_process_periodic_adv_sync_est_evt(data_len, data);
-}
-void btm_ble_process_periodic_adv_pkt(uint8_t data_len, uint8_t* data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_scanner_hci_interface::
- btm_ble_process_periodic_adv_pkt(data_len, data);
-}
-void btm_ble_process_periodic_adv_sync_lost_evt(uint8_t data_len,
- uint8_t* data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_btm_ble_scanner_hci_interface::
- btm_ble_process_periodic_adv_sync_lost_evt(data_len, data);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_btm_ble_scanner_hci_interface.h b/test/mock/mock_stack_btm_ble_scanner_hci_interface.h
deleted file mode 100644
index a28a49810..000000000
--- a/test/mock/mock_stack_btm_ble_scanner_hci_interface.h
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:6
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include "stack/btm/ble_scanner_hci_interface.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace stack_btm_ble_scanner_hci_interface {
-
-// Name: btm_ble_process_periodic_adv_sync_est_evt
-// Params: uint8_t data_len, uint8_t* data
-// Returns: void
-struct btm_ble_process_periodic_adv_sync_est_evt {
- std::function<void(uint8_t data_len, uint8_t* data)> body{
- [](uint8_t data_len, uint8_t* data) {}};
- void operator()(uint8_t data_len, uint8_t* data) { body(data_len, data); };
-};
-extern struct btm_ble_process_periodic_adv_sync_est_evt
- btm_ble_process_periodic_adv_sync_est_evt;
-// Name: btm_ble_process_periodic_adv_pkt
-// Params: uint8_t data_len, uint8_t* data
-// Returns: void
-struct btm_ble_process_periodic_adv_pkt {
- std::function<void(uint8_t data_len, uint8_t* data)> body{
- [](uint8_t data_len, uint8_t* data) {}};
- void operator()(uint8_t data_len, uint8_t* data) { body(data_len, data); };
-};
-extern struct btm_ble_process_periodic_adv_pkt btm_ble_process_periodic_adv_pkt;
-// Name: btm_ble_process_periodic_adv_sync_lost_evt
-// Params: uint8_t data_len, uint8_t* data
-// Returns: void
-struct btm_ble_process_periodic_adv_sync_lost_evt {
- std::function<void(uint8_t data_len, uint8_t* data)> body{
- [](uint8_t data_len, uint8_t* data) {}};
- void operator()(uint8_t data_len, uint8_t* data) { body(data_len, data); };
-};
-extern struct btm_ble_process_periodic_adv_sync_lost_evt
- btm_ble_process_periodic_adv_sync_lost_evt;
-
-} // namespace stack_btm_ble_scanner_hci_interface
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_btm_dev.cc b/test/mock/mock_stack_btm_dev.cc
deleted file mode 100644
index 52573462d..000000000
--- a/test/mock/mock_stack_btm_dev.cc
+++ /dev/null
@@ -1,112 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:16
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <stddef.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include "bt_common.h"
-#include "bt_types.h"
-#include "btm_api.h"
-#include "btu.h"
-#include "device/include/controller.h"
-#include "hcidefs.h"
-#include "hcimsgs.h"
-#include "l2c_api.h"
-#include "main/shim/btm_api.h"
-#include "main/shim/shim.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/include/acl_api.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool BTM_SecAddDevice(const RawAddress& bd_addr, DEV_CLASS dev_class,
- BD_NAME bd_name, uint8_t* features, LinkKey* p_link_key,
- uint8_t key_type, uint8_t pin_length) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_SecDeleteDevice(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_dev_support_role_switch(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_set_bond_type_dev(const RawAddress& bd_addr,
- tBTM_SEC_DEV_REC::tBTM_BOND_TYPE bond_type) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool is_address_equal(void* data, void* context) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool is_handle_equal(void* data, void* context) {
- mock_function_count_map[__func__]++;
- return false;
-}
-char* BTM_SecReadDevName(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_SEC_DEV_REC* btm_find_dev(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_SEC_DEV_REC* btm_find_dev_by_handle(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_SEC_DEV_REC* btm_find_or_alloc_dev(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_SEC_DEV_REC* btm_sec_alloc_dev(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_SEC_DEV_REC* btm_sec_allocate_dev_rec(void) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_SEC_DEV_REC::tBTM_BOND_TYPE btm_get_bond_type_dev(
- const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return tBTM_SEC_DEV_REC::BOND_TYPE_UNKNOWN;
-}
-void BTM_SecClearSecurityFlags(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btm_consolidate_dev(tBTM_SEC_DEV_REC* p_target_rec) {
- mock_function_count_map[__func__]++;
-}
-void wipe_secrets_and_remove(tBTM_SEC_DEV_REC* p_dev_rec) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_btm_devctl.cc b/test/mock/mock_stack_btm_devctl.cc
deleted file mode 100644
index ea3d41ad7..000000000
--- a/test/mock/mock_stack_btm_devctl.cc
+++ /dev/null
@@ -1,123 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:21
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <stddef.h>
-#include <stdlib.h>
-#include <string.h>
-#include "bt_types.h"
-#include "bta/dm/bta_dm_int.h"
-#include "bta/sys/bta_sys.h"
-#include "btcore/include/module.h"
-#include "btif/include/btif_bqr.h"
-#include "btu.h"
-#include "common/message_loop_thread.h"
-#include "device/include/controller.h"
-#include "hci/include/hci_layer.h"
-#include "hcimsgs.h"
-#include "main/shim/btm_api.h"
-#include "main/shim/controller.h"
-#include "main/shim/shim.h"
-#include "osi/include/osi.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/gatt/connection_manager.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/l2cap_controller_interface.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool BTM_IsDeviceUp(void) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tBTM_STATUS BTM_BT_Quality_Report_VSE_Register(
- bool is_register, tBTM_BT_QUALITY_REPORT_RECEIVER* p_bqr_report_receiver) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_DeleteStoredLinkKey(const RawAddress* bd_addr,
- tBTM_CMPL_CB* p_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_EnableTestMode(void) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_ReadLocalDeviceName(char** p_name) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_ReadLocalDeviceNameFromController(
- tBTM_CMPL_CB* p_rln_cmpl_cback) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_RegisterForVSEvents(tBTM_VS_EVT_CB* p_cb, bool is_register) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SetDeviceClass(DEV_CLASS dev_class) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SetLocalDeviceName(char* p_name) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-uint8_t* BTM_ReadDeviceClass(void) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void BTM_VendorSpecificCommand(uint16_t opcode, uint8_t param_len,
- uint8_t* p_param_buf, tBTM_VSC_CMPL_CB* p_cb) {
- mock_function_count_map[__func__]++;
-}
-void BTM_WritePageTimeout(uint16_t timeout) {
- mock_function_count_map[__func__]++;
-}
-void BTM_WriteVoiceSettings(uint16_t settings) {
- mock_function_count_map[__func__]++;
-}
-void BTM_db_reset(void) { mock_function_count_map[__func__]++; }
-void BTM_reset_complete() { mock_function_count_map[__func__]++; }
-void btm_delete_stored_link_key_complete(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_dev_free() { mock_function_count_map[__func__]++; }
-void btm_dev_init() { mock_function_count_map[__func__]++; }
-void btm_read_local_name_complete(uint8_t* p, UNUSED_ATTR uint16_t evt_len) {
- mock_function_count_map[__func__]++;
-}
-void btm_vendor_specific_evt(uint8_t* p, uint8_t evt_len) {
- mock_function_count_map[__func__]++;
-}
-void btm_vsc_complete(uint8_t* p, uint16_t opcode, uint16_t evt_len,
- tBTM_VSC_CMPL_CB* p_vsc_cplt_cback) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_btm_inq.cc b/test/mock/mock_stack_btm_inq.cc
deleted file mode 100644
index 594e74f48..000000000
--- a/test/mock/mock_stack_btm_inq.cc
+++ /dev/null
@@ -1,188 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:44
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <stddef.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include "advertise_data_parser.h"
-#include "bt_common.h"
-#include "bt_types.h"
-#include "btm_api.h"
-#include "btu.h"
-#include "common/time_util.h"
-#include "device/include/controller.h"
-#include "hcidefs.h"
-#include "main/shim/btm_api.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_int.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/btm_ble_api.h"
-#include "stack/include/hcimsgs.h"
-#include "stack/include/inq_hci_link_interface.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void SendRemoteNameRequest(const RawAddress& raw_address) {
- mock_function_count_map[__func__]++;
-}
-bool BTM_HasEirService(const uint32_t* p_eir_uuid, uint16_t uuid16) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_inq_find_bdaddr(const RawAddress& p_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tBTM_EIR_SEARCH_RESULT BTM_HasInquiryEirService(tBTM_INQ_RESULTS* p_results,
- uint16_t uuid16) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTM_INQ_INFO* BTM_InqDbFirst(void) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_INQ_INFO* BTM_InqDbNext(tBTM_INQ_INFO* p_cur) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_INQ_INFO* BTM_InqDbRead(const RawAddress& p_bda) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_STATUS BTM_CancelRemoteDeviceName(void) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_ClearInqDb(const RawAddress* p_bda) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_ReadRemoteDeviceName(const RawAddress& remote_bda,
- tBTM_CMPL_CB* p_cb,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SetConnectability(uint16_t page_mode) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SetDiscoverability(uint16_t inq_mode) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SetInquiryMode(uint8_t mode) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_StartInquiry(tBTM_INQ_RESULTS_CB* p_results_cb,
- tBTM_CMPL_CB* p_cmpl_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_WriteEIR(BT_HDR* p_buff) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_initiate_rem_name(const RawAddress& remote_bda, uint8_t origin,
- uint64_t timeout_ms, tBTM_CMPL_CB* p_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tINQ_DB_ENT* btm_inq_db_find(const RawAddress& p_bda) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tINQ_DB_ENT* btm_inq_db_new(const RawAddress& p_bda) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-uint16_t BTM_IsInquiryActive(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t BTM_GetEirSupportedServices(uint32_t* p_eir_uuid, uint8_t** p,
- uint8_t max_num_uuid16,
- uint8_t* p_num_uuid16) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t BTM_GetEirUuidList(uint8_t* p_eir, size_t eir_len, uint8_t uuid_size,
- uint8_t* p_num_uuid, uint8_t* p_uuid_list,
- uint8_t max_num_uuid) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void BTM_AddEirService(uint32_t* p_eir_uuid, uint16_t uuid16) {
- mock_function_count_map[__func__]++;
-}
-void BTM_CancelInquiry(void) { mock_function_count_map[__func__]++; }
-void BTM_EnableInterlacedInquiryScan() { mock_function_count_map[__func__]++; }
-void BTM_EnableInterlacedPageScan() { mock_function_count_map[__func__]++; }
-void BTM_RemoveEirService(uint32_t* p_eir_uuid, uint16_t uuid16) {
- mock_function_count_map[__func__]++;
-}
-void btm_clr_inq_db(const RawAddress* p_bda) {
- mock_function_count_map[__func__]++;
-}
-void btm_clr_inq_result_flt(void) { mock_function_count_map[__func__]++; }
-void btm_inq_clear_ssp(void) { mock_function_count_map[__func__]++; }
-void btm_inq_db_free(void) { mock_function_count_map[__func__]++; }
-void btm_inq_db_init(void) { mock_function_count_map[__func__]++; }
-void btm_inq_db_reset(void) { mock_function_count_map[__func__]++; }
-void btm_inq_remote_name_timer_timeout(UNUSED_ATTR void* data) {
- mock_function_count_map[__func__]++;
-}
-void btm_inq_rmt_name_failed_cancelled(void) {
- mock_function_count_map[__func__]++;
-}
-void btm_inq_stop_on_ssp(void) { mock_function_count_map[__func__]++; }
-void btm_process_cancel_complete(uint8_t status, uint8_t mode) {
- mock_function_count_map[__func__]++;
-}
-void btm_process_inq_complete(uint8_t status, uint8_t mode) {
- mock_function_count_map[__func__]++;
-}
-void btm_process_inq_results(uint8_t* p, uint8_t hci_evt_len,
- uint8_t inq_res_mode) {
- mock_function_count_map[__func__]++;
-}
-void btm_process_remote_name(const RawAddress* bda, BD_NAME bdn,
- uint16_t evt_len, uint8_t hci_status) {
- mock_function_count_map[__func__]++;
-}
-void btm_set_eir_uuid(uint8_t* p_eir, tBTM_INQ_RESULTS* p_results) {
- mock_function_count_map[__func__]++;
-}
-void btm_sort_inq_result(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_btm_iso.cc b/test/mock/mock_stack_btm_iso.cc
deleted file mode 100644
index b28a8c186..000000000
--- a/test/mock/mock_stack_btm_iso.cc
+++ /dev/null
@@ -1,45 +0,0 @@
-#include <memory>
-
-#include "stack/include/btm_iso_api.h"
-
-using bluetooth::hci::iso_manager::BigCallbacks;
-using bluetooth::hci::iso_manager::CigCallbacks;
-
-namespace bluetooth {
-namespace hci {
-
-struct IsoManager::impl {};
-
-IsoManager::IsoManager() {}
-IsoManager::~IsoManager() {}
-void IsoManager::RegisterCigCallbacks(CigCallbacks* callbacks) const {}
-void IsoManager::RegisterBigCallbacks(BigCallbacks* callbacks) const {}
-void IsoManager::CreateCig(uint8_t cig_id,
- struct iso_manager::cig_create_params cig_params) {}
-void IsoManager::ReconfigureCig(
- uint8_t cig_id, struct iso_manager::cig_create_params cig_params) {}
-void IsoManager::RemoveCig(uint8_t cig_id) {}
-void IsoManager::EstablishCis(
- struct iso_manager::cis_establish_params conn_params) {}
-void IsoManager::DisconnectCis(uint16_t cis_handle, uint8_t reason) {}
-void IsoManager::SetupIsoDataPath(
- uint16_t iso_handle, struct iso_manager::iso_data_path_params path_params) {
-}
-void IsoManager::RemoveIsoDataPath(uint16_t iso_handle, uint8_t data_path_dir) {
-}
-void IsoManager::ReadIsoLinkQuality(uint16_t iso_handle) {}
-void IsoManager::SendIsoData(uint16_t iso_handle, const uint8_t* data,
- uint16_t data_len) {}
-void IsoManager::CreateBig(uint8_t big_id,
- struct iso_manager::big_create_params big_params) {}
-void IsoManager::TerminateBig(uint8_t big_id, uint8_t reason) {}
-void IsoManager::HandleIsoData(void* p_msg) {}
-void IsoManager::HandleDisconnect(uint16_t handle, uint8_t reason) {}
-void IsoManager::HandleNumComplDataPkts(uint8_t* p, uint8_t evt_len) {}
-void IsoManager::HandleHciEvent(uint8_t sub_code, uint8_t* params,
- uint16_t length) {}
-void IsoManager::Start() {}
-void IsoManager::Stop() {}
-
-} // namespace hci
-} // namespace bluetooth
diff --git a/test/mock/mock_stack_btm_main.cc b/test/mock/mock_stack_btm_main.cc
deleted file mode 100644
index 1744bc32d..000000000
--- a/test/mock/mock_stack_btm_main.cc
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:7
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <memory>
-#include <string>
-#include "bt_target.h"
-#include "bt_types.h"
-#include "main/shim/dumpsys.h"
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/btm_client_interface.h"
-#include "stack_config.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void BTM_LogHistory(const std::string& tag, const RawAddress& bd_addr,
- const std::string& msg) {
- mock_function_count_map[__func__]++;
-}
-void BTM_LogHistory(const std::string& tag, const RawAddress& bd_addr,
- const std::string& msg, const std::string& extra) {
- mock_function_count_map[__func__]++;
-}
-void BTM_LogHistory(const std::string& tag, const tBLE_BD_ADDR& ble_bd_addr,
- const std::string& msg) {
- mock_function_count_map[__func__]++;
-}
-void BTM_LogHistory(const std::string& tag, const tBLE_BD_ADDR& ble_bd_addr,
- const std::string& msg, const std::string& extra) {
- mock_function_count_map[__func__]++;
-}
-void btm_free(void) { mock_function_count_map[__func__]++; }
-void btm_init(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_btm_scn.cc b/test/mock/mock_stack_btm_scn.cc
deleted file mode 100644
index fb76009f5..000000000
--- a/test/mock/mock_stack_btm_scn.cc
+++ /dev/null
@@ -1,46 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:3
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "stack/btm/btm_int_types.h"
-#include "stack/include/rfcdefs.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool BTM_FreeSCN(uint8_t scn) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_TryAllocateSCN(uint8_t scn) {
- mock_function_count_map[__func__]++;
- return false;
-}
-uint8_t BTM_AllocateSCN(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
diff --git a/test/mock/mock_stack_btm_sco.cc b/test/mock/mock_stack_btm_sco.cc
deleted file mode 100644
index 1542c5d9b..000000000
--- a/test/mock/mock_stack_btm_sco.cc
+++ /dev/null
@@ -1,125 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:23
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "stack/include/btm_api_types.h"
-#include "stack/include/btm_status.h"
-#include "stack/include/hci_error_code.h"
-#include "types/class_of_device.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool BTM_IsScoActiveByBdaddr(const RawAddress& remote_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_is_sco_active(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_sco_removed(uint16_t hci_handle, tHCI_REASON reason) {
- mock_function_count_map[__func__]++;
- return false;
-}
-const RawAddress* BTM_ReadScoBdAddr(uint16_t sco_inx) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_STATUS BTM_ChangeEScoLinkParms(uint16_t sco_inx,
- tBTM_CHG_ESCO_PARAMS* p_parms) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_CreateSco(const RawAddress* remote_bda, bool is_orig,
- uint16_t pkt_types, uint16_t* p_sco_inx,
- tBTM_SCO_CB* p_conn_cb, tBTM_SCO_CB* p_disc_cb) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_RegForEScoEvts(uint16_t sco_inx,
- tBTM_ESCO_CBACK* p_esco_cback) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_RemoveSco(uint16_t sco_inx) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SetEScoMode(enh_esco_params_t* p_parms) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-uint8_t BTM_GetNumScoLinks(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void BTM_EScoConnRsp(uint16_t sco_inx, uint8_t hci_status,
- enh_esco_params_t* p_parms) {
- mock_function_count_map[__func__]++;
-}
-void BTM_RemoveSco(const RawAddress& bda) {
- mock_function_count_map[__func__]++;
-}
-void btm_esco_proc_conn_chg(uint8_t status, uint16_t handle,
- uint8_t tx_interval, uint8_t retrans_window,
- uint16_t rx_pkt_len, uint16_t tx_pkt_len) {
- mock_function_count_map[__func__]++;
-}
-void btm_route_sco_data(BT_HDR* p_msg) { mock_function_count_map[__func__]++; }
-void btm_sco_acl_removed(const RawAddress* bda) {
- mock_function_count_map[__func__]++;
-}
-void btm_sco_chk_pend_rolechange(uint16_t hci_handle) {
- mock_function_count_map[__func__]++;
-}
-void btm_sco_chk_pend_unpark(tHCI_STATUS hci_status, uint16_t hci_handle) {
- mock_function_count_map[__func__]++;
-}
-void btm_sco_conn_req(const RawAddress& bda, const DEV_CLASS& dev_class,
- uint8_t link_type) {
- mock_function_count_map[__func__]++;
-}
-void btm_sco_connected(tHCI_STATUS hci_status, const RawAddress& bda,
- uint16_t hci_handle, tBTM_ESCO_DATA* p_esco_data) {
- mock_function_count_map[__func__]++;
-}
-void btm_sco_disc_chk_pend_for_modechange(uint16_t hci_handle) {
- mock_function_count_map[__func__]++;
-}
-void btm_sco_on_esco_connect_request(
- const RawAddress& bda, const bluetooth::types::ClassOfDevice& cod) {
- mock_function_count_map[__func__]++;
-}
-void btm_sco_on_sco_connect_request(
- const RawAddress& bda, const bluetooth::types::ClassOfDevice& cod) {
- mock_function_count_map[__func__]++;
-}
-void btm_sco_on_disconnected(uint16_t hci_handle, tHCI_REASON reason) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_btm_sec.cc b/test/mock/mock_stack_btm_sec.cc
deleted file mode 100644
index 27d76f8c9..000000000
--- a/test/mock/mock_stack_btm_sec.cc
+++ /dev/null
@@ -1,303 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:66
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/strings/stringprintf.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
-#include <string.h>
-#include "bt_types.h"
-#include "btif/include/btif_storage.h"
-#include "common/metrics.h"
-#include "common/time_util.h"
-#include "device/include/controller.h"
-#include "hcimsgs.h"
-#include "l2c_api.h"
-#include "main/shim/btm_api.h"
-#include "main/shim/dumpsys.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/acl_api.h"
-#include "stack/include/acl_hci_link_interface.h"
-#include "stack/include/btm_status.h"
-#include "stack/include/l2cap_security_interface.h"
-#include "stack/smp/smp_int.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool BTM_BothEndsSupportSecureConnections(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_GetSecurityFlags(const RawAddress& bd_addr, uint8_t* p_sec_flags) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_GetSecurityFlagsByTransport(const RawAddress& bd_addr,
- uint8_t* p_sec_flags,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_IsAuthenticated(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_IsEncrypted(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_IsLinkKeyAuthed(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_IsLinkKeyKnown(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_PeerSupportsSecureConnections(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tBT_DEVICE_TYPE BTM_GetPeerDeviceTypeFromFeatures(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return BT_DEVICE_TYPE_BREDR;
-}
-bool BTM_SecAddRmtNameNotifyCallback(tBTM_RMT_NAME_CALLBACK* p_callback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_SecDeleteRmtNameNotifyCallback(tBTM_RMT_NAME_CALLBACK* p_callback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_SecIsSecurityPending(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_SecRegister(const tBTM_APPL_INFO* p_cb_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool BTM_SetSecurityLevel(bool is_originator, const char* p_name,
- uint8_t service_id, uint16_t sec_level, uint16_t psm,
- uint32_t mx_proto_id, uint32_t mx_chan_id) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool btm_sec_is_a_bonded_dev(const RawAddress& bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool is_sec_state_equal(void* data, void* context) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool is_state_getting_name(void* data, void* context) {
- mock_function_count_map[__func__]++;
- return false;
-}
-const uint8_t* btm_get_dev_class(const RawAddress& bda) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_LINK_KEY_TYPE BTM_SecGetDeviceLinkKeyType(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tBTM_SEC_DEV_REC* btm_sec_find_dev_by_sec_state(uint8_t state) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_SEC_SERV_REC* btm_sec_find_first_serv(bool is_originator, uint16_t psm) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tBTM_STATUS BTM_SecBond(const RawAddress& bd_addr, tBLE_ADDR_TYPE addr_type,
- tBT_TRANSPORT transport, int device_type,
- uint8_t pin_len, uint8_t* p_pin) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SecBondCancel(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS BTM_SetEncryption(const RawAddress& bd_addr,
- tBT_TRANSPORT transport,
- tBTM_SEC_CALLBACK* p_callback, void* p_ref_data,
- tBTM_BLE_SEC_ACT sec_act) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_sec_bond_by_transport(const RawAddress& bd_addr,
- tBT_TRANSPORT transport, uint8_t pin_len,
- uint8_t* p_pin) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_sec_disconnect(uint16_t handle, tHCI_STATUS reason) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_sec_execute_procedure(tBTM_SEC_DEV_REC* p_dev_rec) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_sec_l2cap_access_req(const RawAddress& bd_addr, uint16_t psm,
- bool is_originator,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_sec_l2cap_access_req_by_requirement(
- const RawAddress& bd_addr, uint16_t security_required, bool is_originator,
- tBTM_SEC_CALLBACK* p_callback, void* p_ref_data) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tBTM_STATUS btm_sec_mx_access_request(const RawAddress& bd_addr,
- bool is_originator,
- uint16_t security_required,
- tBTM_SEC_CALLBACK* p_callback,
- void* p_ref_data) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-uint16_t BTM_GetClockOffset(const RawAddress& remote_bda) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t BTM_SecClrService(uint8_t service_id) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t BTM_SecClrServiceByPsm(uint16_t psm) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void BTM_ConfirmReqReply(tBTM_STATUS res, const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void BTM_PINCodeReply(const RawAddress& bd_addr, uint8_t res, uint8_t pin_len,
- uint8_t* p_pin) {
- mock_function_count_map[__func__]++;
-}
-void BTM_PasskeyReqReply(tBTM_STATUS res, const RawAddress& bd_addr,
- uint32_t passkey) {
- mock_function_count_map[__func__]++;
-}
-void BTM_ReadLocalOobData(void) { mock_function_count_map[__func__]++; }
-void BTM_RemoteOobDataReply(tBTM_STATUS res, const RawAddress& bd_addr,
- const Octet16& c, const Octet16& r) {
- mock_function_count_map[__func__]++;
-}
-void BTM_SetPinType(uint8_t pin_type, PIN_CODE pin_code, uint8_t pin_code_len) {
- mock_function_count_map[__func__]++;
-}
-void NotifyBondingCanceled(tBTM_STATUS btm_status) {
- mock_function_count_map[__func__]++;
-}
-void btm_create_conn_cancel_complete(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_io_capabilities_req(const RawAddress& p) {
- mock_function_count_map[__func__]++;
-}
-void btm_io_capabilities_rsp(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_proc_sp_req_evt(tBTM_SP_EVT event, uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_read_local_oob_complete(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_rem_oob_req(uint8_t* p) { mock_function_count_map[__func__]++; }
-void btm_sec_abort_access_req(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_auth_complete(uint16_t handle, tHCI_STATUS status) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_check_pending_reqs(void) { mock_function_count_map[__func__]++; }
-void btm_sec_clear_ble_keys(tBTM_SEC_DEV_REC* p_dev_rec) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_conn_req(const RawAddress& bda, uint8_t* dc) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_connected(const RawAddress& bda, uint16_t handle,
- tHCI_STATUS status, uint8_t enc_mode,
- tHCI_ROLE assigned_role) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_dev_rec_cback_event(tBTM_SEC_DEV_REC* p_dev_rec,
- tBTM_STATUS btm_status, bool is_le_transport) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_dev_reset(void) { mock_function_count_map[__func__]++; }
-void btm_sec_disconnected(uint16_t handle, tHCI_REASON reason) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_encrypt_change(uint16_t handle, tHCI_STATUS status,
- uint8_t encr_enable) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_link_key_notification(const RawAddress& p_bda,
- const Octet16& link_key, uint8_t key_type) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_link_key_request(uint8_t* p_event) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_pin_code_request(uint8_t* p_event) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_rmt_host_support_feat_evt(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_rmt_name_request_complete(const RawAddress* p_bd_addr,
- uint8_t* p_bd_name, tHCI_STATUS status) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_set_peer_sec_caps(uint16_t hci_handle, bool ssp_supported,
- bool sc_supported,
- bool hci_role_switch_supported,
- bool br_edr_supported, bool le_supported) {
- mock_function_count_map[__func__]++;
-}
-void btm_sec_update_clock_offset(uint16_t handle, uint16_t clock_offset) {
- mock_function_count_map[__func__]++;
-}
-void btm_simple_pair_complete(uint8_t* p) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_btu_hcif.cc b/test/mock/mock_stack_btu_hcif.cc
deleted file mode 100644
index 8eeb1c435..000000000
--- a/test/mock/mock_stack_btu_hcif.cc
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:9
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#define LOG_TAG "bt_btu_hcif"
-#include <base/bind.h>
-#include <base/location.h>
-#include <cstdint>
-#include "btif/include/btif_config.h"
-#include "common/metrics.h"
-#include "device/include/controller.h"
-#include "osi/include/log.h"
-#include "stack/include/acl_hci_link_interface.h"
-#include "stack/include/ble_acl_interface.h"
-#include "stack/include/ble_hci_link_interface.h"
-#include "stack/include/btm_iso_api.h"
-#include "stack/include/btu.h"
-#include "stack/include/dev_hci_link_interface.h"
-#include "stack/include/gatt_api.h"
-#include "stack/include/hci_evt_length.h"
-#include "stack/include/hcidefs.h"
-#include "stack/include/inq_hci_link_interface.h"
-#include "stack/include/l2cap_hci_link_interface.h"
-#include "stack/include/sco_hci_link_interface.h"
-#include "stack/include/sec_hci_link_interface.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-using hci_cmd_cb = base::OnceCallback<void(
- uint8_t* /* return_parameters */, uint16_t /* return_parameters_length*/)>;
-
-struct cmd_with_cb_data {
- hci_cmd_cb cb;
- base::Location posted_from;
-};
-
-void btu_hcif_log_event_metrics(uint8_t evt_code, uint8_t* p_event) {
- mock_function_count_map[__func__]++;
-}
-void btu_hcif_process_event(UNUSED_ATTR uint8_t controller_id, BT_HDR* p_msg) {
- mock_function_count_map[__func__]++;
-}
-void btu_hcif_send_cmd(UNUSED_ATTR uint8_t controller_id, BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
-}
-void btu_hcif_send_cmd_with_cb(const base::Location& posted_from,
- uint16_t opcode, uint8_t* params,
- uint8_t params_len, hci_cmd_cb cb) {
- mock_function_count_map[__func__]++;
-}
-void cmd_with_cb_data_cleanup(cmd_with_cb_data* cb_wrapper) {
- mock_function_count_map[__func__]++;
-}
-void cmd_with_cb_data_init(cmd_with_cb_data* cb_wrapper) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_btu_task.cc b/test/mock/mock_stack_btu_task.cc
deleted file mode 100644
index f4ba8399b..000000000
--- a/test/mock/mock_stack_btu_task.cc
+++ /dev/null
@@ -1,70 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:7
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/logging.h>
-#include <base/run_loop.h>
-#include <base/threading/thread.h>
-#include <pthread.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include "bta/sys/bta_sys.h"
-#include "btcore/include/module.h"
-#include "bte.h"
-#include "btif/include/btif_common.h"
-#include "btm_iso_api.h"
-#include "common/message_loop_thread.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "stack/include/acl_hci_link_interface.h"
-#include "stack/include/btu.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bluetooth::common::MessageLoopThread* get_main_thread() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-bt_status_t do_in_main_thread(const base::Location& from_here,
- base::OnceClosure task) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-bt_status_t do_in_main_thread_delayed(const base::Location& from_here,
- base::OnceClosure task,
- const base::TimeDelta& delay) {
- mock_function_count_map[__func__]++;
- return BT_STATUS_SUCCESS;
-}
-void btu_hci_msg_process(BT_HDR* p_msg) { mock_function_count_map[__func__]++; }
-void main_thread_shut_down() { mock_function_count_map[__func__]++; }
-void main_thread_start_up() { mock_function_count_map[__func__]++; }
-void post_on_bt_main(BtMainClosure closure) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_crypto_toolbox.cc b/test/mock/mock_stack_crypto_toolbox.cc
deleted file mode 100644
index 40b4e6935..000000000
--- a/test/mock/mock_stack_crypto_toolbox.cc
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:8
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_stack_crypto_toolbox.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace stack_crypto_toolbox {
-
-// Function state capture and return values, if needed
-struct h6 h6;
-struct h7 h7;
-struct f4 f4;
-struct f5 f5;
-struct f6 f6;
-struct g2 g2;
-struct ltk_to_link_key ltk_to_link_key;
-struct link_key_to_ltk link_key_to_ltk;
-
-} // namespace stack_crypto_toolbox
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-Octet16 h6(const Octet16& w, std::array<uint8_t, 4> keyid) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_crypto_toolbox::h6(w, keyid);
-}
-Octet16 h7(const Octet16& salt, const Octet16& w) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_crypto_toolbox::h7(salt, w);
-}
-Octet16 f4(const uint8_t* u, const uint8_t* v, const Octet16& x, uint8_t z) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_crypto_toolbox::f4(u, v, x, z);
-}
-void f5(const uint8_t* w, const Octet16& n1, const Octet16& n2, uint8_t* a1,
- uint8_t* a2, Octet16* mac_key, Octet16* ltk) {
- mock_function_count_map[__func__]++;
- test::mock::stack_crypto_toolbox::f5(w, n1, n2, a1, a2, mac_key, ltk);
-}
-Octet16 f6(const Octet16& w, const Octet16& n1, const Octet16& n2,
- const Octet16& r, uint8_t* iocap, uint8_t* a1, uint8_t* a2) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_crypto_toolbox::f6(w, n1, n2, r, iocap, a1, a2);
-}
-uint32_t g2(const uint8_t* u, const uint8_t* v, const Octet16& x,
- const Octet16& y) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_crypto_toolbox::g2(u, v, x, y);
-}
-Octet16 ltk_to_link_key(const Octet16& ltk, bool use_h7) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_crypto_toolbox::ltk_to_link_key(ltk, use_h7);
-}
-Octet16 link_key_to_ltk(const Octet16& link_key, bool use_h7) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_crypto_toolbox::link_key_to_ltk(link_key, use_h7);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_crypto_toolbox.h b/test/mock/mock_stack_crypto_toolbox.h
deleted file mode 100644
index bfbe800c0..000000000
--- a/test/mock/mock_stack_crypto_toolbox.h
+++ /dev/null
@@ -1,169 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:8
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include <base/logging.h>
-#include <base/strings/string_number_conversions.h>
-#include <algorithm>
-#include "stack/crypto_toolbox/aes.h"
-#include "stack/crypto_toolbox/crypto_toolbox.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace stack_crypto_toolbox {
-
-// Shared state between mocked functions and tests
-// Name: h6
-// Params: const Octet16& w, std::array<uint8_t, 4> keyid
-// Returns: Octet16
-struct h6 {
- Octet16 octet16;
- std::function<Octet16(const Octet16& w, std::array<uint8_t, 4> keyid)> body{
- [this](const Octet16& w, std::array<uint8_t, 4> keyid) {
- return octet16;
- }};
- Octet16 operator()(const Octet16& w, std::array<uint8_t, 4> keyid) {
- return body(w, keyid);
- };
-};
-extern struct h6 h6;
-// Name: h7
-// Params: const Octet16& salt, const Octet16& w
-// Returns: Octet16
-struct h7 {
- Octet16 octet16;
- std::function<Octet16(const Octet16& salt, const Octet16& w)> body{
- [this](const Octet16& salt, const Octet16& w) { return octet16; }};
- Octet16 operator()(const Octet16& salt, const Octet16& w) {
- return body(salt, w);
- };
-};
-extern struct h7 h7;
-// Name: f4
-// Params: const uint8_t* u, const uint8_t* v, const Octet16& x, uint8_t z
-// Returns: Octet16
-struct f4 {
- Octet16 octet16;
- std::function<Octet16(const uint8_t* u, const uint8_t* v, const Octet16& x,
- uint8_t z)>
- body{[this](const uint8_t* u, const uint8_t* v, const Octet16& x,
- uint8_t z) { return octet16; }};
- Octet16 operator()(const uint8_t* u, const uint8_t* v, const Octet16& x,
- uint8_t z) {
- return body(u, v, x, z);
- };
-};
-extern struct f4 f4;
-// Name: f5
-// Params: const uint8_t* w, const Octet16& n1, const Octet16& n2, uint8_t* a1,
-// uint8_t* a2, Octet16* mac_key, Octet16* ltk Returns: void
-struct f5 {
- std::function<void(const uint8_t* w, const Octet16& n1, const Octet16& n2,
- uint8_t* a1, uint8_t* a2, Octet16* mac_key, Octet16* ltk)>
- body{[](const uint8_t* w, const Octet16& n1, const Octet16& n2,
- uint8_t* a1, uint8_t* a2, Octet16* mac_key, Octet16* ltk) {}};
- void operator()(const uint8_t* w, const Octet16& n1, const Octet16& n2,
- uint8_t* a1, uint8_t* a2, Octet16* mac_key, Octet16* ltk) {
- body(w, n1, n2, a1, a2, mac_key, ltk);
- };
-};
-extern struct f5 f5;
-// Name: f6
-// Params: const Octet16& w, const Octet16& n1, const Octet16& n2, const
-// Octet16& r, uint8_t* iocap, uint8_t* a1, uint8_t* a2 Returns: Octet16
-struct f6 {
- Octet16 octet16;
- std::function<Octet16(const Octet16& w, const Octet16& n1, const Octet16& n2,
- const Octet16& r, uint8_t* iocap, uint8_t* a1,
- uint8_t* a2)>
- body{[this](const Octet16& w, const Octet16& n1, const Octet16& n2,
- const Octet16& r, uint8_t* iocap, uint8_t* a1,
- uint8_t* a2) { return octet16; }};
- Octet16 operator()(const Octet16& w, const Octet16& n1, const Octet16& n2,
- const Octet16& r, uint8_t* iocap, uint8_t* a1,
- uint8_t* a2) {
- return body(w, n1, n2, r, iocap, a1, a2);
- };
-};
-extern struct f6 f6;
-// Name: g2
-// Params: const uint8_t* u, const uint8_t* v, const Octet16& x, const Octet16&
-// y Returns: uint32_t
-struct g2 {
- std::function<uint32_t(const uint8_t* u, const uint8_t* v, const Octet16& x,
- const Octet16& y)>
- body{[](const uint8_t* u, const uint8_t* v, const Octet16& x,
- const Octet16& y) { return 0; }};
- uint32_t operator()(const uint8_t* u, const uint8_t* v, const Octet16& x,
- const Octet16& y) {
- return body(u, v, x, y);
- };
-};
-extern struct g2 g2;
-// Name: ltk_to_link_key
-// Params: const Octet16& ltk, bool use_h7
-// Returns: Octet16
-struct ltk_to_link_key {
- Octet16 octet16;
- std::function<Octet16(const Octet16& ltk, bool use_h7)> body{
- [this](const Octet16& ltk, bool use_h7) { return octet16; }};
- Octet16 operator()(const Octet16& ltk, bool use_h7) {
- return body(ltk, use_h7);
- };
-};
-extern struct ltk_to_link_key ltk_to_link_key;
-// Name: link_key_to_ltk
-// Params: const Octet16& link_key, bool use_h7
-// Returns: Octet16
-struct link_key_to_ltk {
- Octet16 octet16;
- std::function<Octet16(const Octet16& link_key, bool use_h7)> body{
- [this](const Octet16& link_key, bool use_h7) { return octet16; }};
- Octet16 operator()(const Octet16& link_key, bool use_h7) {
- return body(link_key, use_h7);
- };
-};
-extern struct link_key_to_ltk link_key_to_ltk;
-
-} // namespace stack_crypto_toolbox
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_crypto_toolbox_aes_cmac.cc b/test/mock/mock_stack_crypto_toolbox_aes_cmac.cc
deleted file mode 100644
index 13883331b..000000000
--- a/test/mock/mock_stack_crypto_toolbox_aes_cmac.cc
+++ /dev/null
@@ -1,40 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:1
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "stack/crypto_toolbox/aes.h"
-#include "stack/crypto_toolbox/crypto_toolbox.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace crypto_toolbox {
-Octet16 aes_cmac(const Octet16& key, const uint8_t* input, uint16_t length) {
- mock_function_count_map[__func__]++;
- Octet16 octet16;
- return octet16;
-}
-} // namespace crypto_toolbox
diff --git a/test/mock/mock_stack_gap_ble.cc b/test/mock/mock_stack_gap_ble.cc
deleted file mode 100644
index 999c293f4..000000000
--- a/test/mock/mock_stack_gap_ble.cc
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:6
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "stack/include/gap_api.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool GAP_BleCancelReadPeerDevName(const RawAddress& peer_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool GAP_BleReadPeerDevName(const RawAddress& peer_bda,
- tGAP_BLE_CMPL_CBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool GAP_BleReadPeerPrefConnParams(const RawAddress& peer_bda) {
- mock_function_count_map[__func__]++;
- return false;
-}
-void GAP_BleAttrDBUpdate(uint16_t attr_uuid, tGAP_BLE_ATTR_VALUE* p_value) {
- mock_function_count_map[__func__]++;
-}
-void gap_attr_db_init(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_gap_conn.cc b/test/mock/mock_stack_gap_conn.cc
deleted file mode 100644
index 6600a0dee..000000000
--- a/test/mock/mock_stack_gap_conn.cc
+++ /dev/null
@@ -1,82 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:13
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/strings/stringprintf.h>
-#include <string.h>
-#include "bt_target.h"
-#include "device/include/controller.h"
-#include "gap_api.h"
-#include "l2c_api.h"
-#include "l2cdefs.h"
-#include "osi/include/fixed_queue.h"
-#include "osi/include/mutex.h"
-#include "stack/btm/btm_sec.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-const RawAddress* GAP_ConnGetRemoteAddr(uint16_t gap_handle) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-int GAP_GetRxQueueCnt(uint16_t handle, uint32_t* p_rx_queue_count) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t GAP_ConnClose(uint16_t gap_handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t GAP_ConnGetL2CAPCid(uint16_t gap_handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t GAP_ConnGetRemMtuSize(uint16_t gap_handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t GAP_ConnOpen(const char* p_serv_name, uint8_t service_id,
- bool is_server, const RawAddress* p_rem_bda, uint16_t psm,
- uint16_t le_mps, tL2CAP_CFG_INFO* p_cfg,
- tL2CAP_ERTM_INFO* ertm_info, uint16_t security,
- tGAP_CONN_CALLBACK* p_cb, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t GAP_ConnReadData(uint16_t gap_handle, uint8_t* p_data,
- uint16_t max_len, uint16_t* p_len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint16_t GAP_ConnWriteData(uint16_t gap_handle, BT_HDR* msg) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void GAP_Init(void) { mock_function_count_map[__func__]++; }
-void gap_tx_complete_ind(uint16_t l2cap_cid, uint16_t sdu_sent) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_gatt.cc b/test/mock/mock_stack_gatt.cc
deleted file mode 100644
index 60f4f3d06..000000000
--- a/test/mock/mock_stack_gatt.cc
+++ /dev/null
@@ -1,159 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:27
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-#include "stack/gatt/gatt_int.h"
-#include "stack/include/gatt_api.h"
-#include "types/bluetooth/uuid.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
-
-using namespace bluetooth;
-
-extern std::map<std::string, int> mock_function_count_map;
-tGATT_HDL_LIST_ELEM elem; // gatt_add_an_item_to_list
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool GATTS_DeleteService(tGATT_IF gatt_if, Uuid* p_svc_uuid,
- uint16_t svc_inst) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool GATTS_NVRegister(tGATT_APPL_INFO* p_cb_info) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool GATT_CancelConnect(tGATT_IF gatt_if, const RawAddress& bd_addr,
- bool is_direct) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool GATT_Connect(tGATT_IF gatt_if, const RawAddress& bd_addr, bool is_direct,
- tBT_TRANSPORT transport, bool opportunistic) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool GATT_Connect(tGATT_IF gatt_if, const RawAddress& bd_addr, bool is_direct,
- tBT_TRANSPORT transport, bool opportunistic,
- uint8_t initiating_phys) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool GATT_GetConnIdIfConnected(tGATT_IF gatt_if, const RawAddress& bd_addr,
- uint16_t* p_conn_id, tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool GATT_GetConnectionInfor(uint16_t conn_id, tGATT_IF* p_gatt_if,
- RawAddress& bd_addr, tBT_TRANSPORT* p_transport) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool is_active_service(const Uuid& app_uuid128, Uuid* p_svc_uuid,
- uint16_t start_handle) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tGATT_HDL_LIST_ELEM& gatt_add_an_item_to_list(uint16_t s_handle) {
- mock_function_count_map[__func__]++;
- return elem;
-}
-tGATT_IF GATT_Register(const Uuid& app_uuid128, std::string name,
- tGATT_CBACK* p_cb_info, bool eatt_support) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tGATT_STATUS GATTC_ConfigureMTU(uint16_t conn_id, uint16_t mtu) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS GATTC_Discover(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
- uint16_t start_handle, uint16_t end_handle) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS GATTC_Discover(uint16_t conn_id, tGATT_DISC_TYPE disc_type,
- uint16_t start_handle, uint16_t end_handle,
- const Uuid& uuid) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS GATTC_ExecuteWrite(uint16_t conn_id, bool is_execute) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS GATTC_Read(uint16_t conn_id, tGATT_READ_TYPE type,
- tGATT_READ_PARAM* p_read) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS GATTC_SendHandleValueConfirm(uint16_t conn_id, uint16_t cid) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS GATTC_Write(uint16_t conn_id, tGATT_WRITE_TYPE type,
- tGATT_VALUE* p_write) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS GATTS_AddService(tGATT_IF gatt_if, btgatt_db_element_t* service,
- int count) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS GATTS_HandleValueIndication(uint16_t conn_id, uint16_t attr_handle,
- uint16_t val_len, uint8_t* p_val) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS GATTS_HandleValueNotification(uint16_t conn_id,
- uint16_t attr_handle,
- uint16_t val_len, uint8_t* p_val) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS GATTS_SendRsp(uint16_t conn_id, uint32_t trans_id,
- tGATT_STATUS status, tGATTS_RSP* p_msg) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS GATT_Disconnect(uint16_t conn_id) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-void GATTS_AddHandleRange(tGATTS_HNDL_RANGE* p_hndl_range) {
- mock_function_count_map[__func__]++;
-}
-void GATTS_StopService(uint16_t service_handle) {
- mock_function_count_map[__func__]++;
-}
-void GATT_Deregister(tGATT_IF gatt_if) { mock_function_count_map[__func__]++; }
-void GATT_SetIdleTimeout(const RawAddress& bd_addr, uint16_t idle_tout,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void GATT_StartIf(tGATT_IF gatt_if) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_gatt_attr.cc b/test/mock/mock_stack_gatt_attr.cc
deleted file mode 100644
index 8198b1c7c..000000000
--- a/test/mock/mock_stack_gatt_attr.cc
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:14
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "stack/gatt/gatt_int.h"
-#include "types/bt_transport.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-uint16_t gatt_profile_find_conn_id_by_bd_addr(const RawAddress& remote_bda) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-bool gatt_profile_get_eatt_support(
- const RawAddress& remote_bda,
- base::OnceCallback<void(const RawAddress&, bool)> cb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool gatt_sr_is_cl_change_aware(tGATT_TCB& tcb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tGATT_PROFILE_CLCB* gatt_profile_clcb_alloc(uint16_t conn_id,
- const RawAddress& bda,
- tBT_TRANSPORT tranport) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tGATT_STATUS proc_read_req(uint16_t conn_id, tGATTS_REQ_TYPE,
- tGATT_READ_REQ* p_data, tGATTS_RSP* p_rsp) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS proc_write_req(uint16_t conn_id, tGATTS_REQ_TYPE,
- tGATT_WRITE_REQ* p_data) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-tGATT_STATUS read_attr_value(uint16_t conn_id, uint16_t handle,
- tGATT_VALUE* p_value, bool is_long) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-void GATT_ConfigServiceChangeCCC(const RawAddress& remote_bda, bool enable,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
-}
-void gatt_profile_clcb_dealloc(tGATT_PROFILE_CLCB* p_clcb) {
- mock_function_count_map[__func__]++;
-}
-void gatt_profile_db_init(void) { mock_function_count_map[__func__]++; }
-void gatt_sr_init_cl_status(tGATT_TCB& tcb) {
- mock_function_count_map[__func__]++;
-}
-void gatt_sr_update_cl_status(tGATT_TCB& tcb, bool chg_aware) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_gatt_auth.cc b/test/mock/mock_stack_gatt_auth.cc
deleted file mode 100644
index db0820ee0..000000000
--- a/test/mock/mock_stack_gatt_auth.cc
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:10
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "stack/gatt/gatt_int.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool gatt_security_check_start(tGATT_CLCB* p_clcb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tGATT_SEC_ACTION gatt_determine_sec_act(tGATT_CLCB* p_clcb) {
- mock_function_count_map[__func__]++;
- return GATT_SEC_NONE;
-}
-tGATT_SEC_ACTION gatt_get_sec_act(tGATT_TCB* p_tcb) {
- mock_function_count_map[__func__]++;
- return GATT_SEC_NONE;
-}
-tGATT_STATUS gatt_get_link_encrypt_status(tGATT_TCB& tcb) {
- mock_function_count_map[__func__]++;
- return GATT_SUCCESS;
-}
-void gatt_enc_cmpl_cback(const RawAddress* bd_addr, tBT_TRANSPORT transport,
- UNUSED_ATTR void* p_ref_data, tBTM_STATUS result) {
- mock_function_count_map[__func__]++;
-}
-void gatt_notify_enc_cmpl(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void gatt_sec_check_complete(bool sec_check_ok, tGATT_CLCB* p_clcb,
- uint8_t sec_act) {
- mock_function_count_map[__func__]++;
-}
-void gatt_set_sec_act(tGATT_TCB* p_tcb, tGATT_SEC_ACTION sec_act) {
- mock_function_count_map[__func__]++;
-}
-void gatt_verify_signature(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_gatt_connection_manager.cc b/test/mock/mock_stack_gatt_connection_manager.cc
deleted file mode 100644
index d1341c7d0..000000000
--- a/test/mock/mock_stack_gatt_connection_manager.cc
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:16
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/bind.h>
-#include <base/callback.h>
-#include <base/location.h>
-#include <base/logging.h>
-#include <map>
-#include <memory>
-#include <set>
-#include "internal_include/bt_trace.h"
-#include "main/shim/shim.h"
-#include "osi/include/alarm.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_ble_bgconn.h"
-#include "stack/gatt/connection_manager.h"
-#include "stack/include/l2c_api.h"
-
-using namespace connection_manager;
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool connection_manager::background_connect_add(uint8_t app_id,
- const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool connection_manager::background_connect_remove(uint8_t app_id,
- const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool connection_manager::direct_connect_add(uint8_t app_id,
- const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool connection_manager::direct_connect_remove(uint8_t app_id,
- const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool connection_manager::remove_unconditional(const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return false;
-}
-std::set<tAPP_ID> connection_manager::get_apps_connecting_to(
- const RawAddress& address) {
- mock_function_count_map[__func__]++;
- return std::set<tAPP_ID>();
-}
-void connection_manager::dump(int fd) { mock_function_count_map[__func__]++; }
-void connection_manager::on_app_deregistered(uint8_t app_id) {
- mock_function_count_map[__func__]++;
-}
-void connection_manager::on_connection_complete(const RawAddress& address) {
- mock_function_count_map[__func__]++;
-}
-void connection_manager::reset(bool after_reset) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_gatt_main.cc b/test/mock/mock_stack_gatt_main.cc
deleted file mode 100644
index cdc037b44..000000000
--- a/test/mock/mock_stack_gatt_main.cc
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:23
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "bt_common.h"
-#include "bt_target.h"
-#include "device/include/interop.h"
-#include "l2c_api.h"
-#include "osi/include/osi.h"
-#include "stack/btm/btm_ble_int.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/gatt/gatt_int.h"
-#include "stack/include/l2cap_acl_interface.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-void gatt_init(void) { mock_function_count_map[__func__]++; }
-bool gatt_act_connect(tGATT_REG* p_reg, const RawAddress& bd_addr,
- tBT_TRANSPORT transport, int8_t initiating_phys) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool gatt_connect(const RawAddress& rem_bda, tGATT_TCB* p_tcb,
- tBT_TRANSPORT transport, uint8_t initiating_phys,
- tGATT_IF gatt_if) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool gatt_disconnect(tGATT_TCB* p_tcb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool gatt_update_app_hold_link_status(tGATT_IF gatt_if, tGATT_TCB* p_tcb,
- bool is_add) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tGATT_CH_STATE gatt_get_ch_state(tGATT_TCB* p_tcb) {
- mock_function_count_map[__func__]++;
- return GATT_CH_CLOSE;
-}
-void gatt_add_a_bonded_dev_for_srv_chg(const RawAddress& bda) {
- mock_function_count_map[__func__]++;
-}
-void gatt_chk_srv_chg(tGATTS_SRV_CHG* p_srv_chg_clt) {
- mock_function_count_map[__func__]++;
-}
-void gatt_data_process(tGATT_TCB& tcb, uint16_t cid, BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
-}
-void gatt_find_in_device_record(const RawAddress& bd_addr,
- tBLE_BD_ADDR* address_with_type) {
- mock_function_count_map[__func__]++;
-}
-void gatt_free(void) { mock_function_count_map[__func__]++; }
-void gatt_init_srv_chg(void) { mock_function_count_map[__func__]++; }
-void gatt_l2cif_config_cfm_cback(uint16_t lcid, uint16_t initiator,
- tL2CAP_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
-}
-void gatt_l2cif_config_ind_cback(uint16_t lcid, tL2CAP_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
-}
-void gatt_l2cif_disconnect_ind_cback(uint16_t lcid, bool ack_needed) {
- mock_function_count_map[__func__]++;
-}
-void gatt_notify_conn_update(const RawAddress& remote, uint16_t interval,
- uint16_t latency, uint16_t timeout,
- tHCI_STATUS status) {
- mock_function_count_map[__func__]++;
-}
-void gatt_notify_phy_updated(tGATT_STATUS status, uint16_t handle,
- uint8_t tx_phy, uint8_t rx_phy) {
- mock_function_count_map[__func__]++;
-}
-void gatt_proc_srv_chg(void) { mock_function_count_map[__func__]++; }
-void gatt_send_srv_chg_ind(const RawAddress& peer_bda) {
- mock_function_count_map[__func__]++;
-}
-void gatt_set_ch_state(tGATT_TCB* p_tcb, tGATT_CH_STATE ch_state) {
- mock_function_count_map[__func__]++;
-}
-void gatt_update_app_use_link_flag(tGATT_IF gatt_if, tGATT_TCB* p_tcb,
- bool is_add, bool check_acl_link) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_hidd_api.cc b/test/mock/mock_stack_hidd_api.cc
deleted file mode 100644
index 992e361cf..000000000
--- a/test/mock/mock_stack_hidd_api.cc
+++ /dev/null
@@ -1,111 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:16
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include "bt_types.h"
-#include "btm_api.h"
-#include "btu.h"
-#include "hidd_api.h"
-#include "hiddefs.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/hid/hidd_int.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tHID_STATUS HID_DevAddRecord(uint32_t handle, char* p_name, char* p_description,
- char* p_provider, uint16_t subclass,
- uint16_t desc_len, uint8_t* p_desc_data) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevConnect(void) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevDeregister(void) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevDisconnect(void) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevGetDevice(RawAddress* addr) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevPlugDevice(const RawAddress& addr) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevRegister(tHID_DEV_HOST_CALLBACK* host_cback) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevReportError(uint8_t error) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevSendReport(uint8_t channel, uint8_t type, uint8_t id,
- uint16_t len, uint8_t* p_data) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevSetIncomingPolicy(bool allow) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevSetIncomingQos(uint8_t service_type, uint32_t token_rate,
- uint32_t token_bucket_size,
- uint32_t peak_bandwidth, uint32_t latency,
- uint32_t delay_variation) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevSetOutgoingQos(uint8_t service_type, uint32_t token_rate,
- uint32_t token_bucket_size,
- uint32_t peak_bandwidth, uint32_t latency,
- uint32_t delay_variation) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevUnplugDevice(const RawAddress& addr) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_DevVirtualCableUnplug(void) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-uint8_t HID_DevSetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void HID_DevInit(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_hidh.cc b/test/mock/mock_stack_hidh.cc
deleted file mode 100644
index 79cbcc4a0..000000000
--- a/test/mock/mock_stack_hidh.cc
+++ /dev/null
@@ -1,81 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:11
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "stack/include/hiddefs.h"
-#include "stack/include/hidh_api.h"
-#include "stack/include/sdp_api.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tHID_STATUS HID_HostAddDev(const RawAddress& addr, uint16_t attr_mask,
- uint8_t* handle) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_HostCloseDev(uint8_t dev_handle) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_HostDeregister(void) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_HostGetSDPRecord(const RawAddress& addr,
- tSDP_DISCOVERY_DB* p_db, uint32_t db_len,
- tHID_HOST_SDP_CALLBACK* sdp_cback) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_HostOpenDev(uint8_t dev_handle) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_HostRegister(tHID_HOST_DEV_CALLBACK* dev_cback) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_HostRemoveDev(uint8_t dev_handle) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-tHID_STATUS HID_HostWriteDev(uint8_t dev_handle, uint8_t t_type, uint8_t param,
- uint16_t data, uint8_t report_id, BT_HDR* pbuf) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-uint8_t HID_HostSetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return HID_SUCCESS;
-}
-void HID_HostInit(void) { mock_function_count_map[__func__]++; }
-void hidh_get_str_attr(tSDP_DISC_REC* p_rec, uint16_t attr_id, uint16_t max_len,
- char* str) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_l2cap_api.cc b/test/mock/mock_stack_l2cap_api.cc
deleted file mode 100644
index 1c00c2bf3..000000000
--- a/test/mock/mock_stack_l2cap_api.cc
+++ /dev/null
@@ -1,271 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:33
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include <base/logging.h>
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <string>
-#include "device/include/controller.h"
-#include "main/shim/l2c_api.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/l2c_api.h"
-#include "stack/l2cap/l2c_int.h"
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_stack_l2cap_api.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace stack_l2cap_api {
-
-// Function state capture and return values, if needed
-struct l2c_get_transport_from_fixed_cid l2c_get_transport_from_fixed_cid;
-struct L2CA_Register2 L2CA_Register2;
-struct L2CA_Register L2CA_Register;
-struct L2CA_Deregister L2CA_Deregister;
-struct L2CA_AllocateLePSM L2CA_AllocateLePSM;
-struct L2CA_FreeLePSM L2CA_FreeLePSM;
-struct L2CA_ConnectReq2 L2CA_ConnectReq2;
-struct L2CA_ConnectReq L2CA_ConnectReq;
-struct L2CA_RegisterLECoc L2CA_RegisterLECoc;
-struct L2CA_DeregisterLECoc L2CA_DeregisterLECoc;
-struct L2CA_ConnectLECocReq L2CA_ConnectLECocReq;
-struct L2CA_GetPeerLECocConfig L2CA_GetPeerLECocConfig;
-struct L2CA_ConnectCreditBasedRsp L2CA_ConnectCreditBasedRsp;
-struct L2CA_ConnectCreditBasedReq L2CA_ConnectCreditBasedReq;
-struct L2CA_ReconfigCreditBasedConnsReq L2CA_ReconfigCreditBasedConnsReq;
-struct L2CA_DisconnectReq L2CA_DisconnectReq;
-struct L2CA_DisconnectLECocReq L2CA_DisconnectLECocReq;
-struct L2CA_GetRemoteCid L2CA_GetRemoteCid;
-struct L2CA_SetIdleTimeoutByBdAddr L2CA_SetIdleTimeoutByBdAddr;
-struct L2CA_SetTraceLevel L2CA_SetTraceLevel;
-struct L2CA_SetAclPriority L2CA_SetAclPriority;
-struct L2CA_SetTxPriority L2CA_SetTxPriority;
-struct L2CA_GetPeerFeatures L2CA_GetPeerFeatures;
-struct L2CA_RegisterFixedChannel L2CA_RegisterFixedChannel;
-struct L2CA_ConnectFixedChnl L2CA_ConnectFixedChnl;
-struct L2CA_SendFixedChnlData L2CA_SendFixedChnlData;
-struct L2CA_RemoveFixedChnl L2CA_RemoveFixedChnl;
-struct L2CA_SetLeGattTimeout L2CA_SetLeGattTimeout;
-struct L2CA_DataWrite L2CA_DataWrite;
-struct L2CA_LECocDataWrite L2CA_LECocDataWrite;
-struct L2CA_SetChnlFlushability L2CA_SetChnlFlushability;
-struct L2CA_FlushChannel L2CA_FlushChannel;
-struct L2CA_IsLinkEstablished L2CA_IsLinkEstablished;
-
-} // namespace stack_l2cap_api
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-tBT_TRANSPORT l2c_get_transport_from_fixed_cid(uint16_t fixed_cid) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::l2c_get_transport_from_fixed_cid(
- fixed_cid);
-}
-uint16_t L2CA_Register2(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_Register2(
- psm, p_cb_info, enable_snoop, p_ertm_info, my_mtu, required_remote_mtu,
- sec_level);
-}
-uint16_t L2CA_Register(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_Register(
- psm, p_cb_info, enable_snoop, p_ertm_info, my_mtu, required_remote_mtu,
- sec_level);
-}
-void L2CA_Deregister(uint16_t psm) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_api::L2CA_Deregister(psm);
-}
-uint16_t L2CA_AllocateLePSM(void) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_AllocateLePSM();
-}
-void L2CA_FreeLePSM(uint16_t psm) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_api::L2CA_FreeLePSM(psm);
-}
-uint16_t L2CA_ConnectReq2(uint16_t psm, const RawAddress& p_bd_addr,
- uint16_t sec_level) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_ConnectReq2(psm, p_bd_addr,
- sec_level);
-}
-uint16_t L2CA_ConnectReq(uint16_t psm, const RawAddress& p_bd_addr) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_ConnectReq(psm, p_bd_addr);
-}
-uint16_t L2CA_RegisterLECoc(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_RegisterLECoc(psm, p_cb_info,
- sec_level, cfg);
-}
-void L2CA_DeregisterLECoc(uint16_t psm) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_api::L2CA_DeregisterLECoc(psm);
-}
-uint16_t L2CA_ConnectLECocReq(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg, uint16_t sec_level) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_ConnectLECocReq(psm, p_bd_addr,
- p_cfg, sec_level);
-}
-bool L2CA_GetPeerLECocConfig(uint16_t lcid, tL2CAP_LE_CFG_INFO* peer_cfg) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_GetPeerLECocConfig(lcid, peer_cfg);
-}
-bool L2CA_ConnectCreditBasedRsp(const RawAddress& p_bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids,
- uint16_t result, tL2CAP_LE_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_ConnectCreditBasedRsp(
- p_bd_addr, id, accepted_lcids, result, p_cfg);
-}
-std::vector<uint16_t> L2CA_ConnectCreditBasedReq(uint16_t psm,
- const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_ConnectCreditBasedReq(psm, p_bd_addr,
- p_cfg);
-}
-bool L2CA_ReconfigCreditBasedConnsReq(const RawAddress& bda,
- std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_ReconfigCreditBasedConnsReq(
- bda, lcids, p_cfg);
-}
-bool L2CA_DisconnectReq(uint16_t cid) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_DisconnectReq(cid);
-}
-bool L2CA_DisconnectLECocReq(uint16_t cid) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_DisconnectLECocReq(cid);
-}
-bool L2CA_GetRemoteCid(uint16_t lcid, uint16_t* rcid) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_GetRemoteCid(lcid, rcid);
-}
-bool L2CA_SetIdleTimeoutByBdAddr(const RawAddress& bd_addr, uint16_t timeout,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_SetIdleTimeoutByBdAddr(
- bd_addr, timeout, transport);
-}
-uint8_t L2CA_SetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_SetTraceLevel(new_level);
-}
-bool L2CA_SetAclPriority(const RawAddress& bd_addr, tL2CAP_PRIORITY priority) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_SetAclPriority(bd_addr, priority);
-}
-bool L2CA_SetTxPriority(uint16_t cid, tL2CAP_CHNL_PRIORITY priority) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_SetTxPriority(cid, priority);
-}
-bool L2CA_GetPeerFeatures(const RawAddress& bd_addr, uint32_t* p_ext_feat,
- uint8_t* p_chnl_mask) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_GetPeerFeatures(bd_addr, p_ext_feat,
- p_chnl_mask);
-}
-bool L2CA_RegisterFixedChannel(uint16_t fixed_cid,
- tL2CAP_FIXED_CHNL_REG* p_freg) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_RegisterFixedChannel(fixed_cid,
- p_freg);
-}
-bool L2CA_ConnectFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_ConnectFixedChnl(fixed_cid, rem_bda);
-}
-uint16_t L2CA_SendFixedChnlData(uint16_t fixed_cid, const RawAddress& rem_bda,
- BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_SendFixedChnlData(fixed_cid, rem_bda,
- p_buf);
-}
-bool L2CA_RemoveFixedChnl(uint16_t fixed_cid, const RawAddress& rem_bda) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_RemoveFixedChnl(fixed_cid, rem_bda);
-}
-bool L2CA_SetLeGattTimeout(const RawAddress& rem_bda, uint16_t idle_tout) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_SetLeGattTimeout(rem_bda, idle_tout);
-}
-uint8_t L2CA_DataWrite(uint16_t cid, BT_HDR* p_data) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_DataWrite(cid, p_data);
-}
-uint8_t L2CA_LECocDataWrite(uint16_t cid, BT_HDR* p_data) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_LECocDataWrite(cid, p_data);
-}
-bool L2CA_SetChnlFlushability(uint16_t cid, bool is_flushable) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_SetChnlFlushability(cid,
- is_flushable);
-}
-uint16_t L2CA_FlushChannel(uint16_t lcid, uint16_t num_to_flush) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_FlushChannel(lcid, num_to_flush);
-}
-bool L2CA_IsLinkEstablished(const RawAddress& bd_addr,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_api::L2CA_IsLinkEstablished(bd_addr,
- transport);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_l2cap_api.h b/test/mock/mock_stack_l2cap_api.h
deleted file mode 100644
index 0c363f971..000000000
--- a/test/mock/mock_stack_l2cap_api.h
+++ /dev/null
@@ -1,458 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:33
- *
- * mockcify.pl ver 0.2
- */
-
-#include <functional>
-#include <map>
-#include <string>
-#include <vector>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include <base/logging.h>
-#include <base/strings/stringprintf.h>
-#include <cstdint>
-#include <string>
-#include "device/include/controller.h"
-#include "main/shim/l2c_api.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/include/l2c_api.h"
-#include "stack/l2cap/l2c_int.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace stack_l2cap_api {
-
-// Shared state between mocked functions and tests
-// Name: l2c_get_transport_from_fixed_cid
-// Params: uint16_t fixed_cid
-// Returns: tBT_TRANSPORT
-struct l2c_get_transport_from_fixed_cid {
- std::function<tBT_TRANSPORT(uint16_t fixed_cid)> body{
- [](uint16_t fixed_cid) { return 0; }};
- tBT_TRANSPORT operator()(uint16_t fixed_cid) { return body(fixed_cid); };
-};
-extern struct l2c_get_transport_from_fixed_cid l2c_get_transport_from_fixed_cid;
-// Name: L2CA_Register2
-// Params: uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info, bool enable_snoop,
-// tL2CAP_ERTM_INFO* p_ertm_info, uint16_t my_mtu, uint16_t required_remote_mtu,
-// uint16_t sec_level Returns: uint16_t
-struct L2CA_Register2 {
- std::function<uint16_t(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level)>
- body{[](uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info, uint16_t my_mtu,
- uint16_t required_remote_mtu, uint16_t sec_level) { return 0; }};
- uint16_t operator()(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level) {
- return body(psm, p_cb_info, enable_snoop, p_ertm_info, my_mtu,
- required_remote_mtu, sec_level);
- };
-};
-extern struct L2CA_Register2 L2CA_Register2;
-// Name: L2CA_Register
-// Params: uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info, bool enable_snoop,
-// tL2CAP_ERTM_INFO* p_ertm_info, uint16_t my_mtu, uint16_t required_remote_mtu,
-// uint16_t sec_level Returns: uint16_t
-struct L2CA_Register {
- std::function<uint16_t(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level)>
- body{[](uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info, uint16_t my_mtu,
- uint16_t required_remote_mtu, uint16_t sec_level) { return 0; }};
- uint16_t operator()(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- bool enable_snoop, tL2CAP_ERTM_INFO* p_ertm_info,
- uint16_t my_mtu, uint16_t required_remote_mtu,
- uint16_t sec_level) {
- return body(psm, p_cb_info, enable_snoop, p_ertm_info, my_mtu,
- required_remote_mtu, sec_level);
- };
-};
-extern struct L2CA_Register L2CA_Register;
-// Name: L2CA_Deregister
-// Params: uint16_t psm
-// Returns: void
-struct L2CA_Deregister {
- std::function<void(uint16_t psm)> body{[](uint16_t psm) {}};
- void operator()(uint16_t psm) { body(psm); };
-};
-extern struct L2CA_Deregister L2CA_Deregister;
-// Name: L2CA_AllocateLePSM
-// Params: void
-// Returns: uint16_t
-struct L2CA_AllocateLePSM {
- std::function<uint16_t(void)> body{[](void) { return 0; }};
- uint16_t operator()(void) { return body(); };
-};
-extern struct L2CA_AllocateLePSM L2CA_AllocateLePSM;
-// Name: L2CA_FreeLePSM
-// Params: uint16_t psm
-// Returns: void
-struct L2CA_FreeLePSM {
- std::function<void(uint16_t psm)> body{[](uint16_t psm) {}};
- void operator()(uint16_t psm) { body(psm); };
-};
-extern struct L2CA_FreeLePSM L2CA_FreeLePSM;
-// Name: L2CA_ConnectReq2
-// Params: uint16_t psm, const RawAddress& p_bd_addr, uint16_t sec_level
-// Returns: uint16_t
-struct L2CA_ConnectReq2 {
- std::function<uint16_t(uint16_t psm, const RawAddress& p_bd_addr,
- uint16_t sec_level)>
- body{[](uint16_t psm, const RawAddress& p_bd_addr, uint16_t sec_level) {
- return 0;
- }};
- uint16_t operator()(uint16_t psm, const RawAddress& p_bd_addr,
- uint16_t sec_level) {
- return body(psm, p_bd_addr, sec_level);
- };
-};
-extern struct L2CA_ConnectReq2 L2CA_ConnectReq2;
-// Name: L2CA_ConnectReq
-// Params: uint16_t psm, const RawAddress& p_bd_addr
-// Returns: uint16_t
-struct L2CA_ConnectReq {
- std::function<uint16_t(uint16_t psm, const RawAddress& p_bd_addr)> body{
- [](uint16_t psm, const RawAddress& p_bd_addr) { return 0; }};
- uint16_t operator()(uint16_t psm, const RawAddress& p_bd_addr) {
- return body(psm, p_bd_addr);
- };
-};
-extern struct L2CA_ConnectReq L2CA_ConnectReq;
-// Name: L2CA_RegisterLECoc
-// Params: uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info, uint16_t sec_level,
-// tL2CAP_LE_CFG_INFO cfg Returns: uint16_t
-struct L2CA_RegisterLECoc {
- std::function<uint16_t(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg)>
- body{[](uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg) { return 0; }};
- uint16_t operator()(uint16_t psm, const tL2CAP_APPL_INFO& p_cb_info,
- uint16_t sec_level, tL2CAP_LE_CFG_INFO cfg) {
- return body(psm, p_cb_info, sec_level, cfg);
- };
-};
-extern struct L2CA_RegisterLECoc L2CA_RegisterLECoc;
-// Name: L2CA_DeregisterLECoc
-// Params: uint16_t psm
-// Returns: void
-struct L2CA_DeregisterLECoc {
- std::function<void(uint16_t psm)> body{[](uint16_t psm) {}};
- void operator()(uint16_t psm) { body(psm); };
-};
-extern struct L2CA_DeregisterLECoc L2CA_DeregisterLECoc;
-// Name: L2CA_ConnectLECocReq
-// Params: uint16_t psm, const RawAddress& p_bd_addr, tL2CAP_LE_CFG_INFO* p_cfg,
-// uint16_t sec_level Returns: uint16_t
-struct L2CA_ConnectLECocReq {
- std::function<uint16_t(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg, uint16_t sec_level)>
- body{[](uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg, uint16_t sec_level) { return 0; }};
- uint16_t operator()(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg, uint16_t sec_level) {
- return body(psm, p_bd_addr, p_cfg, sec_level);
- };
-};
-extern struct L2CA_ConnectLECocReq L2CA_ConnectLECocReq;
-// Name: L2CA_GetPeerLECocConfig
-// Params: uint16_t lcid, tL2CAP_LE_CFG_INFO* peer_cfg
-// Returns: bool
-struct L2CA_GetPeerLECocConfig {
- std::function<bool(uint16_t lcid, tL2CAP_LE_CFG_INFO* peer_cfg)> body{
- [](uint16_t lcid, tL2CAP_LE_CFG_INFO* peer_cfg) { return false; }};
- bool operator()(uint16_t lcid, tL2CAP_LE_CFG_INFO* peer_cfg) {
- return body(lcid, peer_cfg);
- };
-};
-extern struct L2CA_GetPeerLECocConfig L2CA_GetPeerLECocConfig;
-// Name: L2CA_ConnectCreditBasedRsp
-// Params: const RawAddress& p_bd_addr, uint8_t id, std::vector<uint16_t>&
-// accepted_lcids, uint16_t result, tL2CAP_LE_CFG_INFO* p_cfg Returns: bool
-struct L2CA_ConnectCreditBasedRsp {
- std::function<bool(const RawAddress& p_bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids, uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg)>
- body{[](const RawAddress& p_bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids, uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg) { return false; }};
- bool operator()(const RawAddress& p_bd_addr, uint8_t id,
- std::vector<uint16_t>& accepted_lcids, uint16_t result,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- return body(p_bd_addr, id, accepted_lcids, result, p_cfg);
- };
-};
-extern struct L2CA_ConnectCreditBasedRsp L2CA_ConnectCreditBasedRsp;
-// Name: L2CA_ConnectCreditBasedReq
-// Params: uint16_t psm, const RawAddress& p_bd_addr, tL2CAP_LE_CFG_INFO* p_cfg
-// Returns: std::vector<uint16_t>
-struct L2CA_ConnectCreditBasedReq {
- std::vector<uint16_t> cids;
- std::function<std::vector<uint16_t>(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg)>
- body{[this](uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) { return cids; }};
- std::vector<uint16_t> operator()(uint16_t psm, const RawAddress& p_bd_addr,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- return body(psm, p_bd_addr, p_cfg);
- };
-};
-extern struct L2CA_ConnectCreditBasedReq L2CA_ConnectCreditBasedReq;
-// Name: L2CA_ReconfigCreditBasedConnsReq
-// Params: const RawAddress& bda, std::vector<uint16_t>& lcids,
-// tL2CAP_LE_CFG_INFO* p_cfg Returns: bool
-struct L2CA_ReconfigCreditBasedConnsReq {
- std::function<bool(const RawAddress& bda, std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg)>
- body{[](const RawAddress& bda, std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg) { return false; }};
- bool operator()(const RawAddress& bda, std::vector<uint16_t>& lcids,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- return body(bda, lcids, p_cfg);
- };
-};
-extern struct L2CA_ReconfigCreditBasedConnsReq L2CA_ReconfigCreditBasedConnsReq;
-// Name: L2CA_DisconnectReq
-// Params: uint16_t cid
-// Returns: bool
-struct L2CA_DisconnectReq {
- std::function<bool(uint16_t cid)> body{[](uint16_t cid) { return false; }};
- bool operator()(uint16_t cid) { return body(cid); };
-};
-extern struct L2CA_DisconnectReq L2CA_DisconnectReq;
-// Name: L2CA_DisconnectLECocReq
-// Params: uint16_t cid
-// Returns: bool
-struct L2CA_DisconnectLECocReq {
- std::function<bool(uint16_t cid)> body{[](uint16_t cid) { return false; }};
- bool operator()(uint16_t cid) { return body(cid); };
-};
-extern struct L2CA_DisconnectLECocReq L2CA_DisconnectLECocReq;
-// Name: L2CA_GetRemoteCid
-// Params: uint16_t lcid, uint16_t* rcid
-// Returns: bool
-struct L2CA_GetRemoteCid {
- std::function<bool(uint16_t lcid, uint16_t* rcid)> body{
- [](uint16_t lcid, uint16_t* rcid) { return false; }};
- bool operator()(uint16_t lcid, uint16_t* rcid) { return body(lcid, rcid); };
-};
-extern struct L2CA_GetRemoteCid L2CA_GetRemoteCid;
-// Name: L2CA_SetIdleTimeoutByBdAddr
-// Params: const RawAddress& bd_addr, uint16_t timeout, tBT_TRANSPORT transport
-// Returns: bool
-struct L2CA_SetIdleTimeoutByBdAddr {
- std::function<bool(const RawAddress& bd_addr, uint16_t timeout,
- tBT_TRANSPORT transport)>
- body{[](const RawAddress& bd_addr, uint16_t timeout,
- tBT_TRANSPORT transport) { return false; }};
- bool operator()(const RawAddress& bd_addr, uint16_t timeout,
- tBT_TRANSPORT transport) {
- return body(bd_addr, timeout, transport);
- };
-};
-extern struct L2CA_SetIdleTimeoutByBdAddr L2CA_SetIdleTimeoutByBdAddr;
-// Name: L2CA_SetTraceLevel
-// Params: uint8_t new_level
-// Returns: uint8_t
-struct L2CA_SetTraceLevel {
- std::function<uint8_t(uint8_t new_level)> body{
- [](uint8_t new_level) { return 0; }};
- uint8_t operator()(uint8_t new_level) { return body(new_level); };
-};
-extern struct L2CA_SetTraceLevel L2CA_SetTraceLevel;
-// Name: L2CA_SetAclPriority
-// Params: const RawAddress& bd_addr, tL2CAP_PRIORITY priority
-// Returns: bool
-struct L2CA_SetAclPriority {
- std::function<bool(const RawAddress& bd_addr, tL2CAP_PRIORITY priority)> body{
- [](const RawAddress& bd_addr, tL2CAP_PRIORITY priority) {
- return false;
- }};
- bool operator()(const RawAddress& bd_addr, tL2CAP_PRIORITY priority) {
- return body(bd_addr, priority);
- };
-};
-extern struct L2CA_SetAclPriority L2CA_SetAclPriority;
-// Name: L2CA_SetTxPriority
-// Params: uint16_t cid, tL2CAP_CHNL_PRIORITY priority
-// Returns: bool
-struct L2CA_SetTxPriority {
- std::function<bool(uint16_t cid, tL2CAP_CHNL_PRIORITY priority)> body{
- [](uint16_t cid, tL2CAP_CHNL_PRIORITY priority) { return false; }};
- bool operator()(uint16_t cid, tL2CAP_CHNL_PRIORITY priority) {
- return body(cid, priority);
- };
-};
-extern struct L2CA_SetTxPriority L2CA_SetTxPriority;
-// Name: L2CA_GetPeerFeatures
-// Params: const RawAddress& bd_addr, uint32_t* p_ext_feat, uint8_t* p_chnl_mask
-// Returns: bool
-struct L2CA_GetPeerFeatures {
- std::function<bool(const RawAddress& bd_addr, uint32_t* p_ext_feat,
- uint8_t* p_chnl_mask)>
- body{[](const RawAddress& bd_addr, uint32_t* p_ext_feat,
- uint8_t* p_chnl_mask) { return false; }};
- bool operator()(const RawAddress& bd_addr, uint32_t* p_ext_feat,
- uint8_t* p_chnl_mask) {
- return body(bd_addr, p_ext_feat, p_chnl_mask);
- };
-};
-extern struct L2CA_GetPeerFeatures L2CA_GetPeerFeatures;
-// Name: L2CA_RegisterFixedChannel
-// Params: uint16_t fixed_cid, tL2CAP_FIXED_CHNL_REG* p_freg
-// Returns: bool
-struct L2CA_RegisterFixedChannel {
- std::function<bool(uint16_t fixed_cid, tL2CAP_FIXED_CHNL_REG* p_freg)> body{
- [](uint16_t fixed_cid, tL2CAP_FIXED_CHNL_REG* p_freg) { return false; }};
- bool operator()(uint16_t fixed_cid, tL2CAP_FIXED_CHNL_REG* p_freg) {
- return body(fixed_cid, p_freg);
- };
-};
-extern struct L2CA_RegisterFixedChannel L2CA_RegisterFixedChannel;
-// Name: L2CA_ConnectFixedChnl
-// Params: uint16_t fixed_cid, const RawAddress& rem_bda
-// Returns: bool
-struct L2CA_ConnectFixedChnl {
- std::function<bool(uint16_t fixed_cid, const RawAddress& rem_bda)> body{
- [](uint16_t fixed_cid, const RawAddress& rem_bda) { return false; }};
- bool operator()(uint16_t fixed_cid, const RawAddress& rem_bda) {
- return body(fixed_cid, rem_bda);
- };
-};
-extern struct L2CA_ConnectFixedChnl L2CA_ConnectFixedChnl;
-// Name: L2CA_SendFixedChnlData
-// Params: uint16_t fixed_cid, const RawAddress& rem_bda, BT_HDR* p_buf
-// Returns: uint16_t
-struct L2CA_SendFixedChnlData {
- std::function<uint16_t(uint16_t fixed_cid, const RawAddress& rem_bda,
- BT_HDR* p_buf)>
- body{[](uint16_t fixed_cid, const RawAddress& rem_bda, BT_HDR* p_buf) {
- return 0;
- }};
- uint16_t operator()(uint16_t fixed_cid, const RawAddress& rem_bda,
- BT_HDR* p_buf) {
- return body(fixed_cid, rem_bda, p_buf);
- };
-};
-extern struct L2CA_SendFixedChnlData L2CA_SendFixedChnlData;
-// Name: L2CA_RemoveFixedChnl
-// Params: uint16_t fixed_cid, const RawAddress& rem_bda
-// Returns: bool
-struct L2CA_RemoveFixedChnl {
- std::function<bool(uint16_t fixed_cid, const RawAddress& rem_bda)> body{
- [](uint16_t fixed_cid, const RawAddress& rem_bda) { return false; }};
- bool operator()(uint16_t fixed_cid, const RawAddress& rem_bda) {
- return body(fixed_cid, rem_bda);
- };
-};
-extern struct L2CA_RemoveFixedChnl L2CA_RemoveFixedChnl;
-// Name: L2CA_SetLeGattTimeout
-// Params: const RawAddress& rem_bda, uint16_t idle_tout
-// Returns: bool
-struct L2CA_SetLeGattTimeout {
- std::function<bool(const RawAddress& rem_bda, uint16_t idle_tout)> body{
- [](const RawAddress& rem_bda, uint16_t idle_tout) { return false; }};
- bool operator()(const RawAddress& rem_bda, uint16_t idle_tout) {
- return body(rem_bda, idle_tout);
- };
-};
-extern struct L2CA_SetLeGattTimeout L2CA_SetLeGattTimeout;
-// Name: L2CA_DataWrite
-// Params: uint16_t cid, BT_HDR* p_data
-// Returns: uint8_t
-struct L2CA_DataWrite {
- std::function<uint8_t(uint16_t cid, BT_HDR* p_data)> body{
- [](uint16_t cid, BT_HDR* p_data) { return 0; }};
- uint8_t operator()(uint16_t cid, BT_HDR* p_data) {
- return body(cid, p_data);
- };
-};
-extern struct L2CA_DataWrite L2CA_DataWrite;
-// Name: L2CA_LECocDataWrite
-// Params: uint16_t cid, BT_HDR* p_data
-// Returns: uint8_t
-struct L2CA_LECocDataWrite {
- std::function<uint8_t(uint16_t cid, BT_HDR* p_data)> body{
- [](uint16_t cid, BT_HDR* p_data) { return 0; }};
- uint8_t operator()(uint16_t cid, BT_HDR* p_data) {
- return body(cid, p_data);
- };
-};
-extern struct L2CA_LECocDataWrite L2CA_LECocDataWrite;
-// Name: L2CA_SetChnlFlushability
-// Params: uint16_t cid, bool is_flushable
-// Returns: bool
-struct L2CA_SetChnlFlushability {
- std::function<bool(uint16_t cid, bool is_flushable)> body{
- [](uint16_t cid, bool is_flushable) { return false; }};
- bool operator()(uint16_t cid, bool is_flushable) {
- return body(cid, is_flushable);
- };
-};
-extern struct L2CA_SetChnlFlushability L2CA_SetChnlFlushability;
-// Name: L2CA_FlushChannel
-// Params: uint16_t lcid, uint16_t num_to_flush
-// Returns: uint16_t
-struct L2CA_FlushChannel {
- std::function<uint16_t(uint16_t lcid, uint16_t num_to_flush)> body{
- [](uint16_t lcid, uint16_t num_to_flush) { return 0; }};
- uint16_t operator()(uint16_t lcid, uint16_t num_to_flush) {
- return body(lcid, num_to_flush);
- };
-};
-extern struct L2CA_FlushChannel L2CA_FlushChannel;
-// Name: L2CA_IsLinkEstablished
-// Params: const RawAddress& bd_addr, tBT_TRANSPORT transport
-// Returns: bool
-struct L2CA_IsLinkEstablished {
- std::function<bool(const RawAddress& bd_addr, tBT_TRANSPORT transport)> body{
- [](const RawAddress& bd_addr, tBT_TRANSPORT transport) { return false; }};
- bool operator()(const RawAddress& bd_addr, tBT_TRANSPORT transport) {
- return body(bd_addr, transport);
- };
-};
-extern struct L2CA_IsLinkEstablished L2CA_IsLinkEstablished;
-
-} // namespace stack_l2cap_api
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_l2cap_ble.cc b/test/mock/mock_stack_l2cap_ble.cc
deleted file mode 100644
index a47ea5589..000000000
--- a/test/mock/mock_stack_l2cap_ble.cc
+++ /dev/null
@@ -1,201 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:22
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_stack_l2cap_ble.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace stack_l2cap_ble {
-
-// Function state capture and return values, if needed
-struct L2CA_UpdateBleConnParams L2CA_UpdateBleConnParams;
-struct L2CA_EnableUpdateBleConnParams L2CA_EnableUpdateBleConnParams;
-struct L2CA_GetBleConnRole L2CA_GetBleConnRole;
-struct l2cble_notify_le_connection l2cble_notify_le_connection;
-struct l2cble_conn_comp l2cble_conn_comp;
-struct l2cble_conn_comp_from_address_with_type
- l2cble_conn_comp_from_address_with_type;
-struct l2cble_process_conn_update_evt l2cble_process_conn_update_evt;
-struct l2cble_process_sig_cmd l2cble_process_sig_cmd;
-struct l2cble_create_conn l2cble_create_conn;
-struct l2c_link_processs_ble_num_bufs l2c_link_processs_ble_num_bufs;
-struct l2c_ble_link_adjust_allocation l2c_ble_link_adjust_allocation;
-struct l2cble_process_rc_param_request_evt l2cble_process_rc_param_request_evt;
-struct l2cble_update_data_length l2cble_update_data_length;
-struct l2cble_process_data_length_change_event
- l2cble_process_data_length_change_event;
-struct l2cble_credit_based_conn_req l2cble_credit_based_conn_req;
-struct l2cble_credit_based_conn_res l2cble_credit_based_conn_res;
-struct l2cble_send_flow_control_credit l2cble_send_flow_control_credit;
-struct l2cble_send_peer_disc_req l2cble_send_peer_disc_req;
-struct l2cble_sec_comp l2cble_sec_comp;
-struct l2ble_sec_access_req l2ble_sec_access_req;
-struct L2CA_AdjustConnectionIntervals L2CA_AdjustConnectionIntervals;
-struct l2cble_use_preferred_conn_params l2cble_use_preferred_conn_params;
-
-} // namespace stack_l2cap_ble
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-bool L2CA_UpdateBleConnParams(const RawAddress& rem_bda, uint16_t min_int,
- uint16_t max_int, uint16_t latency,
- uint16_t timeout, uint16_t min_ce_len,
- uint16_t max_ce_len) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_ble::L2CA_UpdateBleConnParams(
- rem_bda, min_int, max_int, latency, timeout, min_ce_len, max_ce_len);
-}
-bool L2CA_EnableUpdateBleConnParams(const RawAddress& rem_bda, bool enable) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_ble::L2CA_EnableUpdateBleConnParams(rem_bda,
- enable);
-}
-hci_role_t L2CA_GetBleConnRole(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_ble::L2CA_GetBleConnRole(bd_addr);
-}
-void l2cble_notify_le_connection(const RawAddress& bda) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_notify_le_connection(bda);
-}
-bool l2cble_conn_comp(uint16_t handle, uint8_t role, const RawAddress& bda,
- tBLE_ADDR_TYPE type, uint16_t conn_interval,
- uint16_t conn_latency, uint16_t conn_timeout) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_ble::l2cble_conn_comp(
- handle, role, bda, type, conn_interval, conn_latency, conn_timeout);
-}
-bool l2cble_conn_comp_from_address_with_type(
- uint16_t handle, uint8_t role, const tBLE_BD_ADDR& address_with_type,
- uint16_t conn_interval, uint16_t conn_latency, uint16_t conn_timeout) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_ble::l2cble_conn_comp_from_address_with_type(
- handle, role, address_with_type, conn_interval, conn_latency,
- conn_timeout);
-}
-void l2cble_process_conn_update_evt(uint16_t handle, uint8_t status,
- uint16_t interval, uint16_t latency,
- uint16_t timeout) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_process_conn_update_evt(
- handle, status, interval, latency, timeout);
-}
-void l2cble_process_sig_cmd(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_process_sig_cmd(p_lcb, p, pkt_len);
-}
-bool l2cble_create_conn(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_ble::l2cble_create_conn(p_lcb);
-}
-void l2c_link_processs_ble_num_bufs(uint16_t num_lm_ble_bufs) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2c_link_processs_ble_num_bufs(num_lm_ble_bufs);
-}
-void l2c_ble_link_adjust_allocation(void) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2c_ble_link_adjust_allocation();
-}
-void l2cble_process_rc_param_request_evt(uint16_t handle, uint16_t int_min,
- uint16_t int_max, uint16_t latency,
- uint16_t timeout) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_process_rc_param_request_evt(
- handle, int_min, int_max, latency, timeout);
-}
-void l2cble_update_data_length(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_update_data_length(p_lcb);
-}
-void l2cble_process_data_length_change_event(uint16_t handle,
- uint16_t tx_data_len,
- uint16_t rx_data_len) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_process_data_length_change_event(
- handle, tx_data_len, rx_data_len);
-}
-void l2cble_credit_based_conn_req(tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_credit_based_conn_req(p_ccb);
-}
-void l2cble_credit_based_conn_res(tL2C_CCB* p_ccb, uint16_t result) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_credit_based_conn_res(p_ccb, result);
-}
-void l2cble_send_flow_control_credit(tL2C_CCB* p_ccb, uint16_t credit_value) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_send_flow_control_credit(p_ccb,
- credit_value);
-}
-void l2cble_send_peer_disc_req(tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_send_peer_disc_req(p_ccb);
-}
-void l2cble_sec_comp(const RawAddress* bda, tBT_TRANSPORT transport,
- void* p_ref_data, tBTM_STATUS status) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_sec_comp(bda, transport, p_ref_data,
- status);
-}
-tL2CAP_LE_RESULT_CODE l2ble_sec_access_req(const RawAddress& bd_addr,
- uint16_t psm, bool is_originator,
- tL2CAP_SEC_CBACK* p_callback,
- void* p_ref_data) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_l2cap_ble::l2ble_sec_access_req(
- bd_addr, psm, is_originator, p_callback, p_ref_data);
-}
-void L2CA_AdjustConnectionIntervals(uint16_t* min_interval,
- uint16_t* max_interval,
- uint16_t floor_interval) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::L2CA_AdjustConnectionIntervals(
- min_interval, max_interval, floor_interval);
-}
-void l2cble_use_preferred_conn_params(const RawAddress& bda) {
- mock_function_count_map[__func__]++;
- test::mock::stack_l2cap_ble::l2cble_use_preferred_conn_params(bda);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_l2cap_ble.h b/test/mock/mock_stack_l2cap_ble.h
deleted file mode 100644
index a47cf5f41..000000000
--- a/test/mock/mock_stack_l2cap_ble.h
+++ /dev/null
@@ -1,321 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:22
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include "stack/include/l2c_api.h"
-#include "stack/l2cap/l2c_int.h"
-#include "types/ble_address_with_type.h"
-#include "types/hci_role.h"
-#include "types/raw_address.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace stack_l2cap_ble {
-
-// Shared state between mocked functions and tests
-// Name: L2CA_UpdateBleConnParams
-// Params: const RawAddress& rem_bda, uint16_t min_int, uint16_t max_int,
-// uint16_t latency, uint16_t timeout, uint16_t min_ce_len, uint16_t max_ce_len
-// Returns: bool
-struct L2CA_UpdateBleConnParams {
- std::function<bool(const RawAddress& rem_bda, uint16_t min_int,
- uint16_t max_int, uint16_t latency, uint16_t timeout,
- uint16_t min_ce_len, uint16_t max_ce_len)>
- body{[](const RawAddress& rem_bda, uint16_t min_int, uint16_t max_int,
- uint16_t latency, uint16_t timeout, uint16_t min_ce_len,
- uint16_t max_ce_len) { return false; }};
- bool operator()(const RawAddress& rem_bda, uint16_t min_int, uint16_t max_int,
- uint16_t latency, uint16_t timeout, uint16_t min_ce_len,
- uint16_t max_ce_len) {
- return body(rem_bda, min_int, max_int, latency, timeout, min_ce_len,
- max_ce_len);
- };
-};
-extern struct L2CA_UpdateBleConnParams L2CA_UpdateBleConnParams;
-// Name: L2CA_EnableUpdateBleConnParams
-// Params: const RawAddress& rem_bda, bool enable
-// Returns: bool
-struct L2CA_EnableUpdateBleConnParams {
- std::function<bool(const RawAddress& rem_bda, bool enable)> body{
- [](const RawAddress& rem_bda, bool enable) { return false; }};
- bool operator()(const RawAddress& rem_bda, bool enable) {
- return body(rem_bda, enable);
- };
-};
-extern struct L2CA_EnableUpdateBleConnParams L2CA_EnableUpdateBleConnParams;
-// Name: L2CA_GetBleConnRole
-// Params: const RawAddress& bd_addr
-// Returns: hci_role_t
-struct L2CA_GetBleConnRole {
- std::function<hci_role_t(const RawAddress& bd_addr)> body{
- [](const RawAddress& bd_addr) { return HCI_ROLE_CENTRAL; }};
- hci_role_t operator()(const RawAddress& bd_addr) { return body(bd_addr); };
-};
-extern struct L2CA_GetBleConnRole L2CA_GetBleConnRole;
-// Name: l2cble_notify_le_connection
-// Params: const RawAddress& bda
-// Returns: void
-struct l2cble_notify_le_connection {
- std::function<void(const RawAddress& bda)> body{[](const RawAddress& bda) {}};
- void operator()(const RawAddress& bda) { body(bda); };
-};
-extern struct l2cble_notify_le_connection l2cble_notify_le_connection;
-// Name: l2cble_conn_comp
-// Params: uint16_t handle, uint8_t role, const RawAddress& bda, tBLE_ADDR_TYPE
-// type, uint16_t conn_interval, uint16_t conn_latency, uint16_t conn_timeout
-// Returns: bool
-struct l2cble_conn_comp {
- std::function<bool(uint16_t handle, uint8_t role, const RawAddress& bda,
- tBLE_ADDR_TYPE type, uint16_t conn_interval,
- uint16_t conn_latency, uint16_t conn_timeout)>
- body{[](uint16_t handle, uint8_t role, const RawAddress& bda,
- tBLE_ADDR_TYPE type, uint16_t conn_interval,
- uint16_t conn_latency, uint16_t conn_timeout) { return false; }};
- bool operator()(uint16_t handle, uint8_t role, const RawAddress& bda,
- tBLE_ADDR_TYPE type, uint16_t conn_interval,
- uint16_t conn_latency, uint16_t conn_timeout) {
- return body(handle, role, bda, type, conn_interval, conn_latency,
- conn_timeout);
- };
-};
-extern struct l2cble_conn_comp l2cble_conn_comp;
-// Name: l2cble_conn_comp_from_address_with_type
-// Params: uint16_t handle, uint8_t role, const tBLE_BD_ADDR&
-// address_with_type, uint16_t conn_interval, uint16_t conn_latency, uint16_t
-// conn_timeout Returns: bool
-struct l2cble_conn_comp_from_address_with_type {
- std::function<bool(
- uint16_t handle, uint8_t role, const tBLE_BD_ADDR& address_with_type,
- uint16_t conn_interval, uint16_t conn_latency, uint16_t conn_timeout)>
- body{[](uint16_t handle, uint8_t role,
- const tBLE_BD_ADDR& address_with_type, uint16_t conn_interval,
- uint16_t conn_latency, uint16_t conn_timeout) { return false; }};
- bool operator()(uint16_t handle, uint8_t role,
- const tBLE_BD_ADDR& address_with_type, uint16_t conn_interval,
- uint16_t conn_latency, uint16_t conn_timeout) {
- return body(handle, role, address_with_type, conn_interval, conn_latency,
- conn_timeout);
- };
-};
-extern struct l2cble_conn_comp_from_address_with_type
- l2cble_conn_comp_from_address_with_type;
-// Name: l2cble_process_conn_update_evt
-// Params: uint16_t handle, uint8_t status, uint16_t interval, uint16_t latency,
-// uint16_t timeout Returns: void
-struct l2cble_process_conn_update_evt {
- std::function<void(uint16_t handle, uint8_t status, uint16_t interval,
- uint16_t latency, uint16_t timeout)>
- body{[](uint16_t handle, uint8_t status, uint16_t interval,
- uint16_t latency, uint16_t timeout) {}};
- void operator()(uint16_t handle, uint8_t status, uint16_t interval,
- uint16_t latency, uint16_t timeout) {
- body(handle, status, interval, latency, timeout);
- };
-};
-extern struct l2cble_process_conn_update_evt l2cble_process_conn_update_evt;
-// Name: l2cble_process_sig_cmd
-// Params: tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len
-// Returns: void
-struct l2cble_process_sig_cmd {
- std::function<void(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len)> body{
- [](tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {}};
- void operator()(tL2C_LCB* p_lcb, uint8_t* p, uint16_t pkt_len) {
- body(p_lcb, p, pkt_len);
- };
-};
-extern struct l2cble_process_sig_cmd l2cble_process_sig_cmd;
-// Name: l2cble_create_conn
-// Params: tL2C_LCB* p_lcb
-// Returns: bool
-struct l2cble_create_conn {
- std::function<bool(tL2C_LCB* p_lcb)> body{
- [](tL2C_LCB* p_lcb) { return false; }};
- bool operator()(tL2C_LCB* p_lcb) { return body(p_lcb); };
-};
-extern struct l2cble_create_conn l2cble_create_conn;
-// Name: l2c_link_processs_ble_num_bufs
-// Params: uint16_t num_lm_ble_bufs
-// Returns: void
-struct l2c_link_processs_ble_num_bufs {
- std::function<void(uint16_t num_lm_ble_bufs)> body{
- [](uint16_t num_lm_ble_bufs) {}};
- void operator()(uint16_t num_lm_ble_bufs) { body(num_lm_ble_bufs); };
-};
-extern struct l2c_link_processs_ble_num_bufs l2c_link_processs_ble_num_bufs;
-// Name: l2c_ble_link_adjust_allocation
-// Params: void
-// Returns: void
-struct l2c_ble_link_adjust_allocation {
- std::function<void(void)> body{[](void) {}};
- void operator()(void) { body(); };
-};
-extern struct l2c_ble_link_adjust_allocation l2c_ble_link_adjust_allocation;
-// Name: l2cble_process_rc_param_request_evt
-// Params: uint16_t handle, uint16_t int_min, uint16_t int_max, uint16_t
-// latency, uint16_t timeout Returns: void
-struct l2cble_process_rc_param_request_evt {
- std::function<void(uint16_t handle, uint16_t int_min, uint16_t int_max,
- uint16_t latency, uint16_t timeout)>
- body{[](uint16_t handle, uint16_t int_min, uint16_t int_max,
- uint16_t latency, uint16_t timeout) {}};
- void operator()(uint16_t handle, uint16_t int_min, uint16_t int_max,
- uint16_t latency, uint16_t timeout) {
- body(handle, int_min, int_max, latency, timeout);
- };
-};
-extern struct l2cble_process_rc_param_request_evt
- l2cble_process_rc_param_request_evt;
-// Name: l2cble_update_data_length
-// Params: tL2C_LCB* p_lcb
-// Returns: void
-struct l2cble_update_data_length {
- std::function<void(tL2C_LCB* p_lcb)> body{[](tL2C_LCB* p_lcb) {}};
- void operator()(tL2C_LCB* p_lcb) { body(p_lcb); };
-};
-extern struct l2cble_update_data_length l2cble_update_data_length;
-// Name: l2cble_process_data_length_change_event
-// Params: uint16_t handle, uint16_t tx_data_len, uint16_t rx_data_len
-// Returns: void
-struct l2cble_process_data_length_change_event {
- std::function<void(uint16_t handle, uint16_t tx_data_len,
- uint16_t rx_data_len)>
- body{[](uint16_t handle, uint16_t tx_data_len, uint16_t rx_data_len) {}};
- void operator()(uint16_t handle, uint16_t tx_data_len, uint16_t rx_data_len) {
- body(handle, tx_data_len, rx_data_len);
- };
-};
-extern struct l2cble_process_data_length_change_event
- l2cble_process_data_length_change_event;
-// Name: l2cble_credit_based_conn_req
-// Params: tL2C_CCB* p_ccb
-// Returns: void
-struct l2cble_credit_based_conn_req {
- std::function<void(tL2C_CCB* p_ccb)> body{[](tL2C_CCB* p_ccb) {}};
- void operator()(tL2C_CCB* p_ccb) { body(p_ccb); };
-};
-extern struct l2cble_credit_based_conn_req l2cble_credit_based_conn_req;
-// Name: l2cble_credit_based_conn_res
-// Params: tL2C_CCB* p_ccb, uint16_t result
-// Returns: void
-struct l2cble_credit_based_conn_res {
- std::function<void(tL2C_CCB* p_ccb, uint16_t result)> body{
- [](tL2C_CCB* p_ccb, uint16_t result) {}};
- void operator()(tL2C_CCB* p_ccb, uint16_t result) { body(p_ccb, result); };
-};
-extern struct l2cble_credit_based_conn_res l2cble_credit_based_conn_res;
-// Name: l2cble_send_flow_control_credit
-// Params: tL2C_CCB* p_ccb, uint16_t credit_value
-// Returns: void
-struct l2cble_send_flow_control_credit {
- std::function<void(tL2C_CCB* p_ccb, uint16_t credit_value)> body{
- [](tL2C_CCB* p_ccb, uint16_t credit_value) {}};
- void operator()(tL2C_CCB* p_ccb, uint16_t credit_value) {
- body(p_ccb, credit_value);
- };
-};
-extern struct l2cble_send_flow_control_credit l2cble_send_flow_control_credit;
-// Name: l2cble_send_peer_disc_req
-// Params: tL2C_CCB* p_ccb
-// Returns: void
-struct l2cble_send_peer_disc_req {
- std::function<void(tL2C_CCB* p_ccb)> body{[](tL2C_CCB* p_ccb) {}};
- void operator()(tL2C_CCB* p_ccb) { body(p_ccb); };
-};
-extern struct l2cble_send_peer_disc_req l2cble_send_peer_disc_req;
-// Name: l2cble_sec_comp
-// Params: const RawAddress* bda, tBT_TRANSPORT transport, void* p_ref_data,
-// tBTM_STATUS status Returns: void
-struct l2cble_sec_comp {
- std::function<void(const RawAddress* bda, tBT_TRANSPORT transport,
- void* p_ref_data, tBTM_STATUS status)>
- body{[](const RawAddress* bda, tBT_TRANSPORT transport, void* p_ref_data,
- tBTM_STATUS status) {}};
- void operator()(const RawAddress* bda, tBT_TRANSPORT transport,
- void* p_ref_data, tBTM_STATUS status) {
- body(bda, transport, p_ref_data, status);
- };
-};
-extern struct l2cble_sec_comp l2cble_sec_comp;
-// Name: l2ble_sec_access_req
-// Params: const RawAddress& bd_addr, uint16_t psm, bool is_originator,
-// tL2CAP_SEC_CBACK* p_callback, void* p_ref_data Returns: tL2CAP_LE_RESULT_CODE
-struct l2ble_sec_access_req {
- std::function<tL2CAP_LE_RESULT_CODE(
- const RawAddress& bd_addr, uint16_t psm, bool is_originator,
- tL2CAP_SEC_CBACK* p_callback, void* p_ref_data)>
- body{[](const RawAddress& bd_addr, uint16_t psm, bool is_originator,
- tL2CAP_SEC_CBACK* p_callback,
- void* p_ref_data) { return L2CAP_LE_RESULT_CONN_OK; }};
- tL2CAP_LE_RESULT_CODE operator()(const RawAddress& bd_addr, uint16_t psm,
- bool is_originator,
- tL2CAP_SEC_CBACK* p_callback,
- void* p_ref_data) {
- return body(bd_addr, psm, is_originator, p_callback, p_ref_data);
- };
-};
-extern struct l2ble_sec_access_req l2ble_sec_access_req;
-// Name: L2CA_AdjustConnectionIntervals
-// Params: uint16_t* min_interval, uint16_t* max_interval, uint16_t
-// floor_interval Returns: void
-struct L2CA_AdjustConnectionIntervals {
- std::function<void(uint16_t* min_interval, uint16_t* max_interval,
- uint16_t floor_interval)>
- body{[](uint16_t* min_interval, uint16_t* max_interval,
- uint16_t floor_interval) {}};
- void operator()(uint16_t* min_interval, uint16_t* max_interval,
- uint16_t floor_interval) {
- body(min_interval, max_interval, floor_interval);
- };
-};
-extern struct L2CA_AdjustConnectionIntervals L2CA_AdjustConnectionIntervals;
-// Name: l2cble_use_preferred_conn_params
-// Params: const RawAddress& bda
-// Returns: void
-struct l2cble_use_preferred_conn_params {
- std::function<void(const RawAddress& bda)> body{[](const RawAddress& bda) {}};
- void operator()(const RawAddress& bda) { body(bda); };
-};
-extern struct l2cble_use_preferred_conn_params l2cble_use_preferred_conn_params;
-
-} // namespace stack_l2cap_ble
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_l2cap_link.cc b/test/mock/mock_stack_l2cap_link.cc
deleted file mode 100644
index 8840d1d7b..000000000
--- a/test/mock/mock_stack_l2cap_link.cc
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-#define UNUSED_ATTR
-
-#include <cstdint>
-#include "stack/l2cap/l2c_int.h"
-BT_HDR* l2cu_get_next_buffer_to_send(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-bool l2c_link_hci_disc_comp(uint16_t handle, tHCI_REASON reason) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tBTM_STATUS l2cu_ConnectAclForSecurity(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return BTM_SUCCESS;
-}
-tL2C_CCB* l2cu_get_next_channel_in_rr(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void l2c_OnHciModeChangeSendPendingPackets(RawAddress remote) {
- mock_function_count_map[__func__]++;
-}
-void l2c_info_resp_timer_timeout(void* data) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_adjust_allocation(void) { mock_function_count_map[__func__]++; }
-void l2c_link_adjust_chnl_allocation(void) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_check_send_pkts(tL2C_LCB* p_lcb, uint16_t local_cid,
- BT_HDR* p_buf) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_hci_conn_comp(tHCI_STATUS status, uint16_t handle,
- const RawAddress& p_bda) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_hci_conn_req(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_init() { mock_function_count_map[__func__]++; }
-void l2c_link_process_num_completed_pkts(uint8_t* p, uint8_t evt_len) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_role_changed(const RawAddress* bd_addr, uint8_t new_role,
- uint8_t hci_status) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_sec_comp(const RawAddress* p_bda,
- UNUSED_ATTR tBT_TRANSPORT transport, void* p_ref_data,
- uint8_t status) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_sec_comp2(const RawAddress& p_bda,
- UNUSED_ATTR tBT_TRANSPORT transport, void* p_ref_data,
- uint8_t status) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_segments_xmitted(BT_HDR* p_msg) {
- mock_function_count_map[__func__]++;
-}
-void l2c_link_timeout(tL2C_LCB* p_lcb) { mock_function_count_map[__func__]++; }
-void l2c_packets_completed(uint16_t handle, uint16_t num_sent) {
- mock_function_count_map[__func__]++;
-}
-void l2c_pin_code_request(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
-}
-void l2cble_update_sec_act(const RawAddress& bd_addr, uint16_t sec_act) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_l2cap_main.cc b/test/mock/mock_stack_l2cap_main.cc
deleted file mode 100644
index ab28a6cd1..000000000
--- a/test/mock/mock_stack_l2cap_main.cc
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:9
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "bt_common.h"
-#include "bt_target.h"
-#include "hci/include/btsnoop.h"
-#include "hcimsgs.h"
-#include "l2c_api.h"
-#include "l2cdefs.h"
-#include "main/shim/shim.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "stack/l2cap/l2c_int.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-uint8_t l2c_data_write(uint16_t cid, BT_HDR* p_data, uint16_t flags) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void l2c_ccb_timer_timeout(void* data) { mock_function_count_map[__func__]++; }
-void l2c_fcrb_ack_timer_timeout(void* data) {
- mock_function_count_map[__func__]++;
-}
-void l2c_free(void) { mock_function_count_map[__func__]++; }
-void l2c_init(void) { mock_function_count_map[__func__]++; }
-void l2c_lcb_timer_timeout(void* data) { mock_function_count_map[__func__]++; }
-void l2c_process_held_packets(bool timed_out) {
- mock_function_count_map[__func__]++;
-}
-void l2c_rcv_acl_data(BT_HDR* p_msg) { mock_function_count_map[__func__]++; }
-void l2c_receive_hold_timer_timeout(UNUSED_ATTR void* data) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_l2cap_utils.cc b/test/mock/mock_stack_l2cap_utils.cc
deleted file mode 100644
index 304c7596b..000000000
--- a/test/mock/mock_stack_l2cap_utils.cc
+++ /dev/null
@@ -1,283 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:72
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <cstdint>
-#include "stack/include/bt_types.h"
-#include "stack/l2cap/l2c_int.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-BT_HDR* l2cu_build_header(tL2C_LCB* p_lcb, uint16_t len, uint8_t cmd,
- uint8_t signal_id) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-bool l2c_is_cmd_rejected(uint8_t cmd_code, uint8_t signal_id, tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool l2cu_create_conn_le(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool l2cu_create_conn_le(tL2C_LCB* p_lcb, uint8_t initiating_phys) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool l2cu_initialize_fixed_ccb(tL2C_LCB* p_lcb, uint16_t fixed_cid) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool l2cu_is_ccb_active(tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool l2cu_lcb_disconnecting(void) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool l2cu_set_acl_priority(const RawAddress& bd_addr, tL2CAP_PRIORITY priority,
- bool reset_after_rs) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool l2cu_start_post_bond_timer(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tL2C_CCB* l2cu_allocate_ccb(tL2C_LCB* p_lcb, uint16_t cid) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tL2C_CCB* l2cu_find_ccb_by_cid(tL2C_LCB* p_lcb, uint16_t local_cid) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tL2C_CCB* l2cu_find_ccb_by_remote_cid(tL2C_LCB* p_lcb, uint16_t remote_cid) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tL2C_LCB* l2cu_allocate_lcb(const RawAddress& p_bd_addr, bool is_bonding,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tL2C_LCB* l2cu_find_lcb_by_bd_addr(const RawAddress& p_bd_addr,
- tBT_TRANSPORT transport) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tL2C_LCB* l2cu_find_lcb_by_handle(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tL2C_LCB* l2cu_find_lcb_by_state(tL2C_LINK_STATE state) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tL2C_RCB* l2cu_allocate_ble_rcb(uint16_t psm) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tL2C_RCB* l2cu_allocate_rcb(uint16_t psm) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tL2C_RCB* l2cu_find_ble_rcb_by_psm(uint16_t psm) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tL2C_RCB* l2cu_find_rcb_by_psm(uint16_t psm) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-uint8_t l2cu_get_num_hi_priority(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t l2cu_process_peer_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void l2cu_adj_id(tL2C_LCB* p_lcb) { mock_function_count_map[__func__]++; }
-void l2cu_adjust_out_mps(tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_change_pri_ccb(tL2C_CCB* p_ccb, tL2CAP_CHNL_PRIORITY priority) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_check_channel_congestion(tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_create_conn_after_switch(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_create_conn_br_edr(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_dequeue_ccb(tL2C_CCB* p_ccb) { mock_function_count_map[__func__]++; }
-void l2cu_device_reset(void) { mock_function_count_map[__func__]++; }
-void l2cu_disconnect_chnl(tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_enqueue_ccb(tL2C_CCB* p_ccb) { mock_function_count_map[__func__]++; }
-void l2cu_no_dynamic_ccbs(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_process_fixed_chnl_resp(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_process_fixed_disc_cback(tL2C_LCB* p_lcb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_process_our_cfg_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_process_our_cfg_rsp(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_process_peer_cfg_rsp(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_reject_ble_coc_connection(tL2C_LCB* p_lcb, uint8_t rem_id,
- uint16_t result) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_reject_ble_connection(tL2C_CCB* p_ccb, uint8_t rem_id,
- uint16_t result) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_reject_connection(tL2C_LCB* p_lcb, uint16_t remote_cid,
- uint8_t rem_id, uint16_t result) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_reject_credit_based_conn_req(tL2C_LCB* p_lcb, uint8_t rem_id,
- uint8_t num_of_channels,
- uint16_t result) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_release_ble_rcb(tL2C_RCB* p_rcb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_release_ccb(tL2C_CCB* p_ccb) { mock_function_count_map[__func__]++; }
-void l2cu_release_lcb(tL2C_LCB* p_lcb) { mock_function_count_map[__func__]++; }
-void l2cu_release_rcb(tL2C_RCB* p_rcb) { mock_function_count_map[__func__]++; }
-void l2cu_resubmit_pending_sec_req(const RawAddress* p_bda) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_ble_reconfig_rsp(tL2C_LCB* p_lcb, uint8_t rem_id,
- uint16_t result) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_credit_based_reconfig_req(tL2C_CCB* p_ccb,
- tL2CAP_LE_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_ble_credit_based_conn_req(tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_ble_credit_based_conn_res(tL2C_CCB* p_ccb,
- uint16_t result) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_ble_credit_based_disconn_req(tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_ble_flow_control_credit(tL2C_CCB* p_ccb,
- uint16_t credit_value) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_ble_par_req(tL2C_LCB* p_lcb, uint16_t min_int,
- uint16_t max_int, uint16_t latency,
- uint16_t timeout) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_ble_par_rsp(tL2C_LCB* p_lcb, uint16_t reason,
- uint8_t rem_id) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_cmd_reject(tL2C_LCB* p_lcb, uint16_t reason, uint8_t rem_id,
- uint16_t p1, uint16_t p2) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_config_rej(tL2C_CCB* p_ccb, uint8_t* p_data,
- uint16_t data_len, uint16_t rej_len) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_config_req(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_config_rsp(tL2C_CCB* p_ccb, tL2CAP_CFG_INFO* p_cfg) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_connect_req(tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_connect_rsp(tL2C_CCB* p_ccb, uint16_t result,
- uint16_t status) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_credit_based_conn_req(tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_credit_based_conn_res(tL2C_CCB* p_ccb,
- std::vector<uint16_t>& accepted_cids,
- uint16_t result) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_disc_req(tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_disc_rsp(tL2C_LCB* p_lcb, uint8_t remote_id,
- uint16_t local_cid, uint16_t remote_cid) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_echo_rsp(tL2C_LCB* p_lcb, uint8_t signal_id,
- uint8_t* p_data, uint16_t data_len) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_info_req(tL2C_LCB* p_lcb, uint16_t info_type) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_send_peer_info_rsp(tL2C_LCB* p_lcb, uint8_t remote_id,
- uint16_t info_type) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_set_acl_hci_header(BT_HDR* p_buf, tL2C_CCB* p_ccb) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_set_lcb_handle(struct t_l2c_linkcb& p_lcb, uint16_t handle) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_set_non_flushable_pbf(bool is_supported) {
- mock_function_count_map[__func__]++;
-}
-void l2cu_update_lcb_4_bonding(const RawAddress& p_bd_addr, bool is_bonding) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_metrics_logging.cc b/test/mock/mock_stack_metrics_logging.cc
deleted file mode 100644
index 3485c351a..000000000
--- a/test/mock/mock_stack_metrics_logging.cc
+++ /dev/null
@@ -1,115 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:5
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
-#include "common/metrics.h"
-#include "main/shim/metrics_api.h"
-#include "main/shim/shim.h"
-#include "stack/include/stack_metrics_logging.h"
-#include "types/raw_address.h"
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_stack_metrics_logging.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace stack_metrics_logging {
-
-// Function state capture and return values, if needed
-struct log_classic_pairing_event log_classic_pairing_event;
-struct log_link_layer_connection_event log_link_layer_connection_event;
-struct log_smp_pairing_event log_smp_pairing_event;
-struct log_sdp_attribute log_sdp_attribute;
-struct log_manufacturer_info log_manufacturer_info;
-
-} // namespace stack_metrics_logging
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-void log_classic_pairing_event(const RawAddress& address, uint16_t handle,
- uint32_t hci_cmd, uint16_t hci_event,
- uint16_t cmd_status, uint16_t reason_code,
- int64_t event_value) {
- mock_function_count_map[__func__]++;
- test::mock::stack_metrics_logging::log_classic_pairing_event(
- address, handle, hci_cmd, hci_event, cmd_status, reason_code,
- event_value);
-}
-void log_link_layer_connection_event(
- const RawAddress* address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction, uint16_t link_type,
- uint32_t hci_cmd, uint16_t hci_event, uint16_t hci_ble_event,
- uint16_t cmd_status, uint16_t reason_code) {
- mock_function_count_map[__func__]++;
- test::mock::stack_metrics_logging::log_link_layer_connection_event(
- address, connection_handle, direction, link_type, hci_cmd, hci_event,
- hci_ble_event, cmd_status, reason_code);
-}
-void log_smp_pairing_event(const RawAddress& address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason) {
- mock_function_count_map[__func__]++;
- test::mock::stack_metrics_logging::log_smp_pairing_event(
- address, smp_cmd, direction, smp_fail_reason);
-}
-void log_sdp_attribute(const RawAddress& address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value) {
- mock_function_count_map[__func__]++;
- test::mock::stack_metrics_logging::log_sdp_attribute(
- address, protocol_uuid, attribute_id, attribute_size, attribute_value);
-}
-void log_manufacturer_info(const RawAddress& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer,
- const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version) {
- mock_function_count_map[__func__]++;
- test::mock::stack_metrics_logging::log_manufacturer_info(
- address, source_type, source_name, manufacturer, model, hardware_version,
- software_version);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_metrics_logging.h b/test/mock/mock_stack_metrics_logging.h
deleted file mode 100644
index f923859c3..000000000
--- a/test/mock/mock_stack_metrics_logging.h
+++ /dev/null
@@ -1,166 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:5
- *
- * mockcify.pl ver 0.2
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include <frameworks/proto_logging/stats/enums/bluetooth/enums.pb.h>
-#include <frameworks/proto_logging/stats/enums/bluetooth/hci/enums.pb.h>
-#include "common/metrics.h"
-#include "main/shim/metrics_api.h"
-#include "main/shim/shim.h"
-#include "stack/include/stack_metrics_logging.h"
-#include "types/raw_address.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace stack_metrics_logging {
-
-// Shared state between mocked functions and tests
-// Name: log_classic_pairing_event
-// Params: const RawAddress& address, uint16_t handle, uint32_t hci_cmd,
-// uint16_t hci_event, uint16_t cmd_status, uint16_t reason_code, int64_t
-// event_value Returns: void
-struct log_classic_pairing_event {
- std::function<void(const RawAddress& address, uint16_t handle,
- uint32_t hci_cmd, uint16_t hci_event, uint16_t cmd_status,
- uint16_t reason_code, int64_t event_value)>
- body{[](const RawAddress& address, uint16_t handle, uint32_t hci_cmd,
- uint16_t hci_event, uint16_t cmd_status, uint16_t reason_code,
- int64_t event_value) {}};
- void operator()(const RawAddress& address, uint16_t handle, uint32_t hci_cmd,
- uint16_t hci_event, uint16_t cmd_status, uint16_t reason_code,
- int64_t event_value) {
- body(address, handle, hci_cmd, hci_event, cmd_status, reason_code,
- event_value);
- };
-};
-extern struct log_classic_pairing_event log_classic_pairing_event;
-// Name: log_link_layer_connection_event
-// Params: const RawAddress* address, uint32_t connection_handle,
-// android::bluetooth::DirectionEnum direction, uint16_t link_type, uint32_t
-// hci_cmd, uint16_t hci_event, uint16_t hci_ble_event, uint16_t cmd_status,
-// uint16_t reason_code Returns: void
-struct log_link_layer_connection_event {
- std::function<void(const RawAddress* address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction,
- uint16_t link_type, uint32_t hci_cmd, uint16_t hci_event,
- uint16_t hci_ble_event, uint16_t cmd_status,
- uint16_t reason_code)>
- body{[](const RawAddress* address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction, uint16_t link_type,
- uint32_t hci_cmd, uint16_t hci_event, uint16_t hci_ble_event,
- uint16_t cmd_status, uint16_t reason_code) {}};
- void operator()(const RawAddress* address, uint32_t connection_handle,
- android::bluetooth::DirectionEnum direction,
- uint16_t link_type, uint32_t hci_cmd, uint16_t hci_event,
- uint16_t hci_ble_event, uint16_t cmd_status,
- uint16_t reason_code) {
- body(address, connection_handle, direction, link_type, hci_cmd, hci_event,
- hci_ble_event, cmd_status, reason_code);
- };
-};
-extern struct log_link_layer_connection_event log_link_layer_connection_event;
-// Name: log_smp_pairing_event
-// Params: const RawAddress& address, uint8_t smp_cmd,
-// android::bluetooth::DirectionEnum direction, uint8_t smp_fail_reason Returns:
-// void
-struct log_smp_pairing_event {
- std::function<void(const RawAddress& address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason)>
- body{[](const RawAddress& address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason) {}};
- void operator()(const RawAddress& address, uint8_t smp_cmd,
- android::bluetooth::DirectionEnum direction,
- uint8_t smp_fail_reason) {
- body(address, smp_cmd, direction, smp_fail_reason);
- };
-};
-extern struct log_smp_pairing_event log_smp_pairing_event;
-// Name: log_sdp_attribute
-// Params: const RawAddress& address, uint16_t protocol_uuid, uint16_t
-// attribute_id, size_t attribute_size, const char* attribute_value Returns:
-// void
-struct log_sdp_attribute {
- std::function<void(const RawAddress& address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value)>
- body{[](const RawAddress& address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value) {}};
- void operator()(const RawAddress& address, uint16_t protocol_uuid,
- uint16_t attribute_id, size_t attribute_size,
- const char* attribute_value) {
- body(address, protocol_uuid, attribute_id, attribute_size, attribute_value);
- };
-};
-extern struct log_sdp_attribute log_sdp_attribute;
-// Name: log_manufacturer_info
-// Params: const RawAddress& address, android::bluetooth::DeviceInfoSrcEnum
-// source_type, const std::string& source_name, const std::string& manufacturer,
-// const std::string& model, const std::string& hardware_version, const
-// std::string& software_version Returns: void
-struct log_manufacturer_info {
- std::function<void(const RawAddress& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer, const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version)>
- body{[](const RawAddress& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name, const std::string& manufacturer,
- const std::string& model, const std::string& hardware_version,
- const std::string& software_version) {}};
- void operator()(const RawAddress& address,
- android::bluetooth::DeviceInfoSrcEnum source_type,
- const std::string& source_name,
- const std::string& manufacturer, const std::string& model,
- const std::string& hardware_version,
- const std::string& software_version) {
- body(address, source_type, source_name, manufacturer, model,
- hardware_version, software_version);
- };
-};
-extern struct log_manufacturer_info log_manufacturer_info;
-
-} // namespace stack_metrics_logging
-} // namespace mock
-} // namespace test
-
-// END mockcify generation \ No newline at end of file
diff --git a/test/mock/mock_stack_pan_api.cc b/test/mock/mock_stack_pan_api.cc
deleted file mode 100644
index 29023b2d0..000000000
--- a/test/mock/mock_stack_pan_api.cc
+++ /dev/null
@@ -1,92 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:11
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <string.h>
-#include "bnep_api.h"
-#include "bt_common.h"
-#include "bt_types.h"
-#include "btm_api.h"
-#include "hcidefs.h"
-#include "l2c_api.h"
-#include "pan_api.h"
-#include "sdp_api.h"
-#include "sdpdefs.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/pan/pan_int.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tBNEP_RESULT PAN_SetMulticastFilters(uint16_t handle,
- uint16_t num_mcast_filters,
- uint8_t* p_start_array,
- uint8_t* p_end_array) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tPAN_RESULT PAN_Connect(const RawAddress& rem_bda, uint8_t src_role,
- uint8_t dst_role, uint16_t* handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tPAN_RESULT PAN_Disconnect(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tPAN_RESULT PAN_SetProtocolFilters(uint16_t handle, uint16_t num_filters,
- uint16_t* p_start_array,
- uint16_t* p_end_array) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tPAN_RESULT PAN_SetRole(uint8_t role, const char* p_user_name,
- const char* p_nap_name) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tPAN_RESULT PAN_Write(uint16_t handle, const RawAddress& dst,
- const RawAddress& src, uint16_t protocol, uint8_t* p_data,
- uint16_t len, bool ext) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tPAN_RESULT PAN_WriteBuf(uint16_t handle, const RawAddress& dst,
- const RawAddress& src, uint16_t protocol,
- BT_HDR* p_buf, bool ext) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t PAN_SetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void PAN_Deregister(void) { mock_function_count_map[__func__]++; }
-void PAN_Init(void) { mock_function_count_map[__func__]++; }
-void PAN_Register(tPAN_REGISTER* p_register) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_stack_rfcomm_port_api.cc b/test/mock/mock_stack_rfcomm_port_api.cc
deleted file mode 100644
index c2b619901..000000000
--- a/test/mock/mock_stack_rfcomm_port_api.cc
+++ /dev/null
@@ -1,130 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:20
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <base/logging.h>
-#include <string.h>
-#include "bt_common.h"
-#include "l2c_api.h"
-#include "osi/include/log.h"
-#include "osi/include/mutex.h"
-#include "port_api.h"
-#include "rfcdefs.h"
-#include "sdp_api.h"
-#include "stack/include/btm_api_types.h"
-#include "stack/rfcomm/port_int.h"
-#include "stack/rfcomm/rfc_int.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool PORT_IsOpening(RawAddress* bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-const char* PORT_GetResultString(const uint8_t result_code) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-int PORT_CheckConnection(uint16_t handle, RawAddress* bd_addr,
- uint16_t* p_lcid) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int PORT_ClearKeepHandleFlag(uint16_t port_handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int PORT_FlowControl_MaxCredit(uint16_t handle, bool enable) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int PORT_GetState(uint16_t handle, tPORT_STATE* p_settings) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int PORT_ReadData(uint16_t handle, char* p_data, uint16_t max_len,
- uint16_t* p_len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int PORT_SetDataCOCallback(uint16_t port_handle,
- tPORT_DATA_CO_CALLBACK* p_port_cb) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int PORT_SetEventCallback(uint16_t port_handle, tPORT_CALLBACK* p_port_cb) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int PORT_SetEventMask(uint16_t port_handle, uint32_t mask) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int PORT_SetState(uint16_t handle, tPORT_STATE* p_settings) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int PORT_WriteData(uint16_t handle, const char* p_data, uint16_t max_len,
- uint16_t* p_len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int PORT_WriteDataCO(uint16_t handle, int* p_len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int RFCOMM_CreateConnection(uint16_t uuid, uint8_t scn, bool is_server,
- uint16_t mtu, const RawAddress& bd_addr,
- uint16_t* p_handle, tPORT_CALLBACK* p_mgmt_cb) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int RFCOMM_CreateConnectionWithSecurity(uint16_t uuid, uint8_t scn,
- bool is_server, uint16_t mtu,
- const RawAddress& bd_addr,
- uint16_t* p_handle,
- tPORT_CALLBACK* p_mgmt_cb,
- uint16_t sec_mask) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int RFCOMM_RemoveConnection(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int RFCOMM_RemoveServer(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t PORT_SetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void RFCOMM_ClearSecurityRecord(uint32_t scn) {
- mock_function_count_map[__func__]++;
-}
-void RFCOMM_Init(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_sdp.cc b/test/mock/mock_stack_sdp.cc
deleted file mode 100644
index 22252e8d6..000000000
--- a/test/mock/mock_stack_sdp.cc
+++ /dev/null
@@ -1,113 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- */
-
-#include <string.h>
-
-#include "bt_target.h"
-
-#include "sdp_api.h"
-
-#include "osi/include/osi.h"
-
-using bluetooth::Uuid;
-
-bool SDP_InitDiscoveryDb(tSDP_DISCOVERY_DB* p_db, uint32_t len,
- uint16_t num_uuid, const Uuid* p_uuid_list,
- uint16_t num_attr, uint16_t* p_attr_list) {
- return false;
-}
-
-bool SDP_CancelServiceSearch(tSDP_DISCOVERY_DB* p_db) { return false; }
-
-bool SDP_ServiceSearchRequest(const RawAddress& p_bd_addr,
- tSDP_DISCOVERY_DB* p_db,
- tSDP_DISC_CMPL_CB* p_cb) {
- return false;
-}
-
-bool SDP_ServiceSearchAttributeRequest(const RawAddress& p_bd_addr,
- tSDP_DISCOVERY_DB* p_db,
- tSDP_DISC_CMPL_CB* p_cb) {
- return false;
-}
-bool SDP_ServiceSearchAttributeRequest2(const RawAddress& p_bd_addr,
- tSDP_DISCOVERY_DB* p_db,
- tSDP_DISC_CMPL_CB2* p_cb2,
- void* user_data) {
- return false;
-}
-
-tSDP_DISC_ATTR* SDP_FindAttributeInRec(tSDP_DISC_REC* p_rec, uint16_t attr_id) {
- return (NULL);
-}
-
-bool SDP_FindServiceUUIDInRec(tSDP_DISC_REC* p_rec, Uuid* p_uuid) {
- return false;
-}
-
-bool SDP_FindServiceUUIDInRec_128bit(tSDP_DISC_REC* p_rec, Uuid* p_uuid) {
- return false;
-}
-
-tSDP_DISC_REC* SDP_FindServiceInDb(tSDP_DISCOVERY_DB* p_db,
- uint16_t service_uuid,
- tSDP_DISC_REC* p_start_rec) {
- return (NULL);
-}
-
-tSDP_DISC_REC* SDP_FindServiceInDb_128bit(tSDP_DISCOVERY_DB* p_db,
- tSDP_DISC_REC* p_start_rec) {
- return (NULL);
-}
-
-tSDP_DISC_REC* SDP_FindServiceUUIDInDb(tSDP_DISCOVERY_DB* p_db,
- const Uuid& uuid,
- tSDP_DISC_REC* p_start_rec) {
- return (NULL);
-}
-
-bool SDP_FindProtocolListElemInRec(tSDP_DISC_REC* p_rec, uint16_t layer_uuid,
- tSDP_PROTOCOL_ELEM* p_elem) {
- return (false);
-}
-
-bool SDP_FindProfileVersionInRec(tSDP_DISC_REC* p_rec, uint16_t profile_uuid,
- uint16_t* p_version) {
- return (false);
-}
-
-tSDP_STATUS SDP_DiDiscover(const RawAddress& remote_device,
- tSDP_DISCOVERY_DB* p_db, uint32_t len,
- tSDP_DISC_CMPL_CB* p_cb) {
- return SDP_SUCCESS;
-}
-
-uint8_t SDP_GetNumDiRecords(tSDP_DISCOVERY_DB* p_db) { return 0; }
-
-uint16_t SDP_GetDiRecord(uint8_t get_record_index,
- tSDP_DI_GET_RECORD* p_device_info,
- tSDP_DISCOVERY_DB* p_db) {
- return 0;
-}
-uint16_t SDP_SetLocalDiRecord(tSDP_DI_RECORD* p_device_info,
- uint32_t* p_handle) {
- return 0;
-}
-uint8_t SDP_SetTraceLevel(uint8_t new_level) { return 0; }
diff --git a/test/mock/mock_stack_sdp_db.cc b/test/mock/mock_stack_sdp_db.cc
deleted file mode 100644
index d2686cd1a..000000000
--- a/test/mock/mock_stack_sdp_db.cc
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:14
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <stdio.h>
-#include <string.h>
-#include "bt_common.h"
-#include "bt_target.h"
-#include "stack/include/sdp_api.h"
-#include "stack/sdp/sdpint.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool SDP_AddAdditionProtoLists(uint32_t handle, uint16_t num_elem,
- tSDP_PROTO_LIST_ELEM* p_proto_list) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SDP_AddAttribute(uint32_t handle, uint16_t attr_id, uint8_t attr_type,
- uint32_t attr_len, uint8_t* p_val) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SDP_AddLanguageBaseAttrIDList(uint32_t handle, uint16_t lang,
- uint16_t char_enc, uint16_t base_id) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SDP_AddProfileDescriptorList(uint32_t handle, uint16_t profile_uuid,
- uint16_t version) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SDP_AddProtocolList(uint32_t handle, uint16_t num_elem,
- tSDP_PROTOCOL_ELEM* p_elem_list) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SDP_AddSequence(uint32_t handle, uint16_t attr_id, uint16_t num_elem,
- uint8_t type[], uint8_t len[], uint8_t* p_val[]) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SDP_AddServiceClassIdList(uint32_t handle, uint16_t num_services,
- uint16_t* p_service_uuids) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SDP_AddUuidSequence(uint32_t handle, uint16_t attr_id, uint16_t num_uuids,
- uint16_t* p_uuids) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SDP_DeleteAttribute(uint32_t handle, uint16_t attr_id) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SDP_DeleteRecord(uint32_t handle) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tSDP_ATTRIBUTE* sdp_db_find_attr_in_rec(tSDP_RECORD* p_rec, uint16_t start_attr,
- uint16_t end_attr) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tSDP_RECORD* sdp_db_find_record(uint32_t handle) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-tSDP_RECORD* sdp_db_service_search(tSDP_RECORD* p_rec, tSDP_UUID_SEQ* p_seq) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-uint32_t SDP_CreateRecord(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
diff --git a/test/mock/mock_stack_sdp_main.cc b/test/mock/mock_stack_sdp_main.cc
deleted file mode 100644
index df95fd39c..000000000
--- a/test/mock/mock_stack_sdp_main.cc
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:5
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "bt_common.h"
-#include "bt_target.h"
-#include "hcidefs.h"
-#include "l2c_api.h"
-#include "l2cdefs.h"
-#include "osi/include/osi.h"
-#include "sdp_api.h"
-#include "stack/btm/btm_sec.h"
-#include "stack/sdp/sdpint.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-tCONN_CB* sdp_conn_originate(const RawAddress& p_bd_addr) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void sdp_conn_timer_timeout(void* data) { mock_function_count_map[__func__]++; }
-void sdp_disconnect(tCONN_CB* p_ccb, uint16_t reason) {
- mock_function_count_map[__func__]++;
-}
-void sdp_free(void) { mock_function_count_map[__func__]++; }
-void sdp_init(void) { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_smp_act.cc b/test/mock/mock_stack_smp_act.cc
deleted file mode 100644
index a7a25fb75..000000000
--- a/test/mock/mock_stack_smp_act.cc
+++ /dev/null
@@ -1,430 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:71
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-
-// Mock include file to share data between tests and mock
-#include "test/mock/mock_stack_smp_act.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-// Mocked internal structures, if any
-
-namespace test {
-namespace mock {
-namespace stack_smp_act {
-
-// Function state capture and return values, if needed
-struct smp_send_app_cback smp_send_app_cback;
-struct smp_send_pair_fail smp_send_pair_fail;
-struct smp_send_pair_req smp_send_pair_req;
-struct smp_send_pair_rsp smp_send_pair_rsp;
-struct smp_send_confirm smp_send_confirm;
-struct smp_send_init smp_send_init;
-struct smp_send_rand smp_send_rand;
-struct smp_send_pair_public_key smp_send_pair_public_key;
-struct smp_send_commitment smp_send_commitment;
-struct smp_send_dhkey_check smp_send_dhkey_check;
-struct smp_send_keypress_notification smp_send_keypress_notification;
-struct smp_send_enc_info smp_send_enc_info;
-struct smp_send_id_info smp_send_id_info;
-struct smp_send_csrk_info smp_send_csrk_info;
-struct smp_send_ltk_reply smp_send_ltk_reply;
-struct smp_proc_sec_req smp_proc_sec_req;
-struct smp_proc_sec_grant smp_proc_sec_grant;
-struct smp_proc_pair_fail smp_proc_pair_fail;
-struct smp_proc_pair_cmd smp_proc_pair_cmd;
-struct smp_proc_confirm smp_proc_confirm;
-struct smp_proc_init smp_proc_init;
-struct smp_proc_rand smp_proc_rand;
-struct smp_process_pairing_public_key smp_process_pairing_public_key;
-struct smp_process_pairing_commitment smp_process_pairing_commitment;
-struct smp_process_dhkey_check smp_process_dhkey_check;
-struct smp_process_keypress_notification smp_process_keypress_notification;
-struct smp_br_process_pairing_command smp_br_process_pairing_command;
-struct smp_br_process_security_grant smp_br_process_security_grant;
-struct smp_br_check_authorization_request smp_br_check_authorization_request;
-struct smp_br_select_next_key smp_br_select_next_key;
-struct smp_proc_enc_info smp_proc_enc_info;
-struct smp_proc_central_id smp_proc_central_id;
-struct smp_proc_id_info smp_proc_id_info;
-struct smp_proc_id_addr smp_proc_id_addr;
-struct smp_proc_srk_info smp_proc_srk_info;
-struct smp_proc_compare smp_proc_compare;
-struct smp_proc_sl_key smp_proc_sl_key;
-struct smp_start_enc smp_start_enc;
-struct smp_proc_discard smp_proc_discard;
-struct smp_enc_cmpl smp_enc_cmpl;
-struct smp_check_auth_req smp_check_auth_req;
-struct smp_key_pick_key smp_key_pick_key;
-struct smp_key_distribution smp_key_distribution;
-struct smp_decide_association_model smp_decide_association_model;
-struct smp_process_io_response smp_process_io_response;
-struct smp_br_process_peripheral_keys_response
- smp_br_process_peripheral_keys_response;
-struct smp_br_send_pair_response smp_br_send_pair_response;
-struct smp_pairing_cmpl smp_pairing_cmpl;
-struct smp_pair_terminate smp_pair_terminate;
-struct smp_idle_terminate smp_idle_terminate;
-struct smp_both_have_public_keys smp_both_have_public_keys;
-struct smp_start_secure_connection_phase1 smp_start_secure_connection_phase1;
-struct smp_process_local_nonce smp_process_local_nonce;
-struct smp_process_peer_nonce smp_process_peer_nonce;
-struct smp_match_dhkey_checks smp_match_dhkey_checks;
-struct smp_move_to_secure_connections_phase2
- smp_move_to_secure_connections_phase2;
-struct smp_phase_2_dhkey_checks_are_present
- smp_phase_2_dhkey_checks_are_present;
-struct smp_wait_for_both_public_keys smp_wait_for_both_public_keys;
-struct smp_start_passkey_verification smp_start_passkey_verification;
-struct smp_process_secure_connection_oob_data
- smp_process_secure_connection_oob_data;
-struct smp_set_local_oob_keys smp_set_local_oob_keys;
-struct smp_set_local_oob_random_commitment smp_set_local_oob_random_commitment;
-struct smp_link_encrypted smp_link_encrypted;
-struct smp_cancel_start_encryption_attempt smp_cancel_start_encryption_attempt;
-struct smp_proc_ltk_request smp_proc_ltk_request;
-struct smp_process_secure_connection_long_term_key
- smp_process_secure_connection_long_term_key;
-struct smp_set_derive_link_key smp_set_derive_link_key;
-struct smp_derive_link_key_from_long_term_key
- smp_derive_link_key_from_long_term_key;
-struct smp_br_process_link_key smp_br_process_link_key;
-struct smp_key_distribution_by_transport smp_key_distribution_by_transport;
-struct smp_br_pairing_complete smp_br_pairing_complete;
-
-} // namespace stack_smp_act
-} // namespace mock
-} // namespace test
-
-// Mocked functions, if any
-void smp_send_app_cback(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_app_cback(p_cb, p_data);
-}
-void smp_send_pair_fail(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_pair_fail(p_cb, p_data);
-}
-void smp_send_pair_req(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_pair_req(p_cb, p_data);
-}
-void smp_send_pair_rsp(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_pair_rsp(p_cb, p_data);
-}
-void smp_send_confirm(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_confirm(p_cb, p_data);
-}
-void smp_send_init(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_init(p_cb, p_data);
-}
-void smp_send_rand(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_rand(p_cb, p_data);
-}
-void smp_send_pair_public_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_pair_public_key(p_cb, p_data);
-}
-void smp_send_commitment(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_commitment(p_cb, p_data);
-}
-void smp_send_dhkey_check(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_dhkey_check(p_cb, p_data);
-}
-void smp_send_keypress_notification(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_keypress_notification(p_cb, p_data);
-}
-void smp_send_enc_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_enc_info(p_cb, p_data);
-}
-void smp_send_id_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_id_info(p_cb, p_data);
-}
-void smp_send_csrk_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_csrk_info(p_cb, p_data);
-}
-void smp_send_ltk_reply(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_send_ltk_reply(p_cb, p_data);
-}
-void smp_proc_sec_req(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_sec_req(p_cb, p_data);
-}
-void smp_proc_sec_grant(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_sec_grant(p_cb, p_data);
-}
-void smp_proc_pair_fail(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_pair_fail(p_cb, p_data);
-}
-void smp_proc_pair_cmd(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_pair_cmd(p_cb, p_data);
-}
-void smp_proc_confirm(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_confirm(p_cb, p_data);
-}
-void smp_proc_init(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_init(p_cb, p_data);
-}
-void smp_proc_rand(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_rand(p_cb, p_data);
-}
-void smp_process_pairing_public_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_process_pairing_public_key(p_cb, p_data);
-}
-void smp_process_pairing_commitment(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_process_pairing_commitment(p_cb, p_data);
-}
-void smp_process_dhkey_check(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_process_dhkey_check(p_cb, p_data);
-}
-void smp_process_keypress_notification(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_process_keypress_notification(p_cb, p_data);
-}
-void smp_br_process_pairing_command(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_br_process_pairing_command(p_cb, p_data);
-}
-void smp_br_process_security_grant(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_br_process_security_grant(p_cb, p_data);
-}
-void smp_br_check_authorization_request(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_br_check_authorization_request(p_cb, p_data);
-}
-void smp_br_select_next_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_br_select_next_key(p_cb, p_data);
-}
-void smp_proc_enc_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_enc_info(p_cb, p_data);
-}
-void smp_proc_central_id(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_central_id(p_cb, p_data);
-}
-void smp_proc_id_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_id_info(p_cb, p_data);
-}
-void smp_proc_id_addr(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_id_addr(p_cb, p_data);
-}
-void smp_proc_srk_info(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_srk_info(p_cb, p_data);
-}
-void smp_proc_compare(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_compare(p_cb, p_data);
-}
-void smp_proc_sl_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_sl_key(p_cb, p_data);
-}
-void smp_start_enc(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_start_enc(p_cb, p_data);
-}
-void smp_proc_discard(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_proc_discard(p_cb, p_data);
-}
-void smp_enc_cmpl(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_enc_cmpl(p_cb, p_data);
-}
-void smp_check_auth_req(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_check_auth_req(p_cb, p_data);
-}
-void smp_key_pick_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_key_pick_key(p_cb, p_data);
-}
-void smp_key_distribution(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_key_distribution(p_cb, p_data);
-}
-void smp_decide_association_model(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_decide_association_model(p_cb, p_data);
-}
-void smp_process_io_response(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_process_io_response(p_cb, p_data);
-}
-void smp_br_process_peripheral_keys_response(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_br_process_peripheral_keys_response(p_cb,
- p_data);
-}
-void smp_br_send_pair_response(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_br_send_pair_response(p_cb, p_data);
-}
-void smp_pairing_cmpl(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_pairing_cmpl(p_cb, p_data);
-}
-void smp_pair_terminate(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_pair_terminate(p_cb, p_data);
-}
-void smp_idle_terminate(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_idle_terminate(p_cb, p_data);
-}
-void smp_both_have_public_keys(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_both_have_public_keys(p_cb, p_data);
-}
-void smp_start_secure_connection_phase1(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_start_secure_connection_phase1(p_cb, p_data);
-}
-void smp_process_local_nonce(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_process_local_nonce(p_cb, p_data);
-}
-void smp_process_peer_nonce(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_process_peer_nonce(p_cb, p_data);
-}
-void smp_match_dhkey_checks(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_match_dhkey_checks(p_cb, p_data);
-}
-void smp_move_to_secure_connections_phase2(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_move_to_secure_connections_phase2(p_cb,
- p_data);
-}
-void smp_phase_2_dhkey_checks_are_present(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_phase_2_dhkey_checks_are_present(p_cb, p_data);
-}
-void smp_wait_for_both_public_keys(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_wait_for_both_public_keys(p_cb, p_data);
-}
-void smp_start_passkey_verification(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_start_passkey_verification(p_cb, p_data);
-}
-void smp_process_secure_connection_oob_data(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_process_secure_connection_oob_data(p_cb,
- p_data);
-}
-void smp_set_local_oob_keys(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_set_local_oob_keys(p_cb, p_data);
-}
-void smp_set_local_oob_random_commitment(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_set_local_oob_random_commitment(p_cb, p_data);
-}
-void smp_link_encrypted(const RawAddress& bda, uint8_t encr_enable) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_link_encrypted(bda, encr_enable);
-}
-void smp_cancel_start_encryption_attempt() {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_cancel_start_encryption_attempt();
-}
-bool smp_proc_ltk_request(const RawAddress& bda) {
- mock_function_count_map[__func__]++;
- return test::mock::stack_smp_act::smp_proc_ltk_request(bda);
-}
-void smp_process_secure_connection_long_term_key(void) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_process_secure_connection_long_term_key();
-}
-void smp_set_derive_link_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_set_derive_link_key(p_cb, p_data);
-}
-void smp_derive_link_key_from_long_term_key(tSMP_CB* p_cb,
- tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_derive_link_key_from_long_term_key(p_cb,
- p_data);
-}
-void smp_br_process_link_key(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_br_process_link_key(p_cb, p_data);
-}
-void smp_key_distribution_by_transport(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_key_distribution_by_transport(p_cb, p_data);
-}
-void smp_br_pairing_complete(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {
- mock_function_count_map[__func__]++;
- test::mock::stack_smp_act::smp_br_pairing_complete(p_cb, p_data);
-}
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_smp_act.h b/test/mock/mock_stack_smp_act.h
deleted file mode 100644
index 2265902e8..000000000
--- a/test/mock/mock_stack_smp_act.h
+++ /dev/null
@@ -1,707 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:71
- *
- * mockcify.pl ver 0.2
- */
-
-#include <cstdint>
-#include <functional>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-// Original included files, if any
-// NOTE: Since this is a mock file with mock definitions some number of
-// include files may not be required. The include-what-you-use
-// still applies, but crafting proper inclusion is out of scope
-// for this effort. This compilation unit may compile as-is, or
-// may need attention to prune the inclusion set.
-#include "btif/include/btif_api.h"
-#include "stack/smp/smp_int.h"
-#include "types/raw_address.h"
-
-// Mocked compile conditionals, if any
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-namespace test {
-namespace mock {
-namespace stack_smp_act {
-
-// Shared state between mocked functions and tests
-// Name: smp_send_app_cback
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_app_cback {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_app_cback smp_send_app_cback;
-// Name: smp_send_pair_fail
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_pair_fail {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_pair_fail smp_send_pair_fail;
-// Name: smp_send_pair_req
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_pair_req {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_pair_req smp_send_pair_req;
-// Name: smp_send_pair_rsp
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_pair_rsp {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_pair_rsp smp_send_pair_rsp;
-// Name: smp_send_confirm
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_confirm {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_confirm smp_send_confirm;
-// Name: smp_send_init
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_init {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_init smp_send_init;
-// Name: smp_send_rand
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_rand {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_rand smp_send_rand;
-// Name: smp_send_pair_public_key
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_pair_public_key {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_pair_public_key smp_send_pair_public_key;
-// Name: smp_send_commitment
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_commitment {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_commitment smp_send_commitment;
-// Name: smp_send_dhkey_check
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_dhkey_check {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_dhkey_check smp_send_dhkey_check;
-// Name: smp_send_keypress_notification
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_keypress_notification {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_keypress_notification smp_send_keypress_notification;
-// Name: smp_send_enc_info
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_enc_info {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_enc_info smp_send_enc_info;
-// Name: smp_send_id_info
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_id_info {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_id_info smp_send_id_info;
-// Name: smp_send_csrk_info
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_csrk_info {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_csrk_info smp_send_csrk_info;
-// Name: smp_send_ltk_reply
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_send_ltk_reply {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_send_ltk_reply smp_send_ltk_reply;
-// Name: smp_proc_sec_req
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_sec_req {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_sec_req smp_proc_sec_req;
-// Name: smp_proc_sec_grant
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_sec_grant {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_sec_grant smp_proc_sec_grant;
-// Name: smp_proc_pair_fail
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_pair_fail {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_pair_fail smp_proc_pair_fail;
-// Name: smp_proc_pair_cmd
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_pair_cmd {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_pair_cmd smp_proc_pair_cmd;
-// Name: smp_proc_confirm
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_confirm {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_confirm smp_proc_confirm;
-// Name: smp_proc_init
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_init {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_init smp_proc_init;
-// Name: smp_proc_rand
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_rand {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_rand smp_proc_rand;
-// Name: smp_process_pairing_public_key
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_process_pairing_public_key {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_process_pairing_public_key smp_process_pairing_public_key;
-// Name: smp_process_pairing_commitment
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_process_pairing_commitment {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_process_pairing_commitment smp_process_pairing_commitment;
-// Name: smp_process_dhkey_check
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_process_dhkey_check {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_process_dhkey_check smp_process_dhkey_check;
-// Name: smp_process_keypress_notification
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_process_keypress_notification {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_process_keypress_notification
- smp_process_keypress_notification;
-// Name: smp_br_process_pairing_command
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_br_process_pairing_command {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_br_process_pairing_command smp_br_process_pairing_command;
-// Name: smp_br_process_security_grant
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_br_process_security_grant {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_br_process_security_grant smp_br_process_security_grant;
-// Name: smp_br_check_authorization_request
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_br_check_authorization_request {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_br_check_authorization_request
- smp_br_check_authorization_request;
-// Name: smp_br_select_next_key
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_br_select_next_key {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_br_select_next_key smp_br_select_next_key;
-// Name: smp_proc_enc_info
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_enc_info {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_enc_info smp_proc_enc_info;
-// Name: smp_proc_central_id
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_central_id {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_central_id smp_proc_central_id;
-// Name: smp_proc_id_info
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_id_info {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_id_info smp_proc_id_info;
-// Name: smp_proc_id_addr
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_id_addr {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_id_addr smp_proc_id_addr;
-// Name: smp_proc_srk_info
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_srk_info {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_srk_info smp_proc_srk_info;
-// Name: smp_proc_compare
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_compare {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_compare smp_proc_compare;
-// Name: smp_proc_sl_key
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_sl_key {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_sl_key smp_proc_sl_key;
-// Name: smp_start_enc
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_start_enc {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_start_enc smp_start_enc;
-// Name: smp_proc_discard
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_proc_discard {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_proc_discard smp_proc_discard;
-// Name: smp_enc_cmpl
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_enc_cmpl {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_enc_cmpl smp_enc_cmpl;
-// Name: smp_check_auth_req
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_check_auth_req {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_check_auth_req smp_check_auth_req;
-// Name: smp_key_pick_key
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_key_pick_key {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_key_pick_key smp_key_pick_key;
-// Name: smp_key_distribution
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_key_distribution {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_key_distribution smp_key_distribution;
-// Name: smp_decide_association_model
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_decide_association_model {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_decide_association_model smp_decide_association_model;
-// Name: smp_process_io_response
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_process_io_response {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_process_io_response smp_process_io_response;
-// Name: smp_br_process_peripheral_keys_response
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_br_process_peripheral_keys_response {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_br_process_peripheral_keys_response
- smp_br_process_peripheral_keys_response;
-// Name: smp_br_send_pair_response
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_br_send_pair_response {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_br_send_pair_response smp_br_send_pair_response;
-// Name: smp_pairing_cmpl
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_pairing_cmpl {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_pairing_cmpl smp_pairing_cmpl;
-// Name: smp_pair_terminate
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_pair_terminate {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_pair_terminate smp_pair_terminate;
-// Name: smp_idle_terminate
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_idle_terminate {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_idle_terminate smp_idle_terminate;
-// Name: smp_both_have_public_keys
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_both_have_public_keys {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_both_have_public_keys smp_both_have_public_keys;
-// Name: smp_start_secure_connection_phase1
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_start_secure_connection_phase1 {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_start_secure_connection_phase1
- smp_start_secure_connection_phase1;
-// Name: smp_process_local_nonce
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_process_local_nonce {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_process_local_nonce smp_process_local_nonce;
-// Name: smp_process_peer_nonce
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_process_peer_nonce {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_process_peer_nonce smp_process_peer_nonce;
-// Name: smp_match_dhkey_checks
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_match_dhkey_checks {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_match_dhkey_checks smp_match_dhkey_checks;
-// Name: smp_move_to_secure_connections_phase2
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_move_to_secure_connections_phase2 {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_move_to_secure_connections_phase2
- smp_move_to_secure_connections_phase2;
-// Name: smp_phase_2_dhkey_checks_are_present
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_phase_2_dhkey_checks_are_present {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_phase_2_dhkey_checks_are_present
- smp_phase_2_dhkey_checks_are_present;
-// Name: smp_wait_for_both_public_keys
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_wait_for_both_public_keys {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_wait_for_both_public_keys smp_wait_for_both_public_keys;
-// Name: smp_start_passkey_verification
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_start_passkey_verification {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_start_passkey_verification smp_start_passkey_verification;
-// Name: smp_process_secure_connection_oob_data
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_process_secure_connection_oob_data {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_process_secure_connection_oob_data
- smp_process_secure_connection_oob_data;
-// Name: smp_set_local_oob_keys
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_set_local_oob_keys {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_set_local_oob_keys smp_set_local_oob_keys;
-// Name: smp_set_local_oob_random_commitment
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_set_local_oob_random_commitment {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_set_local_oob_random_commitment
- smp_set_local_oob_random_commitment;
-// Name: smp_link_encrypted
-// Params: const RawAddress& bda, uint8_t encr_enable
-// Returns: void
-struct smp_link_encrypted {
- std::function<void(const RawAddress& bda, uint8_t encr_enable)> body{
- [](const RawAddress& bda, uint8_t encr_enable) {}};
- void operator()(const RawAddress& bda, uint8_t encr_enable) {
- body(bda, encr_enable);
- };
-};
-extern struct smp_link_encrypted smp_link_encrypted;
-// Name: smp_cancel_start_encryption_attempt
-// Params:
-// Returns: void
-struct smp_cancel_start_encryption_attempt {
- std::function<void()> body{[]() {}};
- void operator()() { body(); };
-};
-extern struct smp_cancel_start_encryption_attempt
- smp_cancel_start_encryption_attempt;
-// Name: smp_proc_ltk_request
-// Params: const RawAddress& bda
-// Returns: bool
-struct smp_proc_ltk_request {
- std::function<bool(const RawAddress& bda)> body{
- [](const RawAddress& bda) { return false; }};
- bool operator()(const RawAddress& bda) { return body(bda); };
-};
-extern struct smp_proc_ltk_request smp_proc_ltk_request;
-// Name: smp_process_secure_connection_long_term_key
-// Params: void
-// Returns: void
-struct smp_process_secure_connection_long_term_key {
- std::function<void(void)> body{[](void) {}};
- void operator()(void) { body(); };
-};
-extern struct smp_process_secure_connection_long_term_key
- smp_process_secure_connection_long_term_key;
-// Name: smp_set_derive_link_key
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_set_derive_link_key {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_set_derive_link_key smp_set_derive_link_key;
-// Name: smp_derive_link_key_from_long_term_key
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_derive_link_key_from_long_term_key {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_derive_link_key_from_long_term_key
- smp_derive_link_key_from_long_term_key;
-// Name: smp_br_process_link_key
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_br_process_link_key {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_br_process_link_key smp_br_process_link_key;
-// Name: smp_key_distribution_by_transport
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_key_distribution_by_transport {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_key_distribution_by_transport
- smp_key_distribution_by_transport;
-// Name: smp_br_pairing_complete
-// Params: tSMP_CB* p_cb, tSMP_INT_DATA* p_data
-// Returns: void
-struct smp_br_pairing_complete {
- std::function<void(tSMP_CB* p_cb, tSMP_INT_DATA* p_data)> body{
- [](tSMP_CB* p_cb, tSMP_INT_DATA* p_data) {}};
- void operator()(tSMP_CB* p_cb, tSMP_INT_DATA* p_data) { body(p_cb, p_data); };
-};
-extern struct smp_br_pairing_complete smp_br_pairing_complete;
-
-} // namespace stack_smp_act
-} // namespace mock
-} // namespace test
-
-// END mockcify generation
diff --git a/test/mock/mock_stack_smp_api.cc b/test/mock/mock_stack_smp_api.cc
deleted file mode 100644
index 6d6335a47..000000000
--- a/test/mock/mock_stack_smp_api.cc
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:11
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <string.h>
-#include "bt_target.h"
-#include "hcimsgs.h"
-#include "main/shim/shim.h"
-#include "stack/btm/btm_dev.h"
-#include "stack/include/l2c_api.h"
-#include "stack/include/l2cdefs.h"
-#include "stack/include/smp_api.h"
-#include "stack/smp/smp_int.h"
-#include "stack_config.h"
-#include "utils/include/bt_utils.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool SMP_PairCancel(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool SMP_Register(tSMP_CALLBACK* p_cback) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tSMP_STATUS SMP_BR_PairWith(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return SMP_SUCCESS;
-}
-tSMP_STATUS SMP_Pair(const RawAddress& bd_addr) {
- mock_function_count_map[__func__]++;
- return SMP_SUCCESS;
-}
-uint8_t SMP_SetTraceLevel(uint8_t new_level) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void SMP_ConfirmReply(const RawAddress& bd_addr, uint8_t res) {
- mock_function_count_map[__func__]++;
-}
-void SMP_Init(void) { mock_function_count_map[__func__]++; }
-void SMP_OobDataReply(const RawAddress& bd_addr, tSMP_STATUS res, uint8_t len,
- uint8_t* p_data) {
- mock_function_count_map[__func__]++;
-}
-void SMP_PasskeyReply(const RawAddress& bd_addr, uint8_t res,
- uint32_t passkey) {
- mock_function_count_map[__func__]++;
-}
-void SMP_SecureConnectionOobDataReply(uint8_t* p_data) {
- mock_function_count_map[__func__]++;
-}
-void SMP_SecurityGrant(const RawAddress& bd_addr, tSMP_STATUS res) {
- mock_function_count_map[__func__]++;
-}
-
-void SMP_CrLocScOobData() { mock_function_count_map[__func__]++; }
-
-void SMP_ClearLocScOobData() { mock_function_count_map[__func__]++; }
diff --git a/test/mock/mock_stack_srvc_dis.cc b/test/mock/mock_stack_srvc_dis.cc
deleted file mode 100644
index 1885802f6..000000000
--- a/test/mock/mock_stack_srvc_dis.cc
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:10
- */
-
-#include <cstdint>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "stack/include/srvc_api.h"
-#include "stack/srvc/srvc_eng_int.h"
-#include "types/raw_address.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool DIS_ReadDISInfo(const RawAddress& peer_bda, tDIS_READ_CBACK* p_cback,
- tDIS_ATTR_MASK mask) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool dis_gatt_c_read_dis_req(uint16_t conn_id) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool dis_valid_handle_range(uint16_t handle) {
- mock_function_count_map[__func__]++;
- return false;
-}
-tDIS_STATUS DIS_SrInit(tDIS_ATTR_MASK dis_attr_mask) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-tDIS_STATUS DIS_SrUpdate(tDIS_ATTR_BIT dis_attr_bit, tDIS_ATTR* p_info) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t dis_read_attr_value(UNUSED_ATTR uint8_t clcb_idx, uint16_t handle,
- tGATT_VALUE* p_value, bool is_long,
- tGATT_STATUS* p_status) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint8_t dis_write_attr_value(UNUSED_ATTR tGATT_WRITE_REQ* p_data,
- tGATT_STATUS* p_status) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void dis_c_cmpl_cback(tSRVC_CLCB* p_clcb, tGATTC_OPTYPE op, tGATT_STATUS status,
- tGATT_CL_COMPLETE* p_data) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_system_libfmq_eventflag.cc b/test/mock/mock_system_libfmq_eventflag.cc
deleted file mode 100644
index 8bdcb5687..000000000
--- a/test/mock/mock_system_libfmq_eventflag.cc
+++ /dev/null
@@ -1,99 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:11
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <fmq/EventFlag.h>
-
-using namespace android;
-using namespace android::hardware;
-
-namespace android {
-namespace hardware {
-namespace details {
-
-void logError(const std::string& message) {}
-
-} // namespace details
-} // namespace hardware
-} // namespace android
-
-#if 0
-#include <linux/futex.h>
-#include <string.h>
-#include <sys/mman.h>
-#include <sys/syscall.h>
-#include <unistd.h>
-#include <utils/Log.h>
-#include <utils/SystemClock.h>
-#include <new>
-#endif
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-EventFlag::EventFlag(int fd, off_t offset, status_t* status) {
- mock_function_count_map[__func__]++;
-}
-EventFlag::EventFlag(std::atomic<uint32_t>* fwAddr, status_t* status) {
- mock_function_count_map[__func__]++;
-}
-EventFlag::~EventFlag() { mock_function_count_map[__func__]++; }
-status_t EventFlag::createEventFlag(int fd, off_t offset, EventFlag** flag) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-status_t EventFlag::createEventFlag(std::atomic<uint32_t>* fwAddr,
- EventFlag** flag) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-status_t EventFlag::deleteEventFlag(EventFlag** evFlag) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-status_t EventFlag::unmapEventFlagWord(std::atomic<uint32_t>* efWordPtr,
- bool* efWordNeedsUnmapping) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-status_t EventFlag::wait(uint32_t bitmask, uint32_t* efState,
- int64_t timeoutNanoSeconds, bool retry) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-status_t EventFlag::waitHelper(uint32_t bitmask, uint32_t* efState,
- int64_t timeoutNanoSeconds) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-status_t EventFlag::wake(uint32_t bitmask) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void EventFlag::addNanosecondsToCurrentTime(int64_t nanoSeconds,
- struct timespec* waitTime) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/mock/mock_udrv_ulinux_uipc.cc b/test/mock/mock_udrv_ulinux_uipc.cc
deleted file mode 100644
index f32f3998e..000000000
--- a/test/mock/mock_udrv_ulinux_uipc.cc
+++ /dev/null
@@ -1,100 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- * Functions generated:12
- */
-
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include <errno.h>
-#include <fcntl.h>
-#include <signal.h>
-#include <stdio.h>
-#include <stdlib.h>
-#include <string.h>
-#include <sys/mman.h>
-#include <sys/poll.h>
-#include <sys/prctl.h>
-#include <sys/select.h>
-#include <sys/socket.h>
-#include <sys/stat.h>
-#include <sys/un.h>
-#include <unistd.h>
-#include <mutex>
-#include <set>
-#include "audio_a2dp_hw/include/audio_a2dp_hw.h"
-#include "bt_common.h"
-#include "bt_types.h"
-#include "bt_utils.h"
-#include "osi/include/osi.h"
-#include "osi/include/socket_utils/sockets.h"
-#include "uipc.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-bool UIPC_Open(tUIPC_STATE& uipc, tUIPC_CH_ID ch_id, tUIPC_RCV_CBACK* p_cback,
- const char* socket_path) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool UIPC_Send(tUIPC_STATE& uipc, tUIPC_CH_ID ch_id,
- UNUSED_ATTR uint16_t msg_evt, const uint8_t* p_buf,
- uint16_t msglen) {
- mock_function_count_map[__func__]++;
- return false;
-}
-int uipc_start_main_server_thread(tUIPC_STATE& uipc) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::unique_ptr<tUIPC_STATE> UIPC_Init() {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-const char* dump_uipc_event(tUIPC_EVENT event) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-uint32_t UIPC_Read(tUIPC_STATE& uipc, tUIPC_CH_ID ch_id,
- UNUSED_ATTR uint16_t* p_msg_evt, uint8_t* p_buf,
- uint32_t len) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-bool UIPC_Ioctl(tUIPC_STATE& uipc, tUIPC_CH_ID ch_id, uint32_t request,
- void* param) {
- mock_function_count_map[__func__]++;
- return false;
-}
-void UIPC_Close(tUIPC_STATE& uipc, tUIPC_CH_ID ch_id) {
- mock_function_count_map[__func__]++;
-}
-void uipc_close_locked(tUIPC_STATE& uipc, tUIPC_CH_ID ch_id) {
- mock_function_count_map[__func__]++;
-}
-void uipc_main_cleanup(tUIPC_STATE& uipc) {
- mock_function_count_map[__func__]++;
-}
-void uipc_stop_main_server_thread(tUIPC_STATE& uipc) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/rootcanal/Android.bp b/test/rootcanal/Android.bp
index ada32214b..916b53c00 100644
--- a/test/rootcanal/Android.bp
+++ b/test/rootcanal/Android.bp
@@ -13,18 +13,8 @@
// See the License for the specific language governing permissions and
// limitations under the License.
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_binary {
name: "android.hardware.bluetooth@1.1-service.sim",
- defaults: ["gd_defaults"],
proprietary: true,
relative_install_path: "hw",
srcs: [
@@ -54,14 +44,13 @@ cc_binary {
generated_headers: [
"RootCanalGeneratedPackets_h",
"BluetoothGeneratedPackets_h",
- "libbt_init_flags_bridge_header",
],
static_libs: [
"android.hardware.bluetooth-async",
"android.hardware.bluetooth-hci",
"libbt-rootcanal",
"libbt-rootcanal-types",
- "libscriptedbeaconpayload-protos-lite",
+ "libscriptedbeaconpayload-protos-lite",
],
include_dirs: [
"system/bt",
@@ -75,7 +64,6 @@ cc_binary {
cc_library_shared {
name: "android.hardware.bluetooth@1.1-impl-sim",
- defaults: ["gd_defaults"],
proprietary: true,
relative_install_path: "hw",
srcs: [
@@ -103,7 +91,6 @@ cc_library_shared {
generated_headers: [
"RootCanalGeneratedPackets_h",
"BluetoothGeneratedPackets_h",
- "libbt_init_flags_bridge_header",
],
static_libs: [
"android.hardware.bluetooth-async",
diff --git a/test/rootcanal/bluetooth_hci.cc b/test/rootcanal/bluetooth_hci.cc
index ca353c1a6..963f1a7ca 100644
--- a/test/rootcanal/bluetooth_hci.cc
+++ b/test/rootcanal/bluetooth_hci.cc
@@ -41,7 +41,7 @@ namespace {
bool BtTestConsoleEnabled() {
// Assume enabled by default.
- return property_get_bool("vendor.bt.rootcanal_test_console", true);
+ return property_get_bool("bt.rootcanal_test_console", true);
}
} // namespace
@@ -97,14 +97,14 @@ Return<void> BluetoothHci::initialize_impl(
test_channel_transport_.RegisterCommandHandler(
[this](const std::string& name, const std::vector<std::string>& args) {
async_manager_.ExecAsync(
- user_id_, std::chrono::milliseconds(0),
+ std::chrono::milliseconds(0),
[this, name, args]() { test_channel_.HandleCommand(name, args); });
});
controller_ = std::make_shared<DualModeController>();
char mac_property[PROPERTY_VALUE_MAX] = "";
- property_get("vendor.bt.rootcanal_mac_address", mac_property, "3C:5A:B4:01:02:03");
+ property_get("bt.rootcanal_mac_address", mac_property, "3C:5A:B4:01:02:03");
controller_->Initialize({"dmc", std::string(mac_property)});
controller_->RegisterEventChannel(
@@ -136,7 +136,7 @@ Return<void> BluetoothHci::initialize_impl(
controller_->RegisterScoChannel(
[this, cb](std::shared_ptr<std::vector<uint8_t>> packet) {
hidl_vec<uint8_t> sco_packet(packet->begin(), packet->end());
- auto ret = cb->scoDataReceived(sco_packet);
+ auto ret = cb->aclDataReceived(sco_packet);
if (!ret.isOk()) {
LOG_ERROR("Error sending sco callback");
if (!death_recipient_->getHasDied()) {
@@ -163,19 +163,20 @@ Return<void> BluetoothHci::initialize_impl(
controller_->RegisterTaskScheduler(
[this](std::chrono::milliseconds delay, const TaskCallback& task) {
- return async_manager_.ExecAsync(user_id_, delay, task);
+ return async_manager_.ExecAsync(delay, task);
});
controller_->RegisterPeriodicTaskScheduler(
[this](std::chrono::milliseconds delay, std::chrono::milliseconds period,
const TaskCallback& task) {
- return async_manager_.ExecAsyncPeriodically(user_id_, delay, period,
- task);
+ return async_manager_.ExecAsyncPeriodically(delay, period, task);
});
controller_->RegisterTaskCancel(
[this](AsyncTaskId task) { async_manager_.CancelAsyncTask(task); });
+ test_model_.Reset();
+
// Add the controller as a device in the model.
size_t controller_index = test_model_.Add(controller_);
size_t low_energy_phy_index =
@@ -235,51 +236,42 @@ Return<void> BluetoothHci::initialize_impl(
Return<void> BluetoothHci::close() {
LOG_INFO("%s", __func__);
- test_model_.Reset();
return Void();
}
Return<void> BluetoothHci::sendHciCommand(const hidl_vec<uint8_t>& packet) {
- async_manager_.ExecAsync(user_id_, std::chrono::milliseconds(0),
- [this, packet]() {
- std::shared_ptr<std::vector<uint8_t>> packet_copy =
- std::shared_ptr<std::vector<uint8_t>>(
- new std::vector<uint8_t>(packet));
- controller_->HandleCommand(packet_copy);
- });
+ async_manager_.ExecAsync(std::chrono::milliseconds(0), [this, packet]() {
+ std::shared_ptr<std::vector<uint8_t>> packet_copy =
+ std::shared_ptr<std::vector<uint8_t>>(new std::vector<uint8_t>(packet));
+ controller_->HandleCommand(packet_copy);
+ });
return Void();
}
Return<void> BluetoothHci::sendAclData(const hidl_vec<uint8_t>& packet) {
- async_manager_.ExecAsync(user_id_, std::chrono::milliseconds(0),
- [this, packet]() {
- std::shared_ptr<std::vector<uint8_t>> packet_copy =
- std::shared_ptr<std::vector<uint8_t>>(
- new std::vector<uint8_t>(packet));
- controller_->HandleAcl(packet_copy);
- });
+ async_manager_.ExecAsync(std::chrono::milliseconds(0), [this, packet]() {
+ std::shared_ptr<std::vector<uint8_t>> packet_copy =
+ std::shared_ptr<std::vector<uint8_t>>(new std::vector<uint8_t>(packet));
+ controller_->HandleAcl(packet_copy);
+ });
return Void();
}
Return<void> BluetoothHci::sendScoData(const hidl_vec<uint8_t>& packet) {
- async_manager_.ExecAsync(user_id_, std::chrono::milliseconds(0),
- [this, packet]() {
- std::shared_ptr<std::vector<uint8_t>> packet_copy =
- std::shared_ptr<std::vector<uint8_t>>(
- new std::vector<uint8_t>(packet));
- controller_->HandleSco(packet_copy);
- });
+ async_manager_.ExecAsync(std::chrono::milliseconds(0), [this, packet]() {
+ std::shared_ptr<std::vector<uint8_t>> packet_copy =
+ std::shared_ptr<std::vector<uint8_t>>(new std::vector<uint8_t>(packet));
+ controller_->HandleSco(packet_copy);
+ });
return Void();
}
Return<void> BluetoothHci::sendIsoData(const hidl_vec<uint8_t>& packet) {
- async_manager_.ExecAsync(user_id_, std::chrono::milliseconds(0),
- [this, packet]() {
- std::shared_ptr<std::vector<uint8_t>> packet_copy =
- std::shared_ptr<std::vector<uint8_t>>(
- new std::vector<uint8_t>(packet));
- controller_->HandleIso(packet_copy);
- });
+ async_manager_.ExecAsync(std::chrono::milliseconds(0), [this, packet]() {
+ std::shared_ptr<std::vector<uint8_t>> packet_copy =
+ std::shared_ptr<std::vector<uint8_t>>(new std::vector<uint8_t>(packet));
+ controller_->HandleIso(packet_copy);
+ });
return Void();
}
diff --git a/test/rootcanal/bluetooth_hci.h b/test/rootcanal/bluetooth_hci.h
index c46a1e177..99eda9f8f 100644
--- a/test/rootcanal/bluetooth_hci.h
+++ b/test/rootcanal/bluetooth_hci.h
@@ -86,33 +86,19 @@ class BluetoothHci : public IBluetoothHci {
test_vendor_lib::TestChannelTransport remote_hci_transport_;
test_vendor_lib::TestChannelTransport remote_link_layer_transport_;
- test_vendor_lib::AsyncUserId user_id_ = async_manager_.GetNextUserId();
test_vendor_lib::TestModel test_model_{
- [this]() { return async_manager_.GetNextUserId(); },
- [this](test_vendor_lib::AsyncUserId user_id,
- std::chrono::milliseconds delay,
- const test_vendor_lib::TaskCallback& task) {
- return async_manager_.ExecAsync(user_id, delay, task);
+ [this](std::chrono::milliseconds delay, const test_vendor_lib::TaskCallback& task) {
+ return async_manager_.ExecAsync(delay, task);
},
- [this](test_vendor_lib::AsyncUserId user_id,
- std::chrono::milliseconds delay, std::chrono::milliseconds period,
+ [this](std::chrono::milliseconds delay, std::chrono::milliseconds period,
const test_vendor_lib::TaskCallback& task) {
- return async_manager_.ExecAsyncPeriodically(user_id, delay, period,
- task);
- },
-
- [this](test_vendor_lib::AsyncUserId user_id) {
- async_manager_.CancelAsyncTasksFromUser(user_id);
+ return async_manager_.ExecAsyncPeriodically(delay, period, task);
},
- [this](test_vendor_lib::AsyncTaskId task) {
- async_manager_.CancelAsyncTask(task);
- },
+ [this](test_vendor_lib::AsyncTaskId task) { async_manager_.CancelAsyncTask(task); },
- [this](const std::string& server, int port) {
- return ConnectToRemoteServer(server, port);
- }};
+ [this](const std::string& server, int port) { return ConnectToRemoteServer(server, port); }};
test_vendor_lib::TestCommandHandler test_channel_{test_model_};
};
diff --git a/test/run_host_unit_tests.py b/test/run_host_unit_tests.py
index 4a17e2332..5ef34f732 100755
--- a/test/run_host_unit_tests.py
+++ b/test/run_host_unit_tests.py
@@ -26,7 +26,6 @@ HOST_TESTS = [
'net_test_avrcp',
'net_test_btcore',
'net_test_types',
- 'net_test_btm_iso',
'net_test_btpackets',
]
@@ -53,7 +52,8 @@ def get_output_from_command(cmd):
try:
return subprocess.check_output(cmd).strip()
except subprocess.CalledProcessError as e:
- print 'Failed to call {cmd}, return code {code}'.format(cmd=cmd, code=e.returncode)
+ print 'Failed to call {cmd}, return code {code}'.format(
+ cmd=cmd, code=e.returncode)
print e
return None
@@ -68,7 +68,8 @@ def get_android_root_or_die():
if os.path.isfile(soong_ui_bash_path):
# Use value returned from Soong UI instead in case definition to TOP
# changes in the future
- value = get_output_from_command((soong_ui_bash_path, '--dumpvar-mode', '--abs', 'TOP'))
+ value = get_output_from_command(
+ (soong_ui_bash_path, '--dumpvar-mode', '--abs', 'TOP'))
break
parent_path = os.path.abspath(os.path.join(current_path, os.pardir))
if parent_path == current_path:
@@ -86,8 +87,9 @@ def get_android_host_out_or_die():
value = os.environ.get('ANDROID_HOST_OUT')
if not value:
ANDROID_BUILD_TOP = get_android_root_or_die()
- value = get_output_from_command((os.path.join(ANDROID_BUILD_TOP, SOONG_UI_BASH), '--dumpvar-mode', '--abs',
- 'HOST_OUT'))
+ value = get_output_from_command(
+ (os.path.join(ANDROID_BUILD_TOP, SOONG_UI_BASH), '--dumpvar-mode',
+ '--abs', 'HOST_OUT'))
if not value:
print 'Cannot determine ANDROID_HOST_OUT'
sys.exit(1)
@@ -130,7 +132,8 @@ def get_test_cmd_or_die(test_root, test_name, enable_xml, test_filter):
cmd = [test_path]
if enable_xml:
dist_dir = get_android_dist_dir_or_die()
- log_output_path = os.path.join(dist_dir, 'gtest/{0}_test_details.xml'.format(test_name))
+ log_output_path = os.path.join(
+ dist_dir, 'gtest/{0}_test_details.xml'.format(test_name))
cmd.append('--gtest_output=xml:{0}'.format(log_output_path))
if test_filter:
cmd.append('--gtest_filter=%s' % test_filter)
@@ -144,7 +147,8 @@ def build_target(target, num_tasks):
if num_tasks > 1:
build_cmd.append('-j' + str(num_tasks))
build_cmd.append(target)
- p = subprocess.Popen(build_cmd, cwd=ANDROID_BUILD_TOP, env=os.environ.copy())
+ p = subprocess.Popen(
+ build_cmd, cwd=ANDROID_BUILD_TOP, env=os.environ.copy())
return_code = p.wait()
if return_code != 0:
print 'BUILD FAILED, return code: {0}'.format(str(return_code))
@@ -163,7 +167,9 @@ def main():
nargs='?',
const=True,
default=False,
- help='Whether to output structured XML log output in out/dist/gtest directory')
+ help=
+ 'Whether to output structured XML log output in out/dist/gtest directory'
+ )
parser.add_argument(
'-j',
type=int,
@@ -173,14 +179,17 @@ def main():
default=-1,
help='Number of tasks to run at the same time')
parser.add_argument(
- 'rest', nargs=argparse.REMAINDER, help='-- args, other gtest arguments for each individual test')
+ 'rest',
+ nargs=argparse.REMAINDER,
+ help='-- args, other gtest arguments for each individual test')
args = parser.parse_args()
build_target('MODULES-IN-system-bt', args.num_tasks)
TEST_ROOT = get_native_test_root_or_die()
test_results = []
for test in HOST_TESTS:
- test_cmd = get_test_cmd_or_die(TEST_ROOT, test, args.enable_xml, args.rest)
+ test_cmd = get_test_cmd_or_die(TEST_ROOT, test, args.enable_xml,
+ args.rest)
if subprocess.call(test_cmd) != 0:
test_results.append(False)
else:
diff --git a/test/run_unit_tests.sh b/test/run_unit_tests.sh
index 3b17dd159..754d9c57f 100755
--- a/test/run_unit_tests.sh
+++ b/test/run_unit_tests.sh
@@ -14,13 +14,13 @@ known_tests=(
net_test_btif_profile_queue
net_test_btif_config_cache
net_test_device
- net_test_eatt
net_test_hci
net_test_stack
net_test_stack_multi_adv
net_test_stack_ad_parser
net_test_stack_smp
net_test_types
+ net_test_btu_message_loop
net_test_osi
net_test_performance
net_test_stack_rfcomm
diff --git a/test/stub/legacy_trace.cc b/test/stub/legacy_trace.cc
deleted file mode 100644
index 2b4e3dcc5..000000000
--- a/test/stub/legacy_trace.cc
+++ /dev/null
@@ -1,31 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include <cstdint>
-
-// tLEGACY_TRACE_LEVEL
-uint8_t btu_trace_level = 6;
-uint8_t appl_trace_level = 6;
-uint8_t btif_trace_level = 6;
-
-uint8_t A2DP_SetTraceLevel(uint8_t new_level) { return 0; }
-uint8_t AVDT_SetTraceLevel(uint8_t new_level) { return 0; }
-uint8_t AVRC_SetTraceLevel(uint8_t new_level) { return 0; }
-uint8_t BNEP_SetTraceLevel(uint8_t new_level) { return 0; }
-uint8_t BTM_SetTraceLevel(uint8_t new_level) { return 0; }
-uint8_t PAN_SetTraceLevel(uint8_t new_level) { return 0; }
-uint8_t PORT_SetTraceLevel(uint8_t new_level) { return 0; }
-uint8_t SMP_SetTraceLevel(uint8_t new_level) { return 0; }
diff --git a/test/stub/osi.cc b/test/stub/osi.cc
deleted file mode 100644
index b6842ef1b..000000000
--- a/test/stub/osi.cc
+++ /dev/null
@@ -1,645 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-/*
- * Generated mock file from original source file
- */
-
-#include <list>
-#include <map>
-#include <string>
-
-extern std::map<std::string, int> mock_function_count_map;
-
-#include "osi/src/compat.cc" // For strlcpy
-
-#include "osi/include/alarm.h"
-#include "osi/include/allocator.h"
-#include "osi/include/array.h"
-#include "osi/include/buffer.h"
-#include "osi/include/config.h"
-#include "osi/include/fixed_queue.h"
-#include "osi/include/future.h"
-#include "osi/include/hash_map_utils.h"
-#include "osi/include/list.h"
-#include "osi/include/log.h"
-#include "osi/include/osi.h"
-#include "osi/include/reactor.h"
-#include "osi/include/ringbuffer.h"
-#include "osi/include/semaphore.h"
-#include "osi/include/socket.h"
-#include "osi/include/thread.h"
-#include "osi/include/wakelock.h"
-#include "test/common/fake_osi.h"
-
-#ifndef UNUSED_ATTR
-#define UNUSED_ATTR
-#endif
-
-std::list<entry_t>::iterator section_t::Find(const std::string& key) {
- mock_function_count_map[__func__]++;
- return std::find_if(
- entries.begin(), entries.end(),
- [&key](const entry_t& entry) { return entry.key == key; });
-}
-std::list<section_t>::iterator config_t::Find(const std::string& section) {
- mock_function_count_map[__func__]++;
- return std::find_if(
- sections.begin(), sections.end(),
- [&section](const section_t& sec) { return sec.name == section; });
-}
-
-bool checksum_save(const std::string& checksum, const std::string& filename) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool config_get_bool(const config_t& config, const std::string& section,
- const std::string& key, bool def_value) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool config_has_key(const config_t& config, const std::string& section,
- const std::string& key) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool config_has_section(const config_t& config, const std::string& section) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool config_remove_key(config_t* config, const std::string& section,
- const std::string& key) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool config_remove_section(config_t* config, const std::string& section) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool config_save(const config_t& config, const std::string& filename) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool config_t::Has(const std::string& key) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool section_t::Has(const std::string& key) {
- mock_function_count_map[__func__]++;
- return false;
-}
-const std::string* config_get_string(const config_t& config,
- const std::string& section,
- const std::string& key,
- const std::string* def_value) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-int config_get_int(const config_t& config, const std::string& section,
- const std::string& key, int def_value) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::string checksum_read(const char* filename) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::unique_ptr<config_t> config_new(const char* filename) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::unique_ptr<config_t> config_new_clone(const config_t& src) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-std::unique_ptr<config_t> config_new_empty(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-uint64_t config_get_uint64(const config_t& config, const std::string& section,
- const std::string& key, uint64_t def_value) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void config_set_bool(config_t* config, const std::string& section,
- const std::string& key, bool value) {
- mock_function_count_map[__func__]++;
-}
-void config_set_int(config_t* config, const std::string& section,
- const std::string& key, int value) {
- mock_function_count_map[__func__]++;
-}
-void config_set_string(config_t* config, const std::string& section,
- const std::string& key, const std::string& value) {
- mock_function_count_map[__func__]++;
-}
-void config_set_uint64(config_t* config, const std::string& section,
- const std::string& key, uint64_t value) {
- mock_function_count_map[__func__]++;
-}
-void section_t::Set(std::string key, std::string value) {
- mock_function_count_map[__func__]++;
-}
-
-bool array_append_ptr(array_t* array, void* data) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool array_append_value(array_t* array, uint32_t value) {
- mock_function_count_map[__func__]++;
- return false;
-}
-size_t array_length(const array_t* array) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void array_free(array_t* array) { mock_function_count_map[__func__]++; }
-void* array_at(const array_t* array, size_t index) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void* array_ptr(const array_t* array) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-
-size_t allocation_tracker_expect_no_allocations(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-size_t allocation_tracker_resize_for_canary(size_t size) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void allocation_tracker_reset(void) { mock_function_count_map[__func__]++; }
-void allocation_tracker_uninit(void) { mock_function_count_map[__func__]++; }
-void osi_allocator_debug_dump(int fd) { mock_function_count_map[__func__]++; }
-void* allocation_tracker_notify_alloc(uint8_t allocator_id, void* ptr,
- size_t requested_size) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void* allocation_tracker_notify_free(UNUSED_ATTR uint8_t allocator_id,
- void* ptr) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-
-bool reactor_change_registration(reactor_object_t* object,
- void (*read_ready)(void* context),
- void (*write_ready)(void* context)) {
- mock_function_count_map[__func__]++;
- return false;
-}
-reactor_object_t* reactor_register(reactor_t* reactor, int fd, void* context,
- void (*read_ready)(void* context),
- void (*write_ready)(void* context)) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-reactor_status_t reactor_run_once(reactor_t* reactor) {
- mock_function_count_map[__func__]++;
- return REACTOR_STATUS_DONE;
-}
-reactor_status_t reactor_start(reactor_t* reactor) {
- mock_function_count_map[__func__]++;
- return REACTOR_STATUS_DONE;
-}
-reactor_t* reactor_new(void) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void reactor_free(reactor_t* reactor) { mock_function_count_map[__func__]++; }
-void reactor_stop(reactor_t* reactor) { mock_function_count_map[__func__]++; }
-void reactor_unregister(reactor_object_t* obj) {
- mock_function_count_map[__func__]++;
-}
-
-future_t* future_new(void) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-future_t* future_new_immediate(void* value) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void future_ready(future_t* future, void* value) {
- mock_function_count_map[__func__]++;
-}
-void mutex_global_lock(void) { mock_function_count_map[__func__]++; }
-void mutex_global_unlock(void) { mock_function_count_map[__func__]++; }
-void* future_await(future_t* future) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-
-bool thread_is_self(const thread_t* thread) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool thread_post(thread_t* thread, thread_fn func, void* context) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool thread_set_priority(thread_t* thread, int priority) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool thread_set_rt_priority(thread_t* thread, int priority) {
- mock_function_count_map[__func__]++;
- return false;
-}
-const char* thread_name(const thread_t* thread) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-reactor_t* thread_get_reactor(const thread_t* thread) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-thread_t* thread_new(const char* name) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-thread_t* thread_new_sized(const char* name, size_t work_queue_capacity) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void thread_free(thread_t* thread) { mock_function_count_map[__func__]++; }
-void thread_join(thread_t* thread) { mock_function_count_map[__func__]++; }
-void thread_stop(thread_t* thread) { mock_function_count_map[__func__]++; }
-
-char* osi_strdup(const char* str) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-char* osi_strndup(const char* str, size_t len) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void osi_free(void* ptr) { mock_function_count_map[__func__]++; }
-void osi_free_and_reset(void** p_ptr) { mock_function_count_map[__func__]++; }
-void* osi_calloc(size_t size) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void* osi_malloc(size_t size) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-
-bool fixed_queue_is_empty(fixed_queue_t* queue) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool fixed_queue_try_enqueue(fixed_queue_t* queue, void* data) {
- mock_function_count_map[__func__]++;
- return false;
-}
-fixed_queue_t* fixed_queue_new(size_t capacity) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-int fixed_queue_get_dequeue_fd(const fixed_queue_t* queue) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int fixed_queue_get_enqueue_fd(const fixed_queue_t* queue) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-list_t* fixed_queue_get_list(fixed_queue_t* queue) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-size_t fixed_queue_capacity(fixed_queue_t* queue) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-size_t fixed_queue_length(fixed_queue_t* queue) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void fixed_queue_enqueue(fixed_queue_t* queue, void* data) {
- mock_function_count_map[__func__]++;
-}
-void fixed_queue_flush(fixed_queue_t* queue, fixed_queue_free_cb free_cb) {
- mock_function_count_map[__func__]++;
-}
-void fixed_queue_free(fixed_queue_t* queue, fixed_queue_free_cb free_cb) {
- mock_function_count_map[__func__]++;
-}
-void fixed_queue_register_dequeue(fixed_queue_t* queue, reactor_t* reactor,
- fixed_queue_cb ready_cb, void* context) {
- mock_function_count_map[__func__]++;
-}
-void fixed_queue_unregister_dequeue(fixed_queue_t* queue) {
- mock_function_count_map[__func__]++;
-}
-void* fixed_queue_dequeue(fixed_queue_t* queue) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void* fixed_queue_try_dequeue(fixed_queue_t* queue) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void* fixed_queue_try_peek_first(fixed_queue_t* queue) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void* fixed_queue_try_peek_last(fixed_queue_t* queue) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void* fixed_queue_try_remove_from_queue(fixed_queue_t* queue, void* data) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-
-alarm_t* alarm_new(const char* name) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-alarm_t* alarm_new_periodic(const char* name) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-bool alarm_is_scheduled(const alarm_t* alarm) {
- mock_function_count_map[__func__]++;
- return false;
-}
-uint64_t alarm_get_remaining_ms(const alarm_t* alarm) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void alarm_cancel(alarm_t* alarm) { mock_function_count_map[__func__]++; }
-void alarm_cleanup(void) { mock_function_count_map[__func__]++; }
-void alarm_debug_dump(int fd) { mock_function_count_map[__func__]++; }
-void alarm_free(alarm_t* alarm) { mock_function_count_map[__func__]++; }
-void alarm_set(alarm_t* alarm, uint64_t interval_ms, alarm_callback_t cb,
- void* data) {
- mock_function_count_map[__func__]++;
-}
-
-struct fake_osi_alarm_set_on_mloop fake_osi_alarm_set_on_mloop_;
-void alarm_set_on_mloop(alarm_t* alarm, uint64_t interval_ms,
- alarm_callback_t cb, void* data) {
- mock_function_count_map[__func__]++;
- fake_osi_alarm_set_on_mloop_.interval_ms = interval_ms;
- fake_osi_alarm_set_on_mloop_.cb = cb;
- fake_osi_alarm_set_on_mloop_.data = data;
-}
-
-int osi_rand(void) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-
-buffer_t* buffer_new_ref(const buffer_t* buf) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-buffer_t* buffer_new_slice(const buffer_t* buf, size_t slice_size) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-size_t buffer_length(const buffer_t* buf) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void buffer_free(buffer_t* buffer) { mock_function_count_map[__func__]++; }
-void* buffer_ptr(const buffer_t* buf) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-
-bool socket_listen(const socket_t* socket, port_t port) {
- mock_function_count_map[__func__]++;
- return false;
-}
-socket_t* socket_accept(const socket_t* socket) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-socket_t* socket_new(void) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-socket_t* socket_new_from_fd(int fd) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-ssize_t socket_bytes_available(const socket_t* socket) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-ssize_t socket_read(const socket_t* socket, void* buf, size_t count) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-ssize_t socket_write(const socket_t* socket, const void* buf, size_t count) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-ssize_t socket_write_and_transfer_fd(const socket_t* socket, const void* buf,
- size_t count, int fd) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void socket_free(socket_t* socket) { mock_function_count_map[__func__]++; }
-void socket_register(socket_t* socket, reactor_t* reactor, void* context,
- socket_cb read_cb, socket_cb write_cb) {
- mock_function_count_map[__func__]++;
-}
-void socket_unregister(socket_t* socket) {
- mock_function_count_map[__func__]++;
-}
-
-bool list_append(list_t* list, void* data) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool list_contains(const list_t* list, const void* data) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool list_insert_after(list_t* list, list_node_t* prev_node, void* data) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool list_is_empty(const list_t* list) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool list_prepend(list_t* list, void* data) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool list_remove(list_t* list, void* data) {
- mock_function_count_map[__func__]++;
- return false;
-}
-list_node_t* list_back_node(const list_t* list) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-list_node_t* list_begin(const list_t* list) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-list_node_t* list_end(UNUSED_ATTR const list_t* list) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-list_node_t* list_foreach(const list_t* list, list_iter_cb callback,
- void* context) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-list_node_t* list_next(const list_node_t* node) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-list_t* list_new(list_free_cb callback) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-list_t* list_new_internal(list_free_cb callback,
- const allocator_t* zeroed_allocator) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-size_t list_length(const list_t* list) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void list_clear(list_t* list) { mock_function_count_map[__func__]++; }
-void list_free(list_t* list) { mock_function_count_map[__func__]++; }
-void* list_back(const list_t* list) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void* list_front(const list_t* list) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void* list_node(const list_node_t* node) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-
-int osi_socket_local_client(const char* name, int namespaceId, int type) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int osi_socket_local_client_connect(int fd, const char* name, int namespaceId,
- int type UNUSED_ATTR) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int osi_socket_local_server_bind(int s, const char* name, int namespaceId) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int osi_socket_make_sockaddr_un(const char* name, int namespaceId,
- struct sockaddr_un* p_addr, socklen_t* alen) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-
-size_t ringbuffer_available(const ringbuffer_t* rb) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-size_t ringbuffer_delete(ringbuffer_t* rb, size_t length) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-size_t ringbuffer_insert(ringbuffer_t* rb, const uint8_t* p, size_t length) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-size_t ringbuffer_peek(const ringbuffer_t* rb, off_t offset, uint8_t* p,
- size_t length) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-size_t ringbuffer_pop(ringbuffer_t* rb, uint8_t* p, size_t length) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-size_t ringbuffer_size(const ringbuffer_t* rb) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-void ringbuffer_free(ringbuffer_t* rb) { mock_function_count_map[__func__]++; }
-
-bool osi_property_get_bool(const char* key, bool default_value) {
- mock_function_count_map[__func__]++;
- return false;
-}
-int osi_property_get(const char* key, char* value, const char* default_value) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int osi_property_set(const char* key, const char* value) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-int32_t osi_property_get_int32(const char* key, int32_t default_value) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-
-bool semaphore_try_wait(semaphore_t* semaphore) {
- mock_function_count_map[__func__]++;
- return false;
-}
-int semaphore_get_fd(const semaphore_t* semaphore) {
- mock_function_count_map[__func__]++;
- return 0;
-}
-semaphore_t* semaphore_new(unsigned int value) {
- mock_function_count_map[__func__]++;
- return nullptr;
-}
-void semaphore_free(semaphore_t* semaphore) {
- mock_function_count_map[__func__]++;
-}
-void semaphore_post(semaphore_t* semaphore) {
- mock_function_count_map[__func__]++;
-}
-void semaphore_wait(semaphore_t* semaphore) {
- mock_function_count_map[__func__]++;
-}
-
-bool wakelock_acquire(void) {
- mock_function_count_map[__func__]++;
- return false;
-}
-bool wakelock_release(void) {
- mock_function_count_map[__func__]++;
- return false;
-}
-void wakelock_cleanup(void) { mock_function_count_map[__func__]++; }
-void wakelock_debug_dump(int fd) { mock_function_count_map[__func__]++; }
-void wakelock_set_os_callouts(bt_os_callouts_t* callouts) {
- mock_function_count_map[__func__]++;
-}
-void wakelock_set_paths(const char* lock_path, const char* unlock_path) {
- mock_function_count_map[__func__]++;
-}
diff --git a/test/suite/Android.bp b/test/suite/Android.bp
index 25b6e38b1..1d919edcd 100644
--- a/test/suite/Android.bp
+++ b/test/suite/Android.bp
@@ -1,14 +1,5 @@
// Bluetooth test suite for target
// ========================================================
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_test {
name: "net_test_bluetooth",
test_suites: ["device-tests"],
diff --git a/test/suite/BUILD.gn b/test/suite/BUILD.gn
index 20b65d0aa..7e68a1a95 100644
--- a/test/suite/BUILD.gn
+++ b/test/suite/BUILD.gn
@@ -14,36 +14,33 @@
# limitations under the License.
#
-if (defined(use.android) && use.android) {
- executable("net_test_bluetooth") {
- sources = [
- "adapter/adapter_unittest.cc",
- "adapter/bluetooth_test.cc",
- ]
+executable("net_test_bluetooth") {
+ testonly = true
+ sources = [
+ "adapter/adapter_unittest.cc",
+ "adapter/bluetooth_test.cc",
+ ]
- include_dirs = [
- "//bt",
- "//bt/test/suite",
- ]
+ include_dirs = [
+ "//",
+ "//test/suite",
+ ]
- deps = [
- "//bt/btcore",
- "//bt/main:bluetooth",
- "//bt/service:service",
- "//bt/service:service_unittests",
- "//bt/types:types_unittests",
- "//bt/osi",
- ]
+ deps = [
+ "//btcore",
+ "//main:bluetooth",
+ "//service:service",
+ "//service:service_unittests",
+ "//types:types_unittests",
+ "//third_party/libchrome:base",
+ "//osi",
+ "//third_party/googletest:gtest_main",
+ ]
- configs += [
- "//bt:target_defaults",
- "//bt:external_gtest_main",
- ]
-
- libs = [
- "pthread",
- "rt",
- "dl",
- ]
- }
+ libs = [
+ "-lpthread",
+ "-lrt",
+ "-ldl",
+ "-latomic",
+ ]
}
diff --git a/test/suite/adapter/adapter_unittest.cc b/test/suite/adapter/adapter_unittest.cc
index 56720bda3..85549b0d5 100644
--- a/test/suite/adapter/adapter_unittest.cc
+++ b/test/suite/adapter/adapter_unittest.cc
@@ -19,7 +19,6 @@
#include "adapter/bluetooth_test.h"
#include "btcore/include/property.h"
#include "stack/include/bt_types.h"
-#include "types/bt_transport.h"
namespace {
@@ -180,7 +179,7 @@ TEST_F(BluetoothTest, AdapterCleanupDuringDiscovery) {
ASSERT_TRUE(bt_callbacks != nullptr);
for (int i = 0; i < kTestRepeatCount; ++i) {
- bt_interface()->init(bt_callbacks, false, false, 0, nullptr, false);
+ bt_interface()->init(bt_callbacks, false, false, 0, false);
EXPECT_EQ(bt_interface()->enable(), BT_STATUS_SUCCESS);
semaphore_wait(adapter_state_changed_callback_sem_);
EXPECT_EQ(GetState(), BT_STATE_ON) << "Adapter did not turn on.";
diff --git a/test/suite/gatt/gatt_unittest.cc b/test/suite/gatt/gatt_unittest.cc
index e91e7f6dc..b02c96a64 100644
--- a/test/suite/gatt/gatt_unittest.cc
+++ b/test/suite/gatt/gatt_unittest.cc
@@ -27,7 +27,7 @@ namespace bttest {
TEST_F(GattTest, GattClientRegister) {
// Registers gatt client.
bluetooth::Uuid gatt_client_uuid = bluetooth::Uuid::GetRandom();
- gatt_client_interface()->register_client(gatt_client_uuid, false);
+ gatt_client_interface()->register_client(gatt_client_uuid);
semaphore_wait(register_client_callback_sem_);
EXPECT_TRUE(status() == BT_STATUS_SUCCESS)
<< "Error registering GATT client app callback.";
@@ -39,7 +39,7 @@ TEST_F(GattTest, GattClientRegister) {
TEST_F(GattTest, GattServerRegister) {
// Registers gatt server.
bluetooth::Uuid gatt_server_uuid = bluetooth::Uuid::GetRandom();
- gatt_server_interface()->register_server(gatt_server_uuid, false);
+ gatt_server_interface()->register_server(gatt_server_uuid);
semaphore_wait(register_server_callback_sem_);
EXPECT_TRUE(status() == BT_STATUS_SUCCESS)
<< "Error registering GATT server app callback.";
@@ -51,7 +51,7 @@ TEST_F(GattTest, GattServerRegister) {
TEST_F(GattTest, GattServerBuild) {
// Registers gatt server.
bluetooth::Uuid gatt_server_uuid = bluetooth::Uuid::GetRandom();
- gatt_server_interface()->register_server(gatt_server_uuid, false);
+ gatt_server_interface()->register_server(gatt_server_uuid);
semaphore_wait(register_server_callback_sem_);
EXPECT_TRUE(status() == BT_STATUS_SUCCESS)
<< "Error registering GATT server app callback.";
diff --git a/tools/scripts/btsnoop_live.py b/tools/scripts/btsnoop_live.py
index a04dc19e9..00b45fdda 100644
--- a/tools/scripts/btsnoop_live.py
+++ b/tools/scripts/btsnoop_live.py
@@ -94,7 +94,8 @@ def get_file_time():
Obtain current time in file time format for display
"""
date_time = datetime.now()
- file_time = FILETIME_EPOCH_DELTA + (timegm(date_time.timetuple()) * HUNDREDS_OF_NANOSECONDS)
+ file_time = FILETIME_EPOCH_DELTA + (
+ timegm(date_time.timetuple()) * HUNDREDS_OF_NANOSECONDS)
file_time = file_time + (date_time.microsecond * 10)
return file_time
@@ -188,7 +189,8 @@ def init_live_import(conn_str, config_str):
print(dllName + " loaded successfully")
result = live_import.InitializeLiveImport(
- conn_str.encode('ascii', 'ignore'), config_str.encode('ascii', 'ignore'), byref(success))
+ conn_str.encode('ascii', 'ignore'), config_str.encode(
+ 'ascii', 'ignore'), byref(success))
if (result < 0):
print("Live Import Init failed")
return None
@@ -259,7 +261,8 @@ def main():
if data_frag is not None:
snoop_data += data_frag
- print("Bytes received %d Olen %d ilen %d flags %d" % (len(snoop_data), olen, ilen, flags))
+ print("Bytes received %d Olen %d ilen %d flags %d" %
+ (len(snoop_data), olen, ilen, flags))
packet_type = struct.unpack(">B", snoop_data[0:1])[0]
if packet_type == 1:
drf = 1
@@ -280,7 +283,9 @@ def main():
drf = 8
isend = 1
- result = live_import.SendFrame(olen - 1, olen - 1, snoop_data[1:olen], drf, isend, timestamp)
+ result = live_import.SendFrame(olen - 1, olen - 1,
+ snoop_data[1:olen], drf, isend,
+ timestamp)
if (result < 0):
print("Send frame failed")
except KeyboardInterrupt:
diff --git a/tools/scripts/btsnooz.py b/tools/scripts/btsnooz.py
index 622824a47..a29e718d7 100755
--- a/tools/scripts/btsnooz.py
+++ b/tools/scripts/btsnooz.py
@@ -33,11 +33,9 @@ import zlib
TYPE_IN_EVT = 0x10
TYPE_IN_ACL = 0x11
TYPE_IN_SCO = 0x12
-TYPE_IN_ISO = 0x17
TYPE_OUT_CMD = 0x20
TYPE_OUT_ACL = 0x21
TYPE_OUT_SCO = 0x22
-TYPE_OUT_ISO = 0x2d
def type_to_direction(type):
@@ -46,7 +44,7 @@ def type_to_direction(type):
0 = sent packet
1 = received packet
"""
- if type in [TYPE_IN_EVT, TYPE_IN_ACL, TYPE_IN_SCO, TYPE_IN_ISO]:
+ if type in [TYPE_IN_EVT, TYPE_IN_ACL, TYPE_IN_SCO]:
return 1
return 0
@@ -63,9 +61,6 @@ def type_to_hci(type):
return '\x03'
if type == TYPE_IN_EVT:
return '\x04'
- if type == TYPE_IN_ISO or type == TYPE_OUT_ISO:
- return '\x05'
- raise RuntimeError("type_to_hci: unknown type (0x{:02x})".format(type))
def decode_snooz(snooz):
@@ -98,19 +93,23 @@ def decode_snooz_v1(decompressed, last_timestamp_ms):
first_timestamp_ms = last_timestamp_ms + 0x00dcddb30f2f8000
offset = 0
while offset < len(decompressed):
- length, delta_time_ms, type = struct.unpack_from('=HIb', decompressed, offset)
+ length, delta_time_ms, type = struct.unpack_from(
+ '=HIb', decompressed, offset)
offset += 7 + length - 1
first_timestamp_ms -= delta_time_ms
# Second pass does the actual writing out to stdout.
offset = 0
while offset < len(decompressed):
- length, delta_time_ms, type = struct.unpack_from('=HIb', decompressed, offset)
+ length, delta_time_ms, type = struct.unpack_from(
+ '=HIb', decompressed, offset)
first_timestamp_ms += delta_time_ms
offset += 7
sys.stdout.write(struct.pack('>II', length, length))
sys.stdout.write(struct.pack('>II', type_to_direction(type), 0))
- sys.stdout.write(struct.pack('>II', (first_timestamp_ms >> 32), (first_timestamp_ms & 0xFFFFFFFF)))
+ sys.stdout.write(
+ struct.pack('>II', (first_timestamp_ms >> 32),
+ (first_timestamp_ms & 0xFFFFFFFF)))
sys.stdout.write(type_to_hci(type))
sys.stdout.write(decompressed[offset:offset + length - 1])
offset += length - 1
@@ -125,19 +124,23 @@ def decode_snooz_v2(decompressed, last_timestamp_ms):
first_timestamp_ms = last_timestamp_ms + 0x00dcddb30f2f8000
offset = 0
while offset < len(decompressed):
- length, packet_length, delta_time_ms, snooz_type = struct.unpack_from('=HHIb', decompressed, offset)
+ length, packet_length, delta_time_ms, snooz_type = struct.unpack_from(
+ '=HHIb', decompressed, offset)
offset += 9 + length - 1
first_timestamp_ms -= delta_time_ms
# Second pass does the actual writing out to stdout.
offset = 0
while offset < len(decompressed):
- length, packet_length, delta_time_ms, snooz_type = struct.unpack_from('=HHIb', decompressed, offset)
+ length, packet_length, delta_time_ms, snooz_type = struct.unpack_from(
+ '=HHIb', decompressed, offset)
first_timestamp_ms += delta_time_ms
offset += 9
sys.stdout.write(struct.pack('>II', packet_length, length))
sys.stdout.write(struct.pack('>II', type_to_direction(snooz_type), 0))
- sys.stdout.write(struct.pack('>II', (first_timestamp_ms >> 32), (first_timestamp_ms & 0xFFFFFFFF)))
+ sys.stdout.write(
+ struct.pack('>II', (first_timestamp_ms >> 32),
+ (first_timestamp_ms & 0xFFFFFFFF)))
sys.stdout.write(type_to_hci(snooz_type))
sys.stdout.write(decompressed[offset:offset + length - 1])
offset += length - 1
diff --git a/tools/scripts/dump_hearingaid_audio.py b/tools/scripts/dump_hearingaid_audio.py
index 4304a48e1..81cd78d98 100755
--- a/tools/scripts/dump_hearingaid_audio.py
+++ b/tools/scripts/dump_hearingaid_audio.py
@@ -54,11 +54,14 @@ DEBUG_DATA = "DEBUG_DATA"
AUDIO_DATA_B = "AUDIO_DATA_B"
# Debug packet header struct
-header_list_str = ["Event Processed", "Number Packet Nacked By Peripheral", "Number Packet Nacked By Central"]
+header_list_str = [
+ "Event Processed", "Number Packet Nacked By Slave",
+ "Number Packet Nacked By Master"
+]
# Debug frame information structs
data_list_str = [
- "Event Number", "Overrun", "Underrun", "Skips", "Rendered Audio Frame", "First PDU Option", "Second PDU Option",
- "Third PDU Option"
+ "Event Number", "Overrun", "Underrun", "Skips", "Rendered Audio Frame",
+ "First PDU Option", "Second PDU Option", "Third PDU Option"
]
AUDIO_CONTROL_POINT_UUID = "f0d4de7e4a88476c9d9f1937b0996cc0"
@@ -87,12 +90,14 @@ def parse_acl_ha_debug_buffer(data, result):
return
version, data = unpack_data(data, 1)
- update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], DEBUG_VERSION, str(version))
+ update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE],
+ DEBUG_VERSION, str(version))
debug_str = result[TIMESTAMP_TIME_FORMAT]
for p in range(3):
byte_data, data = unpack_data(data, 1)
- debug_str = debug_str + ", " + header_list_str[p] + "=" + str(byte_data).rjust(3)
+ debug_str = debug_str + ", " + header_list_str[p] + "=" + str(
+ byte_data).rjust(3)
if full_debug:
debug_str = debug_str + "\n" + "|".join(data_list_str) + "\n"
@@ -105,15 +110,22 @@ def parse_acl_ha_debug_buffer(data, result):
p = base + counter
byte_data, data = unpack_data(data, 1)
if p == 1:
- data_list_content.append(str(byte_data & 0x03).rjust(len(data_list_str[p])))
- data_list_content.append(str((byte_data >> 2) & 0x03).rjust(len(data_list_str[p + 1])))
- data_list_content.append(str((byte_data >> 4) & 0x0f).rjust(len(data_list_str[p + 2])))
+ data_list_content.append(
+ str(byte_data & 0x03).rjust(len(data_list_str[p])))
+ data_list_content.append(
+ str((byte_data >> 2) & 0x03).rjust(
+ len(data_list_str[p + 1])))
+ data_list_content.append(
+ str((byte_data >> 4) & 0x0f).rjust(
+ len(data_list_str[p + 2])))
base = 2
else:
- data_list_content.append(str(byte_data).rjust(len(data_list_str[p])))
+ data_list_content.append(
+ str(byte_data).rjust(len(data_list_str[p])))
debug_str = debug_str + "|".join(data_list_content) + "\n"
- update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], DEBUG_DATA, debug_str)
+ update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], DEBUG_DATA,
+ debug_str)
def parse_acl_ha_audio_data(data, result):
@@ -122,7 +134,8 @@ def parse_acl_ha_audio_data(data, result):
return
# Remove audio packet number
audio_data_b = data[1:]
- update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], AUDIO_DATA_B, audio_data_b)
+ update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE],
+ AUDIO_DATA_B, audio_data_b)
def parse_acl_ha_audio_type(data, result):
@@ -138,7 +151,8 @@ def parse_acl_ha_audio_type(data, result):
audio_type = "Media"
else:
audio_type = "Unknown"
- update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], AUDIO_TYPE, audio_type)
+ update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], AUDIO_TYPE,
+ audio_type)
def parse_acl_ha_codec(data, result):
@@ -153,8 +167,10 @@ def parse_acl_ha_codec(data, result):
else:
codec = "Unknown"
sample_rate = "Unknown"
- update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], CODEC, codec)
- update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], SAMPLE_RATE, sample_rate)
+ update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], CODEC,
+ codec)
+ update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], SAMPLE_RATE,
+ sample_rate)
parse_acl_ha_audio_type(data, result)
@@ -162,12 +178,14 @@ def parse_acl_ha_audio_control_cmd(data, result):
"""This function parses HA audio control cmd is start/stop."""
control_cmd, data = unpack_data(data, 1)
if control_cmd == 0x01:
- update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], START, True)
- update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], TIMESTAMP_STR_FORMAT,
- result[TIMESTAMP_STR_FORMAT])
+ update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], START,
+ True)
+ update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE],
+ TIMESTAMP_STR_FORMAT, result[TIMESTAMP_STR_FORMAT])
parse_acl_ha_codec(data, result)
elif control_cmd == 0x02:
- update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], START, False)
+ update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], START,
+ False)
#-----------------------------------------------------------------------
@@ -191,7 +209,8 @@ def parse_acl_att_long_uuid(data, result):
long_uuid = "".join(long_uuid_list)
# Check long_uuid is AUDIO_CONTROL_POINT uuid to get the attr_handle.
if long_uuid == AUDIO_CONTROL_POINT_UUID:
- update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE], AUDIO_CONTROL_ATTR_HANDLE, attr_handle)
+ update_audio_data(CONNECTION_HANDLE, result[CONNECTION_HANDLE],
+ AUDIO_CONTROL_ATTR_HANDLE, attr_handle)
def parse_acl_opcode(data, result):
@@ -257,7 +276,8 @@ def parse_hci_evt_peer_address(data, result):
if len(data) < 6:
return
for p in range(0, 6):
- peer_address_list.append("{0:02x}".format(struct.unpack(">B", data[p])[0]))
+ peer_address_list.append("{0:02x}".format(
+ struct.unpack(">B", data[p])[0]))
# Check the address is empty or not.
if peer_address_list == address_empty_list:
del peer_address_list[:]
@@ -267,7 +287,8 @@ def parse_hci_evt_peer_address(data, result):
peer_address_list.reverse()
peer_address = "_".join(peer_address_list)
update_audio_data("", "", PEER_ADDRESS, peer_address)
- update_audio_data(PEER_ADDRESS, peer_address, CONNECTION_HANDLE, result[CONNECTION_HANDLE])
+ update_audio_data(PEER_ADDRESS, peer_address, CONNECTION_HANDLE,
+ result[CONNECTION_HANDLE])
def parse_hci_evt_code(data, result):
@@ -329,7 +350,8 @@ def parse_packet(btsnoop_file):
return False
if packet_flag != 2 and drop == 0:
packet_result[IS_SENT] = (packet_flag == 0)
- packet_result[TIMESTAMP_STR_FORMAT], packet_result[TIMESTAMP_TIME_FORMAT] = convert_time_str(timestamp)
+ packet_result[TIMESTAMP_STR_FORMAT], packet_result[
+ TIMESTAMP_TIME_FORMAT] = convert_time_str(timestamp)
parse_packet_data(packet_data, packet_result)
else:
return False
@@ -353,10 +375,12 @@ def dump_audio_data(data):
if folder is not None:
if not os.path.exists(folder):
os.makedirs(folder)
- audio_file_name = os.path.join(folder, "-".join(file_name_list) + file_type)
+ audio_file_name = os.path.join(folder,
+ "-".join(file_name_list) + file_type)
if data.has_key(DEBUG_VERSION):
file_prefix = "debug_ver_" + data[DEBUG_VERSION] + "-"
- debug_file_name = os.path.join(folder, file_prefix + "-".join(file_name_list) + ".txt")
+ debug_file_name = os.path.join(
+ folder, file_prefix + "-".join(file_name_list) + ".txt")
else:
audio_file_name = "-".join(file_name_list) + file_type
if data.has_key(DEBUG_VERSION):
@@ -367,19 +391,23 @@ def dump_audio_data(data):
if data.has_key(AUDIO_DATA_B):
with open(audio_file_name, "wb+") as audio_file:
audio_file.write(data[AUDIO_DATA_B])
- sys.stdout.write("Finished to dump Audio File: %s\n\n" % audio_file_name)
+ sys.stdout.write(
+ "Finished to dump Audio File: %s\n\n" % audio_file_name)
else:
sys.stdout.write("Fail to dump Audio File: %s\n" % audio_file_name)
sys.stdout.write("There isn't any Hearing Aid audio data.\n\n")
if simple_debug:
- sys.stdout.write("Start to dump audio %s Debug File\n" % audio_file_name)
+ sys.stdout.write(
+ "Start to dump audio %s Debug File\n" % audio_file_name)
if data.has_key(DEBUG_DATA):
with open(debug_file_name, "wb+") as debug_file:
debug_file.write(data[DEBUG_DATA])
- sys.stdout.write("Finished to dump Debug File: %s\n\n" % debug_file_name)
+ sys.stdout.write(
+ "Finished to dump Debug File: %s\n\n" % debug_file_name)
else:
- sys.stdout.write("Fail to dump audio %s Debug File\n" % audio_file_name)
+ sys.stdout.write(
+ "Fail to dump audio %s Debug File\n" % audio_file_name)
sys.stdout.write("There isn't any Hearing Aid debug data.\n\n")
@@ -506,9 +534,11 @@ def convert_time_str(timestamp):
def set_config():
"""This function is for set config by flag and check the argv is correct."""
- argv_parser = argparse.ArgumentParser(description="Extracts Hearing Aid audio data from BTSNOOP.")
+ argv_parser = argparse.ArgumentParser(
+ description="Extracts Hearing Aid audio data from BTSNOOP.")
argv_parser.add_argument("BTSNOOP", help="BLUETOOTH BTSNOOP file.")
- argv_parser.add_argument("-f", "--folder", help="select output folder.", dest="folder")
+ argv_parser.add_argument(
+ "-f", "--folder", help="select output folder.", dest="folder")
argv_parser.add_argument(
"-c1",
"--connection-handle1",
@@ -544,9 +574,17 @@ def set_config():
dest="audio_control_attr_handle",
type=int)
argv_parser.add_argument(
- "-d", "--debug", help="dump full debug buffer content.", dest="full_debug", default="False")
+ "-d",
+ "--debug",
+ help="dump full debug buffer content.",
+ dest="full_debug",
+ default="False")
argv_parser.add_argument(
- "-sd", "--simple-debug", help="dump debug buffer header content.", dest="simple_debug", default="False")
+ "-sd",
+ "--simple-debug",
+ help="dump debug buffer header content.",
+ dest="simple_debug",
+ default="False")
arg = argv_parser.parse_args()
if arg.folder is not None:
@@ -560,16 +598,19 @@ def set_config():
exit(1)
if not (arg.no_start.lower() == "true" or arg.no_start.lower() == "false"):
- argv_parser.error("-ns/--no-start arg is invalid, it should be true/false.")
+ argv_parser.error(
+ "-ns/--no-start arg is invalid, it should be true/false.")
exit(1)
if arg.connection_handle1 is not None:
fake_name = "ConnectionHandle" + str(arg.connection_handle1)
update_audio_data("", "", PEER_ADDRESS, fake_name)
- update_audio_data(PEER_ADDRESS, fake_name, CONNECTION_HANDLE, arg.connection_handle1)
+ update_audio_data(PEER_ADDRESS, fake_name, CONNECTION_HANDLE,
+ arg.connection_handle1)
if arg.no_start.lower() == "true":
update_audio_data(PEER_ADDRESS, fake_name, START, True)
- update_audio_data(PEER_ADDRESS, fake_name, TIMESTAMP_STR_FORMAT, "Unknown")
+ update_audio_data(PEER_ADDRESS, fake_name, TIMESTAMP_STR_FORMAT,
+ "Unknown")
update_audio_data(PEER_ADDRESS, fake_name, CODEC, arg.codec)
update_audio_data(PEER_ADDRESS, fake_name, SAMPLE_RATE, "Unknown")
update_audio_data(PEER_ADDRESS, fake_name, AUDIO_TYPE, "Unknown")
@@ -577,10 +618,12 @@ def set_config():
if arg.connection_handle2 is not None:
fake_name = "ConnectionHandle" + str(arg.connection_handle2)
update_audio_data("", "", PEER_ADDRESS, fake_name)
- update_audio_data(PEER_ADDRESS, fake_name, CONNECTION_HANDLE, arg.connection_handle2)
+ update_audio_data(PEER_ADDRESS, fake_name, CONNECTION_HANDLE,
+ arg.connection_handle2)
if arg.no_start.lower() == "true":
update_audio_data(PEER_ADDRESS, fake_name, START, True)
- update_audio_data(PEER_ADDRESS, fake_name, TIMESTAMP_STR_FORMAT, "Unknown")
+ update_audio_data(PEER_ADDRESS, fake_name, TIMESTAMP_STR_FORMAT,
+ "Unknown")
update_audio_data(PEER_ADDRESS, fake_name, CODEC, arg.codec)
update_audio_data(PEER_ADDRESS, fake_name, SAMPLE_RATE, "Unknown")
update_audio_data(PEER_ADDRESS, fake_name, AUDIO_TYPE, "Unknown")
@@ -610,12 +653,14 @@ def main():
with open(btsnoop_file_name, "rb") as btsnoop_file:
identification = btsnoop_file.read(8)
if identification != "btsnoop\0":
- sys.stderr.write("Check identification fail. It is not correct btsnoop file.")
+ sys.stderr.write(
+ "Check identification fail. It is not correct btsnoop file.")
exit(1)
ver, data_link = struct.unpack(">II", btsnoop_file.read(4 + 4))
if (ver != 1) or (data_link != 1002):
- sys.stderr.write("Check ver or dataLink fail. It is not correct btsnoop file.")
+ sys.stderr.write(
+ "Check ver or dataLink fail. It is not correct btsnoop file.")
exit(1)
while True:
diff --git a/tools/scripts/dump_metrics_ascii.py b/tools/scripts/dump_metrics_ascii.py
index 0adb27832..20d413285 100755
--- a/tools/scripts/dump_metrics_ascii.py
+++ b/tools/scripts/dump_metrics_ascii.py
@@ -33,8 +33,10 @@ def compile_proto(proto_path, output_dir):
if not protoc:
protoc = find_executable('protoc')
if not protoc:
- logging.error("Cannot find Protobuf compiler (>=3.0.0), please install"
- "protobuf-compiler package. Prefer copying from <top>/prebuilts/tools")
+ logging.error(
+ "Cannot find Protobuf compiler (>=3.0.0), please install"
+ "protobuf-compiler package. Prefer copying from <top>/prebuilts/tools"
+ )
logging.error(" prebuilts/tools/linux-x86_64/protoc/bin/protoc")
logging.error("If prebuilts are not available, use apt-get:")
logging.error(" sudo apt-get install protobuf-compiler")
@@ -52,7 +54,11 @@ def compile_proto(proto_path, output_dir):
input_dir = os.path.dirname(proto_path)
output_filename = os.path.basename(proto_path).replace('.proto', '_pb2.py')
output_path = os.path.join(output_dir, output_filename)
- protoc_command = [protoc, '-I=%s' % (input_dir), '--python_out=%s' % (output_dir), proto_path]
+ protoc_command = [
+ protoc,
+ '-I=%s' % (input_dir),
+ '--python_out=%s' % (output_dir), proto_path
+ ]
if subprocess.call(protoc_command, stderr=subprocess.STDOUT) != 0:
logging.error("Fail to compile proto")
return None
@@ -76,7 +82,8 @@ def compile_import_proto(output_dir, proto_path):
try:
output_module = import_module(output_module_name)
except ImportError:
- logging.error("Cannot import generated py-proto %s" % (output_module_name))
+ logging.error(
+ "Cannot import generated py-proto %s" % (output_module_name))
return output_module
@@ -123,7 +130,8 @@ def main():
logging.info("Usage: " + sys.argv[0] + " <path_to_metric_proto>")
logging.info("Requires Protobuf compiler, protoc, version >=3.0.0")
sys.exit(0)
- bluetooth_proto_module = compile_import_proto(tempfile.gettempdir(), sys.argv[1])
+ bluetooth_proto_module = compile_import_proto(tempfile.gettempdir(),
+ sys.argv[1])
if not bluetooth_proto_module:
logging.error("Cannot compile " + sys.argv[1])
sys.exit(1)
diff --git a/tools/scripts/yapf_checker.py b/tools/scripts/yapf_checker.py
index 62a753e7d..86f1f3963 100755
--- a/tools/scripts/yapf_checker.py
+++ b/tools/scripts/yapf_checker.py
@@ -23,7 +23,7 @@ PYTHONPATH_KEY = 'PYTHONPATH'
COMMIT_ID_ENV_KEY = 'PREUPLOAD_COMMIT'
ANDROID_BUILD_TOP_KEY = 'ANDROID_BUILD_TOP'
DEFAULT_YAPF_DIR = 'external/yapf'
-GIT_COMMAND = ['git', 'diff-tree', '--no-commit-id', '--name-only', '--diff-filter=d']
+GIT_COMMAND = ['git', 'diff-tree', '--no-commit-id', '--name-only']
def main():
@@ -45,7 +45,8 @@ def main():
# Gather changed Python files
commit_id = os.environ[COMMIT_ID_ENV_KEY]
full_git_command = GIT_COMMAND + ['-r', commit_id]
- files = subprocess.check_output(full_git_command).decode('utf-8').splitlines()
+ files = subprocess.check_output(full_git_command).decode(
+ 'utf-8').splitlines()
full_files = [os.path.abspath(f) for f in files if f.endswith('.py')]
if not full_files:
return
@@ -55,20 +56,32 @@ def main():
yapf_binary = os.path.join(yapf_dir, 'yapf')
# Run YAPF
- full_yapf_command = ["%s=$%s:%s" % (PYTHONPATH_KEY, PYTHONPATH_KEY, yapf_dir), 'python3', yapf_binary, '-d', '-p'
- ] + full_files
+ full_yapf_command = [
+ "%s=$%s:%s" % (PYTHONPATH_KEY, PYTHONPATH_KEY, yapf_dir), 'python3',
+ yapf_binary, '-d', '-p'
+ ] + full_files
environment = os.environ.copy()
environment[PYTHONPATH_KEY] = environment[PYTHONPATH_KEY] + ":" + yapf_dir
- result = subprocess.run(full_yapf_command[1:], env=environment, stderr=subprocess.STDOUT, stdout=subprocess.PIPE)
+ result = subprocess.run(
+ full_yapf_command[1:],
+ env=environment,
+ stderr=subprocess.STDOUT,
+ stdout=subprocess.PIPE)
if result.returncode != 0 or result.stdout:
logging.error(result.stdout.decode('utf-8').strip())
logging.error('INVALID FORMATTING, return code %d', result.returncode)
- logging.error('To re-run the format command:\n\n' ' %s\n' % ' '.join(full_yapf_command))
- yapf_inplace_format = ' '.join(
- ["%s=$%s:%s" % (PYTHONPATH_KEY, PYTHONPATH_KEY, yapf_dir), 'python3', yapf_binary, '-p', '-i'] + full_files)
- logging.error('If this is a legitimate format error, please run:\n\n' ' %s\n' % yapf_inplace_format)
- logging.error('CAVEAT: Currently, this format the entire Python file if you modify even part of it')
+ logging.error('To re-run the format command:\n\n'
+ ' %s\n' % ' '.join(full_yapf_command))
+ yapf_inplace_format = ' '.join([
+ "%s=$%s:%s" % (PYTHONPATH_KEY, PYTHONPATH_KEY,
+ yapf_dir), 'python3', yapf_binary, '-p', '-i'
+ ] + full_files)
+ logging.error('If this is a legitimate format error, please run:\n\n'
+ ' %s\n' % yapf_inplace_format)
+ logging.error(
+ 'CAVEAT: Currently, this format the entire Python file if you modify even part of it'
+ )
exit(1)
diff --git a/types/Android.bp b/types/Android.bp
index fe887c2ca..bdd319d0f 100644
--- a/types/Android.bp
+++ b/types/Android.bp
@@ -1,13 +1,4 @@
// Bluetooth types
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_headers {
name: "libbluetooth-types-header",
export_include_dirs: ["./"],
diff --git a/types/BUILD.gn b/types/BUILD.gn
index 08a47b648..fa9a4af4c 100644
--- a/types/BUILD.gn
+++ b/types/BUILD.gn
@@ -20,54 +20,43 @@ static_library("types") {
]
sources = [
- "class_of_device.cc",
"bluetooth/uuid.cc",
+ "le_address.cc",
"raw_address.cc",
]
include_dirs = [
- "//bt/",
+ "//",
]
- configs += [
- "//bt:target_defaults",
+ deps = [
+ "//third_party/libchrome:base",
]
}
-if (use.test) {
- executable("net_test_types") {
- sources = [
- "test/class_of_device_unittest.cc",
- "test/raw_address_unittest.cc",
- "test/bluetooth/uuid_unittest.cc",
- ]
-
- include_dirs = [
- "//bt/",
- ]
-
- libs = [
- "dl",
- "pthread",
- "resolv",
- "rt",
- "z",
- ]
+executable("types_unittests") {
+ testonly = true
+ sources = [
+ "test/raw_address_unittest.cc",
+ "test/bluetooth/uuid_unittest.cc",
+ ]
- # For some reason, this is required for host build. Otherwise, I get
- # a complaint from gmock:
- # undefined reference to symbol 'pthread_getspecific@@GLIBC_2.2.5'
- ldflags = [
- "-lpthread"
- ]
+ include_dirs = [
+ "//",
+ ]
- deps = [
- ":types",
- ]
+ libs = [
+ "-ldl",
+ "-lpthread",
+ "-lresolv",
+ "-lrt",
+ "-lz",
+ "-latomic",
+ ]
- configs += [
- "//bt:external_gmock_main",
- "//bt:target_defaults",
- ]
- }
+ deps = [
+ "//types",
+ "//third_party/googletest:gmock_main",
+ "//third_party/libchrome:base",
+ ]
}
diff --git a/types/ble_address_with_type.h b/types/ble_address_with_type.h
deleted file mode 100644
index 850abb900..000000000
--- a/types/ble_address_with_type.h
+++ /dev/null
@@ -1,93 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include <string>
-#include "types/raw_address.h"
-
-#define BLE_ADDR_PUBLIC 0x00
-#define BLE_ADDR_RANDOM 0x01
-#define BLE_ADDR_PUBLIC_ID 0x02
-#define BLE_ADDR_RANDOM_ID 0x03
-#define BLE_ADDR_ANONYMOUS 0xFF
-typedef uint8_t tBLE_ADDR_TYPE;
-#ifdef __cplusplus
-inline std::string AddressTypeText(tBLE_ADDR_TYPE type) {
- switch (type) {
- case BLE_ADDR_PUBLIC:
- return std::string("public");
- case BLE_ADDR_RANDOM:
- return std::string("random");
- case BLE_ADDR_PUBLIC_ID:
- return std::string("public identity");
- case BLE_ADDR_RANDOM_ID:
- return std::string("random identity");
- case BLE_ADDR_ANONYMOUS:
- return std::string("anonymous");
- default:
- return std::string("unknown");
- }
-}
-#endif // __cplusplus
-
-/* BLE ADDR type ID bit */
-#define BLE_ADDR_TYPE_ID_BIT 0x02
-
-#ifdef __cplusplus
-constexpr uint8_t kBleAddressPublicDevice = BLE_ADDR_PUBLIC;
-constexpr uint8_t kBleAddressRandomDevice = BLE_ADDR_RANDOM;
-constexpr uint8_t kBleAddressIdentityBit = BLE_ADDR_TYPE_ID_BIT;
-constexpr uint8_t kBleAddressPublicIdentity =
- kBleAddressIdentityBit | kBleAddressPublicDevice;
-constexpr uint8_t kBleAddressRandomIdentity =
- kBleAddressIdentityBit | kBleAddressRandomDevice;
-
-constexpr uint8_t kResolvableAddressMask = 0xc0;
-constexpr uint8_t kResolvableAddressMsb = 0x40;
-
-struct tBLE_BD_ADDR {
- tBLE_ADDR_TYPE type;
- RawAddress bda;
- bool AddressEquals(const RawAddress& other) const { return other == bda; }
- bool IsPublicDeviceType() const { return type == kBleAddressPublicDevice; }
- bool IsRandomDeviceType() const { return type == kBleAddressRandomDevice; }
- bool IsPublicIdentityType() const {
- return type == kBleAddressPublicIdentity;
- }
- bool lsRandomIdentityType() const {
- return type == kBleAddressRandomIdentity;
- }
- bool IsAddressResolvable() const {
- return ((bda.address)[0] & kResolvableAddressMask) == kResolvableAddressMsb;
- }
- bool IsPublic() const { return type & 0x01; }
- bool IsResolvablePrivateAddress() const {
- return IsAddressResolvable() && IsRandomDeviceType();
- }
- bool IsIdentityType() const {
- return IsPublicIdentityType() || lsRandomIdentityType();
- }
- bool TypeWithoutIdentityEquals(const tBLE_ADDR_TYPE other) const {
- return (other & ~kBleAddressIdentityBit) ==
- (type & ~kBleAddressIdentityBit);
- }
- std::string ToString() const {
- return std::string(bda.ToString() + "[" + AddressTypeText(type) + "]");
- }
-};
-#endif
diff --git a/types/bluetooth/uuid.cc b/types/bluetooth/uuid.cc
index d05f4370f..4e7d54417 100644
--- a/types/bluetooth/uuid.cc
+++ b/types/bluetooth/uuid.cc
@@ -20,7 +20,6 @@
#include <base/rand_util.h>
#include <base/strings/stringprintf.h>
-#include <string.h>
#include <algorithm>
namespace bluetooth {
@@ -155,10 +154,6 @@ Uuid Uuid::GetRandom() {
bool Uuid::IsEmpty() const { return *this == kEmpty; }
-void Uuid::UpdateUuid(const Uuid& uuid) {
- uu = uuid.uu;
-}
-
bool Uuid::operator<(const Uuid& rhs) const {
return std::lexicographical_compare(uu.begin(), uu.end(), rhs.uu.begin(),
rhs.uu.end());
@@ -174,4 +169,4 @@ std::string Uuid::ToString() const {
uu[0], uu[1], uu[2], uu[3], uu[4], uu[5], uu[6], uu[7], uu[8], uu[9],
uu[10], uu[11], uu[12], uu[13], uu[14], uu[15]);
}
-} // namespace bluetooth
+} // namespace bluetooth \ No newline at end of file
diff --git a/types/bluetooth/uuid.h b/types/bluetooth/uuid.h
index 0fe5b5bd1..9fda6b6f9 100644
--- a/types/bluetooth/uuid.h
+++ b/types/bluetooth/uuid.h
@@ -106,9 +106,6 @@ class Uuid final {
// Returns true if this UUID is equal to kEmpty
bool IsEmpty() const;
- // Update UUID with new value
- void UpdateUuid(const Uuid& uuid);
-
bool operator<(const Uuid& rhs) const;
bool operator==(const Uuid& rhs) const;
bool operator!=(const Uuid& rhs) const;
diff --git a/types/bt_transport.h b/types/bt_transport.h
deleted file mode 100644
index 79b34119d..000000000
--- a/types/bt_transport.h
+++ /dev/null
@@ -1,38 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <string>
-
-#define BT_TRANSPORT_INVALID 0
-#define BT_TRANSPORT_UNKNOWN BT_TRANSPORT_INVALID
-#define BT_TRANSPORT_AUTO BT_TRANSPORT_INVALID
-
-#define BT_TRANSPORT_BR_EDR 1
-#define BT_TRANSPORT_LE 2
-typedef uint8_t tBT_TRANSPORT;
-
-inline std::string bt_transport_text(tBT_TRANSPORT transport) {
- switch (transport) {
- case BT_TRANSPORT_BR_EDR:
- return std::string("br_edr");
- case BT_TRANSPORT_LE:
- return std::string("le");
- default:
- return std::string("unknown");
- }
-}
diff --git a/types/class_of_device.h b/types/class_of_device.h
index b0fffc885..4c37ebf26 100644
--- a/types/class_of_device.h
+++ b/types/class_of_device.h
@@ -18,7 +18,6 @@
#pragma once
-#include <cstring>
#include <string>
namespace bluetooth {
@@ -60,4 +59,4 @@ inline std::ostream& operator<<(std::ostream& os, const ClassOfDevice& c) {
} // namespace types
} // namespace bluetooth
-using ::bluetooth::types::ClassOfDevice; // TODO, remove
+using ::bluetooth::types::ClassOfDevice; // TODO, remove \ No newline at end of file
diff --git a/types/hci_role.h b/types/hci_role.h
deleted file mode 100644
index eb582b821..000000000
--- a/types/hci_role.h
+++ /dev/null
@@ -1,49 +0,0 @@
-/*
- * Copyright 2021 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <string>
-
-/* HCI role definitions */
-typedef enum : uint8_t {
- HCI_ROLE_CENTRAL = 0x00,
- HCI_ROLE_PERIPHERAL = 0x01,
- HCI_ROLE_UNKNOWN = 0xff,
-} tHCI_ROLE;
-
-inline std::string hci_role_text(const tHCI_ROLE& role) {
- switch (role) {
- case HCI_ROLE_CENTRAL:
- return std::string("central");
- case HCI_ROLE_PERIPHERAL:
- return std::string("peripheral");
- default:
- return std::string("unknown");
- }
-}
-
-inline tHCI_ROLE to_hci_role(const uint8_t& role) {
- if (role == 0)
- return HCI_ROLE_CENTRAL;
- else if (role == 1)
- return HCI_ROLE_PERIPHERAL;
- else
- return HCI_ROLE_UNKNOWN;
-}
-
-typedef tHCI_ROLE hci_role_t; // LEGACY
-const auto RoleText = hci_role_text; // LEGACY
diff --git a/types/raw_address.cc b/types/raw_address.cc
index d21cf267d..b39e4552e 100644
--- a/types/raw_address.cc
+++ b/types/raw_address.cc
@@ -31,7 +31,7 @@ const RawAddress RawAddress::kEmpty{{0x00, 0x00, 0x00, 0x00, 0x00, 0x00}};
RawAddress::RawAddress(const uint8_t (&addr)[6]) {
std::copy(addr, addr + kLength, address);
-}
+};
std::string RawAddress::ToString() const {
return base::StringPrintf("%02x:%02x:%02x:%02x:%02x:%02x", address[0],
diff --git a/types/raw_address.h b/types/raw_address.h
index ca750181b..b0035c908 100644
--- a/types/raw_address.h
+++ b/types/raw_address.h
@@ -18,7 +18,6 @@
#pragma once
-#include <array>
#include <cstring>
#include <string>
@@ -30,7 +29,7 @@ class RawAddress final {
uint8_t address[kLength];
RawAddress() = default;
- RawAddress(const uint8_t (&addr)[kLength]);
+ RawAddress(const uint8_t (&addr)[6]);
bool operator<(const RawAddress& rhs) const {
return (std::memcmp(address, rhs.address, sizeof(address)) < 0);
diff --git a/udrv/Android.bp b/udrv/Android.bp
index 3bb39c942..4605c5371 100644
--- a/udrv/Android.bp
+++ b/udrv/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "libudrv-uipc",
defaults: ["fluoride_defaults"],
@@ -22,5 +13,7 @@ cc_library_static {
local_include_dirs: [
"include",
],
- host_supported: true,
+ shared_libs: [
+ "liblog",
+ ],
}
diff --git a/udrv/BUILD.gn b/udrv/BUILD.gn
index b42932e66..3712bd418 100644
--- a/udrv/BUILD.gn
+++ b/udrv/BUILD.gn
@@ -22,13 +22,10 @@ source_set("udrv") {
include_dirs = [
"include",
"uipc",
- "//bt/",
- "//bt/internal_include",
- "//bt/stack/include",
- "//bt/utils/include",
- ]
-
- configs += [
- "//bt:target_defaults"
+ "//",
+ "//internal_include",
+ "//stack/include",
+ "//utils/include",
+ "//third_party/libchrome",
]
}
diff --git a/udrv/ulinux/uipc.cc b/udrv/ulinux/uipc.cc
index ad1346d48..24fa71110 100644
--- a/udrv/ulinux/uipc.cc
+++ b/udrv/ulinux/uipc.cc
@@ -365,7 +365,7 @@ static void uipc_flush_ch_locked(tUIPC_STATE& uipc, tUIPC_CH_ID ch_id) {
/* read sufficiently large buffer to ensure flush empties socket faster than
it is getting refilled */
- (void)read(pfd.fd, &buf, UIPC_FLUSH_BUFFER_SIZE);
+ read(pfd.fd, &buf, UIPC_FLUSH_BUFFER_SIZE);
}
}
@@ -485,7 +485,7 @@ int uipc_start_main_server_thread(tUIPC_STATE& uipc) {
uipc.running = 1;
if (pthread_create(&uipc.tid, (const pthread_attr_t*)NULL, uipc_read_task,
- &uipc) != 0) {
+ &uipc) < 0) {
BTIF_TRACE_ERROR("uipc_thread_create pthread_create failed:%d", errno);
return -1;
}
diff --git a/utils/Android.bp b/utils/Android.bp
index befc5cff2..3a40750af 100644
--- a/utils/Android.bp
+++ b/utils/Android.bp
@@ -1,14 +1,5 @@
// Utils static library for target
// ========================================================
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "libbt-utils",
defaults: ["fluoride_defaults"],
@@ -24,5 +15,4 @@ cc_library_static {
shared_libs: [
"libprocessgroup",
],
- host_supported: true,
}
diff --git a/utils/BUILD.gn b/utils/BUILD.gn
index 23bc66054..46b7236d0 100644
--- a/utils/BUILD.gn
+++ b/utils/BUILD.gn
@@ -21,15 +21,9 @@ static_library("utils") {
include_dirs = [
"include",
- "//bt/",
- "//bt/stack/include",
- ]
-
- configs += [
- "//bt:target_defaults",
- ]
-
- deps = [
- "//bt/gd/rust/shim:init_flags_bridge_header",
+ "//",
+ "//stack/include",
+ "//third_party/libchrome",
+ "//third_party/googletest/googletest/include/",
]
}
diff --git a/utils/src/bt_utils.cc b/utils/src/bt_utils.cc
index 0ee53b282..fda47f6ba 100644
--- a/utils/src/bt_utils.cc
+++ b/utils/src/bt_utils.cc
@@ -135,7 +135,8 @@ void raise_priority_a2dp(tHIGH_PRIORITY_TASK high_task) {
}
if (rc) {
- LOG_WARN("failed to change sched policy, tid %d, err: %d", tid, errno);
+ LOG_WARN(LOG_TAG, "failed to change sched policy, tid %d, err: %d", tid,
+ errno);
}
// make A2DP threads use RT scheduling policy since they are part of the
@@ -146,7 +147,8 @@ void raise_priority_a2dp(tHIGH_PRIORITY_TASK high_task) {
const int rc = sched_setscheduler(tid, SCHED_FIFO, &rt_params);
if (rc != 0) {
- LOG_ERROR("%s unable to set SCHED_FIFO priority %d for tid %d, error %s",
+ LOG_ERROR(LOG_TAG,
+ "%s unable to set SCHED_FIFO priority %d for tid %d, error %s",
__func__, A2DP_RT_PRIORITY, tid, strerror(errno));
}
}
diff --git a/vendor_libs/Android.bp b/vendor_libs/Android.bp
index 2763e9bf3..a5092090d 100644
--- a/vendor_libs/Android.bp
+++ b/vendor_libs/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
subdirs = [
"test_vendor_lib",
"linux",
diff --git a/vendor_libs/linux/Android.bp b/vendor_libs/linux/Android.bp
index 99966dfa9..058140e18 100644
--- a/vendor_libs/linux/Android.bp
+++ b/vendor_libs/linux/Android.bp
@@ -1,12 +1,3 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
subdirs = [
"interface",
]
diff --git a/vendor_libs/linux/interface/Android.bp b/vendor_libs/linux/interface/Android.bp
index 85fde7d47..e7d161e3b 100644
--- a/vendor_libs/linux/interface/Android.bp
+++ b/vendor_libs/linux/interface/Android.bp
@@ -13,15 +13,6 @@
// See the License for the specific language governing permissions and
// limitations under the License.
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_binary {
name: "android.hardware.bluetooth@1.1-service.btlinux",
proprietary: true,
@@ -30,6 +21,7 @@ cc_binary {
"hci_packetizer.cc",
"h4_protocol.cc",
"bluetooth_hci.cc",
+ "async_fd_watcher.cc",
"service.cc",
],
cflags: [
@@ -38,7 +30,6 @@ cc_binary {
],
header_libs: ["libbluetooth_headers"],
shared_libs: [
- "android.hardware.bluetooth@1.0",
"android.hardware.bluetooth@1.1",
"libbase",
"libcutils",
@@ -46,29 +37,8 @@ cc_binary {
"liblog",
"libutils",
],
- static_libs: [
- "async_fd_watcher",
- ],
conlyflags: [
"-std=c99",
],
init_rc: ["android.hardware.bluetooth@1.1-service.btlinux.rc"],
}
-
-cc_library_static {
- name: "async_fd_watcher",
- proprietary: true,
- srcs: [
- "async_fd_watcher.cc",
- ],
- cflags: [
- "-Wall",
- "-Werror",
- ],
- shared_libs: [
- "liblog",
- ],
- export_include_dirs: [
- ".",
- ],
-} \ No newline at end of file
diff --git a/vendor_libs/linux/interface/async_fd_watcher.cc b/vendor_libs/linux/interface/async_fd_watcher.cc
index 87d2506f1..ef4a95951 100644
--- a/vendor_libs/linux/interface/async_fd_watcher.cc
+++ b/vendor_libs/linux/interface/async_fd_watcher.cc
@@ -102,9 +102,6 @@ int AsyncFdWatcher::stopThread() {
timeout_cb_ = nullptr;
}
- close(notification_listen_fd_);
- close(notification_write_fd_);
-
return 0;
}
diff --git a/vendor_libs/linux/interface/bluetooth_hci.cc b/vendor_libs/linux/interface/bluetooth_hci.cc
index fe5a86a17..bd987d885 100644
--- a/vendor_libs/linux/interface/bluetooth_hci.cc
+++ b/vendor_libs/linux/interface/bluetooth_hci.cc
@@ -281,15 +281,6 @@ Return<void> BluetoothHci::initialize_impl(
ALOGE("cb == nullptr! -> Unable to call initializationComplete(ERR)");
return Void();
}
- if (hci_handle_ != nullptr) {
- ALOGE("hci_handle != nullptr! -> Double attempt to initialize the HAL");
- auto hidl_status =
- cb->initializationComplete(V1_0::Status::INITIALIZATION_ERROR);
- if (!hidl_status.isOk()) {
- ALOGE("VendorInterface -> Unable to call initializationComplete(ERR)");
- }
- return Void();
- }
death_recipient_->setHasDied(false);
cb->linkToDeath(death_recipient_, 0);
diff --git a/vendor_libs/test_vendor_lib/Android.bp b/vendor_libs/test_vendor_lib/Android.bp
index 160dca81d..4523be59b 100644
--- a/vendor_libs/test_vendor_lib/Android.bp
+++ b/vendor_libs/test_vendor_lib/Android.bp
@@ -1,28 +1,15 @@
// simulation library for testing virtual devices
// ========================================================
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_static {
name: "libbt-rootcanal",
- defaults: [
- "gd_defaults",
- "gd_clang_tidy",
- ],
+ defaults: ["gd_defaults",],
+ header_libs: ["jni_headers"],
host_supported: true,
proprietary: true,
srcs: [
"model/controller/acl_connection.cc",
"model/controller/acl_connection_handler.cc",
"model/controller/dual_mode_controller.cc",
- "model/controller/isochronous_connection_handler.cc",
- "model/controller/le_advertiser.cc",
"model/controller/link_layer_controller.cc",
"model/controller/security_manager.cc",
"model/devices/beacon.cc",
@@ -33,6 +20,8 @@ cc_library_static {
"model/devices/device.cc",
"model/devices/device_properties.cc",
"model/devices/h4_packetizer.cc",
+ "model/devices/h4_protocol.cc",
+ "model/devices/hci_packetizer.cc",
"model/devices/hci_protocol.cc",
"model/devices/hci_socket_device.cc",
"model/devices/keyboard.cc",
@@ -65,7 +54,6 @@ cc_library_static {
generated_headers: [
"RootCanalGeneratedPackets_h",
"BluetoothGeneratedPackets_h",
- "libbt_init_flags_bridge_header",
],
include_dirs: [
"system/bt",
@@ -131,11 +119,10 @@ cc_test_host {
// Linux RootCanal Executable
// ========================================================
-cc_binary_host {
+cc_test_host {
name: "root-canal",
defaults: [
"libchrome_support_defaults",
- "gd_clang_tidy",
],
srcs: [
"desktop/root_canal_main.cc",
@@ -157,30 +144,13 @@ cc_binary_host {
],
shared_libs: [
"liblog",
- "libbacktrace",
],
static_libs: [
"libbt-rootcanal-types",
"libprotobuf-cpp-lite",
"libscriptedbeaconpayload-protos-lite",
"libbt-rootcanal",
- "breakpad_client",
- "libgflags",
],
- sanitize: {
- address: true,
- all_undefined: true,
- },
- target: {
- // TODO(b/181290178) remove it when sanitize option is supported by linux_bionic as well
- linux_bionic: {
- sanitize: {
- address: false,
- cfi: false,
- all_undefined: false,
- },
- },
- },
}
genrule {
diff --git a/vendor_libs/test_vendor_lib/data/Android.bp b/vendor_libs/test_vendor_lib/data/Android.bp
deleted file mode 100644
index ef33f4af3..000000000
--- a/vendor_libs/test_vendor_lib/data/Android.bp
+++ /dev/null
@@ -1,14 +0,0 @@
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
-prebuilt_etc_host {
- name: "controller_properties.json",
- src: "controller_properties.json",
- sub_dir: "rootcanal/data",
-}
diff --git a/vendor_libs/test_vendor_lib/desktop/root_canal_main.cc b/vendor_libs/test_vendor_lib/desktop/root_canal_main.cc
index ed84317f5..95bbfd3bc 100644
--- a/vendor_libs/test_vendor_lib/desktop/root_canal_main.cc
+++ b/vendor_libs/test_vendor_lib/desktop/root_canal_main.cc
@@ -18,71 +18,15 @@
#include <future>
-#include <client/linux/handler/exception_handler.h>
-
-#include <backtrace/Backtrace.h>
-#include <backtrace/backtrace_constants.h>
-
-#include <gflags/gflags.h>
-
#include "os/log.h"
using ::android::bluetooth::root_canal::TestEnvironment;
-DEFINE_string(controller_properties_file, "",
- "controller_properties.json file path");
-DEFINE_string(default_commands_file, "",
- "commands file which root-canal runs it as default");
-
constexpr uint16_t kTestPort = 6401;
constexpr uint16_t kHciServerPort = 6402;
constexpr uint16_t kLinkServerPort = 6403;
-extern "C" const char* __asan_default_options() {
- return "detect_container_overflow=0";
-}
-
-bool crash_callback(const void* crash_context, size_t crash_context_size,
- __attribute__((unused)) void* context) {
- pid_t tid = BACKTRACE_CURRENT_THREAD;
- if (crash_context_size >=
- sizeof(google_breakpad::ExceptionHandler::CrashContext)) {
- auto* ctx =
- static_cast<const google_breakpad::ExceptionHandler::CrashContext*>(
- crash_context);
- tid = ctx->tid;
- int signal_number = ctx->siginfo.si_signo;
- LOG_ERROR("Process crashed, signal: %s[%d], tid: %d",
- strsignal(signal_number), signal_number, ctx->tid);
- } else {
- LOG_ERROR("Process crashed, signal: unknown, tid: unknown");
- }
- std::unique_ptr<Backtrace> backtrace(
- Backtrace::Create(BACKTRACE_CURRENT_PROCESS, tid));
- if (backtrace == nullptr) {
- LOG_ERROR("Failed to create backtrace object");
- return false;
- }
- if (!backtrace->Unwind(0)) {
- LOG_ERROR("backtrace->Unwind failed");
- return false;
- }
- LOG_ERROR("Backtrace:");
- for (size_t i = 0; i < backtrace->NumFrames(); i++) {
- LOG_ERROR("%s", backtrace->FormatFrameData(i).c_str());
- }
- return true;
-}
-
int main(int argc, char** argv) {
- google_breakpad::MinidumpDescriptor descriptor(
- google_breakpad::MinidumpDescriptor::kMicrodumpOnConsole);
- google_breakpad::ExceptionHandler eh(descriptor, nullptr, nullptr, nullptr,
- true, -1);
- eh.set_crash_handler(crash_callback);
-
- gflags::ParseCommandLineFlags(&argc, &argv, true);
-
LOG_INFO("main");
uint16_t test_port = kTestPort;
uint16_t hci_server_port = kHciServerPort;
@@ -112,9 +56,7 @@ int main(int argc, char** argv) {
}
}
- TestEnvironment root_canal(test_port, hci_server_port, link_server_port,
- FLAGS_controller_properties_file,
- FLAGS_default_commands_file);
+ TestEnvironment root_canal(test_port, hci_server_port, link_server_port);
std::promise<void> barrier;
std::future<void> barrier_future = barrier.get_future();
root_canal.initialize(std::move(barrier));
diff --git a/vendor_libs/test_vendor_lib/desktop/test_environment.cc b/vendor_libs/test_vendor_lib/desktop/test_environment.cc
index dadb786e8..1ca3b8ce9 100644
--- a/vendor_libs/test_vendor_lib/desktop/test_environment.cc
+++ b/vendor_libs/test_vendor_lib/desktop/test_environment.cc
@@ -30,26 +30,20 @@ namespace bluetooth {
namespace root_canal {
using test_vendor_lib::AsyncTaskId;
+using test_vendor_lib::DualModeController;
using test_vendor_lib::TaskCallback;
void TestEnvironment::initialize(std::promise<void> barrier) {
- LOG_INFO();
+ LOG_INFO("%s", __func__);
barrier_ = std::move(barrier);
- auto user_id = async_manager_.GetNextUserId();
- test_channel_transport_.RegisterCommandHandler(
- [this, user_id](const std::string& name,
- const std::vector<std::string>& args) {
- async_manager_.ExecAsync(user_id, std::chrono::milliseconds(0),
- [this, name, args]() {
- if (name == "END_SIMULATION") {
- barrier_.set_value();
- } else {
- test_channel_.HandleCommand(name, args);
- }
- });
- });
+ test_channel_transport_.RegisterCommandHandler([this](const std::string& name, const std::vector<std::string>& args) {
+ async_manager_.ExecAsync(std::chrono::milliseconds(0),
+ [this, name, args]() { test_channel_.HandleCommand(name, args); });
+ });
+
+ test_model_.Reset();
SetUpTestChannel();
SetUpHciServer([this](int fd) { test_model_.IncomingHciConnection(fd); });
@@ -65,7 +59,6 @@ void TestEnvironment::initialize(std::promise<void> barrier) {
void TestEnvironment::close() {
LOG_INFO("%s", __func__);
- test_model_.Reset();
}
void TestEnvironment::SetUpHciServer(const std::function<void(int)>& connection_callback) {
@@ -133,7 +126,7 @@ int TestEnvironment::ConnectToRemoteServer(const std::string& server, int port)
return -1;
}
- struct sockaddr_in serv_addr {};
+ struct sockaddr_in serv_addr;
memset((void*)&serv_addr, 0, sizeof(serv_addr));
serv_addr.sin_family = AF_INET;
serv_addr.sin_addr.s_addr = INADDR_ANY;
@@ -154,15 +147,13 @@ int TestEnvironment::ConnectToRemoteServer(const std::string& server, int port)
void TestEnvironment::SetUpTestChannel() {
int socket_fd = test_channel_transport_.SetUp(test_port_);
- test_channel_.RegisterSendResponse([](const std::string& response) {
- LOG_INFO("No test channel: %s", response.c_str());
- });
test_channel_.AddPhy({"BR_EDR"});
test_channel_.AddPhy({"LOW_ENERGY"});
- test_channel_.SetTimerPeriod({"5"});
+ test_channel_.SetTimerPeriod({"10"});
test_channel_.StartTimer({});
- test_channel_.FromFile(default_commands_file_);
+ test_channel_.RegisterSendResponse(
+ [](const std::string& response) { LOG_INFO("No test channel: %s", response.c_str()); });
if (socket_fd == -1) {
LOG_ERROR("Test channel SetUp(%d) failed.", test_port_);
@@ -178,22 +169,13 @@ void TestEnvironment::SetUpTestChannel() {
return;
}
LOG_INFO("Test channel connection accepted.");
- if (test_channel_open_) {
- LOG_WARN("Only one connection at a time is supported");
- async_manager_.StopWatchingFileDescriptor(conn_fd);
- test_channel_transport_.SendResponse(conn_fd, "The connection is broken");
- return;
- }
- test_channel_open_ = true;
test_channel_.RegisterSendResponse(
- [this, conn_fd](const std::string& response) {
- test_channel_transport_.SendResponse(conn_fd, response);
- });
+ [this, conn_fd](const std::string& response) { test_channel_transport_.SendResponse(conn_fd, response); });
async_manager_.WatchFdForNonBlockingReads(conn_fd, [this](int conn_fd) {
test_channel_transport_.OnCommandReady(conn_fd, [this, conn_fd]() {
async_manager_.StopWatchingFileDescriptor(conn_fd);
- test_channel_open_ = false;
+ barrier_.set_value();
});
});
});
diff --git a/vendor_libs/test_vendor_lib/desktop/test_environment.h b/vendor_libs/test_vendor_lib/desktop/test_environment.h
index 815721eea..f48789b5f 100644
--- a/vendor_libs/test_vendor_lib/desktop/test_environment.h
+++ b/vendor_libs/test_vendor_lib/desktop/test_environment.h
@@ -30,16 +30,8 @@ namespace root_canal {
class TestEnvironment {
public:
- TestEnvironment(uint16_t test_port, uint16_t hci_server_port,
- uint16_t link_server_port,
- const std::string& controller_properties_file = "",
- const std::string& default_commands_file = "")
- : test_port_(test_port),
- hci_server_port_(hci_server_port),
- link_server_port_(link_server_port),
- default_commands_file_(default_commands_file),
- controller_(std::make_shared<test_vendor_lib::DualModeController>(
- controller_properties_file)) {}
+ TestEnvironment(uint16_t test_port, uint16_t hci_server_port, uint16_t link_server_port)
+ : test_port_(test_port), hci_server_port_(hci_server_port), link_server_port_(link_server_port) {}
void initialize(std::promise<void> barrier);
@@ -49,8 +41,6 @@ class TestEnvironment {
uint16_t test_port_;
uint16_t hci_server_port_;
uint16_t link_server_port_;
- std::string default_commands_file_;
- bool test_channel_open_{false};
std::promise<void> barrier_;
test_vendor_lib::AsyncManager async_manager_;
@@ -67,31 +57,18 @@ class TestEnvironment {
test_vendor_lib::TestChannelTransport remote_link_layer_transport_;
test_vendor_lib::TestModel test_model_{
- [this]() { return async_manager_.GetNextUserId(); },
- [this](test_vendor_lib::AsyncUserId user_id,
- std::chrono::milliseconds delay,
- const test_vendor_lib::TaskCallback& task) {
- return async_manager_.ExecAsync(user_id, delay, task);
+ [this](std::chrono::milliseconds delay, const test_vendor_lib::TaskCallback& task) {
+ return async_manager_.ExecAsync(delay, task);
},
- [this](test_vendor_lib::AsyncUserId user_id,
- std::chrono::milliseconds delay, std::chrono::milliseconds period,
+ [this](std::chrono::milliseconds delay, std::chrono::milliseconds period,
const test_vendor_lib::TaskCallback& task) {
- return async_manager_.ExecAsyncPeriodically(user_id, delay, period,
- task);
- },
-
- [this](test_vendor_lib::AsyncUserId user) {
- async_manager_.CancelAsyncTasksFromUser(user);
+ return async_manager_.ExecAsyncPeriodically(delay, period, task);
},
- [this](test_vendor_lib::AsyncTaskId task) {
- async_manager_.CancelAsyncTask(task);
- },
+ [this](test_vendor_lib::AsyncTaskId task) { async_manager_.CancelAsyncTask(task); },
- [this](const std::string& server, int port) {
- return ConnectToRemoteServer(server, port);
- }};
+ [this](const std::string& server, int port) { return ConnectToRemoteServer(server, port); }};
test_vendor_lib::TestCommandHandler test_channel_{test_model_};
};
diff --git a/vendor_libs/test_vendor_lib/include/acl.h b/vendor_libs/test_vendor_lib/include/acl.h
new file mode 100644
index 000000000..c7c7b34f7
--- /dev/null
+++ b/vendor_libs/test_vendor_lib/include/acl.h
@@ -0,0 +1,42 @@
+/*
+ * Copyright 2017 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#pragma once
+
+#include <cstdint>
+
+namespace test_vendor_lib {
+namespace acl {
+
+// ACL data packets are specified in the Bluetooth Core Specification Version
+// 4.2, Volume 2, Part E, Section 5.4.2
+static constexpr uint16_t kReservedHandle = 0xF00;
+
+enum class PacketBoundaryFlagsType : uint8_t {
+ FIRST_NON_AUTOMATICALLY_FLUSHABLE = 0,
+ CONTINUING = 1,
+ FIRST_AUTOMATICALLY_FLUSHABLE = 2,
+ COMPLETE = 3
+};
+
+enum class BroadcastFlagsType : uint8_t {
+ POINT_TO_POINT = 0,
+ ACTIVE_SLAVE_BROADCAST = 1,
+ PARKED_SLAVE_BROADCAST = 2,
+ RESERVED = 3
+};
+} // namespace acl
+} // namespace test_vendor_lib
diff --git a/gd/hci/fuzz/status_vs_complete_commands.h b/vendor_libs/test_vendor_lib/include/hci.h
index c50ce5e53..eaa74c0c0 100644
--- a/gd/hci/fuzz/status_vs_complete_commands.h
+++ b/vendor_libs/test_vendor_lib/include/hci.h
@@ -1,5 +1,5 @@
/*
- * Copyright 2019 The Android Open Source Project
+ * Copyright 2018 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
@@ -15,15 +15,18 @@
*/
#pragma once
+#include <cstdint>
-#include "hci/hci_packets.h"
-
-namespace bluetooth {
+namespace test_vendor_lib {
namespace hci {
-namespace fuzz {
-bool uses_command_status(hci::OpCode code);
+enum class PacketType : uint8_t {
+ UNKNOWN = 0,
+ COMMAND = 1,
+ ACL = 2,
+ SCO = 3,
+ EVENT = 4,
+};
-}
} // namespace hci
-} // namespace bluetooth
+} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/controller/acl_connection_handler.cc b/vendor_libs/test_vendor_lib/model/controller/acl_connection_handler.cc
index c9052a356..d798e78ba 100644
--- a/vendor_libs/test_vendor_lib/model/controller/acl_connection_handler.cc
+++ b/vendor_libs/test_vendor_lib/model/controller/acl_connection_handler.cc
@@ -16,10 +16,11 @@
#include "acl_connection_handler.h"
-#include <hci/hci_packets.h>
+#include "os/log.h"
#include "hci/address.h"
-#include "os/log.h"
+
+using std::shared_ptr;
namespace test_vendor_lib {
@@ -28,16 +29,18 @@ using ::bluetooth::hci::AddressType;
using ::bluetooth::hci::AddressWithType;
bool AclConnectionHandler::HasHandle(uint16_t handle) const {
- return acl_connections_.count(handle) != 0;
+ if (acl_connections_.count(handle) == 0) {
+ return false;
+ }
+ return true;
}
uint16_t AclConnectionHandler::GetUnusedHandle() {
- while (HasHandle(last_handle_) ||
- isochronous_connection_handler_.HasHandle(last_handle_)) {
- last_handle_ = (last_handle_ + 1) % kReservedHandle;
+ while (acl_connections_.count(last_handle_) == 1) {
+ last_handle_ = (last_handle_ + 1) % acl::kReservedHandle;
}
uint16_t unused_handle = last_handle_;
- last_handle_ = (last_handle_ + 1) % kReservedHandle;
+ last_handle_ = (last_handle_ + 1) % acl::kReservedHandle;
return unused_handle;
}
@@ -116,7 +119,7 @@ uint16_t AclConnectionHandler::CreateConnection(Address addr,
Phy::Type::BR_EDR});
return handle;
}
- return kReservedHandle;
+ return acl::kReservedHandle;
}
uint16_t AclConnectionHandler::CreateLeConnection(AddressWithType addr,
@@ -127,7 +130,7 @@ uint16_t AclConnectionHandler::CreateLeConnection(AddressWithType addr,
handle, AclConnection{addr, own_addr, Phy::Type::LOW_ENERGY});
return handle;
}
- return kReservedHandle;
+ return acl::kReservedHandle;
}
bool AclConnectionHandler::Disconnect(uint16_t handle) {
@@ -140,7 +143,7 @@ uint16_t AclConnectionHandler::GetHandle(AddressWithType addr) const {
return std::get<0>(pair);
}
}
- return kReservedHandle;
+ return acl::kReservedHandle;
}
uint16_t AclConnectionHandler::GetHandleOnlyAddress(
@@ -150,7 +153,7 @@ uint16_t AclConnectionHandler::GetHandleOnlyAddress(
return std::get<0>(pair);
}
}
- return kReservedHandle;
+ return acl::kReservedHandle;
}
AddressWithType AclConnectionHandler::GetAddress(uint16_t handle) const {
@@ -193,210 +196,4 @@ Phy::Type AclConnectionHandler::GetPhyType(uint16_t handle) const {
return acl_connections_.at(handle).GetPhyType();
}
-std::unique_ptr<bluetooth::hci::LeSetCigParametersCompleteBuilder>
-AclConnectionHandler::SetCigParameters(
- uint8_t id, uint32_t sdu_interval_m_to_s, uint32_t sdu_interval_s_to_m,
- bluetooth::hci::ClockAccuracy accuracy, bluetooth::hci::Packing packing,
- bluetooth::hci::Enable framed, uint16_t max_transport_latency_m_to_s_,
- uint16_t max_transport_latency_s_to_m_,
- std::vector<bluetooth::hci::CisParametersConfig>& streams) {
- std::vector<uint16_t> handles;
- GroupParameters group_parameters{
- .id = id,
- .sdu_interval_m_to_s = sdu_interval_m_to_s,
- .sdu_interval_s_to_m = sdu_interval_s_to_m,
- .interleaved = packing == bluetooth::hci::Packing::INTERLEAVED,
- .framed = framed == bluetooth::hci::Enable::ENABLED,
- .max_transport_latency_m_to_s = max_transport_latency_m_to_s_,
- .max_transport_latency_s_to_m = max_transport_latency_s_to_m_};
- std::vector<StreamParameters> stream_parameters;
- for (size_t i = 0; i < streams.size(); i++) {
- auto handle = GetUnusedHandle();
- StreamParameters a{.group_id = group_parameters.id,
- .stream_id = streams[i].cis_id_,
- .max_sdu_m_to_s = streams[i].max_sdu_m_to_s_,
- .max_sdu_s_to_m = streams[i].max_sdu_s_to_m_,
- .rtn_m_to_s = streams[i].rtn_m_to_s_,
- .rtn_s_to_m = streams[i].rtn_s_to_m_,
- .handle = handle};
- handles.push_back(handle);
- stream_parameters.push_back(std::move(a));
- }
-
- return isochronous_connection_handler_.SetCigParameters(
- group_parameters, stream_parameters, std::move(handles));
-}
-
-void AclConnectionHandler::CreatePendingCis(
- bluetooth::hci::CreateCisConfig config) {
- CisHandles handles;
- handles.cis_handle_ = config.cis_connection_handle_;
- handles.acl_handle_ = config.acl_connection_handle_;
- handles.remote_cis_handle_ = kReservedHandle;
- pending_streams_.emplace_back(std::move(handles));
-}
-
-bool AclConnectionHandler::ConnectCis(uint16_t handle) {
- size_t position;
- CisHandles connection;
- for (position = 0; position < pending_streams_.size(); position++) {
- if (handle == pending_streams_[position].cis_handle_) {
- LOG_INFO("Found handle 0x%04hx", handle);
- connection = pending_streams_[position];
- pending_streams_.erase(pending_streams_.begin() + position);
- connected_streams_.push_back(connection);
- ASSERT(connection.cis_handle_ != kReservedHandle);
- ASSERT(connection.acl_handle_ != kReservedHandle);
- ASSERT(connection.remote_cis_handle_ != kReservedHandle);
- return true;
- }
- }
-
- LOG_INFO("No pending CIS connection with handle 0x%04hx", handle);
- return false;
-}
-
-void AclConnectionHandler::SetRemoteCisHandle(uint16_t handle,
- uint16_t remote_handle) {
- for (size_t position = 0; position < pending_streams_.size(); position++) {
- if (handle == pending_streams_[position].cis_handle_) {
- LOG_INFO("Added remote handle 0x%04hx to handle 0x%04hx", remote_handle,
- pending_streams_[position].cis_handle_);
- pending_streams_[position].remote_cis_handle_ = remote_handle;
- return;
- }
- }
- LOG_INFO("Couldn't find CIS connection with handle 0x%04hx", handle);
-}
-
-bool AclConnectionHandler::RejectCis(uint16_t handle) {
- size_t position;
- for (position = 0; position < pending_streams_.size(); position++) {
- if (handle == pending_streams_[position].cis_handle_) {
- pending_streams_.erase(pending_streams_.begin() + position);
- break;
- }
- }
- if (position == pending_streams_.size()) {
- LOG_INFO("No pending connection with handle 0x%hx", handle);
- return false;
- }
- return true;
-}
-
-uint16_t AclConnectionHandler::GetPendingAclHandle(uint16_t cis_handle) const {
- size_t position;
- uint16_t handle = 0xffff;
- for (position = 0; position < pending_streams_.size(); position++) {
- if (cis_handle == pending_streams_[position].cis_handle_) {
- handle = pending_streams_[position].acl_handle_;
- break;
- }
- }
- if (position == pending_streams_.size()) {
- LOG_INFO("No pending connection with handle 0x%hx", cis_handle);
- }
- return handle;
-}
-
-bool AclConnectionHandler::DisconnectCis(uint16_t cis_handle) {
- size_t position;
- for (position = 0; position < connected_streams_.size(); position++) {
- if (cis_handle == connected_streams_[position].cis_handle_) {
- connected_streams_.erase(connected_streams_.begin() + position);
- break;
- }
- }
- if (position == connected_streams_.size()) {
- LOG_INFO("No connected stream 0x%hx", cis_handle);
- return false;
- }
- return true;
-}
-
-bluetooth::hci::ErrorCode AclConnectionHandler::RemoveCig(uint8_t cig_id) {
- for (const auto& stream : connected_streams_) {
- if (isochronous_connection_handler_.GetGroupId(stream.cis_handle_) ==
- cig_id) {
- return bluetooth::hci::ErrorCode::COMMAND_DISALLOWED;
- }
- }
- for (const auto& stream : pending_streams_) {
- if (isochronous_connection_handler_.GetGroupId(stream.cis_handle_) ==
- cig_id) {
- return bluetooth::hci::ErrorCode::COMMAND_DISALLOWED;
- }
- }
- auto status = isochronous_connection_handler_.RemoveCig(cig_id);
- if (status == bluetooth::hci::ErrorCode::SUCCESS) {
- // Clean up?
- }
- return status;
-}
-
-bool AclConnectionHandler::HasPendingCisConnection(uint16_t handle) const {
- for (const auto& config : pending_streams_) {
- if (config.cis_handle_ == handle) {
- return true;
- }
- }
- return false;
-}
-
-bool AclConnectionHandler::HasPendingCis() const {
- return !pending_streams_.empty();
-}
-
-bool AclConnectionHandler::HasConnectedCis(uint16_t handle) const {
- for (const auto& cs : connected_streams_) {
- if (handle == cs.cis_handle_) {
- return true;
- }
- }
- return false;
-}
-
-bool AclConnectionHandler::HasCisHandle(uint16_t handle) const {
- for (const auto& cs : pending_streams_) {
- if (handle == cs.cis_handle_) {
- return true;
- }
- }
- for (const auto& cs : connected_streams_) {
- if (handle == cs.cis_handle_) {
- return true;
- }
- }
- return isochronous_connection_handler_.HasHandle(handle);
-}
-
-uint16_t AclConnectionHandler::GetAclHandleForCisHandle(
- uint16_t cis_handle) const {
- for (const auto& cs : connected_streams_) {
- if (cis_handle == cs.cis_handle_) {
- return cs.acl_handle_;
- }
- }
- return kReservedHandle;
-}
-
-uint16_t AclConnectionHandler::GetRemoteCisHandleForCisHandle(
- uint16_t cis_handle) const {
- for (const auto& cs : connected_streams_) {
- if (cis_handle == cs.cis_handle_) {
- return cs.remote_cis_handle_;
- }
- }
- return kReservedHandle;
-}
-
-GroupParameters AclConnectionHandler::GetGroupParameters(uint8_t id) const {
- return isochronous_connection_handler_.GetGroupParameters(id);
-}
-
-StreamParameters AclConnectionHandler::GetStreamParameters(
- uint16_t handle) const {
- return isochronous_connection_handler_.GetStreamParameters(handle);
-}
-
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/controller/acl_connection_handler.h b/vendor_libs/test_vendor_lib/model/controller/acl_connection_handler.h
index feca03cc2..0f0b5a74a 100644
--- a/vendor_libs/test_vendor_lib/model/controller/acl_connection_handler.h
+++ b/vendor_libs/test_vendor_lib/model/controller/acl_connection_handler.h
@@ -23,11 +23,10 @@
#include "acl_connection.h"
#include "hci/address.h"
#include "hci/address_with_type.h"
-#include "isochronous_connection_handler.h"
+#include "include/acl.h"
#include "phy.h"
namespace test_vendor_lib {
-static constexpr uint16_t kReservedHandle = 0xF00;
class AclConnectionHandler {
public:
@@ -64,44 +63,6 @@ class AclConnectionHandler {
Phy::Type GetPhyType(uint16_t handle) const;
- std::unique_ptr<bluetooth::hci::LeSetCigParametersCompleteBuilder>
- SetCigParameters(uint8_t id, uint32_t sdu_interval_m_to_s,
- uint32_t sdu_interval_s_to_m,
- bluetooth::hci::ClockAccuracy accuracy,
- bluetooth::hci::Packing packing,
- bluetooth::hci::Enable framing,
- uint16_t max_transport_latency_m_to_s_,
- uint16_t max_transport_latency_s_to_m_,
- std::vector<bluetooth::hci::CisParametersConfig>& streams);
-
- void CreatePendingCis(bluetooth::hci::CreateCisConfig config);
-
- bool ConnectCis(uint16_t handle);
-
- void SetRemoteCisHandle(uint16_t handle, uint16_t remote_handle);
-
- uint16_t GetPendingAclHandle(uint16_t cis_handle) const;
-
- bool RejectCis(uint16_t handle);
-
- bool DisconnectCis(uint16_t handle);
-
- bluetooth::hci::ErrorCode RemoveCig(uint8_t cig_id);
-
- bool HasPendingCis() const;
-
- bool HasPendingCisConnection(uint16_t handle) const;
-
- bool HasCisHandle(uint16_t handle) const;
-
- bool HasConnectedCis(uint16_t handle) const;
-
- uint16_t GetAclHandleForCisHandle(uint16_t cis_handle) const;
- uint16_t GetRemoteCisHandleForCisHandle(uint16_t cis_handle) const;
-
- StreamParameters GetStreamParameters(uint16_t handle) const;
- GroupParameters GetGroupParameters(uint8_t id) const;
-
private:
std::unordered_map<uint16_t, AclConnection> acl_connections_;
bool classic_connection_pending_{false};
@@ -114,15 +75,7 @@ class AclConnectionHandler {
bluetooth::hci::AddressType::PUBLIC_DEVICE_ADDRESS};
uint16_t GetUnusedHandle();
- uint16_t last_handle_{kReservedHandle - 2};
- IsochronousConnectionHandler isochronous_connection_handler_;
- struct CisHandles {
- uint16_t acl_handle_ = kReservedHandle;
- uint16_t cis_handle_ = kReservedHandle;
- uint16_t remote_cis_handle_ = kReservedHandle;
- };
- std::vector<CisHandles> connected_streams_;
- std::vector<CisHandles> pending_streams_;
+ uint16_t last_handle_{acl::kReservedHandle - 2};
};
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/controller/connected_isochronous_group.h b/vendor_libs/test_vendor_lib/model/controller/connected_isochronous_group.h
deleted file mode 100644
index c3df80a66..000000000
--- a/vendor_libs/test_vendor_lib/model/controller/connected_isochronous_group.h
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include "hci/hci_packets.h"
-#include "model/controller/connected_isochronous_stream.h"
-
-namespace test_vendor_lib {
-
-class GroupParameters {
- public:
- uint8_t id;
- uint32_t sdu_interval_m_to_s;
- uint32_t sdu_interval_s_to_m;
- bool interleaved;
- bool framed;
- uint16_t max_transport_latency_m_to_s;
- uint16_t max_transport_latency_s_to_m;
-};
-
-class ConnectedIsochronousGroup {
- public:
- ConnectedIsochronousGroup(GroupParameters parameters,
- std::vector<ConnectedIsochronousStream> streams)
- : parameters_(parameters), streams_(std::move(streams)) {}
-
- virtual ~ConnectedIsochronousGroup() = default;
-
- bool HasConnectedStream() const {
- for (auto& stream : streams_) {
- if (stream.IsConnected()) {
- return true;
- }
- }
- return false;
- }
-
- bool StreamIsConnected(uint16_t handle) const {
- return streams_.at(handle).IsConnected();
- }
-
- bool HasStreams() const { return !streams_.empty(); }
-
- GroupParameters GetParameters() const { return parameters_; }
-
- StreamParameters GetStreamParameters(uint16_t handle) const {
- for (const auto& stream : streams_) {
- if (stream.GetHandle() == handle) {
- return stream.GetConfig();
- }
- }
- return StreamParameters{};
- }
-
- private:
- GroupParameters parameters_;
- std::vector<ConnectedIsochronousStream> streams_;
-};
-
-} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/controller/connected_isochronous_stream.h b/vendor_libs/test_vendor_lib/model/controller/connected_isochronous_stream.h
deleted file mode 100644
index 49a839476..000000000
--- a/vendor_libs/test_vendor_lib/model/controller/connected_isochronous_stream.h
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-
-#include "hci/hci_packets.h"
-
-namespace test_vendor_lib {
-
-class StreamParameters {
- public:
- uint8_t group_id;
- uint8_t stream_id;
- uint16_t max_sdu_m_to_s;
- uint16_t max_sdu_s_to_m;
- uint8_t rtn_m_to_s;
- uint8_t rtn_s_to_m;
- uint16_t handle;
-};
-
-class ConnectedIsochronousStream {
- public:
- ConnectedIsochronousStream(StreamParameters& stream_param)
- : config_(stream_param) {}
-
- virtual ~ConnectedIsochronousStream() = default;
-
- bool IsConnected() const { return is_connected_; }
- StreamParameters GetConfig() const { return config_; }
-
- uint16_t GetHandle() const { return config_.handle; }
- void Connect() { is_connected_ = true; }
-
- void Disconnect() { is_connected_ = false; }
-
- private:
- bool is_connected_{false};
- StreamParameters config_;
-};
-} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/controller/dual_mode_controller.cc b/vendor_libs/test_vendor_lib/model/controller/dual_mode_controller.cc
index 8e142cbcf..5aed73d78 100644
--- a/vendor_libs/test_vendor_lib/model/controller/dual_mode_controller.cc
+++ b/vendor_libs/test_vendor_lib/model/controller/dual_mode_controller.cc
@@ -35,15 +35,12 @@ namespace test_vendor_lib {
constexpr char DualModeController::kControllerPropertiesFile[];
constexpr uint16_t DualModeController::kSecurityManagerNumKeys;
constexpr uint16_t kNumCommandPackets = 0x01;
-constexpr uint16_t kLeMaximumAdvertisingDataLength = 256;
-constexpr uint16_t kLeMaximumDataLength = 64;
-constexpr uint16_t kLeMaximumDataTime = 0x148;
// Device methods.
void DualModeController::Initialize(const std::vector<std::string>& args) {
if (args.size() < 2) return;
- Address addr{};
+ Address addr;
if (Address::FromString(args[1], addr)) {
properties_.SetAddress(addr);
} else {
@@ -72,7 +69,7 @@ void DualModeController::SendCommandCompleteUnknownOpCodeEvent(uint16_t command_
raw_builder_ptr->AddOctets1(
static_cast<uint8_t>(ErrorCode::UNKNOWN_HCI_COMMAND));
- auto packet = gd_hci::EventBuilder::Create(
+ auto packet = gd_hci::EventPacketBuilder::Create(
gd_hci::EventCode::COMMAND_COMPLETE, std::move(raw_builder_ptr));
send_event_(std::move(packet));
}
@@ -81,7 +78,7 @@ DualModeController::DualModeController(const std::string& properties_filename, u
: Device(properties_filename), security_manager_(num_keys) {
loopback_mode_ = LoopbackMode::NO_LOOPBACK;
- Address public_address{};
+ Address public_address;
ASSERT(Address::FromString("3C:5A:B4:04:05:06", public_address));
properties_.SetAddress(public_address);
@@ -91,215 +88,158 @@ DualModeController::DualModeController(const std::string& properties_filename, u
DualModeController::SendLinkLayerPacket(packet, phy_type);
});
- std::array<uint8_t, 64> supported_commands;
- for (size_t i = 0; i < 64; i++) {
- supported_commands[i] = 0;
- }
-
-#define SET_HANDLER(name, method) \
- active_hci_commands_[OpCode::name] = [this](CommandView param) { \
- method(std::move(param)); \
+#define SET_HANDLER(opcode, method) \
+ active_hci_commands_[opcode] = [this](CommandPacketView param) { \
+ method(param); \
};
-
-#define SET_SUPPORTED(name, method) \
- SET_HANDLER(name, method); \
- { \
- uint16_t index = (uint16_t)bluetooth::hci::OpCodeIndex::name; \
- uint16_t byte_index = index / 10; \
- uint8_t bit = 1 << (index % 10); \
- if (byte_index < 36) { \
- supported_commands[byte_index] = supported_commands[byte_index] | bit; \
- } \
- }
-
- SET_SUPPORTED(RESET, Reset);
- SET_SUPPORTED(READ_BUFFER_SIZE, ReadBufferSize);
- SET_SUPPORTED(HOST_BUFFER_SIZE, HostBufferSize);
- SET_SUPPORTED(SNIFF_SUBRATING, SniffSubrating);
- SET_SUPPORTED(READ_ENCRYPTION_KEY_SIZE, ReadEncryptionKeySize);
- SET_SUPPORTED(READ_LOCAL_VERSION_INFORMATION, ReadLocalVersionInformation);
- SET_SUPPORTED(READ_BD_ADDR, ReadBdAddr);
- SET_HANDLER(READ_LOCAL_SUPPORTED_COMMANDS, ReadLocalSupportedCommands);
- SET_SUPPORTED(READ_LOCAL_SUPPORTED_FEATURES, ReadLocalSupportedFeatures);
- SET_SUPPORTED(READ_LOCAL_SUPPORTED_CODECS_V1, ReadLocalSupportedCodecs);
- SET_SUPPORTED(READ_LOCAL_EXTENDED_FEATURES, ReadLocalExtendedFeatures);
- SET_SUPPORTED(READ_REMOTE_EXTENDED_FEATURES, ReadRemoteExtendedFeatures);
- SET_SUPPORTED(SWITCH_ROLE, SwitchRole);
- SET_SUPPORTED(READ_REMOTE_SUPPORTED_FEATURES, ReadRemoteSupportedFeatures);
- SET_SUPPORTED(READ_CLOCK_OFFSET, ReadClockOffset);
- SET_SUPPORTED(IO_CAPABILITY_REQUEST_REPLY, IoCapabilityRequestReply);
- SET_SUPPORTED(USER_CONFIRMATION_REQUEST_REPLY, UserConfirmationRequestReply);
- SET_SUPPORTED(USER_CONFIRMATION_REQUEST_NEGATIVE_REPLY,
- UserConfirmationRequestNegativeReply);
- SET_SUPPORTED(USER_PASSKEY_REQUEST_REPLY, UserPasskeyRequestReply);
- SET_SUPPORTED(USER_PASSKEY_REQUEST_NEGATIVE_REPLY,
- UserPasskeyRequestNegativeReply);
- SET_SUPPORTED(PIN_CODE_REQUEST_REPLY, PinCodeRequestReply);
- SET_SUPPORTED(PIN_CODE_REQUEST_NEGATIVE_REPLY, PinCodeRequestNegativeReply);
- SET_SUPPORTED(REMOTE_OOB_DATA_REQUEST_REPLY, RemoteOobDataRequestReply);
- SET_SUPPORTED(REMOTE_OOB_DATA_REQUEST_NEGATIVE_REPLY,
- RemoteOobDataRequestNegativeReply);
- SET_SUPPORTED(IO_CAPABILITY_REQUEST_NEGATIVE_REPLY,
- IoCapabilityRequestNegativeReply);
- SET_SUPPORTED(REMOTE_OOB_EXTENDED_DATA_REQUEST_REPLY,
- RemoteOobExtendedDataRequestReply);
- SET_SUPPORTED(READ_INQUIRY_RESPONSE_TRANSMIT_POWER_LEVEL,
- ReadInquiryResponseTransmitPowerLevel);
- SET_SUPPORTED(SEND_KEYPRESS_NOTIFICATION, SendKeypressNotification);
- SET_HANDLER(SET_EVENT_MASK_PAGE_2, SetEventMaskPage2);
- SET_SUPPORTED(READ_LOCAL_OOB_DATA, ReadLocalOobData);
- SET_SUPPORTED(READ_LOCAL_OOB_EXTENDED_DATA, ReadLocalOobExtendedData);
- SET_SUPPORTED(WRITE_SIMPLE_PAIRING_MODE, WriteSimplePairingMode);
- SET_SUPPORTED(WRITE_LE_HOST_SUPPORT, WriteLeHostSupport);
- SET_SUPPORTED(WRITE_SECURE_CONNECTIONS_HOST_SUPPORT,
- WriteSecureConnectionsHostSupport);
- SET_SUPPORTED(SET_EVENT_MASK, SetEventMask);
- SET_SUPPORTED(READ_INQUIRY_MODE, ReadInquiryMode);
- SET_SUPPORTED(WRITE_INQUIRY_MODE, WriteInquiryMode);
- SET_SUPPORTED(READ_PAGE_SCAN_TYPE, ReadPageScanType);
- SET_SUPPORTED(WRITE_PAGE_SCAN_TYPE, WritePageScanType);
- SET_SUPPORTED(WRITE_INQUIRY_SCAN_TYPE, WriteInquiryScanType);
- SET_SUPPORTED(READ_INQUIRY_SCAN_TYPE, ReadInquiryScanType);
- SET_SUPPORTED(AUTHENTICATION_REQUESTED, AuthenticationRequested);
- SET_SUPPORTED(SET_CONNECTION_ENCRYPTION, SetConnectionEncryption);
- SET_SUPPORTED(CHANGE_CONNECTION_LINK_KEY, ChangeConnectionLinkKey);
- SET_SUPPORTED(CENTRAL_LINK_KEY, CentralLinkKey);
- SET_SUPPORTED(WRITE_AUTHENTICATION_ENABLE, WriteAuthenticationEnable);
- SET_SUPPORTED(READ_AUTHENTICATION_ENABLE, ReadAuthenticationEnable);
- SET_SUPPORTED(WRITE_CLASS_OF_DEVICE, WriteClassOfDevice);
- SET_SUPPORTED(READ_PAGE_TIMEOUT, ReadPageTimeout);
- SET_SUPPORTED(WRITE_PAGE_TIMEOUT, WritePageTimeout);
- SET_SUPPORTED(WRITE_LINK_SUPERVISION_TIMEOUT, WriteLinkSupervisionTimeout);
- SET_SUPPORTED(HOLD_MODE, HoldMode);
- SET_SUPPORTED(SNIFF_MODE, SniffMode);
- SET_SUPPORTED(EXIT_SNIFF_MODE, ExitSniffMode);
- SET_SUPPORTED(QOS_SETUP, QosSetup);
- SET_SUPPORTED(READ_DEFAULT_LINK_POLICY_SETTINGS,
- ReadDefaultLinkPolicySettings);
- SET_SUPPORTED(WRITE_DEFAULT_LINK_POLICY_SETTINGS,
- WriteDefaultLinkPolicySettings);
- SET_SUPPORTED(FLOW_SPECIFICATION, FlowSpecification);
- SET_SUPPORTED(WRITE_LINK_POLICY_SETTINGS, WriteLinkPolicySettings);
- SET_SUPPORTED(CHANGE_CONNECTION_PACKET_TYPE, ChangeConnectionPacketType);
- SET_SUPPORTED(WRITE_LOCAL_NAME, WriteLocalName);
- SET_SUPPORTED(READ_LOCAL_NAME, ReadLocalName);
- SET_SUPPORTED(WRITE_EXTENDED_INQUIRY_RESPONSE, WriteExtendedInquiryResponse);
- SET_SUPPORTED(REFRESH_ENCRYPTION_KEY, RefreshEncryptionKey);
- SET_SUPPORTED(WRITE_VOICE_SETTING, WriteVoiceSetting);
- SET_SUPPORTED(READ_NUMBER_OF_SUPPORTED_IAC, ReadNumberOfSupportedIac);
- SET_SUPPORTED(READ_CURRENT_IAC_LAP, ReadCurrentIacLap);
- SET_SUPPORTED(WRITE_CURRENT_IAC_LAP, WriteCurrentIacLap);
- SET_SUPPORTED(READ_PAGE_SCAN_ACTIVITY, ReadPageScanActivity);
- SET_SUPPORTED(WRITE_PAGE_SCAN_ACTIVITY, WritePageScanActivity);
- SET_SUPPORTED(READ_INQUIRY_SCAN_ACTIVITY, ReadInquiryScanActivity);
- SET_SUPPORTED(WRITE_INQUIRY_SCAN_ACTIVITY, WriteInquiryScanActivity);
- SET_SUPPORTED(READ_SCAN_ENABLE, ReadScanEnable);
- SET_SUPPORTED(WRITE_SCAN_ENABLE, WriteScanEnable);
- SET_SUPPORTED(SET_EVENT_FILTER, SetEventFilter);
- SET_SUPPORTED(INQUIRY, Inquiry);
- SET_SUPPORTED(INQUIRY_CANCEL, InquiryCancel);
- SET_SUPPORTED(ACCEPT_CONNECTION_REQUEST, AcceptConnectionRequest);
- SET_SUPPORTED(REJECT_CONNECTION_REQUEST, RejectConnectionRequest);
- SET_SUPPORTED(LINK_KEY_REQUEST_REPLY, LinkKeyRequestReply);
- SET_SUPPORTED(LINK_KEY_REQUEST_NEGATIVE_REPLY, LinkKeyRequestNegativeReply);
- SET_SUPPORTED(DELETE_STORED_LINK_KEY, DeleteStoredLinkKey);
- SET_SUPPORTED(REMOTE_NAME_REQUEST, RemoteNameRequest);
- SET_SUPPORTED(LE_SET_EVENT_MASK, LeSetEventMask);
- SET_SUPPORTED(LE_READ_BUFFER_SIZE_V1, LeReadBufferSize);
- SET_SUPPORTED(LE_READ_LOCAL_SUPPORTED_FEATURES, LeReadLocalSupportedFeatures);
- SET_SUPPORTED(LE_SET_RANDOM_ADDRESS, LeSetRandomAddress);
- SET_SUPPORTED(LE_SET_ADVERTISING_PARAMETERS, LeSetAdvertisingParameters);
- SET_SUPPORTED(LE_READ_ADVERTISING_PHYSICAL_CHANNEL_TX_POWER,
- LeReadAdvertisingPhysicalChannelTxPower);
- SET_SUPPORTED(LE_SET_ADVERTISING_DATA, LeSetAdvertisingData);
- SET_SUPPORTED(LE_SET_SCAN_RESPONSE_DATA, LeSetScanResponseData);
- SET_SUPPORTED(LE_SET_ADVERTISING_ENABLE, LeSetAdvertisingEnable);
- SET_SUPPORTED(LE_SET_SCAN_PARAMETERS, LeSetScanParameters);
- SET_SUPPORTED(LE_SET_SCAN_ENABLE, LeSetScanEnable);
- SET_SUPPORTED(LE_CREATE_CONNECTION, LeCreateConnection);
- SET_SUPPORTED(CREATE_CONNECTION, CreateConnection);
- SET_SUPPORTED(CREATE_CONNECTION_CANCEL, CreateConnectionCancel);
- SET_SUPPORTED(DISCONNECT, Disconnect);
- SET_SUPPORTED(LE_CREATE_CONNECTION_CANCEL, LeConnectionCancel);
- SET_SUPPORTED(LE_READ_CONNECT_LIST_SIZE, LeReadConnectListSize);
- SET_SUPPORTED(LE_CLEAR_CONNECT_LIST, LeClearConnectList);
- SET_SUPPORTED(LE_ADD_DEVICE_TO_CONNECT_LIST, LeAddDeviceToConnectList);
- SET_SUPPORTED(LE_REMOVE_DEVICE_FROM_CONNECT_LIST,
- LeRemoveDeviceFromConnectList);
- SET_SUPPORTED(LE_RAND, LeRand);
- SET_SUPPORTED(LE_READ_SUPPORTED_STATES, LeReadSupportedStates);
- SET_HANDLER(LE_GET_VENDOR_CAPABILITIES, LeVendorCap);
- SET_HANDLER(LE_MULTI_ADVT, LeVendorMultiAdv);
- SET_HANDLER(LE_ADV_FILTER, LeAdvertisingFilter);
- SET_HANDLER(LE_ENERGY_INFO, LeEnergyInfo);
- SET_SUPPORTED(LE_SET_EXTENDED_ADVERTISING_RANDOM_ADDRESS,
- LeSetExtendedAdvertisingRandomAddress);
- SET_SUPPORTED(LE_SET_EXTENDED_ADVERTISING_PARAMETERS,
- LeSetExtendedAdvertisingParameters);
- SET_SUPPORTED(LE_SET_EXTENDED_ADVERTISING_DATA, LeSetExtendedAdvertisingData);
- SET_SUPPORTED(LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE,
- LeSetExtendedAdvertisingScanResponse);
- SET_SUPPORTED(LE_SET_EXTENDED_ADVERTISING_ENABLE,
- LeSetExtendedAdvertisingEnable);
- SET_SUPPORTED(LE_READ_MAXIMUM_ADVERTISING_DATA_LENGTH,
- LeReadMaximumAdvertisingDataLength);
- SET_SUPPORTED(LE_READ_NUMBER_OF_SUPPORTED_ADVERTISING_SETS,
- LeReadNumberOfSupportedAdvertisingSets);
- SET_SUPPORTED(LE_REMOVE_ADVERTISING_SET, LeRemoveAdvertisingSet);
- SET_SUPPORTED(LE_CLEAR_ADVERTISING_SETS, LeClearAdvertisingSets);
- SET_SUPPORTED(LE_READ_REMOTE_FEATURES, LeReadRemoteFeatures);
- SET_SUPPORTED(READ_REMOTE_VERSION_INFORMATION, ReadRemoteVersionInformation);
- SET_SUPPORTED(LE_CONNECTION_UPDATE, LeConnectionUpdate);
- SET_SUPPORTED(LE_START_ENCRYPTION, LeStartEncryption);
- SET_SUPPORTED(LE_LONG_TERM_KEY_REQUEST_REPLY, LeLongTermKeyRequestReply);
- SET_SUPPORTED(LE_LONG_TERM_KEY_REQUEST_NEGATIVE_REPLY,
- LeLongTermKeyRequestNegativeReply);
- SET_SUPPORTED(LE_ADD_DEVICE_TO_RESOLVING_LIST, LeAddDeviceToResolvingList);
- SET_SUPPORTED(LE_REMOVE_DEVICE_FROM_RESOLVING_LIST,
- LeRemoveDeviceFromResolvingList);
- SET_SUPPORTED(LE_CLEAR_RESOLVING_LIST, LeClearResolvingList);
- SET_SUPPORTED(LE_READ_RESOLVING_LIST_SIZE, LeReadResolvingListSize);
- SET_SUPPORTED(LE_READ_MAXIMUM_DATA_LENGTH, LeReadMaximumDataLength);
-
- SET_SUPPORTED(LE_SET_EXTENDED_SCAN_PARAMETERS, LeSetExtendedScanParameters);
- SET_SUPPORTED(LE_SET_EXTENDED_SCAN_ENABLE, LeSetExtendedScanEnable);
- SET_SUPPORTED(LE_EXTENDED_CREATE_CONNECTION, LeExtendedCreateConnection);
- SET_SUPPORTED(LE_SET_PRIVACY_MODE, LeSetPrivacyMode);
- SET_SUPPORTED(LE_READ_SUGGESTED_DEFAULT_DATA_LENGTH,
- LeReadSuggestedDefaultDataLength);
- // ISO Commands
- SET_SUPPORTED(LE_READ_ISO_TX_SYNC, LeReadIsoTxSync);
- SET_SUPPORTED(LE_SET_CIG_PARAMETERS, LeSetCigParameters);
- SET_SUPPORTED(LE_CREATE_CIS, LeCreateCis);
- SET_SUPPORTED(LE_REMOVE_CIG, LeRemoveCig);
- SET_SUPPORTED(LE_ACCEPT_CIS_REQUEST, LeAcceptCisRequest);
- SET_SUPPORTED(LE_REJECT_CIS_REQUEST, LeRejectCisRequest);
- SET_SUPPORTED(LE_CREATE_BIG, LeCreateBig);
- SET_SUPPORTED(LE_TERMINATE_BIG, LeTerminateBig);
- SET_SUPPORTED(LE_BIG_CREATE_SYNC, LeBigCreateSync);
- SET_SUPPORTED(LE_BIG_TERMINATE_SYNC, LeBigTerminateSync);
- SET_SUPPORTED(LE_REQUEST_PEER_SCA, LeRequestPeerSca);
- SET_SUPPORTED(LE_SETUP_ISO_DATA_PATH, LeSetupIsoDataPath);
- SET_SUPPORTED(LE_REMOVE_ISO_DATA_PATH, LeRemoveIsoDataPath);
+ SET_HANDLER(OpCode::RESET, Reset);
+ SET_HANDLER(OpCode::READ_BUFFER_SIZE, ReadBufferSize);
+ SET_HANDLER(OpCode::HOST_BUFFER_SIZE, HostBufferSize);
+ SET_HANDLER(OpCode::SNIFF_SUBRATING, SniffSubrating);
+ SET_HANDLER(OpCode::READ_ENCRYPTION_KEY_SIZE, ReadEncryptionKeySize);
+ SET_HANDLER(OpCode::READ_LOCAL_VERSION_INFORMATION,
+ ReadLocalVersionInformation);
+ SET_HANDLER(OpCode::READ_BD_ADDR, ReadBdAddr);
+ SET_HANDLER(OpCode::READ_LOCAL_SUPPORTED_COMMANDS,
+ ReadLocalSupportedCommands);
+ SET_HANDLER(OpCode::READ_LOCAL_SUPPORTED_FEATURES,
+ ReadLocalSupportedFeatures);
+ SET_HANDLER(OpCode::READ_LOCAL_SUPPORTED_CODECS, ReadLocalSupportedCodecs);
+ SET_HANDLER(OpCode::READ_LOCAL_EXTENDED_FEATURES, ReadLocalExtendedFeatures);
+ SET_HANDLER(OpCode::READ_REMOTE_EXTENDED_FEATURES,
+ ReadRemoteExtendedFeatures);
+ SET_HANDLER(OpCode::SWITCH_ROLE, SwitchRole);
+ SET_HANDLER(OpCode::READ_REMOTE_SUPPORTED_FEATURES,
+ ReadRemoteSupportedFeatures);
+ SET_HANDLER(OpCode::READ_CLOCK_OFFSET, ReadClockOffset);
+ SET_HANDLER(OpCode::IO_CAPABILITY_REQUEST_REPLY, IoCapabilityRequestReply);
+ SET_HANDLER(OpCode::USER_CONFIRMATION_REQUEST_REPLY,
+ UserConfirmationRequestReply);
+ SET_HANDLER(OpCode::USER_CONFIRMATION_REQUEST_NEGATIVE_REPLY,
+ UserConfirmationRequestNegativeReply);
+ SET_HANDLER(OpCode::IO_CAPABILITY_REQUEST_NEGATIVE_REPLY,
+ IoCapabilityRequestNegativeReply);
+ SET_HANDLER(OpCode::READ_INQUIRY_RESPONSE_TRANSMIT_POWER_LEVEL,
+ ReadInquiryResponseTransmitPowerLevel);
+ SET_HANDLER(OpCode::WRITE_SIMPLE_PAIRING_MODE, WriteSimplePairingMode);
+ SET_HANDLER(OpCode::WRITE_LE_HOST_SUPPORT, WriteLeHostSupport);
+ SET_HANDLER(OpCode::WRITE_SECURE_CONNECTIONS_HOST_SUPPORT,
+ WriteSecureConnectionsHostSupport);
+ SET_HANDLER(OpCode::SET_EVENT_MASK, SetEventMask);
+ SET_HANDLER(OpCode::READ_INQUIRY_MODE, ReadInquiryMode);
+ SET_HANDLER(OpCode::WRITE_INQUIRY_MODE, WriteInquiryMode);
+ SET_HANDLER(OpCode::READ_PAGE_SCAN_TYPE, ReadPageScanType);
+ SET_HANDLER(OpCode::WRITE_PAGE_SCAN_TYPE, WritePageScanType);
+ SET_HANDLER(OpCode::WRITE_INQUIRY_SCAN_TYPE, WriteInquiryScanType);
+ SET_HANDLER(OpCode::READ_INQUIRY_SCAN_TYPE, ReadInquiryScanType);
+ SET_HANDLER(OpCode::AUTHENTICATION_REQUESTED, AuthenticationRequested);
+ SET_HANDLER(OpCode::SET_CONNECTION_ENCRYPTION, SetConnectionEncryption);
+ SET_HANDLER(OpCode::CHANGE_CONNECTION_LINK_KEY, ChangeConnectionLinkKey);
+ SET_HANDLER(OpCode::MASTER_LINK_KEY, MasterLinkKey);
+ SET_HANDLER(OpCode::WRITE_AUTHENTICATION_ENABLE, WriteAuthenticationEnable);
+ SET_HANDLER(OpCode::READ_AUTHENTICATION_ENABLE, ReadAuthenticationEnable);
+ SET_HANDLER(OpCode::WRITE_CLASS_OF_DEVICE, WriteClassOfDevice);
+ SET_HANDLER(OpCode::READ_PAGE_TIMEOUT, ReadPageTimeout);
+ SET_HANDLER(OpCode::WRITE_PAGE_TIMEOUT, WritePageTimeout);
+ SET_HANDLER(OpCode::WRITE_LINK_SUPERVISION_TIMEOUT,
+ WriteLinkSupervisionTimeout);
+ SET_HANDLER(OpCode::HOLD_MODE, HoldMode);
+ SET_HANDLER(OpCode::SNIFF_MODE, SniffMode);
+ SET_HANDLER(OpCode::EXIT_SNIFF_MODE, ExitSniffMode);
+ SET_HANDLER(OpCode::QOS_SETUP, QosSetup);
+ SET_HANDLER(OpCode::WRITE_DEFAULT_LINK_POLICY_SETTINGS,
+ WriteDefaultLinkPolicySettings);
+ SET_HANDLER(OpCode::FLOW_SPECIFICATION, FlowSpecification);
+ SET_HANDLER(OpCode::WRITE_LINK_POLICY_SETTINGS, WriteLinkPolicySettings);
+ SET_HANDLER(OpCode::CHANGE_CONNECTION_PACKET_TYPE,
+ ChangeConnectionPacketType);
+ SET_HANDLER(OpCode::WRITE_LOCAL_NAME, WriteLocalName);
+ SET_HANDLER(OpCode::READ_LOCAL_NAME, ReadLocalName);
+ SET_HANDLER(OpCode::WRITE_EXTENDED_INQUIRY_RESPONSE,
+ WriteExtendedInquiryResponse);
+ SET_HANDLER(OpCode::REFRESH_ENCRYPTION_KEY, RefreshEncryptionKey);
+ SET_HANDLER(OpCode::WRITE_VOICE_SETTING, WriteVoiceSetting);
+ SET_HANDLER(OpCode::READ_NUMBER_OF_SUPPORTED_IAC, ReadNumberOfSupportedIac);
+ SET_HANDLER(OpCode::READ_CURRENT_IAC_LAP, ReadCurrentIacLap);
+ SET_HANDLER(OpCode::WRITE_CURRENT_IAC_LAP, WriteCurrentIacLap);
+ SET_HANDLER(OpCode::READ_PAGE_SCAN_ACTIVITY, ReadPageScanActivity);
+ SET_HANDLER(OpCode::WRITE_PAGE_SCAN_ACTIVITY, WritePageScanActivity);
+ SET_HANDLER(OpCode::READ_INQUIRY_SCAN_ACTIVITY, ReadInquiryScanActivity);
+ SET_HANDLER(OpCode::WRITE_INQUIRY_SCAN_ACTIVITY, WriteInquiryScanActivity);
+ SET_HANDLER(OpCode::READ_SCAN_ENABLE, ReadScanEnable);
+ SET_HANDLER(OpCode::WRITE_SCAN_ENABLE, WriteScanEnable);
+ SET_HANDLER(OpCode::SET_EVENT_FILTER, SetEventFilter);
+ SET_HANDLER(OpCode::INQUIRY, Inquiry);
+ SET_HANDLER(OpCode::INQUIRY_CANCEL, InquiryCancel);
+ SET_HANDLER(OpCode::ACCEPT_CONNECTION_REQUEST, AcceptConnectionRequest);
+ SET_HANDLER(OpCode::REJECT_CONNECTION_REQUEST, RejectConnectionRequest);
+ SET_HANDLER(OpCode::LINK_KEY_REQUEST_REPLY, LinkKeyRequestReply);
+ SET_HANDLER(OpCode::LINK_KEY_REQUEST_NEGATIVE_REPLY,
+ LinkKeyRequestNegativeReply);
+ SET_HANDLER(OpCode::DELETE_STORED_LINK_KEY, DeleteStoredLinkKey);
+ SET_HANDLER(OpCode::REMOTE_NAME_REQUEST, RemoteNameRequest);
+ SET_HANDLER(OpCode::LE_SET_EVENT_MASK, LeSetEventMask);
+ SET_HANDLER(OpCode::LE_READ_BUFFER_SIZE, LeReadBufferSize);
+ SET_HANDLER(OpCode::LE_READ_LOCAL_SUPPORTED_FEATURES,
+ LeReadLocalSupportedFeatures);
+ SET_HANDLER(OpCode::LE_SET_RANDOM_ADDRESS, LeSetRandomAddress);
+ SET_HANDLER(OpCode::LE_SET_ADVERTISING_PARAMETERS,
+ LeSetAdvertisingParameters);
+ SET_HANDLER(OpCode::LE_SET_ADVERTISING_DATA, LeSetAdvertisingData);
+ SET_HANDLER(OpCode::LE_SET_SCAN_RESPONSE_DATA, LeSetScanResponseData);
+ SET_HANDLER(OpCode::LE_SET_ADVERTISING_ENABLE, LeSetAdvertisingEnable);
+ SET_HANDLER(OpCode::LE_SET_SCAN_PARAMETERS, LeSetScanParameters);
+ SET_HANDLER(OpCode::LE_SET_SCAN_ENABLE, LeSetScanEnable);
+ SET_HANDLER(OpCode::LE_CREATE_CONNECTION, LeCreateConnection);
+ SET_HANDLER(OpCode::CREATE_CONNECTION, CreateConnection);
+ SET_HANDLER(OpCode::DISCONNECT, Disconnect);
+ SET_HANDLER(OpCode::LE_CREATE_CONNECTION_CANCEL, LeConnectionCancel);
+ SET_HANDLER(OpCode::LE_READ_WHITE_LIST_SIZE, LeReadWhiteListSize);
+ SET_HANDLER(OpCode::LE_CLEAR_WHITE_LIST, LeClearWhiteList);
+ SET_HANDLER(OpCode::LE_ADD_DEVICE_TO_WHITE_LIST, LeAddDeviceToWhiteList);
+ SET_HANDLER(OpCode::LE_REMOVE_DEVICE_FROM_WHITE_LIST,
+ LeRemoveDeviceFromWhiteList);
+ SET_HANDLER(OpCode::LE_RAND, LeRand);
+ SET_HANDLER(OpCode::LE_READ_SUPPORTED_STATES, LeReadSupportedStates);
+ SET_HANDLER(OpCode::LE_GET_VENDOR_CAPABILITIES, LeVendorCap);
+ SET_HANDLER(OpCode::LE_MULTI_ADVT, LeVendorMultiAdv);
+ SET_HANDLER(OpCode::LE_ADV_FILTER, LeAdvertisingFilter);
+ SET_HANDLER(OpCode::LE_ENERGY_INFO, LeEnergyInfo);
+ SET_HANDLER(OpCode::LE_SET_EXTENDED_ADVERTISING_RANDOM_ADDRESS,
+ LeSetExtendedAdvertisingRandomAddress);
+ SET_HANDLER(OpCode::LE_SET_EXTENDED_ADVERTISING_PARAMETERS,
+ LeSetExtendedAdvertisingParameters);
+ SET_HANDLER(OpCode::LE_SET_EXTENDED_ADVERTISING_DATA,
+ LeSetExtendedAdvertisingData);
+ SET_HANDLER(OpCode::LE_SET_EXTENDED_ADVERTISING_SCAN_RESPONSE,
+ LeSetExtendedAdvertisingScanResponse);
+ SET_HANDLER(OpCode::LE_SET_EXTENDED_ADVERTISING_ENABLE,
+ LeSetExtendedAdvertisingEnable);
+ SET_HANDLER(OpCode::LE_READ_REMOTE_FEATURES, LeReadRemoteFeatures);
+ SET_HANDLER(OpCode::READ_REMOTE_VERSION_INFORMATION,
+ ReadRemoteVersionInformation);
+ SET_HANDLER(OpCode::LE_CONNECTION_UPDATE, LeConnectionUpdate);
+ SET_HANDLER(OpCode::LE_START_ENCRYPTION, LeStartEncryption);
+ SET_HANDLER(OpCode::LE_ADD_DEVICE_TO_RESOLVING_LIST,
+ LeAddDeviceToResolvingList);
+ SET_HANDLER(OpCode::LE_REMOVE_DEVICE_FROM_RESOLVING_LIST,
+ LeRemoveDeviceFromResolvingList);
+ SET_HANDLER(OpCode::LE_CLEAR_RESOLVING_LIST, LeClearResolvingList);
+ SET_HANDLER(OpCode::LE_SET_EXTENDED_SCAN_PARAMETERS,
+ LeSetExtendedScanParameters);
+ SET_HANDLER(OpCode::LE_SET_EXTENDED_SCAN_ENABLE, LeSetExtendedScanEnable);
+ SET_HANDLER(OpCode::LE_EXTENDED_CREATE_CONNECTION,
+ LeExtendedCreateConnection);
+ SET_HANDLER(OpCode::LE_SET_PRIVACY_MODE, LeSetPrivacyMode);
// Testing Commands
- SET_SUPPORTED(READ_LOOPBACK_MODE, ReadLoopbackMode);
- SET_SUPPORTED(WRITE_LOOPBACK_MODE, WriteLoopbackMode);
-
- SET_SUPPORTED(READ_CLASS_OF_DEVICE, ReadClassOfDevice);
- SET_SUPPORTED(READ_VOICE_SETTING, ReadVoiceSetting);
- SET_SUPPORTED(READ_CONNECTION_ACCEPT_TIMEOUT, ReadConnectionAcceptTimeout);
- SET_SUPPORTED(WRITE_CONNECTION_ACCEPT_TIMEOUT, WriteConnectionAcceptTimeout);
- SET_SUPPORTED(LE_SET_ADDRESS_RESOLUTION_ENABLE, LeSetAddressResolutionEnable);
- SET_SUPPORTED(LE_SET_RESOLVABLE_PRIVATE_ADDRESS_TIMEOUT, LeSetResovalablePrivateAddressTimeout);
+ SET_HANDLER(OpCode::READ_LOOPBACK_MODE, ReadLoopbackMode);
+ SET_HANDLER(OpCode::WRITE_LOOPBACK_MODE, WriteLoopbackMode);
#undef SET_HANDLER
-#undef SET_SUPPORTED
- properties_.SetSupportedCommands(supported_commands);
}
-void DualModeController::SniffSubrating(CommandView command) {
+void DualModeController::SniffSubrating(CommandPacketView command) {
auto command_view = gd_hci::SniffSubratingView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
send_event_(gd_hci::SniffSubratingCompleteBuilder::Create(
@@ -324,7 +264,7 @@ void DualModeController::RegisterTaskCancel(std::function<void(AsyncTaskId)> tas
void DualModeController::HandleAcl(std::shared_ptr<std::vector<uint8_t>> packet) {
bluetooth::hci::PacketView<bluetooth::hci::kLittleEndian> raw_packet(packet);
- auto acl_packet = bluetooth::hci::AclView::Create(raw_packet);
+ auto acl_packet = bluetooth::hci::AclPacketView::Create(raw_packet);
ASSERT(acl_packet.IsValid());
if (loopback_mode_ == LoopbackMode::ENABLE_LOCAL) {
uint16_t handle = acl_packet.GetHandle();
@@ -344,12 +284,10 @@ void DualModeController::HandleAcl(std::shared_ptr<std::vector<uint8_t>> packet)
void DualModeController::HandleSco(std::shared_ptr<std::vector<uint8_t>> packet) {
bluetooth::hci::PacketView<bluetooth::hci::kLittleEndian> raw_packet(packet);
- auto sco_packet = bluetooth::hci::ScoView::Create(raw_packet);
+ auto sco_packet = bluetooth::hci::ScoPacketView::Create(raw_packet);
if (loopback_mode_ == LoopbackMode::ENABLE_LOCAL) {
uint16_t handle = sco_packet.GetHandle();
- auto sco_builder = bluetooth::hci::ScoBuilder::Create(
- handle, sco_packet.GetPacketStatusFlag(), sco_packet.GetData());
- send_sco_(std::move(sco_builder));
+ send_sco_(packet);
std::vector<bluetooth::hci::CompletedPackets> completed_packets;
bluetooth::hci::CompletedPackets cp;
cp.connection_handle_ = handle;
@@ -362,16 +300,13 @@ void DualModeController::HandleSco(std::shared_ptr<std::vector<uint8_t>> packet)
}
void DualModeController::HandleIso(
- std::shared_ptr<std::vector<uint8_t>> packet) {
- bluetooth::hci::PacketView<bluetooth::hci::kLittleEndian> raw_packet(packet);
- auto iso = bluetooth::hci::IsoView::Create(raw_packet);
- ASSERT(iso.IsValid());
- link_layer_controller_.HandleIso(iso);
+ std::shared_ptr<std::vector<uint8_t>> /* packet */) {
+ // TODO: implement handling similar to HandleSco
}
void DualModeController::HandleCommand(std::shared_ptr<std::vector<uint8_t>> packet) {
bluetooth::hci::PacketView<bluetooth::hci::kLittleEndian> raw_packet(packet);
- auto command_packet = bluetooth::hci::CommandView::Create(raw_packet);
+ auto command_packet = bluetooth::hci::CommandPacketView::Create(raw_packet);
ASSERT(command_packet.IsValid());
auto op = command_packet.GetOpCode();
@@ -401,7 +336,7 @@ void DualModeController::HandleCommand(std::shared_ptr<std::vector<uint8_t>> pac
void DualModeController::RegisterEventChannel(
const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>& callback) {
send_event_ =
- [callback](std::shared_ptr<bluetooth::hci::EventBuilder> event) {
+ [callback](std::shared_ptr<bluetooth::hci::EventPacketBuilder> event) {
auto bytes = std::make_shared<std::vector<uint8_t>>();
bluetooth::packet::BitInserter bit_inserter(*bytes);
bytes->reserve(event->size());
@@ -413,42 +348,31 @@ void DualModeController::RegisterEventChannel(
void DualModeController::RegisterAclChannel(
const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>& callback) {
- send_acl_ = [callback](std::shared_ptr<bluetooth::hci::AclBuilder> acl_data) {
- auto bytes = std::make_shared<std::vector<uint8_t>>();
- bluetooth::packet::BitInserter bit_inserter(*bytes);
- bytes->reserve(acl_data->size());
- acl_data->Serialize(bit_inserter);
- callback(std::move(bytes));
- };
+ send_acl_ =
+ [callback](std::shared_ptr<bluetooth::hci::AclPacketBuilder> acl_data) {
+ auto bytes = std::make_shared<std::vector<uint8_t>>();
+ bluetooth::packet::BitInserter bit_inserter(*bytes);
+ bytes->reserve(acl_data->size());
+ acl_data->Serialize(bit_inserter);
+ callback(std::move(bytes));
+ };
link_layer_controller_.RegisterAclChannel(send_acl_);
}
void DualModeController::RegisterScoChannel(
const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>& callback) {
- send_sco_ = [callback](std::shared_ptr<bluetooth::hci::ScoBuilder> sco_data) {
- auto bytes = std::make_shared<std::vector<uint8_t>>();
- bluetooth::packet::BitInserter bit_inserter(*bytes);
- bytes->reserve(sco_data->size());
- sco_data->Serialize(bit_inserter);
- callback(std::move(bytes));
- };
- link_layer_controller_.RegisterScoChannel(send_sco_);
+ link_layer_controller_.RegisterScoChannel(callback);
+ send_sco_ = callback;
}
void DualModeController::RegisterIsoChannel(
const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>&
callback) {
- send_iso_ = [callback](std::shared_ptr<bluetooth::hci::IsoBuilder> iso_data) {
- auto bytes = std::make_shared<std::vector<uint8_t>>();
- bluetooth::packet::BitInserter bit_inserter(*bytes);
- bytes->reserve(iso_data->size());
- iso_data->Serialize(bit_inserter);
- callback(std::move(bytes));
- };
- link_layer_controller_.RegisterIsoChannel(send_iso_);
+ link_layer_controller_.RegisterIsoChannel(callback);
+ send_iso_ = callback;
}
-void DualModeController::Reset(CommandView command) {
+void DualModeController::Reset(CommandPacketView command) {
auto command_view = gd_hci::ResetView::Create(command);
ASSERT(command_view.IsValid());
link_layer_controller_.Reset();
@@ -460,7 +384,7 @@ void DualModeController::Reset(CommandView command) {
ErrorCode::SUCCESS));
}
-void DualModeController::ReadBufferSize(CommandView command) {
+void DualModeController::ReadBufferSize(CommandPacketView command) {
auto command_view = gd_hci::ReadBufferSizeView::Create(command);
ASSERT(command_view.IsValid());
@@ -473,7 +397,7 @@ void DualModeController::ReadBufferSize(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadEncryptionKeySize(CommandView command) {
+void DualModeController::ReadEncryptionKeySize(CommandPacketView command) {
auto command_view = gd_hci::ReadEncryptionKeySizeView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -484,7 +408,7 @@ void DualModeController::ReadEncryptionKeySize(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::HostBufferSize(CommandView command) {
+void DualModeController::HostBufferSize(CommandPacketView command) {
auto command_view = gd_hci::HostBufferSizeView::Create(command);
ASSERT(command_view.IsValid());
auto packet = bluetooth::hci::HostBufferSizeCompleteBuilder::Create(
@@ -492,7 +416,8 @@ void DualModeController::HostBufferSize(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadLocalVersionInformation(CommandView command) {
+void DualModeController::ReadLocalVersionInformation(
+ CommandPacketView command) {
auto command_view = gd_hci::ReadLocalVersionInformationView::Create(command);
ASSERT(command_view.IsValid());
@@ -511,10 +436,10 @@ void DualModeController::ReadLocalVersionInformation(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadRemoteVersionInformation(CommandView command) {
+void DualModeController::ReadRemoteVersionInformation(
+ CommandPacketView command) {
auto command_view = gd_hci::ReadRemoteVersionInformationView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
auto status = link_layer_controller_.SendCommandToRemoteByHandle(
@@ -527,7 +452,7 @@ void DualModeController::ReadRemoteVersionInformation(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadBdAddr(CommandView command) {
+void DualModeController::ReadBdAddr(CommandPacketView command) {
auto command_view = gd_hci::ReadBdAddrView::Create(command);
ASSERT(command_view.IsValid());
auto packet = bluetooth::hci::ReadBdAddrCompleteBuilder::Create(
@@ -535,11 +460,11 @@ void DualModeController::ReadBdAddr(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadLocalSupportedCommands(CommandView command) {
+void DualModeController::ReadLocalSupportedCommands(CommandPacketView command) {
auto command_view = gd_hci::ReadLocalSupportedCommandsView::Create(command);
ASSERT(command_view.IsValid());
- std::array<uint8_t, 64> supported_commands{};
+ std::array<uint8_t, 64> supported_commands;
supported_commands.fill(0x00);
size_t len = properties_.GetSupportedCommands().size();
if (len > 64) {
@@ -554,7 +479,7 @@ void DualModeController::ReadLocalSupportedCommands(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadLocalSupportedFeatures(CommandView command) {
+void DualModeController::ReadLocalSupportedFeatures(CommandPacketView command) {
auto command_view = gd_hci::ReadLocalSupportedFeaturesView::Create(command);
ASSERT(command_view.IsValid());
auto packet =
@@ -564,18 +489,16 @@ void DualModeController::ReadLocalSupportedFeatures(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadLocalSupportedCodecs(CommandView command) {
- auto command_view = gd_hci::ReadLocalSupportedCodecsV1View::Create(command);
+void DualModeController::ReadLocalSupportedCodecs(CommandPacketView command) {
+ auto command_view = gd_hci::ReadLocalSupportedCodecsView::Create(command);
ASSERT(command_view.IsValid());
- auto packet =
- bluetooth::hci::ReadLocalSupportedCodecsV1CompleteBuilder::Create(
- kNumCommandPackets, ErrorCode::SUCCESS,
- properties_.GetSupportedCodecs(),
- properties_.GetVendorSpecificCodecs());
+ auto packet = bluetooth::hci::ReadLocalSupportedCodecsCompleteBuilder::Create(
+ kNumCommandPackets, ErrorCode::SUCCESS, properties_.GetSupportedCodecs(),
+ properties_.GetVendorSpecificCodecs());
send_event_(std::move(packet));
}
-void DualModeController::ReadLocalExtendedFeatures(CommandView command) {
+void DualModeController::ReadLocalExtendedFeatures(CommandPacketView command) {
auto command_view = gd_hci::ReadLocalExtendedFeaturesView::Create(command);
ASSERT(command_view.IsValid());
uint8_t page_number = command_view.GetPageNumber();
@@ -588,10 +511,9 @@ void DualModeController::ReadLocalExtendedFeatures(CommandView command) {
send_event_(std::move(pakcet));
}
-void DualModeController::ReadRemoteExtendedFeatures(CommandView command) {
+void DualModeController::ReadRemoteExtendedFeatures(CommandPacketView command) {
auto command_view = gd_hci::ReadRemoteExtendedFeaturesView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
auto status = link_layer_controller_.SendCommandToRemoteByHandle(
@@ -603,10 +525,9 @@ void DualModeController::ReadRemoteExtendedFeatures(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::SwitchRole(CommandView command) {
+void DualModeController::SwitchRole(CommandPacketView command) {
auto command_view = gd_hci::SwitchRoleView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
auto status = link_layer_controller_.SwitchRole(
@@ -617,10 +538,10 @@ void DualModeController::SwitchRole(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadRemoteSupportedFeatures(CommandView command) {
+void DualModeController::ReadRemoteSupportedFeatures(
+ CommandPacketView command) {
auto command_view = gd_hci::ReadRemoteSupportedFeaturesView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
auto status = link_layer_controller_.SendCommandToRemoteByHandle(
@@ -633,10 +554,9 @@ void DualModeController::ReadRemoteSupportedFeatures(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadClockOffset(CommandView command) {
+void DualModeController::ReadClockOffset(CommandPacketView command) {
auto command_view = gd_hci::ReadClockOffsetView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
@@ -649,7 +569,7 @@ void DualModeController::ReadClockOffset(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::IoCapabilityRequestReply(CommandView command) {
+void DualModeController::IoCapabilityRequestReply(CommandPacketView command) {
auto command_view = gd_hci::IoCapabilityRequestReplyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -669,7 +589,8 @@ void DualModeController::IoCapabilityRequestReply(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::UserConfirmationRequestReply(CommandView command) {
+void DualModeController::UserConfirmationRequestReply(
+ CommandPacketView command) {
auto command_view = gd_hci::UserConfirmationRequestReplyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -685,7 +606,7 @@ void DualModeController::UserConfirmationRequestReply(CommandView command) {
}
void DualModeController::UserConfirmationRequestNegativeReply(
- CommandView command) {
+ CommandPacketView command) {
auto command_view = gd_hci::UserConfirmationRequestNegativeReplyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -701,42 +622,7 @@ void DualModeController::UserConfirmationRequestNegativeReply(
send_event_(std::move(packet));
}
-void DualModeController::PinCodeRequestReply(CommandView command) {
- auto command_view = gd_hci::PinCodeRequestReplyView::Create(
- gd_hci::SecurityCommandView::Create(command));
- ASSERT(command_view.IsValid());
- LOG_INFO("%s", properties_.GetAddress().ToString().c_str());
-
- Address peer = command_view.GetBdAddr();
- uint8_t pin_length = command_view.GetPinCodeLength();
- std::array<uint8_t, 16> pin = command_view.GetPinCode();
- ErrorCode status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
- if (pin_length >= 1 && pin_length <= 0x10) {
- status = link_layer_controller_.PinCodeRequestReply(
- peer, std::vector<uint8_t>(pin.begin(), pin.begin() + pin_length));
- }
-
- send_event_(bluetooth::hci::PinCodeRequestReplyCompleteBuilder::Create(
- kNumCommandPackets, status, peer));
-}
-
-void DualModeController::PinCodeRequestNegativeReply(CommandView command) {
- auto command_view = gd_hci::PinCodeRequestNegativeReplyView::Create(
- gd_hci::SecurityCommandView::Create(command));
- ASSERT(command_view.IsValid());
- LOG_INFO("%s", properties_.GetAddress().ToString().c_str());
-
- Address peer = command_view.GetBdAddr();
-
- auto status = link_layer_controller_.PinCodeRequestNegativeReply(peer);
- auto packet =
- bluetooth::hci::PinCodeRequestNegativeReplyCompleteBuilder::Create(
- kNumCommandPackets, status, peer);
-
- send_event_(std::move(packet));
-}
-
-void DualModeController::UserPasskeyRequestReply(CommandView command) {
+void DualModeController::UserPasskeyRequestReply(CommandPacketView command) {
auto command_view = gd_hci::UserPasskeyRequestReplyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -752,7 +638,8 @@ void DualModeController::UserPasskeyRequestReply(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::UserPasskeyRequestNegativeReply(CommandView command) {
+void DualModeController::UserPasskeyRequestNegativeReply(
+ CommandPacketView command) {
auto command_view = gd_hci::UserPasskeyRequestNegativeReplyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -767,22 +654,27 @@ void DualModeController::UserPasskeyRequestNegativeReply(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::RemoteOobDataRequestReply(CommandView command) {
+void DualModeController::RemoteOobDataRequestReply(CommandPacketView command) {
auto command_view = gd_hci::RemoteOobDataRequestReplyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
Address peer = command_view.GetBdAddr();
+ std::array<uint8_t, 16> c = command_view.GetC();
+ std::array<uint8_t, 16> r = command_view.GetR();
auto status = link_layer_controller_.RemoteOobDataRequestReply(
- peer, command_view.GetC(), command_view.GetR());
+ peer, std::vector<uint8_t>(c.begin(), c.end()),
+ std::vector<uint8_t>(r.begin(), r.end()));
+ auto packet =
+ bluetooth::hci::RemoteOobDataRequestReplyCompleteBuilder::Create(
+ kNumCommandPackets, status, peer);
- send_event_(bluetooth::hci::RemoteOobDataRequestReplyCompleteBuilder::Create(
- kNumCommandPackets, status, peer));
+ send_event_(std::move(packet));
}
void DualModeController::RemoteOobDataRequestNegativeReply(
- CommandView command) {
+ CommandPacketView command) {
auto command_view = gd_hci::RemoteOobDataRequestNegativeReplyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -797,7 +689,8 @@ void DualModeController::RemoteOobDataRequestNegativeReply(
send_event_(std::move(packet));
}
-void DualModeController::IoCapabilityRequestNegativeReply(CommandView command) {
+void DualModeController::IoCapabilityRequestNegativeReply(
+ CommandPacketView command) {
auto command_view = gd_hci::IoCapabilityRequestNegativeReplyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -814,25 +707,8 @@ void DualModeController::IoCapabilityRequestNegativeReply(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::RemoteOobExtendedDataRequestReply(
- CommandView command) {
- auto command_view = gd_hci::RemoteOobExtendedDataRequestReplyView::Create(
- gd_hci::SecurityCommandView::Create(command));
- ASSERT(command_view.IsValid());
-
- Address peer = command_view.GetBdAddr();
-
- auto status = link_layer_controller_.RemoteOobExtendedDataRequestReply(
- peer, command_view.GetC192(), command_view.GetR192(),
- command_view.GetC256(), command_view.GetR256());
-
- send_event_(
- bluetooth::hci::RemoteOobExtendedDataRequestReplyCompleteBuilder::Create(
- kNumCommandPackets, status, peer));
-}
-
void DualModeController::ReadInquiryResponseTransmitPowerLevel(
- CommandView command) {
+ CommandPacketView command) {
auto command_view = gd_hci::ReadInquiryResponseTransmitPowerLevelView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -844,55 +720,21 @@ void DualModeController::ReadInquiryResponseTransmitPowerLevel(
send_event_(std::move(packet));
}
-void DualModeController::SendKeypressNotification(CommandView command) {
- auto command_view = gd_hci::SendKeypressNotificationView::Create(
- gd_hci::SecurityCommandView::Create(command));
- ASSERT(command_view.IsValid());
-
- auto peer = command_view.GetBdAddr();
-
- auto status = link_layer_controller_.SendKeypressNotification(
- peer, command_view.GetNotificationType());
- send_event_(bluetooth::hci::SendKeypressNotificationCompleteBuilder::Create(
- kNumCommandPackets, status, peer));
-}
-
-void DualModeController::SetEventMaskPage2(CommandView command) {
- auto payload =
- std::make_unique<bluetooth::packet::RawBuilder>(std::vector<uint8_t>(
- {static_cast<uint8_t>(bluetooth::hci::ErrorCode::SUCCESS)}));
- send_event_(bluetooth::hci::CommandCompleteBuilder::Create(
- kNumCommandPackets, command.GetOpCode(), std::move(payload)));
-}
-
-void DualModeController::ReadLocalOobData(CommandView command) {
- auto command_view = gd_hci::ReadLocalOobDataView::Create(
- gd_hci::SecurityCommandView::Create(command));
- link_layer_controller_.ReadLocalOobData();
-}
-
-void DualModeController::ReadLocalOobExtendedData(CommandView command) {
- auto command_view = gd_hci::ReadLocalOobExtendedDataView::Create(
- gd_hci::SecurityCommandView::Create(command));
- link_layer_controller_.ReadLocalOobExtendedData();
-}
-
-void DualModeController::WriteSimplePairingMode(CommandView command) {
+void DualModeController::WriteSimplePairingMode(CommandPacketView command) {
auto command_view = gd_hci::WriteSimplePairingModeView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
- auto enabled = command_view.GetSimplePairingMode() == gd_hci::Enable::ENABLED;
- properties_.SetSecureSimplePairingSupport(enabled);
+ link_layer_controller_.WriteSimplePairingMode(
+ command_view.GetSimplePairingMode() == gd_hci::Enable::ENABLED);
auto packet = bluetooth::hci::WriteSimplePairingModeCompleteBuilder::Create(
kNumCommandPackets, ErrorCode::SUCCESS);
send_event_(std::move(packet));
}
-void DualModeController::ChangeConnectionPacketType(CommandView command) {
+void DualModeController::ChangeConnectionPacketType(CommandPacketView command) {
auto command_view = gd_hci::ChangeConnectionPacketTypeView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
@@ -906,41 +748,34 @@ void DualModeController::ChangeConnectionPacketType(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteLeHostSupport(CommandView command) {
+void DualModeController::WriteLeHostSupport(CommandPacketView command) {
auto command_view = gd_hci::WriteLeHostSupportView::Create(command);
ASSERT(command_view.IsValid());
- auto le_support =
- command_view.GetLeSupportedHost() == gd_hci::Enable::ENABLED;
- properties_.SetLeHostSupport(le_support);
auto packet = bluetooth::hci::WriteLeHostSupportCompleteBuilder::Create(
kNumCommandPackets, ErrorCode::SUCCESS);
send_event_(std::move(packet));
}
void DualModeController::WriteSecureConnectionsHostSupport(
- CommandView command) {
+ CommandPacketView command) {
auto command_view = gd_hci::WriteSecureConnectionsHostSupportView::Create(
gd_hci::SecurityCommandView::Create(command));
- ASSERT(command_view.IsValid());
- properties_.SetSecureConnections(
- command_view.GetSecureConnectionsHostSupport() ==
- bluetooth::hci::Enable::ENABLED);
+ properties_.SetExtendedFeatures(properties_.GetExtendedFeatures(1) | 0x8, 1);
auto packet =
bluetooth::hci::WriteSecureConnectionsHostSupportCompleteBuilder::Create(
kNumCommandPackets, ErrorCode::SUCCESS);
send_event_(std::move(packet));
}
-void DualModeController::SetEventMask(CommandView command) {
+void DualModeController::SetEventMask(CommandPacketView command) {
auto command_view = gd_hci::SetEventMaskView::Create(command);
ASSERT(command_view.IsValid());
- properties_.SetEventMask(command_view.GetEventMask());
auto packet = bluetooth::hci::SetEventMaskCompleteBuilder::Create(
kNumCommandPackets, ErrorCode::SUCCESS);
send_event_(std::move(packet));
}
-void DualModeController::ReadInquiryMode(CommandView command) {
+void DualModeController::ReadInquiryMode(CommandPacketView command) {
auto command_view = gd_hci::ReadInquiryModeView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -950,7 +785,7 @@ void DualModeController::ReadInquiryMode(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteInquiryMode(CommandView command) {
+void DualModeController::WriteInquiryMode(CommandPacketView command) {
auto command_view = gd_hci::WriteInquiryModeView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -961,7 +796,7 @@ void DualModeController::WriteInquiryMode(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadPageScanType(CommandView command) {
+void DualModeController::ReadPageScanType(CommandPacketView command) {
auto command_view = gd_hci::ReadPageScanTypeView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -971,7 +806,7 @@ void DualModeController::ReadPageScanType(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WritePageScanType(CommandView command) {
+void DualModeController::WritePageScanType(CommandPacketView command) {
auto command_view = gd_hci::WritePageScanTypeView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -980,7 +815,7 @@ void DualModeController::WritePageScanType(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadInquiryScanType(CommandView command) {
+void DualModeController::ReadInquiryScanType(CommandPacketView command) {
auto command_view = gd_hci::ReadInquiryScanTypeView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -990,7 +825,7 @@ void DualModeController::ReadInquiryScanType(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteInquiryScanType(CommandView command) {
+void DualModeController::WriteInquiryScanType(CommandPacketView command) {
auto command_view = gd_hci::WriteInquiryScanTypeView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -999,10 +834,9 @@ void DualModeController::WriteInquiryScanType(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::AuthenticationRequested(CommandView command) {
+void DualModeController::AuthenticationRequested(CommandPacketView command) {
auto command_view = gd_hci::AuthenticationRequestedView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
auto status = link_layer_controller_.AuthenticationRequested(handle);
@@ -1012,10 +846,9 @@ void DualModeController::AuthenticationRequested(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::SetConnectionEncryption(CommandView command) {
+void DualModeController::SetConnectionEncryption(CommandPacketView command) {
auto command_view = gd_hci::SetConnectionEncryptionView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
uint8_t encryption_enable =
@@ -1028,10 +861,9 @@ void DualModeController::SetConnectionEncryption(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ChangeConnectionLinkKey(CommandView command) {
+void DualModeController::ChangeConnectionLinkKey(CommandPacketView command) {
auto command_view = gd_hci::ChangeConnectionLinkKeyView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
@@ -1042,21 +874,20 @@ void DualModeController::ChangeConnectionLinkKey(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::CentralLinkKey(CommandView command) {
- auto command_view = gd_hci::CentralLinkKeyView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+void DualModeController::MasterLinkKey(CommandPacketView command) {
+ auto command_view = gd_hci::MasterLinkKeyView::Create(
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint8_t key_flag = static_cast<uint8_t>(command_view.GetKeyFlag());
- auto status = link_layer_controller_.CentralLinkKey(key_flag);
+ auto status = link_layer_controller_.MasterLinkKey(key_flag);
- auto packet = bluetooth::hci::CentralLinkKeyStatusBuilder::Create(
+ auto packet = bluetooth::hci::MasterLinkKeyStatusBuilder::Create(
status, kNumCommandPackets);
send_event_(std::move(packet));
}
-void DualModeController::WriteAuthenticationEnable(CommandView command) {
+void DualModeController::WriteAuthenticationEnable(CommandPacketView command) {
auto command_view = gd_hci::WriteAuthenticationEnableView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1068,7 +899,7 @@ void DualModeController::WriteAuthenticationEnable(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadAuthenticationEnable(CommandView command) {
+void DualModeController::ReadAuthenticationEnable(CommandPacketView command) {
auto command_view = gd_hci::ReadAuthenticationEnableView::Create(command);
ASSERT(command_view.IsValid());
auto packet = bluetooth::hci::ReadAuthenticationEnableCompleteBuilder::Create(
@@ -1078,7 +909,7 @@ void DualModeController::ReadAuthenticationEnable(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteClassOfDevice(CommandView command) {
+void DualModeController::WriteClassOfDevice(CommandPacketView command) {
auto command_view = gd_hci::WriteClassOfDeviceView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1090,7 +921,7 @@ void DualModeController::WriteClassOfDevice(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadPageTimeout(CommandView command) {
+void DualModeController::ReadPageTimeout(CommandPacketView command) {
auto command_view = gd_hci::ReadPageTimeoutView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1100,7 +931,7 @@ void DualModeController::ReadPageTimeout(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WritePageTimeout(CommandView command) {
+void DualModeController::WritePageTimeout(CommandPacketView command) {
auto command_view = gd_hci::WritePageTimeoutView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1109,10 +940,9 @@ void DualModeController::WritePageTimeout(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::HoldMode(CommandView command) {
+void DualModeController::HoldMode(CommandPacketView command) {
auto command_view = gd_hci::HoldModeView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
uint16_t hold_mode_max_interval = command_view.GetHoldModeMaxInterval();
@@ -1126,10 +956,9 @@ void DualModeController::HoldMode(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::SniffMode(CommandView command) {
+void DualModeController::SniffMode(CommandPacketView command) {
auto command_view = gd_hci::SniffModeView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
uint16_t sniff_max_interval = command_view.GetSniffMaxInterval();
@@ -1146,10 +975,9 @@ void DualModeController::SniffMode(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ExitSniffMode(CommandView command) {
+void DualModeController::ExitSniffMode(CommandPacketView command) {
auto command_view = gd_hci::ExitSniffModeView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
auto status =
@@ -1160,10 +988,9 @@ void DualModeController::ExitSniffMode(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::QosSetup(CommandView command) {
+void DualModeController::QosSetup(CommandPacketView command) {
auto command_view = gd_hci::QosSetupView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
uint8_t service_type = static_cast<uint8_t>(command_view.GetServiceType());
@@ -1181,35 +1008,20 @@ void DualModeController::QosSetup(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadDefaultLinkPolicySettings(CommandView command) {
- auto command_view = gd_hci::ReadDefaultLinkPolicySettingsView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
- ASSERT(command_view.IsValid());
- uint16_t settings = link_layer_controller_.ReadDefaultLinkPolicySettings();
- auto packet =
- bluetooth::hci::ReadDefaultLinkPolicySettingsCompleteBuilder::Create(
- kNumCommandPackets, ErrorCode::SUCCESS, settings);
- send_event_(std::move(packet));
-}
-
-void DualModeController::WriteDefaultLinkPolicySettings(CommandView command) {
+void DualModeController::WriteDefaultLinkPolicySettings(
+ CommandPacketView command) {
auto command_view = gd_hci::WriteDefaultLinkPolicySettingsView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
- ErrorCode status = link_layer_controller_.WriteDefaultLinkPolicySettings(
- command_view.GetDefaultLinkPolicySettings());
auto packet =
bluetooth::hci::WriteDefaultLinkPolicySettingsCompleteBuilder::Create(
- kNumCommandPackets, status);
+ kNumCommandPackets, ErrorCode::SUCCESS);
send_event_(std::move(packet));
}
-void DualModeController::FlowSpecification(CommandView command) {
+void DualModeController::FlowSpecification(CommandPacketView command) {
auto command_view = gd_hci::FlowSpecificationView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
uint8_t flow_direction =
@@ -1229,10 +1041,9 @@ void DualModeController::FlowSpecification(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteLinkPolicySettings(CommandView command) {
+void DualModeController::WriteLinkPolicySettings(CommandPacketView command) {
auto command_view = gd_hci::WriteLinkPolicySettingsView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
@@ -1246,13 +1057,13 @@ void DualModeController::WriteLinkPolicySettings(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteLinkSupervisionTimeout(CommandView command) {
+void DualModeController::WriteLinkSupervisionTimeout(
+ CommandPacketView command) {
auto command_view = gd_hci::WriteLinkSupervisionTimeoutView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
- uint16_t handle = command_view.GetConnectionHandle();
+ uint16_t handle = command_view.GetHandle();
uint16_t timeout = command_view.GetLinkSupervisionTimeout();
auto status =
@@ -1263,11 +1074,11 @@ void DualModeController::WriteLinkSupervisionTimeout(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadLocalName(CommandView command) {
+void DualModeController::ReadLocalName(CommandPacketView command) {
auto command_view = gd_hci::ReadLocalNameView::Create(command);
ASSERT(command_view.IsValid());
- std::array<uint8_t, 248> local_name{};
+ std::array<uint8_t, 248> local_name;
local_name.fill(0x00);
size_t len = properties_.GetName().size();
if (len > 247) {
@@ -1280,7 +1091,7 @@ void DualModeController::ReadLocalName(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteLocalName(CommandView command) {
+void DualModeController::WriteLocalName(CommandPacketView command) {
auto command_view = gd_hci::WriteLocalNameView::Create(command);
ASSERT(command_view.IsValid());
const auto local_name = command_view.GetLocalName();
@@ -1294,7 +1105,8 @@ void DualModeController::WriteLocalName(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteExtendedInquiryResponse(CommandView command) {
+void DualModeController::WriteExtendedInquiryResponse(
+ CommandPacketView command) {
auto command_view = gd_hci::WriteExtendedInquiryResponseView::Create(command);
ASSERT(command_view.IsValid());
properties_.SetExtendedInquiryData(std::vector<uint8_t>(
@@ -1305,7 +1117,7 @@ void DualModeController::WriteExtendedInquiryResponse(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::RefreshEncryptionKey(CommandView command) {
+void DualModeController::RefreshEncryptionKey(CommandPacketView command) {
auto command_view = gd_hci::RefreshEncryptionKeyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1321,18 +1133,15 @@ void DualModeController::RefreshEncryptionKey(CommandView command) {
send_event_(std::move(complete_packet));
}
-void DualModeController::WriteVoiceSetting(CommandView command) {
+void DualModeController::WriteVoiceSetting(CommandPacketView command) {
auto command_view = gd_hci::WriteVoiceSettingView::Create(command);
ASSERT(command_view.IsValid());
-
- properties_.SetVoiceSetting(command_view.GetVoiceSetting());
-
auto packet = bluetooth::hci::WriteVoiceSettingCompleteBuilder::Create(
kNumCommandPackets, ErrorCode::SUCCESS);
send_event_(std::move(packet));
}
-void DualModeController::ReadNumberOfSupportedIac(CommandView command) {
+void DualModeController::ReadNumberOfSupportedIac(CommandPacketView command) {
auto command_view = gd_hci::ReadNumberOfSupportedIacView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1342,7 +1151,7 @@ void DualModeController::ReadNumberOfSupportedIac(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadCurrentIacLap(CommandView command) {
+void DualModeController::ReadCurrentIacLap(CommandPacketView command) {
auto command_view = gd_hci::ReadCurrentIacLapView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1353,7 +1162,7 @@ void DualModeController::ReadCurrentIacLap(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteCurrentIacLap(CommandView command) {
+void DualModeController::WriteCurrentIacLap(CommandPacketView command) {
auto command_view = gd_hci::WriteCurrentIacLapView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1362,7 +1171,7 @@ void DualModeController::WriteCurrentIacLap(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadPageScanActivity(CommandView command) {
+void DualModeController::ReadPageScanActivity(CommandPacketView command) {
auto command_view = gd_hci::ReadPageScanActivityView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1373,7 +1182,7 @@ void DualModeController::ReadPageScanActivity(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WritePageScanActivity(CommandView command) {
+void DualModeController::WritePageScanActivity(CommandPacketView command) {
auto command_view = gd_hci::WritePageScanActivityView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1382,7 +1191,7 @@ void DualModeController::WritePageScanActivity(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadInquiryScanActivity(CommandView command) {
+void DualModeController::ReadInquiryScanActivity(CommandPacketView command) {
auto command_view = gd_hci::ReadInquiryScanActivityView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1393,7 +1202,7 @@ void DualModeController::ReadInquiryScanActivity(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteInquiryScanActivity(CommandView command) {
+void DualModeController::WriteInquiryScanActivity(CommandPacketView command) {
auto command_view = gd_hci::WriteInquiryScanActivityView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1402,7 +1211,7 @@ void DualModeController::WriteInquiryScanActivity(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::ReadScanEnable(CommandView command) {
+void DualModeController::ReadScanEnable(CommandPacketView command) {
auto command_view = gd_hci::ReadScanEnableView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1411,7 +1220,7 @@ void DualModeController::ReadScanEnable(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteScanEnable(CommandView command) {
+void DualModeController::WriteScanEnable(CommandPacketView command) {
auto command_view = gd_hci::WriteScanEnableView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1428,7 +1237,7 @@ void DualModeController::WriteScanEnable(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::SetEventFilter(CommandView command) {
+void DualModeController::SetEventFilter(CommandPacketView command) {
auto command_view = gd_hci::SetEventFilterView::Create(command);
ASSERT(command_view.IsValid());
auto packet = bluetooth::hci::SetEventFilterCompleteBuilder::Create(
@@ -1436,7 +1245,7 @@ void DualModeController::SetEventFilter(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::Inquiry(CommandView command) {
+void DualModeController::Inquiry(CommandPacketView command) {
auto command_view = gd_hci::InquiryView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1450,7 +1259,7 @@ void DualModeController::Inquiry(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::InquiryCancel(CommandView command) {
+void DualModeController::InquiryCancel(CommandPacketView command) {
auto command_view = gd_hci::InquiryCancelView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1460,14 +1269,13 @@ void DualModeController::InquiryCancel(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::AcceptConnectionRequest(CommandView command) {
+void DualModeController::AcceptConnectionRequest(CommandPacketView command) {
auto command_view = gd_hci::AcceptConnectionRequestView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
Address addr = command_view.GetBdAddr();
bool try_role_switch = command_view.GetRole() ==
- gd_hci::AcceptConnectionRequestRole::BECOME_CENTRAL;
+ gd_hci::AcceptConnectionRequestRole::BECOME_MASTER;
auto status =
link_layer_controller_.AcceptConnectionRequest(addr, try_role_switch);
auto packet = bluetooth::hci::AcceptConnectionRequestStatusBuilder::Create(
@@ -1475,10 +1283,9 @@ void DualModeController::AcceptConnectionRequest(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::RejectConnectionRequest(CommandView command) {
+void DualModeController::RejectConnectionRequest(CommandPacketView command) {
auto command_view = gd_hci::RejectConnectionRequestView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
Address addr = command_view.GetBdAddr();
uint8_t reason = static_cast<uint8_t>(command_view.GetReason());
@@ -1488,7 +1295,7 @@ void DualModeController::RejectConnectionRequest(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LinkKeyRequestReply(CommandView command) {
+void DualModeController::LinkKeyRequestReply(CommandPacketView command) {
auto command_view = gd_hci::LinkKeyRequestReplyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1500,7 +1307,8 @@ void DualModeController::LinkKeyRequestReply(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LinkKeyRequestNegativeReply(CommandView command) {
+void DualModeController::LinkKeyRequestNegativeReply(
+ CommandPacketView command) {
auto command_view = gd_hci::LinkKeyRequestNegativeReplyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1512,7 +1320,7 @@ void DualModeController::LinkKeyRequestNegativeReply(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::DeleteStoredLinkKey(CommandView command) {
+void DualModeController::DeleteStoredLinkKey(CommandPacketView command) {
auto command_view = gd_hci::DeleteStoredLinkKeyView::Create(
gd_hci::SecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1535,7 +1343,7 @@ void DualModeController::DeleteStoredLinkKey(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::RemoteNameRequest(CommandView command) {
+void DualModeController::RemoteNameRequest(CommandPacketView command) {
auto command_view = gd_hci::RemoteNameRequestView::Create(
gd_hci::DiscoveryCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1550,47 +1358,33 @@ void DualModeController::RemoteNameRequest(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeSetEventMask(CommandView command) {
+void DualModeController::LeSetEventMask(CommandPacketView command) {
auto command_view = gd_hci::LeSetEventMaskView::Create(command);
ASSERT(command_view.IsValid());
- properties_.SetLeEventMask(command_view.GetLeEventMask());
+ /*
+ uint64_t mask = args.begin().extract<uint64_t>();
+ link_layer_controller_.SetLeEventMask(mask);
+*/
auto packet = bluetooth::hci::LeSetEventMaskCompleteBuilder::Create(
kNumCommandPackets, ErrorCode::SUCCESS);
send_event_(std::move(packet));
}
-void DualModeController::LeReadBufferSize(CommandView command) {
- auto command_view = gd_hci::LeReadBufferSizeV1View::Create(command);
+void DualModeController::LeReadBufferSize(CommandPacketView command) {
+ auto command_view = gd_hci::LeReadBufferSizeView::Create(command);
ASSERT(command_view.IsValid());
bluetooth::hci::LeBufferSize le_buffer_size;
le_buffer_size.le_data_packet_length_ = properties_.GetLeDataPacketLength();
le_buffer_size.total_num_le_packets_ = properties_.GetTotalNumLeDataPackets();
- auto packet = bluetooth::hci::LeReadBufferSizeV1CompleteBuilder::Create(
+ auto packet = bluetooth::hci::LeReadBufferSizeCompleteBuilder::Create(
kNumCommandPackets, ErrorCode::SUCCESS, le_buffer_size);
send_event_(std::move(packet));
}
-void DualModeController::LeSetAddressResolutionEnable(CommandView command) {
- // NOP
- auto payload =
- std::make_unique<bluetooth::packet::RawBuilder>(std::vector<uint8_t>(
- {static_cast<uint8_t>(bluetooth::hci::ErrorCode::SUCCESS)}));
- send_event_(bluetooth::hci::CommandCompleteBuilder::Create(
- kNumCommandPackets, command.GetOpCode(), std::move(payload)));
-}
-
-void DualModeController::LeSetResovalablePrivateAddressTimeout(CommandView command) {
- // NOP
- auto payload =
- std::make_unique<bluetooth::packet::RawBuilder>(std::vector<uint8_t>(
- {static_cast<uint8_t>(bluetooth::hci::ErrorCode::SUCCESS)}));
- send_event_(bluetooth::hci::CommandCompleteBuilder::Create(
- kNumCommandPackets, command.GetOpCode(), std::move(payload)));
-}
-
-void DualModeController::LeReadLocalSupportedFeatures(CommandView command) {
+void DualModeController::LeReadLocalSupportedFeatures(
+ CommandPacketView command) {
auto command_view = gd_hci::LeReadLocalSupportedFeaturesView::Create(command);
ASSERT(command_view.IsValid());
auto packet =
@@ -1600,7 +1394,7 @@ void DualModeController::LeReadLocalSupportedFeatures(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeSetRandomAddress(CommandView command) {
+void DualModeController::LeSetRandomAddress(CommandPacketView command) {
auto command_view = gd_hci::LeSetRandomAddressView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1610,22 +1404,16 @@ void DualModeController::LeSetRandomAddress(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeSetAdvertisingParameters(CommandView command) {
+void DualModeController::LeSetAdvertisingParameters(CommandPacketView command) {
auto command_view = gd_hci::LeSetAdvertisingParametersView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
ASSERT(command_view.IsValid());
- auto peer_address = command_view.GetPeerAddress();
- auto type = command_view.GetAdvtType();
- if (type != bluetooth::hci::AdvertisingType::ADV_DIRECT_IND &&
- type != bluetooth::hci::AdvertisingType::ADV_DIRECT_IND_LOW) {
- peer_address = Address::kEmpty;
- }
properties_.SetLeAdvertisingParameters(
command_view.GetIntervalMin(), command_view.GetIntervalMax(),
- static_cast<uint8_t>(type),
+ static_cast<uint8_t>(command_view.GetType()),
static_cast<uint8_t>(command_view.GetOwnAddressType()),
- static_cast<uint8_t>(command_view.GetPeerAddressType()), peer_address,
- command_view.GetChannelMap(),
+ static_cast<uint8_t>(command_view.GetPeerAddressType()),
+ command_view.GetPeerAddress(), command_view.GetChannelMap(),
static_cast<uint8_t>(command_view.GetFilterPolicy()));
auto packet =
@@ -1634,26 +1422,12 @@ void DualModeController::LeSetAdvertisingParameters(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeReadAdvertisingPhysicalChannelTxPower(
- CommandView command) {
- auto command_view =
- gd_hci::LeReadAdvertisingPhysicalChannelTxPowerView::Create(
- gd_hci::LeAdvertisingCommandView::Create(command));
- ASSERT(command_view.IsValid());
- auto packet =
- bluetooth::hci::LeReadAdvertisingPhysicalChannelTxPowerCompleteBuilder::
- Create(kNumCommandPackets, ErrorCode::SUCCESS,
- properties_.GetLeAdvertisingPhysicalChannelTxPower());
- send_event_(std::move(packet));
-}
-
-void DualModeController::LeSetAdvertisingData(CommandView command) {
+void DualModeController::LeSetAdvertisingData(CommandPacketView command) {
auto command_view = gd_hci::LeSetAdvertisingDataView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
auto payload = command.GetPayload();
- auto data_size = *payload.begin();
- auto first_data = payload.begin() + 1;
- std::vector<uint8_t> payload_bytes{first_data, first_data + data_size};
+ std::vector<uint8_t> payload_bytes{payload.begin() + 1,
+ payload.begin() + *payload.begin()};
ASSERT_LOG(command_view.IsValid(), "%s command.size() = %zu",
gd_hci::OpCodeText(command.GetOpCode()).c_str(), command.size());
ASSERT(command_view.GetPayload().size() == 32);
@@ -1663,7 +1437,7 @@ void DualModeController::LeSetAdvertisingData(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeSetScanResponseData(CommandView command) {
+void DualModeController::LeSetScanResponseData(CommandPacketView command) {
auto command_view = gd_hci::LeSetScanResponseDataView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1675,17 +1449,18 @@ void DualModeController::LeSetScanResponseData(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeSetAdvertisingEnable(CommandView command) {
+void DualModeController::LeSetAdvertisingEnable(CommandPacketView command) {
auto command_view = gd_hci::LeSetAdvertisingEnableView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
ASSERT(command_view.IsValid());
auto status = link_layer_controller_.SetLeAdvertisingEnable(
command_view.GetAdvertisingEnable() == gd_hci::Enable::ENABLED);
- send_event_(bluetooth::hci::LeSetAdvertisingEnableCompleteBuilder::Create(
- kNumCommandPackets, status));
+ auto packet = bluetooth::hci::LeSetAdvertisingEnableCompleteBuilder::Create(
+ kNumCommandPackets, status);
+ send_event_(std::move(packet));
}
-void DualModeController::LeSetScanParameters(CommandView command) {
+void DualModeController::LeSetScanParameters(CommandPacketView command) {
auto command_view = gd_hci::LeSetScanParametersView::Create(
gd_hci::LeScanningCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1693,7 +1468,8 @@ void DualModeController::LeSetScanParameters(CommandView command) {
static_cast<uint8_t>(command_view.GetLeScanType()));
link_layer_controller_.SetLeScanInterval(command_view.GetLeScanInterval());
link_layer_controller_.SetLeScanWindow(command_view.GetLeScanWindow());
- link_layer_controller_.SetLeAddressType(command_view.GetOwnAddressType());
+ link_layer_controller_.SetLeAddressType(
+ static_cast<uint8_t>(command_view.GetOwnAddressType()));
link_layer_controller_.SetLeScanFilterPolicy(
static_cast<uint8_t>(command_view.GetScanningFilterPolicy()));
auto packet = bluetooth::hci::LeSetScanParametersCompleteBuilder::Create(
@@ -1701,7 +1477,7 @@ void DualModeController::LeSetScanParameters(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeSetScanEnable(CommandView command) {
+void DualModeController::LeSetScanEnable(CommandPacketView command) {
auto command_view = gd_hci::LeSetScanEnableView::Create(
gd_hci::LeScanningCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1717,10 +1493,9 @@ void DualModeController::LeSetScanEnable(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeCreateConnection(CommandView command) {
+void DualModeController::LeCreateConnection(CommandPacketView command) {
auto command_view = gd_hci::LeCreateConnectionView::Create(
- gd_hci::LeConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::LeConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
link_layer_controller_.SetLeScanInterval(command_view.GetLeScanInterval());
link_layer_controller_.SetLeScanWindow(command_view.GetLeScanWindow());
@@ -1728,14 +1503,15 @@ void DualModeController::LeCreateConnection(CommandView command) {
static_cast<uint8_t>(command_view.GetInitiatorFilterPolicy());
link_layer_controller_.SetLeInitiatorFilterPolicy(initiator_filter_policy);
- if (initiator_filter_policy == 0) { // Connect list not used
+ if (initiator_filter_policy == 0) { // White list not used
uint8_t peer_address_type =
static_cast<uint8_t>(command_view.GetPeerAddressType());
Address peer_address = command_view.GetPeerAddress();
link_layer_controller_.SetLePeerAddressType(peer_address_type);
link_layer_controller_.SetLePeerAddress(peer_address);
}
- link_layer_controller_.SetLeAddressType(command_view.GetOwnAddressType());
+ link_layer_controller_.SetLeAddressType(
+ static_cast<uint8_t>(command_view.GetOwnAddressType()));
link_layer_controller_.SetLeConnectionIntervalMin(
command_view.GetConnIntervalMin());
link_layer_controller_.SetLeConnectionIntervalMax(
@@ -1755,22 +1531,24 @@ void DualModeController::LeCreateConnection(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeConnectionUpdate(CommandView command) {
+void DualModeController::LeConnectionUpdate(CommandPacketView command) {
auto command_view = gd_hci::LeConnectionUpdateView::Create(
- gd_hci::LeConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::LeConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
- ErrorCode status = link_layer_controller_.LeConnectionUpdate(command_view);
auto status_packet = bluetooth::hci::LeConnectionUpdateStatusBuilder::Create(
- status, kNumCommandPackets);
+ ErrorCode::CONNECTION_REJECTED_UNACCEPTABLE_BD_ADDR, kNumCommandPackets);
send_event_(std::move(status_packet));
+
+ auto complete_packet =
+ bluetooth::hci::LeConnectionUpdateCompleteBuilder::Create(
+ ErrorCode::SUCCESS, 0x0002, 0x0006, 0x0000, 0x01f4);
+ send_event_(std::move(complete_packet));
}
-void DualModeController::CreateConnection(CommandView command) {
+void DualModeController::CreateConnection(CommandPacketView command) {
auto command_view = gd_hci::CreateConnectionView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
Address address = command_view.GetBdAddr();
@@ -1792,25 +1570,9 @@ void DualModeController::CreateConnection(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::CreateConnectionCancel(CommandView command) {
- auto command_view = gd_hci::CreateConnectionCancelView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
- ASSERT(command_view.IsValid());
-
- Address address = command_view.GetBdAddr();
-
- auto status = link_layer_controller_.CreateConnectionCancel(address);
-
- auto packet = bluetooth::hci::CreateConnectionCancelCompleteBuilder::Create(
- kNumCommandPackets, status, address);
- send_event_(std::move(packet));
-}
-
-void DualModeController::Disconnect(CommandView command) {
+void DualModeController::Disconnect(CommandPacketView command) {
auto command_view = gd_hci::DisconnectView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::ConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
@@ -1823,77 +1585,76 @@ void DualModeController::Disconnect(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeConnectionCancel(CommandView command) {
+void DualModeController::LeConnectionCancel(CommandPacketView command) {
auto command_view = gd_hci::LeCreateConnectionCancelView::Create(
- gd_hci::LeConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::LeConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
- ErrorCode status = link_layer_controller_.SetLeConnect(false);
- send_event_(bluetooth::hci::LeCreateConnectionCancelCompleteBuilder::Create(
- kNumCommandPackets, status));
-
- send_event_(bluetooth::hci::LeConnectionCompleteBuilder::Create(
- ErrorCode::UNKNOWN_CONNECTION, kReservedHandle,
- bluetooth::hci::Role::CENTRAL,
- bluetooth::hci::AddressType::PUBLIC_DEVICE_ADDRESS,
- bluetooth::hci::Address(), 1 /* connection_interval */,
- 2 /* connection_latency */, 3 /* supervision_timeout*/,
- static_cast<bluetooth::hci::ClockAccuracy>(0x00)));
+ link_layer_controller_.SetLeConnect(false);
+ auto packet = bluetooth::hci::LeCreateConnectionCancelStatusBuilder::Create(
+ ErrorCode::SUCCESS, kNumCommandPackets);
+ send_event_(std::move(packet));
+ /* For testing Jakub's patch: Figure out a neat way to call this without
+ recompiling. I'm thinking about a bad device. */
+ /*
+ SendCommandCompleteOnlyStatus(OpCode::LE_CREATE_CONNECTION_CANCEL,
+ ErrorCode::COMMAND_DISALLOWED);
+ */
}
-void DualModeController::LeReadConnectListSize(CommandView command) {
- auto command_view = gd_hci::LeReadConnectListSizeView::Create(
- gd_hci::LeConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+void DualModeController::LeReadWhiteListSize(CommandPacketView command) {
+ auto command_view = gd_hci::LeReadWhiteListSizeView::Create(
+ gd_hci::LeConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
- auto packet = bluetooth::hci::LeReadConnectListSizeCompleteBuilder::Create(
- kNumCommandPackets, ErrorCode::SUCCESS,
- properties_.GetLeConnectListSize());
+ auto packet = bluetooth::hci::LeReadWhiteListSizeCompleteBuilder::Create(
+ kNumCommandPackets, ErrorCode::SUCCESS, properties_.GetLeWhiteListSize());
send_event_(std::move(packet));
}
-void DualModeController::LeClearConnectList(CommandView command) {
- auto command_view = gd_hci::LeClearConnectListView::Create(
- gd_hci::LeConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+void DualModeController::LeClearWhiteList(CommandPacketView command) {
+ auto command_view = gd_hci::LeClearWhiteListView::Create(
+ gd_hci::LeConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
- link_layer_controller_.LeConnectListClear();
- auto packet = bluetooth::hci::LeClearConnectListCompleteBuilder::Create(
+ link_layer_controller_.LeWhiteListClear();
+ auto packet = bluetooth::hci::LeClearWhiteListCompleteBuilder::Create(
kNumCommandPackets, ErrorCode::SUCCESS);
send_event_(std::move(packet));
}
-void DualModeController::LeAddDeviceToConnectList(CommandView command) {
- auto command_view = gd_hci::LeAddDeviceToConnectListView::Create(
- gd_hci::LeConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+void DualModeController::LeAddDeviceToWhiteList(CommandPacketView command) {
+ auto command_view = gd_hci::LeAddDeviceToWhiteListView::Create(
+ gd_hci::LeConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
+ if (link_layer_controller_.LeWhiteListFull()) {
+ auto packet = bluetooth::hci::LeAddDeviceToWhiteListCompleteBuilder::Create(
+ kNumCommandPackets, ErrorCode::MEMORY_CAPACITY_EXCEEDED);
+ send_event_(std::move(packet));
+ return;
+ }
uint8_t addr_type = static_cast<uint8_t>(command_view.GetAddressType());
Address address = command_view.GetAddress();
- ErrorCode result =
- link_layer_controller_.LeConnectListAddDevice(address, addr_type);
- auto packet = bluetooth::hci::LeAddDeviceToConnectListCompleteBuilder::Create(
- kNumCommandPackets, result);
+ link_layer_controller_.LeWhiteListAddDevice(address, addr_type);
+ auto packet = bluetooth::hci::LeAddDeviceToWhiteListCompleteBuilder::Create(
+ kNumCommandPackets, ErrorCode::SUCCESS);
send_event_(std::move(packet));
}
-void DualModeController::LeRemoveDeviceFromConnectList(CommandView command) {
- auto command_view = gd_hci::LeRemoveDeviceFromConnectListView::Create(
- gd_hci::LeConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+void DualModeController::LeRemoveDeviceFromWhiteList(
+ CommandPacketView command) {
+ auto command_view = gd_hci::LeRemoveDeviceFromWhiteListView::Create(
+ gd_hci::LeConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint8_t addr_type = static_cast<uint8_t>(command_view.GetAddressType());
Address address = command_view.GetAddress();
- link_layer_controller_.LeConnectListRemoveDevice(address, addr_type);
+ link_layer_controller_.LeWhiteListRemoveDevice(address, addr_type);
auto packet =
- bluetooth::hci::LeRemoveDeviceFromConnectListCompleteBuilder::Create(
+ bluetooth::hci::LeRemoveDeviceFromWhiteListCompleteBuilder::Create(
kNumCommandPackets, ErrorCode::SUCCESS);
send_event_(std::move(packet));
}
-void DualModeController::LeClearResolvingList(CommandView command) {
+void DualModeController::LeClearResolvingList(CommandPacketView command) {
auto command_view = gd_hci::LeClearResolvingListView::Create(
gd_hci::LeSecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1903,43 +1664,18 @@ void DualModeController::LeClearResolvingList(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeReadResolvingListSize(CommandView command) {
- auto command_view = gd_hci::LeReadResolvingListSizeView::Create(
- gd_hci::LeSecurityCommandView::Create(command));
- ASSERT(command_view.IsValid());
- auto packet = bluetooth::hci::LeReadResolvingListSizeCompleteBuilder::Create(
- kNumCommandPackets, ErrorCode::SUCCESS,
- properties_.GetLeResolvingListSize());
- send_event_(std::move(packet));
-}
-
-void DualModeController::LeReadMaximumDataLength(CommandView command) {
- auto command_view = gd_hci::LeReadMaximumDataLengthView::Create(
- gd_hci::LeSecurityCommandView::Create(command));
- ASSERT(command_view.IsValid());
- bluetooth::hci::LeMaximumDataLength data_length;
- data_length.supported_max_rx_octets_ = kLeMaximumDataLength;
- data_length.supported_max_rx_time_ = kLeMaximumDataTime;
- data_length.supported_max_tx_octets_ = kLeMaximumDataLength + 10;
- data_length.supported_max_tx_time_ = kLeMaximumDataTime + 10;
- send_event_(bluetooth::hci::LeReadMaximumDataLengthCompleteBuilder::Create(
- kNumCommandPackets, ErrorCode::SUCCESS, data_length));
-}
-
-void DualModeController::LeReadSuggestedDefaultDataLength(CommandView command) {
- auto command_view = gd_hci::LeReadSuggestedDefaultDataLengthView::Create(
- gd_hci::LeConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
- ASSERT(command_view.IsValid());
- send_event_(bluetooth::hci::LeReadSuggestedDefaultDataLengthCompleteBuilder::Create(
- kNumCommandPackets, ErrorCode::SUCCESS, kLeMaximumDataLength, kLeMaximumDataTime));
-}
-
-void DualModeController::LeAddDeviceToResolvingList(CommandView command) {
+void DualModeController::LeAddDeviceToResolvingList(CommandPacketView command) {
auto command_view = gd_hci::LeAddDeviceToResolvingListView::Create(
gd_hci::LeSecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
+ if (link_layer_controller_.LeResolvingListFull()) {
+ auto packet =
+ bluetooth::hci::LeAddDeviceToResolvingListCompleteBuilder::Create(
+ kNumCommandPackets, ErrorCode::MEMORY_CAPACITY_EXCEEDED);
+ send_event_(std::move(packet));
+ return;
+ }
uint8_t addr_type =
static_cast<uint8_t>(command_view.GetPeerIdentityAddressType());
Address address = command_view.GetPeerIdentityAddress();
@@ -1948,15 +1684,16 @@ void DualModeController::LeAddDeviceToResolvingList(CommandView command) {
std::array<uint8_t, LinkLayerController::kIrk_size> localIrk =
command_view.GetLocalIrk();
- auto status = link_layer_controller_.LeResolvingListAddDevice(
- address, addr_type, peerIrk, localIrk);
+ link_layer_controller_.LeResolvingListAddDevice(address, addr_type, peerIrk,
+ localIrk);
auto packet =
bluetooth::hci::LeAddDeviceToResolvingListCompleteBuilder::Create(
- kNumCommandPackets, status);
+ kNumCommandPackets, ErrorCode::SUCCESS);
send_event_(std::move(packet));
}
-void DualModeController::LeRemoveDeviceFromResolvingList(CommandView command) {
+void DualModeController::LeRemoveDeviceFromResolvingList(
+ CommandPacketView command) {
auto command_view = gd_hci::LeRemoveDeviceFromResolvingListView::Create(
gd_hci::LeSecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1971,7 +1708,8 @@ void DualModeController::LeRemoveDeviceFromResolvingList(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeSetExtendedScanParameters(CommandView command) {
+void DualModeController::LeSetExtendedScanParameters(
+ CommandPacketView command) {
auto command_view = gd_hci::LeSetExtendedScanParametersView::Create(
gd_hci::LeScanningCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -1980,24 +1718,21 @@ void DualModeController::LeSetExtendedScanParameters(CommandView command) {
ASSERT(command_view.GetScanningPhys() == 1);
ASSERT(parameters.size() == 1);
- auto status = ErrorCode::SUCCESS;
- if (link_layer_controller_.GetLeScanEnable() == OpCode::NONE) {
- link_layer_controller_.SetLeScanType(
- static_cast<uint8_t>(parameters[0].le_scan_type_));
- link_layer_controller_.SetLeScanInterval(parameters[0].le_scan_interval_);
- link_layer_controller_.SetLeScanWindow(parameters[0].le_scan_window_);
- link_layer_controller_.SetLeAddressType(command_view.GetOwnAddressType());
- link_layer_controller_.SetLeScanFilterPolicy(
- static_cast<uint8_t>(command_view.GetScanningFilterPolicy()));
- } else {
- status = ErrorCode::COMMAND_DISALLOWED;
- }
- send_event_(
+ link_layer_controller_.SetLeScanType(
+ static_cast<uint8_t>(parameters[0].le_scan_type_));
+ link_layer_controller_.SetLeScanInterval(parameters[0].le_scan_interval_);
+ link_layer_controller_.SetLeScanWindow(parameters[0].le_scan_window_);
+ link_layer_controller_.SetLeAddressType(
+ static_cast<uint8_t>(command_view.GetOwnAddressType()));
+ link_layer_controller_.SetLeScanFilterPolicy(
+ static_cast<uint8_t>(command_view.GetScanningFilterPolicy()));
+ auto packet =
bluetooth::hci::LeSetExtendedScanParametersCompleteBuilder::Create(
- kNumCommandPackets, status));
+ kNumCommandPackets, ErrorCode::SUCCESS);
+ send_event_(std::move(packet));
}
-void DualModeController::LeSetExtendedScanEnable(CommandView command) {
+void DualModeController::LeSetExtendedScanEnable(CommandPacketView command) {
auto command_view = gd_hci::LeSetExtendedScanEnableView::Create(
gd_hci::LeScanningCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -2014,10 +1749,9 @@ void DualModeController::LeSetExtendedScanEnable(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeExtendedCreateConnection(CommandView command) {
+void DualModeController::LeExtendedCreateConnection(CommandPacketView command) {
auto command_view = gd_hci::LeExtendedCreateConnectionView::Create(
- gd_hci::LeConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::LeConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
ASSERT_LOG(command_view.GetInitiatingPhys() == 1, "Only LE_1M is supported");
auto params = command_view.GetPhyScanParameters();
@@ -2033,7 +1767,8 @@ void DualModeController::LeExtendedCreateConnection(CommandView command) {
static_cast<uint8_t>(command_view.GetPeerAddressType()));
link_layer_controller_.SetLePeerAddress(command_view.GetPeerAddress());
}
- link_layer_controller_.SetLeAddressType(command_view.GetOwnAddressType());
+ link_layer_controller_.SetLeAddressType(
+ static_cast<uint8_t>(command_view.GetOwnAddressType()));
link_layer_controller_.SetLeConnectionIntervalMin(
params[0].conn_interval_min_);
link_layer_controller_.SetLeConnectionIntervalMax(
@@ -2050,7 +1785,7 @@ void DualModeController::LeExtendedCreateConnection(CommandView command) {
status, kNumCommandPackets));
}
-void DualModeController::LeSetPrivacyMode(CommandView command) {
+void DualModeController::LeSetPrivacyMode(CommandPacketView command) {
auto command_view = gd_hci::LeSetPrivacyModeView::Create(
gd_hci::LeSecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -2071,163 +1806,9 @@ void DualModeController::LeSetPrivacyMode(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeReadIsoTxSync(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeReadIsoTxSyncView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- link_layer_controller_.LeReadIsoTxSync(command_view.GetConnectionHandle());
-}
-
-void DualModeController::LeSetCigParameters(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeSetCigParametersView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- link_layer_controller_.LeSetCigParameters(
- command_view.GetCigId(), command_view.GetSduIntervalMToS(),
- command_view.GetSduIntervalSToM(),
- command_view.GetPeripheralsClockAccuracy(), command_view.GetPacking(),
- command_view.GetFraming(), command_view.GetMaxTransportLatencyMToS(),
- command_view.GetMaxTransportLatencySToM(), command_view.GetCisConfig());
-}
-
-void DualModeController::LeCreateCis(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeCreateCisView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- ErrorCode status =
- link_layer_controller_.LeCreateCis(command_view.GetCisConfig());
- send_event_(bluetooth::hci::LeCreateCisStatusBuilder::Create(
- status, kNumCommandPackets));
-}
-
-void DualModeController::LeRemoveCig(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeRemoveCigView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- uint8_t cig = command_view.GetCigId();
- ErrorCode status = link_layer_controller_.LeRemoveCig(cig);
- send_event_(bluetooth::hci::LeRemoveCigCompleteBuilder::Create(
- kNumCommandPackets, status, cig));
-}
-
-void DualModeController::LeAcceptCisRequest(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeAcceptCisRequestView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- ErrorCode status = link_layer_controller_.LeAcceptCisRequest(
- command_view.GetConnectionHandle());
- send_event_(bluetooth::hci::LeAcceptCisRequestStatusBuilder::Create(
- status, kNumCommandPackets));
-}
-
-void DualModeController::LeRejectCisRequest(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeRejectCisRequestView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- link_layer_controller_.LeRejectCisRequest(command_view.GetConnectionHandle(),
- command_view.GetReason());
-}
-
-void DualModeController::LeCreateBig(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeCreateBigView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- ErrorCode status = link_layer_controller_.LeCreateBig(
- command_view.GetBigHandle(), command_view.GetAdvertisingHandle(),
- command_view.GetNumBis(), command_view.GetSduInterval(),
- command_view.GetMaxSdu(), command_view.GetMaxTransportLatency(),
- command_view.GetRtn(), command_view.GetPhy(), command_view.GetPacking(),
- command_view.GetFraming(), command_view.GetEncryption(),
- command_view.GetBroadcastCode());
- send_event_(bluetooth::hci::LeCreateBigStatusBuilder::Create(
- status, kNumCommandPackets));
-}
-
-void DualModeController::LeTerminateBig(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeTerminateBigView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- ErrorCode status = link_layer_controller_.LeTerminateBig(
- command_view.GetBigHandle(), command_view.GetReason());
- send_event_(bluetooth::hci::LeTerminateBigStatusBuilder::Create(
- status, kNumCommandPackets));
-}
-
-void DualModeController::LeBigCreateSync(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeBigCreateSyncView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- ErrorCode status = link_layer_controller_.LeBigCreateSync(
- command_view.GetBigHandle(), command_view.GetSyncHandle(),
- command_view.GetEncryption(), command_view.GetBroadcastCode(),
- command_view.GetMse(), command_view.GetBigSyncTimeout(),
- command_view.GetBis());
- send_event_(bluetooth::hci::LeBigCreateSyncStatusBuilder::Create(
- status, kNumCommandPackets));
-}
-
-void DualModeController::LeBigTerminateSync(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeBigTerminateSyncView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- link_layer_controller_.LeBigTerminateSync(command_view.GetBigHandle());
-}
-
-void DualModeController::LeRequestPeerSca(CommandView command) {
- auto command_view = gd_hci::LeRequestPeerScaView::Create(std::move(command));
- ASSERT(command_view.IsValid());
- ErrorCode status = link_layer_controller_.LeRequestPeerSca(
- command_view.GetConnectionHandle());
- send_event_(bluetooth::hci::LeRequestPeerScaStatusBuilder::Create(
- status, kNumCommandPackets));
-}
-
-void DualModeController::LeSetupIsoDataPath(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeSetupIsoDataPathView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- link_layer_controller_.LeSetupIsoDataPath(
- command_view.GetConnectionHandle(), command_view.GetDataPathDirection(),
- command_view.GetDataPathId(), command_view.GetCodecId(),
- command_view.GetControllerDelay(), command_view.GetCodecConfiguration());
-}
-
-void DualModeController::LeRemoveIsoDataPath(CommandView command) {
- auto iso_command_view = gd_hci::LeIsoCommandView::Create(command);
- ASSERT(iso_command_view.IsValid());
- auto command_view =
- gd_hci::LeRemoveIsoDataPathView::Create(std::move(iso_command_view));
- ASSERT(command_view.IsValid());
- link_layer_controller_.LeRemoveIsoDataPath(
- command_view.GetConnectionHandle(), command_view.GetDataPathDirection());
-}
-
-void DualModeController::LeReadRemoteFeatures(CommandView command) {
+void DualModeController::LeReadRemoteFeatures(CommandPacketView command) {
auto command_view = gd_hci::LeReadRemoteFeaturesView::Create(
- gd_hci::LeConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
+ gd_hci::LeConnectionManagementCommandView::Create(command));
ASSERT(command_view.IsValid());
uint16_t handle = command_view.GetConnectionHandle();
@@ -2235,12 +1816,12 @@ void DualModeController::LeReadRemoteFeatures(CommandView command) {
auto status = link_layer_controller_.SendCommandToRemoteByHandle(
OpCode::LE_READ_REMOTE_FEATURES, command_view.GetPayload(), handle);
- auto packet = bluetooth::hci::LeReadRemoteFeaturesStatusBuilder::Create(
+ auto packet = bluetooth::hci::LeConnectionUpdateStatusBuilder::Create(
status, kNumCommandPackets);
send_event_(std::move(packet));
}
-void DualModeController::LeRand(CommandView command) {
+void DualModeController::LeRand(CommandPacketView command) {
auto command_view = gd_hci::LeRandView::Create(
gd_hci::LeSecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -2254,7 +1835,7 @@ void DualModeController::LeRand(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeReadSupportedStates(CommandView command) {
+void DualModeController::LeReadSupportedStates(CommandPacketView command) {
auto command_view = gd_hci::LeReadSupportedStatesView::Create(command);
ASSERT(command_view.IsValid());
auto packet = bluetooth::hci::LeReadSupportedStatesCompleteBuilder::Create(
@@ -2263,7 +1844,7 @@ void DualModeController::LeReadSupportedStates(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeVendorCap(CommandView command) {
+void DualModeController::LeVendorCap(CommandPacketView command) {
auto command_view = gd_hci::LeGetVendorCapabilitiesView::Create(
gd_hci::VendorCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -2285,7 +1866,7 @@ void DualModeController::LeVendorCap(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::LeVendorMultiAdv(CommandView command) {
+void DualModeController::LeVendorMultiAdv(CommandPacketView command) {
auto command_view = gd_hci::LeMultiAdvtView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -2293,7 +1874,7 @@ void DualModeController::LeVendorMultiAdv(CommandView command) {
static_cast<uint16_t>(OpCode::LE_MULTI_ADVT));
}
-void DualModeController::LeAdvertisingFilter(CommandView command) {
+void DualModeController::LeAdvertisingFilter(CommandPacketView command) {
auto command_view = gd_hci::LeAdvFilterView::Create(
gd_hci::LeScanningCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -2301,7 +1882,7 @@ void DualModeController::LeAdvertisingFilter(CommandView command) {
static_cast<uint16_t>(OpCode::LE_ADV_FILTER));
}
-void DualModeController::LeEnergyInfo(CommandView command) {
+void DualModeController::LeEnergyInfo(CommandPacketView command) {
auto command_view = gd_hci::LeEnergyInfoView::Create(
gd_hci::VendorCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -2310,48 +1891,47 @@ void DualModeController::LeEnergyInfo(CommandView command) {
}
void DualModeController::LeSetExtendedAdvertisingRandomAddress(
- CommandView command) {
+ CommandPacketView command) {
auto command_view = gd_hci::LeSetExtendedAdvertisingRandomAddressView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
ASSERT(command_view.IsValid());
- link_layer_controller_.SetLeExtendedAddress(
- command_view.GetAdvertisingHandle(),
- command_view.GetAdvertisingRandomAddress());
+ properties_.SetLeAddress(command_view.GetAdvertisingRandomAddress());
send_event_(
bluetooth::hci::LeSetExtendedAdvertisingRandomAddressCompleteBuilder::
Create(kNumCommandPackets, ErrorCode::SUCCESS));
}
void DualModeController::LeSetExtendedAdvertisingParameters(
- CommandView command) {
+ CommandPacketView command) {
auto command_view =
gd_hci::LeSetExtendedAdvertisingLegacyParametersView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
// TODO: Support non-legacy parameters
ASSERT(command_view.IsValid());
- link_layer_controller_.SetLeExtendedAdvertisingParameters(
- command_view.GetAdvertisingHandle(),
+ properties_.SetLeAdvertisingParameters(
command_view.GetPrimaryAdvertisingIntervalMin(),
command_view.GetPrimaryAdvertisingIntervalMax(),
- command_view.GetAdvertisingEventLegacyProperties(),
- command_view.GetOwnAddressType(), command_view.GetPeerAddressType(),
- command_view.GetPeerAddress(), command_view.GetAdvertisingFilterPolicy());
+ static_cast<uint8_t>(bluetooth::hci::AdvertisingEventType::ADV_IND),
+ static_cast<uint8_t>(command_view.GetOwnAddressType()),
+ static_cast<uint8_t>(command_view.GetPeerAddressType()),
+ command_view.GetPeerAddress(),
+ command_view.GetPrimaryAdvertisingChannelMap(),
+ static_cast<uint8_t>(command_view.GetAdvertisingFilterPolicy()));
send_event_(
bluetooth::hci::LeSetExtendedAdvertisingParametersCompleteBuilder::Create(
kNumCommandPackets, ErrorCode::SUCCESS, 0xa5));
}
-void DualModeController::LeSetExtendedAdvertisingData(CommandView command) {
+void DualModeController::LeSetExtendedAdvertisingData(
+ CommandPacketView command) {
auto command_view = gd_hci::LeSetExtendedAdvertisingDataView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
ASSERT(command_view.IsValid());
auto raw_command_view = gd_hci::LeSetExtendedAdvertisingDataRawView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
ASSERT(raw_command_view.IsValid());
- link_layer_controller_.SetLeExtendedAdvertisingData(
- command_view.GetAdvertisingHandle(),
- raw_command_view.GetAdvertisingData());
+ properties_.SetLeAdvertisement(raw_command_view.GetAdvertisingData());
auto packet =
bluetooth::hci::LeSetExtendedAdvertisingDataCompleteBuilder::Create(
kNumCommandPackets, ErrorCode::SUCCESS);
@@ -2359,7 +1939,7 @@ void DualModeController::LeSetExtendedAdvertisingData(CommandView command) {
}
void DualModeController::LeSetExtendedAdvertisingScanResponse(
- CommandView command) {
+ CommandPacketView command) {
auto command_view = gd_hci::LeSetExtendedAdvertisingScanResponseView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -2370,67 +1950,19 @@ void DualModeController::LeSetExtendedAdvertisingScanResponse(
Create(kNumCommandPackets, ErrorCode::SUCCESS));
}
-void DualModeController::LeSetExtendedAdvertisingEnable(CommandView command) {
+void DualModeController::LeSetExtendedAdvertisingEnable(
+ CommandPacketView command) {
auto command_view = gd_hci::LeSetExtendedAdvertisingEnableView::Create(
gd_hci::LeAdvertisingCommandView::Create(command));
ASSERT(command_view.IsValid());
- auto enabled_sets = command_view.GetEnabledSets();
- ErrorCode status = ErrorCode::SUCCESS;
- if (enabled_sets.size() == 0) {
- link_layer_controller_.LeDisableAdvertisingSets();
- } else {
- status = link_layer_controller_.SetLeExtendedAdvertisingEnable(
- command_view.GetEnable(), command_view.GetEnabledSets());
- }
+ auto status = link_layer_controller_.SetLeAdvertisingEnable(
+ command_view.GetEnable() == gd_hci::Enable::ENABLED);
send_event_(
bluetooth::hci::LeSetExtendedAdvertisingEnableCompleteBuilder::Create(
kNumCommandPackets, status));
}
-void DualModeController::LeReadMaximumAdvertisingDataLength(
- CommandView command) {
- auto command_view = gd_hci::LeReadMaximumAdvertisingDataLengthView::Create(
- gd_hci::LeAdvertisingCommandView::Create(command));
- ASSERT(command_view.IsValid());
- send_event_(
- bluetooth::hci::LeReadMaximumAdvertisingDataLengthCompleteBuilder::Create(
- kNumCommandPackets, ErrorCode::SUCCESS,
- kLeMaximumAdvertisingDataLength));
-}
-
-void DualModeController::LeReadNumberOfSupportedAdvertisingSets(
- CommandView command) {
- auto command_view =
- gd_hci::LeReadNumberOfSupportedAdvertisingSetsView::Create(
- gd_hci::LeAdvertisingCommandView::Create(command));
- ASSERT(command_view.IsValid());
- send_event_(
- bluetooth::hci::LeReadNumberOfSupportedAdvertisingSetsCompleteBuilder::
- Create(
- kNumCommandPackets, ErrorCode::SUCCESS,
- link_layer_controller_.LeReadNumberOfSupportedAdvertisingSets()));
-}
-
-void DualModeController::LeRemoveAdvertisingSet(CommandView command) {
- auto command_view = gd_hci::LeRemoveAdvertisingSetView::Create(
- gd_hci::LeAdvertisingCommandView::Create(command));
- ASSERT(command_view.IsValid());
- auto status = link_layer_controller_.LeRemoveAdvertisingSet(
- command_view.GetAdvertisingHandle());
- send_event_(bluetooth::hci::LeRemoveAdvertisingSetCompleteBuilder::Create(
- kNumCommandPackets, status));
-}
-
-void DualModeController::LeClearAdvertisingSets(CommandView command) {
- auto command_view = gd_hci::LeClearAdvertisingSetsView::Create(
- gd_hci::LeAdvertisingCommandView::Create(command));
- ASSERT(command_view.IsValid());
- auto status = link_layer_controller_.LeClearAdvertisingSets();
- send_event_(bluetooth::hci::LeClearAdvertisingSetsCompleteBuilder::Create(
- kNumCommandPackets, status));
-}
-
-void DualModeController::LeExtendedScanParams(CommandView command) {
+void DualModeController::LeExtendedScanParams(CommandPacketView command) {
auto command_view = gd_hci::LeExtendedScanParamsView::Create(
gd_hci::LeScanningCommandView::Create(command));
ASSERT(command_view.IsValid());
@@ -2438,94 +1970,23 @@ void DualModeController::LeExtendedScanParams(CommandView command) {
static_cast<uint16_t>(OpCode::LE_EXTENDED_SCAN_PARAMS));
}
-void DualModeController::LeStartEncryption(CommandView command) {
+void DualModeController::LeStartEncryption(CommandPacketView command) {
auto command_view = gd_hci::LeStartEncryptionView::Create(
gd_hci::LeSecurityCommandView::Create(command));
ASSERT(command_view.IsValid());
- ErrorCode status = link_layer_controller_.LeEnableEncryption(
- command_view.GetConnectionHandle(), command_view.GetRand(),
- command_view.GetEdiv(), command_view.GetLtk());
-
- send_event_(bluetooth::hci::LeStartEncryptionStatusBuilder::Create(
- status, kNumCommandPackets));
-}
-
-void DualModeController::LeLongTermKeyRequestReply(CommandView command) {
- auto command_view = gd_hci::LeLongTermKeyRequestReplyView::Create(
- gd_hci::LeSecurityCommandView::Create(command));
- ASSERT(command_view.IsValid());
-
- uint16_t handle = command_view.GetConnectionHandle();
- ErrorCode status = link_layer_controller_.LeLongTermKeyRequestReply(
- handle, command_view.GetLongTermKey());
-
- send_event_(bluetooth::hci::LeLongTermKeyRequestReplyCompleteBuilder::Create(
- kNumCommandPackets, status, handle));
-}
-
-void DualModeController::LeLongTermKeyRequestNegativeReply(
- CommandView command) {
- auto command_view = gd_hci::LeLongTermKeyRequestNegativeReplyView::Create(
- gd_hci::LeSecurityCommandView::Create(command));
- ASSERT(command_view.IsValid());
-
uint16_t handle = command_view.GetConnectionHandle();
- ErrorCode status =
- link_layer_controller_.LeLongTermKeyRequestNegativeReply(handle);
-
- send_event_(
- bluetooth::hci::LeLongTermKeyRequestNegativeReplyCompleteBuilder::Create(
- kNumCommandPackets, status, handle));
-}
-
-void DualModeController::ReadClassOfDevice(CommandView command) {
- auto command_view = gd_hci::ReadClassOfDeviceView::Create(
- gd_hci::DiscoveryCommandView::Create(command));
- ASSERT(command_view.IsValid());
-
- auto packet = bluetooth::hci::ReadClassOfDeviceCompleteBuilder::Create(
- kNumCommandPackets, ErrorCode::SUCCESS, properties_.GetClassOfDevice());
- send_event_(std::move(packet));
-}
-
-void DualModeController::ReadVoiceSetting(CommandView command) {
- auto command_view = gd_hci::ReadVoiceSettingView::Create(command);
- ASSERT(command_view.IsValid());
-
- auto packet = bluetooth::hci::ReadVoiceSettingCompleteBuilder::Create(
- kNumCommandPackets, ErrorCode::SUCCESS, properties_.GetVoiceSetting());
- send_event_(std::move(packet));
-}
-
-void DualModeController::ReadConnectionAcceptTimeout(CommandView command) {
- auto command_view = gd_hci::ReadConnectionAcceptTimeoutView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
- ASSERT(command_view.IsValid());
-
- auto packet =
- bluetooth::hci::ReadConnectionAcceptTimeoutCompleteBuilder::Create(
- kNumCommandPackets, ErrorCode::SUCCESS,
- properties_.GetConnectionAcceptTimeout());
- send_event_(std::move(packet));
-}
-void DualModeController::WriteConnectionAcceptTimeout(CommandView command) {
- auto command_view = gd_hci::WriteConnectionAcceptTimeoutView::Create(
- gd_hci::ConnectionManagementCommandView::Create(
- gd_hci::AclCommandView::Create(command)));
- ASSERT(command_view.IsValid());
-
- properties_.SetConnectionAcceptTimeout(command_view.GetConnAcceptTimeout());
+ auto status_packet = bluetooth::hci::LeStartEncryptionStatusBuilder::Create(
+ ErrorCode::SUCCESS, kNumCommandPackets);
+ send_event_(std::move(status_packet));
- auto packet =
- bluetooth::hci::WriteConnectionAcceptTimeoutCompleteBuilder::Create(
- kNumCommandPackets, ErrorCode::SUCCESS);
- send_event_(std::move(packet));
+ auto complete_packet = bluetooth::hci::EncryptionChangeBuilder::Create(
+ ErrorCode::SUCCESS, handle, bluetooth::hci::EncryptionEnabled::OFF);
+ send_event_(std::move(complete_packet));
}
-void DualModeController::ReadLoopbackMode(CommandView command) {
+void DualModeController::ReadLoopbackMode(CommandPacketView command) {
auto command_view = gd_hci::ReadLoopbackModeView::Create(command);
ASSERT(command_view.IsValid());
auto packet = bluetooth::hci::ReadLoopbackModeCompleteBuilder::Create(
@@ -2534,7 +1995,7 @@ void DualModeController::ReadLoopbackMode(CommandView command) {
send_event_(std::move(packet));
}
-void DualModeController::WriteLoopbackMode(CommandView command) {
+void DualModeController::WriteLoopbackMode(CommandPacketView command) {
auto command_view = gd_hci::WriteLoopbackModeView::Create(command);
ASSERT(command_view.IsValid());
loopback_mode_ = command_view.GetLoopbackMode();
diff --git a/vendor_libs/test_vendor_lib/model/controller/dual_mode_controller.h b/vendor_libs/test_vendor_lib/model/controller/dual_mode_controller.h
index 5d0e7670a..696d24a6d 100644
--- a/vendor_libs/test_vendor_lib/model/controller/dual_mode_controller.h
+++ b/vendor_libs/test_vendor_lib/model/controller/dual_mode_controller.h
@@ -34,7 +34,7 @@
namespace test_vendor_lib {
using ::bluetooth::hci::Address;
-using ::bluetooth::hci::CommandView;
+using ::bluetooth::hci::CommandPacketView;
// Emulates a dual mode BR/EDR + LE controller by maintaining the link layer
// state machine detailed in the Bluetooth Core Specification Version 4.2,
@@ -107,456 +107,372 @@ class DualModeController : public Device {
// Bluetooth Core Specification Version 4.2 Volume 2 Part E 7.1
// 7.1.1
- void Inquiry(CommandView args);
+ void Inquiry(CommandPacketView args);
// 7.1.2
- void InquiryCancel(CommandView args);
+ void InquiryCancel(CommandPacketView args);
// 7.1.5
- void CreateConnection(CommandView args);
+ void CreateConnection(CommandPacketView args);
// 7.1.6
- void Disconnect(CommandView args);
-
- // 7.1.7
- void CreateConnectionCancel(CommandView args);
+ void Disconnect(CommandPacketView args);
// 7.1.8
- void AcceptConnectionRequest(CommandView args);
+ void AcceptConnectionRequest(CommandPacketView args);
// 7.1.9
- void RejectConnectionRequest(CommandView args);
+ void RejectConnectionRequest(CommandPacketView args);
// 7.1.10
- void LinkKeyRequestReply(CommandView args);
+ void LinkKeyRequestReply(CommandPacketView args);
// 7.1.11
- void LinkKeyRequestNegativeReply(CommandView args);
-
- // 7.1.12
- void PinCodeRequestReply(CommandView args);
-
- // 7.1.13
- void PinCodeRequestNegativeReply(CommandView args);
+ void LinkKeyRequestNegativeReply(CommandPacketView args);
// 7.1.14
- void ChangeConnectionPacketType(CommandView args);
+ void ChangeConnectionPacketType(CommandPacketView args);
// 7.1.15
- void AuthenticationRequested(CommandView args);
+ void AuthenticationRequested(CommandPacketView args);
// 7.1.16
- void SetConnectionEncryption(CommandView args);
+ void SetConnectionEncryption(CommandPacketView args);
// 7.1.17
- void ChangeConnectionLinkKey(CommandView args);
+ void ChangeConnectionLinkKey(CommandPacketView args);
// 7.1.18
- void CentralLinkKey(CommandView args);
+ void MasterLinkKey(CommandPacketView args);
// 7.1.19
- void RemoteNameRequest(CommandView args);
+ void RemoteNameRequest(CommandPacketView args);
// 7.2.8
- void SwitchRole(CommandView args);
+ void SwitchRole(CommandPacketView args);
// 7.1.21
- void ReadRemoteSupportedFeatures(CommandView args);
+ void ReadRemoteSupportedFeatures(CommandPacketView args);
// 7.1.22
- void ReadRemoteExtendedFeatures(CommandView args);
+ void ReadRemoteExtendedFeatures(CommandPacketView args);
// 7.1.23
- void ReadRemoteVersionInformation(CommandView args);
+ void ReadRemoteVersionInformation(CommandPacketView args);
// 7.1.24
- void ReadClockOffset(CommandView args);
+ void ReadClockOffset(CommandPacketView args);
// 7.1.29
- void IoCapabilityRequestReply(CommandView args);
+ void IoCapabilityRequestReply(CommandPacketView args);
// 7.1.30
- void UserConfirmationRequestReply(CommandView args);
+ void UserConfirmationRequestReply(CommandPacketView args);
// 7.1.31
- void UserConfirmationRequestNegativeReply(CommandView args);
+ void UserConfirmationRequestNegativeReply(CommandPacketView args);
// 7.1.32
- void UserPasskeyRequestReply(CommandView args);
+ void UserPasskeyRequestReply(CommandPacketView args);
// 7.1.33
- void UserPasskeyRequestNegativeReply(CommandView args);
+ void UserPasskeyRequestNegativeReply(CommandPacketView args);
// 7.1.34
- void RemoteOobDataRequestReply(CommandView args);
+ void RemoteOobDataRequestReply(CommandPacketView args);
// 7.1.35
- void RemoteOobDataRequestNegativeReply(CommandView args);
+ void RemoteOobDataRequestNegativeReply(CommandPacketView args);
// 7.1.36
- void IoCapabilityRequestNegativeReply(CommandView args);
-
- // 7.1.53
- void RemoteOobExtendedDataRequestReply(CommandView args);
+ void IoCapabilityRequestNegativeReply(CommandPacketView args);
// Link Policy Commands
// Bluetooth Core Specification Version 4.2 Volume 2 Part E 7.2
// 7.2.1
- void HoldMode(CommandView args);
+ void HoldMode(CommandPacketView args);
// 7.2.2
- void SniffMode(CommandView args);
+ void SniffMode(CommandPacketView args);
// 7.2.3
- void ExitSniffMode(CommandView args);
+ void ExitSniffMode(CommandPacketView args);
// 7.2.6
- void QosSetup(CommandView args);
+ void QosSetup(CommandPacketView args);
// 7.2.10
- void WriteLinkPolicySettings(CommandView args);
-
- // 7.2.11
- void ReadDefaultLinkPolicySettings(CommandView args);
+ void WriteLinkPolicySettings(CommandPacketView args);
// 7.2.12
- void WriteDefaultLinkPolicySettings(CommandView args);
+ void WriteDefaultLinkPolicySettings(CommandPacketView args);
// 7.2.13
- void FlowSpecification(CommandView args);
+ void FlowSpecification(CommandPacketView args);
// 7.2.14
- void SniffSubrating(CommandView args);
+ void SniffSubrating(CommandPacketView args);
// Link Controller Commands
// Bluetooth Core Specification Version 4.2 Volume 2 Part E 7.3
// 7.3.1
- void SetEventMask(CommandView args);
+ void SetEventMask(CommandPacketView args);
// 7.3.2
- void Reset(CommandView args);
+ void Reset(CommandPacketView args);
// 7.3.3
- void SetEventFilter(CommandView args);
+ void SetEventFilter(CommandPacketView args);
// 7.3.10
- void DeleteStoredLinkKey(CommandView args);
+ void DeleteStoredLinkKey(CommandPacketView args);
// 7.3.11
- void WriteLocalName(CommandView args);
+ void WriteLocalName(CommandPacketView args);
// 7.3.12
- void ReadLocalName(CommandView args);
+ void ReadLocalName(CommandPacketView args);
// 7.3.15
- void ReadPageTimeout(CommandView args);
+ void ReadPageTimeout(CommandPacketView args);
// 7.3.16
- void WritePageTimeout(CommandView args);
+ void WritePageTimeout(CommandPacketView args);
// 7.3.17
- void ReadScanEnable(CommandView args);
+ void ReadScanEnable(CommandPacketView args);
// 7.3.18
- void WriteScanEnable(CommandView args);
+ void WriteScanEnable(CommandPacketView args);
// 7.3.19
- void ReadPageScanActivity(CommandView args);
+ void ReadPageScanActivity(CommandPacketView args);
// 7.3.20
- void WritePageScanActivity(CommandView args);
+ void WritePageScanActivity(CommandPacketView args);
// 7.3.21
- void ReadInquiryScanActivity(CommandView args);
+ void ReadInquiryScanActivity(CommandPacketView args);
// 7.3.22
- void WriteInquiryScanActivity(CommandView args);
+ void WriteInquiryScanActivity(CommandPacketView args);
// 7.3.23
- void ReadAuthenticationEnable(CommandView args);
+ void ReadAuthenticationEnable(CommandPacketView args);
// 7.3.24
- void WriteAuthenticationEnable(CommandView args);
+ void WriteAuthenticationEnable(CommandPacketView args);
// 7.3.26
- void WriteClassOfDevice(CommandView args);
+ void WriteClassOfDevice(CommandPacketView args);
// 7.3.28
- void WriteVoiceSetting(CommandView args);
+ void WriteVoiceSetting(CommandPacketView args);
// 7.3.39
- void HostBufferSize(CommandView args);
+ void HostBufferSize(CommandPacketView args);
// 7.3.42
- void WriteLinkSupervisionTimeout(CommandView args);
+ void WriteLinkSupervisionTimeout(CommandPacketView args);
// 7.3.43
- void ReadNumberOfSupportedIac(CommandView args);
+ void ReadNumberOfSupportedIac(CommandPacketView args);
// 7.3.44
- void ReadCurrentIacLap(CommandView args);
+ void ReadCurrentIacLap(CommandPacketView args);
// 7.3.45
- void WriteCurrentIacLap(CommandView args);
+ void WriteCurrentIacLap(CommandPacketView args);
// 7.3.47
- void ReadInquiryScanType(CommandView args);
+ void ReadInquiryScanType(CommandPacketView args);
// 7.3.48
- void WriteInquiryScanType(CommandView args);
+ void WriteInquiryScanType(CommandPacketView args);
// 7.3.49
- void ReadInquiryMode(CommandView args);
+ void ReadInquiryMode(CommandPacketView args);
// 7.3.50
- void WriteInquiryMode(CommandView args);
+ void WriteInquiryMode(CommandPacketView args);
// 7.3.52
- void ReadPageScanType(CommandView args);
+ void ReadPageScanType(CommandPacketView args);
// 7.3.52
- void WritePageScanType(CommandView args);
+ void WritePageScanType(CommandPacketView args);
// 7.3.56
- void WriteExtendedInquiryResponse(CommandView args);
+ void WriteExtendedInquiryResponse(CommandPacketView args);
// 7.3.57
- void RefreshEncryptionKey(CommandView args);
+ void RefreshEncryptionKey(CommandPacketView args);
// 7.3.59
- void WriteSimplePairingMode(CommandView args);
-
- // 7.3.60
- void ReadLocalOobData(CommandView args);
+ void WriteSimplePairingMode(CommandPacketView args);
// 7.3.61
- void ReadInquiryResponseTransmitPowerLevel(CommandView args);
-
- // 7.3.63
- void SendKeypressNotification(CommandView args);
-
- // 7.3.69
- void SetEventMaskPage2(CommandView args);
+ void ReadInquiryResponseTransmitPowerLevel(CommandPacketView args);
// 7.3.79
- void WriteLeHostSupport(CommandView args);
+ void WriteLeHostSupport(CommandPacketView args);
// 7.3.92
- void WriteSecureConnectionsHostSupport(CommandView args);
-
- // 7.3.95
- void ReadLocalOobExtendedData(CommandView args);
+ void WriteSecureConnectionsHostSupport(CommandPacketView args);
// Informational Parameters Commands
// Bluetooth Core Specification Version 4.2 Volume 2 Part E 7.4
// 7.4.5
- void ReadBufferSize(CommandView args);
+ void ReadBufferSize(CommandPacketView args);
// 7.4.1
- void ReadLocalVersionInformation(CommandView args);
+ void ReadLocalVersionInformation(CommandPacketView args);
// 7.4.6
- void ReadBdAddr(CommandView args);
+ void ReadBdAddr(CommandPacketView args);
// 7.4.2
- void ReadLocalSupportedCommands(CommandView args);
+ void ReadLocalSupportedCommands(CommandPacketView args);
// 7.4.3
- void ReadLocalSupportedFeatures(CommandView args);
+ void ReadLocalSupportedFeatures(CommandPacketView args);
// 7.4.4
- void ReadLocalExtendedFeatures(CommandView args);
+ void ReadLocalExtendedFeatures(CommandPacketView args);
// 7.4.8
- void ReadLocalSupportedCodecs(CommandView args);
+ void ReadLocalSupportedCodecs(CommandPacketView args);
// Status Parameters Commands
// Bluetooth Core Specification Version 4.2 Volume 2 Part E 7.5
// 7.5.7
- void ReadEncryptionKeySize(CommandView args);
+ void ReadEncryptionKeySize(CommandPacketView args);
// Test Commands
// Bluetooth Core Specification Version 4.2 Volume 2 Part E 7.7
// 7.7.1
- void ReadLoopbackMode(CommandView args);
+ void ReadLoopbackMode(CommandPacketView args);
// 7.7.2
- void WriteLoopbackMode(CommandView args);
+ void WriteLoopbackMode(CommandPacketView args);
// LE Controller Commands
// Bluetooth Core Specification Version 4.2 Volume 2 Part E 7.8
// 7.8.1
- void LeSetEventMask(CommandView args);
+ void LeSetEventMask(CommandPacketView args);
// 7.8.2
- void LeReadBufferSize(CommandView args);
+ void LeReadBufferSize(CommandPacketView args);
// 7.8.3
- void LeReadLocalSupportedFeatures(CommandView args);
+ void LeReadLocalSupportedFeatures(CommandPacketView args);
// 7.8.4
- void LeSetRandomAddress(CommandView args);
+ void LeSetRandomAddress(CommandPacketView args);
// 7.8.5
- void LeSetAdvertisingParameters(CommandView args);
-
- // 7.8.6
- void LeReadAdvertisingPhysicalChannelTxPower(CommandView args);
+ void LeSetAdvertisingParameters(CommandPacketView args);
// 7.8.7
- void LeSetAdvertisingData(CommandView args);
+ void LeSetAdvertisingData(CommandPacketView args);
// 7.8.8
- void LeSetScanResponseData(CommandView args);
+ void LeSetScanResponseData(CommandPacketView args);
// 7.8.9
- void LeSetAdvertisingEnable(CommandView args);
+ void LeSetAdvertisingEnable(CommandPacketView args);
// 7.8.10
- void LeSetScanParameters(CommandView args);
+ void LeSetScanParameters(CommandPacketView args);
// 7.8.11
- void LeSetScanEnable(CommandView args);
+ void LeSetScanEnable(CommandPacketView args);
// 7.8.12
- void LeCreateConnection(CommandView args);
+ void LeCreateConnection(CommandPacketView args);
// 7.8.18
- void LeConnectionUpdate(CommandView args);
+ void LeConnectionUpdate(CommandPacketView args);
// 7.8.13
- void LeConnectionCancel(CommandView args);
+ void LeConnectionCancel(CommandPacketView args);
// 7.8.14
- void LeReadConnectListSize(CommandView args);
+ void LeReadWhiteListSize(CommandPacketView args);
// 7.8.15
- void LeClearConnectList(CommandView args);
+ void LeClearWhiteList(CommandPacketView args);
// 7.8.16
- void LeAddDeviceToConnectList(CommandView args);
+ void LeAddDeviceToWhiteList(CommandPacketView args);
// 7.8.17
- void LeRemoveDeviceFromConnectList(CommandView args);
+ void LeRemoveDeviceFromWhiteList(CommandPacketView args);
// 7.8.21
- void LeReadRemoteFeatures(CommandView args);
+ void LeReadRemoteFeatures(CommandPacketView args);
// 7.8.23
- void LeRand(CommandView args);
+ void LeRand(CommandPacketView args);
// 7.8.24
- void LeStartEncryption(CommandView args);
-
- // 7.8.25
- void LeLongTermKeyRequestReply(CommandView args);
-
- // 7.8.26
- void LeLongTermKeyRequestNegativeReply(CommandView args);
+ void LeStartEncryption(CommandPacketView args);
// 7.8.27
- void LeReadSupportedStates(CommandView args);
-
- // 7.8.34
- void LeReadSuggestedDefaultDataLength(CommandView args);
+ void LeReadSupportedStates(CommandPacketView args);
// 7.8.38
- void LeAddDeviceToResolvingList(CommandView args);
+ void LeAddDeviceToResolvingList(CommandPacketView args);
// 7.8.39
- void LeRemoveDeviceFromResolvingList(CommandView args);
+ void LeRemoveDeviceFromResolvingList(CommandPacketView args);
// 7.8.40
- void LeClearResolvingList(CommandView args);
-
- // 7.8.41
- void LeReadResolvingListSize(CommandView args);
-
- // 7.8.44
- void LeSetAddressResolutionEnable(CommandView args);
-
- // 7.8.45
- void LeSetResovalablePrivateAddressTimeout(CommandView args);
-
- // 7.8.46
- void LeReadMaximumDataLength(CommandView args);
+ void LeClearResolvingList(CommandPacketView args);
// 7.8.52
- void LeSetExtendedAdvertisingRandomAddress(CommandView args);
+ void LeSetExtendedAdvertisingRandomAddress(CommandPacketView args);
// 7.8.53
- void LeSetExtendedAdvertisingParameters(CommandView args);
+ void LeSetExtendedAdvertisingParameters(CommandPacketView args);
// 7.8.54
- void LeSetExtendedAdvertisingData(CommandView args);
+ void LeSetExtendedAdvertisingData(CommandPacketView args);
// 7.8.55
- void LeSetExtendedAdvertisingScanResponse(CommandView args);
+ void LeSetExtendedAdvertisingScanResponse(CommandPacketView args);
// 7.8.56
- void LeSetExtendedAdvertisingEnable(CommandView args);
-
- // 7.8.57
- void LeReadMaximumAdvertisingDataLength(CommandView args);
-
- // 7.8.58
- void LeReadNumberOfSupportedAdvertisingSets(CommandView args);
-
- // 7.8.59
- void LeRemoveAdvertisingSet(CommandView args);
-
- // 7.8.60
- void LeClearAdvertisingSets(CommandView args);
+ void LeSetExtendedAdvertisingEnable(CommandPacketView args);
// 7.8.64
- void LeSetExtendedScanParameters(CommandView args);
+ void LeSetExtendedScanParameters(CommandPacketView args);
// 7.8.65
- void LeSetExtendedScanEnable(CommandView args);
+ void LeSetExtendedScanEnable(CommandPacketView args);
// 7.8.66
- void LeExtendedCreateConnection(CommandView args);
+ void LeExtendedCreateConnection(CommandPacketView args);
// 7.8.77
- void LeSetPrivacyMode(CommandView args);
-
- // 7.8.96 - 7.8.110
- void LeReadIsoTxSync(CommandView packet_view);
- void LeSetCigParameters(CommandView packet_view);
- void LeCreateCis(CommandView packet_view);
- void LeRemoveCig(CommandView packet_view);
- void LeAcceptCisRequest(CommandView packet_view);
- void LeRejectCisRequest(CommandView packet_view);
- void LeCreateBig(CommandView packet_view);
- void LeTerminateBig(CommandView packet_view);
- void LeBigCreateSync(CommandView packet_view);
- void LeBigTerminateSync(CommandView packet_view);
- void LeRequestPeerSca(CommandView packet_view);
- void LeSetupIsoDataPath(CommandView packet_view);
- void LeRemoveIsoDataPath(CommandView packet_view);
+ void LeSetPrivacyMode(CommandPacketView args);
// Vendor-specific Commands
- void LeVendorSleepMode(CommandView args);
- void LeVendorCap(CommandView args);
- void LeVendorMultiAdv(CommandView args);
- void LeVendor155(CommandView args);
- void LeVendor157(CommandView args);
- void LeEnergyInfo(CommandView args);
- void LeAdvertisingFilter(CommandView args);
- void LeExtendedScanParams(CommandView args);
-
- // Required commands for handshaking with hci driver
- void ReadClassOfDevice(CommandView args);
- void ReadVoiceSetting(CommandView args);
- void ReadConnectionAcceptTimeout(CommandView args);
- void WriteConnectionAcceptTimeout(CommandView args);
+ void LeVendorSleepMode(CommandPacketView args);
+ void LeVendorCap(CommandPacketView args);
+ void LeVendorMultiAdv(CommandPacketView args);
+ void LeVendor155(CommandPacketView args);
+ void LeVendor157(CommandPacketView args);
+ void LeEnergyInfo(CommandPacketView args);
+ void LeAdvertisingFilter(CommandPacketView args);
+ void LeExtendedScanParams(CommandPacketView args);
void SetTimerPeriod(std::chrono::milliseconds new_period);
void StartTimer();
@@ -574,17 +490,18 @@ class DualModeController : public Device {
void SendCommandCompleteUnknownOpCodeEvent(uint16_t command_opcode) const;
// Callbacks to send packets back to the HCI.
- std::function<void(std::shared_ptr<bluetooth::hci::AclBuilder>)> send_acl_;
- std::function<void(std::shared_ptr<bluetooth::hci::EventBuilder>)>
+ std::function<void(std::shared_ptr<bluetooth::hci::AclPacketBuilder>)>
+ send_acl_;
+ std::function<void(std::shared_ptr<bluetooth::hci::EventPacketBuilder>)>
send_event_;
- std::function<void(std::shared_ptr<bluetooth::hci::ScoBuilder>)> send_sco_;
- std::function<void(std::shared_ptr<bluetooth::hci::IsoBuilder>)> send_iso_;
+ std::function<void(std::shared_ptr<std::vector<uint8_t>>)> send_sco_;
+ std::function<void(std::shared_ptr<std::vector<uint8_t>>)> send_iso_;
// Maintains the commands to be registered and used in the HciHandler object.
// Keys are command opcodes and values are the callbacks to handle each
// command.
std::unordered_map<bluetooth::hci::OpCode,
- std::function<void(bluetooth::hci::CommandView)>>
+ std::function<void(bluetooth::hci::CommandPacketView)>>
active_hci_commands_;
bluetooth::hci::LoopbackMode loopback_mode_;
diff --git a/vendor_libs/test_vendor_lib/model/controller/isochronous_connection_handler.cc b/vendor_libs/test_vendor_lib/model/controller/isochronous_connection_handler.cc
deleted file mode 100644
index ed43da261..000000000
--- a/vendor_libs/test_vendor_lib/model/controller/isochronous_connection_handler.cc
+++ /dev/null
@@ -1,101 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "model/controller/isochronous_connection_handler.h"
-
-#include "os/log.h"
-
-#include "hci/address.h"
-
-using std::shared_ptr;
-
-namespace test_vendor_lib {
-
-using bluetooth::hci::ErrorCode;
-
-std::unique_ptr<bluetooth::hci::LeSetCigParametersCompleteBuilder>
-IsochronousConnectionHandler::SetCigParameters(
- GroupParameters group_parameters, std::vector<StreamParameters>& streams,
- std::vector<uint16_t> handles) {
- if (groups_.count(group_parameters.id) != 0) {
- if (groups_.at(group_parameters.id).HasStreams()) {
- return bluetooth::hci::LeSetCigParametersCompleteBuilder::Create(
- 1, ErrorCode::COMMAND_DISALLOWED, group_parameters.id, {});
- }
- groups_.erase(group_parameters.id);
- }
-
- // TODO: Limit groups and return ErrorCode::MEMORY_CAPACITY_EXCEEDED
- // TODO: Limit connections return ErrorCode::CONNECTION_LIMIT_EXCEEDED
-
- std::vector<ConnectedIsochronousStream> created_streams;
- for (size_t i = 0; i < streams.size(); i++) {
- streams[i].handle = handles[i];
- streams[i].group_id = group_parameters.id;
- created_streams.emplace_back(streams[i]);
- cis_to_group_.emplace(handles[i], group_parameters.id);
- }
-
- groups_.emplace(std::piecewise_construct,
- std::forward_as_tuple(group_parameters.id),
- std::forward_as_tuple(group_parameters, created_streams));
-
- return bluetooth::hci::LeSetCigParametersCompleteBuilder::Create(
- 1, ErrorCode::SUCCESS, group_parameters.id, handles);
-}
-
-bluetooth::hci::ErrorCode IsochronousConnectionHandler::RemoveCig(
- uint8_t cig_id) {
- if (groups_.count(cig_id) != 0) {
- return ErrorCode::UNKNOWN_CONNECTION;
- }
- if (groups_.at(cig_id).HasConnectedStream()) {
- return ErrorCode::COMMAND_DISALLOWED;
- }
- groups_.erase(cig_id);
- auto copy = cis_to_group_;
- cis_to_group_.clear();
- for (auto pair : cis_to_group_) {
- if (pair.second != cig_id) {
- cis_to_group_.emplace(pair.first, pair.second);
- }
- }
- return ErrorCode::SUCCESS;
-}
-
-bool IsochronousConnectionHandler::HasHandle(uint16_t handle) const {
- return cis_to_group_.count(handle) != 0;
-}
-
-uint8_t IsochronousConnectionHandler::GetGroupId(uint16_t handle) const {
- return cis_to_group_.at(handle);
-}
-
-StreamParameters IsochronousConnectionHandler::GetStreamParameters(
- uint16_t handle) const {
- return groups_.at(cis_to_group_.at(handle)).GetStreamParameters(handle);
-}
-
-GroupParameters IsochronousConnectionHandler::GetGroupParameters(
- uint8_t id) const {
- return groups_.at(id).GetParameters();
-}
-
-bool IsochronousConnectionHandler::GetStreamIsConnected(uint16_t handle) const {
- return groups_.at(cis_to_group_.at(handle)).StreamIsConnected(handle);
-}
-
-} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/controller/isochronous_connection_handler.h b/vendor_libs/test_vendor_lib/model/controller/isochronous_connection_handler.h
deleted file mode 100644
index b0e6750c9..000000000
--- a/vendor_libs/test_vendor_lib/model/controller/isochronous_connection_handler.h
+++ /dev/null
@@ -1,57 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <cstdint>
-#include <map>
-#include <set>
-
-#include "hci/hci_packets.h"
-#include "model/controller/connected_isochronous_group.h"
-#include "model/controller/connected_isochronous_stream.h"
-
-namespace test_vendor_lib {
-
-class IsochronousConnectionHandler {
- public:
- IsochronousConnectionHandler() = default;
- virtual ~IsochronousConnectionHandler() = default;
-
- std::unique_ptr<bluetooth::hci::LeSetCigParametersCompleteBuilder>
- SetCigParameters(GroupParameters parameters,
- std::vector<StreamParameters>& streams,
- std::vector<uint16_t> handles);
-
- bluetooth::hci::ErrorCode RemoveCig(uint8_t cig_id);
-
- bool HasHandle(uint16_t handle) const;
-
- uint8_t GetGroupId(uint16_t) const;
-
- StreamParameters GetStreamParameters(uint16_t handle) const;
- GroupParameters GetGroupParameters(uint8_t id) const;
-
- bool GetStreamIsConnected(uint16_t handle) const;
-
- std::vector<uint16_t> GetCigHandles(uint8_t id) const;
-
- private:
- std::map<uint8_t, ConnectedIsochronousGroup> groups_;
- std::map<uint16_t, uint8_t> cis_to_group_;
-};
-
-} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/controller/le_advertiser.cc b/vendor_libs/test_vendor_lib/model/controller/le_advertiser.cc
deleted file mode 100644
index 09a950378..000000000
--- a/vendor_libs/test_vendor_lib/model/controller/le_advertiser.cc
+++ /dev/null
@@ -1,147 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "le_advertiser.h"
-
-using namespace bluetooth::hci;
-
-namespace test_vendor_lib {
-void LeAdvertiser::Initialize(AddressWithType address,
- AddressWithType peer_address,
- LeScanningFilterPolicy filter_policy,
- model::packets::AdvertisementType type,
- const std::vector<uint8_t>& advertisement,
- const std::vector<uint8_t>& scan_response,
- std::chrono::steady_clock::duration interval) {
- address_ = address;
- peer_address_ = peer_address;
- filter_policy_ = filter_policy;
- type_ = type;
- advertisement_ = advertisement;
- scan_response_ = scan_response;
- interval_ = interval;
-}
-
-void LeAdvertiser::InitializeExtended(
- AddressType address_type, AddressWithType peer_address,
- LeScanningFilterPolicy filter_policy,
- model::packets::AdvertisementType type,
- std::chrono::steady_clock::duration interval) {
- address_ = AddressWithType(address_.GetAddress(), address_type);
- peer_address_ = peer_address;
- filter_policy_ = filter_policy;
- type_ = type;
- interval_ = interval;
- LOG_INFO("%s -> %s type = %hhx interval = %d ms", address_.ToString().c_str(),
- peer_address.ToString().c_str(), type_,
- static_cast<int>(interval_.count()));
-}
-
-void LeAdvertiser::Clear() {
- address_ = AddressWithType{};
- peer_address_ = AddressWithType{};
- filter_policy_ = LeScanningFilterPolicy::ACCEPT_ALL;
- type_ = model::packets::AdvertisementType::ADV_IND;
- advertisement_.clear();
- scan_response_.clear();
- interval_ = std::chrono::milliseconds(0);
- enabled_ = false;
-}
-
-void LeAdvertiser::SetAddress(Address address) {
- LOG_INFO("set address %s", address_.ToString().c_str());
- address_ = AddressWithType(address, address_.GetAddressType());
-}
-
-AddressWithType LeAdvertiser::GetAddress() const { return address_; }
-
-void LeAdvertiser::SetData(const std::vector<uint8_t>& data) {
- advertisement_ = data;
-}
-
-void LeAdvertiser::Enable() {
- enabled_ = true;
- last_le_advertisement_ = std::chrono::steady_clock::now() - interval_;
- LOG_INFO("%s -> %s type = %hhx ad length %zu, scan length %zu",
- address_.ToString().c_str(), peer_address_.ToString().c_str(), type_,
- advertisement_.size(), scan_response_.size());
-}
-
-void LeAdvertiser::EnableExtended(
- std::chrono::steady_clock::duration duration) {
- last_le_advertisement_ = std::chrono::steady_clock::now();
- if (duration != std::chrono::milliseconds(0)) {
- ending_time_ = std::chrono::steady_clock::now() + duration;
- }
- enabled_ = true;
- LOG_INFO("%s -> %s type = %hhx ad length %zu, scan length %zu",
- address_.ToString().c_str(), peer_address_.ToString().c_str(), type_,
- advertisement_.size(), scan_response_.size());
-}
-
-void LeAdvertiser::Disable() { enabled_ = false; }
-
-bool LeAdvertiser::IsEnabled() const { return enabled_; }
-
-std::unique_ptr<model::packets::LeAdvertisementBuilder>
-LeAdvertiser::GetAdvertisement(std::chrono::steady_clock::time_point now) {
- if (!enabled_) {
- return nullptr;
- }
-
- if (now - last_le_advertisement_ < interval_) {
- return nullptr;
- }
-
- if (last_le_advertisement_ < ending_time_ && ending_time_ < now) {
- enabled_ = false;
- return nullptr;
- }
-
- last_le_advertisement_ = now;
- return model::packets::LeAdvertisementBuilder::Create(
- address_.GetAddress(), peer_address_.GetAddress(),
- static_cast<model::packets::AddressType>(address_.GetAddressType()),
- type_, advertisement_);
-}
-
-std::unique_ptr<model::packets::LeScanResponseBuilder>
-LeAdvertiser::GetScanResponse(bluetooth::hci::Address scanned,
- bluetooth::hci::Address scanner) {
- if (scanned != address_.GetAddress() || !enabled_ || scan_response_.empty()) {
- return nullptr;
- }
- switch (filter_policy_) {
- case bluetooth::hci::LeScanningFilterPolicy::
- CONNECT_LIST_AND_INITIATORS_IDENTITY:
- case bluetooth::hci::LeScanningFilterPolicy::CONNECT_LIST_ONLY:
- LOG_WARN("ScanResponses don't handle connect list filters");
- return nullptr;
- case bluetooth::hci::LeScanningFilterPolicy::CHECK_INITIATORS_IDENTITY:
- if (scanner != peer_address_.GetAddress()) {
- return nullptr;
- }
- break;
- case bluetooth::hci::LeScanningFilterPolicy::ACCEPT_ALL:
- break;
- }
- return model::packets::LeScanResponseBuilder::Create(
- address_.GetAddress(), peer_address_.GetAddress(),
- static_cast<model::packets::AddressType>(address_.GetAddressType()),
- model::packets::AdvertisementType::SCAN_RESPONSE, scan_response_);
-}
-
-} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/controller/le_advertiser.h b/vendor_libs/test_vendor_lib/model/controller/le_advertiser.h
deleted file mode 100644
index 264f15e0e..000000000
--- a/vendor_libs/test_vendor_lib/model/controller/le_advertiser.h
+++ /dev/null
@@ -1,86 +0,0 @@
-/*
- * Copyright 2020 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#pragma once
-
-#include <chrono>
-#include <cstdint>
-#include <memory>
-
-#include "hci/address_with_type.h"
-#include "hci/hci_packets.h"
-#include "packets/link_layer_packets.h"
-
-namespace test_vendor_lib {
-
-// Track a single advertising instance
-class LeAdvertiser {
- public:
- LeAdvertiser() = default;
- virtual ~LeAdvertiser() = default;
-
- void Initialize(bluetooth::hci::AddressWithType address,
- bluetooth::hci::AddressWithType peer_address,
- bluetooth::hci::LeScanningFilterPolicy filter_policy,
- model::packets::AdvertisementType type,
- const std::vector<uint8_t>& advertisement,
- const std::vector<uint8_t>& scan_response,
- std::chrono::steady_clock::duration interval);
-
- void InitializeExtended(bluetooth::hci::AddressType address_type,
- bluetooth::hci::AddressWithType peer_address,
- bluetooth::hci::LeScanningFilterPolicy filter_policy,
- model::packets::AdvertisementType type,
- std::chrono::steady_clock::duration interval);
-
- void SetAddress(bluetooth::hci::Address address);
-
- void SetData(const std::vector<uint8_t>& data);
-
- std::unique_ptr<model::packets::LeAdvertisementBuilder> GetAdvertisement(
- std::chrono::steady_clock::time_point);
-
- std::unique_ptr<model::packets::LeScanResponseBuilder> GetScanResponse(
- bluetooth::hci::Address scanned_address,
- bluetooth::hci::Address scanner_address);
-
- void Clear();
-
- void Disable();
-
- void Enable();
-
- void EnableExtended(std::chrono::steady_clock::duration duration);
-
- bool IsEnabled() const;
-
- bluetooth::hci::AddressWithType GetAddress() const;
-
- private:
- bluetooth::hci::AddressWithType address_{};
- bluetooth::hci::AddressWithType
- peer_address_{}; // For directed advertisements
- bluetooth::hci::LeScanningFilterPolicy filter_policy_{};
- model::packets::AdvertisementType type_{};
- std::vector<uint8_t> advertisement_;
- std::vector<uint8_t> scan_response_;
- std::chrono::steady_clock::duration interval_{};
- std::chrono::steady_clock::time_point ending_time_{};
- bool enabled_{false};
- std::chrono::steady_clock::time_point last_le_advertisement_;
-};
-
-} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/controller/link_layer_controller.cc b/vendor_libs/test_vendor_lib/model/controller/link_layer_controller.cc
index 7ccc8f238..daac8a1c0 100644
--- a/vendor_libs/test_vendor_lib/model/controller/link_layer_controller.cc
+++ b/vendor_libs/test_vendor_lib/model/controller/link_layer_controller.cc
@@ -15,7 +15,6 @@
*/
#include "link_layer_controller.h"
-#include <hci/hci_packets.h>
#include "include/le_advertisement.h"
#include "os/log.h"
@@ -23,12 +22,6 @@
using std::vector;
using namespace std::chrono;
-using bluetooth::hci::Address;
-using bluetooth::hci::AddressType;
-using bluetooth::hci::AddressWithType;
-
-using namespace model::packets;
-using model::packets::PacketType;
namespace test_vendor_lib {
@@ -49,7 +42,7 @@ void LinkLayerController::SendLeLinkLayerPacket(
std::shared_ptr<model::packets::LinkLayerPacketBuilder> shared_packet =
std::move(packet);
ScheduleTask(milliseconds(50), [this, shared_packet]() {
- send_to_remote_(shared_packet, Phy::Type::LOW_ENERGY);
+ send_to_remote_(std::move(shared_packet), Phy::Type::LOW_ENERGY);
});
}
@@ -58,27 +51,10 @@ void LinkLayerController::SendLinkLayerPacket(
std::shared_ptr<model::packets::LinkLayerPacketBuilder> shared_packet =
std::move(packet);
ScheduleTask(milliseconds(50), [this, shared_packet]() {
- send_to_remote_(shared_packet, Phy::Type::BR_EDR);
+ send_to_remote_(std::move(shared_packet), Phy::Type::BR_EDR);
});
}
-ErrorCode LinkLayerController::SendLeCommandToRemoteByAddress(
- OpCode opcode, bluetooth::packet::PacketView<true> args,
- const Address& remote, const Address& local) {
- switch (opcode) {
- case (OpCode::LE_READ_REMOTE_FEATURES):
- SendLinkLayerPacket(
- model::packets::LeReadRemoteFeaturesBuilder::Create(local, remote));
- break;
- default:
- LOG_INFO("Dropping unhandled command 0x%04x",
- static_cast<uint16_t>(opcode));
- return ErrorCode::UNKNOWN_HCI_COMMAND;
- }
-
- return ErrorCode::SUCCESS;
-}
-
ErrorCode LinkLayerController::SendCommandToRemoteByAddress(
OpCode opcode, bluetooth::packet::PacketView<true> args,
const Address& remote) {
@@ -124,23 +100,16 @@ ErrorCode LinkLayerController::SendCommandToRemoteByAddress(
ErrorCode LinkLayerController::SendCommandToRemoteByHandle(
OpCode opcode, bluetooth::packet::PacketView<true> args, uint16_t handle) {
+ // TODO: Handle LE connections
if (!connections_.HasHandle(handle)) {
return ErrorCode::UNKNOWN_CONNECTION;
}
-
- switch (opcode) {
- case (OpCode::LE_READ_REMOTE_FEATURES):
- return SendLeCommandToRemoteByAddress(
- opcode, args, connections_.GetAddress(handle).GetAddress(),
- connections_.GetOwnAddress(handle).GetAddress());
- default:
- return SendCommandToRemoteByAddress(
- opcode, args, connections_.GetAddress(handle).GetAddress());
- }
+ return SendCommandToRemoteByAddress(
+ opcode, args, connections_.GetAddress(handle).GetAddress());
}
ErrorCode LinkLayerController::SendAclToRemote(
- bluetooth::hci::AclView acl_packet) {
+ bluetooth::hci::AclPacketView acl_packet) {
uint16_t handle = acl_packet.GetHandle();
if (!connections_.HasHandle(handle)) {
return ErrorCode::UNKNOWN_CONNECTION;
@@ -150,7 +119,11 @@ ErrorCode LinkLayerController::SendAclToRemote(
AddressWithType destination = connections_.GetAddress(handle);
Phy::Type phy = connections_.GetPhyType(handle);
- ScheduleTask(milliseconds(1), [this, handle]() {
+ LOG_INFO("%s(%s): handle 0x%x size %d", __func__,
+ properties_.GetAddress().ToString().c_str(), handle,
+ static_cast<int>(acl_packet.size()));
+
+ ScheduleTask(milliseconds(5), [this, handle]() {
std::vector<bluetooth::hci::CompletedPackets> completed_packets;
bluetooth::hci::CompletedPackets cp;
cp.connection_handle_ = handle;
@@ -175,9 +148,9 @@ ErrorCode LinkLayerController::SendAclToRemote(
raw_builder_ptr->AddOctets2(static_cast<uint16_t>(payload_bytes.size()));
raw_builder_ptr->AddOctets(payload_bytes);
- auto acl = model::packets::AclBuilder::Create(my_address.GetAddress(),
- destination.GetAddress(),
- std::move(raw_builder_ptr));
+ auto acl = model::packets::AclPacketBuilder::Create(
+ my_address.GetAddress(), destination.GetAddress(),
+ std::move(raw_builder_ptr));
switch (phy) {
case Phy::Type::BR_EDR:
@@ -193,33 +166,12 @@ ErrorCode LinkLayerController::SendAclToRemote(
void LinkLayerController::IncomingPacket(
model::packets::LinkLayerPacketView incoming) {
ASSERT(incoming.IsValid());
- auto destination_address = incoming.GetDestinationAddress();
-
- // Match broadcasts
- bool address_matches = (destination_address == Address::kEmpty);
-
- // Match addresses from device properties
- if (destination_address == properties_.GetAddress() ||
- destination_address == properties_.GetLeAddress()) {
- address_matches = true;
- }
-
- // Check advertising addresses
- for (const auto& advertiser : advertisers_) {
- if (advertiser.IsEnabled() &&
- advertiser.GetAddress().GetAddress() == destination_address) {
- address_matches = true;
- }
- }
- // Check connection addresses
- if (connections_.GetHandleOnlyAddress(destination_address) !=
- kReservedHandle) {
- address_matches = true;
- }
-
- // Drop packets not addressed to me
- if (!address_matches) {
+ // TODO: Resolvable private addresses?
+ if (incoming.GetDestinationAddress() != properties_.GetAddress() &&
+ incoming.GetDestinationAddress() != properties_.GetLeAddress() &&
+ incoming.GetDestinationAddress() != Address::kEmpty) {
+ // Drop packets not addressed to me
return;
}
@@ -253,18 +205,6 @@ void LinkLayerController::IncomingPacket(
case model::packets::PacketType::IO_CAPABILITY_NEGATIVE_RESPONSE:
IncomingIoCapabilityNegativeResponsePacket(incoming);
break;
- case PacketType::ISO:
- IncomingIsoPacket(incoming);
- break;
- case PacketType::ISO_CONNECTION_REQUEST:
- IncomingIsoConnectionRequestPacket(incoming);
- break;
- case PacketType::ISO_CONNECTION_RESPONSE:
- IncomingIsoConnectionResponsePacket(incoming);
- break;
- case PacketType::KEYPRESS_NOTIFICATION:
- IncomingKeypressNotificationPacket(incoming);
- break;
case model::packets::PacketType::LE_ADVERTISEMENT:
if (le_scan_enable_ != bluetooth::hci::OpCode::NONE || le_connect_) {
IncomingLeAdvertisementPacket(incoming);
@@ -276,18 +216,6 @@ void LinkLayerController::IncomingPacket(
case model::packets::PacketType::LE_CONNECT_COMPLETE:
IncomingLeConnectCompletePacket(incoming);
break;
- case model::packets::PacketType::LE_ENCRYPT_CONNECTION:
- IncomingLeEncryptConnection(incoming);
- break;
- case model::packets::PacketType::LE_ENCRYPT_CONNECTION_RESPONSE:
- IncomingLeEncryptConnectionResponse(incoming);
- break;
- case (model::packets::PacketType::LE_READ_REMOTE_FEATURES):
- IncomingLeReadRemoteFeatures(incoming);
- break;
- case (model::packets::PacketType::LE_READ_REMOTE_FEATURES_RESPONSE):
- IncomingLeReadRemoteFeaturesResponse(incoming);
- break;
case model::packets::PacketType::LE_SCAN:
// TODO: Check Advertising flags and see if we are scannable.
IncomingLeScanPacket(incoming);
@@ -309,18 +237,6 @@ void LinkLayerController::IncomingPacket(
case model::packets::PacketType::PAGE_REJECT:
IncomingPageRejectPacket(incoming);
break;
- case (model::packets::PacketType::PASSKEY):
- IncomingPasskeyPacket(incoming);
- break;
- case (model::packets::PacketType::PASSKEY_FAILED):
- IncomingPasskeyFailedPacket(incoming);
- break;
- case (model::packets::PacketType::PIN_REQUEST):
- IncomingPinRequestPacket(incoming);
- break;
- case (model::packets::PacketType::PIN_RESPONSE):
- IncomingPinResponsePacket(incoming);
- break;
case (model::packets::PacketType::REMOTE_NAME_REQUEST):
IncomingRemoteNameRequest(incoming);
break;
@@ -369,7 +285,7 @@ void LinkLayerController::IncomingAclPacket(
incoming.GetSourceAddress().ToString().c_str(),
incoming.GetDestinationAddress().ToString().c_str());
- auto acl = model::packets::AclView::Create(incoming);
+ auto acl = model::packets::AclPacketView::Create(incoming);
ASSERT(acl.IsValid());
auto payload = acl.GetPayload();
std::shared_ptr<std::vector<uint8_t>> payload_bytes =
@@ -377,14 +293,14 @@ void LinkLayerController::IncomingAclPacket(
bluetooth::hci::PacketView<bluetooth::hci::kLittleEndian> raw_packet(
payload_bytes);
- auto acl_view = bluetooth::hci::AclView::Create(raw_packet);
+ auto acl_view = bluetooth::hci::AclPacketView::Create(raw_packet);
ASSERT(acl_view.IsValid());
- LOG_INFO("Remote handle 0x%x size %d", acl_view.GetHandle(),
+ LOG_INFO("%s: remote handle 0x%x size %d", __func__, acl_view.GetHandle(),
static_cast<int>(acl_view.size()));
uint16_t local_handle =
connections_.GetHandleOnlyAddress(incoming.GetSourceAddress());
- LOG_INFO("Local handle 0x%x", local_handle);
+ LOG_INFO("%s: local handle 0x%x", __func__, local_handle);
std::vector<uint8_t> payload_data(acl_view.GetPayload().begin(),
acl_view.GetPayload().end());
@@ -393,11 +309,6 @@ void LinkLayerController::IncomingAclPacket(
(payload_data.size() + acl_buffer_size - 1) / acl_buffer_size;
auto pb_flag_controller_to_host = acl_view.GetPacketBoundaryFlag();
- if (pb_flag_controller_to_host ==
- bluetooth::hci::PacketBoundaryFlag::FIRST_NON_AUTOMATICALLY_FLUSHABLE) {
- pb_flag_controller_to_host =
- bluetooth::hci::PacketBoundaryFlag::FIRST_AUTOMATICALLY_FLUSHABLE;
- }
for (int i = 0; i < num_packets; i++) {
size_t start_index = acl_buffer_size * i;
size_t end_index =
@@ -406,7 +317,7 @@ void LinkLayerController::IncomingAclPacket(
&payload_data[end_index]);
std::unique_ptr<bluetooth::packet::RawBuilder> raw_builder_ptr =
std::make_unique<bluetooth::packet::RawBuilder>(fragment);
- auto acl_packet = bluetooth::hci::AclBuilder::Create(
+ auto acl_packet = bluetooth::hci::AclPacketBuilder::Create(
local_handle, pb_flag_controller_to_host, acl_view.GetBroadcastFlag(),
std::move(raw_builder_ptr));
pb_flag_controller_to_host =
@@ -467,7 +378,7 @@ void LinkLayerController::IncomingReadRemoteSupportedFeaturesResponse(
ASSERT(view.IsValid());
Address source = packet.GetSourceAddress();
uint16_t handle = connections_.GetHandleOnlyAddress(source);
- if (handle == kReservedHandle) {
+ if (handle == acl::kReservedHandle) {
LOG_INFO("Discarding response from a disconnected device %s",
source.ToString().c_str());
return;
@@ -500,7 +411,7 @@ void LinkLayerController::IncomingReadRemoteExtendedFeaturesResponse(
ASSERT(view.IsValid());
Address source = packet.GetSourceAddress();
uint16_t handle = connections_.GetHandleOnlyAddress(source);
- if (handle == kReservedHandle) {
+ if (handle == acl::kReservedHandle) {
LOG_INFO("Discarding response from a disconnected device %s",
source.ToString().c_str());
return;
@@ -513,10 +424,9 @@ void LinkLayerController::IncomingReadRemoteExtendedFeaturesResponse(
void LinkLayerController::IncomingReadRemoteVersion(
model::packets::LinkLayerPacketView packet) {
SendLinkLayerPacket(
- model::packets::ReadRemoteVersionInformationResponseBuilder::Create(
+ model::packets::ReadRemoteSupportedFeaturesResponseBuilder::Create(
packet.GetDestinationAddress(), packet.GetSourceAddress(),
- properties_.GetLmpPalVersion(), properties_.GetLmpPalSubversion(),
- properties_.GetManufacturerName()));
+ properties_.GetSupportedFeatures()));
}
void LinkLayerController::IncomingReadRemoteVersionResponse(
@@ -526,7 +436,7 @@ void LinkLayerController::IncomingReadRemoteVersionResponse(
ASSERT(view.IsValid());
Address source = packet.GetSourceAddress();
uint16_t handle = connections_.GetHandleOnlyAddress(source);
- if (handle == kReservedHandle) {
+ if (handle == acl::kReservedHandle) {
LOG_INFO("Discarding response from a disconnected device %s",
source.ToString().c_str());
return;
@@ -550,7 +460,7 @@ void LinkLayerController::IncomingReadClockOffsetResponse(
ASSERT(view.IsValid());
Address source = packet.GetSourceAddress();
uint16_t handle = connections_.GetHandleOnlyAddress(source);
- if (handle == kReservedHandle) {
+ if (handle == acl::kReservedHandle) {
LOG_INFO("Discarding response from a disconnected device %s",
source.ToString().c_str());
return;
@@ -567,7 +477,7 @@ void LinkLayerController::IncomingDisconnectPacket(
Address peer = incoming.GetSourceAddress();
uint16_t handle = connections_.GetHandleOnlyAddress(peer);
- if (handle == kReservedHandle) {
+ if (handle == acl::kReservedHandle) {
LOG_INFO("Discarding disconnect from a disconnected device %s",
peer.ToString().c_str());
return;
@@ -582,13 +492,13 @@ void LinkLayerController::IncomingDisconnectPacket(
void LinkLayerController::IncomingEncryptConnection(
model::packets::LinkLayerPacketView incoming) {
- LOG_INFO();
+ LOG_INFO("%s", __func__);
// TODO: Check keys
Address peer = incoming.GetSourceAddress();
uint16_t handle = connections_.GetHandleOnlyAddress(peer);
- if (handle == kReservedHandle) {
- LOG_INFO("Unknown connection @%s", peer.ToString().c_str());
+ if (handle == acl::kReservedHandle) {
+ LOG_INFO("%s: Unknown connection @%s", __func__, peer.ToString().c_str());
return;
}
send_event_(bluetooth::hci::EncryptionChangeBuilder::Create(
@@ -608,12 +518,12 @@ void LinkLayerController::IncomingEncryptConnection(
void LinkLayerController::IncomingEncryptConnectionResponse(
model::packets::LinkLayerPacketView incoming) {
- LOG_INFO();
+ LOG_INFO("%s", __func__);
// TODO: Check keys
uint16_t handle =
connections_.GetHandleOnlyAddress(incoming.GetSourceAddress());
- if (handle == kReservedHandle) {
- LOG_INFO("Unknown connection @%s",
+ if (handle == acl::kReservedHandle) {
+ LOG_INFO("%s: Unknown connection @%s", __func__,
incoming.GetSourceAddress().ToString().c_str());
return;
}
@@ -734,7 +644,7 @@ void LinkLayerController::IncomingInquiryResponsePacket(
raw_builder_ptr->AddOctets1(inquiry_response.GetRssi());
raw_builder_ptr->AddOctets(inquiry_response.GetExtendedData());
- auto packet = bluetooth::hci::EventBuilder::Create(
+ auto packet = bluetooth::hci::EventPacketBuilder::Create(
bluetooth::hci::EventCode::EXTENDED_INQUIRY_RESULT,
std::move(raw_builder_ptr));
send_event_(std::move(packet));
@@ -747,37 +657,32 @@ void LinkLayerController::IncomingInquiryResponsePacket(
void LinkLayerController::IncomingIoCapabilityRequestPacket(
model::packets::LinkLayerPacketView incoming) {
- Address peer = incoming.GetSourceAddress();
- uint16_t handle = connections_.GetHandle(AddressWithType(
- peer, bluetooth::hci::AddressType::PUBLIC_DEVICE_ADDRESS));
- if (handle == kReservedHandle) {
- LOG_INFO("Device not connected %s", peer.ToString().c_str());
- return;
- }
-
- if (!properties_.GetSecureSimplePairingSupported()) {
- LOG_WARN("Trying PIN pairing for %s",
- incoming.GetDestinationAddress().ToString().c_str());
- SendLinkLayerPacket(
- model::packets::IoCapabilityNegativeResponseBuilder::Create(
- incoming.GetDestinationAddress(), incoming.GetSourceAddress(),
- static_cast<uint8_t>(
- ErrorCode::UNSUPPORTED_REMOTE_OR_LMP_FEATURE)));
- security_manager_.AuthenticationRequest(incoming.GetSourceAddress(),
- handle);
- security_manager_.SetPinRequested(peer);
- send_event_(bluetooth::hci::PinCodeRequestBuilder::Create(
- incoming.GetSourceAddress()));
+ LOG_DEBUG("%s", __func__);
+ if (!simple_pairing_mode_enabled_) {
+ LOG_WARN("%s: Only simple pairing mode is implemented", __func__);
return;
}
auto request = model::packets::IoCapabilityRequestView::Create(incoming);
ASSERT(request.IsValid());
+ Address peer = incoming.GetSourceAddress();
uint8_t io_capability = request.GetIoCapability();
uint8_t oob_data_present = request.GetOobDataPresent();
uint8_t authentication_requirements = request.GetAuthenticationRequirements();
+ uint16_t handle = connections_.GetHandle(AddressWithType(
+ peer, bluetooth::hci::AddressType::PUBLIC_DEVICE_ADDRESS));
+ if (handle == acl::kReservedHandle) {
+ LOG_INFO("%s: Device not connected %s", __func__, peer.ToString().c_str());
+ return;
+ }
+
+ security_manager_.AuthenticationRequest(peer, handle);
+
+ security_manager_.SetPeerIoCapability(peer, io_capability, oob_data_present,
+ authentication_requirements);
+
auto packet = bluetooth::hci::IoCapabilityResponseBuilder::Create(
peer, static_cast<bluetooth::hci::IoCapability>(io_capability),
static_cast<bluetooth::hci::OobDataPresent>(oob_data_present),
@@ -785,39 +690,15 @@ void LinkLayerController::IncomingIoCapabilityRequestPacket(
authentication_requirements));
send_event_(std::move(packet));
- bool pairing_started = security_manager_.AuthenticationInProgress();
- if (!pairing_started) {
- security_manager_.AuthenticationRequest(peer, handle);
- StartSimplePairing(peer);
- }
-
- security_manager_.SetPeerIoCapability(peer, io_capability, oob_data_present,
- authentication_requirements);
- if (pairing_started) {
- PairingType pairing_type = security_manager_.GetSimplePairingType();
- if (pairing_type != PairingType::INVALID) {
- ScheduleTask(milliseconds(5), [this, peer, pairing_type]() {
- AuthenticateRemoteStage1(peer, pairing_type);
- });
- } else {
- LOG_INFO("Security Manager returned INVALID");
- }
- }
+ StartSimplePairing(peer);
}
void LinkLayerController::IncomingIoCapabilityResponsePacket(
model::packets::LinkLayerPacketView incoming) {
+ LOG_DEBUG("%s", __func__);
+
auto response = model::packets::IoCapabilityResponseView::Create(incoming);
ASSERT(response.IsValid());
- if (!properties_.GetSecureSimplePairingSupported()) {
- LOG_WARN("Only simple pairing mode is implemented");
- SendLinkLayerPacket(
- model::packets::IoCapabilityNegativeResponseBuilder::Create(
- incoming.GetDestinationAddress(), incoming.GetSourceAddress(),
- static_cast<uint8_t>(
- ErrorCode::UNSUPPORTED_REMOTE_OR_LMP_FEATURE)));
- return;
- }
Address peer = incoming.GetSourceAddress();
uint8_t io_capability = response.GetIoCapability();
@@ -841,250 +722,18 @@ void LinkLayerController::IncomingIoCapabilityResponsePacket(
AuthenticateRemoteStage1(peer, pairing_type);
});
} else {
- LOG_INFO("Security Manager returned INVALID");
+ LOG_INFO("%s: Security Manager returned INVALID", __func__);
}
}
void LinkLayerController::IncomingIoCapabilityNegativeResponsePacket(
model::packets::LinkLayerPacketView incoming) {
+ LOG_DEBUG("%s", __func__);
Address peer = incoming.GetSourceAddress();
ASSERT(security_manager_.GetAuthenticationAddress() == peer);
security_manager_.InvalidateIoCapabilities();
- LOG_INFO("%s doesn't support SSP, try PIN",
- incoming.GetSourceAddress().ToString().c_str());
- security_manager_.SetPinRequested(peer);
- send_event_(bluetooth::hci::PinCodeRequestBuilder::Create(
- incoming.GetSourceAddress()));
-}
-
-void LinkLayerController::IncomingIsoPacket(LinkLayerPacketView incoming) {
- auto iso = IsoDataPacketView::Create(incoming);
- ASSERT(iso.IsValid());
-
- uint16_t cis_handle = iso.GetHandle();
- if (!connections_.HasCisHandle(cis_handle)) {
- LOG_INFO("Dropping ISO packet to unknown handle 0x%hx", cis_handle);
- return;
- }
- if (!connections_.HasConnectedCis(cis_handle)) {
- LOG_INFO("Dropping ISO packet to a disconnected handle 0x%hx", cis_handle);
- return;
- }
-
- auto sc = iso.GetSc();
- switch (sc) {
- case StartContinuation::START: {
- auto iso_start = IsoStartView::Create(iso);
- ASSERT(iso_start.IsValid());
- if (iso.GetCmplt() == Complete::COMPLETE) {
- send_iso_(bluetooth::hci::IsoWithoutTimestampBuilder::Create(
- cis_handle, bluetooth::hci::IsoPacketBoundaryFlag::COMPLETE_SDU,
- 0 /* seq num */, bluetooth::hci::IsoPacketStatusFlag::VALID,
- std::make_unique<bluetooth::packet::RawBuilder>(
- std::vector<uint8_t>(iso_start.GetPayload().begin(),
- iso_start.GetPayload().end()))));
- } else {
- send_iso_(bluetooth::hci::IsoWithoutTimestampBuilder::Create(
- cis_handle, bluetooth::hci::IsoPacketBoundaryFlag::FIRST_FRAGMENT,
- 0 /* seq num */, bluetooth::hci::IsoPacketStatusFlag::VALID,
- std::make_unique<bluetooth::packet::RawBuilder>(
- std::vector<uint8_t>(iso_start.GetPayload().begin(),
- iso_start.GetPayload().end()))));
- }
- } break;
- case StartContinuation::CONTINUATION: {
- auto continuation = IsoContinuationView::Create(iso);
- ASSERT(continuation.IsValid());
- if (iso.GetCmplt() == Complete::COMPLETE) {
- send_iso_(bluetooth::hci::IsoWithoutTimestampBuilder::Create(
- cis_handle, bluetooth::hci::IsoPacketBoundaryFlag::LAST_FRAGMENT,
- 0 /* seq num */, bluetooth::hci::IsoPacketStatusFlag::VALID,
- std::make_unique<bluetooth::packet::RawBuilder>(
- std::vector<uint8_t>(continuation.GetPayload().begin(),
- continuation.GetPayload().end()))));
- } else {
- send_iso_(bluetooth::hci::IsoWithoutTimestampBuilder::Create(
- cis_handle,
- bluetooth::hci::IsoPacketBoundaryFlag::CONTINUATION_FRAGMENT,
- 0 /* seq num */, bluetooth::hci::IsoPacketStatusFlag::VALID,
- std::make_unique<bluetooth::packet::RawBuilder>(
- std::vector<uint8_t>(continuation.GetPayload().begin(),
- continuation.GetPayload().end()))));
- }
- } break;
- }
-}
-
-void LinkLayerController::HandleIso(bluetooth::hci::IsoView iso) {
- auto cis_handle = iso.GetConnectionHandle();
- if (!connections_.HasCisHandle(cis_handle)) {
- LOG_INFO("Dropping ISO packet to unknown handle 0x%hx", cis_handle);
- return;
- }
- if (!connections_.HasConnectedCis(cis_handle)) {
- LOG_INFO("Dropping ISO packet to disconnected handle 0x%hx", cis_handle);
- return;
- }
-
- auto acl_handle = connections_.GetAclHandleForCisHandle(cis_handle);
- uint16_t remote_handle =
- connections_.GetRemoteCisHandleForCisHandle(cis_handle);
- model::packets::StartContinuation start_flag =
- model::packets::StartContinuation::START;
- model::packets::Complete complete_flag = model::packets::Complete::COMPLETE;
- switch (iso.GetPbFlag()) {
- case bluetooth::hci::IsoPacketBoundaryFlag::COMPLETE_SDU:
- start_flag = model::packets::StartContinuation::START;
- complete_flag = model::packets::Complete::COMPLETE;
- break;
- case bluetooth::hci::IsoPacketBoundaryFlag::CONTINUATION_FRAGMENT:
- start_flag = model::packets::StartContinuation::CONTINUATION;
- complete_flag = model::packets::Complete::INCOMPLETE;
- break;
- case bluetooth::hci::IsoPacketBoundaryFlag::FIRST_FRAGMENT:
- start_flag = model::packets::StartContinuation::START;
- complete_flag = model::packets::Complete::INCOMPLETE;
- break;
- case bluetooth::hci::IsoPacketBoundaryFlag::LAST_FRAGMENT:
- start_flag = model::packets::StartContinuation::CONTINUATION;
- complete_flag = model::packets::Complete::INCOMPLETE;
- break;
- }
- if (start_flag == model::packets::StartContinuation::START) {
- if (iso.GetTsFlag() == bluetooth::hci::TimeStampFlag::PRESENT) {
- auto timestamped = bluetooth::hci::IsoWithTimestampView::Create(iso);
- ASSERT(timestamped.IsValid());
- uint32_t timestamp = timestamped.GetTimeStamp();
- std::unique_ptr<bluetooth::packet::RawBuilder> payload =
- std::make_unique<bluetooth::packet::RawBuilder>();
- for (const auto it : timestamped.GetPayload()) {
- payload->AddOctets1(it);
- }
-
- SendLeLinkLayerPacket(model::packets::IsoStartBuilder::Create(
- connections_.GetOwnAddress(acl_handle).GetAddress(),
- connections_.GetAddress(acl_handle).GetAddress(), remote_handle,
- complete_flag, timestamp, std::move(payload)));
- } else {
- auto pkt = bluetooth::hci::IsoWithoutTimestampView::Create(iso);
- ASSERT(pkt.IsValid());
-
- auto payload =
- std::make_unique<bluetooth::packet::RawBuilder>(std::vector<uint8_t>(
- pkt.GetPayload().begin(), pkt.GetPayload().end()));
-
- SendLeLinkLayerPacket(model::packets::IsoStartBuilder::Create(
- connections_.GetOwnAddress(acl_handle).GetAddress(),
- connections_.GetAddress(acl_handle).GetAddress(), remote_handle,
- complete_flag, 0, std::move(payload)));
- }
- } else {
- auto pkt = bluetooth::hci::IsoWithoutTimestampView::Create(iso);
- ASSERT(pkt.IsValid());
- std::unique_ptr<bluetooth::packet::RawBuilder> payload =
- std::make_unique<bluetooth::packet::RawBuilder>(std::vector<uint8_t>(
- pkt.GetPayload().begin(), pkt.GetPayload().end()));
- SendLeLinkLayerPacket(model::packets::IsoContinuationBuilder::Create(
- connections_.GetOwnAddress(acl_handle).GetAddress(),
- connections_.GetAddress(acl_handle).GetAddress(), remote_handle,
- complete_flag, std::move(payload)));
- }
-}
-
-void LinkLayerController::IncomingIsoConnectionRequestPacket(
- LinkLayerPacketView incoming) {
- auto req = IsoConnectionRequestView::Create(incoming);
- ASSERT(req.IsValid());
- std::vector<bluetooth::hci::CisParametersConfig> stream_configs;
- bluetooth::hci::CisParametersConfig stream_config;
-
- stream_config.max_sdu_m_to_s_ = req.GetMaxSduMToS();
- stream_config.max_sdu_s_to_m_ = req.GetMaxSduSToM();
-
- stream_configs.push_back(stream_config);
-
- uint8_t group_id = req.GetCigId();
-
- /* CIG should be created by the local host before use */
- bluetooth::hci::CreateCisConfig config;
- config.cis_connection_handle_ = req.GetRequesterCisHandle();
-
- config.acl_connection_handle_ =
- connections_.GetHandleOnlyAddress(incoming.GetSourceAddress());
- connections_.CreatePendingCis(config);
- connections_.SetRemoteCisHandle(config.cis_connection_handle_,
- req.GetRequesterCisHandle());
- send_event_(bluetooth::hci::LeCisRequestBuilder::Create(
- config.acl_connection_handle_, config.cis_connection_handle_, group_id,
- req.GetId()));
-}
-
-void LinkLayerController::IncomingIsoConnectionResponsePacket(
- LinkLayerPacketView incoming) {
- auto response = IsoConnectionResponseView::Create(incoming);
- ASSERT(response.IsValid());
-
- bluetooth::hci::CreateCisConfig config;
- config.acl_connection_handle_ = response.GetRequesterAclHandle();
- config.cis_connection_handle_ = response.GetRequesterCisHandle();
- if (!connections_.HasPendingCisConnection(config.cis_connection_handle_)) {
- LOG_INFO("Ignoring connection response with unknown CIS handle 0x%04hx",
- config.cis_connection_handle_);
- return;
- }
- ErrorCode status = static_cast<ErrorCode>(response.GetStatus());
- if (status != ErrorCode::SUCCESS) {
- send_event_(bluetooth::hci::LeCisEstablishedBuilder::Create(
- status, config.cis_connection_handle_, 0, 0, 0, 0,
- bluetooth::hci::SecondaryPhyType::NO_PACKETS,
- bluetooth::hci::SecondaryPhyType::NO_PACKETS, 0, 0, 0, 0, 0, 0, 0, 0));
- return;
- }
- connections_.SetRemoteCisHandle(config.cis_connection_handle_,
- response.GetResponderCisHandle());
- connections_.ConnectCis(config.cis_connection_handle_);
- auto stream_parameters =
- connections_.GetStreamParameters(config.cis_connection_handle_);
- auto group_parameters =
- connections_.GetGroupParameters(stream_parameters.group_id);
- // TODO: Which of these are important enough to fake?
- uint32_t cig_sync_delay = 0x100;
- uint32_t cis_sync_delay = 0x200;
- uint32_t latency_m_to_s = group_parameters.max_transport_latency_m_to_s;
- uint32_t latency_s_to_m = group_parameters.max_transport_latency_s_to_m;
- uint8_t nse = 1;
- uint8_t bn_m_to_s = 0;
- uint8_t bn_s_to_m = 0;
- uint8_t ft_m_to_s = 0;
- uint8_t ft_s_to_m = 0;
- uint8_t max_pdu_m_to_s = 0x40;
- uint8_t max_pdu_s_to_m = 0x40;
- uint16_t iso_interval = 0x100;
- send_event_(bluetooth::hci::LeCisEstablishedBuilder::Create(
- status, config.cis_connection_handle_, cig_sync_delay, cis_sync_delay,
- latency_m_to_s, latency_s_to_m,
- bluetooth::hci::SecondaryPhyType::NO_PACKETS,
- bluetooth::hci::SecondaryPhyType::NO_PACKETS, nse, bn_m_to_s, bn_s_to_m,
- ft_m_to_s, ft_s_to_m, max_pdu_m_to_s, max_pdu_s_to_m, iso_interval));
-}
-
-void LinkLayerController::IncomingKeypressNotificationPacket(
- model::packets::LinkLayerPacketView incoming) {
- auto keypress = model::packets::KeypressNotificationView::Create(incoming);
- ASSERT(keypress.IsValid());
- auto notification_type = keypress.GetNotificationType();
- if (notification_type >
- model::packets::PasskeyNotificationType::ENTRY_COMPLETED) {
- LOG_WARN("Dropping unknown notification type %d",
- static_cast<int>(notification_type));
- return;
- }
- send_event_(bluetooth::hci::KeypressNotificationBuilder::Create(
- incoming.GetSourceAddress(),
- static_cast<bluetooth::hci::KeypressNotificationType>(
- notification_type)));
}
void LinkLayerController::IncomingLeAdvertisementPacket(
@@ -1094,8 +743,9 @@ void LinkLayerController::IncomingLeAdvertisementPacket(
Address address = incoming.GetSourceAddress();
auto advertisement = model::packets::LeAdvertisementView::Create(incoming);
ASSERT(advertisement.IsValid());
+ auto adv_type = static_cast<LeAdvertisement::AdvertisementType>(
+ advertisement.GetAdvertisementType());
auto address_type = advertisement.GetAddressType();
- auto adv_type = advertisement.GetAdvertisementType();
if (le_scan_enable_ == bluetooth::hci::OpCode::LE_SET_SCAN_ENABLE) {
vector<uint8_t> ad = advertisement.GetData();
@@ -1111,7 +761,7 @@ void LinkLayerController::IncomingLeAdvertisementPacket(
raw_builder_ptr->AddOctets1(ad.size());
raw_builder_ptr->AddOctets(ad);
raw_builder_ptr->AddOctets1(GetRssi());
- auto packet = bluetooth::hci::EventBuilder::Create(
+ auto packet = bluetooth::hci::EventPacketBuilder::Create(
bluetooth::hci::EventCode::LE_META_EVENT, std::move(raw_builder_ptr));
send_event_(std::move(packet));
}
@@ -1124,24 +774,7 @@ void LinkLayerController::IncomingLeAdvertisementPacket(
raw_builder_ptr->AddOctets1(static_cast<uint8_t>(
bluetooth::hci::SubeventCode::EXTENDED_ADVERTISING_REPORT));
raw_builder_ptr->AddOctets1(0x01); // num reports
- switch (adv_type) {
- case model::packets::AdvertisementType::ADV_IND:
- raw_builder_ptr->AddOctets1(0x13);
- break;
- case model::packets::AdvertisementType::ADV_DIRECT_IND:
- raw_builder_ptr->AddOctets1(0x15);
- break;
- case model::packets::AdvertisementType::ADV_SCAN_IND:
- raw_builder_ptr->AddOctets1(0x12);
- break;
- case model::packets::AdvertisementType::ADV_NONCONN_IND:
- raw_builder_ptr->AddOctets1(0x10);
- break;
- case model::packets::AdvertisementType::SCAN_RESPONSE:
- raw_builder_ptr->AddOctets1(0x1b); // 0x1a for ADV_SCAN_IND scan
- return;
- }
- raw_builder_ptr->AddOctets1(0x00); // Reserved
+ raw_builder_ptr->AddOctets1(static_cast<uint8_t>(adv_type));
raw_builder_ptr->AddOctets1(static_cast<uint8_t>(address_type));
raw_builder_ptr->AddAddress(address);
raw_builder_ptr->AddOctets1(1); // Primary_PHY
@@ -1149,13 +782,14 @@ void LinkLayerController::IncomingLeAdvertisementPacket(
raw_builder_ptr->AddOctets1(0xFF); // Advertising_SID - not provided
raw_builder_ptr->AddOctets1(0x7F); // Tx_Power - Not available
raw_builder_ptr->AddOctets1(GetRssi());
- raw_builder_ptr->AddOctets2(0); // Periodic_Advertising_Interval - None
+ raw_builder_ptr->AddOctets1(0); // Periodic_Advertising_Interval - None
raw_builder_ptr->AddOctets1(0); // Direct_Address_Type - PUBLIC
raw_builder_ptr->AddAddress(Address::kEmpty); // Direct_Address
raw_builder_ptr->AddOctets1(ad.size());
raw_builder_ptr->AddOctets(ad);
- send_event_(bluetooth::hci::EventBuilder::Create(
- bluetooth::hci::EventCode::LE_META_EVENT, std::move(raw_builder_ptr)));
+ auto packet = bluetooth::hci::EventPacketBuilder::Create(
+ bluetooth::hci::EventCode::LE_META_EVENT, std::move(raw_builder_ptr));
+ send_event_(std::move(packet));
}
// Active scanning
@@ -1168,41 +802,27 @@ void LinkLayerController::IncomingLeAdvertisementPacket(
// Connect
if ((le_connect_ && le_peer_address_ == address &&
le_peer_address_type_ == static_cast<uint8_t>(address_type) &&
- (adv_type == model::packets::AdvertisementType::ADV_IND ||
- adv_type == model::packets::AdvertisementType::ADV_DIRECT_IND)) ||
- (LeConnectListContainsDevice(address,
- static_cast<uint8_t>(address_type)))) {
+ (adv_type == LeAdvertisement::AdvertisementType::ADV_IND ||
+ adv_type == LeAdvertisement::AdvertisementType::ADV_DIRECT_IND)) ||
+ (LeWhiteListContainsDevice(address,
+ static_cast<uint8_t>(address_type)))) {
if (!connections_.CreatePendingLeConnection(AddressWithType(
address, static_cast<bluetooth::hci::AddressType>(address_type)))) {
LOG_WARN(
- "CreatePendingLeConnection failed for connection to %s (type %hhx)",
- incoming.GetSourceAddress().ToString().c_str(), address_type);
- }
- Address own_address;
- auto own_address_type =
- static_cast<bluetooth::hci::OwnAddressType>(le_address_type_);
- switch (own_address_type) {
- case bluetooth::hci::OwnAddressType::PUBLIC_DEVICE_ADDRESS:
- own_address = properties_.GetAddress();
- break;
- case bluetooth::hci::OwnAddressType::RANDOM_DEVICE_ADDRESS:
- own_address = properties_.GetLeAddress();
- break;
- default:
- LOG_ALWAYS_FATAL(
- "Unhandled connection address type %s",
- bluetooth::hci::OwnAddressTypeText(own_address_type).c_str());
+ "%s: CreatePendingLeConnection failed for connection to %s (type "
+ "%hhx)",
+ __func__, incoming.GetSourceAddress().ToString().c_str(),
+ address_type);
}
- LOG_INFO("Connecting to %s (type %hhx) own_address %s (type %hhx)",
- incoming.GetSourceAddress().ToString().c_str(), address_type,
- own_address.ToString().c_str(), le_address_type_);
+ LOG_INFO("%s: connecting to %s (type %hhx)", __func__,
+ incoming.GetSourceAddress().ToString().c_str(), address_type);
le_connect_ = false;
le_scan_enable_ = bluetooth::hci::OpCode::NONE;
auto to_send = model::packets::LeConnectBuilder::Create(
- own_address, incoming.GetSourceAddress(), le_connection_interval_min_,
- le_connection_interval_max_, le_connection_latency_,
- le_connection_supervision_timeout_,
+ properties_.GetLeAddress(), incoming.GetSourceAddress(),
+ le_connection_interval_min_, le_connection_interval_max_,
+ le_connection_latency_, le_connection_supervision_timeout_,
static_cast<uint8_t>(le_address_type_));
SendLeLinkLayerPacket(std::move(to_send));
@@ -1217,8 +837,8 @@ void LinkLayerController::HandleLeConnection(AddressWithType address,
uint16_t supervision_timeout) {
// TODO: Choose between LeConnectionComplete and LeEnhancedConnectionComplete
uint16_t handle = connections_.CreateLeConnection(address, own_address);
- if (handle == kReservedHandle) {
- LOG_WARN("No pending connection for connection from %s",
+ if (handle == acl::kReservedHandle) {
+ LOG_WARN("%s: No pending connection for connection from %s", __func__,
address.ToString().c_str());
return;
}
@@ -1226,7 +846,7 @@ void LinkLayerController::HandleLeConnection(AddressWithType address,
ErrorCode::SUCCESS, handle, static_cast<bluetooth::hci::Role>(role),
address.GetAddressType(), address.GetAddress(), connection_interval,
connection_latency, supervision_timeout,
- static_cast<bluetooth::hci::ClockAccuracy>(0x00));
+ static_cast<bluetooth::hci::MasterClockAccuracy>(0x00));
send_event_(std::move(packet));
}
@@ -1241,41 +861,28 @@ void LinkLayerController::IncomingLeConnectPacket(
incoming.GetSourceAddress(), static_cast<bluetooth::hci::AddressType>(
connect.GetAddressType())))) {
LOG_WARN(
- "CreatePendingLeConnection failed for connection from %s (type "
+ "%s: CreatePendingLeConnection failed for connection from %s (type "
"%hhx)",
- incoming.GetSourceAddress().ToString().c_str(),
+ __func__, incoming.GetSourceAddress().ToString().c_str(),
connect.GetAddressType());
return;
}
- bluetooth::hci::AddressWithType my_address{};
- bool matched_advertiser = false;
- for (auto advertiser : advertisers_) {
- AddressWithType advertiser_address = advertiser.GetAddress();
- if (incoming.GetDestinationAddress() == advertiser_address.GetAddress()) {
- my_address = advertiser_address;
- matched_advertiser = true;
- }
- }
-
- if (!matched_advertiser) {
- LOG_INFO("Dropping unmatched connection request to %s",
- incoming.GetSourceAddress().ToString().c_str());
- return;
- }
-
HandleLeConnection(
AddressWithType(
incoming.GetSourceAddress(),
static_cast<bluetooth::hci::AddressType>(connect.GetAddressType())),
- my_address, static_cast<uint8_t>(bluetooth::hci::Role::PERIPHERAL),
- connection_interval, connect.GetLeConnectionLatency(),
+ AddressWithType(incoming.GetDestinationAddress(),
+ static_cast<bluetooth::hci::AddressType>(
+ properties_.GetLeAdvertisingOwnAddressType())),
+ static_cast<uint8_t>(bluetooth::hci::Role::SLAVE), connection_interval,
+ connect.GetLeConnectionLatency(),
connect.GetLeConnectionSupervisionTimeout());
auto to_send = model::packets::LeConnectCompleteBuilder::Create(
incoming.GetDestinationAddress(), incoming.GetSourceAddress(),
connection_interval, connect.GetLeConnectionLatency(),
connect.GetLeConnectionSupervisionTimeout(),
- static_cast<uint8_t>(my_address.GetAddressType()));
+ properties_.GetLeAdvertisingOwnAddressType());
SendLeLinkLayerPacket(std::move(to_send));
}
@@ -1290,109 +897,22 @@ void LinkLayerController::IncomingLeConnectCompletePacket(
AddressWithType(
incoming.GetDestinationAddress(),
static_cast<bluetooth::hci::AddressType>(le_address_type_)),
- static_cast<uint8_t>(bluetooth::hci::Role::CENTRAL),
+ static_cast<uint8_t>(bluetooth::hci::Role::MASTER),
complete.GetLeConnectionInterval(), complete.GetLeConnectionLatency(),
complete.GetLeConnectionSupervisionTimeout());
}
-void LinkLayerController::IncomingLeEncryptConnection(
+void LinkLayerController::IncomingLeScanPacket(
model::packets::LinkLayerPacketView incoming) {
- LOG_INFO();
-
- Address peer = incoming.GetSourceAddress();
- uint16_t handle = connections_.GetHandleOnlyAddress(peer);
- if (handle == kReservedHandle) {
- LOG_INFO("@%s: Unknown connection @%s",
- incoming.GetDestinationAddress().ToString().c_str(),
- peer.ToString().c_str());
- return;
- }
- auto le_encrypt = model::packets::LeEncryptConnectionView::Create(incoming);
- ASSERT(le_encrypt.IsValid());
- // TODO: Save keys to check
-
- send_event_(bluetooth::hci::LeLongTermKeyRequestBuilder::Create(
- handle, le_encrypt.GetRand(), le_encrypt.GetEdiv()));
-}
-
-void LinkLayerController::IncomingLeEncryptConnectionResponse(
- model::packets::LinkLayerPacketView incoming) {
- LOG_INFO();
- // TODO: Check keys
- uint16_t handle =
- connections_.GetHandleOnlyAddress(incoming.GetSourceAddress());
- if (handle == kReservedHandle) {
- LOG_INFO("@%s: Unknown connection @%s",
- incoming.GetDestinationAddress().ToString().c_str(),
- incoming.GetSourceAddress().ToString().c_str());
- return;
- }
- ErrorCode status = ErrorCode::SUCCESS;
- auto response =
- model::packets::LeEncryptConnectionResponseView::Create(incoming);
- ASSERT(response.IsValid());
-
- // Zero LTK is a rejection
- if (response.GetLtk() == std::array<uint8_t, 16>()) {
- status = ErrorCode::AUTHENTICATION_FAILURE;
- }
-
- if (connections_.IsEncrypted(handle)) {
- send_event_(bluetooth::hci::EncryptionKeyRefreshCompleteBuilder::Create(
- status, handle));
- } else {
- connections_.Encrypt(handle);
- send_event_(bluetooth::hci::EncryptionChangeBuilder::Create(
- status, handle, bluetooth::hci::EncryptionEnabled::ON));
- }
-}
-
-void LinkLayerController::IncomingLeReadRemoteFeatures(
- model::packets::LinkLayerPacketView incoming) {
- uint16_t handle =
- connections_.GetHandleOnlyAddress(incoming.GetSourceAddress());
- ErrorCode status = ErrorCode::SUCCESS;
- if (handle == kReservedHandle) {
- LOG_WARN("@%s: Unknown connection @%s",
- incoming.GetDestinationAddress().ToString().c_str(),
- incoming.GetSourceAddress().ToString().c_str());
- }
- SendLinkLayerPacket(
- model::packets::LeReadRemoteFeaturesResponseBuilder::Create(
- incoming.GetDestinationAddress(), incoming.GetSourceAddress(),
- properties_.GetLeSupportedFeatures(), static_cast<uint8_t>(status)));
-}
-
-void LinkLayerController::IncomingLeReadRemoteFeaturesResponse(
- model::packets::LinkLayerPacketView incoming) {
- uint16_t handle =
- connections_.GetHandleOnlyAddress(incoming.GetSourceAddress());
- ErrorCode status = ErrorCode::SUCCESS;
- auto response =
- model::packets::LeReadRemoteFeaturesResponseView::Create(incoming);
- ASSERT(response.IsValid());
- if (handle == kReservedHandle) {
- LOG_INFO("@%s: Unknown connection @%s",
- incoming.GetDestinationAddress().ToString().c_str(),
- incoming.GetSourceAddress().ToString().c_str());
- status = ErrorCode::UNKNOWN_CONNECTION;
- } else {
- status = static_cast<ErrorCode>(response.GetStatus());
- }
- send_event_(bluetooth::hci::LeReadRemoteFeaturesCompleteBuilder::Create(
- status, handle, response.GetFeatures()));
-}
+ auto to_send = model::packets::LeScanResponseBuilder::Create(
+ properties_.GetLeAddress(), incoming.GetSourceAddress(),
+ static_cast<model::packets::AddressType>(properties_.GetLeAddressType()),
+ static_cast<model::packets::AdvertisementType>(
+ properties_.GetLeAdvertisementType()),
+ properties_.GetLeScanResponse());
-void LinkLayerController::IncomingLeScanPacket(
- model::packets::LinkLayerPacketView incoming) {
- for (auto& advertiser : advertisers_) {
- auto to_send = advertiser.GetScanResponse(incoming.GetDestinationAddress(),
- incoming.GetSourceAddress());
- if (to_send != nullptr) {
- SendLeLinkLayerPacket(std::move(to_send));
- }
- }
+ SendLeLinkLayerPacket(std::move(to_send));
}
void LinkLayerController::IncomingLeScanResponsePacket(
@@ -1400,26 +920,23 @@ void LinkLayerController::IncomingLeScanResponsePacket(
auto scan_response = model::packets::LeScanResponseView::Create(incoming);
ASSERT(scan_response.IsValid());
vector<uint8_t> ad = scan_response.GetData();
- auto adv_type = scan_response.GetAdvertisementType();
+ auto adv_type = static_cast<LeAdvertisement::AdvertisementType>(
+ scan_response.GetAdvertisementType());
auto address_type =
static_cast<LeAdvertisement::AddressType>(scan_response.GetAddressType());
if (le_scan_enable_ == bluetooth::hci::OpCode::LE_SET_SCAN_ENABLE) {
- if (adv_type != model::packets::AdvertisementType::SCAN_RESPONSE) {
- return;
- }
std::unique_ptr<bluetooth::packet::RawBuilder> raw_builder_ptr =
std::make_unique<bluetooth::packet::RawBuilder>();
raw_builder_ptr->AddOctets1(
static_cast<uint8_t>(bluetooth::hci::SubeventCode::ADVERTISING_REPORT));
raw_builder_ptr->AddOctets1(0x01); // num reports
- raw_builder_ptr->AddOctets1(static_cast<uint8_t>(
- bluetooth::hci::AdvertisingEventType::SCAN_RESPONSE));
+ raw_builder_ptr->AddOctets1(static_cast<uint8_t>(adv_type));
raw_builder_ptr->AddOctets1(static_cast<uint8_t>(address_type));
raw_builder_ptr->AddAddress(incoming.GetSourceAddress());
raw_builder_ptr->AddOctets1(ad.size());
raw_builder_ptr->AddOctets(ad);
raw_builder_ptr->AddOctets1(GetRssi());
- auto packet = bluetooth::hci::EventBuilder::Create(
+ auto packet = bluetooth::hci::EventPacketBuilder::Create(
bluetooth::hci::EventCode::LE_META_EVENT, std::move(raw_builder_ptr));
send_event_(std::move(packet));
}
@@ -1430,7 +947,7 @@ void LinkLayerController::IncomingLeScanResponsePacket(
raw_builder_ptr->AddOctets1(static_cast<uint8_t>(
bluetooth::hci::SubeventCode::EXTENDED_ADVERTISING_REPORT));
raw_builder_ptr->AddOctets1(0x01); // num reports
- raw_builder_ptr->AddOctets1(0x1a); // TODO: 0x1b for ADV_SCAN_IND
+ raw_builder_ptr->AddOctets1(static_cast<uint8_t>(adv_type));
raw_builder_ptr->AddOctets1(static_cast<uint8_t>(address_type));
raw_builder_ptr->AddAddress(incoming.GetSourceAddress());
raw_builder_ptr->AddOctets1(1); // Primary_PHY
@@ -1443,150 +960,27 @@ void LinkLayerController::IncomingLeScanResponsePacket(
raw_builder_ptr->AddAddress(Address::kEmpty); // Direct_Address
raw_builder_ptr->AddOctets1(ad.size());
raw_builder_ptr->AddOctets(ad);
- auto packet = bluetooth::hci::EventBuilder::Create(
+ auto packet = bluetooth::hci::EventPacketBuilder::Create(
bluetooth::hci::EventCode::LE_META_EVENT, std::move(raw_builder_ptr));
send_event_(std::move(packet));
}
}
-void LinkLayerController::IncomingPasskeyPacket(
- model::packets::LinkLayerPacketView incoming) {
- auto passkey = model::packets::PasskeyView::Create(incoming);
- ASSERT(passkey.IsValid());
- SaveKeyAndAuthenticate('P', incoming.GetSourceAddress());
-}
-
-void LinkLayerController::IncomingPasskeyFailedPacket(
- model::packets::LinkLayerPacketView incoming) {
- auto failed = model::packets::PasskeyFailedView::Create(incoming);
- ASSERT(failed.IsValid());
- auto current_peer = incoming.GetSourceAddress();
- security_manager_.AuthenticationRequestFinished();
- ScheduleTask(milliseconds(5), [this, current_peer]() {
- send_event_(bluetooth::hci::SimplePairingCompleteBuilder::Create(
- ErrorCode::AUTHENTICATION_FAILURE, current_peer));
- });
-}
-
-void LinkLayerController::IncomingPinRequestPacket(
- model::packets::LinkLayerPacketView incoming) {
- auto request = model::packets::PinRequestView::Create(incoming);
- ASSERT(request.IsValid());
- auto peer = incoming.GetSourceAddress();
- auto handle = connections_.GetHandle(AddressWithType(
- peer, bluetooth::hci::AddressType::PUBLIC_DEVICE_ADDRESS));
- if (handle == kReservedHandle) {
- LOG_INFO("Dropping %s request (no connection)", peer.ToString().c_str());
- auto wrong_pin = request.GetPinCode();
- wrong_pin[0] = wrong_pin[0]++;
- SendLinkLayerPacket(model::packets::PinResponseBuilder::Create(
- properties_.GetAddress(), peer, wrong_pin));
- return;
- }
- if (security_manager_.AuthenticationInProgress()) {
- auto current_peer = security_manager_.GetAuthenticationAddress();
- if (current_peer != peer) {
- LOG_INFO("Dropping %s request (%s in progress)", peer.ToString().c_str(),
- current_peer.ToString().c_str());
- auto wrong_pin = request.GetPinCode();
- wrong_pin[0] = wrong_pin[0]++;
- SendLinkLayerPacket(model::packets::PinResponseBuilder::Create(
- properties_.GetAddress(), peer, wrong_pin));
- return;
- }
- } else {
- LOG_INFO("Incoming authentication request %s", peer.ToString().c_str());
- security_manager_.AuthenticationRequest(peer, handle);
- }
- auto current_peer = security_manager_.GetAuthenticationAddress();
- security_manager_.SetRemotePin(peer, request.GetPinCode());
- if (security_manager_.GetPinRequested(peer)) {
- if (security_manager_.GetLocalPinResponseReceived(peer)) {
- SendLinkLayerPacket(model::packets::PinResponseBuilder::Create(
- properties_.GetAddress(), peer, request.GetPinCode()));
- if (security_manager_.PinCompare()) {
- LOG_INFO("Authenticating %s", peer.ToString().c_str());
- SaveKeyAndAuthenticate('L', peer); // Legacy
- } else {
- security_manager_.AuthenticationRequestFinished();
- ScheduleTask(milliseconds(5), [this, peer]() {
- send_event_(bluetooth::hci::SimplePairingCompleteBuilder::Create(
- ErrorCode::AUTHENTICATION_FAILURE, peer));
- });
- }
- }
- } else {
- LOG_INFO("PIN pairing %s", properties_.GetAddress().ToString().c_str());
- ScheduleTask(milliseconds(5), [this, peer]() {
- security_manager_.SetPinRequested(peer);
- send_event_(bluetooth::hci::PinCodeRequestBuilder::Create(peer));
- });
- }
-}
-
-void LinkLayerController::IncomingPinResponsePacket(
- model::packets::LinkLayerPacketView incoming) {
- auto request = model::packets::PinResponseView::Create(incoming);
- ASSERT(request.IsValid());
- auto peer = incoming.GetSourceAddress();
- auto handle = connections_.GetHandle(AddressWithType(
- peer, bluetooth::hci::AddressType::PUBLIC_DEVICE_ADDRESS));
- if (handle == kReservedHandle) {
- LOG_INFO("Dropping %s request (no connection)", peer.ToString().c_str());
- return;
- }
- if (security_manager_.AuthenticationInProgress()) {
- auto current_peer = security_manager_.GetAuthenticationAddress();
- if (current_peer != peer) {
- LOG_INFO("Dropping %s request (%s in progress)", peer.ToString().c_str(),
- current_peer.ToString().c_str());
- return;
- }
- } else {
- LOG_INFO("Dropping response without authentication request %s",
- peer.ToString().c_str());
- return;
- }
- auto current_peer = security_manager_.GetAuthenticationAddress();
- security_manager_.SetRemotePin(peer, request.GetPinCode());
- if (security_manager_.GetPinRequested(peer)) {
- if (security_manager_.GetLocalPinResponseReceived(peer)) {
- SendLinkLayerPacket(model::packets::PinResponseBuilder::Create(
- properties_.GetAddress(), peer, request.GetPinCode()));
- if (security_manager_.PinCompare()) {
- LOG_INFO("Authenticating %s", peer.ToString().c_str());
- SaveKeyAndAuthenticate('L', peer); // Legacy
- } else {
- security_manager_.AuthenticationRequestFinished();
- ScheduleTask(milliseconds(5), [this, peer]() {
- send_event_(bluetooth::hci::SimplePairingCompleteBuilder::Create(
- ErrorCode::AUTHENTICATION_FAILURE, peer));
- });
- }
- }
- } else {
- LOG_INFO("PIN pairing %s", properties_.GetAddress().ToString().c_str());
- ScheduleTask(milliseconds(5), [this, peer]() {
- security_manager_.SetPinRequested(peer);
- send_event_(bluetooth::hci::PinCodeRequestBuilder::Create(peer));
- });
- }
-}
-
void LinkLayerController::IncomingPagePacket(
model::packets::LinkLayerPacketView incoming) {
auto page = model::packets::PageView::Create(incoming);
ASSERT(page.IsValid());
- LOG_INFO("from %s", incoming.GetSourceAddress().ToString().c_str());
+ LOG_INFO("%s from %s", __func__,
+ incoming.GetSourceAddress().ToString().c_str());
if (!connections_.CreatePendingConnection(
incoming.GetSourceAddress(), properties_.GetAuthenticationEnable())) {
// Send a response to indicate that we're busy, or drop the packet?
- LOG_WARN("Failed to create a pending connection for %s",
+ LOG_WARN("%s: Failed to create a pending connection for %s", __func__,
incoming.GetSourceAddress().ToString().c_str());
}
- bluetooth::hci::Address source_address{};
+ bluetooth::hci::Address source_address;
bluetooth::hci::Address::FromString(page.GetSourceAddress().ToString(),
source_address);
@@ -1599,10 +993,10 @@ void LinkLayerController::IncomingPagePacket(
void LinkLayerController::IncomingPageRejectPacket(
model::packets::LinkLayerPacketView incoming) {
- LOG_INFO("%s", incoming.GetSourceAddress().ToString().c_str());
+ LOG_INFO("%s: %s", __func__, incoming.GetSourceAddress().ToString().c_str());
auto reject = model::packets::PageRejectView::Create(incoming);
ASSERT(reject.IsValid());
- LOG_INFO("Sending CreateConnectionComplete");
+ LOG_INFO("%s: Sending CreateConnectionComplete", __func__);
auto packet = bluetooth::hci::ConnectionCompleteBuilder::Create(
static_cast<ErrorCode>(reject.GetReason()), 0x0eff,
incoming.GetSourceAddress(), bluetooth::hci::LinkType::ACL,
@@ -1613,12 +1007,12 @@ void LinkLayerController::IncomingPageRejectPacket(
void LinkLayerController::IncomingPageResponsePacket(
model::packets::LinkLayerPacketView incoming) {
Address peer = incoming.GetSourceAddress();
- LOG_INFO("%s", peer.ToString().c_str());
+ LOG_INFO("%s: %s", __func__, peer.ToString().c_str());
bool awaiting_authentication = connections_.AuthenticatePendingConnection();
uint16_t handle =
connections_.CreateConnection(peer, incoming.GetDestinationAddress());
- if (handle == kReservedHandle) {
- LOG_WARN("No free handles");
+ if (handle == acl::kReservedHandle) {
+ LOG_WARN("%s: No free handles", __func__);
return;
}
auto packet = bluetooth::hci::ConnectionCompleteBuilder::Create(
@@ -1634,41 +1028,63 @@ void LinkLayerController::IncomingPageResponsePacket(
}
void LinkLayerController::TimerTick() {
- if (inquiry_timer_task_id_ != kInvalidTaskId) Inquiry();
+ if (inquiry_state_ == Inquiry::InquiryState::INQUIRY) Inquiry();
+ if (inquiry_state_ == Inquiry::InquiryState::INQUIRY) PageScan();
LeAdvertising();
+ Connections();
}
void LinkLayerController::LeAdvertising() {
+ if (!le_advertising_enable_) {
+ return;
+ }
steady_clock::time_point now = steady_clock::now();
- for (auto& advertiser : advertisers_) {
- auto ad = advertiser.GetAdvertisement(now);
- if (ad == nullptr) {
- continue;
- }
- SendLeLinkLayerPacket(std::move(ad));
+ if (duration_cast<milliseconds>(now - last_le_advertisement_) <
+ milliseconds(200)) {
+ return;
}
+ last_le_advertisement_ = now;
+
+ auto own_address_type = static_cast<model::packets::AddressType>(
+ properties_.GetLeAdvertisingOwnAddressType());
+ Address advertising_address = Address::kEmpty;
+ if (own_address_type == model::packets::AddressType::PUBLIC) {
+ advertising_address = properties_.GetAddress();
+ } else if (own_address_type == model::packets::AddressType::RANDOM) {
+ advertising_address = properties_.GetLeAddress();
+ }
+ ASSERT(advertising_address != Address::kEmpty);
+ auto to_send = model::packets::LeAdvertisementBuilder::Create(
+ advertising_address, Address::kEmpty, own_address_type,
+ static_cast<model::packets::AdvertisementType>(own_address_type),
+ properties_.GetLeAdvertisement());
+ SendLeLinkLayerPacket(std::move(to_send));
+}
+
+void LinkLayerController::Connections() {
+ // TODO: Keep connections alive?
}
void LinkLayerController::RegisterEventChannel(
- const std::function<void(std::shared_ptr<bluetooth::hci::EventBuilder>)>&
- callback) {
+ const std::function<
+ void(std::shared_ptr<bluetooth::hci::EventPacketBuilder>)>& callback) {
send_event_ = callback;
}
void LinkLayerController::RegisterAclChannel(
- const std::function<void(std::shared_ptr<bluetooth::hci::AclBuilder>)>&
- callback) {
+ const std::function<
+ void(std::shared_ptr<bluetooth::hci::AclPacketBuilder>)>& callback) {
send_acl_ = callback;
}
void LinkLayerController::RegisterScoChannel(
- const std::function<void(std::shared_ptr<bluetooth::hci::ScoBuilder>)>&
+ const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>&
callback) {
send_sco_ = callback;
}
void LinkLayerController::RegisterIsoChannel(
- const std::function<void(std::shared_ptr<bluetooth::hci::IsoBuilder>)>&
+ const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>&
callback) {
send_iso_ = callback;
}
@@ -1713,6 +1129,16 @@ void LinkLayerController::RegisterTaskCancel(
cancel_task_ = task_cancel;
}
+void LinkLayerController::AddControllerEvent(milliseconds delay,
+ const TaskCallback& task) {
+ controller_events_.push_back(ScheduleTask(delay, task));
+}
+
+void LinkLayerController::WriteSimplePairingMode(bool enabled) {
+ ASSERT_LOG(enabled, "The spec says don't disable this!");
+ simple_pairing_mode_enabled_ = enabled;
+}
+
void LinkLayerController::StartSimplePairing(const Address& address) {
// IO Capability Exchange (See the Diagram in the Spec)
auto packet = bluetooth::hci::IoCapabilityRequestBuilder::Create(address);
@@ -1739,7 +1165,7 @@ void LinkLayerController::AuthenticateRemoteStage1(const Address& peer,
break;
case PairingType::DISPLAY_PIN:
send_event_(
- bluetooth::hci::UserPasskeyNotificationBuilder::Create(peer, 123456));
+ bluetooth::hci::UserConfirmationRequestBuilder::Create(peer, 123456));
break;
case PairingType::DISPLAY_AND_CONFIRM:
send_event_(
@@ -1748,14 +1174,6 @@ void LinkLayerController::AuthenticateRemoteStage1(const Address& peer,
case PairingType::INPUT_PIN:
send_event_(bluetooth::hci::UserPasskeyRequestBuilder::Create(peer));
break;
- case PairingType::OUT_OF_BAND:
- LOG_INFO("Oob data request for %s", peer.ToString().c_str());
- send_event_(bluetooth::hci::RemoteOobDataRequestBuilder::Create(peer));
- break;
- case PairingType::PEER_HAS_OUT_OF_BAND:
- LOG_INFO("Trusting that %s has OOB data", peer.ToString().c_str());
- SaveKeyAndAuthenticate('P', peer);
- break;
default:
LOG_ALWAYS_FATAL("Invalid PairingType %d",
static_cast<int>(pairing_type));
@@ -1787,23 +1205,16 @@ ErrorCode LinkLayerController::LinkKeyRequestNegativeReply(
security_manager_.DeleteKey(address);
// Simple pairing to get a key
uint16_t handle = connections_.GetHandleOnlyAddress(address);
- if (handle == kReservedHandle) {
- LOG_INFO("Device not connected %s", address.ToString().c_str());
+ if (handle == acl::kReservedHandle) {
+ LOG_INFO("%s: Device not connected %s", __func__,
+ address.ToString().c_str());
return ErrorCode::UNKNOWN_CONNECTION;
}
- if (properties_.GetSecureSimplePairingSupported()) {
- security_manager_.AuthenticationRequest(address, handle);
+ security_manager_.AuthenticationRequest(address, handle);
- ScheduleTask(milliseconds(5),
- [this, address]() { StartSimplePairing(address); });
- } else {
- LOG_INFO("PIN pairing %s", properties_.GetAddress().ToString().c_str());
- ScheduleTask(milliseconds(5), [this, address]() {
- security_manager_.SetPinRequested(address);
- send_event_(bluetooth::hci::PinCodeRequestBuilder::Create(address));
- });
- }
+ ScheduleTask(milliseconds(5),
+ [this, address]() { StartSimplePairing(address); });
return ErrorCode::SUCCESS;
}
@@ -1823,7 +1234,7 @@ ErrorCode LinkLayerController::IoCapabilityRequestReply(
properties_.GetAddress(), peer, io_capability, oob_data_present_flag,
authentication_requirements));
} else {
- LOG_INFO("Requesting remote capability");
+ LOG_INFO("%s: Requesting remote capability", __func__);
SendLinkLayerPacket(model::packets::IoCapabilityRequestBuilder::Create(
properties_.GetAddress(), peer, io_capability, oob_data_present_flag,
@@ -1848,126 +1259,38 @@ ErrorCode LinkLayerController::IoCapabilityRequestNegativeReply(
return ErrorCode::SUCCESS;
}
-void LinkLayerController::SaveKeyAndAuthenticate(uint8_t key_type,
- const Address& peer) {
- std::array<uint8_t, 16> key_vec{'k',
- 'e',
- 'y',
- ' ',
- key_type,
- 5,
- 6,
- 7,
- 8,
- 9,
- 10,
- 11,
- 12,
- 13,
- static_cast<uint8_t>(key_id_ >> 8u),
- static_cast<uint8_t>(key_id_)};
- key_id_ += 1;
+ErrorCode LinkLayerController::UserConfirmationRequestReply(
+ const Address& peer) {
+ if (security_manager_.GetAuthenticationAddress() != peer) {
+ return ErrorCode::AUTHENTICATION_FAILURE;
+ }
+ // TODO: Key could be calculated here.
+ std::array<uint8_t, 16> key_vec{1, 2, 3, 4, 5, 6, 7, 8,
+ 9, 10, 11, 12, 13, 14, 15, 16};
security_manager_.WriteKey(peer, key_vec);
security_manager_.AuthenticationRequestFinished();
- if (key_type == 'L') {
- // Legacy
- ScheduleTask(milliseconds(5), [this, peer, key_vec]() {
- send_event_(bluetooth::hci::LinkKeyNotificationBuilder::Create(
- peer, key_vec, bluetooth::hci::KeyType::AUTHENTICATED_P192));
- });
- } else {
- ScheduleTask(milliseconds(5), [this, peer]() {
- send_event_(bluetooth::hci::SimplePairingCompleteBuilder::Create(
- ErrorCode::SUCCESS, peer));
- });
+ ScheduleTask(milliseconds(5), [this, peer, key_vec]() {
+ send_event_(bluetooth::hci::LinkKeyNotificationBuilder::Create(
+ peer, key_vec, bluetooth::hci::KeyType::AUTHENTICATED_P256));
+ });
- ScheduleTask(milliseconds(5), [this, peer, key_vec]() {
- send_event_(bluetooth::hci::LinkKeyNotificationBuilder::Create(
- peer, key_vec, bluetooth::hci::KeyType::AUTHENTICATED_P256));
- });
- }
+ ScheduleTask(milliseconds(5), [this, peer]() {
+ send_event_(bluetooth::hci::SimplePairingCompleteBuilder::Create(
+ ErrorCode::SUCCESS, peer));
+ });
ScheduleTask(milliseconds(15),
[this, peer]() { AuthenticateRemoteStage2(peer); });
-}
-
-ErrorCode LinkLayerController::PinCodeRequestReply(const Address& peer,
- std::vector<uint8_t> pin) {
- LOG_INFO("%s", properties_.GetAddress().ToString().c_str());
- auto current_peer = security_manager_.GetAuthenticationAddress();
- if (peer != current_peer) {
- LOG_INFO("%s: %s != %s", properties_.GetAddress().ToString().c_str(),
- peer.ToString().c_str(), current_peer.ToString().c_str());
- security_manager_.AuthenticationRequestFinished();
- ScheduleTask(milliseconds(5), [this, current_peer]() {
- send_event_(bluetooth::hci::SimplePairingCompleteBuilder::Create(
- ErrorCode::AUTHENTICATION_FAILURE, current_peer));
- });
- return ErrorCode::UNKNOWN_CONNECTION;
- }
- if (!security_manager_.GetPinRequested(peer)) {
- LOG_INFO("No Pin Requested for %s", peer.ToString().c_str());
- return ErrorCode::COMMAND_DISALLOWED;
- }
- security_manager_.SetLocalPin(peer, pin);
- if (security_manager_.GetRemotePinResponseReceived(peer)) {
- if (security_manager_.PinCompare()) {
- LOG_INFO("Authenticating %s", peer.ToString().c_str());
- SaveKeyAndAuthenticate('L', peer); // Legacy
- } else {
- security_manager_.AuthenticationRequestFinished();
- ScheduleTask(milliseconds(5), [this, peer]() {
- send_event_(bluetooth::hci::SimplePairingCompleteBuilder::Create(
- ErrorCode::AUTHENTICATION_FAILURE, peer));
- });
- }
- } else {
- SendLinkLayerPacket(model::packets::PinRequestBuilder::Create(
- properties_.GetAddress(), peer, pin));
- }
return ErrorCode::SUCCESS;
}
-ErrorCode LinkLayerController::PinCodeRequestNegativeReply(
- const Address& peer) {
- auto current_peer = security_manager_.GetAuthenticationAddress();
- security_manager_.AuthenticationRequestFinished();
- ScheduleTask(milliseconds(5), [this, current_peer]() {
- send_event_(bluetooth::hci::SimplePairingCompleteBuilder::Create(
- ErrorCode::AUTHENTICATION_FAILURE, current_peer));
- });
- if (peer != current_peer) {
- return ErrorCode::UNKNOWN_CONNECTION;
- }
- if (!security_manager_.GetPinRequested(peer)) {
- LOG_INFO("No Pin Requested for %s", peer.ToString().c_str());
- return ErrorCode::COMMAND_DISALLOWED;
- }
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::UserConfirmationRequestReply(
+ErrorCode LinkLayerController::UserConfirmationRequestNegativeReply(
const Address& peer) {
if (security_manager_.GetAuthenticationAddress() != peer) {
return ErrorCode::AUTHENTICATION_FAILURE;
}
- SaveKeyAndAuthenticate('U', peer);
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::UserConfirmationRequestNegativeReply(
- const Address& peer) {
- auto current_peer = security_manager_.GetAuthenticationAddress();
- security_manager_.AuthenticationRequestFinished();
- ScheduleTask(milliseconds(5), [this, current_peer]() {
- send_event_(bluetooth::hci::SimplePairingCompleteBuilder::Create(
- ErrorCode::AUTHENTICATION_FAILURE, current_peer));
- });
- if (peer != current_peer) {
- return ErrorCode::UNKNOWN_CONNECTION;
- }
return ErrorCode::SUCCESS;
}
@@ -1976,87 +1299,48 @@ ErrorCode LinkLayerController::UserPasskeyRequestReply(const Address& peer,
if (security_manager_.GetAuthenticationAddress() != peer) {
return ErrorCode::AUTHENTICATION_FAILURE;
}
- SendLinkLayerPacket(model::packets::PasskeyBuilder::Create(
- properties_.GetAddress(), peer, numeric_value));
- SaveKeyAndAuthenticate('P', peer);
-
+ LOG_INFO("TODO:Do something with the passkey %06d", numeric_value);
return ErrorCode::SUCCESS;
}
ErrorCode LinkLayerController::UserPasskeyRequestNegativeReply(
const Address& peer) {
- auto current_peer = security_manager_.GetAuthenticationAddress();
- security_manager_.AuthenticationRequestFinished();
- ScheduleTask(milliseconds(5), [this, current_peer]() {
- send_event_(bluetooth::hci::SimplePairingCompleteBuilder::Create(
- ErrorCode::AUTHENTICATION_FAILURE, current_peer));
- });
- if (peer != current_peer) {
- return ErrorCode::UNKNOWN_CONNECTION;
+ if (security_manager_.GetAuthenticationAddress() != peer) {
+ return ErrorCode::AUTHENTICATION_FAILURE;
}
return ErrorCode::SUCCESS;
}
ErrorCode LinkLayerController::RemoteOobDataRequestReply(
- const Address& peer, const std::array<uint8_t, 16>& c,
- const std::array<uint8_t, 16>& r) {
+ const Address& peer, const std::vector<uint8_t>& c,
+ const std::vector<uint8_t>& r) {
if (security_manager_.GetAuthenticationAddress() != peer) {
return ErrorCode::AUTHENTICATION_FAILURE;
}
LOG_INFO("TODO:Do something with the OOB data c=%d r=%d", c[0], r[0]);
- SaveKeyAndAuthenticate('o', peer);
-
return ErrorCode::SUCCESS;
}
ErrorCode LinkLayerController::RemoteOobDataRequestNegativeReply(
const Address& peer) {
- auto current_peer = security_manager_.GetAuthenticationAddress();
- security_manager_.AuthenticationRequestFinished();
- ScheduleTask(milliseconds(5), [this, current_peer]() {
- send_event_(bluetooth::hci::SimplePairingCompleteBuilder::Create(
- ErrorCode::AUTHENTICATION_FAILURE, current_peer));
- });
- if (peer != current_peer) {
- return ErrorCode::UNKNOWN_CONNECTION;
- }
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::RemoteOobExtendedDataRequestReply(
- const Address& peer, const std::array<uint8_t, 16>& c192,
- const std::array<uint8_t, 16>& r192, const std::array<uint8_t, 16>& c256,
- const std::array<uint8_t, 16>& r256) {
if (security_manager_.GetAuthenticationAddress() != peer) {
return ErrorCode::AUTHENTICATION_FAILURE;
}
- LOG_INFO(
- "TODO:Do something with the OOB data c192=%d r192=%d c256=%d r256=%d",
- c192[0], r192[0], c256[0], r256[0]);
- SaveKeyAndAuthenticate('O', peer);
-
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::SendKeypressNotification(
- const Address& peer,
- bluetooth::hci::KeypressNotificationType notification_type) {
- if (notification_type >
- bluetooth::hci::KeypressNotificationType::ENTRY_COMPLETED) {
- return ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
- }
-
- SendLinkLayerPacket(model::packets::KeypressNotificationBuilder::Create(
- properties_.GetAddress(), peer,
- static_cast<model::packets::PasskeyNotificationType>(notification_type)));
return ErrorCode::SUCCESS;
}
void LinkLayerController::HandleAuthenticationRequest(const Address& address,
uint16_t handle) {
+ if (simple_pairing_mode_enabled_ == true) {
security_manager_.AuthenticationRequest(address, handle);
auto packet = bluetooth::hci::LinkKeyRequestBuilder::Create(address);
send_event_(std::move(packet));
+ } else { // Should never happen for our phones
+ // Check for a key, try to authenticate, ask for a PIN.
+ auto packet = bluetooth::hci::AuthenticationCompleteBuilder::Create(
+ ErrorCode::AUTHENTICATION_FAILURE, handle);
+ send_event_(std::move(packet));
+ }
}
ErrorCode LinkLayerController::AuthenticationRequested(uint16_t handle) {
@@ -2124,33 +1408,34 @@ ErrorCode LinkLayerController::SetConnectionEncryption(
ErrorCode LinkLayerController::AcceptConnectionRequest(const Address& addr,
bool try_role_switch) {
if (!connections_.HasPendingConnection(addr)) {
- LOG_INFO("No pending connection for %s", addr.ToString().c_str());
+ LOG_INFO("%s: No pending connection for %s", __func__,
+ addr.ToString().c_str());
return ErrorCode::UNKNOWN_CONNECTION;
}
- LOG_INFO("Accept in 200ms");
+ LOG_INFO("%s: Accept in 200ms", __func__);
ScheduleTask(milliseconds(200), [this, addr, try_role_switch]() {
- LOG_INFO("Accepted");
- MakePeripheralConnection(addr, try_role_switch);
+ LOG_INFO("%s: Accepted", __func__);
+ MakeSlaveConnection(addr, try_role_switch);
});
return ErrorCode::SUCCESS;
}
-void LinkLayerController::MakePeripheralConnection(const Address& addr,
- bool try_role_switch) {
- LOG_INFO("Sending page response to %s", addr.ToString().c_str());
+void LinkLayerController::MakeSlaveConnection(const Address& addr,
+ bool try_role_switch) {
+ LOG_INFO("%s sending page response to %s", __func__, addr.ToString().c_str());
auto to_send = model::packets::PageResponseBuilder::Create(
properties_.GetAddress(), addr, try_role_switch);
SendLinkLayerPacket(std::move(to_send));
uint16_t handle =
connections_.CreateConnection(addr, properties_.GetAddress());
- if (handle == kReservedHandle) {
- LOG_INFO("CreateConnection failed");
+ if (handle == acl::kReservedHandle) {
+ LOG_INFO("%s CreateConnection failed", __func__);
return;
}
- LOG_INFO("CreateConnection returned handle 0x%x", handle);
+ LOG_INFO("%s CreateConnection returned handle 0x%x", __func__, handle);
auto packet = bluetooth::hci::ConnectionCompleteBuilder::Create(
ErrorCode::SUCCESS, handle, addr, bluetooth::hci::LinkType::ACL,
bluetooth::hci::Enable::DISABLED);
@@ -2160,22 +1445,22 @@ void LinkLayerController::MakePeripheralConnection(const Address& addr,
ErrorCode LinkLayerController::RejectConnectionRequest(const Address& addr,
uint8_t reason) {
if (!connections_.HasPendingConnection(addr)) {
- LOG_INFO("No pending connection for %s", addr.ToString().c_str());
+ LOG_INFO("%s: No pending connection for %s", __func__,
+ addr.ToString().c_str());
return ErrorCode::UNKNOWN_CONNECTION;
}
- ScheduleTask(milliseconds(200), [this, addr, reason]() {
- RejectPeripheralConnection(addr, reason);
- });
+ ScheduleTask(milliseconds(200),
+ [this, addr, reason]() { RejectSlaveConnection(addr, reason); });
return ErrorCode::SUCCESS;
}
-void LinkLayerController::RejectPeripheralConnection(const Address& addr,
- uint8_t reason) {
+void LinkLayerController::RejectSlaveConnection(const Address& addr,
+ uint8_t reason) {
auto to_send = model::packets::PageRejectBuilder::Create(
properties_.GetAddress(), addr, reason);
- LOG_INFO("Sending page reject to %s (reason 0x%02hhx)",
+ LOG_INFO("%s sending page reject to %s (reason 0x%02hhx)", __func__,
addr.ToString().c_str(), reason);
SendLinkLayerPacket(std::move(to_send));
@@ -2259,7 +1544,7 @@ ErrorCode LinkLayerController::ChangeConnectionLinkKey(uint16_t handle) {
return ErrorCode::COMMAND_DISALLOWED;
}
-ErrorCode LinkLayerController::CentralLinkKey(uint8_t /* key_flag */) {
+ErrorCode LinkLayerController::MasterLinkKey(uint8_t /* key_flag */) {
// TODO: implement real logic
return ErrorCode::COMMAND_DISALLOWED;
}
@@ -2337,62 +1622,6 @@ ErrorCode LinkLayerController::WriteLinkPolicySettings(uint16_t handle,
return ErrorCode::SUCCESS;
}
-ErrorCode LinkLayerController::WriteDefaultLinkPolicySettings(
- uint16_t settings) {
- if (settings > 7 /* Sniff + Hold + Role switch */) {
- return ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
- }
- default_link_policy_settings_ = settings;
- return ErrorCode::SUCCESS;
-}
-
-uint16_t LinkLayerController::ReadDefaultLinkPolicySettings() {
- return default_link_policy_settings_;
-}
-
-void LinkLayerController::ReadLocalOobData() {
- std::array<uint8_t, 16> c_array(
- {'c', ' ', 'a', 'r', 'r', 'a', 'y', ' ', '0', '0', '0', '0', '0', '0',
- static_cast<uint8_t>((oob_id_ % 0x10000) >> 8u),
- static_cast<uint8_t>(oob_id_ % 0x100)});
-
- std::array<uint8_t, 16> r_array(
- {'r', ' ', 'a', 'r', 'r', 'a', 'y', ' ', '0', '0', '0', '0', '0', '0',
- static_cast<uint8_t>((oob_id_ % 0x10000) >> 8u),
- static_cast<uint8_t>(oob_id_ % 0x100)});
-
- send_event_(bluetooth::hci::ReadLocalOobDataCompleteBuilder::Create(
- 1, ErrorCode::SUCCESS, c_array, r_array));
- oob_id_ += 1;
-}
-
-void LinkLayerController::ReadLocalOobExtendedData() {
- std::array<uint8_t, 16> c_192_array(
- {'c', ' ', 'a', 'r', 'r', 'a', 'y', ' ', '1', '9', '2', '0', '0', '0',
- static_cast<uint8_t>((oob_id_ % 0x10000) >> 8u),
- static_cast<uint8_t>(oob_id_ % 0x100)});
-
- std::array<uint8_t, 16> r_192_array(
- {'r', ' ', 'a', 'r', 'r', 'a', 'y', ' ', '1', '9', '2', '0', '0', '0',
- static_cast<uint8_t>((oob_id_ % 0x10000) >> 8u),
- static_cast<uint8_t>(oob_id_ % 0x100)});
-
- std::array<uint8_t, 16> c_256_array(
- {'c', ' ', 'a', 'r', 'r', 'a', 'y', ' ', '2', '5', '6', '0', '0', '0',
- static_cast<uint8_t>((oob_id_ % 0x10000) >> 8u),
- static_cast<uint8_t>(oob_id_ % 0x100)});
-
- std::array<uint8_t, 16> r_256_array(
- {'r', ' ', 'a', 'r', 'r', 'a', 'y', ' ', '2', '5', '6', '0', '0', '0',
- static_cast<uint8_t>((oob_id_ % 0x10000) >> 8u),
- static_cast<uint8_t>(oob_id_ % 0x100)});
-
- send_event_(bluetooth::hci::ReadLocalOobExtendedDataCompleteBuilder::Create(
- 1, ErrorCode::SUCCESS, c_192_array, r_192_array, c_256_array,
- r_256_array));
- oob_id_ += 1;
-}
-
ErrorCode LinkLayerController::FlowSpecification(
uint16_t handle, uint8_t flow_direction, uint8_t service_type,
uint32_t /* token_rate */, uint32_t /* token_bucket_size */,
@@ -2417,222 +1646,35 @@ ErrorCode LinkLayerController::WriteLinkSupervisionTimeout(uint16_t handle,
return ErrorCode::SUCCESS;
}
-ErrorCode LinkLayerController::SetLeExtendedAddress(uint8_t set,
- Address address) {
- advertisers_[set].SetAddress(address);
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::SetLeExtendedAdvertisingData(
- uint8_t set, const std::vector<uint8_t>& data) {
- advertisers_[set].SetData(data);
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::SetLeExtendedAdvertisingParameters(
- uint8_t set, uint16_t interval_min, uint16_t interval_max,
- bluetooth::hci::LegacyAdvertisingProperties type,
- bluetooth::hci::OwnAddressType own_address_type,
- bluetooth::hci::PeerAddressType peer_address_type, Address peer,
- bluetooth::hci::AdvertisingFilterPolicy filter_policy) {
- model::packets::AdvertisementType ad_type;
- switch (type) {
- case bluetooth::hci::LegacyAdvertisingProperties::ADV_IND:
- ad_type = model::packets::AdvertisementType::ADV_IND;
- peer = Address::kEmpty;
- break;
- case bluetooth::hci::LegacyAdvertisingProperties::ADV_NONCONN_IND:
- ad_type = model::packets::AdvertisementType::ADV_NONCONN_IND;
- peer = Address::kEmpty;
- break;
- case bluetooth::hci::LegacyAdvertisingProperties::ADV_SCAN_IND:
- ad_type = model::packets::AdvertisementType::ADV_SCAN_IND;
- peer = Address::kEmpty;
- break;
- case bluetooth::hci::LegacyAdvertisingProperties::ADV_DIRECT_IND_HIGH:
- case bluetooth::hci::LegacyAdvertisingProperties::ADV_DIRECT_IND_LOW:
- ad_type = model::packets::AdvertisementType::ADV_DIRECT_IND;
- break;
- }
- auto interval_ms =
- static_cast<int>((interval_max + interval_min) * 0.625 / 2);
-
- AddressWithType peer_address;
- switch (peer_address_type) {
- case bluetooth::hci::PeerAddressType::PUBLIC_DEVICE_OR_IDENTITY_ADDRESS:
- peer_address = AddressWithType(
- peer, bluetooth::hci::AddressType::PUBLIC_DEVICE_ADDRESS);
- break;
- case bluetooth::hci::PeerAddressType::RANDOM_DEVICE_OR_IDENTITY_ADDRESS:
- peer_address = AddressWithType(
- peer, bluetooth::hci::AddressType::RANDOM_DEVICE_ADDRESS);
- break;
- }
-
- bluetooth::hci::AddressType own_address_address_type;
- switch (own_address_type) {
- case bluetooth::hci::OwnAddressType::RANDOM_DEVICE_ADDRESS:
- own_address_address_type =
- bluetooth::hci::AddressType::RANDOM_DEVICE_ADDRESS;
- break;
- case bluetooth::hci::OwnAddressType::PUBLIC_DEVICE_ADDRESS:
- own_address_address_type =
- bluetooth::hci::AddressType::PUBLIC_DEVICE_ADDRESS;
- break;
- case bluetooth::hci::OwnAddressType::RESOLVABLE_OR_PUBLIC_ADDRESS:
- own_address_address_type =
- bluetooth::hci::AddressType::PUBLIC_IDENTITY_ADDRESS;
- break;
- case bluetooth::hci::OwnAddressType::RESOLVABLE_OR_RANDOM_ADDRESS:
- own_address_address_type =
- bluetooth::hci::AddressType::RANDOM_IDENTITY_ADDRESS;
- break;
- }
-
- bluetooth::hci::LeScanningFilterPolicy scanning_filter_policy;
- switch (filter_policy) {
- case bluetooth::hci::AdvertisingFilterPolicy::ALL_DEVICES:
- scanning_filter_policy =
- bluetooth::hci::LeScanningFilterPolicy::ACCEPT_ALL;
- break;
- case bluetooth::hci::AdvertisingFilterPolicy::LISTED_SCAN:
- scanning_filter_policy =
- bluetooth::hci::LeScanningFilterPolicy::CONNECT_LIST_ONLY;
- break;
- case bluetooth::hci::AdvertisingFilterPolicy::LISTED_CONNECT:
- scanning_filter_policy =
- bluetooth::hci::LeScanningFilterPolicy::CHECK_INITIATORS_IDENTITY;
- break;
- case bluetooth::hci::AdvertisingFilterPolicy::LISTED_SCAN_AND_CONNECT:
- scanning_filter_policy = bluetooth::hci::LeScanningFilterPolicy::
- CONNECT_LIST_AND_INITIATORS_IDENTITY;
- break;
- }
-
- advertisers_[set].InitializeExtended(own_address_address_type, peer_address,
- scanning_filter_policy, ad_type,
- std::chrono::milliseconds(interval_ms));
-
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeRemoveAdvertisingSet(uint8_t set) {
- if (set >= advertisers_.size()) {
- return ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
- }
- advertisers_[set].Disable();
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeClearAdvertisingSets() {
- for (auto& advertiser : advertisers_) {
- if (advertiser.IsEnabled()) {
- return ErrorCode::COMMAND_DISALLOWED;
- }
- }
- for (auto& advertiser : advertisers_) {
- advertiser.Clear();
- }
- return ErrorCode::SUCCESS;
-}
-
-void LinkLayerController::LeConnectionUpdateComplete(
- bluetooth::hci::LeConnectionUpdateView connection_update) {
- uint16_t handle = connection_update.GetConnectionHandle();
- ErrorCode status = ErrorCode::SUCCESS;
- if (!connections_.HasHandle(handle)) {
- status = ErrorCode::UNKNOWN_CONNECTION;
- }
- uint16_t interval_min = connection_update.GetConnIntervalMin();
- uint16_t interval_max = connection_update.GetConnIntervalMax();
- uint16_t latency = connection_update.GetConnLatency();
- uint16_t supervision_timeout = connection_update.GetSupervisionTimeout();
-
- if (interval_min < 6 || interval_max > 0xC80 || interval_min > interval_max ||
- interval_max < interval_min || latency > 0x1F3 ||
- supervision_timeout < 0xA || supervision_timeout > 0xC80 ||
- // The Supervision_Timeout in milliseconds (*10) shall be larger than (1 +
- // Connection_Latency) * Connection_Interval_Max (* 5/4) * 2
- supervision_timeout <= ((((1 + latency) * interval_max * 10) / 4) / 10)) {
- status = ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
- }
- uint16_t interval = (interval_min + interval_max) / 2;
- send_event_(bluetooth::hci::LeConnectionUpdateCompleteBuilder::Create(
- status, handle, interval, latency, supervision_timeout));
-}
-
-ErrorCode LinkLayerController::LeConnectionUpdate(
- bluetooth::hci::LeConnectionUpdateView connection_update) {
- uint16_t handle = connection_update.GetConnectionHandle();
- if (!connections_.HasHandle(handle)) {
- return ErrorCode::UNKNOWN_CONNECTION;
- }
-
- // This could negotiate with the remote device in the future
- ScheduleTask(milliseconds(25), [this, connection_update]() {
- LeConnectionUpdateComplete(connection_update);
- });
-
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeConnectListClear() {
- if (ConnectListBusy()) {
- return ErrorCode::COMMAND_DISALLOWED;
- }
+void LinkLayerController::LeWhiteListClear() { le_white_list_.clear(); }
- le_connect_list_.clear();
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeResolvingListClear() {
- if (ResolvingListBusy()) {
- return ErrorCode::COMMAND_DISALLOWED;
- }
+void LinkLayerController::LeResolvingListClear() { le_resolving_list_.clear(); }
- le_resolving_list_.clear();
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeConnectListAddDevice(Address addr,
- uint8_t addr_type) {
- if (ConnectListBusy()) {
- return ErrorCode::COMMAND_DISALLOWED;
- }
+void LinkLayerController::LeWhiteListAddDevice(Address addr,
+ uint8_t addr_type) {
std::tuple<Address, uint8_t> new_tuple = std::make_tuple(addr, addr_type);
- for (auto dev : le_connect_list_) {
+ for (auto dev : le_white_list_) {
if (dev == new_tuple) {
- return ErrorCode::SUCCESS;
+ return;
}
}
- if (LeConnectListFull()) {
- return ErrorCode::MEMORY_CAPACITY_EXCEEDED;
- }
- le_connect_list_.emplace_back(new_tuple);
- return ErrorCode::SUCCESS;
+ le_white_list_.emplace_back(new_tuple);
}
-ErrorCode LinkLayerController::LeResolvingListAddDevice(
+void LinkLayerController::LeResolvingListAddDevice(
Address addr, uint8_t addr_type, std::array<uint8_t, kIrk_size> peerIrk,
std::array<uint8_t, kIrk_size> localIrk) {
- if (ResolvingListBusy()) {
- return ErrorCode::COMMAND_DISALLOWED;
- }
std::tuple<Address, uint8_t, std::array<uint8_t, kIrk_size>,
std::array<uint8_t, kIrk_size>>
new_tuple = std::make_tuple(addr, addr_type, peerIrk, localIrk);
- for (size_t i = 0; i < le_connect_list_.size(); i++) {
- auto curr = le_connect_list_[i];
+ for (size_t i = 0; i < le_white_list_.size(); i++) {
+ auto curr = le_white_list_[i];
if (std::get<0>(curr) == addr && std::get<1>(curr) == addr_type) {
le_resolving_list_[i] = new_tuple;
- return ErrorCode::SUCCESS;
+ return;
}
}
- if (LeResolvingListFull()) {
- return ErrorCode::MEMORY_CAPACITY_EXCEEDED;
- }
le_resolving_list_.emplace_back(new_tuple);
- return ErrorCode::SUCCESS;
}
void LinkLayerController::LeSetPrivacyMode(uint8_t address_type, Address addr,
@@ -2643,347 +1685,35 @@ void LinkLayerController::LeSetPrivacyMode(uint8_t address_type, Address addr,
LOG_INFO("mode = %d ", mode);
}
-void LinkLayerController::LeReadIsoTxSync(uint16_t handle) {}
-
-void LinkLayerController::LeSetCigParameters(
- uint8_t cig_id, uint32_t sdu_interval_m_to_s, uint32_t sdu_interval_s_to_m,
- bluetooth::hci::ClockAccuracy clock_accuracy,
- bluetooth::hci::Packing packing, bluetooth::hci::Enable framing,
- uint16_t max_transport_latency_m_to_s,
- uint16_t max_transport_latency_s_to_m,
- std::vector<bluetooth::hci::CisParametersConfig> cis_config) {
- send_event_(connections_.SetCigParameters(
- cig_id, sdu_interval_m_to_s, sdu_interval_s_to_m, clock_accuracy, packing,
- framing, max_transport_latency_m_to_s, max_transport_latency_s_to_m,
- cis_config));
-}
-
-ErrorCode LinkLayerController::LeCreateCis(
- std::vector<bluetooth::hci::CreateCisConfig> cis_config) {
- if (connections_.HasPendingCis()) {
- return ErrorCode::COMMAND_DISALLOWED;
- }
- for (auto& config : cis_config) {
- if (!connections_.HasHandle(config.acl_connection_handle_)) {
- LOG_INFO("Unknown ACL handle %04x", config.acl_connection_handle_);
- return ErrorCode::UNKNOWN_CONNECTION;
- }
- if (!connections_.HasCisHandle(config.cis_connection_handle_)) {
- LOG_INFO("Unknown CIS handle %04x", config.cis_connection_handle_);
- return ErrorCode::UNKNOWN_CONNECTION;
- }
- }
- for (auto& config : cis_config) {
- connections_.CreatePendingCis(config);
- auto own_address =
- connections_.GetOwnAddress(config.acl_connection_handle_);
- auto peer_address = connections_.GetAddress(config.acl_connection_handle_);
- StreamParameters stream_parameters =
- connections_.GetStreamParameters(config.cis_connection_handle_);
- GroupParameters group_parameters =
- connections_.GetGroupParameters(stream_parameters.group_id);
-
- SendLeLinkLayerPacket(model::packets::IsoConnectionRequestBuilder::Create(
- own_address.GetAddress(), peer_address.GetAddress(),
- stream_parameters.group_id, group_parameters.sdu_interval_m_to_s,
- group_parameters.sdu_interval_s_to_m, group_parameters.interleaved,
- group_parameters.framed, group_parameters.max_transport_latency_m_to_s,
- group_parameters.max_transport_latency_s_to_m,
- stream_parameters.stream_id, stream_parameters.max_sdu_m_to_s,
- stream_parameters.max_sdu_s_to_m, config.cis_connection_handle_,
- config.acl_connection_handle_));
- }
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeRemoveCig(uint8_t cig_id) {
- return connections_.RemoveCig(cig_id);
-}
-
-ErrorCode LinkLayerController::LeAcceptCisRequest(uint16_t cis_handle) {
- if (!connections_.HasPendingCisConnection(cis_handle)) {
- return ErrorCode::UNKNOWN_CONNECTION;
- }
- auto acl_handle = connections_.GetPendingAclHandle(cis_handle);
-
- connections_.ConnectCis(cis_handle);
-
- SendLeLinkLayerPacket(model::packets::IsoConnectionResponseBuilder::Create(
- connections_.GetOwnAddress(acl_handle).GetAddress(),
- connections_.GetAddress(acl_handle).GetAddress(),
- static_cast<uint8_t>(ErrorCode::SUCCESS), cis_handle, acl_handle,
- connections_.GetRemoteCisHandleForCisHandle(cis_handle)));
-
- // Both sides have to send LeCisEstablished event
-
- uint32_t cig_sync_delay = 0x100;
- uint32_t cis_sync_delay = 0x200;
- uint32_t latency_m_to_s = 0x200;
- uint32_t latency_s_to_m = 0x200;
- uint8_t nse = 1;
- uint8_t bn_m_to_s = 0;
- uint8_t bn_s_to_m = 0;
- uint8_t ft_m_to_s = 0;
- uint8_t ft_s_to_m = 0;
- uint8_t max_pdu_m_to_s = 0x40;
- uint8_t max_pdu_s_to_m = 0x40;
- uint16_t iso_interval = 0x100;
- send_event_(bluetooth::hci::LeCisEstablishedBuilder::Create(
- ErrorCode::SUCCESS, cis_handle, cig_sync_delay, cis_sync_delay,
- latency_m_to_s, latency_s_to_m,
- bluetooth::hci::SecondaryPhyType::NO_PACKETS,
- bluetooth::hci::SecondaryPhyType::NO_PACKETS, nse, bn_m_to_s, bn_s_to_m,
- ft_m_to_s, ft_s_to_m, max_pdu_m_to_s, max_pdu_s_to_m, iso_interval));
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeRejectCisRequest(uint16_t cis_handle,
- ErrorCode reason) {
- if (!connections_.HasPendingCisConnection(cis_handle)) {
- return ErrorCode::UNKNOWN_CONNECTION;
- }
- auto acl_handle = connections_.GetPendingAclHandle(cis_handle);
-
- SendLeLinkLayerPacket(model::packets::IsoConnectionResponseBuilder::Create(
- connections_.GetOwnAddress(acl_handle).GetAddress(),
- connections_.GetAddress(acl_handle).GetAddress(),
- static_cast<uint8_t>(reason), acl_handle, cis_handle, kReservedHandle));
- connections_.RejectCis(cis_handle);
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeCreateBig(
- uint8_t big_handle, uint8_t advertising_handle, uint8_t num_bis,
- uint32_t sdu_interval, uint16_t max_sdu, uint16_t max_transport_latency,
- uint8_t rtn, bluetooth::hci::SecondaryPhyType phy,
- bluetooth::hci::Packing packing, bluetooth::hci::Enable framing,
- bluetooth::hci::Enable encryption, std::vector<uint16_t> broadcast_code) {
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeTerminateBig(uint8_t big_handle,
- ErrorCode reason) {
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeBigCreateSync(
- uint8_t big_handle, uint16_t sync_handle, bluetooth::hci::Enable encryption,
- std::vector<uint16_t> broadcast_code, uint8_t mse,
- uint16_t big_sync_timeout, std::vector<uint8_t> bis) {
- return ErrorCode::SUCCESS;
-}
-
-void LinkLayerController::LeBigTerminateSync(uint8_t big_handle) {}
-
-ErrorCode LinkLayerController::LeRequestPeerSca(uint16_t request_handle) {
- return ErrorCode::SUCCESS;
-}
-
-void LinkLayerController::LeSetupIsoDataPath(
- uint16_t connection_handle,
- bluetooth::hci::DataPathDirection data_path_direction, uint8_t data_path_id,
- uint64_t codec_id, uint32_t controller_Delay,
- std::vector<uint8_t> codec_configuration) {}
-
-void LinkLayerController::LeRemoveIsoDataPath(
- uint16_t connection_handle,
- bluetooth::hci::DataPathDirection data_path_direction) {}
-
-void LinkLayerController::HandleLeEnableEncryption(
- uint16_t handle, std::array<uint8_t, 8> rand, uint16_t ediv,
- std::array<uint8_t, 16> ltk) {
- // TODO: Check keys
- // TODO: Block ACL traffic or at least guard against it
- if (!connections_.HasHandle(handle)) {
- return;
- }
- SendLeLinkLayerPacket(model::packets::LeEncryptConnectionBuilder::Create(
- connections_.GetOwnAddress(handle).GetAddress(),
- connections_.GetAddress(handle).GetAddress(), rand, ediv, ltk));
-}
-
-ErrorCode LinkLayerController::LeEnableEncryption(uint16_t handle,
- std::array<uint8_t, 8> rand,
- uint16_t ediv,
- std::array<uint8_t, 16> ltk) {
- if (!connections_.HasHandle(handle)) {
- LOG_INFO("Unknown handle %04x", handle);
- return ErrorCode::UNKNOWN_CONNECTION;
- }
-
- ScheduleTask(milliseconds(5), [this, handle, rand, ediv, ltk]() {
- HandleLeEnableEncryption(handle, rand, ediv, ltk);
- });
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeLongTermKeyRequestReply(
- uint16_t handle, std::array<uint8_t, 16> ltk) {
- if (!connections_.HasHandle(handle)) {
- LOG_INFO("Unknown handle %04x", handle);
- return ErrorCode::UNKNOWN_CONNECTION;
- }
-
- // TODO: Check keys
- if (connections_.IsEncrypted(handle)) {
- send_event_(bluetooth::hci::EncryptionKeyRefreshCompleteBuilder::Create(
- ErrorCode::SUCCESS, handle));
- } else {
- connections_.Encrypt(handle);
- send_event_(bluetooth::hci::EncryptionChangeBuilder::Create(
- ErrorCode::SUCCESS, handle, bluetooth::hci::EncryptionEnabled::ON));
- }
- SendLeLinkLayerPacket(
- model::packets::LeEncryptConnectionResponseBuilder::Create(
- connections_.GetOwnAddress(handle).GetAddress(),
- connections_.GetAddress(handle).GetAddress(),
- std::array<uint8_t, 8>(), uint16_t(), ltk));
-
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::LeLongTermKeyRequestNegativeReply(
- uint16_t handle) {
- if (!connections_.HasHandle(handle)) {
- LOG_INFO("Unknown handle %04x", handle);
- return ErrorCode::UNKNOWN_CONNECTION;
- }
-
- SendLeLinkLayerPacket(
- model::packets::LeEncryptConnectionResponseBuilder::Create(
- connections_.GetOwnAddress(handle).GetAddress(),
- connections_.GetAddress(handle).GetAddress(),
- std::array<uint8_t, 8>(), uint16_t(), std::array<uint8_t, 16>()));
- return ErrorCode::SUCCESS;
-}
-
-ErrorCode LinkLayerController::SetLeAdvertisingEnable(
- uint8_t le_advertising_enable) {
- if (!le_advertising_enable) {
- advertisers_[0].Disable();
- return ErrorCode::SUCCESS;
- }
- auto interval_ms = (properties_.GetLeAdvertisingIntervalMax() +
- properties_.GetLeAdvertisingIntervalMin()) *
- 0.625 / 2;
-
- Address own_address = properties_.GetAddress();
- if (properties_.GetLeAdvertisingOwnAddressType() ==
- static_cast<uint8_t>(
- bluetooth::hci::AddressType::RANDOM_DEVICE_ADDRESS) ||
- properties_.GetLeAdvertisingOwnAddressType() ==
- static_cast<uint8_t>(
- bluetooth::hci::AddressType::RANDOM_IDENTITY_ADDRESS)) {
- if (properties_.GetLeAddress().ToString() == "bb:bb:bb:ba:d0:1e" ||
- properties_.GetLeAddress() == Address::kEmpty) {
- return ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
- }
- own_address = properties_.GetLeAddress();
- }
- auto own_address_with_type = AddressWithType(
- own_address, static_cast<bluetooth::hci::AddressType>(
- properties_.GetLeAdvertisingOwnAddressType()));
-
- auto interval = std::chrono::milliseconds(static_cast<uint64_t>(interval_ms));
- if (interval < std::chrono::milliseconds(20)) {
- return ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
- }
- advertisers_[0].Initialize(
- own_address_with_type,
- bluetooth::hci::AddressWithType(
- properties_.GetLeAdvertisingPeerAddress(),
- static_cast<bluetooth::hci::AddressType>(
- properties_.GetLeAdvertisingPeerAddressType())),
- static_cast<bluetooth::hci::LeScanningFilterPolicy>(
- properties_.GetLeAdvertisingFilterPolicy()),
- static_cast<model::packets::AdvertisementType>(
- properties_.GetLeAdvertisementType()),
- properties_.GetLeAdvertisement(), properties_.GetLeScanResponse(),
- interval);
- advertisers_[0].Enable();
- return ErrorCode::SUCCESS;
-}
-
-void LinkLayerController::LeDisableAdvertisingSets() {
- for (auto& advertiser : advertisers_) {
- advertiser.Disable();
- }
-}
-
-uint8_t LinkLayerController::LeReadNumberOfSupportedAdvertisingSets() {
- return advertisers_.size();
-}
-
-ErrorCode LinkLayerController::SetLeExtendedAdvertisingEnable(
- bluetooth::hci::Enable enable,
- const std::vector<bluetooth::hci::EnabledSet>& enabled_sets) {
- for (const auto& set : enabled_sets) {
- if (set.advertising_handle_ > advertisers_.size()) {
- return ErrorCode::INVALID_HCI_COMMAND_PARAMETERS;
- }
- }
- for (const auto& set : enabled_sets) {
- auto handle = set.advertising_handle_;
- if (enable == bluetooth::hci::Enable::ENABLED) {
- advertisers_[handle].EnableExtended(
- std::chrono::milliseconds(10 * set.duration_));
- } else {
- advertisers_[handle].Disable();
- }
- }
- return ErrorCode::SUCCESS;
-}
-
-bool LinkLayerController::ConnectListBusy() {
- if (le_connect_) LOG_INFO("le_connect_");
- if (le_scan_enable_ != bluetooth::hci::OpCode::NONE)
- LOG_INFO("le_scan_enable");
- for (auto advertiser : advertisers_)
- if (advertiser.IsEnabled()) {
- LOG_INFO("Advertising");
- return true;
- }
- return le_connect_ || le_scan_enable_ != bluetooth::hci::OpCode::NONE;
-}
-
-bool LinkLayerController::ResolvingListBusy() {
- return ConnectListBusy(); // TODO: Add
- // HCI_LE_Periodic_Advertising_Create_Sync
-}
-
-ErrorCode LinkLayerController::LeConnectListRemoveDevice(Address addr,
- uint8_t addr_type) {
- if (ConnectListBusy()) {
- return ErrorCode::COMMAND_DISALLOWED;
- }
+void LinkLayerController::LeWhiteListRemoveDevice(Address addr,
+ uint8_t addr_type) {
+ // TODO: Add checks to see if advertising, scanning, or a connection request
+ // with the white list is ongoing.
std::tuple<Address, uint8_t> erase_tuple = std::make_tuple(addr, addr_type);
- for (size_t i = 0; i < le_connect_list_.size(); i++) {
- if (le_connect_list_[i] == erase_tuple) {
- le_connect_list_.erase(le_connect_list_.begin() + i);
+ for (size_t i = 0; i < le_white_list_.size(); i++) {
+ if (le_white_list_[i] == erase_tuple) {
+ le_white_list_.erase(le_white_list_.begin() + i);
}
}
- return ErrorCode::SUCCESS;
}
-ErrorCode LinkLayerController::LeResolvingListRemoveDevice(Address addr,
- uint8_t addr_type) {
- if (ResolvingListBusy()) {
- return ErrorCode::COMMAND_DISALLOWED;
- }
- for (size_t i = 0; i < le_connect_list_.size(); i++) {
- auto curr = le_connect_list_[i];
+void LinkLayerController::LeResolvingListRemoveDevice(Address addr,
+ uint8_t addr_type) {
+ // TODO: Add checks to see if advertising, scanning, or a connection request
+ // with the white list is ongoing.
+ for (size_t i = 0; i < le_white_list_.size(); i++) {
+ auto curr = le_white_list_[i];
if (std::get<0>(curr) == addr && std::get<1>(curr) == addr_type) {
le_resolving_list_.erase(le_resolving_list_.begin() + i);
}
}
- return ErrorCode::SUCCESS;
}
-bool LinkLayerController::LeConnectListContainsDevice(Address addr,
- uint8_t addr_type) {
+bool LinkLayerController::LeWhiteListContainsDevice(Address addr,
+ uint8_t addr_type) {
std::tuple<Address, uint8_t> sought_tuple = std::make_tuple(addr, addr_type);
- for (size_t i = 0; i < le_connect_list_.size(); i++) {
- if (le_connect_list_[i] == sought_tuple) {
+ for (size_t i = 0; i < le_white_list_.size(); i++) {
+ if (le_white_list_[i] == sought_tuple) {
return true;
}
}
@@ -2992,8 +1722,8 @@ bool LinkLayerController::LeConnectListContainsDevice(Address addr,
bool LinkLayerController::LeResolvingListContainsDevice(Address addr,
uint8_t addr_type) {
- for (size_t i = 0; i < le_connect_list_.size(); i++) {
- auto curr = le_connect_list_[i];
+ for (size_t i = 0; i < le_white_list_.size(); i++) {
+ auto curr = le_white_list_[i];
if (std::get<0>(curr) == addr && std::get<1>(curr) == addr_type) {
return true;
}
@@ -3001,8 +1731,8 @@ bool LinkLayerController::LeResolvingListContainsDevice(Address addr,
return false;
}
-bool LinkLayerController::LeConnectListFull() {
- return le_connect_list_.size() >= properties_.GetLeConnectListSize();
+bool LinkLayerController::LeWhiteListFull() {
+ return le_white_list_.size() >= properties_.GetLeWhiteListSize();
}
bool LinkLayerController::LeResolvingListFull() {
@@ -3010,31 +1740,29 @@ bool LinkLayerController::LeResolvingListFull() {
}
void LinkLayerController::Reset() {
- if (inquiry_timer_task_id_ != kInvalidTaskId) {
- CancelScheduledTask(inquiry_timer_task_id_);
- inquiry_timer_task_id_ = kInvalidTaskId;
- }
+ inquiry_state_ = Inquiry::InquiryState::STANDBY;
last_inquiry_ = steady_clock::now();
le_scan_enable_ = bluetooth::hci::OpCode::NONE;
- LeDisableAdvertisingSets();
+ le_advertising_enable_ = 0;
le_connect_ = 0;
}
+void LinkLayerController::PageScan() {}
+
void LinkLayerController::StartInquiry(milliseconds timeout) {
- inquiry_timer_task_id_ = ScheduleTask(milliseconds(timeout), [this]() {
- LinkLayerController::InquiryTimeout();
- });
+ ScheduleTask(milliseconds(timeout),
+ [this]() { LinkLayerController::InquiryTimeout(); });
+ inquiry_state_ = Inquiry::InquiryState::INQUIRY;
}
void LinkLayerController::InquiryCancel() {
- ASSERT(inquiry_timer_task_id_ != kInvalidTaskId);
- CancelScheduledTask(inquiry_timer_task_id_);
- inquiry_timer_task_id_ = kInvalidTaskId;
+ ASSERT(inquiry_state_ == Inquiry::InquiryState::INQUIRY);
+ inquiry_state_ = Inquiry::InquiryState::STANDBY;
}
void LinkLayerController::InquiryTimeout() {
- if (inquiry_timer_task_id_ != kInvalidTaskId) {
- inquiry_timer_task_id_ = kInvalidTaskId;
+ if (inquiry_state_ == Inquiry::InquiryState::INQUIRY) {
+ inquiry_state_ = Inquiry::InquiryState::STANDBY;
auto packet =
bluetooth::hci::InquiryCompleteBuilder::Create(ErrorCode::SUCCESS);
send_event_(std::move(packet));
diff --git a/vendor_libs/test_vendor_lib/model/controller/link_layer_controller.h b/vendor_libs/test_vendor_lib/model/controller/link_layer_controller.h
index 952f3d32b..738865d5b 100644
--- a/vendor_libs/test_vendor_lib/model/controller/link_layer_controller.h
+++ b/vendor_libs/test_vendor_lib/model/controller/link_layer_controller.h
@@ -16,12 +16,12 @@
#pragma once
+#include "acl_connection_handler.h"
#include "hci/address.h"
#include "hci/hci_packets.h"
+#include "include/hci.h"
#include "include/inquiry.h"
#include "include/phy.h"
-#include "model/controller/acl_connection_handler.h"
-#include "model/controller/le_advertiser.h"
#include "model/devices/device_properties.h"
#include "model/setup/async_manager.h"
#include "packets/link_layer_packets.h"
@@ -41,18 +41,15 @@ class LinkLayerController {
ErrorCode SendCommandToRemoteByAddress(
OpCode opcode, bluetooth::packet::PacketView<true> args,
const Address& remote);
- ErrorCode SendLeCommandToRemoteByAddress(
- OpCode opcode, bluetooth::packet::PacketView<true> args,
- const Address& remote, const Address& local);
ErrorCode SendCommandToRemoteByHandle(
OpCode opcode, bluetooth::packet::PacketView<true> args, uint16_t handle);
- ErrorCode SendScoToRemote(bluetooth::hci::ScoView sco_packet);
- ErrorCode SendAclToRemote(bluetooth::hci::AclView acl_packet);
+ ErrorCode SendScoToRemote(bluetooth::hci::ScoPacketView sco_packet);
+ ErrorCode SendAclToRemote(bluetooth::hci::AclPacketView acl_packet);
+ void WriteSimplePairingMode(bool enabled);
void StartSimplePairing(const Address& address);
void AuthenticateRemoteStage1(const Address& address, PairingType pairing_type);
void AuthenticateRemoteStage2(const Address& address);
- void SaveKeyAndAuthenticate(uint8_t key_type, const Address& peer);
ErrorCode LinkKeyRequestReply(const Address& address,
const std::array<uint8_t, 16>& key);
ErrorCode LinkKeyRequestNegativeReply(const Address& address);
@@ -61,34 +58,24 @@ class LinkLayerController {
uint8_t authentication_requirements);
ErrorCode IoCapabilityRequestNegativeReply(const Address& peer,
ErrorCode reason);
- ErrorCode PinCodeRequestReply(const Address& peer, std::vector<uint8_t> pin);
- ErrorCode PinCodeRequestNegativeReply(const Address& peer);
ErrorCode UserConfirmationRequestReply(const Address& peer);
ErrorCode UserConfirmationRequestNegativeReply(const Address& peer);
ErrorCode UserPasskeyRequestReply(const Address& peer,
uint32_t numeric_value);
ErrorCode UserPasskeyRequestNegativeReply(const Address& peer);
ErrorCode RemoteOobDataRequestReply(const Address& peer,
- const std::array<uint8_t, 16>& c,
- const std::array<uint8_t, 16>& r);
+ const std::vector<uint8_t>& c,
+ const std::vector<uint8_t>& r);
ErrorCode RemoteOobDataRequestNegativeReply(const Address& peer);
- ErrorCode RemoteOobExtendedDataRequestReply(
- const Address& peer, const std::array<uint8_t, 16>& c_192,
- const std::array<uint8_t, 16>& r_192,
- const std::array<uint8_t, 16>& c_256,
- const std::array<uint8_t, 16>& r_256);
- ErrorCode SendKeypressNotification(
- const Address& peer,
- bluetooth::hci::KeypressNotificationType notification_type);
void HandleSetConnectionEncryption(const Address& address, uint16_t handle, uint8_t encryption_enable);
ErrorCode SetConnectionEncryption(uint16_t handle, uint8_t encryption_enable);
void HandleAuthenticationRequest(const Address& address, uint16_t handle);
ErrorCode AuthenticationRequested(uint16_t handle);
ErrorCode AcceptConnectionRequest(const Address& addr, bool try_role_switch);
- void MakePeripheralConnection(const Address& addr, bool try_role_switch);
+ void MakeSlaveConnection(const Address& addr, bool try_role_switch);
ErrorCode RejectConnectionRequest(const Address& addr, uint8_t reason);
- void RejectPeripheralConnection(const Address& addr, uint8_t reason);
+ void RejectSlaveConnection(const Address& addr, uint8_t reason);
ErrorCode CreateConnection(const Address& addr, uint16_t packet_type,
uint8_t page_scan_mode, uint16_t clock_offset,
uint8_t allow_role_switch);
@@ -109,19 +96,17 @@ class LinkLayerController {
// Set the callbacks for sending packets to the HCI.
void RegisterEventChannel(
- const std::function<void(std::shared_ptr<bluetooth::hci::EventBuilder>)>&
- send_event);
+ const std::function<void(
+ std::shared_ptr<bluetooth::hci::EventPacketBuilder>)>& send_event);
void RegisterAclChannel(
- const std::function<void(std::shared_ptr<bluetooth::hci::AclBuilder>)>&
- send_acl);
+ const std::function<
+ void(std::shared_ptr<bluetooth::hci::AclPacketBuilder>)>& send_acl);
- void RegisterScoChannel(
- const std::function<void(std::shared_ptr<bluetooth::hci::ScoBuilder>)>&
- send_sco);
+ void RegisterScoChannel(const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>& send_sco);
void RegisterIsoChannel(
- const std::function<void(std::shared_ptr<bluetooth::hci::IsoBuilder>)>&
+ const std::function<void(std::shared_ptr<std::vector<uint8_t>>)>&
send_iso);
void RegisterRemoteChannel(
@@ -139,108 +124,37 @@ class LinkLayerController {
void RegisterTaskCancel(std::function<void(AsyncTaskId)> cancel);
void Reset();
+ void AddControllerEvent(std::chrono::milliseconds delay, const TaskCallback& task);
- void LeAdvertising();
-
- ErrorCode SetLeExtendedAddress(uint8_t handle, Address address);
-
- ErrorCode SetLeExtendedAdvertisingData(uint8_t handle,
- const std::vector<uint8_t>& data);
+ void PageScan();
+ void Connections();
- ErrorCode SetLeExtendedAdvertisingParameters(
- uint8_t set, uint16_t interval_min, uint16_t interval_max,
- bluetooth::hci::LegacyAdvertisingProperties type,
- bluetooth::hci::OwnAddressType own_address_type,
- bluetooth::hci::PeerAddressType peer_address_type, Address peer,
- bluetooth::hci::AdvertisingFilterPolicy filter_policy);
- ErrorCode LeRemoveAdvertisingSet(uint8_t set);
- ErrorCode LeClearAdvertisingSets();
- void LeConnectionUpdateComplete(
- bluetooth::hci::LeConnectionUpdateView connection_update_view);
- ErrorCode LeConnectionUpdate(
- bluetooth::hci::LeConnectionUpdateView connection_update_view);
+ void LeAdvertising();
void HandleLeConnection(AddressWithType addr, AddressWithType own_addr,
uint8_t role, uint16_t connection_interval,
uint16_t connection_latency,
uint16_t supervision_timeout);
- bool ConnectListBusy();
- ErrorCode LeConnectListClear();
- ErrorCode LeConnectListAddDevice(Address addr, uint8_t addr_type);
- ErrorCode LeConnectListRemoveDevice(Address addr, uint8_t addr_type);
- bool LeConnectListContainsDevice(Address addr, uint8_t addr_type);
- bool LeConnectListFull();
- bool ResolvingListBusy();
- ErrorCode LeResolvingListClear();
- ErrorCode LeResolvingListAddDevice(Address addr, uint8_t addr_type,
- std::array<uint8_t, kIrk_size> peerIrk,
- std::array<uint8_t, kIrk_size> localIrk);
- ErrorCode LeResolvingListRemoveDevice(Address addr, uint8_t addr_type);
+ void LeWhiteListClear();
+ void LeWhiteListAddDevice(Address addr, uint8_t addr_type);
+ void LeWhiteListRemoveDevice(Address addr, uint8_t addr_type);
+ bool LeWhiteListContainsDevice(Address addr, uint8_t addr_type);
+ bool LeWhiteListFull();
+ void LeResolvingListClear();
+ void LeResolvingListAddDevice(Address addr, uint8_t addr_type,
+ std::array<uint8_t, kIrk_size> peerIrk,
+ std::array<uint8_t, kIrk_size> localIrk);
+ void LeResolvingListRemoveDevice(Address addr, uint8_t addr_type);
bool LeResolvingListContainsDevice(Address addr, uint8_t addr_type);
bool LeResolvingListFull();
void LeSetPrivacyMode(uint8_t address_type, Address addr, uint8_t mode);
- void LeReadIsoTxSync(uint16_t handle);
- void LeSetCigParameters(
- uint8_t cig_id, uint32_t sdu_interval_m_to_s,
- uint32_t sdu_interval_s_to_m,
- bluetooth::hci::ClockAccuracy clock_accuracy,
- bluetooth::hci::Packing packing, bluetooth::hci::Enable framing,
- uint16_t max_transport_latency_m_to_s,
- uint16_t max_transport_latency_s_to_m,
- std::vector<bluetooth::hci::CisParametersConfig> cis_config);
- bluetooth::hci::ErrorCode LeCreateCis(
- std::vector<bluetooth::hci::CreateCisConfig> cis_config);
- bluetooth::hci::ErrorCode LeRemoveCig(uint8_t cig_id);
- bluetooth::hci::ErrorCode LeAcceptCisRequest(uint16_t handle);
- bluetooth::hci::ErrorCode LeRejectCisRequest(
- uint16_t handle, bluetooth::hci::ErrorCode reason);
- bluetooth::hci::ErrorCode LeCreateBig(
- uint8_t big_handle, uint8_t advertising_handle, uint8_t num_bis,
- uint32_t sdu_interval, uint16_t max_sdu, uint16_t max_transport_latency,
- uint8_t rtn, bluetooth::hci::SecondaryPhyType phy,
- bluetooth::hci::Packing packing, bluetooth::hci::Enable framing,
- bluetooth::hci::Enable encryption, std::vector<uint16_t> broadcast_code);
- bluetooth::hci::ErrorCode LeTerminateBig(uint8_t big_handle,
- bluetooth::hci::ErrorCode reason);
- bluetooth::hci::ErrorCode LeBigCreateSync(
- uint8_t big_handle, uint16_t sync_handle,
- bluetooth::hci::Enable encryption, std::vector<uint16_t> broadcast_code,
- uint8_t mse, uint16_t big_syunc_timeout, std::vector<uint8_t> bis);
- void LeBigTerminateSync(uint8_t big_handle);
- bluetooth::hci::ErrorCode LeRequestPeerSca(uint16_t request_handle);
- void LeSetupIsoDataPath(uint16_t connection_handle,
- bluetooth::hci::DataPathDirection data_path_direction,
- uint8_t data_path_id, uint64_t codec_id,
- uint32_t controller_Delay,
- std::vector<uint8_t> codec_configuration);
- void LeRemoveIsoDataPath(
- uint16_t connection_handle,
- bluetooth::hci::DataPathDirection data_path_direction);
-
- void HandleLeEnableEncryption(uint16_t handle, std::array<uint8_t, 8> rand,
- uint16_t ediv, std::array<uint8_t, 16> ltk);
-
- ErrorCode LeEnableEncryption(uint16_t handle, std::array<uint8_t, 8> rand,
- uint16_t ediv, std::array<uint8_t, 16> ltk);
-
- ErrorCode LeLongTermKeyRequestReply(uint16_t handle,
- std::array<uint8_t, 16> ltk);
-
- ErrorCode LeLongTermKeyRequestNegativeReply(uint16_t handle);
-
- ErrorCode SetLeAdvertisingEnable(uint8_t le_advertising_enable);
-
- void LeDisableAdvertisingSets();
-
- uint8_t LeReadNumberOfSupportedAdvertisingSets();
-
- ErrorCode SetLeExtendedAdvertisingEnable(
- bluetooth::hci::Enable enable,
- const std::vector<bluetooth::hci::EnabledSet>& enabled_sets);
-
- bluetooth::hci::OpCode GetLeScanEnable() { return le_scan_enable_; }
+ ErrorCode SetLeAdvertisingEnable(uint8_t le_advertising_enable) {
+ le_advertising_enable_ = le_advertising_enable;
+ // TODO: Check properties and return errors
+ return ErrorCode::SUCCESS;
+ }
void SetLeScanEnable(bluetooth::hci::OpCode enabling_opcode) {
le_scan_enable_ = enabling_opcode;
@@ -260,13 +174,10 @@ class LinkLayerController {
void SetLeFilterDuplicates(uint8_t le_scan_filter_duplicates) {
le_scan_filter_duplicates_ = le_scan_filter_duplicates;
}
- void SetLeAddressType(bluetooth::hci::OwnAddressType le_address_type) {
+ void SetLeAddressType(uint8_t le_address_type) {
le_address_type_ = le_address_type;
}
ErrorCode SetLeConnect(bool le_connect) {
- if (le_connect_ == le_connect) {
- return ErrorCode::COMMAND_DISALLOWED;
- }
le_connect_ = le_connect;
return ErrorCode::SUCCESS;
}
@@ -312,7 +223,7 @@ class LinkLayerController {
ErrorCode ChangeConnectionPacketType(uint16_t handle, uint16_t types);
ErrorCode ChangeConnectionLinkKey(uint16_t handle);
- ErrorCode CentralLinkKey(uint8_t key_flag);
+ ErrorCode MasterLinkKey(uint8_t key_flag);
ErrorCode HoldMode(uint16_t handle, uint16_t hold_mode_max_interval,
uint16_t hold_mode_min_interval);
ErrorCode SniffMode(uint16_t handle, uint16_t sniff_max_interval,
@@ -329,13 +240,6 @@ class LinkLayerController {
uint32_t token_bucket_size,
uint32_t peak_bandwidth, uint32_t access_latency);
ErrorCode WriteLinkSupervisionTimeout(uint16_t handle, uint16_t timeout);
- ErrorCode WriteDefaultLinkPolicySettings(uint16_t settings);
- uint16_t ReadDefaultLinkPolicySettings();
-
- void ReadLocalOobData();
- void ReadLocalOobExtendedData();
-
- void HandleIso(bluetooth::hci::IsoView iso);
protected:
void SendLeLinkLayerPacket(
@@ -343,6 +247,9 @@ class LinkLayerController {
void SendLinkLayerPacket(
std::unique_ptr<model::packets::LinkLayerPacketBuilder> packet);
void IncomingAclPacket(model::packets::LinkLayerPacketView packet);
+ void IncomingAclAckPacket(model::packets::LinkLayerPacketView packet);
+ void IncomingCreateConnectionPacket(
+ model::packets::LinkLayerPacketView packet);
void IncomingDisconnectPacket(model::packets::LinkLayerPacketView packet);
void IncomingEncryptConnection(model::packets::LinkLayerPacketView packet);
void IncomingEncryptConnectionResponse(
@@ -356,33 +263,16 @@ class LinkLayerController {
model::packets::LinkLayerPacketView packet);
void IncomingIoCapabilityNegativeResponsePacket(
model::packets::LinkLayerPacketView packet);
- void IncomingIsoPacket(model::packets::LinkLayerPacketView packet);
- void IncomingIsoConnectionRequestPacket(
- model::packets::LinkLayerPacketView packet);
- void IncomingIsoConnectionResponsePacket(
- model::packets::LinkLayerPacketView packet);
- void IncomingKeypressNotificationPacket(
- model::packets::LinkLayerPacketView packet);
void IncomingLeAdvertisementPacket(
model::packets::LinkLayerPacketView packet);
void IncomingLeConnectPacket(model::packets::LinkLayerPacketView packet);
void IncomingLeConnectCompletePacket(
model::packets::LinkLayerPacketView packet);
- void IncomingLeEncryptConnection(model::packets::LinkLayerPacketView packet);
- void IncomingLeEncryptConnectionResponse(
- model::packets::LinkLayerPacketView packet);
- void IncomingLeReadRemoteFeatures(model::packets::LinkLayerPacketView packet);
- void IncomingLeReadRemoteFeaturesResponse(
- model::packets::LinkLayerPacketView packet);
void IncomingLeScanPacket(model::packets::LinkLayerPacketView packet);
void IncomingLeScanResponsePacket(model::packets::LinkLayerPacketView packet);
void IncomingPagePacket(model::packets::LinkLayerPacketView packet);
void IncomingPageRejectPacket(model::packets::LinkLayerPacketView packet);
void IncomingPageResponsePacket(model::packets::LinkLayerPacketView packet);
- void IncomingPasskeyPacket(model::packets::LinkLayerPacketView packet);
- void IncomingPasskeyFailedPacket(model::packets::LinkLayerPacketView packet);
- void IncomingPinRequestPacket(model::packets::LinkLayerPacketView packet);
- void IncomingPinResponsePacket(model::packets::LinkLayerPacketView packet);
void IncomingReadRemoteLmpFeatures(
model::packets::LinkLayerPacketView packet);
void IncomingReadRemoteLmpFeaturesResponse(
@@ -414,7 +304,7 @@ class LinkLayerController {
// Timing related state
std::vector<AsyncTaskId> controller_events_;
- AsyncTaskId timer_tick_task_{};
+ AsyncTaskId timer_tick_task_;
std::chrono::milliseconds timer_period_ = std::chrono::milliseconds(100);
// Callbacks to schedule tasks.
@@ -424,63 +314,62 @@ class LinkLayerController {
std::function<void(AsyncTaskId)> cancel_task_;
// Callbacks to send packets back to the HCI.
- std::function<void(std::shared_ptr<bluetooth::hci::AclBuilder>)> send_acl_;
- std::function<void(std::shared_ptr<bluetooth::hci::EventBuilder>)>
+ std::function<void(std::shared_ptr<bluetooth::hci::AclPacketBuilder>)>
+ send_acl_;
+ std::function<void(std::shared_ptr<bluetooth::hci::EventPacketBuilder>)>
send_event_;
- std::function<void(std::shared_ptr<bluetooth::hci::ScoBuilder>)> send_sco_;
- std::function<void(std::shared_ptr<bluetooth::hci::IsoBuilder>)> send_iso_;
+ std::function<void(std::shared_ptr<std::vector<uint8_t>>)> send_sco_;
+ std::function<void(std::shared_ptr<std::vector<uint8_t>>)> send_iso_;
// Callback to send packets to remote devices.
std::function<void(std::shared_ptr<model::packets::LinkLayerPacketBuilder>,
Phy::Type phy_type)>
send_to_remote_;
- uint32_t oob_id_ = 1;
- uint32_t key_id_ = 1;
-
// LE state
std::vector<uint8_t> le_event_mask_;
- std::vector<std::tuple<Address, uint8_t>> le_connect_list_;
+ std::vector<std::tuple<Address, uint8_t>> le_white_list_;
std::vector<std::tuple<Address, uint8_t, std::array<uint8_t, kIrk_size>,
std::array<uint8_t, kIrk_size>>>
le_resolving_list_;
- std::array<LeAdvertiser, 3> advertisers_;
+ uint8_t le_advertising_enable_{false};
+ std::chrono::steady_clock::time_point last_le_advertisement_;
bluetooth::hci::OpCode le_scan_enable_{bluetooth::hci::OpCode::NONE};
- uint8_t le_scan_type_{};
- uint16_t le_scan_interval_{};
- uint16_t le_scan_window_{};
- uint8_t le_scan_filter_policy_{};
- uint8_t le_scan_filter_duplicates_{};
- bluetooth::hci::OwnAddressType le_address_type_{};
+ uint8_t le_scan_type_;
+ uint16_t le_scan_interval_;
+ uint16_t le_scan_window_;
+ uint8_t le_scan_filter_policy_;
+ uint8_t le_scan_filter_duplicates_;
+ uint8_t le_address_type_;
bool le_connect_{false};
- uint16_t le_connection_interval_min_{};
- uint16_t le_connection_interval_max_{};
- uint16_t le_connection_latency_{};
- uint16_t le_connection_supervision_timeout_{};
- uint16_t le_connection_minimum_ce_length_{};
- uint16_t le_connection_maximum_ce_length_{};
- uint8_t le_initiator_filter_policy_{};
+ uint16_t le_connection_interval_min_;
+ uint16_t le_connection_interval_max_;
+ uint16_t le_connection_latency_;
+ uint16_t le_connection_supervision_timeout_;
+ uint16_t le_connection_minimum_ce_length_;
+ uint16_t le_connection_maximum_ce_length_;
+ uint8_t le_initiator_filter_policy_;
- Address le_peer_address_{};
- uint8_t le_peer_address_type_{};
+ Address le_peer_address_;
+ uint8_t le_peer_address_type_;
// Classic state
SecurityManager security_manager_{10};
std::chrono::steady_clock::time_point last_inquiry_;
- model::packets::InquiryType inquiry_mode_{
- model::packets::InquiryType::STANDARD};
- AsyncTaskId inquiry_timer_task_id_ = kInvalidTaskId;
- uint64_t inquiry_lap_{};
- uint8_t inquiry_max_responses_{};
- uint16_t default_link_policy_settings_ = 0;
+ model::packets::InquiryType inquiry_mode_;
+ Inquiry::InquiryState inquiry_state_;
+ uint64_t inquiry_lap_;
+ uint8_t inquiry_max_responses_;
bool page_scans_enabled_{false};
bool inquiry_scans_enabled_{false};
+
+ bool simple_pairing_mode_enabled_{false};
};
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/controller/security_manager.cc b/vendor_libs/test_vendor_lib/model/controller/security_manager.cc
index ef4db880c..38b9e64fa 100644
--- a/vendor_libs/test_vendor_lib/model/controller/security_manager.cc
+++ b/vendor_libs/test_vendor_lib/model/controller/security_manager.cc
@@ -63,9 +63,6 @@ void SecurityManager::AuthenticationRequest(const Address& addr, uint16_t handle
authenticating_ = true;
current_handle_ = handle;
peer_address_ = addr;
- peer_pin_requested_ = false;
- peer_pin_received_ = false;
- host_pin_received_ = false;
}
void SecurityManager::AuthenticationRequestFinished() {
@@ -94,7 +91,7 @@ void SecurityManager::SetPeerIoCapability(const Address& addr, uint8_t io_capabi
peer_io_capability_ = IoCapabilityType::INVALID;
peer_capabilities_valid_ = false;
}
- peer_oob_present_flag_ = oob_present_flag;
+ peer_oob_present_flag_ = (oob_present_flag == 1);
if (authentication_requirements <= static_cast<uint8_t>(AuthenticationType::GENERAL_BONDING_MITM)) {
peer_authentication_requirements_ = static_cast<AuthenticationType>(authentication_requirements);
} else {
@@ -108,12 +105,11 @@ void SecurityManager::SetLocalIoCapability(const Address& peer, uint8_t io_capab
ASSERT(peer == peer_address_);
ASSERT_LOG(io_capability <= static_cast<uint8_t>(IoCapabilityType::NO_INPUT_NO_OUTPUT), "io_capability = %d",
static_cast<int>(io_capability));
- ASSERT_LOG(oob_present_flag <= 3, "oob_present_flag = %hhx ",
- oob_present_flag);
+ ASSERT_LOG(oob_present_flag <= 1, "oob_present_flag = %hhx ", oob_present_flag);
ASSERT_LOG(authentication_requirements <= static_cast<uint8_t>(AuthenticationType::GENERAL_BONDING_MITM),
"authentication_requirements = %d", static_cast<int>(authentication_requirements));
host_io_capability_ = static_cast<IoCapabilityType>(io_capability);
- host_oob_present_flag_ = oob_present_flag;
+ host_oob_present_flag_ = (oob_present_flag == 1);
host_authentication_requirements_ = static_cast<AuthenticationType>(authentication_requirements);
host_capabilities_valid_ = true;
}
@@ -133,13 +129,6 @@ PairingType SecurityManager::GetSimplePairingType() {
bool peer_requires_mitm = (peer_authentication_requirements_ == AuthenticationType::NO_BONDING_MITM) ||
(peer_authentication_requirements_ == AuthenticationType::DEDICATED_BONDING_MITM) ||
(peer_authentication_requirements_ == AuthenticationType::GENERAL_BONDING_MITM);
- if (peer_oob_present_flag_ != 0 || host_oob_present_flag_ != 0) {
- if (host_oob_present_flag_ == 0) {
- return PairingType::PEER_HAS_OUT_OF_BAND;
- } else {
- return PairingType::OUT_OF_BAND;
- }
- }
if (!(peer_requires_mitm || host_requires_mitm)) {
return PairingType::AUTO_CONFIRMATION;
}
@@ -156,7 +145,7 @@ PairingType SecurityManager::GetSimplePairingType() {
return PairingType::INPUT_PIN;
case IoCapabilityType::NO_INPUT_NO_OUTPUT:
return PairingType::AUTO_CONFIRMATION;
- case IoCapabilityType::INVALID:
+ default:
return PairingType::INVALID;
}
case IoCapabilityType::DISPLAY_YES_NO:
@@ -166,61 +155,30 @@ PairingType SecurityManager::GetSimplePairingType() {
case IoCapabilityType::DISPLAY_YES_NO:
return PairingType::DISPLAY_AND_CONFIRM;
case IoCapabilityType::KEYBOARD_ONLY:
- return PairingType::INPUT_PIN;
+ return PairingType::DISPLAY_PIN;
case IoCapabilityType::NO_INPUT_NO_OUTPUT:
return PairingType::AUTO_CONFIRMATION;
- case IoCapabilityType::INVALID:
+ default:
return PairingType::INVALID;
}
case IoCapabilityType::KEYBOARD_ONLY:
switch (host_io_capability_) {
case IoCapabilityType::DISPLAY_ONLY:
+ return PairingType::DISPLAY_PIN;
case IoCapabilityType::DISPLAY_YES_NO:
return PairingType::DISPLAY_PIN;
case IoCapabilityType::KEYBOARD_ONLY:
return PairingType::INPUT_PIN;
case IoCapabilityType::NO_INPUT_NO_OUTPUT:
return PairingType::AUTO_CONFIRMATION;
- case IoCapabilityType::INVALID:
+ default:
return PairingType::INVALID;
}
case IoCapabilityType::NO_INPUT_NO_OUTPUT:
return PairingType::AUTO_CONFIRMATION;
- case IoCapabilityType::INVALID:
+ default:
return PairingType::INVALID;
}
}
-void SecurityManager::SetPinRequested(const Address& addr) {
- ASSERT(addr == peer_address_);
- peer_pin_requested_ = true;
-}
-
-bool SecurityManager::GetPinRequested(const Address& addr) {
- return peer_pin_requested_;
-}
-
-void SecurityManager::SetLocalPin(const Address& peer,
- const std::vector<uint8_t>& pin) {
- host_pin_received_ = true;
- host_pin_ = pin;
-}
-
-void SecurityManager::SetRemotePin(const Address& peer,
- const std::vector<uint8_t>& pin) {
- peer_pin_received_ = true;
- peer_pin_ = pin;
-}
-
-bool SecurityManager::GetLocalPinResponseReceived(const Address& peer) {
- return host_pin_received_;
-}
-
-bool SecurityManager::GetRemotePinResponseReceived(const Address& peer) {
- return peer_pin_received_;
-}
-
-bool SecurityManager::PinCompare() {
- return host_pin_received_ && peer_pin_received_ && peer_pin_ == host_pin_;
-}
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/controller/security_manager.h b/vendor_libs/test_vendor_lib/model/controller/security_manager.h
index 738f7e0ff..e77f1d18d 100644
--- a/vendor_libs/test_vendor_lib/model/controller/security_manager.h
+++ b/vendor_libs/test_vendor_lib/model/controller/security_manager.h
@@ -20,7 +20,6 @@
#include <cstdint>
#include <string>
#include <unordered_map>
-#include <vector>
#include "hci/address.h"
@@ -34,8 +33,6 @@ enum class PairingType : uint8_t {
DISPLAY_PIN,
DISPLAY_AND_CONFIRM,
INPUT_PIN,
- OUT_OF_BAND,
- PEER_HAS_OUT_OF_BAND,
INVALID = 0xff,
};
@@ -79,14 +76,6 @@ class SecurityManager {
uint16_t GetAuthenticationHandle();
Address GetAuthenticationAddress();
- void SetPinRequested(const Address& addr);
- bool GetPinRequested(const Address& addr);
- void SetLocalPin(const Address& peer, const std::vector<uint8_t>& pin);
- void SetRemotePin(const Address& peer, const std::vector<uint8_t>& pin);
- bool GetLocalPinResponseReceived(const Address& peer);
- bool GetRemotePinResponseReceived(const Address& peer);
- bool PinCompare();
-
void SetPeerIoCapability(const Address& addr, uint8_t io_capability, uint8_t oob_present_flag,
uint8_t authentication_requirements);
void SetLocalIoCapability(const Address& peer, uint8_t io_capability, uint8_t oob_present_flag,
@@ -101,25 +90,18 @@ class SecurityManager {
std::unordered_map<std::string, std::array<uint8_t, 16>> key_store_;
bool peer_capabilities_valid_{false};
- IoCapabilityType peer_io_capability_{IoCapabilityType::DISPLAY_ONLY};
- uint8_t peer_oob_present_flag_{0};
- AuthenticationType peer_authentication_requirements_{
- AuthenticationType::NO_BONDING};
- bool peer_pin_requested_{false};
- bool peer_pin_received_{false};
- std::vector<uint8_t> peer_pin_;
+ IoCapabilityType peer_io_capability_;
+ bool peer_oob_present_flag_{false};
+ AuthenticationType peer_authentication_requirements_;
bool host_capabilities_valid_{false};
- IoCapabilityType host_io_capability_{IoCapabilityType::DISPLAY_ONLY};
- uint8_t host_oob_present_flag_{0};
- AuthenticationType host_authentication_requirements_{
- AuthenticationType::NO_BONDING};
- std::vector<uint8_t> host_pin_;
- bool host_pin_received_{false};
+ IoCapabilityType host_io_capability_;
+ bool host_oob_present_flag_{false};
+ AuthenticationType host_authentication_requirements_;
bool authenticating_{false};
- uint16_t current_handle_{};
- Address peer_address_{};
+ uint16_t current_handle_;
+ Address peer_address_;
};
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/devices/beacon.cc b/vendor_libs/test_vendor_lib/model/devices/beacon.cc
index c4ac4bdb9..96f6099f4 100644
--- a/vendor_libs/test_vendor_lib/model/devices/beacon.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/beacon.cc
@@ -50,7 +50,7 @@ std::string Beacon::ToString() const {
void Beacon::Initialize(const vector<std::string>& args) {
if (args.size() < 2) return;
- Address addr{};
+ Address addr;
if (Address::FromString(args[1], addr)) properties_.SetLeAddress(addr);
if (args.size() < 3) return;
@@ -70,7 +70,9 @@ void Beacon::TimerTick() {
std::shared_ptr<model::packets::LinkLayerPacketBuilder> to_send =
std::move(ad);
- SendLinkLayerPacket(to_send, Phy::Type::LOW_ENERGY);
+ for (auto phy : phy_layers_[Phy::Type::LOW_ENERGY]) {
+ phy->Send(to_send);
+ }
}
}
@@ -85,7 +87,9 @@ void Beacon::IncomingPacket(model::packets::LinkLayerPacketView packet) {
std::shared_ptr<model::packets::LinkLayerPacketBuilder> to_send =
std::move(scan_response);
- SendLinkLayerPacket(to_send, Phy::Type::LOW_ENERGY);
+ for (auto phy : phy_layers_[Phy::Type::LOW_ENERGY]) {
+ phy->Send(to_send);
+ }
}
}
diff --git a/vendor_libs/test_vendor_lib/model/devices/beacon_swarm.cc b/vendor_libs/test_vendor_lib/model/devices/beacon_swarm.cc
index 17e62ad54..c9f17f143 100644
--- a/vendor_libs/test_vendor_lib/model/devices/beacon_swarm.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/beacon_swarm.cc
@@ -61,7 +61,7 @@ BeaconSwarm::BeaconSwarm() {
void BeaconSwarm::Initialize(const vector<std::string>& args) {
if (args.size() < 2) return;
- Address addr{};
+ Address addr;
if (Address::FromString(args[1], addr)) properties_.SetLeAddress(addr);
if (args.size() < 3) return;
diff --git a/vendor_libs/test_vendor_lib/model/devices/broken_adv.cc b/vendor_libs/test_vendor_lib/model/devices/broken_adv.cc
index 27dc2d105..32c5ebbfe 100644
--- a/vendor_libs/test_vendor_lib/model/devices/broken_adv.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/broken_adv.cc
@@ -51,7 +51,7 @@ BrokenAdv::BrokenAdv() {
void BrokenAdv::Initialize(const vector<std::string>& args) {
if (args.size() < 2) return;
- Address addr{};
+ Address addr;
if (Address::FromString(args[1], addr)) properties_.SetLeAddress(addr);
if (args.size() < 3) return;
diff --git a/vendor_libs/test_vendor_lib/model/devices/car_kit.cc b/vendor_libs/test_vendor_lib/model/devices/car_kit.cc
index 7a0be0d27..65603f1d0 100644
--- a/vendor_libs/test_vendor_lib/model/devices/car_kit.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/car_kit.cc
@@ -24,8 +24,6 @@ using std::vector;
namespace test_vendor_lib {
bool CarKit::registered_ = DeviceBoutique::Register("car_kit", &CarKit::Create);
-const std::string kCarKitPropertiesFile =
- "/etc/bluetooth/car_kit_controller_properties.json";
CarKit::CarKit() : Device(kCarKitPropertiesFile) {
advertising_interval_ms_ = std::chrono::milliseconds(0);
@@ -34,11 +32,10 @@ CarKit::CarKit() : Device(kCarKitPropertiesFile) {
// Stub in packet handling for now
link_layer_controller_.RegisterAclChannel(
- [](std::shared_ptr<bluetooth::hci::AclBuilder>) {});
+ [](std::shared_ptr<bluetooth::hci::AclPacketBuilder>) {});
link_layer_controller_.RegisterEventChannel(
- [](std::shared_ptr<bluetooth::hci::EventBuilder>) {});
- link_layer_controller_.RegisterScoChannel(
- [](std::shared_ptr<bluetooth::hci::ScoBuilder>) {});
+ [](std::shared_ptr<bluetooth::hci::EventPacketBuilder>) {});
+ link_layer_controller_.RegisterScoChannel([](std::shared_ptr<std::vector<uint8_t>>) {});
link_layer_controller_.RegisterRemoteChannel(
[this](std::shared_ptr<model::packets::LinkLayerPacketBuilder> packet,
Phy::Type phy_type) {
@@ -83,7 +80,7 @@ CarKit::CarKit() : Device(kCarKitPropertiesFile) {
void CarKit::Initialize(const vector<std::string>& args) {
if (args.size() < 2) return;
- Address addr{};
+ Address addr;
if (Address::FromString(args[1], addr)) properties_.SetAddress(addr);
LOG_INFO("%s SetAddress %s", ToString().c_str(), addr.ToString().c_str());
diff --git a/vendor_libs/test_vendor_lib/model/devices/car_kit.h b/vendor_libs/test_vendor_lib/model/devices/car_kit.h
index 32fd4311d..f59a2ad51 100644
--- a/vendor_libs/test_vendor_lib/model/devices/car_kit.h
+++ b/vendor_libs/test_vendor_lib/model/devices/car_kit.h
@@ -23,6 +23,10 @@
#include "hci/hci_packets.h"
#include "model/controller/link_layer_controller.h"
+namespace {
+const std::string kCarKitPropertiesFile = "/etc/bluetooth/car_kit_controller_properties.json";
+} // namespace
+
namespace test_vendor_lib {
class CarKit : public Device {
diff --git a/vendor_libs/test_vendor_lib/model/devices/classic.cc b/vendor_libs/test_vendor_lib/model/devices/classic.cc
index def9517cf..e8df43a77 100644
--- a/vendor_libs/test_vendor_lib/model/devices/classic.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/classic.cc
@@ -40,7 +40,7 @@ Classic::Classic() {
void Classic::Initialize(const vector<std::string>& args) {
if (args.size() < 2) return;
- Address addr{};
+ Address addr;
if (Address::FromString(args[1], addr)) properties_.SetAddress(addr);
if (args.size() < 3) return;
diff --git a/vendor_libs/test_vendor_lib/model/devices/device.cc b/vendor_libs/test_vendor_lib/model/devices/device.cc
index f733a84f7..9fdcd5ee4 100644
--- a/vendor_libs/test_vendor_lib/model/devices/device.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/device.cc
@@ -18,6 +18,8 @@
#include "device.h"
+using std::vector;
+
namespace test_vendor_lib {
std::string Device::ToString() const {
@@ -27,25 +29,23 @@ std::string Device::ToString() const {
}
void Device::RegisterPhyLayer(std::shared_ptr<PhyLayer> phy) {
- phy_layers_.push_back(phy);
+ phy_layers_[phy->GetType()].push_back(phy);
}
void Device::UnregisterPhyLayers() {
- for (auto phy : phy_layers_) {
- if (phy != nullptr) {
+ for (auto phy_pair : phy_layers_) {
+ auto phy_list = std::get<1>(phy_pair);
+ for (auto phy : phy_list) {
phy->Unregister();
}
}
- phy_layers_.clear();
}
void Device::UnregisterPhyLayer(Phy::Type phy_type, uint32_t factory_id) {
- for (auto& phy : phy_layers_) {
- if (phy != nullptr && phy->IsFactoryId(factory_id) &&
- phy->GetType() == phy_type) {
- phy->Unregister();
- phy.reset();
- return;
+ for (const auto phy_layer : phy_layers_[phy_type]) {
+ if (phy_layer->IsFactoryId(factory_id)) {
+ phy_layer->Unregister();
+ phy_layers_[phy_type].remove(phy_layer);
}
}
}
@@ -58,19 +58,15 @@ bool Device::IsAdvertisementAvailable() const {
void Device::SendLinkLayerPacket(
std::shared_ptr<model::packets::LinkLayerPacketBuilder> to_send,
Phy::Type phy_type) {
- for (auto phy : phy_layers_) {
- if (phy != nullptr && phy->GetType() == phy_type) {
- phy->Send(to_send);
- }
+ for (auto phy : phy_layers_[phy_type]) {
+ phy->Send(to_send);
}
}
void Device::SendLinkLayerPacket(model::packets::LinkLayerPacketView to_send,
Phy::Type phy_type) {
- for (auto phy : phy_layers_) {
- if (phy != nullptr && phy->GetType() == phy_type) {
- phy->Send(to_send);
- }
+ for (auto phy : phy_layers_[phy_type]) {
+ phy->Send(to_send);
}
}
diff --git a/vendor_libs/test_vendor_lib/model/devices/device.h b/vendor_libs/test_vendor_lib/model/devices/device.h
index c48fc1b92..b9858882f 100644
--- a/vendor_libs/test_vendor_lib/model/devices/device.h
+++ b/vendor_libs/test_vendor_lib/model/devices/device.h
@@ -18,6 +18,7 @@
#include <chrono>
#include <cstdint>
+#include <list>
#include <map>
#include <string>
#include <vector>
@@ -86,16 +87,16 @@ class Device {
Phy::Type phy_type);
protected:
- std::vector<std::shared_ptr<PhyLayer>> phy_layers_;
+ std::map<Phy::Type, std::list<std::shared_ptr<PhyLayer>>> phy_layers_;
std::chrono::steady_clock::time_point last_advertisement_;
// The time between page scans.
- std::chrono::milliseconds page_scan_delay_ms_{};
+ std::chrono::milliseconds page_scan_delay_ms_;
// The spec defines the advertising interval as a 16-bit value, but since it
// is never sent in packets, we use std::chrono::milliseconds.
- std::chrono::milliseconds advertising_interval_ms_{};
+ std::chrono::milliseconds advertising_interval_ms_;
DeviceProperties properties_;
};
diff --git a/vendor_libs/test_vendor_lib/model/devices/device_properties.cc b/vendor_libs/test_vendor_lib/model/devices/device_properties.cc
index 503ad4578..8309268fa 100644
--- a/vendor_libs/test_vendor_lib/model/devices/device_properties.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/device_properties.cc
@@ -1,5 +1,6 @@
/*
* Copyright 2015 The Android Open Source Project
+ *
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
@@ -54,7 +55,7 @@ DeviceProperties::DeviceProperties(const std::string& file_name)
lmp_pal_subversion_(0),
le_data_packet_length_(27),
num_le_data_packets_(15),
- le_connect_list_size_(15),
+ le_white_list_size_(15),
le_resolving_list_size_(15) {
std::string properties_raw;
@@ -65,10 +66,10 @@ DeviceProperties::DeviceProperties(const std::string& file_name)
supported_codecs_ = {0}; // Only SBC is supported.
vendor_specific_codecs_ = {};
- for (int i = 0; i < 35; i++) supported_commands_[i] = 0xff;
+ for (int i = 0; i < 35; i++) supported_commands_.push_back(0xff);
// Mark HCI_LE_Transmitter_Test[v2] and newer commands as unsupported
- // Use SetSupportedComands() to change what's supported.
- for (int i = 35; i < 64; i++) supported_commands_[i] = 0x00;
+ // TODO: Implement a better mapping.
+ for (int i = 35; i < 64; i++) supported_commands_.push_back(0x00);
le_supported_features_ = 0x1f;
le_supported_states_ = 0x3ffffffffff;
@@ -83,17 +84,12 @@ DeviceProperties::DeviceProperties(const std::string& file_name)
return;
}
- auto properties_value = base::JSONReader::Read(properties_raw);
- if (!properties_value) {
- LOG_ERROR(
- "Error controller properties may consist of ill-formed JSON, no "
- "properties read.");
- return;
- }
+ std::unique_ptr<base::Value> properties_value_ptr = base::JSONReader::Read(properties_raw);
+ if (properties_value_ptr.get() == nullptr) LOG_INFO("Error controller properties may consist of ill-formed JSON.");
// Get the underlying base::Value object, which is of type
// base::Value::TYPE_DICTIONARY, and read it into member variables.
- base::Value& properties_dictionary = *properties_value;
+ base::Value& properties_dictionary = *(properties_value_ptr.get());
base::JSONValueConverter<DeviceProperties> converter;
if (!converter.Convert(properties_dictionary, this))
diff --git a/vendor_libs/test_vendor_lib/model/devices/device_properties.h b/vendor_libs/test_vendor_lib/model/devices/device_properties.h
index 968f743c9..960e5d00b 100644
--- a/vendor_libs/test_vendor_lib/model/devices/device_properties.h
+++ b/vendor_libs/test_vendor_lib/model/devices/device_properties.h
@@ -41,14 +41,10 @@ class DeviceProperties {
const std::vector<uint8_t>& GetVersionInformation() const;
// Specification Version 4.2, Volume 2, Part E, Section 7.4.2
- const std::array<uint8_t, 64>& GetSupportedCommands() const {
+ const std::vector<uint8_t>& GetSupportedCommands() const {
return supported_commands_;
}
- void SetSupportedCommands(const std::array<uint8_t, 64>& commands) {
- supported_commands_ = commands;
- }
-
// Specification Version 4.2, Volume 2, Part E, Section 7.4.3
uint64_t GetSupportedFeatures() const {
return extended_features_[0];
@@ -59,35 +55,6 @@ class DeviceProperties {
extended_features_[page_number] = features;
}
- bool GetSecureSimplePairingSupported() const {
- uint64_t ssp_bit = 0x1;
- return extended_features_[1] & ssp_bit;
- }
-
- void SetSecureSimplePairingSupport(bool supported) {
- uint64_t ssp_bit = 0x1;
- extended_features_[1] &= ~ssp_bit;
- if (supported) {
- extended_features_[1] = extended_features_[1] | ssp_bit;
- }
- }
-
- void SetLeHostSupport(bool le_supported) {
- uint64_t le_bit = 0x2;
- extended_features_[1] &= ~le_bit;
- if (le_supported) {
- extended_features_[1] = extended_features_[1] | le_bit;
- }
- }
-
- void SetSecureConnections(bool supported) {
- uint64_t secure_bit = 0x8;
- extended_features_[1] &= ~secure_bit;
- if (supported) {
- extended_features_[1] = extended_features_[1] | secure_bit;
- }
- }
-
// Specification Version 4.2, Volume 2, Part E, Section 7.4.4
uint8_t GetExtendedFeaturesMaximumPageNumber() const {
return extended_features_.size() - 1;
@@ -109,20 +76,6 @@ class DeviceProperties {
uint8_t GetEncryptionKeySize() const { return encryption_key_size_; }
- uint16_t GetVoiceSetting() const { return voice_setting_; }
-
- void SetVoiceSetting(uint16_t voice_setting) {
- voice_setting_ = voice_setting;
- }
-
- uint16_t GetConnectionAcceptTimeout() const {
- return connection_accept_timeout_;
- }
-
- void SetConnectionAcceptTimeout(uint16_t connection_accept_timeout) {
- connection_accept_timeout_ = connection_accept_timeout;
- }
-
uint16_t GetTotalNumAclDataPackets() const {
return num_acl_data_packets_;
}
@@ -225,10 +178,6 @@ class DeviceProperties {
clock_offset_ = offset;
}
- uint64_t GetEventMask() const { return event_mask_; }
-
- void SetEventMask(uint64_t mask) { event_mask_ = mask; }
-
// Low-Energy functions
const Address& GetLeAddress() const {
return le_address_;
@@ -325,25 +274,14 @@ class DeviceProperties {
return le_supported_features_;
}
- // Specification Version 5.2, Volume 4, Part E, Section 7.8.6
- int8_t GetLeAdvertisingPhysicalChannelTxPower() const {
- return le_advertising_physical_channel_tx_power_;
- }
-
void SetLeSupportedFeatures(uint64_t features) {
le_supported_features_ = features;
}
- bool GetLeEventSupported(bluetooth::hci::SubeventCode subevent_code) const {
- return le_event_mask_ & (1u << static_cast<uint64_t>(subevent_code));
- }
-
- uint64_t GetLeEventMask() const { return le_event_mask_; }
-
- void SetLeEventMask(uint64_t mask) { le_event_mask_ = mask; }
-
// Specification Version 4.2, Volume 2, Part E, Section 7.8.14
- uint8_t GetLeConnectListSize() const { return le_connect_list_size_; }
+ uint8_t GetLeWhiteListSize() const {
+ return le_white_list_size_;
+ }
// Specification Version 4.2, Volume 2, Part E, Section 7.8.27
uint64_t GetLeSupportedStates() const {
@@ -371,44 +309,39 @@ class DeviceProperties {
uint8_t lmp_pal_version_;
uint16_t manufacturer_name_;
uint16_t lmp_pal_subversion_;
- uint64_t supported_features_{};
- uint64_t event_mask_{0x00001fffffffffff};
- uint8_t authentication_enable_{};
+ uint64_t supported_features_;
+ uint8_t authentication_enable_;
std::vector<uint8_t> supported_codecs_;
std::vector<uint32_t> vendor_specific_codecs_;
- std::array<uint8_t, 64> supported_commands_;
- std::vector<uint64_t> extended_features_{{0x875b3fd8fe8ffeff, 0x04}};
+ std::vector<uint8_t> supported_commands_;
+ std::vector<uint64_t> extended_features_{{0x875b3fd8fe8ffeff, 0x0f}};
ClassOfDevice class_of_device_{{0, 0, 0}};
std::vector<uint8_t> extended_inquiry_data_;
- std::array<uint8_t, 248> name_{};
- Address address_{};
- uint8_t page_scan_repetition_mode_{};
- uint16_t clock_offset_{};
+ std::array<uint8_t, 248> name_;
+ Address address_;
+ uint8_t page_scan_repetition_mode_;
+ uint16_t clock_offset_;
uint8_t encryption_key_size_{10};
- uint16_t voice_setting_{0x0060};
- uint16_t connection_accept_timeout_{0x7d00};
// Low Energy
uint16_t le_data_packet_length_;
uint8_t num_le_data_packets_;
- uint8_t le_connect_list_size_;
+ uint8_t le_white_list_size_;
uint8_t le_resolving_list_size_;
uint64_t le_supported_features_{0x075b3fd8fe8ffeff};
- int8_t le_advertising_physical_channel_tx_power_{0x00};
uint64_t le_supported_states_;
- uint64_t le_event_mask_{0x01f};
std::vector<uint8_t> le_vendor_cap_;
- Address le_address_{};
- uint8_t le_address_type_{};
-
- uint16_t le_advertising_interval_min_{};
- uint16_t le_advertising_interval_max_{};
- uint8_t le_advertising_own_address_type_{};
- uint8_t le_advertising_peer_address_type_{};
- Address le_advertising_peer_address_{};
- uint8_t le_advertising_channel_map_{};
- uint8_t le_advertising_filter_policy_{};
- uint8_t le_advertisement_type_{};
+ Address le_address_;
+ uint8_t le_address_type_;
+
+ uint16_t le_advertising_interval_min_;
+ uint16_t le_advertising_interval_max_;
+ uint8_t le_advertising_own_address_type_;
+ uint8_t le_advertising_peer_address_type_;
+ Address le_advertising_peer_address_;
+ uint8_t le_advertising_channel_map_;
+ uint8_t le_advertising_filter_policy_;
+ uint8_t le_advertisement_type_;
std::vector<uint8_t> le_advertisement_;
std::vector<uint8_t> le_scan_response_;
};
diff --git a/vendor_libs/test_vendor_lib/model/devices/h4_packetizer.cc b/vendor_libs/test_vendor_lib/model/devices/h4_packetizer.cc
index 721a1f913..6c6969766 100644
--- a/vendor_libs/test_vendor_lib/model/devices/h4_packetizer.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/h4_packetizer.cc
@@ -16,9 +16,8 @@
#include "h4_packetizer.h"
-#include <cerrno>
-
#include <dlfcn.h>
+#include <errno.h>
#include <fcntl.h>
#include <sys/uio.h>
#include <unistd.h>
@@ -26,41 +25,36 @@
#include "os/log.h"
namespace test_vendor_lib {
-size_t H4Packetizer::HciGetPacketLengthForType(PacketType type,
- const uint8_t* preamble) const {
- static const size_t
- packet_length_offset[static_cast<size_t>(PacketType::ISO) + 1] = {
- 0,
- H4Packetizer::COMMAND_LENGTH_OFFSET,
- H4Packetizer::ACL_LENGTH_OFFSET,
- H4Packetizer::SCO_LENGTH_OFFSET,
- H4Packetizer::EVENT_LENGTH_OFFSET,
- H4Packetizer::ISO_LENGTH_OFFSET,
- };
+namespace hci {
+constexpr size_t H4Packetizer::COMMAND_PREAMBLE_SIZE;
+constexpr size_t H4Packetizer::COMMAND_LENGTH_OFFSET;
+constexpr size_t H4Packetizer::ACL_PREAMBLE_SIZE;
+constexpr size_t H4Packetizer::ACL_LENGTH_OFFSET;
+constexpr size_t H4Packetizer::SCO_PREAMBLE_SIZE;
+constexpr size_t H4Packetizer::SCO_LENGTH_OFFSET;
+constexpr size_t H4Packetizer::EVENT_PREAMBLE_SIZE;
+constexpr size_t H4Packetizer::EVENT_LENGTH_OFFSET;
+
+constexpr size_t H4Packetizer::PREAMBLE_SIZE_MAX;
+
+size_t H4Packetizer::HciGetPacketLengthForType(hci::PacketType type, const uint8_t* preamble) {
+ static const size_t packet_length_offset[static_cast<size_t>(hci::PacketType::EVENT) + 1] = {
+ 0,
+ H4Packetizer::COMMAND_LENGTH_OFFSET,
+ H4Packetizer::ACL_LENGTH_OFFSET,
+ H4Packetizer::SCO_LENGTH_OFFSET,
+ H4Packetizer::EVENT_LENGTH_OFFSET,
+ };
size_t offset = packet_length_offset[static_cast<size_t>(type)];
- size_t size = preamble[offset];
- if (type == PacketType::ACL) {
- size |= ((size_t)preamble[offset + 1]) << 8u;
- }
- if (type == PacketType::ISO) {
- size |= ((size_t)preamble[offset + 1] & 0x0fu) << 8u;
- }
- return size;
+ if (type != hci::PacketType::ACL) return preamble[offset];
+ return (((preamble[offset + 1]) << 8) | preamble[offset]);
}
-H4Packetizer::H4Packetizer(int fd, PacketReadCallback command_cb,
- PacketReadCallback event_cb,
- PacketReadCallback acl_cb, PacketReadCallback sco_cb,
- PacketReadCallback iso_cb,
- ClientDisconnectCallback disconnect_cb)
- : uart_fd_(fd),
- command_cb_(std::move(command_cb)),
- event_cb_(std::move(event_cb)),
- acl_cb_(std::move(acl_cb)),
- sco_cb_(std::move(sco_cb)),
- iso_cb_(std::move(iso_cb)),
- disconnect_cb_(std::move(disconnect_cb)) {}
+H4Packetizer::H4Packetizer(int fd, PacketReadCallback command_cb, PacketReadCallback event_cb,
+ PacketReadCallback acl_cb, PacketReadCallback sco_cb, ClientDisconnectCallback disconnect_cb)
+ : uart_fd_(fd), command_cb_(command_cb), event_cb_(event_cb), acl_cb_(acl_cb), sco_cb_(sco_cb),
+ disconnect_cb_(disconnect_cb) {}
size_t H4Packetizer::Send(uint8_t type, const uint8_t* data, size_t length) {
struct iovec iov[] = {{&type, sizeof(type)}, {const_cast<uint8_t*>(data), length}};
@@ -70,131 +64,130 @@ size_t H4Packetizer::Send(uint8_t type, const uint8_t* data, size_t length) {
} while (-1 == ret && EAGAIN == errno);
if (ret == -1) {
- LOG_ERROR("Error writing to UART (%s)", strerror(errno));
+ LOG_ERROR("%s error writing to UART (%s)", __func__, strerror(errno));
} else if (ret < static_cast<ssize_t>(length + 1)) {
- LOG_ERROR("%d / %d bytes written - something went wrong...",
- static_cast<int>(ret), static_cast<int>(length + 1));
+ LOG_ERROR("%s: %d / %d bytes written - something went wrong...", __func__, static_cast<int>(ret),
+ static_cast<int>(length + 1));
}
return ret;
}
void H4Packetizer::OnPacketReady() {
switch (hci_packet_type_) {
- case PacketType::COMMAND:
+ case hci::PacketType::COMMAND:
command_cb_(packet_);
break;
- case PacketType::ACL:
+ case hci::PacketType::ACL:
acl_cb_(packet_);
break;
- case PacketType::SCO:
+ case hci::PacketType::SCO:
sco_cb_(packet_);
break;
- case PacketType::EVENT:
+ case hci::PacketType::EVENT:
event_cb_(packet_);
break;
- case PacketType::ISO:
- iso_cb_(packet_);
- break;
default:
- LOG_ALWAYS_FATAL("Unimplemented packet type %d",
- static_cast<int>(hci_packet_type_));
+ LOG_ALWAYS_FATAL("%s: Unimplemented packet type %d", __func__, static_cast<int>(hci_packet_type_));
}
// Get ready for the next type byte.
- hci_packet_type_ = PacketType::UNKNOWN;
+ hci_packet_type_ = hci::PacketType::UNKNOWN;
}
void H4Packetizer::OnDataReady(int fd) {
- if (disconnected_) return;
- ssize_t bytes_to_read = 0;
- uint8_t* buffer_pointer = nullptr;
-
- static const size_t preamble_size[static_cast<size_t>(PacketType::ISO) + 1] =
- {
- 0,
- H4Packetizer::COMMAND_PREAMBLE_SIZE,
- H4Packetizer::ACL_PREAMBLE_SIZE,
- H4Packetizer::SCO_PREAMBLE_SIZE,
- H4Packetizer::EVENT_PREAMBLE_SIZE,
- H4Packetizer::ISO_PREAMBLE_SIZE,
- };
- switch (state_) {
- case HCI_TYPE:
- bytes_to_read = 1;
- buffer_pointer = &packet_type_;
- break;
- case HCI_PREAMBLE:
- case HCI_PAYLOAD:
- bytes_to_read = packet_.size() - bytes_read_;
- buffer_pointer = packet_.data() + bytes_read_;
- break;
- }
-
- ssize_t bytes_read =
- TEMP_FAILURE_RETRY(read(fd, buffer_pointer, bytes_to_read));
- if (bytes_read == 0) {
- LOG_INFO("remote disconnected!");
- disconnected_ = true;
- disconnect_cb_();
- return;
- } else if (bytes_read < 0) {
- if (errno == EAGAIN) {
- // No data, try again later.
- return;
- } else if (errno == ECONNRESET) {
- // They probably rejected our packet
- disconnected_ = true;
+ if (hci_packet_type_ == hci::PacketType::UNKNOWN) {
+ uint8_t buffer[1] = {0};
+ ssize_t bytes_read = TEMP_FAILURE_RETRY(read(fd, buffer, 1));
+ if (bytes_read == 0) {
+ LOG_INFO("%s: remote disconnected!", __func__);
disconnect_cb_();
return;
- } else {
- LOG_ALWAYS_FATAL(
- "Read error in %s: %s",
- state_ == HCI_TYPE
- ? "HCI_TYPE"
- : state_ == HCI_PREAMBLE ? "HCI_PREAMBLE" : "HCI_PAYLOAD",
- strerror(errno));
+ } else if (bytes_read < 0) {
+ if (errno == EAGAIN) {
+ // No data, try again later.
+ return;
+ } else if (errno == ECONNRESET) {
+ // They probably rejected our packet
+ return;
+ } else {
+ LOG_ALWAYS_FATAL("%s: Read packet type error: %s", __func__, strerror(errno));
+ }
+ } else if (bytes_read > 1) {
+ LOG_ALWAYS_FATAL("%s: More bytes read than expected (%u)!", __func__, static_cast<unsigned int>(bytes_read));
}
- } else if (bytes_read > bytes_to_read) {
- LOG_ALWAYS_FATAL("More bytes read (%u) than expected (%u)!",
- static_cast<int>(bytes_read),
- static_cast<int>(bytes_to_read));
- }
+ hci_packet_type_ = static_cast<hci::PacketType>(buffer[0]);
+ if (hci_packet_type_ != hci::PacketType::ACL && hci_packet_type_ != hci::PacketType::SCO &&
+ hci_packet_type_ != hci::PacketType::COMMAND && hci_packet_type_ != hci::PacketType::EVENT) {
+ LOG_ALWAYS_FATAL("%s: Unimplemented packet type %d", __func__, static_cast<int>(hci_packet_type_));
+ }
+ } else {
+ static const size_t preamble_size[static_cast<size_t>(hci::PacketType::EVENT) + 1] = {
+ 0,
+ H4Packetizer::COMMAND_PREAMBLE_SIZE,
+ H4Packetizer::ACL_PREAMBLE_SIZE,
+ H4Packetizer::SCO_PREAMBLE_SIZE,
+ H4Packetizer::EVENT_PREAMBLE_SIZE,
+ };
- switch (state_) {
- case HCI_TYPE:
- hci_packet_type_ = static_cast<PacketType>(packet_type_);
- if (hci_packet_type_ != PacketType::ACL &&
- hci_packet_type_ != PacketType::SCO &&
- hci_packet_type_ != PacketType::COMMAND &&
- hci_packet_type_ != PacketType::EVENT &&
- hci_packet_type_ != PacketType::ISO) {
- LOG_ALWAYS_FATAL("Unimplemented packet type %hhd", packet_type_);
+ switch (state_) {
+ case HCI_PREAMBLE: {
+ size_t preamble_bytes = preamble_size[static_cast<size_t>(hci_packet_type_)];
+ ssize_t bytes_read = TEMP_FAILURE_RETRY(read(fd, preamble_ + bytes_read_, preamble_bytes - bytes_read_));
+ if (bytes_read == 0) {
+ LOG_ERROR("%s: Will try again to read the header!", __func__);
+ return;
+ }
+ if (bytes_read < 0) {
+ // Ignore temporary failures.
+ if (errno == EAGAIN) {
+ return;
+ }
+ LOG_ALWAYS_FATAL("%s: Read header error: %s", __func__, strerror(errno));
+ }
+ bytes_read_ += bytes_read;
+ if (bytes_read_ == preamble_bytes) {
+ size_t packet_length = HciGetPacketLengthForType(hci_packet_type_, preamble_);
+ packet_.resize(preamble_bytes + packet_length);
+ memcpy(packet_.data(), preamble_, preamble_bytes);
+ bytes_remaining_ = packet_length;
+ if (bytes_remaining_ == 0) {
+ OnPacketReady();
+ state_ = HCI_PREAMBLE;
+ bytes_read_ = 0;
+ } else {
+ state_ = HCI_PAYLOAD;
+ bytes_read_ = 0;
+ }
+ }
+ break;
}
- state_ = HCI_PREAMBLE;
- bytes_read_ = 0;
- packet_.resize(preamble_size[static_cast<size_t>(hci_packet_type_)]);
- break;
- case HCI_PREAMBLE:
- bytes_read_ += bytes_read;
- if (bytes_read_ == packet_.size()) {
- size_t payload_size =
- HciGetPacketLengthForType(hci_packet_type_, packet_.data());
- if (payload_size == 0) {
+
+ case HCI_PAYLOAD: {
+ size_t preamble_bytes = preamble_size[static_cast<size_t>(hci_packet_type_)];
+ ssize_t bytes_read =
+ TEMP_FAILURE_RETRY(read(fd, packet_.data() + preamble_bytes + bytes_read_, bytes_remaining_));
+ if (bytes_read == 0) {
+ LOG_INFO("%s: Will try again to read the payload!", __func__);
+ return;
+ }
+ if (bytes_read < 0) {
+ // Ignore temporary failures.
+ if (errno == EAGAIN) {
+ return;
+ }
+ LOG_ALWAYS_FATAL("%s: Read payload error: %s", __func__, strerror(errno));
+ }
+ bytes_remaining_ -= bytes_read;
+ bytes_read_ += bytes_read;
+ if (bytes_remaining_ == 0) {
OnPacketReady();
- state_ = HCI_TYPE;
- } else {
- packet_.resize(packet_.size() + payload_size);
- state_ = HCI_PAYLOAD;
+ state_ = HCI_PREAMBLE;
+ bytes_read_ = 0;
}
+ break;
}
- break;
- case HCI_PAYLOAD:
- bytes_read_ += bytes_read;
- if (bytes_read_ == packet_.size()) {
- OnPacketReady();
- state_ = HCI_TYPE;
- }
- break;
+ }
}
}
+} // namespace hci
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/devices/h4_packetizer.h b/vendor_libs/test_vendor_lib/model/devices/h4_packetizer.h
index 2f730073a..c8b79176b 100644
--- a/vendor_libs/test_vendor_lib/model/devices/h4_packetizer.h
+++ b/vendor_libs/test_vendor_lib/model/devices/h4_packetizer.h
@@ -19,35 +19,38 @@
#include <functional>
#include <vector>
+#include "hci.h"
#include "hci_protocol.h"
namespace test_vendor_lib {
+namespace hci {
using HciPacketReadyCallback = std::function<void(void)>;
using ClientDisconnectCallback = std::function<void()>;
-enum class PacketType : uint8_t {
- UNKNOWN = 0,
- COMMAND = 1,
- ACL = 2,
- SCO = 3,
- EVENT = 4,
- ISO = 5,
-};
-
class H4Packetizer : public HciProtocol {
public:
- H4Packetizer(int fd, PacketReadCallback command_cb,
- PacketReadCallback event_cb, PacketReadCallback acl_cb,
- PacketReadCallback sco_cb, PacketReadCallback iso_cb,
- ClientDisconnectCallback disconnect_cb);
+ H4Packetizer(int fd, PacketReadCallback command_cb, PacketReadCallback event_cb, PacketReadCallback acl_cb,
+ PacketReadCallback sco_cb, ClientDisconnectCallback disconnect_cb);
- size_t Send(uint8_t type, const uint8_t* data, size_t length) override;
+ size_t Send(uint8_t type, const uint8_t* data, size_t length);
void OnPacketReady();
void OnDataReady(int fd);
+ private:
+ int uart_fd_;
+
+ PacketReadCallback command_cb_;
+ PacketReadCallback event_cb_;
+ PacketReadCallback acl_cb_;
+ PacketReadCallback sco_cb_;
+
+ ClientDisconnectCallback disconnect_cb_;
+
+ hci::PacketType hci_packet_type_{hci::PacketType::UNKNOWN};
+
// 2 bytes for opcode, 1 byte for parameter length (Volume 2, Part E, 5.4.1)
static constexpr size_t COMMAND_PREAMBLE_SIZE = 3;
static constexpr size_t COMMAND_LENGTH_OFFSET = 2;
@@ -65,32 +68,17 @@ class H4Packetizer : public HciProtocol {
static constexpr size_t EVENT_PREAMBLE_SIZE = 2;
static constexpr size_t EVENT_LENGTH_OFFSET = 1;
- // 2 bytes for handle and flags, 12 bits for length (Volume 2, Part E, 5.4.5)
- static constexpr size_t ISO_PREAMBLE_SIZE = 4;
- static constexpr size_t ISO_LENGTH_OFFSET = 2;
-
- private:
- int uart_fd_;
-
- PacketReadCallback command_cb_;
- PacketReadCallback event_cb_;
- PacketReadCallback acl_cb_;
- PacketReadCallback sco_cb_;
- PacketReadCallback iso_cb_;
-
- ClientDisconnectCallback disconnect_cb_;
- bool disconnected_{false};
-
- size_t HciGetPacketLengthForType(PacketType type,
- const uint8_t* preamble) const;
+ static constexpr size_t PREAMBLE_SIZE_MAX = ACL_PREAMBLE_SIZE;
- PacketType hci_packet_type_{PacketType::UNKNOWN};
+ size_t HciGetPacketLengthForType(hci::PacketType type, const uint8_t* preamble);
- enum State { HCI_TYPE, HCI_PREAMBLE, HCI_PAYLOAD };
- State state_{HCI_TYPE};
- uint8_t packet_type_{};
+ enum State { HCI_PREAMBLE, HCI_PAYLOAD };
+ State state_{HCI_PREAMBLE};
+ uint8_t preamble_[PREAMBLE_SIZE_MAX];
std::vector<uint8_t> packet_;
+ size_t bytes_remaining_{0};
size_t bytes_read_{0};
};
+} // namespace hci
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/devices/h4_protocol.cc b/vendor_libs/test_vendor_lib/model/devices/h4_protocol.cc
new file mode 100644
index 000000000..7ba432d99
--- /dev/null
+++ b/vendor_libs/test_vendor_lib/model/devices/h4_protocol.cc
@@ -0,0 +1,105 @@
+//
+// Copyright 2017 The Android Open Source Project
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+
+#include "h4_protocol.h"
+
+#include <errno.h>
+#include <fcntl.h>
+#include <sys/uio.h>
+#include <unistd.h>
+
+#include "os/log.h"
+
+namespace test_vendor_lib {
+namespace hci {
+
+H4Protocol::H4Protocol(int fd, PacketReadCallback command_cb, PacketReadCallback event_cb, PacketReadCallback acl_cb,
+ PacketReadCallback sco_cb)
+ : uart_fd_(fd), command_cb_(command_cb), event_cb_(event_cb), acl_cb_(acl_cb), sco_cb_(sco_cb),
+ hci_packetizer_([this]() {
+ LOG_INFO("in lambda");
+ this->OnPacketReady();
+ }) {}
+
+size_t H4Protocol::Send(uint8_t type, const uint8_t* data, size_t length) {
+ struct iovec iov[] = {{&type, sizeof(type)}, {const_cast<uint8_t*>(data), length}};
+ ssize_t ret = 0;
+ do {
+ ret = TEMP_FAILURE_RETRY(writev(uart_fd_, iov, sizeof(iov) / sizeof(iov[0])));
+ } while (-1 == ret && EAGAIN == errno);
+
+ if (ret == -1) {
+ LOG_ERROR("%s error writing to UART (%s)", __func__, strerror(errno));
+ } else if (ret < static_cast<ssize_t>(length + 1)) {
+ LOG_ERROR("%s: %d / %d bytes written - something went wrong...", __func__, static_cast<int>(ret),
+ static_cast<int>(length + 1));
+ }
+ return ret;
+}
+
+void H4Protocol::OnPacketReady() {
+ LOG_ERROR("%s: before switch", __func__);
+ switch (hci_packet_type_) {
+ case hci::PacketType::COMMAND:
+ command_cb_(hci_packetizer_.GetPacket());
+ break;
+ case hci::PacketType::ACL:
+ acl_cb_(hci_packetizer_.GetPacket());
+ break;
+ case hci::PacketType::SCO:
+ sco_cb_(hci_packetizer_.GetPacket());
+ break;
+ case hci::PacketType::EVENT:
+ event_cb_(hci_packetizer_.GetPacket());
+ break;
+ default:
+ LOG_ALWAYS_FATAL("%s: Unimplemented packet type %d", __func__, static_cast<int>(hci_packet_type_));
+ }
+ // Get ready for the next type byte.
+ hci_packet_type_ = hci::PacketType::UNKNOWN;
+}
+
+void H4Protocol::OnDataReady(int fd) {
+ if (hci_packet_type_ == hci::PacketType::UNKNOWN) {
+ uint8_t buffer[1] = {0};
+ ssize_t bytes_read = TEMP_FAILURE_RETRY(read(fd, buffer, 1));
+ if (bytes_read != 1) {
+ if (bytes_read == 0) {
+ LOG_INFO("%s: Nothing ready, will retry!", __func__);
+ return;
+ } else if (bytes_read < 0) {
+ if (errno == EAGAIN) {
+ // No data, try again later.
+ return;
+ } else {
+ LOG_ALWAYS_FATAL("%s: Read packet type error: %s", __func__, strerror(errno));
+ }
+ } else {
+ LOG_ALWAYS_FATAL("%s: More bytes read than expected (%u)!", __func__, static_cast<unsigned int>(bytes_read));
+ }
+ }
+ hci_packet_type_ = static_cast<hci::PacketType>(buffer[0]);
+ if (hci_packet_type_ != hci::PacketType::ACL && hci_packet_type_ != hci::PacketType::SCO &&
+ hci_packet_type_ != hci::PacketType::COMMAND && hci_packet_type_ != hci::PacketType::EVENT) {
+ LOG_ALWAYS_FATAL("%s: Unimplemented packet type %d", __func__, static_cast<int>(hci_packet_type_));
+ }
+ } else {
+ hci_packetizer_.OnDataReady(fd, hci_packet_type_);
+ }
+}
+
+} // namespace hci
+} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/devices/h4_protocol.h b/vendor_libs/test_vendor_lib/model/devices/h4_protocol.h
new file mode 100644
index 000000000..5e261d5bb
--- /dev/null
+++ b/vendor_libs/test_vendor_lib/model/devices/h4_protocol.h
@@ -0,0 +1,49 @@
+//
+// Copyright 2017 The Android Open Source Project
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+
+#pragma once
+
+#include "hci_protocol.h"
+#include "include/hci.h"
+
+namespace test_vendor_lib {
+namespace hci {
+
+class H4Protocol : public HciProtocol {
+ public:
+ H4Protocol(int fd, PacketReadCallback command_cb, PacketReadCallback event_cb, PacketReadCallback acl_cb,
+ PacketReadCallback sco_cb);
+
+ size_t Send(uint8_t type, const uint8_t* data, size_t length);
+
+ void OnPacketReady();
+
+ void OnDataReady(int fd);
+
+ private:
+ int uart_fd_;
+
+ PacketReadCallback command_cb_;
+ PacketReadCallback event_cb_;
+ PacketReadCallback acl_cb_;
+ PacketReadCallback sco_cb_;
+
+ hci::PacketType hci_packet_type_{hci::PacketType::UNKNOWN};
+ hci::HciPacketizer hci_packetizer_;
+};
+
+} // namespace hci
+} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/devices/hci_packetizer.cc b/vendor_libs/test_vendor_lib/model/devices/hci_packetizer.cc
new file mode 100644
index 000000000..e0c4e4afa
--- /dev/null
+++ b/vendor_libs/test_vendor_lib/model/devices/hci_packetizer.cc
@@ -0,0 +1,128 @@
+//
+// Copyright 2017 The Android Open Source Project
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+
+#include "hci_packetizer.h"
+
+#include <dlfcn.h>
+#include <errno.h>
+#include <fcntl.h>
+#include <unistd.h>
+
+#include "os/log.h"
+
+namespace test_vendor_lib {
+namespace hci {
+constexpr size_t HciPacketizer::COMMAND_PREAMBLE_SIZE;
+constexpr size_t HciPacketizer::COMMAND_LENGTH_OFFSET;
+constexpr size_t HciPacketizer::ACL_PREAMBLE_SIZE;
+constexpr size_t HciPacketizer::ACL_LENGTH_OFFSET;
+constexpr size_t HciPacketizer::SCO_PREAMBLE_SIZE;
+constexpr size_t HciPacketizer::SCO_LENGTH_OFFSET;
+constexpr size_t HciPacketizer::EVENT_PREAMBLE_SIZE;
+constexpr size_t HciPacketizer::EVENT_LENGTH_OFFSET;
+
+constexpr size_t HciPacketizer::PREAMBLE_SIZE_MAX;
+
+size_t HciPacketizer::HciGetPacketLengthForType(hci::PacketType type, const uint8_t* preamble) {
+ static const size_t packet_length_offset[static_cast<size_t>(hci::PacketType::EVENT) + 1] = {
+ 0,
+ HciPacketizer::COMMAND_LENGTH_OFFSET,
+ HciPacketizer::ACL_LENGTH_OFFSET,
+ HciPacketizer::SCO_LENGTH_OFFSET,
+ HciPacketizer::EVENT_LENGTH_OFFSET,
+ };
+
+ size_t offset = packet_length_offset[static_cast<size_t>(type)];
+ if (type != hci::PacketType::ACL) return preamble[offset];
+ return (((preamble[offset + 1]) << 8) | preamble[offset]);
+}
+
+const std::vector<uint8_t>& HciPacketizer::GetPacket() const {
+ return packet_;
+}
+
+void HciPacketizer::OnDataReady(int fd, hci::PacketType packet_type) {
+ static const size_t preamble_size[static_cast<size_t>(hci::PacketType::EVENT) + 1] = {
+ 0,
+ HciPacketizer::COMMAND_PREAMBLE_SIZE,
+ HciPacketizer::ACL_PREAMBLE_SIZE,
+ HciPacketizer::SCO_PREAMBLE_SIZE,
+ HciPacketizer::EVENT_PREAMBLE_SIZE,
+ };
+
+ switch (state_) {
+ case HCI_PREAMBLE: {
+ ssize_t bytes_read = TEMP_FAILURE_RETRY(
+ read(fd, preamble_ + bytes_read_, preamble_size[static_cast<uint8_t>(packet_type)] - bytes_read_));
+ if (bytes_read == 0) {
+ LOG_ERROR("%s: Will try again to read the header!", __func__);
+ return;
+ }
+ if (bytes_read < 0) {
+ // Ignore temporary failures.
+ if (errno == EAGAIN) {
+ return;
+ }
+ LOG_ALWAYS_FATAL("Read header error: %s", strerror(errno));
+ }
+ bytes_read_ += bytes_read;
+ if (bytes_read_ == preamble_size[static_cast<uint8_t>(packet_type)]) {
+ size_t packet_length = HciGetPacketLengthForType(packet_type, preamble_);
+ packet_.resize(preamble_size[static_cast<uint8_t>(packet_type)] + packet_length);
+ memcpy(packet_.data(), preamble_, preamble_size[static_cast<uint8_t>(packet_type)]);
+ LOG_INFO("%s: Read a preamble of size %d length %d %0x %0x %0x", __func__, static_cast<int>(bytes_read_),
+ static_cast<int>(packet_length), preamble_[0], preamble_[1], preamble_[2]);
+ bytes_remaining_ = packet_length;
+ if (bytes_remaining_ == 0) {
+ packet_ready_cb_();
+ state_ = HCI_PREAMBLE;
+ bytes_read_ = 0;
+ } else {
+ state_ = HCI_PAYLOAD;
+ bytes_read_ = 0;
+ }
+ }
+ break;
+ }
+
+ case HCI_PAYLOAD: {
+ ssize_t bytes_read = TEMP_FAILURE_RETRY(
+ read(fd, packet_.data() + preamble_size[static_cast<uint8_t>(packet_type)] + bytes_read_, bytes_remaining_));
+ if (bytes_read == 0) {
+ LOG_INFO("Will try again to read the payload!");
+ return;
+ }
+ if (bytes_read < 0) {
+ // Ignore temporary failures.
+ if (errno == EAGAIN) {
+ return;
+ }
+ LOG_ALWAYS_FATAL("Read payload error: %s", strerror(errno));
+ }
+ bytes_remaining_ -= bytes_read;
+ bytes_read_ += bytes_read;
+ if (bytes_remaining_ == 0) {
+ packet_ready_cb_();
+ state_ = HCI_PREAMBLE;
+ bytes_read_ = 0;
+ }
+ break;
+ }
+ }
+}
+
+} // namespace hci
+} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/devices/hci_packetizer.h b/vendor_libs/test_vendor_lib/model/devices/hci_packetizer.h
new file mode 100644
index 000000000..482300896
--- /dev/null
+++ b/vendor_libs/test_vendor_lib/model/devices/hci_packetizer.h
@@ -0,0 +1,68 @@
+//
+// Copyright 2017 The Android Open Source Project
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+//
+
+#pragma once
+
+#include <functional>
+#include <vector>
+
+#include "include/hci.h"
+
+namespace test_vendor_lib {
+namespace hci {
+
+using HciPacketReadyCallback = std::function<void(void)>;
+
+class HciPacketizer {
+ public:
+ HciPacketizer(HciPacketReadyCallback packet_cb) : packet_ready_cb_(packet_cb){};
+ void OnDataReady(int fd, hci::PacketType packet_type);
+ const std::vector<uint8_t>& GetPacket() const;
+
+ private:
+ // 2 bytes for opcode, 1 byte for parameter length (Volume 2, Part E, 5.4.1)
+ static constexpr size_t COMMAND_PREAMBLE_SIZE = 3;
+ static constexpr size_t COMMAND_LENGTH_OFFSET = 2;
+
+ // 2 bytes for handle, 2 bytes for data length (Volume 2, Part E, 5.4.2)
+ static constexpr size_t ACL_PREAMBLE_SIZE = 4;
+ static constexpr size_t ACL_LENGTH_OFFSET = 2;
+
+ // 2 bytes for handle, 1 byte for data length (Volume 2, Part E, 5.4.3)
+ static constexpr size_t SCO_PREAMBLE_SIZE = 3;
+ static constexpr size_t SCO_LENGTH_OFFSET = 2;
+
+ // 1 byte for event code, 1 byte for parameter length (Volume 2, Part
+ // E, 5.4.4)
+ static constexpr size_t EVENT_PREAMBLE_SIZE = 2;
+ static constexpr size_t EVENT_LENGTH_OFFSET = 1;
+
+ static constexpr size_t PREAMBLE_SIZE_MAX = ACL_PREAMBLE_SIZE;
+
+ size_t HciGetPacketLengthForType(hci::PacketType type, const uint8_t* preamble);
+
+ protected:
+ enum State { HCI_PREAMBLE, HCI_PAYLOAD };
+ State state_{HCI_PREAMBLE};
+ uint8_t preamble_[PREAMBLE_SIZE_MAX];
+ std::vector<uint8_t> packet_;
+ size_t bytes_remaining_{0};
+ size_t bytes_read_{0};
+ HciPacketReadyCallback packet_ready_cb_;
+};
+
+} // namespace hci
+} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/devices/hci_protocol.cc b/vendor_libs/test_vendor_lib/model/devices/hci_protocol.cc
index 30d253054..d2ef535bf 100644
--- a/vendor_libs/test_vendor_lib/model/devices/hci_protocol.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/hci_protocol.cc
@@ -16,6 +16,7 @@
#include "hci_protocol.h"
+#include <assert.h>
#include <errno.h>
#include <fcntl.h>
#include <unistd.h>
@@ -23,6 +24,7 @@
#include "os/log.h"
namespace test_vendor_lib {
+namespace hci {
size_t HciProtocol::WriteSafely(int fd, const uint8_t* data, size_t length) {
size_t transmitted_length = 0;
@@ -47,4 +49,5 @@ size_t HciProtocol::WriteSafely(int fd, const uint8_t* data, size_t length) {
return transmitted_length;
}
+} // namespace hci
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/devices/hci_protocol.h b/vendor_libs/test_vendor_lib/model/devices/hci_protocol.h
index a84961461..3aa76406b 100644
--- a/vendor_libs/test_vendor_lib/model/devices/hci_protocol.h
+++ b/vendor_libs/test_vendor_lib/model/devices/hci_protocol.h
@@ -16,10 +16,11 @@
#pragma once
-#include <functional>
-#include <vector>
+#include "hci.h"
+#include "hci_packetizer.h"
namespace test_vendor_lib {
+namespace hci {
using PacketReadCallback = std::function<void(const std::vector<uint8_t>&)>;
@@ -36,4 +37,5 @@ class HciProtocol {
static size_t WriteSafely(int fd, const uint8_t* data, size_t length);
};
+} // namespace hci
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/devices/hci_socket_device.cc b/vendor_libs/test_vendor_lib/model/devices/hci_socket_device.cc
index c5759ecf8..686571406 100644
--- a/vendor_libs/test_vendor_lib/model/devices/hci_socket_device.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/hci_socket_device.cc
@@ -71,15 +71,13 @@ HciSocketDevice::HciSocketDevice(int file_descriptor) : socket_file_descriptor_(
't',
});
- h4_ = H4Packetizer(
+ h4_ = hci::H4Packetizer(
socket_file_descriptor_,
[this](const std::vector<uint8_t>& raw_command) {
std::shared_ptr<std::vector<uint8_t>> packet_copy = std::make_shared<std::vector<uint8_t>>(raw_command);
HandleCommand(packet_copy);
},
- [](const std::vector<uint8_t>&) {
- LOG_ALWAYS_FATAL("Unexpected Event in HciSocketDevice!");
- },
+ [](const std::vector<uint8_t>&) { LOG_ALWAYS_FATAL("Unexpected Event in HciSocketDevice!"); },
[this](const std::vector<uint8_t>& raw_acl) {
std::shared_ptr<std::vector<uint8_t>> packet_copy = std::make_shared<std::vector<uint8_t>>(raw_acl);
HandleAcl(packet_copy);
@@ -88,29 +86,16 @@ HciSocketDevice::HciSocketDevice(int file_descriptor) : socket_file_descriptor_(
std::shared_ptr<std::vector<uint8_t>> packet_copy = std::make_shared<std::vector<uint8_t>>(raw_sco);
HandleSco(packet_copy);
},
- [this](const std::vector<uint8_t>& raw_iso) {
- std::shared_ptr<std::vector<uint8_t>> packet_copy =
- std::make_shared<std::vector<uint8_t>>(raw_iso);
- HandleIso(packet_copy);
- },
[this]() {
LOG_INFO("HCI socket device disconnected");
- socket_file_descriptor_ = -1;
close_callback_();
});
RegisterEventChannel([this](std::shared_ptr<std::vector<uint8_t>> packet) {
- SendHci(PacketType::EVENT, packet);
- });
- RegisterAclChannel([this](std::shared_ptr<std::vector<uint8_t>> packet) {
- SendHci(PacketType::ACL, packet);
- });
- RegisterScoChannel([this](std::shared_ptr<std::vector<uint8_t>> packet) {
- SendHci(PacketType::SCO, packet);
- });
- RegisterIsoChannel([this](std::shared_ptr<std::vector<uint8_t>> packet) {
- SendHci(PacketType::ISO, packet);
+ SendHci(hci::PacketType::EVENT, packet);
});
+ RegisterAclChannel([this](std::shared_ptr<std::vector<uint8_t>> packet) { SendHci(hci::PacketType::ACL, packet); });
+ RegisterScoChannel([this](std::shared_ptr<std::vector<uint8_t>> packet) { SendHci(hci::PacketType::SCO, packet); });
}
void HciSocketDevice::TimerTick() {
@@ -118,22 +103,25 @@ void HciSocketDevice::TimerTick() {
DualModeController::TimerTick();
}
-void HciSocketDevice::SendHci(
- PacketType packet_type,
- const std::shared_ptr<std::vector<uint8_t>> packet) {
+void HciSocketDevice::SendHci(hci::PacketType packet_type, const std::shared_ptr<std::vector<uint8_t>> packet) {
if (socket_file_descriptor_ == -1) {
- LOG_INFO("Closed socket. Dropping packet of type %d",
- static_cast<int>(packet_type));
+ LOG_INFO("socket_file_descriptor == -1");
return;
}
uint8_t type = static_cast<uint8_t>(packet_type);
- h4_.Send(type, packet->data(), packet->size());
+ int bytes_written;
+ bytes_written = write(socket_file_descriptor_, &type, sizeof(type));
+ if (bytes_written != sizeof(type)) {
+ LOG_WARN("bytes_written %d != sizeof(type)", bytes_written);
+ }
+ bytes_written = write(socket_file_descriptor_, packet->data(), packet->size());
+ if (static_cast<size_t>(bytes_written) != packet->size()) {
+ LOG_WARN("bytes_written %d != packet->size", bytes_written);
+ }
}
void HciSocketDevice::RegisterCloseCallback(std::function<void()> close_callback) {
- if (socket_file_descriptor_ != -1) {
- close_callback_ = close_callback;
- }
+ close_callback_ = close_callback;
}
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/devices/hci_socket_device.h b/vendor_libs/test_vendor_lib/model/devices/hci_socket_device.h
index 285d3123a..0a3bb3b51 100644
--- a/vendor_libs/test_vendor_lib/model/devices/hci_socket_device.h
+++ b/vendor_libs/test_vendor_lib/model/devices/hci_socket_device.h
@@ -22,6 +22,10 @@
#include "model/controller/dual_mode_controller.h"
#include "model/devices/h4_packetizer.h"
+namespace {
+const std::string kHciSocketDevicePropertiesFile = "/etc/bluetooth/hci_socket_device_controller_properties.json";
+} // namespace
+
namespace test_vendor_lib {
class HciSocketDevice : public DualModeController {
@@ -39,20 +43,18 @@ class HciSocketDevice : public DualModeController {
virtual void TimerTick() override;
- void SendHci(PacketType packet_type,
- const std::shared_ptr<std::vector<uint8_t>> packet);
+ void SendHci(hci::PacketType packet_type, const std::shared_ptr<std::vector<uint8_t>> packet);
void RegisterCloseCallback(std::function<void()>);
private:
int socket_file_descriptor_{-1};
- H4Packetizer h4_{socket_file_descriptor_,
- [](const std::vector<uint8_t>&) {},
- [](const std::vector<uint8_t>&) {},
- [](const std::vector<uint8_t>&) {},
- [](const std::vector<uint8_t>&) {},
- [](const std::vector<uint8_t>&) {},
- [] {}};
+ hci::H4Packetizer h4_{socket_file_descriptor_,
+ [](const std::vector<uint8_t>&) {},
+ [](const std::vector<uint8_t>&) {},
+ [](const std::vector<uint8_t>&) {},
+ [](const std::vector<uint8_t>&) {},
+ [] {}};
std::function<void()> close_callback_;
};
diff --git a/vendor_libs/test_vendor_lib/model/devices/keyboard.cc b/vendor_libs/test_vendor_lib/model/devices/keyboard.cc
index f08970437..1244d3ede 100644
--- a/vendor_libs/test_vendor_lib/model/devices/keyboard.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/keyboard.cc
@@ -66,7 +66,7 @@ std::string Keyboard::GetTypeString() const {
void Keyboard::Initialize(const vector<std::string>& args) {
if (args.size() < 2) return;
- Address addr{};
+ Address addr;
if (Address::FromString(args[1], addr)) properties_.SetLeAddress(addr);
if (args.size() < 3) return;
diff --git a/vendor_libs/test_vendor_lib/model/devices/link_layer_socket_device.cc b/vendor_libs/test_vendor_lib/model/devices/link_layer_socket_device.cc
index ca483fe82..ddff51b50 100644
--- a/vendor_libs/test_vendor_lib/model/devices/link_layer_socket_device.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/link_layer_socket_device.cc
@@ -27,40 +27,38 @@ using std::vector;
namespace test_vendor_lib {
LinkLayerSocketDevice::LinkLayerSocketDevice(int socket_fd, Phy::Type phy_type)
- : socket_(socket_fd),
- phy_type_(phy_type),
- size_bytes_(std::make_shared<std::vector<uint8_t>>(kSizeBytes)) {}
+ : socket_(socket_fd), phy_type_(phy_type) {}
void LinkLayerSocketDevice::TimerTick() {
- if (receiving_size_) {
- size_t bytes_received =
- socket_.TryReceive(kSizeBytes, size_bytes_->data() + offset_);
- if (bytes_received < bytes_left_) {
- bytes_left_ -= bytes_received;
- offset_ += bytes_received;
+ if (bytes_left_ == 0) {
+ auto packet_size = std::make_shared<std::vector<uint8_t>>(kSizeBytes);
+
+ size_t bytes_received = socket_.TryReceive(kSizeBytes, packet_size->data());
+ if (bytes_received == 0) {
return;
}
+ ASSERT_LOG(bytes_received == kSizeBytes, "bytes_received == %d", static_cast<int>(bytes_received));
bluetooth::packet::PacketView<bluetooth::packet::kLittleEndian> size(
- {bluetooth::packet::View(size_bytes_, 0, kSizeBytes)});
+ {bluetooth::packet::View(packet_size, 0, kSizeBytes)});
bytes_left_ = size.begin().extract<uint32_t>();
received_ = std::make_shared<std::vector<uint8_t>>(bytes_left_);
offset_ = 0;
- receiving_size_ = false;
}
size_t bytes_received = socket_.TryReceive(bytes_left_, received_->data() + offset_);
- if (bytes_received < bytes_left_) {
- bytes_left_ -= bytes_received;
- offset_ += bytes_received;
+ if (bytes_received == 0) {
return;
}
- bytes_left_ = kSizeBytes;
- offset_ = 0;
- receiving_size_ = true;
- auto packet = model::packets::LinkLayerPacketView::Create(
- bluetooth::packet::PacketView<bluetooth::packet::kLittleEndian>(
- received_));
- ASSERT(packet.IsValid());
- SendLinkLayerPacket(packet, phy_type_);
+ bytes_left_ -= bytes_received;
+ offset_ += bytes_received;
+ if (bytes_left_ == 0) {
+ bluetooth::packet::PacketView<bluetooth::packet::kLittleEndian> packet_view(
+ received_);
+ auto packet = model::packets::LinkLayerPacketView::Create(packet_view);
+ ASSERT(packet.IsValid());
+ SendLinkLayerPacket(packet, phy_type_);
+ offset_ = 0;
+ received_.reset();
+ }
}
void LinkLayerSocketDevice::IncomingPacket(
diff --git a/vendor_libs/test_vendor_lib/model/devices/link_layer_socket_device.h b/vendor_libs/test_vendor_lib/model/devices/link_layer_socket_device.h
index b928df082..564233c76 100644
--- a/vendor_libs/test_vendor_lib/model/devices/link_layer_socket_device.h
+++ b/vendor_libs/test_vendor_lib/model/devices/link_layer_socket_device.h
@@ -52,10 +52,8 @@ class LinkLayerSocketDevice : public Device {
private:
net::PolledSocket socket_;
Phy::Type phy_type_;
- bool receiving_size_{true};
- size_t bytes_left_{kSizeBytes};
- size_t offset_{0};
- std::shared_ptr<std::vector<uint8_t>> size_bytes_;
+ size_t bytes_left_{0};
+ size_t offset_;
std::shared_ptr<std::vector<uint8_t>> received_;
std::vector<model::packets::LinkLayerPacketView> packet_queue_;
};
diff --git a/vendor_libs/test_vendor_lib/model/devices/loopback.cc b/vendor_libs/test_vendor_lib/model/devices/loopback.cc
index c13f95d13..df0c76225 100644
--- a/vendor_libs/test_vendor_lib/model/devices/loopback.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/loopback.cc
@@ -56,7 +56,7 @@ std::string Loopback::ToString() const {
void Loopback::Initialize(const vector<std::string>& args) {
if (args.size() < 2) return;
- Address addr{};
+ Address addr;
if (Address::FromString(args[1], addr)) properties_.SetLeAddress(addr);
if (args.size() < 3) return;
@@ -80,7 +80,10 @@ void Loopback::IncomingPacket(model::packets::LinkLayerPacketView packet) {
std::shared_ptr<model::packets::LinkLayerPacketBuilder> to_send =
std::move(scan_response);
- SendLinkLayerPacket(to_send, Phy::Type::LOW_ENERGY);
+ for (auto phy : phy_layers_[Phy::Type::LOW_ENERGY]) {
+ LOG_INFO("Sending a Scan Response on a Phy");
+ phy->Send(to_send);
+ }
}
}
diff --git a/vendor_libs/test_vendor_lib/model/devices/remote_loopback_device.cc b/vendor_libs/test_vendor_lib/model/devices/remote_loopback_device.cc
index 60f38aa91..db87028e3 100644
--- a/vendor_libs/test_vendor_lib/model/devices/remote_loopback_device.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/remote_loopback_device.cc
@@ -38,7 +38,7 @@ std::string RemoteLoopbackDevice::ToString() const {
void RemoteLoopbackDevice::Initialize(const std::vector<std::string>& args) {
if (args.size() < 2) return;
- Address addr{};
+ Address addr;
if (Address::FromString(args[1], addr)) properties_.SetAddress(addr);
}
diff --git a/vendor_libs/test_vendor_lib/model/devices/scripted_beacon.cc b/vendor_libs/test_vendor_lib/model/devices/scripted_beacon.cc
index 0dacdb756..ffbdd8c46 100644
--- a/vendor_libs/test_vendor_lib/model/devices/scripted_beacon.cc
+++ b/vendor_libs/test_vendor_lib/model/devices/scripted_beacon.cc
@@ -165,12 +165,16 @@ void ScriptedBeacon::TimerTick() {
}
} break;
case PlaybackEvent::PLAYBACK_STARTED: {
+ std::shared_ptr<model::packets::LinkLayerPacketBuilder> to_send;
while (has_time_elapsed(next_ad_.ad_time)) {
auto ad = model::packets::LeAdvertisementBuilder::Create(
next_ad_.address, Address::kEmpty /* Destination */,
model::packets::AddressType::RANDOM,
model::packets::AdvertisementType::ADV_NONCONN_IND, next_ad_.ad);
- SendLinkLayerPacket(std::move(ad), Phy::Type::LOW_ENERGY);
+ to_send = std::move(ad);
+ for (const auto& phy : phy_layers_[Phy::Type::LOW_ENERGY]) {
+ phy->Send(to_send);
+ }
if (packet_num_ < ble_ad_list_.advertisements().size()) {
get_next_advertisement();
} else {
@@ -204,8 +208,12 @@ void ScriptedBeacon::IncomingPacket(
properties_.GetLeAddressType()),
model::packets::AdvertisementType::SCAN_RESPONSE,
properties_.GetLeScanResponse());
+ std::shared_ptr<model::packets::LinkLayerPacketBuilder> to_send =
+ std::move(scan_response);
set_state(PlaybackEvent::SCANNED_ONCE);
- SendLinkLayerPacket(std::move(scan_response), Phy::Type::LOW_ENERGY);
+ for (const auto& phy : phy_layers_[Phy::Type::LOW_ENERGY]) {
+ phy->Send(to_send);
+ }
}
}
}
diff --git a/vendor_libs/test_vendor_lib/model/devices/sniffer.h b/vendor_libs/test_vendor_lib/model/devices/sniffer.h
index 590b182fe..a5c72776c 100644
--- a/vendor_libs/test_vendor_lib/model/devices/sniffer.h
+++ b/vendor_libs/test_vendor_lib/model/devices/sniffer.h
@@ -51,7 +51,7 @@ class Sniffer : public Device {
private:
static bool registered_;
- Address device_to_sniff_{};
+ Address device_to_sniff_;
};
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/setup/async_manager.cc b/vendor_libs/test_vendor_lib/model/setup/async_manager.cc
index 0956f7617..092271dbf 100644
--- a/vendor_libs/test_vendor_lib/model/setup/async_manager.cc
+++ b/vendor_libs/test_vendor_lib/model/setup/async_manager.cc
@@ -119,8 +119,6 @@ class AsyncManager::AsyncFdWatcher {
}
AsyncFdWatcher() = default;
- AsyncFdWatcher(const AsyncFdWatcher&) = delete;
- AsyncFdWatcher& operator=(const AsyncFdWatcher&) = delete;
~AsyncFdWatcher() = default;
@@ -146,6 +144,9 @@ class AsyncManager::AsyncFdWatcher {
}
private:
+ AsyncFdWatcher(const AsyncFdWatcher&) = delete;
+ AsyncFdWatcher& operator=(const AsyncFdWatcher&) = delete;
+
// Make sure to call this with at least one file descriptor ready to be
// watched upon or the thread routine will return immediately
int tryStartThread() {
@@ -261,58 +262,41 @@ class AsyncManager::AsyncFdWatcher {
std::map<int, ReadCallback> watched_shared_fds_;
// A pair of FD to send information to the reading thread
- int notification_listen_fd_{};
- int notification_write_fd_{};
+ int notification_listen_fd_;
+ int notification_write_fd_;
};
// Async task manager implementation
class AsyncManager::AsyncTaskManager {
public:
- AsyncUserId GetNextUserId() { return lastUserId_++; }
-
- AsyncTaskId ExecAsync(AsyncUserId user_id, std::chrono::milliseconds delay,
- const TaskCallback& callback) {
- return scheduleTask(std::make_shared<Task>(
- std::chrono::steady_clock::now() + delay, callback, user_id));
+ AsyncTaskId ExecAsync(std::chrono::milliseconds delay, const TaskCallback& callback) {
+ return scheduleTask(std::make_shared<Task>(std::chrono::steady_clock::now() + delay, callback));
}
- AsyncTaskId ExecAsyncPeriodically(AsyncUserId user_id,
- std::chrono::milliseconds delay,
- std::chrono::milliseconds period,
+ AsyncTaskId ExecAsyncPeriodically(std::chrono::milliseconds delay, std::chrono::milliseconds period,
const TaskCallback& callback) {
- return scheduleTask(std::make_shared<Task>(
- std::chrono::steady_clock::now() + delay, period, callback, user_id));
+ return scheduleTask(std::make_shared<Task>(std::chrono::steady_clock::now() + delay, period, callback));
}
bool CancelAsyncTask(AsyncTaskId async_task_id) {
- // remove task from queue (and task id association) while holding lock
+ // remove task from queue (and task id asociation) while holding lock
std::unique_lock<std::mutex> guard(internal_mutex_);
- return cancel_task_with_lock_held(async_task_id);
- }
-
- bool CancelAsyncTasksFromUser(AsyncUserId user_id) {
- // remove task from queue (and task id association) while holding lock
- std::unique_lock<std::mutex> guard(internal_mutex_);
- if (tasks_by_user_id_.count(user_id) == 0) {
+ if (tasks_by_id.count(async_task_id) == 0) {
return false;
}
- for (auto task : tasks_by_user_id_[user_id]) {
- cancel_task_with_lock_held(task);
- }
- tasks_by_user_id_.erase(user_id);
+ task_queue_.erase(tasks_by_id[async_task_id]);
+ tasks_by_id.erase(async_task_id);
return true;
}
AsyncTaskManager() = default;
- AsyncTaskManager(const AsyncTaskManager&) = delete;
- AsyncTaskManager& operator=(const AsyncTaskManager&) = delete;
~AsyncTaskManager() = default;
int stopThread() {
{
std::unique_lock<std::mutex> guard(internal_mutex_);
- tasks_by_id_.clear();
+ tasks_by_id.clear();
task_queue_.clear();
if (!running_) {
return 0;
@@ -333,22 +317,10 @@ class AsyncManager::AsyncTaskManager {
// Holds the data for each task
class Task {
public:
- Task(std::chrono::steady_clock::time_point time,
- std::chrono::milliseconds period, const TaskCallback& callback,
- AsyncUserId user)
- : time(time),
- periodic(true),
- period(period),
- callback(callback),
- task_id(kInvalidTaskId),
- user_id(user) {}
- Task(std::chrono::steady_clock::time_point time,
- const TaskCallback& callback, AsyncUserId user)
- : time(time),
- periodic(false),
- callback(callback),
- task_id(kInvalidTaskId),
- user_id(user) {}
+ Task(std::chrono::steady_clock::time_point time, std::chrono::milliseconds period, const TaskCallback& callback)
+ : time(time), periodic(true), period(period), callback(callback), task_id(kInvalidTaskId) {}
+ Task(std::chrono::steady_clock::time_point time, const TaskCallback& callback)
+ : time(time), periodic(false), callback(callback), task_id(kInvalidTaskId) {}
// Operators needed to be in a collection
bool operator<(const Task& another) const {
@@ -363,10 +335,9 @@ class AsyncManager::AsyncTaskManager {
// public or gets more complex
std::chrono::steady_clock::time_point time;
bool periodic;
- std::chrono::milliseconds period{};
+ std::chrono::milliseconds period;
TaskCallback callback;
AsyncTaskId task_id;
- AsyncUserId user_id;
};
// A comparator class to put shared pointers to tasks in an ordered set
@@ -376,29 +347,24 @@ class AsyncManager::AsyncTaskManager {
}
};
- bool cancel_task_with_lock_held(AsyncTaskId async_task_id) {
- if (tasks_by_id_.count(async_task_id) == 0) {
- return false;
- }
- task_queue_.erase(tasks_by_id_[async_task_id]);
- tasks_by_id_.erase(async_task_id);
- return true;
- }
+ AsyncTaskManager(const AsyncTaskManager&) = delete;
+ AsyncTaskManager& operator=(const AsyncTaskManager&) = delete;
AsyncTaskId scheduleTask(const std::shared_ptr<Task>& task) {
+ AsyncTaskId task_id = kInvalidTaskId;
{
std::unique_lock<std::mutex> guard(internal_mutex_);
// no more room for new tasks, we need a larger type for IDs
- if (tasks_by_id_.size() == kMaxTaskId) // TODO potentially type unsafe
+ if (tasks_by_id.size() == kMaxTaskId) // TODO potentially type unsafe
return kInvalidTaskId;
do {
lastTaskId_ = NextAsyncTaskId(lastTaskId_);
} while (isTaskIdInUse(lastTaskId_));
task->task_id = lastTaskId_;
// add task to the queue and map
- tasks_by_id_[lastTaskId_] = task;
- tasks_by_user_id_[task->user_id].insert(task->task_id);
+ tasks_by_id[lastTaskId_] = task;
task_queue_.insert(task);
+ task_id = lastTaskId_;
}
// start thread if necessary
int started = tryStartThread();
@@ -409,11 +375,11 @@ class AsyncManager::AsyncTaskManager {
// notify the thread so that it knows of the new task
internal_cond_var_.notify_one();
// return task id
- return task->task_id;
+ return task_id;
}
bool isTaskIdInUse(const AsyncTaskId& task_id) const {
- return tasks_by_id_.count(task_id) != 0;
+ return tasks_by_id.count(task_id) != 0;
}
int tryStartThread() {
@@ -434,7 +400,7 @@ class AsyncManager::AsyncTaskManager {
}
void ThreadRoutine() {
- while (running_) {
+ while (1) {
TaskCallback callback;
bool run_it = false;
{
@@ -450,8 +416,7 @@ class AsyncManager::AsyncTaskManager {
task_p->time += task_p->period;
task_queue_.insert(task_p);
} else {
- tasks_by_user_id_[task_p->user_id].erase(task_p->task_id);
- tasks_by_id_.erase(task_p->task_id);
+ tasks_by_id.erase(task_p->task_id);
}
}
}
@@ -461,19 +426,15 @@ class AsyncManager::AsyncTaskManager {
}
{
std::unique_lock<std::mutex> guard(internal_mutex_);
- // check for termination right before waiting
- if (!running_) break;
- // wait until time for the next task (if any)
+ // wait on condition variable with timeout just in time for next task if
+ // any
if (task_queue_.size() > 0) {
- // Make a copy of the time_point because wait_until takes a reference
- // to it and may read it after waiting, by which time the task may
- // have been freed (e.g. via CancelAsyncTask).
- std::chrono::steady_clock::time_point time =
- (*task_queue_.begin())->time;
- internal_cond_var_.wait_until(guard, time);
+ internal_cond_var_.wait_until(guard, (*task_queue_.begin())->time);
} else {
internal_cond_var_.wait(guard);
}
+ // check for termination right after being notified (and maybe before?)
+ if (!running_) break;
}
}
}
@@ -484,9 +445,7 @@ class AsyncManager::AsyncTaskManager {
std::condition_variable internal_cond_var_;
AsyncTaskId lastTaskId_ = kInvalidTaskId;
- AsyncUserId lastUserId_{1};
- std::map<AsyncTaskId, std::shared_ptr<Task> > tasks_by_id_;
- std::map<AsyncUserId, std::set<AsyncTaskId>> tasks_by_user_id_;
+ std::map<AsyncTaskId, std::shared_ptr<Task> > tasks_by_id;
std::set<std::shared_ptr<Task>, task_p_comparator> task_queue_;
};
@@ -512,32 +471,19 @@ void AsyncManager::StopWatchingFileDescriptor(int file_descriptor) {
fdWatcher_p_->StopWatchingFileDescriptor(file_descriptor);
}
-AsyncUserId AsyncManager::GetNextUserId() {
- return taskManager_p_->GetNextUserId();
-}
-
-AsyncTaskId AsyncManager::ExecAsync(AsyncUserId user_id,
- std::chrono::milliseconds delay,
- const TaskCallback& callback) {
- return taskManager_p_->ExecAsync(user_id, delay, callback);
+AsyncTaskId AsyncManager::ExecAsync(std::chrono::milliseconds delay, const TaskCallback& callback) {
+ return taskManager_p_->ExecAsync(delay, callback);
}
-AsyncTaskId AsyncManager::ExecAsyncPeriodically(
- AsyncUserId user_id, std::chrono::milliseconds delay,
- std::chrono::milliseconds period, const TaskCallback& callback) {
- return taskManager_p_->ExecAsyncPeriodically(user_id, delay, period,
- callback);
+AsyncTaskId AsyncManager::ExecAsyncPeriodically(std::chrono::milliseconds delay, std::chrono::milliseconds period,
+ const TaskCallback& callback) {
+ return taskManager_p_->ExecAsyncPeriodically(delay, period, callback);
}
bool AsyncManager::CancelAsyncTask(AsyncTaskId async_task_id) {
return taskManager_p_->CancelAsyncTask(async_task_id);
}
-bool AsyncManager::CancelAsyncTasksFromUser(
- test_vendor_lib::AsyncUserId user_id) {
- return taskManager_p_->CancelAsyncTasksFromUser(user_id);
-}
-
void AsyncManager::Synchronize(const CriticalCallback& critical) {
std::unique_lock<std::mutex> guard(synchronization_mutex_);
critical();
diff --git a/vendor_libs/test_vendor_lib/model/setup/async_manager.h b/vendor_libs/test_vendor_lib/model/setup/async_manager.h
index 2bcbb69ad..e1ad8888a 100644
--- a/vendor_libs/test_vendor_lib/model/setup/async_manager.h
+++ b/vendor_libs/test_vendor_lib/model/setup/async_manager.h
@@ -20,13 +20,12 @@ using TaskCallback = std::function<void(void)>;
using ReadCallback = std::function<void(int)>;
using CriticalCallback = std::function<void(void)>;
using AsyncTaskId = uint16_t;
-using AsyncUserId = uint16_t;
constexpr uint16_t kInvalidTaskId = 0;
// Manages tasks that should be done in the future. It can watch file
// descriptors to call a given callback when it is certain that a non-blocking
-// read is possible or can call a callback at a specific time (approximately)
-// and (optionally) repeat the call periodically.
+// read is possible or can call a callback at a specific time (aproximately) and
+// (optionally) repeat the call periodically.
// The class is thread safe in the sense that all its member functions can be
// called simultaneously from different concurrent threads. The exception to
// this rule is the class destructor, which is unsafe to call concurrently with
@@ -38,13 +37,12 @@ constexpr uint16_t kInvalidTaskId = 0;
// need of additional synchronization between them. The same applies to task
// callbacks since they also run on a thread of their own, however it is
// possible for a read callback and a task callback to execute at the same time
-// (they are guaranteed to run in different threads) so synchronization is
-// needed to access common state (other than the internal state of the
-// AsyncManager class). While not required, it is strongly recommended to use
-// the Synchronize(const CriticalCallback&) member function to execute code
-// inside critical sections. Callbacks passed to this method on the same
-// AsyncManager object from different threads are granted to *NOT* run
-// concurrently.
+// (they are garanteed to run in different threads) so synchronization is needed
+// to access common state (other than the internal state of the AsyncManager
+// class). While not required, it is strongly recommended to use the
+// Synchronize(const CriticalCallback&) member function to execute code inside
+// critical sections. Callbacks passed to this method on the same AsyncManager
+// object from different threads are granted to *NOT* run concurrently.
class AsyncManager {
public:
// Starts watching a file descriptor in a separate thread. The
@@ -58,49 +56,34 @@ class AsyncManager {
// If the fd was not being watched before the call will be ignored.
void StopWatchingFileDescriptor(int file_descriptor);
- // Get an identifier for the scheduler so that tasks can be cancelled per user
- AsyncUserId GetNextUserId();
-
// Schedules an action to occur in the future. Even if the delay given is not
// positive the callback will be called asynchronously.
- AsyncTaskId ExecAsync(AsyncUserId user_id, std::chrono::milliseconds delay,
- const TaskCallback& callback);
+ AsyncTaskId ExecAsync(std::chrono::milliseconds delay, const TaskCallback& callback);
// Schedules an action to occur periodically in the future. If the delay given
// is not positive the callback will be asynchronously called once for each
// time in the past that it should have been called and then scheduled for
// future times.
- AsyncTaskId ExecAsyncPeriodically(AsyncUserId user_id,
- std::chrono::milliseconds delay,
- std::chrono::milliseconds period,
+ AsyncTaskId ExecAsyncPeriodically(std::chrono::milliseconds delay, std::chrono::milliseconds period,
const TaskCallback& callback);
- // Cancels the/every future occurrence of the action specified by this id. It
- // is guaranteed that the associated callback will not be called after this
+ // Cancels the/every future ocurrence of the action specified by this id. It
+ // is guaranteed that the asociated callback will not be called after this
// method returns (it could be called during the execution of the method).
// The calling thread may block until the scheduling thread acknowledges the
- // cancellation.
+ // cancelation.
bool CancelAsyncTask(AsyncTaskId async_task_id);
- // Cancels the/every future occurrence of the action specified by this id. It
- // is guaranteed that the associated callback will not be called after this
- // method returns (it could be called during the execution of the method).
- // The calling thread may block until the scheduling thread acknowledges the
- // cancellation.
- bool CancelAsyncTasksFromUser(AsyncUserId user_id);
-
// Execs the given code in a synchronized manner. It is guaranteed that code
// given on (possibly)concurrent calls to this member function on the same
// AsyncManager object will never be executed simultaneously. It is the
- // class's user's responsibility to ensure that no calls to Synchronize are
+ // class's user's resposability to ensure that no calls to Synchronize are
// made from inside a CriticalCallback, since that would cause a lock to be
// acquired twice with unpredictable results. It is strongly recommended to
// have very simple CriticalCallbacks, preferably using lambda expressions.
void Synchronize(const CriticalCallback&);
AsyncManager();
- AsyncManager(const AsyncManager&) = delete;
- AsyncManager& operator=(const AsyncManager&) = delete;
~AsyncManager();
@@ -113,7 +96,10 @@ class AsyncManager {
// its own class for clarity purposes.
class AsyncTaskManager;
- // Kept as pointers because we may want to support resetting either without
+ AsyncManager(const AsyncManager&) = delete;
+ AsyncManager& operator=(const AsyncManager&) = delete;
+
+ // Kept as pointers because we may want to support reseting either without
// destroying the other one
std::unique_ptr<AsyncFdWatcher> fdWatcher_p_;
std::unique_ptr<AsyncTaskManager> taskManager_p_;
diff --git a/vendor_libs/test_vendor_lib/model/setup/phy_layer.h b/vendor_libs/test_vendor_lib/model/setup/phy_layer.h
index 00a3067f2..7f0fa3301 100644
--- a/vendor_libs/test_vendor_lib/model/setup/phy_layer.h
+++ b/vendor_libs/test_vendor_lib/model/setup/phy_layer.h
@@ -33,7 +33,7 @@ class PhyLayer {
transmit_to_device_(device_receive) {}
virtual void Send(
- std::shared_ptr<model::packets::LinkLayerPacketBuilder> packet) = 0;
+ const std::shared_ptr<model::packets::LinkLayerPacketBuilder> packet) = 0;
virtual void Send(model::packets::LinkLayerPacketView packet) = 0;
virtual void Receive(model::packets::LinkLayerPacketView packet) = 0;
diff --git a/vendor_libs/test_vendor_lib/model/setup/phy_layer_factory.cc b/vendor_libs/test_vendor_lib/model/setup/phy_layer_factory.cc
index 6fe54429b..b963ce08a 100644
--- a/vendor_libs/test_vendor_lib/model/setup/phy_layer_factory.cc
+++ b/vendor_libs/test_vendor_lib/model/setup/phy_layer_factory.cc
@@ -35,25 +35,18 @@ std::shared_ptr<PhyLayer> PhyLayerFactory::GetPhyLayer(
device_receive,
uint32_t device_id) {
std::shared_ptr<PhyLayer> new_phy = std::make_shared<PhyLayerImpl>(
- phy_type_, next_id_++, device_receive, device_id, this);
+ phy_type_, next_id_++, device_receive, device_id,
+ std::shared_ptr<PhyLayerFactory>(this));
phy_layers_.push_back(new_phy);
return new_phy;
}
void PhyLayerFactory::UnregisterPhyLayer(uint32_t id) {
- for (auto phy : phy_layers_) {
- if (phy->GetId() == id) {
- phy_layers_.remove(phy);
- return;
- }
- }
-}
-
-void PhyLayerFactory::UnregisterAllPhyLayers() {
- while (!phy_layers_.empty()) {
- if (phy_layers_.begin() != phy_layers_.end()) {
- auto id = (*phy_layers_.begin())->GetId();
- UnregisterPhyLayer(id);
+ for (auto it = phy_layers_.begin(); it != phy_layers_.end();) {
+ if ((*it)->GetId() == id) {
+ it = phy_layers_.erase(it);
+ } else {
+ it++;
}
}
}
@@ -114,10 +107,11 @@ PhyLayerImpl::PhyLayerImpl(
Phy::Type phy_type, uint32_t id,
const std::function<void(model::packets::LinkLayerPacketView)>&
device_receive,
- uint32_t device_id, PhyLayerFactory* factory)
+ uint32_t device_id, const std::shared_ptr<PhyLayerFactory> factory)
: PhyLayer(phy_type, id, device_receive, device_id), factory_(factory) {}
PhyLayerImpl::~PhyLayerImpl() {
+ Unregister();
}
void PhyLayerImpl::Send(
diff --git a/vendor_libs/test_vendor_lib/model/setup/phy_layer_factory.h b/vendor_libs/test_vendor_lib/model/setup/phy_layer_factory.h
index a19fdf1a8..7d46733a6 100644
--- a/vendor_libs/test_vendor_lib/model/setup/phy_layer_factory.h
+++ b/vendor_libs/test_vendor_lib/model/setup/phy_layer_factory.h
@@ -16,7 +16,6 @@
#pragma once
-#include <list>
#include <memory>
#include <vector>
@@ -45,21 +44,19 @@ class PhyLayerFactory {
void UnregisterPhyLayer(uint32_t id);
- void UnregisterAllPhyLayers();
-
virtual void TimerTick();
virtual std::string ToString() const;
protected:
virtual void Send(
- std::shared_ptr<model::packets::LinkLayerPacketBuilder> packet,
+ const std::shared_ptr<model::packets::LinkLayerPacketBuilder> packet,
uint32_t id);
virtual void Send(model::packets::LinkLayerPacketView packet, uint32_t id);
private:
Phy::Type phy_type_;
- std::list<std::shared_ptr<PhyLayer>> phy_layers_;
+ std::vector<std::shared_ptr<PhyLayer>> phy_layers_;
uint32_t next_id_{1};
const uint32_t factory_id_;
};
@@ -69,19 +66,22 @@ class PhyLayerImpl : public PhyLayer {
PhyLayerImpl(Phy::Type phy_type, uint32_t id,
const std::function<void(model::packets::LinkLayerPacketView)>&
device_receive,
- uint32_t device_id, PhyLayerFactory* factory);
- ~PhyLayerImpl() override;
+ uint32_t device_id,
+ const std::shared_ptr<PhyLayerFactory> factory);
+ virtual ~PhyLayerImpl() override;
- void Send(
- std::shared_ptr<model::packets::LinkLayerPacketBuilder> packet) override;
+ virtual void Send(
+ const std::shared_ptr<model::packets::LinkLayerPacketBuilder> packet)
+ override;
void Send(model::packets::LinkLayerPacketView packet) override;
void Receive(model::packets::LinkLayerPacketView packet) override;
void Unregister() override;
bool IsFactoryId(uint32_t factory_id) override;
void TimerTick() override;
+ uint32_t device_id_;
private:
- PhyLayerFactory* factory_;
+ std::shared_ptr<PhyLayerFactory> factory_;
};
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/setup/test_channel_transport.cc b/vendor_libs/test_vendor_lib/model/setup/test_channel_transport.cc
index a584b972f..d42bc721c 100644
--- a/vendor_libs/test_vendor_lib/model/setup/test_channel_transport.cc
+++ b/vendor_libs/test_vendor_lib/model/setup/test_channel_transport.cc
@@ -30,7 +30,7 @@ using std::vector;
namespace test_vendor_lib {
int TestChannelTransport::SetUp(int port) {
- struct sockaddr_in listen_address {};
+ struct sockaddr_in listen_address;
socklen_t sockaddr_in_size = sizeof(struct sockaddr_in);
memset(&listen_address, 0, sockaddr_in_size);
@@ -74,17 +74,17 @@ void TestChannelTransport::CleanUp() {
listen_fd_ = -1;
}
-int TestChannelTransport::Accept(int listen_fd) {
- int accept_fd;
+int TestChannelTransport::Accept(int listen_fd_) {
+ int accept_fd = -1;
- OSI_NO_INTR(accept_fd = accept(listen_fd, NULL, NULL));
+ OSI_NO_INTR(accept_fd = accept(listen_fd_, NULL, NULL));
if (accept_fd < 0) {
LOG_INFO("Error accepting test channel connection errno=%d (%s).", errno, strerror(errno));
if (errno != EAGAIN && errno != EWOULDBLOCK) {
- LOG_ERROR("Closing listen_fd (won't try again).");
- close(listen_fd);
+ LOG_ERROR("Closing listen_fd_ (won't try again).");
+ close(listen_fd_);
return -1;
}
}
@@ -99,7 +99,6 @@ void TestChannelTransport::OnCommandReady(int fd, std::function<void(void)> unwa
int bytes_read = read(fd, &command_name_size, 1);
if (bytes_read != 1) {
LOG_INFO("Unexpected (command_name_size) bytes_read: %d != %d", bytes_read, 1);
- close(fd);
}
vector<uint8_t> command_name_raw;
command_name_raw.resize(command_name_size);
@@ -149,10 +148,6 @@ void TestChannelTransport::SendResponse(int fd, const std::string& response) con
uint8_t size_buf[4] = {static_cast<uint8_t>(size & 0xff), static_cast<uint8_t>((size >> 8) & 0xff),
static_cast<uint8_t>((size >> 16) & 0xff), static_cast<uint8_t>((size >> 24) & 0xff)};
int written = write(fd, size_buf, 4);
- if (written == -1 && errno == EBADFD) {
- LOG_WARN("Unable to send a response. EBADFD");
- return;
- }
ASSERT_LOG(written == 4, "What happened? written = %d errno = %d", written, errno);
written = write(fd, response.c_str(), size);
ASSERT_LOG(written == static_cast<int>(size), "What happened? written = %d errno = %d", written, errno);
diff --git a/vendor_libs/test_vendor_lib/model/setup/test_command_handler.cc b/vendor_libs/test_vendor_lib/model/setup/test_command_handler.cc
index 65aba6719..a2b8b2edd 100644
--- a/vendor_libs/test_vendor_lib/model/setup/test_command_handler.cc
+++ b/vendor_libs/test_vendor_lib/model/setup/test_command_handler.cc
@@ -24,7 +24,6 @@
#include "base/files/file_util.h"
#include "base/json/json_reader.h"
-#include "base/strings/string_split.h"
#include "base/values.h"
#include "os/log.h"
@@ -49,7 +48,6 @@ TestCommandHandler::TestCommandHandler(TestModel& test_model) : model_(test_mode
SET_HANDLER("set_timer_period", SetTimerPeriod);
SET_HANDLER("start_timer", StartTimer);
SET_HANDLER("stop_timer", StopTimer);
- SET_HANDLER("reset", Reset);
#undef SET_HANDLER
}
@@ -97,26 +95,6 @@ void TestCommandHandler::HandleCommand(const std::string& name, const vector<std
active_commands_[name](args);
}
-void TestCommandHandler::FromFile(const std::string& file_name) {
- if (file_name.size() == 0) {
- return;
- }
-
- std::string commands_raw;
- if (!base::ReadFileToString(base::FilePath(file_name), &commands_raw)) {
- LOG_ERROR("Error reading commands from file.");
- return;
- }
-
- base::StringPairs command_pairs;
- base::SplitStringIntoKeyValuePairs(commands_raw, ' ', '\n', &command_pairs);
- for (const std::pair<std::string, std::string>& p : command_pairs) {
- auto params = base::SplitString(p.second, " ", base::TRIM_WHITESPACE,
- base::SPLIT_WANT_NONEMPTY);
- HandleCommand(p.first, params);
- }
-}
-
void TestCommandHandler::RegisterSendResponse(const std::function<void(const std::string&)> callback) {
send_response_ = callback;
send_response_("RegisterSendResponse called");
@@ -242,7 +220,7 @@ void TestCommandHandler::SetDeviceAddress(const vector<std::string>& args) {
return;
}
size_t device_id = std::stoi(args[0]);
- Address device_address{};
+ Address device_address;
Address::FromString(args[1], device_address);
model_.SetDeviceAddress(device_id, device_address);
response_string_ = "set_device_address " + args[0];
@@ -256,15 +234,7 @@ void TestCommandHandler::SetTimerPeriod(const vector<std::string>& args) {
LOG_INFO("SetTimerPeriod takes 1 argument");
}
size_t period = std::stoi(args[0]);
- if (period != 0) {
- response_string_ = "set timer period to ";
- response_string_ += args[0];
- model_.SetTimerPeriod(std::chrono::milliseconds(period));
- } else {
- response_string_ = "invalid timer period ";
- response_string_ += args[0];
- }
- send_response_(response_string_);
+ model_.SetTimerPeriod(std::chrono::milliseconds(period));
}
void TestCommandHandler::StartTimer(const vector<std::string>& args) {
@@ -272,8 +242,6 @@ void TestCommandHandler::StartTimer(const vector<std::string>& args) {
LOG_INFO("Unused args: arg[0] = %s", args[0].c_str());
}
model_.StartTimer();
- response_string_ = "timer started";
- send_response_(response_string_);
}
void TestCommandHandler::StopTimer(const vector<std::string>& args) {
@@ -281,17 +249,6 @@ void TestCommandHandler::StopTimer(const vector<std::string>& args) {
LOG_INFO("Unused args: arg[0] = %s", args[0].c_str());
}
model_.StopTimer();
- response_string_ = "timer stopped";
- send_response_(response_string_);
-}
-
-void TestCommandHandler::Reset(const std::vector<std::string>& args) {
- if (args.size() > 0) {
- LOG_INFO("Unused args: arg[0] = %s", args[0].c_str());
- }
- model_.Reset();
- response_string_ = "model reset";
- send_response_(response_string_);
}
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/setup/test_command_handler.h b/vendor_libs/test_vendor_lib/model/setup/test_command_handler.h
index e39ca0c5f..4c62d8476 100644
--- a/vendor_libs/test_vendor_lib/model/setup/test_command_handler.h
+++ b/vendor_libs/test_vendor_lib/model/setup/test_command_handler.h
@@ -40,9 +40,6 @@ class TestCommandHandler {
// Dispatches the action corresponding to the command specified by |name|.
void HandleCommand(const std::string& name, const std::vector<std::string>& args);
- // Dispatches the action from a file
- void FromFile(const std::string& file_name);
-
// Dispatches the action corresponding to the command specified by |name|.
void RegisterSendResponse(const std::function<void(const std::string&)> callback);
@@ -82,8 +79,6 @@ class TestCommandHandler {
void StopTimer(const std::vector<std::string>& args);
- void Reset(const std::vector<std::string>& args);
-
// For manual testing
void AddDefaults();
diff --git a/vendor_libs/test_vendor_lib/model/setup/test_model.cc b/vendor_libs/test_vendor_lib/model/setup/test_model.cc
index 4ac37bdeb..71ef77dbc 100644
--- a/vendor_libs/test_vendor_lib/model/setup/test_model.cc
+++ b/vendor_libs/test_vendor_lib/model/setup/test_model.cc
@@ -37,32 +37,26 @@
#include "base/values.h"
#include "os/log.h"
+#include "osi/include/osi.h"
+
+#include "device_boutique.h"
#include "include/phy.h"
#include "model/devices/hci_socket_device.h"
#include "model/devices/link_layer_socket_device.h"
+using std::vector;
+
namespace test_vendor_lib {
TestModel::TestModel(
- std::function<AsyncUserId()> get_user_id,
- std::function<AsyncTaskId(AsyncUserId, std::chrono::milliseconds,
- const TaskCallback&)>
- event_scheduler,
+ std::function<AsyncTaskId(std::chrono::milliseconds, const TaskCallback&)> event_scheduler,
- std::function<AsyncTaskId(AsyncUserId, std::chrono::milliseconds,
- std::chrono::milliseconds, const TaskCallback&)>
+ std::function<AsyncTaskId(std::chrono::milliseconds, std::chrono::milliseconds, const TaskCallback&)>
periodic_event_scheduler,
- std::function<void(AsyncUserId)> cancel_tasks_from_user,
- std::function<void(AsyncTaskId)> cancel,
- std::function<int(const std::string&, int)> connect_to_remote)
- : get_user_id_(std::move(get_user_id)),
- schedule_task_(std::move(event_scheduler)),
- schedule_periodic_task_(std::move(periodic_event_scheduler)),
- cancel_task_(std::move(cancel)),
- cancel_tasks_from_user_(std::move(cancel_tasks_from_user)),
- connect_to_remote_(std::move(connect_to_remote)) {
- model_user_id_ = get_user_id_();
+ std::function<void(AsyncTaskId)> cancel, std::function<int(const std::string&, int)> connect_to_remote)
+ : schedule_task_(event_scheduler), schedule_periodic_task_(periodic_event_scheduler), cancel_task_(cancel),
+ connect_to_remote_(connect_to_remote) {
// TODO: Remove when registration works!
example_devices_.push_back(std::make_shared<Beacon>());
example_devices_.push_back(std::make_shared<BeaconSwarm>());
@@ -86,9 +80,8 @@ void TestModel::SetTimerPeriod(std::chrono::milliseconds new_period) {
void TestModel::StartTimer() {
LOG_INFO("StartTimer()");
- timer_tick_task_ = schedule_periodic_task_(
- model_user_id_, std::chrono::milliseconds(0), timer_period_,
- [this]() { TestModel::TimerTick(); });
+ timer_tick_task_ =
+ schedule_periodic_task_(std::chrono::milliseconds(0), timer_period_, [this]() { TestModel::TimerTick(); });
}
void TestModel::StopTimer() {
@@ -98,78 +91,75 @@ void TestModel::StopTimer() {
}
size_t TestModel::Add(std::shared_ptr<Device> new_dev) {
- devices_.push_back(std::move(new_dev));
- return devices_.size() - 1;
+ devices_counter_++;
+ devices_[devices_counter_] = new_dev;
+ return devices_counter_;
}
void TestModel::Del(size_t dev_index) {
- if (dev_index >= devices_.size() || devices_[dev_index] == nullptr) {
- LOG_WARN("Unknown device %zu", dev_index);
+ auto device = devices_.find(dev_index);
+ if (device == devices_.end()) {
+ LOG_WARN("Del: can't find device!");
return;
}
- schedule_task_(model_user_id_, std::chrono::milliseconds(0),
- [this, dev_index]() {
- devices_[dev_index]->UnregisterPhyLayers();
- devices_[dev_index] = nullptr;
- });
+ devices_.erase(dev_index);
}
size_t TestModel::AddPhy(Phy::Type phy_type) {
- size_t factory_id = phys_.size();
- phys_.emplace_back(phy_type, factory_id);
- return factory_id;
+ phys_counter_++;
+ std::shared_ptr<PhyLayerFactory> new_phy = std::make_shared<PhyLayerFactory>(phy_type, phys_counter_);
+ phys_[phys_counter_] = new_phy;
+ return phys_counter_;
}
void TestModel::DelPhy(size_t phy_index) {
- if (phy_index >= phys_.size()) {
- LOG_WARN("Unknown phy at index %zu", phy_index);
+ auto phy = phys_.find(phy_index);
+ if (phy == phys_.end()) {
+ LOG_WARN("DelPhy: can't find device!");
return;
}
- schedule_task_(
- model_user_id_, std::chrono::milliseconds(0),
- [this, phy_index]() { phys_[phy_index].UnregisterAllPhyLayers(); });
+ phys_.erase(phy_index);
}
void TestModel::AddDeviceToPhy(size_t dev_index, size_t phy_index) {
- if (dev_index >= devices_.size() || devices_[dev_index] == nullptr) {
- LOG_WARN("Unknown device %zu", dev_index);
+ auto device = devices_.find(dev_index);
+ if (device == devices_.end()) {
+ LOG_WARN("%s: can't find device!", __func__);
return;
}
- if (phy_index >= phys_.size()) {
- LOG_WARN("Can't find phy %zu", phy_index);
+ auto phy = phys_.find(phy_index);
+ if (phy == phys_.end()) {
+ LOG_WARN("%s: can't find phy!", __func__);
return;
}
- auto dev = devices_[dev_index];
- dev->RegisterPhyLayer(phys_[phy_index].GetPhyLayer(
+ auto dev = device->second;
+ dev->RegisterPhyLayer(phy->second->GetPhyLayer(
[dev](model::packets::LinkLayerPacketView packet) {
- dev->IncomingPacket(std::move(packet));
+ dev->IncomingPacket(packet);
},
- dev_index));
+ device->first));
}
void TestModel::DelDeviceFromPhy(size_t dev_index, size_t phy_index) {
- if (dev_index >= devices_.size() || devices_[dev_index] == nullptr) {
- LOG_WARN("Unknown device %zu", dev_index);
+ auto device = devices_.find(dev_index);
+ if (device == devices_.end()) {
+ LOG_WARN("%s: can't find device!", __func__);
return;
}
- if (phy_index >= phys_.size()) {
- LOG_WARN("Can't find phy %zu", phy_index);
+ auto phy = phys_.find(phy_index);
+ if (phy == phys_.end()) {
+ LOG_WARN("%s: can't find phy!", __func__);
return;
}
- schedule_task_(model_user_id_, std::chrono::milliseconds(0),
- [this, dev_index, phy_index]() {
- devices_[dev_index]->UnregisterPhyLayer(
- phys_[phy_index].GetType(),
- phys_[phy_index].GetFactoryId());
- });
+ device->second->UnregisterPhyLayer(phy->second->GetType(), phy->second->GetFactoryId());
}
void TestModel::AddLinkLayerConnection(int socket_fd, Phy::Type phy_type) {
std::shared_ptr<Device> dev = LinkLayerSocketDevice::Create(socket_fd, phy_type);
int index = Add(dev);
- for (size_t i = 0; i < phys_.size(); i++) {
- if (phy_type == phys_[i].GetType()) {
- AddDeviceToPhy(index, i);
+ for (auto& phy : phys_) {
+ if (phy_type == phy.second->GetType()) {
+ AddDeviceToPhy(index, phy.first);
}
}
}
@@ -197,83 +187,62 @@ void TestModel::IncomingHciConnection(int socket_fd) {
dev->Initialize({"IgnoredTypeName", addr});
LOG_INFO("initialized %s", addr.c_str());
- for (size_t i = 0; i < phys_.size(); i++) {
- AddDeviceToPhy(index, i);
+ for (auto& phy : phys_) {
+ AddDeviceToPhy(index, phy.first);
}
- AsyncUserId user_id = get_user_id_();
- dev->RegisterTaskScheduler([user_id, this](std::chrono::milliseconds delay,
- TaskCallback task_callback) {
- return schedule_task_(user_id, delay, std::move(task_callback));
- });
+ dev->RegisterTaskScheduler(schedule_task_);
dev->RegisterTaskCancel(cancel_task_);
- dev->RegisterCloseCallback([this, socket_fd, index, user_id] {
- schedule_task_(user_id, std::chrono::milliseconds(0),
- [this, socket_fd, index, user_id]() {
- OnHciConnectionClosed(socket_fd, index, user_id);
- });
- });
+ dev->RegisterCloseCallback([this, socket_fd, index] { OnHciConnectionClosed(socket_fd, index); });
}
-void TestModel::OnHciConnectionClosed(int socket_fd, size_t index,
- AsyncUserId user_id) {
- if (index >= devices_.size() || devices_[index] == nullptr) {
- LOG_WARN("Unknown device %zu", index);
+void TestModel::OnHciConnectionClosed(int socket_fd, size_t index) {
+ auto device = devices_.find(index);
+ if (device == devices_.end()) {
+ LOG_WARN("OnHciConnectionClosed: can't find device!");
return;
}
int close_result = close(socket_fd);
ASSERT_LOG(close_result == 0, "can't close: %s", strerror(errno));
-
- cancel_tasks_from_user_(user_id);
- devices_[index]->UnregisterPhyLayers();
- devices_[index] = nullptr;
+ device->second->UnregisterPhyLayers();
+ devices_.erase(index);
}
void TestModel::SetDeviceAddress(size_t index, Address address) {
- if (index >= devices_.size() || devices_[index] == nullptr) {
- LOG_WARN("Can't find device %zu", index);
+ auto device = devices_.find(index);
+ if (device == devices_.end()) {
+ LOG_WARN("SetDeviceAddress can't find device!");
return;
}
- devices_[index]->SetAddress(std::move(address));
+ device->second->SetAddress(address);
}
const std::string& TestModel::List() {
list_string_ = "";
list_string_ += " Devices: \r\n";
- for (size_t i = 0; i < devices_.size(); i++) {
- list_string_ += " " + std::to_string(i) + ":";
- if (devices_[i] == nullptr) {
- list_string_ += " deleted \r\n";
- } else {
- list_string_ += devices_[i]->ToString() + " \r\n";
- }
+ for (auto& dev : devices_) {
+ list_string_ += " " + std::to_string(dev.first) + ":";
+ list_string_ += dev.second->ToString() + " \r\n";
}
list_string_ += " Phys: \r\n";
- for (size_t i = 0; i < phys_.size(); i++) {
- list_string_ += " " + std::to_string(i) + ":";
- list_string_ += phys_[i].ToString() + " \r\n";
+ for (auto& phy : phys_) {
+ list_string_ += " " + std::to_string(phy.first) + ":";
+ list_string_ += phy.second->ToString() + " \r\n";
}
return list_string_;
}
void TestModel::TimerTick() {
- for (size_t i = 0; i < devices_.size(); i++) {
- if (devices_[i] != nullptr) {
- devices_[i]->TimerTick();
- }
+ for (auto dev = devices_.begin(); dev != devices_.end();) {
+ auto tmp = dev;
+ dev++;
+ tmp->second->TimerTick();
}
}
void TestModel::Reset() {
StopTimer();
- schedule_task_(model_user_id_, std::chrono::milliseconds(0), [this]() {
- LOG_INFO("Running Reset task");
- for (size_t i = 0; i < devices_.size(); i++) {
- if (devices_[i] != nullptr) {
- devices_[i]->UnregisterPhyLayers();
- }
- }
- devices_.clear();
- });
+ devices_.clear();
+ phys_.clear();
}
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/model/setup/test_model.h b/vendor_libs/test_vendor_lib/model/setup/test_model.h
index 718ffa2cf..d651f5072 100644
--- a/vendor_libs/test_vendor_lib/model/setup/test_model.h
+++ b/vendor_libs/test_vendor_lib/model/setup/test_model.h
@@ -32,22 +32,12 @@ namespace test_vendor_lib {
class TestModel {
public:
- TestModel(
- std::function<AsyncUserId()> getNextUserId,
- std::function<AsyncTaskId(AsyncUserId, std::chrono::milliseconds,
- const TaskCallback&)>
- evtScheduler,
- std::function<AsyncTaskId(AsyncUserId, std::chrono::milliseconds,
- std::chrono::milliseconds, const TaskCallback&)>
- periodicEvtScheduler,
- std::function<void(AsyncUserId)> cancel_user_tasks,
- std::function<void(AsyncTaskId)> cancel,
- std::function<int(const std::string&, int)> connect_to_remote);
+ TestModel(std::function<AsyncTaskId(std::chrono::milliseconds, const TaskCallback&)> evtScheduler,
+ std::function<AsyncTaskId(std::chrono::milliseconds, std::chrono::milliseconds, const TaskCallback&)>
+ periodicEvtScheduler,
+ std::function<void(AsyncTaskId)> cancel, std::function<int(const std::string&, int)> connect_to_remote);
~TestModel() = default;
- TestModel(TestModel& model) = delete;
- TestModel& operator=(const TestModel& model) = delete;
-
// Commands:
// Add a device, return its index
@@ -74,7 +64,7 @@ class TestModel {
void IncomingHciConnection(int socket_fd);
// Handle closed remote connections
- void OnHciConnectionClosed(int socket_fd, size_t index, AsyncUserId user_id);
+ void OnHciConnectionClosed(int socket_fd, size_t index);
// Connect to a remote device
void AddRemote(const std::string& server, int port, Phy::Type phy_type);
@@ -95,25 +85,24 @@ class TestModel {
void Reset();
private:
- std::vector<PhyLayerFactory> phys_;
- std::vector<std::shared_ptr<Device>> devices_;
+ std::map<size_t, std::shared_ptr<PhyLayerFactory>> phys_;
+ size_t phys_counter_ = 0;
+ std::map<size_t, std::shared_ptr<Device>> devices_;
+ size_t devices_counter_ = 0;
std::string list_string_;
// Callbacks to schedule tasks.
- std::function<AsyncUserId()> get_user_id_;
- std::function<AsyncTaskId(AsyncUserId, std::chrono::milliseconds,
- const TaskCallback&)>
- schedule_task_;
- std::function<AsyncTaskId(AsyncUserId, std::chrono::milliseconds,
- std::chrono::milliseconds, const TaskCallback&)>
+ std::function<AsyncTaskId(std::chrono::milliseconds, const TaskCallback&)> schedule_task_;
+ std::function<AsyncTaskId(std::chrono::milliseconds, std::chrono::milliseconds, const TaskCallback&)>
schedule_periodic_task_;
std::function<void(AsyncTaskId)> cancel_task_;
- std::function<void(AsyncUserId)> cancel_tasks_from_user_;
std::function<int(const std::string&, int)> connect_to_remote_;
- AsyncUserId model_user_id_;
AsyncTaskId timer_tick_task_{kInvalidTaskId};
- std::chrono::milliseconds timer_period_{};
+ std::chrono::milliseconds timer_period_;
+
+ TestModel(TestModel& model) = delete;
+ TestModel& operator=(const TestModel& model) = delete;
std::vector<std::shared_ptr<Device>> example_devices_;
};
diff --git a/vendor_libs/test_vendor_lib/packets/link_layer_packets.pdl b/vendor_libs/test_vendor_lib/packets/link_layer_packets.pdl
index 0bd600d36..2d601cdac 100644
--- a/vendor_libs/test_vendor_lib/packets/link_layer_packets.pdl
+++ b/vendor_libs/test_vendor_lib/packets/link_layer_packets.pdl
@@ -36,20 +36,8 @@ enum PacketType : 8 {
REMOTE_NAME_REQUEST = 0x1D,
REMOTE_NAME_REQUEST_RESPONSE = 0x1E,
SCO = 0x1F,
- LE_ENCRYPT_CONNECTION = 0x20,
- LE_ENCRYPT_CONNECTION_RESPONSE = 0x21,
- ISO = 0x22,
- ISO_CONNECTION_REQUEST = 0x23,
- ISO_CONNECTION_RESPONSE = 0x24,
- OOB_DATA = 0x25,
- OOB_DATA_RESPONSE = 0x26,
- PASSKEY = 0x27,
- PASSKEY_FAILED = 0x28,
- KEYPRESS_NOTIFICATION = 0x29,
- PIN_REQUEST = 0x2A,
- PIN_RESPONSE = 0x2B,
- LE_READ_REMOTE_FEATURES = 0x2C,
- LE_READ_REMOTE_FEATURES_RESPONSE = 0x2D,
+ COMMAND = 0x23, // Remove
+ RESPONSE = 0x24, // Remove
}
packet LinkLayerPacket {
@@ -59,7 +47,16 @@ packet LinkLayerPacket {
_body_,
}
-packet Acl : LinkLayerPacket (type = ACL) {
+packet Command : LinkLayerPacket (type = COMMAND) {
+ _payload_,
+}
+
+packet Response : LinkLayerPacket (type = RESPONSE) {
+ opcode : 16,
+ _payload_,
+}
+
+packet AclPacket : LinkLayerPacket (type = ACL) {
_payload_,
}
@@ -237,127 +234,3 @@ packet ScoPacket : LinkLayerPacket (type = SCO) {
_payload_,
}
-packet LeEncryptConnection : LinkLayerPacket (type = LE_ENCRYPT_CONNECTION) {
- rand : 8[8],
- ediv : 16,
- ltk : 8[16],
-}
-
-packet LeEncryptConnectionResponse : LinkLayerPacket (type = LE_ENCRYPT_CONNECTION_RESPONSE) {
- rand : 8[8],
- ediv : 16,
- ltk : 8[16],
-}
-
-enum StartContinuation : 1 {
- START = 0,
- CONTINUATION = 1,
-}
-
-enum Complete : 1 {
- INCOMPLETE = 0,
- COMPLETE = 1,
-}
-
-packet IsoDataPacket : LinkLayerPacket (type = ISO) {
- handle : 12,
- _reserved_ : 4,
- sc : StartContinuation,
- cmplt : Complete,
- _reserved_ : 6,
- _size_(_payload_) : 16,
- _payload_,
-}
-
-packet IsoStart : IsoDataPacket (sc = START) {
- time_offset : 24,
- _payload_,
-}
-
-packet IsoContinuation : IsoDataPacket (sc = CONTINUATION) {
- _payload_,
-}
-
-packet IsoConnectionRequest : LinkLayerPacket (type = ISO_CONNECTION_REQUEST) {
- // Group
- cig_id : 8,
- sdu_interval_m_to_s : 32,
- sdu_interval_s_to_m : 32,
- interleaved : 1,
- framed : 1,
- _reserved_ : 6,
- latency_m_to_s : 16,
- latency_s_to_m : 16,
- // Stream parameters
- id : 8,
- max_sdu_m_to_s_ : 16,
- max_sdu_s_to_m_ : 16,
- // For the response
- requester_cis_handle : 12,
- _reserved_ : 4,
- requester_acl_handle : 12,
- _reserved_ : 4,
-}
-
-packet IsoConnectionResponse : LinkLayerPacket (type = ISO_CONNECTION_RESPONSE){
- status : 8, // ErrorCode (SUCCESS == connected)
- requester_cis_handle : 12,
- _reserved_ : 4,
- requester_acl_handle : 12,
- _reserved_ : 4,
- // For the link layer
- responder_cis_handle : 12,
- _reserved_ : 4,
-}
-
-packet OobData : LinkLayerPacket (type = OOB_DATA){
- c_p_194 : 8[16],
- r_p_194 : 8[16],
- c_p_256 : 8[16],
- r_p_256 : 8[16],
-}
-
-packet OobDataResponse : LinkLayerPacket (type = OOB_DATA_RESPONSE){
- matched : 1,
- _reserved_ : 7,
-}
-
-enum PasskeyNotificationType : 8 {
- ENTRY_STARTED = 0x00,
- DIGIT_ENTERED = 0x01,
- DIGIT_ERASED = 0x02,
- CLEARED = 0x03,
- ENTRY_COMPLETED = 0x04,
-}
-
-packet Passkey : LinkLayerPacket (type = PASSKEY){
- passkey : 20,
- _reserved_ : 4,
-}
-
-packet PasskeyFailed : LinkLayerPacket (type = PASSKEY_FAILED){
-}
-
-packet KeypressNotification : LinkLayerPacket (type = KEYPRESS_NOTIFICATION){
- notification_type : PasskeyNotificationType,
-}
-
-packet PinRequest : LinkLayerPacket (type = PIN_REQUEST) {
- _size_(pin_code) : 5, // 0x01 - 0x10
- _reserved_ : 3,
- pin_code : 8[], // string parameter, first octet first
-}
-
-packet PinResponse : LinkLayerPacket (type = PIN_RESPONSE) {
- _size_(pin_code) : 5, // 0x01 - 0x10
- _reserved_ : 3,
- pin_code : 8[], // string parameter, first octet first
-}
-
-packet LeReadRemoteFeatures : LinkLayerPacket (type = LE_READ_REMOTE_FEATURES) {
-}
-
-packet LeReadRemoteFeaturesResponse : LinkLayerPacket (type = LE_READ_REMOTE_FEATURES_RESPONSE) {
- features : 64,
- status : 8,
-}
diff --git a/vendor_libs/test_vendor_lib/scripts/hci_socket.py b/vendor_libs/test_vendor_lib/scripts/hci_socket.py
index 427b8d406..6833eeb8f 100644
--- a/vendor_libs/test_vendor_lib/scripts/hci_socket.py
+++ b/vendor_libs/test_vendor_lib/scripts/hci_socket.py
@@ -69,7 +69,6 @@ import string
import struct
import sys
from scapy.all import *
-import time
""" Add some more SCAPY stuff"""
@@ -201,10 +200,15 @@ class HCI_Event_Extended_Inquiry_Result(Packet):
bind_layers(HCI_Event_Hdr, HCI_Event_Inquiry_Result, code=0x02)
bind_layers(HCI_Event_Hdr, HCI_Event_Connection_Complete, code=0x03)
bind_layers(HCI_Event_Hdr, HCI_Event_Remote_Name_Request_Complete, code=0x07)
-bind_layers(HCI_Event_Hdr, HCI_Event_Read_Remote_Supported_Features_Complete, code=0x0b)
-bind_layers(HCI_Event_Hdr, HCI_Event_Read_Remote_Version_Information_Complete, code=0x0c)
+bind_layers(
+ HCI_Event_Hdr, HCI_Event_Read_Remote_Supported_Features_Complete, code=0x0b)
+bind_layers(
+ HCI_Event_Hdr,
+ HCI_Event_Read_Remote_Version_Information_Complete,
+ code=0x0c)
bind_layers(HCI_Event_Hdr, HCI_Event_Read_Clock_Offset_Complete, code=0x1c)
-bind_layers(HCI_Event_Hdr, HCI_Event_Read_Remote_Extended_Features_Complete, code=0x23)
+bind_layers(
+ HCI_Event_Hdr, HCI_Event_Read_Remote_Extended_Features_Complete, code=0x23)
bind_layers(HCI_Event_Hdr, HCI_Event_Extended_Inquiry_Result, code=0x2f)
""" END SCAPY stuff"""
@@ -268,7 +272,8 @@ class HCISocket(SuperSocket):
self.done_ = True
print('Rx: type_byte ' + hex(type_byte[0]))
# Read the Payload
- payload = self.rx_bytes(payload_length) if payload_length != 0 else b''
+ payload = self.rx_bytes(
+ payload_length) if payload_length != 0 else b''
packet_bytes = type_byte + header + payload
packet = HCI_Hdr(packet_bytes)
print('Rx: ' + packet.__repr__())
@@ -307,7 +312,8 @@ class HCIShell(cmd.Cmd):
address = split_args[0] if len(split_args) > 0 else 'NULL'
timeout = int(split_args[1]) if len(split_args) > 1 else 2
num_responses = 0
- connect = HCI_Hdr(type='Command') / HCI_Command_Hdr(opcode=0x0405) / HCI_Cmd_Create_Connection(addr=address)
+ connect = HCI_Hdr(type='Command') / HCI_Command_Hdr(
+ opcode=0x0405) / HCI_Cmd_Create_Connection(addr=address)
self._hci.send(connect)
status = None
while status == None:
@@ -327,13 +333,16 @@ class HCIShell(cmd.Cmd):
connection_complete = self._hci.get_packet()
if connection_complete == False:
continue
- if (connection_complete[HCI_Hdr].type == HCI_Hdr(type='Event').type) and (
- connection_complete[HCI_Event_Hdr].code == 0x3):
- status = connection_complete[HCI_Event_Connection_Complete].status
+ if (connection_complete[HCI_Hdr].type == HCI_Hdr(type='Event').type
+ ) and (connection_complete[HCI_Event_Hdr].code == 0x3):
+ status = connection_complete[
+ HCI_Event_Connection_Complete].status
if status != 0:
- print('Connection complete with failed status = ' + str(status))
+ print('Connection complete with failed status = ' +
+ str(status))
return
- handle = connection_complete[HCI_Event_Connection_Complete].handle
+ handle = connection_complete[
+ HCI_Event_Connection_Complete].handle
print('Connection established with handle ' + str(handle))
connection_complete.show()
hexdump(connection_complete)
@@ -343,17 +352,31 @@ class HCIShell(cmd.Cmd):
l2cap_req = self._hci.get_packet()
if l2cap_req == False:
continue
- if (l2cap_req[HCI_Hdr].type == HCI_Hdr(type='ACL Data').type) and (l2cap_req[L2CAP_Hdr].cid == L2CAP_Hdr(
- cid='control').cid) and (l2cap_req[L2CAP_CmdHdr].code == L2CAP_CmdHdr(code='info_req').code) and (
- l2cap_req[L2CAP_InfoReq].type == L2CAP_InfoReq(type='FEAT_MASK').type):
- print('Send Features packet' +
- HCI_Hdr(type='ACL Data') / HCI_ACL_Hdr(handle=l2cap_req[HCI_ACL_Hdr].handle, PB=0, BC=2, len=16) /
- L2CAP_Hdr(len=12, cid='control') / L2CAP_CmdHdr(code='info_resp', id=146, len=8) / L2CAP_InfoResp(
- type=l2cap_req[L2CAP_InfoResp].type, result='success', data=b'\xb8\x00\x00\x00').__repr__())
+ if (l2cap_req[HCI_Hdr].type == HCI_Hdr(type='ACL Data').type) and (
+ l2cap_req[L2CAP_Hdr].cid == L2CAP_Hdr(cid='control').cid
+ ) and (l2cap_req[L2CAP_CmdHdr].code == L2CAP_CmdHdr(code='info_req')
+ .code) and (l2cap_req[L2CAP_InfoReq].type == L2CAP_InfoReq(
+ type='FEAT_MASK').type):
+ print('Send Features packet' + HCI_Hdr(
+ type='ACL Data'
+ ) / HCI_ACL_Hdr(
+ handle=l2cap_req[HCI_ACL_Hdr].handle, PB=0, BC=2, len=16) /
+ L2CAP_Hdr(len=12, cid='control') / L2CAP_CmdHdr(
+ code='info_resp', id=146, len=8) / L2CAP_InfoResp(
+ type=l2cap_req[L2CAP_InfoResp].type,
+ result='success',
+ data=b'\xb8\x00\x00\x00').__repr__())
self._hci.send(
- HCI_Hdr(type='ACL Data') / HCI_ACL_Hdr(handle=l2cap_req[HCI_ACL_Hdr].handle, PB=0, BC=2, len=16) /
- L2CAP_Hdr(len=12, cid='control') / L2CAP_CmdHdr(code='info_resp', id=146, len=8) / L2CAP_InfoResp(
- type=l2cap_req[L2CAP_InfoResp].type, result='success', data=b'\xb8\x00\x00\x00'))
+ HCI_Hdr(type='ACL Data') / HCI_ACL_Hdr(
+ handle=l2cap_req[HCI_ACL_Hdr].handle,
+ PB=0,
+ BC=2,
+ len=16) /
+ L2CAP_Hdr(len=12, cid='control') / L2CAP_CmdHdr(
+ code='info_resp', id=146, len=8) / L2CAP_InfoResp(
+ type=l2cap_req[L2CAP_InfoResp].type,
+ result='success',
+ data=b'\xb8\x00\x00\x00'))
def do_le_scan(self, args):
"""Arguments: enable (0 or 1), filter duplicates (0 or 1) Print the scan responses from reachable devices
@@ -362,11 +385,9 @@ class HCIShell(cmd.Cmd):
split_args = args.split()
enable = int(split_args[0]) if len(split_args) > 0 else 1
filter_dups = int(split_args[1]) if len(split_args) > 1 else 1
- set_scan_parameters = HCI_Hdr(type=1) / HCI_Command_Hdr(opcode=0x200b) / HCI_Cmd_LE_Set_Scan_Parameters(type=1)
- print('Tx: ' + set_scan_parameters.__repr__())
- self._hci.send(set_scan_parameters)
- set_scan_enable = HCI_Hdr(type=1) / HCI_Command_Hdr(opcode=0x200c) / HCI_Cmd_LE_Set_Scan_Enable(
- enable=enable, filter_dups=filter_dups)
+ set_scan_enable = HCI_Hdr(type=1) / HCI_Command_Hdr(
+ opcode=0x200c) / HCI_Cmd_LE_Set_Scan_Enable(
+ enable=enable, filter_dups=filter_dups)
print('Tx: ' + set_scan_enable.__repr__())
self._hci.send(set_scan_enable)
@@ -378,17 +399,12 @@ class HCIShell(cmd.Cmd):
scan_time = int(split_args[0]) if len(split_args) > 0 else 0
max_responses = int(split_args[1]) if len(split_args) > 1 else 0
num_responses = 0
- inquiry = HCI_Hdr(type='Command') / HCI_Command_Hdr(opcode=0x0401) / HCI_Cmd_Inquiry(
- length=scan_time, max_responses=max_responses)
+ inquiry = HCI_Hdr(type='Command') / HCI_Command_Hdr(
+ opcode=0x0401) / HCI_Cmd_Inquiry(
+ length=scan_time, max_responses=max_responses)
print('Tx: ' + inquiry.__repr__())
self._hci.send(inquiry)
- def do_wait(self, args):
- """Arguments: time in seconds (float).
- """
- sleep_time = float(args.split()[0])
- time.sleep(sleep_time)
-
def do_quit(self, args):
"""Arguments: None.
@@ -425,7 +441,8 @@ def main(argv):
else:
hci_shell = HCIShell(hci)
hci_shell.prompt = '$ '
- hci_shell.cmdloop('Welcome to the RootCanal HCI Console \n' + 'Type \'help\' for more information.')
+ hci_shell.cmdloop('Welcome to the RootCanal HCI Console \n' +
+ 'Type \'help\' for more information.')
if __name__ == '__main__':
diff --git a/vendor_libs/test_vendor_lib/scripts/link_layer_socket.py b/vendor_libs/test_vendor_lib/scripts/link_layer_socket.py
index d1268e928..e9779cb6d 100644
--- a/vendor_libs/test_vendor_lib/scripts/link_layer_socket.py
+++ b/vendor_libs/test_vendor_lib/scripts/link_layer_socket.py
@@ -92,7 +92,8 @@ class LinkLayerSocket(object):
while not self.done_:
raw_bytes = b''
while len(raw_bytes) < size and not self.done_:
- more_raw_bytes = self._socket.recv(min(size - len(raw_bytes), 2048))
+ more_raw_bytes = self._socket.recv(
+ min(size - len(raw_bytes), 2048))
if more_raw_bytes:
raw_bytes += more_raw_bytes
return raw_bytes
@@ -109,12 +110,15 @@ class LinkLayerSocket(object):
payload_length |= header[2] << 16
payload_length |= header[3] << 24
print('Rx: type_byte ' + hex(header[4]))
- print('Rx: from ' + hex(header[5]) + ':' + hex(header[6]) + ':' + hex(header[7]) + ':' + hex(header[8]) +
- ':' + hex(header[9]) + ':' + hex(header[10]))
- print('Rx: to ' + hex(header[11]) + ':' + hex(header[12]) + ':' + hex(header[13]) + ':' + hex(header[14]) +
- ':' + hex(header[15]) + ':' + hex(header[16]))
+ print('Rx: from ' + hex(header[5]) + ':' + hex(header[6]) + ':' +
+ hex(header[7]) + ':' + hex(header[8]) + ':' + hex(header[9]) +
+ ':' + hex(header[10]))
+ print('Rx: to ' + hex(header[11]) + ':' + hex(header[12]) + ':' +
+ hex(header[13]) + ':' + hex(header[14]) + ':' +
+ hex(header[15]) + ':' + hex(header[16]))
# Read the Payload
- payload = self.rx_bytes(payload_length) if payload_length != 0 else b''
+ payload = self.rx_bytes(
+ payload_length) if payload_length != 0 else b''
packet_bytes = header + payload
self.packets_.put(packet_bytes)
@@ -187,8 +191,9 @@ def main(argv):
else:
link_layer_shell = LinkLayerShell(link_layer)
link_layer_shell.prompt = '$ '
- link_layer_shell.cmdloop('Welcome to the RootCanal LinkLayer Console \n' +
- 'Type \'help\' for more information.')
+ link_layer_shell.cmdloop(
+ 'Welcome to the RootCanal LinkLayer Console \n' +
+ 'Type \'help\' for more information.')
if __name__ == '__main__':
diff --git a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/Readme.txt b/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/Readme.txt
deleted file mode 100644
index 2c25da764..000000000
--- a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/Readme.txt
+++ /dev/null
@@ -1,11 +0,0 @@
-This test:
-
-- Starts RootCanal
-- Adds scripted beacons
-- Sets the permissions for some of the files
-- Dumps the proto output for manual verification
-
-
-cd $ANDROID_BUILD_TOP/system/bt/vendor_libs/test_vendor_lib
-. scripts/scripted_beacon_test/run_test.sh
-
diff --git a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/add_beacons b/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/add_beacons
deleted file mode 100644
index e6ebf6855..000000000
--- a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/add_beacons
+++ /dev/null
@@ -1,10 +0,0 @@
-wait 1
-add scripted_beacon be:ac:01:55:00:01 scripts/scripted_beacon_test/test_events.pb /tmp/logs/scripted_beacon_test/beacon.pb
-add_device_to_phy 1 1
-add scripted_beacon be:ac:01:55:00:02 scripts/scripted_beacon_test/no_permission.pb /tmp/logs/scripted_beacon_test/no_permission.pb
-add_device_to_phy 2 1
-add scripted_beacon be:ac:01:55:00:02 scripts/scripted_beacon_test/grant_permission.pb /tmp/logs/scripted_beacon_test/grant_permission.pb
-add_device_to_phy 3 1
-list
-wait 10
-quit
diff --git a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/grant_permission.pb b/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/grant_permission.pb
deleted file mode 100644
index 0e065d749..000000000
--- a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/grant_permission.pb
+++ /dev/null
@@ -1,21 +0,0 @@
-
-
- oýoýè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoý ªªªªªªªªªªªªªªª ªªª è \ No newline at end of file
diff --git a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/no_permission.pb b/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/no_permission.pb
deleted file mode 100644
index 0e065d749..000000000
--- a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/no_permission.pb
+++ /dev/null
@@ -1,21 +0,0 @@
-
-
- oýoýè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoý ªªªªªªªªªªªªªªª ªªª è \ No newline at end of file
diff --git a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/run_test.sh b/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/run_test.sh
deleted file mode 100644
index 3cededbf5..000000000
--- a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/run_test.sh
+++ /dev/null
@@ -1,17 +0,0 @@
-
-mkdir -p /tmp/logs/scripted_beacon_test/
-chmod 200 scripts/scripted_beacon_test/no_permission.pb
-chmod 200 scripts/scripted_beacon_test/grant_permission.pb
-# ls -l scripts/scripted_beacon_test/*.pb
-$ANDROID_BUILD_TOP/out/host/linux-x86/bin/root-canal 2> /tmp/logs/scripted_beacon_test/root_canal.log &
-sleep 1
-python3 scripts/test_channel.py 6401 < scripts/scripted_beacon_test/add_beacons > /tmp/logs/scripted_beacon_test/test_channel.log &
-python3 scripts/hci_socket.py 6402 < scripts/scripted_beacon_test/start_scan > /tmp/logs/scripted_beacon_test/hci_device.log &
-sleep 5
-chmod 640 scripts/scripted_beacon_test/grant_permission.pb
-# ls -l scripts/scripted_beacon_test/*.pb
-sleep 15
-echo "Done"
-chmod 640 scripts/scripted_beacon_test/no_permission.pb
-# ls -l scripts/scripted_beacon_test/*.pb
-gqui /tmp/logs/scripted_beacon_test/*.pb
diff --git a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/start_scan b/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/start_scan
deleted file mode 100644
index e34583565..000000000
--- a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/start_scan
+++ /dev/null
@@ -1,3 +0,0 @@
-le_scan 1
-wait 10
-quit
diff --git a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/test_events.pb b/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/test_events.pb
deleted file mode 100644
index 0e065d749..000000000
--- a/vendor_libs/test_vendor_lib/scripts/scripted_beacon_test/test_events.pb
+++ /dev/null
@@ -1,21 +0,0 @@
-
-
- oýoýè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoýªªªªªªªªªªªªªªªªªªè
-,
-oýoý ªªªªªªªªªªªªªªª ªªª è \ No newline at end of file
diff --git a/vendor_libs/test_vendor_lib/scripts/send_simple_commands.py b/vendor_libs/test_vendor_lib/scripts/send_simple_commands.py
index 72f3e18c8..b7b0670f8 100644
--- a/vendor_libs/test_vendor_lib/scripts/send_simple_commands.py
+++ b/vendor_libs/test_vendor_lib/scripts/send_simple_commands.py
@@ -212,7 +212,8 @@ def main(argv):
else:
raw_port_shell = RawPortShell(raw_port)
raw_port_shell.prompt = '$ '
- raw_port_shell.cmdloop('Welcome to the RootCanal Console \n' + 'Type \'help\' for more information.')
+ raw_port_shell.cmdloop('Welcome to the RootCanal Console \n' +
+ 'Type \'help\' for more information.')
if __name__ == '__main__':
diff --git a/vendor_libs/test_vendor_lib/scripts/simple_link_layer_socket.py b/vendor_libs/test_vendor_lib/scripts/simple_link_layer_socket.py
index 5ce2a3594..89552d9ea 100644
--- a/vendor_libs/test_vendor_lib/scripts/simple_link_layer_socket.py
+++ b/vendor_libs/test_vendor_lib/scripts/simple_link_layer_socket.py
@@ -189,7 +189,8 @@ def main(argv):
else:
raw_port_shell = RawPortShell(raw_port)
raw_port_shell.prompt = '$ '
- raw_port_shell.cmdloop('Welcome to the RootCanal Console \n' + 'Type \'help\' for more information.')
+ raw_port_shell.cmdloop('Welcome to the RootCanal Console \n' +
+ 'Type \'help\' for more information.')
if __name__ == '__main__':
diff --git a/vendor_libs/test_vendor_lib/scripts/simple_stack.py b/vendor_libs/test_vendor_lib/scripts/simple_stack.py
index 5139c50bc..52472e9e7 100644
--- a/vendor_libs/test_vendor_lib/scripts/simple_stack.py
+++ b/vendor_libs/test_vendor_lib/scripts/simple_stack.py
@@ -230,7 +230,8 @@ def main(argv):
else:
raw_port_shell = RawPortShell(raw_port)
raw_port_shell.prompt = "$ "
- raw_port_shell.cmdloop("Welcome to the RootCanal Console \n" + 'Type \'help\' for more information.')
+ raw_port_shell.cmdloop("Welcome to the RootCanal Console \n" +
+ 'Type \'help\' for more information.')
if __name__ == "__main__":
diff --git a/vendor_libs/test_vendor_lib/scripts/test_channel.py b/vendor_libs/test_vendor_lib/scripts/test_channel.py
index bca358c72..79b19b1bb 100644
--- a/vendor_libs/test_vendor_lib/scripts/test_channel.py
+++ b/vendor_libs/test_vendor_lib/scripts/test_channel.py
@@ -42,7 +42,6 @@ import socket
import string
import struct
import sys
-import time
DEVICE_NAME_LENGTH = 6
DEVICE_ADDRESS_LENGTH = 6
@@ -74,7 +73,7 @@ class Connection(object):
self._socket.close()
def send(self, data):
- self._socket.sendall(data.encode())
+ self._socket.sendall(data)
def receive(self, size):
return self._socket.recv(size)
@@ -101,35 +100,37 @@ class TestChannel(object):
args_size = len(args)
self.lint_command(name, args, name_size, args_size)
encoded_name = chr(name_size) + name
- encoded_args = chr(args_size) + ''.join(chr(len(arg)) + arg for arg in args)
+ encoded_args = chr(args_size) + ''.join(
+ chr(len(arg)) + arg for arg in args)
command = encoded_name + encoded_args
if self._closed:
return
self._connection.send(command)
if name != 'CLOSE_TEST_CHANNEL':
- print(self.receive_response().decode())
+ print self.receive_response()
def receive_response(self):
if self._closed:
- return b'Closed'
+ return
size_chars = self._connection.receive(4)
size_bytes = bytearray(size_chars)
if not size_chars:
- return b'No response, assuming that the connection is broken'
+ print 'No response, assuming that the connection is broken'
+ return False
response_size = 0
for i in range(0, len(size_chars) - 1):
- response_size |= (size_chars[i] << (8 * i))
+ response_size |= ord(size_chars[i]) << (8 * i)
response = self._connection.receive(response_size)
return response
def lint_command(self, name, args, name_size, args_size):
assert name_size == len(name) and args_size == len(args)
try:
- name.encode()
+ name.encode('utf-8')
for arg in args:
- arg.encode()
+ arg.encode('utf-8')
except UnicodeError:
- print('Unrecognized characters.')
+ print 'Unrecognized characters.'
raise
if name_size > 255 or args_size > 255:
raise ValueError # Size must be encodable in one octet.
@@ -220,43 +221,6 @@ class TestChannelShell(cmd.Cmd):
"""
self._test_channel.send_command('list', args.split())
- def do_set_timer_period(self, args):
- """Arguments: period_ms Set the timer to fire every period_ms milliseconds
- """
- self._test_channel.send_command('set_timer_period', args.split())
-
- def do_start_timer(self, args):
- """Arguments: None. Start the timer.
- """
- self._test_channel.send_command('start_timer', args.split())
-
- def do_stop_timer(self, args):
- """Arguments: None. Stop the timer.
- """
- self._test_channel.send_command('stop_timer', args.split())
-
- def do_wait(self, args):
- """Arguments: time in seconds (float).
- """
- sleep_time = float(args.split()[0])
- time.sleep(sleep_time)
-
- def do_reset(self, args):
- """Arguments: None.
-
- Resets the simulation.
- """
- self._test_channel.send_command('reset', [])
-
- def do_end(self, args):
- """Arguments: None.
-
- Ends the simulation and exits.
- """
- self._test_channel.send_command('END_SIMULATION', [])
- print('Goodbye.')
- return True
-
def do_quit(self, args):
"""Arguments: None.
@@ -264,7 +228,7 @@ class TestChannelShell(cmd.Cmd):
"""
self._test_channel.send_command('CLOSE_TEST_CHANNEL', [])
self._test_channel.close()
- print('Goodbye.')
+ print 'Goodbye.'
return True
def do_help(self, args):
@@ -300,23 +264,24 @@ class TestChannelShell(cmd.Cmd):
def main(argv):
if len(argv) != 2:
- print('Usage: python test_channel.py [port]')
+ print 'Usage: python test_channel.py [port]'
return
try:
port = int(argv[1])
except ValueError:
- print('Error parsing port.')
+ print 'Error parsing port.'
else:
try:
test_channel = TestChannel(port)
- except socket.error as e:
- print('Error connecting to socket: %s' % e)
+ except socket.error, e:
+ print 'Error connecting to socket: %s' % e
except:
- print('Error creating test channel (check argument).')
+ print 'Error creating test channel (check argument).'
else:
test_channel_shell = TestChannelShell(test_channel)
test_channel_shell.prompt = '$ '
- test_channel_shell.cmdloop('Welcome to the RootCanal Console \n' + 'Type \'help\' for more information.')
+ test_channel_shell.cmdloop('Welcome to the RootCanal Console \n' +
+ 'Type \'help\' for more information.')
if __name__ == '__main__':
diff --git a/vendor_libs/test_vendor_lib/test/async_manager_unittest.cc b/vendor_libs/test_vendor_lib/test/async_manager_unittest.cc
index b15c2c6d2..fe2b95ad5 100644
--- a/vendor_libs/test_vendor_lib/test/async_manager_unittest.cc
+++ b/vendor_libs/test_vendor_lib/test/async_manager_unittest.cc
@@ -15,11 +15,11 @@
*/
#include "model/setup/async_manager.h"
-
#include <gtest/gtest.h>
#include <cstdint>
#include <cstring>
#include <vector>
+
#include <netdb.h>
#include <netinet/in.h>
#include <sys/socket.h>
@@ -68,7 +68,7 @@ class AsyncManagerSocketTest : public ::testing::Test {
void ReadIncomingMessage(int fd) {
int n = TEMP_FAILURE_RETRY(read(fd, server_buffer_, kBufferSize - 1));
- ASSERT_FALSE(n < 0);
+ EXPECT_FALSE(n < 0);
if (n == 0) { // got EOF
async_manager_.StopWatchingFileDescriptor(fd);
@@ -93,7 +93,7 @@ class AsyncManagerSocketTest : public ::testing::Test {
void TearDown() override {
async_manager_.StopWatchingFileDescriptor(socket_fd_);
close(socket_fd_);
- ASSERT_TRUE(CheckBufferEquals());
+ EXPECT_TRUE(CheckBufferEquals());
}
int ConnectClient() {
@@ -119,12 +119,12 @@ class AsyncManagerSocketTest : public ::testing::Test {
void WriteFromClient(int socket_cli_fd) {
strcpy(client_buffer_, "1");
int n = write(socket_cli_fd, client_buffer_, strlen(client_buffer_));
- ASSERT_TRUE(n > 0);
+ EXPECT_TRUE(n > 0);
}
void AwaitServerResponse(int socket_cli_fd) {
int n = read(socket_cli_fd, client_buffer_, 1);
- ASSERT_TRUE(n > 0);
+ EXPECT_TRUE(n > 0);
}
private:
@@ -145,7 +145,7 @@ TEST_F(AsyncManagerSocketTest, TestOneConnection) {
}
TEST_F(AsyncManagerSocketTest, TestRepeatedConnections) {
- static const int num_connections = 30;
+ static const int num_connections = 300;
for (int i = 0; i < num_connections; i++) {
int socket_cli_fd = ConnectClient();
WriteFromClient(socket_cli_fd);
@@ -155,7 +155,7 @@ TEST_F(AsyncManagerSocketTest, TestRepeatedConnections) {
}
TEST_F(AsyncManagerSocketTest, TestMultipleConnections) {
- static const int num_connections = 30;
+ static const int num_connections = 300;
int socket_cli_fd[num_connections];
for (int i = 0; i < num_connections; i++) {
socket_cli_fd[i] = ConnectClient();
@@ -168,87 +168,4 @@ TEST_F(AsyncManagerSocketTest, TestMultipleConnections) {
}
}
-class AsyncManagerTest : public ::testing::Test {
- public:
- AsyncManager async_manager_;
-};
-
-TEST_F(AsyncManagerTest, TestSetupTeardown) {}
-
-TEST_F(AsyncManagerTest, TestCancelTask) {
- AsyncUserId user1 = async_manager_.GetNextUserId();
- bool task1_ran = false;
- bool* task1_ran_ptr = &task1_ran;
- AsyncTaskId task1_id =
- async_manager_.ExecAsync(user1, std::chrono::milliseconds(2),
- [task1_ran_ptr]() { *task1_ran_ptr = true; });
- ASSERT_TRUE(async_manager_.CancelAsyncTask(task1_id));
- ASSERT_FALSE(task1_ran);
-}
-
-TEST_F(AsyncManagerTest, TestCancelLongTask) {
- AsyncUserId user1 = async_manager_.GetNextUserId();
- bool task1_ran = false;
- bool* task1_ran_ptr = &task1_ran;
- AsyncTaskId task1_id =
- async_manager_.ExecAsync(user1, std::chrono::milliseconds(2),
- [task1_ran_ptr]() { *task1_ran_ptr = true; });
- bool task2_ran = false;
- bool* task2_ran_ptr = &task2_ran;
- AsyncTaskId task2_id =
- async_manager_.ExecAsync(user1, std::chrono::seconds(2),
- [task2_ran_ptr]() { *task2_ran_ptr = true; });
- ASSERT_FALSE(task1_ran);
- ASSERT_FALSE(task2_ran);
- while (!task1_ran)
- ;
- ASSERT_FALSE(async_manager_.CancelAsyncTask(task1_id));
- ASSERT_FALSE(task2_ran);
- ASSERT_TRUE(async_manager_.CancelAsyncTask(task2_id));
-}
-
-TEST_F(AsyncManagerTest, TestCancelAsyncTasksFromUser) {
- AsyncUserId user1 = async_manager_.GetNextUserId();
- AsyncUserId user2 = async_manager_.GetNextUserId();
- bool task1_ran = false;
- bool* task1_ran_ptr = &task1_ran;
- bool task2_ran = false;
- bool* task2_ran_ptr = &task2_ran;
- bool task3_ran = false;
- bool* task3_ran_ptr = &task3_ran;
- bool task4_ran = false;
- bool* task4_ran_ptr = &task4_ran;
- bool task5_ran = false;
- bool* task5_ran_ptr = &task5_ran;
- AsyncTaskId task1_id =
- async_manager_.ExecAsync(user1, std::chrono::milliseconds(2),
- [task1_ran_ptr]() { *task1_ran_ptr = true; });
- AsyncTaskId task2_id =
- async_manager_.ExecAsync(user1, std::chrono::seconds(2),
- [task2_ran_ptr]() { *task2_ran_ptr = true; });
- AsyncTaskId task3_id =
- async_manager_.ExecAsync(user1, std::chrono::milliseconds(2),
- [task3_ran_ptr]() { *task3_ran_ptr = true; });
- AsyncTaskId task4_id =
- async_manager_.ExecAsync(user1, std::chrono::seconds(2),
- [task4_ran_ptr]() { *task4_ran_ptr = true; });
- AsyncTaskId task5_id =
- async_manager_.ExecAsync(user2, std::chrono::milliseconds(2),
- [task5_ran_ptr]() { *task5_ran_ptr = true; });
- ASSERT_FALSE(task1_ran);
- while (!task1_ran || !task3_ran || !task5_ran)
- ;
- ASSERT_TRUE(task1_ran);
- ASSERT_FALSE(task2_ran);
- ASSERT_TRUE(task3_ran);
- ASSERT_FALSE(task4_ran);
- ASSERT_TRUE(task5_ran);
- async_manager_.CancelAsyncTasksFromUser(user1);
- ASSERT_FALSE(async_manager_.CancelAsyncTask(task1_id));
- ASSERT_FALSE(async_manager_.CancelAsyncTask(task2_id));
- ASSERT_FALSE(async_manager_.CancelAsyncTask(task3_id));
- ASSERT_FALSE(async_manager_.CancelAsyncTask(task4_id));
- ASSERT_FALSE(async_manager_.CancelAsyncTask(task5_id));
-}
-
} // namespace test_vendor_lib
diff --git a/vendor_libs/test_vendor_lib/types/Android.bp b/vendor_libs/test_vendor_lib/types/Android.bp
index 028538ac5..7e1193c48 100644
--- a/vendor_libs/test_vendor_lib/types/Android.bp
+++ b/vendor_libs/test_vendor_lib/types/Android.bp
@@ -1,13 +1,4 @@
// Bluetooth types
-package {
- // See: http://go/android-license-faq
- // A large-scale-change added 'default_applicable_licenses' to import
- // all of the 'license_kinds' from "system_bt_license"
- // to get the below license kinds:
- // SPDX-license-identifier-Apache-2.0
- default_applicable_licenses: ["system_bt_license"],
-}
-
cc_library_headers {
name: "libbt-rootcanal-types-header",
export_include_dirs: ["./"],
diff --git a/vendor_libs/test_vendor_lib/types/BUILD.gn b/vendor_libs/test_vendor_lib/types/BUILD.gn
index f5f7e1e7c..68f76e3c5 100644
--- a/vendor_libs/test_vendor_lib/types/BUILD.gn
+++ b/vendor_libs/test_vendor_lib/types/BUILD.gn
@@ -26,40 +26,37 @@ static_library("types") {
]
include_dirs = [
- "//bt",
+ "//",
]
- configs += [
- "//bt:target_defaults",
+ deps = [
+ "//third_party/libchrome:base",
]
}
-if (use.test) {
- executable("types_unittests") {
- sources = [
- "test/address_unittest.cc",
- "test/bluetooth/uuid_unittest.cc",
- ]
-
- include_dirs = [
- "//bt",
- ]
+executable("types_unittests") {
+ testonly = true
+ sources = [
+ "test/address_unittest.cc",
+ "test/bluetooth/uuid_unittest.cc",
+ ]
- libs = [
- "dl",
- "pthread",
- "resolv",
- "rt",
- "z",
- ]
+ include_dirs = [
+ "//",
+ ]
- deps = [
- "//bt/types",
- ]
+ libs = [
+ "-ldl",
+ "-lpthread",
+ "-lresolv",
+ "-lrt",
+ "-lz",
+ "-latomic",
+ ]
- configs += [
- "//bt:external_gmock_main",
- "//bt:target_defaults",
- ]
- }
+ deps = [
+ "//types",
+ "//third_party/googletest:gmock_main",
+ "//third_party/libchrome:base",
+ ]
}